001package org.hl7.fhir.utilities.xhtml;
002
003/*
004  Copyright (c) 2011+, HL7, Inc.
005  All rights reserved.
006
007  Redistribution and use in source and binary forms, with or without modification, 
008  are permitted provided that the following conditions are met:
009
010 * Redistributions of source code must retain the above copyright notice, this 
011     list of conditions and the following disclaimer.
012 * Redistributions in binary form must reproduce the above copyright notice, 
013     this list of conditions and the following disclaimer in the documentation 
014     and/or other materials provided with the distribution.
015 * Neither the name of HL7 nor the names of its contributors may be used to 
016     endorse or promote products derived from this software without specific 
017     prior written permission.
018
019  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND 
020  ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED 
021  WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. 
022  IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, 
023  INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT 
024  NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR 
025  PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, 
026  WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) 
027  ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE 
028  POSSIBILITY OF SUCH DAMAGE.
029
030 */
031
032
033
034import java.io.IOException;
035import java.io.InputStream;
036import java.io.InputStreamReader;
037import java.io.Reader;
038import java.io.StringReader;
039import java.nio.charset.StandardCharsets;
040import java.util.ArrayList;
041import java.util.HashMap;
042import java.util.HashSet;
043import java.util.List;
044import java.util.Map;
045import java.util.Set;
046
047import org.hl7.fhir.exceptions.FHIRException;
048import org.hl7.fhir.exceptions.FHIRFormatError;
049import org.hl7.fhir.utilities.xhtml.XhtmlNode.Location;
050import org.w3c.dom.Attr;
051import org.w3c.dom.Element;
052import org.w3c.dom.Node;
053import org.xmlpull.v1.XmlPullParser;
054import org.xmlpull.v1.XmlPullParserException;
055
056public class XhtmlParser {
057  public static final String XHTML_NS = "http://www.w3.org/1999/xhtml";
058  private static final char END_OF_CHARS = (char) -1;
059
060  public class NSMap {
061    private Map<String, String> nslist = new HashMap<String, String>();
062
063    public NSMap(NSMap nsm) {
064      if (nsm != null)
065        nslist.putAll(nsm.nslist);
066    }
067
068    public void def(String ns) {
069      nslist.put("", ns);
070    }
071
072    public void ns(String abbrev, String ns) {
073      nslist.put(abbrev, ns);  
074    }
075
076    public String def() {
077      return nslist.get("");
078    }
079
080    public boolean hasDef() {
081      return nslist.containsKey("");
082    }
083
084    public String get(String abbrev) {
085      return nslist.containsKey(abbrev) ? nslist.get(abbrev) : "http://error/undefined-namespace";
086    }
087  }
088
089  public class QName {
090    private String ns;
091    private String name;
092
093    public QName(String src) {
094      if (src.contains(":")) {
095        ns = src.substring(0, src.indexOf(":"));
096        name = src.substring(src.indexOf(":")+1);
097      } else {
098        ns = null;
099        name = src;
100      }
101    }
102
103    public String getName() {
104      return name;
105    }
106
107    public boolean hasNs() {
108      return ns != null;
109    }
110
111    public String getNs() {
112      return ns;
113    }
114
115    @Override
116    public String toString() {
117      return ns+"::"+name;
118    }
119
120  }
121
122  private Set<String> elements = new HashSet<String>();
123  private Set<String> attributes = new HashSet<String>();  
124  private Map<String, String> entities = new HashMap<>();
125
126
127  public XhtmlParser() {
128    super();
129    policy = ParserSecurityPolicy.Accept; // for general parsing
130
131    // set up sets
132    elements.add("p");
133    elements.add("br");
134    elements.add("div");
135    elements.add("h1");
136    elements.add("h2");
137    elements.add("h3");
138    elements.add("h4");
139    elements.add("h5");
140    elements.add("h6");
141    elements.add("a");
142    elements.add("span");
143    elements.add("b");
144    elements.add("em");
145    elements.add("i");
146    elements.add("strong");
147    elements.add("small");
148    elements.add("big");
149    elements.add("tt");
150    elements.add("small");
151    elements.add("dfn");
152    elements.add("q");
153    elements.add("var");
154    elements.add("abbr");
155    elements.add("acronym");
156    elements.add("cite");
157    elements.add("blockquote");
158    elements.add("hr");
159    elements.add("address");
160    elements.add("bdo");
161    elements.add("kbd");
162    elements.add("q");
163    elements.add("sub");
164    elements.add("sup");
165    elements.add("ul");
166    elements.add("ol");
167    elements.add("li");
168    elements.add("dl");
169    elements.add("dt");
170    elements.add("dd");
171    elements.add("pre");
172    elements.add("table");
173    elements.add("caption");
174    elements.add("colgroup");
175    elements.add("col");
176    elements.add("thead");
177    elements.add("tr");
178    elements.add("tfoot");
179    elements.add("tbody");
180    elements.add("th");
181    elements.add("td");
182    elements.add("code");
183    elements.add("samp");
184    elements.add("img");
185    elements.add("map");
186    elements.add("area");
187
188    attributes.add("title");
189    attributes.add("style");
190    attributes.add("class");
191    attributes.add("id");
192    attributes.add("lang");
193    attributes.add("xml:lang");
194    attributes.add("dir");
195    attributes.add("accesskey");
196    attributes.add("tabindex");
197    // tables:
198    attributes.add("span");
199    attributes.add("width");
200    attributes.add("align");
201    attributes.add("valign");
202    attributes.add("char");
203    attributes.add("charoff");
204    attributes.add("abbr");
205    attributes.add("axis");
206    attributes.add("headers");
207    attributes.add("scope");
208    attributes.add("rowspan");
209    attributes.add("colspan");
210
211    attributes.add("a.href");
212    attributes.add("a.name");
213    attributes.add("img.src");
214    attributes.add("img.border");
215    attributes.add("div.xmlns");
216    attributes.add("blockquote.cite");
217    attributes.add("q.cite");
218    attributes.add("a.charset");
219    attributes.add("a.type");
220    attributes.add("a.name");
221    attributes.add("a.href");
222    attributes.add("a.hreflang");
223    attributes.add("a.rel");
224    attributes.add("a.rev");
225    attributes.add("a.shape");
226    attributes.add("a.coords");
227    attributes.add("img.src");
228    attributes.add("img.alt");
229    attributes.add("img.longdesc");
230    attributes.add("img.height");
231    attributes.add("img.width");
232    attributes.add("img.usemap");
233    attributes.add("img.ismap");
234    attributes.add("map.name");
235    attributes.add("area.shape");
236    attributes.add("area.coords");
237    attributes.add("area.href");
238    attributes.add("area.nohref");
239    attributes.add("area.alt");
240    attributes.add("table.summary");
241    attributes.add("table.width");
242    attributes.add("table.border");
243    attributes.add("table.frame");
244    attributes.add("table.rules");
245    attributes.add("table.cellspacing");
246    attributes.add("table.cellpadding");
247
248    defineEntities();
249  }
250
251  public enum ParserSecurityPolicy {
252    Accept,
253    Drop,
254    Reject
255  }
256
257  private ParserSecurityPolicy policy;
258
259  private boolean trimWhitespace;
260  private boolean mustBeWellFormed = true;
261  private boolean validatorMode;
262
263  public boolean isTrimWhitespace() {
264    return trimWhitespace;
265  }
266
267  public void setTrimWhitespace(boolean trimWhitespace) {
268    this.trimWhitespace = trimWhitespace;
269  }
270
271  public boolean isMustBeWellFormed() {
272    return mustBeWellFormed;
273  }
274
275  public XhtmlParser setMustBeWellFormed(boolean mustBeWellFormed) {
276    this.mustBeWellFormed = mustBeWellFormed;
277    return this;
278  }
279
280
281  public boolean isValidatorMode() {
282    return validatorMode;
283  }
284
285  public XhtmlParser setValidatorMode(boolean validatorMode) {
286    this.validatorMode = validatorMode;
287    return this;
288  }
289
290  public ParserSecurityPolicy getPolicy() {
291    return policy;
292  }
293
294  public void setPolicy(ParserSecurityPolicy policy) {
295    this.policy = policy; 
296  }
297
298  public XhtmlNode parseHtmlNode(Element node) throws FHIRFormatError  {
299    return parseHtmlNode(node, null);
300  }
301
302  public XhtmlNode parseHtmlNode(Element node, String defaultNS) throws FHIRFormatError  {
303    XhtmlNode res = parseNode(node, defaultNS);
304    if (res.getNsDecl() == null)
305      res.getAttributes().put("xmlns", XHTML_NS);
306    return res;
307  }
308
309  private XhtmlNode parseNode(Element node, String defaultNS) throws FHIRFormatError  {
310    XhtmlNode res = new XhtmlNode(NodeType.Element);
311    res.setName(node.getLocalName());
312    defaultNS = checkNS(res, node, defaultNS);
313    for (int i = 0; i < node.getAttributes().getLength(); i++) {
314      Attr attr = (Attr) node.getAttributes().item(i);
315      if (attributeIsOk(res.getName(), attr.getName(), attr.getValue()) && !attr.getLocalName().startsWith("xmlns"))
316        res.getAttributes().put(attr.getName(), attr.getValue());
317    }
318    Node child = node.getFirstChild();
319    while (child != null) {
320      if (child.getNodeType() == Node.TEXT_NODE) {
321        res.addText(child.getTextContent());
322      } else if (child.getNodeType() == Node.COMMENT_NODE) {
323        res.addComment(child.getTextContent());
324      } else if (child.getNodeType() == Node.ELEMENT_NODE) {
325        if (elementIsOk(child.getLocalName()))
326          res.getChildNodes().add(parseNode((Element) child, defaultNS));
327      } else
328        throw new FHIRFormatError("Unhandled XHTML feature: "+Integer.toString(child.getNodeType())+descLoc());
329      child = child.getNextSibling();
330    }
331    return res;
332  }  
333
334  private String checkNS(XhtmlNode res, Element node, String defaultNS) {
335    if (!validatorMode)
336      return null;
337    String ns = node.getNamespaceURI();
338    if (ns == null)
339      return null;
340    if (!ns.equals(defaultNS)) {
341      res.getAttributes().put("xmlns", ns);
342      return ns;
343    }
344    return defaultNS;
345  }
346
347  public XhtmlNode parseHtmlNode(XmlPullParser xpp) throws XmlPullParserException, IOException, FHIRFormatError  {
348    XhtmlNode res = parseNode(xpp);
349    if (res.getNsDecl() == null)
350      res.getAttributes().put("xmlns", XHTML_NS);
351    return res;
352
353  }
354  private XhtmlNode parseNode(XmlPullParser xpp) throws XmlPullParserException, IOException, FHIRFormatError  {
355    XhtmlNode res = new XhtmlNode(NodeType.Element);
356    res.setName(xpp.getName());
357
358    for (int i = 0; i < xpp.getAttributeCount(); i++) {
359      String an = "xml".equals(xpp.getAttributePrefix(i)) ? "xml:"+xpp.getAttributeName(i) : xpp.getAttributeName(i);
360      String av = xpp.getAttributeValue(i);
361      if (attributeIsOk(xpp.getName(), an, av)) {
362        res.getAttributes().put(an, av);
363      }
364    }
365    int eventType = xpp.next();
366    while (eventType != XmlPullParser.END_TAG) {
367      if (eventType == XmlPullParser.TEXT) {
368        res.addText(xpp.getText());
369        xpp.next();
370      } else if (eventType == XmlPullParser.COMMENT) {
371        res.addComment(xpp.getText());
372        xpp.next();
373      } else if (eventType == XmlPullParser.START_TAG) {
374        if (elementIsOk(xpp.getName()))
375          res.getChildNodes().add(parseNode(xpp));
376      } else
377        throw new FHIRFormatError("Unhandled XHTML feature: "+Integer.toString(eventType)+descLoc());
378      eventType = xpp.getEventType();
379    }
380    xpp.next();
381    return res;
382  }  
383
384  private boolean attributeIsOk(String elem, String attr, String value) throws FHIRFormatError  {
385    if (validatorMode)
386      return true;
387    boolean ok = attributes.contains(attr) || attributes.contains(elem+"."+attr);
388    if (ok)
389      return true;
390    else switch (policy) {
391    case Accept: return true;
392    case Drop: return false;
393    case Reject: throw new FHIRFormatError("Illegal HTML attribute "+elem+"."+attr);
394    }
395
396    if ((elem+"."+attr).equals("img.src") && !(value.startsWith("#") || value.startsWith("http:") || value.startsWith("https:"))) {
397      switch (policy) {
398      case Accept: return true;
399      case Drop: return false;
400      case Reject: throw new FHIRFormatError("Illegal Image Reference "+value);
401      }
402    }
403    return false;
404  }
405
406  private boolean elementIsOk(String name) throws FHIRFormatError  {
407    if (validatorMode)
408      return true;
409    boolean ok = elements.contains(name);
410    if (ok)
411      return true;
412    else switch (policy) {
413    case Accept: return true;
414    case Drop: return false;
415    case Reject: throw new FHIRFormatError("Illegal HTML element "+name);
416    }
417    return false;
418  }
419
420  private String descLoc() {
421    return " at line "+Integer.toString(line)+" column "+Integer.toString(col);
422  }
423
424  private Reader rdr;
425  private String cache = "";
426  private XhtmlNode unwindPoint;
427  private String lastText = "";
428  private int line = 1;
429  private int col = 0;
430  private char lastChar;
431  private Location lastLoc;
432
433  public XhtmlDocument parse(String source, String entryName) throws FHIRFormatError, IOException  {
434    rdr = new StringReader(source);
435    return parse(entryName);
436  }
437
438  public XhtmlDocument parse(InputStream input, String entryName) throws FHIRFormatError, IOException  {
439    rdr = new InputStreamReader(input, StandardCharsets.UTF_8);
440    return parse(entryName);
441  }
442
443  private XhtmlDocument parse(String entryName) throws FHIRFormatError, IOException 
444  {
445    XhtmlDocument result = new XhtmlDocument();
446    skipWhiteSpaceAndComments(result);
447    if (peekChar() != '<')
448      throw new FHIRFormatError("Unable to Parse HTML - does not start with tag. Found "+peekChar()+descLoc());
449    readChar();
450    markLocation();
451    QName n = new QName(readName().toLowerCase());
452    if ((entryName != null) && !n.getName().equals(entryName))
453      throw new FHIRFormatError("Unable to Parse HTML - starts with '"+n+"' not '"+entryName+"'"+descLoc());
454    XhtmlNode root = result.addTag(n.getName());
455    root.setLocation(markLocation());
456    parseAttributes(root);
457    markLocation();
458    NSMap nsm = checkNamespaces(n, root, null, true);
459    if (readChar() == '/') {
460      if (peekChar() != '>')
461        throw new FHIRFormatError("unexpected non-end of element "+n+" "+descLoc());
462      readChar();
463    } else {
464      unwindPoint = null;
465      List<XhtmlNode> p = new ArrayList<>();
466      parseElementInner(root, p, nsm, true);
467    }
468    return result;
469  }
470
471  private Location markLocation() {
472    Location res = lastLoc;
473    lastLoc = new Location(line, col);
474    return res;
475  }
476
477  private NSMap checkNamespaces(QName n, XhtmlNode node, NSMap nsm, boolean root) {
478    // what we do here is strip out any stated namespace attributes, putting them in the namesapce map
479    // then we figure out what the namespace of this element is, and state it explicitly if it's not the default
480
481    NSMap result = new NSMap(nsm);
482    List<String> nsattrs = new ArrayList<String>();
483    for (String an : node.getAttributes().keySet()) {
484      if (an.equals("xmlns")) {
485        result.def(node.getAttribute(an));
486        nsattrs.add(an);
487      }
488      if (an.startsWith("xmlns:")) {
489        result.ns(an.substring(6), node.getAttribute(an));
490        nsattrs.add(an);
491      }
492    }
493    for (String s : nsattrs)
494      node.getAttributes().remove(s);
495    if (n.hasNs()) {
496      String nns = result.get(n.getNs());
497      if (!nns.equals(result.def())) {
498        node.getAttributes().put("xmlns", nns);
499        result.def(nns);
500      }
501    } else if (root && result.hasDef()) {
502      node.getAttributes().put("xmlns", result.def());
503    }
504    return result;
505  }
506
507  private void addTextNode(XhtmlNode node, StringBuilder s)
508  {
509    String t = isTrimWhitespace() ? s.toString().trim() : s.toString();
510    if (t.length() > 0)
511    {
512      lastText = t;
513      // System.out.println(t);
514      node.addText(t).setLocation(markLocation());
515      s.setLength(0);
516    }
517  }
518  private void parseElementInner(XhtmlNode node, List<XhtmlNode> parents, NSMap nsm, boolean escaping) throws FHIRFormatError, IOException 
519  {
520    StringBuilder s = new StringBuilder();
521    while (peekChar() != END_OF_CHARS && !parents.contains(unwindPoint) && !(node == unwindPoint))
522    {
523      if (peekChar() == '<')
524      {
525        addTextNode(node, s);
526        readChar();
527        if (peekChar() == '!') {
528          String sc = readToCommentEnd();
529          // moved the validator
530          //          if (sc.startsWith("DOCTYPE"))
531          //            throw new FHIRFormatError("Malformed XHTML: Found a DocType declaration, and these are not allowed (XXE security vulnerability protection)");
532          node.addComment(sc).setLocation(markLocation());
533        } else if (peekChar() == '?')
534          node.addComment(readToTagEnd()).setLocation(markLocation());
535        else if (peekChar() == '/') {
536          readChar();
537          QName n = new QName(readToTagEnd());
538          if (node.getName().equals(n.getName()))
539            return;
540          else
541          {
542            if (mustBeWellFormed) {
543              throw new FHIRFormatError("Malformed XHTML: Found \"</"+n.getName()+">\" expecting \"</"+node.getName()+">\""+descLoc());
544            }
545            for (int i = parents.size() - 1; i >= 0; i--)
546            {
547              if (parents.get(i).getName().equals(n))
548                unwindPoint = parents.get(i);
549            }
550            if (unwindPoint != null)
551            {
552              for (int i = parents.size(); i > 0; i--)
553              {
554                if (i < parents.size() && parents.get(i) == unwindPoint)
555                  return;
556                if (i == parents.size())
557                {
558                  parents.get(i - 1).getChildNodes().addAll(node.getChildNodes());
559                  node.getChildNodes().clear();
560                }
561                else
562                {
563                  parents.get(i - 1).getChildNodes().addAll(parents.get(i).getChildNodes());
564                  parents.get(i).getChildNodes().clear();
565                }
566              }
567            }
568          }
569        }
570        else if (Character.isLetterOrDigit(peekChar()))
571        {
572          parseElement(node, parents, nsm);
573        }
574        else
575          throw new FHIRFormatError("Unable to Parse HTML - node '" + node.getName() + "' has unexpected content '"+peekChar()+"' (last text = '"+lastText+"'"+descLoc());
576      }
577      else if (peekChar() == '&') // escaping && 
578      {
579        parseLiteral(s);
580      }
581      else
582        s.append(readChar());
583    }
584    addTextNode(node, s);
585  }
586
587  private void parseElement(XhtmlNode parent, List<XhtmlNode> parents, NSMap nsm) throws IOException, FHIRFormatError 
588  {
589    markLocation();
590    QName name = new QName(readName());
591    XhtmlNode node = parent.addTag(name.getName());
592    node.setLocation(markLocation());
593    List<XhtmlNode> newParents = new ArrayList<XhtmlNode>();
594    newParents.addAll(parents);
595    newParents.add(parent);
596    parseAttributes(node);
597    markLocation();
598    nsm = checkNamespaces(name, node, nsm, false);
599    if (readChar() == '/') {
600      if (peekChar() != '>')
601        throw new FHIRFormatError("unexpected non-end of element "+name+" "+descLoc());
602      readChar();
603    } else {
604      parseElementInner(node, newParents, nsm, "script".equals(name.getName()));
605    }
606  }
607
608  private void parseAttributes(XhtmlNode node) throws FHIRFormatError, IOException 
609  {
610    while (Character.isWhitespace(peekChar()))
611      readChar();
612    while (peekChar() != '>' && peekChar() != '/' && peekChar() != END_OF_CHARS)
613    {
614      String name = readName();
615      if (name.length() == 0)
616      {
617        throw new FHIRFormatError("Unable to read attribute on <"+node.getName()+">"+descLoc());
618      }
619      while (Character.isWhitespace(peekChar()))
620        readChar();
621
622      if (isNameChar(peekChar()) || peekChar() == '>' || peekChar() == '/')
623        node.getAttributes().put(name, null);
624      else if (peekChar() != '=')
625      {
626        throw new FHIRFormatError("Unable to read attribute '"+name+"' value on <"+node.getName()+">"+descLoc());
627      }
628      else
629      {
630        readChar();
631        while (Character.isWhitespace(peekChar()))
632          readChar();
633        if (peekChar() == '"' || peekChar() == '\'')
634          node.getAttributes().put(name, parseAttributeValue(readChar()));
635        else
636          node.getAttributes().put(name, parseAttributeValue(END_OF_CHARS));
637      }
638      while (Character.isWhitespace(peekChar()))
639        readChar();
640    }
641  }
642
643  private String parseAttributeValue(char term) throws IOException, FHIRFormatError 
644  {
645    StringBuilder b = new StringBuilder();
646    while (peekChar() != END_OF_CHARS && peekChar() != '>' && (term != END_OF_CHARS || peekChar() != '/') && peekChar() != term)
647    {
648      if (peekChar() == '&')
649      {
650        parseLiteral(b);
651      }
652      else
653        b.append(readChar());
654    }
655    if (peekChar() == term)
656      readChar();
657    return b.toString();
658  }
659
660
661  private void skipWhiteSpaceAndComments(XhtmlNode focus) throws IOException, FHIRFormatError  {
662    while (Character.isWhitespace(peekChar()) || (peekChar() == 0xfeff))
663      readChar();
664    if (peekChar() == '<')
665    {
666      char ch = readChar();
667      if (peekChar() == '!') {
668        readChar();
669        if (peekChar() == '-') {
670          readChar();
671          if (peekChar() == '-') {
672            readChar();
673            if (peekChar() == ' ')
674              readChar();
675            focus.addComment(readToCommentEnd());
676          } else 
677            throw new FHIRFormatError("unrecognised element type <!"+peekChar()+descLoc());
678        } else
679          focus.addDocType(readToDocTypeEnd());
680        skipWhiteSpaceAndComments(focus);
681      } else if (peekChar() == '?') {
682        String r = readToTagEnd();
683        focus.addInstruction(r.substring(1, r.length()-1));
684        skipWhiteSpaceAndComments(focus);
685      } else 
686        pushChar(ch);
687    }
688  }  
689
690  private void skipWhiteSpace() throws IOException {
691    if (trimWhitespace)
692      while (Character.isWhitespace(peekChar()) || (peekChar() == 0xfeff))
693        readChar();
694  }
695
696  private void skipWhiteSpaceInternal() throws IOException {
697    while (Character.isWhitespace(peekChar()) || (peekChar() == 0xfeff))
698      readChar();
699  }
700
701  private void pushChar(char ch) {
702    cache = Character.toString(ch)+cache;    
703  }
704
705  private char peekChar() throws IOException
706  {
707    if (cache.length() > 0)
708      return cache.charAt(0);
709    else if (!rdr.ready())
710      return END_OF_CHARS;
711    else
712    {
713      int i = rdr.read();
714      if (i == -1)       {
715        cache = "";
716        return END_OF_CHARS;
717      }
718      char c = (char) i;
719      cache =  Character.toString(c);
720      return c;
721    }
722  }
723
724  private char readChar() throws IOException
725  {
726    char c;
727    if (cache.length() > 0)
728    {
729      c = cache.charAt(0);
730      cache = cache.length() == 1 ? "" : cache.substring(1);
731    }
732    else if (!rdr.ready())
733      c = END_OF_CHARS;
734    else
735      c = (char)rdr.read();
736    if (c == '\r' || c == '\n') {
737      if (c == '\r' || lastChar != '\r') {
738        line++;
739        col = 0;
740      }  
741      lastChar = c;      
742    }      
743    col++;
744    return c;
745  }
746
747  private String readToTagEnd() throws IOException, FHIRFormatError 
748  {
749    StringBuilder s = new StringBuilder();
750    while (peekChar() != '>' && peekChar() != END_OF_CHARS)
751      s.append(readChar());
752    if (peekChar() != END_OF_CHARS)
753    {
754      readChar();
755      skipWhiteSpace();
756    } else if (mustBeWellFormed)
757      throw new FHIRFormatError("Unexpected termination of html source"+descLoc());
758    return s.toString();
759  }
760
761  private String readToDocTypeEnd() throws IOException, FHIRFormatError 
762  {
763    StringBuilder s = new StringBuilder();
764
765    boolean done = false;
766    while (!done) {
767      char c = peekChar();
768      if (c == '>') {
769        done = true;
770        readChar();
771      } else if (c != END_OF_CHARS)
772        s.append(readChar());
773      else if (mustBeWellFormed)
774        throw new FHIRFormatError("Unexpected termination of html source"+descLoc());
775    }
776    return s.toString();
777  }
778
779  private String readToCommentEnd() throws IOException, FHIRFormatError 
780  {
781    if (peekChar() == '!')
782      readChar();
783    StringBuilder s = new StringBuilder();
784
785    boolean simple = true;
786    if (peekChar() == '-') {
787      readChar();
788      simple = peekChar() != '-';
789      if (simple)
790        s.append('-');
791      else
792        readChar();
793    }
794
795    boolean doctypeEntities = false;
796
797    boolean done = false;
798    while (!done) {
799      char c = peekChar();
800      if (c == '-') {
801        readChar();
802        if (peekChar() == '-') {
803          readChar();
804          if (peekChar() == '>') {
805            done = true;
806          } else
807            s.append("--");
808        } else 
809          s.append('-');
810      } else if (doctypeEntities && c == ']') {
811        s.append(readChar());
812        if (peekChar() == '>') {
813          done = true;
814        }
815      } else if (simple && peekChar() == '>' && !doctypeEntities) {
816        done = true;
817      } else if (c == '[' && s.toString().startsWith("DOCTYPE ")) {
818        doctypeEntities = true;
819        s.append(readChar());
820      } else if (c != END_OF_CHARS)
821        s.append(readChar());
822      else if (mustBeWellFormed)
823        throw new FHIRFormatError("Unexpected termination of html source"+descLoc());
824    }
825    if (peekChar() != END_OF_CHARS)
826    {
827      readChar();
828      skipWhiteSpace();
829    }
830    if (doctypeEntities) {
831      parseDoctypeEntities(s.toString());
832    }
833    return s.toString();
834  }
835
836  private void parseDoctypeEntities(String s) {
837    while (s.contains("<!ENTITY")) {
838      s = s.substring(s.indexOf("<!ENTITY"));
839      int e = s.indexOf(">");
840      String ed = s.substring(0, e+1);
841      s = s.substring(e+1);
842      ed = ed.substring(8).trim();
843      e = ed.indexOf(" ");
844      String n = ed.substring(0, e).trim();
845      ed = ed.substring(e).trim();
846      e = ed.indexOf(" "); // SYSTEM
847      ed = ed.substring(e).trim();
848      String v = ed.substring(0, ed.length()-1);
849      entities.put(n, v);
850    }
851
852  }
853
854  private boolean isNameChar(char ch)
855  {
856    return Character.isLetterOrDigit(ch) || ch == '_' || ch == '-' || ch == ':';
857  }
858
859  private String readName() throws IOException
860  {
861    StringBuilder s = new StringBuilder();
862    while (isNameChar(peekChar()))
863      s.append(readChar());
864    return s.toString();
865  }
866
867  private String readUntil(char ch) throws IOException
868  {
869    StringBuilder s = new StringBuilder();
870    while (peekChar() != 0 && peekChar() != ch)
871      s.append(readChar());
872    readChar();
873    return s.toString();
874  }
875
876
877  private String readUntil(String sc) throws IOException
878  {
879    StringBuilder s = new StringBuilder();
880    while (peekChar() != 0 && sc.indexOf(peekChar()) == -1)
881      s.append(readChar());
882    readChar();
883    return s.toString();
884  }
885
886  private void parseLiteral(StringBuilder s) throws IOException, FHIRFormatError {
887    // UInt16 w;
888    readChar();
889    String c = readUntil(";&'\"><");
890    if (c.isEmpty())
891      throw new FHIRFormatError("Invalid literal declaration following text: " + s);
892    else if (c.charAt(0) == '#') {
893      if (isInteger(c.substring(1), 10))
894        s.append((char) Integer.parseInt(c.substring(1)));
895      else if (c.charAt(1) == 'x' && isInteger(c.substring(2), 16))
896        s.append((char) Integer.parseInt(c.substring(2), 16));
897    } else if (entities.containsKey(c)) {
898      s.append(entities.get(c));
899      // what's going on here? 
900      // the contents that follow already existed, and then I added the routine to populate the entities 
901      // which was generated from other code. The code that follows is probably redundant, but I haven't
902      // cross checked it. some is welcome to do so... (GG 8-Nov 2021)
903    } else if (c.equals("apos"))
904      s.append('\'');
905    else if (c.equals("quot"))
906      s.append('"');
907    else if (c.equals("nbsp"))
908      s.append(XhtmlNode.NBSP);
909    else if (c.equals("amp"))
910      s.append('&');
911    else if (c.equals("lsquo"))
912      s.append((char) 8216); // right single quotation, U+2019 ISOnum 
913    else if (c.equals("rsquo"))
914      s.append((char) 8217); // right single quotation, U+2019 ISOnum 
915    else if (c.equals("gt"))
916      s.append('>');
917    else if (c.equals("lt"))
918      s.append('<');
919    else if (c.equals("copy"))
920      s.append((char) 169);
921    else if (c.equals("reg"))
922      s.append((char) 174);
923    else if (c.equals("sect"))
924      s.append((char) 0xA7);
925    else if (c.equals("fnof"))
926      s.append((char) 402); // latin small f with hook = function = florin, U+0192 ISOtech -->
927    else if (c.equals("Alpha"))
928      s.append((char) 913); // greek capital letter alpha, U+0391
929    else if (c.equals("Beta"))
930      s.append((char) 914); // greek capital letter beta, U+0392
931    else if (c.equals("Gamma"))
932      s.append((char) 915); // greek capital letter gamma, U+0393 ISOgrk3
933    else if (c.equals("Delta"))
934      s.append((char) 916); // greek capital letter delta, U+0394 ISOgrk3
935    else if (c.equals("Epsilon"))
936      s.append((char) 917); // greek capital letter epsilon, U+0395
937    else if (c.equals("Zeta"))
938      s.append((char) 918); // greek capital letter zeta, U+0396
939    else if (c.equals("Eta"))
940      s.append((char) 919); // greek capital letter eta, U+0397
941    else if (c.equals("Theta"))
942      s.append((char) 920); // greek capital letter theta, U+0398 ISOgrk3
943    else if (c.equals("Iota"))
944      s.append((char) 921); // greek capital letter iota, U+0399
945    else if (c.equals("Kappa"))
946      s.append((char) 922); // greek capital letter kappa, U+039A
947    else if (c.equals("Lambda"))
948      s.append((char) 923); // greek capital letter lambda, U+039B ISOgrk3
949    else if (c.equals("Mu"))
950      s.append((char) 924); // greek capital letter mu, U+039C
951    else if (c.equals("Nu"))
952      s.append((char) 925); // greek capital letter nu, U+039D
953    else if (c.equals("Xi"))
954      s.append((char) 926); // greek capital letter xi, U+039E ISOgrk3
955    else if (c.equals("Omicron"))
956      s.append((char) 927); // greek capital letter omicron, U+039F
957    else if (c.equals("Pi"))
958      s.append((char) 928); // greek capital letter pi, U+03A0 ISOgrk3
959    else if (c.equals("Rho"))
960      s.append((char) 929); // greek capital letter rho, U+03A1
961    else if (c.equals("Sigma"))
962      s.append((char) 931); // greek capital letter sigma, U+03A3 ISOgrk3
963    else if (c.equals("Tau"))
964      s.append((char) 932); // greek capital letter tau, U+03A4
965    else if (c.equals("Upsilon"))
966      s.append((char) 933); // greek capital letter upsilon, U+03A5 ISOgrk3
967    else if (c.equals("Phi"))
968      s.append((char) 934); // greek capital letter phi, U+03A6 ISOgrk3
969    else if (c.equals("Chi"))
970      s.append((char) 935); // greek capital letter chi, U+03A7
971    else if (c.equals("Psi"))
972      s.append((char) 936); // greek capital letter psi, U+03A8 ISOgrk3
973    else if (c.equals("Omega"))
974      s.append((char) 937); // greek capital letter omega, U+03A9 ISOgrk3
975    else if (c.equals("alpha"))
976      s.append((char) 945); // greek small letter alpha, U+03B1 ISOgrk3
977    else if (c.equals("beta"))
978      s.append((char) 946); // greek small letter beta, U+03B2 ISOgrk3
979    else if (c.equals("gamma"))
980      s.append((char) 947); // greek small letter gamma, U+03B3 ISOgrk3
981    else if (c.equals("delta"))
982      s.append((char) 948); // greek small letter delta, U+03B4 ISOgrk3
983    else if (c.equals("epsilon"))
984      s.append((char) 949); // greek small letter epsilon, U+03B5 ISOgrk3
985    else if (c.equals("zeta"))
986      s.append((char) 950); // greek small letter zeta, U+03B6 ISOgrk3
987    else if (c.equals("eta"))
988      s.append((char) 951); // greek small letter eta, U+03B7 ISOgrk3
989    else if (c.equals("theta"))
990      s.append((char) 952); // greek small letter theta, U+03B8 ISOgrk3
991    else if (c.equals("iota"))
992      s.append((char) 953); // greek small letter iota, U+03B9 ISOgrk3
993    else if (c.equals("kappa"))
994      s.append((char) 954); // greek small letter kappa, U+03BA ISOgrk3
995    else if (c.equals("lambda"))
996      s.append((char) 955); // greek small letter lambda, U+03BB ISOgrk3
997    else if (c.equals("mu"))
998      s.append((char) 956); // greek small letter mu, U+03BC ISOgrk3
999    else if (c.equals("nu"))
1000      s.append((char) 957); // greek small letter nu, U+03BD ISOgrk3
1001    else if (c.equals("xi"))
1002      s.append((char) 958); // greek small letter xi, U+03BE ISOgrk3
1003    else if (c.equals("omicron"))
1004      s.append((char) 959); // greek small letter omicron, U+03BF NEW
1005    else if (c.equals("pi"))
1006      s.append((char) 960); // greek small letter pi, U+03C0 ISOgrk3
1007    else if (c.equals("rho"))
1008      s.append((char) 961); // greek small letter rho, U+03C1 ISOgrk3
1009    else if (c.equals("sigmaf"))
1010      s.append((char) 962); // greek small letter final sigma, U+03C2 ISOgrk3
1011    else if (c.equals("sigma"))
1012      s.append((char) 963); // greek small letter sigma, U+03C3 ISOgrk3
1013    else if (c.equals("tau"))
1014      s.append((char) 964); // greek small letter tau, U+03C4 ISOgrk3
1015    else if (c.equals("upsilon"))
1016      s.append((char) 965); // greek small letter upsilon, U+03C5 ISOgrk3
1017    else if (c.equals("phi"))
1018      s.append((char) 966); // greek small letter phi, U+03C6 ISOgrk3
1019    else if (c.equals("chi"))
1020      s.append((char) 967); // greek small letter chi, U+03C7 ISOgrk3
1021    else if (c.equals("psi"))
1022      s.append((char) 968); // greek small letter psi, U+03C8 ISOgrk3
1023    else if (c.equals("omega"))
1024      s.append((char) 969); // greek small letter omega, U+03C9 ISOgrk3
1025    else if (c.equals("thetasym"))
1026      s.append((char) 977); // greek small letter theta symbol, U+03D1 NEW
1027    else if (c.equals("upsih"))
1028      s.append((char) 978); // greek upsilon with hook symbol, U+03D2 NEW
1029    else if (c.equals("piv"))
1030      s.append((char) 982); // greek pi symbol, U+03D6 ISOgrk3
1031    else if (c.equals("bull"))
1032      s.append((char) 8226); // bullet = black small circle, U+2022 ISOpub
1033    else if (c.equals("hellip"))
1034      s.append((char) 8230); // horizontal ellipsis = three dot leader, U+2026 ISOpub
1035    else if (c.equals("prime"))
1036      s.append((char) 8242); // prime = minutes = feet, U+2032 ISOtech
1037    else if (c.equals("Prime"))
1038      s.append((char) 8243); // double prime = seconds = inches, U+2033 ISOtech
1039    else if (c.equals("oline"))
1040      s.append((char) 8254); // overline = spacing overscore, U+203E NEW
1041    else if (c.equals("frasl"))
1042      s.append((char) 8260); // fraction slash, U+2044 NEW
1043    else if (c.equals("weierp"))
1044      s.append((char) 8472); // script capital P = power set = Weierstrass p, U+2118 ISOamso
1045    else if (c.equals("image"))
1046      s.append((char) 8465); // blackletter capital I = imaginary part, U+2111 ISOamso
1047    else if (c.equals("real"))
1048      s.append((char) 8476); // blackletter capital R = real part symbol, U+211C ISOamso
1049    else if (c.equals("trade"))
1050      s.append((char) 8482); // trade mark sign, U+2122 ISOnum
1051    else if (c.equals("alefsym"))
1052      s.append((char) 8501); // alef symbol = first transfinite cardinal, U+2135 NEW
1053    else if (c.equals("larr"))
1054      s.append((char) 8592); // leftwards arrow, U+2190 ISOnum
1055    else if (c.equals("uarr"))
1056      s.append((char) 8593); // upwards arrow, U+2191 ISOnum
1057    else if (c.equals("rarr"))
1058      s.append((char) 8594); // rightwards arrow, U+2192 ISOnum
1059    else if (c.equals("darr"))
1060      s.append((char) 8595); // downwards arrow, U+2193 ISOnum
1061    else if (c.equals("harr"))
1062      s.append((char) 8596); // left right arrow, U+2194 ISOamsa
1063    else if (c.equals("crarr"))
1064      s.append((char) 8629); // downwards arrow with corner leftwards = carriage return, U+21B5 NEW
1065    else if (c.equals("lArr"))
1066      s.append((char) 8656); // leftwards double arrow, U+21D0 ISOtech
1067    else if (c.equals("uArr"))
1068      s.append((char) 8657); // upwards double arrow, U+21D1 ISOamsa
1069    else if (c.equals("rArr"))
1070      s.append((char) 8658); // rightwards double arrow, U+21D2 ISOtech
1071    else if (c.equals("dArr"))
1072      s.append((char) 8659); // downwards double arrow, U+21D3 ISOamsa
1073    else if (c.equals("hArr"))
1074      s.append((char) 8660); // left right double arrow, U+21D4 ISOamsa
1075    else if (c.equals("forall"))
1076      s.append((char) 8704); // for all, U+2200 ISOtech
1077    else if (c.equals("part"))
1078      s.append((char) 8706); // partial differential, U+2202 ISOtech
1079    else if (c.equals("exist"))
1080      s.append((char) 8707); // there exists, U+2203 ISOtech
1081    else if (c.equals("empty"))
1082      s.append((char) 8709); // empty set = null set = diameter, U+2205 ISOamso
1083    else if (c.equals("nabla"))
1084      s.append((char) 8711); // nabla = backward difference, U+2207 ISOtech
1085    else if (c.equals("isin"))
1086      s.append((char) 8712); // element of, U+2208 ISOtech
1087    else if (c.equals("notin"))
1088      s.append((char) 8713); // not an element of, U+2209 ISOtech
1089    else if (c.equals("ni"))
1090      s.append((char) 8715); // contains as member, U+220B ISOtech
1091    else if (c.equals("prod"))
1092      s.append((char) 8719); // n-ary product = product sign, U+220F ISOamsb
1093    else if (c.equals("sum"))
1094      s.append((char) 8721); // n-ary sumation, U+2211 ISOamsb
1095    else if (c.equals("minus"))
1096      s.append((char) 8722); // minus sign, U+2212 ISOtech
1097    else if (c.equals("lowast"))
1098      s.append((char) 8727); // asterisk operator, U+2217 ISOtech
1099    else if (c.equals("radic"))
1100      s.append((char) 8730); // square root = radical sign, U+221A ISOtech
1101    else if (c.equals("prop"))
1102      s.append((char) 8733); // proportional to, U+221D ISOtech
1103    else if (c.equals("infin"))
1104      s.append((char) 8734); // infinity, U+221E ISOtech -->
1105    else if (c.equals("ang"))
1106      s.append((char) 8736); // angle, U+2220 ISOamso
1107    else if (c.equals("and"))
1108      s.append((char) 8743); // logical and = wedge, U+2227 ISOtech
1109    else if (c.equals("or"))
1110      s.append((char) 8744); // logical or = vee, U+2228 ISOtech
1111    else if (c.equals("cap"))
1112      s.append((char) 8745); // intersection = cap, U+2229 ISOtech
1113    else if (c.equals("cup"))
1114      s.append((char) 8746); // union = cup, U+222A ISOtech
1115    else if (c.equals("int"))
1116      s.append((char) 8747); // integral, U+222B ISOtech
1117    else if (c.equals("there4"))
1118      s.append((char) 8756); // therefore, U+2234 ISOtech
1119    else if (c.equals("sim"))
1120      s.append((char) 8764); // tilde operator = varies with = similar t U+223C ISOtech
1121    else if (c.equals("cong"))
1122      s.append((char) 8773); // approximately equal to, U+2245 ISOtec
1123    else if (c.equals("asymp"))
1124      s.append((char) 8776); // almost equal to = asymptotic to, U+2248 ISOamsr
1125    else if (c.equals("ne"))
1126      s.append((char) 8800); // not equal to, U+2260 ISOtech
1127    else if (c.equals("equiv"))
1128      s.append((char) 8801); // identical to, U+2261 ISOtech
1129    else if (c.equals("le"))
1130      s.append((char) 8804); // less-than or equal to, U+2264 ISOtech
1131    else if (c.equals("ge"))
1132      s.append((char) 8805); // greater-than or equal to, U+2265 ISOtech
1133    else if (c.equals("sub"))
1134      s.append((char) 8834); // subset of, U+2282 ISOtech
1135    else if (c.equals("sup"))
1136      s.append((char) 8835); // superset of, U+2283 ISOtech
1137    else if (c.equals("nsub"))
1138      s.append((char) 8836); // not a subset of, U+2284 ISOamsn
1139    else if (c.equals("sube"))
1140      s.append((char) 8838); // subset of or equal to, U+2286 ISOtech
1141    else if (c.equals("supe"))
1142      s.append((char) 8839); // superset of or equal to, U+2287 ISOtech
1143    else if (c.equals("oplus"))
1144      s.append((char) 8853); // circled plus = direct sum, U+2295 ISOamsb
1145    else if (c.equals("otimes"))
1146      s.append((char) 8855); // circled times = vector product, U+2297 ISOamsb -->
1147    else if (c.equals("perp"))
1148      s.append((char) 8869); // up tack = orthogonal to = perpendicular, U+22A5 ISOtech
1149    else if (c.equals("sdot"))
1150      s.append((char) 8901); // dot operator, U+22C5 ISOamsb
1151    else if (c.equals("lceil"))
1152      s.append((char) 8968); // left ceiling = apl upstile, U+2308 ISOamsc
1153    else if (c.equals("rceil"))
1154      s.append((char) 8969); // right ceiling, U+2309 ISOamsc
1155    else if (c.equals("lfloor"))
1156      s.append((char) 8970); // left floor = apl downstile, U+230A ISOamsc
1157    else if (c.equals("rfloor"))
1158      s.append((char) 8971); // right floor, U+230B ISOamsc
1159    else if (c.equals("lang"))
1160      s.append((char) 9001); // left-pointing angle bracket = bra, U+2329 ISOtech
1161    else if (c.equals("rang"))
1162      s.append((char) 9002); // right-pointing angle bracket = ket, U+232A ISOtech
1163    else if (c.equals("loz"))
1164      s.append((char) 9674); // lozenge, U+25CA ISOpub
1165    else if (c.equals("spades"))
1166      s.append((char) 9824); // black spade suit, U+2660 ISOpub
1167    else if (c.equals("clubs"))
1168      s.append((char) 9827); // black club suit = shamrock, U+2663 ISOpub
1169    else if (c.equals("hearts"))
1170      s.append((char) 9829); // black heart suit = valentine, U+2665 ISOpub
1171    else if (c.equals("diams"))
1172      s.append((char) 9830); // black diamond suit, U+2666 ISOpub --
1173    else if (c.equals("ndash"))
1174      s.append((char) 8211); 
1175    else if (c.equals("mdash"))
1176      s.append((char) 8212); 
1177    else if (c.equals("ldquo"))
1178      s.append((char) 8221); 
1179    else if (c.equals("rdquo"))
1180      s.append((char) 201D); 
1181    else if (c.equals("frac14"))
1182      s.append((char) 188); 
1183    else if (!mustBeWellFormed) {
1184      // we guess that this is an accidentally unescaped &
1185      s.append("&"+c);
1186    } else {
1187      throw new FHIRFormatError("unable to parse character reference '" + c + "'' (last text = '" + lastText + "'" + descLoc());
1188    }
1189  }
1190
1191  private boolean isInteger(String s, int base) {
1192    try {
1193      Integer.parseInt(s, base);
1194      return true;
1195    } catch (Exception e) {
1196      return false;
1197    }
1198  }
1199
1200  public XhtmlNode parseFragment(String source) throws IOException, FHIRException  {
1201    rdr = new StringReader(source);
1202    return parseFragment();
1203  }
1204
1205  public XhtmlNode parseFragment(InputStream input) throws IOException, FHIRException  {
1206    rdr = new InputStreamReader(input);
1207    return parseFragment();
1208  }
1209
1210  private XhtmlNode parseFragment() throws IOException, FHIRException 
1211  {
1212    skipWhiteSpace();
1213    if (peekChar() != '<')
1214      throw new FHIRException("Unable to Parse HTML - does not start with tag. Found "+peekChar()+descLoc());
1215    readChar();
1216    if (peekChar() == '?') {
1217      readToTagEnd();
1218      skipWhiteSpaceInternal();
1219      if (peekChar() != '<')
1220        throw new FHIRException("Unable to Parse HTML - does not start with tag after processing instruction. Found "+peekChar()+descLoc());
1221      readChar();
1222    }
1223    String n = readName().toLowerCase();
1224    readToTagEnd();
1225    XhtmlNode result = new XhtmlNode(NodeType.Element);
1226
1227    int colonIndex = n.indexOf(':');
1228    if (colonIndex != -1) {
1229      n = n.substring(colonIndex + 1);
1230    }
1231
1232    result.setName(n);
1233    unwindPoint = null;
1234    List<XhtmlNode> p = new ArrayList<>();
1235    parseElementInner(result, p, null, true);
1236
1237    return result;
1238  }
1239
1240  private void defineEntities() {
1241    entities.put("&AElig;", "\u00C6");
1242    entities.put("&AMP;", "\u0026");
1243    entities.put("&Aacute;", "\u00C1");
1244    entities.put("&Abreve;", "\u0102");
1245    entities.put("&Acirc;", "\u00C2");
1246    entities.put("&Acy;", "\u0410");
1247    entities.put("&Afr;", "\uD835\uDD04");
1248    entities.put("&Agrave;", "\u00C0");
1249    entities.put("&Alpha;", "\u0391");
1250    entities.put("&Amacr;", "\u0100");
1251    entities.put("&And;", "\u2A53");
1252    entities.put("&Aogon;", "\u0104");
1253    entities.put("&Aopf;", "\uD835\uDD38");
1254    entities.put("&ApplyFunction;", "\u2061");
1255    entities.put("&Aring;", "\u00C5");
1256    entities.put("&Ascr;", "\uD835\uDC9C");
1257    entities.put("&Assign;", "\u2254");
1258    entities.put("&Atilde;", "\u00C3");
1259    entities.put("&Auml;", "\u00C4");
1260    entities.put("&Backslash;", "\u2216");
1261    entities.put("&Barv;", "\u2AE7");
1262    entities.put("&Barwed;", "\u2306");
1263    entities.put("&Bcy;", "\u0411");
1264    entities.put("&Because;", "\u2235");
1265    entities.put("&Bernoullis;", "\u212C");
1266    entities.put("&Beta;", "\u0392");
1267    entities.put("&Bfr;", "\uD835\uDD05");
1268    entities.put("&Bopf;", "\uD835\uDD39");
1269    entities.put("&Breve;", "\u02D8");
1270    entities.put("&Bscr;", "\u212C");
1271    entities.put("&Bumpeq;", "\u224E");
1272    entities.put("&CHcy;", "\u0427");
1273    entities.put("&COPY;", "\u00A9");
1274    entities.put("&Cacute;", "\u0106");
1275    entities.put("&Cap;", "\u22D2");
1276    entities.put("&CapitalDifferentialD;", "\u2145");
1277    entities.put("&Cayleys;", "\u212D");
1278    entities.put("&Ccaron;", "\u010C");
1279    entities.put("&Ccedil;", "\u00C7");
1280    entities.put("&Ccirc;", "\u0108");
1281    entities.put("&Cconint;", "\u2230");
1282    entities.put("&Cdot;", "\u010A");
1283    entities.put("&Cedilla;", "\u00B8");
1284    entities.put("&CenterDot;", "\u00B7");
1285    entities.put("&Cfr;", "\u212D");
1286    entities.put("&Chi;", "\u03A7");
1287    entities.put("&CircleDot;", "\u2299");
1288    entities.put("&CircleMinus;", "\u2296");
1289    entities.put("&CirclePlus;", "\u2295");
1290    entities.put("&CircleTimes;", "\u2297");
1291    entities.put("&ClockwiseContourIntegral;", "\u2232");
1292    entities.put("&CloseCurlyDoubleQuote;", "\u201D");
1293    entities.put("&CloseCurlyQuote;", "\u2019");
1294    entities.put("&Colon;", "\u2237");
1295    entities.put("&Colone;", "\u2A74");
1296    entities.put("&Congruent;", "\u2261");
1297    entities.put("&Conint;", "\u222F");
1298    entities.put("&ContourIntegral;", "\u222E");
1299    entities.put("&Copf;", "\u2102");
1300    entities.put("&Coproduct;", "\u2210");
1301    entities.put("&CounterClockwiseContourIntegral;", "\u2233");
1302    entities.put("&Cross;", "\u2A2F");
1303    entities.put("&Cscr;", "\uD835\uDC9E");
1304    entities.put("&Cup;", "\u22D3");
1305    entities.put("&CupCap;", "\u224D");
1306    entities.put("&DD;", "\u2145");
1307    entities.put("&DDotrahd;", "\u2911");
1308    entities.put("&DJcy;", "\u0402");
1309    entities.put("&DScy;", "\u0405");
1310    entities.put("&DZcy;", "\u040F");
1311    entities.put("&Dagger;", "\u2021");
1312    entities.put("&Darr;", "\u21A1");
1313    entities.put("&Dashv;", "\u2AE4");
1314    entities.put("&Dcaron;", "\u010E");
1315    entities.put("&Dcy;", "\u0414");
1316    entities.put("&Del;", "\u2207");
1317    entities.put("&Delta;", "\u0394");
1318    entities.put("&Dfr;", "\uD835\uDD07");
1319    entities.put("&DiacriticalAcute;", "\u00B4");
1320    entities.put("&DiacriticalDot;", "\u02D9");
1321    entities.put("&DiacriticalDoubleAcute;", "\u02DD");
1322    entities.put("&DiacriticalGrave;", "\u0060");
1323    entities.put("&DiacriticalTilde;", "\u02DC");
1324    entities.put("&Diamond;", "\u22C4");
1325    entities.put("&DifferentialD;", "\u2146");
1326    entities.put("&Dopf;", "\uD835\uDD3B");
1327    entities.put("&Dot;", "\u00A8");
1328    entities.put("&DotDot;", "\u20DC");
1329    entities.put("&DotEqual;", "\u2250");
1330    entities.put("&DoubleContourIntegral;", "\u222F");
1331    entities.put("&DoubleDot;", "\u00A8");
1332    entities.put("&DoubleDownArrow;", "\u21D3");
1333    entities.put("&DoubleLeftArrow;", "\u21D0");
1334    entities.put("&DoubleLeftRightArrow;", "\u21D4");
1335    entities.put("&DoubleLeftTee;", "\u2AE4");
1336    entities.put("&DoubleLongLeftArrow;", "\u27F8");
1337    entities.put("&DoubleLongLeftRightArrow;", "\u27FA");
1338    entities.put("&DoubleLongRightArrow;", "\u27F9");
1339    entities.put("&DoubleRightArrow;", "\u21D2");
1340    entities.put("&DoubleRightTee;", "\u22A8");
1341    entities.put("&DoubleUpArrow;", "\u21D1");
1342    entities.put("&DoubleUpDownArrow;", "\u21D5");
1343    entities.put("&DoubleVerticalBar;", "\u2225");
1344    entities.put("&DownArrow;", "\u2193");
1345    entities.put("&DownArrowBar;", "\u2913");
1346    entities.put("&DownArrowUpArrow;", "\u21F5");
1347    entities.put("&DownBreve;", "\u0311");
1348    entities.put("&DownLeftRightVector;", "\u2950");
1349    entities.put("&DownLeftTeeVector;", "\u295E");
1350    entities.put("&DownLeftVector;", "\u21BD");
1351    entities.put("&DownLeftVectorBar;", "\u2956");
1352    entities.put("&DownRightTeeVector;", "\u295F");
1353    entities.put("&DownRightVector;", "\u21C1");
1354    entities.put("&DownRightVectorBar;", "\u2957");
1355    entities.put("&DownTee;", "\u22A4");
1356    entities.put("&DownTeeArrow;", "\u21A7");
1357    entities.put("&Downarrow;", "\u21D3");
1358    entities.put("&Dscr;", "\uD835\uDC9F");
1359    entities.put("&Dstrok;", "\u0110");
1360    entities.put("&ENG;", "\u014A");
1361    entities.put("&ETH;", "\u00D0");
1362    entities.put("&Eacute;", "\u00C9");
1363    entities.put("&Ecaron;", "\u011A");
1364    entities.put("&Ecirc;", "\u00CA");
1365    entities.put("&Ecy;", "\u042D");
1366    entities.put("&Edot;", "\u0116");
1367    entities.put("&Efr;", "\uD835\uDD08");
1368    entities.put("&Egrave;", "\u00C8");
1369    entities.put("&Element;", "\u2208");
1370    entities.put("&Emacr;", "\u0112");
1371    entities.put("&EmptySmallSquare;", "\u25FB");
1372    entities.put("&EmptyVerySmallSquare;", "\u25AB");
1373    entities.put("&Eogon;", "\u0118");
1374    entities.put("&Eopf;", "\uD835\uDD3C");
1375    entities.put("&Epsilon;", "\u0395");
1376    entities.put("&Equal;", "\u2A75");
1377    entities.put("&EqualTilde;", "\u2242");
1378    entities.put("&Equilibrium;", "\u21CC");
1379    entities.put("&Escr;", "\u2130");
1380    entities.put("&Esim;", "\u2A73");
1381    entities.put("&Eta;", "\u0397");
1382    entities.put("&Euml;", "\u00CB");
1383    entities.put("&Exists;", "\u2203");
1384    entities.put("&ExponentialE;", "\u2147");
1385    entities.put("&Fcy;", "\u0424");
1386    entities.put("&Ffr;", "\uD835\uDD09");
1387    entities.put("&FilledSmallSquare;", "\u25FC");
1388    entities.put("&FilledVerySmallSquare;", "\u25AA");
1389    entities.put("&Fopf;", "\uD835\uDD3D");
1390    entities.put("&ForAll;", "\u2200");
1391    entities.put("&Fouriertrf;", "\u2131");
1392    entities.put("&Fscr;", "\u2131");
1393    entities.put("&GJcy;", "\u0403");
1394    entities.put("&GT;", "\u003E");
1395    entities.put("&Gamma;", "\u0393");
1396    entities.put("&Gammad;", "\u03DC");
1397    entities.put("&Gbreve;", "\u011E");
1398    entities.put("&Gcedil;", "\u0122");
1399    entities.put("&Gcirc;", "\u011C");
1400    entities.put("&Gcy;", "\u0413");
1401    entities.put("&Gdot;", "\u0120");
1402    entities.put("&Gfr;", "\uD835\uDD0A");
1403    entities.put("&Gg;", "\u22D9");
1404    entities.put("&Gopf;", "\uD835\uDD3E");
1405    entities.put("&GreaterEqual;", "\u2265");
1406    entities.put("&GreaterEqualLess;", "\u22DB");
1407    entities.put("&GreaterFullEqual;", "\u2267");
1408    entities.put("&GreaterGreater;", "\u2AA2");
1409    entities.put("&GreaterLess;", "\u2277");
1410    entities.put("&GreaterSlantEqual;", "\u2A7E");
1411    entities.put("&GreaterTilde;", "\u2273");
1412    entities.put("&Gscr;", "\uD835\uDCA2");
1413    entities.put("&Gt;", "\u226B");
1414    entities.put("&HARDcy;", "\u042A");
1415    entities.put("&Hacek;", "\u02C7");
1416    entities.put("&Hat;", "\u005E");
1417    entities.put("&Hcirc;", "\u0124");
1418    entities.put("&Hfr;", "\u210C");
1419    entities.put("&HilbertSpace;", "\u210B");
1420    entities.put("&Hopf;", "\u210D");
1421    entities.put("&HorizontalLine;", "\u2500");
1422    entities.put("&Hscr;", "\u210B");
1423    entities.put("&Hstrok;", "\u0126");
1424    entities.put("&HumpDownHump;", "\u224E");
1425    entities.put("&HumpEqual;", "\u224F");
1426    entities.put("&IEcy;", "\u0415");
1427    entities.put("&IJlig;", "\u0132");
1428    entities.put("&IOcy;", "\u0401");
1429    entities.put("&Iacute;", "\u00CD");
1430    entities.put("&Icirc;", "\u00CE");
1431    entities.put("&Icy;", "\u0418");
1432    entities.put("&Idot;", "\u0130");
1433    entities.put("&Ifr;", "\u2111");
1434    entities.put("&Igrave;", "\u00CC");
1435    entities.put("&Im;", "\u2111");
1436    entities.put("&Imacr;", "\u012A");
1437    entities.put("&ImaginaryI;", "\u2148");
1438    entities.put("&Implies;", "\u21D2");
1439    entities.put("&Int;", "\u222C");
1440    entities.put("&Integral;", "\u222B");
1441    entities.put("&Intersection;", "\u22C2");
1442    entities.put("&InvisibleComma;", "\u2063");
1443    entities.put("&InvisibleTimes;", "\u2062");
1444    entities.put("&Iogon;", "\u012E");
1445    entities.put("&Iopf;", "\uD835\uDD40");
1446    entities.put("&Iota;", "\u0399");
1447    entities.put("&Iscr;", "\u2110");
1448    entities.put("&Itilde;", "\u0128");
1449    entities.put("&Iukcy;", "\u0406");
1450    entities.put("&Iuml;", "\u00CF");
1451    entities.put("&Jcirc;", "\u0134");
1452    entities.put("&Jcy;", "\u0419");
1453    entities.put("&Jfr;", "\uD835\uDD0D");
1454    entities.put("&Jopf;", "\uD835\uDD41");
1455    entities.put("&Jscr;", "\uD835\uDCA5");
1456    entities.put("&Jsercy;", "\u0408");
1457    entities.put("&Jukcy;", "\u0404");
1458    entities.put("&KHcy;", "\u0425");
1459    entities.put("&KJcy;", "\u040C");
1460    entities.put("&Kappa;", "\u039A");
1461    entities.put("&Kcedil;", "\u0136");
1462    entities.put("&Kcy;", "\u041A");
1463    entities.put("&Kfr;", "\uD835\uDD0E");
1464    entities.put("&Kopf;", "\uD835\uDD42");
1465    entities.put("&Kscr;", "\uD835\uDCA6");
1466    entities.put("&LJcy;", "\u0409");
1467    entities.put("&LT;", "\u003C");
1468    entities.put("&Lacute;", "\u0139");
1469    entities.put("&Lambda;", "\u039B");
1470    entities.put("&Lang;", "\u27EA");
1471    entities.put("&Laplacetrf;", "\u2112");
1472    entities.put("&Larr;", "\u219E");
1473    entities.put("&Lcaron;", "\u013D");
1474    entities.put("&Lcedil;", "\u013B");
1475    entities.put("&Lcy;", "\u041B");
1476    entities.put("&LeftAngleBracket;", "\u27E8");
1477    entities.put("&LeftArrow;", "\u2190");
1478    entities.put("&LeftArrowBar;", "\u21E4");
1479    entities.put("&LeftArrowRightArrow;", "\u21C6");
1480    entities.put("&LeftCeiling;", "\u2308");
1481    entities.put("&LeftDoubleBracket;", "\u27E6");
1482    entities.put("&LeftDownTeeVector;", "\u2961");
1483    entities.put("&LeftDownVector;", "\u21C3");
1484    entities.put("&LeftDownVectorBar;", "\u2959");
1485    entities.put("&LeftFloor;", "\u230A");
1486    entities.put("&LeftRightArrow;", "\u2194");
1487    entities.put("&LeftRightVector;", "\u294E");
1488    entities.put("&LeftTee;", "\u22A3");
1489    entities.put("&LeftTeeArrow;", "\u21A4");
1490    entities.put("&LeftTeeVector;", "\u295A");
1491    entities.put("&LeftTriangle;", "\u22B2");
1492    entities.put("&LeftTriangleBar;", "\u29CF");
1493    entities.put("&LeftTriangleEqual;", "\u22B4");
1494    entities.put("&LeftUpDownVector;", "\u2951");
1495    entities.put("&LeftUpTeeVector;", "\u2960");
1496    entities.put("&LeftUpVector;", "\u21BF");
1497    entities.put("&LeftUpVectorBar;", "\u2958");
1498    entities.put("&LeftVector;", "\u21BC");
1499    entities.put("&LeftVectorBar;", "\u2952");
1500    entities.put("&Leftarrow;", "\u21D0");
1501    entities.put("&Leftrightarrow;", "\u21D4");
1502    entities.put("&LessEqualGreater;", "\u22DA");
1503    entities.put("&LessFullEqual;", "\u2266");
1504    entities.put("&LessGreater;", "\u2276");
1505    entities.put("&LessLess;", "\u2AA1");
1506    entities.put("&LessSlantEqual;", "\u2A7D");
1507    entities.put("&LessTilde;", "\u2272");
1508    entities.put("&Lfr;", "\uD835\uDD0F");
1509    entities.put("&Ll;", "\u22D8");
1510    entities.put("&Lleftarrow;", "\u21DA");
1511    entities.put("&Lmidot;", "\u013F");
1512    entities.put("&LongLeftArrow;", "\u27F5");
1513    entities.put("&LongLeftRightArrow;", "\u27F7");
1514    entities.put("&LongRightArrow;", "\u27F6");
1515    entities.put("&Longleftarrow;", "\u27F8");
1516    entities.put("&Longleftrightarrow;", "\u27FA");
1517    entities.put("&Longrightarrow;", "\u27F9");
1518    entities.put("&Lopf;", "\uD835\uDD43");
1519    entities.put("&LowerLeftArrow;", "\u2199");
1520    entities.put("&LowerRightArrow;", "\u2198");
1521    entities.put("&Lscr;", "\u2112");
1522    entities.put("&Lsh;", "\u21B0");
1523    entities.put("&Lstrok;", "\u0141");
1524    entities.put("&Lt;", "\u226A");
1525    entities.put("&Map;", "\u2905");
1526    entities.put("&Mcy;", "\u041C");
1527    entities.put("&MediumSpace;", "\u205F");
1528    entities.put("&Mellintrf;", "\u2133");
1529    entities.put("&Mfr;", "\uD835\uDD10");
1530    entities.put("&MinusPlus;", "\u2213");
1531    entities.put("&Mopf;", "\uD835\uDD44");
1532    entities.put("&Mscr;", "\u2133");
1533    entities.put("&Mu;", "\u039C");
1534    entities.put("&NJcy;", "\u040A");
1535    entities.put("&Nacute;", "\u0143");
1536    entities.put("&Ncaron;", "\u0147");
1537    entities.put("&Ncedil;", "\u0145");
1538    entities.put("&Ncy;", "\u041D");
1539    entities.put("&NegativeMediumSpace;", "\u200B");
1540    entities.put("&NegativeThickSpace;", "\u200B");
1541    entities.put("&NegativeThinSpace;", "\u200B");
1542    entities.put("&NegativeVeryThinSpace;", "\u200B");
1543    entities.put("&NestedGreaterGreater;", "\u226B");
1544    entities.put("&NestedLessLess;", "\u226A");
1545    entities.put("&NewLine;", "\n");
1546    entities.put("&Nfr;", "\uD835\uDD11");
1547    entities.put("&NoBreak;", "\u2060");
1548    entities.put("&NonBreakingSpace;", "\u00A0");
1549    entities.put("&Nopf;", "\u2115");
1550    entities.put("&Not;", "\u2AEC");
1551    entities.put("&NotCongruent;", "\u2262");
1552    entities.put("&NotCupCap;", "\u226D");
1553    entities.put("&NotDoubleVerticalBar;", "\u2226");
1554    entities.put("&NotElement;", "\u2209");
1555    entities.put("&NotEqual;", "\u2260");
1556    entities.put("&NotEqualTilde;", "\u2242\u0338");
1557    entities.put("&NotExists;", "\u2204");
1558    entities.put("&NotGreater;", "\u226F");
1559    entities.put("&NotGreaterEqual;", "\u2271");
1560    entities.put("&NotGreaterFullEqual;", "\u2267\u0033");
1561    entities.put("&NotGreaterGreater;", "\u226B\u0033");
1562    entities.put("&NotGreaterLess;", "\u2279");
1563    entities.put("&NotGreaterSlantEqual;", "\u2A7E\u0338");
1564    entities.put("&NotGreaterTilde;", "\u2275");
1565    entities.put("&NotHumpDownHump;", "\u224E\u0338");
1566    entities.put("&NotHumpEqual;", "\u224F\u0338");
1567    entities.put("&NotLeftTriangle;", "\u22EA");
1568    entities.put("&NotLeftTriangleBar;", "\u29CF\u0338");
1569    entities.put("&NotLeftTriangleEqual;", "\u22EC");
1570    entities.put("&NotLess;", "\u226E");
1571    entities.put("&NotLessEqual;", "\u2270");
1572    entities.put("&NotLessGreater;", "\u2278");
1573    entities.put("&NotLessLess;", "\u226A\u0338");
1574    entities.put("&NotLessSlantEqual;", "\u2A7D\u0338");
1575    entities.put("&NotLessTilde;", "\u2274");
1576    entities.put("&NotNestedGreaterGreater;", "\u2AA2\u0338");
1577    entities.put("&NotNestedLessLess;", "\u2AA1\u0338");
1578    entities.put("&NotPrecedes;", "\u2280");
1579    entities.put("&NotPrecedesEqual;", "\u2AAF\u0338");
1580    entities.put("&NotPrecedesSlantEqual;", "\u22E0");
1581    entities.put("&NotReverseElement;", "\u220C");
1582    entities.put("&NotRightTriangle;", "\u22EB");
1583    entities.put("&NotRightTriangleBar;", "\u29D0\u0338");
1584    entities.put("&NotRightTriangleEqual;", "\u22ED");
1585    entities.put("&NotSquareSubset;", "\u228F\u0338");
1586    entities.put("&NotSquareSubsetEqual;", "\u22E2");
1587    entities.put("&NotSquareSuperset;", "\u2290\u0338");
1588    entities.put("&NotSquareSupersetEqual;", "\u22E3");
1589    entities.put("&NotSubset;", "\u2282\u20D2");
1590    entities.put("&NotSubsetEqual;", "\u2288");
1591    entities.put("&NotSucceeds;", "\u2281");
1592    entities.put("&NotSucceedsEqual;", "\u2AB0\u0338");
1593    entities.put("&NotSucceedsSlantEqual;", "\u22E1");
1594    entities.put("&NotSucceedsTilde;", "\u227F\u0338");
1595    entities.put("&NotSuperset;", "\u2283\u20D2");
1596    entities.put("&NotSupersetEqual;", "\u2289");
1597    entities.put("&NotTilde;", "\u2241");
1598    entities.put("&NotTildeEqual;", "\u2244");
1599    entities.put("&NotTildeFullEqual;", "\u2247");
1600    entities.put("&NotTildeTilde;", "\u2249");
1601    entities.put("&NotVerticalBar;", "\u2224");
1602    entities.put("&Nscr;", "\uD835\uDCA9");
1603    entities.put("&Ntilde;", "\u00D1");
1604    entities.put("&Nu;", "\u039D");
1605    entities.put("&OElig;", "\u0152");
1606    entities.put("&Oacute;", "\u00D3");
1607    entities.put("&Ocirc;", "\u00D4");
1608    entities.put("&Ocy;", "\u041E");
1609    entities.put("&Odblac;", "\u0150");
1610    entities.put("&Ofr;", "\uD835\uDD12");
1611    entities.put("&Ograve;", "\u00D2");
1612    entities.put("&Omacr;", "\u014C");
1613    entities.put("&Omega;", "\u03A9");
1614    entities.put("&Omicron;", "\u039F");
1615    entities.put("&Oopf;", "\uD835\uDD46");
1616    entities.put("&OpenCurlyDoubleQuote;", "\u201C");
1617    entities.put("&OpenCurlyQuote;", "\u2018");
1618    entities.put("&Or;", "\u2A54");
1619    entities.put("&Oscr;", "\uD835\uDCAA");
1620    entities.put("&Oslash;", "\u00D8");
1621    entities.put("&Otilde;", "\u00D5");
1622    entities.put("&Otimes;", "\u2A37");
1623    entities.put("&Ouml;", "\u00D6");
1624    entities.put("&OverBar;", "\u203E");
1625    entities.put("&OverBrace;", "\u23DE");
1626    entities.put("&OverBracket;", "\u23B4");
1627    entities.put("&OverParenthesis;", "\u23DC");
1628    entities.put("&PartialD;", "\u2202");
1629    entities.put("&Pcy;", "\u041F");
1630    entities.put("&Pfr;", "\uD835\uDD13");
1631    entities.put("&Phi;", "\u03A6");
1632    entities.put("&Pi;", "\u03A0");
1633    entities.put("&PlusMinus;", "\u00B1");
1634    entities.put("&Poincareplane;", "\u210C");
1635    entities.put("&Popf;", "\u2119");
1636    entities.put("&Pr;", "\u2ABB");
1637    entities.put("&Precedes;", "\u227A");
1638    entities.put("&PrecedesEqual;", "\u2AAF");
1639    entities.put("&PrecedesSlantEqual;", "\u227C");
1640    entities.put("&PrecedesTilde;", "\u227E");
1641    entities.put("&Prime;", "\u2033");
1642    entities.put("&Product;", "\u220F");
1643    entities.put("&Proportion;", "\u2237");
1644    entities.put("&Proportional;", "\u221D");
1645    entities.put("&Pscr;", "\uD835\uDCAB");
1646    entities.put("&Psi;", "\u03A8");
1647    entities.put("&QUOT;", "\\u0022");
1648    entities.put("&Qfr;", "\uD835\uDD14");
1649    entities.put("&Qopf;", "\u211A");
1650    entities.put("&Qscr;", "\uD835\uDCAC");
1651    entities.put("&RBarr;", "\u2910");
1652    entities.put("&REG;", "\u00AE");
1653    entities.put("&Racute;", "\u0154");
1654    entities.put("&Rang;", "\u27EB");
1655    entities.put("&Rarr;", "\u21A0");
1656    entities.put("&Rarrtl;", "\u2916");
1657    entities.put("&Rcaron;", "\u0158");
1658    entities.put("&Rcedil;", "\u0156");
1659    entities.put("&Rcy;", "\u0420");
1660    entities.put("&Re;", "\u211C");
1661    entities.put("&ReverseElement;", "\u220B");
1662    entities.put("&ReverseEquilibrium;", "\u21CB");
1663    entities.put("&ReverseUpEquilibrium;", "\u296F");
1664    entities.put("&Rfr;", "\u211C");
1665    entities.put("&Rho;", "\u03A1");
1666    entities.put("&RightAngleBracket;", "\u27E9");
1667    entities.put("&RightArrow;", "\u2192");
1668    entities.put("&RightArrowBar;", "\u21E5");
1669    entities.put("&RightArrowLeftArrow;", "\u21C4");
1670    entities.put("&RightCeiling;", "\u2309");
1671    entities.put("&RightDoubleBracket;", "\u27E7");
1672    entities.put("&RightDownTeeVector;", "\u295D");
1673    entities.put("&RightDownVector;", "\u21C2");
1674    entities.put("&RightDownVectorBar;", "\u2955");
1675    entities.put("&RightFloor;", "\u230B");
1676    entities.put("&RightTee;", "\u22A2");
1677    entities.put("&RightTeeArrow;", "\u21A6");
1678    entities.put("&RightTeeVector;", "\u295B");
1679    entities.put("&RightTriangle;", "\u22B3");
1680    entities.put("&RightTriangleBar;", "\u29D0");
1681    entities.put("&RightTriangleEqual;", "\u22B5");
1682    entities.put("&RightUpDownVector;", "\u294F");
1683    entities.put("&RightUpTeeVector;", "\u295C");
1684    entities.put("&RightUpVector;", "\u21BE");
1685    entities.put("&RightUpVectorBar;", "\u2954");
1686    entities.put("&RightVector;", "\u21C0");
1687    entities.put("&RightVectorBar;", "\u2953");
1688    entities.put("&Rightarrow;", "\u21D2");
1689    entities.put("&Ropf;", "\u211D");
1690    entities.put("&RoundImplies;", "\u2970");
1691    entities.put("&Rrightarrow;", "\u21DB");
1692    entities.put("&Rscr;", "\u211B");
1693    entities.put("&Rsh;", "\u21B1");
1694    entities.put("&RuleDelayed;", "\u29F4");
1695    entities.put("&SHCHcy;", "\u0429");
1696    entities.put("&SHcy;", "\u0428");
1697    entities.put("&SOFTcy;", "\u042C");
1698    entities.put("&Sacute;", "\u015A");
1699    entities.put("&Sc;", "\u2ABC");
1700    entities.put("&Scaron;", "\u0160");
1701    entities.put("&Scedil;", "\u015E");
1702    entities.put("&Scirc;", "\u015C");
1703    entities.put("&Scy;", "\u0421");
1704    entities.put("&Sfr;", "\uD835\uDD16");
1705    entities.put("&ShortDownArrow;", "\u2193");
1706    entities.put("&ShortLeftArrow;", "\u2190");
1707    entities.put("&ShortRightArrow;", "\u2192");
1708    entities.put("&ShortUpArrow;", "\u2191");
1709    entities.put("&Sigma;", "\u03A3");
1710    entities.put("&SmallCircle;", "\u2218");
1711    entities.put("&Sopf;", "\uD835\uDD4A");
1712    entities.put("&Sqrt;", "\u221A");
1713    entities.put("&Square;", "\u25A1");
1714    entities.put("&SquareIntersection;", "\u2293");
1715    entities.put("&SquareSubset;", "\u228F");
1716    entities.put("&SquareSubsetEqual;", "\u2291");
1717    entities.put("&SquareSuperset;", "\u2290");
1718    entities.put("&SquareSupersetEqual;", "\u2292");
1719    entities.put("&SquareUnion;", "\u2294");
1720    entities.put("&Sscr;", "\uD835\uDCAE");
1721    entities.put("&Star;", "\u22C6");
1722    entities.put("&Sub;", "\u22D0");
1723    entities.put("&Subset;", "\u22D0");
1724    entities.put("&SubsetEqual;", "\u2286");
1725    entities.put("&Succeeds;", "\u227B");
1726    entities.put("&SucceedsEqual;", "\u2AB0");
1727    entities.put("&SucceedsSlantEqual;", "\u227D");
1728    entities.put("&SucceedsTilde;", "\u227F");
1729    entities.put("&SuchThat;", "\u220B");
1730    entities.put("&Sum;", "\u2211");
1731    entities.put("&Sup;", "\u22D1");
1732    entities.put("&Superset;", "\u2283");
1733    entities.put("&SupersetEqual;", "\u2287");
1734    entities.put("&Supset;", "\u22D1");
1735    entities.put("&THORN;", "\u00DE");
1736    entities.put("&TRADE;", "\u2122");
1737    entities.put("&TSHcy;", "\u040B");
1738    entities.put("&TScy;", "\u0426");
1739    entities.put("&Tab;", "\u0009");
1740    entities.put("&Tau;", "\u03A4");
1741    entities.put("&Tcaron;", "\u0164");
1742    entities.put("&Tcedil;", "\u0162");
1743    entities.put("&Tcy;", "\u0422");
1744    entities.put("&Tfr;", "\uD835\uDD17");
1745    entities.put("&Therefore;", "\u2234");
1746    entities.put("&Theta;", "\u0398");
1747    entities.put("&ThickSpace;", "\u205F\u200A");
1748    entities.put("&ThinSpace;", "\u2009");
1749    entities.put("&Tilde;", "\u223C");
1750    entities.put("&TildeEqual;", "\u2243");
1751    entities.put("&TildeFullEqual;", "\u2245");
1752    entities.put("&TildeTilde;", "\u2248");
1753    entities.put("&Topf;", "\uD835\uDD4B");
1754    entities.put("&TripleDot;", "\u20DB");
1755    entities.put("&Tscr;", "\uD835\uDCAF");
1756    entities.put("&Tstrok;", "\u0166");
1757    entities.put("&Uacute;", "\u00DA");
1758    entities.put("&Uarr;", "\u219F");
1759    entities.put("&Uarrocir;", "\u2949");
1760    entities.put("&Ubrcy;", "\u040E");
1761    entities.put("&Ubreve;", "\u016C");
1762    entities.put("&Ucirc;", "\u00DB");
1763    entities.put("&Ucy;", "\u0423");
1764    entities.put("&Udblac;", "\u0170");
1765    entities.put("&Ufr;", "\uD835\uDD18");
1766    entities.put("&Ugrave;", "\u00D9");
1767    entities.put("&Umacr;", "\u016A");
1768    entities.put("&UnderBar;", "\u005F");
1769    entities.put("&UnderBrace;", "\u23DF");
1770    entities.put("&UnderBracket;", "\u23B5");
1771    entities.put("&UnderParenthesis;", "\u23DD");
1772    entities.put("&Union;", "\u22C3");
1773    entities.put("&UnionPlus;", "\u228E");
1774    entities.put("&Uogon;", "\u0172");
1775    entities.put("&Uopf;", "\uD835\uDD4C");
1776    entities.put("&UpArrow;", "\u2191");
1777    entities.put("&UpArrowBar;", "\u2912");
1778    entities.put("&UpArrowDownArrow;", "\u21C5");
1779    entities.put("&UpDownArrow;", "\u2195");
1780    entities.put("&UpEquilibrium;", "\u296E");
1781    entities.put("&UpTee;", "\u22A5");
1782    entities.put("&UpTeeArrow;", "\u21A5");
1783    entities.put("&Uparrow;", "\u21D1");
1784    entities.put("&Updownarrow;", "\u21D5");
1785    entities.put("&UpperLeftArrow;", "\u2196");
1786    entities.put("&UpperRightArrow;", "\u2197");
1787    entities.put("&Upsi;", "\u03D2");
1788    entities.put("&Upsilon;", "\u03A5");
1789    entities.put("&Uring;", "\u016E");
1790    entities.put("&Uscr;", "\uD835\uDCB0");
1791    entities.put("&Utilde;", "\u0168");
1792    entities.put("&Uuml;", "\u00DC");
1793    entities.put("&VDash;", "\u22AB");
1794    entities.put("&Vbar;", "\u2AEB");
1795    entities.put("&Vcy;", "\u0412");
1796    entities.put("&Vdash;", "\u22A9");
1797    entities.put("&Vdashl;", "\u2AE6");
1798    entities.put("&Vee;", "\u22C1");
1799    entities.put("&Verbar;", "\u2016");
1800    entities.put("&Vert;", "\u2016");
1801    entities.put("&VerticalBar;", "\u2223");
1802    entities.put("&VerticalLine;", "\u007C");
1803    entities.put("&VerticalSeparator;", "\u2758");
1804    entities.put("&VerticalTilde;", "\u2240");
1805    entities.put("&VeryThinSpace;", "\u200A");
1806    entities.put("&Vfr;", "\uD835\uDD19");
1807    entities.put("&Vopf;", "\uD835\uDD4D");
1808    entities.put("&Vscr;", "\uD835\uDCB1");
1809    entities.put("&Vvdash;", "\u22AA");
1810    entities.put("&Wcirc;", "\u0174");
1811    entities.put("&Wedge;", "\u22C0");
1812    entities.put("&Wfr;", "\uD835\uDD1A");
1813    entities.put("&Wopf;", "\uD835\uDD4E");
1814    entities.put("&Wscr;", "\uD835\uDCB2");
1815    entities.put("&Xfr;", "\uD835\uDD1B");
1816    entities.put("&Xi;", "\u039E");
1817    entities.put("&Xopf;", "\uD835\uDD4F");
1818    entities.put("&Xscr;", "\uD835\uDCB3");
1819    entities.put("&YAcy;", "\u042F");
1820    entities.put("&YIcy;", "\u0407");
1821    entities.put("&YUcy;", "\u042E");
1822    entities.put("&Yacute;", "\u00DD");
1823    entities.put("&Ycirc;", "\u0176");
1824    entities.put("&Ycy;", "\u042B");
1825    entities.put("&Yfr;", "\uD835\uDD1C");
1826    entities.put("&Yopf;", "\uD835\uDD50");
1827    entities.put("&Yscr;", "\uD835\uDCB4");
1828    entities.put("&Yuml;", "\u0178");
1829    entities.put("&ZHcy;", "\u0416");
1830    entities.put("&Zacute;", "\u0179");
1831    entities.put("&Zcaron;", "\u017D");
1832    entities.put("&Zcy;", "\u0417");
1833    entities.put("&Zdot;", "\u017B");
1834    entities.put("&ZeroWidthSpace;", "\u200B");
1835    entities.put("&Zeta;", "\u0396");
1836    entities.put("&Zfr;", "\u2128");
1837    entities.put("&Zopf;", "\u2124");
1838    entities.put("&Zscr;", "\uD835\uDCB5");
1839    entities.put("&aacute;", "\u00E1");
1840    entities.put("&abreve;", "\u0103");
1841    entities.put("&ac;", "\u223E");
1842    entities.put("&acE;", "\u223E\u0333");
1843    entities.put("&acd;", "\u223F");
1844    entities.put("&acirc;", "\u00E2");
1845    entities.put("&acute;", "\u00B4");
1846    entities.put("&acy;", "\u0430");
1847    entities.put("&aelig;", "\u00E6");
1848    entities.put("&af;", "\u2061");
1849    entities.put("&afr;", "\uD835\uDD1E");
1850    entities.put("&agrave;", "\u00E0");
1851    entities.put("&alefsym;", "\u2135");
1852    entities.put("&aleph;", "\u2135");
1853    entities.put("&alpha;", "\u03B1");
1854    entities.put("&amacr;", "\u0101");
1855    entities.put("&amalg;", "\u2A3F");
1856    entities.put("&amp;", "\u0026");
1857    entities.put("&and;", "\u2227");
1858    entities.put("&andand;", "\u2A55");
1859    entities.put("&andd;", "\u2A5C");
1860    entities.put("&andslope;", "\u2A58");
1861    entities.put("&andv;", "\u2A5A");
1862    entities.put("&ang;", "\u2220");
1863    entities.put("&ange;", "\u29A4");
1864    entities.put("&angle;", "\u2220");
1865    entities.put("&angmsd;", "\u2221");
1866    entities.put("&angmsdaa;", "\u29A8");
1867    entities.put("&angmsdab;", "\u29A9");
1868    entities.put("&angmsdac;", "\u29AA");
1869    entities.put("&angmsdad;", "\u29AB");
1870    entities.put("&angmsdae;", "\u29AC");
1871    entities.put("&angmsdaf;", "\u29AD");
1872    entities.put("&angmsdag;", "\u29AE");
1873    entities.put("&angmsdah;", "\u29AF");
1874    entities.put("&angrt;", "\u221F");
1875    entities.put("&angrtvb;", "\u22BE");
1876    entities.put("&angrtvbd;", "\u299D");
1877    entities.put("&angsph;", "\u2222");
1878    entities.put("&angst;", "\u00C5");
1879    entities.put("&angzarr;", "\u237C");
1880    entities.put("&aogon;", "\u0105");
1881    entities.put("&aopf;", "\uD835\uDD52");
1882    entities.put("&ap;", "\u2248");
1883    entities.put("&apE;", "\u2A70");
1884    entities.put("&apacir;", "\u2A6F");
1885    entities.put("&ape;", "\u224A");
1886    entities.put("&apid;", "\u224B");
1887    entities.put("&apos;", "\u0027");
1888    entities.put("&approx;", "\u2248");
1889    entities.put("&approxeq;", "\u224A");
1890    entities.put("&aring;", "\u00E5");
1891    entities.put("&ascr;", "\uD835\uDCB6");
1892    entities.put("&ast;", "\u002A");
1893    entities.put("&asymp;", "\u2248");
1894    entities.put("&asympeq;", "\u224D");
1895    entities.put("&atilde;", "\u00E3");
1896    entities.put("&auml;", "\u00E4");
1897    entities.put("&awconint;", "\u2233");
1898    entities.put("&awint;", "\u2A11");
1899    entities.put("&bNot;", "\u2AED");
1900    entities.put("&backcong;", "\u224C");
1901    entities.put("&backepsilon;", "\u03F6");
1902    entities.put("&backprime;", "\u2035");
1903    entities.put("&backsim;", "\u223D");
1904    entities.put("&backsimeq;", "\u22CD");
1905    entities.put("&barvee;", "\u22BD");
1906    entities.put("&barwed;", "\u2305");
1907    entities.put("&barwedge;", "\u2305");
1908    entities.put("&bbrk;", "\u23B5");
1909    entities.put("&bbrktbrk;", "\u23B6");
1910    entities.put("&bcong;", "\u224C");
1911    entities.put("&bcy;", "\u0431");
1912    entities.put("&bdquo;", "\u201E");
1913    entities.put("&becaus;", "\u2235");
1914    entities.put("&because;", "\u2235");
1915    entities.put("&bemptyv;", "\u29B0");
1916    entities.put("&bepsi;", "\u03F6");
1917    entities.put("&bernou;", "\u212C");
1918    entities.put("&beta;", "\u03B2");
1919    entities.put("&beth;", "\u2136");
1920    entities.put("&between;", "\u226C");
1921    entities.put("&bfr;", "\uD835\uDD1F");
1922    entities.put("&bigcap;", "\u22C2");
1923    entities.put("&bigcirc;", "\u25EF");
1924    entities.put("&bigcup;", "\u22C3");
1925    entities.put("&bigodot;", "\u2A00");
1926    entities.put("&bigoplus;", "\u2A01");
1927    entities.put("&bigotimes;", "\u2A02");
1928    entities.put("&bigsqcup;", "\u2A06");
1929    entities.put("&bigstar;", "\u2605");
1930    entities.put("&bigtriangledown;", "\u25BD");
1931    entities.put("&bigtriangleup;", "\u25B3");
1932    entities.put("&biguplus;", "\u2A04");
1933    entities.put("&bigvee;", "\u22C1");
1934    entities.put("&bigwedge;", "\u22C0");
1935    entities.put("&bkarow;", "\u290D");
1936    entities.put("&blacklozenge;", "\u29EB");
1937    entities.put("&blacksquare;", "\u25AA");
1938    entities.put("&blacktriangle;", "\u25B4");
1939    entities.put("&blacktriangledown;", "\u25BE");
1940    entities.put("&blacktriangleleft;", "\u25C2");
1941    entities.put("&blacktriangleright;", "\u25B8");
1942    entities.put("&blank;", "\u2423");
1943    entities.put("&blk12;", "\u2592");
1944    entities.put("&blk14;", "\u2591");
1945    entities.put("&blk34;", "\u2593");
1946    entities.put("&block;", "\u2588");
1947    entities.put("&bne;", "\u003D\u20E5");
1948    entities.put("&bnequiv;", "\u2261\u20E5");
1949    entities.put("&bnot;", "\u2310");
1950    entities.put("&bopf;", "\uD835\uDD53");
1951    entities.put("&bot;", "\u22A5");
1952    entities.put("&bottom;", "\u22A5");
1953    entities.put("&bowtie;", "\u22C8");
1954    entities.put("&boxDL;", "\u2557");
1955    entities.put("&boxDR;", "\u2554");
1956    entities.put("&boxDl;", "\u2556");
1957    entities.put("&boxDr;", "\u2553");
1958    entities.put("&boxH;", "\u2550");
1959    entities.put("&boxHD;", "\u2566");
1960    entities.put("&boxHU;", "\u2569");
1961    entities.put("&boxHd;", "\u2564");
1962    entities.put("&boxHu;", "\u2567");
1963    entities.put("&boxUL;", "\u255D");
1964    entities.put("&boxUR;", "\u255A");
1965    entities.put("&boxUl;", "\u255C");
1966    entities.put("&boxUr;", "\u2559");
1967    entities.put("&boxV;", "\u2551");
1968    entities.put("&boxVH;", "\u256C");
1969    entities.put("&boxVL;", "\u2563");
1970    entities.put("&boxVR;", "\u2560");
1971    entities.put("&boxVh;", "\u256B");
1972    entities.put("&boxVl;", "\u2562");
1973    entities.put("&boxVr;", "\u255F");
1974    entities.put("&boxbox;", "\u29C9");
1975    entities.put("&boxdL;", "\u2555");
1976    entities.put("&boxdR;", "\u2552");
1977    entities.put("&boxdl;", "\u2510");
1978    entities.put("&boxdr;", "\u250C");
1979    entities.put("&boxh;", "\u2500");
1980    entities.put("&boxhD;", "\u2565");
1981    entities.put("&boxhU;", "\u2568");
1982    entities.put("&boxhd;", "\u252C");
1983    entities.put("&boxhu;", "\u2534");
1984    entities.put("&boxminus;", "\u229F");
1985    entities.put("&boxplus;", "\u229E");
1986    entities.put("&boxtimes;", "\u22A0");
1987    entities.put("&boxuL;", "\u255B");
1988    entities.put("&boxuR;", "\u2558");
1989    entities.put("&boxul;", "\u2518");
1990    entities.put("&boxur;", "\u2514");
1991    entities.put("&boxv;", "\u2502");
1992    entities.put("&boxvH;", "\u256A");
1993    entities.put("&boxvL;", "\u2561");
1994    entities.put("&boxvR;", "\u255E");
1995    entities.put("&boxvh;", "\u253C");
1996    entities.put("&boxvl;", "\u2524");
1997    entities.put("&boxvr;", "\u251C");
1998    entities.put("&bprime;", "\u2035");
1999    entities.put("&breve;", "\u02D8");
2000    entities.put("&brvbar;", "\u00A6");
2001    entities.put("&bscr;", "\uD835\uDCB7");
2002    entities.put("&bsemi;", "\u204F");
2003    entities.put("&bsim;", "\u223D");
2004    entities.put("&bsime;", "\u22CD");
2005    entities.put("&bsol;", "\\u005C");
2006    entities.put("&bsolb;", "\u29C5");
2007    entities.put("&bsolhsub;", "\u27C8");
2008    entities.put("&bull;", "\u2022");
2009    entities.put("&bullet;", "\u2022");
2010    entities.put("&bump;", "\u224E");
2011    entities.put("&bumpE;", "\u2AAE");
2012    entities.put("&bumpe;", "\u224F");
2013    entities.put("&bumpeq;", "\u224F");
2014    entities.put("&cacute;", "\u0107");
2015    entities.put("&cap;", "\u2229");
2016    entities.put("&capand;", "\u2A44");
2017    entities.put("&capbrcup;", "\u2A49");
2018    entities.put("&capcap;", "\u2A4B");
2019    entities.put("&capcup;", "\u2A47");
2020    entities.put("&capdot;", "\u2A40");
2021    entities.put("&caps;", "\u2229\uFE00");
2022    entities.put("&caret;", "\u2041");
2023    entities.put("&caron;", "\u02C7");
2024    entities.put("&ccaps;", "\u2A4D");
2025    entities.put("&ccaron;", "\u010D");
2026    entities.put("&ccedil;", "\u00E7");
2027    entities.put("&ccirc;", "\u0109");
2028    entities.put("&ccups;", "\u2A4C");
2029    entities.put("&ccupssm;", "\u2A50");
2030    entities.put("&cdot;", "\u010B");
2031    entities.put("&cedil;", "\u00B8");
2032    entities.put("&cemptyv;", "\u29B2");
2033    entities.put("&cent;", "\u00A2");
2034    entities.put("&centerdot;", "\u00B7");
2035    entities.put("&cfr;", "\uD835\uDD20");
2036    entities.put("&chcy;", "\u0447");
2037    entities.put("&check;", "\u2713");
2038    entities.put("&checkmark;", "\u2713");
2039    entities.put("&chi;", "\u03C7");
2040    entities.put("&cir;", "\u25CB");
2041    entities.put("&cirE;", "\u29C3");
2042    entities.put("&circ;", "\u02C6");
2043    entities.put("&circeq;", "\u2257");
2044    entities.put("&circlearrowleft;", "\u21BA");
2045    entities.put("&circlearrowright;", "\u21BB");
2046    entities.put("&circledR;", "\u00AE");
2047    entities.put("&circledS;", "\u24C8");
2048    entities.put("&circledast;", "\u229B");
2049    entities.put("&circledcirc;", "\u229A");
2050    entities.put("&circleddash;", "\u229D");
2051    entities.put("&cire;", "\u2257");
2052    entities.put("&cirfnint;", "\u2A10");
2053    entities.put("&cirmid;", "\u2AEF");
2054    entities.put("&cirscir;", "\u29C2");
2055    entities.put("&clubs;", "\u2663");
2056    entities.put("&clubsuit;", "\u2663");
2057    entities.put("&colon;", "\u003A");
2058    entities.put("&colone;", "\u2254");
2059    entities.put("&coloneq;", "\u2254");
2060    entities.put("&comma;", "\u002C");
2061    entities.put("&commat;", "\u0040");
2062    entities.put("&comp;", "\u2201");
2063    entities.put("&compfn;", "\u2218");
2064    entities.put("&complement;", "\u2201");
2065    entities.put("&complexes;", "\u2102");
2066    entities.put("&cong;", "\u2245");
2067    entities.put("&congdot;", "\u2A6D");
2068    entities.put("&conint;", "\u222E");
2069    entities.put("&copf;", "\uD835\uDD54");
2070    entities.put("&coprod;", "\u2210");
2071    entities.put("&copy;", "\u00A9");
2072    entities.put("&copysr;", "\u2117");
2073    entities.put("&crarr;", "\u21B5");
2074    entities.put("&cross;", "\u2717");
2075    entities.put("&cscr;", "\uD835\uDCB8");
2076    entities.put("&csub;", "\u2ACF");
2077    entities.put("&csube;", "\u2AD1");
2078    entities.put("&csup;", "\u2AD0");
2079    entities.put("&csupe;", "\u2AD2");
2080    entities.put("&ctdot;", "\u22EF");
2081    entities.put("&cudarrl;", "\u2938");
2082    entities.put("&cudarrr;", "\u2935");
2083    entities.put("&cuepr;", "\u22DE");
2084    entities.put("&cuesc;", "\u22DF");
2085    entities.put("&cularr;", "\u21B6");
2086    entities.put("&cularrp;", "\u293D");
2087    entities.put("&cup;", "\u222A");
2088    entities.put("&cupbrcap;", "\u2A48");
2089    entities.put("&cupcap;", "\u2A46");
2090    entities.put("&cupcup;", "\u2A4A");
2091    entities.put("&cupdot;", "\u228D");
2092    entities.put("&cupor;", "\u2A45");
2093    entities.put("&cups;", "\u222A\uFE00");
2094    entities.put("&curarr;", "\u21B7");
2095    entities.put("&curarrm;", "\u293C");
2096    entities.put("&curlyeqprec;", "\u22DE");
2097    entities.put("&curlyeqsucc;", "\u22DF");
2098    entities.put("&curlyvee;", "\u22CE");
2099    entities.put("&curlywedge;", "\u22CF");
2100    entities.put("&curren;", "\u00A4");
2101    entities.put("&curvearrowleft;", "\u21B6");
2102    entities.put("&curvearrowright;", "\u21B7");
2103    entities.put("&cuvee;", "\u22CE");
2104    entities.put("&cuwed;", "\u22CF");
2105    entities.put("&cwconint;", "\u2232");
2106    entities.put("&cwint;", "\u2231");
2107    entities.put("&cylcty;", "\u232D");
2108    entities.put("&dArr;", "\u21D3");
2109    entities.put("&dHar;", "\u2965");
2110    entities.put("&dagger;", "\u2020");
2111    entities.put("&daleth;", "\u2138");
2112    entities.put("&darr;", "\u2193");
2113    entities.put("&dash;", "\u2010");
2114    entities.put("&dashv;", "\u22A3");
2115    entities.put("&dbkarow;", "\u290F");
2116    entities.put("&dblac;", "\u02DD");
2117    entities.put("&dcaron;", "\u010F");
2118    entities.put("&dcy;", "\u0434");
2119    entities.put("&dd;", "\u2146");
2120    entities.put("&ddagger;", "\u2021");
2121    entities.put("&ddarr;", "\u21CA");
2122    entities.put("&ddotseq;", "\u2A77");
2123    entities.put("&deg;", "\u00B0");
2124    entities.put("&delta;", "\u03B4");
2125    entities.put("&demptyv;", "\u29B1");
2126    entities.put("&dfisht;", "\u297F");
2127    entities.put("&dfr;", "\uD835\uDD21");
2128    entities.put("&dharl;", "\u21C3");
2129    entities.put("&dharr;", "\u21C2");
2130    entities.put("&diam;", "\u22C4");
2131    entities.put("&diamond;", "\u22C4");
2132    entities.put("&diamondsuit;", "\u2666");
2133    entities.put("&diams;", "\u2666");
2134    entities.put("&die;", "\u00A8");
2135    entities.put("&digamma;", "\u03DD");
2136    entities.put("&disin;", "\u22F2");
2137    entities.put("&div;", "\u00F7");
2138    entities.put("&divide;", "\u00F7");
2139    entities.put("&divideontimes;", "\u22C7");
2140    entities.put("&divonx;", "\u22C7");
2141    entities.put("&djcy;", "\u0452");
2142    entities.put("&dlcorn;", "\u231E");
2143    entities.put("&dlcrop;", "\u230D");
2144    entities.put("&dollar;", "\u0024");
2145    entities.put("&dopf;", "\uD835\uDD55");
2146    entities.put("&dot;", "\u02D9");
2147    entities.put("&doteq;", "\u2250");
2148    entities.put("&doteqdot;", "\u2251");
2149    entities.put("&dotminus;", "\u2238");
2150    entities.put("&dotplus;", "\u2214");
2151    entities.put("&dotsquare;", "\u22A1");
2152    entities.put("&doublebarwedge;", "\u2306");
2153    entities.put("&downarrow;", "\u2193");
2154    entities.put("&downdownarrows;", "\u21CA");
2155    entities.put("&downharpoonleft;", "\u21C3");
2156    entities.put("&downharpoonright;", "\u21C2");
2157    entities.put("&drbkarow;", "\u2910");
2158    entities.put("&drcorn;", "\u231F");
2159    entities.put("&drcrop;", "\u230C");
2160    entities.put("&dscr;", "\uD835\uDCB9");
2161    entities.put("&dscy;", "\u0455");
2162    entities.put("&dsol;", "\u29F6");
2163    entities.put("&dstrok;", "\u0111");
2164    entities.put("&dtdot;", "\u22F1");
2165    entities.put("&dtri;", "\u25BF");
2166    entities.put("&dtrif;", "\u25BE");
2167    entities.put("&duarr;", "\u21F5");
2168    entities.put("&duhar;", "\u296F");
2169    entities.put("&dwangle;", "\u29A6");
2170    entities.put("&dzcy;", "\u045F");
2171    entities.put("&dzigrarr;", "\u27FF");
2172    entities.put("&eDDot;", "\u2A77");
2173    entities.put("&eDot;", "\u2251");
2174    entities.put("&eacute;", "\u00E9");
2175    entities.put("&easter;", "\u2A6E");
2176    entities.put("&ecaron;", "\u011B");
2177    entities.put("&ecir;", "\u2256");
2178    entities.put("&ecirc;", "\u00EA");
2179    entities.put("&ecolon;", "\u2255");
2180    entities.put("&ecy;", "\u044D");
2181    entities.put("&edot;", "\u0117");
2182    entities.put("&ee;", "\u2147");
2183    entities.put("&efDot;", "\u2252");
2184    entities.put("&efr;", "\uD835\uDD22");
2185    entities.put("&eg;", "\u2A9A");
2186    entities.put("&egrave;", "\u00E8");
2187    entities.put("&egs;", "\u2A96");
2188    entities.put("&egsdot;", "\u2A98");
2189    entities.put("&el;", "\u2A99");
2190    entities.put("&elinters;", "\u23E7");
2191    entities.put("&ell;", "\u2113");
2192    entities.put("&els;", "\u2A95");
2193    entities.put("&elsdot;", "\u2A97");
2194    entities.put("&emacr;", "\u0113");
2195    entities.put("&empty;", "\u2205");
2196    entities.put("&emptyset;", "\u2205");
2197    entities.put("&emptyv;", "\u2205");
2198    entities.put("&emsp13;", "\u2004");
2199    entities.put("&emsp14;", "\u2005");
2200    entities.put("&emsp;", "\u2003");
2201    entities.put("&eng;", "\u014B");
2202    entities.put("&ensp;", "\u2002");
2203    entities.put("&eogon;", "\u0119");
2204    entities.put("&eopf;", "\uD835\uDD56");
2205    entities.put("&epar;", "\u22D5");
2206    entities.put("&eparsl;", "\u29E3");
2207    entities.put("&eplus;", "\u2A71");
2208    entities.put("&epsi;", "\u03B5");
2209    entities.put("&epsilon;", "\u03B5");
2210    entities.put("&epsiv;", "\u03F5");
2211    entities.put("&eqcirc;", "\u2256");
2212    entities.put("&eqcolon;", "\u2255");
2213    entities.put("&eqsim;", "\u2242");
2214    entities.put("&eqslantgtr;", "\u2A96");
2215    entities.put("&eqslantless;", "\u2A95");
2216    entities.put("&equals;", "\u003D");
2217    entities.put("&equest;", "\u225F");
2218    entities.put("&equiv;", "\u2261");
2219    entities.put("&equivDD;", "\u2A78");
2220    entities.put("&eqvparsl;", "\u29E5");
2221    entities.put("&erDot;", "\u2253");
2222    entities.put("&erarr;", "\u2971");
2223    entities.put("&escr;", "\u212F");
2224    entities.put("&esdot;", "\u2250");
2225    entities.put("&esim;", "\u2242");
2226    entities.put("&eta;", "\u03B7");
2227    entities.put("&eth;", "\u00F0");
2228    entities.put("&euml;", "\u00EB");
2229    entities.put("&euro;", "\u20AC");
2230    entities.put("&excl;", "\u0021");
2231    entities.put("&exist;", "\u2203");
2232    entities.put("&expectation;", "\u2130");
2233    entities.put("&exponentiale;", "\u2147");
2234    entities.put("&fallingdotseq;", "\u2252");
2235    entities.put("&fcy;", "\u0444");
2236    entities.put("&female;", "\u2640");
2237    entities.put("&ffilig;", "\uFB03");
2238    entities.put("&fflig;", "\uFB00");
2239    entities.put("&ffllig;", "\uFB04");
2240    entities.put("&ffr;", "\uD835\uDD23");
2241    entities.put("&filig;", "\uFB01");
2242    entities.put("&fjlig;", "\u0066\u006A");
2243    entities.put("&flat;", "\u266D");
2244    entities.put("&fllig;", "\uFB02");
2245    entities.put("&fltns;", "\u25B1");
2246    entities.put("&fnof;", "\u0192");
2247    entities.put("&fopf;", "\uD835\uDD57");
2248    entities.put("&forall;", "\u2200");
2249    entities.put("&fork;", "\u22D4");
2250    entities.put("&forkv;", "\u2AD9");
2251    entities.put("&fpartint;", "\u2A0D");
2252    entities.put("&frac12;", "\u00BD");
2253    entities.put("&frac13;", "\u2153");
2254    entities.put("&frac14;", "\u00BC");
2255    entities.put("&frac15;", "\u2155");
2256    entities.put("&frac16;", "\u2159");
2257    entities.put("&frac18;", "\u215B");
2258    entities.put("&frac23;", "\u2154");
2259    entities.put("&frac25;", "\u2156");
2260    entities.put("&frac34;", "\u00BE");
2261    entities.put("&frac35;", "\u2157");
2262    entities.put("&frac38;", "\u215C");
2263    entities.put("&frac45;", "\u2158");
2264    entities.put("&frac56;", "\u215A");
2265    entities.put("&frac58;", "\u215D");
2266    entities.put("&frac78;", "\u215E");
2267    entities.put("&frasl;", "\u2044");
2268    entities.put("&frown;", "\u2322");
2269    entities.put("&fscr;", "\uD835\uDCBB");
2270    entities.put("&gE;", "\u2267");
2271    entities.put("&gEl;", "\u2A8C");
2272    entities.put("&gacute;", "\u01F5");
2273    entities.put("&gamma;", "\u03B3");
2274    entities.put("&gammad;", "\u03DD");
2275    entities.put("&gap;", "\u2A86");
2276    entities.put("&gbreve;", "\u011F");
2277    entities.put("&gcirc;", "\u011D");
2278    entities.put("&gcy;", "\u0433");
2279    entities.put("&gdot;", "\u0121");
2280    entities.put("&ge;", "\u2265");
2281    entities.put("&gel;", "\u22DB");
2282    entities.put("&geq;", "\u2265");
2283    entities.put("&geqq;", "\u2267");
2284    entities.put("&geqslant;", "\u2A7E");
2285    entities.put("&ges;", "\u2A7E");
2286    entities.put("&gescc;", "\u2AA9");
2287    entities.put("&gesdot;", "\u2A80");
2288    entities.put("&gesdoto;", "\u2A82");
2289    entities.put("&gesdotol;", "\u2A84");
2290    entities.put("&gesl;", "\u22DB\uFE00");
2291    entities.put("&gesles;", "\u2A94");
2292    entities.put("&gfr;", "\uD835\uDD24");
2293    entities.put("&gg;", "\u226B");
2294    entities.put("&ggg;", "\u22D9");
2295    entities.put("&gimel;", "\u2137");
2296    entities.put("&gjcy;", "\u0453");
2297    entities.put("&gl;", "\u2277");
2298    entities.put("&glE;", "\u2A92");
2299    entities.put("&gla;", "\u2AA5");
2300    entities.put("&glj;", "\u2AA4");
2301    entities.put("&gnE;", "\u2269");
2302    entities.put("&gnap;", "\u2A8A");
2303    entities.put("&gnapprox;", "\u2A8A");
2304    entities.put("&gne;", "\u2A88");
2305    entities.put("&gneq;", "\u2A88");
2306    entities.put("&gneqq;", "\u2269");
2307    entities.put("&gnsim;", "\u22E7");
2308    entities.put("&gopf;", "\uD835\uDD58");
2309    entities.put("&grave;", "\u0060");
2310    entities.put("&gscr;", "\u210A");
2311    entities.put("&gsim;", "\u2273");
2312    entities.put("&gsime;", "\u2A8E");
2313    entities.put("&gsiml;", "\u2A90");
2314    entities.put("&gt;", "\u003E");
2315    entities.put("&gtcc;", "\u2AA7");
2316    entities.put("&gtcir;", "\u2A7A");
2317    entities.put("&gtdot;", "\u22D7");
2318    entities.put("&gtlPar;", "\u2995");
2319    entities.put("&gtquest;", "\u2A7C");
2320    entities.put("&gtrapprox;", "\u2A86");
2321    entities.put("&gtrarr;", "\u2978");
2322    entities.put("&gtrdot;", "\u22D7");
2323    entities.put("&gtreqless;", "\u22DB");
2324    entities.put("&gtreqqless;", "\u2A8C");
2325    entities.put("&gtrless;", "\u2277");
2326    entities.put("&gtrsim;", "\u2273");
2327    entities.put("&gvertneqq;", "\u2269\uFE00");
2328    entities.put("&gvnE;", "\u2269\uFE00");
2329    entities.put("&hArr;", "\u21D4");
2330    entities.put("&hairsp;", "\u200A");
2331    entities.put("&half;", "\u00BD");
2332    entities.put("&hamilt;", "\u210B");
2333    entities.put("&hardcy;", "\u044A");
2334    entities.put("&harr;", "\u2194");
2335    entities.put("&harrcir;", "\u2948");
2336    entities.put("&harrw;", "\u21AD");
2337    entities.put("&hbar;", "\u210F");
2338    entities.put("&hcirc;", "\u0125");
2339    entities.put("&hearts;", "\u2665");
2340    entities.put("&heartsuit;", "\u2665");
2341    entities.put("&hellip;", "\u2026");
2342    entities.put("&hercon;", "\u22B9");
2343    entities.put("&hfr;", "\uD835\uDD25");
2344    entities.put("&hksearow;", "\u2925");
2345    entities.put("&hkswarow;", "\u2926");
2346    entities.put("&hoarr;", "\u21FF");
2347    entities.put("&homtht;", "\u223B");
2348    entities.put("&hookleftarrow;", "\u21A9");
2349    entities.put("&hookrightarrow;", "\u21AA");
2350    entities.put("&hopf;", "\uD835\uDD59");
2351    entities.put("&horbar;", "\u2015");
2352    entities.put("&hscr;", "\uD835\uDCBD");
2353    entities.put("&hslash;", "\u210F");
2354    entities.put("&hstrok;", "\u0127");
2355    entities.put("&hybull;", "\u2043");
2356    entities.put("&hyphen;", "\u2010");
2357    entities.put("&iacute;", "\u00ED");
2358    entities.put("&ic;", "\u2063");
2359    entities.put("&icirc;", "\u00EE");
2360    entities.put("&icy;", "\u0438");
2361    entities.put("&iecy;", "\u0435");
2362    entities.put("&iexcl;", "\u00A1");
2363    entities.put("&iff;", "\u21D4");
2364    entities.put("&ifr;", "\uD835\uDD26");
2365    entities.put("&igrave;", "\u00EC");
2366    entities.put("&ii;", "\u2148");
2367    entities.put("&iiiint;", "\u2A0C");
2368    entities.put("&iiint;", "\u222D");
2369    entities.put("&iinfin;", "\u29DC");
2370    entities.put("&iiota;", "\u2129");
2371    entities.put("&ijlig;", "\u0133");
2372    entities.put("&imacr;", "\u012B");
2373    entities.put("&image;", "\u2111");
2374    entities.put("&imagline;", "\u2110");
2375    entities.put("&imagpart;", "\u2111");
2376    entities.put("&imath;", "\u0131");
2377    entities.put("&imof;", "\u22B7");
2378    entities.put("&imped;", "\u01B5");
2379    entities.put("&in;", "\u2208");
2380    entities.put("&incare;", "\u2105");
2381    entities.put("&infin;", "\u221E");
2382    entities.put("&infintie;", "\u29DD");
2383    entities.put("&inodot;", "\u0131");
2384    entities.put("&int;", "\u222B");
2385    entities.put("&intcal;", "\u22BA");
2386    entities.put("&integers;", "\u2124");
2387    entities.put("&intercal;", "\u22BA");
2388    entities.put("&intlarhk;", "\u2A17");
2389    entities.put("&intprod;", "\u2A3C");
2390    entities.put("&iocy;", "\u0451");
2391    entities.put("&iogon;", "\u012F");
2392    entities.put("&iopf;", "\uD835\uDD5A");
2393    entities.put("&iota;", "\u03B9");
2394    entities.put("&iprod;", "\u2A3C");
2395    entities.put("&iquest;", "\u00BF");
2396    entities.put("&iscr;", "\uD835\uDCBE");
2397    entities.put("&isin;", "\u2208");
2398    entities.put("&isinE;", "\u22F9");
2399    entities.put("&isindot;", "\u22F5");
2400    entities.put("&isins;", "\u22F4");
2401    entities.put("&isinsv;", "\u22F3");
2402    entities.put("&isinv;", "\u2208");
2403    entities.put("&it;", "\u2062");
2404    entities.put("&itilde;", "\u0129");
2405    entities.put("&iukcy;", "\u0456");
2406    entities.put("&iuml;", "\u00EF");
2407    entities.put("&jcirc;", "\u0135");
2408    entities.put("&jcy;", "\u0439");
2409    entities.put("&jfr;", "\uD835\uDD27");
2410    entities.put("&jmath;", "\u0237");
2411    entities.put("&jopf;", "\uD835\uDD5B");
2412    entities.put("&jscr;", "\uD835\uDCBF");
2413    entities.put("&jsercy;", "\u0458");
2414    entities.put("&jukcy;", "\u0454");
2415    entities.put("&kappa;", "\u03BA");
2416    entities.put("&kappav;", "\u03F0");
2417    entities.put("&kcedil;", "\u0137");
2418    entities.put("&kcy;", "\u043A");
2419    entities.put("&kfr;", "\uD835\uDD28");
2420    entities.put("&kgreen;", "\u0138");
2421    entities.put("&khcy;", "\u0445");
2422    entities.put("&kjcy;", "\u045C");
2423    entities.put("&kopf;", "\uD835\uDD5C");
2424    entities.put("&kscr;", "\uD835\uDCC0");
2425    entities.put("&lAarr;", "\u21DA");
2426    entities.put("&lArr;", "\u21D0");
2427    entities.put("&lAtail;", "\u291B");
2428    entities.put("&lBarr;", "\u290E");
2429    entities.put("&lE;", "\u2266");
2430    entities.put("&lEg;", "\u2A8B");
2431    entities.put("&lHar;", "\u2962");
2432    entities.put("&lacute;", "\u013A");
2433    entities.put("&laemptyv;", "\u29B4");
2434    entities.put("&lagran;", "\u2112");
2435    entities.put("&lambda;", "\u03BB");
2436    entities.put("&lang;", "\u27E8");
2437    entities.put("&langd;", "\u2991");
2438    entities.put("&langle;", "\u27E8");
2439    entities.put("&lap;", "\u2A85");
2440    entities.put("&laquo;", "\u00AB");
2441    entities.put("&larr;", "\u2190");
2442    entities.put("&larrb;", "\u21E4");
2443    entities.put("&larrbfs;", "\u291F");
2444    entities.put("&larrfs;", "\u291D");
2445    entities.put("&larrhk;", "\u21A9");
2446    entities.put("&larrlp;", "\u21AB");
2447    entities.put("&larrpl;", "\u2939");
2448    entities.put("&larrsim;", "\u2973");
2449    entities.put("&larrtl;", "\u21A2");
2450    entities.put("&lat;", "\u2AAB");
2451    entities.put("&latail;", "\u2919");
2452    entities.put("&late;", "\u2AAD");
2453    entities.put("&lates;", "\u2AAD\uFE00");
2454    entities.put("&lbarr;", "\u290C");
2455    entities.put("&lbbrk;", "\u2772");
2456    entities.put("&lbrace;", "\u007B");
2457    entities.put("&lbrack;", "\u005B");
2458    entities.put("&lbrke;", "\u298B");
2459    entities.put("&lbrksld;", "\u298F");
2460    entities.put("&lbrkslu;", "\u298D");
2461    entities.put("&lcaron;", "\u013E");
2462    entities.put("&lcedil;", "\u013C");
2463    entities.put("&lceil;", "\u2308");
2464    entities.put("&lcub;", "\u007B");
2465    entities.put("&lcy;", "\u043B");
2466    entities.put("&ldca;", "\u2936");
2467    entities.put("&ldquo;", "\u201C");
2468    entities.put("&ldquor;", "\u201E");
2469    entities.put("&ldrdhar;", "\u2967");
2470    entities.put("&ldrushar;", "\u294B");
2471    entities.put("&ldsh;", "\u21B2");
2472    entities.put("&le;", "\u2264");
2473    entities.put("&leftarrow;", "\u2190");
2474    entities.put("&leftarrowtail;", "\u21A2");
2475    entities.put("&leftharpoondown;", "\u21BD");
2476    entities.put("&leftharpoonup;", "\u21BC");
2477    entities.put("&leftleftarrows;", "\u21C7");
2478    entities.put("&leftrightarrow;", "\u2194");
2479    entities.put("&leftrightarrows;", "\u21C6");
2480    entities.put("&leftrightharpoons;", "\u21CB");
2481    entities.put("&leftrightsquigarrow;", "\u21AD");
2482    entities.put("&leftthreetimes;", "\u22CB");
2483    entities.put("&leg;", "\u22DA");
2484    entities.put("&leq;", "\u2264");
2485    entities.put("&leqq;", "\u2266");
2486    entities.put("&leqslant;", "\u2A7D");
2487    entities.put("&les;", "\u2A7D");
2488    entities.put("&lescc;", "\u2AA8");
2489    entities.put("&lesdot;", "\u2A7F");
2490    entities.put("&lesdoto;", "\u2A81");
2491    entities.put("&lesdotor;", "\u2A83");
2492    entities.put("&lesg;", "\u22DA\uFE00");
2493    entities.put("&lesges;", "\u2A93");
2494    entities.put("&lessapprox;", "\u2A85");
2495    entities.put("&lessdot;", "\u22D6");
2496    entities.put("&lesseqgtr;", "\u22DA");
2497    entities.put("&lesseqqgtr;", "\u2A8B");
2498    entities.put("&lessgtr;", "\u2276");
2499    entities.put("&lesssim;", "\u2272");
2500    entities.put("&lfisht;", "\u297C");
2501    entities.put("&lfloor;", "\u230A");
2502    entities.put("&lfr;", "\uD835\uDD29");
2503    entities.put("&lg;", "\u2276");
2504    entities.put("&lgE;", "\u2A91");
2505    entities.put("&lhard;", "\u21BD");
2506    entities.put("&lharu;", "\u21BC");
2507    entities.put("&lharul;", "\u296A");
2508    entities.put("&lhblk;", "\u2584");
2509    entities.put("&ljcy;", "\u0459");
2510    entities.put("&ll;", "\u226A");
2511    entities.put("&llarr;", "\u21C7");
2512    entities.put("&llcorner;", "\u231E");
2513    entities.put("&llhard;", "\u296B");
2514    entities.put("&lltri;", "\u25FA");
2515    entities.put("&lmidot;", "\u0140");
2516    entities.put("&lmoust;", "\u23B0");
2517    entities.put("&lmoustache;", "\u23B0");
2518    entities.put("&lnE;", "\u2268");
2519    entities.put("&lnap;", "\u2A89");
2520    entities.put("&lnapprox;", "\u2A89");
2521    entities.put("&lne;", "\u2A87");
2522    entities.put("&lneq;", "\u2A87");
2523    entities.put("&lneqq;", "\u2268");
2524    entities.put("&lnsim;", "\u22E6");
2525    entities.put("&loang;", "\u27EC");
2526    entities.put("&loarr;", "\u21FD");
2527    entities.put("&lobrk;", "\u27E6");
2528    entities.put("&longleftarrow;", "\u27F5");
2529    entities.put("&longleftrightarrow;", "\u27F7");
2530    entities.put("&longmapsto;", "\u27FC");
2531    entities.put("&longrightarrow;", "\u27F6");
2532    entities.put("&looparrowleft;", "\u21AB");
2533    entities.put("&looparrowright;", "\u21AC");
2534    entities.put("&lopar;", "\u2985");
2535    entities.put("&lopf;", "\uD835\uDD5D");
2536    entities.put("&loplus;", "\u2A2D");
2537    entities.put("&lotimes;", "\u2A34");
2538    entities.put("&lowast;", "\u2217");
2539    entities.put("&lowbar;", "\u005F");
2540    entities.put("&loz;", "\u25CA");
2541    entities.put("&lozenge;", "\u25CA");
2542    entities.put("&lozf;", "\u29EB");
2543    entities.put("&lpar;", "\u0028");
2544    entities.put("&lparlt;", "\u2993");
2545    entities.put("&lrarr;", "\u21C6");
2546    entities.put("&lrcorner;", "\u231F");
2547    entities.put("&lrhar;", "\u21CB");
2548    entities.put("&lrhard;", "\u296D");
2549    entities.put("&lrm;", "\u200E");
2550    entities.put("&lrtri;", "\u22BF");
2551    entities.put("&lsaquo;", "\u2039");
2552    entities.put("&lscr;", "\uD835\uDCC1");
2553    entities.put("&lsh;", "\u21B0");
2554    entities.put("&lsim;", "\u2272");
2555    entities.put("&lsime;", "\u2A8D");
2556    entities.put("&lsimg;", "\u2A8F");
2557    entities.put("&lsqb;", "\u005B");
2558    entities.put("&lsquo;", "\u2018");
2559    entities.put("&lsquor;", "\u201A");
2560    entities.put("&lstrok;", "\u0142");
2561    entities.put("&lt;", "\u003C");
2562    entities.put("&ltcc;", "\u2AA6");
2563    entities.put("&ltcir;", "\u2A79");
2564    entities.put("&ltdot;", "\u22D6");
2565    entities.put("&lthree;", "\u22CB");
2566    entities.put("&ltimes;", "\u22C9");
2567    entities.put("&ltlarr;", "\u2976");
2568    entities.put("&ltquest;", "\u2A7B");
2569    entities.put("&ltrPar;", "\u2996");
2570    entities.put("&ltri;", "\u25C3");
2571    entities.put("&ltrie;", "\u22B4");
2572    entities.put("&ltrif;", "\u25C2");
2573    entities.put("&lurdshar;", "\u294A");
2574    entities.put("&luruhar;", "\u2966");
2575    entities.put("&lvertneqq;", "\u2268\uFE00");
2576    entities.put("&lvnE;", "\u2268\uFE00");
2577    entities.put("&mDDot;", "\u223A");
2578    entities.put("&macr;", "\u00AF");
2579    entities.put("&male;", "\u2642");
2580    entities.put("&malt;", "\u2720");
2581    entities.put("&maltese;", "\u2720");
2582    entities.put("&map;", "\u21A6");
2583    entities.put("&mapsto;", "\u21A6");
2584    entities.put("&mapstodown;", "\u21A7");
2585    entities.put("&mapstoleft;", "\u21A4");
2586    entities.put("&mapstoup;", "\u21A5");
2587    entities.put("&marker;", "\u25AE");
2588    entities.put("&mcomma;", "\u2A29");
2589    entities.put("&mcy;", "\u043C");
2590    entities.put("&mdash;", "\u2014");
2591    entities.put("&measuredangle;", "\u2221");
2592    entities.put("&mfr;", "\uD835\uDD2A");
2593    entities.put("&mho;", "\u2127");
2594    entities.put("&micro;", "\u00B5");
2595    entities.put("&mid;", "\u2223");
2596    entities.put("&midast;", "\u002A");
2597    entities.put("&midcir;", "\u2AF0");
2598    entities.put("&middot;", "\u00B7");
2599    entities.put("&minus;", "\u2212");
2600    entities.put("&minusb;", "\u229F");
2601    entities.put("&minusd;", "\u2238");
2602    entities.put("&minusdu;", "\u2A2A");
2603    entities.put("&mlcp;", "\u2ADB");
2604    entities.put("&mldr;", "\u2026");
2605    entities.put("&mnplus;", "\u2213");
2606    entities.put("&models;", "\u22A7");
2607    entities.put("&mopf;", "\uD835\uDD5E");
2608    entities.put("&mp;", "\u2213");
2609    entities.put("&mscr;", "\uD835\uDCC2");
2610    entities.put("&mstpos;", "\u223E");
2611    entities.put("&mu;", "\u03BC");
2612    entities.put("&multimap;", "\u22B8");
2613    entities.put("&mumap;", "\u22B8");
2614    entities.put("&nGg;", "\u22D9\u0338");
2615    entities.put("&nGt;", "\u226B\u20D2");
2616    entities.put("&nGtv;", "\u226B\u0338");
2617    entities.put("&nLeftarrow;", "\u21CD");
2618    entities.put("&nLeftrightarrow;", "\u21CE");
2619    entities.put("&nLl;", "\u22D8\u0338");
2620    entities.put("&nLt;", "\u226A\u20D2");
2621    entities.put("&nLtv;", "\u226A\u0338");
2622    entities.put("&nRightarrow;", "\u21CF");
2623    entities.put("&nVDash;", "\u22AF");
2624    entities.put("&nVdash;", "\u22AE");
2625    entities.put("&nabla;", "\u2207");
2626    entities.put("&nacute;", "\u0144");
2627    entities.put("&nang;", "\u2220\u20D2");
2628    entities.put("&nap;", "\u2249");
2629    entities.put("&napE;", "\u2A70\u0338");
2630    entities.put("&napid;", "\u224B\u0338");
2631    entities.put("&napos;", "\u0149");
2632    entities.put("&napprox;", "\u2249");
2633    entities.put("&natur;", "\u266E");
2634    entities.put("&natural;", "\u266E");
2635    entities.put("&naturals;", "\u2115");
2636    entities.put("&nbsp;", "\u00A0");
2637    entities.put("&nbump;", "\u224E\u0338");
2638    entities.put("&nbumpe;", "\u224F\u0338");
2639    entities.put("&ncap;", "\u2A43");
2640    entities.put("&ncaron;", "\u0148");
2641    entities.put("&ncedil;", "\u0146");
2642    entities.put("&ncong;", "\u2247");
2643    entities.put("&ncongdot;", "\u2A6D\u0338");
2644    entities.put("&ncup;", "\u2A42");
2645    entities.put("&ncy;", "\u043D");
2646    entities.put("&ndash;", "\u2013");
2647    entities.put("&ne;", "\u2260");
2648    entities.put("&neArr;", "\u21D7");
2649    entities.put("&nearhk;", "\u2924");
2650    entities.put("&nearr;", "\u2197");
2651    entities.put("&nearrow;", "\u2197");
2652    entities.put("&nedot;", "\u2250\u0338");
2653    entities.put("&nequiv;", "\u2262");
2654    entities.put("&nesear;", "\u2928");
2655    entities.put("&nesim;", "\u2242\u0338");
2656    entities.put("&nexist;", "\u2204");
2657    entities.put("&nexists;", "\u2204");
2658    entities.put("&nfr;", "\uD835\uDD2B");
2659    entities.put("&ngE;", "\u2267\u0338");
2660    entities.put("&nge;", "\u2271");
2661    entities.put("&ngeq;", "\u2271");
2662    entities.put("&ngeqq;", "\u2267\u0338");
2663    entities.put("&ngeqslant;", "\u2A7E\u0338");
2664    entities.put("&nges;", "\u2A7E\u0338");
2665    entities.put("&ngsim;", "\u2275");
2666    entities.put("&ngt;", "\u226F");
2667    entities.put("&ngtr;", "\u226F");
2668    entities.put("&nhArr;", "\u21CE");
2669    entities.put("&nharr;", "\u21AE");
2670    entities.put("&nhpar;", "\u2AF2");
2671    entities.put("&ni;", "\u220B");
2672    entities.put("&nis;", "\u22FC");
2673    entities.put("&nisd;", "\u22FA");
2674    entities.put("&niv;", "\u220B");
2675    entities.put("&njcy;", "\u045A");
2676    entities.put("&nlArr;", "\u21CD");
2677    entities.put("&nlE;", "\u2266\u0338");
2678    entities.put("&nlarr;", "\u219A");
2679    entities.put("&nldr;", "\u2025");
2680    entities.put("&nle;", "\u2270");
2681    entities.put("&nleftarrow;", "\u219A");
2682    entities.put("&nleftrightarrow;", "\u21AE");
2683    entities.put("&nleq;", "\u2270");
2684    entities.put("&nleqq;", "\u2266\u0338");
2685    entities.put("&nleqslant;", "\u2A7D\u0338");
2686    entities.put("&nles;", "\u2A7D\u0338");
2687    entities.put("&nless;", "\u226E");
2688    entities.put("&nlsim;", "\u2274");
2689    entities.put("&nlt;", "\u226E");
2690    entities.put("&nltri;", "\u22EA");
2691    entities.put("&nltrie;", "\u22EC");
2692    entities.put("&nmid;", "\u2224");
2693    entities.put("&nopf;", "\uD835\uDD5F");
2694    entities.put("&not;", "\u00AC");
2695    entities.put("&notin;", "\u2209");
2696    entities.put("&notinE;", "\u22F9\u0338");
2697    entities.put("&notindot;", "\u22F5\u0338");
2698    entities.put("&notinva;", "\u2209");
2699    entities.put("&notinvb;", "\u22F7");
2700    entities.put("&notinvc;", "\u22F6");
2701    entities.put("&notni;", "\u220C");
2702    entities.put("&notniva;", "\u220C");
2703    entities.put("&notnivb;", "\u22FE");
2704    entities.put("&notnivc;", "\u22FD");
2705    entities.put("&npar;", "\u2226");
2706    entities.put("&nparallel;", "\u2226");
2707    entities.put("&nparsl;", "\u2AFD\u20E5");
2708    entities.put("&npart;", "\u2202\u0338");
2709    entities.put("&npolint;", "\u2A14");
2710    entities.put("&npr;", "\u2280");
2711    entities.put("&nprcue;", "\u22E0");
2712    entities.put("&npre;", "\u2AAF\u0338");
2713    entities.put("&nprec;", "\u2280");
2714    entities.put("&npreceq;", "\u2AAF\u0338");
2715    entities.put("&nrArr;", "\u21CF");
2716    entities.put("&nrarr;", "\u219B");
2717    entities.put("&nrarrc;", "\u2933\u0338");
2718    entities.put("&nrarrw;", "\u219D\u0338");
2719    entities.put("&nrightarrow;", "\u219B");
2720    entities.put("&nrtri;", "\u22EB");
2721    entities.put("&nrtrie;", "\u22ED");
2722    entities.put("&nsc;", "\u2281");
2723    entities.put("&nsccue;", "\u22E1");
2724    entities.put("&nsce;", "\u2AB0\u0338");
2725    entities.put("&nscr;", "\uD835\uDCC3");
2726    entities.put("&nshortmid;", "\u2224");
2727    entities.put("&nshortparallel;", "\u2226");
2728    entities.put("&nsim;", "\u2241");
2729    entities.put("&nsime;", "\u2244");
2730    entities.put("&nsimeq;", "\u2244");
2731    entities.put("&nsmid;", "\u2224");
2732    entities.put("&nspar;", "\u2226");
2733    entities.put("&nsqsube;", "\u22E2");
2734    entities.put("&nsqsupe;", "\u22E3");
2735    entities.put("&nsub;", "\u2284");
2736    entities.put("&nsubE;", "\u2AC5\u0338");
2737    entities.put("&nsube;", "\u2288");
2738    entities.put("&nsubset;", "\u2282\u20D2");
2739    entities.put("&nsubseteq;", "\u2288");
2740    entities.put("&nsubseteqq;", "\u2AC5\u0338");
2741    entities.put("&nsucc;", "\u2281");
2742    entities.put("&nsucceq;", "\u2AB0\u0338");
2743    entities.put("&nsup;", "\u2285");
2744    entities.put("&nsupE;", "\u2AC6\u0338");
2745    entities.put("&nsupe;", "\u2289");
2746    entities.put("&nsupset;", "\u2283\u20D2");
2747    entities.put("&nsupseteq;", "\u2289");
2748    entities.put("&nsupseteqq;", "\u2AC6\u0338");
2749    entities.put("&ntgl;", "\u2279");
2750    entities.put("&ntilde;", "\u00F1");
2751    entities.put("&ntlg;", "\u2278");
2752    entities.put("&ntriangleleft;", "\u22EA");
2753    entities.put("&ntrianglelefteq;", "\u22EC");
2754    entities.put("&ntriangleright;", "\u22EB");
2755    entities.put("&ntrianglerighteq;", "\u22ED");
2756    entities.put("&nu;", "\u03BD");
2757    entities.put("&num;", "\u0023");
2758    entities.put("&numero;", "\u2116");
2759    entities.put("&numsp;", "\u2007");
2760    entities.put("&nvDash;", "\u22AD");
2761    entities.put("&nvHarr;", "\u2904");
2762    entities.put("&nvap;", "\u224D\u20D2");
2763    entities.put("&nvdash;", "\u22AC");
2764    entities.put("&nvge;", "\u2265\u20D2");
2765    entities.put("&nvgt;", "\u003E\u20D2");
2766    entities.put("&nvinfin;", "\u29DE");
2767    entities.put("&nvlArr;", "\u2902");
2768    entities.put("&nvle;", "\u2264\u20D2");
2769    entities.put("&nvlt;", "\u003C\u20D2");
2770    entities.put("&nvltrie;", "\u22B4\u20D2");
2771    entities.put("&nvrArr;", "\u2903");
2772    entities.put("&nvrtrie;", "\u22B5\u20D2");
2773    entities.put("&nvsim;", "\u223C\u20D2");
2774    entities.put("&nwArr;", "\u21D6");
2775    entities.put("&nwarhk;", "\u2923");
2776    entities.put("&nwarr;", "\u2196");
2777    entities.put("&nwarrow;", "\u2196");
2778    entities.put("&nwnear;", "\u2927");
2779    entities.put("&oS;", "\u24C8");
2780    entities.put("&oacute;", "\u00F3");
2781    entities.put("&oast;", "\u229B");
2782    entities.put("&ocir;", "\u229A");
2783    entities.put("&ocirc;", "\u00F4");
2784    entities.put("&ocy;", "\u043E");
2785    entities.put("&odash;", "\u229D");
2786    entities.put("&odblac;", "\u0151");
2787    entities.put("&odiv;", "\u2A38");
2788    entities.put("&odot;", "\u2299");
2789    entities.put("&odsold;", "\u29BC");
2790    entities.put("&oelig;", "\u0153");
2791    entities.put("&ofcir;", "\u29BF");
2792    entities.put("&ofr;", "\uD835\uDD2C");
2793    entities.put("&ogon;", "\u02DB");
2794    entities.put("&ograve;", "\u00F2");
2795    entities.put("&ogt;", "\u29C1");
2796    entities.put("&ohbar;", "\u29B5");
2797    entities.put("&ohm;", "\u03A9");
2798    entities.put("&oint;", "\u222E");
2799    entities.put("&olarr;", "\u21BA");
2800    entities.put("&olcir;", "\u29BE");
2801    entities.put("&olcross;", "\u29BB");
2802    entities.put("&oline;", "\u203E");
2803    entities.put("&olt;", "\u29C0");
2804    entities.put("&omacr;", "\u014D");
2805    entities.put("&omega;", "\u03C9");
2806    entities.put("&omicron;", "\u03BF");
2807    entities.put("&omid;", "\u29B6");
2808    entities.put("&ominus;", "\u2296");
2809    entities.put("&oopf;", "\uD835\uDD60");
2810    entities.put("&opar;", "\u29B7");
2811    entities.put("&operp;", "\u29B9");
2812    entities.put("&oplus;", "\u2295");
2813    entities.put("&or;", "\u2228");
2814    entities.put("&orarr;", "\u21BB");
2815    entities.put("&ord;", "\u2A5D");
2816    entities.put("&order;", "\u2134");
2817    entities.put("&orderof;", "\u2134");
2818    entities.put("&ordf;", "\u00AA");
2819    entities.put("&ordm;", "\u00BA");
2820    entities.put("&origof;", "\u22B6");
2821    entities.put("&oror;", "\u2A56");
2822    entities.put("&orslope;", "\u2A57");
2823    entities.put("&orv;", "\u2A5B");
2824    entities.put("&oscr;", "\u2134");
2825    entities.put("&oslash;", "\u00F8");
2826    entities.put("&osol;", "\u2298");
2827    entities.put("&otilde;", "\u00F5");
2828    entities.put("&otimes;", "\u2297");
2829    entities.put("&otimesas;", "\u2A36");
2830    entities.put("&ouml;", "\u00F6");
2831    entities.put("&ovbar;", "\u233D");
2832    entities.put("&par;", "\u2225");
2833    entities.put("&para;", "\u00B6");
2834    entities.put("&parallel;", "\u2225");
2835    entities.put("&parsim;", "\u2AF3");
2836    entities.put("&parsl;", "\u2AFD");
2837    entities.put("&part;", "\u2202");
2838    entities.put("&pcy;", "\u043F");
2839    entities.put("&percnt;", "\u0025");
2840    entities.put("&period;", "\u002E");
2841    entities.put("&permil;", "\u2030");
2842    entities.put("&perp;", "\u22A5");
2843    entities.put("&pertenk;", "\u2031");
2844    entities.put("&pfr;", "\uD835\uDD2D");
2845    entities.put("&phi;", "\u03C6");
2846    entities.put("&phiv;", "\u03D5");
2847    entities.put("&phmmat;", "\u2133");
2848    entities.put("&phone;", "\u260E");
2849    entities.put("&pi;", "\u03C0");
2850    entities.put("&pitchfork;", "\u22D4");
2851    entities.put("&piv;", "\u03D6");
2852    entities.put("&planck;", "\u210F");
2853    entities.put("&planckh;", "\u210E");
2854    entities.put("&plankv;", "\u210F");
2855    entities.put("&plus;", "\u002B");
2856    entities.put("&plusacir;", "\u2A23");
2857    entities.put("&plusb;", "\u229E");
2858    entities.put("&pluscir;", "\u2A22");
2859    entities.put("&plusdo;", "\u2214");
2860    entities.put("&plusdu;", "\u2A25");
2861    entities.put("&pluse;", "\u2A72");
2862    entities.put("&plusmn;", "\u00B1");
2863    entities.put("&plussim;", "\u2A26");
2864    entities.put("&plustwo;", "\u2A27");
2865    entities.put("&pm;", "\u00B1");
2866    entities.put("&pointint;", "\u2A15");
2867    entities.put("&popf;", "\uD835\uDD61");
2868    entities.put("&pound;", "\u00A3");
2869    entities.put("&pr;", "\u227A");
2870    entities.put("&prE;", "\u2AB3");
2871    entities.put("&prap;", "\u2AB7");
2872    entities.put("&prcue;", "\u227C");
2873    entities.put("&pre;", "\u2AAF");
2874    entities.put("&prec;", "\u227A");
2875    entities.put("&precapprox;", "\u2AB7");
2876    entities.put("&preccurlyeq;", "\u227C");
2877    entities.put("&preceq;", "\u2AAF");
2878    entities.put("&precnapprox;", "\u2AB9");
2879    entities.put("&precneqq;", "\u2AB5");
2880    entities.put("&precnsim;", "\u22E8");
2881    entities.put("&precsim;", "\u227E");
2882    entities.put("&prime;", "\u2032");
2883    entities.put("&primes;", "\u2119");
2884    entities.put("&prnE;", "\u2AB5");
2885    entities.put("&prnap;", "\u2AB9");
2886    entities.put("&prnsim;", "\u22E8");
2887    entities.put("&prod;", "\u220F");
2888    entities.put("&profalar;", "\u232E");
2889    entities.put("&profline;", "\u2312");
2890    entities.put("&profsurf;", "\u2313");
2891    entities.put("&prop;", "\u221D");
2892    entities.put("&propto;", "\u221D");
2893    entities.put("&prsim;", "\u227E");
2894    entities.put("&prurel;", "\u22B0");
2895    entities.put("&pscr;", "\uD835\uDCC5");
2896    entities.put("&psi;", "\u03C8");
2897    entities.put("&puncsp;", "\u2008");
2898    entities.put("&qfr;", "\uD835\uDD2E");
2899    entities.put("&qint;", "\u2A0C");
2900    entities.put("&qopf;", "\uD835\uDD62");
2901    entities.put("&qprime;", "\u2057");
2902    entities.put("&qscr;", "\uD835\uDCC6");
2903    entities.put("&quaternions;", "\u210D");
2904    entities.put("&quatint;", "\u2A16");
2905    entities.put("&quest;", "\u003F");
2906    entities.put("&questeq;", "\u225F");
2907    entities.put("&quot;", "\\u0022");
2908    entities.put("&rAarr;", "\u21DB");
2909    entities.put("&rArr;", "\u21D2");
2910    entities.put("&rAtail;", "\u291C");
2911    entities.put("&rBarr;", "\u290F");
2912    entities.put("&rHar;", "\u2964");
2913    entities.put("&race;", "\u223D\u0331");
2914    entities.put("&racute;", "\u0155");
2915    entities.put("&radic;", "\u221A");
2916    entities.put("&raemptyv;", "\u29B3");
2917    entities.put("&rang;", "\u27E9");
2918    entities.put("&rangd;", "\u2992");
2919    entities.put("&range;", "\u29A5");
2920    entities.put("&rangle;", "\u27E9");
2921    entities.put("&raquo;", "\u00BB");
2922    entities.put("&rarr;", "\u2192");
2923    entities.put("&rarrap;", "\u2975");
2924    entities.put("&rarrb;", "\u21E5");
2925    entities.put("&rarrbfs;", "\u2920");
2926    entities.put("&rarrc;", "\u2933");
2927    entities.put("&rarrfs;", "\u291E");
2928    entities.put("&rarrhk;", "\u21AA");
2929    entities.put("&rarrlp;", "\u21AC");
2930    entities.put("&rarrpl;", "\u2945");
2931    entities.put("&rarrsim;", "\u2974");
2932    entities.put("&rarrtl;", "\u21A3");
2933    entities.put("&rarrw;", "\u219D");
2934    entities.put("&ratail;", "\u291A");
2935    entities.put("&ratio;", "\u2236");
2936    entities.put("&rationals;", "\u211A");
2937    entities.put("&rbarr;", "\u290D");
2938    entities.put("&rbbrk;", "\u2773");
2939    entities.put("&rbrace;", "\u007D");
2940    entities.put("&rbrack;", "\u005D");
2941    entities.put("&rbrke;", "\u298C");
2942    entities.put("&rbrksld;", "\u298E");
2943    entities.put("&rbrkslu;", "\u2990");
2944    entities.put("&rcaron;", "\u0159");
2945    entities.put("&rcedil;", "\u0157");
2946    entities.put("&rceil;", "\u2309");
2947    entities.put("&rcub;", "\u007D");
2948    entities.put("&rcy;", "\u0440");
2949    entities.put("&rdca;", "\u2937");
2950    entities.put("&rdldhar;", "\u2969");
2951    entities.put("&rdquo;", "\u201D");
2952    entities.put("&rdquor;", "\u201D");
2953    entities.put("&rdsh;", "\u21B3");
2954    entities.put("&real;", "\u211C");
2955    entities.put("&realine;", "\u211B");
2956    entities.put("&realpart;", "\u211C");
2957    entities.put("&reals;", "\u211D");
2958    entities.put("&rect;", "\u25AD");
2959    entities.put("&reg;", "\u00AE");
2960    entities.put("&rfisht;", "\u297D");
2961    entities.put("&rfloor;", "\u230B");
2962    entities.put("&rfr;", "\uD835\uDD2F");
2963    entities.put("&rhard;", "\u21C1");
2964    entities.put("&rharu;", "\u21C0");
2965    entities.put("&rharul;", "\u296C");
2966    entities.put("&rho;", "\u03C1");
2967    entities.put("&rhov;", "\u03F1");
2968    entities.put("&rightarrow;", "\u2192");
2969    entities.put("&rightarrowtail;", "\u21A3");
2970    entities.put("&rightharpoondown;", "\u21C1");
2971    entities.put("&rightharpoonup;", "\u21C0");
2972    entities.put("&rightleftarrows;", "\u21C4");
2973    entities.put("&rightleftharpoons;", "\u21CC");
2974    entities.put("&rightrightarrows;", "\u21C9");
2975    entities.put("&rightsquigarrow;", "\u219D");
2976    entities.put("&rightthreetimes;", "\u22CC");
2977    entities.put("&ring;", "\u02DA");
2978    entities.put("&risingdotseq;", "\u2253");
2979    entities.put("&rlarr;", "\u21C4");
2980    entities.put("&rlhar;", "\u21CC");
2981    entities.put("&rlm;", "\u200F");
2982    entities.put("&rmoust;", "\u23B1");
2983    entities.put("&rmoustache;", "\u23B1");
2984    entities.put("&rnmid;", "\u2AEE");
2985    entities.put("&roang;", "\u27ED");
2986    entities.put("&roarr;", "\u21FE");
2987    entities.put("&robrk;", "\u27E7");
2988    entities.put("&ropar;", "\u2986");
2989    entities.put("&ropf;", "\uD835\uDD63");
2990    entities.put("&roplus;", "\u2A2E");
2991    entities.put("&rotimes;", "\u2A35");
2992    entities.put("&rpar;", "\u0029");
2993    entities.put("&rpargt;", "\u2994");
2994    entities.put("&rppolint;", "\u2A12");
2995    entities.put("&rrarr;", "\u21C9");
2996    entities.put("&rsaquo;", "\u203A");
2997    entities.put("&rscr;", "\uD835\uDCC7");
2998    entities.put("&rsh;", "\u21B1");
2999    entities.put("&rsqb;", "\u005D");
3000    entities.put("&rsquo;", "\u2019");
3001    entities.put("&rsquor;", "\u2019");
3002    entities.put("&rthree;", "\u22CC");
3003    entities.put("&rtimes;", "\u22CA");
3004    entities.put("&rtri;", "\u25B9");
3005    entities.put("&rtrie;", "\u22B5");
3006    entities.put("&rtrif;", "\u25B8");
3007    entities.put("&rtriltri;", "\u29CE");
3008    entities.put("&ruluhar;", "\u2968");
3009    entities.put("&rx;", "\u211E");
3010    entities.put("&sacute;", "\u015B");
3011    entities.put("&sbquo;", "\u201A");
3012    entities.put("&sc;", "\u227B");
3013    entities.put("&scE;", "\u2AB4");
3014    entities.put("&scap;", "\u2AB8");
3015    entities.put("&scaron;", "\u0161");
3016    entities.put("&sccue;", "\u227D");
3017    entities.put("&sce;", "\u2AB0");
3018    entities.put("&scedil;", "\u015F");
3019    entities.put("&scirc;", "\u015D");
3020    entities.put("&scnE;", "\u2AB6");
3021    entities.put("&scnap;", "\u2ABA");
3022    entities.put("&scnsim;", "\u22E9");
3023    entities.put("&scpolint;", "\u2A13");
3024    entities.put("&scsim;", "\u227F");
3025    entities.put("&scy;", "\u0441");
3026    entities.put("&sdot;", "\u22C5");
3027    entities.put("&sdotb;", "\u22A1");
3028    entities.put("&sdote;", "\u2A66");
3029    entities.put("&seArr;", "\u21D8");
3030    entities.put("&searhk;", "\u2925");
3031    entities.put("&searr;", "\u2198");
3032    entities.put("&searrow;", "\u2198");
3033    entities.put("&sect;", "\u00A7");
3034    entities.put("&semi;", "\u003B");
3035    entities.put("&seswar;", "\u2929");
3036    entities.put("&setminus;", "\u2216");
3037    entities.put("&setmn;", "\u2216");
3038    entities.put("&sext;", "\u2736");
3039    entities.put("&sfr;", "\uD835\uDD30");
3040    entities.put("&sfrown;", "\u2322");
3041    entities.put("&sharp;", "\u266F");
3042    entities.put("&shchcy;", "\u0449");
3043    entities.put("&shcy;", "\u0448");
3044    entities.put("&shortmid;", "\u2223");
3045    entities.put("&shortparallel;", "\u2225");
3046    entities.put("&shy;", "\u00AD");
3047    entities.put("&sigma;", "\u03C3");
3048    entities.put("&sigmaf;", "\u03C2");
3049    entities.put("&sigmav;", "\u03C2");
3050    entities.put("&sim;", "\u223C");
3051    entities.put("&simdot;", "\u2A6A");
3052    entities.put("&sime;", "\u2243");
3053    entities.put("&simeq;", "\u2243");
3054    entities.put("&simg;", "\u2A9E");
3055    entities.put("&simgE;", "\u2AA0");
3056    entities.put("&siml;", "\u2A9D");
3057    entities.put("&simlE;", "\u2A9F");
3058    entities.put("&simne;", "\u2246");
3059    entities.put("&simplus;", "\u2A24");
3060    entities.put("&simrarr;", "\u2972");
3061    entities.put("&slarr;", "\u2190");
3062    entities.put("&smallsetminus;", "\u2216");
3063    entities.put("&smashp;", "\u2A33");
3064    entities.put("&smeparsl;", "\u29E4");
3065    entities.put("&smid;", "\u2223");
3066    entities.put("&smile;", "\u2323");
3067    entities.put("&smt;", "\u2AAA");
3068    entities.put("&smte;", "\u2AAC");
3069    entities.put("&smtes;", "\u2AAC\uFE00");
3070    entities.put("&softcy;", "\u044C");
3071    entities.put("&sol;", "\u002F");
3072    entities.put("&solb;", "\u29C4");
3073    entities.put("&solbar;", "\u233F");
3074    entities.put("&sopf;", "\uD835\uDD64");
3075    entities.put("&spades;", "\u2660");
3076    entities.put("&spadesuit;", "\u2660");
3077    entities.put("&spar;", "\u2225");
3078    entities.put("&sqcap;", "\u2293");
3079    entities.put("&sqcaps;", "\u2293\uFE00");
3080    entities.put("&sqcup;", "\u2294");
3081    entities.put("&sqcups;", "\u2294\uFE00");
3082    entities.put("&sqsub;", "\u228F");
3083    entities.put("&sqsube;", "\u2291");
3084    entities.put("&sqsubset;", "\u228F");
3085    entities.put("&sqsubseteq;", "\u2291");
3086    entities.put("&sqsup;", "\u2290");
3087    entities.put("&sqsupe;", "\u2292");
3088    entities.put("&sqsupset;", "\u2290");
3089    entities.put("&sqsupseteq;", "\u2292");
3090    entities.put("&squ;", "\u25A1");
3091    entities.put("&square;", "\u25A1");
3092    entities.put("&squarf;", "\u25AA");
3093    entities.put("&squf;", "\u25AA");
3094    entities.put("&srarr;", "\u2192");
3095    entities.put("&sscr;", "\uD835\uDCC8");
3096    entities.put("&ssetmn;", "\u2216");
3097    entities.put("&ssmile;", "\u2323");
3098    entities.put("&sstarf;", "\u22C6");
3099    entities.put("&star;", "\u2606");
3100    entities.put("&starf;", "\u2605");
3101    entities.put("&straightepsilon;", "\u03F5");
3102    entities.put("&straightphi;", "\u03D5");
3103    entities.put("&strns;", "\u00AF");
3104    entities.put("&sub;", "\u2282");
3105    entities.put("&subE;", "\u2AC5");
3106    entities.put("&subdot;", "\u2ABD");
3107    entities.put("&sube;", "\u2286");
3108    entities.put("&subedot;", "\u2AC3");
3109    entities.put("&submult;", "\u2AC1");
3110    entities.put("&subnE;", "\u2ACB");
3111    entities.put("&subne;", "\u228A");
3112    entities.put("&subplus;", "\u2ABF");
3113    entities.put("&subrarr;", "\u2979");
3114    entities.put("&subset;", "\u2282");
3115    entities.put("&subseteq;", "\u2286");
3116    entities.put("&subseteqq;", "\u2AC5");
3117    entities.put("&subsetneq;", "\u228A");
3118    entities.put("&subsetneqq;", "\u2ACB");
3119    entities.put("&subsim;", "\u2AC7");
3120    entities.put("&subsub;", "\u2AD5");
3121    entities.put("&subsup;", "\u2AD3");
3122    entities.put("&succ;", "\u227B");
3123    entities.put("&succapprox;", "\u2AB8");
3124    entities.put("&succcurlyeq;", "\u227D");
3125    entities.put("&succeq;", "\u2AB0");
3126    entities.put("&succnapprox;", "\u2ABA");
3127    entities.put("&succneqq;", "\u2AB6");
3128    entities.put("&succnsim;", "\u22E9");
3129    entities.put("&succsim;", "\u227F");
3130    entities.put("&sum;", "\u2211");
3131    entities.put("&sung;", "\u266A");
3132    entities.put("&sup1;", "\u00B9");
3133    entities.put("&sup2;", "\u00B2");
3134    entities.put("&sup3;", "\u00B3");
3135    entities.put("&sup;", "\u2283");
3136    entities.put("&supE;", "\u2AC6");
3137    entities.put("&supdot;", "\u2ABE");
3138    entities.put("&supdsub;", "\u2AD8");
3139    entities.put("&supe;", "\u2287");
3140    entities.put("&supedot;", "\u2AC4");
3141    entities.put("&suphsol;", "\u27C9");
3142    entities.put("&suphsub;", "\u2AD7");
3143    entities.put("&suplarr;", "\u297B");
3144    entities.put("&supmult;", "\u2AC2");
3145    entities.put("&supnE;", "\u2ACC");
3146    entities.put("&supne;", "\u228B");
3147    entities.put("&supplus;", "\u2AC0");
3148    entities.put("&supset;", "\u2283");
3149    entities.put("&supseteq;", "\u2287");
3150    entities.put("&supseteqq;", "\u2AC6");
3151    entities.put("&supsetneq;", "\u228B");
3152    entities.put("&supsetneqq;", "\u2ACC");
3153    entities.put("&supsim;", "\u2AC8");
3154    entities.put("&supsub;", "\u2AD4");
3155    entities.put("&supsup;", "\u2AD6");
3156    entities.put("&swArr;", "\u21D9");
3157    entities.put("&swarhk;", "\u2926");
3158    entities.put("&swarr;", "\u2199");
3159    entities.put("&swarrow;", "\u2199");
3160    entities.put("&swnwar;", "\u292A");
3161    entities.put("&szlig;", "\u00DF");
3162    entities.put("&target;", "\u2316");
3163    entities.put("&tau;", "\u03C4");
3164    entities.put("&tbrk;", "\u23B4");
3165    entities.put("&tcaron;", "\u0165");
3166    entities.put("&tcedil;", "\u0163");
3167    entities.put("&tcy;", "\u0442");
3168    entities.put("&tdot;", "\u20DB");
3169    entities.put("&telrec;", "\u2315");
3170    entities.put("&tfr;", "\uD835\uDD31");
3171    entities.put("&there4;", "\u2234");
3172    entities.put("&therefore;", "\u2234");
3173    entities.put("&theta;", "\u03B8");
3174    entities.put("&thetasym;", "\u03D1");
3175    entities.put("&thetav;", "\u03D1");
3176    entities.put("&thickapprox;", "\u2248");
3177    entities.put("&thicksim;", "\u223C");
3178    entities.put("&thinsp;", "\u2009");
3179    entities.put("&thkap;", "\u2248");
3180    entities.put("&thksim;", "\u223C");
3181    entities.put("&thorn;", "\u00FE");
3182    entities.put("&tilde;", "\u02DC");
3183    entities.put("&times;", "\u00D7");
3184    entities.put("&timesb;", "\u22A0");
3185    entities.put("&timesbar;", "\u2A31");
3186    entities.put("&timesd;", "\u2A30");
3187    entities.put("&tint;", "\u222D");
3188    entities.put("&toea;", "\u2928");
3189    entities.put("&top;", "\u22A4");
3190    entities.put("&topbot;", "\u2336");
3191    entities.put("&topcir;", "\u2AF1");
3192    entities.put("&topf;", "\uD835\uDD65");
3193    entities.put("&topfork;", "\u2ADA");
3194    entities.put("&tosa;", "\u2929");
3195    entities.put("&tprime;", "\u2034");
3196    entities.put("&trade;", "\u2122");
3197    entities.put("&triangle;", "\u25B5");
3198    entities.put("&triangledown;", "\u25BF");
3199    entities.put("&triangleleft;", "\u25C3");
3200    entities.put("&trianglelefteq;", "\u22B4");
3201    entities.put("&triangleq;", "\u225C");
3202    entities.put("&triangleright;", "\u25B9");
3203    entities.put("&trianglerighteq;", "\u22B5");
3204    entities.put("&tridot;", "\u25EC");
3205    entities.put("&trie;", "\u225C");
3206    entities.put("&triminus;", "\u2A3A");
3207    entities.put("&triplus;", "\u2A39");
3208    entities.put("&trisb;", "\u29CD");
3209    entities.put("&tritime;", "\u2A3B");
3210    entities.put("&trpezium;", "\u23E2");
3211    entities.put("&tscr;", "\uD835\uDCC9");
3212    entities.put("&tscy;", "\u0446");
3213    entities.put("&tshcy;", "\u045B");
3214    entities.put("&tstrok;", "\u0167");
3215    entities.put("&twixt;", "\u226C");
3216    entities.put("&twoheadleftarrow;", "\u219E");
3217    entities.put("&twoheadrightarrow;", "\u21A0");
3218    entities.put("&uArr;", "\u21D1");
3219    entities.put("&uHar;", "\u2963");
3220    entities.put("&uacute;", "\u00FA");
3221    entities.put("&uarr;", "\u2191");
3222    entities.put("&ubrcy;", "\u045E");
3223    entities.put("&ubreve;", "\u016D");
3224    entities.put("&ucirc;", "\u00FB");
3225    entities.put("&ucy;", "\u0443");
3226    entities.put("&udarr;", "\u21C5");
3227    entities.put("&udblac;", "\u0171");
3228    entities.put("&udhar;", "\u296E");
3229    entities.put("&ufisht;", "\u297E");
3230    entities.put("&ufr;", "\uD835\uDD32");
3231    entities.put("&ugrave;", "\u00F9");
3232    entities.put("&uharl;", "\u21BF");
3233    entities.put("&uharr;", "\u21BE");
3234    entities.put("&uhblk;", "\u2580");
3235    entities.put("&ulcorn;", "\u231C");
3236    entities.put("&ulcorner;", "\u231C");
3237    entities.put("&ulcrop;", "\u230F");
3238    entities.put("&ultri;", "\u25F8");
3239    entities.put("&umacr;", "\u016B");
3240    entities.put("&uml;", "\u00A8");
3241    entities.put("&uogon;", "\u0173");
3242    entities.put("&uopf;", "\uD835\uDD66");
3243    entities.put("&uparrow;", "\u2191");
3244    entities.put("&updownarrow;", "\u2195");
3245    entities.put("&upharpoonleft;", "\u21BF");
3246    entities.put("&upharpoonright;", "\u21BE");
3247    entities.put("&uplus;", "\u228E");
3248    entities.put("&upsi;", "\u03C5");
3249    entities.put("&upsih;", "\u03D2");
3250    entities.put("&upsilon;", "\u03C5");
3251    entities.put("&upuparrows;", "\u21C8");
3252    entities.put("&urcorn;", "\u231D");
3253    entities.put("&urcorner;", "\u231D");
3254    entities.put("&urcrop;", "\u230E");
3255    entities.put("&uring;", "\u016F");
3256    entities.put("&urtri;", "\u25F9");
3257    entities.put("&uscr;", "\uD835\uDCCA");
3258    entities.put("&utdot;", "\u22F0");
3259    entities.put("&utilde;", "\u0169");
3260    entities.put("&utri;", "\u25B5");
3261    entities.put("&utrif;", "\u25B4");
3262    entities.put("&uuarr;", "\u21C8");
3263    entities.put("&uuml;", "\u00FC");
3264    entities.put("&uwangle;", "\u29A7");
3265    entities.put("&vArr;", "\u21D5");
3266    entities.put("&vBar;", "\u2AE8");
3267    entities.put("&vBarv;", "\u2AE9");
3268    entities.put("&vDash;", "\u22A8");
3269    entities.put("&vangrt;", "\u299C");
3270    entities.put("&varepsilon;", "\u03F5");
3271    entities.put("&varkappa;", "\u03F0");
3272    entities.put("&varnothing;", "\u2205");
3273    entities.put("&varphi;", "\u03D5");
3274    entities.put("&varpi;", "\u03D6");
3275    entities.put("&varpropto;", "\u221D");
3276    entities.put("&varr;", "\u2195");
3277    entities.put("&varrho;", "\u03F1");
3278    entities.put("&varsigma;", "\u03C2");
3279    entities.put("&varsubsetneq;", "\u228A\uFE00");
3280    entities.put("&varsubsetneqq;", "\u2ACB\uFE00");
3281    entities.put("&varsupsetneq;", "\u228B\uFE00");
3282    entities.put("&varsupsetneqq;", "\u2ACC\uFE00");
3283    entities.put("&vartheta;", "\u03D1");
3284    entities.put("&vartriangleleft;", "\u22B2");
3285    entities.put("&vartriangleright;", "\u22B3");
3286    entities.put("&vcy;", "\u0432");
3287    entities.put("&vdash;", "\u22A2");
3288    entities.put("&vee;", "\u2228");
3289    entities.put("&veebar;", "\u22BB");
3290    entities.put("&veeeq;", "\u225A");
3291    entities.put("&vellip;", "\u22EE");
3292    entities.put("&verbar;", "\u007C");
3293    entities.put("&vert;", "\u007C");
3294    entities.put("&vfr;", "\uD835\uDD33");
3295    entities.put("&vltri;", "\u22B2");
3296    entities.put("&vnsub;", "\u2282\u20D2");
3297    entities.put("&vnsup;", "\u2283\u20D2");
3298    entities.put("&vopf;", "\uD835\uDD67");
3299    entities.put("&vprop;", "\u221D");
3300    entities.put("&vrtri;", "\u22B3");
3301    entities.put("&vscr;", "\uD835\uDCCB");
3302    entities.put("&vsubnE;", "\u2ACB\uFE00");
3303    entities.put("&vsubne;", "\u228A\uFE00");
3304    entities.put("&vsupnE;", "\u2ACC\uFE00");
3305    entities.put("&vsupne;", "\u228B\uFE00");
3306    entities.put("&vzigzag;", "\u299A");
3307    entities.put("&wcirc;", "\u0175");
3308    entities.put("&wedbar;", "\u2A5F");
3309    entities.put("&wedge;", "\u2227");
3310    entities.put("&wedgeq;", "\u2259");
3311    entities.put("&weierp;", "\u2118");
3312    entities.put("&wfr;", "\uD835\uDD34");
3313    entities.put("&wopf;", "\uD835\uDD68");
3314    entities.put("&wp;", "\u2118");
3315    entities.put("&wr;", "\u2240");
3316    entities.put("&wreath;", "\u2240");
3317    entities.put("&wscr;", "\uD835\uDCCC");
3318    entities.put("&xcap;", "\u22C2");
3319    entities.put("&xcirc;", "\u25EF");
3320    entities.put("&xcup;", "\u22C3");
3321    entities.put("&xdtri;", "\u25BD");
3322    entities.put("&xfr;", "\uD835\uDD35");
3323    entities.put("&xhArr;", "\u27FA");
3324    entities.put("&xharr;", "\u27F7");
3325    entities.put("&xi;", "\u03BE");
3326    entities.put("&xlArr;", "\u27F8");
3327    entities.put("&xlarr;", "\u27F5");
3328    entities.put("&xmap;", "\u27FC");
3329    entities.put("&xnis;", "\u22FB");
3330    entities.put("&xodot;", "\u2A00");
3331    entities.put("&xopf;", "\uD835\uDD69");
3332    entities.put("&xoplus;", "\u2A01");
3333    entities.put("&xotime;", "\u2A02");
3334    entities.put("&xrArr;", "\u27F9");
3335    entities.put("&xrarr;", "\u27F6");
3336    entities.put("&xscr;", "\uD835\uDCCD");
3337    entities.put("&xsqcup;", "\u2A06");
3338    entities.put("&xuplus;", "\u2A04");
3339    entities.put("&xutri;", "\u25B3");
3340    entities.put("&xvee;", "\u22C1");
3341    entities.put("&xwedge;", "\u22C0");
3342    entities.put("&yacute;", "\u00FD");
3343    entities.put("&yacy;", "\u044F");
3344    entities.put("&ycirc;", "\u0177");
3345    entities.put("&ycy;", "\u044B");
3346    entities.put("&yen;", "\u00A5");
3347    entities.put("&yfr;", "\uD835\uDD36");
3348    entities.put("&yicy;", "\u0457");
3349    entities.put("&yopf;", "\uD835\uDD6A");
3350    entities.put("&yscr;", "\uD835\uDCCE");
3351    entities.put("&yucy;", "\u044E");
3352    entities.put("&yuml;", "\u00FF");
3353    entities.put("&zacute;", "\u017A");
3354    entities.put("&zcaron;", "\u017E");
3355    entities.put("&zcy;", "\u0437");
3356    entities.put("&zdot;", "\u017C");
3357    entities.put("&zeetrf;", "\u2128");
3358    entities.put("&zeta;", "\u03B6");
3359    entities.put("&zfr;", "\uD835\uDD37");
3360    entities.put("&zhcy;", "\u0436");
3361    entities.put("&zigrarr;", "\u21DD");
3362    entities.put("&zopf;", "\uD835\uDD6B");
3363    entities.put("&zscr;", "\uD835\uDCCF");
3364    entities.put("&zwj;", "\u200D");
3365    entities.put("&zwnj;", "\u200C");
3366  }
3367
3368}