cyrus-imapd-2.5.10/0000755000175000017500000000000013001246664011037 500000000000000cyrus-imapd-2.5.10/README.andrew0000644000175000017500000000722513001236017013113 00000000000000#!/bin/sh # # This is internal documentation for Computing Services at # Carnegie Mellon University. # # Please refer to doc/readme.html for the 'real' README. # # smake -d init mf all install exit 0 "configure" is no longer in the repository because it's built from "configure.ac", and it's really annoying to keep checking it in only to realize that you don't understand the changes because they're all autoconf spew. to build configure: sh SMakefile to build: smake init all then, as admin (suid binaries on AFS) smake -d install If you get the error 'can not find sources', make sure imap/imap.c is mode a+r. ---- To make a release: - make sure the version number is correct (Makefile.in, imap/version.h) - add upgrade notes to doc/install-upgrade.html - add changes to doc/changes.html - make sure that contrib/drac_auth.patch applies cleanly - commit to repository - make dist - tag the CVS repository with cyrus-release-Major-Minor-Revision - upload tarball to /afs/andrew.cmu.edu/system/archive/cmu/anonftp/pub/cyrus - announce to: info-cyrus comp.mail.imap cyrus-announce freshmeat.net - update cyrusimap.web.cmu.edu:/usr/www/htdocs/downloads.html links to new version - update cyrusimap.web.cmu.edu:/usr/www/htdocs/imapd from tarball --- to bring up a new Andrew Cyrus server: package.protos for: a) backend server %define cyrus21 %define sasl2 %define is_imap %define is_backend %define is_saslauthd %define usesvxfs %define multiple_lun %define hasuser.permits F /etc/user.permits %define hasroot.permits F /etc/root.permits %include /afs/andrew.cmu.edu/wsadmin/cyrus2/src/cyrus.proto b) frontend server %define cyrus21 %define sasl2 %define uses_readwrite %define wsadmin /afs/.andrew.cmu.edu/wsadmin %define is_imap %define is_saslauthd %define is_frontend %include /afs/andrew.cmu.edu/wsadmin/cyrus2/src/cyrus.proto c) smtp server ???? - Larry? ---- Repackage, Reboot, (and redepot/repackage again) - Key the machine (imap, lmtp, smtp, pop, and put them in /imap/conf/srvtab) - remove the rcmd (and smtp?) key from /imap/conf/srvtab - frontends also need mupdate key - create k5 keys: /usr/local/etc/ktutil srv2key chgrp cyrus /etc/krb5.keytab chmod g+r /etc/krb5.keytab - Generate an SSL key for the machine and install to /imap/conf/server.pem (preferrably signed correctly) Something like: mail-fe3:sun4x_58:/imap/conf# openssl req -new -x509 -nodes -out /imap/conf/serv er.pem -keyout /imap/conf/server.pem Using configuration from /usr/local/lib/openssl/openssl.cnf Generating a 1024 bit RSA private key ............++++++ ..........++++++ writing new private key to '/imap/conf/server.pem' ----- You are about to be asked to enter information that will be incorporated into your certificate request. What you are about to enter is what is called a Distinguished Name or a DN. There are quite a few fields but you can leave some blank For some fields there will be a default value, If you enter '.', the field will be left blank. ----- Country Name (2 letter code) [AU]:US State or Province Name (full name) [Some-State]:Pennsylvania Locality Name (eg, city) []:Pittsburgh Organization Name (eg, company) [Internet Widgits Pty Ltd]:Carnegie Mellon University Organizational Unit Name (eg, section) []:Andrew Systems Group Common Name (eg, YOUR name) []:mail-fe3.andrew.cmu.edu Email Address []:advisor@andrew.cmu.edu - is it a backend? run tools/mkimap (as cyrus!) ---------------------------------------------------------------------- To use Insure++ . uncomment appropriate lines from SMakefile . copy psrc to /.psrc . make sure environment variables HOME and (maybe) USER are properly set . mkdir /tmp/insure; chmod 777 /tmp/insure cyrus-imapd-2.5.10/ltmain.sh0000644000175000017500000117147412756047127012627 00000000000000#! /bin/sh ## DO NOT EDIT - This file generated from ./build-aux/ltmain.in ## by inline-source v2014-01-03.01 # libtool (GNU libtool) 2.4.6 # Provide generalized library-building support services. # Written by Gordon Matzigkeit , 1996 # Copyright (C) 1996-2015 Free Software Foundation, Inc. # This is free software; see the source for copying conditions. There is NO # warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. # GNU Libtool is free software; you can redistribute it and/or modify # it under the terms of the GNU General Public License as published by # the Free Software Foundation; either version 2 of the License, or # (at your option) any later version. # # As a special exception to the GNU General Public License, # if you distribute this file as part of a program or library that # is built using GNU Libtool, you may include this file under the # same distribution terms that you use for the rest of that program. # # GNU Libtool is distributed in the hope that it will be useful, but # WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU # General Public License for more details. # # You should have received a copy of the GNU General Public License # along with this program. If not, see . PROGRAM=libtool PACKAGE=libtool VERSION="2.4.6 Debian-2.4.6-2" package_revision=2.4.6 ## ------ ## ## Usage. ## ## ------ ## # Run './libtool --help' for help with using this script from the # command line. ## ------------------------------- ## ## User overridable command paths. ## ## ------------------------------- ## # After configure completes, it has a better idea of some of the # shell tools we need than the defaults used by the functions shared # with bootstrap, so set those here where they can still be over- # ridden by the user, but otherwise take precedence. : ${AUTOCONF="autoconf"} : ${AUTOMAKE="automake"} ## -------------------------- ## ## Source external libraries. ## ## -------------------------- ## # Much of our low-level functionality needs to be sourced from external # libraries, which are installed to $pkgauxdir. # Set a version string for this script. scriptversion=2015-01-20.17; # UTC # General shell script boiler plate, and helper functions. # Written by Gary V. Vaughan, 2004 # Copyright (C) 2004-2015 Free Software Foundation, Inc. # This is free software; see the source for copying conditions. There is NO # warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. # This program is free software; you can redistribute it and/or modify # it under the terms of the GNU General Public License as published by # the Free Software Foundation; either version 3 of the License, or # (at your option) any later version. # As a special exception to the GNU General Public License, if you distribute # this file as part of a program or library that is built using GNU Libtool, # you may include this file under the same distribution terms that you use # for the rest of that program. # This program is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNES FOR A PARTICULAR PURPOSE. See the GNU # General Public License for more details. # You should have received a copy of the GNU General Public License # along with this program. If not, see . # Please report bugs or propose patches to gary@gnu.org. ## ------ ## ## Usage. ## ## ------ ## # Evaluate this file near the top of your script to gain access to # the functions and variables defined here: # # . `echo "$0" | ${SED-sed} 's|[^/]*$||'`/build-aux/funclib.sh # # If you need to override any of the default environment variable # settings, do that before evaluating this file. ## -------------------- ## ## Shell normalisation. ## ## -------------------- ## # Some shells need a little help to be as Bourne compatible as possible. # Before doing anything else, make sure all that help has been provided! DUALCASE=1; export DUALCASE # for MKS sh if test -n "${ZSH_VERSION+set}" && (emulate sh) >/dev/null 2>&1; then : emulate sh NULLCMD=: # Pre-4.2 versions of Zsh do word splitting on ${1+"$@"}, which # is contrary to our usage. Disable this feature. alias -g '${1+"$@"}'='"$@"' setopt NO_GLOB_SUBST else case `(set -o) 2>/dev/null` in *posix*) set -o posix ;; esac fi # NLS nuisances: We save the old values in case they are required later. _G_user_locale= _G_safe_locale= for _G_var in LANG LANGUAGE LC_ALL LC_CTYPE LC_COLLATE LC_MESSAGES do eval "if test set = \"\${$_G_var+set}\"; then save_$_G_var=\$$_G_var $_G_var=C export $_G_var _G_user_locale=\"$_G_var=\\\$save_\$_G_var; \$_G_user_locale\" _G_safe_locale=\"$_G_var=C; \$_G_safe_locale\" fi" done # CDPATH. (unset CDPATH) >/dev/null 2>&1 && unset CDPATH # Make sure IFS has a sensible default sp=' ' nl=' ' IFS="$sp $nl" # There are apparently some retarded systems that use ';' as a PATH separator! if test "${PATH_SEPARATOR+set}" != set; then PATH_SEPARATOR=: (PATH='/bin;/bin'; FPATH=$PATH; sh -c :) >/dev/null 2>&1 && { (PATH='/bin:/bin'; FPATH=$PATH; sh -c :) >/dev/null 2>&1 || PATH_SEPARATOR=';' } fi ## ------------------------- ## ## Locate command utilities. ## ## ------------------------- ## # func_executable_p FILE # ---------------------- # Check that FILE is an executable regular file. func_executable_p () { test -f "$1" && test -x "$1" } # func_path_progs PROGS_LIST CHECK_FUNC [PATH] # -------------------------------------------- # Search for either a program that responds to --version with output # containing "GNU", or else returned by CHECK_FUNC otherwise, by # trying all the directories in PATH with each of the elements of # PROGS_LIST. # # CHECK_FUNC should accept the path to a candidate program, and # set $func_check_prog_result if it truncates its output less than # $_G_path_prog_max characters. func_path_progs () { _G_progs_list=$1 _G_check_func=$2 _G_PATH=${3-"$PATH"} _G_path_prog_max=0 _G_path_prog_found=false _G_save_IFS=$IFS; IFS=${PATH_SEPARATOR-:} for _G_dir in $_G_PATH; do IFS=$_G_save_IFS test -z "$_G_dir" && _G_dir=. for _G_prog_name in $_G_progs_list; do for _exeext in '' .EXE; do _G_path_prog=$_G_dir/$_G_prog_name$_exeext func_executable_p "$_G_path_prog" || continue case `"$_G_path_prog" --version 2>&1` in *GNU*) func_path_progs_result=$_G_path_prog _G_path_prog_found=: ;; *) $_G_check_func $_G_path_prog func_path_progs_result=$func_check_prog_result ;; esac $_G_path_prog_found && break 3 done done done IFS=$_G_save_IFS test -z "$func_path_progs_result" && { echo "no acceptable sed could be found in \$PATH" >&2 exit 1 } } # We want to be able to use the functions in this file before configure # has figured out where the best binaries are kept, which means we have # to search for them ourselves - except when the results are already set # where we skip the searches. # Unless the user overrides by setting SED, search the path for either GNU # sed, or the sed that truncates its output the least. test -z "$SED" && { _G_sed_script=s/aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa/bbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbb/ for _G_i in 1 2 3 4 5 6 7; do _G_sed_script=$_G_sed_script$nl$_G_sed_script done echo "$_G_sed_script" 2>/dev/null | sed 99q >conftest.sed _G_sed_script= func_check_prog_sed () { _G_path_prog=$1 _G_count=0 printf 0123456789 >conftest.in while : do cat conftest.in conftest.in >conftest.tmp mv conftest.tmp conftest.in cp conftest.in conftest.nl echo '' >> conftest.nl "$_G_path_prog" -f conftest.sed conftest.out 2>/dev/null || break diff conftest.out conftest.nl >/dev/null 2>&1 || break _G_count=`expr $_G_count + 1` if test "$_G_count" -gt "$_G_path_prog_max"; then # Best one so far, save it but keep looking for a better one func_check_prog_result=$_G_path_prog _G_path_prog_max=$_G_count fi # 10*(2^10) chars as input seems more than enough test 10 -lt "$_G_count" && break done rm -f conftest.in conftest.tmp conftest.nl conftest.out } func_path_progs "sed gsed" func_check_prog_sed $PATH:/usr/xpg4/bin rm -f conftest.sed SED=$func_path_progs_result } # Unless the user overrides by setting GREP, search the path for either GNU # grep, or the grep that truncates its output the least. test -z "$GREP" && { func_check_prog_grep () { _G_path_prog=$1 _G_count=0 _G_path_prog_max=0 printf 0123456789 >conftest.in while : do cat conftest.in conftest.in >conftest.tmp mv conftest.tmp conftest.in cp conftest.in conftest.nl echo 'GREP' >> conftest.nl "$_G_path_prog" -e 'GREP$' -e '-(cannot match)-' conftest.out 2>/dev/null || break diff conftest.out conftest.nl >/dev/null 2>&1 || break _G_count=`expr $_G_count + 1` if test "$_G_count" -gt "$_G_path_prog_max"; then # Best one so far, save it but keep looking for a better one func_check_prog_result=$_G_path_prog _G_path_prog_max=$_G_count fi # 10*(2^10) chars as input seems more than enough test 10 -lt "$_G_count" && break done rm -f conftest.in conftest.tmp conftest.nl conftest.out } func_path_progs "grep ggrep" func_check_prog_grep $PATH:/usr/xpg4/bin GREP=$func_path_progs_result } ## ------------------------------- ## ## User overridable command paths. ## ## ------------------------------- ## # All uppercase variable names are used for environment variables. These # variables can be overridden by the user before calling a script that # uses them if a suitable command of that name is not already available # in the command search PATH. : ${CP="cp -f"} : ${ECHO="printf %s\n"} : ${EGREP="$GREP -E"} : ${FGREP="$GREP -F"} : ${LN_S="ln -s"} : ${MAKE="make"} : ${MKDIR="mkdir"} : ${MV="mv -f"} : ${RM="rm -f"} : ${SHELL="${CONFIG_SHELL-/bin/sh}"} ## -------------------- ## ## Useful sed snippets. ## ## -------------------- ## sed_dirname='s|/[^/]*$||' sed_basename='s|^.*/||' # Sed substitution that helps us do robust quoting. It backslashifies # metacharacters that are still active within double-quoted strings. sed_quote_subst='s|\([`"$\\]\)|\\\1|g' # Same as above, but do not quote variable references. sed_double_quote_subst='s/\(["`\\]\)/\\\1/g' # Sed substitution that turns a string into a regex matching for the # string literally. sed_make_literal_regex='s|[].[^$\\*\/]|\\&|g' # Sed substitution that converts a w32 file name or path # that contains forward slashes, into one that contains # (escaped) backslashes. A very naive implementation. sed_naive_backslashify='s|\\\\*|\\|g;s|/|\\|g;s|\\|\\\\|g' # Re-'\' parameter expansions in output of sed_double_quote_subst that # were '\'-ed in input to the same. If an odd number of '\' preceded a # '$' in input to sed_double_quote_subst, that '$' was protected from # expansion. Since each input '\' is now two '\'s, look for any number # of runs of four '\'s followed by two '\'s and then a '$'. '\' that '$'. _G_bs='\\' _G_bs2='\\\\' _G_bs4='\\\\\\\\' _G_dollar='\$' sed_double_backslash="\ s/$_G_bs4/&\\ /g s/^$_G_bs2$_G_dollar/$_G_bs&/ s/\\([^$_G_bs]\\)$_G_bs2$_G_dollar/\\1$_G_bs2$_G_bs$_G_dollar/g s/\n//g" ## ----------------- ## ## Global variables. ## ## ----------------- ## # Except for the global variables explicitly listed below, the following # functions in the '^func_' namespace, and the '^require_' namespace # variables initialised in the 'Resource management' section, sourcing # this file will not pollute your global namespace with anything # else. There's no portable way to scope variables in Bourne shell # though, so actually running these functions will sometimes place # results into a variable named after the function, and often use # temporary variables in the '^_G_' namespace. If you are careful to # avoid using those namespaces casually in your sourcing script, things # should continue to work as you expect. And, of course, you can freely # overwrite any of the functions or variables defined here before # calling anything to customize them. EXIT_SUCCESS=0 EXIT_FAILURE=1 EXIT_MISMATCH=63 # $? = 63 is used to indicate version mismatch to missing. EXIT_SKIP=77 # $? = 77 is used to indicate a skipped test to automake. # Allow overriding, eg assuming that you follow the convention of # putting '$debug_cmd' at the start of all your functions, you can get # bash to show function call trace with: # # debug_cmd='eval echo "${FUNCNAME[0]} $*" >&2' bash your-script-name debug_cmd=${debug_cmd-":"} exit_cmd=: # By convention, finish your script with: # # exit $exit_status # # so that you can set exit_status to non-zero if you want to indicate # something went wrong during execution without actually bailing out at # the point of failure. exit_status=$EXIT_SUCCESS # Work around backward compatibility issue on IRIX 6.5. On IRIX 6.4+, sh # is ksh but when the shell is invoked as "sh" and the current value of # the _XPG environment variable is not equal to 1 (one), the special # positional parameter $0, within a function call, is the name of the # function. progpath=$0 # The name of this program. progname=`$ECHO "$progpath" |$SED "$sed_basename"` # Make sure we have an absolute progpath for reexecution: case $progpath in [\\/]*|[A-Za-z]:\\*) ;; *[\\/]*) progdir=`$ECHO "$progpath" |$SED "$sed_dirname"` progdir=`cd "$progdir" && pwd` progpath=$progdir/$progname ;; *) _G_IFS=$IFS IFS=${PATH_SEPARATOR-:} for progdir in $PATH; do IFS=$_G_IFS test -x "$progdir/$progname" && break done IFS=$_G_IFS test -n "$progdir" || progdir=`pwd` progpath=$progdir/$progname ;; esac ## ----------------- ## ## Standard options. ## ## ----------------- ## # The following options affect the operation of the functions defined # below, and should be set appropriately depending on run-time para- # meters passed on the command line. opt_dry_run=false opt_quiet=false opt_verbose=false # Categories 'all' and 'none' are always available. Append any others # you will pass as the first argument to func_warning from your own # code. warning_categories= # By default, display warnings according to 'opt_warning_types'. Set # 'warning_func' to ':' to elide all warnings, or func_fatal_error to # treat the next displayed warning as a fatal error. warning_func=func_warn_and_continue # Set to 'all' to display all warnings, 'none' to suppress all # warnings, or a space delimited list of some subset of # 'warning_categories' to display only the listed warnings. opt_warning_types=all ## -------------------- ## ## Resource management. ## ## -------------------- ## # This section contains definitions for functions that each ensure a # particular resource (a file, or a non-empty configuration variable for # example) is available, and if appropriate to extract default values # from pertinent package files. Call them using their associated # 'require_*' variable to ensure that they are executed, at most, once. # # It's entirely deliberate that calling these functions can set # variables that don't obey the namespace limitations obeyed by the rest # of this file, in order that that they be as useful as possible to # callers. # require_term_colors # ------------------- # Allow display of bold text on terminals that support it. require_term_colors=func_require_term_colors func_require_term_colors () { $debug_cmd test -t 1 && { # COLORTERM and USE_ANSI_COLORS environment variables take # precedence, because most terminfo databases neglect to describe # whether color sequences are supported. test -n "${COLORTERM+set}" && : ${USE_ANSI_COLORS="1"} if test 1 = "$USE_ANSI_COLORS"; then # Standard ANSI escape sequences tc_reset='' tc_bold=''; tc_standout='' tc_red=''; tc_green='' tc_blue=''; tc_cyan='' else # Otherwise trust the terminfo database after all. test -n "`tput sgr0 2>/dev/null`" && { tc_reset=`tput sgr0` test -n "`tput bold 2>/dev/null`" && tc_bold=`tput bold` tc_standout=$tc_bold test -n "`tput smso 2>/dev/null`" && tc_standout=`tput smso` test -n "`tput setaf 1 2>/dev/null`" && tc_red=`tput setaf 1` test -n "`tput setaf 2 2>/dev/null`" && tc_green=`tput setaf 2` test -n "`tput setaf 4 2>/dev/null`" && tc_blue=`tput setaf 4` test -n "`tput setaf 5 2>/dev/null`" && tc_cyan=`tput setaf 5` } fi } require_term_colors=: } ## ----------------- ## ## Function library. ## ## ----------------- ## # This section contains a variety of useful functions to call in your # scripts. Take note of the portable wrappers for features provided by # some modern shells, which will fall back to slower equivalents on # less featureful shells. # func_append VAR VALUE # --------------------- # Append VALUE onto the existing contents of VAR. # We should try to minimise forks, especially on Windows where they are # unreasonably slow, so skip the feature probes when bash or zsh are # being used: if test set = "${BASH_VERSION+set}${ZSH_VERSION+set}"; then : ${_G_HAVE_ARITH_OP="yes"} : ${_G_HAVE_XSI_OPS="yes"} # The += operator was introduced in bash 3.1 case $BASH_VERSION in [12].* | 3.0 | 3.0*) ;; *) : ${_G_HAVE_PLUSEQ_OP="yes"} ;; esac fi # _G_HAVE_PLUSEQ_OP # Can be empty, in which case the shell is probed, "yes" if += is # useable or anything else if it does not work. test -z "$_G_HAVE_PLUSEQ_OP" \ && (eval 'x=a; x+=" b"; test "a b" = "$x"') 2>/dev/null \ && _G_HAVE_PLUSEQ_OP=yes if test yes = "$_G_HAVE_PLUSEQ_OP" then # This is an XSI compatible shell, allowing a faster implementation... eval 'func_append () { $debug_cmd eval "$1+=\$2" }' else # ...otherwise fall back to using expr, which is often a shell builtin. func_append () { $debug_cmd eval "$1=\$$1\$2" } fi # func_append_quoted VAR VALUE # ---------------------------- # Quote VALUE and append to the end of shell variable VAR, separated # by a space. if test yes = "$_G_HAVE_PLUSEQ_OP"; then eval 'func_append_quoted () { $debug_cmd func_quote_for_eval "$2" eval "$1+=\\ \$func_quote_for_eval_result" }' else func_append_quoted () { $debug_cmd func_quote_for_eval "$2" eval "$1=\$$1\\ \$func_quote_for_eval_result" } fi # func_append_uniq VAR VALUE # -------------------------- # Append unique VALUE onto the existing contents of VAR, assuming # entries are delimited by the first character of VALUE. For example: # # func_append_uniq options " --another-option option-argument" # # will only append to $options if " --another-option option-argument " # is not already present somewhere in $options already (note spaces at # each end implied by leading space in second argument). func_append_uniq () { $debug_cmd eval _G_current_value='`$ECHO $'$1'`' _G_delim=`expr "$2" : '\(.\)'` case $_G_delim$_G_current_value$_G_delim in *"$2$_G_delim"*) ;; *) func_append "$@" ;; esac } # func_arith TERM... # ------------------ # Set func_arith_result to the result of evaluating TERMs. test -z "$_G_HAVE_ARITH_OP" \ && (eval 'test 2 = $(( 1 + 1 ))') 2>/dev/null \ && _G_HAVE_ARITH_OP=yes if test yes = "$_G_HAVE_ARITH_OP"; then eval 'func_arith () { $debug_cmd func_arith_result=$(( $* )) }' else func_arith () { $debug_cmd func_arith_result=`expr "$@"` } fi # func_basename FILE # ------------------ # Set func_basename_result to FILE with everything up to and including # the last / stripped. if test yes = "$_G_HAVE_XSI_OPS"; then # If this shell supports suffix pattern removal, then use it to avoid # forking. Hide the definitions single quotes in case the shell chokes # on unsupported syntax... _b='func_basename_result=${1##*/}' _d='case $1 in */*) func_dirname_result=${1%/*}$2 ;; * ) func_dirname_result=$3 ;; esac' else # ...otherwise fall back to using sed. _b='func_basename_result=`$ECHO "$1" |$SED "$sed_basename"`' _d='func_dirname_result=`$ECHO "$1" |$SED "$sed_dirname"` if test "X$func_dirname_result" = "X$1"; then func_dirname_result=$3 else func_append func_dirname_result "$2" fi' fi eval 'func_basename () { $debug_cmd '"$_b"' }' # func_dirname FILE APPEND NONDIR_REPLACEMENT # ------------------------------------------- # Compute the dirname of FILE. If nonempty, add APPEND to the result, # otherwise set result to NONDIR_REPLACEMENT. eval 'func_dirname () { $debug_cmd '"$_d"' }' # func_dirname_and_basename FILE APPEND NONDIR_REPLACEMENT # -------------------------------------------------------- # Perform func_basename and func_dirname in a single function # call: # dirname: Compute the dirname of FILE. If nonempty, # add APPEND to the result, otherwise set result # to NONDIR_REPLACEMENT. # value returned in "$func_dirname_result" # basename: Compute filename of FILE. # value retuned in "$func_basename_result" # For efficiency, we do not delegate to the functions above but instead # duplicate the functionality here. eval 'func_dirname_and_basename () { $debug_cmd '"$_b"' '"$_d"' }' # func_echo ARG... # ---------------- # Echo program name prefixed message. func_echo () { $debug_cmd _G_message=$* func_echo_IFS=$IFS IFS=$nl for _G_line in $_G_message; do IFS=$func_echo_IFS $ECHO "$progname: $_G_line" done IFS=$func_echo_IFS } # func_echo_all ARG... # -------------------- # Invoke $ECHO with all args, space-separated. func_echo_all () { $ECHO "$*" } # func_echo_infix_1 INFIX ARG... # ------------------------------ # Echo program name, followed by INFIX on the first line, with any # additional lines not showing INFIX. func_echo_infix_1 () { $debug_cmd $require_term_colors _G_infix=$1; shift _G_indent=$_G_infix _G_prefix="$progname: $_G_infix: " _G_message=$* # Strip color escape sequences before counting printable length for _G_tc in "$tc_reset" "$tc_bold" "$tc_standout" "$tc_red" "$tc_green" "$tc_blue" "$tc_cyan" do test -n "$_G_tc" && { _G_esc_tc=`$ECHO "$_G_tc" | $SED "$sed_make_literal_regex"` _G_indent=`$ECHO "$_G_indent" | $SED "s|$_G_esc_tc||g"` } done _G_indent="$progname: "`echo "$_G_indent" | $SED 's|.| |g'`" " ## exclude from sc_prohibit_nested_quotes func_echo_infix_1_IFS=$IFS IFS=$nl for _G_line in $_G_message; do IFS=$func_echo_infix_1_IFS $ECHO "$_G_prefix$tc_bold$_G_line$tc_reset" >&2 _G_prefix=$_G_indent done IFS=$func_echo_infix_1_IFS } # func_error ARG... # ----------------- # Echo program name prefixed message to standard error. func_error () { $debug_cmd $require_term_colors func_echo_infix_1 " $tc_standout${tc_red}error$tc_reset" "$*" >&2 } # func_fatal_error ARG... # ----------------------- # Echo program name prefixed message to standard error, and exit. func_fatal_error () { $debug_cmd func_error "$*" exit $EXIT_FAILURE } # func_grep EXPRESSION FILENAME # ----------------------------- # Check whether EXPRESSION matches any line of FILENAME, without output. func_grep () { $debug_cmd $GREP "$1" "$2" >/dev/null 2>&1 } # func_len STRING # --------------- # Set func_len_result to the length of STRING. STRING may not # start with a hyphen. test -z "$_G_HAVE_XSI_OPS" \ && (eval 'x=a/b/c; test 5aa/bb/cc = "${#x}${x%%/*}${x%/*}${x#*/}${x##*/}"') 2>/dev/null \ && _G_HAVE_XSI_OPS=yes if test yes = "$_G_HAVE_XSI_OPS"; then eval 'func_len () { $debug_cmd func_len_result=${#1} }' else func_len () { $debug_cmd func_len_result=`expr "$1" : ".*" 2>/dev/null || echo $max_cmd_len` } fi # func_mkdir_p DIRECTORY-PATH # --------------------------- # Make sure the entire path to DIRECTORY-PATH is available. func_mkdir_p () { $debug_cmd _G_directory_path=$1 _G_dir_list= if test -n "$_G_directory_path" && test : != "$opt_dry_run"; then # Protect directory names starting with '-' case $_G_directory_path in -*) _G_directory_path=./$_G_directory_path ;; esac # While some portion of DIR does not yet exist... while test ! -d "$_G_directory_path"; do # ...make a list in topmost first order. Use a colon delimited # list incase some portion of path contains whitespace. _G_dir_list=$_G_directory_path:$_G_dir_list # If the last portion added has no slash in it, the list is done case $_G_directory_path in */*) ;; *) break ;; esac # ...otherwise throw away the child directory and loop _G_directory_path=`$ECHO "$_G_directory_path" | $SED -e "$sed_dirname"` done _G_dir_list=`$ECHO "$_G_dir_list" | $SED 's|:*$||'` func_mkdir_p_IFS=$IFS; IFS=: for _G_dir in $_G_dir_list; do IFS=$func_mkdir_p_IFS # mkdir can fail with a 'File exist' error if two processes # try to create one of the directories concurrently. Don't # stop in that case! $MKDIR "$_G_dir" 2>/dev/null || : done IFS=$func_mkdir_p_IFS # Bail out if we (or some other process) failed to create a directory. test -d "$_G_directory_path" || \ func_fatal_error "Failed to create '$1'" fi } # func_mktempdir [BASENAME] # ------------------------- # Make a temporary directory that won't clash with other running # libtool processes, and avoids race conditions if possible. If # given, BASENAME is the basename for that directory. func_mktempdir () { $debug_cmd _G_template=${TMPDIR-/tmp}/${1-$progname} if test : = "$opt_dry_run"; then # Return a directory name, but don't create it in dry-run mode _G_tmpdir=$_G_template-$$ else # If mktemp works, use that first and foremost _G_tmpdir=`mktemp -d "$_G_template-XXXXXXXX" 2>/dev/null` if test ! -d "$_G_tmpdir"; then # Failing that, at least try and use $RANDOM to avoid a race _G_tmpdir=$_G_template-${RANDOM-0}$$ func_mktempdir_umask=`umask` umask 0077 $MKDIR "$_G_tmpdir" umask $func_mktempdir_umask fi # If we're not in dry-run mode, bomb out on failure test -d "$_G_tmpdir" || \ func_fatal_error "cannot create temporary directory '$_G_tmpdir'" fi $ECHO "$_G_tmpdir" } # func_normal_abspath PATH # ------------------------ # Remove doubled-up and trailing slashes, "." path components, # and cancel out any ".." path components in PATH after making # it an absolute path. func_normal_abspath () { $debug_cmd # These SED scripts presuppose an absolute path with a trailing slash. _G_pathcar='s|^/\([^/]*\).*$|\1|' _G_pathcdr='s|^/[^/]*||' _G_removedotparts=':dotsl s|/\./|/|g t dotsl s|/\.$|/|' _G_collapseslashes='s|/\{1,\}|/|g' _G_finalslash='s|/*$|/|' # Start from root dir and reassemble the path. func_normal_abspath_result= func_normal_abspath_tpath=$1 func_normal_abspath_altnamespace= case $func_normal_abspath_tpath in "") # Empty path, that just means $cwd. func_stripname '' '/' "`pwd`" func_normal_abspath_result=$func_stripname_result return ;; # The next three entries are used to spot a run of precisely # two leading slashes without using negated character classes; # we take advantage of case's first-match behaviour. ///*) # Unusual form of absolute path, do nothing. ;; //*) # Not necessarily an ordinary path; POSIX reserves leading '//' # and for example Cygwin uses it to access remote file shares # over CIFS/SMB, so we conserve a leading double slash if found. func_normal_abspath_altnamespace=/ ;; /*) # Absolute path, do nothing. ;; *) # Relative path, prepend $cwd. func_normal_abspath_tpath=`pwd`/$func_normal_abspath_tpath ;; esac # Cancel out all the simple stuff to save iterations. We also want # the path to end with a slash for ease of parsing, so make sure # there is one (and only one) here. func_normal_abspath_tpath=`$ECHO "$func_normal_abspath_tpath" | $SED \ -e "$_G_removedotparts" -e "$_G_collapseslashes" -e "$_G_finalslash"` while :; do # Processed it all yet? if test / = "$func_normal_abspath_tpath"; then # If we ascended to the root using ".." the result may be empty now. if test -z "$func_normal_abspath_result"; then func_normal_abspath_result=/ fi break fi func_normal_abspath_tcomponent=`$ECHO "$func_normal_abspath_tpath" | $SED \ -e "$_G_pathcar"` func_normal_abspath_tpath=`$ECHO "$func_normal_abspath_tpath" | $SED \ -e "$_G_pathcdr"` # Figure out what to do with it case $func_normal_abspath_tcomponent in "") # Trailing empty path component, ignore it. ;; ..) # Parent dir; strip last assembled component from result. func_dirname "$func_normal_abspath_result" func_normal_abspath_result=$func_dirname_result ;; *) # Actual path component, append it. func_append func_normal_abspath_result "/$func_normal_abspath_tcomponent" ;; esac done # Restore leading double-slash if one was found on entry. func_normal_abspath_result=$func_normal_abspath_altnamespace$func_normal_abspath_result } # func_notquiet ARG... # -------------------- # Echo program name prefixed message only when not in quiet mode. func_notquiet () { $debug_cmd $opt_quiet || func_echo ${1+"$@"} # A bug in bash halts the script if the last line of a function # fails when set -e is in force, so we need another command to # work around that: : } # func_relative_path SRCDIR DSTDIR # -------------------------------- # Set func_relative_path_result to the relative path from SRCDIR to DSTDIR. func_relative_path () { $debug_cmd func_relative_path_result= func_normal_abspath "$1" func_relative_path_tlibdir=$func_normal_abspath_result func_normal_abspath "$2" func_relative_path_tbindir=$func_normal_abspath_result # Ascend the tree starting from libdir while :; do # check if we have found a prefix of bindir case $func_relative_path_tbindir in $func_relative_path_tlibdir) # found an exact match func_relative_path_tcancelled= break ;; $func_relative_path_tlibdir*) # found a matching prefix func_stripname "$func_relative_path_tlibdir" '' "$func_relative_path_tbindir" func_relative_path_tcancelled=$func_stripname_result if test -z "$func_relative_path_result"; then func_relative_path_result=. fi break ;; *) func_dirname $func_relative_path_tlibdir func_relative_path_tlibdir=$func_dirname_result if test -z "$func_relative_path_tlibdir"; then # Have to descend all the way to the root! func_relative_path_result=../$func_relative_path_result func_relative_path_tcancelled=$func_relative_path_tbindir break fi func_relative_path_result=../$func_relative_path_result ;; esac done # Now calculate path; take care to avoid doubling-up slashes. func_stripname '' '/' "$func_relative_path_result" func_relative_path_result=$func_stripname_result func_stripname '/' '/' "$func_relative_path_tcancelled" if test -n "$func_stripname_result"; then func_append func_relative_path_result "/$func_stripname_result" fi # Normalisation. If bindir is libdir, return '.' else relative path. if test -n "$func_relative_path_result"; then func_stripname './' '' "$func_relative_path_result" func_relative_path_result=$func_stripname_result fi test -n "$func_relative_path_result" || func_relative_path_result=. : } # func_quote_for_eval ARG... # -------------------------- # Aesthetically quote ARGs to be evaled later. # This function returns two values: # i) func_quote_for_eval_result # double-quoted, suitable for a subsequent eval # ii) func_quote_for_eval_unquoted_result # has all characters that are still active within double # quotes backslashified. func_quote_for_eval () { $debug_cmd func_quote_for_eval_unquoted_result= func_quote_for_eval_result= while test 0 -lt $#; do case $1 in *[\\\`\"\$]*) _G_unquoted_arg=`printf '%s\n' "$1" |$SED "$sed_quote_subst"` ;; *) _G_unquoted_arg=$1 ;; esac if test -n "$func_quote_for_eval_unquoted_result"; then func_append func_quote_for_eval_unquoted_result " $_G_unquoted_arg" else func_append func_quote_for_eval_unquoted_result "$_G_unquoted_arg" fi case $_G_unquoted_arg in # Double-quote args containing shell metacharacters to delay # word splitting, command substitution and variable expansion # for a subsequent eval. # Many Bourne shells cannot handle close brackets correctly # in scan sets, so we specify it separately. *[\[\~\#\^\&\*\(\)\{\}\|\;\<\>\?\'\ \ ]*|*]*|"") _G_quoted_arg=\"$_G_unquoted_arg\" ;; *) _G_quoted_arg=$_G_unquoted_arg ;; esac if test -n "$func_quote_for_eval_result"; then func_append func_quote_for_eval_result " $_G_quoted_arg" else func_append func_quote_for_eval_result "$_G_quoted_arg" fi shift done } # func_quote_for_expand ARG # ------------------------- # Aesthetically quote ARG to be evaled later; same as above, # but do not quote variable references. func_quote_for_expand () { $debug_cmd case $1 in *[\\\`\"]*) _G_arg=`$ECHO "$1" | $SED \ -e "$sed_double_quote_subst" -e "$sed_double_backslash"` ;; *) _G_arg=$1 ;; esac case $_G_arg in # Double-quote args containing shell metacharacters to delay # word splitting and command substitution for a subsequent eval. # Many Bourne shells cannot handle close brackets correctly # in scan sets, so we specify it separately. *[\[\~\#\^\&\*\(\)\{\}\|\;\<\>\?\'\ \ ]*|*]*|"") _G_arg=\"$_G_arg\" ;; esac func_quote_for_expand_result=$_G_arg } # func_stripname PREFIX SUFFIX NAME # --------------------------------- # strip PREFIX and SUFFIX from NAME, and store in func_stripname_result. # PREFIX and SUFFIX must not contain globbing or regex special # characters, hashes, percent signs, but SUFFIX may contain a leading # dot (in which case that matches only a dot). if test yes = "$_G_HAVE_XSI_OPS"; then eval 'func_stripname () { $debug_cmd # pdksh 5.2.14 does not do ${X%$Y} correctly if both X and Y are # positional parameters, so assign one to ordinary variable first. func_stripname_result=$3 func_stripname_result=${func_stripname_result#"$1"} func_stripname_result=${func_stripname_result%"$2"} }' else func_stripname () { $debug_cmd case $2 in .*) func_stripname_result=`$ECHO "$3" | $SED -e "s%^$1%%" -e "s%\\\\$2\$%%"`;; *) func_stripname_result=`$ECHO "$3" | $SED -e "s%^$1%%" -e "s%$2\$%%"`;; esac } fi # func_show_eval CMD [FAIL_EXP] # ----------------------------- # Unless opt_quiet is true, then output CMD. Then, if opt_dryrun is # not true, evaluate CMD. If the evaluation of CMD fails, and FAIL_EXP # is given, then evaluate it. func_show_eval () { $debug_cmd _G_cmd=$1 _G_fail_exp=${2-':'} func_quote_for_expand "$_G_cmd" eval "func_notquiet $func_quote_for_expand_result" $opt_dry_run || { eval "$_G_cmd" _G_status=$? if test 0 -ne "$_G_status"; then eval "(exit $_G_status); $_G_fail_exp" fi } } # func_show_eval_locale CMD [FAIL_EXP] # ------------------------------------ # Unless opt_quiet is true, then output CMD. Then, if opt_dryrun is # not true, evaluate CMD. If the evaluation of CMD fails, and FAIL_EXP # is given, then evaluate it. Use the saved locale for evaluation. func_show_eval_locale () { $debug_cmd _G_cmd=$1 _G_fail_exp=${2-':'} $opt_quiet || { func_quote_for_expand "$_G_cmd" eval "func_echo $func_quote_for_expand_result" } $opt_dry_run || { eval "$_G_user_locale $_G_cmd" _G_status=$? eval "$_G_safe_locale" if test 0 -ne "$_G_status"; then eval "(exit $_G_status); $_G_fail_exp" fi } } # func_tr_sh # ---------- # Turn $1 into a string suitable for a shell variable name. # Result is stored in $func_tr_sh_result. All characters # not in the set a-zA-Z0-9_ are replaced with '_'. Further, # if $1 begins with a digit, a '_' is prepended as well. func_tr_sh () { $debug_cmd case $1 in [0-9]* | *[!a-zA-Z0-9_]*) func_tr_sh_result=`$ECHO "$1" | $SED -e 's/^\([0-9]\)/_\1/' -e 's/[^a-zA-Z0-9_]/_/g'` ;; * ) func_tr_sh_result=$1 ;; esac } # func_verbose ARG... # ------------------- # Echo program name prefixed message in verbose mode only. func_verbose () { $debug_cmd $opt_verbose && func_echo "$*" : } # func_warn_and_continue ARG... # ----------------------------- # Echo program name prefixed warning message to standard error. func_warn_and_continue () { $debug_cmd $require_term_colors func_echo_infix_1 "${tc_red}warning$tc_reset" "$*" >&2 } # func_warning CATEGORY ARG... # ---------------------------- # Echo program name prefixed warning message to standard error. Warning # messages can be filtered according to CATEGORY, where this function # elides messages where CATEGORY is not listed in the global variable # 'opt_warning_types'. func_warning () { $debug_cmd # CATEGORY must be in the warning_categories list! case " $warning_categories " in *" $1 "*) ;; *) func_internal_error "invalid warning category '$1'" ;; esac _G_category=$1 shift case " $opt_warning_types " in *" $_G_category "*) $warning_func ${1+"$@"} ;; esac } # func_sort_ver VER1 VER2 # ----------------------- # 'sort -V' is not generally available. # Note this deviates from the version comparison in automake # in that it treats 1.5 < 1.5.0, and treats 1.4.4a < 1.4-p3a # but this should suffice as we won't be specifying old # version formats or redundant trailing .0 in bootstrap.conf. # If we did want full compatibility then we should probably # use m4_version_compare from autoconf. func_sort_ver () { $debug_cmd printf '%s\n%s\n' "$1" "$2" \ | sort -t. -k 1,1n -k 2,2n -k 3,3n -k 4,4n -k 5,5n -k 6,6n -k 7,7n -k 8,8n -k 9,9n } # func_lt_ver PREV CURR # --------------------- # Return true if PREV and CURR are in the correct order according to # func_sort_ver, otherwise false. Use it like this: # # func_lt_ver "$prev_ver" "$proposed_ver" || func_fatal_error "..." func_lt_ver () { $debug_cmd test "x$1" = x`func_sort_ver "$1" "$2" | $SED 1q` } # Local variables: # mode: shell-script # sh-indentation: 2 # eval: (add-hook 'before-save-hook 'time-stamp) # time-stamp-pattern: "10/scriptversion=%:y-%02m-%02d.%02H; # UTC" # time-stamp-time-zone: "UTC" # End: #! /bin/sh # Set a version string for this script. scriptversion=2014-01-07.03; # UTC # A portable, pluggable option parser for Bourne shell. # Written by Gary V. Vaughan, 2010 # Copyright (C) 2010-2015 Free Software Foundation, Inc. # This is free software; see the source for copying conditions. There is NO # warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. # This program is free software: you can redistribute it and/or modify # it under the terms of the GNU General Public License as published by # the Free Software Foundation, either version 3 of the License, or # (at your option) any later version. # This program is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the # GNU General Public License for more details. # You should have received a copy of the GNU General Public License # along with this program. If not, see . # Please report bugs or propose patches to gary@gnu.org. ## ------ ## ## Usage. ## ## ------ ## # This file is a library for parsing options in your shell scripts along # with assorted other useful supporting features that you can make use # of too. # # For the simplest scripts you might need only: # # #!/bin/sh # . relative/path/to/funclib.sh # . relative/path/to/options-parser # scriptversion=1.0 # func_options ${1+"$@"} # eval set dummy "$func_options_result"; shift # ...rest of your script... # # In order for the '--version' option to work, you will need to have a # suitably formatted comment like the one at the top of this file # starting with '# Written by ' and ending with '# warranty; '. # # For '-h' and '--help' to work, you will also need a one line # description of your script's purpose in a comment directly above the # '# Written by ' line, like the one at the top of this file. # # The default options also support '--debug', which will turn on shell # execution tracing (see the comment above debug_cmd below for another # use), and '--verbose' and the func_verbose function to allow your script # to display verbose messages only when your user has specified # '--verbose'. # # After sourcing this file, you can plug processing for additional # options by amending the variables from the 'Configuration' section # below, and following the instructions in the 'Option parsing' # section further down. ## -------------- ## ## Configuration. ## ## -------------- ## # You should override these variables in your script after sourcing this # file so that they reflect the customisations you have added to the # option parser. # The usage line for option parsing errors and the start of '-h' and # '--help' output messages. You can embed shell variables for delayed # expansion at the time the message is displayed, but you will need to # quote other shell meta-characters carefully to prevent them being # expanded when the contents are evaled. usage='$progpath [OPTION]...' # Short help message in response to '-h' and '--help'. Add to this or # override it after sourcing this library to reflect the full set of # options your script accepts. usage_message="\ --debug enable verbose shell tracing -W, --warnings=CATEGORY report the warnings falling in CATEGORY [all] -v, --verbose verbosely report processing --version print version information and exit -h, --help print short or long help message and exit " # Additional text appended to 'usage_message' in response to '--help'. long_help_message=" Warning categories include: 'all' show all warnings 'none' turn off all the warnings 'error' warnings are treated as fatal errors" # Help message printed before fatal option parsing errors. fatal_help="Try '\$progname --help' for more information." ## ------------------------- ## ## Hook function management. ## ## ------------------------- ## # This section contains functions for adding, removing, and running hooks # to the main code. A hook is just a named list of of function, that can # be run in order later on. # func_hookable FUNC_NAME # ----------------------- # Declare that FUNC_NAME will run hooks added with # 'func_add_hook FUNC_NAME ...'. func_hookable () { $debug_cmd func_append hookable_fns " $1" } # func_add_hook FUNC_NAME HOOK_FUNC # --------------------------------- # Request that FUNC_NAME call HOOK_FUNC before it returns. FUNC_NAME must # first have been declared "hookable" by a call to 'func_hookable'. func_add_hook () { $debug_cmd case " $hookable_fns " in *" $1 "*) ;; *) func_fatal_error "'$1' does not accept hook functions." ;; esac eval func_append ${1}_hooks '" $2"' } # func_remove_hook FUNC_NAME HOOK_FUNC # ------------------------------------ # Remove HOOK_FUNC from the list of functions called by FUNC_NAME. func_remove_hook () { $debug_cmd eval ${1}_hooks='`$ECHO "\$'$1'_hooks" |$SED "s| '$2'||"`' } # func_run_hooks FUNC_NAME [ARG]... # --------------------------------- # Run all hook functions registered to FUNC_NAME. # It is assumed that the list of hook functions contains nothing more # than a whitespace-delimited list of legal shell function names, and # no effort is wasted trying to catch shell meta-characters or preserve # whitespace. func_run_hooks () { $debug_cmd case " $hookable_fns " in *" $1 "*) ;; *) func_fatal_error "'$1' does not support hook funcions.n" ;; esac eval _G_hook_fns=\$$1_hooks; shift for _G_hook in $_G_hook_fns; do eval $_G_hook '"$@"' # store returned options list back into positional # parameters for next 'cmd' execution. eval _G_hook_result=\$${_G_hook}_result eval set dummy "$_G_hook_result"; shift done func_quote_for_eval ${1+"$@"} func_run_hooks_result=$func_quote_for_eval_result } ## --------------- ## ## Option parsing. ## ## --------------- ## # In order to add your own option parsing hooks, you must accept the # full positional parameter list in your hook function, remove any # options that you action, and then pass back the remaining unprocessed # options in '_result', escaped suitably for # 'eval'. Like this: # # my_options_prep () # { # $debug_cmd # # # Extend the existing usage message. # usage_message=$usage_message' # -s, --silent don'\''t print informational messages # ' # # func_quote_for_eval ${1+"$@"} # my_options_prep_result=$func_quote_for_eval_result # } # func_add_hook func_options_prep my_options_prep # # # my_silent_option () # { # $debug_cmd # # # Note that for efficiency, we parse as many options as we can # # recognise in a loop before passing the remainder back to the # # caller on the first unrecognised argument we encounter. # while test $# -gt 0; do # opt=$1; shift # case $opt in # --silent|-s) opt_silent=: ;; # # Separate non-argument short options: # -s*) func_split_short_opt "$_G_opt" # set dummy "$func_split_short_opt_name" \ # "-$func_split_short_opt_arg" ${1+"$@"} # shift # ;; # *) set dummy "$_G_opt" "$*"; shift; break ;; # esac # done # # func_quote_for_eval ${1+"$@"} # my_silent_option_result=$func_quote_for_eval_result # } # func_add_hook func_parse_options my_silent_option # # # my_option_validation () # { # $debug_cmd # # $opt_silent && $opt_verbose && func_fatal_help "\ # '--silent' and '--verbose' options are mutually exclusive." # # func_quote_for_eval ${1+"$@"} # my_option_validation_result=$func_quote_for_eval_result # } # func_add_hook func_validate_options my_option_validation # # You'll alse need to manually amend $usage_message to reflect the extra # options you parse. It's preferable to append if you can, so that # multiple option parsing hooks can be added safely. # func_options [ARG]... # --------------------- # All the functions called inside func_options are hookable. See the # individual implementations for details. func_hookable func_options func_options () { $debug_cmd func_options_prep ${1+"$@"} eval func_parse_options \ ${func_options_prep_result+"$func_options_prep_result"} eval func_validate_options \ ${func_parse_options_result+"$func_parse_options_result"} eval func_run_hooks func_options \ ${func_validate_options_result+"$func_validate_options_result"} # save modified positional parameters for caller func_options_result=$func_run_hooks_result } # func_options_prep [ARG]... # -------------------------- # All initialisations required before starting the option parse loop. # Note that when calling hook functions, we pass through the list of # positional parameters. If a hook function modifies that list, and # needs to propogate that back to rest of this script, then the complete # modified list must be put in 'func_run_hooks_result' before # returning. func_hookable func_options_prep func_options_prep () { $debug_cmd # Option defaults: opt_verbose=false opt_warning_types= func_run_hooks func_options_prep ${1+"$@"} # save modified positional parameters for caller func_options_prep_result=$func_run_hooks_result } # func_parse_options [ARG]... # --------------------------- # The main option parsing loop. func_hookable func_parse_options func_parse_options () { $debug_cmd func_parse_options_result= # this just eases exit handling while test $# -gt 0; do # Defer to hook functions for initial option parsing, so they # get priority in the event of reusing an option name. func_run_hooks func_parse_options ${1+"$@"} # Adjust func_parse_options positional parameters to match eval set dummy "$func_run_hooks_result"; shift # Break out of the loop if we already parsed every option. test $# -gt 0 || break _G_opt=$1 shift case $_G_opt in --debug|-x) debug_cmd='set -x' func_echo "enabling shell trace mode" $debug_cmd ;; --no-warnings|--no-warning|--no-warn) set dummy --warnings none ${1+"$@"} shift ;; --warnings|--warning|-W) test $# = 0 && func_missing_arg $_G_opt && break case " $warning_categories $1" in *" $1 "*) # trailing space prevents matching last $1 above func_append_uniq opt_warning_types " $1" ;; *all) opt_warning_types=$warning_categories ;; *none) opt_warning_types=none warning_func=: ;; *error) opt_warning_types=$warning_categories warning_func=func_fatal_error ;; *) func_fatal_error \ "unsupported warning category: '$1'" ;; esac shift ;; --verbose|-v) opt_verbose=: ;; --version) func_version ;; -\?|-h) func_usage ;; --help) func_help ;; # Separate optargs to long options (plugins may need this): --*=*) func_split_equals "$_G_opt" set dummy "$func_split_equals_lhs" \ "$func_split_equals_rhs" ${1+"$@"} shift ;; # Separate optargs to short options: -W*) func_split_short_opt "$_G_opt" set dummy "$func_split_short_opt_name" \ "$func_split_short_opt_arg" ${1+"$@"} shift ;; # Separate non-argument short options: -\?*|-h*|-v*|-x*) func_split_short_opt "$_G_opt" set dummy "$func_split_short_opt_name" \ "-$func_split_short_opt_arg" ${1+"$@"} shift ;; --) break ;; -*) func_fatal_help "unrecognised option: '$_G_opt'" ;; *) set dummy "$_G_opt" ${1+"$@"}; shift; break ;; esac done # save modified positional parameters for caller func_quote_for_eval ${1+"$@"} func_parse_options_result=$func_quote_for_eval_result } # func_validate_options [ARG]... # ------------------------------ # Perform any sanity checks on option settings and/or unconsumed # arguments. func_hookable func_validate_options func_validate_options () { $debug_cmd # Display all warnings if -W was not given. test -n "$opt_warning_types" || opt_warning_types=" $warning_categories" func_run_hooks func_validate_options ${1+"$@"} # Bail if the options were screwed! $exit_cmd $EXIT_FAILURE # save modified positional parameters for caller func_validate_options_result=$func_run_hooks_result } ## ----------------- ## ## Helper functions. ## ## ----------------- ## # This section contains the helper functions used by the rest of the # hookable option parser framework in ascii-betical order. # func_fatal_help ARG... # ---------------------- # Echo program name prefixed message to standard error, followed by # a help hint, and exit. func_fatal_help () { $debug_cmd eval \$ECHO \""Usage: $usage"\" eval \$ECHO \""$fatal_help"\" func_error ${1+"$@"} exit $EXIT_FAILURE } # func_help # --------- # Echo long help message to standard output and exit. func_help () { $debug_cmd func_usage_message $ECHO "$long_help_message" exit 0 } # func_missing_arg ARGNAME # ------------------------ # Echo program name prefixed message to standard error and set global # exit_cmd. func_missing_arg () { $debug_cmd func_error "Missing argument for '$1'." exit_cmd=exit } # func_split_equals STRING # ------------------------ # Set func_split_equals_lhs and func_split_equals_rhs shell variables after # splitting STRING at the '=' sign. test -z "$_G_HAVE_XSI_OPS" \ && (eval 'x=a/b/c; test 5aa/bb/cc = "${#x}${x%%/*}${x%/*}${x#*/}${x##*/}"') 2>/dev/null \ && _G_HAVE_XSI_OPS=yes if test yes = "$_G_HAVE_XSI_OPS" then # This is an XSI compatible shell, allowing a faster implementation... eval 'func_split_equals () { $debug_cmd func_split_equals_lhs=${1%%=*} func_split_equals_rhs=${1#*=} test "x$func_split_equals_lhs" = "x$1" \ && func_split_equals_rhs= }' else # ...otherwise fall back to using expr, which is often a shell builtin. func_split_equals () { $debug_cmd func_split_equals_lhs=`expr "x$1" : 'x\([^=]*\)'` func_split_equals_rhs= test "x$func_split_equals_lhs" = "x$1" \ || func_split_equals_rhs=`expr "x$1" : 'x[^=]*=\(.*\)$'` } fi #func_split_equals # func_split_short_opt SHORTOPT # ----------------------------- # Set func_split_short_opt_name and func_split_short_opt_arg shell # variables after splitting SHORTOPT after the 2nd character. if test yes = "$_G_HAVE_XSI_OPS" then # This is an XSI compatible shell, allowing a faster implementation... eval 'func_split_short_opt () { $debug_cmd func_split_short_opt_arg=${1#??} func_split_short_opt_name=${1%"$func_split_short_opt_arg"} }' else # ...otherwise fall back to using expr, which is often a shell builtin. func_split_short_opt () { $debug_cmd func_split_short_opt_name=`expr "x$1" : 'x-\(.\)'` func_split_short_opt_arg=`expr "x$1" : 'x-.\(.*\)$'` } fi #func_split_short_opt # func_usage # ---------- # Echo short help message to standard output and exit. func_usage () { $debug_cmd func_usage_message $ECHO "Run '$progname --help |${PAGER-more}' for full usage" exit 0 } # func_usage_message # ------------------ # Echo short help message to standard output. func_usage_message () { $debug_cmd eval \$ECHO \""Usage: $usage"\" echo $SED -n 's|^# || /^Written by/{ x;p;x } h /^Written by/q' < "$progpath" echo eval \$ECHO \""$usage_message"\" } # func_version # ------------ # Echo version message to standard output and exit. func_version () { $debug_cmd printf '%s\n' "$progname $scriptversion" $SED -n ' /(C)/!b go :more /\./!{ N s|\n# | | b more } :go /^# Written by /,/# warranty; / { s|^# || s|^# *$|| s|\((C)\)[ 0-9,-]*[ ,-]\([1-9][0-9]* \)|\1 \2| p } /^# Written by / { s|^# || p } /^warranty; /q' < "$progpath" exit $? } # Local variables: # mode: shell-script # sh-indentation: 2 # eval: (add-hook 'before-save-hook 'time-stamp) # time-stamp-pattern: "10/scriptversion=%:y-%02m-%02d.%02H; # UTC" # time-stamp-time-zone: "UTC" # End: # Set a version string. scriptversion='(GNU libtool) 2.4.6' # func_echo ARG... # ---------------- # Libtool also displays the current mode in messages, so override # funclib.sh func_echo with this custom definition. func_echo () { $debug_cmd _G_message=$* func_echo_IFS=$IFS IFS=$nl for _G_line in $_G_message; do IFS=$func_echo_IFS $ECHO "$progname${opt_mode+: $opt_mode}: $_G_line" done IFS=$func_echo_IFS } # func_warning ARG... # ------------------- # Libtool warnings are not categorized, so override funclib.sh # func_warning with this simpler definition. func_warning () { $debug_cmd $warning_func ${1+"$@"} } ## ---------------- ## ## Options parsing. ## ## ---------------- ## # Hook in the functions to make sure our own options are parsed during # the option parsing loop. usage='$progpath [OPTION]... [MODE-ARG]...' # Short help message in response to '-h'. usage_message="Options: --config show all configuration variables --debug enable verbose shell tracing -n, --dry-run display commands without modifying any files --features display basic configuration information and exit --mode=MODE use operation mode MODE --no-warnings equivalent to '-Wnone' --preserve-dup-deps don't remove duplicate dependency libraries --quiet, --silent don't print informational messages --tag=TAG use configuration variables from tag TAG -v, --verbose print more informational messages than default --version print version information -W, --warnings=CATEGORY report the warnings falling in CATEGORY [all] -h, --help, --help-all print short, long, or detailed help message " # Additional text appended to 'usage_message' in response to '--help'. func_help () { $debug_cmd func_usage_message $ECHO "$long_help_message MODE must be one of the following: clean remove files from the build directory compile compile a source file into a libtool object execute automatically set library path, then run a program finish complete the installation of libtool libraries install install libraries or executables link create a library or an executable uninstall remove libraries from an installed directory MODE-ARGS vary depending on the MODE. When passed as first option, '--mode=MODE' may be abbreviated as 'MODE' or a unique abbreviation of that. Try '$progname --help --mode=MODE' for a more detailed description of MODE. When reporting a bug, please describe a test case to reproduce it and include the following information: host-triplet: $host shell: $SHELL compiler: $LTCC compiler flags: $LTCFLAGS linker: $LD (gnu? $with_gnu_ld) version: $progname $scriptversion Debian-2.4.6-2 automake: `($AUTOMAKE --version) 2>/dev/null |$SED 1q` autoconf: `($AUTOCONF --version) 2>/dev/null |$SED 1q` Report bugs to . GNU libtool home page: . General help using GNU software: ." exit 0 } # func_lo2o OBJECT-NAME # --------------------- # Transform OBJECT-NAME from a '.lo' suffix to the platform specific # object suffix. lo2o=s/\\.lo\$/.$objext/ o2lo=s/\\.$objext\$/.lo/ if test yes = "$_G_HAVE_XSI_OPS"; then eval 'func_lo2o () { case $1 in *.lo) func_lo2o_result=${1%.lo}.$objext ;; * ) func_lo2o_result=$1 ;; esac }' # func_xform LIBOBJ-OR-SOURCE # --------------------------- # Transform LIBOBJ-OR-SOURCE from a '.o' or '.c' (or otherwise) # suffix to a '.lo' libtool-object suffix. eval 'func_xform () { func_xform_result=${1%.*}.lo }' else # ...otherwise fall back to using sed. func_lo2o () { func_lo2o_result=`$ECHO "$1" | $SED "$lo2o"` } func_xform () { func_xform_result=`$ECHO "$1" | $SED 's|\.[^.]*$|.lo|'` } fi # func_fatal_configuration ARG... # ------------------------------- # Echo program name prefixed message to standard error, followed by # a configuration failure hint, and exit. func_fatal_configuration () { func__fatal_error ${1+"$@"} \ "See the $PACKAGE documentation for more information." \ "Fatal configuration error." } # func_config # ----------- # Display the configuration for all the tags in this script. func_config () { re_begincf='^# ### BEGIN LIBTOOL' re_endcf='^# ### END LIBTOOL' # Default configuration. $SED "1,/$re_begincf CONFIG/d;/$re_endcf CONFIG/,\$d" < "$progpath" # Now print the configurations for the tags. for tagname in $taglist; do $SED -n "/$re_begincf TAG CONFIG: $tagname\$/,/$re_endcf TAG CONFIG: $tagname\$/p" < "$progpath" done exit $? } # func_features # ------------- # Display the features supported by this script. func_features () { echo "host: $host" if test yes = "$build_libtool_libs"; then echo "enable shared libraries" else echo "disable shared libraries" fi if test yes = "$build_old_libs"; then echo "enable static libraries" else echo "disable static libraries" fi exit $? } # func_enable_tag TAGNAME # ----------------------- # Verify that TAGNAME is valid, and either flag an error and exit, or # enable the TAGNAME tag. We also add TAGNAME to the global $taglist # variable here. func_enable_tag () { # Global variable: tagname=$1 re_begincf="^# ### BEGIN LIBTOOL TAG CONFIG: $tagname\$" re_endcf="^# ### END LIBTOOL TAG CONFIG: $tagname\$" sed_extractcf=/$re_begincf/,/$re_endcf/p # Validate tagname. case $tagname in *[!-_A-Za-z0-9,/]*) func_fatal_error "invalid tag name: $tagname" ;; esac # Don't test for the "default" C tag, as we know it's # there but not specially marked. case $tagname in CC) ;; *) if $GREP "$re_begincf" "$progpath" >/dev/null 2>&1; then taglist="$taglist $tagname" # Evaluate the configuration. Be careful to quote the path # and the sed script, to avoid splitting on whitespace, but # also don't use non-portable quotes within backquotes within # quotes we have to do it in 2 steps: extractedcf=`$SED -n -e "$sed_extractcf" < "$progpath"` eval "$extractedcf" else func_error "ignoring unknown tag $tagname" fi ;; esac } # func_check_version_match # ------------------------ # Ensure that we are using m4 macros, and libtool script from the same # release of libtool. func_check_version_match () { if test "$package_revision" != "$macro_revision"; then if test "$VERSION" != "$macro_version"; then if test -z "$macro_version"; then cat >&2 <<_LT_EOF $progname: Version mismatch error. This is $PACKAGE $VERSION, but the $progname: definition of this LT_INIT comes from an older release. $progname: You should recreate aclocal.m4 with macros from $PACKAGE $VERSION $progname: and run autoconf again. _LT_EOF else cat >&2 <<_LT_EOF $progname: Version mismatch error. This is $PACKAGE $VERSION, but the $progname: definition of this LT_INIT comes from $PACKAGE $macro_version. $progname: You should recreate aclocal.m4 with macros from $PACKAGE $VERSION $progname: and run autoconf again. _LT_EOF fi else cat >&2 <<_LT_EOF $progname: Version mismatch error. This is $PACKAGE $VERSION, revision $package_revision, $progname: but the definition of this LT_INIT comes from revision $macro_revision. $progname: You should recreate aclocal.m4 with macros from revision $package_revision $progname: of $PACKAGE $VERSION and run autoconf again. _LT_EOF fi exit $EXIT_MISMATCH fi } # libtool_options_prep [ARG]... # ----------------------------- # Preparation for options parsed by libtool. libtool_options_prep () { $debug_mode # Option defaults: opt_config=false opt_dlopen= opt_dry_run=false opt_help=false opt_mode= opt_preserve_dup_deps=false opt_quiet=false nonopt= preserve_args= # Shorthand for --mode=foo, only valid as the first argument case $1 in clean|clea|cle|cl) shift; set dummy --mode clean ${1+"$@"}; shift ;; compile|compil|compi|comp|com|co|c) shift; set dummy --mode compile ${1+"$@"}; shift ;; execute|execut|execu|exec|exe|ex|e) shift; set dummy --mode execute ${1+"$@"}; shift ;; finish|finis|fini|fin|fi|f) shift; set dummy --mode finish ${1+"$@"}; shift ;; install|instal|insta|inst|ins|in|i) shift; set dummy --mode install ${1+"$@"}; shift ;; link|lin|li|l) shift; set dummy --mode link ${1+"$@"}; shift ;; uninstall|uninstal|uninsta|uninst|unins|unin|uni|un|u) shift; set dummy --mode uninstall ${1+"$@"}; shift ;; esac # Pass back the list of options. func_quote_for_eval ${1+"$@"} libtool_options_prep_result=$func_quote_for_eval_result } func_add_hook func_options_prep libtool_options_prep # libtool_parse_options [ARG]... # --------------------------------- # Provide handling for libtool specific options. libtool_parse_options () { $debug_cmd # Perform our own loop to consume as many options as possible in # each iteration. while test $# -gt 0; do _G_opt=$1 shift case $_G_opt in --dry-run|--dryrun|-n) opt_dry_run=: ;; --config) func_config ;; --dlopen|-dlopen) opt_dlopen="${opt_dlopen+$opt_dlopen }$1" shift ;; --preserve-dup-deps) opt_preserve_dup_deps=: ;; --features) func_features ;; --finish) set dummy --mode finish ${1+"$@"}; shift ;; --help) opt_help=: ;; --help-all) opt_help=': help-all' ;; --mode) test $# = 0 && func_missing_arg $_G_opt && break opt_mode=$1 case $1 in # Valid mode arguments: clean|compile|execute|finish|install|link|relink|uninstall) ;; # Catch anything else as an error *) func_error "invalid argument for $_G_opt" exit_cmd=exit break ;; esac shift ;; --no-silent|--no-quiet) opt_quiet=false func_append preserve_args " $_G_opt" ;; --no-warnings|--no-warning|--no-warn) opt_warning=false func_append preserve_args " $_G_opt" ;; --no-verbose) opt_verbose=false func_append preserve_args " $_G_opt" ;; --silent|--quiet) opt_quiet=: opt_verbose=false func_append preserve_args " $_G_opt" ;; --tag) test $# = 0 && func_missing_arg $_G_opt && break opt_tag=$1 func_append preserve_args " $_G_opt $1" func_enable_tag "$1" shift ;; --verbose|-v) opt_quiet=false opt_verbose=: func_append preserve_args " $_G_opt" ;; # An option not handled by this hook function: *) set dummy "$_G_opt" ${1+"$@"}; shift; break ;; esac done # save modified positional parameters for caller func_quote_for_eval ${1+"$@"} libtool_parse_options_result=$func_quote_for_eval_result } func_add_hook func_parse_options libtool_parse_options # libtool_validate_options [ARG]... # --------------------------------- # Perform any sanity checks on option settings and/or unconsumed # arguments. libtool_validate_options () { # save first non-option argument if test 0 -lt $#; then nonopt=$1 shift fi # preserve --debug test : = "$debug_cmd" || func_append preserve_args " --debug" case $host in # Solaris2 added to fix http://debbugs.gnu.org/cgi/bugreport.cgi?bug=16452 # see also: http://gcc.gnu.org/bugzilla/show_bug.cgi?id=59788 *cygwin* | *mingw* | *pw32* | *cegcc* | *solaris2* | *os2*) # don't eliminate duplications in $postdeps and $predeps opt_duplicate_compiler_generated_deps=: ;; *) opt_duplicate_compiler_generated_deps=$opt_preserve_dup_deps ;; esac $opt_help || { # Sanity checks first: func_check_version_match test yes != "$build_libtool_libs" \ && test yes != "$build_old_libs" \ && func_fatal_configuration "not configured to build any kind of library" # Darwin sucks eval std_shrext=\"$shrext_cmds\" # Only execute mode is allowed to have -dlopen flags. if test -n "$opt_dlopen" && test execute != "$opt_mode"; then func_error "unrecognized option '-dlopen'" $ECHO "$help" 1>&2 exit $EXIT_FAILURE fi # Change the help message to a mode-specific one. generic_help=$help help="Try '$progname --help --mode=$opt_mode' for more information." } # Pass back the unparsed argument list func_quote_for_eval ${1+"$@"} libtool_validate_options_result=$func_quote_for_eval_result } func_add_hook func_validate_options libtool_validate_options # Process options as early as possible so that --help and --version # can return quickly. func_options ${1+"$@"} eval set dummy "$func_options_result"; shift ## ----------- ## ## Main. ## ## ----------- ## magic='%%%MAGIC variable%%%' magic_exe='%%%MAGIC EXE variable%%%' # Global variables. extracted_archives= extracted_serial=0 # If this variable is set in any of the actions, the command in it # will be execed at the end. This prevents here-documents from being # left over by shells. exec_cmd= # A function that is used when there is no print builtin or printf. func_fallback_echo () { eval 'cat <<_LTECHO_EOF $1 _LTECHO_EOF' } # func_generated_by_libtool # True iff stdin has been generated by Libtool. This function is only # a basic sanity check; it will hardly flush out determined imposters. func_generated_by_libtool_p () { $GREP "^# Generated by .*$PACKAGE" > /dev/null 2>&1 } # func_lalib_p file # True iff FILE is a libtool '.la' library or '.lo' object file. # This function is only a basic sanity check; it will hardly flush out # determined imposters. func_lalib_p () { test -f "$1" && $SED -e 4q "$1" 2>/dev/null | func_generated_by_libtool_p } # func_lalib_unsafe_p file # True iff FILE is a libtool '.la' library or '.lo' object file. # This function implements the same check as func_lalib_p without # resorting to external programs. To this end, it redirects stdin and # closes it afterwards, without saving the original file descriptor. # As a safety measure, use it only where a negative result would be # fatal anyway. Works if 'file' does not exist. func_lalib_unsafe_p () { lalib_p=no if test -f "$1" && test -r "$1" && exec 5<&0 <"$1"; then for lalib_p_l in 1 2 3 4 do read lalib_p_line case $lalib_p_line in \#\ Generated\ by\ *$PACKAGE* ) lalib_p=yes; break;; esac done exec 0<&5 5<&- fi test yes = "$lalib_p" } # func_ltwrapper_script_p file # True iff FILE is a libtool wrapper script # This function is only a basic sanity check; it will hardly flush out # determined imposters. func_ltwrapper_script_p () { test -f "$1" && $lt_truncate_bin < "$1" 2>/dev/null | func_generated_by_libtool_p } # func_ltwrapper_executable_p file # True iff FILE is a libtool wrapper executable # This function is only a basic sanity check; it will hardly flush out # determined imposters. func_ltwrapper_executable_p () { func_ltwrapper_exec_suffix= case $1 in *.exe) ;; *) func_ltwrapper_exec_suffix=.exe ;; esac $GREP "$magic_exe" "$1$func_ltwrapper_exec_suffix" >/dev/null 2>&1 } # func_ltwrapper_scriptname file # Assumes file is an ltwrapper_executable # uses $file to determine the appropriate filename for a # temporary ltwrapper_script. func_ltwrapper_scriptname () { func_dirname_and_basename "$1" "" "." func_stripname '' '.exe' "$func_basename_result" func_ltwrapper_scriptname_result=$func_dirname_result/$objdir/${func_stripname_result}_ltshwrapper } # func_ltwrapper_p file # True iff FILE is a libtool wrapper script or wrapper executable # This function is only a basic sanity check; it will hardly flush out # determined imposters. func_ltwrapper_p () { func_ltwrapper_script_p "$1" || func_ltwrapper_executable_p "$1" } # func_execute_cmds commands fail_cmd # Execute tilde-delimited COMMANDS. # If FAIL_CMD is given, eval that upon failure. # FAIL_CMD may read-access the current command in variable CMD! func_execute_cmds () { $debug_cmd save_ifs=$IFS; IFS='~' for cmd in $1; do IFS=$sp$nl eval cmd=\"$cmd\" IFS=$save_ifs func_show_eval "$cmd" "${2-:}" done IFS=$save_ifs } # func_source file # Source FILE, adding directory component if necessary. # Note that it is not necessary on cygwin/mingw to append a dot to # FILE even if both FILE and FILE.exe exist: automatic-append-.exe # behavior happens only for exec(3), not for open(2)! Also, sourcing # 'FILE.' does not work on cygwin managed mounts. func_source () { $debug_cmd case $1 in */* | *\\*) . "$1" ;; *) . "./$1" ;; esac } # func_resolve_sysroot PATH # Replace a leading = in PATH with a sysroot. Store the result into # func_resolve_sysroot_result func_resolve_sysroot () { func_resolve_sysroot_result=$1 case $func_resolve_sysroot_result in =*) func_stripname '=' '' "$func_resolve_sysroot_result" func_resolve_sysroot_result=$lt_sysroot$func_stripname_result ;; esac } # func_replace_sysroot PATH # If PATH begins with the sysroot, replace it with = and # store the result into func_replace_sysroot_result. func_replace_sysroot () { case $lt_sysroot:$1 in ?*:"$lt_sysroot"*) func_stripname "$lt_sysroot" '' "$1" func_replace_sysroot_result='='$func_stripname_result ;; *) # Including no sysroot. func_replace_sysroot_result=$1 ;; esac } # func_infer_tag arg # Infer tagged configuration to use if any are available and # if one wasn't chosen via the "--tag" command line option. # Only attempt this if the compiler in the base compile # command doesn't match the default compiler. # arg is usually of the form 'gcc ...' func_infer_tag () { $debug_cmd if test -n "$available_tags" && test -z "$tagname"; then CC_quoted= for arg in $CC; do func_append_quoted CC_quoted "$arg" done CC_expanded=`func_echo_all $CC` CC_quoted_expanded=`func_echo_all $CC_quoted` case $@ in # Blanks in the command may have been stripped by the calling shell, # but not from the CC environment variable when configure was run. " $CC "* | "$CC "* | " $CC_expanded "* | "$CC_expanded "* | \ " $CC_quoted"* | "$CC_quoted "* | " $CC_quoted_expanded "* | "$CC_quoted_expanded "*) ;; # Blanks at the start of $base_compile will cause this to fail # if we don't check for them as well. *) for z in $available_tags; do if $GREP "^# ### BEGIN LIBTOOL TAG CONFIG: $z$" < "$progpath" > /dev/null; then # Evaluate the configuration. eval "`$SED -n -e '/^# ### BEGIN LIBTOOL TAG CONFIG: '$z'$/,/^# ### END LIBTOOL TAG CONFIG: '$z'$/p' < $progpath`" CC_quoted= for arg in $CC; do # Double-quote args containing other shell metacharacters. func_append_quoted CC_quoted "$arg" done CC_expanded=`func_echo_all $CC` CC_quoted_expanded=`func_echo_all $CC_quoted` case "$@ " in " $CC "* | "$CC "* | " $CC_expanded "* | "$CC_expanded "* | \ " $CC_quoted"* | "$CC_quoted "* | " $CC_quoted_expanded "* | "$CC_quoted_expanded "*) # The compiler in the base compile command matches # the one in the tagged configuration. # Assume this is the tagged configuration we want. tagname=$z break ;; esac fi done # If $tagname still isn't set, then no tagged configuration # was found and let the user know that the "--tag" command # line option must be used. if test -z "$tagname"; then func_echo "unable to infer tagged configuration" func_fatal_error "specify a tag with '--tag'" # else # func_verbose "using $tagname tagged configuration" fi ;; esac fi } # func_write_libtool_object output_name pic_name nonpic_name # Create a libtool object file (analogous to a ".la" file), # but don't create it if we're doing a dry run. func_write_libtool_object () { write_libobj=$1 if test yes = "$build_libtool_libs"; then write_lobj=\'$2\' else write_lobj=none fi if test yes = "$build_old_libs"; then write_oldobj=\'$3\' else write_oldobj=none fi $opt_dry_run || { cat >${write_libobj}T </dev/null` if test "$?" -eq 0 && test -n "$func_convert_core_file_wine_to_w32_tmp"; then func_convert_core_file_wine_to_w32_result=`$ECHO "$func_convert_core_file_wine_to_w32_tmp" | $SED -e "$sed_naive_backslashify"` else func_convert_core_file_wine_to_w32_result= fi fi } # end: func_convert_core_file_wine_to_w32 # func_convert_core_path_wine_to_w32 ARG # Helper function used by path conversion functions when $build is *nix, and # $host is mingw, cygwin, or some other w32 environment. Relies on a correctly # configured wine environment available, with the winepath program in $build's # $PATH. Assumes ARG has no leading or trailing path separator characters. # # ARG is path to be converted from $build format to win32. # Result is available in $func_convert_core_path_wine_to_w32_result. # Unconvertible file (directory) names in ARG are skipped; if no directory names # are convertible, then the result may be empty. func_convert_core_path_wine_to_w32 () { $debug_cmd # unfortunately, winepath doesn't convert paths, only file names func_convert_core_path_wine_to_w32_result= if test -n "$1"; then oldIFS=$IFS IFS=: for func_convert_core_path_wine_to_w32_f in $1; do IFS=$oldIFS func_convert_core_file_wine_to_w32 "$func_convert_core_path_wine_to_w32_f" if test -n "$func_convert_core_file_wine_to_w32_result"; then if test -z "$func_convert_core_path_wine_to_w32_result"; then func_convert_core_path_wine_to_w32_result=$func_convert_core_file_wine_to_w32_result else func_append func_convert_core_path_wine_to_w32_result ";$func_convert_core_file_wine_to_w32_result" fi fi done IFS=$oldIFS fi } # end: func_convert_core_path_wine_to_w32 # func_cygpath ARGS... # Wrapper around calling the cygpath program via LT_CYGPATH. This is used when # when (1) $build is *nix and Cygwin is hosted via a wine environment; or (2) # $build is MSYS and $host is Cygwin, or (3) $build is Cygwin. In case (1) or # (2), returns the Cygwin file name or path in func_cygpath_result (input # file name or path is assumed to be in w32 format, as previously converted # from $build's *nix or MSYS format). In case (3), returns the w32 file name # or path in func_cygpath_result (input file name or path is assumed to be in # Cygwin format). Returns an empty string on error. # # ARGS are passed to cygpath, with the last one being the file name or path to # be converted. # # Specify the absolute *nix (or w32) name to cygpath in the LT_CYGPATH # environment variable; do not put it in $PATH. func_cygpath () { $debug_cmd if test -n "$LT_CYGPATH" && test -f "$LT_CYGPATH"; then func_cygpath_result=`$LT_CYGPATH "$@" 2>/dev/null` if test "$?" -ne 0; then # on failure, ensure result is empty func_cygpath_result= fi else func_cygpath_result= func_error "LT_CYGPATH is empty or specifies non-existent file: '$LT_CYGPATH'" fi } #end: func_cygpath # func_convert_core_msys_to_w32 ARG # Convert file name or path ARG from MSYS format to w32 format. Return # result in func_convert_core_msys_to_w32_result. func_convert_core_msys_to_w32 () { $debug_cmd # awkward: cmd appends spaces to result func_convert_core_msys_to_w32_result=`( cmd //c echo "$1" ) 2>/dev/null | $SED -e 's/[ ]*$//' -e "$sed_naive_backslashify"` } #end: func_convert_core_msys_to_w32 # func_convert_file_check ARG1 ARG2 # Verify that ARG1 (a file name in $build format) was converted to $host # format in ARG2. Otherwise, emit an error message, but continue (resetting # func_to_host_file_result to ARG1). func_convert_file_check () { $debug_cmd if test -z "$2" && test -n "$1"; then func_error "Could not determine host file name corresponding to" func_error " '$1'" func_error "Continuing, but uninstalled executables may not work." # Fallback: func_to_host_file_result=$1 fi } # end func_convert_file_check # func_convert_path_check FROM_PATHSEP TO_PATHSEP FROM_PATH TO_PATH # Verify that FROM_PATH (a path in $build format) was converted to $host # format in TO_PATH. Otherwise, emit an error message, but continue, resetting # func_to_host_file_result to a simplistic fallback value (see below). func_convert_path_check () { $debug_cmd if test -z "$4" && test -n "$3"; then func_error "Could not determine the host path corresponding to" func_error " '$3'" func_error "Continuing, but uninstalled executables may not work." # Fallback. This is a deliberately simplistic "conversion" and # should not be "improved". See libtool.info. if test "x$1" != "x$2"; then lt_replace_pathsep_chars="s|$1|$2|g" func_to_host_path_result=`echo "$3" | $SED -e "$lt_replace_pathsep_chars"` else func_to_host_path_result=$3 fi fi } # end func_convert_path_check # func_convert_path_front_back_pathsep FRONTPAT BACKPAT REPL ORIG # Modifies func_to_host_path_result by prepending REPL if ORIG matches FRONTPAT # and appending REPL if ORIG matches BACKPAT. func_convert_path_front_back_pathsep () { $debug_cmd case $4 in $1 ) func_to_host_path_result=$3$func_to_host_path_result ;; esac case $4 in $2 ) func_append func_to_host_path_result "$3" ;; esac } # end func_convert_path_front_back_pathsep ################################################## # $build to $host FILE NAME CONVERSION FUNCTIONS # ################################################## # invoked via '$to_host_file_cmd ARG' # # In each case, ARG is the path to be converted from $build to $host format. # Result will be available in $func_to_host_file_result. # func_to_host_file ARG # Converts the file name ARG from $build format to $host format. Return result # in func_to_host_file_result. func_to_host_file () { $debug_cmd $to_host_file_cmd "$1" } # end func_to_host_file # func_to_tool_file ARG LAZY # converts the file name ARG from $build format to toolchain format. Return # result in func_to_tool_file_result. If the conversion in use is listed # in (the comma separated) LAZY, no conversion takes place. func_to_tool_file () { $debug_cmd case ,$2, in *,"$to_tool_file_cmd",*) func_to_tool_file_result=$1 ;; *) $to_tool_file_cmd "$1" func_to_tool_file_result=$func_to_host_file_result ;; esac } # end func_to_tool_file # func_convert_file_noop ARG # Copy ARG to func_to_host_file_result. func_convert_file_noop () { func_to_host_file_result=$1 } # end func_convert_file_noop # func_convert_file_msys_to_w32 ARG # Convert file name ARG from (mingw) MSYS to (mingw) w32 format; automatic # conversion to w32 is not available inside the cwrapper. Returns result in # func_to_host_file_result. func_convert_file_msys_to_w32 () { $debug_cmd func_to_host_file_result=$1 if test -n "$1"; then func_convert_core_msys_to_w32 "$1" func_to_host_file_result=$func_convert_core_msys_to_w32_result fi func_convert_file_check "$1" "$func_to_host_file_result" } # end func_convert_file_msys_to_w32 # func_convert_file_cygwin_to_w32 ARG # Convert file name ARG from Cygwin to w32 format. Returns result in # func_to_host_file_result. func_convert_file_cygwin_to_w32 () { $debug_cmd func_to_host_file_result=$1 if test -n "$1"; then # because $build is cygwin, we call "the" cygpath in $PATH; no need to use # LT_CYGPATH in this case. func_to_host_file_result=`cygpath -m "$1"` fi func_convert_file_check "$1" "$func_to_host_file_result" } # end func_convert_file_cygwin_to_w32 # func_convert_file_nix_to_w32 ARG # Convert file name ARG from *nix to w32 format. Requires a wine environment # and a working winepath. Returns result in func_to_host_file_result. func_convert_file_nix_to_w32 () { $debug_cmd func_to_host_file_result=$1 if test -n "$1"; then func_convert_core_file_wine_to_w32 "$1" func_to_host_file_result=$func_convert_core_file_wine_to_w32_result fi func_convert_file_check "$1" "$func_to_host_file_result" } # end func_convert_file_nix_to_w32 # func_convert_file_msys_to_cygwin ARG # Convert file name ARG from MSYS to Cygwin format. Requires LT_CYGPATH set. # Returns result in func_to_host_file_result. func_convert_file_msys_to_cygwin () { $debug_cmd func_to_host_file_result=$1 if test -n "$1"; then func_convert_core_msys_to_w32 "$1" func_cygpath -u "$func_convert_core_msys_to_w32_result" func_to_host_file_result=$func_cygpath_result fi func_convert_file_check "$1" "$func_to_host_file_result" } # end func_convert_file_msys_to_cygwin # func_convert_file_nix_to_cygwin ARG # Convert file name ARG from *nix to Cygwin format. Requires Cygwin installed # in a wine environment, working winepath, and LT_CYGPATH set. Returns result # in func_to_host_file_result. func_convert_file_nix_to_cygwin () { $debug_cmd func_to_host_file_result=$1 if test -n "$1"; then # convert from *nix to w32, then use cygpath to convert from w32 to cygwin. func_convert_core_file_wine_to_w32 "$1" func_cygpath -u "$func_convert_core_file_wine_to_w32_result" func_to_host_file_result=$func_cygpath_result fi func_convert_file_check "$1" "$func_to_host_file_result" } # end func_convert_file_nix_to_cygwin ############################################# # $build to $host PATH CONVERSION FUNCTIONS # ############################################# # invoked via '$to_host_path_cmd ARG' # # In each case, ARG is the path to be converted from $build to $host format. # The result will be available in $func_to_host_path_result. # # Path separators are also converted from $build format to $host format. If # ARG begins or ends with a path separator character, it is preserved (but # converted to $host format) on output. # # All path conversion functions are named using the following convention: # file name conversion function : func_convert_file_X_to_Y () # path conversion function : func_convert_path_X_to_Y () # where, for any given $build/$host combination the 'X_to_Y' value is the # same. If conversion functions are added for new $build/$host combinations, # the two new functions must follow this pattern, or func_init_to_host_path_cmd # will break. # func_init_to_host_path_cmd # Ensures that function "pointer" variable $to_host_path_cmd is set to the # appropriate value, based on the value of $to_host_file_cmd. to_host_path_cmd= func_init_to_host_path_cmd () { $debug_cmd if test -z "$to_host_path_cmd"; then func_stripname 'func_convert_file_' '' "$to_host_file_cmd" to_host_path_cmd=func_convert_path_$func_stripname_result fi } # func_to_host_path ARG # Converts the path ARG from $build format to $host format. Return result # in func_to_host_path_result. func_to_host_path () { $debug_cmd func_init_to_host_path_cmd $to_host_path_cmd "$1" } # end func_to_host_path # func_convert_path_noop ARG # Copy ARG to func_to_host_path_result. func_convert_path_noop () { func_to_host_path_result=$1 } # end func_convert_path_noop # func_convert_path_msys_to_w32 ARG # Convert path ARG from (mingw) MSYS to (mingw) w32 format; automatic # conversion to w32 is not available inside the cwrapper. Returns result in # func_to_host_path_result. func_convert_path_msys_to_w32 () { $debug_cmd func_to_host_path_result=$1 if test -n "$1"; then # Remove leading and trailing path separator characters from ARG. MSYS # behavior is inconsistent here; cygpath turns them into '.;' and ';.'; # and winepath ignores them completely. func_stripname : : "$1" func_to_host_path_tmp1=$func_stripname_result func_convert_core_msys_to_w32 "$func_to_host_path_tmp1" func_to_host_path_result=$func_convert_core_msys_to_w32_result func_convert_path_check : ";" \ "$func_to_host_path_tmp1" "$func_to_host_path_result" func_convert_path_front_back_pathsep ":*" "*:" ";" "$1" fi } # end func_convert_path_msys_to_w32 # func_convert_path_cygwin_to_w32 ARG # Convert path ARG from Cygwin to w32 format. Returns result in # func_to_host_file_result. func_convert_path_cygwin_to_w32 () { $debug_cmd func_to_host_path_result=$1 if test -n "$1"; then # See func_convert_path_msys_to_w32: func_stripname : : "$1" func_to_host_path_tmp1=$func_stripname_result func_to_host_path_result=`cygpath -m -p "$func_to_host_path_tmp1"` func_convert_path_check : ";" \ "$func_to_host_path_tmp1" "$func_to_host_path_result" func_convert_path_front_back_pathsep ":*" "*:" ";" "$1" fi } # end func_convert_path_cygwin_to_w32 # func_convert_path_nix_to_w32 ARG # Convert path ARG from *nix to w32 format. Requires a wine environment and # a working winepath. Returns result in func_to_host_file_result. func_convert_path_nix_to_w32 () { $debug_cmd func_to_host_path_result=$1 if test -n "$1"; then # See func_convert_path_msys_to_w32: func_stripname : : "$1" func_to_host_path_tmp1=$func_stripname_result func_convert_core_path_wine_to_w32 "$func_to_host_path_tmp1" func_to_host_path_result=$func_convert_core_path_wine_to_w32_result func_convert_path_check : ";" \ "$func_to_host_path_tmp1" "$func_to_host_path_result" func_convert_path_front_back_pathsep ":*" "*:" ";" "$1" fi } # end func_convert_path_nix_to_w32 # func_convert_path_msys_to_cygwin ARG # Convert path ARG from MSYS to Cygwin format. Requires LT_CYGPATH set. # Returns result in func_to_host_file_result. func_convert_path_msys_to_cygwin () { $debug_cmd func_to_host_path_result=$1 if test -n "$1"; then # See func_convert_path_msys_to_w32: func_stripname : : "$1" func_to_host_path_tmp1=$func_stripname_result func_convert_core_msys_to_w32 "$func_to_host_path_tmp1" func_cygpath -u -p "$func_convert_core_msys_to_w32_result" func_to_host_path_result=$func_cygpath_result func_convert_path_check : : \ "$func_to_host_path_tmp1" "$func_to_host_path_result" func_convert_path_front_back_pathsep ":*" "*:" : "$1" fi } # end func_convert_path_msys_to_cygwin # func_convert_path_nix_to_cygwin ARG # Convert path ARG from *nix to Cygwin format. Requires Cygwin installed in a # a wine environment, working winepath, and LT_CYGPATH set. Returns result in # func_to_host_file_result. func_convert_path_nix_to_cygwin () { $debug_cmd func_to_host_path_result=$1 if test -n "$1"; then # Remove leading and trailing path separator characters from # ARG. msys behavior is inconsistent here, cygpath turns them # into '.;' and ';.', and winepath ignores them completely. func_stripname : : "$1" func_to_host_path_tmp1=$func_stripname_result func_convert_core_path_wine_to_w32 "$func_to_host_path_tmp1" func_cygpath -u -p "$func_convert_core_path_wine_to_w32_result" func_to_host_path_result=$func_cygpath_result func_convert_path_check : : \ "$func_to_host_path_tmp1" "$func_to_host_path_result" func_convert_path_front_back_pathsep ":*" "*:" : "$1" fi } # end func_convert_path_nix_to_cygwin # func_dll_def_p FILE # True iff FILE is a Windows DLL '.def' file. # Keep in sync with _LT_DLL_DEF_P in libtool.m4 func_dll_def_p () { $debug_cmd func_dll_def_p_tmp=`$SED -n \ -e 's/^[ ]*//' \ -e '/^\(;.*\)*$/d' \ -e 's/^\(EXPORTS\|LIBRARY\)\([ ].*\)*$/DEF/p' \ -e q \ "$1"` test DEF = "$func_dll_def_p_tmp" } # func_mode_compile arg... func_mode_compile () { $debug_cmd # Get the compilation command and the source file. base_compile= srcfile=$nonopt # always keep a non-empty value in "srcfile" suppress_opt=yes suppress_output= arg_mode=normal libobj= later= pie_flag= for arg do case $arg_mode in arg ) # do not "continue". Instead, add this to base_compile lastarg=$arg arg_mode=normal ;; target ) libobj=$arg arg_mode=normal continue ;; normal ) # Accept any command-line options. case $arg in -o) test -n "$libobj" && \ func_fatal_error "you cannot specify '-o' more than once" arg_mode=target continue ;; -pie | -fpie | -fPIE) func_append pie_flag " $arg" continue ;; -shared | -static | -prefer-pic | -prefer-non-pic) func_append later " $arg" continue ;; -no-suppress) suppress_opt=no continue ;; -Xcompiler) arg_mode=arg # the next one goes into the "base_compile" arg list continue # The current "srcfile" will either be retained or ;; # replaced later. I would guess that would be a bug. -Wc,*) func_stripname '-Wc,' '' "$arg" args=$func_stripname_result lastarg= save_ifs=$IFS; IFS=, for arg in $args; do IFS=$save_ifs func_append_quoted lastarg "$arg" done IFS=$save_ifs func_stripname ' ' '' "$lastarg" lastarg=$func_stripname_result # Add the arguments to base_compile. func_append base_compile " $lastarg" continue ;; *) # Accept the current argument as the source file. # The previous "srcfile" becomes the current argument. # lastarg=$srcfile srcfile=$arg ;; esac # case $arg ;; esac # case $arg_mode # Aesthetically quote the previous argument. func_append_quoted base_compile "$lastarg" done # for arg case $arg_mode in arg) func_fatal_error "you must specify an argument for -Xcompile" ;; target) func_fatal_error "you must specify a target with '-o'" ;; *) # Get the name of the library object. test -z "$libobj" && { func_basename "$srcfile" libobj=$func_basename_result } ;; esac # Recognize several different file suffixes. # If the user specifies -o file.o, it is replaced with file.lo case $libobj in *.[cCFSifmso] | \ *.ada | *.adb | *.ads | *.asm | \ *.c++ | *.cc | *.ii | *.class | *.cpp | *.cxx | \ *.[fF][09]? | *.for | *.java | *.go | *.obj | *.sx | *.cu | *.cup) func_xform "$libobj" libobj=$func_xform_result ;; esac case $libobj in *.lo) func_lo2o "$libobj"; obj=$func_lo2o_result ;; *) func_fatal_error "cannot determine name of library object from '$libobj'" ;; esac func_infer_tag $base_compile for arg in $later; do case $arg in -shared) test yes = "$build_libtool_libs" \ || func_fatal_configuration "cannot build a shared library" build_old_libs=no continue ;; -static) build_libtool_libs=no build_old_libs=yes continue ;; -prefer-pic) pic_mode=yes continue ;; -prefer-non-pic) pic_mode=no continue ;; esac done func_quote_for_eval "$libobj" test "X$libobj" != "X$func_quote_for_eval_result" \ && $ECHO "X$libobj" | $GREP '[]~#^*{};<>?"'"'"' &()|`$[]' \ && func_warning "libobj name '$libobj' may not contain shell special characters." func_dirname_and_basename "$obj" "/" "" objname=$func_basename_result xdir=$func_dirname_result lobj=$xdir$objdir/$objname test -z "$base_compile" && \ func_fatal_help "you must specify a compilation command" # Delete any leftover library objects. if test yes = "$build_old_libs"; then removelist="$obj $lobj $libobj ${libobj}T" else removelist="$lobj $libobj ${libobj}T" fi # On Cygwin there's no "real" PIC flag so we must build both object types case $host_os in cygwin* | mingw* | pw32* | os2* | cegcc*) pic_mode=default ;; esac if test no = "$pic_mode" && test pass_all != "$deplibs_check_method"; then # non-PIC code in shared libraries is not supported pic_mode=default fi # Calculate the filename of the output object if compiler does # not support -o with -c if test no = "$compiler_c_o"; then output_obj=`$ECHO "$srcfile" | $SED 's%^.*/%%; s%\.[^.]*$%%'`.$objext lockfile=$output_obj.lock else output_obj= need_locks=no lockfile= fi # Lock this critical section if it is needed # We use this script file to make the link, it avoids creating a new file if test yes = "$need_locks"; then until $opt_dry_run || ln "$progpath" "$lockfile" 2>/dev/null; do func_echo "Waiting for $lockfile to be removed" sleep 2 done elif test warn = "$need_locks"; then if test -f "$lockfile"; then $ECHO "\ *** ERROR, $lockfile exists and contains: `cat $lockfile 2>/dev/null` This indicates that another process is trying to use the same temporary object file, and libtool could not work around it because your compiler does not support '-c' and '-o' together. If you repeat this compilation, it may succeed, by chance, but you had better avoid parallel builds (make -j) in this platform, or get a better compiler." $opt_dry_run || $RM $removelist exit $EXIT_FAILURE fi func_append removelist " $output_obj" $ECHO "$srcfile" > "$lockfile" fi $opt_dry_run || $RM $removelist func_append removelist " $lockfile" trap '$opt_dry_run || $RM $removelist; exit $EXIT_FAILURE' 1 2 15 func_to_tool_file "$srcfile" func_convert_file_msys_to_w32 srcfile=$func_to_tool_file_result func_quote_for_eval "$srcfile" qsrcfile=$func_quote_for_eval_result # Only build a PIC object if we are building libtool libraries. if test yes = "$build_libtool_libs"; then # Without this assignment, base_compile gets emptied. fbsd_hideous_sh_bug=$base_compile if test no != "$pic_mode"; then command="$base_compile $qsrcfile $pic_flag" else # Don't build PIC code command="$base_compile $qsrcfile" fi func_mkdir_p "$xdir$objdir" if test -z "$output_obj"; then # Place PIC objects in $objdir func_append command " -o $lobj" fi func_show_eval_locale "$command" \ 'test -n "$output_obj" && $RM $removelist; exit $EXIT_FAILURE' if test warn = "$need_locks" && test "X`cat $lockfile 2>/dev/null`" != "X$srcfile"; then $ECHO "\ *** ERROR, $lockfile contains: `cat $lockfile 2>/dev/null` but it should contain: $srcfile This indicates that another process is trying to use the same temporary object file, and libtool could not work around it because your compiler does not support '-c' and '-o' together. If you repeat this compilation, it may succeed, by chance, but you had better avoid parallel builds (make -j) in this platform, or get a better compiler." $opt_dry_run || $RM $removelist exit $EXIT_FAILURE fi # Just move the object if needed, then go on to compile the next one if test -n "$output_obj" && test "X$output_obj" != "X$lobj"; then func_show_eval '$MV "$output_obj" "$lobj"' \ 'error=$?; $opt_dry_run || $RM $removelist; exit $error' fi # Allow error messages only from the first compilation. if test yes = "$suppress_opt"; then suppress_output=' >/dev/null 2>&1' fi fi # Only build a position-dependent object if we build old libraries. if test yes = "$build_old_libs"; then if test yes != "$pic_mode"; then # Don't build PIC code command="$base_compile $qsrcfile$pie_flag" else command="$base_compile $qsrcfile $pic_flag" fi if test yes = "$compiler_c_o"; then func_append command " -o $obj" fi # Suppress compiler output if we already did a PIC compilation. func_append command "$suppress_output" func_show_eval_locale "$command" \ '$opt_dry_run || $RM $removelist; exit $EXIT_FAILURE' if test warn = "$need_locks" && test "X`cat $lockfile 2>/dev/null`" != "X$srcfile"; then $ECHO "\ *** ERROR, $lockfile contains: `cat $lockfile 2>/dev/null` but it should contain: $srcfile This indicates that another process is trying to use the same temporary object file, and libtool could not work around it because your compiler does not support '-c' and '-o' together. If you repeat this compilation, it may succeed, by chance, but you had better avoid parallel builds (make -j) in this platform, or get a better compiler." $opt_dry_run || $RM $removelist exit $EXIT_FAILURE fi # Just move the object if needed if test -n "$output_obj" && test "X$output_obj" != "X$obj"; then func_show_eval '$MV "$output_obj" "$obj"' \ 'error=$?; $opt_dry_run || $RM $removelist; exit $error' fi fi $opt_dry_run || { func_write_libtool_object "$libobj" "$objdir/$objname" "$objname" # Unlock the critical section if it was locked if test no != "$need_locks"; then removelist=$lockfile $RM "$lockfile" fi } exit $EXIT_SUCCESS } $opt_help || { test compile = "$opt_mode" && func_mode_compile ${1+"$@"} } func_mode_help () { # We need to display help for each of the modes. case $opt_mode in "") # Generic help is extracted from the usage comments # at the start of this file. func_help ;; clean) $ECHO \ "Usage: $progname [OPTION]... --mode=clean RM [RM-OPTION]... FILE... Remove files from the build directory. RM is the name of the program to use to delete files associated with each FILE (typically '/bin/rm'). RM-OPTIONS are options (such as '-f') to be passed to RM. If FILE is a libtool library, object or program, all the files associated with it are deleted. Otherwise, only FILE itself is deleted using RM." ;; compile) $ECHO \ "Usage: $progname [OPTION]... --mode=compile COMPILE-COMMAND... SOURCEFILE Compile a source file into a libtool library object. This mode accepts the following additional options: -o OUTPUT-FILE set the output file name to OUTPUT-FILE -no-suppress do not suppress compiler output for multiple passes -prefer-pic try to build PIC objects only -prefer-non-pic try to build non-PIC objects only -shared do not build a '.o' file suitable for static linking -static only build a '.o' file suitable for static linking -Wc,FLAG pass FLAG directly to the compiler COMPILE-COMMAND is a command to be used in creating a 'standard' object file from the given SOURCEFILE. The output file name is determined by removing the directory component from SOURCEFILE, then substituting the C source code suffix '.c' with the library object suffix, '.lo'." ;; execute) $ECHO \ "Usage: $progname [OPTION]... --mode=execute COMMAND [ARGS]... Automatically set library path, then run a program. This mode accepts the following additional options: -dlopen FILE add the directory containing FILE to the library path This mode sets the library path environment variable according to '-dlopen' flags. If any of the ARGS are libtool executable wrappers, then they are translated into their corresponding uninstalled binary, and any of their required library directories are added to the library path. Then, COMMAND is executed, with ARGS as arguments." ;; finish) $ECHO \ "Usage: $progname [OPTION]... --mode=finish [LIBDIR]... Complete the installation of libtool libraries. Each LIBDIR is a directory that contains libtool libraries. The commands that this mode executes may require superuser privileges. Use the '--dry-run' option if you just want to see what would be executed." ;; install) $ECHO \ "Usage: $progname [OPTION]... --mode=install INSTALL-COMMAND... Install executables or libraries. INSTALL-COMMAND is the installation command. The first component should be either the 'install' or 'cp' program. The following components of INSTALL-COMMAND are treated specially: -inst-prefix-dir PREFIX-DIR Use PREFIX-DIR as a staging area for installation The rest of the components are interpreted as arguments to that command (only BSD-compatible install options are recognized)." ;; link) $ECHO \ "Usage: $progname [OPTION]... --mode=link LINK-COMMAND... Link object files or libraries together to form another library, or to create an executable program. LINK-COMMAND is a command using the C compiler that you would use to create a program from several object files. The following components of LINK-COMMAND are treated specially: -all-static do not do any dynamic linking at all -avoid-version do not add a version suffix if possible -bindir BINDIR specify path to binaries directory (for systems where libraries must be found in the PATH setting at runtime) -dlopen FILE '-dlpreopen' FILE if it cannot be dlopened at runtime -dlpreopen FILE link in FILE and add its symbols to lt_preloaded_symbols -export-dynamic allow symbols from OUTPUT-FILE to be resolved with dlsym(3) -export-symbols SYMFILE try to export only the symbols listed in SYMFILE -export-symbols-regex REGEX try to export only the symbols matching REGEX -LLIBDIR search LIBDIR for required installed libraries -lNAME OUTPUT-FILE requires the installed library libNAME -module build a library that can dlopened -no-fast-install disable the fast-install mode -no-install link a not-installable executable -no-undefined declare that a library does not refer to external symbols -o OUTPUT-FILE create OUTPUT-FILE from the specified objects -objectlist FILE use a list of object files found in FILE to specify objects -os2dllname NAME force a short DLL name on OS/2 (no effect on other OSes) -precious-files-regex REGEX don't remove output files matching REGEX -release RELEASE specify package release information -rpath LIBDIR the created library will eventually be installed in LIBDIR -R[ ]LIBDIR add LIBDIR to the runtime path of programs and libraries -shared only do dynamic linking of libtool libraries -shrext SUFFIX override the standard shared library file extension -static do not do any dynamic linking of uninstalled libtool libraries -static-libtool-libs do not do any dynamic linking of libtool libraries -version-info CURRENT[:REVISION[:AGE]] specify library version info [each variable defaults to 0] -weak LIBNAME declare that the target provides the LIBNAME interface -Wc,FLAG -Xcompiler FLAG pass linker-specific FLAG directly to the compiler -Wl,FLAG -Xlinker FLAG pass linker-specific FLAG directly to the linker -XCClinker FLAG pass link-specific FLAG to the compiler driver (CC) All other options (arguments beginning with '-') are ignored. Every other argument is treated as a filename. Files ending in '.la' are treated as uninstalled libtool libraries, other files are standard or library object files. If the OUTPUT-FILE ends in '.la', then a libtool library is created, only library objects ('.lo' files) may be specified, and '-rpath' is required, except when creating a convenience library. If OUTPUT-FILE ends in '.a' or '.lib', then a standard library is created using 'ar' and 'ranlib', or on Windows using 'lib'. If OUTPUT-FILE ends in '.lo' or '.$objext', then a reloadable object file is created, otherwise an executable program is created." ;; uninstall) $ECHO \ "Usage: $progname [OPTION]... --mode=uninstall RM [RM-OPTION]... FILE... Remove libraries from an installation directory. RM is the name of the program to use to delete files associated with each FILE (typically '/bin/rm'). RM-OPTIONS are options (such as '-f') to be passed to RM. If FILE is a libtool library, all the files associated with it are deleted. Otherwise, only FILE itself is deleted using RM." ;; *) func_fatal_help "invalid operation mode '$opt_mode'" ;; esac echo $ECHO "Try '$progname --help' for more information about other modes." } # Now that we've collected a possible --mode arg, show help if necessary if $opt_help; then if test : = "$opt_help"; then func_mode_help else { func_help noexit for opt_mode in compile link execute install finish uninstall clean; do func_mode_help done } | $SED -n '1p; 2,$s/^Usage:/ or: /p' { func_help noexit for opt_mode in compile link execute install finish uninstall clean; do echo func_mode_help done } | $SED '1d /^When reporting/,/^Report/{ H d } $x /information about other modes/d /more detailed .*MODE/d s/^Usage:.*--mode=\([^ ]*\) .*/Description of \1 mode:/' fi exit $? fi # func_mode_execute arg... func_mode_execute () { $debug_cmd # The first argument is the command name. cmd=$nonopt test -z "$cmd" && \ func_fatal_help "you must specify a COMMAND" # Handle -dlopen flags immediately. for file in $opt_dlopen; do test -f "$file" \ || func_fatal_help "'$file' is not a file" dir= case $file in *.la) func_resolve_sysroot "$file" file=$func_resolve_sysroot_result # Check to see that this really is a libtool archive. func_lalib_unsafe_p "$file" \ || func_fatal_help "'$lib' is not a valid libtool archive" # Read the libtool library. dlname= library_names= func_source "$file" # Skip this library if it cannot be dlopened. if test -z "$dlname"; then # Warn if it was a shared library. test -n "$library_names" && \ func_warning "'$file' was not linked with '-export-dynamic'" continue fi func_dirname "$file" "" "." dir=$func_dirname_result if test -f "$dir/$objdir/$dlname"; then func_append dir "/$objdir" else if test ! -f "$dir/$dlname"; then func_fatal_error "cannot find '$dlname' in '$dir' or '$dir/$objdir'" fi fi ;; *.lo) # Just add the directory containing the .lo file. func_dirname "$file" "" "." dir=$func_dirname_result ;; *) func_warning "'-dlopen' is ignored for non-libtool libraries and objects" continue ;; esac # Get the absolute pathname. absdir=`cd "$dir" && pwd` test -n "$absdir" && dir=$absdir # Now add the directory to shlibpath_var. if eval "test -z \"\$$shlibpath_var\""; then eval "$shlibpath_var=\"\$dir\"" else eval "$shlibpath_var=\"\$dir:\$$shlibpath_var\"" fi done # This variable tells wrapper scripts just to set shlibpath_var # rather than running their programs. libtool_execute_magic=$magic # Check if any of the arguments is a wrapper script. args= for file do case $file in -* | *.la | *.lo ) ;; *) # Do a test to see if this is really a libtool program. if func_ltwrapper_script_p "$file"; then func_source "$file" # Transform arg to wrapped name. file=$progdir/$program elif func_ltwrapper_executable_p "$file"; then func_ltwrapper_scriptname "$file" func_source "$func_ltwrapper_scriptname_result" # Transform arg to wrapped name. file=$progdir/$program fi ;; esac # Quote arguments (to preserve shell metacharacters). func_append_quoted args "$file" done if $opt_dry_run; then # Display what would be done. if test -n "$shlibpath_var"; then eval "\$ECHO \"\$shlibpath_var=\$$shlibpath_var\"" echo "export $shlibpath_var" fi $ECHO "$cmd$args" exit $EXIT_SUCCESS else if test -n "$shlibpath_var"; then # Export the shlibpath_var. eval "export $shlibpath_var" fi # Restore saved environment variables for lt_var in LANG LANGUAGE LC_ALL LC_CTYPE LC_COLLATE LC_MESSAGES do eval "if test \"\${save_$lt_var+set}\" = set; then $lt_var=\$save_$lt_var; export $lt_var else $lt_unset $lt_var fi" done # Now prepare to actually exec the command. exec_cmd=\$cmd$args fi } test execute = "$opt_mode" && func_mode_execute ${1+"$@"} # func_mode_finish arg... func_mode_finish () { $debug_cmd libs= libdirs= admincmds= for opt in "$nonopt" ${1+"$@"} do if test -d "$opt"; then func_append libdirs " $opt" elif test -f "$opt"; then if func_lalib_unsafe_p "$opt"; then func_append libs " $opt" else func_warning "'$opt' is not a valid libtool archive" fi else func_fatal_error "invalid argument '$opt'" fi done if test -n "$libs"; then if test -n "$lt_sysroot"; then sysroot_regex=`$ECHO "$lt_sysroot" | $SED "$sed_make_literal_regex"` sysroot_cmd="s/\([ ']\)$sysroot_regex/\1/g;" else sysroot_cmd= fi # Remove sysroot references if $opt_dry_run; then for lib in $libs; do echo "removing references to $lt_sysroot and '=' prefixes from $lib" done else tmpdir=`func_mktempdir` for lib in $libs; do $SED -e "$sysroot_cmd s/\([ ']-[LR]\)=/\1/g; s/\([ ']\)=/\1/g" $lib \ > $tmpdir/tmp-la mv -f $tmpdir/tmp-la $lib done ${RM}r "$tmpdir" fi fi if test -n "$finish_cmds$finish_eval" && test -n "$libdirs"; then for libdir in $libdirs; do if test -n "$finish_cmds"; then # Do each command in the finish commands. func_execute_cmds "$finish_cmds" 'admincmds="$admincmds '"$cmd"'"' fi if test -n "$finish_eval"; then # Do the single finish_eval. eval cmds=\"$finish_eval\" $opt_dry_run || eval "$cmds" || func_append admincmds " $cmds" fi done fi # Exit here if they wanted silent mode. $opt_quiet && exit $EXIT_SUCCESS if test -n "$finish_cmds$finish_eval" && test -n "$libdirs"; then echo "----------------------------------------------------------------------" echo "Libraries have been installed in:" for libdir in $libdirs; do $ECHO " $libdir" done echo echo "If you ever happen to want to link against installed libraries" echo "in a given directory, LIBDIR, you must either use libtool, and" echo "specify the full pathname of the library, or use the '-LLIBDIR'" echo "flag during linking and do at least one of the following:" if test -n "$shlibpath_var"; then echo " - add LIBDIR to the '$shlibpath_var' environment variable" echo " during execution" fi if test -n "$runpath_var"; then echo " - add LIBDIR to the '$runpath_var' environment variable" echo " during linking" fi if test -n "$hardcode_libdir_flag_spec"; then libdir=LIBDIR eval flag=\"$hardcode_libdir_flag_spec\" $ECHO " - use the '$flag' linker flag" fi if test -n "$admincmds"; then $ECHO " - have your system administrator run these commands:$admincmds" fi if test -f /etc/ld.so.conf; then echo " - have your system administrator add LIBDIR to '/etc/ld.so.conf'" fi echo echo "See any operating system documentation about shared libraries for" case $host in solaris2.[6789]|solaris2.1[0-9]) echo "more information, such as the ld(1), crle(1) and ld.so(8) manual" echo "pages." ;; *) echo "more information, such as the ld(1) and ld.so(8) manual pages." ;; esac echo "----------------------------------------------------------------------" fi exit $EXIT_SUCCESS } test finish = "$opt_mode" && func_mode_finish ${1+"$@"} # func_mode_install arg... func_mode_install () { $debug_cmd # There may be an optional sh(1) argument at the beginning of # install_prog (especially on Windows NT). if test "$SHELL" = "$nonopt" || test /bin/sh = "$nonopt" || # Allow the use of GNU shtool's install command. case $nonopt in *shtool*) :;; *) false;; esac then # Aesthetically quote it. func_quote_for_eval "$nonopt" install_prog="$func_quote_for_eval_result " arg=$1 shift else install_prog= arg=$nonopt fi # The real first argument should be the name of the installation program. # Aesthetically quote it. func_quote_for_eval "$arg" func_append install_prog "$func_quote_for_eval_result" install_shared_prog=$install_prog case " $install_prog " in *[\\\ /]cp\ *) install_cp=: ;; *) install_cp=false ;; esac # We need to accept at least all the BSD install flags. dest= files= opts= prev= install_type= isdir=false stripme= no_mode=: for arg do arg2= if test -n "$dest"; then func_append files " $dest" dest=$arg continue fi case $arg in -d) isdir=: ;; -f) if $install_cp; then :; else prev=$arg fi ;; -g | -m | -o) prev=$arg ;; -s) stripme=" -s" continue ;; -*) ;; *) # If the previous option needed an argument, then skip it. if test -n "$prev"; then if test X-m = "X$prev" && test -n "$install_override_mode"; then arg2=$install_override_mode no_mode=false fi prev= else dest=$arg continue fi ;; esac # Aesthetically quote the argument. func_quote_for_eval "$arg" func_append install_prog " $func_quote_for_eval_result" if test -n "$arg2"; then func_quote_for_eval "$arg2" fi func_append install_shared_prog " $func_quote_for_eval_result" done test -z "$install_prog" && \ func_fatal_help "you must specify an install program" test -n "$prev" && \ func_fatal_help "the '$prev' option requires an argument" if test -n "$install_override_mode" && $no_mode; then if $install_cp; then :; else func_quote_for_eval "$install_override_mode" func_append install_shared_prog " -m $func_quote_for_eval_result" fi fi if test -z "$files"; then if test -z "$dest"; then func_fatal_help "no file or destination specified" else func_fatal_help "you must specify a destination" fi fi # Strip any trailing slash from the destination. func_stripname '' '/' "$dest" dest=$func_stripname_result # Check to see that the destination is a directory. test -d "$dest" && isdir=: if $isdir; then destdir=$dest destname= else func_dirname_and_basename "$dest" "" "." destdir=$func_dirname_result destname=$func_basename_result # Not a directory, so check to see that there is only one file specified. set dummy $files; shift test "$#" -gt 1 && \ func_fatal_help "'$dest' is not a directory" fi case $destdir in [\\/]* | [A-Za-z]:[\\/]*) ;; *) for file in $files; do case $file in *.lo) ;; *) func_fatal_help "'$destdir' must be an absolute directory name" ;; esac done ;; esac # This variable tells wrapper scripts just to set variables rather # than running their programs. libtool_install_magic=$magic staticlibs= future_libdirs= current_libdirs= for file in $files; do # Do each installation. case $file in *.$libext) # Do the static libraries later. func_append staticlibs " $file" ;; *.la) func_resolve_sysroot "$file" file=$func_resolve_sysroot_result # Check to see that this really is a libtool archive. func_lalib_unsafe_p "$file" \ || func_fatal_help "'$file' is not a valid libtool archive" library_names= old_library= relink_command= func_source "$file" # Add the libdir to current_libdirs if it is the destination. if test "X$destdir" = "X$libdir"; then case "$current_libdirs " in *" $libdir "*) ;; *) func_append current_libdirs " $libdir" ;; esac else # Note the libdir as a future libdir. case "$future_libdirs " in *" $libdir "*) ;; *) func_append future_libdirs " $libdir" ;; esac fi func_dirname "$file" "/" "" dir=$func_dirname_result func_append dir "$objdir" if test -n "$relink_command"; then # Determine the prefix the user has applied to our future dir. inst_prefix_dir=`$ECHO "$destdir" | $SED -e "s%$libdir\$%%"` # Don't allow the user to place us outside of our expected # location b/c this prevents finding dependent libraries that # are installed to the same prefix. # At present, this check doesn't affect windows .dll's that # are installed into $libdir/../bin (currently, that works fine) # but it's something to keep an eye on. test "$inst_prefix_dir" = "$destdir" && \ func_fatal_error "error: cannot install '$file' to a directory not ending in $libdir" if test -n "$inst_prefix_dir"; then # Stick the inst_prefix_dir data into the link command. relink_command=`$ECHO "$relink_command" | $SED "s%@inst_prefix_dir@%-inst-prefix-dir $inst_prefix_dir%"` else relink_command=`$ECHO "$relink_command" | $SED "s%@inst_prefix_dir@%%"` fi func_warning "relinking '$file'" func_show_eval "$relink_command" \ 'func_fatal_error "error: relink '\''$file'\'' with the above command before installing it"' fi # See the names of the shared library. set dummy $library_names; shift if test -n "$1"; then realname=$1 shift srcname=$realname test -n "$relink_command" && srcname=${realname}T # Install the shared library and build the symlinks. func_show_eval "$install_shared_prog $dir/$srcname $destdir/$realname" \ 'exit $?' tstripme=$stripme case $host_os in cygwin* | mingw* | pw32* | cegcc*) case $realname in *.dll.a) tstripme= ;; esac ;; os2*) case $realname in *_dll.a) tstripme= ;; esac ;; esac if test -n "$tstripme" && test -n "$striplib"; then func_show_eval "$striplib $destdir/$realname" 'exit $?' fi if test "$#" -gt 0; then # Delete the old symlinks, and create new ones. # Try 'ln -sf' first, because the 'ln' binary might depend on # the symlink we replace! Solaris /bin/ln does not understand -f, # so we also need to try rm && ln -s. for linkname do test "$linkname" != "$realname" \ && func_show_eval "(cd $destdir && { $LN_S -f $realname $linkname || { $RM $linkname && $LN_S $realname $linkname; }; })" done fi # Do each command in the postinstall commands. lib=$destdir/$realname func_execute_cmds "$postinstall_cmds" 'exit $?' fi # Install the pseudo-library for information purposes. func_basename "$file" name=$func_basename_result instname=$dir/${name}i func_show_eval "$install_prog $instname $destdir/$name" 'exit $?' # Maybe install the static library, too. test -n "$old_library" && func_append staticlibs " $dir/$old_library" ;; *.lo) # Install (i.e. copy) a libtool object. # Figure out destination file name, if it wasn't already specified. if test -n "$destname"; then destfile=$destdir/$destname else func_basename "$file" destfile=$func_basename_result destfile=$destdir/$destfile fi # Deduce the name of the destination old-style object file. case $destfile in *.lo) func_lo2o "$destfile" staticdest=$func_lo2o_result ;; *.$objext) staticdest=$destfile destfile= ;; *) func_fatal_help "cannot copy a libtool object to '$destfile'" ;; esac # Install the libtool object if requested. test -n "$destfile" && \ func_show_eval "$install_prog $file $destfile" 'exit $?' # Install the old object if enabled. if test yes = "$build_old_libs"; then # Deduce the name of the old-style object file. func_lo2o "$file" staticobj=$func_lo2o_result func_show_eval "$install_prog \$staticobj \$staticdest" 'exit $?' fi exit $EXIT_SUCCESS ;; *) # Figure out destination file name, if it wasn't already specified. if test -n "$destname"; then destfile=$destdir/$destname else func_basename "$file" destfile=$func_basename_result destfile=$destdir/$destfile fi # If the file is missing, and there is a .exe on the end, strip it # because it is most likely a libtool script we actually want to # install stripped_ext= case $file in *.exe) if test ! -f "$file"; then func_stripname '' '.exe' "$file" file=$func_stripname_result stripped_ext=.exe fi ;; esac # Do a test to see if this is really a libtool program. case $host in *cygwin* | *mingw*) if func_ltwrapper_executable_p "$file"; then func_ltwrapper_scriptname "$file" wrapper=$func_ltwrapper_scriptname_result else func_stripname '' '.exe' "$file" wrapper=$func_stripname_result fi ;; *) wrapper=$file ;; esac if func_ltwrapper_script_p "$wrapper"; then notinst_deplibs= relink_command= func_source "$wrapper" # Check the variables that should have been set. test -z "$generated_by_libtool_version" && \ func_fatal_error "invalid libtool wrapper script '$wrapper'" finalize=: for lib in $notinst_deplibs; do # Check to see that each library is installed. libdir= if test -f "$lib"; then func_source "$lib" fi libfile=$libdir/`$ECHO "$lib" | $SED 's%^.*/%%g'` if test -n "$libdir" && test ! -f "$libfile"; then func_warning "'$lib' has not been installed in '$libdir'" finalize=false fi done relink_command= func_source "$wrapper" outputname= if test no = "$fast_install" && test -n "$relink_command"; then $opt_dry_run || { if $finalize; then tmpdir=`func_mktempdir` func_basename "$file$stripped_ext" file=$func_basename_result outputname=$tmpdir/$file # Replace the output file specification. relink_command=`$ECHO "$relink_command" | $SED 's%@OUTPUT@%'"$outputname"'%g'` $opt_quiet || { func_quote_for_expand "$relink_command" eval "func_echo $func_quote_for_expand_result" } if eval "$relink_command"; then : else func_error "error: relink '$file' with the above command before installing it" $opt_dry_run || ${RM}r "$tmpdir" continue fi file=$outputname else func_warning "cannot relink '$file'" fi } else # Install the binary that we compiled earlier. file=`$ECHO "$file$stripped_ext" | $SED "s%\([^/]*\)$%$objdir/\1%"` fi fi # remove .exe since cygwin /usr/bin/install will append another # one anyway case $install_prog,$host in */usr/bin/install*,*cygwin*) case $file:$destfile in *.exe:*.exe) # this is ok ;; *.exe:*) destfile=$destfile.exe ;; *:*.exe) func_stripname '' '.exe' "$destfile" destfile=$func_stripname_result ;; esac ;; esac func_show_eval "$install_prog\$stripme \$file \$destfile" 'exit $?' $opt_dry_run || if test -n "$outputname"; then ${RM}r "$tmpdir" fi ;; esac done for file in $staticlibs; do func_basename "$file" name=$func_basename_result # Set up the ranlib parameters. oldlib=$destdir/$name func_to_tool_file "$oldlib" func_convert_file_msys_to_w32 tool_oldlib=$func_to_tool_file_result func_show_eval "$install_prog \$file \$oldlib" 'exit $?' if test -n "$stripme" && test -n "$old_striplib"; then func_show_eval "$old_striplib $tool_oldlib" 'exit $?' fi # Do each command in the postinstall commands. func_execute_cmds "$old_postinstall_cmds" 'exit $?' done test -n "$future_libdirs" && \ func_warning "remember to run '$progname --finish$future_libdirs'" if test -n "$current_libdirs"; then # Maybe just do a dry run. $opt_dry_run && current_libdirs=" -n$current_libdirs" exec_cmd='$SHELL "$progpath" $preserve_args --finish$current_libdirs' else exit $EXIT_SUCCESS fi } test install = "$opt_mode" && func_mode_install ${1+"$@"} # func_generate_dlsyms outputname originator pic_p # Extract symbols from dlprefiles and create ${outputname}S.o with # a dlpreopen symbol table. func_generate_dlsyms () { $debug_cmd my_outputname=$1 my_originator=$2 my_pic_p=${3-false} my_prefix=`$ECHO "$my_originator" | $SED 's%[^a-zA-Z0-9]%_%g'` my_dlsyms= if test -n "$dlfiles$dlprefiles" || test no != "$dlself"; then if test -n "$NM" && test -n "$global_symbol_pipe"; then my_dlsyms=${my_outputname}S.c else func_error "not configured to extract global symbols from dlpreopened files" fi fi if test -n "$my_dlsyms"; then case $my_dlsyms in "") ;; *.c) # Discover the nlist of each of the dlfiles. nlist=$output_objdir/$my_outputname.nm func_show_eval "$RM $nlist ${nlist}S ${nlist}T" # Parse the name list into a source file. func_verbose "creating $output_objdir/$my_dlsyms" $opt_dry_run || $ECHO > "$output_objdir/$my_dlsyms" "\ /* $my_dlsyms - symbol resolution table for '$my_outputname' dlsym emulation. */ /* Generated by $PROGRAM (GNU $PACKAGE) $VERSION */ #ifdef __cplusplus extern \"C\" { #endif #if defined __GNUC__ && (((__GNUC__ == 4) && (__GNUC_MINOR__ >= 4)) || (__GNUC__ > 4)) #pragma GCC diagnostic ignored \"-Wstrict-prototypes\" #endif /* Keep this code in sync between libtool.m4, ltmain, lt_system.h, and tests. */ #if defined _WIN32 || defined __CYGWIN__ || defined _WIN32_WCE /* DATA imports from DLLs on WIN32 can't be const, because runtime relocations are performed -- see ld's documentation on pseudo-relocs. */ # define LT_DLSYM_CONST #elif defined __osf__ /* This system does not cope well with relocations in const data. */ # define LT_DLSYM_CONST #else # define LT_DLSYM_CONST const #endif #define STREQ(s1, s2) (strcmp ((s1), (s2)) == 0) /* External symbol declarations for the compiler. */\ " if test yes = "$dlself"; then func_verbose "generating symbol list for '$output'" $opt_dry_run || echo ': @PROGRAM@ ' > "$nlist" # Add our own program objects to the symbol list. progfiles=`$ECHO "$objs$old_deplibs" | $SP2NL | $SED "$lo2o" | $NL2SP` for progfile in $progfiles; do func_to_tool_file "$progfile" func_convert_file_msys_to_w32 func_verbose "extracting global C symbols from '$func_to_tool_file_result'" $opt_dry_run || eval "$NM $func_to_tool_file_result | $global_symbol_pipe >> '$nlist'" done if test -n "$exclude_expsyms"; then $opt_dry_run || { eval '$EGREP -v " ($exclude_expsyms)$" "$nlist" > "$nlist"T' eval '$MV "$nlist"T "$nlist"' } fi if test -n "$export_symbols_regex"; then $opt_dry_run || { eval '$EGREP -e "$export_symbols_regex" "$nlist" > "$nlist"T' eval '$MV "$nlist"T "$nlist"' } fi # Prepare the list of exported symbols if test -z "$export_symbols"; then export_symbols=$output_objdir/$outputname.exp $opt_dry_run || { $RM $export_symbols eval "$SED -n -e '/^: @PROGRAM@ $/d' -e 's/^.* \(.*\)$/\1/p' "'< "$nlist" > "$export_symbols"' case $host in *cygwin* | *mingw* | *cegcc* ) eval "echo EXPORTS "'> "$output_objdir/$outputname.def"' eval 'cat "$export_symbols" >> "$output_objdir/$outputname.def"' ;; esac } else $opt_dry_run || { eval "$SED -e 's/\([].[*^$]\)/\\\\\1/g' -e 's/^/ /' -e 's/$/$/'"' < "$export_symbols" > "$output_objdir/$outputname.exp"' eval '$GREP -f "$output_objdir/$outputname.exp" < "$nlist" > "$nlist"T' eval '$MV "$nlist"T "$nlist"' case $host in *cygwin* | *mingw* | *cegcc* ) eval "echo EXPORTS "'> "$output_objdir/$outputname.def"' eval 'cat "$nlist" >> "$output_objdir/$outputname.def"' ;; esac } fi fi for dlprefile in $dlprefiles; do func_verbose "extracting global C symbols from '$dlprefile'" func_basename "$dlprefile" name=$func_basename_result case $host in *cygwin* | *mingw* | *cegcc* ) # if an import library, we need to obtain dlname if func_win32_import_lib_p "$dlprefile"; then func_tr_sh "$dlprefile" eval "curr_lafile=\$libfile_$func_tr_sh_result" dlprefile_dlbasename= if test -n "$curr_lafile" && func_lalib_p "$curr_lafile"; then # Use subshell, to avoid clobbering current variable values dlprefile_dlname=`source "$curr_lafile" && echo "$dlname"` if test -n "$dlprefile_dlname"; then func_basename "$dlprefile_dlname" dlprefile_dlbasename=$func_basename_result else # no lafile. user explicitly requested -dlpreopen . $sharedlib_from_linklib_cmd "$dlprefile" dlprefile_dlbasename=$sharedlib_from_linklib_result fi fi $opt_dry_run || { if test -n "$dlprefile_dlbasename"; then eval '$ECHO ": $dlprefile_dlbasename" >> "$nlist"' else func_warning "Could not compute DLL name from $name" eval '$ECHO ": $name " >> "$nlist"' fi func_to_tool_file "$dlprefile" func_convert_file_msys_to_w32 eval "$NM \"$func_to_tool_file_result\" 2>/dev/null | $global_symbol_pipe | $SED -e '/I __imp/d' -e 's/I __nm_/D /;s/_nm__//' >> '$nlist'" } else # not an import lib $opt_dry_run || { eval '$ECHO ": $name " >> "$nlist"' func_to_tool_file "$dlprefile" func_convert_file_msys_to_w32 eval "$NM \"$func_to_tool_file_result\" 2>/dev/null | $global_symbol_pipe >> '$nlist'" } fi ;; *) $opt_dry_run || { eval '$ECHO ": $name " >> "$nlist"' func_to_tool_file "$dlprefile" func_convert_file_msys_to_w32 eval "$NM \"$func_to_tool_file_result\" 2>/dev/null | $global_symbol_pipe >> '$nlist'" } ;; esac done $opt_dry_run || { # Make sure we have at least an empty file. test -f "$nlist" || : > "$nlist" if test -n "$exclude_expsyms"; then $EGREP -v " ($exclude_expsyms)$" "$nlist" > "$nlist"T $MV "$nlist"T "$nlist" fi # Try sorting and uniquifying the output. if $GREP -v "^: " < "$nlist" | if sort -k 3 /dev/null 2>&1; then sort -k 3 else sort +2 fi | uniq > "$nlist"S; then : else $GREP -v "^: " < "$nlist" > "$nlist"S fi if test -f "$nlist"S; then eval "$global_symbol_to_cdecl"' < "$nlist"S >> "$output_objdir/$my_dlsyms"' else echo '/* NONE */' >> "$output_objdir/$my_dlsyms" fi func_show_eval '$RM "${nlist}I"' if test -n "$global_symbol_to_import"; then eval "$global_symbol_to_import"' < "$nlist"S > "$nlist"I' fi echo >> "$output_objdir/$my_dlsyms" "\ /* The mapping between symbol names and symbols. */ typedef struct { const char *name; void *address; } lt_dlsymlist; extern LT_DLSYM_CONST lt_dlsymlist lt_${my_prefix}_LTX_preloaded_symbols[];\ " if test -s "$nlist"I; then echo >> "$output_objdir/$my_dlsyms" "\ static void lt_syminit(void) { LT_DLSYM_CONST lt_dlsymlist *symbol = lt_${my_prefix}_LTX_preloaded_symbols; for (; symbol->name; ++symbol) {" $SED 's/.*/ if (STREQ (symbol->name, \"&\")) symbol->address = (void *) \&&;/' < "$nlist"I >> "$output_objdir/$my_dlsyms" echo >> "$output_objdir/$my_dlsyms" "\ } }" fi echo >> "$output_objdir/$my_dlsyms" "\ LT_DLSYM_CONST lt_dlsymlist lt_${my_prefix}_LTX_preloaded_symbols[] = { {\"$my_originator\", (void *) 0}," if test -s "$nlist"I; then echo >> "$output_objdir/$my_dlsyms" "\ {\"@INIT@\", (void *) <_syminit}," fi case $need_lib_prefix in no) eval "$global_symbol_to_c_name_address" < "$nlist" >> "$output_objdir/$my_dlsyms" ;; *) eval "$global_symbol_to_c_name_address_lib_prefix" < "$nlist" >> "$output_objdir/$my_dlsyms" ;; esac echo >> "$output_objdir/$my_dlsyms" "\ {0, (void *) 0} }; /* This works around a problem in FreeBSD linker */ #ifdef FREEBSD_WORKAROUND static const void *lt_preloaded_setup() { return lt_${my_prefix}_LTX_preloaded_symbols; } #endif #ifdef __cplusplus } #endif\ " } # !$opt_dry_run pic_flag_for_symtable= case "$compile_command " in *" -static "*) ;; *) case $host in # compiling the symbol table file with pic_flag works around # a FreeBSD bug that causes programs to crash when -lm is # linked before any other PIC object. But we must not use # pic_flag when linking with -static. The problem exists in # FreeBSD 2.2.6 and is fixed in FreeBSD 3.1. *-*-freebsd2.*|*-*-freebsd3.0*|*-*-freebsdelf3.0*) pic_flag_for_symtable=" $pic_flag -DFREEBSD_WORKAROUND" ;; *-*-hpux*) pic_flag_for_symtable=" $pic_flag" ;; *) $my_pic_p && pic_flag_for_symtable=" $pic_flag" ;; esac ;; esac symtab_cflags= for arg in $LTCFLAGS; do case $arg in -pie | -fpie | -fPIE) ;; *) func_append symtab_cflags " $arg" ;; esac done # Now compile the dynamic symbol file. func_show_eval '(cd $output_objdir && $LTCC$symtab_cflags -c$no_builtin_flag$pic_flag_for_symtable "$my_dlsyms")' 'exit $?' # Clean up the generated files. func_show_eval '$RM "$output_objdir/$my_dlsyms" "$nlist" "${nlist}S" "${nlist}T" "${nlist}I"' # Transform the symbol file into the correct name. symfileobj=$output_objdir/${my_outputname}S.$objext case $host in *cygwin* | *mingw* | *cegcc* ) if test -f "$output_objdir/$my_outputname.def"; then compile_command=`$ECHO "$compile_command" | $SED "s%@SYMFILE@%$output_objdir/$my_outputname.def $symfileobj%"` finalize_command=`$ECHO "$finalize_command" | $SED "s%@SYMFILE@%$output_objdir/$my_outputname.def $symfileobj%"` else compile_command=`$ECHO "$compile_command" | $SED "s%@SYMFILE@%$symfileobj%"` finalize_command=`$ECHO "$finalize_command" | $SED "s%@SYMFILE@%$symfileobj%"` fi ;; *) compile_command=`$ECHO "$compile_command" | $SED "s%@SYMFILE@%$symfileobj%"` finalize_command=`$ECHO "$finalize_command" | $SED "s%@SYMFILE@%$symfileobj%"` ;; esac ;; *) func_fatal_error "unknown suffix for '$my_dlsyms'" ;; esac else # We keep going just in case the user didn't refer to # lt_preloaded_symbols. The linker will fail if global_symbol_pipe # really was required. # Nullify the symbol file. compile_command=`$ECHO "$compile_command" | $SED "s% @SYMFILE@%%"` finalize_command=`$ECHO "$finalize_command" | $SED "s% @SYMFILE@%%"` fi } # func_cygming_gnu_implib_p ARG # This predicate returns with zero status (TRUE) if # ARG is a GNU/binutils-style import library. Returns # with nonzero status (FALSE) otherwise. func_cygming_gnu_implib_p () { $debug_cmd func_to_tool_file "$1" func_convert_file_msys_to_w32 func_cygming_gnu_implib_tmp=`$NM "$func_to_tool_file_result" | eval "$global_symbol_pipe" | $EGREP ' (_head_[A-Za-z0-9_]+_[ad]l*|[A-Za-z0-9_]+_[ad]l*_iname)$'` test -n "$func_cygming_gnu_implib_tmp" } # func_cygming_ms_implib_p ARG # This predicate returns with zero status (TRUE) if # ARG is an MS-style import library. Returns # with nonzero status (FALSE) otherwise. func_cygming_ms_implib_p () { $debug_cmd func_to_tool_file "$1" func_convert_file_msys_to_w32 func_cygming_ms_implib_tmp=`$NM "$func_to_tool_file_result" | eval "$global_symbol_pipe" | $GREP '_NULL_IMPORT_DESCRIPTOR'` test -n "$func_cygming_ms_implib_tmp" } # func_win32_libid arg # return the library type of file 'arg' # # Need a lot of goo to handle *both* DLLs and import libs # Has to be a shell function in order to 'eat' the argument # that is supplied when $file_magic_command is called. # Despite the name, also deal with 64 bit binaries. func_win32_libid () { $debug_cmd win32_libid_type=unknown win32_fileres=`file -L $1 2>/dev/null` case $win32_fileres in *ar\ archive\ import\ library*) # definitely import win32_libid_type="x86 archive import" ;; *ar\ archive*) # could be an import, or static # Keep the egrep pattern in sync with the one in _LT_CHECK_MAGIC_METHOD. if eval $OBJDUMP -f $1 | $SED -e '10q' 2>/dev/null | $EGREP 'file format (pei*-i386(.*architecture: i386)?|pe-arm-wince|pe-x86-64)' >/dev/null; then case $nm_interface in "MS dumpbin") if func_cygming_ms_implib_p "$1" || func_cygming_gnu_implib_p "$1" then win32_nmres=import else win32_nmres= fi ;; *) func_to_tool_file "$1" func_convert_file_msys_to_w32 win32_nmres=`eval $NM -f posix -A \"$func_to_tool_file_result\" | $SED -n -e ' 1,100{ / I /{ s|.*|import| p q } }'` ;; esac case $win32_nmres in import*) win32_libid_type="x86 archive import";; *) win32_libid_type="x86 archive static";; esac fi ;; *DLL*) win32_libid_type="x86 DLL" ;; *executable*) # but shell scripts are "executable" too... case $win32_fileres in *MS\ Windows\ PE\ Intel*) win32_libid_type="x86 DLL" ;; esac ;; esac $ECHO "$win32_libid_type" } # func_cygming_dll_for_implib ARG # # Platform-specific function to extract the # name of the DLL associated with the specified # import library ARG. # Invoked by eval'ing the libtool variable # $sharedlib_from_linklib_cmd # Result is available in the variable # $sharedlib_from_linklib_result func_cygming_dll_for_implib () { $debug_cmd sharedlib_from_linklib_result=`$DLLTOOL --identify-strict --identify "$1"` } # func_cygming_dll_for_implib_fallback_core SECTION_NAME LIBNAMEs # # The is the core of a fallback implementation of a # platform-specific function to extract the name of the # DLL associated with the specified import library LIBNAME. # # SECTION_NAME is either .idata$6 or .idata$7, depending # on the platform and compiler that created the implib. # # Echos the name of the DLL associated with the # specified import library. func_cygming_dll_for_implib_fallback_core () { $debug_cmd match_literal=`$ECHO "$1" | $SED "$sed_make_literal_regex"` $OBJDUMP -s --section "$1" "$2" 2>/dev/null | $SED '/^Contents of section '"$match_literal"':/{ # Place marker at beginning of archive member dllname section s/.*/====MARK====/ p d } # These lines can sometimes be longer than 43 characters, but # are always uninteresting /:[ ]*file format pe[i]\{,1\}-/d /^In archive [^:]*:/d # Ensure marker is printed /^====MARK====/p # Remove all lines with less than 43 characters /^.\{43\}/!d # From remaining lines, remove first 43 characters s/^.\{43\}//' | $SED -n ' # Join marker and all lines until next marker into a single line /^====MARK====/ b para H $ b para b :para x s/\n//g # Remove the marker s/^====MARK====// # Remove trailing dots and whitespace s/[\. \t]*$// # Print /./p' | # we now have a list, one entry per line, of the stringified # contents of the appropriate section of all members of the # archive that possess that section. Heuristic: eliminate # all those that have a first or second character that is # a '.' (that is, objdump's representation of an unprintable # character.) This should work for all archives with less than # 0x302f exports -- but will fail for DLLs whose name actually # begins with a literal '.' or a single character followed by # a '.'. # # Of those that remain, print the first one. $SED -e '/^\./d;/^.\./d;q' } # func_cygming_dll_for_implib_fallback ARG # Platform-specific function to extract the # name of the DLL associated with the specified # import library ARG. # # This fallback implementation is for use when $DLLTOOL # does not support the --identify-strict option. # Invoked by eval'ing the libtool variable # $sharedlib_from_linklib_cmd # Result is available in the variable # $sharedlib_from_linklib_result func_cygming_dll_for_implib_fallback () { $debug_cmd if func_cygming_gnu_implib_p "$1"; then # binutils import library sharedlib_from_linklib_result=`func_cygming_dll_for_implib_fallback_core '.idata$7' "$1"` elif func_cygming_ms_implib_p "$1"; then # ms-generated import library sharedlib_from_linklib_result=`func_cygming_dll_for_implib_fallback_core '.idata$6' "$1"` else # unknown sharedlib_from_linklib_result= fi } # func_extract_an_archive dir oldlib func_extract_an_archive () { $debug_cmd f_ex_an_ar_dir=$1; shift f_ex_an_ar_oldlib=$1 if test yes = "$lock_old_archive_extraction"; then lockfile=$f_ex_an_ar_oldlib.lock until $opt_dry_run || ln "$progpath" "$lockfile" 2>/dev/null; do func_echo "Waiting for $lockfile to be removed" sleep 2 done fi func_show_eval "(cd \$f_ex_an_ar_dir && $AR x \"\$f_ex_an_ar_oldlib\")" \ 'stat=$?; rm -f "$lockfile"; exit $stat' if test yes = "$lock_old_archive_extraction"; then $opt_dry_run || rm -f "$lockfile" fi if ($AR t "$f_ex_an_ar_oldlib" | sort | sort -uc >/dev/null 2>&1); then : else func_fatal_error "object name conflicts in archive: $f_ex_an_ar_dir/$f_ex_an_ar_oldlib" fi } # func_extract_archives gentop oldlib ... func_extract_archives () { $debug_cmd my_gentop=$1; shift my_oldlibs=${1+"$@"} my_oldobjs= my_xlib= my_xabs= my_xdir= for my_xlib in $my_oldlibs; do # Extract the objects. case $my_xlib in [\\/]* | [A-Za-z]:[\\/]*) my_xabs=$my_xlib ;; *) my_xabs=`pwd`"/$my_xlib" ;; esac func_basename "$my_xlib" my_xlib=$func_basename_result my_xlib_u=$my_xlib while :; do case " $extracted_archives " in *" $my_xlib_u "*) func_arith $extracted_serial + 1 extracted_serial=$func_arith_result my_xlib_u=lt$extracted_serial-$my_xlib ;; *) break ;; esac done extracted_archives="$extracted_archives $my_xlib_u" my_xdir=$my_gentop/$my_xlib_u func_mkdir_p "$my_xdir" case $host in *-darwin*) func_verbose "Extracting $my_xabs" # Do not bother doing anything if just a dry run $opt_dry_run || { darwin_orig_dir=`pwd` cd $my_xdir || exit $? darwin_archive=$my_xabs darwin_curdir=`pwd` func_basename "$darwin_archive" darwin_base_archive=$func_basename_result darwin_arches=`$LIPO -info "$darwin_archive" 2>/dev/null | $GREP Architectures 2>/dev/null || true` if test -n "$darwin_arches"; then darwin_arches=`$ECHO "$darwin_arches" | $SED -e 's/.*are://'` darwin_arch= func_verbose "$darwin_base_archive has multiple architectures $darwin_arches" for darwin_arch in $darwin_arches; do func_mkdir_p "unfat-$$/$darwin_base_archive-$darwin_arch" $LIPO -thin $darwin_arch -output "unfat-$$/$darwin_base_archive-$darwin_arch/$darwin_base_archive" "$darwin_archive" cd "unfat-$$/$darwin_base_archive-$darwin_arch" func_extract_an_archive "`pwd`" "$darwin_base_archive" cd "$darwin_curdir" $RM "unfat-$$/$darwin_base_archive-$darwin_arch/$darwin_base_archive" done # $darwin_arches ## Okay now we've a bunch of thin objects, gotta fatten them up :) darwin_filelist=`find unfat-$$ -type f -name \*.o -print -o -name \*.lo -print | $SED -e "$sed_basename" | sort -u` darwin_file= darwin_files= for darwin_file in $darwin_filelist; do darwin_files=`find unfat-$$ -name $darwin_file -print | sort | $NL2SP` $LIPO -create -output "$darwin_file" $darwin_files done # $darwin_filelist $RM -rf unfat-$$ cd "$darwin_orig_dir" else cd $darwin_orig_dir func_extract_an_archive "$my_xdir" "$my_xabs" fi # $darwin_arches } # !$opt_dry_run ;; *) func_extract_an_archive "$my_xdir" "$my_xabs" ;; esac my_oldobjs="$my_oldobjs "`find $my_xdir -name \*.$objext -print -o -name \*.lo -print | sort | $NL2SP` done func_extract_archives_result=$my_oldobjs } # func_emit_wrapper [arg=no] # # Emit a libtool wrapper script on stdout. # Don't directly open a file because we may want to # incorporate the script contents within a cygwin/mingw # wrapper executable. Must ONLY be called from within # func_mode_link because it depends on a number of variables # set therein. # # ARG is the value that the WRAPPER_SCRIPT_BELONGS_IN_OBJDIR # variable will take. If 'yes', then the emitted script # will assume that the directory where it is stored is # the $objdir directory. This is a cygwin/mingw-specific # behavior. func_emit_wrapper () { func_emit_wrapper_arg1=${1-no} $ECHO "\ #! $SHELL # $output - temporary wrapper script for $objdir/$outputname # Generated by $PROGRAM (GNU $PACKAGE) $VERSION # # The $output program cannot be directly executed until all the libtool # libraries that it depends on are installed. # # This wrapper script should never be moved out of the build directory. # If it is, it will not operate correctly. # Sed substitution that helps us do robust quoting. It backslashifies # metacharacters that are still active within double-quoted strings. sed_quote_subst='$sed_quote_subst' # Be Bourne compatible if test -n \"\${ZSH_VERSION+set}\" && (emulate sh) >/dev/null 2>&1; then emulate sh NULLCMD=: # Zsh 3.x and 4.x performs word splitting on \${1+\"\$@\"}, which # is contrary to our usage. Disable this feature. alias -g '\${1+\"\$@\"}'='\"\$@\"' setopt NO_GLOB_SUBST else case \`(set -o) 2>/dev/null\` in *posix*) set -o posix;; esac fi BIN_SH=xpg4; export BIN_SH # for Tru64 DUALCASE=1; export DUALCASE # for MKS sh # The HP-UX ksh and POSIX shell print the target directory to stdout # if CDPATH is set. (unset CDPATH) >/dev/null 2>&1 && unset CDPATH relink_command=\"$relink_command\" # This environment variable determines our operation mode. if test \"\$libtool_install_magic\" = \"$magic\"; then # install mode needs the following variables: generated_by_libtool_version='$macro_version' notinst_deplibs='$notinst_deplibs' else # When we are sourced in execute mode, \$file and \$ECHO are already set. if test \"\$libtool_execute_magic\" != \"$magic\"; then file=\"\$0\"" qECHO=`$ECHO "$ECHO" | $SED "$sed_quote_subst"` $ECHO "\ # A function that is used when there is no print builtin or printf. func_fallback_echo () { eval 'cat <<_LTECHO_EOF \$1 _LTECHO_EOF' } ECHO=\"$qECHO\" fi # Very basic option parsing. These options are (a) specific to # the libtool wrapper, (b) are identical between the wrapper # /script/ and the wrapper /executable/ that is used only on # windows platforms, and (c) all begin with the string "--lt-" # (application programs are unlikely to have options that match # this pattern). # # There are only two supported options: --lt-debug and # --lt-dump-script. There is, deliberately, no --lt-help. # # The first argument to this parsing function should be the # script's $0 value, followed by "$@". lt_option_debug= func_parse_lt_options () { lt_script_arg0=\$0 shift for lt_opt do case \"\$lt_opt\" in --lt-debug) lt_option_debug=1 ;; --lt-dump-script) lt_dump_D=\`\$ECHO \"X\$lt_script_arg0\" | $SED -e 's/^X//' -e 's%/[^/]*$%%'\` test \"X\$lt_dump_D\" = \"X\$lt_script_arg0\" && lt_dump_D=. lt_dump_F=\`\$ECHO \"X\$lt_script_arg0\" | $SED -e 's/^X//' -e 's%^.*/%%'\` cat \"\$lt_dump_D/\$lt_dump_F\" exit 0 ;; --lt-*) \$ECHO \"Unrecognized --lt- option: '\$lt_opt'\" 1>&2 exit 1 ;; esac done # Print the debug banner immediately: if test -n \"\$lt_option_debug\"; then echo \"$outputname:$output:\$LINENO: libtool wrapper (GNU $PACKAGE) $VERSION\" 1>&2 fi } # Used when --lt-debug. Prints its arguments to stdout # (redirection is the responsibility of the caller) func_lt_dump_args () { lt_dump_args_N=1; for lt_arg do \$ECHO \"$outputname:$output:\$LINENO: newargv[\$lt_dump_args_N]: \$lt_arg\" lt_dump_args_N=\`expr \$lt_dump_args_N + 1\` done } # Core function for launching the target application func_exec_program_core () { " case $host in # Backslashes separate directories on plain windows *-*-mingw | *-*-os2* | *-cegcc*) $ECHO "\ if test -n \"\$lt_option_debug\"; then \$ECHO \"$outputname:$output:\$LINENO: newargv[0]: \$progdir\\\\\$program\" 1>&2 func_lt_dump_args \${1+\"\$@\"} 1>&2 fi exec \"\$progdir\\\\\$program\" \${1+\"\$@\"} " ;; *) $ECHO "\ if test -n \"\$lt_option_debug\"; then \$ECHO \"$outputname:$output:\$LINENO: newargv[0]: \$progdir/\$program\" 1>&2 func_lt_dump_args \${1+\"\$@\"} 1>&2 fi exec \"\$progdir/\$program\" \${1+\"\$@\"} " ;; esac $ECHO "\ \$ECHO \"\$0: cannot exec \$program \$*\" 1>&2 exit 1 } # A function to encapsulate launching the target application # Strips options in the --lt-* namespace from \$@ and # launches target application with the remaining arguments. func_exec_program () { case \" \$* \" in *\\ --lt-*) for lt_wr_arg do case \$lt_wr_arg in --lt-*) ;; *) set x \"\$@\" \"\$lt_wr_arg\"; shift;; esac shift done ;; esac func_exec_program_core \${1+\"\$@\"} } # Parse options func_parse_lt_options \"\$0\" \${1+\"\$@\"} # Find the directory that this script lives in. thisdir=\`\$ECHO \"\$file\" | $SED 's%/[^/]*$%%'\` test \"x\$thisdir\" = \"x\$file\" && thisdir=. # Follow symbolic links until we get to the real thisdir. file=\`ls -ld \"\$file\" | $SED -n 's/.*-> //p'\` while test -n \"\$file\"; do destdir=\`\$ECHO \"\$file\" | $SED 's%/[^/]*\$%%'\` # If there was a directory component, then change thisdir. if test \"x\$destdir\" != \"x\$file\"; then case \"\$destdir\" in [\\\\/]* | [A-Za-z]:[\\\\/]*) thisdir=\"\$destdir\" ;; *) thisdir=\"\$thisdir/\$destdir\" ;; esac fi file=\`\$ECHO \"\$file\" | $SED 's%^.*/%%'\` file=\`ls -ld \"\$thisdir/\$file\" | $SED -n 's/.*-> //p'\` done # Usually 'no', except on cygwin/mingw when embedded into # the cwrapper. WRAPPER_SCRIPT_BELONGS_IN_OBJDIR=$func_emit_wrapper_arg1 if test \"\$WRAPPER_SCRIPT_BELONGS_IN_OBJDIR\" = \"yes\"; then # special case for '.' if test \"\$thisdir\" = \".\"; then thisdir=\`pwd\` fi # remove .libs from thisdir case \"\$thisdir\" in *[\\\\/]$objdir ) thisdir=\`\$ECHO \"\$thisdir\" | $SED 's%[\\\\/][^\\\\/]*$%%'\` ;; $objdir ) thisdir=. ;; esac fi # Try to get the absolute directory name. absdir=\`cd \"\$thisdir\" && pwd\` test -n \"\$absdir\" && thisdir=\"\$absdir\" " if test yes = "$fast_install"; then $ECHO "\ program=lt-'$outputname'$exeext progdir=\"\$thisdir/$objdir\" if test ! -f \"\$progdir/\$program\" || { file=\`ls -1dt \"\$progdir/\$program\" \"\$progdir/../\$program\" 2>/dev/null | $SED 1q\`; \\ test \"X\$file\" != \"X\$progdir/\$program\"; }; then file=\"\$\$-\$program\" if test ! -d \"\$progdir\"; then $MKDIR \"\$progdir\" else $RM \"\$progdir/\$file\" fi" $ECHO "\ # relink executable if necessary if test -n \"\$relink_command\"; then if relink_command_output=\`eval \$relink_command 2>&1\`; then : else \$ECHO \"\$relink_command_output\" >&2 $RM \"\$progdir/\$file\" exit 1 fi fi $MV \"\$progdir/\$file\" \"\$progdir/\$program\" 2>/dev/null || { $RM \"\$progdir/\$program\"; $MV \"\$progdir/\$file\" \"\$progdir/\$program\"; } $RM \"\$progdir/\$file\" fi" else $ECHO "\ program='$outputname' progdir=\"\$thisdir/$objdir\" " fi $ECHO "\ if test -f \"\$progdir/\$program\"; then" # fixup the dll searchpath if we need to. # # Fix the DLL searchpath if we need to. Do this before prepending # to shlibpath, because on Windows, both are PATH and uninstalled # libraries must come first. if test -n "$dllsearchpath"; then $ECHO "\ # Add the dll search path components to the executable PATH PATH=$dllsearchpath:\$PATH " fi # Export our shlibpath_var if we have one. if test yes = "$shlibpath_overrides_runpath" && test -n "$shlibpath_var" && test -n "$temp_rpath"; then $ECHO "\ # Add our own library path to $shlibpath_var $shlibpath_var=\"$temp_rpath\$$shlibpath_var\" # Some systems cannot cope with colon-terminated $shlibpath_var # The second colon is a workaround for a bug in BeOS R4 sed $shlibpath_var=\`\$ECHO \"\$$shlibpath_var\" | $SED 's/::*\$//'\` export $shlibpath_var " fi $ECHO "\ if test \"\$libtool_execute_magic\" != \"$magic\"; then # Run the actual program with our arguments. func_exec_program \${1+\"\$@\"} fi else # The program doesn't exist. \$ECHO \"\$0: error: '\$progdir/\$program' does not exist\" 1>&2 \$ECHO \"This script is just a wrapper for \$program.\" 1>&2 \$ECHO \"See the $PACKAGE documentation for more information.\" 1>&2 exit 1 fi fi\ " } # func_emit_cwrapperexe_src # emit the source code for a wrapper executable on stdout # Must ONLY be called from within func_mode_link because # it depends on a number of variable set therein. func_emit_cwrapperexe_src () { cat < #include #ifdef _MSC_VER # include # include # include #else # include # include # ifdef __CYGWIN__ # include # endif #endif #include #include #include #include #include #include #include #include #define STREQ(s1, s2) (strcmp ((s1), (s2)) == 0) /* declarations of non-ANSI functions */ #if defined __MINGW32__ # ifdef __STRICT_ANSI__ int _putenv (const char *); # endif #elif defined __CYGWIN__ # ifdef __STRICT_ANSI__ char *realpath (const char *, char *); int putenv (char *); int setenv (const char *, const char *, int); # endif /* #elif defined other_platform || defined ... */ #endif /* portability defines, excluding path handling macros */ #if defined _MSC_VER # define setmode _setmode # define stat _stat # define chmod _chmod # define getcwd _getcwd # define putenv _putenv # define S_IXUSR _S_IEXEC #elif defined __MINGW32__ # define setmode _setmode # define stat _stat # define chmod _chmod # define getcwd _getcwd # define putenv _putenv #elif defined __CYGWIN__ # define HAVE_SETENV # define FOPEN_WB "wb" /* #elif defined other platforms ... */ #endif #if defined PATH_MAX # define LT_PATHMAX PATH_MAX #elif defined MAXPATHLEN # define LT_PATHMAX MAXPATHLEN #else # define LT_PATHMAX 1024 #endif #ifndef S_IXOTH # define S_IXOTH 0 #endif #ifndef S_IXGRP # define S_IXGRP 0 #endif /* path handling portability macros */ #ifndef DIR_SEPARATOR # define DIR_SEPARATOR '/' # define PATH_SEPARATOR ':' #endif #if defined _WIN32 || defined __MSDOS__ || defined __DJGPP__ || \ defined __OS2__ # define HAVE_DOS_BASED_FILE_SYSTEM # define FOPEN_WB "wb" # ifndef DIR_SEPARATOR_2 # define DIR_SEPARATOR_2 '\\' # endif # ifndef PATH_SEPARATOR_2 # define PATH_SEPARATOR_2 ';' # endif #endif #ifndef DIR_SEPARATOR_2 # define IS_DIR_SEPARATOR(ch) ((ch) == DIR_SEPARATOR) #else /* DIR_SEPARATOR_2 */ # define IS_DIR_SEPARATOR(ch) \ (((ch) == DIR_SEPARATOR) || ((ch) == DIR_SEPARATOR_2)) #endif /* DIR_SEPARATOR_2 */ #ifndef PATH_SEPARATOR_2 # define IS_PATH_SEPARATOR(ch) ((ch) == PATH_SEPARATOR) #else /* PATH_SEPARATOR_2 */ # define IS_PATH_SEPARATOR(ch) ((ch) == PATH_SEPARATOR_2) #endif /* PATH_SEPARATOR_2 */ #ifndef FOPEN_WB # define FOPEN_WB "w" #endif #ifndef _O_BINARY # define _O_BINARY 0 #endif #define XMALLOC(type, num) ((type *) xmalloc ((num) * sizeof(type))) #define XFREE(stale) do { \ if (stale) { free (stale); stale = 0; } \ } while (0) #if defined LT_DEBUGWRAPPER static int lt_debug = 1; #else static int lt_debug = 0; #endif const char *program_name = "libtool-wrapper"; /* in case xstrdup fails */ void *xmalloc (size_t num); char *xstrdup (const char *string); const char *base_name (const char *name); char *find_executable (const char *wrapper); char *chase_symlinks (const char *pathspec); int make_executable (const char *path); int check_executable (const char *path); char *strendzap (char *str, const char *pat); void lt_debugprintf (const char *file, int line, const char *fmt, ...); void lt_fatal (const char *file, int line, const char *message, ...); static const char *nonnull (const char *s); static const char *nonempty (const char *s); void lt_setenv (const char *name, const char *value); char *lt_extend_str (const char *orig_value, const char *add, int to_end); void lt_update_exe_path (const char *name, const char *value); void lt_update_lib_path (const char *name, const char *value); char **prepare_spawn (char **argv); void lt_dump_script (FILE *f); EOF cat <= 0) && (st.st_mode & (S_IXUSR | S_IXGRP | S_IXOTH))) return 1; else return 0; } int make_executable (const char *path) { int rval = 0; struct stat st; lt_debugprintf (__FILE__, __LINE__, "(make_executable): %s\n", nonempty (path)); if ((!path) || (!*path)) return 0; if (stat (path, &st) >= 0) { rval = chmod (path, st.st_mode | S_IXOTH | S_IXGRP | S_IXUSR); } return rval; } /* Searches for the full path of the wrapper. Returns newly allocated full path name if found, NULL otherwise Does not chase symlinks, even on platforms that support them. */ char * find_executable (const char *wrapper) { int has_slash = 0; const char *p; const char *p_next; /* static buffer for getcwd */ char tmp[LT_PATHMAX + 1]; size_t tmp_len; char *concat_name; lt_debugprintf (__FILE__, __LINE__, "(find_executable): %s\n", nonempty (wrapper)); if ((wrapper == NULL) || (*wrapper == '\0')) return NULL; /* Absolute path? */ #if defined HAVE_DOS_BASED_FILE_SYSTEM if (isalpha ((unsigned char) wrapper[0]) && wrapper[1] == ':') { concat_name = xstrdup (wrapper); if (check_executable (concat_name)) return concat_name; XFREE (concat_name); } else { #endif if (IS_DIR_SEPARATOR (wrapper[0])) { concat_name = xstrdup (wrapper); if (check_executable (concat_name)) return concat_name; XFREE (concat_name); } #if defined HAVE_DOS_BASED_FILE_SYSTEM } #endif for (p = wrapper; *p; p++) if (*p == '/') { has_slash = 1; break; } if (!has_slash) { /* no slashes; search PATH */ const char *path = getenv ("PATH"); if (path != NULL) { for (p = path; *p; p = p_next) { const char *q; size_t p_len; for (q = p; *q; q++) if (IS_PATH_SEPARATOR (*q)) break; p_len = (size_t) (q - p); p_next = (*q == '\0' ? q : q + 1); if (p_len == 0) { /* empty path: current directory */ if (getcwd (tmp, LT_PATHMAX) == NULL) lt_fatal (__FILE__, __LINE__, "getcwd failed: %s", nonnull (strerror (errno))); tmp_len = strlen (tmp); concat_name = XMALLOC (char, tmp_len + 1 + strlen (wrapper) + 1); memcpy (concat_name, tmp, tmp_len); concat_name[tmp_len] = '/'; strcpy (concat_name + tmp_len + 1, wrapper); } else { concat_name = XMALLOC (char, p_len + 1 + strlen (wrapper) + 1); memcpy (concat_name, p, p_len); concat_name[p_len] = '/'; strcpy (concat_name + p_len + 1, wrapper); } if (check_executable (concat_name)) return concat_name; XFREE (concat_name); } } /* not found in PATH; assume curdir */ } /* Relative path | not found in path: prepend cwd */ if (getcwd (tmp, LT_PATHMAX) == NULL) lt_fatal (__FILE__, __LINE__, "getcwd failed: %s", nonnull (strerror (errno))); tmp_len = strlen (tmp); concat_name = XMALLOC (char, tmp_len + 1 + strlen (wrapper) + 1); memcpy (concat_name, tmp, tmp_len); concat_name[tmp_len] = '/'; strcpy (concat_name + tmp_len + 1, wrapper); if (check_executable (concat_name)) return concat_name; XFREE (concat_name); return NULL; } char * chase_symlinks (const char *pathspec) { #ifndef S_ISLNK return xstrdup (pathspec); #else char buf[LT_PATHMAX]; struct stat s; char *tmp_pathspec = xstrdup (pathspec); char *p; int has_symlinks = 0; while (strlen (tmp_pathspec) && !has_symlinks) { lt_debugprintf (__FILE__, __LINE__, "checking path component for symlinks: %s\n", tmp_pathspec); if (lstat (tmp_pathspec, &s) == 0) { if (S_ISLNK (s.st_mode) != 0) { has_symlinks = 1; break; } /* search backwards for last DIR_SEPARATOR */ p = tmp_pathspec + strlen (tmp_pathspec) - 1; while ((p > tmp_pathspec) && (!IS_DIR_SEPARATOR (*p))) p--; if ((p == tmp_pathspec) && (!IS_DIR_SEPARATOR (*p))) { /* no more DIR_SEPARATORS left */ break; } *p = '\0'; } else { lt_fatal (__FILE__, __LINE__, "error accessing file \"%s\": %s", tmp_pathspec, nonnull (strerror (errno))); } } XFREE (tmp_pathspec); if (!has_symlinks) { return xstrdup (pathspec); } tmp_pathspec = realpath (pathspec, buf); if (tmp_pathspec == 0) { lt_fatal (__FILE__, __LINE__, "could not follow symlinks for %s", pathspec); } return xstrdup (tmp_pathspec); #endif } char * strendzap (char *str, const char *pat) { size_t len, patlen; assert (str != NULL); assert (pat != NULL); len = strlen (str); patlen = strlen (pat); if (patlen <= len) { str += len - patlen; if (STREQ (str, pat)) *str = '\0'; } return str; } void lt_debugprintf (const char *file, int line, const char *fmt, ...) { va_list args; if (lt_debug) { (void) fprintf (stderr, "%s:%s:%d: ", program_name, file, line); va_start (args, fmt); (void) vfprintf (stderr, fmt, args); va_end (args); } } static void lt_error_core (int exit_status, const char *file, int line, const char *mode, const char *message, va_list ap) { fprintf (stderr, "%s:%s:%d: %s: ", program_name, file, line, mode); vfprintf (stderr, message, ap); fprintf (stderr, ".\n"); if (exit_status >= 0) exit (exit_status); } void lt_fatal (const char *file, int line, const char *message, ...) { va_list ap; va_start (ap, message); lt_error_core (EXIT_FAILURE, file, line, "FATAL", message, ap); va_end (ap); } static const char * nonnull (const char *s) { return s ? s : "(null)"; } static const char * nonempty (const char *s) { return (s && !*s) ? "(empty)" : nonnull (s); } void lt_setenv (const char *name, const char *value) { lt_debugprintf (__FILE__, __LINE__, "(lt_setenv) setting '%s' to '%s'\n", nonnull (name), nonnull (value)); { #ifdef HAVE_SETENV /* always make a copy, for consistency with !HAVE_SETENV */ char *str = xstrdup (value); setenv (name, str, 1); #else size_t len = strlen (name) + 1 + strlen (value) + 1; char *str = XMALLOC (char, len); sprintf (str, "%s=%s", name, value); if (putenv (str) != EXIT_SUCCESS) { XFREE (str); } #endif } } char * lt_extend_str (const char *orig_value, const char *add, int to_end) { char *new_value; if (orig_value && *orig_value) { size_t orig_value_len = strlen (orig_value); size_t add_len = strlen (add); new_value = XMALLOC (char, add_len + orig_value_len + 1); if (to_end) { strcpy (new_value, orig_value); strcpy (new_value + orig_value_len, add); } else { strcpy (new_value, add); strcpy (new_value + add_len, orig_value); } } else { new_value = xstrdup (add); } return new_value; } void lt_update_exe_path (const char *name, const char *value) { lt_debugprintf (__FILE__, __LINE__, "(lt_update_exe_path) modifying '%s' by prepending '%s'\n", nonnull (name), nonnull (value)); if (name && *name && value && *value) { char *new_value = lt_extend_str (getenv (name), value, 0); /* some systems can't cope with a ':'-terminated path #' */ size_t len = strlen (new_value); while ((len > 0) && IS_PATH_SEPARATOR (new_value[len-1])) { new_value[--len] = '\0'; } lt_setenv (name, new_value); XFREE (new_value); } } void lt_update_lib_path (const char *name, const char *value) { lt_debugprintf (__FILE__, __LINE__, "(lt_update_lib_path) modifying '%s' by prepending '%s'\n", nonnull (name), nonnull (value)); if (name && *name && value && *value) { char *new_value = lt_extend_str (getenv (name), value, 0); lt_setenv (name, new_value); XFREE (new_value); } } EOF case $host_os in mingw*) cat <<"EOF" /* Prepares an argument vector before calling spawn(). Note that spawn() does not by itself call the command interpreter (getenv ("COMSPEC") != NULL ? getenv ("COMSPEC") : ({ OSVERSIONINFO v; v.dwOSVersionInfoSize = sizeof(OSVERSIONINFO); GetVersionEx(&v); v.dwPlatformId == VER_PLATFORM_WIN32_NT; }) ? "cmd.exe" : "command.com"). Instead it simply concatenates the arguments, separated by ' ', and calls CreateProcess(). We must quote the arguments since Win32 CreateProcess() interprets characters like ' ', '\t', '\\', '"' (but not '<' and '>') in a special way: - Space and tab are interpreted as delimiters. They are not treated as delimiters if they are surrounded by double quotes: "...". - Unescaped double quotes are removed from the input. Their only effect is that within double quotes, space and tab are treated like normal characters. - Backslashes not followed by double quotes are not special. - But 2*n+1 backslashes followed by a double quote become n backslashes followed by a double quote (n >= 0): \" -> " \\\" -> \" \\\\\" -> \\" */ #define SHELL_SPECIAL_CHARS "\"\\ \001\002\003\004\005\006\007\010\011\012\013\014\015\016\017\020\021\022\023\024\025\026\027\030\031\032\033\034\035\036\037" #define SHELL_SPACE_CHARS " \001\002\003\004\005\006\007\010\011\012\013\014\015\016\017\020\021\022\023\024\025\026\027\030\031\032\033\034\035\036\037" char ** prepare_spawn (char **argv) { size_t argc; char **new_argv; size_t i; /* Count number of arguments. */ for (argc = 0; argv[argc] != NULL; argc++) ; /* Allocate new argument vector. */ new_argv = XMALLOC (char *, argc + 1); /* Put quoted arguments into the new argument vector. */ for (i = 0; i < argc; i++) { const char *string = argv[i]; if (string[0] == '\0') new_argv[i] = xstrdup ("\"\""); else if (strpbrk (string, SHELL_SPECIAL_CHARS) != NULL) { int quote_around = (strpbrk (string, SHELL_SPACE_CHARS) != NULL); size_t length; unsigned int backslashes; const char *s; char *quoted_string; char *p; length = 0; backslashes = 0; if (quote_around) length++; for (s = string; *s != '\0'; s++) { char c = *s; if (c == '"') length += backslashes + 1; length++; if (c == '\\') backslashes++; else backslashes = 0; } if (quote_around) length += backslashes + 1; quoted_string = XMALLOC (char, length + 1); p = quoted_string; backslashes = 0; if (quote_around) *p++ = '"'; for (s = string; *s != '\0'; s++) { char c = *s; if (c == '"') { unsigned int j; for (j = backslashes + 1; j > 0; j--) *p++ = '\\'; } *p++ = c; if (c == '\\') backslashes++; else backslashes = 0; } if (quote_around) { unsigned int j; for (j = backslashes; j > 0; j--) *p++ = '\\'; *p++ = '"'; } *p = '\0'; new_argv[i] = quoted_string; } else new_argv[i] = (char *) string; } new_argv[argc] = NULL; return new_argv; } EOF ;; esac cat <<"EOF" void lt_dump_script (FILE* f) { EOF func_emit_wrapper yes | $SED -n -e ' s/^\(.\{79\}\)\(..*\)/\1\ \2/ h s/\([\\"]\)/\\\1/g s/$/\\n/ s/\([^\n]*\).*/ fputs ("\1", f);/p g D' cat <<"EOF" } EOF } # end: func_emit_cwrapperexe_src # func_win32_import_lib_p ARG # True if ARG is an import lib, as indicated by $file_magic_cmd func_win32_import_lib_p () { $debug_cmd case `eval $file_magic_cmd \"\$1\" 2>/dev/null | $SED -e 10q` in *import*) : ;; *) false ;; esac } # func_suncc_cstd_abi # !!ONLY CALL THIS FOR SUN CC AFTER $compile_command IS FULLY EXPANDED!! # Several compiler flags select an ABI that is incompatible with the # Cstd library. Avoid specifying it if any are in CXXFLAGS. func_suncc_cstd_abi () { $debug_cmd case " $compile_command " in *" -compat=g "*|*\ -std=c++[0-9][0-9]\ *|*" -library=stdcxx4 "*|*" -library=stlport4 "*) suncc_use_cstd_abi=no ;; *) suncc_use_cstd_abi=yes ;; esac } # func_mode_link arg... func_mode_link () { $debug_cmd case $host in *-*-cygwin* | *-*-mingw* | *-*-pw32* | *-*-os2* | *-cegcc*) # It is impossible to link a dll without this setting, and # we shouldn't force the makefile maintainer to figure out # what system we are compiling for in order to pass an extra # flag for every libtool invocation. # allow_undefined=no # FIXME: Unfortunately, there are problems with the above when trying # to make a dll that has undefined symbols, in which case not # even a static library is built. For now, we need to specify # -no-undefined on the libtool link line when we can be certain # that all symbols are satisfied, otherwise we get a static library. allow_undefined=yes ;; *) allow_undefined=yes ;; esac libtool_args=$nonopt base_compile="$nonopt $@" compile_command=$nonopt finalize_command=$nonopt compile_rpath= finalize_rpath= compile_shlibpath= finalize_shlibpath= convenience= old_convenience= deplibs= old_deplibs= compiler_flags= linker_flags= dllsearchpath= lib_search_path=`pwd` inst_prefix_dir= new_inherited_linker_flags= avoid_version=no bindir= dlfiles= dlprefiles= dlself=no export_dynamic=no export_symbols= export_symbols_regex= generated= libobjs= ltlibs= module=no no_install=no objs= os2dllname= non_pic_objects= precious_files_regex= prefer_static_libs=no preload=false prev= prevarg= release= rpath= xrpath= perm_rpath= temp_rpath= thread_safe=no vinfo= vinfo_number=no weak_libs= single_module=$wl-single_module func_infer_tag $base_compile # We need to know -static, to get the right output filenames. for arg do case $arg in -shared) test yes != "$build_libtool_libs" \ && func_fatal_configuration "cannot build a shared library" build_old_libs=no break ;; -all-static | -static | -static-libtool-libs) case $arg in -all-static) if test yes = "$build_libtool_libs" && test -z "$link_static_flag"; then func_warning "complete static linking is impossible in this configuration" fi if test -n "$link_static_flag"; then dlopen_self=$dlopen_self_static fi prefer_static_libs=yes ;; -static) if test -z "$pic_flag" && test -n "$link_static_flag"; then dlopen_self=$dlopen_self_static fi prefer_static_libs=built ;; -static-libtool-libs) if test -z "$pic_flag" && test -n "$link_static_flag"; then dlopen_self=$dlopen_self_static fi prefer_static_libs=yes ;; esac build_libtool_libs=no build_old_libs=yes break ;; esac done # See if our shared archives depend on static archives. test -n "$old_archive_from_new_cmds" && build_old_libs=yes # Go through the arguments, transforming them on the way. while test "$#" -gt 0; do arg=$1 shift func_quote_for_eval "$arg" qarg=$func_quote_for_eval_unquoted_result func_append libtool_args " $func_quote_for_eval_result" # If the previous option needs an argument, assign it. if test -n "$prev"; then case $prev in output) func_append compile_command " @OUTPUT@" func_append finalize_command " @OUTPUT@" ;; esac case $prev in bindir) bindir=$arg prev= continue ;; dlfiles|dlprefiles) $preload || { # Add the symbol object into the linking commands. func_append compile_command " @SYMFILE@" func_append finalize_command " @SYMFILE@" preload=: } case $arg in *.la | *.lo) ;; # We handle these cases below. force) if test no = "$dlself"; then dlself=needless export_dynamic=yes fi prev= continue ;; self) if test dlprefiles = "$prev"; then dlself=yes elif test dlfiles = "$prev" && test yes != "$dlopen_self"; then dlself=yes else dlself=needless export_dynamic=yes fi prev= continue ;; *) if test dlfiles = "$prev"; then func_append dlfiles " $arg" else func_append dlprefiles " $arg" fi prev= continue ;; esac ;; expsyms) export_symbols=$arg test -f "$arg" \ || func_fatal_error "symbol file '$arg' does not exist" prev= continue ;; expsyms_regex) export_symbols_regex=$arg prev= continue ;; framework) case $host in *-*-darwin*) case "$deplibs " in *" $qarg.ltframework "*) ;; *) func_append deplibs " $qarg.ltframework" # this is fixed later ;; esac ;; esac prev= continue ;; inst_prefix) inst_prefix_dir=$arg prev= continue ;; mllvm) # Clang does not use LLVM to link, so we can simply discard any # '-mllvm $arg' options when doing the link step. prev= continue ;; objectlist) if test -f "$arg"; then save_arg=$arg moreargs= for fil in `cat "$save_arg"` do # func_append moreargs " $fil" arg=$fil # A libtool-controlled object. # Check to see that this really is a libtool object. if func_lalib_unsafe_p "$arg"; then pic_object= non_pic_object= # Read the .lo file func_source "$arg" if test -z "$pic_object" || test -z "$non_pic_object" || test none = "$pic_object" && test none = "$non_pic_object"; then func_fatal_error "cannot find name of object for '$arg'" fi # Extract subdirectory from the argument. func_dirname "$arg" "/" "" xdir=$func_dirname_result if test none != "$pic_object"; then # Prepend the subdirectory the object is found in. pic_object=$xdir$pic_object if test dlfiles = "$prev"; then if test yes = "$build_libtool_libs" && test yes = "$dlopen_support"; then func_append dlfiles " $pic_object" prev= continue else # If libtool objects are unsupported, then we need to preload. prev=dlprefiles fi fi # CHECK ME: I think I busted this. -Ossama if test dlprefiles = "$prev"; then # Preload the old-style object. func_append dlprefiles " $pic_object" prev= fi # A PIC object. func_append libobjs " $pic_object" arg=$pic_object fi # Non-PIC object. if test none != "$non_pic_object"; then # Prepend the subdirectory the object is found in. non_pic_object=$xdir$non_pic_object # A standard non-PIC object func_append non_pic_objects " $non_pic_object" if test -z "$pic_object" || test none = "$pic_object"; then arg=$non_pic_object fi else # If the PIC object exists, use it instead. # $xdir was prepended to $pic_object above. non_pic_object=$pic_object func_append non_pic_objects " $non_pic_object" fi else # Only an error if not doing a dry-run. if $opt_dry_run; then # Extract subdirectory from the argument. func_dirname "$arg" "/" "" xdir=$func_dirname_result func_lo2o "$arg" pic_object=$xdir$objdir/$func_lo2o_result non_pic_object=$xdir$func_lo2o_result func_append libobjs " $pic_object" func_append non_pic_objects " $non_pic_object" else func_fatal_error "'$arg' is not a valid libtool object" fi fi done else func_fatal_error "link input file '$arg' does not exist" fi arg=$save_arg prev= continue ;; os2dllname) os2dllname=$arg prev= continue ;; precious_regex) precious_files_regex=$arg prev= continue ;; release) release=-$arg prev= continue ;; rpath | xrpath) # We need an absolute path. case $arg in [\\/]* | [A-Za-z]:[\\/]*) ;; *) func_fatal_error "only absolute run-paths are allowed" ;; esac if test rpath = "$prev"; then case "$rpath " in *" $arg "*) ;; *) func_append rpath " $arg" ;; esac else case "$xrpath " in *" $arg "*) ;; *) func_append xrpath " $arg" ;; esac fi prev= continue ;; shrext) shrext_cmds=$arg prev= continue ;; weak) func_append weak_libs " $arg" prev= continue ;; xcclinker) func_append linker_flags " $qarg" func_append compiler_flags " $qarg" prev= func_append compile_command " $qarg" func_append finalize_command " $qarg" continue ;; xcompiler) func_append compiler_flags " $qarg" prev= func_append compile_command " $qarg" func_append finalize_command " $qarg" continue ;; xlinker) func_append linker_flags " $qarg" func_append compiler_flags " $wl$qarg" prev= func_append compile_command " $wl$qarg" func_append finalize_command " $wl$qarg" continue ;; *) eval "$prev=\"\$arg\"" prev= continue ;; esac fi # test -n "$prev" prevarg=$arg case $arg in -all-static) if test -n "$link_static_flag"; then # See comment for -static flag below, for more details. func_append compile_command " $link_static_flag" func_append finalize_command " $link_static_flag" fi continue ;; -allow-undefined) # FIXME: remove this flag sometime in the future. func_fatal_error "'-allow-undefined' must not be used because it is the default" ;; -avoid-version) avoid_version=yes continue ;; -bindir) prev=bindir continue ;; -dlopen) prev=dlfiles continue ;; -dlpreopen) prev=dlprefiles continue ;; -export-dynamic) export_dynamic=yes continue ;; -export-symbols | -export-symbols-regex) if test -n "$export_symbols" || test -n "$export_symbols_regex"; then func_fatal_error "more than one -exported-symbols argument is not allowed" fi if test X-export-symbols = "X$arg"; then prev=expsyms else prev=expsyms_regex fi continue ;; -framework) prev=framework continue ;; -inst-prefix-dir) prev=inst_prefix continue ;; # The native IRIX linker understands -LANG:*, -LIST:* and -LNO:* # so, if we see these flags be careful not to treat them like -L -L[A-Z][A-Z]*:*) case $with_gcc/$host in no/*-*-irix* | /*-*-irix*) func_append compile_command " $arg" func_append finalize_command " $arg" ;; esac continue ;; -L*) func_stripname "-L" '' "$arg" if test -z "$func_stripname_result"; then if test "$#" -gt 0; then func_fatal_error "require no space between '-L' and '$1'" else func_fatal_error "need path for '-L' option" fi fi func_resolve_sysroot "$func_stripname_result" dir=$func_resolve_sysroot_result # We need an absolute path. case $dir in [\\/]* | [A-Za-z]:[\\/]*) ;; *) absdir=`cd "$dir" && pwd` test -z "$absdir" && \ func_fatal_error "cannot determine absolute directory name of '$dir'" dir=$absdir ;; esac case "$deplibs " in *" -L$dir "* | *" $arg "*) # Will only happen for absolute or sysroot arguments ;; *) # Preserve sysroot, but never include relative directories case $dir in [\\/]* | [A-Za-z]:[\\/]* | =*) func_append deplibs " $arg" ;; *) func_append deplibs " -L$dir" ;; esac func_append lib_search_path " $dir" ;; esac case $host in *-*-cygwin* | *-*-mingw* | *-*-pw32* | *-*-os2* | *-cegcc*) testbindir=`$ECHO "$dir" | $SED 's*/lib$*/bin*'` case :$dllsearchpath: in *":$dir:"*) ;; ::) dllsearchpath=$dir;; *) func_append dllsearchpath ":$dir";; esac case :$dllsearchpath: in *":$testbindir:"*) ;; ::) dllsearchpath=$testbindir;; *) func_append dllsearchpath ":$testbindir";; esac ;; esac continue ;; -l*) if test X-lc = "X$arg" || test X-lm = "X$arg"; then case $host in *-*-cygwin* | *-*-mingw* | *-*-pw32* | *-*-beos* | *-cegcc* | *-*-haiku*) # These systems don't actually have a C or math library (as such) continue ;; *-*-os2*) # These systems don't actually have a C library (as such) test X-lc = "X$arg" && continue ;; *-*-openbsd* | *-*-freebsd* | *-*-dragonfly* | *-*-bitrig*) # Do not include libc due to us having libc/libc_r. test X-lc = "X$arg" && continue ;; *-*-rhapsody* | *-*-darwin1.[012]) # Rhapsody C and math libraries are in the System framework func_append deplibs " System.ltframework" continue ;; *-*-sco3.2v5* | *-*-sco5v6*) # Causes problems with __ctype test X-lc = "X$arg" && continue ;; *-*-sysv4.2uw2* | *-*-sysv5* | *-*-unixware* | *-*-OpenUNIX*) # Compiler inserts libc in the correct place for threads to work test X-lc = "X$arg" && continue ;; esac elif test X-lc_r = "X$arg"; then case $host in *-*-openbsd* | *-*-freebsd* | *-*-dragonfly* | *-*-bitrig*) # Do not include libc_r directly, use -pthread flag. continue ;; esac fi func_append deplibs " $arg" continue ;; -mllvm) prev=mllvm continue ;; -module) module=yes continue ;; # Tru64 UNIX uses -model [arg] to determine the layout of C++ # classes, name mangling, and exception handling. # Darwin uses the -arch flag to determine output architecture. -model|-arch|-isysroot|--sysroot) func_append compiler_flags " $arg" func_append compile_command " $arg" func_append finalize_command " $arg" prev=xcompiler continue ;; -mt|-mthreads|-kthread|-Kthread|-pthread|-pthreads|--thread-safe \ |-threads|-fopenmp|-openmp|-mp|-xopenmp|-omp|-qsmp=*) func_append compiler_flags " $arg" func_append compile_command " $arg" func_append finalize_command " $arg" case "$new_inherited_linker_flags " in *" $arg "*) ;; * ) func_append new_inherited_linker_flags " $arg" ;; esac continue ;; -multi_module) single_module=$wl-multi_module continue ;; -no-fast-install) fast_install=no continue ;; -no-install) case $host in *-*-cygwin* | *-*-mingw* | *-*-pw32* | *-*-os2* | *-*-darwin* | *-cegcc*) # The PATH hackery in wrapper scripts is required on Windows # and Darwin in order for the loader to find any dlls it needs. func_warning "'-no-install' is ignored for $host" func_warning "assuming '-no-fast-install' instead" fast_install=no ;; *) no_install=yes ;; esac continue ;; -no-undefined) allow_undefined=no continue ;; -objectlist) prev=objectlist continue ;; -os2dllname) prev=os2dllname continue ;; -o) prev=output ;; -precious-files-regex) prev=precious_regex continue ;; -release) prev=release continue ;; -rpath) prev=rpath continue ;; -R) prev=xrpath continue ;; -R*) func_stripname '-R' '' "$arg" dir=$func_stripname_result # We need an absolute path. case $dir in [\\/]* | [A-Za-z]:[\\/]*) ;; =*) func_stripname '=' '' "$dir" dir=$lt_sysroot$func_stripname_result ;; *) func_fatal_error "only absolute run-paths are allowed" ;; esac case "$xrpath " in *" $dir "*) ;; *) func_append xrpath " $dir" ;; esac continue ;; -shared) # The effects of -shared are defined in a previous loop. continue ;; -shrext) prev=shrext continue ;; -static | -static-libtool-libs) # The effects of -static are defined in a previous loop. # We used to do the same as -all-static on platforms that # didn't have a PIC flag, but the assumption that the effects # would be equivalent was wrong. It would break on at least # Digital Unix and AIX. continue ;; -thread-safe) thread_safe=yes continue ;; -version-info) prev=vinfo continue ;; -version-number) prev=vinfo vinfo_number=yes continue ;; -weak) prev=weak continue ;; -Wc,*) func_stripname '-Wc,' '' "$arg" args=$func_stripname_result arg= save_ifs=$IFS; IFS=, for flag in $args; do IFS=$save_ifs func_quote_for_eval "$flag" func_append arg " $func_quote_for_eval_result" func_append compiler_flags " $func_quote_for_eval_result" done IFS=$save_ifs func_stripname ' ' '' "$arg" arg=$func_stripname_result ;; -Wl,*) func_stripname '-Wl,' '' "$arg" args=$func_stripname_result arg= save_ifs=$IFS; IFS=, for flag in $args; do IFS=$save_ifs func_quote_for_eval "$flag" func_append arg " $wl$func_quote_for_eval_result" func_append compiler_flags " $wl$func_quote_for_eval_result" func_append linker_flags " $func_quote_for_eval_result" done IFS=$save_ifs func_stripname ' ' '' "$arg" arg=$func_stripname_result ;; -Xcompiler) prev=xcompiler continue ;; -Xlinker) prev=xlinker continue ;; -XCClinker) prev=xcclinker continue ;; # -msg_* for osf cc -msg_*) func_quote_for_eval "$arg" arg=$func_quote_for_eval_result ;; # Flags to be passed through unchanged, with rationale: # -64, -mips[0-9] enable 64-bit mode for the SGI compiler # -r[0-9][0-9]* specify processor for the SGI compiler # -xarch=*, -xtarget=* enable 64-bit mode for the Sun compiler # +DA*, +DD* enable 64-bit mode for the HP compiler # -q* compiler args for the IBM compiler # -m*, -t[45]*, -txscale* architecture-specific flags for GCC # -F/path path to uninstalled frameworks, gcc on darwin # -p, -pg, --coverage, -fprofile-* profiling flags for GCC # -fstack-protector* stack protector flags for GCC # @file GCC response files # -tp=* Portland pgcc target processor selection # --sysroot=* for sysroot support # -O*, -g*, -flto*, -fwhopr*, -fuse-linker-plugin GCC link-time optimization # -specs=* GCC specs files # -stdlib=* select c++ std lib with clang # -fsanitize=* Clang/GCC memory and address sanitizer -64|-mips[0-9]|-r[0-9][0-9]*|-xarch=*|-xtarget=*|+DA*|+DD*|-q*|-m*| \ -t[45]*|-txscale*|-p|-pg|--coverage|-fprofile-*|-F*|@*|-tp=*|--sysroot=*| \ -O*|-g*|-flto*|-fwhopr*|-fuse-linker-plugin|-fstack-protector*|-stdlib=*| \ -specs=*|-fsanitize=*) func_quote_for_eval "$arg" arg=$func_quote_for_eval_result func_append compile_command " $arg" func_append finalize_command " $arg" func_append compiler_flags " $arg" continue ;; -Z*) if test os2 = "`expr $host : '.*\(os2\)'`"; then # OS/2 uses -Zxxx to specify OS/2-specific options compiler_flags="$compiler_flags $arg" func_append compile_command " $arg" func_append finalize_command " $arg" case $arg in -Zlinker | -Zstack) prev=xcompiler ;; esac continue else # Otherwise treat like 'Some other compiler flag' below func_quote_for_eval "$arg" arg=$func_quote_for_eval_result fi ;; # Some other compiler flag. -* | +*) func_quote_for_eval "$arg" arg=$func_quote_for_eval_result ;; *.$objext) # A standard object. func_append objs " $arg" ;; *.lo) # A libtool-controlled object. # Check to see that this really is a libtool object. if func_lalib_unsafe_p "$arg"; then pic_object= non_pic_object= # Read the .lo file func_source "$arg" if test -z "$pic_object" || test -z "$non_pic_object" || test none = "$pic_object" && test none = "$non_pic_object"; then func_fatal_error "cannot find name of object for '$arg'" fi # Extract subdirectory from the argument. func_dirname "$arg" "/" "" xdir=$func_dirname_result test none = "$pic_object" || { # Prepend the subdirectory the object is found in. pic_object=$xdir$pic_object if test dlfiles = "$prev"; then if test yes = "$build_libtool_libs" && test yes = "$dlopen_support"; then func_append dlfiles " $pic_object" prev= continue else # If libtool objects are unsupported, then we need to preload. prev=dlprefiles fi fi # CHECK ME: I think I busted this. -Ossama if test dlprefiles = "$prev"; then # Preload the old-style object. func_append dlprefiles " $pic_object" prev= fi # A PIC object. func_append libobjs " $pic_object" arg=$pic_object } # Non-PIC object. if test none != "$non_pic_object"; then # Prepend the subdirectory the object is found in. non_pic_object=$xdir$non_pic_object # A standard non-PIC object func_append non_pic_objects " $non_pic_object" if test -z "$pic_object" || test none = "$pic_object"; then arg=$non_pic_object fi else # If the PIC object exists, use it instead. # $xdir was prepended to $pic_object above. non_pic_object=$pic_object func_append non_pic_objects " $non_pic_object" fi else # Only an error if not doing a dry-run. if $opt_dry_run; then # Extract subdirectory from the argument. func_dirname "$arg" "/" "" xdir=$func_dirname_result func_lo2o "$arg" pic_object=$xdir$objdir/$func_lo2o_result non_pic_object=$xdir$func_lo2o_result func_append libobjs " $pic_object" func_append non_pic_objects " $non_pic_object" else func_fatal_error "'$arg' is not a valid libtool object" fi fi ;; *.$libext) # An archive. func_append deplibs " $arg" func_append old_deplibs " $arg" continue ;; *.la) # A libtool-controlled library. func_resolve_sysroot "$arg" if test dlfiles = "$prev"; then # This library was specified with -dlopen. func_append dlfiles " $func_resolve_sysroot_result" prev= elif test dlprefiles = "$prev"; then # The library was specified with -dlpreopen. func_append dlprefiles " $func_resolve_sysroot_result" prev= else func_append deplibs " $func_resolve_sysroot_result" fi continue ;; # Some other compiler argument. *) # Unknown arguments in both finalize_command and compile_command need # to be aesthetically quoted because they are evaled later. func_quote_for_eval "$arg" arg=$func_quote_for_eval_result ;; esac # arg # Now actually substitute the argument into the commands. if test -n "$arg"; then func_append compile_command " $arg" func_append finalize_command " $arg" fi done # argument parsing loop test -n "$prev" && \ func_fatal_help "the '$prevarg' option requires an argument" if test yes = "$export_dynamic" && test -n "$export_dynamic_flag_spec"; then eval arg=\"$export_dynamic_flag_spec\" func_append compile_command " $arg" func_append finalize_command " $arg" fi oldlibs= # calculate the name of the file, without its directory func_basename "$output" outputname=$func_basename_result libobjs_save=$libobjs if test -n "$shlibpath_var"; then # get the directories listed in $shlibpath_var eval shlib_search_path=\`\$ECHO \"\$$shlibpath_var\" \| \$SED \'s/:/ /g\'\` else shlib_search_path= fi eval sys_lib_search_path=\"$sys_lib_search_path_spec\" eval sys_lib_dlsearch_path=\"$sys_lib_dlsearch_path_spec\" # Definition is injected by LT_CONFIG during libtool generation. func_munge_path_list sys_lib_dlsearch_path "$LT_SYS_LIBRARY_PATH" func_dirname "$output" "/" "" output_objdir=$func_dirname_result$objdir func_to_tool_file "$output_objdir/" tool_output_objdir=$func_to_tool_file_result # Create the object directory. func_mkdir_p "$output_objdir" # Determine the type of output case $output in "") func_fatal_help "you must specify an output file" ;; *.$libext) linkmode=oldlib ;; *.lo | *.$objext) linkmode=obj ;; *.la) linkmode=lib ;; *) linkmode=prog ;; # Anything else should be a program. esac specialdeplibs= libs= # Find all interdependent deplibs by searching for libraries # that are linked more than once (e.g. -la -lb -la) for deplib in $deplibs; do if $opt_preserve_dup_deps; then case "$libs " in *" $deplib "*) func_append specialdeplibs " $deplib" ;; esac fi func_append libs " $deplib" done if test lib = "$linkmode"; then libs="$predeps $libs $compiler_lib_search_path $postdeps" # Compute libraries that are listed more than once in $predeps # $postdeps and mark them as special (i.e., whose duplicates are # not to be eliminated). pre_post_deps= if $opt_duplicate_compiler_generated_deps; then for pre_post_dep in $predeps $postdeps; do case "$pre_post_deps " in *" $pre_post_dep "*) func_append specialdeplibs " $pre_post_deps" ;; esac func_append pre_post_deps " $pre_post_dep" done fi pre_post_deps= fi deplibs= newdependency_libs= newlib_search_path= need_relink=no # whether we're linking any uninstalled libtool libraries notinst_deplibs= # not-installed libtool libraries notinst_path= # paths that contain not-installed libtool libraries case $linkmode in lib) passes="conv dlpreopen link" for file in $dlfiles $dlprefiles; do case $file in *.la) ;; *) func_fatal_help "libraries can '-dlopen' only libtool libraries: $file" ;; esac done ;; prog) compile_deplibs= finalize_deplibs= alldeplibs=false newdlfiles= newdlprefiles= passes="conv scan dlopen dlpreopen link" ;; *) passes="conv" ;; esac for pass in $passes; do # The preopen pass in lib mode reverses $deplibs; put it back here # so that -L comes before libs that need it for instance... if test lib,link = "$linkmode,$pass"; then ## FIXME: Find the place where the list is rebuilt in the wrong ## order, and fix it there properly tmp_deplibs= for deplib in $deplibs; do tmp_deplibs="$deplib $tmp_deplibs" done deplibs=$tmp_deplibs fi if test lib,link = "$linkmode,$pass" || test prog,scan = "$linkmode,$pass"; then libs=$deplibs deplibs= fi if test prog = "$linkmode"; then case $pass in dlopen) libs=$dlfiles ;; dlpreopen) libs=$dlprefiles ;; link) libs="$deplibs %DEPLIBS%" test "X$link_all_deplibs" != Xno && libs="$libs $dependency_libs" ;; esac fi if test lib,dlpreopen = "$linkmode,$pass"; then # Collect and forward deplibs of preopened libtool libs for lib in $dlprefiles; do # Ignore non-libtool-libs dependency_libs= func_resolve_sysroot "$lib" case $lib in *.la) func_source "$func_resolve_sysroot_result" ;; esac # Collect preopened libtool deplibs, except any this library # has declared as weak libs for deplib in $dependency_libs; do func_basename "$deplib" deplib_base=$func_basename_result case " $weak_libs " in *" $deplib_base "*) ;; *) func_append deplibs " $deplib" ;; esac done done libs=$dlprefiles fi if test dlopen = "$pass"; then # Collect dlpreopened libraries save_deplibs=$deplibs deplibs= fi for deplib in $libs; do lib= found=false case $deplib in -mt|-mthreads|-kthread|-Kthread|-pthread|-pthreads|--thread-safe \ |-threads|-fopenmp|-openmp|-mp|-xopenmp|-omp|-qsmp=*) if test prog,link = "$linkmode,$pass"; then compile_deplibs="$deplib $compile_deplibs" finalize_deplibs="$deplib $finalize_deplibs" else func_append compiler_flags " $deplib" if test lib = "$linkmode"; then case "$new_inherited_linker_flags " in *" $deplib "*) ;; * ) func_append new_inherited_linker_flags " $deplib" ;; esac fi fi continue ;; -l*) if test lib != "$linkmode" && test prog != "$linkmode"; then func_warning "'-l' is ignored for archives/objects" continue fi func_stripname '-l' '' "$deplib" name=$func_stripname_result if test lib = "$linkmode"; then searchdirs="$newlib_search_path $lib_search_path $compiler_lib_search_dirs $sys_lib_search_path $shlib_search_path" else searchdirs="$newlib_search_path $lib_search_path $sys_lib_search_path $shlib_search_path" fi for searchdir in $searchdirs; do for search_ext in .la $std_shrext .so .a; do # Search the libtool library lib=$searchdir/lib$name$search_ext if test -f "$lib"; then if test .la = "$search_ext"; then found=: else found=false fi break 2 fi done done if $found; then # deplib is a libtool library # If $allow_libtool_libs_with_static_runtimes && $deplib is a stdlib, # We need to do some special things here, and not later. if test yes = "$allow_libtool_libs_with_static_runtimes"; then case " $predeps $postdeps " in *" $deplib "*) if func_lalib_p "$lib"; then library_names= old_library= func_source "$lib" for l in $old_library $library_names; do ll=$l done if test "X$ll" = "X$old_library"; then # only static version available found=false func_dirname "$lib" "" "." ladir=$func_dirname_result lib=$ladir/$old_library if test prog,link = "$linkmode,$pass"; then compile_deplibs="$deplib $compile_deplibs" finalize_deplibs="$deplib $finalize_deplibs" else deplibs="$deplib $deplibs" test lib = "$linkmode" && newdependency_libs="$deplib $newdependency_libs" fi continue fi fi ;; *) ;; esac fi else # deplib doesn't seem to be a libtool library if test prog,link = "$linkmode,$pass"; then compile_deplibs="$deplib $compile_deplibs" finalize_deplibs="$deplib $finalize_deplibs" else deplibs="$deplib $deplibs" test lib = "$linkmode" && newdependency_libs="$deplib $newdependency_libs" fi continue fi ;; # -l *.ltframework) if test prog,link = "$linkmode,$pass"; then compile_deplibs="$deplib $compile_deplibs" finalize_deplibs="$deplib $finalize_deplibs" else deplibs="$deplib $deplibs" if test lib = "$linkmode"; then case "$new_inherited_linker_flags " in *" $deplib "*) ;; * ) func_append new_inherited_linker_flags " $deplib" ;; esac fi fi continue ;; -L*) case $linkmode in lib) deplibs="$deplib $deplibs" test conv = "$pass" && continue newdependency_libs="$deplib $newdependency_libs" func_stripname '-L' '' "$deplib" func_resolve_sysroot "$func_stripname_result" func_append newlib_search_path " $func_resolve_sysroot_result" ;; prog) if test conv = "$pass"; then deplibs="$deplib $deplibs" continue fi if test scan = "$pass"; then deplibs="$deplib $deplibs" else compile_deplibs="$deplib $compile_deplibs" finalize_deplibs="$deplib $finalize_deplibs" fi func_stripname '-L' '' "$deplib" func_resolve_sysroot "$func_stripname_result" func_append newlib_search_path " $func_resolve_sysroot_result" ;; *) func_warning "'-L' is ignored for archives/objects" ;; esac # linkmode continue ;; # -L -R*) if test link = "$pass"; then func_stripname '-R' '' "$deplib" func_resolve_sysroot "$func_stripname_result" dir=$func_resolve_sysroot_result # Make sure the xrpath contains only unique directories. case "$xrpath " in *" $dir "*) ;; *) func_append xrpath " $dir" ;; esac fi deplibs="$deplib $deplibs" continue ;; *.la) func_resolve_sysroot "$deplib" lib=$func_resolve_sysroot_result ;; *.$libext) if test conv = "$pass"; then deplibs="$deplib $deplibs" continue fi case $linkmode in lib) # Linking convenience modules into shared libraries is allowed, # but linking other static libraries is non-portable. case " $dlpreconveniencelibs " in *" $deplib "*) ;; *) valid_a_lib=false case $deplibs_check_method in match_pattern*) set dummy $deplibs_check_method; shift match_pattern_regex=`expr "$deplibs_check_method" : "$1 \(.*\)"` if eval "\$ECHO \"$deplib\"" 2>/dev/null | $SED 10q \ | $EGREP "$match_pattern_regex" > /dev/null; then valid_a_lib=: fi ;; pass_all) valid_a_lib=: ;; esac if $valid_a_lib; then echo $ECHO "*** Warning: Linking the shared library $output against the" $ECHO "*** static library $deplib is not portable!" deplibs="$deplib $deplibs" else echo $ECHO "*** Warning: Trying to link with static lib archive $deplib." echo "*** I have the capability to make that library automatically link in when" echo "*** you link to this library. But I can only do this if you have a" echo "*** shared version of the library, which you do not appear to have" echo "*** because the file extensions .$libext of this argument makes me believe" echo "*** that it is just a static archive that I should not use here." fi ;; esac continue ;; prog) if test link != "$pass"; then deplibs="$deplib $deplibs" else compile_deplibs="$deplib $compile_deplibs" finalize_deplibs="$deplib $finalize_deplibs" fi continue ;; esac # linkmode ;; # *.$libext *.lo | *.$objext) if test conv = "$pass"; then deplibs="$deplib $deplibs" elif test prog = "$linkmode"; then if test dlpreopen = "$pass" || test yes != "$dlopen_support" || test no = "$build_libtool_libs"; then # If there is no dlopen support or we're linking statically, # we need to preload. func_append newdlprefiles " $deplib" compile_deplibs="$deplib $compile_deplibs" finalize_deplibs="$deplib $finalize_deplibs" else func_append newdlfiles " $deplib" fi fi continue ;; %DEPLIBS%) alldeplibs=: continue ;; esac # case $deplib $found || test -f "$lib" \ || func_fatal_error "cannot find the library '$lib' or unhandled argument '$deplib'" # Check to see that this really is a libtool archive. func_lalib_unsafe_p "$lib" \ || func_fatal_error "'$lib' is not a valid libtool archive" func_dirname "$lib" "" "." ladir=$func_dirname_result dlname= dlopen= dlpreopen= libdir= library_names= old_library= inherited_linker_flags= # If the library was installed with an old release of libtool, # it will not redefine variables installed, or shouldnotlink installed=yes shouldnotlink=no avoidtemprpath= # Read the .la file func_source "$lib" # Convert "-framework foo" to "foo.ltframework" if test -n "$inherited_linker_flags"; then tmp_inherited_linker_flags=`$ECHO "$inherited_linker_flags" | $SED 's/-framework \([^ $]*\)/\1.ltframework/g'` for tmp_inherited_linker_flag in $tmp_inherited_linker_flags; do case " $new_inherited_linker_flags " in *" $tmp_inherited_linker_flag "*) ;; *) func_append new_inherited_linker_flags " $tmp_inherited_linker_flag";; esac done fi dependency_libs=`$ECHO " $dependency_libs" | $SED 's% \([^ $]*\).ltframework% -framework \1%g'` if test lib,link = "$linkmode,$pass" || test prog,scan = "$linkmode,$pass" || { test prog != "$linkmode" && test lib != "$linkmode"; }; then test -n "$dlopen" && func_append dlfiles " $dlopen" test -n "$dlpreopen" && func_append dlprefiles " $dlpreopen" fi if test conv = "$pass"; then # Only check for convenience libraries deplibs="$lib $deplibs" if test -z "$libdir"; then if test -z "$old_library"; then func_fatal_error "cannot find name of link library for '$lib'" fi # It is a libtool convenience library, so add in its objects. func_append convenience " $ladir/$objdir/$old_library" func_append old_convenience " $ladir/$objdir/$old_library" tmp_libs= for deplib in $dependency_libs; do deplibs="$deplib $deplibs" if $opt_preserve_dup_deps; then case "$tmp_libs " in *" $deplib "*) func_append specialdeplibs " $deplib" ;; esac fi func_append tmp_libs " $deplib" done elif test prog != "$linkmode" && test lib != "$linkmode"; then func_fatal_error "'$lib' is not a convenience library" fi continue fi # $pass = conv # Get the name of the library we link against. linklib= if test -n "$old_library" && { test yes = "$prefer_static_libs" || test built,no = "$prefer_static_libs,$installed"; }; then linklib=$old_library else for l in $old_library $library_names; do linklib=$l done fi if test -z "$linklib"; then func_fatal_error "cannot find name of link library for '$lib'" fi # This library was specified with -dlopen. if test dlopen = "$pass"; then test -z "$libdir" \ && func_fatal_error "cannot -dlopen a convenience library: '$lib'" if test -z "$dlname" || test yes != "$dlopen_support" || test no = "$build_libtool_libs" then # If there is no dlname, no dlopen support or we're linking # statically, we need to preload. We also need to preload any # dependent libraries so libltdl's deplib preloader doesn't # bomb out in the load deplibs phase. func_append dlprefiles " $lib $dependency_libs" else func_append newdlfiles " $lib" fi continue fi # $pass = dlopen # We need an absolute path. case $ladir in [\\/]* | [A-Za-z]:[\\/]*) abs_ladir=$ladir ;; *) abs_ladir=`cd "$ladir" && pwd` if test -z "$abs_ladir"; then func_warning "cannot determine absolute directory name of '$ladir'" func_warning "passing it literally to the linker, although it might fail" abs_ladir=$ladir fi ;; esac func_basename "$lib" laname=$func_basename_result # Find the relevant object directory and library name. if test yes = "$installed"; then if test ! -f "$lt_sysroot$libdir/$linklib" && test -f "$abs_ladir/$linklib"; then func_warning "library '$lib' was moved." dir=$ladir absdir=$abs_ladir libdir=$abs_ladir else dir=$lt_sysroot$libdir absdir=$lt_sysroot$libdir fi test yes = "$hardcode_automatic" && avoidtemprpath=yes else if test ! -f "$ladir/$objdir/$linklib" && test -f "$abs_ladir/$linklib"; then dir=$ladir absdir=$abs_ladir # Remove this search path later func_append notinst_path " $abs_ladir" else dir=$ladir/$objdir absdir=$abs_ladir/$objdir # Remove this search path later func_append notinst_path " $abs_ladir" fi fi # $installed = yes func_stripname 'lib' '.la' "$laname" name=$func_stripname_result # This library was specified with -dlpreopen. if test dlpreopen = "$pass"; then if test -z "$libdir" && test prog = "$linkmode"; then func_fatal_error "only libraries may -dlpreopen a convenience library: '$lib'" fi case $host in # special handling for platforms with PE-DLLs. *cygwin* | *mingw* | *cegcc* ) # Linker will automatically link against shared library if both # static and shared are present. Therefore, ensure we extract # symbols from the import library if a shared library is present # (otherwise, the dlopen module name will be incorrect). We do # this by putting the import library name into $newdlprefiles. # We recover the dlopen module name by 'saving' the la file # name in a special purpose variable, and (later) extracting the # dlname from the la file. if test -n "$dlname"; then func_tr_sh "$dir/$linklib" eval "libfile_$func_tr_sh_result=\$abs_ladir/\$laname" func_append newdlprefiles " $dir/$linklib" else func_append newdlprefiles " $dir/$old_library" # Keep a list of preopened convenience libraries to check # that they are being used correctly in the link pass. test -z "$libdir" && \ func_append dlpreconveniencelibs " $dir/$old_library" fi ;; * ) # Prefer using a static library (so that no silly _DYNAMIC symbols # are required to link). if test -n "$old_library"; then func_append newdlprefiles " $dir/$old_library" # Keep a list of preopened convenience libraries to check # that they are being used correctly in the link pass. test -z "$libdir" && \ func_append dlpreconveniencelibs " $dir/$old_library" # Otherwise, use the dlname, so that lt_dlopen finds it. elif test -n "$dlname"; then func_append newdlprefiles " $dir/$dlname" else func_append newdlprefiles " $dir/$linklib" fi ;; esac fi # $pass = dlpreopen if test -z "$libdir"; then # Link the convenience library if test lib = "$linkmode"; then deplibs="$dir/$old_library $deplibs" elif test prog,link = "$linkmode,$pass"; then compile_deplibs="$dir/$old_library $compile_deplibs" finalize_deplibs="$dir/$old_library $finalize_deplibs" else deplibs="$lib $deplibs" # used for prog,scan pass fi continue fi if test prog = "$linkmode" && test link != "$pass"; then func_append newlib_search_path " $ladir" deplibs="$lib $deplibs" linkalldeplibs=false if test no != "$link_all_deplibs" || test -z "$library_names" || test no = "$build_libtool_libs"; then linkalldeplibs=: fi tmp_libs= for deplib in $dependency_libs; do case $deplib in -L*) func_stripname '-L' '' "$deplib" func_resolve_sysroot "$func_stripname_result" func_append newlib_search_path " $func_resolve_sysroot_result" ;; esac # Need to link against all dependency_libs? if $linkalldeplibs; then deplibs="$deplib $deplibs" else # Need to hardcode shared library paths # or/and link against static libraries newdependency_libs="$deplib $newdependency_libs" fi if $opt_preserve_dup_deps; then case "$tmp_libs " in *" $deplib "*) func_append specialdeplibs " $deplib" ;; esac fi func_append tmp_libs " $deplib" done # for deplib continue fi # $linkmode = prog... if test prog,link = "$linkmode,$pass"; then if test -n "$library_names" && { { test no = "$prefer_static_libs" || test built,yes = "$prefer_static_libs,$installed"; } || test -z "$old_library"; }; then # We need to hardcode the library path if test -n "$shlibpath_var" && test -z "$avoidtemprpath"; then # Make sure the rpath contains only unique directories. case $temp_rpath: in *"$absdir:"*) ;; *) func_append temp_rpath "$absdir:" ;; esac fi # Hardcode the library path. # Skip directories that are in the system default run-time # search path. case " $sys_lib_dlsearch_path " in *" $absdir "*) ;; *) case "$compile_rpath " in *" $absdir "*) ;; *) func_append compile_rpath " $absdir" ;; esac ;; esac case " $sys_lib_dlsearch_path " in *" $libdir "*) ;; *) case "$finalize_rpath " in *" $libdir "*) ;; *) func_append finalize_rpath " $libdir" ;; esac ;; esac fi # $linkmode,$pass = prog,link... if $alldeplibs && { test pass_all = "$deplibs_check_method" || { test yes = "$build_libtool_libs" && test -n "$library_names"; }; }; then # We only need to search for static libraries continue fi fi link_static=no # Whether the deplib will be linked statically use_static_libs=$prefer_static_libs if test built = "$use_static_libs" && test yes = "$installed"; then use_static_libs=no fi if test -n "$library_names" && { test no = "$use_static_libs" || test -z "$old_library"; }; then case $host in *cygwin* | *mingw* | *cegcc* | *os2*) # No point in relinking DLLs because paths are not encoded func_append notinst_deplibs " $lib" need_relink=no ;; *) if test no = "$installed"; then func_append notinst_deplibs " $lib" need_relink=yes fi ;; esac # This is a shared library # Warn about portability, can't link against -module's on some # systems (darwin). Don't bleat about dlopened modules though! dlopenmodule= for dlpremoduletest in $dlprefiles; do if test "X$dlpremoduletest" = "X$lib"; then dlopenmodule=$dlpremoduletest break fi done if test -z "$dlopenmodule" && test yes = "$shouldnotlink" && test link = "$pass"; then echo if test prog = "$linkmode"; then $ECHO "*** Warning: Linking the executable $output against the loadable module" else $ECHO "*** Warning: Linking the shared library $output against the loadable module" fi $ECHO "*** $linklib is not portable!" fi if test lib = "$linkmode" && test yes = "$hardcode_into_libs"; then # Hardcode the library path. # Skip directories that are in the system default run-time # search path. case " $sys_lib_dlsearch_path " in *" $absdir "*) ;; *) case "$compile_rpath " in *" $absdir "*) ;; *) func_append compile_rpath " $absdir" ;; esac ;; esac case " $sys_lib_dlsearch_path " in *" $libdir "*) ;; *) case "$finalize_rpath " in *" $libdir "*) ;; *) func_append finalize_rpath " $libdir" ;; esac ;; esac fi if test -n "$old_archive_from_expsyms_cmds"; then # figure out the soname set dummy $library_names shift realname=$1 shift libname=`eval "\\$ECHO \"$libname_spec\""` # use dlname if we got it. it's perfectly good, no? if test -n "$dlname"; then soname=$dlname elif test -n "$soname_spec"; then # bleh windows case $host in *cygwin* | mingw* | *cegcc* | *os2*) func_arith $current - $age major=$func_arith_result versuffix=-$major ;; esac eval soname=\"$soname_spec\" else soname=$realname fi # Make a new name for the extract_expsyms_cmds to use soroot=$soname func_basename "$soroot" soname=$func_basename_result func_stripname 'lib' '.dll' "$soname" newlib=libimp-$func_stripname_result.a # If the library has no export list, then create one now if test -f "$output_objdir/$soname-def"; then : else func_verbose "extracting exported symbol list from '$soname'" func_execute_cmds "$extract_expsyms_cmds" 'exit $?' fi # Create $newlib if test -f "$output_objdir/$newlib"; then :; else func_verbose "generating import library for '$soname'" func_execute_cmds "$old_archive_from_expsyms_cmds" 'exit $?' fi # make sure the library variables are pointing to the new library dir=$output_objdir linklib=$newlib fi # test -n "$old_archive_from_expsyms_cmds" if test prog = "$linkmode" || test relink != "$opt_mode"; then add_shlibpath= add_dir= add= lib_linked=yes case $hardcode_action in immediate | unsupported) if test no = "$hardcode_direct"; then add=$dir/$linklib case $host in *-*-sco3.2v5.0.[024]*) add_dir=-L$dir ;; *-*-sysv4*uw2*) add_dir=-L$dir ;; *-*-sysv5OpenUNIX* | *-*-sysv5UnixWare7.[01].[10]* | \ *-*-unixware7*) add_dir=-L$dir ;; *-*-darwin* ) # if the lib is a (non-dlopened) module then we cannot # link against it, someone is ignoring the earlier warnings if /usr/bin/file -L $add 2> /dev/null | $GREP ": [^:]* bundle" >/dev/null; then if test "X$dlopenmodule" != "X$lib"; then $ECHO "*** Warning: lib $linklib is a module, not a shared library" if test -z "$old_library"; then echo echo "*** And there doesn't seem to be a static archive available" echo "*** The link will probably fail, sorry" else add=$dir/$old_library fi elif test -n "$old_library"; then add=$dir/$old_library fi fi esac elif test no = "$hardcode_minus_L"; then case $host in *-*-sunos*) add_shlibpath=$dir ;; esac add_dir=-L$dir add=-l$name elif test no = "$hardcode_shlibpath_var"; then add_shlibpath=$dir add=-l$name else lib_linked=no fi ;; relink) if test yes = "$hardcode_direct" && test no = "$hardcode_direct_absolute"; then add=$dir/$linklib elif test yes = "$hardcode_minus_L"; then add_dir=-L$absdir # Try looking first in the location we're being installed to. if test -n "$inst_prefix_dir"; then case $libdir in [\\/]*) func_append add_dir " -L$inst_prefix_dir$libdir" ;; esac fi add=-l$name elif test yes = "$hardcode_shlibpath_var"; then add_shlibpath=$dir add=-l$name else lib_linked=no fi ;; *) lib_linked=no ;; esac if test yes != "$lib_linked"; then func_fatal_configuration "unsupported hardcode properties" fi if test -n "$add_shlibpath"; then case :$compile_shlibpath: in *":$add_shlibpath:"*) ;; *) func_append compile_shlibpath "$add_shlibpath:" ;; esac fi if test prog = "$linkmode"; then test -n "$add_dir" && compile_deplibs="$add_dir $compile_deplibs" test -n "$add" && compile_deplibs="$add $compile_deplibs" else test -n "$add_dir" && deplibs="$add_dir $deplibs" test -n "$add" && deplibs="$add $deplibs" if test yes != "$hardcode_direct" && test yes != "$hardcode_minus_L" && test yes = "$hardcode_shlibpath_var"; then case :$finalize_shlibpath: in *":$libdir:"*) ;; *) func_append finalize_shlibpath "$libdir:" ;; esac fi fi fi if test prog = "$linkmode" || test relink = "$opt_mode"; then add_shlibpath= add_dir= add= # Finalize command for both is simple: just hardcode it. if test yes = "$hardcode_direct" && test no = "$hardcode_direct_absolute"; then add=$libdir/$linklib elif test yes = "$hardcode_minus_L"; then add_dir=-L$libdir add=-l$name elif test yes = "$hardcode_shlibpath_var"; then case :$finalize_shlibpath: in *":$libdir:"*) ;; *) func_append finalize_shlibpath "$libdir:" ;; esac add=-l$name elif test yes = "$hardcode_automatic"; then if test -n "$inst_prefix_dir" && test -f "$inst_prefix_dir$libdir/$linklib"; then add=$inst_prefix_dir$libdir/$linklib else add=$libdir/$linklib fi else # We cannot seem to hardcode it, guess we'll fake it. add_dir=-L$libdir # Try looking first in the location we're being installed to. if test -n "$inst_prefix_dir"; then case $libdir in [\\/]*) func_append add_dir " -L$inst_prefix_dir$libdir" ;; esac fi add=-l$name fi if test prog = "$linkmode"; then test -n "$add_dir" && finalize_deplibs="$add_dir $finalize_deplibs" test -n "$add" && finalize_deplibs="$add $finalize_deplibs" else test -n "$add_dir" && deplibs="$add_dir $deplibs" test -n "$add" && deplibs="$add $deplibs" fi fi elif test prog = "$linkmode"; then # Here we assume that one of hardcode_direct or hardcode_minus_L # is not unsupported. This is valid on all known static and # shared platforms. if test unsupported != "$hardcode_direct"; then test -n "$old_library" && linklib=$old_library compile_deplibs="$dir/$linklib $compile_deplibs" finalize_deplibs="$dir/$linklib $finalize_deplibs" else compile_deplibs="-l$name -L$dir $compile_deplibs" finalize_deplibs="-l$name -L$dir $finalize_deplibs" fi elif test yes = "$build_libtool_libs"; then # Not a shared library if test pass_all != "$deplibs_check_method"; then # We're trying link a shared library against a static one # but the system doesn't support it. # Just print a warning and add the library to dependency_libs so # that the program can be linked against the static library. echo $ECHO "*** Warning: This system cannot link to static lib archive $lib." echo "*** I have the capability to make that library automatically link in when" echo "*** you link to this library. But I can only do this if you have a" echo "*** shared version of the library, which you do not appear to have." if test yes = "$module"; then echo "*** But as you try to build a module library, libtool will still create " echo "*** a static module, that should work as long as the dlopening application" echo "*** is linked with the -dlopen flag to resolve symbols at runtime." if test -z "$global_symbol_pipe"; then echo echo "*** However, this would only work if libtool was able to extract symbol" echo "*** lists from a program, using 'nm' or equivalent, but libtool could" echo "*** not find such a program. So, this module is probably useless." echo "*** 'nm' from GNU binutils and a full rebuild may help." fi if test no = "$build_old_libs"; then build_libtool_libs=module build_old_libs=yes else build_libtool_libs=no fi fi else deplibs="$dir/$old_library $deplibs" link_static=yes fi fi # link shared/static library? if test lib = "$linkmode"; then if test -n "$dependency_libs" && { test yes != "$hardcode_into_libs" || test yes = "$build_old_libs" || test yes = "$link_static"; }; then # Extract -R from dependency_libs temp_deplibs= for libdir in $dependency_libs; do case $libdir in -R*) func_stripname '-R' '' "$libdir" temp_xrpath=$func_stripname_result case " $xrpath " in *" $temp_xrpath "*) ;; *) func_append xrpath " $temp_xrpath";; esac;; *) func_append temp_deplibs " $libdir";; esac done dependency_libs=$temp_deplibs fi func_append newlib_search_path " $absdir" # Link against this library test no = "$link_static" && newdependency_libs="$abs_ladir/$laname $newdependency_libs" # ... and its dependency_libs tmp_libs= for deplib in $dependency_libs; do newdependency_libs="$deplib $newdependency_libs" case $deplib in -L*) func_stripname '-L' '' "$deplib" func_resolve_sysroot "$func_stripname_result";; *) func_resolve_sysroot "$deplib" ;; esac if $opt_preserve_dup_deps; then case "$tmp_libs " in *" $func_resolve_sysroot_result "*) func_append specialdeplibs " $func_resolve_sysroot_result" ;; esac fi func_append tmp_libs " $func_resolve_sysroot_result" done if test no != "$link_all_deplibs"; then # Add the search paths of all dependency libraries for deplib in $dependency_libs; do path= case $deplib in -L*) path=$deplib ;; *.la) func_resolve_sysroot "$deplib" deplib=$func_resolve_sysroot_result func_dirname "$deplib" "" "." dir=$func_dirname_result # We need an absolute path. case $dir in [\\/]* | [A-Za-z]:[\\/]*) absdir=$dir ;; *) absdir=`cd "$dir" && pwd` if test -z "$absdir"; then func_warning "cannot determine absolute directory name of '$dir'" absdir=$dir fi ;; esac if $GREP "^installed=no" $deplib > /dev/null; then case $host in *-*-darwin*) depdepl= eval deplibrary_names=`$SED -n -e 's/^library_names=\(.*\)$/\1/p' $deplib` if test -n "$deplibrary_names"; then for tmp in $deplibrary_names; do depdepl=$tmp done if test -f "$absdir/$objdir/$depdepl"; then depdepl=$absdir/$objdir/$depdepl darwin_install_name=`$OTOOL -L $depdepl | awk '{if (NR == 2) {print $1;exit}}'` if test -z "$darwin_install_name"; then darwin_install_name=`$OTOOL64 -L $depdepl | awk '{if (NR == 2) {print $1;exit}}'` fi func_append compiler_flags " $wl-dylib_file $wl$darwin_install_name:$depdepl" func_append linker_flags " -dylib_file $darwin_install_name:$depdepl" path= fi fi ;; *) path=-L$absdir/$objdir ;; esac else eval libdir=`$SED -n -e 's/^libdir=\(.*\)$/\1/p' $deplib` test -z "$libdir" && \ func_fatal_error "'$deplib' is not a valid libtool archive" test "$absdir" != "$libdir" && \ func_warning "'$deplib' seems to be moved" path=-L$absdir fi ;; esac case " $deplibs " in *" $path "*) ;; *) deplibs="$path $deplibs" ;; esac done fi # link_all_deplibs != no fi # linkmode = lib done # for deplib in $libs if test link = "$pass"; then if test prog = "$linkmode"; then compile_deplibs="$new_inherited_linker_flags $compile_deplibs" finalize_deplibs="$new_inherited_linker_flags $finalize_deplibs" else compiler_flags="$compiler_flags "`$ECHO " $new_inherited_linker_flags" | $SED 's% \([^ $]*\).ltframework% -framework \1%g'` fi fi dependency_libs=$newdependency_libs if test dlpreopen = "$pass"; then # Link the dlpreopened libraries before other libraries for deplib in $save_deplibs; do deplibs="$deplib $deplibs" done fi if test dlopen != "$pass"; then test conv = "$pass" || { # Make sure lib_search_path contains only unique directories. lib_search_path= for dir in $newlib_search_path; do case "$lib_search_path " in *" $dir "*) ;; *) func_append lib_search_path " $dir" ;; esac done newlib_search_path= } if test prog,link = "$linkmode,$pass"; then vars="compile_deplibs finalize_deplibs" else vars=deplibs fi for var in $vars dependency_libs; do # Add libraries to $var in reverse order eval tmp_libs=\"\$$var\" new_libs= for deplib in $tmp_libs; do # FIXME: Pedantically, this is the right thing to do, so # that some nasty dependency loop isn't accidentally # broken: #new_libs="$deplib $new_libs" # Pragmatically, this seems to cause very few problems in # practice: case $deplib in -L*) new_libs="$deplib $new_libs" ;; -R*) ;; *) # And here is the reason: when a library appears more # than once as an explicit dependence of a library, or # is implicitly linked in more than once by the # compiler, it is considered special, and multiple # occurrences thereof are not removed. Compare this # with having the same library being listed as a # dependency of multiple other libraries: in this case, # we know (pedantically, we assume) the library does not # need to be listed more than once, so we keep only the # last copy. This is not always right, but it is rare # enough that we require users that really mean to play # such unportable linking tricks to link the library # using -Wl,-lname, so that libtool does not consider it # for duplicate removal. case " $specialdeplibs " in *" $deplib "*) new_libs="$deplib $new_libs" ;; *) case " $new_libs " in *" $deplib "*) ;; *) new_libs="$deplib $new_libs" ;; esac ;; esac ;; esac done tmp_libs= for deplib in $new_libs; do case $deplib in -L*) case " $tmp_libs " in *" $deplib "*) ;; *) func_append tmp_libs " $deplib" ;; esac ;; *) func_append tmp_libs " $deplib" ;; esac done eval $var=\"$tmp_libs\" done # for var fi # Add Sun CC postdeps if required: test CXX = "$tagname" && { case $host_os in linux*) case `$CC -V 2>&1 | sed 5q` in *Sun\ C*) # Sun C++ 5.9 func_suncc_cstd_abi if test no != "$suncc_use_cstd_abi"; then func_append postdeps ' -library=Cstd -library=Crun' fi ;; esac ;; solaris*) func_cc_basename "$CC" case $func_cc_basename_result in CC* | sunCC*) func_suncc_cstd_abi if test no != "$suncc_use_cstd_abi"; then func_append postdeps ' -library=Cstd -library=Crun' fi ;; esac ;; esac } # Last step: remove runtime libs from dependency_libs # (they stay in deplibs) tmp_libs= for i in $dependency_libs; do case " $predeps $postdeps $compiler_lib_search_path " in *" $i "*) i= ;; esac if test -n "$i"; then func_append tmp_libs " $i" fi done dependency_libs=$tmp_libs done # for pass if test prog = "$linkmode"; then dlfiles=$newdlfiles fi if test prog = "$linkmode" || test lib = "$linkmode"; then dlprefiles=$newdlprefiles fi case $linkmode in oldlib) if test -n "$dlfiles$dlprefiles" || test no != "$dlself"; then func_warning "'-dlopen' is ignored for archives" fi case " $deplibs" in *\ -l* | *\ -L*) func_warning "'-l' and '-L' are ignored for archives" ;; esac test -n "$rpath" && \ func_warning "'-rpath' is ignored for archives" test -n "$xrpath" && \ func_warning "'-R' is ignored for archives" test -n "$vinfo" && \ func_warning "'-version-info/-version-number' is ignored for archives" test -n "$release" && \ func_warning "'-release' is ignored for archives" test -n "$export_symbols$export_symbols_regex" && \ func_warning "'-export-symbols' is ignored for archives" # Now set the variables for building old libraries. build_libtool_libs=no oldlibs=$output func_append objs "$old_deplibs" ;; lib) # Make sure we only generate libraries of the form 'libNAME.la'. case $outputname in lib*) func_stripname 'lib' '.la' "$outputname" name=$func_stripname_result eval shared_ext=\"$shrext_cmds\" eval libname=\"$libname_spec\" ;; *) test no = "$module" \ && func_fatal_help "libtool library '$output' must begin with 'lib'" if test no != "$need_lib_prefix"; then # Add the "lib" prefix for modules if required func_stripname '' '.la' "$outputname" name=$func_stripname_result eval shared_ext=\"$shrext_cmds\" eval libname=\"$libname_spec\" else func_stripname '' '.la' "$outputname" libname=$func_stripname_result fi ;; esac if test -n "$objs"; then if test pass_all != "$deplibs_check_method"; then func_fatal_error "cannot build libtool library '$output' from non-libtool objects on this host:$objs" else echo $ECHO "*** Warning: Linking the shared library $output against the non-libtool" $ECHO "*** objects $objs is not portable!" func_append libobjs " $objs" fi fi test no = "$dlself" \ || func_warning "'-dlopen self' is ignored for libtool libraries" set dummy $rpath shift test 1 -lt "$#" \ && func_warning "ignoring multiple '-rpath's for a libtool library" install_libdir=$1 oldlibs= if test -z "$rpath"; then if test yes = "$build_libtool_libs"; then # Building a libtool convenience library. # Some compilers have problems with a '.al' extension so # convenience libraries should have the same extension an # archive normally would. oldlibs="$output_objdir/$libname.$libext $oldlibs" build_libtool_libs=convenience build_old_libs=yes fi test -n "$vinfo" && \ func_warning "'-version-info/-version-number' is ignored for convenience libraries" test -n "$release" && \ func_warning "'-release' is ignored for convenience libraries" else # Parse the version information argument. save_ifs=$IFS; IFS=: set dummy $vinfo 0 0 0 shift IFS=$save_ifs test -n "$7" && \ func_fatal_help "too many parameters to '-version-info'" # convert absolute version numbers to libtool ages # this retains compatibility with .la files and attempts # to make the code below a bit more comprehensible case $vinfo_number in yes) number_major=$1 number_minor=$2 number_revision=$3 # # There are really only two kinds -- those that # use the current revision as the major version # and those that subtract age and use age as # a minor version. But, then there is irix # that has an extra 1 added just for fun # case $version_type in # correct linux to gnu/linux during the next big refactor darwin|freebsd-elf|linux|osf|windows|none) func_arith $number_major + $number_minor current=$func_arith_result age=$number_minor revision=$number_revision ;; freebsd-aout|qnx|sunos) current=$number_major revision=$number_minor age=0 ;; irix|nonstopux) func_arith $number_major + $number_minor current=$func_arith_result age=$number_minor revision=$number_minor lt_irix_increment=no ;; *) func_fatal_configuration "$modename: unknown library version type '$version_type'" ;; esac ;; no) current=$1 revision=$2 age=$3 ;; esac # Check that each of the things are valid numbers. case $current in 0|[1-9]|[1-9][0-9]|[1-9][0-9][0-9]|[1-9][0-9][0-9][0-9]|[1-9][0-9][0-9][0-9][0-9]) ;; *) func_error "CURRENT '$current' must be a nonnegative integer" func_fatal_error "'$vinfo' is not valid version information" ;; esac case $revision in 0|[1-9]|[1-9][0-9]|[1-9][0-9][0-9]|[1-9][0-9][0-9][0-9]|[1-9][0-9][0-9][0-9][0-9]) ;; *) func_error "REVISION '$revision' must be a nonnegative integer" func_fatal_error "'$vinfo' is not valid version information" ;; esac case $age in 0|[1-9]|[1-9][0-9]|[1-9][0-9][0-9]|[1-9][0-9][0-9][0-9]|[1-9][0-9][0-9][0-9][0-9]) ;; *) func_error "AGE '$age' must be a nonnegative integer" func_fatal_error "'$vinfo' is not valid version information" ;; esac if test "$age" -gt "$current"; then func_error "AGE '$age' is greater than the current interface number '$current'" func_fatal_error "'$vinfo' is not valid version information" fi # Calculate the version variables. major= versuffix= verstring= case $version_type in none) ;; darwin) # Like Linux, but with the current version available in # verstring for coding it into the library header func_arith $current - $age major=.$func_arith_result versuffix=$major.$age.$revision # Darwin ld doesn't like 0 for these options... func_arith $current + 1 minor_current=$func_arith_result xlcverstring="$wl-compatibility_version $wl$minor_current $wl-current_version $wl$minor_current.$revision" verstring="-compatibility_version $minor_current -current_version $minor_current.$revision" # On Darwin other compilers case $CC in nagfor*) verstring="$wl-compatibility_version $wl$minor_current $wl-current_version $wl$minor_current.$revision" ;; *) verstring="-compatibility_version $minor_current -current_version $minor_current.$revision" ;; esac ;; freebsd-aout) major=.$current versuffix=.$current.$revision ;; freebsd-elf) func_arith $current - $age major=.$func_arith_result versuffix=$major.$age.$revision ;; irix | nonstopux) if test no = "$lt_irix_increment"; then func_arith $current - $age else func_arith $current - $age + 1 fi major=$func_arith_result case $version_type in nonstopux) verstring_prefix=nonstopux ;; *) verstring_prefix=sgi ;; esac verstring=$verstring_prefix$major.$revision # Add in all the interfaces that we are compatible with. loop=$revision while test 0 -ne "$loop"; do func_arith $revision - $loop iface=$func_arith_result func_arith $loop - 1 loop=$func_arith_result verstring=$verstring_prefix$major.$iface:$verstring done # Before this point, $major must not contain '.'. major=.$major versuffix=$major.$revision ;; linux) # correct to gnu/linux during the next big refactor func_arith $current - $age major=.$func_arith_result versuffix=$major.$age.$revision ;; osf) func_arith $current - $age major=.$func_arith_result versuffix=.$current.$age.$revision verstring=$current.$age.$revision # Add in all the interfaces that we are compatible with. loop=$age while test 0 -ne "$loop"; do func_arith $current - $loop iface=$func_arith_result func_arith $loop - 1 loop=$func_arith_result verstring=$verstring:$iface.0 done # Make executables depend on our current version. func_append verstring ":$current.0" ;; qnx) major=.$current versuffix=.$current ;; sco) major=.$current versuffix=.$current ;; sunos) major=.$current versuffix=.$current.$revision ;; windows) # Use '-' rather than '.', since we only want one # extension on DOS 8.3 file systems. func_arith $current - $age major=$func_arith_result versuffix=-$major ;; *) func_fatal_configuration "unknown library version type '$version_type'" ;; esac # Clear the version info if we defaulted, and they specified a release. if test -z "$vinfo" && test -n "$release"; then major= case $version_type in darwin) # we can't check for "0.0" in archive_cmds due to quoting # problems, so we reset it completely verstring= ;; *) verstring=0.0 ;; esac if test no = "$need_version"; then versuffix= else versuffix=.0.0 fi fi # Remove version info from name if versioning should be avoided if test yes,no = "$avoid_version,$need_version"; then major= versuffix= verstring= fi # Check to see if the archive will have undefined symbols. if test yes = "$allow_undefined"; then if test unsupported = "$allow_undefined_flag"; then if test yes = "$build_old_libs"; then func_warning "undefined symbols not allowed in $host shared libraries; building static only" build_libtool_libs=no else func_fatal_error "can't build $host shared library unless -no-undefined is specified" fi fi else # Don't allow undefined symbols. allow_undefined_flag=$no_undefined_flag fi fi func_generate_dlsyms "$libname" "$libname" : func_append libobjs " $symfileobj" test " " = "$libobjs" && libobjs= if test relink != "$opt_mode"; then # Remove our outputs, but don't remove object files since they # may have been created when compiling PIC objects. removelist= tempremovelist=`$ECHO "$output_objdir/*"` for p in $tempremovelist; do case $p in *.$objext | *.gcno) ;; $output_objdir/$outputname | $output_objdir/$libname.* | $output_objdir/$libname$release.*) if test -n "$precious_files_regex"; then if $ECHO "$p" | $EGREP -e "$precious_files_regex" >/dev/null 2>&1 then continue fi fi func_append removelist " $p" ;; *) ;; esac done test -n "$removelist" && \ func_show_eval "${RM}r \$removelist" fi # Now set the variables for building old libraries. if test yes = "$build_old_libs" && test convenience != "$build_libtool_libs"; then func_append oldlibs " $output_objdir/$libname.$libext" # Transform .lo files to .o files. oldobjs="$objs "`$ECHO "$libobjs" | $SP2NL | $SED "/\.$libext$/d; $lo2o" | $NL2SP` fi # Eliminate all temporary directories. #for path in $notinst_path; do # lib_search_path=`$ECHO "$lib_search_path " | $SED "s% $path % %g"` # deplibs=`$ECHO "$deplibs " | $SED "s% -L$path % %g"` # dependency_libs=`$ECHO "$dependency_libs " | $SED "s% -L$path % %g"` #done if test -n "$xrpath"; then # If the user specified any rpath flags, then add them. temp_xrpath= for libdir in $xrpath; do func_replace_sysroot "$libdir" func_append temp_xrpath " -R$func_replace_sysroot_result" case "$finalize_rpath " in *" $libdir "*) ;; *) func_append finalize_rpath " $libdir" ;; esac done if test yes != "$hardcode_into_libs" || test yes = "$build_old_libs"; then dependency_libs="$temp_xrpath $dependency_libs" fi fi # Make sure dlfiles contains only unique files that won't be dlpreopened old_dlfiles=$dlfiles dlfiles= for lib in $old_dlfiles; do case " $dlprefiles $dlfiles " in *" $lib "*) ;; *) func_append dlfiles " $lib" ;; esac done # Make sure dlprefiles contains only unique files old_dlprefiles=$dlprefiles dlprefiles= for lib in $old_dlprefiles; do case "$dlprefiles " in *" $lib "*) ;; *) func_append dlprefiles " $lib" ;; esac done if test yes = "$build_libtool_libs"; then if test -n "$rpath"; then case $host in *-*-cygwin* | *-*-mingw* | *-*-pw32* | *-*-os2* | *-*-beos* | *-cegcc* | *-*-haiku*) # these systems don't actually have a c library (as such)! ;; *-*-rhapsody* | *-*-darwin1.[012]) # Rhapsody C library is in the System framework func_append deplibs " System.ltframework" ;; *-*-netbsd*) # Don't link with libc until the a.out ld.so is fixed. ;; *-*-openbsd* | *-*-freebsd* | *-*-dragonfly*) # Do not include libc due to us having libc/libc_r. ;; *-*-sco3.2v5* | *-*-sco5v6*) # Causes problems with __ctype ;; *-*-sysv4.2uw2* | *-*-sysv5* | *-*-unixware* | *-*-OpenUNIX*) # Compiler inserts libc in the correct place for threads to work ;; *) # Add libc to deplibs on all other systems if necessary. if test yes = "$build_libtool_need_lc"; then func_append deplibs " -lc" fi ;; esac fi # Transform deplibs into only deplibs that can be linked in shared. name_save=$name libname_save=$libname release_save=$release versuffix_save=$versuffix major_save=$major # I'm not sure if I'm treating the release correctly. I think # release should show up in the -l (ie -lgmp5) so we don't want to # add it in twice. Is that correct? release= versuffix= major= newdeplibs= droppeddeps=no case $deplibs_check_method in pass_all) # Don't check for shared/static. Everything works. # This might be a little naive. We might want to check # whether the library exists or not. But this is on # osf3 & osf4 and I'm not really sure... Just # implementing what was already the behavior. newdeplibs=$deplibs ;; test_compile) # This code stresses the "libraries are programs" paradigm to its # limits. Maybe even breaks it. We compile a program, linking it # against the deplibs as a proxy for the library. Then we can check # whether they linked in statically or dynamically with ldd. $opt_dry_run || $RM conftest.c cat > conftest.c </dev/null` $nocaseglob else potential_libs=`ls $i/$libnameglob[.-]* 2>/dev/null` fi for potent_lib in $potential_libs; do # Follow soft links. if ls -lLd "$potent_lib" 2>/dev/null | $GREP " -> " >/dev/null; then continue fi # The statement above tries to avoid entering an # endless loop below, in case of cyclic links. # We might still enter an endless loop, since a link # loop can be closed while we follow links, # but so what? potlib=$potent_lib while test -h "$potlib" 2>/dev/null; do potliblink=`ls -ld $potlib | $SED 's/.* -> //'` case $potliblink in [\\/]* | [A-Za-z]:[\\/]*) potlib=$potliblink;; *) potlib=`$ECHO "$potlib" | $SED 's|[^/]*$||'`"$potliblink";; esac done if eval $file_magic_cmd \"\$potlib\" 2>/dev/null | $SED -e 10q | $EGREP "$file_magic_regex" > /dev/null; then func_append newdeplibs " $a_deplib" a_deplib= break 2 fi done done fi if test -n "$a_deplib"; then droppeddeps=yes echo $ECHO "*** Warning: linker path does not have real file for library $a_deplib." echo "*** I have the capability to make that library automatically link in when" echo "*** you link to this library. But I can only do this if you have a" echo "*** shared version of the library, which you do not appear to have" echo "*** because I did check the linker path looking for a file starting" if test -z "$potlib"; then $ECHO "*** with $libname but no candidates were found. (...for file magic test)" else $ECHO "*** with $libname and none of the candidates passed a file format test" $ECHO "*** using a file magic. Last file checked: $potlib" fi fi ;; *) # Add a -L argument. func_append newdeplibs " $a_deplib" ;; esac done # Gone through all deplibs. ;; match_pattern*) set dummy $deplibs_check_method; shift match_pattern_regex=`expr "$deplibs_check_method" : "$1 \(.*\)"` for a_deplib in $deplibs; do case $a_deplib in -l*) func_stripname -l '' "$a_deplib" name=$func_stripname_result if test yes = "$allow_libtool_libs_with_static_runtimes"; then case " $predeps $postdeps " in *" $a_deplib "*) func_append newdeplibs " $a_deplib" a_deplib= ;; esac fi if test -n "$a_deplib"; then libname=`eval "\\$ECHO \"$libname_spec\""` for i in $lib_search_path $sys_lib_search_path $shlib_search_path; do potential_libs=`ls $i/$libname[.-]* 2>/dev/null` for potent_lib in $potential_libs; do potlib=$potent_lib # see symlink-check above in file_magic test if eval "\$ECHO \"$potent_lib\"" 2>/dev/null | $SED 10q | \ $EGREP "$match_pattern_regex" > /dev/null; then func_append newdeplibs " $a_deplib" a_deplib= break 2 fi done done fi if test -n "$a_deplib"; then droppeddeps=yes echo $ECHO "*** Warning: linker path does not have real file for library $a_deplib." echo "*** I have the capability to make that library automatically link in when" echo "*** you link to this library. But I can only do this if you have a" echo "*** shared version of the library, which you do not appear to have" echo "*** because I did check the linker path looking for a file starting" if test -z "$potlib"; then $ECHO "*** with $libname but no candidates were found. (...for regex pattern test)" else $ECHO "*** with $libname and none of the candidates passed a file format test" $ECHO "*** using a regex pattern. Last file checked: $potlib" fi fi ;; *) # Add a -L argument. func_append newdeplibs " $a_deplib" ;; esac done # Gone through all deplibs. ;; none | unknown | *) newdeplibs= tmp_deplibs=`$ECHO " $deplibs" | $SED 's/ -lc$//; s/ -[LR][^ ]*//g'` if test yes = "$allow_libtool_libs_with_static_runtimes"; then for i in $predeps $postdeps; do # can't use Xsed below, because $i might contain '/' tmp_deplibs=`$ECHO " $tmp_deplibs" | $SED "s|$i||"` done fi case $tmp_deplibs in *[!\ \ ]*) echo if test none = "$deplibs_check_method"; then echo "*** Warning: inter-library dependencies are not supported in this platform." else echo "*** Warning: inter-library dependencies are not known to be supported." fi echo "*** All declared inter-library dependencies are being dropped." droppeddeps=yes ;; esac ;; esac versuffix=$versuffix_save major=$major_save release=$release_save libname=$libname_save name=$name_save case $host in *-*-rhapsody* | *-*-darwin1.[012]) # On Rhapsody replace the C library with the System framework newdeplibs=`$ECHO " $newdeplibs" | $SED 's/ -lc / System.ltframework /'` ;; esac if test yes = "$droppeddeps"; then if test yes = "$module"; then echo echo "*** Warning: libtool could not satisfy all declared inter-library" $ECHO "*** dependencies of module $libname. Therefore, libtool will create" echo "*** a static module, that should work as long as the dlopening" echo "*** application is linked with the -dlopen flag." if test -z "$global_symbol_pipe"; then echo echo "*** However, this would only work if libtool was able to extract symbol" echo "*** lists from a program, using 'nm' or equivalent, but libtool could" echo "*** not find such a program. So, this module is probably useless." echo "*** 'nm' from GNU binutils and a full rebuild may help." fi if test no = "$build_old_libs"; then oldlibs=$output_objdir/$libname.$libext build_libtool_libs=module build_old_libs=yes else build_libtool_libs=no fi else echo "*** The inter-library dependencies that have been dropped here will be" echo "*** automatically added whenever a program is linked with this library" echo "*** or is declared to -dlopen it." if test no = "$allow_undefined"; then echo echo "*** Since this library must not contain undefined symbols," echo "*** because either the platform does not support them or" echo "*** it was explicitly requested with -no-undefined," echo "*** libtool will only create a static version of it." if test no = "$build_old_libs"; then oldlibs=$output_objdir/$libname.$libext build_libtool_libs=module build_old_libs=yes else build_libtool_libs=no fi fi fi fi # Done checking deplibs! deplibs=$newdeplibs fi # Time to change all our "foo.ltframework" stuff back to "-framework foo" case $host in *-*-darwin*) newdeplibs=`$ECHO " $newdeplibs" | $SED 's% \([^ $]*\).ltframework% -framework \1%g'` new_inherited_linker_flags=`$ECHO " $new_inherited_linker_flags" | $SED 's% \([^ $]*\).ltframework% -framework \1%g'` deplibs=`$ECHO " $deplibs" | $SED 's% \([^ $]*\).ltframework% -framework \1%g'` ;; esac # move library search paths that coincide with paths to not yet # installed libraries to the beginning of the library search list new_libs= for path in $notinst_path; do case " $new_libs " in *" -L$path/$objdir "*) ;; *) case " $deplibs " in *" -L$path/$objdir "*) func_append new_libs " -L$path/$objdir" ;; esac ;; esac done for deplib in $deplibs; do case $deplib in -L*) case " $new_libs " in *" $deplib "*) ;; *) func_append new_libs " $deplib" ;; esac ;; *) func_append new_libs " $deplib" ;; esac done deplibs=$new_libs # All the library-specific variables (install_libdir is set above). library_names= old_library= dlname= # Test again, we may have decided not to build it any more if test yes = "$build_libtool_libs"; then # Remove $wl instances when linking with ld. # FIXME: should test the right _cmds variable. case $archive_cmds in *\$LD\ *) wl= ;; esac if test yes = "$hardcode_into_libs"; then # Hardcode the library paths hardcode_libdirs= dep_rpath= rpath=$finalize_rpath test relink = "$opt_mode" || rpath=$compile_rpath$rpath for libdir in $rpath; do if test -n "$hardcode_libdir_flag_spec"; then if test -n "$hardcode_libdir_separator"; then func_replace_sysroot "$libdir" libdir=$func_replace_sysroot_result if test -z "$hardcode_libdirs"; then hardcode_libdirs=$libdir else # Just accumulate the unique libdirs. case $hardcode_libdir_separator$hardcode_libdirs$hardcode_libdir_separator in *"$hardcode_libdir_separator$libdir$hardcode_libdir_separator"*) ;; *) func_append hardcode_libdirs "$hardcode_libdir_separator$libdir" ;; esac fi else eval flag=\"$hardcode_libdir_flag_spec\" func_append dep_rpath " $flag" fi elif test -n "$runpath_var"; then case "$perm_rpath " in *" $libdir "*) ;; *) func_append perm_rpath " $libdir" ;; esac fi done # Substitute the hardcoded libdirs into the rpath. if test -n "$hardcode_libdir_separator" && test -n "$hardcode_libdirs"; then libdir=$hardcode_libdirs eval "dep_rpath=\"$hardcode_libdir_flag_spec\"" fi if test -n "$runpath_var" && test -n "$perm_rpath"; then # We should set the runpath_var. rpath= for dir in $perm_rpath; do func_append rpath "$dir:" done eval "$runpath_var='$rpath\$$runpath_var'; export $runpath_var" fi test -n "$dep_rpath" && deplibs="$dep_rpath $deplibs" fi shlibpath=$finalize_shlibpath test relink = "$opt_mode" || shlibpath=$compile_shlibpath$shlibpath if test -n "$shlibpath"; then eval "$shlibpath_var='$shlibpath\$$shlibpath_var'; export $shlibpath_var" fi # Get the real and link names of the library. eval shared_ext=\"$shrext_cmds\" eval library_names=\"$library_names_spec\" set dummy $library_names shift realname=$1 shift if test -n "$soname_spec"; then eval soname=\"$soname_spec\" else soname=$realname fi if test -z "$dlname"; then dlname=$soname fi lib=$output_objdir/$realname linknames= for link do func_append linknames " $link" done # Use standard objects if they are pic test -z "$pic_flag" && libobjs=`$ECHO "$libobjs" | $SP2NL | $SED "$lo2o" | $NL2SP` test "X$libobjs" = "X " && libobjs= delfiles= if test -n "$export_symbols" && test -n "$include_expsyms"; then $opt_dry_run || cp "$export_symbols" "$output_objdir/$libname.uexp" export_symbols=$output_objdir/$libname.uexp func_append delfiles " $export_symbols" fi orig_export_symbols= case $host_os in cygwin* | mingw* | cegcc*) if test -n "$export_symbols" && test -z "$export_symbols_regex"; then # exporting using user supplied symfile func_dll_def_p "$export_symbols" || { # and it's NOT already a .def file. Must figure out # which of the given symbols are data symbols and tag # them as such. So, trigger use of export_symbols_cmds. # export_symbols gets reassigned inside the "prepare # the list of exported symbols" if statement, so the # include_expsyms logic still works. orig_export_symbols=$export_symbols export_symbols= always_export_symbols=yes } fi ;; esac # Prepare the list of exported symbols if test -z "$export_symbols"; then if test yes = "$always_export_symbols" || test -n "$export_symbols_regex"; then func_verbose "generating symbol list for '$libname.la'" export_symbols=$output_objdir/$libname.exp $opt_dry_run || $RM $export_symbols cmds=$export_symbols_cmds save_ifs=$IFS; IFS='~' for cmd1 in $cmds; do IFS=$save_ifs # Take the normal branch if the nm_file_list_spec branch # doesn't work or if tool conversion is not needed. case $nm_file_list_spec~$to_tool_file_cmd in *~func_convert_file_noop | *~func_convert_file_msys_to_w32 | ~*) try_normal_branch=yes eval cmd=\"$cmd1\" func_len " $cmd" len=$func_len_result ;; *) try_normal_branch=no ;; esac if test yes = "$try_normal_branch" \ && { test "$len" -lt "$max_cmd_len" \ || test "$max_cmd_len" -le -1; } then func_show_eval "$cmd" 'exit $?' skipped_export=false elif test -n "$nm_file_list_spec"; then func_basename "$output" output_la=$func_basename_result save_libobjs=$libobjs save_output=$output output=$output_objdir/$output_la.nm func_to_tool_file "$output" libobjs=$nm_file_list_spec$func_to_tool_file_result func_append delfiles " $output" func_verbose "creating $NM input file list: $output" for obj in $save_libobjs; do func_to_tool_file "$obj" $ECHO "$func_to_tool_file_result" done > "$output" eval cmd=\"$cmd1\" func_show_eval "$cmd" 'exit $?' output=$save_output libobjs=$save_libobjs skipped_export=false else # The command line is too long to execute in one step. func_verbose "using reloadable object file for export list..." skipped_export=: # Break out early, otherwise skipped_export may be # set to false by a later but shorter cmd. break fi done IFS=$save_ifs if test -n "$export_symbols_regex" && test : != "$skipped_export"; then func_show_eval '$EGREP -e "$export_symbols_regex" "$export_symbols" > "${export_symbols}T"' func_show_eval '$MV "${export_symbols}T" "$export_symbols"' fi fi fi if test -n "$export_symbols" && test -n "$include_expsyms"; then tmp_export_symbols=$export_symbols test -n "$orig_export_symbols" && tmp_export_symbols=$orig_export_symbols $opt_dry_run || eval '$ECHO "$include_expsyms" | $SP2NL >> "$tmp_export_symbols"' fi if test : != "$skipped_export" && test -n "$orig_export_symbols"; then # The given exports_symbols file has to be filtered, so filter it. func_verbose "filter symbol list for '$libname.la' to tag DATA exports" # FIXME: $output_objdir/$libname.filter potentially contains lots of # 's' commands, which not all seds can handle. GNU sed should be fine # though. Also, the filter scales superlinearly with the number of # global variables. join(1) would be nice here, but unfortunately # isn't a blessed tool. $opt_dry_run || $SED -e '/[ ,]DATA/!d;s,\(.*\)\([ \,].*\),s|^\1$|\1\2|,' < $export_symbols > $output_objdir/$libname.filter func_append delfiles " $export_symbols $output_objdir/$libname.filter" export_symbols=$output_objdir/$libname.def $opt_dry_run || $SED -f $output_objdir/$libname.filter < $orig_export_symbols > $export_symbols fi tmp_deplibs= for test_deplib in $deplibs; do case " $convenience " in *" $test_deplib "*) ;; *) func_append tmp_deplibs " $test_deplib" ;; esac done deplibs=$tmp_deplibs if test -n "$convenience"; then if test -n "$whole_archive_flag_spec" && test yes = "$compiler_needs_object" && test -z "$libobjs"; then # extract the archives, so we have objects to list. # TODO: could optimize this to just extract one archive. whole_archive_flag_spec= fi if test -n "$whole_archive_flag_spec"; then save_libobjs=$libobjs eval libobjs=\"\$libobjs $whole_archive_flag_spec\" test "X$libobjs" = "X " && libobjs= else gentop=$output_objdir/${outputname}x func_append generated " $gentop" func_extract_archives $gentop $convenience func_append libobjs " $func_extract_archives_result" test "X$libobjs" = "X " && libobjs= fi fi if test yes = "$thread_safe" && test -n "$thread_safe_flag_spec"; then eval flag=\"$thread_safe_flag_spec\" func_append linker_flags " $flag" fi # Make a backup of the uninstalled library when relinking if test relink = "$opt_mode"; then $opt_dry_run || eval '(cd $output_objdir && $RM ${realname}U && $MV $realname ${realname}U)' || exit $? fi # Do each of the archive commands. if test yes = "$module" && test -n "$module_cmds"; then if test -n "$export_symbols" && test -n "$module_expsym_cmds"; then eval test_cmds=\"$module_expsym_cmds\" cmds=$module_expsym_cmds else eval test_cmds=\"$module_cmds\" cmds=$module_cmds fi else if test -n "$export_symbols" && test -n "$archive_expsym_cmds"; then eval test_cmds=\"$archive_expsym_cmds\" cmds=$archive_expsym_cmds else eval test_cmds=\"$archive_cmds\" cmds=$archive_cmds fi fi if test : != "$skipped_export" && func_len " $test_cmds" && len=$func_len_result && test "$len" -lt "$max_cmd_len" || test "$max_cmd_len" -le -1; then : else # The command line is too long to link in one step, link piecewise # or, if using GNU ld and skipped_export is not :, use a linker # script. # Save the value of $output and $libobjs because we want to # use them later. If we have whole_archive_flag_spec, we # want to use save_libobjs as it was before # whole_archive_flag_spec was expanded, because we can't # assume the linker understands whole_archive_flag_spec. # This may have to be revisited, in case too many # convenience libraries get linked in and end up exceeding # the spec. if test -z "$convenience" || test -z "$whole_archive_flag_spec"; then save_libobjs=$libobjs fi save_output=$output func_basename "$output" output_la=$func_basename_result # Clear the reloadable object creation command queue and # initialize k to one. test_cmds= concat_cmds= objlist= last_robj= k=1 if test -n "$save_libobjs" && test : != "$skipped_export" && test yes = "$with_gnu_ld"; then output=$output_objdir/$output_la.lnkscript func_verbose "creating GNU ld script: $output" echo 'INPUT (' > $output for obj in $save_libobjs do func_to_tool_file "$obj" $ECHO "$func_to_tool_file_result" >> $output done echo ')' >> $output func_append delfiles " $output" func_to_tool_file "$output" output=$func_to_tool_file_result elif test -n "$save_libobjs" && test : != "$skipped_export" && test -n "$file_list_spec"; then output=$output_objdir/$output_la.lnk func_verbose "creating linker input file list: $output" : > $output set x $save_libobjs shift firstobj= if test yes = "$compiler_needs_object"; then firstobj="$1 " shift fi for obj do func_to_tool_file "$obj" $ECHO "$func_to_tool_file_result" >> $output done func_append delfiles " $output" func_to_tool_file "$output" output=$firstobj\"$file_list_spec$func_to_tool_file_result\" else if test -n "$save_libobjs"; then func_verbose "creating reloadable object files..." output=$output_objdir/$output_la-$k.$objext eval test_cmds=\"$reload_cmds\" func_len " $test_cmds" len0=$func_len_result len=$len0 # Loop over the list of objects to be linked. for obj in $save_libobjs do func_len " $obj" func_arith $len + $func_len_result len=$func_arith_result if test -z "$objlist" || test "$len" -lt "$max_cmd_len"; then func_append objlist " $obj" else # The command $test_cmds is almost too long, add a # command to the queue. if test 1 -eq "$k"; then # The first file doesn't have a previous command to add. reload_objs=$objlist eval concat_cmds=\"$reload_cmds\" else # All subsequent reloadable object files will link in # the last one created. reload_objs="$objlist $last_robj" eval concat_cmds=\"\$concat_cmds~$reload_cmds~\$RM $last_robj\" fi last_robj=$output_objdir/$output_la-$k.$objext func_arith $k + 1 k=$func_arith_result output=$output_objdir/$output_la-$k.$objext objlist=" $obj" func_len " $last_robj" func_arith $len0 + $func_len_result len=$func_arith_result fi done # Handle the remaining objects by creating one last # reloadable object file. All subsequent reloadable object # files will link in the last one created. test -z "$concat_cmds" || concat_cmds=$concat_cmds~ reload_objs="$objlist $last_robj" eval concat_cmds=\"\$concat_cmds$reload_cmds\" if test -n "$last_robj"; then eval concat_cmds=\"\$concat_cmds~\$RM $last_robj\" fi func_append delfiles " $output" else output= fi ${skipped_export-false} && { func_verbose "generating symbol list for '$libname.la'" export_symbols=$output_objdir/$libname.exp $opt_dry_run || $RM $export_symbols libobjs=$output # Append the command to create the export file. test -z "$concat_cmds" || concat_cmds=$concat_cmds~ eval concat_cmds=\"\$concat_cmds$export_symbols_cmds\" if test -n "$last_robj"; then eval concat_cmds=\"\$concat_cmds~\$RM $last_robj\" fi } test -n "$save_libobjs" && func_verbose "creating a temporary reloadable object file: $output" # Loop through the commands generated above and execute them. save_ifs=$IFS; IFS='~' for cmd in $concat_cmds; do IFS=$save_ifs $opt_quiet || { func_quote_for_expand "$cmd" eval "func_echo $func_quote_for_expand_result" } $opt_dry_run || eval "$cmd" || { lt_exit=$? # Restore the uninstalled library and exit if test relink = "$opt_mode"; then ( cd "$output_objdir" && \ $RM "${realname}T" && \ $MV "${realname}U" "$realname" ) fi exit $lt_exit } done IFS=$save_ifs if test -n "$export_symbols_regex" && ${skipped_export-false}; then func_show_eval '$EGREP -e "$export_symbols_regex" "$export_symbols" > "${export_symbols}T"' func_show_eval '$MV "${export_symbols}T" "$export_symbols"' fi fi ${skipped_export-false} && { if test -n "$export_symbols" && test -n "$include_expsyms"; then tmp_export_symbols=$export_symbols test -n "$orig_export_symbols" && tmp_export_symbols=$orig_export_symbols $opt_dry_run || eval '$ECHO "$include_expsyms" | $SP2NL >> "$tmp_export_symbols"' fi if test -n "$orig_export_symbols"; then # The given exports_symbols file has to be filtered, so filter it. func_verbose "filter symbol list for '$libname.la' to tag DATA exports" # FIXME: $output_objdir/$libname.filter potentially contains lots of # 's' commands, which not all seds can handle. GNU sed should be fine # though. Also, the filter scales superlinearly with the number of # global variables. join(1) would be nice here, but unfortunately # isn't a blessed tool. $opt_dry_run || $SED -e '/[ ,]DATA/!d;s,\(.*\)\([ \,].*\),s|^\1$|\1\2|,' < $export_symbols > $output_objdir/$libname.filter func_append delfiles " $export_symbols $output_objdir/$libname.filter" export_symbols=$output_objdir/$libname.def $opt_dry_run || $SED -f $output_objdir/$libname.filter < $orig_export_symbols > $export_symbols fi } libobjs=$output # Restore the value of output. output=$save_output if test -n "$convenience" && test -n "$whole_archive_flag_spec"; then eval libobjs=\"\$libobjs $whole_archive_flag_spec\" test "X$libobjs" = "X " && libobjs= fi # Expand the library linking commands again to reset the # value of $libobjs for piecewise linking. # Do each of the archive commands. if test yes = "$module" && test -n "$module_cmds"; then if test -n "$export_symbols" && test -n "$module_expsym_cmds"; then cmds=$module_expsym_cmds else cmds=$module_cmds fi else if test -n "$export_symbols" && test -n "$archive_expsym_cmds"; then cmds=$archive_expsym_cmds else cmds=$archive_cmds fi fi fi if test -n "$delfiles"; then # Append the command to remove temporary files to $cmds. eval cmds=\"\$cmds~\$RM $delfiles\" fi # Add any objects from preloaded convenience libraries if test -n "$dlprefiles"; then gentop=$output_objdir/${outputname}x func_append generated " $gentop" func_extract_archives $gentop $dlprefiles func_append libobjs " $func_extract_archives_result" test "X$libobjs" = "X " && libobjs= fi save_ifs=$IFS; IFS='~' for cmd in $cmds; do IFS=$sp$nl eval cmd=\"$cmd\" IFS=$save_ifs $opt_quiet || { func_quote_for_expand "$cmd" eval "func_echo $func_quote_for_expand_result" } $opt_dry_run || eval "$cmd" || { lt_exit=$? # Restore the uninstalled library and exit if test relink = "$opt_mode"; then ( cd "$output_objdir" && \ $RM "${realname}T" && \ $MV "${realname}U" "$realname" ) fi exit $lt_exit } done IFS=$save_ifs # Restore the uninstalled library and exit if test relink = "$opt_mode"; then $opt_dry_run || eval '(cd $output_objdir && $RM ${realname}T && $MV $realname ${realname}T && $MV ${realname}U $realname)' || exit $? if test -n "$convenience"; then if test -z "$whole_archive_flag_spec"; then func_show_eval '${RM}r "$gentop"' fi fi exit $EXIT_SUCCESS fi # Create links to the real library. for linkname in $linknames; do if test "$realname" != "$linkname"; then func_show_eval '(cd "$output_objdir" && $RM "$linkname" && $LN_S "$realname" "$linkname")' 'exit $?' fi done # If -module or -export-dynamic was specified, set the dlname. if test yes = "$module" || test yes = "$export_dynamic"; then # On all known operating systems, these are identical. dlname=$soname fi fi ;; obj) if test -n "$dlfiles$dlprefiles" || test no != "$dlself"; then func_warning "'-dlopen' is ignored for objects" fi case " $deplibs" in *\ -l* | *\ -L*) func_warning "'-l' and '-L' are ignored for objects" ;; esac test -n "$rpath" && \ func_warning "'-rpath' is ignored for objects" test -n "$xrpath" && \ func_warning "'-R' is ignored for objects" test -n "$vinfo" && \ func_warning "'-version-info' is ignored for objects" test -n "$release" && \ func_warning "'-release' is ignored for objects" case $output in *.lo) test -n "$objs$old_deplibs" && \ func_fatal_error "cannot build library object '$output' from non-libtool objects" libobj=$output func_lo2o "$libobj" obj=$func_lo2o_result ;; *) libobj= obj=$output ;; esac # Delete the old objects. $opt_dry_run || $RM $obj $libobj # Objects from convenience libraries. This assumes # single-version convenience libraries. Whenever we create # different ones for PIC/non-PIC, this we'll have to duplicate # the extraction. reload_conv_objs= gentop= # if reload_cmds runs $LD directly, get rid of -Wl from # whole_archive_flag_spec and hope we can get by with turning comma # into space. case $reload_cmds in *\$LD[\ \$]*) wl= ;; esac if test -n "$convenience"; then if test -n "$whole_archive_flag_spec"; then eval tmp_whole_archive_flags=\"$whole_archive_flag_spec\" test -n "$wl" || tmp_whole_archive_flags=`$ECHO "$tmp_whole_archive_flags" | $SED 's|,| |g'` reload_conv_objs=$reload_objs\ $tmp_whole_archive_flags else gentop=$output_objdir/${obj}x func_append generated " $gentop" func_extract_archives $gentop $convenience reload_conv_objs="$reload_objs $func_extract_archives_result" fi fi # If we're not building shared, we need to use non_pic_objs test yes = "$build_libtool_libs" || libobjs=$non_pic_objects # Create the old-style object. reload_objs=$objs$old_deplibs' '`$ECHO "$libobjs" | $SP2NL | $SED "/\.$libext$/d; /\.lib$/d; $lo2o" | $NL2SP`' '$reload_conv_objs output=$obj func_execute_cmds "$reload_cmds" 'exit $?' # Exit if we aren't doing a library object file. if test -z "$libobj"; then if test -n "$gentop"; then func_show_eval '${RM}r "$gentop"' fi exit $EXIT_SUCCESS fi test yes = "$build_libtool_libs" || { if test -n "$gentop"; then func_show_eval '${RM}r "$gentop"' fi # Create an invalid libtool object if no PIC, so that we don't # accidentally link it into a program. # $show "echo timestamp > $libobj" # $opt_dry_run || eval "echo timestamp > $libobj" || exit $? exit $EXIT_SUCCESS } if test -n "$pic_flag" || test default != "$pic_mode"; then # Only do commands if we really have different PIC objects. reload_objs="$libobjs $reload_conv_objs" output=$libobj func_execute_cmds "$reload_cmds" 'exit $?' fi if test -n "$gentop"; then func_show_eval '${RM}r "$gentop"' fi exit $EXIT_SUCCESS ;; prog) case $host in *cygwin*) func_stripname '' '.exe' "$output" output=$func_stripname_result.exe;; esac test -n "$vinfo" && \ func_warning "'-version-info' is ignored for programs" test -n "$release" && \ func_warning "'-release' is ignored for programs" $preload \ && test unknown,unknown,unknown = "$dlopen_support,$dlopen_self,$dlopen_self_static" \ && func_warning "'LT_INIT([dlopen])' not used. Assuming no dlopen support." case $host in *-*-rhapsody* | *-*-darwin1.[012]) # On Rhapsody replace the C library is the System framework compile_deplibs=`$ECHO " $compile_deplibs" | $SED 's/ -lc / System.ltframework /'` finalize_deplibs=`$ECHO " $finalize_deplibs" | $SED 's/ -lc / System.ltframework /'` ;; esac case $host in *-*-darwin*) # Don't allow lazy linking, it breaks C++ global constructors # But is supposedly fixed on 10.4 or later (yay!). if test CXX = "$tagname"; then case ${MACOSX_DEPLOYMENT_TARGET-10.0} in 10.[0123]) func_append compile_command " $wl-bind_at_load" func_append finalize_command " $wl-bind_at_load" ;; esac fi # Time to change all our "foo.ltframework" stuff back to "-framework foo" compile_deplibs=`$ECHO " $compile_deplibs" | $SED 's% \([^ $]*\).ltframework% -framework \1%g'` finalize_deplibs=`$ECHO " $finalize_deplibs" | $SED 's% \([^ $]*\).ltframework% -framework \1%g'` ;; esac # move library search paths that coincide with paths to not yet # installed libraries to the beginning of the library search list new_libs= for path in $notinst_path; do case " $new_libs " in *" -L$path/$objdir "*) ;; *) case " $compile_deplibs " in *" -L$path/$objdir "*) func_append new_libs " -L$path/$objdir" ;; esac ;; esac done for deplib in $compile_deplibs; do case $deplib in -L*) case " $new_libs " in *" $deplib "*) ;; *) func_append new_libs " $deplib" ;; esac ;; *) func_append new_libs " $deplib" ;; esac done compile_deplibs=$new_libs func_append compile_command " $compile_deplibs" func_append finalize_command " $finalize_deplibs" if test -n "$rpath$xrpath"; then # If the user specified any rpath flags, then add them. for libdir in $rpath $xrpath; do # This is the magic to use -rpath. case "$finalize_rpath " in *" $libdir "*) ;; *) func_append finalize_rpath " $libdir" ;; esac done fi # Now hardcode the library paths rpath= hardcode_libdirs= for libdir in $compile_rpath $finalize_rpath; do if test -n "$hardcode_libdir_flag_spec"; then if test -n "$hardcode_libdir_separator"; then if test -z "$hardcode_libdirs"; then hardcode_libdirs=$libdir else # Just accumulate the unique libdirs. case $hardcode_libdir_separator$hardcode_libdirs$hardcode_libdir_separator in *"$hardcode_libdir_separator$libdir$hardcode_libdir_separator"*) ;; *) func_append hardcode_libdirs "$hardcode_libdir_separator$libdir" ;; esac fi else eval flag=\"$hardcode_libdir_flag_spec\" func_append rpath " $flag" fi elif test -n "$runpath_var"; then case "$perm_rpath " in *" $libdir "*) ;; *) func_append perm_rpath " $libdir" ;; esac fi case $host in *-*-cygwin* | *-*-mingw* | *-*-pw32* | *-*-os2* | *-cegcc*) testbindir=`$ECHO "$libdir" | $SED -e 's*/lib$*/bin*'` case :$dllsearchpath: in *":$libdir:"*) ;; ::) dllsearchpath=$libdir;; *) func_append dllsearchpath ":$libdir";; esac case :$dllsearchpath: in *":$testbindir:"*) ;; ::) dllsearchpath=$testbindir;; *) func_append dllsearchpath ":$testbindir";; esac ;; esac done # Substitute the hardcoded libdirs into the rpath. if test -n "$hardcode_libdir_separator" && test -n "$hardcode_libdirs"; then libdir=$hardcode_libdirs eval rpath=\" $hardcode_libdir_flag_spec\" fi compile_rpath=$rpath rpath= hardcode_libdirs= for libdir in $finalize_rpath; do if test -n "$hardcode_libdir_flag_spec"; then if test -n "$hardcode_libdir_separator"; then if test -z "$hardcode_libdirs"; then hardcode_libdirs=$libdir else # Just accumulate the unique libdirs. case $hardcode_libdir_separator$hardcode_libdirs$hardcode_libdir_separator in *"$hardcode_libdir_separator$libdir$hardcode_libdir_separator"*) ;; *) func_append hardcode_libdirs "$hardcode_libdir_separator$libdir" ;; esac fi else eval flag=\"$hardcode_libdir_flag_spec\" func_append rpath " $flag" fi elif test -n "$runpath_var"; then case "$finalize_perm_rpath " in *" $libdir "*) ;; *) func_append finalize_perm_rpath " $libdir" ;; esac fi done # Substitute the hardcoded libdirs into the rpath. if test -n "$hardcode_libdir_separator" && test -n "$hardcode_libdirs"; then libdir=$hardcode_libdirs eval rpath=\" $hardcode_libdir_flag_spec\" fi finalize_rpath=$rpath if test -n "$libobjs" && test yes = "$build_old_libs"; then # Transform all the library objects into standard objects. compile_command=`$ECHO "$compile_command" | $SP2NL | $SED "$lo2o" | $NL2SP` finalize_command=`$ECHO "$finalize_command" | $SP2NL | $SED "$lo2o" | $NL2SP` fi func_generate_dlsyms "$outputname" "@PROGRAM@" false # template prelinking step if test -n "$prelink_cmds"; then func_execute_cmds "$prelink_cmds" 'exit $?' fi wrappers_required=: case $host in *cegcc* | *mingw32ce*) # Disable wrappers for cegcc and mingw32ce hosts, we are cross compiling anyway. wrappers_required=false ;; *cygwin* | *mingw* ) test yes = "$build_libtool_libs" || wrappers_required=false ;; *) if test no = "$need_relink" || test yes != "$build_libtool_libs"; then wrappers_required=false fi ;; esac $wrappers_required || { # Replace the output file specification. compile_command=`$ECHO "$compile_command" | $SED 's%@OUTPUT@%'"$output"'%g'` link_command=$compile_command$compile_rpath # We have no uninstalled library dependencies, so finalize right now. exit_status=0 func_show_eval "$link_command" 'exit_status=$?' if test -n "$postlink_cmds"; then func_to_tool_file "$output" postlink_cmds=`func_echo_all "$postlink_cmds" | $SED -e 's%@OUTPUT@%'"$output"'%g' -e 's%@TOOL_OUTPUT@%'"$func_to_tool_file_result"'%g'` func_execute_cmds "$postlink_cmds" 'exit $?' fi # Delete the generated files. if test -f "$output_objdir/${outputname}S.$objext"; then func_show_eval '$RM "$output_objdir/${outputname}S.$objext"' fi exit $exit_status } if test -n "$compile_shlibpath$finalize_shlibpath"; then compile_command="$shlibpath_var=\"$compile_shlibpath$finalize_shlibpath\$$shlibpath_var\" $compile_command" fi if test -n "$finalize_shlibpath"; then finalize_command="$shlibpath_var=\"$finalize_shlibpath\$$shlibpath_var\" $finalize_command" fi compile_var= finalize_var= if test -n "$runpath_var"; then if test -n "$perm_rpath"; then # We should set the runpath_var. rpath= for dir in $perm_rpath; do func_append rpath "$dir:" done compile_var="$runpath_var=\"$rpath\$$runpath_var\" " fi if test -n "$finalize_perm_rpath"; then # We should set the runpath_var. rpath= for dir in $finalize_perm_rpath; do func_append rpath "$dir:" done finalize_var="$runpath_var=\"$rpath\$$runpath_var\" " fi fi if test yes = "$no_install"; then # We don't need to create a wrapper script. link_command=$compile_var$compile_command$compile_rpath # Replace the output file specification. link_command=`$ECHO "$link_command" | $SED 's%@OUTPUT@%'"$output"'%g'` # Delete the old output file. $opt_dry_run || $RM $output # Link the executable and exit func_show_eval "$link_command" 'exit $?' if test -n "$postlink_cmds"; then func_to_tool_file "$output" postlink_cmds=`func_echo_all "$postlink_cmds" | $SED -e 's%@OUTPUT@%'"$output"'%g' -e 's%@TOOL_OUTPUT@%'"$func_to_tool_file_result"'%g'` func_execute_cmds "$postlink_cmds" 'exit $?' fi exit $EXIT_SUCCESS fi case $hardcode_action,$fast_install in relink,*) # Fast installation is not supported link_command=$compile_var$compile_command$compile_rpath relink_command=$finalize_var$finalize_command$finalize_rpath func_warning "this platform does not like uninstalled shared libraries" func_warning "'$output' will be relinked during installation" ;; *,yes) link_command=$finalize_var$compile_command$finalize_rpath relink_command=`$ECHO "$compile_var$compile_command$compile_rpath" | $SED 's%@OUTPUT@%\$progdir/\$file%g'` ;; *,no) link_command=$compile_var$compile_command$compile_rpath relink_command=$finalize_var$finalize_command$finalize_rpath ;; *,needless) link_command=$finalize_var$compile_command$finalize_rpath relink_command= ;; esac # Replace the output file specification. link_command=`$ECHO "$link_command" | $SED 's%@OUTPUT@%'"$output_objdir/$outputname"'%g'` # Delete the old output files. $opt_dry_run || $RM $output $output_objdir/$outputname $output_objdir/lt-$outputname func_show_eval "$link_command" 'exit $?' if test -n "$postlink_cmds"; then func_to_tool_file "$output_objdir/$outputname" postlink_cmds=`func_echo_all "$postlink_cmds" | $SED -e 's%@OUTPUT@%'"$output_objdir/$outputname"'%g' -e 's%@TOOL_OUTPUT@%'"$func_to_tool_file_result"'%g'` func_execute_cmds "$postlink_cmds" 'exit $?' fi # Now create the wrapper script. func_verbose "creating $output" # Quote the relink command for shipping. if test -n "$relink_command"; then # Preserve any variables that may affect compiler behavior for var in $variables_saved_for_relink; do if eval test -z \"\${$var+set}\"; then relink_command="{ test -z \"\${$var+set}\" || $lt_unset $var || { $var=; export $var; }; }; $relink_command" elif eval var_value=\$$var; test -z "$var_value"; then relink_command="$var=; export $var; $relink_command" else func_quote_for_eval "$var_value" relink_command="$var=$func_quote_for_eval_result; export $var; $relink_command" fi done relink_command="(cd `pwd`; $relink_command)" relink_command=`$ECHO "$relink_command" | $SED "$sed_quote_subst"` fi # Only actually do things if not in dry run mode. $opt_dry_run || { # win32 will think the script is a binary if it has # a .exe suffix, so we strip it off here. case $output in *.exe) func_stripname '' '.exe' "$output" output=$func_stripname_result ;; esac # test for cygwin because mv fails w/o .exe extensions case $host in *cygwin*) exeext=.exe func_stripname '' '.exe' "$outputname" outputname=$func_stripname_result ;; *) exeext= ;; esac case $host in *cygwin* | *mingw* ) func_dirname_and_basename "$output" "" "." output_name=$func_basename_result output_path=$func_dirname_result cwrappersource=$output_path/$objdir/lt-$output_name.c cwrapper=$output_path/$output_name.exe $RM $cwrappersource $cwrapper trap "$RM $cwrappersource $cwrapper; exit $EXIT_FAILURE" 1 2 15 func_emit_cwrapperexe_src > $cwrappersource # The wrapper executable is built using the $host compiler, # because it contains $host paths and files. If cross- # compiling, it, like the target executable, must be # executed on the $host or under an emulation environment. $opt_dry_run || { $LTCC $LTCFLAGS -o $cwrapper $cwrappersource $STRIP $cwrapper } # Now, create the wrapper script for func_source use: func_ltwrapper_scriptname $cwrapper $RM $func_ltwrapper_scriptname_result trap "$RM $func_ltwrapper_scriptname_result; exit $EXIT_FAILURE" 1 2 15 $opt_dry_run || { # note: this script will not be executed, so do not chmod. if test "x$build" = "x$host"; then $cwrapper --lt-dump-script > $func_ltwrapper_scriptname_result else func_emit_wrapper no > $func_ltwrapper_scriptname_result fi } ;; * ) $RM $output trap "$RM $output; exit $EXIT_FAILURE" 1 2 15 func_emit_wrapper no > $output chmod +x $output ;; esac } exit $EXIT_SUCCESS ;; esac # See if we need to build an old-fashioned archive. for oldlib in $oldlibs; do case $build_libtool_libs in convenience) oldobjs="$libobjs_save $symfileobj" addlibs=$convenience build_libtool_libs=no ;; module) oldobjs=$libobjs_save addlibs=$old_convenience build_libtool_libs=no ;; *) oldobjs="$old_deplibs $non_pic_objects" $preload && test -f "$symfileobj" \ && func_append oldobjs " $symfileobj" addlibs=$old_convenience ;; esac if test -n "$addlibs"; then gentop=$output_objdir/${outputname}x func_append generated " $gentop" func_extract_archives $gentop $addlibs func_append oldobjs " $func_extract_archives_result" fi # Do each command in the archive commands. if test -n "$old_archive_from_new_cmds" && test yes = "$build_libtool_libs"; then cmds=$old_archive_from_new_cmds else # Add any objects from preloaded convenience libraries if test -n "$dlprefiles"; then gentop=$output_objdir/${outputname}x func_append generated " $gentop" func_extract_archives $gentop $dlprefiles func_append oldobjs " $func_extract_archives_result" fi # POSIX demands no paths to be encoded in archives. We have # to avoid creating archives with duplicate basenames if we # might have to extract them afterwards, e.g., when creating a # static archive out of a convenience library, or when linking # the entirety of a libtool archive into another (currently # not supported by libtool). if (for obj in $oldobjs do func_basename "$obj" $ECHO "$func_basename_result" done | sort | sort -uc >/dev/null 2>&1); then : else echo "copying selected object files to avoid basename conflicts..." gentop=$output_objdir/${outputname}x func_append generated " $gentop" func_mkdir_p "$gentop" save_oldobjs=$oldobjs oldobjs= counter=1 for obj in $save_oldobjs do func_basename "$obj" objbase=$func_basename_result case " $oldobjs " in " ") oldobjs=$obj ;; *[\ /]"$objbase "*) while :; do # Make sure we don't pick an alternate name that also # overlaps. newobj=lt$counter-$objbase func_arith $counter + 1 counter=$func_arith_result case " $oldobjs " in *[\ /]"$newobj "*) ;; *) if test ! -f "$gentop/$newobj"; then break; fi ;; esac done func_show_eval "ln $obj $gentop/$newobj || cp $obj $gentop/$newobj" func_append oldobjs " $gentop/$newobj" ;; *) func_append oldobjs " $obj" ;; esac done fi func_to_tool_file "$oldlib" func_convert_file_msys_to_w32 tool_oldlib=$func_to_tool_file_result eval cmds=\"$old_archive_cmds\" func_len " $cmds" len=$func_len_result if test "$len" -lt "$max_cmd_len" || test "$max_cmd_len" -le -1; then cmds=$old_archive_cmds elif test -n "$archiver_list_spec"; then func_verbose "using command file archive linking..." for obj in $oldobjs do func_to_tool_file "$obj" $ECHO "$func_to_tool_file_result" done > $output_objdir/$libname.libcmd func_to_tool_file "$output_objdir/$libname.libcmd" oldobjs=" $archiver_list_spec$func_to_tool_file_result" cmds=$old_archive_cmds else # the command line is too long to link in one step, link in parts func_verbose "using piecewise archive linking..." save_RANLIB=$RANLIB RANLIB=: objlist= concat_cmds= save_oldobjs=$oldobjs oldobjs= # Is there a better way of finding the last object in the list? for obj in $save_oldobjs do last_oldobj=$obj done eval test_cmds=\"$old_archive_cmds\" func_len " $test_cmds" len0=$func_len_result len=$len0 for obj in $save_oldobjs do func_len " $obj" func_arith $len + $func_len_result len=$func_arith_result func_append objlist " $obj" if test "$len" -lt "$max_cmd_len"; then : else # the above command should be used before it gets too long oldobjs=$objlist if test "$obj" = "$last_oldobj"; then RANLIB=$save_RANLIB fi test -z "$concat_cmds" || concat_cmds=$concat_cmds~ eval concat_cmds=\"\$concat_cmds$old_archive_cmds\" objlist= len=$len0 fi done RANLIB=$save_RANLIB oldobjs=$objlist if test -z "$oldobjs"; then eval cmds=\"\$concat_cmds\" else eval cmds=\"\$concat_cmds~\$old_archive_cmds\" fi fi fi func_execute_cmds "$cmds" 'exit $?' done test -n "$generated" && \ func_show_eval "${RM}r$generated" # Now create the libtool archive. case $output in *.la) old_library= test yes = "$build_old_libs" && old_library=$libname.$libext func_verbose "creating $output" # Preserve any variables that may affect compiler behavior for var in $variables_saved_for_relink; do if eval test -z \"\${$var+set}\"; then relink_command="{ test -z \"\${$var+set}\" || $lt_unset $var || { $var=; export $var; }; }; $relink_command" elif eval var_value=\$$var; test -z "$var_value"; then relink_command="$var=; export $var; $relink_command" else func_quote_for_eval "$var_value" relink_command="$var=$func_quote_for_eval_result; export $var; $relink_command" fi done # Quote the link command for shipping. relink_command="(cd `pwd`; $SHELL \"$progpath\" $preserve_args --mode=relink $libtool_args @inst_prefix_dir@)" relink_command=`$ECHO "$relink_command" | $SED "$sed_quote_subst"` if test yes = "$hardcode_automatic"; then relink_command= fi # Only create the output if not a dry run. $opt_dry_run || { for installed in no yes; do if test yes = "$installed"; then if test -z "$install_libdir"; then break fi output=$output_objdir/${outputname}i # Replace all uninstalled libtool libraries with the installed ones newdependency_libs= for deplib in $dependency_libs; do case $deplib in *.la) func_basename "$deplib" name=$func_basename_result func_resolve_sysroot "$deplib" eval libdir=`$SED -n -e 's/^libdir=\(.*\)$/\1/p' $func_resolve_sysroot_result` test -z "$libdir" && \ func_fatal_error "'$deplib' is not a valid libtool archive" func_append newdependency_libs " ${lt_sysroot:+=}$libdir/$name" ;; -L*) func_stripname -L '' "$deplib" func_replace_sysroot "$func_stripname_result" func_append newdependency_libs " -L$func_replace_sysroot_result" ;; -R*) func_stripname -R '' "$deplib" func_replace_sysroot "$func_stripname_result" func_append newdependency_libs " -R$func_replace_sysroot_result" ;; *) func_append newdependency_libs " $deplib" ;; esac done dependency_libs=$newdependency_libs newdlfiles= for lib in $dlfiles; do case $lib in *.la) func_basename "$lib" name=$func_basename_result eval libdir=`$SED -n -e 's/^libdir=\(.*\)$/\1/p' $lib` test -z "$libdir" && \ func_fatal_error "'$lib' is not a valid libtool archive" func_append newdlfiles " ${lt_sysroot:+=}$libdir/$name" ;; *) func_append newdlfiles " $lib" ;; esac done dlfiles=$newdlfiles newdlprefiles= for lib in $dlprefiles; do case $lib in *.la) # Only pass preopened files to the pseudo-archive (for # eventual linking with the app. that links it) if we # didn't already link the preopened objects directly into # the library: func_basename "$lib" name=$func_basename_result eval libdir=`$SED -n -e 's/^libdir=\(.*\)$/\1/p' $lib` test -z "$libdir" && \ func_fatal_error "'$lib' is not a valid libtool archive" func_append newdlprefiles " ${lt_sysroot:+=}$libdir/$name" ;; esac done dlprefiles=$newdlprefiles else newdlfiles= for lib in $dlfiles; do case $lib in [\\/]* | [A-Za-z]:[\\/]*) abs=$lib ;; *) abs=`pwd`"/$lib" ;; esac func_append newdlfiles " $abs" done dlfiles=$newdlfiles newdlprefiles= for lib in $dlprefiles; do case $lib in [\\/]* | [A-Za-z]:[\\/]*) abs=$lib ;; *) abs=`pwd`"/$lib" ;; esac func_append newdlprefiles " $abs" done dlprefiles=$newdlprefiles fi $RM $output # place dlname in correct position for cygwin # In fact, it would be nice if we could use this code for all target # systems that can't hard-code library paths into their executables # and that have no shared library path variable independent of PATH, # but it turns out we can't easily determine that from inspecting # libtool variables, so we have to hard-code the OSs to which it # applies here; at the moment, that means platforms that use the PE # object format with DLL files. See the long comment at the top of # tests/bindir.at for full details. tdlname=$dlname case $host,$output,$installed,$module,$dlname in *cygwin*,*lai,yes,no,*.dll | *mingw*,*lai,yes,no,*.dll | *cegcc*,*lai,yes,no,*.dll) # If a -bindir argument was supplied, place the dll there. if test -n "$bindir"; then func_relative_path "$install_libdir" "$bindir" tdlname=$func_relative_path_result/$dlname else # Otherwise fall back on heuristic. tdlname=../bin/$dlname fi ;; esac $ECHO > $output "\ # $outputname - a libtool library file # Generated by $PROGRAM (GNU $PACKAGE) $VERSION # # Please DO NOT delete this file! # It is necessary for linking the library. # The name that we can dlopen(3). dlname='$tdlname' # Names of this library. library_names='$library_names' # The name of the static archive. old_library='$old_library' # Linker flags that cannot go in dependency_libs. inherited_linker_flags='$new_inherited_linker_flags' # Libraries that this one depends upon. dependency_libs='$dependency_libs' # Names of additional weak libraries provided by this library weak_library_names='$weak_libs' # Version information for $libname. current=$current age=$age revision=$revision # Is this an already installed library? installed=$installed # Should we warn about portability when linking against -modules? shouldnotlink=$module # Files to dlopen/dlpreopen dlopen='$dlfiles' dlpreopen='$dlprefiles' # Directory that this library needs to be installed in: libdir='$install_libdir'" if test no,yes = "$installed,$need_relink"; then $ECHO >> $output "\ relink_command=\"$relink_command\"" fi done } # Do a symbolic link so that the libtool archive can be found in # LD_LIBRARY_PATH before the program is installed. func_show_eval '( cd "$output_objdir" && $RM "$outputname" && $LN_S "../$outputname" "$outputname" )' 'exit $?' ;; esac exit $EXIT_SUCCESS } if test link = "$opt_mode" || test relink = "$opt_mode"; then func_mode_link ${1+"$@"} fi # func_mode_uninstall arg... func_mode_uninstall () { $debug_cmd RM=$nonopt files= rmforce=false exit_status=0 # This variable tells wrapper scripts just to set variables rather # than running their programs. libtool_install_magic=$magic for arg do case $arg in -f) func_append RM " $arg"; rmforce=: ;; -*) func_append RM " $arg" ;; *) func_append files " $arg" ;; esac done test -z "$RM" && \ func_fatal_help "you must specify an RM program" rmdirs= for file in $files; do func_dirname "$file" "" "." dir=$func_dirname_result if test . = "$dir"; then odir=$objdir else odir=$dir/$objdir fi func_basename "$file" name=$func_basename_result test uninstall = "$opt_mode" && odir=$dir # Remember odir for removal later, being careful to avoid duplicates if test clean = "$opt_mode"; then case " $rmdirs " in *" $odir "*) ;; *) func_append rmdirs " $odir" ;; esac fi # Don't error if the file doesn't exist and rm -f was used. if { test -L "$file"; } >/dev/null 2>&1 || { test -h "$file"; } >/dev/null 2>&1 || test -f "$file"; then : elif test -d "$file"; then exit_status=1 continue elif $rmforce; then continue fi rmfiles=$file case $name in *.la) # Possibly a libtool archive, so verify it. if func_lalib_p "$file"; then func_source $dir/$name # Delete the libtool libraries and symlinks. for n in $library_names; do func_append rmfiles " $odir/$n" done test -n "$old_library" && func_append rmfiles " $odir/$old_library" case $opt_mode in clean) case " $library_names " in *" $dlname "*) ;; *) test -n "$dlname" && func_append rmfiles " $odir/$dlname" ;; esac test -n "$libdir" && func_append rmfiles " $odir/$name $odir/${name}i" ;; uninstall) if test -n "$library_names"; then # Do each command in the postuninstall commands. func_execute_cmds "$postuninstall_cmds" '$rmforce || exit_status=1' fi if test -n "$old_library"; then # Do each command in the old_postuninstall commands. func_execute_cmds "$old_postuninstall_cmds" '$rmforce || exit_status=1' fi # FIXME: should reinstall the best remaining shared library. ;; esac fi ;; *.lo) # Possibly a libtool object, so verify it. if func_lalib_p "$file"; then # Read the .lo file func_source $dir/$name # Add PIC object to the list of files to remove. if test -n "$pic_object" && test none != "$pic_object"; then func_append rmfiles " $dir/$pic_object" fi # Add non-PIC object to the list of files to remove. if test -n "$non_pic_object" && test none != "$non_pic_object"; then func_append rmfiles " $dir/$non_pic_object" fi fi ;; *) if test clean = "$opt_mode"; then noexename=$name case $file in *.exe) func_stripname '' '.exe' "$file" file=$func_stripname_result func_stripname '' '.exe' "$name" noexename=$func_stripname_result # $file with .exe has already been added to rmfiles, # add $file without .exe func_append rmfiles " $file" ;; esac # Do a test to see if this is a libtool program. if func_ltwrapper_p "$file"; then if func_ltwrapper_executable_p "$file"; then func_ltwrapper_scriptname "$file" relink_command= func_source $func_ltwrapper_scriptname_result func_append rmfiles " $func_ltwrapper_scriptname_result" else relink_command= func_source $dir/$noexename fi # note $name still contains .exe if it was in $file originally # as does the version of $file that was added into $rmfiles func_append rmfiles " $odir/$name $odir/${name}S.$objext" if test yes = "$fast_install" && test -n "$relink_command"; then func_append rmfiles " $odir/lt-$name" fi if test "X$noexename" != "X$name"; then func_append rmfiles " $odir/lt-$noexename.c" fi fi fi ;; esac func_show_eval "$RM $rmfiles" 'exit_status=1' done # Try to remove the $objdir's in the directories where we deleted files for dir in $rmdirs; do if test -d "$dir"; then func_show_eval "rmdir $dir >/dev/null 2>&1" fi done exit $exit_status } if test uninstall = "$opt_mode" || test clean = "$opt_mode"; then func_mode_uninstall ${1+"$@"} fi test -z "$opt_mode" && { help=$generic_help func_fatal_help "you must specify a MODE" } test -z "$exec_cmd" && \ func_fatal_help "invalid operation mode '$opt_mode'" if test -n "$exec_cmd"; then eval exec "$exec_cmd" exit $EXIT_FAILURE fi exit $exit_status # The TAGs below are defined such that we never get into a situation # where we disable both kinds of libraries. Given conflicting # choices, we go for a static library, that is the most portable, # since we can't tell whether shared libraries were disabled because # the user asked for that or because the platform doesn't support # them. This is particularly important on AIX, because we don't # support having both static and shared libraries enabled at the same # time on that platform, so we default to a shared-only configuration. # If a disable-shared tag is given, we'll fallback to a static-only # configuration. But we'll never go from static-only to shared-only. # ### BEGIN LIBTOOL TAG CONFIG: disable-shared build_libtool_libs=no build_old_libs=yes # ### END LIBTOOL TAG CONFIG: disable-shared # ### BEGIN LIBTOOL TAG CONFIG: disable-static build_old_libs=`case $build_libtool_libs in yes) echo no;; *) echo yes;; esac` # ### END LIBTOOL TAG CONFIG: disable-static # Local Variables: # mode:shell-script # sh-indentation:2 # End: cyrus-imapd-2.5.10/doc/0000755000175000017500000000000013001246645011603 500000000000000cyrus-imapd-2.5.10/doc/questions.html0000644000175000017500000000074113001236020014427 00000000000000 Outstanding Questions in Cyrus Documentation

Questions we really should answer. If you feel like doing us a favor, sit down and answer one.

  • What are the performance implications of single-instance store (as of 1.6.22)?
cyrus-imapd-2.5.10/doc/man/0000755000175000017500000000000013001246654012356 500000000000000cyrus-imapd-2.5.10/doc/man/arbitron.8.html0000644000175000017500000001113013001246654015146 00000000000000 ARBITRON

ARBITRON

NAME
SYNOPSIS
DESCRIPTION
OPTIONS
FILES

NAME

arbitron - arbitron mailboxes

SYNOPSIS

arbitron [ -C config-file ] [ -o ] [ -u ] [ -l ] [ -p months ]
[ -d days | -D mmddyyyy[:mmddyyyy] ] mailbox...

DESCRIPTION

Arbitron collects and reports readership statistics for mailboxes on the server. It also optionally prunes the mailboxes of \Seen state for dormant users.

Arbitron produces one line of output per mailbox, reporting the mailbox name followed by a space, followed by the number of readers (and if -u is specified, followed by a colon and a comma-separated list of the readers userids), and if -o is not specified, another space and the number of subscribers (and if -u is specified, followed by a colon and a comma-separated list of the subscribers userids). IMPORTANT: This format is subject to change in future versions.

Each "reader" is a distinct authentication identity which has "s" rights to the mailbox and which has SELECTed the mailbox within either the past days days or the specified date range. Users are not counted as reading their own personal mailboxes. Personal mailboxes are not reported unless there is at least one reader other than the mailboxes owner.

Arbitron reads its configuration options out of the imapd.conf(5) file unless specified otherwise by -C.

OPTIONS

-C config-file

Read configuration options from config-file.

-o

"old way" -- do not report subscribers.

-u

Report userids in addition to the count(s).

-l

Enable long reporting (comma delimited table consisting of mbox, userid, r/s, start time, end time).

-d days

Count as a reader an authentication identity which has SELECTed the mailbox within days days. Default is 30.

-D mmddyyyy[:mmddyyyy]

Count as a reader an authentication identity which has SELECTed the mailbox within the given date range. The start date and optional end date are specified as 2-digit month of the year, 2-digit day of the month, and 4-digit year. If the end date is not specified, then the current system time is used as the end time.

-p months

Prune \Seen state for users who have not SELECTed the mailbox within months months. Default is infinity.

FILES

/etc/imapd.conf


cyrus-imapd-2.5.10/doc/man/fud.8.html0000644000175000017500000001000413001246656014105 00000000000000 FUD

FUD

NAME
SYNOPSIS
DESCRIPTION
OPTIONS
FILES
BUGS

NAME

FUD - provide information about user mailboxes

SYNOPSIS

fud [ -C config-file ] [ -U uses ] [ -T timeout ] [ -D ]

DESCRIPTION

FUD is a long lived datagram daemon started from master that provides information about when a user last read their mail, when mail last arrived in a user’s mailbox, and how many messages are recent for that user.

Note that for FUD to run properly you must set proto=udp in its cyrus.conf services entry. prefork=1 is also recommended. FUD will automatically proxy any and all FUD requests to the appropriate backend server if it is runing on a Cyrus Murder frontend machine.

FUD reads its configuration options out of the imapd.conf(5) file unless specified otherwise by -C.

OPTIONS

-C config-file

Read configuration options from config-file.

-U uses

The maximum number of times that the process should be used for new connections before shutting down. The default is 250.

-T timeout

The number of seconds that the process will wait for a new connection before shutting down. Note that a value of 0 (zero) will disable the timeout. The default is 60.

-D

Run external debugger specified in debug_command.

FILES

/etc/imapd.conf

Default configuration file.

/etc/cyrus.conf

Cyrus Master process configuration file.

BUGS

Though not really a bug, FUD will silently ignore any requests that it does not consider valid.

Also not really a bug, FUD requires that the anonymous user has the 0 (zero) right on the mailbox in question. This is only a "bug" because 0 is not a standard IMAP ACL bit.

FUD is an experimental interface meant to provide information to build a finger-like service around. Eventually it should be superceded by a more standards-based protocol.


cyrus-imapd-2.5.10/doc/man/cyr_df.8.html0000644000175000017500000000423413001246655014604 00000000000000 CYR_DF

CYR_DF

NAME
SYNOPSIS
DESCRIPTION
OPTIONS
FILES

NAME

cyr_df - report Cyrus spool partition disk space usage

SYNOPSIS

cyr_df [ -C config-file ] [ -m ]

DESCRIPTION

Cyr_df examines the Cyrus spool partitions and reports on their disk space usage. Cyr_df reads its configuration options out of the imapd.conf(5) file unless specified otherwise by -C.

OPTIONS

-C config-file

Read configuration options from config-file.

-m

Report on metadata partitions rather than message file partitions.

FILES

/etc/imapd.conf


cyrus-imapd-2.5.10/doc/man/httpd.8.html0000644000175000017500000000774013001246656014467 00000000000000 HTTPD

HTTPD

NAME
SYNOPSIS
DESCRIPTION
OPTIONS
FILES
SEE ALSO

*

NAME

httpd - HTTP server process

SYNOPSIS

httpd [ -C config-file ] [ -U uses ] [ -T timeout ] [ -D ]
[ -s ] [ -p ssf ]

DESCRIPTION

Httpd is a HTTP server. It accepts commands on its standard input and responds on its standard output. It MUST invoked by master(8) with those descriptors attached to a remote client connection.

Httpd reads its configuration options out of the imapd.conf(5) file unless specified otherwise by -C.

If the directory log/user exists under the directory specified in the configdirectory configuration option, then httpd will create protocol telemetry logs for sessions authenticating as user. The telemetry logs will be stored in the log/user directory with a filename of the httpd process-id.

OPTIONS

-C config-file

Read configuration options from config-file.

-U uses

The maximum number of times that the process should be used for new connections before shutting down. The default is 250.

-T timeout

The number of seconds that the process will wait for a new connection before shutting down. Note that a value of 0 (zero) will disable the timeout. The default is 60.

-D

Run external debugger specified in debug_command.

-s

Serve HTTP over SSL (https). All data to and from httpd is encrypted using the Secure Sockets Layer.

-p ssf

Tell httpd that an external layer exists. An SSF (security strength factor) of 1 means an integrity protection layer exists. Any higher SSF implies some form of privacy protection.

FILES

/etc/imapd.conf

SEE ALSO

imapd.conf(5), master(8)


cyrus-imapd-2.5.10/doc/man/sieveshell.1.html0000644000175000017500000000716513001246662015476 00000000000000 SIEVESHELL

SIEVESHELL

NAME
SYNOPSIS
DESCRIPTION
OPTIONS
REFERENCES
AUTHOR

NAME

sieveshell - remotely manipulate sieve scripts

SYNOPSIS

sieveshell [--user=user] [--authname=authname] [--realm=realm] [--exec=script] server[:port]

sieveshell --help

DESCRIPTION

sieveshell allows users to manipulate their scripts on a remote server. It works via MANAGESIEVE, a work in progress.

The following commands are recognized:

list list scripts on server.

put <filename> upload script to server.

get <name> [<filename>] get script. if no filename display to stdout

delete <name> delete script.

activate <name> activate script.

deactivate deactivate all scripts.

OPTIONS

-u user, --user=user

The authorization name to request; by default, derived from the authentication credentials.

-a authname, --authname=authname

The user to use for authentication (defaults to current user).

-r realm, --realm=realm

The realm to attempt authentication in.

-e script, --exec=script

Instead of working interactively, run commands from script, and exit when done.

REFERENCES

[ MANAGESIEVE ] Martin, T.; "A Protocol for Remotely Managing Sieve Scripts", draft-ietf-managesieve-03.txt, Mirapoint, Inc.; May 2001, work in progress.

AUTHOR

Tim Martin <tmartin@mirapoint.com>, and the rest of the Cyrus team <cyrus-bugs@andrew.cmu.edu>.


cyrus-imapd-2.5.10/doc/man/smtptest.1.html0000644000175000017500000001433513001246662015213 00000000000000 SMTPTEST

SMTPTEST

NAME
SYNOPSIS
DESCRIPTION
OPTIONS
SEE ALSO

NAME

smtptest - interactive SMTP test program

SYNOPSIS

smtptest [ -t keyfile ] [ -p port ] [ -m mechanism ]
[ -a userid ] [ -u userid ] [ -k num ] [ -l num ]
[ -r realm ] [ -f file ] [ -n num ] [ -s ] [ -c ]
[ -i ] [ -o option=value ] [ -v ] hostname

DESCRIPTION

smtptest is a utility that allows you to authenticate to a SMTP server and interactively issue commands to it. Once authenticated you may issue any SMTP command by simply typing it in. It is capable of multiple SASL authentication mechanisms and handles encryption layers transparently. This utility is often used for testing the operation of a smtp server. Also those developing SMTP clients find it useful.

OPTIONS

-t keyfile

Enable TLS. keyfile contains the TLS public and private keys. Specify "" to negotiate a TLS encryption layer but not use TLS authentication.

-p port

Port to connect to. If left off this defaults to smtp as defined in /etc/services.

-m mechanism

Force smtptest to use mechanism for authentication. If not specified the strongest authentication mechanism supported by the server is chosen.

-a userid

Userid to use for authentication; defaults to the current user. This is the userid whose password or credentials will be presented to the server for verification.

-u userid

Userid to use for authorization; defaults to the current user. This is the userid whose identity will be assumed after authentication. NOTE: This is only used with SASL mechanisms that allow proxying (e.g. PLAIN, DIGEST-MD5).

-k num

Minimum protection layer required.

-l num

Maximum protection layer to use (0=none; 1=integrity; etc). For example if you are using the KERBEROS_V4 authentication mechanism specifying 0 will force smtptest to not use any layer and specifying 1 will force it to use the integrity layer. By default the maximum supported protection layer will be used.

-r realm

Specify the realm to use. Certain authentication mechanisms (e.g. DIGEST-MD5) may require one to specify the realm.

-f file

Pipe file into connection after authentication.

-n num

Number of authentication attempts; default = 1. The client will attempt to do SSL/TLS session reuse and/or fast reauth (e.g. DIGEST-MD5), if possible.

-s

Enable SMTP over SSL (smtps).

-c

Enable challenge prompt callbacks. This will cause the OTP mechanism to ask for the the one-time password instead of the secret pass-phrase (library generates the correct response).

-i

Don’t send an initial client response for SASL mechanisms, even if the protocol supports it.

-o option=value

Set the SASL option to value.

-v

Verbose. Print out more information than usual.

SEE ALSO

sendmail(8)


cyrus-imapd-2.5.10/doc/man/nntpd.8.html0000644000175000017500000001207413001246661014457 00000000000000 NNTPD

NNTPD

NAME
SYNOPSIS
DESCRIPTION
OPTIONS
FILES
SEE ALSO

NAME

nntpd - NNTP server process

SYNOPSIS

nntpd [ -C config-file ] [ -U uses ] [ -T timeout ] [ -D ]
[ -s ] [ -r ] [ -f ] [ -p ssf ]

DESCRIPTION

Nntpd is a NNTP server. It accepts commands on its standard input and responds on its standard output. It MUST invoked by master(8) with those descriptors attached to a remote client connection.

Nntpd reads its configuration options out of the imapd.conf(5) file unless specified otherwise by -C. The optional newsprefix option specifies a prefix to be prepended to newsgroup names to make the corresponding IMAP mailbox names. The optional newspostuser option specifies the special userid to be used when contructing the To: header address for following up to articles when read via IMAP. The optional newspeer option specifies the fully qualified hostname of the upstream news server to which articles are fed. The optional allownewnews option enables the NNTP NEWNEWS command. NOTE: For servers with a large volume of articles, the NEWNEWS command can be expensive.

If the directory log/user exists under the directory specified in the configdirectory configuration option, then nntpd will create protocol telemetry logs for sessions authenticating as user. The telemetry logs will be stored in the log/user directory with a filename of the nntpd process-id.

OPTIONS

-C config-file

Read configuration options from config-file.

-U uses

The maximum number of times that the process should be used for new connections before shutting down. The default is 250.

-T timeout

The number of seconds that the process will wait for a new connection before shutting down. Note that a value of 0 (zero) will disable the timeout. The default is 60.

-D

Run external debugger specified in debug_command.

-s

Serve NNTP over SSL (nntps). All data to and from nntpd is encrypted using the Secure Sockets Layer.

-r

Only allow NNTP reader commands. Permitted clients will only be allowed to read/post articles.

-f

Only allow NNTP feeder commands. Permitted clients will only be allowed to feed articles (no reading).

-p ssf

Tell nntpd that an external layer exists. An SSF (security strength factor) of 1 means an integrity protection layer exists. Any higher SSF implies some form of privacy protection.

FILES

/etc/imapd.conf

SEE ALSO

imapd.conf(5), master(8)


cyrus-imapd-2.5.10/doc/man/sync_server.8.html0000644000175000017500000000531413001246662015676 00000000000000 SYNC_SERVER

SYNC_SERVER

NAME
SYNOPSIS
DESCRIPTION
OPTIONS
FILES
SEE ALSO
AUTHORS

NAME

sync_server - server side of the synchronization (replication) engine

SYNOPSIS

sync_server [ -C config-file ] [ -p ssf ]

DESCRIPTION

sync_server is the server side of the the replication system. It runs on the target (replica) system and listens for connections from sync_client which provides instructions for synchronizing the replica system with the master system.

OPTIONS

-C config-file

Read configuration options from config-file.

-p ssf

Tell sync_server that an external layer exists. An SSF (security strength factor) of 1 means an integrity protection layer exists. Any higher SSF implies some form of privacy protection.

FILES

/etc/imapd.conf

SEE ALSO

sync_client(8)

AUTHORS

David Carter (dpc22@cam.ac.uk), Ken Murchison (ken@oceana.com)


cyrus-imapd-2.5.10/doc/man/master.8.html0000644000175000017500000001523113001246660014624 00000000000000 MASTER

MASTER

NAME
SYNOPSIS
DESCRIPTION
OPTIONS
CONFIGURATION
NOTES
FILES
SEE ALSO

NAME

master - master Cyrus process

SYNOPSIS

master [ -C alternate imapd.conf ] [ -M alternate cyrus.conf ] [ -l listen queue ] [ -p pidfile ] [ -P snmp agentx ping interval ] [ -j janitor period ] [ -d ] [ -D ] [ -x snmp agentx socket ]

DESCRIPTION

Master is the process that controls all of the Cyrus processes. This process is responsible for creating all imapd, pop3d, lmtpd and sieved child processes. This process also initializes the Berkeley DB code and performs scheduled cleanup/maintenance.

If this process dies, then no new sessions will be started.

It kills itself and all child processes when it receives a SIGTERM.

OPTIONS

-C alternate imapd.conf

Specifies an alternate imapd.conf for use by master (note that this will not affect any sub-processes spawned by master, you should specify those specifically in the respective entries in cyrus.conf).

-M alternate cyrus.conf

Specifies an alternate cyrus.conf for use by master.

-l listen queue backlog

Increase the listen queue backlog. By default, the listen queue is set to 32. On systems with a high connection rate, it may be desirable to increase this value. refer to listen(2) for details.

-j janitor full-sweeps per second

Sets the amount of times per second the janitor should sweep the entire child table. Leave it at the default of 1 unless you have a really high fork rate (and you have not increased the child hash table size when you compiled Cyrus from its default of 10000 entries).

-p pidfile

Use pidfile as the pidfile. If not specified, defaults to /var/run/cyrus-master.pid

-P snmp agentx ping interval

Sets the amount on time in seconds the subagent will try and reconnect to the master agent (snmpd) if it ever becomes (or starts) disconnected. Requires net-snmp 5.0 or higher.

-d

Start in daemon mode (run in background and disconnect from controlling terminal).

-D

Don’t close stdin/stdout/stderr. Primarily useful for debugging. Note that -d and -D cannot be used together; consider using -L instead.

-L logfile

Redirect stdout and stderr to the given logfile.

-x snmp agentx socket

Address the master agent (most likely snmpd) listens on. Requires net-snmp 5.0 or higher.

CONFIGURATION

Upon execution, master reads its configuration information out of the cyrus.conf(5) file.

Master rereads its configuration file when it receives a hangup signal, SIGHUP. Services and events may be added, deleted or modified when the configuration file is reread. Any active services removed from the configuration file will be allowed to run until completion. Services added or modified to listen on a privileged port may not be able to bind the port, depending on your system configuration. In this case a full restart is needed.

Master propagates the hangup signal, SIGHUP, to its child service processes, so that they stop waiting for incoming connections and exit, allowing them to be recycled. This is useful to make services take into account a new version of the imapd.conf(5) file. Children that are servicing a client connection when SIGHUP is received are allowed to run until the client logouts before being recycled. It may take a long time until the client logouts, so a log message is generated for processes that have not been recycled within 30s.

NOTES

The environment variable CYRUS_VERBOSE can be set to log additional debugging information. Setting the value to 1 results in base level logging. Setting it higher results in more log messages being generated.

FILES

/etc/cyrus.conf, /etc/imapd.conf, /var/run/cyrus-master.pid

SEE ALSO

cyrus.conf(5), imapd.conf(5), imapd(8), pop3d(8), lmtpd(8), timsieved(8), idled(8)


cyrus-imapd-2.5.10/doc/man/rmnews.8.html0000644000175000017500000000505513001246661014650 00000000000000 RMNEWS

RMNEWS

NAME
SYNOPSIS
DESCRIPTION
FILES

NAME

rmnews - expunge and remove news articles

SYNOPSIS

rmnews

DESCRIPTION

Rmnews reads article data from the standard input. It then expunges and removes the listed articles. Rmnews is designed to be used by InterNetNews to remove canceled, superseded, and expired news articles.

The input is processed as an INN expirerm file listing or an INN cancel stream written as a ’’WC’’ entry in the newsfeeds(5) file. This data consists of lines of text, each containing a list of relative article pathnames, with a single space between entries. If a listed file is contained in an IMAP news mailbox, it is expunged out of that mailbox. In any case, each listed file is unlinked.

Rmnews reads its configuration options out of the imapd.conf(5) file. The optional newsprefix option specifies a prefix to be prepended to newsgroup names to make the corresponding IMAP mailbox names. The required partition-news option specifies the pathname prefix to the IMAP news mailboxes. The value of partition-news concatenated with the dots-to-slashes-converted value of newsprefix must be the pathname of the news spool directory.

FILES

/etc/imapd.conf


cyrus-imapd-2.5.10/doc/man/sivtest.1.html0000644000175000017500000001406513001246662015031 00000000000000 SIVTEST

SIVTEST

NAME
SYNOPSIS
DESCRIPTION
OPTIONS
SEE ALSO

NAME

sivtest - interactive MANAGESIEVE test program

SYNOPSIS

sivtest [ -t keyfile ] [ -p port ] [ -m mechanism ]
[ -a userid ] [ -u userid ] [ -k num ] [ -l num ]
[ -r realm ] [ -f file ] [ -n num ] [ -c ]
[ -i ] [ -o option=value ] [ -v ] hostname

DESCRIPTION

sivtest is a utility that allows you to authenticate to a MANAGESIEVE server and interactively issue commands to it. Once authenticated you may issue any MANAGESIEVE command by simply typing it in. It is capable of multiple SASL authentication mechanisms and handles encryption layers transparently. This utility is often used for testing the operation of a timsieved server. Also those developing MANAGESIEVE clients find it useful.

OPTIONS

-t keyfile

Enable TLS. keyfile contains the TLS public and private keys. Specify "" to negotiate a TLS encryption layer but not use TLS authentication.

-p port

Port to connect to. If left off this defaults to sieve as defined in /etc/services.

-m mechanism

Force sivtest to use mechanism for authentication. If not specified the strongest authentication mechanism supported by the server is chosen.

-a userid

Userid to use for authentication; defaults to the current user. This is the userid whose password or credentials will be presented to the server for verification.

-u userid

Userid to use for authorization; defaults to the current user. This is the userid whose identity will be assumed after authentication. NOTE: This is only used with SASL mechanisms that allow proxying (e.g. PLAIN, DIGEST-MD5).

-k num

Minimum protection layer required.

-l num

Maximum protection layer to use (0=none; 1=integrity; etc). For example if you are using the KERBEROS_V4 authentication mechanism specifying 0 will force sivtest to not use any layer and specifying 1 will force it to use the integrity layer. By default the maximum supported protection layer will be used.

-r realm

Specify the realm to use. Certain authentication mechanisms (e.g. DIGEST-MD5) may require one to specify the realm.

-f file

Pipe file into connection after authentication.

-n num

Number of authentication attempts; default = 1. The client will attempt to do SSL/TLS session reuse and/or fast reauth (e.g. DIGEST-MD5), if possible.

-c

Enable challenge prompt callbacks. This will cause the OTP mechanism to ask for the the one-time password instead of the secret pass-phrase (library generates the correct response).

-i

Don’t send an initial client response for SASL mechanisms, even if the protocol supports it.

-o option=value

Set the SASL option to value.

-v

Verbose. Print out more information than usual.

SEE ALSO

timsieved(8)


cyrus-imapd-2.5.10/doc/man/quota.8.html0000644000175000017500000000645313001246661014471 00000000000000 QUOTA

QUOTA

NAME
SYNOPSIS
DESCRIPTION
OPTIONS
FILES

NAME

quota - report and optionally fix quota usage

SYNOPSIS

quota [ -C config-file ] [ -d domain ] [ -f ] [ mailbox-prefix... ]

DESCRIPTION

Quota generates a report listing quota roots, giving their limits and usage. If the -f option is given, quota first fixes any inconsistencies in the quota subsystem, such as mailboxes with the wrong quota root or quota roots with the wrong quota usage reported. If an optional domain is given, the quota listing (and inconsistency fixing) is performed in that domain rather than the default domain. If any optional mailbox-prefix arguments are given, the quota listing (and inconsistency fixing) is limited to quota roots with names that start with one of the given prefixes.

Running quota with both the -f option and mailbox-prefix arguments is not recommended.

Quota reads its configuration options out of the imapd.conf(5) file unless specified otherwise by -C.

OPTIONS

-C config-file

Read configuration options from config-file.

-d domain

List/fix quotas in domain.

-f

Fix any inconsistencies in the quota subsystem before generating a report.

-q

Quiet. If -f is specified, then don’t print the quota vaules, only print messages when things are changed.

FILES

/etc/imapd.conf


cyrus-imapd-2.5.10/doc/man/lmtptest.1.html0000644000175000017500000001403013001246660015172 00000000000000 LMTPTEST

LMTPTEST

NAME
SYNOPSIS
DESCRIPTION
OPTIONS
SEE ALSO

NAME

lmtptest - interactive LMTP test program

SYNOPSIS

lmtptest [ -t keyfile ] [ -p port ] [ -m mechanism ]
[ -a userid ] [ -u userid ] [ -k num ] [ -l num ]
[ -r realm ] [ -f file ] [ -n num ] [ -c ]
[ -i ] [ -o option=value ] [ -v ] hostname

DESCRIPTION

lmtptest is a utility that allows you to authenticate to a LMTP server and interactively issue commands to it. Once authenticated you may issue any LMTP command by simply typing it in. It is capable of multiple SASL authentication mechanisms and handles encryption layers transparently. This utility is often used for testing the operation of a lmtp server. Also those developing LMTP clients find it useful.

OPTIONS

-t keyfile

Enable TLS. keyfile contains the TLS public and private keys. Specify "" to negotiate a TLS encryption layer but not use TLS authentication.

-p port

Port to connect to. If left off this defaults to lmtp as defined in /etc/services.

-m mechanism

Force lmtptest to use mechanism for authentication. If not specified the strongest authentication mechanism supported by the server is chosen.

-a userid

Userid to use for authentication; defaults to the current user. This is the userid whose password or credentials will be presented to the server for verification.

-u userid

Userid to use for authorization; defaults to the current user. This is the userid whose identity will be assumed after authentication. NOTE: This is only used with SASL mechanisms that allow proxying (e.g. PLAIN, DIGEST-MD5).

-k num

Minimum protection layer required.

-l num

Maximum protection layer to use (0=none; 1=integrity; etc). For example if you are using the KERBEROS_V4 authentication mechanism specifying 0 will force lmtptest to not use any layer and specifying 1 will force it to use the integrity layer. By default the maximum supported protection layer will be used.

-r realm

Specify the realm to use. Certain authentication mechanisms (e.g. DIGEST-MD5) may require one to specify the realm.

-f file

Pipe file into connection after authentication.

-n num

Number of authentication attempts; default = 1. The client will attempt to do SSL/TLS session reuse and/or fast reauth (e.g. DIGEST-MD5), if possible.

-c

Enable challenge prompt callbacks. This will cause the OTP mechanism to ask for the the one-time password instead of the secret pass-phrase (library generates the correct response).

-i

Don’t send an initial client response for SASL mechanisms, even if the protocol supports it.

-o option=value

Set the SASL option to value.

-v

Verbose. Print out more information than usual.

SEE ALSO

lmtpd(8)


cyrus-imapd-2.5.10/doc/man/fetchnews.8.html0000644000175000017500000000750613001246656015332 00000000000000 FETCHNEWS

FETCHNEWS

NAME
SYNOPSIS
DESCRIPTION
OPTIONS
FILES

NAME

fetchnews - retrieve new articles from peer and feed to Cyrus

SYNOPSIS

fetchnews [ -C config-file ] [ -s servername[:port] ]
[ -n ] [ -y ] [ -w wildmat ] [ -f tstampfile ]
[ -a authname [ -p password ] ] peername

DESCRIPTION

Fetchnews retrieves news articles from a peer news server and feeds them to a Cyrus server. Fetchnews connects to the peer specified by peername, requests new articles since the time stored in tstampfile and feeds them to servername.

Fetchnews reads its configuration options out of the imapd.conf(5) file unless specified otherwise by -C.

OPTIONS

-C config-file

Read configuration options from config-file.

-s servername

Hostname of the Cyrus server (with optional port) to which articles should be fed. Defaults to "localhost:nntp".

-n

Don’t use the NEWNEWS command. Fetchnews will keep track of the high and low water marks for each group and use them to fetch new articles.

-y

Use 4 instead of 2 digits for year. 2-digits are rfc977- but not y2k-compliant.

-w wildmat

Wildmat pattern specifying which newsgroups to search for new articles. Defaults to "*".

-f tstampfile

File in which to read/write the timestamp of when articles were last retrieved. Defaults to "newsstamp" located in configdir as specified by the configuration options.

-a authname

Userid to use for authentication.

-p password

Password to use for authentication.

FILES

/etc/imapd.conf


cyrus-imapd-2.5.10/doc/man/imapd.8.html0000644000175000017500000001216513001246656014433 00000000000000 IMAPD

IMAPD

NAME
SYNOPSIS
DESCRIPTION
OPTIONS
FILES
SEE ALSO

NAME

imapd - IMAP server process

SYNOPSIS

imapd [ -C config-file ] [ -U uses ] [ -T timeout ] [ -D ]
[ -s ] [ -N ] [ -p ssf ]

DESCRIPTION

Imapd is an IMAP4rev1 server. It accepts commands on its standard input and responds on its standard output. It MUST be invoked by master(8) with those descriptors attached to a remote client connection.

Imapd reads its configuration options out of the imapd.conf(5) file unless specified otherwise by -C.

If the file msg/shutdown is created under the directory specified in the configdirectory configuration option, then imapd will shut down the connection, sending the first line contained in the file to the client as the reason. New connections are denied.

If the file msg/motd is created under the directory specified in the configdirectory configuration option, then imapd will send the first line contained in the file to clients upon connect as an ALERT message which IMAP-compliant clients are required to display. This option serves to annoy users mostly. Unfortunately clients tend to connect far more frequently than is apparent, causing each connection to generate a seperate server ALERT for each connection. Many clients do not display these properly, if they do anything with them at all.

If the directory log/user exists under the directory specified in the configdirectory configuration option, then imapd will create protocol telemetry logs for sessions authenticating as user. The telemetry logs will be stored in the log/user directory with a filename of the imapd process-id.

OPTIONS

-C config-file

Read configuration options from config-file.

-U uses

The maximum number of times that the process should be used for new connections before shutting down. The default is 250.

-T timeout

The number of seconds that the process will wait for a new connection before shutting down. Note that a value of 0 (zero) will disable the timeout. The default is 60.

-D

Run external debugger specified in debug_command.

-s

Serve IMAP over SSL (imaps). All data to and from imapd is encrypted using the Secure Sockets Layer.

-N

Bypass password checking. (Not recommended unless you know what you’re doing.)

-p ssf

Tell imapd that an external layer exists. An SSF (security strength factor) of 1 means an integrity protection layer exists. Any higher SSF implies some form of privacy protection.

FILES

/etc/imapd.conf

SEE ALSO

imapd.conf(5), master(8)


cyrus-imapd-2.5.10/doc/man/installsieve.1.html0000644000175000017500000000702013001246657016027 00000000000000 INSTALLSIEVE

INSTALLSIEVE

NAME
SYNOPSIS
DESCRIPTION
OPTIONS

NAME

installsieve - user utility for managing sieve scripts

SYNOPSIS

installsieve

DESCRIPTION

installsieve is a utility that allows users to manage their sieve scripts kept on the server.

OPTIONS

-v name

View script with the given name. The script if retrieved sucessfully is output to standard output.

-l

List all of the scripts currently on the server. If one of the scripts is active a arrow is printed indicating that it is the active script.

-p port

Port to connect to. If left off this defaults to "sieve" as defined in /etc/services.

-i file

Install a file onto the server. If a script with the same name already exists on the server it is overwritten. Upon sucessfully putting the script on the server the script is set active. If file has the extension .script it is chopped when put on the server since sieve names may not contain a ’.’.

-a name

Set name as the active script. The list of available names can be obtained from the -l option.

-d name

Delete the sieve script on the server with name.

-m mechanism

Force installsieve to use mechanism for authentication. If not specified the strongest authentication mechanism is chosen.

-g name

Get the sieve script with name and save it to disk with a ".script" extension. If a file with that name already exists it is overwritten.

-u user

Userid/Authname to use for authentication; by default, the current user.


cyrus-imapd-2.5.10/doc/man/krb.equiv.5.html0000644000175000017500000000344413001246660015237 00000000000000 KRB.EQUIV

KRB.EQUIV

NAME
DESCRIPTION
SAMPLE FILE

NAME

/etc/krb.equiv - Kerberos equivalences

DESCRIPTION

krb.equiv contains zero or more lines, each of which describes a mapping of a kerberos principal (userid@host) to a local user (userid or alias). Each line of the file consists of two fields, separated by at least one whitespace character; other blanks are ignored. The first field is the kerberos principal name to remap, and the second is the name of the corresponding local user.

SAMPLE FILE

tyq4@ANDY.CMU.EDU tyq4
tyq4@DEANNA.ORG tyq4
ty347@ECE.CMU.EDU tyq4
jj12@ANDY.CMU.EDU tick
tick@DEANNA.ORG tick
jy9o@ANDY.CMU.EDU jyager
jyager@CS.CMU.EDU jyager


cyrus-imapd-2.5.10/doc/man/chk_cyrus.8.html0000644000175000017500000000521513001246654015327 00000000000000 CHK_CYRUS

CHK_CYRUS

NAME
SYNOPSIS
DESCRIPTION
OPTIONS
FILES
SEE ALSO

NAME

chk_cyrus - perform a consistency check of the cyrus mailstore

SYNOPSIS

chk_cyrus [ -C config-file ] [ -P partition ] [ -M mailbox ]

DESCRIPTION

Chk_cyrus is used to perform a consistency check on the cyrus datastore, and output a list of files/directories that are expected to exist, but do not. Status messagess are output to stderr, the list of files/directories is output to stdout. This list can be passed to a backup program to aid a partial restoral, for instance.

Chk_cyrus reads its configuration options out of the imapd.conf(5) file unless specified otherwise by -C.

OPTIONS

-C config-file

Read configuration options from config-file.

-P partition

Run the consistency check for only the given partition. May not be specified with -M. -M mailbox Run the consistency check for only the given mailbox. May not be specified with -P.

FILES

/etc/imapd.conf

SEE ALSO

imapd.conf(5), master(8)


cyrus-imapd-2.5.10/doc/man/ipurge.8.html0000644000175000017500000001200513001246657014626 00000000000000 IPURGE

IPURGE

NAME
SYNOPSIS
DESCRIPTION
OPTIONS
FILES

NAME

ipurge - delete mail from IMAP mailbox or partition based on age or size

SYNOPSIS

ipurge [ -f ] [ -C config-file ] [ -x ] [ -X ] [ -i ] [ -s ] [ -o ] [ -n ]
[ -d days | -b bytes | -k Kbytes | -m Mbytes ]
[ mailbox-pattern... ]

DESCRIPTION

Ipurge deletes messages from the mailbox(es) specified by mailbox-pattern that are older or larger than specified by the -d, -b, -k or -m options. If no mailbox-pattern is given, ipurge works on all mailboxes. If the -x option is given, the message age and size MUST match exactly those specified by -d, -b, -k or -m. The are no default values, and at least one of -d, -b, -k or -m MUST be specified.

Ipurge by default only deletes mail below shared folders, which means that mails in mailbox(es) below INBOX.* and user.* stay untouched. Use the option -f to also delete mail in mailbox(es) below these folders.

Ipurge reads its configuration options out of the imapd.conf(5) file unless specified otherwise by -C.

OPTIONS

-f

Force deletion of mail in all mailboxes.

-C config-file

Read configuration options from config-file.

-d days

Age of message in days.

-b bytes

Size of message in bytes.

-k Kbytes

Size of message in Kbytes (2^10 bytes).

-m Mbytes

Size of message in Mbytes (2^20 bytes).

-x

Perform an exact match on age or size (instead of older or larger).

-X

Use delivery time instead of Date: header for date matches

-i

Invert match logic: -x means not equal, date is for newer, size is for smaller

-s

Skip over messages that have the \Flagged flag set.

-o

Only purge messages that have the \Deleted flag set.

-n

Only print messages that would be deleted (dry run).

FILES

/etc/imapd.conf


cyrus-imapd-2.5.10/doc/man/cyr_synclog.8.html0000644000175000017500000000660513001246655015675 00000000000000 CYR_SYNCLOG

CYR_SYNCLOG

NAME
SYNOPSIS
DESCRIPTION
EXAMPLES
OPTIONS
FILES
SEE ALSO

NAME

cyr_synclog - add entries to the replication log

SYNOPSIS

cyr_synclog [ -C config-file ] [ -type ] <value>

DESCRIPTION

cyr_synclog is used to append a value to the log file. You can either specify the log type and value, or an entire log line.

-u USER

-U UNUSER

-v SIEVE

-m MAILBOX

-M UNMAILBOX

-a APPEND

-c ACL

-q QUOTA

-n ANNOTATION

-s SEEN

-b SUBSCRIPTION

Running without any options will print a short usage document.

cyr_synclog reads any applicable configuration options out of the imapd.conf(5) file unless specified otherwise by -C.

EXAMPLES

Here are some example ways to use cyr_synclog:

cyr_synclog -m user.brong

cyr_synclog -u brong

cyr_synclog -C /etc/imapd-special.conf -s user.brong brong

cyr_synclog "SEEN user.brong brong"

OPTIONS

-C config-file

Read configuration options from config-file.

FILES

/etc/imapd.conf

SEE ALSO

imapd.conf(5)


cyrus-imapd-2.5.10/doc/man/ctl_zoneinfo.8.html0000644000175000017500000000577213001246655016037 00000000000000 CTL_ZONEINFO

CTL_ZONEINFO

NAME
SYNOPSIS
DESCRIPTION
OPTIONS
FILES
SEE ALSO

*

NAME

ctl_zoneinfo - perform operations on the zoneinfo database

SYNOPSIS

ctl_zoneinfo [ -C config-file ] [ -v ] -r version-string

DESCRIPTION

Ctl_zoneinfo is used to perform various administrative operations on the zoneinfo database.

Ctl_zoneinfo reads its configuration options out of the imapd.conf(5) file unless specified otherwise by -C.

OPTIONS

-C config-file

Read configuration options from config-file.

-v

Enable verbose output.

-r version-string

Rebuild the zoneinfo database based on the directory structure of configdirectory/zoneinfo. The database to be rebuilt will be in the default location of configdirectory/zoneinfo.db unless otherwise specified by the zoneinfo_db_path option in imapd.conf. The version-string should describe the source of the timezone data (e.g. "Olson 2013h") and will be used by the timezone module of httpd.

FILES

/etc/imapd.conf

SEE ALSO

imapd.conf(5), master(8), httpd(8)


cyrus-imapd-2.5.10/doc/man/nntptest.1.html0000644000175000017500000001445713001246661015213 00000000000000 NNTPTEST

NNTPTEST

NAME
SYNOPSIS
DESCRIPTION
OPTIONS
SEE ALSO

NAME

nntptest - interactive NNTP test program

SYNOPSIS

nntptest [ -t keyfile ] [ -p port ] [ -m mechanism ]
[ -a userid ] [ -u userid ] [ -k num ] [ -l num ]
[ -r realm ] [ -f file ] [ -n num ] [ -s ] [ -c ]
[ -i ] [ -o option=value ] [ -v ] hostname

DESCRIPTION

nntptest is a utility that allows you to authenticate to a NNTP server and interactively issue commands to it. Once authenticated you may issue any NNTP command by simply typing it in. It is capable of multiple SASL authentication mechanisms and handles encryption layers transparently. This utility is often used for testing the operation of a nntp server. Also those developing NNTP clients find it useful.

OPTIONS

-t keyfile

Enable TLS. keyfile contains the TLS public and private keys. Specify "" to negotiate a TLS encryption layer but not use TLS authentication.

-p port

Port to connect to. If left off this defaults to nntp as defined in /etc/services.

-m mechanism

Force nntptest to use mechanism for authentication. If not specified the strongest authentication mechanism supported by the server is chosen. Specify user to use the AUTHINFO USER/PASS commands instead of AUTHINFO SASL.

-a userid

Userid to use for authentication; defaults to the current user. This is the userid whose password or credentials will be presented to the server for verification.

-u userid

Userid to use for authorization; defaults to the current user. This is the userid whose identity will be assumed after authentication. NOTE: This is only used with SASL mechanisms that allow proxying (e.g. PLAIN, DIGEST-MD5).

-k num

Minimum protection layer required.

-l num

Maximum protection layer to use (0=none; 1=integrity; etc). For example if you are using the KERBEROS_V4 authentication mechanism specifying 0 will force nntptest to not use any layer and specifying 1 will force it to use the integrity layer. By default the maximum supported protection layer will be used.

-r realm

Specify the realm to use. Certain authentication mechanisms (e.g. DIGEST-MD5) may require one to specify the realm.

-f file

Pipe file into connection after authentication.

-n num

Number of authentication attempts; default = 1. The client will attempt to do SSL/TLS session reuse and/or fast reauth (e.g. DIGEST-MD5), if possible.

-s

Enable NNTP over SSL (nntps).

-c

Enable challenge prompt callbacks. This will cause the OTP mechanism to ask for the the one-time password instead of the secret pass-phrase (library generates the correct response).

-i

Don’t send an initial client response for SASL mechanisms, even if the protocol supports it.

-o option=value

Set the SASL option to value.

-v

Verbose. Print out more information than usual.

SEE ALSO

nntpd(8)


cyrus-imapd-2.5.10/doc/man/mbexamine.8.html0000644000175000017500000000604313001246660015277 00000000000000 MBEXAMINE

MBEXAMINE

NAME
SYNOPSIS
DESCRIPTION
OPTIONS
FILES

NAME

mbexamine - examine a cyrus-format mailbox

SYNOPSIS

mbexamine [ -C config-file ] [ -u uid ] mailbox...
mbexamine
[ -C config-file ] [ -s seqnum ] mailbox...
mbexamine
[ -C config-file ] -q mailbox...

DESCRIPTION

Mbexamine will examine the header, index, and cache files of a cyrus format mailbox and dump the information contained therein. It can also limit its output to a specific uid or sequence number, through use of the -s and -u switches. Mbexamine reads its configuration options out of the imapd.conf(5) file unless specified otherwise by -C. It uses the mboxlist database to locate the mailbox on disk.

OPTIONS

-C config-file

Read configuration options from config-file.

-s

Dump information for the given sequence number only.

-u

Dump information for the given uid only.

-q

Compare the quota usage in cyrus.index to the actual message file sizes and report any differences. If there are differences, the mailbox SHOULD be reconstructed.

FILES

/etc/imapd.conf


cyrus-imapd-2.5.10/doc/man/cyradm.1.html0000644000175000017500000004470013001246645014607 00000000000000

NAME

cyradm - Cyrus administration shell, alter ego of Cyrus::IMAP::Shell

SYNOPSIS

  $ cyradm [--user user] [--[no]rc] [--systemrc file] [--userrc file] \
  > [--port n] [--auth mechanism] [--tlskey keyfile] [--notls] \
  > [--cafile cacertfile] [--cadir cacertdir] \
  > [--server] server

but possibly

  $ perl -MCyrus::IMAP::Shell -e 'run("myscript")'

or even (not recommended)

  use Cyrus::IMAP::Admin::Shell;

  run('myscriptname');

DESCRIPTION

This module implements cyradm in Perl. It is a shell around Cyrus::IMAP::Admin. Commands are provided in both Tcl-compatible forms and GNU-style long option forms.

COMMANDS

authenticate [--minssf N] [--maxssf N] [--mechanisms list] [--service name] [--tlskey keyfile] [--notls] [--cafile cacertfile] [--capath cacertdir] [user]
auth [--minssf N] [--maxssf N] [--mechanisms list] [--service name] [--tlskey keyfile] [--notls] [--cafile cacertfile] [--capath cacertdir] [user]
login [--minssf N] [--maxssf N] [--mechanisms list] [--service name] [--tlskey keyfile] [--notls] [--cafile cacertfile] [--capath cacertdir] [user]

Authenticate to server. You must already be connected to a server and Cyrus imapd will refuse to allow you to re-authenticate once you have authenticated once.

chdir directory
cd directory

Change directory. A pwd builtin is not provided, but the default command action will run pwd from a shell if invoked.

createmailbox [--partition partition] [--specialuse specialuse] mailbox
create [--partition partition] [--specialuse specialuse] mailbox
create [--specialuse specialuse] mailbox partition
cm [--partition partition] [--specialuse specialuse] mailbox
cm [--specialuse specialuse] mailbox partition

Create a mailbox on the default or a specified partition. Both old-style and getopt-style usages are accepted (combining them will produce an error). Optionally assign a special use to the mailbox.

deleteaclmailbox mailbox id [...]
deleteacl mailbox id [...]
dam mailbox id [...]

Remove ACLs from the specified mailbox.

deletemailbox mailbox
delete mailbox
dm mailbox

Delete the specified mailbox.

Administrators do not have implicit delete rights on mailboxes. Use the setaclmailbox command to grant the x permission to your principal if you need to delete a mailbox you do not own.

Note that the online help admits to an optional host argument. This argument is not currently used, and will be rejected with an error if specified; it is reserved for IMSP.

disconnect
disc

Disconnect from the current server. The prompt will revert to cyradm>.

exit [number]
quit [number]

Exit cyradm, optionally with a specific exit status; the exit status of the last command will be used if one is not specified.

help [command]
? [command]

Show help for command or all commands.

info [mailbox]

Display the mailbox/server metadata.

listaclmailbox mailbox
listacl mailbox
lam mailbox

List ACLs on the specified mailbox.

listmailbox [--subscribed] [--specialuse] [pattern [reference]]
list [--subscribed] [--specialuse] [pattern [reference]]
lm [--subscribed] [--specialuse] [pattern [reference]]

List all, or all subscribed or special-use, mailboxes matching the specified pattern. The pattern may have embedded wildcards '*' or '%', which match anything or anything except the separator character, respectively.

Mailboxes returned will be relative to the specified reference if one is specified. This allows a mailbox list to be limited to a particular hierarchy.

In some cases when the '%' wildcard is used to end a pattern, it may match an entry which is not a mailbox but which contains other mailboxes. In this case, the entry will be parenthesized to indicate that it is a root for other mailboxes, as opposed to a mailbox itself.

listquota root
lq root

List quotas on specified root. If the specified mailbox path does not have a quota assigned, an error will be raised; see listquotaroot for a way to find the quota root for a mailbox.

listquotaroot mailbox
lqm mailbox
lqr mailbox?

show quota roots and quotas for mailbox

mboxconfig [--private] mailbox attribute value
mboxcfg [--private] mailbox attribute value

Set mailbox metadata, optionally set the private instead of the shared version of the metadata. A value of "none" will remove the attribute.

The currently supported attributes are:

comment

Sets a comment or description associated with the mailbox.

expire

Sets the number of days after which messages will be expired from the mailbox.

news2mail

Sets an email address to which messages injected into the server via NNTP will be sent.

pop3showafter

Sets a time (in RFC3501 format, for example "6-Jan-2011 11:45:32 +1100") which specifies a cutoff date such that POP3 fetching of the folder does not see messages whose internaldate is before or equal to the date.

sharedseen

Enables the use of a shared \Seen flag on messages rather than a per-user \Seen flag. The 's' right in the mailbox ACL still controls whether a user can set the shared \Seen flag.

sieve

Indicates the name of the global sieve script that should be run when a message is delivered to the shared mailbox (not used for personal mailboxes).

squat

Indicates that the mailbox should have a squat index created for it.

/explicit/annotation

Sets the annotation /explicit/annotation on mailbox to value.

renamemailbox [--partition partition] oldname newname
rename [--partition partition] oldname newname
renm [--partition partition] oldname newname
renamemailbox oldname newname [partition]
rename oldname newname [partition]
renm oldname newname [partition]

Rename the specified mailbox, optionally moving it to a different partition. Both old-style and getopt-style usages are accepted; combining them will produce an error.

server [--noauthenticate] [server]
connect [--noauthenticate] [server]
servername [--noauthenticate] [server]

With no arguments, show the current server. With an argument, connect to that server. It will prompt for automatic login unless the --noauthenticate option is specified. (This may change; in particular, either automatic authentication will be removed or all authenticate options will be added.)

When connected to a server, the cyradm prompt changes from cyradm> to servername>, where servername is the fully qualified domain name of the connected server.

setaclmailbox mailbox id rights [id rights ...]
setacl mailbox id rights [id rights ...]
sam mailbox id rights [id rights ...]

Set ACLs on a mailbox. The ACL may be one of the special strings none, read (lrs), post (lrsp), append (lrsip), write (lrswipkxten), delete (lrxten), or all (lrswipkxten), or any combinations of the ACL codes:

l

Lookup (mailbox is visible to LIST/LSUB, SUBSCRIBE mailbox)

r

Read (SELECT/EXAMINE the mailbox, perform STATUS)

s

Seen (set/clear \SEEN flag via STORE, also set \SEEN flag during APPEND/COPY/FETCH BODY[...])

w

Write flags other than \SEEN and \DELETED

i

Insert (APPEND, COPY destination)

p

Post (send mail to mailbox)

k

Create mailbox (CREATE new sub-mailboxes, parent for new mailbox in RENAME)

x

Delete mailbox (DELETE mailbox, old mailbox name in RENAME)

t

Delete messages (set/clear \DELETED flag via STORE, also set \DELETED flag during APPEND/COPY)

e

Perform EXPUNGE and expunge as part of CLOSE

a

Administer (SETACL/DELETEACL/GETACL/LISTRIGHTS)

n

Add, delete or modify annotations

setinfo attribute value

Set server metadata. A value of "none" will remove the attribute. The currently supported attributes are:

motd

Sets a "message of the day". The message gets displayed as an ALERT after authentication.

comment

Sets a comment or description associated with the server.

admin

Sets the administrator email address for the server.

shutdown

Sets a shutdown message. The message gets displayed as an ALERT and all users are disconnected from the server (subsequent logins are disallowed).

expire

Sets the number of days after which messages will be expired from the server (unless overridden by a mailbox annotation).

squat

Indicates that all mailboxes should have a squat indexes created for them (unless overridden by a mailbox annotation).

setquota root resource value [resource value ...]
sq root resource value [resource value ...]

Set a quota on the specified root, which may or may not be an actual mailbox. The only resource understood by Cyrus is STORAGE. The value may be the special string none which will remove the quota.

version
ver

Display the version info of the current server.

xfermailbox [--partition partition] mailbox server
xfer [--partition partition] mailbox server
xfermailbox mailbox server [partition]
xfer mailbox server [partition]

Transfer (relocate) the specified mailbox to a different server. Both old-style and getopt-style usages are accepted; combining them will produce an error.

NOTES

GNU-style long options must be given in their entirety; Tcl-style options may be abbreviated.

Tcl-style options are provided as a compatibility feature. They will probably go away in the future.

Multiple commands can be given on a line, separated by ';' characters.

All commands set an exit status, which at present is not useful.

Unknown commands are passed to a subshell for execution.

The Tcl version of cyradm is used for scripting as well as interactively. While this is possible to a limited extent by use of the run method, scripting would normally be done with Cyrus::IMAP::Admin, which is far more flexible than either interactive cyradm or the Tcl scripting mechanism for Cyrus.

cyradm understands /bin/sh-style redirection: any command can have its standard or error output redirected, with all sh-style redirections (except <>) supported. It does not currently understand pipes or backgrounding.

If the Term::Readline::Perl or Term::Readline::GNU modules are available, cyradm will use it.

An alias facility is implemented internally, but no access is currently provided to it. This will change, if only to allow some of the predefined aliases to be removed if they conflict with useful shell commands.

AUTHOR

Brandon S. Allbery, allbery@ece.cmu.edu

SEE ALSO

Cyrus::IMAP::Admin Term::ReadLine sh(1), perl(1), imapd(8).

cyrus-imapd-2.5.10/doc/man/imtest.1.html0000644000175000017500000001637513001246657014647 00000000000000 IMTEST

IMTEST

NAME
SYNOPSIS
DESCRIPTION
OPTIONS
SEE ALSO

NAME

imtest - interactive IMAP test program

SYNOPSIS

imtest [ -t keyfile ] [ -p port ] [ -m mechanism ]
[ -a userid ] [ -u userid ] [ -k num ] [ -l num ]
[ -r realm ] [ -f file ] [ -n num ] [ -s ] [ -q ]
[ -c ] [ -i ] [ -z ] [ -v ] [ -I file ] [ -x file ]
[ -X file ] [ -o option=value ] hostname

DESCRIPTION

imtest is a utility that allows you to authenticate to a IMAP or IMSP server and interactively issue commands to it. Once authenticated you may issue any IMAP or IMSP command by simply typing it in. It is capable of multiple SASL authentication mechanisms and handles encryption layers transparently. This utility is often used for testing the operation of a imsp or imap server. Also those developing IMAP clients find it useful.

OPTIONS

-t keyfile

Enable TLS. keyfile contains the TLS public and private keys. Specify "" to negotiate a TLS encryption layer but not use TLS authentication.

-p port

Port to connect to. If left off this defaults to imap as defined in /etc/services.

-m mechanism

Force imtest to use mechanism for authentication. If not specified the strongest authentication mechanism supported by the server is chosen. Specify login to use the LOGIN command instead of AUTHENTICATE.

-a userid

Userid to use for authentication; defaults to the current user. This is the userid whose password or credentials will be presented to the server for verification.

-u userid

Userid to use for authorization; defaults to the current user. This is the userid whose identity will be assumed after authentication. NOTE: This is only used with SASL mechanisms that allow proxying (e.g. PLAIN, DIGEST-MD5).

-k num

Minimum protection layer required.

-l num

Maximum protection layer to use (0=none; 1=integrity; etc). For example if you are using the KERBEROS_V4 authentication mechanism specifying 0 will force imtest to not use any layer and specifying 1 will force it to use the integrity layer. By default the maximum supported protection layer will be used.

-r realm

Specify the realm to use. Certain authentication mechanisms (e.g. DIGEST-MD5) may require one to specify the realm.

-f file

Pipe file into connection after authentication.

-n num

Number of authentication attempts; default = 1. The client will attempt to do SSL/TLS session reuse and/or fast reauth (e.g. DIGEST-MD5), if possible.

-s

Enable IMAP over SSL (imaps).

-q

Enable IMAP COMPRESSion (before the last authentication attempt).

-c

Enable challenge prompt callbacks. This will cause the OTP mechanism to ask for the the one-time password instead of the secret pass-phrase (library generates the correct response).

-i

Don’t send an initial client response for SASL mechanisms, even if the protocol supports it.

-I file

Echo the PID of the running process into file (This can be useful with -X).

-x file

Open the named socket for the interactive portion

-X file

Like -x, only close all file descriptors & daemonize the process.

-o option=value

Set the SASL option to value.

-v

Verbose. Print out more information than usual.

-z

Timing test.

SEE ALSO

imapd(8)


cyrus-imapd-2.5.10/doc/man/lmtpd.8.html0000644000175000017500000000650013001246660014450 00000000000000 LMTPD

LMTPD

NAME
SYNOPSIS
DESCRIPTION
OPTIONS
FILES
SEE ALSO

NAME

lmtpd - LMTP server process

SYNOPSIS

lmtpd [ -C config-file ] [ -U uses ] [ -T timeout ] [ -D ]
[ -a ]

DESCRIPTION

Lmtpd is an LMTP server used to deliver mail to the IMAP mailstore. It accepts commands on its standard input and responds on its standard output. It MUST be invoked by master(8) with those descriptors attached to a remote client connection.

Lmtpd reads its configuration options out of the imapd.conf(5) file unless specified otherwise by -C.

OPTIONS

-C config-file

Read configuration options from config-file.

-U uses

The maximum number of times that the process should be used for new connections before shutting down. The default is 250.

-T timeout

The number of seconds that the process will wait for a new connection before shutting down. Note that a value of 0 (zero) will disable the timeout. The default is 60.

-D

Run external debugger specified in debug_command.

-a

Preauthorize connections initiated on an internet socket, instead of requiring LMTP AUTH. This should only be used for connections coming from trusted hosts.

FILES

/etc/imapd.conf

SEE ALSO

imapd.conf(5), master(8)


cyrus-imapd-2.5.10/doc/man/cyr_dbtool.8.html0000644000175000017500000001053013001246655015472 00000000000000 CYR_DBTOOL

CYR_DBTOOL

NAME
SYNOPSIS
DESCRIPTION
OPTIONS
FILES
SEE ALSO

NAME

cyr_dbtool - manage Cyrus databases

SYNOPSIS

cyr_dbtool [ -C config-file ] [ -M ] [ -n ] [ -o ] [ -T ] <db file> <db backend> <action> [ <key> ] [ <value> ]

DESCRIPTION

cyr_dbtool is used to manage a cyrusdb file. The usable actions are:

show [<prefix>]

get <key>

set <key> <value>

delete <key>

consistency

repack

You may omit key or key/value and specify one per line on stdin. Keys are terminated by tab or newline, values are terminated by newline.

Running without any options will list the available database backends and usable actions.

The ’consistency’ command runs a consistency check on the DB by calling

The ’repack’ command will compress the database by removing stale data on backends which support it. It’s a NOOP otherwise.

cyr_dbtool reads any applicable configuration options out of the imapd.conf(5) file unless specified otherwise by -C. note that the file locations are NOT read out of the configuration file, and must be supplied on the command line.

OPTIONS

-C config-file

Read configuration options from config-file.

-M

Uses improved MBOX list sort.

-n

Create the database file if it doesn’t already exist.

-o

Store all the output in memory and only print it once the transaction is completed.

-T

Use a transaction to do the action (most especially for ’show’) - the default used to be transactions.

FILES

/etc/imapd.conf

SEE ALSO

imapd.conf(5)


cyrus-imapd-2.5.10/doc/man/cyr_deny.8.html0000644000175000017500000000663113001246655015155 00000000000000 CYR_DENY

CYR_DENY

NAME
SYNOPSIS
DESCRIPTION
OPTIONS
FILES
SEE ALSO

NAME

cyr_deny - deny users access to Cyrus services

SYNOPSIS

cyr_deny [ -C config-file ] [ -s services ] [ -m message ] user
cyr_deny
[ -C config-file ] -a user
cyr_deny
[ -C config-file ] -l

DESCRIPTION

cyr_deny is used to deny individual users access to Cyrus services. The first synopsis denies user user access to Cyrus services, the second synopsis allows access again. cyr_deny works by adding an entry to the Cyrus deny database; the third synopsis lists the entries in the database.

OPTIONS

-C config-file

Read configuration options from config-file.

-a

Allow access to all services for user user (remove any entry from the deny database).

-s services

Deny access only to the given services, which is a comma-separated list of wildcard patterns. The default is "*" which denies access to all services.

-l

List the entries in the deny database.

-m message

Provide a message which is sent to the user to explain why access is being denied. A default message is used if none is specified.

FILES

/etc/imapd.conf

SEE ALSO

imapd.conf(5)


cyrus-imapd-2.5.10/doc/man/cyr_info.8.html0000644000175000017500000000672213001246655015152 00000000000000 CYR_INFO

CYR_INFO

NAME
SYNOPSIS
DESCRIPTION
OPTIONS
COMMANDS
FILES

NAME

cyr_info - general cyrus inspection tool

SYNOPSIS

cyr_info [ -C alt imapd.conf ] [ -M alt cyrus.conf ] command

DESCRIPTION

Cyr_info is a tool for getting information from Cyrus. The intent is to extend this tool with useful commands to make managing and configuring Cyrus easier. Cyr_info reads its configuration options out of the imapd.conf(5) file unless specified otherwise by -C.

OPTIONS

-C file

Read configuration options from file (imapd.conf format).

-M file

Read service specifications from file (cyrus.conf format).

-n name

Read the configuration as if for the service named name.

COMMANDS

allconf

print ALL configuration options - including default options

conf

print only the configuration options which are not the same as default (regardless of whether you have specified them or not)

lint

print only configuration options which are NOT recognised. This command should not print anything. It uses cyrus.conf to find the names of configured services to avoid displaying any known configuration options for the named service.

proc

print all currently connected processes in the proc directory

FILES

/etc/imapd.conf /etc/cyrus.conf


cyrus-imapd-2.5.10/doc/man/pop3test.1.html0000644000175000017500000001450413001246661015106 00000000000000 POP3TEST

POP3TEST

NAME
SYNOPSIS
DESCRIPTION
OPTIONS
SEE ALSO

NAME

pop3test - interactive POP3 test program

SYNOPSIS

pop3test [ -t keyfile ] [ -p port ] [ -m mechanism ]
[ -a userid ] [ -u userid ] [ -k num ] [ -l num ]
[ -r realm ] [ -f file ] [ -n num ] [ -s ] [ -c ]
[ -i ] [ -o option=value ] [ -v ] hostname

DESCRIPTION

pop3test is a utility that allows you to authenticate to a POP3 server and interactively issue commands to it. Once authenticated you may issue any POP3 command by simply typing it in. It is capable of multiple SASL authentication mechanisms and handles encryption layers transparently. This utility is often used for testing the operation of a pop3 server. Also those developing POP3 clients find it useful.

OPTIONS

-t keyfile

Enable TLS. keyfile contains the TLS public and private keys. Specify "" to negotiate a TLS encryption layer but not use TLS authentication.

-p port

Port to connect to. If left off this defaults to pop3 as defined in /etc/services.

-m mechanism

Force pop3test to use mechanism for authentication. If not specified the strongest authentication mechanism supported by the server is chosen. Specify user to use the USER/PASS commands or apop to use the APOP command instead of AUTH.

-a userid

Userid to use for authentication; defaults to the current user. This is the userid whose password or credentials will be presented to the server for verification.

-u userid

Userid to use for authorization; defaults to the current user. This is the userid whose identity will be assumed after authentication. NOTE: This is only used with SASL mechanisms that allow proxying (e.g. PLAIN, DIGEST-MD5).

-k num

Minimum protection layer required.

-l num

Maximum protection layer to use (0=none; 1=integrity; etc). For example if you are using the KERBEROS_V4 authentication mechanism specifying 0 will force pop3test to not use any layer and specifying 1 will force it to use the integrity layer. By default the maximum supported protection layer will be used.

-r realm

Specify the realm to use. Certain authentication mechanisms (e.g. DIGEST-MD5) may require one to specify the realm.

-f file

Pipe file into connection after authentication.

-n num

Number of authentication attempts; default = 1. The client will attempt to do SSL/TLS session reuse and/or fast reauth (e.g. DIGEST-MD5), if possible.

-s

Enable POP3 over SSL (pop3s).

-c

Enable challenge prompt callbacks. This will cause the OTP mechanism to ask for the the one-time password instead of the secret pass-phrase (library generates the correct response).

-i

Don’t send an initial client response for SASL mechanisms, even if the protocol supports it.

-o option=value

Set the SASL option to value.

-v

Verbose. Print out more information than usual.

SEE ALSO

pop3d(8)


cyrus-imapd-2.5.10/doc/man/timsieved.8.html0000644000175000017500000000463613001246663015334 00000000000000 TIMSIEVED

TIMSIEVED

NAME
SYNOPSIS
DESCRIPTION
OPTIONS
FILES
SEE ALSO

NAME

timsieved - CMU hack for getting sieve scripts onto the server

SYNOPSIS

timsieved [ -C config-file ]

DESCRIPTION

timsieved is a server that allows users to remotely manage their sieve scripts kept on the server. It accepts commands on its standard input and responds on its standard output. It MUST be invoked by master(8) with those descriptors attached to a remote client connection.

Cyrus admins that authenticate and authorize as themselves (e.g. don’t proxy) manage global scripts.

Timsieved reads its configuration options out of the imapd.conf(5) file unless specified otherwise by -C.

OPTIONS

-C config-file

Read configuration options from config-file.

FILES

/etc/imapd.conf

SEE ALSO

imapd.conf(5), master(8)


cyrus-imapd-2.5.10/doc/man/ctl_mboxlist.8.html0000644000175000017500000001342213001246654016037 00000000000000 CTL_MBOXLIST

CTL_MBOXLIST

NAME
SYNOPSIS
DESCRIPTION
OPTIONS
FILES
SEE ALSO

NAME

ctl_mboxlist - perform operations on the mailbox list database

SYNOPSIS

ctl_mboxlist [ -C config-file ] -d [ -x ] [ -p partition ]
[ -f filename ]
ctl_mboxlist
[ -C config-file ] -u [ -f filename ]
ctl_mboxlist
[ -C config-file ] -m [ -a ] [ -w ] [ -i ]
[ -f filename ]
ctl_mboxlist
[ -C config-file ] -v [ -f filename ]

DESCRIPTION

Ctl_mboxlist is used to perform various administrative operations on the mailbox list database.

Ctl_mboxlist reads its configuration options out of the imapd.conf(5) file unless specified otherwise by -C. The configdirectory option is used to determine the default location of the mailbox list database.

OPTIONS

-C config-file

Read configuration options from config-file.

-d

Dump the contents of the database to standard output in a portable flat-text format. NOTE: In Cyrus versions 2.2.13 and earlier, the dump format did not include the mailbox type flags, breaking remote mailboxes (frontends, mupdate master, unified backends) when undumped.

-x

When performing a dump, remove the mailboxes dumped from the mailbox list (mostly useful when specified with -p)

-p partition

When performing a dump, dump only thise mailboxes that live on partition

-u

Load the contents of the database from standard input. The input MUST be in the format output using the -d option. NOTE: Both the old and new formats can be loaded, but the old format will break remote mailboxes.

-m

For backend servers in the Cyrus Murder, synchronize the local mailbox list file with the MUPDATE server.

-a

When used with -m, assume the local mailboxes file is authoritiative, that is, only change the mupdate server, do not delete any local mailboxes. USE THIS OPTION WITH CARE, as it allows namespace collisions into the murder.

-w

When used with -m, print out what would be done but do not perform the operations.

-i

When used with -m, asks for verification before deleting local mailboxes.

-v

Verify the consistency of the mailbox list database and the spool partition(s). Mailboxes present in the database and not located on a spool partition, and those located on a spool partition (directory containing a valid cyrus.header file) and not present in the database will be reported. Note that this function is very I/O intensive.

-f filename

Use the database specified by filename instead of the default (configdirectory/mailboxes.db).

FILES

/etc/imapd.conf

SEE ALSO

imapd.conf(5), master(8)


cyrus-imapd-2.5.10/doc/man/mupdatetest.1.html0000644000175000017500000001400613001246660015660 00000000000000 MUPDATETEST

MUPDATETEST

NAME
SYNOPSIS
DESCRIPTION
OPTIONS
SEE ALSO

NAME

mupdatetest - interactive MUPDATE test program

SYNOPSIS

mupdatetest [ -p port ] [ -m mechanism ]
[ -a userid ] [ -u userid ] [ -k num ] [ -l num ]
[ -r realm ] [ -f file ] [ -n num ] [ -q ]
[ -c ] [ -i ] [ -o option=value ] [ -v ] hostname

DESCRIPTION

mupdatetest is a utility that allows you to authenticate to a MUPDATE server and interactively issue commands to it. Once authenticated you may issue any MUPDATE command by simply typing it in. It is capable of multiple SASL authentication mechanisms and handles encryption layers transparently. This utility is often used for testing the operation of a mupdate server. Note that you must be an admin in order to authenticate to an mupdate server.

OPTIONS

-p port

Port to connect to. If left off this defaults to mupdate as defined in /etc/services.

-m mechanism

Force mupdatetest to use mechanism for authentication. If not specified the strongest authentication mechanism supported by the server is chosen.

-a userid

Userid to use for authentication; defaults to the current user. This is the userid whose password or credentials will be presented to the server for verification.

-u userid

Userid to use for authorization; defaults to the current user. This is the userid whose identity will be assumed after authentication. NOTE: This is only used with SASL mechanisms that allow proxying (e.g. PLAIN, DIGEST-MD5).

-k num

Minimum protection layer required.

-l num

Maximum protection layer to use (0=none; 1=integrity; etc). For example if you are using the KERBEROS_V4 authentication mechanism specifying 0 will force mupdatetest to not use any layer and specifying 1 will force it to use the integrity layer. By default the maximum supported protection layer will be used.

-r realm

Specify the realm to use. Certain authentication mechanisms (e.g. DIGEST-MD5) may require one to specify the realm.

-f file

Pipe file into connection after authentication.

-n num

Number of authentication attempts; default = 1. The client will attempt to fast reauth (e.g. DIGEST-MD5), if possible.

-q

Enable MUPDATE COMPRESSion (before the last authentication attempt).

-c

Enable challenge prompt callbacks. This will cause the OTP mechanism to ask for the the one-time password instead of the secret pass-phrase (library generates the correct response).

-i

Don’t send an initial client response for SASL mechanisms, even if the protocol supports it.

-o option=value

Set the SASL option to value.

-v

Verbose. Print out more information than usual.

SEE ALSO

mupdate(8)


cyrus-imapd-2.5.10/doc/man/sync_client.8.html0000644000175000017500000001656613001246662015661 00000000000000 SYNC_CLIENT

SYNC_CLIENT

NAME
SYNOPSIS
DESCRIPTION
OPTIONS
FILES
SEE ALSO
AUTHORS

NAME

sync_client - client side of the synchronization (replication) engine

SYNOPSIS

sync_client [ -v ] [ -l ] [ -z ] [ -C config-file ] [ -S servername ]
[ -f input-file ] [ -F shutdown_file ] [ -w wait_interval ]
[ -t timeout ] [ -d delay ] [ -r ] [ -u ] [ -m ] [ -A ]
[ -s ] objects...

DESCRIPTION

sync_client is the client side of the replication system. It runs on the client (master) system and connects to the target (replica) system and generates an appropriate sequence of transactions to synchronize the replica system with the master system.

OPTIONS

-v

Verbose mode. Use twice (-v -v) to log all protocol traffic to stderr.

-l

Verbose logging mode.

-o

Only attempt to connect to the backend server once rather than waiting up to 1000 seconds before giving up.

-z

Require compression. The replication protocol will always try to enable deflate compression if both ends support it. Set this flag when you want to abort if compression is not available.

-C config-file

Read configuration options from config-file.

-S servername

Tells sync_client which server to communicate with. Overrides the sync_host configuration option.

-f input-file

In mailbox or user replication mode: provides list of users or mailboxes to replicate. In rolling replication mode, specifies an alternate log file (sync_client will exit after processing the log file).

-F shutdown-file

Rolling replication checks for this file at the end of each replication cycle and shuts down if it is present. Used to request a nice clean shutdown at the first convenient point. The file is removed on shutdown. Overrides sync_shutdown_file option in imapd.conf

-w interval

Wait this long before starting. This option is typically used so that we can attach a debugger to one end of the replication system or the other.

-t timeout

Timeout for single replication run in rolling replication. sync_client will negotiate a restart after this many seconds. Default: 600 seconds

-d delay

Minimum delay between replication runs in rolling replication mode. Larger values provide better efficiency as transactions can be merged. Smaller values mean that the replica system is more up to date and that you don’t end up with large blocks of replication transactions as a single group. Default: 3 seconds.

-r

Rolling (repeat) replication mode. Pick up a list of actions recorded by the lmtpd(8), imapd(8), popd(8) and nntpd(8) daemons from the file specified in sync_log_file. Repeat until sync_shutdown_file appears.

-n

Use the named channel for rolling replication mode. If multiple channels are specified in sync_log_channels then use one of them. This option is probably best combined with -S to connect to a different server with each channel.

-u

User mode. Remaining arguments are list of users who should be replicated.

-A

All users mode. Sync every user on the server to the replica (doesn’t do non-user mailboxes at all... this could be considered a bug and maybe it should do those mailboxes independently)

-m

Mailbox mode. Remaining arguments are list of mailboxes which should be replicated.

-s

Sieve mode. Remaining arguments are list of users whose Sieve files should be replicated. Principally used for debugging purposes: not exposed to sync_client(8).

FILES

/etc/imapd.conf

SEE ALSO

sync_server(8)

AUTHORS

David Carter (dpc22@cam.ac.uk), Ken Murchison (ken@oceana.com)


cyrus-imapd-2.5.10/doc/man/squatter.8.html0000644000175000017500000001145613001246662015210 00000000000000 SQUATTER

SQUATTER

NAME
SYNOPSIS
DESCRIPTION
OPTIONS
FILES

NAME

squatter - create SQUAT indexes for mailboxes

SYNOPSIS

squatter [ -C config-file ] [ -r ] [ -s ] [ -i ] [ -a ] [ -v ] mailbox...

DESCRIPTION

Squatter creates a new SQUAT index for one or more IMAP mailboxes. The SQUAT index is a unified index of all of the header and body text of each message a given mailbox. This index is used to significantly reduce IMAP SEARCH times on a mailbox.

Squatter creates an index of ALL messages in the mailbox, not just those since the last time that it was run (i.e., it does NOT do incremental updates). Any messages appended to the mailbox after squatter is run, will NOT be included in the index. To include new messages in the index, squatter must be run again. For large and active mailboxes, it is recommended to run squatter periodically as an EVENT in cyrus.conf(5)

NOTE: Messages and mailboxes that have not been indexed CAN still be SEARCHed, just not as quickly as those with a SQUAT index.

Squatter reads its configuration options out of the imapd.conf(5) file unless specified otherwise by -C.

OPTIONS

-C config-file

Read configuration options from config-file.

-r

Recursively create indexes for all sub-mailboxes of the mailboxes or mailbox prefixes given as arguments.

-s

Skip mailboxes whose index file is older than their current squat file (within a small time delta).

-i

Incremental updates where squat indexes already exist.

-a

Only create indexes for mailboxes which have the shared /vendor/cmu/cyrus-imapd/squat annotation set to "true".

The value of the /vendor/cmu/cyrus-imapd/squat annotation is inherited by all children of the given mailbox, so an entire mailbox tree can be indexed (or not indexed) by setting a single annotation on the root of that tree with a value of "true" (or "false"). If a mailbox does not have a /vendor/cmu/cyrus-imapd/squat annotation set on it (or does not inherit one), then the mailbox is not indexed. In other words, the implicit value of /vendor/cmu/cyrus-imapd/squat is "false".

-v

Increase the verbosity of progress/status messages.

FILES

/etc/imapd.conf /etc/cyrus.conf


cyrus-imapd-2.5.10/doc/man/mbpath.8.html0000644000175000017500000000447613001246660014615 00000000000000 MBPATH

MBPATH

NAME
SYNOPSIS
DESCRIPTION
OPTIONS
FILES

NAME

mbpath - translate mailbox names to filesystem paths

SYNOPSIS

mbpath [ -C config-file ] [ -q ] [ -s ] [ -m ] [ mailbox-names... ]

DESCRIPTION

Given a mailbox name or a space separated list of mailbox names, mbpath outputs the filesystem path to the mailbox.

Mbpath reads its configuration options out of the imapd.conf(5) file unless specified otherwise by -C.

OPTIONS

-C config-file

Read configuration options from config-file.

-q suppress any error output.

-s if any error occurs, stop processing the list of mailboxes and exit.

-m output the path to the metadata files (if different from the message files).

FILES

/etc/imapd.conf


cyrus-imapd-2.5.10/doc/man/idled.8.html0000644000175000017500000000441413001246656014420 00000000000000 IDLED

IDLED

NAME
SYNOPSIS
DESCRIPTION
OPTIONS
FILES
SEE ALSO

NAME

idled - provide near real-time updates for IMAP IDLE

SYNOPSIS

idled [ -C config-file ]

DESCRIPTION

Idled is a long lived datagram daemon which receives notifications of mailbox changes and signals the appropriate imapd to report the changes to the client. Idled is usually started from master.

Idled reads its configuration options out of the imapd.conf(5) file unless specified otherwise by -C. The idlesocket option is used to specify the Unix domain socket to listen on for notifications.

OPTIONS

-C config-file

Read configuration options from config-file.

FILES

/etc/imapd.conf

SEE ALSO

imapd.conf(5), master(8)


cyrus-imapd-2.5.10/doc/man/deliver.8.html0000644000175000017500000001176213001246656014775 00000000000000 DELIVER

DELIVER

NAME
SYNOPSIS
DESCRIPTION
OPTIONS
NOTES
FILES
SEE ALSO

NAME

deliver - deliver mail to an IMAP mailbox

SYNOPSIS

deliver [ -C config-file ] [ -d ] [ -r address ]
[ -f address ] [ -m mailbox ] [ -a auth-id ]
[ -q ] [ userid ]...
deliver
[ -C config-file ] -l

DESCRIPTION

Deliver reads a message from the standard input and delivers it to one or more IMAP mailboxes.

Deliver reads its configuration options out of the imapd.conf(5) file unless specified otherwise by -C.

OPTIONS

-C config-file

Read configuration options from config-file.

-d

Ignored for compatability with /bin/mail.

-r address

Insert a Return-Path: header containing address

-f address

Insert a Return-Path: header containing address

-m mailbox

Deliver to mailbox. If any userids are specified, attempts to deliver to user.userid.mailbox for each userid. If the ACL on any such mailbox does not grant the sender the "p" right or if -m is not specified, then delivers to the INBOX for the userid, regardless of the ACL on the INBOX.

If no userids are specified, attempts to deliver to mailbox. If the ACL on mailbox does not grant the sender the "p" right, the delivery fails.

-a auth-id

Specify the authorization id of the sender. Defaults to "anonymous".

-q

Deliver message even when receiving mailbox is over quota.

-l

Accept messages using the LMTP protocol.

NOTES

Depending on the setting of reject8bit in imapd.conf(5), deliver either rejects/accepts messages with 8-bit-set characters in the headers. If we accept messages with 8-bit-set characters in the headers, then depending on the setting of munge8bit, these characters are either left un-touched or changed to ’X’. This is because such characters can’t be interpreted since the character set is not known, although some communities not well-served by US-ASCII assume that those characters can be used to represent characters not present in US-ASCII.

A method for encoding 8-bit-set characters is provided by RFC 2047.

FILES

/etc/imapd.conf

SEE ALSO

lmtpd(8)


cyrus-imapd-2.5.10/doc/man/imclient.3.html0000644000175000017500000004077013001246657015144 00000000000000 IMCLIENT

IMCLIENT

NAME
SYNOPSIS
DESCRIPTION
EXAMPLES
BUGS
SEE ALSO
KEYWORDS

NAME

imclient - (library) authenticating callback interface to IMAP/IMSP servers

SYNOPSIS

#include <cyrus/imclient.h>

int imclient_connect(struct imclient **imclient, const char *host, const char *port);

void imclient_close (struct imclient *imclient);
void imclient_setflags(struct imclient *
imclient, intflags);
void imclient_clearflags (struct imclient *
imclient, intflags);
char* imclient_servername (struct imclient *
imclient);
void imclient_addcallback (struct imclient * imclient ,...);
void imclient_send (struct imclient *
imclient, void (*finishproc)(), void *finishrock, const char *fmt, ...);
void imclient_getselectinfo (struct imclient *
imclient, int *fd, int * wanttowrite);
void imclient_processoneevent (struct imclient *
imclient);
int imclient_authenticate (struct imclient *
imclient, struct sasl_client **availmech, const char *service, const char *user, int protallowed);
int imclient_havetls ();
int imclient_starttls (struct imclient *
imclient, char *cert_file, char *key_file, char *CAfile, char *CApath);

DESCRIPTION

The imclient library functions are distributed with Cyrus IMAP and IMSP. These functions are used for building IMAP/IMSP client software. These functions handle Kerberos authentication and can set callbacks based on the keyword in untagged replies or based on the command tag at the end of command replies.

Users must link with the -lcyrus switch, and must supply a function called fatal to be called in case of any error within libcyrus.la.

All of the imclient functions begin with the prefix imclient and takes an argument of type struct imclient * as the first argument which is initialized by imclient_connect and freed by imclient_close.

See below for a description of each function.
imclient_connect()

Connects the client server to the host. If successful, it returns 0 and sets the imclient argument to a pointer to an imclient struct. The imclient struct represents the current connection, flags, and callbacks. On failure, the current errno is returned if a system call failed, -1 is returned if the host name was not found, and -2 is returned if the service name was not found.

imclient_close()

Closes and frees the imclient connection.  

imclient_setflags()

Sets the flags specified by the flags argument on the imclient connection. Currently the only flag allowed is IMCLIENT_CONN_NONSYNCLITERAL (this flag indicates that the server supports non-synchronizing literals described by the LITERAL+ extension).

imclient_clearflags()

Clears the flags specified by the flags argument on the imclient connection.

imclient_servername()

Returns a char * pointer to the name of the server connected to by imclient.

imclient_addcallback()

Adds an untagged data callback to the imclient connection. The function imclient_addcallback takes callbacks of the type imclient_proc_t which is defined to be:

typedef void imclient_proc_t (struct imclient *imclient, void *rock, struct imclient_reply *reply);

and struct imclient_reply * is defined to be:

struct imclient_reply {

char *keyword;
long msgno;
char *text;

};

After the first argument imclient, there can be zero or more instances of the set of keyword, flags, proc, and rock, each adding or changing a single callback. Each instance adds or changes the callback for keyword. The argument, flags, specifies information about the parsing of the untagged data. proc and rock specify the callback function and rock to invoke when the untagged data is received. proc may be a null pointer, in which case no function is invoked. The callback function may not call the functions imclient_close(), imclient_send(), imclient_eof(), imclient_processoneevent(), or imclient_authenticate() on the connection. The callback function may over write the text of untagged data.

imclient_send()

Sends a new command to the imclient connection. finishproc and finnishrock are the function and rock called when the command completes. functionproc may be a null pointer, in which case no callback is made. The call back function may not call the functions imclient_close(), imclient_send(), imclient_eof(), imclient_processoneevent(), or imclient_authenticate() on the connection. The argument, fmt , is a print like specification of the command. It must not include the tag as the tag is automatically added by imclient_send(). The defined %-sequences are:

%% for %
%a
for an IMAP atom
%s
for an astring (which will be quoted or literalized as needed)
%d
for a decimal
%u
for an unsigned decimal
%v
for #astring (argument is a null-terminated array of char * which are written as space separated astrings)

imclient_getselectinfo()

Gets the information for calling select(2). fd is filled in with the file descriptor to select(2) for read. wanttowrite is filled in with a nonzero value if select should be used for write as well.

imclient_processoneevent()

Processes one input or output event on the imclient connection.

imclient_authenticate()

Authenticates the imclient connection using one of the mechanisms in availmech. The argument, user, if not NULL, specifies the user to authenticate as. If the user is NULL, the current user is used. The argument protallowed is a bitmask of permissible protection mechanisms.
On success, 0 is returned. On failure (i.e., "BAD" keyboard, or no authentication mechanisms worked), 1 is returned. On extreme failure (premature "OK"), 2 is returned.

imclient_havetls()

Returns a Boolean indicating whether the imclient library was compiled with TLS (SSL) support. If so, imclient_starttls() may be used to secure the IMAP connection.

imclient_starttls()

Issues a STARTTLS command on an existing IMAP connection and negotiates the secure link. The cert_file and key_file arguments specify the client certificate and secret key to use to authenticate ourselves to the server. If client authentication is not needed, set both of these arguments to NULL.

The CAfile and CApath arguments specify a file or directory, respectively, of CA certificates for validating server certificates. (See SSL_CTX_load_verify_locations(3) for details.) If both of these are NULL, the client will be unable to validate the server’s certificate, in which case the connection may succeed but a warning will be printed to stdout.

EXAMPLES

The following code is a possible skeletion of imclient that relies on Kerberos to do authentication. This code preforms an IMAP CAPABILITY request and prints out the result.

struct sasl_client;
#include <cyrus/xmalloc.h> /* example uses xstrdup */
#include <cyrus/sasl.h>
#include <cyrus/imclient.h>
#include <stdio.h>

extern struct sasl_client krb_sasl_client;

struct sasl_client *login_sasl_client[] = {
&krb_sasl_client,
NULL
};
struct imclient *imclient;
char server[] = "cyrus.andrew.cmu.edu" ;
char port[] = "imap";

void fatal(char* message, int rc) {
fprintf(stderr, "fatal error: %s\n", message);
exit(rc);
}

static void callback_capability(struct imclient *imclient,

void *rock,

struct imclient_reply *reply) {

if (reply->text != NULL) {

*((char**)rock) = xstrdup( reply->text );

}
}

static void end_command (struct imclient *connection, void*

rock, struct imclient_reply *inmsg) {

(*(int*)rock)--;
}

main() {
char* capability_string;
int nc;

if (imclient_connect(&imclient, server, port)) {

fprintf(stderr,

"error: Couldn’t connect to %s %s\n",

server, port);

exit(1);

}

if (imclient_authenticate(imclient, login_sasl_client, "imap"

/* service */,

NULL /* user */, SASL_PROT_ANY)) {

exit(1);

}

imclient_addcallback(imclient, "CAPABILITY",

CALLBACK_NOLITERAL,

callback_capability,

&capability_string,

NULL);

nc = 1;

imclient_send(imclient, end_command,

(void*) &nc, "CAPABILITY");

while(nc > 0) {

imclient_processoneevent(imclient);

}

if (strstr("LITERAL+", capability_string)) {

imclient_setflags(imclient, IMCLIENT_CONN_NONSYNCLITERAL);

}

imclient_send(imclient, NULL, NULL, "LOGOUT");
imclient_close(imclient);

printf("capability text is: %s\n", capability_string);

free(capability_string);
}

BUGS

No known bugs.

SEE ALSO

cyradm, imapd, imspd, RFC2033 (IMAP LITERAL+ extension), RFC2060 (IMAP4rev1 specification), and select(2)

KEYWORDS

IMAP, ACAP, IMSP, Kerberos, Authentication


cyrus-imapd-2.5.10/doc/man/pop3d.8.html0000644000175000017500000001026513001246661014361 00000000000000 POP3D

POP3D

NAME
SYNOPSIS
DESCRIPTION
OPTIONS
FILES
SEE ALSO

NAME

pop3d - POP3 server process

SYNOPSIS

pop3d [ -C config-file ] [ -U uses ] [ -T timeout ] [ -D ]
[ -s ] [ -k ] [ -p ssf ]

DESCRIPTION

Pop3d is a POP3 server. It accepts commands on its standard input and responds on its standard output. It MUST invoked by master(8) with those descriptors attached to a remote client connection.

Pop3d reads its configuration options out of the imapd.conf(5) file unless specified otherwise by -C.

If the directory log/user exists under the directory specified in the configdirectory configuration option, then pop3d will create protocol telemetry logs for sessions authenticating as user. The telemetry logs will be stored in the log/user directory with a filename of the pop3d process-id.

OPTIONS

-C config-file

Read configuration options from config-file.

-U uses

The maximum number of times that the process should be used for new connections before shutting down. The default is 250.

-T timeout

The number of seconds that the process will wait for a new connection before shutting down. Note that a value of 0 (zero) will disable the timeout. The default is 60.

-D

Run external debugger specified in debug_command.

-s

Serve POP3 over SSL (pop3s). All data to and from pop3d is encrypted using the Secure Sockets Layer.

-k

Serve MIT’s KPOP (Kerberized POP) protocol instead.

-p ssf

Tell pop3d that an external layer exists. An SSF (security strength factor) of 1 means an integrity protection layer exists. Any higher SSF implies some form of privacy protection.

FILES

/etc/imapd.conf

SEE ALSO

imapd.conf(5), master(8)


cyrus-imapd-2.5.10/doc/man/smmapd.8.html0000644000175000017500000000616713001246662014624 00000000000000 SMMAPD

SMMAPD

NAME
SYNOPSIS
DESCRIPTION
OPTIONS
FILES

NAME

SMMAPD - Sendmail socket map daemon

SYNOPSIS

smmapd [ -C config-file ] [ -U uses ] [ -T timeout ]
[ -D ]

DESCRIPTION

SMMAPD is a Sendmail socket map daemon which is used to verify that a Cyrus mailbox exists, that it is postable and it is under quota. It accepts commands on its standard input and responds on its standard output. It MUST be invoked by master(8) with those descriptors attached to a remote client connection.

SMMAPD reads its configuration options out of the imapd.conf(5) file unless specified otherwise by -C.

OPTIONS

-C config-file

Read configuration options from config-file.

-U uses

The maximum number of times that the process should be used for new connections before shutting down. The default is 250.

-T timeout

The number of seconds that the process will wait for a new connection before shutting down. Note that a value of 0 (zero) will disable the timeout. The default is 60.

-D

Run external debugger specified in debug_command.

FILES

/etc/imapd.conf

Default configuration file.

/etc/cyrus.conf

Cyrus Master process configuration file.


cyrus-imapd-2.5.10/doc/man/tls_prune.8.html0000644000175000017500000000423513001246663015351 00000000000000 TLS_PRUNE

TLS_PRUNE

NAME
SYNOPSIS
DESCRIPTION
OPTIONS
FILES
SEE ALSO

NAME

tls_prune - prune expired sessions from the TLS sessions database

SYNOPSIS

tls_prune [ -C config-file ]

DESCRIPTION

Tls_prune is used to prune expired sessions from the TLS sessions database. The lifetime of a TLS session is determined by the tls_session_timeout configuration option.

Tls_prune reads its configuration options out of the imapd.conf(5) file unless specified otherwise by -C.

OPTIONS

-C config-file

Read configuration options from config-file.

FILES

/etc/imapd.conf

SEE ALSO

imapd.conf(5), master(8)


cyrus-imapd-2.5.10/doc/man/cvt_cyrusdb.8.html0000644000175000017500000000471413001246655015670 00000000000000 CVT_CYRUSDB

CVT_CYRUSDB

NAME
SYNOPSIS
DESCRIPTION
OPTIONS
FILES
SEE ALSO

NAME

cvt_cyrusdb - convert a database file between cyrus database formats

SYNOPSIS

cvt_cyrusdb [ -C config-file ] <old-file> <old-fileformat> <new-file> <new-file-format>

DESCRIPTION

cvt_cyrusdb is used to convert a cyrusdb file between different database backends. Note that you should not attempt to use the same file for input and output.

Running without any options will list the available database backends.

cvt_cyrusdb reads any applicable configuration options out of the imapd.conf(5) file unless specified otherwise by -C. note that the file locations are NOT read out of the configuration file, and must be supplied on the command line.

OPTIONS

-C config-file

Read configuration options from config-file.

FILES

/etc/imapd.conf

SEE ALSO

imapd.conf(5)


cyrus-imapd-2.5.10/doc/man/cyrus.conf.5.html0000644000175000017500000002531413001246656015427 00000000000000 CYRUS.CONF

CYRUS.CONF

NAME
DESCRIPTION
SECTION DESCRIPTIONS
EXAMPLE
ACCESS CONTROL
SEE ALSO

NAME

cyrus.conf - Cyrus configuration file

DESCRIPTION

/etc/cyrus.conf is the configuration file for the Cyrus master process. It defines the startup procedures, services and events to be spawned by master.

The /etc/cyrus.conf file consists of a series of entries divided into sections of the form

section {

name arguments

...

...

...

}

where section is the name of the section, name is the name of the entry and arguments is the whitespace-separated list of arguments for the entry. The name may be any sequence of alphabetic and numeric characters, but may not contain punctuation such as ’-’ or ’_’. In the SERVICES section, names must be unique.

Blank lines and lines beginning with ’’#’’ are ignored.

SECTION DESCRIPTIONS

The paragraphs below detail the three sections (START, SERVICES, EVENTS) that can be placed in the /etc/cyrus.conf file. The arguments that are available for each entry within the section are described, and each argument’s default value is shown.

Arguments can appear in any order. Some arguments have no default value, these are listed with ’’<no default>’’. For string arguments, the value MUST be enclosed in double quotes.

START
This section lists the processes to run before any SERVICES are spawned. This section is typically used to initialize databases and start long running daemons.
cmd=
<no default>

The command (with options) to spawn as a child process. This string argument is required.

SERVICES
This section is the heart of the /etc/cyrus.conf file. It lists the processes that should be spawned to handle client connections made on certain Internet/UNIX sockets.
babysit=
0

Integer value - if non-zero, will make sure at least one process is pre-forked, and will set the maxforkrate to 10 if it’s zero.

cmd=<no default>

The command (with options) to spawn as a child process. This string argument is required.

listen=<no default>

The UNIX or internet socket to listen on. This string field is required and takes one of the following forms:

path
[ host : ] port

where path is the explicit path to a UNIX socket, host is either the hostname or bracket-enclosed IP address of a network interface, and port is either a port number or service name (as listed in /etc/services).

proto=tcp

The protocol used for this service (tcp, tcp4, tcp6, udp, udp4, udp6). This string argument is optional.

tcp4, udp4: These arguments are used to bind the service to IPv4 only.
tcp6
, udp6: These arguments are used to bind the service to IPv6 only, if the operating system supports this.
tcp
, udp: These arguments are used to bind to both IPv4 and IPv6 if possible.

prefork=0

The number of instances of this service to always have running and waiting for a connection (for faster initial response time). This integer value is optional. Note that if you are listening on multiple network types (i.e. ipv4 and ipv6) then one process will be forked for each address, causing twice as many processes as you might expect.

maxchild=-1

The maximum number of instances of this service to spawn. A value of -1 means unlimited. This integer value is optional.

maxfds=256

The maximum number of file descriptors to which to limit this process. This integer value is optional.

maxforkrate=0

Maximum number of processes to fork per second - the master will insert sleeps to ensure it doesn’t fork faster than this on average.

EVENTS
This section lists processes that should be run at specific intervals, similar to cron jobs. This section is typically used to perform scheduled cleanup/maintenance.
cmd=
<no default>

The command (with options) to spawn as a child process. This string argument is required.

period=0

The interval (in minutes) at which to run the command. This integer value is optional, but SHOULD be a positive integer > 10.

at=<hhmm>

The time (24-hour format) at which to run the command each day. If set to a valid time (0000-2359), period is automatically set to 1440. This string argument is optional.

EXAMPLE

# example cyrus.conf

START {

recover

cmd="ctl_cyrusdb -r"

}

SERVICES {

imap

cmd="imapd" listen="imap" prefork=1
imaps

cmd="imapd -s" listen="imaps" prefork=0
lmtpunix

cmd="lmtpd" listen="/var/imap/socket/lmtp"
lmtp

cmd="lmtpd" listen="localhost:lmtp"

}

EVENTS {

checkpoint

cmd="ctl_cyrusdb -c" period=30
delprune

cmd="cyr_expire -E 3" at=0400
tlsprune

cmd="tls_prune" at=0400

}

ACCESS CONTROL

When TCP Wrappers is used to control access to Cyrus services, the name of the service entry should be used as the process name in the hosts_access(5) table. For instance, in the example above, "imap", "imaps", "lmtpunix" and "lmtp" would be used as the process names. This allows a single daemon such as imapd to be run in different modes or configurations (i.e., SSL and non-SSL enabled) yet still have separate access control rules.

SEE ALSO

master(8), imapd(8), pop3d(8), lmtpd(8), timsieved(8), idled(8), notifyd(8), ctl_cyrusdb(8), ctl_deliver(8), tls_prune(8), hosts_access(5)


cyrus-imapd-2.5.10/doc/man/unexpunge.8.html0000644000175000017500000001066613001246663015361 00000000000000 UNEXPUNGE

UNEXPUNGE

NAME
SYNOPSIS
DESCRIPTION
OPTIONS
FILES
SEE ALSO

NAME

unexpunge - restore expunged (but yet unremoved) messages

SYNOPSIS

unexpunge [ -C config-file ] -l mailbox
unexpunge
[ -C config-file ] -t time-interval [ -d ] [ -v ] [ -f flagname ] mailbox
unexpunge
[ -C config-file ] -a [ -d ] [ -v ] [ -f flagname ] mailbox
unexpunge
[ -C config-file ] -u [ -d ] [ -v ] [ -f flagname ] mailbox uid...

DESCRIPTION

Unexpunge is used to restore expunged messages which have yet to be removed from the Cyrus mailspool. This utility is only useful when the server is configured to use delayed expunge.

Unexpunge reads its configuration options out of the imapd.conf(5) file unless specified otherwise by -C.

OPTIONS

-C config-file

Read configuration options from config-file.

-l

List the expunged messages in the specified mailbox which are available for restoration.

-t time-interval

Unexpunge messages which were expunged in the last time-interval seconds. (modifiers: m: minutes, h: hours, d: days, w: weeks).

-a

Restore all of the expunged messages in the specified mailbox.

-u

Restore only those messages having the specified UIDs in the specified mailbox.

-d

Unset the \Deleted flag on any restored messages.

-f flagname

Set the user flag flagname on any restored messages. This can make it easy to batch operate on just the restored messages afterwards.

-v

Enable verbose output/logging.

FILES

/etc/imapd.conf

SEE ALSO

imapd.conf(5)


cyrus-imapd-2.5.10/doc/man/notifyd.8.html0000644000175000017500000001175713001246661015017 00000000000000 NOTIFYD

NOTIFYD

NAME
SYNOPSIS
DESCRIPTION
OPTIONS
NOTIFICATION METHODS
FILES
SEE ALSO

NAME

notifyd - Cyrus notification server

SYNOPSIS

notifyd [ -C config-file ] [ -U uses ] [ -T timeout ]
[ -D ]

DESCRIPTION

Notifyd is a daemon started from master(8) that handles notification requests on behalf of lmtpd(8). Notifyd accepts the request and performs the notification using the method specified in the request.

Note that for notifyd to run properly you must set proto=udp in its cyrus.conf services entry. prefork=1 is also recommended.

Notifyd reads its configuration options out of the imapd.conf(5) file unless specified otherwise by -C. The notifysocket option is used to specify the Unix domain socket to listen on for notifications.

OPTIONS

-C config-file

Read configuration options from config-file.

-U uses

The maximum number of times that the process should be used for new connections before shutting down. The default is 250.

-T timeout

The number of seconds that the process will wait for a new connection before shutting down. Note that a value of 0 (zero) will disable the timeout. The default is 60.

-D

Run external debugger specified in debug_command.

NOTIFICATION METHODS

null

Ignore the notification request.

log

Log the notification to syslog (for testing).

mailto

Email the notification. This method can ONLY be used in a Sieve ’notify’ action as it requires a mailto: URL to be specified as an :option.

zephyr

Send the notification as a zephyrgram. If used in a Sieve ’notify’ action, additional recipients can be specified as :options.

external

Send the notification via an external program. The path to the program is specified using the notify_external option in the configuration file.

FILES

/etc/imapd.conf

Default configuration file.

/etc/cyrus.conf

Cyrus Master process configuration file.

SEE ALSO

imapd.conf(5), cyrus.conf, master(8), lmtpd(8)


cyrus-imapd-2.5.10/doc/man/reconstruct.8.html0000644000175000017500000002064013001246661015705 00000000000000 RECONSTRUCT

RECONSTRUCT

NAME
SYNOPSIS
DESCRIPTION
OPTIONS
EXAMPLES
FILES

NAME

reconstruct - reconstruct mailboxes

SYNOPSIS

reconstruct [ -C config-file ] [ -p partition ] [ -x ] [ -r ] [ -f ]
[ -k ] [ -s ] [ -g ] [ -G ] [ -R ] [ -o ] [ -O ] mailbox...
reconstruct
[ -C config-file ] -m

DESCRIPTION

Reconstruct rebuilds one or more IMAP mailboxes. When invoked with the -m switch, it rebuilds the master mailboxes file. It can be used to recover from almost any sort of data corruption.

If Reconstruct can find existing header and index files, it attempts to preserve any data in them that is not derivable from the message files themselves. The state reconstruct attempts to preserve includes the flag names, flag state, and internaldate. Reconstruct derives all other information from the message files.

Reconstruct reads its configuration options out of the imapd.conf(5) file unless specified otherwise by -C. Any mailbox directory underneath the path specified in the partition-news configuration option is assumed to be in news format.

Reconstruct does not adjust the quota usage recorded in any quota root files. After running reconstruct, it is advisable to run quota(8) with the -f switch in order to fix the quota root files.

OPTIONS

-C config-file

Read configuration options from config-file.

-p partition

Search for the listed (non-existant) mailboxes on the indicated partition. Create the mailboxes in the database in addition to reconstructing them. (not compatible with the use of wildcards)

-x

When processing a mailbox which is not in the mailbox list (e.g. via the -p or -f options), do not import the metadata from the mailbox, instead create it anew (this specifically affects at least the mailbox’s seen state unique identifier, user flags, and ACL).

-r

Recursively reconstruct all sub-mailboxes of the mailboxes or mailbox prefixes given as arguments.

-f

Examine the filesystem underneath mailbox, adding all directories with a cyrus.header found there as new mailboxes. Useful for restoring mailboxes from backups.

-s

Don’t stat underlying files. This makes reconstruct run faster, at the expense of not noticing some issues (like zero byte files or size mistmatches). "reconstruct -s" should be quite fast.

-q

Emit less verbose information to syslog.

-n

Don’t make any changes. This gives equivalent behaviour to chk_cyrus where problems are reported, but not fixed.

-G

Force re-parsing of the underlying message (checks GUID correctness). Reconstruct with -G should fix all possible individual message issues, including corrupted data files.

-R

Perform a UID upgrade operation on GUID mismatch files. Use this option if you think your index is corrupted rather than your message files, or if all backup attempts have failed and you’re happy to be served the missing files.

-U

Use this option if you have corrupt message files in your spool and have been unable to restore them from backup. This will make the mailbox IOERROR free and fix replication. WARNING this deletes corrupt message files for ever - so make sure you’ve exhausted other options first!

-o

Ignore odd files in your mailbox disk directories. Probably useful if you are using some tool which adds additional tracking files.

-O

Delete odd files. This is the opposite of ’-o’.

-V version

Change the cyrus.index minor version to a specific version. This can be useful for upgrades or downgrades. Use a magical version of max to upgrade to the latest available database format version.

-u

Instead of mailbox prefixes, give usernames on the command line

-m

NOTE: CURRENTLY UNAVAILABLE

Rebuild the mailboxes file. Use whatever data in the existing mailboxes file it can scavenge, then scans all partitions listed in the imapd.conf(5) file for additional mailboxes.

EXAMPLES

You want to reconstruct the index files for a user, you have recovered a deleted mail file from backup and given it a suitable name (eg user/ben-lacy/33.), but it is not visible since it is not indexed:

reconstruct -r user.ben-lacy

If you have the unixhierarchysep:yes option set in /etc/imapd.conf you would need to run:

reconstruct -r user/ben.lacy

FILES

/etc/imapd.conf


cyrus-imapd-2.5.10/doc/man/cyr_expire.8.html0000644000175000017500000001664513001246655015520 00000000000000 CYR_EXPIRE

CYR_EXPIRE

NAME
SYNOPSIS
DESCRIPTION
OPTIONS
FILES
SEE ALSO

NAME

cyr_expire - expire messages and duplicate delivery database entries

SYNOPSIS

cyr_expire [ -C config-file ] [ -D delete-duration ] [ -E expire-duration ] [ -X expunge-duration ] [ -p mailbox-prefix ] [ -u username ] [ -t ] [ -v ]

DESCRIPTION

Cyr_expire is used to run a number of regular maintenance tasks on Cyrus databases, specifically:

expire messages from mailboxes, and

expire entries from the duplicate delivery database, and

cleanse mailboxes of partially expunged messages (when using the "delayed" expunge mode), and

remove deleted mailboxes (when using the "delayed" delete mode).

The expiration of messages is controlled by the /vendor/cmu/cyrus-imapd/expire mailbox annotation which specifies the age (in days) of messages in the given mailbox that should be deleted. A value of 0 means that no expiration is to be performed on that mailbox.

The value of the /vendor/cmu/cyrus-imapd/expire annotation is inherited by all children of the mailbox on which it is set, so an entire mailbox tree can be configured by setting a single annotation on the root of that tree. If a mailbox does not have a /vendor/cmu/cyrus-imapd/expire annotation set on it (or does not inherit one), then no messages are expired from the mailbox.

The annotation can be examined using the info command of cyradm(1p), and modified using the mboxconfig and setinfo commands of cyradm(1p).

Expiration of duplicate delivery database entries for a given mailbox is also controlled by the /vendor/cmu/cyrus-imapd/expire annotation which applies to that mailbox. Unlike message expiration, if no annotation applies to the mailbox then duplicate database entries are expired using the value given to the -E option.

Cyr_expire reads its configuration options out of the imapd.conf(5) file unless specified otherwise by -C.

Cyr_expire requires at least one of -D -E -X or -t to be supplied.

OPTIONS

-C config-file

Read configuration options from config-file.

-D delete-duration

Remove previously deleted mailboxes older than delete-duration (when using the "delayed" delete mode). The value can be a floating point number, and may have a suffix to specify the unit of time. If no suffix, the value is number of days. Valid suffixes are d (days), h (hours), m (minutes) and s (seconds).

-E expire-duration

Prune the duplicate database of entries older than expire-duration. This value is only used for entries which do not have a corresponding /vendor/cmu/cyrus-imapd/expire mailbox annotation. Format is the same as delete-duration.

-X expunge-duration

Expunge previously deleted messages older than expunge-duration (when using the "delayed" expunge mode). Format is the same as delete-duration.

-x

Do not expunge messages even if using delayed expunge mode. This reduces IO traffic considerably, allowing cyr_expire to be run frequently to clean up the duplicate database without overloading the machine.

-p mailbox-prefix

Only find mailboxes starting with this prefix, e.g. "user.justgotspammedlots".

-u userid

Only find mailboxes belonging to this user, e.g. "justgotspammedlots@example.com".

-t

Remove any user flags which are not used by remaining (not expunged) messages.

-v

Enable verbose output.

-a

Skip the annotation lookup, so all /vendor/cmu/cyrus-imapd/expire annotations are ignored entirely. It behaves as if they were not set, so only expire-days is considered for all mailboxes.

FILES

/etc/imapd.conf

SEE ALSO

imapd.conf(5), master(8), cyradm(1p)


cyrus-imapd-2.5.10/doc/man/ctl_cyrusdb.8.html0000644000175000017500000000721613001246654015655 00000000000000 CTL_CYRUSDB

CTL_CYRUSDB

NAME
SYNOPSIS
DESCRIPTION
OPTIONS
FILES
SEE ALSO

NAME

ctl_cyrusdb - perform operations common to all Cyrus databases

SYNOPSIS

ctl_cyrusdb [ -C config-file ] -r [ -x ]
ctl_cyrusdb
[ -C config-file ] -c

DESCRIPTION

Ctl_cyrusdb is used to perform various administrative operations on the Cyrus databases.

Ctl_cyrusdb reads its configuration options out of the imapd.conf(5) file unless specified otherwise by -C. The configdirectory option is used to determine the default location of the Cyrus databases.

OPTIONS

-C config-file

Read configuration options from config-file.

-r

Recover the databases after an application or system failure. Also performs database cleanup like removing mailbox reservations (and any associated mailbox files).

All mailbox files are also checked to make sure the file format matches the configured database type in imapd.conf. If not, the file is automatically converted using the same logic as cvt_cyrusdb.

-x

Used with -r to recover the database only. (Prevents database cleanup).

-c

Checkpoint and archive the databases. Changes to the database which are part of committed transactions are written to disk. Also, a hot backup of the databases is made and inactive log files are removed.

FILES

/etc/imapd.conf

SEE ALSO

imapd.conf(5), master(8)


cyrus-imapd-2.5.10/doc/man/imapd.conf.5.html0000644000175000017500000033277313001246657015367 00000000000000 IMAPD.CONF

IMAPD.CONF

NAME
DESCRIPTION
FIELD DESCRIPTIONS
SEE ALSO

NAME

imapd.conf - IMAP configuration file

DESCRIPTION

/etc/imapd.conf is the configuration file for the Cyrus IMAP server. It defines local parameters for IMAP.

Each line of the /etc/imapd.conf file has the form

option: value

where option is the name of the configuration option being set and value is the value that the configuration option is being set to.

Although there is no limit to the length of a line, a ’’\’’ (backslash) character may be used as the last character on a line to force it to continue on the next one. No additional whitespace is inserted before or after the ’’\’’. Note that a line that is split using ’’\’’ character(s) is still considered a single line. For example

option:\

value1 value2 \

value3

is equivalent to

option: value1 value2 value3

Blank lines and lines beginning with ’’#’’ are ignored.

For boolean and enumerated options, the values ’’yes’’, ’’on’’, ’’t’’, ’’true’’ and ’’1’’ turn the option on, the values ’’no’’, ’’off’’, ’’f’’, ’’false’’ and ’’0’’ turn the option off.

FIELD DESCRIPTIONS

The sections below detail options that can be placed in the /etc/imapd.conf file, and show each option’s default value. Some options have no default value, these are listed with ’’<no default>’’. Some options default to the empty string, these are listed with ’’<none>’’.
addressbookprefix:
#addressbooks

The prefix for the addressbook mailboxes hierarchies. The hierarchy delimiter will be automatically appended. The public addressbook hierarchy will be at the toplevel of the shared namespace. A user’s personal calendar hierarchy will be a child of their Inbox.

admins: <empty string>

The list of userids with administrative rights. Separate each userid with a space. Sites using Kerberos authentication may use separate "admin" instances.

Note that accounts used by users should not be administrators. Administrative accounts should not receive mail. That is, if user "jbRo" is a user reading mail, he should not also be in the admins line. Some problems may occur otherwise, most notably the ability of administrators to create top-level mailboxes visible to users, but not writable by users.

afspts_localrealms: <none>

The list of realms which are to be treated as local, and thus stripped during identifier canonicalization (for the AFSPTS ptloader module). This is different from loginrealms in that it occurs later in the authorization process (as the user id is canonified for PTS lookup)

afspts_mycell: <none>

Cell to use for AFS PTS lookups. Defaults to the local cell.

allowallsubscribe: 0

Allow subscription to nonexistent mailboxes. This option is typically used on backend servers in a Murder so that users can subscribe to mailboxes that don’t reside on their "home" server. This option can also be used as a workaround for IMAP clients which don’t play well with nonexistent or unselectable mailboxes (e.g., Microsoft Outlook).

allowanonymouslogin: 0

Permit logins by the user "anonymous" using any password. Also allows use of the SASL ANONYMOUS mechanism.

allowapop: 1

Allow use of the POP3 APOP authentication command.

Note that this command requires that SASL is compiled with APOP support, that the plaintext passwords are available in a SASL auxprop backend (e.g., sasldb), and that the system can provide enough entropy (e.g., from /dev/urandom) to create a challenge in the banner.

allownewnews: 0

Allow use of the NNTP NEWNEWS command.

Note that this is a very expensive command and should only be enabled when absolutely necessary.

allowplaintext: 0

If enabled, allows the use of cleartext passwords on the wire.

By default, the use of cleartext passwords requires a TLS/SSL encryption layer to be negotiated prior to any cleartext authentication mechanisms being advertised or allowed. To require a TLS/SSL encryption layer to be negotiated prior to ANY authentication, see the tls_required option.

allowusermoves: 0

Allow moving user accounts (with associated meta-data) via RENAME or XFER.

Note that measures should be taken to make sure that the user being moved is not logged in, and cannot login during the move. Failure to do so may result in the user’s meta-data (seen state, subscriptions, etc) being corrupted or out of date.

altnamespace: 0

Use the alternate IMAP namespace, where personal folders reside at the same level in the hierarchy as INBOX.

This option ONLY applies where interaction takes place with the client/user. Currently this is limited to the IMAP protocol (imapd) and Sieve scripts (lmtpd). This option does NOT apply to admin tools such as cyradm (admins ONLY), reconstruct, quota, etc., NOR does it affect LMTP delivery of messages directly to mailboxes via plus-addressing.

annotation_db: twoskip

The cyrusdb backend to use for mailbox annotations.

Allowed values: berkeley, berkeley-hash, skiplist, twoskip

annotation_db_path: <none>

The absolute path to the annotations db file. If not specified, will be confdir/annotations.db

anyoneuseracl: 1

Should non-admin users be allowed to set ACLs for the ’anyone’ user on their mailboxes? In a large organization this can cause support problems, but it’s enabled by default.

annotation_allow_undefined: 0

Allow clients to store values for entries which are not * defined either by Cyrus or in the annotations_definitions * file.

annotation_definitions: <none>

File containing external (third-party) annotation definitions.

Each line of the file specifies the properties of an annotation and has the following form:

name, scope, attrib-type, proxy-type, attrib-names, acl

name

is the hierarchical name as in RFC 5257 or RFC 5464 (in the latter case, without the leading /shared or /private). For example, /vendor/acme/blurdybloop.

scope

specifies whether the annotation is for the server, a mailbox, or a message.

attrib-type

specifies the attribute data type, which is used only to check the string value passed by clients when setting annotations. The attrib-type is one of:
string

any value is accepted.

content-type

this obsolete data type, which was useful for early drafts of the standard, is accepted but silently translated to string.

boolean

only the strings "true" or "false" are accepted. Checking is case-insensitive but the value is forced to lowercase.

int

integers are accepted.

uint

non-negative integers are accepted.

proxy-type

specifies whether this attribute is for the backend or proxy servers or both (proxy_and_backend)

attrib-names

is the space-separated list of available attributes for the annotation. Possible attribute names are value.shared, value.priv, and value (which permits both value.priv and value.shared). The attribute names size, size.shared, and size.priv are accepted but ignored; these attributes are automatically provided by the server if the corresponding value attribute is specified. Some obsolete attributes, which were defined early drafts of the standard, are accepted and ignored with a warning.

extra-permissions

is the extra ACL permission bits required for setting this annotation, in standard IMAP ACL permission bit string format. Note that this is in addition to the permission bits specified in RFC 5257 and RFC 5464, so leaving this field empty is harmless. Note also that there is no way to specify that an annotation can only be set by an admin user; in particular the a permission bit does not achieve this.

Blank lines and lines beginning with ’’#’’ are ignored.

annotation_callout: <none>

The pathname of a callout to be used to automatically add annotations or flags to a message when it is appended to a mailbox. The path can be either an executable (including a script), or a UNIX domain socket.

auditlog: 0

Should cyrus output log entries for every action taken on a message file or mailboxes list entry? It’s noisy so disabled by default, but can be very useful for tracking down what happened if things look strange

auth_mech: unix

The authorization mechanism to use.

Allowed values: unix, pts, krb, krb5

autocreateinboxfolders: <none>

Deprecated in favor of autocreate_inbox_folders.

autocreatequota: 0

Deprecated in favor of autocreate_quota.

autocreatequotamsg: -1

Deprecated in favor of autocreate_quota_messages.

autosievefolders: <none>

Deprecated in favor of autocreate_sieve_folders.

generate_compiled_sieve_script: <none>

Deprecated in favor of autocreate_sieve_script_compile.

autocreate_sieve_compiled_script: <none>

Deprecated in favor of autocreate_sieve_script_compiled.

autosubscribeinboxfolders: <none>

Deprecated in favor of autocreate_subscribe_folders.

autosubscribesharedfolders: <none>

Deprecated in favor of autocreate_subscribe_sharedfolders.

autosubscribe_all_sharedfolders: 0

Deprecated in favor of autocreate_subscribe_sharedfolders_all.

autocreate_inbox_folders: <none>

If a user does not have an INBOX already, and the INBOX is to be created, create the list of folders in this setting as well.

INBOX folders are created under both the following conditions:

1.

The user logins via the IMAP or the POP3 protocol. autocreate_quota option must have a value of zero or greater.

2.

A message arrives for the user through the lmtpd(8). autocreate_post option must be enabled.

autocreate_inbox_folders is a list of INBOX’s subfolders separated by a "|", that are automatically created by the server under the previous two scenarios. Leading and trailing whitespace is stripped, so "Junk | Trash" results in two folders: "Junk" and "Trash".

autocreate_post: 0

If enabled, when lmtpd(8) receives an incoming mail for an INBOX that does not exist, then the INBOX is automatically created by lmtpd(8) and delivery of the message continues.

autocreate_quota: -1

If set to a value of zero or higher, users have their INBOX folders created upon a successful login event or upon lmtpd(8) message delivery if autocreate_post is enabled, provided their INBOX did not yet already exist.

The user’s quota is set to the value if it is greater than zero, otherwise the user has unlimited quota.

Note that quota is specified in kilobytes.

autocreate_quota_messages: -1

If set to a value of zero or higher, users who have their INBOX folders created upon a successful login event (see autocreate_quota), or upon lmtpd(8) message delivery if autocreate_post is enabled, receive the message quota configured in this option.

The default of -1 disables assigning message quota.

For consistency with autocreate_quota, a value of zero is treated as unlimited message quota, rather than a message quota of zero.

autocreate_sieve_folders: <none>

A "|" separated list of subfolders of INBOX that will be automatically created, if requested by a sieve filter, through the "fileinto" action. The default is to create no folders automatically.

Leading and trailing whitespace is stripped from each folder, so a setting of "Junk | Trash" will create two folders: "Junk" and "Trash".

autocreate_sieve_script: <none>

The full path of a file that contains a sieve script. This script automatically becomes a user’s initial default sieve filter script.

When this option is not defined, no default sieve filter is created. The file must be readable by the Cyrus daemon.

autocreate_sieve_script_compile: 0

If set to yes and no compiled sieve script file exists, the sieve script which is compiled on the fly will be saved in the file name that autocreate_sieve_compiledscript option points to. In order a compiled script to be generated, autocreate_sieve_script and autocreate_sieve_compiledscript must have valid values

autocreate_sieve_script_compiled: <none>

The full path of a file that contains a compiled in bytecode sieve script. This script automatically becomes a user’s initial default sieve filter script. If this option is not specified, or the filename doesn’t exist then the script defined by autocreate_sieve_script is compiled on the fly and installed as the user’s default sieve script

autocreate_subscribe_folders: <none>

A list of folder names, separated by "|", that the users get automatically subscribed to, when their INBOX is created. These folder names must have been included in the autocreateinboxfolders option of the imapd.conf.

autocreate_subscribe_sharedfolders: <none>

A list of shared folders (bulletin boards), separated by "|", that the users get automatically subscribed to, after their INBOX is created. The shared folder must have been created and the user must have the required permissions to get subscribed to it. Otherwise, subscribing to the shared folder fails.

autocreate_subscribe_sharedfolders_all: 0

If set to yes, the user is automatically subscribed to all shared folders, one has permission to subscribe to.

autocreate_users: anyone

A space separated list of users and/or groups that are allowed their INBOX to be automatically created.

berkeley_cachesize: 512

Size (in kilobytes) of the shared memory buffer pool (cache) used by the berkeley environment. The minimum allowed value is 20. The maximum allowed value is 4194303 (4GB).

berkeley_locks_max: 50000

Maximum number of locks to be held or requested in the berkeley environment.

berkeley_txns_max: 100

Maximum number of transactions to be supported in the berkeley environment.

boundary_limit: 1000

messages are parsed recursively and a deep enough MIME structure can cause a stack overflow. Do not parse deeper than this many layers of MIME structure. The default of 1000 is much higher than any sane message should have.

caldav_allowscheduling: on

Enable calendar scheduling operations. If set to "apple", the server will emulate Apple CalendarServer behavior as closely as possible.

Allowed values: off, on, apple

caldav_maxdatetime: 20380119T031407Z

The latest date and time accepted by the server (ISO format). This value is also used for expanding non-terminating recurrence rules.

Note that increasing this value will require the DAV databases for calendars to be reconstructed with the dav_reconstruct utility in order to see its effect on serer-side time-based queries.

caldav_mindatetime: 19011213T204552Z

The earliest date and time accepted by the server (ISO format).

caldav_realm: <none>

The realm to present for HTTP authentication of CalDAV resources. If not set (the default), the value of the "servername" option will be used.

calendarprefix: #calendars

The prefix for the calendar mailboxes hierarchies. The hierarchy delimiter will be automatically appended. The public calendar hierarchy will be at the toplevel of the shared namespace. A user’s personal calendar hierarchy will be a child of their Inbox.

calendar_user_address_set: <none>

Space-separated list of domains corresponding to calendar user addresses for which the server is responsible. If not set (the default), the value of the "servername" option will be used.

carddav_realm: <none>

The realm to present for HTTP authentication of CardDAV resources. If not set (the default), the value of the "servername" option will be used.

chatty: 0

If yes, syslog tags and commands for every IMAP command, mailboxes for every lmtp connection, every POP3 command, etc

client_timeout: 10

Number of seconds to wait before returning a timeout failure when performing a client connection (e.g., in a murder environment)

commandmintimer: <none>

Time in seconds. Any imap command that takes longer than this time is logged.

configdirectory: <none>

The pathname of the IMAP configuration directory. This field is required.

createonpost: 0

Deprecated in favor of autocreate_post.

dav_realm: <none>

The realm to present for HTTP authentication of generic DAV resources (principals). If not set (the default), the value of the "servername" option will be used.

debug_command: <none>

Debug command to be used by processes started with -D option. The string is a C format string that gets 3 options: the first is the name of the executable (without path). The second is the pid (integer) and the third is the service ID. Example: /usr/local/bin/gdb /usr/cyrus/bin/%s %d

defaultacl: anyone lrs

The Access Control List (ACL) placed on a newly-created (non-user) mailbox that does not have a parent mailbox.

defaultdomain: <none>

The default domain for virtual domain support

defaultpartition: <none>

The partition name used by default for new mailboxes. If not specified, the partition with the most free space will be used for new mailboxes.

Note that the partition specified by this option must also be specified as partition-name, where you substitute ’name’ for the alphanumeric string you set defaultpartition to.

defaultserver: <none>

The backend server name used by default for new mailboxes. If not specified, the server with the most free space will be used for new mailboxes.

deletedprefix: DELETED

If "delete_mode" set to be "delayed", the prefix for the deleted mailboxes hierarchy. The hierarchy delimiter will be automatically appended.

delete_mode: delayed

The manner in which mailboxes are deleted. "immediate" mode is the default behavior in which mailboxes are removed immediately. In "delayed" mode, mailboxes are renamed to a special hiearchy defined by the "deletedprefix" option to be removed later by cyr_expire.

Allowed values: immediate, delayed

deleteright: c

Deprecated - only used for backwards compatibility with existing installations. Lists the old RFC 2086 right which was used to grant the user the ability to delete a mailbox. If a user has this right, they will automatically be given the new ’x’ right.

disable_user_namespace: 0

Preclude list command on user namespace. If set to ’yes’, the LIST response will never include any other user’s mailbox. Admin users will always see all mailboxes. The default is ’no’

disable_shared_namespace: 0

Preclude list command on shared namespace. If set to ’yes’, the LIST response will never include any non-user mailboxes. Admin users will always see all mailboxes. The default is ’no’

disconnect_on_vanished_mailbox: 0

If enabled, IMAP/POP3/NNTP clients will be disconnected by the server if the currently selected mailbox is (re)moved by another session. Otherwise, the missing mailbox is treated as empty while in use by the client.

ischedule_dkim_domain: <none>

The domain to be reported as doing iSchedule DKIM signing.

ischedule_dkim_key_file: <none>

File containing the private key for iSchedule DKIM signing.

ischedule_dkim_selector: <none>

Name of the selector subdividing the domain namespace. This specifies the actual key used for iSchedule DKIM signing within the domain.

duplicate_db: twoskip

The cyrusdb backend to use for the duplicate delivery suppression and sieve.

Allowed values: berkeley, berkeley-nosync, berkeley-hash, berkeley-hash-nosync, skiplist, sql, twoskip

duplicate_db_path: <none>

The absolute path to the duplicate db file. If not specified, will be confdir/deliver.db

duplicatesuppression: 1

If enabled, lmtpd will suppress delivery of a message to a mailbox if a message with the same message-id (or resent-message-id) is recorded as having already been delivered to the mailbox. Records the mailbox and message-id/resent-message-id of all successful deliveries.

event_content_inclusion_mode: standard

The mode in which message content may be included with MessageAppend and MessageNew. "standard" mode is the default behavior in which message is included up to a size with the notification. In "message" mode, the message is included and may be truncated to a size. In "header" mode, it includes headers truncated to a size. In "body" mode, it includes body truncated to a size. In "headerbody" mode, it includes full headers and body truncated to a size

Allowed values: standard, message, header, body, headerbody

event_content_size: 0

Truncate the message content that may be included with MessageAppend and MessageNew. Set 0 to include the entire message itself

event_exclude_flags: <none>

Don’t send event notification for given IMAP flag(s)

event_exclude_specialuse: Junk

Don’t send event notification for folder with given special-use attributes. Set ALL for any folder

event_extra_params: timestamp

Space-separated list of extra parameters to add to any appropriated event.

Allowed values: bodyStructure, clientAddress, diskUsed, flagNames, messageContent, messageSize, messages, modseq, service, timestamp, uidnext, vnd.cmu.midset, vnd.cmu.unseenMessages, vnd.cmu.envelope, vnd.cmu.sessionId, vnd.cmu.mbtype, vnd.cmu.davFilename, vnd.cmu.davUid

event_groups: message mailbox

Space-separated list of groups of related events to turn on notification

Allowed values: message, quota, flags, access, mailbox, subscription

event_notifier: <none>

Notifyd(8) method to use for "EVENT" notifications which are based on the RFC 5423. If not set, "EVENT" notifications are disabled.

expunge_mode: delayed

The mode in which messages (and their corresponding cache entries) are expunged. "default" mode is the default behavior in which the message files are purged at the time of the EXPUNGE, but index and cache records are retained to facilitate QRESYNC. In "delayed" mode, the message files are also retained, allowing unexpunge to rescue them. In "immediate" mode, both the message files and the index records are removed as soon as possible. In all cases, nothing will be finally purged until all other processes have closed the mailbox to ensure they never see data disappear under them. In "default" or "delayed" mode, a later run of "cyr_expire" will clean out the retained records (and possibly message files). This reduces the amount of I/O that takes place at the time of EXPUNGE and should result in greater responsiveness for the client, especially when expunging a large number of messages.

Allowed values: default, immediate, delayed

failedloginpause: 3

Number of seconds to pause after a failed login.

flushseenstate: 1

Deprecated. No longer used

foolstupidclients: 0

If enabled, only list the personal namespace when a LIST "*" is performed (it changes the request to a LIST "INBOX*").

force_sasl_client_mech: <none>

Force preference of a given SASL mechanism for client side operations (e.g., murder environments). This is separate from (and overridden by) the ability to use the <host shortname>_mechs option to set preferred mechanisms for a specific host

fulldirhash: 0

If enabled, uses an improved directory hashing scheme which hashes on the entire username instead of using just the first letter as the hash. This changes hash algorithm used for quota and user directories and if hashimapspool is enabled, the entire mail spool.

Note that this option CANNOT be changed on a live system. The server must be quiesced and then the directories moved with the rehash utility.

hashimapspool: 0

If enabled, the partitions will also be hashed, in addition to the hashing done on configuration directories. This is recommended if one partition has a very bushy mailbox tree.

debug: 0

If enabled, allow syslog() to pass LOG_DEBUG messages.

hostname_mechs: <none>

Force a particular list of SASL mechanisms to be used when authenticating to the backend server hostname (where hostname is the short hostname of the server in question). If it is not specified it will query the server for available mechanisms and pick one to use. - Cyrus Murder

hostname_password: <none>

The password to use for authentication to the backend server hostname (where hostname is the short hostname of the server) - Cyrus Murder

httpallowcompress: 1

If enabled, the server will compress response payloads if the client indicates that it can accept them. Note that the compressed data will appear in telemetry logs, leaving only the response headers as human-readable.

httpallowcors: <none>

A wildmat pattern specifying a list of origin URIs ( scheme "://" host [ ":" port ] ) that are allowed to make Cross-Origin Resource Sharing (CORS) requests on the server. By default, CORS requests are disabled.

Note that the scheme and host should both be lowercase, the port should be omitted if using the default for the scheme (80 for http, 443 for https), and there should be no trailing ’/’ (e.g.: "http://www.example.com:8080", "https://example.org").

httpallowtrace: 0

Allow use of the TRACE method.

Note that sensitive data might be disclosed by the response.

httpallowedurls: <none>

Space-separated list of relative URLs (paths) rooted at "httpdocroot" (see below) to be served by httpd. If set, this option will limit served static content to only those paths specified (returning "404 Not Found" to any other client requested URLs). Otherwise, httpd will serve any content found in "httpdocroot".

Note that any path specified by "rss_feedlist_template" is an exception to this rule.

httpcontentmd5: 0

If enabled, HTTP responses will include a Content-MD5 header for the purpose of providing an end-to-end message integrity check (MIC) of the payload body. Note that enabling this option will use additional CPU to generate the MD5 digest, which may be ignored by clients anyways.

httpdocroot: <none>

If set, http will serve the static content (html/text/jpeg/gif files, etc) rooted at this directory. Otherwise, httpd will not serve any static content.

httpkeepalive: 20

Set the length of the HTTP server’s keepalive heartbeat in seconds. The default is 20. The minimum value is 0, which will disable the keepalive heartbeat. When enabled, if a request takes longer than httpkeepalive seconds to process, the server will send the client provisional responses every httpkeepalive seconds until the final response can be sent

httpmodules: <empty string>

Space-separated list of HTTP modules that will be enabled in httpd(8). This option has no effect on modules that are disabled at compile time due to missing dependencies (e.g. libical).

Allowed values: caldav, carddav, domainkey, ischedule, rss, timezone

httpprettytelemetry: 0

If enabled, HTTP response payloads including server-generated markup languages (HTML, XML) will utilize line breaks and indentation to promote better human-readability in telemetry logs. Note that enabling this option will increase the amount of data sent across the wire.

httptimeout: 5

Set the length of the HTTP server’s inactivity autologout timer, in minutes. The default is 5. The minimum value is 0, which will disable persistent connections.

idlesocket: {configdirectory}/socket/idle

Unix domain socket that idled listens on.

ignorereference: 0

For backwards compatibility with Cyrus 1.5.10 and earlier -- ignore the reference argument in LIST or LSUB commands.

imapidlepoll: 60

The interval (in seconds) for polling for mailbox changes and ALERTs while running the IDLE command. This option is used when idled is not enabled or cannot be contacted. The minimum value is 1. A value of 0 will disable IDLE.

imapidresponse: 1

If enabled, the server responds to an ID command with a parameter list containing: version, vendor, support-url, os, os-version, command, arguments, environment. Otherwise the server returns NIL.

imapmagicplus: 0

Only list a restricted set of mailboxes via IMAP by using userid+namespace syntax as the authentication/authorization id. Using userid+ (with an empty namespace) will list only subscribed mailboxes.

implicit_owner_rights: lkxa

The implicit Access Control List (ACL) for the owner of a mailbox.

@include: <none>

Directive which includes the specified file as part of the configuration. If the path to the file is not absolute, CYRUS_PATH is prepended.

improved_mboxlist_sort: 0

If enabled, a special comparator will be used which will correctly sort mailbox names that contain characters such as ’ ’ and ’-’.

Note that this option SHOULD NOT be changed on a live system. The mailboxes database should be dumped (ctl_mboxlist) before the option is changed, removed, and then undumped after changing the option. When not using flat files for the subscriptions databases the same has to be done (cyr_dbtool) for each subscription database See improved_mboxlist_sort.html.

internaldate_heuristic: standard

Mechanism to determine email internaldates on delivery/reconstruct. "standard" uses time() when delivering a message, mtime on reconstruct. "receivedheader" looks at the top most Received header or time/mtime otherwise

Allowed values: standard, receivedheader

iolog: 0

Should cyrus output I/O log entries

ldap_authz: <none>

SASL authorization ID for the LDAP server

ldap_base: <empty string>

Contains the LDAP base dn for the LDAP ptloader module

ldap_bind_dn: <none>

Bind DN for the connection to the LDAP server (simple bind). Do not use for anonymous simple binds

ldap_deref: never

Specify how aliases dereferencing is handled during search.

Allowed values: search, find, always, never

ldap_domain_base_dn: <empty string>

Base DN to search for domain name spaces.

ldap_domain_filter:
(&(objectclass=domainrelatedobject)(associateddomain=%s))

Filter to use searching for domains

ldap_domain_name_attribute: associateddomain

The attribute name for domains.

ldap_domain_scope: sub

Search scope

Allowed values: sub, one, base

ldap_domain_result_attribute: inetdomainbasedn

Result attribute

ldap_filter: (uid=%u)

Specify a filter that searches user identifiers. The following tokens can be used in the filter string:

%% = % %u = user %U = user portion of %u (%U = test when %u = test@domain.tld) %d = domain portion of %u if available (%d = domain.tld when %u = %test@domain.tld), otherwise same as %r %D = user dn. (use when ldap_member_method: filter) %1-9 = domain tokens (%1 = tld, %2 = domain when %d = domain.tld)

ldap_filter is not used when ldap_sasl is enabled.

ldap_group_base: <empty string>

LDAP base dn for ldap_group_filter.

ldap_group_filter: (cn=%u)

Specify a filter that searches for group identifiers. See ldap_filter for more options.

ldap_group_scope: sub

Specify search scope for ldap_group_filter.

Allowed values: sub, one, base

ldap_id: <none>

SASL authentication ID for the LDAP server

ldap_mech: <none>

SASL mechanism for LDAP authentication

ldap_user_attribute: <none>

Specify LDAP attribute to use as canonical user id

ldap_member_attribute: <none>

See ldap_member_method.

ldap_member_base: <empty string>

LDAP base dn for ldap_member_filter.

ldap_member_filter: (member=%D)

Specify a filter for "ldap_member_method: filter". See ldap_filter for more options.

ldap_member_method: attribute

Specify a group method. The "attribute" method retrieves groups from a multi-valued attribute specified in ldap_member_attribute.

The "filter" method uses a filter, specified by ldap_member_filter, to find groups; ldap_member_attribute is a single-value attribute group name.

Allowed values: attribute, filter

ldap_member_scope: sub

Specify search scope for ldap_member_filter.

Allowed values: sub, one, base

ldap_password: <none>

Password for the connection to the LDAP server (SASL and simple bind). Do not use for anonymous simple binds

ldap_realm: <none>

SASL realm for LDAP authentication

ldap_referrals: 0

Specify whether or not the client should follow referrals.

ldap_restart: 1

Specify whether or not LDAP I/O operations are automatically restarted if they abort prematurely.

ldap_sasl: 1

Use SASL for LDAP binds in the LDAP PTS module.

ldap_sasl_authc: <none>

Deprecated. Use ldap_id

ldap_sasl_authz: <none>

Deprecated. Use ldap_authz

ldap_sasl_mech: <none>

Deprecated. Use ldap_mech

ldap_sasl_password: <none>

Deprecated. User ldap_password

ldap_sasl_realm: <none>

Deprecated. Use ldap_realm

ldap_scope: sub

Specify search scope.

Allowed values: sub, one, base

ldap_servers: ldap://localhost/

Deprecated. Use ldap_uri

ldap_size_limit: 1

Specify a number of entries for a search request to return.

ldap_start_tls: 0

Use transport layer security for ldap:// using STARTTLS. Do not use ldaps:// in ’ldap_uri’ with this option enabled.

ldap_time_limit: 5

Specify a number of seconds for a search request to complete.

ldap_timeout: 5

Specify a number of seconds a search can take before timing out.

ldap_ca_dir: <none>

Path to a directory with CA (Certificate Authority) certificates.

ldap_ca_file: <none>

Patch to a file containing CA (Certificate Authority) certificate(s).

ldap_client_cert: <none>

File containing the client certificate.

ldap_verify_peer: 0

Require and verify server certificate. If this option is yes, you must specify ldap_ca_file or ldap_ca_dir.

ldap_ciphers: <none>

List of SSL/TLS ciphers to allow. The format of the string is described in ciphers(1).

ldap_client_key: <none>

File containing the private client key.

ldap_tls_cacert_dir: <none>

Deprecated in favor of ldap_ca_dir.

ldap_tls_cacert_file: <none>

Deprecated in favor of ldap_ca_file.

ldap_tls_cert: <none>

Deprecated in favor of ldap_client_cert.

ldap_tls_key: <none>

Deprecated in favor of ldap_client_key.

ldap_tls_check_peer: <none>

Deprecated in favor of ldap_verify_peer.

ldap_tls_ciphers: <none>

Deprecated in favor of ldap_ciphers.

ldap_uri: <none>

Contains a list of the URLs of all the LDAP servers when using the LDAP PTS module.

ldap_version: 3

Specify the LDAP protocol version. If ldap_start_tls and/or ldap_use_sasl are enabled, ldap_version will be automatically set to 3.

lmtp_downcase_rcpt: 1

If enabled, lmtpd will convert the recipient addresses to lowercase (up to a ’+’ character, if present).

lmtp_fuzzy_mailbox_match: 0

If enabled, and the mailbox specified in the detail part of the recipient (everything after the ’+’) does not exist, lmtpd will try to find the closest match (ignoring case, ignoring whitespace, falling back to parent) to the specified mailbox name.

lmtp_over_quota_perm_failure: 0

If enabled, lmtpd returns a permanent failure code when a user’s mailbox is over quota. By default, the failure is temporary, causing the MTA to queue the message and retry later.

lmtp_strict_quota: 0

If enabled, lmtpd returns a failure code when the incoming message will cause the user’s mailbox to exceed its quota. By default, the failure won’t occur until the mailbox is already over quota.

lmtp_strict_rfc2821: 1

By default, lmtpd will be strict (per RFC 2821) with regards to which envelope addresses are allowed. If this option is set to false, 8bit characters in the local-part of envelope addresses are changed to ’X’ instead. This is useful to avoid generating backscatter with certain MTAs like Postfix or Exim which accept such messages.

lmtpsocket: {configdirectory}/socket/lmtp

Unix domain socket that lmtpd listens on, used by deliver(8). This should match the path specified in cyrus.conf(5).

lmtptxn_timeout: 300

Timeout (in seconds) used during a lmtp transaction to a remote backend (e.g. in a murder environment). Can be used to prevent hung lmtpds on proxy hosts when a backend server becomes unresponsive during a lmtp transaction. The default is 300 - change to zero for infinite.

loginrealms: <empty string>

The list of remote realms whose users may authenticate using cross-realm authentication identifiers. Separate each realm name by a space. (A cross-realm identity is considered any identity returned by SASL with an "@" in it.).

loginuseacl: 0

If enabled, any authentication identity which has a rights on a user’s INBOX may log in as that user.

logtimestamps: 0

Include notations in the protocol telemetry logs indicating the number of seconds since the last command or response.

mailbox_default_options: 0

Default "options" field for the mailbox on create. You’ll want to know what you’re doing before setting this, but it can apply some default annotations like duplicate supression

mailbox_initial_flags: <none>

space-separated list of permanent flags which will be pre-set in every newly created mailbox. If you know you will require particular flag names then this avoids a possible race condition against a client that fills the entire 128 available slots. Default is NULL, which is no flags. Example: $Label1 $Label2 $Label3 NotSpam Spam

mailnotifier: <none>

Notifyd(8) method to use for "MAIL" notifications. If not set, "MAIL" notifications are disabled.

maxheaderlines: 1000

Maximum number of lines of header that will be processed into cache records. Default 1000. If set to zero, it is unlimited. If a message hits the limit, an error will be logged and the rest of the lines in the header will be skipped. This is to avoid malformed messages causing giant cache records

maxlogins_per_host: 0

Maximum number of logged in sessions allowed per host, zero means no limit

maxlogins_per_user: 0

Maximum number of logged in sessions allowed per user, zero means no limit

maxmessagesize: 0

Maximum incoming LMTP message size. If non-zero, lmtpd will reject messages larger than maxmessagesize bytes. If set to 0, this will allow messages of any size (the default).

maxquoted: 131072

Maximum size of a single quoted string for the parser. Default 128k

maxword: 131072

Maximum size of a single word for the parser. Default 128k

mboxkey_db: twoskip

The cyrusdb backend to use for mailbox keys.

Allowed values: berkeley, skiplist, twoskip

mboxlist_db: twoskip

The cyrusdb backend to use for the mailbox list.

Allowed values: flat, berkeley, berkeley-hash, skiplist, sql, twoskip

mboxlist_db_path: <none>

The absolute path to the mailboxes db file. If not specified will be confdir/mailboxes.db

mboxname_lockpath: <none>

Path to mailbox name lock files (default $conf/lock)

metapartition_files: <empty string>

Space-separated list of metadata files to be stored on a metapartition rather than in the mailbox directory on a spool partition.

Allowed values: header, index, cache, expunge, squat, annotations, lock, dav

metapartition-name: <none>

The pathname of the metadata partition name, corresponding to spool partition partition-name. For any mailbox residing in a directory on partition-name, the metadata files listed in metapartition_files will be stored in a corresponding directory on metapartition-name. Note that not every partition-name option is required to have a corresponding metapartition-name option, so that you can selectively choose which spool partitions will have separate metadata partitions.

mupdate_authname: <none>

The SASL username (Authentication Name) to use when authenticating to the mupdate server (if needed).

mupdate_config: standard

The configuration of the mupdate servers in the Cyrus Murder. The "standard" config is one in which there are discreet frontend (proxy) and backend servers. The "unified" config is one in which a server can be both a frontend and backend. The "replicated" config is one in which multiple backend servers all share the same mailspool, but each have their own "replicated" copy of mailboxes.db.

Allowed values: standard, unified, replicated

munge8bit: 1

If enabled, lmtpd munges messages with 8-bit characters in the headers. The 8-bit characters are changed to ’X’. If reject8bit is enabled, setting munge8bit has no effect. (A proper solution to non-ASCII characters in headers is offered by RFC 2047 and its predecessors.)

mupdate_connections_max: 128

The max number of connections that a mupdate process will allow, this is related to the number of file descriptors in the mupdate process. Beyond this number connections will be immediately issued a BYE response.

mupdate_password: <none>

The SASL password (if needed) to use when authenticating to the mupdate server.

mupdate_port: 3905

The port of the mupdate server for the Cyrus Murder

mupdate_realm: <none>

The SASL realm (if needed) to use when authenticating to the mupdate server.

mupdate_retry_delay: 20

The base time to wait between connection retries to the mupdate server.

mupdate_server: <none>

The mupdate server for the Cyrus Murder

mupdate_username: <empty string>

The SASL username (Authorization Name) to use when authenticating to the mupdate server

mupdate_workers_max: 50

The maximum number of mupdate worker threads (overall)

mupdate_workers_maxspare: 10

The maximum number of idle mupdate worker threads

mupdate_workers_minspare: 2

The minimum number of idle mupdate worker threads

mupdate_workers_start: 5

The number of mupdate worker threads to start

netscapeurl: <none>

If enabled at compile time, this specifies a URL to reply when Netscape asks the server where the mail administration HTTP server is. Administrators should set this to a local resource.

newsaddheaders: to

Space-separated list of headers to be added to incoming usenet articles. Added To: headers will contain email delivery addresses corresponding to each newsgroup in the Newsgroups: header. Added Reply-To: headers will contain email delivery addresses corresponding to each newsgroup in the Followup-To: or Newsgroups: header. If the specified header(s) already exist in an article, the email delivery addresses will be appended to the original header body(s).

This option applies if and only if the newspostuser option is set.

Allowed values: to, replyto

newsgroups: *

A wildmat pattern specifying which mailbox hierarchies should be treated as newsgroups. Only mailboxes matching the wildmat will accept and/or serve articles via NNTP. If not set, a default wildmat of "*" (ALL shared mailboxes) will be used. If the newsprefix option is also set, the default wildmat will be translated to "<newsprefix>.*"

newsmaster: news

Userid that is used for checking access controls when executing Usenet control messages. For instance, to allow articles to be automatically deleted by cancel messages, give the "news" user the ’d’ right on the desired mailboxes. To allow newsgroups to be automatically created, deleted and renamed by the corresponding control messages, give the "news" user the ’c’ right on the desired mailbox hierarchies.

newspeer: <none>

A list of whitespace-separated news server specifications to which articles should be fed. Each server specification is a string of the form [user[:pass]@]host[:port][/wildmat] where ’host’ is the fully qualified hostname of the server, ’port’ is the port on which the server is listening, ’user’ and ’pass’ are the authentication credentials and ’wildmat’ is a pattern that specifies which groups should be fed. If no ’port’ is specified, port 119 is used. If no ’wildmat’ is specified, all groups are fed. If ’user’ is specified (even if empty), then the NNTP POST command will be used to feed the article to the server, otherwise the IHAVE command will be used.

A ’@’ may be used in place of ’!’ in the wildmat to prevent feeding articles cross-posted to the given group, otherwise cross-posted articles are fed if any part of the wildmat matches. For example, the string "peer.example.com:*,!control.*,@local.*" would feed all groups except control messages and local groups to peer.example.com. In the case of cross-posting to local groups, these articles would not be fed.

newspostuser: <none>

Userid used to deliver usenet articles to newsgroup folders (usually via lmtp2nntp). For example, if set to "post", email sent to "post+comp.mail.imap" would be delivered to the "comp.mail.imap" folder.

When set, the Cyrus NNTP server will add the header(s) specified in the newsaddheaders option to each incoming usenet article. The added header(s) will contain email delivery addresses corresponding to each relevent newsgroup. If not set, no headers are added to usenet articles.

newsprefix: <none>

Prefix to be prepended to newsgroup names to make the corresponding IMAP mailbox names.

newsrc_db_path: <none>

The absolute path to the newsrc db file. If not specified, will be confdir/fetchnews.db

nntptimeout: 3

Set the length of the NNTP server’s inactivity autologout timer, in minutes. The minimum value is 3, the default.

notifysocket: {configdirectory}/socket/notify

Unix domain socket that the mail notification daemon listens on.

notify_external: <none>

Path to the external program that notifyd(8) will call to send mail notifications.

The external program will be called with the following command line options:
-c
class
-p
priority
-u
user
-m
mailbox

And the notification message will be available on stdin.

partition-name: <none>

The pathname of the partition name. At least one partition pathname MUST be specified. If the defaultpartition option is used, then its pathname MUST be specified. For example, if the value of the defaultpartion option is default, then the partition-default field is required.

partition_select_mode: freespace-most

Partition selection mode.
random

(pseudo-)random selection

freespace-most

partition with the most free space (KiB)

freespace-percent-most

partition with the most free space (%)

freespace-percent-weighted

each partition is weighted according to its free space (%); the more free space the partition has, the more chances it has to be selected

freespace-percent-weighted-delta

each partition is weighted according to its difference of free space (%) compared to the most used partition; the more the partition is lagging behind the most used partition, the more chances it has to be selected

Note that actually even the most used partition has a few chances to be selected, and those chances increase when other partitions get closer

Allowed values: random, freespace-most, freespace-percent-most, freespace-percent-weighted, freespace-percent-weighted-delta

partition_select_exclude: <none>

List of partitions to exclude from selection mode.

partition_select_usage_reinit: 0

For a given session, number of operations (e.g. partition selection) for which partitions usage data are cached.

partition_select_soft_usage_limit: 0

Limit of partition usage (%): if a partition is over that limit, it is automatically excluded from selection mode.

If all partitions are over that limit, this feature is not used anymore.

plaintextloginpause: 0

Number of seconds to pause after a successful plaintext login. For systems that support strong authentication, this permits users to perceive a cost of using plaintext passwords. (This does not affect the use of PLAIN in SASL authentications.)

plaintextloginalert: <none>

Message to send to client after a successful plaintext login.

popexpiretime: -1

The number of days advertised as being the minimum a message may be left on the POP server before it is deleted (via the CAPA command, defined in the POP3 Extension Mechanism, which some clients may support). "NEVER", the default, may be specified with a negative number. The Cyrus POP3 server never deletes mail, no matter what the value of this parameter is. However, if a site implements a less liberal policy, it needs to change this parameter accordingly.

popminpoll: 0

Set the minimum amount of time the server forces users to wait between successive POP logins, in minutes.

popsubfolders: 0

Allow access to subfolders of INBOX via POP3 by using userid+subfolder syntax as the authentication/authorization id.

poppollpadding: 1

Create a softer minimum poll restriction. Allows poppollpadding connections before the minpoll restriction is triggered. Additionally, one padding entry is recovered every popminpoll minutes. This allows for the occasional polling rate faster than popminpoll, (i.e., for clients that require a send/receive to send mail) but still enforces the rate long-term. Default is 1 (disabled).

The easiest way to think of it is a queue of past connections, with one slot being filled for every connection, and one slot being cleared every popminpoll minutes. When the queue is full, the user will not be able to check mail again until a slot is cleared. If the user waits a sufficient amount of time, they will get back many or all of the slots.

poptimeout: 10

Set the length of the POP server’s inactivity autologout timer, in minutes. The minimum value is 10, the default.

popuseacl: 0

Enforce IMAP ACLs in the pop server. Due to the nature of the POP3 protocol, the only rights which are used by the pop server are ’r’, user to open the mailbox and list/retrieve messages. The ’t’ right allows the user to delete messages. The ’s’ right allows messages retrieved by the user to have the \Seen flag set (only if popuseimapflags is also enabled).

popuseimapflags: 0

If enabled, the pop server will set and obey IMAP flags. Messages having the \Deleted flag are ignored as if they do not exist. Messages that are retrieved by the client will have the \Seen flag set. All messages will have the \Recent flag unset.

postmaster: postmaster

Username that is used as the ’From’ address in rejection MDNs produced by sieve.

postuser: <empty string>

Userid used to deliver messages to shared folders. For example, if set to "bb", email sent to "bb+shared.blah" would be delivered to the "shared.blah" folder. By default, an email address of "+shared.blah" would be used.

proc_path: <none>

Path to proc directory. Default is NULL - must be an absolute path if specified. If not specified, the path $confdir/proc/ will be used.

proxy_authname: proxy

The authentication name to use when authenticating to a backend server in the Cyrus Murder.

proxy_compress: 0

Try to enable protocol-specific compression when performing a client connection to a backend server in the Cyrus Murder.

Note that this should only be necessary over slow network connections. Also note that currently only IMAP and MUPDATE support compression.

proxy_password: <none>

The default password to use when authenticating to a backend server in the Cyrus Murder. May be overridden on a host-specific basis using the hostname_password option.

proxy_realm: <none>

The authentication realm to use when authenticating to a backend server in the Cyrus Murder

proxyd_allow_status_referral: 0

Set to true to allow proxyd to issue referrals to clients that support it when answering the STATUS command. This is disabled by default since some clients issue many STATUS commands in a row, and do not cache the connections that these referrals would cause, thus resulting in a higher authentication load on the respective backend server.

proxyd_disable_mailbox_referrals: 0

Set to true to disable the use of mailbox-referrals on the proxy servers.

proxyservers: <none>

A list of users and groups that are allowed to proxy for other users, separated by spaces. Any user listed in this will be allowed to login for any other user: use with caution. In a standard murder this option should ONLY be set on backends. DO NOT SET on frontends or things won’t work properly.

pts_module: afskrb

The PTS module to use.

Allowed values: afskrb, ldap

ptloader_sock: <none>

Unix domain socket that ptloader listens on. (defaults to configdir/ptclient/ptsock)

ptscache_db: twoskip

The cyrusdb backend to use for the pts cache.

Allowed values: berkeley, berkeley-hash, skiplist, twoskip

ptscache_db_path: <none>

The absolute path to the ptscache db file. If not specified, will be confdir/ptscache.db

ptscache_timeout: 10800

The timeout (in seconds) for the PTS cache database when using the auth_krb_pts authorization method (default: 3 hours).

ptskrb5_convert524: 1

When using the AFSKRB ptloader module with Kerberos 5 canonicalization, do the final 524 conversion to get a n AFS style name (using ’.’ instead of ’/’, and using short names

ptskrb5_strip_default_realm: 1

When using the AFSKRB ptloader module with Kerberos 5 canonicalization, strip the default realm from the userid (this does not affect the stripping of realms specified by the afspts_localrealms option)

qosmarking: cs0

This specifies the Class Selector or Differentiated Services Code Point designation on IP headers (in the ToS field).

Allowed values: cs0, cs1, cs2, cs3, cs4, cs5, cs6, cs7, af11, af12, af13, af21, af22, af23, af31, af32, af33, af41, af42, af43, ef

quota_db: quotalegacy

The cyrusdb backend to use for quotas.

Allowed values: flat, berkeley, berkeley-hash, skiplist, sql, quotalegacy, twoskip

quota_db_path: <none>

The absolute path for the quota database (if you choose a single-file quota DB type - or the base path if you choose quotalegacy). If not specified will be confdir/quota.db or confdir/quota/

quotawarn: 90

The percent of quota utilization over which the server generates warnings.

quotawarnkb: 0

The maximum amount of free space (in kB) at which to give a quota warning (if this value is 0, or if the quota is smaller than this amount, then warnings are always given).

quotawarnmsg: 0

The maximum amount of messages at which to give a quota warning (if this value is 0, or if the quota is smaller than this amount, then warnings are always given).

reject8bit: 0

If enabled, lmtpd rejects messages with 8-bit characters in the headers.

rfc2046_strict: 0

If enabled, imapd will be strict (per RFC 2046) when matching MIME boundary strings. This means that boundaries containing other boundaries as substrings will be treated as identical. Since enabling this option will break some messages created by Eudora 5.1 (and earlier), it is recommended that it be left disabled unless there is good reason to do otherwise.

rfc3028_strict: 1

If enabled, Sieve will be strict (per RFC 3028) with regards to which headers are allowed to be used in address and envelope tests. This means that only those headers which are defined to contain addresses will be allowed in address tests and only "to" and "from" will be allowed in envelope tests. When disabled, ANY grammatically correct header will be allowed.

rss_feedlist_template: <none>

File containing HTML that will be used as a template for displaying the list of available RSS feeds. A single instance of the variable %RSS_FEEDLIST% should appear in the file, which will be replaced by a nested unordered list of feeds. The toplevel unordered list will be tagged with an id of "feed" (<ul id=’feed’>) which can be used by stylesheet(s) in your template. The dynamically created list of feeds based on the HTML template will be accessible at the "/rss" URL on the server.

rss_feeds: *

A wildmat pattern specifying which mailbox hierarchies should be treated as RSS feeds. Only mailboxes matching the wildmat will have their messages available via RSS. If not set, a default wildmat of "*" (ALL mailboxes) will be used.

rss_maxage: 0

Maximum age (in days) of items to display in an RSS channel. If non-zero, httpd will only display items received within the last rss_maxage days. If set to 0, all available items will be displayed (the default).

rss_maxitems: 0

Maximum number of items to display in an RSS channel. If non-zero, httpd will display no more than the rss_maxitems most recent items. If set to 0, all available items will be displayed (the default).

rss_maxsynopsis: 0

Maximum RSS item synopsis length. If non-zero, httpd will display no more than the first rss_maxsynopsis characters of an item’s synopsis. If set to 0, the entire synopsis will be displayed (the default).

rss_realm: <none>

The realm to present for HTTP authentication of RSS feeds. If not set (the default), the value of the "servername" option will be used.

sasl_auto_transition: 0

If enabled, the SASL library will automatically create authentication secrets when given a plaintext password. See the SASL documentation.

sasl_maximum_layer: 256

Maximum SSF (security strength factor) that the server will allow a client to negotiate.

sasl_minimum_layer: 0

The minimum SSF that the server will allow a client to negotiate. A value of 1 requires integrity protection; any higher value requires some amount of encryption.

sasl_option: 0

Any SASL option can be set by preceding it with "sasl_". This file overrides the SASL configuration file.

sasl_pwcheck_method: <none>

The mechanism used by the server to verify plaintext passwords. Possible values include "auxprop", "saslauthd", and "pwcheck".

search_skipdiacrit: 1

When searching, should diacriticals be stripped from the search terms. The default is "true", a search for "hav" will match "HÃ¥vard". This is not RFC5051 complient, but it backwards compatible, and may be preferred by some sites.

search_whitespace: merge

When searching, how whitespace should be handled. Options are: "skip" (default in 2.3 and earlier series) - where a search for "equi" would match "the quick brown fox". "merge" - the default, where "he qu" would match "the quick brownfox", and "keep", where whitespace must match exactly. The default of "merge" is recommended for most cases - it’s a good compromise which keeps words separate.

Allowed values: skip, merge, keep

seenstate_db: twoskip

The cyrusdb backend to use for the seen state.

Allowed values: flat, berkeley, berkeley-hash, skiplist, twoskip

sendmail: /usr/lib/sendmail

The pathname of the sendmail executable. Sieve invokes sendmail for sending rejections, redirects and vacation responses.

serverlist: <none>

Whitespace separated list of backend server names. Used for finding server with the most available free space for proxying CREATE.

serverlist_select_mode: freespace-most

Server selection mode.
random

(pseudo-)random selection

freespace-most

backend with the most (total) free space (KiB)

freespace-percent-most

backend whose partition has the most free space (%)

freespace-percent-weighted

same as for partition selection, comparing the free space (%) of the least used partition of each backend

freespace-percent-weighted-delta

same as for partition selection, comparing the free space (%) of the least used partition of each backend

Allowed values: random, freespace-most, freespace-percent-most, freespace-percent-weighted, freespace-percent-weighted-delta

serverlist_select_usage_reinit: 0

For a given session, number of operations (e.g. backend selection) for which backend usage data are cached.

serverlist_select_soft_usage_limit: 0

Limit of backend usage (%): if a backend is over that limit, it is automatically excluded from selection mode.

If all backends are over that limit, this feature is not used anymore.

servername: <none>

This is the hostname visible in the greeting messages of the POP, IMAP and LMTP daemons. If it is unset, then the result returned from gethostname(2) is used. This is also the value used by murder clusters to identify the host name. It should be resolvable by DNS to the correct host, and unique within an active cluster. If you are using low level replication (e.g. drbd) then it should be the same on each copy and the DNS name should also be moved to the new master on failover.

serverinfo: on

The server information to display in the greeting and capability responses. Information is displayed as follows:

"off" = no server information in the greeting or capabilities
"min" = servername in the greeting; no server information in the capabilities
"on" = servername and product version in the greeting; product version in the capabilities

Allowed values: off, min, on

sharedprefix: Shared Folders

If using the alternate IMAP namespace, the prefix for the shared namespace. The hierarchy delimiter will be automatically appended.

sieve_allowreferrals: 1

If enabled, timsieved will issue referrals to clients when the user’s scripts reside on a remote server (in a Murder). Otherwise, timsieved will proxy traffic to the remote server.

sieve_extensions: fileinto reject vacation vacation-seconds imapflags
notify envelope relational regex subaddress copy date index imap4flags

Space-separated list of Sieve extensions allowed to be used in sieve scripts, enforced at submission by timsieved(8). Any previously installed script will be unaffected by this option and will continue to execute regardless of the extensions used. This option has no effect on options that are disabled at compile time (e.g., "regex").

Allowed values: fileinto, reject, vacation, vacation-seconds, imapflags, notify, include, envelope, body, relational, regex, subaddress, copy, date, index, imap4flags

sieve_maxscriptsize: 32

Maximum size (in kilobytes) any sieve script can be, enforced at submission by timsieved(8).

sieve_maxscripts: 5

Maximum number of sieve scripts any user may have, enforced at submission by timsieved(8).

sieve_utf8fileinto: 0

If enabled, the sieve engine expects folder names for the fileinto action in scripts to use UTF8 encoding. Otherwise, modified UTF7 encoding should be used.

sieve_sasl_send_unsolicited_capability: 0

If enabled, timsieved will emit a capability response after a successful SASL authentication, per draft-martin-managesieve-12.txt .

sieve_vacation_min_response: 259200 /* 3 days */

Minimum time interval (in seconds) between consecutive vacation responses, per draft-ietf-vacation-seconds.txt .

sieve_vacation_max_response: 7776000 /* 90 days */

Maximum time interval (in seconds) between consecutive vacation responses, per draft-ietf-vacation-seconds.txt .

sievedir: /usr/sieve

If sieveusehomedir is false, this directory is searched for Sieve scripts.

sievenotifier: <none>

Notifyd(8) method to use for "SIEVE" notifications. If not set, "SIEVE" notifications are disabled.

This method is only used when no method is specified in the script.

sieveusehomedir: 0

If enabled, lmtpd will look for Sieve scripts in user’s home directories: ~user/.sieve.

anysievefolder: 0

It must be "yes" in order to permit the autocreation of any INBOX subfolder requested by a sieve filter, through the "fileinto" action. (default = no)

singleinstancestore: 1

If enabled, imapd, lmtpd and nntpd attempt to only write one copy of a message per partition and create hard links, resulting in a potentially large disk savings.

skiplist_always_checkpoint: 1

If enabled, this option forces the skiplist cyrusdb backend to always checkpoint when doing a recovery. This causes slightly more IO, but on the other hand leads to more efficient databases, and the entire file is already "hot".

skiplist_unsafe: 0

If enabled, this option forces the skiplist cyrusdb backend to not sync writes to the disk. Enabling this option is NOT RECOMMENDED.

soft_noauth: 1

If enabled, lmtpd returns temporary failures if the client does not successfully authenticate. Otherwise lmtpd returns permanent failures (causing the mail to bounce immediately).

specialuse_extra: <none>

Whitespace separated list of extra special-use attributes that can be set on a mailbox. RFC 6154 currently lists what special-use attributes can be set. This allows extending that list in the future or adding your own if needed.

specialusealways: 0

If enabled, this option causes LIST and LSUB output to always include the XLIST "special-use" flags

sql_database: <none>

Name of the database which contains the cyrusdb table(s).

sql_engine: <none>

Name of the SQL engine to use.

Allowed values: mysql, pgsql, sqlite

sql_hostnames: <empty string>

Comma separated list of SQL servers (in host[:port] format).

sql_passwd: <none>

Password to use for authentication to the SQL server.

sql_user: <none>

Username to use for authentication to the SQL server.

sql_usessl: 0

If enabled, a secure connection will be made to the SQL server.

srvtab: <empty string>

The pathname of srvtab file containing the server’s private key. This option is passed to the SASL library and overrides its default setting.

submitservers: <none>

A list of users and groups that are allowed to resolve "urlauth=submit+" IMAP URLs, separated by spaces. Any user listed in this will be allowed to fetch the contents of any valid "urlauth=submit+" IMAP URL: use with caution.

subscription_db: flat

The cyrusdb backend to use for the subscriptions list.

Allowed values: flat, berkeley, berkeley-hash, skiplist, twoskip

suppress_capabilities: <none>

Suppress the named capabilities from any capability response. Use the exact case as it appears in the response, e.g. "suppress_capabilities: ESEARCH QRESYNC WITHIN XLIST LIST-EXTENDED" if you have a murder with 2.3.x backends and don’t want clients being confused by new capabilities that some backends don’t support.

statuscache: 0

Enable/disable the imap status cache.

statuscache_db: twoskip

The cyrusdb backend to use for the imap status cache.

Allowed values: berkeley, berkeley-nosync, berkeley-hash, berkeley-hash-nosync, skiplist, sql, twoskip

statuscache_db_path: <none>

The absolute path to the statuscache db file. If not specified, will be confdir/statuscache.db

sync_authname: <none>

The authentication name to use when authenticating to a sync server. Prefix with a channel name to only apply for that channel

sync_host: <none>

Name of the host (replica running sync_server(8)) to which replication actions will be sent by sync_client(8). Prefix with a channel name to only apply for that channel

sync_log: 0

Enable replication action logging by lmtpd(8), imapd(8), pop3d(8), and nntpd(8). The log {configdirectory}/sync/log is used by sync_client(8) for "rolling" replication.

sync_log_chain: 0

Enable replication action logging by sync_server as well, allowing chaining of replicas. Use this on ’B’ for A => B => C replication layout

sync_log_channels: <none>

If specified, log all events to multiple log files in directories specified by each "channel". To run these log files, you need to pass the -n option to sync_client -r with the channel name. Use this for a mesh style replication layout - every machine replicating to every other machine. You can use "" (the two-character string U+22 U+22) to mean the default sync channel.

sync_log_unsuppressable_channels: squatter

If specified, the named channels are exempt from the effect of setting sync_log_chain:off, i.e. they are always logged to by the sync_server process. This is only really useful to allow rolling search indexing on a replica.

sync_password: <none>

The default password to use when authenticating to a sync server. Prefix with a channel name to only apply for that channel

sync_port: csync

Name of the service (or port number) of the replication service on replica host. The default is "csync" which is usally port 2005, but any service name or numeric port can be specified. Prefix with a channel name to only apply for that channel

sync_realm: <none>

The authentication realm to use when authenticating to a sync server. Prefix with a channel name to only apply for that channel

sync_repeat_interval: 1

Minimum interval (in seconds) between replication runs in rolling replication mode. If a replication run takes longer than this time, we repeat immediately. Prefix with a channel name to only apply for that channel

sync_shutdown_file: <none>

Simple latch used to tell sync_client(8) that it should shut down at the next opportunity. Safer than sending signals to running processes. Prefix with a channel name to only apply for that channel

sync_timeout: 1800

Number of seconds to wait for a response before returning a timeout failure when talking to a replication peer (client or server).

syslog_prefix: <none>

String to be prepended to the process name in syslog entries.

syslog_facility: <none>

Configure a syslog facility. The default is whatever is compiled in. Allowed values are: DAEMON, MAIL, NEWS, USER, and LOCAL0 through to LOCAL7

tcp_keepalive: 0

Enable keepalive on TCP connections

tcp_keepalive_cnt: 0

Number of TCP keepalive probes to send before declaring the connection dead (0 == system default)

tcp_keepalive_idle: 0

Number of seconds a connection must be idle before keepalive probes are sent (0 == system default)

tcp_keepalive_intvl: 0

Number of seconds between keepalive probes (0 == system default)

temp_path: /tmp

The pathname to store temporary files in

timeout: 30

The length of the IMAP server’s inactivity autologout timer, in minutes. The minimum value is 30, the default.

tls_ca_file: DEFAULT

Deprecated in favor of tls_client_ca_file.

tls_ca_path: DEFAULT

Deprecated in favor of tls_client_ca_dir.

tlscache_db: DEFAULT

Deprecated in favor of tls_sessions_db.

tlscache_db_path: DEFAULT

Deprecated in favor of tls_sessions_db_path.

tls_cert_file: DEFAULT

Deprecated in favor of tls_server_cert.

tls_cipher_list: DEFAULT

Deprecated in favor of tls_ciphers.

tls_ciphers: DEFAULT

The list of SSL/TLS ciphers to allow. The format of the string is described in ciphers(1).

tls_client_ca_dir: <none>

Path to a directory containing the CA certificates used to verify client SSL certificates used for authentication.

tls_client_ca_file: <none>

Path to a file containing the CA certificate(s) used to verify client SSL certificates used for authentication.

tls_client_cert: <none>

File containing the certificate presented to a server for authentication during STARTTLS. A value of "disabled" will disable this server’s use of certificate-based authentication.

tls_client_certs: optional

Disable ("off"), allow ("optional", default) or require ("require") the use of SSL certificates by clients to authenticate themselves.

Allowed values: off, optional, require

tls_client_key: <none>

File containing the private key belonging to the tls_client_cert certificate. A value of "disabled" will disable this server’s use of certificate-based authentication.

tls_eccurve: prime256v1

The elliptic curve used for ECDHE. Default is NIST Suite B prime256. See ’openssl ecparam -list_curves’ for possible values.

tls_key_file: DEFAULT

Deprecated in favor of tls_server_key.

tls_required: 0

If enabled, require a TLS/SSL encryption layer to be negotiated prior to ANY authentication mechanisms being advertised or allowed.

tls_prefer_server_ciphers: 0

Prefer the ciphers on the server side instead of client side.

tls_server_ca_dir: <none>

Path to a directory with CA certificates used to verify certificates offered when this server connects to other servers. This directory must have filenames with the hashed value of the certificates (see openssl(1)).

tls_server_ca_file: <none>

Path to a file containing CA certificates used to verify certificates offered when this server connects to other servers.

tls_server_cert: <none>

File containing the certificate presented to clients.

tls_server_key: <none>

File containing the private key belonging to the certificate in tls_server_cert.

tls_sessions_db: twoskip

The cyrusdb backend to use for the TLS cache.

Allowed values: berkeley, berkeley-nosync, berkeley-hash, berkeley-hash-nosync, skiplist, sql, twoskip

tls_sessions_db_path: <none>

The absolute path to the TLS sessions db file. If not specified, will be confdir/tls_sessions.db

tls_session_timeout: 1440

The length of time (in minutes) that a TLS session will be cached for later reuse. The maximum value is 1440 (24 hours), the default. A value of 0 will disable session caching.

tls_versions: tls1_0 tls1_1 tls1_2

A list of SSL/TLS versions to not disable. Cyrus IMAP SSL/TLS starts with all protocols, and substracts protocols not in this list. Newer versions of SSL/TLS will need to be added here to allow them to get disabled.

umask: 077

The umask value used by various Cyrus IMAP programs.

userdeny_db: flat

The cyrusdb backend to use for the user access list.

Allowed values: flat, berkeley, berkeley-hash, skiplist, sql, twoskip

userdeny_db_path: <none>

The absolute path to the userdeny db file. If not specified, will be confdir/user_deny.db

username_tolower: 1

Convert usernames to all lowercase before login/authentication. This is useful with authentication backends which ignore case during username lookups (such as LDAP).

userprefix: Other Users

If using the alternate IMAP namespace, the prefix for the other users namespace. The hierarchy delimiter will be automatically appended.

unix_group_enable: 1

Should we look up groups when using auth_unix (disable this if you are not using groups in ACLs for your IMAP server, and you are using auth_unix with a backend (such as LDAP) that can make getgrent() calls very slow)

unixhierarchysep: 0

Use the UNIX separator character ’/’ for delimiting levels of mailbox hierarchy. Turn off to use the netnews separator character ’.’. Note that with the newnews separator, no dots may occur in mailbox names.

virtdomains: off

Enable virtual domain support. If enabled, the user’s domain will be determined by splitting a fully qualified userid at the last ’@’ or ’%’ symbol. If the userid is unqualified, and the virtdomains option is set to "on", then the domain will be determined by doing a reverse lookup on the IP address of the incoming network interface, otherwise the user is assumed to be in the default domain (if set).

Allowed values: off, userid, on

lmtp_catchall_mailbox: <none>

Mail sent to mailboxes which do not exist, will be delivered to this user. NOTE: This must be an existing local user name with an INBOX, NOT an email address!

zoneinfo_db: twoskip

The cyrusdb backend to use for zoneinfo.

Allowed values: flat, berkeley, berkeley-hash, skiplist, twoskip

zoneinfo_db_path: <none>

The absolute path to the zoneinfo db file. If not specified, will be confdir/zoneinfo.db

SEE ALSO

imapd(8), pop3d(8), nntpd(8), lmtpd(8), httpd(8), timsieved(8), idled(8), notifyd(8), deliver(8), master(8), ciphers(1)


cyrus-imapd-2.5.10/doc/man/sync_reset.8.html0000644000175000017500000000530013001246662015505 00000000000000 SYNC_RESET

SYNC_RESET

NAME
SYNOPSIS
DESCRIPTION
OPTIONS
FILES
SEE ALSO
AUTHORS

NAME

sync_reset - Account reset utility. DANGER.

SYNOPSIS

sync_reset [ -C config-file ] [ -v ] [ -f ]

DESCRIPTION

Sync_reset is a small utility program to destroy user accounts on a system. The only safeguard which is in place is the obligary force option.

OPTIONS

-C config-file

Read configuration options from config-file.

-v

Verbose mode.

-f

Force operation. Without this flag sync_reset just bails out with an error. Principally here to try and prevent accidents with command autorepeat.

FILES

/etc/imapd.conf

SEE ALSO

sync_client(8)

AUTHORS

David Carter (dpc22@cam.ac.uk), Ken Murchison (ken@oceana.com)


cyrus-imapd-2.5.10/doc/man/ctl_deliver.8.html0000644000175000017500000000524713001246654015636 00000000000000 CTL_DELIVER

CTL_DELIVER

NAME
SYNOPSIS
DESCRIPTION
OPTIONS
FILES
SEE ALSO

NAME

ctl_deliver - perform operations on the duplicate delivery database

SYNOPSIS

ctl_deliver [ -C config-file ] -d [ -f filename ]

DESCRIPTION

Ctl_deliver is used to perform various administrative operations on the duplicate delivery database.

Ctl_deliver reads its configuration options out of the imapd.conf(5) file unless specified otherwise by -C.

OPTIONS

-C config-file

Read configuration options from config-file.

-d

Dump the contents of the database to standard output in a portable flat-text format.

-f filename

Use the database specified by filename instead of the default (configdirectory/deliver.db).

FILES

/etc/imapd.conf

SEE ALSO

imapd.conf(5), master(8)


cyrus-imapd-2.5.10/doc/feedback.html0000644000175000017500000000420113001236020014114 00000000000000 Sending Feedback on the Cyrus IMAP Server

Sending Feedback on the Cyrus IMAP Server

Feedback on and fixes for the software or on the document may be sent to cyrus-bugs+@andrew.cmu.edu. Unfortunately, we cannot guarantee a response but we'll try the best we can. As usual, a high quality and complete message helps us tremendously.

If you submit a patch, please send unified diffs (-u) if your diff program supports them, or context diffs (-c) if it doesn't. Plain diffs are very difficult to evaluate. GNU diff can do this.

When reporting problems, be sure to include the relevant information. For example, you must include:

  • the version of imapd
  • the version of libsasl
  • your system type (uname -a often provides the right information).
You should also include:
  • the options you passed to ./configure
  • the errors from make (if any)
  • the config.status file generated by configure

NOTE: If you are able to connect to the imap server, all of this information can be gathered by using the version command in cyradm. If you cannot use cyradm because you are having perl problems, you can connect using imtest and then run the following IMAP command:

  • a ID NIL

The info-cyrus@andrew.cmu.edu mailing list exists for the discussion of this server and other Cyrus software; more information is available in the mailing-list document. You may get faster/more responses by posting to this list instead of to cyrus-bugs, as there are more readers here.


last modified: $Date: 2010/01/06 17:01:29 $
Return to the Cyrus IMAP Server Home Page cyrus-imapd-2.5.10/doc/altnamespace.html0000644000175000017500000001075013001236020015033 00000000000000 Cyrus IMAP Server: Altername Namespace

Cyrus IMAP Server: Alternate Namespace

This document describes the alternatives to the standard mailbox presentation method. These alternatives may be used together or independently.

The namespace options do NOT change the rules governing the behavior of mailboxes (as described in overview.html) or how mailboxes are stored on the filesystem. The mailboxes are ALWAYS stored using the netnews convention and internal namespace. When configured to use one (or both) of the options below, the server simply translates mailbox names between the internal names and the external names when used by the client in the IMAP protocol and in Sieve scripts.

This design allows the namespace to be changed at runtime (even on a running server) without having to reconfigure the server. This also means that one mailstore can support multiple namespaces if configured correctly.

NOTE: If you are upgrading an existing server which uses timsieved to manage Sieve scripts and choose to enable one of the namespace options, you should run the script "tools/translatesieve" after configuring the namespace option(s). This script will translate the folder names in fileinto actions.

Alternate Mailbox Namespace

The alternate namespace allows a user's personal mailboxes to appear as if they reside at the same level as that user's INBOX as opposed to children of it. For example, if user "bovik" had a personal "work" mailbox, it would appear to user "bovik" as "work" instead of "INBOX.work" as it would in the standard namespace.

This configuration requires that a special prefix be used for shared folders (to distinguish them from personal folders) and for accessing other users' folders. By default, the prefix for shared folders is "Shared Folders" and the prefix for other users folders is "Other Users". For example, a shared folder "foo" in the standard namespace would be presented as "Shared Folders.foo" in the alternate namespace.

NOTE: All tools for administering the server, including admins using cyradm, always use the internal namespace.

Configuring the Alternate Namespace

To use the alternate namespace, turn on the altnamespace option in /etc/imapd.conf. The prefixes used for shared folders and other users folders can be changed from the defaults by setting the sharedprefix and userprefix options respectively.

UNIX Hierarchy Convention

The UNIX hierarchy convention uses the traditional UNIX separator character ("/") to delimit levels of the mailbox hierarchy instead of the netnews character ("."). For example, if user "bovik" had a personal "work" mailbox, it would appear to user "bovik" as "INBOX/work" in the standard namespace.

When the UNIX hierarchy convention is used, the "." character MAY be used in mailbox names, including user names. In order to maintain backwards compatibility with the internal namespace, all "." characters are translated to a benign character (currently "^") before any data is stored to disk. For example, if user "elmer.fudd" had a personal "rabbit.holes" mailbox, it would be stored as "user.elmer^fud.rabbit^holes" in the internal namespace. It is important to remember this phenomenon if/when reverting back to the netnews hierarchy convention.

Configuring the UNIX Hierarchy Convention

To use the UNIX hierarchy separator, turn on the unixhierarchysep option in /etc/imapd.conf.


Return to the Cyrus IMAP Server Home Page cyrus-imapd-2.5.10/doc/index.html0000644000175000017500000000465513001236020013514 00000000000000 Cyrus IMAP Server v2.5 Documentation

Cyrus IMAP Server, version 2.5

IMAP (Internet Message Access Protocol) is an Internet standards-track protocol for accessing messages (mail, bboards, news, etc). The Cyrus IMAP server differs from other IMAP server implementations in that it is generally intended to be run on sealed servers, where normal users are not permitted to log in. The mailbox database is stored in parts of the filesystem that are private to the Cyrus IMAP system. All user access to messages is through the IMAP, POP3, KPOP or NNTP protocols.

The private mailbox database design gives the server large advantages in efficiency, scalability, and administratability. Multiple concurrent read/write connections to the same mailbox are permitted. The server supports access control lists on mailboxes and storage quotas on mailbox hierarchies.

The Cyrus project is the implementation of IMAP servers by the Carnegie Mellon University Computing Services Department. Over the next few months, we will be releasing components of this server, which will provide better mail security and easier mail administration.

The Cyrus IMAP Server Distribution

Cyrus IMAP Server distribution

Documentation


Go to the Project Cyrus homepage.
cyrus-imapd-2.5.10/doc/internal/0000755000175000017500000000000013001236020013401 500000000000000cyrus-imapd-2.5.10/doc/internal/var_directory_structure.html0000644000175000017500000000465112772415051021232 00000000000000 Cyrus IMAP Server: var directory structure

Cyrus IMAP Server: var directory structure

Directory structure under /var/spool/imap

stage./
  Normal staging directory

sync./
  Staging directory for replication system
  Includes
    sync./locks/*

  which are lock files for each user on the system to prevent two
  replication runs from trying to update the same account at the same time
  (nothing disasterous should happen even without this lock, but the second
  job in will get a bit confused if the target end changes under its feet,
  and will probably drop back to a recovery mode.

user/
  Familiar user.userid space.

Directory structure under /var/imap

Complete list:

  drwxr-xr-x    2 cyrus    cyrus         232 Sep  7 08:21 db
  drwxr-x---    2 cyrus    cyrus         112 Sep  7 19:51 db.backup1
  drwxr-x---    2 cyrus    cyrus         112 Sep  7 19:21 db.backup2
  -rw-r-----    1 cyrus    cyrus    20799488 Sep  7 19:51 deliver.db
  drwxr-xr-x    2 cyrus    cyrus          48 Sep  7 10:16 log
  -rw-r-----    1 cyrus    cyrus     1995000 Sep  7 19:38 mailboxes.db
  -rw-r--r--    1 cyrus    cyrus          10 Jun  2 10:08 master_machine
  -rw-r--r--    1 cyrus    cyrus          71 Sep  7 08:21 master_uuid
  drwxr-xr-x    2 cyrus    cyrus          48 Jun  2 10:08 msg
  drwxr-xr-x    2 cyrus    cyrus        1872 Sep  7 19:55 proc
  drwxr-xr-x   28 cyrus    cyrus         672 Jun  2 10:08 quota
  drwxr-xr-x    2 cyrus    cyrus         224 Sep  7 08:21 socket
  drwxr-xr-x    2 cyrus    cyrus          72 Sep  7 10:19 sync
  drwxr-xr-x   28 cyrus    cyrus         672 Jun  2 10:08 user

Most of that will be familiar. New entries are:

master_machine
  Defines machine number in replication cluster. Used as sanity check
  aginst master_uuid file. Sample content:

    machine=1

master_uuid
  Full information about UUID schema in use. See ./uuid for details.
  Sample content:

     schema=1
     machine=1
     timestamp_generation=0
     master_start_time=1062919294

sync/current
  Transaction log from IMAP, POP and LMTP daemons, typically feed into
  sync_client running as asynchronous replication engine.

  Rotated to be sync/current-<pid> by asychronous runner.
cyrus-imapd-2.5.10/doc/internal/bytecode.html0000644000175000017500000001351512772415051016033 00000000000000 Cyrus IMAP Server: Sieve Bytecode

Cyrus IMAP Server: Sieve Bytecode

Motivation

The motivation behind moving to Sieve Bytecode is severalfold:

  • Parsing a script at each execution is expensive computationally
  • Lex/Yacc are costly in terms of memory usage and executable size, whereas a bytecode parser is much lighter weight.
  • Using bytecode can simplify the code for the execution phase, which is far more frequently occuring than the upload/compile phase.
  • Rewriting a significant part of the sieve execution framework forces a decent amount of refactoring on what has traditionally been a problematic part of the Cyrus code base. There is still work to do in this area.

Overall Bytecode Format

In the final bytecode, each opcode/parameter is aligned on a 4-byte boundary. Strings are NUL-terminated (and padded to a 4-byte boundary as needed).

Ideally, we'd have all integers in network byte order, so as to make the scripts portable, but version 1 does not have this feature.

At the beginning of the file, there is a magic header to identify it as a bytecode file, and a 4 byte version number. Immediately following the version number are the opcodes that relate to the script.

Generation

A Sieve Bytecode file is generated in three "passes":

  • Generate a parse tree using lex/yacc from the sieve script. (addr.y, addr-lex.l, sieve.y, sieve-lex.l).
  • Serialize the parse tree into an intermediate form, where strings are held separate from the rest of the representation. (bc_generate.c)
  • Serialize the intermediate form into the final bytecode. (bc_emit.c)

The intermediate form is an array of bytecode_t unions, with strings located elsewhere in memory. The entry point is bc_generate: sieve_generate_bytecode() / bc_action_generate().

bc_action_generate traverses the commandlist_t tree and emits opcodes in sequence.

Simple actions (STOP, DISCARD, KEEP, MARK, UNMARK) have no arguments, and processing proceeds directly.

More complicated options have a sequence of arguments that are emitted following the initial opcode.

For example, single argument commands such as REJECT, FILEINTO, REDIRECT are followed by a bytecode_t for a string's length, and then a bytecode_t which contains a pointer to a string.

Commands such as ADDFLAG, SETFLAG, REMOVEFLAG, which take a stringlist, format the stringlist as (using bc_stringlist_generate):

{Number of Strings}{String 1 Length}{String 1 Ptr}{String 2 Length}....

So their resulting final output would appear as:

{Opcode}{...stringlist from above...}

Even more complicated action opcodes (vacation, notify) etc, may take a sequence of integer values (flags), stringlists, or individual strings. These are more specifically documented in the code.

This leaves us with the IF keyword (and tests). In the pass 1 form, IF appears as the following bytecode_t structures:

{IF opcode}
{Beginning of the then block}
{End of the then block / beginning of the else block}
{End of the else block / -1 for no else block}
{....test opcodes....}
{....'then' action opcodes....}
{....'else' action opcodes.... [optional]}

Test opcodes are generated by the bc_test_generate function, which is very similar to bc_action_generate (tests without arguments are just opcodes, tests with arguments have them serialized into place directly following the original opcode). Test lists are represented as {number of tests}{address of the end of the list}{test 1}{test 2}.

In the third pass, strings are serialized into place, and if statement jumps are resolved to actual addresses within the file This is done in bc_emit: sieve_emit_bytecode / bc_action_emit.

This results in a totally serialized representation, using byte offsets within the file instead of indexes into the array of bytecode_t's. In addition to the manipulations that are necessary to do this, there are several other changes in format.

Two new opcodes exist: NULL and JUMP (which performs an unconditional jump).

Stringlists and testslists now include a precomputed byte length of the entire list, so it can be skipped over as needed.

So as to be executable without a stack, the IF statements are designed as follows:

{IF opcode}
{....test block....}
{JUMP (location of false condition) }
{....then block....}
{(if there is an else) JUMP (end of else block)}
{(if there is an else) .... else block ....}

The idea being that if the test is true, the instruction pointer should move to the then block, otherwise the else block will be hit automatically (due to the unconditional jump).

Evaluation

The evaluation routines are in bc_eval.c, the basic idea is that we can simply mmap the bytecode, run straight through it, and complete the processing without maintaining a stack.

The processing is done by overlaying a bytecode_input_t array over the mmap. This allows addressing elements within the file to be simple. There is an instruction pointer which is incremented as each action is performed, or as actions/tests are skipped.

Of special note in bc_eval.c is the unwrap_string function which will pull a string out of the bytecode, and return the instruction pointer at the end of the string.

Other things to consider

The Bytecode can be extended to contain other extensions. This could require regeneration of older scripts. In many cases this can be avoided by putting the new commands at the end of the proper enum in bytecode.h

cyrus-imapd-2.5.10/doc/internal/index.html0000644000175000017500000000303512772415051015340 00000000000000 Cyrus IMAP Server: Cyrus Internals

Cyrus IMAP Server: Cyrus Internals

These documents are intended for persons interested in contributing to the Cyrus IMAP development effort, or for those interested in lower- level details about how Cyrus is implemented.

The Cyrus IMAP Server Distribution

Cyrus IMAP Server distribution

Cyrus Internals

cyrus-imapd-2.5.10/doc/internal/mailbox-api.html0000644000175000017500000002773313001236020016425 00000000000000 Mailbox API

Mailbox API

Intro

The Mailbox API is implemented in imap/mailbox.h and imap/mailbox.c. It wraps the data structures of the cyrus.header, cyrus.index and cyrus.cache files in a psuedo-object-oriented way, allowing easy changes to the mailbox while keeping the internal cached data structures consistent.

Opening and closing

struct mailbox *mailbox = NULL;
int r;
const char *mboxname = "user.brong";

r = mailbox_open_iwl(mboxname, &mailbox);
// or
r = mailbox_open_irl(mboxname, &mailbox);
// or
r = mailbox_open_exlusive(mboxname, &mailbox);
if (r) return r;

do_stuff(mailbox);

mailbox_close(&mailbox);

It is always necessary to obtain an index lock when opening a mailbox, because the index header read must be consistent. The locks are as follows:

FunctionNamelockIndex Lock
mailbox_open_iwlSharedExclusive
mailbox_open_irlSharedShared
mailbox_open_exclusiveExclusiveExclusive

It should never be necessary to call mailbox_open_exclusive, but it's included for completeness. Use mailbox_open_iwl if you expect to need to write to the index (or even if you're not sure) and mailbox_open_irl when you know you're only reading from the file and wish to allow other readers to work concurrently.

Many actions are delayed until the mailbox is closed, or even until the last mailbox is closed for things that require an exclusive namelock to perform like deletion or repack. See below under "delayed actions" for more detail.

To avoid opening the same file multiple times, the mailbox API refcounts open mailboxes. If you open the same mailbox again (i.e. a URL fetch or status command on the currently select mailbox) then the same mailbox will be returned. It must be unlocked (see below or the open command will return IMAP_MAILBOX_LOCKED). The matching close will reduce the refcount, and only the final close will do the cleanup actions.

Locking and unlocking

You can keep a mailbox "open", maintaining the namelock, while releasing the index lock to allow other processes to make changes to the mailbox. By holding the namelock, you know that record numbers won't change, and the underlying message files won't be deleted.

mailbox_close will call mailbox_unlock_index if the index is still locked, so it is not neccessary to explicitly unlock the index before closing.

r = mailbox_unlock_index(mailbox, NULL);

// sleep on user input...

r = mailbox_lock_index(mailbox, LOCK_SHARED);
// or
r = mailbox_lock_index(mailbox, LOCK_EXCLUSIVE);

For example, mailbox_unlock_index and mailbox_lock_index are used extensively by the index module, allowing an imap client to maintain a long lived connection selected to a mailbox and know that messages won't magically disappear from under it - yet at the same time allow new mail delivery to happen or other imap connections to query the mailbox.

If you have built an accurate statuscache item for the locked mailbox, you can pass this as the second parameter to mailbox_index_unlock. If there have been any changes, mailbox_index_unlock will invalidated the statuscache. If you give it the new value, then it will store that value instead. For example:

struct statusdata sdata;
index_status(state, &sdata);
/* RECENT is zero for everyone else because we wrote a new
 * recentuid! */
sdata.recent = 0;
mailbox_unlock_index(state->mailbox, &sdata);

See "delayed actions" below for delayed actions performed during an unlock.

Creating, renaming and deleting

WARNING: These functions only change the mailbox files on disk. They don't update the mailboxes.db records or contact murder servers. In most cases you are probably looking for the mboxlist_ functions instead.

Creating a mailbox is somewhat longwinded - as there are many optional parameters.

int mailbox_create(const char *name, const char *part, const char *acl,
                   const char *uniqueid, int options, unsigned uidvalidity,
                   struct mailbox **mailboxptr);

Most interesting to note is that on success, mailboxptr will contain the same mailbox that mailbox_open_exclusive above would have returned, with an exclusive namelock and an exclusive index lock. This allows you to perform other consistency operations after creating the mailbox with a full guarantee that no other process will even be able to know of the mailbox's existence! You can still roll-back by deleting the mailbox and the next process will get the namelock and see no mailbox with that name.

int mailbox_rename_copy(struct mailbox *oldmailbox,
                        const char *newname, const char *newpart,
                        const char *userid, int ignorequota,
                        struct mailbox **newmailboxptr);

Very similar to mailbox_create - the new mailbox is created with an exclusive name lock and returned. The old mailbox must be passed in with an exclusive index lock but is fine with a shared namelock, as it will be passed to mailbox_delete.

int mailbox_delete(struct mailbox **mailboxptr);

Just like mailbox_close above, this closes the mailbox. Before it does so, it sets the OPT_MAILBOX_DELETED option flag in the index header. The interesting work is actualy done in mailbox_close. See below under "delayed actions".

mailbox_delete requires an exclusive index lock, but can complete quite happily with only a shared namelock.

Reading and writing records

Ok - so you have a mailbox, it's opened, and the index is locked. Time to start reading and writing some records!

At the mailbox level there is no concept of "message numbers" from imap, only "record numbers". The canonical variable name to refer to record numbers is recno. All records are read and written using struct index_record values.

Here at the API definitions used for reading and writing:

int mailbox_read_index_record(struct mailbox *mailbox,
                              uint32_t recno,
                              struct index_record *record);
int mailbox_rewrite_index_record(struct mailbox *mailbox,
                                 struct index_record *record);
int mailbox_append_index_record(struct mailbox *mailbox,
                                struct index_record *record);
int mailbox_commit(mailbox);

An example of iterating through a mailbox

uint32_t recno;
struct index_record record;
int make_changes;

for (recno = 1; recno <= mailbox->i.num_records; recno++) {
    if (mailbox_read_index_record(mailbox, recno, &record))
        fatal("invalid record", EC_SOFTWARE); // or return an error
    if (record.system_flags & FLAG_EXPUNGED)
        continue; // skip expunged records
    make_changes = do_stuff(mailbox, &record);
    if (make_changes)
        mailbox_rewrite_index_record(mailbox, &record);
}

NOTE: mailbox_rewrite_index_record doesn't need a recno, as that's cached inside the index_record struct.

NOTE: You need an exclusively locked index to use rewrite or append, but only a shared index lock to use read.

There are a range of consistency checks done to ensure that a rewrite doesn't violate IMAP semantics (an expunged message can never be unexpunged, UIDs can't change, etc) and the internal tracking counts and quota data are updated as well. They will be committed at unlock time, see "delayed actions"

If you don't set the record.silent field to a true value before rewriting or appending, the record.modseq and record.last_updated values will be changed. This allows condstore to work correctly.

Appending

To append a record, the file must have already been copied into place (XXX - plan to move to a stage based system where the mailbox API handles the staging, but that's not finished yet) and been parsed into the record struct. The UID must be set already, and must be greater than the UID of any existing record in the mailbox. There are a range of consistency checks done.

The internal consistency counts are updated by append as well.

Committing

When you have finished making any changes, you need to "commit". This will write the updated values for any index header fields, rewite the cyrus.header file if needed and fsync all changes to disk.

It is a fatal error to unlock (or close) a mailbox that has had changes without committing, as it can leave the mailbox in a corrupted state.

Cache records

Cache records are accessed through record.crec which is not filled by read_index_record. The cache file is only read and mapped into memory as needed, so you if you want to access cache records, the basic API is as follows:
int mailbox_cacherecord(struct mailbox *mailbox,
                        struct index_record *record);
const char *cacheitem_base(struct index_record *record, int field);
unsigned cacheitem_size(struct index_record *record, int field);
struct buf *cacheitem_buf(struct index_record *record, int field);

You must always call mailbox_cacherecord on a record before trying to access any of the cache items. "field" above is the individual field (there are 10) in the cache record. There's more information on those fields in the mailbox internal format documentation.

for (recno = 1; recno <= mailbox->i.num_records; recno++) {
    if (mailbox_read_index_record(mailbox, recno, &record))
        fatal("invalid record", EC_SOFTWARE); // or return an error
    if (record.system_flags & FLAG_EXPUNGED)
        continue; // skip expunged records
    if (mailbox_cacherecord(mailbox, &record))
        fatal("failed to read cache", EC_SOFTWARE);
    ...
    envelope_length = cacheitem_size(&record, CACHE_ENVELOPE);
}

See imap/mailbox.h for the full list of constants.

Delayed Actions

Here's the bit you've been waiting for! What happens during unlock and close

first, unlock

Anything that makes any changes sets the mailbox->has_changed flag. If this is set, then before the index gets unlocked:

  • the updatenotifier (idle) is called
  • sync_log_mailbox (replication) gets called
  • the statuscache value gets erased (or replaced if you passed in an updated value).

then: close

next the index is unlocked (see above)

third, any "unlink" commands scheduled for email files are run. These can't be done until after the mailbox_commit to ensure consistency - the file isn't deleted until the record is written as unlinked! But we save the unlink until now so that other tasks aren't waiting for the index lock while the unlinks run. Unlink is expensive in IO and time.

finally we check for MAILBOX_NEEDS_REPACK or MAILBOX_DELETED option flags. If either is sets, then we make a non-blocking attempt to get an exclusive namelock. If the non-blocking attempt fails, then another process has the mailbox open, so save the cleanup for them! If it succeeds, then go ahead with either mailbox_delete_cleanup or mailbox_index_repack as appropriate.

After this it's just a matter of releasing malloc'd memory and finally releasing the name lock.

cyrus-imapd-2.5.10/doc/internal/mailbox-format.html0000644000175000017500000005073013001236020017135 00000000000000 Mailbox File Formats

Mailbox File Formats

Intro

This documentation refers to the "version 12" cyrus index format and associated mailbox files.

No external tools should make use of this information. The only supported method of access to the mail store is through the standard interfaces: IMAP, POP, NNTP, LMTP, etc.

A cyrus mailbox is a directory in the filesystem. It contains the following files:

  • zero or more message files
  • the cyrus.header metadata file
  • the cyrus.index metadata file
  • the cyrus.cache metadata file
  • zero or one cyrus.squat search indexes
  • zero or more subdirectories

With "split metadata" configuration, the mailbox may actually be split between multiple disks, with the files being in the same relative directory on the meta disk. See the imapd.conf option metapartition_files for more information

Message Files

The message files are named by their UID, followed by a ".", so UID 423 would be named "423.". They are stored in wire-format: lines are terminated by CRLF and binary data is not allowed.

cyrus.header

This file contains mailbox-wide information that does not change often. Its format:

<Mailbox Header Magic String>
<Quota Root>\t<Mailbox Unique ID String>\n
<Space-separated list of user flags>\n
<Mailbox ACL>\n

The Mailbox Unique ID String is used for non-owner per-user \Seen flags so they remain with the mailbox during renames, and also by the replication subsystem to detect mailbox renames.

The ACL is a copy of the value stored in mailboxes.db, and isn't actually used.

Locking Considerations

The cyrus.index file must be locked in exclusive mode while making changes to the cyrus.header file to ensure consistency. All changes are made by rewriting the entire file and renaming the new version into place.

cyrus.cache

The cyrus.cache file is a pure cache of information that's also present in the message files. It exists to make ENVELOPE and specific header fetches more efficient, as well as to assist with searches and sorts.

If a cyrus.cache file is missing or corrupted, it can be re-generated by running a reconstruct on the mailbox.

The format is 10 individual records each prefixed with a 32 bit length value in network byte order. The offset of each message's cache record is stored in the cyrus.index file (documented below). The records in a cyrus.cache file are of variable length, depending on the contents of the associated message.

The first 4 bytes of the cyrus.cache file are a "generation number" which must match the first 4 bytes of the associated cyrus.index file. In the past this was used to track consistency between the files, but the name locking scheme and per-record CRC check in cyrus 2.4 and above means this is just a backup consistency check rather than an essential format feature.

+------------------------------------------------------------------------+
|Gen # (32bits)|Size 1 (32bits)|Data 1                                   |
+------------------------------------------------------------------------+
|           |Size 2 (32bits)|Data 2            |Size 3 (32bits)| Data 3  |
+------------------------------------------------------------------------+
| .....                                                                  |
+------------------------------------------------------------------------+

While there are occasional changes to the cache format, this information is NOT stored in the cyrus.cache file. Instead, there is a "cache_version" field in the cyrus.index record, so multiple different versions of cache data may exist in the same cache file.

The order of fields per record in the cache file is as follows: (keep in mind that they are all preceeded by a 4 byte network byte order size).

Envelope Response
Raw IMAP response for a request for the envelope.
Bodystructure Response
Raw IMAP response for a request for the bodystructure.
Body Response
Raw IMAP response for an (old style) request for the body.
Binary Bodystructure

Offsets into the message file to pull out various body parts. Because of the nature of MIME parts, this is somewhat recursive.

This looks like the following (starting the octet following the cache field size). All of the fields are bit32s.

  [
   [Number of message parts+1 for the rfc822 header if present]
   [
    [Offset in the message file of the header of this part]
    [Size (octets) of the header of this part]
    [Offset in the message file of the content of this part]
    [Size (octets) of the content of this part]
    [Encoding Type of this part]
   ]
      (repeat for each part as well as once for the headers)
   [zero *or* number of sub-parts in the case of a multipart.
    if nonzero, this is a recursion into the top structure]
      (repeat for each part)
  ]

Note if this is not a message/rfc822, than the values for the sizes of the part 0 are -1 (to indicate that it doesn't exist). Sub-parts are not possible for a part 0, so they aren't included when finding recursive entries.

The offset and size info for both the mime header and content part are useful in order to do fast indexing on the appropriate parts of the message file when a client does a FETCH request for BODY[HEADER], or BODY[2.MIME].

Note that the top level RFC822 headers are a treated as a separate part from their body text ("0" or "HEADER").

In the case of a multipart/alternative, the content size & offset refers to the size of the entire mime part.

A very simple message (with a single text/plain part) would therefore look like:

  [[2][rfc822 header][text/plain body part info][0]]

A simple multipart/alternative message might look like:

  [[3][rfc822 header][text/plain message part info]
      [second message part info][0][0]]

A message with an attachment that has two subparts:

  [[3][rfc822 header info][rfc822 first body part info][attachment info][0][
	[3][NIL header info][sub part 1 info][sub part 2 info][0][0]]]

A message with an attached message/rfc822 message with the following total structure:

    message/rfc822
      0 headers; content-type: multipart/mixed
      1 text/plain
      2 message/rfc822
        0 headers; content-type: multipart/alternative
        1 text/plain
        2 text/html
  [[3][rfc822 header part 0][text/plain part 1][overall attachment info][0][
       [3][rfc822 header part 2.0][text/plain part 2.1][text/html part 2.2]
          [0][0]]]
Cache Header

Any cached header fields. The exact set of fields here depends on the cache record version - there is a function in imap/mailbox.c to determine if a named header would be cached based on the version. These are in the same format they would appear in the message file:

  HeaderName: headerdata\r\n

Examples include: References, In-Reply-To, etc.

From
The from header.
To
The to header.
Cc
The CC header.
Bcc
The BCC header.
Subject
The Subject header.

Locking Considerations

The cyrus.index file must be locked in exclusive mode while making changes to the cyrus.cache file to ensure consistency. All new cache records are created by reading the current end-of-file offset, appending the new cache record, and storing that start offset into the associated cyrus.index record.

cyrus.index

The cyrus.index file is NOT just a cache - it stores information not present in the message file!

The cyrus.index file consists of a fixed width header, followed by fixed width records. In the past, it would be rewritten on every expunge, but since Cyrus 2.4 the expunged records remain in the cyrus.index file for a configurable time to support QRESYNC and more efficient delayed expunge.

The cyrus.index file is the "heart" of the mailbox format - containing checksums (CRC32) of everything else, and the most frequently updated fields. All fields are stored in network byte order and aligned on 4 byte boundaries. Due to some 64 bit values being stored, the header and individual records are aligned on 8 byte boundaries.

The overall format looks sort of like this:

cyrus.index:
+----------------+
| Mailbox Header |
+----------------+
| Msg: Num 1     |
+----------------+
| Msg: Num 2     |
+----------------+
|     ...        |
+----------------+

The basic idea being that there is one header, and then all the message records are evenly spaced throughout the file. All of the message records are at well-known offsets, making any part of the file accessable at roughly equal speed.

Locking Considerations

cyrus.index files can not be repacked (i.e. records can not change UID for a particular offset, and the file can't be rewritten or deleted) unless there's an exclusive namelock held for the mailbox name. This is to avoid race conditions and simplify the use of mailboxes. Whenever a mailbox is opened, the caller holds a shared namelock on the mailbox name for the duration of the "mailbox object"'s existence.

All reads of a cyrus.index file must be done with a lock held, and all writes must be done with an exclusive lock held. This ensures CRC32 checksums of individual headers and records are always consistent. There are no direct "offset" reads done any more, instead the mailbox API provides a way to read an entire cyrus.index header or cyrus.index record into a struct, performing consistency checks. Writes are also done with a complete record struct.

Detail of cyrus.index header

The index header contains the following information, in order:

Generation Number (4 bytes)
A number that is basically the "revision number" of the mailbox. It must match between the cache and index files. This is to ensure that if we fail to sync both the cache and index files and a crash happens (so that only one is synced), we do not provide bad data to the user. This is also backed by having indiviual cache checksums on each record.
Format (4 bytes)
Basically obsolete (indicates netnews or regular).
Minor Version (4 bytes)
Indicates the version number of the index file. This can be used for on-the-fly upgrades of the index and cache files.
Start Offset (4 bytes)
Size of index header.
Record Size (4 bytes)
Size of an index record.
Num Records (4 bytes)
How many records are in this index (including records for expunged records. See below for "Exists" which has moved from pre-version 12 files.
Last Appenddate (4 bytes)
(time_t) of the last time a message was appended
Last UID (4 bytes)
Highest UID of all messages in the mailbox (UIDNEXT - 1).
Quota Mailbox Used (8 bytes)
Total amount of storage used by all of the messages in the mailbox. Platforms that don't support 64-bit integers only use the last 4 bytes.
POP3 Last Login (4 bytes)
(time_t) of the last pop3 login to this INBOX, used to enforce the "poptimeout" imapd.conf option.
UIDvalidity (4 bytes)
The UID validitiy of this mailbox. Cyrus currently uses the time() when this mailbox was created.
Deleted, Answered, and Flagged (4 bytes each)
Counts of how many messages have each flag.
Mailbox Options (4 bytes)
Bitmask of mailbox options, consisting of any combination of the following:
POP3_NEW_UIDL
Flag signalling that we're using "uidvalidity.uid" instead of just "uid" for the output of the POP3 UIDL command.
IMAP_SHAREDSEEN
Flag signalling that we're supporting a shared \Seen flag on the mailbox.
IMAP_DUPDELIVER
Flag signalling that we're allowing duplicate delivery of messages to the mailbox, overriding system-wide duplicate suppression.
MAILBOX_NEEDS_REPACK
Flag signalling that the mailbox is due to be repacked. During mailbox_close() every process will attempt to take an exclusive namelock on the mailbox and repack.
MAILBOX_DELETED
Flag signalling that the mailbox is deleted. This can be set with a shared namelock, and indicates to all other users of the mailbox that they need to close it and attempt cleanup. The last process to close the mailbox will perform the final cleanup under an exclusive namelock, giving the other processes a chance to finish their current operation first without files disappearing from under them!
Leaked Cache (4 bytes)
Number of leaked records in the cache file.
Highest ModSeq (8 bytes)
Highest Modification Sequence of all the messages in the mailbox (CONDSTORE).
Deleted ModSeq (8 bytes)
Lowest Modification Sequence before which expunged message data may have been purged from the mailbox and forgotten (CONDSTORE/QRESYNC support).
Exists (4 bytes)
See NumRecords above. This is the count of non-expunged records in the mailbox and corresponds to the IMAP status item "EXISTS".
First Expunged (4 bytes)
lowest modified time of an expunged message in this mailbox (or zero if there are no expunged messages) - used to determine if the mailbox needs repacking.
Last Repack Time (4 bytes)
a timestamp for the last repack, to ensure repacks aren't done too close together if expunges were closely spaced
Header File CRC (4 bytes)
CRC32 value of the bytes in the cyrus.header file for this mailbox. Must be rewritten whenever the cyrus.header file is changed (see locking considerations above - this is why the cyrus.index must be exclusively locked!)
Sync CRC (4 bytes)
An XOR of the CRC32 of a specially generated value for each of the non-expunged records in this mailbox. This is a cached value which allows the replication subsystem to quickly determine that all non-expunged records in a mailbox are in sync and detect possible "split brain" scenarios with low bandwidth use.
Recent UID (4 bytes)
The highest UID last time an IMAP client logged in as the mailbox owner (or anybody if SHAREDSEEN is enabled) selected this mailbox. Used to generate the \Recent flags in IMAP
Recent Time (4 bytes)
Used for consistency with the seen_db code, but probably not actually necessary. Oh well
Header CRC (4 bytes)
Must always be the LAST record of the header. This is the CRC32 of the actual bytes on disk (network order format) for the rest of the cyrus.index. By keeping it last, it can be easily calculated with the following snippet of code: crc = crc32_map(buf, OFFSET_HEADER_CRC); - i.e. crc32 from the start of the buffer to just before this field.

There are also spare fields in the index header, to allow for future expansion without forcing an upgrade of the file, and to round up to be divisible by 8 bytes.

Detail of cyrus.index records

These records start immediately following the cyrus.index header, and are all fixed size. They are in-order by uid of the message.

UID (4 bytes)
UID of the message
INTERNALDATE (4 bytes)
INTERNALDATE of the message (where possible, this matches the creation and modification times of the file on disk to help reconstruct in the event of data loss)
SENTDATE (4 bytes)
Contents of the Date: header chomped to day resolution with timezone stripped.
SIZE (4 bytes)
Size of the whole message (in octets)
HEADER SIZE (4 bytes)
Size of the message header (in octets)
GMTIME (4 bytes)
Contents of the Date: header at 1 second resolution and converted to GMT (for sort)
CACHE_OFFSET (4 bytes)
Offset into the cyrus.cache file for the beginning of this message's cache entry.
LAST UPDATED (4 bytes)
(time_t) of the last time this record was changed
SYSTEM FLAGS (4 bytes)
Bitmask showing which system flags are set/unset
USER FLAGS (MAX_USER_FLAGS / 32 bytes)
Bitmask showing which user flags are set/unset (bits correspond to positions in the cyrus.header flag list, i.e. (1<<0) == the flag name
CONTENT_LINES (4 bytes)
Number of text lines contained in the message content (body).
CACHE_VERSION (4 bytes)
Indicates the version number of the cache record for the message (determines which headers are cached, see list in mailbox.c).
GUID (MESSAGE_GUID_SIZE bytes)
Globally Unique IDentifier of the message (used by replication engine). This is the sha1 value of the bytes as stored on disk.
MODSEQ (8 bytes)
Modification Sequence of the message (CONDSTORE).
CACHE_CRC (4 bytes)
This is the CRC32 of all the bytes of the cache record (all 10 fields) as stored on disk. Again, calculated over the exact bytes stored in the cyrus.cache file.
RECORD_CRC (4 bytes)
Like the header CRC - this is the CRC32 of all the bytes in on-disk order that exist in this record. Records are always rewritten as the entire record, including the updated CRC, so it's always consistent if you have a lock on the cyrus.index file, because writers will wait until they get an exclusive lock to make modifications.

Notes

  • Expunge is super quick now - it's just a flag update!
  • Append is relatively fast (it only adds to the end of both the cache and index files and modifies the index header)
  • Message unlinks always happen during the "close" phase - which may be noticed when you select another mailbox, but otherwise are delayed from the actual action. With delayed expunge, the unlinks are pushed off to cyr_expire which is a background task, and will never be noticed by the user.
  • Message delivery is something like this:
    1. write/sync message file
    2. write/sync new cyrus.cache record
    3. write/sync new cyrus.index record
    4. calculate, write, sync new cyrus.index header
    5. acknowledge message delivery

    The message isn't delivered until the new index header is written. In case of a crash before the new index header is written, any previous writes will be overwritten on the next delivery (and will not be noticed by the readers).

    Note that certain power failure situations (power failure in the middle of a disk sector write) could cause a mailbox to need reconstruction (possibly even losing some flag state). These failure modes are not possible in the "Hardware RAID disk model" (which we will describe somewhere else when we get around to it).

Future considerations

  • Cache all header fields? (or all up to Xk?) This could greatly improve speeds of clients that just ask for everything, but also increases the expense of rewriting the cache file (as well as the size it takes on disk).
  • Reformat cache file to use a (size)(size)(size)(size)(data)(data)(data) format. This makes accesses anywhere in the cache file equally fast, as opposed to having to iterate through all the entires for a given message to get to the last one. Note that either way is still O(1) so maybe it doesn't matter much.
  • It would be useful to store a uniqueid -> mailbox name index, so that we could fix arbitron again.
cyrus-imapd-2.5.10/doc/internal/index-api.html0000644000175000017500000000547212772415051016116 00000000000000 Index API

Index API

Intro

The Index API is implemented in imap/index.h and imap/index.c. It provides a snapshot view into the underlying mailbox (see the Mailbox API documentation which obeys IMAP semantics, as well as all the searching and sorting logic.

Opening and closing

struct index_state *state = NULL;
struct index_init init;
int r;
const char *mboxname = "user.brong";

memset(&init, 0, sizeof(struct index_init));
init.userid = imapd_userid;
init.authstate = imapd_authstate;
init.out = imapd_out;

r = index_open(mboxname, &init, &state);
if (r) return r;

do_stuff(state);

index_close(&state);

The index_init interface sucks. So does passing lots of parameters. For now, this will do! Just pass NULL if you're only reading, or use the code already in imapd and you'll be fine.

The Index Model

Ok - I think a few words about the index model and how it differs from direct mailbox access are needed! In the past, index.c used pointers directly into the mmaped cyrus.index file and maintained the old mmaped copy if an expunge took place. Under the namelock regime, this is no longer required because namelocks will avoid the file being re-written.

Also, memory is now cheap. Rather than using locks to ensure consistency, we just keep a copy of the struct index_record for even message in the index, stored in memory. Since these are about 100 bytes each, a 1 million email mailbox will take rougly 100Mb of memory. That's not too bad on a modern server, and that's a huge mailbox.

So - the model works like this:

  • Create the index state or re-lock (index_lock) the mailbox on an existing index.
  • call index_refresh
  • if any changes are to be made (i.e. flag updates for a store, non-peek body fetch, expunge) then cycle through the refreshed state map and update the records which are affected.
  • call index_unlock (unlock the underlying mailbox and commit the statuscache changes)

    At this point the index lock is released and we have not yet generated any network traffic. Now start generating the response.

  • if expunges are allowed, call index_tellexpunge
  • call index_tellchanges to tell about all other changes
  • return any response that the command itself required
cyrus-imapd-2.5.10/doc/internal/caldav_scheduling_flowchart.html0000644000175000017500000003615613001236020021732 00000000000000 Cyrus CalDAV Scheduling Flowchart

Cyrus CalDAV Scheduling Flowchart

caldav_put() - create/modify via HTTP PUT on a resource or POST (add-member) on a calendar

  1. Check if the new resource is a scheduling resource (contains ORGANIZER property). If not, skip to step 4.
  2. Check for (and load) any existing resource.
  3. Check if the authenticated user matches ORGANIZER:
  4. Store the new/modified resource.

caldav_delete_sched() - remove via HTTP DELETE on a resource

  1. Check if the existing resource is a scheduling resource (has Schedule-Tag). If not, we are done.
  2. Load the existing resource.
  3. Check if the authenticated user matches ORGANIZER. If yes, goto sched_request(), otherwise goto sched_reply().

caldav_post() - busytime query via HTTP POST on Scheduling Outbox

  1. Check the ACL on the owner's Scheduling Outbox. If the authenticated user doesn't have the DACL_SCHEDFB right, fail.
  2. sched_busytime_query().

sched_pollstatus - perform a voter response update


sched_request() - perform an organizer request / attendee status update

  1. Check the ACL on the owner's Scheduling Outbox. If the authenticated user doesn't have the DACL_INVITE right, fail.
  2. If the request includes a resource, then set METHOD:REQUEST, otherwise set METHOD:CANCEL.
  3. Create an iTIP message template, copying over any CALSCALE property and VTIMEZONE components.
  4. If not an attendee status update and the existing resource is a scheduling resource: Foreach component in the existing resource, add it and its SEQUENCE to our hash table keyed by RECURRENCE-ID (for comparison against new/modified resource).
  5. Create a hash table of attendees. This will hold attendee-specific iTIP messages.
  6. Foreach component in the new/modified resource:
    1. Lookup (by RECURRENCE-ID) and remove the component from the hash table of existing components.
    2. If the component exists compare all of DTSTART, DTEND, DURATION, RRULE, RDATE, EXDATE to those of the new component.
    3. If the component is new or changed, then process_attendees().
  7. Foreach remaining component in the hash table of existing components do sched_cancel().
  8. Foreach iTIP message in our hash table of ATTENDEES, sched_deliver() the iTIP message.
  9. Foreach component in the new/modified resource update the SCHEDULE-STATUS of each ATTENDEE.

process_attendees() - create a suitable iTIP request message for each attendee

  1. Foreach ATTENDEE in the component, remove the SCHEDULE-STATUS parameter, and set PROPSTAT=NEEDS-ACTION if required.
  2. Make a copy of the component and clean_component().
  3. Foreach ATTENDEE in the cleaned component:
    1. Check the CalDAV Scheduling parameters. If SCHEDULE-AGENT != SERVER, skip to the next attendee.
    2. Lookup attendee in our hash table.
    3. If it doesn't exist, create a clone of our iTIP template and insert it into our hash table of attendees.
    4. Add the component to the attendee's iTIP message.
    5. Add the component “number†to our mask of new components appearing in the attendee's iTIP message.
  4. If the component is not the "master", foreach attendee do sched_exclude().

sched_exclude() - exclude an attendee from a recurrence instance

  1. If the component did not appear in the attendee's iTIP message, add an EXDATE property (based on the RECURRENCE-ID of the component) to the master component of the attendee's iTIP message.

sched_cancel() - cancel an organizer event/task

  1. Set STATUS:CANCELLED on the component.
  2. process_attendees().

sched_reply() - perform an attendee reply

  1. Check the CalDAV Scheduling parameters on ORGANIZER. If SCHEDULE-AGENT != SERVER, we are done.
  2. Check the ACL on the owner's Scheduling Outbox. If the authenticated user doesn't have the DACL_REPLY right, fail.
  3. Create a new iTIP (METHOD:REPLY) message, copying over any CALSCALE property and VTIMEZONE components.
  4. Foreach component in the existing resource:
    1. trim_attendees().
    2. Add the trimmed component and the attendee's PARTSTAT to our hash table keyed by RECURRENCE-ID (for comparison against new/modified resource).
  5. Foreach component in the new/modified resource:
    1. trim_attendees().
    2. Lookup (by RECURRENCE-ID) and remove the component from the hash table of existing components.
    3. If the component exists:
      1. If component is VPOLL, add voter responses to REPLY via sched_vpoll_reply().
      2. Otherwise, compare the PARTSTAT of the ATTENDEE to that of the new component.
    4. If the component is new or the PARTSTAT has changed:
      1. clean_component().
      2. Add the component to our iTIP message.
      3. Add the component “number†to our mask of new components appearing in our iTIP message.
  6. Foreach remaining component in the hash table of existing components do sched_decline().
  7. sched_deliver() our iTIP message.
  8. Foreach component in the new/modified resource that appeared in our iTIP message, update the SCHEDULE-STATUS of the ORGANIZER.

trim_attendees() - remove all attendees other than the one replying

  1. Clone the component and remove all ATTENDEE properties other than the one corresponding to the owner of the calendar.
  2. Return the ATTENDEE property of owner, his/her PARTSTAT parameter, and the RECURRENCE-ID of the component.

sched_vpoll_reply() - add voter responses to VPOLL reply

sched_decline() - decline a recurrence instance for an attendee

  1. Set PARTSTAT of ATTENDEE to DECLINED.
  2. clean_component().
  3. Add the component to our iTIP message.

clean_component() - sanitize a component for use in an iTIP message

  1. Update DTSTAMP.
  2. Remove any VALARM components.
  3. For a reply/decline only, remove scheduling parameters from ORGANIZER.

sched_deliver() - deliver an iTIP message to a recipient

  1. Lookup the recipient.
  2. If local to our server goto sched_deliver_local(), otherwise goto sched_deliver_remote().

sched_deliver_local() - deliver an iTIP message to a local user

  1. Check the ACL on the owner's Scheduling Inbox. If the sender doesn't have the proper right (DACL_INVITE for request/cancel, DACL_REPLY for reply), fail.
  2. Search the recipient's calendars for a resource having the specified UID.
  3. If the resource doesn't exist:
    1. If the iTIP method is REPLY, fail (we are done).
    2. If the iTIP method is CANCEL, ignore it (we are done).
    3. Otherwise, create a new (empty) attendee object and target the recipient's Default calendar.
  4. Otherwise, load the existing resource.
  5. Update the new/existing resource:
    1. If the iTIP method is CANCEL, set STATUS:CANCELLED on all existing components.
    2. If the iTIP method is REPLY, do deliver_merge_reply().
    3. If the iTIP method is REQUEST, do deliver_merge_request().
    4. If the iTIP method is POLLSTATUS, do deliver_merge_pollstatus().
  6. Store the new/updated resource in the recipient's target calendar.
  7. Record the delivery status (SCHEDULE-STATUS).
  8. If the iTIP message is something other than just a PARTSTAT update from an attendee, store the iTIP message as a new resource in the recipient's Inbox.
  9. If the iTIP method is REPLY, send an update other attendees via sched_pollstatus() (VPOLL only) or sched_request().

deliver_merge_reply() - update an organizer resource with an attendee reply

  1. Foreach component in the existing resource, add it to our hash table keyed by RECURRENCE-ID (for comparison against iTIP message).
  2. Foreach component in the iTIP message:
    1. Lookup (by RECURRENCE-ID) the component from the hash table of existing components.
    2. If the component doesn't exist (new recurrence overridden by ATTENDEE) create a new recurring component:
      1. Clone the existing master component.
      2. Remove the RRULE property.
      3. Add the RECURRENCE-ID from the iTIP message.
      4. Replace the DTSTART, DTEND, SEQUENCE properties with those from the iTIP message.
      5. Add the new component to our existing resource.
    3. Get the sending ATTENDEE from the iTIP message.
    4. Find the matching ATTENDEE in the existing component.
    5. If not found (ATTENDEE added themselves to this recurrence), add new ATTENDEE to the component.
    6. Set the ATTENDEE PARTSTAT, RSVP, and SCHEDULE-STATUS parameters in the existing component.
    7. If the component is VPOLL, update the voter responses in the existing component via deliver_merge_vpoll_reply().
  3. Return the sending ATTENDEE.

deliver_merge_vpoll_reply() - update an organizer resource with voter responses

  1. Foreach sub-component in the existing resource, replace any voter response(s) with those from the reply.

deliver_merge_request() - create/update an attendee resource with an organizer request

  1. Foreach VTIMEZONE component in the existing resource, add it to our hash table keyed by TZID (for comparison against iTIP message).
  2. Foreach VTIMEZONE component in the iTIP message:
    1. Lookup (by TZID) the VTIMEZONE component from the hash table of existing components.
    2. If the component exists, remove it from the existing object.
    3. Add the VTIMEZONE from the iTIP message to our existing object.
  3. Foreach component in the existing resource, add it to our hash table keyed by RECURRENCE-ID (for comparison against iTIP message).
  4. Foreach component in the iTIP message:
    1. Clone a new component from the iTIP component.
    2. Lookup (by RECURRENCE-ID) the component from the hash table of existing components.
    3. If the component exists:
      1. Compare the SEQUENCE of the new component to the existing component to see if it has changed.
      2. Copy any COMPLETED, PERCENT-COMPLETE, or TRANSP properties from the existing component to the new component.
      3. Copy any ORGANIZER SCHEDULE-STATUS parameter from the existing component to the new component.
      4. Remove the existing component from the existing object.
    4. Add the new component to the existing object.

deliver_merge_pollstatus() - update voter responses on a voter resource

  1. Foreach sub-component in the existing resource, add it to our hash table keyed by POLL-ITEM-ID (for comparison against iTIP message). The sub-component entry includes a hash table of VOTERs.
  2. Foreach sub-component in the iTIP message:
    1. Lookup (by POLL-ITEM-ID) the sub-component from the hash table of existing sub-components.
    2. If the component exists, foreach VOTER in the sub-component in the iTIP message:
      1. Lookup VOTER in the hash table of existing sub-component.
      2. Add/update VOTER response.

sched_deliver_remote() - deliver an iTIP message to a remote user

  1. If the recipient is local to our Murder, goto isched_send(), otherwise goto imip_send().
  2. Retrieve status of iTIP message delivery.

isched_send() - deliver an iTIP message to a remote user via iSchedule (HTTP)

imip_send() - deliver an iTIP message to a remote user via iMIP (SMTP)


sched_busytime_query() - perform a busytime query

busytime_query_local() - perform a busytime query on a local user

busytime_query_remote() - perform a busytime query on a remote user

cyrus-imapd-2.5.10/doc/internal/index-format-history.txt0000644000175000017500000001333012772415051020177 00000000000000cyrus.index format history. We only track Cyrus version 2 index formats here, so starting with version 3 as shipped with 2.0.0. NOTE: offsets in the code were sometimes defined in terms of the previous field rather than exact offsets, which is bogus since the format on disk will always be exact offsets, so all offsets here are specified exactly. Version 3: 2.0.0 2000-04-25 H:56 R:52 ============================================= /* Offsets of index header fields */ #define OFFSET_GENERATION_NO 0 #define OFFSET_FORMAT 4 #define OFFSET_MINOR_VERSION 8 #define OFFSET_START_OFFSET 12 #define OFFSET_RECORD_SIZE 16 #define OFFSET_EXISTS 20 #define OFFSET_LAST_APPENDDATE 24 #define OFFSET_LAST_UID 28 #define OFFSET_QUOTA_MAILBOX_USED 32 #define OFFSET_POP3_LAST_LOGIN 36 #define OFFSET_UIDVALIDITY 40 #define OFFSET_DELETED 44>------/* added for ACAP */ #define OFFSET_ANSWERED 48 #define OFFSET_FLAGGED 52 /* Offsets of index_record fields in index file */ #define OFFSET_UID 0 #define OFFSET_INTERNALDATE 4 #define OFFSET_SENTDATE 8 #define OFFSET_SIZE 12 #define OFFSET_HEADER_SIZE 16 #define OFFSET_CONTENT_OFFSET 20 #define OFFSET_CACHE_OFFSET 24 #define OFFSET_LAST_UPDATED 28 #define OFFSET_SYSTEM_FLAGS 32 #define OFFSET_USER_FLAGS 36 Version 4: 2.1.4 2002-04-30 H:76 R:52 ============================================= The UIDL format was changed to include the mailbox UIDVALIDITY, but this breaks existing caching when upgrading, so a header field was added to track when an existing mailbox ever got empty, so that the UIDL format could be changed from then. Also defined some spares so new fields could be added to the header without a format change. #define OFFSET_POP3_NEW_UIDL 56>/* added for Outlook stupidity */ #define OFFSET_SPARE0 60 #define OFFSET_SPARE1 64 #define OFFSET_SPARE2 68 #define OFFSET_SPARE3 72 Version 5: 2.2.1 2003-07-16 H:76 R:52 ============================================= To save repacking the cache file every single EXPUNGE, a new header field was added to track when the cache had enough dirty data to justify a repack. Strictly this didn't need a version bump. #define OFFSET_LEAKED_CACHE 60 /* Number of leaked records in cache file */ Version 6: 2.2.2 2003-10-28 H:76 R:60 ============================================= #define OFFSET_POP3_NEW_UIDL 56>/* added for Outlook stupidity */ Version 7: 2.3.0 2005-12-05 H:76 R:72 ============================================= Added replication support, and the UUID field to allow efficient replication of copies. The UUID is 12 bytes long. #define OFFSET_MESSAGE_UUID 60 Version 8: 2.3.4 2006-05-23 H:92 R:80 ============================================= Added support for CONDSTORE (RFC4551) in the header, including renaming the POP3_NEW_UIDL to a more general bitmap of options (to which CONDSTORE_ENABLED was added) #define OFFSET_MAILBOX_OPTIONS 60 #define OFFSET_HIGHESTMODSEQ_64 68 /* CONDSTORE (64-bit modseq) */ #define OFFSET_HIGHESTMODSEQ 72 /* CONDSTORE (32-bit modseq) */ #define OFFSET_SPARE0 76 /* Spares - only use these if the index */ #define OFFSET_SPARE1 80 /* record size remains the same */ #define OFFSET_SPARE2 84 /* (see note above about spares) */ #define OFFSET_SPARE3 88 And the record: #define OFFSET_MODSEQ_64 72 /* CONDSTORE (64-bit modseq) */ #define OFFSET_MODSEQ 76 /* CONDSTORE (32-bit modseq) */ Version 9: 2.3.7 2006-07-10 H:96 R:80 ============================================= Due to the header not being divisible by 8 bytes, the 64 bit reads for modseq values were inefficient - so this change just added extra padding for alignment. #define OFFSET_SPARE4 92 Version 10: 2.3.10 2007-10-24 H:96 R:88 ============================================= Switch UUID to GUID, which is a 20 byte sha1 instead of a 12 byte calculated value. #define OFFSET_MESSAGE_GUID 60 #define OFFSET_MODSEQ_64 80 /* CONDSTORE (64-bit modseq) */ #define OFFSET_MODSEQ 84 /* CONDSTORE (32-bit modseq) */ Version 11 never existed, it was used internally at Fastmail but never released in a public Cyrus release. Version 12: 2.4.0 2010-11-10 H:128 R:96 ============================================= Major rewrite. Renamed exists to NUM_RECORDS and added a separate new record for EXISTS (number of unexpunged records) #define OFFSET_NUM_RECORDS 20 Also DELETEDMODSEQ for QRESYNC support, CRCs throughout, fields for supporting per-user SEEN storage in the cyrus.index file (RECENTUID and RECENTTIME) and fields to support expunge cleanup. #define OFFSET_DELETEDMODSEQ_64 76 /* CONDSTORE (64-bit modseq) */ #define OFFSET_DELETEDMODSEQ 80 /* CONDSTORE (32-bit modseq) */ #define OFFSET_EXISTS 84 /* Non-expunged records */ #define OFFSET_FIRST_EXPUNGED 88 /* last_updated of oldest expunged message */ #define OFFSET_LAST_REPACK_TIME 92 /* time of last expunged cleanup */ #define OFFSET_HEADER_FILE_CRC 96 /* CRC32 of the index header file */ #define OFFSET_SYNC_CRC 100 /* XOR of SYNC CRCs of unexpunged records */ #define OFFSET_RECENTUID 104 /* last UID the owner was told about */ #define OFFSET_RECENTTIME 108 /* last timestamp for seen data */ #define OFFSET_SPARE0 112 /* Spares - only use these if the index */ #define OFFSET_SPARE1 116 /* record size remains the same */ #define OFFSET_SPARE2 120 /* (see note above about spares) */ #define OFFSET_HEADER_CRC 124 /* includes all zero for the spares! */ And the record had some changes too. Header size was always identical to content offset, so replace that with a GMTIME field for efficient sort by REVERSE ARRIVAL. #define OFFSET_GMTIME 20 Also, two new CRC fields for integrity checks on both the cache record and the index record itself #define OFFSET_CACHE_CRC 88 /* CRC32 of cache record */ #define OFFSET_RECORD_CRC 92 cyrus-imapd-2.5.10/doc/internal/specials.html0000644000175000017500000000273412772415051016041 00000000000000 Cyrus IMAP Server: Special Characters

Cyrus IMAP Server: Special Characters

This document is supposed to be a repository of "special characters" used in Cyrus naming of users, folders, directory paths, etc.

Current Uses


Character: +
  • (LMTP) Separation of postuser and target mailbox for delivery
  • (LMTP) Separation of username and submailbox for delivery
  • (IMAP) Flag at end of login name that indicates that LIST should return LSUB results (when imapmagicplus is set)
  • (POP3) POP a subfolder directly (e.g. rjs3+foo POPs user.rjs3.foo)

Character: . /
  • [mailbox names] Hierarchy separators

Character: ^
  • [mailbox names] In unixhierarchysep, ^ is the part of the internal name that represents a '.'

Characters: @ %
  • [usernames] These are realm separators for the purposes of authentication

Future Uses

Character: +
  • IMAP LIST filters (e.g. rjs3+foo will only list folders that match foo*)
  • possibly other interpretations here:
    - rjs3+foo will do an effective chroot(foo.)
    - rjs3+foo will only list folders in user.rjs3.foo*
cyrus-imapd-2.5.10/doc/internal/internationalization.html0000644000175000017500000004343413001236020020464 00000000000000 internationalization

charset code

introduction

Cyrus currently transcodes characters to a canonical UTF-8 form for searching. The base spec of IMAP4 only requires understanding multiple character sets to properly implement SEARCH. Since the base spec came out, several extensions have been proposed that require further charset support: SORT, THREAD, and the Sieve subsystem. As of this writing, Cyrus doesn't correctly support these other commands.

Cyrus currently only believes in 16-bit characters. Technically, Unicode has up to 21-bit characters (expressible in UTF-16 and 3-byte UTF-8) and ISO 10646 allows up to 31-bit characters (though ISO's current policy is to not allocate any characters outside of the 21-bit Unicode range). The lower 16-bit characters make up the basic multilingual plane (BMP) where the majority of languages live. This restriction is apparent in charset.c:writeutf8(), the UTF-8 decoders, and the Unicode canonicalization table used by Cyrus. Since Cyrus's known character sets (except for UTF-8) don't contain any characters off of the BMP this isn't seen to be a major problem.

Throughout this text, Unicode and ISO 10646 will be used interchangible to refer to the 16-bit character set of the BMP, regardless of encoding. "Character", unless otherwise specified, refers to a single Unicode character ffff or under.

cyrus canonical form

Since when users search e-mail messages it's much easier for them to eliminate false positives than realize there are hits that aren't displayed, the Cyrus searching algorithm errs on the side of more matches. Before comparing any two strings, Cyrus puts them in a canonical form. Logically, the process works as follows:

  • the input string is translated into a sequence of Unicode characters.
  • each character is transformed into lowercase. (For some characters, a single uppercase character may transform into multiple lowercase characters.)
  • each character is fully decomposed.
  • all whitespace (Unicode general categories starting with Z) is removed.
  • combining diacritical marks, such as the accent on é, are removed. (These are Unicode characters 0300-03ff.)
  • certain characters are expanded to alternative spellings using ASCII characters, such as "æ" to "ae".
  • the output characters are then encoded in UTF-8.

The actual transcoding does all of these steps at once with the aid of tables, carefully built at compile-time.

The central part of Cyrus's internationalization support is it's transcoding routines in lib/charset.[ch], and lib/chartable.[ch]. Cyrus's transcoding routines are very elegant and very compact, thus somewhat intimidating. During compilation, Cyrus builds up a large number of tables (see mkchartable) and uses them so that it never has to consider more than a single octet at a time while outputing the Cyrus canonical form for an input string.

external interface

lib/charset.h is the public interface for Cyrus lib clients to get character canonicalization and searching support. In contains the following functions:

char *charset_convert(const char *s, int charset, char *buf, int bufsz)
Given a string s in charset charset, decode it into canonical form in buf. buf must be reallocable and currently at least size bufsz.
char *charset_decode_mimeheader(const char *s, char *buf, int bufsz)
Given a string s containing possible MIME encoded substrings (per RFC 2047), decode into canonical form in buf. buf must be reallocable and currently at least size bufsz.
charset_index charset_lookupname(const char *name)
Given name return the Cyrus charset index. 0 always represents US-ASCII. The returned charset_index may be saved in a file; it is stable and is an integer. If this version of Cyrus does not support the charset, CHARSET_UNKNOWN_CHARSET is returned.
comp_pat *charset_compilepat(const char *s)
Compiles a NUL-terminated canonicalized string s into a Boyer-Moore table for fast searching. I'll describe these compiled patterns later.
void charset_freepat(comp_pat *pat)
Frees a pattern previously return by charset_compilepat().
int charset_searchstring(const char *substr, comp_pat *pat, const char *s, int len)
Searches for a canonicalized string substr in the canonicalized string s. s is of length len. substr must have been previously compiled into pat. Returns non-zero for a hit, zero for no match.
int charset_searchfile(const char *substr, comp_pat *pat, const char *msg_base, int mapnl, int len, charset_index charset, int encoding)
Searches for the canonicalized string substr with compiled pattern pat in a large buffer starting at msg_base of length len. The large buffer is of charset charset with the encoding encoding. charset_searchfile() will dynamically unencode and canonicalize the search text looking for substr. (If mapnl is set, the buffer has only \n instead of \r\n, but the length assumes that each \n is dynamically converted to \r\n. This feature is deprecated.)
char *charset_decode_mimebody(const char *msg_base, int len, int encoding, char **buf, int *bufsz, int *outlen)
Decode the MIME body part (per RFC 2045) located in the large buffer starting at msg_base of length len. The large buffer is of encoding encoding. charset_decode_mimebody() will decode into buf. buf must be reallocable and currently at least size bufsz. The number of decoded bytes is returned in outlen.
charset_extractfile()
Used by squatter and possibly other text indexing engines, but not described here.

the TRANSLATE macro: using the transcoding tables

The external interface is implemented with the help of the START and TRANSLATE macros:

void START(struct decode_state *state, const unsigned char (*table)[256][4])
START initializes state to be ready for transcoding of the charset translation table given with table. The starting active table is always the first one in the list passed in.
void TRANSLATE(struct decode_state *state, unsigned char input, unsigned char *outbuf, unsigned outindex)
TRANSLATE takes four parameters: state is the current state of the translation; it must have been initialized with START and is modified by TRANSLATE; input is one octet of input from the stream to be transcoded; outbuf is a pointer to the start of the buffer to write output characters; outindex is the index where this translation should be written. The size of outbuf must be at least outindex + charset_max_translation.

Each charset consists of a set of one or more tables; the table parameter passed into START is the first of these tables and the others are adjacent in memory. Characters are transcoded by indexing into the active table with input and examining the 4 octet translation. The 4 octet translation may consist of 0–3 character translations followed by a control code or a series of control codes. In effect, the translation for a given octet is a mini-program that consists either of UTF-8 octets or control codes. One of the control codes RET, END, JSR, or JMP must occur in the 4 octet translation.

control codes

Control codes are represented by uppercase US-ASCII characters since no uppercase characters can appear in the output translation (recall that Cyrus canonical form downcases). Any uppercase US-ASCII character ([A .. Z]) is thus interpreted specially by the TRANSLATE virtual machine. Any other octet encountered as an output translation is presumed to be part of the UTF-8 output sequence and copied to the output.

The names of control codes are actually C pre-processor defines to uppercase US-ASCII characters. As the mnenomics are easier to understand, I use them in discussing their semantics.

control code reference

TRANSLATE recognizes the following "normal" control codes:

XLT
This is the first octet of the four octet sequence, indicating that the desired translation is larger than 3 UTF-8 octets. The next two octets represent an offset to look up in the special chartables_long_translations[] table. After that translation is copied to the outbuf, the final octet is interpreted (it must be either a RET or an END).
JSR
The TRANSLATE virtual machine has a stack, fixed at size 1. A JSR copies address of the current active table to the stack and transitions to the active table given by the next two octets. (For instance, table 1 would be the next table after the table given as a parameter to START.) Translation of the current octet stops after encountering a JSR.

JSRs are useful for converting a two octet input character: the first octet in the character will make a JSR to some table; the second octet will produce a translation and RET to the current table.

Since the virtual machine has a fixed size stack, it would be highly unusual for the virtual machine to encounter two different JSRs without an intervening RET.

JMP
Similiar to JSR, but does not change the stack. It is the equivalent of a goto. JMPs are useful to deal with modal input character sets (such as an escape in ISO-2022-JP, see how the tables are generated).
RET
Indicates that we are done translating this input octet and we should return to the previous active table. It might appear as the first of the 4 translation octets, in which case this input character translates into nothing (it might be whitespace, for instance).
END
Indicates we are done translating this input octet. When TRANSLATE is next called, that input octet will be interpreted against the current active table; the stack does not change.

In addition, it recognizes the following "special" control codes for charsets that aren't easily represented by a set of tables, UTF-8 and UTF-7:

U7F
UTF-7 consists of US-ASCII characters and a special escape character that indicates a transition to base-64 encoded UTF-16 characters. The virtual machine has built in code to handle the base64 decoding. In UTF-7's base64, 8 input octets result in 3 characters, so the tables would be rather large.
U7N
This indicates that the current octet is the continuation of the base-64 section.
U83
One and two character UTF-8 sequences are handled normally in the charset code. To keep the table size down, 3 octet sequences are handled specially. U83 indicates that the current input octet is the start of a three character sequence. It is also an implicit jump to the 2nd table in the UTF-8 sequence, ending this translation.
U83_2
This input octet 2nd of 3-octet UTF-8 input, with an implicit jump to the 3rd table.
U83_3
3rd octet of a 3-octet UTF-8 input. This produces the output characters and has an implicit jump to the 1st table of UTF-8.

Finally, it's useful to mention the special character EMPTY which is guaranteed not to match any character. It is also represented by an uppercase US-ASCII character.

searching and compiled patterns

boyer-moore

brief description of boyer-moore xxx

cyrus implementation

why two arrays? us-ascii optimization, really kinda useless now xxx

meta-data stored at the end xxx

generating the tables: mkchartable

The program mkchartable is used to generate the charset transcoding tables used by TRANSLATE. These tables are carefully constructed so no more than a single octet need be examined at a time; this octet results in either an output stream of UTF-8 characters being generated or some sort of state change.

mkchartable uses three different sorts of input files to generate these tables. These files are located in the lib/charset directory.

charset tables

Each charset file maps a single charset to the corresponding Unicode characters. For the US-ASCII and ISO-8859-x character sets this is trivial: each input byte corresponds to a single Unicode character. (Actually, some ISO-8859-x octets do not map to any Unicode character. In that case, the file either does not contain that octet or map it to "????".)

Other character sets are trickier. For instance, GB-2312 has both single and double byte characters, but is still a simple map from input character to output character. More complicated are modal character encodings. For instance, ISO-2022-JP starts in US-ASCII mode and uses 1B as an escape character followed by another two characters to select a new mode.

The input charset labels modes with ":" followed by the mode name. The starting mode "US-ASCII" in ISO-2022-JP is preceeded by ":US-ASCII". Mode transitions are denoted by a Unicode conversion of ">newmode" or ":newmode". To denote that the octet 42 transitions into the "US-ASCII" mode, the charset file has "42 >US-ASCII". The mode names themselves are arbitrary labels and have no effect on the output.

The input charset labels modes with ":" followed by the mode name. The mode name is optionally followed by a space and the "<" character. If the "<" character is present, then all translations will be followed by a RET instruction instead of an END instruction.

The transition ">newmode" results in a JSR instruction being generated. A JMP instruction is generated by a transition of ":newmode".

The input byte can be specified as "*". This is used to define the "default action" which is used for input bytes that are not otherwise defined for the mode. If the default action is not explicitly stated, it is a translation to EMPTY.

unicode data table

The unidata2.txt file is verbatim from the Unicode standard. More recent versions should be available from their website. Each entry in the file describers a Unicode character by the following properties, seperated by semicolons:

  • code point (16-bit character value) in hex
  • character name (unused by Cyrus)
  • general category, such as whitespace or puncuation
  • the canonical combining class (unused)
  • bidirection chategory (unused)
  • character decomposition
  • decimal digit value (unused)
  • digit value (unused, and, no, I don't know the difference)
  • numeric value including fractions (unused)
  • mirrored character (unused)
  • Unicode 1.0 name (unused)
  • comment (unused)
  • upper case equivalent (unused)
  • lower case equivalent

In general, Cyrus uses the lower case equivalent if there is one, and the decomposed value otherwise.

unicode fixup table

The unifix.txt file contains Cyrus-specific mappings for characters. It overrides the unidata2.txt table. Each rule in the file is explained with a comment. It's helpful to remember that the Unicode general categories starting with Z represent whitespace, and whitespace is always removed.

generating chartable.c

how mkchartable works: collapses the encoding modes, the unicode translations, and other normalizations into the output tables described above xxx

for the future

Sieve/ACAP comparators

adjustable normalization?

The use of uppercase US-ASCII characters is one of the annoyances in trying to generalize the charset transcoding. If we continue to restrict the characters under consideration to the BMP, switching to UTF-8 control codes that start 4 or 5 byte sequences is possible.

Another possibility is to use a NUL character as an escape sequence, though this increases the size of each control code by 1 octet.

handle >2 octet input characters

make UTF-8 more regular

consider whether we really need U83, U83_2, U83_3. also consider changing { U83, 0, 0, 0 } translations to { U83, JMP, 0, 1 } sequences to at least eliminate the implicit jump.

require minimal UTF-8 characters

references

xxx

  • [UNICODE] Unicode / ISO 10646
  • [UTF-8] utf-8 RFC
  • [UTF-7] utf-7 RFC
  • [BM] boyer-moore
  • [ACAP] the comparators reference. see section XXX of RFC 2244.
cyrus-imapd-2.5.10/doc/internal/prot-events0000644000175000017500000000551313001236020015536 00000000000000Return-Path: Received: from mail3.andrew.cmu.edu ([unix socket]) by mail3.andrew.cmu.edu (Cyrus v2.1.1-053) with LMTP; Sun, 03 Feb 2002 10:37:49 -0500 X-Sieve: CMU Sieve 2.0 Received: from mx1.andrew.cmu.edu (MX1.ANDREW.CMU.EDU [128.2.10.111]) by mail3.andrew.cmu.edu (8.12.2.Beta3/8.12.2.Beta3) with ESMTP id g13FbmZ5001152 for ; Sun, 3 Feb 2002 10:37:48 -0500 (EST) Received: from eagle.oceana.com (eagle.oceana.com [208.17.123.12]) by mx1.andrew.cmu.edu (8.12.2.Beta3/8.12.2.Beta3) with ESMTP id g13FblJw022603 for ; Sun, 3 Feb 2002 10:37:47 -0500 Received: from oceana.com (ppp4.oceana.com [192.168.10.246]) by eagle.oceana.com (8.12.2/8.12.2) with ESMTP id g13FbkNT024933 for ; Sun, 3 Feb 2002 10:37:47 -0500 Message-ID: <3C5D5966.C5318D4C@oceana.com> Date: Sun, 03 Feb 2002 10:38:14 -0500 From: Ken Murchison Organization: Oceana Matrix Ltd. X-Mailer: Mozilla 4.79 [en] (Win98; U) X-Accept-Language: en,pdf MIME-Version: 1.0 To: Lawrence Greenfield Subject: Re: prot events References: <200202030504.g1354Zm0002888@smtp5.andrew.cmu.edu> Content-Type: text/plain; charset=us-ascii Content-Transfer-Encoding: 7bit Lawrence Greenfield wrote: > > Can you give me some details on how the event API in the prot layer > works? I'm a little unclear about the memory management, what should > be returned from the event callback, Either the event pointer (if the event is still active), or NULL (if the event has been removed by the callback). > and how to reschedule an event. Simply set the 'mark' time in the event to the wall time you want it to run again. > (I'd like to make an event called every X seconds of idle time; I know > the API can't do exactly that but I suspect I can fake it well enough.) Look at backend_timeout() in proxyd.c and/or drac_ping() in contrib/drac_auth.patch, they do exactly this. The API is pretty simple: - use prot_addwaitevent() to add an event (linked list) callback onto a stream. takes the stream, the 'mark' time at which to run the event (NOT an interval, but the future clock value), the function pointer, and a rock to pass to the callback as args, and returns a pointer to the event (to use for future removal). - use prot_removewaitevent() to remove an event. takes the stream and a pointer to the event as args. - the event callback gets the stream, a pointer to the event and the rock as args. To reschedule an event, simply set the 'mark' time and return the event pointer. If the callback removes the event, then return NULL. If you see and flaws in this API, feel free to go ahead and change it. Ken -- Kenneth Murchison Oceana Matrix Ltd. Software Engineer 21 Princeton Place 716-662-8973 x26 Orchard Park, NY 14127 --PGP Public Key-- http://www.oceana.com/~ken/ksm.pgp cyrus-imapd-2.5.10/doc/internal/hacking0000644000175000017500000003343513001236020014660 00000000000000This file aims to be a guide to Cyrus coding style/conventions/useful utilities for people trying to approach the code in a sane way. It's not well organized right now but hopefully that will improve with time ;) - Memory Allocation: - All cyrus memory allocation should be done through the libcyrus functions. These are all written to correctly call fatal() in the event of an out-of-memory condition. - In addition to xmalloc and xrealloc, we provide replacements for strdup, strndup, and a malloc that will guarantee zeroed block of memory (xzmalloc). - If you are going to need to do a large number of small allocations, and then free them all at once, you should look at the memory pool routines, which are much faster, but will leak memory until you free the entire pool at once. - strlcpy vs strncpy vs memcpy - use strlcpy when you know the size of the buffer, e.g.: char buf[50]; strlcpy(buf, src, sizeof(buf)); - use memcpy to truncate a string into a buffer you know is large enough. Note that when you do this the resulting buffer will NOT BE NULL TERMINATED. memcpy(buf, src, 4); buf[5] = '\0' - you should try to avoid strncpy, since it is much slower than memcpy (it zero-fills the rest of the buffer) and isn't as safe as strlcpy. - Use of the functions in this way will reduce the confusion involved in their various behaviors. In other words, this avoids things that look like: strncpy(buf, src, sizeof(buf)-1); - map_refresh and map_free - In many cases, it is far more effective to read a file via the operating system's mmap facility than it is to via the traditional read() and lseek system calls. To this end, Cyrus provides an operating system independent wrapper around the mmap() services (or lack thereof) of the operating system. - Cyrus currently only supports read-only memory maps, all writes back to a file need to be done via the more traditional facilities. This is to enable very low-performance support for operating systems which do not provide an mmap() facility via a fake userspace mmap. - To create a map, simply call map_refresh on the map (details are in lib/map.h). To free it, call map_free on the same map. - Despite the fact that the maps are read-only, it is often useful to open the file descriptors O_RDWR, especially if the file decriptors could possibly be used for writing elsewhere in the code. Some operating systems REQUIRE file descriptors that are mmap()ed to be opened O_RDWR, so just do it. - Network Functions - Cyrus abstracts socket stream access to a concept we refer to as "prot streams" Prot Streams take care of all of the necessary SASL and TLS/SSL encrpytion that may need to happen before data goes out/comes in from the network. The API is documented in lib/prot.h - (todo) Authorization Modules Some general hints that all made it into my 11/15 16:47 commit that I think may be generally useful to people hacking on the cyrus source: - Command line apps should link cli_fatal.o so they all fatal() in the same way, unless there is a really good reason they need to do something unique. - If you call cyrus_init() you must call cyrus_done() before you exit. - No one should ever call DB->init() or DB->done() cyrusdb functions except for in libcyrus_init() - I've been trying to keep #include statements for libcyrus and libimap alphabetical, and below any system includes, but this is merely my personal style - Don't exit at the bottom of main with exit(x) use return instead. - For all the command line utilities that need to be sure that they are running as cyrus, it should be the first thing they do, and they should exit with an appropriate fatal() call - All services should have a shut_down call. It should be the ONLY way of exiting the application. fatal() should always make an attempt to call shut_down() if it can (though it should have a recursive fatal() trap just in case). Similarly, commandline utilities probably don't need a shut_down(). - Coding Standards These are the generally agreed upon coding standards as thrashed out on the cyrus-devel list in June 2010. - Spacing is 4 characters with soft tabs at 8 - mixed tabs and spaces This corresponds to the vi settings sw=4 sts=4 ts=8 et. - Group the '*' character with the variable not the type, i.e. char *foo; /* correct */ char* foo; /* WRONG */ - The keywords 'if', 'for', and 'while' take a space after the keyword. The parentheses around the following expression are not closely connected to the expression without any spaces. The ';' inside the 'for' expression have a space after them and not before. For example: if (condition) /* correct */ if(condition) /* WRONG */ if( condition ) /* WRONG */ for (i = 0; i < x; i++) /* correct */ for(i = 0; i < x; i++) /* WRONG */ for (i = 0 ;i < x ;i++) /* WRONG */ for(i = 0 ;i < x ;i++) /* WRONG */ while (foo) /* correct */ while(foo) /* WRONG */ while( foo ) /* WRONG */ - Use spaces around the double-character logical operator '||' but don't use spaces around single-character bitwise operator '|'. int flags = FOO|BAR; /* correct */ int flags = FOO | BAR; /* WRONG */ if (itchy || scratchy) /* correct */ if (itchy||scratchy) /* WRONG */ - Function definitions are followed by a brace on a line by itself, all other braces are inline. Return types are inline with function definition. Old K&R style function definitions are not allowed. void thing(int val) /* correct */ { /* correct */ ...body... } /* correct */ void /* WRONG */ thing(int val) /* WRONG */ { /* WRONG */ ...body... } /* WRONG */ void /* WRONG */ thing( /* WRONG */ int val) /* WRONG */ { /* WRONG */ ...body... } /* WRONG */ void /* WRONG */ antique(val) /* WRONG */ int val; /* WRONG */ { /* WRONG */ ...body... } /* WRONG */ void thing(int val) { /* WRONG */ ...body... } /* WRONG */ void noargs(void) /* correct */ { /* correct */ ...body... } /* correct */ void noargs() /* WRONG */ { /* WRONG */ ...body... } /* WRONG */ Long argument lists should be split across multiple lines, with the second and subsequent lines indented so that they line up with the start of the first line of arguments. void toomanyargs(int arg1, const char *arg2, /* correct */ struct whatever *arg3, int arg4) /* correct */ { /* correct */ ...body... } /* correct */ void toomanyargs(int arg1, const char *arg2, /* WRONG */ struct whatever *arg3, int arg4) /* WRONG */ { /* WRONG */ ...body... } /* WRONG */ void toomanyargs( /* WRONG */ int arg1, /* WRONG */ const char *arg2, /* WRONG */ struct whatever *arg3, /* WRONG */ int arg4) /* WRONG */ { /* WRONG */ ...body... } /* WRONG */ - Within a function, braces are used in old-fashioned K&R style. Specifically: - open braces are placed at the end of the line containing the statement (such as an 'if') to which they belong, after a single space. - closing braces are placed on a line by themselves, aligned with the start of the statement to which their matching open brace belongs. - this applies even when the closing brace is followed by an 'else' keyword. Yes, it's ugly and hard to read, but you get used to it and most of the code is currently like that. Deal with it. while (cond) { /* correct */ ...body... /* correct */ } /* correct */ while (cond){ /* WRONG */ ...body... /* WRONG */ } /* WRONG */ while (cond) { ...body... } /* WRONG */ while (cond) { /* WRONG */ ...body... } /* WRONG */ while (cond) /* WRONG */ { /* WRONG */ ...body... /* WRONG */ } /* WRONG */ while (cond) /* WRONG */ { /* WRONG */ ...body... /* WRONG */ } /* WRONG */ if (cond) { /* correct */ ...body... /* correct */ } /* correct */ else if (othercond) { /* correct */ ...body... /* correct */ } /* correct */ else { /* correct */ ...body... /* correct */ } /* correct */ if (cond) { /* WRONG */ ...body... /* WRONG */ } else if (othercond) { /* WRONG */ ...body... /* WRONG */ } else { /* WRONG */ ...body... /* WRONG */ } /* WRONG */ if (cond) /* WRONG */ { /* WRONG */ ...body... /* WRONG */ } /* WRONG */ else if (othercond) /* WRONG */ { /* WRONG */ ...body... /* WRONG */ } /* WRONG */ else /* WRONG */ { /* WRONG */ ...body... /* WRONG */ } /* WRONG */ - The braces around a block used in an 'if'...'else if'...'else' may be omitted if the statement is very simple and clear, such as a single function call. This is a judgement call though, so play it safe and use braces. if (cond) /* correct, maybe */ function(); /* correct, maybe */ else /* correct, maybe */ other_function(); /* correct, maybe */ - The 'goto' keyword needs to be used very very sparingly and only with forethought. The only clearly good example is to goto a label at the end of a function to do cleanup under error conditions. void foo(struct bar *b) /* correct */ { /* correct */ char *x = xmalloc(...); /* correct */ if (b == NULL) /* correct */ goto error; /* correct */ if (b->quux != 42) /* correct */ goto error; /* correct */ ...do useful things... /* correct */ error: /* correct */ free(x); /* correct */ } /* correct */ Very occasionally, it may be permissable to use 'goto' from within a complicated or multiply-nested loop, to the top of a loop, but only if using another control structure is *less* clear. - Generally, zero return is SUCCESS and integer return is an error code. - Use "const char *" where possible. int is_tacky(const char *name) /* correct */ { /* correct */ return !strcmp(name, "britney"); /* correct */ } /* correct */ int is_tacky(char *name) /* WRONG */ { /* WRONG */ return !strcmp(name, "britney"); /* WRONG */ } /* WRONG */ - Use 'struct buf' for variable length strings where possible. - RAII http://en.wikipedia.org/wiki/Resource_Acquisition_Is_Initialization In practice, this means each structure should have a single cleanup function which handles all possible states of the structure and is called whenever the structure needs cleaning up. Likewise, any resources allocated during a function should be cleaned up in the same function, in a single code block at the end of the function (see the comments on 'goto'). - If you find yourself passing the same multiple parameters through many functions, create a struct and pass around a pointer to that instead. - DON'T EVER REUSE THE SAME VARIABLE FOR TWO DIFFERENT PURPOSES IN THE SAME FUNCTION. IN FACT, DON'T REUSE THE SAME VARIABLE _NAME_ FOR DIFFERENT PURPOSES. KTHXBYE. (note: this doesn't apply to 'i', 'n', etc which are used in multiple loops. It applies to using the same name for an absolute offset and a "within this mmap" offset though, and it also applies to using the same variable name for native order and network order numbers, which is where I've seen it a few times and been super frustrated!) cyrus-imapd-2.5.10/doc/internal/cyrusdb-api.html0000644000175000017500000002722613001236020016442 00000000000000 cyrusdb API

cyrusdb API

Intro

The cyrusdb API is a common interface to a key-value store, used throughout the Cyrus code. It allows a choice of different backends for different access patterns, while ensuring a consistent interface.

This document will describe the interface, and how to use the cyrusdb interface from within parts of Cyrus code, as well as how to implement your own backend

If you pass incorrect values to these APIs, you will get an assertion failure in most cases. That's generally considered safer than silenty breaking things. Exceptions are noted below.

Code Layout

The implementation of each interface is in lib/cyrusdb_NAME.c, for example lib/cyrusdb_flat.c. General functions are in lib/cyrusdb.c and the interface in lib/cyrusdb.h.

Configuration

The name of the backend for each of the main internal databases can be configured in imapd.conf, for example: annotation_db: skiplist. This is then read in imap/global.h and imap/global.c during startup, so that the global variable config_annotation_db gets set to the actual database backend:

    config_annotation_db =
            cyrusdb_fromname(config_getstring(IMAPOPT_ANNOTATION_DB));

cyrusdb_fromname uses the database name to find the struct cyrusdb_backend * of the actual database.

The main module for each database then sets up a "short name" to refer to the struct containing the funtion pointers for each action on that database type, giving an "object oriented" API to the database, for example:

  #define DB config_annotation_db

  r = DB->open(fname, dbflags, &db);

  r = DB->fetch(&db, key, keylen, &data, &datalen, &tid);

A full example

  struct cyrusdb_backend *BE = NULL;
  struct db *db = NULL;
  struct txn *tid = NULL;

  cyrus_init(alt_config, "toolname", 0);

  BE = cyrusdb_fromname("skiplist");

  r = BE->open(filename, flags, &db);

  r = BE->fetch(db, key, keylen, &data, &datalen, &tid);

  r = BE->commit(db, tid);

  r = DB->close(db);

  cyrus_done();

Note that you always open a database first, and close it at the end. You must always call cyrus_init() and cyrus_done() to properly intialise and clean up the DB environments.

This example also uses a transaction, meaning that the database is locked in exclusive mode between the 'fetch' (the first use of the transaction) and the commit.

About Transactions

The cyrusdb interface works in two modes - transactional and non-transactional. The value of the 'tid' parameter decides which mode is used. There are three possible values:

  • NULL - non-transactional. Will create a temporary lock for the duration of the current action - either a write lock for "store" or a read lock for "fetch". If you call "foreach", the lock will be dropped between each record fetched
  • Pointer to NULL - transactional, transaction not yet started. Will always take a write lock on the database, and update the pointer to point to the new transaction.
  • Pointer to a valid transaction. Will keep using this transaction

If you are currently in a transaction, you MUST pass the same transaction to every database call. It is not possible to mix or nest transactions. There is one exception in the skiplist backend: If you pass NULL to a fetch or foreach while the database is in a transaction, it will silently do the read in the current transaction rather than returning an error

API Reference

All functions follow the normal C API of returning '0' on success, and an error code on failure

init(const char *dbdir, int flags)

Is called once per process. Don't call this yourself, use cyrus_init(). No other calls will be made until this is called. Dbdir is the directory where database log files and other "state information" is stored.

Flags:

  • CYRUSDB_RECOVER - called by ctl_cyrusdb -r during startup to do initial setup after a restart

done()

The opposite of init() - called once per process to do any cleaning up after all database usage is finished

sync()

Perform a checkpoint of the database environment. Used by berkeley backend. Is called by ctl_cyrusdb -c on a regular basis

archive(const char **fnames, const char *dirname)

Archives the database environment and named database files into the named directory. Called by ctl_cyrusdb -c to take backups of important databases.

Errors:

  • CYRUSDB_IOERROR - if an error occurs copying a file

open(const char *fname, int flags, struct db **retdb)

Opens the database with the specified 'file name' (or other descriptor, for example the sql backend is not a filename), and if successful returns an opaque database structure

Flags:

  • CYRUSDB_CREATE - create the database if it doesn't exist
  • CYRUSDB_MBOXSORT - sort '.' first, so folder listing is correct

Errors:

  • CYRUSDB_IOERROR - if there is any error reading the file, or any corruption detected while loading the file

close(struct db *db)

Close the named database. Will release any locks if they are still held, but it's bad practice to close without committing or aborting, so the backend should log an error

Errors:

  • CYRUSDB_IOERROR - if there are any errors during close

fetch(struct db *db, const char *key, size_t keylen, const char **data, size_t *datalen, struct txn **tidptr)

fetchlock(struct db *db, const char *key, size_t keylen, const char **data, size_t *datalen, struct txn **tidptr)

Fetch the value for the exact key given by key and keylen. If data is not NULL, set datalen and return a valid pointer to the start of the value.

Fetchlock is identical to fetch, but gives a hint to the database that the record is likely to be modified soon.

NOTE: it is possible to store a key with a zero length data record, in which case *datalen will be set to zero, and *data will be set to a non-NULL value

It is an error to call fetch with a NULL key or a zero keylen

It is an error to call fetch with a NULL datalen and a non-NULL data, however it is acceptable to call with a NULL data and a non-NULL datalen if you are only interested in the length

Errors:

  • CYRUSDB_IOERROR - if any error occurs reading from the database
  • CYRUSDB_LOCKED - if tidptr is incorrect
  • CYRUSDB_NOTFOUND - if there is no record that matches the key

foreach(struct db *db, const char *prefix, size_t prefixlen, foreach_p *goodp, foreach_p *procp, void *rock, struct txn **tidptr)

Iterate over all records matching the given prefix, in database order (which may be MBOXLIST sort, depending on the parameters given to open

It is legal to give a NULL pointer as prefix if prefixlen is zero, in which case it will return all records in the database. It is an error to give a non-zero prefixlen with a NULL prefix.

goodp - this function is only used for deciding if the record needs to be further processed. It can be used for basic filtering, and returns true (non-zero) to process, or zero to skip and move straight to the next record. Because goodp can't make any database changes, it doesn't break the lock, so it's faster to use goodp to filter records if you don't need to process all of them. NULL is a legal value for goodp, and means that all records will be processed.

procp - procp is the main callback function. If you use foreach in non-transactional mode, the database is unlocked before calling procp, and locked again afterwards. You are allowed to add, delete or modify values in the same database from within procp. If procp returns non-zero, the foreach loop breaks at this point, and the return value of the foreach becomes the return value of procp. If procp returns zero, the foreach loop will continue at the NEXT record by sort order, regardless of whether the current record has changed or been removed. procp MUST NOT be NULL.

Errors:

  • procp_result - whatever your callback returns
  • CYRUSDB_IOERROR - if any error occurs while reading
  • CYRUSDB_LOCKED - if tidptr is incorrect

create(struct db *db, const char *key, size_t keylen, const char *data, size_t datalen, struct txn **tidptr)

store(struct db *db, const char *key, size_t keylen, const char *data, size_t datalen, struct txn **tidptr)

Create a new record or replace an existing one. The only difference between these two is that create will return an error if the record already exists, while store will replace it

If tidptr is NULL, create/store will take a write lock for the duration of the action.

Any failure during create/store will abort the current transaction as well as returning an error

It is legal to pass NULL for the data field ONLY if datalen is zero. It is not legal to pass NULL for key or zero for keylen

Errors:

  • CYRUSDB_IOERROR - any error to write to the database
  • CYRUSDB_LOCKED - if tidptr is incorrect
  • CYRUSDB_EXISTS - if create is called on an existing key
  • CYRUSDB_AGAIN - if a deadlock is created. The current transaction has been aborted, but a retry may succeed

delete(struct db *db, const char *key, size_t keylen, struct txn **tidptr, int force)

Delete the given record from the database. If force is true, then succeed even if the record doesn't currently exist.

It is not legal to pass NULL for key or zero for keylen

Errors:

  • CYRUSDB_IOERROR - any error to write to the database
  • CYRUSDB_LOCKED - if tidptr is incorrect
  • CYRUSDB_NOTFOUND - if force is not set and the key doesn't exist
  • CYRUSDB_AGAIN - if a deadlock is created. The current transaction has been aborted, but a retry may succeed

commit(struct db *db, struct txn *tid)

Commit the current transaction. tid will not be valid after this call, regardless of success

If the commit fails, it will attempt to abort the transaction

Errors:

  • CYRUSDB_IOERROR - any error to write to the database
  • CYRUSDB_LOCKED - if tidptr is incorrect
  • CYRUSDB_AGAIN - if a deadlock is created. The current transaction has been aborted, but a retry may succeed

abort(struct db *db, struct txn *tid)

Abort the current transaction. tid will not be valid after this call, regardless of success

Attempt to roll back all changes made in the current transaction.

Errors:

  • CYRUSDB_IOERROR - any error to write to the database
  • CYRUSDB_LOCKED - if tidptr is incorrect

dump(struct db *db, int detail)

Optional function to dump the internal structure of the database to stdout for debugging purposes. Don't use.

consistent(struct db *db)

Check if the DB is internally consistent. Looks pretty bogus, and isn't used anywhere. Don't use.

cyrus-imapd-2.5.10/doc/internal/replication_examples.html0000644000175000017500000001171012772415051020437 00000000000000 Cyrus IMAP Server: Replication Examples

Cyrus IMAP Server: Replication Examples

Introduction

The replication system creates a link between two Cyrus mailstores: a master and a replica system. Both systems can be live mailstores with active users: here in Cambridge we install systems in pairs.

Typically half of the users will be using each system, and each system replicates to its partner. In the event of a failover everyone uses the remaining system in a pair. This is typically safe as the IMAP/POP/SMTP servers define which of the two systems is the live server for any given account, and the replica just plays a game of follow my leader.

Occasionally I think about introducing some form of sanity check so that we have to explicitly issue a command to the remaining backend system as well as the proxies in the event of a failover.

A short example of replication in action

Index:

  #: Annotation
  C: Command issued by client
  S: Command issued by server

# Authentication between systems is done using SSH key based authentication:

C: $ ssh -x cyrus-2 /usr/local/cyrus/bin/sync_server
S: * Sync Server v0.0 [EXPERIMENTAL]

# Create new auth_state and ask for all information about given list of
# folders (namely user.dpc22). Returns:
#
#   "**" unsolicited response for each mailbox. Returns:
#      Folder UniqueID, Name, ACL, UIDlast, timestamp for last seen update.
#
#   "*" response for each mail message in folder:
#      UID, GUID, flags (other than \Seen state)

C: user_some dpc22 user.dpc22
S: ** 6b98205c796c6c61 user.dpc22 \
S:     "dpc22   lrswipcda       anonymous       0      " 4151 1062945305
S: * 1 000000000000000000000000 ()
S: * 3697 0101003f4c56b00545000000 ()
S: * 3919 0101003f4c56b04b2900000d ()
S: * 3937 0101003f4c56b0514900001f ()
S: * 4066 0101003f4c56b07422000002 ()
S: * 4089 0101003f4c56b07e56000023 (\answered)
S: * 4118 0101003f4c56b08328000016 ()
S: * 4131 0101003f4c56b084d7000002 ()
S: * 4136 0101003f4c56b087f3000001 ()
S: * 4140 0101003f4c56b08c9d000026 ()
S: OK User_Some finished

# Select a folder to work with

C: select user.dpc22
S: OK 6b98205c796c6c61 4151 1062945305

# Remove message with UID "1" from folder list (message which has been
# sitting in my inbox since January, has no GUID defined)

C: expunge 1
S: OK Expunge Complete

# Set some user flags on message UID "4140"

C: setflags 4140 (hello world)
S: OK Updated flags on 1 messages okay

# Demonstrate that something has changed:

C: status
S: * 3697 0101003f4c56b00545000000 ()
S: * 3919 0101003f4c56b04b2900000d ()
S: * 3937 0101003f4c56b0514900001f ()
S: * 4066 0101003f4c56b07422000002 ()
S: * 4089 0101003f4c56b07e56000023 (\answered)
S: * 4118 0101003f4c56b08328000016 ()
S: * 4131 0101003f4c56b084d7000002 ()
S: * 4136 0101003f4c56b087f3000001 ()
S: * 4140 0101003f4c56b08c9d000026 (hello world)
S: OK 4151

# Now lets correct the damage that we just inflicted:

C: $ replicate -s cyrus-2 -v -v -m user.dpc22
S: MAILBOXES user.dpc22
S: USER_SOME dpc22 user.dpc22
S: SELECT user.dpc22
S: SETFLAGS [1 msgs]
S: UPLOAD [1 msgs]
S: SETSEEN dpc22 ...
S: ENDUSER

C: $ ssh -x cyrus-2 /usr/local/cyrus/bin/sync_server
S: * Sync Server v0.0 [EXPERIMENTAL]
S: user_some dpc22 user.dpc22
S: ** 6b98205c796c6c61 user.dpc22 \
S:    "dpc22   lrswipcda       anonymous       0      " 4156 1062968731
S: * 1 000000000000000000000000 ()
S: * 3697 0101003f4c56b00545000000 ()
S: * 3919 0101003f4c56b04b2900000d ()
S: * 3937 0101003f4c56b0514900001f ()
S: * 4066 0101003f4c56b07422000002 ()
S: * 4089 0101003f4c56b07e56000023 (\answered)
S: * 4118 0101003f4c56b08328000016 ()
S: * 4131 0101003f4c56b084d7000002 ()
S: * 4136 0101003f4c56b087f3000001 ()
S: * 4140 0101003f4c56b08c9d000026 ()
S: OK User_Some finished

# Back where we started: the replication engine reinserted message UID 0
# which was missing, and removed "hello world" from message UID 4140

Tracking messages between folders

# I've just saved a message from my inbox into a folder named "zzz",
# creating the folder the process.

C: $ replicate -s cyrus-2 -v -v -m user.dpc22 user.dpc22.zzz

Replication action on two MAILBOX objects:

S: MAILBOXES user.dpc22 user.dpc22.zzz

Ask server for contents of the two folders:

S:   USER_SOME dpc22 ...

Reserve message with given GUID in user.dpc22 so that it can be moved

S:   RESERVE user.dpc22 ...

Remove message from source folder (reserved copy left behind)

S:   SELECT user.dpc22
S:   EXPUNGE [1 msgs]
S:   SETSEEN dpc22 ...

Create target folder and copy in message that we reserved (doesn't have to
be uploaded again)

S:   CREATE user.dpc22.zzz 7f6f384c3f5ba99a
S:      "dpc22        lrswipcda       anonymous       0       " 0 1062971802
S: SELECT user.dpc22.zzz
S: UPLOAD [1 msgs]
S: SETSEEN dpc22 ...
S: ENDUSER
cyrus-imapd-2.5.10/doc/internal/database-formats.html0000644000175000017500000002216013001236020017425 00000000000000 Database Formats

Database Formats

Introduction

This is an attempt to document the cyrus database formats. It should not be considered authoritative and is subject to change.

No external tools should make use of this information. The only supported method of access to the databases is via the API specific to the database and the underlying cyrusdb interface.

Mailbox List (mailboxes.db)

This database contains the master list of all mailboxes on the system. The database is indexed by mailbox name and each data record contains the mailbox type, the partition on which the mailbox resides and the ACL on the mailbox. The format of each record is as follows:

Key: <Mailbox Name>

Data: <Type Number>SP<Partition>SP<ACL (space-separated userid/rights pairs)>

Annotations (annotations.db)

This database contains mailbox and server annotations. The database is indexed by mailbox name (empty for server annotations) + annotation name + userid (empty for shared annotations) and each data record contains the value size, value data, content-type of the data and timestamp of the record. The format is each record is as follows:

Key: <Mailbox Name>\0<Annotation Name>\0<Userid>\0

Data: <Value Size (4 bytes)><Value>\0<Content-Type>\0<Timestamp (4 bytes)>

Quotas (quotas.db)

This database contains the master list of quotaroots on the system. The database is indexed by quota root and each data record contains the current usage of all mailboxes under the quota root and the limit of the quota root. The format of each record is as follows:

Key: <Quota Root>

Data: <Usage (in bytes)>SP<Limit (in Kbytes)>

Legacy Quotas

The legacy quota database uses a distributed system in which each quota root is stored in a separate file named by quota root and the contents has the following format:

<Usage (in bytes)>\n
<Limit (in Kbytes)>\n

The translation to/from this data record format is handled by the quota_legacy cyrusdb backend.

Duplicate Delivery (deliver.db)

This database is used for duplicate delivery suppression, retrieving usenet articles by message-id, and tracking Sieve redirects and vacation responses. The database is indexed by message-id + recipient (either mailbox or email address) and each data record contains the timestamp of the record and the UID of the message within the mailbox (if delivered locally). The format of each record is as follows:

Key: <Message-ID>\0<Recipient>\0

Data: <Timestamp (4 bytes)><Message UID (4 bytes)>

TLS cache (tls_sessions.db)

This database caches SSL/TLS sessions so that subsequent connections using the same session-id can bypass the SSL/TLS handshaking, resulting is shorter connection times. The database is indexed by session-id and each data record contains the timestamp of the record and the ASN1 representation of the session data. The format of each record is as follows:

Key: <Session-ID (multi-byte)>

Data: <Timestamp (4 bytes)><Session Data (multi-byte)>

PTS cache (ptscache.db)

This database caches authentication state records, resulting in shorter authentication/canonicalization times. The database is indexed by userid and each data record contains an authentication state for the userid. The format of each record is as follows:

Key: <Userid>

Data: <Auth State (multi-byte)>

STATUS cache (statuscache.db)

This database caches IMAP STATUS information resulting in less I/O when the STATUS information hasn't changed (mailbox and \Seen state unchanged). The database is indexed by mailbox name + userid and each data record contains the database version number, a bitmask of the stored status items, the mtime, inode, and size of the cyrus.index file at the time the record was written, the total number of messages in the mailbox, the number of recent messages, the next UID value, the mailbox UID validity value, the number of unseen messages, and the highest modification sequence in the mailbox. The format of each record is as follows:

Key: <Mailbox Name>\0<Userid>\0

Data: <Version>SP<Bitmask of Items>SP<Mtime of Index>SP<Inode of Index>SP<Size of Index>SP<# of Messages>SP<# of Recent Messages>SP<Next UID>SP<UID Validity>SP<# of Unseen Messages>SP<Highest Mod Sequence>

User Access (user_deny.db)

This database contains a list of users that are denied access to Cyrus services. The database is indexed by userid and each data record contains the database version number (currently 2), a list of wildmat patterns specifying Cyrus services to be denied, and a text message to be displayed to the user upon denial. The service names to be matched are those as used in cyrus.conf(5). The format of each record is as follows:

Key: <Userid>

Data: <Version>TAB<Deny List (comma-separated wildmat patterns)>TAB<Deny Message>

Timezone Info (zoneinfo.db)

This database is used for the timezone service and contains records relating to timezones and their aliases. The database is indexed by timezone ID and each data record contains the database version number, a record type, a timestamp, and an optional list of strings (either aliases for a timezone or the reference timezone for an alias). The format of each record is as follows:

Key: <TZID>

Data: <Version>SP<Record Type>SP<Timestamp>SP<Data Strings (TAB-separated)>

Seen State (<userid>.seen)

This database is a per-user database and maintains the list of messages that the user has read in each mailbox. The database is indexed by mailbox unique-id and each data record contains the database version number, the timestamp of when a message was last read, the message unique-id of the last read message, the timestamp of the last record change and a list of message unique-ids which have been read. The format of each record is as follows:

Key: <Mailbox UID>

Data: <Version>SP<Last Read Time>SP<Last Read UID>SP<Last Change Time>SP<List of Read UIDs>

Subscriptions (<userid>.sub)

This database is per-user and contains the list of mailboxes to which the user has subscribed. The database is indexed by mailbox name and each data record contains no data. The format of each record is follows:

Key: <Mailbox Name>

Data: None

Mailbox Keys (<userid>.mboxkey)

This database is per-user and contains the list of mailbox access keys which are used for generating URLAUTH-authorized URLs. The database is indexed by mailbox name and each data record contains the database version number and the associated access key. The format of each record is follows:

Key: <Mailbox Name>

Data: <Version (2 bytes)><Access Key (multi-byte)>

DAV Index (<userid>.dav)

This SQLite database is per-user and primarily maintains a mapping from DAV resource names (URLs) to the corresponding Cyrus mailboxes and IMAP message UIDs. The database is designed to have one table per resource type (iCalendar, vCard, etc) with each table containing metadata specific to that resource type.

CalDAV

The format of the iCalendar table used by CalDAV is as follows:

CREATE TABLE ical_objs (
 rowid INTEGER PRIMARY KEY,
 creationdate INTEGER,
 mailbox TEXT NOT NULL,
 resource TEXT NOT NULL,
 imap_uid INTEGER,
 lock_token TEXT,
 lock_owner TEXT,
 lock_ownerid TEXT,
 lock_expire INTEGER,
 comp_type INTEGER,
 ical_uid TEXT,
 organizer TEXT,
 dtstart TEXT,
 dtend TEXT,
 comp_flags INTEGER,
 sched_tag TEXT,
 UNIQUE( mailbox, resource )
);

Because CalDAV Scheduling requires the server to locate a resource by iCalendar UID regardless of which calendar collection (mailbox) it resides in, the iCalendar table has an additional index as follows:

CREATE INDEX idx_ical_uid ON ical_objs ( ical_uid );

CardDAV

The format of the vCard table used by CardDAV is as follows (work in progress):

CREATE TABLE vcard_objs (
 rowid INTEGER PRIMARY KEY,
 creationdate INTEGER,
 mailbox TEXT NOT NULL,
 resource TEXT NOT NULL,
 imap_uid INTEGER,
 lock_token TEXT,
 lock_owner TEXT,
 lock_ownerid TEXT,
 lock_expire INTEGER,
 version INTEGER,
 vcard_uid TEXT,
 kind INTEGER,
 fullname TEXT,
 name TEXT,
 nickname TEXT,
 email TEXT,
 UNIQUE( mailbox, resource )
);
cyrus-imapd-2.5.10/doc/internal/unit-tests.html0000644000175000017500000006250513001236020016336 00000000000000 Unit Tests

Unit Tests

Table of Contents

1. Introduction

Recently, a set of regression unit tests has been added to Cyrus. This document explains the purpose implementation of those unit tests, and gives an example of how to add more unit tests (because there are never enough unit tests!).

2. What Is A Unit Test?

The definition on Wikipedia sheds some light:

...unit testing is a method by which individual units of source code are tested to determine if they are fit for use. A unit is the smallest testable part of an application.
In other words, unit testing is about verifying that small pieces of code, like individual functions, modules, or classes, work in isolation. It is not about testing the system as a whole.

The tests implemenented here are also regression tests, which in Wikipedia's words means:

Regression testing is any type of software testing that seeks to uncover software errors after changes to the program (e.g. bugfixes or new functionality) have been made, by retesting the program. The intent of regression testing is to assure that a change, such as a bugfix, did not introduce new bugs.

In other words, the tests are designed to be easy to run and to work out fully automatically whether they have passed or failed, so that they can be run usefully by people who didn't write them.

3. Running The Tests

This section takes you through the process of running Cyrus' unit tests.

3.1. Setting Up The Machine

Cyrus' unit tests are all located in a new directory, cyrus-imapd/cunit/. They're written in C, like the remainder of Cyrus, and use the CUnit library from SourceForge, with some home grown wrappers and other improvements to make our lives easier.

Your first step is step is to ensure that the CUnit library (including the headers) is installed. Some modern operating systems already have CUnit, for example on Ubuntu you can just do:

me@ubuntu> sudo apt-get install libcunit1-dev

Alternately, you can download the CUnit source, build it and install it. It's not a complicated or difficult library, this shouldn't take long. When you've done, install it in /usr/include and /usr/lib.

3.2 Configure Script

Because of the dependency on the CUnit library, the tests are disabled by default; this means you need enable them with an option to the configure script:

me@mybox> ./configure --enable-unit-tests ... checking for CU_initialize_registry in -lcunit... yes checking CUnit/CUnit.h usability... yes checking CUnit/CUnit.h presence... yes checking for CUnit/CUnit.h... yes ...

3.3 Make

First you need to build Cyrus itself, using the traditional all: target.

me@mybox> make all ...

Then, use the new check: target to build and run the unit tests.

me@mybox> make check cd . && /bin/bash /home/me/cyrus-imapd/missing --run automake-1.11 --foreign Makefile cd . && /bin/bash ./config.status Makefile depfiles (a) config.status: creating Makefile config.status: executing depfiles commands ... make[3]: Entering directory `/home/me/cyrus-imapd' make[3]: `sieve/test' is up to date. cunit/cunit.pl --project cunit/default.cunit --generate-wrapper cunit/mboxname.testc (b) gcc -DHAVE_CONFIG_H ... -c -o cunit/mboxname.o cunit/mboxname.testc-cunit.c rm -f cunit/mboxname.testc-cunit.c /bin/bash ./libtool --tag=CC --mode=link gcc -fPIC -g -O2 -o cunit/unit cunit/unit.o ... lib/libcyrus_min.la ... (c) ... Running unit tests (d) CUnit - A Unit testing framework for C - Version 2.1-0 http://cunit.sourceforge.net/ ... Suite: mboxname (e) Test: dir_hash_c ... passed Test: to_parts ... passed Test: to_userid ... passed Test: to_usermbox ... passed ... --Run Summary: Type Total Ran Passed Failed (f) suites 34 34 n/a 0 tests 323 323 323 0 asserts 1079745 1079745 1079745 0 make[1]: Leaving directory `/home/me/cyrus-imapd/cunit'

Let's take a closer look at what's happening here.

(a)
The check: target causes automake to re-run itself. This is normal automake behaviour. Note that the older build system used to run make recursively in sub-directories, the newer automake-based system builds everything from the top directory.
(b)
The cunit/ directory contains a number of C source files (called, for reasons too complicated to explain here, whatever.testc) with test code in them. For each of those, a small wrapper C source file is generated and then compiled into an object file.
(c)
Finally, all the compiled object files are linked into an executable, with a main() routine from unit.c, and a number of libraries and object files from other parts of the Cyrus tree.
(d)
The resulting executable is then run.
(e)
The test executable runs all the built tests one by one, telling us which ones passed and which ones failed as it runs them. You can also run it manually with the name of a test as an argument, and it will run only the named test.
(f)
At the end, the text executable prints a summary of how many tests it ran and how many passed and failed. The key thing to look at here is the rightmost column, it should be all zero.

3.4 Using Valgrind

Some failure modes are subtle, and cannot be detected in the C code itself; this is where the Valgrind program comes in very handy. It detects buffer overruns and memory leaks and various other kinds of subtle errors.

To run the unit tests with Valgrind, use the new valgrind: target.

me@mybox> make valgrind ... valgrind --tool=memcheck --leak-check=full ./unit -v (a) ==2999== Memcheck, a memory error detector ==2999== Copyright (C) 2002-2010, and GNU GPL'd, by Julian Seward et al. ==2999== Using Valgrind-3.6.0.SVN-Debian and LibVEX; [...] ==2999== Command: ./unit -v ==2999== ... --Run Summary: Type Total Ran Passed Failed (b) suites 9 9 n/a 0 tests 51 51 50 1 asserts 474 474 473 1 ... ==2999== HEAP SUMMARY: (c) ==2999== in use at exit: 4,489 bytes in 134 blocks ==2999== total heap usage: 715 allocs, 581 frees, 352,763 bytes allocated ==2999== ==2999== 4 bytes in 1 blocks are definitely lost in loss record 3 of 50 ==2999== at 0x4C2815C: malloc (vg_replace_malloc.c:236) ==2999== by 0x44A0CA: xmalloc (xmalloc.c:57) ==2999== by 0x4399D8: strconcat (util.c:631) ==2999== by 0x40C059: test_uncast_null (strconcat.c:51) ==2999== by 0x61B32A9: ??? (in /usr/lib/libcunit.so.1.0.1) ==2999== by 0x61B36ED: ??? (in /usr/lib/libcunit.so.1.0.1) ==2999== by 0x61B3827: CU_run_all_tests (in /usr/lib/libcunit.so.1.0.1) ==2999== by 0x4066CC: run_tests (unit.c:144) ==2999== by 0x406806: main (unit.c:283) ==2999== ...

Here's an explanation of what's happening in the example.

(a)
The test executable is run as before, but using the valgrind program. The first thing we see is Valgrind's banner message.
(b)
The test executable proceeds as normal and eventually emits it's run summary, then exits.
(c)
After the test executable exits, Valgrind checks for memory leaks and prints both a summary of all leaks and a stack trace showing where each block of leaked memory was allocated.

I'd just like to say that I love Valgrind and I think it's immensely useful. I would have made running the tests under Valgrind the only option for the check: target, except that Valgrind is not available on all of Cyrus' supported platforms.

3.5 The Tests Are Failing

So you've noticed that some of the tests are failing. Let me make the guiding principle of unit testing as clear as possible: THE UNIT TESTS SHOULD NOT FAIL. All of the tests are designed to pass all the time, in everyone's environment. The unit tests are run automatically every twelve hours on the Cyrus Continuous Integration server, and a failing test fails the whole build and makes people unhappy.

There are a few rules which you should follow to help us all get the most benefit out of unit testing

  • If you see a test failing, investigate it.
  • If you can't investigate, complain on the mailing list or raise a bug so that somebody else can investigate.
  • When writing tests, write them to work in all environments and all combinations of configure script options. It's ok to have a test which is empty in some circumstances; it's not ok to have a test that fails.
  • When adding code, write new tests for the new code.
  • When modifying code, write new tests for the new behaviour.
  • When looking at old code, also take a look at the coverage report and consider writing tests for the existing code.

3.6 Debugging A Test

With the new Cyrus build system, the file cunit/unit is no longer an executable, it's a shell script which sets up some environment variables before running the real executable which is hidden away. This makes debugging a failing test somewhat challenging. The solution is:

me@mybox> ( cd cunit ; libtool --mode=execute gdb --args unit -t crc32 ) ... Reading symbols from /home/me/cyrus-imapd/cunit/.libs/lt-unit...done. (gdb) list crc32.testc:1 1 /* Unit test for lib/crc32.c */ 2 #include "cunit/cunit.h" 3 #include "crc32.h" ... (gdb) break test_map Breakpoint 1 at 0x44a2f8: file ./cunit/crc32.testc, line 11. (gdb) run Starting program: /home/me/cyrus-imapd/cunit/.libs/lt-unit -t -v crc32 [Thread debugging using libthread_db enabled] CUnit - A Unit testing framework for C - Version 2.1-0 http://cunit.sourceforge.net/ Suite: crc32 Test: map ... Breakpoint 1, test_map () at ./cunit/crc32.testc:11 11 c = crc32_map(TEXT, sizeof(TEXT)-1); (gdb)

Note the -t option. This turns off test timeouts, which is very useful for manual debugging.

4. Adding Your Own Tests

Adding your own tests is quite simple. Here's how.

4.1 Where To Put Your Tests

The unit test code in Cyrus is contained in a set of C source files in the cunit directory. For reasons too complex to go into here, these are named whatever.testc instead of the more usual whatever.c. If you look closely, you will see that each of those C source files maps to a "Suite" in CUnit parlance. For example, cunit/glob.testc is listed as the Suite "glob" in CUnit's runtime output.

Typically, each Suite tests a single module or a related set of functions; for example, cunit/glob.testc contains tests for the glob module in lib/glob.c.

So, if you want to add a new test for a module which already has some existing tests, the sensible thing to do is to add a new test to the existing suite. Otherwise, you'll need to add a new Suite.

4.1 Adding A New Suite

Each Suite is a single C source file in the cunit/ directory. Your first step is to create a new C source file. For this example, you'll create a new Suite to test the CRC32 routines which live in lib/crc32.c.

me@mybox> vi cunit/crc32.testc ...

The file should contain something like this.

/* Unit test for lib/crc32.c */ #include "cunit/cunit.h" (a) #include "crc32.h" (b) static void test_map(void) (c) { static const char TEXT[] = "lorem ipsum"; (d) static uint32_t CRC32 = 0x0; uint32_t c; (e) c = crc32_map(TEXT, sizeof(TEXT)-1); (f) CU_ASSERT_EQUAL(c, CRC32); (g) }

Here's an explanation of what all these bits are for.

(a)
You need to include the header "cunit/cunit.h", which is a thin Cyrus wrapper around the CUnit's library's header, <CUnit/CUnit.h> with some extra conveniences.
(b)
You should also include any headers you need for declarations of the functions which you'll be testing. Note that the Cyrus lib/ and imap/ directories are already in the include path, so any header in there can be included without the directory prefix, e.g. "crc32.h" for lib/crc32.h.
(c)
You need to have at least one function which looks like this: it takes no arguments, returns void, and is named test_whatever. It may be static or extern, but I recommend static. Functions with this signature are automatically discovered in the source code by the Cyrus unit test infrastructure, so all you have to do is write the function. Later, a CUnit test named "whatever" will be created automatically for your test_whatever function.
(d)
Here's a good place to define the test inputs and expected outputs. Note that for this example you have no idea of the actual correct output. The right thing to do there is to manually calculate the expected result from first principles, or to use a different piece of software which you believe to be working. For this example, let's just use a known incorrect value and see what happens.
(e)
Here's a good place for local variables you need during the test.
(f)
Call the function under test (crc32_map() in this example) with known inputs, and capture the results in a local variable c.
(g)
Compare the actual result in c with the expected result in CRC32. The CU_ASSERT_EQUAL() macro checks that it's two arguments are equal (using an integer comparison), and if they're different it prints a message and records a failure. Note that unlike the libc assert() macro, control will continue even if the assert fails. The CUnit library provides a whole family of similar macros, see the online CUnit documentation for more details.

Now you need to tell the Cyrus build system about your new Suite.

me@mybox> vi Makefile.am ...

You need to add the filename of your new test to the definition of the cunit_TESTS variable.

cunit_TESTS = \ cunit/annotate.testc \ cunit/backend.testc \ cunit/binhex.testc \ cunit/bitvector.testc \ cunit/buf.testc \ cunit/byteorder64.testc \ cunit/charset.testc \ cunit/crc32.testc \ cunit/db.testc \ cunit/dlist.testc \ cunit/duplicate.testc \

At this point you should be able to just rebuild and rerun using make check. You can also just rebuild without rerunning by using the command make cunit/unit.

Note that sometimes this doesn't quite work right, and you may be able to work around this problem using the command rm cunit/default.cunit.

me@mybox> make check ... ../cunit/cunit.pl [...] --add-sources [...] crc32.testc ... ../cunit/cunit.pl [...] --generate-wrapper crc32.testc gcc -c [...] -g -O2 .cunit-crc32.c gcc [...] -o unit [...] .cunit-crc32.o ... Running unit tests CUnit - A Unit testing framework for C - Version 2.1-0 http://cunit.sourceforge.net/ ... Suite: crc32 Test: map ... FAILED 1. crc32.testc:12 - CU_ASSERT_EQUAL(c=1926722702,CRC32=0)

Note how the test failure told us which in source file and at what line number the failure occurred, and what the actual and expected values were. Let's go and fix that up now.

static const char TEXT[] = "lorem ipsum"; static uint32_t CRC32 = 0x72d7748e;

Re-run make check and you'll see your test being rebuilt and rerun, and this time passing.

me@mybox> make check ... ../cunit/cunit.pl [...] --generate-wrapper crc32.testc gcc -c [...] -g -O2 .cunit-crc32.c gcc [...] -o unit [...] .cunit-crc32.o ... Running unit tests CUnit - A Unit testing framework for C - Version 2.1-0 http://cunit.sourceforge.net/ ... Suite: crc32 Test: map ... passed

4.2 Adding A Test To A Suite

Adding a new test to an existing test is easy: all you have to do is add a new function to an existing C source file in the cunit/ directory. As an example, let's add a test for the crc_iovec() function.

me@mybox> vi cunit/crc32.testc ...
static void test_iovec(void) (a) { static const char TEXT1[] = "lorem"; (b) static const char TEXT2[] = " ipsum"; static uint32_t CRC32 = 0x72d7748e; uint32_t c; (c) struct iovec iov[2]; memset(iov, 0, sizeof(iov)); (d) iov[0].iov_base = TEXT1; iov[0].iov_len = sizeof(TEXT1)-1; iov[1].iov_base = TEXT2; iov[1].iov_len = sizeof(TEXT2)-1; c = crc32_iovec(iov, 2); (e) CU_ASSERT_EQUAL(c, CRC32); (f) }

Here's an explanation of what all these bits are for.

(a)
Your new test function should look like this: it takes no arguments, returns void, and is named test_whatever. It may be static or extern, but I recommend static. Functions with this signature are automatically discovered in the source code by the Cyrus unit test infrastructure, so all you have to do is write the function. Later, a CUnit test named "whatever" will be created automatically for your test_whatever function. Note that the opening curly brace must be on the next line or the unit test infrastructure will not find the function.
(b)
Here's a good place to define the test inputs and expected outputs.
(c)
Here's a good place for local variables you need during the test.
(d)
Here you set up the input conditions for the function under test.
(e)
Call the function under test with your known inputs, and capture the results in a local variable, here c.
(f)
Compare the actual result in c with the expected result in CRC32. The CU_ASSERT_EQUAL() macro checks that it's two arguments are equal (using an integer comparison), and if they're different it prints a message and records a failure. Note that unlike the libc assert() macro, control will continue even if the assert fails. The CUnit library provides a whole family of similar macros, see the online CUnit documentation for more details.

Now run make check and you'll see your test being built and run.

me@mybox> make check ... ../cunit/cunit.pl [...] --generate-wrapper crc32.testc gcc -c [...] -g -O2 .cunit-crc32.c gcc [...] -o unit [...] .cunit-crc32.o ... Running unit tests CUnit - A Unit testing framework for C - Version 2.1-0 http://cunit.sourceforge.net/ ... Suite: crc32 Test: map ... passed Test: iovec ... passed

4.3 Suite Setup And Teardown

Sometimes the behaviour of the functions under test depend on external influences such as environment variables, global variables, or the presence of certain files.

These kinds of functions need special treatment to ensure that their behaviour is locked down during the running of your tests. Otherwise, all sorts of strange behaviour may confuse the results of the tests. For example, a test might succeed the first time it's run in a given directory and fail the next time. Or a test might succeed when run by the author of the test but fail when run by another user.

CUnit provides a special arrangement which helps you in such cases: the suite initialisation and cleanup functions. These are two functions that you write and which live in the suite source. They are called from CUnit respectively before any of the tests in the suite is run, and after all tests from that suite are run.

Here's how to use them. The suite setup function should set up any global state that the functions under test rely on, in such a way that their state is predictable and always the same no matter who runs the test or when or how many times. Similarly the suite teardown function should clean up any state which might possibly interfere with other test suites. Note that some suites will need an setup function but not necessarily a teardown function.

Adding these functions is very easy: you just write functions of the appropriate signature (names, arguments and return type) and the Cyrus unit test infrastructure will automatically discover them and arrange for them to be called. The functions should look like (actual example taken from cunit/mboxname.testc) this:

static enum enum_value old_config_virtdomains; static int set_up(void) { old_config_virtdomains = config_virtdomains; config_virtdomains = IMAP_ENUM_VIRTDOMAINS_ON; return 0; } static int tear_down(void) { config_virtdomains = old_config_virtdomains; return 0; }

The functions should return 0 on success, and non-zero on error. They must not call and CU_* functions or macros.

Good luck and good testing!

cyrus-imapd-2.5.10/doc/internal/locking0000644000175000017500000000013712772415051014714 00000000000000In an ideal world, our locking order is: cyrus.header cyrus.index quota seen mailboxes file cyrus-imapd-2.5.10/doc/internal/cyrus.css0000644000175000017500000000126313001236020015202 00000000000000/* * Basic style sheet for Cyrus internal documentation. * Because if I have to write it, it will at least look nice. */ body, p, blockquote { font-family: Helvetica,Verdana,Ariel,sans; font-size: 12pt; color: black; background: #f8f8ff; } h1, h2, h3 { font-family: Helvetica,Verdana,Ariel,sans; color: black; background: #f8f8ff; } h1 { font-size: 18pt; } h2 { font-size: 14pt; } h3 { font-size: 12pt; } blockquote.src, blockquote.cmds { font-family: Courier,fixed; font-size: 12pt; color: black; background: #c0c0c0; white-space: pre; } span.note { color: #c04040; font-weight: bold; } span.lineno { color: #707070; } ul.toc { list-style-type: none; } cyrus-imapd-2.5.10/doc/internal/replication_protocol.html0000644000175000017500000000414012772415051020461 00000000000000 Cyrus IMAP Server: Replication Protocol v2.4+

Cyrus IMAP Server: Replication Protocol v2.4+

DList 1.0

The DList protocol is based closely on the IMAP wire protocol, using atoms and literals as the basis, but with two extended types of data:

  • kvlist
  • rfc822-object
A wart of the protocol is the rfc822-object, which contains an explicit cyrus backend partition. This will be removed in future versions of Cyrus.

types

atom

An atom is actually a sequence of any character other than '\0', the NULL byte. Character encoding is not specified, but it can contain 8 bit characters, and is probably utf8

flag

Flag is a horrible special case of atom to allow \word to be represented as an IMAP atom on the wire. This is one of many special cases in the IMAP protocol, and is duplicated into dlist just to make it easier to read

num32/num

Both stored as 64 bit integers internally, and sent as decimal numbers over the wire, this type exists only in the API, it just looks like a string on the wire.

hex32/hex

Stored like num internally, but sent as an 8 or 16 character hexadecimal string on the wire

map

Like atom, but can contain NULL. All values are parsed off the wire as 'map' type and then converted on demand into the requested type

list

Encoded in parentheses like so (item item item) a list type can be nested inside other lists: (item (sub sub) item)

kvlist

A kvlist allows named parameters, and is indicated with a leading % character. % is invalid in atoms, so parsing is unambiguous, e.g:

%(key1 value1 key2 (list of values) key3 value3)

rfc822-object/file

Finally the ugly one. These look like a literal, but with a leading % and two more fields:

%{partition sha1 size}\r\n
data
cyrus-imapd-2.5.10/doc/internal/improved_mboxlist_sort.html0000644000175000017500000000204512734634210021044 00000000000000 Enabling improved_mboxlist_sort

Enabling improved_mboxlist_sort

You can't enable and disable improved_mboxlist_sort on a live system. You need to dump and load the necessary database after stopping and before starting the master process.

Dumping the mailboxes.db file

ctl_mboxlist -d > /var/tmp/mailboxes.txt
ctl_mboxlist -u < /var/tmp/mailboxes.txt

If your subscription databases are not in flat files you need to do something similar. Each user will have his own subscription file. Do the following for each subscription file.

cyr_dbtool -C $file skiplist show > $file.TXT
cyr_dbtool -n $file skiplist set < $file.TXT

The above fragments will overwrite the original file. So you could redirect to a temporary file and overwrite the database if the import succeeds.

cyrus-imapd-2.5.10/doc/internal/prot.html0000644000175000017500000000547712772415051015231 00000000000000 prot layer

prot layer

The prot layer, defined in prot.h, is a stdio replacement for network i/o. It does the standard buffering of input and output and allows certain operations especially suited for request/response protocols like IMAP.

Events

The prot layer allows "events" to be associated with each prot stream. These events are trigger at the given time or after when the protstream is attempted to be read from.

An event is currently represented by the following datastructure:

struct prot_waitevent;

typedef struct prot_waitevent *prot_waiteventcallback_t(struct protstream *s,
                            struct prot_waitevent *ev,
                            void *rock);

struct prot_waitevent {
    time_t mark;
    prot_waiteventcallback_t *proc;
    void *rock;
    struct prot_waitevent *next;
};

The application is currently allowed to modify mark, proc, and rock as desired when there are no active calls to a prot function on the stream which this event is associated.

The API is as follows:
  • Use prot_addwaitevent() to add an event callback onto the stream:
    extern struct prot_waitevent *prot_addwaitevent(struct protstream *s,
                            time_t mark,
                            prot_waiteventcallback_t *proc,
                            void *rock);
    
    where s is the stream to add the event to, mark is the time to trigger the event, proc is the callback to make, and rock is an opaque data item handed to the callback. It returns a pointer to the event structure; this is the pointer that must be used to remove the event or modify it in some way.
  • Use prot_removewaitevent() to remove an event:
    extern void prot_removewaitevent(struct protstream *s,
                     struct prot_waitevent *event);
    
    It requires event to have been returned from prot_addwaitevent() previously. No further references are allowed to event or its fields. event->rock is not free'd nor examined in any way. This function may be called while inside the callback event->proc(). If an event is removed inside of its callback, that callback must return NULL.

Some common things to do with events:

  • To reschedule an event ev, simply set ev->mark to the next time it should trigger. If currently in ev->proc(), it should return ev.

last modified: $Date: 2003/08/06 21:28:05 $ cyrus-imapd-2.5.10/doc/internal/master-state-machine.fig0000644000175000017500000001446313001236020020033 00000000000000#FIG 3.2 Landscape Center Inches Letter 100.00 Single -2 1200 2 6 3375 2550 4650 3900 6 3375 2550 4650 3825 4 0 0 50 -1 0 12 0.7854 4 180 1500 3516 3741 SIGCHLD(service)\001 -6 4 0 0 50 -1 0 12 0.7854 4 135 675 3675 3900 nactive--\001 -6 6 4050 9525 4950 9900 4 0 0 50 -1 0 12 0.0000 4 135 855 4050 9675 Connection\001 4 0 0 50 -1 0 12 0.0000 4 90 660 4050 9900 nconn++\001 -6 6 2625 6900 3975 8175 6 2700 6900 3975 8175 4 0 0 50 -1 0 12 5.4978 4 180 1500 2797 7041 SIGCHLD(service)\001 -6 4 0 0 50 -1 0 12 5.4978 4 135 675 2638 7200 nactive--\001 -6 6 2100 450 4350 900 4 0 0 50 -1 0 12 0.0000 4 180 2205 2100 600 Child in illegal state detected\001 4 0 0 50 -1 0 12 0.0000 4 180 1770 2100 825 (via message handling)\001 -6 6 11100 3450 13125 3825 4 0 0 50 -1 0 12 0.0000 4 180 1965 11100 3600 ConnectionMulti(service)\001 4 0 0 50 -1 0 12 0.0000 4 90 660 11100 3825 nconn++\001 -6 6 8100 5850 9450 7350 4 0 0 50 -1 0 12 0.7854 4 180 1605 8210 7116 Unavailable(service)\001 4 0 0 50 -1 0 12 0.7854 4 180 1155 8369 7275 readyworkers--\001 -6 6 8925 6300 10200 7725 4 0 0 50 -1 0 12 0.7854 4 180 1425 9055 7470 Available(service)\001 4 0 0 50 -1 0 12 0.7854 4 180 1245 9214 7630 readyworkers++\001 -6 6 8100 8250 10125 8700 4 0 0 50 -1 0 12 0.0000 4 180 1965 8100 8400 ConnectionMulti(service)\001 4 0 0 50 -1 0 12 0.0000 4 180 1950 8100 8625 nconn++ readyworkers++\001 -6 6 8325 1875 9975 3450 4 0 0 50 -1 0 12 5.4978 4 180 1965 8484 2016 ConnectionMulti(service)\001 4 0 0 50 -1 0 12 5.4978 4 90 660 8325 2175 nconn++\001 -6 6 11175 9075 12900 9825 2 1 1 1 0 7 50 -1 -1 4.000 0 0 -1 0 0 2 11175 9225 11850 9225 2 1 0 1 0 7 50 -1 -1 4.000 0 0 -1 0 0 2 11175 9525 11850 9525 2 1 2 1 0 7 50 -1 -1 3.000 0 0 -1 0 0 2 11175 9825 11850 9825 4 0 0 50 -1 0 12 0.0000 4 135 975 11925 9825 Initial States\001 4 0 0 50 -1 0 12 0.0000 4 180 795 11925 9525 Messages\001 4 0 0 50 -1 0 12 0.0000 4 180 555 11925 9225 Signals\001 -6 6 9750 375 12825 1350 4 0 0 50 -1 0 36 0.0000 4 495 2925 9750 750 Cyrus Master\001 4 0 0 50 -1 0 36 0.0000 4 375 3060 9750 1350 State Machine\001 -6 6 8100 9075 9975 9525 4 0 0 50 -1 0 12 0.0000 4 180 1560 8100 9225 Connection(service)\001 4 0 0 50 -1 0 12 0.0000 4 180 1860 8100 9450 nconn++ readyworkers--\001 -6 6 10050 2400 12000 2775 4 0 0 50 -1 0 12 0.0000 4 180 1935 10050 2550 New Service (nactive++)\001 4 0 0 50 -1 0 12 0.0000 4 135 645 10050 2775 or Event\001 -6 6 3375 4200 5325 4725 4 0 0 50 -1 0 12 -0.0000 4 180 1875 3446 4628 nactive-- readyworkers--\001 4 0 0 50 -1 0 12 -0.0000 4 180 1500 3446 4403 SIGCHLD(service)\001 -6 6 6750 2475 7125 4050 4 0 0 50 -1 0 12 1.5708 4 180 1560 6900 4050 Connection(service)\001 4 0 0 50 -1 0 12 1.5708 4 90 660 7125 4050 nconn++\001 -6 2 4 0 1 0 7 50 -1 -1 0.000 0 0 7 0 0 5 7200 2325 7200 1125 5175 1125 5175 2325 7200 2325 2 4 0 1 0 7 50 -1 -1 0.000 0 0 7 0 0 5 2850 5700 2850 4500 825 4500 825 5700 2850 5700 2 4 0 1 0 7 50 -1 -1 0.000 0 0 7 0 0 5 12075 5775 12075 4575 10050 4575 10050 5775 12075 5775 2 4 0 1 0 7 50 -1 -1 0.000 0 0 7 0 0 5 7200 9225 7200 8025 5175 8025 5175 9225 7200 9225 2 1 1 1 0 7 50 -1 -1 4.000 0 0 -1 1 0 2 1 1 1.00 60.00 120.00 5175 1275 1425 4500 2 1 1 1 0 7 50 -1 -1 4.000 0 0 -1 1 0 2 1 1 1.00 60.00 120.00 5175 8325 2325 5700 2 1 1 1 0 7 50 -1 -1 4.000 0 0 -1 1 0 2 1 1 1.00 60.00 120.00 5175 8850 1800 5700 2 1 1 1 0 7 50 -1 -1 4.000 0 0 -1 1 0 2 1 1 1.00 60.00 120.00 10050 4800 2850 4800 2 1 0 1 0 7 50 -1 -1 4.000 0 0 -1 1 0 5 1 1 1.00 60.00 120.00 1350 5700 1350 6300 525 6300 525 5325 825 5325 2 1 2 1 0 7 50 -1 -1 3.000 0 0 -1 1 0 2 1 1 1.00 60.00 120.00 975 2250 975 4500 2 1 1 1 0 7 50 -1 -1 4.000 0 0 -1 1 0 5 1 1 1.00 60.00 120.00 1575 5700 1575 6675 300 6675 300 5100 825 5100 2 1 0 1 0 7 50 -1 -1 3.000 0 0 -1 1 0 2 1 1 1.00 60.00 120.00 7200 2025 10350 4575 2 1 0 1 0 7 50 -1 -1 3.000 0 0 -1 1 0 2 1 1 1.00 60.00 120.00 7275 1575 10875 4575 2 1 1 1 0 7 50 -1 -1 4.000 0 0 -1 1 0 2 1 1 1.00 60.00 120.00 5175 1875 2250 4500 2 1 1 1 0 7 50 -1 -1 4.000 0 0 -1 1 0 2 1 1 1.00 60.00 120.00 10050 5400 2850 5400 2 1 0 1 0 7 50 -1 -1 3.000 0 0 -1 1 0 2 1 1 1.00 60.00 120.00 10200 5775 7200 8325 2 1 0 1 0 7 50 -1 -1 3.000 0 0 -1 1 0 3 1 1 1.00 60.00 120.00 7200 8400 7200 8625 10500 5775 2 1 0 1 0 7 50 -1 -1 3.000 0 0 -1 1 0 3 1 1 1.00 60.00 120.00 7200 8775 10425 8775 10950 5775 2 1 0 1 0 7 50 -1 -1 3.000 0 0 -1 1 0 5 1 1 1.00 60.00 120.00 5700 9225 5700 9975 3975 9975 3975 9000 5175 9000 2 1 0 1 0 7 50 -1 -1 3.000 0 0 -1 1 0 5 1 1 1.00 60.00 120.00 5850 9225 5850 9975 7575 9975 7575 9075 7200 9075 2 1 2 1 0 7 50 -1 -1 3.000 0 0 -1 1 0 3 1 1 1.00 60.00 120.00 3975 750 5475 750 5475 1125 2 1 2 1 0 7 50 -1 -1 3.000 0 0 -1 1 0 3 1 1 1.00 60.00 120.00 6300 750 5775 750 5775 1125 2 1 0 1 0 7 50 -1 -1 3.000 0 0 -1 1 0 5 1 1 1.00 60.00 120.00 11400 4575 11400 3900 13050 3900 13050 4875 12075 4875 2 1 0 1 0 7 50 -1 -1 3.000 0 0 -1 1 0 3 1 1 1.00 60.00 120.00 11175 5775 10725 8925 7200 8925 2 1 0 1 0 7 50 -1 -1 3.000 0 0 -1 1 0 5 1 1 1.00 60.00 120.00 11325 5775 11325 6450 13050 6450 13050 5550 12075 5550 2 1 2 1 0 7 50 -1 -1 3.000 0 0 -1 1 0 3 1 1 1.00 60.00 120.00 10800 2700 10800 4125 11250 4575 2 1 0 1 0 7 50 -1 -1 3.000 0 0 -1 1 0 2 1 1 1.00 60.00 120.00 5550 2325 5550 8025 2 1 0 1 0 7 50 -1 -1 3.000 0 0 -1 1 0 2 1 1 1.00 60.00 120.00 6600 2325 6600 8025 4 0 0 50 -1 0 24 0.0000 4 255 765 1350 5250 Dead\001 4 0 0 50 -1 0 24 0.0000 4 255 1470 5475 1875 Unknown\001 4 0 0 50 -1 0 24 0.0000 4 330 750 5775 8775 Busy\001 4 0 0 50 -1 0 24 0.0000 4 330 915 10500 5325 Ready\001 4 0 0 50 -1 0 12 0.0000 4 180 465 675 6150 (Any)\001 4 0 0 50 -1 0 12 0.0000 4 180 1425 450 1875 Unregistered Child\001 4 0 0 50 -1 0 12 0.0000 4 135 795 675 2100 SIGCHLD\001 4 0 0 50 -1 0 12 0.0000 4 135 795 375 6900 SIGCHLD\001 4 0 0 50 -1 0 12 0.7854 4 180 1545 2850 3225 SIGCHLD(!service)\001 4 0 0 50 -1 0 12 5.4978 4 180 1545 3300 6450 SIGCHLD(!service)\001 4 0 0 50 -1 0 12 0.0000 4 135 900 6075 9900 Unavailable\001 4 0 0 50 -1 0 12 0.0000 4 180 2220 6375 825 Message from unknown child\001 4 0 0 50 -1 0 12 0.0000 4 180 1425 11550 6300 Available(service)\001 4 0 0 50 -1 0 12 5.4978 4 180 1425 7950 3000 Available(service)\001 4 0 0 50 -1 0 12 0.0000 4 180 2895 9900 1650 based on a sketch by hmh@debian.org\001 4 0 0 50 -1 0 12 -0.0000 4 180 1545 3450 5700 SIGCHLD(!service)\001 4 0 0 50 -1 0 12 1.5708 4 180 1605 5775 4050 Unavailable(service)\001 cyrus-imapd-2.5.10/doc/internal/draft-release-notes0000644000175000017500000000166513001236020017120 00000000000000 ============== ?? commit 0fac0a0 Author: ellie timoney AuthorDate: Fri May 15 10:58:38 2015 +1000 Commit: ellie timoney CommitDate: Fri May 15 10:58:38 2015 +1000 ptclient: fixed typo introduced by adab408 commit dd9a2e1 (phab/cyrus-imapd-2.5, cyrus-imapd-2.5) Author: Jeroen van Meeuwen (Kolab Systems) AuthorDate: Wed May 13 14:46:06 2015 +0200 Commit: Jeroen van Meeuwen (Kolab Systems) CommitDate: Wed May 13 14:46:06 2015 +0200 Oops, LOG_ERROR -> LOG_ERR commit adab408 Author: Jeroen van Meeuwen (Kolab Systems) AuthorDate: Wed May 13 14:20:23 2015 +0200 Commit: Jeroen van Meeuwen (Kolab Systems) CommitDate: Wed May 13 14:20:23 2015 +0200 Use all member attribute values of groups found without a sizelimit, if the sizelimit is indeed configured cyrus-imapd-2.5.10/doc/internal/namelocks.html0000644000175000017500000001034012772415051016202 00000000000000 name locks

Namelocks

Intro

Name locks are an addition to the cyrus internals to address a range of race conditions and complexities. These ills are most easily avoided by ensuring that only one process can do certain operations at once. Name locks also mean crashes can't leave the mailbox "broken" forever.

Unfortunately, locks can't be retained over a rewrite-rename cycle, and every meta file in a regular mailbox gets rewritten upon occasion. Even cyrus.header gets a rewrite when a new userflag is added.

The "RESERVED FLAG" method of handling mailbox creation is a nasty brutish method that breaks on process crashes, causing a full mailboxes.db sweep to be necessary on restart, and making that name unusable until the entire server is restarted. It's also unusable for serialisation of operations without making the mailbox "disappear" to other clients.

Mailbox names are supposed to be exclusive per server, not just per partition, so any lock has to apply to the entire server.

MURDER Considerations: Due to the way the mupdate protocol works, RESERVED records are still created over mupdate. This sucks, and a better way would be to support an "EXCLUSIVE CREATE" command, where the create only succeeds if the record doesn't already exist. Then a task could create the mailbox on the local server and retain an exclusive namelock while trying to assert the name on the mupdate server. If this failed (someone else got in first) then the mailbox could be cleaned up locally before releasing the exclusive namelock, meaning other users on the local server would never see it existing.

Implementation

It's a simple matter of having a file under $confdir/lock - in a directory tree using the same hashing structure as the mailbox tree. This directory can be symlinked or mounted to a tmpfs since the locks need not persist across restarts. Due to race conditions while cleaning up, the easist approach is to only ever delete lock files during restart, so the unlock code doesn't try to remove them. Lock files are zero byte in size, and are locked using the flock or fcntl primatives used by the rest of cyrus.

API

Lock types:

  • LOCK_SHARED - shared lock on the name. Requried whenever you have an open mailbox with that name
  • LOCK_EXCLUSIVE - exclusive lock on the name. Required to create or finish deleting a mailbox, and required when repacking the cyrus.index and cyrus.cache files.
  • LOCK_NONBLOCKING - attempt to take an exclusive lock on the name, but if it's not available, return immediately with r == IMAP_MAILBOX_LOCKED rather than blocking until the lock is available.

The mboxname is always an internal name, so convert it first.

Example:

struct mboxlock *lock = NULL;
int locktype = LOCK_SHARED; /* or LOCK_EXCLUSIVE or LOCK_NONBLOCKING */

r = mboxname_lock("user.brong", &lock, locktype);
if (!r) {
    do_stuff();
    mboxname_release(&lock);
}

If mboxname_lock fails, lock will remain NULL. It should always be initialised to NULL before being passed to mailbox_lock. It will be set back to NULL by mboxname_release.

Re-locking considerations

It is not possible to hold multiple locks to the same name within the same process. If you call mboxname_lock with the same name within a process, and the same locktype then a reference counter is incremented and the same lock is returned. If you use a different locktype (i.e. one shared, the other exclusive. Non-blocking is considered exclusive for this test) then IMAP_MAILBOX_LOCKED will be returned to avoid breaking the locking semantics. This is a restriction of the underlying fcntl/flock subsystem.

On the way out, the reference counter is decremented with each release and the lock isn't freed until the counter gets back to zero.

cyrus-imapd-2.5.10/doc/anoncvs.html0000644000175000017500000000635613001236020014054 00000000000000 Cyrus IMAP: Anonymous CVS Access

Cyrus IMAP: Anonymous CVS Access

This file is for those who are reading Cyrus sources via anonymous CVS, or those who would like to. If you're someone who would like to work with the source code and get more frequent updates, keeping in mind that we take some liberties with proper CVS use, you might want to get Cyrus via anonymous CVS.
If you're not a programmer, please don't do this. If you're not at least a little experienced with C, configure, and IMAP, please stick with the tarball releases at ftp://ftp.andrew.cmu.edu/pub/cyrus-mail/.

To get to the repository, get a version of CVS with client-server support (anything remotely recent has this, I think) and do this:

cvs -d :pserver:anoncvs@cvs.andrew.cmu.edu:/cvs login
(enter "anonymous" as the password)
cvs -d :pserver:anoncvs@cvs.andrew.cmu.edu:/cvs co -d cyrus-imapd cyrus
(the first -d specifies the CVSROOT, in this case, our CVS server, and a path to the CVS repository; co says "check out", -d says "and stick it in the directory cyrus-imapd", and "cyrus" specifies the "cyrus" collection). The password is "anonymous".

You will need autoconf, yacc (bison) and lex (flex) to build CVS from the repository because we don't keep generated files in the repository, along with the usual tools to build Cyrus (a compiler, a Unix box, a network.) To create the configure script, do the following:


      aclocal -I cmulocal
      autoheader
      autoconf
      

Read access to the repository is availible to anyone via cvs.andrew.cmu.edu. Write access is availible to only a few people at CMU.

Please note that the version in the repository is not the version we are running. We have a seperate system that resembles version control for releases of software on the Andrew system, and sometimes changes don't get propigated back to CVS.

What is here is supposed to be stable. It's supposed to work, and compile, and not have amazingly broken changes that can't possibly work. But that may not be the case--and since you decided to use CVS, you shouldn't complain when something doesn't work. You should submit a patch.

There is no warranty on the Cyrus software. There is no warranty on anything in CVS, and even less of a guarantee of it working. (There. You've been warned.)

Please refer to Sending Feedback if you would like to submit a bug, feature request or (best of all) patch.

Thanks to Ryan Troll for putting the time in to make the CVS server work and actually documenting it.


last modified: $Date: 2010/01/06 17:01:28 $
Return to the Cyrus IMAP Server Home Page cyrus-imapd-2.5.10/doc/netnews.png0000644000175000017500000002453013001246644013717 00000000000000‰PNG  IHDRaWya pHYs N NwŒ#tEXtSoftwareGPL Ghostscript 9.19ã å IDATxœíÝK²£¸¢P¨ÈÉTçί:5^ƒLŠƒ@H|%±Vddc Â`´- ÜÃÐ毷 P“_᤾ïÉcUß÷¥µT­–6ô@±Ç’ÌW4•-}í«ïðbwgÈZ#ŒÂ¸ ­nð¢exÚ:Ñ$f”çM©nþpîÅ’ÃpÉÚÛŸA%·úÑm©}ë­’+ù0 ·®kZøVŠ:¶öbc1JÙËgàrŽ¢ÕVØzO_@™þ O»íN@wKï-§®€¯ùžÚ®Œ[Š}»íOYÚÞïŒîÞËåEå”hÛÊ€ñˆÕÁ7au¾˜²5ô'\Ú"åDžJ6çÌÛØ¶Ê¼µÒøØígÔOïç±–ªpKŽñ÷gw±áôÜ&²ÆÄ$ÎpøHX=°//@Êrv—°µ—Wå~XâËÏz·¾¤¿ñ’Ü·w.9MuéSNÜë¯\;O'©ø¸œ­óìÖùn7%ÄOm['ô°<‹òdzѢ„«HÄ’„·w7½E‚ÑjñÂ÷'Reî.'>¥ÛÞˉ{üLŽ «CjRÞ¢”ä¾ÕÇ–°*Œ.ÙÒÄ3C<ô>žw?˜‡÷NúA 4ãÇ€ñ ?ùÃ0LKf_9sí¾p!,XXÂéµógÅX-ÀÐy‰H]™9kÉÓû³õò󛼚>§…G6m+ ¤´²„»,ëHìnmw+@î[¾„]«/<³üH™·Î ñX—°ß‹qÕÞ9|šjwü&™ñï‘—K·•åÌŽX¼<\lÊ”ÝÅÆ‹”RÈÈÓ _æUGÂ…È}«—~ð\¸ü¬£në©°H–¼ºp9»‹ŠOY]ЪkFyŸù* ÕY4„ð)§®¶INÀw\ž¾ãàM2GQ4ælË“äÄ×Ú%<¤º Ré €8õQœn;€ Â@á ƒðAxÈ <dž2O„'€ Â@á ƒðAxÈ <dž2O„'€ Â@á ƒðAxÈ <dž2O„'€ Â@á ƒðAxÈ <dž2O„'€ Â@á ƒðAxÈ <dž2O„'€ Â@á ƒðAxÈ <dž2O~½]àm}ÿûaxµužàc¦¨´ 9¥Ñm³’$§dÂ|LØò$9åÐmŸ1Ʀa0Èé á ZF¥1?IN‡OЮ©©)$9%<@sôÊÝéíðôµ½ûµíàa‘¦&.òFxšòÿÚÞ¶÷Ëo—óåüA‡§Åå‘[÷éú”ª‡ì¹Þà]—45É^9Oš^Ûðùõ®#Ÿ@€œ9ÙºÃø9ïyšï¡ª›^²4¹¥a~ê|ns¾©Éyûœ·Œ¾³ÃZÝÒq»æE#®uk»¾ÓuŽ2ÂmoY« ༠¿Ž†‹r~Î'LN»KÞê9_ëØÝ"EL.ÕtÕÒXS|xZÛoypæš/võòÎÈu*ï’¢€Ïºã¼çz¿ÂÓ¢»mq“Éùôôd“¾Þn­ýiZ×Ö1*0 EqëHpîWCx û‡SX9Ÿrç¬Â¯Í\BŠZumЛ^RCxšÄ;ìÎ/vqǰYknuŽàk›¢\Äç¥|.&«'ê®[9Ô·þîÕãÿ¦“˜OôKê O‹š;zÊ"#¨tÌ=©¨å"¸Ix#¢ùôní›Ã¼Ûa1Ï”¢î®)ân½¿%/ùëí$X4ÿ§ÉT=œ_WúSañæ…äBÃðû_9oòVWòêù“1XÎá®mH4?9¯N_}8Hš8ó"K…Ï>süÏ«§K¾n]µ(®P|ËÓÖwè݇'¸»ð”)où·y·-ÊE °°ˆM«„ySÐ…ƒM«{Ý%)a»˜)><]â­^6ÕÕ^IQ.b€Ð<Ùo5Žf}.²>ÔSƒô[gÝkOAådAÖ|#¯ì³2ô}}û¢¾2¿òõtÕ»#3^ß|XõÀÁyfŸÕTß¹ýñ2kyâKÞ½FoQ1ÀÂÝŸ‹3 À èøðÄ'•¢\Ä¡[ÑÜ…¦©‰\ÂßVBŠJã:¢„'èºNŠü©„'øIŠ‚r9„'Ø EAóŒjâá öHQÐÝsœ#éß&<Á¤((Š‘àÜIx‚KIQð®ËƒŽ:ÂÜCŠ‚'Ý÷AóÉ% <Áͤ(¸• èxœðO‘¢àB. ã=ÂOŠâÐñaÂð‡E Ðñy¢¹€þž ÒOç&(„Eçº/RÅõƒ#H§òûû6hyrh‹úÐA”ð"EµÇtF·p)ª^‚äÐò\¤¼¶¨J½>÷öÂ=%~ñ%Âpµ’RTuëO>ÝspŽðܦ¤E×¹¿%\Cxî'E½KS\JxzÁÔ,¿èP›ë·f†!Ò¶>»Õs‘8\FŠzصAGlªßÝP|!ñ"M _5Nÿ.«í^³z(LÍî [s.¦Ï»piY³Á-îLQóC-®)³lJÔÝPzí³xj1eµF+Á_oà£Â+w†,Ã0¤,-q6¸Ò0üþ×÷¿ÿqÆøNïêùEÑœ'+ Hµ²šÏ"ñèLrº¼RÓmW«­Ã¨œ`yôèaTª«º£9@xzÓØ¹iŠÜáÀÓg[N4pŠ‹IQY\@Ç!W@« IŸvç…E/çÚ^?Ýv/Ûm½ªí4q á95ºnMœÿ!9q%=zÓ{r¾{®ÓC÷QÏT@«/Ï]fX¹ìÖD·~±×òô¾[ãâð”ë/V{Á‹ÁG³âmQÍ÷1-6Ðt\ç¾ èî+Þ­‰„§"LGçá"/<3[z›*Áwk"á ¨P˜¢ºæQºêª[4óÁKŒy*Ånˆ~%eO_5æ_;V'B)Ú¾³º g¶ëÂR4ç• (~ ƒ]ïÖDÂÓkR. ˆÏ²üÝC*2Ûtd-«ãÃÕ‰PœªóÓj›ÓÉÜ#61sk”Xût?+”Éê%u[W§×D×,£}fÕxAÃ5ev—¸“1Omiuì<C·À=žì:œ¯Kr‚› O™ŠP5ž"<ÂxL‹gKW. ƒ7O3SCÎü)»óoÍ|¦H«Ä&xƒã?…‰$žQÆg§À´xxÒÝwò OEºããÀtÛ\aµ}mƒÓîDàqÂ@¾ø ¤i”Ò±¸sÇÆëè¶ZtøêýéU)LëŠ<{¦ @‘„' oõjÉ:ð1ÂP¹ÕÌôL ™úæä'øá hÎcQFf‚Ož€†H3Àý\mTkñ³n’ð-O@….¿À ™ðTe›'<õp]Pá ¨' ÂP6± (Œð”JlŠ$<囀‚ O@IÄ& xÂP± ¨„ð¼íÎØÔ÷}×uß…Wñ(\ïã ¼éÎ[7õ}}§¸Ë _£å x‰~: NÂð8± ¨™ð@x® 6Ÿ!<çˆMÀÇOÀQbðIÂOl>LxrˆMÀç O@±  ëº®ûëí5oÝô…äôo_⢀’O@Tß»éå Á>Lx6L±éËÉ)1$-f­ iÆ<†7ýÛwŸ+ÿ€þ~$¡p™óÙÆgÇ?ä'h—ðÌT›.Ï+STšRÑj&§LiñhŽðt]WslZÍ('›¶óŸ×ÞØ¦W’Ó¼ÛhšðÖFlšG¥¿‡ç’S¤ÅkìàÛš¨\?T}Òkà‹1ÝAlêûûOqS<º(´=Qfàcžà{êÞ47»ýî'ã«àc|Å¡!ýŸ6€Ä£z«éeœ>O‹´±>K ç™f胮œÇ>†ÍĦ.)²ÜÞŠsu³S§å jàSJ+tB…/Ù LaxмpuÊü%a̳ڭÆ6bS¦ƒHe†¯1`œF-ZwâçÎÔ[óŦ/gœsjëº\£Â¼ŠaÌ Yt·-¢Ì|úµI%Ò·ÛªtkƒS­MÉtÏžhHØk>œÂÊü”;d752-–_{lê®ø•€« O´hu˜öôðübç ›»V‡CEJx­fbÓHrÊcÌÍÙê°›ÜÑê³5¢hjåzFc› oʦ剆,®h-F#Y*ìÅ;³®ô§æóÌ;m48é¤jàšX˜yñ¦Ûgb\WlºG—ý×Xfø-O0óÀý–V[©Øðá ~z%‹¸½çW•Æ=€: OP± àm:סmĦgÕ8~¨Æ2Ã׸UÏ﫜Ð÷}?»¶±Š‡@á|Ų½xàUÞ뤫±§Æ2Ã×ó¥j£ŸÎ­›€æøŠåi#6 ÆVœË _cÌ”Äð&€â鶃2´ÑÚäÀOð¶6bSgxð:×á=ÍĦRÕ8~¨Æ2Ã×hy‚7´›tÒŸ$<Áãܺ  fÚ‡áAm48Õ£Æ.°Ë _£å !6´Bx‚›µ›ôÓü!<ÁmÄ&€é\‡´›êWãø¡Ë _ãçYàR~_ uºíà"m´6館#<Á¸uSç÷Uêÿ´Ó…‡@ǰ sÎi£Á©Q £ÒðdÌ”Ϙ'8Êð¦Fõýòa¼I«SæB8Ð Ýv¯Ö&ÛÓŽ’Ðê‹yV—3Î4Ix‚mĦÎð¦M㾢Ϣ1iz¶[ËXóÿç É-BdP릙Øô%¹ã‡æI[ái1OÖ ‡Ëì胢hy‚=mT\:érDºíÂy"/¿Ê¼Ç°«ÿ`„Ú O°Ml"aè÷"ÓŒOÓÄ ƒÔê­"Ï7ÑmÜ¢§~ºíF‘ÝÝüsøVXxŒ[@`ºA½Ü€à¨”[O”y{ŠÅè«ép9Ýv0ÓL?Nº|ãÎÇæ”yJŒyH$¦úõ¨ŽðD+Ä&¨“çTç+íô¬ØÄ ú?õðt¢§”üð;ÝvY|Ê)ŠO)•Óâ϶ƒHe~ŒaRB·Õj૨N:È~Üõññ በ5›:7 € ÌOófhMÒÜJû0Ui#6ñ”»Àj,s™4Jq-O¥èçôz¥?ü«= ¥…’¡ÆV¨ñßðûÓò£9jü÷b!™ Óq'ÑÝv¼¡Ö&ÛZi7 ŸZL¹°+²œE£Tiá‘›Kµ§¾¦¹V}¥™´ØD%wÛMYdÞ¨3O*ãSáÌÓ”ÕqKw”ykCÂbSšbãÔWꣴ<ñ±‰ªL™cÊCS6 ãÈ4}˜ÙëIé f¼ÈÏ×Kxâ œtÒñG½cŒ¶ÚÒx×âìèvç垸Y Nb3«=zÓSÓøîbsÉjÁ\ÇW”­óegÓfOܦ™ºØÄÌ<­†¤i†ñaÉAj²ÎõnaØ2xÞÀ™µjÂ7ðá¦N‹qN«¬N\Œ ?•?†7ÛÂK·žâ-úøJ f?ø}*ôó‡@þû —­eQžiz½wvhÒê ÛÈäÒmW‰©u'Ò;Ÿg÷R×ižø«¢Ïö]WÝ·“tÒÑŠÈ@ïðÙ,Æ×k”ª‚^„tÂS=¦#z =a .²Îb¶ð“ÿ¬¬.³ÿöb­*í¢9ÏË×ÒÙýÂSëK<’œø ÏYP-œdÌS‹æ]róö§K–Y5Ûø¼ÒKM%™¦¼>x viyjÂî §.ó‹FQiÎð&XSÚ`©ÈJÝýœrO[¨ù£ ÆûE†7%.0\f o‚4¥ –š›<½0|\}÷rhÕ÷¨¸£¹(ºÌï§Ôxˆ[æ¥BâÔŠ=#.³–§VŒíC׿§;–ù tpµ;øæëuíOžZqG¾©.3ub<¤´,®±¨>GS_Ó\«4“ÂåjÆð&à=¥ –Ь´ºç žxØDV¿°Fz®ÇQ‹™ç³…GVDQJ,57xþza>Nxâ=bo;<¶i‘–vg>¶^WÚ`©ÈO¯>ËMü< Ïòû*Ôf1ü@2ü¼ ‘ŸŽyñ§ZEz«_£å‰§è¤£†)´5Úi±ØÕ—h€5õ]ŽØªƒ—Y¾ÚËVãå¬ÄÕxnw«€r O53¸W_Ó\«4“P‚ÏíºíÊ%<dž2O„'€ Â@á ƒðAxÈ <\§»Àý„'€¨>xN¾Dx*Hß÷}ß×õZ6æ¤aƇ០ø’ú~ü¯U~ˆŠ3£éïníá|ž.xªñÜ7Ìþ;ò€¦ O{¶zëF•}EÎúõvª²;Z\Ï´Nxضꦢ!úh‘ð°MÆ<¬égÿÌhyâJÿôÿLÿoøß‹%³´9„'Κ&h^}7ÂjU¥7%û¿îÿÞ.«®ëàá:´¾ »U•†§©ÌaûSuŸ=ºúë£è¶ã·úÎÄùkuäа·ÃÓt%Ke÷¨7¶÷d*:@› {ãVýìßðçßG ³yèÏþ$VØÀ“Øä³˜MC¤{¼åiõ— †gž>̦ú1‡±=ijUÐ8eš'lšÏ6½pñ* âñ–§xSÓðó_“Ó»+ÞæñhúûÃÿæ‰jõ%c`š"”Ž6HôÞ˜§ybøÎïh^·¥Ss‘ÜO*ãçY>’œº‹·ôLlZô÷]elÍÿ]¸X(ÇÛWÛqTV:Ùºàn꼋ÏvaI võÝ«UÏÜàk :—tö%Þa|Z×"f™nºé¦›^øôZ¸ÃøG=ž.üH¸Ã8@{Üa|uÕ½AW*i ú;þÚf§n»ÌF²ÔKxÚ_]uoЕ>ž.Wc™ˆ«ñÜþp™Ë¸Úî}ðGd€ OýìFÞýì§QÂÙ†µŒ%Q3OÝÏ»xo…¡°µOl»ÏS¤?4üù¹¾¬AQÀk¿Â™øghÔ7ZžFÃvcÒ3#ðN»­Ý@µ¾žFýÚ˜§é÷zçK–‚¯Ù :«Ã%ù@·Ý°ñ÷ÖSóï‹ò|Çôõi˜}üûàœ0ª š´@à¾×òI(åƒï›|ÞÆ<¤è7ö§»ää-h‹ðT¾7\Þ¹¸$>%ück"TB}Wßÿ¼È˜'€ Â@á ƒðAxÈ <dž2¸IæCÆŽÍïª5Ý‚lëV[)÷(†a1Ûî»Â’P‘­Úa·6YÌÐ÷+÷zL¬SÌ6Í“òÚĪj±üi‹æ/¿£Ös“Ì'¬îÎé©nm§.vüâ˜[>_Åê2ã% "‹ÓxJm> =‘:eþìÖl«õÝÖBæ¯^¯§vëÓÕ*ò*ºín·š»§§rè]Ã0,Ç”’PÝp°[›ìvqDê”Èlñ$íô0RòÕåGæ?Så­–YxzZ¤}2ë%‘égJ@½Ò“îð·ôÃ/L a¥Ù*­1O·Û/o3LYozIÂè­)‘ŽÂÈkoW;Ð¥•x&Ÿf;pæO윉,?eøÔn•R-OO˜BÆV‹e7ÛçcV$×GJ2ü1Ÿ³ÛhA]r÷µÜí@m’rŠNl+:Ó¤´5Îdu™¹+ZmJˆ×Y»MZž2eÛûš v/ß‹—d~¬äòÌkxW¼G"òÍyk¶ôõ®¾vÞ³qGr¾Îžž9¦µîÐñ7_þá’$¾|õ8“–JR›Du‹J\ãÖZ·{Í+¦Õ~’“¡ê|¥Ûîvå Ž;_’)uIKõ~zxÕO®î&ÂS)ÂqE›w“çÆ¬3¯àBñÚ$rSƒÝ%§s>¼ŠÄ5®ŽLJ_Åù:K·Ý"CÏâÇq⑚>óVIÒû ÃFÔKúHžöÓk“ÈœóP²[§Äg[­,R^;U¤óª'œ1ªi녇ǫèÈ Û ƒðAxÈ <dž2O„'€ Â@á ƒðAxÈ <dž2O„'€ Â@á ƒðAxÈ <dž2O„'€ Â@á ƒðAxÈ <dž2O„'€ Â@á ƒðAxÈ <dž2O„'€ Â@á ƒðAxÈ <dž2O„'€ Â@á ƒðAxÈðëíД¾ï»®†!œ87ͰúÔÖüáÂû¾ç_¬®%<ùéÎܽ›E]ŸøÎI,ž¢Û»ØØÕ½¾Ô÷Žç´?eÃãÄÕ §§oïÎ NÐmG"çÁñ©y´ çܪ›k‘^ËV´¥aQÃ,8M gžO©¢ŽL)ðOx¢tYw‘…\Z¨'ìÖµáø˜®ª- ǵ쎕N™X²Õ}ÙÑ‘åÜSÀ'|m{i’n;ž9ýí#§ÎbϪ‘¶¥«nõ´Ûm÷¤»wSÑ£["uº™­D‘¶%·zâ{„'´Zm9eau×L¯šÒ´šß;ð.á ÚvÞ¥W¢«5úVóFؔŭŒ¿©$@gÌ4fÑ8”X‰¦Ï®…Òˆ¶p7-Oи)íY̹ø{>žæ¦¢²%«AqêÀýÂÐ4x…Ï—qšÊáŒÄ}tÛdž2O„'€ Â@á ƒðAxÈ <dž2O„'€ Â@á ï· @Sú¾»p¯ÿ)סz7‰w·IEND®B`‚cyrus-imapd-2.5.10/doc/install-perf.html0000644000175000017500000001502613001236020014777 00000000000000 Performance Notes

Performance Notes

Cyrus presents various performance issues for you to consider. If you never expect to have more than 100 simultaneous users, chances are any hardware you have will be fine. If you plan on having thousands or more users, please be sure to review this section.

If your configuration directory is not /var/imap, adjust accordingly.

  • /var/imap/proc - After a successful login, the imapd creates a file in var/imap/proc that is its unix process id. It also contains the name of any SELECTed mailbox. The file is deleted when the user logs out.

    Given the potential load, this is a good candidate to move elsewhere. This can be done by symlink'ing the directory to another partition. We symlink it to a directory on a memory/virtual memory filesystem (specifically Solaris' tmpfs). If you use a tmpfs type filesystem, make sure that you have sufficient memory/swap to do this.

    Some people don't care about this information and just #ifdef out the code. We probably should add a configure option to do this.

  • /var/imap/mailboxes.db - The mailboxes list is often the ultimate source of contention between imapd processes, especially if clients are inefficient about their use of the LIST command. For this reason it is often better to use the skiplist backend which is optimized for enumeration of the database, as opposed to the default, Berkeley DB (use --with-mboxlist-db=skiplist).

    Mika Iisakkila (mika.iisakkila@pingrid.fi) writes: Nevertheless, you can also tweak the Berkeley backend if you want to or have to stick with it. Cyrus doesn't do anything to increase the BDB cache size, and the default (256 kB) is way too small for any reasonably large site. With some 50000 mailboxes and random operations, I found the hit rate for the default BDB cache to be 70-80%. After growing the cache size to 2M, the hit rate approached 99% and disk traffic was greatly reduced since most of the operations are reads anyway. Therefore processes could complete their work and release their locks much more quickly, and the dreaded "DBERROR: xxx lockers" messages stayed at a comfortable level. You can modify the source (/lib/cyrusdb_db3.c, the setting is commented out) or you can put a DB_CONFIG file under /var/imap/db with the appropriate setting. Read more about this in the Berkeley docs before trying it - typos and incorrect settings can wreak havoc.

  • /var/imap/deliverdb - Unless you disable duplicate delivery suppression, each time a mail message is delivered it needs to lock the database and check to see if the message-id has been seen already. If you require really high throughput delivery, you may want to disable this feature.

    We run with it enabled and it doesn't significantly impact our performance.

  • /var/spool/mqueue - Sendmail can be pretty harsh on the spool partition. Having this on a separate disk is usually a good idea. Consider using LMTP and delivering from a separate machine.
  • Unused SASL mechanisms - If you just build the SASL library and copy all the mechanisms into /usr/lib/sasl2, the imapd will try to use them and allocate some amount of memory for each. In general, the operating system will swap out those pages but you may be allocating more swap space than you need. So look in usr/lib/sasl2 and if you don't plan on using those mechanisms, don't leave them there.
  • You may want to increase the listen queue value when starting up the master process. For example, you may want to do this if you see the listen queue drop counter increasing quickly. Under Solaris, look at the variable tcpListenDrop (from netstat -sP tcp).
  • Database recovery. If restarting the server takes a long time due to the cyrusdb database recovery procedure (this is usually true if you have a large number of deliveries) you should look into shortening the interval between checkpoints, controlled by the cyrusdb event in /etc/cyrus.conf. We run checkpoints every 5 minutes; the current suggested install interval is 30 minutes.
  • Some filesystems support the noatime mount option. The server does not use the atime information so you can go ahead and enable this feature.
  • Depending on your syslog configuration and usage volume, Cyrus may generate thousands of syslog messages. On Linux, syslog performance can be greatly improved by disabling synchronous logging (disabling fsync() after each message). Prepending filenames in etc/syslog.conf with a "-", e.g., "/var/log/maillog" becomes "-/var/log/maillog", disables syslog's fsync() call after each log message. If you log many messages those fsync()s will kill your I/O throughput. Note that if you do not need the detail provided by the LOG_DEBUG level, then not logging these messages can significantly reduces the number of log entries that Cyrus makes.

In general, there's no magic bullet for performance. It depends on your hardware, your operating system, and how your users use the system. In general, an imapd process takes up anywhere from 256 Kbytes of memory to 512 Kbytes when it is first fired up. CPU has not been a big deal, but it may become more important as the IMAP sessions are encrypted and now that searching may be more frequent. Disk I/O is probably the most important and having a hardware RAID subsystem with a decent amount of write-back cache would be a good thing.

Again, if you are talking about less than 100 interactive users it is likely that any relatively modern hardware can support it. If you are talking about having more than 1000 interactive users, you should know how to predict your utilization, go overboard on hardware, be willing to suffer growing pains, or be able to hire someone that can help.

There are a number of good performance tuning articles out for Solaris by Adrian Cockcroft. Go to your favorite search engine and look for his name.


last modified: $Date: 2010/01/06 17:01:29 $ cyrus-imapd-2.5.10/doc/murder.png0000644000175000017500000004164413001246644013537 00000000000000‰PNG  IHDRSï>Mì pHYs N NwŒ#tEXtSoftwareGPL Ghostscript 9.19ã å IDATxœíÝÙ–ë¨EQ¹Æýÿ_ÎûàJŠ$‚ h$ѬùpF[B¨ß5ŸŸŸŸ øçí à!$?€SüO~ôù|ä‡ßNáÏç3[ïpRÛbõäðÆüª£É:Ø%¨uvN4¬—ÚòñŒïªÙoì:_°½4Éåè![Ìy¬£QCc°â Ê%£Žb”cïeT}ð€]Ò®óÛûÓÛkÍ'?Ä?P=ç$Â`þF»ÚQn­ü<‹4^¿Ã Œ¬Ló|Þõ_ò+þˆ_å@Ÿ;eNu*MÏÀþM~‡Ž™ÃkCø›yv¶wë.3Õþ8Ue”;< êý2²$ŸØwQx®½“_åª÷eÂ;Q†»o‹‹Ýsmb²rÕ\+¯GL6•áSw–S,$|è¹Ü-YS…{ªm/vµÂözQ+£nCÖNíŽð«K~_ñ;>.O92ÏÉã¸ýIk`èóY°ar¹ˆ<„§>É:ý|>FjÉ"?å7$»ôOÝSN2›žB‡ÅÌ—û¤¡p£Ú¹å>1îU·—†Zu+¸v¸øîóçÙ(¾ü'â]6Q8Ïï¶|ÏšwTã# ¯OnHOû–l¿‘«;Éqr,;Jú§ž›qcø )’#vnÌNnw3RÚåXéÎjŒZ;Í;>À©¥Íïë{P~¬-­v*IËÁ­•| sJmþ¹»>žqï åž’’Anøç[…«4W»výùןÛf^)°¢?ɯóä7ðÜbåuOb+n\y&@ØóØ\ŸCβ?Ž« 'Ô\m»£vªÙïÙñÞÞvSÌŠ[ìÚ&ñd»òWÓß=¹âô—%¾›Dí¯ë©v¸H`þùíßñ†®ä—´% ?©ØmÎïe¸×Ïs¯Wwˆ#£úíóU²5ïø€¢“_gî~tޝ ïì€T#W´ÒÌV5¿Î+ñ{êéwi=íåϵãrÒ6?ÿ­_sÞÞòðù£9lÝtmSm}’ÁdÞU˹o!ß4uYÎ÷¦jWz[9_wßc¨ò_ò+Fû|Ðsöí?{ 9ÿÙOÁh¸ þŽg¯$#¬Or}•¼Êª³¯°ó&ÜQ=•riô_wkjL¶¶j«ûÚçïýïêJÏ•“X¥Px Ì8Ǩg û>ÄäÛ¸—G­ƒ=uu°ùÛ\™Îv‹biÅ9j«InÄÚúäó–=!u]ÈIËÁ†,v»Xcch(ÄÞ¼ei¹¢ª ¯ªvî+{uGWçK-§XCÏf@³Œ5æ¶ŒÎ&à¦ÎnóTNØóü°„Æ··9/rÀŸÏçãùÐYÚ$5 ÉGø&­ŸŸŸáeÞWÒ!`8’¶’Óçóqf¾$l©Íužý5é™ÑP‹ä‡=ÙQ/Žbáo,KRZœ®ä'Ɉj3jÒ< ú‹mH~ØYU<úF´°Â“Ú&T ÕÏ“~~~Æv^Nð¿·+Ü%Épýrñ®X~®&²ÀÐà— IÈ A›ðGÈgê52ÉÎYÿ„rŽš ’6©äŠºpÍ\n¬x˜ðIr-`\šÏ’šä L*™T˜è1¬# XZHTì€qð/2`{´ù4øÝB½Ñþ0×ó.ïk^Õ»Wý„ÛXÏ\׎{ÇN.™RÔXlW@Úü€‰NÆ›ñ¿ª$ ™;—‡ÿÞq¥ã±o­ml­ ·Uõyô—¿ÖÇê¸ÃÀÓr/5i{ÕJîÃÜ}3µ…çÆUïþvVÕžŠ§¶U ¸XU£4geÔÇûk˜›œ©ªxJX7»ü±•š‘ü<ª¿mCv·H¿’wdˤ—“Œ®ÆšðynD5Ì©õIþEå2bnõ¹p¼…äà.Ÿ¿’o«šd:OÛ²O6k’Úª57¦’8iúº¯µ/n¤Øx˜8 '•Œ ,öùʘ¥®qu9 M6"zFLJˆgSÝä$ÔåRºþf>uç¬Ý·I î$°¶8Ìí:ÅfTµ¡Å |ĵŒó/^ à:?Ë{þ¼»Ð™žªÞŠØ‡å°ÉX ~ªÚP g&©0Ѐäp îð8×ùa7‹Þ"Gë;à$?lh¹µhZ,‡Þ^7ºõÙu3Øiîn}Ê`óˆž ú§U[“¶š\’µ³Ÿ«ÉN*:‘üÜ"~Âíc“›Ç õU‡þrÚ6ƒÏïKAŠ/Û®íÖÝá7üÆK ­„å:@ð’€'T½±Àx©CÃ`µ:k%Ç5Jkž£ª2kß´ÑPTq1:ß`á™ÖØŠóxSÍÕÅn,^çÒhØØ€/®óp»ðV«øEõj£`òíWòj,õ¿êèê›jJþ¯;“õÉUɳXdáF™Å“½œ)Y »ÂÅeë\¤ñ’´7µÚƺ0Ú·Šóh¬¾†éªÕΕcŒueÖWn9ËZÙ‹g¢ÍÀíÔScqàÐÉ•‹¹eájYnBF­¾çÔp6˴ϯžù•ƒÅÕþˆ7Õ˩禢΋Qa{ÙziÛÆ`|XL6þy´‹jžn2¹ÜFëØXÎä<Ñæàim''tÔDøÖ™¯6¾\bŒš'‰ÓØæi 4*Ü6цiùµunÊÍÆøÑ?]Ïbo8AW/Šhó𨶳š3äõœ2ÕP›²ìVIgç}É éè´›¾r…ß±lûËtÆ5Ï{ ·,F·/,‡6?`^ôÏ€U`'$?` ¹&%Â` z{ÙÑÏ…6?` É«’Ï=á¦A@ɘ‹=©Îùä3ÀÉH~À¤jƒZík †L°’p $?ÿéo8$ÀÌH~*Ч K#ù‰>e˜ÉÀÓh8€·üL‡†C¸ ÉÀ’¸üì‰>eH~EŸ2€‘ü ‹†C›!ù@;¬…ä÷âf §A}Bóï­$?x}Ê€j¹­z‰´Jò€Ùѧ `’쀆C$?8 ‡.’ àf`{$?€}ÊÀêH~€avêSNêùL­>ŸÏ}úÎQR¾ý¡º²ä瓬2xüZ¢á0I`w?­#L®m¾üyÑÍÃß?ä$—x” ’`.6Ê(ÉìOìÿªœrŽX%Nxañ: ¹µ©c‘üëñ¤Ÿæ,bÄÊ$!];FÕO’žSùy±üÜ„œ5,ÊõêúûòÏÛ` ¹.`™{ä'aà¸c7˜ürŽèQþ>¿ˆ}k!ùð‡'ÊTşȕ鱶™ðŠfª¥rxÉ—¸W´§/Õs‘bÄzFÄ9¸Î€”ñà’¶KââÛo'©,V}´Š¿|O í§±T݃B²\« »Yñ`´bɱ[­nÅ5¸Déí8Éà$?€SüNAò8Éà$?^ÐùªÜ¤ø“R1L‹äØ|ó<¾î62ð1ró?‘=H~èŒV4µÍÏ~]‡,Üÿþ·±ywÚôŒf$?R¡YNz߯’o¯¿9)ùªjB²ðÜe"T;ÊØÏÜtŠ6$?ßf¹8ú„@–¼ß6 ÖöâÝxBjáñ`¹ÿ&V]ó§†ÈÜ$°ºÉïóWÕˆ=5ªÑ\ìÝæ¯!–ð›î3j#›[.œÚrØÓaD½ïW=×óÅ×ðÅ[Tòßb­ìÊ_±oiX›ß÷—Ðõê¹áçל[jhÀçWúýDÚJ˜s7é‘;¥Ý*·ÙÍ·!#‘ìxUk›Zøåkð3êÜVŸâ„°¢{{{åõµ£´’k*/–Pum„¿†ê¸êo)ÙhØr}CÅ ÌþܿߵmÿÆWþíÂÁªZ2FCúÿë™ ÇÇÄ[QÒ†éùa–œŒÿ#ÆìÊØmlW;ùßÀ²’ßas‘[Oî ãâ&( ÏW¯X u^Ô±ŒYUÿÈU&Ì`nÉ—Ø„Ô Ì¾DIþQÜïâ]£s»2©ÅØÔƒŒ]ÉÜÂQwpuÞ=ƒò¿¹å¯v’BŒEŠÉ’Œ©Ñ—lçžaL¨jröˆFeråUº†µùÉúÁ%SŸßÆíø“¸Ø\!jÔ“‡,0‰†2r©ç¦ª”ûÍ¢žŸâ%¦îoÆIÇúüŠ?ün-Æf”–”eïwrxY¥ø+c»ÄN—”ŸìγQ\#€æ’\2!çr“Îk,=»Ìø“dBBÝG•œü’!Zá1ÃÚüŠ('>àöoú?ï²ÑÉi 8°§†µ³ð“iJlþÐSÜÀzö»d×µÇ9Uí;rQü˜­’ Í}&”«€ºôr‡£¤‡QÂúêY¤öèño˜Î õWG¹ë:?yÀRVÉ/éâqÜsÌÏ+þCq`{Ÿ —ž)&ù˜½cUm`ûÝuÛWTÛ§)wRÙí››Šg¢öW¹g/=µ27~Fôó«³g&4ª28İ6¿$xÅ¿ïÿj¯SÒÏbôL%…ȃu®£9W ü07pÕñÔ˜¢:§@ƒb¤ól`ó"ð‰±ßÉ© Ùã<äA&7¤QɤI9ê¼Ë‰Æ™R~eTØ^z¹_Ëö\÷,R' Á© Ù ­ØŒºbù±g-jÝsë›ÜÈ{{Ï4ÿ:€3Ûƒ1›øzzÆnBòk÷Ø•¹€ ÝqüænðwrRííDÉ7Ät–'’_;6P8Ù[gþt>ûö&yI«QT[eÈ|»÷ì¤!ßÈ;ÄÕ{Æ;'*‹õŒ˜kä‹C^ÕôÎ!Ãðᩪуä@*Î@áä¦ìä5÷ÈQÔ§ %¹-ü7ž¨‘«Ôbs·çJë_U%ùÞBo/.¹˜R¼•Dí-{9“Ï«ž,&‹•eªÎ=¨6À…2«F!ó½e@òË]à™ûÑ0¤XÝÊþ‚±”e×?®Œº÷Ö{¬Wõ\áH=—'ªku ‡ra_ûe?:QÓ:¯ú_h;É]§î8¹c»,ªj ØÅÊ!“:‰Ð(Ç_=2ß ÆôöþüºÄMCñWɇþ!/-Õ}É­V–3Dh—N —ŸU½Ì-Þ ~ÓÜá@ —+m¹á5,‡‡Å™âwWÆ®ƒü=\<âíÁÓàweÞ¯c·Yx’œZ¬][9¡»qIß<ž»ÎOý%äÒÿ­=dî"Œâ0þj$Ÿ÷FÏîÊ~§âÆl·18‡,\õß"9º¾üó«~Õ³<ãa†T8WÃÎuÚ¹vjGñÏø ¹0,^çî ¦4¹ŽâOBøKKŠ’x&d×ÙhÛKZ7ŠEy¦Eæ›Çøëürù&4YÙM_ž 1 f¤%ù•%Ô$þí•ÛusSQ?uîP%[ìåÛ˜s{MaŸîñ–1É/ùù"?ýh—äÎj±ö9)WIÏ/›$žaÄS瀇úã*Þ˜=Çè˱#$'rÏžå,Ù9S²4cÜbáê‡ÑÒS<³ª‡µQ–'c{Zjir™Û@{øbí¹0êvÓ¡O"óÍlLòËøŒ\2°}Îý΢ê9‚§@»X5æV Œâü]äÏdj>ѳ¶äª©ìù-ž™<¿cý:+Ü_xÃføA)WIŽ~;!óÍoäu~ž5íl~(kÿtÎM·8|ÿ™‰_¨x—Ú-x™»€Ì žÍ8éFL ì)97­¸4OSº¬˜ZÉÜ·I+Tq»þ ÷îl<»õð•›AµnHWZ1ˆ}“ÖÛ7ÎÇAñ`É Éh Hº3’bíšÈrB á\eœÿrSyxÊõGØ"êÔ‹ û¬¯nÌrP÷V{G¸þîe²Xã,î/ÙØ ªš$s»¼Ì£êädÍýÇ¢á¶kXòÊ{eŠå8©‡ÐÜ×mlMVjµý4Â[ذ›òCβß?–›wÖ3…ç­xLXÅ­™oÅ·Dy‡°‰ù7 ¶œ)`K¤H¼·XÞ's'æÒ¶œ)`¡ãþ튠m~Àò¶<þn9SÀê‰Kú6@› y'=€g`ç}Ö í|ľÕÑæ@JÞ±.ÿˆ‡Œÿk ¼"Úù6Cò@W|úXøÊóP³åù¶4uò[ñzˆëŒc­µ¹>PÛWÎsk­…sÄv—¹UÄ* Ÿ¿ÔáåkWüÛÛ$È|‡ÐÛûɼ‡§êÚXµ¿C-Y„]N®´ø+Y±ør ÿÔíù’‹ÂY¤4ákwpùúþŠ›Ê5bs•R/lªôU:8;ˆBÆ‚-.áxiØK`†µ«ƒ,ÐyÜà ñ•¬…QÿõìàÏS÷8쪷ÍO=ˆ\Ú;m“£IøUá9É“HújeâCÅìÃ_<ƒ¡ðxÆ|%çªáŸYuÖNØŸ—ûy­òŸª¶ØžÍU-9.DSÆ~*?‰I±jeü„âX*£†¹!_Y Å:479h–޽þG@‚£l$?,c‰+g{$áï:`– DæƒÉk83ÑøÀƒü¼½ÍsÙrÃÓ°Š&´>­d‡_ø¿–sbŸ|¬®ý,t‡ãÔêmóóœ“&yÿØsÿ„ÛÏóhü qxDƒaOuÉ=^ÒxR¼=¢§CZ«ªQ5ÅÜÀÎBd=÷N„mǵ¥—I.åÓø M}oWës_xYÜ27Q|þ¾›(ù#"GT'aWÃóG\N<]ù¾#»¹q/-²$3øeÔJΩœzqîÖE—ŠÆ?œ¬ç—Ï‹¿šÆî­ÐiLòKRÔ%ö15 ÉÛåˆr9¹ÂaìÂÕö9¤*ñÀa–«®Ïi5™èN±¯m.öh³×#·ýâdËmöÃ/p_n `6#ïí­jp檠jçQ›‡ì~ÅB~~_ÃPµs¶Í]î“Õ3Aì[zö¿Š!žÆ?àììhäÛÛâf'u€ø+yV3FôlôváµÔôvÓ¾W[¬\ÎFór6˜…Çpå°½Ú®! hLò“÷|~…ÿ#~ÉËïü5¹D«_[5j§Ò3wêB^7 ôľEgÙà\¡™ù*x ™7¡}%å¹^°ª8 Œ}Ë-ÿܼW-6-Ÿ-Æ?8ÓÈ;<Œ‰qâ¯:÷ôŸ«võª07dí ÛD¥ûbß™²ç&ß\i×FÛÀÖÛæ';Rãoe/mÂsÖ±'Q¥89ÿYÐîV‡÷Ör—Q„>ë·+²›±›p”ïðP‡‘}¾—vœz©œÿäd7=Ê+ÿªê“üç›d“«ýõL 7†™Vý·–SáâÊ?8Ä]×ÝÿàÜ|¦bÉ›fp ·Ïë<‰Ýu¾ëIÎóÏ9nBì[WþÀÞÆ?É9<—dxɘ™ì1÷]œÇ•°±ñm~œøõLì#\>ƒÆ?ØÒÔïíÅ*ˆ¯û„µü‹• {!ù¡×“p4ø%î×ßÞï› ãbà>$?t!‚Î_Ü¡öáÿ$B ßÓÉ/~ôÝØsImá4ÖïáØGÊT=Ðì&t±Ф6á¸ÏÓÉO¾E÷ßp깊»;‘ÎDã $<`~Ã’_.8óA2XÕ©%÷Ö¸¶íˆ;_Ï/–¼á±f¿0¹‹5r6°®É/¤4ã5hvrJËýa›+͘PnÒêa¾oð8|ö°/B y¬t`]cÚüÂQ ~}­ÿµ­q̺þSB9F’»þæNc¢jŸo2¡Üˆ<¡úz¯™‡æ¥¢‡›ýÂD/ÖÎ.hÆqïu~U9I^x§6æõLÔ8´å‚3Sž€üä^ «!ᇻ1ù©½ÀöðÅÞ^c¬âDí¯â³—@ß:­NâÅy?y±¯‚Æ¿ ‘ð¨nL~ߨäÉL¹”–ü-Ë “Cæ&šû*¹6Ñ ©ÌuÌ©îÙÜÀ»¿Ohü{ @Îè(x7ö:kͰÄf¨Ã~Hxך›ÖŠužÄŠ‹n‰:ódÑ~³¢.K ñ¯ À­H~нž&©Úu9D€Wü à„½´šýâš\g§€©üš$4LR t:§ñ„` $?üqÂúó4û}íÔøGÂsøÛnBòÃ¦Ê è4aø»V»mˆ—/b_» É×5ßùxªÈ‚æìüÝ©OÝ—ísW>Ó^ŽžûÀ´H~˜î4ŒQfkö ÞêüÝ)áüo¹ Cæyü0|cBtÉ !ùnÂd0a•0Ü­‡$¼Z¹÷a:KñULÉ;“®ù:\$¿Ã‘±¶7m³ßWgã ÏÏÿ u£„â·É‹7so`W3"k xÉï\sjç¬îã9ñ“ðF©Ý¿ìvAõ[u…~ÿ«þa—Fò;GÛsLÞì÷e·HM^ùU|rÕÆàiçsN7ü7®@C•t"ùgæ+o8Üd¶ðg´áMUO4‹WeîúB¯ ù…Ó*žÔÐK»Ó3Ÿßb?oEvÂÚE9ïê(Ö$î–Í~F!Æ"dòØ7yõ6pß¾ã:<¶‡CT­è·ŠëŒ½Ñæw Ž>è÷ä4þÀH~G˜?öÍ_à T]E7ËËxÞÇöX¹°Å¢äÉáöKebò‘C—¸ìAý|W$¿ýql…aþ¦Ðø·1Ö)ŠäÓ¥øU„Æ/Fã­3ž©lƒä·³UΗ'ìi¯ Gº_·Jã€Ü“ ã{Æû¯µoKPj IDAT²Ó§üjΣÖÉoÑÇ:7—978ÜÍÓ†·è¶qwãß™ `f¹½~ì;iäTâFD99ù rYÈÌÇ“#’ßµàÁ±s£YèÔ¾PU§2/íînü[néÍ|v†0÷=ð4êTìKÄ«e™þº=é”äw²ÔNîHx«?0™+ÿІ¬ß¸7íÊ÷µwScYà `ì!“‹MKé¬Ã H~»Yëp¼Vmouf^3#‘nà2áaËx]œÃîÛåTª~/÷[šä·•µ6¾3M’ð–;T©¸óCe7ÎÉh(¨º†ÝF{!:]´—¹%«EÙwË“.<’ß&VlüØûè?IÂ;¿9Æ£.ä}‘ò¿j"4îvô|ÕР‚“Ù‘+éüµG´{o‹VýמÜëH~;àú¢uÞNg_ÿrdVøÊ¸JÉ>:u‘kJdï"ù-oѳÝrÕ^7áƒÆ?¿ñ¸ ##ª#&ŸØ{4W ó ù­m¹ü´õµårÞ©Ùï‹Æ?•ÑÛ{‰Xf§´¶ËÞY#À¯øçÅiÃöÊö£ùɨ*–fÓ°%/¡xRIöÇ8Ëq«^ÎQõFÿ´Îa4­ÿ5J«úÜ9póφÎr¦ë_=…·=AóÅ­6¿CÑŒ‡œšý;ÍìwÝ9×`|m²#K>(çÒÚº,|(Ÿ¯–+$<óL~ˆ=ä6 õõhrÈÇêc|˜{ºÞÀíÖ8è-ý4r’€,õñ÷NË ·>ã¼u9^§‘dǬx]‘šœŒw®V“*ö¶ñX5¨ 6P25´zN»©“ü°0ÒÛ+f>¢áªì¢µ×cn¹ëù'Z µÏ1Ù í8UÕ Ú®œ£Ä×éÕHê\,Gîí6ùV­L2ûr`{ÒKlêG¾WßçÕvä8Éê)Sõ´Ôß9¬¯ÉÙûÔ­i¾gw^1ÏAø{Ó¸ÎÏIÚÜË`'9ꌤq Yíä†Sj޲ò²Ûûù‰p9àä<Ÿ;#ö¤‹% ¬Ø[™Ïvë.3¼p’ʪÎúž¸ætÆy(îÖ”Ó•cÙ§´dýçE{ŠI[ÚŽä=cÈÜâJªZÛ*yG+&nE|…º¨= ߦX¦=®gÒmu¾Ä¾­uàân`Ém ÐsF5d¶³ç;¬Ø\1U§ªÌœúïj¡g¡ªÔ9>©,·|–ð-ë¡YK®_c˜¸1,WæýûÑî £¨%$ÃøëW,®†Qˆ¬˜½’qsu%{æ%™„½”rÕ(ÖA.a9•ܬÚ7ióCÁЧÃW ïdÙÍ~«£/øVɶêD.‡Q¯ÍˆË ŸÇÈL6¼ÎñWa[² ‘³‹MÊ1ö—¶ùð_cÒžjäê+Mý<)¼áÔÃ@¯Ïow3Éo]¤¸A"ùýîø™ÔPfÕðCêëû蹬à<Ù7¤ÃªÄf¤[ÊQ»ÂÈUiÔ)sl·éð>_úv÷C_0p’þØ#Ôê±[½DïrßH÷çF ÃäJ¶¯¢+žrâòÕy©ÊQ‹µçQ­•?f9[“yÌ}õ 2ß ˆ€À@G<¹ã¦®¥[½UçÙ–•¼èg¶"Vµv:Wåð¾Ý7­ë<}Á@3®óÃæ<‹ôܵ€‡=¶væÜVñµ}šMð ùa^¡s–ú–Únõà6$¸/¨Bòÿ& X³Õï"óÁÆ}Á€ÉÀkœÍ~d>T¡/0üp]S6øávø#ó¡}Á@‚ä`Fd>ŒE_0ðEòÃàgøÅÿUµWô¨9u`µÌ¤û&.Áó:ÿÕÀ‘û°8X2Œº¨Õgæ>WOZñt±Œe(§þ¤¤Ù̇[ьÑü0˜L{2ý„OrÑÐ`÷ ÆB²mŠW& VUU%“Ú^Ú)*·(j'ê|€óÈ|x}Á8ïð8Ý­Wø©1ÂnÛSÙïçp¶VM1[‹%_˜QŒV¹É)¶Xš™¼xÚãUx‘|Mo Á®hóÊ1(Ø ØÚWW93cÓ[®«4Wu”†–Nµë¶8VüßዱS˜N´˜}Á×ÛmÿÍN[MÍH~G»ãL_u¬ô~‹W}Õ3Åæ…SU9ÑKëR˯j=5¢Õ[GùdfOxsr_ðrsºhZ}Ƀ%Ç »-§êàRÕçÛ9E#]…–³+V’úäFQ»ªs×ù9«gÏcUÿû}rÍ–„?ÌIý1ƆŠE‘üÎõÖ)¶ç—Ùð7„³‘²j#5Í«¸‡K£/ ùa0™-Œ d\÷LõìÉ9‡l¨³Ýì&¿*žoj§ÚîxÓeÎÄÌ©ó;¹/K;â»â‰äá4‡+6írxרÅRÛÎ÷bkôrÊuÞØ6}Á+nW+Öù-´ùa.ïº)T£K[ß.Í~X}ÁXÉïDœVq7®çÃáè Æ´H~F’ùhöÃ6¸/³!ù‡*nB;` /“ ùèuGæ£Ù£//"ù…S)ƺµð‡íÑŒç‘üð5.Ø:ßHÖð\½¶±šÍÛDúvè ÆcH~™*sxj"ßëzežŸ”`Oèá7ìáÉÌG³D_0nõÏÛÀn¾ï“•úGÄ;çϘZ±Üˆ ³P妩«_Å‹17bƒð²`ÎCÀ~~}"oW Ë£Ío^Æ jÛJ{àl¦ÿ὿®ø‚5u9|?L†‰‡ Ÿ\âçxü¹úGRf®nÉ$Ônî¤òràëï—3Òìž]šýú‚1Éo^vPx¾>E2—üü¾š¶§Ïðß?б/W~’ð䵆rFd!Ƈq ž@_,*I¥FQò¿µ¸ž˜ }ÁèDò›šÚlÖ°“?›[ïB¿†¿ÂU³fg¯ïWΚǕìY¼I£Q”\8Ϋ›Û‰›Ç‹f?@â¾`´á:¿ȶ¥9¯öˆCÕTçigÅÔ.Ýð•,S-?Ç Nrþ5ë¸9óÍv=÷â9?‘iO˜m~kˆÿj›úaþ³ø¿Fe±þöž+“_Ì!÷„ôI“”æYI êåzj}ÔùÊ¥R9°q`Î<í|ÐŒ¢‰fî3Uû“SUí=|ÅÙÇpž}M’¸uc^qOY±ÎxXC_ðŠÛÕŠu~ m~;0~ä±3àkª†aQ{ØßOFòÛŠq¿' Z¢©/àV }Á¸H~»Š¯l[ëԎǰaÇâ¾à“‘ü6—ìÞìØ¸ßhö²ï6ÖNI~lÐÉý­œ8Ï´tæ î (p2®:ÄÉoõó\õÔÈEÇÚ#óÝŠ…àG$?HGEÀÃ;·Ì|ôù@’ßžü'Å" ç9Ï[Ú2ózðö6ükÔË’så/®ð|¢ÖÐóIU•Ö5áë׆ã}nЀ6¿ u¶cõ´Æ/=“ÿ5»þößå>If°vø\•âÑ«æwBÌà>$?d5D@Ï{fOâL–ûD†6{xO “Ù\Ô™«ý Éo7wœý0 O¹V´Q«¡¿/7üÒéáÀÌhÃu~¨`_ ¨æGŒ˜’ëN Œ¯ö+ï™ôºWŒp=ŸmÝu¯ ùm属/5&×ö]™û0ä` ÚîAQ'Ü5"?Ÿ™/ ü€—ÈlåÅkžz #Ç­-­gêË¡oWâj?` w¨ëü®óÛÇ»Û}çs=wÔ–°2_·z€ÉƒÕFÀÐ/œŒè?‘׿"2`ˆO–G™9÷Õ;™Ïoæ½XÈŠ»ÒŠu~ m~¸]gGð±È|€áH~;Xå·ЉÌ׆«ý€fÜ ’^@Ì!óu"üNòÁû¹¯°’ßò–>Ï2€»Å‘Ž£Í±H~˜ÂÉÌ7Í~@`4ìáX$¿µíw†K"àfs—8a<Œ†=ØH~˜TxÓZüßmùnE³ŽBêüv¹m¿^`2€~4ì¡ÉkØ ’ùžD³6CÃF!ù­êسڊÌ÷ ÂVGÃî@òê–ˆ€d>UH{¸ÛÉoчRû<-±9# ™oUÍ~û(°ºqñ°#’ߵྴèIè]óD@¢ù¢–[k(EÃ^tJòÛ ©¢èÅHSßl¸Ú3 aó ùagOF@2€ {˜Éo1´^´¹5’ù&G³žAÖ@òÃYÆF@2p8ö°’ßJh·¨3’ùÖB³F¡a«#ùátµÌ·(šѰ‡ü–ÁIënÅHæÎAÚîH~@JFÀäs,Šf?Øßq’ß8]½âÂY ÀfhØÃH~€NíÛ}ýí èD³ßáhØH~ àDõ0ãz¾y^À‰†= Fòþ㿇ƒ¸.šý¶GÃ` ùÍŽSÔ3šïÛM" +k „¿ýа8‘üpºQ‰í[M€À3hØÚü¦F³Ä­îh¥£xñÛ¬£Uаô#ùáDôÌ'—´aZ¤=`,’ÎòüÕxD@  ݸÀ­H~Sã7Ðëw`§÷örYÅëhØCòÃþ^Ï| " @Ãð’v6[æKß•¼w£a˜É{š<ó%ˆ€o áxö€ ‘ü°›µ2_‚øÍhØNCòÃÈ|D@xаœŒä‡ðZÕZDÀc©kœ†=ÉS£©¯ðI¼£a€Šä‡I‘ùÆ"îM>Œõ @EòÃtÈ|·J" Ëyu¹PsÉ!‹<黜i\+@’¦@æ{ ½Àp’^Fæ›N@òÃkÈ|s"ÀÆH~x™o D@ØÉ"ó­ˆÛ ùá!d¾ `u$?ÜŽÌ·"à™Ô·À…òA¿‡wV b$?܈̷="à9’ôÐùÖ·²HqºT¬gd8ôûçí `OŸÏç{„â uˆŸ_Ÿ_o×÷*îÚr(nê(žrŒwÛÓõTÉxKJmiÅj8ç×øÜ?ï8m~Œv¾ÃÑ ¸%O€ˆ»}¯ëúþ 䶇ïWñDö#Ër’OrSTKá+»J—ÖÒ–Œ«VÌèOFÌM.·Üälu ü!AòÃ0d>Ĉ€‡S/ 4þo6IÖI0JŽ›Ðrc+–«@n,#ÞÙU¢§æv‡{\á1’ óÁ@Ü@mz»Š«¦n_Œ¨[¬­¬@±>áʇ†Eá™_v"4ã:?táz>øq-à!Ú™d¡lºk˜t1üyŠÊu¶zªäT5¿Î%Ì.m~hD;šÑ ¸"™6Џö`q¾ ¿’QÚ²K\Ž,V½Æ.W1u˜¸=ÏîÒõLB­¹AÖ_-*™÷¶ÖGléˆMaÅ-~æ:“ù0Ü pæ.gÅ:Ÿcݵ³bÍW¬ó[hóC2nB+ <ƒä2žAÄh‚´H~( óáD@,ÍÓ"ù!‹Ì‡$ zü à‹ yîgØH~øƒÌ‡ÉÑ =H~ø™k!žF=FÙÆó¹á)Ê×oäzý…¶l¨xoo;ï^ÃNx;ÜÝŠ/F³Ã–àªjØŸ7¼åÌ_ÕæW¨'ÁÖ‹ûüEæÃƈ€w/+»¢HX¼É‹Â’Õ åþHª‘ “¼¯LÜ<_j!rŠÉ²4uA©}½=£·÷D..Áè.^€I4I¾JÞik lKŽW¹«ú¾Ÿ'ßz¦"‡ñT5žb1Y§è èGò;ˇKúp$"`¿qÔŒ%‡Œ[ÕÒŽ'ô|»×Ø ÃY𠬫qz{OA÷.pÑÜ'NrþE÷L€2‰ªª‡t–Vuç Ð6¿ýñÛr½ÈQ/tûþ¡^äãWrŸÛ£;{lãïŸèÅS޼¦07”ï¬U<Û$nuÄõ^+^Ö6¤Îd>ÀïØÅ»˜… -=7[ ÷¡ÍoOd>Kà05!VÊÞH~»!óÀcâç°¼]À…ä·2<ŒC.–CòÛ™xüÖFæü½n"ù­$Îyd>ઠsÎÇjÀÆH~ËH^õHæÃƪž|kMøobè¹Ý¡óV‰ä}qc_†Q[7ŽÕ˜Éo ͯ¼&1°q¯HÕ»•É‘{àÁÈÆÃ¨iHÆ„H~ àØ9æp9‚ lúJFqFÉÜ`m£W5ÈÉIد±®ú/0ÉojꙕƒîC˜CŽšHBj1%„àU,áŠRZ¼}&¥%S±ëiÔʘGÏ\˯ÔI«ÿMf“ý 7!ùÍ«ê”€Ëæp+gëWhª^Ë+‡ÿ¾3÷çç§vô\¤ä®¿¹Ó~Ÿ¯1é\…åRîCò›ç`hœÃ ü T¹‹Þ:ƒNíŽ ¯™–y=Í}&”«@ˆ_W|”DîC#Ū7ߨßú?[O/-ÓÛŸ'ŒZÙ3Uluž ɘa+2îcP»5“žP»[íèžÞ^c¬âDí¯dî—ìûöÌË»Œ,˜Èå¶Ü·riÇŸØ¥%•1úýãÒäÆTìh{U™ßZÝ$?àF„9l)ih)þá/ùo[èñžKiÉß²œ¤ÂI~M‚cî+£ÂFÅf; xRòe¦{M©ŸÛºþ.¥\áêçÎÅkoWÅBäè3„{’PÍŸç^ßÃQd»Ë•ÙÂír'`£»SN:÷‡:i<WM´j\uøIV=?칫múu¶Ñ?/N%.¡8¼ì}VÿxwE“ü€ë¢qJ"‹Ý„YÛÀY>i£-~Þ6¿dŠ“œ;H~ØaF‘—iò*Æ\ƒ«ìL—“°ë+ªXˆ¿MÑŽ•žìr^GòÃJöØë`?wr«ŽùqM:Ã_¿zusH~x—ÍÀ<­n—¸$Wšzã…ÑCúL–2¦bWO-Êì•t8i kÚÜmX±Î1ç°œwºë à]´ùÁ‹0ÀêH~‹ûŸ0À¯ížGùܵâðCî©uÈ2æºvÖª&*žÇACüÖPѸlÀpmOôøùùyò²úPɱ/w+ëuçµ7½~$¿©åSiEžp7µªêr~O””SRˆ1b[ëš¿VÏ–j¨-Gò›Wó“Ðàò†MÏ›âqåƒß.Çm¹®Oãm`Ūª#ªw¤3™sÖ’¯¾’ù²'š f,ÎmÂbIDAT0üæ%ð"õ9ÎÖÜEr9FãVî)ÁžBŒª¶Í—:@nÖ’š‡#;ƒZœ /­)”Ø’ßØ“L¨ùú³ªcZn*µ÷¨U]Ýü{»ápÝ9#É'„?Øþy»€•Ä9£-dxr•:•$ß\ކFUûçëjŠŒm÷>ç–™E$?€K¼<ÇæóË= ÷ªWþå¦è¬jnà†æFϬ¹qÖ-Ρ@ù!ñû`ÅŸA+ÖXÚŠ;ÝŠuð.ÚüNAò8Éà$?€SüNAò8Éà$?€SüNAò8Éà$?€SüNAò8Éà$?€SüNAò8Éàÿ{»ù|>oWÀì8PØÞççççí:à ôöœ‚äp ’À)H~§ ùœ‚äp ’À)H~§ ùœ‚äpŠmßÛ›¼Óÿ’ºÏ§ývrܸ¼(˜œ|oï3»-‡Ù6ù}}˜ŸÏ§'Ï ©ÃÕ—)<#ÞIeôµ§sèp‡{{“£¹çà.‡i(Ä>£%·™%y+Þéüûïl‡Ž‹£p¼ÍÛü®ß£[òë9ÓÃ/íð¥þ! IÈÂsÆÕ+VCwP÷Ðøëï!kžC‡:#=€mÞæ—/ï¾ÿýùù‘Ÿ¿³s…¨uÇ\µÀäøž£sÓÐàó+þð»ÓåZ}pªCÇÅÑÀöm~áÀZÛÁâûŽß ôrHÏÀCjà˹7åÚêŠ*Neø¡ãâèló6¿D®W7‘ü&.ß=×Ùćcÿå5Å9jI~C:£•áÅCÇÅÑ8Õæm~ÉÑ3þYþU»l’ž£[')Džr͹凹¹@®é<û}Iøä­C‡s.l‰Ë{Nñ¬.‰ãÌ™IEND®B`‚cyrus-imapd-2.5.10/doc/install-sieve.html0000644000175000017500000000762513001236020015164 00000000000000 Installing Sieve

Installing Sieve

This section assumes that you compiled Cyrus with sieve support. If you specified --disable-sieve when running ./configure, you did NOT compile the server with sieve support.

Configure outgoing mail

Some Sieve actions (redirect, vacation) can send outgoing mail.

You'll need to make sure that "lmtpd" can send outgoing messages. Currently, it invokes "/usr/lib/sendmail" by default to send messages. Change this by adding a line like:

   sendmail: /usr/sbin/sendmail

in your "/etc/imapd.conf". If you're using Postfix or another MTA, make sure that the sendmail referenced in "/etc/imapd.conf" is Sendmail-compatible.

Managing Sieve Scripts

Since Cyrus is based around the concept of a sealed-server, the normal way for users to manipulate Sieve scripts is through the "sieveshell" utility.

If, for some reason, you do have user home directories on the server, you can use the "sieveusehomedir" option and have the sieve script stored in the home directory of the user as "~/.sieve".

Testing the sieve server

  1. "timsieved", is a ManageSieve server used for transporting user Sieve scripts to the sealed IMAP server. It is incompatible with the "sieveusehomedir" option. It is named after the principal author, Tim Martin, who desperately wanted something named after him in the Cyrus distribution.
  2. From your normal account, telnet to the sieve port on the server you're setting up:
       telnet foobar sieve
    

    If your server is running, you'll get a message similar to the following one:

       Trying 128.2.10.192...
       Connected to foobar.andrew.cmu.edu.
       Escape character is '^]'.
       "IMPLEMENTATION" "Cyrus timsieved v1.1.0"
       "SASL" "ANONYMOUS PLAIN KERBEROS_V4 GSSAPI"
       "SIEVE" "fileinto reject envelope vacation imapflags notify subaddress regex"
       OK
    

    Any message other than one similar to the one above means there is a problem. Make sure all of authentication methods you wish to support are listed. This list should be identical to the one listed by "imapd" earlier. Next terminate the connection, by typing "logout".

  3. Next test authenticating to the sieve server. To do this run the "sieveshell" utility. You must specify the server. If you run this utility from a different machine without the "sieve" entry in "/etc/services", port 4190 will be used.
      "sieveshell foobar"
        Please enter your password: ******
        > quit
    
    This should produce the message "Authentication failed" with a description of the failure if there was a problem.

  4. Next you should attempt to place a sieve script on the server. To do this create a file named "myscript.script" with the following lines. Replace "foo@example.org" with an email address you can send mail from, but that is not the one you are working on now.
      require ["reject","fileinto"];
    
      if address :is :all "From" "foo@example.org"
      {
        reject "testing";
      }
    
    To place this script on the server run the following command:
      "sieveshell foobar"
        Please enter your password: ******
        > put myscript.script
        > activate myscript
        > quit
    
    This should place your script on the server and make it the active script.

  5. Test that the sieve script is actually run from deliver. Send a message to the address you're working on from the address mentioned in the sieve script. The message should be rejected.


last modified: $Date: 2001/10/23 18:14:48 $ cyrus-imapd-2.5.10/doc/install-upgrade.html0000644000175000017500000007763213001236020015505 00000000000000 Upgrading From Previous Versions

Upgrading From Previous Versions

Upgrading from all 2.4 series to 2.5

  • It is strongly advised to shut down the server completely while performing the upgrade, because newer daemons will write mailboxes.db entries which aren't compatible with the old daemons, and may cause crashes if you try to upgrade a running server. You can start the server again immediately with the new daemons installed.
  • The most important change is that index file upgrades are no longer automatic. This avoids the IO storm caused by upgrades from 2.3 to 2.4. Even if you are upgrading from Cyrus 2.2, it won't cause an IO storm any more.
    Instead, you need to run reconstruct -V max to upgrade each mailbox in turn. This will upgrade all mailboxes to the current minor version 13. This can be safely done while the server is running.
  • Older version mailboxes will continue to work "forever", though newer features like annotation quotas will fail, since there's no space in the mailbox header to store them.
    There may be slightly inconsistent search results until you upgrade. The cyrus.cache format in 2.3 and earlier ran words together in cache, so searches won't obey word boundaries like they do in 2.4+
  • If you were running Cyrus 2.3.x with expunge_mode: delayed, then the contents of the cyrus.expunge file will be removed the first time the mailbox is opened, and the mailbox will act as if expunge_mode: immediate was set until it is upgraded. This is because version 2.3 mailboxes used the cyrus.expunge file, and it's not worth the complexity to try to recreate that file.
  • After all mailboxes are upgraded, you should run quota -f to make sure all the message and folder count quotas are correct. Cyrus 2.5 supports new quota types, and the counts need to be calculated.
  • Many configuration options have changed and new features have been added, read the release notes.
  • Mailboxes.db and quota internal formats have changed.
  • Just go read the release notes already: https://docs.cyrus.foundation/imap/release-notes/2.5.0.html

Upgrading from 2.4.17-caldav-beta10 or earlier

  • The schema used for the CalDAV database has changed. ALL sites MUST run the dav_reconstruct utility for each of their CalDAV users.

Upgrading from 2.4.17-caldav-beta9 or earlier

  • The time span calculations for recurring events in which the component containing the RRULE is not the first component have been fixed. We recommend ALL sites run the dav_reconstruct utility for each of their CalDAV users.

Upgrading from 2.4.17-caldav-beta6 or earlier

  • The time span calculations for various VCALENDAR components, especially VTODO (tasks), have been fixed. We recommend ALL sites run the dav_reconstruct utility for each of their CalDAV users.

Upgrading from 2.4.12

  • some LOG_DEBUG level messages are no longer created by default in the duplicate delivery system, so you won't see them in syslog any more
  • mailboxes in the DELETED. heirarchy are now always suppressed for non-admin users, even if delayed delete is not enabled (see Bug #3604). If you happen to be using this namespace at your site for something else, you're crazy - but you can set "deletedprefix" in imapd.conf to an invalid value (e.g. '-') if you need.

Upgrading from 2.4.11

  • To support bug-interoperability with older versions of Cyrus, the quota command now supports "-1" as a synonym for unlimited storage

Upgrading from 2.4.10

  • Duplicate database formats have changed, so any duplicate or vacation data will be lost - meaning that vacation responses will be sent again, and duplicates just across the upgrade time will both get delivered.

Upgrading from 2.4.9

  • quota -f now works correctly. If you are upgrading from earlier than 2.4.9 we recommend that you run quota -f to ensure that all quotas are now correct. There is a slight race condition in the quota command, so it's safest to run with the server shut down, but this has always existed.
  • On the topic of quota -f, the documentation has been updated to make it quite clear that you need to give "complete" prefixes if using quotalegacy, as it doesn't implement quite the same semantics as other databases. If you run 'quota -f a' and you have domains starting with 'a', you will be quite sad at the results. So don't do that. Running quota -f with no argument, or with a full domain or full user specification is perfectly safe.

Upgrading from 2.4.8

  • CYRUS_PREFIX environemnt varabile. If you have an environment variable "CYRUS_PREFIX" then config files will be searched for in there first, so for example the file /var/cyrus/etc/imapd.conf will override /etc/imapd.conf if your CYRUS_PREFIX is /var/cyrus. This is to make things easier for sites with multiple installs on a single machine. You will want to check that there aren't unexpected files in those locations when upgrading.
  • New config options: *_db_path allow moving individual DB files to different partitions - for example you may want to put the deliver.db onto tmpfs to improve performance.
  • KNOWN BUG: quota -f can double ALL quota usage values for all users. This is particularly bad because of the bug fixed in this release where quotaroots were not correctly updated on folder rename. Recommended workaround: run quota -f twice.

Upgrading from 2.4.7

  • New config option: proc_path allows setting the path to the proc directory onto tmpfs more easily

Upgrading from 2.4.6

  • New config option: failedloginpause allows you to change the pause after a failed login from the existing default of 3 seconds
  • On Solaris: now getpassphrase is used, so passwords longer than 8 characters will work with management tools
  • $confdir/proc now gets created automatically if it doesn't exist, which may impact init script design
  • If you have damaged mailboxes that weren't previously fixable, a reconstruct of those mailboxes may be advised

Upgrading from 2.4.5

  • New config option: suppress_capabilities, which takes a space separated list of capabilities which will NOT be given in any imap capability response. This can be used on frontends to not display capabilities that older backends don't have, so clients don't get confused

Upgrading from 2.4.4

  • sync_client no longer forks two process - it just pre-forks a single process in rolling replication mode and uses it "forever". This is to avoid the bug where it used to open the BDB environment once before forking, then close it in every child, causing the reference count to go negative. This also means you can start it without '-o' and still have the master start without the replica already running.

Upgrading from 2.4.3

  • Actually, it's more upgrading directly to here from 2.3.x or older. ALL upgrades from previous versions now incur a full re-parse of all messages, which may take a while. In exchange you get reliable upgrades though, and guaranteed still-searchable cyrus.cache records.

Upgrading from 2.4.2

  • The AFS ptloader configure options have changed. If you were previously specifying --with-afs when you built, you'll now want to use --enable-afs instead. Additionally, you may now specify --with-afs-libdir and --with-afs-incdir to facilitate finding the AFS libraries and header files.
  • The sync_log_names option has been replaced with sync_log_channels and the documentation and tools updated to match. This is to use a less overloaded term and allow multi-channel replication to be used.
  • Cyrus 2.4.3 can now XFER mailboxes back to earlier version (at least as far back as Cyrus 2.2.12) in a murder configuration.
  • sync_client in rolling mode now only connects after forking, so it no longer blocks startup. You can remove the '-o' option from your cyrus.conf entry if you want, and not have to start sync_client manually afterwards!

Upgrading from 2.4.0

  • The response to the "ID" command has changed slightly to include git metadata rather than CVS metadata - so your in-house tools expecting a particular value may need changing (very unlikely)

Upgrading from 2.3.16

  • There is a new index format, so downgrades are not possible without a reconstruct. We recommend that you take a full backup before upgrading, and perform an upgrade with a small test server if possible to make sure everything will work for your site.
  • MURDER does work, but you can't rename a mailbox back to a previous version backend because the index was upgraded.
  • There is a new replication protocol, so you can't replicate between 2.4.0 and previous versions in either direction. You need to upgrade both before you can restart repliation.
  • The default value for delayed_expunge has changed to provide better QRESYNC and replication support. The default is still pretty efficient, but you may want to change it to 'immediate', the previous default
  • The default type for all databases is now skiplist which is very reliable now, all the bugs are ironed out! Because ctl_cyrusdb -r automatically converts databases between known types, you shouldn't need to do anything, but if you want to keep the old defaults, you'll need to make them explicit in your imapd.conf as follows:
    duplicate_db: berkeley-nosync
    ptscache_db: berkeley
    statuscache_db: berkeley-nosync
    tlscache_db: berkeley-nosync
    
  • There is a new lock folder which defaults to configdir/lock/ and contains one zerobyte file per mailbox. These can get pretty hot, and don't need to persist over reboots (they will be auto-created when needed) - so you may want to define mboxname_lockpath to be on tmpfs or ramfs or similar. It certainly makes sense to clean it out on restart, because names will persist in there forever otherwise. Even on mailbox delete these files aren't removed (to avoid potential race conditions)
  • The make_md5 and make_sha1 utilities no longer exist. If you want to check message file integrity, the best way is reconstruct -r -n -G. This will parse every message file, check the sha1 against the value stored in the cyrus.index, and tell you about mismatches without fixing them.
  • Speaking of reconstruct, the switches have changed, as has the implementation. It fixes the mailbox "in place" a lot more rather than creating a new mailbox, meaning that IMAP semantics won't be broken. It's more likely to abort rather than complete if your filesystem permissions are wrong - fix them first!
    -kRemoved, expunge data is always kept
    -gRemoved, GUIDs are always stored
    -GChanged, now means "re-parse the message". If not specified, reconstruct only checks the message size and assumes the rest of the stuff in the index record is OK (pretty safe because we do CRC32 checks on index records now)
    -sAdded, skip the stat call, so reconstruct doesn't even check the message file size - just that a file with the correct name exists at all
    -nAdded, don't make any changes, just report what would have been done if -n wasn't specified
    If you try to use -k or -g, you will get a warning but the reconstruct will still run.

Upgrading from 2.3.15

  • The SQL detection code in configure has been reworked. Separate options for the include directories and lib directories have been added. Previous SQL options may not work as expected.

Upgrading from 2.3.10

  • STARTTLS is now allowed for externally preauth'd LMTP connections. If you don't want STARTTLS to be advertised and used by preauth'd clients, you can set <service_name>_tls_cert_file: disabled in imapd.conf.

Upgrading from 2.3.9

  • The method used for generating Globally Unique IDentifiers used for replication has been changed to be the SHA1 hash of the messages. If you wish to upgrade the existing GUIDs in particular mailbox(es) or the entire server, perform the following steps in the listed order. Note that is is NOT REQUIRED that existing GUIDs be upgraded.
    1. Zero GUIDs on the replica (reconstruct -g)
    2. Regenerate GUIDs on the master (reconstruct -G)
    3. Regenerate GUIDs on the replica (reconstruct -G)

Upgrading from 2.3.8

  • You must install and configure Cyrus SASL version 2.1.17 or later to use Cyrus IMAP 2.3.9 and later. You can download SASL at http://www.cyrusimap.org/mediawiki/index.php/Downloads#SASL_Library.
  • The default value of the allowplaintext option has been changed to disabled (0). If you need to allow cleartext passwords on the wire, then you will have to explicitly enable the allowplaintext option in imapd.conf.

Upgrading from 2.3.3 or later (64-bit machines)

  • Due to byte alignment issues in cyrus.index, all mailboxes will have to be reconstructed.

Upgrading from 2.3.4 or 2.3.5

  • Any mailboxes which had messages appended/delivered/copied with a 2.3.4 service or copied with a 2.3.5 imapd MUST be reconstructed in order for the new messages to be displayed by clients.

Upgrading from 2.2.x or earlier

  • If you wish to use separate metadata partition(s), you MUST first shut down Cyrus and then perform the following:
    1. Set the metapartition-* and metapartition_files options to suit your configuration. For a full description of these options, see the imapd.conf(5) man page.
    2. Create the metadata partition directory(s) listed in the metapartition-* option(s), setting the ownership and permissions in same fashion as step 6 of install-configure.
    3. Run the tools/migrate-metadata script (as the cyrus user) to move the metadata files listed in the metapartition_files option from the spool partition(s) to the new metadata partition(s). This script may take a long time to run depending on the number of mailboxes on the server, but presumably the metadata partitions are located on high speed storage, so the writes should be relatively fast.
    4. Restart Cyrus.

Upgrading from 2.2.2 or earlier

  • The Cyrus database backend configuration is now handled at runtime using imapd.conf options. If you are not using the default backend for any of the databases, make sure that you specify the correct backend(s) in appropriate option(s).
  • The format of the newspeer option has been changed. The existing format will still be parsed, but the option should be upgraded to use the new format (see imapd.conf(5) for details).

Upgrading from 2.2.1 or earlier

  • The sieve bytecode format has changed again to correct an issue with the short circuiting of the allof and anyof operators. To upgrade existing scripts (outside of home directories), you can run the tools/masssievec perl script included with the distribution. It requires a path to your sievec binary. This should also upgrade scripts that have already been compiled to bytecode. For example:
    masssievec /usr/src/cyrus/sieve/sievec
    

Upgrading from 2.2.0 or earlier

  • The improved directory hashing (fulldirhash) is now a runtime configuration option. If you are currently using this feature, then make sure that you enable the fulldirhash option in imapd.conf.
  • The format of mailbox index files has changed. They are upgraded on the fly, so you need to do nothing to upgrade. However, to downgrade them you will need to remove the cyrus.index files, and reconstruct the mailboxes, otherwise the index files will be invalid.
  • ctl_deliver -E has been deprecated in favor of cyr_expire -E. This new tool does both duplicate delivery database pruning as well as message expunging. You should replace the appropriate EVENTS entry in cyrus.conf with one of those in the sample configurations in the master/conf directory.
  • The sieve bytecode format has changed. The new format is encoded in network byte order, and will be transferable between architechures. To upgrade existing scripts (outside of home directories), you can run the tools/masssievec perl script included with the distribution. It requires a path to your sievec binary. This should also upgrade scripts that have already been compiled to bytecode. For example:
    masssievec /usr/src/cyrus/sieve/sievec
    

Upgrading from 2.1.x or earlier

General information (ALL SITES)

  • The default database formats for the mailbox list and the seen state databases has been changed to the skiplist backend. There are two ways of dealing with this if you have been using the defaults.
    1. Specify --with-mboxlist-db=berkeley and --with-seen-db=flat to configure. This will instruct Cyrus to continue to use the previous defaults.
    2. Use the cvt_cyrusdb program to directly convert the databases. This should be done with the server down, and with the binaries from the new Cyrus distribution. Change any paths that do not match your configuration.
      For the mailbox list, the command looks like:
      /usr/cyrus/bin/cvt_cyrusdb /var/imap/mailboxes.db berkeley /var/imap/mailboxes.db.new skiplist
      mv /var/imap/mailboxes.db.new /var/imap/mailboxes.db
      
      Note that the use of full paths to the database files is important. You should also backup your old mailboxes database before moving the new one in.
      For the seen state databases, the command to get them all in one fell swoop looks like:
      find /var/imap/user -name \*.seen -exec /usr/cyrus/bin/cvt_cyrusdb \{\} flat \{\}.new skiplist \; -exec mv \{\}.new \{\} \;
      
      The slashes are important for shell escaping. Again, you should back up the contents of your /var/imap/user directory before executing this command. These commands may take some time to complete, especially if your databases are large.
    We believe that skiplist offers considerable performance advantages for these two databases over the previous defaults.
  • Sieve scripts are now compiled into bytecode. The program sievec is provided to do this process manually (timsieved will compile submitted sieve scripts as they are uploaded). To upgrade existing scripts (outside of home directories), you can run the tools/masssievec perl script included with the distribution. It requires a path to your sievec binary. For example:
    masssievec /usr/src/cyrus/sieve/sievec
    
    Note that this will fail for scripts that use the "envelope" extention but do not require it. Cyrus 2.1's timsieved did not do appropriate checking that the optional envelope test was required before it was used.
  • Configuration subsystem changes:
    • The tls_[service]_* configuration options have been removed. Now use [servicename]_tls_*, where servicename is the service identifier from cyrus.conf for that particular process.
    • The admins and lmtp_admins configuration options no longer union. Per-service options completely override the default value when they are specified.
    • lmtp_allowplaintext is no longer a defined parameter and must be specified using the service name of your lmtp process if you require a specific value.

Specialized information (Murder, AFS, etc.)

  • The IMAP IDLE command is now supported by proxyd and is controlled by the imapidlepoll option, which is enabled by default (60 seconds). To disable IMAP IDLE in proxyd, set imapidlepoll to 0.
  • User moves via RENAME and XFER are now controlled by the allowusermoves option, which defaults to off.
  • If you use ptloader, it now runs as a regular cyrus service. This means that you will need master to acquire and maintain AFS tokens for it. You will also need to create the ptclient directory under your imap configdirectory, to hold the PTS cache (now a full-fledged cyrusdb) and UNIX socket. In cyrus.conf, ptloader should be setup to listen on <configdirectory>/ptclient/ptsock. See the master/test/cmu-backend.conf example configuration file.
  • Also, ptloader has been given a generic interface. You should now specify "--with-auth=pts" (instead of "--with-auth=krb_pts") to configure. There is also a --with-pts= configure option that defaults to afskrb (Kerberos Canonicalization, AFS PTS Groups). There is also an experimental ldap module. Note also that if ptloader fails the lookup, authorization (and therefore authentication) will now fail, as canonicalization is done inside of ptloader.
  • The format of sieve referrals has changed to be more consistant with the current managesieve draft, this may cause interoperability problems when using managesieve clients and servers from different cyrus versions.
  • Clients that use old-style ACL commands that include the "MAILBOX" directive will no longer function. We do not know of any clients that have this problem currently.
  • Any applications that link libcyrus.a now need to link libcyrus_min.a as well.

Upgrading from 2.1.13 or earlier

  • We are now more forgiving of MIME boundry headers generated by earlier versions of eudora. However, if you have messages already in the mailstore that you want to fix you will need to reconstruct the affected mailboxes to regenerate the cached bodystructure data to take this into account. Nothing needs to be done for new messages to be treated in this way.

Upgrading from 2.1.12 or earlier

  • timsieved was corrected to behave properly in the altnamespace configuration. However, this means that it was previously looking for sieve scripts in "user.name" format instead of the (correct) "user^name" format. A sample script to do this (which should be run in the top level of the sieve directory) is in tools/convert-sieve.pl. Note that this is only needed if you are running with altnamespace turned on.

Upgrading from 2.1.3 or earlier

  • If you use notifications (previously notify_zephyr or notify_unix) this functionality has been seperated out to notifyd. See the notifyd manpage and example entries in master/conf.

Upgrading from 2.1.2 or earlier

  • Sieve has been updated to be compliant with RFC 3028 and draft-martin-sieve-notify-01. All notify actions and any fileinto and/or redirect actions using stringlists will have to be updated/changed.

Upgrading from 2.0.16 or earlier

  • You must install and configure Cyrus SASL version 2 to use Cyrus IMAP 2.1 and later. You can download SASL at http://www.cyrusimap.org/mediawiki/index.php/Downloads#SASL_Library.
  • If you use timsieved to manage Sieve scripts, and have enabled the alternate namespace and/or the Unix hierarchy separator, run the script "tools/translatesieve". This script will translate the folder names in fileinto actions.
  • Cyrus now uses the service name "sieve" instead of "imap" for the SASL profile of timsieved. If you use timsieved to manage Sieve scripts, be sure to update your password checking mechanism appropriately,
  • If you have enabled the improved directory hashing scheme, run the script "tools/rehash full". This script will rehash your existing directories.
  • The hashed deliver databases (used for duplicate delivery suppression and Sieve) have been merged into a single deliver.db database. You can safely remove the entire /var/imap/deliverdb directory structure after shutting down the server.
  • All of the Cyrus databases have been unified under a single BDB environment. A new ctl_cyrusdb tool is now used for database recovery and checkpointing instead of ctl_mboxlist and ctl_deliver. You should replace the appropriate START and EVENTS entries in cyrus.conf with those in the sample configurations in the master/conf directory.
  • Cyrus now caches SSL/TLS sessions in an external database. If you have support for SSL/TLS, and haven't disabled session caching (see imapd.conf(5)), you should add a line like the following to the EVENTS section of cyrus.conf to prune expired sessions from the database:
       # this is only necessary if caching TLS sessions
       tlsprune      cmd="tls_prune" period=1440
    

Upgrading from 2.0.6, 2.0.7, 2.0.8, or 2.0.9 or earlier

  • If you use timsieved to manage Sieve scripts, run the script "tools/upgradesieve". timsieved now uses symlinks instead of hard links.

Upgrading from a previous 2.0 version to 2.0.6

Warning: You do not need to follow these instructions if you're upgrading from version 1.6.
  • You can now pick whether to use Berkeley db to store seen state, the subscription files, and the mailboxes file or a flat text file, at compile time only. (Look in imap/seen_db.c and imap/mboxlist.h.)
  • The format of the mailboxes file and seen state has changed. It is not possible to preserve seen state, but upgrade the mailboxes file as follows:
    1. Run ctl_mboxlist -d > mboxlist.temp to dump existing mailboxes.
    2. Remove old database files: rm mailboxes.db db/* user/*/*.seen
    3. With the new version of ctl_mboxlist, run ctl_mboxlist -u < mboxlist.temp.

Upgrading from 1.6.22 or 1.6.24

Warning: Cyrus imapd 2.0 will automatically convert on-disk file formats as the server is used. It is not possible to run 1.6 after 2.0 has been used on a mail spool without reconstructing every mailbox.
  • Create some extra directories and remove the duplicate delivery database:
       mkdir /var/imap/db
       mkdir /var/imap/socket
       chown cyrus /var/imap/db /var/imap/socket
       rm -rf /var/imap/deliverdb
    
  • Convert mailboxes file to Berkeley DB:
       su cyrus
       cd /var/imap
       ctl_mboxlist -u < mailboxes
       ctl_cyrusdb -c
    
    Please keep a backup of your mailboxes file. You can dump an old-style mailboxes file by using ctl_mboxlist -d.
  • remove "/etc/inetd.conf" entries. The imap and popd3d lines need to be removed from /etc/inetd.conf and inetd needs to be restarted.
  • master process configuration: You'll need to configure the master process Cyrus process and ensure that it starts on boot. see this section of the configuration instructions.
  • MTA configuration. You will have to reconfigure your MTA to speak to lmtpd. See this section of the configuration document.
  • cyrus.seen conversion. The cyrus.seen file will be automatically upgraded as users read mail. After some time, you might want to delete the cyrus.seen file in each mailbox; it is superceded by the user/joe.seen file.
  • cyrus.index conversion. The cyrus.index file will be automatically upgraded the first time each mailbox is SELECTed.
  • Netnews conversion. The netnews programs are no longer built. If you are using netnews, you will need to apply the diff in the netnews/ directory to INN or see if INN is now distributing those changes. You will also want to run remotepurge on a regular basis to purge old netnews posts.

Upgrading from 1.6.13

  • Upgrading from the Cyrus IMAP server version 1.6.13 or earlier: if you use Sieve, you should run the "tools/upgradesieve" script, as the format of the "/usr/sieve" directory has changed slightly.

    timsieved, included in this release, will handle maintenance of Sieve scripts.

  • Upgrading from the Cyrus IMAP server version 1.6.10 or earlier: if you export news via the IMAP server, you'll have to change your "newsfeeds" file to contain
    collectnews!:*:Tf,WR:collectnews
    The format of the input to collectnews has changed.

    Duplicate delivery suppression is now required for Sieve.

  • Upgrading from the Cyrus IMAP server version 1.6.1 or earlier (including 1.5.x!): the quota and user directories are now hashed by the first character of the username. This is to reduce the number of entries in any given directory. It doesn't do a great job (and in some cases it will do a really poor job) but as a quick hack it shouldn't make things worse. Optionally, the data partitions can also be hashed by enabling the "hashimapspool" option.

    You must hash your directories using the "dohash" script in the tools subdirectory. (If you want to hash your mail spool, be sure to set "hashimapspool" before running "dohash".) This must be run as the Cyrus user. Be sure to stop mail service while converting. Doing this in single user mode is probably the safest.

Upgrading from 1.5

  • Upgrading from the Cyrus IMAP server version 1.5 or earlier: libsasl is now required. Configuring SASL to work may be a chore, especially if you use shadow passwords.
  • An ANSI C compiler is now required. gcc should work fine and can be acquired from http://www.gnu.org/software/gcc/gcc.html.
  • Make sure to read the upgrading instructions under 1.6 above.
  • Upgrading from 1.5.14 or earlier requires deleting the delivered database. Remove the file delivered.db in the configdirectory and make a directory called "deliverdb" in the configdirectory. This may cause some duplicates to get through.
  • Upgrading from 1.5.14 or earlier requires removing the PTS cache database (if the AFS PTS group support is used, which is not the default). The PTS cache is in /var/ptclient/ptscache.db, and you should remove it. This is because the format for the PTS cache for IMSP has changed. If you use AFS ACLs, IMSPd, and IMAPd on the same machine, make sure you have version 1.5a5 of the IMSP server for this version of the IMAP server. (If you don't have IMSP, or AFS, don't worry about it.)

last modified: $Date: 2010/01/06 17:01:29 $ cyrus-imapd-2.5.10/doc/install-netnews.html0000644000175000017500000002251013001236020015522 00000000000000 Cyrus and Netnews

Cyrus and Netnews

Note that the NNTP support in Cyrus is still relatively young in the grand scheme of things, and has not been tested under a heavy Usenet load. That being said, the code appears to be stable and is currently running in production serving 50-60 newsgroups with a volume of about 6000 messages per day.

Introduction

Cyrus has the ability to export Usenet via IMAP and/or export shared IMAP mailboxes via NNTP. This is made possible by a new NNTP daemon which is included with Cyrus.

This document assumes that you have successfully been able to setup your Cyrus IMAP server. If you have not already done so, please refer to the rest of the documentation. This document also assumes that you are familiar with Usenet and shared IMAP mailboxes.

There is a diagram that shows the interactions of the various components of the NNTP support in Cyrus which may be helpful in understanding the "big picture".

Installation

You will need to build Cyrus IMAPd with the --enable-nntp configure option. This builds nntpd and the associated utilities.

Requirements

Obviously you must have a newsfeed or news reader access from your ISP or Usenet provider.

Configuration

The first thing that must be done is to decide where your newsgroup mailboxes will reside, either at the toplevel of your hierarchy (eg, comp.mail.imap) or rooted elsewhere (eg, netnews.comp.mail.imap). If your newsgroup mailboxes are not at the toplevel of your hierarchy, then you must specify the parent with the newsprefix in imapd.conf. Using the example above, newsprefix would be set to netnews.

You must create a mailbox for each newsgroup that you would like to receive/export before the newsgroups can be used. If some groups are private, be sure to set the ACLs accordingly. The tools/mknewsgroups script can be used to help facilitate mass creation of newsgroup mailboxes. When using this script, be sure to add posting rights for 'anyone' (eg. mknewsgroups -a 'anyone +p' ...) so that articles can be fed/posted.

Receiving articles

In order to receive usenet articles, you must make sure that the Cyrus nntpd service is enabled in cyrus.conf. The master/conf/normal.conf and master/conf/prefork.conf sample configs both include entries for nntpd (disabled by default).

Push (traditional) feeds

If your usenet peer will be pushing articles to you, no further configuration is necessary, beyond letting your peer access your Cyrus server on port 119 (nntp).

Pull (suck) feeds

If you prefer to pull articles from your peer (and your provider allows it), then you can use the fetchnews utility which will retrieve articles from your peer and feed them to your Cyrus server. If supported by your peer, fetchnews will use the NEWNEWS command, otherwise it will fallback to keeping track of the high water mark of each group. You will probably want to configure fetchnews as an EVENT in cyrus.conf to be called periodically (eg, once an hour, every 15 minutes, etc).

As an alternative to fetchnews, you can also use the suck program to pull articles from your peer.

imapfeed

Alternatively, if you already have an INN v2.3 server in-house you can use the included imapfeed utility (written by the authors of Cyrus) to feed articles to your Cyrus server via LMTP. Consult the INN documentation for further details.

Control Messages

Control messages are accepted, parsed and delivered to the corresponding control.* pseudo-group (eg, control.newgroup, control.cancel, etc) if it exists, so that they may be reviewed by an administrator.

Automatic execution of control messages is only performed if the newsmaster (default = "news") user has the proper access control for the given mailbox. For example, to allow cancel control messages to be performed for "misc.test" articles, give the "news" user the 'd' right on "misc.test". To allow newgroup, rmgroup and mvgroup control messages to be performed on the "misc" hierarchy, give the "news" user the 'c' right on "misc".

NOTE: No sender or PGP verification of control messages is currently implemented.

Reading/Posting articles

In order to have articles posted by your local users propagate to the outside world, you must specify the name of your usenet peer(s) with the newspeer option in imapd.conf. This is the host(s) that nntpd contacts to feed outgoing articles. Depending on the configuration of the newspeer option, articles will be fed to the upstream server(s) using either the POST or IHAVE command. Also note that you may specify an optional wildmat to filter which groups will be fed (see imapd.conf(5) for details).

Newsgroups can also be gatewayed to email by setting /vendor/cmu/cyrus-imapd/news2mail mailbox annotations to the corresponding email addresses.

News clients

If anonymous logins are disabled (default) in imapd.conf, then your news clients will have to be configured to login with a username and password, otherwise they will not be allowed to post. Furthermore, if plaintext logins are disabled in imapd.conf, then you might have to configure your news clients to use SSL/TLS and enable the nntps service in cyrus.conf.

If you want to allow your news clients to use the NNTP NEWNEWS command, you will have to enable the allownewnews option in imapd.conf.

Email clients

If you are exporting Usenet via IMAP, and your users' messaging clients are not savvy enough to reply to and post articles via NNTP, then you will have to configure your server so your users can reply to and post articles via SMTP.

To help faciliate this, you can set the newspostuser option to a "pseudo" user which will be used to construct email delivery addresses for each incoming article. These addresses are inserted into a Reply-To: in the article. For example, if set to "post", an article posted to comp.mail.imap will have an address of "post+comp.mail.imap" inserted into the Reply-To: header. This will allow a user to easily reply to an article via email. Otherwise, the users will have to learn the correct email address format for posting and replying to articles.

In order for these email messages to be fed into your news server (and subsequently to the outside world) you need to use an email to news gateway, such as lmtp2nntp. You need to configure your MTA (Sendmail, Postfix, etc) so that lmtp2nntp is used as the local mailer whenever it receives a news article. A simple rule for doing this in Sendmail is shown below:

# mail addressed to post+ goes to lmtp2nntp@localhost
LOCAL_RULE_0
Rpost + $+ < @ $=w . >		$#lmtp2nntp $@ localhost $: $1

For other configurations, consult the lmtp2nntp and documentation and your MTA documentation.

NOTE: If anonymous logins are disabled (default) in imapd.conf, then you should configure lmtp2nntp to use its "feed" operation mode.

Expiring articles

Expiration of articles is done by the cyr_expire utility. Control over when articles are expunged is accomplished with the /vendor/cmu/cyrus-imapd/expire mailbox annotation. This annotation sets the number of days that messages should be kept in the mailbox before they expire. All entries in the duplicate deliver database that correspond to these messages are also kept for the same number of days before they are purged (overriding the cyr_expire -E option).

Setting the expire time to 0 (zero) for a mailbox will ensure that neither the messages nor the corresponding database entries will ever be expired. This can be useful for shared mailboxes (e.g. mailing list archives) which are being exported via NNTP. Note that this will cause the duplicate delivery database to consistently grow in proportion to the number of messages in such mailboxes.

If a mailbox does not have an expire time set on it, then the messages will never be expunged, but the corresponding database entries WILL be expired after the default number of days (cyr_expire -E option).

Note that the /vendor/cmu/cyrus-imapd/expire mailbox annotation is inherited by child mailboxes, so that you may control expiration on an entire mailbox/newsgroup hierarchy simply by setting the annotation on the root of the hierarchy. For example, if you set the annotation on comp, then ALL of the newsgroups in the comp hierarchy will be expired at the same time. Similarly, if you set the annotation on alt.binaries, all of the binary newsgroups under alt will be expired at the same time (independently from comp).


last modified: $Date: 2006/11/30 17:11:16 $ cyrus-imapd-2.5.10/doc/install-compile.html0000644000175000017500000002512213001236020015471 00000000000000 Compiling the IMAP Server

Compiling the IMAP Server

Once you have unpacked the files by extracting the tar archive, "cd" to the "cyrus-imapd-NNNN" directory where NNNN is the version number. The configuration files and various subdirectories are stored there. In the directory that the configure file is in, type "./configure" to configure the software. Please continue to read this document as there are switches to ./configure that may apply to you.

configure Overview

The "configure" shell script attempts to guess correct values for various system-dependent variables used during compilation. It uses those values to create a "Makefile" in each directory of the package. Finally, it creates a shell script "config.status" that you can run in the future to recreate the current configuration, a file "config.cache" that saves the results of its tests to speed up reconfiguring, and a file "config.log" containing compiler output (useful mainly for debugging "configure").

Running "configure" takes awhile. While running, it prints some messages telling which features it is checking for.

You can compile the package in a different directory from the one containing the source code. Doing so allows you to compile it on more than one kind of computer at the same time. To do this, you must use a version of "make" that supports the "VPATH" variable, such as GNU "make". "cd" to the directory where you want the object files and executables to go and run the "configure" script. "configure" automatically checks for the source code in the directory that "configure" is in and in "..".

By default, "make install" will install files (other than server-specific programs) in "/usr/local/bin", "/usr/local/man", etc. You can specify an installation prefix other than "/usr/local" by giving "configure" the option "--prefix=PATH".

You can specify separate installation prefixes for architecture-specific files and architecture-independent files. If you give "configure" the option "--exec-prefix=PATH", the package will use PATH as the prefix for installing programs and libraries. Documentation and other data files will still use the regular prefix.

By default, "make install" will install the server-specific programs in "/usr/cyrus/bin". You can specify a server-specific installation prefix other than "/usr/cyrus" by giving "configure" the option "--with-cyrus-prefix=PATH".

Options to configure

Here are a list of switches that can be used with "configure".

--help
Print a summary of the options to "configure", and exit.

--with-auth=METHOD
Specifies the authorization (group membership) module to use. Currently implemented authorization modules are:
unix
Unix /etc/passwd and /etc/group file
krb
Kerberos principals (requires Kerberos libraries). Optionally, specify where to find Kerberos v4 with "--with-krb=DIR" IMPORTANT: The Kerberos v4 support requires the DES library. Some vendor distributions of Kerberos, including the one with Solaris, do not have this support and cannot be used.
krb_pts
Kerberos principals with AFS PTserver groups (requires Kerberos and AFS libraries). Optionally, specify where the AFS libraries are found with "--with-afs=PATH". Also requires krb support as above.
Any method of authenticating with SASL can be used with any authorization module.

--with-krb=PATH
Specifies where to find the Kerberos library.

--with-com_err=PATH
Specifies where to find the com_err environment.

--with-cyrus-group=USER
Specifies the group used for installing setguid programs. By default, configure uses "mail".

--with-cyrus-prefix=PATH
Change the location of the server software. By default, the cyrus-prefix is /usr/cyrus.

--with-cyrus-user=USER
Specifies the userid that the Cyrus IMAP server will run as. By default, configure uses "cyrus".

--with-dbdir=PATH
Specifies where to find the Berkeley DB library.

--with-duplicate-db=DB
Specifies which database backend to use for the duplicate delivery database. By default, configure uses "berkeley_nosync".

--with-mboxlist-db=DB
Specifies which database backend to use for the mailbox list. By default, configure uses "berkeley".

--with-seen-db=DB
Specifies which database backend to use for the seen state. By default, configure uses "flat".

--with-subs-db=DB
Specifies which database backend to use for the subscriptions list. By default, configure uses "flat".

--with-tls-db=DB
Specifies which database backend to use for the TLS cache. By default, configure uses "berkeley_nosync".

--with-idle=METHOD
Specifies the IMAP IDLE method to use. Currently implemented IDLE methods are:
idled
Use the IDLE daemon. The IDLE daemon listens on a UNIX socket for messages from lmtpd/imapd/pop3d that a mailbox has been updated. The daemon then signals those (if any) imapd that are idling on the mailbox to check for the changes.
poll
Periodically poll the mailbox for changes.
no
Disable IMAP IDLE.
By default, configure uses "poll".

--with-lock=METHOD
Specifies the locking method to use. Currently implemented locking methods are:
flock
flock() locking
fcntl
fcntl() locking
By default, configure uses "fcntl" if the "fcntl()" function exists, "flock" otherwise.

--with-openssl=PATH
Specifies where to find the OpenSSL library.

--with-egd-socket=FILE
Specifies which socket to use to connect to the Entropy Gathering Daemon.

--with-perl=PATH
Specifies where to find the Perl binary (full path, including name of binary).

--with-sasl=PATH
Specifies the path to the directories containing the library (.../lib) and include (.../include) files for libsasl.

--with-statedir=PATH
Specifies the directory used for communicating with various daemons. By default, configure uses "/var".

--with-libwrap=PATH
Specifies where to find the TCP wrappers library.

--with-ucdsnmp=PATH
Specifies where to find the SNMP library.

--with-zephyr=PATH
Specifies where to find the Zephyr library (for notifyd).

--enable-listext
Enables support for LISTEXT extension.

--enable-murder
Enables support for IMAP Murder.

--enable-netscapehack
Enables support for X-NETSCAPE extension (administration URLs).

--disable-sieve
By default, Sieve support is enabled. Use --disable-sieve to disable compiling the Sieve library and to disable all Sieve support.

--disable-cyradm
Do not compile the cyradm administrative client.

--disable-server
Do not compile the IMAP server programs.

Run configure --help for further configuration options.

Some systems require unusual options for compilation or linking that the "configure" script does not know about. You can give "configure" initial values for variables by setting them in the environment. Using a Bourne-compatible shell, you can do that on the command line like this:

   CC=c89 CFLAGS=-O2 LIBS=-lposix ./configure
Or on systems that have the "env" program, you can do it like this:
   env CPPFLAGS=-I/usr/local/include LDFLAGS=-s ./configure
The "make" variables that you might want to override with environment variables when running "configure" are:
CC
C compiler program.
Default is "cc", or "gcc" if "gcc" is in your PATH.
(For "CC", any value given in the environment overrides the value that "configure" would choose.)
CFLAGS
Debugging and optimization options for the C compiler.
CPPFLAGS
Header file search directory ("-IDIR") and any other miscellaneous options for the C preprocessor and compiler. If it is not set in the environment when "configure" runs, the default value is empty.
LDFLAGS
Stripping ("-s") and any other miscellaneous options for the linker. If it is not set in the environment when "configure" runs, the default value is empty.
DEFS
Configuration options, in the form "-Dfoo -Dbar ..."
LIBS
Libraries to link with, in the form "-lfoo -lbar ..."
(For "DEFS" and "LIBS", any value given in the environment is added to the value that "configure" chooses.)
If you need to do unusual things to compile the package, we encourage you to figure out how "configure" could check whether to do them. After doing so, please send us a patch! Instructions for doing so can be found on the feedback page.

The file "configure.ac" is used as a template to create "configure" by a program called "autoconf". You will only need it if you want to regenerate "configure" using a newer version of "autoconf".

Once you have successfully run "configure", execute the following commands:


   make all CFLAGS=-O
If you want, you can override the "make" variables CFLAGS and LDFLAGS by entering the following:
   make all CFLAGS=-O2 LDFLAGS=-s


last modified: $Date: 2006/11/30 17:11:16 $ cyrus-imapd-2.5.10/doc/README.autosievefolder0000644000175000017500000000403213001236020015563 00000000000000Original documentation for the merged autosieve patch below. It would be great to tidy this up. Cyrus IMAP autosievefolder patch ---------------------------------- NOTE : This patch has been created at the University of Athens. For more info, as well as more patches on Cyrus IMAPD server, please visit http://email.uoa.gr NOTE : Patch updated to Cyrus IMAPD 2.4.x by Martin Matuska When the lmtpd daemon receives an email message prior to delivering it to the INBOX folder of the user, checks if the user has specified sieve filters. If the user has specified sieve filters the filters are evaluated. If the message matches any of the filters the action that is specified in the filter is executed. If the action is FileInto it is stored in the subfolder specified in the filter. If the subfolder doesn't exist then the message is sent to the INBOX folder of the user. With this patch if the folder doesn't exist AND the name of the subfolder is specified in the autosievefolders option, OR the anysievefolder is set to yes in the cyrus-imap configuration file then the subfolder is created and the mail is stored there. Check the following options of the imapd.conf file ================================================== * anysievefolder : It must be "yes" in order to permit the autocreation of any INBOX subfolder requested by a sieve filter, through the "fileinto" action. (default = no) * autosievefolders : It is a "|" separated list of subfolders of INBOX that will be automatically created, if requested by a sieve filter, through the "fileinto" action. (default = null) i.e. autosievefolders: Junk | Spam WARNING: anysievefolder, takes precedence over autosievefolders . Which means that if anysievefolder is set to "yes", cyrus will create any INBOX subfolder requested, no-matter what the value of autosievefolders is. Things to be done ================= 1. Support cyrus wildcards in the autosievefolders option. For more information and updates please visit http://email.uoa.gr/projects/cyrus/autosievefolder cyrus-imapd-2.5.10/doc/install-testing.html0000644000175000017500000001143713001236020015522 00000000000000 Testing the IMAP Server

Testing the IMAP Server

To test the IMAP server, reboot and perform the following steps (all of these samples use "foobar" as the IMAP server name). A list of answers to common installation problems is maintained in http://www.cyrusimap.org/mediawiki/index.php/FAQ#Cyrus_IMAP_Questions.
  1. From your normal account, telnet to the IMAP port on the server you're setting up:
       telnet foobar imap
    
    If your server is running, you'll get the following message:
       Trying 128.2.232.95...
       Connected to foobar.andrew.cmu.edu.
       Escape character is '^]'.
       * OK foobar.andrew.cmu.edu Cyrus IMAP4 v2.0.0 server ready
    

    Any message other than one starting with "* OK" means there is a problem. To terminate the connection, type ". logout".

    Naturally the version number should match the version you just installed.

  2. Use "imtest" to test logging in with plaintext passwords:
       /usr/local/bin/imtest -m login foobar
    

    If you want to specify a different user, do:

       /usr/local/bin/imtest -m login -a USER foobar
    
    If your server is running, you'll get the following message:
       % /usr/local/bin/imtest -m login foobar
       S: * OK mail1.andrew.cmu.edu Cyrus IMAP4 v2.0.0 server ready
       C: C01 CAPABILITY
       S: * CAPABILITY IMAP4 IMAP4rev1 ACL QUOTA LITERAL+ NAMESPACE UIDPLUS
       X-NON-HIERARCHICAL-RENAME NO_ATOMIC_RENAME AUTH=GSSAPI AUTH=ANONYMOUS
       AUTH=KERBEROS_V4 UNSELECT
       S: C01 OK Completed
       Password:
       + go ahead
       L01 OK User logged in
       Authenticated.
       Security strength factor: 0
    

    Any message other than one starting with a "L01 OK" means there is a problem. If the test fails, a more specific error message should be written through syslog to the server log. To terminate the connection, type ". logout".

  3. You should now test the server with each of the various authentication mechanisms you have installed. The supported mechanisms are listed in the CAPABILITY line:
      * CAPABILITY IMAP4 IMAP4rev1 ACL QUOTA LITERAL+ NAMESPACE UIDPLUS
      X-NON-HIERARCHICAL-RENAME NO_ATOMIC_RENAME AUTH=ANONYMOUS
      AUTH=KERBEROS_V4 AUTH=DIGEST-MD5 AUTH=CRAM-MD5 UNSELECT
      . OK Completed
    
    Each of the mechanism names is preceded by a 'AUTH='. For this example the ANONYMOUS, KERBEROS_V4, DIGEST-MD5, and CRAM-MD5 mechanisms are available. If a mechanism does not appear that you wish to use, examine the libsasl log messages. Generally, if a mechanism does not appear, it means it failed to initialize. (For example, if the server is unable to access the srvtab file the KERBEROS_V4 mechanism will refuse to load.)

    Plaintext login is a special case: the PLAIN SASL mechanism is only advertised under an encrypted connection. However, plaintext logins are available (as long as you haven't disabled plaintext) by using -m login(as above).

    To terminate the imtest connection, type ". logout".

    Once you are satisfied with the authentication mechanism list you should attempt to log in with each of those mechanisms. Run imtest specifying which mechanism you would like to use.

       /usr/local/bin/imtest -m KERBEROS_V4 foobar
       C: C01 CAPABILITY
       S: * OK foobar.andrew.cmu.edu Cyrus IMAP4 v2.0.0 server ready
       S: * CAPABILITY IMAP4 IMAP4rev1 ACL QUOTA LITERAL+ NAMESPACE
       UIDPLUS X-NON-HIERARCHICAL-RENAME NO_ATOMIC_RENAME AUTH=ANONYMOUS
       AUTH=GSSAPI AUTH=KERBEROS_V4 UNSELECT
       S: C01 OK Completed
       C: A01 AUTHENTICATE KERBEROS_V4
       S: + wYcDAA==
       C: BAYBQU5EUkVXLkNNVS5FRFUAOCAm7F/Y+HabCzJ
          /UMtVcvWRjTohuq/USaCV6gYdkAU5DOcADAq
       S: + 0aAsUGQZhgQ=
       C: ADMe/cVivAYYzy1yd4Vojg==
       S: A01 OK Success (privacy protection)
       Authenticated.
       Security strength factor: 56
    

    Any message other than one starting with a "A01 OK" means there is a problem. If the test fails, a more specific error message is written through syslog to the server log. To terminate the connection, type ". logout".

    See the libsasl documentation for a full description of all the mechanisms. It is also possible to support "security layers" (privacy or integrity protected connections). By default, imtest uses the strongest layer available with the selected mechanism; use "-l" to choose an alternate layer.


last modified: $Date: 2010/01/06 17:01:29 $ cyrus-imapd-2.5.10/doc/install-admin-mb.html0000644000175000017500000000637713001236020015540 00000000000000 Administering Mailboxes

Administering Mailboxes

The "cyradm" command (see the cyradm(1) man page for complete documentation) manages the creation of, deletion of, ACLs on, and quotas on mailboxes. To get an overview of the command, type "cyradm <host>". Once "cyradm" has started, the user prompt is replaced with the name of the host followed by a ">". Type "help" at the new prompt. The following information is displayed:
   createmailbox, cm        create a mailbox
   deleteaclmailbox, dam    delete an ACL on a mailbox
   deletemailbox, dm        delete a mailbox
   help                     get help on commands
   listaclmailbox, lam      list the ACL on a mailbox
   listmailbox, lm          list mailboxes
   listquota, lq            list quota on root
   listquotaroot, lqr, lqm  list quota roots on mailbox
   quit                     exit program
   renamemailbox, renm      rename a mailbox
   setaclmailbox, sam       set an ACL on a mailbox
   setquota, sq             set quota limits
Note:It's not necessary to run "cyradm" on the same system as the IMAP server.

Note:If you run "cyradm" on a system not using Kerberos for authentication, you will be prompted for your user name and password before you can issue any "cyradm" commands. By default, you will be prompted for the password of the user ID of the current shell. If you want to authenticate as a different user, use the "-a" option. If the user that you authenticate as is a Cyrus admin, you can proxy as a particular user by also using the "-u" option.

The mailbox naming convention requires that the primary mailbox (INBOX) for anyone must be named "user.<userid>". To create a mailbox, type:

   createmailbox user.<userid>
For example, to create a mailbox for the userid "smith", type:
   createmailbox user.smith
To limit "smith" to 10,000 kilobytes of mail, type:
   setquota user.smith 10000
Once the INBOX is created, users can create their own additional mailboxes from a mail program. If Smith created a work mailbox and a play mailbox, the full names of the mailboxes would be:
   user.smith.work
   user.smith.play

Access rights are discussed in detail in the cyradm(1) man pages. Note that the administrator must grant herself create/delete access explicitly before she can delete a mailbox:

   setaclmailbox <mail_box> <admin_userid> c
   deletemailbox <mail_box>
Once you have created mailboxes, your IMAP server installation is done. You must then configure a mail interface, such as Pine or Mulberry, to work with the IMAP server.


last modified: $Date: 2010/01/06 17:01:29 $ cyrus-imapd-2.5.10/doc/install-snmpmon.html0000644000175000017500000000154513001236020015533 00000000000000 SNMP Monitoring

SNMP Monitoring

TODO:finish this section. The majority of this section will get moved to the external CySNIIP docs and this will be stuff specific to the imapd.

Cyrus uses an auxillary process called "tugowar", so named because there's a push-pull model. Various components of the Cyrus mail system push data to tugowar, and tugowar listens for SNMP queries (remote clients pull the data from tugowar).

Configuring tugowar

Testing the tugowar daemon

SNMP data exported


last modified: $Date: 2000/04/25 02:56:42 $ cyrus-imapd-2.5.10/doc/notes.html0000644000175000017500000000125513001236020013526 00000000000000 Notes
  • appending: it's important that the index records for individual messages make it to disk before the index header indicating that they're there. so something like:
    1. sync messages to disk (or depend on link() being atomic)
    2. create new index records, flush to disk
    3. create new header if necessary (adding new user flag), flush to disk
    4. flush cache file
    5. update index header, flush to disk
cyrus-imapd-2.5.10/doc/install-configure.html0000644000175000017500000004732113001236020016027 00000000000000 Installing and configuring the IMAP Server

Installing and configuring the IMAP Server

This section describes the shell scripts to run and the configuration files to modify once "configure" and "make" have run.
  1. Create a user and group for the Cyrus subsystem. The examples in this document assume a user of "cyrus" and a group of "mail", though any user and group name can be used. If a user other than "cyrus" is to be used, it must have been previously specified in the "--with-cyrus-user=" option to "configure". If a group other than "mail" is to be used, it must have been previously specified in the "--with-cyrus-group=" option to "configure".

  2. After you've logged in as "root", install the cyrus software.
       make install
    
    Be sure that the server programs ended up in the directory specified by "--with-cyrus-prefix" (by default, "/usr/cyrus/bin").

  3. The Cyrus IMAP server uses the 4.3BSD syslog that separates messages into both levels and categories. Invoke "man syslog" to see if "openlog()" takes three arguments. If it does not, replace the system "syslogd" and "syslog.conf" with the files provided in the "syslog" directory.
       mv syslogd /etc/syslogd
       mv syslog.conf /etc/syslog.conf
    
    If you do not copy the "syslog/syslog.conf" file to the "/etc" directory, be sure to add support for "local6.debug". The file should include a line like:
       local6.debug  /var/log/imapd.log
    
    You probably also want to log SASL messages with a line like:
       auth.debug /var/log/auth.log
    
    After installation and testing, you probably want to change the ".debug" component to something a little less verbose. Create the log files:
       touch /var/log/imapd.log /var/log/auth.log
    
  4. Create the file "/etc/imapd.conf". Here is a sample "imapd.conf" with a minimal number of values defined:
       configdirectory: /var/imap
       partition-default: /var/spool/imap
       admins: curtj abell
       sasl_pwcheck_method: saslauthd
    
    For a description of all the fields in this file, see the imapd.conf(5) man page. (Note that this file also exports values to libsasl, the most important of them the pwcheck_method. In this example, users are authenticated via the saslauthd daemon, which can be run in a number of different ways.)

    READ THE imapd.conf(5) MAN PAGE. There are options in there that you will want to know about and default behavior that you may not like.

    Note that everyday users should not be administrators. Admins have powers not granted to regular users and while the server allows them to receive mail, some problems will occur if admins are used as regular users. You also should not read mail as an administrator. You should have separate accounts for reading mail and administrating. This is especially true if using the altnamespace option, because admins are always presented with the standard (internal) namespace.

  5. Create the configuration directory specified by the "configdirectory" option in "imapd.conf." The configuration directory is similar in concept to the "/usr/lib/news" directory. It stores information about the IMAP server as a whole.

    This document uses the configuration directory "/var/imap" in its examples. This directory should be owned by the cyrus user and group and should not permit access to other users.

       cd /var
       mkdir imap
       chown cyrus imap
       chgrp mail imap
       chmod 750 imap
    
  6. Create the default partition directories specified in the "/etc/imapd.conf" file.

    This document uses a default partition directory of "/var/spool/imap" in the following example:

       cd /var/spool
       mkdir imap
       chown cyrus imap
       chgrp mail imap
       chmod 750 imap
    
    The partition directory is similar in concept to /var/spool/news. It is where the mailboxes are stored. Unlike most netnews systems, Cyrus allows you to have more than one partition.
  7. If you wish to use Sieve, and you didn't configure deliver to look in home directories (see the imapd.conf man page), create the Sieve directory:
       cd /usr
       mkdir sieve
       chown cyrus sieve
       chgrp mail sieve
       chmod 750 sieve
    
  8. Change to the Cyrus user and use the tool "tools/mkimap" to create the rest of the directories (subdirectories of the directories you just created).
       su cyrus
       tools/mkimap
       exit
    
    
    If Perl is not available, it should be easy (but time consuming) to create these directories by hand.

  9. LINUX SYSTEMS USING EXT2FS ONLY: Set the user, quota, and partition directories to update synchronously. Failure to do this may lead to data corruption and/or loss of mail after a system crash. Unfortunately, doing so may result in a serious performance hit. If you are using a newer filesystem than ext2fs on Linux, this step should not be necessary. (Running ext3 in any mode is safe.)
       cd /var/imap
       chattr +S user quota user/* quota/*
       chattr +S /var/spool/imap /var/spool/imap/*
    
    Also set the queue directory of the mail daemon to update synchronously. The following example is for sendmail:
       chattr +S /var/spool/mqueue
    

  10. To enable STARTTLS support, see how to configure OpenSSL below.

  11. Add the following lines to the "/etc/services" file if they aren't already there.
       pop3      110/tcp
       nntp      119/tcp
       imap      143/tcp
       imsp      406/tcp
       nntps     563/tcp
       acap      674/tcp
       imaps     993/tcp
       pop3s     995/tcp
       kpop      1109/tcp
       lmtp      2003/tcp
       sieve     4190/tcp
       fud       4201/udp
    

  12. Remove "/etc/[x]inetd.conf" entries. Any imap, imaps, pop3, pop3s, kpop, lmtp and sieve lines need to be removed from /etc/[x]inetd.conf and [x]inetd needs to be restarted.

Configuring the Master Process

  1. Choose a configuration from the master/conf directory:
    small.conf
    bare-bones server supporting IMAP and POP
    normal.conf
    server supporting IMAP, POP, the SSL wrapped versions, and the Sieve script management protocol
    prefork.conf
    The same configuration as above, but with some preforked processes for faster processing.
    backend-cmu.conf
    Our configuration (for Murder Backend / typical IMAP servers)
    frontend-cmu.conf
    Our configuration (for Murder Frontend servers)

    To use normal.conf, do:

       cp master/conf/normal.conf /etc/cyrus.conf
    

    Optionally, you can edit /etc/cyrus.conf to disable or enable certain services, or to tune the number of preforked copies. Be sure not to remove the entries that are labeled required.

  2. Arrange to start "/usr/cyrus/bin/master" as root when the system starts. It will bind some ports and then give up its root privileges. Until your system reboots, you can start the master process by hand:
       /usr/cyrus/bin/master &
    

  3. Monitor the progress of the master process by examining the imapd.log file. It should never exit by itself, but you can shut down the mail system by sending it a signal with kill.

  4. Clean Shutdown - you can shut the master process down cleanly by sending it a SIGQUIT rather than SIGTERM signal. This will cause the master process to send SIGQUIT to all its children and then wait for them to finish cleanly. This avoids issues like a message being appended by lmtpd but the sync_log record never being written.

    Since a clean shutdown may never finish if a child process is stuck for some reason the recommended approach is to send a SIGQUIT then loop on the master process sending a signal 0 every second until either the master process has gone away or a suitable time has expired (maybe 10 seconds). You can then send a SIGTERM if the process still exists.

    At FastMail the following snippet of perl is used (warning: Linux specific signal numbers - check your own system before using this):

        my $pid = `cat $PIDFILE`;
        chomp($pid);
        print "Trying nice shutdown - killing $pid with SIGQUIT\n";
        kill 3, $pid;
        foreach my $num (1..10) {
          if (kill 0, $pid) {
            print "Not dead yet after $num seconds\n";
            sleep 1;
          }
          else {
            last;
          }
        }
        if (kill 0, $pid) {
          print "No more Mr. Nice Guy - killing $pid with SIGTERM\n";
          kill 15, $pid;
        }
    

Configuring the Mail Transfer Agent

In order to deliver mail to the Cyrus system, you'll have to configure your MTA (Sendmail, Postfix, Exim, etc.) to use LMTP.

Configuring Sendmail

Generate a sendmail configuration file which delivers local mail to the IMAP server. See the file cf/README in the Sendmail distribution for information on how to create a complete configuration file. This file also lists variables that can be used to customize the mailer definitions mentioned below.

The following configurations assume that you are using the lmtpunix service from one of the sample cyrus.conf files discussed above.

  • For Sendmail 8.12.4 and higher, use the cyrusv2 mailer definition in the Sendmail distribution:
    define(`confLOCAL_MAILER', `cyrusv2')
    MAILER(`cyrusv2')
    
    If you wish to change the name of the UNIX socket or switch to TCP, define CYRUSV2_MAILER_ARGS appropriately as described in cf/README.
  • For Sendmail 8.10 - 8.12.3, use the cyrusv2.mc file as a template to create a Sendmail configuration file.
  • For Sendmail 8.9.x and earlier, use the cyrus mailer definition in the Sendmail distribution:
    define(`confLOCAL_MAILER', `cyrus')
    MAILER(`cyrus')
    
    Edit /etc/group and add user "daemon" to the "mail" group. This will permit sendmail to run the "deliver" (LMTP client) program to deliver mail to the IMAP server.

Cyrus also includes a socket map daemon smmapd which can be used by Sendmail 8.13 and higher (a patch for 8.12 is available) to verify at RCPT TO time that a message can be delivered to the particular mailbox. To use this daemon, add smmapd as a service in cyrus.conf and configure Sendmail accordingly.

Configuring Postfix

The Postfix source distribution comes with the file "README_FILES/LMTP_README". Even if you are using a binary distribution of Postfix, it would be well worth your while to download the full Postfix source. Not only will you get the above file, but numerous other "readme" files and sample configuration files.

One thing you need to watch out for is the UID and GID of the Postfix software. As it states in the Postfix "INSTALL" document, you must create a new account that does not share its UID and GID with any other user account. This is for security reasons. If you installed Postfix with a GID of "mail", you will need to select a different GID for Cyrus. See the Cyrus configure options "--with-cyrus-user" and "--with-cyrus-group". (This was more crucial when the use of Cyrus' "deliver" was more prevalent, but it is still a good idea to follow this policy.)

Another thing to note is the location of your "sendmail" command. On some platforms this will be "/usr/sbin/sendmail", on others, "/usr/lib/sendmail". Cyrus will need to know where this command is. See Installing Sieve for more details.

Assuming that you are using the lmtpunix service from one of the sample cyrus.conf files discussed above, the Postfix configuration file "/etc/postfix/main.cf" should have the following line:

  mailbox_transport = lmtp:unix:/var/imap/socket/lmtp

Naturally, both the Postfix UID and the Cyrus UID need to be able to access the specified socket file.

Starting with Postfix snapshot-20010222, you can improve the efficiency of LMTP delivery via the "mailbox_transport" by putting the following entries in "/etc/postfix/main.cf":

  local_destination_recipient_limit = 300
  local_destination_concurrency_limit = 5

Of course you should adjust these settings as appropriate for the capacity of the hardware you are using. The recipient limit setting can be used to take advantage of the single instance message store capability of Cyrus. The concurrency limit can be used to control how many simultaneous LMTP sessions will be permitted to the Cyrus message store.

Additional examples are included in the Postfix file "README_FILES/LMTP_README".

Configuring Exim 4

Generate an Exim configuration file which delivers local mail to the IMAP server. See the Exim documentation for information on how to create a complete configuration file.

Cyrus is designed to be used as a black-box server -- there are usually no local user accounts. As a result, you must define the following "router":

localuser:
  driver = accept
  transport = local_delivery

The following "transports" assume that you are using either the lmtpunix or lmtp service from one of the sample cyrus.conf files discussed above.

  • Using lmtpunix (UNIX socket):
    local_delivery:
      driver = lmtp
      command = "/usr/cyrus/bin/deliver -l"
      batch_max = 20
      user = cyrus
    
  • Using lmtp (TCP socket -- Exim and Cyrus on same host):
    local_delivery:
      driver = smtp
      protocol = lmtp
      hosts = localhost
      allow_localhost
    

For more advanced configurations (such as address verification, etc), consult the Exim documentation and sample configurations.

Exporting Netnews via IMAP

If you wish to use export Netnews via IMAP, consult install-netnews.html.

SSL, TLS, and OpenSSL

Transport Layer Security (TLS), is a standardized version of the Secure Sockets Layer (SSL v3) standard. IMAP can make use of two different versions of TLS/SSL: STARTTLS and an SSL wrapped session.

In STARTTLS, a client connects to the IMAP port as normal and then issues the STARTTLS command, which begins a TLS negotiation. This is currently supported by the Cyrus IMAP server when it is compiled with OpenSSL.

The alternative, a SSL wrapped connection, involves the client connected to a seperate port ("imaps") and negotiating a SSL session before starting the IMAP protocol. Again, this is supported natively by the Cyrus IMAP server when it is compiled with OpenSSL.

Both TLS and SSL require a server key and a certificate. Optionally, in addition to establishing a secure connection, TLS can authenticate the client.

Configuring Cyrus with OpenSSL

  1. OpenSSL requires the certificate and key in PEM format. You can create the server's private key and certificate yourself using OpenSSL. Here, we create a self-signed key for the machine "foobar.andrew.cmu.edu" and put both the certificate and key in the file "/var/imap/server.pem".

    Please do not blindly enter in the information to OpenSSL below. Instead, enter the appropriate information for your organization (i.e., NOT Carnegie Mellon University for the Organization Name, etc.).

    openssl req -new -x509 -nodes -out /var/imap/server.pem -keyout /var/imap/server.pem -days 365
    Using configuration from /usr/local/lib/openssl/openssl.cnf
    Generating a 1024 bit RSA private key
    .............+++++
    ......................+++++
    writing new private key to '/var/imap/server.pem'
    -----
    You are about to be asked to enter information that will be incorporated
    into your certificate request.
    What you are about to enter is what is called a Distinguished Name or a DN.
    There are quite a few fields but you can leave some blank
    For some fields there will be a default value,
    If you enter '.', the field will be left blank.
    -----
    Country Name (2 letter code) [AU]:US
    State or Province Name (full name) [Some-State]:Pennsylvania
    Locality Name (eg, city) []:Pittsburgh
    Organization Name (eg, company) [Internet Widgits Pty Ltd]:Carnegie Mellon University
    Organizational Unit Name (eg, section) []:Andrew Systems Group
    Common Name (eg, YOUR name) []:foobar.andrew.cmu.edu
    Email Address []:
    
  2. Make sure to make key file(s) readable by the Cyrus user. For example: chown cyrus /var/imap/server.pem
  3. Add the following to /etc/imapd.conf to tell the server where to find the certificate and key files (used for ALL services):
    server_cert_file: /var/imap/server.cert
    server_key_file: /var/imap/server.key
    
    Optionally, you can use separate certificates and key files for each service:
    [servicename]_server_cert_file: /var/imap/imap-server.cert
    [servicename]_server_key_file: /var/imap/imap-server.key
    
    "servicename" here refers to the name of the service as specified in cyrus.conf. It is not necessarily the name of the binary.

    This is useful if you want to use different hostnames for each service (e.g., via virtual host interfaces or DNS CNAMEs). In the absence of any of the service specific options, the value of the global option is used. A value of disabled for the certificate or key file for a particular service will disable SSL/TLS for that service.

    If you have a Certificate Authority (CA), you may wish to generate a certificate request and send it to be signed by your CA.

    By default, Cyrus will cache SSL/TLS sessions for reuse for up to 24 hours. By adjusting the value of the tls_session_timeout option in imapd.conf, the session caching can be disabled (0) or the expiration period shortened.

  4. You can test STARTTLS by using imtest:
    imtest -t "" foobar.andrew.cmu.edu
    

Client-side certificates

Client certificates are somewhat harder to configure than server certificates. You'll need a CA (certificate authority) and need to generate client certificates signed by that CA. STARTTLS in Sendmail and other MTAs have similiar problems, so Claus Assman's page is a good reference.

You can use the self-signed certificate generated above as a CA for client certificates. To do this, try the following:

TODO: write me!

Unfortunately, there's no standard on how to convert the client's authenticate DN (distinguished name) to a SASL authentication name.

Alternate Namespace and UNIX Hierarchy Convention

If you wish to use the alternate namespace and/or the UNIX hierarchy convention, consult altnamespace.html.


last modified: $Date: 2010/01/06 17:01:29 $ cyrus-imapd-2.5.10/doc/README.autocreate0000644000175000017500000002223713001236020014526 00000000000000Original documentation for the merged autocomplete patch below. It would be great to tidy this up. Cyrus IMAP autocreate Inbox patch ---------------------------------- NOTE : This patch has been created at the University of Athens. For more info, as well as more patches on Cyrus IMAPD server, please visit http://email.uoa.gr/ NOTE : Patch updated for Cyrus IMAP 2.4.x by Martin Matuska The design of Cyrus IMAP server does not predict the automatic creation of users' INBOX folders. The creation of a user's INBOX is considered to be an external task, that has to be completed as part of the user email account creation procedure. Hence, to create a new email account the site administrator has to: a) Include the new account in the user database for the authentication procedure (e.g. sasldb, shadow, mysql, ldap). b) Create the corresponding INBOX folder. Alternatively, the user, if succesfully authenticated, may create his own INBOX folder, as long as the configuration of the site allows it (see "autocreatequota" in imapd.conf). Unlike what not careful readers may think, enabling the "autocreatequota" option, doesn't lead to the automatic INBOX folder creation by Cyrus IMAP server. In fact, "autocreate" means that the IMAP clients are allowed to automatically create the user INBOX. This patch adds the functionality of automatic creation of the users' INBOX folders into the Cyrus IMAP server. It is implemented as two features, namely the "create on login" and "create on post". Create on login =============== This feauture provides automatic creation of a user's INBOX folder when all of the following requirements are met: i) The user has succesfully passed the authentication procedure. ii) The user's authorisation ID (typically the same as the user's authentication ID) doesn't belong to the imap_admins or admins accounts (see imapd.conf). iii) The "autocreatequota" option in the imap configuration file has been set to a non zero value. iv) The corresponding to the user's authorisation ID INBOX folder does not exist. The user's first login is the most typical case when all four requirements are met. Note that if the authenticated ID is allowed to proxy to another account for which all of the above requirements are met, the corresponding INBOX folder for that account will be created. Create on post ============== This feauture provides automatic creation of a user's INBOX folder when all of the following requirements are met. i) An email message addressed to the user has been received. ii) The recipient is not any of the imap_admins or admins accounts. Note that passing emails to admins or imap_admins accounts from the MTA to LMTP should be avoided in any case. iii) The recipient's INBOX does not exist. iv) The "autocreatequota" option in the imap configuration file has been set to a non zero value. v) The "createonpost" option in the imap configuration file has been switched on. Besides the automatic creation of INBOX folder, additional functionalities are provided: (A) Automatic creation of INBOX subfolders controlled by "autocreateinboxfolders" configuration option. eg autocreateinboxfolders: sent|drafts|spam|templates (B) Automatic subscription of INBOX subfolders controlled by "autosubscribeinboxfolders" configuration option. eg autosubscribeinboxfolders: sent|spam Obviously, only subscription to subfolders included in the "autocreateinboxfolder" list is meaningful. (C) Automatic subscription to shared folders (bulletin boards). The user gets automatically subscribed to the shared folders declared in the "autosubscribesharedfolders" configuration option in imapd.conf. eg autosubscribesharedfolders: public_folder | public_folder.subfolder In order the above action to succeed, the shared folder has to pre-exist the INBOX creation and the user must have the appropriate permissions in order to be able to subscribe to the shared folder. * A new config option has been added. 'autosubscribe_all_sharedfolders' is a yes/no option. When set to yes, the user is automatically subscribed to all shared folders one has permission to subscribe to. Please, note that when this option is set to yes, then 'autosubscribesharedfolders' option is overriden. (D) Automatic creation of a predefined default sieve script. This is very useful when a default sieve script is used for every user. Usually, a default anti-spam script may me be written in a file and copied to each user sieve scripts upon the INBOX creation. The imapd.conf options that have been added are 'autocreate_sieve_script', 'autocreate_sieve_compiledscript' and 'generate_compiled_sieve_script'. autocreate_sieve_script configuration option refers to the full path of the file that contains the sieve script. The default value is null and if no file is defined, then no default script is created upon INBOX creation. (The feature is disabled) eg autocreate_sieve_script: /etc/default_sieve_script autocreate_sieve_compiledscript configuration option refers to the full path of the file that contains the bytecode compiled sieve script. If this filename is defined in imapd.conf and the file exists, then it is automatically copied in the user's sieve directory. If it is not defined, then a bytecode sieve script gets on the fly compiled by the daemon. eg autocreate_sieve_compiledscript: /etc/default_sieve_script.bc generate_compiled_sieve_script is a boolean option that triggers the compilation of the source sieve script to bytecode sieve script. The file that the bytecode script will be saved is pointed by autocreate_sieve_compiledscript. Ways of compiling a sieve script : 1. Compile a sieve script using the standard sievec utility, distributed by CMU 2. Compile a sieve script using the compile_sieve utility, released by UoA. This tool is almost identical to the sievec utility, with the difference that it reads the input and output file from autocreate_sieve_script and autocreate_sieve_compiledscript options in imapd.conf 3. Let cyrus create a compiled sieve script using a source script. Cyrus can be instructed to save the compiled script any time a compiled script does not exist. NOTES : 1. In order this functionality to work, the following requirements must have been met: - 'sieveusehomedir' option must be 'no' in the configuration (default). - 'sievedir' option must have a valid value. 2. Currently, this patch checks the validity of the source script while generating a bytecode compiled script, but not the validity of the bytecode sieve script file. The administrator should make sure that the provided files contain a valid sieve script as well as the compiled script is updated every time the source script changes. (E) The administrator may control for which users and/or groups may the INBOXes automatically be created. The autocreate_users option restricts the groups for which the patch will create the mailboxes. The default value of autocreate_users is anyone. So, if not set at all, the patch will work for all users. However, one may set: autocreate_users: user1 user2 group:group1 group:group2 In that case, the INBOX will be created only for user1, user2 and the users that belong to group1 and group2. More refined control per service is provided by the options imap_autocreate_users, pop3_autocreate_users and lmtp_autocreate_users. These options override the autocreate_users option and offer per service control. Example: One may want to restrict the create on post functionality only for a specific group of users. To achieve this, the following lines must be added in the imapd.conf file: createonpost: yes lmtp_autocreate_users: group:groupname Issues to be considered ======================= I) In order to use the create on post feauture one should be absolutely sure that: a) The MTA checks the validity of the email recipient before sending the email to LMTP. This is an RFC821 requirement. This usually expands to "the mta should be able to use the account database as user mailbox database". b) Only authorised accounts/services can talk to LMTP. II) Especially in the case of imap logins, the current patch implementation checks for the INBOX folder existence upon login, causing an extra mailbox lookup in most of the cases. A better approach would be to chase the "IMAP_MAILBOX_NONEXISTENT" error code and check if the error is associated with an INBOX folder. However, this would mess up Cyrus code. The way it was implemented may not have been the most performance optimised, but it produces a much cleaner and simple patch. Virtual Domains Support ======================= Virtual domains are supported by all versions of the patch for cyrus-imapd-2.2.1-BETA and later. However, it is not possible to declare different INBOX subfolders to be created or shared folders to be subscribed to for every domain. Things to be done ================= 1. Support MUPDATE It is within the developers' intentions to support the mupdate protocol, but serious design issues on future cyrus releases have to resolved first. 2. Select different attributes (quota, partition, sieve filter, etc) depending on the group a user belongs to. For more information and updates please visit http://email.uoa.gr/projects/cyrus/autocreate cyrus-imapd-2.5.10/doc/install-replication.html0000644000175000017500000001323113001236020016350 00000000000000 Cyrus replication

Cyrus replication

Note that Cyrus replication is still relatively young in the grand scheme of things, and if you choose to deploy you are doing so at your own risk. The core of the replication code has been used successfully in production at Cambridge University since the summer of 2003, but it has been rewritten extensively as part of the integration into the mainstream Cyrus codebase. The replication code as integrated into Cyrus 2.3 has been running in production at Fastmail.fm and Columbia.edu since early 2006 and will be put into production at CMU in winter 2007.

The Cyrus team owes a debt of gratitude to the kind folks at Cambridge, Columbia, and Fastmail for their considerable effort in helping to identify and correct the bugs the in Cyrus 2.3 replication code.

Introduction & Assumptions

The Cyrus replication engine is designed to replicate the mailstore on standalone Cyrus servers or "backend" servers in a Cyrus Murder to provide a high-availability environment. It is NOT intended to replicate "frontend" servers or the "mupdate master" in a Cyrus Murder. Note that load balancing is not possible with the current replication code, but it is intended to be supported in the future.

This document assumes that you have successfully been able to setup atleast one Cyrus IMAP server. This server will become your first "master" server. It also assumes that you are familliar with the administration and day to day operations of the Cyrus IMAP server and the SASL authentication library. If you feel uncomfortable with this, please refer to the rest of the documentation first.

Installation

You will need to build Cyrus IMAPd with the --enable-replication configure option. This builds the replication client/server applications and utilities.

Requirements

  • Atleast one standalone or "backend" Cyrus IMAP server.
  • Atleast one machine that will become the first "replica" server.

Configuring the "replica" server

The "replica" server is a standalone server which listens for and processes synchronization messages from a "master" server. The "replica" server needs to be configured to accept these synchonization messages. The "replica" server MUST NOT be configured to be part of a Murder (it should only be configured into the Murder at the point at which it replaces a failed backend "master").

  1. Configure a standalone server as described in the rest of the documentation.
  2. Add the following line to the "/etc/services" file.
       csync     2005/tcp
    

    Note that the port number is arbitrary as long as its not being used by any other services on your network.

  3. Add a line similar to the following in the SERVICES section of cyrus.conf:

      syncserver       cmd="/usr/cyrus/bin/sync_server" listen="csync"
    

  4. Start/restart "/usr/cyrus/bin/master".

Configuring the "master" server

The "master" server is the standalone or "backend" server which is actively serving mailboxes to clients. This server needs to be configured to synchronize its mailstore with a "replica" server.

  1. Add the following line to the "/etc/services" file.
       csync     2005/tcp
    

    Note that the port number MUST be the same as that used on the "replica" server.

  2. Specify the hostname of the "replica" server and how to authenticate to it using the following imap.conf options:
    • sync_host
    • sync_authname
    • sync_realm
    • sync_password

    Note that sync_authname MUST be an admin on the "replica" server. Also note that sync_realm and sync_password may not be necessary depending on the SASL mechanism used for authentication.

Compression

If you are running replication over a remote link, then the tradeoff between bandwidth and CPU usage will tilt strongly in favour of enabling compression to save bandwidth at a slight increase in CPU cost. You can set the 'sync_compress' imapd.conf value, or pass the '-z' flag to sync_client.
  1. sync_compress: 1

"Rolling" replication

"Rolling" replication means that the "master" server continuously synchonizes itself with the replica. To configure "rolling" replication, perform the following:
  1. Enable the sync_log option in imapd.conf. This allows the imapd, pop3d, nntpd, and lmtpd services to log synchonization actions which will be periodically serviced by sync_client.
  2. Optionally, adjust the sync_repeat_interval in imapd.conf.
  3. Add a line similar to the following in the STARTUP section of cyrus.conf:
      syncclient       cmd="/usr/cyrus/bin/sync_client -r"
    
  4. Start/restart "/usr/cyrus/bin/master".

Administration

Manual replication

To manually synchonize any part of the mailstore, simply run sync_client(8) with the appropriate command line options. Note that you CAN manually synchonize even if "rolling" replication has been configured.

You can also run cyr_synclog(8) instead, which will insert the record into the rolling replication log.

Failover


last modified: $Date: 2010/01/06 17:01:29 $ cyrus-imapd-2.5.10/doc/install.html0000644000175000017500000000510513001236020014042 00000000000000 Installing and Configuring the Cyrus IMAP Server

Installing and Configuring the Cyrus IMAP Server

The Internet Message Access Protocol (IMAP) is an Internet standards-track protocol for accessing messages (mail, news, etc). The IMAP server stores and provides access to messages.

The file doc/questions.html contains a list of questions we'd like to answer but haven't gotten to yet; doc/faq.html contains some answers that we have thought of. Please feel free to contribute!

Please refer to Sending Feedback if you would like to submit a bug, feature request or patch.

For detailed changes, refer to the file doc/changes in the distribution.

Contents

Other interesting stuff

Here's some software that you may want to run with Cyrus. This software isn't maintained or supported by CMU, so please ask the maintainers for support.

  • Websieve, a web-based front-end for Sieve script management with Cyrus.
  • Sendmail, the most popular MTA around.
  • Postfix, a popular competitor MTA.


Return to the Cyrus IMAP Server Home Page cyrus-imapd-2.5.10/doc/sieve.html0000644000175000017500000000124713001236020013512 00000000000000 Sieve: A mail filtering language

Sieve: A mail filtering language

Sieve is a Internet standards-track protocol for filtering messages on delivery. The Cyrus Sieve implementation supports filing messages into specific folders, forwarding messages, rejecting messages, and the standard vacation function. It can reply to messages based on headers or envelope information.

Cyrus Sieve

Some simple sample Sieve scripts

cyrus-imapd-2.5.10/doc/install-auth.html0000644000175000017500000001720213001236020015002 00000000000000 Authenticating Users

Authenticating Users

Introduction

The Cyrus IMAP Server uses the Cyrus SASL library to authenticate users. Please refer to the Cyrus SASL documentation for specific details on SASL. This section focuses specifically on the server processes distributed with Cyrus IMAPd.

Authentication Mechanisms

At this writing, the underlying Cyrus SASL library supports a variety of SASL mechanisms, including CRAM-MD5, DIGEST-MD5, KERBEROS_V4, and GSSAPI. The Cyrus IMAP, POP, and LMTP servers also support STARTTLS using client-side certificates and the EXTERNAL authentication method.

GSSAPI is specific to Kerberos version 5. Additionally, STARTTLS client side certificates have not been extensively tested.

When STARTTLS is enabled, the PLAIN SASL mechanism (if installed) also becomes available. This is because one should not pass a clear text password over the wire unless the connection is encrypted.

The IMAP protocol also supports a way for users to authenticate without using SASL (the specification). This is via the 'LOGIN' command (not to be confused by the LOGIN SASL mechanism). The IMAP LOGIN command (as with PLAIN) will send your password in clear-text to the server. In this case, the password is still verified through the Cyrus SASL library, though no SASL mechanism actually performs a negotiation.

The POP server is capable of APOP authentication, but this requries that Cyrus SASL be compiled --with-checkapop, and also that you are using an auxprop backend for your password store (e.g. the sasldb auxprop plugin).

Authentication Recommendations

  • If you are running a mail server on a single machine, we recommend that you configure the system to use CRAM-MD5 or DIGEST-MD5. We have not provided utilities for you to let users change their passwords but either we or someone else might provide that feature.
  • If you have more than one mail server, we recommend that you configure the system to use GSSAPI and Kerberos5.
  • If you have some other authentication mechanism that requires the clear text password, you should use saslauthd.

    saslauthd is something specific to the Cyrus SASL libraries. While it is less generic than PAM, it is much simpler to configure. The IMAP server simply sends a userid and a corresponding password down a Unix domain pipe. Then, saslauthd takes that userid and password and tries to authenticate with it -- using whatever authentication you use -- and simply returns "yes" or "no" as to whether or not the password was correct.

    It is possible to configure saslauthd to check these passwords via a PAM mechanism, /etc/passwd, or other possibilities.

    PAM stands for pluggable authentication modules and the purpose is to provide a common API which applications can use to obtain authentication for a user. You can think of PAM as a complementary layer under the SASL layer. See http://www.kernel.org/pub/linux/libs/pam/FAQ for more information on PAM. By using a PAM module, all the other applications on your system can take advantage of it -- for example, login, xlock, etc.

    Keep in mind that when you use PLAIN or LOGIN you should encrypt the stream so a user's password cannot be trivially sniffed off of the network.

Configuring Authentication

Cyrus SASL has a number of options that can be configured by the application. To configure these via imapd.conf, simply prefix the appropriate option name with sasl_ (e.g. pwcheck_method becomes sasl_pwcheck_method).

/etc/sasldb2

The easiest method for authenticating users is to use the libsasl authentication database and create users using the "saslpasswd2" utility. Set "sasl_pwcheck_method: auxprop", and be sure that the SASL sasldb auxprop module is installed (it is, by default). Make sure Cyrus can read "/etc/sasldb2":

   chown cyrus /etc/sasldb2*

Shadow Passwords

If you want to authenticate users from "/etc/shadow", things are considerably more complicated, since the cyrus user cannot read the shadow password file. Additionally, this will not allow you to use shared secret mechanisms. To do this, it is necessary to configure libsasl with saslauthd support, and set "sasl_pwcheck_method: saslauthd". The SASL library will then make calls to an external utility running as root to authenticate users.

Kerberos

Configuring Kerberos v4

Cyrus IMAP supports Kerberos v4 if the SASL library was compiled with KERBEROS_V4 support.

You'll have to create a Kerberos v4 identity for the server and add the server's key to the "srvtab" file. The file must be readable by the cyrus user. The server's Kerberos identity is "imap.HOST@REALM", where "HOST" is the first component of the machine's host name and "REALM" is the machine's Kerberos realm.

  1. Here is a sample session, creating a srvtab file for the host named "foobar":
       ksrvutil -f /var/imap/srvtab add
    

    Here is the information "ksrvutil" requests. Respond by filling in values or by pressing RETURN. In this example, the host name is "foobar" and the realm is "ANDREW.CMU.EDU".

       Name: imap
       Instance: foobar
       Realm: ANDREW.CMU.EDU
       Version number:
       New principal: imap.foobar@ANDREW.CMU.EDU; version 0
       Is this correct? (y,n) [y]
       Password:
       Verifying, please re-enter Password:
       Key successfully added.
       Would you like to add another key? (y,n) [y] n
    
  2. If you plan to install Kerberized POP, create the Kerberos identity "pop.HOST@REALM" and add the key to the "srvtab" file. Likewise, if you plan on using LMTP over TCP, create the Kerberos identity "lmtp.HOST@REALM" and add the key to the "srvtab" file.

  3. Make the "srvtab" file owned by the cyrus user:

       chown cyrus /var/imap/srvtab
    
  4. Add the option srvtab option to /etc/imapd.conf:
       srvtab: /var/imap/srvtab
  5. Test using imtest -m KERBEROS_V4. imtest will attempt to authorize as the current Unix user regardless of the current ticket's held. Override this with the -u option.

Troubleshooting Kerberos_V4 problems

Run the program "krbck" (found in the imap directory) as the cyrus user on the IMAP server. This program will diagnose some common Kerberos v4 configuration errors.

Configuring Kerberos v5

Cyrus IMAP supports Kerberos v5 if the SASL library was compiled with GSSAPI support.

You'll have to create a Kerberos v5 identity for the server. Kerberos v5 keys are generally stored in "/etc/krb5.keytab".

  1. Add the "imap/hostname" key using "kadmin".
  2. Let the cyrus user read "/etc/krb5.keytab": user:
       chown cyrus /etc/krb5.keytab
    
  3. Test using imtest -m GSSAPI. imtest will attempt to authorize as the current Unix user regardless of the current ticket's held. Override this with the -u option.

last modified: $Date: 2010/01/06 17:01:29 $ cyrus-imapd-2.5.10/doc/overview.html0000644000175000017500000010572013001236020014246 00000000000000 Cyrus IMAP Server: Overview and Concepts

Cyrus IMAP Server: Overview and Concepts

This document gives an overview of the Cyrus IMAP server. The Cyrus IMAP (Internet Message Access Protocol) server provides access to personal mail and system-wide bulletin boards through the IMAP protocol. The Cyrus IMAP server is a scalable enterprise mail system designed for use from small to large enterprise environments using standards-based technologies.

A full Cyrus IMAP implementation allows a seamless mail and bulletin board environment to be set up across multiple servers. It differs from other IMAP server implementations in that it is run on "sealed" servers, where users are not normally permitted to log in. The mailbox database is stored in parts of the filesystem that are private to the Cyrus IMAP system. All user access to mail is through software using the IMAP, IMAPS, POP3, POP3S, or KPOP protocols.

The private mailbox database design gives the server large advantages in efficiency, scalability, and administratability. Multiple concurrent read/write connections to the same mailbox are permitted. The server supports access control lists on mailboxes and storage quotas on mailbox hierarchies.

This document is organized into the following areas:

Mailbox Namespace

By default, the Cyrus IMAP server presents mailboxes using the netnews namespace convention. Mailbox names are case-sensitive. A mailbox name may not start or end with a "." character, nor may it contain two "." characters in a row.

In this implementation, non-ASCII characters and shell metacharacters are not permitted in mailbox names.

Optionally, the server can present mailboxes using the UNIX hierarchy convention.

Standard (Internal) Namespace

All personal mailboxes for user "bovik" begin with the string "user.bovik.". For example, if user "bovik" had a personal "work" mailbox, it would be called "user.bovik.work". To user "bovik", however, the prefix "user.bovik." normally appears as "INBOX.". The mailbox "user.bovik.work" would therefore appear as "INBOX.work". If the access control list of the mailbox permitted other users to see that mailbox, it would appear to them as "user.bovik.work".

The mailbox "user.bovik" is where the user "bovik" normally receives new mail, and normally appears to user "bovik" as "INBOX". The mailbox "user.bovik" is referred to in this document as user "bovik"'s INBOX.

Administrators create and delete users by creating and deleting the users' INBOX. If a user has an INBOX, then they are allowed to subscribe to mailboxes. Only users without dots in their userid are permitted to have an INBOX. (A user with a dot in their userid would be able to login but would not be able to receive mail. Note that when using the unix hierarchy seperator, this is not the case, and any user may have a dot in their userid.)

When an administrator deletes a user's INBOX, all of the user's personal mailboxes are deleted as well.

With the one notable exception of INBOX, all mailbox names are system-wide--they refer to the same mailbox regardless of the user. Access control lists determine which users can access or see which mailboxes. Using

In contexts which permit relative mailbox names, the mailbox namespace works as follows:

  • Names that do not start with "." are fully qualified.
  • Names that start with "." are relative to the current context.
Thus, if you are working with folder names and the top of the hierarchy is named "cmu.", the name "comp.infosystems.www" resolves to "comp.infosystems.www" and the name ".comp.infosystems.www" resolves to "cmu.comp.infosystems.www".

Alternate Namespace

The Cyrus IMAP server can also use an alternate namespace which allows a user's personal mailboxes to appear as if they reside at the same level as that user's INBOX as opposed to children of it. With this feature, it may appear that there are non-unique names for mailboxes between users (2 different users may each have a top level "work" mailbox), but the internal representation is still user.name.work.

Access Control Lists

Access to each mailbox is controlled by each mailbox's access control list. Access Control Lists (ACLs) provide a powerful mechanism for specifying the users or groups of users who have permission to access the mailboxes. An ACL is a list of zero or more entries. Each entry has an identifier and a set of rights. The identifier specifies the user or group of users for which the entry applies. The set of rights is one or more letters or digits, each letter or digit conferring a particular privilege.

Access Rights

The defined rights are:
l
lookup - The user may see that the mailbox exists.
r
read - The user may read the mailbox. The user may select the mailbox, fetch data, perform searches, and copy messages from the mailbox.
s
seen - Keep per-user seen state. The "Seen" and "Recent" flags are preserved for the user.
w
write - The user may modify flags and keywords other than "Seen" and "Deleted" (which are controlled by other sets of rights).
i
insert - The user may insert new messages into the mailbox.
p
post - The user may send mail to the submission address for the mailbox. This right differs from the "i" right in that the delivery system inserts trace information into submitted messages.
c
create - The user may create new sub-mailboxes of the mailbox, or delete or rename the current mailbox.
d
delete - The user may store the "Deleted" flag, and perform expunges.
a
administer - The user may change the ACL on the mailbox.
You can combine access rights in different ways. For example:
lrs
The user can read the mailbox.
lrsp
The user can read the mailbox, and can post to it through the delivery system. Most delivery systems do not provide authentication, so the "p" right usually has meaning only for the "anonymous" user.
lr
The user can see the mailbox and can read it, but the server does not preserve the "Seen" and "Recent" flags. This set of rights is primarily useful for "anonymous IMAP."
rs
The user can read the mailbox and the server preserves the "Seen" and "Recent" flags, but the mailbox is not visible to the user through the various mailbox listing commands. The user must know the name of the mailbox to be able to access it.
lrsip
The user can read and append to the mailbox, either through IMAP, or through the delivery system.

Identifiers

The identifier part of an ACL entry specifies the user or group for which the entry applies.

There are two special identifiers, "anonymous", and "anyone", which are explained below. The meaning of other identifiers usually depends on the authorization mechanism being used (selected by --with-auth at compile time, defaulting to Unix).

"anonymous" and "anyone"

With any authorization mechanism, two special identifiers are defined. The identifier "anonymous" refers to the anonymous, or unauthenticated user. The identifier "anyone" refers to all users, including the anonymous user.

Kerberos vs. Unix Authorization

The Cyrus IMAP server comes with four authorization mechanisms, one is compatible with Unix-style ("/etc/passwd") authorization, one for use with Kerberos 4, one for use with Kerberos 5, and one for use with an external authorization process (ptloader) which can interface with other group databases (e.g. AFS PTS groups, LDAP Groups, etc).

Note that authorization is not authentication. Authentication is the act of proving who you are. Authorization is the act of determining what rights you have. Authentication is discussed in the Login Authentication part of this document.

In the Unix authorization mechanism, identifiers are either a valid userid or the string "group": followed by a group listed in "/etc/group". Thus:

    root                Refers to the user root
    group:staff         Refers to the group staff

It is also possible to use unix groups with users authenticated through a non-/etc/passwd backend. Note that using unix groups in this way (without associated /etc/passwd entries) is not recommended.

Using the Kerberos authorization mechanism, identifiers are of the form:

    principal.instance@realm
If ".instance" is omitted, it defaults to the null string. If "@realm" is omitted, it defaults to the local realm.

The file "/etc/krb.equiv" contains mappings between Kerberos principals. The file contains zero or more lines, each containing two fields. Any identity matching the first field of a line is changed to the second identity during canonicalization. For example, a line in "/etc/krb.equiv" of:

    bovik@REMOTE.COM bovik
will cause the identity "bovik@REMOTE.COM" to be treated as if it were the local identity "bovik".

A site may wish to write their own authorization mechanism, perhaps to implement a local group mechanism. If it does so (by implementing an auth_[whatever] module), it will dictate its own form and meaning of identifiers.

Negative Rights

Any of the above defined identifiers may be prefixed with a "-" character. The associated rights are then removed from that identifier. These are referred to as "negative rights".

Calculating Users' Rights

To calculate the set of rights granted to a user, the server first calculates the union of all of the rights granted to the user and to all groups the user is a member of. The server then calculates and removes the union of all the negative rights granted to the user and to all groups the user is a member of.

For example, given the ACL:

   anyone       lrsp
   fred         lwi
   -anonymous   s
The user "fred" will be granted the rights "lrswip" and the anonymous user will be granted the rights "lrp".

Implicit Rights for Administrators on Personal Mailboxes

Regardless of the ACL on a mailbox, users who are listed in the "admins" configuration option in "/etc/imapd.conf" implicitly have the "l" and "a" rights on all mailboxes. Users also implicitly have the "l" and "a" rights on their INBOX and all of their personal mailboxes.

Initial ACLs for Newly Created Mailboxes

When a mailbox is created, its ACL starts off with a copy of the ACL of its closest parent mailbox. When a user is created, the ACL on the user's INBOX starts off with a single entry granting all rights to the user. When a non-user mailbox is created and does not have a parent, its ACL is initialized to the value of the "defaultacl" option in "/etc/imapd.conf"

Note that some rights are available implicitly, for example 'anonymous' always has 'p' on user INBOXes, and users always have rights on mailboxes within their INBOX hierarchy.

Login Authentication

This section discusses different types of authentication (ways of logging in) that can be used with Cyrus IMAP.

The Cyrus IMAP server uses the Cyrus SASL library for authentication. This section describes how to configure SASL with use with Cyrus imapd. Please consult the Cyrus SASL System Administrator's Guide for more detailed, up-to-date information.

Anonymous Logins

Regardless of the SASL mechanism used by an individual connection, the server can support anonymous login. If the "allowanonymouslogin" option in "/etc/imapd.conf" is turned on, then the server will permit plaintext password logins using the user "anonymous" and any password. Additionally, the server will enable any SASL mechanisms that allow anonymous logins.

Plaintext Authentication

The SASL library has several ways of verifying plaintext passwords Plaintext passwords are passed either by the IMAP LOGIN command or by the SASL PLAIN mechanism (under a TLS layer).
  • PAM
  • Kerberos v4 Plaintext passwords are verified by obtaining a ticket for the server's Kerberos identity, to protect against Kerberos server spoofing attacks.
  • /etc/passwd
  • /etc/shadow
  • etc.
sasl_auto_transition automatically creates secrets for shared secret authentication when given a password.

The method of plaintext password verification is always through the SASL library, even in the case of the internal LOGIN command. This is to allow the SASL library to be the only source of authentication information. You'll want to look at the sasl_pwcheck_method option in the SASL documentation to understand how to configure a plaintext password verifier for your system.

To disallow the use of plaintext passwords for authentication, you can set allowplaintext: no in imapd.conf. This will still allow PLAIN under TLS, but IMAP LOGIN commands will now fail.

Kerberos Logins

The Kerberos SASL mechanism supports the KERBEROS_V4 authentication mechanism. The mechanism requires that a srvtab file exist in the location given in the "srvtab" configuration option. The srvtab file must be readable by the Cyrus server and must contain a "imap.<host>@<realm>" service key, where <host> is the first component of the server's host name and <realm> is the server's Kerberos realm.

The server will permit logins by identities in the local realm and identities in the realms listed in the "loginrealms" option in "/etc/imapd.conf".

The file "/etc/krb.equiv" contains mappings between Kerberos principals. The file contains zero or more lines, each containing two fields. Any identity matching the first field of a line is permitted to log in as the identity in the second field.

If the "loginuseacl" configuration option is turned on, than any Kerberos identity that is granted the "a" right on the user's INBOX is permitted to log in as that user.

Shared Secrets Logins

Some mechanisms require the user and the server to share a secret (generally a password) that can be used for comparison without actually passing the password in the clear across the network. For these mechanism (such as CRAM-MD5 and DIGEST-MD5), you will need to supply a source of passwords, such as the sasldb (which is described more fully in the Cyrus SASL distribution)

Quotas

Quotas allow server administrators to limit resources used by hierarchies of mailboxes on the server.

Supports Quotas on Storage

The Cyrus IMAP server supports quotas on storage, which is defined as the number of bytes of the relevant RFC-822 messages, in kilobytes. Each copy of a message is counted independently, even when the server can conserve disk space use by making hard links to message files. The additional disk space overhead used by mailbox index and cache files is not charged against a quota.

Quota Roots

Quotas are applied to quota roots, which can be at any level of the mailbox hierarchy. Quota roots need not also be mailboxes.

Quotas on a quota root apply to the sum of the usage of any mailbox at that level and any sub-mailboxes of that level that are not underneath a quota root on a sub-hierarchy. This means that each mailbox is limited by at most one quota root.

For example, if the mailboxes

   user.bovik
   user.bovik.list.imap
   user.bovik.list.info-cyrus
   user.bovik.saved
   user.bovik.todo

exist and the quota roots

   user.bovik
   user.bovik.list
   user.bovik.saved
exist, then the quota root "user.bovik" applies to the mailboxes "user.bovik" and "user.bovik.todo"; the quota root "user.bovik.list" applies to the mailboxes "user.bovik.list.imap" and "user.bovik.list.info-cyrus"; and the quota root "user.bovik.saved" applies to the mailbox "user.bovik.saved".

Quota roots are created automatically when they are mentioned in the "setquota" command. Quota roots may not be deleted through the protocol, see Removing Quota Roots for instructions on how to delete them.

Mail Delivery Behavior

Normally, in order for a message to be inserted into a mailbox, the quota root for the mailbox must have enough unused storage so that inserting the message will not cause the block quota to go over the limit.

Mail delivery is a special case. In order for a message to be delivered to a mailbox, the quota root for the mailbox must not have usage that is over the limit. If the usage is not over the limit, then one message may be delivered regardless of its size. This puts the mailbox's usage over the quota, causing a user to be informed of the problem and permitting them to correct it. If delivery were not permitted in this case, the user would have no practical way of knowing that there was mail that could not be delivered.

If the usage is over the limit, then the mail delivery will fail with a temporary error. This will cause the delivery system to re-attempt delivery for a couple of days (permitting the user time to notice and correct the problem) and then return the mail to the sender.

Quota Warnings Upon Select When User Has "d" Rights

When a user selects a mailbox whose quota root has usage that is close to or over the limit and the user has "d" rights on the mailbox, the server will issue an alert notifying the user that usage is close to or over the limit. The threshold of usage at which the server will issue quota warnings is set by the "quotawarn" configuration option.

The server only issues warnings when the user has "d" rights because only users with "d" rights are capable of correcting the problem.

Quotas and Partitions

Quota roots are independent of partitions. A single quota root can apply to mailboxes in different partitions.

New Mail Notification

The Cyrus IMAP server comes with a notification daemon which supports multiple mechanisms for notifying users of new mail. Notifications can be configured to be sent upon normal delivery ("MAIL" class) and/or sent as requested by a Sieve script ("SIEVE" class).

By default, both types of notifications are disabled. Notifications are enabled by using one or both of the following configuration options:

  • the "mailnotifier" option selects the notifyd method to use for "MAIL" class notifications
  • the "sievenotifier" option selects the notifyd method to use for "SIEVE" class notifications (when no method is specified by the Sieve action)

Partitions

Partitions allow administrators to store different mailboxes in different parts of the Unix filesystem. This is intended to be used to allow hierarchies of mailboxes to be spread across multiple disks.

Specifying Partitions with "create"

When an administrator creates a new mailbox, the name of the partition for the mailbox may be specified using an optional second argument to the "create" command. Non-administrators are not permitted to specify the partition of a mailbox. If the partition is not specified, then the mailbox inherits the partition of its most immediate parent mailbox. If the mailbox has no parent, it gets the partition specified in the "defaultpartition" configuration option.

The optional second argument to the "create" command can usually be given only when using a specialized Cyrus-aware administrative client such as cyradm.

Changing Partitions with "rename"

An administrator may change the partition of a mailbox by using the rename command with an optional third argument. When a third argument to rename is given, the first and second arguments can be the same--this changes the partition of a mailbox without changing its name. If a third argument to rename is not given and the first argument is not "INBOX", the partition of a mailbox does not change. If a third argument to rename is not given and the first argument is "INBOX", the newly created mailbox gets the same partition it would get from the "create" command.

News

Cyrus has the ability to export Usenet via IMAP and/or export shared IMAP mailboxes via an NNTP server which is included with Cyrus. For more information on exporting news groups through the IMAP server, see install-netnews.html.

POP3 Server

The Cyrus IMAP server software comes with a compatibility POP3 server. Due to limitations in the POP3 protocol, the server can only access a user's INBOX and only one instance of a POP3 server may exist for any one user at any time. While a POP3 server has a user's INBOX open, expunge operations from any concurrent IMAP session will fail.

When Kerberos login authentication is being used, the POP3 server uses the server identity "pop.host@realm" instead of "imap.host@realm", where "host" is the first component of the server's host name and "realm" is the server's Kerberos realm. When the POP3 server is invoked with the "-k" switch, the server exports MIT's KPOP protocol instead of generic POP3.

The syslog facility

The Cyrus IMAP server software sends log messages to the "local6" syslog facility. The severity levels used are:
  • CRIT - Critical errors which probably require prompt administrator action
  • ERR - I/O errors, including failure to update quota usage. The syslog message includes the specific file and Unix error.
  • WARNING - Protection mechanism failures, client inactivity timeouts
  • NOTICE - Authentications, both successful and unsuccessful
  • INFO - Mailbox openings, duplicate delivery suppression

Mail Directory Recovery

This section describes the various databases used by the Cyrus IMAP server software and what can be done to recover from various inconsistencies in these databases.

Reconstructing Mailbox Directories

The largest database is the mailbox directories. Each mailbox directory contains the following files:
message files
There is one file per message, containing the message in RFC 822 format. Lines in the message are separated by CRLF, not just LF. The file name of each message is the message's UID followed by a dot (.).

In netnews newsgroups, the message files instead follow the format and naming conventions imposed by the netnews software.

cyrus.header
This file contains a magic number and variable-length information about the mailbox itself.

cyrus.index
This file contains fixed-length information about the mailbox itself and each message in the mailbox.

cyrus.cache
This file contans variable-length information about each message in the mailbox.

cyrus.seen
This file contains variable-length state information about each reader of the mailbox who has "s" permissions.
The "reconstruct" program can be used to recover from corruption in mailbox directories. If "reconstruct" can find existing header and index files, it attempts to preserve any data in them that is not derivable from the message files themselves. The state "reconstruct" attempts to preserve includes the flag names, flag state, and internal date. "Reconstruct" derives all other information from the message files.

An administrator may recover from a damaged disk by restoring message files from a backup and then running reconstruct to regenerate what it can of the other files.

The "reconstruct" program does not adjust the quota usage recorded in any quota root files. After running reconstruct, it is advisable to run "quota -f" (described below) in order to fix the quota root files.

Reconstructing the Mailboxes File

NOTE: CURRENTLY UNAVAILABLE

The mailboxes file in the configuration directory is the most critical file in the entire Cyrus IMAP system. It contains a sorted list of each mailbox on the server, along with the mailboxes quota root and ACL. To reconstruct a corrupted mailboxes file, run the "reconstruct -m" command. The "reconstruct" program, when invoked with the "-m" switch, scavenges and corrects whatever data it can find in the existing mailboxes file. It then scans all partitions listed in the imapd.conf file for additional mailbox directories to put in the mailboxes file.

The cyrus.header file in each mailbox directory stores a redundant copy of the mailbox ACL, to be used as a backup when rebuilding the mailboxes file.

Reconstructing Quota Roots

The subdirectory "quota" of the configuration directory (specified in the "configdirectory" configuration option) contains one file per quota root, with the file name being the name of the quota root. These files store the quota usage and limits of each of the quota roots.

The "quota" program, when invoked with the "-f" switch, recalculates the quota root of each mailbox and the quota usage of each quota root.

Removing Quota Roots

To remove a quota root, remove the quota root's file. Then run "quota -f" to make the quota files consistent again.

Subscriptions

The subdirectory "user" of the configuration directory contains user subscriptions. There is one file per user, with a filename of the userid followed by ".sub". Each file contains a sorted list of subscribed mailboxes.

There is no program to recover from damaged subscription files. A site may recover from lost subscription files by restoring from backups.

Configuration Directory

Many objects in the configuration directory are discussed in the Database Recovery section. This section documents two other directories that reside in the configuration directory.

"log" Directory

The subdirectory "log" under the configuration directory permits administrators to keep protocol telemetry logs on a per-user basis.

If a subdirectory of "log" exists with the same name as a user, the IMAP and POP3 servers will keep a telemetry log of protocol sessions authenticating as that user. The telemetry log is stored in the subdirectory with a filename of the server process-id and starts with the first command following authentication.

"proc" Directory

The subdirectory "proc" under the configuration directory contains one file per active server process. The file name is the ASCII representation of the process id and the file contains the following tab-separated fields:
  • hostname of the client
  • login name of the user, if logged in
  • selected mailbox, if a mailbox is selected
The file may contain arbitrary characters after the first newline character.

The "proc" subdirectory is normally be cleaned out on server reboot.

Message Delivery

Mail transport agents such as Sendmail, Postfix, or Exim communicate with the Cyrus server via LMTP (the Local Mail Transport Protocol) implemented by the LMTP daemon. This can be done either directly by the MTA (prefered, for performance reasons) or via the deliver LMTP client.

Local Mail Transfer Protocol

LMTP, the Local Mail Transfer Protocol, is a variant of SMTP design for transferring mail to the final message store. LMTP allows MTAs to deliver "local" mail over a network. This is an easy optimization so that the IMAP server doesn't need to maintain a queue of messages or run an MTA.

The Cyrus server implements LMTP via the lmtpd daemon. LMTP can either be used over a network via TCP or local via a UNIX domain socket. There are security differnces between these two alternatives; read more below

For final delivery via LMTP over a TCP socket, it is necessary to use LMTP AUTH. This is accomplished using SASL to authenticate the delivering user. If your mail server is performing delivery via LMTP AUTH (that is, using a SASL mechanism), you will want their authentication id to be an LMTP admins (either via the admins imapd.conf option or via the <service>_admins option, typically lmtp_admins).

Alternatively you may deliver via LMTP to a unix domain socket, and the connection will be preauthenticated as an administrative user (and access control is accomplished by controlling access to the socket).

Note that if a user has a sieve script, the sieve script runs authorized as *that* user, and the rights of the posting user are ignored for the purposes of determining the outcome of the sieve script.

Single Instance Store

If a delivery attempt mentions several recipients (only possible if the MTA is speaking LMTP to lmtpd), the server attempts to store as few copies of a message as possible. It will store one copy of the message per partition, and create hard links for all other recipients of the message.

Single instance store can be turned off by using the "singleinstancestore" flag in the configuration file.

Duplicate Delivery Suppression

A message is considered a duplicate if two copies of a message with the same message-id and the same envelope receipient are received. Cyrus uses the duplicate delivery database to hold this information, and it looks approximately 3 days back in the default install.

Duplicate delivery suppression can be turned off by using the "duplicatesuppression" flag in the configuration file.

Sieve, a Mail Filtering Language

Sieve is a mail filtering language that can filter mail into an appropriate IMAP mailbox as it is delivered via lmtp. For more information, look here.

Cyrus Murder, the IMAP Aggregator

Cyrus now supports the distribution of mailboxes across a number of IMAP servers to allow for horizontal scalability. For information on setting up this configuration, see here.


Return to the Cyrus IMAP Server Home Page cyrus-imapd-2.5.10/doc/murder.fig0000644000175000017500000001170213001236020013473 00000000000000#FIG 3.2 Landscape Center Inches Letter 100.00 Single -2 1200 2 6 8400 6075 10800 6900 4 0 0 50 0 0 12 0.0000 4 180 2370 8400 6225 Client connects to any frontend\001 4 0 0 50 0 0 12 0.0000 4 180 1995 8400 6450 server, which then queries\001 4 0 0 50 0 0 12 0.0000 4 135 1965 8400 6675 its local mailbox database\001 4 0 0 50 0 0 12 0.0000 4 135 2295 8400 6900 for the location of the mailbox.\001 -6 6 825 1800 3075 3075 4 0 0 50 0 0 12 0.0000 4 180 1920 825 1950 Backend Servers perform\001 4 0 0 50 0 0 12 0.0000 4 135 1950 825 2175 RESERVE and COMMIT\001 4 0 0 50 0 0 12 0.0000 4 180 2250 825 2400 operations to mupdate master\001 4 0 0 50 0 0 12 0.0000 4 180 2100 825 2625 before allowing any mailbox\001 4 0 0 50 0 0 12 0.0000 4 180 1920 825 2850 operation that affects the\001 4 0 0 50 0 0 12 0.0000 4 135 1365 825 3075 mailbox database.\001 -6 6 5250 1800 9225 2475 4 0 0 50 0 0 12 0.0000 4 135 2940 5250 1950 Frontend server mailbox databases are\001 4 0 0 50 0 0 12 0.0000 4 180 3300 5250 2400 mupdate connection to the mupdate master.\001 4 0 0 50 0 0 12 0.0000 4 180 3960 5250 2175 updated based upon a stream on a frotnend-initiated\001 -6 6 9600 1500 11250 2400 4 0 0 50 0 0 12 0.0000 4 135 1575 9600 1650 Connection to LMTP\001 4 0 0 50 0 0 12 0.0000 4 180 1440 9600 1875 proxy (possibly via\001 4 0 0 50 0 0 12 0.0000 4 135 1620 9600 2100 unix socket on SMTP\001 4 0 0 50 0 0 12 0.0000 4 180 555 9600 2325 server)\001 -6 6 6075 750 10950 1200 4 0 0 50 0 0 12 0.0000 4 180 4875 6075 1125 the master mupdate server to determine final destination of mail.\001 4 0 0 50 0 0 12 0.0000 4 180 4245 6075 900 LMTP proxies perform mupdate lookups directly against\001 -6 6 7950 3150 9075 4050 4 0 0 50 0 0 12 0.0000 4 180 960 7950 3300 LMTP Proxy\001 4 0 0 50 0 0 12 0.0000 4 180 930 7950 3525 (possibly on\001 4 0 0 50 0 0 12 0.0000 4 135 1005 7950 3750 a Frontend or\001 4 0 0 50 0 0 12 0.0000 4 180 1080 7950 3975 SMTP server)\001 -6 6 10125 3600 13200 4500 4 0 0 50 0 0 12 0.0000 4 180 2580 10125 3750 Final mail delivery is via an LMTP\001 4 0 0 50 0 0 12 0.0000 4 180 2595 10125 3975 proxy which uses LMTP to deliver\001 4 0 0 50 0 0 12 0.0000 4 135 2715 10125 4200 to the correct backend server based\001 4 0 0 50 0 0 12 0.0000 4 180 3060 10125 4425 on information from the mupdate master.\001 -6 6 3450 4200 6150 5325 4 0 0 50 0 0 12 0.0000 4 180 2550 3450 4350 Frontend servers perform mailbox\001 4 0 0 50 0 0 12 0.0000 4 180 2700 3450 4575 lookup, and then connect via IMAP,\001 4 0 0 50 0 0 12 0.0000 4 165 2415 3450 4800 POP, NNTP, MANAGESIEVE,\001 4 0 0 50 0 0 12 0.0000 4 165 2205 3450 5025 or LMTP to backend servers,\001 4 0 0 50 0 0 12 0.0000 4 180 1125 3450 5250 as appropriate.\001 -6 2 2 0 1 0 7 50 0 -1 0.000 0 0 -1 0 0 5 1650 3375 2550 3375 2550 5100 1650 5100 1650 3375 2 2 0 1 0 7 50 0 -1 0.000 0 0 -1 0 0 5 6975 3375 7875 3375 7875 5100 6975 5100 6975 3375 2 2 0 1 0 7 50 0 -1 0.000 0 0 -1 0 0 5 10875 4725 11775 4725 11775 6450 10875 6450 10875 4725 2 2 0 1 0 7 50 0 -1 0.000 0 0 -1 0 0 5 6975 5475 7875 5475 7875 7200 6975 7200 6975 5475 2 2 0 1 0 7 50 0 -1 0.000 0 0 -1 0 0 5 4125 975 5025 975 5025 2700 4125 2700 4125 975 2 2 0 1 0 7 50 0 -1 0.000 0 0 -1 0 0 5 1650 5475 2550 5475 2550 7200 1650 7200 1650 5475 2 1 0 1 0 7 50 0 -1 0.000 0 0 -1 1 0 3 1 1 1.00 60.00 120.00 2550 3750 2550 3675 4125 2325 2 1 0 1 0 7 50 0 -1 0.000 0 0 -1 1 0 3 1 1 1.00 60.00 120.00 5100 2325 5025 2400 6975 3675 2 1 0 1 0 7 50 0 -1 0.000 0 0 -1 1 0 3 1 1 1.00 60.00 120.00 5025 2325 5025 2400 6975 5850 2 1 0 1 0 7 50 0 -1 0.000 0 0 -1 1 0 2 1 1 1.00 60.00 120.00 10875 5100 7875 4200 2 1 0 1 0 7 50 0 -1 0.000 0 0 -1 1 0 2 1 1 1.00 60.00 120.00 10875 5325 7875 6000 2 1 0 1 0 7 50 0 -1 0.000 0 0 -1 1 0 2 1 1 1.00 60.00 120.00 6975 6450 2550 4950 2 1 0 1 0 7 50 0 -1 0.000 0 0 -1 1 0 3 1 1 1.00 60.00 120.00 6975 3900 6975 3825 2550 4050 2 1 0 1 0 7 50 0 -1 0.000 0 0 -1 1 0 2 1 1 1.00 60.00 120.00 6990 4380 2565 6630 2 1 0 1 0 7 50 0 -1 0.000 0 0 -1 1 0 3 1 1 1.00 60.00 120.00 6900 6530 6975 6530 2550 6830 2 2 0 1 0 7 50 0 -1 0.000 0 0 -1 0 0 5 11550 1425 12450 1425 12450 3150 11550 3150 11550 1425 2 1 0 1 0 7 50 0 -1 0.000 0 0 -1 0 0 2 9375 2550 9300 1575 2 1 0 1 0 7 50 0 -1 0.000 0 0 -1 1 0 2 1 1 1.00 60.00 120.00 11550 1950 9975 2775 2 1 0 1 0 7 50 0 -1 0.000 0 0 -1 1 0 2 1 1 1.00 60.00 120.00 9075 2925 2550 3750 2 1 0 1 0 7 50 0 -1 0.000 0 0 -1 1 0 2 1 1 1.00 60.00 120.00 9300 1575 5025 1200 2 1 0 1 0 7 50 0 -1 0.000 0 0 -1 1 0 2 1 1 1.00 60.00 120.00 2580 5753 4155 2528 2 2 0 1 0 7 50 0 -1 0.000 0 0 -1 0 0 5 9075 2550 9975 2550 9975 4275 9075 4275 9075 2550 4 0 0 50 0 0 12 0.0000 4 180 1275 4125 750 Mupdate Master\001 4 0 0 50 0 0 12 0.0000 4 135 1290 1575 7500 Backend Servers\001 4 0 0 50 0 0 24 0.0000 4 330 6090 525 375 Cyrus MURDER component interactions\001 4 0 0 50 0 0 12 0.0000 4 135 1305 6975 7500 Frontend Servers\001 4 0 0 50 0 0 12 0.0000 4 135 1020 11550 3450 SMTP Server\001 4 0 0 50 0 0 12 0.0000 4 135 1875 10875 6750 IMAP/POP/NNTP Client\001 cyrus-imapd-2.5.10/doc/os.html0000644000175000017500000000435313001236020013021 00000000000000 Operating System Notes

Operating System Notes

All

  1. Shadow passwords
    On any system with shadow passwords (including Solaris 2.5 with Unix authentication), read the SASL documentation carefully to make sure it is configured correctly.

Solaris

  1. Modern Solaris systems have several useful utilities in /usr/proc/bin, among them pmap. This can be used to calculate the incremental cost (number of non-shared pages) of an imapd process, which is useful for sizing purposes.

HP-UX

  1. The memory mapping support (mmap(2)) in HP-UX does not have the right semantics for the Cyrus IMAP server under the 9.0 and 10.0 release of the operating system. It appears this is related to the hardware's use of inverse page tables. It is recommended that large-scale sites consider using some other platform.

  2. HP-UX 9.0.4: Comments from testers
    The C that ships with HP-UX is totally unsuited for use with unix packages. Either the HP-UX ANSI C developers kit must be purchased separately from HP or GNU's gcc compiler (which can bootstrap itself from the basic HP C) must be built on the target system.

Linux

  1. synchronous FS updates.
    By turning on synchronous updates for ext2fs, all updates (instead of just meta-data) become synchronous. This is good for reliability, but bad for performance.

    The big problem used to be with the mailboxes file. The 2.0 release and later addressed this problem by changing the flat file to a Berkerley DB database.

    Note this is for ext2fs. If you are using a newer filesystem (such as xfs, jfs, or reiserfs) the synchronous metadata issue shouldn't come up. Then again, we haven't really looked at other filesystems for Linux yet. (It appears that the different filesystems support slightly different semantics, and it's not always clear what the right thing for the application to do is.)


last modified: $Date: 2010/01/06 17:01:29 $ cyrus-imapd-2.5.10/doc/install-prereq.html0000644000175000017500000000660513001236020015344 00000000000000 Prerequisites and other notes

Prerequisites and other notes

The following programs and/or packages are required.

  • libsasl, version 2.1.7 or higher. To obtain libsasl, ftp it from ftp.andrew.cmu.edu. Earlier versions of SASL will not work; please get the latest one. Configure SASL so that it supports whatever authentication method your site uses. Please pay careful attention to the SASL configuration. This is the biggest problem that most people have.
  • Berkeley DB, version 3.0.55 or higher. Berkeley DB can be obtained from Sleepycat. It is strongly recommended that libsasl be compiled with Berkeley DB support, using the same version of Berkeley DB. (If you have a Berkeley DB version mismatch, somewhat perplexing crashes result.)
  • GNU Make is required. Get it from the Free Software Foundation. It is probably easier to find it via ftp.

The following programs and/or packages are required for specific features. If you don't have them, certain features of the IMAP server will be disabled.

  • Perl, version 5. To obtain Perl, see the Comprehensive Perl Archive. This is required for cyradm (written by Brandon Allbery). It is also used for some installation scripts: you don't need it but it may make your life easier. We recommend at least version 5.00502.
  • OpenSSL, version 0.9.4 or higher. Required for STARTTLS support and for IMAP/POP3 wrapped in SSL (the imaps/pop3s ports). Available from http://www.openssl.org/.
  • libwrap, from Wietse Venema. This will allow one to control who is accessing what service, based on IP address. Available from ftp://ftp.porcupine.org/pub/security/ in the tcp_wrappers package..
  • Net-SNMP (formerly UCD-SNMP), version 4.2 or higher. Required for SNMP monitoring of the IMAP server. Available from http://www.net-snmp.org/.
  • If you use AFS PTS support for groups, Cyrus still depends on Kerberos and AFS. If you successfully compiled SASL with your Kerberos library, it's likely that it will work well with Cyrus.
  • We recommend using an MTA (mail transfer agent) that supports LMTP (local mail transfer protocol). We use Sendmail and recommend version 8.12.8 or higher, available from http://www.sendmail.org. Others have reported success with Postfix.

The following programs and/or packages are recommended:

  • flex - libcyrus_sieve has two different lexical analyzers, and that's hard to do with traditional lex.
  • gcc - we build using gcc and the compiler options -O2 -g.


last modified: $Date: 2010/01/06 17:01:29 $ cyrus-imapd-2.5.10/doc/bugs.html0000644000175000017500000000740113001236020013335 00000000000000 Changes to the Cyrus IMAP Server

Known bugs in the Cyrus IMAP Server

We're working on moving to a Bugzilla database. It's still being built up, but you can search/add to it here. Eventually, all the bugs below will be in there.

imapd and core utilities

  • Multiple APPENDs don't always correctly return the EXISTS response. (can't reproduce?)
  • Particularly large quotas can wrap around.
  • The RENAME command is not atomic.
  • reconstruct doesn't deal with the mailboxes.db file.
  • we should deal with having to reset UIDs
  • the algorithm used for naming stage files is fragile and not threadsafe.
  • during appendstage(), the message is parsed once per delivery, not once at the beginning.
  • master should pay attention to processes that have told it they are listening, and make sure they don't die abnormally. likewise, it should be on the lookout for continually forking services.
  • master should probably have a babysitting service ("always keep this process running").

proxyd and Cyrus Murder

  • RENAME across servers isn't implemented.
  • Tagged lines with literals can cause problems for proxyd.

lmtpd, deliver, and sieve

  • 8-bit set characters are coerced to 'X', but not before the notify_zephyr code (if used) has had a chance to send them out.
  • Deliver does not handle messages containing NUL properly due to stdio problems (the characters between the NUL and the LF will be lost.)
  • Deliver doesn't gracefully handle CR CR sequences in messages. Well, ok, it hangs.

authentication and authorization

  • Using AFS groups with ptclient, users with negative rights as part of groups may be granted access to mailboxes if ptclient has died. We plan to have this fixed eventually.
  • In some failures of the krbck program, the error messages printed out bear no resemblance to what actually went wrong.

other utilities

  • cyradm may need to change authname/username stuff. Something to check.
  • imtest: it would be nice for the authorization name to default to the authentication name, except when specifically overridden.
  • any utilities doing db operations should catch signals and poll for them to see if it should exit (like mbpath, ipurge).

libraries

Things we want to do

  • Implement the IMAP VIEW extension.
  • Implement the IMAP ANNOTATE extension.
  • Implement some sort of backup/restore system that's more efficient and easier to use than Amanda on the filesystem.
  • Add mailbox version numbers.
  • Add mailbox tombstones (gives NEWNAME support).
  • Design and implement ALIST, the advanced list command.
  • Investigate changing from the prot layer to using sfio.
  • Write a test module for lmtpengine.
  • Allow renaming users. (RENAME user.joe user.harry.) Needs to move all metadata per-user data. (seen, subscriptions, sieve state?)

Please refer to Sending Feedback if you would like to submit a bug, feature request or (best of all) patch.


Last update: $Date: 2006/11/30 17:11:16 $
Return to the Cyrus IMAP Server Home Page cyrus-imapd-2.5.10/doc/changes.html0000644000175000017500000041021413001241324014010 00000000000000 Changes to the Cyrus IMAP Server

Changes to the Cyrus IMAP Server since 2.5.9

Dependency changes

  • Jansson versions >= 2.3 are now supported (was >= 2.7)
  • Restored support for AutoConf 2.63
  • GCC 6 is now supported

Other changes

  • master(8) now supports a "-V" (print version and exit) option
  • version information is now based on git describe, not hard-coded strings

Bug fixes

  • Fixed Issue #34: imapd in murder no longer crashes on MOVE to nonexistent folder (thanks Wolfgang Breyha)
  • Fixed Issue #15: replication no longer crashes on mailboxes that are too old to be replicated. Instead, it fails with an error and logs a warning that they need to be reconstructed
  • Fixed Issue #45: extended LIST doesn't lose options when proxied to backend
  • Fixed Task #142: extended LIST response no longer missing \HasNoChildren flag on last mailbox
  • Fixed Issue #49: httpd no longer crashes with assertion failure on shutdown after CardDAV has been used
  • Fixed Issue #31: the ldap_timeout setting is now used correctly
  • Fixed bugzilla #3909: idled(8) no longer runs as root (thanks Carlos Velasco)
  • Fixed Issue #5: renaming folder with annotations no longer increases annotation quota usage
  • Fixed: URLFETCH crash when section is NULL
  • various build system improvements

Changes to the Cyrus IMAP Server since 2.5.8

Dependency changes

  • Libical 2.0.0 is now supported.
  • preliminary support for OpenSSL 1.1.0 (not yet released)

Other changes

  • ipurge(8) now supports a “-n” (dry run) option (thanks Valentin Vidic)

Bug fixes

  • Fixed: imapd now proxies LIST (special-use) to backend (thanks John Capo)
  • Fixed: sync_client handles its shutdown file more reliably (thanks John Capo)
  • Fixed: httpd no longer crashes with assertion failure on shutdown after CalDAV has been used
  • Fixed bugzilla #3938: squat search now handles pre-2.5 cyrus.squat data
  • Fixed Issue #5: twoskip database I/O performance in unlocked foreach
  • various build system improvements

Changes to the Cyrus IMAP Server since 2.5.7

Murder changes

  • Allow replicated backends in a discrete Murder to both actively participate in the Murder.
  • When choosing between ANNOTATEMORE and METADATA, favour what the client used.

Other changes

  • cyr_dbtool now supports improved_mboxlist_sort (-M)

Bug fixes

  • Fixed: master on pselect systems no longer chokes on repeated interrupts (thanks Jens Erat and team)
  • Fixed: better iOS CalDAV support (don’t announce VPOLL)
  • Fixed: backported version detection code to detect future versions
  • Fixed bug #3927: don’t break cyrus.index on XFER of mailbox with annotations (thanks Wolfgang Breyha)
  • Fixed: replication/XFER of mailbox names containing ‘@’
  • Fixed: METADATA and GETMETADATA pattern/list recognition
  • Fixed bug #3862: don’t leave behind inconsistent mailboxes when mupdate fails during mailbox rename
  • Fixed compilation with Sun Studio 12 C Compiler (thanks Marty Lee)
  • Fixed bug #3765: ctl_cyrusdb now uses database paths from imapd.conf (thanks Simon Matter)
  • Fixed T227: service processes no longer crash with ‘-T 0’ argument (thanks Ian Batten and Jens Erat)
  • various build system fixes

Changes to the Cyrus IMAP Server since 2.5.6

Security fixes

  • CVE-2015-8077, CVE-2015-8078: protect against integer overflow in urlfetch range checks

SSL changes

  • Support for legacy SSLv2 and SSLv3 protocols has been removed

    These protocols were previously enabled by default, but could be disabled by removing them from tls_versions in imapd.conf(5). They are now completely unsupported.

    Administrators needing to support these protocols may find a patch in contrib/allow-broken-sslv23.patch. With this patch, SSLv2 and SSLv3 will be disabled by default, but can be enabled by adding them to tls_versions. Users of this patch do so at their own risk.

  • Support for TLS compression has been removed (thanks OndÅ™ej Surý)

    This was previously disabled by default, but could be enabled with tls_compression in imapd.conf(5). It is now completely unsupported.

Bug fixes

  • Fixed: crash in sync_server when built with buggy Sun CC (thanks Jens Erat)
  • Fixed bug #3908: crash in ctl_mboxlist -m
  • Fixed: setrlimit error on startup
  • Fixed T216: don’t break quotas when transferring mailboxes between backends
  • Fixed: idled shutdown on platforms without pselect (thanks Thomas Jarosch)
  • Fixed: autocreate_sieve now uses sievedir setting correctly
  • Fixed bug #3907: cyradm --cadir option is now called --capath, and works (thanks Leena Heino)
  • Fixed bug #3905: fix segfault in all daemons when built with -DUSE_SETPROCTITLE
  • Fixed: pop3d no longer applies plaintextloginpause to TLS connections
  • Fixed bug #3866: lmtpd now consults local mailboxes.db first, before mupdate master (thanks Michael Menge)

Debian patches

A number of patches from Debian’s repository have been merged. Thanks to the various developers who contributed them to the Debian project, and to Ondřej Surý for collating and sending them upstream.

Changes to the Cyrus IMAP Server since 2.5.5

New imapd.conf options

  • tls_required (default: 0). Set this to 1 to require a TLS session for ALL authentications, not just plain ones (thanks Carlos Velasco)

New cyradm options

  • --tlskey keyfile: use certificate with keyfile to authenticate with server
  • --notls: disable StartTLS negotiation
  • --cafile cacertfile: Use CA certificate file to validate server certificate
  • --cadir cacertdirectory: Use CA certificate directory to validate server certificate
  • Thanks Leena Heino and Carlos Velasco

Bug fixes

  • Fixed: cyr_synclog checks its arguments more strictly to avoid producing junk sync loc entries
  • Fixed: reconstruct no longer segfaults on failure on Solaris 10 (thanks Marty Lee)
  • Fixed: cyradm metadata implementation cleaned up and output made consistent (thanks Leena Heino)
  • Fixed: timsieved no longer discloses name/version if ServerInfo is Off or Min (thanks Carlos Velasco)

Changes to the Cyrus IMAP Server since 2.5.4

  • Security fix: compiling with --enable-autocreate no longer allows arbitrary mailbox creation
  • Fixed T207: don't segfault on mboxutil -d of MBTYPE_DELETED mailboxes (thanks Chris Stromsoe)
  • Fixed lock management over rename (thanks Thomas Jarosch)
  • Miscellaneous other fixes (thanks Thomas Jarosch)

Changes to the Cyrus IMAP Server since 2.5.3

  • Security fix: handle urlfetch range starting outside message range
  • Fixed bug: better error messages when reading corrupted twoskip databases
  • Fixed bug: treat autocreate_quota_messages:0 as unlimited
  • Fixed T203: make autocreate_quota:0 work as documented

Changes to the Cyrus IMAP Server since 2.5.2

  • Fixed T183: don't crash on login when event notifications are enabled

Changes to the Cyrus IMAP Server since 2.5.1

  • Fixed T179: ptloader should no longer crash in ptsmodule_standard_root_dn
  • Improved consistency of event notification parameters
  • Fixed bug: no longer run out of memory in mupdate with twoskip (mmap leak)
  • Fixed bug: no longer crash on ctl_mboxlist -d for remote mailboxes

Changes to the Cyrus IMAP Server since 2.5.0

  • Fixed: allow SYNC_CRC to be optional, making upgrades easier in future
  • Fixed: XFER deletes source mailbox less aggressively, avoiding data loss under pathological conditions
  • Fixed T163: XFER no longer bails out on header CRC mismatch
  • Fixed T117: now error out silently on non-TLS connections to services with implicit TLS
  • Fixed reconstruct bug: upgrading mailbox format now adds GUIDs to shared folders (Thanks Norbert Warmuth)
  • Fixed T165: xfer no longer fails due to bad version comparison
  • Fixed xfer bug: version 2.5 is now detected properly
  • Fixed T109: XLIST behaviour is now compatible with Outlook 2013 (Thanks Leena Heino)
  • Fixed T116: LIST now correctly handles domains starting with "inbox."
  • Fixed T120: admin users can now SETANNOTATION correctly
  • Fixed T118: imapd no longer crashes when selected mailbox is listed
  • Fixed T156: LMTP no longer incorrectly rejects messages delivered using 'deliver'
  • Fixed T76: lmtpd no longer crashes when delivering to a shared mailbox (Thanks Leena Heino)
  • Fixed quota bug: no longer crash when setting quotas on shared folder hierarchies
  • Fixed compilation problem on Solaris 10 (Thanks Leena Heino)
  • Fixed bug: QuotaChange event notification now always includes maxMessages parameter
  • Fixed bug: event notifications now include paths for shared folders
  • Fixed bug: GETMETADATA now handles mailbox patterns correctly
  • Various fixes to compiling and tool chains
  • cyradm changes:
    • createmailbox command now accepts –specialuse flag if server supports CREATE-SPECIAL-USE
    • listmailbox command now returns special-use attribute if server supports SPECIAL-USE
    • listmailbox command now accepts –specialuse flag to list only mailboxes with special-use attribute
    • cyradm now uses LIST and REMOTE rather than RLIST if server supports LIST-EXTENDED
    • mboxconfig now accepts –private flag to switch from default shared to private version of an annotation
    • getmetadata: new command
    • setmetadata: new command
    • Cyrus::IMAP::Admin::getinfo now returns a different data structure to support the above
    • Cyrus::IMAP::Admin new ACL flag for modifying annotations

Changes from 2.4 to 2.5

Changes to the Cyrus IMAP Server since 2.4.17-caldav-beta10

  • Properly do time range filtering on a recurring event where the recurring component isn't the first component in the iCalendar stream.
  • Properly do time range filtering on an uncompleted task with no due time.
  • Added short-circuits to calculation of recurring event time span.
  • Faster free/busy calculation for non-recurring events.
  • Added caldav_mindatetime and caldav_maxdatetime options.

Changes to the Cyrus IMAP Server since 2.4.17-caldav-beta9

  • DAV DB changes now occur in the mailbox API which means that replication works for calendars and addressbooks.
  • IMAP XFER is now based on replication.
  • Added support for free/busy query URL to CalDAV.
  • Authentication for GET/HEAD requests is now done on-demand so that free/busy queries and/or calendar subscriptions can be done anonymously (subject to ACL).
  • Added support for VAVAILABILITY, VPOLL, RSCALE to CalDAV based on current drafts (requires libical from git).
  • Updated http_timezone.c to be compliant with current draft.
  • Numerous other CalDAV fixes/enhancements.

Changes to the Cyrus IMAP Server since 2.4.17-caldav-beta8

  • Fixed bug in parsing of Accept header (now accepts */* and type/*).
  • Fixed telemetry logging bug (old garbage appearing in log).
  • Added a workaround for the DELETE bug in MacOS X 10.9.0 Calendar client.

Changes to the Cyrus IMAP Server since 2.4.17-caldav-beta7

  • Added Timzone Service module along with associated admin tools (ctl_zoneinfo, vzic).
  • Added support for accepting/returning jCal (requires Jansson) and xCal data wherever iCalendar data is allowed.
  • Proxied responses (including chunked) are now piped to client rather than being buffered and forwarded.
  • Better handling of COPY/MOVE between backends (including LOCKs).
  • Fixed "annotation truncation" bug where the largest allowed annotation value was slightly less than 4k (solves problem reading CalDavZAP settings).
  • GET on ./well-known now returns a list of /.well-known/ URLs on the server.
  • Added support for X-HTTP-Method-Override header in POST requests.
  • Added replacement functions for those not present in libxml2 < v2.8.0
  • Plugged a few more memory leaks found by Valgrind.

Changes to the Cyrus IMAP Server since 2.4.17-caldav-beta6

  • Plugged several memory leaks found by Valgrind
  • Less verbose reconnect communication between frontend and backend
  • GET on calendar-home-set now returns a list of subscribe-able calendars
  • Auto-provisioning of calendars/addressbooks now works via a frontend proxy
  • Fixed several conformance bugs detected by CalDAVTester
  • Added support for optionally adding Content-MD5 header to responses (see httpcontentmd5 option)
  • Fixed time-based queries for components other than VEVENT

Changes to the Cyrus IMAP Server since 2.4.17-caldav-beta5

  • RSS module now produces Atom 1.0 output rather than RSS 2.0 (we prefer IETF standards)
  • PROPFIND/REPORT allprop/propname requests are now supported
  • unixhierarchysep is now supported by all HTTP modules
  • Completely rewrote write_body() - Range requests are now supported on non-chunked Content-Encoded data
  • Added cache control response headers where appropriate to make Redbot happy
  • Fixed handling of telemetry log file descriptors and truncation
  • Allow GET on calendar collections for "exporting" entire calendar
  • Fixed POST on calendar collection (add-member)
  • Fixed parsing of calendar-query filter
  • Added several CalDAV/iCalendar validation checks based on CalDAVTester results

Changes to the Cyrus IMAP Server since 2.4.17-caldav-beta4

  • Always verify authorization credentials supplied by the client (a proxy may be reusing an existing connection as a different user)
  • Don't bother supporting Digest qop=auth-int since no clients seem to use it
  • Don't show addressbook mailboxes in IMAP LIST output
  • Plugged leaked memory found by Valgrind
  • Better handling of request/response bodies
  • Added httpprettytelemetry option
  • Added httpallowcors option (Cross-Origin Resource Sharing)

Changes to the Cyrus IMAP Server since 2.4.17-caldav-beta3

  • Plugged leaked memory found by Valgrind
  • Rewrote list_feeds() to not use memmem()
  • OPTIONS method can be used without authentication
  • Better handling of Connection:keep-alive
  • Added httpallowedurls option

Changes to the Cyrus IMAP Server since 2.4.17-caldav-beta2

  • Fixed security bug where a user-agent could access files outside of httpdocroot.
  • Changed annotation entry name scheme to be "/vendor/cmu/cyrus-httpd/<" ns-href ">" prop

Changes to the Cyrus IMAP Server since 2.4.17-caldav-beta1

  • Fixed Bug #3792: Build failures on Solaris 10
  • Path to user's DAV DB will be created, if necessary
  • Fixed bug where calendars and addressbooks were using the same mailbox type flag
  • Fixed [un]signed int / size_t mismatches in formatted output

Changes to the Cyrus IMAP Server since 2.4.17

  • Added httpd service with CalDAV, CardDAV, RSS, and iSchedule modules

Changes to the Cyrus IMAP Server since 2.4.16

  • A bunch of cleanups and fixes to compiling
  • A bunch of sieve cleanups
  • Fixed bug #3691: unixhierarchysep is now obeyed when printing the mailbox name in unexpunge
  • Fixed bug #3718: crashes fetching message parts
  • Fixed bug #3719: pop3 seen update of final message in a mailbox
  • Improved documentation of "proxyservers" option
  • Fixed bug #3737: lost emails in XFER delivery race
  • Fixed bug #3725: inefficient statuscache use in some cases
  • Fixed bug #3484: use of sasl property types (compile fix)
  • Fixed bug #3754: failure to support binary append. This was found by a popular library switching to using binary appends
  • Fixed bug #3735: user prefix searching now works with fulldirhash
  • Fixed bug #3696: can no longer rename the same mailbox twice, which left things in a corrupted state if you caught the race.
  • Fixed bug #3715: using berkeley for mailboxes.db was very broken. It now works.
  • Fixed bug #3733: reconstruct with missing cyrus.index will use file timestamps for internaldate rather than setting it to NOW if internaldate_heuristic is set to standard
  • Fixed bug #3729: better documentation for xlist-* in 2.4.
  • Fixed bug #2717: fetches of individual messages or short ranges no longer need to parse over the entire index.
  • Fixed bug #3742: reconstruct can now fix multiple folders with the same uniqueid again (regression from 2.3) and also sync_client avoids a crash in that broken case.

Changes to the Cyrus IMAP Server since 2.4.15

  • Bug #3651 - 64 bit dirhash breaks existing systems. NOTE this includes a fix to the re-written rehash tool released with 2.4.15

Changes to the Cyrus IMAP Server since 2.4.14

  • Bug #3664, #3665 - Sieve filters don't work if mailbox contains dots
  • Bug #3651 - 64 bit dirhash breaks existing systems. NOTE - this includes a complete rewrite of tools/rehash, making it much simpler and more reliable. Check the usage statement
  • Bug #1228 - mailbox dumps need to dump quotaroots
  • Bug #3613 - CATENATE command returns BADURL
  • Bug #3627 - enabling improved_mboxlist_sort documentation mention subscription files
  • Bug #3661 - Memory leaks in sync_server, nntpd, popd
  • Bug #3621 - quota bug involving nested quota roots
  • Bug #3667 - FLAGS.SILENT needs to return new MODSEQ if QRESYNC enabled

Changes to the Cyrus IMAP Server since 2.4.13

  • Bug #2685 - folder delete and annotations
  • Bug #3381 - tools/rehash script is not 64bit safe
  • Bug #3405 - Cyrus IMAP tls support for ctl_mboxlist
  • Bug #3485 - cyr_expire tries to delete parent directories that are not empty
  • Bug #3582 - Extra LF+SP characters been inserted in the middle of the XML attachments
  • Bug #3598 - lmtp auditlog for murder proxy mode
  • Bug #3623 - OpenBSD (and other platforms without working mmap) multiple bugs
  • Bug #3626 - Renaming a mailbox doesn't remove old folder
  • Bug #3628 - folders with spaces and subfolders with same prefix as parent folder don't show up
  • Bug #3634 - RENAME INBOX no longer works
  • Bug #3635 - cmd_rename() fails to check error codes
  • Bug #3636 - unexpunge locks mailbox until all output is emitted
  • Bug #3637 - imapd and ipop3d in 2.4 no longer log expunge events to syslog
  • Bug #3638 - sessionid logging improvements for murder environments
  • Bug #3640 - LMTP accepts NULL bytes in headers, resulting in incorrect header/mail size in meta-data
  • Bug #3642 - iPhone 5 expects SPECIAL-USE in LIST output
  • Bug #3649 - unable to remove mailbox
  • Bug #3650 - ENVELOPE contains unexpected CRLF
  • Bug #3645 - Ability to delete folder "shared"

Changes to the Cyrus IMAP Server since 2.4.12

  • Bug #3565 - fix gcc compiler warnings - thanks Dilyan Palauzov <dilyan.palauzov@aegee.org>
  • Bug #2685 - rename annots in delayed folder delete. Avoids annotations "reappearing" when a folder is recreated
  • Bug #3566 - actually fix in a backward compatible way. 2.4.12 broke older versions of bison
  • Lots of small cleanups from CMU as they prepared to build RSS into their 2.4 build. Thanks Ken
  • Bug #3591/#3609 - fix crash in mupdate on partition move
  • Bug #3610 - fix replication of partition move
  • Bug #3564 - document the way prefork interacts with multiple network protocols
  • Bug #3586 - allow rename of "\Noselect" if subfolders exist
  • A handful of small cleanups (#3593, #3594, #3595) from David Carter <dpc22@cam.ac.uk>. Very much appreciated
  • Disabled duplicate_check DEBUG level log messages by default. Thanks Philip Prindeville <philipp@redfish-solutions.com>
  • Bug #3608 - log mailbox name in more sync failure cases
  • Bug #3615 - fix proxyd_disable_mailbox_referrals. Thanks Andrew Morgan <morgan@orst.edu>
  • Bug #3611 - fix crash in sync_mailbox_full if expunge fails
  • Backported some nice fixes from master, including safer thread/sort (there were some crashes on bad messages before)
  • Fixed infinite loop on suppress_capabilities with substrings of other capabilities. Ouch.
  • Fixed LIST and LSUB again - this time to make LIST "" "*%" work without breaking other things
  • Bug #3588 - make XFER not break if the wrong server name was used. The start of making murder safer
  • Bug #3603 - tidied up usage of kick_mupdate so it never gets called on standard murder backends
  • Bug #3604 - always suppress the DELETED.* mailbox names, even if delete_mode is immediate. It means a config change or different frontend won't show undeletable mailboxes
  • Bug #3602 - allow UpperCase in service names to work

Changes to the Cyrus IMAP Server since 2.4.11

  • Bug #3150 - fix issue with overview and messages without a References header
  • fixed nntp login with tab and space in password
  • Bug #3501 - be more relaxed about names of DELETED folders
  • Bug #3553 - fix QRESYNC passing to murder backend - thanks alec <alec@alec.pl>
  • Bug #3554 - only show ENABLED response the first time each option is ENABLEd
  • Lots of cleanup of build process and backporting of APIs
  • Bug #3502 - make configure.in more portable - thanks OBATA Akio <obata@lins.jp>
  • Bug #3533 - add missing break statements in sieve - thanks Thomas Jarosch <thomas.jarosch@intra2net.com>
  • Bug #3550 - support wildcards for ACLS in cyradm - thanks <mark.cave-ayland@siriusit.co.uk>
  • Bug #3556 - print remote server in mbpath - thanks Wolfgang Breyha <wbreyha@gmx.net>
  • Bug #3559 - make XFER work with unlimited quota - thanks Wolfgang Breyha <wbreyha@gmx.net>
  • Bug #3547 - use strconcat() in writefile()
  • fixed a case where skiplist library could write error messages directly to stdout
  • Bug #3545 - fix sign extension in squat_decode_64
  • Bug #3558 - return error if backend doesn't support LIST-EXTENDED
  • Bug #3565 - clean up in preparation for automake
  • fixed incomplete authentication checks in nntpd, reported by Secunia as SA46093 - thanks Stefan Cornelius, Secunia Research

Changes to the Cyrus IMAP Server since 2.4.10

  • fixed replication recovery from different messages at the each end
  • Bug #3489 - fixed quotalegacy handling of prefixes so only exact subfolders match
  • Bug #3498 - fixed deletion of users quota files with unixheriarchysep enabled, thanks Leena Heino
  • Bug #3491 - NOOP and UNAUTHENTICATE for timsieved, thanks Dilyan Palauzov
  • Bug #3492 - better response codes for timsieved, thanks Dilyan Palauzov
  • Bug #3497 - fix cmd syslog from master, thanks Kristof Katus
  • Bug #3503 - compilation of perl libraries on dragonfly and freebsd, thanks OBATA Akio
  • Bug #3451 - allow CC to have spaces
  • Bug #3505 - fix sync_reset, thanks David Carter
  • Bug #3506 - use literal+ for sync_(client|server), thanks David Carter
  • Bug #3300 - use portable function for TCP constants, thanks OBATA Akio
  • Bug #3507 - fix replication recovery with non-delayed expunge, thanks Julien Coloos
  • Bug #3495 - improved duplicate suppression, thanks Kristof Katus
  • Bug #2772/3463 - fixed crashes in THREAD by correcting folding of references headers
  • Bug #3439 - fix ugly syslog message for vacation
  • Bug #3499 - options to disable namespaces to reduce load on big servers with no shared folders. Thanks Olivier ROLAND
  • Changed skiplist to truncate old files after checkpoint, which can save disk space on tmpfs or small ssds when old copies were held open by other processes
  • Made Cyrus more robust against corruption in mailboxes.db data, so it will return an error rather than crashing on invalid entries
  • Fix for CVE-2011-3208, a remotely exploitable buffer overflow in nntpd - thanks Coverity

Changes to the Cyrus IMAP Server since 2.4.9

  • fixed handling of unparsable emails during append (which would cause invalid cyrus.index records otherwise)
  • quota: fix a pile of bugs. #1801, virtdomain support; #2728, slow user delete; #3178, "file name too long" with big mailbox names; #3179, quota -f doubles usage.
  • Bug #3043 - parse multiple groups in headers correctly
  • Bug #3158 - lmtp backend connection timeout
  • Bug #3223 - limit MIME parsing depth to avoid stack overflows
  • Bug #3273 - add SORT=DISPLAY support (but note: still questions about correctness of unicode sorting)
  • Bug #3504 - convert all sieve scripts to \r\n line endings on upload
  • Bug #3402 - options to munge 8bit characters in headers during lmtp delivery to avoid backscatter
  • sync_client: fix broken keepalive TCP options (I doubt anyone ever tried to use it)
  • Bug #3482 - add "-o" option to ipurge to only purge messages with \Deleted flag set

Changes to the Cyrus IMAP Server since 2.4.8

  • fixed crashes in seen handling
  • Bug #3453 - fixed LSUB replication
  • Bug #3442 - allow disabling PCRE if it's buggy at your site
  • Bug #3443 - LSUB response fixes
  • Bug #3448 - XFER error handling (murder)
  • Bug #3437 - fixed regression: quotaroot wasn't being updated on rename
  • Bug #3456 - fixed crash on rename user.foo user.foo without partition change
  • config update: database paths for most databases are now configurable in imapd.conf
  • Bug #3303 - fixed index lock breaking on XFER (thanks Julien Coloos)
  • Bug #3457 - fixed ESEARCH parsing (was breaking iPhones)
  • Bug #3188 - fixed XFER with unlimited quota (thanks again Julien Coloos)
  • Misc other quota fixes (there are still known bugs with the quota system)
  • Bug #3169 - fixed GETQUOTAROOT for domain quotaroots
  • Bug #3465 - fixed compilation with Perl 5.14 (thanks hsk@imb-jena.de, and also thanks to Ondrej Sury who reported it separately)
  • Bug #3464 - fix for sendmail exec failure. This was a nasty one, and sat with a patch for years. Big thanks to Jesús Roncero for the original patch, and to Donald Buczek for re-reporting it.
  • Bug #3467 - compilation fix for stricter compilers
  • Bug #3466 - fix FUD client handling of 64 bit time datatypes
  • Bug #3477 - this is a replay of 3444 and 3446 which only got fixed on master, not in stable (thanks Leena Heino for the patch this time)
  • Bug #3470 - finally fix the underlying logic for LIST/LSUB and children matches, which has been bandaid-fixed a few times in the past few stable releases
  • Bug #3438 - fix authentication (-a option) for deliver command
  • Bug #3431 - actually an enhancement - look for config files in $ENV{CYRUS_PREFIX} first
  • Bug #3430 - fractional days and other units in cyr_expire

Changes to the Cyrus IMAP Server since 2.4.7

  • Bug #3428 - allow charset argument to "thread" to be quoted
  • Bug #3429 - fixed mupdate crash
  • Bug #3404 - had crept back in! Fix LIST "" user properly
  • Bug #3388 - fix reconstruct internaldate flap when file hardlinked with different internaldates
  • Bug #3410 - don't require a partition on murder frontends
  • Bug #3406 - fix compile on FreeBSD
  • Bug #3415 - fix nntpd
  • Bug #3390 - add 'proc_path' config variable
  • Bug #3364 - allow setting unlimited quota through a proxy server
  • Bug #3433 - append '0.' file rather than deleting in reconstruct
  • Fixed bug in reconstruct where a record rewrite lost the cache pointer until you did a SECOND reconstruct (no bug number)
  • Bug #3440 - fixed cyr_expire crash if run with -x

Changes to the Cyrus IMAP Server since 2.4.6

  • Fixed Bug #3357 - lmtpd offering STARTTLS in pre-authorized mode.
  • Fixed Bug #3392 - allowing INBOX.INBOX to be created if the case didn't match
  • Fixed Bug #3404 - incorrect LIST "" "user" response
  • Fixed Bug #3417 - crash on zero-byte quota file
  • Fixed numberous bugs with mailbox upgrades
  • Fixed replication errors, which have been reported many times on the mailing list, but don't have bug numbers.
  • Increated "paranoia" about record ordering in mailbox, which would have detected some bad bugs in replication that caused the infinite runaway mailbox filling reported in 2.4.6 and below
  • Increased syslogging detail about replication issues
  • Fixed reconstruct crash with zero-byte index file
  • Fixed cyradm perl library path finding
  • Fixed incorrect use of LITERAL+ formats in our responses to clients. Unreported, but could be causing wierd hard-to-track-down bugs out there
  • Fixed append immediately on create
  • Upgraded Unicode database to version 6.0
  • Fixed reconstruct crash on folder names with many digits (i.e. ebay auction numbers)
  • Fixed reconstruct crash with file called '0.'
  • Made reconstruct '-n' option actually exist, as advertised in the man page
  • Fixed bug #3423 - STARTTLS plaintext command injection vulnerability
  • Bug #3382 Added "failedloginpause" config option
  • Bugs #3383/3385 Removed some obsolete config options
  • Bug #3389 $confdir/proc not created on the fly
  • Bug #3394 fix imtest parsing of MECHLIST
  • Bug #3399 fix with_ldap option default
  • Bug #3307 fix mbpath crash on remote mailbox
  • Bug #3420 use getpassphrase on Solaris, now passwords over 8 characters long work with cyrus tools
  • Bug #3400 and others - lots of bugs with XFER between different versions in murder clusters fixed, including a bug that caused only mailboxes with zero messages to be rejected for upgrade
  • Bug #3391 fix rename which just moves between partitions
  • Bug #3103 fix imtest using plain authentication when it must not
  • Bug #3426 fix TLS on sockets other than stdin
  • Added support for BDB versions 5 and above

Changes to the Cyrus IMAP Server since 2.4.5

  • Fixed Bug #3370 - corruption on OpenBSD and other systems without a reliable mmap
  • Fixed Bug #3360 - race condition which could lose seen data on XFER with upgrade
  • Lots of documentation updates
  • Fixed Bug #3355 - added an option to suppress items from the capability response (and bug #3356 when the first attempt was buggy)
  • Fixed Bug #3357 - crash when calling ctl_mboxlist on mailboxes with annotations
  • Fixed Bug #3369 - crash when undumping mailbox during XFER
  • Fixed Bug #3361 - shared folders not listing in LSUB "" % - only with unixheirsep and altnamespace
  • Fixed Bug #3362 - "too many open files" when doing XFER of a user with too many sub mailboxes. Makes XFER less "atomic", but now it works, which is good!
  • Fixed Bug #3313 - md5 library usage. Properly this time!

Changes to the Cyrus IMAP Server since 2.4.4

  • Tidy up of the git version number added to the ID response
  • Fixed incorrect time field in date searches (Bug #3339) - thanks Greg Banks for noticing this one
  • Fixed reconstruct crash and other potential issues (Bug #3353) - first reported Paul Dekkers
  • Fixed ACL passing for rename/delete on murder backends (Bug #3342) - first reported by Robert Spellman
  • Fixed corruption of long (>1024 byte) seen records on replica (Bug #3344) - found at FastMail by Bron Gondwana
  • Made all perl utilities use /usr/bin/perl in the #! line (Bug #2275) - reported by Yann Rouillard over 5 years ago!
  • Fixed crash on message with incomplete final boundary (Bug #3345) - found at FastMail by Bron Gondwana
  • Regression: sync_crc was being set to 00000000 on repack - introduced in 2.4.4 (Bug #3347) - first found at FastMail, but also seen at multiple other sites
  • Always print [CLOSED] response when selecting a new mailbox, even if a CONDSTORE enabling command has not been sent (Bug #3352) - reported by Jan Kundrát, author of the Trojita IMAP client
  • Fixed crash with reconstruct -rf and missing mailboxes.db entries (Bug #3351) - reported by Giles Malet
  • Made sync_server report errors earlier if there are extra records on the master which aren't present on the replica (Bug #3355) - thanks to David Carter for finding it and a first pass at a fix
  • Stopped expunges to never-reported-messages being showed (basically if the 'EXPUNGE' command was run, and it expunged a message that the client had never even seen - seriously rare race condition, Bug #3356) - discovered by Bron Gondwana hammering a testbed with Dovecot's imaptest tool
  • Fixed compile with old PCRE (Bug #3358) - found and fixed by Simon Matter
  • Fixed missing quota usage after XFER (Buf #3349) - found by Dave McMurtrie

Changes to the Cyrus IMAP Server since 2.4.3

  • Rewrite index_upgrade to always parse the message files and re-create cyrus.cache, to avoid upgrade upgrade failures where cache errors occured.
  • Fixed sync_reset handling of user deletions
  • Fixed proc file handling of LOGIN and folder unselect
  • use cyrus.expunge file (if still present) to delete bogus records from a failed index upgrade (cause by bugs in earlier version)
  • detect version 2.5 in XFER to support use with master git branch in a murder
  • made pop3 expunge much more efficient
  • handle missing seen file in XFER

Changes to the Cyrus IMAP Server since 2.4.2

  • Many fixes to replication edge case handling
  • Added missing flags to reconstruct
  • Replicate DELETED.user folders in sync_client -u (matches XFER behaviour now)
  • Make sync_client only connect after forking in rolling mode. Fixes two things - ssl crashes due to shared resource conflicts, and also means master will start up even if the replica is not contactable
  • Fixed crash on cyr_expire and ipurge annotation based expiry
  • Many XFER fixes for compatibility across versions:
    • allowing XFER in from delayed_expunge mailboxes
    • allowing XFER back all the way to Cyrus 2.2.12. This was accomplished by adding logic that can generate backwards-compatible older version indexes, and version detection from the imapd banner.
    • correctly fixing seen information for sub-mailboxes on XFER in
  • Multi-target replication. Strictly this is a new feature - there was a broken implementation in 2.4.0, which is how this snuck in to the bugfix release. It's not super-well documented yet, but it works by creating a separate log file for each destination "channel", and then running one sync_client process per channel, so replication can fall behind on one without affecting replication to the other.
  • Fixed some crashes and errors which occured when upgrading and opening corrupted mailboxes
  • Modified AFS ptloader configure options to allow building on more modern systems

Changes to the Cyrus IMAP Server since 2.4.1

  • Fix build on Solaris

Changes to the Cyrus IMAP Server since 2.4.0

  • Fix cyrdump to work with -C for alternate config
  • Change master to process all pending child messages once per loop, which fixes a DoS situation if there is too much message churn in a slower box - thanks to Henrique de Moraes Holschuh <hmh@debian.org>
  • Reconstruct added flags -R, -U, -o, -O to give options handling corrupt or missing files
  • Reconstruct fixed a pile of bugs, including a nasty one which created mailboxes with a UIDVALIDITY of 0
  • Fixed EXPUNGE in murder
  • Fixed LSUB where subscribed mailboxes are on different murder backends
  • New build system using git commit ID rather than CVS date information to uniquely identify a release or development build via the "ID" command. Also changes the CYRUS_VERSION string for builds directly from git.

Changes to the Cyrus IMAP Server since 2.3.x

  • All databases are now default skiplist, and ctl_cyrusdb will automatically convert database type on startup.
  • make_sha1 and make_md5 are removed (replaced by GUID and reconstruct changes)
  • Charset subsystem rewritten - Unicode 5.2 rather than Unicode 2, and UTF-8 support in sieve.
  • Core mailbox handling code largely rewritten with new APIs, CRC checksums, new locking mechanisms, merging of cyrus.index and cyrus.expunge, inclusion of user \Seen flag, and much more.
  • Replication code largely rewritten to provide better performance, consistency checking, and recovery from "split-brain" scenarios.
  • Added support for LIST-EXTENDED IMAP extension. Removed support for deprecated (compile-time) LISTEXT IMAP extension. Based on work by Martin Konold <martin.konold@erfrakon.de>
  • Added support for ESEARCH IMAP extension.
  • Added support for WITHIN extension to IMAP SEARCH.
  • Added support for ENABLE IMAP extension.
  • Added support for QRESYNC IMAP extension.
  • Added support for URLAUTH=BINARY IMAP extension.
  • Removed legacy IMAP[2|3|4] cruft. We now only support IMAPrev1 + extensions.
  • Added support for marking QoS on traffic. (courtesy of Philip Prindeville <philipp@redfish-solutions.com>)
  • Modified user_deny.db code to open database once at service startup time.
  • ... and hundreds of tiny things too numerous to mention in a short change log ...

Changes to the Cyrus IMAP Server since 2.3.17

  • Fix for incomplete authentication checks in nntpd, reported by Secunia as SA46093 - thanks Stefan Cornelius, Secunia Research

Changes to the Cyrus IMAP Server since 2.3.16

  • Fix for CVE-2011-3208, a remotely exploitable buffer overflow in nntpd

Changes to the Cyrus IMAP Server since 2.3.15

  • Added user_deny.db to be able to selectively deny users access to Cyrus services.
  • Added disconnect_on_vanished_mailbox option. See imapd.conf(5) for details
  • Reworked SQL detection code in configure. See install-upgrade.html for more details.
  • Added popuseimapflags option which enables setting and obeying IMAP flags in the POP server.
  • Added optimized method of handling an empty maildrop in pop3d. Requires statuscache to be enabled. (based on work of Cyril Servant <elfejoyeux@gmail.com>)
  • Added annotation_definitions option for specifying external (third-party) annotations. (courtesy of Thomas Viehmann <tv@beamnet.de>)
  • Added sync_compress option to compress replication traffic
  • Added user_folder_limit option to limit the number of folders a non-admin user is allowed to create.
  • Added -x option to cyr_expire to disable expunge
  • Track idle state so a shutdown doesn't leave idled killing random other processes on a busy system
  • Fix missing closedir() - bug #3159 (thanks Simon Matter)
  • Make Cyrus compile with older GCC (thanks Simon Matter)

Changes to the Cyrus IMAP Server since 2.3.14

  • Fixed CERT VU#336053 - Potential buffer overflow in Sieve.
  • Added new cyr_df tool for reporting Cyrus spool partition disk space usage.
  • Fixed a crash when selecting a folder after using the SCAN command
  • Split mupdate_synchronize() into network scarfing and mailbox comparision pieces. This allows us to not lock out the mailboxes.db and mupdate clients while scarfing the UPDATE response, which can be quite time consuming over slow links.
  • Added support for MUPDATE COMPRESS and IMAP COMPRESS commands which help speed up bulk data commands over slow links. Inspired by work of Dave Cridland <dave@cridland.net>
  • Allow frontend servers in a Murder to proxy the CREATE, DELETE, SETACL, SETQUOTA, and GETQUOTA commands for toplevel mailboxes. In order for a frontend to know where to CREATE a toplevel mailbox, either the defaultserver option must be set (ALL new toplevel mailboxes are created on this particular server), or the serverlist option must be set (new toplevel mailboxes are created on whichever server has the most available spool space).
  • Use delayed expunge in ipurge to avoid corrupting cache file and as a bonus make it unexpungable.
  • Run daily tasks at the same time each day instead of exactly 24 hours apart to detect daylight savings changes
  • Fixed Bug #2727 by immediately expunging old messages on INBOX to INBOX.sub rename
  • Fixed incorrect quota calculations on sync_server when replicating unexpunged messages (thanks David Carter)
  • Allow user rename to succeed even if the user is over quota
  • Fixed a skiplist foreach bug and various datatype size issues that caused problems on some 64 bit architectures
  • Added additional logging of mailbox events if condstore is enabled to ensure modseq values are always correctly replicated
  • Fixed "DBERROR db4: environment reference count went negative" by forking idled before opening the database environment.
  • Fixed a squatter bug where any short search term (< 4 characters) would cause squatter to return all messages regardless of the other filters being applied

Changes to the Cyrus IMAP Server since 2.3.13

  • Fixed incompatibility between older ManageSieve clients and newer servers that issue an auto-capability response after AUTH with a SASL security layer.
  • Fixed quota calculation to ignore files not mentioned in the index
  • Correct cache truncation after an aborted append (was leaving empty holes in the cache file>)
  • Fixed ACLs copying when renaming users
  • Fixed TLS session reuse
  • Log more detail about changes done by a reconstruct (indicating that there were problems with the mailbox before hand - mainly as a debugging aid)
  • Ensured that the longest possible named mailbox can still be deleted when delayed delete is enabled by increasing buffer sizes
  • Add configuration option mailbox_default_options allowing (for example) modsequences to be turned on for all new mailboxes
  • Replication:
    • added -R option to sync_client to do rolling replication in the foreground (to run under supervise or similar)
    • made cyr_synclog run as cyrus user if started as root
    • Changed ADDSUB/DELSUB replication to replicate current state rather than log explicit changes, avoiding a bug where if multiple subscription changes happened in one sync run, the replica could be incorrect
    • Changed replication logging related to user creation and mailboxes to ensure correct replication of delayed delete of entire users
    • Always overwrite the seen DB on the replica with the full DB from the master on "setseen_all" to guarantee consistency
    • Sync all mailbox annotations, not just condstore, ensuring mailbox is consistent on both ends (solves POP3_NEW_UIDL bug)

Changes to the Cyrus IMAP Server since 2.3.12

  • Added an experimental "sql" backend for cyrusdb. Currently MySQL, PostgreSQL, and SQLite are supported. See the new sql_* options for details.
  • Added support for IMAP [CAPABILITY] response code to client-side of Murder proxies.
  • Added support for ManageSieve auto-capability response after STARTTLS and after AUTH with a SASL security layer.
  • Made MAXWORD and MAXQUOTED sizes configurable via imapd.conf -- courtesy of Fastmail.fm.
  • Rewrote cyrusdb_quotalegacy.c to use readir() rather than glob.c. This avoids a potential crash due to conflicts between glibc and Heimdal implementations of glob().
  • Added support for fulldirhash to ctl_mboxlist -v.
  • More skiplist transaction fixes -- courtesy of Fastmail.fm.
  • cyr_expire no longer has a default of 0 (zero) for -X and -D. These options must be used explicitly in order to have the desired effect.
  • Added sieve_utf8fileinto option.
  • Added sieve_sasl_send_unsolicited_capability and sieve_sasl_expect_unsolicited_capability options.
  • Several 32/64-bit compatibility fixes.
  • Fixed miscellaneous bugs and build issues.

Changes to the Cyrus IMAP Server since 2.3.11

  • Added statuscache.db to cache IMAP STATUS data which significantly reduces the amount of I/O necessary when neither the mailbox nor \Seen state has changed -- courtesy of Fastmail.fm.
  • Added option to unexpunge to restore messages by time interval -- courtesy of David Carter.
  • Implemented undocumented IMAP SCAN extension, which allows Pine/Alpine to do cross-mailbox searches -- based on work of David Carter.
  • Implemented incremental squat updates (see squatter.8) -- courtesy of David Carter.
  • Fixed major bugs in reconstruct -k implementation -- courtesy of David Carter.
  • Added code to promote transaction safety and to track the lock status of skiplist databases -- courtesy of Fastmail.fm.
  • Added option to mbexamine to compare quota usage in cyrus.index to the actual message file sizes.
  • Allow long lines in imapd.conf to be split across multiple lines by using backslash as a continuation character.
  • The Sieve compiler now translates UTF-8 mailbox names used in fileinto to modified UTF-7 so that messages will be successfully inserted into the mailbox.
  • Use a more appropriate argument with LHLO command.
  • Added serverinfo option to control the information displayed in banner greetings and capability responses.
  • Fixed miscellaneous bugs and build issues.

Changes to the Cyrus IMAP Server since 2.3.10

  • Fixed several skiplist bugs -- courtesy of Fastmail.fm.
  • Add robustness to skiplist recovery -- courtesy of Fastmail.fm.
  • Added support for modification sequences to replication protocol (for CONDSTORE) -- courtesy of David Carter.
  • Fixed delayed delete replication -- courtesy of Fastmail.fm.
  • Allow [un]deleting of user INBOXes (renaming to/from deleted hierarchy) to work when using delayed delete -- courtesy of Simon Matter.
  • Fixed interaction with removal of rights and implicitownerrights.
  • Fixed parsing of single FETCH item when using FETCH modifiers.
  • Prevented SSL_accept() from blocking indefinitely when using TLS/SSL. This should eliminate a lot of hung SSL-wrapped processes.
  • Allow STARTTLS to be used to externally preauth'd LMTP connections.
  • Allow a TLS client certificate to be sufficient authentication for LMTP.
  • timsieved now automatically sends CAPABILITY response after STARTTLS. This code was reintroduced after being mistakenly removed as part of bug #1338.
  • Fixed miscellaneous bugs and build issues.

Changes to the Cyrus IMAP Server since 2.3.9

  • Added support for "delayed" delete, in which mailboxes are renamed to a special admin-only "deleted" hierarchy at the time of the DELETE (hiding them from the client), rather than immediately removing them from the filesystem. This allows messages/mailboxes to be recovered by the admin in case of user error. The mailboxes and messages can be removed at a later time by cyr_expire. The new delete_mode and deletedprefix options in imapd.conf controls whether deletes are "immediate" or "delayed" and the mailbox hierarchy for "delayed" deletes. -- courtesy of David Carter and FastMail.fm.
  • Fixed the special case of RENAMEing an Inbox, so that it doesn't keep the same mailbox uniqueid, thus allowing it to replicate properly (seen state is still preserved).
  • Disabled Nagle's algorithm in sync_client and sync_server to increase the throughput of the replication protocol. -- courtesy of Wes Craig.
  • Added support for a shared \Seen flag on messages (must be enabled on a per-mailbox basis with the /vendor/cmu/cyrus-imapd/sharedseen mailbox annotation.
  • Added -g and -G options to reconstruct -- courtesy of David Carter.
  • Added SETUIDVALIDITY command to the replication protocol -- courtesy of David Carter.
  • Finally fixed (again?) alignment issues on 64-bit SPARC.
  • Changed message GUIDs used by replication to be the SHA1 hash of the messages -- based on work of David Carter and Fastmail.fm.
  • Improve the performance of commands that operate on sequence-sets. The sequence-set is now parsed only once, and the commands operate on a sorted list of seq-ranges.
  • Added new cyr_synclog utility for adding events to the replication log -- courtesy of Fastmail.fm.
  • Added support for PCRE library -- courtesy of Fastmail.fm.
  • Added support for disabling duplicate delivery suppression on a per-folder basis with the /vendor/cmu/cyrus-imapd/duplicatedeliver mailbox annotation -- courtesy of Fastmail.fm.
  • Fixed miscellaneous bugs and build issues.

Changes to the Cyrus IMAP Server since 2.3.8

  • Added support for BDB 4.5 and 4.6.
  • Fixed bug in frontend handling of CREATE for both proxying and referring. -- courtesy of Gary Mills
  • Fixed local deletion during XFER from a unified server. -- courtesy of Gary Mills
  • Fixed XFER bug which prevented sieve scripts from being migrated. -- courtesy of Gary Mills
  • Allow utilities to be run as root (acquiring 'cyrus' uid on-the-fly).
  • Changed the default value of the allowplaintext option to disabled (0).
  • Finally fixed 64-bit alignment problem with HIGHESTMODSEQ.
  • Fixed initialization of UUID subsystem for replication. -- courtesy of Fastmail.fm
  • Added -a option to cyr_expire to ignore to skip annotation check. -- courtesy of Fastmail.fm
  • Set the mtime of synchronized message files to INTERNALDATE (makes reconstruction a little friendlier). -- courtesy of Fastmail.fm
  • Fixed a bug in sync_client which caused it to bail when a message was deleted out from under it.
  • Allow sync_server to accept unauthenticated connections from sync_client on a UNIX socket.
  • Drastically reduced the amount of time it takes for a mupdate slave to synchronize with a master.
  • Added URI contained in the Content-Location header to the BODYSTRUCTURE response (per RFC 3501). -- inspired by Fastmail.fm
  • Fixed flushseenstate bug which was causing unsolicited EXPUNGE responses during FETCH/STORE. -- courtesy of David Carter
  • Added option to ctl_mboxlist to verify the consistency of the mailbox list database and the spool partition(s). See ctl_mboxlist.8 for details.
  • RENAME now copies cyrus.expunge index file as well as expunged message files.
  • Fixed replication of 64-bit quotas. -- courtesy of David Carter
  • Fixed miscellaneous bugs, memory leaks, and build issues.

Changes to the Cyrus IMAP Server since 2.3.7

  • Added improved_mboxlist_sort option which fixes LIST/LSUB problem with characters like '-' and ' ' in mailbox names. See imapd.conf.5 for details
  • Fixed problem with mupdate randomly spinning.
  • Fixed problem with DELETEing mailboxes with split metadata directories.
  • Fixed compatibility problem with RFC 4314 ACLs and mixed 2.2/2.3 environments.
  • Fixed problem with replication and COPYing \Seen messages.
  • Fixed problem with replication and XFER.
  • Added options to reconstruct to preserve cyrus.expunge and to synchronize changes to a replica server.
  • Removed (broken) support for proxying of pipelined IMAP commands.
  • Added new cyr_dbtool utility for manipulating Cyrus databases (courtesy of Fastmail.fm).
  • Better sanity checking of IMAP URLs.
  • Fixed miscellaneous bugs and build issues.

Changes to the Cyrus IMAP Server since 2.3.6

  • Fixed problems with replication and virtual domains.
  • Fixed problems with newer cyrus.index files on 64-bit machines.
  • Added '-p <ssf>' option to services so that PLAIN authentication can be used without TLS in secure environments.
  • Added munge8bit to control whether unencoded 8-bit characters in headers are changed to 'X' or are left alone.
  • Added sieve_allowreferrals option to control whether timsieved issues referrals or proxys traffic to backends.
  • Fixed miscellaneous bugs and build issues.

Changes to the Cyrus IMAP Server since 2.3.5

  • Fixed COPY code so that clients display new messages (added MODSEQ).
  • Fixed imtest to be compatible with SASL 2.1.22.

Changes to the Cyrus IMAP Server since 2.3.4

  • Fixed append/delivery code so that clients display new messages.

Changes to the Cyrus IMAP Server since 2.3.3

  • Added support for BINARY APPEND (including CATENATE). Based on contributions from Tom Esh <esh@lucent.com>.
  • Added support for CONDSTORE (must be enabled on a per-mailbox basis with the /vendor/cmu/cyrus-imapd/condstore mailbox annotation.
  • Fixed bug in reconstruct using bad name for cyrus.header.
  • Fixed bug with replication and default partition.
  • ctl_mboxlist now dumps/undumps the mailbox type flags, making it useful for remote mailboxes.
  • Better logging to facilitate message tracking (Wes Craig <wes@umich.edu>).
  • Implemented CAPABILITY response in banner and after authentication.
  • Fixed miscellaneous bugs and build issues.

Changes to the Cyrus IMAP Server since 2.3.2

  • Fixed broken berkeley (btree) backend.

Changes to the Cyrus IMAP Server since 2.3.1

  • Added more extensive output to arbitron.
  • Allow responses of any length from backend when proxing IMAP/POP3/NNTP traffic.
  • Properly handle timeouts when proxying.
  • Added plaintextloginalert option.
  • Fixed segfault in deliver.
  • Only allow mbpath to be run as Cyrus user.
  • Added nntptimeout option for nntpd.
  • Added berkeley_hash and berkeley_hash_nosync cyrusdb backends (seem to perform better under heavy loads).
  • Added TLS support to cyradm.
  • Fixed miscellaneous bugs and build issues.

Changes to the Cyrus IMAP Server since 2.3.0

  • Updated ACL code to RFC 4314 (separate rights for message delete, mailbox delete, and expunge).
  • Fixed IDLE to use idled for local mailboxes.
  • Fixed miscellaneous build issues.

Changes to the Cyrus IMAP Server since 2.2.x

  • Added support for "unified" and "replicated" Murders. A Murder no longer has to have discrete frontend and backend servers; any one "unified" server can both proxy and serve local mailboxes (proxy functionality in proxyd and lmtpproxyd has been merged with imapd and lmtpd respectively), or all "replicated" servers can serve the same mailboxes from a shared filesystem. The new mupdate_config option in imapd.conf is used to determine whether a Murder is using a "traditional", "unified" or "replicated" configuration.
  • Ported/rewrote/integrated David Carter's mailspool replication code. Development sponsored by Columbia University.
  • Added support for "delayed" expunge, in which messages are removed from the mailbox index at the time of the EXPUNGE (hiding them from the client), but the message files and cache entries are left behind, to be purged at a later time by cyr_expire. This reduces the amount of I/O that takes place at the time of EXPUNGE and should result in greater responsiveness for the client, especially when expunging a large number of messages. The new expunge_mode option in imapd.conf controls whether expunges are "immediate" or "delayed". Development sponsored by FastMail.
  • Added support to place some/all mailbox metadata files (cyrus.* files) on a separate (probably high-speed) partition. See the new metapartition and metapartition_files options for details. Development sponsored by FastMail.
  • Added support for accessing subfolders of INBOX via POP3. See the new popsubfolders option for details. Development sponsored by FastMail.
  • Added support to lmtpd to do "fuzzy" mailbox matching on user+detail addresses. See the new lmtp_fuzzy_mailbox_match option for details. Development sponsored by FastMail.
  • Added new sieve_extensions option to allow individual Sieve extensions to be enabled/disabled.
  • The Sieve "include" extension is now supported. This also allows for global sieve scripts. See the new sieve_extensions options to enable it.
  • The Sieve "body" extension is now supported. See the new sieve_extensions option to enable it. Development sponsored by FastMail.
  • The $text$ variable for Sieve notify messages is now supported. Development sponsored by FastMail.
  • The MIME structure of a new message destined for multiple recipients is now only parsed once rather than once per delivery, resulting in better performance. Development sponsored by FastMail.
  • Support 64-bit quota usage (both per mailbox and for the entire quotaroot), based on a patch from Jeremy Rumpf. Development sponsored by FastMail.
  • Added new flushseenstate option which causes imapd to immediately flush changes in \Seen state to disk rather than caching them until the mailbox is closed. Enabling this option may fix \Seen state weirdness with MS Outlook, at the expense of performance/scalability. Based on a patch by John A. Tamplin (jtampli@sph.emory.edu).
  • The Sieve "copy" extension is now supported.
  • The IMAP "CATENATE" and "URLAUTH" extensions are now supported.
  • Updated Sieve "vacation" extension to draft-ietf-sieve-vacation-04.
  • Added support for Sieve scripts on shared mailboxes via the /vendor/cmu/cyrus-imapd/sieve annotation.

Changes to the Cyrus IMAP Server since 2.2.13

  • ctl_mboxlist now dumps/undumps the mailbox type flags, making it useful for remote mailboxes.
  • Added sieve_allowreferrals option to control whether timsieved issues referrals or proxys traffic to backends.

Changes to the Cyrus IMAP Server since 2.2.12

  • Allow sieve scripts to be run on shared mailboxes (via sieve annotation).
  • Updated nntpd to be compliant with latest draft (soon to be RFC3977).
  • Updated IMAP UIDPLUS extension to be compliant with latest specification (RFC4315).
  • Performance improvements to quota utility.
  • Fixed possible race condition in IMAP IDLE.
  • Made ptloader runtime configurable.
  • Added more extensive output to arbitron.
  • Allow responses of any length from backend when proxing IMAP/POP3/NNTP traffic.
  • Added plaintextloginalert option.
  • Only allow mbpath to be run as Cyrus user.
  • Added berkeley_hash and berkeley_hash_nosync cyrusdb backends (seem to perform better under heavy loads).
  • Added lastpop mailbox annotation.
  • Added subscribe/unsubscribe support to cyradm.
  • Fixed miscellaneous bugs and build issues.

Changes to the Cyrus IMAP Server since 2.2.11

  • Revert index change which wasn't supposed to make it into 2.2.11

Changes to the Cyrus IMAP Server since 2.2.10

  • Fix possible single byte overflow in mailbox handling code.
  • Fix possible single byte overflows in the imapd annotate extension.
  • Fix stack buffer overflows in fetchnews (exploitable by peer news server), backend (exploitable by admin), and in imapd (exploitable by users though only on platforms where a filename may be larger than a mailbox name).

Changes to the Cyrus IMAP Server since 2.2.9

  • Fix 0 termination in mysasl_canon_user.
  • Check for imap magic plus buffer overflow in proxyd also (CAN-2004-1015).
  • Only send an over quota ALERT on SELECT if the quotaroot is different from the last ALERT, or we haven't sent an ALERT in over 10 min.

Changes to the Cyrus IMAP Server since 2.2.8

  • Change ACLs correctly when renaming a user
  • Do not abandon std{in,out,err} file descriptors; syslog assumes it can use stderr if syslogd isn't running.
  • Clean up imap magic plus to avoid buffer overrun (CAN-2004-1011)
  • Fix lack of bounds checking in PARTIAL and FETCH (CAN-2004-1012, CAN-2004-1013)
  • Do not attempt to reuse a freed connection in lmtpproxyd.
  • Allow login without authentication with -N switch in proxyd.
  • Fix use of xrealloc and fold pointers in lmtpengine.

Changes to the Cyrus IMAP Server since 2.2.7

  • Fix a double-free bug in the notify code
  • Fix a problem with idled and an empty mailbox list

Changes to the Cyrus IMAP Server since 2.2.6

  • Fix handling of PARTIAL command and partial body fetches
  • A large number of portability fixes supplied by Albert Chin <china@thewrittenword.com>
  • Added client_timeout option to control connect() timeouts for proxy code
  • Added popuseacl option
  • Fix a number of issues with the quota -f tool
  • Fix thread safety issue in saslserver()
  • Fix possible stage file leak in append code
  • Fix bugs in handling of MULTIAPPEND introduced in 2.2.3
  • Fixed regression bug in Sieve vacation

Changes to the Cyrus IMAP Server since 2.2.5

  • Fix a bug in the proxy code where a backend connection might get closed twice
  • Improved consistancy checking in chk_cyrus
  • Fix segfault in APPEND code
  • Fix a bug with an interaction between sieve and unixhierarchysep
  • Fix a file descriptor leak in the quotadb code
  • Fix a triggered assertation in service-thread services
  • Add a number of internal consistancy checks to the skiplist code
  • Allow mbpath to handle virtual domains
  • Fix various MANAGESIEVE client authentication issues
  • Other minor fixes

Changes to the Cyrus IMAP Server since 2.2.4

  • Bug fixed in hash table code that could sometimes cause crashes with the quotalegacy database
  • Net-SNMP compatibility
  • Significantly improved com_err detection
  • Assorted minor NNTP improvements
  • Assorted other minor bugfixes

Changes to the Cyrus IMAP Server since 2.2.3

  • Quota now uses the cyrusdb interface (quotalegacy by default).
  • All incoming messages are now staged to disk before locking the destination mailbox (locks are no longer held during a network read).
  • Fixed off-by-one error in fetchnews (articles are no longer skipped).
  • nntpd now uses the Followup-To: header (if exists) instead of the Newsgroups: header when constructing post address(es) and adds them to the Reply-To: header instead of the To: header.
  • Added berkeley_locks_max, berkeley_txns_max and berkeley_cachesize options.
  • Added imapmagicplus option.
  • Substantial work on afspts/ptloader canonicalization code
  • Much improved LDAP ptloader code (no more internal OpenLDAP dependencies)
  • Fixed a number of IPv6 related bugs

Changes to the Cyrus IMAP Server since 2.2.2

  • Berkeley DB 4.2 Support - note that the Cyrus Berkeley enviroment needs to be reset (db_recover) before a Berkeley DB version upgrade or you need to remove all berkeley dbs. Special care needs to be taken when berkley db is used for mboxlist.
  • Runtime configuration of the Cyrus databases. The cyrudb backend used for each database can be specified with an imapd.conf option. NOTE: You MUST convert the database using cvt_cyrusdb BEFORE changing the backend in imapd.conf.
  • Sendmail socket map support (smmapd) for verifying that mailboxes exist and are deliverable before accepting the message and sending it to Cyrus.
  • New userid mode for virtual domains, which does NOT do reverse lookups of the IP address.
  • nntpd now supports the Xref header.
  • nntpd can now use the POST command to feed articles to upstream servers.
  • fetchnews can now be used with NNTP servers which don't support the NEWNEWS command.
  • lmtpd now initializes duplicate.db only when it is necessary (when using Sieve or duplicatesuppression).
  • Sieve now verifies that text strings are valid UTF-8.
  • Sieve now verifies that address tests and envelope tests are done on headers which contain addresses (can be disabled with rfc3028_strict: no).
  • Services will now notice that a new binary has been installed and will restart using the new binary once the existing connection is closed.

Changes to the Cyrus IMAP Server since 2.2.1

  • Major bugfixes in murder altnamespace/unixhierarchysep/virtdomain support (Thanks in large part to work by Christian Schulte <cs@schulte.it>)
  • Improved master process accounting (Henrique de Moraes Holschuh <hmh@debian.org>)
  • Significantly improved message header caching (based in large part on code supplied by David Carter <David.Carter@ucs.cam.ac.uk> from the University of Cambridge)
  • The sieve bytecode format has been updated once more, to correctly handle short-circuiting of the allof and anyof operators
  • Support for warning quota based on absolute mailbox size
  • Correct handling of annotations during XFER operations
  • Simple support for IMAP BINARY extension
  • Support for Automake 1.7 and Autoconf 2.57
  • Support for IMAP initial SASL response (the SASL-IR extension)

Changes to the Cyrus IMAP Server since 2.2.0

  • The improved directory hashing (fulldirhash) is now a runtime configuration option.
  • The netnews.db has been integrated into deliver.db.
  • Full r/w ANNOTATEMORE support, including more annotations that allow the control of operations such as message expiration. ANNOTATEMORE is also always enabled now.
  • expirenews has been replaced by cyr_expire which uses annotations for fine-grained mailbox expiration.
  • squatter can now use annotations for fine-grained mailbox indexing.
  • Many nntpd enhancements including: reader-only and feeder-only modes, support for LIST NEWSGROUPS (via mailbox annotations) and gatewaying news to mail (via mailbox annotations).
  • fetchnews can now authenticate to the remote server.
  • Removed deprecated LAST command from pop3d.
  • Sieve Bytecode is now stored in network byte order, meaning that bytecode files can be freely moved between different platforms
  • Sieve relational extension now working again.
  • Sieve vacation now uses the correct subject.
  • A large number of bugs involving virtual domain support have been fixed, including issues with the Murder, and with Sieve.

Changes to the Cyrus IMAP Server since 2.1.x

  • There have been extensive performance and consistancy changes to the configuration subsystem. This will both ensure greater consistancy between the documentation and the code, as well as a more standard format for specifing service-specific configuration options in imapd.conf. Important changes are detailed here:
    • The tls_[service]_* configuration options have been removed. Now use [servicename]_tls_*, where servicename is the service identifier from cyrus.conf for that particular process.
    • Administrative groups (e.g. admins and lmtp_admins) no longer union, service groups completely override the generic group.
    • lmtp_allowplaintext is no longer a defined parameter and must be specified using the service name of your lmtp process if you require a specific value
  • libcyrus has been split into libcyrus_min and libcyrus, so as to allow sensative applications (such as master) include the least amount of code necessary for operation
  • Virtual domain support. See the virtual domains document for details.
  • Users can now be renamed (even across domains). Note that this is not atomic and weirdness may occur if the user is logged in during the rename. See the allowusermoves option in imapd.conf(5) for details.
  • The db3 and db3-nosync database backends have been renamed to berkeley and berkeley-nosync respectively (to avoid confusion over whether or not db4 is supported).
  • The default mailbox list and seen state database formats have changed to skiplist from Berkeley and Flat, respectively.
  • ptloader is now a regular cyrus service. This has several implications, see install-upgrade.html for more details.
  • NNTP support. Usenet news can now be fed to and read from Cyrus directly via NNTP, without the need for a local news server. See netnews document for details.
  • IPv6 support, provided by Hajimu UMEMOTO <ume@mahoroba.org>
  • Sieve scripts are now compiled to bytecode to allow for faster execution (and lmtpd no longer needs lex or yacc). See install-upgrade.html for more details.
  • The functionality of pop3proxyd has been merged into pop3d. Be sure to update cyrus.conf on your frontend machines accordingly.
  • The functionality of ctl_deliver -E has been moved to cyr_expire -E. Be sure to update cyrus.conf on your machines accordingly.

Changes to the Cyrus IMAP Server since 2.1.14

  • Correct a potential DOS attack in the fud daemon.
  • Arbitron now works again
  • Telemetry logging for mupdate
  • Duplicate Suppression logging for redirect sieve actions
  • A number of bugs in reconstruct have been fixed. also added the -p and -x options
  • Better stubbing out of user_deleteacl
  • No longer log any shutdown() failures
  • Improved IPv6 support (for systems with two getnameinfo implementations)
  • Misc Documentation Improvements

Changes to the Cyrus IMAP Server since 2.1.13

  • Be more forgiving in the parsing of MIME boundary headers, specifically those generated by Eudora where the outer boundaries are substrings of the inner boundaries. This feature can be disabled by enabling the rfc2046_strict option.
  • Allow cyradm to handle aggregate mailbox sets for ACL and DELETE operations.
  • Add a lmtp_downcase_rcpt option to force the lowercasing of recipient addresses (Henrique de Moraes Holschuh <hmh@debian.org>).
  • Include more MIME headers in sieve rejection notices
  • Add an mbexamine command for debugging purposes
  • LMTP will now fatal error if we cannot initialize the duplicate delivery database.
  • Continued audit by Security Appraisers and Bynari
  • Correctly terminate the processes by calling service_abort even on successful exit (helps to fix a db3 lockers problem)
  • Fix some murder+altnamespace/unixhiersep issues
  • Fix imclient's handling of literals.
  • Add support for the windows-1256 character set
  • Don't log 'could not shut down filedescriptor' messages when the socket is already not connected
  • Now include a script to convert sieve script names to the altnamespace format
  • Added a --with-extraident configure option to make it easier to set the extra version information that is compiled into the binary.
  • Minor build fixes.
  • Minor other bug fixes.

Changes to the Cyrus IMAP Server since 2.1.12

  • Add maxfds= option in cyrus.conf
  • "The shutdown() Patch" by Henrique de Moraes Holschuh <hmh@debian.org> and Jeremy Howard <jhoward@fastmail.fm>
  • Now report both built-with and running-with OpenSSL versions
  • Misc other small bugfixes
  • Security Appraisers and Bynari review of the majority of the modules in imap/

Changes to the Cyrus IMAP Server since 2.1.11

  • Master now will forcibly exit if a service is not executable
  • Master now has a daemon mode and pidfile support (-d and -p options)
  • Berkeley DB Configuration methods have changed. Hopefully they're more generic now. You can still use --with-dbdir, or you can use --with-bdb-libdir and --with-bdb-incdir
  • timsieved now handles usernames with dots (when unixhierarchysep is active)
  • tugowar has been removed from the distribution.
  • Squatter now has an option to skip unmodified mailboxes.
  • Properly hash username to remove a user's sieve scripts when their INBOX is removed.
  • Reset output buffer when prot_flush returns EOF.
  • Minor Makefile improvements with use of $(srcdir)
  • Remotepurge improvement for empty mailboxes
  • Fix for AFS overwriting the canonicalized username in ptloader
  • Security audit of imapd.c performed by SecurityAppraisers and Bynari

Changes to the Cyrus IMAP Server since 2.1.10

  • Fixed some potential buffer overflows in the sieve code, as well as a pre-login buffer overflow in the IMAP parsing code.
  • ipurge can now skip flagged messages
  • Fix a problem with the flat backend and tracking new files
  • Fix a problem with the memory pool routines on 64-bit machines

Changes to the Cyrus IMAP Server since 2.1.9

  • support Berkley DB 4.1
  • more portable use of errno throughout
  • timsieved now does telemetry logging
  • libcyrus.a no longer supplies fs_get() and fs_give()

Changes to the Cyrus IMAP Server since 2.1.8

  • Fix a strlcpy() off-by-one error.
  • Better handling of errors in connecting to LMTP servers for deliver and lmtpproxyd.
  • Fix bug in pop3proxyd's pop3s handling.
  • Fix Exim install documentation.

Changes to the Cyrus IMAP Server since 2.1.7

  • Fix a severe locking problem during failed CREATEs
  • Change default locking method to fcntl from flock
  • Don't cleanup the original mailbox during a RENAME while holding the mailbox list lock
  • Quoting fixes in cyradm
  • Small pathname fix in rehash script

Changes to the Cyrus IMAP Server since 2.1.6

  • Correct some minor version number errors.

Changes to the Cyrus IMAP Server since 2.1.5

  • Better locking of the mailbox list during mupdate operations for CREATE and RENAME
  • Permissions fixes for annotations.
  • pop3proxyd now does telemetry logging
  • Cleanup a number of leaks in the murder code
  • Correct semantics of our provided strlcpy(). Fix places where strlcpy() was being used incorrectly.
  • Correct a significant memory leak in the memory pool routines
  • OpenSSL is now handled correctly for the perl modules
  • Small documentation cleanups
  • The normal assortment of small bugfixes

Changes to the Cyrus IMAP Server since 2.1.4

  • Sieve is no longer dependent on duplicate delivery suppression (it still uses the duplicate delivery database however).
  • Sieve now supports draft-segmuller-sieve-relation-02.txt
  • imtest now includes all the functionality previously kept in pop3test, lmtptest, smtptest, and mupdatetest. imtest will notice if it is invoked with one of these names and do the right thing. The -P flag can be used to force a particular protocol. As part of this, the default install location for mupdatetest has changed to be the same as the other test utilities. imtest also includes new MANAGESIEVE functionality (sivtest) as well as the ability to reconnect to the same server multiple times (useful for testing SSL/TLS session caching and DIGEST-MD5 fast reauth).
  • snmpgen generates stubbed out code so we don't waste resources on something that just doesn't work. At some point in time, we'll make it work again as it would be useful to gather aggregate statistics on what commands are being used so we can better tune the server. This change closes bug #1191. New bug 1267 opened to re-enable the feature.
  • Added the chk_cyrus program to help point out missing message files and/or mailboxes
  • ANNOTATEMORE improvements. Server annotation support has been added. We are also now using the /vendor/cmu/cyrus-imapd hierarchy. The "info" command in cyradm now returns annotations for the given mailbox (provided that ANNOTATEMORE support is compiled into the server)
  • The RENAME command has been almost entirely rewritten. Now we rely on mailbox-level locking instead of locking the entire mailboxes file for the duration of the rename. ctl_cyrusdb -r now also cleans up "reserved" mailboxes that may appear in the event of a crash.
  • ctl_mboxlist can now dump only a particular partition
  • The configuration subsystem now uses a hash table to speed up lookups of options. Additionally, the hash table implementation has been updated to possibly take advantage of memory pools.
  • Many bugfixes related to the Cyrus Murder. Includes improvments to subscription handling as well as correct merging of seen state on mailbox moves.
  • Can now configure an external debugger (debug_command option in imapd.conf.
  • Misc. autoconf-related fixes (most notably those related to sasl_checkapop and O_DSYNC).
  • Misc. locking-related fixes.
  • Security fixes related to handling large literals in getxstring(), as well as correct usage of layers in timsieved.

Changes to the Cyrus IMAP Server since 2.1.3

  • All "MAIL" and "SIEVE" notifications are now handled by notifyd which is a daemon that supports multiple notification methods. The mailnotifier and sievenotifier options have been added to /etc/imapd.conf to configure notifications. (Ken Murchison)
  • Many feature enhancements and bugfixes for the Cyrus Murder. The code now supports live (but not transparent) moving of mailboxes from one server to another.
  • Some warning fixes.
  • fdatasync() is no longer required.
  • Fixed a bug in imap/append.c that would show itself if a message was being delivered to five or more different partitions.
  • Deliveries now don't create a redudant temporary file using tmpfile(); the staging directory is used instead. (Ken Murchison)
  • Fix a possible crashing bug in squatter. (Ken Murchison)
  • Deleting a user now also removes their Sieve scripts.
  • cyrusdb_skiplist: release locks during iteration. Should prevent denial of service attacks and possibly increase performance.
  • cyrusdb_skiplist: introduce a new mode using O_DSYNC writes which is possibly faster on Solaris. Currently off (it seems to hurt performance on Linux).
  • master has preliminary code to avoid forking storms.
  • sieveshell should now loop through all available SASL mechanisms before conceding defeat.
  • sieveshell can now upload a file to a different name.

Changes to the Cyrus IMAP Server since 2.1.2

  • fud now runs from the Cyrus master process; more generally, the Cyrus master process can deal with UDP services. (Amos Gouaux, amos@utdallas.edu)
  • Sieve has been updated to be compliant with RFC 3028 and draft-martin-sieve-notify-01. All notify actions and any fileinto and/or redirect actions using stringlists will have to be updated/changed.
  • added cvt_cyrusdb for quick conversions between different cyrusdb backends.
  • fixed a bug in the Sieve header cache, where legal header names were being rejected.
  • many Murder-related fixes
  • suppress a bogus TLS session reuse DBERROR message
  • make the list of acceptable TLS ciphers configurable in /etc/imapd.conf
  • cyrusdb_skiplist fixes; it's now suitable for using in production environments though there are still performance problems outstanding

Changes to the Cyrus IMAP Server since 2.1.1

  • now compatible with Berkeley DB4 (Larry M. Rosenbaum, lmr@ornl.gov)
  • timsieved now supports proxying via loginuseacl (Amos Gouaux, amos@utdallas.edu)
  • Sieve vacation now does a case-insensitive comparison of :addresses
  • Warning-related bug fixes from Henrique de Moras Holschuh hmh@debian.org
  • automatic archival of db3 files so that filesystem backups are always consistent (Ken Murchison, ken@oceana.com)
  • added a skiplist database backend, still needs more testing
  • further work on the Cyrus Murder
  • fixed bug in remotepurge dealing with mailboxes with characters that need to be escaped inside quoted-strings
  • Cyrus::IMAP::Admin now supports referrals
  • cyradm, via Cyrus::IMAP::Shell, now can remove quotaroots
  • timsieved, sieveshell, and the MANAGESIEVE protocol extended with referrals

Changes to the Cyrus IMAP Server since 2.1.0

  • now compatible with Cyrus SASL 2.1.0
  • fixed a problem with LMTP AUTH and unix domain sockets
  • make deleting users faster
  • add a "-n" switch to remotepurge
  • cyradm now does implicit SASL authorization
  • fix for Sieve :matches comparator

Changes to the Cyrus IMAP Server since 2.0.16

  • migrated to SASLv2 (Rob Siemborski)
  • altnamespace: it is now possible to display user mailboxes as siblings to the INBOX at the top-level (Ken Murchison)
  • unixhierarchysep: it is now possible possible to use slash as the hierarchy seperator, instead of a period. (Ken Murchison, inspired by David Fuchs, dfuchs@uniserve.com)
  • SSL/TLS session caching (Ken Murchison)
  • support for IMAP CHILDREN & LISTEXT extensions (Ken Murchison, work in progress)
  • check recipient quota & ACL at time of RCPT TO: in lmtpd (Ken Murchison)
  • support for LMTP STARTTLS & SIZE extensions (Ken Murchison)
  • unified deliver.db, using cyrusdb interface, hopefully improving concurrency and performance (Ken Murchison)
  • fixed STORE FLAGS () bug (Ken Murchison)
  • fixed SEARCH SUBJECT vs. SEARCH HEADER SUBJECT bug (Ken Murchison)
  • users without an INBOX can have subscriptions (Ken Murchison; noticing a trend here?)
  • added cyrusdb_db3_nosync backend, used for duplicatedb and session cache, to postpone non-critical writes. (Ken Murchison)
  • support for STARTTLS and AUTH=ANONYMOUS for timsieved (Ken Murchison)
  • do setgid and initgroups in master (as urged by several people)
  • added more config info to IMAP ID (in a vain attempt to improve debugging)
  • configure now checks for DB3.3
  • SQUAT (Rob O'Callahan, roc@cs.cmu.edu)
  • change SEARCH HEADER x to SEARCH x utilizing internal cache where possible (Rob O'Callahan, roc@cs.cmu.edu)
  • an improved directory hashing option (Gary Mills, mills@cc.UManitoba.CA)
  • use of EGD for SSL/TLS (Amos Gouaux, amos@utdallas.edu)
  • separate certs/keys for services (Henning P. Schmiedehausen, hps@intermeta.de)
  • ability to force ipurge to traverse personal folders (Carsten Hoeger, choeger@suse.de)
  • fixed zero quota bugs in cyradm (Leena Heino, liinu@uta.fi)
  • ignore trailing whitespace in imapd.conf
  • Received: header (with TLS and AUTH info)
  • added '-i' switch to sendmail command line for SIEVE reject, redirect and vacation
  • small fixes to notify_unix
  • added "duplicatesuppression" switch to imapd.conf for enabling/disabling duplicate delivery suppression (Birger Toedtmann, birger@takatukaland.de)

Changes to the Cyrus IMAP Server since 2.0.15

  • fixed a longstanding bug in quota that would affect people with unusual top-level hierarchy, fix by John Darrow, John.P.Darrow@wheaton.edu.
  • some important fixes to db3 interface code, by Walter Wong wcw@cmu.edu, prompted by complaints from Scott Adkins adkinss@ohio.edu.
  • fixed some memory leaks in imclient and in the Perl IMAP module, prompted by Toni Andjelkovic toni@soth.at.
  • fixed a longstanding authentication error in the Perl IMAP module, should remove pesky extra Password: prompt.
  • fixed some allocation bugs in the managesieve perl module.

Changes to the Cyrus IMAP Server since 2.0.14

  • fixed memory management bugs in imapd, lmtpd that were being hit due to the connection reuse code and causing subtle and annoying problems.
  • we now clean up better when deleting a user
  • fixed an endian bug in ipurge
  • pop3d now can also reuse processes.
  • fix a bug in imclient that would strike when cyradm specifies a mechanism on the command-line. (SASL mechanism names aren't case sensitive.)
  • fix some bugs in handling SIGHUP in master
  • fix a couple of goofs in Admin.pm

Changes to the Cyrus IMAP Server since 2.0.13

  • fixed a silly bug with reusing SSL connections
  • lmtpd can now service multiple clients in sequence, hopefully improving performance
  • changed how Berkeley db databases are opened, hopefully lessening the chance of deadlock and improving performance
  • fixed a couple of memory leaks
  • lessened the chance of a race condition during index_check()

Changes to the Cyrus IMAP Server since 2.0.12

  • refactored code so less duplication
  • added alternate config file for partial virtual domain support
  • pop3d can now disable USER/PASS commands.
  • STARTTLS now accepts a SSLv23 hello but doesn't allow SSLv23 to be negotiated.
  • imtest no longer buffers to aid use as an automated layer.
  • master now supports maximum number of service processes via the "maxchild" modifier.
  • fixed a bug in the Sieve string lexer.
  • one imapd process can now service multiple clients in sequence, eliminating a large number of forks.

Changes to the Cyrus IMAP Server since 2.0.11

  • portability fixes involving setrlimit()
  • fixed compiler warnings
  • the STARTTLS command will only accept TLSv1 now, not SSLv2/v3. The imaps port is unaffected by this change.
  • timsieved no longer returns garbage strings.

Changes to the Cyrus IMAP Server since 2.0.9

  • some small memory savings
  • the "fud" daemon once again works correctly
  • the IDLE extension now uses signals correctly
  • problems with libwrap have been resolved
  • imapd and pop3d now log connections protected via TLS.
  • efficiency improvements when searching for a particular message-id
  • fixed an envelope-parsing bug affecting SORT and THREAD
  • made RENAME keep the same mailbox uniqueid, preserving seen state across renames
  • STOREing flags to multiple messages in one command is now more efficient
  • RENAME now preserves the ACL
  • LIST is now as efficient as Cyrus v1.6, modulo Berkeley DB issues.
  • Sieve zephyr notifications are now correct.
  • crash in reconstruct now fixed.
  • man pages added for cyrus.conf, master, lmtpd, idled, ctl_mboxlist, and ctl_deliver.
  • master can now listen on specific interfaces
  • master can now reread /etc/cyrus.conf on SIGHUP.
  • timsieved now uses symlinks instead of hard links.

Changes to the Cyrus IMAP Server since 2.0.8

  • remembered to update this file
  • bug in Cyrus::IMAP perl module affecting cyradm's setquota fixed
  • portability fix with socklen_t

Changes to the Cyrus IMAP Server since 2.0.7

  • preliminary implementation of the IDLE extension (Ken Murchison, ken@oceana.com).
  • THREAD=REFERENCES now part of the normal build.
  • tweaks to the installation documentation and suggested Sendmail configuration
  • portability fixes and other small bugfixes
  • added "-a" flag to lmtpd
  • master process can now export statistics about running processes via UCD SNMP AgentX
  • many fixes to Cyrus Murder-related code
  • fixes to perl code, especially the Sieve interface. added an IMSP interface to the perl code, but it still needs work.

Changes to the Cyrus IMAP Server since 2.0.6

  • some number of random static variables eliminated, to save on memory footprint
  • recursive RENAME was a little to eager; fixed. RENAME will also give the client a hint that a sub-RENAME failed. (mostly probably useful for cyradm, but cyradm doesn't take advantage of it yet.)
  • THREAD=X-JWZ has turned into THREAD=REFERENCES (Ken Murchison)
  • DELETE wasn't failing cleanly in database code; fixed.
  • off-by-one bug in seen_db fixed.
  • starting/committing/aborting transactions now logged more correctly in cyrsudb_db3
  • master will now accept port numbers instead of just service names in cyrus.conf. also logs even more verbosely (see bug #115.)
  • libwrap_init() is now inside the loop, since i don't quite understand the semantics of libwrap calls.
  • setquota in cyradm now behaves more sanely (and gives correct usage message).
  • bugfixes to the managesieve client perl api. (still needs work.)
  • small fixes in timsieved.
  • added a "make dist" target so i won't dread releases as much.

Changes to the Cyrus IMAP Server since 2.0.5

  • APPEND now honors the \Seen flag.
  • mailboxes file can once again be a flat text file. (compile-time choice)
  • subscriptions file can be flat text or berkeley db. likewise for seen state.
  • unfortunately, the format of the mailboxes file has changed.
  • implementation of "JWZ" threading, a first pass on the forthcoming THREAD=REFERENCES.
  • bugfixes in libacap.
  • bugfixes in other Murder related functionality.
  • removal of dead code.
  • will now look in CYRUS_PREFIX/etc/imapd.conf if there's no /etc/imapd.conf.
  • more paranoid implementation of ID.
  • more descriptive lmtp errors.
  • finished implementation of LMTP 8BITMIME.
  • fixed minor bugs in pop3d.
  • small test suite for cyrusdb backends added in lib/test/.
  • added -DPERL_POLLUTE to the perl compilation to deal with Perl 5.6.
  • small additions to the Sieve library.
  • As usual, owe lots of thanks to Ken Murchison for his hard work and awesome implementations.

Changes to the Cyrus IMAP Server SINCE 2.0.4

  • Now should work with Berkeley DB 3.1, but does not auto-upgrade 3.0 databases (and, in fact, I haven't written any upgrade software yet).
  • SORT and THREAD should now function correctly.
  • Some configure fixes.
  • Some fixes for possible race conditions in initializing services and database structures.
  • Some non-gcc compile fixes with structure initialization.
  • Some non gcc compile fixes with structure initialization.

Changes to the Cyrus IMAP Server SINCE 2.0.3

  • fixed mbpath and ipurge. Thanks to Alain Turbide for the bug report.
  • configure: removed mmap_private.c; it was buggy, and not worth supporting.
  • configure: improvements in detecting libwrap, typos fixed in detecting libsasl.
  • Merged the acapsieve library into libacap.
  • improvements to the ACAP API.
  • invariant checks added to the skiplist code.
  • bugfix in TCL cyradm.
  • acapmbox.c: bugfixes in handling acap connections.
  • fix the size given for a unix socket address (changes throughout the code), patch thanks to Vladimir Kravchenko, jimson@null.ru.
  • rewrote deliver to use the generic LMTP API in lmtpengine.c. Likewise, implemented the client-side API in lmtpengine.c. (Still need to implement AUTH.)
  • added SORT and THREAD support (Ken Murchison, ken@oceana.com.)
  • In checking an APPEND command, we were rejecting valid system flags and accepting invalid ones.
  • minor bug fixes to proxyd.
  • large amount of debugging code added to target-acap.
  • build fixes to Perl programs.
  • allow plaintext authentication to timsieved.

Changes to the Cyrus IMAP Server in 2.0

  • The mailboxes file is now a transaction-protected Berkeley database.
  • The core delivery process has been moved to lmtpd. deliver is now a simple wrapper to create an LMTP transaction.
  • master process, responsible for spawning services (imapd, lmtpd, etc.) and for routine housekeeping. Optionally, it can use libwrap to allow or deny connections.
  • ACAP (Application Configuration Access Protocol) support for Cyrus Murder: IMAP Aggregator.
  • Sieve enhancements: regular expressions, notifications, automatically setting IMAP flags.
  • SNMP (Simple Network Management Protocol) support for monitoring usage (e.g. number of users logged in) as well as for instrumenting protocol usage (e.g. number of times CREATE has been called).
  • Perl version of cyradm contributed by Brandon Allbery (allbery@ece.cmu.edu). Eventually we expect to transition to the Perl version away from the TCL version.
  • Bugfix in modified UTF-7 processing (for mailbox names). Bugfix in index_searchcacheheader().
  • Implemented the extension MULTIAPPEND.
  • RENAME is now hierarchical.
  • The right that controls whether a mailbox may be deleted is now "c". (It used to be "d".)
  • An additional backend for seen state has been created, seen_db. It stores seen state in a per-user database.

Changes to the Cyrus IMAP Server Since Version 1.6.20

  • Some fixes to the TLS support to gracefully degrade service.
  • Sieve now correctly re-sieves messages that are received with identical message-ids, but different envelopes. It also obeys plus-addressing on keep actions. (Fixes by Ken Murchison, ken@oceana.com.)
  • The server wasn't correctly calculating the percentage of quota used when deciding whether or not to issue a warning.
  • Implemented single-instance store: deliver, when using LMTP, will only store one copy of a message per partition, and hard link it among multiple users. Sites with a large number of partitions could see a performance decrease.

Changes to the Cyrus IMAP Server Since Version 1.6.19

  • Added STARTTLS support; requires OpenSSL.
  • Sieve now uses MDNs to reject messages instead of DSNs, conforming to the latest Sieve specification. (Ken Murchison)
  • The duplicate delivery database expiration (deliver -E) was deleting all entries; fixed.
  • imtest is now a little smarter about parsing the protocol to avoid synchronization errors prior to authentication.
  • timsieved's parser is now written in C; should be no noticeable changes, but should make compiling it much easier.

Changes to the Cyrus IMAP Server Since Version 1.6.16

  • Fix to enclosed message parsing (thanks to John Myers).
  • When trying to skip over non-synchronizing literals during error recovery, the IMAP server never stopped eating. Fixed.
  • Added with-sasldir as a configure option.
  • Fixed a bug in cyradm when it got the CAPABILITY list.
  • Fixed bugs relating to the incomplete SASLfication of deliver.
  • Fixed bugs in deliver relating to duplicate delivery suppression and Sieve vacation functionality.
  • Fixed a memory leak in deliver.
  • When looking for SASL options, imapd wasn't defaulting to the option without the plugin name requesting it. This caused PLAIN authentications to incorrectly fail.
  • Changed the expiration time of pts entries to 3 hours; only affects sites using krb_pts as the authorization method.
  • Fixed some bugs in imclient; mostly affects cyradm.
  • Fixed a bug in the Sieve lexer and improved the usefulness of the Sieve test program.

Changes to the Cyrus IMAP Server Since Version 1.6.13

  • An annoying memory management bug in imclient was fixed and it's efficiency was improved somewhat.
  • Added the sieve client (installsieve) and server (timsieved) for getting sieve scripts onto the server and managing them once they are there.
  • The default Sieve script layout has changed to sievedir/u/user/default; this supports multiple Sieve scripts per user with the ability to switch between them.
  • Fixed the kerberos-to-local-host bug (patch by Greg Hudson, ghudson@mit.edu).
  • Started changes to deliver to support LMTP AUTH.
  • Improved the error messages logged when authentication fails.
  • Fixed a bug dealing with argument processing in the arbitron program.
  • pop3d now correctly supports SASL AUTH.
  • imtest will no longer prompt for authentication or authorization names; instead, it defaults to the current Unix user. Override on the command line.
  • Likewise, cyradm will no longer prompt. It now accepts "-m" to specify what SASL mechanism to use, and the pwcommand option to authenticate should once again work when used non-interactively.

Changes to the Cyrus IMAP Server Since Version 1.6.10

  • Changed the sieve option in the configure script to --disable-sieve.
  • Updated reconstruct and quota to check for hashed imap spool directories correctly.
  • deliver now will not use Sieve if duplicate delivery suppression is disabled. There was also a bug that caused the duplicate delivery database to be checked even if dupelim was disabled.
  • deliver now uses tm_gmtoff if available to check for the local timezone.
  • The default format for reading information from INN has changed. If you use INN to feed imapd news, you must change your "newsfeeds" file to contain
    collectnews!:*:Tf,WO:collectnews
    
  • The dohash script now takes a "-i" option to run interactively and the "-f" option to issue warnings instead of fatal errors.

Changes to the Cyrus IMAP Server Since Version 1.6.1-BETA

  • cyradm should now work with all mechanisms (it now handles empty challenges and responses).
  • Fixed deliver to deal with arbitrarily long headers
  • COPY for non-existent sequence numbers returns NO; this contrasts to UID COPY, which always returns OK.
  • FETCH for non-existent sequence numbers returns NO; this contrasts to UID FETCH, which always returns OK.
  • Fixed a misleading BAD responses to commands that take sequences.
  • Added UIDNEXT untagged response to a SELECT (from draft-crispin-imapv-07.txt).
  • pop3d now correctly passes SASL configuration options to libsasl.
  • imtest now correctly flushes the server's output to the screen.
  • Added more hashing using a simple but stupid algorithm. Now whenever there is a mailbox access, quota access, or subscription access, it goes through a hash function. this is done to help reduce the number of files/directories in any given directory.
  • Added the binary mbpath. Given a mailbox name, this binary will print the filesystem path to that mailbox. This way if you have multiple partitions and hashing turned out, you don't have to spend as many mental cycles figuring out where the actual directory is.
  • deliver now checks sieveusehomedir and sievedir in the config file to determine where to look for sieve scripts.
  • ptloader now has a workaround for afs 3.5.
  • clarified an error message in message.c when an unexpected end of file is encountered.
  • fixed some random memory leaks in deliver.
  • fixed a fairly major bug in prot_fill. it was performing incorrectly when reading only a single character.
  • fixed a bug in how imtest looked for OK or NO.
  • fixed a memory leak in imapd.
  • imapd now allows any user (or member of a group) listed in "proxyservers" to proxy.

Changes to the Cyrus IMAP Server Since Version 1.6.0-BETA

  • fixed stupid bug in imapd
  • fixed sasl/config.c interaction
  • fixed use of stat in imtest

Changes to the Cyrus IMAP Server Since Version 1.5.24

  • ANSI C is now required.
  • imtest's interface has changed, to allow for SASL authentication. Sorry, but it had to happen. It now also includes a timing test (-z) which we use to test the SASL layers.
  • imtest no longer uses a non-synchronizing literal with LOGIN, so it should work against all IMAP servers.
  • The prot layer now uses SASL for encryption and authentication. This changed a large amount of code, and some build procedures.
  • As a side effect of SASL, --enable-static-libraries now doesn't do anything. We are considering compiling cyrus with libtool to change this.
  • Error codes returned by programs have changed, and programs return EX_TEMPFAIL far more than they used to. This is because Sendmail considers most not-EX_TEMPFAIL errors permanent; now, if it may not be permanent, EX_TEMPFAIL is returned. (See lib/exitcodes.h.)
  • Two bugs fixed: UID FETCH's with no messages in range now return OK, not BAD. And an obscure bug in LIST case sensitivity is fixed.

Changes to the Cyrus IMAP Server Since Version 1.5.19

  • Most of the charset.c code (and mkchartable.c code) has been replaced thanks to John Myers).
  • Bug fix in message.c to look up headers in the cache when they're in the cache correctly; thanks to Chris Newman for the fix.
  • Code cleanup here and there (thanks to Bruce Balden).
  • Annoying (and confusing) lines in syslog every time a message was delivered if deliver was compiled using dbm saying that deliver was "unable to fetch entry" have been removed.
  • Content-Disposition lines were being parsed improperly. If they had no optional arguments, they were being ignored as if they were syntactically incorrect. This is fixed, but imapd will continue to serve wrong information unless cyrus.caches are rebuilt (with reconstruct) for any message that was added to the mailbox before this bug was fixed.
  • The arbitron program now takes a mailbox pattern argument for the mailbox to run on. The manpage always said it did anyway.
  • Uninitialized variable fixed in imapd.c with the shutdown file code.
  • Minor tweaks to purify build config.
  • Fix minor memory leak in proc.c where procfname wasn't being free'd.
  • Fix brain fart in auth_krb_pts.c where a CLOSE() was done to a DB handle BEFORE we access the data read from the DB database. This means we were copying free'd memory into the groups list. Note this only affects people using DB, AFS and ptloader.
  • Committed minor syslog log level changes in ptloader and deliver.
  • make distclean now does what it's supposed to.
  • Possibly misnamed experimental --enable-static-libraries switch that tries to do a good job of building binaries with whatever static libraries are availible. If you use this, you do so at your own risk, and if it fails, we will disavow all knowledge of you and your team. Good luck, Jim.
  • Add optional third argument to imtest for it to take input from a file. This is a gross hack.

Changes to the Cyrus IMAP Server Since Version 1.5.14

  • LIST now honors the reference argument.

    This behavior can be turned off by a configuration option imapd.conf--which may be desirable because of certain clients that ask for a "mail directory" setting for IMAP which will now cause problems when it was ignored before. (The default is for the reference argument to be honored.)

  • The arbitron program now takes a mailbox pattern argument for the mailbox to run on. The manpage always said it did anyway.
  • Added --disable-server switch to optionally prevent compilation of server to help sites that just want client libraries (so cyradm and libcyrus can be compiled on remote systems without installing stuff into /usr/cyrus/bin, etc.) For now, the server is still configured in this case, and a Makefile is generated. This could change in future versions.
  • Fixed a mmap leak in index.c in index_search_evaluate that caused problems on complex searches. Thanks to Jeff Schiller for pointing this out. Fixed a potential leak in mboxlist.c that happened if a rename went awry. Thanks to Chris Newman for pointing this out.
  • Fixed a bug in LIST and LSUB code so that user.* mailboxes will be printed on every LIST instead of just the first one.
  • Implemented the POP3 Extension Mechanism, RFC 2449, in order to advertise the capabilities already supported.
  • Fixed a bug in mailbox.c that disallowed MUTF-7 representations of ASCII characters when it shouldn't have. (Thanks to John Myers for providing a fix and to Per Steinar Iversen for telling me that I didn't do it before.)
  • More cleanup the ptloader/auth_krb_pts code. If you use Kerberos and IMSP, you *MUST* pick up cyrus-imspd-v1.5a6 (or newer).
  • A few configure tweaks.
  • Duplicate delivery changes:
    • Split out duplicate delivery elimination to multiple files. This should help reduce the lock contention that normally occurs with this file. To not clutter config_dir, the files will be located in a subdirectory named deliverdb, for example /var/imap/deliverdb. If you don't make this directory, nothing bad will happen (other than duplicate delivery elimination will not work).
    • The time value is now stored as an integer in native byte order as opposed to converting it to a string before it is stored in the database.
    • checkdelivered() now obtains a read lock instead of a write lock when trying to check for duplicates. Only markdelivered() grabs a write lock.
  • Added logic to cause cyradm to abort more cleanly if not given command line arguments in an interactive session. This gets rid of the dreaded application-specific intialization failed messages.

Changes to the Cyrus IMAP Server Since Version 1.5.11

  • The CREATE command now ignores a trailing hierarchy delimiter instead of ignoring the CREATE command.
  • UIDPLUS is now always advertised in CAPABILITY and is always availible. The UIDPLUS extension is a set of optimizations using UID values instead of sequence numbers and is described in RFC 2359.
  • Cyrus no longer rejects messages with 8-bit characters in the headers. Rather than reject the message, characters with the 8th bit set are changed to 'X'. Internationalization in headers is supported by the mechanism specified in RFC 2047 (and RFC 1342).

Changes to the Cyrus IMAP Server Since Version 1.5.10

  • If ENABLE_EXPERIMENT is set, the server no longer claims to support OPTIMIZE-1; instead, it claims to support UIDPLUS. The Getuids command has been removed since it is not in the UIDPLUS document (draft-myers-imap-optimize-03.txt).
  • The checks for Tcl in configure are much smarter. The configure script asks tclsh where its configuration lives, then consults the shell scripts that have that information. This should work with 7.5 or better, which is what the server requires anyway. (All the previous checks to look for Tcl libraries are gone; now, configure runs tclsh and asks it where the Tcl libraries are, then runs the shell scripts that are in that directory. Since the tclConfig.sh script may not be in that directory, it looks in .. as well.)
  • The checks for com_err in configure are a little smarter and look to see if all the pieces are there before trying to use them.
  • Added support for the NAMESPACE extension (if --enable-experiment is supplied).
  • Added a "reject8bit" switch to imapd.conf. If set to "true", messages containing 8-bit-set characters in the headers are rejected (the previous behavior); if set to "false" or left to the default value, messages containing 8-bit-set characters have these characters changed to a constant character ('X').
  • Added the "fud" program. This is an interm hack designed to allow allow finger information to be retrieved for cyrus users. This is experimental and it is not recommend that services be built arround this feature, since it is likely to be removed in a future release of the IMAP server.
  • Bug fix: User defined flags now work properly.

Changes to the Cyrus IMAP Server Since Version 1.5.2

  • Fixed a bug with word alignment on Solaris using Kerberos compiled with Sun's CC. (Several patches were submitted; thanks to everyone who did so.)
  • Patches from John Myers, including more glob fixes.
  • Use the default hash function from DB. Note that this means that the existing delivered.db and ptscache.db is NOT compatible with this release. These files should be removed.
  • Provide two debugging programs that dump the databases: ptdump and dump_deliverdb.
  • Multiple changes to ptloader. added a bunch of flags; let it reauthenticate on its own; added support perl wrapper; added bunch of debugging information/output; bunch of other cleanups
  • The mailboxes file is now closed if it isn't likely to be referenced, hopefully preventing old mailboxes files from hanging around in memory as frequently.
  • Added a patch from Eric Hagberg to work around a possible deadlock condition in mboxlist.c where rename isn't atomic.
  • Patch from John Myers to get rid of cyrus.seen corruption in bsearch_mem.
  • Patch from John Myers and to allow ISO-8859-1 characters in mailbox names.
  • Makedepend still runs, and still generates warnings, but these are squirrled away in makedepend.log.
  • On mailbox delete, the server will no longer try and unlink ".." and "." as we got a report that it seriously breaks one file system (even as non-root).
  • Added some support for Netscape's very misleading "Administrate My Mail" menu option in Communicator. Allows for a URL to be set in imapd.conf for the page to refer users to; needs to be turned on with --enable-netscapehack at compile time to enable it.
  • Bug swap: imtest quotes password with a non-synchronizing literal in order to allow weird characters like ) in passwords. But it doesn't look to see if the server supports non-synchronizing literals.
  • If the file "msg/motd" exists, the first line is now sent to clients upon login.
  • Bug fix: to handle BODY[] properly when fetching news articles (truncation no longer occurs). (thanks to John Prevost)
  • The makedepend supplied should now run on Solaris Intel. (thanks to Chris Newman)
  • Added some hacks to pwcheck.c for Linux and Digital Unix where the default protections on the socket don't allow the cyrus user to read it. (thanks to Lyndon Nerenberg)
  • Bug fix: Flags beginning with \ are system flags and users can only create the defined flags. The code to do this before was confused.
  • The configure scripts and makefiles have some random fixes.
  • Added a contrib directory for reasons of laziness in collecting patches, not all of which should be in the distribution.
  • ptloader can now renew its AFS authentication by reading from a srvtab file.
  • The configure script now looks for a libcom_err and can use an installed one if one exists.
  • Other small bug fixes.

Changes to the Cyrus IMAP Server Since Version 1.5

  • Bug fix: RENAME corrupted mailboxes if they had been EXPUNGEd. (may have only happened with INBOX, which Pine tickles once a month.)
  • Bug fix: auth_newstate now initializes its structures.
  • Bug fix: pop3d.c, a printf was changed to prot_printf.
  • Cyrus now sends X-NON-HIERARCHICAL-RENAME to alert clients that it is not handling RENAME in an IMAP4rev1 compliant manner. This will be fixed in a subsequent release.
  • Bug fix: imclient_autenticate now does resolution on the hostname before authenticating to it. This caused problems when authenticating to an address that was a CNAME.
  • Bug fix: LIST %.% (and other multiple hierarchy delimiter matches) works properly. Several other glob.c fixes are included as well.
  • Bug fix: a fetch of exclusively BODY[HEADER.FIELDS...] should now work properly.
  • Bug fix: reconstruct now considers a nonexistant INN news directory to be empty; this makes reconstruct fix the cyrus.* files in the imap news partition.
  • Added a manpage for imclient.
  • Fixed a few other minor bugs.

Changes to the Cyrus IMAP Server Since Version 1.4

  • Implemented the "IMAP4rev1" protocol commands. (The hierarchical behavior of RENAME, which was added late to the IMAP4rev1 specification, is not implemented.) Changes the minor version number of the cyrus mailbox database format to 1. IMPORTANT: it is necessary to run the command "reconstruct -r" as the cyrus user after upgrading the Cyrus IMAP software from version 1.4 or earlier.
  • If the file "msg/shutdown" exits in the configuration directory, the IMAP server will issue the first line in the file in an untagged BYE message and shut down.
  • Permit SPACE in mailbox names.
  • Permit the "modified UTF-7" internationalized mailbox name convention.
  • "User opened mailbox" messages are now logged at the DEBUG level instead of the INFO level.
  • Added -q (ignore quota) switch to deliver.
  • New "krbck" program for diagnosing common kerberos problems.
  • auth_unix no longer requires users to be in the passwd file.
  • AUTHENTICATE command now reports the protection mechanism in use in the text of the tagged OK response
  • Make MAILBOX_BADFORMAT and MAILBOX_NOTSUPPORTED temporary errors.
  • Use the header cache for SEARCH HEADER
  • Use "unspecified-domain" instead of server's hostname to fill out RFC 822 addresses without the "@domain" part.
  • Make "reconstruct -r" with no args reconstruct every mailbox.
  • The configure script now defaults to using unix_pwcheck instead of unix if the file /etc/shadow exists.
  • The location of the pwcheck socket directory now defaults to "/var/ptclient/". It is controlled by the "--with-statedir=DIR" option, which defaults to "/var".
  • Bug fix: by using an certain address form, one could deliver to a user's mailbox bypassing the ACL's.
  • Bug fix: un-fold header lines when parsing for the ENVELOPE.
  • Delete quota roots when deleting the last mailbox that uses them. Doesn't catch all cases, but should get over 99% of them.
  • Implement plaintextloginpause configuration option, imposes artificial delay on plaintext password logins.
  • Implement popminpoll configuration option, limits frequency of POP3 logins.
  • Implement AFS PT server group support.
  • Remove persistence of POP3 LAST value and remove Status: hack
  • Support the new ACL command set in the IMAP server.
  • Bug fix: Have to initialize reply to 0 in pop3d. Was causing POP3 server to occasionally drop the connection during authentication.
  • Bug fix: The COPY command wasn't issuing a [TRYCREATE] when appropriate for sub-mailboxes of INBOX.
  • Bug fix: Renaming a mailbox wasn't correctly changing its UIDVALIDITY.
  • Bug fix: Renaming a mailbox to itself, in order to move it to a different partition, was not working correctly.
  • Update the AUTH support in pop3d to conform to the latest draft specification.
  • Update cyradm to use Tcl 7.5 instead of Tcl 7.4
  • Re-implement large sections of the netnews support. It no longer requires modifications to INN, as it now expunges the index entries for expired/canceled articles upon select of the newsgroup.
  • Implement newsspool configuration option, for separating the directories for the news spool and the various cyrus.* IMAP server index files.
  • Bug fix: permit empty flag list in APPEND command
  • Bug fix: deal with truncated Date: header values.
  • Bug fix: memory mapping code, deal better with 0-length maps, since mmap() appears to crap out on that boundary condition.
  • Portability fix: if no strerror, have to define NEED_SYS_ERRLIST.
  • Bug fix: used append instead of lappend in cyradmin, preventing use of any port other than IMAP.
  • When the client is streaming its commands, the IMAP server attempts to stream its tagged responses.
  • Modify zephyr support to compile without Kerberos support.
  • Add a bunch of prototype declararations to the code.
  • In deliver, change the MULT support to instead use the LMTP syntax.
  • imclient: support tagged intermediate replies and a default callback.
  • Implement some experimental protocol extensions for optimizing disconnected use resynchronization. Most extensions are disabled by default. Client authors should contact info-cyrus@andrew.cmu.edu if they wish to experiment with these.
  • In Makefiles, change $(AR) to ar -- HPUX make is defective.
  • In deliver, use HAVE_LIBDB to select use of db over dbm
  • Add map_stupidshared mapping module for older versions of Digital Unix. It's not quite as bad as HPUX, but...
  • Bug fix: in imclient.c, don't free NULL pointers and don't call htons() on the output of getservbyname(). Have to abort sending the command if you get a tagged response when sending a literal.
  • The auth_xxx routines now create/take a state argument instead of maintaining internal static state.
  • Solaris mktime() is buggy in some releases. Create and use mkgmtime() for parsing date strings.
  • Message parsing routines now use memory mapping, though they still copy data around in line-sized buffers.

Changes to the Cyrus IMAP Server Since Version 1.3

  • Implemented the "reconstruct -m" command, for reconstructing the mailboxes file. IMPORTANT: it is necessary to run the command "reconstruct -m" as the cyrus user after upgrading the Cyrus IMAP software from version 1.3 or earlier. We recommend you make a backup copy of the mailboxes file in the configuration directory before performing the conversion.
  • Mailbox names are now case sensitive, not case insensitive. "INBOX" is the exception, and is treated as being case-insensitive.
  • Personal mailboxes now appear to their owners as being under the "INBOX." hierarchy. For example, the mailbox "user.bovik.work" appears to the user "bovik" as "INBOX.work". The user may still refer to the mailbox with the name "user.bovik.work".
  • Previously, the code used "anybody" as the name of the group that all users are in, but the documentation used the name "anyone". Changed the code to match the documentation. The name "anybody" will be canonicalized to the name "anyone".
  • The install document now gives different recommended locations for the server databases. The recommended location of the configuration directory changed from "/usr/cyrus" to "/var/imap" and the recommended location of the default partition directory changed from "/usr/spool/cyrus" to "/var/spool/imap". It is NOT necessary to change the locations of these directories when upgrading from version 1.3 or earlier of the Cyrus IMAP server software. If you do wish to change the locations of these directories to match the new recommendations, simply rename the directories and change the appropriate values in your /etc/imapd.conf file.
  • Created a "make install" rule. See the installation document for all the new corresponding configure options. Note the recommended location of the "imapd", "pop3d", and "deliver" programs has changed, this change needs to be reflected in the "inetd.conf" and "sendmail.cf" files.
  • New "login_unix_pwcheck" module and "pwcheck" daemon, for improved shadow password support. See the "pwcheck/README.pwcheck" file in the distribution for details.
  • Renamed the "login_unix_shadow" module to "login_unix_getspnam".
  • Added a mail notification mechanism, using Zephyr.
  • Added a feature to automatically create user IMAP accounts. Controlled by the "autocreatequota" config option.
  • Added the "logtimestamps" config option, for putting timestamp information into protocol telemetry logs.
  • Beefed up the Kerberos checks in Configure to ensure the DES library routines exist.
  • On some systems, the "echo" command with no arguments emits a newline. Changed the installation document to instead use the "true" command to create the "mailboxes" file.
  • Store a redundant copy of a mailbox's ACL in the cyrus.header file, so "reconstruct -m" may later use it as a backup.
  • Had to remove the declaration of tcl_RcFileName for the latest version of Tcl.
  • Make much more extensive use of memory mapping. Replace the binary search module with one that searches a memory mapped area.
  • Replaced the yacc-based RFC822 address parser with a hand-coded one.
  • Replaced the et (error table) libary with a version that doesn't require lex or yacc. Remove the lex/yacc checking from Configure.
  • Safety feature: most programs now refuse to run as root.
  • Bug fix: Issue [TRYCREATE] tag on COPY command when appropriate.
  • Bug fix: The quoted-printable decoder wasn't ignoring trailing whitespace, as required by MIME.
  • Bug fix: Don't spew cascade errors if the server gets an EOF during/after reading an APPEND literal.
  • Bug fix: gmtmoff_gmtime.c was returning results with the wrong sign.
  • Bug fix: imclient_send was appending spaces to %d and %u and the response parser was not handling responses that did not contain a space after the keyword.
  • Bug fix: rmnews wasn't removing some (un-indexed) article files correctly.
  • Completely disabled the dropoff code for now. It will be completely replaced when IMSP integration is implemented
  • Added workaround for the Linux mkdir() problem.
  • In Configure, use a more direct test for a working shared-memory mmap
  • In collectnews, avoid O(n**2) behavior when processing articles that have already expired.
  • Bug fix: append_addseen() would screw up if no messages were previously seen.
  • Added the CMU-specific amssync and cmulocal directories.
  • Use memmove instead of bcopy.
  • Implemented the first pass of SMTP/MULT support in deliver.
  • Added cacheid parameter to auth_setid(), for AFS PT server support.

Changes to the Cyrus IMAP Server Since Version 1.2

  • Fixed bug in character set code that broke text searches. Sites which care about searching headers need to reconstruct their existing mailboxes.

Changes to the Cyrus IMAP Server Since Version 1.1-Beta

  • Add support for UIDVALIDITY special information token.
  • Add syncnews and arbitron programs.
  • Redo duplicate delivery elimination in deliver.
  • Bug fixed: Must re-read files after acquiring a lock. Cannot trust the mtime of a file to increment when writing the file--file could be written to multiple times in the same second.
  • Bug fixed: EXAMINE command should not affect \Recent status.
  • Update the user's \Recent high-water-mark when we report new messages.
  • Portability changes
  • Upgrade to autoconf 2.1
  • Allow privacy to be turned off at compile-time with --disable-privacy configure switch.
  • Fix typo in cyradm preventing "all" from being recognized.
  • Include map_private.c memory mapping module for systems like HPUX which have half-working mmap() implementations.
  • Switch to using UTF-8 for internal search format. Sites which care about internationalized searching of headers need to reconstruct all their existing mailboxes.
  • Fix some errors in the iso-8859-* tables.
  • Add and correct a bunch of case-independence mappings in the character tables.
  • First pass at implementing the STATUS extension; disabled for release.
  • First pass at implementing IMAP/IMSP server integration. Not ready for general use.
  • Add new_cred and free_cred mechanisms to authentication modules.
  • Don't complain when doing "reconstruct -r foo" and foo isn't a mailbox.
  • Add IMAP_QUOTAROOT_NONEXISTENT error code.
  • Bug fix: Avoid divide by zero when quota is zero
  • Bug fix: In an error case of the ACL handling code, we have to restore tab before breaking out of loop.
  • Fix file descriptor leak in quota system.
  • Change a bunch of int variables to unsigned.
  • Better error reporting on reads that end up short.

Changes to the Cyrus IMAP Server Since Version 1.0-Beta

  • Improved installation document.
  • New "cyradm" administrative client.
  • Changed the syslog facility from "local4" to "local6".
  • Removed the renounce setuid check in "deliver". The "deliver" program must now be non-executable by other.
  • Fixed a typo in the parsing of SEARCH DELETED. (This bug constantly got tripped by newer C-clients.)
  • Redesigned the implementation of SEARCH CHARSET.
    Sites that wish to search for non-ASCII characters in the headers of existing mailboxes must run reconstruct on all their mailboxes after upgrading to this version.
  • Added AUTH and KPOP support to the POP3 server.
  • Added search support for the ISO-2022-JP character set.
  • Replaced the search engine with a partial Boyer-Moore algorithm.
  • Special-case optimized searching US-ASCII text.
  • Fixed a bug which caused the message parser to spin-loop on a particular degenerate invalid-MIME case.
  • Fixed a performance bug in the message parser.
  • Tracked last-minute changes to the IMAP4 protocol.
  • Fixed a bug in UNSUBSCRIBE which caused too many subscriptions to be removed.
  • Added a bunch more "configure" options.
  • Ported to HPUX.
  • Fixed a bug in the LIST/LSUB \Noselect code.
  • Fixed bug in the globbing code which caused the "*%" pattern to work incorrectly.
  • Client-side Kerberos support is now conditionalized on HAVE_ACTE_KRB, which is set by configure.
  • Fixed some invalid buffer-alignment assumptions in the Kerberos code.
  • Made the lexers compatible with flex. Configure now looks for and prefers to use flex and bison/byacc.
  • Made the IMAP server check for the existence of the mailboxes file upon startup, in order to give a more informative error message for this common configuration error.
  • Fixed other minor bugs.

last modified: $Date: 2010/04/22 17:29:53 $
Return to the Cyrus IMAP Server Home Page cyrus-imapd-2.5.10/doc/install-virtdomains.html0000644000175000017500000002077613001236020016412 00000000000000 Configuring Virtual Domains

Configuring Virtual Domains

Introduction

Virtual domains is the practice of hosting a service for more than one domain on one server. Cyrus IMAP has the ability to host IMAP/POP mailboxes for multiple domains (e.g., test@example.com and test@example.net) on a single server or Murder.

In order to accomplish this, Cyrus needs to know which domain to look in when a mailbox is accessed. There are two ways in which Cyrus can determine the domain:

  • Fully qualified userid - the client logs in with a userid containing the domain in which the user belongs (e.g., test@example.com or test%example.net)
  • IP address - the server looks up the domain based on the IP address of the receiving interface (useful for servers with multiple NICs or using IP aliasing)

Both of these methods are active if the virtdomains option is set to on (or yes, 1, true) and can be used in conjunction with one another. If the virtdomains option is set to userid, then only the first method is used. Note that a fully qualified userid takes precedence over a domain obtained from the IP address.

Concepts

Perhaps the most important part of this process is to understand the changes in the paradigm.

  • Everyone is in a domain - It's best to think of every user as existing inside a domain. Unqualified users are technically inside the defaultdomain.
  • Names can be qualified - Global admins can reference mailboxes and IDs by qualified names. That is, for any given mailbox command, you can add @domain to the end of the mailbox name. Here are some examples:
    • cyradm> create user.jill@example.net (create a user)
    • cyradm> create user.rick@example.net (create another user)
    • cyradm> setquota user.rick@example.net 50000 (define a quota)
    • cyradm> setaclmailbox user.rick@example.net jill@example.net read (give Jill read access to Rick's mailbox)
    • cyradm> listmailbox *@example.net (list all mailboxes in the example.net domain)
  • Each mailbox exists in only one domain
  • Domains are mutually exclusive - Users only have access to mailboxes within their own domain (intra-domain). The following example will not work: setacl user.jill@herdomain.com rick@hisdomain.com read.
  • Global and Domain admins - The Cyrus virtual domains implementation supports per-domain administrators as well as global (inter-domain) administrators. Domain-specific administrators are specified with a fully qualified userid in the admins option (e.g., admin@example.net) and only have access to mailboxes in the associated domain. Global administrators are specified with unqualified userids.

Quick Start

  1. Add virtdomains: yes to imapd.conf
  2. Add a defaultdomain entry to imapd.conf
  3. Use cyradm (as a global or domain admin) to create mailboxes for each domain.

Configuration

Support for virtual domains is enabled by turning on the virtdomains option in imapd.conf.

When upgrading from a single domain installation to a virtual domain installation, the name of the existing domain (domain of the server hostname) should be specified using the defaultdomain option in imapd.conf. This allows users to continue to access their mailboxes using unqualified userids. For example, if the primary IP address on your server resolves to 'www.xxx.yyy.zzz', then set defaultdomain to 'xxx.yyy.zzz'.

Even for new installations, it is recommended that the "real" domain of the server (domain of its primary hostname), be set to the defaultdomain. See Administrators below for further discussion.

Here is a sample imapd.conf with a minimal set of configuration options.

configdirectory: /var/imap
partition-default: /var/spool/imap
admins: admin rick.admin@hisdomain.com jill.admin@herdomain.net
virtdomains: yes
defaultdomain: exampleisp.net

This example has three domains: exampleisp.net, hisdomain.com, and herdomain.net. admin can administer all three domains, while rick.admin@hisdomain.com and jill.admin@herdomain.net can only administer their respective domains.

Note that everyday users should not be administrators. In the above example, Jill and Rick have separate administrative accounts for their domains.

Multiple IP Addresses

In order to use a multiple IP address configuration, the server must be able to do a reverse lookup on the IP address to determine the hostname of the receiving interface. For example:


192.168.0.1  ->  mail.example.com
192.168.0.2  ->  mail.example.net
192.168.0.3  ->  mail.foo.bar

Once the server obtains the fully qualified hostname of the interface, it removes the localpart (i.e., 'mail') and uses the remainder as the domain for any user that logs in.

This address to hostname mapping would usually be done via DNS, /etc/hosts, NIS, etc. Configuration of the various naming services is beyond the scope of this document.

Delivering mail

To deliver mail to your virtual domains, configure your MTA so that the envelope recipient (RCPT TO) passed to lmtpd is fully qualified with the correct domain.

Configuring Sendmail

In general, follow the basic configuration instructions. Here are a few caveats:

  • It is easiest to use the mailertable to route mail to Cyrus, rather than adding the domain to the local-host-names file ($w). This prevents Sendmail from changing the domain name to the local host name.
    example.com              cyrusv2:/var/imap/socket/lmtp
    
  • You'll have to use the Cyrus mailer in LMTP mode, and you'll have to change the mailer flags so that it provides the full domain while communicating via LMTP. Specifically these changes:
    S=EnvFromSMTP/HdrFromSMTP, R=EnvToSMTP
    

Mail Clients

The only changes you'll need to make to mail clients is to change usernames to the fully qualified domain names, i.e., user@example.com. Note that to support some mail clients, the user%example.com form of userid is also supported. Users in the default domain will not need to reconfigure their clients (as unqualified userids are assumed to be in the default domain).

Administration

The Cyrus virtual domains implementation supports per-domain administrators as well as "global" (inter-domain) administrators. Domain-specific administrators are specified with a fully qualified userid in the admins option (e.g., admin@example.net) and only have access to mailboxes in the associated domain. Mailbox names should be specified in the same fashion as on a single domain configuration.

Global administrators are specified with an unqualified userid in the admins option and have access to any mailbox on the server. Because global admins use unqualified userids, they belong to the defaultdomain. As a result, you CANNOT have a global admin without specifying a defaultdomain. Note that when trying to login as a global admin to a multi-homed server from a remote machine, it might be necessary to fully qualify the userid with the defaultdomain.

Global admins must use mailbox@domain syntax when specifying mailboxes outside of the defaultdomain. Examples (using cyradm):

To create a new INBOX for user 'test' in defaultdomain:


   cm user.test

To create a new INBOX for user 'test' in domain 'example.com':


   cm user.test@example.com

To list all mailboxes in domain 'example.com':


   lm *@example.com


last modified: $Date: 2010/01/06 17:01:29 $ cyrus-imapd-2.5.10/doc/specs.html0000644000175000017500000004651413001236020013522 00000000000000 Cyrus IMAP Server Protocol Specifications

Cyrus IMAP Server Protocol Specifications


IMAP

RFC 3501 Internet Message Access Protocol - version 4rev1
being updated by rfc3501-errata
RFC 1730 Internet Message Access Protocol - version 4
RFC 4314 IMAP4 Access Control List (ACL) Extension
RFC 2087 IMAP4 QUOTA extension
RFC 2088 IMAP4 non-synchronizing literals
RFC 2177 IMAP4 IDLE command
RFC 2192 IMAP URL Scheme
being updated by draft-ietf-lemonade-rfc2192bis
RFC 2193 IMAP4 Mailbox Referrals
RFC 2342 IMAP4 Namespace
RFC 4315 Internet Message Access Protocol (IMAP) - UIDPLUS extension
RFC 2971 IMAP4 ID extension
RFC 3348 IMAP4 Child Mailbox Extension
RFC 3502 IMAP MULTIAPPEND extension
RFC 3516 IMAP4 Binary Content Extension
RFC 3691 Internet Message Access Protocol (IMAP) UNSELECT command
RFC 4466 Collected Extensions to IMAP4 ABNF
RFC 4467 Internet Message Access Protocol (IMAP) - URLAUTH Extension
RFC 4469 Internet Message Access Protocol (IMAP) CATENATE Extension
RFC 4550 Internet Email to Support Diverse Service Environments (Lemonade) Profile
RFC 4551 IMAP Extension for Conditional STORE operation
RFC 4731 IMAP4 Extension to SEARCH Command for Controlling What Kind of Information Is Returned
RFC 4959 IMAP Extension for Simple Authentication and Security Layer (SASL) Initial Client Response
RFC 4978 The IMAP COMPRESS Extension
RFC 5032 WITHIN Search Extension to the IMAP Protocol
RFC 5161 The IMAP ENABLE Extension
RFC 5162 IMAP4 Extensions for Quick Mailbox Resynchronization
RFC 5256 Internet Message Access Protocol - SORT and THREAD Extensions
RFC 5258 Internet Message Access Protocol version 4 - LIST Command Extensions
RFC 5524 Extended URLFETCH for Binary and Converted Parts
draft-daboo-imap-annotatemore ANNOTATEMORE Draft
RFC 5464 The IMAP METADATA Extension
draft-ietf-morg-list-specialuse IMAP SPECIALUSE Draft (And non-standard Google XLIST support)
RFC 5819 IMAP4 Extension for Returning STATUS Information in Extended LIST
RFC 5957 Display-Based Address Sorting for the IMAP4 SORT Extension

POP

RFC 1939 Post Office Protocol - Version 3 (POP3)
RFC 2449 POP3 Extension Mechanism
RFC 2595 Using TLS with IMAP, POP3 and ACAP
RFC 5034 The Post Office Protocol (POP3) Simple Authentication and Security Layer (SASL) Authentication Mechanism
RFC 3206The SYS and AUTH POP Response Codes

NNTP

RFC 3977 Network News Transfer Protocol (NNTP)
RFC 4642 Using Transport Layer Security (TLS) with Network News Transfer Protocol (NNTP)
RFC 4643 Network News Transfer Protocol (NNTP) Extension for Authentication
RFC 4644 Network News Transfer Protocol (NNTP) Extension for Streaming Feeds
RFC 2980 Common NNTP Extensions

SASL

RFC 4422 Simple Authentication and Security Layer (SASL)
RFC 4505 Anonymous Simple Authentication and Security Layer (SASL) Mechanism
RFC 4616 The PLAIN Simple Authentication and Security Layer (SASL) Mechanism
RFC 2195 IMAP/POP AUTHorize Extension for Simple Challenge/Response
being revised by draft-ietf-sasl-crammd5
RFC 2444 The One-Time-Password SASL Mechanism
RFC 2831 Using Digest Authentication as a SASL Mechanism

TLS/SSL

RFC 4346 The Transport Layer Security (TLS) Protocol Version 1.1
RFC 2246 The TLS Protocol Version 1.0
draft-freier-ssl-version3 The SSL Protocol Version 3.0
draft-hickman-netscape-ssl The SSL Protocol Version 2.0

LMTP

RFC 2033 Local Mail Transfer Protocol
RFC 5321 Simple Mail Transfer Protocol
RFC 1869 SMTP Service Extensions
RFC 1652 SMTP Service Extension for 8bit-MIMEtransport
RFC 1870 SMTP Service Extension for Message Size Declaration
RFC 2034 SMTP Service Extension for Returning Enhanced Error Codes
RFC 3463 Enhanced Mail System Status Codes
RFC 3207 SMTP Service Extension for Secure SMTP over TLS
RFC 4954 SMTP Service Extension for Authentication
RFC 2920 SMTP Service Extension for Command Pipelining
RFC 3848 ESMTP and LMTP Transmission Types Registration
draft-murchison-lmtp-ignorequota LMTP Service Extension for Ignoring Recipient Quotas

Sieve

RFC 5228 Sieve: A Mail Filtering Language
RFC 5230 Sieve Email Filtering: Vacation Extension
RFC 5231 Sieve Email Filtering: Relational Extension
RFC 5232 Sieve Email Filtering: Imap4flags Extension
RFC 5233 Sieve Email Filtering: Subaddress Extension
RFC 5260 Sieve Email Filtering: Date and Index Extensions
RFC 5173 Sieve Email Filtering: Body Extension
RFC 3894 Sieve Extension: Copying Without Side Effects
RFC 2298 Extensible Message Format for Message Disposition Notifications (MDNs)
RFC 6131 Sieve Vacation Extension: "Seconds" Parameter
RFC 6609 Sieve Email Filtering: Include Extension
draft-ietf-sieve-regex Sieve Email Filtering -- Regular Expression Extension
draft-melnikov-sieve-imapflags Sieve -- IMAP flag Extension
draft-martin-sieve-notify Sieve -- An extension for providing instant notifications
draft-ietf-sieve-managesieve A Protocol for Remotely Managing Sieve Scripts

HTTP

RFC 7230 Hypertext Transfer Protocol (HTTP/1.1): Message Syntax and Routing
RFC 7231 Hypertext Transfer Protocol (HTTP/1.1): Semantics and Content
RFC 7232 Hypertext Transfer Protocol (HTTP/1.1): Conditional Requests
RFC 7233 Hypertext Transfer Protocol (HTTP/1.1): Range Requests
RFC 7234 Hypertext Transfer Protocol (HTTP/1.1): Caching
RFC 7235 Hypertext Transfer Protocol (HTTP/1.1): Authentication
RFC 2617
being updated by
draft-ietf-httpauth-basicauth-update
draft-ietf-httpauth-digest
HTTP Authentication: Basic and Digest Access Authentication
RFC 4559 SPNEGO-based Kerberos and NTLM HTTP Authentication in Microsoft Windows
[MS-NTHT] NTLM Over HTTP Protocol Specification
RFC 2817 HTTP Upgrading to TLS Within HTTP/1.1
RFC 2818 HTTP Over TLS
RFC 6797 HTTP Strict Transport Security (HSTS)
RFC 7239 Forwarded HTTP Extension
RFC 7240 Prefer Header for HTTP
RFC 4918 HTTP Extensions for Web Distributed Authoring and Versioning (WebDAV)
RFC 3253 Versioning Extensions to WebDAV (Web Distributed Authoring and Versioning)
RFC 3744 Web Distributed Authoring and Versioning (WebDAV) Access Control Protocol
RFC 4331 Quota and Size Properties for Distributed Authoring and Versioning (DAV) Collections
RFC 5397 WebDAV Current Principal Extension
RFC 5689 Extended MKCOL for Web Distributed Authoring and Versioning (WebDAV)
RFC 5995 Using POST to Add Members to Web Distributed Authoring and Versioning (WebDAV) Collections
RFC 6578 Collection Synchronization for Web Distributed Authoring and Versioning (WebDAV)
RFC 4791 Calendaring Extensions to WebDAV (CalDAV)
RFC 6638 Scheduling Extensions to CalDAV
RFC 6352 CardDAV: vCard Extensions to Web Distributed Authoring and Versioning (WebDAV)
RFC 6764 Locating Services for Calendaring Extensions to WebDAV (CalDAV) and vCard Extensions to WebDAV (CardDAV)
draft-ietf-tzdist-service Time Zone Data Distribution Service
draft-ietf-tzdist-caldav-timezone-ref CalDAV: Time Zones by Reference
draft-ietf-calext-rscale Non-Gregorian Recurrence Rules in iCalendar
draft-daboo-calendar-availability Calendar Availability
draft-york-vpoll VPOLL: Consensus Scheduling Component for iCalendar
draft-desruisseaux-ischedule Internet Calendar Scheduling Protocol (iSchedule)
draft-thomson-hybi-http-timeout Hypertext Transfer Protocol (HTTP) Keep-Alive Header
draft-murchison-webdav-prefer Use of the Prefer Header Field in Web Distributed Authoring and Versioning (WebDAV)
caldav-ctag Calendar Collection Entity Tag (CTag) in CalDAV
Brief HeaderMicrosoft 'Brief' header extension

Other

RFC 3656 MUPDATE Protocol (For Cyrus Murder)
RFC 5322 Internet Message Format
RFC 5536 Netnews Article Format
RFC 5537 Netnews Architecture and Protocols
RFC 3656 MUPDATE Protocol (For Cyrus Murder)
RFC 5423 Internet Message Store Events
RFC 4287 The Atom Syndication Format
RFC 5545 Internet Calendaring and Scheduling Core Object Specification (iCalendar)
RFC 5546 iCalendar Transport-Independent Interoperability Protocol (iTIP)
RFC 6047 iCalendar Message-Based Interoperability Protocol (iMIP)
RFC 6231 xCal: The XML Format for iCalendar
RFC 7265 jCal: The JSON Format for iCalendar
RFC 6350 vCard Format Specification
RFC 6376 DomainKeys Identified Mail (DKIM) Signatures
cyrus-imapd-2.5.10/doc/netnews.fig0000644000175000017500000001052113001236020013656 00000000000000#FIG 3.2 Landscape Center Inches Letter 100.00 Single -2 1200 2 6 2400 1875 3600 3900 2 2 0 1 0 7 50 0 -1 0.000 0 0 -1 0 0 5 2550 1875 3450 1875 3450 3600 2550 3600 2550 1875 4 1 0 50 0 0 16 0.0000 4 165 1140 3000 3900 NNTP Peer\001 -6 6 10725 1875 12075 3900 2 2 0 1 0 7 50 0 -1 0.000 0 0 -1 0 0 5 10950 1875 11850 1875 11850 3600 10950 3600 10950 1875 4 1 0 50 0 0 16 0.0000 4 165 1320 11400 3900 NNTP Client\001 -6 6 10425 5550 12375 7650 2 2 0 1 0 7 50 0 -1 0.000 0 0 -1 0 0 5 10950 5550 11850 5550 11850 7275 10950 7275 10950 5550 4 1 0 50 0 0 16 0.0000 4 195 1935 11400 7575 IMAP/POP3 Client\001 -6 6 3525 8325 9375 9600 6 3525 8550 9375 9600 6 3525 8550 9375 9600 6 3675 8775 9225 8925 6 3675 8775 9225 8925 1 3 0 1 4 4 50 0 20 0.000 1 0.0000 3750 8850 75 75 3750 8850 3825 8850 1 3 0 1 2 2 50 0 41 0.000 1 0.0000 4950 8850 75 75 4950 8850 5025 8850 1 3 0 1 1 1 50 0 41 0.000 1 0.0000 6150 8850 75 75 6150 8850 6225 8850 1 3 0 1 5 5 50 0 41 0.000 1 0.0000 7350 8850 75 75 7350 8850 7425 8850 1 3 0 1 31 31 50 0 41 0.000 1 0.0000 8550 8850 75 75 8550 8850 8625 8850 4 0 0 50 0 0 12 0.0000 4 135 465 5100 8925 IMAP\001 4 0 0 50 0 0 12 0.0000 4 135 480 7500 8925 SMTP\001 4 0 0 50 0 0 12 0.0000 4 135 480 8700 8925 LMTP\001 4 0 0 50 0 0 12 0.0000 4 135 480 3900 8925 NNTP\001 -6 4 0 0 50 0 0 12 0.0000 4 135 435 6300 8925 POP3\001 -6 6 4725 9225 8250 9375 2 1 0 1 0 7 50 0 -1 0.000 0 0 -1 0 0 2 4725 9300 5325 9300 2 1 1 1 0 7 50 0 -1 3.000 0 0 -1 0 0 2 7125 9300 7725 9300 4 0 0 50 0 0 12 0.0000 4 135 435 7800 9375 Email\001 4 0 0 50 0 0 12 0.0000 4 135 690 5400 9375 Netnews\001 -6 2 2 0 1 0 7 50 0 -1 0.000 0 0 -1 0 0 5 3525 8550 9375 8550 9375 9600 3525 9600 3525 8550 -6 -6 4 0 0 50 0 0 12 0.0000 4 135 750 3525 8475 LEGEND\001 -6 6 2325 5550 3675 7575 2 2 0 1 0 7 50 0 -1 0.000 0 0 -1 0 0 5 2550 5550 3450 5550 3450 7275 2550 7275 2550 5550 4 1 0 50 0 0 16 0.0000 4 165 1350 3000 7575 SMTP Server\001 4 1 4 50 0 0 12 0.0000 4 180 750 3000 5925 lmtp2nntp\001 4 1 31 50 0 0 12 0.0000 4 180 600 3000 6525 cyrusv2\001 -6 6 6825 3675 7725 6375 2 1 2 1 0 7 50 0 -1 4.000 0 0 -1 0 0 2 6825 4875 7725 4875 2 1 2 1 0 7 50 0 -1 4.000 0 0 -1 0 0 2 6825 4275 7725 4275 2 2 0 1 0 7 50 0 -1 0.000 0 0 -1 0 0 5 6825 3675 7725 3675 7725 6000 6825 6000 6825 3675 2 1 2 1 0 7 50 0 -1 4.000 0 0 -1 0 0 2 6825 5475 7725 5475 4 1 0 50 0 0 16 0.0000 4 225 585 7275 6300 Cyrus\001 4 1 4 50 0 0 12 0.0000 4 180 420 7275 4050 nntpd\001 4 1 31 50 0 0 12 0.0000 4 180 420 7275 4650 lmtpd\001 4 1 2 50 0 0 12 0.0000 4 180 450 7275 5775 imapd\001 4 1 1 50 0 0 12 0.0000 4 180 450 7275 5250 pop3d\001 -6 2 1 0 1 4 7 50 0 -1 0.000 0 0 -1 1 0 2 1 1 1.00 60.00 120.00 3450 5850 6825 4050 2 1 1 1 31 7 50 0 -1 4.000 0 0 -1 1 0 2 1 1 1.00 60.00 120.00 3450 6375 6825 4575 2 1 1 1 5 7 50 0 -1 4.000 0 0 -1 1 1 2 0 0 1.00 60.00 120.00 0 0 1.00 60.00 120.00 2550 6975 1125 6975 2 1 0 1 4 7 50 0 -1 0.000 0 0 -1 1 1 2 0 0 1.00 60.00 120.00 0 0 1.00 60.00 120.00 2550 2775 1125 2775 2 1 0 1 4 7 50 0 -1 0.000 0 0 -1 1 1 2 1 1 1.00 60.00 120.00 1 1 1.00 60.00 120.00 3450 2775 6825 3900 2 1 0 1 4 7 50 0 -1 0.000 0 0 -1 1 1 2 1 1 1.00 60.00 120.00 1 1 1.00 60.00 120.00 7725 3900 10950 2625 2 1 1 1 4 7 50 0 -1 4.000 0 0 -1 1 1 2 1 1 1.00 60.00 120.00 1 1 1.00 60.00 120.00 7725 4050 10950 2775 2 1 1 1 23 7 50 0 -1 4.000 0 0 -1 1 0 2 1 1 1.00 60.00 120.00 10950 7050 3450 7050 2 1 0 1 23 7 50 0 -1 0.000 0 0 -1 1 0 2 1 1 1.00 60.00 120.00 10950 6900 3450 6900 2 1 2 1 0 7 50 0 -1 4.000 0 0 -1 0 0 2 2550 6150 3450 6150 2 1 2 1 0 7 50 0 -1 4.000 0 0 -1 0 0 2 2550 6750 3450 6750 2 1 1 1 1 7 50 0 -1 4.000 0 0 -1 1 0 2 1 1 1.00 60.00 120.00 7723 5188 10948 5863 2 1 0 1 2 7 50 0 -1 0.000 0 0 -1 1 0 2 1 1 1.00 60.00 120.00 7725 5775 10950 6450 2 1 1 1 2 7 50 0 -1 4.000 0 0 -1 1 1 2 1 1 1.00 60.00 120.00 0 0 1.00 60.00 120.00 7725 5625 10950 6300 4 1 5 50 0 0 12 0.0000 4 180 375 1875 7200 relay\001 4 1 5 50 0 0 12 0.0000 4 150 330 7275 6825 post\001 4 1 5 50 0 0 12 0.0000 4 135 510 7275 7275 submit\001 4 1 4 50 0 0 12 0.0000 4 180 1110 1875 3000 feed (IHAVE)\001 4 0 0 50 0 0 24 0.0000 4 330 6990 600 750 Cyrus Email / Netnews component interactions\001 4 1 23 50 0 0 12 0.0000 4 180 465 3000 7050 smtpd\001 4 1 4 50 0 0 12 0.0000 4 180 975 9075 3075 read (POST)\001 4 1 4 50 0 0 12 0.0000 4 180 1110 5175 3075 feed (IHAVE)\001 4 1 4 50 0 0 12 0.0000 4 180 1110 4650 4800 feed (IHAVE)\001 cyrus-imapd-2.5.10/doc/sieve-protocol.html0000644000175000017500000000545713001236020015360 00000000000000 Protocol for Sieve script exchange

Protocol for Sieve script exchange

Please note that this document is not authoritative and may well be out of date; you should look at specs.html for the current authoritative document for the MANAGESIEVE protocol. Note: This is not a standards track protocol. If you decide to base a program upon it you have been warned. This is a simple text-based protocol for getting user sieve scripts onto the (presumably sealed) IMAP server. The requirements for this process are:
  • the user must authenticate to gain access, preferably via a secure SASL mechanism.
  • only valid sieve scripts may be accepted
Additional features provided:
  • the ability to manage multiple scripts on the server with zero or one of them being the "active" sieve script

Types

This is a line-oriented protocol much like [IMAP] or [ACAP]. There are two types: ATOMS and strings, all space ('SP') separated. Strings may be quoted or literal. See [ACAP] for detailed descriptions.
sievename is a string where only certain characters are allowed and it must be at least 1 character long.

Commands

AUTHENTICATE SP string [SP string] EOL
SASL authentication; the parameters are the mechanism and optionally the initial data. Initial data is base64 encoded. The server replies with an OK or NO response, or a base64 string followed by an EOL. Client then replies with a base64 string followed by an EOL, and the procedure is repeated.
NOOP EOL
No side effects. Valid replies: OK or NO.
LOGOUT EOL
Logout: terminates connection. Valid replies: OK or NO.
GETSCRIPT SP sievename EOL
The parameter is the name of the requested script. Returns: string EOL containing the script data. Get the script with name sievename from the server. Valid replies: OK or NO.
PUTSCRIPT SP sievename SP string EOL
Puts sievename with data data onto the server if possible. Valid replies: OK or NO.
SETACTIVE SP sievename EOL
Set the script with the name sievename as the active script. Any other script that was active is no longer. Valid replies: OK or NO.
DELETESCRIPT SP sievename EOL
Delete the script with sievename. Valid replies: OK or NO.
LISTSCRIPTS EOL
Returns zero or more: sievename EOL. Where the active script has a '*' at the end of its name. Valid replies: OK or NO.
cyrus-imapd-2.5.10/doc/install-http.html0000644000175000017500000012037613001236020015027 00000000000000 Cyrus HTTP

Cyrus HTTP (RSS, CalDAV, CardDAV, iSchedule, TimeZone)

Note that the HTTP service and associated modules in Cyrus are still under development. This release should be considered beta quality.

Introduction

Cyrus http service has the ability to:

  • Serve IMAP mailboxes as RSS feeds.
  • Act as a calendar and scheduling (CalDAV) server by using IMAP mailboxes as calendar collections and RFC 5322 messages to store iCalendar data.
  • Act as a contacts (CardDAV) server by using IMAP mailboxes as addressbook collections and RFC 5322 messages to store vCard data.
  • Allow scheduling transactions between separate calendaring and scheduling systems via the iSchedule protocol (currently only used within a Cyrus Murder).
  • Act as a Time Zone Distribution Service by serving iCalendar (VTIMEZONE) data to client systems.
  • Serve static content (such as the RSS feed list template and/or the CalDAV/CardDAV JavaScript clients mentioned below).
Unlike the Apache HTTP Server, Cyrus HTTP is NOT a general purpose HTTP server. Its feature set is limited to what is required to support the facilities listed above.

This document assumes that you are familiar with building and configuring a Cyrus server. If you have not already done so, please read and understand the rest of the installation documentation before continuing. Note: The "Installation" section below augments the "Compiling the IMAP Server" document. The remaining sections assume that your Cyrus server has already been successfully configured.

This document also assumes that you are familiar with RSS, WebDAV, calendaring, and contacts.

Installation

You will need to build Cyrus with the --enable-http configure option. This builds httpd and the associated modules and utilities based on the availability of the prerequisites listed below.

General Requirements

  • Must have LibXML2 installed.
  • Must have a recent SASL release (v2.1.26 or later) in order to support HTTP Digest, Negotiate, and NTLM authentication. Otherwise, only HTTP Basic authentication will be available.
  • Optionally install OpenSSL for HTTPS support.
  • Optionally install Zlib for compression support.

Additional CalDAV / CardDAV Requirements

  • Must have Libical installed.
  • Must have SQLite v3.x (or later) installed.
  • Optionally install Jansson for jCal/jCard support.
  • Optionally install ICU4C for non-Gregorian calendar support, if Libical has support for the RSCALE extension.

Additional iSchedule Requirements

  • Must meet CalDAV requirements above.
  • Must have OpenDKIM with support for iSchedule canonicalization installed (currently requires a CMU patch).

Additional Time Zone Distribution Service Requirements

General Configuration

The Cyrus httpd service is configurable via several options in imapd.conf. Several of those options are discussed in the sections below. Admins should consult the imapd.conf(5) manpage for the full list of options used by the httpd service and its various modules.

The support for RSS, CalDAV, and CardDAV is divided into separate modules which run as part of the Cyrus httpd service. Selection of which module(s) are enabled is done by setting the httpmodules option accordingly. By default, no modules are enabled.

Cyrus httpd also can serve static content, the location of which is set by the httpdocroot option. Any content contained in the specified directory (including sub-directories) will be served as static content only. Cyrus httpd does NOT have the ability to execute any server-side scripts.

HTTP Authentication

As with other Cyrus services, the Cyrus httpd service uses Cyrus SASL to perform its authentication. Cyrus supports the following HTTP authentication schemes: Basic, Digest, Negotiate (Kerberos only), and NTLM. While Basic is available in all versions of SASL, the remaining schemes are only available in Cyrus SASL 2.1.16 (and higher).

Similar to plaintext login commands supported by the other Cyrus services (IMAP LOGIN, POP3 USER/PASS), the Cyrus httpd service determines whether to advertise the HTTP Basic authentication scheme based on the allowplaintext option and whether the client has connected over a TLS protected connection (HTTPS).

The availability of the other HTTP authentication schemes is controlled by the sasl_mech_list option. For Cyrus httpd the DIGEST-MD5, GSS-SPNEGO, and NTLM SASL plugins support the Digest, Negotiate, and NTLM authentication schemes respectively, provided that these plugins are installed on the server.

RSS Module

Configuration

When enabled, the RSS module will default to serving ALL mailboxes to which the authenticated user has access as RSS feeds. The rss_feeds option can be used to limit the set of mailboxes that can be served as RSS feeds. For example, setting rss_feeds to *,!user will serve all shared mailboxes, but no personal mailboxes.

The list of available RSS feeds can be obtained by clients by accessing the /rss/ URL on the Cyrus server. By default, the server will present the list as a simple unordered list in an HTML document. To customize the look and feel of the feed list, the rss_feedlist_template option can be used to point to a HTML template file. This file can utilize Cascading Style Sheets, JavaScript, etc. Any and all content that the template file references MUST reside under the httpdocroot as set above. Consult the imapd.conf(5) manpage for specifics on the required contents of this custom file. Note that for sites running Cyrus Murder, rss_feedlist_template only needs to be set on frontend servers, since only those servers have the complete mailbox list.

CalDAV Module

Configuration

When enabled, the CalDAV module allows Cyrus to function as a calendar and scheduling server. This module uses a subset of the mailbox hierarchy as calendar collections, the toplevel of which is specified by the calendarprefix option. The public calendar hierarchy will reside at the toplevel of the shared mailbox namespace. A user's personal calendar hierarchy will be a child of their Inbox. For example, using the default value for calendarprefix, a calendar named Default for user murch would reside in the mailbox named user.murch.#calendars.Default.

Note that mailboxes in the calendar hierarchies (those under calendarprefix) SHOULD NOT be accessed with an IMAP client as doing so will leave a mailbox in a state unsuitable for CalDAV. To this end, calendar mailboxes will not be returned by Cyrus imapd in response to an IMAP client's request for the available mailbox list, but Cyrus imapd will not otherwise prevent an IMAP client from accessing them.

By default, the CalDAV module will automatically perform scheduling operations when a scheduling object (invite or reply) is stored on or deleted from the server. Support for the calendar-auto-schedule feature can be disabled with the caldav_allowscheduling option.

Administration

Calendar provisioning

The CalDAV module will automatically create the required calendars for a user the first time that the user authenticates to the CalDAV server. Note that the user MUST have an existing IMAP Inbox in order for the calendars to be created.

Calendar access controls

The CalDAV module uses the same access controls as the other Cyrus services. The cyradm(1) tool can be used to adjust ACLs on calendars as needed. The tables below show how the access controls are used by the CalDAV module.


Mapping of IMAP Rights to WebDAV Privileges & HTTP Methods
IMAP right WebDAV privilege HTTP methods
l - lookup DAV:read
(aggregates DAV:read-current-user-privilege-set,
CALDAV:read-free-busy)
GET/HEAD, PROPFIND, REPORT,
COPY/MOVE (on target)
r - read
s - seen
w - write DAV:write-properties PROPPATCH, COPY/MOVE (on target)
i - insert DAV:write-content PUT, LOCK, COPY/MOVE (on target)
p - post CYRUS:add-resource (aggregated under DAV:bind) POST
k - create mailbox CYRUS:make-collection (aggregated under DAV:bind) MKCOL, MKCALENDAR
x - delete mailbox CYRUS:remove-collection (aggregated under DAV:unbind) DELETE
t - delete message CYRUS:remove-resource (aggregated under DAV:unbind) DELETE, MOVE (on source)
e - expunge
a - admin CYRUS:admin
(aggregates DAV:read-acl, DAV:write-acl, DAV:unlock)
ACL, UNLOCK, PROPFIND (DAV:acl only)
9 - free/busy CALDAV:read-free-busy (regular calendar collection only) REPORT (CALDAV:free-busy-query only)
CALDAV:schedule-query-freebusy (Scheduling Inbox only)
CALDAV:schedule-send-freebusy (Scheduling Outbox only)
8 - invite CALDAV:schedule-deliver-invite (Scheduling Inbox only)
CALDAV:schedule-send-invite (Scheduling Outbox only)
7 - reply CALDAV:schedule-deliver-reply (Scheduling Inbox only)
CALDAV:schedule-send-reply (Scheduling Outbox only)


Default WebDAV Privileges by Collection
Collection ACL
Regular Calendar owner - DAV:all + CALDAV:read-free-busy (lrwipkxta9)
anyone - CALDAV:read-free-busy (9)
Scheduling Inbox owner - DAV:all + CALDAV:schedule-deliver (lrwipkxta789)
anyone - CALDAV:schedule-deliver (789)
Scheduling Outbox owner - DAV:all + CALDAV:schedule-send (lrwipkxta789)

Client Setup

Mozilla Lightning

For each calendar that you would like to add to this client, perform the following steps:

  1. Select the "File -> New -> Calendar..." menu option.
  2. Select the "On the Network" option and click Continue.
  3. Select "CalDAV" as the Format.
  4. Enter a URL of the following form as the Location: https://<servername>/dav/calendars/user/<userid>/<calendar>/

Cyrus will auto-provision a calendar with name "Default" which can be used in the URL above.

Apple iCal

This client will autodetect all available calendars on a server. To add a Cyrus server to this client, perform the following steps:

  1. Select the "Calendar -> Preferences" menu option.
  2. Select the "Accounts" tab.
  3. Click the "+" button.
  4. Select "CalDAV" as the Account Type.
  5. Fill in User Name, Password, and Server Address accordingly.
  6. Click Create.

Apple iOS Calendar

This client will autodetect all available calendars on a server. To add a Cyrus server to this client, perform the following steps:

  1. Run the "Settings" app.
  2. Select the "Mail, Contacts, Calendars" menu.
  3. Select the "Add Account..." menu.
  4. Select the "Other" menu.
  5. Select the "Add CalDAV Account" menu.
  6. Fill in Server, User Name, Password, and Description accordingly.
  7. Click Next.

Evolution

This client will autodetect all available calendars on a server. For each calendar that you would like to add to this client, perform the following steps:

  1. Select the "New -> Calendar" menu option.
  2. Select "CalDAV" as the Type.
  3. Fill in Server and User accordingly.
  4. Click "Find Calendars".
  5. Select the desired calendar from the list.
  6. Click "Apply".
  7. Click "OK".

aCal

This client will autodetect all available calendars on a server. To add a Cyrus server to this client, perform the following steps:

  1. Press the Andoid "Menu" button.
  2. Select "Settings".
  3. Select "Servers".
  4. Select "Add Server".
  5. Select "Manual Configuration".
  6. Fill in Username, Password, and User URL (servername) accordingly.
  7. Press "Apply".

CalDavZAP

This client will autodetect all available calendars on a server. To configure this client for a Cyrus server, edit config.js as follows:

  1. Set the href value in the globalNetworkCheckSettings array to a URL of the following form: https://<servername>/dav/principals/user/
    Note that the trailing "/" is REQUIRED.
  2. Set the globalSettingsType option to calendar-home-set
  3. Set any other options as desired (e.g. globalDatepickerFirstDayOfWeek, globalTimeZone).

CardDAV Module

Configuration

When enabled, the CardDAV module allows Cyrus to function as a contacts server. This module uses a subset of the mailbox hierarchy as addressbook collections, the toplevel of which is specified by the addressbookprefix option. The public addressbook hierarchy will reside at the toplevel of the shared mailbox namespace. A user's personal addressbook hierarchy will be a child of their Inbox. For example, using the default value for addressbookprefix, an addressbook named Default for user murch would reside in the mailbox named user.murch.#addressbooks.Default.

Note that mailboxes in the addressbook hierarchies (those under addressbookprefix) SHOULD NOT be accessed with an IMAP client as doing so will leave a mailbox in a state unsuitable for CardDAV. To this end, addressbook mailboxes will not returned by Cyrus imapd in response to an IMAP client's request for the available mailbox list, but Cyrus imapd will not otherwise prevent an IMAP client from accessing them.

Administration

Addressbook provisioning

The CardDAV module will automatically create a default addressbook for a user the first time that the user authenticates to the CardDAV server. Note that the user MUST have an existing IMAP Inbox in order for the addressbook to be created.

Addressbook access controls

Cyrus uses the same access controls for addressbooks as it does for calendars, except that the scheduling rights (7, 8, 9) have no use with addressbooks and are ignored.

Client Setup

Apple Contacts

This client will autodetect all available addressbooks on a server. To add a Cyrus server to this client, perform the following steps:

  1. Select the "Contacts -> Preferences" menu option.
  2. Select the "Accounts" tab.
  3. Click the "+" button.
  4. Select "CardDAV" as the Account Type.
  5. Fill in User Name, Password, and Server Address accordingly.
  6. Click Create.

Apple iOS Contacts

This client will autodetect all available addressbooks on a server. To add a Cyrus server to this client, perform the following steps:

  1. Run the "Settings" app.
  2. Select the "Mail, Contacts, Calendars" menu.
  3. Select the "Add Account..." menu.
  4. Select the "Other" menu.
  5. Select the "Add CardDAV Account" menu.
  6. Fill in Server, User Name, Password, and Description accordingly.
  7. Click Next.

CardDavMATE

This client will autodetect all available addressbooks on a server. To configure this client for a Cyrus server, edit config.js as follows:

  1. Set the href value in the globalNetworkCheckSettings array to a URL of the following form: https://<servername>/dav/principals/user/
    Note that the trailing "/" is REQUIRED.
  2. Set the globalSettingsType option to addressbook-home-set
  3. Set any other options as desired.

Time Zone Distribution Service Module

Configuration

When enabled, the Time Zone module allows Cyrus to function as a Time Zone Distribution Service, providing time zone data to client systems. This module stores time zone data in the zoneinfo/ subdirectory of the Cyrus configuration directory (as specified by the configdir option). The data is indexed by a database whose location is specified by the zoneinfo_db_path option, using the format specified by the zoneinfo_db option.

Administration

This module is designed to use the IANA Time Zone Database data (a.k.a. Olson Database) converted to the iCalendar format. The steps to populate the Cyrus zoneinfo/ directory are as follows:

  1. Build the vzic utility located in the tools/vzic/ subdirectory of the Cyrus source code. Simply running make in the tools/vzic/ subdirectory should suffice.
  2. Download the latest version of the Time Zone Database data from IANA. Only the data is required, NOT the code.
  3. Expand the downloaded time zone data into the temporary directory of your choice.
  4. Populate configdir/zoneinfo/ with iCalendar data:

    Initial Install Only

    1. Convert the raw data into iCalendar format by running vzic as follows:

      vzic --pure --olson-dir <location-of-raw-data> --output-dir <configdir>/zoneinfo

      This will create and install iCalendar data directly into the configdir/zoneinfo/ directory.

    Updating Data Only

    1. Convert the raw data into iCalendar format by running vzic as follows:

      vzic --pure --olson-dir <location-of-raw-data>

      This will create a zoneinfo/ subdirectory in your current location (preferably tools/vzic/).

    2. Merge new/updated iCalendar data into the configdir/zoneinfo/ directory by running vzic-merge.pl in your current location:

      vzic-merge.pl

  5. Rebuild the Cyrus zoneinfo index by running ctl_zoneinfo as follows:

    ctl_zoneinfo -r <version-string>

    where <version-string> describes the recently downloaded time zone data (e.g. "IANA Time Zone Database v.2013h").

  6. Verify that the zoneinfo index database and all iCalendar data files/links are readable by the cyrus user.

iSchedule Module

This module will be automatically enabled if and only if both the CalDAV module and the caldav_allowscheduling options are enabled in a Cyrus Murder.

Support for scheduling with external servers is currently under development and will require a future release of OpenDKIM.

DomainKey Module

Currently unavailable. Will be available once iSchedule support to external servers is available.

Cyrus HTTP

Cyrus HTTP (RSS, CalDAV, CardDAV, iSchedule, DomainKey)

Note that the HTTP service and associated modules in Cyrus are still under development. This release should be considered beta quality.

Introduction

Cyrus http service has the ability to:

  • Serve IMAP mailboxes as RSS feeds.
  • Act as a calendar and scheduling (CalDAV) server by using IMAP mailboxes as calendar collections and RFC 5322 messages to store iCalendar data.
  • Act as a contacts (CardDAV) server by using IMAP mailboxes as addressbook collections and RFC 5322 messages to store vCard data.
  • Allow scheduling transactions between separate calendaring and scheduling systems via the iSchedule protocol (currently only used within a Cyrus Murder).
Unlike the Apache HTTP Server, Cyrus HTTP is NOT a general purpose HTTP server. Its feature set is limited to what is required to support the facilities listed above.

This document assumes that you are familiar with building and configuring a Cyrus server. If you have not already done so, please read and understand the rest of the installation documentation before continuing. Note: The "Installation" section below augments the "Compiling the IMAP Server" document. The remaining sections assume that your Cyrus server has already been successfully configured.

This document also assumes that you are familiar with RSS, WebDAV, calendaring, and contacts.

Installation

You will need to build Cyrus with the --enable-http configure option. This builds httpd and the associated modules and utilities based on the availability of the prerequisites listed below.

General Requirements

  • Must have libxml2 installed.
  • Must have a recent SASL build (v2.1.26 or later) in order to support HTTP Digest, Negotiate, and NTLM authentication. Otherwise, only HTTP Basic authentication will be available

CalDAV / CardDAV Requirements

  • Must have libical installed.
  • Must have SQLite v3.x (or later) installed.
  • Optionally install json-c for jCal/jCard support.

General Configuration

The Cyrus httpd service is configurable via several options in imapd.conf. Several of those options are discussed in the sections below. Admins should consult the imapd.conf(5) manpage for the full list of options used by the httpd service and its various modules.

The support for RSS, CalDAV, and CardDAV is divided into separate modules which run as part of the Cyrus httpd service. Selection of which module(s) are enabled is done by setting the httpmodules option accordingly. By default, no modules are enabled.

Cyrus httpd also can serve static content, the location of which is set by the httpdocroot option. Any content contained in the specified directory (including sub-directories) will be served as static content only. Cyrus httpd does NOT have the ability to execute any server-side scripts.

HTTP Authentication

As with other Cyrus services, the Cyrus httpd service uses Cyrus SASL to perform its authentication. Cyrus supports the following HTTP authentication schemes: Basic, Digest, Negotiate (Kerberos only), and NTLM. While Basic is available in all versions of SASL, the remaining schemes are only available in Cyrus SASL 2.1.16 (and higher).

Similar to plaintext login commands supported by the other Cyrus services (IMAP LOGIN, POP3 USER/PASS), the Cyrus httpd service determines whether to advertise the HTTP Basic authentication scheme based on the allowplaintext option and whether the client has connected over a TLS protected connection (HTTPS).

The availability of the other HTTP authentication schemes is controlled by the sasl_mech_list option. For Cyrus httpd the DIGEST-MD5, GSS-SPNEGO, and NTLM SASL plugins support the Digest, Negotiate, and NTLM authentication schemes respectively, provided that these plugins are installed on the server.

RSS Module

Configuration

When enabled, the RSS module will default to serving ALL mailboxes to which the authenticated user has access as RSS feeds. The rss_feeds option can be used to limit the set of mailboxes that can be served as RSS feeds. For example, setting rss_feeds to *,!user will serve all shared mailboxes, but no personal mailboxes.

The list of available RSS feeds can be obtained by clients by accessing the /rss/ URL on the Cyrus server. By default, the server will present the list as a simple unordered list in an HTML document. To customize the look and feel of the feed list, the rss_feedlist_template option can be used to point to a HTML template file. This file can utilize Cascading Style Sheets, JavaScript, etc. Any and all content that the template file references MUST reside under the httpdocroot as set above. Consult the imapd.conf(5) manpage for specifics on the required contents of this custom file. Note that for sites running Cyrus Murder, rss_feedlist_template only needs to be set on frontend servers, since only those servers have the complete mailbox list.

CalDAV Module

Configuration

When enabled, the CalDAV module allows Cyrus to function as a calendar and scheduling server. This module uses a subset of the mailbox hierarchy as calendar collections, the toplevel of which is specified by the calendarprefix option. The public calendar hierarchy will reside at the toplevel of the shared mailbox namespace. A user's personal calendar hierarchy will be a child of their Inbox. For example, using the default value for calendarprefix, a calendar named Default for user murch would reside in the mailbox named user.murch.#calendars.Default.

Note that mailboxes in the calendar hierarchies (those under calendarprefix) SHOULD NOT be accessed with an IMAP client as doing so will leave a mailbox in a state unsuitable for CalDAV. To this end, calendar mailboxes will not returned by Cyrus imapd in response to an IMAP client's request for the available mailbox list, but Cyrus imapd will not otherwise prevent an IMAP client from accessing them.

By default, the CalDAV module will automatically perform scheduling operations when a scheduling object (invite or reply) is stored on or deleted from the server. Support for the calendar-auto-schedule feature can be disabled with the caldav_allowscheduling option.

Administration

Calendar provisioning

The CalDAV module will automatically create the required calendars for a user the first time that the user authenticates to the CalDAV server. Note that the user MUST have an existing IMAP Inbox in order for the calendars to be created.

Calendar access controls

The CalDAV module uses the same access controls as the other Cyrus services. The cyradm(1) tool can be used to adjust ACLs on calendars as needed. The tables below show how the access controls are used by the CalDAV module.


Mapping of IMAP Rights to WebDAV Privileges & HTTP Methods
IMAP right WebDAV privilege HTTP methods
l - lookup DAV:read
(aggregates DAV:read-current-user-privilege-set,
CALDAV:read-free-busy)
GET/HEAD, PROPFIND, REPORT,
COPY/MOVE (on target)
r - read
s - seen
w - write DAV:write-properties PROPPATCH, COPY/MOVE (on target)
i - insert DAV:write-content PUT, LOCK, COPY/MOVE (on target)
p - post CYRUS:add-resource (aggregated under DAV:bind) POST
k - create mailbox CYRUS:make-collection (aggregated under DAV:bind) MKCOL, MKCALENDAR
x - delete mailbox CYRUS:remove-collection (aggregated under DAV:unbind) DELETE
t - delete message CYRUS:remove-resource (aggregated under DAV:unbind) DELETE, MOVE (on source)
e - expunge
a - admin CYRUS:admin
(aggregates DAV:read-acl, DAV:write-acl, DAV:unlock)
ACL, UNLOCK, PROPFIND (DAV:acl only)
9 - free/busy CALDAV:read-free-busy (regular calendar collection only) REPORT (CALDAV:free-busy-query only)
CALDAV:schedule-query-freebusy (Scheduling Inbox only)
CALDAV:schedule-send-freebusy (Scheduling Outbox only)
8 - invite CALDAV:schedule-deliver-invite (Scheduling Inbox only)
CALDAV:schedule-send-invite (Scheduling Outbox only)
7 - reply CALDAV:schedule-deliver-reply (Scheduling Inbox only)
CALDAV:schedule-send-reply (Scheduling Outbox only)


Default WebDAV Privileges by Collection
Collection ACL
Regular Calendar owner - DAV:all + CALDAV:read-free-busy (lrwipkxta9)
anyone - CALDAV:read-free-busy (9)
Scheduling Inbox owner - DAV:all + CALDAV:schedule-deliver (lrwipkxta789)
anyone - CALDAV:schedule-deliver (789)
Scheduling Outbox owner - DAV:all + CALDAV:schedule-send (lrwipkxta789)

Client Setup

Mozilla Lightning

For each calendar that you would like to add to this client, perform the following steps:

  1. Select the "File -> New -> Calendar..." menu option.
  2. Select the "On the Network" option and click Continue.
  3. Select "CalDAV" as the Format.
  4. Enter a URL of the following form as the Location: https://<servername>/dav/calendars/user/<userid>/<calendar>/

Cyrus will auto-provision a calendar with name "Default" which can be used in the URL above.

Apple iCal

This client will autodetect all available calendars on a server. To add a Cyrus server to this client, perform the following steps:

  1. Select the "Calendar -> Preferences" menu option.
  2. Select the "Accounts" tab.
  3. Click the "+" button.
  4. Select "CalDAV" as the Account Type.
  5. Fill in User Name, Password, and Server Address accordingly.
  6. Click Create.

Apple iOS Calendar

This client will autodetect all available calendars on a server. To add a Cyrus server to this client, perform the following steps:

  1. Run the "Settings" app.
  2. Select the "Mail, Contacts, Calendars" menu.
  3. Select the "Add Account..." menu.
  4. Select the "Other" menu.
  5. Select the "Add CalDAV Account" menu.
  6. Fill in Server, User Name, Password, and Description accordingly.
  7. Click Next.

Evolution

This client will autodetect all available calendars on a server. For each calendar that you would like to add to this client, perform the following steps:

  1. Select the "New -> Calendar" menu option.
  2. Select "CalDAV" as the Type.
  3. Fill in Server and User accordingly.
  4. Click "Find Calendars".
  5. Select the desired calendar from the list.
  6. Click "Apply".
  7. Click "OK".

aCal

This client will autodetect all available calendars on a server. To add a Cyrus server to this client, perform the following steps:

  1. Press the Andoid "Menu" button.
  2. Select "Settings".
  3. Select "Servers".
  4. Select "Add Server".
  5. Select "Manual Configuration".
  6. Fill in Username, Password, and User URL (servername) accordingly.
  7. Press "Apply".

CalDavZAP

This client will autodetect all available calendars on a server. To configure this client for a Cyrus server, edit config.js as follows:

  1. Set the href value in the globalNetworkCheckSettings array to a URL of the following form: https://<servername>/dav/principals/user/
    Note that the trailing "/" is REQUIRED.
  2. Set the globalSettingsType option to calendar-home-set
  3. Set any other options as desired (e.g. globalDatepickerFirstDayOfWeek, globalTimeZone).

CardDAV Module

Configuration

When enabled, the CardDAV module allows Cyrus to function as a contacts server. This module uses a subset of the mailbox hierarchy as addressbook collections, the toplevel of which is specified by the addressbookprefix option. The public addressbook hierarchy will reside at the toplevel of the shared mailbox namespace. A user's personal addressbook hierarchy will be a child of their Inbox. For example, using the default value for addressbookprefix, an addressbook named Default for user murch would reside in the mailbox named user.murch.#addressbooks.Default.

Note that mailboxes in the addressbook hierarchies (those under addressbookprefix) SHOULD NOT be accessed with an IMAP client as doing so will leave a mailbox in a state unsuitable for CardDAV. To this end, addressbook mailboxes will not returned by Cyrus imapd in response to an IMAP client's request for the available mailbox list, but Cyrus imapd will not otherwise prevent an IMAP client from accessing them.

Administration

Addressbook provisioning

The CardDAV module will automatically create a default addressbook for a user the first time that the user authenticates to the CardDAV server. Note that the user MUST have an existing IMAP Inbox in order for the addressbook to be created.

Addressbook access controls

Cyrus uses the same access controls for addressbooks as it does for calendars, except that the scheduling rights (7, 8, 9) have no use with addressbooks and are ignored.

Client Setup

Apple Contacts

This client will autodetect all available addressbooks on a server. To add a Cyrus server to this client, perform the following steps:

  1. Select the "Contacts -> Preferences" menu option.
  2. Select the "Accounts" tab.
  3. Click the "+" button.
  4. Select "CardDAV" as the Account Type.
  5. Fill in User Name, Password, and Server Address accordingly.
  6. Click Create.

Apple iOS Contacts

This client will autodetect all available addressbooks on a server. To add a Cyrus server to this client, perform the following steps:

  1. Run the "Settings" app.
  2. Select the "Mail, Contacts, Calendars" menu.
  3. Select the "Add Account..." menu.
  4. Select the "Other" menu.
  5. Select the "Add CardDAV Account" menu.
  6. Fill in Server, User Name, Password, and Description accordingly.
  7. Click Next.

CardDavMATE

This client will autodetect all available addressbooks on a server. To configure this client for a Cyrus server, edit config.js as follows:

  1. Set the href value in the globalNetworkCheckSettings array to a URL of the following form: https://<servername>/dav/principals/user/
    Note that the trailing "/" is REQUIRED.
  2. Set the globalSettingsType option to addressbook-home-set
  3. Set any other options as desired.

iSchedule Module

This module will be automatically enabled if and only if both the CalDAV module and the caldav_allowscheduling options are enabled in a Cyrus Murder.

Support for scheduling with external servers is currently under development and will require a future release of OpenDKIM.

DomainKey Module

Currently unavailable. Will be available once iSchedule support to external servers is available.

cyrus-imapd-2.5.10/doc/ag.html0000644000175000017500000007066113001236020012774 00000000000000 Cyrus IMAP Server: Cyrus Murder Concepts

Cyrus IMAP Server: Cyrus Murder Concepts

Abstract

The Cyrus IMAP Aggregator transparently distributes IMAP and POP mailboxes across multiple servers. Unlike other systems for load balancing IMAP mailboxes, the aggregator allows users to access mailboxes on any of the IMAP servers in the system.

The software described below is now available as part of the Cyrus IMAP distribution , versions 2.1.3 and higher. Please refer to the documentation for setup and install instructions.

Please send any questions or comments to cyrus-bugs@andrew.cmu.edu.

1.0 Overview

Scaling a service usually takes one of two paths: buy bigger and faster machines, or distribute the load across multiple machines. The first approach is obvious and (hopefully) easy, though at some point software tuning becomes necessary to take advantage of the bigger machines. However, if one of these large machines go down, then your entire system is unavailable.

The second approach has the benefit that there is no longer a single point of failure and the aggregate cost of multiple machines may be significantly lower than the cost of a single large machine. However, the system may be harder to implement as well as harder to manage.

In the IMAP space, the approach of buying a larger machine is pretty obvious. Distributing the load is a bit trickier since there is no concept of mailbox location in IMAP (excluding RFC2193 mailbox referrals, which are not widely implemented by clients). Clients traditionally assume that the server they are talking to is the server with the mailbox they are looking for.

The approaches to distributing the load among IMAP servers generally sacrifice the unified system image. For pure email, this is an acceptable compromise; however, trying to share mailboxes becomes difficult or even impossible. Specific examples can be found in Appendix A: DNS Name Load Balancing and Appendix B: IMAP Multiplexing).

We propose a new approach to overcome these problems. We call it the the Cyrus IMAP Aggregator. The Cyrus aggregator takes a murder of IMAP servers and presents a server independent view to the clients. That is, all the mailboxes across all the IMAP servers are aggregated to a single image, thereby appearing to be only one IMAP server to the clients.

2.0 Architecture

The Cyrus IMAP Aggregator has three classes of servers: IMAP frontend, IMAP backend, and MUPDATE. The frontend servers act as the primary communication point between the end user clients and the back endservers. The frontends use the MUPDATE server as an authoritative source for mailbox names, locations, and permissions. The back end servers store the actual IMAP data (and keep the MUPDATE server appraised as to changes in the Mailbox list).

The Cyrus IMAP Aggregator requires version 2.1.3 or higher of the Cyrus IMAP Distribution.

2.1 Back End Servers

The backend servers serve the actual data and are fully functional standalone IMAP servers that serve a set of mailboxes. Each backend server maintains a local mailboxes database that lists what mailboxes are available on that server.

The imapd processes on a backend server can stand by themselves, so that each backend IMAP server can be used in isolation, without a MUPDATE server or any frontend servers. However, they are configured so that they won't process any mailbox operations (CREATE, DELETE, RENAME, SETACL, etc) unless the master MUPDATE server can be contacted and authorizes the transaction.

In this mode, the imapd processes update the local mailboxes database themselves. Additionally, on a CREATE they need to reserve a place with the MUPDATE server to insure that other backend servers aren't creating the same mailbox before proceeding. Once the local aspects of mailbox creation are complete, the mailbox is activated on the MUPDATE server, and is considered available to any client through the frontends.

2.2 Front End Servers

The front end servers, unlike the back end servers, are fully interchangeable with each other and the front end servers can be considered 'dataless'; any loss of a proxy results in no loss of data. The only persistent data that is needed (the mailbox list) is kept on the MUPDATE master server. This list is synchronized between the frontend and the MUPDATE master when the frontend comes up.

The list of mailboxes in the murder is maintained by the MUPDATE server. The MUPDATE protocol is described at RFC3656.

For IMAP service on a frontend, there are two main types of processes, the proxyd and the mupdate (slave mode) synchronization process. The proxyd handles the IMAP session with clients. It relies on a consistent and complete mailboxes database that reflects the state of the world. It never writes to the mailboxes database. Instead, the mailboxes database is kept in sync with the master by a slave mupdate process.

2.3 Mail Delivery

The incoming mail messages go to an lmtp proxy (either running on a frontend, a mail exchanger, or any other server). The lmtp proxy running on the front end server uses the master MUPDATE server to determine the location of the destination folder and then transfers the message to the appropriate back end server via LMTP. If the backend is not up (or otherwise fails to accept the message), then the LMTP proxy returns a failure to the connected MTA.

If a sieve script is present, the lmtp proxy server must do the processing as the end result of the processing may result in the mail message going to a different back end server than where the user's INBOX is. Note that the current implementation runs SIEVE on the backend servers, and holds the requirement that all of a user's mailboxes live on the same backend.

2.4 Clients

Clients that support RFC2193 IMAP referrals can bypass the aggregator front end. See section 3.8 for more details.

Clients are encouraged to bypass the front ends via approved mechanisms. This should result in better performance for the client and less load for the servers.

3.0 Implementation

3.1 Assumptions

  • Operations that change the mailbox list are (comparatively) rare. The vast majority of IMAP sessions do not manipulate the state of the mailbox list.
  • Read operations on the mailbox list are very frequent.
  • A mailbox name must be unique among all the back end servers.
  • The MUPDATE master server will be able to handle the load from the frontend, backend, and LMTP proxy servers. Currently, the MUPDATE master can be a bottleneck in the throughput of mailbox operations, but as the MUPDATE protocol allows for slave server to act as replicas, it is theoretically possible to reduce the load of read operations against the master to a very low level.
  • IMAP clients are not sensitive to somewhat loose mailbox tree consistency, and some amount of consistency can be sacrificed for speed. As is, IMAP gives no guarantees about the state of the mailbox tree from one command to the next. However, it's important to note that different IMAP sessions do communicate out of band: two sessions for the same client should see sensible results. In the Murder case, this means that the same client talking to two different frontends should see sensible results.
  • A single IMAP connection should see consistent results: once an operation is done, it is done, and needs to be reflected in the current session. The straightforward case that must work correctly is (provided there is no interleaved DELETE in another session):
         A001 CREATE INBOX.new
         A002 SELECT INBOX.new
    
  • Accesses to non-existant mailboxes are rare.

3.2 Authentication

The user authenticates to the frontend server via any supported SASL mechanism or via plaintext. If authentication is successful, the front end server will authenticate to the back end server using a SASL mechanism (in our case KERBEROS_V4 or GSSAPI) as a privileged user. This user is able to switch to the authorization of the actual user being proxied for and any authorization checks happen as if the user actually authenticated directly to the back end server. Note this is a native feature of many SASL mechanisms and nothing special with the aggregator.

To help protect the backends from a compromised frontends, all administrative actions (creating users, top level mailboxes, quota changes, etc) must be done directly from the client to the backend, as administrative permissions are not granted to any of the proxy servers. IMAP Referrals provide a way to accomplish this with minimal client UI changes.

3.3 Subscriptions

[LSUB, SUBSCRIBE, UNSUBSCRIBE]
The front end server directs the LSUB to the back end server that has the user's INBOX. As such, the back end server may have entries in the subscription database that do not exist on that server. The frontend server needs to process the list returned by the backend server and either remove or tag with \NoSelect the entries which are not currently active within the murder.

If the user's INBOX server is down and the LSUB fails, then the aggregator replies with NO with an appropriate error message. Clients should not assume that the user has no subscriptions (though apparently some clients do this).

3.4 Finding a Mailbox

[SETQUOTA, GETQUOTA, EXAMINE, STATUS]
The front end machine looks up the location of the mailbox, connects via IMAP to the back end server, and issues the equivalent command there.

A quota root is not allowed to span across multiple servers. Atleast, not with the semantics that it will be inclusive across the murder.

[SELECT]
To SELECT a mailbox:

  1. proxyd: lookup foo.bar in local mailboxes database
  2. if yes, proxyd -> back end: send SELECT
  3. if no, proxyd -> mupdate slave -> mupdate master: send a ping along the UPDATE channel in order to ensure that we have received the latest data from the MUPDATE master.
  4. if mailbox still doesn't exist, fail operation
  5. if mailbox does exist, and the client supports referrals, refer the client. Otherwise continue as a proxy with a selected mailbox.

SELECT on mailboxes that do not exist are much more expensive but the assumption is that this does not frequently occur (or if it does, it is just after the mailbox has been created and the frontend hasn't seen the update yet).

3.5 Operations within a Mailbox

[APPEND, CHECK, CLOSE, EXPUNGE, SEARCH, FETCH, STORE, UID]
These commands are sent to the appropriate back end server. The aggregator does not need to modify any of these commands before sending them to the back end server.

3.6 COPY

COPY is somewhat special as it acts upon messages in the currently SELECT'd mailbox but then interacts with another mailbox.

In the case where the destination mailbox is on the same back end server as the the source folder, the COPY command is issued to the back end server and the back end server takes care of the command.

If the destination folder is on a different back end server, the front end intervenes and does the COPY by FETCHing the messages from the source back end server and then APPENDs the messages to the destination server.

3.7 Operations on the Mailbox List

[CREATE, DELETE, RENAME, SETACL]
These commands are all done by the back end server using the MUPDATE server as a lock manager. Changes are then propogated to the frontend via the MUPDATE protocol.

[LIST]


LIST is handled by the front end servers; no interaction is required with the back end server as the front ends have a local database that is never more than a few seconds out of date.

[CREATE]
CREATE creates the mailbox on the same back end server as the parent mailbox. If the parent exists but exists on multiple back end servers, if there is no parent folder, a tagged NO response is returned.

When this happens, the administrator has two choices. He may connect directly to a back end server and issue the CREATE on that server. Alternatively, a second argument can be given to CREATE after the mailbox name. This argument specifies the specific host name on which the mailbox is to be created.

The following operations occur for CREATE on the front end:

  1. proxyd: verify that mailbox doesn't exist in MUPDATE mailbox list.
  2. proxyd: decide where to send CREATE (the server of the parent mailbox, as top level mailboxes cannot be created by the proxies).
  3. proxyd -> back end: duplicate CREATE command and verifies that the CREATE does not create an inconsistency in the mailbox list (i.e. the folder name is still unique).

The following operations occur for CREATE on the back end:

  1. imapd: verify ACLs to best of ability (CRASH: aborted)
  2. imapd: start mailboxes transaction (CRASH: aborted)
  3. imapd may have to open an MUPDATE connection here if one doesn't already exist
  4. imapd -> MUPDATE: set foo.bar reserved (CRASH: MUPDATE externally inconsistent)
  5. imapd: create foo.bar in spool disk (CRASH: MUPDATE externally inconsistent, back end externally inconsistent, this can be resolved when the backend comes back up by clearing the state from both MUPDATE and the backend)
  6. imapd: add foo.bar to mailboxes dataset (CRASH: ditto)
  7. imapd: commit transaction (CRASH: ditto, but the recovery can activate the mailbox in mupdate instead)
  8. imapd -> MUPDATE: set foo.bar active (CRASH: committed)

Failure modes: Above, all back end inconsistencies result in the next CREATE attempt failing. The earlier MUPDATE inconsistency results in any attempts to CREATE the mailbox on another back end failing. The latter one makes the mailbox unreachable and un-createable. Though, this is safer than potentially having the mailbox appaear in two places when the failed backend comes back up.

[RENAME]
RENAME is only interesting in the cross-server case. In this case it issues a (non-standard) XFER command to the backend that currently hosts the mailbox, which performs a binary transfer of the mailbox (and in the case of a user's inbox, their associated seen state and subscription list) to the new backend. During this time the mailbox is marked as RESERVED in mupdate, and when it is complete it is activated on the new server in MUPDATE. The deactivation prevents clients from accessing the mailbox, and causes mail delivery to temporarily fail.

3.8 IMAP Referrals

If clients support IMAP Mailbox Referrals [MBOXREF], the client can improve performance and reduce the load on the aggregator by using the IMAP referrals that are sent to it and going to the appropriate back end servers.

The front end servers will advertise the MAILBOX-REFERRALS capability. The back end servers will also advertise this capability (but only because they need to refer clients while a mailbox is moving between servers).

Since there is no way for the server to know if a client supports referrals, the Cyrus IMAP Aggregator will assume the clients do not support referrals unless the client issues a RLSUB or a RLIST command.

Once a client issues one of those commands, then the aggregator will issue referrals for any command that is safe for the client to contact the IMAP server directly. Most commands that perform operations within a mailbox (cf Section 3.3) fall into this category. Some commands will not be possible without a referrals-capable client (such as most commands done as administrator).

RFC2193 indicates that the client does not stick the referred server. As such the SELECT will get issued to the front end server and not the referred server. Additionally, CREATE, RENAME, and DELETE get sent to the frontend which will proxy the command to the correct back end server.

3.9 POP

POP is easy given that POP only allows access to the user's INBOX. When it comes to POP, the IMAP Aggregator acts just like a multiplexor. The user authenticates to front end server. The front end determines where the user's INBOX is located and does a direct pass through of the POP commands from the client to the appropriate back end server.

3.10 MUPDATE

The mupdate (slave) process (one per front end) holds open an MUPDATE connection and listens for updates from the MUPDATE master server (as backends inform it of updates). The slave makes these modifications on the local copy of the mailboxes database.

4.0 Analysis

??? Add timing info? Random load testing?

4.1 Mailboxes Database

A benefit of having the mailbox information on the front end is that LIST is very cheap. The front end servers can process this request without having to contact each back end server.

We're also assuming that LIST is a much more frequent operation than any of the mailbox operations and thus should be the case to optimize. (In addition to the fact that any operation that needs to be forwarded to a backend needs to know which backend it is being forwarded to, so lookups in the mailbox list are also quite frequent).

4.2 Failure Mode Analysis

What happens when a back end server comes up? Resynchronization with the MUPDATE server. Any mailboxes that exist locally but are not in MUPDATE are pushed to MUPDATE. Any mailboxes that exist locally but are in MUPDATE as living on a different server are deleted. Any mailboxes that do not exist locally but exist in MUPDATE as living on this server are removed from MUPDATE.

What happens when a front end server comes up? The only thing that needs to happen is for the front end to connect to the MUPDATE server, issue an UPDATE command, and resynchronize its local database copy with the copy on the master server.

Where's the true mailboxes file? The MUPDATE master contains authoritative information as to the location of any mailbox (in the case of a conflict), but the backends are authoritative as to which mailboxes actually exist.

4.3 Summary of Benefits

  • Availability - By allowing multiple front-ends, failures of the front-end only result in a reduction of capacity. Users currently connected still lose their session but can just reconnect to get back online.

    The failure of the back-ends will result in the loss of availability. However, given that the data is distributed among multiple servers, the failure of a single server does not result the entire system being down. Our experience with AFS was that this type of partitioned failure was acceptable (if not ideal).

    The failure of the mupdate master will cause write operations to the mailbox list to fail, but accesses to mailboxes themselves (as well as read operations to the mailbox list) will continue uninterrupted.

    At this point, there may be some ideas but no plans for providing a high availability solution which would allow for back-end servers or the MUPDATE server to fail with no availability impact.

  • Load scalability - We have not done any specific benchmarks to show that this system actually performs better. However, it is clear that it scales to a larger number of users than a single server architechure would. Though, based on the fact that we have not had any performance problems similar to when we were running a single machine, and we are handling about 20% more concurrent users, things have been a rousing success.

    Live statistics can be found under the "cyrus overview" section at: http://graphs.andrew.cmu.edu.

  • Management benefits - As with AFS, administrators have the flexibility of placement of data on the servers, "live" move of data between servers,
  • User benefits - The user only needs to know a single server name for configuration. The same name can be handed out to all users.

    Users don't lose the ability to share their folders and those folders are visible to other users. A user's INBOX folder hierarchy can also exist across multiple machines.

5.0 Futures

  • It would be nice to be able to replicate the messages in a mailbox among multiple servers and not just do partitioning for availability.

  • We are also evaluating using the aggregator to be able to provide mailboxes to the user with a different backup policy or even different "quality of service." For example, we are looking to give users a larger quota than default but not back up the servers where these mailboxes exist.

  • There is possibility that LDAP could be used instead of MUPDATE. However at this time the replication capabilities of LDAP are insufficient for the needs of the Aggregator

  • It would be nice if quotaroots had some better semantics with respect to the murder (either make them first-class entities, or have them apply across servers).

Appendix A: DNS Name Load Balancing

One method of load balancing is to use DNS to spread your users to multiple machines.

One method is to create a DNS CNAME for each letter of the alphabet. Then, each user sets their IMAP server to be the first letter of their userid. For example, the userid 'tom' would set his IMAP server to be T.IMAP.ANDREW.CMU.EDU and T.IMAP.ANDREW.CMU.EDU would resolve to an actual mail server.

Given that this does not provide a good distribution, another option is to create a DNS CNAME for each user. Using the previous example, the user 'tom' would set his IMAP server to be TOM.IMAP.ANDREW.CMU.EDU which then points to an actual mail server.

The good part is that you don't have all your users on one machine and growth can be accommodated without any user reconfiguration.

The drawback is with shared folders. The mail client now must support multiple servers and users must potentially configure a server for each user with a shared folder he wishes to view. Also, the user's INBOX hierarchy must also reside on a single machine.

Appendix B: IMAP Multiplexing

Another method of spreading out the load is to use IMAP multiplexing. This is very similar to the IMAP Aggregator in that there are frontend and backend servers. The frontend servers do the lookup and then forward the request to the appropriate backend server.

The multiplexor looks at the user who has authenticated. Once the user has authenticated, the frontend does a lookup for the backend server and then connects the session to a single backend server. This provides the flexibility of balancing the users among any arbitrary server but it creates a problem where a user can not share a folder with a user on a different back end server.

Multiplexors references:

Appendix C: Definitions

IMAP connection
A single IMAP TCP/IP session with a single IMAP server is a "connection".
client
A client is a process on a remote computer that communicates with the set of servers distributing mail data, be they ACAP, IMAP, LDAP, or IMSP servers. A client opens one or more connections to various servers.
mailbox tree
The collection of all mailboxes at a given site in a namespace is called the mailbox tree. Generally, the user Bovik's personal data is found in user.bovik.
mailboxes database
A local database containing a list of mailboxes known to a particular server. (In old Cyrus terms, this maps to /var/imap/mailboxes.)
mailbox dataset
The store of mailbox information on the ACAP server is the "mailbox dataset".
mailbox operation
The following IMAP commands are "mailbox operations": CREATE, RENAME, DELETE, and SETACL.
MTA
The mail transport agent (e.g. sendmail, postfix).
Murder of IMAP servers
A grouping of IMAP servers. It sounded cool for crows so we decided to use it for IMAP servers as well.
quota operations
The quota IMAP commands (GETQUOTA, GETQUOTAROOT, and SETQUOTA) operate on mailbox trees. In future versions of Cyrus, it is expected that a quotaroot will be a subset of a mailbox tree that resides on one partition on one server. For rational, see section xxx.

Appendix D: ACAP

It was originally intended to use the general purpose protocol ACAP instead of the (task specific) MUPDATE. We expected the following commands to query the ACAP server:

[LSUB, SUBSCRIBE, UNSUBSCRIBE, SETQUOTA, GETQUOTA, EXAMINE, STATUS]
All these commands could be handled by the mailboxes dataset.[MBOXDSET] This would mainly be a client enhancement. For example, a client could use this to quickly check all the new messages in every folder a user is subscribed to and would also be able to talk directly to the back-end where the data is and thereby skipping the front-ends.

Appendix E: Naming

An alternate name was suggested (unfortunately too late) by Philip Lewis. He writes:

i would have called it an atlas.... or iatlas (pronounced "yatlas")
it is a collection of (i)maps.

References

  • [ACAP] Newman, Myers, "ACAP -- Application Configuration Access Protocol", RFC 2244, November 1997.
  • [AFS] J. Howard, "An Overview of the Andrew File System", Usenix, Feb 1988.
  • [IMAP] M. Crispin, "Internet Message Access Protocol", RFC 2060, December 1996.
  • [LMTP] J. Myers, "Local Mail Transfer Protocol", RFC 2033, October 1996.
  • [MBOXDSET] L. Greenfield, "ACAP Mailbox Dataset Class", November 1998, available from the author, leg+@andrew.cmu.edu.
  • [MBOXREF] M. Gahrns, "IMAP4 Mailbox Referrals", RFC 2193, September 1997.
  • [SIEVE] T. Showalter, "Sieve: A Mail Filtering Language", RFC 3028, January 2001.

Document Change Log

  • 3.1 - cleanups
  • 3.0 - actual implementation. MUPDATE instead of ACAP, mailbox moves now possible (4/4/02)
  • 2.0 - closer to implementation. ACAP is now required. Ditch MOIS
  • 1.0 - Initial revision.
cyrus-imapd-2.5.10/doc/mailing-list.html0000644000175000017500000000374313001236020014773 00000000000000 info-cyrus mailing list

info-cyrus mailing list

We run a mailing list for users of Project Cyrus software. The info-cyrus@andrew.cmu.edu mailing list exists for the discussion of this server and other Cyrus software. Please do NOT send subscription requests to the list.

To subscribe: Send mail to info-cyrus-subscribe@lists.andrew.cmu.edu to subscribe (or just click the link above and that should just work).

An archive is availible via anonymous IMAP at imap://cyrus.andrew.cmu.edu/archive.info-cyrus.

A web archive is also available at http://www.cyrusimap.org/mediawiki/index.php/Cyrus_Mailing_Lists#Archives

If you are not subscribed to the list (or you are sending the message from a different address than the one which you are subscribed under), your message is directed to a human for approval. Unfortunately, the human does not always promptly process the message.

There is also a developers list available at cyrus-devel@lists.andrew.cmu.edu. with similar subscription methods and archive location

Detailed contact information can be found at http://www.cyrusimap.org/mediawiki/index.php/Contact


last modified: $Date: 2010/01/06 17:01:29 $
Return to the Cyrus IMAP Server Home Page cyrus-imapd-2.5.10/doc/man.html0000644000175000017500000000567313001236020013161 00000000000000 Cyrus IMAP Server Man Pages

Cyrus IMAP Server Man Pages

User Commands Subroutines File Formats System Administration cyrus-imapd-2.5.10/doc/install-murder.html0000644000175000017500000004030513001236020015337 00000000000000 Installing The Cyrus Murder

Installing The Cyrus Murder

The Cyrus Murder provides the ability to horizontally scale your Cyrus IMAP environment across multiple servers. It is similar in nature to various proxy solutions such as nginx or perdition with the difference being that Murder offers a uniform namespace. If you're not currently using shared mailboxes and you don't intend to use shared mailboxes in the future, you should probably just consider using a simple proxy solution.


Introduction & Assumptions

This document is intended to be a guide to the configuration of a Cyrus IMAP Aggregator, aka Cyrus Murder. It is recommended that you review this document to become familliar with the concepts at work. This document is a work in progress and is at this point incomplete.

This document assumes that you have successfully been able to setup atleast one Cyrus IMAP server. This server will become your first backend server. It also assumes that you are familliar with the administration and day to day operations of the Cyrus IMAP server and the SASL authentication library. If you feel uncomfortable with this, please refer to the rest of the documentation first.

There is a diagram that shows the interactions of the various components of the Cyrus Murder which may be helpful in understanding the "big picture".

Installation

You will need to build Cyrus IMAPd with the --enable-murder configure option. This builds the proxyds and the associated utilities.

Requirements

  • Atleast one Cyrus IMAP server. If there are more than one, their name spaces must not conflict. That is, all the mailbox names must be unique (or in different namespaces)
  • Atleast one machine that will become the first Frontend Server.
  • One machine to become the MUPDATE master server. This can be the same as one of your frontend servers.

Configuring the MUPDATE Master

The mupdate master server needs to be running the mupdate service in master mode. Note that you can have the MUPDATE master be one of your frontend machines, just do not configure a slave mupdate process on this machine.

To configure an mupdate master, you will want a cyrus.conf that includes a line similar to the following in the SERVICES section:

  mupdate       cmd="/usr/cyrus/bin/mupdate -m" listen=3905 prefork=1
Note the "-m" option to tell mupdate that it should start in master mode.

You will also need to configure atleast a skeleton imapd.conf that defines the configdirectory, a bogus partition-default and the admins that can authenticate to the server. Note that slave mupdate servers as well as the backend servers will need to be able to authenticate as admins on the master. Here is a very simple imapd.conf for a master server:

configdirectory: /imap/conf
partition-default: /tmp

admins: mupdateslave1 backend1
You will also need to configure SASL to properly allow authentication in your enviornment.

Setting up the backends to push changes to the MUPDATE Master

On the backends, configuration to be a part of a murder is easy. You just need to configure the backend to be a part of the murder. To do this, set the mupdate_server option in imapd.conf. Depending on what authentication mechanisms you are using, you may also want to set some or all of the following:
  • mupdate_username
  • mupdate_authname
  • mupdate_realm
  • mupdate_password
Once these settings are successfully made, any mailbox operation on the backend will be sent to the mupdate master for confirmation and entry into the mupdate database.

You must also configure atleast one user/group using the proxyservers imapd.conf option. This user should not be an administrator, since this means that anyone who can get ahold of your proxy servers now has full administrative control on your backend. Example:

admins: cyrus
proxyservers: murder
Keep in mind that you will need to create the proxy user(s) and be sure that they can authenticate to the backend as well. NOTE: proxyservers should not be set on your frontends. It is also used to determine which servers to create mailboxes on.

Importing the database from the backend

Importing the current mailboxes database is easy, as there is a ctl_mboxlist option to do so. To do the first synchronization, simply change to the cyrus user, and issue a ctl_mboxlist -m.

Note that you may wish to issue a ctl_mboxlist -mw first to be sure you understand all the operations that this command will perform, since it does require that all mailboxes are unique in the murder namespace.

If everything is configured properly, the mailbox database of the current host will dump to the mupdate master. If there are problems, the most likely cause is a misconfiguration of the authentication settings, or that mupdate might not be running on the master. Using mupdatetest may be helpful in this case (it establishes an authenticated connection to the mupdate server, if it can).

It is also useful to have the backends automatically resync the state of their local mailboxes database with the master on start up. You can configure this by adding the following to the START section of cyrus.conf on the backends:

  mupdatepush   cmd="ctl_mboxlist -m"
This will perform synchronization with the mupdate master each time the backend restarts, bringing the mupdate database up to date with the contents of the backend (and performing ACTIVATE and DELETES as needed to do so).

Warning: If somehow a mailbox exists on two (or more) backend servers, each time one of them synchronizes its database that backend server will become authoritative. Though this should not happen during normal operation of the murder (because of the consistancy guarantees of the MUPDATE protocol, and the fact that mailbox operations are denied if the mupdate master is down), it is possible when first creating the mupdate database or when bringing a new backend server into the murder.

Configuring the frontends

Configuring the frontends is a two step process. First, you want to set mupdate_server (and friends) as you did for the backends above. However, because the frontends only talk to the mupdate master via a slave running on the local machine, you will also need to set up a slave on the same machine, in the SERVICES section of cyrus.conf, like so:

  # mupdate database service - must prefork atleast 1
  mupdate       cmd="mupdate" listen=3905 prefork=1
Note that as this is a threaded service, you must prefork atleast 1 of them so that the database can be synchronized at startup. Otherwise, the service will not start running until after you recieve an mupdate client connection to the slave (which is not a recommended configuration at this point).

You will also want to change all of your imapd entries to be proxyd, and all of your lmtpd entries to be lmtpproxyd. That is, you will probably have a SERVICES section that looks more like this now:

  mupdate       cmd="/usr/cyrus/bin/mupdate" listen=3905 prefork=1

  imap          cmd="proxyd" listen="imap" prefork=5
  imaps         cmd="proxyd -s" listen="imaps" prefork=1
  pop3          cmd="pop3d" listen="pop3" prefork=0
  pop3s         cmd="pop3d -s" listen="pop3s" prefork=0
  kpop          cmd="pop3d -k" listen="kpop" prefork=0
  nntp          cmd="nntpd" listen="nntp" prefork=0
  nntps         cmd="nntpd -s" listen="nntps" prefork=0
  sieve         cmd="timsieved" listen="sieve" prefork=0
  lmtp          cmd="lmtpproxyd" listen="/var/imap/socket/lmtp" prefork=0
Note that timsieved does not need a proxy daemon, the managesieve protocol deals with the murder with referrals to the backends internally.

Additionally, you will need entries in imapd.conf to indicate the proxy auth name and passwords (if you are using a SASL mechanism that requires them) to the backends, for example, if your backends are mail1.andrew.cmu.edu and mail2.andrew.cmu.edu with passwords of foo and bar, and an auth name of murder:

mail1_password: foo
mail2_password: bar
proxy_authname: murder
If your SASL mechanism does not require authnames or passwords (e.g. KERBEROS_V4), then this is not required. Note that we used the same authname as the configured in the proxyservers line in the backend's imapd.conf above.

When you start master on the frontend, a local mailboxes database should automatically synchronize itself with the contents of the mupdate master, and you should be ready to go. Your clients should connect to the frontends, and the frontends will proxy or refer as applicable to the blackend servers.

Additional backend configuration

If your authentication system requires usernames, passwords, etc, to authenticate (e.g. it isn't Kerberos), then you will also need to specify proxy_authname (and friends) in the backend imapd.confs as well. This is so that the backends can authenticate to eachother to facilitate maibox moves. (Backend machines will need to be full admins).

Delivering mail

To deliver mail to your Murder, configure your MTA just as you did before, but instead of connecting directly to lmtpd, it should connect to lmtpproxyd. You can connect to the lmtpproxyd running on the frontend machines, or you can install master and lmtpproxyd on your SMTP servers.

Administration

Keeping the database synced

Consistancy in the database is maintained by pushing the current status of the backends to the master, and having the frontends stay up to date with the master's database. Since the frontends resync themselves entirely when they startup, downtime should not at all be a problem. (While they are up they should be continously recieving database updates, as well as when they lose connection to the master, they will try to reconnect and resync their database upon reconnection)

Provided that the namespace of the backend servers is kept discrete (with no mailboxes existing on the same server), it is not a big deal to resync the mupdate master using ctl_mboxlist -m. If two servers do have the same mailbox, this will need to be resolved before database consistancy can be guranteed.

Moving Mailboxes between backends

There is currently no 100% foolproof way to do this, however, if you issue a rename command to a frontend (as you would to move a mailbox between partitions), and replace the partition name with the name of the new backend, it will move the mailbox to the indicated backend. You can also use the format backend.domain.com!partition to move to a specific partition (otherwise the default partition will be used). In cyradm, this looks like:

cyrus.andrew.cmu.edu> rename user.bcyrus user.bcyrus mail2.andrew.cmu.edu!u2
Note that since seen state is stored per-user, it is possible that when moving a shared mailbox users will have strange effects. The general rule is that moving an INBOX will move the entire user (including all sub-mailboxes to the INBOX, and seen state, and subscriptions, and sieve scripts, etc). The seen state is merged with the seen state on the new backend, so that no data is lost (seen state is also the only part left behind on the source backend). In the case of any other mailbox, however, only that individual mailbox is moved. If it is a quota root, the new quota root is instated on the new server, but otherwise quotas can appear to be violated, since each backend only takes care of its own quota.

In general, its better to leave trees of mailboxes on the same server, and not move submailboxes of inboxes between servers.

Adding additional backend servers

This is very easy to do, simply configure an empty backend server and set its mupdate_server parameter to point at the mupdate master. Then, issue mailbox creates to it as you would any other backend server.

Backups

xxx, need to write stuff. You don't need to really backup the data on the mupdate master or slaves, since this data can all be generated directly from the backends quite easily.

Gotchyas

  • Clients dealing with a pool of frontend servers - Some clients may not be terribly efficient caching connections to a pool of imap servers, this isn't a problem, per se, but it may mean that you will see many more authentications than you are used to.
    • Kerberos issues - If you are using kerberos authentication, you will want to ensure that all your machines are keyed properly, as we have seen problems with different clients trying to authenticate to different services (e.g. imap.imap-pool instead of imap.pool-frontend-1), so test the clients in use in your enviornment and be sure that they work with whatever keying scheme you use.
  • Clients dealing with referrals - Some clients (we've had particuar trouble with pine, though most of these issues have now been resolved and new versions should be OK (that is, pine > 4.44), but as referrals have not been extensively used by any IMAP server until now, referrals are very likely to not work correctly or have surprising effects.
  • Clients dealing with getting a NO on LSUB commands - Some clients (Outlook, for example) may behave poorly if an LSUB command returns a NO, which may be the case if the backend server with the user's inbox is down. We have, for example, seen this result in the deletion of the disconnected message cache.
  • Behavior of cyradm / some mailbox operations - The behavior of some administrative commands might be slightly unexpected. For example, you can only issue a SETQUOTA to a frontend server if the entire mailbox tree underneath where you are setting the quota exists on the same backend server, otherwise you will need to connect directly to the backend servers to perform the needed changes. Similarally, mailboxes will be created on the same backend server that their parent is in. In order to create them on a different server (or to create a new top level mailbox) you will need to connect directly to the desired backend server.
  • Subscriptions - If users want subscribe to a mailbox other than on their backend home server, they won't be able to, unless you set "allowallsubscribe: t" in the backend imapd.confs. This essentially lets any string be subscribed to successfully.
  • Restarting the mupdate master - Because ctl_cyrusdb -r clears reservations on mailbox, if you restart the mupdate master (and run recovery), then this could (we suspect, very rarely) lead to inconsistancies in the mupdate database.

Troubleshooting & when things go wrong

  • Mailbox operations are being denied - This is an indication that the mupdate master may be down. Restart it.
  • Mailbox operations are not being seen by one or more frontends - This indicates that the mupdate process on a slave may have died, you may need to restart master. Alternatively, mupdate will retry connections every 20 seconds or so for about 20 attempts if the master does go down.
  • A frontend's mailboxes.db is corrupt / out of sync - Restart master on the frontend, and have the mupdate process resynch the local database. You may need to remove the local mailboxes database if the corruption is extreme.
  • A mailbox's location keeps switching between two (or more) backend hosts. - It probably actually exists on both hosts. Delete the mailbox from all but one of the hosts, and run a ctl_mboxlist -m on the one where you want it to actually live.
  • Databases are never created on the frontends/slaves - Check to ensure that the mupdate slave process is started, (is prefork=1)
cyrus-imapd-2.5.10/doc/cyrusv2.mc0000644000175000017500000000530113001236020013442 00000000000000# divert(-1) # # Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. # # Redistribution and use in source and binary forms, with or without # modification, are permitted provided that the following conditions # are met: # # 1. Redistributions of source code must retain the above copyright # notice, this list of conditions and the following disclaimer. # # 2. Redistributions in binary form must reproduce the above copyright # notice, this list of conditions and the following disclaimer in # the documentation and/or other materials provided with the # distribution. # # 3. The name "Carnegie Mellon University" must not be used to # endorse or promote products derived from this software without # prior written permission. For permission or any legal # details, please contact # Carnegie Mellon University # Center for Technology Transfer and Enterprise Creation # 4615 Forbes Avenue # Suite 302 # Pittsburgh, PA 15213 # (412) 268-7393, fax: (412) 268-7395 # innovation@andrew.cmu.edu # # 4. Redistributions of any form whatsoever must retain the following # acknowledgment: # "This product includes software developed by Computing Services # at Carnegie Mellon University (http://www.cmu.edu/computing/)." # # CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO # THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY # AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE # FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES # WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN # AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING # OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. # # This sample mc file is for a site that uses the Cyrus IMAP server # exclusively for local mail. This requires Sendmail 8.10 or later. # divert(0)dnl VERSIONID(`cyrus v2 sample configuartion') OSTYPE(linux) define(`confBIND_OPTS',`-DNSRCH -DEFNAMES') define(`confTO_IDENT',`0') dnl setting cyrus as the trusted user will make it easier to pass dnl Sendmail's safefile checks. however, it means that someone with the dnl "cyrus" password could easily become root. dnl define(`confTRUSTED_USER', `cyrus') define(`confLOCAL_MAILER', `cyrus') dnl if you aren't using Sendmail 8.12, you might need to remove dnl the following feature. FEATURE(`preserve_local_plus_detail') FEATURE(`nocanonify') FEATURE(`always_add_domain') MAILER(`local') MAILER(`smtp') MAILER_DEFINITIONS Mcyrus, P=[IPC], F=lsDFMnqA@/:|SmXz, E=\r\n, S=EnvFromL, R=EnvToL/HdrToL, T=DNS/RFC822/X-Unix, A=FILE /var/imap/socket/lmtp LOCAL_RULE_0 Rbb + $+ < @ $=w . > $#cyrus $: + $1 cyrus-imapd-2.5.10/doc/readme.html0000644000175000017500000002011613001236020013630 00000000000000 Cyrus IMAP Server Release Information

Cyrus IMAP Server Release Information

IMAP (Internet Message Access Protocol) is an Internet standards-track protocol for accessing messages (mail, bboards, news, etc). The Cyrus IMAP server differs from other IMAP server implementations in that it is generally intended to be run on "sealed" servers, where normal users are not permitted to log in. The mailbox database is stored in parts of the filesystem that are private to the Cyrus IMAP system. All user access to mail is through the IMAP, NNTP, POP3, or KPOP protocols.

The private mailbox database design gives the server large advantages in efficiency, scalability, and administratability. Multiple concurrent read/write connections to the same mailbox are permitted. The server supports access control lists on mailboxes and storage quotas on mailbox hierarchies.

Features

The Cyrus server supports the IMAP4rev1 protocol described in RFC 3501. IMAP4rev1 has been approved as a proposed standard.

Character sets supported for searching are: us-ascii, iso-8859-1, iso-8859-2, iso-8859-3, iso-8859-4, iso-8859-5, iso-8859-6, iso-8859-7, iso-8859-8, iso-8859-9, koi8-r, iso-2022-jp, iso-2022-kr, gb2312, big5, iso-8859-15, windows-1252, windows-1256. The character mapping tables most likely contain errors.

The server supports any authentication mechanism available from the SASL library. Currently, support includes: KERBEROS_V4, GSSAPI, CRAM-MD5, DIGEST-MD5, OTP, PLAIN, and STARTTLS.

The server supports imaps/pop3s/nntps (IMAP/POP3/NNTP encrypted using SSL).

The server makes an attempt to do single instance store where possible when an email message is addressed to multiple recipients.

We current support the following IMAP capabilities: IMAP4 IMAP4rev1 ACL RIGHTS=kxte QUOTA LITERAL+ NAMESPACE UIDPLUS ID NO_ATOMIC_RENAME UNSELECT CHILDREN MULTIAPPEND SORT SORT=MODSEQ THREAD=ORDEREDSUBJECT THREAD=REFERENCES ANNOTATEMORE CATENATE CONDSTORE URLAUTH IDLE STARTTLS SASL-IR.

The server supports SIEVE for server side email filtering.

Upgrade Caveats

This section reserved for WARNING WARNING WARNING comments.

Note that the replication protocol currently does not have the facility to support the IMAP CONDSTORE extension (modification sequences). It is recommended that you do not try to use both CONDSTORE and replication at this time. The deficiencies in the replication protocol will be fixed in version 2.3.9.

Installation Overview

This system should be expected to have the same order-of-magnitude installation complexity as a netnews system. Maintenance should have similar complexity, except administrators will have to deal with creation and deletion of users and will have the option of managing quotas and access control lists.

This package is distributed as a source only release. It is expected that you can compile and configure software. Installation instructions are in the install.html. Please be sure to read this document.

A detailed overview of the server is available in overview.html.

This server has been successfully installed on a number of Unix systems. We run the software under SPARC Solaris 8. Please refer to os.html for operating system specific issues.

Server Notes

The mailbox namespace is like that for netnews--hierarchical names separated by the "." character. Mailboxes without a parent may only be created by an administrator. Mailboxes with a parent may be created as the ACL (Access Control List) on the parent mailbox permits.

Users' personal mailboxes are under the "user" hierarchy. The names of the personal mailboxes for user "bovik" all start with the prefix "user.bovik.". The mailbox "user.bovik" is special in that it is presented to user "bovik" as if it were named "INBOX". Creating the mailbox "user.bovik" is equivalent to creating an account for user "bovik"--it permits "bovik" to receive mail, create personal mailboxes, and subscribe to mailboxes. Deleting the mailbox "user.bovik" has the special-case side-effect of deleting all mailboxes starting with "user.bovik." and of deleting the subscriptions for "bovik."

Licensing Information

The following copyright applies to the code:
 * Copyright (c) 1994-2008 Carnegie Mellon University.  All rights reserved.
 *
 * Redistribution and use in source and binary forms, with or without
 * modification, are permitted provided that the following conditions
 * are met:
 *
 * 1. Redistributions of source code must retain the above copyright
 *    notice, this list of conditions and the following disclaimer.
 *
 * 2. Redistributions in binary form must reproduce the above copyright
 *    notice, this list of conditions and the following disclaimer in
 *    the documentation and/or other materials provided with the
 *    distribution.
 *
 * 3. The name "Carnegie Mellon University" must not be used to
 *    endorse or promote products derived from this software without
 *    prior written permission. For permission or any legal
 *    details, please contact
 *      Carnegie Mellon University
 *      Center for Technology Transfer and Enterprise Creation
 *      4615 Forbes Avenue
 *      Suite 302
 *      Pittsburgh, PA  15213
 *      (412) 268-7393, fax: (412) 268-7395
 *      innovation@andrew.cmu.edu
 *
 * 4. Redistributions of any form whatsoever must retain the following
 *    acknowledgment:
 *    "This product includes software developed by Computing Services
 *     at Carnegie Mellon University (http://www.cmu.edu/computing/)."
 *
 * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO
 * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY
 * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE
 * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
 * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN
 * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING
 * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.

If you find this software useful and valuable in your work, we would welcome any support you can offer toward continuing this work. We gratefully accept contributions, whether intellectual or monetary. Intellectual contributions in the form of code or constructive collaboration can be directed via the feedback page.

If you wish to provide financial support to the Cyrus Project, send a check payable to "Carnegie Mellon University" to

      Project Cyrus
      Computing Services
      Carnegie Mellon University
      5000 Forbes Ave
      Pittsburgh, PA 15213
      USA

Summary

If you want to install the server, be sure to read the installation instructions in install.html.

More details about the server implementation is in the server overview document.

Please refer to Sending Feedback if you would like to submit a bug, feature request or (best of all) patch.

There is a mailing list. See the mailing list document for details.

A list of known problems can be found in the bugs file.

O'Reilly has a book out named Managing IMAP. While the book does not directly talk about the 2.0 code base, it provides very good information on the configuration and setup that can be applied to the newer code.


last modified: 2001/08/03 21:18:05
Return to the Cyrus IMAP Server Home Page cyrus-imapd-2.5.10/doc/faq.html0000644000175000017500000003111313001236020013141 00000000000000 Cyrus IMAP Server FAQ

Cyrus IMAP Server FAQ

  • POP-Before-SMTP It is not included in the default distribution because there is already a standard way of doing this with SMTP AUTH. Any good MTA and/or MUA should support SMTP AUTH, so we shouldn't have to create a hack in an unrelated service. However, if you would like to install it anyway, we recommend using DRAC, along with the patch available in contrib/drac_auth.patch.
  • Using NFS We don't recommend it. If you want to do it, it may possibly work but you may also lose your email or have corrupted cyrus.* files. You can look at the mailing list archives for more information.
  • Using AFS/Coda We don't recommend it. It's even less likely to work than NFS. If you want to do it, it may possibly work but you may also lose your email or have corrupted cyrus.* files. CMU's previous e-mail system, AMS, leveraged AFS extensively for storage (and transit) purposes. For various reasons it didn't scale particularly well and led to CMU's interest in IMAP.

    Cyrus was designed to use a local filesystem with Unix semantics and a working mmap()/write() combination. AFS doesn't provide these semantics so won't work correctly.

  • Virtual hosting - See virtual domains configuration.
  • dots in userids - you can have a '.' in your username IF, AND ONLY IF, you use the UNIX hierarchy convention.
  • renaming users - Supported, but try to make sure that the user is not, and cannot login when doing the rename. Otherwise user-meta may get corrupted and/or out of sync.
  • plus addressing - Plus addressing allows direct delivery to a particular mailbox (other than an INBOX). This is done in two ways.

    The first way allows delivery to a subfolder of a specific user's INBOX. This is done via an address of the form: username+mailfolder@domain, which will deliver to the user's INBOX.mailfolder folder (or altnamespace equivalent). This submailbox must allow the posting user the 'p' right (generally, this means 'anyone' must have the 'p' right), otherwise the message will just be filed into the user's INBOX.

    The second way is to form an address like [postuser]+mailfolder@domain. This will deliver into the mailbox 'mailfolder'. [postuser] is the string specified in the imapd.conf option of the same name, and may be the empty string. As before, the posting user will need to have the 'p' right on the mailbox.

    For both methods, if 'mailfolder' is more than one level deep, you will need to conform to the hierarchy separator appropriate to your site.

  • Performance/Capacity/Scaling - See the performance guide.

General Questions

Q: What are the advantages of LMTP?

A: LMTP protocol differs from SMTP in that it causes the Cyrus to return, after the final "." of the DATA command, one reply for each recipient. If, for example, a server is given a transaction for two recipients, delivery to the first succeeds, and delivery to the second encounters a temporary failure condition, the MTA will get a separate response for each recipient and will only have to reattempt to deliver it to the second recipient. If using SMTP, only a single temporary failure response would be returned, and the entire transaction would have to be reattempted.

Furthermore, LMTP is superior to invoking command-line delivery agents from the MTA in that most ESMTP extensions are supported by LMTP, without having to extend any interfaces.

Lastly, because LMTP can be run over TCP, it allows you to run SMTP (and spam/virus scanning) and mailbox access on separate servers, thus allowing better scalability.

Q: How do I configure my MTA?

A: See Configuring the Mail Transfer Agent

Q: How should I configure partitions to deal with a large number of users?

A: The key is not to over-subscribe any partitions. Avoid putting too many users on any one partition, such that read/write performance becomes unacceptable. Good RAID performance (plenty of read/write cache, and perhaps RAID 10 instead of RAID 5) will improve the number of users a partition can serve. To benefit from multiple partitions, each should be on its own set of disks, served by an unsaturated interface (FC, SCSI, SAS, SATA, etc) to the host running Cyrus.

See the performance guide or general performance guidelines. Also see metapartition_files and metapartition-name in imapd.conf.5 for additional configuration options which can help with performance, especially if you have access to high-speed storage (faster than disks).

Troubleshooting

Q: Why doesn't imapd/pop3d/nntpd/lmtpd/timsieved advertise PLAIN or plaintext login commands?

A: Unless otherwise configured, Cyrus services only advertise PLAIN or plaintext login commands on encrypted connections (SSL-wrapped connections or after a successful STARTTLS command). This behavior can be changed with the use of the allowplaintext option in imapd.conf.5.

Q: I'm getting syslog'd messages from the master process saying processes are "signaled to death by 10". What's up?

A: If you're using Berkeley DB 3.0.55, try installing some patches to Berkeley DB available from http://www.sleepycat.com/update/3.0.55/patch.3.0.55.html.

Q: I've used saslpasswd2 to create CRAM-MD5 secrets, but imapd doesn't say AUTH=CRAM-MD5. Why?

A: Make sure /etc/sasldb2 is readable by the Cyrus user.

Q: I'm using "sasl_pwcheck_method: saslauthd", but authentication isn't working.

A: Make sure that the saslauthd daemon is running (you'll want to start it when the system boots). imapd is unable to connect to saslauthd if the following message appears in the logs:

Dec  6 12:58:57 mail3.andrew.cmu.edu imapd[1297]: cannot connect to saslauthd server

Make sure that saslauthd is running and that the cyrus user can access the unix domain socket (defaults to /var/run/mux).

Q: I'm getting messages about "duplicate_prune". What's wrong?

A: These messages look like

Jan 14 13:46:24 grant ctl_deliver[9060]: duplicate_prune: opening
  /var/imap/deliverdb/deliver-x.db: No such file or directory
Jan 14 13:46:24 grant ctl_deliver[9060]: duplicate_prune: opening
  /var/imap/deliverdb/deliver-y.db: No such file or directory
Jan 14 13:46:24 grant ctl_deliver[9060]: duplicate_prune: opening
  /var/imap/deliverdb/deliver-z.db: No such file or directory

These messages are normal; one file is maintained for each user beginning with "x", "y", "z", etc. If you're first starting or you have no users beginning with these letters, these messages are completely normal and can be ignored.

Q: I'm getting a message about "imapd: could not getenv(CYRUS_SERVICE); exiting" in my imapd.log. What's wrong?

A: Remove all imap, pop, lmtp and sieve lines from [x]inetd.conf and restart [x]inetd. Cyrus is run out of its own "master" process.

Q: How do I use different SSL/TLS certificates for imap and pop?

A: Specify the different certs using the appropriate options in imapd.conf. Read imapd.conf(5) for details.

Q: My KPOP client is complaining about TLS keys. What should I do?

A: Disable TLS for the kpop service. Either set tls_pop3_cert_file to disabled in imapd.conf (which will also disable SSL/TLS for pop3), or use a separate config file for kpop. For example, change the kpop service in cyrus.conf to something like:

kpop    cmd="pop3d -k -C /etc/kpopd.conf" listen="kpop"

then copy /etc/imapd.conf to /etc/kpopd.conf and remove the tls_* options.

Q: Eudora 5.x can't connect using STARTTLS ("SSL Neogotiation Failed"). What should I do?

A: First, complain to QUALCOMM because their STARTTLS implementation is broken. Eudora doesn't support TLSv1 (per RFC2246) and Cyrus requires it. If you really need this before it is fixed in Eudora, remove or comment out the following lines in tls.c:

    if (tlsonly) {
        off |= SSL_OP_NO_SSLv2;
        off |= SSL_OP_NO_SSLv3;
    }
Q: I'm getting messages in imapd.log like "DBERROR db3: 16 lockers". What's wrong?

A: Nothing is wrong. These messages are logged whenever Berkeley DB encounters lock contention, but aren't necessarily problems. This is especially likely when you have an empty or small duplicate delivery database and are receiving a large volume of e-mail.

Berkeley DB 4.0 has a bug where the number of lockers isn't decremented properly, causing this number to be unreliable.

Q: All of the 8bit characters in the headers of messages that I receive are being changed to 'X's. What's going on?

A: 8-bit characters are illegal in message headers. Following the principle of "be liberal in what you accept, and strict in what you send", Cyrus converts them to Xs. (Without a character set, having the 8-bit characters replaced with Xs is just as good as having them be any other 8-bit character, especially for sorting and searching). Alternatively, you can set "reject8bit: t" in imapd.conf to reject the messages outright. It might also be reasonable for Cyrus to support the use of a default character set, however thus far no one has done the work to do so (it would also involve QP-encoding the corrupted headers).

Q: Why can't I delete any messages from my over-quota mailbox? I'm using a client with a 'trash folder'.

A: Trash folders, as they are commonly implemented (as actual IMAP mailboxes), do not fit the IMAP delete/expunge model very well. In fact, naive client implementations will get stuck in a situation where they cannot delete a message from a mailbox because they try to COPY it to the trash folder before deleting the message. This operation will fail due to the mailbox being over quota. This is separate from the fact that a specific mailbox name is not interoperable between clients (one might call it 'trash', another 'Trash', another 'Recycle Bin', etc)

Given the lack of protocol support for a trash folder, this is mostly a quality-of-implementation issue on the client side. There are a few options here:

  • Contact your client vendor to have the broken client fixed (one possibility is to have the client ask the user if they wish to permanantly delete the message if the COPY operation fails).
  • Stop using the 'trash mailbox' feature of your client (if possible).
  • Set a separate quota root on the 'trash folders' of users. This last option is significantly harder to do correctly, since it assumes that all clients that make use of a trash folder do so with the same folder name.
Q: How do I stop Cyrus from advertising the DIGEST-MD5 and CRAM-MD5 shared secret SASL mechanisms?

A: Not really a Cyrus IMAPd question, this can be fixed by just removing the SASL plugins from where Cyrus SASL installed them (if no other applications require them), or by using the sasl_mech_list imapd.conf option to list only the mechanisms that you require.


last modified: $Date: 2010/01/06 17:01:29 $
Return to the Cyrus IMAP Server Home Page cyrus-imapd-2.5.10/doc/text/0000755000175000017500000000000013001246663012567 500000000000000cyrus-imapd-2.5.10/doc/text/install-snmpmon0000644000175000017500000000077113001246663015572 00000000000000SNMP Monitoring TODO:finish this section. The majority of this section will get moved to the external CySNIIP docs and this will be stuff specific to the imapd. Cyrus uses an auxillary process called "tugowar", so named because there's a push-pull model. Various components of the Cyrus mail system push data to tugowar, and tugowar listens for SNMP queries (remote clients pull the data from tugowar). Configuring tugowar Testing the tugowar daemon SNMP data exported cyrus-imapd-2.5.10/doc/text/man0000644000175000017500000000201413001246663013202 00000000000000Cyrus IMAP Server Man Pages User Commands * cyradm(1) * imtest(1) * installsieve(1) * lmtptest(1) * mupdatetest(1) * nntptest(1) * pop3test(1) * shellsieve(1) * sivtest(1) * smtptest(1) Subroutines * imclient(3) File Formats * cyrus.conf(5) * imapd.conf(5) * krb.equiv(5) System Administration * arbitron(8) * chk_cyrus(8) * ctl_cyrusdb(8) * ctl_deliver(8) * ctl_mboxlist(8) * cyr_dbtool(8) * cyr_df(8) * cyr_expire(8) * deliver(8) * fetchnews(8) * fud(8) * httpd(8) * idled(8) * imapd(8) * ipurge(8) * lmtpd(8) * master(8) * mbexamine(8) * mbpath(8) * nntpd(8) * notifyd(8) * pop3d(8) * quota(8) * reconstruct(8) * smmapd(8) * squatter(8) * syncnews(8) * timsieved(8) * tls_prune(8) * unexpunge(8) cyrus-imapd-2.5.10/doc/text/install0000644000175000017500000000303413001246663014100 00000000000000 Installing and Configuring the Cyrus IMAP Server The Internet Message Access Protocol (IMAP) is an Internet standards-track protocol for accessing messages (mail, news, etc). The IMAP server stores and provides access to messages. The file doc/questions.html contains a list of questions we'd like to answer but haven't gotten to yet; doc/faq.html contains some answers that we have thought of. Please feel free to contribute! Please refer to Sending Feedback if you would like to submit a bug, feature request or patch. For detailed changes, refer to the file doc/changes in the distribution. Contents * Upgrading From Previous Versions * Prerequisites * Authenticating Users * Compiling the IMAP Server * Configuring the IMAP Server * Testing the IMAP Server * Administering Mailboxes * Installing SIEVE * SNMP Monitoring * Cyrus and Netnews * Cyrus HTTP (RSS, CalDAV, CardDAV, Timezone Service) * Virtual Domains * Cyrus Replication * Cyrus Murder: The IMAP Aggregator * Operating System Specific Notes * Performance Notes Other interesting stuff Here's some software that you may want to run with Cyrus. This software isn't maintained or supported by CMU, so please ask the maintainers for support. * Websieve, a web-based front-end for Sieve script management with Cyrus. * Sendmail, the most popular MTA around. * Postfix, a popular competitor MTA. cyrus-imapd-2.5.10/doc/text/install-murder0000644000175000017500000004023013001246663015373 00000000000000Installing The Cyrus Murder The Cyrus Murder provides the ability to horizontally scale your Cyrus IMAP environment across multiple servers. It is similar in nature to various proxy solutions such as nginx or perdition with the difference being that Murder offers a uniform namespace. If you're not currently using shared mailboxes and you don't intend to use shared mailboxes in the future, you should probably just consider using a simple proxy solution. Introduction & Assumptions This document is intended to be a guide to the configuration of a Cyrus IMAP Aggregator, aka Cyrus Murder. It is recommended that you review this document to become familliar with the concepts at work. This document is a work in progress and is at this point incomplete. This document assumes that you have successfully been able to setup atleast one Cyrus IMAP server. This server will become your first backend server. It also assumes that you are familliar with the administration and day to day operations of the Cyrus IMAP server and the SASL authentication library. If you feel uncomfortable with this, please refer to the rest of the documentation first. There is a diagram that shows the interactions of the various components of the Cyrus Murder which may be helpful in understanding the "big picture". Installation You will need to build Cyrus IMAPd with the --enable-murder configure option. This builds the proxyds and the associated utilities. Requirements * Atleast one Cyrus IMAP server. If there are more than one, their name spaces must not conflict. That is, all the mailbox names must be unique (or in different namespaces) * Atleast one machine that will become the first Frontend Server. * One machine to become the MUPDATE master server. This can be the same as one of your frontend servers. Configuring the MUPDATE Master The mupdate master server needs to be running the mupdate service in master mode. Note that you can have the MUPDATE master be one of your frontend machines, just do not configure a slave mupdate process on this machine. To configure an mupdate master, you will want a cyrus.conf that includes a line similar to the following in the SERVICES section: mupdate cmd="/usr/cyrus/bin/mupdate -m" listen=3905 prefork=1 Note the "-m" option to tell mupdate that it should start in master mode. You will also need to configure atleast a skeleton imapd.conf that defines the configdirectory, a bogus partition-default and the admins that can authenticate to the server. Note that slave mupdate servers as well as the backend servers will need to be able to authenticate as admins on the master. Here is a very simple imapd.conf for a master server: configdirectory: /imap/conf partition-default: /tmp admins: mupdateslave1 backend1 You will also need to configure SASL to properly allow authentication in your enviornment. Setting up the backends to push changes to the MUPDATE Master On the backends, configuration to be a part of a murder is easy. You just need to configure the backend to be a part of the murder. To do this, set the mupdate_server option in imapd.conf. Depending on what authentication mechanisms you are using, you may also want to set some or all of the following: * mupdate_username * mupdate_authname * mupdate_realm * mupdate_password Once these settings are successfully made, any mailbox operation on the backend will be sent to the mupdate master for confirmation and entry into the mupdate database. You must also configure atleast one user/group using the proxyservers imapd.conf option. This user should not be an administrator, since this means that anyone who can get ahold of your proxy servers now has full administrative control on your backend. Example: admins: cyrus proxyservers: murder Keep in mind that you will need to create the proxy user(s) and be sure that they can authenticate to the backend as well. NOTE: proxyservers should not be set on your frontends. It is also used to determine which servers to create mailboxes on. Importing the database from the backend Importing the current mailboxes database is easy, as there is a ctl_mboxlist option to do so. To do the first synchronization, simply change to the cyrus user, and issue a ctl_mboxlist -m. Note that you may wish to issue a ctl_mboxlist -mw first to be sure you understand all the operations that this command will perform, since it does require that all mailboxes are unique in the murder namespace. If everything is configured properly, the mailbox database of the current host will dump to the mupdate master. If there are problems, the most likely cause is a misconfiguration of the authentication settings, or that mupdate might not be running on the master. Using mupdatetest may be helpful in this case (it establishes an authenticated connection to the mupdate server, if it can). It is also useful to have the backends automatically resync the state of their local mailboxes database with the master on start up. You can configure this by adding the following to the START section of cyrus.conf on the backends: mupdatepush cmd="ctl_mboxlist -m" This will perform synchronization with the mupdate master each time the backend restarts, bringing the mupdate database up to date with the contents of the backend (and performing ACTIVATE and DELETES as needed to do so). Warning: If somehow a mailbox exists on two (or more) backend servers, each time one of them synchronizes its database that backend server will become authoritative. Though this should not happen during normal operation of the murder (because of the consistancy guarantees of the MUPDATE protocol, and the fact that mailbox operations are denied if the mupdate master is down), it is possible when first creating the mupdate database or when bringing a new backend server into the murder. Configuring the frontends Configuring the frontends is a two step process. First, you want to set mupdate_server (and friends) as you did for the backends above. However, because the frontends only talk to the mupdate master via a slave running on the local machine, you will also need to set up a slave on the same machine, in the SERVICES section of cyrus.conf, like so: # mupdate database service - must prefork atleast 1 mupdate cmd="mupdate" listen=3905 prefork=1 Note that as this is a threaded service, you must prefork atleast 1 of them so that the database can be synchronized at startup. Otherwise, the service will not start running until after you recieve an mupdate client connection to the slave (which is not a recommended configuration at this point). You will also want to change all of your imapd entries to be proxyd, and all of your lmtpd entries to be lmtpproxyd. That is, you will probably have a SERVICES section that looks more like this now: mupdate cmd="/usr/cyrus/bin/mupdate" listen=3905 prefork=1 imap cmd="proxyd" listen="imap" prefork=5 imaps cmd="proxyd -s" listen="imaps" prefork=1 pop3 cmd="pop3d" listen="pop3" prefork=0 pop3s cmd="pop3d -s" listen="pop3s" prefork=0 kpop cmd="pop3d -k" listen="kpop" prefork=0 nntp cmd="nntpd" listen="nntp" prefork=0 nntps cmd="nntpd -s" listen="nntps" prefork=0 sieve cmd="timsieved" listen="sieve" prefork=0 lmtp cmd="lmtpproxyd" listen="/var/imap/socket/lmtp" prefork=0 Note that timsieved does not need a proxy daemon, the managesieve protocol deals with the murder with referrals to the backends internally. Additionally, you will need entries in imapd.conf to indicate the proxy auth name and passwords (if you are using a SASL mechanism that requires them) to the backends, for example, if your backends are mail1.andrew.cmu.edu and mail2.andrew.cmu.edu with passwords of foo and bar, and an auth name of murder: mail1_password: foo mail2_password: bar proxy_authname: murder If your SASL mechanism does not require authnames or passwords (e.g. KERBEROS_V4), then this is not required. Note that we used the same authname as the configured in the proxyservers line in the backend's imapd.conf above. When you start master on the frontend, a local mailboxes database should automatically synchronize itself with the contents of the mupdate master, and you should be ready to go. Your clients should connect to the frontends, and the frontends will proxy or refer as applicable to the blackend servers. Additional backend configuration If your authentication system requires usernames, passwords, etc, to authenticate (e.g. it isn't Kerberos), then you will also need to specify proxy_authname (and friends) in the backend imapd.confs as well. This is so that the backends can authenticate to eachother to facilitate maibox moves. (Backend machines will need to be full admins). Delivering mail To deliver mail to your Murder, configure your MTA just as you did before, but instead of connecting directly to lmtpd, it should connect to lmtpproxyd. You can connect to the lmtpproxyd running on the frontend machines, or you can install master and lmtpproxyd on your SMTP servers. Administration Keeping the database synced Consistancy in the database is maintained by pushing the current status of the backends to the master, and having the frontends stay up to date with the master's database. Since the frontends resync themselves entirely when they startup, downtime should not at all be a problem. (While they are up they should be continously recieving database updates, as well as when they lose connection to the master, they will try to reconnect and resync their database upon reconnection) Provided that the namespace of the backend servers is kept discrete (with no mailboxes existing on the same server), it is not a big deal to resync the mupdate master using ctl_mboxlist -m. If two servers do have the same mailbox, this will need to be resolved before database consistancy can be guranteed. Moving Mailboxes between backends There is currently no 100% foolproof way to do this, however, if you issue a rename command to a frontend (as you would to move a mailbox between partitions), and replace the partition name with the name of the new backend, it will move the mailbox to the indicated backend. You can also use the format backend.domain.com!partition to move to a specific partition (otherwise the default partition will be used). In cyradm, this looks like: cyrus.andrew.cmu.edu> rename user.bcyrus user.bcyrus mail2.andrew.cmu.edu!u2 Note that since seen state is stored per-user, it is possible that when moving a shared mailbox users will have strange effects. The general rule is that moving an INBOX will move the entire user (including all sub-mailboxes to the INBOX, and seen state, and subscriptions, and sieve scripts, etc). The seen state is merged with the seen state on the new backend, so that no data is lost (seen state is also the only part left behind on the source backend). In the case of any other mailbox, however, only that individual mailbox is moved. If it is a quota root, the new quota root is instated on the new server, but otherwise quotas can appear to be violated, since each backend only takes care of its own quota. In general, its better to leave trees of mailboxes on the same server, and not move submailboxes of inboxes between servers. Adding additional backend servers This is very easy to do, simply configure an empty backend server and set its mupdate_server parameter to point at the mupdate master. Then, issue mailbox creates to it as you would any other backend server. Backups xxx, need to write stuff. You don't need to really backup the data on the mupdate master or slaves, since this data can all be generated directly from the backends quite easily. Gotchyas * Clients dealing with a pool of frontend servers - Some clients may not be terribly efficient caching connections to a pool of imap servers, this isn't a problem, per se, but it may mean that you will see many more authentications than you are used to. * Kerberos issues - If you are using kerberos authentication, you will want to ensure that all your machines are keyed properly, as we have seen problems with different clients trying to authenticate to different services (e.g. imap.imap-pool instead of imap.pool-frontend-1), so test the clients in use in your enviornment and be sure that they work with whatever keying scheme you use. * Clients dealing with referrals - Some clients (we've had particuar trouble with pine, though most of these issues have now been resolved and new versions should be OK (that is, pine > 4.44), but as referrals have not been extensively used by any IMAP server until now, referrals are very likely to not work correctly or have surprising effects. * Clients dealing with getting a NO on LSUB commands - Some clients (Outlook, for example) may behave poorly if an LSUB command returns a NO, which may be the case if the backend server with the user's inbox is down. We have, for example, seen this result in the deletion of the disconnected message cache. * Behavior of cyradm / some mailbox operations - The behavior of some administrative commands might be slightly unexpected. For example, you can only issue a SETQUOTA to a frontend server if the entire mailbox tree underneath where you are setting the quota exists on the same backend server, otherwise you will need to connect directly to the backend servers to perform the needed changes. Similarally, mailboxes will be created on the same backend server that their parent is in. In order to create them on a different server (or to create a new top level mailbox) you will need to connect directly to the desired backend server. * Subscriptions - If users want subscribe to a mailbox other than on their backend home server, they won't be able to, unless you set "allowallsubscribe: t" in the backend imapd.confs. This essentially lets any string be subscribed to successfully. * Restarting the mupdate master - Because ctl_cyrusdb -r clears reservations on mailbox, if you restart the mupdate master (and run recovery), then this could (we suspect, very rarely) lead to inconsistancies in the mupdate database. Troubleshooting & when things go wrong * Mailbox operations are being denied - This is an indication that the mupdate master may be down. Restart it. * Mailbox operations are not being seen by one or more frontends - This indicates that the mupdate process on a slave may have died, you may need to restart master. Alternatively, mupdate will retry connections every 20 seconds or so for about 20 attempts if the master does go down. * A frontend's mailboxes.db is corrupt / out of sync - Restart master on the frontend, and have the mupdate process resynch the local database. You may need to remove the local mailboxes database if the corruption is extreme. * A mailbox's location keeps switching between two (or more) backend hosts. - It probably actually exists on both hosts. Delete the mailbox from all but one of the hosts, and run a ctl_mboxlist -m on the one where you want it to actually live. * Databases are never created on the frontends/slaves - Check to ensure that the mupdate slave process is started, (is prefork=1) cyrus-imapd-2.5.10/doc/text/anoncvs0000644000175000017500000000516013001246663014103 00000000000000Cyrus IMAP: Anonymous CVS Access This file is for those who are reading Cyrus sources via anonymous CVS, or those who would like to. If you're someone who would like to work with the source code and get more frequent updates, keeping in mind that we take some liberties with proper CVS use, you might want to get Cyrus via anonymous CVS. If you're not a programmer, please don't do this. If you're not at least a little experienced with C, configure, and IMAP, please stick with the tarball releases at ftp://ftp.andrew.cmu.edu/pub/cyrus-mail/. To get to the repository, get a version of CVS with client-server support (anything remotely recent has this, I think) and do this: cvs -d :pserver:anoncvs@cvs.andrew.cmu.edu:/cvs login (enter "anonymous" as the password) cvs -d :pserver:anoncvs@cvs.andrew.cmu.edu:/cvs co -d cyrus-imapd cyrus (the first -d specifies the CVSROOT, in this case, our CVS server, and a path to the CVS repository; co says "check out", -d says "and stick it in the directory cyrus-imapd", and "cyrus" specifies the "cyrus" collection). The password is "anonymous". You will need autoconf, yacc (bison) and lex (flex) to build CVS from the repository because we don't keep generated files in the repository, along with the usual tools to build Cyrus (a compiler, a Unix box, a network.) To create the configure script, do the following: aclocal -I cmulocal autoheader autoconf Read access to the repository is availible to anyone via cvs.andrew.cmu.edu. Write access is availible to only a few people at CMU. Please note that the version in the repository is not the version we are running. We have a seperate system that resembles version control for releases of software on the Andrew system, and sometimes changes don't get propigated back to CVS. What is here is supposed to be stable. It's supposed to work, and compile, and not have amazingly broken changes that can't possibly work. But that may not be the case--and since you decided to use CVS, you shouldn't complain when something doesn't work. You should submit a patch. There is no warranty on the Cyrus software. There is no warranty on anything in CVS, and even less of a guarantee of it working. (There. You've been warned.) Please refer to Sending Feedback if you would like to submit a bug, feature request or (best of all) patch. Thanks to Ryan Troll for putting the time in to make the CVS server work and actually documenting it. cyrus-imapd-2.5.10/doc/text/ag0000644000175000017500000000024113001246663013016 00000000000000Cyrus IMAP Server: Cyrus Murder Concepts * Abstract * Overview * Architecture * Implementation * Analysis * Futures cyrus-imapd-2.5.10/doc/text/index0000644000175000017500000000276013001246663013546 00000000000000Cyrus IMAP Server, version 2.5 IMAP (Internet Message Access Protocol) is an Internet standards-track protocol for accessing messages (mail, bboards, news, etc). The Cyrus IMAP server differs from other IMAP server implementations in that it is generally intended to be run on sealed servers, where normal users are not permitted to log in. The mailbox database is stored in parts of the filesystem that are private to the Cyrus IMAP system. All user access to messages is through the IMAP, POP3, KPOP or NNTP protocols. The private mailbox database design gives the server large advantages in efficiency, scalability, and administratability. Multiple concurrent read/write connections to the same mailbox are permitted. The server supports access control lists on mailboxes and storage quotas on mailbox hierarchies. The Cyrus project is the implementation of IMAP servers by the Carnegie Mellon University Computing Services Department. Over the next few months, we will be releasing components of this server, which will provide better mail security and easier mail administration. The Cyrus IMAP Server Distribution Cyrus IMAP Server distribution Documentation * General release information * Overview and Concepts * Installing the Cyrus IMAP Server * Changes since the last release * Frequently Asked Questions * Man Pages * Protocol Specifications * Internal Documentation cyrus-imapd-2.5.10/doc/text/sieve0000644000175000017500000000064713001246663013554 00000000000000 Sieve: A mail filtering language Sieve is a Internet standards-track protocol for filtering messages on delivery. The Cyrus Sieve implementation supports filing messages into specific folders, forwarding messages, rejecting messages, and the standard vacation function. It can reply to messages based on headers or envelope information. Cyrus Sieve Some simple sample Sieve scripts cyrus-imapd-2.5.10/doc/text/install-virtdomains0000644000175000017500000001727613001246663016452 00000000000000Configuring Virtual Domains Introduction Virtual domains is the practice of hosting a service for more than one domain on one server. Cyrus IMAP has the ability to host IMAP/POP mailboxes for multiple domains (e.g., test@example.com and test@example.net) on a single server or Murder. In order to accomplish this, Cyrus needs to know which domain to look in when a mailbox is accessed. There are two ways in which Cyrus can determine the domain: * Fully qualified userid - the client logs in with a userid containing the domain in which the user belongs (e.g., test@example.com or test%example.net) * IP address - the server looks up the domain based on the IP address of the receiving interface (useful for servers with multiple NICs or using IP aliasing) Both of these methods are active if the virtdomains option is set to on (or yes, 1, true) and can be used in conjunction with one another. If the virtdomains option is set to userid, then only the first method is used. Note that a fully qualified userid takes precedence over a domain obtained from the IP address. Concepts Perhaps the most important part of this process is to understand the changes in the paradigm. * Everyone is in a domain - It's best to think of every user as existing inside a domain. Unqualified users are technically inside the defaultdomain. * Names can be qualified - Global admins can reference mailboxes and IDs by qualified names. That is, for any given mailbox command, you can add @domain to the end of the mailbox name. Here are some examples: * cyradm> create user.jill@example.net (create a user) * cyradm> create user.rick@example.net (create another user) * cyradm> setquota user.rick@example.net 50000 (define a quota) * cyradm> setaclmailbox user.rick@example.net jill@example.net read (give Jill read access to Rick's mailbox) * cyradm> listmailbox *@example.net (list all mailboxes in the example.net domain) * Each mailbox exists in only one domain * Domains are mutually exclusive - Users only have access to mailboxes within their own domain (intra-domain). The following example will not work: setacl user.jill@herdomain.com rick@hisdomain.com read. * Global and Domain admins - The Cyrus virtual domains implementation supports per-domain administrators as well as global (inter-domain) administrators. Domain-specific administrators are specified with a fully qualified userid in the admins option (e.g., admin@example.net) and only have access to mailboxes in the associated domain. Global administrators are specified with unqualified userids. Quick Start 1. Add virtdomains: yes to imapd.conf 2. Add a defaultdomain entry to imapd.conf 3. Use cyradm (as a global or domain admin) to create mailboxes for each domain. Configuration Support for virtual domains is enabled by turning on the virtdomains option in imapd.conf. When upgrading from a single domain installation to a virtual domain installation, the name of the existing domain (domain of the server hostname) should be specified using the defaultdomain option in imapd.conf. This allows users to continue to access their mailboxes using unqualified userids. For example, if the primary IP address on your server resolves to 'www.xxx.yyy.zzz', then set defaultdomain to 'xxx.yyy.zzz'. Even for new installations, it is recommended that the "real" domain of the server (domain of its primary hostname), be set to the defaultdomain. See Administrators below for further discussion. Here is a sample imapd.conf with a minimal set of configuration options. configdirectory: /var/imap partition-default: /var/spool/imap admins: admin rick.admin@hisdomain.com jill.admin@herdomain.net virtdomains: yes defaultdomain: exampleisp.net This example has three domains: exampleisp.net, hisdomain.com, and herdomain.net. admin can administer all three domains, while rick.admin@hisdomain.com and jill.admin@herdomain.net can only administer their respective domains. Note that everyday users should not be administrators. In the above example, Jill and Rick have separate administrative accounts for their domains. Multiple IP Addresses In order to use a multiple IP address configuration, the server must be able to do a reverse lookup on the IP address to determine the hostname of the receiving interface. For example: 192.168.0.1 -> mail.example.com 192.168.0.2 -> mail.example.net 192.168.0.3 -> mail.foo.bar Once the server obtains the fully qualified hostname of the interface, it removes the localpart (i.e., 'mail') and uses the remainder as the domain for any user that logs in. This address to hostname mapping would usually be done via DNS, /etc/hosts, NIS, etc. Configuration of the various naming services is beyond the scope of this document. Delivering mail To deliver mail to your virtual domains, configure your MTA so that the envelope recipient (RCPT TO) passed to lmtpd is fully qualified with the correct domain. Configuring Sendmail In general, follow the basic configuration instructions. Here are a few caveats: * It is easiest to use the mailertable to route mail to Cyrus, rather than adding the domain to the local-host-names file ($w). This prevents Sendmail from changing the domain name to the local host name. example.com cyrusv2:/var/imap/socket/lmtp * You'll have to use the Cyrus mailer in LMTP mode, and you'll have to change the mailer flags so that it provides the full domain while communicating via LMTP. Specifically these changes: S=EnvFromSMTP/HdrFromSMTP, R=EnvToSMTP Mail Clients The only changes you'll need to make to mail clients is to change usernames to the fully qualified domain names, i.e., user@example.com. Note that to support some mail clients, the user%example.com form of userid is also supported. Users in the default domain will not need to reconfigure their clients (as unqualified userids are assumed to be in the default domain). Administration The Cyrus virtual domains implementation supports per-domain administrators as well as "global" (inter-domain) administrators. Domain-specific administrators are specified with a fully qualified userid in the admins option (e.g., admin@example.net) and only have access to mailboxes in the associated domain. Mailbox names should be specified in the same fashion as on a single domain configuration. Global administrators are specified with an unqualified userid in the admins option and have access to any mailbox on the server. Because global admins use unqualified userids, they belong to the defaultdomain. As a result, you CANNOT have a global admin without specifying a defaultdomain. Note that when trying to login as a global admin to a multi-homed server from a remote machine, it might be necessary to fully qualify the userid with the defaultdomain. Global admins must use mailbox@domain syntax when specifying mailboxes outside of the defaultdomain. Examples (using cyradm): To create a new INBOX for user 'test' in defaultdomain: cm user.test To create a new INBOX for user 'test' in domain 'example.com': cm user.test@example.com To list all mailboxes in domain 'example.com': lm *@example.com cyrus-imapd-2.5.10/doc/text/altnamespace0000644000175000017500000000677413001246663015105 00000000000000 Cyrus IMAP Server: Alternate Namespace This document describes the alternatives to the standard mailbox presentation method. These alternatives may be used together or independently. The namespace options do NOT change the rules governing the behavior of mailboxes (as described in overview.html) or how mailboxes are stored on the filesystem. The mailboxes are ALWAYS stored using the netnews convention and internal namespace. When configured to use one (or both) of the options below, the server simply translates mailbox names between the internal names and the external names when used by the client in the IMAP protocol and in Sieve scripts. This design allows the namespace to be changed at runtime (even on a running server) without having to reconfigure the server. This also means that one mailstore can support multiple namespaces if configured correctly. NOTE: If you are upgrading an existing server which uses timsieved to manage Sieve scripts and choose to enable one of the namespace options, you should run the script "tools/translatesieve" after configuring the namespace option(s). This script will translate the folder names in fileinto actions. Alternate Mailbox Namespace The alternate namespace allows a user's personal mailboxes to appear as if they reside at the same level as that user's INBOX as opposed to children of it. For example, if user "bovik" had a personal "work" mailbox, it would appear to user "bovik" as "work" instead of "INBOX.work" as it would in the standard namespace. This configuration requires that a special prefix be used for shared folders (to distinguish them from personal folders) and for accessing other users' folders. By default, the prefix for shared folders is "Shared Folders" and the prefix for other users folders is "Other Users". For example, a shared folder "foo" in the standard namespace would be presented as "Shared Folders.foo" in the alternate namespace. NOTE: All tools for administering the server, including admins using cyradm, always use the internal namespace. Configuring the Alternate Namespace To use the alternate namespace, turn on the altnamespace option in /etc/imapd.conf. The prefixes used for shared folders and other users folders can be changed from the defaults by setting the sharedprefix and userprefix options respectively. UNIX Hierarchy Convention The UNIX hierarchy convention uses the traditional UNIX separator character ("/") to delimit levels of the mailbox hierarchy instead of the netnews character ("."). For example, if user "bovik" had a personal "work" mailbox, it would appear to user "bovik" as "INBOX/work" in the standard namespace. When the UNIX hierarchy convention is used, the "." character MAY be used in mailbox names, including user names. In order to maintain backwards compatibility with the internal namespace, all "." characters are translated to a benign character (currently "^") before any data is stored to disk. For example, if user "elmer.fudd" had a personal "rabbit.holes" mailbox, it would be stored as "user.elmer^fud.rabbit^holes" in the internal namespace. It is important to remember this phenomenon if/when reverting back to the netnews hierarchy convention. Configuring the UNIX Hierarchy Convention To use the UNIX hierarchy separator, turn on the unixhierarchysep option in /etc/imapd.conf. cyrus-imapd-2.5.10/doc/text/install-compile0000644000175000017500000002346313001246663015536 00000000000000Compiling the IMAP Server Once you have unpacked the files by extracting the tar archive, "cd" to the "cyrus-imapd-NNNN" directory where NNNN is the version number. The configuration files and various subdirectories are stored there. In the directory that the configure file is in, type "./configure" to configure the software. Please continue to read this document as there are switches to ./configure that may apply to you. configure Overview The "configure" shell script attempts to guess correct values for various system-dependent variables used during compilation. It uses those values to create a "Makefile" in each directory of the package. Finally, it creates a shell script "config.status" that you can run in the future to recreate the current configuration, a file "config.cache" that saves the results of its tests to speed up reconfiguring, and a file "config.log" containing compiler output (useful mainly for debugging "configure"). Running "configure" takes awhile. While running, it prints some messages telling which features it is checking for. You can compile the package in a different directory from the one containing the source code. Doing so allows you to compile it on more than one kind of computer at the same time. To do this, you must use a version of "make" that supports the "VPATH" variable, such as GNU "make". "cd" to the directory where you want the object files and executables to go and run the "configure" script. "configure" automatically checks for the source code in the directory that "configure" is in and in "..". By default, "make install" will install files (other than server-specific programs) in "/usr/local/bin", "/usr/local/man", etc. You can specify an installation prefix other than "/usr/local" by giving "configure" the option "--prefix=PATH". You can specify separate installation prefixes for architecture-specific files and architecture-independent files. If you give "configure" the option "--exec-prefix=PATH", the package will use PATH as the prefix for installing programs and libraries. Documentation and other data files will still use the regular prefix. By default, "make install" will install the server-specific programs in "/usr/cyrus/bin". You can specify a server-specific installation prefix other than "/usr/cyrus" by giving "configure" the option "--with-cyrus-prefix=PATH". Options to configure Here are a list of switches that can be used with "configure". --help Print a summary of the options to "configure", and exit. --with-auth=METHOD Specifies the authorization (group membership) module to use. Currently implemented authorization modules are: unix Unix /etc/passwd and /etc/group file krb Kerberos principals (requires Kerberos libraries). Optionally, specify where to find Kerberos v4 with "--with-krb=DIR" IMPORTANT: The Kerberos v4 support requires the DES library. Some vendor distributions of Kerberos, including the one with Solaris, do not have this support and cannot be used. krb_pts Kerberos principals with AFS PTserver groups (requires Kerberos and AFS libraries). Optionally, specify where the AFS libraries are found with "--with-afs=PATH". Also requires krb support as above. Any method of authenticating with SASL can be used with any authorization module. --with-krb=PATH Specifies where to find the Kerberos library. --with-com_err=PATH Specifies where to find the com_err environment. --with-cyrus-group=USER Specifies the group used for installing setguid programs. By default, configure uses "mail". --with-cyrus-prefix=PATH Change the location of the server software. By default, the cyrus-prefix is /usr/cyrus. --with-cyrus-user=USER Specifies the userid that the Cyrus IMAP server will run as. By default, configure uses "cyrus". --with-dbdir=PATH Specifies where to find the Berkeley DB library. --with-duplicate-db=DB Specifies which database backend to use for the duplicate delivery database. By default, configure uses "berkeley_nosync". --with-mboxlist-db=DB Specifies which database backend to use for the mailbox list. By default, configure uses "berkeley". --with-seen-db=DB Specifies which database backend to use for the seen state. By default, configure uses "flat". --with-subs-db=DB Specifies which database backend to use for the subscriptions list. By default, configure uses "flat". --with-tls-db=DB Specifies which database backend to use for the TLS cache. By default, configure uses "berkeley_nosync". --with-idle=METHOD Specifies the IMAP IDLE method to use. Currently implemented IDLE methods are: idled Use the IDLE daemon. The IDLE daemon listens on a UNIX socket for messages from lmtpd/imapd/pop3d that a mailbox has been updated. The daemon then signals those (if any) imapd that are idling on the mailbox to check for the changes. poll Periodically poll the mailbox for changes. no Disable IMAP IDLE. By default, configure uses "poll". --with-lock=METHOD Specifies the locking method to use. Currently implemented locking methods are: flock flock() locking fcntl fcntl() locking By default, configure uses "fcntl" if the "fcntl()" function exists, "flock" otherwise. --with-openssl=PATH Specifies where to find the OpenSSL library. --with-egd-socket=FILE Specifies which socket to use to connect to the Entropy Gathering Daemon. --with-perl=PATH Specifies where to find the Perl binary (full path, including name of binary). --with-sasl=PATH Specifies the path to the directories containing the library (.../lib) and include (.../include) files for libsasl. --with-statedir=PATH Specifies the directory used for communicating with various daemons. By default, configure uses "/var". --with-libwrap=PATH Specifies where to find the TCP wrappers library. --with-ucdsnmp=PATH Specifies where to find the SNMP library. --with-zephyr=PATH Specifies where to find the Zephyr library (for notifyd). --enable-listext Enables support for LISTEXT extension. --enable-murder Enables support for IMAP Murder. --enable-netscapehack Enables support for X-NETSCAPE extension (administration URLs). --disable-sieve By default, Sieve support is enabled. Use --disable-sieve to disable compiling the Sieve library and to disable all Sieve support. --disable-cyradm Do not compile the cyradm administrative client. --disable-server Do not compile the IMAP server programs. Run configure --help for further configuration options. Some systems require unusual options for compilation or linking that the "configure" script does not know about. You can give "configure" initial values for variables by setting them in the environment. Using a Bourne-compatible shell, you can do that on the command line like this: CC=c89 CFLAGS=-O2 LIBS=-lposix ./configure Or on systems that have the "env" program, you can do it like this: env CPPFLAGS=-I/usr/local/include LDFLAGS=-s ./configure The "make" variables that you might want to override with environment variables when running "configure" are: CC C compiler program. Default is "cc", or "gcc" if "gcc" is in your PATH. (For "CC", any value given in the environment overrides the value that "configure" would choose.) CFLAGS Debugging and optimization options for the C compiler. CPPFLAGS Header file search directory ("-IDIR") and any other miscellaneous options for the C preprocessor and compiler. If it is not set in the environment when "configure" runs, the default value is empty. LDFLAGS Stripping ("-s") and any other miscellaneous options for the linker. If it is not set in the environment when "configure" runs, the default value is empty. DEFS Configuration options, in the form "-Dfoo -Dbar ..." LIBS Libraries to link with, in the form "-lfoo -lbar ..." (For "DEFS" and "LIBS", any value given in the environment is added to the value that "configure" chooses.) If you need to do unusual things to compile the package, we encourage you to figure out how "configure" could check whether to do them. After doing so, please send us a patch! Instructions for doing so can be found on the feedback page. The file "configure.ac" is used as a template to create "configure" by a program called "autoconf". You will only need it if you want to regenerate "configure" using a newer version of "autoconf". Once you have successfully run "configure", execute the following commands: make all CFLAGS=-O If you want, you can override the "make" variables CFLAGS and LDFLAGS by entering the following: make all CFLAGS=-O2 LDFLAGS=-s cyrus-imapd-2.5.10/doc/text/readme0000644000175000017500000001703113001246663013671 00000000000000 Cyrus IMAP Server Release Information IMAP (Internet Message Access Protocol) is an Internet standards-track protocol for accessing messages (mail, bboards, news, etc). The Cyrus IMAP server differs from other IMAP server implementations in that it is generally intended to be run on "sealed" servers, where normal users are not permitted to log in. The mailbox database is stored in parts of the filesystem that are private to the Cyrus IMAP system. All user access to mail is through the IMAP, NNTP, POP3, or KPOP protocols. The private mailbox database design gives the server large advantages in efficiency, scalability, and administratability. Multiple concurrent read/write connections to the same mailbox are permitted. The server supports access control lists on mailboxes and storage quotas on mailbox hierarchies. Features The Cyrus server supports the IMAP4rev1 protocol described in RFC 3501. IMAP4rev1 has been approved as a proposed standard. Character sets supported for searching are: us-ascii, iso-8859-1, iso-8859-2, iso-8859-3, iso-8859-4, iso-8859-5, iso-8859-6, iso-8859-7, iso-8859-8, iso-8859-9, koi8-r, iso-2022-jp, iso-2022-kr, gb2312, big5, iso-8859-15, windows-1252, windows-1256. The character mapping tables most likely contain errors. The server supports any authentication mechanism available from the SASL library. Currently, support includes: KERBEROS_V4, GSSAPI, CRAM-MD5, DIGEST-MD5, OTP, PLAIN, and STARTTLS. The server supports imaps/pop3s/nntps (IMAP/POP3/NNTP encrypted using SSL). The server makes an attempt to do single instance store where possible when an email message is addressed to multiple recipients. We current support the following IMAP capabilities: IMAP4 IMAP4rev1 ACL RIGHTS=kxte QUOTA LITERAL+ NAMESPACE UIDPLUS ID NO_ATOMIC_RENAME UNSELECT CHILDREN MULTIAPPEND SORT SORT=MODSEQ THREAD=ORDEREDSUBJECT THREAD=REFERENCES ANNOTATEMORE CATENATE CONDSTORE URLAUTH IDLE STARTTLS SASL-IR. The server supports SIEVE for server side email filtering. Upgrade Caveats This section reserved for WARNING WARNING WARNING comments. Note that the replication protocol currently does not have the facility to support the IMAP CONDSTORE extension (modification sequences). It is recommended that you do not try to use both CONDSTORE and replication at this time. The deficiencies in the replication protocol will be fixed in version 2.3.9. Installation Overview This system should be expected to have the same order-of-magnitude installation complexity as a netnews system. Maintenance should have similar complexity, except administrators will have to deal with creation and deletion of users and will have the option of managing quotas and access control lists. This package is distributed as a source only release. It is expected that you can compile and configure software. Installation instructions are in the install.html. Please be sure to read this document. A detailed overview of the server is available in overview.html. This server has been successfully installed on a number of Unix systems. We run the software under SPARC Solaris 8. Please refer to os.html for operating system specific issues. Server Notes The mailbox namespace is like that for netnews--hierarchical names separated by the "." character. Mailboxes without a parent may only be created by an administrator. Mailboxes with a parent may be created as the ACL (Access Control List) on the parent mailbox permits. Users' personal mailboxes are under the "user" hierarchy. The names of the personal mailboxes for user "bovik" all start with the prefix "user.bovik.". The mailbox "user.bovik" is special in that it is presented to user "bovik" as if it were named "INBOX". Creating the mailbox "user.bovik" is equivalent to creating an account for user "bovik"--it permits "bovik" to receive mail, create personal mailboxes, and subscribe to mailboxes. Deleting the mailbox "user.bovik" has the special-case side-effect of deleting all mailboxes starting with "user.bovik." and of deleting the subscriptions for "bovik." Licensing Information The following copyright applies to the code: * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. If you find this software useful and valuable in your work, we would welcome any support you can offer toward continuing this work. We gratefully accept contributions, whether intellectual or monetary. Intellectual contributions in the form of code or constructive collaboration can be directed via the feedback page. If you wish to provide financial support to the Cyrus Project, send a check payable to "Carnegie Mellon University" to Project Cyrus Computing Services Carnegie Mellon University 5000 Forbes Ave Pittsburgh, PA 15213 USA Summary If you want to install the server, be sure to read the installation instructions in install.html. More details about the server implementation is in the server overview document. Please refer to Sending Feedback if you would like to submit a bug, feature request or (best of all) patch. There is a mailing list. See the mailing list document for details. A list of known problems can be found in the bugs file. O'Reilly has a book out named Managing IMAP. While the book does not directly talk about the 2.0 code base, it provides very good information on the configuration and setup that can be applied to the newer code. cyrus-imapd-2.5.10/doc/text/install-auth0000644000175000017500000001622113001246663015041 00000000000000Authenticating Users Introduction The Cyrus IMAP Server uses the Cyrus SASL library to authenticate users. Please refer to the Cyrus SASL documentation for specific details on SASL. This section focuses specifically on the server processes distributed with Cyrus IMAPd. Authentication Mechanisms At this writing, the underlying Cyrus SASL library supports a variety of SASL mechanisms, including CRAM-MD5, DIGEST-MD5, KERBEROS_V4, and GSSAPI. The Cyrus IMAP, POP, and LMTP servers also support STARTTLS using client-side certificates and the EXTERNAL authentication method. GSSAPI is specific to Kerberos version 5. Additionally, STARTTLS client side certificates have not been extensively tested. When STARTTLS is enabled, the PLAIN SASL mechanism (if installed) also becomes available. This is because one should not pass a clear text password over the wire unless the connection is encrypted. The IMAP protocol also supports a way for users to authenticate without using SASL (the specification). This is via the 'LOGIN' command (not to be confused by the LOGIN SASL mechanism). The IMAP LOGIN command (as with PLAIN) will send your password in clear-text to the server. In this case, the password is still verified through the Cyrus SASL library, though no SASL mechanism actually performs a negotiation. The POP server is capable of APOP authentication, but this requries that Cyrus SASL be compiled --with-checkapop, and also that you are using an auxprop backend for your password store (e.g. the sasldb auxprop plugin). Authentication Recommendations * If you are running a mail server on a single machine, we recommend that you configure the system to use CRAM-MD5 or DIGEST-MD5. We have not provided utilities for you to let users change their passwords but either we or someone else might provide that feature. * If you have more than one mail server, we recommend that you configure the system to use GSSAPI and Kerberos5. * If you have some other authentication mechanism that requires the clear text password, you should use saslauthd. saslauthd is something specific to the Cyrus SASL libraries. While it is less generic than PAM, it is much simpler to configure. The IMAP server simply sends a userid and a corresponding password down a Unix domain pipe. Then, saslauthd takes that userid and password and tries to authenticate with it -- using whatever authentication you use -- and simply returns "yes" or "no" as to whether or not the password was correct. It is possible to configure saslauthd to check these passwords via a PAM mechanism, /etc/passwd, or other possibilities. PAM stands for pluggable authentication modules and the purpose is to provide a common API which applications can use to obtain authentication for a user. You can think of PAM as a complementary layer under the SASL layer. See http://www.kernel.org/pub/linux/libs/pam/FAQ for more information on PAM. By using a PAM module, all the other applications on your system can take advantage of it -- for example, login, xlock, etc. Keep in mind that when you use PLAIN or LOGIN you should encrypt the stream so a user's password cannot be trivially sniffed off of the network. Configuring Authentication Cyrus SASL has a number of options that can be configured by the application. To configure these via imapd.conf, simply prefix the appropriate option name with sasl_ (e.g. pwcheck_method becomes sasl_pwcheck_method). /etc/sasldb2 The easiest method for authenticating users is to use the libsasl authentication database and create users using the "saslpasswd2" utility. Set "sasl_pwcheck_method: auxprop", and be sure that the SASL sasldb auxprop module is installed (it is, by default). Make sure Cyrus can read "/etc/sasldb2": chown cyrus /etc/sasldb2* Shadow Passwords If you want to authenticate users from "/etc/shadow", things are considerably more complicated, since the cyrus user cannot read the shadow password file. Additionally, this will not allow you to use shared secret mechanisms. To do this, it is necessary to configure libsasl with saslauthd support, and set "sasl_pwcheck_method: saslauthd". The SASL library will then make calls to an external utility running as root to authenticate users. Kerberos Configuring Kerberos v4 Cyrus IMAP supports Kerberos v4 if the SASL library was compiled with KERBEROS_V4 support. You'll have to create a Kerberos v4 identity for the server and add the server's key to the "srvtab" file. The file must be readable by the cyrus user. The server's Kerberos identity is "imap.HOST@REALM", where "HOST" is the first component of the machine's host name and "REALM" is the machine's Kerberos realm. 1. Here is a sample session, creating a srvtab file for the host named "foobar": ksrvutil -f /var/imap/srvtab add Here is the information "ksrvutil" requests. Respond by filling in values or by pressing RETURN. In this example, the host name is "foobar" and the realm is "ANDREW.CMU.EDU". Name: imap Instance: foobar Realm: ANDREW.CMU.EDU Version number: New principal: imap.foobar@ANDREW.CMU.EDU; version 0 Is this correct? (y,n) [y] Password: Verifying, please re-enter Password: Key successfully added. Would you like to add another key? (y,n) [y] n 2. If you plan to install Kerberized POP, create the Kerberos identity "pop.HOST@REALM" and add the key to the "srvtab" file. Likewise, if you plan on using LMTP over TCP, create the Kerberos identity "lmtp.HOST@REALM" and add the key to the "srvtab" file. 3. Make the "srvtab" file owned by the cyrus user: chown cyrus /var/imap/srvtab 4. Add the option srvtab option to /etc/imapd.conf: srvtab: /var/imap/srvtab 5. Test using imtest -m KERBEROS_V4. imtest will attempt to authorize as the current Unix user regardless of the current ticket's held. Override this with the -u option. Troubleshooting Kerberos_V4 problems Run the program "krbck" (found in the imap directory) as the cyrus user on the IMAP server. This program will diagnose some common Kerberos v4 configuration errors. Configuring Kerberos v5 Cyrus IMAP supports Kerberos v5 if the SASL library was compiled with GSSAPI support. You'll have to create a Kerberos v5 identity for the server. Kerberos v5 keys are generally stored in "/etc/krb5.keytab". 1. Add the "imap/hostname" key using "kadmin". 2. Let the cyrus user read "/etc/krb5.keytab": user: chown cyrus /etc/krb5.keytab 3. Test using imtest -m GSSAPI. imtest will attempt to authorize as the current Unix user regardless of the current ticket's held. Override this with the -u option. cyrus-imapd-2.5.10/doc/text/feedback0000644000175000017500000000301013001246663014150 00000000000000Sending Feedback on the Cyrus IMAP Server Feedback on and fixes for the software or on the document may be sent to cyrus-bugs+@andrew.cmu.edu. Unfortunately, we cannot guarantee a response but we'll try the best we can. As usual, a high quality and complete message helps us tremendously. If you submit a patch, please send unified diffs (-u) if your diff program supports them, or context diffs (-c) if it doesn't. Plain diffs are very difficult to evaluate. GNU diff can do this. When reporting problems, be sure to include the relevant information. For example, you must include: * the version of imapd * the version of libsasl * your system type (uname -a often provides the right information). You should also include: * the options you passed to ./configure * the errors from make (if any) * the config.status file generated by configure NOTE: If you are able to connect to the imap server, all of this information can be gathered by using the version command in cyradm. If you cannot use cyradm because you are having perl problems, you can connect using imtest and then run the following IMAP command: * a ID NIL The info-cyrus@andrew.cmu.edu mailing list exists for the discussion of this server and other Cyrus software; more information is available in the mailing-list document. You may get faster/more responses by posting to this list instead of to cyrus-bugs, as there are more readers here. cyrus-imapd-2.5.10/doc/text/faq0000644000175000017500000003112213001246663013200 00000000000000Cyrus IMAP Server FAQ * POP-Before-SMTP It is not included in the default distribution because there is already a standard way of doing this with SMTP AUTH. Any good MTA and/or MUA should support SMTP AUTH, so we shouldn't have to create a hack in an unrelated service. However, if you would like to install it anyway, we recommend using DRAC, along with the patch available in contrib/drac_auth.patch. * Using NFS We don't recommend it. If you want to do it, it may possibly work but you may also lose your email or have corrupted cyrus.* files. You can look at the mailing list archives for more information. * Using AFS/Coda We don't recommend it. It's even less likely to work than NFS. If you want to do it, it may possibly work but you may also lose your email or have corrupted cyrus.* files. CMU's previous e-mail system, AMS, leveraged AFS extensively for storage (and transit) purposes. For various reasons it didn't scale particularly well and led to CMU's interest in IMAP. Cyrus was designed to use a local filesystem with Unix semantics and a working mmap()/write() combination. AFS doesn't provide these semantics so won't work correctly. * Virtual hosting - See virtual domains configuration. * dots in userids - you can have a '.' in your username IF, AND ONLY IF, you use the UNIX hierarchy convention. * renaming users - Supported, but try to make sure that the user is not, and cannot login when doing the rename. Otherwise user-meta may get corrupted and/or out of sync. * plus addressing - Plus addressing allows direct delivery to a particular mailbox (other than an INBOX). This is done in two ways. The first way allows delivery to a subfolder of a specific user's INBOX. This is done via an address of the form: username+mailfolder@domain, which will deliver to the user's INBOX.mailfolder folder (or altnamespace equivalent). This submailbox must allow the posting user the 'p' right (generally, this means 'anyone' must have the 'p' right), otherwise the message will just be filed into the user's INBOX. The second way is to form an address like [postuser]+mailfolder@domain. This will deliver into the mailbox 'mailfolder'. [postuser] is the string specified in the imapd.conf option of the same name, and may be the empty string. As before, the posting user will need to have the 'p' right on the mailbox. For both methods, if 'mailfolder' is more than one level deep, you will need to conform to the hierarchy separator appropriate to your site. * Performance/Capacity/Scaling - See the performance guide. General Questions Q: What are the advantages of LMTP? A: LMTP protocol differs from SMTP in that it causes the Cyrus to return, after the final "." of the DATA command, one reply for each recipient. If, for example, a server is given a transaction for two recipients, delivery to the first succeeds, and delivery to the second encounters a temporary failure condition, the MTA will get a separate response for each recipient and will only have to reattempt to deliver it to the second recipient. If using SMTP, only a single temporary failure response would be returned, and the entire transaction would have to be reattempted. Furthermore, LMTP is superior to invoking command-line delivery agents from the MTA in that most ESMTP extensions are supported by LMTP, without having to extend any interfaces. Lastly, because LMTP can be run over TCP, it allows you to run SMTP (and spam/virus scanning) and mailbox access on separate servers, thus allowing better scalability. Q: How do I configure my MTA? A: See Configuring the Mail Transfer Agent Q: How should I configure partitions to deal with a large number of users? A: The key is not to over-subscribe any partitions. Avoid putting too many users on any one partition, such that read/write performance becomes unacceptable. Good RAID performance (plenty of read/write cache, and perhaps RAID 10 instead of RAID 5) will improve the number of users a partition can serve. To benefit from multiple partitions, each should be on its own set of disks, served by an unsaturated interface (FC, SCSI, SAS, SATA, etc) to the host running Cyrus. See the performance guide or general performance guidelines. Also see metapartition_files and metapartition-name in imapd.conf.5 for additional configuration options which can help with performance, especially if you have access to high-speed storage (faster than disks). Troubleshooting Q: Why doesn't imapd/pop3d/nntpd/lmtpd/timsieved advertise PLAIN or plaintext login commands? A: Unless otherwise configured, Cyrus services only advertise PLAIN or plaintext login commands on encrypted connections (SSL-wrapped connections or after a successful STARTTLS command). This behavior can be changed with the use of the allowplaintext option in imapd.conf.5. Q: I'm getting syslog'd messages from the master process saying processes are "signaled to death by 10". What's up? A: If you're using Berkeley DB 3.0.55, try installing some patches to Berkeley DB available from http://www.sleepycat.com/update/3.0.55/patch.3.0.55.html. Q: I've used saslpasswd2 to create CRAM-MD5 secrets, but imapd doesn't say AUTH=CRAM-MD5. Why? A: Make sure /etc/sasldb2 is readable by the Cyrus user. Q: I'm using "sasl_pwcheck_method: saslauthd", but authentication isn't working. A: Make sure that the saslauthd daemon is running (you'll want to start it when the system boots). imapd is unable to connect to saslauthd if the following message appears in the logs: Dec 6 12:58:57 mail3.andrew.cmu.edu imapd[1297]: cannot connect to saslauthd server Make sure that saslauthd is running and that the cyrus user can access the unix domain socket (defaults to /var/run/mux). Q: I'm getting messages about "duplicate_prune". What's wrong? A: These messages look like Jan 14 13:46:24 grant ctl_deliver[9060]: duplicate_prune: opening /var/imap/deliverdb/deliver-x.db: No such file or directory Jan 14 13:46:24 grant ctl_deliver[9060]: duplicate_prune: opening /var/imap/deliverdb/deliver-y.db: No such file or directory Jan 14 13:46:24 grant ctl_deliver[9060]: duplicate_prune: opening /var/imap/deliverdb/deliver-z.db: No such file or directory These messages are normal; one file is maintained for each user beginning with "x", "y", "z", etc. If you're first starting or you have no users beginning with these letters, these messages are completely normal and can be ignored. Q: I'm getting a message about "imapd: could not getenv(CYRUS_SERVICE); exiting" in my imapd.log. What's wrong? A: Remove all imap, pop, lmtp and sieve lines from [x]inetd.conf and restart [x]inetd. Cyrus is run out of its own "master" process. Q: How do I use different SSL/TLS certificates for imap and pop? A: Specify the different certs using the appropriate options in imapd.conf. Read imapd.conf(5) for details. Q: My KPOP client is complaining about TLS keys. What should I do? A: Disable TLS for the kpop service. Either set tls_pop3_cert_file to disabled in imapd.conf (which will also disable SSL/TLS for pop3), or use a separate config file for kpop. For example, change the kpop service in cyrus.conf to something like: kpop cmd="pop3d -k -C /etc/kpopd.conf" listen="kpop" then copy /etc/imapd.conf to /etc/kpopd.conf and remove the tls_* options. Q: Eudora 5.x can't connect using STARTTLS ("SSL Neogotiation Failed"). What should I do? A: First, complain to QUALCOMM because their STARTTLS implementation is broken. Eudora doesn't support TLSv1 (per RFC2246) and Cyrus requires it. If you really need this before it is fixed in Eudora, remove or comment out the following lines in tls.c: if (tlsonly) { off |= SSL_OP_NO_SSLv2; off |= SSL_OP_NO_SSLv3; } Q: I'm getting messages in imapd.log like "DBERROR db3: 16 lockers". What's wrong? A: Nothing is wrong. These messages are logged whenever Berkeley DB encounters lock contention, but aren't necessarily problems. This is especially likely when you have an empty or small duplicate delivery database and are receiving a large volume of e-mail. Berkeley DB 4.0 has a bug where the number of lockers isn't decremented properly, causing this number to be unreliable. Q: All of the 8bit characters in the headers of messages that I receive are being changed to 'X's. What's going on? A: 8-bit characters are illegal in message headers. Following the principle of "be liberal in what you accept, and strict in what you send", Cyrus converts them to Xs. (Without a character set, having the 8-bit characters replaced with Xs is just as good as having them be any other 8-bit character, especially for sorting and searching). Alternatively, you can set "reject8bit: t" in imapd.conf to reject the messages outright. It might also be reasonable for Cyrus to support the use of a default character set, however thus far no one has done the work to do so (it would also involve QP-encoding the corrupted headers). Q: Why can't I delete any messages from my over-quota mailbox? I'm using a client with a 'trash folder'. A: Trash folders, as they are commonly implemented (as actual IMAP mailboxes), do not fit the IMAP delete/expunge model very well. In fact, naive client implementations will get stuck in a situation where they cannot delete a message from a mailbox because they try to COPY it to the trash folder before deleting the message. This operation will fail due to the mailbox being over quota. This is separate from the fact that a specific mailbox name is not interoperable between clients (one might call it 'trash', another 'Trash', another 'Recycle Bin', etc) Given the lack of protocol support for a trash folder, this is mostly a quality-of-implementation issue on the client side. There are a few options here: * Contact your client vendor to have the broken client fixed (one possibility is to have the client ask the user if they wish to permanantly delete the message if the COPY operation fails). * Stop using the 'trash mailbox' feature of your client (if possible). * Set a separate quota root on the 'trash folders' of users. This last option is significantly harder to do correctly, since it assumes that all clients that make use of a trash folder do so with the same folder name. Q: How do I stop Cyrus from advertising the DIGEST-MD5 and CRAM-MD5 shared secret SASL mechanisms? A: Not really a Cyrus IMAPd question, this can be fixed by just removing the SASL plugins from where Cyrus SASL installed them (if no other applications require them), or by using the sasl_mech_list imapd.conf option to list only the mechanisms that you require. cyrus-imapd-2.5.10/doc/text/mailing-list0000644000175000017500000000222713001246663015026 00000000000000info-cyrus mailing list We run a mailing list for users of Project Cyrus software. The info-cyrus@andrew.cmu.edu mailing list exists for the discussion of this server and other Cyrus software. Please do NOT send subscription requests to the list. To subscribe: Send mail to info-cyrus-subscribe@lists.andrew.cmu.edu to subscribe (or just click the link above and that should just work). An archive is availible via anonymous IMAP at imap://cyrus.andrew.cmu.edu/archive.info-cyrus. A web archive is also available at http://www.cyrusimap.org/mediawiki/index.php/Cyrus_Mailing_Lists#Archives If you are not subscribed to the list (or you are sending the message from a different address than the one which you are subscribed under), your message is directed to a human for approval. Unfortunately, the human does not always promptly process the message. There is also a developers list available at cyrus-devel@lists.andrew.cmu.edu. with similar subscription methods and archive location Detailed contact information can be found at http://www.cyrusimap.org/mediawiki/index.php/Contact cyrus-imapd-2.5.10/doc/text/notes0000644000175000017500000000074513001246663013570 00000000000000 * appending: it's important that the index records for individual messages make it to disk before the index header indicating that they're there. so something like: 1. sync messages to disk (or depend on link() being atomic) 2. create new index records, flush to disk 3. create new header if necessary (adding new user flag), flush to disk 4. flush cache file 5. update index header, flush to disk cyrus-imapd-2.5.10/doc/text/install-prereq0000644000175000017500000000522713001246663015402 00000000000000Prerequisites and other notes The following programs and/or packages are required. * libsasl, version 2.1.7 or higher. To obtain libsasl, ftp it from ftp.andrew.cmu.edu. Earlier versions of SASL will not work; please get the latest one. Configure SASL so that it supports whatever authentication method your site uses. Please pay careful attention to the SASL configuration. This is the biggest problem that most people have. * Berkeley DB, version 3.0.55 or higher. Berkeley DB can be obtained from Sleepycat. It is strongly recommended that libsasl be compiled with Berkeley DB support, using the same version of Berkeley DB. (If you have a Berkeley DB version mismatch, somewhat perplexing crashes result.) * GNU Make is required. Get it from the Free Software Foundation. It is probably easier to find it via ftp. The following programs and/or packages are required for specific features. If you don't have them, certain features of the IMAP server will be disabled. * Perl, version 5. To obtain Perl, see the Comprehensive Perl Archive. This is required for cyradm (written by Brandon Allbery). It is also used for some installation scripts: you don't need it but it may make your life easier. We recommend at least version 5.00502. * OpenSSL, version 0.9.4 or higher. Required for STARTTLS support and for IMAP/POP3 wrapped in SSL (the imaps/pop3s ports). Available from http://www.openssl.org/. * libwrap, from Wietse Venema. This will allow one to control who is accessing what service, based on IP address. Available from ftp://ftp.porcupine.org/pub/security/ in the tcp_wrappers package.. * Net-SNMP (formerly UCD-SNMP), version 4.2 or higher. Required for SNMP monitoring of the IMAP server. Available from http://www.net-snmp.org/. * If you use AFS PTS support for groups, Cyrus still depends on Kerberos and AFS. If you successfully compiled SASL with your Kerberos library, it's likely that it will work well with Cyrus. * We recommend using an MTA (mail transfer agent) that supports LMTP (local mail transfer protocol). We use Sendmail and recommend version 8.12.8 or higher, available from http://www.sendmail.org. Others have reported success with Postfix. The following programs and/or packages are recommended: * flex - libcyrus_sieve has two different lexical analyzers, and that's hard to do with traditional lex. * gcc - we build using gcc and the compiler options -O2 -g. cyrus-imapd-2.5.10/doc/text/os0000644000175000017500000000377613001246663013070 00000000000000Operating System Notes All 1. Shadow passwords On any system with shadow passwords (including Solaris 2.5 with Unix authentication), read the SASL documentation carefully to make sure it is configured correctly. Solaris 1. Modern Solaris systems have several useful utilities in /usr/proc/bin, among them pmap. This can be used to calculate the incremental cost (number of non-shared pages) of an imapd process, which is useful for sizing purposes. HP-UX 1. The memory mapping support (mmap(2)) in HP-UX does not have the right semantics for the Cyrus IMAP server under the 9.0 and 10.0 release of the operating system. It appears this is related to the hardware's use of inverse page tables. It is recommended that large-scale sites consider using some other platform. 2. HP-UX 9.0.4: Comments from testers The C that ships with HP-UX is totally unsuited for use with unix packages. Either the HP-UX ANSI C developers kit must be purchased separately from HP or GNU's gcc compiler (which can bootstrap itself from the basic HP C) must be built on the target system. Linux 1. synchronous FS updates. By turning on synchronous updates for ext2fs, all updates (instead of just meta-data) become synchronous. This is good for reliability, but bad for performance. The big problem used to be with the mailboxes file. The 2.0 release and later addressed this problem by changing the flat file to a Berkerley DB database. Note this is for ext2fs. If you are using a newer filesystem (such as xfs, jfs, or reiserfs) the synchronous metadata issue shouldn't come up. Then again, we haven't really looked at other filesystems for Linux yet. (It appears that the different filesystems support slightly different semantics, and it's not always clear what the right thing for the application to do is.) cyrus-imapd-2.5.10/doc/text/specs0000644000175000017500000002121013001246663013543 00000000000000Cyrus IMAP Server Protocol Specifications IMAP RFC 3501 Internet Message Access Protocol - version 4rev1 being updated by rfc3501-errata RFC 1730 Internet Message Access Protocol - version 4 RFC 4314 IMAP4 Access Control List (ACL) Extension RFC 2087 IMAP4 QUOTA extension RFC 2088 IMAP4 non-synchronizing literals RFC 2177 IMAP4 IDLE command RFC 2192 IMAP URL Scheme being updated by draft-ietf-lemonade-rfc2192bis RFC 2193 IMAP4 Mailbox Referrals RFC 2342 IMAP4 Namespace RFC 4315 Internet Message Access Protocol (IMAP) - UIDPLUS extension RFC 2971 IMAP4 ID extension RFC 3348 IMAP4 Child Mailbox Extension RFC 3502 IMAP MULTIAPPEND extension RFC 3516 IMAP4 Binary Content Extension RFC 3691 Internet Message Access Protocol (IMAP) UNSELECT command RFC 4466 Collected Extensions to IMAP4 ABNF RFC 4467 Internet Message Access Protocol (IMAP) - URLAUTH Extension RFC 4469 Internet Message Access Protocol (IMAP) CATENATE Extension RFC 4550 Internet Email to Support Diverse Service Environments (Lemonade) Profile RFC 4551 IMAP Extension for Conditional STORE operation RFC 4731 IMAP4 Extension to SEARCH Command for Controlling What Kind of Information Is Returned RFC 4959 IMAP Extension for Simple Authentication and Security Layer (SASL) Initial Client Response RFC 4978 The IMAP COMPRESS Extension RFC 5032 WITHIN Search Extension to the IMAP Protocol RFC 5161 The IMAP ENABLE Extension RFC 5162 IMAP4 Extensions for Quick Mailbox Resynchronization RFC 5256 Internet Message Access Protocol - SORT and THREAD Extensions RFC 5258 Internet Message Access Protocol version 4 - LIST Command Extensions RFC 5524 Extended URLFETCH for Binary and Converted Parts draft-daboo-imap-annotatemore ANNOTATEMORE Draft RFC 5464 The IMAP METADATA Extension draft-ietf-morg-list-specialuse IMAP SPECIALUSE Draft (And non-standard Google XLIST support) RFC 5819 IMAP4 Extension for Returning STATUS Information in Extended LIST RFC 5957 Display-Based Address Sorting for the IMAP4 SORT Extension POP RFC 1939 Post Office Protocol - Version 3 (POP3) RFC 2449 POP3 Extension Mechanism RFC 2595 Using TLS with IMAP, POP3 and ACAP RFC 5034 The Post Office Protocol (POP3) Simple Authentication and Security Layer (SASL) Authentication Mechanism RFC 3206The SYS and AUTH POP Response Codes NNTP RFC 3977 Network News Transfer Protocol (NNTP) RFC 4642 Using Transport Layer Security (TLS) with Network News Transfer Protocol (NNTP) RFC 4643 Network News Transfer Protocol (NNTP) Extension for Authentication RFC 4644 Network News Transfer Protocol (NNTP) Extension for Streaming Feeds RFC 2980 Common NNTP Extensions SASL RFC 4422 Simple Authentication and Security Layer (SASL) RFC 4505 Anonymous Simple Authentication and Security Layer (SASL) Mechanism RFC 4616 The PLAIN Simple Authentication and Security Layer (SASL) Mechanism RFC 2195 IMAP/POP AUTHorize Extension for Simple Challenge/Response being revised by draft-ietf-sasl-crammd5 RFC 2444 The One-Time-Password SASL Mechanism RFC 2831 Using Digest Authentication as a SASL Mechanism TLS/SSL RFC 4346 The Transport Layer Security (TLS) Protocol Version 1.1 RFC 2246 The TLS Protocol Version 1.0 draft-freier-ssl-version3 The SSL Protocol Version 3.0 draft-hickman-netscape-ssl The SSL Protocol Version 2.0 LMTP RFC 2033 Local Mail Transfer Protocol RFC 5321 Simple Mail Transfer Protocol RFC 1869 SMTP Service Extensions RFC 1652 SMTP Service Extension for 8bit-MIMEtransport RFC 1870 SMTP Service Extension for Message Size Declaration RFC 2034 SMTP Service Extension for Returning Enhanced Error Codes RFC 3463 Enhanced Mail System Status Codes RFC 3207 SMTP Service Extension for Secure SMTP over TLS RFC 4954 SMTP Service Extension for Authentication RFC 2920 SMTP Service Extension for Command Pipelining RFC 3848 ESMTP and LMTP Transmission Types Registration draft-murchison-lmtp-ignorequota LMTP Service Extension for Ignoring Recipient Quotas Sieve RFC 5228 Sieve: A Mail Filtering Language RFC 5230 Sieve Email Filtering: Vacation Extension RFC 5231 Sieve Email Filtering: Relational Extension RFC 5232 Sieve Email Filtering: Imap4flags Extension RFC 5233 Sieve Email Filtering: Subaddress Extension RFC 5260 Sieve Email Filtering: Date and Index Extensions RFC 5173 Sieve Email Filtering: Body Extension RFC 3894 Sieve Extension: Copying Without Side Effects RFC 2298 Extensible Message Format for Message Disposition Notifications (MDNs) RFC 6131 Sieve Vacation Extension: "Seconds" Parameter RFC 6609 Sieve Email Filtering: Include Extension draft-ietf-sieve-regex Sieve Email Filtering -- Regular Expression Extension draft-melnikov-sieve-imapflags Sieve -- IMAP flag Extension draft-martin-sieve-notify Sieve -- An extension for providing instant notifications draft-ietf-sieve-managesieve A Protocol for Remotely Managing Sieve Scripts HTTP RFC 7230 Hypertext Transfer Protocol (HTTP/1.1): Message Syntax and Routing RFC 7231 Hypertext Transfer Protocol (HTTP/1.1): Semantics and Content RFC 7232 Hypertext Transfer Protocol (HTTP/1.1): Conditional Requests RFC 7233 Hypertext Transfer Protocol (HTTP/1.1): Range Requests RFC 7234 Hypertext Transfer Protocol (HTTP/1.1): Caching RFC 7235 Hypertext Transfer Protocol (HTTP/1.1): Authentication RFC 2617 being updated by draft-ietf-httpauth-basicauth-update draft-ietf-httpauth-digest HTTP Authentication: Basic and Digest Access Authentication RFC 4559 SPNEGO-based Kerberos and NTLM HTTP Authentication in Microsoft Windows [MS-NTHT] NTLM Over HTTP Protocol Specification RFC 2817 HTTP Upgrading to TLS Within HTTP/1.1 RFC 2818 HTTP Over TLS RFC 6797 HTTP Strict Transport Security (HSTS) RFC 7239 Forwarded HTTP Extension RFC 7240 Prefer Header for HTTP RFC 4918 HTTP Extensions for Web Distributed Authoring and Versioning (WebDAV) RFC 3253 Versioning Extensions to WebDAV (Web Distributed Authoring and Versioning) RFC 3744 Web Distributed Authoring and Versioning (WebDAV) Access Control Protocol RFC 4331 Quota and Size Properties for Distributed Authoring and Versioning (DAV) Collections RFC 5397 WebDAV Current Principal Extension RFC 5689 Extended MKCOL for Web Distributed Authoring and Versioning (WebDAV) RFC 5995 Using POST to Add Members to Web Distributed Authoring and Versioning (WebDAV) Collections RFC 6578 Collection Synchronization for Web Distributed Authoring and Versioning (WebDAV) RFC 4791 Calendaring Extensions to WebDAV (CalDAV) RFC 6638 Scheduling Extensions to CalDAV RFC 6352 CardDAV: vCard Extensions to Web Distributed Authoring and Versioning (WebDAV) RFC 6764 Locating Services for Calendaring Extensions to WebDAV (CalDAV) and vCard Extensions to WebDAV (CardDAV) draft-ietf-tzdist-service Time Zone Data Distribution Service draft-ietf-tzdist-caldav-timezone-ref CalDAV: Time Zones by Reference draft-ietf-calext-rscale Non-Gregorian Recurrence Rules in iCalendar draft-daboo-calendar-availability Calendar Availability draft-york-vpoll VPOLL: Consensus Scheduling Component for iCalendar draft-desruisseaux-ischedule Internet Calendar Scheduling Protocol (iSchedule) draft-thomson-hybi-http-timeout Hypertext Transfer Protocol (HTTP) Keep-Alive Header draft-murchison-webdav-prefer Use of the Prefer Header Field in Web Distributed Authoring and Versioning (WebDAV) caldav-ctag Calendar Collection Entity Tag (CTag) in CalDAV Brief HeaderMicrosoft 'Brief' header extension Other RFC 3656 MUPDATE Protocol (For Cyrus Murder) RFC 5322 Internet Message Format RFC 5536 Netnews Article Format RFC 5537 Netnews Architecture and Protocols RFC 3656 MUPDATE Protocol (For Cyrus Murder) RFC 5423 Internet Message Store Events RFC 4287 The Atom Syndication Format RFC 5545 Internet Calendaring and Scheduling Core Object Specification (iCalendar) RFC 5546 iCalendar Transport-Independent Interoperability Protocol (iTIP) RFC 6047 iCalendar Message-Based Interoperability Protocol (iMIP) RFC 6231 xCal: The XML Format for iCalendar RFC 7265 jCal: The JSON Format for iCalendar RFC 6350 vCard Format Specification RFC 6376 DomainKeys Identified Mail (DKIM) Signatures cyrus-imapd-2.5.10/doc/text/install-perf0000644000175000017500000001447213001246663015042 00000000000000Performance Notes Cyrus presents various performance issues for you to consider. If you never expect to have more than 100 simultaneous users, chances are any hardware you have will be fine. If you plan on having thousands or more users, please be sure to review this section. If your configuration directory is not /var/imap, adjust accordingly. * /var/imap/proc - After a successful login, the imapd creates a file in var/imap/proc that is its unix process id. It also contains the name of any SELECTed mailbox. The file is deleted when the user logs out. Given the potential load, this is a good candidate to move elsewhere. This can be done by symlink'ing the directory to another partition. We symlink it to a directory on a memory/virtual memory filesystem (specifically Solaris' tmpfs). If you use a tmpfs type filesystem, make sure that you have sufficient memory/swap to do this. Some people don't care about this information and just #ifdef out the code. We probably should add a configure option to do this. * /var/imap/mailboxes.db - The mailboxes list is often the ultimate source of contention between imapd processes, especially if clients are inefficient about their use of the LIST command. For this reason it is often better to use the skiplist backend which is optimized for enumeration of the database, as opposed to the default, Berkeley DB (use --with-mboxlist-db=skiplist). Mika Iisakkila (mika.iisakkila@pingrid.fi) writes: Nevertheless, you can also tweak the Berkeley backend if you want to or have to stick with it. Cyrus doesn't do anything to increase the BDB cache size, and the default (256 kB) is way too small for any reasonably large site. With some 50000 mailboxes and random operations, I found the hit rate for the default BDB cache to be 70-80%. After growing the cache size to 2M, the hit rate approached 99% and disk traffic was greatly reduced since most of the operations are reads anyway. Therefore processes could complete their work and release their locks much more quickly, and the dreaded "DBERROR: xxx lockers" messages stayed at a comfortable level. You can modify the source (/lib/cyrusdb_db3.c, the setting is commented out) or you can put a DB_CONFIG file under /var/imap/db with the appropriate setting. Read more about this in the Berkeley docs before trying it - typos and incorrect settings can wreak havoc. * /var/imap/deliverdb - Unless you disable duplicate delivery suppression, each time a mail message is delivered it needs to lock the database and check to see if the message-id has been seen already. If you require really high throughput delivery, you may want to disable this feature. We run with it enabled and it doesn't significantly impact our performance. * /var/spool/mqueue - Sendmail can be pretty harsh on the spool partition. Having this on a separate disk is usually a good idea. Consider using LMTP and delivering from a separate machine. * Unused SASL mechanisms - If you just build the SASL library and copy all the mechanisms into /usr/lib/sasl2, the imapd will try to use them and allocate some amount of memory for each. In general, the operating system will swap out those pages but you may be allocating more swap space than you need. So look in usr/lib/sasl2 and if you don't plan on using those mechanisms, don't leave them there. * You may want to increase the listen queue value when starting up the master process. For example, you may want to do this if you see the listen queue drop counter increasing quickly. Under Solaris, look at the variable tcpListenDrop (from netstat -sP tcp). * Database recovery. If restarting the server takes a long time due to the cyrusdb database recovery procedure (this is usually true if you have a large number of deliveries) you should look into shortening the interval between checkpoints, controlled by the cyrusdb event in /etc/cyrus.conf. We run checkpoints every 5 minutes; the current suggested install interval is 30 minutes. * Some filesystems support the noatime mount option. The server does not use the atime information so you can go ahead and enable this feature. * Depending on your syslog configuration and usage volume, Cyrus may generate thousands of syslog messages. On Linux, syslog performance can be greatly improved by disabling synchronous logging (disabling fsync() after each message). Prepending filenames in etc/syslog.conf with a "-", e.g., "/var/log/maillog" becomes "-/var/log/maillog", disables syslog's fsync() call after each log message. If you log many messages those fsync()s will kill your I/O throughput. Note that if you do not need the detail provided by the LOG_DEBUG level, then not logging these messages can significantly reduces the number of log entries that Cyrus makes. In general, there's no magic bullet for performance. It depends on your hardware, your operating system, and how your users use the system. In general, an imapd process takes up anywhere from 256 Kbytes of memory to 512 Kbytes when it is first fired up. CPU has not been a big deal, but it may become more important as the IMAP sessions are encrypted and now that searching may be more frequent. Disk I/O is probably the most important and having a hardware RAID subsystem with a decent amount of write-back cache would be a good thing. Again, if you are talking about less than 100 interactive users it is likely that any relatively modern hardware can support it. If you are talking about having more than 1000 interactive users, you should know how to predict your utilization, go overboard on hardware, be willing to suffer growing pains, or be able to hire someone that can help. There are a number of good performance tuning articles out for Solaris by Adrian Cockcroft. Go to your favorite search engine and look for his name. cyrus-imapd-2.5.10/doc/text/sieve-protocol0000644000175000017500000000504013001246663015403 00000000000000Protocol for Sieve script exchange Please note that this document is not authoritative and may well be out of date; you should look at specs.html for the current authoritative document for the MANAGESIEVE protocol. Note: This is not a standards track protocol. If you decide to base a program upon it you have been warned. This is a simple text-based protocol for getting user sieve scripts onto the (presumably sealed) IMAP server. The requirements for this process are: * the user must authenticate to gain access, preferably via a secure SASL mechanism. * only valid sieve scripts may be accepted Additional features provided: * the ability to manage multiple scripts on the server with zero or one of them being the "active" sieve script Types This is a line-oriented protocol much like [IMAP] or [ACAP]. There are two types: ATOMS and strings, all space ('SP') separated. Strings may be quoted or literal. See [ACAP] for detailed descriptions. sievename is a string where only certain characters are allowed and it must be at least 1 character long. Commands AUTHENTICATE SP string [SP string] EOL SASL authentication; the parameters are the mechanism and optionally the initial data. Initial data is base64 encoded. The server replies with an OK or NO response, or a base64 string followed by an EOL. Client then replies with a base64 string followed by an EOL, and the procedure is repeated. NOOP EOL No side effects. Valid replies: OK or NO. LOGOUT EOL Logout: terminates connection. Valid replies: OK or NO. GETSCRIPT SP sievename EOL The parameter is the name of the requested script. Returns: string EOL containing the script data. Get the script with name sievename from the server. Valid replies: OK or NO. PUTSCRIPT SP sievename SP string EOL Puts sievename with data data onto the server if possible. Valid replies: OK or NO. SETACTIVE SP sievename EOL Set the script with the name sievename as the active script. Any other script that was active is no longer. Valid replies: OK or NO. DELETESCRIPT SP sievename EOL Delete the script with sievename. Valid replies: OK or NO. LISTSCRIPTS EOL Returns zero or more: sievename EOL. Where the active script has a '*' at the end of its name. Valid replies: OK or NO. cyrus-imapd-2.5.10/doc/text/install-netnews0000644000175000017500000002133613001246663015566 00000000000000Cyrus and Netnews Note that the NNTP support in Cyrus is still relatively young in the grand scheme of things, and has not been tested under a heavy Usenet load. That being said, the code appears to be stable and is currently running in production serving 50-60 newsgroups with a volume of about 6000 messages per day. Introduction Cyrus has the ability to export Usenet via IMAP and/or export shared IMAP mailboxes via NNTP. This is made possible by a new NNTP daemon which is included with Cyrus. This document assumes that you have successfully been able to setup your Cyrus IMAP server. If you have not already done so, please refer to the rest of the documentation. This document also assumes that you are familiar with Usenet and shared IMAP mailboxes. There is a diagram that shows the interactions of the various components of the NNTP support in Cyrus which may be helpful in understanding the "big picture". Installation You will need to build Cyrus IMAPd with the --enable-nntp configure option. This builds nntpd and the associated utilities. Requirements Obviously you must have a newsfeed or news reader access from your ISP or Usenet provider. Configuration The first thing that must be done is to decide where your newsgroup mailboxes will reside, either at the toplevel of your hierarchy (eg, comp.mail.imap) or rooted elsewhere (eg, netnews.comp.mail.imap). If your newsgroup mailboxes are not at the toplevel of your hierarchy, then you must specify the parent with the newsprefix in imapd.conf. Using the example above, newsprefix would be set to netnews. You must create a mailbox for each newsgroup that you would like to receive/export before the newsgroups can be used. If some groups are private, be sure to set the ACLs accordingly. The tools/mknewsgroups script can be used to help facilitate mass creation of newsgroup mailboxes. When using this script, be sure to add posting rights for 'anyone' (eg. mknewsgroups -a 'anyone +p' ...) so that articles can be fed/posted. Receiving articles In order to receive usenet articles, you must make sure that the Cyrus nntpd service is enabled in cyrus.conf. The master/conf/normal.conf and master/conf/prefork.conf sample configs both include entries for nntpd (disabled by default). Push (traditional) feeds If your usenet peer will be pushing articles to you, no further configuration is necessary, beyond letting your peer access your Cyrus server on port 119 (nntp). Pull (suck) feeds If you prefer to pull articles from your peer (and your provider allows it), then you can use the fetchnews utility which will retrieve articles from your peer and feed them to your Cyrus server. If supported by your peer, fetchnews will use the NEWNEWS command, otherwise it will fallback to keeping track of the high water mark of each group. You will probably want to configure fetchnews as an EVENT in cyrus.conf to be called periodically (eg, once an hour, every 15 minutes, etc). As an alternative to fetchnews, you can also use the suck program to pull articles from your peer. imapfeed Alternatively, if you already have an INN v2.3 server in-house you can use the included imapfeed utility (written by the authors of Cyrus) to feed articles to your Cyrus server via LMTP. Consult the INN documentation for further details. Control Messages Control messages are accepted, parsed and delivered to the corresponding control.* pseudo-group (eg, control.newgroup, control.cancel, etc) if it exists, so that they may be reviewed by an administrator. Automatic execution of control messages is only performed if the newsmaster (default = "news") user has the proper access control for the given mailbox. For example, to allow cancel control messages to be performed for "misc.test" articles, give the "news" user the 'd' right on "misc.test". To allow newgroup, rmgroup and mvgroup control messages to be performed on the "misc" hierarchy, give the "news" user the 'c' right on "misc". NOTE: No sender or PGP verification of control messages is currently implemented. Reading/Posting articles In order to have articles posted by your local users propagate to the outside world, you must specify the name of your usenet peer(s) with the newspeer option in imapd.conf. This is the host(s) that nntpd contacts to feed outgoing articles. Depending on the configuration of the newspeer option, articles will be fed to the upstream server(s) using either the POST or IHAVE command. Also note that you may specify an optional wildmat to filter which groups will be fed (see imapd.conf(5) for details). Newsgroups can also be gatewayed to email by setting /vendor/cmu/cyrus-imapd/news2mail mailbox annotations to the corresponding email addresses. News clients If anonymous logins are disabled (default) in imapd.conf, then your news clients will have to be configured to login with a username and password, otherwise they will not be allowed to post. Furthermore, if plaintext logins are disabled in imapd.conf, then you might have to configure your news clients to use SSL/TLS and enable the nntps service in cyrus.conf. If you want to allow your news clients to use the NNTP NEWNEWS command, you will have to enable the allownewnews option in imapd.conf. Email clients If you are exporting Usenet via IMAP, and your users' messaging clients are not savvy enough to reply to and post articles via NNTP, then you will have to configure your server so your users can reply to and post articles via SMTP. To help faciliate this, you can set the newspostuser option to a "pseudo" user which will be used to construct email delivery addresses for each incoming article. These addresses are inserted into a Reply-To: in the article. For example, if set to "post", an article posted to comp.mail.imap will have an address of "post+comp.mail.imap" inserted into the Reply-To: header. This will allow a user to easily reply to an article via email. Otherwise, the users will have to learn the correct email address format for posting and replying to articles. In order for these email messages to be fed into your news server (and subsequently to the outside world) you need to use an email to news gateway, such as lmtp2nntp. You need to configure your MTA (Sendmail, Postfix, etc) so that lmtp2nntp is used as the local mailer whenever it receives a news article. A simple rule for doing this in Sendmail is shown below: # mail addressed to post+ goes to lmtp2nntp@localhost LOCAL_RULE_0 Rpost + $+ < @ $=w . > $#lmtp2nntp $@ localhost $: $1 For other configurations, consult the lmtp2nntp and documentation and your MTA documentation. NOTE: If anonymous logins are disabled (default) in imapd.conf, then you should configure lmtp2nntp to use its "feed" operation mode. Expiring articles Expiration of articles is done by the cyr_expire utility. Control over when articles are expunged is accomplished with the /vendor/cmu/cyrus-imapd/expire mailbox annotation. This annotation sets the number of days that messages should be kept in the mailbox before they expire. All entries in the duplicate deliver database that correspond to these messages are also kept for the same number of days before they are purged (overriding the cyr_expire -E option). Setting the expire time to 0 (zero) for a mailbox will ensure that neither the messages nor the corresponding database entries will ever be expired. This can be useful for shared mailboxes (e.g. mailing list archives) which are being exported via NNTP. Note that this will cause the duplicate delivery database to consistently grow in proportion to the number of messages in such mailboxes. If a mailbox does not have an expire time set on it, then the messages will never be expunged, but the corresponding database entries WILL be expired after the default number of days (cyr_expire -E option). Note that the /vendor/cmu/cyrus-imapd/expire mailbox annotation is inherited by child mailboxes, so that you may control expiration on an entire mailbox/newsgroup hierarchy simply by setting the annotation on the root of the hierarchy. For example, if you set the annotation on comp, then ALL of the newsgroups in the comp hierarchy will be expired at the same time. Similarly, if you set the annotation on alt.binaries, all of the binary newsgroups under alt will be expired at the same time (independently from comp). cyrus-imapd-2.5.10/doc/text/changes0000644000175000017500000000311313001246663014040 00000000000000Changes to the Cyrus IMAP Server since 2.5.9 Dependency changes * Jansson versions >= 2.3 are now supported (was >= 2.7) * Restored support for AutoConf 2.63 * GCC 6 is now supported Other changes * master(8) now supports a "-V" (print version and exit) option * version information is now based on git describe, not hard-coded strings Bug fixes * Fixed Issue #34: imapd in murder no longer crashes on MOVE to nonexistent folder (thanks Wolfgang Breyha) * Fixed Issue #15: replication no longer crashes on mailboxes that are too old to be replicated. Instead, it fails with an error and logs a warning that they need to be reconstructed * Fixed Issue #45: extended LIST doesn't lose options when proxied to backend * Fixed Task #142: extended LIST response no longer missing \HasNoChildren flag on last mailbox * Fixed Issue #49: httpd no longer crashes with assertion failure on shutdown after CardDAV has been used * Fixed Issue #31: the ldap_timeout setting is now used correctly * Fixed bugzilla #3909: idled(8) no longer runs as root (thanks Carlos Velasco) * Fixed Issue #5: renaming folder with annotations no longer increases annotation quota usage * Fixed: URLFETCH crash when section is NULL * various build system improvements Changes to the Cyrus IMAP Server since 2.5.8 Dependency changes * Libical 2.0.0 is now supported. * preliminary support for OpenSSL 1.1.0 (not yet released) Other changes cyrus-imapd-2.5.10/doc/text/install-configure0000644000175000017500000004664613001246663016077 00000000000000Installing and configuring the IMAP Server This section describes the shell scripts to run and the configuration files to modify once "configure" and "make" have run. 1. Create a user and group for the Cyrus subsystem. The examples in this document assume a user of "cyrus" and a group of "mail", though any user and group name can be used. If a user other than "cyrus" is to be used, it must have been previously specified in the "--with-cyrus-user=" option to "configure". If a group other than "mail" is to be used, it must have been previously specified in the "--with-cyrus-group=" option to "configure". 2. After you've logged in as "root", install the cyrus software. make install Be sure that the server programs ended up in the directory specified by "--with-cyrus-prefix" (by default, "/usr/cyrus/bin"). 3. The Cyrus IMAP server uses the 4.3BSD syslog that separates messages into both levels and categories. Invoke "man syslog" to see if "openlog()" takes three arguments. If it does not, replace the system "syslogd" and "syslog.conf" with the files provided in the "syslog" directory. mv syslogd /etc/syslogd mv syslog.conf /etc/syslog.conf If you do not copy the "syslog/syslog.conf" file to the "/etc" directory, be sure to add support for "local6.debug". The file should include a line like: local6.debug /var/log/imapd.log You probably also want to log SASL messages with a line like: auth.debug /var/log/auth.log After installation and testing, you probably want to change the ".debug" component to something a little less verbose. Create the log files: touch /var/log/imapd.log /var/log/auth.log 4. Create the file "/etc/imapd.conf". Here is a sample "imapd.conf" with a minimal number of values defined: configdirectory: /var/imap partition-default: /var/spool/imap admins: curtj abell sasl_pwcheck_method: saslauthd For a description of all the fields in this file, see the imapd.conf(5) man page. (Note that this file also exports values to libsasl, the most important of them the pwcheck_method. In this example, users are authenticated via the saslauthd daemon, which can be run in a number of different ways.) READ THE imapd.conf(5) MAN PAGE. There are options in there that you will want to know about and default behavior that you may not like. Note that everyday users should not be administrators. Admins have powers not granted to regular users and while the server allows them to receive mail, some problems will occur if admins are used as regular users. You also should not read mail as an administrator. You should have separate accounts for reading mail and administrating. This is especially true if using the altnamespace option, because admins are always presented with the standard (internal) namespace. 5. Create the configuration directory specified by the "configdirectory" option in "imapd.conf." The configuration directory is similar in concept to the "/usr/lib/news" directory. It stores information about the IMAP server as a whole. This document uses the configuration directory "/var/imap" in its examples. This directory should be owned by the cyrus user and group and should not permit access to other users. cd /var mkdir imap chown cyrus imap chgrp mail imap chmod 750 imap 6. Create the default partition directories specified in the "/etc/imapd.conf" file. This document uses a default partition directory of "/var/spool/imap" in the following example: cd /var/spool mkdir imap chown cyrus imap chgrp mail imap chmod 750 imap The partition directory is similar in concept to /var/spool/news. It is where the mailboxes are stored. Unlike most netnews systems, Cyrus allows you to have more than one partition. 7. If you wish to use Sieve, and you didn't configure deliver to look in home directories (see the imapd.conf man page), create the Sieve directory: cd /usr mkdir sieve chown cyrus sieve chgrp mail sieve chmod 750 sieve 8. Change to the Cyrus user and use the tool "tools/mkimap" to create the rest of the directories (subdirectories of the directories you just created). su cyrus tools/mkimap exit If Perl is not available, it should be easy (but time consuming) to create these directories by hand. 9. LINUX SYSTEMS USING EXT2FS ONLY: Set the user, quota, and partition directories to update synchronously. Failure to do this may lead to data corruption and/or loss of mail after a system crash. Unfortunately, doing so may result in a serious performance hit. If you are using a newer filesystem than ext2fs on Linux, this step should not be necessary. (Running ext3 in any mode is safe.) cd /var/imap chattr +S user quota user/* quota/* chattr +S /var/spool/imap /var/spool/imap/* Also set the queue directory of the mail daemon to update synchronously. The following example is for sendmail: chattr +S /var/spool/mqueue 10. To enable STARTTLS support, see how to configure OpenSSL below. 11. Add the following lines to the "/etc/services" file if they aren't already there. pop3 110/tcp nntp 119/tcp imap 143/tcp imsp 406/tcp nntps 563/tcp acap 674/tcp imaps 993/tcp pop3s 995/tcp kpop 1109/tcp lmtp 2003/tcp sieve 4190/tcp fud 4201/udp 12. Remove "/etc/[x]inetd.conf" entries. Any imap, imaps, pop3, pop3s, kpop, lmtp and sieve lines need to be removed from /etc/[x]inetd.conf and [x]inetd needs to be restarted. Configuring the Master Process 1. Choose a configuration from the master/conf directory: small.conf bare-bones server supporting IMAP and POP normal.conf server supporting IMAP, POP, the SSL wrapped versions, and the Sieve script management protocol prefork.conf The same configuration as above, but with some preforked processes for faster processing. backend-cmu.conf Our configuration (for Murder Backend / typical IMAP servers) frontend-cmu.conf Our configuration (for Murder Frontend servers) To use normal.conf, do: cp master/conf/normal.conf /etc/cyrus.conf Optionally, you can edit /etc/cyrus.conf to disable or enable certain services, or to tune the number of preforked copies. Be sure not to remove the entries that are labeled required. 2. Arrange to start "/usr/cyrus/bin/master" as root when the system starts. It will bind some ports and then give up its root privileges. Until your system reboots, you can start the master process by hand: /usr/cyrus/bin/master & 3. Monitor the progress of the master process by examining the imapd.log file. It should never exit by itself, but you can shut down the mail system by sending it a signal with kill. 4. Clean Shutdown - you can shut the master process down cleanly by sending it a SIGQUIT rather than SIGTERM signal. This will cause the master process to send SIGQUIT to all its children and then wait for them to finish cleanly. This avoids issues like a message being appended by lmtpd but the sync_log record never being written. Since a clean shutdown may never finish if a child process is stuck for some reason the recommended approach is to send a SIGQUIT then loop on the master process sending a signal 0 every second until either the master process has gone away or a suitable time has expired (maybe 10 seconds). You can then send a SIGTERM if the process still exists. At FastMail the following snippet of perl is used (warning: Linux specific signal numbers - check your own system before using this): my $pid = `cat $PIDFILE`; chomp($pid); print "Trying nice shutdown - killing $pid with SIGQUIT\n"; kill 3, $pid; foreach my $num (1..10) { if (kill 0, $pid) { print "Not dead yet after $num seconds\n"; sleep 1; } else { last; } } if (kill 0, $pid) { print "No more Mr. Nice Guy - killing $pid with SIGTERM\n"; kill 15, $pid; } Configuring the Mail Transfer Agent In order to deliver mail to the Cyrus system, you'll have to configure your MTA (Sendmail, Postfix, Exim, etc.) to use LMTP. Configuring Sendmail Generate a sendmail configuration file which delivers local mail to the IMAP server. See the file cf/README in the Sendmail distribution for information on how to create a complete configuration file. This file also lists variables that can be used to customize the mailer definitions mentioned below. The following configurations assume that you are using the lmtpunix service from one of the sample cyrus.conf files discussed above. * For Sendmail 8.12.4 and higher, use the cyrusv2 mailer definition in the Sendmail distribution: define(`confLOCAL_MAILER', `cyrusv2') MAILER(`cyrusv2') If you wish to change the name of the UNIX socket or switch to TCP, define CYRUSV2_MAILER_ARGS appropriately as described in cf/README. * For Sendmail 8.10 - 8.12.3, use the cyrusv2.mc file as a template to create a Sendmail configuration file. * For Sendmail 8.9.x and earlier, use the cyrus mailer definition in the Sendmail distribution: define(`confLOCAL_MAILER', `cyrus') MAILER(`cyrus') Edit /etc/group and add user "daemon" to the "mail" group. This will permit sendmail to run the "deliver" (LMTP client) program to deliver mail to the IMAP server. Cyrus also includes a socket map daemon smmapd which can be used by Sendmail 8.13 and higher (a patch for 8.12 is available) to verify at RCPT TO time that a message can be delivered to the particular mailbox. To use this daemon, add smmapd as a service in cyrus.conf and configure Sendmail accordingly. Configuring Postfix The Postfix source distribution comes with the file "README_FILES/LMTP_README". Even if you are using a binary distribution of Postfix, it would be well worth your while to download the full Postfix source. Not only will you get the above file, but numerous other "readme" files and sample configuration files. One thing you need to watch out for is the UID and GID of the Postfix software. As it states in the Postfix "INSTALL" document, you must create a new account that does not share its UID and GID with any other user account. This is for security reasons. If you installed Postfix with a GID of "mail", you will need to select a different GID for Cyrus. See the Cyrus configure options "--with-cyrus-user" and "--with-cyrus-group". (This was more crucial when the use of Cyrus' "deliver" was more prevalent, but it is still a good idea to follow this policy.) Another thing to note is the location of your "sendmail" command. On some platforms this will be "/usr/sbin/sendmail", on others, "/usr/lib/sendmail". Cyrus will need to know where this command is. See Installing Sieve for more details. Assuming that you are using the lmtpunix service from one of the sample cyrus.conf files discussed above, the Postfix configuration file "/etc/postfix/main.cf" should have the following line: mailbox_transport = lmtp:unix:/var/imap/socket/lmtp Naturally, both the Postfix UID and the Cyrus UID need to be able to access the specified socket file. Starting with Postfix snapshot-20010222, you can improve the efficiency of LMTP delivery via the "mailbox_transport" by putting the following entries in "/etc/postfix/main.cf": local_destination_recipient_limit = 300 local_destination_concurrency_limit = 5 Of course you should adjust these settings as appropriate for the capacity of the hardware you are using. The recipient limit setting can be used to take advantage of the single instance message store capability of Cyrus. The concurrency limit can be used to control how many simultaneous LMTP sessions will be permitted to the Cyrus message store. Additional examples are included in the Postfix file "README_FILES/LMTP_README". Configuring Exim 4 Generate an Exim configuration file which delivers local mail to the IMAP server. See the Exim documentation for information on how to create a complete configuration file. Cyrus is designed to be used as a black-box server -- there are usually no local user accounts. As a result, you must define the following "router": localuser: driver = accept transport = local_delivery The following "transports" assume that you are using either the lmtpunix or lmtp service from one of the sample cyrus.conf files discussed above. * Using lmtpunix (UNIX socket): local_delivery: driver = lmtp command = "/usr/cyrus/bin/deliver -l" batch_max = 20 user = cyrus * Using lmtp (TCP socket -- Exim and Cyrus on same host): local_delivery: driver = smtp protocol = lmtp hosts = localhost allow_localhost For more advanced configurations (such as address verification, etc), consult the Exim documentation and sample configurations. Exporting Netnews via IMAP If you wish to use export Netnews via IMAP, consult install-netnews.html. SSL, TLS, and OpenSSL Transport Layer Security (TLS), is a standardized version of the Secure Sockets Layer (SSL v3) standard. IMAP can make use of two different versions of TLS/SSL: STARTTLS and an SSL wrapped session. In STARTTLS, a client connects to the IMAP port as normal and then issues the STARTTLS command, which begins a TLS negotiation. This is currently supported by the Cyrus IMAP server when it is compiled with OpenSSL. The alternative, a SSL wrapped connection, involves the client connected to a seperate port ("imaps") and negotiating a SSL session before starting the IMAP protocol. Again, this is supported natively by the Cyrus IMAP server when it is compiled with OpenSSL. Both TLS and SSL require a server key and a certificate. Optionally, in addition to establishing a secure connection, TLS can authenticate the client. Configuring Cyrus with OpenSSL 1. OpenSSL requires the certificate and key in PEM format. You can create the server's private key and certificate yourself using OpenSSL. Here, we create a self-signed key for the machine "foobar.andrew.cmu.edu" and put both the certificate and key in the file "/var/imap/server.pem". Please do not blindly enter in the information to OpenSSL below. Instead, enter the appropriate information for your organization (i.e., NOT Carnegie Mellon University for the Organization Name, etc.). openssl req -new -x509 -nodes -out /var/imap/server.pem -keyout /var/imap/server.pem -days 365 Using configuration from /usr/local/lib/openssl/openssl.cnf Generating a 1024 bit RSA private key .............+++++ ......................+++++ writing new private key to '/var/imap/server.pem' ----- You are about to be asked to enter information that will be incorporated into your certificate request. What you are about to enter is what is called a Distinguished Name or a DN. There are quite a few fields but you can leave some blank For some fields there will be a default value, If you enter '.', the field will be left blank. ----- Country Name (2 letter code) [AU]:US State or Province Name (full name) [Some-State]:Pennsylvania Locality Name (eg, city) []:Pittsburgh Organization Name (eg, company) [Internet Widgits Pty Ltd]:Carnegie Mellon University Organizational Unit Name (eg, section) []:Andrew Systems Group Common Name (eg, YOUR name) []:foobar.andrew.cmu.edu Email Address []: 2. Make sure to make key file(s) readable by the Cyrus user. For example: chown cyrus /var/imap/server.pem 3. Add the following to /etc/imapd.conf to tell the server where to find the certificate and key files (used for ALL services): server_cert_file: /var/imap/server.cert server_key_file: /var/imap/server.key Optionally, you can use separate certificates and key files for each service: [servicename]_server_cert_file: /var/imap/imap-server.cert [servicename]_server_key_file: /var/imap/imap-server.key "servicename" here refers to the name of the service as specified in cyrus.conf. It is not necessarily the name of the binary. This is useful if you want to use different hostnames for each service (e.g., via virtual host interfaces or DNS CNAMEs). In the absence of any of the service specific options, the value of the global option is used. A value of disabled for the certificate or key file for a particular service will disable SSL/TLS for that service. If you have a Certificate Authority (CA), you may wish to generate a certificate request and send it to be signed by your CA. By default, Cyrus will cache SSL/TLS sessions for reuse for up to 24 hours. By adjusting the value of the tls_session_timeout option in imapd.conf, the session caching can be disabled (0) or the expiration period shortened. 4. You can test STARTTLS by using imtest: imtest -t "" foobar.andrew.cmu.edu Client-side certificates Client certificates are somewhat harder to configure than server certificates. You'll need a CA (certificate authority) and need to generate client certificates signed by that CA. STARTTLS in Sendmail and other MTAs have similiar problems, so Claus Assman's page is a good reference. You can use the self-signed certificate generated above as a CA for client certificates. To do this, try the following: TODO: write me! Unfortunately, there's no standard on how to convert the client's authenticate DN (distinguished name) to a SASL authentication name. Alternate Namespace and UNIX Hierarchy Convention If you wish to use the alternate namespace and/or the UNIX hierarchy convention, consult altnamespace.html. cyrus-imapd-2.5.10/doc/text/install-upgrade0000644000175000017500000000124113001246663015523 00000000000000Upgrading From Previous Versions Upgrading from all 2.4 series to 2.5 * It is strongly advised to shut down the server completely while performing the upgrade, because newer daemons will write mailboxes.db entries which aren't compatible with the old daemons, and may cause crashes if you try to upgrade a running server. You can start the server again immediately with the new daemons installed. * The most important change is that index file upgrades are no longer automatic. This avoids the IO storm caused by upgrades from 2.3 to 2.4. Even if you are upgrading from Cyrus 2.2, it won't cause an IO cyrus-imapd-2.5.10/doc/text/install-replication0000644000175000017500000001227713001246663016420 00000000000000Cyrus replication Note that Cyrus replication is still relatively young in the grand scheme of things, and if you choose to deploy you are doing so at your own risk. The core of the replication code has been used successfully in production at Cambridge University since the summer of 2003, but it has been rewritten extensively as part of the integration into the mainstream Cyrus codebase. The replication code as integrated into Cyrus 2.3 has been running in production at Fastmail.fm and Columbia.edu since early 2006 and will be put into production at CMU in winter 2007. The Cyrus team owes a debt of gratitude to the kind folks at Cambridge, Columbia, and Fastmail for their considerable effort in helping to identify and correct the bugs the in Cyrus 2.3 replication code. Introduction & Assumptions The Cyrus replication engine is designed to replicate the mailstore on standalone Cyrus servers or "backend" servers in a Cyrus Murder to provide a high-availability environment. It is NOT intended to replicate "frontend" servers or the "mupdate master" in a Cyrus Murder. Note that load balancing is not possible with the current replication code, but it is intended to be supported in the future. This document assumes that you have successfully been able to setup atleast one Cyrus IMAP server. This server will become your first "master" server. It also assumes that you are familliar with the administration and day to day operations of the Cyrus IMAP server and the SASL authentication library. If you feel uncomfortable with this, please refer to the rest of the documentation first. Installation You will need to build Cyrus IMAPd with the --enable-replication configure option. This builds the replication client/server applications and utilities. Requirements * Atleast one standalone or "backend" Cyrus IMAP server. * Atleast one machine that will become the first "replica" server. Configuring the "replica" server The "replica" server is a standalone server which listens for and processes synchronization messages from a "master" server. The "replica" server needs to be configured to accept these synchonization messages. The "replica" server MUST NOT be configured to be part of a Murder (it should only be configured into the Murder at the point at which it replaces a failed backend "master"). 1. Configure a standalone server as described in the rest of the documentation. 2. Add the following line to the "/etc/services" file. csync 2005/tcp Note that the port number is arbitrary as long as its not being used by any other services on your network. 3. Add a line similar to the following in the SERVICES section of cyrus.conf: syncserver cmd="/usr/cyrus/bin/sync_server" listen="csync" 4. Start/restart "/usr/cyrus/bin/master". Configuring the "master" server The "master" server is the standalone or "backend" server which is actively serving mailboxes to clients. This server needs to be configured to synchronize its mailstore with a "replica" server. 1. Add the following line to the "/etc/services" file. csync 2005/tcp Note that the port number MUST be the same as that used on the "replica" server. 2. Specify the hostname of the "replica" server and how to authenticate to it using the following imap.conf options: * sync_host * sync_authname * sync_realm * sync_password Note that sync_authname MUST be an admin on the "replica" server. Also note that sync_realm and sync_password may not be necessary depending on the SASL mechanism used for authentication. Compression If you are running replication over a remote link, then the tradeoff between bandwidth and CPU usage will tilt strongly in favour of enabling compression to save bandwidth at a slight increase in CPU cost. You can set the 'sync_compress' imapd.conf value, or pass the '-z' flag to sync_client. 1. sync_compress: 1 "Rolling" replication "Rolling" replication means that the "master" server continuously synchonizes itself with the replica. To configure "rolling" replication, perform the following: 1. Enable the sync_log option in imapd.conf. This allows the imapd, pop3d, nntpd, and lmtpd services to log synchonization actions which will be periodically serviced by sync_client. 2. Optionally, adjust the sync_repeat_interval in imapd.conf. 3. Add a line similar to the following in the STARTUP section of cyrus.conf: syncclient cmd="/usr/cyrus/bin/sync_client -r" 4. Start/restart "/usr/cyrus/bin/master". Administration Manual replication To manually synchonize any part of the mailstore, simply run sync_client(8) with the appropriate command line options. Note that you CAN manually synchonize even if "rolling" replication has been configured. You can also run cyr_synclog(8) instead, which will insert the record into the rolling replication log. Failover cyrus-imapd-2.5.10/doc/text/install-testing0000644000175000017500000001125313001246663015555 00000000000000Testing the IMAP Server To test the IMAP server, reboot and perform the following steps (all of these samples use "foobar" as the IMAP server name). A list of answers to common installation problems is maintained in http://www.cyrusimap.org/mediawiki/index.php/FAQ#Cyrus_IMAP_Questions. 1. From your normal account, telnet to the IMAP port on the server you're setting up: telnet foobar imap If your server is running, you'll get the following message: Trying 128.2.232.95... Connected to foobar.andrew.cmu.edu. Escape character is '^]'. * OK foobar.andrew.cmu.edu Cyrus IMAP4 v2.0.0 server ready Any message other than one starting with "* OK" means there is a problem. To terminate the connection, type ". logout". Naturally the version number should match the version you just installed. 2. Use "imtest" to test logging in with plaintext passwords: /usr/local/bin/imtest -m login foobar If you want to specify a different user, do: /usr/local/bin/imtest -m login -a USER foobar If your server is running, you'll get the following message: % /usr/local/bin/imtest -m login foobar S: * OK mail1.andrew.cmu.edu Cyrus IMAP4 v2.0.0 server ready C: C01 CAPABILITY S: * CAPABILITY IMAP4 IMAP4rev1 ACL QUOTA LITERAL+ NAMESPACE UIDPLUS X-NON-HIERARCHICAL-RENAME NO_ATOMIC_RENAME AUTH=GSSAPI AUTH=ANONYMOUS AUTH=KERBEROS_V4 UNSELECT S: C01 OK Completed Password: + go ahead L01 OK User logged in Authenticated. Security strength factor: 0 Any message other than one starting with a "L01 OK" means there is a problem. If the test fails, a more specific error message should be written through syslog to the server log. To terminate the connection, type ". logout". 3. You should now test the server with each of the various authentication mechanisms you have installed. The supported mechanisms are listed in the CAPABILITY line: * CAPABILITY IMAP4 IMAP4rev1 ACL QUOTA LITERAL+ NAMESPACE UIDPLUS X-NON-HIERARCHICAL-RENAME NO_ATOMIC_RENAME AUTH=ANONYMOUS AUTH=KERBEROS_V4 AUTH=DIGEST-MD5 AUTH=CRAM-MD5 UNSELECT . OK Completed Each of the mechanism names is preceded by a 'AUTH='. For this example the ANONYMOUS, KERBEROS_V4, DIGEST-MD5, and CRAM-MD5 mechanisms are available. If a mechanism does not appear that you wish to use, examine the libsasl log messages. Generally, if a mechanism does not appear, it means it failed to initialize. (For example, if the server is unable to access the srvtab file the KERBEROS_V4 mechanism will refuse to load.) Plaintext login is a special case: the PLAIN SASL mechanism is only advertised under an encrypted connection. However, plaintext logins are available (as long as you haven't disabled plaintext) by using -m login(as above). To terminate the imtest connection, type ". logout". Once you are satisfied with the authentication mechanism list you should attempt to log in with each of those mechanisms. Run imtest specifying which mechanism you would like to use. /usr/local/bin/imtest -m KERBEROS_V4 foobar C: C01 CAPABILITY S: * OK foobar.andrew.cmu.edu Cyrus IMAP4 v2.0.0 server ready S: * CAPABILITY IMAP4 IMAP4rev1 ACL QUOTA LITERAL+ NAMESPACE UIDPLUS X-NON-HIERARCHICAL-RENAME NO_ATOMIC_RENAME AUTH=ANONYMOUS AUTH=GSSAPI AUTH=KERBEROS_V4 UNSELECT S: C01 OK Completed C: A01 AUTHENTICATE KERBEROS_V4 S: + wYcDAA== C: BAYBQU5EUkVXLkNNVS5FRFUAOCAm7F/Y+HabCzJ /UMtVcvWRjTohuq/USaCV6gYdkAU5DOcADAq S: + 0aAsUGQZhgQ= C: ADMe/cVivAYYzy1yd4Vojg== S: A01 OK Success (privacy protection) Authenticated. Security strength factor: 56 Any message other than one starting with a "A01 OK" means there is a problem. If the test fails, a more specific error message is written through syslog to the server log. To terminate the connection, type ". logout". See the libsasl documentation for a full description of all the mechanisms. It is also possible to support "security layers" (privacy or integrity protected connections). By default, imtest uses the strongest layer available with the selected mechanism; use "-l" to choose an alternate layer. cyrus-imapd-2.5.10/doc/text/install-sieve0000644000175000017500000000731613001246663015220 00000000000000Installing Sieve This section assumes that you compiled Cyrus with sieve support. If you specified --disable-sieve when running ./configure, you did NOT compile the server with sieve support. Configure outgoing mail Some Sieve actions (redirect, vacation) can send outgoing mail. You'll need to make sure that "lmtpd" can send outgoing messages. Currently, it invokes "/usr/lib/sendmail" by default to send messages. Change this by adding a line like: sendmail: /usr/sbin/sendmail in your "/etc/imapd.conf". If you're using Postfix or another MTA, make sure that the sendmail referenced in "/etc/imapd.conf" is Sendmail-compatible. Managing Sieve Scripts Since Cyrus is based around the concept of a sealed-server, the normal way for users to manipulate Sieve scripts is through the "sieveshell" utility. If, for some reason, you do have user home directories on the server, you can use the "sieveusehomedir" option and have the sieve script stored in the home directory of the user as "~/.sieve". Testing the sieve server 1. "timsieved", is a ManageSieve server used for transporting user Sieve scripts to the sealed IMAP server. It is incompatible with the "sieveusehomedir" option. It is named after the principal author, Tim Martin, who desperately wanted something named after him in the Cyrus distribution. 2. From your normal account, telnet to the sieve port on the server you're setting up: telnet foobar sieve If your server is running, you'll get a message similar to the following one: Trying 128.2.10.192... Connected to foobar.andrew.cmu.edu. Escape character is '^]'. "IMPLEMENTATION" "Cyrus timsieved v1.1.0" "SASL" "ANONYMOUS PLAIN KERBEROS_V4 GSSAPI" "SIEVE" "fileinto reject envelope vacation imapflags notify subaddress regex" OK Any message other than one similar to the one above means there is a problem. Make sure all of authentication methods you wish to support are listed. This list should be identical to the one listed by "imapd" earlier. Next terminate the connection, by typing "logout". 3. Next test authenticating to the sieve server. To do this run the "sieveshell" utility. You must specify the server. If you run this utility from a different machine without the "sieve" entry in "/etc/services", port 4190 will be used. "sieveshell foobar" Please enter your password: ****** > quit This should produce the message "Authentication failed" with a description of the failure if there was a problem. 4. Next you should attempt to place a sieve script on the server. To do this create a file named "myscript.script" with the following lines. Replace "foo@example.org" with an email address you can send mail from, but that is not the one you are working on now. require ["reject","fileinto"]; if address :is :all "From" "foo@example.org" { reject "testing"; } To place this script on the server run the following command: "sieveshell foobar" Please enter your password: ****** > put myscript.script > activate myscript > quit This should place your script on the server and make it the active script. 5. Test that the sieve script is actually run from deliver. Send a message to the address you're working on from the address mentioned in the sieve script. The message should be rejected. cyrus-imapd-2.5.10/doc/text/bugs0000644000175000017500000000624213001246663013376 00000000000000 Known bugs in the Cyrus IMAP Server We're working on moving to a Bugzilla database. It's still being built up, but you can search/add to it here. Eventually, all the bugs below will be in there. imapd and core utilities * Multiple APPENDs don't always correctly return the EXISTS response. (can't reproduce?) * Particularly large quotas can wrap around. * The RENAME command is not atomic. * reconstruct doesn't deal with the mailboxes.db file. * we should deal with having to reset UIDs * the algorithm used for naming stage files is fragile and not threadsafe. * during appendstage(), the message is parsed once per delivery, not once at the beginning. * master should pay attention to processes that have told it they are listening, and make sure they don't die abnormally. likewise, it should be on the lookout for continually forking services. * master should probably have a babysitting service ("always keep this process running"). proxyd and Cyrus Murder * RENAME across servers isn't implemented. * Tagged lines with literals can cause problems for proxyd. lmtpd, deliver, and sieve * 8-bit set characters are coerced to 'X', but not before the notify_zephyr code (if used) has had a chance to send them out. * Deliver does not handle messages containing NUL properly due to stdio problems (the characters between the NUL and the LF will be lost.) * Deliver doesn't gracefully handle CR CR sequences in messages. Well, ok, it hangs. authentication and authorization * Using AFS groups with ptclient, users with negative rights as part of groups may be granted access to mailboxes if ptclient has died. We plan to have this fixed eventually. * In some failures of the krbck program, the error messages printed out bear no resemblance to what actually went wrong. other utilities * cyradm may need to change authname/username stuff. Something to check. * imtest: it would be nice for the authorization name to default to the authentication name, except when specifically overridden. * any utilities doing db operations should catch signals and poll for them to see if it should exit (like mbpath, ipurge). libraries Things we want to do * Implement the IMAP VIEW extension. * Implement the IMAP ANNOTATE extension. * Implement some sort of backup/restore system that's more efficient and easier to use than Amanda on the filesystem. * Add mailbox version numbers. * Add mailbox tombstones (gives NEWNAME support). * Design and implement ALIST, the advanced list command. * Investigate changing from the prot layer to using sfio. * Write a test module for lmtpengine. * Allow renaming users. (RENAME user.joe user.harry.) Needs to move all metadata per-user data. (seen, subscriptions, sieve state?) Please refer to Sending Feedback if you would like to submit a bug, feature request or (best of all) patch. cyrus-imapd-2.5.10/doc/text/install-admin-mb0000644000175000017500000000523213001246663015564 00000000000000Administering Mailboxes The "cyradm" command (see the cyradm(1) man page for complete documentation) manages the creation of, deletion of, ACLs on, and quotas on mailboxes. To get an overview of the command, type "cyradm ". Once "cyradm" has started, the user prompt is replaced with the name of the host followed by a ">". Type "help" at the new prompt. The following information is displayed: createmailbox, cm create a mailbox deleteaclmailbox, dam delete an ACL on a mailbox deletemailbox, dm delete a mailbox help get help on commands listaclmailbox, lam list the ACL on a mailbox listmailbox, lm list mailboxes listquota, lq list quota on root listquotaroot, lqr, lqm list quota roots on mailbox quit exit program renamemailbox, renm rename a mailbox setaclmailbox, sam set an ACL on a mailbox setquota, sq set quota limits Note:It's not necessary to run "cyradm" on the same system as the IMAP server. Note:If you run "cyradm" on a system not using Kerberos for authentication, you will be prompted for your user name and password before you can issue any "cyradm" commands. By default, you will be prompted for the password of the user ID of the current shell. If you want to authenticate as a different user, use the "-a" option. If the user that you authenticate as is a Cyrus admin, you can proxy as a particular user by also using the "-u" option. The mailbox naming convention requires that the primary mailbox (INBOX) for anyone must be named "user.". To create a mailbox, type: createmailbox user. For example, to create a mailbox for the userid "smith", type: createmailbox user.smith To limit "smith" to 10,000 kilobytes of mail, type: setquota user.smith 10000 Once the INBOX is created, users can create their own additional mailboxes from a mail program. If Smith created a work mailbox and a play mailbox, the full names of the mailboxes would be: user.smith.work user.smith.play Access rights are discussed in detail in the cyradm(1) man pages. Note that the administrator must grant herself create/delete access explicitly before she can delete a mailbox: setaclmailbox c deletemailbox Once you have created mailboxes, your IMAP server installation is done. You must then configure a mail interface, such as Pine or Mulberry, to work with the IMAP server. cyrus-imapd-2.5.10/doc/text/questions0000644000175000017500000000031213001246663014460 00000000000000 Questions we really should answer. If you feel like doing us a favor, sit down and answer one. * What are the performance implications of single-instance store (as of 1.6.22)? cyrus-imapd-2.5.10/doc/text/overview0000644000175000017500000007712713001246663014316 00000000000000Cyrus IMAP Server: Overview and Concepts This document gives an overview of the Cyrus IMAP server. The Cyrus IMAP (Internet Message Access Protocol) server provides access to personal mail and system-wide bulletin boards through the IMAP protocol. The Cyrus IMAP server is a scalable enterprise mail system designed for use from small to large enterprise environments using standards-based technologies. A full Cyrus IMAP implementation allows a seamless mail and bulletin board environment to be set up across multiple servers. It differs from other IMAP server implementations in that it is run on "sealed" servers, where users are not normally permitted to log in. The mailbox database is stored in parts of the filesystem that are private to the Cyrus IMAP system. All user access to mail is through software using the IMAP, IMAPS, POP3, POP3S, or KPOP protocols. The private mailbox database design gives the server large advantages in efficiency, scalability, and administratability. Multiple concurrent read/write connections to the same mailbox are permitted. The server supports access control lists on mailboxes and storage quotas on mailbox hierarchies. This document is organized into the following areas: * Mailbox Namespace * Standard (Internal) Namespace * Alternate Namespace * Access Control Lists * Access Rights * Identifiers * "anonymous" and "anyone" * Kerberos vs. Unix Authorization * Negative Rights * Calculating Users' Rights * Implicit Rights for Administrators on Personal Mailboxes * Initial ACLs for Newly Created Mailboxes * Login Authentication * Anonymous Logins * Kerberos Logins * Unix Logins * Quotas * Supports Quotas on Storage * Quota Roots * Mail Delivery Behavior * Quota Warnings Upon Select When User Has "d" Rights * Quotas and Partitions * New Mail Notification * Partitions * Specifying Partitions with "create" * Changing Partitions with "rename" * News * POP3 Server * The syslog facility * Mail Directory Recovery * Reconstructing Mailbox Directories * Reconstructing the Mailboxes File * Reconstructing Quota Roots * Removing Quota Roots * Subscriptions * Configuration Directory * "log" Directory * "proc" Directory * Message Delivery * Local Mail Transfer Protocol * Single Instance Store * Duplicate Delivery Suppression * Sieve, a Mail Filtering Language Mailbox Namespace By default, the Cyrus IMAP server presents mailboxes using the netnews namespace convention. Mailbox names are case-sensitive. A mailbox name may not start or end with a "." character, nor may it contain two "." characters in a row. In this implementation, non-ASCII characters and shell metacharacters are not permitted in mailbox names. Optionally, the server can present mailboxes using the UNIX hierarchy convention. Standard (Internal) Namespace All personal mailboxes for user "bovik" begin with the string "user.bovik.". For example, if user "bovik" had a personal "work" mailbox, it would be called "user.bovik.work". To user "bovik", however, the prefix "user.bovik." normally appears as "INBOX.". The mailbox "user.bovik.work" would therefore appear as "INBOX.work". If the access control list of the mailbox permitted other users to see that mailbox, it would appear to them as "user.bovik.work". The mailbox "user.bovik" is where the user "bovik" normally receives new mail, and normally appears to user "bovik" as "INBOX". The mailbox "user.bovik" is referred to in this document as user "bovik"'s INBOX. Administrators create and delete users by creating and deleting the users' INBOX. If a user has an INBOX, then they are allowed to subscribe to mailboxes. Only users without dots in their userid are permitted to have an INBOX. (A user with a dot in their userid would be able to login but would not be able to receive mail. Note that when using the unix hierarchy seperator, this is not the case, and any user may have a dot in their userid.) When an administrator deletes a user's INBOX, all of the user's personal mailboxes are deleted as well. With the one notable exception of INBOX, all mailbox names are system-wide--they refer to the same mailbox regardless of the user. Access control lists determine which users can access or see which mailboxes. Using In contexts which permit relative mailbox names, the mailbox namespace works as follows: * Names that do not start with "." are fully qualified. * Names that start with "." are relative to the current context. Thus, if you are working with folder names and the top of the hierarchy is named "cmu.", the name "comp.infosystems.www" resolves to "comp.infosystems.www" and the name ".comp.infosystems.www" resolves to "cmu.comp.infosystems.www". Alternate Namespace The Cyrus IMAP server can also use an alternate namespace which allows a user's personal mailboxes to appear as if they reside at the same level as that user's INBOX as opposed to children of it. With this feature, it may appear that there are non-unique names for mailboxes between users (2 different users may each have a top level "work" mailbox), but the internal representation is still user.name.work. Access Control Lists Access to each mailbox is controlled by each mailbox's access control list. Access Control Lists (ACLs) provide a powerful mechanism for specifying the users or groups of users who have permission to access the mailboxes. An ACL is a list of zero or more entries. Each entry has an identifier and a set of rights. The identifier specifies the user or group of users for which the entry applies. The set of rights is one or more letters or digits, each letter or digit conferring a particular privilege. Access Rights The defined rights are: l lookup - The user may see that the mailbox exists. r read - The user may read the mailbox. The user may select the mailbox, fetch data, perform searches, and copy messages from the mailbox. s seen - Keep per-user seen state. The "Seen" and "Recent" flags are preserved for the user. w write - The user may modify flags and keywords other than "Seen" and "Deleted" (which are controlled by other sets of rights). i insert - The user may insert new messages into the mailbox. p post - The user may send mail to the submission address for the mailbox. This right differs from the "i" right in that the delivery system inserts trace information into submitted messages. c create - The user may create new sub-mailboxes of the mailbox, or delete or rename the current mailbox. d delete - The user may store the "Deleted" flag, and perform expunges. a administer - The user may change the ACL on the mailbox. You can combine access rights in different ways. For example: lrs The user can read the mailbox. lrsp The user can read the mailbox, and can post to it through the delivery system. Most delivery systems do not provide authentication, so the "p" right usually has meaning only for the "anonymous" user. lr The user can see the mailbox and can read it, but the server does not preserve the "Seen" and "Recent" flags. This set of rights is primarily useful for "anonymous IMAP." rs The user can read the mailbox and the server preserves the "Seen" and "Recent" flags, but the mailbox is not visible to the user through the various mailbox listing commands. The user must know the name of the mailbox to be able to access it. lrsip The user can read and append to the mailbox, either through IMAP, or through the delivery system. Identifiers The identifier part of an ACL entry specifies the user or group for which the entry applies. There are two special identifiers, "anonymous", and "anyone", which are explained below. The meaning of other identifiers usually depends on the authorization mechanism being used (selected by --with-auth at compile time, defaulting to Unix). "anonymous" and "anyone" With any authorization mechanism, two special identifiers are defined. The identifier "anonymous" refers to the anonymous, or unauthenticated user. The identifier "anyone" refers to all users, including the anonymous user. Kerberos vs. Unix Authorization The Cyrus IMAP server comes with four authorization mechanisms, one is compatible with Unix-style ("/etc/passwd") authorization, one for use with Kerberos 4, one for use with Kerberos 5, and one for use with an external authorization process (ptloader) which can interface with other group databases (e.g. AFS PTS groups, LDAP Groups, etc). Note that authorization is not authentication. Authentication is the act of proving who you are. Authorization is the act of determining what rights you have. Authentication is discussed in the Login Authentication part of this document. In the Unix authorization mechanism, identifiers are either a valid userid or the string "group": followed by a group listed in "/etc/group". Thus: root Refers to the user root group:staff Refers to the group staff It is also possible to use unix groups with users authenticated through a non-/etc/passwd backend. Note that using unix groups in this way (without associated /etc/passwd entries) is not recommended. Using the Kerberos authorization mechanism, identifiers are of the form: principal.instance@realm If ".instance" is omitted, it defaults to the null string. If "@realm" is omitted, it defaults to the local realm. The file "/etc/krb.equiv" contains mappings between Kerberos principals. The file contains zero or more lines, each containing two fields. Any identity matching the first field of a line is changed to the second identity during canonicalization. For example, a line in "/etc/krb.equiv" of: bovik@REMOTE.COM bovik will cause the identity "bovik@REMOTE.COM" to be treated as if it were the local identity "bovik". A site may wish to write their own authorization mechanism, perhaps to implement a local group mechanism. If it does so (by implementing an auth_[whatever] module), it will dictate its own form and meaning of identifiers. Negative Rights Any of the above defined identifiers may be prefixed with a "-" character. The associated rights are then removed from that identifier. These are referred to as "negative rights". Calculating Users' Rights To calculate the set of rights granted to a user, the server first calculates the union of all of the rights granted to the user and to all groups the user is a member of. The server then calculates and removes the union of all the negative rights granted to the user and to all groups the user is a member of. For example, given the ACL: anyone lrsp fred lwi -anonymous s The user "fred" will be granted the rights "lrswip" and the anonymous user will be granted the rights "lrp". Implicit Rights for Administrators on Personal Mailboxes Regardless of the ACL on a mailbox, users who are listed in the "admins" configuration option in "/etc/imapd.conf" implicitly have the "l" and "a" rights on all mailboxes. Users also implicitly have the "l" and "a" rights on their INBOX and all of their personal mailboxes. Initial ACLs for Newly Created Mailboxes When a mailbox is created, its ACL starts off with a copy of the ACL of its closest parent mailbox. When a user is created, the ACL on the user's INBOX starts off with a single entry granting all rights to the user. When a non-user mailbox is created and does not have a parent, its ACL is initialized to the value of the "defaultacl" option in "/etc/imapd.conf" Note that some rights are available implicitly, for example 'anonymous' always has 'p' on user INBOXes, and users always have rights on mailboxes within their INBOX hierarchy. Login Authentication This section discusses different types of authentication (ways of logging in) that can be used with Cyrus IMAP. The Cyrus IMAP server uses the Cyrus SASL library for authentication. This section describes how to configure SASL with use with Cyrus imapd. Please consult the Cyrus SASL System Administrator's Guide for more detailed, up-to-date information. Anonymous Logins Regardless of the SASL mechanism used by an individual connection, the server can support anonymous login. If the "allowanonymouslogin" option in "/etc/imapd.conf" is turned on, then the server will permit plaintext password logins using the user "anonymous" and any password. Additionally, the server will enable any SASL mechanisms that allow anonymous logins. Plaintext Authentication The SASL library has several ways of verifying plaintext passwords Plaintext passwords are passed either by the IMAP LOGIN command or by the SASL PLAIN mechanism (under a TLS layer). * PAM * Kerberos v4 Plaintext passwords are verified by obtaining a ticket for the server's Kerberos identity, to protect against Kerberos server spoofing attacks. * /etc/passwd * /etc/shadow * etc. sasl_auto_transition automatically creates secrets for shared secret authentication when given a password. The method of plaintext password verification is always through the SASL library, even in the case of the internal LOGIN command. This is to allow the SASL library to be the only source of authentication information. You'll want to look at the sasl_pwcheck_method option in the SASL documentation to understand how to configure a plaintext password verifier for your system. To disallow the use of plaintext passwords for authentication, you can set allowplaintext: no in imapd.conf. This will still allow PLAIN under TLS, but IMAP LOGIN commands will now fail. Kerberos Logins The Kerberos SASL mechanism supports the KERBEROS_V4 authentication mechanism. The mechanism requires that a srvtab file exist in the location given in the "srvtab" configuration option. The srvtab file must be readable by the Cyrus server and must contain a "imap.@" service key, where is the first component of the server's host name and is the server's Kerberos realm. The server will permit logins by identities in the local realm and identities in the realms listed in the "loginrealms" option in "/etc/imapd.conf". The file "/etc/krb.equiv" contains mappings between Kerberos principals. The file contains zero or more lines, each containing two fields. Any identity matching the first field of a line is permitted to log in as the identity in the second field. If the "loginuseacl" configuration option is turned on, than any Kerberos identity that is granted the "a" right on the user's INBOX is permitted to log in as that user. Shared Secrets Logins Some mechanisms require the user and the server to share a secret (generally a password) that can be used for comparison without actually passing the password in the clear across the network. For these mechanism (such as CRAM-MD5 and DIGEST-MD5), you will need to supply a source of passwords, such as the sasldb (which is described more fully in the Cyrus SASL distribution) Quotas Quotas allow server administrators to limit resources used by hierarchies of mailboxes on the server. Supports Quotas on Storage The Cyrus IMAP server supports quotas on storage, which is defined as the number of bytes of the relevant RFC-822 messages, in kilobytes. Each copy of a message is counted independently, even when the server can conserve disk space use by making hard links to message files. The additional disk space overhead used by mailbox index and cache files is not charged against a quota. Quota Roots Quotas are applied to quota roots, which can be at any level of the mailbox hierarchy. Quota roots need not also be mailboxes. Quotas on a quota root apply to the sum of the usage of any mailbox at that level and any sub-mailboxes of that level that are not underneath a quota root on a sub-hierarchy. This means that each mailbox is limited by at most one quota root. For example, if the mailboxes user.bovik user.bovik.list.imap user.bovik.list.info-cyrus user.bovik.saved user.bovik.todo exist and the quota roots user.bovik user.bovik.list user.bovik.saved exist, then the quota root "user.bovik" applies to the mailboxes "user.bovik" and "user.bovik.todo"; the quota root "user.bovik.list" applies to the mailboxes "user.bovik.list.imap" and "user.bovik.list.info-cyrus"; and the quota root "user.bovik.saved" applies to the mailbox "user.bovik.saved". Quota roots are created automatically when they are mentioned in the "setquota" command. Quota roots may not be deleted through the protocol, see Removing Quota Roots for instructions on how to delete them. Mail Delivery Behavior Normally, in order for a message to be inserted into a mailbox, the quota root for the mailbox must have enough unused storage so that inserting the message will not cause the block quota to go over the limit. Mail delivery is a special case. In order for a message to be delivered to a mailbox, the quota root for the mailbox must not have usage that is over the limit. If the usage is not over the limit, then one message may be delivered regardless of its size. This puts the mailbox's usage over the quota, causing a user to be informed of the problem and permitting them to correct it. If delivery were not permitted in this case, the user would have no practical way of knowing that there was mail that could not be delivered. If the usage is over the limit, then the mail delivery will fail with a temporary error. This will cause the delivery system to re-attempt delivery for a couple of days (permitting the user time to notice and correct the problem) and then return the mail to the sender. Quota Warnings Upon Select When User Has "d" Rights When a user selects a mailbox whose quota root has usage that is close to or over the limit and the user has "d" rights on the mailbox, the server will issue an alert notifying the user that usage is close to or over the limit. The threshold of usage at which the server will issue quota warnings is set by the "quotawarn" configuration option. The server only issues warnings when the user has "d" rights because only users with "d" rights are capable of correcting the problem. Quotas and Partitions Quota roots are independent of partitions. A single quota root can apply to mailboxes in different partitions. New Mail Notification The Cyrus IMAP server comes with a notification daemon which supports multiple mechanisms for notifying users of new mail. Notifications can be configured to be sent upon normal delivery ("MAIL" class) and/or sent as requested by a Sieve script ("SIEVE" class). By default, both types of notifications are disabled. Notifications are enabled by using one or both of the following configuration options: * the "mailnotifier" option selects the notifyd method to use for "MAIL" class notifications * the "sievenotifier" option selects the notifyd method to use for "SIEVE" class notifications (when no method is specified by the Sieve action) Partitions Partitions allow administrators to store different mailboxes in different parts of the Unix filesystem. This is intended to be used to allow hierarchies of mailboxes to be spread across multiple disks. Specifying Partitions with "create" When an administrator creates a new mailbox, the name of the partition for the mailbox may be specified using an optional second argument to the "create" command. Non-administrators are not permitted to specify the partition of a mailbox. If the partition is not specified, then the mailbox inherits the partition of its most immediate parent mailbox. If the mailbox has no parent, it gets the partition specified in the "defaultpartition" configuration option. The optional second argument to the "create" command can usually be given only when using a specialized Cyrus-aware administrative client such as cyradm. Changing Partitions with "rename" An administrator may change the partition of a mailbox by using the rename command with an optional third argument. When a third argument to rename is given, the first and second arguments can be the same--this changes the partition of a mailbox without changing its name. If a third argument to rename is not given and the first argument is not "INBOX", the partition of a mailbox does not change. If a third argument to rename is not given and the first argument is "INBOX", the newly created mailbox gets the same partition it would get from the "create" command. News Cyrus has the ability to export Usenet via IMAP and/or export shared IMAP mailboxes via an NNTP server which is included with Cyrus. For more information on exporting news groups through the IMAP server, see install-netnews.html. POP3 Server The Cyrus IMAP server software comes with a compatibility POP3 server. Due to limitations in the POP3 protocol, the server can only access a user's INBOX and only one instance of a POP3 server may exist for any one user at any time. While a POP3 server has a user's INBOX open, expunge operations from any concurrent IMAP session will fail. When Kerberos login authentication is being used, the POP3 server uses the server identity "pop.host@realm" instead of "imap.host@realm", where "host" is the first component of the server's host name and "realm" is the server's Kerberos realm. When the POP3 server is invoked with the "-k" switch, the server exports MIT's KPOP protocol instead of generic POP3. The syslog facility The Cyrus IMAP server software sends log messages to the "local6" syslog facility. The severity levels used are: * CRIT - Critical errors which probably require prompt administrator action * ERR - I/O errors, including failure to update quota usage. The syslog message includes the specific file and Unix error. * WARNING - Protection mechanism failures, client inactivity timeouts * NOTICE - Authentications, both successful and unsuccessful * INFO - Mailbox openings, duplicate delivery suppression Mail Directory Recovery This section describes the various databases used by the Cyrus IMAP server software and what can be done to recover from various inconsistencies in these databases. Reconstructing Mailbox Directories The largest database is the mailbox directories. Each mailbox directory contains the following files: message files There is one file per message, containing the message in RFC 822 format. Lines in the message are separated by CRLF, not just LF. The file name of each message is the message's UID followed by a dot (.). In netnews newsgroups, the message files instead follow the format and naming conventions imposed by the netnews software. cyrus.header This file contains a magic number and variable-length information about the mailbox itself. cyrus.index This file contains fixed-length information about the mailbox itself and each message in the mailbox. cyrus.cache This file contans variable-length information about each message in the mailbox. cyrus.seen This file contains variable-length state information about each reader of the mailbox who has "s" permissions. The "reconstruct" program can be used to recover from corruption in mailbox directories. If "reconstruct" can find existing header and index files, it attempts to preserve any data in them that is not derivable from the message files themselves. The state "reconstruct" attempts to preserve includes the flag names, flag state, and internal date. "Reconstruct" derives all other information from the message files. An administrator may recover from a damaged disk by restoring message files from a backup and then running reconstruct to regenerate what it can of the other files. The "reconstruct" program does not adjust the quota usage recorded in any quota root files. After running reconstruct, it is advisable to run "quota -f" (described below) in order to fix the quota root files. Reconstructing the Mailboxes File NOTE: CURRENTLY UNAVAILABLE The mailboxes file in the configuration directory is the most critical file in the entire Cyrus IMAP system. It contains a sorted list of each mailbox on the server, along with the mailboxes quota root and ACL. To reconstruct a corrupted mailboxes file, run the "reconstruct -m" command. The "reconstruct" program, when invoked with the "-m" switch, scavenges and corrects whatever data it can find in the existing mailboxes file. It then scans all partitions listed in the imapd.conf file for additional mailbox directories to put in the mailboxes file. The cyrus.header file in each mailbox directory stores a redundant copy of the mailbox ACL, to be used as a backup when rebuilding the mailboxes file. Reconstructing Quota Roots The subdirectory "quota" of the configuration directory (specified in the "configdirectory" configuration option) contains one file per quota root, with the file name being the name of the quota root. These files store the quota usage and limits of each of the quota roots. The "quota" program, when invoked with the "-f" switch, recalculates the quota root of each mailbox and the quota usage of each quota root. Removing Quota Roots To remove a quota root, remove the quota root's file. Then run "quota -f" to make the quota files consistent again. Subscriptions The subdirectory "user" of the configuration directory contains user subscriptions. There is one file per user, with a filename of the userid followed by ".sub". Each file contains a sorted list of subscribed mailboxes. There is no program to recover from damaged subscription files. A site may recover from lost subscription files by restoring from backups. Configuration Directory Many objects in the configuration directory are discussed in the Database Recovery section. This section documents two other directories that reside in the configuration directory. "log" Directory The subdirectory "log" under the configuration directory permits administrators to keep protocol telemetry logs on a per-user basis. If a subdirectory of "log" exists with the same name as a user, the IMAP and POP3 servers will keep a telemetry log of protocol sessions authenticating as that user. The telemetry log is stored in the subdirectory with a filename of the server process-id and starts with the first command following authentication. "proc" Directory The subdirectory "proc" under the configuration directory contains one file per active server process. The file name is the ASCII representation of the process id and the file contains the following tab-separated fields: * hostname of the client * login name of the user, if logged in * selected mailbox, if a mailbox is selected The file may contain arbitrary characters after the first newline character. The "proc" subdirectory is normally be cleaned out on server reboot. Message Delivery Mail transport agents such as Sendmail, Postfix, or Exim communicate with the Cyrus server via LMTP (the Local Mail Transport Protocol) implemented by the LMTP daemon. This can be done either directly by the MTA (prefered, for performance reasons) or via the deliver LMTP client. Local Mail Transfer Protocol LMTP, the Local Mail Transfer Protocol, is a variant of SMTP design for transferring mail to the final message store. LMTP allows MTAs to deliver "local" mail over a network. This is an easy optimization so that the IMAP server doesn't need to maintain a queue of messages or run an MTA. The Cyrus server implements LMTP via the lmtpd daemon. LMTP can either be used over a network via TCP or local via a UNIX domain socket. There are security differnces between these two alternatives; read more below For final delivery via LMTP over a TCP socket, it is necessary to use LMTP AUTH. This is accomplished using SASL to authenticate the delivering user. If your mail server is performing delivery via LMTP AUTH (that is, using a SASL mechanism), you will want their authentication id to be an LMTP admins (either via the admins imapd.conf option or via the _admins option, typically lmtp_admins). Alternatively you may deliver via LMTP to a unix domain socket, and the connection will be preauthenticated as an administrative user (and access control is accomplished by controlling access to the socket). Note that if a user has a sieve script, the sieve script runs authorized as *that* user, and the rights of the posting user are ignored for the purposes of determining the outcome of the sieve script. Single Instance Store If a delivery attempt mentions several recipients (only possible if the MTA is speaking LMTP to lmtpd), the server attempts to store as few copies of a message as possible. It will store one copy of the message per partition, and create hard links for all other recipients of the message. Single instance store can be turned off by using the "singleinstancestore" flag in the configuration file. Duplicate Delivery Suppression A message is considered a duplicate if two copies of a message with the same message-id and the same envelope receipient are received. Cyrus uses the duplicate delivery database to hold this information, and it looks approximately 3 days back in the default install. Duplicate delivery suppression can be turned off by using the "duplicatesuppression" flag in the configuration file. Sieve, a Mail Filtering Language Sieve is a mail filtering language that can filter mail into an appropriate IMAP mailbox as it is delivered via lmtp. For more information, look here. Cyrus Murder, the IMAP Aggregator Cyrus now supports the distribution of mailboxes across a number of IMAP servers to allow for horizontal scalability. For information on setting up this configuration, see here. cyrus-imapd-2.5.10/doc/text/install-http0000644000175000017500000001750713001246663015067 00000000000000Cyrus HTTP (RSS, CalDAV, CardDAV, iSchedule, TimeZone) Note that the HTTP service and associated modules in Cyrus are still under development. This release should be considered beta quality. Introduction Cyrus http service has the ability to: * Serve IMAP mailboxes as RSS feeds. * Act as a calendar and scheduling (CalDAV) server by using IMAP mailboxes as calendar collections and RFC 5322 messages to store iCalendar data. * Act as a contacts (CardDAV) server by using IMAP mailboxes as addressbook collections and RFC 5322 messages to store vCard data. * Allow scheduling transactions between separate calendaring and scheduling systems via the iSchedule protocol (currently only used within a Cyrus Murder). * Act as a Time Zone Distribution Service by serving iCalendar (VTIMEZONE) data to client systems. * Serve static content (such as the RSS feed list template and/or the CalDAV/CardDAV JavaScript clients mentioned below). Unlike the Apache HTTP Server, Cyrus HTTP is NOT a general purpose HTTP server. Its feature set is limited to what is required to support the facilities listed above. This document assumes that you are familiar with building and configuring a Cyrus server. If you have not already done so, please read and understand the rest of the installation documentation before continuing. Note: The "Installation" section below augments the "Compiling the IMAP Server" document. The remaining sections assume that your Cyrus server has already been successfully configured. This document also assumes that you are familiar with RSS, WebDAV, calendaring, and contacts. Installation You will need to build Cyrus with the --enable-http configure option. This builds httpd and the associated modules and utilities based on the availability of the prerequisites listed below. General Requirements * Must have LibXML2 installed. * Must have a recent SASL release (v2.1.26 or later) in order to support HTTP Digest, Negotiate, and NTLM authentication. Otherwise, only HTTP Basic authentication will be available. * Optionally install OpenSSL for HTTPS support. * Optionally install Zlib for compression support. Additional CalDAV / CardDAV Requirements * Must have Libical installed. * Must have SQLite v3.x (or later) installed. * Optionally install Jansson for jCal/jCard support. * Optionally install ICU4C for non-Gregorian calendar support, if Libical has support for the RSCALE extension. Additional iSchedule Requirements * Must meet CalDAV requirements above. * Must have OpenDKIM with support for iSchedule canonicalization installed (currently requires a CMU patch). Additional Time Zone Distribution Service Requirements * Must have Libical installed. * Must have Jansson installed. General Configuration The Cyrus httpd service is configurable via several options in imapd.conf. Several of those options are discussed in the sections below. Admins should consult the imapd.conf(5) manpage for the full list of options used by the httpd service and its various modules. The support for RSS, CalDAV, and CardDAV is divided into separate modules which run as part of the Cyrus httpd service. Selection of which module(s) are enabled is done by setting the httpmodules option accordingly. By default, no modules are enabled. Cyrus httpd also can serve static content, the location of which is set by the httpdocroot option. Any content contained in the specified directory (including sub-directories) will be served as static content only. Cyrus httpd does NOT have the ability to execute any server-side scripts. HTTP Authentication As with other Cyrus services, the Cyrus httpd service uses Cyrus SASL to perform its authentication. Cyrus supports the following HTTP authentication schemes: Basic, Digest, Negotiate (Kerberos only), and NTLM. While Basic is available in all versions of SASL, the remaining schemes are only available in Cyrus SASL 2.1.16 (and higher). Similar to plaintext login commands supported by the other Cyrus services (IMAP LOGIN, POP3 USER/PASS), the Cyrus httpd service determines whether to advertise the HTTP Basic authentication scheme based on the allowplaintext option and whether the client has connected over a TLS protected connection (HTTPS). The availability of the other HTTP authentication schemes is controlled by the sasl_mech_list option. For Cyrus httpd the DIGEST-MD5, GSS-SPNEGO, and NTLM SASL plugins support the Digest, Negotiate, and NTLM authentication schemes respectively, provided that these plugins are installed on the server. RSS Module Configuration When enabled, the RSS module will default to serving ALL mailboxes to which the authenticated user has access as RSS feeds. The rss_feeds option can be used to limit the set of mailboxes that can be served as RSS feeds. For example, setting rss_feeds to *,!user will serve all shared mailboxes, but no personal mailboxes. The list of available RSS feeds can be obtained by clients by accessing the /rss/ URL on the Cyrus server. By default, the server will present the list as a simple unordered list in an HTML document. To customize the look and feel of the feed list, the rss_feedlist_template option can be used to point to a HTML template file. This file can utilize Cascading Style Sheets, JavaScript, etc. Any and all content that the template file references MUST reside under the httpdocroot as set above. Consult the imapd.conf(5) manpage for specifics on the required contents of this custom file. Note that for sites running Cyrus Murder, rss_feedlist_template only needs to be set on frontend servers, since only those servers have the complete mailbox list. CalDAV Module Configuration When enabled, the CalDAV module allows Cyrus to function as a calendar and scheduling server. This module uses a subset of the mailbox hierarchy as calendar collections, the toplevel of which is specified by the calendarprefix option. The public calendar hierarchy will reside at the toplevel of the shared mailbox namespace. A user's personal calendar hierarchy will be a child of their Inbox. For example, using the default value for calendarprefix, a calendar named Default for user murch would reside in the mailbox named user.murch.#calendars.Default. Note that mailboxes in the calendar hierarchies (those under calendarprefix) SHOULD NOT be accessed with an IMAP client as doing so will leave a mailbox in a state unsuitable for CalDAV. To this end, calendar mailboxes will not be returned by Cyrus imapd in response to an IMAP client's request for the available mailbox list, but Cyrus imapd will not otherwise prevent an IMAP client from accessing them. By default, the CalDAV module will automatically perform scheduling operations when a scheduling object (invite or reply) is stored on or deleted from the server. Support for the calendar-auto-schedule feature can be disabled with the caldav_allowscheduling option. Administration Calendar provisioning The CalDAV module will automatically create the required calendars for a user the first time that the user authenticates to the CalDAV server. Note that the user MUST have an existing IMAP Inbox in order for the calendars to be created. Calendar access controls The CalDAV module uses the same access controls as the other Cyrus services. The cyradm(1) tool can be used to adjust ACLs on calendars as needed. The tables below show how the access controls are used by the CalDAV module. cyrus-imapd-2.5.10/compile0000755000175000017500000001624512657715017012356 00000000000000#! /bin/sh # Wrapper for compilers which do not understand '-c -o'. scriptversion=2012-10-14.11; # UTC # Copyright (C) 1999-2014 Free Software Foundation, Inc. # Written by Tom Tromey . # # This program is free software; you can redistribute it and/or modify # it under the terms of the GNU General Public License as published by # the Free Software Foundation; either version 2, or (at your option) # any later version. # # This program is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the # GNU General Public License for more details. # # You should have received a copy of the GNU General Public License # along with this program. If not, see . # As a special exception to the GNU General Public License, if you # distribute this file as part of a program that contains a # configuration script generated by Autoconf, you may include it under # the same distribution terms that you use for the rest of that program. # This file is maintained in Automake, please report # bugs to or send patches to # . nl=' ' # We need space, tab and new line, in precisely that order. Quoting is # there to prevent tools from complaining about whitespace usage. IFS=" "" $nl" file_conv= # func_file_conv build_file lazy # Convert a $build file to $host form and store it in $file # Currently only supports Windows hosts. If the determined conversion # type is listed in (the comma separated) LAZY, no conversion will # take place. func_file_conv () { file=$1 case $file in / | /[!/]*) # absolute file, and not a UNC file if test -z "$file_conv"; then # lazily determine how to convert abs files case `uname -s` in MINGW*) file_conv=mingw ;; CYGWIN*) file_conv=cygwin ;; *) file_conv=wine ;; esac fi case $file_conv/,$2, in *,$file_conv,*) ;; mingw/*) file=`cmd //C echo "$file " | sed -e 's/"\(.*\) " *$/\1/'` ;; cygwin/*) file=`cygpath -m "$file" || echo "$file"` ;; wine/*) file=`winepath -w "$file" || echo "$file"` ;; esac ;; esac } # func_cl_dashL linkdir # Make cl look for libraries in LINKDIR func_cl_dashL () { func_file_conv "$1" if test -z "$lib_path"; then lib_path=$file else lib_path="$lib_path;$file" fi linker_opts="$linker_opts -LIBPATH:$file" } # func_cl_dashl library # Do a library search-path lookup for cl func_cl_dashl () { lib=$1 found=no save_IFS=$IFS IFS=';' for dir in $lib_path $LIB do IFS=$save_IFS if $shared && test -f "$dir/$lib.dll.lib"; then found=yes lib=$dir/$lib.dll.lib break fi if test -f "$dir/$lib.lib"; then found=yes lib=$dir/$lib.lib break fi if test -f "$dir/lib$lib.a"; then found=yes lib=$dir/lib$lib.a break fi done IFS=$save_IFS if test "$found" != yes; then lib=$lib.lib fi } # func_cl_wrapper cl arg... # Adjust compile command to suit cl func_cl_wrapper () { # Assume a capable shell lib_path= shared=: linker_opts= for arg do if test -n "$eat"; then eat= else case $1 in -o) # configure might choose to run compile as 'compile cc -o foo foo.c'. eat=1 case $2 in *.o | *.[oO][bB][jJ]) func_file_conv "$2" set x "$@" -Fo"$file" shift ;; *) func_file_conv "$2" set x "$@" -Fe"$file" shift ;; esac ;; -I) eat=1 func_file_conv "$2" mingw set x "$@" -I"$file" shift ;; -I*) func_file_conv "${1#-I}" mingw set x "$@" -I"$file" shift ;; -l) eat=1 func_cl_dashl "$2" set x "$@" "$lib" shift ;; -l*) func_cl_dashl "${1#-l}" set x "$@" "$lib" shift ;; -L) eat=1 func_cl_dashL "$2" ;; -L*) func_cl_dashL "${1#-L}" ;; -static) shared=false ;; -Wl,*) arg=${1#-Wl,} save_ifs="$IFS"; IFS=',' for flag in $arg; do IFS="$save_ifs" linker_opts="$linker_opts $flag" done IFS="$save_ifs" ;; -Xlinker) eat=1 linker_opts="$linker_opts $2" ;; -*) set x "$@" "$1" shift ;; *.cc | *.CC | *.cxx | *.CXX | *.[cC]++) func_file_conv "$1" set x "$@" -Tp"$file" shift ;; *.c | *.cpp | *.CPP | *.lib | *.LIB | *.Lib | *.OBJ | *.obj | *.[oO]) func_file_conv "$1" mingw set x "$@" "$file" shift ;; *) set x "$@" "$1" shift ;; esac fi shift done if test -n "$linker_opts"; then linker_opts="-link$linker_opts" fi exec "$@" $linker_opts exit 1 } eat= case $1 in '') echo "$0: No command. Try '$0 --help' for more information." 1>&2 exit 1; ;; -h | --h*) cat <<\EOF Usage: compile [--help] [--version] PROGRAM [ARGS] Wrapper for compilers which do not understand '-c -o'. Remove '-o dest.o' from ARGS, run PROGRAM with the remaining arguments, and rename the output as expected. If you are trying to build a whole package this is not the right script to run: please start by reading the file 'INSTALL'. Report bugs to . EOF exit $? ;; -v | --v*) echo "compile $scriptversion" exit $? ;; cl | *[/\\]cl | cl.exe | *[/\\]cl.exe ) func_cl_wrapper "$@" # Doesn't return... ;; esac ofile= cfile= for arg do if test -n "$eat"; then eat= else case $1 in -o) # configure might choose to run compile as 'compile cc -o foo foo.c'. # So we strip '-o arg' only if arg is an object. eat=1 case $2 in *.o | *.obj) ofile=$2 ;; *) set x "$@" -o "$2" shift ;; esac ;; *.c) cfile=$1 set x "$@" "$1" shift ;; *) set x "$@" "$1" shift ;; esac fi shift done if test -z "$ofile" || test -z "$cfile"; then # If no '-o' option was seen then we might have been invoked from a # pattern rule where we don't need one. That is ok -- this is a # normal compilation that the losing compiler can handle. If no # '.c' file was seen then we are probably linking. That is also # ok. exec "$@" fi # Name of file we expect compiler to create. cofile=`echo "$cfile" | sed 's|^.*[\\/]||; s|^[a-zA-Z]:||; s/\.c$/.o/'` # Create the lock directory. # Note: use '[/\\:.-]' here to ensure that we don't use the same name # that we are using for the .o file. Also, base the name on the expected # object file name, since that is what matters with a parallel build. lockdir=`echo "$cofile" | sed -e 's|[/\\:.-]|_|g'`.d while true; do if mkdir "$lockdir" >/dev/null 2>&1; then break fi sleep 1 done # FIXME: race condition here if user kills between mkdir and trap. trap "rmdir '$lockdir'; exit 1" 1 2 15 # Run the compile. "$@" ret=$? if test -f "$cofile"; then test "$cofile" = "$ofile" || mv "$cofile" "$ofile" elif test -f "${cofile}bj"; then test "${cofile}bj" = "$ofile" || mv "${cofile}bj" "$ofile" fi rmdir "$lockdir" exit $ret # Local Variables: # mode: shell-script # sh-indentation: 2 # eval: (add-hook 'write-file-hooks 'time-stamp) # time-stamp-start: "scriptversion=" # time-stamp-format: "%:y-%02m-%02d.%02H" # time-stamp-time-zone: "UTC" # time-stamp-end: "; # UTC" # End: cyrus-imapd-2.5.10/man/0000755000175000017500000000000013001246664011612 500000000000000cyrus-imapd-2.5.10/man/nntpd.80000644000175000017500000001057213001236020012734 00000000000000.\" -*- nroff -*- .TH NNTPD 8 "Project Cyrus" CMU .\" .\" Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. .\" .\" Redistribution and use in source and binary forms, with or without .\" modification, are permitted provided that the following conditions .\" are met: .\" .\" 1. Redistributions of source code must retain the above copyright .\" notice, this list of conditions and the following disclaimer. .\" .\" 2. Redistributions in binary form must reproduce the above copyright .\" notice, this list of conditions and the following disclaimer in .\" the documentation and/or other materials provided with the .\" distribution. .\" .\" 3. The name "Carnegie Mellon University" must not be used to .\" endorse or promote products derived from this software without .\" prior written permission. For permission or any legal .\" details, please contact .\" Carnegie Mellon University .\" Center for Technology Transfer and Enterprise Creation .\" 4615 Forbes Avenue .\" Suite 302 .\" Pittsburgh, PA 15213 .\" (412) 268-7393, fax: (412) 268-7395 .\" innovation@andrew.cmu.edu .\" .\" 4. Redistributions of any form whatsoever must retain the following .\" acknowledgment: .\" "This product includes software developed by Computing Services .\" at Carnegie Mellon University (http://www.cmu.edu/computing/)." .\" .\" CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO .\" THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY .\" AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE .\" FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES .\" WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN .\" AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING .\" OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. .SH NAME nntpd \- NNTP server process .SH SYNOPSIS .B nntpd [ .B \-C .I config-file ] [ .B \-U .I uses ] [ .B \-T .I timeout ] [ .B \-D ] .br [ .B \-s ] [ .B \-r ] [ .B \-f ] [ .B \-p .I ssf ] .SH DESCRIPTION .I Nntpd is a NNTP server. It accepts commands on its standard input and responds on its standard output. It MUST invoked by .IR master (8) with those descriptors attached to a remote client connection. .PP .I Nntpd reads its configuration options out of the .IR imapd.conf (5) file unless specified otherwise by \fB-C\fR. The optional .I newsprefix option specifies a prefix to be prepended to newsgroup names to make the corresponding IMAP mailbox names. The optional .I newspostuser option specifies the special userid to be used when contructing the To: header address for following up to articles when read via IMAP. The optional .I newspeer option specifies the fully qualified hostname of the upstream news server to which articles are fed. The optional .I allownewnews option enables the NNTP NEWNEWS command. NOTE: For servers with a large volume of articles, the NEWNEWS command can be expensive. .PP If the directory .RI log/ user exists under the directory specified in the .I configdirectory configuration option, then .I nntpd will create protocol telemetry logs for sessions authenticating as .IR user . The telemetry logs will be stored in the .RI log/ user directory with a filename of the .I nntpd process-id. .SH OPTIONS .TP .BI \-C " config-file" Read configuration options from \fIconfig-file\fR. .TP .BI \-U " uses" The maximum number of times that the process should be used for new connections before shutting down. The default is 250. .TP .BI \-T " timeout" The number of seconds that the process will wait for a new connection before shutting down. Note that a value of 0 (zero) will disable the timeout. The default is 60. .TP .BI \-D Run external debugger specified in debug_command. .TP .BI \-s Serve NNTP over SSL (nntps). All data to and from .I nntpd is encrypted using the Secure Sockets Layer. .TP .BI \-r Only allow NNTP reader commands. Permitted clients will only be allowed to read/post articles. .TP .BI \-f Only allow NNTP feeder commands. Permitted clients will only be allowed to feed articles (no reading). .TP .BI \-p " ssf" Tell .I nntpd that an external layer exists. An SSF (security strength factor) of 1 means an integrity protection layer exists. Any higher SSF implies some form of privacy protection. .SH FILES .TP .B /etc/imapd.conf .SH SEE ALSO .PP \fBimapd.conf(5)\fR, \fBmaster(8)\fR cyrus-imapd-2.5.10/man/ctl_cyrusdb.80000644000175000017500000000634113001236020014125 00000000000000.\" -*- nroff -*- .TH CTL_CYRUSDB 8 "Project Cyrus" CMU .\" .\" Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. .\" .\" Redistribution and use in source and binary forms, with or without .\" modification, are permitted provided that the following conditions .\" are met: .\" .\" 1. Redistributions of source code must retain the above copyright .\" notice, this list of conditions and the following disclaimer. .\" .\" 2. Redistributions in binary form must reproduce the above copyright .\" notice, this list of conditions and the following disclaimer in .\" the documentation and/or other materials provided with the .\" distribution. .\" .\" 3. The name "Carnegie Mellon University" must not be used to .\" endorse or promote products derived from this software without .\" prior written permission. For permission or any legal .\" details, please contact .\" Carnegie Mellon University .\" Center for Technology Transfer and Enterprise Creation .\" 4615 Forbes Avenue .\" Suite 302 .\" Pittsburgh, PA 15213 .\" (412) 268-7393, fax: (412) 268-7395 .\" innovation@andrew.cmu.edu .\" .\" 4. Redistributions of any form whatsoever must retain the following .\" acknowledgment: .\" "This product includes software developed by Computing Services .\" at Carnegie Mellon University (http://www.cmu.edu/computing/)." .\" .\" CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO .\" THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY .\" AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE .\" FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES .\" WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN .\" AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING .\" OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. .SH NAME ctl_cyrusdb \- perform operations common to all Cyrus databases .SH SYNOPSIS .B ctl_cyrusdb [ .B \-C .I config-file ] .B \-r [ .B \-x ] .br .B ctl_cyrusdb [ .B \-C .I config-file ] .B \-c .SH DESCRIPTION .I Ctl_cyrusdb is used to perform various administrative operations on the Cyrus databases. .PP .I Ctl_cyrusdb reads its configuration options out of the .IR imapd.conf (5) file unless specified otherwise by \fB-C\fR. The .I configdirectory option is used to determine the default location of the Cyrus databases. .SH OPTIONS .TP .BI \-C " config-file" Read configuration options from \fIconfig-file\fR. .TP .B \-r Recover the databases after an application or system failure. Also performs database cleanup like removing mailbox reservations (and any associated mailbox files). All mailbox files are also checked to make sure the file format matches the configured database type in imapd.conf. If not, the file is automatically converted using the same logic as cvt_cyrusdb. .TP .B \-x Used with -r to recover the database only. (Prevents database cleanup). .TP .B \-c Checkpoint and archive the databases. Changes to the database which are part of committed transactions are written to disk. Also, a \fIhot\fR backup of the databases is made and inactive log files are removed. .SH FILES .TP .B /etc/imapd.conf .SH SEE ALSO .PP \fBimapd.conf(5)\fR, \fBmaster(8)\fR cyrus-imapd-2.5.10/man/pop3test.10000644000175000017500000001170013001236020013355 00000000000000.\" -*- nroff -*- .TH POP3TEST 1 "Project Cyrus" CMU .\" .\" Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. .\" .\" Redistribution and use in source and binary forms, with or without .\" modification, are permitted provided that the following conditions .\" are met: .\" .\" 1. Redistributions of source code must retain the above copyright .\" notice, this list of conditions and the following disclaimer. .\" .\" 2. Redistributions in binary form must reproduce the above copyright .\" notice, this list of conditions and the following disclaimer in .\" the documentation and/or other materials provided with the .\" distribution. .\" .\" 3. The name "Carnegie Mellon University" must not be used to .\" endorse or promote products derived from this software without .\" prior written permission. For permission or any legal .\" details, please contact .\" Carnegie Mellon University .\" Center for Technology Transfer and Enterprise Creation .\" 4615 Forbes Avenue .\" Suite 302 .\" Pittsburgh, PA 15213 .\" (412) 268-7393, fax: (412) 268-7395 .\" innovation@andrew.cmu.edu .\" .\" 4. Redistributions of any form whatsoever must retain the following .\" acknowledgment: .\" "This product includes software developed by Computing Services .\" at Carnegie Mellon University (http://www.cmu.edu/computing/)." .\" .\" CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO .\" THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY .\" AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE .\" FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES .\" WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN .\" AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING .\" OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. .SH NAME pop3test \- interactive POP3 test program .SH SYNOPSIS .B pop3test [ .B \-t .I keyfile ] [ .B \-p .I port ] [ .B \-m .I mechanism ] .br [ .B \-a .I userid ] [ .B \-u .I userid ] [ .B \-k .I num ] [ .B \-l .I num ] .br [ .B \-r .I realm ] [ .B \-f .I file ] [ .B \-n .I num ] [ .B \-s ] [ .B \-c ] .br [ .B \-i ] [ .B \-o \fIoption\fB=\fIvalue\fR ] [ .B \-v ] \fIhostname\fR .SH DESCRIPTION .I pop3test is a utility that allows you to authenticate to a POP3 server and interactively issue commands to it. Once authenticated you may issue any POP3 command by simply typing it in. It is capable of multiple SASL authentication mechanisms and handles encryption layers transparently. This utility is often used for testing the operation of a pop3 server. Also those developing POP3 clients find it useful. .PP .SH OPTIONS .TP .BI \-t " keyfile" Enable TLS. \fIkeyfile\fR contains the TLS public and private keys. Specify \fB""\fR to negotiate a TLS encryption layer but not use TLS authentication. .TP .BI \-p " port" Port to connect to. If left off this defaults to \fBpop3\fR as defined in /etc/services. .TP .BI -m " mechanism" Force pop3test to use \fImechanism\fR for authentication. If not specified the strongest authentication mechanism supported by the server is chosen. Specify \fBuser\fR to use the USER/PASS commands or \fBapop\fR to use the APOP command instead of AUTH. .TP .BI -a " userid" Userid to use for authentication; defaults to the current user. This is the userid whose password or credentials will be presented to the server for verification. .TP .BI -u " userid" Userid to use for authorization; defaults to the current user. This is the userid whose identity will be assumed after authentication. \fBNOTE:\fR This is only used with SASL mechanisms that allow proxying (e.g. PLAIN, DIGEST-MD5). .TP .BI -k " num" Minimum protection layer required. .TP .BI -l " num" Maximum protection layer to use (\fB0\fR=none; \fB1=\fRintegrity; etc). For example if you are using the KERBEROS_V4 authentication mechanism specifying \fB0\fR will force pop3test to not use any layer and specifying \fB1\fR will force it to use the integrity layer. By default the maximum supported protection layer will be used. .TP .BI -r " realm" Specify the \fIrealm\fR to use. Certain authentication mechanisms (e.g. DIGEST-MD5) may require one to specify the realm. .TP .BI -f " file" Pipe \fIfile\fR into connection after authentication. .TP .BI -n " num" Number of authentication attempts; default = 1. The client will attempt to do SSL/TLS session reuse and/or fast reauth (e.g. DIGEST-MD5), if possible. .TP .B -s Enable POP3 over SSL (pop3s). .TP .B -c Enable challenge prompt callbacks. This will cause the OTP mechanism to ask for the the one-time password instead of the secret pass-phrase (library generates the correct response). .TP .B -i Don't send an initial client response for SASL mechanisms, even if the protocol supports it. .TP \fB-o \fIoption\fB=\fIvalue\fR Set the SASL \fIoption\fR to \fIvalue\fR. .TP .B -v Verbose. Print out more information than usual. .SH SEE ALSO .PP \fBpop3d(8)\fR cyrus-imapd-2.5.10/man/deliver.80000644000175000017500000001012313001236020013233 00000000000000.\" -*- nroff -*- .TH DELIVER 8 "Project Cyrus" CMU .\" .\" Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. .\" .\" Redistribution and use in source and binary forms, with or without .\" modification, are permitted provided that the following conditions .\" are met: .\" .\" 1. Redistributions of source code must retain the above copyright .\" notice, this list of conditions and the following disclaimer. .\" .\" 2. Redistributions in binary form must reproduce the above copyright .\" notice, this list of conditions and the following disclaimer in .\" the documentation and/or other materials provided with the .\" distribution. .\" .\" 3. The name "Carnegie Mellon University" must not be used to .\" endorse or promote products derived from this software without .\" prior written permission. For permission or any legal .\" details, please contact .\" Carnegie Mellon University .\" Center for Technology Transfer and Enterprise Creation .\" 4615 Forbes Avenue .\" Suite 302 .\" Pittsburgh, PA 15213 .\" (412) 268-7393, fax: (412) 268-7395 .\" innovation@andrew.cmu.edu .\" .\" 4. Redistributions of any form whatsoever must retain the following .\" acknowledgment: .\" "This product includes software developed by Computing Services .\" at Carnegie Mellon University (http://www.cmu.edu/computing/)." .\" .\" CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO .\" THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY .\" AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE .\" FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES .\" WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN .\" AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING .\" OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. .SH NAME deliver \- deliver mail to an IMAP mailbox .SH SYNOPSIS .B deliver [ .B \-C .I config-file ] [ .B \-d ] [ .B \-r .I address ] .br [ .B \-f .I address ] [ .B \-m .I mailbox ] [ .B \-a .I auth-id ] .br [ .B \-q ] [ .I userid ]... .br .B deliver [ .B \-C .I config-file ] .B \-l .SH DESCRIPTION .I Deliver reads a message from the standard input and delivers it to one or more IMAP mailboxes. .PP .I Deliver reads its configuration options out of the .IR imapd.conf (5) file unless specified otherwise by \fB-C\fR. .SH OPTIONS .TP .BI \-C " config-file" Read configuration options from \fIconfig-file\fR. .TP .B \-d Ignored for compatability with .B /bin/mail. .TP .BI \-r " address" Insert a .B Return-Path: header containing .I address .TP .BI \-f " address" Insert a .B Return-Path: header containing .I address .TP .BI \-m " mailbox" Deliver to .IR mailbox . If any .IR userid s are specified, attempts to deliver to .RI user. userid . mailbox for each .IR userid . If the ACL on any such mailbox does not grant the sender the "p" right or if .B \-m is not specified, then delivers to the INBOX for the .IR userid , regardless of the ACL on the INBOX. .IP If no .IR userid s are specified, attempts to deliver to .IR mailbox . If the ACL on .I mailbox does not grant the sender the "p" right, the delivery fails. .TP .BI \-a " auth-id" Specify the authorization id of the sender. Defaults to "anonymous". .TP .B \-q Deliver message even when receiving mailbox is over quota. .TP .B \-l Accept messages using the LMTP protocol. .SH NOTES Depending on the setting of \fBreject8bit\fR in \fBimapd.conf(5)\fR, deliver either rejects/accepts messages with 8-bit-set characters in the headers. If we accept messages with 8-bit-set characters in the headers, then depending on the setting of \fBmunge8bit\fR, these characters are either left un-touched or changed to `X'. This is because such characters can't be interpreted since the character set is not known, although some communities not well-served by US-ASCII assume that those characters can be used to represent characters not present in US-ASCII. .PP A method for encoding 8-bit-set characters is provided by RFC 2047. .SH FILES .TP .B /etc/imapd.conf .SH SEE ALSO .PP \fBlmtpd(8)\fR cyrus-imapd-2.5.10/man/mbexamine.80000644000175000017500000000573613001236020013564 00000000000000.\" -*- nroff -*- .TH MBEXAMINE 8 "Project Cyrus" CMU .\" .\" Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. .\" .\" Redistribution and use in source and binary forms, with or without .\" modification, are permitted provided that the following conditions .\" are met: .\" .\" 1. Redistributions of source code must retain the above copyright .\" notice, this list of conditions and the following disclaimer. .\" .\" 2. Redistributions in binary form must reproduce the above copyright .\" notice, this list of conditions and the following disclaimer in .\" the documentation and/or other materials provided with the .\" distribution. .\" .\" 3. The name "Carnegie Mellon University" must not be used to .\" endorse or promote products derived from this software without .\" prior written permission. For permission or any legal .\" details, please contact .\" Carnegie Mellon University .\" Center for Technology Transfer and Enterprise Creation .\" 4615 Forbes Avenue .\" Suite 302 .\" Pittsburgh, PA 15213 .\" (412) 268-7393, fax: (412) 268-7395 .\" innovation@andrew.cmu.edu .\" .\" 4. Redistributions of any form whatsoever must retain the following .\" acknowledgment: .\" "This product includes software developed by Computing Services .\" at Carnegie Mellon University (http://www.cmu.edu/computing/)." .\" .\" CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO .\" THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY .\" AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE .\" FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES .\" WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN .\" AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING .\" OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. .SH NAME mbexamine \- examine a cyrus-format mailbox .SH SYNOPSIS .B mbexamine [ .B \-C .I config-file ] [ .B \-u uid ] .IR mailbox ... .br .B mbexamine [ .B \-C .I config-file ] [ .B \-s seqnum ] .IR mailbox ... .br .B mbexamine [ .B \-C .I config-file ] .B \-q .IR mailbox ... .br .SH DESCRIPTION .I Mbexamine will examine the header, index, and cache files of a cyrus format mailbox and dump the information contained therein. It can also limit its output to a specific uid or sequence number, through use of the -s and -u switches. .I Mbexamine reads its configuration options out of the .IR imapd.conf (5) file unless specified otherwise by \fB-C\fR. It uses the mboxlist database to locate the mailbox on disk. .SH OPTIONS .TP .BI \-C " config-file" Read configuration options from \fIconfig-file\fR. .TP .B \-s Dump information for the given sequence number only. .TP .B \-u Dump information for the given uid only. .TP .B \-q Compare the quota usage in cyrus.index to the actual message file sizes and report any differences. If there are differences, the mailbox SHOULD be reconstructed. .SH FILES .B /etc/imapd.conf cyrus-imapd-2.5.10/man/pop3d.80000644000175000017500000000720113001236020012631 00000000000000.\" -*- nroff -*- .TH POP3D 8 "Project Cyrus" CMU .\" .\" Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. .\" .\" Redistribution and use in source and binary forms, with or without .\" modification, are permitted provided that the following conditions .\" are met: .\" .\" 1. Redistributions of source code must retain the above copyright .\" notice, this list of conditions and the following disclaimer. .\" .\" 2. Redistributions in binary form must reproduce the above copyright .\" notice, this list of conditions and the following disclaimer in .\" the documentation and/or other materials provided with the .\" distribution. .\" .\" 3. The name "Carnegie Mellon University" must not be used to .\" endorse or promote products derived from this software without .\" prior written permission. For permission or any legal .\" details, please contact .\" Carnegie Mellon University .\" Center for Technology Transfer and Enterprise Creation .\" 4615 Forbes Avenue .\" Suite 302 .\" Pittsburgh, PA 15213 .\" (412) 268-7393, fax: (412) 268-7395 .\" innovation@andrew.cmu.edu .\" .\" 4. Redistributions of any form whatsoever must retain the following .\" acknowledgment: .\" "This product includes software developed by Computing Services .\" at Carnegie Mellon University (http://www.cmu.edu/computing/)." .\" .\" CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO .\" THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY .\" AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE .\" FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES .\" WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN .\" AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING .\" OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. .SH NAME pop3d \- POP3 server process .SH SYNOPSIS .B pop3d [ .B \-C .I config-file ] [ .B \-U .I uses ] [ .B \-T .I timeout ] [ .B \-D ] .br [ .B \-s ] [ .B \-k ] [ .B \-p .I ssf ] .SH DESCRIPTION .I Pop3d is a POP3 server. It accepts commands on its standard input and responds on its standard output. It MUST invoked by .IR master (8) with those descriptors attached to a remote client connection. .PP .I Pop3d reads its configuration options out of the .IR imapd.conf (5) file unless specified otherwise by \fB-C\fR. .PP If the directory .RI log/ user exists under the directory specified in the .I configdirectory configuration option, then .I pop3d will create protocol telemetry logs for sessions authenticating as .IR user . The telemetry logs will be stored in the .RI log/ user directory with a filename of the .I pop3d process-id. .SH OPTIONS .TP .BI \-C " config-file" Read configuration options from \fIconfig-file\fR. .TP .BI \-U " uses" The maximum number of times that the process should be used for new connections before shutting down. The default is 250. .TP .BI \-T " timeout" The number of seconds that the process will wait for a new connection before shutting down. Note that a value of 0 (zero) will disable the timeout. The default is 60. .TP .BI \-D Run external debugger specified in debug_command. .TP .BI \-s Serve POP3 over SSL (pop3s). All data to and from .I pop3d is encrypted using the Secure Sockets Layer. .TP .B \-k Serve MIT's KPOP (Kerberized POP) protocol instead. .TP .BI \-p " ssf" Tell .I pop3d that an external layer exists. An SSF (security strength factor) of 1 means an integrity protection layer exists. Any higher SSF implies some form of privacy protection. .SH FILES .TP .B /etc/imapd.conf .SH SEE ALSO .PP \fBimapd.conf(5)\fR, \fBmaster(8)\fR cyrus-imapd-2.5.10/man/arbitron.80000644000175000017500000001024513001236020013426 00000000000000.\" -*- nroff -*- .TH ARBITRON 8 "Project Cyrus" CMU .\" .\" Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. .\" .\" Redistribution and use in source and binary forms, with or without .\" modification, are permitted provided that the following conditions .\" are met: .\" .\" 1. Redistributions of source code must retain the above copyright .\" notice, this list of conditions and the following disclaimer. .\" .\" 2. Redistributions in binary form must reproduce the above copyright .\" notice, this list of conditions and the following disclaimer in .\" the documentation and/or other materials provided with the .\" distribution. .\" .\" 3. The name "Carnegie Mellon University" must not be used to .\" endorse or promote products derived from this software without .\" prior written permission. For permission or any legal .\" details, please contact .\" Carnegie Mellon University .\" Center for Technology Transfer and Enterprise Creation .\" 4615 Forbes Avenue .\" Suite 302 .\" Pittsburgh, PA 15213 .\" (412) 268-7393, fax: (412) 268-7395 .\" innovation@andrew.cmu.edu .\" .\" 4. Redistributions of any form whatsoever must retain the following .\" acknowledgment: .\" "This product includes software developed by Computing Services .\" at Carnegie Mellon University (http://www.cmu.edu/computing/)." .\" .\" CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO .\" THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY .\" AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE .\" FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES .\" WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN .\" AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING .\" OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. .SH NAME arbitron \- arbitron mailboxes .SH SYNOPSIS .B arbitron [ .B \-C .I config-file ] [ .B \-o ] [ .B \-u ] [ .B \-l ] [ .B \-p .I months ] .br [ .B \-d .I days | .B \-D \fImmddyyyy\fR[\fB:\fImmddyyyy\fR] ] \fImailbox\fR... .SH DESCRIPTION .I Arbitron collects and reports readership statistics for mailboxes on the server. It also optionally prunes the mailboxes of \\Seen state for dormant users. .PP .I Arbitron produces one line of output per mailbox, reporting the mailbox name followed by a space, followed by the number of readers (and if -u is specified, followed by a colon and a comma-separated list of the readers userids), and if -o is not specified, another space and the number of subscribers (and if -u is specified, followed by a colon and a comma-separated list of the subscribers userids). \fBIMPORTANT: This format is subject to change in future versions.\fR .PP Each "reader" is a distinct authentication identity which has "s" rights to the mailbox and which has SELECTed the mailbox within either the past .I days days or the specified date range. Users are not counted as reading their own personal mailboxes. Personal mailboxes are not reported unless there is at least one reader other than the mailboxes owner. .PP .I Arbitron reads its configuration options out of the .IR imapd.conf (5) file unless specified otherwise by \fB-C\fR. .SH OPTIONS .TP .BI \-C " config-file" Read configuration options from \fIconfig-file\fR. .TP .BI \-o "old way" -- do not report subscribers. .TP .BI \-u Report userids in addition to the count(s). .TP .BI \-l Enable long reporting (comma delimited table consisting of mbox, userid, r/s, start time, end time). .TP .BI "\-d " days Count as a reader an authentication identity which has SELECTed the mailbox within .I days days. Default is 30. .TP \fB\-D\fR \fImmddyyyy\fR[\fB:\fImmddyyyy\fR] Count as a reader an authentication identity which has SELECTed the mailbox within the given date range. The start date and optional end date are specified as 2-digit month of the year, 2-digit day of the month, and 4-digit year. If the end date is not specified, then the current system time is used as the end time. .TP .BI "\-p " months Prune \\Seen state for users who have not SELECTed the mailbox within .I months months. Default is infinity. .SH FILES .TP .B /etc/imapd.conf cyrus-imapd-2.5.10/man/ctl_zoneinfo.80000644000175000017500000000570513001236020014304 00000000000000.\" -*- nroff -*- .TH CTL_ZONEINFO 8 "Project Cyrus" CMU .\" .\" Copyright (c) 1994-2013 Carnegie Mellon University. All rights reserved. .\" .\" Redistribution and use in source and binary forms, with or without .\" modification, are permitted provided that the following conditions .\" are met: .\" .\" 1. Redistributions of source code must retain the above copyright .\" notice, this list of conditions and the following disclaimer. .\" .\" 2. Redistributions in binary form must reproduce the above copyright .\" notice, this list of conditions and the following disclaimer in .\" the documentation and/or other materials provided with the .\" distribution. .\" .\" 3. The name "Carnegie Mellon University" must not be used to .\" endorse or promote products derived from this software without .\" prior written permission. For permission or any legal .\" details, please contact .\" Carnegie Mellon University .\" Center for Technology Transfer and Enterprise Creation .\" 4615 Forbes Avenue .\" Suite 302 .\" Pittsburgh, PA 15213 .\" (412) 268-7393, fax: (412) 268-7395 .\" innovation@andrew.cmu.edu * .\" 4. Redistributions of any form whatsoever must retain the following .\" acknowledgment: .\" "This product includes software developed by Computing Services .\" at Carnegie Mellon University (http://www.cmu.edu/computing/)." .\" .\" CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO .\" THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY .\" AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE .\" FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES .\" WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN .\" AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING .\" OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. .\" .SH NAME ctl_zoneinfo \- perform operations on the zoneinfo database .SH SYNOPSIS .B ctl_zoneinfo [ .B \-C .I config-file ] [ .B \-v ] .B \-r .I version-string .SH DESCRIPTION .I Ctl_zoneinfo is used to perform various administrative operations on the zoneinfo database. .PP .I Ctl_zoneinfo reads its configuration options out of the .IR imapd.conf (5) file unless specified otherwise by \fB-C\fR. .SH OPTIONS .TP .BI \-C " config-file" Read configuration options from \fIconfig-file\fR. .TP .B \-v Enable verbose output. .TP .BI \-r " version-string" Rebuild the zoneinfo database based on the directory structure of \fIconfigdirectory\fB/zoneinfo\fR. The database to be rebuilt will be in the default location of \fIconfigdirectory\fB/zoneinfo.db\fR unless otherwise specified by the \fIzoneinfo_db_path\fR option in \fBimapd.conf\fR. The \fIversion-string\fR should describe the source of the timezone data (e.g. "Olson 2013h") and will be used by the \fItimezone\fR module of \fBhttpd\fR. .SH FILES .TP .B /etc/imapd.conf .SH SEE ALSO .PP \fBimapd.conf(5)\fR, \fBmaster(8)\fR, \fBhttpd(8)\fR cyrus-imapd-2.5.10/man/fud.80000644000175000017500000000726513001236020012374 00000000000000.\" -*- nroff -*- .TH FUD 8 "Project Cyrus" CMU .\" .\" Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. .\" .\" Redistribution and use in source and binary forms, with or without .\" modification, are permitted provided that the following conditions .\" are met: .\" .\" 1. Redistributions of source code must retain the above copyright .\" notice, this list of conditions and the following disclaimer. .\" .\" 2. Redistributions in binary form must reproduce the above copyright .\" notice, this list of conditions and the following disclaimer in .\" the documentation and/or other materials provided with the .\" distribution. .\" .\" 3. The name "Carnegie Mellon University" must not be used to .\" endorse or promote products derived from this software without .\" prior written permission. For permission or any legal .\" details, please contact .\" Carnegie Mellon University .\" Center for Technology Transfer and Enterprise Creation .\" 4615 Forbes Avenue .\" Suite 302 .\" Pittsburgh, PA 15213 .\" (412) 268-7393, fax: (412) 268-7395 .\" innovation@andrew.cmu.edu .\" .\" 4. Redistributions of any form whatsoever must retain the following .\" acknowledgment: .\" "This product includes software developed by Computing Services .\" at Carnegie Mellon University (http://www.cmu.edu/computing/)." .\" .\" CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO .\" THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY .\" AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE .\" FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES .\" WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN .\" AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING .\" OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. .SH NAME FUD \- provide information about user mailboxes .SH SYNOPSIS .B fud [ .B \-C .I config-file ] [ .B \-U .I uses ] [ .B \-T .I timeout ] [ .B \-D ] .SH DESCRIPTION .B FUD is a long lived datagram daemon started from master that provides information about when a user last read their mail, when mail last arrived in a user's mailbox, and how many messages are recent for that user. .PP Note that for .B FUD to run properly you must set proto=udp in its cyrus.conf services entry. prefork=1 is also recommended. .B FUD will automatically proxy any and all FUD requests to the appropriate backend server if it is runing on a Cyrus Murder frontend machine. .PP .B FUD reads its configuration options out of the .IR imapd.conf (5) file unless specified otherwise by \fB-C\fR. .SH OPTIONS .TP .BI \-C " config-file" Read configuration options from \fIconfig-file\fR. .TP .BI \-U " uses" The maximum number of times that the process should be used for new connections before shutting down. The default is 250. .TP .BI \-T " timeout" The number of seconds that the process will wait for a new connection before shutting down. Note that a value of 0 (zero) will disable the timeout. The default is 60. .TP .BI \-D Run external debugger specified in debug_command. .SH FILES .TP .B /etc/imapd.conf Default configuration file. .TP .B /etc/cyrus.conf Cyrus Master process configuration file. .SH BUGS Though not really a bug, .B FUD will silently ignore any requests that it does not consider valid. .PP Also not really a bug, .B FUD requires that the anonymous user has the 0 (zero) right on the mailbox in question. This is only a "bug" because 0 is not a standard IMAP ACL bit. .PP .B FUD is an experimental interface meant to provide information to build a finger-like service around. Eventually it should be superceded by a more standards-based protocol. cyrus-imapd-2.5.10/man/nntptest.10000644000175000017500000001165513001236020013464 00000000000000.\" -*- nroff -*- .TH NNTPTEST 1 "Project Cyrus" CMU .\" .\" Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. .\" .\" Redistribution and use in source and binary forms, with or without .\" modification, are permitted provided that the following conditions .\" are met: .\" .\" 1. Redistributions of source code must retain the above copyright .\" notice, this list of conditions and the following disclaimer. .\" .\" 2. Redistributions in binary form must reproduce the above copyright .\" notice, this list of conditions and the following disclaimer in .\" the documentation and/or other materials provided with the .\" distribution. .\" .\" 3. The name "Carnegie Mellon University" must not be used to .\" endorse or promote products derived from this software without .\" prior written permission. For permission or any legal .\" details, please contact .\" Carnegie Mellon University .\" Center for Technology Transfer and Enterprise Creation .\" 4615 Forbes Avenue .\" Suite 302 .\" Pittsburgh, PA 15213 .\" (412) 268-7393, fax: (412) 268-7395 .\" innovation@andrew.cmu.edu .\" .\" 4. Redistributions of any form whatsoever must retain the following .\" acknowledgment: .\" "This product includes software developed by Computing Services .\" at Carnegie Mellon University (http://www.cmu.edu/computing/)." .\" .\" CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO .\" THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY .\" AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE .\" FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES .\" WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN .\" AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING .\" OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. .SH NAME nntptest \- interactive NNTP test program .SH SYNOPSIS .B nntptest [ .B \-t .I keyfile ] [ .B \-p .I port ] [ .B \-m .I mechanism ] .br [ .B \-a .I userid ] [ .B \-u .I userid ] [ .B \-k .I num ] [ .B \-l .I num ] .br [ .B \-r .I realm ] [ .B \-f .I file ] [ .B \-n .I num ] [ .B \-s ] [ .B \-c ] .br [ .B \-i ] [ .B \-o \fIoption\fB=\fIvalue\fR ] [ .B \-v ] \fIhostname\fR .SH DESCRIPTION .I nntptest is a utility that allows you to authenticate to a NNTP server and interactively issue commands to it. Once authenticated you may issue any NNTP command by simply typing it in. It is capable of multiple SASL authentication mechanisms and handles encryption layers transparently. This utility is often used for testing the operation of a nntp server. Also those developing NNTP clients find it useful. .PP .SH OPTIONS .TP .BI \-t " keyfile" Enable TLS. \fIkeyfile\fR contains the TLS public and private keys. Specify \fB""\fR to negotiate a TLS encryption layer but not use TLS authentication. .TP .BI \-p " port" Port to connect to. If left off this defaults to \fBnntp\fR as defined in /etc/services. .TP .BI -m " mechanism" Force nntptest to use \fImechanism\fR for authentication. If not specified the strongest authentication mechanism supported by the server is chosen. Specify \fBuser\fR to use the AUTHINFO USER/PASS commands instead of AUTHINFO SASL. .TP .BI -a " userid" Userid to use for authentication; defaults to the current user. This is the userid whose password or credentials will be presented to the server for verification. .TP .BI -u " userid" Userid to use for authorization; defaults to the current user. This is the userid whose identity will be assumed after authentication. \fBNOTE:\fR This is only used with SASL mechanisms that allow proxying (e.g. PLAIN, DIGEST-MD5). .TP .BI -k " num" Minimum protection layer required. .TP .BI -l " num" Maximum protection layer to use (\fB0\fR=none; \fB1=\fRintegrity; etc). For example if you are using the KERBEROS_V4 authentication mechanism specifying \fB0\fR will force nntptest to not use any layer and specifying \fB1\fR will force it to use the integrity layer. By default the maximum supported protection layer will be used. .TP .BI -r " realm" Specify the \fIrealm\fR to use. Certain authentication mechanisms (e.g. DIGEST-MD5) may require one to specify the realm. .TP .BI -f " file" Pipe \fIfile\fR into connection after authentication. .TP .BI -n " num" Number of authentication attempts; default = 1. The client will attempt to do SSL/TLS session reuse and/or fast reauth (e.g. DIGEST-MD5), if possible. .TP .B -s Enable NNTP over SSL (nntps). .TP .B -c Enable challenge prompt callbacks. This will cause the OTP mechanism to ask for the the one-time password instead of the secret pass-phrase (library generates the correct response). .TP .B -i Don't send an initial client response for SASL mechanisms, even if the protocol supports it. .TP \fB-o \fIoption\fB=\fIvalue\fR Set the SASL \fIoption\fR to \fIvalue\fR. .TP .B -v Verbose. Print out more information than usual. .SH SEE ALSO .PP \fBnntpd(8)\fR cyrus-imapd-2.5.10/man/cvt_cyrusdb.80000644000175000017500000000531713001236020014141 00000000000000.\" -*- nroff -*- .TH CVT_CYRUSDB 8 "Project Cyrus" CMU .\" .\" Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. .\" .\" Redistribution and use in source and binary forms, with or without .\" modification, are permitted provided that the following conditions .\" are met: .\" .\" 1. Redistributions of source code must retain the above copyright .\" notice, this list of conditions and the following disclaimer. .\" .\" 2. Redistributions in binary form must reproduce the above copyright .\" notice, this list of conditions and the following disclaimer in .\" the documentation and/or other materials provided with the .\" distribution. .\" .\" 3. The name "Carnegie Mellon University" must not be used to .\" endorse or promote products derived from this software without .\" prior written permission. For permission or any legal .\" details, please contact .\" Carnegie Mellon University .\" Center for Technology Transfer and Enterprise Creation .\" 4615 Forbes Avenue .\" Suite 302 .\" Pittsburgh, PA 15213 .\" (412) 268-7393, fax: (412) 268-7395 .\" innovation@andrew.cmu.edu .\" .\" 4. Redistributions of any form whatsoever must retain the following .\" acknowledgment: .\" "This product includes software developed by Computing Services .\" at Carnegie Mellon University (http://www.cmu.edu/computing/)." .\" .\" CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO .\" THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY .\" AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE .\" FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES .\" WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN .\" AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING .\" OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. .SH NAME cvt_cyrusdb \- convert a database file between cyrus database formats .SH SYNOPSIS .B cvt_cyrusdb [ .B \-C .I config-file ] .SH DESCRIPTION .I cvt_cyrusdb is used to convert a cyrusdb file between different database backends. Note that you should not attempt to use the same file for input and output. .PP Running without any options will list the available database backends. .PP .I cvt_cyrusdb reads any applicable configuration options out of the .IR imapd.conf (5) file unless specified otherwise by \fB-C\fR. note that the file locations are NOT read out of the configuration file, and must be supplied on the command line. .SH OPTIONS .TP .BI \-C " config-file" Read configuration options from \fIconfig-file\fR. .SH FILES .TP .B /etc/imapd.conf .SH SEE ALSO .PP \fBimapd.conf(5)\fR cyrus-imapd-2.5.10/man/imtest.10000644000175000017500000001253513001236020013110 00000000000000.\" -*- nroff -*- .TH IMTEST 1 "Project Cyrus" CMU .\" .\" Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. .\" .\" Redistribution and use in source and binary forms, with or without .\" modification, are permitted provided that the following conditions .\" are met: .\" .\" 1. Redistributions of source code must retain the above copyright .\" notice, this list of conditions and the following disclaimer. .\" .\" 2. Redistributions in binary form must reproduce the above copyright .\" notice, this list of conditions and the following disclaimer in .\" the documentation and/or other materials provided with the .\" distribution. .\" .\" 3. The name "Carnegie Mellon University" must not be used to .\" endorse or promote products derived from this software without .\" prior written permission. For permission or any legal .\" details, please contact .\" Carnegie Mellon University .\" Center for Technology Transfer and Enterprise Creation .\" 4615 Forbes Avenue .\" Suite 302 .\" Pittsburgh, PA 15213 .\" (412) 268-7393, fax: (412) 268-7395 .\" innovation@andrew.cmu.edu .\" .\" 4. Redistributions of any form whatsoever must retain the following .\" acknowledgment: .\" "This product includes software developed by Computing Services .\" at Carnegie Mellon University (http://www.cmu.edu/computing/)." .\" .\" CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO .\" THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY .\" AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE .\" FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES .\" WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN .\" AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING .\" OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. .SH NAME imtest \- interactive IMAP test program .SH SYNOPSIS .B imtest [ .B \-t .I keyfile ] [ .B \-p .I port ] [ .B \-m .I mechanism ] .br [ .B \-a .I userid ] [ .B \-u .I userid ] [ .B \-k .I num ] [ .B \-l .I num ] .br [ .B \-r .I realm ] [ .B \-f .I file ] [ .B \-n .I num ] [ .B \-s ] [ .B \-q ] .br [ .B \-c ] [ .B \-i ] [ .B \-z ] [ .B \-v ] [ .B \-I .I file ] [ .B \-x .I file ] .br [ .B \-X .I file ] [ .B \-o \fIoption\fB=\fIvalue\fR ] \fIhostname\fR .SH DESCRIPTION .I imtest is a utility that allows you to authenticate to a IMAP or IMSP server and interactively issue commands to it. Once authenticated you may issue any IMAP or IMSP command by simply typing it in. It is capable of multiple SASL authentication mechanisms and handles encryption layers transparently. This utility is often used for testing the operation of a imsp or imap server. Also those developing IMAP clients find it useful. .PP .SH OPTIONS .TP .BI \-t " keyfile" Enable TLS. \fIkeyfile\fR contains the TLS public and private keys. Specify \fB""\fR to negotiate a TLS encryption layer but not use TLS authentication. .TP .BI \-p " port" Port to connect to. If left off this defaults to \fBimap\fR as defined in /etc/services. .TP .BI -m " mechanism" Force imtest to use \fImechanism\fR for authentication. If not specified the strongest authentication mechanism supported by the server is chosen. Specify \fBlogin\fR to use the LOGIN command instead of AUTHENTICATE. .TP .BI -a " userid" Userid to use for authentication; defaults to the current user. This is the userid whose password or credentials will be presented to the server for verification. .TP .BI -u " userid" Userid to use for authorization; defaults to the current user. This is the userid whose identity will be assumed after authentication. \fBNOTE:\fR This is only used with SASL mechanisms that allow proxying (e.g. PLAIN, DIGEST-MD5). .TP .BI -k " num" Minimum protection layer required. .TP .BI -l " num" Maximum protection layer to use (\fB0\fR=none; \fB1=\fRintegrity; etc). For example if you are using the KERBEROS_V4 authentication mechanism specifying \fB0\fR will force imtest to not use any layer and specifying \fB1\fR will force it to use the integrity layer. By default the maximum supported protection layer will be used. .TP .BI -r " realm" Specify the \fIrealm\fR to use. Certain authentication mechanisms (e.g. DIGEST-MD5) may require one to specify the realm. .TP .BI -f " file" Pipe \fIfile\fR into connection after authentication. .TP .BI -n " num" Number of authentication attempts; default = 1. The client will attempt to do SSL/TLS session reuse and/or fast reauth (e.g. DIGEST-MD5), if possible. .TP .B -s Enable IMAP over SSL (imaps). .TP .B -q Enable IMAP COMPRESSion (before the last authentication attempt). .TP .B -c Enable challenge prompt callbacks. This will cause the OTP mechanism to ask for the the one-time password instead of the secret pass-phrase (library generates the correct response). .TP .B -i Don't send an initial client response for SASL mechanisms, even if the protocol supports it. .TP .BI -I " file" Echo the PID of the running process into .I file (This can be useful with -X). .TP .BI -x " file" Open the named socket for the interactive portion .TP .BI -X " file" Like -x, only close all file descriptors & daemonize the process. .TP \fB-o \fIoption\fB=\fIvalue\fR Set the SASL \fIoption\fR to \fIvalue\fR. .TP .B -v Verbose. Print out more information than usual. .TP .B -z Timing test. .SH SEE ALSO .PP \fBimapd(8)\fR cyrus-imapd-2.5.10/man/imclient.30000644000175000017500000002561613001236020013415 00000000000000.TH IMCLIENT 3 "Project Cyrus" CMU .\" .\" Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. .\" .\" Redistribution and use in source and binary forms, with or without .\" modification, are permitted provided that the following conditions .\" are met: .\" .\" 1. Redistributions of source code must retain the above copyright .\" notice, this list of conditions and the following disclaimer. .\" .\" 2. Redistributions in binary form must reproduce the above copyright .\" notice, this list of conditions and the following disclaimer in .\" the documentation and/or other materials provided with the .\" distribution. .\" .\" 3. The name "Carnegie Mellon University" must not be used to .\" endorse or promote products derived from this software without .\" prior written permission. For permission or any legal .\" details, please contact .\" Carnegie Mellon University .\" Center for Technology Transfer and Enterprise Creation .\" 4615 Forbes Avenue .\" Suite 302 .\" Pittsburgh, PA 15213 .\" (412) 268-7393, fax: (412) 268-7395 .\" innovation@andrew.cmu.edu .\" .\" 4. Redistributions of any form whatsoever must retain the following .\" acknowledgment: .\" "This product includes software developed by Computing Services .\" at Carnegie Mellon University (http://www.cmu.edu/computing/)." .\" .\" CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO .\" THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY .\" AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE .\" FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES .\" WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN .\" AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING .\" OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. .SH NAME imclient \- (library) authenticating callback interface to IMAP/IMSP servers .SH SYNOPSIS .ad l .ft B #include .sp .ft .if .LP .ft B .BI "int imclient_connect(struct imclient **" imclient ", const char *" host ", const char *" port ");" .PP .BI "void imclient_close (struct imclient *" imclient ");" .sp .025i .BI "void imclient_setflags(struct imclient *" imclient ", int" flags ");" .sp .025i .BI "void imclient_clearflags (struct imclient *" imclient ", int" flags ");" .sp .025i .BI "char* imclient_servername (struct imclient *" imclient ");" .sp .025i .B "void imclient_addcallback (struct imclient *" imclient ",...);" .sp .025i .BI "void imclient_send (struct imclient *" imclient ", void (*" finishproc ")(), void *" finishrock ", const char *" fmt ", ...);" .sp .025i .BI "void imclient_getselectinfo (struct imclient *" imclient ", int *" fd ", int * " wanttowrite ");" .sp .025i .BI "void imclient_processoneevent (struct imclient *" imclient ");" .sp .025i .BI "int imclient_authenticate (struct imclient *" imclient ", struct sasl_client **" availmech ", const char *" service ", const char *" user ", int " protallowed ");" .sp .025i .BI "int imclient_havetls ();" .sp .025i .BI "int imclient_starttls (struct imclient *" imclient ", char *" cert_file ", char *" key_file ", char *" CAfile ", char *" CApath ");" .SH DESCRIPTION The imclient library functions are distributed with Cyrus IMAP and IMSP. These functions are used for building IMAP/IMSP client software. These functions handle Kerberos authentication and can set callbacks based on the keyword in untagged replies or based on the command tag at the end of command replies. Users must link with the -lcyrus switch, and must supply a function called .I fatal to be called in case of any error within .I libcyrus.la. .PP All of the .B imclient functions begin with the prefix .I imclient and takes an argument of type .B struct imclient * as the first argument which is initialized by .B imclient_connect and freed by .B imclient_close. See below for a description of each function. .IP \fB\imclient_connect() \fP5 Connects the client server to the host. If successful, it returns 0 and sets the imclient argument to a pointer to an .B imclient struct. The .B imclient struct represents the current connection, flags, and callbacks. On failure, the current .B errno is returned if a system call failed, -1 is returned if the host name was not found, and -2 is returned if the service name was not found. .IP \fB\imclient_close() \fP5 Closes and frees the .B imclient connection. .IP \fB\ imclient_setflags() \fP5 Sets the flags specified by the .B flags argument on the .B imclient connection. Currently the only flag allowed is .B IMCLIENT_CONN_NONSYNCLITERAL (this flag indicates that the server supports non-synchronizing literals described by the LITERAL+ extension). .IP \fB\imclient_clearflags() \fP5 Clears the flags specified by the .B flags argument on the .B imclient connection. .IP \fB\imclient_servername() \fP5 Returns a char * pointer to the name of the server connected to by .B imclient. .IP \fB\imclient_addcallback() \fP5 Adds an untagged data callback to the .B imclient connection. The function .B imclient_addcallback takes callbacks of the type .B imclient_proc_t which is defined to be: .in 1.5i typedef void imclient_proc_t (struct imclient *imclient, void *rock, struct imclient_reply *reply); .in .sp .025i and .B struct imclient_reply * is defined to be: .sp .025i .in 1.5i struct imclient_reply { .in .in 2i char *keyword; long msgno; char *text; .in .in 1.5i }; .in .sp After the first argument .B imclient, there can be zero or more instances of the set of .B keyword, .B flags, .B proc, and .B rock, each adding or changing a single callback. Each instance adds or changes the callback for .B keyword. The argument, .B flags, specifies information about the parsing of the untagged data. .B proc and .B rock specify the callback function and rock to invoke when the untagged data is received. .B proc may be a null pointer, in which case no function is invoked. The callback function may not call the functions .B imclient_close(), imclient_send(), imclient_eof(), .B imclient_processoneevent(), or .B imclient_authenticate() on the connection. The callback function may over write the text of untagged data. .IP \fB\imclient_send() \fP5 Sends a new command to the .B imclient connection. .B finishproc and .B finnishrock are the function and rock called when the command completes. .B functionproc may be a null pointer, in which case no callback is made. The call back function may not call the functions .B imclient_close(), imclient_send(), imclient_eof(), imclient_processoneevent(), or .B imclient_authenticate() on the connection. The argument, .B fmt , is a print like specification of the command. It must not include the tag as the tag is automatically added by imclient_send(). The defined %-sequences are: .sp .025i .in 1.5i .B %% for % .sp .025i .B %a for an IMAP atom .sp .025i .B %s for an astring (which will be quoted or literalized as needed) .sp .025i .B %d for a decimal .sp .025i .B %u for an unsigned decimal .sp .025i .B %v for #astring (argument is a null-terminated array of .B char * which are written as space separated astrings) .in .IP \fB\imclient_getselectinfo() \fP5 Gets the information for calling .B select(2). .B fd is filled in with the file descriptor to .B select(2) for read. .B wanttowrite is filled in with a nonzero value if select should be used for write as well. .IP \fB\imclient_processoneevent() \fP5 Processes one input or output event on the .B imclient connection. .IP \fB\imclient_authenticate() \fP5 Authenticates the .B imclient connection using one of the mechanisms in .B availmech. The argument, .B user, if not NULL, specifies the user to authenticate as. If the user is NULL, the current user is used. The argument .B protallowed is a bitmask of permissible protection mechanisms. .sp .025i On success, 0 is returned. On failure (i.e., "BAD" keyboard, or no authentication mechanisms worked), 1 is returned. On extreme failure (premature "OK"), 2 is returned. .IP \fB\imclient_havetls() \fP5 Returns a Boolean indicating whether the .B imclient library was compiled with TLS (SSL) support. If so, .B imclient_starttls() may be used to secure the IMAP connection. .IP \fB\imclient_starttls() \fP5 Issues a STARTTLS command on an existing IMAP connection and negotiates the secure link. The .B cert_file and .B key_file arguments specify the client certificate and secret key to use to authenticate ourselves to the server. If client authentication is not needed, set both of these arguments to NULL. .sp The .B CAfile and .B CApath arguments specify a file or directory, respectively, of CA certificates for validating server certificates. (See .B SSL_CTX_load_verify_locations(3) for details.) If both of these are NULL, the client will be unable to validate the server's certificate, in which case the connection may succeed but a warning will be printed to stdout. .SH EXAMPLES The following code is a possible skeletion of .B imclient that relies on Kerberos to do authentication. This code preforms an IMAP CAPABILITY request and prints out the result. .nf struct sasl_client; #include /* example uses xstrdup */ #include #include #include extern struct sasl_client krb_sasl_client; struct sasl_client *login_sasl_client[] = { &krb_sasl_client, NULL }; struct imclient *imclient; char server[] = "cyrus.andrew.cmu.edu" ; char port[] = "imap"; void fatal(char* message, int rc) { fprintf(stderr, "fatal error: %s\en", message); exit(rc); } static void callback_capability(struct imclient *imclient, void *rock, struct imclient_reply *reply) { if (reply->text != NULL) { *((char**)rock) = xstrdup( reply->text ); } } static void end_command (struct imclient *connection, void* rock, struct imclient_reply *inmsg) { (*(int*)rock)--; } main() { char* capability_string; int nc; if (imclient_connect(&imclient, server, port)) { fprintf(stderr, "error: Couldn't connect to %s %s\en", server, port); exit(1); } if (imclient_authenticate(imclient, login_sasl_client, "imap" /* service */, NULL /* user */, SASL_PROT_ANY)) { exit(1); } imclient_addcallback(imclient, "CAPABILITY", CALLBACK_NOLITERAL, callback_capability, &capability_string, NULL); nc = 1; imclient_send(imclient, end_command, (void*) &nc, "CAPABILITY"); while(nc > 0) { imclient_processoneevent(imclient); } if (strstr("LITERAL+", capability_string)) { imclient_setflags(imclient, IMCLIENT_CONN_NONSYNCLITERAL); } imclient_send(imclient, NULL, NULL, "LOGOUT"); imclient_close(imclient); printf("capability text is: %s\en", capability_string); free(capability_string); } .fi .SH BUGS No known bugs. .SH SEE ALSO .B cyradm, imapd, imspd, RFC2033 (IMAP LITERAL+ extension), RFC2060 (IMAP4rev1 specification), and .B select(2) .SH KEYWORDS IMAP, ACAP, IMSP, Kerberos, Authentication cyrus-imapd-2.5.10/man/ctl_deliver.80000644000175000017500000000525013001236020014102 00000000000000.\" -*- nroff -*- .TH CTL_DELIVER 8 "Project Cyrus" CMU .\" .\" Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. .\" .\" Redistribution and use in source and binary forms, with or without .\" modification, are permitted provided that the following conditions .\" are met: .\" .\" 1. Redistributions of source code must retain the above copyright .\" notice, this list of conditions and the following disclaimer. .\" .\" 2. Redistributions in binary form must reproduce the above copyright .\" notice, this list of conditions and the following disclaimer in .\" the documentation and/or other materials provided with the .\" distribution. .\" .\" 3. The name "Carnegie Mellon University" must not be used to .\" endorse or promote products derived from this software without .\" prior written permission. For permission or any legal .\" details, please contact .\" Carnegie Mellon University .\" Center for Technology Transfer and Enterprise Creation .\" 4615 Forbes Avenue .\" Suite 302 .\" Pittsburgh, PA 15213 .\" (412) 268-7393, fax: (412) 268-7395 .\" innovation@andrew.cmu.edu .\" .\" 4. Redistributions of any form whatsoever must retain the following .\" acknowledgment: .\" "This product includes software developed by Computing Services .\" at Carnegie Mellon University (http://www.cmu.edu/computing/)." .\" .\" CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO .\" THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY .\" AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE .\" FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES .\" WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN .\" AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING .\" OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. .SH NAME ctl_deliver \- perform operations on the duplicate delivery database .SH SYNOPSIS .B ctl_deliver [ .B \-C .I config-file ] .B \-d [ \fB\-f \fIfilename\fR ] .SH DESCRIPTION .I Ctl_deliver is used to perform various administrative operations on the duplicate delivery database. .PP .I Ctl_deliver reads its configuration options out of the .IR imapd.conf (5) file unless specified otherwise by \fB-C\fR. .SH OPTIONS .TP .BI \-C " config-file" Read configuration options from \fIconfig-file\fR. .TP .B \-d Dump the contents of the database to standard output in a portable flat-text format. .TP \fB\-f \fIfilename\fR Use the database specified by \fIfilename\fR instead of the default (\fIconfigdirectory\fB/deliver.db\fR). .SH FILES .TP .B /etc/imapd.conf .SH SEE ALSO .PP \fBimapd.conf(5)\fR, \fBmaster(8)\fR cyrus-imapd-2.5.10/man/notifyd.80000644000175000017500000000756513001236020013275 00000000000000.\" -*- nroff -*- .TH NOTIFYD 8 "Project Cyrus" CMU .\" .\" Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. .\" .\" Redistribution and use in source and binary forms, with or without .\" modification, are permitted provided that the following conditions .\" are met: .\" .\" 1. Redistributions of source code must retain the above copyright .\" notice, this list of conditions and the following disclaimer. .\" .\" 2. Redistributions in binary form must reproduce the above copyright .\" notice, this list of conditions and the following disclaimer in .\" the documentation and/or other materials provided with the .\" distribution. .\" .\" 3. The name "Carnegie Mellon University" must not be used to .\" endorse or promote products derived from this software without .\" prior written permission. For permission or any legal .\" details, please contact .\" Carnegie Mellon University .\" Center for Technology Transfer and Enterprise Creation .\" 4615 Forbes Avenue .\" Suite 302 .\" Pittsburgh, PA 15213 .\" (412) 268-7393, fax: (412) 268-7395 .\" innovation@andrew.cmu.edu .\" .\" 4. Redistributions of any form whatsoever must retain the following .\" acknowledgment: .\" "This product includes software developed by Computing Services .\" at Carnegie Mellon University (http://www.cmu.edu/computing/)." .\" .\" CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO .\" THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY .\" AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE .\" FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES .\" WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN .\" AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING .\" OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. .SH NAME notifyd \- Cyrus notification server .SH SYNOPSIS .B notifyd [ .B \-C .I config-file ] [ .B \-U .I uses ] [ .B \-T .I timeout ] .br [ .B \-D ] .SH DESCRIPTION .B Notifyd is a daemon started from master(8) that handles notification requests on behalf of lmtpd(8). .B Notifyd accepts the request and performs the notification using the method specified in the request. .PP Note that for .B notifyd to run properly you must set proto=udp in its cyrus.conf services entry. prefork=1 is also recommended. .PP .B Notifyd reads its configuration options out of the .IR imapd.conf (5) file unless specified otherwise by \fB-C\fR. The .I notifysocket option is used to specify the Unix domain socket to listen on for notifications. .SH OPTIONS .TP .BI \-C " config-file" Read configuration options from \fIconfig-file\fR. .TP .BI \-U " uses" The maximum number of times that the process should be used for new connections before shutting down. The default is 250. .TP .BI \-T " timeout" The number of seconds that the process will wait for a new connection before shutting down. Note that a value of 0 (zero) will disable the timeout. The default is 60. .TP .BI \-D Run external debugger specified in debug_command. .SH NOTIFICATION METHODS .TP .B null Ignore the notification request. .TP .B log Log the notification to syslog (for testing). .TP .B mailto Email the notification. This method can ONLY be used in a Sieve 'notify' action as it requires a \fImailto:\fR URL to be specified as an \fI:option\fR. .TP .B zephyr Send the notification as a zephyrgram. If used in a Sieve 'notify' action, additional recipients can be specified as \fI:options\fR. .TP .B external Send the notification via an external program. The path to the program is specified using the \fInotify_external\fR option in the configuration file. .SH FILES .TP .B /etc/imapd.conf Default configuration file. .TP .B /etc/cyrus.conf Cyrus Master process configuration file. .SH SEE ALSO .PP \fBimapd.conf(5)\fR, \fBcyrus.conf\fR, \fBmaster(8)\fR, \fBlmtpd(8)\fR cyrus-imapd-2.5.10/man/sync_server.80000644000175000017500000000532213001236020014150 00000000000000.\" -*- nroff -*- .TH SYNC_SERVER 8 "Project Cyrus" CMU .\" .\" Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. .\" .\" Redistribution and use in source and binary forms, with or without .\" modification, are permitted provided that the following conditions .\" are met: .\" .\" 1. Redistributions of source code must retain the above copyright .\" notice, this list of conditions and the following disclaimer. .\" .\" 2. Redistributions in binary form must reproduce the above copyright .\" notice, this list of conditions and the following disclaimer in .\" the documentation and/or other materials provided with the .\" distribution. .\" .\" 3. The name "Carnegie Mellon University" must not be used to .\" endorse or promote products derived from this software without .\" prior written permission. For permission or any legal .\" details, please contact .\" Carnegie Mellon University .\" Center for Technology Transfer and Enterprise Creation .\" 4615 Forbes Avenue .\" Suite 302 .\" Pittsburgh, PA 15213 .\" (412) 268-7393, fax: (412) 268-7395 .\" innovation@andrew.cmu.edu .\" .\" 4. Redistributions of any form whatsoever must retain the following .\" acknowledgment: .\" "This product includes software developed by Computing Services .\" at Carnegie Mellon University (http://www.cmu.edu/computing/)." .\" .\" CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO .\" THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY .\" AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE .\" FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES .\" WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN .\" AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING .\" OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. .SH NAME sync_server \- server side of the synchronization (replication) engine .SH SYNOPSIS .B sync_server [ .B \-C .I config-file ] [ .B \-p .I ssf ] .SH DESCRIPTION .B sync_server is the server side of the the replication system. It runs on the target (replica) system and listens for connections from .B sync_client which provides instructions for synchronizing the replica system with the master system. .SH OPTIONS .TP .BI \-C " config-file" Read configuration options from \fIconfig-file\fR. .TP .BI \-p " ssf" Tell .B sync_server that an external layer exists. An SSF (security strength factor) of 1 means an integrity protection layer exists. Any higher SSF implies some form of privacy protection. .SH FILES .TP .B /etc/imapd.conf .SH SEE ALSO .PP \fBsync_client\fR(8) .SH AUTHORS David Carter (dpc22@cam.ac.uk), Ken Murchison (ken@oceana.com) cyrus-imapd-2.5.10/man/rmnews.80000644000175000017500000000605513001236020013125 00000000000000.\" -*- nroff -*- .TH RMNEWS 8 "Project Cyrus" CMU .\" .\" Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. .\" .\" Redistribution and use in source and binary forms, with or without .\" modification, are permitted provided that the following conditions .\" are met: .\" .\" 1. Redistributions of source code must retain the above copyright .\" notice, this list of conditions and the following disclaimer. .\" .\" 2. Redistributions in binary form must reproduce the above copyright .\" notice, this list of conditions and the following disclaimer in .\" the documentation and/or other materials provided with the .\" distribution. .\" .\" 3. The name "Carnegie Mellon University" must not be used to .\" endorse or promote products derived from this software without .\" prior written permission. For permission or any legal .\" details, please contact .\" Carnegie Mellon University .\" Center for Technology Transfer and Enterprise Creation .\" 4615 Forbes Avenue .\" Suite 302 .\" Pittsburgh, PA 15213 .\" (412) 268-7393, fax: (412) 268-7395 .\" innovation@andrew.cmu.edu .\" .\" 4. Redistributions of any form whatsoever must retain the following .\" acknowledgment: .\" "This product includes software developed by Computing Services .\" at Carnegie Mellon University (http://www.cmu.edu/computing/)." .\" .\" CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO .\" THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY .\" AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE .\" FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES .\" WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN .\" AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING .\" OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. .SH NAME rmnews \- expunge and remove news articles .SH SYNOPSIS .B rmnews .SH DESCRIPTION .I Rmnews reads article data from the standard input. It then expunges and removes the listed articles. .I Rmnews is designed to be used by InterNetNews to remove canceled, superseded, and expired news articles. .PP The input is processed as an INN .I expirerm file listing or an INN cancel stream written as a ``WC'' entry in the .IR newsfeeds (5) file. This data consists of lines of text, each containing a list of relative article pathnames, with a single space between entries. If a listed file is contained in an IMAP news mailbox, it is expunged out of that mailbox. In any case, each listed file is unlinked. .PP .I Rmnews reads its configuration options out of the .IR imapd.conf (5) file. The optional .I newsprefix option specifies a prefix to be prepended to newsgroup names to make the corresponding IMAP mailbox names. The required .I partition-news option specifies the pathname prefix to the IMAP news mailboxes. The value of .I partition-news concatenated with the dots-to-slashes-converted value of .I newsprefix must be the pathname of the news spool directory. .SH FILES .TP .B /etc/imapd.conf cyrus-imapd-2.5.10/man/installsieve.10000644000175000017500000000657313001236020014312 00000000000000.\" -*- nroff -*- .TH INSTALLSIEVE 1 "Project Cyrus" CMU .\" .\" Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. .\" .\" Redistribution and use in source and binary forms, with or without .\" modification, are permitted provided that the following conditions .\" are met: .\" .\" 1. Redistributions of source code must retain the above copyright .\" notice, this list of conditions and the following disclaimer. .\" .\" 2. Redistributions in binary form must reproduce the above copyright .\" notice, this list of conditions and the following disclaimer in .\" the documentation and/or other materials provided with the .\" distribution. .\" .\" 3. The name "Carnegie Mellon University" must not be used to .\" endorse or promote products derived from this software without .\" prior written permission. For permission or any legal .\" details, please contact .\" Carnegie Mellon University .\" Center for Technology Transfer and Enterprise Creation .\" 4615 Forbes Avenue .\" Suite 302 .\" Pittsburgh, PA 15213 .\" (412) 268-7393, fax: (412) 268-7395 .\" innovation@andrew.cmu.edu .\" .\" 4. Redistributions of any form whatsoever must retain the following .\" acknowledgment: .\" "This product includes software developed by Computing Services .\" at Carnegie Mellon University (http://www.cmu.edu/computing/)." .\" .\" CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO .\" THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY .\" AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE .\" FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES .\" WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN .\" AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING .\" OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. .SH NAME installsieve \- user utility for managing sieve scripts .SH SYNOPSIS .B installsieve .SH DESCRIPTION .I installsieve is a utility that allows users to manage their sieve scripts kept on the server. .PP .SH OPTIONS .TP .BI \-v " name" View script with the given name. The script if retrieved sucessfully is output to standard output. .TP .B \-l List all of the scripts currently on the server. If one of the scripts is active a arrow is printed indicating that it is the active script. .TP .BI \-p " port" Port to connect to. If left off this defaults to "sieve" as defined in /etc/services. .TP .BI \-i " file" Install a file onto the server. If a script with the same name already exists on the server it is overwritten. Upon sucessfully putting the script on the server the script is set active. If \fIfile\fP has the extension .script it is chopped when put on the server since sieve names may not contain a '.'. .TP .BI \-a " name" Set \fIname\fP as the active script. The list of available names can be obtained from the \fB-l\fP option. .TP .BI \-d " name" Delete the sieve script on the server with \fIname\fP. .TP .BI \-m " mechanism" Force installsieve to use \fImechanism\fP for authentication. If not specified the strongest authentication mechanism is chosen. .TP .BI \-g " name" Get the sieve script with \fIname\fP and save it to disk with a ".script" extension. If a file with that name already exists it is overwritten. .TP .BI \-u " user" Userid/Authname to use for authentication; by default, the current user. cyrus-imapd-2.5.10/man/lmtptest.10000644000175000017500000001144313001236020013454 00000000000000.\" -*- nroff -*- .TH LMTPTEST 1 "Project Cyrus" CMU .\" .\" Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. .\" .\" Redistribution and use in source and binary forms, with or without .\" modification, are permitted provided that the following conditions .\" are met: .\" .\" 1. Redistributions of source code must retain the above copyright .\" notice, this list of conditions and the following disclaimer. .\" .\" 2. Redistributions in binary form must reproduce the above copyright .\" notice, this list of conditions and the following disclaimer in .\" the documentation and/or other materials provided with the .\" distribution. .\" .\" 3. The name "Carnegie Mellon University" must not be used to .\" endorse or promote products derived from this software without .\" prior written permission. For permission or any legal .\" details, please contact .\" Carnegie Mellon University .\" Center for Technology Transfer and Enterprise Creation .\" 4615 Forbes Avenue .\" Suite 302 .\" Pittsburgh, PA 15213 .\" (412) 268-7393, fax: (412) 268-7395 .\" innovation@andrew.cmu.edu .\" .\" 4. Redistributions of any form whatsoever must retain the following .\" acknowledgment: .\" "This product includes software developed by Computing Services .\" at Carnegie Mellon University (http://www.cmu.edu/computing/)." .\" .\" CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO .\" THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY .\" AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE .\" FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES .\" WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN .\" AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING .\" OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. .SH NAME lmtptest \- interactive LMTP test program .SH SYNOPSIS .B lmtptest [ .B \-t .I keyfile ] [ .B \-p .I port ] [ .B \-m .I mechanism ] .br [ .B \-a .I userid ] [ .B \-u .I userid ] [ .B \-k .I num ] [ .B \-l .I num ] .br [ .B \-r .I realm ] [ .B \-f .I file ] [ .B \-n .I num ] [ .B \-c ] .br [ .B \-i ] [ .B \-o \fIoption\fB=\fIvalue\fR ] [ .B \-v ] \fIhostname\fR .SH DESCRIPTION .I lmtptest is a utility that allows you to authenticate to a LMTP server and interactively issue commands to it. Once authenticated you may issue any LMTP command by simply typing it in. It is capable of multiple SASL authentication mechanisms and handles encryption layers transparently. This utility is often used for testing the operation of a lmtp server. Also those developing LMTP clients find it useful. .PP .SH OPTIONS .TP .BI \-t " keyfile" Enable TLS. \fIkeyfile\fR contains the TLS public and private keys. Specify \fB""\fR to negotiate a TLS encryption layer but not use TLS authentication. .TP .BI \-p " port" Port to connect to. If left off this defaults to \fBlmtp\fR as defined in /etc/services. .TP .BI -m " mechanism" Force lmtptest to use \fImechanism\fR for authentication. If not specified the strongest authentication mechanism supported by the server is chosen. .TP .BI -a " userid" Userid to use for authentication; defaults to the current user. This is the userid whose password or credentials will be presented to the server for verification. .TP .BI -u " userid" Userid to use for authorization; defaults to the current user. This is the userid whose identity will be assumed after authentication. \fBNOTE:\fR This is only used with SASL mechanisms that allow proxying (e.g. PLAIN, DIGEST-MD5). .TP .BI -k " num" Minimum protection layer required. .TP .BI -l " num" Maximum protection layer to use (\fB0\fR=none; \fB1=\fRintegrity; etc). For example if you are using the KERBEROS_V4 authentication mechanism specifying \fB0\fR will force lmtptest to not use any layer and specifying \fB1\fR will force it to use the integrity layer. By default the maximum supported protection layer will be used. .TP .BI -r " realm" Specify the \fIrealm\fR to use. Certain authentication mechanisms (e.g. DIGEST-MD5) may require one to specify the realm. .TP .BI -f " file" Pipe \fIfile\fR into connection after authentication. .TP .BI -n " num" Number of authentication attempts; default = 1. The client will attempt to do SSL/TLS session reuse and/or fast reauth (e.g. DIGEST-MD5), if possible. .TP .B -c Enable challenge prompt callbacks. This will cause the OTP mechanism to ask for the the one-time password instead of the secret pass-phrase (library generates the correct response). .TP .B -i Don't send an initial client response for SASL mechanisms, even if the protocol supports it. .TP \fB-o \fIoption\fB=\fIvalue\fR Set the SASL \fIoption\fR to \fIvalue\fR. .TP .B -v Verbose. Print out more information than usual. .SH SEE ALSO .PP \fBlmtpd(8)\fR cyrus-imapd-2.5.10/man/sivtest.10000644000175000017500000001150013001236020013273 00000000000000.\" -*- nroff -*- .TH SIVTEST 1 "Project Cyrus" CMU .\" .\" Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. .\" .\" Redistribution and use in source and binary forms, with or without .\" modification, are permitted provided that the following conditions .\" are met: .\" .\" 1. Redistributions of source code must retain the above copyright .\" notice, this list of conditions and the following disclaimer. .\" .\" 2. Redistributions in binary form must reproduce the above copyright .\" notice, this list of conditions and the following disclaimer in .\" the documentation and/or other materials provided with the .\" distribution. .\" .\" 3. The name "Carnegie Mellon University" must not be used to .\" endorse or promote products derived from this software without .\" prior written permission. For permission or any legal .\" details, please contact .\" Carnegie Mellon University .\" Center for Technology Transfer and Enterprise Creation .\" 4615 Forbes Avenue .\" Suite 302 .\" Pittsburgh, PA 15213 .\" (412) 268-7393, fax: (412) 268-7395 .\" innovation@andrew.cmu.edu .\" .\" 4. Redistributions of any form whatsoever must retain the following .\" acknowledgment: .\" "This product includes software developed by Computing Services .\" at Carnegie Mellon University (http://www.cmu.edu/computing/)." .\" .\" CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO .\" THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY .\" AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE .\" FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES .\" WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN .\" AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING .\" OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. .SH NAME sivtest \- interactive MANAGESIEVE test program .SH SYNOPSIS .B sivtest [ .B \-t .I keyfile ] [ .B \-p .I port ] [ .B \-m .I mechanism ] .br [ .B \-a .I userid ] [ .B \-u .I userid ] [ .B \-k .I num ] [ .B \-l .I num ] .br [ .B \-r .I realm ] [ .B \-f .I file ] [ .B \-n .I num ] [ .B \-c ] .br [ .B \-i ] [ .B \-o \fIoption\fB=\fIvalue\fR ] [ .B \-v ] \fIhostname\fR .SH DESCRIPTION .I sivtest is a utility that allows you to authenticate to a MANAGESIEVE server and interactively issue commands to it. Once authenticated you may issue any MANAGESIEVE command by simply typing it in. It is capable of multiple SASL authentication mechanisms and handles encryption layers transparently. This utility is often used for testing the operation of a timsieved server. Also those developing MANAGESIEVE clients find it useful. .PP .SH OPTIONS .TP .BI \-t " keyfile" Enable TLS. \fIkeyfile\fR contains the TLS public and private keys. Specify \fB""\fR to negotiate a TLS encryption layer but not use TLS authentication. .TP .BI \-p " port" Port to connect to. If left off this defaults to \fBsieve\fR as defined in /etc/services. .TP .BI -m " mechanism" Force sivtest to use \fImechanism\fR for authentication. If not specified the strongest authentication mechanism supported by the server is chosen. .TP .BI -a " userid" Userid to use for authentication; defaults to the current user. This is the userid whose password or credentials will be presented to the server for verification. .TP .BI -u " userid" Userid to use for authorization; defaults to the current user. This is the userid whose identity will be assumed after authentication. \fBNOTE:\fR This is only used with SASL mechanisms that allow proxying (e.g. PLAIN, DIGEST-MD5). .TP .BI -k " num" Minimum protection layer required. .TP .BI -l " num" Maximum protection layer to use (\fB0\fR=none; \fB1=\fRintegrity; etc). For example if you are using the KERBEROS_V4 authentication mechanism specifying \fB0\fR will force sivtest to not use any layer and specifying \fB1\fR will force it to use the integrity layer. By default the maximum supported protection layer will be used. .TP .BI -r " realm" Specify the \fIrealm\fR to use. Certain authentication mechanisms (e.g. DIGEST-MD5) may require one to specify the realm. .TP .BI -f " file" Pipe \fIfile\fR into connection after authentication. .TP .BI -n " num" Number of authentication attempts; default = 1. The client will attempt to do SSL/TLS session reuse and/or fast reauth (e.g. DIGEST-MD5), if possible. .TP .B -c Enable challenge prompt callbacks. This will cause the OTP mechanism to ask for the the one-time password instead of the secret pass-phrase (library generates the correct response). .TP .B -i Don't send an initial client response for SASL mechanisms, even if the protocol supports it. .TP \fB-o \fIoption\fB=\fIvalue\fR Set the SASL \fIoption\fR to \fIvalue\fR. .TP .B -v Verbose. Print out more information than usual. .SH SEE ALSO .PP \fBtimsieved(8)\fR cyrus-imapd-2.5.10/man/idled.80000644000175000017500000000511413001236020012666 00000000000000.\" -*- nroff -*- .TH IDLED 8 "Project Cyrus" CMU .\" .\" Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. .\" .\" Redistribution and use in source and binary forms, with or without .\" modification, are permitted provided that the following conditions .\" are met: .\" .\" 1. Redistributions of source code must retain the above copyright .\" notice, this list of conditions and the following disclaimer. .\" .\" 2. Redistributions in binary form must reproduce the above copyright .\" notice, this list of conditions and the following disclaimer in .\" the documentation and/or other materials provided with the .\" distribution. .\" .\" 3. The name "Carnegie Mellon University" must not be used to .\" endorse or promote products derived from this software without .\" prior written permission. For permission or any legal .\" details, please contact .\" Carnegie Mellon University .\" Center for Technology Transfer and Enterprise Creation .\" 4615 Forbes Avenue .\" Suite 302 .\" Pittsburgh, PA 15213 .\" (412) 268-7393, fax: (412) 268-7395 .\" innovation@andrew.cmu.edu .\" .\" 4. Redistributions of any form whatsoever must retain the following .\" acknowledgment: .\" "This product includes software developed by Computing Services .\" at Carnegie Mellon University (http://www.cmu.edu/computing/)." .\" .\" CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO .\" THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY .\" AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE .\" FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES .\" WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN .\" AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING .\" OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. .SH NAME idled \- provide near real-time updates for IMAP IDLE .SH SYNOPSIS .B idled [ .B \-C .I config-file ] .SH DESCRIPTION .I Idled is a long lived datagram daemon which receives notifications of mailbox changes and signals the appropriate .IR imapd to report the changes to the client. .I Idled is usually started from .I master. .PP .I Idled reads its configuration options out of the .IR imapd.conf (5) file unless specified otherwise by \fB-C\fR. The .I idlesocket option is used to specify the Unix domain socket to listen on for notifications. .SH OPTIONS .TP .BI \-C " config-file" Read configuration options from \fIconfig-file\fR. .SH FILES .TP .B /etc/imapd.conf .SH SEE ALSO .PP \fBimapd.conf(5)\fR, \fBmaster(8)\fR cyrus-imapd-2.5.10/man/tls_prune.80000644000175000017500000000474513001236020013631 00000000000000.\" -*- nroff -*- .TH TLS_PRUNE 8 "Project Cyrus" CMU .\" .\" Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. .\" .\" Redistribution and use in source and binary forms, with or without .\" modification, are permitted provided that the following conditions .\" are met: .\" .\" 1. Redistributions of source code must retain the above copyright .\" notice, this list of conditions and the following disclaimer. .\" .\" 2. Redistributions in binary form must reproduce the above copyright .\" notice, this list of conditions and the following disclaimer in .\" the documentation and/or other materials provided with the .\" distribution. .\" .\" 3. The name "Carnegie Mellon University" must not be used to .\" endorse or promote products derived from this software without .\" prior written permission. For permission or any legal .\" details, please contact .\" Carnegie Mellon University .\" Center for Technology Transfer and Enterprise Creation .\" 4615 Forbes Avenue .\" Suite 302 .\" Pittsburgh, PA 15213 .\" (412) 268-7393, fax: (412) 268-7395 .\" innovation@andrew.cmu.edu .\" .\" 4. Redistributions of any form whatsoever must retain the following .\" acknowledgment: .\" "This product includes software developed by Computing Services .\" at Carnegie Mellon University (http://www.cmu.edu/computing/)." .\" .\" CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO .\" THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY .\" AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE .\" FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES .\" WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN .\" AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING .\" OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. .SH NAME tls_prune \- prune expired sessions from the TLS sessions database .SH SYNOPSIS .B tls_prune [ .B \-C .I config-file ] .SH DESCRIPTION .I Tls_prune is used to prune expired sessions from the TLS sessions database. The lifetime of a TLS session is determined by the \fBtls_session_timeout\fR configuration option. .PP .I Tls_prune reads its configuration options out of the .IR imapd.conf (5) file unless specified otherwise by \fB-C\fR. .SH OPTIONS .TP .BI \-C " config-file" Read configuration options from \fIconfig-file\fR. .SH FILES .TP .B /etc/imapd.conf .SH SEE ALSO .PP \fBimapd.conf(5)\fR, \fBmaster(8)\fR cyrus-imapd-2.5.10/man/sync_client.80000644000175000017500000001306713001236020014125 00000000000000.\" -*- nroff -*- .TH SYNC_CLIENT 8 "Project Cyrus" CMU .\" .\" Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. .\" .\" Redistribution and use in source and binary forms, with or without .\" modification, are permitted provided that the following conditions .\" are met: .\" .\" 1. Redistributions of source code must retain the above copyright .\" notice, this list of conditions and the following disclaimer. .\" .\" 2. Redistributions in binary form must reproduce the above copyright .\" notice, this list of conditions and the following disclaimer in .\" the documentation and/or other materials provided with the .\" distribution. .\" .\" 3. The name "Carnegie Mellon University" must not be used to .\" endorse or promote products derived from this software without .\" prior written permission. For permission or any legal .\" details, please contact .\" Carnegie Mellon University .\" Center for Technology Transfer and Enterprise Creation .\" 4615 Forbes Avenue .\" Suite 302 .\" Pittsburgh, PA 15213 .\" (412) 268-7393, fax: (412) 268-7395 .\" innovation@andrew.cmu.edu .\" .\" 4. Redistributions of any form whatsoever must retain the following .\" acknowledgment: .\" "This product includes software developed by Computing Services .\" at Carnegie Mellon University (http://www.cmu.edu/computing/)." .\" .\" CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO .\" THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY .\" AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE .\" FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES .\" WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN .\" AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING .\" OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. .SH NAME sync_client \- client side of the synchronization (replication) engine .SH SYNOPSIS .B sync_client [ .B \-v ] [ .B \-l ] [ .B \-z ] [ .B \-C .I config-file ] [ .B \-S .I servername ] .br [ .B \-f .I input-file ] [ .B \-F .I shutdown_file ] [ .B \-w .I wait_interval ] .br [ .B \-t .I timeout ] [ .B \-d .I delay ] [ .B \-r ] [ .B \-u ] [ .B \-m ] [ .B \-A ] .br [ .B \-s ] .IR objects ... .SH DESCRIPTION .B sync_client is the client side of the replication system. It runs on the client (master) system and connects to the target (replica) system and generates an appropriate sequence of transactions to synchronize the replica system with the master system. .SH OPTIONS .TP .BI \-v Verbose mode. Use twice (-v -v) to log all protocol traffic to stderr. .TP .BI \-l Verbose logging mode. .TP .BI \-o Only attempt to connect to the backend server once rather than waiting up to 1000 seconds before giving up. .TP .BI \-z Require compression. The replication protocol will always try to enable deflate compression if both ends support it. Set this flag when you want to abort if compression is not available. .TP .BI \-C " config-file" Read configuration options from \fIconfig-file\fR. .TP .BI \-S " servername" Tells .B sync_client which server to communicate with. Overrides the \fIsync_host\fR configuration option. .TP .BI \-f " input-file" In mailbox or user replication mode: provides list of users or mailboxes to replicate. In rolling replication mode, specifies an alternate log file .RB ( sync_client will exit after processing the log file). .TP .BI \-F " shutdown-file" Rolling replication checks for this file at the end of each replication cycle and shuts down if it is present. Used to request a nice clean shutdown at the first convenient point. The file is removed on shutdown. Overrides .I sync_shutdown_file option in .I imapd.conf .TP .BI \-w " interval" Wait this long before starting. This option is typically used so that we can attach a debugger to one end of the replication system or the other. .TP .BI \-t " timeout" Timeout for single replication run in rolling replication. .B sync_client will negotiate a restart after this many seconds. Default: 600 seconds .TP .BI \-d " delay" Minimum delay between replication runs in rolling replication mode. Larger values provide better efficiency as transactions can be merged. Smaller values mean that the replica system is more up to date and that you don't end up with large blocks of replication transactions as a single group. Default: 3 seconds. .TP .BI \-r Rolling (repeat) replication mode. Pick up a list of actions recorded by the .BR lmtpd "(8), " imapd "(8), " popd "(8) and " nntpd (8) daemons from the file specified in .IR sync_log_file . Repeat until .I sync_shutdown_file appears. .TP .BI \-n Use the named channel for rolling replication mode. If multiple channels are specified in .I sync_log_channels then use one of them. This option is probably best combined with .B \-S to connect to a different server with each channel. .TP .BI \-u User mode. Remaining arguments are list of users who should be replicated. .TP .BI \-A All users mode. Sync every user on the server to the replica (doesn't do non-user mailboxes at all... this could be considered a bug and maybe it should do those mailboxes independently) .TP .BI \-m Mailbox mode. Remaining arguments are list of mailboxes which should be replicated. .TP .BI \-s Sieve mode. Remaining arguments are list of users whose Sieve files should be replicated. Principally used for debugging purposes: not exposed to .BR sync_client (8). .SH FILES .TP .B /etc/imapd.conf .SH SEE ALSO .PP \fBsync_server\fR(8) .SH AUTHORS David Carter (dpc22@cam.ac.uk), Ken Murchison (ken@oceana.com) cyrus-imapd-2.5.10/man/lmtpd.80000644000175000017500000000617313001236020012733 00000000000000.\" -*- nroff -*- .TH LMTPD 8 "Project Cyrus" CMU .\" .\" Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. .\" .\" Redistribution and use in source and binary forms, with or without .\" modification, are permitted provided that the following conditions .\" are met: .\" .\" 1. Redistributions of source code must retain the above copyright .\" notice, this list of conditions and the following disclaimer. .\" .\" 2. Redistributions in binary form must reproduce the above copyright .\" notice, this list of conditions and the following disclaimer in .\" the documentation and/or other materials provided with the .\" distribution. .\" .\" 3. The name "Carnegie Mellon University" must not be used to .\" endorse or promote products derived from this software without .\" prior written permission. For permission or any legal .\" details, please contact .\" Carnegie Mellon University .\" Center for Technology Transfer and Enterprise Creation .\" 4615 Forbes Avenue .\" Suite 302 .\" Pittsburgh, PA 15213 .\" (412) 268-7393, fax: (412) 268-7395 .\" innovation@andrew.cmu.edu .\" .\" 4. Redistributions of any form whatsoever must retain the following .\" acknowledgment: .\" "This product includes software developed by Computing Services .\" at Carnegie Mellon University (http://www.cmu.edu/computing/)." .\" .\" CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO .\" THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY .\" AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE .\" FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES .\" WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN .\" AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING .\" OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. .SH NAME lmtpd \- LMTP server process .SH SYNOPSIS .B lmtpd [ .B \-C .I config-file ] [ .B \-U .I uses ] [ .B \-T .I timeout ] [ .B \-D ] .br [ .B \-a ] .SH DESCRIPTION .I Lmtpd is an LMTP server used to deliver mail to the IMAP mailstore. It accepts commands on its standard input and responds on its standard output. It MUST be invoked by .IR master (8) with those descriptors attached to a remote client connection. .PP .I Lmtpd reads its configuration options out of the .IR imapd.conf (5) file unless specified otherwise by \fB-C\fR. .SH OPTIONS .TP .BI \-C " config-file" Read configuration options from \fIconfig-file\fR. .TP .BI \-U " uses" The maximum number of times that the process should be used for new connections before shutting down. The default is 250. .TP .BI \-T " timeout" The number of seconds that the process will wait for a new connection before shutting down. Note that a value of 0 (zero) will disable the timeout. The default is 60. .TP .BI \-D Run external debugger specified in debug_command. .TP .BI \-a Preauthorize connections initiated on an internet socket, instead of requiring LMTP AUTH. This should only be used for connections coming from trusted hosts. .SH FILES .TP .B /etc/imapd.conf .SH SEE ALSO .PP \fBimapd.conf(5)\fR, \fBmaster(8)\fR cyrus-imapd-2.5.10/man/cyr_expire.80000644000175000017500000001333313001236020013760 00000000000000.\" -*- nroff -*- .TH CYR_EXPIRE 8 "Project Cyrus" CMU .\" .\" Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. .\" .\" Redistribution and use in source and binary forms, with or without .\" modification, are permitted provided that the following conditions .\" are met: .\" .\" 1. Redistributions of source code must retain the above copyright .\" notice, this list of conditions and the following disclaimer. .\" .\" 2. Redistributions in binary form must reproduce the above copyright .\" notice, this list of conditions and the following disclaimer in .\" the documentation and/or other materials provided with the .\" distribution. .\" .\" 3. The name "Carnegie Mellon University" must not be used to .\" endorse or promote products derived from this software without .\" prior written permission. For permission or any legal .\" details, please contact .\" Carnegie Mellon University .\" Center for Technology Transfer and Enterprise Creation .\" 4615 Forbes Avenue .\" Suite 302 .\" Pittsburgh, PA 15213 .\" (412) 268-7393, fax: (412) 268-7395 .\" innovation@andrew.cmu.edu .\" .\" 4. Redistributions of any form whatsoever must retain the following .\" acknowledgment: .\" "This product includes software developed by Computing Services .\" at Carnegie Mellon University (http://www.cmu.edu/computing/)." .\" .\" CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO .\" THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY .\" AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE .\" FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES .\" WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN .\" AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING .\" OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. .SH NAME cyr_expire \- expire messages and duplicate delivery database entries .SH SYNOPSIS .B cyr_expire [ .B \-C .I config-file ] [ .BI \-D " delete-duration" ] [ .BI \-E " expire-duration" ] [ .BI \-X " expunge-duration" ] [ .BI \-p " mailbox-prefix" ] [ .BI \-u " username" ] [ .B \-t ] [ .B \-v ] .SH DESCRIPTION .PP \fBCyr_expire\fR is used to run a number of regular maintenance tasks on Cyrus databases, specifically: .IP \(bu 2m expire messages from mailboxes, and .IP \(bu 2m expire entries from the duplicate delivery database, and .IP \(bu 2m cleanse mailboxes of partially expunged messages (when using the "delayed" expunge mode), and .IP \(bu 2m remove deleted mailboxes (when using the "delayed" delete mode). .PP The expiration of messages is controlled by the \fB/vendor/cmu/cyrus-imapd/expire\fR mailbox annotation which specifies the age (in days) of messages in the given mailbox that should be deleted. A value of 0 means that no expiration is to be performed on that mailbox. .PP The value of the \fB/vendor/cmu/cyrus-imapd/expire\fR annotation is inherited by all children of the mailbox on which it is set, so an entire mailbox tree can be configured by setting a single annotation on the root of that tree. If a mailbox does not have a \fB/vendor/cmu/cyrus-imapd/expire\fR annotation set on it (or does not inherit one), then no messages are expired from the mailbox. .PP The annotation can be examined using the \fBinfo\fR command of \fBcyradm(1p)\fR, and modified using the \fBmboxconfig\fR and \fBsetinfo\fR commands of \fBcyradm(1p)\fR. .PP Expiration of duplicate delivery database entries for a given mailbox is also controlled by the \fB/vendor/cmu/cyrus-imapd/expire\fR annotation which applies to that mailbox. Unlike message expiration, if no annotation applies to the mailbox then duplicate database entries are expired using the value given to the \fB-E\fR option. .PP \fBCyr_expire\fR reads its configuration options out of the \fIimapd.conf\fR(5) file unless specified otherwise by \fB-C\fR. .PP \fBCyr_expire\fR requires at least one of \fB-D -E\fR \fB-X\fR or \fB-t\fR to be supplied. .SH OPTIONS .TP \fB\-C\fI config-file\fR Read configuration options from \fIconfig-file\fR. .TP \fB\-D \fIdelete-duration\fR Remove previously deleted mailboxes older than \fIdelete-duration\fR (when using the "delayed" delete mode). The value can be a floating point number, and may have a suffix to specify the unit of time. If no suffix, the value is number of days. Valid suffixes are \fBd\fR (days), \fBh\fR (hours), \fBm\fR (minutes) and \fBs\fR (seconds). .TP \fB\-E \fIexpire-duration\fR Prune the duplicate database of entries older than \fIexpire-duration\fR. This value is only used for entries which do not have a corresponding \fB/vendor/cmu/cyrus-imapd/expire\fR mailbox annotation. Format is the same as delete-duration. .TP \fB\-X \fIexpunge-duration\fR Expunge previously deleted messages older than \fIexpunge-duration\fR (when using the "delayed" expunge mode). Format is the same as delete-duration. .TP \fB\-x Do not expunge messages even if using delayed expunge mode. This reduces IO traffic considerably, allowing \fBcyr_expire\fR to be run frequently to clean up the duplicate database without overloading the machine. .TP \fB\-p \fImailbox-prefix\fR Only find mailboxes starting with this prefix, e.g. "user.justgotspammedlots". .TP \fB\-u \fIuserid\fR Only find mailboxes belonging to this user, e.g. "justgotspammedlots@example.com". .TP \fB\-t\fR Remove any user flags which are not used by remaining (not expunged) messages. .TP .B \-v Enable verbose output. .TP .B \-a Skip the annotation lookup, so all \fB/vendor/cmu/cyrus-imapd/expire\fR annotations are ignored entirely. It behaves as if they were not set, so only \fIexpire-days\fR is considered for all mailboxes. .SH FILES .TP .B /etc/imapd.conf .SH SEE ALSO .PP \fBimapd.conf(5)\fR, \fBmaster(8)\fR, \fBcyradm(1p)\fR cyrus-imapd-2.5.10/man/unexpunge.80000644000175000017500000000700313001236020013622 00000000000000.\" -*- nroff -*- .TH UNEXPUNGE 8 "Project Cyrus" CMU .\" .\" Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. .\" .\" Redistribution and use in source and binary forms, with or without .\" modification, are permitted provided that the following conditions .\" are met: .\" .\" 1. Redistributions of source code must retain the above copyright .\" notice, this list of conditions and the following disclaimer. .\" .\" 2. Redistributions in binary form must reproduce the above copyright .\" notice, this list of conditions and the following disclaimer in .\" the documentation and/or other materials provided with the .\" distribution. .\" .\" 3. The name "Carnegie Mellon University" must not be used to .\" endorse or promote products derived from this software without .\" prior written permission. For permission or any legal .\" details, please contact .\" Carnegie Mellon University .\" Center for Technology Transfer and Enterprise Creation .\" 4615 Forbes Avenue .\" Suite 302 .\" Pittsburgh, PA 15213 .\" (412) 268-7393, fax: (412) 268-7395 .\" innovation@andrew.cmu.edu .\" .\" 4. Redistributions of any form whatsoever must retain the following .\" acknowledgment: .\" "This product includes software developed by Computing Services .\" at Carnegie Mellon University (http://www.cmu.edu/computing/)." .\" .\" CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO .\" THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY .\" AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE .\" FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES .\" WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN .\" AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING .\" OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. .SH NAME unexpunge \- restore expunged (but yet unremoved) messages .SH SYNOPSIS .B unexpunge [ .B \-C .I config-file ] .B \-l .I mailbox .br .B unexpunge [ .B \-C .I config-file ] .B \-t time-interval [ .B \-d ] [ .B \-v ] [ .B \-f .I flagname ] .I mailbox .br .B unexpunge [ .B \-C .I config-file ] .B \-a [ .B \-d ] [ .B \-v ] [ .B \-f .I flagname ] .I mailbox .br .B unexpunge [ .B \-C .I config-file ] .B \-u [ .B \-d ] [ .B \-v ] [ .B \-f .I flagname ] .IR "mailbox uid" ... .SH DESCRIPTION .I Unexpunge is used to restore expunged messages which have yet to be removed from the Cyrus mailspool. This utility is only useful when the server is configured to use \fBdelayed\fR expunge. .PP .I Unexpunge reads its configuration options out of the .IR imapd.conf (5) file unless specified otherwise by \fB-C\fR. .SH OPTIONS .TP .BI \-C " config-file" Read configuration options from \fIconfig-file\fR. .TP .B \-l List the expunged messages in the specified mailbox which are available for restoration. .TP .BI \-t " time-interval" Unexpunge messages which were expunged in the last time-interval seconds. (modifiers: m: minutes, h: hours, d: days, w: weeks). .TP .B \-a Restore \fBall\fR of the expunged messages in the specified mailbox. .TP .B \-u Restore only those messages having the specified UIDs in the specified mailbox. .TP .B \-d Unset the \fI\\Deleted\fR flag on any restored messages. .TP .BI \-f " flagname" Set the user flag .I flagname on any restored messages. This can make it easy to batch operate on just the restored messages afterwards. .TP .B \-v Enable verbose output/logging. .SH FILES .TP .B /etc/imapd.conf .SH SEE ALSO .PP \fBimapd.conf(5)\fR cyrus-imapd-2.5.10/man/chk_cyrus.80000644000175000017500000000557613001236020013613 00000000000000.\" -*- nroff -*- .TH CHK_CYRUS 8 "Project Cyrus" CMU .\" .\" Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. .\" .\" Redistribution and use in source and binary forms, with or without .\" modification, are permitted provided that the following conditions .\" are met: .\" .\" 1. Redistributions of source code must retain the above copyright .\" notice, this list of conditions and the following disclaimer. .\" .\" 2. Redistributions in binary form must reproduce the above copyright .\" notice, this list of conditions and the following disclaimer in .\" the documentation and/or other materials provided with the .\" distribution. .\" .\" 3. The name "Carnegie Mellon University" must not be used to .\" endorse or promote products derived from this software without .\" prior written permission. For permission or any legal .\" details, please contact .\" Carnegie Mellon University .\" Center for Technology Transfer and Enterprise Creation .\" 4615 Forbes Avenue .\" Suite 302 .\" Pittsburgh, PA 15213 .\" (412) 268-7393, fax: (412) 268-7395 .\" innovation@andrew.cmu.edu .\" .\" 4. Redistributions of any form whatsoever must retain the following .\" acknowledgment: .\" "This product includes software developed by Computing Services .\" at Carnegie Mellon University (http://www.cmu.edu/computing/)." .\" .\" CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO .\" THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY .\" AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE .\" FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES .\" WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN .\" AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING .\" OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. .SH NAME chk_cyrus \- perform a consistency check of the cyrus mailstore .SH SYNOPSIS .B chk_cyrus [ .B \-C .I config-file ] [ .B \-P .I partition ] [ .B \-M .I mailbox ] .SH DESCRIPTION .I Chk_cyrus is used to perform a consistency check on the cyrus datastore, and output a list of files/directories that are expected to exist, but do not. Status messagess are output to stderr, the list of files/directories is output to stdout. This list can be passed to a backup program to aid a partial restoral, for instance. .PP .I Chk_cyrus reads its configuration options out of the .IR imapd.conf (5) file unless specified otherwise by \fB-C\fR. .SH OPTIONS .TP .BI \-C " config-file" Read configuration options from \fIconfig-file\fR. .TP .BI \-P " partition" Run the consistency check for only the given partition. May not be specified with -M. .BI \-M " mailbox" Run the consistency check for only the given mailbox. May not be specified with -P. .SH FILES .TP .B /etc/imapd.conf .SH SEE ALSO .PP \fBimapd.conf(5)\fR, \fBmaster(8)\fR cyrus-imapd-2.5.10/man/cyr_deny.80000644000175000017500000000610213001236020013417 00000000000000.\" -*- nroff -*- .TH CYR_DENY 8 "Project Cyrus" CMU .\" .\" Copyright (c) 1994-2012 Carnegie Mellon University. All rights reserved. .\" .\" Redistribution and use in source and binary forms, with or without .\" modification, are permitted provided that the following conditions .\" are met: .\" .\" 1. Redistributions of source code must retain the above copyright .\" notice, this list of conditions and the following disclaimer. .\" .\" 2. Redistributions in binary form must reproduce the above copyright .\" notice, this list of conditions and the following disclaimer in .\" the documentation and/or other materials provided with the .\" distribution. .\" .\" 3. The name "Carnegie Mellon University" must not be used to .\" endorse or promote products derived from this software without .\" prior written permission. For permission or any legal .\" details, please contact .\" Carnegie Mellon University .\" Center for Technology Transfer and Enterprise Creation .\" 4615 Forbes Avenue .\" Suite 302 .\" Pittsburgh, PA 15213 .\" (412) 268-7393, fax: (412) 268-7395 .\" innovation@andrew.cmu.edu .\" 4. Redistributions of any form whatsoever must retain the following .\" acknowledgment: .\" "This product includes software developed by Computing Services .\" at Carnegie Mellon University (http://www.cmu.edu/computing/)." .\" .\" CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO .\" THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY .\" AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE .\" FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES .\" WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN .\" AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING .\" OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. .SH NAME cyr_deny \- deny users access to Cyrus services .SH SYNOPSIS .B cyr_deny [ .B \-C .I config-file ] [ .B \-s .I services ] [ .B \-m .I message ] .I user .br .B cyr_deny [ .B \-C .I config-file ] .B -a .I user .br .B cyr_deny [ .B \-C .I config-file ] .B -l .SH DESCRIPTION .I cyr_deny is used to deny individual users access to Cyrus services. The first synopsis denies user \fIuser\fP access to Cyrus services, the second synopsis allows access again. \fBcyr_deny\fP works by adding an entry to the Cyrus deny database; the third synopsis lists the entries in the database. .SH OPTIONS .TP .BI \-C " config-file" Read configuration options from \fIconfig-file\fR. .TP .B \-a Allow access to all services for user \fIuser\fP (remove any entry from the deny database). .TP .BI \-s " services" Deny access only to the given \fIservices\fP, which is a comma-separated list of wildcard patterns. The default is "*" which denies access to all services. .TP .B \-l List the entries in the deny database. .TP .BI \-m " message" Provide a message which is sent to the user to explain why access is being denied. A default message is used if none is specified. .SH FILES .TP .B /etc/imapd.conf .SH SEE ALSO .PP \fBimapd.conf(5)\fR cyrus-imapd-2.5.10/man/smtptest.10000644000175000017500000001153113001236020013461 00000000000000.\" -*- nroff -*- .TH SMTPTEST 1 "Project Cyrus" CMU .\" .\" Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. .\" .\" Redistribution and use in source and binary forms, with or without .\" modification, are permitted provided that the following conditions .\" are met: .\" .\" 1. Redistributions of source code must retain the above copyright .\" notice, this list of conditions and the following disclaimer. .\" .\" 2. Redistributions in binary form must reproduce the above copyright .\" notice, this list of conditions and the following disclaimer in .\" the documentation and/or other materials provided with the .\" distribution. .\" .\" 3. The name "Carnegie Mellon University" must not be used to .\" endorse or promote products derived from this software without .\" prior written permission. For permission or any legal .\" details, please contact .\" Carnegie Mellon University .\" Center for Technology Transfer and Enterprise Creation .\" 4615 Forbes Avenue .\" Suite 302 .\" Pittsburgh, PA 15213 .\" (412) 268-7393, fax: (412) 268-7395 .\" innovation@andrew.cmu.edu .\" .\" 4. Redistributions of any form whatsoever must retain the following .\" acknowledgment: .\" "This product includes software developed by Computing Services .\" at Carnegie Mellon University (http://www.cmu.edu/computing/)." .\" .\" CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO .\" THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY .\" AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE .\" FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES .\" WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN .\" AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING .\" OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. .SH NAME smtptest \- interactive SMTP test program .SH SYNOPSIS .B smtptest [ .B \-t .I keyfile ] [ .B \-p .I port ] [ .B \-m .I mechanism ] .br [ .B \-a .I userid ] [ .B \-u .I userid ] [ .B \-k .I num ] [ .B \-l .I num ] .br [ .B \-r .I realm ] [ .B \-f .I file ] [ .B \-n .I num ] [ .B \-s ] [ .B \-c ] .br [ .B \-i ] [ .B \-o \fIoption\fB=\fIvalue\fR ] [ .B \-v ] \fIhostname\fR .SH DESCRIPTION .I smtptest is a utility that allows you to authenticate to a SMTP server and interactively issue commands to it. Once authenticated you may issue any SMTP command by simply typing it in. It is capable of multiple SASL authentication mechanisms and handles encryption layers transparently. This utility is often used for testing the operation of a smtp server. Also those developing SMTP clients find it useful. .PP .SH OPTIONS .TP .BI \-t " keyfile" Enable TLS. \fIkeyfile\fR contains the TLS public and private keys. Specify \fB""\fR to negotiate a TLS encryption layer but not use TLS authentication. .TP .BI \-p " port" Port to connect to. If left off this defaults to \fBsmtp\fR as defined in /etc/services. .TP .BI -m " mechanism" Force smtptest to use \fImechanism\fR for authentication. If not specified the strongest authentication mechanism supported by the server is chosen. .TP .BI -a " userid" Userid to use for authentication; defaults to the current user. This is the userid whose password or credentials will be presented to the server for verification. .TP .BI -u " userid" Userid to use for authorization; defaults to the current user. This is the userid whose identity will be assumed after authentication. \fBNOTE:\fR This is only used with SASL mechanisms that allow proxying (e.g. PLAIN, DIGEST-MD5). .TP .BI -k " num" Minimum protection layer required. .TP .BI -l " num" Maximum protection layer to use (\fB0\fR=none; \fB1=\fRintegrity; etc). For example if you are using the KERBEROS_V4 authentication mechanism specifying \fB0\fR will force smtptest to not use any layer and specifying \fB1\fR will force it to use the integrity layer. By default the maximum supported protection layer will be used. .TP .BI -r " realm" Specify the \fIrealm\fR to use. Certain authentication mechanisms (e.g. DIGEST-MD5) may require one to specify the realm. .TP .BI -f " file" Pipe \fIfile\fR into connection after authentication. .TP .BI -n " num" Number of authentication attempts; default = 1. The client will attempt to do SSL/TLS session reuse and/or fast reauth (e.g. DIGEST-MD5), if possible. .TP .B -s Enable SMTP over SSL (smtps). .TP .B -c Enable challenge prompt callbacks. This will cause the OTP mechanism to ask for the the one-time password instead of the secret pass-phrase (library generates the correct response). .TP .B -i Don't send an initial client response for SASL mechanisms, even if the protocol supports it. .TP \fB-o \fIoption\fB=\fIvalue\fR Set the SASL \fIoption\fR to \fIvalue\fR. .TP .B -v Verbose. Print out more information than usual. .SH SEE ALSO .PP \fBsendmail(8)\fR cyrus-imapd-2.5.10/man/sync_reset.80000644000175000017500000000511013001236020013757 00000000000000.\" -*- nroff -*- .TH SYNC_RESET 8 "Project Cyrus" CMU .\" .\" Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. .\" .\" Redistribution and use in source and binary forms, with or without .\" modification, are permitted provided that the following conditions .\" are met: .\" .\" 1. Redistributions of source code must retain the above copyright .\" notice, this list of conditions and the following disclaimer. .\" .\" 2. Redistributions in binary form must reproduce the above copyright .\" notice, this list of conditions and the following disclaimer in .\" the documentation and/or other materials provided with the .\" distribution. .\" .\" 3. The name "Carnegie Mellon University" must not be used to .\" endorse or promote products derived from this software without .\" prior written permission. For permission or any legal .\" details, please contact .\" Carnegie Mellon University .\" Center for Technology Transfer and Enterprise Creation .\" 4615 Forbes Avenue .\" Suite 302 .\" Pittsburgh, PA 15213 .\" (412) 268-7393, fax: (412) 268-7395 .\" innovation@andrew.cmu.edu .\" .\" 4. Redistributions of any form whatsoever must retain the following .\" acknowledgment: .\" "This product includes software developed by Computing Services .\" at Carnegie Mellon University (http://www.cmu.edu/computing/)." .\" .\" CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO .\" THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY .\" AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE .\" FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES .\" WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN .\" AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING .\" OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. .SH NAME sync_reset \- Account reset utility. DANGER. .SH SYNOPSIS .B sync_reset [ .B \-C .I config-file ] [ .B \-v ] [ .B \-f ] .SH DESCRIPTION .I Sync_reset is a small utility program to destroy user accounts on a system. The only safeguard which is in place is the obligary force option. .SH OPTIONS .TP .BI \-C " config-file" Read configuration options from \fIconfig-file\fR. .TP .BI \-v Verbose mode. .TP .BI \-f Force operation. Without this flag \fIsync_reset\fR just bails out with an error. Principally here to try and prevent accidents with command autorepeat. .SH FILES .TP .B /etc/imapd.conf .SH SEE ALSO .PP \fBsync_client(8)\fR .SH AUTHORS David Carter (dpc22@cam.ac.uk), Ken Murchison (ken@oceana.com) cyrus-imapd-2.5.10/man/imapd.conf.50000644000175000017500000024607713001246643013653 00000000000000.\" -*- nroff -*- .\" auto-generated by config2man 1.6 .\" -*- nroff -*- .TH IMAPD.CONF 5 "Project Cyrus" CMU .\" .\" Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. .\" .\" Redistribution and use in source and binary forms, with or without .\" modification, are permitted provided that the following conditions .\" are met: .\" .\" 1. Redistributions of source code must retain the above copyright .\" notice, this list of conditions and the following disclaimer. .\" .\" 2. Redistributions in binary form must reproduce the above copyright .\" notice, this list of conditions and the following disclaimer in .\" the documentation and/or other materials provided with the .\" distribution. .\" .\" 3. The name "Carnegie Mellon University" must not be used to .\" endorse or promote products derived from this software without .\" prior written permission. For permission or any legal .\" details, please contact .\" Carnegie Mellon University .\" Center for Technology Transfer and Enterprise Creation .\" 4615 Forbes Avenue .\" Suite 302 .\" Pittsburgh, PA 15213 .\" (412) 268-7393, fax: (412) 268-7395 .\" innovation@andrew.cmu.edu .\" .\" 4. Redistributions of any form whatsoever must retain the following .\" acknowledgment: .\" "This product includes software developed by Computing Services .\" at Carnegie Mellon University (http://www.cmu.edu/computing/)." .\" .\" CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO .\" THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY .\" AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE .\" FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES .\" WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN .\" AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING .\" OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. .SH NAME imapd.conf \- IMAP configuration file .SH DESCRIPTION \fB/etc/imapd.conf\fR is the configuration file for the Cyrus IMAP server. It defines local parameters for IMAP. .PP Each line of the \fB/etc/imapd.conf\fR file has the form .IP \fIoption\fR: \fIvalue\fR .PP where \fIoption\fR is the name of the configuration option being set and \fIvalue\fR is the value that the configuration option is being set to. .PP Although there is no limit to the length of a line, a ``\\'' (backslash) character may be used as the last character on a line to force it to continue on the next one. No additional whitespace is inserted before or after the ``\\''. Note that a line that is split using ``\\'' character(s) is still considered a single line. For example .IP \fIoption\fR:\\ .br .in +1 \fIvalue\fR1 \fIvalue\fR2 \\ .br .in +1 \fIvalue\fR3 .PP is equivalent to .IP \fIoption\fR: \fIvalue\fR1 \fIvalue\fR2 \fIvalue\fR3 .PP Blank lines and lines beginning with ``#'' are ignored. .PP For boolean and enumerated options, the values ``yes'', ``on'', ``t'', ``true'' and ``1'' turn the option on, the values ``no'', ``off'', ``f'', ``false'' and ``0'' turn the option off. .SH FIELD DESCRIPTIONS .PP The sections below detail options that can be placed in the \fB/etc/imapd.conf\fR file, and show each option's default value. Some options have no default value, these are listed with ``''. Some options default to the empty string, these are listed with ``''. .IP "\fBaddressbookprefix:\fR #addressbooks" 5 .RS 5 The prefix for the addressbook mailboxes hierarchies. The hierarchy delimiter will be automatically appended. The public addressbook hierarchy will be at the toplevel of the shared namespace. A user's personal calendar hierarchy will be a child of their Inbox. .RE .IP "\fBadmins:\fR " 5 .RS 5 The list of userids with administrative rights. Separate each userid with a space. Sites using Kerberos authentication may use separate "admin" instances. .PP Note that accounts used by users should not be administrators. Administrative accounts should not receive mail. That is, if user "jbRo" is a user reading mail, he should not also be in the admins line. Some problems may occur otherwise, most notably the ability of administrators to create top-level mailboxes visible to users, but not writable by users. .RE .IP "\fBafspts_localrealms:\fR " 5 .RS 5 The list of realms which are to be treated as local, and thus stripped during identifier canonicalization (for the AFSPTS ptloader module). This is different from loginrealms in that it occurs later in the authorization process (as the user id is canonified for PTS lookup) .RE .IP "\fBafspts_mycell:\fR " 5 Cell to use for AFS PTS lookups. Defaults to the local cell. .IP "\fBallowallsubscribe:\fR 0" 5 .RS 5 Allow subscription to nonexistent mailboxes. This option is typically used on backend servers in a Murder so that users can subscribe to mailboxes that don't reside on their "home" server. This option can also be used as a workaround for IMAP clients which don't play well with nonexistent or unselectable mailboxes (e.g., Microsoft Outlook). .RE .IP "\fBallowanonymouslogin:\fR 0" 5 .RS 5 Permit logins by the user "anonymous" using any password. Also allows use of the SASL ANONYMOUS mechanism. .RE .IP "\fBallowapop:\fR 1" 5 .RS 5 Allow use of the POP3 APOP authentication command. .PP Note that this command requires that SASL is compiled with APOP support, that the plaintext passwords are available in a SASL auxprop backend (e.g., sasldb), and that the system can provide enough entropy (e.g., from /dev/urandom) to create a challenge in the banner. .RE .IP "\fBallownewnews:\fR 0" 5 .RS 5 Allow use of the NNTP NEWNEWS command. .PP Note that this is a very expensive command and should only be enabled when absolutely necessary. .RE .IP "\fBallowplaintext:\fR 0" 5 .RS 5 If enabled, allows the use of cleartext passwords on the wire. .PP By default, the use of cleartext passwords requires a TLS/SSL encryption layer to be negotiated prior to any cleartext authentication mechanisms being advertised or allowed. To require a TLS/SSL encryption layer to be negotiated prior to ANY authentication, see the \fItls_required\fR option. .RE .IP "\fBallowusermoves:\fR 0" 5 .RS 5 Allow moving user accounts (with associated meta-data) via RENAME or XFER. .PP Note that measures should be taken to make sure that the user being moved is not logged in, and cannot login during the move. Failure to do so may result in the user's meta-data (seen state, subscriptions, etc) being corrupted or out of date. .RE .IP "\fBaltnamespace:\fR 0" 5 .RS 5 Use the alternate IMAP namespace, where personal folders reside at the same level in the hierarchy as INBOX. .PP This option ONLY applies where interaction takes place with the client/user. Currently this is limited to the IMAP protocol (imapd) and Sieve scripts (lmtpd). This option does NOT apply to admin tools such as cyradm (admins ONLY), reconstruct, quota, etc., NOR does it affect LMTP delivery of messages directly to mailboxes via plus-addressing. .RE .IP "\fBannotation_db:\fR twoskip" 5 The cyrusdb backend to use for mailbox annotations. Allowed values: \fIberkeley\fR, \fIberkeley-hash\fR, \fIskiplist\fR, \fItwoskip\fR .IP "\fBannotation_db_path:\fR " 5 .RS 5 The absolute path to the annotations db file. If not specified, will be confdir/annotations.db .RE .IP "\fBanyoneuseracl:\fR 1" 5 .RS 5 Should non-admin users be allowed to set ACLs for the 'anyone' user on their mailboxes? In a large organization this can cause support problems, but it's enabled by default. .RE .IP "\fBannotation_allow_undefined:\fR 0" 5 .RS 5 Allow clients to store values for entries which are not * defined either by Cyrus or in the annotations_definitions * file. .RE .IP "\fBannotation_definitions:\fR " 5 .RS 5 File containing external (third-party) annotation definitions. .PP Each line of the file specifies the properties of an annotation and has the following form: .IP \fIname\fR, \fIscope\fR, \fIattrib-type\fR, \fIproxy-type\fR, \fIattrib-names\fR, \fIacl\fR .\" .IP \fIname\fR 5 is the hierarchical name as in RFC 5257 or RFC 5464 (in the latter case, without the leading \fB/shared\fR or \fB/private\fR). For example, /vendor/acme/blurdybloop. .\" .IP \fIscope\fR 5 specifies whether the annotation is for the \fBserver\fR, a \fBmailbox\fR, or a \fBmessage\fR. .\" .IP \fIattrib-type\fR 5 .RS 5 specifies the attribute data type, which is used only to check the string value passed by clients when setting annotations. The \fIattrib-type\fR is one of: .\" .IP \fBstring\fR 5 any value is accepted. .\" .IP \fBcontent-type\fR 5 this obsolete data type, which was useful for early drafts of the standard, is accepted but silently translated to \fBstring\fR. .\" .IP \fBboolean\fR 5 only the strings "true" or "false" are accepted. Checking is case-insensitive but the value is forced to lowercase. .\" .IP \fBint\fR 5 integers are accepted. .\" .IP \fBuint\fR 5 non-negative integers are accepted. .\" .RE .\" .IP \fIproxy-type\fR 5 specifies whether this attribute is for the \fBbackend\fR or \fBproxy\fR servers or both (\fBproxy_and_backend\fR) .\" .IP \fIattrib-names\fR 5 is the space-separated list of available attributes for the annotation. Possible attribute names are \fBvalue.shared\fR, \fBvalue.priv\fR, and \fBvalue\fR (which permits both \fBvalue.priv\fR and \fBvalue.shared\fR). The attribute names \fBsize\fR, \fBsize.shared\fR, and \fBsize.priv\fR are accepted but ignored; these attributes are automatically provided by the server if the corresponding \fBvalue\fR attribute is specified. Some obsolete attributes, which were defined early drafts of the standard, are accepted and ignored with a warning. .\" .IP \fIextra-permissions\fR 5 is the extra ACL permission bits required for setting this annotation, in standard IMAP ACL permission bit string format. Note that this is in addition to the permission bits specified in RFC 5257 and RFC 5464, so leaving this field empty is harmless. Note also that there is no way to specify that an annotation can only be set by an admin user; in particular the \fBa\fP permission bit does not achieve this. .PP Blank lines and lines beginning with ``#'' are ignored. .RE .IP "\fBannotation_callout:\fR " 5 .RS 5 The pathname of a callout to be used to automatically add annotations or flags to a message when it is appended to a mailbox. The path can be either an executable (including a script), or a UNIX domain socket. .RE .IP "\fBauditlog:\fR 0" 5 .RS 5 Should cyrus output log entries for every action taken on a message file or mailboxes list entry? It's noisy so disabled by default, but can be very useful for tracking down what happened if things look strange .RE .IP "\fBauth_mech:\fR unix" 5 The authorization mechanism to use. Allowed values: \fIunix\fR, \fIpts\fR, \fIkrb\fR, \fIkrb5\fR .IP "\fBautocreateinboxfolders:\fR " 5 Deprecated in favor of \fIautocreate_inbox_folders\fR. .IP "\fBautocreatequota:\fR 0" 5 Deprecated in favor of \fIautocreate_quota\fR. .IP "\fBautocreatequotamsg:\fR -1" 5 Deprecated in favor of \fIautocreate_quota_messages\fR. .IP "\fBautosievefolders:\fR " 5 Deprecated in favor of \fIautocreate_sieve_folders\fR. .IP "\fBgenerate_compiled_sieve_script:\fR " 5 Deprecated in favor of \fIautocreate_sieve_script_compile\fR. .IP "\fBautocreate_sieve_compiled_script:\fR " 5 Deprecated in favor of \fIautocreate_sieve_script_compiled\fR. .IP "\fBautosubscribeinboxfolders:\fR " 5 Deprecated in favor of \fIautocreate_subscribe_folders\fR. .IP "\fBautosubscribesharedfolders:\fR " 5 Deprecated in favor of \fIautocreate_subscribe_sharedfolders\fR. .IP "\fBautosubscribe_all_sharedfolders:\fR 0" 5 Deprecated in favor of \fIautocreate_subscribe_sharedfolders_all\fR. .IP "\fBautocreate_inbox_folders:\fR " 5 .RS 5 If a user does not have an INBOX already, and the INBOX is to be created, create the list of folders in this setting as well. .PP INBOX folders are created under both the following conditions: .\" .IP 1. The user logins via the IMAP or the POP3 protocol. \fIautocreate_quota\fR option must have a value of zero or greater. .IP 2. A message arrives for the user through the \fIlmtpd(8)\fR. \fIautocreate_post\fR option must be enabled. .PP \fIautocreate_inbox_folders\fR is a list of INBOX's subfolders separated by a "|", that are automatically created by the server under the previous two scenarios. Leading and trailing whitespace is stripped, so "Junk | Trash" results in two folders: "Junk" and "Trash". .RE .IP "\fBautocreate_post:\fR 0" 5 .RS 5 If enabled, when \fIlmtpd(8)\fR receives an incoming mail for an INBOX that does not exist, then the INBOX is automatically created by \fIlmtpd(8)\fR and delivery of the message continues. .RE .IP "\fBautocreate_quota:\fR -1" 5 .RS 5 If set to a value of zero or higher, users have their INBOX folders created upon a successful login event or upon \fIlmtpd(8)\fR message delivery if \fIautocreate_post\fR is enabled, provided their INBOX did not yet already exist. .PP The user's quota is set to the value if it is greater than zero, otherwise the user has unlimited quota. .PP Note that quota is specified in kilobytes. .RE .IP "\fBautocreate_quota_messages:\fR -1" 5 .RS 5 If set to a value of zero or higher, users who have their INBOX folders created upon a successful login event (see \fIautocreate_quota\fR), or upon \fIlmtpd(8)\fR message delivery if \fIautocreate_post\fR is enabled, receive the message quota configured in this option. .PP The default of -1 disables assigning message quota. .PP For consistency with \fIautocreate_quota\fR, a value of zero is treated as unlimited message quota, rather than a message quota of zero. .RE .IP "\fBautocreate_sieve_folders:\fR " 5 .RS 5 A "|" separated list of subfolders of INBOX that will be automatically created, if requested by a sieve filter, through the "fileinto" action. The default is to create no folders automatically. .PP Leading and trailing whitespace is stripped from each folder, so a setting of "Junk | Trash" will create two folders: "Junk" and "Trash". .RE .IP "\fBautocreate_sieve_script:\fR " 5 .RS 5 The full path of a file that contains a sieve script. This script automatically becomes a user's initial default sieve filter script. .PP When this option is not defined, no default sieve filter is created. The file must be readable by the Cyrus daemon. .RE .IP "\fBautocreate_sieve_script_compile:\fR 0" 5 .RS 5 If set to yes and no compiled sieve script file exists, the sieve script which is compiled on the fly will be saved in the file name that autocreate_sieve_compiledscript option points to. In order a compiled script to be generated, autocreate_sieve_script and autocreate_sieve_compiledscript must have valid values .RE .IP "\fBautocreate_sieve_script_compiled:\fR " 5 .RS 5 The full path of a file that contains a compiled in bytecode sieve script. This script automatically becomes a user's initial default sieve filter script. If this option is not specified, or the filename doesn't exist then the script defined by autocreate_sieve_script is compiled on the fly and installed as the user's default sieve script .RE .IP "\fBautocreate_subscribe_folders:\fR " 5 .RS 5 A list of folder names, separated by "|", that the users get automatically subscribed to, when their INBOX is created. These folder names must have been included in the autocreateinboxfolders option of the imapd.conf. .RE .IP "\fBautocreate_subscribe_sharedfolders:\fR " 5 .RS 5 A list of shared folders (bulletin boards), separated by "|", that the users get automatically subscribed to, after their INBOX is created. The shared folder must have been created and the user must have the required permissions to get subscribed to it. Otherwise, subscribing to the shared folder fails. .RE .IP "\fBautocreate_subscribe_sharedfolders_all:\fR 0" 5 .RS 5 If set to yes, the user is automatically subscribed to all shared folders, one has permission to subscribe to. .RE .IP "\fBautocreate_users:\fR anyone" 5 .RS 5 A space separated list of users and/or groups that are allowed their INBOX to be automatically created. .RE .IP "\fBberkeley_cachesize:\fR 512" 5 .RS 5 Size (in kilobytes) of the shared memory buffer pool (cache) used by the berkeley environment. The minimum allowed value is 20. The maximum allowed value is 4194303 (4GB). .RE .IP "\fBberkeley_locks_max:\fR 50000" 5 .RS 5 Maximum number of locks to be held or requested in the berkeley environment. .RE .IP "\fBberkeley_txns_max:\fR 100" 5 .RS 5 Maximum number of transactions to be supported in the berkeley environment. .RE .IP "\fBboundary_limit:\fR 1000" 5 .RS 5 messages are parsed recursively and a deep enough MIME structure can cause a stack overflow. Do not parse deeper than this many layers of MIME structure. The default of 1000 is much higher than any sane message should have. .RE .IP "\fBcaldav_allowscheduling:\fR on" 5 .RS 5 Enable calendar scheduling operations. If set to "apple", the server will emulate Apple CalendarServer behavior as closely as possible. Allowed values: \fIoff\fR, \fIon\fR, \fIapple\fR .RE .IP "\fBcaldav_maxdatetime:\fR 20380119T031407Z" 5 .RS 5 The latest date and time accepted by the server (ISO format). This value is also used for expanding non-terminating recurrence rules. .PP Note that increasing this value will require the DAV databases for calendars to be reconstructed with the \fBdav_reconstruct\fR utility in order to see its effect on serer-side time-based queries. .RE .IP "\fBcaldav_mindatetime:\fR 19011213T204552Z" 5 The earliest date and time accepted by the server (ISO format). .IP "\fBcaldav_realm:\fR " 5 .RS 5 The realm to present for HTTP authentication of CalDAV resources. If not set (the default), the value of the "servername" option will be used. .RE .IP "\fBcalendarprefix:\fR #calendars" 5 .RS 5 The prefix for the calendar mailboxes hierarchies. The hierarchy delimiter will be automatically appended. The public calendar hierarchy will be at the toplevel of the shared namespace. A user's personal calendar hierarchy will be a child of their Inbox. .RE .IP "\fBcalendar_user_address_set:\fR " 5 .RS 5 Space-separated list of domains corresponding to calendar user addresses for which the server is responsible. If not set (the default), the value of the "servername" option will be used. .RE .IP "\fBcarddav_realm:\fR " 5 .RS 5 The realm to present for HTTP authentication of CardDAV resources. If not set (the default), the value of the "servername" option will be used. .RE .IP "\fBchatty:\fR 0" 5 .RS 5 If yes, syslog tags and commands for every IMAP command, mailboxes for every lmtp connection, every POP3 command, etc .RE .IP "\fBclient_timeout:\fR 10" 5 .RS 5 Number of seconds to wait before returning a timeout failure when performing a client connection (e.g., in a murder environment) .RE .IP "\fBcommandmintimer:\fR " 5 .RS 5 Time in seconds. Any imap command that takes longer than this time is logged. .RE .IP "\fBconfigdirectory:\fR " 5 .RS 5 The pathname of the IMAP configuration directory. This field is required. .RE .IP "\fBcreateonpost:\fR 0" 5 Deprecated in favor of \fIautocreate_post\fR. .IP "\fBdav_realm:\fR " 5 .RS 5 The realm to present for HTTP authentication of generic DAV resources (principals). If not set (the default), the value of the "servername" option will be used. .RE .IP "\fBdebug_command:\fR " 5 .RS 5 Debug command to be used by processes started with -D option. The string is a C format string that gets 3 options: the first is the name of the executable (without path). The second is the pid (integer) and the third is the service ID. Example: /usr/local/bin/gdb /usr/cyrus/bin/%s %d .RE .IP "\fBdefaultacl:\fR anyone lrs" 5 .RS 5 The Access Control List (ACL) placed on a newly-created (non-user) mailbox that does not have a parent mailbox. .RE .IP "\fBdefaultdomain:\fR " 5 The default domain for virtual domain support .IP "\fBdefaultpartition:\fR " 5 .RS 5 The partition name used by default for new mailboxes. If not specified, the partition with the most free space will be used for new mailboxes. .PP Note that the partition specified by this option must also be specified as \fIpartition-name\fR, where you substitute 'name' for the alphanumeric string you set \fIdefaultpartition\fR to. .RE .IP "\fBdefaultserver:\fR " 5 .RS 5 The backend server name used by default for new mailboxes. If not specified, the server with the most free space will be used for new mailboxes. .RE .IP "\fBdeletedprefix:\fR DELETED" 5 .RS 5 If "delete_mode" set to be "delayed", the prefix for the deleted mailboxes hierarchy. The hierarchy delimiter will be automatically appended. .RE .IP "\fBdelete_mode:\fR delayed" 5 .RS 5 The manner in which mailboxes are deleted. "immediate" mode is the default behavior in which mailboxes are removed immediately. In "delayed" mode, mailboxes are renamed to a special hiearchy defined by the "deletedprefix" option to be removed later by cyr_expire. Allowed values: \fIimmediate\fR, \fIdelayed\fR .RE .IP "\fBdeleteright:\fR c" 5 .RS 5 Deprecated - only used for backwards compatibility with existing installations. Lists the old RFC 2086 right which was used to grant the user the ability to delete a mailbox. If a user has this right, they will automatically be given the new 'x' right. .RE .IP "\fBdisable_user_namespace:\fR 0" 5 .RS 5 Preclude list command on user namespace. If set to 'yes', the LIST response will never include any other user's mailbox. Admin users will always see all mailboxes. The default is 'no' .RE .IP "\fBdisable_shared_namespace:\fR 0" 5 .RS 5 Preclude list command on shared namespace. If set to 'yes', the LIST response will never include any non-user mailboxes. Admin users will always see all mailboxes. The default is 'no' .RE .IP "\fBdisconnect_on_vanished_mailbox:\fR 0" 5 .RS 5 If enabled, IMAP/POP3/NNTP clients will be disconnected by the server if the currently selected mailbox is (re)moved by another session. Otherwise, the missing mailbox is treated as empty while in use by the client. .RE .IP "\fBischedule_dkim_domain:\fR " 5 The domain to be reported as doing iSchedule DKIM signing. .IP "\fBischedule_dkim_key_file:\fR " 5 File containing the private key for iSchedule DKIM signing. .IP "\fBischedule_dkim_selector:\fR " 5 .RS 5 Name of the selector subdividing the domain namespace. This specifies the actual key used for iSchedule DKIM signing within the domain. .RE .IP "\fBduplicate_db:\fR twoskip" 5 .RS 5 The cyrusdb backend to use for the duplicate delivery suppression and sieve. Allowed values: \fIberkeley\fR, \fIberkeley-nosync\fR, \fIberkeley-hash\fR, \fIberkeley-hash-nosync\fR, \fIskiplist\fR, \fIsql\fR, \fItwoskip\fR .RE .IP "\fBduplicate_db_path:\fR " 5 .RS 5 The absolute path to the duplicate db file. If not specified, will be confdir/deliver.db .RE .IP "\fBduplicatesuppression:\fR 1" 5 .RS 5 If enabled, lmtpd will suppress delivery of a message to a mailbox if a message with the same message-id (or resent-message-id) is recorded as having already been delivered to the mailbox. Records the mailbox and message-id/resent-message-id of all successful deliveries. .RE .IP "\fBevent_content_inclusion_mode:\fR standard" 5 .RS 5 The mode in which message content may be included with MessageAppend and MessageNew. "standard" mode is the default behavior in which message is included up to a size with the notification. In "message" mode, the message is included and may be truncated to a size. In "header" mode, it includes headers truncated to a size. In "body" mode, it includes body truncated to a size. In "headerbody" mode, it includes full headers and body truncated to a size Allowed values: \fIstandard\fR, \fImessage\fR, \fIheader\fR, \fIbody\fR, \fIheaderbody\fR .RE .IP "\fBevent_content_size:\fR 0" 5 .RS 5 Truncate the message content that may be included with MessageAppend and MessageNew. Set 0 to include the entire message itself .RE .IP "\fBevent_exclude_flags:\fR " 5 Don't send event notification for given IMAP flag(s) .IP "\fBevent_exclude_specialuse:\fR \\Junk" 5 .RS 5 Don't send event notification for folder with given special-use attributes. Set ALL for any folder .RE .IP "\fBevent_extra_params:\fR timestamp" 5 Space-separated list of extra parameters to add to any appropriated event. Allowed values: \fIbodyStructure\fR, \fIclientAddress\fR, \fIdiskUsed\fR, \fIflagNames\fR, \fImessageContent\fR, \fImessageSize\fR, \fImessages\fR, \fImodseq\fR, \fIservice\fR, \fItimestamp\fR, \fIuidnext\fR, \fIvnd.cmu.midset\fR, \fIvnd.cmu.unseenMessages\fR, \fIvnd.cmu.envelope\fR, \fIvnd.cmu.sessionId\fR, \fIvnd.cmu.mbtype\fR, \fIvnd.cmu.davFilename\fR, \fIvnd.cmu.davUid\fR .IP "\fBevent_groups:\fR message mailbox" 5 Space-separated list of groups of related events to turn on notification Allowed values: \fImessage\fR, \fIquota\fR, \fIflags\fR, \fIaccess\fR, \fImailbox\fR, \fIsubscription\fR .IP "\fBevent_notifier:\fR " 5 .RS 5 Notifyd(8) method to use for "EVENT" notifications which are based on the RFC 5423. If not set, "EVENT" notifications are disabled. .RE .IP "\fBexpunge_mode:\fR delayed" 5 .RS 5 The mode in which messages (and their corresponding cache entries) are expunged. "default" mode is the default behavior in which the message files are purged at the time of the EXPUNGE, but index and cache records are retained to facilitate QRESYNC. In "delayed" mode, the message files are also retained, allowing unexpunge to rescue them. In "immediate" mode, both the message files and the index records are removed as soon as possible. In all cases, nothing will be finally purged until all other processes have closed the mailbox to ensure they never see data disappear under them. In "default" or "delayed" mode, a later run of "cyr_expire" will clean out the retained records (and possibly message files). This reduces the amount of I/O that takes place at the time of EXPUNGE and should result in greater responsiveness for the client, especially when expunging a large number of messages. Allowed values: \fIdefault\fR, \fIimmediate\fR, \fIdelayed\fR .RE .IP "\fBfailedloginpause:\fR 3" 5 Number of seconds to pause after a failed login. .IP "\fBflushseenstate:\fR 1" 5 Deprecated. No longer used .IP "\fBfoolstupidclients:\fR 0" 5 .RS 5 If enabled, only list the personal namespace when a LIST "*" is performed (it changes the request to a LIST "INBOX*"). .RE .IP "\fBforce_sasl_client_mech:\fR " 5 .RS 5 Force preference of a given SASL mechanism for client side operations (e.g., murder environments). This is separate from (and overridden by) the ability to use the _mechs option to set preferred mechanisms for a specific host .RE .IP "\fBfulldirhash:\fR 0" 5 .RS 5 If enabled, uses an improved directory hashing scheme which hashes on the entire username instead of using just the first letter as the hash. This changes hash algorithm used for quota and user directories and if \fIhashimapspool\fR is enabled, the entire mail spool. .PP Note that this option CANNOT be changed on a live system. The server must be quiesced and then the directories moved with the \fBrehash\fR utility. .RE .IP "\fBhashimapspool:\fR 0" 5 .RS 5 If enabled, the partitions will also be hashed, in addition to the hashing done on configuration directories. This is recommended if one partition has a very bushy mailbox tree. .RE .IP "\fBdebug:\fR 0" 5 If enabled, allow syslog() to pass LOG_DEBUG messages. .IP "\fBhostname_mechs:\fR " 5 .RS 5 Force a particular list of SASL mechanisms to be used when authenticating to the backend server hostname (where hostname is the short hostname of the server in question). If it is not specified it will query the server for available mechanisms and pick one to use. - Cyrus Murder .RE .IP "\fBhostname_password:\fR " 5 .RS 5 The password to use for authentication to the backend server hostname (where hostname is the short hostname of the server) - Cyrus Murder .RE .IP "\fBhttpallowcompress:\fR 1" 5 .RS 5 If enabled, the server will compress response payloads if the client indicates that it can accept them. Note that the compressed data will appear in telemetry logs, leaving only the response headers as human-readable. .RE .IP "\fBhttpallowcors:\fR " 5 .RS 5 A wildmat pattern specifying a list of origin URIs ( scheme "://" host [ ":" port ] ) that are allowed to make Cross-Origin Resource Sharing (CORS) requests on the server. By default, CORS requests are disabled. .PP Note that the scheme and host should both be lowercase, the port should be omitted if using the default for the scheme (80 for http, 443 for https), and there should be no trailing '/' (e.g.: "http://www.example.com:8080", "https://example.org"). .RE .IP "\fBhttpallowtrace:\fR 0" 5 .RS 5 Allow use of the TRACE method. .PP Note that sensitive data might be disclosed by the response. .RE .IP "\fBhttpallowedurls:\fR " 5 .RS 5 Space-separated list of relative URLs (paths) rooted at "httpdocroot" (see below) to be served by httpd. If set, this option will limit served static content to only those paths specified (returning "404 Not Found" to any other client requested URLs). Otherwise, httpd will serve any content found in "httpdocroot". .PP Note that any path specified by "rss_feedlist_template" is an exception to this rule. .RE .IP "\fBhttpcontentmd5:\fR 0" 5 .RS 5 If enabled, HTTP responses will include a Content-MD5 header for the purpose of providing an end-to-end message integrity check (MIC) of the payload body. Note that enabling this option will use additional CPU to generate the MD5 digest, which may be ignored by clients anyways. .RE .IP "\fBhttpdocroot:\fR " 5 .RS 5 If set, http will serve the static content (html/text/jpeg/gif files, etc) rooted at this directory. Otherwise, httpd will not serve any static content. .RE .IP "\fBhttpkeepalive:\fR 20" 5 .RS 5 Set the length of the HTTP server's keepalive heartbeat in seconds. The default is 20. The minimum value is 0, which will disable the keepalive heartbeat. When enabled, if a request takes longer than \fIhttpkeepalive\fR seconds to process, the server will send the client provisional responses every \fIhttpkeepalive\fR seconds until the final response can be sent .RE .IP "\fBhttpmodules:\fR " 5 .RS 5 Space-separated list of HTTP modules that will be enabled in httpd(8). This option has no effect on modules that are disabled at compile time due to missing dependencies (e.g. libical). Allowed values: \fIcaldav\fR, \fIcarddav\fR, \fIdomainkey\fR, \fIischedule\fR, \fIrss\fR, \fItimezone\fR .RE .IP "\fBhttpprettytelemetry:\fR 0" 5 .RS 5 If enabled, HTTP response payloads including server-generated markup languages (HTML, XML) will utilize line breaks and indentation to promote better human-readability in telemetry logs. Note that enabling this option will increase the amount of data sent across the wire. .RE .IP "\fBhttptimeout:\fR 5" 5 .RS 5 Set the length of the HTTP server's inactivity autologout timer, in minutes. The default is 5. The minimum value is 0, which will disable persistent connections. .RE .IP "\fBidlesocket:\fR {configdirectory}/socket/idle" 5 Unix domain socket that idled listens on. .IP "\fBignorereference:\fR 0" 5 .RS 5 For backwards compatibility with Cyrus 1.5.10 and earlier -- ignore the reference argument in LIST or LSUB commands. .RE .IP "\fBimapidlepoll:\fR 60" 5 .RS 5 The interval (in seconds) for polling for mailbox changes and ALERTs while running the IDLE command. This option is used when idled is not enabled or cannot be contacted. The minimum value is 1. A value of 0 will disable IDLE. .RE .IP "\fBimapidresponse:\fR 1" 5 .RS 5 If enabled, the server responds to an ID command with a parameter list containing: version, vendor, support-url, os, os-version, command, arguments, environment. Otherwise the server returns NIL. .RE .IP "\fBimapmagicplus:\fR 0" 5 .RS 5 Only list a restricted set of mailboxes via IMAP by using userid+namespace syntax as the authentication/authorization id. Using userid+ (with an empty namespace) will list only subscribed mailboxes. .RE .IP "\fBimplicit_owner_rights:\fR lkxa" 5 The implicit Access Control List (ACL) for the owner of a mailbox. .IP "\fB@include:\fR " 5 .RS 5 Directive which includes the specified file as part of the configuration. If the path to the file is not absolute, CYRUS_PATH is prepended. .RE .IP "\fBimproved_mboxlist_sort:\fR 0" 5 .RS 5 If enabled, a special comparator will be used which will correctly sort mailbox names that contain characters such as ' ' and '-'. .PP Note that this option SHOULD NOT be changed on a live system. The mailboxes database should be dumped (ctl_mboxlist) before the option is changed, removed, and then undumped after changing the option. When not using flat files for the subscriptions databases the same has to be done (cyr_dbtool) for each subscription database See improved_mboxlist_sort.html. .RE .IP "\fBinternaldate_heuristic:\fR standard" 5 .RS 5 Mechanism to determine email internaldates on delivery/reconstruct. "standard" uses time() when delivering a message, mtime on reconstruct. "receivedheader" looks at the top most Received header or time/mtime otherwise Allowed values: \fIstandard\fR, \fIreceivedheader\fR .RE .IP "\fBiolog:\fR 0" 5 Should cyrus output I/O log entries .IP "\fBldap_authz:\fR " 5 SASL authorization ID for the LDAP server .IP "\fBldap_base:\fR " 5 Contains the LDAP base dn for the LDAP ptloader module .IP "\fBldap_bind_dn:\fR " 5 .RS 5 Bind DN for the connection to the LDAP server (simple bind). Do not use for anonymous simple binds .RE .IP "\fBldap_deref:\fR never" 5 Specify how aliases dereferencing is handled during search. Allowed values: \fIsearch\fR, \fIfind\fR, \fIalways\fR, \fInever\fR .IP "\fBldap_domain_base_dn:\fR " 5 Base DN to search for domain name spaces. .IP "\fBldap_domain_filter:\fR (&(objectclass=domainrelatedobject)(associateddomain=%s))" 5 Filter to use searching for domains .IP "\fBldap_domain_name_attribute:\fR associateddomain" 5 The attribute name for domains. .IP "\fBldap_domain_scope:\fR sub" 5 Search scope Allowed values: \fIsub\fR, \fIone\fR, \fIbase\fR .IP "\fBldap_domain_result_attribute:\fR inetdomainbasedn" 5 Result attribute .IP "\fBldap_filter:\fR (uid=%u)" 5 .RS 5 Specify a filter that searches user identifiers. The following tokens can be used in the filter string: %% = % %u = user %U = user portion of %u (%U = test when %u = test@domain.tld) %d = domain portion of %u if available (%d = domain.tld when %u = %test@domain.tld), otherwise same as %r %D = user dn. (use when ldap_member_method: filter) %1-9 = domain tokens (%1 = tld, %2 = domain when %d = domain.tld) ldap_filter is not used when ldap_sasl is enabled. .RE .IP "\fBldap_group_base:\fR " 5 LDAP base dn for ldap_group_filter. .IP "\fBldap_group_filter:\fR (cn=%u)" 5 .RS 5 Specify a filter that searches for group identifiers. See ldap_filter for more options. .RE .IP "\fBldap_group_scope:\fR sub" 5 Specify search scope for ldap_group_filter. Allowed values: \fIsub\fR, \fIone\fR, \fIbase\fR .IP "\fBldap_id:\fR " 5 SASL authentication ID for the LDAP server .IP "\fBldap_mech:\fR " 5 SASL mechanism for LDAP authentication .IP "\fBldap_user_attribute:\fR " 5 Specify LDAP attribute to use as canonical user id .IP "\fBldap_member_attribute:\fR " 5 See ldap_member_method. .IP "\fBldap_member_base:\fR " 5 LDAP base dn for ldap_member_filter. .IP "\fBldap_member_filter:\fR (member=%D)" 5 .RS 5 Specify a filter for "ldap_member_method: filter". See ldap_filter for more options. .RE .IP "\fBldap_member_method:\fR attribute" 5 .RS 5 Specify a group method. The "attribute" method retrieves groups from a multi-valued attribute specified in ldap_member_attribute. The "filter" method uses a filter, specified by ldap_member_filter, to find groups; ldap_member_attribute is a single-value attribute group name. Allowed values: \fIattribute\fR, \fIfilter\fR .RE .IP "\fBldap_member_scope:\fR sub" 5 Specify search scope for ldap_member_filter. Allowed values: \fIsub\fR, \fIone\fR, \fIbase\fR .IP "\fBldap_password:\fR " 5 .RS 5 Password for the connection to the LDAP server (SASL and simple bind). Do not use for anonymous simple binds .RE .IP "\fBldap_realm:\fR " 5 SASL realm for LDAP authentication .IP "\fBldap_referrals:\fR 0" 5 Specify whether or not the client should follow referrals. .IP "\fBldap_restart:\fR 1" 5 .RS 5 Specify whether or not LDAP I/O operations are automatically restarted if they abort prematurely. .RE .IP "\fBldap_sasl:\fR 1" 5 Use SASL for LDAP binds in the LDAP PTS module. .IP "\fBldap_sasl_authc:\fR " 5 Deprecated. Use ldap_id .IP "\fBldap_sasl_authz:\fR " 5 Deprecated. Use ldap_authz .IP "\fBldap_sasl_mech:\fR " 5 Deprecated. Use ldap_mech .IP "\fBldap_sasl_password:\fR " 5 Deprecated. User ldap_password .IP "\fBldap_sasl_realm:\fR " 5 Deprecated. Use ldap_realm .IP "\fBldap_scope:\fR sub" 5 Specify search scope. Allowed values: \fIsub\fR, \fIone\fR, \fIbase\fR .IP "\fBldap_servers:\fR ldap://localhost/" 5 Deprecated. Use ldap_uri .IP "\fBldap_size_limit:\fR 1" 5 Specify a number of entries for a search request to return. .IP "\fBldap_start_tls:\fR 0" 5 .RS 5 Use transport layer security for ldap:// using STARTTLS. Do not use ldaps:// in 'ldap_uri' with this option enabled. .RE .IP "\fBldap_time_limit:\fR 5" 5 Specify a number of seconds for a search request to complete. .IP "\fBldap_timeout:\fR 5" 5 Specify a number of seconds a search can take before timing out. .IP "\fBldap_ca_dir:\fR " 5 Path to a directory with CA (Certificate Authority) certificates. .IP "\fBldap_ca_file:\fR " 5 Patch to a file containing CA (Certificate Authority) certificate(s). .IP "\fBldap_client_cert:\fR " 5 File containing the client certificate. .IP "\fBldap_verify_peer:\fR 0" 5 .RS 5 Require and verify server certificate. If this option is yes, you must specify ldap_ca_file or ldap_ca_dir. .RE .IP "\fBldap_ciphers:\fR " 5 .RS 5 List of SSL/TLS ciphers to allow. The format of the string is described in ciphers(1). .RE .IP "\fBldap_client_key:\fR " 5 File containing the private client key. .IP "\fBldap_tls_cacert_dir:\fR " 5 Deprecated in favor of \fIldap_ca_dir\fR. .IP "\fBldap_tls_cacert_file:\fR " 5 Deprecated in favor of \fIldap_ca_file\fR. .IP "\fBldap_tls_cert:\fR " 5 Deprecated in favor of \fIldap_client_cert\fR. .IP "\fBldap_tls_key:\fR " 5 Deprecated in favor of \fIldap_client_key\fR. .IP "\fBldap_tls_check_peer:\fR " 5 Deprecated in favor of \fIldap_verify_peer\fR. .IP "\fBldap_tls_ciphers:\fR " 5 Deprecated in favor of \fIldap_ciphers\fR. .IP "\fBldap_uri:\fR " 5 .RS 5 Contains a list of the URLs of all the LDAP servers when using the LDAP PTS module. .RE .IP "\fBldap_version:\fR 3" 5 .RS 5 Specify the LDAP protocol version. If ldap_start_tls and/or ldap_use_sasl are enabled, ldap_version will be automatically set to 3. .RE .IP "\fBlmtp_downcase_rcpt:\fR 1" 5 .RS 5 If enabled, lmtpd will convert the recipient addresses to lowercase (up to a '+' character, if present). .RE .IP "\fBlmtp_fuzzy_mailbox_match:\fR 0" 5 .RS 5 If enabled, and the mailbox specified in the detail part of the recipient (everything after the '+') does not exist, lmtpd will try to find the closest match (ignoring case, ignoring whitespace, falling back to parent) to the specified mailbox name. .RE .IP "\fBlmtp_over_quota_perm_failure:\fR 0" 5 .RS 5 If enabled, lmtpd returns a permanent failure code when a user's mailbox is over quota. By default, the failure is temporary, causing the MTA to queue the message and retry later. .RE .IP "\fBlmtp_strict_quota:\fR 0" 5 .RS 5 If enabled, lmtpd returns a failure code when the incoming message will cause the user's mailbox to exceed its quota. By default, the failure won't occur until the mailbox is already over quota. .RE .IP "\fBlmtp_strict_rfc2821:\fR 1" 5 .RS 5 By default, lmtpd will be strict (per RFC 2821) with regards to which envelope addresses are allowed. If this option is set to false, 8bit characters in the local-part of envelope addresses are changed to 'X' instead. This is useful to avoid generating backscatter with certain MTAs like Postfix or Exim which accept such messages. .RE .IP "\fBlmtpsocket:\fR {configdirectory}/socket/lmtp" 5 .RS 5 Unix domain socket that lmtpd listens on, used by deliver(8). This should match the path specified in cyrus.conf(5). .RE .IP "\fBlmtptxn_timeout:\fR 300" 5 .RS 5 Timeout (in seconds) used during a lmtp transaction to a remote backend (e.g. in a murder environment). Can be used to prevent hung lmtpds on proxy hosts when a backend server becomes unresponsive during a lmtp transaction. The default is 300 - change to zero for infinite. .RE .IP "\fBloginrealms:\fR " 5 .RS 5 The list of remote realms whose users may authenticate using cross-realm authentication identifiers. Separate each realm name by a space. (A cross-realm identity is considered any identity returned by SASL with an "@" in it.). .RE .IP "\fBloginuseacl:\fR 0" 5 .RS 5 If enabled, any authentication identity which has \fBa\fR rights on a user's INBOX may log in as that user. .RE .IP "\fBlogtimestamps:\fR 0" 5 .RS 5 Include notations in the protocol telemetry logs indicating the number of seconds since the last command or response. .RE .IP "\fBmailbox_default_options:\fR 0" 5 .RS 5 Default "options" field for the mailbox on create. You'll want to know what you're doing before setting this, but it can apply some default annotations like duplicate supression .RE .IP "\fBmailbox_initial_flags:\fR " 5 .RS 5 space-separated list of permanent flags which will be pre-set in every newly created mailbox. If you know you will require particular flag names then this avoids a possible race condition against a client that fills the entire 128 available slots. Default is NULL, which is no flags. Example: $Label1 $Label2 $Label3 NotSpam Spam .RE .IP "\fBmailnotifier:\fR " 5 .RS 5 Notifyd(8) method to use for "MAIL" notifications. If not set, "MAIL" notifications are disabled. .RE .IP "\fBmaxheaderlines:\fR 1000" 5 .RS 5 Maximum number of lines of header that will be processed into cache records. Default 1000. If set to zero, it is unlimited. If a message hits the limit, an error will be logged and the rest of the lines in the header will be skipped. This is to avoid malformed messages causing giant cache records .RE .IP "\fBmaxlogins_per_host:\fR 0" 5 .RS 5 Maximum number of logged in sessions allowed per host, zero means no limit .RE .IP "\fBmaxlogins_per_user:\fR 0" 5 .RS 5 Maximum number of logged in sessions allowed per user, zero means no limit .RE .IP "\fBmaxmessagesize:\fR 0" 5 .RS 5 Maximum incoming LMTP message size. If non-zero, lmtpd will reject messages larger than \fImaxmessagesize\fR bytes. If set to 0, this will allow messages of any size (the default). .RE .IP "\fBmaxquoted:\fR 131072" 5 Maximum size of a single quoted string for the parser. Default 128k .IP "\fBmaxword:\fR 131072" 5 Maximum size of a single word for the parser. Default 128k .IP "\fBmboxkey_db:\fR twoskip" 5 The cyrusdb backend to use for mailbox keys. Allowed values: \fIberkeley\fR, \fIskiplist\fR, \fItwoskip\fR .IP "\fBmboxlist_db:\fR twoskip" 5 The cyrusdb backend to use for the mailbox list. Allowed values: \fIflat\fR, \fIberkeley\fR, \fIberkeley-hash\fR, \fIskiplist\fR, \fIsql\fR, \fItwoskip\fR .IP "\fBmboxlist_db_path:\fR " 5 .RS 5 The absolute path to the mailboxes db file. If not specified will be confdir/mailboxes.db .RE .IP "\fBmboxname_lockpath:\fR " 5 Path to mailbox name lock files (default $conf/lock) .IP "\fBmetapartition_files:\fR " 5 .RS 5 Space-separated list of metadata files to be stored on a \fImetapartition\fR rather than in the mailbox directory on a spool partition. Allowed values: \fIheader\fR, \fIindex\fR, \fIcache\fR, \fIexpunge\fR, \fIsquat\fR, \fIannotations\fR, \fIlock\fR, \fIdav\fR .RE .IP "\fBmetapartition-name:\fR " 5 .RS 5 The pathname of the metadata partition \fIname\fR, corresponding to spool partition \fBpartition-name\fR. For any mailbox residing in a directory on \fBpartition-name\fR, the metadata files listed in \fImetapartition_files\fR will be stored in a corresponding directory on \fBmetapartition-name\fR. Note that not every \fBpartition-name\fR option is required to have a corresponding \fBmetapartition-name\fR option, so that you can selectively choose which spool partitions will have separate metadata partitions. .RE .IP "\fBmupdate_authname:\fR " 5 .RS 5 The SASL username (Authentication Name) to use when authenticating to the mupdate server (if needed). .RE .IP "\fBmupdate_config:\fR standard" 5 .RS 5 The configuration of the mupdate servers in the Cyrus Murder. The "standard" config is one in which there are discreet frontend (proxy) and backend servers. The "unified" config is one in which a server can be both a frontend and backend. The "replicated" config is one in which multiple backend servers all share the same mailspool, but each have their own "replicated" copy of mailboxes.db. Allowed values: \fIstandard\fR, \fIunified\fR, \fIreplicated\fR .RE .IP "\fBmunge8bit:\fR 1" 5 .RS 5 If enabled, lmtpd munges messages with 8-bit characters in the headers. The 8-bit characters are changed to `X'. If \fBreject8bit\fR is enabled, setting \fBmunge8bit\fR has no effect. (A proper solution to non-ASCII characters in headers is offered by RFC 2047 and its predecessors.) .RE .IP "\fBmupdate_connections_max:\fR 128" 5 .RS 5 The max number of connections that a mupdate process will allow, this is related to the number of file descriptors in the mupdate process. Beyond this number connections will be immediately issued a BYE response. .RE .IP "\fBmupdate_password:\fR " 5 .RS 5 The SASL password (if needed) to use when authenticating to the mupdate server. .RE .IP "\fBmupdate_port:\fR 3905" 5 The port of the mupdate server for the Cyrus Murder .IP "\fBmupdate_realm:\fR " 5 .RS 5 The SASL realm (if needed) to use when authenticating to the mupdate server. .RE .IP "\fBmupdate_retry_delay:\fR 20" 5 The base time to wait between connection retries to the mupdate server. .IP "\fBmupdate_server:\fR " 5 The mupdate server for the Cyrus Murder .IP "\fBmupdate_username:\fR " 5 .RS 5 The SASL username (Authorization Name) to use when authenticating to the mupdate server .RE .IP "\fBmupdate_workers_max:\fR 50" 5 The maximum number of mupdate worker threads (overall) .IP "\fBmupdate_workers_maxspare:\fR 10" 5 The maximum number of idle mupdate worker threads .IP "\fBmupdate_workers_minspare:\fR 2" 5 The minimum number of idle mupdate worker threads .IP "\fBmupdate_workers_start:\fR 5" 5 The number of mupdate worker threads to start .IP "\fBnetscapeurl:\fR " 5 .RS 5 If enabled at compile time, this specifies a URL to reply when Netscape asks the server where the mail administration HTTP server is. Administrators should set this to a local resource. .RE .IP "\fBnewsaddheaders:\fR to" 5 .RS 5 Space-separated list of headers to be added to incoming usenet articles. Added \fITo:\fR headers will contain email delivery addresses corresponding to each newsgroup in the \fINewsgroups:\fR header. Added \fIReply-To:\fR headers will contain email delivery addresses corresponding to each newsgroup in the \fIFollowup-To:\fR or \fINewsgroups:\fR header. If the specified header(s) already exist in an article, the email delivery addresses will be appended to the original header body(s). .br .sp This option applies if and only if the \fBnewspostuser\fR option is set. Allowed values: \fIto\fR, \fIreplyto\fR .RE .IP "\fBnewsgroups:\fR *" 5 .RS 5 A wildmat pattern specifying which mailbox hierarchies should be treated as newsgroups. Only mailboxes matching the wildmat will accept and/or serve articles via NNTP. If not set, a default wildmat of "*" (ALL shared mailboxes) will be used. If the \fInewsprefix\fR option is also set, the default wildmat will be translated to ".*" .RE .IP "\fBnewsmaster:\fR news" 5 .RS 5 Userid that is used for checking access controls when executing Usenet control messages. For instance, to allow articles to be automatically deleted by cancel messages, give the "news" user the 'd' right on the desired mailboxes. To allow newsgroups to be automatically created, deleted and renamed by the corresponding control messages, give the "news" user the 'c' right on the desired mailbox hierarchies. .RE .IP "\fBnewspeer:\fR " 5 .RS 5 A list of whitespace-separated news server specifications to which articles should be fed. Each server specification is a string of the form [user[:pass]@]host[:port][/wildmat] where 'host' is the fully qualified hostname of the server, 'port' is the port on which the server is listening, 'user' and 'pass' are the authentication credentials and 'wildmat' is a pattern that specifies which groups should be fed. If no 'port' is specified, port 119 is used. If no 'wildmat' is specified, all groups are fed. If 'user' is specified (even if empty), then the NNTP POST command will be used to feed the article to the server, otherwise the IHAVE command will be used. .br .sp A '@' may be used in place of '!' in the wildmat to prevent feeding articles cross-posted to the given group, otherwise cross-posted articles are fed if any part of the wildmat matches. For example, the string "peer.example.com:*,!control.*,@local.*" would feed all groups except control messages and local groups to peer.example.com. In the case of cross-posting to local groups, these articles would not be fed. .RE .IP "\fBnewspostuser:\fR " 5 .RS 5 Userid used to deliver usenet articles to newsgroup folders (usually via lmtp2nntp). For example, if set to "post", email sent to "post+comp.mail.imap" would be delivered to the "comp.mail.imap" folder. .br .sp When set, the Cyrus NNTP server will add the header(s) specified in the \fBnewsaddheaders\fR option to each incoming usenet article. The added header(s) will contain email delivery addresses corresponding to each relevent newsgroup. If not set, no headers are added to usenet articles. .RE .IP "\fBnewsprefix:\fR " 5 .RS 5 Prefix to be prepended to newsgroup names to make the corresponding IMAP mailbox names. .RE .IP "\fBnewsrc_db_path:\fR " 5 .RS 5 The absolute path to the newsrc db file. If not specified, will be confdir/fetchnews.db .RE .IP "\fBnntptimeout:\fR 3" 5 .RS 5 Set the length of the NNTP server's inactivity autologout timer, in minutes. The minimum value is 3, the default. .RE .IP "\fBnotifysocket:\fR {configdirectory}/socket/notify" 5 Unix domain socket that the mail notification daemon listens on. .IP "\fBnotify_external:\fR " 5 .RS 5 Path to the external program that notifyd(8) will call to send mail notifications. .PP The external program will be called with the following command line options: .TP .BI \-c " class" .TP .BI \-p " priority" .TP .BI \-u " user" .TP .BI \-m " mailbox" .PP And the notification message will be available on \fIstdin\fR. .RE .IP "\fBpartition-name:\fR " 5 .RS 5 The pathname of the partition \fIname\fR. At least one partition pathname MUST be specified. If the \fBdefaultpartition\fR option is used, then its pathname MUST be specified. For example, if the value of the \fBdefaultpartion\fR option is \fBdefault\fR, then the \fBpartition-default\fR field is required. .RE .IP "\fBpartition_select_mode:\fR freespace-most" 5 .RS 5 Partition selection mode. .PP .IP \fIrandom\fR 5 (pseudo-)random selection .IP \fIfreespace-most\fR 5 partition with the most free space (KiB) .IP \fIfreespace-percent-most\fR 5 partition with the most free space (%) .IP \fIfreespace-percent-weighted\fR 5 each partition is weighted according to its free space (%); the more free space the partition has, the more chances it has to be selected .IP \fIfreespace-percent-weighted-delta\fR 5 each partition is weighted according to its difference of free space (%) compared to the most used partition; the more the partition is lagging behind the most used partition, the more chances it has to be selected .PP Note that actually even the most used partition has a few chances to be selected, and those chances increase when other partitions get closer Allowed values: \fIrandom\fR, \fIfreespace-most\fR, \fIfreespace-percent-most\fR, \fIfreespace-percent-weighted\fR, \fIfreespace-percent-weighted-delta\fR .RE .IP "\fBpartition_select_exclude:\fR " 5 List of partitions to exclude from selection mode. .IP "\fBpartition_select_usage_reinit:\fR 0" 5 .RS 5 For a given session, number of \fBoperations\fR (e.g. partition selection) for which partitions usage data are cached. .RE .IP "\fBpartition_select_soft_usage_limit:\fR 0" 5 .RS 5 Limit of partition usage (%): if a partition is over that limit, it is automatically excluded from selection mode. .PP If all partitions are over that limit, this feature is not used anymore. .RE .IP "\fBplaintextloginpause:\fR 0" 5 .RS 5 Number of seconds to pause after a successful plaintext login. For systems that support strong authentication, this permits users to perceive a cost of using plaintext passwords. (This does not affect the use of PLAIN in SASL authentications.) .RE .IP "\fBplaintextloginalert:\fR " 5 Message to send to client after a successful plaintext login. .IP "\fBpopexpiretime:\fR -1" 5 .RS 5 The number of days advertised as being the minimum a message may be left on the POP server before it is deleted (via the CAPA command, defined in the POP3 Extension Mechanism, which some clients may support). "NEVER", the default, may be specified with a negative number. The Cyrus POP3 server never deletes mail, no matter what the value of this parameter is. However, if a site implements a less liberal policy, it needs to change this parameter accordingly. .RE .IP "\fBpopminpoll:\fR 0" 5 .RS 5 Set the minimum amount of time the server forces users to wait between successive POP logins, in minutes. .RE .IP "\fBpopsubfolders:\fR 0" 5 .RS 5 Allow access to subfolders of INBOX via POP3 by using userid+subfolder syntax as the authentication/authorization id. .RE .IP "\fBpoppollpadding:\fR 1" 5 .RS 5 Create a softer minimum poll restriction. Allows \fIpoppollpadding\fR connections before the minpoll restriction is triggered. Additionally, one padding entry is recovered every \fIpopminpoll\fR minutes. This allows for the occasional polling rate faster than popminpoll, (i.e., for clients that require a send/receive to send mail) but still enforces the rate long-term. Default is 1 (disabled). .br .sp The easiest way to think of it is a queue of past connections, with one slot being filled for every connection, and one slot being cleared every \fIpopminpoll\fR minutes. When the queue is full, the user will not be able to check mail again until a slot is cleared. If the user waits a sufficient amount of time, they will get back many or all of the slots. .RE .IP "\fBpoptimeout:\fR 10" 5 .RS 5 Set the length of the POP server's inactivity autologout timer, in minutes. The minimum value is 10, the default. .RE .IP "\fBpopuseacl:\fR 0" 5 .RS 5 Enforce IMAP ACLs in the pop server. Due to the nature of the POP3 protocol, the only rights which are used by the pop server are 'r', 't', and 's' for the owner of the mailbox. The 'r' right allows the user to open the mailbox and list/retrieve messages. The 't' right allows the user to delete messages. The 's' right allows messages retrieved by the user to have the \\Seen flag set (only if \fIpopuseimapflags\fR is also enabled). .RE .IP "\fBpopuseimapflags:\fR 0" 5 .RS 5 If enabled, the pop server will set and obey IMAP flags. Messages having the \\Deleted flag are ignored as if they do not exist. Messages that are retrieved by the client will have the \\Seen flag set. All messages will have the \\Recent flag unset. .RE .IP "\fBpostmaster:\fR postmaster" 5 .RS 5 Username that is used as the 'From' address in rejection MDNs produced by sieve. .RE .IP "\fBpostuser:\fR " 5 .RS 5 Userid used to deliver messages to shared folders. For example, if set to "bb", email sent to "bb+shared.blah" would be delivered to the "shared.blah" folder. By default, an email address of "+shared.blah" would be used. .RE .IP "\fBproc_path:\fR " 5 .RS 5 Path to proc directory. Default is NULL - must be an absolute path if specified. If not specified, the path $confdir/proc/ will be used. .RE .IP "\fBproxy_authname:\fR proxy" 5 .RS 5 The authentication name to use when authenticating to a backend server in the Cyrus Murder. .RE .IP "\fBproxy_compress:\fR 0" 5 .RS 5 Try to enable protocol-specific compression when performing a client connection to a backend server in the Cyrus Murder. .PP Note that this should only be necessary over slow network connections. Also note that currently only IMAP and MUPDATE support compression. .RE .IP "\fBproxy_password:\fR " 5 .RS 5 The default password to use when authenticating to a backend server in the Cyrus Murder. May be overridden on a host-specific basis using the hostname_password option. .RE .IP "\fBproxy_realm:\fR " 5 .RS 5 The authentication realm to use when authenticating to a backend server in the Cyrus Murder .RE .IP "\fBproxyd_allow_status_referral:\fR 0" 5 .RS 5 Set to true to allow proxyd to issue referrals to clients that support it when answering the STATUS command. This is disabled by default since some clients issue many STATUS commands in a row, and do not cache the connections that these referrals would cause, thus resulting in a higher authentication load on the respective backend server. .RE .IP "\fBproxyd_disable_mailbox_referrals:\fR 0" 5 .RS 5 Set to true to disable the use of mailbox-referrals on the proxy servers. .RE .IP "\fBproxyservers:\fR " 5 .RS 5 A list of users and groups that are allowed to proxy for other users, separated by spaces. Any user listed in this will be allowed to login for any other user: use with caution. In a standard murder this option should ONLY be set on backends. DO NOT SET on frontends or things won't work properly. .RE .IP "\fBpts_module:\fR afskrb" 5 The PTS module to use. Allowed values: \fIafskrb\fR, \fIldap\fR .IP "\fBptloader_sock:\fR " 5 .RS 5 Unix domain socket that ptloader listens on. (defaults to configdir/ptclient/ptsock) .RE .IP "\fBptscache_db:\fR twoskip" 5 The cyrusdb backend to use for the pts cache. Allowed values: \fIberkeley\fR, \fIberkeley-hash\fR, \fIskiplist\fR, \fItwoskip\fR .IP "\fBptscache_db_path:\fR " 5 .RS 5 The absolute path to the ptscache db file. If not specified, will be confdir/ptscache.db .RE .IP "\fBptscache_timeout:\fR 10800" 5 .RS 5 The timeout (in seconds) for the PTS cache database when using the auth_krb_pts authorization method (default: 3 hours). .RE .IP "\fBptskrb5_convert524:\fR 1" 5 .RS 5 When using the AFSKRB ptloader module with Kerberos 5 canonicalization, do the final 524 conversion to get a n AFS style name (using '.' instead of '/', and using short names .RE .IP "\fBptskrb5_strip_default_realm:\fR 1" 5 .RS 5 When using the AFSKRB ptloader module with Kerberos 5 canonicalization, strip the default realm from the userid (this does not affect the stripping of realms specified by the afspts_localrealms option) .RE .IP "\fBqosmarking:\fR cs0" 5 .RS 5 This specifies the Class Selector or Differentiated Services Code Point designation on IP headers (in the ToS field). Allowed values: \fIcs0\fR, \fIcs1\fR, \fIcs2\fR, \fIcs3\fR, \fIcs4\fR, \fIcs5\fR, \fIcs6\fR, \fIcs7\fR, \fIaf11\fR, \fIaf12\fR, \fIaf13\fR, \fIaf21\fR, \fIaf22\fR, \fIaf23\fR, \fIaf31\fR, \fIaf32\fR, \fIaf33\fR, \fIaf41\fR, \fIaf42\fR, \fIaf43\fR, \fIef\fR .RE .IP "\fBquota_db:\fR quotalegacy" 5 The cyrusdb backend to use for quotas. Allowed values: \fIflat\fR, \fIberkeley\fR, \fIberkeley-hash\fR, \fIskiplist\fR, \fIsql\fR, \fIquotalegacy\fR, \fItwoskip\fR .IP "\fBquota_db_path:\fR " 5 .RS 5 The absolute path for the quota database (if you choose a single-file quota DB type - or the base path if you choose quotalegacy). If not specified will be confdir/quota.db or confdir/quota/ .RE .IP "\fBquotawarn:\fR 90" 5 .RS 5 The percent of quota utilization over which the server generates warnings. .RE .IP "\fBquotawarnkb:\fR 0" 5 .RS 5 The maximum amount of free space (in kB) at which to give a quota warning (if this value is 0, or if the quota is smaller than this amount, then warnings are always given). .RE .IP "\fBquotawarnmsg:\fR 0" 5 .RS 5 The maximum amount of messages at which to give a quota warning (if this value is 0, or if the quota is smaller than this amount, then warnings are always given). .RE .IP "\fBreject8bit:\fR 0" 5 .RS 5 If enabled, lmtpd rejects messages with 8-bit characters in the headers. .RE .IP "\fBrfc2046_strict:\fR 0" 5 .RS 5 If enabled, imapd will be strict (per RFC 2046) when matching MIME boundary strings. This means that boundaries containing other boundaries as substrings will be treated as identical. Since enabling this option will break some messages created by Eudora 5.1 (and earlier), it is recommended that it be left disabled unless there is good reason to do otherwise. .RE .IP "\fBrfc3028_strict:\fR 1" 5 .RS 5 If enabled, Sieve will be strict (per RFC 3028) with regards to which headers are allowed to be used in address and envelope tests. This means that only those headers which are defined to contain addresses will be allowed in address tests and only "to" and "from" will be allowed in envelope tests. When disabled, ANY grammatically correct header will be allowed. .RE .IP "\fBrss_feedlist_template:\fR " 5 .RS 5 File containing HTML that will be used as a template for displaying the list of available RSS feeds. A single instance of the variable %RSS_FEEDLIST% should appear in the file, which will be replaced by a nested unordered list of feeds. The toplevel unordered list will be tagged with an id of "feed" (
    ) which can be used by stylesheet(s) in your template. The dynamically created list of feeds based on the HTML template will be accessible at the "/rss" URL on the server. .RE .IP "\fBrss_feeds:\fR *" 5 .RS 5 A wildmat pattern specifying which mailbox hierarchies should be treated as RSS feeds. Only mailboxes matching the wildmat will have their messages available via RSS. If not set, a default wildmat of "*" (ALL mailboxes) will be used. .RE .IP "\fBrss_maxage:\fR 0" 5 .RS 5 Maximum age (in days) of items to display in an RSS channel. If non-zero, httpd will only display items received within the last \fIrss_maxage\fR days. If set to 0, all available items will be displayed (the default). .RE .IP "\fBrss_maxitems:\fR 0" 5 .RS 5 Maximum number of items to display in an RSS channel. If non-zero, httpd will display no more than the \fIrss_maxitems\fR most recent items. If set to 0, all available items will be displayed (the default). .RE .IP "\fBrss_maxsynopsis:\fR 0" 5 .RS 5 Maximum RSS item synopsis length. If non-zero, httpd will display no more than the first \fIrss_maxsynopsis\fR characters of an item's synopsis. If set to 0, the entire synopsis will be displayed (the default). .RE .IP "\fBrss_realm:\fR " 5 .RS 5 The realm to present for HTTP authentication of RSS feeds. If not set (the default), the value of the "servername" option will be used. .RE .IP "\fBsasl_auto_transition:\fR 0" 5 .RS 5 If enabled, the SASL library will automatically create authentication secrets when given a plaintext password. See the SASL documentation. .RE .IP "\fBsasl_maximum_layer:\fR 256" 5 .RS 5 Maximum SSF (security strength factor) that the server will allow a client to negotiate. .RE .IP "\fBsasl_minimum_layer:\fR 0" 5 .RS 5 The minimum SSF that the server will allow a client to negotiate. A value of 1 requires integrity protection; any higher value requires some amount of encryption. .RE .IP "\fBsasl_option:\fR 0" 5 .RS 5 Any SASL option can be set by preceding it with "sasl_". This file overrides the SASL configuration file. .RE .IP "\fBsasl_pwcheck_method:\fR " 5 .RS 5 The mechanism used by the server to verify plaintext passwords. Possible values include "auxprop", "saslauthd", and "pwcheck". .RE .IP "\fBsearch_skipdiacrit:\fR 1" 5 .RS 5 When searching, should diacriticals be stripped from the search terms. The default is "true", a search for "hav" will match "Håvard". This is not RFC5051 complient, but it backwards compatible, and may be preferred by some sites. .RE .IP "\fBsearch_whitespace:\fR merge" 5 .RS 5 When searching, how whitespace should be handled. Options are: "skip" (default in 2.3 and earlier series) - where a search for "equi" would match "the quick brown fox". "merge" - the default, where "he qu" would match "the quick brownfox", and "keep", where whitespace must match exactly. The default of "merge" is recommended for most cases - it's a good compromise which keeps words separate. Allowed values: \fIskip\fR, \fImerge\fR, \fIkeep\fR .RE .IP "\fBseenstate_db:\fR twoskip" 5 The cyrusdb backend to use for the seen state. Allowed values: \fIflat\fR, \fIberkeley\fR, \fIberkeley-hash\fR, \fIskiplist\fR, \fItwoskip\fR .IP "\fBsendmail:\fR /usr/lib/sendmail" 5 .RS 5 The pathname of the sendmail executable. Sieve invokes sendmail for sending rejections, redirects and vacation responses. .RE .IP "\fBserverlist:\fR " 5 .RS 5 Whitespace separated list of backend server names. Used for finding server with the most available free space for proxying CREATE. .RE .IP "\fBserverlist_select_mode:\fR freespace-most" 5 .RS 5 Server selection mode. .PP .IP \fIrandom\fR 5 (pseudo-)random selection .IP \fIfreespace-most\fR 5 backend with the most (total) free space (KiB) .IP \fIfreespace-percent-most\fR 5 backend whose partition has the most free space (%) .IP \fIfreespace-percent-weighted\fR 5 same as for partition selection, comparing the free space (%) of the least used partition of each backend .IP \fIfreespace-percent-weighted-delta\fR 5 same as for partition selection, comparing the free space (%) of the least used partition of each backend Allowed values: \fIrandom\fR, \fIfreespace-most\fR, \fIfreespace-percent-most\fR, \fIfreespace-percent-weighted\fR, \fIfreespace-percent-weighted-delta\fR .RE .IP "\fBserverlist_select_usage_reinit:\fR 0" 5 .RS 5 For a given session, number of \fBoperations\fR (e.g. backend selection) for which backend usage data are cached. .RE .IP "\fBserverlist_select_soft_usage_limit:\fR 0" 5 .RS 5 Limit of backend usage (%): if a backend is over that limit, it is automatically excluded from selection mode. .PP If all backends are over that limit, this feature is not used anymore. .RE .IP "\fBservername:\fR " 5 .RS 5 This is the hostname visible in the greeting messages of the POP, IMAP and LMTP daemons. If it is unset, then the result returned from gethostname(2) is used. This is also the value used by murder clusters to identify the host name. It should be resolvable by DNS to the correct host, and unique within an active cluster. If you are using low level replication (e.g. drbd) then it should be the same on each copy and the DNS name should also be moved to the new master on failover. .RE .IP "\fBserverinfo:\fR on" 5 .RS 5 The server information to display in the greeting and capability responses. Information is displayed as follows: .IP "off" = no server information in the greeting or capabilities .br "min" = \fIservername\fR in the greeting; no server information in the capabilities .br "on" = \fIservername\fR and product version in the greeting; product version in the capabilities Allowed values: \fIoff\fR, \fImin\fR, \fIon\fR .RE .IP "\fBsharedprefix:\fR Shared Folders" 5 .RS 5 If using the alternate IMAP namespace, the prefix for the shared namespace. The hierarchy delimiter will be automatically appended. .RE .IP "\fBsieve_allowreferrals:\fR 1" 5 .RS 5 If enabled, timsieved will issue referrals to clients when the user's scripts reside on a remote server (in a Murder). Otherwise, timsieved will proxy traffic to the remote server. .RE .IP "\fBsieve_extensions:\fR fileinto reject vacation vacation-seconds imapflags notify envelope relational regex subaddress copy date index imap4flags" 5 .RS 5 Space-separated list of Sieve extensions allowed to be used in sieve scripts, enforced at submission by timsieved(8). Any previously installed script will be unaffected by this option and will continue to execute regardless of the extensions used. This option has no effect on options that are disabled at compile time (e.g., "regex"). Allowed values: \fIfileinto\fR, \fIreject\fR, \fIvacation\fR, \fIvacation-seconds\fR, \fIimapflags\fR, \fInotify\fR, \fIinclude\fR, \fIenvelope\fR, \fIbody\fR, \fIrelational\fR, \fIregex\fR, \fIsubaddress\fR, \fIcopy\fR, \fIdate\fR, \fIindex\fR, \fIimap4flags\fR .RE .IP "\fBsieve_maxscriptsize:\fR 32" 5 .RS 5 Maximum size (in kilobytes) any sieve script can be, enforced at submission by timsieved(8). .RE .IP "\fBsieve_maxscripts:\fR 5" 5 .RS 5 Maximum number of sieve scripts any user may have, enforced at submission by timsieved(8). .RE .IP "\fBsieve_utf8fileinto:\fR 0" 5 .RS 5 If enabled, the sieve engine expects folder names for the \fIfileinto\fR action in scripts to use UTF8 encoding. Otherwise, modified UTF7 encoding should be used. .RE .IP "\fBsieve_sasl_send_unsolicited_capability:\fR 0" 5 .RS 5 If enabled, timsieved will emit a capability response after a successful SASL authentication, per draft-martin-managesieve-12.txt . .RE .IP "\fBsieve_vacation_min_response:\fR 259200 /* 3 days */" 5 .RS 5 Minimum time interval (in seconds) between consecutive vacation responses, per draft-ietf-vacation-seconds.txt . .RE .IP "\fBsieve_vacation_max_response:\fR 7776000 /* 90 days */" 5 .RS 5 Maximum time interval (in seconds) between consecutive vacation responses, per draft-ietf-vacation-seconds.txt . .RE .IP "\fBsievedir:\fR /usr/sieve" 5 .RS 5 If sieveusehomedir is false, this directory is searched for Sieve scripts. .RE .IP "\fBsievenotifier:\fR " 5 .RS 5 Notifyd(8) method to use for "SIEVE" notifications. If not set, "SIEVE" notifications are disabled. .PP This method is only used when no method is specified in the script. .RE .IP "\fBsieveusehomedir:\fR 0" 5 .RS 5 If enabled, lmtpd will look for Sieve scripts in user's home directories: ~user/.sieve. .RE .IP "\fBanysievefolder:\fR 0" 5 .RS 5 It must be "yes" in order to permit the autocreation of any INBOX subfolder requested by a sieve filter, through the "fileinto" action. (default = no) .RE .IP "\fBsingleinstancestore:\fR 1" 5 .RS 5 If enabled, imapd, lmtpd and nntpd attempt to only write one copy of a message per partition and create hard links, resulting in a potentially large disk savings. .RE .IP "\fBskiplist_always_checkpoint:\fR 1" 5 .RS 5 If enabled, this option forces the skiplist cyrusdb backend to always checkpoint when doing a recovery. This causes slightly more IO, but on the other hand leads to more efficient databases, and the entire file is already "hot". .RE .IP "\fBskiplist_unsafe:\fR 0" 5 .RS 5 If enabled, this option forces the skiplist cyrusdb backend to not sync writes to the disk. Enabling this option is NOT RECOMMENDED. .RE .IP "\fBsoft_noauth:\fR 1" 5 .RS 5 If enabled, lmtpd returns temporary failures if the client does not successfully authenticate. Otherwise lmtpd returns permanent failures (causing the mail to bounce immediately). .RE .IP "\fBspecialuse_extra:\fR " 5 .RS 5 Whitespace separated list of extra special-use attributes that can be set on a mailbox. RFC 6154 currently lists what special-use attributes can be set. This allows extending that list in the future or adding your own if needed. .RE .IP "\fBspecialusealways:\fR 0" 5 .RS 5 If enabled, this option causes LIST and LSUB output to always include the XLIST "special-use" flags .RE .IP "\fBsql_database:\fR " 5 Name of the database which contains the cyrusdb table(s). .IP "\fBsql_engine:\fR " 5 Name of the SQL engine to use. Allowed values: \fImysql\fR, \fIpgsql\fR, \fIsqlite\fR .IP "\fBsql_hostnames:\fR " 5 Comma separated list of SQL servers (in host[:port] format). .IP "\fBsql_passwd:\fR " 5 Password to use for authentication to the SQL server. .IP "\fBsql_user:\fR " 5 Username to use for authentication to the SQL server. .IP "\fBsql_usessl:\fR 0" 5 If enabled, a secure connection will be made to the SQL server. .IP "\fBsrvtab:\fR " 5 .RS 5 The pathname of \fIsrvtab\fR file containing the server's private key. This option is passed to the SASL library and overrides its default setting. .RE .IP "\fBsubmitservers:\fR " 5 .RS 5 A list of users and groups that are allowed to resolve "urlauth=submit+" IMAP URLs, separated by spaces. Any user listed in this will be allowed to fetch the contents of any valid "urlauth=submit+" IMAP URL: use with caution. .RE .IP "\fBsubscription_db:\fR flat" 5 The cyrusdb backend to use for the subscriptions list. Allowed values: \fIflat\fR, \fIberkeley\fR, \fIberkeley-hash\fR, \fIskiplist\fR, \fItwoskip\fR .IP "\fBsuppress_capabilities:\fR " 5 .RS 5 Suppress the named capabilities from any capability response. Use the exact case as it appears in the response, e.g. "suppress_capabilities: ESEARCH QRESYNC WITHIN XLIST LIST-EXTENDED" if you have a murder with 2.3.x backends and don't want clients being confused by new capabilities that some backends don't support. .RE .IP "\fBstatuscache:\fR 0" 5 Enable/disable the imap status cache. .IP "\fBstatuscache_db:\fR twoskip" 5 The cyrusdb backend to use for the imap status cache. Allowed values: \fIberkeley\fR, \fIberkeley-nosync\fR, \fIberkeley-hash\fR, \fIberkeley-hash-nosync\fR, \fIskiplist\fR, \fIsql\fR, \fItwoskip\fR .IP "\fBstatuscache_db_path:\fR " 5 .RS 5 The absolute path to the statuscache db file. If not specified, will be confdir/statuscache.db .RE .IP "\fBsync_authname:\fR " 5 .RS 5 The authentication name to use when authenticating to a sync server. Prefix with a channel name to only apply for that channel .RE .IP "\fBsync_host:\fR " 5 .RS 5 Name of the host (replica running sync_server(8)) to which replication actions will be sent by sync_client(8). Prefix with a channel name to only apply for that channel .RE .IP "\fBsync_log:\fR 0" 5 .RS 5 Enable replication action logging by lmtpd(8), imapd(8), pop3d(8), and nntpd(8). The log {configdirectory}/sync/log is used by sync_client(8) for "rolling" replication. .RE .IP "\fBsync_log_chain:\fR 0" 5 .RS 5 Enable replication action logging by sync_server as well, allowing chaining of replicas. Use this on 'B' for A => B => C replication layout .RE .IP "\fBsync_log_channels:\fR " 5 .RS 5 If specified, log all events to multiple log files in directories specified by each "channel". To run these log files, you need to pass the -n option to sync_client -r with the channel name. Use this for a mesh style replication layout - every machine replicating to every other machine. You can use "" (the two-character string U+22 U+22) to mean the default sync channel. .RE .IP "\fBsync_log_unsuppressable_channels:\fR squatter" 5 .RS 5 If specified, the named channels are exempt from the effect of setting sync_log_chain:off, i.e. they are always logged to by the sync_server process. This is only really useful to allow rolling search indexing on a replica. .RE .IP "\fBsync_password:\fR " 5 .RS 5 The default password to use when authenticating to a sync server. Prefix with a channel name to only apply for that channel .RE .IP "\fBsync_port:\fR csync" 5 .RS 5 Name of the service (or port number) of the replication service on replica host. The default is "csync" which is usally port 2005, but any service name or numeric port can be specified. Prefix with a channel name to only apply for that channel .RE .IP "\fBsync_realm:\fR " 5 .RS 5 The authentication realm to use when authenticating to a sync server. Prefix with a channel name to only apply for that channel .RE .IP "\fBsync_repeat_interval:\fR 1" 5 .RS 5 Minimum interval (in seconds) between replication runs in rolling replication mode. If a replication run takes longer than this time, we repeat immediately. Prefix with a channel name to only apply for that channel .RE .IP "\fBsync_shutdown_file:\fR " 5 .RS 5 Simple latch used to tell sync_client(8) that it should shut down at the next opportunity. Safer than sending signals to running processes. Prefix with a channel name to only apply for that channel .RE .IP "\fBsync_timeout:\fR 1800" 5 .RS 5 Number of seconds to wait for a response before returning a timeout failure when talking to a replication peer (client or server). .RE .IP "\fBsyslog_prefix:\fR " 5 String to be prepended to the process name in syslog entries. .IP "\fBsyslog_facility:\fR " 5 .RS 5 Configure a syslog facility. The default is whatever is compiled in. Allowed values are: DAEMON, MAIL, NEWS, USER, and LOCAL0 through to LOCAL7 .RE .IP "\fBtcp_keepalive:\fR 0" 5 Enable keepalive on TCP connections .IP "\fBtcp_keepalive_cnt:\fR 0" 5 .RS 5 Number of TCP keepalive probes to send before declaring the connection dead (0 == system default) .RE .IP "\fBtcp_keepalive_idle:\fR 0" 5 .RS 5 Number of seconds a connection must be idle before keepalive probes are sent (0 == system default) .RE .IP "\fBtcp_keepalive_intvl:\fR 0" 5 Number of seconds between keepalive probes (0 == system default) .IP "\fBtemp_path:\fR /tmp" 5 The pathname to store temporary files in .IP "\fBtimeout:\fR 30" 5 .RS 5 The length of the IMAP server's inactivity autologout timer, in minutes. The minimum value is 30, the default. .RE .IP "\fBtls_ca_file:\fR DEFAULT" 5 Deprecated in favor of \fItls_client_ca_file\fR. .IP "\fBtls_ca_path:\fR DEFAULT" 5 Deprecated in favor of \fItls_client_ca_dir\fR. .IP "\fBtlscache_db:\fR DEFAULT" 5 Deprecated in favor of \fItls_sessions_db\fR. .IP "\fBtlscache_db_path:\fR DEFAULT" 5 Deprecated in favor of \fItls_sessions_db_path\fR. .IP "\fBtls_cert_file:\fR DEFAULT" 5 Deprecated in favor of \fItls_server_cert\fR. .IP "\fBtls_cipher_list:\fR DEFAULT" 5 Deprecated in favor of \fItls_ciphers\fR. .IP "\fBtls_ciphers:\fR DEFAULT" 5 .RS 5 The list of SSL/TLS ciphers to allow. The format of the string is described in ciphers(1). .RE .IP "\fBtls_client_ca_dir:\fR " 5 .RS 5 Path to a directory containing the CA certificates used to verify client SSL certificates used for authentication. .RE .IP "\fBtls_client_ca_file:\fR " 5 .RS 5 Path to a file containing the CA certificate(s) used to verify client SSL certificates used for authentication. .RE .IP "\fBtls_client_cert:\fR " 5 .RS 5 File containing the certificate presented to a server for authentication during STARTTLS. A value of "disabled" will disable this server's use of certificate-based authentication. .RE .IP "\fBtls_client_certs:\fR optional" 5 .RS 5 Disable ("off"), allow ("optional", default) or require ("require") the use of SSL certificates by clients to authenticate themselves. Allowed values: \fIoff\fR, \fIoptional\fR, \fIrequire\fR .RE .IP "\fBtls_client_key:\fR " 5 .RS 5 File containing the private key belonging to the tls_client_cert certificate. A value of "disabled" will disable this server's use of certificate-based authentication. .RE .IP "\fBtls_eccurve:\fR prime256v1" 5 .RS 5 The elliptic curve used for ECDHE. Default is NIST Suite B prime256. See 'openssl ecparam -list_curves' for possible values. .RE .IP "\fBtls_key_file:\fR DEFAULT" 5 Deprecated in favor of \fItls_server_key\fR. .IP "\fBtls_required:\fR 0" 5 .RS 5 If enabled, require a TLS/SSL encryption layer to be negotiated prior to ANY authentication mechanisms being advertised or allowed. .RE .IP "\fBtls_prefer_server_ciphers:\fR 0" 5 Prefer the ciphers on the server side instead of client side. .IP "\fBtls_server_ca_dir:\fR " 5 .RS 5 Path to a directory with CA certificates used to verify certificates offered when this server connects to other servers. This directory must have filenames with the hashed value of the certificates (see openssl(1)). .RE .IP "\fBtls_server_ca_file:\fR " 5 .RS 5 Path to a file containing CA certificates used to verify certificates offered when this server connects to other servers. .RE .IP "\fBtls_server_cert:\fR " 5 File containing the certificate presented to clients. .IP "\fBtls_server_key:\fR " 5 .RS 5 File containing the private key belonging to the certificate in tls_server_cert. .RE .IP "\fBtls_sessions_db:\fR twoskip" 5 The cyrusdb backend to use for the TLS cache. Allowed values: \fIberkeley\fR, \fIberkeley-nosync\fR, \fIberkeley-hash\fR, \fIberkeley-hash-nosync\fR, \fIskiplist\fR, \fIsql\fR, \fItwoskip\fR .IP "\fBtls_sessions_db_path:\fR " 5 .RS 5 The absolute path to the TLS sessions db file. If not specified, will be confdir/tls_sessions.db .RE .IP "\fBtls_session_timeout:\fR 1440" 5 .RS 5 The length of time (in minutes) that a TLS session will be cached for later reuse. The maximum value is 1440 (24 hours), the default. A value of 0 will disable session caching. .RE .IP "\fBtls_versions:\fR tls1_0 tls1_1 tls1_2" 5 .RS 5 A list of SSL/TLS versions to not disable. Cyrus IMAP SSL/TLS starts with all protocols, and substracts protocols not in this list. Newer versions of SSL/TLS will need to be added here to allow them to get disabled. .RE .IP "\fBumask:\fR 077" 5 The umask value used by various Cyrus IMAP programs. .IP "\fBuserdeny_db:\fR flat" 5 The cyrusdb backend to use for the user access list. Allowed values: \fIflat\fR, \fIberkeley\fR, \fIberkeley-hash\fR, \fIskiplist\fR, \fIsql\fR, \fItwoskip\fR .IP "\fBuserdeny_db_path:\fR " 5 .RS 5 The absolute path to the userdeny db file. If not specified, will be confdir/user_deny.db .RE .IP "\fBusername_tolower:\fR 1" 5 .RS 5 Convert usernames to all lowercase before login/authentication. This is useful with authentication backends which ignore case during username lookups (such as LDAP). .RE .IP "\fBuserprefix:\fR Other Users" 5 .RS 5 If using the alternate IMAP namespace, the prefix for the other users namespace. The hierarchy delimiter will be automatically appended. .RE .IP "\fBunix_group_enable:\fR 1" 5 .RS 5 Should we look up groups when using auth_unix (disable this if you are not using groups in ACLs for your IMAP server, and you are using auth_unix with a backend (such as LDAP) that can make getgrent() calls very slow) .RE .IP "\fBunixhierarchysep:\fR 0" 5 .RS 5 Use the UNIX separator character '/' for delimiting levels of mailbox hierarchy. Turn off to use the netnews separator character '.'. Note that with the newnews separator, no dots may occur in mailbox names. .RE .IP "\fBvirtdomains:\fR off" 5 .RS 5 Enable virtual domain support. If enabled, the user's domain will be determined by splitting a fully qualified userid at the last '@' or '%' symbol. If the userid is unqualified, and the virtdomains option is set to "on", then the domain will be determined by doing a reverse lookup on the IP address of the incoming network interface, otherwise the user is assumed to be in the default domain (if set). Allowed values: \fIoff\fR, \fIuserid\fR, \fIon\fR .RE .IP "\fBlmtp_catchall_mailbox:\fR " 5 .RS 5 Mail sent to mailboxes which do not exist, will be delivered to this user. NOTE: This must be an existing local user name with an INBOX, NOT an email address! .RE .IP "\fBzoneinfo_db:\fR twoskip" 5 The cyrusdb backend to use for zoneinfo. Allowed values: \fIflat\fR, \fIberkeley\fR, \fIberkeley-hash\fR, \fIskiplist\fR, \fItwoskip\fR .IP "\fBzoneinfo_db_path:\fR " 5 .RS 5 The absolute path to the zoneinfo db file. If not specified, will be confdir/zoneinfo.db .RE .SH SEE ALSO .PP \fBimapd(8)\fR, \fBpop3d(8)\fR, \fBnntpd(8)\fR, \fBlmtpd(8)\fR, \fBhttpd(8)\fR, \fBtimsieved(8)\fR, \fBidled(8)\fR, \fBnotifyd(8)\fR, \fBdeliver(8)\fR, \fBmaster(8)\fR, \fBciphers(1)\fR cyrus-imapd-2.5.10/man/cyr_synclog.80000644000175000017500000000556313001236020014150 00000000000000.\" -*- nroff -*- .TH CYR_SYNCLOG 8 "Project Cyrus" CMU .\" .\" Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. .\" .\" Redistribution and use in source and binary forms, with or without .\" modification, are permitted provided that the following conditions .\" are met: .\" .\" 1. Redistributions of source code must retain the above copyright .\" notice, this list of conditions and the following disclaimer. .\" .\" 2. Redistributions in binary form must reproduce the above copyright .\" notice, this list of conditions and the following disclaimer in .\" the documentation and/or other materials provided with the .\" distribution. .\" .\" 3. The name "Carnegie Mellon University" must not be used to .\" endorse or promote products derived from this software without .\" prior written permission. For permission or any legal .\" details, please contact .\" Carnegie Mellon University .\" Center for Technology Transfer and Enterprise Creation .\" 4615 Forbes Avenue .\" Suite 302 .\" Pittsburgh, PA 15213 .\" (412) 268-7393, fax: (412) 268-7395 .\" innovation@andrew.cmu.edu .\" .\" 4. Redistributions of any form whatsoever must retain the following .\" acknowledgment: .\" "This product includes software developed by Computing Services .\" at Carnegie Mellon University (http://www.cmu.edu/computing/)." .\" .\" CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO .\" THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY .\" AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE .\" FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES .\" WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN .\" AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING .\" OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. .SH NAME cyr_synclog \- add entries to the replication log .SH SYNOPSIS .B cyr_synclog [ .B \-C .I config-file ] [ .B \-type ] .SH DESCRIPTION .I cyr_synclog is used to append a value to the log file. You can either specify the log type and value, or an entire log line. .PP \-u USER \-U UNUSER \-v SIEVE \-m MAILBOX \-M UNMAILBOX \-a APPEND \-c ACL \-q QUOTA \-n ANNOTATION \-s SEEN \-b SUBSCRIPTION .PP Running without any options will print a short usage document. .PP .I cyr_synclog reads any applicable configuration options out of the .IR imapd.conf (5) file unless specified otherwise by \fB-C\fR. .SH EXAMPLES Here are some example ways to use cyr_synclog: .PP cyr_synclog \-m user.brong cyr_synclog \-u brong cyr_synclog \-C /etc/imapd-special.conf \-s user.brong brong cyr_synclog "SEEN user.brong brong" .SH OPTIONS .TP .BI \-C " config-file" Read configuration options from \fIconfig-file\fR. .SH FILES .TP .B /etc/imapd.conf .SH SEE ALSO .PP \fBimapd.conf(5)\fR cyrus-imapd-2.5.10/man/mbpath.80000644000175000017500000000531213001236020013060 00000000000000.\" -*- nroff -*- .TH MBPATH 8 "Project Cyrus" CMU .\" .\" Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. .\" .\" Redistribution and use in source and binary forms, with or without .\" modification, are permitted provided that the following conditions .\" are met: .\" .\" 1. Redistributions of source code must retain the above copyright .\" notice, this list of conditions and the following disclaimer. .\" .\" 2. Redistributions in binary form must reproduce the above copyright .\" notice, this list of conditions and the following disclaimer in .\" the documentation and/or other materials provided with the .\" distribution. .\" .\" 3. The name "Carnegie Mellon University" must not be used to .\" endorse or promote products derived from this software without .\" prior written permission. For permission or any legal .\" details, please contact .\" Carnegie Mellon University .\" Center for Technology Transfer and Enterprise Creation .\" 4615 Forbes Avenue .\" Suite 302 .\" Pittsburgh, PA 15213 .\" (412) 268-7393, fax: (412) 268-7395 .\" innovation@andrew.cmu.edu .\" .\" 4. Redistributions of any form whatsoever must retain the following .\" acknowledgment: .\" "This product includes software developed by Computing Services .\" at Carnegie Mellon University (http://www.cmu.edu/computing/)." .\" .\" CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO .\" THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY .\" AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE .\" FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES .\" WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN .\" AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING .\" OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. .SH NAME mbpath \- translate mailbox names to filesystem paths .SH SYNOPSIS .B mbpath [ .B \-C .I config-file ] [ .B \-q ] [ .B \-s ] [ .B \-m ] [ .IR mailbox-names ... ] .SH DESCRIPTION Given a mailbox name or a space separated list of mailbox names, .I mbpath outputs the filesystem path to the mailbox. .PP .I Mbpath reads its configuration options out of the .IR imapd.conf (5) file unless specified otherwise by \fB-C\fR. .SH OPTIONS .TP .BI \-C " config-file" Read configuration options from \fIconfig-file\fR. .PP .I \-q suppress any error output. .PP .I \-s if any error occurs, stop processing the list of mailboxes and exit. .PP .I \-m output the path to the metadata files (if different from the message files). .SH FILES .TP .B /etc/imapd.conf .\" $Header: /mnt/data/cyrus/cvsroot/src/cyrus/man/mbpath.8,v 1.8 2010/01/06 17:01:52 murch Exp $ cyrus-imapd-2.5.10/man/master.80000644000175000017500000001332613001236020013104 00000000000000.\" -*- nroff -*- .TH MASTER 8 "Project Cyrus" CMU .\" .\" Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. .\" .\" Redistribution and use in source and binary forms, with or without .\" modification, are permitted provided that the following conditions .\" are met: .\" .\" 1. Redistributions of source code must retain the above copyright .\" notice, this list of conditions and the following disclaimer. .\" .\" 2. Redistributions in binary form must reproduce the above copyright .\" notice, this list of conditions and the following disclaimer in .\" the documentation and/or other materials provided with the .\" distribution. .\" .\" 3. The name "Carnegie Mellon University" must not be used to .\" endorse or promote products derived from this software without .\" prior written permission. For permission or any legal .\" details, please contact .\" Carnegie Mellon University .\" Center for Technology Transfer and Enterprise Creation .\" 4615 Forbes Avenue .\" Suite 302 .\" Pittsburgh, PA 15213 .\" (412) 268-7393, fax: (412) 268-7395 .\" innovation@andrew.cmu.edu .\" .\" 4. Redistributions of any form whatsoever must retain the following .\" acknowledgment: .\" "This product includes software developed by Computing Services .\" at Carnegie Mellon University (http://www.cmu.edu/computing/)." .\" .\" CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO .\" THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY .\" AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE .\" FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES .\" WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN .\" AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING .\" OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. .SH NAME master \- master Cyrus process .SH SYNOPSIS .B master [ .B \-C .I alternate imapd.conf ] [ .B \-M .I alternate cyrus.conf ] [ .B \-l .I listen queue ] [ .B \-p .I pidfile ] [ .B \-P .I snmp agentx ping interval ] [ .B \-j .I janitor period ] [ .B \-d ] [ .B \-D ] [ .B \-x .I snmp agentx socket ] .SH DESCRIPTION .I Master is the process that controls all of the Cyrus processes. This process is responsible for creating all imapd, pop3d, lmtpd and sieved child processes. This process also initializes the Berkeley DB code and performs scheduled cleanup/maintenance. .PP If this process dies, then no new sessions will be started. .PP It kills itself and all child processes when it receives a SIGTERM. .SH OPTIONS .TP .BI \-C " alternate imapd.conf" Specifies an alternate imapd.conf for use by master (note that this will not affect any sub-processes spawned by master, you should specify those specifically in the respective entries in cyrus.conf). .TP .BI \-M " alternate cyrus.conf" Specifies an alternate cyrus.conf for use by master. .TP .BI \-l " listen queue backlog" Increase the listen queue backlog. By default, the listen queue is set to 32. On systems with a high connection rate, it may be desirable to increase this value. refer to \fBlisten(2)\fR for details. .TP .BI \-j " janitor full-sweeps per second" Sets the amount of times per second the janitor should sweep the entire child table. Leave it at the default of 1 unless you have a really high fork rate (and you have not increased the child hash table size when you compiled Cyrus from its default of 10000 entries). .TP .BI \-p " pidfile" Use .I pidfile as the pidfile. If not specified, defaults to /var/run/cyrus-master.pid .TP .BI \-P " snmp agentx ping interval" Sets the amount on time in seconds the subagent will try and reconnect to the master agent (snmpd) if it ever becomes (or starts) disconnected. Requires net-snmp 5.0 or higher. .TP .BI \-d Start in daemon mode (run in background and disconnect from controlling terminal). .TP .BI \-D Don't close stdin/stdout/stderr. Primarily useful for debugging. Note that -d and -D cannot be used together; consider using -L instead. .TP .BI \-L " logfile" Redirect stdout and stderr to the given \fIlogfile\fP. .TP .BI \-x " snmp agentx socket" Address the master agent (most likely snmpd) listens on. Requires net-snmp 5.0 or higher. .SH CONFIGURATION Upon execution, .I master reads its configuration information out of the .IR cyrus.conf (5) file. .PP .I Master rereads its configuration file when it receives a hangup signal, SIGHUP. Services and events may be added, deleted or modified when the configuration file is reread. Any active services removed from the configuration file will be allowed to run until completion. Services added or modified to listen on a privileged port may not be able to bind the port, depending on your system configuration. In this case a full restart is needed. .PP .I Master propagates the hangup signal, SIGHUP, to its child service processes, so that they stop waiting for incoming connections and exit, allowing them to be recycled. This is useful to make services take into account a new version of the .IR imapd.conf (5) file. Children that are servicing a client connection when SIGHUP is received are allowed to run until the client logouts before being recycled. It may take a long time until the client logouts, so a log message is generated for processes that have not been recycled within 30s. .SH NOTES The environment variable \fBCYRUS_VERBOSE\fR can be set to log additional debugging information. Setting the value to 1 results in base level logging. Setting it higher results in more log messages being generated. .SH FILES .TP .B /etc/cyrus.conf, /etc/imapd.conf, /var/run/cyrus-master.pid .SH SEE ALSO .PP \fBcyrus.conf(5)\fR, \fBimapd.conf(5)\fR, \fBimapd(8)\fR, \fBpop3d(8)\fR, \fBlmtpd(8)\fR, \fBtimsieved(8)\fR, \fBidled(8)\fR cyrus-imapd-2.5.10/man/sieveshell.10000644000175000017500000001337513001246643013765 00000000000000.\" Automatically generated by Pod::Man 2.28 (Pod::Simple 3.29) .\" .\" Standard preamble: .\" ======================================================================== .de Sp \" Vertical space (when we can't use .PP) .if t .sp .5v .if n .sp .. .de Vb \" Begin verbatim text .ft CW .nf .ne \\$1 .. .de Ve \" End verbatim text .ft R .fi .. .\" Set up some character translations and predefined strings. \*(-- will .\" give an unbreakable dash, \*(PI will give pi, \*(L" will give a left .\" double quote, and \*(R" will give a right double quote. \*(C+ will .\" give a nicer C++. Capital omega is used to do unbreakable dashes and .\" therefore won't be available. \*(C` and \*(C' expand to `' in nroff, .\" nothing in troff, for use with C<>. .tr \(*W- .ds C+ C\v'-.1v'\h'-1p'\s-2+\h'-1p'+\s0\v'.1v'\h'-1p' .ie n \{\ . ds -- \(*W- . ds PI pi . if (\n(.H=4u)&(1m=24u) .ds -- \(*W\h'-12u'\(*W\h'-12u'-\" diablo 10 pitch . if (\n(.H=4u)&(1m=20u) .ds -- \(*W\h'-12u'\(*W\h'-8u'-\" diablo 12 pitch . ds L" "" . ds R" "" . ds C` "" . ds C' "" 'br\} .el\{\ . ds -- \|\(em\| . ds PI \(*p . ds L" `` . ds R" '' . ds C` . ds C' 'br\} .\" .\" Escape single quotes in literal strings from groff's Unicode transform. .ie \n(.g .ds Aq \(aq .el .ds Aq ' .\" .\" If the F register is turned on, we'll generate index entries on stderr for .\" titles (.TH), headers (.SH), subsections (.SS), items (.Ip), and index .\" entries marked with X<> in POD. Of course, you'll have to process the .\" output yourself in some meaningful fashion. .\" .\" Avoid warning from groff about undefined register 'F'. .de IX .. .nr rF 0 .if \n(.g .if rF .nr rF 1 .if (\n(rF:(\n(.g==0)) \{ . if \nF \{ . de IX . tm Index:\\$1\t\\n%\t"\\$2" .. . if !\nF==2 \{ . nr % 0 . nr F 2 . \} . \} .\} .rr rF .\" .\" Accent mark definitions (@(#)ms.acc 1.5 88/02/08 SMI; from UCB 4.2). .\" Fear. Run. Save yourself. No user-serviceable parts. . \" fudge factors for nroff and troff .if n \{\ . ds #H 0 . ds #V .8m . ds #F .3m . ds #[ \f1 . ds #] \fP .\} .if t \{\ . ds #H ((1u-(\\\\n(.fu%2u))*.13m) . ds #V .6m . ds #F 0 . ds #[ \& . ds #] \& .\} . \" simple accents for nroff and troff .if n \{\ . ds ' \& . ds ` \& . ds ^ \& . ds , \& . ds ~ ~ . ds / .\} .if t \{\ . ds ' \\k:\h'-(\\n(.wu*8/10-\*(#H)'\'\h"|\\n:u" . ds ` \\k:\h'-(\\n(.wu*8/10-\*(#H)'\`\h'|\\n:u' . ds ^ \\k:\h'-(\\n(.wu*10/11-\*(#H)'^\h'|\\n:u' . ds , \\k:\h'-(\\n(.wu*8/10)',\h'|\\n:u' . ds ~ \\k:\h'-(\\n(.wu-\*(#H-.1m)'~\h'|\\n:u' . ds / \\k:\h'-(\\n(.wu*8/10-\*(#H)'\z\(sl\h'|\\n:u' .\} . \" troff and (daisy-wheel) nroff accents .ds : \\k:\h'-(\\n(.wu*8/10-\*(#H+.1m+\*(#F)'\v'-\*(#V'\z.\h'.2m+\*(#F'.\h'|\\n:u'\v'\*(#V' .ds 8 \h'\*(#H'\(*b\h'-\*(#H' .ds o \\k:\h'-(\\n(.wu+\w'\(de'u-\*(#H)/2u'\v'-.3n'\*(#[\z\(de\v'.3n'\h'|\\n:u'\*(#] .ds d- \h'\*(#H'\(pd\h'-\w'~'u'\v'-.25m'\f2\(hy\fP\v'.25m'\h'-\*(#H' .ds D- D\\k:\h'-\w'D'u'\v'-.11m'\z\(hy\v'.11m'\h'|\\n:u' .ds th \*(#[\v'.3m'\s+1I\s-1\v'-.3m'\h'-(\w'I'u*2/3)'\s-1o\s+1\*(#] .ds Th \*(#[\s+2I\s-2\h'-\w'I'u*3/5'\v'-.3m'o\v'.3m'\*(#] .ds ae a\h'-(\w'a'u*4/10)'e .ds Ae A\h'-(\w'A'u*4/10)'E . \" corrections for vroff .if v .ds ~ \\k:\h'-(\\n(.wu*9/10-\*(#H)'\s-2\u~\d\s+2\h'|\\n:u' .if v .ds ^ \\k:\h'-(\\n(.wu*10/11-\*(#H)'\v'-.4m'^\v'.4m'\h'|\\n:u' . \" for low resolution devices (crt and lpr) .if \n(.H>23 .if \n(.V>19 \ \{\ . ds : e . ds 8 ss . ds o a . ds d- d\h'-1'\(ga . ds D- D\h'-1'\(hy . ds th \o'bp' . ds Th \o'LP' . ds ae ae . ds Ae AE .\} .rm #[ #] #H #V #F C .\" ======================================================================== .\" .IX Title "SIEVESHELL 1" .TH SIEVESHELL 1 "2016-10-17" "perl v5.22.2" "User Contributed Perl Documentation" .\" For nroff, turn off justification. Always turn off hyphenation; it makes .\" way too many mistakes in technical documents. .if n .ad l .nh .SH "NAME" sieveshell \- remotely manipulate sieve scripts .SH "SYNOPSIS" .IX Header "SYNOPSIS" sieveshell [\fB\-\-user\fR=\fIuser\fR] [\fB\-\-authname\fR=\fIauthname\fR] [\fB\-\-realm\fR=\fIrealm\fR] [\fB\-\-exec\fR=\fIscript\fR] \fIserver\fR[\fB:\fR\fIport\fR] .PP sieveshell \fB\-\-help\fR .SH "DESCRIPTION" .IX Header "DESCRIPTION" \&\fBsieveshell\fR allows users to manipulate their scripts on a remote server. It works via \s-1MANAGESIEVE,\s0 a work in progress. .PP The following commands are recognized: .Sp .RS 4 \&\fBlist\fR list scripts on server. .Sp \&\fBput\fR upload script to server. .Sp \&\fBget\fR [] get script. if no filename display to stdout .Sp \&\fBdelete\fR delete script. .Sp \&\fBactivate\fR activate script. .Sp \&\fBdeactivate\fR deactivate all scripts. .RE .SH "OPTIONS" .IX Header "OPTIONS" .IP "\fB\-u\fR \fIuser\fR, \fB\-\-user\fR=\fIuser\fR" 4 .IX Item "-u user, --user=user" The authorization name to request; by default, derived from the authentication credentials. .IP "\fB\-a\fR \fIauthname\fR, \fB\-\-authname\fR=\fIauthname\fR" 4 .IX Item "-a authname, --authname=authname" The user to use for authentication (defaults to current user). .IP "\fB\-r\fR \fIrealm\fR, \fB\-\-realm\fR=\fIrealm\fR" 4 .IX Item "-r realm, --realm=realm" The realm to attempt authentication in. .IP "\fB\-e\fR \fIscript\fR, \fB\-\-exec\fR=\fIscript\fR" 4 .IX Item "-e script, --exec=script" Instead of working interactively, run commands from \fIscript\fR, and exit when done. .SH "REFERENCES" .IX Header "REFERENCES" [\s-1MANAGESIEVE\s0] Martin, T.; \*(L"A Protocol for Remotely Managing Sieve Scripts\*(R", draft\-ietf\-managesieve\-03.txt, Mirapoint, Inc.; May 2001, work in progress. .SH "AUTHOR" .IX Header "AUTHOR" Tim Martin , and the rest of the Cyrus team . cyrus-imapd-2.5.10/man/krb.equiv.50000644000175000017500000000500713001236020013511 00000000000000.\" -*- nroff -*- .TH KRB.EQUIV 5 "Project Cyrus" CMU .\" .\" Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. .\" .\" Redistribution and use in source and binary forms, with or without .\" modification, are permitted provided that the following conditions .\" are met: .\" .\" 1. Redistributions of source code must retain the above copyright .\" notice, this list of conditions and the following disclaimer. .\" .\" 2. Redistributions in binary form must reproduce the above copyright .\" notice, this list of conditions and the following disclaimer in .\" the documentation and/or other materials provided with the .\" distribution. .\" .\" 3. The name "Carnegie Mellon University" must not be used to .\" endorse or promote products derived from this software without .\" prior written permission. For permission or any legal .\" details, please contact .\" Carnegie Mellon University .\" Center for Technology Transfer and Enterprise Creation .\" 4615 Forbes Avenue .\" Suite 302 .\" Pittsburgh, PA 15213 .\" (412) 268-7393, fax: (412) 268-7395 .\" innovation@andrew.cmu.edu .\" .\" 4. Redistributions of any form whatsoever must retain the following .\" acknowledgment: .\" "This product includes software developed by Computing Services .\" at Carnegie Mellon University (http://www.cmu.edu/computing/)." .\" .\" CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO .\" THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY .\" AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE .\" FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES .\" WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN .\" AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING .\" OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. .SH NAME \fB/etc/krb.equiv\fR \- Kerberos equivalences .SH DESCRIPTION .I krb.equiv contains zero or more lines, each of which describes a mapping of a kerberos principal (\fIuserid@host\fR) to a local user (\fIuserid\fR or alias). Each line of the file consists of two fields, separated by at least one whitespace character; other blanks are ignored. The first field is the kerberos principal name to remap, and the second is the name of the corresponding local user. .SH SAMPLE FILE .PP .nf tyq4@ANDY.CMU.EDU tyq4 tyq4@DEANNA.ORG tyq4 ty347@ECE.CMU.EDU tyq4 jj12@ANDY.CMU.EDU tick tick@DEANNA.ORG tick jy9o@ANDY.CMU.EDU jyager jyager@CS.CMU.EDU jyager cyrus-imapd-2.5.10/man/httpd.80000644000175000017500000000707213001236020012735 00000000000000.\" -*- nroff -*- .TH HTTPD 8 "Project Cyrus" CMU .\" .\" Copyright (c) 1994-2011 Carnegie Mellon University. All rights reserved. .\" .\" Redistribution and use in source and binary forms, with or without .\" modification, are permitted provided that the following conditions .\" are met: .\" .\" 1. Redistributions of source code must retain the above copyright .\" notice, this list of conditions and the following disclaimer. .\" .\" 2. Redistributions in binary form must reproduce the above copyright .\" notice, this list of conditions and the following disclaimer in .\" the documentation and/or other materials provided with the .\" distribution. .\" .\" 3. The name "Carnegie Mellon University" must not be used to .\" endorse or promote products derived from this software without .\" prior written permission. For permission or any legal .\" details, please contact .\" Carnegie Mellon University .\" Center for Technology Transfer and Enterprise Creation .\" 4615 Forbes Avenue .\" Suite 302 .\" Pittsburgh, PA 15213 .\" (412) 268-7393, fax: (412) 268-7395 .\" innovation@andrew.cmu.edu * .\" 4. Redistributions of any form whatsoever must retain the following .\" acknowledgment: .\" "This product includes software developed by Computing Services .\" at Carnegie Mellon University (http://www.cmu.edu/computing/)." .\" .\" CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO .\" THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY .\" AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE .\" FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES .\" WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN .\" AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING .\" OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. .\" .SH NAME httpd \- HTTP server process .SH SYNOPSIS .B httpd [ .B \-C .I config-file ] [ .B \-U .I uses ] [ .B \-T .I timeout ] [ .B \-D ] .br [ .B \-s ] [ .B \-p .I ssf ] .SH DESCRIPTION .I Httpd is a HTTP server. It accepts commands on its standard input and responds on its standard output. It MUST invoked by .IR master (8) with those descriptors attached to a remote client connection. .PP .I Httpd reads its configuration options out of the .IR imapd.conf (5) file unless specified otherwise by \fB-C\fR. .PP If the directory .RI log/ user exists under the directory specified in the .I configdirectory configuration option, then .I httpd will create protocol telemetry logs for sessions authenticating as .IR user . The telemetry logs will be stored in the .RI log/ user directory with a filename of the .I httpd process-id. .SH OPTIONS .TP .BI \-C " config-file" Read configuration options from \fIconfig-file\fR. .TP .BI \-U " uses" The maximum number of times that the process should be used for new connections before shutting down. The default is 250. .TP .BI \-T " timeout" The number of seconds that the process will wait for a new connection before shutting down. Note that a value of 0 (zero) will disable the timeout. The default is 60. .TP .BI \-D Run external debugger specified in debug_command. .TP .BI \-s Serve HTTP over SSL (https). All data to and from .I httpd is encrypted using the Secure Sockets Layer. .TP .BI \-p " ssf" Tell .I httpd that an external layer exists. An SSF (security strength factor) of 1 means an integrity protection layer exists. Any higher SSF implies some form of privacy protection. .SH FILES .TP .B /etc/imapd.conf .SH SEE ALSO .PP \fBimapd.conf(5)\fR, \fBmaster(8)\fR cyrus-imapd-2.5.10/man/quota.80000644000175000017500000000632213001236020012740 00000000000000.\" -*- nroff -*- .TH QUOTA 8 "Project Cyrus" CMU .\" .\" Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. .\" .\" Redistribution and use in source and binary forms, with or without .\" modification, are permitted provided that the following conditions .\" are met: .\" .\" 1. Redistributions of source code must retain the above copyright .\" notice, this list of conditions and the following disclaimer. .\" .\" 2. Redistributions in binary form must reproduce the above copyright .\" notice, this list of conditions and the following disclaimer in .\" the documentation and/or other materials provided with the .\" distribution. .\" .\" 3. The name "Carnegie Mellon University" must not be used to .\" endorse or promote products derived from this software without .\" prior written permission. For permission or any legal .\" details, please contact .\" Carnegie Mellon University .\" Center for Technology Transfer and Enterprise Creation .\" 4615 Forbes Avenue .\" Suite 302 .\" Pittsburgh, PA 15213 .\" (412) 268-7393, fax: (412) 268-7395 .\" innovation@andrew.cmu.edu .\" .\" 4. Redistributions of any form whatsoever must retain the following .\" acknowledgment: .\" "This product includes software developed by Computing Services .\" at Carnegie Mellon University (http://www.cmu.edu/computing/)." .\" .\" CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO .\" THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY .\" AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE .\" FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES .\" WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN .\" AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING .\" OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. .SH NAME quota \- report and optionally fix quota usage .SH SYNOPSIS .B quota [ .B \-C .I config-file ] [ .B \-d .I domain ] [ .B \-f ] [ .IR mailbox-prefix ... ] .SH DESCRIPTION .I Quota generates a report listing quota roots, giving their limits and usage. If the .I \-f option is given, .I quota first fixes any inconsistencies in the quota subsystem, such as mailboxes with the wrong quota root or quota roots with the wrong quota usage reported. If an optional .I domain is given, the quota listing (and inconsistency fixing) is performed in that domain rather than the default domain. If any optional .I mailbox-prefix arguments are given, the quota listing (and inconsistency fixing) is limited to quota roots with names that start with one of the given prefixes. .PP Running .I quota with both the .I \-f option and .I mailbox-prefix arguments is not recommended. .PP .I Quota reads its configuration options out of the .IR imapd.conf (5) file unless specified otherwise by \fB-C\fR. .SH OPTIONS .TP .BI \-C " config-file" Read configuration options from \fIconfig-file\fR. .TP .BI \-d " domain" List/fix quotas in \fIdomain\fR. .TP .B \-f Fix any inconsistencies in the quota subsystem before generating a report. .TP .B \-q Quiet. If -f is specified, then don't print the quota vaules, only print messages when things are changed. .SH FILES .TP .B /etc/imapd.conf cyrus-imapd-2.5.10/man/squatter.80000644000175000017500000001013513001236020013454 00000000000000.\" -*- nroff -*- .TH SQUATTER 8 "Project Cyrus" CMU .\" .\" Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. .\" .\" Redistribution and use in source and binary forms, with or without .\" modification, are permitted provided that the following conditions .\" are met: .\" .\" 1. Redistributions of source code must retain the above copyright .\" notice, this list of conditions and the following disclaimer. .\" .\" 2. Redistributions in binary form must reproduce the above copyright .\" notice, this list of conditions and the following disclaimer in .\" the documentation and/or other materials provided with the .\" distribution. .\" .\" 3. The name "Carnegie Mellon University" must not be used to .\" endorse or promote products derived from this software without .\" prior written permission. For permission or any legal .\" details, please contact .\" Carnegie Mellon University .\" Center for Technology Transfer and Enterprise Creation .\" 4615 Forbes Avenue .\" Suite 302 .\" Pittsburgh, PA 15213 .\" (412) 268-7393, fax: (412) 268-7395 .\" innovation@andrew.cmu.edu .\" .\" 4. Redistributions of any form whatsoever must retain the following .\" acknowledgment: .\" "This product includes software developed by Computing Services .\" at Carnegie Mellon University (http://www.cmu.edu/computing/)." .\" .\" CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO .\" THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY .\" AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE .\" FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES .\" WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN .\" AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING .\" OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. .SH NAME squatter \- create SQUAT indexes for mailboxes .SH SYNOPSIS .B squatter [ .B \-C .I config-file ] [ .B \-r ] [ .B \-s ] [ .B \-i ] [ .B \-a ] [ .B \-v ] .IR mailbox ... .SH DESCRIPTION .I Squatter creates a new SQUAT index for one or more IMAP mailboxes. The SQUAT index is a unified index of all of the header and body text of each message a given mailbox. This index is used to significantly reduce IMAP SEARCH times on a mailbox. .PP .I Squatter creates an index of ALL messages in the mailbox, not just those since the last time that it was run (i.e., it does NOT do incremental updates). Any messages appended to the mailbox after .I squatter is run, will NOT be included in the index. To include new messages in the index, .I squatter must be run again. For large and active mailboxes, it is recommended to run .I squatter periodically as an EVENT in .IR cyrus.conf (5) . .PP .B NOTE: Messages and mailboxes that have not been indexed CAN still be SEARCHed, just not as quickly as those with a SQUAT index. .PP .I Squatter reads its configuration options out of the .IR imapd.conf (5) file unless specified otherwise by \fB-C\fR. .SH OPTIONS .TP .BI \-C " config-file" Read configuration options from \fIconfig-file\fR. .TP .B \-r Recursively create indexes for all sub-mailboxes of the mailboxes or mailbox prefixes given as arguments. .TP .B \-s Skip mailboxes whose index file is older than their current squat file (within a small time delta). .TP .B \-i Incremental updates where squat indexes already exist. .TP .B \-a Only create indexes for mailboxes which have the shared \fI/vendor/cmu/cyrus-imapd/squat\fR annotation set to "true". .br .sp The value of the \fB/vendor/cmu/cyrus-imapd/squat\fR annotation is inherited by all children of the given mailbox, so an entire mailbox tree can be indexed (or not indexed) by setting a single annotation on the root of that tree with a value of "true" (or "false"). If a mailbox does not have a \fB/vendor/cmu/cyrus-imapd/squat\fR annotation set on it (or does not inherit one), then the mailbox is not indexed. In other words, the implicit value of \fB/vendor/cmu/cyrus-imapd/squat\fR is "false". .TP .B \-v Increase the verbosity of progress/status messages. .SH FILES .TP .B /etc/imapd.conf /etc/cyrus.conf cyrus-imapd-2.5.10/man/cyr_info.80000644000175000017500000000621213001236020013415 00000000000000.\" -*- nroff -*- .TH CYR_INFO 8 "Project Cyrus" CMU .\" .\" Copyright (c) 1994-2009 Carnegie Mellon University. All rights reserved. .\" .\" Redistribution and use in source and binary forms, with or without .\" modification, are permitted provided that the following conditions .\" are met: .\" .\" 1. Redistributions of source code must retain the above copyright .\" notice, this list of conditions and the following disclaimer. .\" .\" 2. Redistributions in binary form must reproduce the above copyright .\" notice, this list of conditions and the following disclaimer in .\" the documentation and/or other materials provided with the .\" distribution. .\" .\" 3. The name "Carnegie Mellon University" must not be used to .\" endorse or promote products derived from this software without .\" prior written permission. For permission or any legal .\" details, please contact .\" Carnegie Mellon University .\" Center for Technology Transfer and Enterprise Creation .\" 4615 Forbes Avenue .\" Suite 302 .\" Pittsburgh, PA 15213 .\" (412) 268-7393, fax: (412) 268-7395 .\" innovation@andrew.cmu.edu .\" .\" 4. Redistributions of any form whatsoever must retain the following .\" acknowledgment: .\" "This product includes software developed by Computing Services .\" at Carnegie Mellon University (http://www.cmu.edu/computing/)." .\" .\" CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO .\" THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY .\" AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE .\" FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES .\" WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN .\" AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING .\" OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. .SH NAME cyr_info \- general cyrus inspection tool .SH SYNOPSIS .B cyr_info [ .B \-C .I alt imapd.conf ] [ .B \-M .I alt cyrus.conf ] command .SH DESCRIPTION .I Cyr_info is a tool for getting information from Cyrus. The intent is to extend this tool with useful commands to make managing and configuring Cyrus easier. .I Cyr_info reads its configuration options out of the .IR imapd.conf (5) file unless specified otherwise by \fB-C\fR. .SH OPTIONS .TP .BI \-C " file" Read configuration options from \fIfile\fR (imapd.conf format). .TP .BI \-M " file" Read service specifications from \fIfile\fR (cyrus.conf format). .TP .BI \-n " name" Read the configuration as if for the service named \fIname\fR. .SH COMMANDS .TP .BI allconf print ALL configuration options - including default options .TP .BI conf print only the configuration options which are not the same as default (regardless of whether you have specified them or not) .TP .BI lint print only configuration options which are NOT recognised. This command should not print anything. It uses cyrus.conf to find the names of configured services to avoid displaying any known configuration options for the named service. .TP .BI proc print all currently connected processes in the proc directory .SH FILES .B /etc/imapd.conf .B /etc/cyrus.conf cyrus-imapd-2.5.10/man/ctl_mboxlist.80000644000175000017500000001114313001236020014307 00000000000000.\" -*- nroff -*- .TH CTL_MBOXLIST 8 "Project Cyrus" CMU .\" .\" Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. .\" .\" Redistribution and use in source and binary forms, with or without .\" modification, are permitted provided that the following conditions .\" are met: .\" .\" 1. Redistributions of source code must retain the above copyright .\" notice, this list of conditions and the following disclaimer. .\" .\" 2. Redistributions in binary form must reproduce the above copyright .\" notice, this list of conditions and the following disclaimer in .\" the documentation and/or other materials provided with the .\" distribution. .\" .\" 3. The name "Carnegie Mellon University" must not be used to .\" endorse or promote products derived from this software without .\" prior written permission. For permission or any legal .\" details, please contact .\" Carnegie Mellon University .\" Center for Technology Transfer and Enterprise Creation .\" 4615 Forbes Avenue .\" Suite 302 .\" Pittsburgh, PA 15213 .\" (412) 268-7393, fax: (412) 268-7395 .\" innovation@andrew.cmu.edu .\" 4. Redistributions of any form whatsoever must retain the following .\" acknowledgment: .\" "This product includes software developed by Computing Services .\" at Carnegie Mellon University (http://www.cmu.edu/computing/)." .\" .\" CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO .\" THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY .\" AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE .\" FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES .\" WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN .\" AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING .\" OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. .SH NAME ctl_mboxlist \- perform operations on the mailbox list database .SH SYNOPSIS .B ctl_mboxlist [ .B \-C .I config-file ] .B \-d [ .B \-x ] [ \fB\-p \fIpartition\fR ] .br [ \fB\-f \fIfilename\fR ] .br .B ctl_mboxlist [ .B \-C .I config-file ] .B \-u [ \fB\-f \fIfilename\fR ] .br .B ctl_mboxlist [ .B \-C .I config-file ] .B \-m [ \fB\-a \fR ] [ \fB\-w \fR ] [ \fB\-i \fR ] .br [ \fB\-f \fIfilename\fR ] .br .B ctl_mboxlist [ .B \-C .I config-file ] .B \-v [ \fB\-f \fIfilename\fR ] .SH DESCRIPTION .I Ctl_mboxlist is used to perform various administrative operations on the mailbox list database. .PP .I Ctl_mboxlist reads its configuration options out of the .IR imapd.conf (5) file unless specified otherwise by \fB-C\fR. The .I configdirectory option is used to determine the default location of the mailbox list database. .SH OPTIONS .TP .BI \-C\ "config-file" Read configuration options from \fIconfig-file\fR. .TP .B \-d Dump the contents of the database to standard output in a portable flat-text format. NOTE: In Cyrus versions 2.2.13 and earlier, the dump format did not include the mailbox type flags, breaking remote mailboxes (frontends, mupdate master, unified backends) when undumped. .TP .B \-x When performing a dump, remove the mailboxes dumped from the mailbox list (mostly useful when specified with -p) .TP .BI \-p\ "partition" When performing a dump, dump only thise mailboxes that live on \fIpartition\fR .TP .B \-u Load the contents of the database from standard input. The input MUST be in the format output using the \fB\-d\fR option. NOTE: Both the old and new formats can be loaded, but the old format will break remote mailboxes. .TP .B \-m For backend servers in the Cyrus Murder, synchronize the local mailbox list file with the MUPDATE server. .TP .B \-a When used with -m, assume the local mailboxes file is authoritiative, that is, only change the mupdate server, do not delete any local mailboxes. USE THIS OPTION WITH CARE, as it allows namespace collisions into the murder. .TP .B \-w When used with -m, print out what would be done but do not perform the operations. .TP .B \-i When used with -m, asks for verification before deleting local mailboxes. .TP .B \-v Verify the consistency of the mailbox list database and the spool partition(s). Mailboxes present in the database and not located on a spool partition, and those located on a spool partition (directory containing a valid cyrus.header file) and not present in the database will be reported. Note that this function is very I/O intensive. .TP \fB\-f \fIfilename\fR Use the database specified by \fIfilename\fR instead of the default (\fIconfigdirectory\fB/mailboxes.db\fR). .SH FILES .TP .B /etc/imapd.conf .SH SEE ALSO .PP \fBimapd.conf(5)\fR, \fBmaster(8)\fR cyrus-imapd-2.5.10/man/ipurge.80000644000175000017500000000757113001236020013111 00000000000000.\" -*- nroff -*- .TH IPURGE 8 "Project Cyrus" CMU .\" .\" Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. .\" .\" Redistribution and use in source and binary forms, with or without .\" modification, are permitted provided that the following conditions .\" are met: .\" .\" 1. Redistributions of source code must retain the above copyright .\" notice, this list of conditions and the following disclaimer. .\" .\" 2. Redistributions in binary form must reproduce the above copyright .\" notice, this list of conditions and the following disclaimer in .\" the documentation and/or other materials provided with the .\" distribution. .\" .\" 3. The name "Carnegie Mellon University" must not be used to .\" endorse or promote products derived from this software without .\" prior written permission. For permission or any legal .\" details, please contact .\" Carnegie Mellon University .\" Center for Technology Transfer and Enterprise Creation .\" 4615 Forbes Avenue .\" Suite 302 .\" Pittsburgh, PA 15213 .\" (412) 268-7393, fax: (412) 268-7395 .\" innovation@andrew.cmu.edu .\" .\" 4. Redistributions of any form whatsoever must retain the following .\" acknowledgment: .\" "This product includes software developed by Computing Services .\" at Carnegie Mellon University (http://www.cmu.edu/computing/)." .\" .\" CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO .\" THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY .\" AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE .\" FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES .\" WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN .\" AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING .\" OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. .SH NAME ipurge \- delete mail from IMAP mailbox or partition based on age or size .SH SYNOPSIS .B ipurge [ .B \-f ] [ .B \-C .I config-file ] [ .B \-x ] [ .B \-X ] [ .B \-i ] [ .B \-s ] [ .B \-o ] [ .B \-n ] .br [ .BI \-d " days" | .BI \-b " bytes" | .BI \-k " Kbytes" | .BI \-m " Mbytes" ] .br [ .IR mailbox-pattern ... ] .SH DESCRIPTION .I Ipurge deletes messages from the mailbox(es) specified by \fImailbox-pattern\fR that are older or larger than specified by the \fB-d\fR, \fB-b\fR, \fB-k\fR or \fB-m\fR options. If no \fImailbox-pattern\fR is given, \fIipurge\fR works on all mailboxes. If the \fB-x\fR option is given, the message age and size MUST match exactly those specified by \fB-d\fR, \fB-b\fR, \fB-k\fR or \fB-m\fR. The are no default values, and at least one of \fB-d\fR, \fB-b\fR, \fB-k\fR or \fB-m\fR MUST be specified. .PP .I Ipurge by default only deletes mail below shared folders, which means that mails in mailbox(es) below INBOX.* and user.* stay untouched. Use the option \fB-f\fR to also delete mail in mailbox(es) below these folders. .PP .I Ipurge reads its configuration options out of the .IR imapd.conf (5) file unless specified otherwise by \fB-C\fR. .SH OPTIONS .TP .BI \-f Force deletion of mail in \fIall\fR mailboxes. .TP .BI \-C " config-file" Read configuration options from \fIconfig-file\fR. .TP .BI \-d " days" Age of message in \fIdays\fR. .TP .BI \-b " bytes" Size of message in \fIbytes\fR. .TP .BI \-k " Kbytes" Size of message in \fIKbytes\fR (2^10 bytes). .TP .BI \-m " Mbytes" Size of message in \fIMbytes\fR (2^20 bytes). .TP .B \-x Perform an exact match on age or size (instead of older or larger). .TP .B \-X Use delivery time instead of Date: header for date matches .TP .B \-i Invert match logic: -x means not equal, date is for newer, size is for smaller .TP .B \-s Skip over messages that have the \\Flagged flag set. .TP .B \-o Only purge messages that have the \\Deleted flag set. .TP .B \-n Only print messages that would be deleted (dry run). .SH FILES .TP .B /etc/imapd.conf cyrus-imapd-2.5.10/man/timsieved.80000644000175000017500000000526613001236020013606 00000000000000.\" -*- nroff -*- .TH TIMSIEVED 8 "Project Cyrus" CMU .\" .\" Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. .\" .\" Redistribution and use in source and binary forms, with or without .\" modification, are permitted provided that the following conditions .\" are met: .\" .\" 1. Redistributions of source code must retain the above copyright .\" notice, this list of conditions and the following disclaimer. .\" .\" 2. Redistributions in binary form must reproduce the above copyright .\" notice, this list of conditions and the following disclaimer in .\" the documentation and/or other materials provided with the .\" distribution. .\" .\" 3. The name "Carnegie Mellon University" must not be used to .\" endorse or promote products derived from this software without .\" prior written permission. For permission or any legal .\" details, please contact .\" Carnegie Mellon University .\" Center for Technology Transfer and Enterprise Creation .\" 4615 Forbes Avenue .\" Suite 302 .\" Pittsburgh, PA 15213 .\" (412) 268-7393, fax: (412) 268-7395 .\" innovation@andrew.cmu.edu .\" .\" 4. Redistributions of any form whatsoever must retain the following .\" acknowledgment: .\" "This product includes software developed by Computing Services .\" at Carnegie Mellon University (http://www.cmu.edu/computing/)." .\" .\" CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO .\" THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY .\" AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE .\" FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES .\" WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN .\" AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING .\" OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. .SH NAME timsieved \- CMU hack for getting sieve scripts onto the server .SH SYNOPSIS .B timsieved [ .B \-C .I config-file ] .SH DESCRIPTION .I timsieved is a server that allows users to remotely manage their sieve scripts kept on the server. It accepts commands on its standard input and responds on its standard output. It MUST be invoked by .IR master (8) with those descriptors attached to a remote client connection. .PP Cyrus admins that authenticate and authorize as themselves (e.g. don't proxy) manage global scripts. .PP .I Timsieved reads its configuration options out of the .IR imapd.conf (5) file unless specified otherwise by \fB-C\fR. .PP .SH OPTIONS .TP .BI \-C " config-file" Read configuration options from \fIconfig-file\fR. .SH FILES .TP .B /etc/imapd.conf .SH SEE ALSO .PP \fBimapd.conf(5)\fR, \fBmaster(8)\fR cyrus-imapd-2.5.10/man/imapd.80000644000175000017500000001073513001236020012704 00000000000000.\" -*- nroff -*- .TH IMAPD 8 "Project Cyrus" CMU .\" .\" Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. .\" .\" Redistribution and use in source and binary forms, with or without .\" modification, are permitted provided that the following conditions .\" are met: .\" .\" 1. Redistributions of source code must retain the above copyright .\" notice, this list of conditions and the following disclaimer. .\" .\" 2. Redistributions in binary form must reproduce the above copyright .\" notice, this list of conditions and the following disclaimer in .\" the documentation and/or other materials provided with the .\" distribution. .\" .\" 3. The name "Carnegie Mellon University" must not be used to .\" endorse or promote products derived from this software without .\" prior written permission. For permission or any legal .\" details, please contact .\" Carnegie Mellon University .\" Center for Technology Transfer and Enterprise Creation .\" 4615 Forbes Avenue .\" Suite 302 .\" Pittsburgh, PA 15213 .\" (412) 268-7393, fax: (412) 268-7395 .\" innovation@andrew.cmu.edu .\" .\" 4. Redistributions of any form whatsoever must retain the following .\" acknowledgment: .\" "This product includes software developed by Computing Services .\" at Carnegie Mellon University (http://www.cmu.edu/computing/)." .\" .\" CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO .\" THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY .\" AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE .\" FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES .\" WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN .\" AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING .\" OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. .SH NAME imapd \- IMAP server process .SH SYNOPSIS .B imapd [ .B \-C .I config-file ] [ .B \-U .I uses ] [ .B \-T .I timeout ] [ .B \-D ] .br [ .B \-s ] [ .B \-N ] [ .B \-p .I ssf ] .SH DESCRIPTION .I Imapd is an IMAP4rev1 server. It accepts commands on its standard input and responds on its standard output. It MUST be invoked by .IR master (8) with those descriptors attached to a remote client connection. .PP .I Imapd reads its configuration options out of the .IR imapd.conf (5) file unless specified otherwise by \fB-C\fR. .PP If the file msg/shutdown is created under the directory specified in the .I configdirectory configuration option, then .I imapd will shut down the connection, sending the first line contained in the file to the client as the reason. New connections are denied. .PP If the file msg/motd is created under the directory specified in the .I configdirectory configuration option, then .I imapd will send the first line contained in the file to clients upon connect as an ALERT message which IMAP-compliant clients are required to display. This option serves to annoy users mostly. Unfortunately clients tend to connect far more frequently than is apparent, causing each connection to generate a seperate server ALERT for each connection. Many clients do not display these properly, if they do anything with them at all. .PP If the directory .RI log/ user exists under the directory specified in the .I configdirectory configuration option, then .I imapd will create protocol telemetry logs for sessions authenticating as .IR user . The telemetry logs will be stored in the .RI log/ user directory with a filename of the .I imapd process-id. .SH OPTIONS .TP .BI \-C " config-file" Read configuration options from \fIconfig-file\fR. .TP .BI \-U " uses" The maximum number of times that the process should be used for new connections before shutting down. The default is 250. .TP .BI \-T " timeout" The number of seconds that the process will wait for a new connection before shutting down. Note that a value of 0 (zero) will disable the timeout. The default is 60. .TP .BI \-D Run external debugger specified in debug_command. .TP .BI \-s Serve IMAP over SSL (imaps). All data to and from .I imapd is encrypted using the Secure Sockets Layer. .TP .BI \-N Bypass password checking. (Not recommended unless you know what you're doing.) .TP .BI \-p " ssf" Tell .I imapd that an external layer exists. An SSF (security strength factor) of 1 means an integrity protection layer exists. Any higher SSF implies some form of privacy protection. .SH FILES .TP .B /etc/imapd.conf .SH SEE ALSO .PP \fBimapd.conf(5)\fR, \fBmaster(8)\fR cyrus-imapd-2.5.10/man/cyr_dbtool.80000644000175000017500000000670413001236020013753 00000000000000.\" -*- nroff -*- .TH CYR_DBTOOL 8 "Project Cyrus" CMU .\" .\" Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. .\" .\" Redistribution and use in source and binary forms, with or without .\" modification, are permitted provided that the following conditions .\" are met: .\" .\" 1. Redistributions of source code must retain the above copyright .\" notice, this list of conditions and the following disclaimer. .\" .\" 2. Redistributions in binary form must reproduce the above copyright .\" notice, this list of conditions and the following disclaimer in .\" the documentation and/or other materials provided with the .\" distribution. .\" .\" 3. The name "Carnegie Mellon University" must not be used to .\" endorse or promote products derived from this software without .\" prior written permission. For permission or any legal .\" details, please contact .\" Carnegie Mellon University .\" Center for Technology Transfer and Enterprise Creation .\" 4615 Forbes Avenue .\" Suite 302 .\" Pittsburgh, PA 15213 .\" (412) 268-7393, fax: (412) 268-7395 .\" innovation@andrew.cmu.edu .\" .\" 4. Redistributions of any form whatsoever must retain the following .\" acknowledgment: .\" "This product includes software developed by Computing Services .\" at Carnegie Mellon University (http://www.cmu.edu/computing/)." .\" .\" CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO .\" THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY .\" AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE .\" FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES .\" WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN .\" AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING .\" OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. .SH NAME cyr_dbtool \- manage Cyrus databases .SH SYNOPSIS .B cyr_dbtool [ .B \-C .I config-file ] [ .B \-M ] [ .B \-n ] [ .B \-o ] [ .B \-T ] [ ] [ ] .SH DESCRIPTION .I cyr_dbtool is used to manage a cyrusdb file. The usable actions are: .PP .BI show " []" .PP .BI get " " .PP .BI set " " .PP .BI delete " " .PP .BI consistency .PP .BI repack .PP You may omit key or key/value and specify one per line on stdin. Keys are terminated by tab or newline, values are terminated by newline. .PP Running without any options will list the available database backends and usable actions. .PP The 'consistency' command runs a consistency check on the DB by calling 'myconsistent' on it. .PP The 'repack' command will compress the database by removing stale data on backends which support it. It's a NOOP otherwise. .PP .I cyr_dbtool reads any applicable configuration options out of the .IR imapd.conf (5) file unless specified otherwise by \fB-C\fR. note that the file locations are NOT read out of the configuration file, and must be supplied on the command line. .SH OPTIONS .TP .BI \-C " config-file" Read configuration options from \fIconfig-file\fR. .TP .BI \-M Uses improved MBOX list sort. .TP .BI \-n Create the database file if it doesn't already exist. .TP .BI \-o Store all the output in memory and only print it once the transaction is completed. .TP .BI \-T Use a transaction to do the action (most especially for 'show') - the default used to be transactions. .SH FILES .TP .B /etc/imapd.conf .SH SEE ALSO .PP \fBimapd.conf(5)\fR cyrus-imapd-2.5.10/man/smmapd.80000644000175000017500000000607213001236020013072 00000000000000.\" -*- nroff -*- .TH SMMAPD 8 "Project Cyrus" CMU .\" .\" Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. .\" .\" Redistribution and use in source and binary forms, with or without .\" modification, are permitted provided that the following conditions .\" are met: .\" .\" 1. Redistributions of source code must retain the above copyright .\" notice, this list of conditions and the following disclaimer. .\" .\" 2. Redistributions in binary form must reproduce the above copyright .\" notice, this list of conditions and the following disclaimer in .\" the documentation and/or other materials provided with the .\" distribution. .\" .\" 3. The name "Carnegie Mellon University" must not be used to .\" endorse or promote products derived from this software without .\" prior written permission. For permission or any legal .\" details, please contact .\" Carnegie Mellon University .\" Center for Technology Transfer and Enterprise Creation .\" 4615 Forbes Avenue .\" Suite 302 .\" Pittsburgh, PA 15213 .\" (412) 268-7393, fax: (412) 268-7395 .\" innovation@andrew.cmu.edu .\" .\" 4. Redistributions of any form whatsoever must retain the following .\" acknowledgment: .\" "This product includes software developed by Computing Services .\" at Carnegie Mellon University (http://www.cmu.edu/computing/)." .\" .\" CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO .\" THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY .\" AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE .\" FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES .\" WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN .\" AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING .\" OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. .SH NAME SMMAPD \- Sendmail socket map daemon .SH SYNOPSIS .B smmapd [ .B \-C .I config-file ] [ .B \-U .I uses ] [ .B \-T .I timeout ] .br [ .B \-D ] .SH DESCRIPTION .B SMMAPD is a Sendmail socket map daemon which is used to verify that a Cyrus mailbox exists, that it is postable and it is under quota. It accepts commands on its standard input and responds on its standard output. It MUST be invoked by .IR master (8) with those descriptors attached to a remote client connection. .PP .B SMMAPD reads its configuration options out of the .IR imapd.conf (5) file unless specified otherwise by \fB-C\fR. .SH OPTIONS .TP .BI \-C " config-file" Read configuration options from \fIconfig-file\fR. .TP .BI \-U " uses" The maximum number of times that the process should be used for new connections before shutting down. The default is 250. .TP .BI \-T " timeout" The number of seconds that the process will wait for a new connection before shutting down. Note that a value of 0 (zero) will disable the timeout. The default is 60. .TP .BI \-D Run external debugger specified in debug_command. .SH FILES .TP .B /etc/imapd.conf Default configuration file. .TP .B /etc/cyrus.conf Cyrus Master process configuration file. cyrus-imapd-2.5.10/man/mupdatetest.10000644000175000017500000001133513001236020014137 00000000000000.\" -*- nroff -*- .TH MUPDATETEST 1 "Project Cyrus" CMU .\" .\" Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. .\" .\" Redistribution and use in source and binary forms, with or without .\" modification, are permitted provided that the following conditions .\" are met: .\" .\" 1. Redistributions of source code must retain the above copyright .\" notice, this list of conditions and the following disclaimer. .\" .\" 2. Redistributions in binary form must reproduce the above copyright .\" notice, this list of conditions and the following disclaimer in .\" the documentation and/or other materials provided with the .\" distribution. .\" .\" 3. The name "Carnegie Mellon University" must not be used to .\" endorse or promote products derived from this software without .\" prior written permission. For permission or any legal .\" details, please contact .\" Carnegie Mellon University .\" Center for Technology Transfer and Enterprise Creation .\" 4615 Forbes Avenue .\" Suite 302 .\" Pittsburgh, PA 15213 .\" (412) 268-7393, fax: (412) 268-7395 .\" innovation@andrew.cmu.edu .\" .\" 4. Redistributions of any form whatsoever must retain the following .\" acknowledgment: .\" "This product includes software developed by Computing Services .\" at Carnegie Mellon University (http://www.cmu.edu/computing/)." .\" .\" CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO .\" THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY .\" AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE .\" FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES .\" WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN .\" AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING .\" OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. .SH NAME mupdatetest \- interactive MUPDATE test program .SH SYNOPSIS .B mupdatetest [ .B \-p .I port ] [ .B \-m .I mechanism ] .br [ .B \-a .I userid ] [ .B \-u .I userid ] [ .B \-k .I num ] [ .B \-l .I num ] .br [ .B \-r .I realm ] [ .B \-f .I file ] [ .B \-n .I num ] [ .B \-q ] .br [ .B \-c ] [ .B \-i ] [ .B \-o \fIoption\fB=\fIvalue\fR ] [ .B \-v ] \fIhostname\fR .SH DESCRIPTION .I mupdatetest is a utility that allows you to authenticate to a MUPDATE server and interactively issue commands to it. Once authenticated you may issue any MUPDATE command by simply typing it in. It is capable of multiple SASL authentication mechanisms and handles encryption layers transparently. This utility is often used for testing the operation of a mupdate server. Note that you must be an admin in order to authenticate to an mupdate server. .PP .SH OPTIONS .TP .BI \-p " port" Port to connect to. If left off this defaults to \fBmupdate\fR as defined in /etc/services. .TP .BI -m " mechanism" Force mupdatetest to use \fImechanism\fR for authentication. If not specified the strongest authentication mechanism supported by the server is chosen. .TP .BI -a " userid" Userid to use for authentication; defaults to the current user. This is the userid whose password or credentials will be presented to the server for verification. .TP .BI -u " userid" Userid to use for authorization; defaults to the current user. This is the userid whose identity will be assumed after authentication. \fBNOTE:\fR This is only used with SASL mechanisms that allow proxying (e.g. PLAIN, DIGEST-MD5). .TP .BI -k " num" Minimum protection layer required. .TP .BI -l " num" Maximum protection layer to use (\fB0\fR=none; \fB1=\fRintegrity; etc). For example if you are using the KERBEROS_V4 authentication mechanism specifying \fB0\fR will force mupdatetest to not use any layer and specifying \fB1\fR will force it to use the integrity layer. By default the maximum supported protection layer will be used. .TP .BI -r " realm" Specify the \fIrealm\fR to use. Certain authentication mechanisms (e.g. DIGEST-MD5) may require one to specify the realm. .TP .BI -f " file" Pipe \fIfile\fR into connection after authentication. .TP .BI -n " num" Number of authentication attempts; default = 1. The client will attempt to fast reauth (e.g. DIGEST-MD5), if possible. .TP .B -q Enable MUPDATE COMPRESSion (before the last authentication attempt). .TP .B -c Enable challenge prompt callbacks. This will cause the OTP mechanism to ask for the the one-time password instead of the secret pass-phrase (library generates the correct response). .TP .B -i Don't send an initial client response for SASL mechanisms, even if the protocol supports it. .TP \fB-o \fIoption\fB=\fIvalue\fR Set the SASL \fIoption\fR to \fIvalue\fR. .TP .B -v Verbose. Print out more information than usual. .SH SEE ALSO .PP \fBmupdate(8)\fR cyrus-imapd-2.5.10/man/fetchnews.80000644000175000017500000000673613001236020013606 00000000000000.\" -*- nroff -*- .TH FETCHNEWS 8 "Project Cyrus" CMU .\" .\" Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. .\" .\" Redistribution and use in source and binary forms, with or without .\" modification, are permitted provided that the following conditions .\" are met: .\" .\" 1. Redistributions of source code must retain the above copyright .\" notice, this list of conditions and the following disclaimer. .\" .\" 2. Redistributions in binary form must reproduce the above copyright .\" notice, this list of conditions and the following disclaimer in .\" the documentation and/or other materials provided with the .\" distribution. .\" .\" 3. The name "Carnegie Mellon University" must not be used to .\" endorse or promote products derived from this software without .\" prior written permission. For permission or any legal .\" details, please contact .\" Carnegie Mellon University .\" Center for Technology Transfer and Enterprise Creation .\" 4615 Forbes Avenue .\" Suite 302 .\" Pittsburgh, PA 15213 .\" (412) 268-7393, fax: (412) 268-7395 .\" innovation@andrew.cmu.edu .\" .\" 4. Redistributions of any form whatsoever must retain the following .\" acknowledgment: .\" "This product includes software developed by Computing Services .\" at Carnegie Mellon University (http://www.cmu.edu/computing/)." .\" .\" CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO .\" THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY .\" AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE .\" FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES .\" WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN .\" AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING .\" OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. .SH NAME fetchnews \- retrieve new articles from peer and feed to Cyrus .SH SYNOPSIS .B fetchnews [ .B \-C .I config-file ] [ .B \-s .I servername[:port] ] .br [ .B \-n ] [ .B \-y ] [ .B \-w .I wildmat ] [ .B \-f .I tstampfile ] .br [ .B \-a .I authname [ .B \-p .I password ] ] .I peername .SH DESCRIPTION .I Fetchnews retrieves news articles from a peer news server and feeds them to a Cyrus server. .I Fetchnews connects to the peer specified by .IR peername , requests new articles since the time stored in .I tstampfile and feeds them to .IR servername . .PP .I Fetchnews reads its configuration options out of the .IR imapd.conf (5) file unless specified otherwise by \fB-C\fR. .SH OPTIONS .TP .BI \-C " config-file" Read configuration options from \fIconfig-file\fR. .TP .BI \-s " servername" Hostname of the Cyrus server (with optional port) to which articles should be fed. Defaults to "localhost:nntp". .TP .B \-n Don't use the NEWNEWS command. .I Fetchnews will keep track of the high and low water marks for each group and use them to fetch new articles. .TP .B \-y Use 4 instead of 2 digits for year. 2-digits are rfc977- but not y2k-compliant. .TP .BI \-w " wildmat" Wildmat pattern specifying which newsgroups to search for new articles. Defaults to "*". .TP .BI \-f " tstampfile" File in which to read/write the timestamp of when articles were last retrieved. Defaults to "newsstamp" located in .I configdir as specified by the configuration options. .TP .BI \-a " authname" Userid to use for authentication. .TP .BI \-p " password" Password to use for authentication. .SH FILES .TP .B /etc/imapd.conf cyrus-imapd-2.5.10/man/reconstruct.80000644000175000017500000001436513001236020014170 00000000000000.\" -*- nroff -*- .TH RECONSTRUCT 8 "Project Cyrus" CMU .\" .\" Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. .\" .\" Redistribution and use in source and binary forms, with or without .\" modification, are permitted provided that the following conditions .\" are met: .\" .\" 1. Redistributions of source code must retain the above copyright .\" notice, this list of conditions and the following disclaimer. .\" .\" 2. Redistributions in binary form must reproduce the above copyright .\" notice, this list of conditions and the following disclaimer in .\" the documentation and/or other materials provided with the .\" distribution. .\" .\" 3. The name "Carnegie Mellon University" must not be used to .\" endorse or promote products derived from this software without .\" prior written permission. For permission or any legal .\" details, please contact .\" Carnegie Mellon University .\" Center for Technology Transfer and Enterprise Creation .\" 4615 Forbes Avenue .\" Suite 302 .\" Pittsburgh, PA 15213 .\" (412) 268-7393, fax: (412) 268-7395 .\" innovation@andrew.cmu.edu .\" .\" 4. Redistributions of any form whatsoever must retain the following .\" acknowledgment: .\" "This product includes software developed by Computing Services .\" at Carnegie Mellon University (http://www.cmu.edu/computing/)." .\" .\" CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO .\" THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY .\" AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE .\" FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES .\" WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN .\" AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING .\" OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. .SH NAME reconstruct \- reconstruct mailboxes .SH SYNOPSIS .B reconstruct [ .B \-C .I config-file ] [ .B \-p .I partition ] [ .B \-x ] [ .B \-r ] [ .B \-f ] .br [ .B \-k ] [ .B \-s ] [ .B \-g ] [ .B \-G ] [ .B \-R ] [ .B \-o ] [ .B \-O ] .IR mailbox ... .br .br .B reconstruct [ .B \-C .I config-file ] .B \-m .SH DESCRIPTION .I Reconstruct rebuilds one or more IMAP mailboxes. When invoked with the .B \-m switch, it rebuilds the master mailboxes file. It can be used to recover from almost any sort of data corruption. .PP If .I Reconstruct can find existing header and index files, it attempts to preserve any data in them that is not derivable from the message files themselves. The state .I reconstruct attempts to preserve includes the flag names, flag state, and internaldate. .I Reconstruct derives all other information from the message files. .PP .I Reconstruct reads its configuration options out of the .IR imapd.conf (5) file unless specified otherwise by \fB-C\fR. Any mailbox directory underneath the path specified in the .I partition-news configuration option is assumed to be in news format. .PP .I Reconstruct does not adjust the quota usage recorded in any quota root files. After running .IR reconstruct , it is advisable to run .IR quota (8) with the .I \-f switch in order to fix the quota root files. .SH OPTIONS .TP .BI \-C " config-file" Read configuration options from \fIconfig-file\fR. .TP .BI \-p " partition" Search for the listed (non-existant) mailboxes on the indicated partition. Create the mailboxes in the database in addition to reconstructing them. (not compatible with the use of wildcards) .TP .B \-x When processing a mailbox which is not in the mailbox list (e.g. via the -p or -f options), do not import the metadata from the mailbox, instead create it anew (this specifically affects at least the mailbox's seen state unique identifier, user flags, and ACL). .TP .B \-r Recursively reconstruct all sub-mailboxes of the mailboxes or mailbox prefixes given as arguments. .TP .B \-f Examine the filesystem underneath mailbox, adding all directories with a cyrus.header found there as new mailboxes. Useful for restoring mailboxes from backups. .TP .B \-s Don't stat underlying files. This makes reconstruct run faster, at the expense of not noticing some issues (like zero byte files or size mistmatches). "reconstruct -s" should be quite fast. .TP .B \-q Emit less verbose information to syslog. .TP .B \-n Don't make any changes. This gives equivalent behaviour to .I chk_cyrus where problems are reported, but not fixed. .TP .B \-G Force re-parsing of the underlying message (checks GUID correctness). Reconstruct with -G should fix all possible individual message issues, including corrupted data files. .TP .B \-R Perform a UID upgrade operation on GUID mismatch files. Use this option if you think your index is corrupted rather than your message files, or if all backup attempts have failed and you're happy to be served the missing files. .TP .B \-U Use this option if you have corrupt message files in your spool and have been unable to restore them from backup. This will make the mailbox IOERROR free and fix replication. .B WARNING this deletes corrupt message files for ever - so make sure you've exhausted other options first! .TP .B -o Ignore odd files in your mailbox disk directories. Probably useful if you are using some tool which adds additional tracking files. .TP .B -O Delete odd files. This is the opposite of '-o'. .TP .BI \-V " version" Change the cyrus.index minor version to a specific version. This can be useful for upgrades or downgrades. Use a magical version of \fImax\fR to upgrade to the latest available database format version. .TP .B -u Instead of mailbox prefixes, give usernames on the command line .TP .B \-m .B NOTE: CURRENTLY UNAVAILABLE .br Rebuild the .I mailboxes file. Use whatever data in the existing .I mailboxes file it can scavenge, then scans all partitions listed in the .IR imapd.conf (5) file for additional mailboxes. .SH EXAMPLES You want to reconstruct the index files for a user, you have recovered a deleted mail file from backup and given it a suitable name (eg user/ben-lacy/33.), but it is not visible since it is not indexed: .nf reconstruct -r user.ben-lacy .fi .PP If you have the \fBunixhierarchysep:yes\fR option set in \fB/etc/imapd.conf\fR you would need to run: .nf reconstruct -r user/ben.lacy .fi .SH FILES .TP .B /etc/imapd.conf cyrus-imapd-2.5.10/man/cyr_df.80000644000175000017500000000461613001236020013061 00000000000000.\" -*- nroff -*- .TH CYR_DF 8 "Project Cyrus" CMU .\" .\" Copyright (c) 1994-2009 Carnegie Mellon University. All rights reserved. .\" .\" Redistribution and use in source and binary forms, with or without .\" modification, are permitted provided that the following conditions .\" are met: .\" .\" 1. Redistributions of source code must retain the above copyright .\" notice, this list of conditions and the following disclaimer. .\" .\" 2. Redistributions in binary form must reproduce the above copyright .\" notice, this list of conditions and the following disclaimer in .\" the documentation and/or other materials provided with the .\" distribution. .\" .\" 3. The name "Carnegie Mellon University" must not be used to .\" endorse or promote products derived from this software without .\" prior written permission. For permission or any legal .\" details, please contact .\" Carnegie Mellon University .\" Center for Technology Transfer and Enterprise Creation .\" 4615 Forbes Avenue .\" Suite 302 .\" Pittsburgh, PA 15213 .\" (412) 268-7393, fax: (412) 268-7395 .\" innovation@andrew.cmu.edu .\" .\" 4. Redistributions of any form whatsoever must retain the following .\" acknowledgment: .\" "This product includes software developed by Computing Services .\" at Carnegie Mellon University (http://www.cmu.edu/computing/)." .\" .\" CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO .\" THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY .\" AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE .\" FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES .\" WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN .\" AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING .\" OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. .SH NAME cyr_df \- report Cyrus spool partition disk space usage .SH SYNOPSIS .B cyr_df [ .B \-C .I config-file ] [ .B \-m ] .SH DESCRIPTION .I Cyr_df examines the Cyrus spool partitions and reports on their disk space usage. .I Cyr_df reads its configuration options out of the .IR imapd.conf (5) file unless specified otherwise by \fB-C\fR. .SH OPTIONS .TP .BI \-C " config-file" Read configuration options from \fIconfig-file\fR. .TP .B \-m Report on metadata partitions rather than message file partitions. .SH FILES .B /etc/imapd.conf cyrus-imapd-2.5.10/man/cyrus.conf.50000644000175000017500000001645213001236020013702 00000000000000.\" -*- nroff -*- .TH CYRUS.CONF 5 "Project Cyrus" CMU .\" .\" Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. .\" .\" Redistribution and use in source and binary forms, with or without .\" modification, are permitted provided that the following conditions .\" are met: .\" .\" 1. Redistributions of source code must retain the above copyright .\" notice, this list of conditions and the following disclaimer. .\" .\" 2. Redistributions in binary form must reproduce the above copyright .\" notice, this list of conditions and the following disclaimer in .\" the documentation and/or other materials provided with the .\" distribution. .\" .\" 3. The name "Carnegie Mellon University" must not be used to .\" endorse or promote products derived from this software without .\" prior written permission. For permission or any legal .\" details, please contact .\" Carnegie Mellon University .\" Center for Technology Transfer and Enterprise Creation .\" 4615 Forbes Avenue .\" Suite 302 .\" Pittsburgh, PA 15213 .\" (412) 268-7393, fax: (412) 268-7395 .\" innovation@andrew.cmu.edu .\" .\" 4. Redistributions of any form whatsoever must retain the following .\" acknowledgment: .\" "This product includes software developed by Computing Services .\" at Carnegie Mellon University (http://www.cmu.edu/computing/)." .\" .\" CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO .\" THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY .\" AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE .\" FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES .\" WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN .\" AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING .\" OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. .SH NAME cyrus.conf \- Cyrus configuration file .SH DESCRIPTION \fB/etc/cyrus.conf\fR is the configuration file for the Cyrus \fBmaster\fR process. It defines the startup procedures, services and events to be spawned by \fBmaster\fR. .PP The \fB/etc/cyrus.conf\fR file consists of a series of entries divided into sections of the form .P .RS \fIsection\fR { .RS \fIname arguments .br ... .br ... .br ... \fR .RE } .RE .PP where \fIsection\fR is the name of the section, \fIname\fR is the name of the entry and \fIarguments\fR is the whitespace-separated list of arguments for the entry. The \fIname\fR may be any sequence of alphabetic and numeric characters, but may not contain punctuation such as '-' or '_'. In the \fBSERVICES\fP section, names must be unique. .PP Blank lines and lines beginning with ``#'' are ignored. .SH SECTION DESCRIPTIONS The paragraphs below detail the three sections (\fBSTART\fR, \fBSERVICES\fR, \fBEVENTS\fR) that can be placed in the \fB/etc/cyrus.conf\fR file. The arguments that are available for each entry within the section are described, and each argument's default value is shown. .PP Arguments can appear in any order. Some arguments have no default value, these are listed with ``''. For string arguments, the value MUST be enclosed in double quotes. .SS START This section lists the processes to run before any \fBSERVICES\fR are spawned. This section is typically used to initialize databases and start long running daemons. .IP "\fBcmd=\fR" 5 The command (with options) to spawn as a child process. This string argument is required. .SS SERVICES This section is the heart of the \fB/etc/cyrus.conf\fR file. It lists the processes that should be spawned to handle client connections made on certain Internet/UNIX sockets. .IP "\fBbabysit=\fR0" 5 Integer value - if non-zero, will make sure at least one process is pre-forked, and will set the maxforkrate to 10 if it's zero. .IP "\fBcmd=\fR" 5 The command (with options) to spawn as a child process. This string argument is required. .IP "\fBlisten=\fR" 5 The UNIX or internet socket to listen on. This string field is required and takes one of the following forms: \fIpath\fR .br \fR[ \fIhost\fR \fB: \fR] \fIport\fR .br .sp where \fIpath\fR is the explicit path to a UNIX socket, \fIhost\fR is either the hostname or bracket-enclosed IP address of a network interface, and \fIport\fR is either a port number or service name (as listed in \fB/etc/services\fR). .IP "\fBproto=\fRtcp" 5 The protocol used for this service (\fItcp\fR, \fItcp4\fR, \fItcp6\fR, \fIudp\fR, \fIudp4\fR, \fIudp6\fR). This string argument is optional. \fBtcp4\fR, \fBudp4\fR: These arguments are used to bind the service to IPv4 only. .br \fBtcp6\fR, \fBudp6\fR: These arguments are used to bind the service to IPv6 only, if the operating system supports this. .br \fBtcp\fR, \fBudp\fR: These arguments are used to bind to both IPv4 and IPv6 if possible. .IP "\fBprefork=\fR0" 5 The number of instances of this service to always have running and waiting for a connection (for faster initial response time). This integer value is optional. Note that if you are listening on multiple network types (i.e. ipv4 and ipv6) then one process will be forked for each address, causing twice as many processes as you might expect. .IP "\fBmaxchild=\fR-1" 5 The maximum number of instances of this service to spawn. A value of -1 means unlimited. This integer value is optional. .IP "\fBmaxfds=\fR256" 5 The maximum number of file descriptors to which to limit this process. This integer value is optional. .IP "\fBmaxforkrate=\fR0" 5 Maximum number of processes to fork per second - the master will insert sleeps to ensure it doesn't fork faster than this on average. .SS EVENTS This section lists processes that should be run at specific intervals, similar to cron jobs. This section is typically used to perform scheduled cleanup/maintenance. .IP "\fBcmd=\fR" 5 The command (with options) to spawn as a child process. This string argument is required. .IP "\fBperiod=\fR0" 5 The interval (in minutes) at which to run the command. This integer value is optional, but SHOULD be a positive integer > 10. .IP "\fBat=\fR" 5 The time (24-hour format) at which to run the command each day. If set to a valid time (0000-2359), period is automatically set to 1440. This string argument is optional. .SH EXAMPLE # example cyrus.conf START { recover cmd="ctl_cyrusdb -r" .br } SERVICES { imap cmd="imapd" listen="imap" prefork=1 imaps cmd="imapd -s" listen="imaps" prefork=0 lmtpunix cmd="lmtpd" listen="/var/imap/socket/lmtp" lmtp cmd="lmtpd" listen="localhost:lmtp" .br } EVENTS { checkpoint cmd="ctl_cyrusdb -c" period=30 delprune cmd="cyr_expire -E 3" at=0400 tlsprune cmd="tls_prune" at=0400 .br } .SH ACCESS CONTROL When TCP Wrappers is used to control access to Cyrus services, the \fIname\fR of the service entry should be used as the process name in the \fBhosts_access(5)\fR table. For instance, in the example above, "imap", "imaps", "lmtpunix" and "lmtp" would be used as the process names. This allows a single daemon such as imapd to be run in different modes or configurations (i.e., SSL and non-SSL enabled) yet still have separate access control rules. .SH SEE ALSO .PP \fBmaster(8)\fR, \fBimapd(8)\fR, \fBpop3d(8)\fR, \fBlmtpd(8)\fR, \fBtimsieved(8)\fR, \fBidled(8)\fR, \fBnotifyd(8)\fR, \fBctl_cyrusdb(8)\fR, \fBctl_deliver(8)\fR, \fBtls_prune(8)\fR, \fBhosts_access(5)\fR cyrus-imapd-2.5.10/netnews/0000755000175000017500000000000013001246664012522 500000000000000cyrus-imapd-2.5.10/netnews/readconfig.h0000644000175000017500000000422613001236020014701 00000000000000/* * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #ifndef READCONFIG_H #define READCONFIG_H #include "macros.h" int EXPreadfile(FILE *F); int ExpireExists(int num); time_t GetExpireTime(int num); char *GetExpireName(int num); int readconfig_init(void); void artificial_matchall(int days); void callback_list(struct imclient *imclient, void *rock, struct imclient_reply *reply); #endif /* READCONFIG_H */ cyrus-imapd-2.5.10/netnews/readconfig.c0000644000175000017500000003216013001236020014672 00000000000000/* The code for reading expire.ctl files (most of this file) * was borrowed from innd * Minor modifications to that code were made * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ /* Copyright 1991 Rich Salz. * All rights reserved. * * Redistribution and use in any form are permitted provided that the * following restrictions are are met: * 1. Source distributions must retain this entire copyright notice * and comment. * 2. Binary distributions must include the acknowledgement ``This * product includes software developed by Rich Salz'' in the * documentation or other materials provided with the * distribution. This must not be represented as an endorsement * or promotion without specific prior written permission. * 3. The origin of this software must not be misrepresented, either * by explicit claim or by omission. Credits must appear in the * source and documentation. * 4. Altered versions must be plainly marked as such in the source * and documentation and must not be misrepresented as being the * original software. * THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR IMPLIED * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF * MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. */ #include #include #include #include #include "macros.h" #include "xmalloc.h" #include "imclient.h" #include "imparse.h" #include "wildmat.h" #include "util.h" #define NUM_STORAGE_CLASSES 100 #define BOOL int #define FALSE (0) #define TRUE (1) #define STATIC static typedef struct _NEWSGROUP { char *Name; char *Rest; unsigned long Last; unsigned long Lastpurged; /* These fields are new. */ time_t Keep; time_t Default; time_t Purge; /* X flag => remove entire article when it expires in this group */ BOOL Poison; } NEWSGROUP; typedef struct _EXPIRECLASS { time_t Keep; time_t Default; time_t Purge; BOOL Missing; BOOL ReportedMissing; } EXPIRECLASS; /* ** Expire-specific stuff. */ #define MAGIC_TIME 49710. STATIC NEWSGROUP EXPdefault; STATIC int nGroups; STATIC int nGroups_alloc; STATIC time_t EXPremember; STATIC time_t Now; STATIC EXPIRECLASS EXPclasses[NUM_STORAGE_CLASSES]; STATIC NEWSGROUP *Groups; STATIC int EXPverbose; /* ** Split a line at a specified field separator into a vector and return ** the number of fields found, or -1 on error. */ STATIC int EXPsplit(char *p, char sep, char **argv, int count) { int i; if (!p) return 0; while (*p == sep) ++p; if (!*p) return 0; if (!p) return 0; while (*p == sep) ++p; if (!*p) return 0; for (i = 1, *argv++ = p; *p; ) if (*p++ == sep) { p[-1] = '\0'; for (; *p == sep; p++); if (!*p) return i; if (++i == count) /* Overflow. */ return -1; *argv++ = p; } return i; } /* ** Parse a number field converting it into a "when did this start?". ** This makes the "keep it" tests fast, but inverts the logic of ** just about everything you expect. Print a message and return FALSE ** on error. */ STATIC BOOL EXPgetnum(int line, char *word, time_t *v, char *name) { char *p; BOOL SawDot; double d; if (caseEQ(word, "never")) { *v = (time_t)0; return TRUE; } /* Check the number. We don't have strtod yet. */ for (p = word; ISWHITE(*p); p++) continue; if (*p == '+' || *p == '-') p++; for (SawDot = FALSE; *p; p++) if (*p == '.') { if (SawDot) break; SawDot = TRUE; } else if (!Uisdigit(*p)) break; if (*p) { (void)fprintf(stderr, "Line %d, bad `%c' character in %s field\n", line, *p, name); return FALSE; } d = atof(word); if (d > MAGIC_TIME) *v = (time_t)0; else *v = Now - (time_t)(d * 86400.); return TRUE; } /* ** Set the expiration fields for all groups that match this pattern. */ STATIC void EXPmatch(char *p, NEWSGROUP *v, char mod) { NEWSGROUP *ngp; int i; BOOL negate; negate = *p == '!'; if (negate) p++; for (ngp = Groups, i = nGroups; --i >= 0; ngp++) { if (negate ? !wildmat(ngp->Name, p) : wildmat(ngp->Name, p)) if (mod == 'a') { /*|| (mod == 'm' && ngp->Rest[0] == NF_FLAG_MODERATED) || (mod == 'u' && ngp->Rest[0] != NF_FLAG_MODERATED)) { */ ngp->Keep = v->Keep; ngp->Default = v->Default; ngp->Purge = v->Purge; ngp->Poison = v->Poison; if (EXPverbose > 4) { (void)printf("%s", ngp->Name); (void)printf(" %13.13s", ctime(&v->Keep) + 3); (void)printf(" %13.13s", ctime(&v->Default) + 3); (void)printf(" %13.13s", ctime(&v->Purge) + 3); (void)printf(" (%s)\n", p); } } } } /* ** Parse the expiration control file. Return TRUE if okay. */ BOOL EXPreadfile(FILE *F) { char *p; int i; int j; int k; char mod; NEWSGROUP v; BOOL SawDefault; char buff[BUFSIZ]; char *fields[7]; char **patterns; /* Scan all lines. */ EXPremember = -1; SawDefault = FALSE; patterns = NEW(char*, nGroups); for (i = 0; i < NUM_STORAGE_CLASSES; i++) EXPclasses[i].ReportedMissing = EXPclasses[i].Missing = TRUE; for (i = 1; fgets(buff, sizeof buff, F) != NULL; i++) { if ((p = strchr(buff, '\n')) == NULL) { (void)fprintf(stderr, "Line %d too long\n", i); return FALSE; } *p = '\0'; p = strchr(buff, '#'); if (p) *p = '\0'; else p = buff + strlen(buff); while (--p >= buff) { if (Uisspace(*p)) *p = '\0'; else break; } if (buff[0] == '\0') continue; if ((j = EXPsplit(buff, ':', fields, SIZEOF(fields))) == -1) { (void)fprintf(stderr, "Line %d too many fields\n", i); return FALSE; } /* Expired-article remember line? */ if (EQ(fields[0], "/remember/")) { if (j != 2) { (void)fprintf(stderr, "Line %d bad format\n", i); return FALSE; } if (EXPremember != -1) { (void)fprintf(stderr, "Line %d duplicate /remember/\n", i); return FALSE; } if (!EXPgetnum(i, fields[1], &EXPremember, "remember")) return FALSE; continue; } /* Storage class line? */ if (j == 4) { j = atoi(fields[0]); if ((j < 0) || (j > NUM_STORAGE_CLASSES)) { fprintf(stderr, "Line %d bad storage class %d\n", i, j); } if (!EXPgetnum(i, fields[1], &EXPclasses[j].Keep, "keep") || !EXPgetnum(i, fields[2], &EXPclasses[j].Default, "default") || !EXPgetnum(i, fields[3], &EXPclasses[j].Purge, "purge")) return FALSE; /* These were turned into offsets, so the test is the opposite * of what you think it should be. If Purge isn't forever, * make sure it's greater then the other two fields. */ if (EXPclasses[j].Purge) { /* Some value not forever; make sure other values are in range. */ if (EXPclasses[j].Keep && EXPclasses[j].Keep < EXPclasses[j].Purge) { (void)fprintf(stderr, "Line %d keep>purge\n", i); return FALSE; } if (EXPclasses[j].Default && EXPclasses[j].Default < EXPclasses[j].Purge) { (void)fprintf(stderr, "Line %d default>purge\n", i); return FALSE; } } EXPclasses[j].Missing = FALSE; continue; } /* Regular expiration line -- right number of fields? */ if (j != 5) { (void)fprintf(stderr, "Line %d bad format\n", i); return FALSE; } /* Parse the fields. */ if (strchr(fields[1], 'M') != NULL) mod = 'm'; else if (strchr(fields[1], 'U') != NULL) mod = 'u'; else if (strchr(fields[1], 'A') != NULL) mod = 'a'; else { (void)fprintf(stderr, "Line %d bad modflag\n", i); return FALSE; } v.Poison = (strchr(fields[1], 'X') != NULL); if (!EXPgetnum(i, fields[2], &v.Keep, "keep") || !EXPgetnum(i, fields[3], &v.Default, "default") || !EXPgetnum(i, fields[4], &v.Purge, "purge")) return FALSE; /* These were turned into offsets, so the test is the opposite * of what you think it should be. If Purge isn't forever, * make sure it's greater then the other two fields. */ if (v.Purge) { /* Some value not forever; make sure other values are in range. */ if (v.Keep && v.Keep < v.Purge) { (void)fprintf(stderr, "Line %d keep>purge\n", i); return FALSE; } if (v.Default && v.Default < v.Purge) { (void)fprintf(stderr, "Line %d default>purge\n", i); return FALSE; } } /* Is this the default line? */ if (fields[0][0] == '*' && fields[0][1] == '\0' && mod == 'a') { if (SawDefault) { (void)fprintf(stderr, "Line %d duplicate default\n", i); return FALSE; } EXPdefault.Keep = v.Keep; EXPdefault.Default = v.Default; EXPdefault.Purge = v.Purge; EXPdefault.Poison = v.Poison; SawDefault = TRUE; } /* Assign to all groups that match the pattern and flags. */ if ((j = EXPsplit(fields[0], ',', patterns, nGroups)) == -1) { (void)fprintf(stderr, "Line %d too many patterns\n", i); return FALSE; } for (k = 0; k < j; k++) EXPmatch(patterns[k], &v, mod); } DISPOSE(patterns); return TRUE; } int ExpireExists(int num) { if ((num<0) || (num>=nGroups)) return 1; return 0; } time_t GetExpireTime(int num) { return Groups[num].Default; } char *GetExpireName(int num) { return Groups[num].Name; } int readconfig_init(void) { Now = time(NULL); nGroups = 0; nGroups_alloc = 1000; Groups=(NEWSGROUP *) malloc(sizeof(NEWSGROUP) * 1000); if (Groups==NULL) fatal("Unable to alloc",0); return 0; } void artificial_matchall(int days) { NEWSGROUP ne; ne.Default = Now - (time_t)(days * 86400.); EXPmatch("*", &ne,'a'); } #if 0 /* debugginf */ void show_groups(void) { int lup; for (lup=0;luptext; if (*s++ != '(') return; end = strchr(s, ')'); if (!end) return; attributes = s; s = end; *s++ = '\0'; if (*s++ != ' ') return; if (*s == 'N') { if (s[1] != 'I' || s[2] != 'L') return; separator = ""; s += 3; } else if (*s == '\"') { s++; if (*s == '\\') s++; separator = s++; if (*s != '\"') return; *s++ = '\0'; } (void)separator; if (*s++ != ' ') return; c = imparse_astring(&s, &mailbox); if (c != '\0') return; if ((strncasecmp(mailbox,"INBOX",5)!=0) && (strncasecmp(mailbox,"user.",5)!=0)) { Groups[nGroups].Name = malloc( strlen(mailbox)+1); strcpy(Groups[nGroups].Name, mailbox); nGroups++; if (nGroups >= nGroups_alloc) { nGroups_alloc +=1000; Groups=(NEWSGROUP *) realloc(Groups, sizeof(NEWSGROUP) * nGroups_alloc); if (Groups==NULL) fatal("Unable to alloc",0); } } for (s = attributes; (end = strchr(s, ' '))!=NULL; s = end+1) { *s = '\0'; } } cyrus-imapd-2.5.10/netnews/macros.h0000644000175000017500000001071213001236020014061 00000000000000/* Here be some useful macros. * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ /* ** Memory allocation. Wrappers around wrapper functions. ** Don't replace any existing definitions, for use with malloc-debug ** packages, e.g. */ #include "xmalloc.h" #if defined(_DEBUG_MALLOC_INC) #undef _DEBUG_MALLOC_INC #include "malloc.h" #else #define malloc_enter(func) #define malloc_leave(func) #define malloc_chain_check() #define malloc_dump(fd) #define malloc_list(a,b,c) #define malloc_size(hist) (*(hist) = 0, 0) #endif /* defined(_DEBUG_MALLOC_INC) */ #if !defined(NEW) #define NEW(T, c) \ ((T *)xmalloc((unsigned int)(sizeof (T) * (c)))) #define RENEW(p, T, c) \ (p = (T *)xrealloc((char *)(p), (unsigned int)(sizeof (T) * (c)), \ __FILE__, __LINE__)) /* =()<#define DISPOSE(p) free((@@ *)p)>()= */ #define DISPOSE(p) free((void *)p) /* This properly belongs in libinn.h. */ extern int (*xmemfailure)(); #define ONALLOCFAIL(func) (xmemfailure = (func)) #endif /* !defined(NEW) */ /* ** Copy a string to allocated memory. */ #define COPY(p) \ strcpy(NEW(char, strlen(p) + 1), p) /* ** Wrappers around str[n]cmp. Don't add the ((a) == (b)) test here; it's ** already been done in places where it's time-critical. */ #define EQ(a, b) (strcmp((a), (b)) == 0) #define EQn(a, b, n) (strncmp((a), (b), (SIZE_T)(n)) == 0) #define caseEQ(a, b) (strcasecmp((a), (b)) == 0) #define caseEQn(a, b, n) (strncasecmp((a), (b), (SIZE_T)(n)) == 0) /* ** Cast a pointer into another point, but keep lint quiet. */ #if !defined(lint) #define CAST(t, p) ((t)(p)) #else #define CAST(t, p) ((p) ? (t)NULL : (t)NULL) #endif /* !defined(lint) */ /* ** usually includes \n, which is not what we want. */ #define ISWHITE(c) ((c) == ' ' || (c) == '\t') /* ** Get the number of elements in a fixed-size array, or a pointer just ** past the end of it. */ #define SIZEOF(array) ((int)(sizeof array / sizeof array[0])) #define ENDOF(array) (&array[SIZEOF(array)]) /* ** Get the length of a string constant. */ #define STRLEN(string) ((int)(sizeof string - 1)) /* ** Turn a TIMEINFO into a floating point number. */ #define TIMEINFOasDOUBLE(t) \ ((double)(t).time + ((double)(t).usec) / 1000000.0) /* ** Get the size when binding an AF_UNIX socket. */ #if defined(DO_BIND_USE_SIZEOF) #define AF_UNIX_SOCKSIZE(S) (sizeof S) #else #define AF_UNIX_SOCKSIZE(S) (sizeof S.sun_family + strlen(S.sun_path) + 1) #endif /* defined(DO_BIND_USE_SIZEOF) */ /* ** Use a read or recv call to read a descriptor. */ #if defined(HAVE_UNIX_DOMAIN_SOCKETS) #define RECVorREAD(fd, p, s) recv((fd), (p), (s), 0) #else #define RECVorREAD(fd, p, s) read((fd), (p), (s)) #endif /* defined(HAVE_UNIX_DOMAIN_SOCKETS) */ cyrus-imapd-2.5.10/netnews/remotepurge.c0000644000175000017500000004027313001236020015133 00000000000000/* Remotely purge old/too big articles * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include #include #include #include #include #include #include #include #include #include #ifdef HAVE_UNISTD_H #include #endif #include #include #include #include #include #include #include "prot.h" #include "imclient.h" #include "util.h" #include "xmalloc.h" #include "exitcodes.h" #include "readconfig.h" #define SECS_IN_DAY (24*60*60) #define NOTFINISHED 0 #define IMAP_OK 1 #define IMAP_NO 2 #define IMAP_BAD 3 #define IMAP_EOF 4 /* for statistical purposes */ typedef struct mbox_stats_s { int total; /* total including those deleted */ int total_bytes; int deleted; int deleted_bytes; } mbox_stats_t; typedef struct uid_list_s { unsigned long *list; int allocsize; int size; } uid_list_t; /* globals for callback functions */ static int days = -1; int size = -1; static int current_mbox_exists = 0; static int verbose = 0; static int noop = 0; static char *username = NULL; //char *authname = NULL; static char *realm = NULL; static struct imclient *imclient_conn; static int cmd_done; static char *cmd_resp = NULL; static FILE *configstream; static void spew(int level, const char *fmt, ...) { va_list ap; char buf[1024]; if (verbose < level) return; va_start(ap, fmt); vsnprintf(buf, sizeof buf, fmt, ap); va_end(ap); if (verbose) { printf("%s\n", buf); } syslog(LOG_DEBUG, "%s", buf); } /* libcyrus makes us define this */ EXPORTED void fatal(const char *s, int code) { if (cmd_resp) { syslog(LOG_ERR, "fatal error: %s (%s)", s, cmd_resp); fprintf(stderr, "fatal error: %s (%s)\n", s, cmd_resp); } else { syslog(LOG_ERR, "fatal error: %s", s); fprintf(stderr, "fatal error: %s\n", s); } exit(code); } /*********************** * Parse a mech list of the form: ... AUTH=foo AUTH=bar ... * * Return: string with mechs seperated by spaces * ***********************/ typedef struct capabilies_s { char *mechs; /* 0 = false; 1 = true */ int starttls; int logindisabled; } capabilities_t; static capabilities_t *parsecapabilitylist(char *str) { char *tmp; int num=0; capabilities_t *ret=(capabilities_t *) xmalloc(sizeof(capabilities_t)); ret->mechs = (char *)xmalloc(strlen(str)+1); ret->starttls=0; ret->logindisabled=0; /* check for stattls */ if (strstr(str,"STARTTLS")!=NULL) { ret->starttls=1; } /* check for login being disabled */ if (strstr(str,"LOGINDISABLED")!=NULL) { ret->logindisabled=1; } strcpy(ret->mechs,""); while ((tmp=strstr(str,"AUTH="))!=NULL) { char *end=tmp+5; tmp+=5; while(((*end)!=' ') && ((*end)!='\0')) end++; (*end)='\0'; /* add entry to list */ if (num>0) strcat(ret->mechs," "); strcat(ret->mechs, tmp); num++; /* reset the string */ str=end+1; } return ret; } /* * IMAP command completion callback */ static void callback_capability(struct imclient *imclient, void *rock, struct imclient_reply *reply) { (void)imclient; char *s; capabilities_t **caps = (capabilities_t **) rock; s = reply->text; *caps = parsecapabilitylist(s); } /* * IMAP command completion callback */ static void callback_finish(struct imclient *imclient, void *rock, struct imclient_reply *reply) { (void)imclient; (void)rock; if (!strcmp(reply->keyword, "OK")) { cmd_done = IMAP_OK; } else if (!strcmp(reply->keyword, "NO")) { cmd_resp = reply->text; cmd_done = IMAP_NO; } else if (!strcmp(reply->keyword, "BAD")) { cmd_resp = reply->text; cmd_done = IMAP_BAD; } else if (!strcmp(reply->keyword, "EOF")) { syslog(LOG_ERR, "connection closed prematurely"); cmd_done = IMAP_EOF; } else { printf("Huh?\n"); cmd_done = IMAP_BAD; } } /* * Callback to deal with untagged LIST/LSUB data */ extern void callback_list(struct imclient *imclient, void *rock, struct imclient_reply *reply); /* void print_stats(mbox_stats_t *stats) { syslog(LOG_INFO, "total messages considered %d deleted %d", stats->total, stats->deleted); printf("total messages \t\t %d\n",stats->total); printf("deleted messages \t\t %d\n",stats->deleted); printf("remaining messages\t\t %d\n\n",stats->total - stats->deleted); } */ static void callback_exists(struct imclient *imclient, void *rock, struct imclient_reply *reply) { (void)imclient; (void)rock; current_mbox_exists = reply->msgno; } static void callback_search(struct imclient *imclient, void *rock, struct imclient_reply *reply) { (void)imclient; uid_list_t *uids = (uid_list_t *) rock; const char *s; uint32_t num; s = reply->text; while (Uisdigit(*s)) { if (parseuint32(s, &s, &num)) break; if (uids->size >= uids->allocsize) { if (uids->allocsize) uids->allocsize *= 2; else uids->allocsize = 250; uids->list = xrealloc(uids->list, sizeof(unsigned long) * uids->allocsize); } uids->list[uids->size] = num; uids->size++; if (*s == '\0') break; s++; } } static int send_delete(const char *mbox, const char *uidlist) { imclient_send(imclient_conn, callback_finish, imclient_conn, "UID STORE %a +FLAGS.SILENT (\\Deleted)", uidlist); cmd_done = NOTFINISHED; while (cmd_done == NOTFINISHED) { imclient_processoneevent(imclient_conn); } if (cmd_done == IMAP_OK) return 0; else if (cmd_done == IMAP_NO) { syslog(LOG_ERR, "%s can't mark messages deleted: %s", mbox, cmd_resp ? cmd_resp : ""); return -1; } else fatal("marking message deleted", EC_TEMPFAIL); } static void mark_all_deleted(const char *mbox, uid_list_t *list, mbox_stats_t *stats) { int i; char buf[1024]; int pos; unsigned long run_start; int first_time; unsigned long *A = list->list; int r; if (list->size == 0) return; /* we send blocks of 500 or so characters */ i = 0; pos = 0; first_time = 1; run_start = A[i++]; r = 0; for (; i < list->size && r == 0; i++) { if (A[i] == A[i-1] + 1) continue; /* continue this run */ if (first_time) { first_time = 0; } else { buf[pos++] = ','; } if (run_start != A[i-1]) { /* run contains more than one entry */ pos += sprintf(buf + pos, "%lu:%lu", run_start, A[i-1]); } else { /* singleton */ pos += sprintf(buf + pos, "%lu", A[i-1]); } if (pos > 500) { r = send_delete(mbox, buf); pos = 0; first_time = 1; } run_start = A[i]; } if (!r) { /* handle the last entry */ if (!first_time) { buf[pos++] = ','; } if (run_start != A[i-1]) { sprintf(buf + pos, "%lu:%lu", run_start, A[i-1]); } else { sprintf(buf + pos, "%lu", A[i-1]); } /* send out the last one */ send_delete(mbox, buf); stats->deleted += list->size; } } static char *month_string(int mon) { switch(mon) { case 0: return "Jan"; case 1: return "Feb"; case 2: return "Mar"; case 3: return "Apr"; case 4: return "May"; case 5: return "Jun"; case 6: return "Jul"; case 7: return "Aug"; case 8: return "Sep"; case 9: return "Oct"; case 10: return "Nov"; case 11: return "Dec"; default: return "BAD"; } } /* we don't check what comes in on matchlen and maycreate, should we? */ static int purge_me(char *name, time_t when) { mbox_stats_t stats; char search_string[200]; static uid_list_t uidlist; struct tm *my_tm; if (when == 0) return 0; my_tm = gmtime(&when); snprintf(search_string,sizeof(search_string), "BEFORE %d-%s-%d", my_tm->tm_mday, month_string(my_tm->tm_mon), 1900+my_tm->tm_year); if (noop) { printf("%s: %s\n", name, search_string); return 0; } memset(&stats, '\0', sizeof(mbox_stats_t)); spew(2, "%s selecting", name); /* select mailbox */ imclient_addcallback(imclient_conn, "EXISTS", CALLBACK_NUMBERED, callback_exists, (void *)0, (char *)0); imclient_send(imclient_conn, callback_finish, (void *)imclient_conn, "%a %s", "SELECT", name); cmd_done = NOTFINISHED; while (cmd_done == NOTFINISHED) { imclient_processoneevent(imclient_conn); } spew(2, "%s selecting", name); if (cmd_done == IMAP_NO) { syslog(LOG_ERR, "unable to select %s: %s", name, cmd_resp); return 0; } else if (cmd_done != IMAP_OK) { fatal("selecting mailbox", EC_TEMPFAIL); } stats.total = current_mbox_exists; spew(2, "%s exists %d", name, current_mbox_exists); /* Only search if there are actually messages in the mailbox! */ if(current_mbox_exists) { /* make out list of uids */ uidlist.size = 0; /* reset to 0 */ spew(3, "%s searching for messages %s", name, search_string); imclient_addcallback(imclient_conn, "SEARCH", 0, callback_search, (void *)&uidlist, (char *)0); imclient_send(imclient_conn, callback_finish, (void *)imclient_conn, "UID SEARCH %a", search_string); cmd_done = NOTFINISHED; while (cmd_done == NOTFINISHED) { imclient_processoneevent(imclient_conn); } if (cmd_done != IMAP_OK) { fatal("UID Search failed", EC_TEMPFAIL); } if (uidlist.size > 0) { mark_all_deleted(name, &uidlist, &stats); } } after_search: /* close mailbox */ imclient_send(imclient_conn, callback_finish, (void *)imclient_conn, "CLOSE"); cmd_done = NOTFINISHED; while (cmd_done == NOTFINISHED) { imclient_processoneevent(imclient_conn); } if (cmd_done != IMAP_OK) { fatal("unable to CLOSE mailbox", EC_TEMPFAIL); } if(current_mbox_exists) { spew(1, "%s exists %d deleted %d", name, current_mbox_exists, uidlist.size); } else { spew(1, "%s exists %d (skipped)", name, current_mbox_exists, uidlist.size); } return 0; } static int purge_all(void) { int num = 0; int ret = 0; while (ret == 0) { ret = ExpireExists(num); if (ret == 0) purge_me(GetExpireName(num), GetExpireTime(num)); num++; } return 0; } static void do_list(char *matchstr) { imclient_send(imclient_conn, callback_finish, (void *)imclient_conn, "%a %s %s", "LIST", "*", matchstr); cmd_done = NOTFINISHED; while (cmd_done == NOTFINISHED) { imclient_processoneevent(imclient_conn); } if (cmd_done!=IMAP_OK) fatal("unable to LIST mailboxes", EC_TEMPFAIL); } /* * What we were given on the command line might just be a path or might not have an extension etc... */ static char *parseconfigpath(char *str) { char *ret; /* if it ends with a '/' add expire.ctl */ if (str[strlen(str)-1] == '/') { ret = (char *) xmalloc(strlen(str)+strlen("expire.ctl")+1); strcpy(ret,str); strcat(ret,"expire.ctl"); return ret; } return str; } static void remote_purge(char *configpath, char **matches) { char *name; imclient_addcallback(imclient_conn, "LIST", 0, callback_list, (void *)0, (char *)0); if (matches[0]==NULL) { syslog(LOG_WARNING, "matching all mailboxes for possible purge"); spew(1, "matching all mailboxes"); do_list("*"); } else { while (matches[0]!=NULL) { spew(0, "matching %s", matches[0]); do_list(matches[0]); matches++; } } spew(1, "completed list"); if (configpath!=NULL) { name = parseconfigpath(configpath); configstream = fopen(name,"r"); if (configstream == NULL) fatal("unable to open config file", EC_CONFIG); EXPreadfile(configstream); /* ret val */ } else { artificial_matchall(days); } purge_all(); } /* didn't give correct parameters; let's exit */ static void usage(void) { printf("Usage: remotepurge [options] hostname [[match1] ... ]\n"); printf(" -p port : port to use\n"); printf(" -k # : minimum protection layer required\n"); printf(" -l # : max protection layer (0=none; 1=integrity; etc)\n"); printf(" -u user : authorization name to use\n"); printf(" -v : verbose\n"); printf(" -n : don't actually purge\n"); printf(" -m mech : SASL mechanism to use (\"login\" for LOGIN)\n"); printf(" -r realm : realm\n"); printf(" -e expire.ctl : use expire.ctl file (specify full path)\n"); printf(" -d days : purge all message old\n"); exit(EC_USAGE); } int main(int argc, char **argv) { char *mechanism=NULL; char servername[1024]; char *expirectlfile = NULL; int maxssf = 128; int minssf = 0; char c; char *tls_keyfile="";(void)tls_keyfile; char *port = "imap"; int dotls=0; int r; capabilities_t *capabilitylist; /* look at all the extra args */ while ((c = getopt(argc, argv, "d:vne:k:l:p:u:a:m:t:")) != EOF) switch (c) { case 'd': days = atoi(optarg); break; case 'e': expirectlfile = optarg; break; case 'v': verbose++; break; case 'k': minssf=atoi(optarg); break; case 'l': maxssf=atoi(optarg); break; case 'p': port = optarg; break; case 'u': username = optarg; break; case 'm': mechanism=optarg; break; case 'r': realm=optarg; break; case 't': dotls=1; tls_keyfile=optarg; break; case 'n': noop = 1; break; case '?': default: usage(); break; } (void)dotls;(void)mechanism; if (optind >= argc) usage(); if ((days==-1) && (expirectlfile == NULL)) { printf("Must specify expire.ctl file OR days old OR bytes large\n\n"); usage(); } /* next to last arg is server name */ strncpy(servername, argv[optind], 1023); r = imclient_connect (&imclient_conn, servername, port, NULL); if (r!=0) { fatal("imclient_connect()", EC_TEMPFAIL); } spew(0, "connected"); /* get capabilities */ imclient_addcallback(imclient_conn, "CAPABILITY", 0, callback_capability, (void *) &capabilitylist, (char *) 0); imclient_send(imclient_conn, callback_finish, NULL, "CAPABILITY"); cmd_done = 0; while (cmd_done == 0) { imclient_processoneevent(imclient_conn); } r = imclient_authenticate(imclient_conn, capabilitylist->mechs, "imap", username, minssf, maxssf); if (r!=0) { fatal("imclient_authenticate()\n", EC_CONFIG); } spew(0, "authenticated"); readconfig_init(); remote_purge(expirectlfile, argv+(optind+1)); spew(0, "done"); exit(0); } cyrus-imapd-2.5.10/netnews/inn.diffs0000755000175000017500000034420413001236020014236 00000000000000This is a patch against INN 2.2.1 for allowing INN to deliver directly to an IMAP server using LMTP and IMAP (to handle control messages) This patch will hopefully be included in future versions on INN. To configure INN to deliver to an IMAP server put something like the following in your newsfeeds file. imapfeed!:\ !*,\ :Tc,Wnm*,S30000:/usr/news/bin/startinnfeed imapfeed # A real-time feed through innfeed. myhostname.cmu.edu\ :!junk,!control/!foo\ :Tm:imapfeed! *** Makefile.old Mon Feb 28 00:50:47 2000 --- Makefile Thu Feb 10 23:39:19 2000 *************** *** 19,25 **** SRC = article.c \ buffer.c \ - connection.c \ endpoint.c \ host.c \ innlistener.c \ --- 19,24 ---- *************** *** 51,61 **** --- 50,62 ---- config_l.o config_y.o INNFEED_BIN = $D$(PATHBIN)/innfeed + IMAPFEED_BIN = $D$(PATHBIN)/imapfeed STARTINNFEED = $D$(PATHBIN)/startinnfeed ALL_INSTALLED = $D$(PATHBIN)/innfeed $D$(PATHBIN)/startinnfeed \ + $D$(PATHBIN)/imapfeed \ $D$(PATHBIN)/procbatch $D$(PATHBIN)/innfeed-convcfg MAN_INSTALLED = $D$(MANDIR)/man1/innfeed.1 $D$(MANDIR)/man5/innfeed.conf.5 *************** *** 95,101 **** DEPENDFLAGS = -s -c '$(CC) -E' .c.o: ! $(COMPILE.c) $< $(OUTPUT_OPTION) .c.E: $(CPP.c) $< $(OUTPUT_OPTION) --- 96,102 ---- DEPENDFLAGS = -s -c '$(CC) -E' .c.o: ! $(COMPILE.c) $(SASLFLAGS) $< $(OUTPUT_OPTION) .c.E: $(CPP.c) $< $(OUTPUT_OPTION) *************** *** 103,114 **** .sh: $(RM) $@ ; $(CP) $< $@ ; $(CHMOD) a-w,a+x $@ ! all: innfeed startinnfeed install: $(ALL_INSTALLED) ! innfeed: $(OBJS) version.o $(MALLOC) $(LIBNEWS) ! $(LINK.c) -o $@ $(OBJS) version.o $(LIBNEWS) $(LIBNEWS) $(LIBS) $D$(PATHBIN)/innfeed: innfeed $(LIBTOOL) ../installit.sh $(OWNER) -m 550 -b .OLD $? $@ --- 104,118 ---- .sh: $(RM) $@ ; $(CP) $< $@ ; $(CHMOD) a-w,a+x $@ ! all: innfeed startinnfeed imapfeed install: $(ALL_INSTALLED) ! innfeed: $(OBJS) version.o connection.o $(MALLOC) $(LIBNEWS) ! $(LINK.c) -o $@ $(OBJS) version.o connection.o $(LIBNEWS) $(LIBNEWS) $(LIBS) ! ! imapfeed: $(OBJS) version.o imap_connection.o $(MALLOC) $(LIBNEWS) ! $(LINK.c) -o $@ $(OBJS) version.o imap_connection.o $(LIBNEWS) $(LIBNEWS) $(LIBS) $(LIB_SASL) $D$(PATHBIN)/innfeed: innfeed $(LIBTOOL) ../installit.sh $(OWNER) -m 550 -b .OLD $? $@ *************** *** 135,140 **** --- 139,145 ---- echo "" ; echo "" ;\ fi + objs: $(OBJS) tags: $(SRC) $(INCS) *************** *** 227,232 **** --- 232,239 ---- article.o: article.c article.h buffer.h config.h endpoint.h misc.h \ msgs.h sysconfig.h buffer.o: buffer.c buffer.h config.h misc.h sysconfig.h + imapconnection.o: article.h buffer.h config.h configfile.h imapconnection.c \ + connection.h endpoint.h host.h misc.h msgs.h sysconfig.h connection.o: article.h buffer.h config.h configfile.h connection.c \ connection.h endpoint.h host.h misc.h msgs.h sysconfig.h endpoint.o: buffer.h config.h configfile.h endpoint.c endpoint.h host.h \ polarbear:/afs/andrew/system/src/host/inn/013/innfeed> diff -c main.old main.c *** main.old Mon Feb 28 00:51:23 2000 --- main.c Tue Feb 1 00:33:54 2000 *************** *** 103,108 **** --- 103,113 ---- bool useMMap = false ; void (*gPrintInfo) (void) ; char *dflTapeDir; + /* these are used by imapfeed */ + char *deliver_username = NULL; + char *deliver_authname = NULL; + char *deliver_password = NULL; + char *deliver_realm = NULL; /* imports */ extern char *versionInfo ; *************** *** 162,168 **** struct rlimit rl; bool val; - strcpy (dateString,ctime(&now)) ; dateString [24] = '\0' ; --- 167,172 ---- *************** *** 842,847 **** --- 846,877 ---- logFile = buildFilename (innconf->pathlog,p) ; FREE (p) ; } + + /* For imap/lmtp delivering */ + if (getString (topScope,"deliver-username",&p, NO_INHERIT)) + { + deliver_username = p; + /* don't need to free */ + } + + if (getString (topScope,"deliver-authname",&p, NO_INHERIT)) + { + deliver_authname = p; + /* don't need to free */ + } + + if (getString (topScope,"deliver-password",&p, NO_INHERIT)) + { + deliver_password = p; + /* don't need to free */ + } + + if (getString (topScope,"deliver-realm",&p, NO_INHERIT)) + { + deliver_realm = p; + /* don't need to free */ + } + return 1 ; polarbear:/afs/andrew/system/src/host/inn/013/innfeed> diff -c startinnfeed.old startinnfeed.c *** startinnfeed.old Mon Feb 28 00:50:28 2000 --- startinnfeed.c Mon Feb 28 14:06:28 2000 *************** *** 78,86 **** else { char **evp = NULL ; ! innfeed = NEW(char, (strlen(innconf->pathbin)+1+strlen(INNFEED)+1)); ! sprintf(innfeed, "%s/%s", innconf->pathbin, INNFEED); av[0] = (char *) innfeed; #if defined (USE_DMALLOC) --- 78,98 ---- else { char **evp = NULL ; + char *execname = INNFEED; + + if (ac == 2) + { + if (strcmp(av[1], "imapfeed") == 0) { + execname = imapfeed; + av[1] = NULL; + } else { + syslog(LOG_ERR, "Only imapfeed is a valid argument to startinnfeed"); + exit(1); + } + } ! innfeed = NEW(char, (strlen(innconf->pathbin)+1+strlen(execname)+1)); ! sprintf(innfeed, "%s/%s", innconf->pathbin, execname); av[0] = (char *) innfeed; #if defined (USE_DMALLOC) polarbear:/afs/andrew/system/src/host/inn/013/innfeed> diff -c /dev/null imap_connection.c *** /dev/null Mon Dec 31 23:00:00 1979 --- imap_connection.c Mon Feb 28 00:45:20 2000 *************** *** 0 **** --- 1,4408 ---- + /* feed articles to an IMAP server via LMTP and IMAP + Tim Martin + + Instead of feeding articles via nntp to another host this feeds the + messages via lmtp to a host and the control messages (cancel's + etc..) it preforms via IMAP. This means it has 2 active connections + at any given time and 2 queues. + + When an article comes in it is immediatly placed in the lmtp + queue. When an article is picked off the lmtp queue for processing + first check if it's a control message. if so place it in the IMAP + queue. If not attempt to deliver via lmtp. + + This attempts to follow the exact same api as connection.c. + + TODO: + + feed to smtp + security layers? <--punt on for now + authname/password per connection object + untagged IMAP messages + */ + + #ifdef HAVE_SASL + #include + #endif /* HAVE_SASL */ + + #include + #include + #include + #include + #include + #include + #include + + #include + + #include "buffer.h" + #include "connection.h" + #include "endpoint.h" + #include "host.h" + #include "article.h" + #include "msgs.h" + #include "configfile.h" + #include "clibrary.h" + + + + #define IMAP_PORT 143 + + #ifdef SMTPMODE + #define LMTP_PORT 25 + #else + #define LMTP_PORT 2003 + #endif /* SMTPMODE */ + + /* The name to prepend to deliver directly to newsgroup bboards */ + #define NEWS_USERNAME "bb" + + #define IMAP_TAGLENGTH 6 + + #define QUEUE_MAX_SIZE 250 + + #define DOSOMETHING_TIMEOUT 60 + + + + /* external */ + extern char *deliver_username; + extern char *deliver_authname; + extern char *deliver_password; + extern char *deliver_realm; + + + char hostname[MAXHOSTNAMELEN]; + char *mailfrom_name = ""; /* default to no return path */ + + /* states the imap connection may be in */ + typedef enum { + + IMAP_DISCONNECTED = 1, + IMAP_WAITING, + + IMAP_CONNECTED_NOTAUTH, + + IMAP_READING_INTRO, + + IMAP_WRITING_CAPABILITY, + IMAP_READING_CAPABILITY, + + IMAP_WRITING_STARTAUTH, + IMAP_READING_STEPAUTH, + IMAP_WRITING_STEPAUTH, + + IMAP_IDLE_AUTHED, + + IMAP_WRITING_CREATE, + IMAP_READING_CREATE, + + IMAP_WRITING_DELETE, + IMAP_READING_DELETE, + + IMAP_WRITING_SELECT, + IMAP_READING_SELECT, + + IMAP_WRITING_SEARCH, + IMAP_READING_SEARCH, + + IMAP_WRITING_STORE, + IMAP_READING_STORE, + + IMAP_WRITING_CLOSE, + IMAP_READING_CLOSE, + + IMAP_WRITING_QUIT, + IMAP_READING_QUIT + + } imap_state_t; + + typedef enum { + LMTP_DISCONNECTED = 1, + LMTP_WAITING, + + LMTP_CONNECTED_NOTAUTH, + + LMTP_READING_INTRO, + + LMTP_WRITING_LHLO, + LMTP_READING_LHLO, + + LMTP_WRITING_STARTAUTH, + LMTP_READING_STEPAUTH, + LMTP_WRITING_STEPAUTH, + + LMTP_AUTHED_IDLE, + + LMTP_READING_MAILFROM, + LMTP_READING_RCPTTO, + LMTP_READING_DATA, + LMTP_READING_CONTENTS, + + LMTP_WRITING_UPTODATA, + LMTP_WRITING_CONTENTS, + + LMTP_WRITING_QUIT, + LMTP_READING_QUIT + + } lmtp_state_t; + + typedef struct imap_capabilities_s { + + int imap4; /* does server support imap4bis? */ + int logindisabled; /* does the server allow the login command? */ + + char *saslmechs; /* supported SASL mechanisms */ + + } imap_capabilities_t; + + typedef struct lmtp_capabilities_s { + + int Eightbitmime; + int EnhancedStatusCodes; + int pipelining; + + char *saslmechs; + + } lmtp_capabilities_t; + + typedef enum { + STAT_CONT = 0, + STAT_NO = 1, + STAT_OK = 2, + STAT_FAIL = 3 + } imt_stat; + + /* Message types */ + typedef enum { + + DELIVER, + CREATE_FOLDER, + CANCEL_MSG, + DELETE_FOLDER + + } control_type_t; + + typedef struct control_item_s { + + Article article; + char *folder; + char *msgid; /* only for cancel's */ + unsigned long uid; /* only for cancel's */ + + } control_item_t; + + typedef struct article_queue_s { + + control_type_t type; + + time_t arrived; + time_t nextsend; /* time we should next try to send article */ + + int trys; + + int counts_toward_size; + + union { + Article article; + control_item_t *control; + void *generic; + } data; + + struct article_queue_s *next; + + } article_queue_t; + + typedef struct Q_s { + + article_queue_t *head; + + article_queue_t *tail; + + int size; + + } Q_t; + + typedef struct connection_s { + + /* common stuff */ + char *ServerName; + + char *lmtp_respBuffer; /* buffer all responses are read into */ + Buffer lmtp_rBuffer; /* buffer all responses are read into */ + + Host myHost ; /* the host who owns the connection */ + + time_t timeCon ; /* the time the connect happened (last auth suceeded) */ + + int issue_quit; /* Three states: + * 0 - don't do anything + * 1 - after issue quit enter wait state + * 2 - after issue quit reconnect + * 3 - after issue quit delete connection + * 4 - nuke cxn + */ + + /* Statistics */ + int lmtp_suceeded; + int lmtp_failed; + + int cancel_suceeded; + int cancel_failed; + + int create_suceeded; + int create_failed; + + int remove_suceeded; + int remove_failed; + + + /* LMTP stuff */ + int lmtp_port; + lmtp_state_t lmtp_state; + #ifdef HAVE_SASL + sasl_conn_t *saslconn_lmtp; + #endif /* HAVE_SASL */ + int sockfd_lmtp; + + time_t lmtp_timeCon ; + + EndPoint lmtp_endpoint; + u_int ident ; /* an identifier for syslogging. */ + + lmtp_capabilities_t *lmtp_capabilities; + + int lmtp_have_mailfrom; + int lmtp_disconnects; + char *lmtp_tofree_str; + + article_queue_t *current_article; + Buffer *current_bufs; + int current_rcpts_issued; + int current_rcpts_okayed; + + /* Timer for the max amount of time to wait for a response from the + remote */ + u_int lmtp_readTimeout ; + TimeoutId lmtp_readBlockedTimerId ; + + /* Timer for the max amount of time to wait for a any amount of data + to be written to the remote */ + u_int lmtp_writeTimeout ; + TimeoutId lmtp_writeBlockedTimerId ; + + /* Timer for the number of seconds to sleep before attempting a + reconnect. */ + u_int lmtp_sleepTimeout ; + TimeoutId lmtp_sleepTimerId ; + + /* Timer for max amount between queueing some articles and trying to send them */ + u_int dosomethingTimeout ; + TimeoutId dosomethingTimerId ; + + Q_t lmtp_todeliver_q; + + + + /* IMAP stuff */ + int imap_port; + #ifdef HAVE_SASL + sasl_conn_t *imap_saslconn; + #endif /* HAVE_SASL */ + + char *imap_respBuffer; + Buffer imap_rBuffer; + EndPoint imap_endpoint; + + imap_capabilities_t *imap_capabilities; + + int imap_sockfd; + + time_t imap_timeCon ; + + imap_state_t imap_state; + int imap_disconnects; + char *imap_tofree_str; + + char imap_currentTag[IMAP_TAGLENGTH]; + int imap_tag_num; + + /* Timer for the max amount of time to wait for a response from the + remote */ + u_int imap_readTimeout ; + TimeoutId imap_readBlockedTimerId ; + + /* Timer for the max amount of time to wait for a any amount of data + to be written to the remote */ + u_int imap_writeTimeout ; + TimeoutId imap_writeBlockedTimerId ; + + /* Timer for the number of seconds to sleep before attempting a + reconnect. */ + u_int imap_sleepTimeout ; + TimeoutId imap_sleepTimerId ; + + Q_t imap_controlMsg_q; + + article_queue_t *current_control; + + struct connection_s *next; + + } connection_t; + + static Connection gCxnList = NULL ; + static u_int gCxnCount= 0 ; + static u_int max_reconnect_period = MAX_RECON_PER ; + static u_int init_reconnect_period = INIT_RECON_PER; + + typedef enum { + RET_OK = 0, + RET_FAIL = 1, + RET_QUEUE_EMPTY, + RET_EXCEEDS_SIZE, + RET_NO_FULLLINE, + RET_NO, + RET_ARTICLE_BAD + } conn_ret; + + + /********** Private Function Declarations *************/ + + static void lmtp_readCB (EndPoint e, IoStatus i, Buffer *b, void *d); + static void imap_readCB (EndPoint e, IoStatus i, Buffer *b, void *d); + static void imap_writeCB (EndPoint e, IoStatus i, Buffer *b, void *d); + static void lmtp_writeCB (EndPoint e, IoStatus i, Buffer *b, void *d); + + static conn_ret lmtp_Connect(connection_t *cxn); + static conn_ret imap_Connect(connection_t *cxn); + + static void prepareReopenCbk (Connection cxn, int type); + + static void lmtp_readTimeoutCbk (TimeoutId id, void *data); + static void imap_readTimeoutCbk (TimeoutId id, void *data); + + static void dosomethingTimeoutCbk (TimeoutId id, void *data); + + static conn_ret WriteToWire_imapstr(connection_t *cxn, char *str, int slen); + static conn_ret WriteToWire_lmtpstr(connection_t *cxn, char *str, int slen); + + static conn_ret WriteToWire(connection_t *cxn, EndpRWCB callback, + EndPoint endp, Buffer *array); + static void lmtp_sendmessage(connection_t *cxn, Article justadded); + static conn_ret imap_ProcessQueue(connection_t *cxn); + + static conn_ret FindHeader(Buffer *bufs, char *header, char **start, char **end); + static conn_ret PopFromQueue(Q_t *q, article_queue_t **item); + static void QueueForgetAbout(connection_t *cxn, article_queue_t *item, int failed); + + static void delConnection (Connection cxn); + + static void DeferAllArticles(connection_t *cxn, Q_t *q); + + static void lmtp_Disconnect(connection_t *cxn); + static void imap_Disconnect(connection_t *cxn); + static conn_ret imap_listenintro(connection_t *cxn); + + static void imap_writeTimeoutCbk (TimeoutId id, void *data); + static void lmtp_writeTimeoutCbk (TimeoutId id, void *data); + + /******************** PRIVATE FUNCTIONS ***************************/ + + static char *imap_stateToString(int state) + { + switch (state) + { + case IMAP_DISCONNECTED: return "Disconnected"; + case IMAP_WAITING: return "Waiting"; + case IMAP_CONNECTED_NOTAUTH: return "Connected but not Authenticated"; + case IMAP_READING_INTRO: return "Reading Intro line"; + case IMAP_WRITING_CAPABILITY: return "Writing capability"; + case IMAP_READING_CAPABILITY: return "Reading capability"; + case IMAP_WRITING_STARTAUTH: return "Writing Startauth"; + case IMAP_READING_STEPAUTH: return "Reading Stepauth"; + case IMAP_WRITING_STEPAUTH: return "Writing Stepauth"; + case IMAP_IDLE_AUTHED: return "Idle. Authenticated"; + case IMAP_WRITING_CREATE: return "Writing create"; + case IMAP_READING_CREATE: return "Reading create response"; + case IMAP_WRITING_DELETE: return "Writing Delete command"; + case IMAP_READING_DELETE: return "Reading Delete response"; + case IMAP_WRITING_SELECT: return "Writing Select"; + case IMAP_READING_SELECT: return "Reading Select response"; + case IMAP_WRITING_SEARCH: return "Writing Search"; + case IMAP_READING_SEARCH: return "Reading Search response"; + case IMAP_WRITING_STORE: return "Writing Store"; + case IMAP_READING_STORE: return "Reading Store response"; + case IMAP_WRITING_CLOSE: return "Writing Close"; + case IMAP_READING_CLOSE: return "Reading Close response"; + case IMAP_WRITING_QUIT: return "Writing Quit"; + case IMAP_READING_QUIT: return "Reading Quit"; + default: return "Unknown state"; + } + } + + static char *lmtp_stateToString(int state) + { + switch(state) + { + case LMTP_DISCONNECTED: return "Disconnected"; + case LMTP_WAITING: return "Waiting"; + case LMTP_CONNECTED_NOTAUTH: return "Connected but not authenticated"; + case LMTP_READING_INTRO: return "Reading intro"; + case LMTP_WRITING_LHLO: return "Writing LHLO"; + case LMTP_READING_LHLO: return "Reading LHLO response"; + case LMTP_WRITING_STARTAUTH: return "Writing Start Auth"; + case LMTP_READING_STEPAUTH: return "Reading stepauth"; + case LMTP_WRITING_STEPAUTH: return "writing stepauth"; + case LMTP_AUTHED_IDLE: return "Idle. Authenticated"; + case LMTP_READING_MAILFROM: return "Reading mailfrom"; + case LMTP_READING_RCPTTO: return "Reading RCPTTO response"; + case LMTP_READING_DATA: return "Reading DATA response"; + case LMTP_READING_CONTENTS: return "Reading contents response"; + case LMTP_WRITING_UPTODATA: return "Writing MAIL FROM, RCPTTO, DATA commands"; + case LMTP_WRITING_CONTENTS: return "Writing contents of message"; + case LMTP_WRITING_QUIT: return "Writing Quit"; + case LMTP_READING_QUIT: return "Reading Quit"; + default: return "Unknown state"; + } + } + + /******************************* Queue functions ***********************************/ + + /* + * Add a message to a generic queue + * + * q - the queue adding to + * item - the data to add to the queue + * type - the type of item it is (i.e. cancel,lmtp,etc..) + * addsmsg - weather this should be counted toward the queue size + * this is for control msg's that create multiple queue items. + * For example a cancel message canceling a message in multiple + * newsgroups will create >1 queue item but we only want it to count + * once towards the queue + * must - wheather we must take it even though it may put us over our max size + */ + + static conn_ret AddToQueue(Q_t *q, void *item, control_type_t type, int addsmsg, bool must) + { + article_queue_t *newentry; + + if (must == false) + { + if (q->size >= QUEUE_MAX_SIZE) + { + return RET_EXCEEDS_SIZE; + } + } else { + if (q->size >= QUEUE_MAX_SIZE * 10) + { + d_printf(0,"Queue has grown way too much. Dropping article\n"); + return RET_FAIL; + } + } + + /* add to the end of our queue */ + newentry = (article_queue_t *) malloc(sizeof(article_queue_t)); + + newentry->type = type; + + /* send as soon as possible */ + newentry->nextsend = newentry->arrived = time(NULL); + + newentry->trys = 0; + + newentry->data.generic = item; + newentry->next = NULL; + newentry->counts_toward_size = addsmsg; + + /* add to end of queue */ + if (q->tail == NULL) + { + q->head = newentry; + q->tail = newentry; + } else { + + q->tail->next = newentry; + q->tail = newentry; + } + + q->size+=addsmsg; + + return RET_OK; + } + + /* + * Pop an item from the queue + * + * q - the queue to pop from + * item - where the item shall be placed upon sucess + * + */ + + static conn_ret PopFromQueue(Q_t *q, article_queue_t **item) + { + article_queue_t *todel; + + /* if queue empty return error */ + if ( q->head == NULL) + { + return RET_QUEUE_EMPTY; + } + + /* set what we return */ + *item = q->head; + + q->head = q->head->next; + if (q->head == NULL) q->tail = NULL; + + q->size-=(*item)->counts_toward_size; + + return RET_OK; + } + + /* + * ReQueue an item. Will either put it back in the queue for another try + * or forget about it + * + * cxn - our connection object (needed so forget about things) + * q - the queue to requeue to + * entry - the item to put back + */ + + static void ReQueue(connection_t *cxn, Q_t *q, article_queue_t *entry) + { + /* look at the time it's been here */ + entry->nextsend = time(NULL) + (entry->trys *30); /* xxx better formula? */ + + entry->trys++; + + /* give up after 5 tries xxx configurable??? */ + if (entry->trys == 5) + { + QueueForgetAbout(cxn, entry,1); + return; + } + + + /* ok let's add back to the end of the queue */ + entry->next = NULL; + + /* add to end of queue */ + if (q->tail == NULL) + { + q->head = entry; + q->tail = entry; + } else { + q->tail->next = entry; + q->tail = entry; + } + + q->size+=entry->counts_toward_size; + } + + + + /* + * Forget about an item. Tells host object if we suceeded/failed/etc with the message + * + * cxn - connection object + * item - item + * failed - type of failure (see below) + * + * failed: + * 0 - suceeded delivering message + * 1 - failed delivering message + * 2 - Try to give back to host + * 3 - Article missing (i.e. can't find on disk) + */ + + static void QueueForgetAbout(connection_t *cxn, article_queue_t *item, int failed) + { + Article art = NULL; + + switch (item->type) + { + case DELIVER: + if (failed>0) + cxn->lmtp_failed++; + art = item->data.article; + break; + + case CANCEL_MSG: + if (failed>0) + cxn->cancel_failed++; + free(item->data.control->msgid); + free(item->data.control->folder); + + if (item->counts_toward_size == 1) + art = item->data.control->article; + + free(item->data.control ); + break; + + case CREATE_FOLDER: + if (failed>0) + cxn->create_failed++; + free(item->data.control->folder); + + art = item->data.control->article; + + free(item->data.control ); + break; + + case DELETE_FOLDER: + if (failed>0) + cxn->remove_failed++; + free(item->data.control->folder); + + art = item->data.control->article; + + free(item->data.control ); + break; + + default: + d_printf(0,"Unknown type to forget about\n"); + break; + } + + if (art!=NULL) + switch (failed) + { + case 0: + hostArticleAccepted (cxn->myHost, cxn, art); + break; + case 1: + hostArticleRejected (cxn->myHost, cxn, art); + break; + case 2: + hostTakeBackArticle (cxn->myHost, cxn, art); + break; + case 3: + hostArticleIsMissing(cxn->myHost, cxn, art); + break; + default: + d_printf(0,"Not understood\n"); + + } + + free(item); + } + + /* + * How much space is available in the queue + */ + + static int QueueSpace(Q_t *q) + { + int ret = QUEUE_MAX_SIZE - q->size; + if (ret < 0) ret = 0; + return ret; + } + + /* + * How many items are in the queue + */ + + static int QueueItems(Q_t *q) + { + return q->size; + } + + + /***************************** END Queue functions ***********************************/ + + /***************************** Generic Parse Functions *******************************/ + + /* returns the end of the header */ + + static char *GetUntil(char *str) + { + while (((*str) != '\0') && ( (*str) != '\r') && ( (*str) != '\n')) + { + str++; + } + + return str; + } + + /* + * Finds the given header in the message + * Returns NULL if not found + * + * returns something malloc'ed + */ + static conn_ret FindHeader(Buffer *bufs, char *header, char **start, char **end) + { + Buffer b; + int size; + char *str_base; + char *str; + int headerlen = strlen(header); + + if (bufs==NULL) + { + if (start) + *start=NULL; + return RET_ARTICLE_BAD; + } + + b = bufs[0]; + size = bufferSize(b); + str_base = bufferBase(b); + str = str_base; + + while ( (((int)str) - ((int)str_base)) < size - headerlen) + { + if (*str == header[0]) + { + if ((strncasecmp(header, str, headerlen)==0) && ( *(str + headerlen)==':')) + { + if (start) + { + *start = str+headerlen+1; + + /* get rid of leading whitespace */ + while ( isspace((int) **start)) + (*start)++; + } + + if (end) + *end = GetUntil(str+headerlen+1); + + return RET_OK; + } + } /*else if (*str == '\n') { */ + /* end of headers */ + /* return RET_NO; + }*/ + /* str = GetUntil(str); + if (*str == '\n') str++; */ + str++; + } + + return RET_NO; + } + + static conn_ret GetLine(char *buf, char *ret, int retmaxsize) + { + char *str_base; + char *str; + + int size = strlen(buf); + str_base = buf; + str = str_base; + + while ( (*str) != '\0') + { + if ((*str) == '\n') + { + if (str-str_base > retmaxsize) + { + d_printf(0,"Max size exceeded! %s\n",str_base); + return RET_FAIL; + } + + /* fill in the return string */ + memcpy(ret, str_base, str-str_base); + ret[ str - str_base -1] = '\0'; + + memcpy( str_base, str_base + (str-str_base)+1, size - (str-str_base)); + str_base[size - (str-str_base)]='\0'; + + return RET_OK; + } + + str++; + } + + /* couldn't find a full line */ + return RET_NO_FULLLINE; + } + + + + /************************** END Generic Parse Functions *******************************/ + + /************************ Writing to Network functions *****************/ + + static conn_ret WriteToWire(connection_t *cxn, EndpRWCB callback, + EndPoint endp, Buffer *array) + { + + if (array == NULL) return RET_FAIL; + + prepareWrite (endp, + array, + NULL, + callback, + cxn); + + return RET_OK; + } + + static conn_ret WriteToWire_str(connection_t *cxn, EndpRWCB callback, + EndPoint endp, char *str, int slen) + { + bool res; + conn_ret result; + Buffer buff; + Buffer *writeArr; + char *p; + + if (slen==-1) slen = strlen(str); + + buff = newBufferByCharP(str, slen+1, slen); + ASSERT (buff != NULL); + + writeArr = makeBufferArray (buff, NULL) ; + + result = WriteToWire(cxn, callback, endp, writeArr); + + return result; + } + + static conn_ret WriteToWire_imapstr(connection_t *cxn, char *str, int slen) + { + /* prepare the timeouts */ + clearTimer (cxn->imap_readBlockedTimerId) ; + + /* set up the write timer. */ + clearTimer (cxn->imap_writeBlockedTimerId) ; + + if (cxn->imap_writeTimeout > 0) + cxn->imap_writeBlockedTimerId = prepareSleep (imap_writeTimeoutCbk, cxn->imap_writeTimeout, + cxn); + cxn->imap_tofree_str = str; + return WriteToWire_str(cxn, imap_writeCB, cxn->imap_endpoint, str, slen); + } + + static conn_ret WriteToWire_lmtpstr(connection_t *cxn, char *str, int slen) + { + /* prepare the timeouts */ + clearTimer (cxn->lmtp_readBlockedTimerId) ; + + /* set up the write timer. */ + clearTimer (cxn->lmtp_writeBlockedTimerId) ; + + if (cxn->lmtp_writeTimeout > 0) + cxn->lmtp_writeBlockedTimerId = prepareSleep (lmtp_writeTimeoutCbk, cxn->lmtp_writeTimeout, + cxn) ; + + + + cxn->lmtp_tofree_str = str; + return WriteToWire_str(cxn, lmtp_writeCB, cxn->lmtp_endpoint, str, slen); + } + + static conn_ret WriteArticle(connection_t *cxn, Buffer *array) + { + int array_len = bufferArrayLen (array); + int lup=0; + int result; + + for (lup=0;luplmtp_endpoint, array); + + if (result!=RET_OK) + { + return result; + } + + cxn->lmtp_state = LMTP_WRITING_CONTENTS; + + return RET_OK; + } + + /************************ END Writing to Network functions *****************/ + + + + /* + * Adds a cancel item to the control queue + * Cancel item to delete message with in + * + * cxn - connection object + * folder - pointer to start of folder string (this is a pointer into the actual message buffer) + * folderlen - length of folder string + * msgid - pointer to start of msgid string (this is a pointer into the actual message buffer) + * msgidlen - length of msgid string + * art - the article for this control message (NULL if this cancel object lacks one) + * must - if must be accepted into queue + */ + + static conn_ret addCancelItem(connection_t *cxn, char *folder, int folderlen, char *msgid, int msgidlen, + Article art, int must) + { + control_item_t *item; + conn_ret result; + + ASSERT(folder); ASSERT(msgid); ASSERT(cxn); + + /* create the object */ + item = CALLOC (control_item_t, 1) ; + ASSERT (item != NULL) ; + + item->folder = calloc (folderlen+1, 1); + ASSERT (item->folder != NULL); + memcpy(item->folder, folder, folderlen); + item->folder[folderlen] = '\0'; + + item->msgid = calloc (msgidlen+1, 1); + ASSERT (item->msgid != NULL); + memcpy(item->msgid, msgid, msgidlen); + item->msgid[msgidlen] = '\0'; + + item->article = art; + + /* try to add to the queue (counts if art isn't null) */ + result = AddToQueue(&(cxn->imap_controlMsg_q), item, CANCEL_MSG, (art != NULL), must); + if (result != RET_OK) + { + d_printf(1,"I thought we had space in queue but apparently not\n"); + + /* cleanup */ + free(item->folder); + free(item->msgid); + free(item); + + return result; + } + + return RET_OK; + } + + static conn_ret AddControlMsg(connection_t *cxn, Article art, Buffer *bufs, char *control_header, + char *control_header_end, bool must) + { + char *rcpt_list = NULL, *rcpt_list_end; + char *orig_control_header; + control_item_t *item; + int res; + conn_ret result; + + + /* make sure contents ok; this also should load it into memory */ + res = artContentsOk (art); + if (res==false) + { + d_printf(0,"Article seems bad\n"); + hostArticleIsMissing (cxn->myHost, cxn, art); + return RET_FAIL; + } + + /* now let's look at the control to see what it is */ + + orig_control_header = control_header; /* save so we can free later */ + + if (strncasecmp(control_header,"newgroup",8)==0) + { + /* jump past "newgroup" */ + control_header+=8; + + /* go past all white space */ + while (( (*control_header)==' ') && ((*control_header)=='\t') && (control_header!=control_header_end)) + { + control_header++; + } + + if (control_header == control_header_end) + { + d_printf(0,"Control header contains newgroup with no group specified\n"); + res = RET_FAIL; + goto cleanup; + } + + item = CALLOC (control_item_t, 1); + ASSERT (item != NULL) ; + + item->folder = calloc (strlen(control_header)+1, 1); + ASSERT (item->folder != NULL); + strcpy(item->folder, control_header); + + item->article = art; + + result = AddToQueue(&(cxn->imap_controlMsg_q), item, CREATE_FOLDER,1,must); + if (result != RET_OK) + { + d_printf(1,"I thought we had space in queue but apparently not\n"); + res = RET_FAIL; + goto cleanup; + } + + } else if (strncasecmp(control_header,"rmgroup",7)==0) + { + + /* jump past "rmgroup" */ + control_header+=7; + + while (( (*control_header)==' ') && (control_header!=control_header_end)) + { + control_header++; + } + + if (control_header == control_header_end) + { + d_printf(0,"Control header contains rmgroup with no group specified\n"); + res = RET_FAIL; + goto cleanup; + } + + item = CALLOC (control_item_t, 1); + ASSERT (item != NULL) ; + + + item->folder = calloc (strlen(control_header)+1, 1); + ASSERT (item->folder != NULL); + strcpy(item->folder, control_header); + + item->article = art; + + result = AddToQueue(&(cxn->imap_controlMsg_q), item, DELETE_FOLDER,1,must); + if (result != RET_OK) + { + d_printf(1,"I thought we had space in queue but apparently not\n"); + res = RET_FAIL; + goto cleanup; + } + + } else if (strncasecmp(control_header,"cancel",6)==0) { + char *str, *laststart; + int tmplen; + + /* jump past "cancel" */ + control_header+=6; + + while (( (*control_header)==' ') && (control_header!=control_header_end)) + { + control_header++; + } + + if (control_header == control_header_end) + { + d_printf(0,"Control header contains cancel with no msgid specified\n"); + res = RET_FAIL; + goto cleanup; + } + + result = FindHeader(bufs, "Newsgroups", &rcpt_list, &rcpt_list_end); + if (result!=RET_OK) + { + d_printf(0,"Cancel msg contains no newsgroups header\n"); + res = RET_FAIL; + goto cleanup; + } + + str = rcpt_list; + laststart = rcpt_list; + + while ( str != rcpt_list_end) + { + if ((*str) == ',') + { + /* eliminate leading whitespace */ + while (((*laststart) ==' ') || ((*laststart)=='\t')) + { + laststart++; + } + + res = addCancelItem(cxn, laststart, str - laststart, control_header, control_header_end - control_header, + NULL,must); + if (res!=RET_OK) goto cleanup; + + laststart = str+1; + } + + str++; + } + + if (laststartmyHost), cxn->ident); + d_printf(1,"imap queue = %d lmtp queue = %d\n",QueueItems(&(cxn->imap_controlMsg_q)), + QueueItems(&(cxn->lmtp_todeliver_q))); + d_printf(1,"imap state = %s\n",imap_stateToString(cxn->imap_state)); + d_printf(1,"lmtp state = %s\n",lmtp_stateToString(cxn->lmtp_state)); + d_printf(1,"delivered: yes: %d no: %d\n",cxn->lmtp_suceeded, cxn->lmtp_failed); + d_printf(1,"control: yes: %d no: %d\n",cxn->cancel_suceeded, cxn->cancel_failed); + d_printf(1,"create: yes: %d no: %d\n",cxn->create_suceeded, cxn->create_failed); + d_printf(1,"remove: yes: %d no: %d\n",cxn->remove_suceeded, cxn->remove_failed); + } + + /**************************** SASL helper functions ******************************/ + + #ifdef HAVE_SASL + /* callback to get userid or authid */ + static int getsimple(void *context __attribute__((unused)), + int id, + const char **result, + unsigned *len) + { + char *username; + char *authid; + + if (! result) + return SASL_BADPARAM; + + switch (id) { + case SASL_CB_GETREALM: + *result = deliver_realm; + if (len) + *len = deliver_realm ? strlen(deliver_realm) : 0; + break; + + case SASL_CB_USER: + *result = deliver_username; + if (len) + *len = deliver_username ? strlen(deliver_username) : 0; + break; + case SASL_CB_AUTHNAME: + authid=deliver_authname; + *result = authid; + if (len) + *len = authid ? strlen(authid) : 0; + break; + case SASL_CB_LANGUAGE: + *result = NULL; + if (len) + *len = 0; + break; + default: + return SASL_BADPARAM; + } + return SASL_OK; + } + + /* callback to get password */ + static int + getsecret(sasl_conn_t *conn, + void *context __attribute__((unused)), + int id, + sasl_secret_t **psecret) + { + if (! conn || ! psecret || id != SASL_CB_PASS) + return SASL_BADPARAM; + + if (deliver_password==NULL) + { + d_printf(0,"SASL requested a password but I don't have one\n"); + return SASL_FAIL; + } + + *psecret = (sasl_secret_t *) malloc(sizeof(sasl_secret_t)+strlen(deliver_password)+1); + if (! *psecret) + return SASL_FAIL; + + strcpy((*psecret)->data, deliver_password); + (*psecret)->len=strlen(deliver_password); + + return SASL_OK; + } + + + /* callbacks we support */ + static sasl_callback_t saslcallbacks[] = { + { + SASL_CB_GETREALM, &getsimple, NULL + }, { + SASL_CB_USER, &getsimple, NULL + }, { + SASL_CB_AUTHNAME, &getsimple, NULL + }, { + SASL_CB_PASS, &getsecret, NULL + }, { + SASL_CB_LIST_END, NULL, NULL + } + }; + + static sasl_security_properties_t *make_secprops(int min,int max) + { + sasl_security_properties_t *ret=(sasl_security_properties_t *) + malloc(sizeof(sasl_security_properties_t)); + + ret->maxbufsize=1024; + ret->min_ssf=min; + ret->max_ssf=max; + + ret->security_flags=0; + ret->property_names=NULL; + ret->property_values=NULL; + + return ret; + } + + static conn_ret SetSASLProperties(sasl_conn_t *conn, int sock, int minssf, int maxssf) + { + int saslresult; + sasl_security_properties_t *secprops=NULL; + int addrsize=sizeof(struct sockaddr_in); + struct sockaddr_in saddr_l; + struct sockaddr_in saddr_r; + + /* create a security structure and give it to sasl */ + secprops = make_secprops(minssf, maxssf); + if (secprops != NULL) + { + sasl_setprop(conn, SASL_SEC_PROPS, secprops); + free(secprops); + } + + if (getpeername(sock,(struct sockaddr *)&saddr_r,&addrsize)!=0) + return RET_FAIL; + + if (sasl_setprop(conn, SASL_IP_REMOTE, &saddr_r)!=SASL_OK) + return RET_FAIL; + + addrsize=sizeof(struct sockaddr_in); + if (getsockname(sock,(struct sockaddr *) &saddr_l,&addrsize)!=0) + return RET_FAIL; + + if (sasl_setprop(conn, SASL_IP_LOCAL, &saddr_l)!=SASL_OK) + return RET_FAIL; + + return RET_OK; + } + #endif /* HAVE_SASL */ + + /************************** END SASL helper functions ******************************/ + + /************************* Startup functions **********************************/ + + static conn_ret Initialize(connection_t *cxn, int respTimeout) + { + conn_ret saslresult; + + + #ifdef HAVE_SASL + /* Initialize SASL */ + saslresult=sasl_client_init(saslcallbacks); + + if (saslresult!=SASL_OK) + { + d_printf(0,"Error initializing SASL (%s)", + sasl_errstring(saslresult, NULL, NULL)); + return RET_FAIL; + } + #endif /* HAVE_SASL */ + + d_printf(1,"initializing....\n"); + + + + cxn->lmtp_rBuffer = newBuffer(4096); + if (cxn->lmtp_rBuffer == NULL) + { + d_printf(0,"Failure allocating buffer\n"); + return RET_FAIL; + } + bufferAddNullByte(cxn->lmtp_rBuffer); + + + cxn->imap_rBuffer = newBuffer(4096); + if (cxn->imap_rBuffer == NULL) + { + d_printf(0,"Failure allocating buffer\n"); + return RET_FAIL; + } + bufferAddNullByte(cxn->imap_rBuffer); + + d_printf(1,"Timeout is %d\n",respTimeout); + /* Initialize timeouts */ + cxn->lmtp_writeTimeout = respTimeout; + cxn->lmtp_readTimeout = respTimeout; + cxn->imap_writeTimeout = respTimeout; + cxn->imap_readTimeout = respTimeout; + cxn->lmtp_sleepTimerId = 0 ; + cxn->lmtp_sleepTimeout = init_reconnect_period ; + cxn->imap_sleepTimerId = 0 ; + cxn->imap_sleepTimeout = init_reconnect_period ; + + cxn->dosomethingTimeout = DOSOMETHING_TIMEOUT; + + /* set up the write timer. */ + clearTimer (cxn->dosomethingTimerId) ; + + if (cxn->dosomethingTimeout > 0) + cxn->dosomethingTimerId = prepareSleep (dosomethingTimeoutCbk, + cxn->dosomethingTimeout, cxn); + + + + return RET_OK; + } + + + /* initialize the network */ + static conn_ret init_net(char *serverFQDN, + int port, + int *sock) + { + struct sockaddr_in addr; + struct hostent *hp; + + if ((hp = gethostbyname(serverFQDN)) == NULL) { + perror("gethostbyname"); + return RET_FAIL; + } + + if (( (*sock) = socket(AF_INET, SOCK_STREAM, 0)) < 0) { + perror("socket"); + return RET_FAIL; + } + + addr.sin_family = AF_INET; + memcpy(&addr.sin_addr, hp->h_addr, hp->h_length); + addr.sin_port = htons(port); + + if (connect( (*sock), (struct sockaddr *) &addr, sizeof (addr)) < 0) { + perror("connect"); + return RET_FAIL; + } + + return RET_OK; + } + + + + static conn_ret SetupLMTPConnection(connection_t *cxn, + char *serverName, + int port) + { + int saslresult; + conn_ret result; + + cxn->lmtp_port = port; + + if (serverName==NULL) + { + d_printf(0,"Servername is null"); + return RET_FAIL; + } + + d_printf(1,"lmtp Servername is [%s]",serverName); + + #ifdef HAVE_SASL + /* Free the SASL connection if we already had one */ + if (cxn->saslconn_lmtp!=NULL) + { + sasl_dispose(&cxn->saslconn_lmtp); + } + + /* Start SASL */ + saslresult=sasl_client_new("lmtp", + serverName, + NULL, + 0, + &cxn->saslconn_lmtp); + + if (saslresult != SASL_OK) + { + d_printf(0,"Error creating a new SASL connection (%s)", + sasl_errstring(saslresult,NULL,NULL)); + return RET_FAIL; + } + #endif /* HAVE_SASL */ + + /* Connect the Socket */ + result = init_net(serverName, + LMTP_PORT, /*port,*/ + &(cxn->sockfd_lmtp)); + + if (result != RET_OK) + { + d_printf(0,"Unable to start network connection to lmtp host"); + return RET_FAIL; + } + + if (cxn->lmtp_respBuffer) free(cxn->lmtp_respBuffer); + cxn->lmtp_respBuffer = (char *) malloc (4096); + cxn->lmtp_respBuffer[0]='\0'; + + /* Free if we had an existing one */ + if (cxn->lmtp_endpoint != NULL) + { + delEndPoint(cxn->lmtp_endpoint); + cxn->lmtp_endpoint = NULL; + } + + cxn->lmtp_endpoint = newEndPoint(cxn->sockfd_lmtp); + if (cxn->lmtp_endpoint == NULL) + { + d_printf(0,"Failure creating endpoint\n"); + return RET_FAIL; + } + + #ifdef HAVE_SASL + /* Set the SASL properties */ + result = SetSASLProperties(cxn->saslconn_lmtp, cxn->sockfd_lmtp, + 0, 0); + + if (result != RET_OK) + { + d_printf(0,"Error setting sasl properties"); + + return RET_FAIL; + } + #endif /* HAVE_SASL */ + + + return RET_OK; + } + + static conn_ret SetupIMAPConnection(connection_t *cxn, + char *serverName, + int port) + { + int saslresult; + conn_ret result; + + cxn->imap_port = port; + + if (serverName==NULL) + { + d_printf(0,"Servername is null"); + return RET_FAIL; + } + + d_printf(1,"imap server name is %s\n",serverName); + + #ifdef HAVE_SASL + /* Free the SASL connection if we already had one */ + if (cxn->imap_saslconn!=NULL) + { + d_printf(1,"Disposing of IMAP connection\n"); + sasl_dispose(&cxn->imap_saslconn); + } + + /* Start SASL */ + saslresult=sasl_client_new("imap", + serverName, + NULL, + 0, + &cxn->imap_saslconn); + + if (saslresult != SASL_OK) + { + d_printf(0,"Error creating a new SASL connection (%s)", + sasl_errstring(saslresult,NULL,NULL)); + return RET_FAIL; + } + #endif /* HAVE_SASL */ + + /* Connect the Socket */ + result = init_net(serverName, + port, + &(cxn->imap_sockfd)); + + if (result != RET_OK) + { + d_printf(0,"Unable to start network connection for IMAP"); + return RET_FAIL; + } + + if (cxn->imap_respBuffer) free(cxn->imap_respBuffer); + cxn->imap_respBuffer = (char *) malloc (4096); + cxn->imap_respBuffer[0]='\0'; + + /* Free if we had an existing one */ + if (cxn->imap_endpoint != NULL) + { + delEndPoint(cxn->imap_endpoint); + cxn->imap_endpoint = NULL; + } + + cxn->imap_endpoint = newEndPoint(cxn->imap_sockfd); + if (cxn->imap_endpoint == NULL) + { + d_printf(0,"Failure creating imap endpoint\n"); + return RET_FAIL; + } + + #ifdef HAVE_SASL + /* Set the SASL properties */ + result = SetSASLProperties(cxn->imap_saslconn, cxn->imap_sockfd, + 0, 0); + if (result != RET_OK) + { + d_printf(0,"Error setting sasl properties"); + return result; + } + #endif /* HAVE_SASL */ + + + return RET_OK; + } + + /************************* END Startup functions **********************************/ + + /* Return the response code for this line + -1 if it doesn't seem to have one + */ + static int ask_code(char *str) + { + int ret = 0; + + if (str==NULL) return -1; + + if (strlen(str) < 3) return -1; + + /* check to make sure 0-2 are digits */ + if ((isdigit((int) str[0])==0) || + (isdigit((int) str[1])==0) || + (isdigit((int) str[2])==0)) + { + d_printf(0,"Response does not begin with a code [%s]\n",str); + return -1; + } + + + ret = ((str[0]-'0')*100)+ + ((str[1]-'0')*10)+ + (str[2]-'0'); + + return ret; + } + + /* is this a continuation or not? + 220-fdfsd is (1) + 220 fdsfs is not (0) + */ + + static int ask_keepgoing(char *str) + { + if (str==NULL) return 0; + if (strlen(str) < 4) return 0; + + if (str[3]=='-') return 1; + + return 0; + } + + + static conn_ret lmtp_listenintro(connection_t *cxn) + { + char *str; + Buffer *readBuffers; + + /* set up to receive */ + readBuffers = makeBufferArray (bufferTakeRef (cxn->lmtp_rBuffer), NULL) ; + prepareRead(cxn->lmtp_endpoint, readBuffers, lmtp_readCB, cxn, 5); + + cxn->lmtp_state = LMTP_READING_INTRO; + + return RET_OK; + } + + + + /************************** IMAP functions ***********************/ + + static conn_ret imap_Connect(connection_t *cxn) + { + conn_ret result; + + /* make the IMAP connection */ + result = SetupIMAPConnection(cxn, + cxn->ServerName, + IMAP_PORT); + + /* Listen to the intro and start the authenticating process */ + result = imap_listenintro(cxn); + + return result; + } + + /* + * This is called when the data write timeout for the remote + * goes off. We tear down the connection and notify our host. + */ + static void imap_writeTimeoutCbk (TimeoutId id, void *data) + { + connection_t *cxn = (Connection) data ; + const char *peerName ; + + peerName = hostPeerName (cxn->myHost) ; + + syslog (LOG_WARNING, "timeout for %s", peerName); + d_printf (0,"%s: shutting down non-responsive connection (state=%d)\n", + hostPeerName (cxn->myHost), cxn->imap_state) ; + + cxnLogStats (cxn,true) ; + + imap_Disconnect(cxn); + } + + /* + * This is called when the timeout for the reponse from the remote + * goes off. We tear down the connection and notify our host. + */ + static void imap_readTimeoutCbk (TimeoutId id, void *data) + { + Connection cxn = (Connection) data ; + const char *peerName ; + + ASSERT (id == cxn->imap_readBlockedTimerId) ; + + peerName = hostPeerName (cxn->myHost) ; + + syslog (LOG_WARNING, RESPONSE_TIMEOUT, peerName, cxn->ident) ; + d_printf (0,"%s:%d shutting down non-repsonsive imap connection\n", + hostPeerName (cxn->myHost), cxn->ident) ; + + cxnLogStats (cxn,true) ; + + if (cxn->imap_state == IMAP_DISCONNECTED) + { + imap_Disconnect(cxn); + lmtp_Disconnect(cxn); + delConnection (cxn) ; + } + else { + imap_Disconnect(cxn); + } + } + + /* + * Called by the EndPoint class when the timer goes off + */ + void imap_reopenTimeoutCbk (TimeoutId id, void *data) + { + Connection cxn = (Connection) data ; + + ASSERT (id == cxn->imap_sleepTimerId) ; + + cxn->imap_sleepTimerId = 0 ; + + d_printf(1,"[imap] Reopen timeout\n"); + + if (cxn->imap_state != IMAP_DISCONNECTED) + { + syslog (LOG_ERR,CXN_BAD_STATE,hostPeerName (cxn->myHost), + cxn->ident,imap_stateToString (cxn->imap_state)) ; + } + else { + if (imap_Connect(cxn) != RET_OK) + prepareReopenCbk(cxn, 0); + } + } + + static void imap_Disconnect(connection_t *cxn) + { + clearTimer (cxn->imap_sleepTimerId) ; + clearTimer (cxn->imap_readBlockedTimerId) ; + clearTimer (cxn->imap_writeBlockedTimerId) ; + + DeferAllArticles(cxn, &(cxn->imap_controlMsg_q)) ; /* give any articles back to Host */ + + cxn->imap_state = IMAP_DISCONNECTED; + + cxn->imap_disconnects++; + + cxn->imap_respBuffer[0]='\0'; + + if (cxn->issue_quit == 0) + prepareReopenCbk(cxn,0); + } + + /************************** END IMAP functions ***********************/ + + /************************ LMTP functions **************************/ + + /* + * Create a network lmtp connection + * and start listening for the intro string + * + */ + + static conn_ret lmtp_Connect(connection_t *cxn) + { + conn_ret result; + + /* make the LMTP connection */ + result = SetupLMTPConnection(cxn, + cxn->ServerName, + LMTP_PORT); + + if (result!=RET_OK) return result; + + /* Listen to the intro */ + result = lmtp_listenintro(cxn); + + return result; + } + + + + static void lmtp_Disconnect(connection_t *cxn) + { + clearTimer (cxn->lmtp_sleepTimerId) ; + clearTimer (cxn->lmtp_readBlockedTimerId) ; + clearTimer (cxn->lmtp_writeBlockedTimerId) ; + + DeferAllArticles(cxn, &(cxn->lmtp_todeliver_q)) ; /* give any articles back to Host */ + + cxn->lmtp_have_mailfrom = 0; + + cxn->lmtp_state = LMTP_DISCONNECTED; + + cxn->lmtp_disconnects++; + + cxn->lmtp_respBuffer[0]='\0'; + + if (cxn->issue_quit == 0) + prepareReopenCbk(cxn,1); + } + + + + /* + * Called by the EndPoint class when the timer goes off + */ + void lmtp_reopenTimeoutCbk (TimeoutId id, void *data) + { + Connection cxn = (Connection) data ; + + ASSERT (id == cxn->lmtp_sleepTimerId) ; + + cxn->lmtp_sleepTimerId = 0 ; + + d_printf(1,"[lmtp] Reopen timeout\n"); + + if (cxn->lmtp_state != LMTP_DISCONNECTED) + { + syslog (LOG_ERR,CXN_BAD_STATE,hostPeerName (cxn->myHost), + cxn->ident,lmtp_stateToString (cxn->lmtp_state)) ; + } + else { + if (lmtp_Connect(cxn) != RET_OK) + prepareReopenCbk(cxn, 1); + } + } + + /* + * Set up the callback used when the Connection is sleeping (i.e. will try + * to reopen the connection). + * + * type (0 = imap, 1 = lmtp) + */ + static void prepareReopenCbk (Connection cxn, int type) + { + /* xxx check state */ + + d_printf (1,"%s:%d Setting up a reopen callback\n", + hostPeerName (cxn->myHost), cxn->ident) ; + + if (type == 0) + cxn->imap_sleepTimerId = prepareSleep (imap_reopenTimeoutCbk, cxn->imap_sleepTimeout, cxn) ; + else + cxn->lmtp_sleepTimerId = prepareSleep (lmtp_reopenTimeoutCbk, cxn->lmtp_sleepTimeout, cxn) ; + + /* bump the sleep timer amount each time to wait longer and longer. Gets + reset in resetConnection() */ + if (type == 0) { + cxn->imap_sleepTimeout *= 2 ; + if (cxn->imap_sleepTimeout > max_reconnect_period) + cxn->imap_sleepTimeout = max_reconnect_period ; + } else { + cxn->lmtp_sleepTimeout *= 2 ; + if (cxn->lmtp_sleepTimeout > max_reconnect_period) + cxn->lmtp_sleepTimeout = max_reconnect_period ; + } + } + + /* + * This is called when the timeout for the reponse from the remote + * goes off. We tear down the connection and notify our host. + */ + static void lmtp_readTimeoutCbk (TimeoutId id, void *data) + { + Connection cxn = (Connection) data ; + const char *peerName ; + + ASSERT (id == cxn->lmtp_readBlockedTimerId) ; + + peerName = hostPeerName (cxn->myHost) ; + + syslog (LOG_WARNING, RESPONSE_TIMEOUT, peerName, cxn->ident) ; + d_printf (0,"%s:%d shutting down non-repsonsive lmtp connection\n", + hostPeerName (cxn->myHost), cxn->ident) ; + + cxnLogStats (cxn,true) ; + + if (cxn->lmtp_state == LMTP_DISCONNECTED) + { + imap_Disconnect(cxn); + lmtp_Disconnect(cxn); + delConnection (cxn) ; + } + else { + lmtp_Disconnect(cxn); + } + } + + + + /* + * This is called when the data write timeout for the remote + * goes off. We tear down the connection and notify our host. + */ + static void lmtp_writeTimeoutCbk (TimeoutId id, void *data) + { + connection_t *cxn = (Connection) data ; + const char *peerName ; + + peerName = hostPeerName (cxn->myHost) ; + + syslog (LOG_WARNING, "timeout for %s", peerName); + d_printf (0,"%s: shutting down non-responsive connection (state = %d)\n", + hostPeerName (cxn->myHost), cxn->lmtp_state) ; + + cxnLogStats (cxn,true) ; + + lmtp_Disconnect(cxn); + } + + /************************ END LMTP functions **************************/ + + /************************** LMTP write functions ********************/ + + static conn_ret lmtp_IssueQuit(connection_t *cxn) + { + int result; + char *p; + + /* say hello */ + p = (char *) malloc(20); + + sprintf (p, "QUIT\r\n", hostname); /* our domain name */ + + result = WriteToWire_lmtpstr(cxn, p, strlen(p)); + if (result!=RET_OK) return result; + + cxn->lmtp_state = LMTP_WRITING_QUIT; + + return RET_OK; + } + + static conn_ret lmtp_getcapabilities(connection_t *cxn) + { + int result; + char *p; + + if (cxn->lmtp_capabilities != NULL) + { + free( cxn->lmtp_capabilities->saslmechs); + free( cxn->lmtp_capabilities ); + cxn->lmtp_capabilities = NULL; + } + + cxn->lmtp_capabilities = CALLOC (lmtp_capabilities_t, 1); + ASSERT (cxn->lmtp_capabilities != NULL) ; + + /* say hello */ + p = (char *) malloc(20+strlen(hostname)); + + #ifdef SMTPMODE + sprintf (p, "EHLO %s\r\n", hostname); /* our domain name */ + #else + sprintf (p, "LHLO %s\r\n", hostname); /* our domain name */ + #endif /* SMTPMODE */ + + result = WriteToWire_lmtpstr(cxn, p, strlen(p)); + if (result!=RET_OK) return result; + + cxn->lmtp_state = LMTP_WRITING_LHLO; + + return RET_OK; + } + + #ifdef HAVE_SASL + static conn_ret lmtp_authenticate(connection_t *cxn) + { + int saslresult; + + const char *mechusing; + char *out; + unsigned int outlen; + char *in; + unsigned int inlen; + char *inbase64; + int inbase64len; + int status; + int result; + + char *p; + + sasl_interact_t *client_interact=NULL; + + + cxn->lmtp_have_mailfrom = 0; + + saslresult=sasl_client_start(cxn->saslconn_lmtp, + cxn->lmtp_capabilities->saslmechs, + NULL, &client_interact, + &out, &outlen, + &mechusing); + + + + if ((saslresult != SASL_OK) && + (saslresult != SASL_CONTINUE)) { + + d_printf(0,"Error calling sasl_client_start (%s)\n",sasl_errstring(saslresult, NULL, NULL)); + return RET_FAIL; + } + + d_printf(1,"Decided to use mech=%s\n",mechusing); + + p = (char *) malloc(strlen(mechusing)+(outlen*2+10)+30); + + if (out!=NULL) + { + + /* convert to base64 */ + inbase64 = (char *) malloc(outlen*2+10); + + saslresult = sasl_encode64(out, outlen, + inbase64, outlen*2+10, (unsigned *) &inbase64len); + if (saslresult != SASL_OK) return RET_FAIL; + + sprintf (p, "AUTH %s %s\r\n",mechusing,inbase64); + } else { + sprintf (p, "AUTH %s\r\n",mechusing); + } + + result = WriteToWire_lmtpstr(cxn, p, strlen(p)); + + cxn->lmtp_state = LMTP_WRITING_STARTAUTH; + + return RET_OK; + } + + static imt_stat lmtp_getauthline(char *str, char **line, int *linelen) + { + char buf[4096]; + int saslresult; + int response_code = -1; + + response_code = ask_code(str); + + if (response_code == 334) { + + /* continue */ + + } else if (response_code == 235) { + + /* woohoo! authentication complete */ + return STAT_OK; + + } else { + /* failure of some sort */ + d_printf(0,"LMTP Authentication failure (%d)\n",response_code); + return STAT_NO; + } + + str += 4; /* jump past the "334 " */ + + *line = (char *) malloc(strlen(str)+30); + if ((*line)==NULL) { + return STAT_NO; + } + + /* decode this line */ + saslresult = sasl_decode64(str, strlen(str), + *line, (unsigned *) linelen); + if (saslresult != SASL_OK) { + d_printf(0,"LMTP base64 decoding error\n"); + return STAT_NO; + } + + return STAT_CONT; + } + #endif /* HAVE_SASL */ + + static void lmtp_writeCB (EndPoint e, IoStatus i, Buffer *b, void *d) + { + connection_t *cxn = (connection_t *) d; + Buffer *readBuffers; + + clearTimer (cxn->lmtp_writeBlockedTimerId) ; + + /* Free the string that was written */ + freeBufferArray (b); + if (cxn->lmtp_tofree_str!=NULL) + { + free(cxn->lmtp_tofree_str); + cxn->lmtp_tofree_str=NULL; + } + + /* set up to receive */ + readBuffers = makeBufferArray (bufferTakeRef (cxn->lmtp_rBuffer), NULL) ; + prepareRead(cxn->lmtp_endpoint, readBuffers, lmtp_readCB, cxn, 5); + + /* set up the response timer. */ + clearTimer (cxn->lmtp_readBlockedTimerId) ; + + if (cxn->lmtp_readTimeout > 0) + cxn->lmtp_readBlockedTimerId = prepareSleep (lmtp_readTimeoutCbk, + cxn->lmtp_readTimeout, cxn) ; + + + switch (cxn->lmtp_state) + { + + case LMTP_WRITING_LHLO: + + cxn->lmtp_state = LMTP_READING_LHLO; + + break; + + case LMTP_WRITING_STARTAUTH: + case LMTP_WRITING_STEPAUTH: + + cxn->lmtp_state = LMTP_READING_STEPAUTH; + + break; + + case LMTP_WRITING_UPTODATA: + + /* expect result to mail from */ + if (cxn->lmtp_have_mailfrom==1) + { + cxn->lmtp_state = LMTP_READING_RCPTTO; + } else { + cxn->lmtp_state = LMTP_READING_MAILFROM; + } + + break; + + case LMTP_WRITING_CONTENTS: + /* so we sent the whole DATA command + let's see what the server responded */ + + cxn->lmtp_state = LMTP_READING_CONTENTS; + + break; + + case LMTP_WRITING_QUIT: + cxn->lmtp_state = LMTP_READING_QUIT; + break; + + default: + + d_printf(0,"LMTP: Unknown state. Internal error\n"); + + break; + } + } + + /************************** END LMTP write functions ********************/ + + /************************** IMAP sending functions ************************/ + + + static void imap_writeCB (EndPoint e, IoStatus i, Buffer *b, void *d) + { + connection_t *cxn = (connection_t *) d; + Buffer *readBuffers; + + clearTimer (cxn->imap_writeBlockedTimerId) ; + + /* free the string we just wrote out */ + freeBufferArray (b); + if (cxn->imap_tofree_str!=NULL) + { + free(cxn->imap_tofree_str); + cxn->imap_tofree_str=NULL; + } + + /* set up to receive */ + readBuffers = makeBufferArray (bufferTakeRef (cxn->imap_rBuffer), NULL) ; + prepareRead(cxn->imap_endpoint, readBuffers, imap_readCB, cxn, 5); + + /* set up the response timer. */ + clearTimer (cxn->imap_readBlockedTimerId) ; + + if (cxn->imap_readTimeout > 0) + cxn->imap_readBlockedTimerId = prepareSleep (imap_readTimeoutCbk, + cxn->imap_readTimeout, cxn) ; + + switch (cxn->imap_state) + { + + case IMAP_WRITING_CAPABILITY: + + cxn->imap_state = IMAP_READING_CAPABILITY; + break; + + case IMAP_WRITING_STEPAUTH: + case IMAP_WRITING_STARTAUTH: + + cxn->imap_state = IMAP_READING_STEPAUTH; + + break; + + case IMAP_WRITING_CREATE: + + cxn->imap_state = IMAP_READING_CREATE; + + break; + + case IMAP_WRITING_DELETE: + + cxn->imap_state = IMAP_READING_DELETE; + + break; + + case IMAP_WRITING_SELECT: + + cxn->imap_state = IMAP_READING_SELECT; + + break; + + case IMAP_WRITING_SEARCH: + + cxn->imap_state = IMAP_READING_SEARCH; + + break; + + case IMAP_WRITING_STORE: + + cxn->imap_state = IMAP_READING_STORE; + + break; + + case IMAP_WRITING_CLOSE: + + cxn->imap_state = IMAP_READING_CLOSE; + + break; + + case IMAP_WRITING_QUIT: + + cxn->imap_state = IMAP_READING_QUIT; + + break; + + default: + d_printf(0,"invalid imap state\n"); + imap_Disconnect(cxn); + break; + + } + } + + /* + * Tag is already allocated + */ + + static void imap_GetTag(connection_t *cxn) + { + sprintf(cxn->imap_currentTag,"%06d",cxn->imap_tag_num); + cxn->imap_tag_num++; + if (cxn->imap_tag_num >= 999999) + { + cxn->imap_tag_num = 0; + } + } + + #ifdef HAVE_SASL + static conn_ret imap_sendAuthStep(connection_t *cxn, char *str) + { + conn_ret result; + int saslresult; + char in[4096]; + unsigned int inlen; + char *out; + unsigned int outlen; + char *inbase64; + unsigned int inbase64len; + + /* base64 decode it */ + + saslresult = sasl_decode64(str, strlen(str), + in, &inlen); + if (saslresult != SASL_OK) { + d_printf(0,"IMAP base64 decoding error\n"); + return RET_FAIL; + } + + saslresult=sasl_client_step(cxn->imap_saslconn, + in, + inlen, + NULL, + &out, + &outlen); + + /* check if sasl suceeded */ + if (saslresult != SASL_OK && saslresult != SASL_CONTINUE) { + + d_printf(0,"sasl_client_step failed with %s\n", + sasl_errstring(saslresult,NULL,NULL)); + cxn->imap_state = IMAP_CONNECTED_NOTAUTH; + return RET_FAIL; + } + + inbase64 = (char *) malloc(outlen*2+10); + + /* convert to base64 */ + saslresult = sasl_encode64(out, outlen, + inbase64, outlen*2, (unsigned *) &inbase64len); + + if (saslresult != SASL_OK) return RET_FAIL; + + /* append endline */ + strcpy(inbase64 + inbase64len, "\r\n"); + inbase64len+=2; + + if (out!=NULL) free(out); + + /* send to server */ + result = WriteToWire_imapstr(cxn,inbase64, inbase64len); + + cxn->imap_state = IMAP_WRITING_STEPAUTH; + + return result; + } + #endif /* HAVE_SASL */ + + static conn_ret imap_sendAuthenticate(connection_t *cxn) + { + int saslresult; + + const char *mechusing; + char *out; + unsigned int outlen; + char *in; + unsigned int inlen; + char *inbase64; + int inbase64len; + int status; + int result; + + char *p; + + #ifdef HAVE_SASL + sasl_interact_t *client_interact=NULL; + + d_printf(1,"[imap] Mechs = %s\n",cxn->imap_capabilities->saslmechs); + + saslresult=sasl_client_start(cxn->imap_saslconn, + cxn->imap_capabilities->saslmechs, + NULL, &client_interact, + &out, &outlen, + &mechusing); + + + + /* If no mechs try "login" */ + if (saslresult == SASL_NOMECH) + { + + #else /* HAVE_SASL */ + + { /* always do login */ + + #endif /* HAVE_SASL */ + d_printf(1,"No mechanism found. Trying login method\n"); + + if (cxn->imap_capabilities->logindisabled==1) + { + d_printf(0,"Login command w/o security layer not allowed on this server\n"); + return RET_FAIL; + } + + if (deliver_authname==NULL) + { + d_printf(0,"[imap] Unable to log in b/c authname not specified\n"); + return RET_FAIL; + } + + if (deliver_password==NULL) + { + d_printf(0,"[imap] Unable to log in b/c password not specified\n"); + return RET_FAIL; + } + + p = (char *) malloc(strlen(cxn->imap_currentTag)+strlen(deliver_authname)+ + strlen(deliver_password)+30); + + imap_GetTag(cxn); + + sprintf (p, "%s LOGIN %s \"%s\"\r\n",cxn->imap_currentTag, deliver_authname, deliver_password); + + result = WriteToWire_imapstr(cxn, p, strlen(p)); + + cxn->imap_state = IMAP_WRITING_STARTAUTH; + + return RET_OK; + } + + #ifdef HAVE_SASL + if ((saslresult != SASL_OK) && + (saslresult != SASL_CONTINUE)) { + + d_printf(0,"[imap] Error calling sasl_client_start (%s) mechusing = %s\n", + sasl_errstring(saslresult, NULL, NULL), mechusing); + return RET_FAIL; + } + #endif /* HAVE_SASL */ + + d_printf(1,"[imap] Trying to authenticate to imap with %s mechanism\n",mechusing); + + p = (char *) malloc(strlen(cxn->imap_currentTag)+strlen(mechusing)+40); + + imap_GetTag(cxn); + + sprintf (p, "%s AUTHENTICATE %s\r\n",cxn->imap_currentTag, mechusing); + + result = WriteToWire_imapstr(cxn, p, strlen(p)); + + cxn->imap_state = IMAP_WRITING_STARTAUTH; + + return RET_OK; + } + + static conn_ret imap_CreateGroup(connection_t *cxn, char *bboard) + { + conn_ret result; + char *tosend; + int newlen=strlen(bboard); + + d_printf(1,"Ok creating group [%s]\n",bboard); + + imap_GetTag(cxn); + + tosend = (char *) malloc(30+newlen); + + sprintf(tosend,"%s CREATE %s\r\n",cxn->imap_currentTag,bboard); + + result = WriteToWire_imapstr(cxn, tosend, -1); + if (result!=RET_OK) return result; + + cxn->imap_state = IMAP_WRITING_CREATE; + + return RET_OK; + } + + static conn_ret imap_DeleteGroup(connection_t *cxn, char *bboard) + { + conn_ret result; + char *tosend; + int newlen=strlen(bboard); + + d_printf(1,"Ok removing [%s]\n",bboard); + + imap_GetTag(cxn); + + tosend = (char *) malloc(30+newlen); + + sprintf(tosend,"%s DELETE %s\r\n",cxn->imap_currentTag,bboard); + + result = WriteToWire_imapstr(cxn, tosend, -1); + if (result!=RET_OK) return result; + + cxn->imap_state = IMAP_WRITING_DELETE; + + return RET_OK; + } + + static conn_ret imap_CancelMsg(connection_t *cxn, char *newsgroup) + { + conn_ret result; + char *tosend; + + ASSERT(newsgroup); + + tosend = (char *) malloc(7+10+strlen(newsgroup)+100); + + imap_GetTag(cxn); + + /* select mbox */ + sprintf(tosend,"%s SELECT %s\r\n",cxn->imap_currentTag, newsgroup); + + result = WriteToWire_imapstr(cxn, tosend, -1); + if (result != RET_OK) return result; + + cxn->imap_state = IMAP_WRITING_SELECT; + + return RET_OK; + } + + static conn_ret imap_sendSearch(connection_t *cxn, char *msgid) + { + conn_ret result; + char *tosend; + + ASSERT(msgid); + + tosend = (char *) malloc(7+40+strlen(msgid)); + + imap_GetTag(cxn); + + /* preform search */ + sprintf(tosend,"%s UID SEARCH header \"Message-ID\" \"%s\"\r\n",cxn->imap_currentTag, msgid); + + result = WriteToWire_imapstr(cxn, tosend, -1); + if (result != RET_OK) return result; + + cxn->imap_state = IMAP_WRITING_SEARCH; + + return RET_OK; + } + + static conn_ret imap_sendKill(connection_t *cxn, unsigned uid) + { + conn_ret result; + char *tosend; + + tosend = (char *) malloc(7+50+20); + + imap_GetTag(cxn); + + sprintf(tosend,"%s UID STORE %d +FLAGS.SILENT (\\Deleted)\r\n",cxn->imap_currentTag, uid); + + result = WriteToWire_imapstr(cxn, tosend, -1); + if (result != RET_OK) return result; + + cxn->imap_state = IMAP_WRITING_STORE; + + return RET_OK; + } + + static conn_ret imap_sendClose(connection_t *cxn) + { + char *tosend; + conn_ret result; + + tosend = (char *) malloc(7+10); + + imap_GetTag(cxn); + + sprintf(tosend,"%s CLOSE\r\n",cxn->imap_currentTag); + + result = WriteToWire_imapstr(cxn, tosend, -1); + if (result != RET_OK) return result; + + cxn->imap_state = IMAP_WRITING_CLOSE; + + return RET_OK; + } + + static conn_ret imap_sendQuit(connection_t *cxn) + { + char *tosend; + conn_ret result; + + tosend = (char *) malloc(7+12); + + imap_GetTag(cxn); + + sprintf(tosend,"%s LOGOUT\r\n",cxn->imap_currentTag); + + result = WriteToWire_imapstr(cxn, tosend, -1); + if (result != RET_OK) return result; + + cxn->imap_state = IMAP_WRITING_QUIT; + + return RET_OK; + } + + + static conn_ret imap_sendCapability(connection_t *cxn) + { + conn_ret result; + char *tosend; + + imap_GetTag(cxn); + + tosend = (char *) malloc(5+13+5); + + sprintf(tosend,"%s CAPABILITY\r\n",cxn->imap_currentTag); + + result = WriteToWire_imapstr(cxn, tosend, -1); + if (result != RET_OK) return result; + + cxn->imap_state = IMAP_WRITING_CAPABILITY; + + return RET_OK; + } + + /************************** END IMAP sending functions ************************/ + + /************************** IMAP reading functions ***************************/ + + static conn_ret imap_listenintro(connection_t *cxn) + { + char *str; + Buffer *readBuffers; + + /* set up to receive */ + readBuffers = makeBufferArray (bufferTakeRef (cxn->imap_rBuffer), NULL) ; + prepareRead(cxn->imap_endpoint, readBuffers, imap_readCB, cxn, 5); + + cxn->imap_state = IMAP_READING_INTRO; + + return RET_OK; + } + + static conn_ret imap_ParseCapability(char *string, imap_capabilities_t **caps) + { + char *str = string; + char *start = str; + + /* allocate the caps structure if it doesn't already exist */ + if ( (*caps) == NULL) + { + (*caps) = (imap_capabilities_t *) malloc( sizeof(imap_capabilities_t)); + memset( (*caps), 0, sizeof(imap_capabilities_t)); + } + + while ( (*str) != '\0') + { + + while (((*str) != '\0') && ((*str)!=' ')) + { + str++; + } + + if ( (*str) != '\0') + { + *str = '\0'; + str++; + } + + if ( strcasecmp(start,"IMAP4")==0) + { + (*caps)->imap4 = 1; + } else if (strcasecmp(start,"LOGINDISABLED")==0) { + (*caps)->logindisabled = 1; + } else if ( strncmp(start, "AUTH=", 5)==0) { + + if ( (*caps)->saslmechs == NULL) + { + (*caps)->saslmechs = (char *) malloc(strlen(start+5)+1); + strcpy( (*caps)->saslmechs, start+5); + } else { + + (*caps)->saslmechs = (char *) realloc((*caps)->saslmechs, + strlen((*caps)->saslmechs)+1+strlen(start+5)+1); + + strcat( (*caps)->saslmechs, " "); + strcat( (*caps)->saslmechs, start+5); + } + } + + start = str; + + } + + d_printf(1,"[imap] parsed capabilities: saslmechs = %s\n",(*caps)->saslmechs); + + return RET_OK; + } + + + static void imap_readCB (EndPoint e, IoStatus i, Buffer *b, void *d) + { + connection_t *cxn = (connection_t *) d; + Buffer *modeCmdBuffers, *readBuffers ; + + int okno; + char *str; + char strbuf[4096]; + char *linestart; + conn_ret ret; + char *p; + int result; + + int oldsize; + char *old; + + p = bufferBase(b[0]); + + /* Add what we got to our internal read buffer */ + bufferAddNullByte (b[0]) ; + + if (i != IoDone) + { + errno = endPointErrno (e); + + d_printf(0,"IO not done: errno = %s\n",strerror(errno)); + freeBufferArray (b); + imap_Disconnect(cxn); + return; + } + + if (strchr (p, '\n') == NULL) + { + /* partial read. expand buffer and retry */ + + d_printf(0,"Partial. retry [%s]\n",p); + if (expandBuffer (b[0], BUFFER_EXPAND_AMOUNT)==false) + { + d_printf(0,"expanding buffer returned false\n"); + imap_Disconnect(cxn); + return; + } + readBuffers = makeBufferArray (bufferTakeRef (b[0]), NULL) ; + + if ( !prepareRead (e, readBuffers, imap_readCB, cxn, 1) ) + { + imap_Disconnect(cxn); + } + + freeBufferArray (b); + return; + } + + clearTimer (cxn->imap_readBlockedTimerId) ; + + /* we got something. add to our buffer and free b */ + + strcat(cxn->imap_respBuffer, p); + + bufferSetDataSize( b[0], 0); + + freeBufferArray (b); + + + + /* goto here to take another step */ + reset: + + /* see if we have a full line */ + ret = GetLine( cxn->imap_respBuffer , strbuf, sizeof(strbuf)); + str = strbuf; + linestart = str; + + /* if we don't have a full line */ + if ( ret == RET_NO_FULLLINE) + { + + readBuffers = makeBufferArray (bufferTakeRef (cxn->imap_rBuffer), NULL) ; + + if ( !prepareRead (e, readBuffers, imap_readCB, cxn, 1) ) + { + imap_Disconnect(cxn); + } + return; + + } else if (ret!=RET_OK) + { + return; + } + + /* if untagged */ + if ((str[0]=='*') && (str[1]==' ')) + { + str+=2; + + /* now figure out what kind of untagged it is */ + if (strncasecmp(str,"CAPABILITY ",11)==0) + { + str+=11; + + imap_ParseCapability(str,&(cxn->imap_capabilities)); + + } else if (strncasecmp(str,"SEARCH",6)==0) { + + str+=6; + + if ( (*str) == ' ') + { + str++; + + cxn->current_control->data.control->uid = atoi(str); + + d_printf(1,"i think the UID = %d\n",cxn->current_control->data.control->uid); + } else { + /* it's probably a blank uid (i.e. message doesn't exist) */ + cxn->current_control->data.control->uid = -1; + } + + + } else if (strncasecmp(str,"OK ",3)==0) { + + if (cxn->imap_state==IMAP_READING_INTRO) + { + imap_sendCapability(cxn); /* xxx errors */ + return; + + } else { + + } + + + } else { + /* untagged command not understood */ + } + + /* always might be more to look at */ + goto reset; + + } else if ((str[0]=='+') && (str[1]==' ')) { + + str+=2; + + if (cxn->imap_state == IMAP_READING_STEPAUTH) + { + #ifdef HAVE_SASL + if (imap_sendAuthStep(cxn, str)!=RET_OK) + { + imap_Disconnect(cxn); + } + #else + d_printf(0,"Invalid state\n"); + imap_Disconnect(cxn); + #endif /* HAVE_SASL */ + + return; + } else { + d_printf(0,"+ response unexpected\n"); + imap_Disconnect(cxn); + return; + } + + + } else if (strncmp(str, cxn->imap_currentTag, IMAP_TAGLENGTH)==0) { /* see if it matches our tag */ + str +=IMAP_TAGLENGTH; + + if (str[0]!=' ') + { + d_printf(0,"Tag with no space afterward\n"); + imap_Disconnect(cxn); + return; + } + str++; + + /* should be OK/NO */ + if (strncmp(str,"OK",2)==0) + { + okno = 1; + } else { + okno = 0; + } + + switch(cxn->imap_state) + { + case IMAP_READING_CAPABILITY: + + if (okno==1) { + if (imap_sendAuthenticate(cxn)!=RET_OK) + { + d_printf(0,"IMAP sendauthenticate failed\n"); + imap_Disconnect(cxn); + } + return; + } else { + d_printf(0,"CAPABILITY gave a NO response\n"); + imap_Disconnect(cxn); + } + return; + + break; + case IMAP_READING_STEPAUTH: + + if (okno == 1) { + + cxn->imap_sleepTimeout = init_reconnect_period ; + + cxn->imap_timeCon = theTime () ; + cxn->timeCon = theTime () ; + + d_printf(0,"%s:%d IMAP authentication succeeded!\n", + hostPeerName (cxn->myHost), cxn->ident); + + cxn->imap_disconnects=0; + + cxn->imap_state = IMAP_IDLE_AUTHED; + + /* try to send a message if we have one */ + + imap_ProcessQueue(cxn); + } else { + d_printf(0,"IMAP Authentication failed with [%s]\n",str); + imap_Disconnect(cxn); + } + + return; + + break; + + case IMAP_READING_CREATE: + + if (okno==1) { + + d_printf(1,"Create successful\n"); + cxn->create_suceeded++; + + /* we can delete article now */ + QueueForgetAbout(cxn, cxn->current_control,0); + + } else { + d_printf(1,"Create failed with [%s] for %s\n",str, + cxn->current_control->data.control->folder); + + ReQueue(cxn, &(cxn->imap_controlMsg_q), cxn->current_control); + } + + imap_ProcessQueue(cxn); + + break; + + case IMAP_READING_DELETE: + + if (okno==1) { + + d_printf(1,"Delete successful\n"); + cxn->remove_suceeded++; + + /* we can delete article now */ + QueueForgetAbout(cxn, cxn->current_control,0); + + } else { + d_printf(1,"Delete mailbox failed with [%s] for %s\n",str, + cxn->current_control->data.control->folder); + + ReQueue(cxn, &(cxn->imap_controlMsg_q), cxn->current_control); + + } + + imap_ProcessQueue(cxn); + return; + + break; + + case IMAP_READING_SELECT: + + if (okno==1) { + + imap_sendSearch(cxn, cxn->current_control->data.control->msgid); + return; + + } else { + d_printf(1,"Select failed with [%s] for %s\n",str, + cxn->current_control->data.control->folder); + + ReQueue(cxn, &(cxn->imap_controlMsg_q), cxn->current_control); + + cxn->imap_state = IMAP_IDLE_AUTHED; + + imap_ProcessQueue(cxn); + return; + } + + break; + + case IMAP_READING_SEARCH: + + /* if no message let's forget about it */ + if (cxn->current_control->data.control->uid == -1) + { + d_printf(1,"Search didn't find the message\n"); + ReQueue(cxn, &(cxn->imap_controlMsg_q), cxn->current_control); + if (imap_sendClose(cxn) != RET_OK) + imap_Disconnect(cxn); + return; + } + + if (okno==1) { + + /* we got a uid. let's delete it */ + if (imap_sendKill(cxn, cxn->current_control->data.control->uid) != RET_OK) + imap_Disconnect(cxn); + return; + + } else { + d_printf(1,"Received NO response to SEARCH command\n"); + ReQueue(cxn, &(cxn->imap_controlMsg_q), cxn->current_control); + + if (imap_sendClose(cxn) != RET_OK) + imap_Disconnect(cxn); + return; + } + + break; + + case IMAP_READING_STORE: + + if (okno==1) { + + d_printf(1,"Processed a Cancel fully\n"); + + /* we can delete article now */ + QueueForgetAbout(cxn, cxn->current_control,0); + + cxn->cancel_suceeded++; + + if (imap_sendClose(cxn) != RET_OK) + imap_Disconnect(cxn); + return; + + } else { + + d_printf(1,"Store failed\n"); + ReQueue(cxn, &(cxn->imap_controlMsg_q), cxn->current_control); + + if (imap_sendClose(cxn) != RET_OK) + imap_Disconnect(cxn); + return; + } + + break; + + case IMAP_READING_CLOSE: + + if (okno==1) { + + } else { + /* we can't do anything about it */ + d_printf(1,"Close failed\n"); + } + + cxn->imap_state = IMAP_IDLE_AUTHED; + + imap_ProcessQueue(cxn); + return; + + + break; + + case IMAP_READING_QUIT: + + /* we don't care if the server said OK or NO just + that it said something */ + + d_printf(1,"Read quit\n"); + + cxn->imap_state = IMAP_DISCONNECTED; + + switch (cxn->issue_quit) + { + case 1: + if (cxn->lmtp_state == LMTP_DISCONNECTED) + { + cxn->lmtp_state = LMTP_WAITING; + cxn->imap_state = IMAP_WAITING; + cxn->issue_quit = 0; + hostCxnWaiting (cxn->myHost,cxn) ; /* tell our Host we're waiting */ + } + break; + case 2: + if (cxn->lmtp_state == LMTP_DISCONNECTED) + { + cxn->issue_quit = 0; + + if (imap_Connect(cxn)!=RET_OK) prepareReopenCbk(cxn,0); + if (lmtp_Connect(cxn)!=RET_OK) prepareReopenCbk(cxn,1); + } + break; + case 3: + if (cxn->lmtp_state == LMTP_DISCONNECTED) + { + delConnection(cxn); + } + break; + + } + + break; + + + default: + d_printf(0,"I don't understand state %d [%s]\n",cxn->imap_state,str); + imap_Disconnect(cxn); + break; + } + + + } else { + d_printf(0,"tag doesn't match\n"); + imap_Disconnect(cxn); + } + + } + + /************************** END IMAP reading functions ***************************/ + + /*************************** LMTP reading functions ****************************/ + + static void lmtp_readCB (EndPoint e, IoStatus i, Buffer *b, void *d) + { + connection_t *cxn = (connection_t *) d; + char str[4096]; + Buffer *readBuffers; + int result; + int response_code; + int inlen; + char *in; + int outlen; + char *out; + char *inbase64; + int inbase64len; + int saslresult; + imt_stat status; + conn_ret ret; + #ifdef HAVE_SASL + sasl_interact_t *client_interact=NULL; + #endif /* HAVE_SASL */ + + char *p = bufferBase(b[0]); + + bufferAddNullByte (b[0]) ; + + if (i != IoDone) + { + d_printf(0,"IO not done\n"); + + freeBufferArray (b); + lmtp_Disconnect(cxn); + return; + } + + if (strchr (p, '\n') == NULL) + { + /* partial read. expand buffer and retry */ + + d_printf(0,"Partial. retry\n"); + expandBuffer (b[0], BUFFER_EXPAND_AMOUNT) ; + readBuffers = makeBufferArray (bufferTakeRef (b[0]), NULL) ; + + if ( !prepareRead (e, readBuffers, lmtp_readCB, cxn, 1) ) + { + lmtp_Disconnect(cxn); + } + + freeBufferArray (b); + return; + } + + clearTimer (cxn->lmtp_readBlockedTimerId) ; + + /* Add what we got to our internal read buffer */ + strcat(cxn->lmtp_respBuffer, p); + + bufferSetDataSize( b[0], 0); + + freeBufferArray (b); + + reset: + + /* see if we have a full line */ + ret = GetLine( cxn->lmtp_respBuffer, str, sizeof(str)); + + /* get a line */ + if (ret!=RET_OK) + { + if (ret!=RET_NO_FULLLINE) + { + /* was a more serious error */ + d_printf(0,"Internal error getting line from server\n"); + lmtp_Disconnect(cxn); + return; + } + + /* set up to receive some more */ + readBuffers = makeBufferArray (bufferTakeRef (cxn->lmtp_rBuffer), NULL) ; + prepareRead(cxn->lmtp_endpoint, readBuffers, lmtp_readCB, cxn, 5); + return; + } + + switch (cxn->lmtp_state) + { + + case LMTP_READING_INTRO: + + if (ask_code(str)!=220) + { + d_printf(0,"Initial server msg does not start with 220 (began with %d)\n", + ask_code(str)); + lmtp_Disconnect(cxn); + return; + } + + /* the initial intro could have many lines via + continuations. see if we need to read more */ + if (ask_keepgoing(str)==1) + { + goto reset; + } + + result = lmtp_getcapabilities(cxn); + + if (result != RET_OK) + { + d_printf(0,"lmtp_getcapabilities() failure\n"); + lmtp_Disconnect(cxn); + return; + } + + break; + + case LMTP_READING_LHLO: + + /* recieve the response(s) */ + response_code = ask_code(str); + + if (response_code != 250) /* was none */ + { + d_printf(0,"Response code unexpected (%d)\n",response_code); + lmtp_Disconnect(cxn); + return; + } + + /* look for one we know about; ignore all others */ + if (strncmp(str+4,"8BITMIME",strlen("8BITMIME"))==0) + { + cxn->lmtp_capabilities->Eightbitmime = 1; + } else if (strncmp(str+4, "ENHANCEDSTATUSCODES", + strlen("ENHANCEDSTATUSCODES"))==0) { + cxn->lmtp_capabilities->EnhancedStatusCodes = 1; + } else if (strncmp(str+4, "AUTH",4)==0) { + + cxn->lmtp_capabilities->saslmechs = (char *) malloc(strlen(str+4+5)+5); + ASSERT (cxn->lmtp_capabilities->saslmechs != NULL) ; + + /* copy string removing endline */ + strcpy(cxn->lmtp_capabilities->saslmechs, str+4+5); + + } else if (strncmp(str+4,"PIPELINING",strlen("PIPELINING"))==0) { + cxn->lmtp_capabilities->pipelining = 1; + } else { + /* don't care; ignore */ + } + + /* see if this is the last line of the capability */ + if (ask_keepgoing(str)==1) + { + goto reset; + } else { + + /* we require a few capabilities */ + #ifndef SMTPMODE + if (cxn->lmtp_capabilities->pipelining!=1) + { + d_printf(0,"We require the capability PIPELINING\n"); + + lmtp_Disconnect(cxn); + return; + } + #endif /* SMTPMODE */ + #ifdef HAVE_SASL + /* start the authentication */ + result = lmtp_authenticate(cxn); + + if (result != RET_OK) + { + d_printf(0,"lmtp_authenticate returned error\n"); + lmtp_Disconnect(cxn); + return; + } + #else + cxn->lmtp_state = LMTP_AUTHED_IDLE; + d_printf(0,"Even though we can't authenticate. we're going to try to feed anyway\n"); + /* We just assume we don't need to authenticate (great assumption huh?) */ + hostRemoteStreams (cxn->myHost, cxn, true) ; + + cxn->lmtp_timeCon = theTime () ; + cxn->timeCon = theTime () ; + + + + + /* try to send a message if we have one */ + lmtp_sendmessage(cxn,NULL); + return; + #endif /* HAVE_SASL */ + + + } + + + break; + + #ifdef HAVE_SASL + case LMTP_READING_STEPAUTH: + + inlen = 0; + status = lmtp_getauthline(str, &in, &inlen); + + switch (status) + { + + case STAT_CONT: + + saslresult=sasl_client_step(cxn->saslconn_lmtp, + in, + inlen, + &client_interact, + &out, + &outlen); + + free(in); + + /* check if sasl suceeded */ + if (saslresult != SASL_OK && saslresult != SASL_CONTINUE) { + + d_printf(0,"sasl_client_step returned error (%s)\n", + sasl_errstring(saslresult,NULL,NULL)); + + lmtp_Disconnect(cxn); + return; + } + + /* convert to base64 */ + inbase64 = (char *) malloc(outlen*2+10); + + saslresult = sasl_encode64(out, outlen, + inbase64, outlen*2+10, (unsigned *) &inbase64len); + + free(out); + + if (saslresult != SASL_OK) + { + d_printf(0,"sasl_encode64 returned error (%s)\n", + sasl_errstring(saslresult,NULL,NULL)); + + lmtp_Disconnect(cxn); + return; + } + + /* add an endline */ + strcpy(inbase64 + inbase64len, "\r\n"); + + /* send to server */ + result = WriteToWire_lmtpstr(cxn,inbase64, inbase64len+2); + + if (result != RET_OK) + { + d_printf(0,"WriteToWrite failure\n"); + lmtp_Disconnect(cxn); + return; + } + + cxn->lmtp_state = LMTP_WRITING_STEPAUTH; + break; + + case STAT_OK: + + cxn->lmtp_sleepTimeout = init_reconnect_period ; + + d_printf(0,"%s:%d LMTP authenticated succeeded\n", + hostPeerName (cxn->myHost), cxn->ident); + + cxn->lmtp_disconnects=0; + + hostRemoteStreams (cxn->myHost, cxn, true) ; + + cxn->lmtp_timeCon = theTime () ; + cxn->timeCon = theTime () ; + + cxn->lmtp_state = LMTP_AUTHED_IDLE; + + + /* try to send a message if we have one */ + lmtp_sendmessage(cxn,NULL); + return; + + break; + + default: + d_printf(0,"lmtp failed authentication\n"); + lmtp_Disconnect(cxn); + return; + } + + break; + #endif /* HAVE_SASL */ + + case LMTP_READING_MAILFROM: + + if (ask_code(str)!=250) + { + d_printf(0,"MAILFROM failed with (%d)\n",ask_code(str)); + lmtp_Disconnect(cxn); + return; + } + + /* we pipelined so next we recieve the rcpt's */ + cxn->lmtp_state = LMTP_READING_RCPTTO; + + goto reset; + + break; + + case LMTP_READING_RCPTTO: + + if (ask_code(str)!=250) + { + d_printf(1,"RCPTTO failed with (%d) %s\n",ask_code(str), str); + + cxn->current_rcpts_issued--; + + } else { + cxn->current_rcpts_okayed++; + } + + /* if issued equals number okayed then we're done */ + if ( cxn->current_rcpts_okayed == cxn->current_rcpts_issued) + { + cxn->lmtp_state = LMTP_READING_DATA; + } else { + /* stay in same state */ + } + + goto reset; + + break; + + case LMTP_READING_DATA: + + if (cxn->current_rcpts_issued == 0) + { + d_printf(1,"None of the rcpts were accepted for this message. Re-queueing\n"); + + ReQueue(cxn, &(cxn->lmtp_todeliver_q), cxn->current_article); + + cxn->lmtp_have_mailfrom = 1; + + cxn->lmtp_state = LMTP_AUTHED_IDLE; + lmtp_sendmessage(cxn,NULL); + } else { + + cxn->lmtp_have_mailfrom = 0; + + if (WriteArticle(cxn, cxn->current_bufs) != RET_OK) + { + d_printf(0,"Error writing article\n"); + lmtp_Disconnect(cxn); + return; + } + + cxn->lmtp_state = LMTP_WRITING_CONTENTS; + } + + break; + + case LMTP_READING_CONTENTS: + + /* need 1 response from server for every rcpt */ + cxn->current_rcpts_issued--; + + if (ask_code(str)!=250) + { + d_printf(1,"DATA failed with %d (%s)\n",ask_code(str), str); + cxn->current_rcpts_okayed--; + } + + + if (cxn->current_rcpts_issued>0) + { + goto reset; + } + + /* + * current_rcpts_okayed is number that suceeded + * + */ + + if (cxn->current_rcpts_okayed==0) + { + cxn->lmtp_state = LMTP_AUTHED_IDLE; + + } else { + + cxn->lmtp_state = LMTP_AUTHED_IDLE; + cxn->lmtp_suceeded++; + d_printf(1,"Woohoo! message accepted\n"); + } + + /* we can delete article now */ + QueueForgetAbout(cxn, cxn->current_article,0); + + #ifdef SMTPMODE + lmtp_Disconnect(cxn); + #else + /* try to send another if we have one and we're still idle + * forgetting the msg might have made us unidle + */ + if (cxn->lmtp_state == LMTP_AUTHED_IDLE) + { + lmtp_sendmessage(cxn,NULL); + } + #endif + + break; + + case LMTP_READING_QUIT: + + d_printf(1,"LMTP read quit\n"); + + cxn->lmtp_state = LMTP_DISCONNECTED; + + switch (cxn->issue_quit) + { + case 1: + if (cxn->imap_state == IMAP_DISCONNECTED) + { + cxn->lmtp_state = LMTP_WAITING; + cxn->imap_state = IMAP_WAITING; + cxn->issue_quit = 0; + hostCxnWaiting (cxn->myHost,cxn) ; /* tell our Host we're waiting */ + } + break; + case 2: + if (cxn->imap_state == IMAP_DISCONNECTED) + { + cxn->issue_quit = 0; + if (imap_Connect(cxn)!=RET_OK) prepareReopenCbk(cxn,0); + if (lmtp_Connect(cxn)!=RET_OK) prepareReopenCbk(cxn,1); + } + break; + case 3: + if (cxn->imap_state == IMAP_DISCONNECTED) + { + delConnection(cxn); + } + break; + } + + break; + + default: + + d_printf(0,"Bad state in lmtp_readCB %d\n",cxn->lmtp_state); + lmtp_Disconnect(cxn); + return; + } + + + } + + /* + * Add a rcpt to: to the string + * + */ + + static void addrcpt(char *newrcpt, int newrcptlen, char **out, int *outalloc) + { + int size = strlen(*out); + int newsize = size + 9+strlen(NEWS_USERNAME)+1+newrcptlen+3; + + /* see if we need to grow the string */ + if (newsize > *outalloc) + { + (*outalloc)+=200; + (*out) = realloc(*out, *outalloc); + ASSERT(*out); + } + + sprintf((*out)+size,"RCPT TO:<%s+",NEWS_USERNAME); + size+=9+strlen(NEWS_USERNAME)+1; + + memcpy((*out)+size, newrcpt, newrcptlen); + size+=newrcptlen; + + strcpy((*out)+size,">\r\n"); + } + + /* + * Takes the newsgroups header value and makes it into a list of RCPT TO:'s we can send over the wire + * + * in - newsgroups header start + * in_end - end of newsgroups header + * num - number of rcpt's we created + */ + + static char *ConvertRcptList(char *in, char *in_end, int *num) + { + int retalloc = 400; + char *ret = malloc(retalloc); + char *str = in; + char *laststart = in; + int len; + + (*num) = 0; + + /* start it off empty */ + strcpy(ret,""); + + while ( str != in_end) + { + if ((*str) == ',') + { + /* eliminate leading whitespace */ + while (((*laststart) ==' ') || ((*laststart)=='\t')) + { + laststart++; + } + + #ifndef SMTPMODE + addrcpt(laststart, str - laststart, &ret, &retalloc); + (*num)++; + #endif /* SMTPMODE */ + laststart = str+1; + } + + str++; + } + + if (laststartimap_controlMsg_q), &item); + + if (result==RET_QUEUE_EMPTY) + { + if (cxn->issue_quit) + { + imap_sendQuit(cxn); + return; + } + + cxn->imap_state = IMAP_IDLE_AUTHED; + + /* now we wait for articles from our Host, or we have some + articles already. On infrequently used connections, the + network link is torn down and rebuilt as needed. So we may + be rebuilding the connection here in which case we have an + article to send. */ + + /* make sure imap has _lots_ of space too */ + if ((QueueItems(&(cxn->lmtp_todeliver_q)) == 0) && + (QueueItems(&(cxn->imap_controlMsg_q)) == 0)) + { + if (hostGimmeArticle (cxn->myHost,cxn)==true) + goto retry; + } + + return RET_OK; + } + + cxn->current_control = item; + + switch (item->type) + { + case CREATE_FOLDER: + imap_CreateGroup(cxn, item->data.control->folder); + break; + + case CANCEL_MSG: + + imap_CancelMsg(cxn, item->data.control->folder); + + break; + + case DELETE_FOLDER: + imap_DeleteGroup(cxn, item->data.control->folder); + break; + default: + break; + } + + return RET_OK; + } + + + + /* + * + * Pulls a message off the queue and trys to start sending it. If the + * message is a control message put it in the control queue and grab + * another message. If the message doesn't exist on disk or something + * is wrong with it tell the host and try again. If we run out of + * messages to get tell the host we want more + * + * cxn - connection object + * justadded - the article that was just added to the queue + */ + + static void lmtp_sendmessage(connection_t *cxn, Article justadded) + { + bool res; + conn_ret result; + FILE *stream; + char *str; + char *p; + Buffer *bufs; + char *control_header = NULL; + char *control_header_end = NULL; + + article_queue_t *item; + char *rcpt_list, *rcpt_list_end; + + /* retry point */ + retry: + + /* pull an article off the queue */ + result = PopFromQueue(&(cxn->lmtp_todeliver_q), &item); + + if (result==RET_QUEUE_EMPTY) + { + + if (cxn->issue_quit) + { + lmtp_IssueQuit(cxn); + return; + } + /* now we wait for articles from our Host, or we have some + articles already. On infrequently used connections, the + network link is torn down and rebuilt as needed. So we may + be rebuilding the connection here in which case we have an + article to send. */ + + /* make sure imap has space too */ + if ((QueueItems(&(cxn->lmtp_todeliver_q)) == 0) && + (QueueItems(&(cxn->imap_controlMsg_q)) == 0)) + { + if (hostGimmeArticle (cxn->myHost,cxn)==true) + goto retry; + } + + return; + } + + /* make sure contents ok; this also should load it into memory */ + res = artContentsOk (item->data.article); + if (res==false) + { + if (justadded == item->data.article) { + ReQueue(cxn, &(cxn->lmtp_todeliver_q), item); + return; + + } else { + /* tell to reject taking this message */ + QueueForgetAbout(cxn,item,3); + } + + goto retry; + } + + /* Check if it's a control message */ + bufs = artGetNntpBuffers (item->data.article); + if (bufs == NULL) + { + /* tell to reject taking this message */ + QueueForgetAbout(cxn,item,3); + goto retry; + } + + result = FindHeader(bufs, "Control", &control_header, &control_header_end); + + if (result == RET_OK) + { + result = AddControlMsg(cxn, item->data.article, bufs, control_header,control_header_end, 1); + + if (result != RET_OK) + { + d_printf(1,"Error adding to control queue\n"); + ReQueue(cxn, &(cxn->lmtp_todeliver_q), item); + return; + } + + switch(cxn->imap_state) + { + case IMAP_IDLE_AUTHED: + /* we're idle. let's process the queue */ + imap_ProcessQueue(cxn); + break; + case IMAP_DISCONNECTED: + case IMAP_WAITING: + /* Let's connect. Once we're connected we can worry about the message */ + if (imap_Connect(cxn) != RET_OK) prepareReopenCbk(cxn,0); + break; + default: + /* we're doing something right now */ + break; + + } + + /* all we did was add a control message. we still want to get an lmtp message */ + goto retry; + } + + if (cxn->current_bufs!=NULL) + { + /* freeBufferArray(cxn->current_bufs); */ + cxn->current_bufs = NULL; + } + cxn->current_bufs = bufs; + cxn->current_article = item; + + /* we make use of pipelining here + send: + mail from + rctp to + data + */ + + /* find out who it's going to */ + result = FindHeader(cxn->current_bufs, "Newsgroups", &rcpt_list, &rcpt_list_end); + + if ((result != RET_OK) || (rcpt_list == NULL)) + { + d_printf(1,"Didn't find Newsgroups header\n"); + QueueForgetAbout(cxn, cxn->current_article,1); + goto retry; + } + + /* free's original rcpt_list */ + rcpt_list = ConvertRcptList(rcpt_list, rcpt_list_end, &cxn->current_rcpts_issued); + cxn->current_rcpts_okayed = 0; + + + + if (cxn->lmtp_have_mailfrom==1) + { + p = (char *) malloc (strlen(rcpt_list)+50); + sprintf (p, "%sDATA\r\n", rcpt_list); + } else { + p = (char *) malloc (strlen(rcpt_list)+strlen(mailfrom_name)+50); + sprintf (p, "MAIL FROM:<%s>\r\n%sDATA\r\n", mailfrom_name,rcpt_list); + } + + cxn->lmtp_state = LMTP_WRITING_UPTODATA; + + result = WriteToWire_lmtpstr(cxn, p, strlen(p)); + + if (result != RET_OK) + { + d_printf(0,"Failed trying to write\n"); + lmtp_Disconnect(cxn); + return; + } + } + + /* + * Called by the EndPoint class when the timer goes off + */ + static void dosomethingTimeoutCbk (TimeoutId id, void *data) + { + Connection cxn = (Connection) data ; + + ASSERT (id == cxn->dosomethingTimerId) ; + + show_stats(cxn); + + /* we're disconnected but there are things to send */ + if ((cxn->lmtp_state == LMTP_DISCONNECTED) && + QueueItems(&(cxn->lmtp_todeliver_q)) > 0) + lmtp_Connect(cxn); + + if ((cxn->imap_state == IMAP_DISCONNECTED) && + (QueueItems(&(cxn->imap_controlMsg_q)) > 0)) + imap_Connect(cxn); + + + /* if we're idle and there are items to send let's send them */ + if ((cxn->lmtp_state == LMTP_AUTHED_IDLE) && + QueueItems(&(cxn->lmtp_todeliver_q)) > 0) + lmtp_sendmessage(cxn,NULL); + + if ((cxn->imap_state == IMAP_IDLE_AUTHED) && + (QueueItems(&(cxn->imap_controlMsg_q)) > 0)) + imap_ProcessQueue(cxn); + + /* set up the timer. */ + clearTimer (cxn->dosomethingTimerId) ; + + cxn->dosomethingTimerId = prepareSleep (dosomethingTimeoutCbk, + cxn->dosomethingTimeout, cxn); + } + + /* Give all articles in the queue back to the host. We're probably + * going to exit soon. + * */ + + static void DeferAllArticles(connection_t *cxn, Q_t *q) + { + article_queue_t *cur; + conn_ret ret; + + while (1) + { + ret = PopFromQueue(q, &cur); + if (ret == RET_QUEUE_EMPTY) return; + + if (ret == RET_OK) + { + QueueForgetAbout(cxn, cur,2); + } else { + d_printf(0,"Error emptying queue\n"); + return; + } + } + } + + /* + * Does the actual deletion of a connection and all its private data. + */ + static void delConnection (Connection cxn) + { + bool shutDown; + Connection c, q; + + if (cxn == NULL) + return ; + + d_printf (1,"Deleting connection: %s:%d\n", + hostPeerName (cxn->myHost),cxn->ident) ; + + for (c = gCxnList, q = NULL ; c != NULL ; q = c, c = c->next) + if (c == cxn) + { + if (gCxnList == c) + gCxnList = gCxnList->next ; + else + q->next = c->next ; + break ; + } + + ASSERT (c != NULL) ; + + if (cxn->lmtp_endpoint != NULL) + delEndPoint (cxn->lmtp_endpoint) ; + if (cxn->imap_endpoint != NULL) + delEndPoint (cxn->imap_endpoint) ; + + delBuffer (cxn->imap_rBuffer) ; + delBuffer (cxn->lmtp_rBuffer) ; + + /* tell the Host we're outta here. */ + shutDown = hostCxnGone (cxn->myHost, cxn) ; + + cxn->ident = 0 ; + cxn->timeCon = 0 ; + + FREE (cxn->ServerName) ; + + clearTimer (cxn->imap_readBlockedTimerId) ; + clearTimer (cxn->imap_writeBlockedTimerId) ; + clearTimer (cxn->lmtp_readBlockedTimerId) ; + clearTimer (cxn->lmtp_writeBlockedTimerId) ; + clearTimer (cxn->imap_sleepTimerId); + clearTimer (cxn->lmtp_sleepTimerId); + clearTimer (cxn->dosomethingTimerId); + + FREE(cxn->imap_respBuffer); + FREE(cxn->lmtp_respBuffer); + + FREE (cxn) ; + + if (shutDown) + { + /* exit program if that was the last connexion for the last host */ + /* XXX what about if there are ever multiple listeners? + XXX this will be executed if all hosts on only one of the + XXX listeners have gone */ + time_t now = theTime () ; + char dateString [30] ; + + strcpy (dateString,ctime (&now)) ; + dateString [24] = '\0' ; + + syslog (LOG_NOTICE,STOPPING_PROGRAM,dateString) ; + + exit (0) ; + } + } + + + /******************** PUBLIC FUNCTIONS ****************************/ + + + + /* + * Create a new Connection. + * + * HOST is the host object we're owned by. + * IDENT is an identifier to be added to syslog entries so we can tell + * what's happening on different connections to the same peer. + * IPNAME is the name (or ip address) of the remote) + * MAXTOUT is the maximum amount of time to wait for a response before + * considering the remote host dead. + * PORTNUM is the portnum to contact on the remote end. + * RESPTIMEOUT is the amount of time to wait for a response from a remote + * before considering the connection dead. + * CLOSEPERIOD is the number of seconds after connecting that the + * connections should be closed down and reinitialized (due to problems + * with old NNTP servers that hold history files open. Value of 0 means + * no close down. + */ + + Connection newConnection (Host host, + u_int ident, + const char *ipname, + u_int artTout, + u_int portNum, + u_int respTimeout, + u_int closePeriod, + double lowPassLow, + double lowPassHigh, + double lowPassFilter) + { + Connection cxn; + /* check arguements */ + + /* allocate connection structure */ + cxn = CALLOC (connection_t, 1) ; + ASSERT (cxn != NULL) ; + + cxn->ident = ident ; + + cxn->ServerName = malloc( strlen(ipname)+1); + strcpy(cxn->ServerName, ipname); + + cxn->myHost = host ; + + /* setup mailfrom user */ + if (gethostname(hostname, MAXHOSTNAMELEN)!=0) + { + d_printf(0,"gethostname failed\n"); + return NULL; + } + + mailfrom_name = (char *) malloc (20+strlen(hostname)); + ASSERT (mailfrom_name != NULL); + + sprintf(mailfrom_name,"news@%s",hostname); + + cxn->next = gCxnList ; + gCxnList = cxn ; + gCxnCount++ ; + + /* init stuff */ + Initialize(cxn, respTimeout); + + return cxn; + } + + + /* Causes the Connection to build the network connection. */ + bool cxnConnect (Connection cxn) + { + conn_ret result; + + d_printf(1,"Connecting...\n"); + + /* make the lmtp connection */ + if (lmtp_Connect(cxn) != RET_OK) return false; + + if (imap_Connect(cxn) != RET_OK) return false; + + return true; + } + + + void QuitIfIdle(Connection cxn) + { + if ((cxn->lmtp_state == LMTP_AUTHED_IDLE) && (QueueItems(&(cxn->lmtp_todeliver_q))<=0)) + lmtp_IssueQuit(cxn); + if ((cxn->imap_state == IMAP_IDLE_AUTHED) && (QueueItems(&(cxn->imap_controlMsg_q))<=0)) + imap_sendQuit(cxn); + } + + /* puts the connection into the wait state (i.e. waits for an article + before initiating a connect). Can only be called right after + newConnection returns, or while the Connection is in the (internal) + Sleeping state. */ + void cxnWait (Connection cxn) + { + cxn->issue_quit = 1; + + QuitIfIdle(cxn); + } + + /* The Connection will disconnect as if cxnDisconnect were called and then + it automatically reconnects to the remote. */ + void cxnFlush (Connection cxn) + { + cxn->issue_quit = 2; + + QuitIfIdle(cxn); + } + + + + /* The Connection sends remaining articles, then issues a QUIT and then + deletes itself */ + void cxnClose (Connection cxn) + { + d_printf(0,"%s:%d Closing cxn\n",hostPeerName (cxn->myHost), cxn->ident); + cxn->issue_quit = 3; + + QuitIfIdle(cxn); + } + + /* The Connection drops all queueed articles, then issues a QUIT and then + deletes itself */ + void cxnTerminate (Connection cxn) + { + d_printf(0,"%s:%d Terminate\n",hostPeerName (cxn->myHost), cxn->ident); + + DeferAllArticles(cxn, &(cxn->lmtp_todeliver_q)) ; /* give any articles back to Host */ + DeferAllArticles(cxn, &(cxn->imap_controlMsg_q)) ; /* give any articles back to Host */ + + cxn->issue_quit = 3; + + QuitIfIdle(cxn); + } + + /* Blow away the connection gracelessly and immedately clean up */ + void cxnNuke (Connection cxn) + { + d_printf(0,"%s:%d Nuking connection\n",cxn->ServerName, cxn->ident); + + cxn->issue_quit = 4; + + DeferAllArticles(cxn, &(cxn->lmtp_todeliver_q)) ; /* give any articles back to Host */ + DeferAllArticles(cxn, &(cxn->imap_controlMsg_q)) ; /* give any articles back to Host */ + + imap_Disconnect(cxn); + lmtp_Disconnect(cxn); + + hostCxnDead (cxn->myHost,cxn); + delConnection(cxn); + } + + /* + * must + * true - must queue article. Don't try sending + * false - queue of article may fail. Try sending + * + * Always adds to lmtp queue even if control message + * + */ + + bool ProcessArticle(Connection cxn, Article art, bool must) + { + conn_ret result; + + /* if it's a regular message let's add it to the queue */ + result = AddToQueue(&(cxn->lmtp_todeliver_q), art, DELIVER,1,must); + + if (result == RET_EXCEEDS_SIZE) { + return false; + } + + if (result != RET_OK) + { + d_printf(0,"Error adding to delivery queue\n"); + return must; + } + + if (must == true) return true; + + switch (cxn->lmtp_state) + { + case LMTP_WAITING: + case LMTP_DISCONNECTED: + if (lmtp_Connect(cxn) != RET_OK) prepareReopenCbk(cxn,1); + break; + + case LMTP_AUTHED_IDLE: + lmtp_sendmessage(cxn,art); + break; + default: + /* currently doing something */ + break; + } + + return true; + } + + /* Tells the Connection to take the article and handle its + transmission. If it can't (due to queue size or whatever), then the + function returns false. The connection assumes ownership of the + article if it accepts it (returns true). */ + bool cxnTakeArticle (Connection cxn, Article art) + { + /* if we're closing down always refuse */ + if (cxn->issue_quit == 1) return false; + + return ProcessArticle (cxn,art,false); + } + + /* Tell the Connection to take the article (if it can) for later + processing. Assumes ownership of it if it takes it. */ + bool cxnQueueArticle (Connection cxn, Article art) + { + return ProcessArticle (cxn,art,true); + } + + /* generate a syslog message for the connections activity. Called by Host. */ + void cxnLogStats (Connection cxn, bool final) + { + const char *peerName ; + time_t now = theTime() ; + + ASSERT (cxn != NULL) ; + + peerName = hostPeerName (cxn->myHost) ; + + syslog (LOG_NOTICE, + "Host: %s:%d status: %s time: %d Delivered (%d of %d) Cancelled (%d of %d) Created (%d of %d) Deleted (%d of %d)", + peerName, cxn->ident, + (final ? "final" : "checkpoint"), (long) (now - cxn->timeCon), + cxn->lmtp_suceeded, cxn->lmtp_suceeded + cxn->lmtp_failed, + cxn->cancel_suceeded, cxn->cancel_suceeded + cxn->cancel_failed, + cxn->create_suceeded, cxn->create_suceeded + cxn->create_failed, + cxn->remove_suceeded, cxn->remove_suceeded + cxn->remove_failed); + + show_stats(cxn); + + if (final) + { + cxn->lmtp_suceeded = 0; + cxn->lmtp_failed = 0; + cxn->cancel_suceeded = 0; + cxn->cancel_failed = 0; + cxn->create_suceeded = 0; + cxn->create_failed = 0; + cxn->remove_suceeded = 0; + cxn->remove_failed = 0; + + if (cxn->timeCon > 0) + cxn->timeCon = theTime() ; + } + + } + + /* return the number of articles the connection can be given. This lets + the host shovel in as many as possible. May be zero. */ + size_t cxnQueueSpace (Connection cxn) + { + int lmtpsize; + int imapsize; + + lmtpsize = QueueSpace(&(cxn->lmtp_todeliver_q)); + imapsize = QueueSpace(&(cxn->imap_controlMsg_q)); + + if (lmtpsize >=1) lmtpsize--; + if (imapsize >=1) imapsize--; + + d_printf(1,"Q Space lmtp size = %d state = %d\n",lmtpsize,cxn->lmtp_state); + d_printf(1,"Q Space imap size = %d state = %d\n",imapsize,cxn->imap_state); + + /* return the smaller of our 2 queues */ + if (lmtpsize < imapsize) + return lmtpsize; + else + return imapsize; + } + + /* adjust the mode no-CHECK filter values */ + void cxnSetCheckThresholds (Connection cxn, + double lowFilter, double highFilter, + double lowPassFilter) + { + d_printf(1,"Threshold change. This means nothing to me\n"); + } + + /* print some debugging info. */ + void gPrintCxnInfo (FILE *fp, u_int indentAmt) + { + char indent [INDENT_BUFFER_SIZE] ; + u_int i ; + Connection cxn ; + + for (i = 0 ; i < MIN(INDENT_BUFFER_SIZE - 1,indentAmt) ; i++) + indent [i] = ' ' ; + indent [i] = '\0' ; + + fprintf (fp,"%sGlobal Connection list : (count %d) {\n", + indent,gCxnCount) ; + for (cxn = gCxnList ; cxn != NULL ; cxn = cxn->next) + printCxnInfo (cxn,fp,indentAmt + INDENT_INCR) ; + fprintf (fp,"%s}\n",indent) ; + } + + void printCxnInfo (Connection cxn, FILE *fp, u_int indentAmt) + { + char indent [INDENT_BUFFER_SIZE] ; + u_int i ; + article_queue_t *artH ; + + for (i = 0 ; i < MIN(INDENT_BUFFER_SIZE - 1,indentAmt) ; i++) + indent [i] = ' ' ; + indent [i] = '\0' ; + + fprintf (fp,"%sConnection : %p {\n",indent,cxn) ; + fprintf (fp,"%s host : %p\n",indent, (void *) cxn->myHost) ; + fprintf (fp,"%s endpoint (imap): %p\n",indent,cxn->imap_endpoint) ; + fprintf (fp,"%s endpoint (lmtp): %p\n",indent,cxn->lmtp_endpoint) ; + fprintf (fp,"%s state (imap) : %s\n",indent, imap_stateToString (cxn->imap_state)) ; + fprintf (fp,"%s state (lmtp) : %s\n",indent, lmtp_stateToString (cxn->lmtp_state)) ; + fprintf (fp,"%s ident : %d\n",indent,cxn->ident) ; + fprintf (fp,"%s ip-name (imap): %s\n", indent, cxn->ServerName) ; + fprintf (fp,"%s ip-name (lmtp): %s\n", indent, cxn->ServerName) ; + fprintf (fp,"%s port-number (imap) : %d\n",indent,cxn->imap_port) ; + fprintf (fp,"%s port-number (lmtp) : %d\n",indent,cxn->lmtp_port) ; + + fprintf (fp,"%s Issuing Quit : %d\n",indent, cxn->issue_quit) ; + + fprintf (fp,"%s time-connected (imap) : %ld\n",indent,(long) cxn->imap_timeCon) ; + fprintf (fp,"%s time-connected (lmtp) : %ld\n",indent,(long) cxn->lmtp_timeCon) ; + fprintf (fp,"%s articles from INN : %d\n",indent, + cxn->lmtp_suceeded+ + cxn->lmtp_failed+ + cxn->cancel_suceeded+ + cxn->cancel_failed+ + cxn->create_suceeded+ + cxn->create_failed+ + cxn->remove_suceeded+ + cxn->remove_failed+ + QueueSpace(&(cxn->lmtp_todeliver_q))+ + QueueSpace(&(cxn->imap_controlMsg_q)) + ); + fprintf(fp,"%s LMTP STATS: yes: %d no: %d\n",cxn->lmtp_suceeded, cxn->lmtp_failed); + fprintf(fp,"%s control: yes: %d no: %d\n",cxn->cancel_suceeded, cxn->cancel_failed); + fprintf(fp,"%s create: yes: %d no: %d\n",cxn->create_suceeded, cxn->create_failed); + fprintf(fp,"%s remove: yes: %d no: %d\n",cxn->remove_suceeded, cxn->remove_failed); + + fprintf (fp,"%s response-timeout : %d\n",indent,cxn->imap_readTimeout) ; + fprintf (fp,"%s response-callback : %d\n",indent,cxn->imap_readBlockedTimerId) ; + + fprintf (fp,"%s write-timeout : %d\n",indent,cxn->imap_writeTimeout) ; + fprintf (fp,"%s write-callback : %d\n",indent,cxn->imap_writeBlockedTimerId) ; + + fprintf (fp,"%s reopen wait : %d\n",indent,cxn->imap_sleepTimeout) ; + fprintf (fp,"%s reopen id : %d\n",indent,cxn->imap_sleepTimerId) ; + + fprintf (fp,"%s IMAP queue {\n",indent) ; + for (artH = cxn->imap_controlMsg_q.head; artH != NULL ; artH = artH->next) + printArticleInfo (artH->data.article,fp,indentAmt + INDENT_INCR) ; + fprintf (fp,"%s }\n",indent) ; + + fprintf (fp,"%s LMTP queue {\n",indent) ; + for (artH = cxn->lmtp_todeliver_q.head ; artH != NULL ; artH = artH->next) + printArticleInfo (artH->data.control->article,fp,indentAmt + INDENT_INCR) ; + fprintf (fp,"%s }\n",indent) ; + + fprintf (fp,"%s}\n",indent) ; + } + + /* config file load callback */ + int cxnConfigLoadCbk (void *data) + { + long iv ; + char *sv ; + int rval = 1 ; + FILE *fp = (FILE *) data ; + + (void) data ; /* keep lint happy */ + + if (getInteger (topScope,"max-reconnect-time",&iv,NO_INHERIT)) + { + if (iv < 1) + { + rval = 0 ; + logOrPrint (LOG_ERR,fp,LESS_THAN_ONE,"max-reconnect-time", + iv,"global scope",(long) MAX_RECON_PER); + iv = MAX_RECON_PER ; + } + } + else + iv = MAX_RECON_PER ; + max_reconnect_period = (u_int) iv ; + + if (getInteger (topScope,"initial-reconnect-time",&iv,NO_INHERIT)) + { + if (iv < 1) + { + rval = 0 ; + logOrPrint (LOG_ERR,fp,LESS_THAN_ONE,"initial-reconnect-time", + iv,"global scope",(long)INIT_RECON_PER); + iv = INIT_RECON_PER ; + } + } + else + iv = INIT_RECON_PER ; + init_reconnect_period = (u_int) iv ; + + return rval ; + } + + /* check connection state is in cxnWaitingS, cxnConnectingS or cxnIdleS */ + bool cxnCheckstate (Connection cxn) + { + d_printf(1,"Being asked to check state\n"); + + /* return false if either connection is doing something */ + + if (cxn->imap_state > IMAP_IDLE_AUTHED) + { + return false; + } + + if (cxn->lmtp_state > LMTP_AUTHED_IDLE) + { + return false; + } + + return true; + } + cyrus-imapd-2.5.10/Makefile.in0000644000175000017500000144517313001246602013033 00000000000000# Makefile.in generated by automake 1.15 from Makefile.am. # @configure_input@ # Copyright (C) 1994-2014 Free Software Foundation, Inc. # This Makefile.in is free software; the Free Software Foundation # gives unlimited permission to copy and/or distribute it, # with or without modifications, as long as this notice is preserved. # This program is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY, to the extent permitted by law; without # even the implied warranty of MERCHANTABILITY or FITNESS FOR A # PARTICULAR PURPOSE. @SET_MAKE@ # # @configure_input@ # # Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. # # Redistribution and use in source and binary forms, with or without # modification, are permitted provided that the following conditions # are met: # # 1. Redistributions of source code must retain the above copyright # notice, this list of conditions and the following disclaimer. # # 2. Redistributions in binary form must reproduce the above copyright # notice, this list of conditions and the following disclaimer in # the documentation and/or other materials provided with the # distribution. # # 3. The name "Carnegie Mellon University" must not be used to # endorse or promote products derived from this software without # prior written permission. For permission or any legal # details, please contact # Carnegie Mellon University # Center for Technology Transfer and Enterprise Creation # 4615 Forbes Avenue # Suite 302 # Pittsburgh, PA 15213 # (412) 268-7393, fax: (412) 268-7395 # innovation@andrew.cmu.edu # # 4. Redistributions of any form whatsoever must retain the following # acknowledgment: # "This product includes software developed by Computing Services # at Carnegie Mellon University (http://www.cmu.edu/computing/)." # # CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO # THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY # AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE # FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES # WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN # AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING # OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. # VPATH = @srcdir@ am__is_gnu_make = { \ if test -z '$(MAKELEVEL)'; then \ false; \ elif test -n '$(MAKE_HOST)'; then \ true; \ elif test -n '$(MAKE_VERSION)' && test -n '$(CURDIR)'; then \ true; \ else \ false; \ fi; \ } am__make_running_with_option = \ case $${target_option-} in \ ?) ;; \ *) echo "am__make_running_with_option: internal error: invalid" \ "target option '$${target_option-}' specified" >&2; \ exit 1;; \ esac; \ has_opt=no; \ sane_makeflags=$$MAKEFLAGS; \ if $(am__is_gnu_make); then \ sane_makeflags=$$MFLAGS; \ else \ case $$MAKEFLAGS in \ *\\[\ \ ]*) \ bs=\\; \ sane_makeflags=`printf '%s\n' "$$MAKEFLAGS" \ | sed "s/$$bs$$bs[$$bs $$bs ]*//g"`;; \ esac; \ fi; \ skip_next=no; \ strip_trailopt () \ { \ flg=`printf '%s\n' "$$flg" | sed "s/$$1.*$$//"`; \ }; \ for flg in $$sane_makeflags; do \ test $$skip_next = yes && { skip_next=no; continue; }; \ case $$flg in \ *=*|--*) continue;; \ -*I) strip_trailopt 'I'; skip_next=yes;; \ -*I?*) strip_trailopt 'I';; \ -*O) strip_trailopt 'O'; skip_next=yes;; \ -*O?*) strip_trailopt 'O';; \ -*l) strip_trailopt 'l'; skip_next=yes;; \ -*l?*) strip_trailopt 'l';; \ -[dEDm]) skip_next=yes;; \ -[JT]) skip_next=yes;; \ esac; \ case $$flg in \ *$$target_option*) has_opt=yes; break;; \ esac; \ done; \ test $$has_opt = yes am__make_dryrun = (target_option=n; $(am__make_running_with_option)) am__make_keepgoing = (target_option=k; $(am__make_running_with_option)) pkgdatadir = $(datadir)/@PACKAGE@ pkgincludedir = $(includedir)/@PACKAGE@ pkglibdir = $(libdir)/@PACKAGE@ pkglibexecdir = $(libexecdir)/@PACKAGE@ am__cd = CDPATH="$${ZSH_VERSION+.}$(PATH_SEPARATOR)" && cd install_sh_DATA = $(install_sh) -c -m 644 install_sh_PROGRAM = $(install_sh) -c install_sh_SCRIPT = $(install_sh) -c INSTALL_HEADER = $(INSTALL_DATA) transform = $(program_transform_name) NORMAL_INSTALL = : PRE_INSTALL = : POST_INSTALL = : NORMAL_UNINSTALL = : PRE_UNINSTALL = : POST_UNINSTALL = : build_triplet = @build@ host_triplet = @host@ target_triplet = @target@ @HAVE_LDAP_TRUE@am__append_1 = $(LDAP_CPPFLAGS) EXTRA_PROGRAMS = tools/htmlstrip$(EXEEXT) check_PROGRAMS = $(am__EXEEXT_1) $(am__EXEEXT_2) $(am__EXEEXT_3) service_PROGRAMS = $(am__EXEEXT_4) $(am__EXEEXT_5) $(am__EXEEXT_6) \ $(am__EXEEXT_7) $(am__EXEEXT_8) $(am__EXEEXT_9) \ $(am__EXEEXT_10) $(am__EXEEXT_11) $(am__EXEEXT_12) user_PROGRAMS = $(am__EXEEXT_13) $(am__EXEEXT_14) $(am__EXEEXT_15) \ $(am__EXEEXT_16) $(am__EXEEXT_17) $(am__EXEEXT_18) \ $(am__EXEEXT_19) $(am__EXEEXT_20) $(am__EXEEXT_21) \ $(am__EXEEXT_22) $(am__EXEEXT_23) @COM_ERR_TRUE@am__append_2 = com_err/et/compile_et @COM_ERR_TRUE@am__append_3 = com_err/et/libcyrus_com_err.la bin_PROGRAMS = imtest/imtest$(EXEEXT) @SERVER_TRUE@am__append_4 = \ @SERVER_TRUE@ imap/mupdate_err.c \ @SERVER_TRUE@ imap/nntp_err.c \ @SERVER_TRUE@ imap/lmtpstats.c \ @SERVER_TRUE@ imap/pushstats.c \ @SERVER_TRUE@ imap/rfc822_header.c \ @SERVER_TRUE@ imap/rfc822_header.h @SERVER_TRUE@am__append_5 = imap/libcyrus_imap.la @SERVER_TRUE@am__append_6 = \ @SERVER_TRUE@ imap/imapd \ @SERVER_TRUE@ imap/lmtpd \ @SERVER_TRUE@ imap/pop3d \ @SERVER_TRUE@ imap/smmapd @SERVER_TRUE@am__append_7 = \ @SERVER_TRUE@ imap/arbitron \ @SERVER_TRUE@ imap/chk_cyrus \ @SERVER_TRUE@ imap/ctl_cyrusdb \ @SERVER_TRUE@ imap/ctl_deliver \ @SERVER_TRUE@ imap/ctl_mboxlist \ @SERVER_TRUE@ imap/cvt_cyrusdb \ @SERVER_TRUE@ imap/cyr_df \ @SERVER_TRUE@ imap/cyrdump \ @SERVER_TRUE@ imap/cyr_dbtool \ @SERVER_TRUE@ imap/cyr_deny \ @SERVER_TRUE@ imap/cyr_expire \ @SERVER_TRUE@ imap/cyr_info \ @SERVER_TRUE@ imap/cyr_sequence \ @SERVER_TRUE@ imap/cyr_synclog \ @SERVER_TRUE@ imap/cyr_userseen \ @SERVER_TRUE@ imap/deliver \ @SERVER_TRUE@ imap/ipurge \ @SERVER_TRUE@ imap/mbexamine \ @SERVER_TRUE@ imap/mbpath \ @SERVER_TRUE@ imap/mbtool \ @SERVER_TRUE@ imap/quota \ @SERVER_TRUE@ imap/reconstruct \ @SERVER_TRUE@ imap/squatter @HAVE_CLAMAV_TRUE@@SERVER_TRUE@am__append_8 = imap/cyr_virusscan @NNTPD_TRUE@@SERVER_TRUE@am__append_9 = imap/nntpd @NNTPD_TRUE@@SERVER_TRUE@am__append_10 = imap/fetchnews @SERVER_TRUE@am__append_11 = imap/fud @IDLED_TRUE@@SERVER_TRUE@am__append_12 = imap/idled @MURDER_TRUE@@SERVER_TRUE@am__append_13 = imap/mupdate @HTTPD_TRUE@@SERVER_TRUE@am__append_14 = $(HTTP_CPPFLAGS) @HTTPD_TRUE@@SERVER_TRUE@am__append_15 = $(HTTP_LIBS) @HTTPD_TRUE@@SERVER_TRUE@am__append_16 = \ @HTTPD_TRUE@@SERVER_TRUE@ imap/http_err.c \ @HTTPD_TRUE@@SERVER_TRUE@ imap/http_err.h \ @HTTPD_TRUE@@SERVER_TRUE@ imap/tz_err.c \ @HTTPD_TRUE@@SERVER_TRUE@ imap/tz_err.h @HTTPD_TRUE@@SERVER_TRUE@am__append_17 = imap/httpd @HTTPD_TRUE@@SERVER_TRUE@am__append_18 = \ @HTTPD_TRUE@@SERVER_TRUE@ imap/ctl_zoneinfo \ @HTTPD_TRUE@@SERVER_TRUE@ imap/dav_reconstruct @REPLICATION_TRUE@@SERVER_TRUE@am__append_19 = imap/sync_client imap/sync_reset @REPLICATION_TRUE@@SERVER_TRUE@am__append_20 = imap/sync_server @HAVE_SSL_TRUE@@SERVER_TRUE@am__append_21 = imap/tls_prune @SERVER_TRUE@am__append_22 = imap/unexpunge master/master @SERVER_TRUE@@SIEVE_TRUE@am__append_23 = notifyd/notifytest @SERVER_TRUE@@SIEVE_TRUE@am__append_24 = notifyd/notifyd @SERVER_FALSE@am__append_25 = \ @SERVER_FALSE@ imap/mupdate_err.c \ @SERVER_FALSE@ imap/nntp_err.c \ @SERVER_FALSE@ imap/lmtpstats.c \ @SERVER_FALSE@ imap/pushstats.c \ @SERVER_FALSE@ imap/rfc822_header.c \ @SERVER_FALSE@ imap/rfc822_header.h @HTTPD_FALSE@@SERVER_FALSE@am__append_26 = \ @HTTPD_FALSE@@SERVER_FALSE@ imap/http_err.c \ @HTTPD_FALSE@@SERVER_FALSE@ imap/http_err.h \ @HTTPD_FALSE@@SERVER_FALSE@ imap/tz_err.c \ @HTTPD_FALSE@@SERVER_FALSE@ imap/tz_err.h @CMULOCAL_TRUE@am__append_27 = depot/rc.local.imap depot/rc.local.ptclient @CMULOCAL_TRUE@am__append_28 = netnews/remotepurge @PTCLIENT_TRUE@am__append_29 = ptclient/ptdump ptclient/ptexpire @PTCLIENT_TRUE@am__append_30 = \ @PTCLIENT_TRUE@ ptclient/ptloader @PERL_TRUE@am__append_31 = perl/annotator perl/imap @PERL_TRUE@am__append_32 = perl/libcyrus.la perl/libcyrus_min.la @PERL_TRUE@@SIEVE_TRUE@am__append_33 = perl/sieve/managesieve @SIEVE_TRUE@am__append_34 = sieve/addr.c sieve/sieve.c sieve/sieve_err.c @SIEVE_TRUE@am__append_35 = sieve/libcyrus_sieve_lex.la @SIEVE_TRUE@am__append_36 = sieve/libcyrus_sieve.la @SIEVE_TRUE@am__append_37 = sieve/test @SIEVE_TRUE@am__append_38 = sieve/sievec sieve/sieved @SERVER_TRUE@@SIEVE_TRUE@am__append_39 = timsieved/timsieved @CUNIT_TRUE@am__append_40 = cunit/registers.h $(CUNIT_PROJECT) @CUNIT_TRUE@am__append_41 = cunit/registers.h $(CUNIT_PROJECT) @CUNIT_TRUE@am__append_42 = cunit/unit @CUNIT_TRUE@@SIEVE_TRUE@am__append_43 = cunit/sieve.testc @CUNIT_TRUE@@SIEVE_TRUE@am__append_44 = sieve/libcyrus_sieve.la @HAVE_CLAMAV_FALSE@am__append_45 = \ @HAVE_CLAMAV_FALSE@ imap/cyr_virusscan.c @HTTPD_FALSE@am__append_46 = \ @HTTPD_FALSE@ imap/ctl_zoneinfo.c @AUTOCREATE_TRUE@am__append_47 = \ @AUTOCREATE_TRUE@ imap/autocreate.h \ @AUTOCREATE_TRUE@ imap/autocreate.c @SIEVE_TRUE@am__append_48 = sieve/libcyrus_sieve.la @JANSSON_TRUE@am__append_49 = $(JANSSON_LIBS) @JANSSON_TRUE@am__append_50 = $(JANSSON_CFLAGS) @HTTPD_TRUE@am__append_51 = \ @HTTPD_TRUE@ imap/caldav_db.c \ @HTTPD_TRUE@ imap/caldav_db.h \ @HTTPD_TRUE@ imap/carddav_db.c \ @HTTPD_TRUE@ imap/carddav_db.h \ @HTTPD_TRUE@ imap/dav_db.c \ @HTTPD_TRUE@ imap/dav_db.h \ @HTTPD_TRUE@ imap/dav_util.c \ @HTTPD_TRUE@ imap/dav_util.h \ @HTTPD_TRUE@ imap/http_caldav.c \ @HTTPD_TRUE@ imap/http_caldav_sched.h \ @HTTPD_TRUE@ imap/http_carddav.c \ @HTTPD_TRUE@ imap/http_client.c \ @HTTPD_TRUE@ imap/http_client.h \ @HTTPD_TRUE@ imap/http_dav.c \ @HTTPD_TRUE@ imap/http_dav.h \ @HTTPD_TRUE@ imap/http_dblookup.c \ @HTTPD_TRUE@ imap/http_ischedule.c \ @HTTPD_TRUE@ imap/http_proxy.c \ @HTTPD_TRUE@ imap/http_proxy.h \ @HTTPD_TRUE@ imap/http_rss.c \ @HTTPD_TRUE@ imap/http_timezone.c \ @HTTPD_TRUE@ imap/httpd.c \ @HTTPD_TRUE@ imap/httpd.h \ @HTTPD_TRUE@ imap/jcal.c \ @HTTPD_TRUE@ imap/jcal.h \ @HTTPD_TRUE@ imap/json_support.h \ @HTTPD_TRUE@ imap/proxy.c \ @HTTPD_TRUE@ imap/proxy.h \ @HTTPD_TRUE@ imap/smtpclient.c \ @HTTPD_TRUE@ imap/smtpclient.h \ @HTTPD_TRUE@ imap/spool.c \ @HTTPD_TRUE@ imap/spool.h \ @HTTPD_TRUE@ imap/xcal.c \ @HTTPD_TRUE@ imap/xcal.h \ @HTTPD_TRUE@ imap/zoneinfo_db.c \ @HTTPD_TRUE@ imap/zoneinfo_db.h @HTTPD_TRUE@am__append_52 = \ @HTTPD_TRUE@ imap/http_err.c \ @HTTPD_TRUE@ imap/tz_err.c @AUTOCREATE_TRUE@am__append_53 = \ @AUTOCREATE_TRUE@ imap/autocreate.c \ @AUTOCREATE_TRUE@ imap/autocreate.h @SIEVE_TRUE@am__append_54 = imap/lmtp_sieve.c imap/lmtp_sieve.h imap/smtpclient.c @SIEVE_TRUE@am__append_55 = sieve/libcyrus_sieve.la @AUTOCREATE_TRUE@am__append_56 = \ @AUTOCREATE_TRUE@ imap/autocreate.c \ @AUTOCREATE_TRUE@ imap/autocreate.h @SIEVE_TRUE@am__append_57 = sieve/libcyrus_sieve.la @USE_BERKELEY_TRUE@am__append_58 = lib/cyrusdb_berkeley.c @USE_SQL_TRUE@am__append_59 = lib/cyrusdb_sql.c @GMTOFF_TM_TRUE@am__append_60 = lib/gmtoff_tm.c @GMTOFF_TM_FALSE@am__append_61 = lib/gmtoff_gmtime.c @NONBLOCK_FCNTL_TRUE@am__append_62 = lib/nonblock_fcntl.c @NONBLOCK_FCNTL_FALSE@am__append_63 = lib/nonblock_ioctl.c @IPV6_noGETADDRINFO_TRUE@am__append_64 = lib/getaddrinfo.c @IPV6_noGETNAMEINFO_TRUE@am__append_65 = lib/getnameinfo.c @LOCK_FCNTL_TRUE@am__append_66 = lib/lock_fcntl.c @LOCK_FCNTL_FALSE@am__append_67 = lib/lock_flock.c @MAP_SHARED_TRUE@am__append_68 = lib/map_shared.c @MAP_SHARED_FALSE@@MAP_STUPIDSHARED_TRUE@am__append_69 = lib/map_stupidshared.c @MAP_SHARED_FALSE@@MAP_STUPIDSHARED_FALSE@am__append_70 = lib/map_nommap.c @NNTPD_TRUE@am__append_71 = \ @NNTPD_TRUE@ man/fetchnews.8 \ @NNTPD_TRUE@ man/nntpd.8 @NNTPD_FALSE@am__append_72 = \ @NNTPD_FALSE@ man/fetchnews.8 \ @NNTPD_FALSE@ man/nntpd.8 @HTTPD_TRUE@am__append_73 = \ @HTTPD_TRUE@ man/ctl_zoneinfo.8 \ @HTTPD_TRUE@ man/httpd.8 @HTTPD_FALSE@am__append_74 = \ @HTTPD_FALSE@ man/ctl_zoneinfo.8 \ @HTTPD_FALSE@ man/httpd.8 @ZEPHYR_TRUE@am__append_75 = notifyd/notify_zephyr.c notifyd/notify_zephyr.h @HAVE_LDAP_TRUE@am__append_76 = ptclient/ldap.c @HAVE_LDAP_TRUE@am__append_77 = $(LDAP_LIBS) @HAVE_LDAP_TRUE@am__append_78 = $(LDAP_LDFLAGS) @USE_AFSKRB_TRUE@am__append_79 = ptclient/afskrb.c @USE_AFSKRB_TRUE@am__append_80 = $(AFS_LIBS) @USE_AFSKRB_TRUE@am__append_81 = $(AFS_LDFLAGS) subdir = . ACLOCAL_M4 = $(top_srcdir)/aclocal.m4 am__aclocal_m4_deps = $(top_srcdir)/cmulocal/berkdb.m4 \ $(top_srcdir)/cmulocal/bsd_sockets.m4 \ $(top_srcdir)/cmulocal/c-fpic.m4 \ $(top_srcdir)/cmulocal/common.m4 \ $(top_srcdir)/cmulocal/cyrus.m4 $(top_srcdir)/cmulocal/ipv6.m4 \ $(top_srcdir)/cmulocal/libtool.m4 \ $(top_srcdir)/cmulocal/libwrap.m4 \ $(top_srcdir)/cmulocal/ltoptions.m4 \ $(top_srcdir)/cmulocal/ltsugar.m4 \ $(top_srcdir)/cmulocal/ltversion.m4 \ $(top_srcdir)/cmulocal/lt~obsolete.m4 \ $(top_srcdir)/cmulocal/perlmake.m4 \ $(top_srcdir)/cmulocal/sasl2.m4 $(top_srcdir)/cmulocal/sql.m4 \ $(top_srcdir)/cmulocal/ucdsnmp.m4 \ $(top_srcdir)/cmulocal/visibility.m4 \ $(top_srcdir)/cmulocal/zlib.m4 $(top_srcdir)/configure.ac am__configure_deps = $(am__aclocal_m4_deps) $(CONFIGURE_DEPENDENCIES) \ $(ACLOCAL_M4) DIST_COMMON = $(srcdir)/Makefile.am $(top_srcdir)/configure \ $(am__configure_deps) $(dist_noinst_SCRIPTS) \ $(am__dist_sysconf_DATA_DIST) $(include_HEADERS) \ $(nobase_include_HEADERS) $(noinst_HEADERS) $(am__DIST_COMMON) am__CONFIG_DISTCLEAN_FILES = config.status config.cache config.log \ configure.lineno config.status.lineno mkinstalldirs = $(install_sh) -d CONFIG_HEADER = config.h CONFIG_CLEAN_FILES = libcyrus_min.pc libcyrus.pc libcyrus_sieve.pc \ perl/annotator/Makefile.PL perl/imap/Makefile.PL \ perl/sieve/managesieve/Makefile.PL CONFIG_CLEAN_VPATH_FILES = LIBRARIES = $(noinst_LIBRARIES) ARFLAGS = cru AM_V_AR = $(am__v_AR_@AM_V@) am__v_AR_ = $(am__v_AR_@AM_DEFAULT_V@) am__v_AR_0 = @echo " AR " $@; am__v_AR_1 = perl_sieve_lib_libisieve_a_AR = $(AR) $(ARFLAGS) perl_sieve_lib_libisieve_a_LIBADD = am__dirstamp = $(am__leading_dot)dirstamp am_perl_sieve_lib_libisieve_a_OBJECTS = \ perl/sieve/lib/isieve.$(OBJEXT) perl/sieve/lib/lex.$(OBJEXT) \ perl/sieve/lib/request.$(OBJEXT) perl_sieve_lib_libisieve_a_OBJECTS = \ $(am_perl_sieve_lib_libisieve_a_OBJECTS) am__vpath_adj_setup = srcdirstrip=`echo "$(srcdir)" | sed 's|.|.|g'`; am__vpath_adj = case $$p in \ $(srcdir)/*) f=`echo "$$p" | sed "s|^$$srcdirstrip/||"`;; \ *) f=$$p;; \ esac; am__strip_dir = f=`echo $$p | sed -e 's|^.*/||'`; am__install_max = 40 am__nobase_strip_setup = \ srcdirstrip=`echo "$(srcdir)" | sed 's/[].[^$$\\*|]/\\\\&/g'` am__nobase_strip = \ for p in $$list; do echo "$$p"; done | sed -e "s|$$srcdirstrip/||" am__nobase_list = $(am__nobase_strip_setup); \ for p in $$list; do echo "$$p $$p"; done | \ sed "s| $$srcdirstrip/| |;"' / .*\//!s/ .*/ ./; s,\( .*\)/[^/]*$$,\1,' | \ $(AWK) 'BEGIN { files["."] = "" } { files[$$2] = files[$$2] " " $$1; \ if (++n[$$2] == $(am__install_max)) \ { print $$2, files[$$2]; n[$$2] = 0; files[$$2] = "" } } \ END { for (dir in files) print dir, files[dir] }' am__base_list = \ sed '$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;s/\n/ /g' | \ sed '$$!N;$$!N;$$!N;$$!N;s/\n/ /g' am__uninstall_files_from_dir = { \ test -z "$$files" \ || { test ! -d "$$dir" && test ! -f "$$dir" && test ! -r "$$dir"; } \ || { echo " ( cd '$$dir' && rm -f" $$files ")"; \ $(am__cd) "$$dir" && rm -f $$files; }; \ } am__installdirs = "$(DESTDIR)$(libdir)" "$(DESTDIR)$(bindir)" \ "$(DESTDIR)$(servicedir)" "$(DESTDIR)$(userdir)" \ "$(DESTDIR)$(man1dir)" "$(DESTDIR)$(man3dir)" \ "$(DESTDIR)$(man5dir)" "$(DESTDIR)$(man8dir)" \ "$(DESTDIR)$(sysconfdir)" "$(DESTDIR)$(pkgconfigdir)" \ "$(DESTDIR)$(includedir)" "$(DESTDIR)$(includedir)" \ "$(DESTDIR)$(includedir)" "$(DESTDIR)$(includedir)" LTLIBRARIES = $(lib_LTLIBRARIES) $(noinst_LTLIBRARIES) com_err_et_libcyrus_com_err_la_LIBADD = am_com_err_et_libcyrus_com_err_la_OBJECTS = \ com_err/et/com_err_et_libcyrus_com_err_la-com_err.lo \ com_err/et/com_err_et_libcyrus_com_err_la-error_message.lo \ com_err/et/com_err_et_libcyrus_com_err_la-et_name.lo \ com_err/et/com_err_et_libcyrus_com_err_la-init_et.lo com_err_et_libcyrus_com_err_la_OBJECTS = \ $(am_com_err_et_libcyrus_com_err_la_OBJECTS) AM_V_lt = $(am__v_lt_@AM_V@) am__v_lt_ = $(am__v_lt_@AM_DEFAULT_V@) am__v_lt_0 = --silent am__v_lt_1 = com_err_et_libcyrus_com_err_la_LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC \ $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=link $(CCLD) \ $(com_err_et_libcyrus_com_err_la_CFLAGS) $(CFLAGS) \ $(AM_LDFLAGS) $(LDFLAGS) -o $@ @COM_ERR_TRUE@am_com_err_et_libcyrus_com_err_la_rpath = -rpath \ @COM_ERR_TRUE@ $(libdir) am__DEPENDENCIES_1 = @JANSSON_TRUE@am__DEPENDENCIES_2 = $(am__DEPENDENCIES_1) imap_libcyrus_imap_la_DEPENDENCIES = $(am__DEPENDENCIES_1) \ $(am__DEPENDENCIES_1) lib/libcyrus_min.la lib/libcyrus.la \ $(am__DEPENDENCIES_2) am__imap_libcyrus_imap_la_SOURCES_DIST = imap/annotate.c \ imap/annotate.h imap/append.c imap/append.h imap/backend.c \ imap/backend.h imap/convert_code.c imap/convert_code.h \ imap/dlist.c imap/dlist.h imap/duplicate.c imap/duplicate.h \ imap/global.c imap/global.h imap/idle.c imap/idle.h \ imap/idlemsg.c imap/idlemsg.h imap/imapparse.c imap/index.c \ imap/index.h imap/mailbox.c imap/mailbox.h imap/mbdump.c \ imap/mbdump.h imap/mboxkey.c imap/mboxkey.h imap/mboxlist.c \ imap/mboxlist.h imap/mboxevent.c imap/mboxevent.h \ imap/mboxname.c imap/mboxname.h imap/message_guid.c \ imap/message_guid.h imap/message.c imap/message.h \ imap/mupdate-client.c imap/mupdate-client.h imap/mutex.h \ imap/notify.c imap/notify.h imap/partlist.c imap/partlist.h \ imap/proc.c imap/proc.h imap/protocol.h imap/quota_db.c \ imap/rfc822_header.c imap/rfc822_header.h imap/saslclient.c \ imap/saslclient.h imap/saslserver.c imap/search_engines.c \ imap/search_engines.h imap/seen.h imap/seen_db.c \ imap/sequence.c imap/sequence.h imap/setproctitle.c \ imap/squat.c imap/squat.h imap/squat_internal.c \ imap/squat_internal.h imap/statuscache.h imap/statuscache_db.c \ imap/sync_log.c imap/sync_log.h imap/telemetry.c \ imap/telemetry.h imap/tls.c imap/tls.h imap/tls_th-lock.c \ imap/tls_th-lock.h imap/user.c imap/user.h imap/userdeny_db.c \ imap/userdeny.h imap/version.c imap/version.h imap/caldav_db.c \ imap/caldav_db.h imap/carddav_db.c imap/carddav_db.h \ imap/dav_db.c imap/dav_db.h imap/dav_util.c imap/dav_util.h \ imap/http_caldav.c imap/http_caldav_sched.h \ imap/http_carddav.c imap/http_client.c imap/http_client.h \ imap/http_dav.c imap/http_dav.h imap/http_dblookup.c \ imap/http_ischedule.c imap/http_proxy.c imap/http_proxy.h \ imap/http_rss.c imap/http_timezone.c imap/httpd.c imap/httpd.h \ imap/jcal.c imap/jcal.h imap/json_support.h imap/proxy.c \ imap/proxy.h imap/smtpclient.c imap/smtpclient.h imap/spool.c \ imap/spool.h imap/xcal.c imap/xcal.h imap/zoneinfo_db.c \ imap/zoneinfo_db.h @HTTPD_TRUE@am__objects_1 = imap/imap_libcyrus_imap_la-caldav_db.lo \ @HTTPD_TRUE@ imap/imap_libcyrus_imap_la-carddav_db.lo \ @HTTPD_TRUE@ imap/imap_libcyrus_imap_la-dav_db.lo \ @HTTPD_TRUE@ imap/imap_libcyrus_imap_la-dav_util.lo \ @HTTPD_TRUE@ imap/imap_libcyrus_imap_la-http_caldav.lo \ @HTTPD_TRUE@ imap/imap_libcyrus_imap_la-http_carddav.lo \ @HTTPD_TRUE@ imap/imap_libcyrus_imap_la-http_client.lo \ @HTTPD_TRUE@ imap/imap_libcyrus_imap_la-http_dav.lo \ @HTTPD_TRUE@ imap/imap_libcyrus_imap_la-http_dblookup.lo \ @HTTPD_TRUE@ imap/imap_libcyrus_imap_la-http_ischedule.lo \ @HTTPD_TRUE@ imap/imap_libcyrus_imap_la-http_proxy.lo \ @HTTPD_TRUE@ imap/imap_libcyrus_imap_la-http_rss.lo \ @HTTPD_TRUE@ imap/imap_libcyrus_imap_la-http_timezone.lo \ @HTTPD_TRUE@ imap/imap_libcyrus_imap_la-httpd.lo \ @HTTPD_TRUE@ imap/imap_libcyrus_imap_la-jcal.lo \ @HTTPD_TRUE@ imap/imap_libcyrus_imap_la-proxy.lo \ @HTTPD_TRUE@ imap/imap_libcyrus_imap_la-smtpclient.lo \ @HTTPD_TRUE@ imap/imap_libcyrus_imap_la-spool.lo \ @HTTPD_TRUE@ imap/imap_libcyrus_imap_la-xcal.lo \ @HTTPD_TRUE@ imap/imap_libcyrus_imap_la-zoneinfo_db.lo am_imap_libcyrus_imap_la_OBJECTS = \ imap/imap_libcyrus_imap_la-annotate.lo \ imap/imap_libcyrus_imap_la-append.lo \ imap/imap_libcyrus_imap_la-backend.lo \ imap/imap_libcyrus_imap_la-convert_code.lo \ imap/imap_libcyrus_imap_la-dlist.lo \ imap/imap_libcyrus_imap_la-duplicate.lo \ imap/imap_libcyrus_imap_la-global.lo \ imap/imap_libcyrus_imap_la-idle.lo \ imap/imap_libcyrus_imap_la-idlemsg.lo \ imap/imap_libcyrus_imap_la-imapparse.lo \ imap/imap_libcyrus_imap_la-index.lo \ imap/imap_libcyrus_imap_la-mailbox.lo \ imap/imap_libcyrus_imap_la-mbdump.lo \ imap/imap_libcyrus_imap_la-mboxkey.lo \ imap/imap_libcyrus_imap_la-mboxlist.lo \ imap/imap_libcyrus_imap_la-mboxevent.lo \ imap/imap_libcyrus_imap_la-mboxname.lo \ imap/imap_libcyrus_imap_la-message_guid.lo \ imap/imap_libcyrus_imap_la-message.lo \ imap/imap_libcyrus_imap_la-mupdate-client.lo \ imap/imap_libcyrus_imap_la-notify.lo \ imap/imap_libcyrus_imap_la-partlist.lo \ imap/imap_libcyrus_imap_la-proc.lo \ imap/imap_libcyrus_imap_la-quota_db.lo \ imap/imap_libcyrus_imap_la-rfc822_header.lo \ imap/imap_libcyrus_imap_la-saslclient.lo \ imap/imap_libcyrus_imap_la-saslserver.lo \ imap/imap_libcyrus_imap_la-search_engines.lo \ imap/imap_libcyrus_imap_la-seen_db.lo \ imap/imap_libcyrus_imap_la-sequence.lo \ imap/imap_libcyrus_imap_la-setproctitle.lo \ imap/imap_libcyrus_imap_la-squat.lo \ imap/imap_libcyrus_imap_la-squat_internal.lo \ imap/imap_libcyrus_imap_la-statuscache_db.lo \ imap/imap_libcyrus_imap_la-sync_log.lo \ imap/imap_libcyrus_imap_la-telemetry.lo \ imap/imap_libcyrus_imap_la-tls.lo \ imap/imap_libcyrus_imap_la-tls_th-lock.lo \ imap/imap_libcyrus_imap_la-user.lo \ imap/imap_libcyrus_imap_la-userdeny_db.lo \ imap/imap_libcyrus_imap_la-version.lo $(am__objects_1) dist_imap_libcyrus_imap_la_OBJECTS = @HTTPD_TRUE@am__objects_2 = imap/imap_libcyrus_imap_la-http_err.lo \ @HTTPD_TRUE@ imap/imap_libcyrus_imap_la-tz_err.lo nodist_imap_libcyrus_imap_la_OBJECTS = \ imap/imap_libcyrus_imap_la-imap_err.lo \ imap/imap_libcyrus_imap_la-mupdate_err.lo $(am__objects_2) imap_libcyrus_imap_la_OBJECTS = $(am_imap_libcyrus_imap_la_OBJECTS) \ $(dist_imap_libcyrus_imap_la_OBJECTS) \ $(nodist_imap_libcyrus_imap_la_OBJECTS) imap_libcyrus_imap_la_LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC \ $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=link $(CCLD) \ $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) $(AM_LDFLAGS) \ $(LDFLAGS) -o $@ @SERVER_TRUE@am_imap_libcyrus_imap_la_rpath = -rpath $(libdir) lib_libcyrus_la_DEPENDENCIES = $(am__DEPENDENCIES_1) \ $(am__DEPENDENCIES_1) $(am__DEPENDENCIES_1) am__lib_libcyrus_la_SOURCES_DIST = lib/acl.c lib/acl_afs.c lib/auth.c \ lib/auth_krb.c lib/auth_krb5.c lib/auth_pts.c lib/auth_unix.c \ lib/bitvector.c lib/bsearch.c lib/byteorder64.c lib/charset.c \ lib/command.c lib/crc32.c lib/cyrusdb.c lib/cyrusdb_flat.c \ lib/cyrusdb_quotalegacy.c lib/cyrusdb_skiplist.c \ lib/cyrusdb_twoskip.c lib/glob.c lib/imapurl.c lib/imclient.c \ lib/imparse.c lib/iostat.c lib/iptostring.c lib/libcyr_cfg.c \ lib/lsort.c lib/mappedfile.c lib/mkgmtime.c lib/parseaddr.c \ lib/prot.c lib/ptrarray.c lib/rfc822tok.c lib/signals.c \ lib/stristr.c lib/times.c lib/tok.c lib/wildmat.c \ lib/cyrusdb_berkeley.c lib/cyrusdb_sql.c lib/gmtoff_tm.c \ lib/gmtoff_gmtime.c lib/nonblock_fcntl.c lib/nonblock_ioctl.c @USE_BERKELEY_TRUE@am__objects_3 = \ @USE_BERKELEY_TRUE@ lib/lib_libcyrus_la-cyrusdb_berkeley.lo @USE_SQL_TRUE@am__objects_4 = lib/lib_libcyrus_la-cyrusdb_sql.lo @GMTOFF_TM_TRUE@am__objects_5 = lib/lib_libcyrus_la-gmtoff_tm.lo @GMTOFF_TM_FALSE@am__objects_6 = lib/lib_libcyrus_la-gmtoff_gmtime.lo @NONBLOCK_FCNTL_TRUE@am__objects_7 = \ @NONBLOCK_FCNTL_TRUE@ lib/lib_libcyrus_la-nonblock_fcntl.lo @NONBLOCK_FCNTL_FALSE@am__objects_8 = \ @NONBLOCK_FCNTL_FALSE@ lib/lib_libcyrus_la-nonblock_ioctl.lo am_lib_libcyrus_la_OBJECTS = lib/lib_libcyrus_la-acl.lo \ lib/lib_libcyrus_la-acl_afs.lo lib/lib_libcyrus_la-auth.lo \ lib/lib_libcyrus_la-auth_krb.lo \ lib/lib_libcyrus_la-auth_krb5.lo \ lib/lib_libcyrus_la-auth_pts.lo \ lib/lib_libcyrus_la-auth_unix.lo \ lib/lib_libcyrus_la-bitvector.lo \ lib/lib_libcyrus_la-bsearch.lo \ lib/lib_libcyrus_la-byteorder64.lo \ lib/lib_libcyrus_la-charset.lo lib/lib_libcyrus_la-command.lo \ lib/lib_libcyrus_la-crc32.lo lib/lib_libcyrus_la-cyrusdb.lo \ lib/lib_libcyrus_la-cyrusdb_flat.lo \ lib/lib_libcyrus_la-cyrusdb_quotalegacy.lo \ lib/lib_libcyrus_la-cyrusdb_skiplist.lo \ lib/lib_libcyrus_la-cyrusdb_twoskip.lo \ lib/lib_libcyrus_la-glob.lo lib/lib_libcyrus_la-imapurl.lo \ lib/lib_libcyrus_la-imclient.lo lib/lib_libcyrus_la-imparse.lo \ lib/lib_libcyrus_la-iostat.lo \ lib/lib_libcyrus_la-iptostring.lo \ lib/lib_libcyrus_la-libcyr_cfg.lo lib/lib_libcyrus_la-lsort.lo \ lib/lib_libcyrus_la-mappedfile.lo \ lib/lib_libcyrus_la-mkgmtime.lo \ lib/lib_libcyrus_la-parseaddr.lo lib/lib_libcyrus_la-prot.lo \ lib/lib_libcyrus_la-ptrarray.lo \ lib/lib_libcyrus_la-rfc822tok.lo \ lib/lib_libcyrus_la-signals.lo lib/lib_libcyrus_la-stristr.lo \ lib/lib_libcyrus_la-times.lo lib/lib_libcyrus_la-tok.lo \ lib/lib_libcyrus_la-wildmat.lo $(am__objects_3) \ $(am__objects_4) $(am__objects_5) $(am__objects_6) \ $(am__objects_7) $(am__objects_8) nodist_lib_libcyrus_la_OBJECTS = lib/lib_libcyrus_la-chartable.lo lib_libcyrus_la_OBJECTS = $(am_lib_libcyrus_la_OBJECTS) \ $(nodist_lib_libcyrus_la_OBJECTS) lib_libcyrus_la_LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC \ $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=link $(CCLD) \ $(lib_libcyrus_la_CFLAGS) $(CFLAGS) $(AM_LDFLAGS) $(LDFLAGS) \ -o $@ LIBOBJDIR = lib/ lib_libcyrus_min_la_DEPENDENCIES = $(LTLIBOBJS) am__lib_libcyrus_min_la_SOURCES_DIST = lib/arrayu64.c lib/assert.c \ lib/hash.c lib/hashu64.c lib/libconfig.c lib/mpool.c \ lib/retry.c lib/strarray.c lib/strhash.c lib/util.c \ lib/vparse.c lib/xmalloc.c lib/xstrlcat.c lib/xstrlcpy.c \ lib/getaddrinfo.c lib/getnameinfo.c lib/lock_fcntl.c \ lib/lock_flock.c lib/map_shared.c lib/map_stupidshared.c \ lib/map_nommap.c @IPV6_noGETADDRINFO_TRUE@am__objects_9 = lib/lib_libcyrus_min_la-getaddrinfo.lo @IPV6_noGETNAMEINFO_TRUE@am__objects_10 = lib/lib_libcyrus_min_la-getnameinfo.lo @LOCK_FCNTL_TRUE@am__objects_11 = \ @LOCK_FCNTL_TRUE@ lib/lib_libcyrus_min_la-lock_fcntl.lo @LOCK_FCNTL_FALSE@am__objects_12 = \ @LOCK_FCNTL_FALSE@ lib/lib_libcyrus_min_la-lock_flock.lo @MAP_SHARED_TRUE@am__objects_13 = \ @MAP_SHARED_TRUE@ lib/lib_libcyrus_min_la-map_shared.lo @MAP_SHARED_FALSE@@MAP_STUPIDSHARED_TRUE@am__objects_14 = lib/lib_libcyrus_min_la-map_stupidshared.lo @MAP_SHARED_FALSE@@MAP_STUPIDSHARED_FALSE@am__objects_15 = lib/lib_libcyrus_min_la-map_nommap.lo am_lib_libcyrus_min_la_OBJECTS = lib/lib_libcyrus_min_la-arrayu64.lo \ lib/lib_libcyrus_min_la-assert.lo \ lib/lib_libcyrus_min_la-hash.lo \ lib/lib_libcyrus_min_la-hashu64.lo \ lib/lib_libcyrus_min_la-libconfig.lo \ lib/lib_libcyrus_min_la-mpool.lo \ lib/lib_libcyrus_min_la-retry.lo \ lib/lib_libcyrus_min_la-strarray.lo \ lib/lib_libcyrus_min_la-strhash.lo \ lib/lib_libcyrus_min_la-util.lo \ lib/lib_libcyrus_min_la-vparse.lo \ lib/lib_libcyrus_min_la-xmalloc.lo \ lib/lib_libcyrus_min_la-xstrlcat.lo \ lib/lib_libcyrus_min_la-xstrlcpy.lo $(am__objects_9) \ $(am__objects_10) $(am__objects_11) $(am__objects_12) \ $(am__objects_13) $(am__objects_14) $(am__objects_15) nodist_lib_libcyrus_min_la_OBJECTS = \ lib/lib_libcyrus_min_la-imapopts.lo lib_libcyrus_min_la_OBJECTS = $(am_lib_libcyrus_min_la_OBJECTS) \ $(nodist_lib_libcyrus_min_la_OBJECTS) lib_libcyrus_min_la_LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC \ $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=link $(CCLD) \ $(lib_libcyrus_min_la_CFLAGS) $(CFLAGS) $(AM_LDFLAGS) \ $(LDFLAGS) -o $@ am__DEPENDENCIES_3 = $(am__DEPENDENCIES_1) $(am__DEPENDENCIES_1) \ $(am__DEPENDENCIES_1) perl_libcyrus_la_DEPENDENCIES = $(am__DEPENDENCIES_3) am__perl_libcyrus_la_SOURCES_DIST = lib/acl.c lib/acl_afs.c lib/auth.c \ lib/auth_krb.c lib/auth_krb5.c lib/auth_pts.c lib/auth_unix.c \ lib/bitvector.c lib/bsearch.c lib/byteorder64.c lib/charset.c \ lib/command.c lib/crc32.c lib/cyrusdb.c lib/cyrusdb_flat.c \ lib/cyrusdb_quotalegacy.c lib/cyrusdb_skiplist.c \ lib/cyrusdb_twoskip.c lib/glob.c lib/imapurl.c lib/imclient.c \ lib/imparse.c lib/iostat.c lib/iptostring.c lib/libcyr_cfg.c \ lib/lsort.c lib/mappedfile.c lib/mkgmtime.c lib/parseaddr.c \ lib/prot.c lib/ptrarray.c lib/rfc822tok.c lib/signals.c \ lib/stristr.c lib/times.c lib/tok.c lib/wildmat.c \ lib/cyrusdb_berkeley.c lib/cyrusdb_sql.c lib/gmtoff_tm.c \ lib/gmtoff_gmtime.c lib/nonblock_fcntl.c lib/nonblock_ioctl.c @USE_BERKELEY_TRUE@am__objects_16 = lib/cyrusdb_berkeley.lo @USE_SQL_TRUE@am__objects_17 = lib/cyrusdb_sql.lo @GMTOFF_TM_TRUE@am__objects_18 = lib/gmtoff_tm.lo @GMTOFF_TM_FALSE@am__objects_19 = lib/gmtoff_gmtime.lo @NONBLOCK_FCNTL_TRUE@am__objects_20 = lib/nonblock_fcntl.lo @NONBLOCK_FCNTL_FALSE@am__objects_21 = lib/nonblock_ioctl.lo am__objects_22 = lib/acl.lo lib/acl_afs.lo lib/auth.lo lib/auth_krb.lo \ lib/auth_krb5.lo lib/auth_pts.lo lib/auth_unix.lo \ lib/bitvector.lo lib/bsearch.lo lib/byteorder64.lo \ lib/charset.lo lib/command.lo lib/crc32.lo lib/cyrusdb.lo \ lib/cyrusdb_flat.lo lib/cyrusdb_quotalegacy.lo \ lib/cyrusdb_skiplist.lo lib/cyrusdb_twoskip.lo lib/glob.lo \ lib/imapurl.lo lib/imclient.lo lib/imparse.lo lib/iostat.lo \ lib/iptostring.lo lib/libcyr_cfg.lo lib/lsort.lo \ lib/mappedfile.lo lib/mkgmtime.lo lib/parseaddr.lo lib/prot.lo \ lib/ptrarray.lo lib/rfc822tok.lo lib/signals.lo lib/stristr.lo \ lib/times.lo lib/tok.lo lib/wildmat.lo $(am__objects_16) \ $(am__objects_17) $(am__objects_18) $(am__objects_19) \ $(am__objects_20) $(am__objects_21) am_perl_libcyrus_la_OBJECTS = $(am__objects_22) perl_libcyrus_la_OBJECTS = $(am_perl_libcyrus_la_OBJECTS) @PERL_TRUE@am_perl_libcyrus_la_rpath = perl_libcyrus_min_la_DEPENDENCIES = $(lib_libcyrus_min_la_LIBADD) am__perl_libcyrus_min_la_SOURCES_DIST = lib/arrayu64.c lib/assert.c \ lib/hash.c lib/hashu64.c lib/libconfig.c lib/mpool.c \ lib/retry.c lib/strarray.c lib/strhash.c lib/util.c \ lib/vparse.c lib/xmalloc.c lib/xstrlcat.c lib/xstrlcpy.c \ lib/getaddrinfo.c lib/getnameinfo.c lib/lock_fcntl.c \ lib/lock_flock.c lib/map_shared.c lib/map_stupidshared.c \ lib/map_nommap.c @IPV6_noGETADDRINFO_TRUE@am__objects_23 = lib/getaddrinfo.lo @IPV6_noGETNAMEINFO_TRUE@am__objects_24 = lib/getnameinfo.lo @LOCK_FCNTL_TRUE@am__objects_25 = lib/lock_fcntl.lo @LOCK_FCNTL_FALSE@am__objects_26 = lib/lock_flock.lo @MAP_SHARED_TRUE@am__objects_27 = lib/map_shared.lo @MAP_SHARED_FALSE@@MAP_STUPIDSHARED_TRUE@am__objects_28 = lib/map_stupidshared.lo @MAP_SHARED_FALSE@@MAP_STUPIDSHARED_FALSE@am__objects_29 = \ @MAP_SHARED_FALSE@@MAP_STUPIDSHARED_FALSE@ lib/map_nommap.lo am__objects_30 = lib/arrayu64.lo lib/assert.lo lib/hash.lo \ lib/hashu64.lo lib/libconfig.lo lib/mpool.lo lib/retry.lo \ lib/strarray.lo lib/strhash.lo lib/util.lo lib/vparse.lo \ lib/xmalloc.lo lib/xstrlcat.lo lib/xstrlcpy.lo \ $(am__objects_23) $(am__objects_24) $(am__objects_25) \ $(am__objects_26) $(am__objects_27) $(am__objects_28) \ $(am__objects_29) am_perl_libcyrus_min_la_OBJECTS = $(am__objects_30) perl_libcyrus_min_la_OBJECTS = $(am_perl_libcyrus_min_la_OBJECTS) @PERL_TRUE@am_perl_libcyrus_min_la_rpath = sieve_libcyrus_sieve_la_DEPENDENCIES = sieve/libcyrus_sieve_lex.la \ $(am__DEPENDENCIES_1) lib/libcyrus_min.la lib/libcyrus.la am_sieve_libcyrus_sieve_la_OBJECTS = \ sieve/sieve_libcyrus_sieve_la-addr.lo \ sieve/sieve_libcyrus_sieve_la-bc_dump.lo \ sieve/sieve_libcyrus_sieve_la-bc_emit.lo \ sieve/sieve_libcyrus_sieve_la-bc_eval.lo \ sieve/sieve_libcyrus_sieve_la-bc_generate.lo \ sieve/sieve_libcyrus_sieve_la-comparator.lo \ sieve/sieve_libcyrus_sieve_la-flags.lo \ sieve/sieve_libcyrus_sieve_la-interp.lo \ sieve/sieve_libcyrus_sieve_la-message.lo \ sieve/sieve_libcyrus_sieve_la-script.lo \ sieve/sieve_libcyrus_sieve_la-sieve.lo \ sieve/sieve_libcyrus_sieve_la-tree.lo \ sieve/sieve_libcyrus_sieve_la-varlist.lo nodist_sieve_libcyrus_sieve_la_OBJECTS = \ sieve/sieve_libcyrus_sieve_la-sieve_err.lo sieve_libcyrus_sieve_la_OBJECTS = \ $(am_sieve_libcyrus_sieve_la_OBJECTS) \ $(nodist_sieve_libcyrus_sieve_la_OBJECTS) sieve_libcyrus_sieve_la_LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC \ $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=link $(CCLD) \ $(sieve_libcyrus_sieve_la_CFLAGS) $(CFLAGS) $(AM_LDFLAGS) \ $(LDFLAGS) -o $@ @SIEVE_TRUE@am_sieve_libcyrus_sieve_la_rpath = -rpath $(libdir) sieve_libcyrus_sieve_lex_la_DEPENDENCIES = am_sieve_libcyrus_sieve_lex_la_OBJECTS = \ sieve/sieve_libcyrus_sieve_lex_la-addr-lex.lo \ sieve/sieve_libcyrus_sieve_lex_la-sieve-lex.lo sieve_libcyrus_sieve_lex_la_OBJECTS = \ $(am_sieve_libcyrus_sieve_lex_la_OBJECTS) sieve_libcyrus_sieve_lex_la_LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC \ $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=link $(CCLD) \ $(sieve_libcyrus_sieve_lex_la_CFLAGS) $(CFLAGS) $(AM_LDFLAGS) \ $(LDFLAGS) -o $@ @SIEVE_TRUE@am_sieve_libcyrus_sieve_lex_la_rpath = @SERVER_TRUE@@SIEVE_TRUE@am__EXEEXT_1 = notifyd/notifytest$(EXEEXT) @SIEVE_TRUE@am__EXEEXT_2 = sieve/test$(EXEEXT) @CUNIT_TRUE@am__EXEEXT_3 = cunit/unit$(EXEEXT) @SERVER_TRUE@am__EXEEXT_4 = imap/imapd$(EXEEXT) imap/lmtpd$(EXEEXT) \ @SERVER_TRUE@ imap/pop3d$(EXEEXT) imap/smmapd$(EXEEXT) @NNTPD_TRUE@@SERVER_TRUE@am__EXEEXT_5 = imap/nntpd$(EXEEXT) @SERVER_TRUE@am__EXEEXT_6 = imap/fud$(EXEEXT) @MURDER_TRUE@@SERVER_TRUE@am__EXEEXT_7 = imap/mupdate$(EXEEXT) @HTTPD_TRUE@@SERVER_TRUE@am__EXEEXT_8 = imap/httpd$(EXEEXT) @REPLICATION_TRUE@@SERVER_TRUE@am__EXEEXT_9 = \ @REPLICATION_TRUE@@SERVER_TRUE@ imap/sync_server$(EXEEXT) @SERVER_TRUE@@SIEVE_TRUE@am__EXEEXT_10 = notifyd/notifyd$(EXEEXT) @PTCLIENT_TRUE@am__EXEEXT_11 = ptclient/ptloader$(EXEEXT) @SERVER_TRUE@@SIEVE_TRUE@am__EXEEXT_12 = timsieved/timsieved$(EXEEXT) @SERVER_TRUE@am__EXEEXT_13 = imap/arbitron$(EXEEXT) \ @SERVER_TRUE@ imap/chk_cyrus$(EXEEXT) imap/ctl_cyrusdb$(EXEEXT) \ @SERVER_TRUE@ imap/ctl_deliver$(EXEEXT) \ @SERVER_TRUE@ imap/ctl_mboxlist$(EXEEXT) \ @SERVER_TRUE@ imap/cvt_cyrusdb$(EXEEXT) imap/cyr_df$(EXEEXT) \ @SERVER_TRUE@ imap/cyrdump$(EXEEXT) imap/cyr_dbtool$(EXEEXT) \ @SERVER_TRUE@ imap/cyr_deny$(EXEEXT) imap/cyr_expire$(EXEEXT) \ @SERVER_TRUE@ imap/cyr_info$(EXEEXT) imap/cyr_sequence$(EXEEXT) \ @SERVER_TRUE@ imap/cyr_synclog$(EXEEXT) \ @SERVER_TRUE@ imap/cyr_userseen$(EXEEXT) imap/deliver$(EXEEXT) \ @SERVER_TRUE@ imap/ipurge$(EXEEXT) imap/mbexamine$(EXEEXT) \ @SERVER_TRUE@ imap/mbpath$(EXEEXT) imap/mbtool$(EXEEXT) \ @SERVER_TRUE@ imap/quota$(EXEEXT) imap/reconstruct$(EXEEXT) \ @SERVER_TRUE@ imap/squatter$(EXEEXT) @HAVE_CLAMAV_TRUE@@SERVER_TRUE@am__EXEEXT_14 = \ @HAVE_CLAMAV_TRUE@@SERVER_TRUE@ imap/cyr_virusscan$(EXEEXT) @NNTPD_TRUE@@SERVER_TRUE@am__EXEEXT_15 = imap/fetchnews$(EXEEXT) @IDLED_TRUE@@SERVER_TRUE@am__EXEEXT_16 = imap/idled$(EXEEXT) @HTTPD_TRUE@@SERVER_TRUE@am__EXEEXT_17 = imap/ctl_zoneinfo$(EXEEXT) \ @HTTPD_TRUE@@SERVER_TRUE@ imap/dav_reconstruct$(EXEEXT) @REPLICATION_TRUE@@SERVER_TRUE@am__EXEEXT_18 = \ @REPLICATION_TRUE@@SERVER_TRUE@ imap/sync_client$(EXEEXT) \ @REPLICATION_TRUE@@SERVER_TRUE@ imap/sync_reset$(EXEEXT) @HAVE_SSL_TRUE@@SERVER_TRUE@am__EXEEXT_19 = imap/tls_prune$(EXEEXT) @SERVER_TRUE@am__EXEEXT_20 = imap/unexpunge$(EXEEXT) \ @SERVER_TRUE@ master/master$(EXEEXT) @CMULOCAL_TRUE@am__EXEEXT_21 = netnews/remotepurge$(EXEEXT) @PTCLIENT_TRUE@am__EXEEXT_22 = ptclient/ptdump$(EXEEXT) \ @PTCLIENT_TRUE@ ptclient/ptexpire$(EXEEXT) @SIEVE_TRUE@am__EXEEXT_23 = sieve/sievec$(EXEEXT) \ @SIEVE_TRUE@ sieve/sieved$(EXEEXT) PROGRAMS = $(bin_PROGRAMS) $(service_PROGRAMS) $(user_PROGRAMS) am__cunit_unit_SOURCES_DIST = cunit/unit.c cunit/cunit.h \ cunit/syslog.c cunit/cunit-syslog.h cunit/timeout.c \ cunit/timeout.h cunit/annotate.testc cunit/backend.testc \ cunit/binhex.testc cunit/bitvector.testc cunit/buf.testc \ cunit/byteorder64.testc cunit/charset.testc cunit/crc32.testc \ cunit/db.testc cunit/dlist.testc cunit/duplicate.testc \ cunit/getxstring.testc cunit/glob.testc cunit/guid.testc \ cunit/hash.testc cunit/imapurl.testc cunit/mboxname.testc \ cunit/md5.testc cunit/message.testc cunit/msgid.testc \ cunit/parseaddr.testc cunit/parse.testc cunit/prot.testc \ cunit/ptrarray.testc cunit/quota.testc cunit/rfc822tok.testc \ cunit/sieve.testc cunit/spool.testc cunit/squat.testc \ cunit/strarray.testc cunit/strconcat.testc cunit/times.testc \ cunit/tok.testc imap/mutex_fake.c imap/spool.c @CUNIT_TRUE@am__objects_31 = cunit/unit.$(OBJEXT) \ @CUNIT_TRUE@ cunit/syslog.$(OBJEXT) cunit/timeout.$(OBJEXT) @CUNIT_TRUE@@SIEVE_TRUE@am__objects_32 = cunit/sieve.$(OBJEXT) @CUNIT_TRUE@am__objects_33 = cunit/annotate.$(OBJEXT) \ @CUNIT_TRUE@ cunit/backend.$(OBJEXT) cunit/binhex.$(OBJEXT) \ @CUNIT_TRUE@ cunit/bitvector.$(OBJEXT) cunit/buf.$(OBJEXT) \ @CUNIT_TRUE@ cunit/byteorder64.$(OBJEXT) \ @CUNIT_TRUE@ cunit/charset.$(OBJEXT) cunit/crc32.$(OBJEXT) \ @CUNIT_TRUE@ cunit/db.$(OBJEXT) cunit/dlist.$(OBJEXT) \ @CUNIT_TRUE@ cunit/duplicate.$(OBJEXT) \ @CUNIT_TRUE@ cunit/getxstring.$(OBJEXT) cunit/glob.$(OBJEXT) \ @CUNIT_TRUE@ cunit/guid.$(OBJEXT) cunit/hash.$(OBJEXT) \ @CUNIT_TRUE@ cunit/imapurl.$(OBJEXT) cunit/mboxname.$(OBJEXT) \ @CUNIT_TRUE@ cunit/md5.$(OBJEXT) cunit/message.$(OBJEXT) \ @CUNIT_TRUE@ cunit/msgid.$(OBJEXT) cunit/parseaddr.$(OBJEXT) \ @CUNIT_TRUE@ cunit/parse.$(OBJEXT) cunit/prot.$(OBJEXT) \ @CUNIT_TRUE@ cunit/ptrarray.$(OBJEXT) cunit/quota.$(OBJEXT) \ @CUNIT_TRUE@ cunit/rfc822tok.$(OBJEXT) $(am__objects_32) \ @CUNIT_TRUE@ cunit/spool.$(OBJEXT) cunit/squat.$(OBJEXT) \ @CUNIT_TRUE@ cunit/strarray.$(OBJEXT) cunit/strconcat.$(OBJEXT) \ @CUNIT_TRUE@ cunit/times.$(OBJEXT) cunit/tok.$(OBJEXT) @CUNIT_TRUE@am_cunit_unit_OBJECTS = $(am__objects_31) \ @CUNIT_TRUE@ $(am__objects_33) imap/mutex_fake.$(OBJEXT) \ @CUNIT_TRUE@ imap/spool.$(OBJEXT) cunit_unit_OBJECTS = $(am_cunit_unit_OBJECTS) am__DEPENDENCIES_4 = lib/libcyrus.la lib/libcyrus_min.la \ $(am__DEPENDENCIES_1) $(am__DEPENDENCIES_1) \ $(am__DEPENDENCIES_1) $(am__DEPENDENCIES_1) am__DEPENDENCIES_5 = imap/libcyrus_imap.la $(am__DEPENDENCIES_4) \ $(am__DEPENDENCIES_1) @CUNIT_TRUE@cunit_unit_DEPENDENCIES = $(am__append_44) \ @CUNIT_TRUE@ $(am__DEPENDENCIES_5) am_imap_arbitron_OBJECTS = imap/arbitron.$(OBJEXT) \ imap/cli_fatal.$(OBJEXT) imap/mutex_fake.$(OBJEXT) imap_arbitron_OBJECTS = $(am_imap_arbitron_OBJECTS) imap_arbitron_DEPENDENCIES = $(am__DEPENDENCIES_5) am_imap_chk_cyrus_OBJECTS = imap/chk_cyrus.$(OBJEXT) \ imap/cli_fatal.$(OBJEXT) imap/mutex_fake.$(OBJEXT) imap_chk_cyrus_OBJECTS = $(am_imap_chk_cyrus_OBJECTS) imap_chk_cyrus_DEPENDENCIES = $(am__DEPENDENCIES_5) am_imap_ctl_cyrusdb_OBJECTS = imap/cli_fatal.$(OBJEXT) \ imap/ctl_cyrusdb.$(OBJEXT) imap/mutex_fake.$(OBJEXT) imap_ctl_cyrusdb_OBJECTS = $(am_imap_ctl_cyrusdb_OBJECTS) imap_ctl_cyrusdb_DEPENDENCIES = $(am__DEPENDENCIES_5) am_imap_ctl_deliver_OBJECTS = imap/cli_fatal.$(OBJEXT) \ imap/ctl_deliver.$(OBJEXT) imap/mutex_fake.$(OBJEXT) imap_ctl_deliver_OBJECTS = $(am_imap_ctl_deliver_OBJECTS) imap_ctl_deliver_DEPENDENCIES = $(am__DEPENDENCIES_5) am_imap_ctl_mboxlist_OBJECTS = imap/cli_fatal.$(OBJEXT) \ imap/ctl_mboxlist.$(OBJEXT) imap/mutex_fake.$(OBJEXT) imap_ctl_mboxlist_OBJECTS = $(am_imap_ctl_mboxlist_OBJECTS) imap_ctl_mboxlist_DEPENDENCIES = $(am__DEPENDENCIES_5) am__imap_ctl_zoneinfo_SOURCES_DIST = imap/cli_fatal.c \ imap/ctl_zoneinfo.c imap/mutex_fake.c @HTTPD_TRUE@am_imap_ctl_zoneinfo_OBJECTS = imap/cli_fatal.$(OBJEXT) \ @HTTPD_TRUE@ imap/ctl_zoneinfo.$(OBJEXT) \ @HTTPD_TRUE@ imap/mutex_fake.$(OBJEXT) imap_ctl_zoneinfo_OBJECTS = $(am_imap_ctl_zoneinfo_OBJECTS) @HTTPD_TRUE@imap_ctl_zoneinfo_DEPENDENCIES = $(am__DEPENDENCIES_5) am_imap_cvt_cyrusdb_OBJECTS = imap/cli_fatal.$(OBJEXT) \ imap/cvt_cyrusdb.$(OBJEXT) imap/mutex_fake.$(OBJEXT) imap_cvt_cyrusdb_OBJECTS = $(am_imap_cvt_cyrusdb_OBJECTS) imap_cvt_cyrusdb_DEPENDENCIES = $(am__DEPENDENCIES_5) am_imap_cyr_dbtool_OBJECTS = imap/cli_fatal.$(OBJEXT) \ imap/cyr_dbtool.$(OBJEXT) imap/mutex_fake.$(OBJEXT) imap_cyr_dbtool_OBJECTS = $(am_imap_cyr_dbtool_OBJECTS) imap_cyr_dbtool_DEPENDENCIES = $(am__DEPENDENCIES_5) am_imap_cyr_deny_OBJECTS = imap/cli_fatal.$(OBJEXT) \ imap/cyr_deny.$(OBJEXT) imap/mutex_fake.$(OBJEXT) imap_cyr_deny_OBJECTS = $(am_imap_cyr_deny_OBJECTS) imap_cyr_deny_DEPENDENCIES = $(am__DEPENDENCIES_5) am_imap_cyr_df_OBJECTS = imap/cli_fatal.$(OBJEXT) \ imap/cyr_df.$(OBJEXT) imap/mutex_fake.$(OBJEXT) imap_cyr_df_OBJECTS = $(am_imap_cyr_df_OBJECTS) imap_cyr_df_DEPENDENCIES = $(am__DEPENDENCIES_5) am_imap_cyr_expire_OBJECTS = imap/cli_fatal.$(OBJEXT) \ imap/cyr_expire.$(OBJEXT) imap/mutex_fake.$(OBJEXT) imap_cyr_expire_OBJECTS = $(am_imap_cyr_expire_OBJECTS) imap_cyr_expire_DEPENDENCIES = $(am__DEPENDENCIES_5) am_imap_cyr_info_OBJECTS = imap/cli_fatal.$(OBJEXT) \ imap/cyr_info.$(OBJEXT) imap/mutex_fake.$(OBJEXT) \ master/masterconf.$(OBJEXT) imap_cyr_info_OBJECTS = $(am_imap_cyr_info_OBJECTS) imap_cyr_info_DEPENDENCIES = $(am__DEPENDENCIES_5) am_imap_cyr_sequence_OBJECTS = imap/cli_fatal.$(OBJEXT) \ imap/cyr_sequence.$(OBJEXT) imap/mutex_fake.$(OBJEXT) imap_cyr_sequence_OBJECTS = $(am_imap_cyr_sequence_OBJECTS) imap_cyr_sequence_DEPENDENCIES = $(am__DEPENDENCIES_5) am_imap_cyr_synclog_OBJECTS = imap/cli_fatal.$(OBJEXT) \ imap/cyr_synclog.$(OBJEXT) imap/mutex_fake.$(OBJEXT) imap_cyr_synclog_OBJECTS = $(am_imap_cyr_synclog_OBJECTS) imap_cyr_synclog_DEPENDENCIES = $(am__DEPENDENCIES_5) am_imap_cyr_userseen_OBJECTS = imap/cli_fatal.$(OBJEXT) \ imap/cyr_userseen.$(OBJEXT) imap/mutex_fake.$(OBJEXT) imap_cyr_userseen_OBJECTS = $(am_imap_cyr_userseen_OBJECTS) imap_cyr_userseen_DEPENDENCIES = $(am__DEPENDENCIES_5) am__imap_cyr_virusscan_SOURCES_DIST = imap/cli_fatal.c \ imap/cyr_virusscan.c imap/mutex_fake.c @HAVE_CLAMAV_TRUE@am_imap_cyr_virusscan_OBJECTS = \ @HAVE_CLAMAV_TRUE@ imap/cli_fatal.$(OBJEXT) \ @HAVE_CLAMAV_TRUE@ imap/cyr_virusscan.$(OBJEXT) \ @HAVE_CLAMAV_TRUE@ imap/mutex_fake.$(OBJEXT) imap_cyr_virusscan_OBJECTS = $(am_imap_cyr_virusscan_OBJECTS) @HAVE_CLAMAV_TRUE@imap_cyr_virusscan_DEPENDENCIES = \ @HAVE_CLAMAV_TRUE@ $(am__DEPENDENCIES_5) am_imap_cyrdump_OBJECTS = imap/cli_fatal.$(OBJEXT) \ imap/cyrdump.$(OBJEXT) imap/mutex_fake.$(OBJEXT) imap_cyrdump_OBJECTS = $(am_imap_cyrdump_OBJECTS) imap_cyrdump_DEPENDENCIES = $(am__DEPENDENCIES_5) am_imap_dav_reconstruct_OBJECTS = imap/cli_fatal.$(OBJEXT) \ imap/mutex_fake.$(OBJEXT) imap/dav_reconstruct.$(OBJEXT) imap_dav_reconstruct_OBJECTS = $(am_imap_dav_reconstruct_OBJECTS) imap_dav_reconstruct_DEPENDENCIES = $(am__DEPENDENCIES_5) am_imap_deliver_OBJECTS = imap/deliver.$(OBJEXT) \ imap/lmtpengine.$(OBJEXT) imap/lmtpstats.$(OBJEXT) \ imap/mutex_fake.$(OBJEXT) imap/proxy.$(OBJEXT) \ imap/spool.$(OBJEXT) imap_deliver_OBJECTS = $(am_imap_deliver_OBJECTS) imap_deliver_DEPENDENCIES = $(am__DEPENDENCIES_5) am_imap_fetchnews_OBJECTS = imap/cli_fatal.$(OBJEXT) \ imap/fetchnews.$(OBJEXT) imap/mutex_fake.$(OBJEXT) imap_fetchnews_OBJECTS = $(am_imap_fetchnews_OBJECTS) imap_fetchnews_DEPENDENCIES = $(am__DEPENDENCIES_5) am_imap_fud_OBJECTS = imap/fud.$(OBJEXT) imap/mutex_fake.$(OBJEXT) \ master/service.$(OBJEXT) imap_fud_OBJECTS = $(am_imap_fud_OBJECTS) am__DEPENDENCIES_6 = $(am__DEPENDENCIES_5) $(am__DEPENDENCIES_1) imap_fud_DEPENDENCIES = $(am__DEPENDENCIES_6) am_imap_httpd_OBJECTS = imap/caldav_db.$(OBJEXT) \ imap/carddav_db.$(OBJEXT) imap/dav_db.$(OBJEXT) \ imap/dav_util.$(OBJEXT) imap/http_caldav.$(OBJEXT) \ imap/http_carddav.$(OBJEXT) imap/http_client.$(OBJEXT) \ imap/http_dav.$(OBJEXT) imap/http_dblookup.$(OBJEXT) \ imap/http_ischedule.$(OBJEXT) imap/http_proxy.$(OBJEXT) \ imap/http_rss.$(OBJEXT) imap/http_timezone.$(OBJEXT) \ imap/httpd.$(OBJEXT) imap/jcal.$(OBJEXT) \ imap/mutex_fake.$(OBJEXT) imap/proxy.$(OBJEXT) \ imap/smtpclient.$(OBJEXT) imap/spool.$(OBJEXT) \ imap/xcal.$(OBJEXT) imap/zoneinfo_db.$(OBJEXT) \ master/service.$(OBJEXT) nodist_imap_httpd_OBJECTS = imap/http_err.$(OBJEXT) \ imap/tz_err.$(OBJEXT) imap_httpd_OBJECTS = $(am_imap_httpd_OBJECTS) \ $(nodist_imap_httpd_OBJECTS) imap_httpd_DEPENDENCIES = $(am__DEPENDENCIES_6) am_imap_idled_OBJECTS = imap/idled.$(OBJEXT) imap/mutex_fake.$(OBJEXT) imap_idled_OBJECTS = $(am_imap_idled_OBJECTS) imap_idled_DEPENDENCIES = $(am__DEPENDENCIES_5) am__imap_imapd_SOURCES_DIST = imap/imap_proxy.c imap/imap_proxy.h \ imap/imapd.c imap/imapd.h imap/mutex_fake.c imap/pushstats.c \ imap/pushstats.h imap/proxy.c imap/proxy.h master/service.c \ imap/autocreate.h imap/autocreate.c @AUTOCREATE_TRUE@am__objects_34 = imap/autocreate.$(OBJEXT) am_imap_imapd_OBJECTS = imap/imap_proxy.$(OBJEXT) imap/imapd.$(OBJEXT) \ imap/mutex_fake.$(OBJEXT) imap/pushstats.$(OBJEXT) \ imap/proxy.$(OBJEXT) master/service.$(OBJEXT) \ $(am__objects_34) imap_imapd_OBJECTS = $(am_imap_imapd_OBJECTS) imap_imapd_DEPENDENCIES = $(am__append_48) $(am__DEPENDENCIES_6) am_imap_ipurge_OBJECTS = imap/cli_fatal.$(OBJEXT) \ imap/ipurge.$(OBJEXT) imap/mutex_fake.$(OBJEXT) imap_ipurge_OBJECTS = $(am_imap_ipurge_OBJECTS) imap_ipurge_DEPENDENCIES = $(am__DEPENDENCIES_5) am__imap_lmtpd_SOURCES_DIST = imap/lmtpd.c imap/lmtpd.h \ imap/lmtpengine.c imap/lmtpengine.h imap/lmtpstats.c \ imap/lmtpstats.h imap/mutex_fake.c imap/proxy.c imap/spool.c \ master/service.c imap/autocreate.c imap/autocreate.h \ imap/lmtp_sieve.c imap/lmtp_sieve.h imap/smtpclient.c @SIEVE_TRUE@am__objects_35 = imap/lmtp_sieve.$(OBJEXT) \ @SIEVE_TRUE@ imap/smtpclient.$(OBJEXT) am_imap_lmtpd_OBJECTS = imap/lmtpd.$(OBJEXT) imap/lmtpengine.$(OBJEXT) \ imap/lmtpstats.$(OBJEXT) imap/mutex_fake.$(OBJEXT) \ imap/proxy.$(OBJEXT) imap/spool.$(OBJEXT) \ master/service.$(OBJEXT) $(am__objects_34) $(am__objects_35) imap_lmtpd_OBJECTS = $(am_imap_lmtpd_OBJECTS) imap_lmtpd_DEPENDENCIES = $(am__append_55) $(am__DEPENDENCIES_6) am_imap_mbexamine_OBJECTS = imap/cli_fatal.$(OBJEXT) \ imap/mbexamine.$(OBJEXT) imap/mutex_fake.$(OBJEXT) imap_mbexamine_OBJECTS = $(am_imap_mbexamine_OBJECTS) imap_mbexamine_DEPENDENCIES = $(am__DEPENDENCIES_5) am_imap_mbpath_OBJECTS = imap/cli_fatal.$(OBJEXT) \ imap/mbpath.$(OBJEXT) imap/mutex_fake.$(OBJEXT) imap_mbpath_OBJECTS = $(am_imap_mbpath_OBJECTS) imap_mbpath_DEPENDENCIES = $(am__DEPENDENCIES_5) am_imap_mbtool_OBJECTS = imap/cli_fatal.$(OBJEXT) \ imap/mbtool.$(OBJEXT) imap/mutex_fake.$(OBJEXT) imap_mbtool_OBJECTS = $(am_imap_mbtool_OBJECTS) imap_mbtool_DEPENDENCIES = $(am__DEPENDENCIES_5) am_imap_mupdate_OBJECTS = imap/mupdate.$(OBJEXT) \ imap/mupdate-slave.$(OBJEXT) imap/mutex_pthread.$(OBJEXT) \ imap/tls_th-lock.$(OBJEXT) master/service-thread.$(OBJEXT) imap_mupdate_OBJECTS = $(am_imap_mupdate_OBJECTS) imap_mupdate_DEPENDENCIES = $(am__DEPENDENCIES_6) am_imap_nntpd_OBJECTS = imap/mutex_fake.$(OBJEXT) imap/nntpd.$(OBJEXT) \ imap/proxy.$(OBJEXT) imap/smtpclient.$(OBJEXT) \ imap/spool.$(OBJEXT) master/service.$(OBJEXT) nodist_imap_nntpd_OBJECTS = imap/nntp_err.$(OBJEXT) imap_nntpd_OBJECTS = $(am_imap_nntpd_OBJECTS) \ $(nodist_imap_nntpd_OBJECTS) imap_nntpd_DEPENDENCIES = $(am__DEPENDENCIES_6) am__imap_pop3d_SOURCES_DIST = imap/mutex_fake.c imap/pop3d.c \ imap/proxy.c master/service.c imap/autocreate.c \ imap/autocreate.h am_imap_pop3d_OBJECTS = imap/mutex_fake.$(OBJEXT) imap/pop3d.$(OBJEXT) \ imap/proxy.$(OBJEXT) master/service.$(OBJEXT) \ $(am__objects_34) imap_pop3d_OBJECTS = $(am_imap_pop3d_OBJECTS) imap_pop3d_DEPENDENCIES = $(am__append_57) $(am__DEPENDENCIES_6) am_imap_quota_OBJECTS = imap/cli_fatal.$(OBJEXT) \ imap/mutex_fake.$(OBJEXT) imap/quota.$(OBJEXT) imap_quota_OBJECTS = $(am_imap_quota_OBJECTS) imap_quota_DEPENDENCIES = $(am__DEPENDENCIES_5) am_imap_reconstruct_OBJECTS = imap/cli_fatal.$(OBJEXT) \ imap/mutex_fake.$(OBJEXT) imap/reconstruct.$(OBJEXT) imap_reconstruct_OBJECTS = $(am_imap_reconstruct_OBJECTS) imap_reconstruct_DEPENDENCIES = $(am__DEPENDENCIES_5) am_imap_smmapd_OBJECTS = imap/mutex_fake.$(OBJEXT) \ imap/proxy.$(OBJEXT) imap/smmapd.$(OBJEXT) \ master/service.$(OBJEXT) imap_smmapd_OBJECTS = $(am_imap_smmapd_OBJECTS) imap_smmapd_DEPENDENCIES = $(am__DEPENDENCIES_6) am_imap_squatter_OBJECTS = imap/cli_fatal.$(OBJEXT) \ imap/mutex_fake.$(OBJEXT) imap/squatter.$(OBJEXT) \ imap/squat_build.$(OBJEXT) imap_squatter_OBJECTS = $(am_imap_squatter_OBJECTS) imap_squatter_DEPENDENCIES = $(am__DEPENDENCIES_5) am_imap_sync_client_OBJECTS = imap/mutex_fake.$(OBJEXT) \ imap/sync_client.$(OBJEXT) imap/sync_support.$(OBJEXT) imap_sync_client_OBJECTS = $(am_imap_sync_client_OBJECTS) imap_sync_client_DEPENDENCIES = $(am__DEPENDENCIES_5) am_imap_sync_reset_OBJECTS = imap/mutex_fake.$(OBJEXT) \ imap/sync_reset.$(OBJEXT) imap/sync_support.$(OBJEXT) imap_sync_reset_OBJECTS = $(am_imap_sync_reset_OBJECTS) imap_sync_reset_DEPENDENCIES = $(am__DEPENDENCIES_5) am_imap_sync_server_OBJECTS = imap/mutex_fake.$(OBJEXT) \ imap/sync_server.$(OBJEXT) imap/sync_support.$(OBJEXT) \ master/service.$(OBJEXT) imap_sync_server_OBJECTS = $(am_imap_sync_server_OBJECTS) imap_sync_server_DEPENDENCIES = $(am__DEPENDENCIES_6) am_imap_tls_prune_OBJECTS = imap/cli_fatal.$(OBJEXT) \ imap/mutex_fake.$(OBJEXT) imap/tls_prune.$(OBJEXT) imap_tls_prune_OBJECTS = $(am_imap_tls_prune_OBJECTS) imap_tls_prune_DEPENDENCIES = $(am__DEPENDENCIES_5) am_imap_unexpunge_OBJECTS = imap/cli_fatal.$(OBJEXT) \ imap/mutex_fake.$(OBJEXT) imap/unexpunge.$(OBJEXT) imap_unexpunge_OBJECTS = $(am_imap_unexpunge_OBJECTS) imap_unexpunge_DEPENDENCIES = $(am__DEPENDENCIES_5) am_imtest_imtest_OBJECTS = imtest/imtest_imtest-imtest.$(OBJEXT) imtest_imtest_OBJECTS = $(am_imtest_imtest_OBJECTS) imtest_imtest_DEPENDENCIES = $(am__DEPENDENCIES_4) imtest_imtest_LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ $(LIBTOOLFLAGS) --mode=link $(CCLD) $(imtest_imtest_CFLAGS) \ $(CFLAGS) $(AM_LDFLAGS) $(LDFLAGS) -o $@ am_master_master_OBJECTS = master/cyrusMasterMIB.$(OBJEXT) \ master/master.$(OBJEXT) master/masterconf.$(OBJEXT) master_master_OBJECTS = $(am_master_master_OBJECTS) master_master_DEPENDENCIES = lib/libcyrus_min.la $(am__DEPENDENCIES_1) \ $(am__DEPENDENCIES_1) am_netnews_remotepurge_OBJECTS = netnews/readconfig.$(OBJEXT) \ netnews/remotepurge.$(OBJEXT) netnews_remotepurge_OBJECTS = $(am_netnews_remotepurge_OBJECTS) netnews_remotepurge_DEPENDENCIES = $(am__DEPENDENCIES_4) am__notifyd_notifyd_SOURCES_DIST = imap/mutex_fake.c master/service.c \ notifyd/notify_external.c notifyd/notify_external.h \ notifyd/notify_log.c notifyd/notify_log.h \ notifyd/notify_mailto.c notifyd/notify_mailto.h \ notifyd/notify_null.c notifyd/notify_null.h notifyd/notifyd.c \ notifyd/notifyd.h notifyd/notify_zephyr.c \ notifyd/notify_zephyr.h @ZEPHYR_TRUE@am__objects_36 = notifyd/notify_zephyr.$(OBJEXT) am_notifyd_notifyd_OBJECTS = imap/mutex_fake.$(OBJEXT) \ master/service.$(OBJEXT) notifyd/notify_external.$(OBJEXT) \ notifyd/notify_log.$(OBJEXT) notifyd/notify_mailto.$(OBJEXT) \ notifyd/notify_null.$(OBJEXT) notifyd/notifyd.$(OBJEXT) \ $(am__objects_36) notifyd_notifyd_OBJECTS = $(am_notifyd_notifyd_OBJECTS) notifyd_notifyd_DEPENDENCIES = $(am__DEPENDENCIES_6) \ $(am__DEPENDENCIES_1) am_notifyd_notifytest_OBJECTS = notifyd/notifytest.$(OBJEXT) \ imap/mutex_fake.$(OBJEXT) notifyd_notifytest_OBJECTS = $(am_notifyd_notifytest_OBJECTS) notifyd_notifytest_DEPENDENCIES = $(am__DEPENDENCIES_4) am_ptclient_ptdump_OBJECTS = imap/cli_fatal.$(OBJEXT) \ imap/mutex_fake.$(OBJEXT) ptclient/ptdump.$(OBJEXT) ptclient_ptdump_OBJECTS = $(am_ptclient_ptdump_OBJECTS) ptclient_ptdump_DEPENDENCIES = $(am__DEPENDENCIES_5) am_ptclient_ptexpire_OBJECTS = imap/cli_fatal.$(OBJEXT) \ imap/mutex_fake.$(OBJEXT) ptclient/ptexpire.$(OBJEXT) ptclient_ptexpire_OBJECTS = $(am_ptclient_ptexpire_OBJECTS) ptclient_ptexpire_DEPENDENCIES = $(am__DEPENDENCIES_5) am__ptclient_ptloader_SOURCES_DIST = imap/mutex_fake.c \ ptclient/ptloader.c ptclient/ptloader.h \ master/service-thread.c ptclient/ldap.c ptclient/afskrb.c @HAVE_LDAP_TRUE@am__objects_37 = ptclient/ldap.$(OBJEXT) @USE_AFSKRB_TRUE@am__objects_38 = ptclient/afskrb.$(OBJEXT) am_ptclient_ptloader_OBJECTS = imap/mutex_fake.$(OBJEXT) \ ptclient/ptloader.$(OBJEXT) master/service-thread.$(OBJEXT) \ $(am__objects_37) $(am__objects_38) ptclient_ptloader_OBJECTS = $(am_ptclient_ptloader_OBJECTS) @HAVE_LDAP_TRUE@am__DEPENDENCIES_7 = $(am__DEPENDENCIES_1) @USE_AFSKRB_TRUE@am__DEPENDENCIES_8 = $(am__DEPENDENCIES_1) ptclient_ptloader_DEPENDENCIES = $(am__DEPENDENCIES_6) \ $(am__DEPENDENCIES_7) $(am__DEPENDENCIES_8) ptclient_ptloader_LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC \ $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=link $(CCLD) \ $(AM_CFLAGS) $(CFLAGS) $(ptclient_ptloader_LDFLAGS) $(LDFLAGS) \ -o $@ sieve_sievec_SOURCES = sieve/sievec.c sieve_sievec_OBJECTS = sieve/sievec.$(OBJEXT) am__DEPENDENCIES_9 = sieve/libcyrus_sieve.la $(am__DEPENDENCIES_4) sieve_sievec_DEPENDENCIES = $(am__DEPENDENCIES_9) sieve_sieved_SOURCES = sieve/sieved.c sieve_sieved_OBJECTS = sieve/sieved.$(OBJEXT) sieve_sieved_DEPENDENCIES = $(am__DEPENDENCIES_9) am_sieve_test_OBJECTS = sieve/test.$(OBJEXT) imap/mutex_fake.$(OBJEXT) sieve_test_OBJECTS = $(am_sieve_test_OBJECTS) sieve_test_DEPENDENCIES = sieve/libcyrus_sieve.la \ $(am__DEPENDENCIES_5) am_timsieved_timsieved_OBJECTS = imap/mutex_fake.$(OBJEXT) \ imap/proxy.$(OBJEXT) master/service.$(OBJEXT) \ timsieved/actions.$(OBJEXT) timsieved/lex.$(OBJEXT) \ timsieved/parser.$(OBJEXT) timsieved/scripttest.$(OBJEXT) \ timsieved/timsieved.$(OBJEXT) timsieved_timsieved_OBJECTS = $(am_timsieved_timsieved_OBJECTS) timsieved_timsieved_DEPENDENCIES = sieve/libcyrus_sieve.la \ $(am__DEPENDENCIES_6) tools_htmlstrip_SOURCES = tools/htmlstrip.c tools_htmlstrip_OBJECTS = tools/htmlstrip.$(OBJEXT) tools_htmlstrip_LDADD = $(LDADD) SCRIPTS = $(dist_noinst_SCRIPTS) AM_V_P = $(am__v_P_@AM_V@) am__v_P_ = $(am__v_P_@AM_DEFAULT_V@) am__v_P_0 = false am__v_P_1 = : AM_V_GEN = $(am__v_GEN_@AM_V@) am__v_GEN_ = $(am__v_GEN_@AM_DEFAULT_V@) am__v_GEN_0 = @echo " GEN " $@; am__v_GEN_1 = AM_V_at = $(am__v_at_@AM_V@) am__v_at_ = $(am__v_at_@AM_DEFAULT_V@) am__v_at_0 = @ am__v_at_1 = DEFAULT_INCLUDES = -I.@am__isrc@ depcomp = $(SHELL) $(top_srcdir)/depcomp am__depfiles_maybe = depfiles am__mv = mv -f COMPILE = $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) \ $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) LTCOMPILE = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) \ $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) \ $(AM_CFLAGS) $(CFLAGS) AM_V_CC = $(am__v_CC_@AM_V@) am__v_CC_ = $(am__v_CC_@AM_DEFAULT_V@) am__v_CC_0 = @echo " CC " $@; am__v_CC_1 = CCLD = $(CC) LINK = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \ $(LIBTOOLFLAGS) --mode=link $(CCLD) $(AM_CFLAGS) $(CFLAGS) \ $(AM_LDFLAGS) $(LDFLAGS) -o $@ AM_V_CCLD = $(am__v_CCLD_@AM_V@) am__v_CCLD_ = $(am__v_CCLD_@AM_DEFAULT_V@) am__v_CCLD_0 = @echo " CCLD " $@; am__v_CCLD_1 = @MAINTAINER_MODE_FALSE@am__skiplex = test -f $@ || LEXCOMPILE = $(LEX) $(AM_LFLAGS) $(LFLAGS) LTLEXCOMPILE = $(LIBTOOL) $(AM_V_lt) $(AM_LIBTOOLFLAGS) \ $(LIBTOOLFLAGS) --mode=compile $(LEX) $(AM_LFLAGS) $(LFLAGS) AM_V_LEX = $(am__v_LEX_@AM_V@) am__v_LEX_ = $(am__v_LEX_@AM_DEFAULT_V@) am__v_LEX_0 = @echo " LEX " $@; am__v_LEX_1 = YLWRAP = $(top_srcdir)/ylwrap @MAINTAINER_MODE_FALSE@am__skipyacc = test -f $@ || am__yacc_c2h = sed -e s/cc$$/hh/ -e s/cpp$$/hpp/ -e s/cxx$$/hxx/ \ -e s/c++$$/h++/ -e s/c$$/h/ YACCCOMPILE = $(YACC) $(AM_YFLAGS) $(YFLAGS) LTYACCCOMPILE = $(LIBTOOL) $(AM_V_lt) $(AM_LIBTOOLFLAGS) \ $(LIBTOOLFLAGS) --mode=compile $(YACC) $(AM_YFLAGS) $(YFLAGS) AM_V_YACC = $(am__v_YACC_@AM_V@) am__v_YACC_ = $(am__v_YACC_@AM_DEFAULT_V@) am__v_YACC_0 = @echo " YACC " $@; am__v_YACC_1 = SOURCES = $(perl_sieve_lib_libisieve_a_SOURCES) \ $(com_err_et_libcyrus_com_err_la_SOURCES) \ $(imap_libcyrus_imap_la_SOURCES) \ $(dist_imap_libcyrus_imap_la_SOURCES) \ $(nodist_imap_libcyrus_imap_la_SOURCES) \ $(lib_libcyrus_la_SOURCES) $(nodist_lib_libcyrus_la_SOURCES) \ $(lib_libcyrus_min_la_SOURCES) \ $(nodist_lib_libcyrus_min_la_SOURCES) \ $(perl_libcyrus_la_SOURCES) $(perl_libcyrus_min_la_SOURCES) \ $(sieve_libcyrus_sieve_la_SOURCES) \ $(nodist_sieve_libcyrus_sieve_la_SOURCES) \ $(sieve_libcyrus_sieve_lex_la_SOURCES) $(cunit_unit_SOURCES) \ $(imap_arbitron_SOURCES) $(imap_chk_cyrus_SOURCES) \ $(imap_ctl_cyrusdb_SOURCES) $(imap_ctl_deliver_SOURCES) \ $(imap_ctl_mboxlist_SOURCES) $(imap_ctl_zoneinfo_SOURCES) \ $(imap_cvt_cyrusdb_SOURCES) $(imap_cyr_dbtool_SOURCES) \ $(imap_cyr_deny_SOURCES) $(imap_cyr_df_SOURCES) \ $(imap_cyr_expire_SOURCES) $(imap_cyr_info_SOURCES) \ $(imap_cyr_sequence_SOURCES) $(imap_cyr_synclog_SOURCES) \ $(imap_cyr_userseen_SOURCES) $(imap_cyr_virusscan_SOURCES) \ $(imap_cyrdump_SOURCES) $(imap_dav_reconstruct_SOURCES) \ $(imap_deliver_SOURCES) $(imap_fetchnews_SOURCES) \ $(imap_fud_SOURCES) $(imap_httpd_SOURCES) \ $(nodist_imap_httpd_SOURCES) $(imap_idled_SOURCES) \ $(imap_imapd_SOURCES) $(imap_ipurge_SOURCES) \ $(imap_lmtpd_SOURCES) $(imap_mbexamine_SOURCES) \ $(imap_mbpath_SOURCES) $(imap_mbtool_SOURCES) \ $(imap_mupdate_SOURCES) $(imap_nntpd_SOURCES) \ $(nodist_imap_nntpd_SOURCES) $(imap_pop3d_SOURCES) \ $(imap_quota_SOURCES) $(imap_reconstruct_SOURCES) \ $(imap_smmapd_SOURCES) $(imap_squatter_SOURCES) \ $(imap_sync_client_SOURCES) $(imap_sync_reset_SOURCES) \ $(imap_sync_server_SOURCES) $(imap_tls_prune_SOURCES) \ $(imap_unexpunge_SOURCES) $(imtest_imtest_SOURCES) \ $(master_master_SOURCES) $(netnews_remotepurge_SOURCES) \ $(notifyd_notifyd_SOURCES) $(notifyd_notifytest_SOURCES) \ $(ptclient_ptdump_SOURCES) $(ptclient_ptexpire_SOURCES) \ $(ptclient_ptloader_SOURCES) sieve/sievec.c sieve/sieved.c \ $(sieve_test_SOURCES) $(timsieved_timsieved_SOURCES) \ tools/htmlstrip.c DIST_SOURCES = $(perl_sieve_lib_libisieve_a_SOURCES) \ $(com_err_et_libcyrus_com_err_la_SOURCES) \ $(am__imap_libcyrus_imap_la_SOURCES_DIST) \ $(dist_imap_libcyrus_imap_la_SOURCES) \ $(am__lib_libcyrus_la_SOURCES_DIST) \ $(am__lib_libcyrus_min_la_SOURCES_DIST) \ $(am__perl_libcyrus_la_SOURCES_DIST) \ $(am__perl_libcyrus_min_la_SOURCES_DIST) \ $(sieve_libcyrus_sieve_la_SOURCES) \ $(sieve_libcyrus_sieve_lex_la_SOURCES) \ $(am__cunit_unit_SOURCES_DIST) $(imap_arbitron_SOURCES) \ $(imap_chk_cyrus_SOURCES) $(imap_ctl_cyrusdb_SOURCES) \ $(imap_ctl_deliver_SOURCES) $(imap_ctl_mboxlist_SOURCES) \ $(am__imap_ctl_zoneinfo_SOURCES_DIST) \ $(imap_cvt_cyrusdb_SOURCES) $(imap_cyr_dbtool_SOURCES) \ $(imap_cyr_deny_SOURCES) $(imap_cyr_df_SOURCES) \ $(imap_cyr_expire_SOURCES) $(imap_cyr_info_SOURCES) \ $(imap_cyr_sequence_SOURCES) $(imap_cyr_synclog_SOURCES) \ $(imap_cyr_userseen_SOURCES) \ $(am__imap_cyr_virusscan_SOURCES_DIST) $(imap_cyrdump_SOURCES) \ $(imap_dav_reconstruct_SOURCES) $(imap_deliver_SOURCES) \ $(imap_fetchnews_SOURCES) $(imap_fud_SOURCES) \ $(imap_httpd_SOURCES) $(imap_idled_SOURCES) \ $(am__imap_imapd_SOURCES_DIST) $(imap_ipurge_SOURCES) \ $(am__imap_lmtpd_SOURCES_DIST) $(imap_mbexamine_SOURCES) \ $(imap_mbpath_SOURCES) $(imap_mbtool_SOURCES) \ $(imap_mupdate_SOURCES) $(imap_nntpd_SOURCES) \ $(am__imap_pop3d_SOURCES_DIST) $(imap_quota_SOURCES) \ $(imap_reconstruct_SOURCES) $(imap_smmapd_SOURCES) \ $(imap_squatter_SOURCES) $(imap_sync_client_SOURCES) \ $(imap_sync_reset_SOURCES) $(imap_sync_server_SOURCES) \ $(imap_tls_prune_SOURCES) $(imap_unexpunge_SOURCES) \ $(imtest_imtest_SOURCES) $(master_master_SOURCES) \ $(netnews_remotepurge_SOURCES) \ $(am__notifyd_notifyd_SOURCES_DIST) \ $(notifyd_notifytest_SOURCES) $(ptclient_ptdump_SOURCES) \ $(ptclient_ptexpire_SOURCES) \ $(am__ptclient_ptloader_SOURCES_DIST) sieve/sievec.c \ sieve/sieved.c $(sieve_test_SOURCES) \ $(timsieved_timsieved_SOURCES) tools/htmlstrip.c RECURSIVE_TARGETS = all-recursive check-recursive cscopelist-recursive \ ctags-recursive dvi-recursive html-recursive info-recursive \ install-data-recursive install-dvi-recursive \ install-exec-recursive install-html-recursive \ install-info-recursive install-pdf-recursive \ install-ps-recursive install-recursive installcheck-recursive \ installdirs-recursive pdf-recursive ps-recursive \ tags-recursive uninstall-recursive am__can_run_installinfo = \ case $$AM_UPDATE_INFO_DIR in \ n|no|NO) false;; \ *) (install-info --version) >/dev/null 2>&1;; \ esac man1dir = $(mandir)/man1 man3dir = $(mandir)/man3 man5dir = $(mandir)/man5 man8dir = $(mandir)/man8 NROFF = nroff MANS = $(dist_man_MANS) am__dist_sysconf_DATA_DIST = depot/rc.local.imap \ depot/rc.local.ptclient DATA = $(dist_sysconf_DATA) $(pkgconfig_DATA) HEADERS = $(include_HEADERS) $(nobase_include_HEADERS) \ $(nobase_nodist_include_HEADERS) $(nodist_include_HEADERS) \ $(noinst_HEADERS) RECURSIVE_CLEAN_TARGETS = mostlyclean-recursive clean-recursive \ distclean-recursive maintainer-clean-recursive am__recursive_targets = \ $(RECURSIVE_TARGETS) \ $(RECURSIVE_CLEAN_TARGETS) \ $(am__extra_recursive_targets) AM_RECURSIVE_TARGETS = $(am__recursive_targets:-recursive=) TAGS CTAGS \ cscope distdir dist dist-all distcheck am__tagged_files = $(HEADERS) $(SOURCES) $(TAGS_FILES) \ $(LISP)config.h.in # Read a list of newline-separated strings from the standard input, # and print each of them once, without duplicates. Input order is # *not* preserved. am__uniquify_input = $(AWK) '\ BEGIN { nonempty = 0; } \ { items[$$0] = 1; nonempty = 1; } \ END { if (nonempty) { for (i in items) print i; }; } \ ' # Make sure the list of sources is unique. This is necessary because, # e.g., the same source file might be shared among _SOURCES variables # for different programs/libraries. am__define_uniq_tagged_files = \ list='$(am__tagged_files)'; \ unique=`for i in $$list; do \ if test -f "$$i"; then echo $$i; else echo $(srcdir)/$$i; fi; \ done | $(am__uniquify_input)` ETAGS = etags CTAGS = ctags CSCOPE = cscope am__DIST_COMMON = $(dist_man_MANS) $(srcdir)/Makefile.in \ $(srcdir)/config.h.in $(srcdir)/libcyrus.pc.in \ $(srcdir)/libcyrus_min.pc.in $(srcdir)/libcyrus_sieve.pc.in \ $(top_srcdir)/lib/ftruncate.c \ $(top_srcdir)/lib/getdtablesize.c $(top_srcdir)/lib/memmem.c \ $(top_srcdir)/lib/memmove.c $(top_srcdir)/lib/posix_fadvise.c \ $(top_srcdir)/lib/strcasecmp.c $(top_srcdir)/lib/strerror.c \ $(top_srcdir)/lib/strsep.c \ $(top_srcdir)/perl/annotator/Makefile.PL.in \ $(top_srcdir)/perl/imap/Makefile.PL.in \ $(top_srcdir)/perl/sieve/managesieve/Makefile.PL.in COPYING \ INSTALL README compile config.guess config.sub depcomp \ install-sh ltmain.sh missing sieve/addr-lex.c sieve/addr.c \ sieve/sieve-lex.c sieve/sieve.c ylwrap DISTFILES = $(DIST_COMMON) $(DIST_SOURCES) $(TEXINFOS) $(EXTRA_DIST) distdir = $(PACKAGE)-$(VERSION) top_distdir = $(distdir) am__remove_distdir = \ if test -d "$(distdir)"; then \ find "$(distdir)" -type d ! -perm -200 -exec chmod u+w {} ';' \ && rm -rf "$(distdir)" \ || { sleep 5 && rm -rf "$(distdir)"; }; \ else :; fi am__post_remove_distdir = $(am__remove_distdir) am__relativize = \ dir0=`pwd`; \ sed_first='s,^\([^/]*\)/.*$$,\1,'; \ sed_rest='s,^[^/]*/*,,'; \ sed_last='s,^.*/\([^/]*\)$$,\1,'; \ sed_butlast='s,/*[^/]*$$,,'; \ while test -n "$$dir1"; do \ first=`echo "$$dir1" | sed -e "$$sed_first"`; \ if test "$$first" != "."; then \ if test "$$first" = ".."; then \ dir2=`echo "$$dir0" | sed -e "$$sed_last"`/"$$dir2"; \ dir0=`echo "$$dir0" | sed -e "$$sed_butlast"`; \ else \ first2=`echo "$$dir2" | sed -e "$$sed_first"`; \ if test "$$first2" = "$$first"; then \ dir2=`echo "$$dir2" | sed -e "$$sed_rest"`; \ else \ dir2="../$$dir2"; \ fi; \ dir0="$$dir0"/"$$first"; \ fi; \ fi; \ dir1=`echo "$$dir1" | sed -e "$$sed_rest"`; \ done; \ reldir="$$dir2" DIST_ARCHIVES = $(distdir).tar.gz $(distdir).tar.bz2 GZIP_ENV = --best DIST_TARGETS = dist-bzip2 dist-gzip distuninstallcheck_listfiles = find . -type f -print am__distuninstallcheck_listfiles = $(distuninstallcheck_listfiles) \ | sed 's|^\./|$(prefix)/|' | grep -v '$(infodir)/dir$$' distcleancheck_listfiles = find . -type f -print ACLOCAL = @ACLOCAL@ AFS_LDFLAGS = @AFS_LDFLAGS@ AFS_LIBS = @AFS_LIBS@ AMTAR = @AMTAR@ AM_DEFAULT_VERBOSITY = @AM_DEFAULT_VERBOSITY@ AR = @AR@ AUTOCONF = @AUTOCONF@ AUTOHEADER = @AUTOHEADER@ AUTOMAKE = @AUTOMAKE@ AWK = @AWK@ BDB_INC = @BDB_INC@ BDB_LIB = @BDB_LIB@ CC = @CC@ CCDEPMODE = @CCDEPMODE@ CFLAGS = @CFLAGS@ CFLAG_VISIBILITY = @CFLAG_VISIBILITY@ CMU_LIB_SUBDIR = @CMU_LIB_SUBDIR@ COMPILE_ET = @COMPILE_ET@ COM_ERR_CPPFLAGS = @COM_ERR_CPPFLAGS@ COM_ERR_LIBS = @COM_ERR_LIBS@ COV_CFLAGS = @COV_CFLAGS@ COV_LDFLAGS = @COV_LDFLAGS@ CPP = @CPP@ CPPFLAGS = @CPPFLAGS@ CYGPATH_W = @CYGPATH_W@ DEFS = @DEFS@ DEPDIR = @DEPDIR@ DKIM_CFLAGS = @DKIM_CFLAGS@ DKIM_LIBS = @DKIM_LIBS@ DLLTOOL = @DLLTOOL@ DSYMUTIL = @DSYMUTIL@ DUMPBIN = @DUMPBIN@ DYNSASLFLAGS = @DYNSASLFLAGS@ ECHO_C = @ECHO_C@ ECHO_N = @ECHO_N@ ECHO_T = @ECHO_T@ EGREP = @EGREP@ EXEEXT = @EXEEXT@ FGREP = @FGREP@ GPERF = @GPERF@ GREP = @GREP@ GSSAPIBASE_LIBS = @GSSAPIBASE_LIBS@ HAVE_VISIBILITY = @HAVE_VISIBILITY@ HTTP_CPPFLAGS = @HTTP_CPPFLAGS@ HTTP_LIBS = @HTTP_LIBS@ ICAL_CFLAGS = @ICAL_CFLAGS@ ICAL_LIBS = @ICAL_LIBS@ ICU_CFLAGS = @ICU_CFLAGS@ ICU_LIBS = @ICU_LIBS@ INSTALL = @INSTALL@ INSTALL_DATA = @INSTALL_DATA@ INSTALL_PROGRAM = @INSTALL_PROGRAM@ INSTALL_SCRIPT = @INSTALL_SCRIPT@ INSTALL_STRIP_PROGRAM = @INSTALL_STRIP_PROGRAM@ JANSSON_CFLAGS = @JANSSON_CFLAGS@ JANSSON_LIBS = @JANSSON_LIBS@ JSON_CFLAGS = @JSON_CFLAGS@ JSON_LIBS = @JSON_LIBS@ LD = @LD@ LDAP_CPPFLAGS = @LDAP_CPPFLAGS@ LDAP_LDFLAGS = @LDAP_LDFLAGS@ LDAP_LIBS = @LDAP_LIBS@ LDFLAGS = @LDFLAGS@ LEX = @LEX@ LEXLIB = @LEXLIB@ LEX_OUTPUT_ROOT = @LEX_OUTPUT_ROOT@ LIBOBJS = @LIBOBJS@ LIBS = @LIBS@ LIBTOOL = @LIBTOOL@ LIBTOOL_DEPS = @LIBTOOL_DEPS@ LIB_CLAMAV = @LIB_CLAMAV@ LIB_CRYPT = @LIB_CRYPT@ LIB_DYN_SASL = @LIB_DYN_SASL@ LIB_RT = @LIB_RT@ LIB_SASL = @LIB_SASL@ LIB_SOCKET = @LIB_SOCKET@ LIB_UCDSNMP = @LIB_UCDSNMP@ LIB_UUID = @LIB_UUID@ LIB_WRAP = @LIB_WRAP@ LIPO = @LIPO@ LN_S = @LN_S@ LOCALDEFS = @LOCALDEFS@ LTLIBOBJS = @LTLIBOBJS@ LT_SYS_LIBRARY_PATH = @LT_SYS_LIBRARY_PATH@ MAINT = @MAINT@ MAKEINFO = @MAKEINFO@ MANIFEST_TOOL = @MANIFEST_TOOL@ MKDIR_P = @MKDIR_P@ NM = @NM@ NMEDIT = @NMEDIT@ OBJDUMP = @OBJDUMP@ OBJEXT = @OBJEXT@ OPENSSL_CFLAGS = @OPENSSL_CFLAGS@ OPENSSL_LIBS = @OPENSSL_LIBS@ OTOOL = @OTOOL@ OTOOL64 = @OTOOL64@ PACKAGE = @PACKAGE@ PACKAGE_BUGREPORT = @PACKAGE_BUGREPORT@ PACKAGE_NAME = @PACKAGE_NAME@ PACKAGE_STRING = @PACKAGE_STRING@ PACKAGE_TARNAME = @PACKAGE_TARNAME@ PACKAGE_URL = @PACKAGE_URL@ PACKAGE_VERSION = @PACKAGE_VERSION@ PATH_SEPARATOR = @PATH_SEPARATOR@ PERL = @PERL@ PERL_CCCDLFLAGS = @PERL_CCCDLFLAGS@ PERL_PREINSTALL = @PERL_PREINSTALL@ PKG_CONFIG = @PKG_CONFIG@ PKG_CONFIG_COM_ERR_LIB = @PKG_CONFIG_COM_ERR_LIB@ PKG_CONFIG_LIBDIR = @PKG_CONFIG_LIBDIR@ PKG_CONFIG_PATH = @PKG_CONFIG_PATH@ RANLIB = @RANLIB@ SASLFLAGS = @SASLFLAGS@ SED = @SED@ SET_MAKE = @SET_MAKE@ SHELL = @SHELL@ SNMP_CONFIG = @SNMP_CONFIG@ SQLITE3_CFLAGS = @SQLITE3_CFLAGS@ SQLITE3_LIBS = @SQLITE3_LIBS@ SSL_CPPFLAGS = @SSL_CPPFLAGS@ SSL_LIBS = @SSL_LIBS@ STRIP = @STRIP@ VERSION = @VERSION@ XML2_CFLAGS = @XML2_CFLAGS@ XML2_LIBS = @XML2_LIBS@ YACC = @YACC@ YFLAGS = @YFLAGS@ ZEPHYR_LIBS = @ZEPHYR_LIBS@ ZLIB = @ZLIB@ abs_builddir = @abs_builddir@ abs_srcdir = @abs_srcdir@ abs_top_builddir = @abs_top_builddir@ abs_top_srcdir = @abs_top_srcdir@ ac_ct_AR = @ac_ct_AR@ ac_ct_CC = @ac_ct_CC@ ac_ct_DUMPBIN = @ac_ct_DUMPBIN@ am__include = @am__include@ am__leading_dot = @am__leading_dot@ am__quote = @am__quote@ am__tar = @am__tar@ am__untar = @am__untar@ bindir = @bindir@ build = @build@ build_alias = @build_alias@ build_cpu = @build_cpu@ build_os = @build_os@ build_vendor = @build_vendor@ builddir = @builddir@ cyrus_cv_sigveclib = @cyrus_cv_sigveclib@ cyrus_group = @cyrus_group@ cyrus_user = @cyrus_user@ datadir = @datadir@ datarootdir = @datarootdir@ docdir = @docdir@ dvidir = @dvidir@ exec_prefix = @exec_prefix@ host = @host@ host_alias = @host_alias@ host_cpu = @host_cpu@ host_os = @host_os@ host_vendor = @host_vendor@ htmldir = @htmldir@ includedir = @includedir@/cyrus infodir = @infodir@ install_sh = @install_sh@ libdir = @libdir@ libexecdir = @libexecdir@ localedir = @localedir@ localstatedir = @localstatedir@ mandir = @mandir@ mkdir_p = @mkdir_p@ oldincludedir = @oldincludedir@ pdfdir = @pdfdir@ prefix = @prefix@ program_transform_name = @program_transform_name@ psdir = @psdir@ runstatedir = @runstatedir@ sbindir = @sbindir@ servicedir = @servicedir@ sharedstatedir = @sharedstatedir@ srcdir = @srcdir@ sysconfdir = @sysconfdir@ target = @target@ target_alias = @target_alias@ target_cpu = @target_cpu@ target_os = @target_os@ target_vendor = @target_vendor@ top_build_prefix = @top_build_prefix@ top_builddir = @top_builddir@ top_srcdir = @top_srcdir@ userdir = @userdir@ ACLOCAL_AMFLAGS = -I cmulocal AM_CFLAGS = @PERL_CCCDLFLAGS@ $(COV_CFLAGS) AM_CPPFLAGS = $(COM_ERR_CPPFLAGS) -I${top_builddir} \ -I${top_builddir}/lib -I${top_srcdir} -I${top_srcdir}/lib \ ${DEFS} ${LOCALDEFS} $(SASLFLAGS) $(SSL_CPPFLAGS) \ $(am__append_1) $(am__append_14) AM_LDFLAGS = $(COV_LDFLAGS) $(am__append_15) BUILT_SOURCES = xversion.h imap/imap_err.c lib/imapopts.c \ lib/imapopts.h $(am__append_2) $(am__append_4) \ $(am__append_16) $(am__append_34) $(am__append_40) DISTCLEANFILES = \ imap/imap_err.c \ imap/imap_err.h \ imap/mupdate_err.c \ imap/mupdate_err.h \ imap/nntp_err.c \ imap/nntp_err.h \ imap/http_err.c \ imap/http_err.h \ imap/tz_err.c \ imap/tz_err.h \ com_err/et/compile_et \ perl/annotator/Makefile \ perl/annotator/Makefile.PL \ perl/imap/Makefile \ perl/imap/Makefile.PL \ perl/sieve/managesieve/Makefile \ perl/sieve/managesieve/Makefile.PL \ perl/sieve/scripts/installsieve \ perl/sieve/scripts/sieveshell \ sieve/sieve_err.c \ sieve/sieve_err.h MAINTAINERCLEANFILES = \ doc/murder.png \ doc/netnews.png \ doc/man/cyradm.1.html \ man/imapd.conf.5 \ man/sieveshell.1 \ doc/man/sieveshell.1.html \ imap/lmtpstats.h \ imap/pushstats.h \ lib/chartable.c \ lib/imapopts.h \ sieve/addr.h \ sieve/sieve.h SUBDIRS = . $(am__append_31) $(am__append_33) DIST_SUBDIRS = . dist_sysconf_DATA = $(am__append_27) lib_LTLIBRARIES = lib/libcyrus_min.la lib/libcyrus.la $(am__append_3) \ $(am__append_5) $(am__append_36) noinst_HEADERS = lib/byteorder64.h lib/gai.h lib/libconfig.h lib/md5.h \ lib/prot.h lib/ptrarray.h lib/util.h lib/xstrlcat.h \ lib/xstrlcpy.h noinst_LTLIBRARIES = $(am__append_32) $(am__append_35) CLEANFILES = $(am__append_41) EXTRA_DIST = $(wildcard tools/vzic/*) $(am__append_25) \ $(am__append_26) COPYING INSTALL README.andrew SMakefile \ xversion.h com_err/et/et_c.awk com_err/et/et_h.awk \ com_err/et/test1.et com_err/et/test2.et com_err/et/test_et.c \ contrib/allow-broken-sslv23.patch contrib/drac_auth.patch \ contrib/sieve-spamasssassin contrib/fud-client.c \ contrib/deliver-notify-zephyr.patch contrib/add-cyrus-user \ contrib/README contrib/cyrus-graphtools.1.0 \ contrib/cyrus-graphtools.1.0/cgi-bin/cyrus_master.pl \ contrib/cyrus-graphtools.1.0/cgi-bin/graph_cyrus_db.pl \ contrib/cyrus-graphtools.1.0/cgi-bin/graph_cyrus_db-sum.pl \ contrib/cyrus-graphtools.1.0/html \ contrib/cyrus-graphtools.1.0/html/index.html \ contrib/cyrus-graphtools.1.0/README \ contrib/cyrus-graphtools.1.0/script \ contrib/cyrus-graphtools.1.0/script/cyrus.pl \ contrib/cyrus-graphtools.1.0/script/run \ contrib/cyrus-graphtools.1.0/script/cyrusrc \ contrib/dkim_canon_ischedule.patch contrib/notify_unix/notify \ contrib/notify_unix/net-server-prefork-0.01.tgz \ contrib/notify_unix/README contrib/notify_unix/sql_notify.pl \ contrib/notify_unix/simple_notify.pl contrib/squatrunner.pl \ contrib/mupdate-test.pl contrib/squatrunner.txt \ cunit/cacert.pem cunit/cert.pem cunit/cunit.pl \ cunit/cunit-to-junit.pl cunit/key.pem cunit/vg.supp \ doc/murder.png doc/netnews.png doc imap/dav_util.h \ imap/http_err.et imap/imap_err.et imap/mupdate_err.et \ imap/nntp_err.et imap/rfc822_header.st imap/tz_err.et \ lib/charset/aliases.txt lib/charset/big5.t \ lib/charset/gb2312.t lib/charset/iso-2022-jp.t \ lib/charset/iso-2022-kr.t lib/charset/iso-8859-10.t \ lib/charset/iso-8859-11.t lib/charset/iso-8859-13.t \ lib/charset/iso-8859-14.t lib/charset/iso-8859-15.t \ lib/charset/iso-8859-16.t lib/charset/iso-8859-1.t \ lib/charset/iso-8859-2.t lib/charset/iso-8859-3.t \ lib/charset/iso-8859-4.t lib/charset/iso-8859-5.t \ lib/charset/iso-8859-6.t lib/charset/iso-8859-7.t \ lib/charset/iso-8859-8.t lib/charset/iso-8859-9.t \ lib/charset/koi8-r.t lib/charset/UnicodeData.txt \ lib/charset/unifix.txt lib/charset/us-ascii.t \ lib/charset/windows-1250.t lib/charset/windows-1251.t \ lib/charset/windows-1252.t lib/charset/windows-1254.t \ lib/charset/windows-1255.t lib/charset/windows-1256.t \ lib/charset/windows-1258.t lib/charset/windows-874.t \ lib/imapoptions lib/test/cyrusdb.c lib/test/cyrusdb.INPUT \ lib/test/cyrusdblong.INPUT lib/test/cyrusdblong.OUTPUT \ lib/test/cyrusdb.OUTPUT lib/test/cyrusdbtxn.INPUT \ lib/test/cyrusdbtxn.OUTPUT lib/test/pool.c lib/test/rnddb.c \ lib/test/testglob2.c master/CYRUS-MASTER.mib \ master/conf/cmu-backend.conf master/conf/cmu-frontend.conf \ master/conf/normal.conf master/conf/prefork.conf \ master/conf/small.conf master/README netnews/inn.diffs \ perl/annotator/Daemon.pm perl/annotator/Makefile.PL.in \ perl/annotator/MANIFEST perl/annotator/Message.pm \ perl/annotator/README perl/imap/Changes perl/imap/cyradm.sh \ perl/imap/cyrperl.h perl/imap/Cyrus/Shell.pm \ perl/imap/examples/auditmbox.pl \ perl/imap/examples/imapcollate.pl perl/imap/examples/imapdu.pl \ perl/imap/examples/test-imsp.pl perl/imap/IMAP/Admin.pm \ perl/imap/IMAP/IMSP.pm perl/imap/IMAP/Shell.pm \ perl/imap/IMAP.pm perl/imap/IMAP.xs perl/imap/Makefile.PL.in \ perl/imap/MANIFEST perl/imap/README perl/imap/t/01-imclient.t \ perl/imap/t/02-admin.t perl/imap/typemap perl/imap/xsutil.c \ perl/sieve/managesieve/Makefile.PL.in \ perl/sieve/managesieve/managesieve.h \ perl/sieve/managesieve/managesieve.pm \ perl/sieve/managesieve/managesieve.xs \ perl/sieve/managesieve/MANIFEST perl/sieve/managesieve/typemap \ ptclient/README ptclient/test.c ptclient/test2.c sieve/addr.h \ sieve/sieve.h sieve/sieve_err.et sieve/tests/testExtension \ sieve/tests/testExtension/uberExtensionTestScript.key \ sieve/tests/testExtension/testm \ sieve/tests/testExtension/testm/uetest-envelope \ sieve/tests/testExtension/testm/uetest-asub \ sieve/tests/testExtension/testm/uetest-areg \ sieve/tests/testExtension/testm/uetest-count \ sieve/tests/testExtension/testm/uetest-value \ sieve/tests/testExtension/testm/uetest-hreg \ sieve/tests/testExtension/serverm \ sieve/tests/testExtension/serverm/uetmail-hreg \ sieve/tests/testExtension/serverm/uetmail-value \ sieve/tests/testExtension/serverm/uetmail-count2 \ sieve/tests/testExtension/serverm/uetmail-envelope \ sieve/tests/testExtension/serverm/uetmail-asub \ sieve/tests/testExtension/serverm/uetmail-value2 \ sieve/tests/testExtension/serverm/uetmail-areg \ sieve/tests/testExtension/serverm/uetmail-count \ sieve/tests/testExtension/uberExtensionTestScript.s \ sieve/tests/README sieve/tests/action sieve/tests/action/testm \ sieve/tests/action/testm/uatest-keep \ sieve/tests/action/testm/uatest-redirect \ sieve/tests/action/testm/uatest-discard \ sieve/tests/action/testm/uatest-stop2 \ sieve/tests/action/testm/uatest-stop \ sieve/tests/action/serverm \ sieve/tests/action/serverm/uamail-stop2 \ sieve/tests/action/serverm/uamail-redirect \ sieve/tests/action/serverm/uamail-stop \ sieve/tests/action/serverm/uamail-keep \ sieve/tests/action/serverm/uamail-discard \ sieve/tests/action/uberActionScript.key \ sieve/tests/action/uberActionScript.s sieve/tests/test \ sieve/tests/test/uberTestScript.key sieve/tests/test/testm \ sieve/tests/test/testm/utest-header \ sieve/tests/test/testm/utest-address sieve/tests/test/serverm \ sieve/tests/test/serverm/utmail-address \ sieve/tests/test/serverm/utmail-header \ sieve/tests/test/uberTestScript.s sieve/tests/actionExtensions \ sieve/tests/actionExtensions/uberExtensionActionScript.s \ sieve/tests/actionExtensions/testm \ sieve/tests/actionExtensions/testm/ueatest-flag4 \ sieve/tests/actionExtensions/testm/ueatest-flag2 \ sieve/tests/actionExtensions/testm/ueatest-fileinto \ sieve/tests/actionExtensions/testm/ueatest-denotify \ sieve/tests/actionExtensions/testm/ueatest-vacation \ sieve/tests/actionExtensions/testm/ueatest-reject \ sieve/tests/actionExtensions/testm/ueatest-mark \ sieve/tests/actionExtensions/testm/ueatest-denotify2 \ sieve/tests/actionExtensions/testm/ueatest-flag5 \ sieve/tests/actionExtensions/testm/ueatest-notify2 \ sieve/tests/actionExtensions/testm/ueatest-notify \ sieve/tests/actionExtensions/testm/ueatest-flag1 \ sieve/tests/actionExtensions/testm/ueatest-flag3 \ sieve/tests/actionExtensions/testm/ueatest-unmark \ sieve/tests/actionExtensions/uberExtensionActionScript.key \ sieve/tests/actionExtensions/serverm \ sieve/tests/actionExtensions/serverm/ueamail-flag4 \ sieve/tests/actionExtensions/serverm/ueamail-denotify \ sieve/tests/actionExtensions/serverm/ueamail-mark \ sieve/tests/actionExtensions/serverm/ueamail-denotify2 \ sieve/tests/actionExtensions/serverm/ueamail-flag2 \ sieve/tests/actionExtensions/serverm/ueamail-unmark \ sieve/tests/actionExtensions/serverm/ueamail-reject \ sieve/tests/actionExtensions/serverm/ueamail-flag3 \ sieve/tests/actionExtensions/serverm/ueamail-fileinto \ sieve/tests/actionExtensions/serverm/ueamail-flag1 \ sieve/tests/actionExtensions/serverm/ueamail-notify \ sieve/tests/actionExtensions/serverm/ueamail-flag5 \ sieve/tests/actionExtensions/serverm/ueamail-notify2 \ sieve/tests/actionExtensions/serverm/ueamail-vacation \ timsieved/TODO $(am__append_45) $(am__append_46) \ $(am__append_72) $(am__append_74) @COM_ERR_TRUE@COMPILE_ET_DEP = com_err/et/compile_et @PERL_TRUE@@SIEVE_TRUE@noinst_LIBRARIES = perl/sieve/lib/libisieve.a TEXINFO_TEX = com_err/et/texinfo.tex dist_noinst_SCRIPTS = \ com_err/et/compile_et.sh \ com_err/et/config_script \ imap/lmtpstats.snmp \ imap/pushstats.snmp \ lib/mkchartable.pl \ lib/test/run \ perl/sieve/scripts/installsieve.pl \ perl/sieve/scripts/sieveshell.pl \ tools/arbitronsort.pl \ tools/compile_st.pl \ tools/config2header \ tools/config2man \ tools/convert-sieve.pl \ tools/dohash \ tools/fixsearchpath.pl \ tools/git-version.sh \ tools/jenkins-build.sh \ tools/masssievec \ tools/migrate-metadata \ tools/mkimap \ tools/mknewsgroups \ tools/mupdate-loadgen.pl \ tools/rehash \ tools/translatesieve \ tools/undohash \ tools/upgradesieve \ snmp/snmpgen noinst_MAN = \ com_err/et/com_err.3 \ com_err/et/compile_et.1 noinst_TEXINFOS = com_err/et/com_err.texinfo pkgconfigdir = $(libdir)/pkgconfig pkgconfig_DATA = libcyrus_min.pc libcyrus.pc libcyrus_sieve.pc com_err_et_libcyrus_com_err_la_SOURCES = \ com_err/et/com_err.c \ com_err/et/com_err.h \ com_err/et/error_message.c \ com_err/et/error_table.h \ com_err/et/et_name.c \ com_err/et/init_et.c \ com_err/et/internal.h \ com_err/et/mit-sipb-copyright.h com_err_et_libcyrus_com_err_la_CFLAGS = $(AM_CFLAGS) $(CFLAG_VISIBILITY) # ---- Libraries ---- # BASIC is the libraries that every Cyrus program (except master) will # need to link with. # # Note that several places in the code use -lcrypto, e.g. for SHA1 or # MD5 algorithms, without needing SSL. Currently we have no way of # minimally linking such code. LD_BASIC_ADD = lib/libcyrus.la lib/libcyrus_min.la ${LIBS} $(LIB_RT) \ ${LIB_SASL} $(SSL_LIBS) # UTILITY is the libraries that utility programs which use Cyrus' # mailbox and message handling code need to link with. LD_UTILITY_ADD = imap/libcyrus_imap.la $(LD_BASIC_ADD) $(COM_ERR_LIBS) # SERVER is the libraries that network-facing servers need to link with # # Note that the code is horribly intertwingled e.g. in imap/global.c # so that even utilities which never open a socket need to link against # the SASL library. LD_SERVER_ADD = $(LD_UTILITY_ADD) $(LIB_WRAP) # ---- @CUNIT_TRUE@CUNIT_PROJECT = cunit/default.cunit @CUNIT_TRUE@cunit_FRAMEWORK = \ @CUNIT_TRUE@ cunit/unit.c \ @CUNIT_TRUE@ cunit/cunit.h \ @CUNIT_TRUE@ cunit/syslog.c \ @CUNIT_TRUE@ cunit/cunit-syslog.h \ @CUNIT_TRUE@ cunit/timeout.c \ @CUNIT_TRUE@ cunit/timeout.h @CUNIT_TRUE@cunit_TESTS = cunit/annotate.testc cunit/backend.testc \ @CUNIT_TRUE@ cunit/binhex.testc cunit/bitvector.testc \ @CUNIT_TRUE@ cunit/buf.testc cunit/byteorder64.testc \ @CUNIT_TRUE@ cunit/charset.testc cunit/crc32.testc \ @CUNIT_TRUE@ cunit/db.testc cunit/dlist.testc \ @CUNIT_TRUE@ cunit/duplicate.testc cunit/getxstring.testc \ @CUNIT_TRUE@ cunit/glob.testc cunit/guid.testc cunit/hash.testc \ @CUNIT_TRUE@ cunit/imapurl.testc cunit/mboxname.testc \ @CUNIT_TRUE@ cunit/md5.testc cunit/message.testc \ @CUNIT_TRUE@ cunit/msgid.testc cunit/parseaddr.testc \ @CUNIT_TRUE@ cunit/parse.testc cunit/prot.testc \ @CUNIT_TRUE@ cunit/ptrarray.testc cunit/quota.testc \ @CUNIT_TRUE@ cunit/rfc822tok.testc $(am__append_43) \ @CUNIT_TRUE@ cunit/spool.testc cunit/squat.testc \ @CUNIT_TRUE@ cunit/strarray.testc cunit/strconcat.testc \ @CUNIT_TRUE@ cunit/times.testc cunit/tok.testc @CUNIT_TRUE@cunit_unit_SOURCES = $(cunit_FRAMEWORK) $(cunit_TESTS) \ @CUNIT_TRUE@ imap/mutex_fake.c imap/spool.c @CUNIT_TRUE@cunit_unit_LDADD = $(am__append_44) $(LD_UTILITY_ADD) \ @CUNIT_TRUE@ -lcunit @CUNIT_TRUE@CUNIT_PL = cunit/cunit.pl --project $(CUNIT_PROJECT) # To run under Valgrind, do: make VG=1 check @CUNIT_TRUE@VALGRIND = valgrind --tool=memcheck --leak-check=full --suppressions=vg.supp tools_htmlstrip_SOURCE = tools/htmlstrip.c include_HEADERS = \ lib/acl.h \ lib/arrayu64.h \ lib/assert.h \ lib/auth.h \ lib/auth_pts.h \ lib/bitvector.h \ lib/bsearch.h \ lib/charset.h \ lib/chartable.h \ lib/command.h \ lib/crc32.h \ lib/cyr_lock.h \ lib/cyrusdb.h \ lib/exitcodes.h \ lib/glob.h \ lib/gmtoff.h \ lib/hash.h \ lib/hashu64.h \ lib/imapurl.h \ lib/imclient.h \ lib/imparse.h \ lib/iostat.h \ lib/iptostring.h \ lib/libcyr_cfg.h \ lib/lsort.h \ lib/map.h \ lib/mappedfile.h \ lib/mkgmtime.h \ lib/mpool.h \ lib/nonblock.h \ lib/parseaddr.h \ lib/retry.h \ lib/rfc822tok.h \ lib/signals.h \ lib/strarray.h \ lib/strhash.h \ lib/stristr.h \ lib/sysexits.h \ lib/times.h \ lib/tok.h \ lib/vparse.h \ lib/wildmat.h \ lib/xmalloc.h nodist_include_HEADERS = \ lib/imapopts.h nobase_include_HEADERS = sieve/sieve_interface.h nobase_nodist_include_HEADERS = sieve/sieve_err.h imap_arbitron_SOURCES = imap/arbitron.c imap/cli_fatal.c imap/mutex_fake.c imap_arbitron_LDADD = $(LD_UTILITY_ADD) imap_chk_cyrus_SOURCES = imap/chk_cyrus.c imap/cli_fatal.c imap/mutex_fake.c imap_chk_cyrus_LDADD = $(LD_UTILITY_ADD) imap_ctl_cyrusdb_SOURCES = imap/cli_fatal.c imap/ctl_cyrusdb.c imap/mutex_fake.c imap_ctl_cyrusdb_LDADD = $(LD_UTILITY_ADD) imap_ctl_deliver_SOURCES = imap/cli_fatal.c imap/ctl_deliver.c imap/mutex_fake.c imap_ctl_deliver_LDADD = $(LD_UTILITY_ADD) imap_ctl_mboxlist_SOURCES = imap/cli_fatal.c imap/ctl_mboxlist.c imap/mutex_fake.c imap_ctl_mboxlist_LDADD = $(LD_UTILITY_ADD) imap_cvt_cyrusdb_SOURCES = imap/cli_fatal.c imap/cvt_cyrusdb.c imap/mutex_fake.c imap_cvt_cyrusdb_LDADD = $(LD_UTILITY_ADD) imap_cyrdump_SOURCES = imap/cli_fatal.c imap/cyrdump.c imap/mutex_fake.c imap_cyrdump_LDADD = $(LD_UTILITY_ADD) imap_cyr_dbtool_SOURCES = imap/cli_fatal.c imap/cyr_dbtool.c imap/mutex_fake.c imap_cyr_dbtool_LDADD = $(LD_UTILITY_ADD) imap_cyr_deny_SOURCES = imap/cli_fatal.c imap/cyr_deny.c imap/mutex_fake.c imap_cyr_deny_LDADD = $(LD_UTILITY_ADD) imap_cyr_df_SOURCES = imap/cli_fatal.c imap/cyr_df.c imap/mutex_fake.c imap_cyr_df_LDADD = $(LD_UTILITY_ADD) imap_cyr_expire_SOURCES = imap/cli_fatal.c imap/cyr_expire.c imap/mutex_fake.c imap_cyr_expire_LDADD = $(LD_UTILITY_ADD) imap_cyr_info_SOURCES = imap/cli_fatal.c imap/cyr_info.c imap/mutex_fake.c master/masterconf.c imap_cyr_info_LDADD = $(LD_UTILITY_ADD) imap_cyr_sequence_SOURCES = imap/cli_fatal.c imap/cyr_sequence.c imap/mutex_fake.c imap_cyr_sequence_LDADD = $(LD_UTILITY_ADD) imap_cyr_synclog_SOURCES = imap/cli_fatal.c imap/cyr_synclog.c imap/mutex_fake.c imap_cyr_synclog_LDADD = $(LD_UTILITY_ADD) imap_cyr_userseen_SOURCES = imap/cli_fatal.c imap/cyr_userseen.c imap/mutex_fake.c imap_cyr_userseen_LDADD = $(LD_UTILITY_ADD) @HAVE_CLAMAV_TRUE@imap_cyr_virusscan_SOURCES = imap/cli_fatal.c imap/cyr_virusscan.c imap/mutex_fake.c @HAVE_CLAMAV_TRUE@imap_cyr_virusscan_LDADD = $(LD_UTILITY_ADD) -lclamav @HTTPD_TRUE@imap_ctl_zoneinfo_SOURCES = imap/cli_fatal.c imap/ctl_zoneinfo.c imap/mutex_fake.c @HTTPD_TRUE@imap_ctl_zoneinfo_LDADD = $(LD_UTILITY_ADD) imap_deliver_SOURCES = \ imap/deliver.c \ imap/lmtpengine.c \ imap/lmtpstats.c \ imap/mutex_fake.c \ imap/proxy.c \ imap/spool.c imap_deliver_LDADD = $(LD_UTILITY_ADD) imap_fetchnews_SOURCES = imap/cli_fatal.c imap/fetchnews.c imap/mutex_fake.c imap_fetchnews_LDADD = $(LD_UTILITY_ADD) imap_fud_SOURCES = imap/fud.c imap/mutex_fake.c master/service.c imap_fud_LDADD = $(LD_SERVER_ADD) imap_idled_SOURCES = imap/idled.c imap/mutex_fake.c imap_idled_LDADD = $(LD_UTILITY_ADD) imap_imapd_SOURCES = imap/imap_proxy.c imap/imap_proxy.h imap/imapd.c \ imap/imapd.h imap/mutex_fake.c imap/pushstats.c \ imap/pushstats.h imap/proxy.c imap/proxy.h master/service.c \ $(am__append_47) imap_imapd_LDADD = $(am__append_48) $(LD_SERVER_ADD) imap_ipurge_SOURCES = imap/cli_fatal.c imap/ipurge.c imap/mutex_fake.c imap_ipurge_LDADD = $(LD_UTILITY_ADD) nodist_imap_libcyrus_imap_la_SOURCES = imap/imap_err.c \ imap/mupdate_err.c imap/mupdate_err.h $(am__append_52) dist_imap_libcyrus_imap_la_SOURCES = imap_libcyrus_imap_la_SOURCES = imap/annotate.c imap/annotate.h \ imap/append.c imap/append.h imap/backend.c imap/backend.h \ imap/convert_code.c imap/convert_code.h imap/dlist.c \ imap/dlist.h imap/duplicate.c imap/duplicate.h imap/global.c \ imap/global.h imap/idle.c imap/idle.h imap/idlemsg.c \ imap/idlemsg.h imap/imapparse.c imap/index.c imap/index.h \ imap/mailbox.c imap/mailbox.h imap/mbdump.c imap/mbdump.h \ imap/mboxkey.c imap/mboxkey.h imap/mboxlist.c imap/mboxlist.h \ imap/mboxevent.c imap/mboxevent.h imap/mboxname.c \ imap/mboxname.h imap/message_guid.c imap/message_guid.h \ imap/message.c imap/message.h imap/mupdate-client.c \ imap/mupdate-client.h imap/mutex.h imap/notify.c imap/notify.h \ imap/partlist.c imap/partlist.h imap/proc.c imap/proc.h \ imap/protocol.h imap/quota_db.c imap/rfc822_header.c \ imap/rfc822_header.h imap/saslclient.c imap/saslclient.h \ imap/saslserver.c imap/search_engines.c imap/search_engines.h \ imap/seen.h imap/seen_db.c imap/sequence.c imap/sequence.h \ imap/setproctitle.c imap/squat.c imap/squat.h \ imap/squat_internal.c imap/squat_internal.h imap/statuscache.h \ imap/statuscache_db.c imap/sync_log.c imap/sync_log.h \ imap/telemetry.c imap/telemetry.h imap/tls.c imap/tls.h \ imap/tls_th-lock.c imap/tls_th-lock.h imap/user.c imap/user.h \ imap/userdeny_db.c imap/userdeny.h imap/version.c \ imap/version.h $(am__append_51) imap_libcyrus_imap_la_LIBADD = $(COM_ERR_LIBS) $(LIB_UUID) \ lib/libcyrus_min.la lib/libcyrus.la $(am__append_49) imap_libcyrus_imap_la_CFLAGS = $(AM_CFLAGS) $(CFLAG_VISIBILITY) \ $(am__append_50) imap_lmtpd_SOURCES = imap/lmtpd.c imap/lmtpd.h imap/lmtpengine.c \ imap/lmtpengine.h imap/lmtpstats.c imap/lmtpstats.h \ imap/mutex_fake.c imap/proxy.c imap/spool.c master/service.c \ $(am__append_53) $(am__append_54) imap_lmtpd_LDADD = $(am__append_55) $(LD_SERVER_ADD) imap_mbexamine_SOURCES = imap/cli_fatal.c imap/mbexamine.c imap/mutex_fake.c imap_mbexamine_LDADD = $(LD_UTILITY_ADD) imap_mbpath_SOURCES = imap/cli_fatal.c imap/mbpath.c imap/mutex_fake.c imap_mbpath_LDADD = $(LD_UTILITY_ADD) imap_mbtool_SOURCES = imap/cli_fatal.c imap/mbtool.c imap/mutex_fake.c imap_mbtool_LDADD = $(LD_UTILITY_ADD) imap_mupdate_SOURCES = \ imap/mupdate.c \ imap/mupdate.h \ imap/mupdate-slave.c \ imap/mutex_pthread.c \ imap/tls_th-lock.c \ master/service-thread.c imap_mupdate_LDADD = $(LD_SERVER_ADD) -lpthread nodist_imap_nntpd_SOURCES = \ imap/nntp_err.c \ imap/nntp_err.h imap_nntpd_SOURCES = \ imap/mutex_fake.c \ imap/nntpd.c \ imap/proxy.c \ imap/smtpclient.c \ imap/smtpclient.h \ imap/spool.c \ imap/spool.h \ master/service.c imap_nntpd_LDADD = $(LD_SERVER_ADD) nodist_imap_httpd_SOURCES = \ imap/http_err.c \ imap/http_err.h \ imap/tz_err.c \ imap/tz_err.h imap_httpd_SOURCES = \ imap/caldav_db.c \ imap/carddav_db.c \ imap/carddav_db.h \ imap/dav_db.c \ imap/dav_util.c \ imap/http_caldav.c \ imap/http_carddav.c \ imap/http_client.c \ imap/http_dav.c \ imap/http_dblookup.c \ imap/http_ischedule.c \ imap/http_proxy.c \ imap/http_rss.c \ imap/http_timezone.c \ imap/httpd.c \ imap/jcal.c \ imap/json_support.h \ imap/mutex_fake.c \ imap/proxy.c \ imap/smtpclient.c \ imap/spool.c \ imap/xcal.c \ imap/zoneinfo_db.c \ master/service.c imap_httpd_LDADD = $(LD_SERVER_ADD) imap_pop3d_SOURCES = imap/mutex_fake.c imap/pop3d.c imap/proxy.c \ master/service.c $(am__append_56) imap_pop3d_LDADD = $(am__append_57) $(LD_SERVER_ADD) imap_quota_SOURCES = imap/cli_fatal.c imap/mutex_fake.c imap/quota.c imap/quota.h imap_quota_LDADD = $(LD_UTILITY_ADD) imap_reconstruct_SOURCES = imap/cli_fatal.c imap/mutex_fake.c imap/reconstruct.c imap_reconstruct_LDADD = $(LD_UTILITY_ADD) imap_dav_reconstruct_SOURCES = imap/cli_fatal.c imap/mutex_fake.c imap/dav_reconstruct.c imap_dav_reconstruct_LDADD = $(LD_UTILITY_ADD) imap_smmapd_SOURCES = imap/mutex_fake.c imap/proxy.c imap/smmapd.c master/service.c imap_smmapd_LDADD = $(LD_SERVER_ADD) imap_squatter_SOURCES = imap/cli_fatal.c imap/mutex_fake.c imap/squatter.c imap/squat_build.c imap_squatter_LDADD = $(LD_UTILITY_ADD) imap_sync_client_SOURCES = imap/mutex_fake.c imap/sync_client.c \ imap/sync_support.c imap/sync_support.h imap_sync_client_LDADD = $(LD_UTILITY_ADD) imap_sync_reset_SOURCES = imap/mutex_fake.c imap/sync_reset.c imap/sync_support.c imap_sync_reset_LDADD = $(LD_UTILITY_ADD) imap_sync_server_SOURCES = imap/mutex_fake.c imap/sync_server.c imap/sync_support.c master/service.c imap_sync_server_LDADD = $(LD_SERVER_ADD) imap_tls_prune_SOURCES = imap/cli_fatal.c imap/mutex_fake.c imap/tls_prune.c imap_tls_prune_LDADD = $(LD_UTILITY_ADD) imap_unexpunge_SOURCES = imap/cli_fatal.c imap/mutex_fake.c imap/unexpunge.c imap_unexpunge_LDADD = $(LD_UTILITY_ADD) imtest_imtest_SOURCES = imtest/imtest.c imtest_imtest_LDADD = $(LD_BASIC_ADD) imtest_imtest_CFLAGS = $(AM_CFLAGS) $(CFLAG_VISIBILITY) nodist_lib_libcyrus_la_SOURCES = lib/chartable.c lib_libcyrus_la_SOURCES = lib/acl.c lib/acl_afs.c lib/auth.c \ lib/auth_krb.c lib/auth_krb5.c lib/auth_pts.c lib/auth_unix.c \ lib/bitvector.c lib/bsearch.c lib/byteorder64.c lib/charset.c \ lib/command.c lib/crc32.c lib/cyrusdb.c lib/cyrusdb_flat.c \ lib/cyrusdb_quotalegacy.c lib/cyrusdb_skiplist.c \ lib/cyrusdb_twoskip.c lib/glob.c lib/imapurl.c lib/imclient.c \ lib/imparse.c lib/iostat.c lib/iptostring.c lib/libcyr_cfg.c \ lib/lsort.c lib/mappedfile.c lib/mkgmtime.c lib/parseaddr.c \ lib/prot.c lib/ptrarray.c lib/rfc822tok.c lib/signals.c \ lib/stristr.c lib/times.c lib/tok.c lib/wildmat.c \ $(am__append_58) $(am__append_59) $(am__append_60) \ $(am__append_61) $(am__append_62) $(am__append_63) lib_libcyrus_la_LIBADD = $(LIB_RT) ${LIB_SASL} $(SSL_LIBS) lib_libcyrus_la_CFLAGS = $(AM_CFLAGS) $(CFLAG_VISIBILITY) nodist_lib_libcyrus_min_la_SOURCES = \ lib/imapopts.c lib_libcyrus_min_la_SOURCES = lib/arrayu64.c lib/assert.c lib/hash.c \ lib/hashu64.c lib/libconfig.c lib/mpool.c lib/retry.c \ lib/strarray.c lib/strhash.c lib/util.c lib/vparse.c \ lib/xmalloc.c lib/xstrlcat.c lib/xstrlcpy.c $(am__append_64) \ $(am__append_65) $(am__append_66) $(am__append_67) \ $(am__append_68) $(am__append_69) $(am__append_70) lib_libcyrus_min_la_LIBADD = $(LTLIBOBJS) lib_libcyrus_min_la_CFLAGS = $(AM_CFLAGS) $(CFLAG_VISIBILITY) dist_man_MANS = man/imtest.1 man/installsieve.1 man/lmtptest.1 \ man/mupdatetest.1 man/nntptest.1 man/pop3test.1 \ man/sieveshell.1 man/sivtest.1 man/smtptest.1 man/imclient.3 \ man/cyrus.conf.5 man/imapd.conf.5 man/krb.equiv.5 \ man/arbitron.8 man/chk_cyrus.8 man/ctl_cyrusdb.8 \ man/ctl_deliver.8 man/ctl_mboxlist.8 man/cyr_expire.8 \ man/cvt_cyrusdb.8 man/cyr_dbtool.8 man/cyr_deny.8 man/cyr_df.8 \ man/cyr_info.8 man/cyr_synclog.8 man/deliver.8 man/fud.8 \ man/idled.8 man/imapd.8 man/ipurge.8 man/lmtpd.8 man/master.8 \ man/mbexamine.8 man/mbpath.8 man/notifyd.8 man/pop3d.8 \ man/quota.8 man/reconstruct.8 man/rmnews.8 man/smmapd.8 \ man/squatter.8 man/sync_client.8 man/sync_reset.8 \ man/sync_server.8 man/timsieved.8 man/tls_prune.8 \ man/unexpunge.8 $(am__append_71) $(am__append_73) master_master_SOURCES = \ master/cyrusMasterMIB.c \ master/cyrusMasterMIB.h \ master/master.c \ master/master.h \ master/masterconf.c \ master/masterconf.h \ master/service.h master_master_LDADD = lib/libcyrus_min.la $(LIB_UCDSNMP) $(LIBS) -lm netnews_remotepurge_SOURCES = \ netnews/macros.h \ netnews/readconfig.c \ netnews/readconfig.h \ netnews/remotepurge.c netnews_remotepurge_LDADD = $(LD_BASIC_ADD) notifyd_notifyd_SOURCES = imap/mutex_fake.c master/service.c \ notifyd/notify_external.c notifyd/notify_external.h \ notifyd/notify_log.c notifyd/notify_log.h \ notifyd/notify_mailto.c notifyd/notify_mailto.h \ notifyd/notify_null.c notifyd/notify_null.h notifyd/notifyd.c \ notifyd/notifyd.h $(am__append_75) notifyd_notifyd_LDADD = $(LD_SERVER_ADD) $(ZEPHYR_LIBS) notifyd_notifytest_SOURCES = notifyd/notifytest.c imap/mutex_fake.c notifyd_notifytest_LDADD = $(LD_BASIC_ADD) perl_libcyrus_la_SOURCES = $(lib_libcyrus_la_SOURCES) perl_libcyrus_la_LIBADD = $(lib_libcyrus_la_LIBADD) perl_libcyrus_min_la_SOURCES = $(lib_libcyrus_min_la_SOURCES) perl_libcyrus_min_la_LIBADD = $(lib_libcyrus_min_la_LIBADD) perl_sieve_lib_libisieve_a_SOURCES = \ perl/sieve/lib/codes.h \ perl/sieve/lib/isieve.c \ perl/sieve/lib/isieve.h \ perl/sieve/lib/lex.c \ perl/sieve/lib/lex.h \ perl/sieve/lib/request.c \ perl/sieve/lib/request.h ptclient_ptdump_SOURCES = imap/cli_fatal.c imap/mutex_fake.c ptclient/ptdump.c ptclient_ptdump_LDADD = $(LD_UTILITY_ADD) ptclient_ptexpire_SOURCES = imap/cli_fatal.c imap/mutex_fake.c ptclient/ptexpire.c ptclient_ptexpire_LDADD = $(LD_UTILITY_ADD) ptclient_ptloader_SOURCES = imap/mutex_fake.c ptclient/ptloader.c \ ptclient/ptloader.h master/service-thread.c $(am__append_76) \ $(am__append_79) ptclient_ptloader_LDFLAGS = $(am__append_78) $(am__append_81) ptclient_ptloader_LDADD = $(LD_SERVER_ADD) $(am__append_77) \ $(am__append_80) # Each new version of flex seems to generate new sign-comparison # warnings, while they switch code around between int/yy_size_t. # # This is a pain because most of us Cyrus devs build with -Werror. # # Instead of continuing to maintain an ever-growing, increasingly # precarious set of post-hoc fixes (see: the former lex-fix rule), # let's just ignore sign-comparison warnings from flex-generated # sources only. sieve_libcyrus_sieve_lex_la_SOURCES = \ sieve/addr-lex.l \ sieve/sieve-lex.l sieve_libcyrus_sieve_lex_la_LIBADD = sieve_libcyrus_sieve_lex_la_CFLAGS = $(AM_CFLAGS) $(CFLAG_VISIBILITY) -Wno-sign-compare nodist_sieve_libcyrus_sieve_la_SOURCES = \ sieve/sieve_err.c \ sieve/sieve_err.h sieve_libcyrus_sieve_la_SOURCES = \ sieve/bytecode.h \ sieve/addr.y \ sieve/bc_dump.c \ sieve/bc_emit.c \ sieve/bc_eval.c \ sieve/bc_generate.c \ sieve/comparator.c \ sieve/comparator.h \ sieve/flags.c \ sieve/flags.h \ sieve/interp.c \ sieve/interp.h \ sieve/message.c \ sieve/message.h \ sieve/script.c \ sieve/script.h \ sieve/sieve.y \ sieve/tree.c \ sieve/tree.h \ sieve/varlist.c \ sieve/varlist.h sieve_libcyrus_sieve_la_LIBADD = \ sieve/libcyrus_sieve_lex.la \ $(COM_ERR_LIBS) \ lib/libcyrus_min.la \ lib/libcyrus.la sieve_libcyrus_sieve_la_CFLAGS = $(AM_CFLAGS) $(CFLAG_VISIBILITY) LD_SIEVE_ADD = sieve/libcyrus_sieve.la $(LD_BASIC_ADD) sieve_sievec_LDADD = $(LD_SIEVE_ADD) sieve_sieved_LDADD = $(LD_SIEVE_ADD) sieve_test_SOURCES = sieve/test.c imap/mutex_fake.c sieve_test_LDADD = sieve/libcyrus_sieve.la $(LD_UTILITY_ADD) timsieved_timsieved_SOURCES = \ imap/mutex_fake.c \ imap/proxy.c \ master/service.c \ timsieved/actions.c \ timsieved/actions.h \ timsieved/codes.h \ timsieved/lex.c \ timsieved/lex.h \ timsieved/parser.c \ timsieved/parser.h \ timsieved/scripttest.c \ timsieved/scripttest.h \ timsieved/timsieved.c timsieved_timsieved_LDADD = sieve/libcyrus_sieve.la $(LD_SERVER_ADD) SUFFIXES = .fig.png all: $(BUILT_SOURCES) config.h $(MAKE) $(AM_MAKEFLAGS) all-recursive .SUFFIXES: .SUFFIXES: .fig.png .c .fig .l .lo .o .obj .png .testc .y am--refresh: Makefile @: $(srcdir)/Makefile.in: @MAINTAINER_MODE_TRUE@ $(srcdir)/Makefile.am $(am__configure_deps) @for dep in $?; do \ case '$(am__configure_deps)' in \ *$$dep*) \ echo ' cd $(srcdir) && $(AUTOMAKE) --foreign'; \ $(am__cd) $(srcdir) && $(AUTOMAKE) --foreign \ && exit 0; \ exit 1;; \ esac; \ done; \ echo ' cd $(top_srcdir) && $(AUTOMAKE) --foreign Makefile'; \ $(am__cd) $(top_srcdir) && \ $(AUTOMAKE) --foreign Makefile Makefile: $(srcdir)/Makefile.in $(top_builddir)/config.status @case '$?' in \ *config.status*) \ echo ' $(SHELL) ./config.status'; \ $(SHELL) ./config.status;; \ *) \ echo ' cd $(top_builddir) && $(SHELL) ./config.status $@ $(am__depfiles_maybe)'; \ cd $(top_builddir) && $(SHELL) ./config.status $@ $(am__depfiles_maybe);; \ esac; $(top_builddir)/config.status: $(top_srcdir)/configure $(CONFIG_STATUS_DEPENDENCIES) $(SHELL) ./config.status --recheck $(top_srcdir)/configure: @MAINTAINER_MODE_TRUE@ $(am__configure_deps) $(am__cd) $(srcdir) && $(AUTOCONF) $(ACLOCAL_M4): @MAINTAINER_MODE_TRUE@ $(am__aclocal_m4_deps) $(am__cd) $(srcdir) && $(ACLOCAL) $(ACLOCAL_AMFLAGS) $(am__aclocal_m4_deps): config.h: stamp-h1 @test -f $@ || rm -f stamp-h1 @test -f $@ || $(MAKE) $(AM_MAKEFLAGS) stamp-h1 stamp-h1: $(srcdir)/config.h.in $(top_builddir)/config.status @rm -f stamp-h1 cd $(top_builddir) && $(SHELL) ./config.status config.h $(srcdir)/config.h.in: @MAINTAINER_MODE_TRUE@ $(am__configure_deps) ($(am__cd) $(top_srcdir) && $(AUTOHEADER)) rm -f stamp-h1 touch $@ distclean-hdr: -rm -f config.h stamp-h1 libcyrus_min.pc: $(top_builddir)/config.status $(srcdir)/libcyrus_min.pc.in cd $(top_builddir) && $(SHELL) ./config.status $@ libcyrus.pc: $(top_builddir)/config.status $(srcdir)/libcyrus.pc.in cd $(top_builddir) && $(SHELL) ./config.status $@ libcyrus_sieve.pc: $(top_builddir)/config.status $(srcdir)/libcyrus_sieve.pc.in cd $(top_builddir) && $(SHELL) ./config.status $@ perl/annotator/Makefile.PL: $(top_builddir)/config.status $(top_srcdir)/perl/annotator/Makefile.PL.in cd $(top_builddir) && $(SHELL) ./config.status $@ perl/imap/Makefile.PL: $(top_builddir)/config.status $(top_srcdir)/perl/imap/Makefile.PL.in cd $(top_builddir) && $(SHELL) ./config.status $@ perl/sieve/managesieve/Makefile.PL: $(top_builddir)/config.status $(top_srcdir)/perl/sieve/managesieve/Makefile.PL.in cd $(top_builddir) && $(SHELL) ./config.status $@ clean-noinstLIBRARIES: -test -z "$(noinst_LIBRARIES)" || rm -f $(noinst_LIBRARIES) perl/sieve/lib/$(am__dirstamp): @$(MKDIR_P) perl/sieve/lib @: > perl/sieve/lib/$(am__dirstamp) perl/sieve/lib/$(DEPDIR)/$(am__dirstamp): @$(MKDIR_P) perl/sieve/lib/$(DEPDIR) @: > perl/sieve/lib/$(DEPDIR)/$(am__dirstamp) perl/sieve/lib/isieve.$(OBJEXT): perl/sieve/lib/$(am__dirstamp) \ perl/sieve/lib/$(DEPDIR)/$(am__dirstamp) perl/sieve/lib/lex.$(OBJEXT): perl/sieve/lib/$(am__dirstamp) \ perl/sieve/lib/$(DEPDIR)/$(am__dirstamp) perl/sieve/lib/request.$(OBJEXT): perl/sieve/lib/$(am__dirstamp) \ perl/sieve/lib/$(DEPDIR)/$(am__dirstamp) perl/sieve/lib/libisieve.a: $(perl_sieve_lib_libisieve_a_OBJECTS) $(perl_sieve_lib_libisieve_a_DEPENDENCIES) $(EXTRA_perl_sieve_lib_libisieve_a_DEPENDENCIES) perl/sieve/lib/$(am__dirstamp) $(AM_V_at)-rm -f perl/sieve/lib/libisieve.a $(AM_V_AR)$(perl_sieve_lib_libisieve_a_AR) perl/sieve/lib/libisieve.a $(perl_sieve_lib_libisieve_a_OBJECTS) $(perl_sieve_lib_libisieve_a_LIBADD) $(AM_V_at)$(RANLIB) perl/sieve/lib/libisieve.a install-libLTLIBRARIES: $(lib_LTLIBRARIES) @$(NORMAL_INSTALL) @list='$(lib_LTLIBRARIES)'; test -n "$(libdir)" || list=; \ list2=; for p in $$list; do \ if test -f $$p; then \ list2="$$list2 $$p"; \ else :; fi; \ done; \ test -z "$$list2" || { \ echo " $(MKDIR_P) '$(DESTDIR)$(libdir)'"; \ $(MKDIR_P) "$(DESTDIR)$(libdir)" || exit 1; \ echo " $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 '$(DESTDIR)$(libdir)'"; \ $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 "$(DESTDIR)$(libdir)"; \ } uninstall-libLTLIBRARIES: @$(NORMAL_UNINSTALL) @list='$(lib_LTLIBRARIES)'; test -n "$(libdir)" || list=; \ for p in $$list; do \ $(am__strip_dir) \ echo " $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=uninstall rm -f '$(DESTDIR)$(libdir)/$$f'"; \ $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=uninstall rm -f "$(DESTDIR)$(libdir)/$$f"; \ done clean-libLTLIBRARIES: -test -z "$(lib_LTLIBRARIES)" || rm -f $(lib_LTLIBRARIES) @list='$(lib_LTLIBRARIES)'; \ locs=`for p in $$list; do echo $$p; done | \ sed 's|^[^/]*$$|.|; s|/[^/]*$$||; s|$$|/so_locations|' | \ sort -u`; \ test -z "$$locs" || { \ echo rm -f $${locs}; \ rm -f $${locs}; \ } clean-noinstLTLIBRARIES: -test -z "$(noinst_LTLIBRARIES)" || rm -f $(noinst_LTLIBRARIES) @list='$(noinst_LTLIBRARIES)'; \ locs=`for p in $$list; do echo $$p; done | \ sed 's|^[^/]*$$|.|; s|/[^/]*$$||; s|$$|/so_locations|' | \ sort -u`; \ test -z "$$locs" || { \ echo rm -f $${locs}; \ rm -f $${locs}; \ } com_err/et/$(am__dirstamp): @$(MKDIR_P) com_err/et @: > com_err/et/$(am__dirstamp) com_err/et/$(DEPDIR)/$(am__dirstamp): @$(MKDIR_P) com_err/et/$(DEPDIR) @: > com_err/et/$(DEPDIR)/$(am__dirstamp) com_err/et/com_err_et_libcyrus_com_err_la-com_err.lo: \ com_err/et/$(am__dirstamp) \ com_err/et/$(DEPDIR)/$(am__dirstamp) com_err/et/com_err_et_libcyrus_com_err_la-error_message.lo: \ com_err/et/$(am__dirstamp) \ com_err/et/$(DEPDIR)/$(am__dirstamp) com_err/et/com_err_et_libcyrus_com_err_la-et_name.lo: \ com_err/et/$(am__dirstamp) \ com_err/et/$(DEPDIR)/$(am__dirstamp) com_err/et/com_err_et_libcyrus_com_err_la-init_et.lo: \ com_err/et/$(am__dirstamp) \ com_err/et/$(DEPDIR)/$(am__dirstamp) com_err/et/libcyrus_com_err.la: $(com_err_et_libcyrus_com_err_la_OBJECTS) $(com_err_et_libcyrus_com_err_la_DEPENDENCIES) $(EXTRA_com_err_et_libcyrus_com_err_la_DEPENDENCIES) com_err/et/$(am__dirstamp) $(AM_V_CCLD)$(com_err_et_libcyrus_com_err_la_LINK) $(am_com_err_et_libcyrus_com_err_la_rpath) $(com_err_et_libcyrus_com_err_la_OBJECTS) $(com_err_et_libcyrus_com_err_la_LIBADD) $(LIBS) imap/$(am__dirstamp): @$(MKDIR_P) imap @: > imap/$(am__dirstamp) imap/$(DEPDIR)/$(am__dirstamp): @$(MKDIR_P) imap/$(DEPDIR) @: > imap/$(DEPDIR)/$(am__dirstamp) imap/imap_libcyrus_imap_la-annotate.lo: imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/imap_libcyrus_imap_la-append.lo: imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/imap_libcyrus_imap_la-backend.lo: imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/imap_libcyrus_imap_la-convert_code.lo: imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/imap_libcyrus_imap_la-dlist.lo: imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/imap_libcyrus_imap_la-duplicate.lo: imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/imap_libcyrus_imap_la-global.lo: imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/imap_libcyrus_imap_la-idle.lo: imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/imap_libcyrus_imap_la-idlemsg.lo: imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/imap_libcyrus_imap_la-imapparse.lo: imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/imap_libcyrus_imap_la-index.lo: imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/imap_libcyrus_imap_la-mailbox.lo: imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/imap_libcyrus_imap_la-mbdump.lo: imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/imap_libcyrus_imap_la-mboxkey.lo: imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/imap_libcyrus_imap_la-mboxlist.lo: imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/imap_libcyrus_imap_la-mboxevent.lo: imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/imap_libcyrus_imap_la-mboxname.lo: imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/imap_libcyrus_imap_la-message_guid.lo: imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/imap_libcyrus_imap_la-message.lo: imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/imap_libcyrus_imap_la-mupdate-client.lo: imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/imap_libcyrus_imap_la-notify.lo: imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/imap_libcyrus_imap_la-partlist.lo: imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/imap_libcyrus_imap_la-proc.lo: imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/imap_libcyrus_imap_la-quota_db.lo: imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/imap_libcyrus_imap_la-rfc822_header.lo: imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/imap_libcyrus_imap_la-saslclient.lo: imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/imap_libcyrus_imap_la-saslserver.lo: imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/imap_libcyrus_imap_la-search_engines.lo: imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/imap_libcyrus_imap_la-seen_db.lo: imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/imap_libcyrus_imap_la-sequence.lo: imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/imap_libcyrus_imap_la-setproctitle.lo: imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/imap_libcyrus_imap_la-squat.lo: imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/imap_libcyrus_imap_la-squat_internal.lo: imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/imap_libcyrus_imap_la-statuscache_db.lo: imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/imap_libcyrus_imap_la-sync_log.lo: imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/imap_libcyrus_imap_la-telemetry.lo: imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/imap_libcyrus_imap_la-tls.lo: imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/imap_libcyrus_imap_la-tls_th-lock.lo: imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/imap_libcyrus_imap_la-user.lo: imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/imap_libcyrus_imap_la-userdeny_db.lo: imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/imap_libcyrus_imap_la-version.lo: imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/imap_libcyrus_imap_la-caldav_db.lo: imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/imap_libcyrus_imap_la-carddav_db.lo: imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/imap_libcyrus_imap_la-dav_db.lo: imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/imap_libcyrus_imap_la-dav_util.lo: imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/imap_libcyrus_imap_la-http_caldav.lo: imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/imap_libcyrus_imap_la-http_carddav.lo: imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/imap_libcyrus_imap_la-http_client.lo: imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/imap_libcyrus_imap_la-http_dav.lo: imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/imap_libcyrus_imap_la-http_dblookup.lo: imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/imap_libcyrus_imap_la-http_ischedule.lo: imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/imap_libcyrus_imap_la-http_proxy.lo: imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/imap_libcyrus_imap_la-http_rss.lo: imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/imap_libcyrus_imap_la-http_timezone.lo: imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/imap_libcyrus_imap_la-httpd.lo: imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/imap_libcyrus_imap_la-jcal.lo: imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/imap_libcyrus_imap_la-proxy.lo: imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/imap_libcyrus_imap_la-smtpclient.lo: imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/imap_libcyrus_imap_la-spool.lo: imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/imap_libcyrus_imap_la-xcal.lo: imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/imap_libcyrus_imap_la-zoneinfo_db.lo: imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/imap_libcyrus_imap_la-imap_err.lo: imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/imap_libcyrus_imap_la-mupdate_err.lo: imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/imap_libcyrus_imap_la-http_err.lo: imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/imap_libcyrus_imap_la-tz_err.lo: imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/libcyrus_imap.la: $(imap_libcyrus_imap_la_OBJECTS) $(imap_libcyrus_imap_la_DEPENDENCIES) $(EXTRA_imap_libcyrus_imap_la_DEPENDENCIES) imap/$(am__dirstamp) $(AM_V_CCLD)$(imap_libcyrus_imap_la_LINK) $(am_imap_libcyrus_imap_la_rpath) $(imap_libcyrus_imap_la_OBJECTS) $(imap_libcyrus_imap_la_LIBADD) $(LIBS) lib/$(am__dirstamp): @$(MKDIR_P) lib @: > lib/$(am__dirstamp) lib/$(DEPDIR)/$(am__dirstamp): @$(MKDIR_P) lib/$(DEPDIR) @: > lib/$(DEPDIR)/$(am__dirstamp) lib/lib_libcyrus_la-acl.lo: lib/$(am__dirstamp) \ lib/$(DEPDIR)/$(am__dirstamp) lib/lib_libcyrus_la-acl_afs.lo: lib/$(am__dirstamp) \ lib/$(DEPDIR)/$(am__dirstamp) lib/lib_libcyrus_la-auth.lo: lib/$(am__dirstamp) \ lib/$(DEPDIR)/$(am__dirstamp) lib/lib_libcyrus_la-auth_krb.lo: lib/$(am__dirstamp) \ lib/$(DEPDIR)/$(am__dirstamp) lib/lib_libcyrus_la-auth_krb5.lo: lib/$(am__dirstamp) \ lib/$(DEPDIR)/$(am__dirstamp) lib/lib_libcyrus_la-auth_pts.lo: lib/$(am__dirstamp) \ lib/$(DEPDIR)/$(am__dirstamp) lib/lib_libcyrus_la-auth_unix.lo: lib/$(am__dirstamp) \ lib/$(DEPDIR)/$(am__dirstamp) lib/lib_libcyrus_la-bitvector.lo: lib/$(am__dirstamp) \ lib/$(DEPDIR)/$(am__dirstamp) lib/lib_libcyrus_la-bsearch.lo: lib/$(am__dirstamp) \ lib/$(DEPDIR)/$(am__dirstamp) lib/lib_libcyrus_la-byteorder64.lo: lib/$(am__dirstamp) \ lib/$(DEPDIR)/$(am__dirstamp) lib/lib_libcyrus_la-charset.lo: lib/$(am__dirstamp) \ lib/$(DEPDIR)/$(am__dirstamp) lib/lib_libcyrus_la-command.lo: lib/$(am__dirstamp) \ lib/$(DEPDIR)/$(am__dirstamp) lib/lib_libcyrus_la-crc32.lo: lib/$(am__dirstamp) \ lib/$(DEPDIR)/$(am__dirstamp) lib/lib_libcyrus_la-cyrusdb.lo: lib/$(am__dirstamp) \ lib/$(DEPDIR)/$(am__dirstamp) lib/lib_libcyrus_la-cyrusdb_flat.lo: lib/$(am__dirstamp) \ lib/$(DEPDIR)/$(am__dirstamp) lib/lib_libcyrus_la-cyrusdb_quotalegacy.lo: lib/$(am__dirstamp) \ lib/$(DEPDIR)/$(am__dirstamp) lib/lib_libcyrus_la-cyrusdb_skiplist.lo: lib/$(am__dirstamp) \ lib/$(DEPDIR)/$(am__dirstamp) lib/lib_libcyrus_la-cyrusdb_twoskip.lo: lib/$(am__dirstamp) \ lib/$(DEPDIR)/$(am__dirstamp) lib/lib_libcyrus_la-glob.lo: lib/$(am__dirstamp) \ lib/$(DEPDIR)/$(am__dirstamp) lib/lib_libcyrus_la-imapurl.lo: lib/$(am__dirstamp) \ lib/$(DEPDIR)/$(am__dirstamp) lib/lib_libcyrus_la-imclient.lo: lib/$(am__dirstamp) \ lib/$(DEPDIR)/$(am__dirstamp) lib/lib_libcyrus_la-imparse.lo: lib/$(am__dirstamp) \ lib/$(DEPDIR)/$(am__dirstamp) lib/lib_libcyrus_la-iostat.lo: lib/$(am__dirstamp) \ lib/$(DEPDIR)/$(am__dirstamp) lib/lib_libcyrus_la-iptostring.lo: lib/$(am__dirstamp) \ lib/$(DEPDIR)/$(am__dirstamp) lib/lib_libcyrus_la-libcyr_cfg.lo: lib/$(am__dirstamp) \ lib/$(DEPDIR)/$(am__dirstamp) lib/lib_libcyrus_la-lsort.lo: lib/$(am__dirstamp) \ lib/$(DEPDIR)/$(am__dirstamp) lib/lib_libcyrus_la-mappedfile.lo: lib/$(am__dirstamp) \ lib/$(DEPDIR)/$(am__dirstamp) lib/lib_libcyrus_la-mkgmtime.lo: lib/$(am__dirstamp) \ lib/$(DEPDIR)/$(am__dirstamp) lib/lib_libcyrus_la-parseaddr.lo: lib/$(am__dirstamp) \ lib/$(DEPDIR)/$(am__dirstamp) lib/lib_libcyrus_la-prot.lo: lib/$(am__dirstamp) \ lib/$(DEPDIR)/$(am__dirstamp) lib/lib_libcyrus_la-ptrarray.lo: lib/$(am__dirstamp) \ lib/$(DEPDIR)/$(am__dirstamp) lib/lib_libcyrus_la-rfc822tok.lo: lib/$(am__dirstamp) \ lib/$(DEPDIR)/$(am__dirstamp) lib/lib_libcyrus_la-signals.lo: lib/$(am__dirstamp) \ lib/$(DEPDIR)/$(am__dirstamp) lib/lib_libcyrus_la-stristr.lo: lib/$(am__dirstamp) \ lib/$(DEPDIR)/$(am__dirstamp) lib/lib_libcyrus_la-times.lo: lib/$(am__dirstamp) \ lib/$(DEPDIR)/$(am__dirstamp) lib/lib_libcyrus_la-tok.lo: lib/$(am__dirstamp) \ lib/$(DEPDIR)/$(am__dirstamp) lib/lib_libcyrus_la-wildmat.lo: lib/$(am__dirstamp) \ lib/$(DEPDIR)/$(am__dirstamp) lib/lib_libcyrus_la-cyrusdb_berkeley.lo: lib/$(am__dirstamp) \ lib/$(DEPDIR)/$(am__dirstamp) lib/lib_libcyrus_la-cyrusdb_sql.lo: lib/$(am__dirstamp) \ lib/$(DEPDIR)/$(am__dirstamp) lib/lib_libcyrus_la-gmtoff_tm.lo: lib/$(am__dirstamp) \ lib/$(DEPDIR)/$(am__dirstamp) lib/lib_libcyrus_la-gmtoff_gmtime.lo: lib/$(am__dirstamp) \ lib/$(DEPDIR)/$(am__dirstamp) lib/lib_libcyrus_la-nonblock_fcntl.lo: lib/$(am__dirstamp) \ lib/$(DEPDIR)/$(am__dirstamp) lib/lib_libcyrus_la-nonblock_ioctl.lo: lib/$(am__dirstamp) \ lib/$(DEPDIR)/$(am__dirstamp) lib/lib_libcyrus_la-chartable.lo: lib/$(am__dirstamp) \ lib/$(DEPDIR)/$(am__dirstamp) lib/libcyrus.la: $(lib_libcyrus_la_OBJECTS) $(lib_libcyrus_la_DEPENDENCIES) $(EXTRA_lib_libcyrus_la_DEPENDENCIES) lib/$(am__dirstamp) $(AM_V_CCLD)$(lib_libcyrus_la_LINK) -rpath $(libdir) $(lib_libcyrus_la_OBJECTS) $(lib_libcyrus_la_LIBADD) $(LIBS) lib/lib_libcyrus_min_la-arrayu64.lo: lib/$(am__dirstamp) \ lib/$(DEPDIR)/$(am__dirstamp) lib/lib_libcyrus_min_la-assert.lo: lib/$(am__dirstamp) \ lib/$(DEPDIR)/$(am__dirstamp) lib/lib_libcyrus_min_la-hash.lo: lib/$(am__dirstamp) \ lib/$(DEPDIR)/$(am__dirstamp) lib/lib_libcyrus_min_la-hashu64.lo: lib/$(am__dirstamp) \ lib/$(DEPDIR)/$(am__dirstamp) lib/lib_libcyrus_min_la-libconfig.lo: lib/$(am__dirstamp) \ lib/$(DEPDIR)/$(am__dirstamp) lib/lib_libcyrus_min_la-mpool.lo: lib/$(am__dirstamp) \ lib/$(DEPDIR)/$(am__dirstamp) lib/lib_libcyrus_min_la-retry.lo: lib/$(am__dirstamp) \ lib/$(DEPDIR)/$(am__dirstamp) lib/lib_libcyrus_min_la-strarray.lo: lib/$(am__dirstamp) \ lib/$(DEPDIR)/$(am__dirstamp) lib/lib_libcyrus_min_la-strhash.lo: lib/$(am__dirstamp) \ lib/$(DEPDIR)/$(am__dirstamp) lib/lib_libcyrus_min_la-util.lo: lib/$(am__dirstamp) \ lib/$(DEPDIR)/$(am__dirstamp) lib/lib_libcyrus_min_la-vparse.lo: lib/$(am__dirstamp) \ lib/$(DEPDIR)/$(am__dirstamp) lib/lib_libcyrus_min_la-xmalloc.lo: lib/$(am__dirstamp) \ lib/$(DEPDIR)/$(am__dirstamp) lib/lib_libcyrus_min_la-xstrlcat.lo: lib/$(am__dirstamp) \ lib/$(DEPDIR)/$(am__dirstamp) lib/lib_libcyrus_min_la-xstrlcpy.lo: lib/$(am__dirstamp) \ lib/$(DEPDIR)/$(am__dirstamp) lib/lib_libcyrus_min_la-getaddrinfo.lo: lib/$(am__dirstamp) \ lib/$(DEPDIR)/$(am__dirstamp) lib/lib_libcyrus_min_la-getnameinfo.lo: lib/$(am__dirstamp) \ lib/$(DEPDIR)/$(am__dirstamp) lib/lib_libcyrus_min_la-lock_fcntl.lo: lib/$(am__dirstamp) \ lib/$(DEPDIR)/$(am__dirstamp) lib/lib_libcyrus_min_la-lock_flock.lo: lib/$(am__dirstamp) \ lib/$(DEPDIR)/$(am__dirstamp) lib/lib_libcyrus_min_la-map_shared.lo: lib/$(am__dirstamp) \ lib/$(DEPDIR)/$(am__dirstamp) lib/lib_libcyrus_min_la-map_stupidshared.lo: lib/$(am__dirstamp) \ lib/$(DEPDIR)/$(am__dirstamp) lib/lib_libcyrus_min_la-map_nommap.lo: lib/$(am__dirstamp) \ lib/$(DEPDIR)/$(am__dirstamp) lib/lib_libcyrus_min_la-imapopts.lo: lib/$(am__dirstamp) \ lib/$(DEPDIR)/$(am__dirstamp) lib/libcyrus_min.la: $(lib_libcyrus_min_la_OBJECTS) $(lib_libcyrus_min_la_DEPENDENCIES) $(EXTRA_lib_libcyrus_min_la_DEPENDENCIES) lib/$(am__dirstamp) $(AM_V_CCLD)$(lib_libcyrus_min_la_LINK) -rpath $(libdir) $(lib_libcyrus_min_la_OBJECTS) $(lib_libcyrus_min_la_LIBADD) $(LIBS) lib/acl.lo: lib/$(am__dirstamp) lib/$(DEPDIR)/$(am__dirstamp) lib/acl_afs.lo: lib/$(am__dirstamp) lib/$(DEPDIR)/$(am__dirstamp) lib/auth.lo: lib/$(am__dirstamp) lib/$(DEPDIR)/$(am__dirstamp) lib/auth_krb.lo: lib/$(am__dirstamp) lib/$(DEPDIR)/$(am__dirstamp) lib/auth_krb5.lo: lib/$(am__dirstamp) lib/$(DEPDIR)/$(am__dirstamp) lib/auth_pts.lo: lib/$(am__dirstamp) lib/$(DEPDIR)/$(am__dirstamp) lib/auth_unix.lo: lib/$(am__dirstamp) lib/$(DEPDIR)/$(am__dirstamp) lib/bitvector.lo: lib/$(am__dirstamp) lib/$(DEPDIR)/$(am__dirstamp) lib/bsearch.lo: lib/$(am__dirstamp) lib/$(DEPDIR)/$(am__dirstamp) lib/byteorder64.lo: lib/$(am__dirstamp) lib/$(DEPDIR)/$(am__dirstamp) lib/charset.lo: lib/$(am__dirstamp) lib/$(DEPDIR)/$(am__dirstamp) lib/command.lo: lib/$(am__dirstamp) lib/$(DEPDIR)/$(am__dirstamp) lib/crc32.lo: lib/$(am__dirstamp) lib/$(DEPDIR)/$(am__dirstamp) lib/cyrusdb.lo: lib/$(am__dirstamp) lib/$(DEPDIR)/$(am__dirstamp) lib/cyrusdb_flat.lo: lib/$(am__dirstamp) lib/$(DEPDIR)/$(am__dirstamp) lib/cyrusdb_quotalegacy.lo: lib/$(am__dirstamp) \ lib/$(DEPDIR)/$(am__dirstamp) lib/cyrusdb_skiplist.lo: lib/$(am__dirstamp) \ lib/$(DEPDIR)/$(am__dirstamp) lib/cyrusdb_twoskip.lo: lib/$(am__dirstamp) \ lib/$(DEPDIR)/$(am__dirstamp) lib/glob.lo: lib/$(am__dirstamp) lib/$(DEPDIR)/$(am__dirstamp) lib/imapurl.lo: lib/$(am__dirstamp) lib/$(DEPDIR)/$(am__dirstamp) lib/imclient.lo: lib/$(am__dirstamp) lib/$(DEPDIR)/$(am__dirstamp) lib/imparse.lo: lib/$(am__dirstamp) lib/$(DEPDIR)/$(am__dirstamp) lib/iostat.lo: lib/$(am__dirstamp) lib/$(DEPDIR)/$(am__dirstamp) lib/iptostring.lo: lib/$(am__dirstamp) lib/$(DEPDIR)/$(am__dirstamp) lib/libcyr_cfg.lo: lib/$(am__dirstamp) lib/$(DEPDIR)/$(am__dirstamp) lib/lsort.lo: lib/$(am__dirstamp) lib/$(DEPDIR)/$(am__dirstamp) lib/mappedfile.lo: lib/$(am__dirstamp) lib/$(DEPDIR)/$(am__dirstamp) lib/mkgmtime.lo: lib/$(am__dirstamp) lib/$(DEPDIR)/$(am__dirstamp) lib/parseaddr.lo: lib/$(am__dirstamp) lib/$(DEPDIR)/$(am__dirstamp) lib/prot.lo: lib/$(am__dirstamp) lib/$(DEPDIR)/$(am__dirstamp) lib/ptrarray.lo: lib/$(am__dirstamp) lib/$(DEPDIR)/$(am__dirstamp) lib/rfc822tok.lo: lib/$(am__dirstamp) lib/$(DEPDIR)/$(am__dirstamp) lib/signals.lo: lib/$(am__dirstamp) lib/$(DEPDIR)/$(am__dirstamp) lib/stristr.lo: lib/$(am__dirstamp) lib/$(DEPDIR)/$(am__dirstamp) lib/times.lo: lib/$(am__dirstamp) lib/$(DEPDIR)/$(am__dirstamp) lib/tok.lo: lib/$(am__dirstamp) lib/$(DEPDIR)/$(am__dirstamp) lib/wildmat.lo: lib/$(am__dirstamp) lib/$(DEPDIR)/$(am__dirstamp) lib/cyrusdb_berkeley.lo: lib/$(am__dirstamp) \ lib/$(DEPDIR)/$(am__dirstamp) lib/cyrusdb_sql.lo: lib/$(am__dirstamp) lib/$(DEPDIR)/$(am__dirstamp) lib/gmtoff_tm.lo: lib/$(am__dirstamp) lib/$(DEPDIR)/$(am__dirstamp) lib/gmtoff_gmtime.lo: lib/$(am__dirstamp) \ lib/$(DEPDIR)/$(am__dirstamp) lib/nonblock_fcntl.lo: lib/$(am__dirstamp) \ lib/$(DEPDIR)/$(am__dirstamp) lib/nonblock_ioctl.lo: lib/$(am__dirstamp) \ lib/$(DEPDIR)/$(am__dirstamp) perl/$(am__dirstamp): @$(MKDIR_P) perl @: > perl/$(am__dirstamp) perl/libcyrus.la: $(perl_libcyrus_la_OBJECTS) $(perl_libcyrus_la_DEPENDENCIES) $(EXTRA_perl_libcyrus_la_DEPENDENCIES) perl/$(am__dirstamp) $(AM_V_CCLD)$(LINK) $(am_perl_libcyrus_la_rpath) $(perl_libcyrus_la_OBJECTS) $(perl_libcyrus_la_LIBADD) $(LIBS) lib/arrayu64.lo: lib/$(am__dirstamp) lib/$(DEPDIR)/$(am__dirstamp) lib/assert.lo: lib/$(am__dirstamp) lib/$(DEPDIR)/$(am__dirstamp) lib/hash.lo: lib/$(am__dirstamp) lib/$(DEPDIR)/$(am__dirstamp) lib/hashu64.lo: lib/$(am__dirstamp) lib/$(DEPDIR)/$(am__dirstamp) lib/libconfig.lo: lib/$(am__dirstamp) lib/$(DEPDIR)/$(am__dirstamp) lib/mpool.lo: lib/$(am__dirstamp) lib/$(DEPDIR)/$(am__dirstamp) lib/retry.lo: lib/$(am__dirstamp) lib/$(DEPDIR)/$(am__dirstamp) lib/strarray.lo: lib/$(am__dirstamp) lib/$(DEPDIR)/$(am__dirstamp) lib/strhash.lo: lib/$(am__dirstamp) lib/$(DEPDIR)/$(am__dirstamp) lib/util.lo: lib/$(am__dirstamp) lib/$(DEPDIR)/$(am__dirstamp) lib/vparse.lo: lib/$(am__dirstamp) lib/$(DEPDIR)/$(am__dirstamp) lib/xmalloc.lo: lib/$(am__dirstamp) lib/$(DEPDIR)/$(am__dirstamp) lib/xstrlcat.lo: lib/$(am__dirstamp) lib/$(DEPDIR)/$(am__dirstamp) lib/xstrlcpy.lo: lib/$(am__dirstamp) lib/$(DEPDIR)/$(am__dirstamp) lib/getaddrinfo.lo: lib/$(am__dirstamp) lib/$(DEPDIR)/$(am__dirstamp) lib/getnameinfo.lo: lib/$(am__dirstamp) lib/$(DEPDIR)/$(am__dirstamp) lib/lock_fcntl.lo: lib/$(am__dirstamp) lib/$(DEPDIR)/$(am__dirstamp) lib/lock_flock.lo: lib/$(am__dirstamp) lib/$(DEPDIR)/$(am__dirstamp) lib/map_shared.lo: lib/$(am__dirstamp) lib/$(DEPDIR)/$(am__dirstamp) lib/map_stupidshared.lo: lib/$(am__dirstamp) \ lib/$(DEPDIR)/$(am__dirstamp) lib/map_nommap.lo: lib/$(am__dirstamp) lib/$(DEPDIR)/$(am__dirstamp) perl/libcyrus_min.la: $(perl_libcyrus_min_la_OBJECTS) $(perl_libcyrus_min_la_DEPENDENCIES) $(EXTRA_perl_libcyrus_min_la_DEPENDENCIES) perl/$(am__dirstamp) $(AM_V_CCLD)$(LINK) $(am_perl_libcyrus_min_la_rpath) $(perl_libcyrus_min_la_OBJECTS) $(perl_libcyrus_min_la_LIBADD) $(LIBS) sieve/$(am__dirstamp): @$(MKDIR_P) sieve @: > sieve/$(am__dirstamp) sieve/$(DEPDIR)/$(am__dirstamp): @$(MKDIR_P) sieve/$(DEPDIR) @: > sieve/$(DEPDIR)/$(am__dirstamp) sieve/sieve_libcyrus_sieve_la-addr.lo: sieve/$(am__dirstamp) \ sieve/$(DEPDIR)/$(am__dirstamp) sieve/sieve_libcyrus_sieve_la-bc_dump.lo: sieve/$(am__dirstamp) \ sieve/$(DEPDIR)/$(am__dirstamp) sieve/sieve_libcyrus_sieve_la-bc_emit.lo: sieve/$(am__dirstamp) \ sieve/$(DEPDIR)/$(am__dirstamp) sieve/sieve_libcyrus_sieve_la-bc_eval.lo: sieve/$(am__dirstamp) \ sieve/$(DEPDIR)/$(am__dirstamp) sieve/sieve_libcyrus_sieve_la-bc_generate.lo: sieve/$(am__dirstamp) \ sieve/$(DEPDIR)/$(am__dirstamp) sieve/sieve_libcyrus_sieve_la-comparator.lo: sieve/$(am__dirstamp) \ sieve/$(DEPDIR)/$(am__dirstamp) sieve/sieve_libcyrus_sieve_la-flags.lo: sieve/$(am__dirstamp) \ sieve/$(DEPDIR)/$(am__dirstamp) sieve/sieve_libcyrus_sieve_la-interp.lo: sieve/$(am__dirstamp) \ sieve/$(DEPDIR)/$(am__dirstamp) sieve/sieve_libcyrus_sieve_la-message.lo: sieve/$(am__dirstamp) \ sieve/$(DEPDIR)/$(am__dirstamp) sieve/sieve_libcyrus_sieve_la-script.lo: sieve/$(am__dirstamp) \ sieve/$(DEPDIR)/$(am__dirstamp) sieve/sieve_libcyrus_sieve_la-sieve.lo: sieve/$(am__dirstamp) \ sieve/$(DEPDIR)/$(am__dirstamp) sieve/sieve_libcyrus_sieve_la-tree.lo: sieve/$(am__dirstamp) \ sieve/$(DEPDIR)/$(am__dirstamp) sieve/sieve_libcyrus_sieve_la-varlist.lo: sieve/$(am__dirstamp) \ sieve/$(DEPDIR)/$(am__dirstamp) sieve/sieve_libcyrus_sieve_la-sieve_err.lo: sieve/$(am__dirstamp) \ sieve/$(DEPDIR)/$(am__dirstamp) sieve/libcyrus_sieve.la: $(sieve_libcyrus_sieve_la_OBJECTS) $(sieve_libcyrus_sieve_la_DEPENDENCIES) $(EXTRA_sieve_libcyrus_sieve_la_DEPENDENCIES) sieve/$(am__dirstamp) $(AM_V_CCLD)$(sieve_libcyrus_sieve_la_LINK) $(am_sieve_libcyrus_sieve_la_rpath) $(sieve_libcyrus_sieve_la_OBJECTS) $(sieve_libcyrus_sieve_la_LIBADD) $(LIBS) sieve/sieve_libcyrus_sieve_lex_la-addr-lex.lo: sieve/$(am__dirstamp) \ sieve/$(DEPDIR)/$(am__dirstamp) sieve/sieve_libcyrus_sieve_lex_la-sieve-lex.lo: sieve/$(am__dirstamp) \ sieve/$(DEPDIR)/$(am__dirstamp) sieve/libcyrus_sieve_lex.la: $(sieve_libcyrus_sieve_lex_la_OBJECTS) $(sieve_libcyrus_sieve_lex_la_DEPENDENCIES) $(EXTRA_sieve_libcyrus_sieve_lex_la_DEPENDENCIES) sieve/$(am__dirstamp) $(AM_V_CCLD)$(sieve_libcyrus_sieve_lex_la_LINK) $(am_sieve_libcyrus_sieve_lex_la_rpath) $(sieve_libcyrus_sieve_lex_la_OBJECTS) $(sieve_libcyrus_sieve_lex_la_LIBADD) $(LIBS) install-binPROGRAMS: $(bin_PROGRAMS) @$(NORMAL_INSTALL) @list='$(bin_PROGRAMS)'; test -n "$(bindir)" || list=; \ if test -n "$$list"; then \ echo " $(MKDIR_P) '$(DESTDIR)$(bindir)'"; \ $(MKDIR_P) "$(DESTDIR)$(bindir)" || exit 1; \ fi; \ for p in $$list; do echo "$$p $$p"; done | \ sed 's/$(EXEEXT)$$//' | \ while read p p1; do if test -f $$p \ || test -f $$p1 \ ; then echo "$$p"; echo "$$p"; else :; fi; \ done | \ sed -e 'p;s,.*/,,;n;h' \ -e 's|.*|.|' \ -e 'p;x;s,.*/,,;s/$(EXEEXT)$$//;$(transform);s/$$/$(EXEEXT)/' | \ sed 'N;N;N;s,\n, ,g' | \ $(AWK) 'BEGIN { files["."] = ""; dirs["."] = 1 } \ { d=$$3; if (dirs[d] != 1) { print "d", d; dirs[d] = 1 } \ if ($$2 == $$4) files[d] = files[d] " " $$1; \ else { print "f", $$3 "/" $$4, $$1; } } \ END { for (d in files) print "f", d, files[d] }' | \ while read type dir files; do \ if test "$$dir" = .; then dir=; else dir=/$$dir; fi; \ test -z "$$files" || { \ echo " $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files '$(DESTDIR)$(bindir)$$dir'"; \ $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files "$(DESTDIR)$(bindir)$$dir" || exit $$?; \ } \ ; done uninstall-binPROGRAMS: @$(NORMAL_UNINSTALL) @list='$(bin_PROGRAMS)'; test -n "$(bindir)" || list=; \ files=`for p in $$list; do echo "$$p"; done | \ sed -e 'h;s,^.*/,,;s/$(EXEEXT)$$//;$(transform)' \ -e 's/$$/$(EXEEXT)/' \ `; \ test -n "$$list" || exit 0; \ echo " ( cd '$(DESTDIR)$(bindir)' && rm -f" $$files ")"; \ cd "$(DESTDIR)$(bindir)" && rm -f $$files clean-binPROGRAMS: @list='$(bin_PROGRAMS)'; test -n "$$list" || exit 0; \ echo " rm -f" $$list; \ rm -f $$list || exit $$?; \ test -n "$(EXEEXT)" || exit 0; \ list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \ echo " rm -f" $$list; \ rm -f $$list clean-checkPROGRAMS: @list='$(check_PROGRAMS)'; test -n "$$list" || exit 0; \ echo " rm -f" $$list; \ rm -f $$list || exit $$?; \ test -n "$(EXEEXT)" || exit 0; \ list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \ echo " rm -f" $$list; \ rm -f $$list install-servicePROGRAMS: $(service_PROGRAMS) @$(NORMAL_INSTALL) @list='$(service_PROGRAMS)'; test -n "$(servicedir)" || list=; \ if test -n "$$list"; then \ echo " $(MKDIR_P) '$(DESTDIR)$(servicedir)'"; \ $(MKDIR_P) "$(DESTDIR)$(servicedir)" || exit 1; \ fi; \ for p in $$list; do echo "$$p $$p"; done | \ sed 's/$(EXEEXT)$$//' | \ while read p p1; do if test -f $$p \ || test -f $$p1 \ ; then echo "$$p"; echo "$$p"; else :; fi; \ done | \ sed -e 'p;s,.*/,,;n;h' \ -e 's|.*|.|' \ -e 'p;x;s,.*/,,;s/$(EXEEXT)$$//;$(transform);s/$$/$(EXEEXT)/' | \ sed 'N;N;N;s,\n, ,g' | \ $(AWK) 'BEGIN { files["."] = ""; dirs["."] = 1 } \ { d=$$3; if (dirs[d] != 1) { print "d", d; dirs[d] = 1 } \ if ($$2 == $$4) files[d] = files[d] " " $$1; \ else { print "f", $$3 "/" $$4, $$1; } } \ END { for (d in files) print "f", d, files[d] }' | \ while read type dir files; do \ if test "$$dir" = .; then dir=; else dir=/$$dir; fi; \ test -z "$$files" || { \ echo " $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files '$(DESTDIR)$(servicedir)$$dir'"; \ $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files "$(DESTDIR)$(servicedir)$$dir" || exit $$?; \ } \ ; done uninstall-servicePROGRAMS: @$(NORMAL_UNINSTALL) @list='$(service_PROGRAMS)'; test -n "$(servicedir)" || list=; \ files=`for p in $$list; do echo "$$p"; done | \ sed -e 'h;s,^.*/,,;s/$(EXEEXT)$$//;$(transform)' \ -e 's/$$/$(EXEEXT)/' \ `; \ test -n "$$list" || exit 0; \ echo " ( cd '$(DESTDIR)$(servicedir)' && rm -f" $$files ")"; \ cd "$(DESTDIR)$(servicedir)" && rm -f $$files clean-servicePROGRAMS: @list='$(service_PROGRAMS)'; test -n "$$list" || exit 0; \ echo " rm -f" $$list; \ rm -f $$list || exit $$?; \ test -n "$(EXEEXT)" || exit 0; \ list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \ echo " rm -f" $$list; \ rm -f $$list install-userPROGRAMS: $(user_PROGRAMS) @$(NORMAL_INSTALL) @list='$(user_PROGRAMS)'; test -n "$(userdir)" || list=; \ if test -n "$$list"; then \ echo " $(MKDIR_P) '$(DESTDIR)$(userdir)'"; \ $(MKDIR_P) "$(DESTDIR)$(userdir)" || exit 1; \ fi; \ for p in $$list; do echo "$$p $$p"; done | \ sed 's/$(EXEEXT)$$//' | \ while read p p1; do if test -f $$p \ || test -f $$p1 \ ; then echo "$$p"; echo "$$p"; else :; fi; \ done | \ sed -e 'p;s,.*/,,;n;h' \ -e 's|.*|.|' \ -e 'p;x;s,.*/,,;s/$(EXEEXT)$$//;$(transform);s/$$/$(EXEEXT)/' | \ sed 'N;N;N;s,\n, ,g' | \ $(AWK) 'BEGIN { files["."] = ""; dirs["."] = 1 } \ { d=$$3; if (dirs[d] != 1) { print "d", d; dirs[d] = 1 } \ if ($$2 == $$4) files[d] = files[d] " " $$1; \ else { print "f", $$3 "/" $$4, $$1; } } \ END { for (d in files) print "f", d, files[d] }' | \ while read type dir files; do \ if test "$$dir" = .; then dir=; else dir=/$$dir; fi; \ test -z "$$files" || { \ echo " $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files '$(DESTDIR)$(userdir)$$dir'"; \ $(INSTALL_PROGRAM_ENV) $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL_PROGRAM) $$files "$(DESTDIR)$(userdir)$$dir" || exit $$?; \ } \ ; done uninstall-userPROGRAMS: @$(NORMAL_UNINSTALL) @list='$(user_PROGRAMS)'; test -n "$(userdir)" || list=; \ files=`for p in $$list; do echo "$$p"; done | \ sed -e 'h;s,^.*/,,;s/$(EXEEXT)$$//;$(transform)' \ -e 's/$$/$(EXEEXT)/' \ `; \ test -n "$$list" || exit 0; \ echo " ( cd '$(DESTDIR)$(userdir)' && rm -f" $$files ")"; \ cd "$(DESTDIR)$(userdir)" && rm -f $$files clean-userPROGRAMS: @list='$(user_PROGRAMS)'; test -n "$$list" || exit 0; \ echo " rm -f" $$list; \ rm -f $$list || exit $$?; \ test -n "$(EXEEXT)" || exit 0; \ list=`for p in $$list; do echo "$$p"; done | sed 's/$(EXEEXT)$$//'`; \ echo " rm -f" $$list; \ rm -f $$list cunit/$(am__dirstamp): @$(MKDIR_P) cunit @: > cunit/$(am__dirstamp) cunit/$(DEPDIR)/$(am__dirstamp): @$(MKDIR_P) cunit/$(DEPDIR) @: > cunit/$(DEPDIR)/$(am__dirstamp) cunit/unit.$(OBJEXT): cunit/$(am__dirstamp) \ cunit/$(DEPDIR)/$(am__dirstamp) cunit/syslog.$(OBJEXT): cunit/$(am__dirstamp) \ cunit/$(DEPDIR)/$(am__dirstamp) cunit/timeout.$(OBJEXT): cunit/$(am__dirstamp) \ cunit/$(DEPDIR)/$(am__dirstamp) cunit/annotate.$(OBJEXT): cunit/$(am__dirstamp) \ cunit/$(DEPDIR)/$(am__dirstamp) cunit/backend.$(OBJEXT): cunit/$(am__dirstamp) \ cunit/$(DEPDIR)/$(am__dirstamp) cunit/binhex.$(OBJEXT): cunit/$(am__dirstamp) \ cunit/$(DEPDIR)/$(am__dirstamp) cunit/bitvector.$(OBJEXT): cunit/$(am__dirstamp) \ cunit/$(DEPDIR)/$(am__dirstamp) cunit/buf.$(OBJEXT): cunit/$(am__dirstamp) \ cunit/$(DEPDIR)/$(am__dirstamp) cunit/byteorder64.$(OBJEXT): cunit/$(am__dirstamp) \ cunit/$(DEPDIR)/$(am__dirstamp) cunit/charset.$(OBJEXT): cunit/$(am__dirstamp) \ cunit/$(DEPDIR)/$(am__dirstamp) cunit/crc32.$(OBJEXT): cunit/$(am__dirstamp) \ cunit/$(DEPDIR)/$(am__dirstamp) cunit/db.$(OBJEXT): cunit/$(am__dirstamp) \ cunit/$(DEPDIR)/$(am__dirstamp) cunit/dlist.$(OBJEXT): cunit/$(am__dirstamp) \ cunit/$(DEPDIR)/$(am__dirstamp) cunit/duplicate.$(OBJEXT): cunit/$(am__dirstamp) \ cunit/$(DEPDIR)/$(am__dirstamp) cunit/getxstring.$(OBJEXT): cunit/$(am__dirstamp) \ cunit/$(DEPDIR)/$(am__dirstamp) cunit/glob.$(OBJEXT): cunit/$(am__dirstamp) \ cunit/$(DEPDIR)/$(am__dirstamp) cunit/guid.$(OBJEXT): cunit/$(am__dirstamp) \ cunit/$(DEPDIR)/$(am__dirstamp) cunit/hash.$(OBJEXT): cunit/$(am__dirstamp) \ cunit/$(DEPDIR)/$(am__dirstamp) cunit/imapurl.$(OBJEXT): cunit/$(am__dirstamp) \ cunit/$(DEPDIR)/$(am__dirstamp) cunit/mboxname.$(OBJEXT): cunit/$(am__dirstamp) \ cunit/$(DEPDIR)/$(am__dirstamp) cunit/md5.$(OBJEXT): cunit/$(am__dirstamp) \ cunit/$(DEPDIR)/$(am__dirstamp) cunit/message.$(OBJEXT): cunit/$(am__dirstamp) \ cunit/$(DEPDIR)/$(am__dirstamp) cunit/msgid.$(OBJEXT): cunit/$(am__dirstamp) \ cunit/$(DEPDIR)/$(am__dirstamp) cunit/parseaddr.$(OBJEXT): cunit/$(am__dirstamp) \ cunit/$(DEPDIR)/$(am__dirstamp) cunit/parse.$(OBJEXT): cunit/$(am__dirstamp) \ cunit/$(DEPDIR)/$(am__dirstamp) cunit/prot.$(OBJEXT): cunit/$(am__dirstamp) \ cunit/$(DEPDIR)/$(am__dirstamp) cunit/ptrarray.$(OBJEXT): cunit/$(am__dirstamp) \ cunit/$(DEPDIR)/$(am__dirstamp) cunit/quota.$(OBJEXT): cunit/$(am__dirstamp) \ cunit/$(DEPDIR)/$(am__dirstamp) cunit/rfc822tok.$(OBJEXT): cunit/$(am__dirstamp) \ cunit/$(DEPDIR)/$(am__dirstamp) cunit/sieve.$(OBJEXT): cunit/$(am__dirstamp) \ cunit/$(DEPDIR)/$(am__dirstamp) cunit/spool.$(OBJEXT): cunit/$(am__dirstamp) \ cunit/$(DEPDIR)/$(am__dirstamp) cunit/squat.$(OBJEXT): cunit/$(am__dirstamp) \ cunit/$(DEPDIR)/$(am__dirstamp) cunit/strarray.$(OBJEXT): cunit/$(am__dirstamp) \ cunit/$(DEPDIR)/$(am__dirstamp) cunit/strconcat.$(OBJEXT): cunit/$(am__dirstamp) \ cunit/$(DEPDIR)/$(am__dirstamp) cunit/times.$(OBJEXT): cunit/$(am__dirstamp) \ cunit/$(DEPDIR)/$(am__dirstamp) cunit/tok.$(OBJEXT): cunit/$(am__dirstamp) \ cunit/$(DEPDIR)/$(am__dirstamp) imap/mutex_fake.$(OBJEXT): imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/spool.$(OBJEXT): imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) cunit/unit$(EXEEXT): $(cunit_unit_OBJECTS) $(cunit_unit_DEPENDENCIES) $(EXTRA_cunit_unit_DEPENDENCIES) cunit/$(am__dirstamp) @rm -f cunit/unit$(EXEEXT) $(AM_V_CCLD)$(LINK) $(cunit_unit_OBJECTS) $(cunit_unit_LDADD) $(LIBS) imap/arbitron.$(OBJEXT): imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/cli_fatal.$(OBJEXT): imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/arbitron$(EXEEXT): $(imap_arbitron_OBJECTS) $(imap_arbitron_DEPENDENCIES) $(EXTRA_imap_arbitron_DEPENDENCIES) imap/$(am__dirstamp) @rm -f imap/arbitron$(EXEEXT) $(AM_V_CCLD)$(LINK) $(imap_arbitron_OBJECTS) $(imap_arbitron_LDADD) $(LIBS) imap/chk_cyrus.$(OBJEXT): imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/chk_cyrus$(EXEEXT): $(imap_chk_cyrus_OBJECTS) $(imap_chk_cyrus_DEPENDENCIES) $(EXTRA_imap_chk_cyrus_DEPENDENCIES) imap/$(am__dirstamp) @rm -f imap/chk_cyrus$(EXEEXT) $(AM_V_CCLD)$(LINK) $(imap_chk_cyrus_OBJECTS) $(imap_chk_cyrus_LDADD) $(LIBS) imap/ctl_cyrusdb.$(OBJEXT): imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/ctl_cyrusdb$(EXEEXT): $(imap_ctl_cyrusdb_OBJECTS) $(imap_ctl_cyrusdb_DEPENDENCIES) $(EXTRA_imap_ctl_cyrusdb_DEPENDENCIES) imap/$(am__dirstamp) @rm -f imap/ctl_cyrusdb$(EXEEXT) $(AM_V_CCLD)$(LINK) $(imap_ctl_cyrusdb_OBJECTS) $(imap_ctl_cyrusdb_LDADD) $(LIBS) imap/ctl_deliver.$(OBJEXT): imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/ctl_deliver$(EXEEXT): $(imap_ctl_deliver_OBJECTS) $(imap_ctl_deliver_DEPENDENCIES) $(EXTRA_imap_ctl_deliver_DEPENDENCIES) imap/$(am__dirstamp) @rm -f imap/ctl_deliver$(EXEEXT) $(AM_V_CCLD)$(LINK) $(imap_ctl_deliver_OBJECTS) $(imap_ctl_deliver_LDADD) $(LIBS) imap/ctl_mboxlist.$(OBJEXT): imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/ctl_mboxlist$(EXEEXT): $(imap_ctl_mboxlist_OBJECTS) $(imap_ctl_mboxlist_DEPENDENCIES) $(EXTRA_imap_ctl_mboxlist_DEPENDENCIES) imap/$(am__dirstamp) @rm -f imap/ctl_mboxlist$(EXEEXT) $(AM_V_CCLD)$(LINK) $(imap_ctl_mboxlist_OBJECTS) $(imap_ctl_mboxlist_LDADD) $(LIBS) imap/ctl_zoneinfo.$(OBJEXT): imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/ctl_zoneinfo$(EXEEXT): $(imap_ctl_zoneinfo_OBJECTS) $(imap_ctl_zoneinfo_DEPENDENCIES) $(EXTRA_imap_ctl_zoneinfo_DEPENDENCIES) imap/$(am__dirstamp) @rm -f imap/ctl_zoneinfo$(EXEEXT) $(AM_V_CCLD)$(LINK) $(imap_ctl_zoneinfo_OBJECTS) $(imap_ctl_zoneinfo_LDADD) $(LIBS) imap/cvt_cyrusdb.$(OBJEXT): imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/cvt_cyrusdb$(EXEEXT): $(imap_cvt_cyrusdb_OBJECTS) $(imap_cvt_cyrusdb_DEPENDENCIES) $(EXTRA_imap_cvt_cyrusdb_DEPENDENCIES) imap/$(am__dirstamp) @rm -f imap/cvt_cyrusdb$(EXEEXT) $(AM_V_CCLD)$(LINK) $(imap_cvt_cyrusdb_OBJECTS) $(imap_cvt_cyrusdb_LDADD) $(LIBS) imap/cyr_dbtool.$(OBJEXT): imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/cyr_dbtool$(EXEEXT): $(imap_cyr_dbtool_OBJECTS) $(imap_cyr_dbtool_DEPENDENCIES) $(EXTRA_imap_cyr_dbtool_DEPENDENCIES) imap/$(am__dirstamp) @rm -f imap/cyr_dbtool$(EXEEXT) $(AM_V_CCLD)$(LINK) $(imap_cyr_dbtool_OBJECTS) $(imap_cyr_dbtool_LDADD) $(LIBS) imap/cyr_deny.$(OBJEXT): imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/cyr_deny$(EXEEXT): $(imap_cyr_deny_OBJECTS) $(imap_cyr_deny_DEPENDENCIES) $(EXTRA_imap_cyr_deny_DEPENDENCIES) imap/$(am__dirstamp) @rm -f imap/cyr_deny$(EXEEXT) $(AM_V_CCLD)$(LINK) $(imap_cyr_deny_OBJECTS) $(imap_cyr_deny_LDADD) $(LIBS) imap/cyr_df.$(OBJEXT): imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/cyr_df$(EXEEXT): $(imap_cyr_df_OBJECTS) $(imap_cyr_df_DEPENDENCIES) $(EXTRA_imap_cyr_df_DEPENDENCIES) imap/$(am__dirstamp) @rm -f imap/cyr_df$(EXEEXT) $(AM_V_CCLD)$(LINK) $(imap_cyr_df_OBJECTS) $(imap_cyr_df_LDADD) $(LIBS) imap/cyr_expire.$(OBJEXT): imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/cyr_expire$(EXEEXT): $(imap_cyr_expire_OBJECTS) $(imap_cyr_expire_DEPENDENCIES) $(EXTRA_imap_cyr_expire_DEPENDENCIES) imap/$(am__dirstamp) @rm -f imap/cyr_expire$(EXEEXT) $(AM_V_CCLD)$(LINK) $(imap_cyr_expire_OBJECTS) $(imap_cyr_expire_LDADD) $(LIBS) imap/cyr_info.$(OBJEXT): imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) master/$(am__dirstamp): @$(MKDIR_P) master @: > master/$(am__dirstamp) master/$(DEPDIR)/$(am__dirstamp): @$(MKDIR_P) master/$(DEPDIR) @: > master/$(DEPDIR)/$(am__dirstamp) master/masterconf.$(OBJEXT): master/$(am__dirstamp) \ master/$(DEPDIR)/$(am__dirstamp) imap/cyr_info$(EXEEXT): $(imap_cyr_info_OBJECTS) $(imap_cyr_info_DEPENDENCIES) $(EXTRA_imap_cyr_info_DEPENDENCIES) imap/$(am__dirstamp) @rm -f imap/cyr_info$(EXEEXT) $(AM_V_CCLD)$(LINK) $(imap_cyr_info_OBJECTS) $(imap_cyr_info_LDADD) $(LIBS) imap/cyr_sequence.$(OBJEXT): imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/cyr_sequence$(EXEEXT): $(imap_cyr_sequence_OBJECTS) $(imap_cyr_sequence_DEPENDENCIES) $(EXTRA_imap_cyr_sequence_DEPENDENCIES) imap/$(am__dirstamp) @rm -f imap/cyr_sequence$(EXEEXT) $(AM_V_CCLD)$(LINK) $(imap_cyr_sequence_OBJECTS) $(imap_cyr_sequence_LDADD) $(LIBS) imap/cyr_synclog.$(OBJEXT): imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/cyr_synclog$(EXEEXT): $(imap_cyr_synclog_OBJECTS) $(imap_cyr_synclog_DEPENDENCIES) $(EXTRA_imap_cyr_synclog_DEPENDENCIES) imap/$(am__dirstamp) @rm -f imap/cyr_synclog$(EXEEXT) $(AM_V_CCLD)$(LINK) $(imap_cyr_synclog_OBJECTS) $(imap_cyr_synclog_LDADD) $(LIBS) imap/cyr_userseen.$(OBJEXT): imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/cyr_userseen$(EXEEXT): $(imap_cyr_userseen_OBJECTS) $(imap_cyr_userseen_DEPENDENCIES) $(EXTRA_imap_cyr_userseen_DEPENDENCIES) imap/$(am__dirstamp) @rm -f imap/cyr_userseen$(EXEEXT) $(AM_V_CCLD)$(LINK) $(imap_cyr_userseen_OBJECTS) $(imap_cyr_userseen_LDADD) $(LIBS) imap/cyr_virusscan.$(OBJEXT): imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/cyr_virusscan$(EXEEXT): $(imap_cyr_virusscan_OBJECTS) $(imap_cyr_virusscan_DEPENDENCIES) $(EXTRA_imap_cyr_virusscan_DEPENDENCIES) imap/$(am__dirstamp) @rm -f imap/cyr_virusscan$(EXEEXT) $(AM_V_CCLD)$(LINK) $(imap_cyr_virusscan_OBJECTS) $(imap_cyr_virusscan_LDADD) $(LIBS) imap/cyrdump.$(OBJEXT): imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/cyrdump$(EXEEXT): $(imap_cyrdump_OBJECTS) $(imap_cyrdump_DEPENDENCIES) $(EXTRA_imap_cyrdump_DEPENDENCIES) imap/$(am__dirstamp) @rm -f imap/cyrdump$(EXEEXT) $(AM_V_CCLD)$(LINK) $(imap_cyrdump_OBJECTS) $(imap_cyrdump_LDADD) $(LIBS) imap/dav_reconstruct.$(OBJEXT): imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/dav_reconstruct$(EXEEXT): $(imap_dav_reconstruct_OBJECTS) $(imap_dav_reconstruct_DEPENDENCIES) $(EXTRA_imap_dav_reconstruct_DEPENDENCIES) imap/$(am__dirstamp) @rm -f imap/dav_reconstruct$(EXEEXT) $(AM_V_CCLD)$(LINK) $(imap_dav_reconstruct_OBJECTS) $(imap_dav_reconstruct_LDADD) $(LIBS) imap/deliver.$(OBJEXT): imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/lmtpengine.$(OBJEXT): imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/lmtpstats.$(OBJEXT): imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/proxy.$(OBJEXT): imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/deliver$(EXEEXT): $(imap_deliver_OBJECTS) $(imap_deliver_DEPENDENCIES) $(EXTRA_imap_deliver_DEPENDENCIES) imap/$(am__dirstamp) @rm -f imap/deliver$(EXEEXT) $(AM_V_CCLD)$(LINK) $(imap_deliver_OBJECTS) $(imap_deliver_LDADD) $(LIBS) imap/fetchnews.$(OBJEXT): imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/fetchnews$(EXEEXT): $(imap_fetchnews_OBJECTS) $(imap_fetchnews_DEPENDENCIES) $(EXTRA_imap_fetchnews_DEPENDENCIES) imap/$(am__dirstamp) @rm -f imap/fetchnews$(EXEEXT) $(AM_V_CCLD)$(LINK) $(imap_fetchnews_OBJECTS) $(imap_fetchnews_LDADD) $(LIBS) imap/fud.$(OBJEXT): imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) master/service.$(OBJEXT): master/$(am__dirstamp) \ master/$(DEPDIR)/$(am__dirstamp) imap/fud$(EXEEXT): $(imap_fud_OBJECTS) $(imap_fud_DEPENDENCIES) $(EXTRA_imap_fud_DEPENDENCIES) imap/$(am__dirstamp) @rm -f imap/fud$(EXEEXT) $(AM_V_CCLD)$(LINK) $(imap_fud_OBJECTS) $(imap_fud_LDADD) $(LIBS) imap/caldav_db.$(OBJEXT): imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/carddav_db.$(OBJEXT): imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/dav_db.$(OBJEXT): imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/dav_util.$(OBJEXT): imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/http_caldav.$(OBJEXT): imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/http_carddav.$(OBJEXT): imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/http_client.$(OBJEXT): imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/http_dav.$(OBJEXT): imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/http_dblookup.$(OBJEXT): imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/http_ischedule.$(OBJEXT): imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/http_proxy.$(OBJEXT): imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/http_rss.$(OBJEXT): imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/http_timezone.$(OBJEXT): imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/httpd.$(OBJEXT): imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/jcal.$(OBJEXT): imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/smtpclient.$(OBJEXT): imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/xcal.$(OBJEXT): imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/zoneinfo_db.$(OBJEXT): imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/http_err.$(OBJEXT): imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/tz_err.$(OBJEXT): imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/httpd$(EXEEXT): $(imap_httpd_OBJECTS) $(imap_httpd_DEPENDENCIES) $(EXTRA_imap_httpd_DEPENDENCIES) imap/$(am__dirstamp) @rm -f imap/httpd$(EXEEXT) $(AM_V_CCLD)$(LINK) $(imap_httpd_OBJECTS) $(imap_httpd_LDADD) $(LIBS) imap/idled.$(OBJEXT): imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/idled$(EXEEXT): $(imap_idled_OBJECTS) $(imap_idled_DEPENDENCIES) $(EXTRA_imap_idled_DEPENDENCIES) imap/$(am__dirstamp) @rm -f imap/idled$(EXEEXT) $(AM_V_CCLD)$(LINK) $(imap_idled_OBJECTS) $(imap_idled_LDADD) $(LIBS) imap/imap_proxy.$(OBJEXT): imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/imapd.$(OBJEXT): imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/pushstats.$(OBJEXT): imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/autocreate.$(OBJEXT): imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/imapd$(EXEEXT): $(imap_imapd_OBJECTS) $(imap_imapd_DEPENDENCIES) $(EXTRA_imap_imapd_DEPENDENCIES) imap/$(am__dirstamp) @rm -f imap/imapd$(EXEEXT) $(AM_V_CCLD)$(LINK) $(imap_imapd_OBJECTS) $(imap_imapd_LDADD) $(LIBS) imap/ipurge.$(OBJEXT): imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/ipurge$(EXEEXT): $(imap_ipurge_OBJECTS) $(imap_ipurge_DEPENDENCIES) $(EXTRA_imap_ipurge_DEPENDENCIES) imap/$(am__dirstamp) @rm -f imap/ipurge$(EXEEXT) $(AM_V_CCLD)$(LINK) $(imap_ipurge_OBJECTS) $(imap_ipurge_LDADD) $(LIBS) imap/lmtpd.$(OBJEXT): imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/lmtp_sieve.$(OBJEXT): imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/lmtpd$(EXEEXT): $(imap_lmtpd_OBJECTS) $(imap_lmtpd_DEPENDENCIES) $(EXTRA_imap_lmtpd_DEPENDENCIES) imap/$(am__dirstamp) @rm -f imap/lmtpd$(EXEEXT) $(AM_V_CCLD)$(LINK) $(imap_lmtpd_OBJECTS) $(imap_lmtpd_LDADD) $(LIBS) imap/mbexamine.$(OBJEXT): imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/mbexamine$(EXEEXT): $(imap_mbexamine_OBJECTS) $(imap_mbexamine_DEPENDENCIES) $(EXTRA_imap_mbexamine_DEPENDENCIES) imap/$(am__dirstamp) @rm -f imap/mbexamine$(EXEEXT) $(AM_V_CCLD)$(LINK) $(imap_mbexamine_OBJECTS) $(imap_mbexamine_LDADD) $(LIBS) imap/mbpath.$(OBJEXT): imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/mbpath$(EXEEXT): $(imap_mbpath_OBJECTS) $(imap_mbpath_DEPENDENCIES) $(EXTRA_imap_mbpath_DEPENDENCIES) imap/$(am__dirstamp) @rm -f imap/mbpath$(EXEEXT) $(AM_V_CCLD)$(LINK) $(imap_mbpath_OBJECTS) $(imap_mbpath_LDADD) $(LIBS) imap/mbtool.$(OBJEXT): imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/mbtool$(EXEEXT): $(imap_mbtool_OBJECTS) $(imap_mbtool_DEPENDENCIES) $(EXTRA_imap_mbtool_DEPENDENCIES) imap/$(am__dirstamp) @rm -f imap/mbtool$(EXEEXT) $(AM_V_CCLD)$(LINK) $(imap_mbtool_OBJECTS) $(imap_mbtool_LDADD) $(LIBS) imap/mupdate.$(OBJEXT): imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/mupdate-slave.$(OBJEXT): imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/mutex_pthread.$(OBJEXT): imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/tls_th-lock.$(OBJEXT): imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) master/service-thread.$(OBJEXT): master/$(am__dirstamp) \ master/$(DEPDIR)/$(am__dirstamp) imap/mupdate$(EXEEXT): $(imap_mupdate_OBJECTS) $(imap_mupdate_DEPENDENCIES) $(EXTRA_imap_mupdate_DEPENDENCIES) imap/$(am__dirstamp) @rm -f imap/mupdate$(EXEEXT) $(AM_V_CCLD)$(LINK) $(imap_mupdate_OBJECTS) $(imap_mupdate_LDADD) $(LIBS) imap/nntpd.$(OBJEXT): imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/nntp_err.$(OBJEXT): imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/nntpd$(EXEEXT): $(imap_nntpd_OBJECTS) $(imap_nntpd_DEPENDENCIES) $(EXTRA_imap_nntpd_DEPENDENCIES) imap/$(am__dirstamp) @rm -f imap/nntpd$(EXEEXT) $(AM_V_CCLD)$(LINK) $(imap_nntpd_OBJECTS) $(imap_nntpd_LDADD) $(LIBS) imap/pop3d.$(OBJEXT): imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/pop3d$(EXEEXT): $(imap_pop3d_OBJECTS) $(imap_pop3d_DEPENDENCIES) $(EXTRA_imap_pop3d_DEPENDENCIES) imap/$(am__dirstamp) @rm -f imap/pop3d$(EXEEXT) $(AM_V_CCLD)$(LINK) $(imap_pop3d_OBJECTS) $(imap_pop3d_LDADD) $(LIBS) imap/quota.$(OBJEXT): imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/quota$(EXEEXT): $(imap_quota_OBJECTS) $(imap_quota_DEPENDENCIES) $(EXTRA_imap_quota_DEPENDENCIES) imap/$(am__dirstamp) @rm -f imap/quota$(EXEEXT) $(AM_V_CCLD)$(LINK) $(imap_quota_OBJECTS) $(imap_quota_LDADD) $(LIBS) imap/reconstruct.$(OBJEXT): imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/reconstruct$(EXEEXT): $(imap_reconstruct_OBJECTS) $(imap_reconstruct_DEPENDENCIES) $(EXTRA_imap_reconstruct_DEPENDENCIES) imap/$(am__dirstamp) @rm -f imap/reconstruct$(EXEEXT) $(AM_V_CCLD)$(LINK) $(imap_reconstruct_OBJECTS) $(imap_reconstruct_LDADD) $(LIBS) imap/smmapd.$(OBJEXT): imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/smmapd$(EXEEXT): $(imap_smmapd_OBJECTS) $(imap_smmapd_DEPENDENCIES) $(EXTRA_imap_smmapd_DEPENDENCIES) imap/$(am__dirstamp) @rm -f imap/smmapd$(EXEEXT) $(AM_V_CCLD)$(LINK) $(imap_smmapd_OBJECTS) $(imap_smmapd_LDADD) $(LIBS) imap/squatter.$(OBJEXT): imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/squat_build.$(OBJEXT): imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/squatter$(EXEEXT): $(imap_squatter_OBJECTS) $(imap_squatter_DEPENDENCIES) $(EXTRA_imap_squatter_DEPENDENCIES) imap/$(am__dirstamp) @rm -f imap/squatter$(EXEEXT) $(AM_V_CCLD)$(LINK) $(imap_squatter_OBJECTS) $(imap_squatter_LDADD) $(LIBS) imap/sync_client.$(OBJEXT): imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/sync_support.$(OBJEXT): imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/sync_client$(EXEEXT): $(imap_sync_client_OBJECTS) $(imap_sync_client_DEPENDENCIES) $(EXTRA_imap_sync_client_DEPENDENCIES) imap/$(am__dirstamp) @rm -f imap/sync_client$(EXEEXT) $(AM_V_CCLD)$(LINK) $(imap_sync_client_OBJECTS) $(imap_sync_client_LDADD) $(LIBS) imap/sync_reset.$(OBJEXT): imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/sync_reset$(EXEEXT): $(imap_sync_reset_OBJECTS) $(imap_sync_reset_DEPENDENCIES) $(EXTRA_imap_sync_reset_DEPENDENCIES) imap/$(am__dirstamp) @rm -f imap/sync_reset$(EXEEXT) $(AM_V_CCLD)$(LINK) $(imap_sync_reset_OBJECTS) $(imap_sync_reset_LDADD) $(LIBS) imap/sync_server.$(OBJEXT): imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/sync_server$(EXEEXT): $(imap_sync_server_OBJECTS) $(imap_sync_server_DEPENDENCIES) $(EXTRA_imap_sync_server_DEPENDENCIES) imap/$(am__dirstamp) @rm -f imap/sync_server$(EXEEXT) $(AM_V_CCLD)$(LINK) $(imap_sync_server_OBJECTS) $(imap_sync_server_LDADD) $(LIBS) imap/tls_prune.$(OBJEXT): imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/tls_prune$(EXEEXT): $(imap_tls_prune_OBJECTS) $(imap_tls_prune_DEPENDENCIES) $(EXTRA_imap_tls_prune_DEPENDENCIES) imap/$(am__dirstamp) @rm -f imap/tls_prune$(EXEEXT) $(AM_V_CCLD)$(LINK) $(imap_tls_prune_OBJECTS) $(imap_tls_prune_LDADD) $(LIBS) imap/unexpunge.$(OBJEXT): imap/$(am__dirstamp) \ imap/$(DEPDIR)/$(am__dirstamp) imap/unexpunge$(EXEEXT): $(imap_unexpunge_OBJECTS) $(imap_unexpunge_DEPENDENCIES) $(EXTRA_imap_unexpunge_DEPENDENCIES) imap/$(am__dirstamp) @rm -f imap/unexpunge$(EXEEXT) $(AM_V_CCLD)$(LINK) $(imap_unexpunge_OBJECTS) $(imap_unexpunge_LDADD) $(LIBS) imtest/$(am__dirstamp): @$(MKDIR_P) imtest @: > imtest/$(am__dirstamp) imtest/$(DEPDIR)/$(am__dirstamp): @$(MKDIR_P) imtest/$(DEPDIR) @: > imtest/$(DEPDIR)/$(am__dirstamp) imtest/imtest_imtest-imtest.$(OBJEXT): imtest/$(am__dirstamp) \ imtest/$(DEPDIR)/$(am__dirstamp) imtest/imtest$(EXEEXT): $(imtest_imtest_OBJECTS) $(imtest_imtest_DEPENDENCIES) $(EXTRA_imtest_imtest_DEPENDENCIES) imtest/$(am__dirstamp) @rm -f imtest/imtest$(EXEEXT) $(AM_V_CCLD)$(imtest_imtest_LINK) $(imtest_imtest_OBJECTS) $(imtest_imtest_LDADD) $(LIBS) master/cyrusMasterMIB.$(OBJEXT): master/$(am__dirstamp) \ master/$(DEPDIR)/$(am__dirstamp) master/master.$(OBJEXT): master/$(am__dirstamp) \ master/$(DEPDIR)/$(am__dirstamp) master/master$(EXEEXT): $(master_master_OBJECTS) $(master_master_DEPENDENCIES) $(EXTRA_master_master_DEPENDENCIES) master/$(am__dirstamp) @rm -f master/master$(EXEEXT) $(AM_V_CCLD)$(LINK) $(master_master_OBJECTS) $(master_master_LDADD) $(LIBS) netnews/$(am__dirstamp): @$(MKDIR_P) netnews @: > netnews/$(am__dirstamp) netnews/$(DEPDIR)/$(am__dirstamp): @$(MKDIR_P) netnews/$(DEPDIR) @: > netnews/$(DEPDIR)/$(am__dirstamp) netnews/readconfig.$(OBJEXT): netnews/$(am__dirstamp) \ netnews/$(DEPDIR)/$(am__dirstamp) netnews/remotepurge.$(OBJEXT): netnews/$(am__dirstamp) \ netnews/$(DEPDIR)/$(am__dirstamp) netnews/remotepurge$(EXEEXT): $(netnews_remotepurge_OBJECTS) $(netnews_remotepurge_DEPENDENCIES) $(EXTRA_netnews_remotepurge_DEPENDENCIES) netnews/$(am__dirstamp) @rm -f netnews/remotepurge$(EXEEXT) $(AM_V_CCLD)$(LINK) $(netnews_remotepurge_OBJECTS) $(netnews_remotepurge_LDADD) $(LIBS) notifyd/$(am__dirstamp): @$(MKDIR_P) notifyd @: > notifyd/$(am__dirstamp) notifyd/$(DEPDIR)/$(am__dirstamp): @$(MKDIR_P) notifyd/$(DEPDIR) @: > notifyd/$(DEPDIR)/$(am__dirstamp) notifyd/notify_external.$(OBJEXT): notifyd/$(am__dirstamp) \ notifyd/$(DEPDIR)/$(am__dirstamp) notifyd/notify_log.$(OBJEXT): notifyd/$(am__dirstamp) \ notifyd/$(DEPDIR)/$(am__dirstamp) notifyd/notify_mailto.$(OBJEXT): notifyd/$(am__dirstamp) \ notifyd/$(DEPDIR)/$(am__dirstamp) notifyd/notify_null.$(OBJEXT): notifyd/$(am__dirstamp) \ notifyd/$(DEPDIR)/$(am__dirstamp) notifyd/notifyd.$(OBJEXT): notifyd/$(am__dirstamp) \ notifyd/$(DEPDIR)/$(am__dirstamp) notifyd/notify_zephyr.$(OBJEXT): notifyd/$(am__dirstamp) \ notifyd/$(DEPDIR)/$(am__dirstamp) notifyd/notifyd$(EXEEXT): $(notifyd_notifyd_OBJECTS) $(notifyd_notifyd_DEPENDENCIES) $(EXTRA_notifyd_notifyd_DEPENDENCIES) notifyd/$(am__dirstamp) @rm -f notifyd/notifyd$(EXEEXT) $(AM_V_CCLD)$(LINK) $(notifyd_notifyd_OBJECTS) $(notifyd_notifyd_LDADD) $(LIBS) notifyd/notifytest.$(OBJEXT): notifyd/$(am__dirstamp) \ notifyd/$(DEPDIR)/$(am__dirstamp) notifyd/notifytest$(EXEEXT): $(notifyd_notifytest_OBJECTS) $(notifyd_notifytest_DEPENDENCIES) $(EXTRA_notifyd_notifytest_DEPENDENCIES) notifyd/$(am__dirstamp) @rm -f notifyd/notifytest$(EXEEXT) $(AM_V_CCLD)$(LINK) $(notifyd_notifytest_OBJECTS) $(notifyd_notifytest_LDADD) $(LIBS) ptclient/$(am__dirstamp): @$(MKDIR_P) ptclient @: > ptclient/$(am__dirstamp) ptclient/$(DEPDIR)/$(am__dirstamp): @$(MKDIR_P) ptclient/$(DEPDIR) @: > ptclient/$(DEPDIR)/$(am__dirstamp) ptclient/ptdump.$(OBJEXT): ptclient/$(am__dirstamp) \ ptclient/$(DEPDIR)/$(am__dirstamp) ptclient/ptdump$(EXEEXT): $(ptclient_ptdump_OBJECTS) $(ptclient_ptdump_DEPENDENCIES) $(EXTRA_ptclient_ptdump_DEPENDENCIES) ptclient/$(am__dirstamp) @rm -f ptclient/ptdump$(EXEEXT) $(AM_V_CCLD)$(LINK) $(ptclient_ptdump_OBJECTS) $(ptclient_ptdump_LDADD) $(LIBS) ptclient/ptexpire.$(OBJEXT): ptclient/$(am__dirstamp) \ ptclient/$(DEPDIR)/$(am__dirstamp) ptclient/ptexpire$(EXEEXT): $(ptclient_ptexpire_OBJECTS) $(ptclient_ptexpire_DEPENDENCIES) $(EXTRA_ptclient_ptexpire_DEPENDENCIES) ptclient/$(am__dirstamp) @rm -f ptclient/ptexpire$(EXEEXT) $(AM_V_CCLD)$(LINK) $(ptclient_ptexpire_OBJECTS) $(ptclient_ptexpire_LDADD) $(LIBS) ptclient/ptloader.$(OBJEXT): ptclient/$(am__dirstamp) \ ptclient/$(DEPDIR)/$(am__dirstamp) ptclient/ldap.$(OBJEXT): ptclient/$(am__dirstamp) \ ptclient/$(DEPDIR)/$(am__dirstamp) ptclient/afskrb.$(OBJEXT): ptclient/$(am__dirstamp) \ ptclient/$(DEPDIR)/$(am__dirstamp) ptclient/ptloader$(EXEEXT): $(ptclient_ptloader_OBJECTS) $(ptclient_ptloader_DEPENDENCIES) $(EXTRA_ptclient_ptloader_DEPENDENCIES) ptclient/$(am__dirstamp) @rm -f ptclient/ptloader$(EXEEXT) $(AM_V_CCLD)$(ptclient_ptloader_LINK) $(ptclient_ptloader_OBJECTS) $(ptclient_ptloader_LDADD) $(LIBS) sieve/sievec.$(OBJEXT): sieve/$(am__dirstamp) \ sieve/$(DEPDIR)/$(am__dirstamp) sieve/sievec$(EXEEXT): $(sieve_sievec_OBJECTS) $(sieve_sievec_DEPENDENCIES) $(EXTRA_sieve_sievec_DEPENDENCIES) sieve/$(am__dirstamp) @rm -f sieve/sievec$(EXEEXT) $(AM_V_CCLD)$(LINK) $(sieve_sievec_OBJECTS) $(sieve_sievec_LDADD) $(LIBS) sieve/sieved.$(OBJEXT): sieve/$(am__dirstamp) \ sieve/$(DEPDIR)/$(am__dirstamp) sieve/sieved$(EXEEXT): $(sieve_sieved_OBJECTS) $(sieve_sieved_DEPENDENCIES) $(EXTRA_sieve_sieved_DEPENDENCIES) sieve/$(am__dirstamp) @rm -f sieve/sieved$(EXEEXT) $(AM_V_CCLD)$(LINK) $(sieve_sieved_OBJECTS) $(sieve_sieved_LDADD) $(LIBS) sieve/test.$(OBJEXT): sieve/$(am__dirstamp) \ sieve/$(DEPDIR)/$(am__dirstamp) sieve/test$(EXEEXT): $(sieve_test_OBJECTS) $(sieve_test_DEPENDENCIES) $(EXTRA_sieve_test_DEPENDENCIES) sieve/$(am__dirstamp) @rm -f sieve/test$(EXEEXT) $(AM_V_CCLD)$(LINK) $(sieve_test_OBJECTS) $(sieve_test_LDADD) $(LIBS) timsieved/$(am__dirstamp): @$(MKDIR_P) timsieved @: > timsieved/$(am__dirstamp) timsieved/$(DEPDIR)/$(am__dirstamp): @$(MKDIR_P) timsieved/$(DEPDIR) @: > timsieved/$(DEPDIR)/$(am__dirstamp) timsieved/actions.$(OBJEXT): timsieved/$(am__dirstamp) \ timsieved/$(DEPDIR)/$(am__dirstamp) timsieved/lex.$(OBJEXT): timsieved/$(am__dirstamp) \ timsieved/$(DEPDIR)/$(am__dirstamp) timsieved/parser.$(OBJEXT): timsieved/$(am__dirstamp) \ timsieved/$(DEPDIR)/$(am__dirstamp) timsieved/scripttest.$(OBJEXT): timsieved/$(am__dirstamp) \ timsieved/$(DEPDIR)/$(am__dirstamp) timsieved/timsieved.$(OBJEXT): timsieved/$(am__dirstamp) \ timsieved/$(DEPDIR)/$(am__dirstamp) timsieved/timsieved$(EXEEXT): $(timsieved_timsieved_OBJECTS) $(timsieved_timsieved_DEPENDENCIES) $(EXTRA_timsieved_timsieved_DEPENDENCIES) timsieved/$(am__dirstamp) @rm -f timsieved/timsieved$(EXEEXT) $(AM_V_CCLD)$(LINK) $(timsieved_timsieved_OBJECTS) $(timsieved_timsieved_LDADD) $(LIBS) tools/$(am__dirstamp): @$(MKDIR_P) tools @: > tools/$(am__dirstamp) tools/$(DEPDIR)/$(am__dirstamp): @$(MKDIR_P) tools/$(DEPDIR) @: > tools/$(DEPDIR)/$(am__dirstamp) tools/htmlstrip.$(OBJEXT): tools/$(am__dirstamp) \ tools/$(DEPDIR)/$(am__dirstamp) tools/htmlstrip$(EXEEXT): $(tools_htmlstrip_OBJECTS) $(tools_htmlstrip_DEPENDENCIES) $(EXTRA_tools_htmlstrip_DEPENDENCIES) tools/$(am__dirstamp) @rm -f tools/htmlstrip$(EXEEXT) $(AM_V_CCLD)$(LINK) $(tools_htmlstrip_OBJECTS) $(tools_htmlstrip_LDADD) $(LIBS) mostlyclean-compile: -rm -f *.$(OBJEXT) -rm -f com_err/et/*.$(OBJEXT) -rm -f com_err/et/*.lo -rm -f cunit/*.$(OBJEXT) -rm -f imap/*.$(OBJEXT) -rm -f imap/*.lo -rm -f imtest/*.$(OBJEXT) -rm -f lib/*.$(OBJEXT) -rm -f lib/*.lo -rm -f master/*.$(OBJEXT) -rm -f netnews/*.$(OBJEXT) -rm -f notifyd/*.$(OBJEXT) -rm -f perl/sieve/lib/*.$(OBJEXT) -rm -f ptclient/*.$(OBJEXT) -rm -f sieve/*.$(OBJEXT) -rm -f sieve/*.lo -rm -f timsieved/*.$(OBJEXT) -rm -f tools/*.$(OBJEXT) distclean-compile: -rm -f *.tab.c @AMDEP_TRUE@@am__include@ @am__quote@com_err/et/$(DEPDIR)/com_err_et_libcyrus_com_err_la-com_err.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@com_err/et/$(DEPDIR)/com_err_et_libcyrus_com_err_la-error_message.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@com_err/et/$(DEPDIR)/com_err_et_libcyrus_com_err_la-et_name.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@com_err/et/$(DEPDIR)/com_err_et_libcyrus_com_err_la-init_et.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@cunit/$(DEPDIR)/syslog.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@cunit/$(DEPDIR)/timeout.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@cunit/$(DEPDIR)/unit.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/arbitron.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/autocreate.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/caldav_db.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/carddav_db.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/chk_cyrus.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/cli_fatal.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/ctl_cyrusdb.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/ctl_deliver.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/ctl_mboxlist.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/ctl_zoneinfo.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/cvt_cyrusdb.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/cyr_dbtool.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/cyr_deny.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/cyr_df.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/cyr_expire.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/cyr_info.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/cyr_sequence.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/cyr_synclog.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/cyr_userseen.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/cyr_virusscan.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/cyrdump.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/dav_db.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/dav_reconstruct.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/dav_util.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/deliver.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/fetchnews.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/fud.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/http_caldav.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/http_carddav.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/http_client.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/http_dav.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/http_dblookup.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/http_err.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/http_ischedule.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/http_proxy.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/http_rss.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/http_timezone.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/httpd.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/idled.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/imap_libcyrus_imap_la-annotate.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/imap_libcyrus_imap_la-append.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/imap_libcyrus_imap_la-backend.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/imap_libcyrus_imap_la-caldav_db.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/imap_libcyrus_imap_la-carddav_db.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/imap_libcyrus_imap_la-convert_code.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/imap_libcyrus_imap_la-dav_db.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/imap_libcyrus_imap_la-dav_util.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/imap_libcyrus_imap_la-dlist.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/imap_libcyrus_imap_la-duplicate.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/imap_libcyrus_imap_la-global.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/imap_libcyrus_imap_la-http_caldav.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/imap_libcyrus_imap_la-http_carddav.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/imap_libcyrus_imap_la-http_client.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/imap_libcyrus_imap_la-http_dav.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/imap_libcyrus_imap_la-http_dblookup.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/imap_libcyrus_imap_la-http_err.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/imap_libcyrus_imap_la-http_ischedule.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/imap_libcyrus_imap_la-http_proxy.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/imap_libcyrus_imap_la-http_rss.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/imap_libcyrus_imap_la-http_timezone.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/imap_libcyrus_imap_la-httpd.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/imap_libcyrus_imap_la-idle.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/imap_libcyrus_imap_la-idlemsg.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/imap_libcyrus_imap_la-imap_err.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/imap_libcyrus_imap_la-imapparse.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/imap_libcyrus_imap_la-index.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/imap_libcyrus_imap_la-jcal.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/imap_libcyrus_imap_la-mailbox.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/imap_libcyrus_imap_la-mbdump.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/imap_libcyrus_imap_la-mboxevent.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/imap_libcyrus_imap_la-mboxkey.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/imap_libcyrus_imap_la-mboxlist.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/imap_libcyrus_imap_la-mboxname.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/imap_libcyrus_imap_la-message.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/imap_libcyrus_imap_la-message_guid.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/imap_libcyrus_imap_la-mupdate-client.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/imap_libcyrus_imap_la-mupdate_err.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/imap_libcyrus_imap_la-notify.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/imap_libcyrus_imap_la-partlist.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/imap_libcyrus_imap_la-proc.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/imap_libcyrus_imap_la-proxy.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/imap_libcyrus_imap_la-quota_db.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/imap_libcyrus_imap_la-rfc822_header.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/imap_libcyrus_imap_la-saslclient.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/imap_libcyrus_imap_la-saslserver.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/imap_libcyrus_imap_la-search_engines.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/imap_libcyrus_imap_la-seen_db.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/imap_libcyrus_imap_la-sequence.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/imap_libcyrus_imap_la-setproctitle.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/imap_libcyrus_imap_la-smtpclient.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/imap_libcyrus_imap_la-spool.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/imap_libcyrus_imap_la-squat.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/imap_libcyrus_imap_la-squat_internal.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/imap_libcyrus_imap_la-statuscache_db.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/imap_libcyrus_imap_la-sync_log.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/imap_libcyrus_imap_la-telemetry.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/imap_libcyrus_imap_la-tls.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/imap_libcyrus_imap_la-tls_th-lock.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/imap_libcyrus_imap_la-tz_err.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/imap_libcyrus_imap_la-user.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/imap_libcyrus_imap_la-userdeny_db.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/imap_libcyrus_imap_la-version.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/imap_libcyrus_imap_la-xcal.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/imap_libcyrus_imap_la-zoneinfo_db.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/imap_proxy.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/imapd.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/ipurge.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/jcal.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/lmtp_sieve.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/lmtpd.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/lmtpengine.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/lmtpstats.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/mbexamine.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/mbpath.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/mbtool.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/mupdate-slave.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/mupdate.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/mutex_fake.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/mutex_pthread.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/nntp_err.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/nntpd.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/pop3d.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/proxy.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/pushstats.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/quota.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/reconstruct.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/smmapd.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/smtpclient.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/spool.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/squat_build.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/squatter.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/sync_client.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/sync_reset.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/sync_server.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/sync_support.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/tls_prune.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/tls_th-lock.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/tz_err.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/unexpunge.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/xcal.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imap/$(DEPDIR)/zoneinfo_db.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@imtest/$(DEPDIR)/imtest_imtest-imtest.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/acl.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/acl_afs.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/arrayu64.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/assert.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/auth.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/auth_krb.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/auth_krb5.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/auth_pts.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/auth_unix.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/bitvector.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/bsearch.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/byteorder64.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/charset.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/command.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/crc32.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/cyrusdb.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/cyrusdb_berkeley.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/cyrusdb_flat.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/cyrusdb_quotalegacy.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/cyrusdb_skiplist.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/cyrusdb_sql.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/cyrusdb_twoskip.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/ftruncate.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/getaddrinfo.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/getdtablesize.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/getnameinfo.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/glob.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/gmtoff_gmtime.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/gmtoff_tm.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/hash.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/hashu64.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/imapurl.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/imclient.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/imparse.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/iostat.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/iptostring.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/lib_libcyrus_la-acl.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/lib_libcyrus_la-acl_afs.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/lib_libcyrus_la-auth.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/lib_libcyrus_la-auth_krb.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/lib_libcyrus_la-auth_krb5.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/lib_libcyrus_la-auth_pts.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/lib_libcyrus_la-auth_unix.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/lib_libcyrus_la-bitvector.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/lib_libcyrus_la-bsearch.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/lib_libcyrus_la-byteorder64.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/lib_libcyrus_la-charset.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/lib_libcyrus_la-chartable.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/lib_libcyrus_la-command.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/lib_libcyrus_la-crc32.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/lib_libcyrus_la-cyrusdb.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/lib_libcyrus_la-cyrusdb_berkeley.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/lib_libcyrus_la-cyrusdb_flat.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/lib_libcyrus_la-cyrusdb_quotalegacy.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/lib_libcyrus_la-cyrusdb_skiplist.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/lib_libcyrus_la-cyrusdb_sql.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/lib_libcyrus_la-cyrusdb_twoskip.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/lib_libcyrus_la-glob.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/lib_libcyrus_la-gmtoff_gmtime.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/lib_libcyrus_la-gmtoff_tm.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/lib_libcyrus_la-imapurl.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/lib_libcyrus_la-imclient.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/lib_libcyrus_la-imparse.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/lib_libcyrus_la-iostat.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/lib_libcyrus_la-iptostring.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/lib_libcyrus_la-libcyr_cfg.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/lib_libcyrus_la-lsort.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/lib_libcyrus_la-mappedfile.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/lib_libcyrus_la-mkgmtime.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/lib_libcyrus_la-nonblock_fcntl.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/lib_libcyrus_la-nonblock_ioctl.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/lib_libcyrus_la-parseaddr.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/lib_libcyrus_la-prot.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/lib_libcyrus_la-ptrarray.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/lib_libcyrus_la-rfc822tok.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/lib_libcyrus_la-signals.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/lib_libcyrus_la-stristr.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/lib_libcyrus_la-times.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/lib_libcyrus_la-tok.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/lib_libcyrus_la-wildmat.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/lib_libcyrus_min_la-arrayu64.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/lib_libcyrus_min_la-assert.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/lib_libcyrus_min_la-getaddrinfo.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/lib_libcyrus_min_la-getnameinfo.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/lib_libcyrus_min_la-hash.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/lib_libcyrus_min_la-hashu64.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/lib_libcyrus_min_la-imapopts.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/lib_libcyrus_min_la-libconfig.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/lib_libcyrus_min_la-lock_fcntl.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/lib_libcyrus_min_la-lock_flock.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/lib_libcyrus_min_la-map_nommap.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/lib_libcyrus_min_la-map_shared.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/lib_libcyrus_min_la-map_stupidshared.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/lib_libcyrus_min_la-mpool.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/lib_libcyrus_min_la-retry.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/lib_libcyrus_min_la-strarray.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/lib_libcyrus_min_la-strhash.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/lib_libcyrus_min_la-util.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/lib_libcyrus_min_la-vparse.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/lib_libcyrus_min_la-xmalloc.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/lib_libcyrus_min_la-xstrlcat.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/lib_libcyrus_min_la-xstrlcpy.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/libconfig.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/libcyr_cfg.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/lock_fcntl.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/lock_flock.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/lsort.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/map_nommap.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/map_shared.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/map_stupidshared.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/mappedfile.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/memmem.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/memmove.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/mkgmtime.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/mpool.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/nonblock_fcntl.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/nonblock_ioctl.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/parseaddr.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/posix_fadvise.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/prot.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/ptrarray.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/retry.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/rfc822tok.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/signals.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/strarray.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/strcasecmp.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/strerror.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/strhash.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/stristr.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/strsep.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/times.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/tok.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/util.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/vparse.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/wildmat.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/xmalloc.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/xstrlcat.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@lib/$(DEPDIR)/xstrlcpy.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@master/$(DEPDIR)/cyrusMasterMIB.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@master/$(DEPDIR)/master.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@master/$(DEPDIR)/masterconf.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@master/$(DEPDIR)/service-thread.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@master/$(DEPDIR)/service.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@netnews/$(DEPDIR)/readconfig.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@netnews/$(DEPDIR)/remotepurge.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@notifyd/$(DEPDIR)/notify_external.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@notifyd/$(DEPDIR)/notify_log.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@notifyd/$(DEPDIR)/notify_mailto.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@notifyd/$(DEPDIR)/notify_null.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@notifyd/$(DEPDIR)/notify_zephyr.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@notifyd/$(DEPDIR)/notifyd.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@notifyd/$(DEPDIR)/notifytest.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@perl/sieve/lib/$(DEPDIR)/isieve.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@perl/sieve/lib/$(DEPDIR)/lex.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@perl/sieve/lib/$(DEPDIR)/request.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@ptclient/$(DEPDIR)/afskrb.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@ptclient/$(DEPDIR)/ldap.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@ptclient/$(DEPDIR)/ptdump.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@ptclient/$(DEPDIR)/ptexpire.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@ptclient/$(DEPDIR)/ptloader.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@sieve/$(DEPDIR)/sieve_libcyrus_sieve_la-addr.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@sieve/$(DEPDIR)/sieve_libcyrus_sieve_la-bc_dump.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@sieve/$(DEPDIR)/sieve_libcyrus_sieve_la-bc_emit.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@sieve/$(DEPDIR)/sieve_libcyrus_sieve_la-bc_eval.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@sieve/$(DEPDIR)/sieve_libcyrus_sieve_la-bc_generate.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@sieve/$(DEPDIR)/sieve_libcyrus_sieve_la-comparator.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@sieve/$(DEPDIR)/sieve_libcyrus_sieve_la-flags.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@sieve/$(DEPDIR)/sieve_libcyrus_sieve_la-interp.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@sieve/$(DEPDIR)/sieve_libcyrus_sieve_la-message.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@sieve/$(DEPDIR)/sieve_libcyrus_sieve_la-script.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@sieve/$(DEPDIR)/sieve_libcyrus_sieve_la-sieve.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@sieve/$(DEPDIR)/sieve_libcyrus_sieve_la-sieve_err.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@sieve/$(DEPDIR)/sieve_libcyrus_sieve_la-tree.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@sieve/$(DEPDIR)/sieve_libcyrus_sieve_la-varlist.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@sieve/$(DEPDIR)/sieve_libcyrus_sieve_lex_la-addr-lex.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@sieve/$(DEPDIR)/sieve_libcyrus_sieve_lex_la-sieve-lex.Plo@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@sieve/$(DEPDIR)/sievec.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@sieve/$(DEPDIR)/sieved.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@sieve/$(DEPDIR)/test.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@timsieved/$(DEPDIR)/actions.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@timsieved/$(DEPDIR)/lex.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@timsieved/$(DEPDIR)/parser.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@timsieved/$(DEPDIR)/scripttest.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@timsieved/$(DEPDIR)/timsieved.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@tools/$(DEPDIR)/htmlstrip.Po@am__quote@ .c.o: @am__fastdepCC_TRUE@ $(AM_V_CC)depbase=`echo $@ | sed 's|[^/]*$$|$(DEPDIR)/&|;s|\.o$$||'`;\ @am__fastdepCC_TRUE@ $(COMPILE) -MT $@ -MD -MP -MF $$depbase.Tpo -c -o $@ $< &&\ @am__fastdepCC_TRUE@ $(am__mv) $$depbase.Tpo $$depbase.Po @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c -o $@ $< .c.obj: @am__fastdepCC_TRUE@ $(AM_V_CC)depbase=`echo $@ | sed 's|[^/]*$$|$(DEPDIR)/&|;s|\.obj$$||'`;\ @am__fastdepCC_TRUE@ $(COMPILE) -MT $@ -MD -MP -MF $$depbase.Tpo -c -o $@ `$(CYGPATH_W) '$<'` &&\ @am__fastdepCC_TRUE@ $(am__mv) $$depbase.Tpo $$depbase.Po @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(COMPILE) -c -o $@ `$(CYGPATH_W) '$<'` .c.lo: @am__fastdepCC_TRUE@ $(AM_V_CC)depbase=`echo $@ | sed 's|[^/]*$$|$(DEPDIR)/&|;s|\.lo$$||'`;\ @am__fastdepCC_TRUE@ $(LTCOMPILE) -MT $@ -MD -MP -MF $$depbase.Tpo -c -o $@ $< &&\ @am__fastdepCC_TRUE@ $(am__mv) $$depbase.Tpo $$depbase.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LTCOMPILE) -c -o $@ $< com_err/et/com_err_et_libcyrus_com_err_la-com_err.lo: com_err/et/com_err.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(com_err_et_libcyrus_com_err_la_CFLAGS) $(CFLAGS) -MT com_err/et/com_err_et_libcyrus_com_err_la-com_err.lo -MD -MP -MF com_err/et/$(DEPDIR)/com_err_et_libcyrus_com_err_la-com_err.Tpo -c -o com_err/et/com_err_et_libcyrus_com_err_la-com_err.lo `test -f 'com_err/et/com_err.c' || echo '$(srcdir)/'`com_err/et/com_err.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) com_err/et/$(DEPDIR)/com_err_et_libcyrus_com_err_la-com_err.Tpo com_err/et/$(DEPDIR)/com_err_et_libcyrus_com_err_la-com_err.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='com_err/et/com_err.c' object='com_err/et/com_err_et_libcyrus_com_err_la-com_err.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(com_err_et_libcyrus_com_err_la_CFLAGS) $(CFLAGS) -c -o com_err/et/com_err_et_libcyrus_com_err_la-com_err.lo `test -f 'com_err/et/com_err.c' || echo '$(srcdir)/'`com_err/et/com_err.c com_err/et/com_err_et_libcyrus_com_err_la-error_message.lo: com_err/et/error_message.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(com_err_et_libcyrus_com_err_la_CFLAGS) $(CFLAGS) -MT com_err/et/com_err_et_libcyrus_com_err_la-error_message.lo -MD -MP -MF com_err/et/$(DEPDIR)/com_err_et_libcyrus_com_err_la-error_message.Tpo -c -o com_err/et/com_err_et_libcyrus_com_err_la-error_message.lo `test -f 'com_err/et/error_message.c' || echo '$(srcdir)/'`com_err/et/error_message.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) com_err/et/$(DEPDIR)/com_err_et_libcyrus_com_err_la-error_message.Tpo com_err/et/$(DEPDIR)/com_err_et_libcyrus_com_err_la-error_message.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='com_err/et/error_message.c' object='com_err/et/com_err_et_libcyrus_com_err_la-error_message.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(com_err_et_libcyrus_com_err_la_CFLAGS) $(CFLAGS) -c -o com_err/et/com_err_et_libcyrus_com_err_la-error_message.lo `test -f 'com_err/et/error_message.c' || echo '$(srcdir)/'`com_err/et/error_message.c com_err/et/com_err_et_libcyrus_com_err_la-et_name.lo: com_err/et/et_name.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(com_err_et_libcyrus_com_err_la_CFLAGS) $(CFLAGS) -MT com_err/et/com_err_et_libcyrus_com_err_la-et_name.lo -MD -MP -MF com_err/et/$(DEPDIR)/com_err_et_libcyrus_com_err_la-et_name.Tpo -c -o com_err/et/com_err_et_libcyrus_com_err_la-et_name.lo `test -f 'com_err/et/et_name.c' || echo '$(srcdir)/'`com_err/et/et_name.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) com_err/et/$(DEPDIR)/com_err_et_libcyrus_com_err_la-et_name.Tpo com_err/et/$(DEPDIR)/com_err_et_libcyrus_com_err_la-et_name.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='com_err/et/et_name.c' object='com_err/et/com_err_et_libcyrus_com_err_la-et_name.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(com_err_et_libcyrus_com_err_la_CFLAGS) $(CFLAGS) -c -o com_err/et/com_err_et_libcyrus_com_err_la-et_name.lo `test -f 'com_err/et/et_name.c' || echo '$(srcdir)/'`com_err/et/et_name.c com_err/et/com_err_et_libcyrus_com_err_la-init_et.lo: com_err/et/init_et.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(com_err_et_libcyrus_com_err_la_CFLAGS) $(CFLAGS) -MT com_err/et/com_err_et_libcyrus_com_err_la-init_et.lo -MD -MP -MF com_err/et/$(DEPDIR)/com_err_et_libcyrus_com_err_la-init_et.Tpo -c -o com_err/et/com_err_et_libcyrus_com_err_la-init_et.lo `test -f 'com_err/et/init_et.c' || echo '$(srcdir)/'`com_err/et/init_et.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) com_err/et/$(DEPDIR)/com_err_et_libcyrus_com_err_la-init_et.Tpo com_err/et/$(DEPDIR)/com_err_et_libcyrus_com_err_la-init_et.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='com_err/et/init_et.c' object='com_err/et/com_err_et_libcyrus_com_err_la-init_et.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(com_err_et_libcyrus_com_err_la_CFLAGS) $(CFLAGS) -c -o com_err/et/com_err_et_libcyrus_com_err_la-init_et.lo `test -f 'com_err/et/init_et.c' || echo '$(srcdir)/'`com_err/et/init_et.c imap/imap_libcyrus_imap_la-annotate.lo: imap/annotate.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -MT imap/imap_libcyrus_imap_la-annotate.lo -MD -MP -MF imap/$(DEPDIR)/imap_libcyrus_imap_la-annotate.Tpo -c -o imap/imap_libcyrus_imap_la-annotate.lo `test -f 'imap/annotate.c' || echo '$(srcdir)/'`imap/annotate.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) imap/$(DEPDIR)/imap_libcyrus_imap_la-annotate.Tpo imap/$(DEPDIR)/imap_libcyrus_imap_la-annotate.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='imap/annotate.c' object='imap/imap_libcyrus_imap_la-annotate.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -c -o imap/imap_libcyrus_imap_la-annotate.lo `test -f 'imap/annotate.c' || echo '$(srcdir)/'`imap/annotate.c imap/imap_libcyrus_imap_la-append.lo: imap/append.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -MT imap/imap_libcyrus_imap_la-append.lo -MD -MP -MF imap/$(DEPDIR)/imap_libcyrus_imap_la-append.Tpo -c -o imap/imap_libcyrus_imap_la-append.lo `test -f 'imap/append.c' || echo '$(srcdir)/'`imap/append.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) imap/$(DEPDIR)/imap_libcyrus_imap_la-append.Tpo imap/$(DEPDIR)/imap_libcyrus_imap_la-append.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='imap/append.c' object='imap/imap_libcyrus_imap_la-append.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -c -o imap/imap_libcyrus_imap_la-append.lo `test -f 'imap/append.c' || echo '$(srcdir)/'`imap/append.c imap/imap_libcyrus_imap_la-backend.lo: imap/backend.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -MT imap/imap_libcyrus_imap_la-backend.lo -MD -MP -MF imap/$(DEPDIR)/imap_libcyrus_imap_la-backend.Tpo -c -o imap/imap_libcyrus_imap_la-backend.lo `test -f 'imap/backend.c' || echo '$(srcdir)/'`imap/backend.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) imap/$(DEPDIR)/imap_libcyrus_imap_la-backend.Tpo imap/$(DEPDIR)/imap_libcyrus_imap_la-backend.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='imap/backend.c' object='imap/imap_libcyrus_imap_la-backend.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -c -o imap/imap_libcyrus_imap_la-backend.lo `test -f 'imap/backend.c' || echo '$(srcdir)/'`imap/backend.c imap/imap_libcyrus_imap_la-convert_code.lo: imap/convert_code.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -MT imap/imap_libcyrus_imap_la-convert_code.lo -MD -MP -MF imap/$(DEPDIR)/imap_libcyrus_imap_la-convert_code.Tpo -c -o imap/imap_libcyrus_imap_la-convert_code.lo `test -f 'imap/convert_code.c' || echo '$(srcdir)/'`imap/convert_code.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) imap/$(DEPDIR)/imap_libcyrus_imap_la-convert_code.Tpo imap/$(DEPDIR)/imap_libcyrus_imap_la-convert_code.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='imap/convert_code.c' object='imap/imap_libcyrus_imap_la-convert_code.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -c -o imap/imap_libcyrus_imap_la-convert_code.lo `test -f 'imap/convert_code.c' || echo '$(srcdir)/'`imap/convert_code.c imap/imap_libcyrus_imap_la-dlist.lo: imap/dlist.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -MT imap/imap_libcyrus_imap_la-dlist.lo -MD -MP -MF imap/$(DEPDIR)/imap_libcyrus_imap_la-dlist.Tpo -c -o imap/imap_libcyrus_imap_la-dlist.lo `test -f 'imap/dlist.c' || echo '$(srcdir)/'`imap/dlist.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) imap/$(DEPDIR)/imap_libcyrus_imap_la-dlist.Tpo imap/$(DEPDIR)/imap_libcyrus_imap_la-dlist.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='imap/dlist.c' object='imap/imap_libcyrus_imap_la-dlist.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -c -o imap/imap_libcyrus_imap_la-dlist.lo `test -f 'imap/dlist.c' || echo '$(srcdir)/'`imap/dlist.c imap/imap_libcyrus_imap_la-duplicate.lo: imap/duplicate.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -MT imap/imap_libcyrus_imap_la-duplicate.lo -MD -MP -MF imap/$(DEPDIR)/imap_libcyrus_imap_la-duplicate.Tpo -c -o imap/imap_libcyrus_imap_la-duplicate.lo `test -f 'imap/duplicate.c' || echo '$(srcdir)/'`imap/duplicate.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) imap/$(DEPDIR)/imap_libcyrus_imap_la-duplicate.Tpo imap/$(DEPDIR)/imap_libcyrus_imap_la-duplicate.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='imap/duplicate.c' object='imap/imap_libcyrus_imap_la-duplicate.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -c -o imap/imap_libcyrus_imap_la-duplicate.lo `test -f 'imap/duplicate.c' || echo '$(srcdir)/'`imap/duplicate.c imap/imap_libcyrus_imap_la-global.lo: imap/global.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -MT imap/imap_libcyrus_imap_la-global.lo -MD -MP -MF imap/$(DEPDIR)/imap_libcyrus_imap_la-global.Tpo -c -o imap/imap_libcyrus_imap_la-global.lo `test -f 'imap/global.c' || echo '$(srcdir)/'`imap/global.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) imap/$(DEPDIR)/imap_libcyrus_imap_la-global.Tpo imap/$(DEPDIR)/imap_libcyrus_imap_la-global.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='imap/global.c' object='imap/imap_libcyrus_imap_la-global.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -c -o imap/imap_libcyrus_imap_la-global.lo `test -f 'imap/global.c' || echo '$(srcdir)/'`imap/global.c imap/imap_libcyrus_imap_la-idle.lo: imap/idle.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -MT imap/imap_libcyrus_imap_la-idle.lo -MD -MP -MF imap/$(DEPDIR)/imap_libcyrus_imap_la-idle.Tpo -c -o imap/imap_libcyrus_imap_la-idle.lo `test -f 'imap/idle.c' || echo '$(srcdir)/'`imap/idle.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) imap/$(DEPDIR)/imap_libcyrus_imap_la-idle.Tpo imap/$(DEPDIR)/imap_libcyrus_imap_la-idle.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='imap/idle.c' object='imap/imap_libcyrus_imap_la-idle.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -c -o imap/imap_libcyrus_imap_la-idle.lo `test -f 'imap/idle.c' || echo '$(srcdir)/'`imap/idle.c imap/imap_libcyrus_imap_la-idlemsg.lo: imap/idlemsg.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -MT imap/imap_libcyrus_imap_la-idlemsg.lo -MD -MP -MF imap/$(DEPDIR)/imap_libcyrus_imap_la-idlemsg.Tpo -c -o imap/imap_libcyrus_imap_la-idlemsg.lo `test -f 'imap/idlemsg.c' || echo '$(srcdir)/'`imap/idlemsg.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) imap/$(DEPDIR)/imap_libcyrus_imap_la-idlemsg.Tpo imap/$(DEPDIR)/imap_libcyrus_imap_la-idlemsg.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='imap/idlemsg.c' object='imap/imap_libcyrus_imap_la-idlemsg.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -c -o imap/imap_libcyrus_imap_la-idlemsg.lo `test -f 'imap/idlemsg.c' || echo '$(srcdir)/'`imap/idlemsg.c imap/imap_libcyrus_imap_la-imapparse.lo: imap/imapparse.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -MT imap/imap_libcyrus_imap_la-imapparse.lo -MD -MP -MF imap/$(DEPDIR)/imap_libcyrus_imap_la-imapparse.Tpo -c -o imap/imap_libcyrus_imap_la-imapparse.lo `test -f 'imap/imapparse.c' || echo '$(srcdir)/'`imap/imapparse.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) imap/$(DEPDIR)/imap_libcyrus_imap_la-imapparse.Tpo imap/$(DEPDIR)/imap_libcyrus_imap_la-imapparse.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='imap/imapparse.c' object='imap/imap_libcyrus_imap_la-imapparse.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -c -o imap/imap_libcyrus_imap_la-imapparse.lo `test -f 'imap/imapparse.c' || echo '$(srcdir)/'`imap/imapparse.c imap/imap_libcyrus_imap_la-index.lo: imap/index.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -MT imap/imap_libcyrus_imap_la-index.lo -MD -MP -MF imap/$(DEPDIR)/imap_libcyrus_imap_la-index.Tpo -c -o imap/imap_libcyrus_imap_la-index.lo `test -f 'imap/index.c' || echo '$(srcdir)/'`imap/index.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) imap/$(DEPDIR)/imap_libcyrus_imap_la-index.Tpo imap/$(DEPDIR)/imap_libcyrus_imap_la-index.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='imap/index.c' object='imap/imap_libcyrus_imap_la-index.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -c -o imap/imap_libcyrus_imap_la-index.lo `test -f 'imap/index.c' || echo '$(srcdir)/'`imap/index.c imap/imap_libcyrus_imap_la-mailbox.lo: imap/mailbox.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -MT imap/imap_libcyrus_imap_la-mailbox.lo -MD -MP -MF imap/$(DEPDIR)/imap_libcyrus_imap_la-mailbox.Tpo -c -o imap/imap_libcyrus_imap_la-mailbox.lo `test -f 'imap/mailbox.c' || echo '$(srcdir)/'`imap/mailbox.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) imap/$(DEPDIR)/imap_libcyrus_imap_la-mailbox.Tpo imap/$(DEPDIR)/imap_libcyrus_imap_la-mailbox.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='imap/mailbox.c' object='imap/imap_libcyrus_imap_la-mailbox.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -c -o imap/imap_libcyrus_imap_la-mailbox.lo `test -f 'imap/mailbox.c' || echo '$(srcdir)/'`imap/mailbox.c imap/imap_libcyrus_imap_la-mbdump.lo: imap/mbdump.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -MT imap/imap_libcyrus_imap_la-mbdump.lo -MD -MP -MF imap/$(DEPDIR)/imap_libcyrus_imap_la-mbdump.Tpo -c -o imap/imap_libcyrus_imap_la-mbdump.lo `test -f 'imap/mbdump.c' || echo '$(srcdir)/'`imap/mbdump.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) imap/$(DEPDIR)/imap_libcyrus_imap_la-mbdump.Tpo imap/$(DEPDIR)/imap_libcyrus_imap_la-mbdump.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='imap/mbdump.c' object='imap/imap_libcyrus_imap_la-mbdump.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -c -o imap/imap_libcyrus_imap_la-mbdump.lo `test -f 'imap/mbdump.c' || echo '$(srcdir)/'`imap/mbdump.c imap/imap_libcyrus_imap_la-mboxkey.lo: imap/mboxkey.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -MT imap/imap_libcyrus_imap_la-mboxkey.lo -MD -MP -MF imap/$(DEPDIR)/imap_libcyrus_imap_la-mboxkey.Tpo -c -o imap/imap_libcyrus_imap_la-mboxkey.lo `test -f 'imap/mboxkey.c' || echo '$(srcdir)/'`imap/mboxkey.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) imap/$(DEPDIR)/imap_libcyrus_imap_la-mboxkey.Tpo imap/$(DEPDIR)/imap_libcyrus_imap_la-mboxkey.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='imap/mboxkey.c' object='imap/imap_libcyrus_imap_la-mboxkey.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -c -o imap/imap_libcyrus_imap_la-mboxkey.lo `test -f 'imap/mboxkey.c' || echo '$(srcdir)/'`imap/mboxkey.c imap/imap_libcyrus_imap_la-mboxlist.lo: imap/mboxlist.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -MT imap/imap_libcyrus_imap_la-mboxlist.lo -MD -MP -MF imap/$(DEPDIR)/imap_libcyrus_imap_la-mboxlist.Tpo -c -o imap/imap_libcyrus_imap_la-mboxlist.lo `test -f 'imap/mboxlist.c' || echo '$(srcdir)/'`imap/mboxlist.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) imap/$(DEPDIR)/imap_libcyrus_imap_la-mboxlist.Tpo imap/$(DEPDIR)/imap_libcyrus_imap_la-mboxlist.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='imap/mboxlist.c' object='imap/imap_libcyrus_imap_la-mboxlist.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -c -o imap/imap_libcyrus_imap_la-mboxlist.lo `test -f 'imap/mboxlist.c' || echo '$(srcdir)/'`imap/mboxlist.c imap/imap_libcyrus_imap_la-mboxevent.lo: imap/mboxevent.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -MT imap/imap_libcyrus_imap_la-mboxevent.lo -MD -MP -MF imap/$(DEPDIR)/imap_libcyrus_imap_la-mboxevent.Tpo -c -o imap/imap_libcyrus_imap_la-mboxevent.lo `test -f 'imap/mboxevent.c' || echo '$(srcdir)/'`imap/mboxevent.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) imap/$(DEPDIR)/imap_libcyrus_imap_la-mboxevent.Tpo imap/$(DEPDIR)/imap_libcyrus_imap_la-mboxevent.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='imap/mboxevent.c' object='imap/imap_libcyrus_imap_la-mboxevent.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -c -o imap/imap_libcyrus_imap_la-mboxevent.lo `test -f 'imap/mboxevent.c' || echo '$(srcdir)/'`imap/mboxevent.c imap/imap_libcyrus_imap_la-mboxname.lo: imap/mboxname.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -MT imap/imap_libcyrus_imap_la-mboxname.lo -MD -MP -MF imap/$(DEPDIR)/imap_libcyrus_imap_la-mboxname.Tpo -c -o imap/imap_libcyrus_imap_la-mboxname.lo `test -f 'imap/mboxname.c' || echo '$(srcdir)/'`imap/mboxname.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) imap/$(DEPDIR)/imap_libcyrus_imap_la-mboxname.Tpo imap/$(DEPDIR)/imap_libcyrus_imap_la-mboxname.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='imap/mboxname.c' object='imap/imap_libcyrus_imap_la-mboxname.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -c -o imap/imap_libcyrus_imap_la-mboxname.lo `test -f 'imap/mboxname.c' || echo '$(srcdir)/'`imap/mboxname.c imap/imap_libcyrus_imap_la-message_guid.lo: imap/message_guid.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -MT imap/imap_libcyrus_imap_la-message_guid.lo -MD -MP -MF imap/$(DEPDIR)/imap_libcyrus_imap_la-message_guid.Tpo -c -o imap/imap_libcyrus_imap_la-message_guid.lo `test -f 'imap/message_guid.c' || echo '$(srcdir)/'`imap/message_guid.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) imap/$(DEPDIR)/imap_libcyrus_imap_la-message_guid.Tpo imap/$(DEPDIR)/imap_libcyrus_imap_la-message_guid.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='imap/message_guid.c' object='imap/imap_libcyrus_imap_la-message_guid.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -c -o imap/imap_libcyrus_imap_la-message_guid.lo `test -f 'imap/message_guid.c' || echo '$(srcdir)/'`imap/message_guid.c imap/imap_libcyrus_imap_la-message.lo: imap/message.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -MT imap/imap_libcyrus_imap_la-message.lo -MD -MP -MF imap/$(DEPDIR)/imap_libcyrus_imap_la-message.Tpo -c -o imap/imap_libcyrus_imap_la-message.lo `test -f 'imap/message.c' || echo '$(srcdir)/'`imap/message.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) imap/$(DEPDIR)/imap_libcyrus_imap_la-message.Tpo imap/$(DEPDIR)/imap_libcyrus_imap_la-message.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='imap/message.c' object='imap/imap_libcyrus_imap_la-message.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -c -o imap/imap_libcyrus_imap_la-message.lo `test -f 'imap/message.c' || echo '$(srcdir)/'`imap/message.c imap/imap_libcyrus_imap_la-mupdate-client.lo: imap/mupdate-client.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -MT imap/imap_libcyrus_imap_la-mupdate-client.lo -MD -MP -MF imap/$(DEPDIR)/imap_libcyrus_imap_la-mupdate-client.Tpo -c -o imap/imap_libcyrus_imap_la-mupdate-client.lo `test -f 'imap/mupdate-client.c' || echo '$(srcdir)/'`imap/mupdate-client.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) imap/$(DEPDIR)/imap_libcyrus_imap_la-mupdate-client.Tpo imap/$(DEPDIR)/imap_libcyrus_imap_la-mupdate-client.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='imap/mupdate-client.c' object='imap/imap_libcyrus_imap_la-mupdate-client.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -c -o imap/imap_libcyrus_imap_la-mupdate-client.lo `test -f 'imap/mupdate-client.c' || echo '$(srcdir)/'`imap/mupdate-client.c imap/imap_libcyrus_imap_la-notify.lo: imap/notify.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -MT imap/imap_libcyrus_imap_la-notify.lo -MD -MP -MF imap/$(DEPDIR)/imap_libcyrus_imap_la-notify.Tpo -c -o imap/imap_libcyrus_imap_la-notify.lo `test -f 'imap/notify.c' || echo '$(srcdir)/'`imap/notify.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) imap/$(DEPDIR)/imap_libcyrus_imap_la-notify.Tpo imap/$(DEPDIR)/imap_libcyrus_imap_la-notify.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='imap/notify.c' object='imap/imap_libcyrus_imap_la-notify.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -c -o imap/imap_libcyrus_imap_la-notify.lo `test -f 'imap/notify.c' || echo '$(srcdir)/'`imap/notify.c imap/imap_libcyrus_imap_la-partlist.lo: imap/partlist.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -MT imap/imap_libcyrus_imap_la-partlist.lo -MD -MP -MF imap/$(DEPDIR)/imap_libcyrus_imap_la-partlist.Tpo -c -o imap/imap_libcyrus_imap_la-partlist.lo `test -f 'imap/partlist.c' || echo '$(srcdir)/'`imap/partlist.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) imap/$(DEPDIR)/imap_libcyrus_imap_la-partlist.Tpo imap/$(DEPDIR)/imap_libcyrus_imap_la-partlist.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='imap/partlist.c' object='imap/imap_libcyrus_imap_la-partlist.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -c -o imap/imap_libcyrus_imap_la-partlist.lo `test -f 'imap/partlist.c' || echo '$(srcdir)/'`imap/partlist.c imap/imap_libcyrus_imap_la-proc.lo: imap/proc.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -MT imap/imap_libcyrus_imap_la-proc.lo -MD -MP -MF imap/$(DEPDIR)/imap_libcyrus_imap_la-proc.Tpo -c -o imap/imap_libcyrus_imap_la-proc.lo `test -f 'imap/proc.c' || echo '$(srcdir)/'`imap/proc.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) imap/$(DEPDIR)/imap_libcyrus_imap_la-proc.Tpo imap/$(DEPDIR)/imap_libcyrus_imap_la-proc.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='imap/proc.c' object='imap/imap_libcyrus_imap_la-proc.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -c -o imap/imap_libcyrus_imap_la-proc.lo `test -f 'imap/proc.c' || echo '$(srcdir)/'`imap/proc.c imap/imap_libcyrus_imap_la-quota_db.lo: imap/quota_db.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -MT imap/imap_libcyrus_imap_la-quota_db.lo -MD -MP -MF imap/$(DEPDIR)/imap_libcyrus_imap_la-quota_db.Tpo -c -o imap/imap_libcyrus_imap_la-quota_db.lo `test -f 'imap/quota_db.c' || echo '$(srcdir)/'`imap/quota_db.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) imap/$(DEPDIR)/imap_libcyrus_imap_la-quota_db.Tpo imap/$(DEPDIR)/imap_libcyrus_imap_la-quota_db.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='imap/quota_db.c' object='imap/imap_libcyrus_imap_la-quota_db.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -c -o imap/imap_libcyrus_imap_la-quota_db.lo `test -f 'imap/quota_db.c' || echo '$(srcdir)/'`imap/quota_db.c imap/imap_libcyrus_imap_la-rfc822_header.lo: imap/rfc822_header.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -MT imap/imap_libcyrus_imap_la-rfc822_header.lo -MD -MP -MF imap/$(DEPDIR)/imap_libcyrus_imap_la-rfc822_header.Tpo -c -o imap/imap_libcyrus_imap_la-rfc822_header.lo `test -f 'imap/rfc822_header.c' || echo '$(srcdir)/'`imap/rfc822_header.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) imap/$(DEPDIR)/imap_libcyrus_imap_la-rfc822_header.Tpo imap/$(DEPDIR)/imap_libcyrus_imap_la-rfc822_header.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='imap/rfc822_header.c' object='imap/imap_libcyrus_imap_la-rfc822_header.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -c -o imap/imap_libcyrus_imap_la-rfc822_header.lo `test -f 'imap/rfc822_header.c' || echo '$(srcdir)/'`imap/rfc822_header.c imap/imap_libcyrus_imap_la-saslclient.lo: imap/saslclient.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -MT imap/imap_libcyrus_imap_la-saslclient.lo -MD -MP -MF imap/$(DEPDIR)/imap_libcyrus_imap_la-saslclient.Tpo -c -o imap/imap_libcyrus_imap_la-saslclient.lo `test -f 'imap/saslclient.c' || echo '$(srcdir)/'`imap/saslclient.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) imap/$(DEPDIR)/imap_libcyrus_imap_la-saslclient.Tpo imap/$(DEPDIR)/imap_libcyrus_imap_la-saslclient.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='imap/saslclient.c' object='imap/imap_libcyrus_imap_la-saslclient.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -c -o imap/imap_libcyrus_imap_la-saslclient.lo `test -f 'imap/saslclient.c' || echo '$(srcdir)/'`imap/saslclient.c imap/imap_libcyrus_imap_la-saslserver.lo: imap/saslserver.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -MT imap/imap_libcyrus_imap_la-saslserver.lo -MD -MP -MF imap/$(DEPDIR)/imap_libcyrus_imap_la-saslserver.Tpo -c -o imap/imap_libcyrus_imap_la-saslserver.lo `test -f 'imap/saslserver.c' || echo '$(srcdir)/'`imap/saslserver.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) imap/$(DEPDIR)/imap_libcyrus_imap_la-saslserver.Tpo imap/$(DEPDIR)/imap_libcyrus_imap_la-saslserver.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='imap/saslserver.c' object='imap/imap_libcyrus_imap_la-saslserver.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -c -o imap/imap_libcyrus_imap_la-saslserver.lo `test -f 'imap/saslserver.c' || echo '$(srcdir)/'`imap/saslserver.c imap/imap_libcyrus_imap_la-search_engines.lo: imap/search_engines.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -MT imap/imap_libcyrus_imap_la-search_engines.lo -MD -MP -MF imap/$(DEPDIR)/imap_libcyrus_imap_la-search_engines.Tpo -c -o imap/imap_libcyrus_imap_la-search_engines.lo `test -f 'imap/search_engines.c' || echo '$(srcdir)/'`imap/search_engines.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) imap/$(DEPDIR)/imap_libcyrus_imap_la-search_engines.Tpo imap/$(DEPDIR)/imap_libcyrus_imap_la-search_engines.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='imap/search_engines.c' object='imap/imap_libcyrus_imap_la-search_engines.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -c -o imap/imap_libcyrus_imap_la-search_engines.lo `test -f 'imap/search_engines.c' || echo '$(srcdir)/'`imap/search_engines.c imap/imap_libcyrus_imap_la-seen_db.lo: imap/seen_db.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -MT imap/imap_libcyrus_imap_la-seen_db.lo -MD -MP -MF imap/$(DEPDIR)/imap_libcyrus_imap_la-seen_db.Tpo -c -o imap/imap_libcyrus_imap_la-seen_db.lo `test -f 'imap/seen_db.c' || echo '$(srcdir)/'`imap/seen_db.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) imap/$(DEPDIR)/imap_libcyrus_imap_la-seen_db.Tpo imap/$(DEPDIR)/imap_libcyrus_imap_la-seen_db.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='imap/seen_db.c' object='imap/imap_libcyrus_imap_la-seen_db.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -c -o imap/imap_libcyrus_imap_la-seen_db.lo `test -f 'imap/seen_db.c' || echo '$(srcdir)/'`imap/seen_db.c imap/imap_libcyrus_imap_la-sequence.lo: imap/sequence.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -MT imap/imap_libcyrus_imap_la-sequence.lo -MD -MP -MF imap/$(DEPDIR)/imap_libcyrus_imap_la-sequence.Tpo -c -o imap/imap_libcyrus_imap_la-sequence.lo `test -f 'imap/sequence.c' || echo '$(srcdir)/'`imap/sequence.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) imap/$(DEPDIR)/imap_libcyrus_imap_la-sequence.Tpo imap/$(DEPDIR)/imap_libcyrus_imap_la-sequence.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='imap/sequence.c' object='imap/imap_libcyrus_imap_la-sequence.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -c -o imap/imap_libcyrus_imap_la-sequence.lo `test -f 'imap/sequence.c' || echo '$(srcdir)/'`imap/sequence.c imap/imap_libcyrus_imap_la-setproctitle.lo: imap/setproctitle.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -MT imap/imap_libcyrus_imap_la-setproctitle.lo -MD -MP -MF imap/$(DEPDIR)/imap_libcyrus_imap_la-setproctitle.Tpo -c -o imap/imap_libcyrus_imap_la-setproctitle.lo `test -f 'imap/setproctitle.c' || echo '$(srcdir)/'`imap/setproctitle.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) imap/$(DEPDIR)/imap_libcyrus_imap_la-setproctitle.Tpo imap/$(DEPDIR)/imap_libcyrus_imap_la-setproctitle.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='imap/setproctitle.c' object='imap/imap_libcyrus_imap_la-setproctitle.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -c -o imap/imap_libcyrus_imap_la-setproctitle.lo `test -f 'imap/setproctitle.c' || echo '$(srcdir)/'`imap/setproctitle.c imap/imap_libcyrus_imap_la-squat.lo: imap/squat.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -MT imap/imap_libcyrus_imap_la-squat.lo -MD -MP -MF imap/$(DEPDIR)/imap_libcyrus_imap_la-squat.Tpo -c -o imap/imap_libcyrus_imap_la-squat.lo `test -f 'imap/squat.c' || echo '$(srcdir)/'`imap/squat.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) imap/$(DEPDIR)/imap_libcyrus_imap_la-squat.Tpo imap/$(DEPDIR)/imap_libcyrus_imap_la-squat.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='imap/squat.c' object='imap/imap_libcyrus_imap_la-squat.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -c -o imap/imap_libcyrus_imap_la-squat.lo `test -f 'imap/squat.c' || echo '$(srcdir)/'`imap/squat.c imap/imap_libcyrus_imap_la-squat_internal.lo: imap/squat_internal.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -MT imap/imap_libcyrus_imap_la-squat_internal.lo -MD -MP -MF imap/$(DEPDIR)/imap_libcyrus_imap_la-squat_internal.Tpo -c -o imap/imap_libcyrus_imap_la-squat_internal.lo `test -f 'imap/squat_internal.c' || echo '$(srcdir)/'`imap/squat_internal.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) imap/$(DEPDIR)/imap_libcyrus_imap_la-squat_internal.Tpo imap/$(DEPDIR)/imap_libcyrus_imap_la-squat_internal.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='imap/squat_internal.c' object='imap/imap_libcyrus_imap_la-squat_internal.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -c -o imap/imap_libcyrus_imap_la-squat_internal.lo `test -f 'imap/squat_internal.c' || echo '$(srcdir)/'`imap/squat_internal.c imap/imap_libcyrus_imap_la-statuscache_db.lo: imap/statuscache_db.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -MT imap/imap_libcyrus_imap_la-statuscache_db.lo -MD -MP -MF imap/$(DEPDIR)/imap_libcyrus_imap_la-statuscache_db.Tpo -c -o imap/imap_libcyrus_imap_la-statuscache_db.lo `test -f 'imap/statuscache_db.c' || echo '$(srcdir)/'`imap/statuscache_db.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) imap/$(DEPDIR)/imap_libcyrus_imap_la-statuscache_db.Tpo imap/$(DEPDIR)/imap_libcyrus_imap_la-statuscache_db.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='imap/statuscache_db.c' object='imap/imap_libcyrus_imap_la-statuscache_db.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -c -o imap/imap_libcyrus_imap_la-statuscache_db.lo `test -f 'imap/statuscache_db.c' || echo '$(srcdir)/'`imap/statuscache_db.c imap/imap_libcyrus_imap_la-sync_log.lo: imap/sync_log.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -MT imap/imap_libcyrus_imap_la-sync_log.lo -MD -MP -MF imap/$(DEPDIR)/imap_libcyrus_imap_la-sync_log.Tpo -c -o imap/imap_libcyrus_imap_la-sync_log.lo `test -f 'imap/sync_log.c' || echo '$(srcdir)/'`imap/sync_log.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) imap/$(DEPDIR)/imap_libcyrus_imap_la-sync_log.Tpo imap/$(DEPDIR)/imap_libcyrus_imap_la-sync_log.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='imap/sync_log.c' object='imap/imap_libcyrus_imap_la-sync_log.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -c -o imap/imap_libcyrus_imap_la-sync_log.lo `test -f 'imap/sync_log.c' || echo '$(srcdir)/'`imap/sync_log.c imap/imap_libcyrus_imap_la-telemetry.lo: imap/telemetry.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -MT imap/imap_libcyrus_imap_la-telemetry.lo -MD -MP -MF imap/$(DEPDIR)/imap_libcyrus_imap_la-telemetry.Tpo -c -o imap/imap_libcyrus_imap_la-telemetry.lo `test -f 'imap/telemetry.c' || echo '$(srcdir)/'`imap/telemetry.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) imap/$(DEPDIR)/imap_libcyrus_imap_la-telemetry.Tpo imap/$(DEPDIR)/imap_libcyrus_imap_la-telemetry.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='imap/telemetry.c' object='imap/imap_libcyrus_imap_la-telemetry.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -c -o imap/imap_libcyrus_imap_la-telemetry.lo `test -f 'imap/telemetry.c' || echo '$(srcdir)/'`imap/telemetry.c imap/imap_libcyrus_imap_la-tls.lo: imap/tls.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -MT imap/imap_libcyrus_imap_la-tls.lo -MD -MP -MF imap/$(DEPDIR)/imap_libcyrus_imap_la-tls.Tpo -c -o imap/imap_libcyrus_imap_la-tls.lo `test -f 'imap/tls.c' || echo '$(srcdir)/'`imap/tls.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) imap/$(DEPDIR)/imap_libcyrus_imap_la-tls.Tpo imap/$(DEPDIR)/imap_libcyrus_imap_la-tls.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='imap/tls.c' object='imap/imap_libcyrus_imap_la-tls.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -c -o imap/imap_libcyrus_imap_la-tls.lo `test -f 'imap/tls.c' || echo '$(srcdir)/'`imap/tls.c imap/imap_libcyrus_imap_la-tls_th-lock.lo: imap/tls_th-lock.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -MT imap/imap_libcyrus_imap_la-tls_th-lock.lo -MD -MP -MF imap/$(DEPDIR)/imap_libcyrus_imap_la-tls_th-lock.Tpo -c -o imap/imap_libcyrus_imap_la-tls_th-lock.lo `test -f 'imap/tls_th-lock.c' || echo '$(srcdir)/'`imap/tls_th-lock.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) imap/$(DEPDIR)/imap_libcyrus_imap_la-tls_th-lock.Tpo imap/$(DEPDIR)/imap_libcyrus_imap_la-tls_th-lock.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='imap/tls_th-lock.c' object='imap/imap_libcyrus_imap_la-tls_th-lock.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -c -o imap/imap_libcyrus_imap_la-tls_th-lock.lo `test -f 'imap/tls_th-lock.c' || echo '$(srcdir)/'`imap/tls_th-lock.c imap/imap_libcyrus_imap_la-user.lo: imap/user.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -MT imap/imap_libcyrus_imap_la-user.lo -MD -MP -MF imap/$(DEPDIR)/imap_libcyrus_imap_la-user.Tpo -c -o imap/imap_libcyrus_imap_la-user.lo `test -f 'imap/user.c' || echo '$(srcdir)/'`imap/user.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) imap/$(DEPDIR)/imap_libcyrus_imap_la-user.Tpo imap/$(DEPDIR)/imap_libcyrus_imap_la-user.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='imap/user.c' object='imap/imap_libcyrus_imap_la-user.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -c -o imap/imap_libcyrus_imap_la-user.lo `test -f 'imap/user.c' || echo '$(srcdir)/'`imap/user.c imap/imap_libcyrus_imap_la-userdeny_db.lo: imap/userdeny_db.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -MT imap/imap_libcyrus_imap_la-userdeny_db.lo -MD -MP -MF imap/$(DEPDIR)/imap_libcyrus_imap_la-userdeny_db.Tpo -c -o imap/imap_libcyrus_imap_la-userdeny_db.lo `test -f 'imap/userdeny_db.c' || echo '$(srcdir)/'`imap/userdeny_db.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) imap/$(DEPDIR)/imap_libcyrus_imap_la-userdeny_db.Tpo imap/$(DEPDIR)/imap_libcyrus_imap_la-userdeny_db.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='imap/userdeny_db.c' object='imap/imap_libcyrus_imap_la-userdeny_db.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -c -o imap/imap_libcyrus_imap_la-userdeny_db.lo `test -f 'imap/userdeny_db.c' || echo '$(srcdir)/'`imap/userdeny_db.c imap/imap_libcyrus_imap_la-version.lo: imap/version.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -MT imap/imap_libcyrus_imap_la-version.lo -MD -MP -MF imap/$(DEPDIR)/imap_libcyrus_imap_la-version.Tpo -c -o imap/imap_libcyrus_imap_la-version.lo `test -f 'imap/version.c' || echo '$(srcdir)/'`imap/version.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) imap/$(DEPDIR)/imap_libcyrus_imap_la-version.Tpo imap/$(DEPDIR)/imap_libcyrus_imap_la-version.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='imap/version.c' object='imap/imap_libcyrus_imap_la-version.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -c -o imap/imap_libcyrus_imap_la-version.lo `test -f 'imap/version.c' || echo '$(srcdir)/'`imap/version.c imap/imap_libcyrus_imap_la-caldav_db.lo: imap/caldav_db.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -MT imap/imap_libcyrus_imap_la-caldav_db.lo -MD -MP -MF imap/$(DEPDIR)/imap_libcyrus_imap_la-caldav_db.Tpo -c -o imap/imap_libcyrus_imap_la-caldav_db.lo `test -f 'imap/caldav_db.c' || echo '$(srcdir)/'`imap/caldav_db.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) imap/$(DEPDIR)/imap_libcyrus_imap_la-caldav_db.Tpo imap/$(DEPDIR)/imap_libcyrus_imap_la-caldav_db.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='imap/caldav_db.c' object='imap/imap_libcyrus_imap_la-caldav_db.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -c -o imap/imap_libcyrus_imap_la-caldav_db.lo `test -f 'imap/caldav_db.c' || echo '$(srcdir)/'`imap/caldav_db.c imap/imap_libcyrus_imap_la-carddav_db.lo: imap/carddav_db.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -MT imap/imap_libcyrus_imap_la-carddav_db.lo -MD -MP -MF imap/$(DEPDIR)/imap_libcyrus_imap_la-carddav_db.Tpo -c -o imap/imap_libcyrus_imap_la-carddav_db.lo `test -f 'imap/carddav_db.c' || echo '$(srcdir)/'`imap/carddav_db.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) imap/$(DEPDIR)/imap_libcyrus_imap_la-carddav_db.Tpo imap/$(DEPDIR)/imap_libcyrus_imap_la-carddav_db.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='imap/carddav_db.c' object='imap/imap_libcyrus_imap_la-carddav_db.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -c -o imap/imap_libcyrus_imap_la-carddav_db.lo `test -f 'imap/carddav_db.c' || echo '$(srcdir)/'`imap/carddav_db.c imap/imap_libcyrus_imap_la-dav_db.lo: imap/dav_db.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -MT imap/imap_libcyrus_imap_la-dav_db.lo -MD -MP -MF imap/$(DEPDIR)/imap_libcyrus_imap_la-dav_db.Tpo -c -o imap/imap_libcyrus_imap_la-dav_db.lo `test -f 'imap/dav_db.c' || echo '$(srcdir)/'`imap/dav_db.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) imap/$(DEPDIR)/imap_libcyrus_imap_la-dav_db.Tpo imap/$(DEPDIR)/imap_libcyrus_imap_la-dav_db.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='imap/dav_db.c' object='imap/imap_libcyrus_imap_la-dav_db.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -c -o imap/imap_libcyrus_imap_la-dav_db.lo `test -f 'imap/dav_db.c' || echo '$(srcdir)/'`imap/dav_db.c imap/imap_libcyrus_imap_la-dav_util.lo: imap/dav_util.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -MT imap/imap_libcyrus_imap_la-dav_util.lo -MD -MP -MF imap/$(DEPDIR)/imap_libcyrus_imap_la-dav_util.Tpo -c -o imap/imap_libcyrus_imap_la-dav_util.lo `test -f 'imap/dav_util.c' || echo '$(srcdir)/'`imap/dav_util.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) imap/$(DEPDIR)/imap_libcyrus_imap_la-dav_util.Tpo imap/$(DEPDIR)/imap_libcyrus_imap_la-dav_util.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='imap/dav_util.c' object='imap/imap_libcyrus_imap_la-dav_util.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -c -o imap/imap_libcyrus_imap_la-dav_util.lo `test -f 'imap/dav_util.c' || echo '$(srcdir)/'`imap/dav_util.c imap/imap_libcyrus_imap_la-http_caldav.lo: imap/http_caldav.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -MT imap/imap_libcyrus_imap_la-http_caldav.lo -MD -MP -MF imap/$(DEPDIR)/imap_libcyrus_imap_la-http_caldav.Tpo -c -o imap/imap_libcyrus_imap_la-http_caldav.lo `test -f 'imap/http_caldav.c' || echo '$(srcdir)/'`imap/http_caldav.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) imap/$(DEPDIR)/imap_libcyrus_imap_la-http_caldav.Tpo imap/$(DEPDIR)/imap_libcyrus_imap_la-http_caldav.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='imap/http_caldav.c' object='imap/imap_libcyrus_imap_la-http_caldav.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -c -o imap/imap_libcyrus_imap_la-http_caldav.lo `test -f 'imap/http_caldav.c' || echo '$(srcdir)/'`imap/http_caldav.c imap/imap_libcyrus_imap_la-http_carddav.lo: imap/http_carddav.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -MT imap/imap_libcyrus_imap_la-http_carddav.lo -MD -MP -MF imap/$(DEPDIR)/imap_libcyrus_imap_la-http_carddav.Tpo -c -o imap/imap_libcyrus_imap_la-http_carddav.lo `test -f 'imap/http_carddav.c' || echo '$(srcdir)/'`imap/http_carddav.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) imap/$(DEPDIR)/imap_libcyrus_imap_la-http_carddav.Tpo imap/$(DEPDIR)/imap_libcyrus_imap_la-http_carddav.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='imap/http_carddav.c' object='imap/imap_libcyrus_imap_la-http_carddav.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -c -o imap/imap_libcyrus_imap_la-http_carddav.lo `test -f 'imap/http_carddav.c' || echo '$(srcdir)/'`imap/http_carddav.c imap/imap_libcyrus_imap_la-http_client.lo: imap/http_client.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -MT imap/imap_libcyrus_imap_la-http_client.lo -MD -MP -MF imap/$(DEPDIR)/imap_libcyrus_imap_la-http_client.Tpo -c -o imap/imap_libcyrus_imap_la-http_client.lo `test -f 'imap/http_client.c' || echo '$(srcdir)/'`imap/http_client.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) imap/$(DEPDIR)/imap_libcyrus_imap_la-http_client.Tpo imap/$(DEPDIR)/imap_libcyrus_imap_la-http_client.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='imap/http_client.c' object='imap/imap_libcyrus_imap_la-http_client.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -c -o imap/imap_libcyrus_imap_la-http_client.lo `test -f 'imap/http_client.c' || echo '$(srcdir)/'`imap/http_client.c imap/imap_libcyrus_imap_la-http_dav.lo: imap/http_dav.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -MT imap/imap_libcyrus_imap_la-http_dav.lo -MD -MP -MF imap/$(DEPDIR)/imap_libcyrus_imap_la-http_dav.Tpo -c -o imap/imap_libcyrus_imap_la-http_dav.lo `test -f 'imap/http_dav.c' || echo '$(srcdir)/'`imap/http_dav.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) imap/$(DEPDIR)/imap_libcyrus_imap_la-http_dav.Tpo imap/$(DEPDIR)/imap_libcyrus_imap_la-http_dav.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='imap/http_dav.c' object='imap/imap_libcyrus_imap_la-http_dav.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -c -o imap/imap_libcyrus_imap_la-http_dav.lo `test -f 'imap/http_dav.c' || echo '$(srcdir)/'`imap/http_dav.c imap/imap_libcyrus_imap_la-http_dblookup.lo: imap/http_dblookup.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -MT imap/imap_libcyrus_imap_la-http_dblookup.lo -MD -MP -MF imap/$(DEPDIR)/imap_libcyrus_imap_la-http_dblookup.Tpo -c -o imap/imap_libcyrus_imap_la-http_dblookup.lo `test -f 'imap/http_dblookup.c' || echo '$(srcdir)/'`imap/http_dblookup.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) imap/$(DEPDIR)/imap_libcyrus_imap_la-http_dblookup.Tpo imap/$(DEPDIR)/imap_libcyrus_imap_la-http_dblookup.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='imap/http_dblookup.c' object='imap/imap_libcyrus_imap_la-http_dblookup.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -c -o imap/imap_libcyrus_imap_la-http_dblookup.lo `test -f 'imap/http_dblookup.c' || echo '$(srcdir)/'`imap/http_dblookup.c imap/imap_libcyrus_imap_la-http_ischedule.lo: imap/http_ischedule.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -MT imap/imap_libcyrus_imap_la-http_ischedule.lo -MD -MP -MF imap/$(DEPDIR)/imap_libcyrus_imap_la-http_ischedule.Tpo -c -o imap/imap_libcyrus_imap_la-http_ischedule.lo `test -f 'imap/http_ischedule.c' || echo '$(srcdir)/'`imap/http_ischedule.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) imap/$(DEPDIR)/imap_libcyrus_imap_la-http_ischedule.Tpo imap/$(DEPDIR)/imap_libcyrus_imap_la-http_ischedule.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='imap/http_ischedule.c' object='imap/imap_libcyrus_imap_la-http_ischedule.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -c -o imap/imap_libcyrus_imap_la-http_ischedule.lo `test -f 'imap/http_ischedule.c' || echo '$(srcdir)/'`imap/http_ischedule.c imap/imap_libcyrus_imap_la-http_proxy.lo: imap/http_proxy.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -MT imap/imap_libcyrus_imap_la-http_proxy.lo -MD -MP -MF imap/$(DEPDIR)/imap_libcyrus_imap_la-http_proxy.Tpo -c -o imap/imap_libcyrus_imap_la-http_proxy.lo `test -f 'imap/http_proxy.c' || echo '$(srcdir)/'`imap/http_proxy.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) imap/$(DEPDIR)/imap_libcyrus_imap_la-http_proxy.Tpo imap/$(DEPDIR)/imap_libcyrus_imap_la-http_proxy.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='imap/http_proxy.c' object='imap/imap_libcyrus_imap_la-http_proxy.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -c -o imap/imap_libcyrus_imap_la-http_proxy.lo `test -f 'imap/http_proxy.c' || echo '$(srcdir)/'`imap/http_proxy.c imap/imap_libcyrus_imap_la-http_rss.lo: imap/http_rss.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -MT imap/imap_libcyrus_imap_la-http_rss.lo -MD -MP -MF imap/$(DEPDIR)/imap_libcyrus_imap_la-http_rss.Tpo -c -o imap/imap_libcyrus_imap_la-http_rss.lo `test -f 'imap/http_rss.c' || echo '$(srcdir)/'`imap/http_rss.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) imap/$(DEPDIR)/imap_libcyrus_imap_la-http_rss.Tpo imap/$(DEPDIR)/imap_libcyrus_imap_la-http_rss.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='imap/http_rss.c' object='imap/imap_libcyrus_imap_la-http_rss.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -c -o imap/imap_libcyrus_imap_la-http_rss.lo `test -f 'imap/http_rss.c' || echo '$(srcdir)/'`imap/http_rss.c imap/imap_libcyrus_imap_la-http_timezone.lo: imap/http_timezone.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -MT imap/imap_libcyrus_imap_la-http_timezone.lo -MD -MP -MF imap/$(DEPDIR)/imap_libcyrus_imap_la-http_timezone.Tpo -c -o imap/imap_libcyrus_imap_la-http_timezone.lo `test -f 'imap/http_timezone.c' || echo '$(srcdir)/'`imap/http_timezone.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) imap/$(DEPDIR)/imap_libcyrus_imap_la-http_timezone.Tpo imap/$(DEPDIR)/imap_libcyrus_imap_la-http_timezone.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='imap/http_timezone.c' object='imap/imap_libcyrus_imap_la-http_timezone.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -c -o imap/imap_libcyrus_imap_la-http_timezone.lo `test -f 'imap/http_timezone.c' || echo '$(srcdir)/'`imap/http_timezone.c imap/imap_libcyrus_imap_la-httpd.lo: imap/httpd.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -MT imap/imap_libcyrus_imap_la-httpd.lo -MD -MP -MF imap/$(DEPDIR)/imap_libcyrus_imap_la-httpd.Tpo -c -o imap/imap_libcyrus_imap_la-httpd.lo `test -f 'imap/httpd.c' || echo '$(srcdir)/'`imap/httpd.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) imap/$(DEPDIR)/imap_libcyrus_imap_la-httpd.Tpo imap/$(DEPDIR)/imap_libcyrus_imap_la-httpd.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='imap/httpd.c' object='imap/imap_libcyrus_imap_la-httpd.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -c -o imap/imap_libcyrus_imap_la-httpd.lo `test -f 'imap/httpd.c' || echo '$(srcdir)/'`imap/httpd.c imap/imap_libcyrus_imap_la-jcal.lo: imap/jcal.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -MT imap/imap_libcyrus_imap_la-jcal.lo -MD -MP -MF imap/$(DEPDIR)/imap_libcyrus_imap_la-jcal.Tpo -c -o imap/imap_libcyrus_imap_la-jcal.lo `test -f 'imap/jcal.c' || echo '$(srcdir)/'`imap/jcal.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) imap/$(DEPDIR)/imap_libcyrus_imap_la-jcal.Tpo imap/$(DEPDIR)/imap_libcyrus_imap_la-jcal.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='imap/jcal.c' object='imap/imap_libcyrus_imap_la-jcal.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -c -o imap/imap_libcyrus_imap_la-jcal.lo `test -f 'imap/jcal.c' || echo '$(srcdir)/'`imap/jcal.c imap/imap_libcyrus_imap_la-proxy.lo: imap/proxy.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -MT imap/imap_libcyrus_imap_la-proxy.lo -MD -MP -MF imap/$(DEPDIR)/imap_libcyrus_imap_la-proxy.Tpo -c -o imap/imap_libcyrus_imap_la-proxy.lo `test -f 'imap/proxy.c' || echo '$(srcdir)/'`imap/proxy.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) imap/$(DEPDIR)/imap_libcyrus_imap_la-proxy.Tpo imap/$(DEPDIR)/imap_libcyrus_imap_la-proxy.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='imap/proxy.c' object='imap/imap_libcyrus_imap_la-proxy.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -c -o imap/imap_libcyrus_imap_la-proxy.lo `test -f 'imap/proxy.c' || echo '$(srcdir)/'`imap/proxy.c imap/imap_libcyrus_imap_la-smtpclient.lo: imap/smtpclient.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -MT imap/imap_libcyrus_imap_la-smtpclient.lo -MD -MP -MF imap/$(DEPDIR)/imap_libcyrus_imap_la-smtpclient.Tpo -c -o imap/imap_libcyrus_imap_la-smtpclient.lo `test -f 'imap/smtpclient.c' || echo '$(srcdir)/'`imap/smtpclient.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) imap/$(DEPDIR)/imap_libcyrus_imap_la-smtpclient.Tpo imap/$(DEPDIR)/imap_libcyrus_imap_la-smtpclient.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='imap/smtpclient.c' object='imap/imap_libcyrus_imap_la-smtpclient.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -c -o imap/imap_libcyrus_imap_la-smtpclient.lo `test -f 'imap/smtpclient.c' || echo '$(srcdir)/'`imap/smtpclient.c imap/imap_libcyrus_imap_la-spool.lo: imap/spool.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -MT imap/imap_libcyrus_imap_la-spool.lo -MD -MP -MF imap/$(DEPDIR)/imap_libcyrus_imap_la-spool.Tpo -c -o imap/imap_libcyrus_imap_la-spool.lo `test -f 'imap/spool.c' || echo '$(srcdir)/'`imap/spool.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) imap/$(DEPDIR)/imap_libcyrus_imap_la-spool.Tpo imap/$(DEPDIR)/imap_libcyrus_imap_la-spool.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='imap/spool.c' object='imap/imap_libcyrus_imap_la-spool.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -c -o imap/imap_libcyrus_imap_la-spool.lo `test -f 'imap/spool.c' || echo '$(srcdir)/'`imap/spool.c imap/imap_libcyrus_imap_la-xcal.lo: imap/xcal.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -MT imap/imap_libcyrus_imap_la-xcal.lo -MD -MP -MF imap/$(DEPDIR)/imap_libcyrus_imap_la-xcal.Tpo -c -o imap/imap_libcyrus_imap_la-xcal.lo `test -f 'imap/xcal.c' || echo '$(srcdir)/'`imap/xcal.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) imap/$(DEPDIR)/imap_libcyrus_imap_la-xcal.Tpo imap/$(DEPDIR)/imap_libcyrus_imap_la-xcal.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='imap/xcal.c' object='imap/imap_libcyrus_imap_la-xcal.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -c -o imap/imap_libcyrus_imap_la-xcal.lo `test -f 'imap/xcal.c' || echo '$(srcdir)/'`imap/xcal.c imap/imap_libcyrus_imap_la-zoneinfo_db.lo: imap/zoneinfo_db.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -MT imap/imap_libcyrus_imap_la-zoneinfo_db.lo -MD -MP -MF imap/$(DEPDIR)/imap_libcyrus_imap_la-zoneinfo_db.Tpo -c -o imap/imap_libcyrus_imap_la-zoneinfo_db.lo `test -f 'imap/zoneinfo_db.c' || echo '$(srcdir)/'`imap/zoneinfo_db.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) imap/$(DEPDIR)/imap_libcyrus_imap_la-zoneinfo_db.Tpo imap/$(DEPDIR)/imap_libcyrus_imap_la-zoneinfo_db.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='imap/zoneinfo_db.c' object='imap/imap_libcyrus_imap_la-zoneinfo_db.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -c -o imap/imap_libcyrus_imap_la-zoneinfo_db.lo `test -f 'imap/zoneinfo_db.c' || echo '$(srcdir)/'`imap/zoneinfo_db.c imap/imap_libcyrus_imap_la-imap_err.lo: imap/imap_err.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -MT imap/imap_libcyrus_imap_la-imap_err.lo -MD -MP -MF imap/$(DEPDIR)/imap_libcyrus_imap_la-imap_err.Tpo -c -o imap/imap_libcyrus_imap_la-imap_err.lo `test -f 'imap/imap_err.c' || echo '$(srcdir)/'`imap/imap_err.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) imap/$(DEPDIR)/imap_libcyrus_imap_la-imap_err.Tpo imap/$(DEPDIR)/imap_libcyrus_imap_la-imap_err.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='imap/imap_err.c' object='imap/imap_libcyrus_imap_la-imap_err.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -c -o imap/imap_libcyrus_imap_la-imap_err.lo `test -f 'imap/imap_err.c' || echo '$(srcdir)/'`imap/imap_err.c imap/imap_libcyrus_imap_la-mupdate_err.lo: imap/mupdate_err.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -MT imap/imap_libcyrus_imap_la-mupdate_err.lo -MD -MP -MF imap/$(DEPDIR)/imap_libcyrus_imap_la-mupdate_err.Tpo -c -o imap/imap_libcyrus_imap_la-mupdate_err.lo `test -f 'imap/mupdate_err.c' || echo '$(srcdir)/'`imap/mupdate_err.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) imap/$(DEPDIR)/imap_libcyrus_imap_la-mupdate_err.Tpo imap/$(DEPDIR)/imap_libcyrus_imap_la-mupdate_err.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='imap/mupdate_err.c' object='imap/imap_libcyrus_imap_la-mupdate_err.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -c -o imap/imap_libcyrus_imap_la-mupdate_err.lo `test -f 'imap/mupdate_err.c' || echo '$(srcdir)/'`imap/mupdate_err.c imap/imap_libcyrus_imap_la-http_err.lo: imap/http_err.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -MT imap/imap_libcyrus_imap_la-http_err.lo -MD -MP -MF imap/$(DEPDIR)/imap_libcyrus_imap_la-http_err.Tpo -c -o imap/imap_libcyrus_imap_la-http_err.lo `test -f 'imap/http_err.c' || echo '$(srcdir)/'`imap/http_err.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) imap/$(DEPDIR)/imap_libcyrus_imap_la-http_err.Tpo imap/$(DEPDIR)/imap_libcyrus_imap_la-http_err.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='imap/http_err.c' object='imap/imap_libcyrus_imap_la-http_err.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -c -o imap/imap_libcyrus_imap_la-http_err.lo `test -f 'imap/http_err.c' || echo '$(srcdir)/'`imap/http_err.c imap/imap_libcyrus_imap_la-tz_err.lo: imap/tz_err.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -MT imap/imap_libcyrus_imap_la-tz_err.lo -MD -MP -MF imap/$(DEPDIR)/imap_libcyrus_imap_la-tz_err.Tpo -c -o imap/imap_libcyrus_imap_la-tz_err.lo `test -f 'imap/tz_err.c' || echo '$(srcdir)/'`imap/tz_err.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) imap/$(DEPDIR)/imap_libcyrus_imap_la-tz_err.Tpo imap/$(DEPDIR)/imap_libcyrus_imap_la-tz_err.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='imap/tz_err.c' object='imap/imap_libcyrus_imap_la-tz_err.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imap_libcyrus_imap_la_CFLAGS) $(CFLAGS) -c -o imap/imap_libcyrus_imap_la-tz_err.lo `test -f 'imap/tz_err.c' || echo '$(srcdir)/'`imap/tz_err.c lib/lib_libcyrus_la-acl.lo: lib/acl.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_la_CFLAGS) $(CFLAGS) -MT lib/lib_libcyrus_la-acl.lo -MD -MP -MF lib/$(DEPDIR)/lib_libcyrus_la-acl.Tpo -c -o lib/lib_libcyrus_la-acl.lo `test -f 'lib/acl.c' || echo '$(srcdir)/'`lib/acl.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) lib/$(DEPDIR)/lib_libcyrus_la-acl.Tpo lib/$(DEPDIR)/lib_libcyrus_la-acl.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='lib/acl.c' object='lib/lib_libcyrus_la-acl.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_la_CFLAGS) $(CFLAGS) -c -o lib/lib_libcyrus_la-acl.lo `test -f 'lib/acl.c' || echo '$(srcdir)/'`lib/acl.c lib/lib_libcyrus_la-acl_afs.lo: lib/acl_afs.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_la_CFLAGS) $(CFLAGS) -MT lib/lib_libcyrus_la-acl_afs.lo -MD -MP -MF lib/$(DEPDIR)/lib_libcyrus_la-acl_afs.Tpo -c -o lib/lib_libcyrus_la-acl_afs.lo `test -f 'lib/acl_afs.c' || echo '$(srcdir)/'`lib/acl_afs.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) lib/$(DEPDIR)/lib_libcyrus_la-acl_afs.Tpo lib/$(DEPDIR)/lib_libcyrus_la-acl_afs.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='lib/acl_afs.c' object='lib/lib_libcyrus_la-acl_afs.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_la_CFLAGS) $(CFLAGS) -c -o lib/lib_libcyrus_la-acl_afs.lo `test -f 'lib/acl_afs.c' || echo '$(srcdir)/'`lib/acl_afs.c lib/lib_libcyrus_la-auth.lo: lib/auth.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_la_CFLAGS) $(CFLAGS) -MT lib/lib_libcyrus_la-auth.lo -MD -MP -MF lib/$(DEPDIR)/lib_libcyrus_la-auth.Tpo -c -o lib/lib_libcyrus_la-auth.lo `test -f 'lib/auth.c' || echo '$(srcdir)/'`lib/auth.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) lib/$(DEPDIR)/lib_libcyrus_la-auth.Tpo lib/$(DEPDIR)/lib_libcyrus_la-auth.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='lib/auth.c' object='lib/lib_libcyrus_la-auth.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_la_CFLAGS) $(CFLAGS) -c -o lib/lib_libcyrus_la-auth.lo `test -f 'lib/auth.c' || echo '$(srcdir)/'`lib/auth.c lib/lib_libcyrus_la-auth_krb.lo: lib/auth_krb.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_la_CFLAGS) $(CFLAGS) -MT lib/lib_libcyrus_la-auth_krb.lo -MD -MP -MF lib/$(DEPDIR)/lib_libcyrus_la-auth_krb.Tpo -c -o lib/lib_libcyrus_la-auth_krb.lo `test -f 'lib/auth_krb.c' || echo '$(srcdir)/'`lib/auth_krb.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) lib/$(DEPDIR)/lib_libcyrus_la-auth_krb.Tpo lib/$(DEPDIR)/lib_libcyrus_la-auth_krb.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='lib/auth_krb.c' object='lib/lib_libcyrus_la-auth_krb.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_la_CFLAGS) $(CFLAGS) -c -o lib/lib_libcyrus_la-auth_krb.lo `test -f 'lib/auth_krb.c' || echo '$(srcdir)/'`lib/auth_krb.c lib/lib_libcyrus_la-auth_krb5.lo: lib/auth_krb5.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_la_CFLAGS) $(CFLAGS) -MT lib/lib_libcyrus_la-auth_krb5.lo -MD -MP -MF lib/$(DEPDIR)/lib_libcyrus_la-auth_krb5.Tpo -c -o lib/lib_libcyrus_la-auth_krb5.lo `test -f 'lib/auth_krb5.c' || echo '$(srcdir)/'`lib/auth_krb5.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) lib/$(DEPDIR)/lib_libcyrus_la-auth_krb5.Tpo lib/$(DEPDIR)/lib_libcyrus_la-auth_krb5.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='lib/auth_krb5.c' object='lib/lib_libcyrus_la-auth_krb5.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_la_CFLAGS) $(CFLAGS) -c -o lib/lib_libcyrus_la-auth_krb5.lo `test -f 'lib/auth_krb5.c' || echo '$(srcdir)/'`lib/auth_krb5.c lib/lib_libcyrus_la-auth_pts.lo: lib/auth_pts.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_la_CFLAGS) $(CFLAGS) -MT lib/lib_libcyrus_la-auth_pts.lo -MD -MP -MF lib/$(DEPDIR)/lib_libcyrus_la-auth_pts.Tpo -c -o lib/lib_libcyrus_la-auth_pts.lo `test -f 'lib/auth_pts.c' || echo '$(srcdir)/'`lib/auth_pts.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) lib/$(DEPDIR)/lib_libcyrus_la-auth_pts.Tpo lib/$(DEPDIR)/lib_libcyrus_la-auth_pts.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='lib/auth_pts.c' object='lib/lib_libcyrus_la-auth_pts.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_la_CFLAGS) $(CFLAGS) -c -o lib/lib_libcyrus_la-auth_pts.lo `test -f 'lib/auth_pts.c' || echo '$(srcdir)/'`lib/auth_pts.c lib/lib_libcyrus_la-auth_unix.lo: lib/auth_unix.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_la_CFLAGS) $(CFLAGS) -MT lib/lib_libcyrus_la-auth_unix.lo -MD -MP -MF lib/$(DEPDIR)/lib_libcyrus_la-auth_unix.Tpo -c -o lib/lib_libcyrus_la-auth_unix.lo `test -f 'lib/auth_unix.c' || echo '$(srcdir)/'`lib/auth_unix.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) lib/$(DEPDIR)/lib_libcyrus_la-auth_unix.Tpo lib/$(DEPDIR)/lib_libcyrus_la-auth_unix.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='lib/auth_unix.c' object='lib/lib_libcyrus_la-auth_unix.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_la_CFLAGS) $(CFLAGS) -c -o lib/lib_libcyrus_la-auth_unix.lo `test -f 'lib/auth_unix.c' || echo '$(srcdir)/'`lib/auth_unix.c lib/lib_libcyrus_la-bitvector.lo: lib/bitvector.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_la_CFLAGS) $(CFLAGS) -MT lib/lib_libcyrus_la-bitvector.lo -MD -MP -MF lib/$(DEPDIR)/lib_libcyrus_la-bitvector.Tpo -c -o lib/lib_libcyrus_la-bitvector.lo `test -f 'lib/bitvector.c' || echo '$(srcdir)/'`lib/bitvector.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) lib/$(DEPDIR)/lib_libcyrus_la-bitvector.Tpo lib/$(DEPDIR)/lib_libcyrus_la-bitvector.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='lib/bitvector.c' object='lib/lib_libcyrus_la-bitvector.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_la_CFLAGS) $(CFLAGS) -c -o lib/lib_libcyrus_la-bitvector.lo `test -f 'lib/bitvector.c' || echo '$(srcdir)/'`lib/bitvector.c lib/lib_libcyrus_la-bsearch.lo: lib/bsearch.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_la_CFLAGS) $(CFLAGS) -MT lib/lib_libcyrus_la-bsearch.lo -MD -MP -MF lib/$(DEPDIR)/lib_libcyrus_la-bsearch.Tpo -c -o lib/lib_libcyrus_la-bsearch.lo `test -f 'lib/bsearch.c' || echo '$(srcdir)/'`lib/bsearch.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) lib/$(DEPDIR)/lib_libcyrus_la-bsearch.Tpo lib/$(DEPDIR)/lib_libcyrus_la-bsearch.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='lib/bsearch.c' object='lib/lib_libcyrus_la-bsearch.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_la_CFLAGS) $(CFLAGS) -c -o lib/lib_libcyrus_la-bsearch.lo `test -f 'lib/bsearch.c' || echo '$(srcdir)/'`lib/bsearch.c lib/lib_libcyrus_la-byteorder64.lo: lib/byteorder64.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_la_CFLAGS) $(CFLAGS) -MT lib/lib_libcyrus_la-byteorder64.lo -MD -MP -MF lib/$(DEPDIR)/lib_libcyrus_la-byteorder64.Tpo -c -o lib/lib_libcyrus_la-byteorder64.lo `test -f 'lib/byteorder64.c' || echo '$(srcdir)/'`lib/byteorder64.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) lib/$(DEPDIR)/lib_libcyrus_la-byteorder64.Tpo lib/$(DEPDIR)/lib_libcyrus_la-byteorder64.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='lib/byteorder64.c' object='lib/lib_libcyrus_la-byteorder64.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_la_CFLAGS) $(CFLAGS) -c -o lib/lib_libcyrus_la-byteorder64.lo `test -f 'lib/byteorder64.c' || echo '$(srcdir)/'`lib/byteorder64.c lib/lib_libcyrus_la-charset.lo: lib/charset.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_la_CFLAGS) $(CFLAGS) -MT lib/lib_libcyrus_la-charset.lo -MD -MP -MF lib/$(DEPDIR)/lib_libcyrus_la-charset.Tpo -c -o lib/lib_libcyrus_la-charset.lo `test -f 'lib/charset.c' || echo '$(srcdir)/'`lib/charset.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) lib/$(DEPDIR)/lib_libcyrus_la-charset.Tpo lib/$(DEPDIR)/lib_libcyrus_la-charset.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='lib/charset.c' object='lib/lib_libcyrus_la-charset.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_la_CFLAGS) $(CFLAGS) -c -o lib/lib_libcyrus_la-charset.lo `test -f 'lib/charset.c' || echo '$(srcdir)/'`lib/charset.c lib/lib_libcyrus_la-command.lo: lib/command.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_la_CFLAGS) $(CFLAGS) -MT lib/lib_libcyrus_la-command.lo -MD -MP -MF lib/$(DEPDIR)/lib_libcyrus_la-command.Tpo -c -o lib/lib_libcyrus_la-command.lo `test -f 'lib/command.c' || echo '$(srcdir)/'`lib/command.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) lib/$(DEPDIR)/lib_libcyrus_la-command.Tpo lib/$(DEPDIR)/lib_libcyrus_la-command.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='lib/command.c' object='lib/lib_libcyrus_la-command.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_la_CFLAGS) $(CFLAGS) -c -o lib/lib_libcyrus_la-command.lo `test -f 'lib/command.c' || echo '$(srcdir)/'`lib/command.c lib/lib_libcyrus_la-crc32.lo: lib/crc32.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_la_CFLAGS) $(CFLAGS) -MT lib/lib_libcyrus_la-crc32.lo -MD -MP -MF lib/$(DEPDIR)/lib_libcyrus_la-crc32.Tpo -c -o lib/lib_libcyrus_la-crc32.lo `test -f 'lib/crc32.c' || echo '$(srcdir)/'`lib/crc32.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) lib/$(DEPDIR)/lib_libcyrus_la-crc32.Tpo lib/$(DEPDIR)/lib_libcyrus_la-crc32.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='lib/crc32.c' object='lib/lib_libcyrus_la-crc32.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_la_CFLAGS) $(CFLAGS) -c -o lib/lib_libcyrus_la-crc32.lo `test -f 'lib/crc32.c' || echo '$(srcdir)/'`lib/crc32.c lib/lib_libcyrus_la-cyrusdb.lo: lib/cyrusdb.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_la_CFLAGS) $(CFLAGS) -MT lib/lib_libcyrus_la-cyrusdb.lo -MD -MP -MF lib/$(DEPDIR)/lib_libcyrus_la-cyrusdb.Tpo -c -o lib/lib_libcyrus_la-cyrusdb.lo `test -f 'lib/cyrusdb.c' || echo '$(srcdir)/'`lib/cyrusdb.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) lib/$(DEPDIR)/lib_libcyrus_la-cyrusdb.Tpo lib/$(DEPDIR)/lib_libcyrus_la-cyrusdb.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='lib/cyrusdb.c' object='lib/lib_libcyrus_la-cyrusdb.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_la_CFLAGS) $(CFLAGS) -c -o lib/lib_libcyrus_la-cyrusdb.lo `test -f 'lib/cyrusdb.c' || echo '$(srcdir)/'`lib/cyrusdb.c lib/lib_libcyrus_la-cyrusdb_flat.lo: lib/cyrusdb_flat.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_la_CFLAGS) $(CFLAGS) -MT lib/lib_libcyrus_la-cyrusdb_flat.lo -MD -MP -MF lib/$(DEPDIR)/lib_libcyrus_la-cyrusdb_flat.Tpo -c -o lib/lib_libcyrus_la-cyrusdb_flat.lo `test -f 'lib/cyrusdb_flat.c' || echo '$(srcdir)/'`lib/cyrusdb_flat.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) lib/$(DEPDIR)/lib_libcyrus_la-cyrusdb_flat.Tpo lib/$(DEPDIR)/lib_libcyrus_la-cyrusdb_flat.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='lib/cyrusdb_flat.c' object='lib/lib_libcyrus_la-cyrusdb_flat.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_la_CFLAGS) $(CFLAGS) -c -o lib/lib_libcyrus_la-cyrusdb_flat.lo `test -f 'lib/cyrusdb_flat.c' || echo '$(srcdir)/'`lib/cyrusdb_flat.c lib/lib_libcyrus_la-cyrusdb_quotalegacy.lo: lib/cyrusdb_quotalegacy.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_la_CFLAGS) $(CFLAGS) -MT lib/lib_libcyrus_la-cyrusdb_quotalegacy.lo -MD -MP -MF lib/$(DEPDIR)/lib_libcyrus_la-cyrusdb_quotalegacy.Tpo -c -o lib/lib_libcyrus_la-cyrusdb_quotalegacy.lo `test -f 'lib/cyrusdb_quotalegacy.c' || echo '$(srcdir)/'`lib/cyrusdb_quotalegacy.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) lib/$(DEPDIR)/lib_libcyrus_la-cyrusdb_quotalegacy.Tpo lib/$(DEPDIR)/lib_libcyrus_la-cyrusdb_quotalegacy.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='lib/cyrusdb_quotalegacy.c' object='lib/lib_libcyrus_la-cyrusdb_quotalegacy.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_la_CFLAGS) $(CFLAGS) -c -o lib/lib_libcyrus_la-cyrusdb_quotalegacy.lo `test -f 'lib/cyrusdb_quotalegacy.c' || echo '$(srcdir)/'`lib/cyrusdb_quotalegacy.c lib/lib_libcyrus_la-cyrusdb_skiplist.lo: lib/cyrusdb_skiplist.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_la_CFLAGS) $(CFLAGS) -MT lib/lib_libcyrus_la-cyrusdb_skiplist.lo -MD -MP -MF lib/$(DEPDIR)/lib_libcyrus_la-cyrusdb_skiplist.Tpo -c -o lib/lib_libcyrus_la-cyrusdb_skiplist.lo `test -f 'lib/cyrusdb_skiplist.c' || echo '$(srcdir)/'`lib/cyrusdb_skiplist.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) lib/$(DEPDIR)/lib_libcyrus_la-cyrusdb_skiplist.Tpo lib/$(DEPDIR)/lib_libcyrus_la-cyrusdb_skiplist.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='lib/cyrusdb_skiplist.c' object='lib/lib_libcyrus_la-cyrusdb_skiplist.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_la_CFLAGS) $(CFLAGS) -c -o lib/lib_libcyrus_la-cyrusdb_skiplist.lo `test -f 'lib/cyrusdb_skiplist.c' || echo '$(srcdir)/'`lib/cyrusdb_skiplist.c lib/lib_libcyrus_la-cyrusdb_twoskip.lo: lib/cyrusdb_twoskip.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_la_CFLAGS) $(CFLAGS) -MT lib/lib_libcyrus_la-cyrusdb_twoskip.lo -MD -MP -MF lib/$(DEPDIR)/lib_libcyrus_la-cyrusdb_twoskip.Tpo -c -o lib/lib_libcyrus_la-cyrusdb_twoskip.lo `test -f 'lib/cyrusdb_twoskip.c' || echo '$(srcdir)/'`lib/cyrusdb_twoskip.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) lib/$(DEPDIR)/lib_libcyrus_la-cyrusdb_twoskip.Tpo lib/$(DEPDIR)/lib_libcyrus_la-cyrusdb_twoskip.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='lib/cyrusdb_twoskip.c' object='lib/lib_libcyrus_la-cyrusdb_twoskip.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_la_CFLAGS) $(CFLAGS) -c -o lib/lib_libcyrus_la-cyrusdb_twoskip.lo `test -f 'lib/cyrusdb_twoskip.c' || echo '$(srcdir)/'`lib/cyrusdb_twoskip.c lib/lib_libcyrus_la-glob.lo: lib/glob.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_la_CFLAGS) $(CFLAGS) -MT lib/lib_libcyrus_la-glob.lo -MD -MP -MF lib/$(DEPDIR)/lib_libcyrus_la-glob.Tpo -c -o lib/lib_libcyrus_la-glob.lo `test -f 'lib/glob.c' || echo '$(srcdir)/'`lib/glob.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) lib/$(DEPDIR)/lib_libcyrus_la-glob.Tpo lib/$(DEPDIR)/lib_libcyrus_la-glob.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='lib/glob.c' object='lib/lib_libcyrus_la-glob.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_la_CFLAGS) $(CFLAGS) -c -o lib/lib_libcyrus_la-glob.lo `test -f 'lib/glob.c' || echo '$(srcdir)/'`lib/glob.c lib/lib_libcyrus_la-imapurl.lo: lib/imapurl.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_la_CFLAGS) $(CFLAGS) -MT lib/lib_libcyrus_la-imapurl.lo -MD -MP -MF lib/$(DEPDIR)/lib_libcyrus_la-imapurl.Tpo -c -o lib/lib_libcyrus_la-imapurl.lo `test -f 'lib/imapurl.c' || echo '$(srcdir)/'`lib/imapurl.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) lib/$(DEPDIR)/lib_libcyrus_la-imapurl.Tpo lib/$(DEPDIR)/lib_libcyrus_la-imapurl.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='lib/imapurl.c' object='lib/lib_libcyrus_la-imapurl.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_la_CFLAGS) $(CFLAGS) -c -o lib/lib_libcyrus_la-imapurl.lo `test -f 'lib/imapurl.c' || echo '$(srcdir)/'`lib/imapurl.c lib/lib_libcyrus_la-imclient.lo: lib/imclient.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_la_CFLAGS) $(CFLAGS) -MT lib/lib_libcyrus_la-imclient.lo -MD -MP -MF lib/$(DEPDIR)/lib_libcyrus_la-imclient.Tpo -c -o lib/lib_libcyrus_la-imclient.lo `test -f 'lib/imclient.c' || echo '$(srcdir)/'`lib/imclient.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) lib/$(DEPDIR)/lib_libcyrus_la-imclient.Tpo lib/$(DEPDIR)/lib_libcyrus_la-imclient.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='lib/imclient.c' object='lib/lib_libcyrus_la-imclient.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_la_CFLAGS) $(CFLAGS) -c -o lib/lib_libcyrus_la-imclient.lo `test -f 'lib/imclient.c' || echo '$(srcdir)/'`lib/imclient.c lib/lib_libcyrus_la-imparse.lo: lib/imparse.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_la_CFLAGS) $(CFLAGS) -MT lib/lib_libcyrus_la-imparse.lo -MD -MP -MF lib/$(DEPDIR)/lib_libcyrus_la-imparse.Tpo -c -o lib/lib_libcyrus_la-imparse.lo `test -f 'lib/imparse.c' || echo '$(srcdir)/'`lib/imparse.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) lib/$(DEPDIR)/lib_libcyrus_la-imparse.Tpo lib/$(DEPDIR)/lib_libcyrus_la-imparse.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='lib/imparse.c' object='lib/lib_libcyrus_la-imparse.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_la_CFLAGS) $(CFLAGS) -c -o lib/lib_libcyrus_la-imparse.lo `test -f 'lib/imparse.c' || echo '$(srcdir)/'`lib/imparse.c lib/lib_libcyrus_la-iostat.lo: lib/iostat.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_la_CFLAGS) $(CFLAGS) -MT lib/lib_libcyrus_la-iostat.lo -MD -MP -MF lib/$(DEPDIR)/lib_libcyrus_la-iostat.Tpo -c -o lib/lib_libcyrus_la-iostat.lo `test -f 'lib/iostat.c' || echo '$(srcdir)/'`lib/iostat.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) lib/$(DEPDIR)/lib_libcyrus_la-iostat.Tpo lib/$(DEPDIR)/lib_libcyrus_la-iostat.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='lib/iostat.c' object='lib/lib_libcyrus_la-iostat.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_la_CFLAGS) $(CFLAGS) -c -o lib/lib_libcyrus_la-iostat.lo `test -f 'lib/iostat.c' || echo '$(srcdir)/'`lib/iostat.c lib/lib_libcyrus_la-iptostring.lo: lib/iptostring.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_la_CFLAGS) $(CFLAGS) -MT lib/lib_libcyrus_la-iptostring.lo -MD -MP -MF lib/$(DEPDIR)/lib_libcyrus_la-iptostring.Tpo -c -o lib/lib_libcyrus_la-iptostring.lo `test -f 'lib/iptostring.c' || echo '$(srcdir)/'`lib/iptostring.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) lib/$(DEPDIR)/lib_libcyrus_la-iptostring.Tpo lib/$(DEPDIR)/lib_libcyrus_la-iptostring.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='lib/iptostring.c' object='lib/lib_libcyrus_la-iptostring.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_la_CFLAGS) $(CFLAGS) -c -o lib/lib_libcyrus_la-iptostring.lo `test -f 'lib/iptostring.c' || echo '$(srcdir)/'`lib/iptostring.c lib/lib_libcyrus_la-libcyr_cfg.lo: lib/libcyr_cfg.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_la_CFLAGS) $(CFLAGS) -MT lib/lib_libcyrus_la-libcyr_cfg.lo -MD -MP -MF lib/$(DEPDIR)/lib_libcyrus_la-libcyr_cfg.Tpo -c -o lib/lib_libcyrus_la-libcyr_cfg.lo `test -f 'lib/libcyr_cfg.c' || echo '$(srcdir)/'`lib/libcyr_cfg.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) lib/$(DEPDIR)/lib_libcyrus_la-libcyr_cfg.Tpo lib/$(DEPDIR)/lib_libcyrus_la-libcyr_cfg.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='lib/libcyr_cfg.c' object='lib/lib_libcyrus_la-libcyr_cfg.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_la_CFLAGS) $(CFLAGS) -c -o lib/lib_libcyrus_la-libcyr_cfg.lo `test -f 'lib/libcyr_cfg.c' || echo '$(srcdir)/'`lib/libcyr_cfg.c lib/lib_libcyrus_la-lsort.lo: lib/lsort.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_la_CFLAGS) $(CFLAGS) -MT lib/lib_libcyrus_la-lsort.lo -MD -MP -MF lib/$(DEPDIR)/lib_libcyrus_la-lsort.Tpo -c -o lib/lib_libcyrus_la-lsort.lo `test -f 'lib/lsort.c' || echo '$(srcdir)/'`lib/lsort.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) lib/$(DEPDIR)/lib_libcyrus_la-lsort.Tpo lib/$(DEPDIR)/lib_libcyrus_la-lsort.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='lib/lsort.c' object='lib/lib_libcyrus_la-lsort.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_la_CFLAGS) $(CFLAGS) -c -o lib/lib_libcyrus_la-lsort.lo `test -f 'lib/lsort.c' || echo '$(srcdir)/'`lib/lsort.c lib/lib_libcyrus_la-mappedfile.lo: lib/mappedfile.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_la_CFLAGS) $(CFLAGS) -MT lib/lib_libcyrus_la-mappedfile.lo -MD -MP -MF lib/$(DEPDIR)/lib_libcyrus_la-mappedfile.Tpo -c -o lib/lib_libcyrus_la-mappedfile.lo `test -f 'lib/mappedfile.c' || echo '$(srcdir)/'`lib/mappedfile.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) lib/$(DEPDIR)/lib_libcyrus_la-mappedfile.Tpo lib/$(DEPDIR)/lib_libcyrus_la-mappedfile.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='lib/mappedfile.c' object='lib/lib_libcyrus_la-mappedfile.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_la_CFLAGS) $(CFLAGS) -c -o lib/lib_libcyrus_la-mappedfile.lo `test -f 'lib/mappedfile.c' || echo '$(srcdir)/'`lib/mappedfile.c lib/lib_libcyrus_la-mkgmtime.lo: lib/mkgmtime.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_la_CFLAGS) $(CFLAGS) -MT lib/lib_libcyrus_la-mkgmtime.lo -MD -MP -MF lib/$(DEPDIR)/lib_libcyrus_la-mkgmtime.Tpo -c -o lib/lib_libcyrus_la-mkgmtime.lo `test -f 'lib/mkgmtime.c' || echo '$(srcdir)/'`lib/mkgmtime.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) lib/$(DEPDIR)/lib_libcyrus_la-mkgmtime.Tpo lib/$(DEPDIR)/lib_libcyrus_la-mkgmtime.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='lib/mkgmtime.c' object='lib/lib_libcyrus_la-mkgmtime.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_la_CFLAGS) $(CFLAGS) -c -o lib/lib_libcyrus_la-mkgmtime.lo `test -f 'lib/mkgmtime.c' || echo '$(srcdir)/'`lib/mkgmtime.c lib/lib_libcyrus_la-parseaddr.lo: lib/parseaddr.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_la_CFLAGS) $(CFLAGS) -MT lib/lib_libcyrus_la-parseaddr.lo -MD -MP -MF lib/$(DEPDIR)/lib_libcyrus_la-parseaddr.Tpo -c -o lib/lib_libcyrus_la-parseaddr.lo `test -f 'lib/parseaddr.c' || echo '$(srcdir)/'`lib/parseaddr.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) lib/$(DEPDIR)/lib_libcyrus_la-parseaddr.Tpo lib/$(DEPDIR)/lib_libcyrus_la-parseaddr.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='lib/parseaddr.c' object='lib/lib_libcyrus_la-parseaddr.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_la_CFLAGS) $(CFLAGS) -c -o lib/lib_libcyrus_la-parseaddr.lo `test -f 'lib/parseaddr.c' || echo '$(srcdir)/'`lib/parseaddr.c lib/lib_libcyrus_la-prot.lo: lib/prot.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_la_CFLAGS) $(CFLAGS) -MT lib/lib_libcyrus_la-prot.lo -MD -MP -MF lib/$(DEPDIR)/lib_libcyrus_la-prot.Tpo -c -o lib/lib_libcyrus_la-prot.lo `test -f 'lib/prot.c' || echo '$(srcdir)/'`lib/prot.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) lib/$(DEPDIR)/lib_libcyrus_la-prot.Tpo lib/$(DEPDIR)/lib_libcyrus_la-prot.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='lib/prot.c' object='lib/lib_libcyrus_la-prot.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_la_CFLAGS) $(CFLAGS) -c -o lib/lib_libcyrus_la-prot.lo `test -f 'lib/prot.c' || echo '$(srcdir)/'`lib/prot.c lib/lib_libcyrus_la-ptrarray.lo: lib/ptrarray.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_la_CFLAGS) $(CFLAGS) -MT lib/lib_libcyrus_la-ptrarray.lo -MD -MP -MF lib/$(DEPDIR)/lib_libcyrus_la-ptrarray.Tpo -c -o lib/lib_libcyrus_la-ptrarray.lo `test -f 'lib/ptrarray.c' || echo '$(srcdir)/'`lib/ptrarray.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) lib/$(DEPDIR)/lib_libcyrus_la-ptrarray.Tpo lib/$(DEPDIR)/lib_libcyrus_la-ptrarray.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='lib/ptrarray.c' object='lib/lib_libcyrus_la-ptrarray.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_la_CFLAGS) $(CFLAGS) -c -o lib/lib_libcyrus_la-ptrarray.lo `test -f 'lib/ptrarray.c' || echo '$(srcdir)/'`lib/ptrarray.c lib/lib_libcyrus_la-rfc822tok.lo: lib/rfc822tok.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_la_CFLAGS) $(CFLAGS) -MT lib/lib_libcyrus_la-rfc822tok.lo -MD -MP -MF lib/$(DEPDIR)/lib_libcyrus_la-rfc822tok.Tpo -c -o lib/lib_libcyrus_la-rfc822tok.lo `test -f 'lib/rfc822tok.c' || echo '$(srcdir)/'`lib/rfc822tok.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) lib/$(DEPDIR)/lib_libcyrus_la-rfc822tok.Tpo lib/$(DEPDIR)/lib_libcyrus_la-rfc822tok.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='lib/rfc822tok.c' object='lib/lib_libcyrus_la-rfc822tok.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_la_CFLAGS) $(CFLAGS) -c -o lib/lib_libcyrus_la-rfc822tok.lo `test -f 'lib/rfc822tok.c' || echo '$(srcdir)/'`lib/rfc822tok.c lib/lib_libcyrus_la-signals.lo: lib/signals.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_la_CFLAGS) $(CFLAGS) -MT lib/lib_libcyrus_la-signals.lo -MD -MP -MF lib/$(DEPDIR)/lib_libcyrus_la-signals.Tpo -c -o lib/lib_libcyrus_la-signals.lo `test -f 'lib/signals.c' || echo '$(srcdir)/'`lib/signals.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) lib/$(DEPDIR)/lib_libcyrus_la-signals.Tpo lib/$(DEPDIR)/lib_libcyrus_la-signals.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='lib/signals.c' object='lib/lib_libcyrus_la-signals.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_la_CFLAGS) $(CFLAGS) -c -o lib/lib_libcyrus_la-signals.lo `test -f 'lib/signals.c' || echo '$(srcdir)/'`lib/signals.c lib/lib_libcyrus_la-stristr.lo: lib/stristr.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_la_CFLAGS) $(CFLAGS) -MT lib/lib_libcyrus_la-stristr.lo -MD -MP -MF lib/$(DEPDIR)/lib_libcyrus_la-stristr.Tpo -c -o lib/lib_libcyrus_la-stristr.lo `test -f 'lib/stristr.c' || echo '$(srcdir)/'`lib/stristr.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) lib/$(DEPDIR)/lib_libcyrus_la-stristr.Tpo lib/$(DEPDIR)/lib_libcyrus_la-stristr.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='lib/stristr.c' object='lib/lib_libcyrus_la-stristr.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_la_CFLAGS) $(CFLAGS) -c -o lib/lib_libcyrus_la-stristr.lo `test -f 'lib/stristr.c' || echo '$(srcdir)/'`lib/stristr.c lib/lib_libcyrus_la-times.lo: lib/times.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_la_CFLAGS) $(CFLAGS) -MT lib/lib_libcyrus_la-times.lo -MD -MP -MF lib/$(DEPDIR)/lib_libcyrus_la-times.Tpo -c -o lib/lib_libcyrus_la-times.lo `test -f 'lib/times.c' || echo '$(srcdir)/'`lib/times.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) lib/$(DEPDIR)/lib_libcyrus_la-times.Tpo lib/$(DEPDIR)/lib_libcyrus_la-times.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='lib/times.c' object='lib/lib_libcyrus_la-times.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_la_CFLAGS) $(CFLAGS) -c -o lib/lib_libcyrus_la-times.lo `test -f 'lib/times.c' || echo '$(srcdir)/'`lib/times.c lib/lib_libcyrus_la-tok.lo: lib/tok.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_la_CFLAGS) $(CFLAGS) -MT lib/lib_libcyrus_la-tok.lo -MD -MP -MF lib/$(DEPDIR)/lib_libcyrus_la-tok.Tpo -c -o lib/lib_libcyrus_la-tok.lo `test -f 'lib/tok.c' || echo '$(srcdir)/'`lib/tok.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) lib/$(DEPDIR)/lib_libcyrus_la-tok.Tpo lib/$(DEPDIR)/lib_libcyrus_la-tok.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='lib/tok.c' object='lib/lib_libcyrus_la-tok.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_la_CFLAGS) $(CFLAGS) -c -o lib/lib_libcyrus_la-tok.lo `test -f 'lib/tok.c' || echo '$(srcdir)/'`lib/tok.c lib/lib_libcyrus_la-wildmat.lo: lib/wildmat.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_la_CFLAGS) $(CFLAGS) -MT lib/lib_libcyrus_la-wildmat.lo -MD -MP -MF lib/$(DEPDIR)/lib_libcyrus_la-wildmat.Tpo -c -o lib/lib_libcyrus_la-wildmat.lo `test -f 'lib/wildmat.c' || echo '$(srcdir)/'`lib/wildmat.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) lib/$(DEPDIR)/lib_libcyrus_la-wildmat.Tpo lib/$(DEPDIR)/lib_libcyrus_la-wildmat.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='lib/wildmat.c' object='lib/lib_libcyrus_la-wildmat.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_la_CFLAGS) $(CFLAGS) -c -o lib/lib_libcyrus_la-wildmat.lo `test -f 'lib/wildmat.c' || echo '$(srcdir)/'`lib/wildmat.c lib/lib_libcyrus_la-cyrusdb_berkeley.lo: lib/cyrusdb_berkeley.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_la_CFLAGS) $(CFLAGS) -MT lib/lib_libcyrus_la-cyrusdb_berkeley.lo -MD -MP -MF lib/$(DEPDIR)/lib_libcyrus_la-cyrusdb_berkeley.Tpo -c -o lib/lib_libcyrus_la-cyrusdb_berkeley.lo `test -f 'lib/cyrusdb_berkeley.c' || echo '$(srcdir)/'`lib/cyrusdb_berkeley.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) lib/$(DEPDIR)/lib_libcyrus_la-cyrusdb_berkeley.Tpo lib/$(DEPDIR)/lib_libcyrus_la-cyrusdb_berkeley.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='lib/cyrusdb_berkeley.c' object='lib/lib_libcyrus_la-cyrusdb_berkeley.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_la_CFLAGS) $(CFLAGS) -c -o lib/lib_libcyrus_la-cyrusdb_berkeley.lo `test -f 'lib/cyrusdb_berkeley.c' || echo '$(srcdir)/'`lib/cyrusdb_berkeley.c lib/lib_libcyrus_la-cyrusdb_sql.lo: lib/cyrusdb_sql.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_la_CFLAGS) $(CFLAGS) -MT lib/lib_libcyrus_la-cyrusdb_sql.lo -MD -MP -MF lib/$(DEPDIR)/lib_libcyrus_la-cyrusdb_sql.Tpo -c -o lib/lib_libcyrus_la-cyrusdb_sql.lo `test -f 'lib/cyrusdb_sql.c' || echo '$(srcdir)/'`lib/cyrusdb_sql.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) lib/$(DEPDIR)/lib_libcyrus_la-cyrusdb_sql.Tpo lib/$(DEPDIR)/lib_libcyrus_la-cyrusdb_sql.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='lib/cyrusdb_sql.c' object='lib/lib_libcyrus_la-cyrusdb_sql.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_la_CFLAGS) $(CFLAGS) -c -o lib/lib_libcyrus_la-cyrusdb_sql.lo `test -f 'lib/cyrusdb_sql.c' || echo '$(srcdir)/'`lib/cyrusdb_sql.c lib/lib_libcyrus_la-gmtoff_tm.lo: lib/gmtoff_tm.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_la_CFLAGS) $(CFLAGS) -MT lib/lib_libcyrus_la-gmtoff_tm.lo -MD -MP -MF lib/$(DEPDIR)/lib_libcyrus_la-gmtoff_tm.Tpo -c -o lib/lib_libcyrus_la-gmtoff_tm.lo `test -f 'lib/gmtoff_tm.c' || echo '$(srcdir)/'`lib/gmtoff_tm.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) lib/$(DEPDIR)/lib_libcyrus_la-gmtoff_tm.Tpo lib/$(DEPDIR)/lib_libcyrus_la-gmtoff_tm.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='lib/gmtoff_tm.c' object='lib/lib_libcyrus_la-gmtoff_tm.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_la_CFLAGS) $(CFLAGS) -c -o lib/lib_libcyrus_la-gmtoff_tm.lo `test -f 'lib/gmtoff_tm.c' || echo '$(srcdir)/'`lib/gmtoff_tm.c lib/lib_libcyrus_la-gmtoff_gmtime.lo: lib/gmtoff_gmtime.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_la_CFLAGS) $(CFLAGS) -MT lib/lib_libcyrus_la-gmtoff_gmtime.lo -MD -MP -MF lib/$(DEPDIR)/lib_libcyrus_la-gmtoff_gmtime.Tpo -c -o lib/lib_libcyrus_la-gmtoff_gmtime.lo `test -f 'lib/gmtoff_gmtime.c' || echo '$(srcdir)/'`lib/gmtoff_gmtime.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) lib/$(DEPDIR)/lib_libcyrus_la-gmtoff_gmtime.Tpo lib/$(DEPDIR)/lib_libcyrus_la-gmtoff_gmtime.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='lib/gmtoff_gmtime.c' object='lib/lib_libcyrus_la-gmtoff_gmtime.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_la_CFLAGS) $(CFLAGS) -c -o lib/lib_libcyrus_la-gmtoff_gmtime.lo `test -f 'lib/gmtoff_gmtime.c' || echo '$(srcdir)/'`lib/gmtoff_gmtime.c lib/lib_libcyrus_la-nonblock_fcntl.lo: lib/nonblock_fcntl.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_la_CFLAGS) $(CFLAGS) -MT lib/lib_libcyrus_la-nonblock_fcntl.lo -MD -MP -MF lib/$(DEPDIR)/lib_libcyrus_la-nonblock_fcntl.Tpo -c -o lib/lib_libcyrus_la-nonblock_fcntl.lo `test -f 'lib/nonblock_fcntl.c' || echo '$(srcdir)/'`lib/nonblock_fcntl.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) lib/$(DEPDIR)/lib_libcyrus_la-nonblock_fcntl.Tpo lib/$(DEPDIR)/lib_libcyrus_la-nonblock_fcntl.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='lib/nonblock_fcntl.c' object='lib/lib_libcyrus_la-nonblock_fcntl.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_la_CFLAGS) $(CFLAGS) -c -o lib/lib_libcyrus_la-nonblock_fcntl.lo `test -f 'lib/nonblock_fcntl.c' || echo '$(srcdir)/'`lib/nonblock_fcntl.c lib/lib_libcyrus_la-nonblock_ioctl.lo: lib/nonblock_ioctl.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_la_CFLAGS) $(CFLAGS) -MT lib/lib_libcyrus_la-nonblock_ioctl.lo -MD -MP -MF lib/$(DEPDIR)/lib_libcyrus_la-nonblock_ioctl.Tpo -c -o lib/lib_libcyrus_la-nonblock_ioctl.lo `test -f 'lib/nonblock_ioctl.c' || echo '$(srcdir)/'`lib/nonblock_ioctl.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) lib/$(DEPDIR)/lib_libcyrus_la-nonblock_ioctl.Tpo lib/$(DEPDIR)/lib_libcyrus_la-nonblock_ioctl.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='lib/nonblock_ioctl.c' object='lib/lib_libcyrus_la-nonblock_ioctl.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_la_CFLAGS) $(CFLAGS) -c -o lib/lib_libcyrus_la-nonblock_ioctl.lo `test -f 'lib/nonblock_ioctl.c' || echo '$(srcdir)/'`lib/nonblock_ioctl.c lib/lib_libcyrus_la-chartable.lo: lib/chartable.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_la_CFLAGS) $(CFLAGS) -MT lib/lib_libcyrus_la-chartable.lo -MD -MP -MF lib/$(DEPDIR)/lib_libcyrus_la-chartable.Tpo -c -o lib/lib_libcyrus_la-chartable.lo `test -f 'lib/chartable.c' || echo '$(srcdir)/'`lib/chartable.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) lib/$(DEPDIR)/lib_libcyrus_la-chartable.Tpo lib/$(DEPDIR)/lib_libcyrus_la-chartable.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='lib/chartable.c' object='lib/lib_libcyrus_la-chartable.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_la_CFLAGS) $(CFLAGS) -c -o lib/lib_libcyrus_la-chartable.lo `test -f 'lib/chartable.c' || echo '$(srcdir)/'`lib/chartable.c lib/lib_libcyrus_min_la-arrayu64.lo: lib/arrayu64.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_min_la_CFLAGS) $(CFLAGS) -MT lib/lib_libcyrus_min_la-arrayu64.lo -MD -MP -MF lib/$(DEPDIR)/lib_libcyrus_min_la-arrayu64.Tpo -c -o lib/lib_libcyrus_min_la-arrayu64.lo `test -f 'lib/arrayu64.c' || echo '$(srcdir)/'`lib/arrayu64.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) lib/$(DEPDIR)/lib_libcyrus_min_la-arrayu64.Tpo lib/$(DEPDIR)/lib_libcyrus_min_la-arrayu64.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='lib/arrayu64.c' object='lib/lib_libcyrus_min_la-arrayu64.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_min_la_CFLAGS) $(CFLAGS) -c -o lib/lib_libcyrus_min_la-arrayu64.lo `test -f 'lib/arrayu64.c' || echo '$(srcdir)/'`lib/arrayu64.c lib/lib_libcyrus_min_la-assert.lo: lib/assert.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_min_la_CFLAGS) $(CFLAGS) -MT lib/lib_libcyrus_min_la-assert.lo -MD -MP -MF lib/$(DEPDIR)/lib_libcyrus_min_la-assert.Tpo -c -o lib/lib_libcyrus_min_la-assert.lo `test -f 'lib/assert.c' || echo '$(srcdir)/'`lib/assert.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) lib/$(DEPDIR)/lib_libcyrus_min_la-assert.Tpo lib/$(DEPDIR)/lib_libcyrus_min_la-assert.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='lib/assert.c' object='lib/lib_libcyrus_min_la-assert.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_min_la_CFLAGS) $(CFLAGS) -c -o lib/lib_libcyrus_min_la-assert.lo `test -f 'lib/assert.c' || echo '$(srcdir)/'`lib/assert.c lib/lib_libcyrus_min_la-hash.lo: lib/hash.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_min_la_CFLAGS) $(CFLAGS) -MT lib/lib_libcyrus_min_la-hash.lo -MD -MP -MF lib/$(DEPDIR)/lib_libcyrus_min_la-hash.Tpo -c -o lib/lib_libcyrus_min_la-hash.lo `test -f 'lib/hash.c' || echo '$(srcdir)/'`lib/hash.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) lib/$(DEPDIR)/lib_libcyrus_min_la-hash.Tpo lib/$(DEPDIR)/lib_libcyrus_min_la-hash.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='lib/hash.c' object='lib/lib_libcyrus_min_la-hash.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_min_la_CFLAGS) $(CFLAGS) -c -o lib/lib_libcyrus_min_la-hash.lo `test -f 'lib/hash.c' || echo '$(srcdir)/'`lib/hash.c lib/lib_libcyrus_min_la-hashu64.lo: lib/hashu64.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_min_la_CFLAGS) $(CFLAGS) -MT lib/lib_libcyrus_min_la-hashu64.lo -MD -MP -MF lib/$(DEPDIR)/lib_libcyrus_min_la-hashu64.Tpo -c -o lib/lib_libcyrus_min_la-hashu64.lo `test -f 'lib/hashu64.c' || echo '$(srcdir)/'`lib/hashu64.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) lib/$(DEPDIR)/lib_libcyrus_min_la-hashu64.Tpo lib/$(DEPDIR)/lib_libcyrus_min_la-hashu64.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='lib/hashu64.c' object='lib/lib_libcyrus_min_la-hashu64.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_min_la_CFLAGS) $(CFLAGS) -c -o lib/lib_libcyrus_min_la-hashu64.lo `test -f 'lib/hashu64.c' || echo '$(srcdir)/'`lib/hashu64.c lib/lib_libcyrus_min_la-libconfig.lo: lib/libconfig.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_min_la_CFLAGS) $(CFLAGS) -MT lib/lib_libcyrus_min_la-libconfig.lo -MD -MP -MF lib/$(DEPDIR)/lib_libcyrus_min_la-libconfig.Tpo -c -o lib/lib_libcyrus_min_la-libconfig.lo `test -f 'lib/libconfig.c' || echo '$(srcdir)/'`lib/libconfig.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) lib/$(DEPDIR)/lib_libcyrus_min_la-libconfig.Tpo lib/$(DEPDIR)/lib_libcyrus_min_la-libconfig.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='lib/libconfig.c' object='lib/lib_libcyrus_min_la-libconfig.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_min_la_CFLAGS) $(CFLAGS) -c -o lib/lib_libcyrus_min_la-libconfig.lo `test -f 'lib/libconfig.c' || echo '$(srcdir)/'`lib/libconfig.c lib/lib_libcyrus_min_la-mpool.lo: lib/mpool.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_min_la_CFLAGS) $(CFLAGS) -MT lib/lib_libcyrus_min_la-mpool.lo -MD -MP -MF lib/$(DEPDIR)/lib_libcyrus_min_la-mpool.Tpo -c -o lib/lib_libcyrus_min_la-mpool.lo `test -f 'lib/mpool.c' || echo '$(srcdir)/'`lib/mpool.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) lib/$(DEPDIR)/lib_libcyrus_min_la-mpool.Tpo lib/$(DEPDIR)/lib_libcyrus_min_la-mpool.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='lib/mpool.c' object='lib/lib_libcyrus_min_la-mpool.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_min_la_CFLAGS) $(CFLAGS) -c -o lib/lib_libcyrus_min_la-mpool.lo `test -f 'lib/mpool.c' || echo '$(srcdir)/'`lib/mpool.c lib/lib_libcyrus_min_la-retry.lo: lib/retry.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_min_la_CFLAGS) $(CFLAGS) -MT lib/lib_libcyrus_min_la-retry.lo -MD -MP -MF lib/$(DEPDIR)/lib_libcyrus_min_la-retry.Tpo -c -o lib/lib_libcyrus_min_la-retry.lo `test -f 'lib/retry.c' || echo '$(srcdir)/'`lib/retry.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) lib/$(DEPDIR)/lib_libcyrus_min_la-retry.Tpo lib/$(DEPDIR)/lib_libcyrus_min_la-retry.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='lib/retry.c' object='lib/lib_libcyrus_min_la-retry.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_min_la_CFLAGS) $(CFLAGS) -c -o lib/lib_libcyrus_min_la-retry.lo `test -f 'lib/retry.c' || echo '$(srcdir)/'`lib/retry.c lib/lib_libcyrus_min_la-strarray.lo: lib/strarray.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_min_la_CFLAGS) $(CFLAGS) -MT lib/lib_libcyrus_min_la-strarray.lo -MD -MP -MF lib/$(DEPDIR)/lib_libcyrus_min_la-strarray.Tpo -c -o lib/lib_libcyrus_min_la-strarray.lo `test -f 'lib/strarray.c' || echo '$(srcdir)/'`lib/strarray.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) lib/$(DEPDIR)/lib_libcyrus_min_la-strarray.Tpo lib/$(DEPDIR)/lib_libcyrus_min_la-strarray.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='lib/strarray.c' object='lib/lib_libcyrus_min_la-strarray.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_min_la_CFLAGS) $(CFLAGS) -c -o lib/lib_libcyrus_min_la-strarray.lo `test -f 'lib/strarray.c' || echo '$(srcdir)/'`lib/strarray.c lib/lib_libcyrus_min_la-strhash.lo: lib/strhash.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_min_la_CFLAGS) $(CFLAGS) -MT lib/lib_libcyrus_min_la-strhash.lo -MD -MP -MF lib/$(DEPDIR)/lib_libcyrus_min_la-strhash.Tpo -c -o lib/lib_libcyrus_min_la-strhash.lo `test -f 'lib/strhash.c' || echo '$(srcdir)/'`lib/strhash.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) lib/$(DEPDIR)/lib_libcyrus_min_la-strhash.Tpo lib/$(DEPDIR)/lib_libcyrus_min_la-strhash.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='lib/strhash.c' object='lib/lib_libcyrus_min_la-strhash.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_min_la_CFLAGS) $(CFLAGS) -c -o lib/lib_libcyrus_min_la-strhash.lo `test -f 'lib/strhash.c' || echo '$(srcdir)/'`lib/strhash.c lib/lib_libcyrus_min_la-util.lo: lib/util.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_min_la_CFLAGS) $(CFLAGS) -MT lib/lib_libcyrus_min_la-util.lo -MD -MP -MF lib/$(DEPDIR)/lib_libcyrus_min_la-util.Tpo -c -o lib/lib_libcyrus_min_la-util.lo `test -f 'lib/util.c' || echo '$(srcdir)/'`lib/util.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) lib/$(DEPDIR)/lib_libcyrus_min_la-util.Tpo lib/$(DEPDIR)/lib_libcyrus_min_la-util.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='lib/util.c' object='lib/lib_libcyrus_min_la-util.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_min_la_CFLAGS) $(CFLAGS) -c -o lib/lib_libcyrus_min_la-util.lo `test -f 'lib/util.c' || echo '$(srcdir)/'`lib/util.c lib/lib_libcyrus_min_la-vparse.lo: lib/vparse.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_min_la_CFLAGS) $(CFLAGS) -MT lib/lib_libcyrus_min_la-vparse.lo -MD -MP -MF lib/$(DEPDIR)/lib_libcyrus_min_la-vparse.Tpo -c -o lib/lib_libcyrus_min_la-vparse.lo `test -f 'lib/vparse.c' || echo '$(srcdir)/'`lib/vparse.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) lib/$(DEPDIR)/lib_libcyrus_min_la-vparse.Tpo lib/$(DEPDIR)/lib_libcyrus_min_la-vparse.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='lib/vparse.c' object='lib/lib_libcyrus_min_la-vparse.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_min_la_CFLAGS) $(CFLAGS) -c -o lib/lib_libcyrus_min_la-vparse.lo `test -f 'lib/vparse.c' || echo '$(srcdir)/'`lib/vparse.c lib/lib_libcyrus_min_la-xmalloc.lo: lib/xmalloc.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_min_la_CFLAGS) $(CFLAGS) -MT lib/lib_libcyrus_min_la-xmalloc.lo -MD -MP -MF lib/$(DEPDIR)/lib_libcyrus_min_la-xmalloc.Tpo -c -o lib/lib_libcyrus_min_la-xmalloc.lo `test -f 'lib/xmalloc.c' || echo '$(srcdir)/'`lib/xmalloc.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) lib/$(DEPDIR)/lib_libcyrus_min_la-xmalloc.Tpo lib/$(DEPDIR)/lib_libcyrus_min_la-xmalloc.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='lib/xmalloc.c' object='lib/lib_libcyrus_min_la-xmalloc.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_min_la_CFLAGS) $(CFLAGS) -c -o lib/lib_libcyrus_min_la-xmalloc.lo `test -f 'lib/xmalloc.c' || echo '$(srcdir)/'`lib/xmalloc.c lib/lib_libcyrus_min_la-xstrlcat.lo: lib/xstrlcat.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_min_la_CFLAGS) $(CFLAGS) -MT lib/lib_libcyrus_min_la-xstrlcat.lo -MD -MP -MF lib/$(DEPDIR)/lib_libcyrus_min_la-xstrlcat.Tpo -c -o lib/lib_libcyrus_min_la-xstrlcat.lo `test -f 'lib/xstrlcat.c' || echo '$(srcdir)/'`lib/xstrlcat.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) lib/$(DEPDIR)/lib_libcyrus_min_la-xstrlcat.Tpo lib/$(DEPDIR)/lib_libcyrus_min_la-xstrlcat.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='lib/xstrlcat.c' object='lib/lib_libcyrus_min_la-xstrlcat.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_min_la_CFLAGS) $(CFLAGS) -c -o lib/lib_libcyrus_min_la-xstrlcat.lo `test -f 'lib/xstrlcat.c' || echo '$(srcdir)/'`lib/xstrlcat.c lib/lib_libcyrus_min_la-xstrlcpy.lo: lib/xstrlcpy.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_min_la_CFLAGS) $(CFLAGS) -MT lib/lib_libcyrus_min_la-xstrlcpy.lo -MD -MP -MF lib/$(DEPDIR)/lib_libcyrus_min_la-xstrlcpy.Tpo -c -o lib/lib_libcyrus_min_la-xstrlcpy.lo `test -f 'lib/xstrlcpy.c' || echo '$(srcdir)/'`lib/xstrlcpy.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) lib/$(DEPDIR)/lib_libcyrus_min_la-xstrlcpy.Tpo lib/$(DEPDIR)/lib_libcyrus_min_la-xstrlcpy.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='lib/xstrlcpy.c' object='lib/lib_libcyrus_min_la-xstrlcpy.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_min_la_CFLAGS) $(CFLAGS) -c -o lib/lib_libcyrus_min_la-xstrlcpy.lo `test -f 'lib/xstrlcpy.c' || echo '$(srcdir)/'`lib/xstrlcpy.c lib/lib_libcyrus_min_la-getaddrinfo.lo: lib/getaddrinfo.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_min_la_CFLAGS) $(CFLAGS) -MT lib/lib_libcyrus_min_la-getaddrinfo.lo -MD -MP -MF lib/$(DEPDIR)/lib_libcyrus_min_la-getaddrinfo.Tpo -c -o lib/lib_libcyrus_min_la-getaddrinfo.lo `test -f 'lib/getaddrinfo.c' || echo '$(srcdir)/'`lib/getaddrinfo.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) lib/$(DEPDIR)/lib_libcyrus_min_la-getaddrinfo.Tpo lib/$(DEPDIR)/lib_libcyrus_min_la-getaddrinfo.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='lib/getaddrinfo.c' object='lib/lib_libcyrus_min_la-getaddrinfo.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_min_la_CFLAGS) $(CFLAGS) -c -o lib/lib_libcyrus_min_la-getaddrinfo.lo `test -f 'lib/getaddrinfo.c' || echo '$(srcdir)/'`lib/getaddrinfo.c lib/lib_libcyrus_min_la-getnameinfo.lo: lib/getnameinfo.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_min_la_CFLAGS) $(CFLAGS) -MT lib/lib_libcyrus_min_la-getnameinfo.lo -MD -MP -MF lib/$(DEPDIR)/lib_libcyrus_min_la-getnameinfo.Tpo -c -o lib/lib_libcyrus_min_la-getnameinfo.lo `test -f 'lib/getnameinfo.c' || echo '$(srcdir)/'`lib/getnameinfo.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) lib/$(DEPDIR)/lib_libcyrus_min_la-getnameinfo.Tpo lib/$(DEPDIR)/lib_libcyrus_min_la-getnameinfo.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='lib/getnameinfo.c' object='lib/lib_libcyrus_min_la-getnameinfo.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_min_la_CFLAGS) $(CFLAGS) -c -o lib/lib_libcyrus_min_la-getnameinfo.lo `test -f 'lib/getnameinfo.c' || echo '$(srcdir)/'`lib/getnameinfo.c lib/lib_libcyrus_min_la-lock_fcntl.lo: lib/lock_fcntl.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_min_la_CFLAGS) $(CFLAGS) -MT lib/lib_libcyrus_min_la-lock_fcntl.lo -MD -MP -MF lib/$(DEPDIR)/lib_libcyrus_min_la-lock_fcntl.Tpo -c -o lib/lib_libcyrus_min_la-lock_fcntl.lo `test -f 'lib/lock_fcntl.c' || echo '$(srcdir)/'`lib/lock_fcntl.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) lib/$(DEPDIR)/lib_libcyrus_min_la-lock_fcntl.Tpo lib/$(DEPDIR)/lib_libcyrus_min_la-lock_fcntl.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='lib/lock_fcntl.c' object='lib/lib_libcyrus_min_la-lock_fcntl.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_min_la_CFLAGS) $(CFLAGS) -c -o lib/lib_libcyrus_min_la-lock_fcntl.lo `test -f 'lib/lock_fcntl.c' || echo '$(srcdir)/'`lib/lock_fcntl.c lib/lib_libcyrus_min_la-lock_flock.lo: lib/lock_flock.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_min_la_CFLAGS) $(CFLAGS) -MT lib/lib_libcyrus_min_la-lock_flock.lo -MD -MP -MF lib/$(DEPDIR)/lib_libcyrus_min_la-lock_flock.Tpo -c -o lib/lib_libcyrus_min_la-lock_flock.lo `test -f 'lib/lock_flock.c' || echo '$(srcdir)/'`lib/lock_flock.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) lib/$(DEPDIR)/lib_libcyrus_min_la-lock_flock.Tpo lib/$(DEPDIR)/lib_libcyrus_min_la-lock_flock.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='lib/lock_flock.c' object='lib/lib_libcyrus_min_la-lock_flock.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_min_la_CFLAGS) $(CFLAGS) -c -o lib/lib_libcyrus_min_la-lock_flock.lo `test -f 'lib/lock_flock.c' || echo '$(srcdir)/'`lib/lock_flock.c lib/lib_libcyrus_min_la-map_shared.lo: lib/map_shared.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_min_la_CFLAGS) $(CFLAGS) -MT lib/lib_libcyrus_min_la-map_shared.lo -MD -MP -MF lib/$(DEPDIR)/lib_libcyrus_min_la-map_shared.Tpo -c -o lib/lib_libcyrus_min_la-map_shared.lo `test -f 'lib/map_shared.c' || echo '$(srcdir)/'`lib/map_shared.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) lib/$(DEPDIR)/lib_libcyrus_min_la-map_shared.Tpo lib/$(DEPDIR)/lib_libcyrus_min_la-map_shared.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='lib/map_shared.c' object='lib/lib_libcyrus_min_la-map_shared.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_min_la_CFLAGS) $(CFLAGS) -c -o lib/lib_libcyrus_min_la-map_shared.lo `test -f 'lib/map_shared.c' || echo '$(srcdir)/'`lib/map_shared.c lib/lib_libcyrus_min_la-map_stupidshared.lo: lib/map_stupidshared.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_min_la_CFLAGS) $(CFLAGS) -MT lib/lib_libcyrus_min_la-map_stupidshared.lo -MD -MP -MF lib/$(DEPDIR)/lib_libcyrus_min_la-map_stupidshared.Tpo -c -o lib/lib_libcyrus_min_la-map_stupidshared.lo `test -f 'lib/map_stupidshared.c' || echo '$(srcdir)/'`lib/map_stupidshared.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) lib/$(DEPDIR)/lib_libcyrus_min_la-map_stupidshared.Tpo lib/$(DEPDIR)/lib_libcyrus_min_la-map_stupidshared.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='lib/map_stupidshared.c' object='lib/lib_libcyrus_min_la-map_stupidshared.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_min_la_CFLAGS) $(CFLAGS) -c -o lib/lib_libcyrus_min_la-map_stupidshared.lo `test -f 'lib/map_stupidshared.c' || echo '$(srcdir)/'`lib/map_stupidshared.c lib/lib_libcyrus_min_la-map_nommap.lo: lib/map_nommap.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_min_la_CFLAGS) $(CFLAGS) -MT lib/lib_libcyrus_min_la-map_nommap.lo -MD -MP -MF lib/$(DEPDIR)/lib_libcyrus_min_la-map_nommap.Tpo -c -o lib/lib_libcyrus_min_la-map_nommap.lo `test -f 'lib/map_nommap.c' || echo '$(srcdir)/'`lib/map_nommap.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) lib/$(DEPDIR)/lib_libcyrus_min_la-map_nommap.Tpo lib/$(DEPDIR)/lib_libcyrus_min_la-map_nommap.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='lib/map_nommap.c' object='lib/lib_libcyrus_min_la-map_nommap.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_min_la_CFLAGS) $(CFLAGS) -c -o lib/lib_libcyrus_min_la-map_nommap.lo `test -f 'lib/map_nommap.c' || echo '$(srcdir)/'`lib/map_nommap.c lib/lib_libcyrus_min_la-imapopts.lo: lib/imapopts.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_min_la_CFLAGS) $(CFLAGS) -MT lib/lib_libcyrus_min_la-imapopts.lo -MD -MP -MF lib/$(DEPDIR)/lib_libcyrus_min_la-imapopts.Tpo -c -o lib/lib_libcyrus_min_la-imapopts.lo `test -f 'lib/imapopts.c' || echo '$(srcdir)/'`lib/imapopts.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) lib/$(DEPDIR)/lib_libcyrus_min_la-imapopts.Tpo lib/$(DEPDIR)/lib_libcyrus_min_la-imapopts.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='lib/imapopts.c' object='lib/lib_libcyrus_min_la-imapopts.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(lib_libcyrus_min_la_CFLAGS) $(CFLAGS) -c -o lib/lib_libcyrus_min_la-imapopts.lo `test -f 'lib/imapopts.c' || echo '$(srcdir)/'`lib/imapopts.c sieve/sieve_libcyrus_sieve_la-addr.lo: sieve/addr.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(sieve_libcyrus_sieve_la_CFLAGS) $(CFLAGS) -MT sieve/sieve_libcyrus_sieve_la-addr.lo -MD -MP -MF sieve/$(DEPDIR)/sieve_libcyrus_sieve_la-addr.Tpo -c -o sieve/sieve_libcyrus_sieve_la-addr.lo `test -f 'sieve/addr.c' || echo '$(srcdir)/'`sieve/addr.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) sieve/$(DEPDIR)/sieve_libcyrus_sieve_la-addr.Tpo sieve/$(DEPDIR)/sieve_libcyrus_sieve_la-addr.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='sieve/addr.c' object='sieve/sieve_libcyrus_sieve_la-addr.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(sieve_libcyrus_sieve_la_CFLAGS) $(CFLAGS) -c -o sieve/sieve_libcyrus_sieve_la-addr.lo `test -f 'sieve/addr.c' || echo '$(srcdir)/'`sieve/addr.c sieve/sieve_libcyrus_sieve_la-bc_dump.lo: sieve/bc_dump.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(sieve_libcyrus_sieve_la_CFLAGS) $(CFLAGS) -MT sieve/sieve_libcyrus_sieve_la-bc_dump.lo -MD -MP -MF sieve/$(DEPDIR)/sieve_libcyrus_sieve_la-bc_dump.Tpo -c -o sieve/sieve_libcyrus_sieve_la-bc_dump.lo `test -f 'sieve/bc_dump.c' || echo '$(srcdir)/'`sieve/bc_dump.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) sieve/$(DEPDIR)/sieve_libcyrus_sieve_la-bc_dump.Tpo sieve/$(DEPDIR)/sieve_libcyrus_sieve_la-bc_dump.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='sieve/bc_dump.c' object='sieve/sieve_libcyrus_sieve_la-bc_dump.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(sieve_libcyrus_sieve_la_CFLAGS) $(CFLAGS) -c -o sieve/sieve_libcyrus_sieve_la-bc_dump.lo `test -f 'sieve/bc_dump.c' || echo '$(srcdir)/'`sieve/bc_dump.c sieve/sieve_libcyrus_sieve_la-bc_emit.lo: sieve/bc_emit.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(sieve_libcyrus_sieve_la_CFLAGS) $(CFLAGS) -MT sieve/sieve_libcyrus_sieve_la-bc_emit.lo -MD -MP -MF sieve/$(DEPDIR)/sieve_libcyrus_sieve_la-bc_emit.Tpo -c -o sieve/sieve_libcyrus_sieve_la-bc_emit.lo `test -f 'sieve/bc_emit.c' || echo '$(srcdir)/'`sieve/bc_emit.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) sieve/$(DEPDIR)/sieve_libcyrus_sieve_la-bc_emit.Tpo sieve/$(DEPDIR)/sieve_libcyrus_sieve_la-bc_emit.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='sieve/bc_emit.c' object='sieve/sieve_libcyrus_sieve_la-bc_emit.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(sieve_libcyrus_sieve_la_CFLAGS) $(CFLAGS) -c -o sieve/sieve_libcyrus_sieve_la-bc_emit.lo `test -f 'sieve/bc_emit.c' || echo '$(srcdir)/'`sieve/bc_emit.c sieve/sieve_libcyrus_sieve_la-bc_eval.lo: sieve/bc_eval.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(sieve_libcyrus_sieve_la_CFLAGS) $(CFLAGS) -MT sieve/sieve_libcyrus_sieve_la-bc_eval.lo -MD -MP -MF sieve/$(DEPDIR)/sieve_libcyrus_sieve_la-bc_eval.Tpo -c -o sieve/sieve_libcyrus_sieve_la-bc_eval.lo `test -f 'sieve/bc_eval.c' || echo '$(srcdir)/'`sieve/bc_eval.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) sieve/$(DEPDIR)/sieve_libcyrus_sieve_la-bc_eval.Tpo sieve/$(DEPDIR)/sieve_libcyrus_sieve_la-bc_eval.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='sieve/bc_eval.c' object='sieve/sieve_libcyrus_sieve_la-bc_eval.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(sieve_libcyrus_sieve_la_CFLAGS) $(CFLAGS) -c -o sieve/sieve_libcyrus_sieve_la-bc_eval.lo `test -f 'sieve/bc_eval.c' || echo '$(srcdir)/'`sieve/bc_eval.c sieve/sieve_libcyrus_sieve_la-bc_generate.lo: sieve/bc_generate.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(sieve_libcyrus_sieve_la_CFLAGS) $(CFLAGS) -MT sieve/sieve_libcyrus_sieve_la-bc_generate.lo -MD -MP -MF sieve/$(DEPDIR)/sieve_libcyrus_sieve_la-bc_generate.Tpo -c -o sieve/sieve_libcyrus_sieve_la-bc_generate.lo `test -f 'sieve/bc_generate.c' || echo '$(srcdir)/'`sieve/bc_generate.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) sieve/$(DEPDIR)/sieve_libcyrus_sieve_la-bc_generate.Tpo sieve/$(DEPDIR)/sieve_libcyrus_sieve_la-bc_generate.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='sieve/bc_generate.c' object='sieve/sieve_libcyrus_sieve_la-bc_generate.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(sieve_libcyrus_sieve_la_CFLAGS) $(CFLAGS) -c -o sieve/sieve_libcyrus_sieve_la-bc_generate.lo `test -f 'sieve/bc_generate.c' || echo '$(srcdir)/'`sieve/bc_generate.c sieve/sieve_libcyrus_sieve_la-comparator.lo: sieve/comparator.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(sieve_libcyrus_sieve_la_CFLAGS) $(CFLAGS) -MT sieve/sieve_libcyrus_sieve_la-comparator.lo -MD -MP -MF sieve/$(DEPDIR)/sieve_libcyrus_sieve_la-comparator.Tpo -c -o sieve/sieve_libcyrus_sieve_la-comparator.lo `test -f 'sieve/comparator.c' || echo '$(srcdir)/'`sieve/comparator.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) sieve/$(DEPDIR)/sieve_libcyrus_sieve_la-comparator.Tpo sieve/$(DEPDIR)/sieve_libcyrus_sieve_la-comparator.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='sieve/comparator.c' object='sieve/sieve_libcyrus_sieve_la-comparator.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(sieve_libcyrus_sieve_la_CFLAGS) $(CFLAGS) -c -o sieve/sieve_libcyrus_sieve_la-comparator.lo `test -f 'sieve/comparator.c' || echo '$(srcdir)/'`sieve/comparator.c sieve/sieve_libcyrus_sieve_la-flags.lo: sieve/flags.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(sieve_libcyrus_sieve_la_CFLAGS) $(CFLAGS) -MT sieve/sieve_libcyrus_sieve_la-flags.lo -MD -MP -MF sieve/$(DEPDIR)/sieve_libcyrus_sieve_la-flags.Tpo -c -o sieve/sieve_libcyrus_sieve_la-flags.lo `test -f 'sieve/flags.c' || echo '$(srcdir)/'`sieve/flags.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) sieve/$(DEPDIR)/sieve_libcyrus_sieve_la-flags.Tpo sieve/$(DEPDIR)/sieve_libcyrus_sieve_la-flags.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='sieve/flags.c' object='sieve/sieve_libcyrus_sieve_la-flags.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(sieve_libcyrus_sieve_la_CFLAGS) $(CFLAGS) -c -o sieve/sieve_libcyrus_sieve_la-flags.lo `test -f 'sieve/flags.c' || echo '$(srcdir)/'`sieve/flags.c sieve/sieve_libcyrus_sieve_la-interp.lo: sieve/interp.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(sieve_libcyrus_sieve_la_CFLAGS) $(CFLAGS) -MT sieve/sieve_libcyrus_sieve_la-interp.lo -MD -MP -MF sieve/$(DEPDIR)/sieve_libcyrus_sieve_la-interp.Tpo -c -o sieve/sieve_libcyrus_sieve_la-interp.lo `test -f 'sieve/interp.c' || echo '$(srcdir)/'`sieve/interp.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) sieve/$(DEPDIR)/sieve_libcyrus_sieve_la-interp.Tpo sieve/$(DEPDIR)/sieve_libcyrus_sieve_la-interp.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='sieve/interp.c' object='sieve/sieve_libcyrus_sieve_la-interp.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(sieve_libcyrus_sieve_la_CFLAGS) $(CFLAGS) -c -o sieve/sieve_libcyrus_sieve_la-interp.lo `test -f 'sieve/interp.c' || echo '$(srcdir)/'`sieve/interp.c sieve/sieve_libcyrus_sieve_la-message.lo: sieve/message.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(sieve_libcyrus_sieve_la_CFLAGS) $(CFLAGS) -MT sieve/sieve_libcyrus_sieve_la-message.lo -MD -MP -MF sieve/$(DEPDIR)/sieve_libcyrus_sieve_la-message.Tpo -c -o sieve/sieve_libcyrus_sieve_la-message.lo `test -f 'sieve/message.c' || echo '$(srcdir)/'`sieve/message.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) sieve/$(DEPDIR)/sieve_libcyrus_sieve_la-message.Tpo sieve/$(DEPDIR)/sieve_libcyrus_sieve_la-message.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='sieve/message.c' object='sieve/sieve_libcyrus_sieve_la-message.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(sieve_libcyrus_sieve_la_CFLAGS) $(CFLAGS) -c -o sieve/sieve_libcyrus_sieve_la-message.lo `test -f 'sieve/message.c' || echo '$(srcdir)/'`sieve/message.c sieve/sieve_libcyrus_sieve_la-script.lo: sieve/script.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(sieve_libcyrus_sieve_la_CFLAGS) $(CFLAGS) -MT sieve/sieve_libcyrus_sieve_la-script.lo -MD -MP -MF sieve/$(DEPDIR)/sieve_libcyrus_sieve_la-script.Tpo -c -o sieve/sieve_libcyrus_sieve_la-script.lo `test -f 'sieve/script.c' || echo '$(srcdir)/'`sieve/script.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) sieve/$(DEPDIR)/sieve_libcyrus_sieve_la-script.Tpo sieve/$(DEPDIR)/sieve_libcyrus_sieve_la-script.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='sieve/script.c' object='sieve/sieve_libcyrus_sieve_la-script.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(sieve_libcyrus_sieve_la_CFLAGS) $(CFLAGS) -c -o sieve/sieve_libcyrus_sieve_la-script.lo `test -f 'sieve/script.c' || echo '$(srcdir)/'`sieve/script.c sieve/sieve_libcyrus_sieve_la-sieve.lo: sieve/sieve.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(sieve_libcyrus_sieve_la_CFLAGS) $(CFLAGS) -MT sieve/sieve_libcyrus_sieve_la-sieve.lo -MD -MP -MF sieve/$(DEPDIR)/sieve_libcyrus_sieve_la-sieve.Tpo -c -o sieve/sieve_libcyrus_sieve_la-sieve.lo `test -f 'sieve/sieve.c' || echo '$(srcdir)/'`sieve/sieve.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) sieve/$(DEPDIR)/sieve_libcyrus_sieve_la-sieve.Tpo sieve/$(DEPDIR)/sieve_libcyrus_sieve_la-sieve.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='sieve/sieve.c' object='sieve/sieve_libcyrus_sieve_la-sieve.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(sieve_libcyrus_sieve_la_CFLAGS) $(CFLAGS) -c -o sieve/sieve_libcyrus_sieve_la-sieve.lo `test -f 'sieve/sieve.c' || echo '$(srcdir)/'`sieve/sieve.c sieve/sieve_libcyrus_sieve_la-tree.lo: sieve/tree.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(sieve_libcyrus_sieve_la_CFLAGS) $(CFLAGS) -MT sieve/sieve_libcyrus_sieve_la-tree.lo -MD -MP -MF sieve/$(DEPDIR)/sieve_libcyrus_sieve_la-tree.Tpo -c -o sieve/sieve_libcyrus_sieve_la-tree.lo `test -f 'sieve/tree.c' || echo '$(srcdir)/'`sieve/tree.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) sieve/$(DEPDIR)/sieve_libcyrus_sieve_la-tree.Tpo sieve/$(DEPDIR)/sieve_libcyrus_sieve_la-tree.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='sieve/tree.c' object='sieve/sieve_libcyrus_sieve_la-tree.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(sieve_libcyrus_sieve_la_CFLAGS) $(CFLAGS) -c -o sieve/sieve_libcyrus_sieve_la-tree.lo `test -f 'sieve/tree.c' || echo '$(srcdir)/'`sieve/tree.c sieve/sieve_libcyrus_sieve_la-varlist.lo: sieve/varlist.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(sieve_libcyrus_sieve_la_CFLAGS) $(CFLAGS) -MT sieve/sieve_libcyrus_sieve_la-varlist.lo -MD -MP -MF sieve/$(DEPDIR)/sieve_libcyrus_sieve_la-varlist.Tpo -c -o sieve/sieve_libcyrus_sieve_la-varlist.lo `test -f 'sieve/varlist.c' || echo '$(srcdir)/'`sieve/varlist.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) sieve/$(DEPDIR)/sieve_libcyrus_sieve_la-varlist.Tpo sieve/$(DEPDIR)/sieve_libcyrus_sieve_la-varlist.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='sieve/varlist.c' object='sieve/sieve_libcyrus_sieve_la-varlist.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(sieve_libcyrus_sieve_la_CFLAGS) $(CFLAGS) -c -o sieve/sieve_libcyrus_sieve_la-varlist.lo `test -f 'sieve/varlist.c' || echo '$(srcdir)/'`sieve/varlist.c sieve/sieve_libcyrus_sieve_la-sieve_err.lo: sieve/sieve_err.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(sieve_libcyrus_sieve_la_CFLAGS) $(CFLAGS) -MT sieve/sieve_libcyrus_sieve_la-sieve_err.lo -MD -MP -MF sieve/$(DEPDIR)/sieve_libcyrus_sieve_la-sieve_err.Tpo -c -o sieve/sieve_libcyrus_sieve_la-sieve_err.lo `test -f 'sieve/sieve_err.c' || echo '$(srcdir)/'`sieve/sieve_err.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) sieve/$(DEPDIR)/sieve_libcyrus_sieve_la-sieve_err.Tpo sieve/$(DEPDIR)/sieve_libcyrus_sieve_la-sieve_err.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='sieve/sieve_err.c' object='sieve/sieve_libcyrus_sieve_la-sieve_err.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(sieve_libcyrus_sieve_la_CFLAGS) $(CFLAGS) -c -o sieve/sieve_libcyrus_sieve_la-sieve_err.lo `test -f 'sieve/sieve_err.c' || echo '$(srcdir)/'`sieve/sieve_err.c sieve/sieve_libcyrus_sieve_lex_la-addr-lex.lo: sieve/addr-lex.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(sieve_libcyrus_sieve_lex_la_CFLAGS) $(CFLAGS) -MT sieve/sieve_libcyrus_sieve_lex_la-addr-lex.lo -MD -MP -MF sieve/$(DEPDIR)/sieve_libcyrus_sieve_lex_la-addr-lex.Tpo -c -o sieve/sieve_libcyrus_sieve_lex_la-addr-lex.lo `test -f 'sieve/addr-lex.c' || echo '$(srcdir)/'`sieve/addr-lex.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) sieve/$(DEPDIR)/sieve_libcyrus_sieve_lex_la-addr-lex.Tpo sieve/$(DEPDIR)/sieve_libcyrus_sieve_lex_la-addr-lex.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='sieve/addr-lex.c' object='sieve/sieve_libcyrus_sieve_lex_la-addr-lex.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(sieve_libcyrus_sieve_lex_la_CFLAGS) $(CFLAGS) -c -o sieve/sieve_libcyrus_sieve_lex_la-addr-lex.lo `test -f 'sieve/addr-lex.c' || echo '$(srcdir)/'`sieve/addr-lex.c sieve/sieve_libcyrus_sieve_lex_la-sieve-lex.lo: sieve/sieve-lex.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(sieve_libcyrus_sieve_lex_la_CFLAGS) $(CFLAGS) -MT sieve/sieve_libcyrus_sieve_lex_la-sieve-lex.lo -MD -MP -MF sieve/$(DEPDIR)/sieve_libcyrus_sieve_lex_la-sieve-lex.Tpo -c -o sieve/sieve_libcyrus_sieve_lex_la-sieve-lex.lo `test -f 'sieve/sieve-lex.c' || echo '$(srcdir)/'`sieve/sieve-lex.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) sieve/$(DEPDIR)/sieve_libcyrus_sieve_lex_la-sieve-lex.Tpo sieve/$(DEPDIR)/sieve_libcyrus_sieve_lex_la-sieve-lex.Plo @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='sieve/sieve-lex.c' object='sieve/sieve_libcyrus_sieve_lex_la-sieve-lex.lo' libtool=yes @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(sieve_libcyrus_sieve_lex_la_CFLAGS) $(CFLAGS) -c -o sieve/sieve_libcyrus_sieve_lex_la-sieve-lex.lo `test -f 'sieve/sieve-lex.c' || echo '$(srcdir)/'`sieve/sieve-lex.c imtest/imtest_imtest-imtest.o: imtest/imtest.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imtest_imtest_CFLAGS) $(CFLAGS) -MT imtest/imtest_imtest-imtest.o -MD -MP -MF imtest/$(DEPDIR)/imtest_imtest-imtest.Tpo -c -o imtest/imtest_imtest-imtest.o `test -f 'imtest/imtest.c' || echo '$(srcdir)/'`imtest/imtest.c @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) imtest/$(DEPDIR)/imtest_imtest-imtest.Tpo imtest/$(DEPDIR)/imtest_imtest-imtest.Po @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='imtest/imtest.c' object='imtest/imtest_imtest-imtest.o' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imtest_imtest_CFLAGS) $(CFLAGS) -c -o imtest/imtest_imtest-imtest.o `test -f 'imtest/imtest.c' || echo '$(srcdir)/'`imtest/imtest.c imtest/imtest_imtest-imtest.obj: imtest/imtest.c @am__fastdepCC_TRUE@ $(AM_V_CC)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imtest_imtest_CFLAGS) $(CFLAGS) -MT imtest/imtest_imtest-imtest.obj -MD -MP -MF imtest/$(DEPDIR)/imtest_imtest-imtest.Tpo -c -o imtest/imtest_imtest-imtest.obj `if test -f 'imtest/imtest.c'; then $(CYGPATH_W) 'imtest/imtest.c'; else $(CYGPATH_W) '$(srcdir)/imtest/imtest.c'; fi` @am__fastdepCC_TRUE@ $(AM_V_at)$(am__mv) imtest/$(DEPDIR)/imtest_imtest-imtest.Tpo imtest/$(DEPDIR)/imtest_imtest-imtest.Po @AMDEP_TRUE@@am__fastdepCC_FALSE@ $(AM_V_CC)source='imtest/imtest.c' object='imtest/imtest_imtest-imtest.obj' libtool=no @AMDEPBACKSLASH@ @AMDEP_TRUE@@am__fastdepCC_FALSE@ DEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCC_FALSE@ $(AM_V_CC@am__nodep@)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(imtest_imtest_CFLAGS) $(CFLAGS) -c -o imtest/imtest_imtest-imtest.obj `if test -f 'imtest/imtest.c'; then $(CYGPATH_W) 'imtest/imtest.c'; else $(CYGPATH_W) '$(srcdir)/imtest/imtest.c'; fi` .l.c: $(AM_V_LEX)$(am__skiplex) $(SHELL) $(YLWRAP) $< $(LEX_OUTPUT_ROOT).c $@ -- $(LEXCOMPILE) .y.c: $(AM_V_YACC)$(am__skipyacc) $(SHELL) $(YLWRAP) $< y.tab.c $@ y.tab.h `echo $@ | $(am__yacc_c2h)` y.output $*.output -- $(YACCCOMPILE) mostlyclean-libtool: -rm -f *.lo clean-libtool: -rm -rf .libs _libs -rm -rf com_err/et/.libs com_err/et/_libs -rm -rf cunit/.libs cunit/_libs -rm -rf imap/.libs imap/_libs -rm -rf imtest/.libs imtest/_libs -rm -rf lib/.libs lib/_libs -rm -rf master/.libs master/_libs -rm -rf netnews/.libs netnews/_libs -rm -rf notifyd/.libs notifyd/_libs -rm -rf perl/.libs perl/_libs -rm -rf ptclient/.libs ptclient/_libs -rm -rf sieve/.libs sieve/_libs -rm -rf timsieved/.libs timsieved/_libs -rm -rf tools/.libs tools/_libs distclean-libtool: -rm -f libtool config.lt install-man1: $(dist_man_MANS) @$(NORMAL_INSTALL) @list1=''; \ list2='$(dist_man_MANS)'; \ test -n "$(man1dir)" \ && test -n "`echo $$list1$$list2`" \ || exit 0; \ echo " $(MKDIR_P) '$(DESTDIR)$(man1dir)'"; \ $(MKDIR_P) "$(DESTDIR)$(man1dir)" || exit 1; \ { for i in $$list1; do echo "$$i"; done; \ if test -n "$$list2"; then \ for i in $$list2; do echo "$$i"; done \ | sed -n '/\.1[a-z]*$$/p'; \ fi; \ } | while read p; do \ if test -f $$p; then d=; else d="$(srcdir)/"; fi; \ echo "$$d$$p"; echo "$$p"; \ done | \ sed -e 'n;s,.*/,,;p;h;s,.*\.,,;s,^[^1][0-9a-z]*$$,1,;x' \ -e 's,\.[0-9a-z]*$$,,;$(transform);G;s,\n,.,' | \ sed 'N;N;s,\n, ,g' | { \ list=; while read file base inst; do \ if test "$$base" = "$$inst"; then list="$$list $$file"; else \ echo " $(INSTALL_DATA) '$$file' '$(DESTDIR)$(man1dir)/$$inst'"; \ $(INSTALL_DATA) "$$file" "$(DESTDIR)$(man1dir)/$$inst" || exit $$?; \ fi; \ done; \ for i in $$list; do echo "$$i"; done | $(am__base_list) | \ while read files; do \ test -z "$$files" || { \ echo " $(INSTALL_DATA) $$files '$(DESTDIR)$(man1dir)'"; \ $(INSTALL_DATA) $$files "$(DESTDIR)$(man1dir)" || exit $$?; }; \ done; } uninstall-man1: @$(NORMAL_UNINSTALL) @list=''; test -n "$(man1dir)" || exit 0; \ files=`{ for i in $$list; do echo "$$i"; done; \ l2='$(dist_man_MANS)'; for i in $$l2; do echo "$$i"; done | \ sed -n '/\.1[a-z]*$$/p'; \ } | sed -e 's,.*/,,;h;s,.*\.,,;s,^[^1][0-9a-z]*$$,1,;x' \ -e 's,\.[0-9a-z]*$$,,;$(transform);G;s,\n,.,'`; \ dir='$(DESTDIR)$(man1dir)'; $(am__uninstall_files_from_dir) install-man3: $(dist_man_MANS) @$(NORMAL_INSTALL) @list1=''; \ list2='$(dist_man_MANS)'; \ test -n "$(man3dir)" \ && test -n "`echo $$list1$$list2`" \ || exit 0; \ echo " $(MKDIR_P) '$(DESTDIR)$(man3dir)'"; \ $(MKDIR_P) "$(DESTDIR)$(man3dir)" || exit 1; \ { for i in $$list1; do echo "$$i"; done; \ if test -n "$$list2"; then \ for i in $$list2; do echo "$$i"; done \ | sed -n '/\.3[a-z]*$$/p'; \ fi; \ } | while read p; do \ if test -f $$p; then d=; else d="$(srcdir)/"; fi; \ echo "$$d$$p"; echo "$$p"; \ done | \ sed -e 'n;s,.*/,,;p;h;s,.*\.,,;s,^[^3][0-9a-z]*$$,3,;x' \ -e 's,\.[0-9a-z]*$$,,;$(transform);G;s,\n,.,' | \ sed 'N;N;s,\n, ,g' | { \ list=; while read file base inst; do \ if test "$$base" = "$$inst"; then list="$$list $$file"; else \ echo " $(INSTALL_DATA) '$$file' '$(DESTDIR)$(man3dir)/$$inst'"; \ $(INSTALL_DATA) "$$file" "$(DESTDIR)$(man3dir)/$$inst" || exit $$?; \ fi; \ done; \ for i in $$list; do echo "$$i"; done | $(am__base_list) | \ while read files; do \ test -z "$$files" || { \ echo " $(INSTALL_DATA) $$files '$(DESTDIR)$(man3dir)'"; \ $(INSTALL_DATA) $$files "$(DESTDIR)$(man3dir)" || exit $$?; }; \ done; } uninstall-man3: @$(NORMAL_UNINSTALL) @list=''; test -n "$(man3dir)" || exit 0; \ files=`{ for i in $$list; do echo "$$i"; done; \ l2='$(dist_man_MANS)'; for i in $$l2; do echo "$$i"; done | \ sed -n '/\.3[a-z]*$$/p'; \ } | sed -e 's,.*/,,;h;s,.*\.,,;s,^[^3][0-9a-z]*$$,3,;x' \ -e 's,\.[0-9a-z]*$$,,;$(transform);G;s,\n,.,'`; \ dir='$(DESTDIR)$(man3dir)'; $(am__uninstall_files_from_dir) install-man5: $(dist_man_MANS) @$(NORMAL_INSTALL) @list1=''; \ list2='$(dist_man_MANS)'; \ test -n "$(man5dir)" \ && test -n "`echo $$list1$$list2`" \ || exit 0; \ echo " $(MKDIR_P) '$(DESTDIR)$(man5dir)'"; \ $(MKDIR_P) "$(DESTDIR)$(man5dir)" || exit 1; \ { for i in $$list1; do echo "$$i"; done; \ if test -n "$$list2"; then \ for i in $$list2; do echo "$$i"; done \ | sed -n '/\.5[a-z]*$$/p'; \ fi; \ } | while read p; do \ if test -f $$p; then d=; else d="$(srcdir)/"; fi; \ echo "$$d$$p"; echo "$$p"; \ done | \ sed -e 'n;s,.*/,,;p;h;s,.*\.,,;s,^[^5][0-9a-z]*$$,5,;x' \ -e 's,\.[0-9a-z]*$$,,;$(transform);G;s,\n,.,' | \ sed 'N;N;s,\n, ,g' | { \ list=; while read file base inst; do \ if test "$$base" = "$$inst"; then list="$$list $$file"; else \ echo " $(INSTALL_DATA) '$$file' '$(DESTDIR)$(man5dir)/$$inst'"; \ $(INSTALL_DATA) "$$file" "$(DESTDIR)$(man5dir)/$$inst" || exit $$?; \ fi; \ done; \ for i in $$list; do echo "$$i"; done | $(am__base_list) | \ while read files; do \ test -z "$$files" || { \ echo " $(INSTALL_DATA) $$files '$(DESTDIR)$(man5dir)'"; \ $(INSTALL_DATA) $$files "$(DESTDIR)$(man5dir)" || exit $$?; }; \ done; } uninstall-man5: @$(NORMAL_UNINSTALL) @list=''; test -n "$(man5dir)" || exit 0; \ files=`{ for i in $$list; do echo "$$i"; done; \ l2='$(dist_man_MANS)'; for i in $$l2; do echo "$$i"; done | \ sed -n '/\.5[a-z]*$$/p'; \ } | sed -e 's,.*/,,;h;s,.*\.,,;s,^[^5][0-9a-z]*$$,5,;x' \ -e 's,\.[0-9a-z]*$$,,;$(transform);G;s,\n,.,'`; \ dir='$(DESTDIR)$(man5dir)'; $(am__uninstall_files_from_dir) install-man8: $(dist_man_MANS) @$(NORMAL_INSTALL) @list1=''; \ list2='$(dist_man_MANS)'; \ test -n "$(man8dir)" \ && test -n "`echo $$list1$$list2`" \ || exit 0; \ echo " $(MKDIR_P) '$(DESTDIR)$(man8dir)'"; \ $(MKDIR_P) "$(DESTDIR)$(man8dir)" || exit 1; \ { for i in $$list1; do echo "$$i"; done; \ if test -n "$$list2"; then \ for i in $$list2; do echo "$$i"; done \ | sed -n '/\.8[a-z]*$$/p'; \ fi; \ } | while read p; do \ if test -f $$p; then d=; else d="$(srcdir)/"; fi; \ echo "$$d$$p"; echo "$$p"; \ done | \ sed -e 'n;s,.*/,,;p;h;s,.*\.,,;s,^[^8][0-9a-z]*$$,8,;x' \ -e 's,\.[0-9a-z]*$$,,;$(transform);G;s,\n,.,' | \ sed 'N;N;s,\n, ,g' | { \ list=; while read file base inst; do \ if test "$$base" = "$$inst"; then list="$$list $$file"; else \ echo " $(INSTALL_DATA) '$$file' '$(DESTDIR)$(man8dir)/$$inst'"; \ $(INSTALL_DATA) "$$file" "$(DESTDIR)$(man8dir)/$$inst" || exit $$?; \ fi; \ done; \ for i in $$list; do echo "$$i"; done | $(am__base_list) | \ while read files; do \ test -z "$$files" || { \ echo " $(INSTALL_DATA) $$files '$(DESTDIR)$(man8dir)'"; \ $(INSTALL_DATA) $$files "$(DESTDIR)$(man8dir)" || exit $$?; }; \ done; } uninstall-man8: @$(NORMAL_UNINSTALL) @list=''; test -n "$(man8dir)" || exit 0; \ files=`{ for i in $$list; do echo "$$i"; done; \ l2='$(dist_man_MANS)'; for i in $$l2; do echo "$$i"; done | \ sed -n '/\.8[a-z]*$$/p'; \ } | sed -e 's,.*/,,;h;s,.*\.,,;s,^[^8][0-9a-z]*$$,8,;x' \ -e 's,\.[0-9a-z]*$$,,;$(transform);G;s,\n,.,'`; \ dir='$(DESTDIR)$(man8dir)'; $(am__uninstall_files_from_dir) install-dist_sysconfDATA: $(dist_sysconf_DATA) @$(NORMAL_INSTALL) @list='$(dist_sysconf_DATA)'; test -n "$(sysconfdir)" || list=; \ if test -n "$$list"; then \ echo " $(MKDIR_P) '$(DESTDIR)$(sysconfdir)'"; \ $(MKDIR_P) "$(DESTDIR)$(sysconfdir)" || exit 1; \ fi; \ for p in $$list; do \ if test -f "$$p"; then d=; else d="$(srcdir)/"; fi; \ echo "$$d$$p"; \ done | $(am__base_list) | \ while read files; do \ echo " $(INSTALL_DATA) $$files '$(DESTDIR)$(sysconfdir)'"; \ $(INSTALL_DATA) $$files "$(DESTDIR)$(sysconfdir)" || exit $$?; \ done uninstall-dist_sysconfDATA: @$(NORMAL_UNINSTALL) @list='$(dist_sysconf_DATA)'; test -n "$(sysconfdir)" || list=; \ files=`for p in $$list; do echo $$p; done | sed -e 's|^.*/||'`; \ dir='$(DESTDIR)$(sysconfdir)'; $(am__uninstall_files_from_dir) install-pkgconfigDATA: $(pkgconfig_DATA) @$(NORMAL_INSTALL) @list='$(pkgconfig_DATA)'; test -n "$(pkgconfigdir)" || list=; \ if test -n "$$list"; then \ echo " $(MKDIR_P) '$(DESTDIR)$(pkgconfigdir)'"; \ $(MKDIR_P) "$(DESTDIR)$(pkgconfigdir)" || exit 1; \ fi; \ for p in $$list; do \ if test -f "$$p"; then d=; else d="$(srcdir)/"; fi; \ echo "$$d$$p"; \ done | $(am__base_list) | \ while read files; do \ echo " $(INSTALL_DATA) $$files '$(DESTDIR)$(pkgconfigdir)'"; \ $(INSTALL_DATA) $$files "$(DESTDIR)$(pkgconfigdir)" || exit $$?; \ done uninstall-pkgconfigDATA: @$(NORMAL_UNINSTALL) @list='$(pkgconfig_DATA)'; test -n "$(pkgconfigdir)" || list=; \ files=`for p in $$list; do echo $$p; done | sed -e 's|^.*/||'`; \ dir='$(DESTDIR)$(pkgconfigdir)'; $(am__uninstall_files_from_dir) install-includeHEADERS: $(include_HEADERS) @$(NORMAL_INSTALL) @list='$(include_HEADERS)'; test -n "$(includedir)" || list=; \ if test -n "$$list"; then \ echo " $(MKDIR_P) '$(DESTDIR)$(includedir)'"; \ $(MKDIR_P) "$(DESTDIR)$(includedir)" || exit 1; \ fi; \ for p in $$list; do \ if test -f "$$p"; then d=; else d="$(srcdir)/"; fi; \ echo "$$d$$p"; \ done | $(am__base_list) | \ while read files; do \ echo " $(INSTALL_HEADER) $$files '$(DESTDIR)$(includedir)'"; \ $(INSTALL_HEADER) $$files "$(DESTDIR)$(includedir)" || exit $$?; \ done uninstall-includeHEADERS: @$(NORMAL_UNINSTALL) @list='$(include_HEADERS)'; test -n "$(includedir)" || list=; \ files=`for p in $$list; do echo $$p; done | sed -e 's|^.*/||'`; \ dir='$(DESTDIR)$(includedir)'; $(am__uninstall_files_from_dir) install-nobase_includeHEADERS: $(nobase_include_HEADERS) @$(NORMAL_INSTALL) @list='$(nobase_include_HEADERS)'; test -n "$(includedir)" || list=; \ if test -n "$$list"; then \ echo " $(MKDIR_P) '$(DESTDIR)$(includedir)'"; \ $(MKDIR_P) "$(DESTDIR)$(includedir)" || exit 1; \ fi; \ $(am__nobase_list) | while read dir files; do \ xfiles=; for file in $$files; do \ if test -f "$$file"; then xfiles="$$xfiles $$file"; \ else xfiles="$$xfiles $(srcdir)/$$file"; fi; done; \ test -z "$$xfiles" || { \ test "x$$dir" = x. || { \ echo " $(MKDIR_P) '$(DESTDIR)$(includedir)/$$dir'"; \ $(MKDIR_P) "$(DESTDIR)$(includedir)/$$dir"; }; \ echo " $(INSTALL_HEADER) $$xfiles '$(DESTDIR)$(includedir)/$$dir'"; \ $(INSTALL_HEADER) $$xfiles "$(DESTDIR)$(includedir)/$$dir" || exit $$?; }; \ done uninstall-nobase_includeHEADERS: @$(NORMAL_UNINSTALL) @list='$(nobase_include_HEADERS)'; test -n "$(includedir)" || list=; \ $(am__nobase_strip_setup); files=`$(am__nobase_strip)`; \ dir='$(DESTDIR)$(includedir)'; $(am__uninstall_files_from_dir) install-nobase_nodist_includeHEADERS: $(nobase_nodist_include_HEADERS) @$(NORMAL_INSTALL) @list='$(nobase_nodist_include_HEADERS)'; test -n "$(includedir)" || list=; \ if test -n "$$list"; then \ echo " $(MKDIR_P) '$(DESTDIR)$(includedir)'"; \ $(MKDIR_P) "$(DESTDIR)$(includedir)" || exit 1; \ fi; \ $(am__nobase_list) | while read dir files; do \ xfiles=; for file in $$files; do \ if test -f "$$file"; then xfiles="$$xfiles $$file"; \ else xfiles="$$xfiles $(srcdir)/$$file"; fi; done; \ test -z "$$xfiles" || { \ test "x$$dir" = x. || { \ echo " $(MKDIR_P) '$(DESTDIR)$(includedir)/$$dir'"; \ $(MKDIR_P) "$(DESTDIR)$(includedir)/$$dir"; }; \ echo " $(INSTALL_HEADER) $$xfiles '$(DESTDIR)$(includedir)/$$dir'"; \ $(INSTALL_HEADER) $$xfiles "$(DESTDIR)$(includedir)/$$dir" || exit $$?; }; \ done uninstall-nobase_nodist_includeHEADERS: @$(NORMAL_UNINSTALL) @list='$(nobase_nodist_include_HEADERS)'; test -n "$(includedir)" || list=; \ $(am__nobase_strip_setup); files=`$(am__nobase_strip)`; \ dir='$(DESTDIR)$(includedir)'; $(am__uninstall_files_from_dir) install-nodist_includeHEADERS: $(nodist_include_HEADERS) @$(NORMAL_INSTALL) @list='$(nodist_include_HEADERS)'; test -n "$(includedir)" || list=; \ if test -n "$$list"; then \ echo " $(MKDIR_P) '$(DESTDIR)$(includedir)'"; \ $(MKDIR_P) "$(DESTDIR)$(includedir)" || exit 1; \ fi; \ for p in $$list; do \ if test -f "$$p"; then d=; else d="$(srcdir)/"; fi; \ echo "$$d$$p"; \ done | $(am__base_list) | \ while read files; do \ echo " $(INSTALL_HEADER) $$files '$(DESTDIR)$(includedir)'"; \ $(INSTALL_HEADER) $$files "$(DESTDIR)$(includedir)" || exit $$?; \ done uninstall-nodist_includeHEADERS: @$(NORMAL_UNINSTALL) @list='$(nodist_include_HEADERS)'; test -n "$(includedir)" || list=; \ files=`for p in $$list; do echo $$p; done | sed -e 's|^.*/||'`; \ dir='$(DESTDIR)$(includedir)'; $(am__uninstall_files_from_dir) # This directory's subdirectories are mostly independent; you can cd # into them and run 'make' without going through this Makefile. # To change the values of 'make' variables: instead of editing Makefiles, # (1) if the variable is set in 'config.status', edit 'config.status' # (which will cause the Makefiles to be regenerated when you run 'make'); # (2) otherwise, pass the desired values on the 'make' command line. $(am__recursive_targets): @fail=; \ if $(am__make_keepgoing); then \ failcom='fail=yes'; \ else \ failcom='exit 1'; \ fi; \ dot_seen=no; \ target=`echo $@ | sed s/-recursive//`; \ case "$@" in \ distclean-* | maintainer-clean-*) list='$(DIST_SUBDIRS)' ;; \ *) list='$(SUBDIRS)' ;; \ esac; \ for subdir in $$list; do \ echo "Making $$target in $$subdir"; \ if test "$$subdir" = "."; then \ dot_seen=yes; \ local_target="$$target-am"; \ else \ local_target="$$target"; \ fi; \ ($(am__cd) $$subdir && $(MAKE) $(AM_MAKEFLAGS) $$local_target) \ || eval $$failcom; \ done; \ if test "$$dot_seen" = "no"; then \ $(MAKE) $(AM_MAKEFLAGS) "$$target-am" || exit 1; \ fi; test -z "$$fail" ID: $(am__tagged_files) $(am__define_uniq_tagged_files); mkid -fID $$unique tags: tags-recursive TAGS: tags tags-am: $(TAGS_DEPENDENCIES) $(am__tagged_files) set x; \ here=`pwd`; \ if ($(ETAGS) --etags-include --version) >/dev/null 2>&1; then \ include_option=--etags-include; \ empty_fix=.; \ else \ include_option=--include; \ empty_fix=; \ fi; \ list='$(SUBDIRS)'; for subdir in $$list; do \ if test "$$subdir" = .; then :; else \ test ! -f $$subdir/TAGS || \ set "$$@" "$$include_option=$$here/$$subdir/TAGS"; \ fi; \ done; \ $(am__define_uniq_tagged_files); \ shift; \ if test -z "$(ETAGS_ARGS)$$*$$unique"; then :; else \ test -n "$$unique" || unique=$$empty_fix; \ if test $$# -gt 0; then \ $(ETAGS) $(ETAGSFLAGS) $(AM_ETAGSFLAGS) $(ETAGS_ARGS) \ "$$@" $$unique; \ else \ $(ETAGS) $(ETAGSFLAGS) $(AM_ETAGSFLAGS) $(ETAGS_ARGS) \ $$unique; \ fi; \ fi ctags: ctags-recursive CTAGS: ctags ctags-am: $(TAGS_DEPENDENCIES) $(am__tagged_files) $(am__define_uniq_tagged_files); \ test -z "$(CTAGS_ARGS)$$unique" \ || $(CTAGS) $(CTAGSFLAGS) $(AM_CTAGSFLAGS) $(CTAGS_ARGS) \ $$unique GTAGS: here=`$(am__cd) $(top_builddir) && pwd` \ && $(am__cd) $(top_srcdir) \ && gtags -i $(GTAGS_ARGS) "$$here" cscope: cscope.files test ! -s cscope.files \ || $(CSCOPE) -b -q $(AM_CSCOPEFLAGS) $(CSCOPEFLAGS) -i cscope.files $(CSCOPE_ARGS) clean-cscope: -rm -f cscope.files cscope.files: clean-cscope cscopelist cscopelist: cscopelist-recursive cscopelist-am: $(am__tagged_files) list='$(am__tagged_files)'; \ case "$(srcdir)" in \ [\\/]* | ?:[\\/]*) sdir="$(srcdir)" ;; \ *) sdir=$(subdir)/$(srcdir) ;; \ esac; \ for i in $$list; do \ if test -f "$$i"; then \ echo "$(subdir)/$$i"; \ else \ echo "$$sdir/$$i"; \ fi; \ done >> $(top_builddir)/cscope.files distclean-tags: -rm -f TAGS ID GTAGS GRTAGS GSYMS GPATH tags -rm -f cscope.out cscope.in.out cscope.po.out cscope.files distdir: $(DISTFILES) $(am__remove_distdir) test -d "$(distdir)" || mkdir "$(distdir)" @srcdirstrip=`echo "$(srcdir)" | sed 's/[].[^$$\\*]/\\\\&/g'`; \ topsrcdirstrip=`echo "$(top_srcdir)" | sed 's/[].[^$$\\*]/\\\\&/g'`; \ list='$(DISTFILES)'; \ dist_files=`for file in $$list; do echo $$file; done | \ sed -e "s|^$$srcdirstrip/||;t" \ -e "s|^$$topsrcdirstrip/|$(top_builddir)/|;t"`; \ case $$dist_files in \ */*) $(MKDIR_P) `echo "$$dist_files" | \ sed '/\//!d;s|^|$(distdir)/|;s,/[^/]*$$,,' | \ sort -u` ;; \ esac; \ for file in $$dist_files; do \ if test -f $$file || test -d $$file; then d=.; else d=$(srcdir); fi; \ if test -d $$d/$$file; then \ dir=`echo "/$$file" | sed -e 's,/[^/]*$$,,'`; \ if test -d "$(distdir)/$$file"; then \ find "$(distdir)/$$file" -type d ! -perm -700 -exec chmod u+rwx {} \;; \ fi; \ if test -d $(srcdir)/$$file && test $$d != $(srcdir); then \ cp -fpR $(srcdir)/$$file "$(distdir)$$dir" || exit 1; \ find "$(distdir)/$$file" -type d ! -perm -700 -exec chmod u+rwx {} \;; \ fi; \ cp -fpR $$d/$$file "$(distdir)$$dir" || exit 1; \ else \ test -f "$(distdir)/$$file" \ || cp -p $$d/$$file "$(distdir)/$$file" \ || exit 1; \ fi; \ done @list='$(DIST_SUBDIRS)'; for subdir in $$list; do \ if test "$$subdir" = .; then :; else \ $(am__make_dryrun) \ || test -d "$(distdir)/$$subdir" \ || $(MKDIR_P) "$(distdir)/$$subdir" \ || exit 1; \ dir1=$$subdir; dir2="$(distdir)/$$subdir"; \ $(am__relativize); \ new_distdir=$$reldir; \ dir1=$$subdir; dir2="$(top_distdir)"; \ $(am__relativize); \ new_top_distdir=$$reldir; \ echo " (cd $$subdir && $(MAKE) $(AM_MAKEFLAGS) top_distdir="$$new_top_distdir" distdir="$$new_distdir" \\"; \ echo " am__remove_distdir=: am__skip_length_check=: am__skip_mode_fix=: distdir)"; \ ($(am__cd) $$subdir && \ $(MAKE) $(AM_MAKEFLAGS) \ top_distdir="$$new_top_distdir" \ distdir="$$new_distdir" \ am__remove_distdir=: \ am__skip_length_check=: \ am__skip_mode_fix=: \ distdir) \ || exit 1; \ fi; \ done -test -n "$(am__skip_mode_fix)" \ || find "$(distdir)" -type d ! -perm -755 \ -exec chmod u+rwx,go+rx {} \; -o \ ! -type d ! -perm -444 -links 1 -exec chmod a+r {} \; -o \ ! -type d ! -perm -400 -exec chmod a+r {} \; -o \ ! -type d ! -perm -444 -exec $(install_sh) -c -m a+r {} {} \; \ || chmod -R a+r "$(distdir)" dist-gzip: distdir tardir=$(distdir) && $(am__tar) | GZIP=$(GZIP_ENV) gzip -c >$(distdir).tar.gz $(am__post_remove_distdir) dist-bzip2: distdir tardir=$(distdir) && $(am__tar) | BZIP2=$${BZIP2--9} bzip2 -c >$(distdir).tar.bz2 $(am__post_remove_distdir) dist-lzip: distdir tardir=$(distdir) && $(am__tar) | lzip -c $${LZIP_OPT--9} >$(distdir).tar.lz $(am__post_remove_distdir) dist-xz: distdir tardir=$(distdir) && $(am__tar) | XZ_OPT=$${XZ_OPT--e} xz -c >$(distdir).tar.xz $(am__post_remove_distdir) dist-tarZ: distdir @echo WARNING: "Support for distribution archives compressed with" \ "legacy program 'compress' is deprecated." >&2 @echo WARNING: "It will be removed altogether in Automake 2.0" >&2 tardir=$(distdir) && $(am__tar) | compress -c >$(distdir).tar.Z $(am__post_remove_distdir) dist-shar: distdir @echo WARNING: "Support for shar distribution archives is" \ "deprecated." >&2 @echo WARNING: "It will be removed altogether in Automake 2.0" >&2 shar $(distdir) | GZIP=$(GZIP_ENV) gzip -c >$(distdir).shar.gz $(am__post_remove_distdir) dist-zip: distdir -rm -f $(distdir).zip zip -rq $(distdir).zip $(distdir) $(am__post_remove_distdir) dist dist-all: $(MAKE) $(AM_MAKEFLAGS) $(DIST_TARGETS) am__post_remove_distdir='@:' $(am__post_remove_distdir) # This target untars the dist file and tries a VPATH configuration. Then # it guarantees that the distribution is self-contained by making another # tarfile. distcheck: dist case '$(DIST_ARCHIVES)' in \ *.tar.gz*) \ GZIP=$(GZIP_ENV) gzip -dc $(distdir).tar.gz | $(am__untar) ;;\ *.tar.bz2*) \ bzip2 -dc $(distdir).tar.bz2 | $(am__untar) ;;\ *.tar.lz*) \ lzip -dc $(distdir).tar.lz | $(am__untar) ;;\ *.tar.xz*) \ xz -dc $(distdir).tar.xz | $(am__untar) ;;\ *.tar.Z*) \ uncompress -c $(distdir).tar.Z | $(am__untar) ;;\ *.shar.gz*) \ GZIP=$(GZIP_ENV) gzip -dc $(distdir).shar.gz | unshar ;;\ *.zip*) \ unzip $(distdir).zip ;;\ esac chmod -R a-w $(distdir) chmod u+w $(distdir) mkdir $(distdir)/_build $(distdir)/_build/sub $(distdir)/_inst chmod a-w $(distdir) test -d $(distdir)/_build || exit 0; \ dc_install_base=`$(am__cd) $(distdir)/_inst && pwd | sed -e 's,^[^:\\/]:[\\/],/,'` \ && dc_destdir="$${TMPDIR-/tmp}/am-dc-$$$$/" \ && am__cwd=`pwd` \ && $(am__cd) $(distdir)/_build/sub \ && ../../configure \ $(AM_DISTCHECK_CONFIGURE_FLAGS) \ $(DISTCHECK_CONFIGURE_FLAGS) \ --srcdir=../.. --prefix="$$dc_install_base" \ && $(MAKE) $(AM_MAKEFLAGS) \ && $(MAKE) $(AM_MAKEFLAGS) dvi \ && $(MAKE) $(AM_MAKEFLAGS) check \ && $(MAKE) $(AM_MAKEFLAGS) install \ && $(MAKE) $(AM_MAKEFLAGS) installcheck \ && $(MAKE) $(AM_MAKEFLAGS) uninstall \ && $(MAKE) $(AM_MAKEFLAGS) distuninstallcheck_dir="$$dc_install_base" \ distuninstallcheck \ && chmod -R a-w "$$dc_install_base" \ && ({ \ (cd ../.. && umask 077 && mkdir "$$dc_destdir") \ && $(MAKE) $(AM_MAKEFLAGS) DESTDIR="$$dc_destdir" install \ && $(MAKE) $(AM_MAKEFLAGS) DESTDIR="$$dc_destdir" uninstall \ && $(MAKE) $(AM_MAKEFLAGS) DESTDIR="$$dc_destdir" \ distuninstallcheck_dir="$$dc_destdir" distuninstallcheck; \ } || { rm -rf "$$dc_destdir"; exit 1; }) \ && rm -rf "$$dc_destdir" \ && $(MAKE) $(AM_MAKEFLAGS) dist \ && rm -rf $(DIST_ARCHIVES) \ && $(MAKE) $(AM_MAKEFLAGS) distcleancheck \ && cd "$$am__cwd" \ || exit 1 $(am__post_remove_distdir) @(echo "$(distdir) archives ready for distribution: "; \ list='$(DIST_ARCHIVES)'; for i in $$list; do echo $$i; done) | \ sed -e 1h -e 1s/./=/g -e 1p -e 1x -e '$$p' -e '$$x' distuninstallcheck: @test -n '$(distuninstallcheck_dir)' || { \ echo 'ERROR: trying to run $@ with an empty' \ '$$(distuninstallcheck_dir)' >&2; \ exit 1; \ }; \ $(am__cd) '$(distuninstallcheck_dir)' || { \ echo 'ERROR: cannot chdir into $(distuninstallcheck_dir)' >&2; \ exit 1; \ }; \ test `$(am__distuninstallcheck_listfiles) | wc -l` -eq 0 \ || { echo "ERROR: files left after uninstall:" ; \ if test -n "$(DESTDIR)"; then \ echo " (check DESTDIR support)"; \ fi ; \ $(distuninstallcheck_listfiles) ; \ exit 1; } >&2 distcleancheck: distclean @if test '$(srcdir)' = . ; then \ echo "ERROR: distcleancheck can only run from a VPATH build" ; \ exit 1 ; \ fi @test `$(distcleancheck_listfiles) | wc -l` -eq 0 \ || { echo "ERROR: files left in build directory after distclean:" ; \ $(distcleancheck_listfiles) ; \ exit 1; } >&2 @CUNIT_FALSE@check-local: check-am: all-am $(MAKE) $(AM_MAKEFLAGS) $(check_PROGRAMS) $(MAKE) $(AM_MAKEFLAGS) check-local check: $(BUILT_SOURCES) $(MAKE) $(AM_MAKEFLAGS) check-recursive all-am: Makefile $(LIBRARIES) $(LTLIBRARIES) $(PROGRAMS) $(SCRIPTS) \ $(MANS) $(DATA) $(HEADERS) config.h install-binPROGRAMS: install-libLTLIBRARIES installdirs: installdirs-recursive installdirs-am: for dir in "$(DESTDIR)$(libdir)" "$(DESTDIR)$(bindir)" "$(DESTDIR)$(servicedir)" "$(DESTDIR)$(userdir)" "$(DESTDIR)$(man1dir)" "$(DESTDIR)$(man3dir)" "$(DESTDIR)$(man5dir)" "$(DESTDIR)$(man8dir)" "$(DESTDIR)$(sysconfdir)" "$(DESTDIR)$(pkgconfigdir)" "$(DESTDIR)$(includedir)" "$(DESTDIR)$(includedir)" "$(DESTDIR)$(includedir)" "$(DESTDIR)$(includedir)"; do \ test -z "$$dir" || $(MKDIR_P) "$$dir"; \ done install: $(BUILT_SOURCES) $(MAKE) $(AM_MAKEFLAGS) install-recursive install-exec: install-exec-recursive install-data: install-data-recursive uninstall: uninstall-recursive install-am: all-am @$(MAKE) $(AM_MAKEFLAGS) install-exec-am install-data-am installcheck: installcheck-recursive install-strip: if test -z '$(STRIP)'; then \ $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ install; \ else \ $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM="$(INSTALL_STRIP_PROGRAM)" \ install_sh_PROGRAM="$(INSTALL_STRIP_PROGRAM)" INSTALL_STRIP_FLAG=-s \ "INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'" install; \ fi mostlyclean-generic: -test -z "$(LIBOBJS)" || rm -f $(LIBOBJS) -test -z "$(LTLIBOBJS)" || rm -f $(LTLIBOBJS) clean-generic: -test -z "$(CLEANFILES)" || rm -f $(CLEANFILES) distclean-generic: -test -z "$(CONFIG_CLEAN_FILES)" || rm -f $(CONFIG_CLEAN_FILES) -test . = "$(srcdir)" || test -z "$(CONFIG_CLEAN_VPATH_FILES)" || rm -f $(CONFIG_CLEAN_VPATH_FILES) -rm -f com_err/et/$(DEPDIR)/$(am__dirstamp) -rm -f com_err/et/$(am__dirstamp) -rm -f cunit/$(DEPDIR)/$(am__dirstamp) -rm -f cunit/$(am__dirstamp) -rm -f imap/$(DEPDIR)/$(am__dirstamp) -rm -f imap/$(am__dirstamp) -rm -f imtest/$(DEPDIR)/$(am__dirstamp) -rm -f imtest/$(am__dirstamp) -rm -f lib/$(DEPDIR)/$(am__dirstamp) -rm -f lib/$(am__dirstamp) -rm -f master/$(DEPDIR)/$(am__dirstamp) -rm -f master/$(am__dirstamp) -rm -f netnews/$(DEPDIR)/$(am__dirstamp) -rm -f netnews/$(am__dirstamp) -rm -f notifyd/$(DEPDIR)/$(am__dirstamp) -rm -f notifyd/$(am__dirstamp) -rm -f perl/$(am__dirstamp) -rm -f perl/sieve/lib/$(DEPDIR)/$(am__dirstamp) -rm -f perl/sieve/lib/$(am__dirstamp) -rm -f ptclient/$(DEPDIR)/$(am__dirstamp) -rm -f ptclient/$(am__dirstamp) -rm -f sieve/$(DEPDIR)/$(am__dirstamp) -rm -f sieve/$(am__dirstamp) -rm -f timsieved/$(DEPDIR)/$(am__dirstamp) -rm -f timsieved/$(am__dirstamp) -rm -f tools/$(DEPDIR)/$(am__dirstamp) -rm -f tools/$(am__dirstamp) -test -z "$(DISTCLEANFILES)" || rm -f $(DISTCLEANFILES) maintainer-clean-generic: @echo "This command is intended for maintainers to use" @echo "it deletes files that may require special tools to rebuild." -rm -f sieve/addr-lex.c -rm -f sieve/addr.c -rm -f sieve/sieve-lex.c -rm -f sieve/sieve.c -test -z "$(BUILT_SOURCES)" || rm -f $(BUILT_SOURCES) -test -z "$(MAINTAINERCLEANFILES)" || rm -f $(MAINTAINERCLEANFILES) clean: clean-recursive clean-am: clean-binPROGRAMS clean-checkPROGRAMS clean-generic \ clean-libLTLIBRARIES clean-libtool clean-noinstLIBRARIES \ clean-noinstLTLIBRARIES clean-servicePROGRAMS \ clean-userPROGRAMS mostlyclean-am distclean: distclean-recursive -rm -f $(am__CONFIG_DISTCLEAN_FILES) -rm -rf com_err/et/$(DEPDIR) cunit/$(DEPDIR) imap/$(DEPDIR) imtest/$(DEPDIR) lib/$(DEPDIR) master/$(DEPDIR) netnews/$(DEPDIR) notifyd/$(DEPDIR) perl/sieve/lib/$(DEPDIR) ptclient/$(DEPDIR) sieve/$(DEPDIR) timsieved/$(DEPDIR) tools/$(DEPDIR) -rm -f Makefile distclean-am: clean-am distclean-compile distclean-generic \ distclean-hdr distclean-libtool distclean-tags dvi: dvi-recursive dvi-am: html: html-recursive html-am: info: info-recursive info-am: install-data-am: install-includeHEADERS install-man \ install-nobase_includeHEADERS \ install-nobase_nodist_includeHEADERS \ install-nodist_includeHEADERS install-pkgconfigDATA \ install-servicePROGRAMS install-userPROGRAMS @$(NORMAL_INSTALL) $(MAKE) $(AM_MAKEFLAGS) install-data-hook install-dvi: install-dvi-recursive install-dvi-am: install-exec-am: install-binPROGRAMS install-dist_sysconfDATA \ install-libLTLIBRARIES @$(NORMAL_INSTALL) $(MAKE) $(AM_MAKEFLAGS) install-exec-hook install-html: install-html-recursive install-html-am: install-info: install-info-recursive install-info-am: install-man: install-man1 install-man3 install-man5 install-man8 install-pdf: install-pdf-recursive install-pdf-am: install-ps: install-ps-recursive install-ps-am: installcheck-am: maintainer-clean: maintainer-clean-recursive -rm -f $(am__CONFIG_DISTCLEAN_FILES) -rm -rf $(top_srcdir)/autom4te.cache -rm -rf com_err/et/$(DEPDIR) cunit/$(DEPDIR) imap/$(DEPDIR) imtest/$(DEPDIR) lib/$(DEPDIR) master/$(DEPDIR) netnews/$(DEPDIR) notifyd/$(DEPDIR) perl/sieve/lib/$(DEPDIR) ptclient/$(DEPDIR) sieve/$(DEPDIR) timsieved/$(DEPDIR) tools/$(DEPDIR) -rm -f Makefile maintainer-clean-am: distclean-am maintainer-clean-generic mostlyclean: mostlyclean-recursive mostlyclean-am: mostlyclean-compile mostlyclean-generic \ mostlyclean-libtool pdf: pdf-recursive pdf-am: ps: ps-recursive ps-am: uninstall-am: uninstall-binPROGRAMS uninstall-dist_sysconfDATA \ uninstall-includeHEADERS uninstall-libLTLIBRARIES \ uninstall-man uninstall-nobase_includeHEADERS \ uninstall-nobase_nodist_includeHEADERS \ uninstall-nodist_includeHEADERS uninstall-pkgconfigDATA \ uninstall-servicePROGRAMS uninstall-userPROGRAMS uninstall-man: uninstall-man1 uninstall-man3 uninstall-man5 \ uninstall-man8 .MAKE: $(am__recursive_targets) all check check-am install install-am \ install-data-am install-exec-am install-strip .PHONY: $(am__recursive_targets) CTAGS GTAGS TAGS all all-am \ am--refresh check check-am check-local clean clean-binPROGRAMS \ clean-checkPROGRAMS clean-cscope clean-generic \ clean-libLTLIBRARIES clean-libtool clean-noinstLIBRARIES \ clean-noinstLTLIBRARIES clean-servicePROGRAMS \ clean-userPROGRAMS cscope cscopelist-am ctags ctags-am dist \ dist-all dist-bzip2 dist-gzip dist-lzip dist-shar dist-tarZ \ dist-xz dist-zip distcheck distclean distclean-compile \ distclean-generic distclean-hdr distclean-libtool \ distclean-tags distcleancheck distdir distuninstallcheck dvi \ dvi-am html html-am info info-am install install-am \ install-binPROGRAMS install-data install-data-am \ install-data-hook install-dist_sysconfDATA install-dvi \ install-dvi-am install-exec install-exec-am install-exec-hook \ install-html install-html-am install-includeHEADERS \ install-info install-info-am install-libLTLIBRARIES \ install-man install-man1 install-man3 install-man5 \ install-man8 install-nobase_includeHEADERS \ install-nobase_nodist_includeHEADERS \ install-nodist_includeHEADERS install-pdf install-pdf-am \ install-pkgconfigDATA install-ps install-ps-am \ install-servicePROGRAMS install-strip install-userPROGRAMS \ installcheck installcheck-am installdirs installdirs-am \ maintainer-clean maintainer-clean-generic mostlyclean \ mostlyclean-compile mostlyclean-generic mostlyclean-libtool \ pdf pdf-am ps ps-am tags tags-am uninstall uninstall-am \ uninstall-binPROGRAMS uninstall-dist_sysconfDATA \ uninstall-includeHEADERS uninstall-libLTLIBRARIES \ uninstall-man uninstall-man1 uninstall-man3 uninstall-man5 \ uninstall-man8 uninstall-nobase_includeHEADERS \ uninstall-nobase_nodist_includeHEADERS \ uninstall-nodist_includeHEADERS uninstall-pkgconfigDATA \ uninstall-servicePROGRAMS uninstall-userPROGRAMS .PRECIOUS: Makefile com_err/et/compile_et: com_err/et/compile_et.sh com_err/et/config_script \ config.h @${top_srcdir}/com_err/et/config_script ${top_srcdir}/com_err/et/compile_et.sh ${AWK} ${SED} > $@ @chmod 755 $@ @CUNIT_TRUE@.testc.o: @CUNIT_TRUE@ $(CUNIT_PL) --generate-wrapper $< @CUNIT_TRUE@ $(COMPILE) -c -o $@ $<-cunit.c @CUNIT_TRUE@ $(RM) $<-cunit.c @CUNIT_TRUE@$(CUNIT_PROJECT): @CUNIT_TRUE@ $(RM) $@ @CUNIT_TRUE@ $(CUNIT_PL) --add-sources $(cunit_TESTS) @CUNIT_TRUE@cunit/registers.h: $(CUNIT_PROJECT) @CUNIT_TRUE@ $(CUNIT_PL) --generate-register-function $@ @CUNIT_TRUE@check-local: @CUNIT_TRUE@ @echo "Running unit tests" @CUNIT_TRUE@ @vg= ; \ @CUNIT_TRUE@ test -z "$$VG" || vg="$(VALGRIND)" ; \ @CUNIT_TRUE@ f="-v" ; \ @CUNIT_TRUE@ test "x$$CUFORMAT" = xjunit && f="-x" ; \ @CUNIT_TRUE@ cd cunit ; \ @CUNIT_TRUE@ $$vg ./unit $$f ; \ @CUNIT_TRUE@ retval=$$? ; \ @CUNIT_TRUE@ if [ "x$$CUFORMAT" = xjunit ] ; then \ @CUNIT_TRUE@ $(RM) -rf reports ; mkdir reports ; ./cunit-to-junit.pl ; \ @CUNIT_TRUE@ fi ; \ @CUNIT_TRUE@ exit $$retval imap/lmtpstats.c: imap/lmtpstats.snmp snmp/snmpgen cd imap && ../${top_srcdir}/snmp/snmpgen ../${top_srcdir}/imap/lmtpstats.snmp imap/pushstats.c: imap/pushstats.snmp snmp/snmpgen cd imap && ../${top_srcdir}/snmp/snmpgen ../${top_srcdir}/imap/pushstats.snmp imap/imap_err.h imap/imap_err.c: imap/imap_err.et $(COMPILE_ET_DEP) cd imap && $(COMPILE_ET) ../$(top_srcdir)/imap/imap_err.et imap/mupdate_err.h imap/mupdate_err.c: imap/mupdate_err.et $(COMPILE_ET_DEP) cd imap && $(COMPILE_ET) ../$(top_srcdir)/imap/mupdate_err.et imap/nntp_err.h imap/nntp_err.c: imap/nntp_err.et $(COMPILE_ET_DEP) cd imap && $(COMPILE_ET) ../$(top_srcdir)/imap/nntp_err.et imap/http_err.h imap/http_err.c: imap/http_err.et $(COMPILE_ET_DEP) cd imap && $(COMPILE_ET) ../$(top_srcdir)/imap/http_err.et imap/tz_err.h imap/tz_err.c: imap/tz_err.et $(COMPILE_ET_DEP) cd imap && $(COMPILE_ET) ../$(top_srcdir)/imap/tz_err.et @MAINTAINER_MODE_TRUE@imap/rfc822_header.c: imap/rfc822_header.st @MAINTAINER_MODE_TRUE@ ${top_srcdir}/tools/compile_st.pl -c $< > $@.NEW && mv $@.NEW $@ @MAINTAINER_MODE_TRUE@imap/rfc822_header.h: imap/rfc822_header.st @MAINTAINER_MODE_TRUE@ ${top_srcdir}/tools/compile_st.pl -h $< > $@.NEW && mv $@.NEW $@ lib/chartable.c: lib/mkchartable.pl lib/charset/unifix.txt \ $(top_srcdir)/lib/charset/*.t lib/charset/UnicodeData.txt \ lib/charset/aliases.txt @echo "### Building chartables..." perl $(top_srcdir)/lib/mkchartable.pl -m $(top_srcdir)/lib/charset/unifix.txt -m $(top_srcdir)/lib/charset/UnicodeData.txt -a $(top_srcdir)/lib/charset/aliases.txt -o $@ $(top_srcdir)/lib/charset/*.t || (rm -f $@ && exit 1) @echo "### Done building chartables." lib/imapopts.h: lib/imapopts.c lib/imapopts.c: lib/imapoptions tools/config2header $(top_srcdir)/tools/config2header CC="$(CC)" $(top_builddir)/lib/imapopts.c $(top_builddir)/lib/imapopts.h < $(top_srcdir)/lib/imapoptions #this is from lib/test/Makefile.in, however testglob.c does not exist in #/lib/test, instead testglob2.c is there. #lib_test_testglob_LIRBARIES = lib/libcyrus.la lib/libcyrus_min.la -ldb-4.0 @SET_MAKE@ sieve/sieve_err.h sieve/sieve_err.c: sieve/sieve_err.et $(COMPILE_ET_DEP) cd sieve && $(COMPILE_ET) ../$(top_srcdir)/sieve/sieve_err.et # The lex-fix rule is now obsolete, but let's leave a crumb here for a # while so that custom build scripts that expect it to exist don't choke. lex-fix: snapshot:: @echo "Creating snapshot $(PACKAGE_NAME)-$(PACKAGE_VERSION)" @$(MKDIR_P) snapshot @git archive --format=tar --prefix=$(PACKAGE_NAME)-$(PACKAGE_VERSION)/ HEAD | tar -C snapshot/ -x -f - @echo "/* $(PACKAGE_NAME) $(PACKAGE_VERSION) */" > snapshot/$(PACKAGE_NAME)-$(PACKAGE_VERSION)/xversion.h @echo "#define _CYRUS_VERSION \"$(PACKAGE_VERSION)\"" >> snapshot/$(PACKAGE_NAME)-$(PACKAGE_VERSION)/xversion.h @echo "#define CYRUS_GITVERSION \"`git log --abbrev=8 --pretty=\"format:%h %ci\" -1 | cut -d\" \" -f1,2`\"" >> snapshot/$(PACKAGE_NAME)-$(PACKAGE_VERSION)/xversion.h @touch snapshot/$(PACKAGE_NAME)-$(PACKAGE_VERSION)/xversion @echo "creating tarfile" tar -C snapshot -c -f - $(PACKAGE_NAME)-$(PACKAGE_VERSION) | gzip -9 > $(PACKAGE_NAME)-$(PACKAGE_VERSION).tar.gz @rm -rf snapshot man/imapd.conf.5: $(top_srcdir)/tools/config2man $(top_srcdir)/lib/imapoptions @echo creating man/imapd.conf.5 @$(MKDIR_P) man $(top_srcdir)/tools/config2man $(top_srcdir)/lib/imapoptions > $@ man/sieveshell.1: $(top_srcdir)/perl/sieve/scripts/sieveshell.pl @echo creating man/sieveshell.1 @$(MKDIR_P) man pod2man $(top_srcdir)/perl/sieve/scripts/sieveshell.pl > $@ doc/man/cyradm.1.html: $(top_srcdir)/perl/imap/cyradm.sh @$(MKDIR_P) doc/man pod2html $(top_srcdir)/perl/imap/cyradm.sh > $@ rm pod2htm* doc/man/sieveshell.1.html: $(top_srcdir)/perl/sieve/scripts/sieveshell.pl @$(MKDIR_P) doc/man pod2html $(top_srcdir)/perl/sieve/scripts/sieveshell.pl > $@ rm pod2htm* dist-old:: distgit @echo "creating configure" @cd dist/cyrus-imapd-$(PACKAGE_VERSION) ; sh SMakefile @for d in $(DIST_SUBDIRS); \ do \ (cd dist/cyrus-imapd-$(PACKAGE_VERSION)/$$d; \ if [ -f Makefile.dist ]; then \ echo "### Making" dist "in" `pwd`; \ $(MAKE) $(MFLAGS) YACC='$(YACC)' LEX='$(LEX)' \ COMPILE_ET='$(COMPILE_ET)' -f Makefile.dist dist ; \ fi) || exit 1; \ done @echo "creating tarfile" @cd dist ; tar cf - cyrus-imapd-$(PACKAGE_VERSION) | \ gzip -9 > ../cyrus-imapd-$(PACKAGE_VERSION).tar.gz rm -f distgit rm -rf dist distgit: $(MKDIR_P) dist @echo "checking out the distribution from tag $(PACKAGE_NAME)-$(PACKAGE_VERSION)" git archive --format=tar --prefix=$(PACKAGE_NAME)-$(PACKAGE_VERSION)/ $(PACKAGE_NAME)-$(PACKAGE_VERSION) | tar -C dist -x -f - echo "/* Release $(PACKAGE_NAME)-$(PACKAGE_VERSION) */" > dist/$(PACKAGE_NAME)-$(PACKAGE_VERSION)/xversion.h echo "#define _CYRUS_VERSION \"v$(PACKAGE_VERSION)\"" >> dist/$(PACKAGE_NAME)-$(PACKAGE_VERSION)/xversion.h echo "#define CYRUS_GITVERSION \"`git log --abbrev=8 --pretty=\"format:%h %ci\" -1 | cut -d\" \" -f1,2`\"" >> dist/$(PACKAGE_NAME)-$(PACKAGE_VERSION)/xversion.h touch dist/$(PACKAGE_NAME)-$(PACKAGE_VERSION)/xversion touch distgit xversion xversion.h: @echo "/* Development version */" > xversion.h.tmp @echo "#define _CYRUS_VERSION \"$(PACKAGE_VERSION)\"" >> xversion.h.tmp @echo "#define CYRUS_GITVERSION \"`git log --abbrev=8 --pretty=\"format:%h %ci\" -1 | cut -d\" \" -f1,2`\"" >> xversion.h.tmp @cmp -s xversion.h.tmp xversion.h || mv xversion.h.tmp xversion.h @rm -f xversion.h.tmp .PHONY: doc doc: tools/htmlstrip doc/man/cyradm.1.html doc/man/sieveshell.1.html @$(MKDIR_P) doc/text doc/man for man in $(top_builddir)/man/*.[1-9] $(top_srcdir)/man/*.[1-9]; \ do \ echo "=== $$man ==="; \ groff -man -Thtml $$man > doc/man/`basename $$man`.html; \ done rm -f doc/groff-html-*.png for file in $(top_srcdir)/doc/*.html; \ do \ echo "=== $$file ==="; \ tools/htmlstrip $$file > doc/text/`basename $$file .html`; \ done @echo "== done ==" install-data-hook: @CMULOCAL_TRUE@ $(INSTALL) -m 644 $(top_srcdir)/depot/depot.conf $(DESTDIR)/ install-exec-hook: @PERL_TRUE@ for s in installsieve sieveshell; \ @PERL_TRUE@ do \ @PERL_TRUE@ $(PERL_PREINSTALL) < perl/sieve/scripts/$$s.pl > perl/sieve/scripts/$$s ;\ @PERL_TRUE@ $(INSTALL) -m 755 perl/sieve/scripts/$$s $(DESTDIR)$(bindir)/$$s ; \ @PERL_TRUE@ done @$(MKDIR_P) $(DESTDIR)$(userdir) @$(MKDIR_P) $(DESTDIR)$(servicedir) @SERVER_TRUE@ cd $(DESTDIR)$(servicedir) && \ @SERVER_TRUE@ $(LN_S) -f pop3d pop3proxyd && \ @SERVER_TRUE@ $(LN_S) -f imapd proxyd && \ @SERVER_TRUE@ $(LN_S) -f lmtpd lmtpproxyd @$(MKDIR_P) $(DESTDIR)$(bindir) cd $(DESTDIR)$(bindir) && \ $(LN_S) -f imtest lmtptest && \ $(LN_S) -f imtest mupdatetest && \ $(LN_S) -f imtest nntptest && \ $(LN_S) -f imtest pop3test && \ $(LN_S) -f imtest sivtest && \ $(LN_S) -f imtest smtptest && \ $(LN_S) -f imtest synctest .fig.png: fig2dev -L png $< $@ valgrind: $(MAKE) VG=yes check libtool: $(LIBTOOL_DEPS) $(SHELL) ./config.status libtool # Tell versions [3.59,3.63) of GNU make to not export all variables. # Otherwise a system limit (for SysV at least) may be exceeded. .NOEXPORT: cyrus-imapd-2.5.10/cunit/0000755000175000017500000000000013001246664012161 500000000000000cyrus-imapd-2.5.10/cunit/strconcat.testc0000644000175000017500000000443413001236020015133 00000000000000#include #include "cunit/cunit.h" #include "util.h" static void test_null(void) { char *s; s = strconcat((char *)NULL); CU_ASSERT_PTR_NULL(s); } static void test_single(void) { static const char word1[] = "lorem"; char *s; s = strconcat(word1, (char *)NULL); CU_ASSERT_PTR_NOT_NULL(s); CU_ASSERT_STRING_EQUAL(s, "lorem"); free(s); } static void test_multiple(void) { static const char word1[] = "lorem"; static const char word2[] = "ipsum"; static const char word3[] = "dolor"; static const char word4[] = "sit"; static const char word5[] = "amet"; static const char word6[] = "consectetur adipisicing elit"; char *s; s = strconcat(word1, " ", word2, " ", word3, " ", word4, " ", word5, ", ", word6, (char *)NULL); CU_ASSERT_PTR_NOT_NULL(s); CU_ASSERT_STRING_EQUAL(s, "lorem ipsum dolor sit amet, consectetur adipisicing elit"); free(s); } static void test_uncast_null(void) { static const char word1[] = "foo"; static const char word2[] = "bar"; char *s; /* * On some platforms, a combination of the ABI model, default * type of the "NULL" define, and the behaviour of varargs * can screw up the usage of an uncast NULL as a terminator. * This will tell us if we're on one of those. */ s = strconcat(word1, NULL, word2, (char *)NULL); CU_ASSERT_PTR_NOT_NULL(s); CU_ASSERT_STRING_EQUAL(s, "foo"); free(s); } /* This doesn't really belong in this .c file * but it's the least worst choice */ static void test_strcmpsafe(void) { /* chosen so word1 < word2 lexically */ static const char word1[] = "bar"; static const char word2[] = "foo"; /* basic behaviour is identical to strcmp() */ CU_ASSERT_EQUAL(strcmpsafe(word1, word1), 0); CU_ASSERT_EQUAL(strcmpsafe(word2, word2), 0); CU_ASSERT(strcmpsafe(word1, word2) < 0); CU_ASSERT(strcmpsafe(word2, word1) > 0); /* but it's safe with NULLs */ CU_ASSERT_EQUAL(strcmpsafe(NULL, NULL), 0); CU_ASSERT_EQUAL(strcmpsafe("", NULL), 0); CU_ASSERT_EQUAL(strcmpsafe(NULL, ""), 0); CU_ASSERT(strcmpsafe(word1, NULL) > 0); CU_ASSERT(strcmpsafe(word2, NULL) > 0); CU_ASSERT(strcmpsafe(NULL, word1) < 0); CU_ASSERT(strcmpsafe(NULL, word2) < 0); } /* vim: set ft=c: */ cyrus-imapd-2.5.10/cunit/buf.testc0000644000175000017500000011654613001236020013717 00000000000000#include "config.h" #include "cunit/cunit.h" #include "prot.h" #include "xmalloc.h" #include "util.h" #include "retry.h" #include "map.h" #include "util.h" #include static void test_simple(void) { #define WORD0 "lorem" #define WORD1 "ipsum" struct buf b = BUF_INITIALIZER; const char *s; CU_ASSERT_EQUAL(b.len, 0); CU_ASSERT(b.alloc >= b.len); CU_ASSERT_EQUAL(buf_len(&b), b.len); CU_ASSERT_PTR_NULL(b.s); buf_appendcstr(&b, WORD0); buf_putc(&b, ' '); buf_appendcstr(&b, WORD1); CU_ASSERT_EQUAL(b.len, sizeof(WORD0)-1+sizeof(WORD1)-1+1); CU_ASSERT_EQUAL(buf_len(&b), b.len); CU_ASSERT(b.alloc >= b.len); CU_ASSERT_PTR_NOT_NULL(b.s); s = buf_cstring(&b); CU_ASSERT_EQUAL(b.len, sizeof(WORD0)-1+sizeof(WORD1)-1+1); CU_ASSERT_EQUAL(buf_len(&b), b.len); CU_ASSERT(b.alloc >= b.len); CU_ASSERT_PTR_NOT_NULL(b.s); CU_ASSERT_PTR_NOT_NULL(s); CU_ASSERT_STRING_EQUAL(s, WORD0" "WORD1); buf_free(&b); #undef WORD0 #undef WORD1 } static void test_map(void) { #define WORD0 "lorem" #define WORD1 "ipsum" struct buf b = BUF_INITIALIZER; const char *map; size_t len; CU_ASSERT_EQUAL(b.len, 0); CU_ASSERT(b.alloc >= b.len); CU_ASSERT_EQUAL(buf_len(&b), b.len); CU_ASSERT_PTR_NULL(b.s); buf_appendmap(&b, WORD0, sizeof(WORD0)-1); buf_putc(&b, ' '); buf_appendmap(&b, WORD1, 2); CU_ASSERT_EQUAL(b.len, sizeof(WORD0)+2); CU_ASSERT_EQUAL(buf_len(&b), b.len); CU_ASSERT(b.alloc >= b.len); CU_ASSERT_PTR_NOT_NULL(b.s); map = (void *)0xdeadbeef; len = 42; buf_getmap(&b, &map, &len); CU_ASSERT_EQUAL(b.len, sizeof(WORD0)+2); CU_ASSERT_EQUAL(buf_len(&b), b.len); CU_ASSERT_EQUAL(len, b.len); CU_ASSERT(b.alloc >= b.len); CU_ASSERT_PTR_NOT_NULL(b.s); CU_ASSERT_PTR_NOT_NULL(map); CU_ASSERT(!memcmp(map, WORD0" ip", sizeof(WORD0)+2)); buf_free(&b); #undef WORD0 #undef WORD1 } static void test_initm(void) { struct buf b = BUF_INITIALIZER; /* data thanks to hipsteripsum.me */ static const char WORD0[] = "terry richardson fanny pack"; char *s = xstrdup(WORD0); buf_initm(&b, s, sizeof(WORD0)-1); CU_ASSERT_EQUAL(b.len, sizeof(WORD0)-1); CU_ASSERT_EQUAL(buf_len(&b), b.len); CU_ASSERT(b.alloc >= b.len); CU_ASSERT_PTR_NOT_NULL(b.s); CU_ASSERT(!memcmp(b.s, WORD0, sizeof(WORD0)-1)); /* we don't free(s) - the buf_free() should do that */ buf_free(&b); } static void test_long(void) { struct buf b = BUF_INITIALIZER; int i; char *exp; #define SZ 6 #define N 10000 char tt[SZ+1]; CU_ASSERT_EQUAL(b.len, 0); CU_ASSERT(b.alloc >= b.len); CU_ASSERT_EQUAL(buf_len(&b), b.len); CU_ASSERT_PTR_NULL(b.s); for (i = 0 ; i < N ; i++) { snprintf(tt, sizeof(tt), "%c%05d", 'A'+(i%26), i); buf_appendcstr(&b, tt); } buf_cstring(&b); CU_ASSERT_EQUAL(b.len, SZ*N); CU_ASSERT_EQUAL(buf_len(&b), b.len); CU_ASSERT(b.alloc >= b.len); CU_ASSERT_PTR_NOT_NULL(b.s); exp = xmalloc(SZ*N+1); for (i = 0 ; i < N ; i++) snprintf(exp+SZ*i, SZ+1, "%c%05d", 'A'+(i%26), i); CU_ASSERT(!strcmp(b.s, exp)); free(exp); buf_free(&b); #undef N #undef SZ } static void test_setcstr(void) { #define WORD0 "lorem" struct buf b = BUF_INITIALIZER; CU_ASSERT_EQUAL(b.len, 0); CU_ASSERT(b.alloc >= b.len); CU_ASSERT_EQUAL(buf_len(&b), b.len); CU_ASSERT_PTR_NULL(b.s); buf_setcstr(&b, WORD0); buf_cstring(&b); CU_ASSERT_EQUAL(b.len, sizeof(WORD0)-1); CU_ASSERT_EQUAL(buf_len(&b), b.len); CU_ASSERT(b.alloc >= b.len); CU_ASSERT_PTR_NOT_NULL(b.s); CU_ASSERT_STRING_EQUAL(b.s, WORD0); buf_free(&b); #undef WORD0 } static void test_setmap(void) { #define WORD1 "ipsum" struct buf b = BUF_INITIALIZER; CU_ASSERT_EQUAL(b.len, 0); CU_ASSERT(b.alloc >= b.len); CU_ASSERT_EQUAL(buf_len(&b), b.len); CU_ASSERT_PTR_NULL(b.s); buf_setmap(&b, WORD1, sizeof(WORD1)-1); buf_cstring(&b); CU_ASSERT_EQUAL(b.len, sizeof(WORD1)-1); CU_ASSERT_EQUAL(buf_len(&b), b.len); CU_ASSERT(b.alloc >= b.len); CU_ASSERT_PTR_NOT_NULL(b.s); CU_ASSERT_STRING_EQUAL(b.s, WORD1); buf_free(&b); #undef WORD1 } static void test_append(void) { #define WORD0 "lorem" #define WORD1 "ipsum" struct buf b = BUF_INITIALIZER; struct buf b2 = BUF_INITIALIZER; const char *s; CU_ASSERT_EQUAL(b.len, 0); CU_ASSERT(b.alloc >= b.len); CU_ASSERT_EQUAL(buf_len(&b), b.len); CU_ASSERT_PTR_NULL(b.s); CU_ASSERT_EQUAL(b2.len, 0); CU_ASSERT(b2.alloc >= b2.len); CU_ASSERT_EQUAL(buf_len(&b2), b2.len); CU_ASSERT_PTR_NULL(b2.s); buf_setmap(&b, WORD0, sizeof(WORD0)-1); buf_setmap(&b2, WORD1, sizeof(WORD1)-1); buf_append(&b, &b2); CU_ASSERT_EQUAL(b.len, sizeof(WORD0)-1+sizeof(WORD1)-1); CU_ASSERT_EQUAL(buf_len(&b), b.len); CU_ASSERT(b.alloc >= b.len); CU_ASSERT_PTR_NOT_NULL(b.s); s = buf_cstring(&b); CU_ASSERT_STRING_EQUAL(s, WORD0""WORD1); CU_ASSERT_EQUAL(b2.len, sizeof(WORD1)-1); CU_ASSERT_EQUAL(buf_len(&b2), b2.len); CU_ASSERT(b2.alloc >= b2.len); CU_ASSERT_PTR_NOT_NULL(b2.s); s = buf_cstring(&b2); CU_ASSERT_STRING_EQUAL(s, WORD1); buf_free(&b); buf_free(&b2); #undef WORD0 #undef WORD1 } static void test_appendbit32(void) { #define HEX0 0xcafebabe #define HEX1 0xdeadbeef static const unsigned char HEX[8] = { 0xca, 0xfe, 0xba, 0xbe, 0xde, 0xad, 0xbe, 0xef }; struct buf b = BUF_INITIALIZER; CU_ASSERT_EQUAL(b.len, 0); CU_ASSERT(b.alloc >= b.len); CU_ASSERT_EQUAL(buf_len(&b), b.len); CU_ASSERT_PTR_NULL(b.s); buf_appendbit32(&b, HEX0); buf_appendbit32(&b, HEX1); CU_ASSERT_EQUAL(b.len, 8); CU_ASSERT_EQUAL(buf_len(&b), b.len); CU_ASSERT(b.alloc >= b.len); CU_ASSERT_PTR_NOT_NULL(b.s); CU_ASSERT(!memcmp(b.s, HEX, sizeof(HEX))); buf_free(&b); #undef HEX0 #undef HEX1 } static void test_reset(void) { #define WORD0 "lorem" #define WORD1 "ipsum" struct buf b = BUF_INITIALIZER; const char *s; CU_ASSERT_EQUAL(b.len, 0); CU_ASSERT(b.alloc >= b.len); CU_ASSERT_EQUAL(buf_len(&b), b.len); CU_ASSERT_PTR_NULL(b.s); buf_appendcstr(&b, WORD0); buf_reset(&b); buf_appendcstr(&b, WORD1); CU_ASSERT_EQUAL(b.len, sizeof(WORD1)-1); CU_ASSERT_EQUAL(buf_len(&b), b.len); CU_ASSERT(b.alloc >= b.len); CU_ASSERT_PTR_NOT_NULL(b.s); s = buf_cstring(&b); CU_ASSERT_PTR_NOT_NULL(s); CU_ASSERT_STRING_EQUAL(s, WORD1); buf_free(&b); #undef WORD0 #undef WORD1 } static void test_copy(void) { #define WORD0 "lorem" #define WORD1 "ipsum" struct buf b = BUF_INITIALIZER; struct buf b2 = BUF_INITIALIZER; const char *s; CU_ASSERT_EQUAL(b.len, 0); CU_ASSERT(b.alloc >= b.len); CU_ASSERT_EQUAL(buf_len(&b), b.len); CU_ASSERT_PTR_NULL(b.s); CU_ASSERT_EQUAL(b2.len, 0); CU_ASSERT(b2.alloc >= b2.len); CU_ASSERT_EQUAL(buf_len(&b2), b2.len); CU_ASSERT_PTR_NULL(b2.s); buf_setmap(&b, WORD0, sizeof(WORD0)-1); buf_setmap(&b2, WORD1, sizeof(WORD1)-1); buf_copy(&b, &b2); CU_ASSERT_EQUAL(b.len, sizeof(WORD1)-1); CU_ASSERT_EQUAL(buf_len(&b), b.len); CU_ASSERT(b.alloc >= b.len); CU_ASSERT_PTR_NOT_NULL(b.s); s = buf_cstring(&b); CU_ASSERT_STRING_EQUAL(s, WORD1); CU_ASSERT_EQUAL(b2.len, sizeof(WORD1)-1); CU_ASSERT_EQUAL(buf_len(&b2), b2.len); CU_ASSERT(b2.alloc >= b2.len); CU_ASSERT_PTR_NOT_NULL(b2.s); s = buf_cstring(&b2); CU_ASSERT_STRING_EQUAL(s, WORD1); buf_free(&b); buf_free(&b2); #undef WORD0 #undef WORD1 } static void test_move(void) { #define WORD0 "lorem" #define WORD1 "ipsummma" struct buf b = BUF_INITIALIZER; struct buf b2 = BUF_INITIALIZER; const char *s; CU_ASSERT_EQUAL(b.len, 0); CU_ASSERT(b.alloc >= b.len); CU_ASSERT_EQUAL(buf_len(&b), b.len); CU_ASSERT_PTR_NULL(b.s); CU_ASSERT_EQUAL(b2.len, 0); CU_ASSERT(b2.alloc >= b2.len); CU_ASSERT_EQUAL(buf_len(&b2), b2.len); CU_ASSERT_PTR_NULL(b2.s); buf_setmap(&b, WORD0, sizeof(WORD0)-1); buf_setmap(&b2, WORD1, sizeof(WORD1)-1); buf_move(&b, &b2); CU_ASSERT_EQUAL(b.len, sizeof(WORD1)-1); CU_ASSERT_EQUAL(buf_len(&b), b.len); CU_ASSERT(b.alloc >= b.len); CU_ASSERT_PTR_NOT_NULL(b.s); s = buf_cstring(&b); CU_ASSERT_STRING_EQUAL(s, WORD1); CU_ASSERT_EQUAL(b2.len, 0); CU_ASSERT_EQUAL(buf_len(&b2), b2.len); CU_ASSERT_EQUAL(b2.alloc, 0); CU_ASSERT_PTR_NULL(b2.s); buf_free(&b); buf_free(&b2); #undef WORD0 #undef WORD1 } static void test_printf(void) { #define WORD0 "lorem" #define WORD1 "ipsum" #define DEC0 31337 #define HEX0 0xcafebabe struct buf b = BUF_INITIALIZER; const char *s; CU_ASSERT_EQUAL(b.len, 0); CU_ASSERT(b.alloc >= b.len); CU_ASSERT_EQUAL(buf_len(&b), b.len); CU_ASSERT_PTR_NULL(b.s); buf_printf(&b, WORD0" %s 0x%x %d", WORD1, HEX0, DEC0); CU_ASSERT_EQUAL(b.len, sizeof(WORD0)+sizeof(WORD1)+16); CU_ASSERT_EQUAL(buf_len(&b), b.len); CU_ASSERT(b.alloc >= b.len); CU_ASSERT_PTR_NOT_NULL(b.s); s = buf_cstring(&b); CU_ASSERT_PTR_NOT_NULL(s); CU_ASSERT_STRING_EQUAL(s, WORD0" "WORD1" 0xcafebabe 31337"); buf_free(&b); #undef WORD0 #undef WORD1 #undef DEC0 #undef HEX0 } static void test_long_printf(void) { struct buf b = BUF_INITIALIZER; int i; const char *s; char *exp; #define SZ 6 #define N 10000 CU_ASSERT_EQUAL(b.len, 0); CU_ASSERT(b.alloc >= b.len); CU_ASSERT_EQUAL(buf_len(&b), b.len); CU_ASSERT_PTR_NULL(b.s); exp = xmalloc(SZ*N+1); for (i = 0 ; i < N ; i++) snprintf(exp+SZ*i, SZ+1, "%c%05d", 'A'+(i%26), i); buf_printf(&b, "x%sy", exp); s = buf_cstring(&b); CU_ASSERT_EQUAL(b.len, SZ*N+2); CU_ASSERT_EQUAL(buf_len(&b), b.len); CU_ASSERT(b.alloc >= b.len); CU_ASSERT_PTR_NOT_NULL(b.s); CU_ASSERT_PTR_NOT_NULL(s); CU_ASSERT_EQUAL(s[0], 'x'); CU_ASSERT(!memcmp(s+1, exp, SZ*N)); CU_ASSERT_EQUAL(s[SZ*N+1], 'y'); buf_free(&b); free(exp); #undef N #undef SZ } static void test_replace_all(void) { #define WORD0 "lorem" #define WORD0REP "LAUREN BACALL" #define WORD0REP2 "L0R3M" #define WORD0REP3 "LRM" #define WORD0REP4 "XloremY" #define WORD1 "ipsum" #define WORD1 "ipsum" #define WORD2 "dolor" #define WORD3 "sit" #define WORD4 "amet" struct buf b = BUF_INITIALIZER; unsigned int n; char *buf_s; CU_ASSERT_EQUAL(b.len, 0); CU_ASSERT(b.alloc >= b.len); CU_ASSERT_EQUAL(buf_len(&b), b.len); CU_ASSERT_PTR_NULL(b.s); /* simple test: a single replacement */ buf_reset(&b); buf_appendcstr(&b, WORD0" "WORD1); buf_cstring(&b); CU_ASSERT_EQUAL(b.len, sizeof(WORD0" "WORD1)-1); CU_ASSERT_EQUAL(buf_len(&b), b.len); CU_ASSERT(b.alloc >= b.len); CU_ASSERT_PTR_NOT_NULL(b.s); CU_ASSERT_STRING_EQUAL(b.s, WORD0" "WORD1); n = buf_replace_all(&b, WORD0, WORD0REP); CU_ASSERT_EQUAL(n, 1); CU_ASSERT_EQUAL(b.len, sizeof(WORD0REP" "WORD1)-1); CU_ASSERT_EQUAL(buf_len(&b), b.len); CU_ASSERT(b.alloc >= b.len); CU_ASSERT_PTR_NOT_NULL(b.s); CU_ASSERT_STRING_EQUAL(b.s, WORD0REP" "WORD1); /* simple test: failure to match */ buf_reset(&b); buf_appendcstr(&b, WORD0" "WORD1); buf_cstring(&b); CU_ASSERT_EQUAL(b.len, sizeof(WORD0" "WORD1)-1); CU_ASSERT_EQUAL(buf_len(&b), b.len); CU_ASSERT(b.alloc >= b.len); CU_ASSERT_PTR_NOT_NULL(b.s); CU_ASSERT_STRING_EQUAL(b.s, WORD0" "WORD1); n = buf_replace_all(&b, WORD4, WORD0REP); CU_ASSERT_EQUAL(n, 0); CU_ASSERT_EQUAL(b.len, sizeof(WORD0" "WORD1)-1); CU_ASSERT_EQUAL(buf_len(&b), b.len); CU_ASSERT(b.alloc >= b.len); CU_ASSERT_PTR_NOT_NULL(b.s); CU_ASSERT_STRING_EQUAL(b.s, WORD0" "WORD1); /* a replacement which doesn't change the size */ buf_reset(&b); buf_appendcstr(&b, WORD0" "WORD1); buf_cstring(&b); CU_ASSERT_EQUAL(b.len, sizeof(WORD0" "WORD1)-1); CU_ASSERT_EQUAL(buf_len(&b), b.len); CU_ASSERT(b.alloc >= b.len); CU_ASSERT_PTR_NOT_NULL(b.s); CU_ASSERT_STRING_EQUAL(b.s, WORD0" "WORD1); buf_s = b.s; n = buf_replace_all(&b, WORD0, WORD0REP2); CU_ASSERT_EQUAL(n, 1); CU_ASSERT_EQUAL(b.len, sizeof(WORD0REP2" "WORD1)-1); CU_ASSERT_EQUAL(buf_len(&b), b.len); CU_ASSERT(b.alloc >= b.len); CU_ASSERT_PTR_NOT_NULL(b.s); CU_ASSERT_PTR_EQUAL(b.s, buf_s); /* no size change => no realloc */ CU_ASSERT_STRING_EQUAL(b.s, WORD0REP2" "WORD1); /* a replacement which shrinks the size */ buf_reset(&b); buf_appendcstr(&b, WORD0" "WORD1); buf_cstring(&b); CU_ASSERT_EQUAL(b.len, sizeof(WORD0" "WORD1)-1); CU_ASSERT_EQUAL(buf_len(&b), b.len); CU_ASSERT(b.alloc >= b.len); CU_ASSERT_PTR_NOT_NULL(b.s); CU_ASSERT_STRING_EQUAL(b.s, WORD0" "WORD1); /* a replacement with an empty string */ buf_reset(&b); buf_appendcstr(&b, WORD0" "WORD1); buf_cstring(&b); CU_ASSERT_EQUAL(b.len, sizeof(WORD0" "WORD1)-1); CU_ASSERT_EQUAL(buf_len(&b), b.len); CU_ASSERT(b.alloc >= b.len); CU_ASSERT_PTR_NOT_NULL(b.s); CU_ASSERT_STRING_EQUAL(b.s, WORD0" "WORD1); buf_s = b.s; n = buf_replace_all(&b, WORD0, ""); CU_ASSERT_EQUAL(n, 1); CU_ASSERT_EQUAL(b.len, sizeof(" "WORD1)-1); CU_ASSERT_EQUAL(buf_len(&b), b.len); CU_ASSERT(b.alloc >= b.len); CU_ASSERT_PTR_NOT_NULL(b.s); CU_ASSERT_PTR_EQUAL(b.s, buf_s); /* no size change => no realloc */ CU_ASSERT_STRING_EQUAL(b.s, " "WORD1); /* a replacement with a NULL string */ buf_reset(&b); buf_appendcstr(&b, WORD0" "WORD1); buf_cstring(&b); CU_ASSERT_EQUAL(b.len, sizeof(WORD0" "WORD1)-1); CU_ASSERT_EQUAL(buf_len(&b), b.len); CU_ASSERT(b.alloc >= b.len); CU_ASSERT_PTR_NOT_NULL(b.s); CU_ASSERT_STRING_EQUAL(b.s, WORD0" "WORD1); buf_s = b.s; n = buf_replace_all(&b, WORD0, NULL); CU_ASSERT_EQUAL(n, 1); CU_ASSERT_EQUAL(b.len, sizeof(" "WORD1)-1); CU_ASSERT_EQUAL(buf_len(&b), b.len); CU_ASSERT(b.alloc >= b.len); CU_ASSERT_PTR_NOT_NULL(b.s); CU_ASSERT_PTR_EQUAL(b.s, buf_s); /* no size change => no realloc */ CU_ASSERT_STRING_EQUAL(b.s, " "WORD1); /* multiple replacements, including abutted ones */ buf_reset(&b); buf_appendcstr(&b, WORD0" "WORD1" "WORD2" "WORD0" "WORD3" "WORD0""WORD0" "WORD4); buf_cstring(&b); CU_ASSERT_EQUAL(b.len, sizeof(WORD0" "WORD1" "WORD2" "WORD0" "WORD3" "WORD0""WORD0" "WORD4)-1); CU_ASSERT_EQUAL(buf_len(&b), b.len); CU_ASSERT(b.alloc >= b.len); CU_ASSERT_PTR_NOT_NULL(b.s); CU_ASSERT_STRING_EQUAL(b.s, WORD0" "WORD1" "WORD2" "WORD0" "WORD3" "WORD0""WORD0" "WORD4); n = buf_replace_all(&b, WORD0, WORD0REP2); CU_ASSERT_EQUAL(n, 4); CU_ASSERT_EQUAL(b.len, sizeof(WORD0REP2" "WORD1" "WORD2" "WORD0REP2" "WORD3" "WORD0REP2""WORD0REP2" "WORD4)-1); CU_ASSERT_EQUAL(buf_len(&b), b.len); CU_ASSERT(b.alloc >= b.len); CU_ASSERT_PTR_NOT_NULL(b.s); CU_ASSERT_STRING_EQUAL(b.s, WORD0REP2" "WORD1" "WORD2" "WORD0REP2" "WORD3" "WORD0REP2""WORD0REP2" "WORD4); /* multiple replacements with a replacement which contains the match */ buf_reset(&b); buf_appendcstr(&b, WORD0" "WORD1" "WORD2" "WORD0" "WORD3" "WORD0""WORD0" "WORD4); buf_cstring(&b); CU_ASSERT_EQUAL(b.len, sizeof(WORD0" "WORD1" "WORD2" "WORD0" "WORD3" "WORD0""WORD0" "WORD4)-1); CU_ASSERT_EQUAL(buf_len(&b), b.len); CU_ASSERT(b.alloc >= b.len); CU_ASSERT_PTR_NOT_NULL(b.s); CU_ASSERT_STRING_EQUAL(b.s, WORD0" "WORD1" "WORD2" "WORD0" "WORD3" "WORD0""WORD0" "WORD4); n = buf_replace_all(&b, WORD0, WORD0REP4); CU_ASSERT_EQUAL(n, 4); CU_ASSERT_EQUAL(b.len, sizeof(WORD0REP4" "WORD1" "WORD2" "WORD0REP4" "WORD3" "WORD0REP4""WORD0REP4" "WORD4)-1); CU_ASSERT_EQUAL(buf_len(&b), b.len); CU_ASSERT(b.alloc >= b.len); CU_ASSERT_PTR_NOT_NULL(b.s); CU_ASSERT_STRING_EQUAL(b.s, WORD0REP4" "WORD1" "WORD2" "WORD0REP4" "WORD3" "WORD0REP4""WORD0REP4" "WORD4); buf_free(&b); #undef WORD0 #undef WORD0REP #undef WORD0REP2 #undef WORD0REP3 #undef WORD0REP4 #undef WORD1 #undef WORD2 #undef WORD3 #undef WORD4 } /* we use buf_init_ro() instead of buf_appendcstr() to test * the case where the input buffer is not a C string before * caling buf_replace_*() */ #define TESTCASE_START(in, reg, rep, expn, exp) \ { \ static const char _in[] = in; \ static const char _reg[] = reg; \ static const char *_rep = rep; \ static const int _expn = expn; \ static const char _exp[] = exp; \ struct buf b = BUF_INITIALIZER; \ regex_t re; \ unsigned int n; \ int r; \ \ buf_init_ro(&b, _in, sizeof(_in)-1); \ CU_ASSERT_EQUAL(b.len, sizeof(_in)-1); \ CU_ASSERT_EQUAL(buf_len(&b), b.len); \ CU_ASSERT_PTR_NOT_NULL(b.s); \ CU_ASSERT_STRING_EQUAL(b.s, _in); \ \ r = regcomp(&re, _reg, REG_EXTENDED); \ CU_ASSERT_EQUAL(r, 0); #define TESTCASE_MIDDLE \ n = buf_replace_one_re(&b, &re, _rep); #define TESTCASE_END \ CU_ASSERT_EQUAL(n, _expn); \ CU_ASSERT_EQUAL(b.len, sizeof(_exp)-1); \ CU_ASSERT_EQUAL(buf_len(&b), b.len); \ CU_ASSERT(b.alloc >= b.len); \ CU_ASSERT_PTR_NOT_NULL(b.s); \ CU_ASSERT_STRING_EQUAL(b.s, _exp); \ regfree(&re); \ buf_free(&b); \ } #define TESTCASE(in, reg, rep, expn, exp) \ TESTCASE_START(in, reg, rep, expn, exp) \ TESTCASE_MIDDLE \ TESTCASE_END static void test_replace_one_re(void) { /* data thanks to hipsteripsum.me */ #define WORD0 "bespoke" #define WORD0_RE "be[a-df-z]+e" #define WORD0REP "butcher" #define WORD0REP2 "BeSp0K3" #define WORD0REP3 "BpK" #define WORD0REP4 "XbespokeY" #define WORD1 "tattooed" #define WORD2 "fap" #define WORD3 "keffiyeh" #define WORD4 "biodiesel" #define WORD4_RE "[a-z]iod[a-z]+" const char *buf_s; /* simple test: a single replacement */ TESTCASE(WORD0" "WORD1, WORD0_RE, WORD0REP, 1, WORD0REP" "WORD1); /* simple test: failure to match */ TESTCASE_START(WORD0" "WORD1, WORD4_RE, WORD0REP, 0, WORD0" "WORD1); TESTCASE_MIDDLE buf_cstring(&b); TESTCASE_END /* a replacement which doesn't change the size */ TESTCASE_START(WORD0" "WORD1, WORD0_RE, WORD0REP2, 1, WORD0REP2" "WORD1); buf_s = buf_cstring(&b); TESTCASE_MIDDLE CU_ASSERT_PTR_EQUAL(buf_cstring(&b), buf_s); /* no size change => no realloc */ TESTCASE_END /* a replacement which shrinks the size */ TESTCASE_START(WORD0" "WORD1, WORD0_RE, WORD0REP3, 1, WORD0REP3" "WORD1); buf_s = buf_cstring(&b); TESTCASE_MIDDLE CU_ASSERT_PTR_EQUAL(buf_cstring(&b), buf_s); /* no size change => no realloc */ TESTCASE_END /* a replacement with an empty string */ TESTCASE(WORD0" "WORD1, WORD0_RE, "", 1, " "WORD1); /* a replacement with a NULL string */ TESTCASE(WORD0" "WORD1, WORD0_RE, NULL, 1, " "WORD1); /* multiple matches, including abutted ones */ TESTCASE(WORD0" "WORD1" "WORD2" "WORD0" "WORD3" "WORD0""WORD0" "WORD4, WORD0_RE, WORD0REP2, 1, WORD0REP2" "WORD1" "WORD2" "WORD0" "WORD3" "WORD0""WORD0" "WORD4); /* multiple matches with a replacement which contains the match */ TESTCASE(WORD0" "WORD1" "WORD2" "WORD0" "WORD3" "WORD0""WORD0" "WORD4, WORD0_RE, WORD0REP4, 1, WORD0REP4" "WORD1" "WORD2" "WORD0" "WORD3" "WORD0""WORD0" "WORD4); #undef WORD0 #undef WORD0REP #undef WORD0REP2 #undef WORD0REP3 #undef WORD0REP4 #undef WORD1 #undef WORD2 #undef WORD3 #undef WORD4 } #undef TESTCASE_MIDDLE #define TESTCASE_MIDDLE \ n = buf_replace_all_re(&b, &re, _rep); static void test_replace_all_re(void) { /* data thanks to hipsteripsum.me */ #define WORD0 "bespoke" #define WORD0_RE "be[a-df-z]+e" #define WORD0REP "butcher" #define WORD0REP2 "BeSp0K3" #define WORD0REP3 "BpK" #define WORD0REP4 "XbespokeY" #define WORD1 "tattooed" #define WORD2 "fap" #define WORD3 "keffiyeh" #define WORD4 "biodiesel" #define WORD4_RE "[a-z]iod[a-z]+" const char *buf_s; /* simple test: a single replacement */ TESTCASE(WORD0" "WORD1, WORD0_RE, WORD0REP, 1, WORD0REP" "WORD1); /* simple test: failure to match */ TESTCASE_START(WORD0" "WORD1, WORD4_RE, WORD0REP, 0, WORD0" "WORD1); TESTCASE_MIDDLE buf_cstring(&b); TESTCASE_END /* a replacement which doesn't change the size */ TESTCASE_START(WORD0" "WORD1, WORD0_RE, WORD0REP2, 1, WORD0REP2" "WORD1); buf_s = buf_cstring(&b); TESTCASE_MIDDLE CU_ASSERT_PTR_EQUAL(buf_cstring(&b), buf_s); /* no size change => no realloc */ TESTCASE_END /* a replacement which shrinks the size */ TESTCASE_START(WORD0" "WORD1, WORD0_RE, WORD0REP3, 1, WORD0REP3" "WORD1); buf_s = buf_cstring(&b); TESTCASE_MIDDLE CU_ASSERT_PTR_EQUAL(buf_cstring(&b), buf_s); /* no size change => no realloc */ TESTCASE_END /* a replacement with an empty string */ TESTCASE(WORD0" "WORD1, WORD0_RE, "", 1, " "WORD1); /* a replacement with a NULL string */ TESTCASE(WORD0" "WORD1, WORD0_RE, NULL, 1, " "WORD1); /* multiple matches, including abutted ones */ TESTCASE(WORD0" "WORD1" "WORD2" "WORD0" "WORD3" "WORD0""WORD0" "WORD4, WORD0_RE, WORD0REP2, 4, WORD0REP2" "WORD1" "WORD2" "WORD0REP2" "WORD3" "WORD0REP2""WORD0REP2" "WORD4); /* multiple matches with a replacement which contains the match */ TESTCASE(WORD0" "WORD1" "WORD2" "WORD0" "WORD3" "WORD0""WORD0" "WORD4, WORD0_RE, WORD0REP4, 4, WORD0REP4" "WORD1" "WORD2" "WORD0REP4" "WORD3" "WORD0REP4""WORD0REP4" "WORD4); #undef WORD0 #undef WORD0REP #undef WORD0REP2 #undef WORD0REP3 #undef WORD0REP4 #undef WORD1 #undef WORD2 #undef WORD3 #undef WORD4 } #undef TESTCASE_START #undef TESTCASE_MIDDLE #undef TESTCASE_END #undef TESTCASE #define TESTCASE(in, off, rep, exp) \ { \ static const char _in[] = in; \ int _off = off; \ static const char _rep[] = rep; \ static const char _exp[] = exp; \ struct buf b = BUF_INITIALIZER; \ \ buf_appendcstr(&b, _in); \ buf_cstring(&b); \ CU_ASSERT_EQUAL(b.len, sizeof(_in)-1); \ CU_ASSERT_PTR_NOT_NULL(b.s); \ CU_ASSERT_STRING_EQUAL(b.s, _in); \ \ buf_insertcstr(&b, _off, _rep); \ CU_ASSERT_EQUAL(b.len, sizeof(_exp)-1); \ CU_ASSERT(b.alloc >= b.len); \ buf_cstring(&b); \ CU_ASSERT_PTR_NOT_NULL(b.s); \ CU_ASSERT_STRING_EQUAL(b.s, _exp); \ buf_free(&b); \ } static void test_insertcstr(void) { /* data thanks to hipsteripsum.me */ #define WORD0 "gastropub" #define WORD1 "vegan brunch" #define WORD2 "portland" TESTCASE(WORD0" "WORD2, 0, WORD1"\t", WORD1"\t"WORD0" "WORD2); TESTCASE(WORD0" "WORD2, sizeof(WORD0)-1, "\t"WORD1, WORD0"\t"WORD1" "WORD2); TESTCASE(WORD0" "WORD2, sizeof(WORD0" "WORD2)-1, "\t"WORD1, WORD0" "WORD2"\t"WORD1); TESTCASE("", 0, WORD1, WORD1); TESTCASE("", 1, WORD1, ""); #undef WORD0 #undef WORD1 #undef WORD2 } #undef TESTCASE #define TESTCASE(in, off, rep, exp) \ { \ static const char _in[] = in; \ int _off = off; \ static const char _rep[] = rep; \ static const char _exp[] = exp; \ struct buf b = BUF_INITIALIZER; \ \ buf_appendcstr(&b, _in); \ buf_cstring(&b); \ CU_ASSERT_EQUAL(b.len, sizeof(_in)-1); \ CU_ASSERT_PTR_NOT_NULL(b.s); \ CU_ASSERT_STRING_EQUAL(b.s, _in); \ \ buf_insertmap(&b, _off, _rep, sizeof(_rep)-1); \ CU_ASSERT_EQUAL(b.len, sizeof(_exp)-1); \ CU_ASSERT(b.alloc >= b.len); \ buf_cstring(&b); \ CU_ASSERT_PTR_NOT_NULL(b.s); \ CU_ASSERT_STRING_EQUAL(b.s, _exp); \ buf_free(&b); \ } static void test_insertmap(void) { /* data thanks to hipsteripsum.me */ #define WORD0 "gastropub" #define WORD1 "vegan brunch" #define WORD2 "portland" TESTCASE(WORD0" "WORD2, 0, WORD1"\t", WORD1"\t"WORD0" "WORD2); TESTCASE(WORD0" "WORD2, sizeof(WORD0)-1, "\t"WORD1, WORD0"\t"WORD1" "WORD2); TESTCASE(WORD0" "WORD2, sizeof(WORD0" "WORD2)-1, "\t"WORD1, WORD0" "WORD2"\t"WORD1); TESTCASE("", 0, WORD1, WORD1); TESTCASE("", 1, WORD1, ""); #undef WORD0 #undef WORD1 #undef WORD2 } #undef TESTCASE #define TESTCASE(in, off, rep, exp) \ { \ static const char _in[] = in; \ int _off = off; \ static const char _rep[] = rep; \ struct buf _repb = BUF_INITIALIZER; \ static const char _exp[] = exp; \ struct buf b = BUF_INITIALIZER; \ \ buf_appendmap(&_repb, _rep, sizeof(_rep)-1); \ \ buf_appendcstr(&b, _in); \ buf_cstring(&b); \ CU_ASSERT_EQUAL(b.len, sizeof(_in)-1); \ CU_ASSERT_PTR_NOT_NULL(b.s); \ CU_ASSERT_STRING_EQUAL(b.s, _in); \ \ buf_insert(&b, _off, &_repb); \ CU_ASSERT_EQUAL(b.len, sizeof(_exp)-1); \ CU_ASSERT(b.alloc >= b.len); \ buf_cstring(&b); \ CU_ASSERT_PTR_NOT_NULL(b.s); \ CU_ASSERT_STRING_EQUAL(b.s, _exp); \ buf_free(&b); \ buf_free(&_repb); \ } static void test_insert(void) { /* data thanks to hipsteripsum.me */ #define WORD0 "gastropub" #define WORD1 "brunch" #define WORD2 "portland" TESTCASE(WORD0" "WORD2, 0, WORD1"\t", WORD1"\t"WORD0" "WORD2); TESTCASE(WORD0" "WORD2, sizeof(WORD0)-1, "\t"WORD1, WORD0"\t"WORD1" "WORD2); TESTCASE(WORD0" "WORD2, sizeof(WORD0" "WORD2)-1, "\t"WORD1, WORD0" "WORD2"\t"WORD1); TESTCASE("", 0, WORD1, WORD1); TESTCASE("", 1, WORD1, ""); #undef WORD0 #undef WORD1 #undef WORD2 } #undef TESTCASE #define TESTCASE(in, off, xlen, exp) \ { \ static const char _in[] = in; \ int _off = off; \ int _len = xlen; \ static const char _exp[] = exp; \ struct buf b = BUF_INITIALIZER; \ \ buf_appendcstr(&b, _in); \ buf_cstring(&b); \ CU_ASSERT_EQUAL(b.len, sizeof(_in)-1); \ CU_ASSERT_PTR_NOT_NULL(b.s); \ CU_ASSERT_STRING_EQUAL(b.s, _in); \ \ buf_remove(&b, _off, _len); \ CU_ASSERT_EQUAL(b.len, sizeof(_exp)-1); \ CU_ASSERT(b.alloc >= b.len); \ buf_cstring(&b); \ CU_ASSERT_PTR_NOT_NULL(b.s); \ CU_ASSERT_STRING_EQUAL(b.s, _exp); \ buf_free(&b); \ } static void test_remove(void) { /* data thanks to hipsteripsum.me */ #define WORD0 "fingerstache" #define WORD1 "scenester" #define WORD2 "ennui" TESTCASE(WORD0" "WORD1"\t"WORD2, 0, sizeof(WORD0), WORD1"\t"WORD2); TESTCASE(WORD0" "WORD1"\t"WORD2, 0, 0, WORD0" "WORD1"\t"WORD2); TESTCASE(WORD0" "WORD1"\t"WORD2, sizeof(WORD0), sizeof(WORD1), WORD0" "WORD2); TESTCASE(WORD0" "WORD1"\t"WORD2, sizeof(WORD0)+sizeof(WORD1), sizeof(WORD2)-1, WORD0" "WORD1"\t"); TESTCASE(WORD0" "WORD1"\t"WORD2, sizeof(WORD0)+sizeof(WORD1), sizeof(WORD2)-1+20, WORD0" "WORD1"\t"); TESTCASE(WORD0" "WORD1"\t"WORD2, 0, sizeof(WORD0" "WORD1"\t"WORD2)-1, ""); TESTCASE("", 0, 1, ""); #undef WORD0 #undef WORD1 #undef WORD2 } #undef TESTCASE static void test_truncate(void) { #define WORD0 "lorem" #define WORD1 "ipsum" struct buf b = BUF_INITIALIZER; unsigned int i; CU_ASSERT_EQUAL(b.len, 0); CU_ASSERT(b.alloc >= b.len); CU_ASSERT_EQUAL(buf_len(&b), b.len); CU_ASSERT_PTR_NULL(b.s); /* buf_truncate() which shortens the buffer */ buf_reset(&b); buf_appendcstr(&b, WORD0" "WORD1); buf_cstring(&b); CU_ASSERT_EQUAL(b.len, sizeof(WORD0" "WORD1)-1); CU_ASSERT_EQUAL(buf_len(&b), b.len); CU_ASSERT(b.alloc >= b.len); CU_ASSERT_PTR_NOT_NULL(b.s); CU_ASSERT_STRING_EQUAL(b.s, WORD0" "WORD1); buf_truncate(&b, sizeof(WORD0)-1); buf_cstring(&b); CU_ASSERT_EQUAL(b.len, sizeof(WORD0)-1); CU_ASSERT_EQUAL(buf_len(&b), b.len); CU_ASSERT(b.alloc >= b.len); CU_ASSERT_PTR_NOT_NULL(b.s); CU_ASSERT_STRING_EQUAL(b.s, WORD0); /* buf_truncate() which extends and zero-fills the buffer */ buf_reset(&b); buf_appendcstr(&b, WORD0" "WORD1); buf_cstring(&b); CU_ASSERT_EQUAL(b.len, sizeof(WORD0" "WORD1)-1); CU_ASSERT_EQUAL(buf_len(&b), b.len); CU_ASSERT(b.alloc >= b.len); CU_ASSERT_PTR_NOT_NULL(b.s); CU_ASSERT_STRING_EQUAL(b.s, WORD0" "WORD1); buf_truncate(&b, sizeof(WORD0" "WORD1)-1+2048); buf_cstring(&b); CU_ASSERT_EQUAL(b.len, sizeof(WORD0" "WORD1)-1+2048); CU_ASSERT_EQUAL(buf_len(&b), b.len); CU_ASSERT(b.alloc >= b.len); CU_ASSERT_PTR_NOT_NULL(b.s); CU_ASSERT_STRING_EQUAL(b.s, WORD0" "WORD1); for (i=sizeof(WORD0" "WORD1)-1; i 0); /* compare different strings where one is * an initial subset of the other */ buf_reset(&a); buf_appendcstr(&a, WORD0SUB); buf_reset(&b); buf_appendcstr(&b, WORD0); CU_ASSERT_PTR_NOT_NULL(a.s); CU_ASSERT_EQUAL(a.len, sizeof(WORD0SUB)-1); CU_ASSERT_PTR_NOT_NULL(b.s); CU_ASSERT_EQUAL(b.len, sizeof(WORD0)-1); d = buf_cmp(&a, &b); CU_ASSERT(d < 0); d = buf_cmp(&b, &a); CU_ASSERT(d > 0); buf_free(&a); buf_free(&b); #undef WORD0 #undef WORD0SUB #undef WORD1 } static void test_cow(void) { static const char DATA0[] = "LoRem"; struct buf b = BUF_INITIALIZER; CU_ASSERT_EQUAL(b.len, 0); CU_ASSERT(b.alloc >= b.len); CU_ASSERT_EQUAL(buf_len(&b), b.len); CU_ASSERT_PTR_NULL(b.s); buf_init_ro(&b, DATA0, sizeof(DATA0)-1); CU_ASSERT_EQUAL(b.len, sizeof(DATA0)-1); CU_ASSERT_EQUAL(b.alloc, 0); CU_ASSERT_EQUAL(buf_len(&b), b.len); CU_ASSERT_PTR_EQUAL(b.s, (char *)DATA0); buf_putc(&b, 'X'); CU_ASSERT_EQUAL(b.len, sizeof(DATA0)-1+1); CU_ASSERT(b.alloc >= b.len); CU_ASSERT_EQUAL(buf_len(&b), b.len); CU_ASSERT_PTR_NOT_EQUAL(b.s, (char *)DATA0); buf_free(&b); } static void test_cow2(void) { static const char DATA0[] = "cardigan umami"; struct buf b = BUF_INITIALIZER; CU_ASSERT_EQUAL(b.len, 0); CU_ASSERT(b.alloc >= b.len); CU_ASSERT_EQUAL(buf_len(&b), b.len); CU_ASSERT_PTR_NULL(b.s); buf_init_ro_cstr(&b, DATA0); CU_ASSERT_EQUAL(b.len, sizeof(DATA0)-1); CU_ASSERT_EQUAL(b.alloc, 0); CU_ASSERT_EQUAL(buf_len(&b), b.len); CU_ASSERT_PTR_EQUAL(b.s, (char *)DATA0); buf_putc(&b, 'X'); CU_ASSERT_EQUAL(b.len, sizeof(DATA0)-1+1); CU_ASSERT(b.alloc >= b.len); CU_ASSERT_EQUAL(buf_len(&b), b.len); CU_ASSERT_PTR_NOT_EQUAL(b.s, (char *)DATA0); buf_free(&b); } static void test_findchar(void) { struct buf b = BUF_INITIALIZER; int i; buf_appendcstr(&b, "ABCDEF"); /* Note: buf is NOT a C-string so should get a Valgrind * error if findchar() runs off the end */ i = buf_findchar(&b, 0, 'A'); CU_ASSERT_EQUAL(i, 0); i = buf_findchar(&b, 0, 'C'); CU_ASSERT_EQUAL(i, 2); i = buf_findchar(&b, 0, 'F'); CU_ASSERT_EQUAL(i, 5); i = buf_findchar(&b, 0, 'X'); CU_ASSERT_EQUAL(i, -1); i = buf_findchar(&b, 0, -1); CU_ASSERT_EQUAL(i, -1); i = buf_findchar(&b, 2, 'A'); CU_ASSERT_EQUAL(i, -1); i = buf_findchar(&b, 2, 'C'); CU_ASSERT_EQUAL(i, 2); i = buf_findchar(&b, 2, 'F'); CU_ASSERT_EQUAL(i, 5); i = buf_findchar(&b, 2, 'X'); CU_ASSERT_EQUAL(i, -1); i = buf_findchar(&b, 2, -1); CU_ASSERT_EQUAL(i, -1); i = buf_findchar(&b, 6, 'F'); CU_ASSERT_EQUAL(i, -1); i = buf_findchar(&b, 6, 'X'); CU_ASSERT_EQUAL(i, -1); buf_free(&b); } static void test_cowappendmap(void) { /* data thanks to hipsteripsum.me */ #define WORD0 "beard" #define WORD1 "narwhal" struct buf b = BUF_INITIALIZER; buf_cowappendmap(&b, WORD0, sizeof(WORD0)-1); CU_ASSERT_EQUAL(b.len, sizeof(WORD0)-1); CU_ASSERT(b.alloc == 0); CU_ASSERT_PTR_NOT_NULL(b.s); CU_ASSERT(!memcmp(b.s, WORD0, sizeof(WORD0)-1)); buf_cowappendmap(&b, WORD1, sizeof(WORD1)-1); CU_ASSERT_EQUAL(b.len, sizeof(WORD0)-1+sizeof(WORD1)-1); CU_ASSERT(b.alloc >= b.len); CU_ASSERT_PTR_NOT_NULL(b.s); CU_ASSERT(!memcmp(b.s, WORD0""WORD1, sizeof(WORD0)-1+sizeof(WORD1)-1)); buf_free(&b); #undef WORD0 #undef WORD1 } static void test_cowappendfree(void) { /* data thanks to hipsteripsum.me */ #define WORD0 "beard" #define WORD1 "narwhal" struct buf b = BUF_INITIALIZER; char *s; s = xstrdup(WORD0); buf_cowappendfree(&b, s, strlen(s)); CU_ASSERT_EQUAL(b.len, sizeof(WORD0)-1); CU_ASSERT(b.alloc >= b.len); CU_ASSERT_PTR_NOT_NULL(b.s); CU_ASSERT(!memcmp(b.s, WORD0, sizeof(WORD0)-1)); s = xstrdup(WORD1); buf_cowappendfree(&b, s, strlen(s)); CU_ASSERT_EQUAL(b.len, sizeof(WORD0)-1+sizeof(WORD1)-1); CU_ASSERT(b.alloc >= b.len); CU_ASSERT_PTR_NOT_NULL(b.s); CU_ASSERT(!memcmp(b.s, WORD0""WORD1, sizeof(WORD0)-1+sizeof(WORD1)-1)); /* we don't free s, buf_free() should do that */ buf_free(&b); #undef WORD0 #undef WORD1 } static void test_bufprint(void) { struct buf b = BUF_INITIALIZER; struct protstream *outstream; int i; outstream = prot_writebuf(&b); for (i = 0; i < 5000; i++) { prot_putc('.', outstream); } prot_flush(outstream); prot_free(outstream); CU_ASSERT_EQUAL(b.len, 5000); buf_free(&b); } #ifdef HAVE_ZLIB static void test_compress(void) { struct buf b = BUF_INITIALIZER; static const char DATA0[] = "LoRem"; int r; buf_printf(&b, "%s", DATA0); CU_ASSERT_STRING_EQUAL(buf_cstring(&b), DATA0); r = buf_deflate(&b, Z_DEFAULT_COMPRESSION, DEFLATE_RAW); CU_ASSERT_EQUAL(r, 0); CU_ASSERT_STRING_NOT_EQUAL(buf_cstring(&b), DATA0); r = buf_inflate(&b, DEFLATE_RAW); CU_ASSERT_EQUAL(r, 0); CU_ASSERT_STRING_EQUAL(buf_cstring(&b), DATA0); buf_free(&b); } #endif static void test_replace_shorten(void) { struct buf b = BUF_INITIALIZER; buf_appendcstr(&b, "dreamcatcher skateboard"); /* Test that buf_replace_all() does not wander off the end of the * buffer if a replacement operation at the end of the string * shortens the string - this would show up in Valgrind. */ buf_replace_all(&b, "skateboard", "truck"); CU_ASSERT_STRING_EQUAL(b.s, "dreamcatcher truck"); buf_free(&b); } static void test_replace_cow_cstr(void) { struct buf b = BUF_INITIALIZER; static const char DATA0[] = "food truck vegan"; buf_init_ro_cstr(&b, DATA0); CU_ASSERT_PTR_NOT_NULL(b.s); CU_ASSERT_PTR_EQUAL(b.s, DATA0); CU_ASSERT_STRING_EQUAL(b.s, "food truck vegan"); /* There was a bug where buf_replace_all() was enforcing that * the buffer was a C string but not that it was writable, which * is often the same but isn't after a buf_init_ro_cstr(). With * the bug, buf_replace_all() would SEGV */ buf_replace_all(&b, "truck", "vinyl"); CU_ASSERT_PTR_NOT_NULL(b.s); CU_ASSERT_PTR_NOT_EQUAL(b.s, DATA0); CU_ASSERT_STRING_EQUAL(b.s, "food vinyl vegan"); buf_free(&b); } static void test_findline(void) { struct buf b = BUF_INITIALIZER; int r; #define WORD0 "etsy" #define WORD1 "quinoa" #define WORD2 "dreamcatcher" #define WORD3 "shoreditch" #define WORD4 "williamsburg" #define WORD5 "brooklyn" #define WORDU "banksy" buf_appendcstr(&b, WORD0"\n"WORD1"\n"WORD2"\n"WORD3" "WORD4"\n"WORD5"\n"); CU_ASSERT_EQUAL(b.len, sizeof(WORD0)+sizeof(WORD1)+sizeof(WORD2)+ sizeof(WORD3)+sizeof(WORD4)+sizeof(WORD5)); /* a zero length line is always unfound */ r = buf_findline(&b, ""); CU_ASSERT_EQUAL(r, -1); r = buf_findline(&b, "\n"); CU_ASSERT_EQUAL(r, -1); /* a line which is not present is unfound */ r = buf_findline(&b, WORDU); CU_ASSERT_EQUAL(r, -1); r = buf_findline(&b, WORDU"\n"); CU_ASSERT_EQUAL(r, -1); /* only the first line of the needle is searched for */ r = buf_findline(&b, WORD1"\n"WORD3"\n"); CU_ASSERT_EQUAL(r, sizeof(WORD0)); /* the very first line is found */ r = buf_findline(&b, WORD0); CU_ASSERT_EQUAL(r, 0); r = buf_findline(&b, WORD0"\n"); CU_ASSERT_EQUAL(r, 0); /* a line which is neither first nor last is found */ r = buf_findline(&b, WORD1); CU_ASSERT_EQUAL(r, sizeof(WORD0)); r = buf_findline(&b, WORD1"\n"); CU_ASSERT_EQUAL(r, sizeof(WORD0)); /* a word which is a subset of a present line, is unfound */ r = buf_findline(&b, WORD3); CU_ASSERT_EQUAL(r, -1); r = buf_findline(&b, WORD3"\n"); CU_ASSERT_EQUAL(r, -1); r = buf_findline(&b, WORD4); CU_ASSERT_EQUAL(r, -1); r = buf_findline(&b, WORD4"\n"); CU_ASSERT_EQUAL(r, -1); /* the very last line is found */ r = buf_findline(&b, WORD5); CU_ASSERT_EQUAL(r, sizeof(WORD0)+sizeof(WORD1)+sizeof(WORD2)+ sizeof(WORD3)+sizeof(WORD4)); r = buf_findline(&b, WORD5"\n"); CU_ASSERT_EQUAL(r, sizeof(WORD0)+sizeof(WORD1)+sizeof(WORD2)+ sizeof(WORD3)+sizeof(WORD4)); /* a word which is a subset of an earlier line, but * matches a later present line, is found */ buf_reset(&b); buf_appendcstr(&b, WORD0"\n"WORD1" "WORD2"\n"WORD1"\n"WORD2"\n"WORD5"\n"); CU_ASSERT_EQUAL(b.len, sizeof(WORD0)+sizeof(WORD1)+sizeof(WORD2)+ sizeof(WORD1)+sizeof(WORD2)+sizeof(WORD5)); r = buf_findline(&b, WORD1); CU_ASSERT_EQUAL(r, sizeof(WORD0)+sizeof(WORD1)+sizeof(WORD2)); r = buf_findline(&b, WORD1"\n"); CU_ASSERT_EQUAL(r, sizeof(WORD0)+sizeof(WORD1)+sizeof(WORD2)); r = buf_findline(&b, WORD2); CU_ASSERT_EQUAL(r, sizeof(WORD0)+sizeof(WORD1)+sizeof(WORD2)+ sizeof(WORD1)); r = buf_findline(&b, WORD2"\n"); CU_ASSERT_EQUAL(r, sizeof(WORD0)+sizeof(WORD1)+sizeof(WORD2)+ sizeof(WORD1)); /* a word which is the first subset of the first line, is unfound */ buf_reset(&b); buf_appendcstr(&b, WORD0" "WORD1"\n"WORD2" "WORD3"\n"); CU_ASSERT_EQUAL(b.len, sizeof(WORD0)+sizeof(WORD1)+sizeof(WORD2)+ sizeof(WORD3)); r = buf_findline(&b, WORD0); CU_ASSERT_EQUAL(r, -1); r = buf_findline(&b, WORD0"\n"); CU_ASSERT_EQUAL(r, -1); /* a word which is the last subset of the last line, is unfound */ r = buf_findline(&b, WORD3); CU_ASSERT_EQUAL(r, -1); r = buf_findline(&b, WORD3"\n"); CU_ASSERT_EQUAL(r, -1); buf_free(&b); #undef WORD0 #undef WORD1 #undef WORD2 #undef WORD3 #undef WORD4 #undef WORD5 #undef WORDU } /* TODO: test the Copy-On-Write feature of buf_ensure()...if anyone * actually uses it */ /* vim: set ft=c: */ cyrus-imapd-2.5.10/cunit/duplicate.testc0000644000175000017500000002112413001236020015100 00000000000000#include #include #include "config.h" #include "cunit/cunit.h" #include "imap/duplicate.h" #include "xmalloc.h" #include "retry.h" #include "imap/global.h" #include "imap/imap_err.h" #include "cyrusdb.h" #include "libcyr_cfg.h" #include "libconfig.h" #define DBDIR "test-mb-dbdir" struct result { struct result *next; char *id; char *to; char *date; time_t mark; unsigned long uid; }; #define GOTRESULT(expid, expto, expdate, expmark, expuid) \ { \ struct result *actual = results; \ CU_ASSERT_PTR_NOT_NULL_FATAL(results); \ results = results->next; \ CU_ASSERT_STRING_EQUAL(expid, actual->id); \ CU_ASSERT_STRING_EQUAL(expto, actual->to); \ CU_ASSERT_STRING_EQUAL(expdate, actual->date); \ CU_ASSERT_EQUAL(expmark, actual->mark); \ CU_ASSERT_EQUAL(expuid, actual->uid); \ free(actual->id); \ free(actual->to); \ free(actual->date); \ free(actual); \ } static void test_getset(void) { duplicate_key_t dkey = DUPLICATE_INITIALIZER; time_t t; time_t now; static const char MSGID1[] = ""; static const char MSGID2[] = ""; static const char FOLDER[] = "user.smurf"; static const char DATE[] = "Wed, 27 Oct 2010 18:37:26 +1100"; static unsigned long UID = 42; /* an invalid key returns 0 */ dkey.id = NULL; dkey.to = NULL; dkey.date = NULL; t = duplicate_check(&dkey); CU_ASSERT_EQUAL(t, 0); /* a valid but missing key returns 0 */ dkey.id = MSGID1; dkey.to = FOLDER; dkey.date = DATE; t = duplicate_check(&dkey); CU_ASSERT_EQUAL(t, 0); /* the other one too */ dkey.id = MSGID2; dkey.to = FOLDER; dkey.date = DATE; t = duplicate_check(&dkey); CU_ASSERT_EQUAL(t, 0); /* mark appears to succeed */ dkey.id = MSGID1; dkey.to = FOLDER; dkey.date = DATE; now = time(NULL); duplicate_mark(&dkey, now, UID); /* an invalid key still returns 0 */ dkey.id = NULL; dkey.to = NULL; dkey.date = NULL; t = duplicate_check(&dkey); CU_ASSERT_EQUAL(t, 0); /* a valid and present key returns non-zero */ dkey.id = MSGID1; dkey.to = FOLDER; dkey.date = DATE; t = duplicate_check(&dkey); CU_ASSERT_NOT_EQUAL(t, 0); CU_ASSERT_EQUAL(t, now); /* a valid but missing key still returns 0 */ dkey.id = MSGID2; dkey.to = FOLDER; dkey.date = DATE; t = duplicate_check(&dkey); CU_ASSERT_EQUAL(t, 0); } static int finder(const duplicate_key_t *dkey, time_t mark, unsigned long uid, void *rock) { struct result **head = (struct result **)rock; struct result **tail; struct result *res; // if (verbose) // fprintf(stderr, "found: id=\"%s\" to=\"%s\" date=\"%s\" " // "mark=%lu uid=%lu\n", // dkey->id, dkey->to, dkey->date, // (unsigned long)mark, (unsigned long)uid); /* remember arguments for later perusal */ res = xzmalloc(sizeof(*res)); res->id = xstrdup(dkey->id); res->to = xstrdup(dkey->to); res->date = xstrdup(dkey->date); res->mark = mark; res->uid = uid; /* append to the list. yes, it's inefficient. */ for (tail = head ; *tail ; tail = &(*tail)->next) ; *tail = res; return 0; } static void test_find(void) { duplicate_key_t dkey = DUPLICATE_INITIALIZER; struct result *results = NULL; static const char MSGID1[] = ""; static const char MSGID2[] = ""; /* test data from hipsteripsum.me */ static const char FOLDER1[] = "user.vegan"; static const char FOLDER2[] = "user.irony"; static const char FOLDER3[] = "user.single.origin"; static const char FOLDER4[] = "user.loko"; static const char FOLDER5[] = "user.biodiesel"; static const char DATE1[] = "Wed, 27 Oct 2010 18:01:02 +1100"; static const char DATE2[] = "Wed, 27 Oct 2010 18:03:04 +1100"; static const char DATE3[] = "Wed, 27 Oct 2010 18:05:06 +1100"; static const char DATE4[] = "Wed, 27 Oct 2010 18:07:08 +1100"; static const char DATE5[] = "Wed, 27 Oct 2010 18:09:10 +1100"; static time_t MARK1 = 1319088235; static time_t MARK2 = 1319088235; static time_t MARK3 = 1319088236; static time_t MARK4 = 1319088735; static time_t MARK5 = 1319089235; static unsigned long UID1 = 23; static unsigned long UID2 = 37; static unsigned long UID3 = 42; static unsigned long UID4 = 1007; static unsigned long UID5 = 314159; int r; /* find on an empty db returns nothing */ r = duplicate_find(MSGID1, finder, &results); CU_ASSERT_EQUAL(r, 0); CU_ASSERT_PTR_NULL(results); r = duplicate_find(MSGID2, finder, &results); CU_ASSERT_EQUAL(r, 0); CU_ASSERT_PTR_NULL(results); /* add one entry */ dkey.id = MSGID1; dkey.to = FOLDER1; dkey.date = DATE1; duplicate_mark(&dkey, MARK1, UID1); /* find returns the only entry */ r = duplicate_find(MSGID1, finder, &results); CU_ASSERT_EQUAL(r, 0); GOTRESULT(MSGID1, FOLDER1, DATE1, MARK1, UID1); CU_ASSERT_PTR_NULL(results); /* find of another msgid returns nothing */ r = duplicate_find(MSGID2, finder, &results); CU_ASSERT_EQUAL(r, 0); CU_ASSERT_PTR_NULL(results); /* add some more entries */ dkey.id = MSGID1; dkey.to = FOLDER2; dkey.date = DATE2; duplicate_mark(&dkey, MARK2, UID2); dkey.id = MSGID1; dkey.to = FOLDER3; dkey.date = DATE3; duplicate_mark(&dkey, MARK3, UID3); /* find returns all the entries in lexical order */ r = duplicate_find(MSGID1, finder, &results); CU_ASSERT_EQUAL(r, 0); GOTRESULT(MSGID1, FOLDER2, DATE2, MARK2, UID2); GOTRESULT(MSGID1, FOLDER3, DATE3, MARK3, UID3); GOTRESULT(MSGID1, FOLDER1, DATE1, MARK1, UID1); CU_ASSERT_PTR_NULL(results); /* find of another msgid returns nothing */ r = duplicate_find(MSGID2, finder, &results); CU_ASSERT_EQUAL(r, 0); CU_ASSERT_PTR_NULL(results); /* add some entries for another msgid */ dkey.id = MSGID2; dkey.to = FOLDER4; dkey.date = DATE4; duplicate_mark(&dkey, MARK4, UID4); dkey.id = MSGID2; dkey.to = FOLDER5; dkey.date = DATE5; duplicate_mark(&dkey, MARK5, UID5); /* find returns all the entries in lexical order */ r = duplicate_find(MSGID1, finder, &results); CU_ASSERT_EQUAL(r, 0); GOTRESULT(MSGID1, FOLDER2, DATE2, MARK2, UID2); GOTRESULT(MSGID1, FOLDER3, DATE3, MARK3, UID3); GOTRESULT(MSGID1, FOLDER1, DATE1, MARK1, UID1); CU_ASSERT_PTR_NULL(results); /* find of another msgid all it's entries in lexical order */ r = duplicate_find(MSGID2, finder, &results); CU_ASSERT_EQUAL(r, 0); GOTRESULT(MSGID2, FOLDER5, DATE5, MARK5, UID5); GOTRESULT(MSGID2, FOLDER4, DATE4, MARK4, UID4); CU_ASSERT_PTR_NULL(results); /* find with msgid="" returns all the entries for all msgids */ r = duplicate_find("", finder, &results); CU_ASSERT_EQUAL(r, 0); GOTRESULT(MSGID1, FOLDER2, DATE2, MARK2, UID2); GOTRESULT(MSGID1, FOLDER3, DATE3, MARK3, UID3); GOTRESULT(MSGID1, FOLDER1, DATE1, MARK1, UID1); GOTRESULT(MSGID2, FOLDER5, DATE5, MARK5, UID5); GOTRESULT(MSGID2, FOLDER4, DATE4, MARK4, UID4); CU_ASSERT_PTR_NULL(results); /* likewise msgid=NULL */ r = duplicate_find(NULL, finder, &results); CU_ASSERT_EQUAL(r, 0); GOTRESULT(MSGID1, FOLDER2, DATE2, MARK2, UID2); GOTRESULT(MSGID1, FOLDER3, DATE3, MARK3, UID3); GOTRESULT(MSGID1, FOLDER1, DATE1, MARK1, UID1); GOTRESULT(MSGID2, FOLDER5, DATE5, MARK5, UID5); GOTRESULT(MSGID2, FOLDER4, DATE4, MARK4, UID4); CU_ASSERT_PTR_NULL(results); } static void config_read_string(const char *s) { char *fname = xstrdup("/tmp/cyrus-cunit-configXXXXXX"); int fd = mkstemp(fname); retry_write(fd, s, strlen(s)); config_reset(); config_read(fname, 0); unlink(fname); free(fname); close(fd); } static int set_up(void) { int r; const char * const *d; static const char * const dirs[] = { DBDIR, DBDIR"/db", NULL }; r = system("rm -rf " DBDIR); if (r) return r; for (d = dirs ; *d ; d++) { r = mkdir(*d, 0777); if (r < 0) { int e = errno; perror(*d); return e; } } libcyrus_config_setstring(CYRUSOPT_CONFIG_DIR, DBDIR); config_read_string( "configdirectory: "DBDIR"/conf\n" ); cyrusdb_init(); config_duplicate_db = "skiplist"; duplicate_init(0); return 0; } static int tear_down(void) { int r; duplicate_done(); cyrusdb_done(); config_duplicate_db = NULL; config_reset(); r = system("rm -rf " DBDIR); if (r) r = -1; return r; } /* vim: set ft=c: */ cyrus-imapd-2.5.10/cunit/ptrarray.testc0000644000175000017500000004064113001236020014777 00000000000000#include #include "cunit/cunit.h" #include "ptrarray.h" #define PTR0 ((void *)0xcafebabe) #define PTR1 ((void *)0xcafebabf) #define PTR2 ((void *)0xcafebac0) #define PTR3 ((void *)0xcafebac1) #define PTR4 ((void *)0xcafebac2) #define PTR5 ((void *)0xcafebac3) #define PTR0REP ((void *)0xc0ffee00) #define PTR0REP2 ((void *)0xc0ffee01) #define PTR2REP ((void *)0xc0ffee02) #define PTRNOTHERE ((void *)0xdefaced0) static void test_fini_null(void) { /* _fini(NULL) is harmless */ ptrarray_fini(NULL); /* _free(NULL) is harmless */ ptrarray_free(NULL); } static void test_auto(void) { ptrarray_t pa = PTRARRAY_INITIALIZER; void *p1; void *p2; CU_ASSERT_EQUAL(pa.count, 0); CU_ASSERT(pa.alloc >= pa.count); CU_ASSERT_PTR_NULL(ptrarray_nth(&pa, 0)); CU_ASSERT_PTR_NULL(ptrarray_nth(&pa, -1)); p1 = PTR0; ptrarray_append(&pa, p1); CU_ASSERT_EQUAL(pa.count, 1); CU_ASSERT(pa.alloc >= pa.count); CU_ASSERT_PTR_NOT_NULL(pa.data); CU_ASSERT_PTR_EQUAL(ptrarray_nth(&pa, 0), p1); CU_ASSERT_PTR_EQUAL(ptrarray_nth(&pa, -1), p1); p2 = PTR0; ptrarray_append(&pa, p2); CU_ASSERT_EQUAL(pa.count, 2); CU_ASSERT(pa.alloc >= pa.count); CU_ASSERT_PTR_NOT_NULL(pa.data); CU_ASSERT_PTR_EQUAL(ptrarray_nth(&pa, 0), p1); CU_ASSERT_PTR_EQUAL(ptrarray_nth(&pa, 1), p2); CU_ASSERT_PTR_EQUAL(ptrarray_nth(&pa, -1), p2); ptrarray_fini(&pa); CU_ASSERT_EQUAL(pa.count, 0); CU_ASSERT_EQUAL(pa.alloc, 0); CU_ASSERT_PTR_NULL(pa.data); } static void test_heap(void) { ptrarray_t *pa = ptrarray_new(); void *p1; void *p2; CU_ASSERT_EQUAL(pa->count, 0); CU_ASSERT(pa->alloc >= pa->count); CU_ASSERT_PTR_NULL(ptrarray_nth(pa, 0)); CU_ASSERT_PTR_NULL(ptrarray_nth(pa, -1)); p1 = PTR0; ptrarray_append(pa, p1); CU_ASSERT_EQUAL(pa->count, 1); CU_ASSERT(pa->alloc >= pa->count); CU_ASSERT_PTR_NOT_NULL(pa->data); CU_ASSERT_PTR_EQUAL(ptrarray_nth(pa, 0), p1); CU_ASSERT_PTR_EQUAL(ptrarray_nth(pa, -1), p1); p2 = PTR1; ptrarray_append(pa, p2); CU_ASSERT_EQUAL(pa->count, 2); CU_ASSERT(pa->alloc >= pa->count); CU_ASSERT_PTR_NOT_NULL(pa->data); CU_ASSERT_PTR_EQUAL(ptrarray_nth(pa, 0), p1); CU_ASSERT_PTR_EQUAL(ptrarray_nth(pa, 1), p2); CU_ASSERT_PTR_EQUAL(ptrarray_nth(pa, -1), p2); ptrarray_free(pa); } static void test_set(void) { ptrarray_t pa = PTRARRAY_INITIALIZER; CU_ASSERT_EQUAL(pa.count, 0); CU_ASSERT(pa.alloc >= pa.count); CU_ASSERT_PTR_NULL(ptrarray_nth(&pa, 0)); CU_ASSERT_PTR_NULL(ptrarray_nth(&pa, -1)); ptrarray_append(&pa, PTR0); CU_ASSERT_EQUAL(pa.count, 1); CU_ASSERT(pa.alloc >= pa.count); CU_ASSERT_PTR_NOT_NULL(pa.data); CU_ASSERT_PTR_EQUAL(ptrarray_nth(&pa, 0), PTR0); ptrarray_set(&pa, 0, PTR0REP); CU_ASSERT_EQUAL(pa.count, 1); CU_ASSERT(pa.alloc >= pa.count); CU_ASSERT_PTR_NOT_NULL(pa.data); CU_ASSERT_PTR_EQUAL(ptrarray_nth(&pa, 0), PTR0REP); ptrarray_set(&pa, -1, PTR0REP2); CU_ASSERT_EQUAL(pa.count, 1); CU_ASSERT(pa.alloc >= pa.count); CU_ASSERT_PTR_NOT_NULL(pa.data); CU_ASSERT_PTR_EQUAL(ptrarray_nth(&pa, 0), PTR0REP2); ptrarray_append(&pa, PTR1); ptrarray_append(&pa, PTR2); ptrarray_append(&pa, PTR3); ptrarray_append(&pa, PTR4); CU_ASSERT_EQUAL(pa.count, 5); CU_ASSERT(pa.alloc >= pa.count); CU_ASSERT_PTR_NOT_NULL(pa.data); CU_ASSERT_PTR_EQUAL(ptrarray_nth(&pa, 0), PTR0REP2); CU_ASSERT_PTR_EQUAL(ptrarray_nth(&pa, 1), PTR1); CU_ASSERT_PTR_EQUAL(ptrarray_nth(&pa, 2), PTR2); CU_ASSERT_PTR_EQUAL(ptrarray_nth(&pa, 3), PTR3); CU_ASSERT_PTR_EQUAL(ptrarray_nth(&pa, 4), PTR4); ptrarray_set(&pa, 2, PTR2REP); CU_ASSERT_EQUAL(pa.count, 5); CU_ASSERT(pa.alloc >= pa.count); CU_ASSERT_PTR_NOT_NULL(pa.data); CU_ASSERT_PTR_EQUAL(ptrarray_nth(&pa, 0), PTR0REP2); CU_ASSERT_PTR_EQUAL(ptrarray_nth(&pa, 1), PTR1); CU_ASSERT_PTR_EQUAL(ptrarray_nth(&pa, 2), PTR2REP); CU_ASSERT_PTR_EQUAL(ptrarray_nth(&pa, 3), PTR3); CU_ASSERT_PTR_EQUAL(ptrarray_nth(&pa, 4), PTR4); ptrarray_fini(&pa); } static void test_insert(void) { ptrarray_t pa = PTRARRAY_INITIALIZER; CU_ASSERT_EQUAL(pa.count, 0); CU_ASSERT(pa.alloc >= pa.count); CU_ASSERT_PTR_NULL(ptrarray_nth(&pa, 0)); CU_ASSERT_PTR_NULL(ptrarray_nth(&pa, -1)); ptrarray_insert(&pa, 0, PTR0); CU_ASSERT_EQUAL(pa.count, 1); CU_ASSERT(pa.alloc >= pa.count); CU_ASSERT_PTR_NOT_NULL(pa.data); CU_ASSERT_PTR_EQUAL(ptrarray_nth(&pa, 0), PTR0); ptrarray_insert(&pa, -1, PTR1); CU_ASSERT_EQUAL(pa.count, 2); CU_ASSERT(pa.alloc >= pa.count); CU_ASSERT_PTR_NOT_NULL(pa.data); CU_ASSERT_PTR_EQUAL(ptrarray_nth(&pa, 0), PTR1); CU_ASSERT_PTR_EQUAL(ptrarray_nth(&pa, 1), PTR0); ptrarray_insert(&pa, 0, PTR2); CU_ASSERT_EQUAL(pa.count, 3); CU_ASSERT(pa.alloc >= pa.count); CU_ASSERT_PTR_NOT_NULL(pa.data); CU_ASSERT_PTR_EQUAL(ptrarray_nth(&pa, 0), PTR2); CU_ASSERT_PTR_EQUAL(ptrarray_nth(&pa, 1), PTR1); CU_ASSERT_PTR_EQUAL(ptrarray_nth(&pa, 2), PTR0); ptrarray_insert(&pa, -1, PTR3); CU_ASSERT_EQUAL(pa.count, 4); CU_ASSERT(pa.alloc >= pa.count); CU_ASSERT_PTR_NOT_NULL(pa.data); CU_ASSERT_PTR_EQUAL(ptrarray_nth(&pa, 0), PTR2); CU_ASSERT_PTR_EQUAL(ptrarray_nth(&pa, 1), PTR1); CU_ASSERT_PTR_EQUAL(ptrarray_nth(&pa, 2), PTR3); CU_ASSERT_PTR_EQUAL(ptrarray_nth(&pa, 3), PTR0); ptrarray_insert(&pa, 2, PTR4); CU_ASSERT_EQUAL(pa.count, 5); CU_ASSERT(pa.alloc >= pa.count); CU_ASSERT_PTR_NOT_NULL(pa.data); CU_ASSERT_PTR_EQUAL(ptrarray_nth(&pa, 0), PTR2); CU_ASSERT_PTR_EQUAL(ptrarray_nth(&pa, 1), PTR1); CU_ASSERT_PTR_EQUAL(ptrarray_nth(&pa, 2), PTR4); CU_ASSERT_PTR_EQUAL(ptrarray_nth(&pa, 3), PTR3); CU_ASSERT_PTR_EQUAL(ptrarray_nth(&pa, 4), PTR0); ptrarray_fini(&pa); } /* test that _set() and _insert() of a bad * index will fail silently and leave no side effects */ static void test_bad_index(void) { ptrarray_t pa = PTRARRAY_INITIALIZER; CU_ASSERT_EQUAL(pa.count, 0); CU_ASSERT(pa.alloc >= pa.count); CU_ASSERT_PTR_NULL(ptrarray_nth(&pa, 0)); CU_ASSERT_PTR_NULL(ptrarray_nth(&pa, -1)); /* when the ptrarray is empty, -1 is a bad index */ ptrarray_set(&pa, -1, PTR0); CU_ASSERT_EQUAL(pa.count, 0); CU_ASSERT_PTR_NULL(ptrarray_nth(&pa, 0)); CU_ASSERT_PTR_NULL(ptrarray_nth(&pa, -1)); ptrarray_insert(&pa, -1, PTR0); CU_ASSERT_EQUAL(pa.count, 0); CU_ASSERT_PTR_NULL(ptrarray_nth(&pa, 0)); CU_ASSERT_PTR_NULL(ptrarray_nth(&pa, -1)); /* a negative number larger than the (non-zero) count is a bad index */ ptrarray_append(&pa, PTR1); ptrarray_append(&pa, PTR2); ptrarray_set(&pa, -4, PTR0); CU_ASSERT_EQUAL(pa.count, 2); CU_ASSERT_PTR_EQUAL(ptrarray_nth(&pa, 0), PTR1); CU_ASSERT_PTR_EQUAL(ptrarray_nth(&pa, -1), PTR2); ptrarray_insert(&pa, -4, PTR0); CU_ASSERT_EQUAL(pa.count, 2); CU_ASSERT_PTR_EQUAL(ptrarray_nth(&pa, 0), PTR1); CU_ASSERT_PTR_EQUAL(ptrarray_nth(&pa, -1), PTR2); ptrarray_fini(&pa); } static void test_remove(void) { ptrarray_t pa = PTRARRAY_INITIALIZER; void *p; CU_ASSERT_EQUAL(pa.count, 0); CU_ASSERT(pa.alloc >= pa.count); CU_ASSERT_PTR_NULL(ptrarray_nth(&pa, 0)); CU_ASSERT_PTR_NULL(ptrarray_nth(&pa, -1)); ptrarray_append(&pa, PTR0); ptrarray_append(&pa, PTR1); ptrarray_append(&pa, PTR2); ptrarray_append(&pa, PTR3); ptrarray_append(&pa, PTR4); CU_ASSERT_EQUAL(pa.count, 5); CU_ASSERT(pa.alloc >= pa.count); CU_ASSERT_PTR_NOT_NULL(pa.data); CU_ASSERT_PTR_EQUAL(ptrarray_nth(&pa, 0), PTR0); CU_ASSERT_PTR_EQUAL(ptrarray_nth(&pa, 1), PTR1); CU_ASSERT_PTR_EQUAL(ptrarray_nth(&pa, 2), PTR2); CU_ASSERT_PTR_EQUAL(ptrarray_nth(&pa, 3), PTR3); CU_ASSERT_PTR_EQUAL(ptrarray_nth(&pa, 4), PTR4); p = ptrarray_remove(&pa, 2); CU_ASSERT_PTR_EQUAL(p, PTR2); CU_ASSERT_EQUAL(pa.count, 4); CU_ASSERT(pa.alloc >= pa.count); CU_ASSERT_PTR_NOT_NULL(pa.data); CU_ASSERT_PTR_EQUAL(ptrarray_nth(&pa, 0), PTR0); CU_ASSERT_PTR_EQUAL(ptrarray_nth(&pa, 1), PTR1); CU_ASSERT_PTR_EQUAL(ptrarray_nth(&pa, 2), PTR3); CU_ASSERT_PTR_EQUAL(ptrarray_nth(&pa, 3), PTR4); p = ptrarray_remove(&pa, 0); CU_ASSERT_PTR_EQUAL(p, PTR0); CU_ASSERT_EQUAL(pa.count, 3); CU_ASSERT(pa.alloc >= pa.count); CU_ASSERT_PTR_NOT_NULL(pa.data); CU_ASSERT_PTR_EQUAL(ptrarray_nth(&pa, 0), PTR1); CU_ASSERT_PTR_EQUAL(ptrarray_nth(&pa, 1), PTR3); CU_ASSERT_PTR_EQUAL(ptrarray_nth(&pa, 2), PTR4); p = ptrarray_remove(&pa, -1); CU_ASSERT_PTR_EQUAL(p, PTR4); CU_ASSERT_EQUAL(pa.count, 2); CU_ASSERT(pa.alloc >= pa.count); CU_ASSERT_PTR_NOT_NULL(pa.data); CU_ASSERT_PTR_EQUAL(ptrarray_nth(&pa, 0), PTR1); CU_ASSERT_PTR_EQUAL(ptrarray_nth(&pa, 1), PTR3); p = ptrarray_remove(&pa, 1); CU_ASSERT_PTR_EQUAL(p, PTR3); CU_ASSERT_EQUAL(pa.count, 1); CU_ASSERT(pa.alloc >= pa.count); CU_ASSERT_PTR_NOT_NULL(pa.data); CU_ASSERT_PTR_EQUAL(ptrarray_nth(&pa, 0), PTR1); p = ptrarray_remove(&pa, 0); CU_ASSERT_PTR_EQUAL(p, PTR1); CU_ASSERT_EQUAL(pa.count, 0); CU_ASSERT(pa.alloc >= pa.count); CU_ASSERT_PTR_NOT_NULL(pa.data); CU_ASSERT_PTR_NULL(ptrarray_nth(&pa, 0)); p = ptrarray_remove(&pa, 0); CU_ASSERT_PTR_NULL(p); ptrarray_fini(&pa); } static void test_takevf(void) { ptrarray_t *pa; void **pp; pa = ptrarray_new(); CU_ASSERT_PTR_NOT_NULL(pa); ptrarray_append(pa, PTR0); ptrarray_append(pa, PTR1); ptrarray_append(pa, PTR2); ptrarray_append(pa, PTR3); ptrarray_append(pa, PTR4); CU_ASSERT_EQUAL(pa->count, 5); CU_ASSERT(pa->alloc >= pa->count); CU_ASSERT_PTR_NOT_NULL(pa->data); CU_ASSERT_PTR_EQUAL(ptrarray_nth(pa, 0), PTR0); CU_ASSERT_PTR_EQUAL(ptrarray_nth(pa, 1), PTR1); CU_ASSERT_PTR_EQUAL(ptrarray_nth(pa, 2), PTR2); CU_ASSERT_PTR_EQUAL(ptrarray_nth(pa, 3), PTR3); CU_ASSERT_PTR_EQUAL(ptrarray_nth(pa, 4), PTR4); pp = ptrarray_takevf(pa); /* note: takevf frees the ptrarray itself */ CU_ASSERT_PTR_NOT_NULL(pp); CU_ASSERT_PTR_EQUAL(pp[0], PTR0); CU_ASSERT_PTR_EQUAL(pp[1], PTR1); CU_ASSERT_PTR_EQUAL(pp[2], PTR2); CU_ASSERT_PTR_EQUAL(pp[3], PTR3); CU_ASSERT_PTR_EQUAL(pp[4], PTR4); CU_ASSERT_PTR_NULL(pp[5]); free(pp); } static void test_truncate(void) { ptrarray_t pa = PTRARRAY_INITIALIZER; CU_ASSERT_EQUAL(pa.count, 0); CU_ASSERT(pa.alloc >= pa.count); CU_ASSERT_PTR_NULL(ptrarray_nth(&pa, 0)); CU_ASSERT_PTR_NULL(ptrarray_nth(&pa, -1)); ptrarray_append(&pa, PTR0); ptrarray_append(&pa, PTR1); ptrarray_append(&pa, PTR2); ptrarray_append(&pa, PTR3); ptrarray_append(&pa, PTR4); CU_ASSERT_EQUAL(pa.count, 5); CU_ASSERT(pa.alloc >= pa.count); CU_ASSERT_PTR_NOT_NULL(pa.data); CU_ASSERT_PTR_EQUAL(ptrarray_nth(&pa, 0), PTR0); CU_ASSERT_PTR_EQUAL(ptrarray_nth(&pa, 1), PTR1); CU_ASSERT_PTR_EQUAL(ptrarray_nth(&pa, 2), PTR2); CU_ASSERT_PTR_EQUAL(ptrarray_nth(&pa, 3), PTR3); CU_ASSERT_PTR_EQUAL(ptrarray_nth(&pa, 4), PTR4); /* expand the array */ ptrarray_truncate(&pa, 7); CU_ASSERT_EQUAL(pa.count, 7); CU_ASSERT(pa.alloc >= pa.count); CU_ASSERT_PTR_NOT_NULL(pa.data); CU_ASSERT_PTR_EQUAL(ptrarray_nth(&pa, 0), PTR0); CU_ASSERT_PTR_EQUAL(ptrarray_nth(&pa, 1), PTR1); CU_ASSERT_PTR_EQUAL(ptrarray_nth(&pa, 2), PTR2); CU_ASSERT_PTR_EQUAL(ptrarray_nth(&pa, 3), PTR3); CU_ASSERT_PTR_EQUAL(ptrarray_nth(&pa, 4), PTR4); CU_ASSERT_PTR_NULL(ptrarray_nth(&pa, 5)); CU_ASSERT_PTR_NULL(ptrarray_nth(&pa, 6)); /* truncate to the existing size is a no-op */ ptrarray_truncate(&pa, 7); CU_ASSERT_EQUAL(pa.count, 7); CU_ASSERT(pa.alloc >= pa.count); CU_ASSERT_PTR_NOT_NULL(pa.data); CU_ASSERT_PTR_EQUAL(ptrarray_nth(&pa, 0), PTR0); CU_ASSERT_PTR_EQUAL(ptrarray_nth(&pa, 1), PTR1); CU_ASSERT_PTR_EQUAL(ptrarray_nth(&pa, 2), PTR2); CU_ASSERT_PTR_EQUAL(ptrarray_nth(&pa, 3), PTR3); CU_ASSERT_PTR_EQUAL(ptrarray_nth(&pa, 4), PTR4); CU_ASSERT_PTR_NULL(ptrarray_nth(&pa, 5)); CU_ASSERT_PTR_NULL(ptrarray_nth(&pa, 6)); /* shrink the array */ ptrarray_truncate(&pa, 4); CU_ASSERT_EQUAL(pa.count, 4); CU_ASSERT(pa.alloc >= pa.count); CU_ASSERT_PTR_NOT_NULL(pa.data); CU_ASSERT_PTR_EQUAL(ptrarray_nth(&pa, 0), PTR0); CU_ASSERT_PTR_EQUAL(ptrarray_nth(&pa, 1), PTR1); CU_ASSERT_PTR_EQUAL(ptrarray_nth(&pa, 2), PTR2); CU_ASSERT_PTR_EQUAL(ptrarray_nth(&pa, 3), PTR3); /* shrink the array harder */ ptrarray_truncate(&pa, 3); CU_ASSERT_EQUAL(pa.count, 3); CU_ASSERT(pa.alloc >= pa.count); CU_ASSERT_PTR_NOT_NULL(pa.data); CU_ASSERT_PTR_EQUAL(ptrarray_nth(&pa, 0), PTR0); CU_ASSERT_PTR_EQUAL(ptrarray_nth(&pa, 1), PTR1); CU_ASSERT_PTR_EQUAL(ptrarray_nth(&pa, 2), PTR2); /* shrink the array to nothing */ ptrarray_truncate(&pa, 0); CU_ASSERT_EQUAL(pa.count, 0); CU_ASSERT(pa.alloc >= pa.count); /* whether pa.data is NULL is undefined at this time */ CU_ASSERT_PTR_NULL(ptrarray_nth(&pa, 0)); CU_ASSERT_PTR_NULL(ptrarray_nth(&pa, -1)); ptrarray_fini(&pa); } static void test_find(void) { ptrarray_t pa = PTRARRAY_INITIALIZER; int i; CU_ASSERT_EQUAL(pa.count, 0); CU_ASSERT(pa.alloc >= pa.count); CU_ASSERT_PTR_NULL(ptrarray_nth(&pa, 0)); CU_ASSERT_PTR_NULL(ptrarray_nth(&pa, -1)); ptrarray_append(&pa, PTR0); ptrarray_append(&pa, PTR1); ptrarray_append(&pa, PTR2); ptrarray_append(&pa, PTR3); ptrarray_append(&pa, PTR0); ptrarray_append(&pa, PTR4); CU_ASSERT_EQUAL(pa.count, 6); CU_ASSERT(pa.alloc >= pa.count); CU_ASSERT_PTR_NOT_NULL(pa.data); CU_ASSERT_PTR_EQUAL(ptrarray_nth(&pa, 0), PTR0); CU_ASSERT_PTR_EQUAL(ptrarray_nth(&pa, 1), PTR1); CU_ASSERT_PTR_EQUAL(ptrarray_nth(&pa, 2), PTR2); CU_ASSERT_PTR_EQUAL(ptrarray_nth(&pa, 3), PTR3); CU_ASSERT_PTR_EQUAL(ptrarray_nth(&pa, 4), PTR0); CU_ASSERT_PTR_EQUAL(ptrarray_nth(&pa, 5), PTR4); /* search for something which isn't there */ i = ptrarray_find(&pa, PTRNOTHERE, 0); CU_ASSERT_EQUAL(i, -1); /* search for something which isn't there, starting off the end */ i = ptrarray_find(&pa, PTRNOTHERE, 7); CU_ASSERT_EQUAL(i, -1); /* search for something which is there */ i = ptrarray_find(&pa, PTR1, 0); CU_ASSERT_EQUAL(i, 1); i = ptrarray_find(&pa, PTR1, i+1); CU_ASSERT_EQUAL(i, -1); /* search for something which is there, starting off the end */ i = ptrarray_find(&pa, PTR1, 7); CU_ASSERT_EQUAL(i, -1); /* search for something which is there multiple times */ i = ptrarray_find(&pa, PTR0, 0); CU_ASSERT_EQUAL(i, 0); i = ptrarray_find(&pa, PTR0, i+1); CU_ASSERT_EQUAL(i, 4); i = ptrarray_find(&pa, PTR0, i+1); CU_ASSERT_EQUAL(i, -1); ptrarray_fini(&pa); } static void test_add(void) { ptrarray_t pa = PTRARRAY_INITIALIZER; CU_ASSERT_EQUAL(pa.count, 0); CU_ASSERT(pa.alloc >= pa.count); CU_ASSERT_PTR_NULL(ptrarray_nth(&pa, 0)); CU_ASSERT_PTR_NULL(ptrarray_nth(&pa, -1)); /* _add() on an empty array appends */ ptrarray_add(&pa, PTR0); CU_ASSERT_EQUAL(pa.count, 1); CU_ASSERT(pa.alloc >= pa.count); CU_ASSERT_PTR_NOT_NULL(pa.data); CU_ASSERT_PTR_EQUAL(ptrarray_nth(&pa, 0), PTR0); /* _add() of an item already present is a no-op */ ptrarray_add(&pa, PTR0); CU_ASSERT_EQUAL(pa.count, 1); CU_ASSERT(pa.alloc >= pa.count); CU_ASSERT_PTR_NOT_NULL(pa.data); CU_ASSERT_PTR_EQUAL(ptrarray_nth(&pa, 0), PTR0); /* _add() of an item not already present appends */ ptrarray_add(&pa, PTR1); CU_ASSERT_EQUAL(pa.count, 2); CU_ASSERT(pa.alloc >= pa.count); CU_ASSERT_PTR_NOT_NULL(pa.data); CU_ASSERT_PTR_EQUAL(ptrarray_nth(&pa, 0), PTR0); CU_ASSERT_PTR_EQUAL(ptrarray_nth(&pa, 1), PTR1); /* _add() of an item already present is a no-op */ ptrarray_add(&pa, PTR0); CU_ASSERT_EQUAL(pa.count, 2); CU_ASSERT(pa.alloc >= pa.count); CU_ASSERT_PTR_NOT_NULL(pa.data); CU_ASSERT_PTR_EQUAL(ptrarray_nth(&pa, 0), PTR0); CU_ASSERT_PTR_EQUAL(ptrarray_nth(&pa, 1), PTR1); ptrarray_add(&pa, PTR1); CU_ASSERT_EQUAL(pa.count, 2); CU_ASSERT(pa.alloc >= pa.count); CU_ASSERT_PTR_NOT_NULL(pa.data); CU_ASSERT_PTR_EQUAL(ptrarray_nth(&pa, 0), PTR0); CU_ASSERT_PTR_EQUAL(ptrarray_nth(&pa, 1), PTR1); ptrarray_fini(&pa); } /* vim: set ft=c: */ cyrus-imapd-2.5.10/cunit/cunit.h0000644000175000017500000002055613001236020013365 00000000000000/* cunit.h - wrapper for CUnit assert macros * * Copyright (c) 1994-2010 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #ifndef INCLUDED_CUNIT_H #define INCLUDED_CUNIT_H #include #include #include #include "cunit-syslog.h" extern int verbose; /* * The standard CUnit assertion *EQUAL* macros have a flaw: they do * not report the actual values of the 'actual' and 'expected' values, * which makes it rather hard to see why an assertion failed. So we * replace the macros with improved ones, keeping the same API. */ extern CU_BOOL CU_assertFormatImplementation(CU_BOOL bValue, unsigned int uiLine, char strFile[], char strFunction[], CU_BOOL bFatal, char strConditionFormat[], ...); extern void __cunit_wrap_test(const char *name, void (*fn)(void)); extern int __cunit_wrap_fixture(const char *name, int (*fn)(void)); #undef CU_ASSERT_EQUAL #define CU_ASSERT_EQUAL(actual,expected) \ { long long _a = (actual), _e = (expected); \ CU_assertFormatImplementation((_a == _e), __LINE__, \ __FILE__, "", CU_FALSE, \ "CU_ASSERT_EQUAL(" #actual "=%lld," #expected "=%lld)", _a, _e); } #undef CU_ASSERT_EQUAL_FATAL #define CU_ASSERT_EQUAL_FATAL(actual,expected) \ { long long _a = (actual), _e = (expected); \ CU_assertFormatImplementation((_a == _e), __LINE__, \ __FILE__, "", CU_TRUE, \ "CU_ASSERT_EQUAL_FATAL(" #actual "=%lld," #expected "=%lld)", _a, _e); } #undef CU_ASSERT_NOT_EQUAL #define CU_ASSERT_NOT_EQUAL(actual,expected) \ { long long _a = (actual), _e = (expected); \ CU_assertFormatImplementation((_a != _e), __LINE__, \ __FILE__, "", CU_FALSE, \ "CU_ASSERT_NOT_EQUAL(" #actual "=%lld," #expected "=%lld)", _a, _e); } #undef CU_ASSERT_NOT_EQUAL_FATAL #define CU_ASSERT_NOT_EQUAL_FATAL(actual,expected) \ { long long _a = (actual), _e = (expected); \ CU_assertFormatImplementation((_a != _e), __LINE__, \ __FILE__, "", CU_TRUE, \ "CU_ASSERT_NOT_EQUAL_FATAL(" #actual "=%lld," #expected "=%lld)", _a, _e); } #undef CU_ASSERT_PTR_EQUAL #define CU_ASSERT_PTR_EQUAL(actual,expected) \ { const void *_a = (actual), *_e = (expected); \ CU_assertFormatImplementation((_a == _e), __LINE__, \ __FILE__, "", CU_FALSE, \ "CU_ASSERT_PTR_EQUAL(" #actual "=%p," #expected "=%p)", _a, _e); } #undef CU_ASSERT_PTR_EQUAL_FATAL #define CU_ASSERT_PTR_EQUAL_FATAL(actual,expected) \ { const void *_a = (actual), *_e = (expected); \ CU_assertFormatImplementation((_a == _e), __LINE__, \ __FILE__, "", CU_TRUE, \ "CU_ASSERT_PTR_EQUAL_FATAL(" #actual "=%p," #expected "=%p)", _a, _e); } #undef CU_ASSERT_PTR_NOT_EQUAL #define CU_ASSERT_PTR_NOT_EQUAL(actual,expected) \ { const void *_a = (actual), *_e = (expected); \ CU_assertFormatImplementation((_a != _e), __LINE__, \ __FILE__, "", CU_FALSE, \ "CU_ASSERT_PTR_NOT_EQUAL(" #actual "=%p," #expected "=%p)", _a, _e); } #undef CU_ASSERT_PTR_NOT_EQUAL_FATAL #define CU_ASSERT_PTR_NOT_EQUAL_FATAL(actual,expected) \ { const void *_a = (actual), *_e = (expected); \ CU_assertFormatImplementation((_a != _e), __LINE__, \ __FILE__, "", CU_TRUE, \ "CU_ASSERT_PTR_NOT_EQUAL_FATAL(" #actual "=%p," #expected "=%p)", _a, _e); } #undef CU_ASSERT_PTR_NULL #define CU_ASSERT_PTR_NULL(actual) \ { const void *_a = (actual); \ CU_assertFormatImplementation(!(_a), __LINE__, \ __FILE__, "", CU_FALSE, \ "CU_ASSERT_PTR_NULL(" #actual ")"); } #undef CU_ASSERT_PTR_NULL_FATAL #define CU_ASSERT_PTR_NULL_FATAL(actual) \ { const void *_a = (actual); \ CU_assertFormatImplementation(!(_a), __LINE__, \ __FILE__, "", CU_TRUE, \ "CU_ASSERT_PTR_NULL_FATAL(" #actual ")"); } #undef CU_ASSERT_PTR_NOT_NULL #define CU_ASSERT_PTR_NOT_NULL(actual) \ { const void *_a = (actual); \ CU_assertFormatImplementation(!!(_a), __LINE__, \ __FILE__, "", CU_FALSE, \ "CU_ASSERT_PTR_NOT_NULL(" #actual ")"); } #undef CU_ASSERT_PTR_NOT_NULL_FATAL #define CU_ASSERT_PTR_NOT_NULL_FATAL(actual) \ { const void *_a = (actual); \ CU_assertFormatImplementation(!!(_a), __LINE__, \ __FILE__, "", CU_TRUE, \ "CU_ASSERT_PTR_NOT_NULL_FATAL(" #actual ")"); } #undef CU_ASSERT_STRING_EQUAL #define CU_ASSERT_STRING_EQUAL(actual,expected) \ { const char *_a = (actual), *_e = (expected); \ CU_assertFormatImplementation(!strcmp(_a?_a:"",_e?_e:""), __LINE__, \ __FILE__, "", CU_FALSE, \ "CU_ASSERT_STRING_EQUAL(" #actual "=\"%s\"," #expected "=\"%s\")", _a, _e); } #undef CU_ASSERT_STRING_EQUAL_FATAL #define CU_ASSERT_STRING_EQUAL_FATAL(actual,expected) \ { const char *_a = (actual), *_e = (expected); \ CU_assertFormatImplementation(!strcmp(_a?_a:"",_e?_e:""), __LINE__, \ __FILE__, "", CU_TRUE, \ "CU_ASSERT_STRING_EQUAL_FATAL(" #actual "=\"%s\"," #expected "=\"%s\")", _a, _e); } #undef CU_ASSERT_STRING_NOT_EQUAL #define CU_ASSERT_STRING_NOT_EQUAL(actual,expected) \ { const char *_a = (actual), *_e = (expected); \ CU_assertFormatImplementation(!!strcmp(_a?_a:"",_e?_e:""), __LINE__, \ __FILE__, "", CU_FALSE, \ "CU_ASSERT_STRING_NOT_EQUAL(" #actual "=\"%s\"," #expected "=\"%s\")", _a, _e); } #undef CU_ASSERT_STRING_NOT_EQUAL_FATAL #define CU_ASSERT_STRING_NOT_EQUAL_FATAL(actual,expected) \ { const char *_a = (actual), *_e = (expected); \ CU_assertFormatImplementation(!!strcmp(_a?_a:"",_e?_e:""), __LINE__, \ __FILE__, "", CU_TRUE, \ "CU_ASSERT_STRING_NOT_EQUAL_FATAL(" #actual "=\"%s\"," #expected "=\"%s\")", _a, _e); } #define CU_SYSLOG_MATCH(re) \ CU_syslogMatchBegin((re), __FILE__, __LINE__) #define CU_ASSERT_SYSLOG(match, expected) \ { const char *_s = NULL; unsigned int _e = (expected), \ _a = CU_syslogMatchEnd((match), &_s); \ CU_assertFormatImplementation((_a == _e), __LINE__, \ __FILE__, "", CU_FALSE, \ "CU_ASSERT_SYSLOG(/%s/=%u, " #expected "=%u)", _s, _a, _e); } #define CU_ASSERT_SYSLOG_FATAL(match, expected) \ { const char *_s = NULL; unsigned int _e = (expected), \ _a = CU_syslogMatchEnd((match), &_s); \ CU_assertFormatImplementation((_a == _e), __LINE__, \ __FILE__, "", CU_TRUE, \ "CU_ASSERT_SYSLOG_FATAL(/%s/=%u, " #expected "=%u)", _s, _a, _e); } /* for parametrised tests */ #define CUNIT_PARAM(x) (x) struct cunit_param { /* initialisation state */ const char *name; char **variable; /* iteration state */ int nvalues; char **values; int idx; char *freeme1; }; #define __CUNIT_DECLARE_PARAM(nm) \ { #nm, &nm, 0, NULL, 0, NULL } #define __CUNIT_LAST_PARAM \ { NULL, NULL, 0, NULL, 0, NULL } extern void __cunit_params_begin(struct cunit_param *); extern int __cunit_params_next(struct cunit_param *); extern void __cunit_params_end(void); #endif /* INCLUDED_CUNIT_H */ cyrus-imapd-2.5.10/cunit/glob.testc0000644000175000017500000000767713001236020014072 00000000000000#include #include #include #include "cunit/cunit.h" #include "glob.h" static void test_star(void) { glob *g; int r; g = glob_init("fo*", GLOB_HIERARCHY); CU_ASSERT_PTR_NOT_EQUAL_FATAL(g, NULL); r = glob_test(g, "foo", 0, NULL); CU_ASSERT_EQUAL(r, 3); r = glob_test(g, "meh", 0, NULL); CU_ASSERT_EQUAL(r, -1); r = glob_test(g, "mofoo", 0, NULL); CU_ASSERT_EQUAL(r, -1); r = glob_test(g, "fnarp", 0, NULL); CU_ASSERT_EQUAL(r, -1); r = glob_test(g, "fod", 0, NULL); CU_ASSERT_EQUAL(r, 3); r = glob_test(g, "foonly", 0, NULL); CU_ASSERT_EQUAL(r, 6); r = glob_test(g, "foon.ly", 0, NULL); CU_ASSERT_EQUAL(r, 7); r = glob_test(g, "fo.only", 0, NULL); CU_ASSERT_EQUAL(r, 7); r = glob_test(g, "f.oonly", 0, NULL); CU_ASSERT_EQUAL(r, -1); glob_free(&g); } static void test_percent(void) { glob *g; int r; g = glob_init("fo%", GLOB_HIERARCHY); CU_ASSERT_PTR_NOT_EQUAL_FATAL(g, NULL); r = glob_test(g, "foo", 0, NULL); CU_ASSERT_EQUAL(r, 3); r = glob_test(g, "meh", 0, NULL); CU_ASSERT_EQUAL(r, -1); r = glob_test(g, "fnarp", 0, NULL); CU_ASSERT_EQUAL(r, -1); r = glob_test(g, "fod", 0, NULL); CU_ASSERT_EQUAL(r, 3); r = glob_test(g, "foonly", 0, NULL); CU_ASSERT_EQUAL(r, 6); r = glob_test(g, "foon.ly", 0, NULL); CU_ASSERT_EQUAL(r, -1); r = glob_test(g, "fo.only", 0, NULL); CU_ASSERT_EQUAL(r, -1); r = glob_test(g, "f.oonly", 0, NULL); CU_ASSERT_EQUAL(r, -1); glob_free(&g); } static void test_percent_percent(void) { glob *g; int r; g = glob_init("fo%.%", GLOB_HIERARCHY); CU_ASSERT_PTR_NOT_EQUAL_FATAL(g, NULL); r = glob_test(g, "foonly", 0, NULL); CU_ASSERT_EQUAL(r, -1); r = glob_test(g, "foon.ly", 0, NULL); CU_ASSERT_EQUAL(r, 7); r = glob_test(g, "fo.only", 0, NULL); CU_ASSERT_EQUAL(r, 7); r = glob_test(g, "f.oonly", 0, NULL); CU_ASSERT_EQUAL(r, -1); glob_free(&g); } static void test_questionmark(void) { glob *g; int r; g = glob_init("fo?", 0); CU_ASSERT_PTR_NOT_EQUAL_FATAL(g, NULL); r = glob_test(g, "foo", 0, NULL); CU_ASSERT_EQUAL(r, 3); r = glob_test(g, "meh", 0, NULL); CU_ASSERT_EQUAL(r, -1); r = glob_test(g, "fnarp", 0, NULL); CU_ASSERT_EQUAL(r, -1); r = glob_test(g, "fod", 0, NULL); CU_ASSERT_EQUAL(r, 3); r = glob_test(g, "foonly", 0, NULL); CU_ASSERT_EQUAL(r, -1); glob_free(&g); } static void test_star_substring(void) { glob *g; int r; g = glob_init("fo*", GLOB_SUBSTRING|GLOB_HIERARCHY); CU_ASSERT_PTR_NOT_EQUAL_FATAL(g, NULL); r = glob_test(g, "foo", 0, NULL); CU_ASSERT_EQUAL(r, 3); r = glob_test(g, "meh", 0, NULL); CU_ASSERT_EQUAL(r, -1); r = glob_test(g, "mofoo", 0, NULL); CU_ASSERT_EQUAL(r, 5); r = glob_test(g, "fnarp", 0, NULL); CU_ASSERT_EQUAL(r, -1); r = glob_test(g, "fod", 0, NULL); CU_ASSERT_EQUAL(r, 3); r = glob_test(g, "foonly", 0, NULL); CU_ASSERT_EQUAL(r, 6); r = glob_test(g, "foon.ly", 0, NULL); CU_ASSERT_EQUAL(r, 7); r = glob_test(g, "fo.only", 0, NULL); CU_ASSERT_EQUAL(r, 7); r = glob_test(g, "f.oonly", 0, NULL); CU_ASSERT_EQUAL(r, -1); r = glob_test(g, "mo.foo", 0, NULL); CU_ASSERT_EQUAL(r, 6); glob_free(&g); } static void test_star_icase(void) { glob *g; int r; g = glob_init("fo*", GLOB_ICASE|GLOB_HIERARCHY); CU_ASSERT_PTR_NOT_EQUAL_FATAL(g, NULL); r = glob_test(g, "foo", 0, NULL); CU_ASSERT_EQUAL(r, 3); r = glob_test(g, "meh", 0, NULL); CU_ASSERT_EQUAL(r, -1); r = glob_test(g, "FOO", 0, NULL); CU_ASSERT_EQUAL(r, 3); r = glob_test(g, "MEH", 0, NULL); CU_ASSERT_EQUAL(r, -1); r = glob_test(g, "Foo", 0, NULL); CU_ASSERT_EQUAL(r, 3); r = glob_test(g, "Meh", 0, NULL); CU_ASSERT_EQUAL(r, -1); glob_free(&g); } /* vim: set ft=c: */ cyrus-imapd-2.5.10/cunit/cunit-syslog.h0000644000175000017500000000453013001236020014675 00000000000000/* cunit-syslog.h - declarations for CUnit syslog functions * * Copyright (c) 1994-2011 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #ifndef __CUNIT_SYSLOG_H__ #define __CUNIT_SYSLOG_H__ /* returns an active match number from 1 up */ extern unsigned int CU_syslogMatchBegin(const char *re, const char *filename, unsigned int lineno); /* returns count of given match (or 0 for sum of all matches), and remove the match */ extern unsigned int CU_syslogMatchEnd(unsigned int match, const char **s); /* reset all matches, call before each test */ #define CU_syslogMatchReset() \ CU_syslogMatchEnd(0, NULL) #endif /* __CUNIT_SYSLOG_H__ */ cyrus-imapd-2.5.10/cunit/spool.testc0000644000175000017500000002413713001236020014271 00000000000000#include "config.h" #include "cunit/cunit.h" #include "imap/imap_err.h" #include "prot.h" #include "retry.h" #include "xmalloc.h" #include "imap/spool.h" #define DELIVERED "Fri, 29 Oct 2010 13:07:07 +1100" #define FIRST_RX "Fri, 29 Oct 2010 13:05:01 +1100" #define SECOND_RX "Fri, 29 Oct 2010 13:03:03 +1100" #define THIRD_RX "Fri, 29 Oct 2010 13:01:01 +1100" #define SENT "Thu, 28 Oct 2010 18:37:26 +1100" #define HFROM "Fred Bloggs " #define HFROM2 "Antoine Lavoisier " #define HTO "Sarah Jane Smith " #define HDATE SENT #define HSUBJECT "Simple testing email" #define HMESSAGEID "" #define HRECEIVED1 "from mail.quux.com (mail.quux.com [10.0.0.1]) by mail.gmail.com (Software); " FIRST_RX #define HRECEIVED2 "from mail.bar.com (mail.bar.com [10.0.0.1]) by mail.quux.com (Software); " SECOND_RX #define HRECEIVED3 "from mail.fastmail.fm (mail.fastmail.fm [10.0.0.1]) by mail.bar.com (Software); " THIRD_RX static void test_simple(void) { hdrcache_t cache; const char **val; cache = spool_new_hdrcache(); CU_ASSERT_PTR_NOT_NULL(cache); val = spool_getheader(cache, "Nonesuch"); CU_ASSERT_PTR_NULL(val); val = spool_getheader(cache, "From"); CU_ASSERT_PTR_NULL(val); val = spool_getheader(cache, "fRoM"); CU_ASSERT_PTR_NULL(val); val = spool_getheader(cache, "from"); CU_ASSERT_PTR_NULL(val); spool_cache_header(xstrdup("From"), xstrdup(HFROM), cache); val = spool_getheader(cache, "Nonesuch"); CU_ASSERT_PTR_NULL(val); val = spool_getheader(cache, "From"); CU_ASSERT_PTR_NOT_NULL(val); CU_ASSERT_STRING_EQUAL(val[0], HFROM); CU_ASSERT_PTR_NULL(val[1]); val = spool_getheader(cache, "fRoM"); CU_ASSERT_PTR_NOT_NULL(val); CU_ASSERT_STRING_EQUAL(val[0], HFROM); CU_ASSERT_PTR_NULL(val[1]); val = spool_getheader(cache, "from"); CU_ASSERT_PTR_NOT_NULL(val); CU_ASSERT_STRING_EQUAL(val[0], HFROM); CU_ASSERT_PTR_NULL(val[1]); spool_cache_header(xstrdup("To"), xstrdup(HTO), cache); spool_cache_header(xstrdup("Date"), xstrdup(HDATE), cache); spool_cache_header(xstrdup("Subject"), xstrdup(HSUBJECT), cache); spool_cache_header(xstrdup("Message-ID"), xstrdup(HMESSAGEID), cache); spool_cache_header(xstrdup("Received"), xstrdup(HRECEIVED1), cache); spool_cache_header(xstrdup("Received"), xstrdup(HRECEIVED2), cache); spool_cache_header(xstrdup("Received"), xstrdup(HRECEIVED3), cache); val = spool_getheader(cache, "Nonesuch"); CU_ASSERT_PTR_NULL(val); val = spool_getheader(cache, "From"); CU_ASSERT_PTR_NOT_NULL(val); CU_ASSERT_STRING_EQUAL(val[0], HFROM); CU_ASSERT_PTR_NULL(val[1]); val = spool_getheader(cache, "fRoM"); CU_ASSERT_PTR_NOT_NULL(val); CU_ASSERT_STRING_EQUAL(val[0], HFROM); CU_ASSERT_PTR_NULL(val[1]); val = spool_getheader(cache, "from"); CU_ASSERT_PTR_NOT_NULL(val); CU_ASSERT_STRING_EQUAL(val[0], HFROM); CU_ASSERT_PTR_NULL(val[1]); val = spool_getheader(cache, "To"); CU_ASSERT_PTR_NOT_NULL(val); CU_ASSERT_STRING_EQUAL(val[0], HTO); CU_ASSERT_PTR_NULL(val[1]); val = spool_getheader(cache, "Subject"); CU_ASSERT_PTR_NOT_NULL(val); CU_ASSERT_STRING_EQUAL(val[0], HSUBJECT); CU_ASSERT_PTR_NULL(val[1]); val = spool_getheader(cache, "message-id"); CU_ASSERT_PTR_NOT_NULL(val); CU_ASSERT_STRING_EQUAL(val[0], HMESSAGEID); CU_ASSERT_PTR_NULL(val[1]); val = spool_getheader(cache, "received"); CU_ASSERT_PTR_NOT_NULL(val); CU_ASSERT_STRING_EQUAL(val[0], HRECEIVED1); CU_ASSERT_STRING_EQUAL(val[1], HRECEIVED2); CU_ASSERT_STRING_EQUAL(val[2], HRECEIVED3); CU_ASSERT_PTR_NULL(val[3]); spool_free_hdrcache(cache); } static void test_fill(void) { static const char MSG[] = "From: " HFROM "\r\n" "To: " HTO "\r\n" "Date: " HDATE "\r\n" "Subject: " HSUBJECT "\r\n" "Message-ID: " HMESSAGEID "\r\n" "Received: " HRECEIVED1 "\r\n" "Received: " HRECEIVED2 "\r\n" "Received: " HRECEIVED3 "\r\n" "\r\n" "Hello, World\r\n"; hdrcache_t cache; const char **val; int fd; char tempfile[32]; int r; struct protstream *pin; FILE *fout; /* Setup @pin to point to the start of a file open for (at least) * reading containing the message. */ strcpy(tempfile, "/tmp/spooltestAXXXXXX"); fd = mkstemp(tempfile); CU_ASSERT(fd >= 0); r = retry_write(fd, MSG, sizeof(MSG)-1); CU_ASSERT_EQUAL(r, sizeof(MSG)-1); lseek(fd, SEEK_SET, 0); pin = prot_new(fd, /*read*/0); CU_ASSERT_PTR_NOT_NULL(pin); /* Setup @fout to ignore data written to it */ fout = fopen("/dev/null", "w"); CU_ASSERT_PTR_NOT_NULL(fout); cache = spool_new_hdrcache(); CU_ASSERT_PTR_NOT_NULL(cache); /* TODO: test non-NULL skipheaders */ r = spool_fill_hdrcache(pin, fout, cache, NULL); CU_ASSERT_EQUAL(r, 0); val = spool_getheader(cache, "Nonesuch"); CU_ASSERT_PTR_NULL(val); val = spool_getheader(cache, "From"); CU_ASSERT_PTR_NOT_NULL(val); CU_ASSERT_STRING_EQUAL(val[0], HFROM); CU_ASSERT_PTR_NULL(val[1]); val = spool_getheader(cache, "fRoM"); CU_ASSERT_PTR_NOT_NULL(val); CU_ASSERT_STRING_EQUAL(val[0], HFROM); CU_ASSERT_PTR_NULL(val[1]); val = spool_getheader(cache, "from"); CU_ASSERT_PTR_NOT_NULL(val); CU_ASSERT_STRING_EQUAL(val[0], HFROM); CU_ASSERT_PTR_NULL(val[1]); val = spool_getheader(cache, "To"); CU_ASSERT_PTR_NOT_NULL(val); CU_ASSERT_STRING_EQUAL(val[0], HTO); CU_ASSERT_PTR_NULL(val[1]); val = spool_getheader(cache, "Subject"); CU_ASSERT_PTR_NOT_NULL(val); CU_ASSERT_STRING_EQUAL(val[0], HSUBJECT); CU_ASSERT_PTR_NULL(val[1]); val = spool_getheader(cache, "message-id"); CU_ASSERT_PTR_NOT_NULL(val); CU_ASSERT_STRING_EQUAL(val[0], HMESSAGEID); CU_ASSERT_PTR_NULL(val[1]); val = spool_getheader(cache, "received"); CU_ASSERT_PTR_NOT_NULL(val); CU_ASSERT_STRING_EQUAL(val[0], HRECEIVED1); CU_ASSERT_STRING_EQUAL(val[1], HRECEIVED2); CU_ASSERT_STRING_EQUAL(val[2], HRECEIVED3); CU_ASSERT_PTR_NULL(val[3]); spool_free_hdrcache(cache); fclose(fout); prot_free(pin); unlink(tempfile); } /* BZ3640: headers with NULL bytes shall be rejected. */ static void test_fill_null(void) { static const char MSG[] = "From: " HFROM "\r\n" "To: " HTO "\r\n" "Date: " HDATE "\r\n" "Subject: " HSUBJECT "\r\n" "Message-ID: " HMESSAGEID "\r\n" "Received: " HRECEIVED1 "\r\n" "Received:\0" HRECEIVED2 "\r\n" "Received: " HRECEIVED3 "\r\n" "\r\n" "Hello, World\r\n"; hdrcache_t cache; int fd; char tempfile[32]; int r; struct protstream *pin; FILE *fout; /* Setup @pin to point to the start of a file open for (at least) * reading containing the message. */ strcpy(tempfile, "/tmp/spooltestAXXXXXX"); fd = mkstemp(tempfile); CU_ASSERT(fd >= 0); r = retry_write(fd, MSG, sizeof(MSG)-1); CU_ASSERT_EQUAL(r, sizeof(MSG)-1); lseek(fd, SEEK_SET, 0); pin = prot_new(fd, /*read*/0); CU_ASSERT_PTR_NOT_NULL(pin); /* Setup @fout to ignore data written to it */ fout = fopen("/dev/null", "w"); CU_ASSERT_PTR_NOT_NULL(fout); cache = spool_new_hdrcache(); CU_ASSERT_PTR_NOT_NULL(cache); r = spool_fill_hdrcache(pin, fout, cache, NULL); CU_ASSERT_EQUAL(r, IMAP_MESSAGE_CONTAINSNULL); spool_free_hdrcache(cache); fclose(fout); prot_free(pin); unlink(tempfile); } /* BZ3386: insert more unique headers than the internal limit of 4009 * headers, and see what happens. */ static void test_bz3386(void) { hdrcache_t cache; #define N 5000 int i; char name[32]; char body[128]; char body2[128]; /* use a different buffer Just In Case */ const char **val; cache = spool_new_hdrcache(); CU_ASSERT_PTR_NOT_NULL(cache); for (i = 0 ; i < N ; i++) { snprintf(name, sizeof(name), "X-Foo-%d-%c", i, 'A'+(i%26)); snprintf(body, sizeof(body), "value %d %c", i, 'A'+(i%26)); spool_cache_header(xstrdup(name), xstrdup(body), cache); } strcpy(body, "Old Buffer"); for (i = 0 ; i < N ; i++) { snprintf(name, sizeof(name), "X-Foo-%d-%c", i, 'A'+(i%26)); snprintf(body2, sizeof(body2), "value %d %c", i, 'A'+(i%26)); val = spool_getheader(cache, name); CU_ASSERT_PTR_NOT_NULL(val); CU_ASSERT_STRING_EQUAL(val[0], body2); CU_ASSERT_PTR_NULL(val[1]); } spool_free_hdrcache(cache); #undef N } static void test_replace(void) { #define FOOBAR1 "If music be the foo of love" #define FOOBAR2 "Foo glorious foo" #define FOOBAR3 "Foo is an important part of a balanced diet" /* apologies to Fran Liebowitz */ #define FOOBAR4 "Foo and Drug Administration" hdrcache_t cache; const char **val; cache = spool_new_hdrcache(); CU_ASSERT_PTR_NOT_NULL(cache); val = spool_getheader(cache, "From"); CU_ASSERT_PTR_NULL(val); /* replace a single line */ spool_cache_header(xstrdup("From"), xstrdup(HFROM), cache); val = spool_getheader(cache, "From"); CU_ASSERT_PTR_NOT_NULL(val); CU_ASSERT_STRING_EQUAL(val[0], HFROM); CU_ASSERT_PTR_NULL(val[1]); spool_replace_header(xstrdup("From"), xstrdup(HFROM2), cache); val = spool_getheader(cache, "From"); CU_ASSERT_PTR_NOT_NULL(val); CU_ASSERT_STRING_EQUAL(val[0], HFROM2); CU_ASSERT_PTR_NULL(val[1]); /* replace multiple lines with one */ spool_cache_header(xstrdup("X-FooBar"), xstrdup(FOOBAR1), cache); spool_cache_header(xstrdup("X-FooBar"), xstrdup(FOOBAR2), cache); spool_cache_header(xstrdup("X-FooBar"), xstrdup(FOOBAR3), cache); val = spool_getheader(cache, "X-FooBar"); CU_ASSERT_PTR_NOT_NULL(val); CU_ASSERT_STRING_EQUAL(val[0], FOOBAR1); CU_ASSERT_STRING_EQUAL(val[1], FOOBAR2); CU_ASSERT_STRING_EQUAL(val[2], FOOBAR3); CU_ASSERT_PTR_NULL(val[3]); spool_replace_header(xstrdup("X-FooBar"), xstrdup(FOOBAR4), cache); val = spool_getheader(cache, "X-FooBar"); CU_ASSERT_PTR_NOT_NULL(val); CU_ASSERT_STRING_EQUAL(val[0], FOOBAR4); CU_ASSERT_PTR_NULL(val[1]); spool_free_hdrcache(cache); #undef FOOBAR1 #undef FOOBAR2 #undef FOOBAR3 #undef FOOBAR4 } /* vim: set ft=c: */ cyrus-imapd-2.5.10/cunit/md5.testc0000644000175000017500000000223413001236020013614 00000000000000#include "cunit/cunit.h" #include "md5.h" static const char *asciify(unsigned char mac[16]) { static char buf[33]; int i; for (i = 0 ; i < 16 ; i++) sprintf(buf+2*i, "%02x", mac[i]); return buf; } static void test_single(void) { MD5_CTX ctx; unsigned char result[16]; static const char text[] = "Hello World"; static const char expected[33] = "b10a8db164e0754105b7a99be72e3fe5"; CU_ASSERT_EQUAL(MD5_DIGEST_LENGTH, 16); MD5Init(&ctx); MD5Update(&ctx, text, strlen(text)); MD5Final(result, &ctx); CU_ASSERT_STRING_EQUAL(asciify(result), expected); } static void test_multiple(void) { MD5_CTX ctx; unsigned char result[16]; static const char text1[] = "lorem ipsum"; static const char text2[] = " dolor sit amet,"; static const char text3[] = " consectetur adipisicing elit"; static const char expected[33] = "247ce3dcb025a6fd563b878072be7cc9"; MD5Init(&ctx); MD5Update(&ctx, text1, strlen(text1)); MD5Update(&ctx, text2, strlen(text2)); MD5Update(&ctx, text3, strlen(text3)); MD5Final(result, &ctx); CU_ASSERT_STRING_EQUAL(asciify(result), expected); } /* vim: set ft=c: */ cyrus-imapd-2.5.10/cunit/sieve.testc0000644000175000017500000013440413001236020014247 00000000000000/* Unit test for sieve */ /* Heavily based on the old sieve/test.c which bore this message: * * - * test.c -- tester for libcyrus_sieve * - * Larry Greenfield * */ #include "cunit/cunit.h" #include #include "sieve/bytecode.h" #include "sieve/comparator.h" #include "sieve/message.h" #include "sieve/sieve_interface.h" #include "imap/message.h" #include "prot.h" #include "retry.h" #include "imap/spool.h" #include "map.h" #include "util.h" #include "cyrusdb.h" #include "libcyr_cfg.h" #include "libconfig.h" #include "xstrlcat.h" #include "xstrlcpy.h" #include "xmalloc.h" #define DBDIR "test-sieve-dbdir" #define PARTITION "default" typedef struct { sieve_interp_t *interp; sieve_execute_t *exe; struct { unsigned int actions; unsigned int errors; unsigned int redirects; unsigned int discards; unsigned int rejects; unsigned int fileintos; unsigned int keeps; unsigned int notifies; unsigned int vaction_responses; } stats; char *redirected_to; char *reject_message; char *filed_mailbox; char *filed_flags; char *notify_method; char *notify_priority; char *notify_options; char *vacation_message; char *vacation_subject; char *vacation_to; char *vacation_from; strarray_t *compile_errors; strarray_t *run_errors; } sieve_test_context_t; typedef struct { const char *text; int length; struct message_content content; hdrcache_t headers; char *filename; } sieve_test_message_t; /* set to SIEVE_DONE if you want to test "already responded */ int autorespond_reponse = SIEVE_OK; extern int verbose; #define TESTCASE(_comp, _mode, _pat, _text, _result) \ comprock = NULL; \ c = lookup_comp(_comp, _mode, -1, &comprock); \ CU_ASSERT_PTR_NOT_NULL(c); \ if (c) { \ res = c(_text, strlen(_text), _pat, comprock); \ CU_ASSERT_EQUAL(res, _result); \ } static void test_comparator(void) { void *comprock; comparator_t *c; int res; TESTCASE( B_OCTET, B_IS, "", "", 1 ); TESTCASE( B_OCTET, B_IS, "a", "", 0 ); TESTCASE( B_OCTET, B_IS, "", "a", 0 ); TESTCASE( B_OCTET, B_IS, "a", "a", 1 ); TESTCASE( B_OCTET, B_IS, "a", "A", 0 ); TESTCASE( B_ASCIICASEMAP, B_IS, "", "", 1 ); TESTCASE( B_ASCIICASEMAP, B_IS, "a", "", 0 ); TESTCASE( B_ASCIICASEMAP, B_IS, "", "a", 0 ); TESTCASE( B_ASCIICASEMAP, B_IS, "a", "a", 1 ); TESTCASE( B_ASCIICASEMAP, B_IS, "a", "A", 1 ); TESTCASE( B_ASCIINUMERIC, B_IS, "123", "123", 1 ); TESTCASE( B_ASCIINUMERIC, B_IS, "123", "-123", 0 ); TESTCASE( B_ASCIINUMERIC, B_IS, "abc", "123", 0 ); TESTCASE( B_ASCIINUMERIC, B_IS, "abc", "abc", 1 ); TESTCASE( B_ASCIINUMERIC, B_IS, "12345678900", "3755744308", 0 ); /* test for 32bit overflow */ TESTCASE( B_ASCIINUMERIC, B_IS, "1567", "1567pounds", 1 ); TESTCASE( B_ASCIINUMERIC, B_IS, "", "", 1 ); TESTCASE( B_ASCIINUMERIC, B_IS, "123456789", "567", 0 ); TESTCASE( B_ASCIINUMERIC, B_IS, "567", "123456789", 0 ); TESTCASE( B_ASCIINUMERIC, B_IS, "123456789", "00000123456789", 1 ); TESTCASE( B_ASCIINUMERIC, B_IS, "102", "1024", 0 ); TESTCASE( B_ASCIINUMERIC, B_IS, "1567M", "1567 arg", 1 ); TESTCASE( B_OCTET, B_CONTAINS, "", "", 1 ); TESTCASE( B_OCTET, B_CONTAINS, "", "a", 1 ); TESTCASE( B_OCTET, B_CONTAINS, "a", "", 0 ); TESTCASE( B_OCTET, B_CONTAINS, "a", "a", 1 ); TESTCASE( B_OCTET, B_CONTAINS, "a", "ab", 1 ); TESTCASE( B_OCTET, B_CONTAINS, "a", "ba", 1 ); TESTCASE( B_OCTET, B_CONTAINS, "a", "aba", 1 ); TESTCASE( B_OCTET, B_CONTAINS, "a", "bab", 1 ); TESTCASE( B_OCTET, B_CONTAINS, "a", "bb", 0 ); TESTCASE( B_OCTET, B_CONTAINS, "a", "bbb", 0 ); TESTCASE( B_OCTET, B_MATCHES, "", "", 1 ); TESTCASE( B_OCTET, B_MATCHES, "", "a", 0 ); TESTCASE( B_OCTET, B_MATCHES, "a", "", 0 ); TESTCASE( B_OCTET, B_MATCHES, "a", "a", 1 ); TESTCASE( B_OCTET, B_MATCHES, "a", "ab", 0 ); TESTCASE( B_OCTET, B_MATCHES, "a", "ba", 0 ); TESTCASE( B_OCTET, B_MATCHES, "a", "aba", 0 ); TESTCASE( B_OCTET, B_MATCHES, "a", "bab", 0 ); TESTCASE( B_OCTET, B_MATCHES, "a", "bb", 0 ); TESTCASE( B_OCTET, B_MATCHES, "a", "bbb", 0 ); TESTCASE( B_OCTET, B_MATCHES, "*", "", 1 ); TESTCASE( B_OCTET, B_MATCHES, "*", "a", 1 ); TESTCASE( B_OCTET, B_MATCHES, "*a*", "", 0 ); TESTCASE( B_OCTET, B_MATCHES, "*a*", "a", 1 ); TESTCASE( B_OCTET, B_MATCHES, "*a*", "ab", 1 ); TESTCASE( B_OCTET, B_MATCHES, "*a*", "ba", 1 ); TESTCASE( B_OCTET, B_MATCHES, "*a*", "aba", 1 ); TESTCASE( B_OCTET, B_MATCHES, "*a*", "bab", 1 ); TESTCASE( B_OCTET, B_MATCHES, "*a*", "bb", 0 ); TESTCASE( B_OCTET, B_MATCHES, "*a*", "bbb", 0 ); TESTCASE( B_OCTET, B_MATCHES, "*a", "", 0 ); TESTCASE( B_OCTET, B_MATCHES, "*a", "a", 1 ); TESTCASE( B_OCTET, B_MATCHES, "*a", "ab", 0 ); TESTCASE( B_OCTET, B_MATCHES, "*a", "ba", 1 ); TESTCASE( B_OCTET, B_MATCHES, "*a", "aba", 1 ); TESTCASE( B_OCTET, B_MATCHES, "*a", "bab", 0 ); TESTCASE( B_OCTET, B_MATCHES, "*a", "bb", 0 ); TESTCASE( B_OCTET, B_MATCHES, "*a", "bbb", 0 ); TESTCASE( B_OCTET, B_MATCHES, "a*", "", 0 ); TESTCASE( B_OCTET, B_MATCHES, "a*", "a", 1 ); TESTCASE( B_OCTET, B_MATCHES, "a*", "ab", 1 ); TESTCASE( B_OCTET, B_MATCHES, "a*", "ba", 0 ); TESTCASE( B_OCTET, B_MATCHES, "a*", "aba", 1 ); TESTCASE( B_OCTET, B_MATCHES, "a*", "bab", 0 ); TESTCASE( B_OCTET, B_MATCHES, "a*", "bb", 0 ); TESTCASE( B_OCTET, B_MATCHES, "a*", "bbb", 0 ); TESTCASE( B_OCTET, B_MATCHES, "a*b", "", 0 ); TESTCASE( B_OCTET, B_MATCHES, "a*b", "a", 0 ); TESTCASE( B_OCTET, B_MATCHES, "a*b", "ab", 1 ); TESTCASE( B_OCTET, B_MATCHES, "a*b", "ba", 0 ); TESTCASE( B_OCTET, B_MATCHES, "a*b", "aba", 0 ); TESTCASE( B_OCTET, B_MATCHES, "a*b", "bab", 0 ); TESTCASE( B_OCTET, B_MATCHES, "a*b", "bb", 0 ); TESTCASE( B_OCTET, B_MATCHES, "a*b", "bbb", 0 ); TESTCASE( B_OCTET, B_MATCHES, "a*b", "abbb", 1 ); TESTCASE( B_OCTET, B_MATCHES, "a*b", "acb", 1 ); TESTCASE( B_OCTET, B_MATCHES, "a*b", "acbc", 0 ); TESTCASE( B_OCTET, B_MATCHES, "a?b", "", 0 ); TESTCASE( B_OCTET, B_MATCHES, "a?b", "a", 0 ); TESTCASE( B_OCTET, B_MATCHES, "a?b", "ab", 0 ); TESTCASE( B_OCTET, B_MATCHES, "a?b", "ba", 0 ); TESTCASE( B_OCTET, B_MATCHES, "a?b", "aba", 0 ); TESTCASE( B_OCTET, B_MATCHES, "a?b", "bab", 0 ); TESTCASE( B_OCTET, B_MATCHES, "a?b", "bb", 0 ); TESTCASE( B_OCTET, B_MATCHES, "a?b", "bbb", 0 ); TESTCASE( B_OCTET, B_MATCHES, "a?b", "abbb", 0 ); TESTCASE( B_OCTET, B_MATCHES, "a?b", "acb", 1 ); TESTCASE( B_OCTET, B_MATCHES, "a?b", "acbc", 0 ); TESTCASE( B_OCTET, B_MATCHES, "a*?b", "", 0 ); TESTCASE( B_OCTET, B_MATCHES, "a*?b", "a", 0 ); TESTCASE( B_OCTET, B_MATCHES, "a*?b", "ab", 0 ); TESTCASE( B_OCTET, B_MATCHES, "a*?b", "ba", 0 ); TESTCASE( B_OCTET, B_MATCHES, "a*?b", "aba", 0 ); TESTCASE( B_OCTET, B_MATCHES, "a*?b", "bab", 0 ); TESTCASE( B_OCTET, B_MATCHES, "a*?b", "bb", 0 ); TESTCASE( B_OCTET, B_MATCHES, "a*?b", "bbb", 0 ); TESTCASE( B_OCTET, B_MATCHES, "a*?b", "abbb", 1 ); TESTCASE( B_OCTET, B_MATCHES, "a*?b", "acb", 1 ); TESTCASE( B_OCTET, B_MATCHES, "a*?b", "acbc", 0 ); TESTCASE( B_OCTET, B_MATCHES, "a?*b", "", 0 ); TESTCASE( B_OCTET, B_MATCHES, "a?*b", "a", 0 ); TESTCASE( B_OCTET, B_MATCHES, "a?*b", "ab", 0 ); TESTCASE( B_OCTET, B_MATCHES, "a?*b", "ba", 0 ); TESTCASE( B_OCTET, B_MATCHES, "a?*b", "aba", 0 ); TESTCASE( B_OCTET, B_MATCHES, "a?*b", "bab", 0 ); TESTCASE( B_OCTET, B_MATCHES, "a?*b", "bb", 0 ); TESTCASE( B_OCTET, B_MATCHES, "a?*b", "bbb", 0 ); TESTCASE( B_OCTET, B_MATCHES, "a?*b", "abbb", 1 ); TESTCASE( B_OCTET, B_MATCHES, "a?*b", "acb", 1 ); TESTCASE( B_OCTET, B_MATCHES, "a?*b", "acbc", 0 ); TESTCASE( B_OCTET, B_MATCHES, "a*?*b", "", 0 ); TESTCASE( B_OCTET, B_MATCHES, "a*?*b", "a", 0 ); TESTCASE( B_OCTET, B_MATCHES, "a*?*b", "ab", 0 ); TESTCASE( B_OCTET, B_MATCHES, "a*?*b", "ba", 0 ); TESTCASE( B_OCTET, B_MATCHES, "a*?*b", "aba", 0 ); TESTCASE( B_OCTET, B_MATCHES, "a*?*b", "bab", 0 ); TESTCASE( B_OCTET, B_MATCHES, "a*?*b", "bb", 0 ); TESTCASE( B_OCTET, B_MATCHES, "a*?*b", "bbb", 0 ); TESTCASE( B_OCTET, B_MATCHES, "a*?*b", "abbb", 1 ); TESTCASE( B_OCTET, B_MATCHES, "a*?*b", "acb", 1 ); TESTCASE( B_OCTET, B_MATCHES, "a*?*b?", "acbc", 1 ); TESTCASE( B_ASCIICASEMAP, B_MATCHES, "a*b", "", 0 ); TESTCASE( B_ASCIICASEMAP, B_MATCHES, "a*b", "a", 0 ); TESTCASE( B_ASCIICASEMAP, B_MATCHES, "a*b", "ab", 1 ); TESTCASE( B_ASCIICASEMAP, B_MATCHES, "a*b", "ba", 0 ); TESTCASE( B_ASCIICASEMAP, B_MATCHES, "a*b", "aba", 0 ); TESTCASE( B_ASCIICASEMAP, B_MATCHES, "a*b", "bab", 0 ); TESTCASE( B_ASCIICASEMAP, B_MATCHES, "a*b", "bb", 0 ); TESTCASE( B_ASCIICASEMAP, B_MATCHES, "a*b", "bbb", 0 ); TESTCASE( B_ASCIICASEMAP, B_MATCHES, "a*b", "abbb", 1 ); TESTCASE( B_ASCIICASEMAP, B_MATCHES, "a*b", "acb", 1 ); TESTCASE( B_ASCIICASEMAP, B_MATCHES, "a*b", "acbc", 0 ); TESTCASE( B_ASCIICASEMAP, B_MATCHES, "a*b", "", 0 ); TESTCASE( B_ASCIICASEMAP, B_MATCHES, "a*b", "A", 0 ); TESTCASE( B_ASCIICASEMAP, B_MATCHES, "a*b", "Ab", 1 ); TESTCASE( B_ASCIICASEMAP, B_MATCHES, "a*b", "BA", 0 ); TESTCASE( B_ASCIICASEMAP, B_MATCHES, "a*b", "ABA", 0 ); TESTCASE( B_ASCIICASEMAP, B_MATCHES, "a*b", "BAb", 0 ); TESTCASE( B_ASCIICASEMAP, B_MATCHES, "a*b", "BB", 0 ); TESTCASE( B_ASCIICASEMAP, B_MATCHES, "a*b", "BBB", 0 ); TESTCASE( B_ASCIICASEMAP, B_MATCHES, "a*b", "aBBB", 1 ); TESTCASE( B_ASCIICASEMAP, B_MATCHES, "a*b", "ACB", 1 ); TESTCASE( B_ASCIICASEMAP, B_MATCHES, "a*b", "ACBC", 0 ); } /* gets the header "head" from msg. */ static int getheader(void *mc, const char *name, const char ***body) { sieve_test_message_t *msg = (sieve_test_message_t *)mc; *body = spool_getheader(msg->headers, name); if (!*body) return SIEVE_FAIL; return SIEVE_OK; } static int getsize(void *mc, int *size) { sieve_test_message_t *msg = (sieve_test_message_t *)mc; *size = msg->length; return SIEVE_OK; } static int getbody(void *mc, const char **content_types, sieve_bodypart_t ***parts) { sieve_test_message_t *msg = (sieve_test_message_t *)mc; int r = 0; if (!msg->content.body) { /* parse the message body if we haven't already */ FILE *fp = fopen(msg->filename, "r"); CU_ASSERT_PTR_NOT_NULL(fp); r = message_parse_file(fp, &msg->content.base, &msg->content.len, &msg->content.body); CU_ASSERT_EQUAL(r, 0); fclose(fp); } /* XXX currently struct bodypart as defined in message.h is the same as sieve_bodypart_t as defined in sieve_interface.h, so we can typecast */ if (!r) message_fetch_part(&msg->content, content_types, (struct bodypart ***) parts); if (r) return SIEVE_FAIL; return SIEVE_OK; } static int getinclude(void *sc __attribute__((unused)), const char *script, int isglobal __attribute__((unused)), char *fpath, size_t size) { strlcpy(fpath, script, size); strlcat(fpath, ".bc", size); return SIEVE_OK; } static int redirect(void *ac, void *ic, void *sc __attribute__((unused)), void *mc __attribute__((unused)), const char **errmsg __attribute__((unused))) { sieve_redirect_context_t *rc = (sieve_redirect_context_t *)ac; sieve_test_context_t *ctx = (sieve_test_context_t *)ic; ctx->stats.actions++; ctx->stats.redirects++; free(ctx->redirected_to); ctx->redirected_to = xstrdup(rc->addr); /* TODO: test returning SIEVE_FAIL */ return SIEVE_OK; } static int discard(void *ac __attribute__((unused)), void *ic, void *sc __attribute__((unused)), void *mc __attribute__((unused)), const char **errmsg __attribute__((unused))) { sieve_test_context_t *ctx = (sieve_test_context_t *)ic; ctx->stats.actions++; ctx->stats.discards++; /* TODO: test returning SIEVE_FAIL */ return SIEVE_OK; } static int reject(void *ac, void *ic, void *sc __attribute__((unused)), void *mc __attribute__((unused)), const char **errmsg __attribute__((unused))) { sieve_reject_context_t *rc = (sieve_reject_context_t *)ac; sieve_test_context_t *ctx = (sieve_test_context_t *)ic; ctx->stats.actions++; ctx->stats.rejects++; free(ctx->reject_message); ctx->reject_message = xstrdup(rc->msg); /* TODO: test returning SIEVE_FAIL */ return SIEVE_OK; } static int fileinto(void *ac, void *ic, void *sc __attribute__((unused)), void *mc __attribute__((unused)), const char **errmsg __attribute__((unused))) { sieve_fileinto_context_t *fc = (sieve_fileinto_context_t *)ac; sieve_test_context_t *ctx = (sieve_test_context_t *)ic; ctx->stats.actions++; ctx->stats.fileintos++; free(ctx->filed_mailbox); ctx->filed_mailbox = xstrdup(fc->mailbox); free(ctx->filed_flags); ctx->filed_flags = strarray_join(fc->imapflags, " "); /* TODO: test returning SIEVE_FAIL */ return SIEVE_OK; } static int keep(void *ac, void *ic, void *sc __attribute__((unused)), void *mc __attribute__((unused)), const char **errmsg __attribute__((unused))) { sieve_keep_context_t *kc = (sieve_keep_context_t *)ac; sieve_test_context_t *ctx = (sieve_test_context_t *)ic; ctx->stats.actions++; ctx->stats.keeps++; free(ctx->filed_flags); ctx->filed_flags = strarray_join(kc->imapflags, " "); /* TODO: test returning SIEVE_FAIL */ return SIEVE_OK; } static int notify(void *ac, void *ic, void *sc __attribute__((unused)), void *mc __attribute__((unused)), const char **errmsg __attribute__((unused))) { sieve_notify_context_t *nc = (sieve_notify_context_t *)ac; sieve_test_context_t *ctx = (sieve_test_context_t *)ic; struct buf opts = BUF_INITIALIZER; const char **p; for (p = nc->options ; *p ; p++) { if (opts.len) buf_putc(&opts, ' '); buf_appendcstr(&opts, *p); } ctx->stats.actions++; ctx->stats.notifies++; free(ctx->notify_options); ctx->notify_options = buf_release(&opts); free(ctx->notify_method); ctx->notify_method = xstrdup(nc->method); free(ctx->notify_priority); ctx->notify_method = xstrdup(nc->priority); /* TODO: test returning SIEVE_FAIL */ return SIEVE_OK; } static int mysieve_error(int lineno, const char *msg, void *ic, void *sc __attribute__((unused))) { sieve_test_context_t *ctx = (sieve_test_context_t *)ic; struct buf buf = BUF_INITIALIZER; ctx->stats.errors++; buf_printf(&buf, "line %d: %s", lineno, msg); strarray_appendm(ctx->compile_errors, buf_release(&buf)); return SIEVE_OK; } static int mysieve_execute_error(const char *msg, void *ic, void *sc __attribute__((unused)), void *mc __attribute__((unused))) { sieve_test_context_t *ctx = (sieve_test_context_t *)ic; ctx->stats.errors++; strarray_append(ctx->run_errors, msg); return SIEVE_OK; } static int autorespond(void *ac __attribute__((unused)), void *ic __attribute__((unused)), void *sc __attribute__((unused)), void *mc __attribute__((unused)), const char **errmsg __attribute__((unused))) { return autorespond_reponse; } static int send_response(void *ac, void *ic, void *sc __attribute__((unused)), void *mc __attribute__((unused)), const char **errmsg __attribute__((unused))) { sieve_send_response_context_t *src = (sieve_send_response_context_t *)ac; sieve_test_context_t *ctx = (sieve_test_context_t *)ic; ctx->stats.actions++; ctx->stats.vaction_responses++; free(ctx->vacation_message); ctx->vacation_message = xstrdup(src->msg); free(ctx->vacation_subject); ctx->vacation_subject = xstrdup(src->subj); free(ctx->vacation_to); ctx->vacation_to = xstrdup(src->addr); free(ctx->vacation_from); ctx->vacation_from = xstrdup(src->fromaddr); /* TODO: test returning SIEVE_FAIL */ return SIEVE_OK; } #ifndef HAVE_FMEMOPEN static FILE *fmemopen(const void *buf, size_t len, const char *mode) { FILE *fp; fp = fopen("/dev/null", mode); if (!fp) return NULL; setbuffer(fp, buf, len); return fp; } #endif static void config_read_string(const char *s) { char *fname = xstrdup("/tmp/cyrus-cunit-configXXXXXX"); int fd = mkstemp(fname); retry_write(fd, s, strlen(s)); config_reset(); config_read(fname, 0); unlink(fname); free(fname); close(fd); } static int set_up(void) { libcyrus_config_setstring(CYRUSOPT_CONFIG_DIR, DBDIR); config_read_string( "configdirectory: "DBDIR"/conf\n" "defaultpartition: "PARTITION"\n" "partition-"PARTITION": "DBDIR"/data\n" "sievenotifier: mailto\n" "sieve_extensions: fileinto reject vacation imapflags notify" \ " envelope body relational regex subaddress copy date index\n" ); libcyrus_init(); return 0; } static int tear_down(void) { libcyrus_done(); return 0; } static void context_setup(sieve_test_context_t *ctx, const char *script) { int r; static strarray_t mark = STRARRAY_INITIALIZER; static sieve_vacation_t vacation = { 0, /* min response */ 0, /* max response */ &autorespond, /* autorespond() */ &send_response /* send_response() */ }; int len = strlen(script); int fd; FILE *fp; sieve_script_t *scr = NULL; bytecode_info_t *bytecode = NULL; char tempfile[32]; memset(ctx, 0, sizeof(*ctx)); if (!mark.count) strarray_append(&mark, "\\flagged"); ctx->compile_errors = strarray_new(); ctx->run_errors = strarray_new(); ctx->interp = sieve_interp_alloc(ctx); sieve_register_redirect(ctx->interp, redirect); sieve_register_discard(ctx->interp, discard); sieve_register_reject(ctx->interp, reject); sieve_register_fileinto(ctx->interp, fileinto); sieve_register_keep(ctx->interp, keep); sieve_register_size(ctx->interp, getsize); sieve_register_header(ctx->interp, getheader); sieve_register_envelope(ctx->interp, getheader); sieve_register_body(ctx->interp, getbody); sieve_register_include(ctx->interp, getinclude); sieve_register_vacation(ctx->interp, &vacation); sieve_register_imapflags(ctx->interp, &mark); sieve_register_notify(ctx->interp, notify); sieve_register_parse_error(ctx->interp, mysieve_error); sieve_register_execute_error(ctx->interp, mysieve_execute_error); /* Here we pretend to be the sieve compiler, and generate * a file of compiled bytecode from the script string */ fp = fmemopen((void *)script, len, "r"); r = sieve_script_parse(ctx->interp, fp, ctx, &scr); CU_ASSERT_EQUAL(r, SIEVE_OK); fclose(fp); r = sieve_generate_bytecode(&bytecode, scr); CU_ASSERT(r > 0); strcpy(tempfile, "/tmp/sievetest-BC-XXXXXX"); fd = mkstemp(tempfile); CU_ASSERT(fd >= 0); r = sieve_emit_bytecode(fd, bytecode); CU_ASSERT(r > 0); sieve_free_bytecode(&bytecode); sieve_script_free(&scr); /* Now load the compiled bytecode */ r = sieve_script_load(tempfile, &ctx->exe); CU_ASSERT_EQUAL(r, SIEVE_OK); unlink(tempfile); } static void context_cleanup(sieve_test_context_t *ctx) { int r; if (verbose > 1) { int i; fprintf(stderr, "sieve test context\n"); fprintf(stderr, " actions: %u\n", ctx->stats.actions); fprintf(stderr, " errors: %u\n", ctx->stats.errors); fprintf(stderr, " redirects: %u\n", ctx->stats.redirects); fprintf(stderr, " discards: %u\n", ctx->stats.discards); fprintf(stderr, " rejects: %u\n", ctx->stats.rejects); fprintf(stderr, " fileintos: %u\n", ctx->stats.fileintos); fprintf(stderr, " keeps: %u\n", ctx->stats.keeps); fprintf(stderr, " notifies: %u\n", ctx->stats.notifies); fprintf(stderr, " vaction_responses: %u\n", ctx->stats.vaction_responses); if (ctx->redirected_to) fprintf(stderr, " redirected_to: %s\n", ctx->redirected_to); if (ctx->reject_message) fprintf(stderr, " reject_message: %s\n", ctx->reject_message); if (ctx->filed_mailbox) fprintf(stderr, " filed_mailbox: %s\n", ctx->filed_mailbox); if (ctx->filed_flags) fprintf(stderr, " filed_flags: %s\n", ctx->filed_flags); if (ctx->notify_method) fprintf(stderr, " notify_method: %s\n", ctx->notify_method); if (ctx->notify_priority) fprintf(stderr, " notify_priority: %s\n", ctx->notify_priority); if (ctx->notify_options) fprintf(stderr, " notify_options: %s\n", ctx->notify_options); if (ctx->vacation_message) fprintf(stderr, " vacation_message: %s\n", ctx->vacation_message); if (ctx->vacation_subject) fprintf(stderr, " vacation_subject: %s\n", ctx->vacation_subject); if (ctx->vacation_to) fprintf(stderr, " vacation_to: %s\n", ctx->vacation_to); if (ctx->vacation_from) fprintf(stderr, " vacation_from: %s\n", ctx->vacation_from); if (ctx->compile_errors->count) { fprintf(stderr, " compile_errors:\n"); for (i = 0 ; i < ctx->compile_errors->count ; i++) fprintf(stderr, "\t[%d] %s\n", i, ctx->compile_errors->data[i]); } if (ctx->run_errors->count) { fprintf(stderr, " run_errors:\n"); for (i = 0 ; i < ctx->run_errors->count ; i++) fprintf(stderr, "\t[%d] %s\n", i, ctx->run_errors->data[i]); } } /*used to be sieve_script_free*/ r = sieve_script_unload(&ctx->exe); CU_ASSERT_EQUAL(r, SIEVE_OK); CU_ASSERT_PTR_NULL(ctx->exe); r = sieve_interp_free(&ctx->interp); CU_ASSERT_EQUAL(r, SIEVE_OK); free(ctx->redirected_to); free(ctx->reject_message); free(ctx->filed_mailbox); free(ctx->filed_flags); free(ctx->notify_method); free(ctx->notify_priority); free(ctx->notify_options); free(ctx->vacation_message); free(ctx->vacation_subject); free(ctx->vacation_to); free(ctx->vacation_from); strarray_free(ctx->compile_errors); strarray_free(ctx->run_errors); } static sieve_test_message_t *message_new(const char *text, int len) { sieve_test_message_t *msg; struct protstream *pin; FILE *fout; int fd; int r; char tempfile[32]; msg = xzmalloc(sizeof(sieve_test_message_t)); msg->text = text; msg->length = len; msg->headers = spool_new_hdrcache(); strcpy(tempfile, "/tmp/sievetest-MS-XXXXXX"); fd = mkstemp(tempfile); CU_ASSERT(fd >= 0); msg->filename = xstrdup(tempfile); r = retry_write(fd, text, len); CU_ASSERT_EQUAL(r, len); lseek(fd, SEEK_SET, 0); pin = prot_new(fd, /*read*/0); CU_ASSERT_PTR_NOT_NULL(pin); fout = fopen("/dev/null", "w"); CU_ASSERT_PTR_NOT_NULL(fout); r = spool_fill_hdrcache(pin, fout, msg->headers, NULL); CU_ASSERT_EQUAL(r, 0); fclose(fout); prot_free(pin); return msg; } static void message_free(sieve_test_message_t *msg) { spool_free_hdrcache(msg->headers); if (msg->content.body) message_free_body(msg->content.body); if (msg->content.base) map_free(&msg->content.base, &msg->content.len); unlink(msg->filename); free(msg->filename); free(msg); } static void run_message(sieve_test_context_t *ctx, const char *text) { sieve_test_message_t *msg; int r; msg = message_new(text, strlen(text)); CU_ASSERT_PTR_NOT_NULL(msg); r = sieve_execute_bytecode(ctx->exe, ctx->interp, ctx, msg); CU_ASSERT_EQUAL(r, SIEVE_OK); message_free(msg); } static void test_address_all(void) { static const char SCRIPT_IS[] = "if address :all :is \"from\" \"zme@true.com\"\n" "{redirect \"me@blah.com\";}\n" ; static const char SCRIPT_CONTAINS[] = "if address :all :contains \"from\" \"true.com\"\n" "{redirect \"me@blah.com\";}\n" ; static const char SCRIPT_MATCHES[] = "if address :all :matches \"from\" \"*true.com\"\n" "{redirect \"me@blah.com\";}\n" ; static const char MSG_TRUE[] = "Date: Mon, 25 Jan 2003 08:51:06 -0500\r\n" "From: zme@true.com\r\n" "To: you\r\n" "Subject: simple address test\r\n" "\r\n" "blah\n" ; static const char MSG_FALSE[] = "Date: Mon, 25 Jan 2003 08:51:06 -0500\r\n" "From: zme@false.com\r\n" "To: you\r\n" "Subject: simple address test\r\n" "\r\n" "blah\n" ; sieve_test_context_t ctx; /* Test :is */ context_setup(&ctx, SCRIPT_IS); CU_ASSERT_EQUAL(ctx.stats.errors, 0); run_message(&ctx, MSG_TRUE); CU_ASSERT_EQUAL(ctx.stats.errors, 0); CU_ASSERT_EQUAL(ctx.stats.actions, 1); CU_ASSERT_EQUAL(ctx.stats.redirects, 1); CU_ASSERT_EQUAL(ctx.stats.keeps, 0); CU_ASSERT_STRING_EQUAL(ctx.redirected_to, "me@blah.com"); run_message(&ctx, MSG_FALSE); CU_ASSERT_EQUAL(ctx.stats.errors, 0); CU_ASSERT_EQUAL(ctx.stats.actions, 2); CU_ASSERT_EQUAL(ctx.stats.redirects, 1); CU_ASSERT_EQUAL(ctx.stats.keeps, 1); CU_ASSERT_STRING_EQUAL(ctx.redirected_to, "me@blah.com"); context_cleanup(&ctx); /* Test :contains */ context_setup(&ctx, SCRIPT_CONTAINS); CU_ASSERT_EQUAL(ctx.stats.errors, 0); run_message(&ctx, MSG_TRUE); CU_ASSERT_EQUAL(ctx.stats.errors, 0); CU_ASSERT_EQUAL(ctx.stats.actions, 1); CU_ASSERT_EQUAL(ctx.stats.redirects, 1); CU_ASSERT_EQUAL(ctx.stats.keeps, 0); CU_ASSERT_STRING_EQUAL(ctx.redirected_to, "me@blah.com"); run_message(&ctx, MSG_FALSE); CU_ASSERT_EQUAL(ctx.stats.errors, 0); CU_ASSERT_EQUAL(ctx.stats.actions, 2); CU_ASSERT_EQUAL(ctx.stats.redirects, 1); CU_ASSERT_EQUAL(ctx.stats.keeps, 1); CU_ASSERT_STRING_EQUAL(ctx.redirected_to, "me@blah.com"); context_cleanup(&ctx); /* Test :matches */ context_setup(&ctx, SCRIPT_MATCHES); CU_ASSERT_EQUAL(ctx.stats.errors, 0); run_message(&ctx, MSG_TRUE); CU_ASSERT_EQUAL(ctx.stats.errors, 0); CU_ASSERT_EQUAL(ctx.stats.actions, 1); CU_ASSERT_EQUAL(ctx.stats.redirects, 1); CU_ASSERT_EQUAL(ctx.stats.keeps, 0); CU_ASSERT_STRING_EQUAL(ctx.redirected_to, "me@blah.com"); run_message(&ctx, MSG_FALSE); CU_ASSERT_EQUAL(ctx.stats.errors, 0); CU_ASSERT_EQUAL(ctx.stats.actions, 2); CU_ASSERT_EQUAL(ctx.stats.redirects, 1); CU_ASSERT_EQUAL(ctx.stats.keeps, 1); CU_ASSERT_STRING_EQUAL(ctx.redirected_to, "me@blah.com"); context_cleanup(&ctx); } static void test_exists(void) { static const char SCRIPT[] = "if exists \"flooglewart\"\n" "{redirect \"me@blah.com\";}\n" ; static const char MSG_TRUE[] = "Date: Mon, 25 Jan 2003 08:51:06 -0500\r\n" "From: zme@true.com\r\n" "To: you\r\n" "Subject: simple address test\r\n" "Flooglewart: fnarp fmeh oogedyboogedy\r\n" "\r\n" "blah\n" ; static const char MSG_FALSE[] = "Date: Mon, 25 Jan 2003 08:51:06 -0500\r\n" "From: yme@false.com\r\n" "To: you\r\n" "Subject: simple address test\r\n" "\r\n" "blah\n" ; sieve_test_context_t ctx; context_setup(&ctx, SCRIPT); CU_ASSERT_EQUAL(ctx.stats.errors, 0); run_message(&ctx, MSG_TRUE); CU_ASSERT_EQUAL(ctx.stats.errors, 0); CU_ASSERT_EQUAL(ctx.stats.actions, 1); CU_ASSERT_EQUAL(ctx.stats.redirects, 1); CU_ASSERT_EQUAL(ctx.stats.keeps, 0); CU_ASSERT_STRING_EQUAL(ctx.redirected_to, "me@blah.com"); run_message(&ctx, MSG_FALSE); CU_ASSERT_EQUAL(ctx.stats.errors, 0); CU_ASSERT_EQUAL(ctx.stats.actions, 2); CU_ASSERT_EQUAL(ctx.stats.redirects, 1); CU_ASSERT_EQUAL(ctx.stats.keeps, 1); CU_ASSERT_STRING_EQUAL(ctx.redirected_to, "me@blah.com"); context_cleanup(&ctx); } static void test_address_domain(void) { static const char SCRIPT[] = "if address :domain :is \"from\" \"true.com\"\n" "{redirect \"me@blah.com\";}\n" ; static const char MSG_TRUE[] = "Date: Mon, 25 Jan 2003 08:51:06 -0500\r\n" "From: zme@true.com\r\n" "To: you\r\n" "Subject: simple address test\r\n" "\r\n" "blah\n" ; static const char MSG_FALSE[] = "Date: Mon, 25 Jan 2003 08:51:06 -0500\r\n" "From: zme@false.com\r\n" "To: you\r\n" "Subject: simple address test\r\n" "\r\n" "blah\n" ; sieve_test_context_t ctx; context_setup(&ctx, SCRIPT); CU_ASSERT_EQUAL(ctx.stats.errors, 0); run_message(&ctx, MSG_TRUE); CU_ASSERT_EQUAL(ctx.stats.errors, 0); CU_ASSERT_EQUAL(ctx.stats.actions, 1); CU_ASSERT_EQUAL(ctx.stats.redirects, 1); CU_ASSERT_EQUAL(ctx.stats.keeps, 0); CU_ASSERT_STRING_EQUAL(ctx.redirected_to, "me@blah.com"); run_message(&ctx, MSG_FALSE); CU_ASSERT_EQUAL(ctx.stats.errors, 0); CU_ASSERT_EQUAL(ctx.stats.actions, 2); CU_ASSERT_EQUAL(ctx.stats.redirects, 1); CU_ASSERT_EQUAL(ctx.stats.keeps, 1); CU_ASSERT_STRING_EQUAL(ctx.redirected_to, "me@blah.com"); context_cleanup(&ctx); } static void test_address_localpart(void) { static const char SCRIPT[] = "if address :localpart :is \"from\" \"zme\"\n" "{redirect \"me@blah.com\";}\n" ; static const char MSG_TRUE[] = "Date: Mon, 25 Jan 2003 08:51:06 -0500\r\n" "From: zme@true.com\r\n" "To: you\r\n" "Subject: simple address test\r\n" "\r\n" "blah\n" ; static const char MSG_FALSE[] = "Date: Mon, 25 Jan 2003 08:51:06 -0500\r\n" "From: yme@false.com\r\n" "To: you\r\n" "Subject: simple address test\r\n" "\r\n" "blah\n" ; sieve_test_context_t ctx; context_setup(&ctx, SCRIPT); CU_ASSERT_EQUAL(ctx.stats.errors, 0); run_message(&ctx, MSG_TRUE); CU_ASSERT_EQUAL(ctx.stats.errors, 0); CU_ASSERT_EQUAL(ctx.stats.actions, 1); CU_ASSERT_EQUAL(ctx.stats.redirects, 1); CU_ASSERT_EQUAL(ctx.stats.keeps, 0); CU_ASSERT_STRING_EQUAL(ctx.redirected_to, "me@blah.com"); run_message(&ctx, MSG_FALSE); CU_ASSERT_EQUAL(ctx.stats.errors, 0); CU_ASSERT_EQUAL(ctx.stats.actions, 2); CU_ASSERT_EQUAL(ctx.stats.redirects, 1); CU_ASSERT_EQUAL(ctx.stats.keeps, 1); CU_ASSERT_STRING_EQUAL(ctx.redirected_to, "me@blah.com"); context_cleanup(&ctx); } static void test_address_index(void) { static const char SCRIPT[] = "require [\"index\"];\n" "if address :index 2 :is \"from\" \"zme@true.com\"\n" "{redirect \"me@blah.com\";}\n" ; static const char SCRIPT_LAST[] = "require [\"index\"];\n" "if address :index 3 :last :is \"from\" \"zme@true.com\"\n" "{redirect \"me@blah.com\";}\n" ; static const char MSG_TRUE[] = "Date: Mon, 25 Jan 2003 08:51:06 -0500\r\n" "From: zme@false.com\r\n" "From: zme@true.com\r\n" "From: zme@false.com\r\n" "From: zme@false.com\r\n" "To: you\r\n" "Subject: simple address test\r\n" "\r\n" "blah\n" ; static const char MSG_FALSE[] = "Date: Mon, 25 Jan 2003 08:51:06 -0500\r\n" "From: zme@true.com\r\n" "From: zme@false.com\r\n" "From: zme@true.com\r\n" "From: zme@true.com\r\n" "To: you\r\n" "Subject: simple address test\r\n" "\r\n" "blah\n" ; sieve_test_context_t ctx; /* Test :index */ context_setup(&ctx, SCRIPT); CU_ASSERT_EQUAL(ctx.stats.errors, 0); run_message(&ctx, MSG_TRUE); CU_ASSERT_EQUAL(ctx.stats.errors, 0); CU_ASSERT_EQUAL(ctx.stats.actions, 1); CU_ASSERT_EQUAL(ctx.stats.redirects, 1); CU_ASSERT_EQUAL(ctx.stats.keeps, 0); CU_ASSERT_STRING_EQUAL(ctx.redirected_to, "me@blah.com"); run_message(&ctx, MSG_FALSE); CU_ASSERT_EQUAL(ctx.stats.errors, 0); CU_ASSERT_EQUAL(ctx.stats.actions, 2); CU_ASSERT_EQUAL(ctx.stats.redirects, 1); CU_ASSERT_EQUAL(ctx.stats.keeps, 1); CU_ASSERT_STRING_EQUAL(ctx.redirected_to, "me@blah.com"); context_cleanup(&ctx); /* Test :index :last */ context_setup(&ctx, SCRIPT_LAST); CU_ASSERT_EQUAL(ctx.stats.errors, 0); run_message(&ctx, MSG_TRUE); CU_ASSERT_EQUAL(ctx.stats.errors, 0); CU_ASSERT_EQUAL(ctx.stats.actions, 1); CU_ASSERT_EQUAL(ctx.stats.redirects, 1); CU_ASSERT_EQUAL(ctx.stats.keeps, 0); CU_ASSERT_STRING_EQUAL(ctx.redirected_to, "me@blah.com"); run_message(&ctx, MSG_FALSE); CU_ASSERT_EQUAL(ctx.stats.errors, 0); CU_ASSERT_EQUAL(ctx.stats.actions, 2); CU_ASSERT_EQUAL(ctx.stats.redirects, 1); CU_ASSERT_EQUAL(ctx.stats.keeps, 1); CU_ASSERT_STRING_EQUAL(ctx.redirected_to, "me@blah.com"); context_cleanup(&ctx); } static void test_header_index(void) { static const char SCRIPT[] = "require [\"index\"];\n" "if header :index 3 :is \"X-Virus-Status\" \"Clean\"\n" "{redirect \"me@blah.com\";}\n" ; static const char SCRIPT_LAST[] = "require [\"index\"];\n" "if header :index 2 :last :is \"X-Virus-Status\" \"Clean\"\n" "{redirect \"me@blah.com\";}\n" ; static const char MSG_TRUE[] = "Date: Mon, 25 Jan 2003 08:51:06 -0500\r\n" "From: zme@true.com\r\n" "To: you\r\n" "Subject: simple address test\r\n" "X-Virus-Status: *****\r\n" "X-Virus-Status: *****\r\n" "X-Virus-Status: Clean\r\n" "X-Virus-Status: *****\r\n" "\r\n" "blah\n" ; static const char MSG_FALSE[] = "Date: Mon, 25 Jan 2003 08:51:06 -0500\r\n" "From: zme@false.com\r\n" "To: you\r\n" "Subject: simple address test\r\n" "X-Virus-Status: Clean\r\n" "X-Virus-Status: Clean\r\n" "X-Virus-Status: *****\r\n" "X-Virus-Status: Clean\r\n" "\r\n" "blah\n" ; sieve_test_context_t ctx; /* Test :index */ context_setup(&ctx, SCRIPT); CU_ASSERT_EQUAL(ctx.stats.errors, 0); run_message(&ctx, MSG_TRUE); CU_ASSERT_EQUAL(ctx.stats.errors, 0); CU_ASSERT_EQUAL(ctx.stats.actions, 1); CU_ASSERT_EQUAL(ctx.stats.redirects, 1); CU_ASSERT_EQUAL(ctx.stats.keeps, 0); CU_ASSERT_STRING_EQUAL(ctx.redirected_to, "me@blah.com"); run_message(&ctx, MSG_FALSE); CU_ASSERT_EQUAL(ctx.stats.errors, 0); CU_ASSERT_EQUAL(ctx.stats.actions, 2); CU_ASSERT_EQUAL(ctx.stats.redirects, 1); CU_ASSERT_EQUAL(ctx.stats.keeps, 1); CU_ASSERT_STRING_EQUAL(ctx.redirected_to, "me@blah.com"); context_cleanup(&ctx); /* Test :index :last */ context_setup(&ctx, SCRIPT_LAST); CU_ASSERT_EQUAL(ctx.stats.errors, 0); run_message(&ctx, MSG_TRUE); CU_ASSERT_EQUAL(ctx.stats.errors, 0); CU_ASSERT_EQUAL(ctx.stats.actions, 1); CU_ASSERT_EQUAL(ctx.stats.redirects, 1); CU_ASSERT_EQUAL(ctx.stats.keeps, 0); CU_ASSERT_STRING_EQUAL(ctx.redirected_to, "me@blah.com"); run_message(&ctx, MSG_FALSE); CU_ASSERT_EQUAL(ctx.stats.errors, 0); CU_ASSERT_EQUAL(ctx.stats.actions, 2); CU_ASSERT_EQUAL(ctx.stats.redirects, 1); CU_ASSERT_EQUAL(ctx.stats.keeps, 1); CU_ASSERT_STRING_EQUAL(ctx.redirected_to, "me@blah.com"); context_cleanup(&ctx); } static void test_date_year(void) { static const char SCRIPT[] = "require [\"date\", \"index\"];\n" "if date :index 1 :last :is \"received\" \"year\" [ \"1983\", \"1993\", \"2003\", \"2013\" ]\n" "{redirect \"me@blah.com\";}\n" ; static const char MSG_TRUE[] = "Date: Sat, 16 Nov 2013 12:46:49 +1100\r\n" "Received: from localhost (localhost [127.0.0.1])\r\n" " by mail.com (Cyrus v2.3.16) with LMTPA;\r\n" " Tue, 16 Nov 2010 12:50:12 +1100\r\n" "Received: from localhost (localhost [127.0.0.1])\r\n" " by mail.com (Cyrus v2.3.16) with LMTPA;\r\n" " Tue, 16 Nov 2013 12:50:12 +1100\r\n" "From: zme@true.com\r\n" "To: you\r\n" "Subject: simple address test\r\n" "\r\n" "blah\n" ; static const char MSG_FALSE[] = "Date: Tue, 16 Nov 2010 12:46:49 +1100\r\n" "Received: from localhost (localhost [127.0.0.1])\r\n" " by mail.com (Cyrus v2.3.16) with LMTPA;\r\n" " Tue, 16 Nov 2013 12:50:12 +1100\r\n" "Received: from localhost (localhost [127.0.0.1])\r\n" " by mail.com (Cyrus v2.3.16) with LMTPA;\r\n" " Tue, 16 Nov 2010 12:50:12 +1100\r\n" "From: yme@false.com\r\n" "To: you\r\n" "Subject: simple address test\r\n" "\r\n" "blah\n" ; sieve_test_context_t ctx; context_setup(&ctx, SCRIPT); CU_ASSERT_EQUAL(ctx.stats.errors, 0); run_message(&ctx, MSG_TRUE); CU_ASSERT_EQUAL(ctx.stats.errors, 0); CU_ASSERT_EQUAL(ctx.stats.actions, 1); CU_ASSERT_EQUAL(ctx.stats.redirects, 1); CU_ASSERT_EQUAL(ctx.stats.keeps, 0); CU_ASSERT_STRING_EQUAL(ctx.redirected_to, "me@blah.com"); run_message(&ctx, MSG_FALSE); CU_ASSERT_EQUAL(ctx.stats.errors, 0); CU_ASSERT_EQUAL(ctx.stats.actions, 2); CU_ASSERT_EQUAL(ctx.stats.redirects, 1); CU_ASSERT_EQUAL(ctx.stats.keeps, 1); CU_ASSERT_STRING_EQUAL(ctx.redirected_to, "me@blah.com"); context_cleanup(&ctx); } static void test_date_zone_month(void) { static const char SCRIPT[] = "require [\"date\"];\n" "if date :is :zone \"-0800\" \"date\" \"month\" \"11\"\n" "{redirect \"me@blah.com\";}\n" ; static const char MSG_TRUE[] = "Date: Fri, 1 Nov 2013 19:46:49 +1100\r\n" "From: zme@true.com\r\n" "To: you\r\n" "Subject: simple address test\r\n" "\r\n" "blah\n" ; static const char MSG_FALSE[] = "Date: Fri, 1 Nov 2013 11:46:49 +1100\r\n" "From: yme@false.com\r\n" "To: you\r\n" "Subject: simple address test\r\n" "\r\n" "blah\n" ; sieve_test_context_t ctx; context_setup(&ctx, SCRIPT); CU_ASSERT_EQUAL(ctx.stats.errors, 0); run_message(&ctx, MSG_TRUE); CU_ASSERT_EQUAL(ctx.stats.errors, 0); CU_ASSERT_EQUAL(ctx.stats.actions, 1); CU_ASSERT_EQUAL(ctx.stats.redirects, 1); CU_ASSERT_EQUAL(ctx.stats.keeps, 0); CU_ASSERT_STRING_EQUAL(ctx.redirected_to, "me@blah.com"); run_message(&ctx, MSG_FALSE); CU_ASSERT_EQUAL(ctx.stats.errors, 0); CU_ASSERT_EQUAL(ctx.stats.actions, 2); CU_ASSERT_EQUAL(ctx.stats.redirects, 1); CU_ASSERT_EQUAL(ctx.stats.keeps, 1); CU_ASSERT_STRING_EQUAL(ctx.redirected_to, "me@blah.com"); context_cleanup(&ctx); } static void test_date_date(void) { static const char SCRIPT[] = "require [\"date\"];\n" "if date :is :originalzone \"date\" \"date\" \"2013-11-02\"\n" "{redirect \"me@blah.com\";}\n" ; static const char MSG_TRUE[] = "Date: Sat, 2 Nov 2013 19:46:49 +1100\r\n" "From: zme@true.com\r\n" "To: you\r\n" "Subject: simple address test\r\n" "\r\n" "blah\n" ; static const char MSG_FALSE[] = "Date: Fri, 1 Nov 2013 19:45:49 +1100\r\n" "From: yme@false.com\r\n" "To: you\r\n" "Subject: simple address test\r\n" "\r\n" "blah\n" ; sieve_test_context_t ctx; context_setup(&ctx, SCRIPT); CU_ASSERT_EQUAL(ctx.stats.errors, 0); run_message(&ctx, MSG_TRUE); CU_ASSERT_EQUAL(ctx.stats.errors, 0); CU_ASSERT_EQUAL(ctx.stats.actions, 1); CU_ASSERT_EQUAL(ctx.stats.redirects, 1); CU_ASSERT_EQUAL(ctx.stats.keeps, 0); CU_ASSERT_STRING_EQUAL(ctx.redirected_to, "me@blah.com"); run_message(&ctx, MSG_FALSE); CU_ASSERT_EQUAL(ctx.stats.errors, 0); CU_ASSERT_EQUAL(ctx.stats.actions, 2); CU_ASSERT_EQUAL(ctx.stats.redirects, 1); CU_ASSERT_EQUAL(ctx.stats.keeps, 1); CU_ASSERT_STRING_EQUAL(ctx.redirected_to, "me@blah.com"); context_cleanup(&ctx); } static void test_date_time(void) { static const char SCRIPT[] = "require [\"date\"];\n" "if date :is :originalzone \"date\" \"time\" \"19:46:49\"\n" "{redirect \"me@blah.com\";}\n" ; static const char MSG_TRUE[] = "Date: Sat, 2 Nov 2013 19:46:49 +1100\r\n" "From: zme@true.com\r\n" "To: you\r\n" "Subject: simple address test\r\n" "\r\n" "blah\n" ; static const char MSG_FALSE[] = "Date: Sat, 2 Nov 2013 19:45:49 +1100\r\n" "From: yme@false.com\r\n" "To: you\r\n" "Subject: simple address test\r\n" "\r\n" "blah\n" ; sieve_test_context_t ctx; context_setup(&ctx, SCRIPT); CU_ASSERT_EQUAL(ctx.stats.errors, 0); run_message(&ctx, MSG_TRUE); CU_ASSERT_EQUAL(ctx.stats.errors, 0); CU_ASSERT_EQUAL(ctx.stats.actions, 1); CU_ASSERT_EQUAL(ctx.stats.redirects, 1); CU_ASSERT_EQUAL(ctx.stats.keeps, 0); CU_ASSERT_STRING_EQUAL(ctx.redirected_to, "me@blah.com"); run_message(&ctx, MSG_FALSE); CU_ASSERT_EQUAL(ctx.stats.errors, 0); CU_ASSERT_EQUAL(ctx.stats.actions, 2); CU_ASSERT_EQUAL(ctx.stats.redirects, 1); CU_ASSERT_EQUAL(ctx.stats.keeps, 1); CU_ASSERT_STRING_EQUAL(ctx.redirected_to, "me@blah.com"); context_cleanup(&ctx); } static void test_date_originalzone_day(void) { static const char SCRIPT[] = "require [\"date\"];\n" "if date :is :originalzone \"date\" \"day\" \"16\"\n" "{redirect \"me@blah.com\";}\n" ; static const char MSG_TRUE[] = "Date: Sat, 16 Nov 2013 12:46:49 +1100\r\n" "From: zme@true.com\r\n" "To: you\r\n" "Subject: simple address test\r\n" "\r\n" "blah\n" ; static const char MSG_FALSE[] = "Date: Fri, 15 Nov 2013 12:46:49 +1100\r\n" "From: yme@false.com\r\n" "To: you\r\n" "Subject: simple address test\r\n" "\r\n" "blah\n" ; sieve_test_context_t ctx; context_setup(&ctx, SCRIPT); CU_ASSERT_EQUAL(ctx.stats.errors, 0); run_message(&ctx, MSG_TRUE); CU_ASSERT_EQUAL(ctx.stats.errors, 0); CU_ASSERT_EQUAL(ctx.stats.actions, 1); CU_ASSERT_EQUAL(ctx.stats.redirects, 1); CU_ASSERT_EQUAL(ctx.stats.keeps, 0); CU_ASSERT_STRING_EQUAL(ctx.redirected_to, "me@blah.com"); run_message(&ctx, MSG_FALSE); CU_ASSERT_EQUAL(ctx.stats.errors, 0); CU_ASSERT_EQUAL(ctx.stats.actions, 2); CU_ASSERT_EQUAL(ctx.stats.redirects, 1); CU_ASSERT_EQUAL(ctx.stats.keeps, 1); CU_ASSERT_STRING_EQUAL(ctx.redirected_to, "me@blah.com"); context_cleanup(&ctx); } static void test_date_weekend_weekday(void) { static const char SCRIPT[] = "require [\"date\"];\n" "if anyof(date :is :zone \"-0800\" \"date\" \"weekday\" \"0\",\n" " date :is :zone \"-0800\" \"date\" \"weekday\" \"6\")\n" "{redirect \"me@blah.com\";}\n" ; static const char MSG_TRUE[] = "Date: Sat, 2 Nov 2013 19:46:49 +1100\r\n" "From: zme@true.com\r\n" "To: you\r\n" "Subject: simple address test\r\n" "\r\n" "blah\n" ; static const char MSG_FALSE[] = "Date: Fri, 1 Nov 2013 11:46:49 +1100\r\n" "From: yme@false.com\r\n" "To: you\r\n" "Subject: simple address test\r\n" "\r\n" "blah\n" ; sieve_test_context_t ctx; context_setup(&ctx, SCRIPT); CU_ASSERT_EQUAL(ctx.stats.errors, 0); run_message(&ctx, MSG_TRUE); CU_ASSERT_EQUAL(ctx.stats.errors, 0); CU_ASSERT_EQUAL(ctx.stats.actions, 1); CU_ASSERT_EQUAL(ctx.stats.redirects, 1); CU_ASSERT_EQUAL(ctx.stats.keeps, 0); CU_ASSERT_STRING_EQUAL(ctx.redirected_to, "me@blah.com"); run_message(&ctx, MSG_FALSE); CU_ASSERT_EQUAL(ctx.stats.errors, 0); CU_ASSERT_EQUAL(ctx.stats.actions, 2); CU_ASSERT_EQUAL(ctx.stats.redirects, 1); CU_ASSERT_EQUAL(ctx.stats.keeps, 1); CU_ASSERT_STRING_EQUAL(ctx.redirected_to, "me@blah.com"); context_cleanup(&ctx); } static void test_date_zone(void) { static const char SCRIPT[] = "require [\"date\"];\n" "if date :is :originalzone \"date\" \"zone\" \"+1100\"\n" "{redirect \"me@blah.com\";}\n" ; static const char MSG_TRUE[] = "Date: Sat, 2 Nov 2013 19:46:49 +1100\r\n" "From: zme@true.com\r\n" "To: you\r\n" "Subject: simple address test\r\n" "\r\n" "blah\n" ; static const char MSG_FALSE[] = "Date: Fri, 1 Nov 2013 11:46:49 -0700\r\n" "From: yme@false.com\r\n" "To: you\r\n" "Subject: simple address test\r\n" "\r\n" "blah\n" ; sieve_test_context_t ctx; context_setup(&ctx, SCRIPT); CU_ASSERT_EQUAL(ctx.stats.errors, 0); run_message(&ctx, MSG_TRUE); CU_ASSERT_EQUAL(ctx.stats.errors, 0); CU_ASSERT_EQUAL(ctx.stats.actions, 1); CU_ASSERT_EQUAL(ctx.stats.redirects, 1); CU_ASSERT_EQUAL(ctx.stats.keeps, 0); CU_ASSERT_STRING_EQUAL(ctx.redirected_to, "me@blah.com"); run_message(&ctx, MSG_FALSE); CU_ASSERT_EQUAL(ctx.stats.errors, 0); CU_ASSERT_EQUAL(ctx.stats.actions, 2); CU_ASSERT_EQUAL(ctx.stats.redirects, 1); CU_ASSERT_EQUAL(ctx.stats.keeps, 1); CU_ASSERT_STRING_EQUAL(ctx.redirected_to, "me@blah.com"); context_cleanup(&ctx); } static void test_currentdate_true(void) { static const char SCRIPT[] = "require [\"date\", \"relational\"];\n" "if allof(currentdate :zone \"+0000\" :value \"ge\" \"date\" \"2014-01-01\",\n" " currentdate :zone \"+0000\" :value \"le\" \"date\" \"2114-01-01\")\n" "{redirect \"me@blah.com\";}\n" ; static const char MSG_TRUE[] = "Date: Tue, 16 Nov 2010 12:46:49 +1100\r\n" "From: yme@true.com\r\n" "To: you\r\n" "Subject: simple address test\r\n" "\r\n" "blah\n" ; sieve_test_context_t ctx; context_setup(&ctx, SCRIPT); CU_ASSERT_EQUAL(ctx.stats.errors, 0); run_message(&ctx, MSG_TRUE); CU_ASSERT_EQUAL(ctx.stats.errors, 0); CU_ASSERT_EQUAL(ctx.stats.actions, 1); CU_ASSERT_EQUAL(ctx.stats.redirects, 1); CU_ASSERT_EQUAL(ctx.stats.keeps, 0); CU_ASSERT_STRING_EQUAL(ctx.redirected_to, "me@blah.com"); context_cleanup(&ctx); } static void test_currentdate_false(void) { static const char SCRIPT[] = "require [\"date\", \"relational\"];\n" "if allof(currentdate :zone \"+0000\" :value \"ge\" \"date\" \"1970-01-01\",\n" " currentdate :zone \"+0000\" :value \"le\" \"date\" \"2014-01-01\")\n" "{redirect \"me@blah.com\";}\n" ; static const char MSG_FALSE[] = "Date: Tue, 16 Nov 2010 12:46:49 +1100\r\n" "From: yme@false.com\r\n" "To: you\r\n" "Subject: simple address test\r\n" "\r\n" "blah\n" ; sieve_test_context_t ctx; context_setup(&ctx, SCRIPT); CU_ASSERT_EQUAL(ctx.stats.errors, 0); run_message(&ctx, MSG_FALSE); CU_ASSERT_EQUAL(ctx.stats.errors, 0); CU_ASSERT_EQUAL(ctx.stats.actions, 1); CU_ASSERT_EQUAL(ctx.stats.redirects, 0); CU_ASSERT_EQUAL(ctx.stats.keeps, 1); CU_ASSERT_STRING_EQUAL(ctx.redirected_to, NULL); context_cleanup(&ctx); } // TODO: test // if size :over 10K { redirect "me@blah.com"; } // TODO: test // if true {...} // // if false {...} // // if not false {...} // // if true {...} else {...} // // if false {...} elsif true {...} else {...} // // if false {...} elsif false {...} else {...} // // if false {} else {...} // // if true { if true { if true { ... } } } // // if allof(false, false) {...} else {...} // // if allof(false,true) {...} else {...} // // if allof(true,false) {...} else {...} // // if allof(true,true) {...} else {...} // // if anyof(false, false) {...} else {...} // // if anyof(false,true) {...} else {...} // // if anyof(true,false) {...} else {...} // // if anyof(true,true) {...} else {...} /* vim: set ft=c: */ cyrus-imapd-2.5.10/cunit/cert.pem0000644000175000017500000000643113001236020013526 00000000000000Certificate: Data: Version: 3 (0x2) Serial Number: dc:ff:1e:12:b0:0b:b6:a1 Signature Algorithm: sha1WithRSAEncryption Issuer: C=AU, ST=Victoria, O=Cyrus IMAP Testers, Inc., OU=SSL Wrangling, CN=Greg Banks/emailAddress=gnb@fastmail.fm Validity Not Before: Feb 1 07:40:55 2011 GMT Not After : Feb 1 07:40:55 2012 GMT Subject: C=AU, ST=Victoria, O=Cyrus IMAP Testers, Inc., OU=SSL Wranglers, CN=Greg Banks/emailAddress=gnb@fastmail.fm Subject Public Key Info: Public Key Algorithm: rsaEncryption RSA Public Key: (1024 bit) Modulus (1024 bit): 00:f2:cc:96:27:92:93:ad:56:9c:78:85:68:d0:bd: 00:00:62:7a:d5:22:b3:54:f0:4a:1b:bc:18:8d:7e: 37:1f:cb:b0:04:ab:d8:91:55:37:c8:89:79:2f:94: cd:02:d3:34:0f:49:ca:68:80:1c:8b:9b:be:43:c4: 8f:a1:53:04:a8:35:b7:8d:d8:67:ec:92:30:89:87: 55:0b:a9:9d:45:37:88:af:ea:99:64:11:9c:5e:c2: d5:95:17:df:37:23:f1:0c:75:e9:0b:b6:1e:b0:80: 7d:a0:da:87:6c:80:3f:73:72:f4:d4:b4:5d:54:78: 07:6b:ef:7f:7f:0a:08:84:bb Exponent: 65537 (0x10001) X509v3 extensions: X509v3 Basic Constraints: CA:FALSE Netscape Comment: OpenSSL Generated Certificate X509v3 Subject Key Identifier: 96:48:A2:12:B6:AD:DC:B8:94:D4:4E:46:94:C4:1E:AF:32:4C:B9:01 X509v3 Authority Key Identifier: keyid:D3:8D:00:56:9B:71:99:CE:00:44:F4:86:98:AE:A9:78:AB:20:17:8A Signature Algorithm: sha1WithRSAEncryption 7a:4c:82:b7:55:31:76:89:44:08:57:0d:c9:df:82:e7:1f:94: b1:5f:a6:bc:93:63:d7:90:74:25:b0:0b:5b:eb:b6:d0:46:e3: 59:34:8c:e8:46:7a:33:af:b6:4d:3f:b8:0a:dd:89:51:22:f2: f8:26:97:9e:4b:62:8a:10:f4:87:0c:cb:53:ff:c8:2b:a2:95: 0e:02:65:e5:97:b5:ad:c6:87:25:c9:dc:35:b5:c7:e2:4d:d5: cb:dd:a7:2a:e4:0f:7e:e1:a3:b8:fa:11:02:61:0e:04:2b:3a: a7:73:80:e1:26:24:24:6c:fb:35:50:31:6e:ce:15:53:c7:43: 1a:60 -----BEGIN CERTIFICATE----- MIIDGzCCAoSgAwIBAgIJANz/HhKwC7ahMA0GCSqGSIb3DQEBBQUAMIGQMQswCQYD VQQGEwJBVTERMA8GA1UECBMIVmljdG9yaWExITAfBgNVBAoTGEN5cnVzIElNQVAg VGVzdGVycywgSW5jLjEWMBQGA1UECxMNU1NMIFdyYW5nbGluZzETMBEGA1UEAxMK R3JlZyBCYW5rczEeMBwGCSqGSIb3DQEJARYPZ25iQGZhc3RtYWlsLmZtMB4XDTEx MDIwMTA3NDA1NVoXDTEyMDIwMTA3NDA1NVowgZAxCzAJBgNVBAYTAkFVMREwDwYD VQQIEwhWaWN0b3JpYTEhMB8GA1UEChMYQ3lydXMgSU1BUCBUZXN0ZXJzLCBJbmMu MRYwFAYDVQQLEw1TU0wgV3JhbmdsZXJzMRMwEQYDVQQDEwpHcmVnIEJhbmtzMR4w HAYJKoZIhvcNAQkBFg9nbmJAZmFzdG1haWwuZm0wgZ8wDQYJKoZIhvcNAQEBBQAD gY0AMIGJAoGBAPLMlieSk61WnHiFaNC9AABietUis1TwShu8GI1+Nx/LsASr2JFV N8iJeS+UzQLTNA9JymiAHIubvkPEj6FTBKg1t43YZ+ySMImHVQupnUU3iK/qmWQR nF7C1ZUX3zcj8Qx16Qu2HrCAfaDah2yAP3Ny9NS0XVR4B2vvf38KCIS7AgMBAAGj ezB5MAkGA1UdEwQCMAAwLAYJYIZIAYb4QgENBB8WHU9wZW5TU0wgR2VuZXJhdGVk IENlcnRpZmljYXRlMB0GA1UdDgQWBBSWSKIStq3cuJTUTkaUxB6vMky5ATAfBgNV HSMEGDAWgBTTjQBWm3GZzgBE9IaYrql4qyAXijANBgkqhkiG9w0BAQUFAAOBgQB6 TIK3VTF2iUQIVw3J34LnH5SxX6a8k2PXkHQlsAtb67bQRuNZNIzoRnozr7ZNP7gK 3YlRIvL4JpeeS2KKEPSHDMtT/8gropUOAmXll7Wtxoclydw1tcfiTdXL3acq5A9+ 4aO4+hECYQ4EKzqnc4DhJiQkbPs1UDFuzhVTx0MaYA== -----END CERTIFICATE----- cyrus-imapd-2.5.10/cunit/vg.supp0000644000175000017500000000725412772415051013440 00000000000000# Valgrind suppressions file for Cyrus unit tests # # Copyright (c) 1994-2011 Carnegie Mellon University. All rights reserved. # # Redistribution and use in source and binary forms, with or without # modification, are permitted provided that the following conditions # are met: # # 1. Redistributions of source code must retain the above copyright # notice, this list of conditions and the following disclaimer. # # 2. Redistributions in binary form must reproduce the above copyright # notice, this list of conditions and the following disclaimer in # the documentation and/or other materials provided with the # distribution. # # 3. The name "Carnegie Mellon University" must not be used to # endorse or promote products derived from this software without # prior written permission. For permission or any legal # details, please contact # Carnegie Mellon University # Center for Technology Transfer and Enterprise Creation # 4615 Forbes Avenue # Suite 302 # Pittsburgh, PA 15213 # (412) 268-7393, fax: (412) 268-7395 # innovation@andrew.cmu.edu # # 4. Redistributions of any form whatsoever must retain the following # acknowledgment: # "This product includes software developed by Computing Services # at Carnegie Mellon University (http://www.cmu.edu/computing/)." # # CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO # THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY # AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE # FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES # WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN # AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING # OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. # { bdb_environment_leak Memcheck:Leak fun:malloc ... fun:__env_config fun:__env_open ... fun:init fun:cyrusdb_init ... } { getpwnam_leak Memcheck:Leak fun:malloc ... fun:__nss_database_lookup ... fun:getpwnam ... } { getgrouplist_leak Memcheck:Leak fun:malloc ... fun:__nss_database_lookup ... fun:getgrouplist ... } { getpwuid_leak Memcheck:Leak fun:malloc ... fun:__nss_database_lookup ... fun:getpwuid ... } { zlib_inflateInit2_cond Memcheck:Cond fun:inflateReset2 fun:inflateInit2_ fun:prot_setcompress ... } { zlib_inflateInit2_cond Memcheck:Cond fun:inflateReset2 fun:inflateInit2_ fun:buf_inflate ... } { zlib_deflate_cond Memcheck:Cond fun:memcpy ... fun:deflate fun:prot_flush_encode ... } { zlib_deflate_data4 Memcheck:Value4 fun:memcpy ... fun:deflate fun:prot_flush_encode ... } { zlib_deflate_data8 Memcheck:Value8 fun:memcpy ... fun:deflate fun:prot_flush_encode ... } { libcrypto_bugs_1 Memcheck:Cond ... fun:X509_verify ... } { libcrypto_bugs_2 Memcheck:Cond ... fun:RSA_sign ... } { libcrypto_bugs_3 Memcheck:Cond ... fun:DH_generate_key ... } { libcrypto_bugs_4 Memcheck:Cond ... fun:DH_compute_key ... } { libcrypto_bugs_5 Memcheck:Cond ... fun:RSA_setup_blinding ... } { libcrypto_bugs_6 Memcheck:Leak fun:malloc ... fun:get_dh1024 ... fun:tls_init_serverengine ... } { # This function is part of the unit tests and deliberately # passes bogus mappings to msync() in the expectation of # generating an error from the kernel. is_valid_mapping Memcheck:Param msync(start) fun:__msync_nocancel fun:is_valid_mapping ... } cyrus-imapd-2.5.10/cunit/db.testc0000644000175000017500000013316213001236020013521 00000000000000#include "config.h" #include "cunit/cunit.h" #include "xmalloc.h" #include "imap/global.h" #include "retry.h" #include "cyrusdb.h" #include "libcyr_cfg.h" #include "util.h" #include "hash.h" #define DBDIR "test-mb-dbdir" struct binary_result { struct binary_result *next; char *key; size_t keylen; char *data; size_t datalen; }; static char *backend = CUNIT_PARAM("skiplist,flat,berkeley,twoskip"); static char *filename; static char *filename2; static void config_read_string(const char *s) { char *fname = xstrdup("/tmp/cyrus-cunit-configXXXXXX"); int fd = mkstemp(fname); retry_write(fd, s, strlen(s)); config_reset(); config_read(fname, 0); unlink(fname); free(fname); close(fd); } static int fexists(const char *fname) { struct stat sb; int r; r = stat(fname, &sb); if (r < 0) r = -errno; return r; } static char *make_basedir(const char * const *reldirs) { int r; int unique = 0; const char *tmpdir; char *basedir; char path[PATH_MAX]; const char * const *d; tmpdir = getenv("TMPDIR"); if (!tmpdir) tmpdir = "/tmp"; for (;;) { if (unique) snprintf(path, sizeof(path), "%s/cunit-db-test.%d.%d", tmpdir, getpid(), unique); else snprintf(path, sizeof(path), "%s/cunit-db-test.%d", tmpdir, getpid()); r = mkdir(path, 0700); if (!r) break; /* success! */ if (errno != EEXIST) { perror(path); return NULL; } unique++; } basedir = xstrdup(path); for (d = reldirs ; *d ; d++) { snprintf(path, sizeof(path), "%s/%s", basedir, *d); r = mkdir(path, 0700); if (r < 0) { perror(path); free(basedir); return NULL; } } return basedir; } #define CANSTORE(key, keylen, data, datalen) \ r = cyrusdb_store(db, key, keylen, data, datalen, &txn); \ CU_ASSERT_EQUAL(r, CYRUSDB_OK); \ CU_ASSERT_PTR_NOT_NULL(txn); #define BADDATA ((const char *)0xdeadbeef) #define BADLEN ((int)0xcafebabe) #define CANFETCH(key, keylen, expdata, expdatalen) \ { \ const char *_data = BADDATA; \ size_t _datalen = BADLEN; \ r = cyrusdb_fetch(db, key, keylen, &_data, &_datalen, &txn); \ CU_ASSERT_EQUAL(r, CYRUSDB_OK); \ CU_ASSERT_PTR_NOT_NULL(txn); \ CU_ASSERT_PTR_NOT_NULL(_data); \ CU_ASSERT_PTR_NOT_EQUAL(_data, BADDATA); \ CU_ASSERT_PTR_NOT_EQUAL(_data, expdata); \ CU_ASSERT_NOT_EQUAL(_datalen, BADLEN); \ CU_ASSERT_EQUAL(_datalen, expdatalen); \ CU_ASSERT(!memcmp(_data, expdata, _datalen)); \ } #define CANFETCH_NOTXN(key, keylen, expdata, expdatalen) \ { \ const char *_data = BADDATA; \ size_t _datalen = BADLEN; \ r = cyrusdb_fetch(db, key, keylen, &_data, &_datalen, NULL); \ CU_ASSERT_EQUAL(r, CYRUSDB_OK); \ CU_ASSERT_PTR_NOT_NULL(_data); \ CU_ASSERT_PTR_NOT_EQUAL(_data, BADDATA); \ CU_ASSERT_PTR_NOT_EQUAL(_data, expdata); \ CU_ASSERT_NOT_EQUAL(_datalen, BADLEN); \ CU_ASSERT_EQUAL(_datalen, expdatalen); \ CU_ASSERT(!memcmp(_data, expdata, _datalen)); \ } #define CANFETCHNEXT(key, keylen, expkey, expkeylen, expdata, expdatalen) \ { \ const char *_data = BADDATA; \ size_t _datalen = BADLEN; \ const char *_key = BADDATA; \ size_t _keylen = BADLEN; \ r = cyrusdb_fetchnext(db, key, keylen, &_key, &_keylen, &_data, &_datalen, &txn); \ CU_ASSERT_EQUAL(r, CYRUSDB_OK); \ CU_ASSERT_PTR_NOT_NULL(txn); \ CU_ASSERT_PTR_NOT_NULL(_data); \ CU_ASSERT_PTR_NOT_NULL(_key); \ CU_ASSERT_PTR_NOT_EQUAL(_data, BADDATA); \ CU_ASSERT_PTR_NOT_EQUAL(_data, expdata); \ CU_ASSERT_PTR_NOT_EQUAL(_key, BADDATA); \ CU_ASSERT_PTR_NOT_EQUAL(_key, expdata); \ CU_ASSERT_NOT_EQUAL(_datalen, BADLEN); \ CU_ASSERT_NOT_EQUAL(_keylen, BADLEN); \ CU_ASSERT_EQUAL(_datalen, expdatalen); \ CU_ASSERT(!memcmp(_data, expdata, _datalen)); \ CU_ASSERT_EQUAL(_keylen, expkeylen); \ CU_ASSERT(!memcmp(_key, expkey, _keylen)); \ } #define CANNOTFETCH(key, keylen, experror) \ { \ const char *_data = BADDATA; \ size_t _datalen = BADLEN; \ r = cyrusdb_fetch(db, key, keylen, &_data, &_datalen, &txn); \ CU_ASSERT_EQUAL(r, experror); \ CU_ASSERT_PTR_NOT_NULL(txn); \ CU_ASSERT_PTR_NULL(_data); \ CU_ASSERT_PTR_NOT_EQUAL(_data, BADDATA); \ CU_ASSERT_EQUAL(_datalen, 0); \ CU_ASSERT_NOT_EQUAL(_datalen, BADLEN); \ } #define CANNOTFETCHNEXT(key, keylen, experror) \ { \ r = cyrusdb_fetchnext(db, key, keylen, NULL, 0, NULL, 0, &txn); \ CU_ASSERT_EQUAL(r, experror); \ CU_ASSERT_PTR_NOT_NULL(txn); \ } #define CANCOMMIT() \ r = cyrusdb_commit(db, txn); \ CU_ASSERT_EQUAL(r, CYRUSDB_OK); \ txn = NULL; #define CANREOPEN() \ r = cyrusdb_close(db); \ db = NULL; \ CU_ASSERT_EQUAL(r, CYRUSDB_OK); \ r = cyrusdb_open(backend, filename, 0, &db); \ CU_ASSERT_EQUAL(r, CYRUSDB_OK); \ CU_ASSERT_PTR_NOT_NULL(db); #define GOTRESULT(expkey, expkeylen, expdata, expdatalen) \ { \ const char *_key = (expkey); \ size_t _keylen = (expkeylen); \ const char *_data = (expdata); \ size_t _datalen = (expdatalen); \ struct binary_result *actual = results; \ CU_ASSERT_PTR_NOT_NULL_FATAL(results); \ results = results->next; \ CU_ASSERT_EQUAL(_keylen, actual->keylen); \ CU_ASSERT_EQUAL(0, memcmp(_data, actual->data, _datalen)); \ CU_ASSERT_EQUAL(_datalen, actual->datalen); \ CU_ASSERT_EQUAL(0, memcmp(_key, actual->key, _keylen)); \ free(actual->key); \ free(actual->data); \ free(actual); \ } static void test_openclose(void) { struct db *db = NULL; int r; CU_ASSERT_EQUAL(fexists(filename), -ENOENT); /* open() without _CREATE fails with NOTFOUND * and doesn't create the db */ r = cyrusdb_open(backend, filename, 0, &db); CU_ASSERT(r == CYRUSDB_NOTFOUND || r == CYRUSDB_IOERROR); CU_ASSERT_PTR_NULL(db); CU_ASSERT_EQUAL(fexists(filename), -ENOENT); /* open() with _CREATE succeeds and creates the db */ r = cyrusdb_open(backend, filename, CYRUSDB_CREATE, &db); CU_ASSERT_EQUAL(r, CYRUSDB_OK); CU_ASSERT_PTR_NOT_NULL(db); CU_ASSERT_EQUAL(fexists(filename), 0); /* closing succeeds and leaves the file in place */ r = cyrusdb_close(db); CU_ASSERT_EQUAL(r, CYRUSDB_OK); CU_ASSERT_EQUAL(fexists(filename), 0); } static void test_multiopen(void) { struct db *db1 = NULL; struct txn *txn1 = NULL; struct db *db = NULL; struct txn *txn = NULL; int r; /* data courtesy hipsteripsum.me */ static const char KEY1[] = "mustache"; static const char DATA1[] = "blog lomo"; static const char KEY2[] = "cred"; static const char DATA2[] = "beard ethical"; static const char KEY3[] = "leggings"; static const char DATA3[] = "tumblr salvia"; CU_ASSERT_EQUAL(fexists(filename), -ENOENT); /* open() with _CREATE succeeds and creates the db */ r = cyrusdb_open(backend, filename, CYRUSDB_CREATE, &db); CU_ASSERT_EQUAL(r, CYRUSDB_OK); CU_ASSERT_PTR_NOT_NULL(db); CU_ASSERT_EQUAL(fexists(filename), 0); /* 1st txn starts */ CANSTORE(KEY1, strlen(KEY1), DATA1, strlen(DATA1)); CANCOMMIT(); /* 1st txn ends */ /* * Note: the transaction started on the first db reference is * carefully *not* left open when starting a transaction on the * second db reference. Supported nested transactions is actually * quite a challenge for some backends, and is NOT part of the Cyrus * DB semantics. All we're testing here is that both db references * work fine as long as the transactions do not overlap. */ db1 = db; txn1 = txn; { db = NULL; txn = NULL; /* a second open() with the same filename returns * another reference to the same db */ r = cyrusdb_open(backend, filename, 0, &db); CU_ASSERT_EQUAL(r, CYRUSDB_OK); CU_ASSERT_PTR_NOT_NULL(db); /* 2nd txn starts */ CANSTORE(KEY2, strlen(KEY2), DATA2, strlen(DATA2)); CANCOMMIT(); /* 2nd txn ends */ /* closing succeeds and leaves the file in place */ r = cyrusdb_close(db); CU_ASSERT_EQUAL(r, CYRUSDB_OK); CU_ASSERT_EQUAL(fexists(filename), 0); } db = db1; txn = txn1; /* the 1st db ref still works */ /* 3rd txn starts */ CANSTORE(KEY3, strlen(KEY3), DATA3, strlen(DATA3)); CANCOMMIT(); /* 3rd txn ends */ /* closing the other reference succeeds and leaves the file in place */ r = cyrusdb_close(db); CU_ASSERT_EQUAL(r, CYRUSDB_OK); CU_ASSERT_EQUAL(fexists(filename), 0); /* re-opening works */ r = cyrusdb_open(backend, filename, 0, &db); CU_ASSERT_EQUAL(r, CYRUSDB_OK); CU_ASSERT_PTR_NOT_NULL(db); CU_ASSERT_EQUAL(fexists(filename), 0); /* all the records are present in the file */ /* 4th txn starts */ CANFETCH(KEY1, strlen(KEY1), DATA1, strlen(DATA1)); CANFETCH(KEY2, strlen(KEY2), DATA2, strlen(DATA2)); CANFETCH(KEY3, strlen(KEY3), DATA3, strlen(DATA3)); CANCOMMIT(); /* 4th txn ends */ /* out of TXN works too */ CANFETCH_NOTXN(KEY1, strlen(KEY1), DATA1, strlen(DATA1)); CANFETCH_NOTXN(KEY2, strlen(KEY2), DATA2, strlen(DATA2)); CANFETCH_NOTXN(KEY3, strlen(KEY3), DATA3, strlen(DATA3)); r = cyrusdb_close(db); CU_ASSERT_EQUAL(r, CYRUSDB_OK); CU_ASSERT_EQUAL(fexists(filename), 0); } static void test_opentwo(void) { struct db *db1 = NULL; struct db *db2 = NULL; int r; CU_ASSERT_EQUAL(fexists(filename), -ENOENT); CU_ASSERT_EQUAL(fexists(filename2), -ENOENT); /* open() with _CREATE succeeds and creates the db */ r = cyrusdb_open(backend, filename, CYRUSDB_CREATE, &db1); CU_ASSERT_EQUAL(r, CYRUSDB_OK); CU_ASSERT_PTR_NOT_NULL(db1); CU_ASSERT_EQUAL(fexists(filename), 0); CU_ASSERT_EQUAL(fexists(filename2), -ENOENT); /* open() of the 2nd filename with _CREATE * succeeds and creates another separate db */ r = cyrusdb_open(backend, filename2, CYRUSDB_CREATE, &db2); CU_ASSERT_EQUAL(r, CYRUSDB_OK); CU_ASSERT_PTR_NOT_NULL(db2); CU_ASSERT_EQUAL(fexists(filename), 0); CU_ASSERT_EQUAL(fexists(filename2), 0); CU_ASSERT_PTR_NOT_EQUAL(db1, db2); /* closing succeeds and leaves the file in place */ r = cyrusdb_close(db1); CU_ASSERT_EQUAL(r, CYRUSDB_OK); /* closing the other reference succeeds and leaves the file in place */ r = cyrusdb_close(db2); CU_ASSERT_EQUAL(r, CYRUSDB_OK); CU_ASSERT_EQUAL(fexists(filename), 0); CU_ASSERT_EQUAL(fexists(filename2), 0); } static void test_readwrite(void) { struct db *db = NULL; struct txn *txn = NULL; static const char KEY[] = "skeleton"; static const char DATA[] = "dem bones dem bones dem thighbones"; int r; r = cyrusdb_open(backend, filename, CYRUSDB_CREATE, &db); CU_ASSERT_EQUAL(r, CYRUSDB_OK); CU_ASSERT_PTR_NOT_NULL(db); /* the database is initially empty, so fetch will fail */ CANNOTFETCH(KEY, strlen(KEY), CYRUSDB_NOTFOUND); /* store()ing a record succeeds */ CANSTORE(KEY, strlen(KEY), DATA, strlen(DATA)); /* the record can be fetched back */ CANFETCH(KEY, strlen(KEY), DATA, strlen(DATA)); /* commit succeeds */ CANCOMMIT(); /* data can be read back in a new transaction */ CANFETCH(KEY, strlen(KEY), DATA, strlen(DATA)); /* close the txn - it doesn't matter here if we commit or abort */ CANCOMMIT(); /* close and re-open the database */ CANREOPEN(); /* data can still be read back */ CANFETCH(KEY, strlen(KEY), DATA, strlen(DATA)); /* close the txn - it doesn't matter here if we commit or abort */ CANCOMMIT(); /* closing succeeds */ r = cyrusdb_close(db); CU_ASSERT_EQUAL(r, CYRUSDB_OK); } static void test_multirw(void) { struct db *db = NULL; struct txn *txn = NULL; static const char KEY[] = "skeleton"; static const char DATA1[] = "dem bones"; static const char DATA2[] = "Dem KneeBones"; int r; r = cyrusdb_open(backend, filename, CYRUSDB_CREATE, &db); CU_ASSERT_EQUAL(r, CYRUSDB_OK); CU_ASSERT_PTR_NOT_NULL(db); /* the database is initially empty, so fetch will fail */ CANNOTFETCH(KEY, strlen(KEY), CYRUSDB_NOTFOUND); /* store()ing a record succeeds */ CANSTORE(KEY, strlen(KEY), DATA1, strlen(DATA1)); /* the record can be fetched back */ CANFETCH(KEY, strlen(KEY), DATA1, strlen(DATA1)); /* store()ing the record again, in the same txn, succeeds */ CANSTORE(KEY, strlen(KEY), DATA2, strlen(DATA2)); /* fetching again gets the new data */ CANFETCH(KEY, strlen(KEY), DATA2, strlen(DATA2)); /* commit succeeds */ CANCOMMIT(); /* new data can be read back in a new transaction */ CANFETCH(KEY, strlen(KEY), DATA2, strlen(DATA2)); /* close the txn - it doesn't matter here if we commit or abort */ CANCOMMIT(); /* close and re-open the database */ CANREOPEN(); /* new data can still be read back */ CANFETCH(KEY, strlen(KEY), DATA2, strlen(DATA2)); /* close the txn - it doesn't matter here if we commit or abort */ CANCOMMIT(); CANFETCH_NOTXN(KEY, strlen(KEY), DATA2, strlen(DATA2)); /* closing succeeds */ r = cyrusdb_close(db); CU_ASSERT_EQUAL(r, CYRUSDB_OK); } /* read-write of a non-NULL zero length datum */ static void test_readwrite_zerolen(void) { struct db *db = NULL; struct txn *txn = NULL; /* test data thanks to hipsteripsum.me */ static const char KEY[] = "keffiyeh"; static const char DATA[] = ""; int r; r = cyrusdb_open(backend, filename, CYRUSDB_CREATE, &db); CU_ASSERT_EQUAL(r, CYRUSDB_OK); CU_ASSERT_PTR_NOT_NULL(db); /* the database is initially empty, so fetch will fail */ CANNOTFETCH(KEY, strlen(KEY), CYRUSDB_NOTFOUND); /* store()ing a record succeeds */ CANSTORE(KEY, strlen(KEY), DATA, 0); /* the records can be fetched back; we get non-NULL * zero-length data */ CANFETCH(KEY, strlen(KEY), DATA, 0); /* commit succeeds */ CANCOMMIT(); /* data can be read back in a new transaction */ CANFETCH(KEY, strlen(KEY), DATA, 0); /* close the txn - it doesn't matter here if we commit or abort */ CANCOMMIT(); /* close and re-open the database */ CANREOPEN(); /* data can still be read back */ CANFETCH(KEY, strlen(KEY), DATA, 0); /* close the txn - it doesn't matter here if we commit or abort */ CANCOMMIT(); /* closing succeeds */ r = cyrusdb_close(db); CU_ASSERT_EQUAL(r, CYRUSDB_OK); } /* read-write of a NULL zero length datum */ static void test_readwrite_null(void) { struct db *db = NULL; struct txn *txn = NULL; /* test data thanks to hipsteripsum.me */ static const char KEY[] = "skateboard"; static const char EMPTY[] = ""; int r; r = cyrusdb_open(backend, filename, CYRUSDB_CREATE, &db); CU_ASSERT_EQUAL(r, CYRUSDB_OK); CU_ASSERT_PTR_NOT_NULL(db); /* the database is initially empty, so fetch will fail */ CANNOTFETCH(KEY, strlen(KEY), CYRUSDB_NOTFOUND); /* store()ing a record succeeds */ CANSTORE(KEY, strlen(KEY), NULL, 0); /* the records can be fetched back; we get non-NULL * zero-length data */ CANFETCH(KEY, strlen(KEY), EMPTY, 0); /* commit succeeds */ CANCOMMIT(); /* data can be read back in a new transaction */ CANFETCH(KEY, strlen(KEY), EMPTY, 0); /* close the txn - it doesn't matter here if we commit or abort */ CANCOMMIT(); /* close and re-open the database */ CANREOPEN(); /* data can still be read back */ CANFETCH(KEY, strlen(KEY), EMPTY, 0); /* close the txn - it doesn't matter here if we commit or abort */ CANCOMMIT(); /* closing succeeds */ r = cyrusdb_close(db); CU_ASSERT_EQUAL(r, CYRUSDB_OK); } static void test_abort(void) { struct db *db = NULL; struct txn *txn = NULL; static const char KEY[] = "yale"; static const char DATA[] = "standford mit harvard"; int r; r = cyrusdb_open(backend, filename, CYRUSDB_CREATE, &db); CU_ASSERT_EQUAL(r, CYRUSDB_OK); CU_ASSERT_PTR_NOT_NULL(db); /* the database is initially empty, so fetch will fail */ CANNOTFETCH(KEY, strlen(KEY), CYRUSDB_NOTFOUND); /* store()ing a record succeeds */ CANSTORE(KEY, strlen(KEY), DATA, strlen(DATA)); /* the record can be fetched back */ CANFETCH(KEY, strlen(KEY), DATA, strlen(DATA)); /* abort succeeds */ r = cyrusdb_abort(db, txn); CU_ASSERT_EQUAL(r, CYRUSDB_OK); txn = NULL; /* data is not present in a new transaction */ CANNOTFETCH(KEY, strlen(KEY), CYRUSDB_NOTFOUND); /* close the new txn - it doesn't matter here if we commit or abort */ CANCOMMIT(); /* close and re-open the database */ CANREOPEN(); /* data is still not present after close/reopen */ CANNOTFETCH(KEY, strlen(KEY), CYRUSDB_NOTFOUND); /* close the txn - it doesn't matter here if we commit or abort */ CANCOMMIT(); /* closing succeeds */ r = cyrusdb_close(db); CU_ASSERT_EQUAL(r, CYRUSDB_OK); } static void test_delete(void) { struct db *db = NULL; struct txn *txn = NULL; /* random word generator to the rescue! */ static const char KEY1[] = "buzzes"; static const char DATA1[] = "afro timur funky cents hewitt"; static const char KEY2[] = "galas"; static const char DATA2[] = "assad goering flemish brynner heshvan"; static const char KEY3[] = "bathes"; static const char DATA3[] = "flax corm naipaul enable herrera fating"; int r; r = cyrusdb_open(backend, filename, CYRUSDB_CREATE, &db); CU_ASSERT_EQUAL(r, CYRUSDB_OK); CU_ASSERT_PTR_NOT_NULL(db); /* store() some records */ CANSTORE(KEY1, strlen(KEY1), DATA1, strlen(DATA1)); CANSTORE(KEY2, strlen(KEY2), DATA2, strlen(DATA2)); CANSTORE(KEY3, strlen(KEY3), DATA3, strlen(DATA3)); /* commit succeeds */ CANCOMMIT(); /* all records can be fetched back */ CANFETCH(KEY1, strlen(KEY1), DATA1, strlen(DATA1)); CANFETCH(KEY2, strlen(KEY2), DATA2, strlen(DATA2)); CANFETCH(KEY3, strlen(KEY3), DATA3, strlen(DATA3)); /* one of the records can be deleted */ r = cyrusdb_delete(db, KEY2, strlen(KEY2), &txn, 1); CU_ASSERT_EQUAL(r, CYRUSDB_OK); CU_ASSERT_PTR_NOT_NULL(txn); /* deleted record cannot be fetch()ed now */ CANNOTFETCH(KEY2, strlen(KEY2), CYRUSDB_NOTFOUND); /* but others can */ CANFETCH(KEY1, strlen(KEY1), DATA1, strlen(DATA1)); CANFETCH(KEY3, strlen(KEY3), DATA3, strlen(DATA3)); /* commit succeeds */ CANCOMMIT(); /* deleted record still cannot be fetch()ed in a new txn */ CANNOTFETCH(KEY2, strlen(KEY2), CYRUSDB_NOTFOUND); /* but others can */ CANFETCH(KEY1, strlen(KEY1), DATA1, strlen(DATA1)); CANFETCH(KEY3, strlen(KEY3), DATA3, strlen(DATA3)); /* close the txn - it doesn't matter here if we commit or abort */ CANCOMMIT(); /* close and re-open the database */ CANREOPEN(); /* deleted record still cannot be fetch()ed and re-open */ CANNOTFETCH(KEY2, strlen(KEY2), CYRUSDB_NOTFOUND); /* but others can */ CANFETCH(KEY1, strlen(KEY1), DATA1, strlen(DATA1)); CANFETCH(KEY3, strlen(KEY3), DATA3, strlen(DATA3)); /* close the txn - it doesn't matter here if we commit or abort */ CANCOMMIT(); /* closing succeeds */ r = cyrusdb_close(db); CU_ASSERT_EQUAL(r, CYRUSDB_OK); } static int foreacher(void *rock, const char *key, size_t keylen, const char *data, size_t datalen) { struct binary_result **head = (struct binary_result **)rock; struct binary_result **tail; struct binary_result *res; /* check that key and data are correct */ CU_ASSERT_PTR_NOT_NULL(key); CU_ASSERT(keylen > 0); CU_ASSERT_PTR_NOT_NULL(data); CU_ASSERT(datalen > 0); /* remember them for later perusal */ res = xzmalloc(sizeof(*res)); res->key = xmemdup(key, keylen); res->keylen = keylen; res->data = xmemdup(data, datalen); res->datalen = datalen; /* append to the list. yes, it's inefficient. */ for (tail = head ; *tail ; tail = &(*tail)->next) ; *tail = res; return 0; } struct deleteit { struct db *db; struct binary_result **results; }; static int deleter(void *rock, const char *key, size_t keylen, const char *data, size_t datalen) { struct deleteit *dd = rock; int r; r = foreacher(dd->results, key, keylen, data, datalen); if (r) return r; r = cyrusdb_delete(dd->db, key, keylen, NULL, 0/*force*/); if (r) return r; return 0; } static void test_mboxlist(void) { struct db *db = NULL; struct txn *txn = NULL; struct binary_result *results = NULL; /* random word generator to the rescue! */ static const char KEY1[] = "INBOX.a"; static const char DATA1[] = "delays maj bullish packard ronald"; static const char KEY2[] = "INBOX.a b"; static const char DATA2[] = "bobby tswana cu albumin created"; static const char KEY3[] = "INBOX.a.b"; static const char DATA3[] = "aleut stoic muscovy adonis moe docent"; int r; r = cyrusdb_open(backend, filename, CYRUSDB_CREATE, &db); CU_ASSERT_EQUAL(r, CYRUSDB_OK); CU_ASSERT_PTR_NOT_NULL(db); /* store() some records */ CANSTORE(KEY1, strlen(KEY1), DATA1, strlen(DATA1)); CANSTORE(KEY2, strlen(KEY2), DATA2, strlen(DATA2)); CANSTORE(KEY3, strlen(KEY3), DATA3, strlen(DATA3)); /* commit succeeds */ CANCOMMIT(); /* all records can be fetched back */ CANFETCH(KEY1, strlen(KEY1), DATA1, strlen(DATA1)); CANFETCH(KEY2, strlen(KEY2), DATA2, strlen(DATA2)); CANFETCH(KEY3, strlen(KEY3), DATA3, strlen(DATA3)); /* commit succeeds */ CANCOMMIT(); /* foreach succeeds */ r = cyrusdb_foreach(db, NULL, 0, NULL, foreacher, &results, &txn); CU_ASSERT_EQUAL(r, CYRUSDB_OK); /* got the expected keys in the expected order */ GOTRESULT(KEY1, strlen(KEY1), DATA1, strlen(DATA1)); /* flat is always in mboxlist order! */ if (!strcmp(backend, "flat")) { GOTRESULT(KEY3, strlen(KEY3), DATA3, strlen(DATA3)); GOTRESULT(KEY2, strlen(KEY2), DATA2, strlen(DATA2)); } else { GOTRESULT(KEY2, strlen(KEY2), DATA2, strlen(DATA2)); GOTRESULT(KEY3, strlen(KEY3), DATA3, strlen(DATA3)); } /* foreach iterated over exactly all the keys */ CU_ASSERT_PTR_NULL(results); /* close the txn - it doesn't matter here if we commit or abort */ CANCOMMIT(); /* closing succeeds */ r = cyrusdb_close(db); CU_ASSERT_EQUAL(r, CYRUSDB_OK); /* try again with mboxlist sort */ r = cyrusdb_open(backend, filename2, CYRUSDB_CREATE | CYRUSDB_MBOXSORT, &db); CU_ASSERT_EQUAL(r, CYRUSDB_OK); CU_ASSERT_PTR_NOT_NULL(db); /* store() some records */ CANSTORE(KEY1, strlen(KEY1), DATA1, strlen(DATA1)); CANSTORE(KEY2, strlen(KEY2), DATA2, strlen(DATA2)); CANSTORE(KEY3, strlen(KEY3), DATA3, strlen(DATA3)); /* commit succeeds */ CANCOMMIT(); /* foreach succeeds */ r = cyrusdb_foreach(db, NULL, 0, NULL, foreacher, &results, &txn); CU_ASSERT_EQUAL(r, CYRUSDB_OK); /* got the expected keys in the expected order - that is MBOXLIST * sort order, so 3 before 2 */ GOTRESULT(KEY1, strlen(KEY1), DATA1, strlen(DATA1)); GOTRESULT(KEY3, strlen(KEY3), DATA3, strlen(DATA3)); GOTRESULT(KEY2, strlen(KEY2), DATA2, strlen(DATA2)); /* foreach iterated over exactly all the keys */ CU_ASSERT_PTR_NULL(results); /* close the txn - it doesn't matter here if we commit or abort */ CANCOMMIT(); /* closing succeeds */ r = cyrusdb_close(db); CU_ASSERT_EQUAL(r, CYRUSDB_OK); } static void test_foreach(void) { struct db *db = NULL; struct txn *txn = NULL; struct binary_result *results = NULL; struct deleteit deldata; /* random word generator to the rescue! */ static const char KEY1[] = "carib"; static const char DATA1[] = "delays maj bullish packard ronald"; static const char KEY2[] = "cubist"; static const char DATA2[] = "bobby tswana cu albumin created"; static const char KEY3[] = "eulogy"; static const char DATA3[] = "aleut stoic muscovy adonis moe docent"; int r; r = cyrusdb_open(backend, filename, CYRUSDB_CREATE, &db); CU_ASSERT_EQUAL(r, CYRUSDB_OK); CU_ASSERT_PTR_NOT_NULL(db); /* store() some records */ CANSTORE(KEY1, strlen(KEY1), DATA1, strlen(DATA1)); CANSTORE(KEY2, strlen(KEY2), DATA2, strlen(DATA2)); CANSTORE(KEY3, strlen(KEY3), DATA3, strlen(DATA3)); /* commit succeeds */ CANCOMMIT(); /* all records can be fetched back */ CANFETCH(KEY1, strlen(KEY1), DATA1, strlen(DATA1)); CANFETCH(KEY2, strlen(KEY2), DATA2, strlen(DATA2)); CANFETCH(KEY3, strlen(KEY3), DATA3, strlen(DATA3)); /* commit succeeds */ CANCOMMIT(); /* foreach succeeds */ r = cyrusdb_foreach(db, NULL, 0, NULL, foreacher, &results, &txn); CU_ASSERT_EQUAL(r, CYRUSDB_OK); /* got the expected keys in the expected order */ GOTRESULT(KEY1, strlen(KEY1), DATA1, strlen(DATA1)); GOTRESULT(KEY2, strlen(KEY2), DATA2, strlen(DATA2)); GOTRESULT(KEY3, strlen(KEY3), DATA3, strlen(DATA3)); /* foreach iterated over exactly all the keys */ CU_ASSERT_PTR_NULL(results); /* only check "fetchnext" iteration if it's defined for this backend */ if (cyrusdb_canfetchnext(backend)) { CANFETCHNEXT(NULL, 0, KEY1, strlen(KEY1), DATA1, strlen(DATA1)); CANFETCHNEXT(KEY1, strlen(KEY1), KEY2, strlen(KEY2), DATA2, strlen(DATA2)); CANFETCHNEXT(KEY2, strlen(KEY2), KEY3, strlen(KEY3), DATA3, strlen(DATA3)); CANNOTFETCHNEXT(KEY3, strlen(KEY3), CYRUSDB_NOTFOUND); } /* close the txn - it doesn't matter here if we commit or abort */ CANCOMMIT(); /* check again without TXN */ /* foreach succeeds without txn */ r = cyrusdb_foreach(db, NULL, 0, NULL, foreacher, &results, NULL); CU_ASSERT_EQUAL(r, CYRUSDB_OK); /* got the expected keys in the expected order */ GOTRESULT(KEY1, strlen(KEY1), DATA1, strlen(DATA1)); GOTRESULT(KEY2, strlen(KEY2), DATA2, strlen(DATA2)); GOTRESULT(KEY3, strlen(KEY3), DATA3, strlen(DATA3)); /* foreach iterated over exactly all the keys */ CU_ASSERT_PTR_NULL(results); /* delete all the records after viewing them */ deldata.db = db; deldata.results = &results; r = cyrusdb_foreach(db, NULL, 0, NULL, deleter, &deldata, NULL); CU_ASSERT_EQUAL(r, CYRUSDB_OK); /* got the expected keys in the expected order */ GOTRESULT(KEY1, strlen(KEY1), DATA1, strlen(DATA1)); GOTRESULT(KEY2, strlen(KEY2), DATA2, strlen(DATA2)); GOTRESULT(KEY3, strlen(KEY3), DATA3, strlen(DATA3)); /* foreach iterated over exactly all the keys */ CU_ASSERT_PTR_NULL(results); /* nothing left! */ r = cyrusdb_foreach(db, NULL, 0, NULL, foreacher, &deldata, NULL); CU_ASSERT_EQUAL(r, CYRUSDB_OK); CU_ASSERT_PTR_NULL(results); /* closing succeeds */ r = cyrusdb_close(db); CU_ASSERT_EQUAL(r, CYRUSDB_OK); } struct ffrock { struct db *db; struct txn **tid; int state; }; #define K0 "affect" #define K0U "bother" #define K1 "carib" #define K2 "cubist" #define K3 "eulogy" #define K4 "kidding" #define K4A "notice" #define K5 "penguin" #define K6 "zebra" static int ffstatemachine(void *rockp, const char *key, size_t keylen, const char *data __attribute((unused)), size_t datalen __attribute((unused))) { struct ffrock *fr = (struct ffrock *)rockp; char *kcopy = xstrndup(key, keylen); int r; /* oh yeah, state machine time */ switch (fr->state) { case 0: CU_ASSERT_STRING_EQUAL(kcopy, K1); fr->state = 1; break; case 1: CU_ASSERT_STRING_EQUAL(kcopy, K2); /* test prior-location store */ r = cyrusdb_store(fr->db, K0, strlen(K0), "", 0, fr->tid); CU_ASSERT_EQUAL(r, 0); fr->state = 2; break; case 2: CU_ASSERT_STRING_EQUAL(kcopy, K3); /* test prior non-existent fetch - can cause infinite loops if buggy */ r = cyrusdb_fetch(fr->db, K0U, strlen(K0U), NULL, NULL, fr->tid); CU_ASSERT_EQUAL(r, CYRUSDB_NOTFOUND); fr->state = 3; break; case 3: CU_ASSERT_STRING_EQUAL(kcopy, K4); r = cyrusdb_store(fr->db, K4A, strlen(K4A), "", 0, fr->tid); CU_ASSERT_EQUAL(r, 0); fr->state = 4; break; case 4: /* we found the after-added record correctly */ CU_ASSERT_STRING_EQUAL(kcopy, K4A); r = cyrusdb_store(fr->db, K4A, strlen(K4A), "another", 7, fr->tid); CU_ASSERT_EQUAL(r, 0); fr->state = 5; break; case 5: /* didn't repeat after replacing */ CU_ASSERT_STRING_EQUAL(kcopy, K5); r = cyrusdb_delete(fr->db, K5, strlen(K5), fr->tid, /*force*/1); fr->state = 6; break; case 6: /* moved on after deleting */ CU_ASSERT_STRING_EQUAL(kcopy, K6); fr->state = 7; break; default: CU_ASSERT(0); /* bogus state found */ break; } free(kcopy); return 0; } static void test_foreach_changes(void) { struct db *db = NULL; struct txn *txn = NULL; struct ffrock rock; /* random word generator to the rescue! */ static const char KEY1[] = K1; static const char DATA1[] = "delays maj bullish packard ronald"; static const char KEY2[] = K2; static const char DATA2[] = "bobby tswana cu albumin created"; static const char KEY3[] = K3; static const char DATA3[] = "aleut stoic muscovy adonis moe docent"; static const char KEY4[] = K4; static const char DATA4[] = "curry deterrent drove raising hiring"; static const char KEY5[] = K5; static const char DATA5[] = "joining keeper angle burden buffer"; static const char KEY6[] = K6; static const char DATA6[] = "annoying push security plenty ending"; int r; if (!strcmp(backend, "flat")) return; /* flat concurency is bogus */ r = cyrusdb_open(backend, filename, CYRUSDB_CREATE, &db); CU_ASSERT_EQUAL(r, CYRUSDB_OK); CU_ASSERT_PTR_NOT_NULL(db); /* store() some records */ CANSTORE(KEY1, strlen(KEY1), DATA1, strlen(DATA1)); CANSTORE(KEY2, strlen(KEY2), DATA2, strlen(DATA2)); CANSTORE(KEY3, strlen(KEY3), DATA3, strlen(DATA3)); CANSTORE(KEY4, strlen(KEY4), DATA4, strlen(DATA4)); CANSTORE(KEY5, strlen(KEY5), DATA5, strlen(DATA5)); CANSTORE(KEY6, strlen(KEY6), DATA6, strlen(DATA6)); /* commit succeeds */ CANCOMMIT(); rock.db = db; rock.state = 0; rock.tid = &txn; /* foreach succeeds */ r = cyrusdb_foreach(db, NULL, 0, NULL, ffstatemachine, &rock, rock.tid); CU_ASSERT_EQUAL(r, CYRUSDB_OK); CU_ASSERT_EQUAL(rock.state, 7); /* close the txn - it doesn't matter here if we commit or abort */ CANCOMMIT(); /* closing succeeds */ r = cyrusdb_close(db); CU_ASSERT_EQUAL(r, CYRUSDB_OK); /* check again without TXN */ db = NULL; r = cyrusdb_open(backend, filename2, CYRUSDB_CREATE, &db); CU_ASSERT_EQUAL(r, CYRUSDB_OK); CU_ASSERT_PTR_NOT_NULL(db); /* store() some records */ CANSTORE(KEY1, strlen(KEY1), DATA1, strlen(DATA1)); CANSTORE(KEY2, strlen(KEY2), DATA2, strlen(DATA2)); CANSTORE(KEY3, strlen(KEY3), DATA3, strlen(DATA3)); CANSTORE(KEY4, strlen(KEY4), DATA4, strlen(DATA4)); CANSTORE(KEY5, strlen(KEY5), DATA5, strlen(DATA5)); CANSTORE(KEY6, strlen(KEY6), DATA6, strlen(DATA6)); /* commit succeeds */ CANCOMMIT(); rock.db = db; rock.state = 0; rock.tid = NULL; /* foreach succeeds without txn */ r = cyrusdb_foreach(db, NULL, 0, NULL, ffstatemachine, &rock, rock.tid); CU_ASSERT_EQUAL(r, CYRUSDB_OK); CU_ASSERT_EQUAL(rock.state, 7); /* closing succeeds */ r = cyrusdb_close(db); CU_ASSERT_EQUAL(r, CYRUSDB_OK); } #undef K0 #undef K0U #undef K1 #undef K2 #undef K3 #undef K4 #undef K4A #undef K5 #undef K6 static void test_binary_keys(void) { struct db *db = NULL; struct txn *txn = NULL; /* data from hipsteripsum.me */ static const char KEY1[] = "master\0cleanse"; static const char DATA1[] = "ethical"; static const char KEY2[] = "cardigan\tdreamcatcher"; static const char DATA2[] = "shoreditch"; static const char KEY3[] = "pitchfork\rcarles"; static const char DATA3[] = "tumble"; static const char KEY4[] = "seitan\nraw\ndenim"; static const char DATA4[] = "fap"; static const char KEY5[] = { 0x01, 0x02, 0x04, 0x08, 0x10, 0x20, 0x40, 0x80, 0x00/*unused*/}; static const char DATA5[] = "farm-to-table"; struct binary_result *results = NULL; int r; r = cyrusdb_open(backend, filename, CYRUSDB_CREATE, &db); CU_ASSERT_EQUAL(r, CYRUSDB_OK); CU_ASSERT_PTR_NOT_NULL(db); /* the database is initially empty, so fetch will fail */ CANNOTFETCH(KEY1, sizeof(KEY1)-1, CYRUSDB_NOTFOUND); CANNOTFETCH(KEY2, sizeof(KEY2)-1, CYRUSDB_NOTFOUND); CANNOTFETCH(KEY3, sizeof(KEY3)-1, CYRUSDB_NOTFOUND); CANNOTFETCH(KEY4, sizeof(KEY4)-1, CYRUSDB_NOTFOUND); CANNOTFETCH(KEY5, sizeof(KEY5)-1, CYRUSDB_NOTFOUND); /* store()ing a record succeeds */ CANSTORE(KEY1, sizeof(KEY1)-1, DATA1, sizeof(DATA1)-1); CANSTORE(KEY2, sizeof(KEY2)-1, DATA2, sizeof(DATA2)-1); CANSTORE(KEY3, sizeof(KEY3)-1, DATA3, sizeof(DATA3)-1); CANSTORE(KEY4, sizeof(KEY4)-1, DATA4, sizeof(DATA4)-1); CANSTORE(KEY5, sizeof(KEY5)-1, DATA5, sizeof(DATA5)-1); /* the record can be fetched back */ CANFETCH(KEY1, sizeof(KEY1)-1, DATA1, sizeof(DATA1)-1); CANFETCH(KEY2, sizeof(KEY2)-1, DATA2, sizeof(DATA2)-1); CANFETCH(KEY3, sizeof(KEY3)-1, DATA3, sizeof(DATA3)-1); CANFETCH(KEY4, sizeof(KEY4)-1, DATA4, sizeof(DATA4)-1); CANFETCH(KEY5, sizeof(KEY5)-1, DATA5, sizeof(DATA5)-1); /* commit succeeds */ CANCOMMIT(); /* data can be read back in a new transaction */ CANFETCH(KEY1, sizeof(KEY1)-1, DATA1, sizeof(DATA1)-1); CANFETCH(KEY2, sizeof(KEY2)-1, DATA2, sizeof(DATA2)-1); CANFETCH(KEY3, sizeof(KEY3)-1, DATA3, sizeof(DATA3)-1); CANFETCH(KEY4, sizeof(KEY4)-1, DATA4, sizeof(DATA4)-1); CANFETCH(KEY5, sizeof(KEY5)-1, DATA5, sizeof(DATA5)-1); /* close the txn - it doesn't matter here if we commit or abort */ CANCOMMIT(); /* foreach succeeds */ r = cyrusdb_foreach(db, NULL, 0, NULL, foreacher, &results, &txn); CU_ASSERT_EQUAL(r, CYRUSDB_OK); /* got the expected keys in the expected order */ GOTRESULT(KEY5, sizeof(KEY5)-1, DATA5, sizeof(DATA5)-1); GOTRESULT(KEY2, sizeof(KEY2)-1, DATA2, sizeof(DATA2)-1); GOTRESULT(KEY1, sizeof(KEY1)-1, DATA1, sizeof(DATA1)-1); GOTRESULT(KEY3, sizeof(KEY3)-1, DATA3, sizeof(DATA3)-1); GOTRESULT(KEY4, sizeof(KEY4)-1, DATA4, sizeof(DATA4)-1); /* foreach iterated over exactly all the keys */ CU_ASSERT_PTR_NULL(results); /* close the txn - it doesn't matter here if we commit or abort */ CANCOMMIT(); /* close and re-open the database */ CANREOPEN(); /* data can still be read back */ CANFETCH(KEY1, sizeof(KEY1)-1, DATA1, sizeof(DATA1)-1); CANFETCH(KEY2, sizeof(KEY2)-1, DATA2, sizeof(DATA2)-1); CANFETCH(KEY3, sizeof(KEY3)-1, DATA3, sizeof(DATA3)-1); CANFETCH(KEY4, sizeof(KEY4)-1, DATA4, sizeof(DATA4)-1); CANFETCH(KEY5, sizeof(KEY5)-1, DATA5, sizeof(DATA5)-1); /* close the txn - it doesn't matter here if we commit or abort */ CANCOMMIT(); /* foreach still succeeds - out of txn */ r = cyrusdb_foreach(db, NULL, 0, NULL, foreacher, &results, NULL); CU_ASSERT_EQUAL(r, CYRUSDB_OK); /* got the expected keys in the expected order */ GOTRESULT(KEY5, sizeof(KEY5)-1, DATA5, sizeof(DATA5)-1); GOTRESULT(KEY2, sizeof(KEY2)-1, DATA2, sizeof(DATA2)-1); GOTRESULT(KEY1, sizeof(KEY1)-1, DATA1, sizeof(DATA1)-1); GOTRESULT(KEY3, sizeof(KEY3)-1, DATA3, sizeof(DATA3)-1); GOTRESULT(KEY4, sizeof(KEY4)-1, DATA4, sizeof(DATA4)-1); /* foreach iterated over exactly all the keys */ CU_ASSERT_PTR_NULL(results); /* closing succeeds */ r = cyrusdb_close(db); CU_ASSERT_EQUAL(r, CYRUSDB_OK); } static void test_binary_data(void) { struct db *db = NULL; struct txn *txn = NULL; /* data from hipsteripsum.me */ static const char KEY1[] = "vinyl"; static const char DATA1[] = "cosby\0sweater"; static const char KEY2[] = "blog"; static const char DATA2[] = "next\tlevel"; static const char KEY3[] = "chambray"; static const char DATA3[] = "mcsweeneys\rletterpress"; static const char KEY4[] = "synth"; static const char DATA4[] = "readymade\ncliche\nterry\nrichardson"; static const char KEY5[] = "fixie"; static const char DATA5[] = { 0x01, 0x02, 0x04, 0x08, 0x10, 0x20, 0x40, 0x80, 0x00/*unused*/}; struct binary_result *results = NULL; int r; r = cyrusdb_open(backend, filename, CYRUSDB_CREATE, &db); CU_ASSERT_EQUAL(r, CYRUSDB_OK); CU_ASSERT_PTR_NOT_NULL(db); /* the database is initially empty, so fetch will fail */ CANNOTFETCH(KEY1, sizeof(KEY1)-1, CYRUSDB_NOTFOUND); CANNOTFETCH(KEY2, sizeof(KEY2)-1, CYRUSDB_NOTFOUND); CANNOTFETCH(KEY3, sizeof(KEY3)-1, CYRUSDB_NOTFOUND); CANNOTFETCH(KEY4, sizeof(KEY4)-1, CYRUSDB_NOTFOUND); CANNOTFETCH(KEY5, sizeof(KEY5)-1, CYRUSDB_NOTFOUND); /* store()ing a record succeeds */ CANSTORE(KEY1, sizeof(KEY1)-1, DATA1, sizeof(DATA1)-1); CANSTORE(KEY2, sizeof(KEY2)-1, DATA2, sizeof(DATA2)-1); CANSTORE(KEY3, sizeof(KEY3)-1, DATA3, sizeof(DATA3)-1); CANSTORE(KEY4, sizeof(KEY4)-1, DATA4, sizeof(DATA4)-1); CANSTORE(KEY5, sizeof(KEY5)-1, DATA5, sizeof(DATA5)-1); /* the record can be fetched back */ CANFETCH(KEY1, sizeof(KEY1)-1, DATA1, sizeof(DATA1)-1); CANFETCH(KEY2, sizeof(KEY2)-1, DATA2, sizeof(DATA2)-1); CANFETCH(KEY3, sizeof(KEY3)-1, DATA3, sizeof(DATA3)-1); CANFETCH(KEY4, sizeof(KEY4)-1, DATA4, sizeof(DATA4)-1); CANFETCH(KEY5, sizeof(KEY5)-1, DATA5, sizeof(DATA5)-1); /* commit succeeds */ CANCOMMIT(); /* data can be read back in a new transaction */ CANFETCH(KEY1, sizeof(KEY1)-1, DATA1, sizeof(DATA1)-1); CANFETCH(KEY2, sizeof(KEY2)-1, DATA2, sizeof(DATA2)-1); CANFETCH(KEY3, sizeof(KEY3)-1, DATA3, sizeof(DATA3)-1); CANFETCH(KEY4, sizeof(KEY4)-1, DATA4, sizeof(DATA4)-1); CANFETCH(KEY5, sizeof(KEY5)-1, DATA5, sizeof(DATA5)-1); /* close the txn - it doesn't matter here if we commit or abort */ CANCOMMIT(); /* foreach succeeds */ r = cyrusdb_foreach(db, NULL, 0, NULL, foreacher, &results, &txn); CU_ASSERT_EQUAL(r, CYRUSDB_OK); /* got the expected keys in the expected order */ GOTRESULT(KEY2, sizeof(KEY2)-1, DATA2, sizeof(DATA2)-1); GOTRESULT(KEY3, sizeof(KEY3)-1, DATA3, sizeof(DATA3)-1); GOTRESULT(KEY5, sizeof(KEY5)-1, DATA5, sizeof(DATA5)-1); GOTRESULT(KEY4, sizeof(KEY4)-1, DATA4, sizeof(DATA4)-1); GOTRESULT(KEY1, sizeof(KEY1)-1, DATA1, sizeof(DATA1)-1); /* foreach iterated over exactly all the keys */ CU_ASSERT_PTR_NULL(results); /* close the txn - it doesn't matter here if we commit or abort */ CANCOMMIT(); /* close and re-open the database */ CANREOPEN(); /* data can still be read back */ CANFETCH(KEY1, sizeof(KEY1)-1, DATA1, sizeof(DATA1)-1); CANFETCH(KEY2, sizeof(KEY2)-1, DATA2, sizeof(DATA2)-1); CANFETCH(KEY3, sizeof(KEY3)-1, DATA3, sizeof(DATA3)-1); CANFETCH(KEY4, sizeof(KEY4)-1, DATA4, sizeof(DATA4)-1); CANFETCH(KEY5, sizeof(KEY5)-1, DATA5, sizeof(DATA5)-1); /* foreach still succeeds */ r = cyrusdb_foreach(db, NULL, 0, NULL, foreacher, &results, &txn); CU_ASSERT_EQUAL(r, CYRUSDB_OK); /* got the expected keys in the expected order */ GOTRESULT(KEY2, sizeof(KEY2)-1, DATA2, sizeof(DATA2)-1); GOTRESULT(KEY3, sizeof(KEY3)-1, DATA3, sizeof(DATA3)-1); GOTRESULT(KEY5, sizeof(KEY5)-1, DATA5, sizeof(DATA5)-1); GOTRESULT(KEY4, sizeof(KEY4)-1, DATA4, sizeof(DATA4)-1); GOTRESULT(KEY1, sizeof(KEY1)-1, DATA1, sizeof(DATA1)-1); /* foreach iterated over exactly all the keys */ CU_ASSERT_PTR_NULL(results); /* close the txn - it doesn't matter here if we commit or abort */ CANCOMMIT(); /* closing succeeds */ r = cyrusdb_close(db); CU_ASSERT_EQUAL(r, CYRUSDB_OK); } const char *nth_compound(unsigned int n, const char * const * words /*[37]*/, const char *sep, struct buf *res) { buf_reset(res); if ((n / 1000) % 10) { buf_appendcstr(res, words[28 + (n / 1000) % 10]); } if ((n / 100) % 10) { if (res->len && sep) buf_appendcstr(res, sep); buf_appendcstr(res, words[19 + (n / 100) % 10]); } if ((n / 10) % 10) { if (res->len && sep) buf_appendcstr(res, sep); buf_appendcstr(res, words[10 + (n / 10) % 10]); } if (res->len && sep) buf_appendcstr(res, sep); buf_appendcstr(res, words[n % 10]); return buf_cstring(res); } static const char *nth_key(unsigned int n) { static const char * const words[37] = { "dray", "bite", "cue", "ado", "felt", "firm", "sal", "ahab", "cab", "lord", "blob", "be", "coil", "hay", "bled", "got", "leta", "sept", "deft", "ibm", "kama", "bean", "ado", "cord", "firm", "ben", "fore", "huck", "haas", "jack", "aden", "nerf", "gash", "stu", "nona", "gel", "ale" }; static struct buf buf = BUF_INITIALIZER; return nth_compound(n, words, ".", &buf); } static const char *nth_data(unsigned int n) { static const char * const words[37] = { "abettor", "afresh", "aisling", "arthur", "ascots", "belled", "berserk", "border", "bourbon", "brawny", "carpels", "cavils", "coating", "cologne", "concern", "consul", "crater", "crocks", "deirdre", "dewier", "disdain", "dowdier", "duncan", "eighth", "enigma", "evelyn", "fennel", "flowery", "flukier", "forums", "gametes", "gamins", "gavels", "gibbers", "gulags", "gunther", "gunwale" }; static struct buf buf = BUF_INITIALIZER; return nth_compound(n, words, " ", &buf); } static int finder(void *rock, const char *key, size_t keylen, const char *data, size_t datalen) { hash_table *exphash = (hash_table *)rock; char *expected; struct buf kbuf = BUF_INITIALIZER; /* check that key and data are correct */ CU_ASSERT_PTR_NOT_NULL(key); CU_ASSERT(keylen > 0); CU_ASSERT_PTR_NOT_NULL(data); CU_ASSERT(datalen > 0); buf_appendmap(&kbuf, key, keylen); buf_cstring(&kbuf); expected = hash_lookup(kbuf.s, exphash); CU_ASSERT_EQUAL(datalen, strlen(expected)); CU_ASSERT_EQUAL(0, memcmp(data, expected, datalen)); hash_del(kbuf.s, exphash); free(expected); buf_free(&kbuf); return 0; } static void count_cb(const char *key __attribute__((unused)), void *data __attribute__((unused)), void *rock) { unsigned int *np = (unsigned int *)rock; (*np)++; } static unsigned int hash_count(hash_table *ht) { unsigned int n = 0; hash_enumerate(ht, count_cb, &n); return n; } #define FOREACH_PRECONDITION(condition, expcount) \ { \ unsigned int nsubset = 0; \ unsigned int i; \ for (i = 0 ; i <= MAXN ; i++) { \ const char *key = nth_key(i); \ const char *data = nth_data(i); \ if ((condition)) { \ hash_insert(key, (void *)xstrdup(data), &exphash); \ nsubset++; \ } \ } \ CU_ASSERT_EQUAL(nsubset, expcount); \ CU_ASSERT_EQUAL(hash_count(&exphash), nsubset); \ } #define FOREACH_POSTCONDITION() \ CU_ASSERT_EQUAL(r, CYRUSDB_OK); \ CU_ASSERT_EQUAL(hash_count(&exphash), 0); #define FOREACH_TEST(prefix, prefixlen, good, condition, expcount) \ FOREACH_PRECONDITION(condition, expcount); \ r = cyrusdb_foreach(db, prefix, prefixlen, good, finder, &exphash, &txn); \ FOREACH_POSTCONDITION() static void test_many(void) { struct db *db = NULL; struct txn *txn = NULL; hash_table exphash = HASH_TABLE_INITIALIZER; #define MAXN 4095 unsigned int n; int r; construct_hash_table(&exphash, (MAXN+1)*4, 0); r = cyrusdb_open(backend, filename, CYRUSDB_CREATE, &db); CU_ASSERT_EQUAL(r, CYRUSDB_OK); CU_ASSERT_PTR_NOT_NULL(db); /* store() some records */ for (n = 0 ; n <= MAXN ; n++) { const char *key = nth_key(n); const char *data = nth_data(n); CANSTORE(key, strlen(key), data, strlen(data)); } /* commit succeeds */ CANCOMMIT(); /* check the records all made it */ for (n = 0 ; n <= MAXN ; n++) { const char *key = nth_key(n); const char *data = nth_data(n); CANFETCH(key, strlen(key), data, strlen(data)); } /* prefix=NULL: iterate all the records */ FOREACH_TEST(/*prefix*/NULL, /*prefixlen*/0, /*good*/NULL, /*condition*/1, MAXN+1); /* prefix="": iterate all the records */ FOREACH_TEST(/*prefix*/"", /*prefixlen*/0, /*good*/NULL, /*condition*/1, MAXN+1); /* prefix=an uncommon prefix: iterate some of the records */ FOREACH_TEST(/*prefix*/"jack.", /*prefixlen*/5, /*good*/NULL, /*condition*/i / 1000 == 1, 1000); /* delete records one by one, checking that foreach * walks over the expected number from time to time */ for (n = 0 ; n <= MAXN ; n++) { const char *key = nth_key(n); r = cyrusdb_delete(db, key, strlen(key), &txn, 1); CU_ASSERT_EQUAL(r, CYRUSDB_OK); CU_ASSERT_PTR_NOT_NULL(txn); if (n && n % 301 == 0) { FOREACH_TEST(/*prefix*/NULL, /*prefixlen*/0, /*good*/NULL, /*condition*/i > n, MAXN-n); } } /* close the txn - it doesn't matter here if we commit or abort */ CANCOMMIT(); /* closing succeeds */ r = cyrusdb_close(db); CU_ASSERT_EQUAL(r, CYRUSDB_OK); free_hash_table(&exphash, free); #undef MAXN } static char *basedir; static int set_up(void) { char buf[PATH_MAX]; static const char * const reldirs[] = { "db", "conf", "conf/lock/", "conf/lock/user", "stuff", NULL }; basedir = make_basedir(reldirs); if (!basedir) return -1; libcyrus_config_setstring(CYRUSOPT_CONFIG_DIR, basedir); snprintf(buf, sizeof(buf), "configdirectory: %s/conf\n", basedir); config_read_string(buf); cyrusdb_init(); filename = strconcat(basedir, "/stuff/cyrus.", backend, "-test", (char *)NULL); filename2 = strconcat(basedir, "/stuff/cyrus.", backend, "-testB", (char *)NULL); return 0; } static int tear_down(void) { int r = 0; cyrusdb_done(); if (basedir) { char buf[PATH_MAX]; snprintf(buf, sizeof(buf), "rm -rf \"%s\"", basedir); r = system(buf); if (r) r = -1; } free(filename); filename = NULL; free(filename2); filename2 = NULL; free(basedir); basedir = NULL; return r; } /* vim: set ft=c: */ cyrus-imapd-2.5.10/cunit/annotate.testc0000644000175000017500000016250313001236020014746 00000000000000#if HAVE_CONFIG_H #include #endif #include "cunit/cunit.h" #include "assert.h" #include "xmalloc.h" #include "retry.h" #include "util.h" #include "imap/global.h" #include "libcyr_cfg.h" #include "imap/annotate.h" #include "imap/mboxlist.h" #include "imap/imap_err.h" #define DBDIR "test-dbdir" #define MBOXNAME1_INT "user.smurf" #define MBOXNAME2_INT "user.smurfette" #define PARTITION "default" #define COMMENT "/comment" #define EXENTRY "/vendor/example.com/a-non-default-entry" #define VALUE_SHARED "value.shared" #define SIZE_SHARED "size.shared" #define VALUE0 "Hello World" #define LENGTH0 "11" #define VALUE1 "lorem ipsum" #define VALUE2 "dolor sit amet" #define ACL "anyone\tlrswipkxtecdan\t" static int isadmin; static const char *userid; static struct auth_state *auth_state; static const char *old_annotation_definitions = NULL; static void config_read_string(const char *s) { char *fname = xstrdup("/tmp/cyrus-cunit-configXXXXXX"); int fd = mkstemp(fname); retry_write(fd, s, strlen(s)); config_reset(); config_read(fname, 0); unlink(fname); free(fname); close(fd); } static void set_annotation_definitions(const char *s) { static const char *fname = DBDIR"/conf/annotations.def"; int fd; if (s) { fd = open(fname, O_WRONLY|O_CREAT|O_TRUNC, 0666); assert(fd >= 0); retry_write(fd, s, strlen(s)); close(fd); } else { unlink(fname); } imapopts[IMAPOPT_ANNOTATION_DEFINITIONS].val.s = fname; } static int fexists(const char *fname) { struct stat sb; int r; r = stat(fname, &sb); if (r < 0) r = -errno; return r; } static void fetch_cb(const char *mboxname, uint32_t uid, const char *entry, struct attvaluelist *avlist, void *rock) { strarray_t *results = (strarray_t *)rock; struct buf buf = BUF_INITIALIZER; buf_printf(&buf, "mboxname=\"%s\" uid=%u entry=\"%s\"", mboxname, uid, entry); for ( ; avlist ; avlist = avlist->next) { buf_printf(&buf, " %s=", avlist->attrib); if (avlist->value.s) buf_printf(&buf, "\"%s\"", buf_cstring(&avlist->value)); else buf_printf(&buf, "NIL"); } strarray_appendm(results, buf_release(&buf)); } /* test_begin_without_open deleted -- begin has been removed */ /* test_commit_without_begin deleted -- begin has been removed */ /* test_store_without_begin deleted -- begin has been removed */ static void test_getset_server_shared(void) { int r; annotate_state_t *astate = NULL; strarray_t entries = STRARRAY_INITIALIZER; strarray_t attribs = STRARRAY_INITIALIZER; strarray_t results = STRARRAY_INITIALIZER; struct entryattlist *ealist = NULL; struct buf val = BUF_INITIALIZER; struct buf val2 = BUF_INITIALIZER; annotate_init(NULL, NULL); annotatemore_open(); astate = annotate_state_new(); r = annotate_state_set_server(astate); CU_ASSERT_EQUAL(r, 0); annotate_state_set_auth(astate, isadmin, userid, auth_state); strarray_append(&entries, COMMENT); strarray_append(&attribs, VALUE_SHARED); /* check that there is no value initially */ r = annotate_state_fetch(astate, &entries, &attribs, fetch_cb, &results, NULL); CU_ASSERT_EQUAL(r, 0); CU_ASSERT_EQUAL_FATAL(results.count, 1); #define EXPECTED \ "mboxname=\"\" " \ "uid=0 " \ "entry=\"" COMMENT "\" " \ VALUE_SHARED "=NIL" CU_ASSERT_STRING_EQUAL(results.data[0], EXPECTED); #undef EXPECTED strarray_truncate(&results, 0); r = annotatemore_lookup(/*mboxname*/"", COMMENT, /*userid*/"", &val); CU_ASSERT_EQUAL(r, 0); CU_ASSERT_PTR_NULL(val.s); /* set a value */ /* pretend to be admin */ annotate_state_set_auth(astate, /*isadmin*/1, userid, auth_state); buf_appendcstr(&val, VALUE0); setentryatt(&ealist, COMMENT, VALUE_SHARED, &val); r = annotate_state_store(astate, ealist); CU_ASSERT_EQUAL(r, 0); freeentryatts(ealist); ealist = NULL; /* check that we can fetch the value back in the same txn */ r = annotate_state_fetch(astate, &entries, &attribs, fetch_cb, &results, NULL); CU_ASSERT_EQUAL(r, 0); CU_ASSERT_EQUAL_FATAL(results.count, 1); #define EXPECTED \ "mboxname=\"\" " \ "uid=0 " \ "entry=\"" COMMENT "\" " \ VALUE_SHARED "=\"" VALUE0 "\"" CU_ASSERT_STRING_EQUAL(results.data[0], EXPECTED); #undef EXPECTED strarray_truncate(&results, 0); r = annotatemore_lookup(/*mboxname*/"", COMMENT, /*userid*/"", &val2); CU_ASSERT_EQUAL_FATAL(r, 0); CU_ASSERT_PTR_NOT_NULL_FATAL(val2.s); CU_ASSERT_STRING_EQUAL(buf_cstring(&val2), VALUE0); buf_free(&val2); r = annotate_state_commit(&astate); CU_ASSERT_EQUAL(r, 0); /* check that we can fetch the value back in a new txn */ astate = annotate_state_new(); annotate_state_set_auth(astate, /*isadmin*/0, userid, auth_state); r = annotate_state_set_server(astate); CU_ASSERT_EQUAL(r, 0); r = annotate_state_fetch(astate, &entries, &attribs, fetch_cb, &results, NULL); CU_ASSERT_EQUAL(r, 0); CU_ASSERT_EQUAL_FATAL(results.count, 1); #define EXPECTED \ "mboxname=\"\" " \ "uid=0 " \ "entry=\"" COMMENT "\" " \ VALUE_SHARED "=\"" VALUE0 "\"" CU_ASSERT_STRING_EQUAL(results.data[0], EXPECTED); #undef EXPECTED strarray_truncate(&results, 0); r = annotatemore_lookup(/*mboxname*/"", COMMENT, /*userid*/"", &val2); CU_ASSERT_EQUAL_FATAL(r, 0); CU_ASSERT_PTR_NOT_NULL_FATAL(val2.s); CU_ASSERT_STRING_EQUAL(buf_cstring(&val2), VALUE0); buf_free(&val2); annotate_state_abort(&astate); annotatemore_close(); /* check that we can fetch the value back after close and re-open */ annotatemore_open(); astate = annotate_state_new(); annotate_state_set_auth(astate, /*isadmin*/0, userid, auth_state); r = annotate_state_set_server(astate); CU_ASSERT_EQUAL(r, 0); r = annotate_state_fetch(astate, &entries, &attribs, fetch_cb, &results, NULL); CU_ASSERT_EQUAL(r, 0); CU_ASSERT_EQUAL_FATAL(results.count, 1); #define EXPECTED \ "mboxname=\"\" " \ "uid=0 " \ "entry=\"" COMMENT "\" " \ VALUE_SHARED "=\"" VALUE0 "\"" CU_ASSERT_STRING_EQUAL(results.data[0], EXPECTED); #undef EXPECTED strarray_truncate(&results, 0); r = annotatemore_lookup(/*mboxname*/"", COMMENT, /*userid*/"", &val2); CU_ASSERT_EQUAL_FATAL(r, 0); CU_ASSERT_PTR_NOT_NULL_FATAL(val2.s); CU_ASSERT_STRING_EQUAL(buf_cstring(&val2), VALUE0); buf_free(&val2); /* delete the value */ buf_free(&val); setentryatt(&ealist, COMMENT, VALUE_SHARED, &val); /* pretend to be admin */ annotate_state_set_auth(astate, /*isadmin*/1, userid, auth_state); r = annotate_state_store(astate, ealist); CU_ASSERT_EQUAL(r, 0); freeentryatts(ealist); ealist = NULL; r = annotate_state_commit(&astate); CU_ASSERT_EQUAL(r, 0); /* check that there is no value any more */ astate = annotate_state_new(); annotate_state_set_auth(astate, /*isadmin*/0, userid, auth_state); r = annotate_state_set_server(astate); CU_ASSERT_EQUAL(r, 0); annotate_state_set_auth(astate, isadmin, userid, auth_state); r = annotate_state_fetch(astate, &entries, &attribs, fetch_cb, &results, NULL); CU_ASSERT_EQUAL(r, 0); CU_ASSERT_EQUAL_FATAL(results.count, 1); #define EXPECTED \ "mboxname=\"\" " \ "uid=0 " \ "entry=\"" COMMENT "\" " \ VALUE_SHARED "=NIL" CU_ASSERT_STRING_EQUAL(results.data[0], EXPECTED); #undef EXPECTED strarray_truncate(&results, 0); r = annotatemore_lookup(/*mboxname*/"", COMMENT, /*userid*/"", &val); CU_ASSERT_EQUAL(r, 0); CU_ASSERT_PTR_NULL(val.s); annotate_state_abort(&astate); annotatemore_close(); strarray_fini(&entries); strarray_fini(&attribs); strarray_fini(&results); buf_free(&val); } static void test_getset_mailbox_shared(void) { int r; annotate_state_t *astate = NULL; strarray_t entries = STRARRAY_INITIALIZER; strarray_t attribs = STRARRAY_INITIALIZER; strarray_t results = STRARRAY_INITIALIZER; struct entryattlist *ealist = NULL; struct buf val = BUF_INITIALIZER; struct buf val2 = BUF_INITIALIZER; struct mailbox *mailbox = NULL; annotate_init(NULL, NULL); annotatemore_open(); r = mailbox_open_iwl(MBOXNAME1_INT, &mailbox); CU_ASSERT_EQUAL_FATAL(r, 0); astate = annotate_state_new(); r = annotate_state_set_mailbox(astate, mailbox); CU_ASSERT_EQUAL(r, 0); annotate_state_set_auth(astate, isadmin, userid, auth_state); strarray_append(&entries, COMMENT); strarray_append(&attribs, VALUE_SHARED); /* check that there is no value initially */ r = annotate_state_fetch(astate, &entries, &attribs, fetch_cb, &results, NULL); CU_ASSERT_EQUAL(r, 0); CU_ASSERT_EQUAL_FATAL(results.count, 1); #define EXPECTED \ "mboxname=\"" MBOXNAME1_INT "\" " \ "uid=0 " \ "entry=\"" COMMENT "\" " \ VALUE_SHARED "=NIL" CU_ASSERT_STRING_EQUAL(results.data[0], EXPECTED); #undef EXPECTED strarray_truncate(&results, 0); r = annotatemore_lookup(MBOXNAME1_INT, COMMENT, /*userid*/"", &val); CU_ASSERT_EQUAL(r, 0); CU_ASSERT_PTR_NULL(val.s); /* set a value */ buf_appendcstr(&val, VALUE0); setentryatt(&ealist, COMMENT, VALUE_SHARED, &val); r = annotate_state_store(astate, ealist); CU_ASSERT_EQUAL(r, 0); freeentryatts(ealist); ealist = NULL; /* check that we can fetch the value back in the same txn */ r = annotate_state_fetch(astate, &entries, &attribs, fetch_cb, &results, NULL); CU_ASSERT_EQUAL(r, 0); CU_ASSERT_EQUAL_FATAL(results.count, 1); #define EXPECTED \ "mboxname=\"" MBOXNAME1_INT "\" " \ "uid=0 " \ "entry=\"" COMMENT "\" " \ VALUE_SHARED "=\"" VALUE0 "\"" CU_ASSERT_STRING_EQUAL(results.data[0], EXPECTED); #undef EXPECTED strarray_truncate(&results, 0); r = annotatemore_lookup(MBOXNAME1_INT, COMMENT, /*userid*/"", &val2); CU_ASSERT_EQUAL_FATAL(r, 0); CU_ASSERT_PTR_NOT_NULL_FATAL(val2.s); CU_ASSERT_STRING_EQUAL(buf_cstring(&val2), VALUE0); buf_free(&val2); r = annotate_state_commit(&astate); CU_ASSERT_EQUAL(r, 0); /* check that we can fetch the value back in a new txn */ astate = annotate_state_new(); r = annotate_state_set_mailbox(astate, mailbox); CU_ASSERT_EQUAL(r, 0); annotate_state_set_auth(astate, isadmin, userid, auth_state); r = annotate_state_fetch(astate, &entries, &attribs, fetch_cb, &results, NULL); CU_ASSERT_EQUAL(r, 0); CU_ASSERT_EQUAL_FATAL(results.count, 1); #define EXPECTED \ "mboxname=\"" MBOXNAME1_INT "\" " \ "uid=0 " \ "entry=\"" COMMENT "\" " \ VALUE_SHARED "=\"" VALUE0 "\"" CU_ASSERT_STRING_EQUAL(results.data[0], EXPECTED); #undef EXPECTED strarray_truncate(&results, 0); r = annotatemore_lookup(MBOXNAME1_INT, COMMENT, /*userid*/"", &val2); CU_ASSERT_EQUAL_FATAL(r, 0); CU_ASSERT_PTR_NOT_NULL_FATAL(val2.s); CU_ASSERT_STRING_EQUAL(buf_cstring(&val2), VALUE0); buf_free(&val2); annotate_state_abort(&astate); annotatemore_close(); /* check that we can fetch the value back after close and re-open */ annotatemore_open(); astate = annotate_state_new(); r = annotate_state_set_mailbox(astate, mailbox); CU_ASSERT_EQUAL(r, 0); annotate_state_set_auth(astate, isadmin, userid, auth_state); r = annotate_state_fetch(astate, &entries, &attribs, fetch_cb, &results, NULL); CU_ASSERT_EQUAL(r, 0); CU_ASSERT_EQUAL_FATAL(results.count, 1); #define EXPECTED \ "mboxname=\"" MBOXNAME1_INT "\" " \ "uid=0 " \ "entry=\"" COMMENT "\" " \ VALUE_SHARED "=\"" VALUE0 "\"" CU_ASSERT_STRING_EQUAL(results.data[0], EXPECTED); #undef EXPECTED strarray_truncate(&results, 0); r = annotatemore_lookup(MBOXNAME1_INT, COMMENT, /*userid*/"", &val2); CU_ASSERT_EQUAL_FATAL(r, 0); CU_ASSERT_PTR_NOT_NULL_FATAL(val2.s); CU_ASSERT_STRING_EQUAL(buf_cstring(&val2), VALUE0); buf_free(&val2); /* delete the value */ buf_free(&val); setentryatt(&ealist, COMMENT, VALUE_SHARED, &val); r = annotate_state_store(astate, ealist); CU_ASSERT_EQUAL(r, 0); freeentryatts(ealist); ealist = NULL; r = annotate_state_commit(&astate); CU_ASSERT_EQUAL(r, 0); /* check that there is no value any more */ astate = annotate_state_new(); r = annotate_state_set_mailbox(astate, mailbox); CU_ASSERT_EQUAL(r, 0); annotate_state_set_auth(astate, isadmin, userid, auth_state); r = annotate_state_fetch(astate, &entries, &attribs, fetch_cb, &results, NULL); CU_ASSERT_EQUAL(r, 0); CU_ASSERT_EQUAL_FATAL(results.count, 1); #define EXPECTED \ "mboxname=\"" MBOXNAME1_INT "\" " \ "uid=0 " \ "entry=\"" COMMENT "\" " \ VALUE_SHARED "=NIL" CU_ASSERT_STRING_EQUAL(results.data[0], EXPECTED); #undef EXPECTED strarray_truncate(&results, 0); buf_free(&val); r = annotatemore_lookup(MBOXNAME1_INT, COMMENT, /*userid*/"", &val); CU_ASSERT_EQUAL(r, 0); CU_ASSERT_PTR_NULL(val.s); annotate_state_abort(&astate); annotatemore_close(); strarray_fini(&entries); strarray_fini(&attribs); strarray_fini(&results); buf_free(&val); mailbox_close(&mailbox); } static void test_getset_message_shared(void) { int r; annotate_state_t *astate = NULL; strarray_t entries = STRARRAY_INITIALIZER; strarray_t attribs = STRARRAY_INITIALIZER; strarray_t results = STRARRAY_INITIALIZER; struct entryattlist *ealist = NULL; struct buf val = BUF_INITIALIZER; struct buf val2 = BUF_INITIALIZER; struct mailbox *mailbox = NULL; annotate_init(NULL, NULL); annotatemore_open(); r = mailbox_open_iwl(MBOXNAME1_INT, &mailbox); CU_ASSERT_EQUAL_FATAL(r, 0); r = mailbox_get_annotate_state(mailbox, 42, &astate); CU_ASSERT_EQUAL(r, 0); annotate_state_set_auth(astate, isadmin, userid, auth_state); strarray_append(&entries, COMMENT); strarray_append(&attribs, VALUE_SHARED); /* check that there is no value initially */ r = annotate_state_fetch(astate, &entries, &attribs, fetch_cb, &results, NULL); CU_ASSERT_EQUAL(r, 0); CU_ASSERT_EQUAL_FATAL(results.count, 1); #define EXPECTED \ "mboxname=\"" MBOXNAME1_INT "\" " \ "uid=42 " \ "entry=\"" COMMENT "\" " \ VALUE_SHARED "=NIL" CU_ASSERT_STRING_EQUAL(results.data[0], EXPECTED); #undef EXPECTED strarray_truncate(&results, 0); r = annotatemore_msg_lookup(MBOXNAME1_INT, 42, COMMENT, /*userid*/"", &val); CU_ASSERT_EQUAL(r, 0); CU_ASSERT_PTR_NULL(val.s); /* set a value */ buf_appendcstr(&val, VALUE0); setentryatt(&ealist, COMMENT, VALUE_SHARED, &val); r = annotate_state_store(astate, ealist); CU_ASSERT_EQUAL(r, 0); freeentryatts(ealist); ealist = NULL; /* check that we can fetch the value back in the same txn */ r = annotate_state_fetch(astate, &entries, &attribs, fetch_cb, &results, NULL); CU_ASSERT_EQUAL(r, 0); CU_ASSERT_EQUAL_FATAL(results.count, 1); #define EXPECTED \ "mboxname=\"" MBOXNAME1_INT "\" " \ "uid=42 " \ "entry=\"" COMMENT "\" " \ VALUE_SHARED "=\"" VALUE0 "\"" CU_ASSERT_STRING_EQUAL(results.data[0], EXPECTED); #undef EXPECTED strarray_truncate(&results, 0); r = annotatemore_msg_lookup(MBOXNAME1_INT, 42, COMMENT, /*userid*/"", &val2); CU_ASSERT_EQUAL_FATAL(r, 0); CU_ASSERT_PTR_NOT_NULL_FATAL(val2.s); CU_ASSERT_STRING_EQUAL(buf_cstring(&val2), VALUE0); buf_free(&val2); r = mailbox_commit(mailbox); CU_ASSERT_EQUAL(r, 0); mailbox_close(&mailbox); /* check that we can fetch the value back in a new txn */ r = mailbox_open_iwl(MBOXNAME1_INT, &mailbox); CU_ASSERT_EQUAL_FATAL(r, 0); r = mailbox_get_annotate_state(mailbox, 42, &astate); CU_ASSERT_EQUAL(r, 0); annotate_state_set_auth(astate, isadmin, userid, auth_state); r = annotate_state_fetch(astate, &entries, &attribs, fetch_cb, &results, NULL); CU_ASSERT_EQUAL(r, 0); CU_ASSERT_EQUAL_FATAL(results.count, 1); #define EXPECTED \ "mboxname=\"" MBOXNAME1_INT "\" " \ "uid=42 " \ "entry=\"" COMMENT "\" " \ VALUE_SHARED "=\"" VALUE0 "\"" CU_ASSERT_STRING_EQUAL(results.data[0], EXPECTED); #undef EXPECTED strarray_truncate(&results, 0); r = annotatemore_msg_lookup(MBOXNAME1_INT, 42, COMMENT, /*userid*/"", &val2); CU_ASSERT_EQUAL_FATAL(r, 0); CU_ASSERT_PTR_NOT_NULL_FATAL(val2.s); CU_ASSERT_STRING_EQUAL(buf_cstring(&val2), VALUE0); buf_free(&val2); r = mailbox_commit(mailbox); CU_ASSERT_EQUAL(r, 0); mailbox_close(&mailbox); annotatemore_close(); /* check that we can fetch the value back after close and re-open */ annotatemore_open(); r = mailbox_open_iwl(MBOXNAME1_INT, &mailbox); CU_ASSERT_EQUAL_FATAL(r, 0); r = mailbox_get_annotate_state(mailbox, 42, &astate); CU_ASSERT_EQUAL(r, 0); annotate_state_set_auth(astate, isadmin, userid, auth_state); r = annotate_state_fetch(astate, &entries, &attribs, fetch_cb, &results, NULL); CU_ASSERT_EQUAL(r, 0); CU_ASSERT_EQUAL_FATAL(results.count, 1); #define EXPECTED \ "mboxname=\"" MBOXNAME1_INT "\" " \ "uid=42 " \ "entry=\"" COMMENT "\" " \ VALUE_SHARED "=\"" VALUE0 "\"" CU_ASSERT_STRING_EQUAL(results.data[0], EXPECTED); #undef EXPECTED strarray_truncate(&results, 0); r = annotatemore_msg_lookup(MBOXNAME1_INT, 42, COMMENT, /*userid*/"", &val2); CU_ASSERT_EQUAL_FATAL(r, 0); CU_ASSERT_PTR_NOT_NULL_FATAL(val2.s); CU_ASSERT_STRING_EQUAL(buf_cstring(&val2), VALUE0); buf_free(&val2); /* delete the value */ buf_free(&val); setentryatt(&ealist, COMMENT, VALUE_SHARED, &val); r = annotate_state_store(astate, ealist); CU_ASSERT_EQUAL(r, 0); freeentryatts(ealist); ealist = NULL; r = mailbox_commit(mailbox); CU_ASSERT_EQUAL(r, 0); mailbox_close(&mailbox); /* check that there is no value any more */ r = mailbox_open_iwl(MBOXNAME1_INT, &mailbox); CU_ASSERT_EQUAL_FATAL(r, 0); r = mailbox_get_annotate_state(mailbox, 42, &astate); CU_ASSERT_EQUAL(r, 0); annotate_state_set_auth(astate, isadmin, userid, auth_state); r = annotate_state_fetch(astate, &entries, &attribs, fetch_cb, &results, NULL); CU_ASSERT_EQUAL(r, 0); CU_ASSERT_EQUAL_FATAL(results.count, 1); #define EXPECTED \ "mboxname=\"" MBOXNAME1_INT "\" " \ "uid=42 " \ "entry=\"" COMMENT "\" " \ VALUE_SHARED "=NIL" CU_ASSERT_STRING_EQUAL(results.data[0], EXPECTED); #undef EXPECTED strarray_truncate(&results, 0); buf_free(&val); r = annotatemore_msg_lookup(MBOXNAME1_INT, 42, COMMENT, /*userid*/"", &val); CU_ASSERT_EQUAL(r, 0); CU_ASSERT_PTR_NULL(val.s); r = mailbox_commit(mailbox); CU_ASSERT_EQUAL(r, 0); mailbox_close(&mailbox); annotatemore_close(); strarray_fini(&entries); strarray_fini(&attribs); strarray_fini(&results); buf_free(&val); mailbox_close(&mailbox); } static void test_delete(void) { int r; annotate_state_t *astate = NULL; struct mboxlist_entry mbentry; strarray_t entries = STRARRAY_INITIALIZER; strarray_t attribs = STRARRAY_INITIALIZER; struct entryattlist *ealist = NULL; struct buf val = BUF_INITIALIZER; struct buf val2 = BUF_INITIALIZER; struct mailbox *mailbox = NULL; CU_ASSERT_EQUAL(fexists(DBDIR"/data/user/smurf/cyrus.annotations"), -ENOENT); annotate_init(NULL, NULL); annotatemore_open(); r = mailbox_open_iwl(MBOXNAME1_INT, &mailbox); CU_ASSERT_EQUAL_FATAL(r, 0); memset(&mbentry, 0, sizeof(mbentry)); mbentry.name = MBOXNAME1_INT; mbentry.mbtype = 0; mbentry.partition = PARTITION; mbentry.acl = ACL; strarray_append(&entries, COMMENT); strarray_append(&attribs, VALUE_SHARED); /* set some values */ buf_appendcstr(&val, VALUE0); setentryatt(&ealist, COMMENT, VALUE_SHARED, &val); astate = annotate_state_new(); annotate_state_set_auth(astate, isadmin, userid, auth_state); r = annotate_state_set_mailbox(astate, mailbox); CU_ASSERT_EQUAL(r, 0); r = annotate_state_store(astate, ealist); CU_ASSERT_EQUAL(r, 0); freeentryatts(ealist); ealist = NULL; r = annotate_state_commit(&astate); CU_ASSERT_EQUAL(r, 0); buf_reset(&val); buf_appendcstr(&val, VALUE1); setentryatt(&ealist, COMMENT, VALUE_SHARED, &val); r = mailbox_get_annotate_state(mailbox, 42, &astate); CU_ASSERT_EQUAL(r, 0); annotate_state_set_auth(astate, isadmin, userid, auth_state); r = annotate_state_store(astate, ealist); CU_ASSERT_EQUAL(r, 0); freeentryatts(ealist); ealist = NULL; buf_reset(&val); buf_appendcstr(&val, VALUE2); setentryatt(&ealist, COMMENT, VALUE_SHARED, &val); r = mailbox_get_annotate_state(mailbox, 127, &astate); CU_ASSERT_EQUAL(r, 0); annotate_state_set_auth(astate, isadmin, userid, auth_state); r = annotate_state_store(astate, ealist); CU_ASSERT_EQUAL(r, 0); freeentryatts(ealist); ealist = NULL; r = mailbox_commit(mailbox); CU_ASSERT_EQUAL(r, 0); mailbox_close(&mailbox); /* check that we can fetch the values back */ r = annotatemore_msg_lookup(MBOXNAME1_INT, 0, COMMENT, /*userid*/"", &val2); CU_ASSERT_EQUAL_FATAL(r, 0); CU_ASSERT_PTR_NOT_NULL_FATAL(val2.s); CU_ASSERT_STRING_EQUAL(buf_cstring(&val2), VALUE0); buf_free(&val2); r = annotatemore_msg_lookup(MBOXNAME1_INT, 42, COMMENT, /*userid*/"", &val2); CU_ASSERT_EQUAL_FATAL(r, 0); CU_ASSERT_PTR_NOT_NULL_FATAL(val2.s); CU_ASSERT_STRING_EQUAL(buf_cstring(&val2), VALUE1); buf_free(&val2); r = annotatemore_msg_lookup(MBOXNAME1_INT, 127, COMMENT, /*userid*/"", &val2); CU_ASSERT_EQUAL_FATAL(r, 0); CU_ASSERT_PTR_NOT_NULL_FATAL(val2.s); CU_ASSERT_STRING_EQUAL(buf_cstring(&val2), VALUE2); buf_free(&val2); CU_ASSERT_EQUAL(fexists(DBDIR"/data/user/smurf/cyrus.annotations"), 0); /* delete all the entries associated with the mailbox */ r = mailbox_open_iwl(MBOXNAME1_INT, &mailbox); CU_ASSERT_EQUAL_FATAL(r, 0); r = annotate_delete_mailbox(mailbox); CU_ASSERT_EQUAL(r, 0); CU_ASSERT_EQUAL(fexists(DBDIR"/data/user/smurf/cyrus.annotations"), -ENOENT); /* check that the values are gone */ r = annotatemore_msg_lookup(MBOXNAME1_INT, 0, COMMENT, /*userid*/"", &val2); CU_ASSERT_EQUAL_FATAL(r, 0); CU_ASSERT_PTR_NULL_FATAL(val2.s); buf_free(&val2); r = annotatemore_msg_lookup(MBOXNAME1_INT, 42, COMMENT, /*userid*/"", &val2); CU_ASSERT_EQUAL_FATAL(r, 0); CU_ASSERT_PTR_NULL_FATAL(val2.s); buf_free(&val2); r = annotatemore_msg_lookup(MBOXNAME1_INT, 127, COMMENT, /*userid*/"", &val2); CU_ASSERT_EQUAL_FATAL(r, 0); CU_ASSERT_PTR_NULL_FATAL(val2.s); buf_free(&val2); annotatemore_close(); CU_ASSERT_EQUAL(fexists(DBDIR"/data/user/smurf/cyrus.annotations"), -ENOENT); strarray_fini(&entries); strarray_fini(&attribs); buf_free(&val); mailbox_close(&mailbox); } static void test_rename(void) { int r; annotate_state_t *astate = NULL; strarray_t entries = STRARRAY_INITIALIZER; strarray_t attribs = STRARRAY_INITIALIZER; struct entryattlist *ealist = NULL; struct buf val = BUF_INITIALIZER; struct buf val2 = BUF_INITIALIZER; struct mailbox *mailbox1 = NULL; struct mailbox *mailbox2 = NULL; annotate_init(NULL, NULL); annotatemore_open(); CU_ASSERT_EQUAL(fexists(DBDIR"/data/user/smurf/cyrus.annotations"), -ENOENT); CU_ASSERT_EQUAL(fexists(DBDIR"/data/user/smurfette/cyrus.annotations"), -ENOENT); r = mailbox_open_iwl(MBOXNAME1_INT, &mailbox1); CU_ASSERT_EQUAL_FATAL(r, 0); r = mailbox_open_iwl(MBOXNAME2_INT, &mailbox2); CU_ASSERT_EQUAL_FATAL(r, 0); strarray_append(&entries, COMMENT); strarray_append(&attribs, VALUE_SHARED); /* set some values */ buf_appendcstr(&val, VALUE0); setentryatt(&ealist, COMMENT, VALUE_SHARED, &val); astate = annotate_state_new(); annotate_state_set_auth(astate, isadmin, userid, auth_state); r = annotate_state_set_mailbox(astate, mailbox1); CU_ASSERT_EQUAL(r, 0); r = annotate_state_store(astate, ealist); CU_ASSERT_EQUAL(r, 0); r = annotate_state_commit(&astate); CU_ASSERT_EQUAL(r, 0); freeentryatts(ealist); ealist = NULL; buf_reset(&val); buf_appendcstr(&val, VALUE1); setentryatt(&ealist, COMMENT, VALUE_SHARED, &val); r = mailbox_get_annotate_state(mailbox1, 42, &astate); CU_ASSERT_EQUAL(r, 0); annotate_state_set_auth(astate, isadmin, userid, auth_state); r = annotate_state_store(astate, ealist); CU_ASSERT_EQUAL(r, 0); freeentryatts(ealist); ealist = NULL; buf_reset(&val); buf_appendcstr(&val, VALUE2); setentryatt(&ealist, COMMENT, VALUE_SHARED, &val); r = mailbox_get_annotate_state(mailbox1, 127, &astate); CU_ASSERT_EQUAL(r, 0); annotate_state_set_auth(astate, isadmin, userid, auth_state); r = annotate_state_store(astate, ealist); CU_ASSERT_EQUAL(r, 0); freeentryatts(ealist); ealist = NULL; r = mailbox_commit(mailbox1); CU_ASSERT_EQUAL(r, 0); mailbox_close(&mailbox1); r = mailbox_open_iwl(MBOXNAME1_INT, &mailbox1); CU_ASSERT_EQUAL_FATAL(r, 0); /* check that we can fetch the values back */ r = annotatemore_msg_lookup(MBOXNAME1_INT, 0, COMMENT, /*userid*/"", &val2); CU_ASSERT_EQUAL_FATAL(r, 0); CU_ASSERT_PTR_NOT_NULL_FATAL(val2.s); CU_ASSERT_STRING_EQUAL(buf_cstring(&val2), VALUE0); buf_free(&val2); r = annotatemore_msg_lookup(MBOXNAME1_INT, 42, COMMENT, /*userid*/"", &val2); CU_ASSERT_EQUAL_FATAL(r, 0); CU_ASSERT_PTR_NOT_NULL_FATAL(val2.s); CU_ASSERT_STRING_EQUAL(buf_cstring(&val2), VALUE1); buf_free(&val2); r = annotatemore_msg_lookup(MBOXNAME1_INT, 127, COMMENT, /*userid*/"", &val2); CU_ASSERT_EQUAL_FATAL(r, 0); CU_ASSERT_PTR_NOT_NULL_FATAL(val2.s); CU_ASSERT_STRING_EQUAL(buf_cstring(&val2), VALUE2); buf_free(&val2); CU_ASSERT_EQUAL(fexists(DBDIR"/data/user/smurf/cyrus.annotations"), 0); CU_ASSERT_EQUAL(fexists(DBDIR"/data/user/smurfette/cyrus.annotations"), -ENOENT); /* rename MBOXNAME1 -> MBOXNAME2 */ r = annotate_rename_mailbox(mailbox1, mailbox2); CU_ASSERT_EQUAL(r, 0); r = mailbox_copy_files(mailbox1, PARTITION, MBOXNAME2_INT); CU_ASSERT_EQUAL(r, 0); r = mailbox_rename_cleanup(&mailbox1, 0); CU_ASSERT_EQUAL(r, 0); CU_ASSERT_PTR_NULL(mailbox1); CU_ASSERT_EQUAL(fexists(DBDIR"/data/user/smurf/cyrus.annotations"), -ENOENT); CU_ASSERT_EQUAL(fexists(DBDIR"/data/user/smurfette/cyrus.annotations"), 0); /* check that the values are gone under the old name */ r = annotatemore_msg_lookup(MBOXNAME1_INT, 0, COMMENT, /*userid*/"", &val2); CU_ASSERT_EQUAL_FATAL(r, 0); CU_ASSERT_PTR_NULL_FATAL(val2.s); buf_free(&val2); r = annotatemore_msg_lookup(MBOXNAME1_INT, 42, COMMENT, /*userid*/"", &val2); CU_ASSERT_EQUAL_FATAL(r, 0); CU_ASSERT_PTR_NULL_FATAL(val2.s); buf_free(&val2); r = annotatemore_msg_lookup(MBOXNAME1_INT, 127, COMMENT, /*userid*/"", &val2); CU_ASSERT_EQUAL_FATAL(r, 0); CU_ASSERT_PTR_NULL_FATAL(val2.s); buf_free(&val2); /* check that the values are present under the new name */ r = annotatemore_msg_lookup(MBOXNAME2_INT, 0, COMMENT, /*userid*/"", &val2); CU_ASSERT_EQUAL_FATAL(r, 0); CU_ASSERT_PTR_NOT_NULL_FATAL(val2.s); CU_ASSERT_STRING_EQUAL(buf_cstring(&val2), VALUE0); buf_free(&val2); r = annotatemore_msg_lookup(MBOXNAME2_INT, 42, COMMENT, /*userid*/"", &val2); CU_ASSERT_EQUAL_FATAL(r, 0); CU_ASSERT_PTR_NOT_NULL_FATAL(val2.s); CU_ASSERT_STRING_EQUAL(buf_cstring(&val2), VALUE1); buf_free(&val2); r = annotatemore_msg_lookup(MBOXNAME2_INT, 127, COMMENT, /*userid*/"", &val2); CU_ASSERT_EQUAL_FATAL(r, 0); CU_ASSERT_PTR_NOT_NULL_FATAL(val2.s); CU_ASSERT_STRING_EQUAL(buf_cstring(&val2), VALUE2); buf_free(&val2); CU_ASSERT_EQUAL(fexists(DBDIR"/data/user/smurf/cyrus.annotations"), -ENOENT); CU_ASSERT_EQUAL(fexists(DBDIR"/data/user/smurfette/cyrus.annotations"), 0); annotatemore_close(); strarray_fini(&entries); strarray_fini(&attribs); buf_free(&val); mailbox_close(&mailbox1); mailbox_close(&mailbox2); } static void test_abort(void) { int r; annotate_state_t *astate = NULL; strarray_t entries = STRARRAY_INITIALIZER; strarray_t attribs = STRARRAY_INITIALIZER; struct entryattlist *ealist = NULL; struct buf val = BUF_INITIALIZER; struct buf val2 = BUF_INITIALIZER; struct mailbox *mailbox = NULL; annotate_init(NULL, NULL); annotatemore_open(); r = mailbox_open_iwl(MBOXNAME1_INT, &mailbox); CU_ASSERT_EQUAL_FATAL(r, 0); strarray_append(&entries, COMMENT); strarray_append(&attribs, VALUE_SHARED); /* check that the values we'll be setting are not already present */ buf_free(&val2); r = annotatemore_msg_lookup("", 0, COMMENT, /*userid*/"", &val2); CU_ASSERT_EQUAL_FATAL(r, 0); CU_ASSERT_PTR_NULL_FATAL(val2.s); buf_free(&val2); r = annotatemore_msg_lookup(MBOXNAME1_INT, 0, COMMENT, /*userid*/"", &val2); CU_ASSERT_EQUAL_FATAL(r, 0); CU_ASSERT_PTR_NULL_FATAL(val2.s); buf_free(&val2); r = annotatemore_msg_lookup(MBOXNAME1_INT, 42, COMMENT, /*userid*/"", &val2); CU_ASSERT_EQUAL_FATAL(r, 0); CU_ASSERT_PTR_NULL_FATAL(val2.s); /* set a per-server value */ buf_appendcstr(&val, VALUE0); setentryatt(&ealist, COMMENT, VALUE_SHARED, &val); astate = annotate_state_new(); r = annotate_state_set_server(astate); CU_ASSERT_EQUAL(r, 0); annotate_state_set_auth(astate, /*isadmin*/1, userid, auth_state); r = annotate_state_store(astate, ealist); CU_ASSERT_EQUAL(r, 0); freeentryatts(ealist); ealist = NULL; /* but abort the txn */ annotate_state_abort(&astate); /* check that the values are still not present */ buf_free(&val2); r = annotatemore_msg_lookup("", 0, COMMENT, /*userid*/"", &val2); CU_ASSERT_EQUAL_FATAL(r, 0); CU_ASSERT_PTR_NULL_FATAL(val2.s); /* set a per-mailbox value */ buf_appendcstr(&val, VALUE0); setentryatt(&ealist, COMMENT, VALUE_SHARED, &val); astate = annotate_state_new(); r = annotate_state_set_mailbox(astate, mailbox); CU_ASSERT_EQUAL(r, 0); annotate_state_set_auth(astate, /*isadmin*/0, userid, auth_state); r = annotate_state_store(astate, ealist); CU_ASSERT_EQUAL(r, 0); freeentryatts(ealist); ealist = NULL; /* but abort the txn */ annotate_state_abort(&astate); /* check that the values are still not present */ buf_free(&val2); r = annotatemore_msg_lookup("", 0, COMMENT, /*userid*/"", &val2); CU_ASSERT_EQUAL_FATAL(r, 0); CU_ASSERT_PTR_NULL_FATAL(val2.s); buf_free(&val2); r = annotatemore_msg_lookup(MBOXNAME1_INT, 0, COMMENT, /*userid*/"", &val2); CU_ASSERT_EQUAL_FATAL(r, 0); CU_ASSERT_PTR_NULL_FATAL(val2.s); /* set a per-message value */ buf_reset(&val); buf_appendcstr(&val, VALUE1); setentryatt(&ealist, COMMENT, VALUE_SHARED, &val); r = mailbox_get_annotate_state(mailbox, 42, &astate); CU_ASSERT_EQUAL(r, 0); annotate_state_set_auth(astate, isadmin, userid, auth_state); r = annotate_state_store(astate, ealist); CU_ASSERT_EQUAL(r, 0); freeentryatts(ealist); ealist = NULL; /* but abort the txn */ annotate_state_abort(&mailbox->annot_state); /* check that the values are still not present */ buf_free(&val2); r = annotatemore_msg_lookup("", 0, COMMENT, /*userid*/"", &val2); CU_ASSERT_EQUAL_FATAL(r, 0); CU_ASSERT_PTR_NULL_FATAL(val2.s); buf_free(&val2); r = annotatemore_msg_lookup(MBOXNAME1_INT, 0, COMMENT, /*userid*/"", &val2); CU_ASSERT_EQUAL_FATAL(r, 0); CU_ASSERT_PTR_NULL_FATAL(val2.s); buf_free(&val2); r = annotatemore_msg_lookup(MBOXNAME1_INT, 42, COMMENT, /*userid*/"", &val2); CU_ASSERT_EQUAL_FATAL(r, 0); CU_ASSERT_PTR_NULL_FATAL(val2.s); annotatemore_close(); strarray_fini(&entries); strarray_fini(&attribs); buf_free(&val); buf_free(&val2); mailbox_close(&mailbox); } static void test_msg_copy(void) { int r; annotate_state_t *astate = NULL; strarray_t entries = STRARRAY_INITIALIZER; strarray_t attribs = STRARRAY_INITIALIZER; struct entryattlist *ealist = NULL; struct buf val = BUF_INITIALIZER; struct buf val2 = BUF_INITIALIZER; struct mailbox *mailbox1 = NULL; struct mailbox *mailbox2 = NULL; annotate_init(NULL, NULL); annotatemore_open(); CU_ASSERT_EQUAL(fexists(DBDIR"/data/user/smurf/cyrus.annotations"), -ENOENT); CU_ASSERT_EQUAL(fexists(DBDIR"/data/user/smurfette/cyrus.annotations"), -ENOENT); r = mailbox_open_iwl(MBOXNAME1_INT, &mailbox1); CU_ASSERT_EQUAL_FATAL(r, 0); r = mailbox_open_iwl(MBOXNAME2_INT, &mailbox2); CU_ASSERT_EQUAL_FATAL(r, 0); strarray_append(&entries, COMMENT); strarray_append(&attribs, VALUE_SHARED); /* set some values */ buf_appendcstr(&val, VALUE0); setentryatt(&ealist, COMMENT, VALUE_SHARED, &val); r = mailbox_get_annotate_state(mailbox1, 17, &astate); CU_ASSERT_EQUAL(r, 0); annotate_state_set_auth(astate, isadmin, userid, auth_state); r = annotate_state_store(astate, ealist); CU_ASSERT_EQUAL(r, 0); freeentryatts(ealist); ealist = NULL; buf_reset(&val); buf_appendcstr(&val, VALUE1); setentryatt(&ealist, COMMENT, VALUE_SHARED, &val); r = mailbox_get_annotate_state(mailbox1, 42, &astate); CU_ASSERT_EQUAL(r, 0); annotate_state_set_auth(astate, isadmin, userid, auth_state); r = annotate_state_store(astate, ealist); CU_ASSERT_EQUAL(r, 0); freeentryatts(ealist); ealist = NULL; buf_reset(&val); buf_appendcstr(&val, VALUE2); setentryatt(&ealist, COMMENT, VALUE_SHARED, &val); r = mailbox_get_annotate_state(mailbox1, 127, &astate); CU_ASSERT_EQUAL(r, 0); annotate_state_set_auth(astate, isadmin, userid, auth_state); r = annotate_state_store(astate, ealist); CU_ASSERT_EQUAL(r, 0); freeentryatts(ealist); ealist = NULL; r = mailbox_commit(mailbox1); CU_ASSERT_EQUAL(r, 0); mailbox_close(&mailbox1); /* check that we can fetch the values back */ buf_free(&val2); r = annotatemore_msg_lookup(MBOXNAME1_INT, 17, COMMENT, /*userid*/"", &val2); CU_ASSERT_EQUAL_FATAL(r, 0); CU_ASSERT_PTR_NOT_NULL_FATAL(val2.s); CU_ASSERT_STRING_EQUAL(buf_cstring(&val2), VALUE0); buf_free(&val2); r = annotatemore_msg_lookup(MBOXNAME1_INT, 42, COMMENT, /*userid*/"", &val2); CU_ASSERT_EQUAL_FATAL(r, 0); CU_ASSERT_PTR_NOT_NULL_FATAL(val2.s); CU_ASSERT_STRING_EQUAL(buf_cstring(&val2), VALUE1); buf_free(&val2); r = annotatemore_msg_lookup(MBOXNAME1_INT, 127, COMMENT, /*userid*/"", &val2); CU_ASSERT_EQUAL_FATAL(r, 0); CU_ASSERT_PTR_NOT_NULL_FATAL(val2.s); CU_ASSERT_STRING_EQUAL(buf_cstring(&val2), VALUE2); buf_free(&val2); r = annotatemore_msg_lookup(MBOXNAME2_INT, 35, COMMENT, /*userid*/"", &val2); CU_ASSERT_EQUAL_FATAL(r, 0); CU_ASSERT_PTR_NULL_FATAL(val2.s); CU_ASSERT_EQUAL(fexists(DBDIR"/data/user/smurf/cyrus.annotations"), 0); CU_ASSERT_EQUAL(fexists(DBDIR"/data/user/smurfette/cyrus.annotations"), -ENOENT); /* copy MBOXNAME1,17 -> MBOXNAME2,35 */ r = mailbox_open_iwl(MBOXNAME1_INT, &mailbox1); CU_ASSERT_EQUAL_FATAL(r, 0); /* ensure we have an astate connected to the destination * mailbox, so that the annotation txn will be committed * when we close the mailbox */ r = mailbox_get_annotate_state(mailbox2, 35, &astate); CU_ASSERT_EQUAL(r, 0); r = annotate_msg_copy(mailbox1, 17, mailbox2, 35, "smurf"); CU_ASSERT_EQUAL(r, 0); r = mailbox_commit(mailbox2); CU_ASSERT_EQUAL(r, 0); mailbox_close(&mailbox2); mailbox_close(&mailbox1); CU_ASSERT_EQUAL(fexists(DBDIR"/data/user/smurf/cyrus.annotations"), 0); CU_ASSERT_EQUAL(fexists(DBDIR"/data/user/smurfette/cyrus.annotations"), 0); /* check that the values copied are present for both mailboxes */ buf_free(&val2); r = annotatemore_msg_lookup(MBOXNAME1_INT, 17, COMMENT, /*userid*/"", &val2); CU_ASSERT_EQUAL_FATAL(r, 0); CU_ASSERT_PTR_NOT_NULL_FATAL(val2.s); CU_ASSERT_STRING_EQUAL(buf_cstring(&val2), VALUE0); buf_free(&val2); r = annotatemore_msg_lookup(MBOXNAME2_INT, 35, COMMENT, /*userid*/"", &val2); CU_ASSERT_EQUAL_FATAL(r, 0); CU_ASSERT_PTR_NOT_NULL_FATAL(val2.s); CU_ASSERT_STRING_EQUAL(buf_cstring(&val2), VALUE0); /* check that the values not copied are only present in the source * mailbox */ buf_free(&val2); r = annotatemore_msg_lookup(MBOXNAME1_INT, 42, COMMENT, /*userid*/"", &val2); CU_ASSERT_EQUAL_FATAL(r, 0); CU_ASSERT_PTR_NOT_NULL_FATAL(val2.s); CU_ASSERT_STRING_EQUAL(buf_cstring(&val2), VALUE1); buf_free(&val2); r = annotatemore_msg_lookup(MBOXNAME1_INT, 127, COMMENT, /*userid*/"", &val2); CU_ASSERT_EQUAL_FATAL(r, 0); CU_ASSERT_PTR_NOT_NULL_FATAL(val2.s); CU_ASSERT_STRING_EQUAL(buf_cstring(&val2), VALUE2); buf_free(&val2); r = annotatemore_msg_lookup(MBOXNAME2_INT, 42, COMMENT, /*userid*/"", &val2); CU_ASSERT_EQUAL_FATAL(r, 0); CU_ASSERT_PTR_NULL(val2.s); buf_free(&val2); r = annotatemore_msg_lookup(MBOXNAME2_INT, 127, COMMENT, /*userid*/"", &val2); CU_ASSERT_EQUAL_FATAL(r, 0); CU_ASSERT_PTR_NULL(val2.s); CU_ASSERT_EQUAL(fexists(DBDIR"/data/user/smurf/cyrus.annotations"), 0); CU_ASSERT_EQUAL(fexists(DBDIR"/data/user/smurfette/cyrus.annotations"), 0); annotatemore_close(); strarray_fini(&entries); strarray_fini(&attribs); buf_free(&val); buf_free(&val2); mailbox_close(&mailbox1); mailbox_close(&mailbox2); } static void test_missing_definitions_file(void) { set_annotation_definitions(NULL); CU_SYSLOG_MATCH("annotations\\.def: could not open.*No such file"); annotate_init(NULL, NULL); /* if we got here, we didn't fatal() */ /* but we did complain to syslog */ CU_ASSERT_SYSLOG(/*all*/0, 1); } static void test_broken_definitions_file_1(void) { set_annotation_definitions( EXENTRY",sXerver,string,backend,value.shared,\n"); CU_SYSLOG_MATCH("invalid annotation scope.*'sXerver'"); annotate_init(NULL, NULL); /* if we got here, we didn't fatal() */ /* but we did complain to syslog */ CU_ASSERT_SYSLOG(/*all*/0, 1); } static void test_broken_definitions_file_2(void) { set_annotation_definitions( EXENTRY",server,stXring,backend,value.shared,\n"); CU_SYSLOG_MATCH("invalid annotation type.*'stXring'"); annotate_init(NULL, NULL); /* if we got here, we didn't fatal() */ /* but we did complain to syslog */ CU_ASSERT_SYSLOG(/*all*/0, 1); } static void test_broken_definitions_file_3(void) { set_annotation_definitions( EXENTRY",server,string,bacXkend,value.shared,\n"); CU_SYSLOG_MATCH("invalid annotation proxy type.*'bacXkend'"); annotate_init(NULL, NULL); /* if we got here, we didn't fatal() */ /* but we did complain to syslog */ CU_ASSERT_SYSLOG(/*all*/0, 1); } static void test_broken_definitions_file_4(void) { set_annotation_definitions( EXENTRY",server,string,backend,valuXe.shared,\n"); CU_SYSLOG_MATCH("invalid annotation attributes.*'valuXe.shared'"); annotate_init(NULL, NULL); /* if we got here, we didn't fatal() */ /* but we did complain to syslog */ CU_ASSERT_SYSLOG(/*all*/0, 1); } static void test_broken_definitions_file_5(void) { set_annotation_definitions( "/flags/foobar,message,string,backend,value.shared,\n"); CU_SYSLOG_MATCH("message entry under /flags/"); annotate_init(NULL, NULL); /* if we got here, we didn't fatal() */ /* but we did complain to syslog */ CU_ASSERT_SYSLOG(/*all*/0, 1); } static void test_broken_definitions_file_6(void) { set_annotation_definitions( "/vendor/cmu/cyrus-imapd/foobar,server,string,backend,value.shared,\n"); CU_SYSLOG_MATCH("annotation under /vendor/cmu/cyrus-imapd/"); annotate_init(NULL, NULL); /* if we got here, we didn't fatal() */ /* but we did complain to syslog */ CU_ASSERT_SYSLOG(/*all*/0, 1); } static void test_broken_definitions_file_7(void) { set_annotation_definitions( EXENTRY",server,string,backend,value.shared,,,,\n"); CU_SYSLOG_MATCH("junk at end of line"); annotate_init(NULL, NULL); /* if we got here, we didn't fatal() */ /* but we did complain to syslog */ CU_ASSERT_SYSLOG(/*all*/0, 1); } static void test_broken_definitions_file_8(void) { set_annotation_definitions( EXENTRY",server,string,\n"); CU_SYSLOG_MATCH("invalid annotation attributes.*"); annotate_init(NULL, NULL); /* if we got here, we didn't fatal() */ /* but we did complain to syslog */ /* Please note that this one complains to syslog twice */ CU_ASSERT_SYSLOG(/*all*/0, 2); } static void test_broken_definitions_file_9(void) { /* test that when parsing a bitfield, only the first * invalid name is reported in the error context */ set_annotation_definitions( EXENTRY",server,string,backend,value valXue valYue,\n"); CU_SYSLOG_MATCH("invalid annotation attributes.*'valXue'"); annotate_init(NULL, NULL); /* if we got here, we didn't fatal() */ /* but we did complain to syslog */ CU_ASSERT_SYSLOG(/*all*/0, 1); } static void test_broken_definitions_file_10(void) { set_annotation_definitions( EXENTRY",ser@ver,string,backend,value.shared,\n"); CU_SYSLOG_MATCH("invalid character.*'@"); annotate_init(NULL, NULL); /* if we got here, we didn't fatal() */ /* but we did complain to syslog */ CU_ASSERT_SYSLOG(/*all*/0, 1); } static void test_getset_server_undefined(void) { int r; annotate_state_t *astate = NULL; strarray_t entries = STRARRAY_INITIALIZER; strarray_t attribs = STRARRAY_INITIALIZER; strarray_t results = STRARRAY_INITIALIZER; struct entryattlist *ealist = NULL; struct buf val = BUF_INITIALIZER; struct buf val2 = BUF_INITIALIZER; annotate_init(NULL, NULL); annotatemore_open(); astate = annotate_state_new(); r = annotate_state_set_server(astate); CU_ASSERT_EQUAL(r, 0); annotate_state_set_auth(astate, isadmin, userid, auth_state); strarray_append(&entries, EXENTRY); strarray_append(&attribs, VALUE_SHARED); /* check that there is no value initially */ r = annotate_state_fetch(astate, &entries, &attribs, fetch_cb, &results, NULL); CU_ASSERT_EQUAL(r, 0); CU_ASSERT_EQUAL_FATAL(results.count, 1); #define EXPECTED \ "mboxname=\"\" " \ "uid=0 " \ "entry=\"" EXENTRY "\" " \ VALUE_SHARED "=NIL" CU_ASSERT_STRING_EQUAL(results.data[0], EXPECTED); #undef EXPECTED strarray_truncate(&results, 0); r = annotatemore_lookup(/*mboxname*/"", EXENTRY, /*userid*/"", &val); CU_ASSERT_EQUAL(r, 0); CU_ASSERT_PTR_NULL(val.s); /* setting a value should fail */ buf_appendcstr(&val, VALUE0); setentryatt(&ealist, EXENTRY, VALUE_SHARED, &val); annotate_state_set_auth(astate, /*isadmin*/1, userid, auth_state); r = annotate_state_store(astate, ealist); annotate_state_set_auth(astate, /*isadmin*/0, userid, auth_state); CU_ASSERT_EQUAL(r, IMAP_PERMISSION_DENIED); freeentryatts(ealist); ealist = NULL; r = annotate_state_commit(&astate); CU_ASSERT_EQUAL(r, 0); /* check that there is no value */ astate = annotate_state_new(); r = annotate_state_set_server(astate); CU_ASSERT_EQUAL(r, 0); annotate_state_set_auth(astate, /*isadmin*/0, userid, auth_state); r = annotate_state_fetch(astate, &entries, &attribs, fetch_cb, &results, NULL); CU_ASSERT_EQUAL(r, 0); CU_ASSERT_EQUAL_FATAL(results.count, 1); #define EXPECTED \ "mboxname=\"\" " \ "uid=0 " \ "entry=\"" EXENTRY "\" " \ VALUE_SHARED "=NIL" CU_ASSERT_STRING_EQUAL(results.data[0], EXPECTED); #undef EXPECTED strarray_truncate(&results, 0); buf_free(&val); r = annotatemore_lookup(/*mboxname*/"", EXENTRY, /*userid*/"", &val); CU_ASSERT_EQUAL(r, 0); CU_ASSERT_PTR_NULL(val.s); annotate_state_abort(&astate); annotatemore_close(); strarray_fini(&entries); strarray_fini(&attribs); strarray_fini(&results); buf_free(&val); buf_free(&val2); } static void test_getset_server_defined(void) { int r; annotate_state_t *astate = NULL; strarray_t entries = STRARRAY_INITIALIZER; strarray_t attribs = STRARRAY_INITIALIZER; strarray_t results = STRARRAY_INITIALIZER; struct entryattlist *ealist = NULL; struct buf val = BUF_INITIALIZER; struct buf val2 = BUF_INITIALIZER; set_annotation_definitions( EXENTRY",server,string,backend,value.shared,\n"); annotate_init(NULL, NULL); annotatemore_open(); astate = annotate_state_new(); r = annotate_state_set_server(astate); CU_ASSERT_EQUAL(r, 0); annotate_state_set_auth(astate, isadmin, userid, auth_state); strarray_append(&entries, EXENTRY); strarray_append(&attribs, VALUE_SHARED); strarray_append(&attribs, SIZE_SHARED); /* check that there is no value initially */ r = annotate_state_fetch(astate, &entries, &attribs, fetch_cb, &results, NULL); CU_ASSERT_EQUAL(r, 0); CU_ASSERT_EQUAL_FATAL(results.count, 1); #define EXPECTED \ "mboxname=\"\" " \ "uid=0 " \ "entry=\"" EXENTRY "\" " \ VALUE_SHARED "=NIL " \ SIZE_SHARED "=\"0\"" CU_ASSERT_STRING_EQUAL(results.data[0], EXPECTED); #undef EXPECTED strarray_truncate(&results, 0); r = annotatemore_lookup(/*mboxname*/"", EXENTRY, /*userid*/"", &val); CU_ASSERT_EQUAL(r, 0); CU_ASSERT_PTR_NULL(val.s); /* set a value */ buf_appendcstr(&val, VALUE0); setentryatt(&ealist, EXENTRY, VALUE_SHARED, &val); annotate_state_set_auth(astate, /*isadmin*/1, userid, auth_state); r = annotate_state_store(astate, ealist); annotate_state_set_auth(astate, /*isadmin*/0, userid, auth_state); CU_ASSERT_EQUAL(r, 0); freeentryatts(ealist); ealist = NULL; /* check that we can fetch the value back in the same txn */ r = annotate_state_fetch(astate, &entries, &attribs, fetch_cb, &results, NULL); CU_ASSERT_EQUAL(r, 0); CU_ASSERT_EQUAL_FATAL(results.count, 1); #define EXPECTED \ "mboxname=\"\" " \ "uid=0 " \ "entry=\"" EXENTRY "\" " \ VALUE_SHARED "=\"" VALUE0 "\" " \ SIZE_SHARED "=\"" LENGTH0 "\"" CU_ASSERT_STRING_EQUAL(results.data[0], EXPECTED); #undef EXPECTED strarray_truncate(&results, 0); r = annotatemore_lookup(/*mboxname*/"", EXENTRY, /*userid*/"", &val2); CU_ASSERT_EQUAL_FATAL(r, 0); CU_ASSERT_PTR_NOT_NULL_FATAL(val2.s); CU_ASSERT_STRING_EQUAL(buf_cstring(&val2), VALUE0); buf_free(&val2); r = annotate_state_commit(&astate); CU_ASSERT_EQUAL(r, 0); /* check that we can fetch the value back in a new txn */ astate = annotate_state_new(); r = annotate_state_set_server(astate); CU_ASSERT_EQUAL(r, 0); annotate_state_set_auth(astate, isadmin, userid, auth_state); r = annotate_state_fetch(astate, &entries, &attribs, fetch_cb, &results, NULL); CU_ASSERT_EQUAL(r, 0); CU_ASSERT_EQUAL_FATAL(results.count, 1); #define EXPECTED \ "mboxname=\"\" " \ "uid=0 " \ "entry=\"" EXENTRY "\" " \ VALUE_SHARED "=\"" VALUE0 "\" " \ SIZE_SHARED "=\"" LENGTH0 "\"" CU_ASSERT_STRING_EQUAL(results.data[0], EXPECTED); #undef EXPECTED strarray_truncate(&results, 0); r = annotatemore_lookup(/*mboxname*/"", EXENTRY, /*userid*/"", &val2); CU_ASSERT_EQUAL_FATAL(r, 0); CU_ASSERT_PTR_NOT_NULL_FATAL(val2.s); CU_ASSERT_STRING_EQUAL(buf_cstring(&val2), VALUE0); buf_free(&val2); annotate_state_abort(&astate); annotatemore_close(); /* check that we can fetch the value back after close and re-open */ annotatemore_open(); astate = annotate_state_new(); r = annotate_state_set_server(astate); CU_ASSERT_EQUAL(r, 0); annotate_state_set_auth(astate, isadmin, userid, auth_state); r = annotate_state_fetch(astate, &entries, &attribs, fetch_cb, &results, NULL); CU_ASSERT_EQUAL(r, 0); CU_ASSERT_EQUAL_FATAL(results.count, 1); #define EXPECTED \ "mboxname=\"\" " \ "uid=0 " \ "entry=\"" EXENTRY "\" " \ VALUE_SHARED "=\"" VALUE0 "\" " \ SIZE_SHARED "=\"" LENGTH0 "\"" CU_ASSERT_STRING_EQUAL(results.data[0], EXPECTED); #undef EXPECTED strarray_truncate(&results, 0); r = annotatemore_lookup(/*mboxname*/"", EXENTRY, /*userid*/"", &val2); CU_ASSERT_EQUAL_FATAL(r, 0); CU_ASSERT_PTR_NOT_NULL_FATAL(val2.s); CU_ASSERT_STRING_EQUAL(buf_cstring(&val2), VALUE0); buf_free(&val2); buf_free(&val); setentryatt(&ealist, EXENTRY, VALUE_SHARED, &val); annotate_state_set_auth(astate, /*isadmin*/1, userid, auth_state); r = annotate_state_store(astate, ealist); annotate_state_set_auth(astate, /*isadmin*/0, userid, auth_state); CU_ASSERT_EQUAL(r, 0); freeentryatts(ealist); ealist = NULL; r = annotate_state_commit(&astate); CU_ASSERT_EQUAL(r, 0); /* check that there is no value any more */ astate = annotate_state_new(); r = annotate_state_set_server(astate); CU_ASSERT_EQUAL(r, 0); annotate_state_set_auth(astate, isadmin, userid, auth_state); r = annotate_state_fetch(astate, &entries, &attribs, fetch_cb, &results, NULL); CU_ASSERT_EQUAL(r, 0); CU_ASSERT_EQUAL_FATAL(results.count, 1); #define EXPECTED \ "mboxname=\"\" " \ "uid=0 " \ "entry=\"" EXENTRY "\" " \ VALUE_SHARED "=NIL " \ SIZE_SHARED "=\"0\"" CU_ASSERT_STRING_EQUAL(results.data[0], EXPECTED); #undef EXPECTED strarray_truncate(&results, 0); r = annotatemore_lookup(/*mboxname*/"", EXENTRY, /*userid*/"", &val); CU_ASSERT_EQUAL(r, 0); CU_ASSERT_PTR_NULL(val.s); annotate_state_abort(&astate); annotatemore_close(); strarray_fini(&entries); strarray_fini(&attribs); strarray_fini(&results); buf_free(&val); } static const char *stringifyea(const struct entryattlist *ea) { const struct attvaluelist *av; static struct buf buf; buf_reset(&buf); for ( ; ea ; ea = ea->next) { buf_printf(&buf, "(%s", ea->entry); for (av = ea->attvalues ; av ; av = av->next) { buf_printf(&buf, "(%s\"", av->attrib); buf_appendmap(&buf, av->value.s, av->value.len); buf_appendcstr(&buf, "\")"); } buf_putc(&buf, ')'); } return buf_cstring(&buf); } static void test_setentryatt(void) { struct entryattlist *eal = NULL; struct buf val = BUF_INITIALIZER; CU_ASSERT_PTR_NULL(eal); CU_ASSERT_STRING_EQUAL(stringifyea(eal), ""); /* Test data courtesy http://hipsteripsum.me */ /* append an ea and av */ buf_init_ro(&val, "coffee", 6); setentryatt(&eal, "letterpress", "single-origin", &val); CU_ASSERT_PTR_NOT_NULL(eal); CU_ASSERT_STRING_EQUAL(stringifyea(eal), "(letterpress(single-origin\"coffee\"))"); /* append another ea and av */ buf_init_ro(&val, "mustache", 8); setentryatt(&eal, "cosby", "sweater", &val); CU_ASSERT_PTR_NOT_NULL(eal); CU_ASSERT_STRING_EQUAL(stringifyea(eal), "(letterpress(single-origin\"coffee\"))" "(cosby(sweater\"mustache\"))"); /* append a third ea and av */ buf_init_ro(&val, "portland", 8); setentryatt(&eal, "cred", "artisan", &val); CU_ASSERT_PTR_NOT_NULL(eal); CU_ASSERT_STRING_EQUAL(stringifyea(eal), "(letterpress(single-origin\"coffee\"))" "(cosby(sweater\"mustache\"))" "(cred(artisan\"portland\"))"); /* replace the value in an av */ buf_init_ro(&val, "shoreditch", 10); setentryatt(&eal, "cosby", "sweater", &val); CU_ASSERT_PTR_NOT_NULL(eal); CU_ASSERT_STRING_EQUAL(stringifyea(eal), "(letterpress(single-origin\"coffee\"))" "(cosby(sweater\"shoreditch\"))" "(cred(artisan\"portland\"))"); /* add an av to an existing ea */ buf_init_ro(&val, "gluten-free", 11); setentryatt(&eal, "letterpress", "biodiesel", &val); CU_ASSERT_PTR_NOT_NULL(eal); CU_ASSERT_STRING_EQUAL(stringifyea(eal), "(letterpress(single-origin\"coffee\")" "(biodiesel\"gluten-free\"))" "(cosby(sweater\"shoreditch\"))" "(cred(artisan\"portland\"))"); freeentryatts(eal); buf_free(&val); } static void test_clearentryatt(void) { struct entryattlist *eal = NULL; struct buf val = BUF_INITIALIZER; /* Test data courtesy http://hipsteripsum.me */ /* append an ea and av */ buf_init_ro(&val, "coffee", 6); setentryatt(&eal, "letterpress", "single-origin", &val); /* add an av to an existing ea */ buf_init_ro(&val, "gluten-free", 11); setentryatt(&eal, "letterpress", "biodiesel", &val); /* add another av to an existing ea */ buf_init_ro(&val, "organic", 7); setentryatt(&eal, "letterpress", "keffiyeh", &val); /* append another ea and av */ buf_init_ro(&val, "shoreditch", 10); setentryatt(&eal, "cosby", "sweater", &val); /* append a third ea and av */ buf_init_ro(&val, "portland", 8); setentryatt(&eal, "cred", "artisan", &val); CU_ASSERT_PTR_NOT_NULL(eal); CU_ASSERT_STRING_EQUAL(stringifyea(eal), "(letterpress(single-origin\"coffee\")" "(biodiesel\"gluten-free\")" "(keffiyeh\"organic\"))" "(cosby(sweater\"shoreditch\"))" "(cred(artisan\"portland\"))"); clearentryatt(&eal, "cosby", "sweater"); CU_ASSERT_PTR_NOT_NULL(eal); CU_ASSERT_STRING_EQUAL(stringifyea(eal), "(letterpress(single-origin\"coffee\")" "(biodiesel\"gluten-free\")" "(keffiyeh\"organic\"))" "(cred(artisan\"portland\"))"); clearentryatt(&eal, "letterpress", "biodiesel"); CU_ASSERT_PTR_NOT_NULL(eal); CU_ASSERT_STRING_EQUAL(stringifyea(eal), "(letterpress(single-origin\"coffee\")" "(keffiyeh\"organic\"))" "(cred(artisan\"portland\"))"); clearentryatt(&eal, "letterpress", "single-origin"); CU_ASSERT_PTR_NOT_NULL(eal); CU_ASSERT_STRING_EQUAL(stringifyea(eal), "(letterpress" "(keffiyeh\"organic\"))" "(cred(artisan\"portland\"))"); clearentryatt(&eal, "letterpress", "keffiyeh"); CU_ASSERT_PTR_NOT_NULL(eal); CU_ASSERT_STRING_EQUAL(stringifyea(eal), "(cred(artisan\"portland\"))"); clearentryatt(&eal, "cred", "artisan"); CU_ASSERT_PTR_NULL(eal); CU_ASSERT_STRING_EQUAL(stringifyea(eal), ""); freeentryatts(eal); buf_free(&val); } static int set_up(void) { int r; struct mboxlist_entry mbentry; struct mailbox *mailbox; const char * const *d; static const char * const dirs[] = { DBDIR, DBDIR"/db", DBDIR"/conf", DBDIR"/data", DBDIR"/data/user", DBDIR"/data/user/smurf", DBDIR"/data/user/smurfette", NULL }; r = system("rm -rf " DBDIR); if (r) return r; r = fexists(DBDIR); if (r != -ENOENT) return ENOTDIR; for (d = dirs ; *d ; d++) { r = mkdir(*d, 0777); if (r < 0) { int e = errno; perror(*d); return e; } } libcyrus_config_setstring(CYRUSOPT_CONFIG_DIR, DBDIR); config_read_string( "configdirectory: "DBDIR"/conf\n" "defaultpartition: "PARTITION"\n" "partition-"PARTITION": "DBDIR"/data\n" ); cyrusdb_init(); config_mboxlist_db = "skiplist"; config_annotation_db = "skiplist"; config_quota_db = "skiplist"; userid = "smurf"; isadmin = 0; auth_state = auth_newstate(userid); quotadb_init(0); quotadb_open(NULL); mboxlist_init(0); mboxlist_open(NULL); memset(&mbentry, 0, sizeof(mbentry)); mbentry.name = MBOXNAME1_INT; mbentry.mbtype = 0; mbentry.partition = PARTITION; mbentry.acl = ACL; r = mboxlist_update(&mbentry, /*localonly*/1); if (r) return r; r = mailbox_create(MBOXNAME1_INT, /*mbtype*/0, PARTITION, ACL, /*uniqueid*/NULL, /*options*/0, /*uidvalidity*/0, &mailbox); if (r) return r; mailbox_close(&mailbox); memset(&mbentry, 0, sizeof(mbentry)); mbentry.name = MBOXNAME2_INT; mbentry.mbtype = 0; mbentry.partition = PARTITION; mbentry.acl = ACL; r = mboxlist_update(&mbentry, /*localonly*/1); if (r) return r; r = mailbox_create(MBOXNAME2_INT, /*mbtype*/0, PARTITION, ACL, /*uniqueid*/NULL, /*options*/0, /*uidvalidity*/0, &mailbox); if (r) return r; mailbox_close(&mailbox); old_annotation_definitions = imapopts[IMAPOPT_ANNOTATION_DEFINITIONS].val.s; return 0; } static int tear_down(void) { int r; mboxlist_close(); mboxlist_done(); quotadb_close(); quotadb_done(); annotate_done(); imapopts[IMAPOPT_ANNOTATION_DEFINITIONS].val.s = old_annotation_definitions; auth_freestate(auth_state); cyrusdb_done(); config_mboxlist_db = NULL; config_annotation_db = NULL; r = system("rm -rf " DBDIR); if (r) r = -1; return r; } /* vim: set ft=c: */ cyrus-imapd-2.5.10/cunit/tok.testc0000644000175000017500000002447013001236020013732 00000000000000#include "config.h" #include "cunit/cunit.h" #include "tok.h" #include "xmalloc.h" #define WORD0 "lorem" #define WORD1 "ipsum" #define WORD2 "dolor" #define WORD3 "sit" #define WORD4 "amet" static void test_simple(void) { static const char PHRASE[] = WORD0" "WORD1" "WORD2" "WORD3" "WORD4; tok_t tok = TOK_INITIALIZER(PHRASE, NULL, 0); char *p; p = tok_next(&tok); CU_ASSERT_STRING_EQUAL(p, WORD0); p = tok_next(&tok); CU_ASSERT_STRING_EQUAL(p, WORD1); p = tok_next(&tok); CU_ASSERT_STRING_EQUAL(p, WORD2); p = tok_next(&tok); CU_ASSERT_STRING_EQUAL(p, WORD3); p = tok_next(&tok); CU_ASSERT_STRING_EQUAL(p, WORD4); p = tok_next(&tok); CU_ASSERT_PTR_NULL(p); tok_fini(&tok); } static void test_init(void) { static const char PHRASE[] = WORD0" "WORD1" "WORD2" "WORD3" "WORD4; tok_t tok; char *p; tok_init(&tok, PHRASE, NULL, 0); p = tok_next(&tok); CU_ASSERT_STRING_EQUAL(p, WORD0); p = tok_next(&tok); CU_ASSERT_STRING_EQUAL(p, WORD1); p = tok_next(&tok); CU_ASSERT_STRING_EQUAL(p, WORD2); p = tok_next(&tok); CU_ASSERT_STRING_EQUAL(p, WORD3); p = tok_next(&tok); CU_ASSERT_STRING_EQUAL(p, WORD4); p = tok_next(&tok); CU_ASSERT_PTR_NULL(p); tok_fini(&tok); } static void test_initm(void) { static const char PHRASE[] = WORD0" "WORD1" "WORD2" "WORD3" "WORD4; tok_t tok; char *p; char buf[1024]; strcpy(buf, PHRASE); tok_initm(&tok, buf, NULL, 0); p = tok_next(&tok); CU_ASSERT_STRING_EQUAL(p, WORD0); p = tok_next(&tok); CU_ASSERT_STRING_EQUAL(p, WORD1); p = tok_next(&tok); CU_ASSERT_STRING_EQUAL(p, WORD2); p = tok_next(&tok); CU_ASSERT_STRING_EQUAL(p, WORD3); p = tok_next(&tok); CU_ASSERT_STRING_EQUAL(p, WORD4); p = tok_next(&tok); CU_ASSERT_PTR_NULL(p); tok_fini(&tok); } static void test_freebuffer(void) { static const char PHRASE[] = WORD0" "WORD1" "WORD2" "WORD3" "WORD4; tok_t tok; char *p; tok_initm(&tok, xstrdup(PHRASE), NULL, TOK_FREEBUFFER); p = tok_next(&tok); CU_ASSERT_STRING_EQUAL(p, WORD0); p = tok_next(&tok); CU_ASSERT_STRING_EQUAL(p, WORD1); p = tok_next(&tok); CU_ASSERT_STRING_EQUAL(p, WORD2); p = tok_next(&tok); CU_ASSERT_STRING_EQUAL(p, WORD3); p = tok_next(&tok); CU_ASSERT_STRING_EQUAL(p, WORD4); p = tok_next(&tok); CU_ASSERT_PTR_NULL(p); tok_fini(&tok); } static void test_multiple_delim(void) { static const char PHRASE[] = WORD0" "WORD1" \t "WORD2"\r"WORD3"\r\n \t\t\t "WORD4; tok_t tok = TOK_INITIALIZER(PHRASE, NULL, 0); char *p; p = tok_next(&tok); CU_ASSERT_STRING_EQUAL(p, WORD0); p = tok_next(&tok); CU_ASSERT_STRING_EQUAL(p, WORD1); p = tok_next(&tok); CU_ASSERT_STRING_EQUAL(p, WORD2); p = tok_next(&tok); CU_ASSERT_STRING_EQUAL(p, WORD3); p = tok_next(&tok); CU_ASSERT_STRING_EQUAL(p, WORD4); p = tok_next(&tok); CU_ASSERT_PTR_NULL(p); tok_fini(&tok); } static void test_nondefault_delim(void) { static const char PHRASE[] = WORD0","WORD1","WORD2","WORD3","WORD4; tok_t tok = TOK_INITIALIZER(PHRASE, ",", 0); char *p; p = tok_next(&tok); CU_ASSERT_STRING_EQUAL(p, WORD0); p = tok_next(&tok); CU_ASSERT_STRING_EQUAL(p, WORD1); p = tok_next(&tok); CU_ASSERT_STRING_EQUAL(p, WORD2); p = tok_next(&tok); CU_ASSERT_STRING_EQUAL(p, WORD3); p = tok_next(&tok); CU_ASSERT_STRING_EQUAL(p, WORD4); p = tok_next(&tok); CU_ASSERT_PTR_NULL(p); tok_fini(&tok); } static void test_empty(void) { static const char PHRASE[] = ","WORD0","WORD1",,,"WORD2","WORD3","WORD4","; tok_t tok = TOK_INITIALIZER(PHRASE, ",", TOK_EMPTY); char *p; p = tok_next(&tok); CU_ASSERT_STRING_EQUAL(p, ""); p = tok_next(&tok); CU_ASSERT_STRING_EQUAL(p, WORD0); p = tok_next(&tok); CU_ASSERT_STRING_EQUAL(p, WORD1); p = tok_next(&tok); CU_ASSERT_STRING_EQUAL(p, ""); p = tok_next(&tok); CU_ASSERT_STRING_EQUAL(p, ""); p = tok_next(&tok); CU_ASSERT_STRING_EQUAL(p, WORD2); p = tok_next(&tok); CU_ASSERT_STRING_EQUAL(p, WORD3); p = tok_next(&tok); CU_ASSERT_STRING_EQUAL(p, WORD4); p = tok_next(&tok); CU_ASSERT_STRING_EQUAL(p, ""); p = tok_next(&tok); CU_ASSERT_PTR_NULL(p); tok_fini(&tok); } static void test_trimleft(void) { static const char PHRASE[] = " "WORD0",\t"WORD1" ,\r\n "WORD2", "WORD3","WORD4; tok_t tok = TOK_INITIALIZER(PHRASE, ",", TOK_TRIMLEFT); char *p; p = tok_next(&tok); CU_ASSERT_STRING_EQUAL(p, WORD0); p = tok_next(&tok); CU_ASSERT_STRING_EQUAL(p, WORD1" "); p = tok_next(&tok); CU_ASSERT_STRING_EQUAL(p, WORD2); p = tok_next(&tok); CU_ASSERT_STRING_EQUAL(p, WORD3); p = tok_next(&tok); CU_ASSERT_STRING_EQUAL(p, WORD4); p = tok_next(&tok); CU_ASSERT_PTR_NULL(p); tok_fini(&tok); } static void test_trimright(void) { static const char PHRASE[] = WORD0","WORD1"\t, "WORD2"\r\n ,"WORD3" ,"WORD4" "; tok_t tok = TOK_INITIALIZER(PHRASE, ",", TOK_TRIMRIGHT); char *p; p = tok_next(&tok); CU_ASSERT_STRING_EQUAL(p, WORD0); p = tok_next(&tok); CU_ASSERT_STRING_EQUAL(p, WORD1); p = tok_next(&tok); CU_ASSERT_STRING_EQUAL(p, " "WORD2); p = tok_next(&tok); CU_ASSERT_STRING_EQUAL(p, WORD3); p = tok_next(&tok); CU_ASSERT_STRING_EQUAL(p, WORD4); p = tok_next(&tok); CU_ASSERT_PTR_NULL(p); tok_fini(&tok); } static void test_trimboth(void) { static const char PHRASE[] = " "WORD0" \t,"WORD1"\t, "WORD2"\r\n , "WORD3" \t ,"WORD4"\r\n"; tok_t tok = TOK_INITIALIZER(PHRASE, ",", TOK_TRIMLEFT|TOK_TRIMRIGHT); char *p; p = tok_next(&tok); CU_ASSERT_STRING_EQUAL(p, WORD0); p = tok_next(&tok); CU_ASSERT_STRING_EQUAL(p, WORD1); p = tok_next(&tok); CU_ASSERT_STRING_EQUAL(p, WORD2); p = tok_next(&tok); CU_ASSERT_STRING_EQUAL(p, WORD3); p = tok_next(&tok); CU_ASSERT_STRING_EQUAL(p, WORD4); p = tok_next(&tok); CU_ASSERT_PTR_NULL(p); tok_fini(&tok); } static void test_offset(void) { static const char PHRASE[] = WORD0" "WORD1" "WORD2" "WORD3" "WORD4; tok_t tok = TOK_INITIALIZER(PHRASE, NULL, 0); char *p; CU_ASSERT_EQUAL(tok_offset(&tok), 0); p = tok_next(&tok); CU_ASSERT_STRING_EQUAL(p, WORD0); CU_ASSERT_EQUAL(tok_offset(&tok), 0); p = tok_next(&tok); CU_ASSERT_STRING_EQUAL(p, WORD1); CU_ASSERT_EQUAL(tok_offset(&tok), sizeof(WORD0" ")-1); p = tok_next(&tok); CU_ASSERT_STRING_EQUAL(p, WORD2); CU_ASSERT_EQUAL(tok_offset(&tok), sizeof(WORD0" "WORD1" ")-1); p = tok_next(&tok); CU_ASSERT_STRING_EQUAL(p, WORD3); CU_ASSERT_EQUAL(tok_offset(&tok), sizeof(WORD0" "WORD1" "WORD2" ")-1); p = tok_next(&tok); CU_ASSERT_STRING_EQUAL(p, WORD4); CU_ASSERT_EQUAL(tok_offset(&tok), sizeof(WORD0" "WORD1" "WORD2" "WORD3" " )-1); p = tok_next(&tok); CU_ASSERT_PTR_NULL(p); tok_fini(&tok); } static void test_stopearly(void) { static const char PHRASE[] = WORD0" "WORD1" "WORD2" "WORD3" "WORD4; tok_t tok = TOK_INITIALIZER(PHRASE, NULL, 0); char *p; /* test that ceasing to call tok_next() before the end * of the tokens does not leak memory as long as tok_fini() * is called; we rely on Valgrind to find memleaks */ p = tok_next(&tok); CU_ASSERT_STRING_EQUAL(p, WORD0); tok_fini(&tok); } static void test_nofini(void) { static const char PHRASE[] = WORD0" "WORD1" "WORD2" "WORD3" "WORD4; tok_t tok = TOK_INITIALIZER(PHRASE, NULL, 0); char *p; /* test the converse of stopearly, i.e. that tok_fini() is * not necessary if all the tokens are read with tok_next(); * again we rely on Valgrind to find memleaks */ p = tok_next(&tok); CU_ASSERT_STRING_EQUAL(p, WORD0); p = tok_next(&tok); CU_ASSERT_STRING_EQUAL(p, WORD1); p = tok_next(&tok); CU_ASSERT_STRING_EQUAL(p, WORD2); p = tok_next(&tok); CU_ASSERT_STRING_EQUAL(p, WORD3); p = tok_next(&tok); CU_ASSERT_STRING_EQUAL(p, WORD4); p = tok_next(&tok); CU_ASSERT_PTR_NULL(p); /* no tok_fini */ } static void test_blank(void) { static const char PHRASE[] = ""; tok_t tok = TOK_INITIALIZER(PHRASE, NULL, 0); char *p; p = tok_next(&tok); CU_ASSERT_PTR_NULL(p); tok_fini(&tok); } static void test_initnull(void) { tok_t tok; char *p; tok_init(&tok, NULL, NULL, 0); p = tok_next(&tok); CU_ASSERT_PTR_NULL(p); tok_fini(&tok); } static void test_initmnull(void) { tok_t tok; char *p; tok_initm(&tok, NULL, NULL, 0); p = tok_next(&tok); CU_ASSERT_PTR_NULL(p); tok_fini(&tok); } /* Test some portability stubs */ static void test_memmem(void) { #define TESTCASEN(haystack, haystacklen, needle, expoff) \ { \ static const char _haystack[] = (haystack); \ int _haystacklen = (haystacklen); \ static const char _needle[] = (needle); \ int _expoff = (expoff); \ void *p; \ \ p = memmem(_haystack, _haystacklen, \ _needle, sizeof(_needle)-1); \ if (_expoff < 0) { \ CU_ASSERT_PTR_NULL(p); \ } \ else { \ CU_ASSERT_PTR_NOT_NULL(p); \ CU_ASSERT((const char *)p >= _haystack); \ CU_ASSERT((const char *)p < \ _haystack+sizeof(_haystack)-1); \ CU_ASSERT_PTR_EQUAL(p, _haystack+_expoff); \ } \ } #define TESTCASE(haystack, needle, expoff) \ TESTCASEN(haystack, sizeof(haystack)-1, needle, expoff) /* needle easily found */ TESTCASE("quinoa etsy dreamcatcher", "etsy", 7); /* needle not found */ TESTCASE("quinoa etsy dreamcatcher", "cosby", -1); /* first character of needle not found */ TESTCASE("quinoa etsy dreamcatcher", "xylem", -1); /* haystack length is obeyed */ TESTCASEN("quinoa etsy dreamcatcher", 6, "etsy", -1); /* needle first character is repeated in haystack */ TESTCASE("eeeeeeeeeeeeeeeeeepeeeeeeee", "ep", 17); /* needle first character is repeated in needle & haystack */ TESTCASE("eeeeeeeeeeeeeeeeeepeeeeeeee", "eeep", 15); /* no false match near end of haystack */ TESTCASE("quinoa etsy dreamcatcher", "hermes", -1); /* partial matches precede actual match */ TESTCASE("qququiquqquinquinoa", "quinoa", 13); /* match is after embedded nul */ TESTCASE("locavore\0vegan", "vegan", 9); #undef TESTCASE } /* vim: set ft=c: */ cyrus-imapd-2.5.10/cunit/imapurl.testc0000644000175000017500000002763113001236020014610 00000000000000#include #include #include "cunit/cunit.h" #include "imapurl.h" static void test_fromurl_cclient(void) { static const char URL[] = "{foo}bar"; struct imapurl iurl; int r; memset(&iurl, 0x45, sizeof(iurl)); r = imapurl_fromURL(&iurl, URL); CU_ASSERT_EQUAL(r, 0); CU_ASSERT_PTR_NULL(iurl.user); CU_ASSERT_PTR_NULL(iurl.auth); CU_ASSERT_STRING_EQUAL(iurl.server, "foo"); CU_ASSERT_STRING_EQUAL(iurl.mailbox, "bar"); CU_ASSERT_EQUAL(iurl.uidvalidity, 0); CU_ASSERT_EQUAL(iurl.uid, 0); CU_ASSERT_PTR_NULL(iurl.section); CU_ASSERT_EQUAL(iurl.start_octet, 0); CU_ASSERT_EQUAL(iurl.octet_count, 0); CU_ASSERT_PTR_NULL(iurl.urlauth.access); CU_ASSERT_PTR_NULL(iurl.urlauth.mech); CU_ASSERT_PTR_NULL(iurl.urlauth.token); CU_ASSERT_EQUAL(iurl.urlauth.expire, 0); CU_ASSERT_EQUAL(iurl.urlauth.rump_len, 0); free(iurl.freeme); } static void test_fromurl(void) { static const char URL[] = "imap://jeeves/deverill"; struct imapurl iurl; int r; memset(&iurl, 0x45, sizeof(iurl)); r = imapurl_fromURL(&iurl, URL); CU_ASSERT_EQUAL(r, 0); CU_ASSERT_PTR_NULL(iurl.user); CU_ASSERT_PTR_NULL(iurl.auth); CU_ASSERT_STRING_EQUAL(iurl.server, "jeeves"); CU_ASSERT_STRING_EQUAL(iurl.mailbox, "deverill"); CU_ASSERT_EQUAL(iurl.uidvalidity, 0); CU_ASSERT_EQUAL(iurl.uid, 0); CU_ASSERT_PTR_NULL(iurl.section); CU_ASSERT_EQUAL(iurl.start_octet, 0); CU_ASSERT_EQUAL(iurl.octet_count, 0); CU_ASSERT_PTR_NULL(iurl.urlauth.access); CU_ASSERT_PTR_NULL(iurl.urlauth.mech); CU_ASSERT_PTR_NULL(iurl.urlauth.token); CU_ASSERT_EQUAL(iurl.urlauth.expire, 0); CU_ASSERT_EQUAL(iurl.urlauth.rump_len, 0); free(iurl.freeme); } static void test_fromurl_user(void) { static const char URL[] = "imap://wooster@jeeves/deverill"; struct imapurl iurl; int r; memset(&iurl, 0x45, sizeof(iurl)); r = imapurl_fromURL(&iurl, URL); CU_ASSERT_EQUAL(r, 0); CU_ASSERT_STRING_EQUAL(iurl.user, "wooster"); CU_ASSERT_PTR_NULL(iurl.auth); CU_ASSERT_STRING_EQUAL(iurl.server, "jeeves"); CU_ASSERT_STRING_EQUAL(iurl.mailbox, "deverill"); CU_ASSERT_EQUAL(iurl.uidvalidity, 0); CU_ASSERT_EQUAL(iurl.uid, 0); CU_ASSERT_PTR_NULL(iurl.section); CU_ASSERT_EQUAL(iurl.start_octet, 0); CU_ASSERT_EQUAL(iurl.octet_count, 0); CU_ASSERT_PTR_NULL(iurl.urlauth.access); CU_ASSERT_PTR_NULL(iurl.urlauth.mech); CU_ASSERT_PTR_NULL(iurl.urlauth.token); CU_ASSERT_EQUAL(iurl.urlauth.expire, 0); CU_ASSERT_EQUAL(iurl.urlauth.rump_len, 0); free(iurl.freeme); } static void test_fromurl_encuser(void) { static const char URL[] = "imap://%53po%64e@jeeves/deverill"; struct imapurl iurl; int r; memset(&iurl, 0x45, sizeof(iurl)); r = imapurl_fromURL(&iurl, URL); CU_ASSERT_EQUAL(r, 0); CU_ASSERT_STRING_EQUAL(iurl.user, "Spode"); CU_ASSERT_PTR_NULL(iurl.auth); CU_ASSERT_STRING_EQUAL(iurl.server, "jeeves"); CU_ASSERT_STRING_EQUAL(iurl.mailbox, "deverill"); CU_ASSERT_EQUAL(iurl.uidvalidity, 0); CU_ASSERT_EQUAL(iurl.uid, 0); CU_ASSERT_PTR_NULL(iurl.section); CU_ASSERT_EQUAL(iurl.start_octet, 0); CU_ASSERT_EQUAL(iurl.octet_count, 0); CU_ASSERT_PTR_NULL(iurl.urlauth.access); CU_ASSERT_PTR_NULL(iurl.urlauth.mech); CU_ASSERT_PTR_NULL(iurl.urlauth.token); CU_ASSERT_EQUAL(iurl.urlauth.expire, 0); CU_ASSERT_EQUAL(iurl.urlauth.rump_len, 0); free(iurl.freeme); } static void test_fromurl_options(void) { static const char URL[] = "imap://wooster@jeeves/deverill" ";UIDVALIDITY=7890" "/;UID=123456" "/;SECTION=1.4" "/;PARTIAL=1.1023"; struct imapurl iurl; int r; memset(&iurl, 0x45, sizeof(iurl)); r = imapurl_fromURL(&iurl, URL); CU_ASSERT_EQUAL(r, 0); CU_ASSERT_STRING_EQUAL(iurl.user, "wooster"); CU_ASSERT_PTR_NULL(iurl.auth); CU_ASSERT_STRING_EQUAL(iurl.server, "jeeves"); CU_ASSERT_STRING_EQUAL(iurl.mailbox, "deverill"); CU_ASSERT_EQUAL(iurl.uidvalidity, 7890); CU_ASSERT_EQUAL(iurl.uid, 123456); CU_ASSERT_STRING_EQUAL(iurl.section, "1.4"); CU_ASSERT_EQUAL(iurl.start_octet, 1); CU_ASSERT_EQUAL(iurl.octet_count, 1023); CU_ASSERT_PTR_NULL(iurl.urlauth.access); CU_ASSERT_PTR_NULL(iurl.urlauth.mech); CU_ASSERT_PTR_NULL(iurl.urlauth.token); CU_ASSERT_EQUAL(iurl.urlauth.expire, 0); CU_ASSERT_EQUAL(iurl.urlauth.rump_len, 0); free(iurl.freeme); } static void test_fromurl_urlauth(void) { static const char URL[] = "imap://wooster@jeeves/deverill" "/;UID=123456" ";EXPIRE=2010-11-24T06:57:26Z" ";URLAUTH=submit+fred:internal:91354a473744909de610943775f92038"; struct imapurl iurl; int r; memset(&iurl, 0x45, sizeof(iurl)); r = imapurl_fromURL(&iurl, URL); CU_ASSERT_EQUAL(r, 0); CU_ASSERT_STRING_EQUAL(iurl.user, "wooster"); CU_ASSERT_PTR_NULL(iurl.auth); CU_ASSERT_STRING_EQUAL(iurl.server, "jeeves"); CU_ASSERT_STRING_EQUAL(iurl.mailbox, "deverill"); CU_ASSERT_EQUAL(iurl.uidvalidity, 0); CU_ASSERT_EQUAL(iurl.uid, 123456); CU_ASSERT_PTR_NULL(iurl.section); CU_ASSERT_EQUAL(iurl.start_octet, 0); CU_ASSERT_EQUAL(iurl.octet_count, 0); CU_ASSERT_STRING_EQUAL(iurl.urlauth.access, "submit+fred"); CU_ASSERT_STRING_EQUAL(iurl.urlauth.mech, "internal"); CU_ASSERT_STRING_EQUAL(iurl.urlauth.token, "91354a473744909de610943775f92038"); CU_ASSERT_EQUAL(iurl.urlauth.expire, 1290581846); CU_ASSERT_EQUAL(iurl.urlauth.rump_len, 90); free(iurl.freeme); } // TODO: {foo is invalid // TODO: imap:// is invalid // TODO: imap://server/ and imap://server // TODO: %xx encoding in username // TODO: %xx encoding in section // TODO: lowercase option names // TODO: relative urls // TODO: it doesn't seem like it parses a host port // specially, it will be accidentally appended to .server // TODO: no / before ; // TODO: invalidly formatted uidvalidity // TODO: invalidly formatted uid // TODO: invalidly formatted section // TODO: ;AUTH=* at end of user name // TODO: ;AUTH= at end of user name // TODO: ?enc-search at the end static void test_tourl(void) { static const char URL[] = "imap://jeeves/deverill"; struct imapurl iurl; char buf[300]; memset(&iurl, 0, sizeof(iurl)); iurl.server = "jeeves"; iurl.mailbox = "deverill"; memset(buf, 0x45, sizeof(buf)); imapurl_toURL(buf, &iurl); CU_ASSERT_STRING_EQUAL(buf, URL); } static void test_tourl_server(void) { static const char URL[] = "imap://jeeves"; struct imapurl iurl; char buf[300]; memset(&iurl, 0, sizeof(iurl)); iurl.server = "jeeves"; memset(buf, 0x45, sizeof(buf)); imapurl_toURL(buf, &iurl); CU_ASSERT_STRING_EQUAL(buf, URL); } static void test_tourl_user(void) { static const char URL[] = "imap://wooster@jeeves/deverill"; struct imapurl iurl; char buf[300]; memset(&iurl, 0, sizeof(iurl)); iurl.user = "wooster"; iurl.server = "jeeves"; iurl.mailbox = "deverill"; memset(buf, 0x45, sizeof(buf)); imapurl_toURL(buf, &iurl); CU_ASSERT_STRING_EQUAL(buf, URL); } static void test_tourl_options(void) { static const char URL[] = "imap://jeeves/deverill" ";UIDVALIDITY=7890" "/;UID=123456" "/;SECTION=1.4" "/;PARTIAL=1.1023"; struct imapurl iurl; char buf[300]; memset(&iurl, 0, sizeof(iurl)); iurl.server = "jeeves"; iurl.mailbox = "deverill"; iurl.uidvalidity = 7890; iurl.uid = 123456; iurl.section = "1.4"; iurl.start_octet = 1; iurl.octet_count = 1023; memset(buf, 0x45, sizeof(buf)); imapurl_toURL(buf, &iurl); CU_ASSERT_STRING_EQUAL(buf, URL); } static void test_tourl_urlauth(void) { static const char URL[] = "imap://jeeves/deverill" "/;UID=123456" ";EXPIRE=2010-11-24T06:57:26Z" ";URLAUTH=submit+fred:internal:91354a473744909de610943775f92038"; struct imapurl iurl; char buf[300]; memset(&iurl, 0, sizeof(iurl)); iurl.server = "jeeves"; iurl.mailbox = "deverill"; iurl.uid = 123456; iurl.urlauth.access = "submit+fred"; iurl.urlauth.mech = "internal"; iurl.urlauth.token = "91354a473744909de610943775f92038"; iurl.urlauth.expire = 1290581846; memset(buf, 0x45, sizeof(buf)); imapurl_toURL(buf, &iurl); CU_ASSERT_STRING_EQUAL(buf, URL); } static void test_tourl_ampersand(void) { /* * Test a mailbox name containing an ampersand, which * character is significant to both the modified UTF-7 * encoding of mailbox names and to URL-encoding. */ static const char URL[] = "imap://goons/Goosey%26Bawks"; struct imapurl iurl; char buf[300]; memset(&iurl, 0, sizeof(iurl)); iurl.server = "goons"; iurl.mailbox = "Goosey&-Bawks"; memset(buf, 0x45, sizeof(buf)); imapurl_toURL(buf, &iurl); CU_ASSERT_STRING_EQUAL(buf, URL); } static void test_tourl_urlunsafe(void) { /* * Test a mailbox name containing characters which are * not special to modified UTF-7 but are unsafe in URLs. */ static const char URL[] = "imap://gibberish/%20%22%23%25%2B%3A%3B%3C%3D%3E%3F%40%5B%5C%5D%5E%60%7B%7C%7D"; struct imapurl iurl; char buf[300]; memset(&iurl, 0, sizeof(iurl)); iurl.server = "gibberish"; iurl.mailbox = " \"#%+:;<=>?@[\\]^`{|}"; memset(buf, 0x45, sizeof(buf)); imapurl_toURL(buf, &iurl); CU_ASSERT_STRING_EQUAL(buf, URL); } static void test_tourl_utf7_high(void) { /* * This guy has a mailbox whose name is expressed in * Unicode 5.0 Cuneiform. The name is three glyphs: * * 12073 CUNEIFORM SIGN DIB * 12020 CUNEIFORM SIGN AL * 12129 CUNEIFORM SIGN HA * * Presumably it contains emails discussing some ancestor * of Cut Me Own Throat Dibbler. Anyway, this tests the * UTF-7 -> UTF-16 -> UCS-4 -> UTF-8 -> URL-encoded * path when converting a mailbox name. */ static const char URL[] = "imap://uruk/%F0%92%81%B3%F0%92%80%A0%F0%92%84%A9"; struct imapurl iurl; char buf[300]; memset(&iurl, 0, sizeof(iurl)); iurl.server = "uruk"; iurl.mailbox = "&2Ajcc9gI3CDYCN0p-"; memset(buf, 0x45, sizeof(buf)); imapurl_toURL(buf, &iurl); CU_ASSERT_STRING_EQUAL(buf, URL); } static void test_fromurl_utf2_high(void) { /* Same Cuneiform as above, but test the opposite conversion */ static const char URL[] = "imap://uruk/%F0%92%81%B3%F0%92%80%A0%F0%92%84%A9"; struct imapurl iurl; int r; memset(&iurl, 0x45, sizeof(iurl)); r = imapurl_fromURL(&iurl, URL); CU_ASSERT_EQUAL(r, 0); CU_ASSERT_PTR_NULL(iurl.user); CU_ASSERT_PTR_NULL(iurl.auth); CU_ASSERT_STRING_EQUAL(iurl.server, "uruk"); CU_ASSERT_STRING_EQUAL(iurl.mailbox, "&2Ajcc9gI3CDYCN0p-"); CU_ASSERT_EQUAL(iurl.uidvalidity, 0); CU_ASSERT_EQUAL(iurl.uid, 0); CU_ASSERT_PTR_NULL(iurl.section); CU_ASSERT_EQUAL(iurl.start_octet, 0); CU_ASSERT_EQUAL(iurl.octet_count, 0); CU_ASSERT_PTR_NULL(iurl.urlauth.access); CU_ASSERT_PTR_NULL(iurl.urlauth.mech); CU_ASSERT_PTR_NULL(iurl.urlauth.token); CU_ASSERT_EQUAL(iurl.urlauth.expire, 0); CU_ASSERT_EQUAL(iurl.urlauth.rump_len, 0); free(iurl.freeme); } /* This test was located in lib/test/imapurl.c. */ static void test_cycle(void) { struct imapurl iurl; struct imapurl iurl2; static const char URL[] = "imap://;AUTH=*@server/%C3%A4%20%C3%84;UIDVALIDITY=1234567890"; int r; char url[400]; memset(&iurl, 0, sizeof(struct imapurl)); iurl.server = "server"; iurl.auth = "*"; iurl.mailbox = "&AOQ- &AMQ-"; /* "ä Ä" */ iurl.uidvalidity = 1234567890; memset(url, 0x45, sizeof(url)); imapurl_toURL(url, &iurl); CU_ASSERT_STRING_EQUAL(url, URL); r = imapurl_fromURL(&iurl2, url); CU_ASSERT_EQUAL(r, 0); CU_ASSERT_STRING_EQUAL(iurl2.mailbox, "&AOQ- &AMQ-"); CU_ASSERT_EQUAL(iurl2.uidvalidity, 1234567890); free(iurl2.freeme); } /* vim: set ft=c: */ cyrus-imapd-2.5.10/cunit/squat.testc0000644000175000017500000000574113001236020014272 00000000000000#include "config.h" #include "cunit/cunit.h" #include "imap/squat_internal.h" static void test_coding_int32(void) { SquatInt32 out; char *r; char buf[4]; #define TESTCASE(value) \ { \ SquatInt32 _v = (value); \ memset(buf, 0xa5, sizeof(buf)); \ r = squat_encode_32(buf, _v); \ CU_ASSERT_PTR_EQUAL(r, buf+4); \ out = squat_decode_32(buf); \ CU_ASSERT_EQUAL(out, _v); \ } TESTCASE(0x0); TESTCASE(0x1); TESTCASE(0x100); TESTCASE(0x10000); TESTCASE(0x1000000); TESTCASE(0x80); TESTCASE(0x8000); TESTCASE(0x800000); TESTCASE(0x80000000); TESTCASE(0xff); TESTCASE(0xffff); TESTCASE(0xffffff); TESTCASE(0xffffffff); TESTCASE(0xcafebabe); TESTCASE(0xbdefaced); #undef TESTCASE } static void test_coding_int64(void) { SquatInt64 out; char *r; char buf[8]; #define TESTCASE(value) \ { \ SquatInt64 _v = (value); \ memset(buf, 0xa5, sizeof(buf)); \ r = squat_encode_64(buf, _v); \ CU_ASSERT_PTR_EQUAL(r, buf+8); \ out = squat_decode_64(buf); \ CU_ASSERT_EQUAL(out, _v); \ } TESTCASE(0x0); TESTCASE(0x1); TESTCASE(0x100); TESTCASE(0x10000); TESTCASE(0x1000000); TESTCASE(0x100000000); TESTCASE(0x10000000000); TESTCASE(0x1000000000000); TESTCASE(0x100000000000000); TESTCASE(0x80); TESTCASE(0x8000); TESTCASE(0x800000); TESTCASE(0x80000000); TESTCASE(0x8000000000); TESTCASE(0x800000000000); TESTCASE(0x80000000000000); TESTCASE(0x8000000000000000); TESTCASE(0xff); TESTCASE(0xffff); TESTCASE(0xffffff); TESTCASE(0xffffffff); TESTCASE(0xffffffffff); TESTCASE(0xffffffffffff); TESTCASE(0xffffffffffffff); TESTCASE(0xffffffffffffffff); TESTCASE(0xcafebabebdefaced); #undef TESTCASE } /* test the variable-length int encoding */ static void test_coding_I(void) { SquatInt64 out; int count; const char *s; char *r; char buf[9]; #define TESTCASE(value) \ { \ SquatInt64 _v = (value); \ memset(buf, 0xa5, sizeof(buf)); \ count = squat_count_encode_I(_v); \ CU_ASSERT(count >= 1); \ CU_ASSERT(count <= 9); \ r = squat_encode_I(buf, _v); \ CU_ASSERT_PTR_EQUAL(r, buf+count); \ s = buf; \ out = squat_decode_I(&s); \ CU_ASSERT_EQUAL(out, _v); \ CU_ASSERT_PTR_EQUAL((char *)s, buf+count); \ } TESTCASE(0x0); TESTCASE(0x1); TESTCASE(0x100); TESTCASE(0x10000); TESTCASE(0x1000000); TESTCASE(0x100000000); TESTCASE(0x10000000000); TESTCASE(0x1000000000000); TESTCASE(0x100000000000000); TESTCASE(0x80); TESTCASE(0x8000); TESTCASE(0x800000); TESTCASE(0x80000000); TESTCASE(0x8000000000); TESTCASE(0x800000000000); TESTCASE(0x80000000000000); TESTCASE(0xff); TESTCASE(0xffff); TESTCASE(0xffffff); TESTCASE(0xffffffff); TESTCASE(0xffffffffff); TESTCASE(0xffffffffffff); TESTCASE(0xffffffffffffff); TESTCASE(0x4afebabebdefaced); #undef TESTCASE } /* vim: set ft=c: */ cyrus-imapd-2.5.10/cunit/parseaddr.testc0000644000175000017500000004166713001236020015111 00000000000000#include #include "cunit/cunit.h" #include "parseaddr.h" static void test_single(void) { struct address *a; a = NULL; parseaddr_list("Fred Bloggs ", &a); CU_ASSERT_PTR_NOT_NULL_FATAL(a); CU_ASSERT_STRING_EQUAL(a->name, "Fred Bloggs"); CU_ASSERT_STRING_EQUAL(a->mailbox, "fbloggs"); CU_ASSERT_STRING_EQUAL(a->domain, "fastmail.fm"); CU_ASSERT_PTR_NULL(a->next); parseaddr_free(a); } static void test_noname(void) { struct address *a; a = NULL; parseaddr_list("fbloggs@fastmail.fm", &a); CU_ASSERT_PTR_NOT_NULL_FATAL(a); CU_ASSERT_PTR_NULL(a->name); CU_ASSERT_STRING_EQUAL(a->mailbox, "fbloggs"); CU_ASSERT_STRING_EQUAL(a->domain, "fastmail.fm"); CU_ASSERT_PTR_NULL(a->next); parseaddr_free(a); a = NULL; parseaddr_list("", &a); CU_ASSERT_PTR_NOT_NULL_FATAL(a); CU_ASSERT_PTR_NULL(a->name); CU_ASSERT_STRING_EQUAL(a->mailbox, "fbloggs"); CU_ASSERT_STRING_EQUAL(a->domain, "fastmail.fm"); CU_ASSERT_PTR_NULL(a->next); parseaddr_free(a); a = NULL; parseaddr_list(" ", &a); CU_ASSERT_PTR_NOT_NULL_FATAL(a); CU_ASSERT_PTR_NULL(a->name); CU_ASSERT_STRING_EQUAL(a->mailbox, "fbloggs"); CU_ASSERT_STRING_EQUAL(a->domain, "fastmail.fm"); CU_ASSERT_PTR_NULL(a->next); parseaddr_free(a); } static void test_single_append(void) { struct address *a; struct address *origa; a = NULL; parseaddr_list("Fred Bloggs ", &a); CU_ASSERT_PTR_NOT_NULL_FATAL(a); CU_ASSERT_STRING_EQUAL(a->name, "Fred Bloggs"); CU_ASSERT_STRING_EQUAL(a->mailbox, "fbloggs"); CU_ASSERT_STRING_EQUAL(a->domain, "fastmail.fm"); CU_ASSERT_PTR_NULL(a->next); origa = a; parseaddr_list("Sarah Jane Smith ", &a); CU_ASSERT_PTR_EQUAL_FATAL(a, origa); CU_ASSERT_STRING_EQUAL(a->name, "Fred Bloggs"); CU_ASSERT_STRING_EQUAL(a->mailbox, "fbloggs"); CU_ASSERT_STRING_EQUAL(a->domain, "fastmail.fm"); CU_ASSERT_PTR_NOT_NULL_FATAL(a->next); CU_ASSERT_STRING_EQUAL(a->next->name, "Sarah Jane Smith"); CU_ASSERT_STRING_EQUAL(a->next->mailbox, "sjsmith"); CU_ASSERT_STRING_EQUAL(a->next->domain, "gmail.com"); CU_ASSERT_PTR_NULL(a->next->next); parseaddr_free(a); } static void test_multiple(void) { struct address *a; a = NULL; parseaddr_list("Fred Bloggs , Sarah Jane Smith ", &a); CU_ASSERT_PTR_NOT_NULL_FATAL(a); CU_ASSERT_STRING_EQUAL(a->name, "Fred Bloggs"); CU_ASSERT_STRING_EQUAL(a->mailbox, "fbloggs"); CU_ASSERT_STRING_EQUAL(a->domain, "fastmail.fm"); CU_ASSERT_PTR_NOT_NULL_FATAL(a->next); CU_ASSERT_STRING_EQUAL(a->next->name, "Sarah Jane Smith"); CU_ASSERT_STRING_EQUAL(a->next->mailbox, "sjsmith"); CU_ASSERT_STRING_EQUAL(a->next->domain, "gmail.com"); CU_ASSERT_PTR_NULL(a->next->next); parseaddr_free(a); } static void test_quoted_name(void) { struct address *a; a = NULL; parseaddr_list("\"Fred Bloggs\" ", &a); CU_ASSERT_PTR_NOT_NULL_FATAL(a); CU_ASSERT_STRING_EQUAL(a->name, "Fred Bloggs"); CU_ASSERT_STRING_EQUAL(a->mailbox, "fbloggs"); CU_ASSERT_STRING_EQUAL(a->domain, "fastmail.fm"); CU_ASSERT_PTR_NULL(a->next); parseaddr_free(a); } static void test_quoted_name_comma(void) { struct address *a; a = NULL; parseaddr_list("\"Bloggs, Fred\" ", &a); CU_ASSERT_PTR_NOT_NULL_FATAL(a); CU_ASSERT_STRING_EQUAL(a->name, "Bloggs, Fred"); CU_ASSERT_STRING_EQUAL(a->mailbox, "fbloggs"); CU_ASSERT_STRING_EQUAL(a->domain, "fastmail.fm"); CU_ASSERT_PTR_NULL(a->next); parseaddr_free(a); } static void test_quoted_name_unbalanced(void) { struct address *a; /* If a quoted string is not terminated, we are parsing a header * field with an unbalanced " and should fail. */ a = NULL; parseaddr_list("\"Charles Manson ", &a); CU_ASSERT_PTR_NULL_FATAL(a); } static void test_quoted_name_folded(void) { struct address *a; /* If a quoted string contains an embedded CR+LF+WSP, because we're * parsing a header value directly, the CR+LF should be stripped out * and the WSP and any following WSP* should be preserved (i.e. we * should perform header field unfolding per RFC2822) */ a = NULL; parseaddr_list("\"Akira\r\n \t Yoshizawa\" ", &a); CU_ASSERT_PTR_NOT_NULL_FATAL(a); CU_ASSERT_STRING_EQUAL(a->name, "Akira \t Yoshizawa"); CU_ASSERT_STRING_EQUAL(a->mailbox, "akira"); CU_ASSERT_STRING_EQUAL(a->domain, "origami.jp"); CU_ASSERT_PTR_NULL(a->next); parseaddr_free(a); } static void test_quoted_name_crlf(void) { struct address *a; /* If a quoted string contains an embedded CR+LF *without* trailing * WSP, then we have walked off the end of the header field and thus * we're parsing a header field which has an unbalanced ", and * should fail. */ a = NULL; parseaddr_list("\"Akira\r\nYoshizawa\" ", &a); CU_ASSERT_PTR_NULL_FATAL(a); /* CR+LF+CR+LF is a subcase of that, for the last header field. */ a = NULL; parseaddr_list("\"Akira\r\n\r\nYoshizawa\" ", &a); CU_ASSERT_PTR_NULL_FATAL(a); /* A lone CR is invalid and the parse should fail */ a = NULL; parseaddr_list("\"Akira\rYoshizawa\" ", &a); CU_ASSERT_PTR_NULL_FATAL(a); /* A lone LF is invalid and the parse should fail */ a = NULL; parseaddr_list("\"Akira\nYoshizawa\" ", &a); CU_ASSERT_PTR_NULL_FATAL(a); } static void test_comment_name(void) { struct address *a; a = NULL; parseaddr_list("fbloggs@fastmail.fm (Fred Bloggs)", &a); CU_ASSERT_PTR_NOT_NULL_FATAL(a); CU_ASSERT_STRING_EQUAL(a->name, "Fred Bloggs"); CU_ASSERT_STRING_EQUAL(a->mailbox, "fbloggs"); CU_ASSERT_STRING_EQUAL(a->domain, "fastmail.fm"); CU_ASSERT_PTR_NULL(a->next); parseaddr_free(a); } static void test_quoted_mailbox(void) { struct address *a; a = NULL; parseaddr_list("Fred Bloggs <\"fred bloggs\"@fastmail.fm>", &a); CU_ASSERT_PTR_NOT_NULL_FATAL(a); CU_ASSERT_STRING_EQUAL(a->name, "Fred Bloggs"); CU_ASSERT_STRING_EQUAL(a->mailbox, "fred bloggs"); CU_ASSERT_STRING_EQUAL(a->domain, "fastmail.fm"); CU_ASSERT_PTR_NULL(a->next); parseaddr_free(a); } static void test_mailbox_comment(void) { struct address *a; /* This example is from the RFC822 text */ a = NULL; parseaddr_list("Wilt . (the Stilt) Chamberlain@NBA.US", &a); CU_ASSERT_PTR_NOT_NULL_FATAL(a); CU_ASSERT_PTR_NULL(a->name); // CU_ASSERT_STRING_EQUAL(a->mailbox, "Wilt.Chamberlain"); CU_ASSERT_STRING_EQUAL(a->domain, "NBA.US"); CU_ASSERT_PTR_NULL(a->next); parseaddr_free(a); } static void test_domain_literal(void) { struct address *a; a = NULL; parseaddr_list("Fred Bloggs ", &a); CU_ASSERT_PTR_NOT_NULL_FATAL(a); CU_ASSERT_STRING_EQUAL(a->name, "Fred Bloggs"); CU_ASSERT_STRING_EQUAL(a->mailbox, "fbloggs"); CU_ASSERT_STRING_EQUAL(a->domain, "[192.168.0.1]"); CU_ASSERT_PTR_NULL(a->next); parseaddr_free(a); } static void test_dotted_mailbox(void) { struct address *a; a = NULL; parseaddr_list("Fred Bloggs ", &a); CU_ASSERT_PTR_NOT_NULL_FATAL(a); CU_ASSERT_STRING_EQUAL(a->name, "Fred Bloggs"); CU_ASSERT_STRING_EQUAL(a->mailbox, "Fred.Bloggs"); CU_ASSERT_STRING_EQUAL(a->domain, "fastmail.fm"); CU_ASSERT_PTR_NULL(a->next); parseaddr_free(a); } static void test_long_domain(void) { struct address *a; a = NULL; parseaddr_list("Fred Bloggs ", &a); CU_ASSERT_PTR_NOT_NULL_FATAL(a); CU_ASSERT_STRING_EQUAL(a->name, "Fred Bloggs"); CU_ASSERT_STRING_EQUAL(a->mailbox, "fbloggs"); CU_ASSERT_STRING_EQUAL(a->domain, "a.really.quite.surprisingly.long.domain.name.com"); CU_ASSERT_PTR_NULL(a->next); parseaddr_free(a); } static void test_rfc2047_text(void) { struct address *a; /* RFC2047 MIME-encoded text in an address is passed through * unmolested, to be decoded by upper layers, or not, on demand */ a = NULL; parseaddr_list("=?UTF-8?Q?=F0=92=8C=89=F0=92=8B=9B?= ", &a); CU_ASSERT_PTR_NOT_NULL_FATAL(a); CU_ASSERT_STRING_EQUAL(a->name, "=?UTF-8?Q?=F0=92=8C=89=F0=92=8B=9B?="); CU_ASSERT_STRING_EQUAL(a->mailbox, "Dumusi"); CU_ASSERT_STRING_EQUAL(a->domain, "lagash.sm"); CU_ASSERT_PTR_NULL(a->next); parseaddr_free(a); } static void test_group(void) { struct address *a; a = NULL; parseaddr_list("Buddies: Fred Bloggs , Sarah Jane Smith ;", &a); CU_ASSERT_PTR_NOT_NULL_FATAL(a); CU_ASSERT_PTR_NULL(a->name); CU_ASSERT_STRING_EQUAL(a->mailbox, "Buddies"); CU_ASSERT_PTR_NULL(a->domain); CU_ASSERT_PTR_NOT_NULL_FATAL(a->next); CU_ASSERT_STRING_EQUAL(a->next->name, "Fred Bloggs"); CU_ASSERT_STRING_EQUAL(a->next->mailbox, "fbloggs"); CU_ASSERT_STRING_EQUAL(a->next->domain, "fastmail.fm"); CU_ASSERT_PTR_NOT_NULL_FATAL(a->next->next); CU_ASSERT_STRING_EQUAL(a->next->next->name, "Sarah Jane Smith"); CU_ASSERT_STRING_EQUAL(a->next->next->mailbox, "sjsmith"); CU_ASSERT_STRING_EQUAL(a->next->next->domain, "gmail.com"); CU_ASSERT_PTR_NOT_NULL_FATAL(a->next->next->next); CU_ASSERT_PTR_NULL(a->next->next->next->name); CU_ASSERT_PTR_NULL(a->next->next->next->mailbox); CU_ASSERT_PTR_NULL(a->next->next->next->domain); CU_ASSERT_PTR_NULL(a->next->next->next->next); parseaddr_free(a); } static void test_multi_group(void) { struct address *a; struct address *cur; a = NULL; parseaddr_list("group: g1@d1.org, g2@d2.org;, group2: g3@d3.org;", &a); cur = a; CU_ASSERT_PTR_NOT_NULL_FATAL(cur); CU_ASSERT_PTR_NULL(cur->name); CU_ASSERT_STRING_EQUAL(cur->mailbox, "group"); CU_ASSERT_PTR_NULL(cur->domain); cur = cur->next; CU_ASSERT_PTR_NOT_NULL_FATAL(cur); CU_ASSERT_PTR_NULL(cur->name); CU_ASSERT_STRING_EQUAL(cur->mailbox, "g1"); CU_ASSERT_STRING_EQUAL(cur->domain, "d1.org"); cur = cur->next; CU_ASSERT_PTR_NOT_NULL_FATAL(cur); CU_ASSERT_PTR_NULL(cur->name); CU_ASSERT_STRING_EQUAL(cur->mailbox, "g2"); CU_ASSERT_STRING_EQUAL(cur->domain, "d2.org"); cur = cur->next; CU_ASSERT_PTR_NOT_NULL_FATAL(cur); CU_ASSERT_PTR_NULL(cur->name); CU_ASSERT_PTR_NULL(cur->mailbox); CU_ASSERT_PTR_NULL(cur->domain); cur = cur->next; CU_ASSERT_PTR_NOT_NULL_FATAL(cur); CU_ASSERT_PTR_NULL(cur->name); CU_ASSERT_STRING_EQUAL(cur->mailbox, "group2"); CU_ASSERT_PTR_NULL(cur->domain); cur = cur->next; CU_ASSERT_PTR_NOT_NULL_FATAL(cur); CU_ASSERT_PTR_NULL(cur->name); CU_ASSERT_STRING_EQUAL(cur->mailbox, "g3"); CU_ASSERT_STRING_EQUAL(cur->domain, "d3.org"); cur = cur->next; CU_ASSERT_PTR_NOT_NULL_FATAL(cur); CU_ASSERT_PTR_NULL(cur->name); CU_ASSERT_PTR_NULL(cur->mailbox); CU_ASSERT_PTR_NULL(cur->domain); cur = cur->next; CU_ASSERT_PTR_NULL(cur); parseaddr_free(a); } static void test_multi_group_mixed(void) { struct address *a; struct address *cur; a = NULL; parseaddr_list("Buddies: Fred Bloggs , " "Sarah Jane Smith ;, " "foobar@fastmail.fm, " "group2: Fred Bloggs Junior ;", &a); cur = a; CU_ASSERT_PTR_NOT_NULL_FATAL(cur); CU_ASSERT_PTR_NULL(cur->name); CU_ASSERT_STRING_EQUAL(cur->mailbox, "Buddies"); CU_ASSERT_PTR_NULL(cur->domain); cur = cur->next; CU_ASSERT_PTR_NOT_NULL_FATAL(cur); CU_ASSERT_STRING_EQUAL(cur->name, "Fred Bloggs"); CU_ASSERT_STRING_EQUAL(cur->mailbox, "fbloggs"); CU_ASSERT_STRING_EQUAL(cur->domain, "fastmail.fm"); cur = cur->next; CU_ASSERT_PTR_NOT_NULL_FATAL(cur); CU_ASSERT_STRING_EQUAL(cur->name, "Sarah Jane Smith"); CU_ASSERT_STRING_EQUAL(cur->mailbox, "sjsmith"); CU_ASSERT_STRING_EQUAL(cur->domain, "gmail.com"); cur = cur->next; CU_ASSERT_PTR_NOT_NULL_FATAL(cur); CU_ASSERT_PTR_NULL(cur->name); CU_ASSERT_PTR_NULL(cur->mailbox); CU_ASSERT_PTR_NULL(cur->domain); cur = cur->next; CU_ASSERT_PTR_NOT_NULL_FATAL(cur); CU_ASSERT_PTR_NULL(cur->name); CU_ASSERT_STRING_EQUAL(cur->mailbox, "foobar"); CU_ASSERT_STRING_EQUAL(cur->domain, "fastmail.fm"); cur = cur->next; CU_ASSERT_PTR_NOT_NULL_FATAL(cur); CU_ASSERT_PTR_NULL(cur->name); CU_ASSERT_STRING_EQUAL(cur->mailbox, "group2"); CU_ASSERT_PTR_NULL(cur->domain); cur = cur->next; CU_ASSERT_PTR_NOT_NULL_FATAL(cur); CU_ASSERT_STRING_EQUAL(cur->name, "Fred Bloggs Junior"); CU_ASSERT_STRING_EQUAL(cur->mailbox, "fbloggs_jr"); CU_ASSERT_STRING_EQUAL(cur->domain, "fastmail.fm"); cur = cur->next; CU_ASSERT_PTR_NOT_NULL_FATAL(cur); CU_ASSERT_PTR_NULL(cur->name); CU_ASSERT_PTR_NULL(cur->mailbox); CU_ASSERT_PTR_NULL(cur->domain); cur = cur->next; CU_ASSERT_PTR_NULL(cur); parseaddr_free(a); } /* TODO: test the source routing feature */ /* Test the iterator interface */ static void test_iterator(void) { struct address_itr ai; const struct address *a; address_itr_init(&ai, ""); a = address_itr_next(&ai); CU_ASSERT_PTR_NULL(a); address_itr_fini(&ai); address_itr_init(&ai, "Fred Bloggs , Sarah Jane Smith "); a = address_itr_next(&ai); CU_ASSERT_PTR_NOT_NULL_FATAL(a); CU_ASSERT_STRING_EQUAL(a->name, "Fred Bloggs"); CU_ASSERT_STRING_EQUAL(a->mailbox, "fbloggs"); CU_ASSERT_STRING_EQUAL(a->domain, "fastmail.fm"); a = address_itr_next(&ai); CU_ASSERT_PTR_NOT_NULL_FATAL(a); CU_ASSERT_STRING_EQUAL(a->name, "Sarah Jane Smith"); CU_ASSERT_STRING_EQUAL(a->mailbox, "sjsmith"); CU_ASSERT_STRING_EQUAL(a->domain, "gmail.com"); CU_ASSERT_PTR_NULL(a->next); address_itr_fini(&ai); } static void test_canonicalise(void) { char *addr; addr = address_canonicalise("Fred Bloggs "); CU_ASSERT_STRING_EQUAL(addr, "F.Bloggs@fastmail.fm"); free(addr); } /* * Test getting parts of a fully featured address */ static void test_getparts(void) { struct address *a; char *s; a = NULL; parseaddr_list("Fred Bloggs ", &a); CU_ASSERT_PTR_NOT_NULL_FATAL(a); s = address_get_all(a, 0); CU_ASSERT_STRING_EQUAL(s, "fbloggs+foo@FastMAIL.fm"); free(s); s = address_get_all(a, 1); CU_ASSERT_STRING_EQUAL(s, "fbloggs+foo@fastmail.fm"); free(s); s = address_get_localpart(a); CU_ASSERT_STRING_EQUAL(s, "fbloggs+foo"); free(s); s = address_get_domain(a, 0); CU_ASSERT_STRING_EQUAL(s, "FastMAIL.fm"); free(s); s = address_get_domain(a, 1); CU_ASSERT_STRING_EQUAL(s, "fastmail.fm"); free(s); s = address_get_user(a); CU_ASSERT_STRING_EQUAL(s, "fbloggs"); free(s); s = address_get_detail(a); CU_ASSERT_STRING_EQUAL(s, "foo"); free(s); parseaddr_free(a); } /* * Test getting parts of an address with no detail part */ static void test_getparts_nodetail(void) { struct address *a; char *s; a = NULL; parseaddr_list("Fred Bloggs ", &a); CU_ASSERT_PTR_NOT_NULL_FATAL(a); s = address_get_all(a, 0); CU_ASSERT_STRING_EQUAL(s, "fbloggs@FastMAIL.fm"); free(s); s = address_get_all(a, 1); CU_ASSERT_STRING_EQUAL(s, "fbloggs@fastmail.fm"); free(s); s = address_get_localpart(a); CU_ASSERT_STRING_EQUAL(s, "fbloggs"); free(s); s = address_get_domain(a, 0); CU_ASSERT_STRING_EQUAL(s, "FastMAIL.fm"); free(s); s = address_get_domain(a, 1); CU_ASSERT_STRING_EQUAL(s, "fastmail.fm"); free(s); s = address_get_user(a); CU_ASSERT_STRING_EQUAL(s, "fbloggs"); free(s); s = address_get_detail(a); CU_ASSERT_PTR_NULL(s); parseaddr_free(a); } /* * Test getting parts of an address with no domain part */ static void test_getparts_nodomain(void) { struct address *a; char *s; a = NULL; parseaddr_list("Fred Bloggs ", &a); CU_ASSERT_PTR_NOT_NULL_FATAL(a); s = address_get_all(a, 0); CU_ASSERT_STRING_EQUAL(s, "fbloggs@unspecified-domain"); free(s); s = address_get_all(a, 1); CU_ASSERT_STRING_EQUAL(s, "fbloggs@unspecified-domain"); free(s); s = address_get_localpart(a); CU_ASSERT_STRING_EQUAL(s, "fbloggs"); free(s); s = address_get_domain(a, 0); CU_ASSERT_STRING_EQUAL(s, "unspecified-domain"); free(s); s = address_get_domain(a, 1); CU_ASSERT_STRING_EQUAL(s, "unspecified-domain"); free(s); s = address_get_user(a); CU_ASSERT_STRING_EQUAL(s, "fbloggs"); free(s); s = address_get_detail(a); CU_ASSERT_PTR_NULL(s); parseaddr_free(a); } /* vim: set ft=c: */ cyrus-imapd-2.5.10/cunit/mboxname.testc0000644000175000017500000002774413001236020014752 00000000000000#if HAVE_CONFIG_H #include #endif #include "cunit/cunit.h" #include "libconfig.h" #include "imap/mboxname.h" #include "imap/mailbox.h" #include "imap/global.h" static void test_dir_hash_c(void) { static const char FRED[] = "fred"; static const char FRED_DRAFTS[] = "fred.Drafts"; static const char JANEAT_SENT[] = "bloggs.com!user.jane.Sent"; static const char SHARED[] = "Gossip"; static const char INTERNAL[] = "internal!Tattle"; static const char LONGNAME[] = "thisisareallylongname"; static const char LONGNAME_SUB[] = "thisisareallylongname.with.a.subdir"; char c; c = dir_hash_c(FRED, 0); CU_ASSERT_EQUAL(c, 'f'); c = dir_hash_c(FRED_DRAFTS, 0); CU_ASSERT_EQUAL(c, 'f'); c = dir_hash_c(JANEAT_SENT, 0); CU_ASSERT_EQUAL(c, 'b'); c = dir_hash_c(SHARED, 0); CU_ASSERT_EQUAL(c, 'g'); c = dir_hash_c(INTERNAL, 0); CU_ASSERT_EQUAL(c, 'i'); c = dir_hash_c(LONGNAME, 0); CU_ASSERT_EQUAL(c, 't'); c = dir_hash_c(LONGNAME_SUB, 0); CU_ASSERT_EQUAL(c, 't'); c = dir_hash_c(FRED, 1); CU_ASSERT_EQUAL(c, 'E'); c = dir_hash_c(FRED_DRAFTS, 1); CU_ASSERT_EQUAL(c, 'E'); c = dir_hash_c(JANEAT_SENT, 1); CU_ASSERT_EQUAL(c, 'L'); c = dir_hash_c(SHARED, 1); CU_ASSERT_EQUAL(c, 'K'); c = dir_hash_c(INTERNAL, 1); CU_ASSERT_EQUAL(c, 'I'); c = dir_hash_c(LONGNAME, 1); CU_ASSERT_EQUAL(c, 'J'); c = dir_hash_c(LONGNAME_SUB, 1); CU_ASSERT_EQUAL(c, 'J'); } static void test_to_parts(void) { static const char FRED_DRAFTS[] = "user.fred.Drafts"; static const char JANEAT_SENT[] = "bloggs.com!user.jane.Sent"; static const char SHARED[] = "shared.Gossip"; static const char SHAREDAT[] = "foonly.com!shared.Tattle"; struct mboxname_parts parts; int r; r = mboxname_to_parts(FRED_DRAFTS, &parts); CU_ASSERT_EQUAL(r, 0); CU_ASSERT_PTR_NULL(parts.domain); CU_ASSERT_STRING_EQUAL(parts.userid, "fred"); CU_ASSERT_STRING_EQUAL(parts.box, "Drafts"); mboxname_free_parts(&parts); r = mboxname_to_parts(JANEAT_SENT, &parts); CU_ASSERT_EQUAL(r, 0); CU_ASSERT_STRING_EQUAL(parts.domain, "bloggs.com"); CU_ASSERT_STRING_EQUAL(parts.userid, "jane"); CU_ASSERT_STRING_EQUAL(parts.box, "Sent"); mboxname_free_parts(&parts); r = mboxname_to_parts(SHARED, &parts); CU_ASSERT_EQUAL(r, 0); CU_ASSERT_PTR_NULL(parts.domain); CU_ASSERT_PTR_NULL(parts.userid); CU_ASSERT_STRING_EQUAL(parts.box, "shared.Gossip"); mboxname_free_parts(&parts); r = mboxname_to_parts(SHAREDAT, &parts); CU_ASSERT_EQUAL(r, 0); CU_ASSERT_STRING_EQUAL(parts.domain, "foonly.com"); CU_ASSERT_PTR_NULL(parts.userid); CU_ASSERT_STRING_EQUAL(parts.box, "shared.Tattle"); mboxname_free_parts(&parts); } static void test_to_userid(void) { static const char SAM_DRAFTS[] = "user.sam.Drafts"; static const char BETTYAT_SENT[] = "boop.com!user.betty.Sent"; static const char SHARED[] = "shared.Gossip"; static const char SHAREDAT[] = "foonly.com!shared.Tattle"; const char *r; r = mboxname_to_userid(SAM_DRAFTS); CU_ASSERT_STRING_EQUAL(r, "sam"); r = mboxname_to_userid(BETTYAT_SENT); CU_ASSERT_STRING_EQUAL(r, "betty@boop.com"); r = mboxname_to_userid(SHARED); CU_ASSERT_PTR_NULL(r); r = mboxname_to_userid(SHAREDAT); CU_ASSERT_PTR_NULL(r); } static void test_to_usermbox(void) { char *r; r = mboxname_user_mbox(NULL, NULL); CU_ASSERT_PTR_NULL(r); r = mboxname_user_mbox(NULL, "extra.stuff"); CU_ASSERT_PTR_NULL(r); r = mboxname_user_mbox("sam", NULL); CU_ASSERT_STRING_EQUAL(r, "user.sam"); free(r); r = mboxname_user_mbox("betty@boop.com", NULL); CU_ASSERT_STRING_EQUAL(r, "boop.com!user.betty"); free(r); r = mboxname_user_mbox("sam", "sub"); CU_ASSERT_STRING_EQUAL(r, "user.sam.sub"); free(r); r = mboxname_user_mbox("sam", "sub.deep.stuff"); CU_ASSERT_STRING_EQUAL(r, "user.sam.sub.deep.stuff"); free(r); r = mboxname_user_mbox("betty@boop.com", "sub"); CU_ASSERT_STRING_EQUAL(r, "boop.com!user.betty.sub"); free(r); r = mboxname_user_mbox("betty@boop.com", "sub.deep.stuff"); CU_ASSERT_STRING_EQUAL(r, "boop.com!user.betty.sub.deep.stuff"); free(r); } static void test_same_userid(void) { static const char FRED_DRAFTS[] = "user.fred.Drafts"; static const char FRED_SENT[] = "user.fred.Sent"; static const char JANE_SENT[] = "user.jane.Sent"; CU_ASSERT_EQUAL(mboxname_same_userid(FRED_DRAFTS, FRED_SENT), 1); CU_ASSERT_EQUAL(mboxname_same_userid(JANE_SENT, FRED_SENT), 0); } static void test_same_userid_domain(void) { static const char FREDAT_DRAFTS[] = "bloggs.com!user.fred.Drafts"; static const char FREDAT_SENT[] = "bloggs.com!user.fred.Sent"; static const char JANEAT_SENT[] = "bloggs.com!user.jane.Sent"; static const char JANE_SENT[] = "user.jane.Sent"; CU_ASSERT_EQUAL(mboxname_same_userid(FREDAT_DRAFTS, FREDAT_SENT), 1); CU_ASSERT_EQUAL(mboxname_same_userid(JANEAT_SENT, FREDAT_SENT), 0); CU_ASSERT_EQUAL(mboxname_same_userid(JANE_SENT, FREDAT_SENT), 0); CU_ASSERT_EQUAL(mboxname_same_userid(JANE_SENT, JANEAT_SENT), 0); } static void test_contains(void) { static const char FOO[] = "bloggs.com!user.foo"; static const char FOOBAR[] = "bloggs.com!user.foobar"; static const char FOODRAFT[] = "bloggs.com!user.foo.Drafts"; static const char FOONET[] = "bloggs.net!user.foo"; static const char FOONONE[] = "user.foo"; CU_ASSERT_EQUAL(mboxname_is_prefix(FOO, FOOBAR), 0); CU_ASSERT_EQUAL(mboxname_is_prefix(FOOBAR, FOO), 0); CU_ASSERT_EQUAL(mboxname_is_prefix(FOO, FOODRAFT), 0); CU_ASSERT_EQUAL(mboxname_is_prefix(FOODRAFT, FOO), 1); CU_ASSERT_EQUAL(mboxname_is_prefix(FOOBAR, FOOBAR), 1); CU_ASSERT_EQUAL(mboxname_is_prefix(FOO, FOONET), 0); CU_ASSERT_EQUAL(mboxname_is_prefix(FOONET, FOO), 0); CU_ASSERT_EQUAL(mboxname_is_prefix(FOONONE, FOO), 0); CU_ASSERT_EQUAL(mboxname_is_prefix(FOO, FOONONE), 0); } static void test_parts_same_userid(void) { static const char FRED_DRAFTS[] = "user.fred.Drafts"; static const char FRED_SENT[] = "user.fred.Sent"; static const char JANE_SENT[] = "user.jane.Sent"; struct mboxname_parts parts1, parts2; int r; r = mboxname_to_parts(FRED_DRAFTS, &parts1); CU_ASSERT_EQUAL(r, 0); r = mboxname_to_parts(FRED_SENT, &parts2); CU_ASSERT_EQUAL(r, 0); CU_ASSERT_EQUAL(mboxname_parts_same_userid(&parts1, &parts2), 1); mboxname_free_parts(&parts1); mboxname_free_parts(&parts2); r = mboxname_to_parts(JANE_SENT, &parts1); CU_ASSERT_EQUAL(r, 0); r = mboxname_to_parts(FRED_SENT, &parts2); CU_ASSERT_EQUAL(r, 0); CU_ASSERT_EQUAL(mboxname_parts_same_userid(&parts1, &parts2), 0); mboxname_free_parts(&parts1); mboxname_free_parts(&parts2); } static void test_parts_same_userid_domain(void) { static const char FREDAT_DRAFTS[] = "bloggs.com!user.fred.Drafts"; static const char FREDAT_SENT[] = "bloggs.com!user.fred.Sent"; static const char JANEAT_SENT[] = "bloggs.com!user.jane.Sent"; static const char JANE_SENT[] = "user.jane.Sent"; struct mboxname_parts parts1, parts2; int r; r = mboxname_to_parts(FREDAT_DRAFTS, &parts1); CU_ASSERT_EQUAL(r, 0); r = mboxname_to_parts(FREDAT_SENT, &parts2); CU_ASSERT_EQUAL(r, 0); CU_ASSERT_EQUAL(mboxname_parts_same_userid(&parts1, &parts2), 1); mboxname_free_parts(&parts1); mboxname_free_parts(&parts2); r = mboxname_to_parts(JANEAT_SENT, &parts1); CU_ASSERT_EQUAL(r, 0); r = mboxname_to_parts(FREDAT_SENT, &parts2); CU_ASSERT_EQUAL(r, 0); CU_ASSERT_EQUAL(mboxname_parts_same_userid(&parts1, &parts2), 0); mboxname_free_parts(&parts1); mboxname_free_parts(&parts2); r = mboxname_to_parts(JANE_SENT, &parts1); CU_ASSERT_EQUAL(r, 0); r = mboxname_to_parts(FREDAT_SENT, &parts2); CU_ASSERT_EQUAL(r, 0); CU_ASSERT_EQUAL(mboxname_parts_same_userid(&parts1, &parts2), 0); mboxname_free_parts(&parts1); mboxname_free_parts(&parts2); r = mboxname_to_parts(JANE_SENT, &parts1); CU_ASSERT_EQUAL(r, 0); r = mboxname_to_parts(JANEAT_SENT, &parts2); CU_ASSERT_EQUAL(r, 0); CU_ASSERT_EQUAL(mboxname_parts_same_userid(&parts1, &parts2), 0); mboxname_free_parts(&parts1); mboxname_free_parts(&parts2); } /* This structure encapsulates all the variables which affect * namespace translation in one place */ static struct { const char *userid; int isadmin; int altnamespace; int virtdomains; const char *defdomain; const char *userprefix; const char *sharedprefix; int unixhierarchysep; } conf; static void toexternal_helper(const char *intname, const char *extname_expected) { struct namespace ns; char extname[MAX_MAILBOX_NAME]; int r; config_virtdomains = conf.virtdomains; config_defdomain = conf.defdomain; imapopts[IMAPOPT_UNIXHIERARCHYSEP].val.b = conf.unixhierarchysep; imapopts[IMAPOPT_ALTNAMESPACE].val.b = conf.altnamespace; imapopts[IMAPOPT_USERPREFIX].val.s = conf.userprefix; imapopts[IMAPOPT_SHAREDPREFIX].val.s = conf.sharedprefix; r = mboxname_init_namespace(&ns, conf.isadmin); CU_ASSERT_EQUAL_FATAL(r, 0); memset(extname, 0x45, sizeof(extname)); r = ns.mboxname_toexternal(&ns, intname, conf.userid, extname); CU_ASSERT_EQUAL_FATAL(r, 0); CU_ASSERT_STRING_EQUAL(extname, extname_expected); } static void test_toexternal_simple(void) { memset(&conf, 0, sizeof(conf)); conf.virtdomains = 0; conf.userid = "fred"; toexternal_helper("user.fred", "INBOX"); toexternal_helper("user.fred.foo", "INBOX.foo"); toexternal_helper("user.fred.foo.barracuda", "INBOX.foo.barracuda"); toexternal_helper("user.jane", "user.jane"); toexternal_helper("user.jane.baz", "user.jane.baz"); toexternal_helper("shared.quux", "shared.quux"); } static void test_toexternal_domains(void) { memset(&conf, 0, sizeof(conf)); conf.virtdomains = 1; conf.userid = "fred@bloggs.com"; toexternal_helper("bloggs.com!user.fred", "INBOX"); toexternal_helper("bloggs.com!user.fred.foo", "INBOX.foo"); toexternal_helper("bloggs.com!user.fred.foo.barracuda", "INBOX.foo.barracuda"); toexternal_helper("bloggs.com!user.jane", "user.jane"); toexternal_helper("bloggs.com!user.jane.baz", "user.jane.baz"); toexternal_helper("boop.com!user.betty", "user.betty@boop.com"); toexternal_helper("bloggs.com!shared.quux", "shared.quux"); toexternal_helper("boop.com!shared.quux", "shared.quux@boop.com"); } static void test_toexternal_unixhier(void) { memset(&conf, 0, sizeof(conf)); conf.unixhierarchysep = 1; conf.userid = "fred"; toexternal_helper("user.fred", "INBOX"); toexternal_helper("user.fred.foo", "INBOX/foo"); toexternal_helper("user.fred.foo.barracuda", "INBOX/foo/barracuda"); toexternal_helper("user.jane", "user/jane"); toexternal_helper("user.jane.baz", "user/jane/baz"); toexternal_helper("shared.quux", "shared/quux"); } static void test_toexternal_alt(void) { memset(&conf, 0, sizeof(conf)); conf.altnamespace = 1; conf.userprefix = "Uvvers"; conf.sharedprefix = "Chaired"; conf.userid = "fred"; toexternal_helper("user.fred", "INBOX"); toexternal_helper("user.fred.foo", "foo"); toexternal_helper("user.fred.foo.barracuda", "foo.barracuda"); toexternal_helper("user.jane", "Uvvers.jane"); toexternal_helper("user.jane.baz", "Uvvers.jane.baz"); toexternal_helper("shared.quux", "Chaired.shared.quux"); } static enum enum_value old_config_virtdomains; static int set_up(void) { /* * TODO: this is pretty hacky. There should be some * cleaner way of pushing aside the config for a moment * and temporarily setting up a particular set of config * options for testing. */ old_config_virtdomains = config_virtdomains; config_virtdomains = IMAP_ENUM_VIRTDOMAINS_ON; return 0; } static int tear_down(void) { config_virtdomains = old_config_virtdomains; return 0; } /* vim: set ft=c: */ cyrus-imapd-2.5.10/cunit/hash.testc0000644000175000017500000001622213001236020014054 00000000000000#include "cunit/cunit.h" #include "strarray.h" #include "util.h" #include "hash.h" static void count_cb(const char *key __attribute__((unused)), void *data __attribute__((unused)), void *rock) { unsigned int *countp = (unsigned int *)rock; (*countp)++; } static void printer_cb(const char *key, void *data, void *rock) { strarray_t *sa = (strarray_t *)rock; struct buf buf = BUF_INITIALIZER; buf_printf(&buf, "%s=%s", key, (char *)data); strarray_appendm(sa, buf_release(&buf)); } #define KEY0 "Yale" #define KEY1 "Lockwood" #define KEY2 "Skeleton" static const char * const values[] = { "Paper", "Glass", "Wood", "Diamond" }; #define VALUE0 ((void *)values[0]) #define VALUE1 ((void *)values[1]) #define VALUE2 ((void *)values[2]) #define VALUE3 ((void *)values[3]) static void test_old(void) { /* this is the old test code in lib/hash.c converted to CUnit */ hash_table table; static const char * const strings[] = { "1","2","3","4","5","A decently long string", NULL }; static const char * const junk[] = { "The first data", "The second data", "The third data", "The fourth data", "The fifth datum", "The sixth piece of data" }; int i; void *j; strarray_t sa = STRARRAY_INITIALIZER; construct_hash_table(&table, 200, 1); for (i = 0 ; NULL != strings[i] ; i++ ) { j = hash_insert(strings[i], (void *)junk[i], &table); CU_ASSERT_PTR_EQUAL((void *)junk[i], j); } for (i = 0 ; NULL != strings[i] ; i++) { j = hash_lookup(strings[i], &table); CU_ASSERT_PTR_NOT_NULL(j); CU_ASSERT_PTR_EQUAL((void *)junk[i], j); } for (i = 0 ; NULL != strings[i] ; i++) { strarray_truncate(&sa, 0); hash_enumerate(&table, printer_cb, &sa); CU_ASSERT_EQUAL(6-i, sa.count); if (i < 1) CU_ASSERT(strarray_find(&sa, "1=The first data", 0) >= 0); if (i < 2) CU_ASSERT(strarray_find(&sa, "2=The second data", 0) >= 0); if (i < 3) CU_ASSERT(strarray_find(&sa, "3=The third data", 0) >= 0); if (i < 4) CU_ASSERT(strarray_find(&sa, "4=The fourth data", 0) >= 0); if (i < 5) CU_ASSERT(strarray_find(&sa, "5=The fifth datum", 0) >= 0); if (i < 6) CU_ASSERT(strarray_find(&sa, "A decently long string=The sixth piece of data", 0) >= 0); strarray_fini(&sa); j = hash_del((char *)strings[i], &table); CU_ASSERT_PTR_EQUAL((void *)junk[i], j); } for (i = 0 ; NULL != strings[i] ; i++) { j = hash_lookup(strings[i], &table); CU_ASSERT_PTR_NULL(j); } free_hash_table(&table, NULL); } static void test_empty(void) { hash_table ht; hash_table *h; void *d; unsigned int count; /* construct an empty hash table */ h = construct_hash_table(&ht, 1024, 0); CU_ASSERT_PTR_EQUAL(&ht, h); /* lookup the empty hash table */ d = hash_lookup(KEY0, &ht); CU_ASSERT_PTR_NULL(d); /* delete from the empty hash table */ d = hash_del(KEY0, &ht); CU_ASSERT_PTR_NULL(d); /* enumerate the empty hash table */ count = 0; hash_enumerate(&ht, count_cb, &count); CU_ASSERT_EQUAL(0, count); /* free the hash table */ free_hash_table(&ht, NULL); } static void test_reinsert(void) { hash_table ht; hash_table *h; void *d; unsigned int count; /* construct an empty hash table */ h = construct_hash_table(&ht, 1024, 0); CU_ASSERT_PTR_EQUAL(&ht, h); /* insert into the table */ d = hash_insert(KEY0, VALUE0, &ht); /* no old data so hash_insert() returns the new data pointer */ CU_ASSERT_PTR_EQUAL(VALUE0, d); /* lookup the hash table */ d = hash_lookup(KEY0, &ht); CU_ASSERT_PTR_EQUAL(VALUE0, d); /* enumerate the hash table */ count = 0; hash_enumerate(&ht, count_cb, &count); CU_ASSERT_EQUAL(1, count); /* re-insert into the hash table */ d = hash_insert(KEY0, VALUE1, &ht); /* get the old value back */ CU_ASSERT_PTR_EQUAL(VALUE0, d); /* lookup the hash table */ d = hash_lookup(KEY0, &ht); CU_ASSERT_PTR_EQUAL(VALUE1, d); /* enumerate the hash table */ count = 0; hash_enumerate(&ht, count_cb, &count); CU_ASSERT_EQUAL(1, count); /* delete from the hash table */ d = hash_del(KEY0, &ht); CU_ASSERT_PTR_EQUAL(VALUE1, d); /* lookup the hash table */ d = hash_lookup(KEY0, &ht); CU_ASSERT_PTR_NULL(d); /* enumerate the hash table */ count = 0; hash_enumerate(&ht, count_cb, &count); CU_ASSERT_EQUAL(0, count); /* free the hash table */ free_hash_table(&ht, NULL); } static const char *key(unsigned int i) { static char buf[32]; snprintf(buf, sizeof(buf), "%u", i); return buf; } static void *value(unsigned int i) { return (void *)(unsigned long)(0xdead0000 + i); } static unsigned int freed_count = 0; static void lincoln(void *x __attribute__((unused))) { ++freed_count; } /* test overloading a hash table with more * entries than the configured number of buckets */ static void test_many(void) { hash_table ht; hash_table *h; void *d; unsigned int count; #define N 2048 unsigned int i; /* construct an empty hash table */ h = construct_hash_table(&ht, N/8, 0); CU_ASSERT_PTR_EQUAL(&ht, h); /* insert lots of entries into the table */ for (i = 0 ; i < N ; i++) { d = hash_insert(key(i), value(i), &ht); CU_ASSERT_PTR_EQUAL(value(i), d); } /* lookup all the entries in the hash table */ for (i = 0 ; i < N ; i++) { d = hash_lookup(key(i), &ht); CU_ASSERT_PTR_EQUAL(value(i), d); } /* lookup and delete entries that aren't there */ for (i = N ; i < 2*N ; i++) { d = hash_lookup(key(i), &ht); CU_ASSERT_PTR_NULL(d); d = hash_del(key(i), &ht); CU_ASSERT_PTR_NULL(d); } d = hash_del("Not here please stop looking", &ht); CU_ASSERT_PTR_NULL(d); d = hash_lookup("Not here please stop looking", &ht); CU_ASSERT_PTR_NULL(d); /* enumerate the hash table */ count = 0; hash_enumerate(&ht, count_cb, &count); CU_ASSERT_EQUAL(N, count); /* delete from the hash table */ for (i = 0 ; i < N ; i++) { d = hash_del(key(i), &ht); CU_ASSERT_PTR_EQUAL(value(i), d); } /* all the entries should be gone */ for (i = 0 ; i < N ; i++) { d = hash_lookup(key(i), &ht); CU_ASSERT_PTR_NULL(d); } /* enumerate the hash table: should be empty now */ count = 0; hash_enumerate(&ht, count_cb, &count); CU_ASSERT_EQUAL(0, count); /* free the hash table */ freed_count = 0; free_hash_table(&ht, lincoln); CU_ASSERT_EQUAL(0, freed_count); } static void test_freeing_nonempty(void) { hash_table ht; hash_table *h; void *d; unsigned int count; #define N 2048 unsigned int i; /* construct an empty hash table */ h = construct_hash_table(&ht, N/8, 0); CU_ASSERT_PTR_EQUAL(&ht, h); /* insert lots of entries into the table */ for (i = 0 ; i < N ; i++) { d = hash_insert(key(i), value(i), &ht); CU_ASSERT_PTR_EQUAL(value(i), d); } /* enumerate the hash table */ count = 0; hash_enumerate(&ht, count_cb, &count); CU_ASSERT_EQUAL(N, count); /* free the hash table */ freed_count = 0; free_hash_table(&ht, lincoln); CU_ASSERT_EQUAL(N, freed_count); } /* vim: set ft=c: */ cyrus-imapd-2.5.10/cunit/cacert.pem0000644000175000017500000000704613001236020014035 00000000000000Certificate: Data: Version: 3 (0x2) Serial Number: dc:ff:1e:12:b0:0b:b6:a0 Signature Algorithm: sha1WithRSAEncryption Issuer: C=AU, ST=Victoria, O=Cyrus IMAP Testers, Inc., OU=SSL Wrangling, CN=Greg Banks/emailAddress=gnb@fastmail.fm Validity Not Before: Feb 1 06:35:58 2011 GMT Not After : Jan 31 06:35:58 2014 GMT Subject: C=AU, ST=Victoria, O=Cyrus IMAP Testers, Inc., OU=SSL Wrangling, CN=Greg Banks/emailAddress=gnb@fastmail.fm Subject Public Key Info: Public Key Algorithm: rsaEncryption RSA Public Key: (1024 bit) Modulus (1024 bit): 00:da:e4:ec:8f:ef:07:6d:58:b3:13:3e:d0:25:30: 07:11:35:88:df:70:5c:f5:0d:10:5c:a6:96:4b:e4: 9c:f3:df:3f:8f:54:fa:00:1b:a2:b9:e8:5f:17:19: ee:a8:9a:5d:40:59:6b:d3:90:1b:6f:6c:3b:27:0c: be:e0:32:1a:a6:31:bc:57:e5:20:86:c8:c2:2f:b1: 7c:a0:fe:a9:d7:57:7e:6c:3e:ee:92:b7:f7:7a:fe: 20:e1:4e:46:91:0a:4a:c2:5b:23:1c:f2:03:0a:8d: cc:c9:e4:9b:d8:02:fb:97:6e:38:ee:ce:8d:1f:6b: d6:45:70:f8:b9:3b:6e:d3:a7 Exponent: 65537 (0x10001) X509v3 extensions: X509v3 Subject Key Identifier: D3:8D:00:56:9B:71:99:CE:00:44:F4:86:98:AE:A9:78:AB:20:17:8A X509v3 Authority Key Identifier: keyid:D3:8D:00:56:9B:71:99:CE:00:44:F4:86:98:AE:A9:78:AB:20:17:8A DirName:/C=AU/ST=Victoria/O=Cyrus IMAP Testers, Inc./OU=SSL Wrangling/CN=Greg Banks/emailAddress=gnb@fastmail.fm serial:DC:FF:1E:12:B0:0B:B6:A0 X509v3 Basic Constraints: CA:TRUE Signature Algorithm: sha1WithRSAEncryption 6f:ec:eb:37:40:53:b0:af:c7:db:28:64:6f:5d:49:80:7d:2f: 98:59:3b:18:c4:f9:19:57:5d:04:80:97:0e:9e:dc:d5:fe:da: 93:d9:55:38:ec:33:f7:e2:e2:c0:ba:9c:13:4d:15:1b:52:40: af:93:1b:6c:97:74:7a:cc:1d:8d:31:ec:cd:b0:ba:31:5e:18: 44:45:7a:80:3d:e4:6d:18:dc:87:95:f9:2b:8e:3c:1f:64:04: b1:8e:10:fb:6b:db:60:ed:62:75:d5:08:ab:55:03:ff:a5:7c: 33:0a:66:07:35:37:b2:49:93:e7:8a:80:c7:0d:e9:c0:fe:9b: 80:2a -----BEGIN CERTIFICATE----- MIIDmTCCAwKgAwIBAgIJANz/HhKwC7agMA0GCSqGSIb3DQEBBQUAMIGQMQswCQYD VQQGEwJBVTERMA8GA1UECBMIVmljdG9yaWExITAfBgNVBAoTGEN5cnVzIElNQVAg VGVzdGVycywgSW5jLjEWMBQGA1UECxMNU1NMIFdyYW5nbGluZzETMBEGA1UEAxMK R3JlZyBCYW5rczEeMBwGCSqGSIb3DQEJARYPZ25iQGZhc3RtYWlsLmZtMB4XDTEx MDIwMTA2MzU1OFoXDTE0MDEzMTA2MzU1OFowgZAxCzAJBgNVBAYTAkFVMREwDwYD VQQIEwhWaWN0b3JpYTEhMB8GA1UEChMYQ3lydXMgSU1BUCBUZXN0ZXJzLCBJbmMu MRYwFAYDVQQLEw1TU0wgV3JhbmdsaW5nMRMwEQYDVQQDEwpHcmVnIEJhbmtzMR4w HAYJKoZIhvcNAQkBFg9nbmJAZmFzdG1haWwuZm0wgZ8wDQYJKoZIhvcNAQEBBQAD gY0AMIGJAoGBANrk7I/vB21YsxM+0CUwBxE1iN9wXPUNEFymlkvknPPfP49U+gAb ornoXxcZ7qiaXUBZa9OQG29sOycMvuAyGqYxvFflIIbIwi+xfKD+qddXfmw+7pK3 93r+IOFORpEKSsJbIxzyAwqNzMnkm9gC+5duOO7OjR9r1kVw+Lk7btOnAgMBAAGj gfgwgfUwHQYDVR0OBBYEFNONAFabcZnOAET0hpiuqXirIBeKMIHFBgNVHSMEgb0w gbqAFNONAFabcZnOAET0hpiuqXirIBeKoYGWpIGTMIGQMQswCQYDVQQGEwJBVTER MA8GA1UECBMIVmljdG9yaWExITAfBgNVBAoTGEN5cnVzIElNQVAgVGVzdGVycywg SW5jLjEWMBQGA1UECxMNU1NMIFdyYW5nbGluZzETMBEGA1UEAxMKR3JlZyBCYW5r czEeMBwGCSqGSIb3DQEJARYPZ25iQGZhc3RtYWlsLmZtggkA3P8eErALtqAwDAYD VR0TBAUwAwEB/zANBgkqhkiG9w0BAQUFAAOBgQBv7Os3QFOwr8fbKGRvXUmAfS+Y WTsYxPkZV10EgJcOntzV/tqT2VU47DP34uLAupwTTRUbUkCvkxtsl3R6zB2NMezN sLoxXhhERXqAPeRtGNyHlfkrjjwfZASxjhD7a9tg7WJ11QirVQP/pXwzCmYHNTey SZPnioDHDenA/puAKg== -----END CERTIFICATE----- cyrus-imapd-2.5.10/cunit/dlist.testc0000644000175000017500000002143113001236020014246 00000000000000#include "config.h" #include "cunit/cunit.h" #include "prot.h" #include "imap/dlist.h" #include "util.h" /* XXX - need LOTS of dlist tests */ static void test_nil(void) { struct buf b = BUF_INITIALIZER; struct dlist *dl = dlist_newlist(NULL, NULL); struct dlist *item; int r; dlist_setatom(dl, "STRING", "NIL"); dlist_setatom(dl, "EMPTY", NULL); dlist_printbuf(dl, 0, &b); CU_ASSERT_STRING_EQUAL(buf_cstring(&b), "(\"NIL\" NIL)"); dlist_free(&dl); r = dlist_parsemap(&dl, 0, b.s, b.len); CU_ASSERT_EQUAL(r, 0); CU_ASSERT_PTR_NOT_NULL(dl); item = dlist_getchildn(dl, 0); CU_ASSERT_PTR_NOT_NULL(item); CU_ASSERT_EQUAL(item->type, DL_ATOM); CU_ASSERT_STRING_EQUAL(item->sval, "NIL"); item = dlist_getchildn(dl, 1); CU_ASSERT_PTR_NOT_NULL(item); CU_ASSERT_EQUAL(item->type, DL_NIL); CU_ASSERT_PTR_NULL(item->sval); dlist_free(&dl); buf_free(&b); } static void test_splice_middle(void) { struct dlist *dl = dlist_newlist(NULL, "NAME"); struct dlist *dl2 = NULL; struct buf b = BUF_INITIALIZER; struct buf b2 = BUF_INITIALIZER; int i; for (i = 1; i <= 10; i++) { dlist_setnum32(dl, "NUM", i); } dl2 = dlist_splice(dl, 5); dlist_printbuf(dl, 0, &b); dlist_printbuf(dl2, 0, &b2); CU_ASSERT_STRING_EQUAL(dl->name, "NAME"); CU_ASSERT_STRING_EQUAL(dl2->name, "NAME"); CU_ASSERT_STRING_EQUAL(buf_cstring(&b), "(6 7 8 9 10)"); CU_ASSERT_STRING_EQUAL(buf_cstring(&b2), "(1 2 3 4 5)"); dlist_free(&dl); dlist_free(&dl2); buf_free(&b); buf_free(&b2); } static void test_splice_none(void) { struct dlist *dl = dlist_newlist(NULL, "NAME"); struct dlist *dl2 = NULL; struct buf b = BUF_INITIALIZER; struct buf b2 = BUF_INITIALIZER; int i; for (i = 1; i <= 10; i++) { dlist_setnum32(dl, "NUM", i); } dl2 = dlist_splice(dl, 0); dlist_printbuf(dl, 0, &b); dlist_printbuf(dl2, 0, &b2); CU_ASSERT_STRING_EQUAL(dl->name, "NAME"); CU_ASSERT_STRING_EQUAL(dl2->name, "NAME"); CU_ASSERT_STRING_EQUAL(buf_cstring(&b), "(1 2 3 4 5 6 7 8 9 10)"); CU_ASSERT_STRING_EQUAL(buf_cstring(&b2), "()"); dlist_free(&dl); dlist_free(&dl2); buf_free(&b); buf_free(&b2); } static void test_splice_one(void) { struct dlist *dl = dlist_newlist(NULL, "NAME"); struct dlist *dl2 = NULL; struct buf b = BUF_INITIALIZER; struct buf b2 = BUF_INITIALIZER; int i; for (i = 1; i <= 10; i++) { dlist_setnum32(dl, "NUM", i); } dl2 = dlist_splice(dl, 1); dlist_printbuf(dl, 0, &b); dlist_printbuf(dl2, 0, &b2); CU_ASSERT_STRING_EQUAL(dl->name, "NAME"); CU_ASSERT_STRING_EQUAL(dl2->name, "NAME"); CU_ASSERT_STRING_EQUAL(buf_cstring(&b), "(2 3 4 5 6 7 8 9 10)"); CU_ASSERT_STRING_EQUAL(buf_cstring(&b2), "(1)"); dlist_free(&dl); dlist_free(&dl2); buf_free(&b); buf_free(&b2); } static void test_splice_allbut(void) { struct dlist *dl = dlist_newlist(NULL, "NAME"); struct dlist *dl2 = NULL; struct buf b = BUF_INITIALIZER; struct buf b2 = BUF_INITIALIZER; int i; for (i = 1; i <= 10; i++) { dlist_setnum32(dl, "NUM", i); } dl2 = dlist_splice(dl, 9); dlist_printbuf(dl, 0, &b); dlist_printbuf(dl2, 0, &b2); CU_ASSERT_STRING_EQUAL(dl->name, "NAME"); CU_ASSERT_STRING_EQUAL(dl2->name, "NAME"); CU_ASSERT_STRING_EQUAL(buf_cstring(&b), "(10)"); CU_ASSERT_STRING_EQUAL(buf_cstring(&b2), "(1 2 3 4 5 6 7 8 9)"); dlist_free(&dl); dlist_free(&dl2); buf_free(&b); buf_free(&b2); } static void test_splice_all(void) { struct dlist *dl = dlist_newlist(NULL, "NAME"); struct dlist *dl2 = NULL; struct buf b = BUF_INITIALIZER; struct buf b2 = BUF_INITIALIZER; int i; for (i = 1; i <= 10; i++) { dlist_setnum32(dl, "NUM", i); } dl2 = dlist_splice(dl, 10); dlist_printbuf(dl, 0, &b); dlist_printbuf(dl2, 0, &b2); CU_ASSERT_STRING_EQUAL(dl->name, "NAME"); CU_ASSERT_STRING_EQUAL(dl2->name, "NAME"); CU_ASSERT_STRING_EQUAL(buf_cstring(&b), "()"); CU_ASSERT_STRING_EQUAL(buf_cstring(&b2), "(1 2 3 4 5 6 7 8 9 10)"); dlist_free(&dl); dlist_free(&dl2); buf_free(&b); buf_free(&b2); } static void test_splice_over(void) { struct dlist *dl = dlist_newlist(NULL, "NAME"); struct dlist *dl2 = NULL; struct buf b = BUF_INITIALIZER; struct buf b2 = BUF_INITIALIZER; int i; for (i = 1; i <= 10; i++) { dlist_setnum32(dl, "NUM", i); } dl2 = dlist_splice(dl, 11); dlist_printbuf(dl, 0, &b); dlist_printbuf(dl2, 0, &b2); CU_ASSERT_STRING_EQUAL(dl->name, "NAME"); CU_ASSERT_STRING_EQUAL(dl2->name, "NAME"); CU_ASSERT_STRING_EQUAL(buf_cstring(&b), "()"); CU_ASSERT_STRING_EQUAL(buf_cstring(&b2), "(1 2 3 4 5 6 7 8 9 10)"); dlist_free(&dl); dlist_free(&dl2); buf_free(&b); buf_free(&b2); } static void test_splat_start(void) { struct dlist *dl = NULL; struct dlist *sub = NULL; struct buf b = BUF_INITIALIZER; struct buf b2 = BUF_INITIALIZER; int r; buf_printf(&b, "((a b) (c d) (e f))"); r = dlist_parsemap(&dl, 0, b.s, b.len); CU_ASSERT_EQUAL(r, 0); CU_ASSERT_PTR_NOT_NULL(dl); sub = dlist_getchildn(dl, 0); dlist_splat(dl, sub); dlist_printbuf(dl, 0, &b2); CU_ASSERT_STRING_EQUAL(buf_cstring(&b2), "(a b (c d) (e f))"); dlist_free(&dl); buf_free(&b); buf_free(&b2); } static void test_splat_middle(void) { struct dlist *dl = NULL; struct dlist *sub = NULL; struct buf b = BUF_INITIALIZER; struct buf b2 = BUF_INITIALIZER; int r; buf_printf(&b, "((a b) (c d) (e f))"); r = dlist_parsemap(&dl, 0, b.s, b.len); CU_ASSERT_EQUAL(r, 0); CU_ASSERT_PTR_NOT_NULL(dl); sub = dlist_getchildn(dl, 1); dlist_splat(dl, sub); dlist_printbuf(dl, 0, &b2); CU_ASSERT_STRING_EQUAL(buf_cstring(&b2), "((a b) c d (e f))"); dlist_free(&dl); buf_free(&b); buf_free(&b2); } static void test_splat_end(void) { struct dlist *dl = NULL; struct dlist *sub = NULL; struct buf b = BUF_INITIALIZER; struct buf b2 = BUF_INITIALIZER; int r; buf_printf(&b, "((a b) (c d) (e f))"); r = dlist_parsemap(&dl, 0, b.s, b.len); CU_ASSERT_EQUAL(r, 0); CU_ASSERT_PTR_NOT_NULL(dl); sub = dlist_getchildn(dl, 2); dlist_splat(dl, sub); dlist_printbuf(dl, 0, &b2); CU_ASSERT_STRING_EQUAL(buf_cstring(&b2), "((a b) (c d) e f)"); dlist_free(&dl); buf_free(&b); buf_free(&b2); } static void test_splat_short(void) { struct dlist *dl = NULL; struct dlist *sub = NULL; struct buf b = BUF_INITIALIZER; struct buf b2 = BUF_INITIALIZER; int r; buf_printf(&b, "((a b) (c) (d e))"); r = dlist_parsemap(&dl, 0, b.s, b.len); CU_ASSERT_EQUAL(r, 0); CU_ASSERT_PTR_NOT_NULL(dl); sub = dlist_getchildn(dl, 1); dlist_splat(dl, sub); dlist_printbuf(dl, 0, &b2); CU_ASSERT_STRING_EQUAL(buf_cstring(&b2), "((a b) c (d e))"); dlist_free(&dl); buf_free(&b); buf_free(&b2); } static void test_splat_empty(void) { struct dlist *dl = NULL; struct dlist *sub = NULL; struct buf b = BUF_INITIALIZER; struct buf b2 = BUF_INITIALIZER; int r; buf_printf(&b, "((a b) () (c d))"); r = dlist_parsemap(&dl, 0, b.s, b.len); CU_ASSERT_EQUAL(r, 0); CU_ASSERT_PTR_NOT_NULL(dl); sub = dlist_getchildn(dl, 1); dlist_splat(dl, sub); dlist_printbuf(dl, 0, &b2); CU_ASSERT_STRING_EQUAL(buf_cstring(&b2), "((a b) (c d))"); dlist_free(&dl); buf_free(&b); buf_free(&b2); } static void test_splat_nonlist(void) { struct dlist *dl = NULL; struct dlist *sub = NULL; struct buf b = BUF_INITIALIZER; struct buf b2 = BUF_INITIALIZER; int r; buf_printf(&b, "(a b c d e)"); r = dlist_parsemap(&dl, 0, b.s, b.len); CU_ASSERT_EQUAL(r, 0); CU_ASSERT_PTR_NOT_NULL(dl); sub = dlist_getchildn(dl, 2); dlist_splat(dl, sub); dlist_printbuf(dl, 0, &b2); CU_ASSERT_STRING_EQUAL(buf_cstring(&b2), "(a b d e)"); dlist_free(&dl); buf_free(&b); buf_free(&b2); } static void test_deepstructure(void) { struct dlist *dl = NULL; struct dlist *di = NULL; struct buf b = BUF_INITIALIZER; struct buf b2 = BUF_INITIALIZER; int r; buf_setcstr(&b, "%(toplevel %(sub thing) ANOTHER (value is %(list with interesting things) (in it)) ExTrA ExTrA READ \"all about it\" INCLUDING 123456)"); r = dlist_parsemap(&dl, 0, b.s, b.len); CU_ASSERT_EQUAL(r, 0); CU_ASSERT_PTR_NOT_NULL(dl); di = dlist_getchild(dl, "INCLUDING"); CU_ASSERT_EQUAL(dlist_num(di), 123456); dlist_printbuf(dl, 0, &b2); CU_ASSERT_STRING_EQUAL(buf_cstring(&b2), buf_cstring(&b)); dlist_free(&dl); buf_free(&b); buf_free(&b2); } /* vim: set ft=c: */ cyrus-imapd-2.5.10/cunit/byteorder64.testc0000644000175000017500000000136512772415051015325 00000000000000#include "cunit/cunit.h" #include "byteorder64.h" union align64 { uint64_t i64; char buf[8]; }; static void test_byteorder(void) { union align64 source; union align64 result; source.buf[0] = 0; source.buf[1] = 0; source.buf[2] = 0; source.buf[3] = 0; source.buf[4] = 0; source.buf[5] = 0; source.buf[6] = 0; source.buf[7] = 1; /* test 64 bit */ CU_ASSERT_EQUAL(ntohll(*((uint64_t *)(source.buf))), 1); *((uint64_t *)result.buf) = htonll(1); CU_ASSERT_EQUAL(memcmp(result.buf, source.buf, 8), 0); /* test 32 bit */ CU_ASSERT_EQUAL(ntohl(*((uint32_t *)(source.buf+4))), 1); *((uint32_t *)(result.buf)) = htonl(1); CU_ASSERT_EQUAL(memcmp(result.buf, source.buf+4, 4), 0); } cyrus-imapd-2.5.10/cunit/syslog.c0000644000175000017500000001671713001236020013562 00000000000000/* * Copyright (c) 1994-2011 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include #include #include #include #include #include #include #include #include #include "cunit-syslog.h" extern int verbose; struct slmatch { const char *re; /* NULL => disabled */ unsigned int count; regex_t cre; /* compiled regex */ }; #define MAX_SLMATCH 32 static unsigned int nslmatches = 0; static struct slmatch slmatches[MAX_SLMATCH]; #if !defined(va_copy) # if defined(__va_copy) # define va_copy __va_copy # else # define va_copy(d,s) (d) = (s) # endif #endif static char *match_error(struct slmatch *sl, int r) { static char buf[2048]; int n; buf[0] = '\0'; if (sl->re) snprintf(buf, sizeof(buf)-100, "/%s/: ", sl->re); n = strlen(buf); regerror(r, &sl->cre, buf+n, sizeof(buf)-n-1); strcat(buf, "\n"); return buf; } static void vlog(int prio, const char *fmt, va_list args) { if (nslmatches) { int e = errno; /* save errno Just In Case */ va_list args2; unsigned int i; int r; char line[2048]; /* This only works for all cases because of the glibc * extension which supports %m in printf() */ va_copy(args2, args); vsnprintf(line, sizeof(line), fmt, args2); va_end(args2); for (i = 0 ; i < MAX_SLMATCH ; i++) { if (!slmatches[i].re) continue; /* empty slot */ r = regexec(&slmatches[i].cre, line, 0, NULL, 0); if (!r) { /* found */ if (verbose >= 2) fprintf(stderr, "\nSYSLOG matched /%s/\n", slmatches[i].re); slmatches[i].count++; break; } else { fprintf(stderr, "\nSYSLOG didn't match '%s' against '%s'\n", line, slmatches[i].re); } if (r != REG_NOMATCH) { /* error */ const char *msg = match_error(&slmatches[i], r); CU_assertImplementation(0, __LINE__, msg, __FILE__, NULL, CU_TRUE); /* NOTREACHED */ break; } } errno = e; } /* glibc handles %m in vfprintf() so we don't need to do * anything special to simulate that feature of syslog() */ /* TODO: find and expand %m on non-glibc platforms */ if (verbose < 2) return; fprintf(stderr, "\nSYSLOG %d[", prio & LOG_PRIMASK); vfprintf(stderr, fmt, args); fprintf(stderr, "]\n"); fflush(stderr); } #if defined(__GLIBC__) /* Under some but not all combinations of options, glibc * defines syslog() as an inline that calls this function */ void __syslog_chk(int prio, int whatever __attribute__((unused)), const char *fmt, ...) { va_list args; va_start(args, fmt); vlog(prio, fmt, args); va_end(args); } #endif void syslog(int prio, const char *fmt, ...) { va_list args; va_start(args, fmt); vlog(prio, fmt, args); va_end(args); } unsigned int CU_syslogMatchBegin(const char *re, const char *filename, unsigned int lineno) { unsigned int i; int r; /* find an empty slot */ for (i = 0 ; i < MAX_SLMATCH ; i++) { if (!slmatches[i].re) { /* found */ slmatches[i].re = re; slmatches[i].count = 0; r = regcomp(&slmatches[i].cre, re, REG_EXTENDED|REG_ICASE|REG_NOSUB); if (r) { const char *msg = match_error(&slmatches[i], r); memset(&slmatches[i], 0, sizeof(slmatches[i])); CU_assertImplementation(0, lineno, msg, filename, NULL, CU_TRUE); /* NOTREACHED */ return 0; } nslmatches++; return i+1; } } CU_assertImplementation(0, lineno, "No free syslog match slots", filename, NULL, CU_TRUE); /* NOTREACHED */ return 0; } unsigned int CU_syslogMatchEnd(unsigned int match, const char **sp) { unsigned int i; unsigned int count = 0; const char *s = NULL; for (i = 0 ; i < MAX_SLMATCH ; i++) { if (!slmatches[i].re) continue; /* empty slot */ if (match && match != i+1) continue; /* not the slot for @match */ if (!s) s = slmatches[i].re; else s = "(multiple matches)"; count += slmatches[i].count; regfree(&slmatches[i].cre); memset(&slmatches[i], 0, sizeof(slmatches[i])); nslmatches--; if (match) break; /* only looking for a single slot */ } if (match && !s) { s = "invalid match number"; count = ~0U; } if (sp) *sp = s; return count; } /* Meta-test code for CU_*SYSLOG* macros. */ #if 0 static void test_syslog(void) { int m1, m2; // /* invalid regular expression, 1st macro fails */ // CU_SYSLOG_MATCH("[foo"); // syslog(LOG_ERR, "fnarp"); // CU_ASSERT_SYSLOG(/*all*/0, 0); // /* no syslog messages => count is 0 */ // CU_SYSLOG_MATCH("foo.*baz"); // CU_ASSERT_SYSLOG(/*all*/0, 0); // /* one syslog message which doesn't match => count is 0, // * both macros succeed */ // CU_SYSLOG_MATCH("foo.*baz"); // syslog(LOG_ERR, "fnarp"); // CU_ASSERT_SYSLOG(/*all*/0, 0); // /* one syslog message which does match => count is 1, // * both macros succeed */ // CU_SYSLOG_MATCH("foo.*baz"); // syslog(LOG_ERR, "foo bar baz"); // CU_ASSERT_SYSLOG(/*all*/0, 1); // /* one syslog message which does match => count is 1, // * we check for 5, 2nd macro fails */ // CU_SYSLOG_MATCH("foo.*baz"); // syslog(LOG_ERR, "foo bar baz"); // CU_ASSERT_SYSLOG(/*all*/0, 5); // /* one syslog message with multiple matches => count is 1, // * all 3 macros succeed */ // CU_SYSLOG_MATCH("fuu.*bas"); // CU_SYSLOG_MATCH("bleah"); // syslog(LOG_ERR, "fuu bleah bas"); // CU_ASSERT_SYSLOG(/*all*/0, 1); // /* one syslog message with multiple matches which are tracked // * separately => count is 1, all 4 macros succeed */ // m1 = CU_SYSLOG_MATCH("fuu.*bas"); // m2 = CU_SYSLOG_MATCH("bleah"); // syslog(LOG_ERR, "fuu bleah bas"); // CU_ASSERT_SYSLOG(m1, 1); // CU_ASSERT_SYSLOG(m2, 0); } #endif cyrus-imapd-2.5.10/cunit/getxstring.testc0000644000175000017500000006164213001236020015335 00000000000000/* Test the getxstring() function */ #include "config.h" #include "cunit/cunit.h" #include "prot.h" #include "imap/global.h" /* * Here's the ABNF describing the various types of string from RF3501. * This is included for amusement mainly, as the getxstring() code takes * many liberties with it, being at times more liberal and at times more * conservative than the strict interpretation of the ABNF. As these * behaviours have been in the field a long time and clients may well * depend on them, we test for the existing behaviour rather than strict * RFC compliance. * * astring = 1*ASTRING-CHAR / string * * ASTRING-CHAR = ATOM-CHAR / resp-specials * * ATOM-CHAR = * * atom-specials = "(" / ")" / "{" / SP / CTL / list-wildcards / * quoted-specials / resp-specials * * string = quoted / literal * * list-wildcards = "%" / "*" * * literal = "{" number "}" CRLF *CHAR8 * ; Number represents the number of CHAR8s * * nil = "NIL" * * nstring = string / nil * * quoted = DQUOTE *QUOTED-CHAR DQUOTE * * QUOTED-CHAR = / * "\" quoted-specials * * quoted-specials = DQUOTE / "\" * * resp-specials = "]" * * string = quoted / literal */ /* * Run a single testcase. * * Note: prot_setisclient() turns off off literal synchronising so * we don't have to futz around with testing that. */ #define _TESTCASE_PRE(fut, input, retval) \ do { \ struct buf b = BUF_INITIALIZER; \ struct protstream *p; \ int c; \ p = prot_readmap(input, sizeof(input)-1); \ CU_ASSERT_PTR_NOT_NULL(p); \ prot_setisclient(p, 1); \ c = fut(p, NULL, &b); \ CU_ASSERT_EQUAL(c, retval); \ if (c != EOF) { #define _TESTCASE_POST() \ } \ prot_free(p); \ buf_free(&b); \ } while (0) #define TESTCASE(fut, input, retval, output) \ do { \ int outputlen = sizeof(output)-1; \ _TESTCASE_PRE(fut, input, retval); \ CU_ASSERT_EQUAL(b.len, outputlen); \ CU_ASSERT(!memcmp(b.s, output, outputlen)); \ _TESTCASE_POST(); \ } while(0) #define TESTCASE_NULL(fut, input, retval) \ do { \ _TESTCASE_PRE(fut, input, retval); \ CU_ASSERT_EQUAL(b.len, 0); \ CU_ASSERT_PTR_NULL(b.s); \ _TESTCASE_POST(); \ } while(0) /* * getastring() parses something vaguely like an astring, with a few differences. */ static void test_getastring(void) { /* Simple sequences of ascii alphanumerics characters are atoms */ TESTCASE(getastring, "hydrogen helium", ' ', "hydrogen"); TESTCASE(getastring, "258 uranium", ' ', "258"); TESTCASE(getastring, "uranium258 plutonium", ' ', "uranium258"); /* The character sequence NIL is not special, it's parsed as an atom */ TESTCASE(getastring, "NIL by mouth", ' ', "NIL"); TESTCASE(getastring, "NELLY the lamb", ' ', "NELLY"); /* * List wildcards aren't part of an atom, but Cyrus accepts them * in order to implement the "mailbox" and "list-mailbox" rules, * which are like astrings but also allow unquoted wildcards, * as astrings. */ TESTCASE(getastring, "foo*bar baz", ' ', "foo*bar"); TESTCASE(getastring, "baz%quux foo", ' ', "baz%quux"); /* * Various special characters are not part of atoms. * * Again the server code is very liberal in accepting all kinds of * things which aren't in the ABNF, so we test for the liberal * interpretation and note the conservative one in a comment. */ TESTCASE(getastring, "foo(bar baz", '(', "foo"); TESTCASE(getastring, "foo)bar baz", ')', "foo"); TESTCASE(getastring, "foo{bar baz", ' ', "foo{bar"); /* should be: '{', "foo" */ TESTCASE(getastring, "foo\"bar baz", '"', "foo"); TESTCASE(getastring, "foo\\bar baz", ' ', "foo\\bar"); /* should be: '\\', "foo" */ TESTCASE(getastring, "foo]bar baz", ' ', "foo]bar"); /* should be ']', "foo" */ /* * Quoted strings are astrings */ TESTCASE(getastring, "\"foo\" bar", ' ', "foo"); TESTCASE(getastring, "\"NIL\" by mouth ", ' ', "NIL"); TESTCASE(getastring, "\"foo bar\" baz", ' ', "foo bar"); TESTCASE(getastring, "\"foo bar", EOF, ""); TESTCASE(getastring, "\"foo\\\"bar\" baz", ' ', "foo\"bar"); TESTCASE(getastring, "\"foo\\\\bar\" baz", ' ', "foo\\bar"); /* Any non-special char can be escaped with \ */ TESTCASE(getastring, "\"foo\\bar\" baz", ' ', "foobar"); /* \n and \r can be escaped with \ */ TESTCASE(getastring, "\"foo\\\nbar\" baz", ' ', "foo\nbar"); TESTCASE(getastring, "\"foo\\\rbar\" baz", ' ', "foo\rbar"); /* Non-escaped \n and \r. The server is actually more * conversative than the ABNF and rejects these. */ TESTCASE(getastring, "\"foo\nbar\" baz", EOF, ""); /* should be ' ', "foo\nbar" */ TESTCASE(getastring, "\"foo\rbar\" baz", EOF, ""); /* should be ' ', "foo\rbar" */ /* * Literals are astrings */ /* boring literal */ TESTCASE(getastring, "{3}\r\nfoo ", ' ', "foo"); /* literal NIL */ TESTCASE(getastring, "{3}\r\nNIL ", ' ', "NIL"); /* literals with embedded space */ TESTCASE(getastring, "{7}\r\nfoo bar ", ' ', "foo bar"); /* literals with embedded \n or \r */ TESTCASE(getastring, "{7}\r\nfoo\nbar ", ' ', "foo\nbar"); TESTCASE(getastring, "{7}\r\nfoo\rbar ", ' ', "foo\rbar"); /* literals with 8-bit chars */ TESTCASE(getastring, "{7}\r\nfoo\277bar ", ' ', "foo\277bar"); /* literals with embedded NUL - getastring() rejects these */ TESTCASE(getastring, "{7}\r\nfoo\0bar ", EOF, ""); /* should be ' ', "foo\0bar" */ } /* * getbastring() is just the same as getastring() but allows embedded * NULs in literals. */ static void test_getbastring(void) { /* Simple sequences of ascii alphanumerics characters are atoms */ TESTCASE(getbastring, "hydrogen helium", ' ', "hydrogen"); TESTCASE(getbastring, "258 uranium", ' ', "258"); TESTCASE(getbastring, "uranium258 plutonium", ' ', "uranium258"); /* The character sequence NIL is not special, it's parsed as an atom */ TESTCASE(getbastring, "NIL by mouth", ' ', "NIL"); TESTCASE(getbastring, "NELLY the lamb", ' ', "NELLY"); /* * List wildcards aren't part of an atom, but Cyrus accepts them * in order to implement the "mailbox" and "list-mailbox" rules, * which are like astrings but also allow unquoted wildcards, * as astrings. This is probably sheer laziness on Cyrus' part * but it's a liberal-server interpretation which has been in the * field a while now, so we ought to preserve it. */ TESTCASE(getbastring, "foo*bar baz", ' ', "foo*bar"); TESTCASE(getbastring, "baz%quux foo", ' ', "baz%quux"); /* * Various special characters are not part of atoms. * * Again the server code is very liberal in accepting all kinds of * things which aren't in the ABNF, so we test for the liberal * interpretation and note the conservative one in a comment. */ TESTCASE(getbastring, "foo(bar baz", '(', "foo"); TESTCASE(getbastring, "foo)bar baz", ')', "foo"); TESTCASE(getbastring, "foo{bar baz", ' ', "foo{bar"); /* should be: '{', "foo" */ TESTCASE(getbastring, "foo\"bar baz", '"', "foo"); TESTCASE(getbastring, "foo\\bar baz", ' ', "foo\\bar"); /* should be: '\\', "foo" */ TESTCASE(getbastring, "foo]bar baz", ' ', "foo]bar"); /* should be ']', "foo" */ /* * Quoted strings are astrings */ TESTCASE(getbastring, "\"foo\" bar", ' ', "foo"); TESTCASE(getbastring, "\"NIL\" by mouth ", ' ', "NIL"); TESTCASE(getbastring, "\"foo bar\" baz", ' ', "foo bar"); TESTCASE(getbastring, "\"foo bar", EOF, ""); TESTCASE(getbastring, "\"foo\\\"bar\" baz", ' ', "foo\"bar"); TESTCASE(getbastring, "\"foo\\\\bar\" baz", ' ', "foo\\bar"); /* Any non-special char can be escaped with \ */ TESTCASE(getbastring, "\"foo\\bar\" baz", ' ', "foobar"); /* \n and \r can be escaped with \ */ TESTCASE(getbastring, "\"foo\\\nbar\" baz", ' ', "foo\nbar"); TESTCASE(getbastring, "\"foo\\\rbar\" baz", ' ', "foo\rbar"); /* Non-escaped \n and \r. The server is actually more * conversative than the ABNF and rejects these. */ TESTCASE(getbastring, "\"foo\nbar\" baz", EOF, ""); /* should be ' ', "foo\nbar" */ TESTCASE(getbastring, "\"foo\rbar\" baz", EOF, ""); /* should be ' ', "foo\rbar" */ /* * Literals are astrings */ /* boring literal */ TESTCASE(getbastring, "{3}\r\nfoo ", ' ', "foo"); /* literal NIL */ TESTCASE(getbastring, "{3}\r\nNIL ", ' ', "NIL"); /* literals with embedded space */ TESTCASE(getbastring, "{7}\r\nfoo bar ", ' ', "foo bar"); /* literals with embedded \n or \r */ TESTCASE(getbastring, "{7}\r\nfoo\nbar ", ' ', "foo\nbar"); TESTCASE(getbastring, "{7}\r\nfoo\rbar ", ' ', "foo\rbar"); /* literals with 8-bit chars */ TESTCASE(getbastring, "{7}\r\nfoo\277bar ", ' ', "foo\277bar"); /* literals with embedded NUL - getbastring() allows these */ TESTCASE(getbastring, "{7}\r\nfoo\0bar ", ' ', "foo\0bar"); } /* * getstring() parses something very like a 'string' in the ABNF. */ static void test_getstring(void) { /* Simple sequences of ascii alphanumerics characters are atoms * which are not strings */ TESTCASE(getstring, "hydrogen helium", EOF, ""); TESTCASE(getstring, "258 uranium", EOF, ""); TESTCASE(getstring, "uranium258 plutonium", EOF, ""); /* The character sequence NIL is not special, it's parsed as an atom */ TESTCASE(getstring, "NIL by mouth", EOF, ""); TESTCASE(getstring, "NELLY the lamb", EOF, ""); /* * List wildcards aren't part of an atom, but Cyrus accepts them * in order to implement the "mailbox" and "list-mailbox" rules, * which are like astrings but also allow unquoted wildcards, * as astrings. This is probably sheer laziness on Cyrus' part * but it's a liberal-server interpretation which has been in the * field a while now, so we ought to preserve it. */ TESTCASE(getstring, "foo*bar baz", EOF, ""); TESTCASE(getstring, "baz%quux foo", EOF, ""); /* * Various special characters are not part of atoms. * * Again the server code is very liberal in accepting all kinds of * things which aren't in the ABNF, so we test for the liberal * interpretation and note the conservative one in a comment. */ TESTCASE(getstring, "foo(bar baz", EOF, ""); TESTCASE(getstring, "foo)bar baz", EOF, ""); TESTCASE(getstring, "foo{bar baz", EOF, ""); TESTCASE(getstring, "foo\"bar baz", EOF, ""); TESTCASE(getstring, "foo\\bar baz", EOF, ""); TESTCASE(getstring, "foo]bar baz", EOF, ""); /* * Quoted strings are strings */ TESTCASE(getstring, "\"foo\" bar", ' ', "foo"); TESTCASE(getstring, "\"NIL\" by mouth ", ' ', "NIL"); TESTCASE(getstring, "\"foo bar\" baz", ' ', "foo bar"); TESTCASE(getstring, "\"foo bar", EOF, ""); TESTCASE(getstring, "\"foo\\\"bar\" baz", ' ', "foo\"bar"); TESTCASE(getstring, "\"foo\\\\bar\" baz", ' ', "foo\\bar"); /* Any non-special char can be escaped with \ */ TESTCASE(getstring, "\"foo\\bar\" baz", ' ', "foobar"); /* \n and \r can be escaped with \ */ TESTCASE(getstring, "\"foo\\\nbar\" baz", ' ', "foo\nbar"); TESTCASE(getstring, "\"foo\\\rbar\" baz", ' ', "foo\rbar"); /* Non-escaped \n and \r. The server is actually more * conversative than the ABNF and rejects these. */ TESTCASE(getstring, "\"foo\nbar\" baz", EOF, ""); /* should be ' ', "foo\nbar" */ TESTCASE(getstring, "\"foo\rbar\" baz", EOF, ""); /* should be ' ', "foo\rbar" */ /* * Literals are strings */ /* boring literal */ TESTCASE(getstring, "{3}\r\nfoo ", ' ', "foo"); /* literal NIL */ TESTCASE(getstring, "{3}\r\nNIL ", ' ', "NIL"); /* literals with embedded space */ TESTCASE(getstring, "{7}\r\nfoo bar ", ' ', "foo bar"); /* literals with embedded \n or \r */ TESTCASE(getstring, "{7}\r\nfoo\nbar ", ' ', "foo\nbar"); TESTCASE(getstring, "{7}\r\nfoo\rbar ", ' ', "foo\rbar"); /* literals with 8-bit chars */ TESTCASE(getstring, "{7}\r\nfoo\277bar ", ' ', "foo\277bar"); /* literals with embedded NUL - getstring() rejects these */ TESTCASE(getqstring, "{7}\r\nfoo\0bar ", EOF, ""); /* should be ' ', "foo\0bar" */ } /* * getqstring() accepts something very like the qstring in the ABNF. * Atoms, NIL and literals all fail. */ static void test_getqstring(void) { /* Simple sequences of ascii alphanumerics characters are atoms * which are not qstrings */ TESTCASE(getqstring, "hydrogen helium", EOF, ""); TESTCASE(getqstring, "258 uranium", EOF, ""); TESTCASE(getqstring, "uranium258 plutonium", EOF, ""); /* The character sequence NIL is not special, it's parsed as an atom */ TESTCASE(getqstring, "NIL by mouth", EOF, ""); TESTCASE(getqstring, "NELLY the lamb", EOF, ""); /* * List wildcards aren't part of an atom, but Cyrus accepts them * in order to implement the "mailbox" and "list-mailbox" rules, * which are like astrings but also allow unquoted wildcards, * as astrings. This is probably sheer laziness on Cyrus' part * but it's a liberal-server interpretation which has been in the * field a while now, so we ought to preserve it. */ TESTCASE(getqstring, "foo*bar baz", EOF, ""); TESTCASE(getqstring, "baz%quux foo", EOF, ""); /* * Various special characters are not part of atoms. * * Again the server code is very liberal in accepting all kinds of * things which aren't in the ABNF, so we test for the liberal * interpretation and note the conservative one in a comment. */ TESTCASE(getqstring, "foo(bar baz", EOF, ""); TESTCASE(getqstring, "foo)bar baz", EOF, ""); TESTCASE(getqstring, "foo{bar baz", EOF, ""); TESTCASE(getqstring, "foo\"bar baz", EOF, ""); TESTCASE(getqstring, "foo\\bar baz", EOF, ""); TESTCASE(getqstring, "foo]bar baz", EOF, ""); /* * Quoted strings */ TESTCASE(getqstring, "\"foo\" bar", ' ', "foo"); TESTCASE(getqstring, "\"NIL\" by mouth ", ' ', "NIL"); TESTCASE(getqstring, "\"foo bar\" baz", ' ', "foo bar"); TESTCASE(getqstring, "\"foo bar", EOF, ""); TESTCASE(getqstring, "\"foo\\\"bar\" baz", ' ', "foo\"bar"); TESTCASE(getqstring, "\"foo\\\\bar\" baz", ' ', "foo\\bar"); /* Any non-special char can be escaped with \ */ TESTCASE(getqstring, "\"foo\\bar\" baz", ' ', "foobar"); /* \n and \r can be escaped with \ */ TESTCASE(getqstring, "\"foo\\\nbar\" baz", ' ', "foo\nbar"); TESTCASE(getqstring, "\"foo\\\rbar\" baz", ' ', "foo\rbar"); /* Non-escaped \n and \r. The server is actually more * conversative than the ABNF and rejects these. */ TESTCASE(getqstring, "\"foo\nbar\" baz", EOF, ""); /* should be ' ', "foo\nbar" */ TESTCASE(getqstring, "\"foo\rbar\" baz", EOF, ""); /* should be ' ', "foo\rbar" */ /* * Literals are not qstrings */ /* boring literal */ TESTCASE(getqstring, "{3}\r\nfoo ", EOF, ""); /* literal NIL */ TESTCASE(getqstring, "{3}\r\nNIL ", EOF, ""); /* literals with embedded space */ TESTCASE(getqstring, "{7}\r\nfoo bar ", EOF, ""); /* literals with embedded \n or \r */ TESTCASE(getqstring, "{7}\r\nfoo\nbar ", EOF, ""); TESTCASE(getqstring, "{7}\r\nfoo\rbar ", EOF, ""); /* literals with 8-bit chars */ TESTCASE(getqstring, "{7}\r\nfoo\277bar ", EOF, ""); /* literals with embedded NUL */ TESTCASE(getqstring, "{7}\r\nfoo\0bar ", EOF, ""); } /* * getnstring() parses something vaguely like an nstring, with a few differences. */ static void test_getnstring(void) { /* Simple sequences of ascii alphanumerics characters are atoms */ TESTCASE(getnstring, "hydrogen helium", EOF, ""); TESTCASE(getnstring, "258 uranium", EOF, ""); TESTCASE(getnstring, "uranium258 plutonium", EOF, ""); /* The character sequence NIL is special for nstrings only */ TESTCASE_NULL(getnstring, "NIL by mouth", ' '); TESTCASE(getnstring, "NELLY ", EOF, ""); /* * List wildcards aren't part of an atom, but Cyrus accepts them * in order to implement the "mailbox" and "list-mailbox" rules, * which are like astrings but also allow unquoted wildcards, * as astrings. */ TESTCASE(getnstring, "foo*bar baz", EOF, ""); TESTCASE(getnstring, "baz%quux foo", EOF, ""); /* * Various special characters are not part of atoms. * * Again the server code is very liberal in accepting all kinds of * things which aren't in the ABNF, so we test for the liberal * interpretation and note the conservative one in a comment. */ TESTCASE(getnstring, "foo(bar baz", EOF, ""); TESTCASE(getnstring, "foo)bar baz", EOF, ""); TESTCASE(getnstring, "foo{bar baz", EOF, ""); TESTCASE(getnstring, "foo\"bar baz", EOF, ""); TESTCASE(getnstring, "foo\\bar baz", EOF, ""); TESTCASE(getnstring, "foo]bar baz", EOF, ""); /* * Quoted strings are nstrings */ TESTCASE(getnstring, "\"foo\" bar", ' ', "foo"); TESTCASE(getnstring, "\"NIL\" by mouth ", ' ', "NIL"); TESTCASE(getnstring, "\"foo bar\" baz", ' ', "foo bar"); TESTCASE(getnstring, "\"foo bar", EOF, ""); TESTCASE(getnstring, "\"foo\\\"bar\" baz", ' ', "foo\"bar"); TESTCASE(getnstring, "\"foo\\\\bar\" baz", ' ', "foo\\bar"); /* Any non-special char can be escaped with \ */ TESTCASE(getnstring, "\"foo\\bar\" baz", ' ', "foobar"); /* \n and \r can be escaped with \ */ TESTCASE(getnstring, "\"foo\\\nbar\" baz", ' ', "foo\nbar"); TESTCASE(getnstring, "\"foo\\\rbar\" baz", ' ', "foo\rbar"); /* Non-escaped \n and \r. The server is actually more * conversative than the ABNF and rejects these. */ TESTCASE(getnstring, "\"foo\nbar\" baz", EOF, ""); /* should be ' ', "foo\nbar" */ TESTCASE(getnstring, "\"foo\rbar\" baz", EOF, ""); /* should be ' ', "foo\rbar" */ /* * Literals are nstrings */ /* boring literal */ TESTCASE(getnstring, "{3}\r\nfoo ", ' ', "foo"); /* literal NIL */ TESTCASE(getnstring, "{3}\r\nNIL ", ' ', "NIL"); /* literals with embedded space */ TESTCASE(getnstring, "{7}\r\nfoo bar ", ' ', "foo bar"); /* literals with embedded \n or \r */ TESTCASE(getnstring, "{7}\r\nfoo\nbar ", ' ', "foo\nbar"); TESTCASE(getnstring, "{7}\r\nfoo\rbar ", ' ', "foo\rbar"); /* literals with 8-bit chars */ TESTCASE(getnstring, "{7}\r\nfoo\277bar ", ' ', "foo\277bar"); /* literals with embedded NUL - getnstring() rejects these */ TESTCASE(getnstring, "{7}\r\nfoo\0bar ", EOF, ""); /* should be ' ', "foo\0bar" */ } /* * getbnstring() is just like getnstring() but allows embedded NULs in * literals. */ static void test_getbnstring(void) { /* Simple sequences of ascii alphanumerics characters are atoms */ TESTCASE(getbnstring, "hydrogen helium", EOF, ""); TESTCASE(getbnstring, "258 uranium", EOF, ""); TESTCASE(getbnstring, "uranium258 plutonium", EOF, ""); /* The character sequence NIL is special for nstrings only */ TESTCASE_NULL(getbnstring, "NIL by mouth", ' '); TESTCASE(getbnstring, "NELLY ", EOF, ""); /* * List wildcards aren't part of an atom, but Cyrus accepts them * in order to implement the "mailbox" and "list-mailbox" rules, * which are like astrings but also allow unquoted wildcards, * as astrings. */ TESTCASE(getnstring, "foo*bar baz", EOF, ""); TESTCASE(getbnstring, "baz%quux foo", EOF, ""); /* * Various special characters are not part of atoms. * * Again the server code is very liberal in accepting all kinds of * things which aren't in the ABNF, so we test for the liberal * interpretation and note the conservative one in a comment. */ TESTCASE(getbnstring, "foo(bar baz", EOF, ""); TESTCASE(getbnstring, "foo)bar baz", EOF, ""); TESTCASE(getbnstring, "foo{bar baz", EOF, ""); TESTCASE(getbnstring, "foo\"bar baz", EOF, ""); TESTCASE(getbnstring, "foo\\bar baz", EOF, ""); TESTCASE(getbnstring, "foo]bar baz", EOF, ""); /* * Quoted strings are nstrings */ TESTCASE(getbnstring, "\"foo\" bar", ' ', "foo"); TESTCASE(getbnstring, "\"NIL\" by mouth ", ' ', "NIL"); TESTCASE(getbnstring, "\"foo bar\" baz", ' ', "foo bar"); TESTCASE(getbnstring, "\"foo bar", EOF, ""); TESTCASE(getbnstring, "\"foo\\\"bar\" baz", ' ', "foo\"bar"); TESTCASE(getbnstring, "\"foo\\\\bar\" baz", ' ', "foo\\bar"); /* Any non-special char can be escaped with \ */ TESTCASE(getbnstring, "\"foo\\bar\" baz", ' ', "foobar"); /* \n and \r can be escaped with \ */ TESTCASE(getbnstring, "\"foo\\\nbar\" baz", ' ', "foo\nbar"); TESTCASE(getbnstring, "\"foo\\\rbar\" baz", ' ', "foo\rbar"); /* Non-escaped \n and \r. The server is actually more * conversative than the ABNF and rejects these. */ TESTCASE(getbnstring, "\"foo\nbar\" baz", EOF, ""); /* should be ' ', "foo\nbar" */ TESTCASE(getbnstring, "\"foo\rbar\" baz", EOF, ""); /* should be ' ', "foo\rbar" */ /* * Literals are nstrings */ /* boring literal */ TESTCASE(getbnstring, "{3}\r\nfoo ", ' ', "foo"); /* literal NIL */ TESTCASE(getbnstring, "{3}\r\nNIL ", ' ', "NIL"); /* literals with embedded space */ TESTCASE(getbnstring, "{7}\r\nfoo bar ", ' ', "foo bar"); /* literals with embedded \n or \r */ TESTCASE(getbnstring, "{7}\r\nfoo\nbar ", ' ', "foo\nbar"); TESTCASE(getbnstring, "{7}\r\nfoo\rbar ", ' ', "foo\rbar"); /* literals with 8-bit chars */ TESTCASE(getbnstring, "{7}\r\nfoo\277bar ", ' ', "foo\277bar"); /* literals with embedded NUL - getbnstring() allows these */ TESTCASE(getbnstring, "{7}\r\nfoo\0bar ", ' ', "foo\0bar"); } /* * getnastring() gets an astring, but with NIL returning NULL */ static void test_getnastring(void) { /* Simple sequences of ascii alphanumerics characters are atoms */ TESTCASE(getnastring, "hydrogen helium", ' ', "hydrogen"); TESTCASE(getnastring, "258 uranium", ' ', "258"); TESTCASE(getnastring, "uranium258 plutonium", ' ', "uranium258"); /* The character sequence NIL is special, unless quoted */ TESTCASE_NULL(getnastring, "NIL by mouth", ' '); TESTCASE(getnastring, "NELLY the lamb", ' ', "NELLY"); /* * List wildcards aren't part of an atom, but Cyrus accepts them * in order to implement the "mailbox" and "list-mailbox" rules, * which are like astrings but also allow unquoted wildcards, * as astrings. */ TESTCASE(getnastring, "foo*bar baz", ' ', "foo*bar"); TESTCASE(getnastring, "baz%quux foo", ' ', "baz%quux"); /* * Various special characters are not part of atoms. * * Again the server code is very liberal in accepting all kinds of * things which aren't in the ABNF, so we test for the liberal * interpretation and note the conservative one in a comment. */ TESTCASE(getnastring, "foo(bar baz", '(', "foo"); TESTCASE(getnastring, "foo)bar baz", ')', "foo"); TESTCASE(getnastring, "foo{bar baz", ' ', "foo{bar"); /* should be: '{', "foo" */ TESTCASE(getnastring, "foo\"bar baz", '"', "foo"); TESTCASE(getnastring, "foo\\bar baz", ' ', "foo\\bar"); /* should be: '\\', "foo" */ TESTCASE(getnastring, "foo]bar baz", ' ', "foo]bar"); /* should be ']', "foo" */ /* * Quoted strings are astrings */ TESTCASE(getnastring, "\"foo\" bar", ' ', "foo"); /* literals with embedded space */ TESTCASE(getnastring, "\"NIL\" by mouth ", ' ', "NIL"); TESTCASE(getnastring, "\"foo bar\" baz", ' ', "foo bar"); TESTCASE(getnastring, "\"foo bar", EOF, ""); TESTCASE(getnastring, "\"foo\\\"bar\" baz", ' ', "foo\"bar"); TESTCASE(getnastring, "\"foo\\\\bar\" baz", ' ', "foo\\bar"); /* Any non-special char can be escaped with \ */ TESTCASE(getnastring, "\"foo\\bar\" baz", ' ', "foobar"); /* \n and \r can be escaped with \ */ TESTCASE(getnastring, "\"foo\\\nbar\" baz", ' ', "foo\nbar"); TESTCASE(getnastring, "\"foo\\\rbar\" baz", ' ', "foo\rbar"); /* Non-escaped \n and \r. The server is actually more * conversative than the ABNF and rejects these. */ TESTCASE(getnastring, "\"foo\nbar\" baz", EOF, ""); /* should be ' ', "foo\nbar" */ TESTCASE(getnastring, "\"foo\rbar\" baz", EOF, ""); /* should be ' ', "foo\rbar" */ /* * Literals are astrings */ /* boring literal */ TESTCASE(getnastring, "{3}\r\nfoo ", ' ', "foo"); /* literal NIL */ TESTCASE(getnastring, "{3}\r\nNIL ", ' ', "NIL"); /* literals with embedded space */ TESTCASE(getnastring, "{7}\r\nfoo bar ", ' ', "foo bar"); /* literals with embedded \n or \r */ TESTCASE(getnastring, "{7}\r\nfoo\nbar ", ' ', "foo\nbar"); TESTCASE(getnastring, "{7}\r\nfoo\rbar ", ' ', "foo\rbar"); /* literals with 8-bit chars */ TESTCASE(getnastring, "{7}\r\nfoo\277bar ", ' ', "foo\277bar"); /* literals with embedded NUL - getastring() rejects these */ TESTCASE(getnastring, "{7}\r\nfoo\0bar ", EOF, ""); /* should be ' ', "foo\0bar" */ } /* vim: set ft=c: */ cyrus-imapd-2.5.10/cunit/rfc822tok.testc0000644000175000017500000003124413001236020014656 00000000000000#include "config.h" #include "cunit/cunit.h" #include "rfc822tok.h" #define WORD0 "lorem" #define WORD1 "ipsum" #define WORD2 "dolor" #define WORD2A "do" #define WORD2B "lor" #define WORD3 "sit" #define WORD4 "amet" #define BADPOINTER ((void *)0xdeadbeef) static void test_simple(void) { static const char PHRASE[] = WORD0" "WORD1" "WORD2" "WORD3" "WORD4; rfc822tok_t tok = RFC822TOK_INITIALIZER; char *p; int t; rfc822tok_init(&tok, PHRASE, sizeof(PHRASE)-1, 0); p = BADPOINTER; t = rfc822tok_next(&tok, &p); CU_ASSERT_EQUAL(t, RFC822_ATOM); CU_ASSERT_STRING_EQUAL(p, WORD0); p = BADPOINTER; t = rfc822tok_next(&tok, &p); CU_ASSERT_EQUAL(t, RFC822_ATOM); CU_ASSERT_STRING_EQUAL(p, WORD1); p = BADPOINTER; t = rfc822tok_next(&tok, &p); CU_ASSERT_EQUAL(t, RFC822_ATOM); CU_ASSERT_STRING_EQUAL(p, WORD2); p = BADPOINTER; t = rfc822tok_next(&tok, &p); CU_ASSERT_EQUAL(t, RFC822_ATOM); CU_ASSERT_STRING_EQUAL(p, WORD3); p = BADPOINTER; t = rfc822tok_next(&tok, &p); CU_ASSERT_EQUAL(t, RFC822_ATOM); CU_ASSERT_STRING_EQUAL(p, WORD4); p = BADPOINTER; t = rfc822tok_next(&tok, &p); CU_ASSERT_EQUAL(t, EOF); CU_ASSERT_PTR_NULL(p); rfc822tok_fini(&tok); } /* test that ceasing to call rfc822tok_next() before the end * of the tokens does not leak memory as long as rfc822tok_fini() * is called; we rely on Valgrind to find memleaks */ static void test_stopearly(void) { static const char PHRASE[] = WORD0" "WORD1" "WORD2" "WORD3" "WORD4; rfc822tok_t tok = RFC822TOK_INITIALIZER; char *p; int t; rfc822tok_init(&tok, PHRASE, sizeof(PHRASE)-1, 0); p = BADPOINTER; t = rfc822tok_next(&tok, &p); CU_ASSERT_EQUAL(t, RFC822_ATOM); CU_ASSERT_STRING_EQUAL(p, WORD0); rfc822tok_fini(&tok); } /* tokenizing an empty string just returns EOF */ static void test_blank(void) { static const char PHRASE[] = ""; rfc822tok_t tok = RFC822TOK_INITIALIZER; char *p; int t; rfc822tok_init(&tok, PHRASE, sizeof(PHRASE)-1, 0); p = BADPOINTER; t = rfc822tok_next(&tok, &p); CU_ASSERT_EQUAL(t, EOF); CU_ASSERT_PTR_NULL(p); rfc822tok_fini(&tok); } /* tokenizing a NULL string just returns EOF */ static void test_null(void) { rfc822tok_t tok = RFC822TOK_INITIALIZER; char *p; int t; rfc822tok_init(&tok, NULL, 0, 0); p = BADPOINTER; t = rfc822tok_next(&tok, &p); CU_ASSERT_EQUAL(t, EOF); CU_ASSERT_PTR_NULL(p); rfc822tok_fini(&tok); } /* non-trivial whitespace between atoms */ static void test_whitespace(void) { static const char PHRASE[] = WORD0" "WORD1"\t"WORD2" \t \v \t "WORD3"\r\n\t"WORD4; rfc822tok_t tok = RFC822TOK_INITIALIZER; char *p; int t; rfc822tok_init(&tok, PHRASE, sizeof(PHRASE)-1, 0); p = BADPOINTER; t = rfc822tok_next(&tok, &p); CU_ASSERT_EQUAL(t, RFC822_ATOM); CU_ASSERT_STRING_EQUAL(p, WORD0); p = BADPOINTER; t = rfc822tok_next(&tok, &p); CU_ASSERT_EQUAL(t, RFC822_ATOM); CU_ASSERT_STRING_EQUAL(p, WORD1); p = BADPOINTER; t = rfc822tok_next(&tok, &p); CU_ASSERT_EQUAL(t, RFC822_ATOM); CU_ASSERT_STRING_EQUAL(p, WORD2); p = BADPOINTER; t = rfc822tok_next(&tok, &p); CU_ASSERT_EQUAL(t, RFC822_ATOM); CU_ASSERT_STRING_EQUAL(p, WORD3); p = BADPOINTER; t = rfc822tok_next(&tok, &p); CU_ASSERT_EQUAL(t, RFC822_ATOM); CU_ASSERT_STRING_EQUAL(p, WORD4); p = BADPOINTER; t = rfc822tok_next(&tok, &p); CU_ASSERT_EQUAL(t, EOF); CU_ASSERT_PTR_NULL(p); rfc822tok_fini(&tok); } /* whitespace and non-trivial comments between atoms */ static void test_comments(void) { static const char PHRASE[] = WORD0"()" WORD1"( hello world )" WORD2" ( he\\l\\lo \\) world\r\n and friends) " WORD3" (hell(o( (w)or)ld))" WORD4; rfc822tok_t tok = RFC822TOK_INITIALIZER; char *p; int t; rfc822tok_init(&tok, PHRASE, sizeof(PHRASE)-1, 0); p = BADPOINTER; t = rfc822tok_next(&tok, &p); CU_ASSERT_EQUAL(t, RFC822_ATOM); CU_ASSERT_STRING_EQUAL(p, WORD0); p = BADPOINTER; t = rfc822tok_next(&tok, &p); CU_ASSERT_EQUAL(t, RFC822_ATOM); CU_ASSERT_STRING_EQUAL(p, WORD1); p = BADPOINTER; t = rfc822tok_next(&tok, &p); CU_ASSERT_EQUAL(t, RFC822_ATOM); CU_ASSERT_STRING_EQUAL(p, WORD2); p = BADPOINTER; t = rfc822tok_next(&tok, &p); CU_ASSERT_EQUAL(t, RFC822_ATOM); CU_ASSERT_STRING_EQUAL(p, WORD3); p = BADPOINTER; t = rfc822tok_next(&tok, &p); CU_ASSERT_EQUAL(t, RFC822_ATOM); CU_ASSERT_STRING_EQUAL(p, WORD4); p = BADPOINTER; t = rfc822tok_next(&tok, &p); CU_ASSERT_EQUAL(t, EOF); CU_ASSERT_PTR_NULL(p); rfc822tok_fini(&tok); } static void test_quoted_strings(void) { static const char PHRASE[] = "\""WORD0"\"" "\""WORD1"\\x\" " "\""WORD2A"\\\""WORD2B"\" " "\""WORD3" \r\n\t \t"WORD4"\""; rfc822tok_t tok = RFC822TOK_INITIALIZER; char *p; int t; rfc822tok_init(&tok, PHRASE, sizeof(PHRASE)-1, 0); p = BADPOINTER; t = rfc822tok_next(&tok, &p); CU_ASSERT_EQUAL(t, RFC822_QSTRING); CU_ASSERT_STRING_EQUAL(p, WORD0); p = BADPOINTER; t = rfc822tok_next(&tok, &p); CU_ASSERT_EQUAL(t, RFC822_QSTRING); CU_ASSERT_STRING_EQUAL(p, WORD1"x"); p = BADPOINTER; t = rfc822tok_next(&tok, &p); CU_ASSERT_EQUAL(t, RFC822_QSTRING); CU_ASSERT_STRING_EQUAL(p, WORD2A"\""WORD2B); p = BADPOINTER; t = rfc822tok_next(&tok, &p); CU_ASSERT_EQUAL(t, RFC822_QSTRING); CU_ASSERT_STRING_EQUAL(p, WORD3" \t \t"WORD4); p = BADPOINTER; t = rfc822tok_next(&tok, &p); CU_ASSERT_EQUAL(t, EOF); CU_ASSERT_PTR_NULL(p); rfc822tok_fini(&tok); } static void test_special_dot(void) { static const char PHRASE[] = WORD0" " WORD1"."WORD2"."WORD3" " WORD4; rfc822tok_t tok = RFC822TOK_INITIALIZER; char *p; int t; /* by default '.' are not special */ rfc822tok_init(&tok, PHRASE, sizeof(PHRASE)-1, 0); p = BADPOINTER; t = rfc822tok_next(&tok, &p); CU_ASSERT_EQUAL(t, RFC822_ATOM); CU_ASSERT_STRING_EQUAL(p, WORD0); p = BADPOINTER; t = rfc822tok_next(&tok, &p); CU_ASSERT_EQUAL(t, RFC822_ATOM); CU_ASSERT_STRING_EQUAL(p, WORD1"."WORD2"."WORD3); p = BADPOINTER; t = rfc822tok_next(&tok, &p); CU_ASSERT_EQUAL(t, RFC822_ATOM); CU_ASSERT_STRING_EQUAL(p, WORD4); p = BADPOINTER; t = rfc822tok_next(&tok, &p); CU_ASSERT_EQUAL(t, EOF); CU_ASSERT_PTR_NULL(p); rfc822tok_fini(&tok); /* with the flag, '.' are special */ rfc822tok_init(&tok, PHRASE, sizeof(PHRASE)-1, RFC822_SPECIAL_DOT); p = BADPOINTER; t = rfc822tok_next(&tok, &p); CU_ASSERT_EQUAL(t, RFC822_ATOM); CU_ASSERT_STRING_EQUAL(p, WORD0); p = BADPOINTER; t = rfc822tok_next(&tok, &p); CU_ASSERT_EQUAL(t, RFC822_ATOM); CU_ASSERT_STRING_EQUAL(p, WORD1); p = BADPOINTER; t = rfc822tok_next(&tok, &p); CU_ASSERT_EQUAL(t, '.'); CU_ASSERT_PTR_NULL(p); p = BADPOINTER; t = rfc822tok_next(&tok, &p); CU_ASSERT_EQUAL(t, RFC822_ATOM); CU_ASSERT_STRING_EQUAL(p, WORD2); p = BADPOINTER; t = rfc822tok_next(&tok, &p); CU_ASSERT_EQUAL(t, '.'); CU_ASSERT_PTR_NULL(p); p = BADPOINTER; t = rfc822tok_next(&tok, &p); CU_ASSERT_EQUAL(t, RFC822_ATOM); CU_ASSERT_STRING_EQUAL(p, WORD3); p = BADPOINTER; t = rfc822tok_next(&tok, &p); CU_ASSERT_EQUAL(t, RFC822_ATOM); CU_ASSERT_STRING_EQUAL(p, WORD4); p = BADPOINTER; t = rfc822tok_next(&tok, &p); CU_ASSERT_EQUAL(t, EOF); CU_ASSERT_PTR_NULL(p); rfc822tok_fini(&tok); } static void test_special_equal(void) { static const char PHRASE[] = WORD0" " WORD1"="WORD2"="WORD3" " WORD4; rfc822tok_t tok = RFC822TOK_INITIALIZER; char *p; int t; /* by default '=' are not special */ rfc822tok_init(&tok, PHRASE, sizeof(PHRASE)-1, 0); p = BADPOINTER; t = rfc822tok_next(&tok, &p); CU_ASSERT_EQUAL(t, RFC822_ATOM); CU_ASSERT_STRING_EQUAL(p, WORD0); p = BADPOINTER; t = rfc822tok_next(&tok, &p); CU_ASSERT_EQUAL(t, RFC822_ATOM); CU_ASSERT_STRING_EQUAL(p, WORD1"="WORD2"="WORD3); p = BADPOINTER; t = rfc822tok_next(&tok, &p); CU_ASSERT_EQUAL(t, RFC822_ATOM); CU_ASSERT_STRING_EQUAL(p, WORD4); p = BADPOINTER; t = rfc822tok_next(&tok, &p); CU_ASSERT_EQUAL(t, EOF); CU_ASSERT_PTR_NULL(p); rfc822tok_fini(&tok); /* with the flag, '=' are special */ rfc822tok_init(&tok, PHRASE, sizeof(PHRASE)-1, RFC822_SPECIAL_EQUAL); p = BADPOINTER; t = rfc822tok_next(&tok, &p); CU_ASSERT_EQUAL(t, RFC822_ATOM); CU_ASSERT_STRING_EQUAL(p, WORD0); p = BADPOINTER; t = rfc822tok_next(&tok, &p); CU_ASSERT_EQUAL(t, RFC822_ATOM); CU_ASSERT_STRING_EQUAL(p, WORD1); p = BADPOINTER; t = rfc822tok_next(&tok, &p); CU_ASSERT_EQUAL(t, '='); CU_ASSERT_PTR_NULL(p); p = BADPOINTER; t = rfc822tok_next(&tok, &p); CU_ASSERT_EQUAL(t, RFC822_ATOM); CU_ASSERT_STRING_EQUAL(p, WORD2); p = BADPOINTER; t = rfc822tok_next(&tok, &p); CU_ASSERT_EQUAL(t, '='); CU_ASSERT_PTR_NULL(p); p = BADPOINTER; t = rfc822tok_next(&tok, &p); CU_ASSERT_EQUAL(t, RFC822_ATOM); CU_ASSERT_STRING_EQUAL(p, WORD3); p = BADPOINTER; t = rfc822tok_next(&tok, &p); CU_ASSERT_EQUAL(t, RFC822_ATOM); CU_ASSERT_STRING_EQUAL(p, WORD4); p = BADPOINTER; t = rfc822tok_next(&tok, &p); CU_ASSERT_EQUAL(t, EOF); CU_ASSERT_PTR_NULL(p); rfc822tok_fini(&tok); } struct token { int token; const char *text; }; #define TESTCASE(in, inlen, exp) \ do { \ const struct token *_exp = (exp); \ rfc822tok_t _tok = RFC822TOK_INITIALIZER; \ rfc822tok_init(&_tok, (in), (inlen), RFC822_SPECIAL_EQUAL); \ for (;; _exp++) { \ char *_p = BADPOINTER; \ int _t = rfc822tok_next(&_tok, &_p); \ CU_ASSERT_EQUAL(_t, _exp->token); \ CU_ASSERT_PTR_NOT_EQUAL(_p, BADPOINTER); \ if (_t > 255) { \ CU_ASSERT_STRING_EQUAL(_p, _exp->text); \ } \ else { \ CU_ASSERT_PTR_NULL(_p); \ } \ if (_exp->token == EOF) break; \ } \ rfc822tok_fini(&_tok); \ } while(0) /* a real-world example */ static void test_content_type(void) { /* Examples from RFC2045 */ { static const char PHRASE[] = "Content-Type: text/plain; charset=us-ascii\r\n"; static const struct token EXP[] = { { RFC822_ATOM, "Content-Type" }, { ':', NULL }, { RFC822_ATOM, "text/plain" }, { ';', NULL }, { RFC822_ATOM, "charset" }, { '=', NULL }, { RFC822_ATOM, "us-ascii" }, { EOF, NULL }}; TESTCASE(PHRASE, sizeof(PHRASE)-1, EXP); } { static const char PHRASE[] = "Content-Type: text/plain; charset=us-ascii (Plain text)\r\n"; static const struct token EXP[] = { { RFC822_ATOM, "Content-Type" }, { ':', NULL }, { RFC822_ATOM, "text/plain" }, { ';', NULL }, { RFC822_ATOM, "charset" }, { '=', NULL }, { RFC822_ATOM, "us-ascii" }, { EOF, NULL }}; TESTCASE(PHRASE, sizeof(PHRASE)-1, EXP); } { static const char PHRASE[] = "Content-Type: text/plain; charset=\"us-ascii\"\r\n"; static const struct token EXP[] = { { RFC822_ATOM, "Content-Type" }, { ':', NULL }, { RFC822_ATOM, "text/plain" }, { ';', NULL }, { RFC822_ATOM, "charset" }, { '=', NULL }, { RFC822_QSTRING, "us-ascii" }, { EOF, NULL }}; TESTCASE(PHRASE, sizeof(PHRASE)-1, EXP); } { static const char PHRASE[] = "Content-Type: \"text/plain\"; charset=\"us-ascii\"\r\n"; static const struct token EXP[] = { { RFC822_ATOM, "Content-Type" }, { ':', NULL }, { RFC822_QSTRING, "text/plain" }, { ';', NULL }, { RFC822_ATOM, "charset" }, { '=', NULL }, { RFC822_QSTRING, "us-ascii" }, { EOF, NULL }}; TESTCASE(PHRASE, sizeof(PHRASE)-1, EXP); } /* some made-up examples */ { static const char PHRASE[] = "Content-Type : text/plain ; charset = \"us-ascii\" \r\n"; static const struct token EXP[] = { { RFC822_ATOM, "Content-Type" }, { ':', NULL }, { RFC822_ATOM, "text/plain" }, { ';', NULL }, { RFC822_ATOM, "charset" }, { '=', NULL }, { RFC822_QSTRING, "us-ascii" }, { EOF, NULL }}; TESTCASE(PHRASE, sizeof(PHRASE)-1, EXP); } { static const char PHRASE[] = "Content-Type: text/plain\r\n ; charset = us-ascii \r\n"; static const struct token EXP[] = { { RFC822_ATOM, "Content-Type" }, { ':', NULL }, { RFC822_ATOM, "text/plain" }, { ';', NULL }, { RFC822_ATOM, "charset" }, { '=', NULL }, { RFC822_ATOM, "us-ascii" }, { EOF, NULL }}; TESTCASE(PHRASE, sizeof(PHRASE)-1, EXP); } } /* vim: set ft=c: */ cyrus-imapd-2.5.10/cunit/parse.testc0000644000175000017500000001621613001236020014246 00000000000000#include "config.h" #include "cunit/cunit.h" #include "xmalloc.h" #include "prot.h" #include "imap/global.h" #include "util.h" #define CANARY 0xdeadbeef #define CANARY64 0xdeadbeefcafebabe static void test_parsenum(void) { const char NUM[] = "18338747846901181684 some other stuff"; bit64 val = CANARY64; int r; r = parsenum(NUM, NULL, strlen(NUM), &val); CU_ASSERT_EQUAL(r, 0); CU_ASSERT_EQUAL(val, 18338747846901181684LLU); } int wrap_getint32(const char *s, int32_t *valp) { struct protstream *prot; char *b; int c; b = xstrdup(s); /* work around bug in prot_ungetc */ prot = prot_readmap(b, strlen(b)); *valp = CANARY; c = getint32(prot, valp); free(b); prot_free(prot); return c; } static void test_getint32(void) { static const char STR1[] = "0 "; static const int32_t VAL1 = 0; static const char STR2[] = "1234567890 "; static const int32_t VAL2 = 1234567890; // static const char STR3[] = "12345678901234567890 "; static const char STR4[] = "123)"; static const int32_t VAL4 = 123; static const char STR5[] = "y&+123 "; static const char STR6[] = "123"; static const int32_t VAL6 = 123; static const char STR7[] = "-123 "; static const char STR8[] = "+123 "; int32_t val; int c; /* test a valid zero value */ c = wrap_getint32(STR1, &val); CU_ASSERT_EQUAL(c, ' '); CU_ASSERT_EQUAL(val, VAL1); /* test a valid value with all the digits */ c = wrap_getint32(STR2, &val); CU_ASSERT_EQUAL(c, ' '); CU_ASSERT_EQUAL(val, VAL2); // This test fatal()s which we cannot catch for now // /* test a string with too many digits */ // c = wrap_getint32(STR3, &val); // CU_ASSERT_EQUAL(c, EOF); // CU_ASSERT_EQUAL(val, CANARY); /* test a valid value with a different terminator */ c = wrap_getint32(STR4, &val); CU_ASSERT_EQUAL(c, ')'); CU_ASSERT_EQUAL(val, VAL4); /* test an invalid string */ c = wrap_getint32(STR5, &val); CU_ASSERT_EQUAL(c, EOF); /* sadly, val is undefined at this point */ /* test the corner case where we encounter EOF * at the end of a valid string of digits */ c = wrap_getint32(STR6, &val); CU_ASSERT_EQUAL(c, EOF); CU_ASSERT_EQUAL(val, VAL6); /* test a leading - */ c = wrap_getint32(STR7, &val); /* this would have succeeded if getint32() weren't broken */ CU_ASSERT_EQUAL(c, EOF); /* sadly, val is undefined at this point */ /* test a leading + */ c = wrap_getint32(STR8, &val); /* this would have succeeded if getint32() weren't broken */ CU_ASSERT_EQUAL(c, EOF); /* sadly, val is undefined at this point */ } int wrap_getsint32(const char *s, int32_t *valp) { struct protstream *prot; char *b; int c; b = xstrdup(s); /* work around bug in prot_ungetc */ prot = prot_readmap(b, strlen(b)); *valp = CANARY; c = getsint32(prot, valp); free(b); prot_free(prot); return c; } static void test_getsint32(void) { static const char STR1[] = "0 "; static const int32_t VAL1 = 0; static const char STR2[] = "1234567890 "; static const int32_t VAL2 = 1234567890; // static const char STR3[] = "12345678901234567890 "; static const char STR4[] = "123)"; static const int32_t VAL4 = 123; static const char STR5[] = "y&+123 "; static const char STR6[] = "123"; static const int32_t VAL6 = 123; static const char STR7[] = "-123 "; static const int32_t VAL7 = -123; static const char STR8[] = "+123 "; static const int32_t VAL8 = 123; int32_t val; int c; /* test a valid zero value */ c = wrap_getsint32(STR1, &val); CU_ASSERT_EQUAL(c, ' '); CU_ASSERT_EQUAL(val, VAL1); /* test a valid value with all the digits */ c = wrap_getsint32(STR2, &val); CU_ASSERT_EQUAL(c, ' '); CU_ASSERT_EQUAL(val, VAL2); // This test fatal()s which we cannot catch for now // /* test a string with too many digits */ // c = wrap_getsint32(STR3, &val); // CU_ASSERT_EQUAL(c, EOF); // CU_ASSERT_EQUAL(val, CANARY); /* test a valid value with a different terminator */ c = wrap_getsint32(STR4, &val); CU_ASSERT_EQUAL(c, ')'); CU_ASSERT_EQUAL(val, VAL4); /* test an invalid string */ c = wrap_getsint32(STR5, &val); CU_ASSERT_EQUAL(c, EOF); /* sadly, val is undefined at this point */ /* test the corner case where we encounter EOF * at the end of a valid string of digits */ c = wrap_getsint32(STR6, &val); CU_ASSERT_EQUAL(c, EOF); CU_ASSERT_EQUAL(val, VAL6); /* test a leading - */ c = wrap_getsint32(STR7, &val); CU_ASSERT_EQUAL(c, ' '); CU_ASSERT_EQUAL(val, VAL7); /* test a leading + */ c = wrap_getsint32(STR8, &val); CU_ASSERT_EQUAL(c, ' '); CU_ASSERT_EQUAL(val, VAL8); } int wrap_getmodseq(const char *s, modseq_t *valp) { struct protstream *prot; char *b; int c; b = xstrdup(s); /* work around bug in prot_ungetc */ prot = prot_readmap(b, strlen(b)); *valp = CANARY64; c = getmodseq(prot, valp); free(b); prot_free(prot); return c; } static void test_getmodseq(void) { static const char STR1[] = "0 "; static const modseq_t VAL1 = 0; static const char STR2[] = "1234567890 "; static const modseq_t VAL2 = 1234567890; static const char STR3[] = "12345678901234567890 "; static const modseq_t VAL3 = 12345678901234567890ULL; // static const char STR3a[] = "123456789012345678901234567890 "; static const char STR4[] = "123)"; static const modseq_t VAL4 = 123; static const char STR5[] = "y&+123 "; static const char STR6[] = "123"; static const modseq_t VAL6 = 123; static const char STR7[] = "-123 "; static const char STR8[] = "+123 "; modseq_t val; int c; /* test a valid zero value */ c = wrap_getmodseq(STR1, &val); CU_ASSERT_EQUAL(c, ' '); CU_ASSERT_EQUAL(val, VAL1); /* test a valid value with all the digits */ c = wrap_getmodseq(STR2, &val); CU_ASSERT_EQUAL(c, ' '); CU_ASSERT_EQUAL(val, VAL2); /* test a valid value >32b */ c = wrap_getmodseq(STR3, &val); CU_ASSERT_EQUAL(c, ' '); CU_ASSERT_EQUAL(val, VAL3); // This test fatal()s which we cannot catch for now // /* test a string with too many digits */ // c = wrap_getmodseq(STR3a, &val); // CU_ASSERT_EQUAL(c, EOF); // CU_ASSERT_EQUAL(val, CANARY64); /* test a valid value with a different terminator */ c = wrap_getmodseq(STR4, &val); CU_ASSERT_EQUAL(c, ')'); CU_ASSERT_EQUAL(val, VAL4); /* test an invalid string */ c = wrap_getmodseq(STR5, &val); CU_ASSERT_EQUAL(c, EOF); /* sadly, val is undefined at this point */ /* test the corner case where we encounter EOF * at the end of a valid string of digits */ c = wrap_getmodseq(STR6, &val); CU_ASSERT_EQUAL(c, EOF); CU_ASSERT_EQUAL(val, VAL6); /* test a leading - */ c = wrap_getmodseq(STR7, &val); CU_ASSERT_EQUAL(c, EOF); /* sadly, val is undefined at this point */ /* test a leading + */ c = wrap_getmodseq(STR8, &val); CU_ASSERT_EQUAL(c, EOF); /* sadly, val is undefined at this point */ } /* vim: set ft=c: */ cyrus-imapd-2.5.10/cunit/bitvector.testc0000644000175000017500000002322713001236020015135 00000000000000#include #include "cunit/cunit.h" #include "bitvector.h" static void test_free(void) { bitvector_t bv = BV_INITIALIZER; /* it's ok to call free() even if we never * set or cleared any bits */ bv_free(&bv); } static void test_basic(void) { bitvector_t bv = BV_INITIALIZER; /* read-only operations do not expand the vector */ CU_ASSERT_EQUAL(0, bv.length); CU_ASSERT_EQUAL(0, bv.alloc); CU_ASSERT_EQUAL(0, bv_isset(&bv, 0)); CU_ASSERT_EQUAL(0, bv_isset(&bv, 7)); CU_ASSERT_EQUAL(0, bv_isset(&bv, 23)); CU_ASSERT_EQUAL(0, bv_isset(&bv, 104)); CU_ASSERT_EQUAL(0, bv.length); CU_ASSERT_EQUAL(0, bv.alloc); /* can set bit0 and get it back */ bv_set(&bv, 0); CU_ASSERT_EQUAL(1, bv.length); CU_ASSERT_NOT_EQUAL(0, bv.alloc); CU_ASSERT_EQUAL(1, bv_isset(&bv, 0)); CU_ASSERT_EQUAL(0, bv_isset(&bv, 7)); CU_ASSERT_EQUAL(0, bv_isset(&bv, 23)); CU_ASSERT_EQUAL(0, bv_isset(&bv, 104)); CU_ASSERT_EQUAL(1, bv.length); CU_ASSERT_NOT_EQUAL(0, bv.alloc); /* can set bit23 and get it back */ bv_set(&bv, 23); CU_ASSERT_EQUAL(24, bv.length); CU_ASSERT_NOT_EQUAL(0, bv.alloc); CU_ASSERT_EQUAL(1, bv_isset(&bv, 0)); CU_ASSERT_EQUAL(0, bv_isset(&bv, 7)); CU_ASSERT_EQUAL(1, bv_isset(&bv, 23)); CU_ASSERT_EQUAL(0, bv_isset(&bv, 104)); CU_ASSERT_EQUAL(24, bv.length); CU_ASSERT_NOT_EQUAL(0, bv.alloc); /* can set all bits, does not change length */ bv_setall(&bv); CU_ASSERT_EQUAL(24, bv.length); CU_ASSERT_NOT_EQUAL(0, bv.alloc); CU_ASSERT_EQUAL(1, bv_isset(&bv, 0)); CU_ASSERT_EQUAL(1, bv_isset(&bv, 7)); CU_ASSERT_EQUAL(1, bv_isset(&bv, 23)); CU_ASSERT_EQUAL(0, bv_isset(&bv, 104)); CU_ASSERT_EQUAL(24, bv.length); CU_ASSERT_NOT_EQUAL(0, bv.alloc); /* can clear all bits, does not change length */ bv_clearall(&bv); CU_ASSERT_EQUAL(24, bv.length); CU_ASSERT_NOT_EQUAL(0, bv.alloc); CU_ASSERT_EQUAL(0, bv_isset(&bv, 0)); CU_ASSERT_EQUAL(0, bv_isset(&bv, 7)); CU_ASSERT_EQUAL(0, bv_isset(&bv, 23)); CU_ASSERT_EQUAL(0, bv_isset(&bv, 104)); CU_ASSERT_EQUAL(24, bv.length); CU_ASSERT_NOT_EQUAL(0, bv.alloc); /* can set the size, does not change existing bits */ bv_set(&bv, 0); bv_set(&bv, 23); bv_setsize(&bv, 105); CU_ASSERT_EQUAL(105, bv.length); CU_ASSERT_NOT_EQUAL(0, bv.alloc); CU_ASSERT_EQUAL(1, bv_isset(&bv, 0)); CU_ASSERT_EQUAL(0, bv_isset(&bv, 7)); CU_ASSERT_EQUAL(1, bv_isset(&bv, 23)); CU_ASSERT_EQUAL(0, bv_isset(&bv, 104)); CU_ASSERT_EQUAL(105, bv.length); CU_ASSERT_NOT_EQUAL(0, bv.alloc); /* setall now works on the new size */ bv_setall(&bv); CU_ASSERT_EQUAL(105, bv.length); CU_ASSERT_NOT_EQUAL(0, bv.alloc); CU_ASSERT_EQUAL(1, bv_isset(&bv, 0)); CU_ASSERT_EQUAL(1, bv_isset(&bv, 7)); CU_ASSERT_EQUAL(1, bv_isset(&bv, 23)); CU_ASSERT_EQUAL(1, bv_isset(&bv, 104)); CU_ASSERT_EQUAL(105, bv.length); CU_ASSERT_NOT_EQUAL(0, bv.alloc); bv_free(&bv); } static void test_andeq(void) { bitvector_t a = BV_INITIALIZER; bitvector_t b = BV_INITIALIZER; bv_set(&a, 0); bv_set(&a, 3); CU_ASSERT_EQUAL(4, a.length); CU_ASSERT_EQUAL(1, bv_isset(&a, 0)); CU_ASSERT_EQUAL(1, bv_isset(&a, 3)); bv_set(&b, 0); bv_set(&b, 23); CU_ASSERT_EQUAL(24, b.length); CU_ASSERT_EQUAL(1, bv_isset(&b, 0)); CU_ASSERT_EQUAL(1, bv_isset(&b, 23)); bv_andeq(&a, &b); CU_ASSERT_EQUAL(24, a.length); CU_ASSERT_EQUAL(1, bv_isset(&a, 0)); CU_ASSERT_EQUAL(0, bv_isset(&a, 3)); CU_ASSERT_EQUAL(0, bv_isset(&a, 23)); bv_free(&a); bv_free(&b); } static void test_andeq_noexpand(void) { bitvector_t a = BV_INITIALIZER; bitvector_t b = BV_INITIALIZER; bv_set(&a, 0); bv_set(&a, 23); CU_ASSERT_EQUAL(24, a.length); CU_ASSERT_EQUAL(1, bv_isset(&a, 0)); CU_ASSERT_EQUAL(1, bv_isset(&a, 23)); bv_set(&b, 0); bv_set(&b, 3); bv_set(&b, 7); CU_ASSERT_EQUAL(8, b.length); CU_ASSERT_EQUAL(1, bv_isset(&b, 0)); CU_ASSERT_EQUAL(1, bv_isset(&b, 3)); CU_ASSERT_EQUAL(1, bv_isset(&b, 7)); bv_andeq(&a, &b); CU_ASSERT_EQUAL(24, a.length); CU_ASSERT_EQUAL(1, bv_isset(&a, 0)); CU_ASSERT_EQUAL(0, bv_isset(&a, 3)); CU_ASSERT_EQUAL(0, bv_isset(&a, 7)); CU_ASSERT_EQUAL(0, bv_isset(&a, 23)); bv_free(&a); bv_free(&b); } static void test_oreq(void) { bitvector_t a = BV_INITIALIZER; bitvector_t b = BV_INITIALIZER; bv_set(&a, 0); bv_set(&a, 3); CU_ASSERT_EQUAL(4, a.length); CU_ASSERT_EQUAL(1, bv_isset(&a, 0)); CU_ASSERT_EQUAL(1, bv_isset(&a, 3)); bv_set(&b, 0); bv_set(&b, 23); CU_ASSERT_EQUAL(24, b.length); CU_ASSERT_EQUAL(1, bv_isset(&b, 0)); CU_ASSERT_EQUAL(1, bv_isset(&b, 23)); bv_oreq(&a, &b); CU_ASSERT_EQUAL(24, a.length); CU_ASSERT_EQUAL(1, bv_isset(&a, 0)); CU_ASSERT_EQUAL(1, bv_isset(&a, 3)); CU_ASSERT_EQUAL(1, bv_isset(&a, 23)); bv_free(&a); bv_free(&b); } static void test_oreq_noexpand(void) { bitvector_t a = BV_INITIALIZER; bitvector_t b = BV_INITIALIZER; bv_set(&a, 0); bv_set(&a, 23); CU_ASSERT_EQUAL(24, a.length); CU_ASSERT_EQUAL(1, bv_isset(&a, 0)); CU_ASSERT_EQUAL(1, bv_isset(&a, 23)); bv_set(&b, 0); bv_set(&b, 3); CU_ASSERT_EQUAL(4, b.length); CU_ASSERT_EQUAL(1, bv_isset(&b, 0)); CU_ASSERT_EQUAL(1, bv_isset(&b, 3)); bv_oreq(&a, &b); CU_ASSERT_EQUAL(24, a.length); CU_ASSERT_EQUAL(1, bv_isset(&a, 0)); CU_ASSERT_EQUAL(1, bv_isset(&a, 3)); CU_ASSERT_EQUAL(1, bv_isset(&a, 23)); bv_free(&a); bv_free(&b); } static void test_shrink_expand(void) { bitvector_t bv = BV_INITIALIZER; int i; /* set up some bits */ bv_setsize(&bv, 59); bv_setall(&bv); CU_ASSERT_EQUAL(59, bv.length); CU_ASSERT_EQUAL(1, bv_isset(&bv, 0)); CU_ASSERT_EQUAL(1, bv_isset(&bv, 3)); CU_ASSERT_EQUAL(1, bv_isset(&bv, 4)); CU_ASSERT_EQUAL(1, bv_isset(&bv, 23)); CU_ASSERT_EQUAL(1, bv_isset(&bv, 58)); for (i = 55 ; i >= 4 ; i--) { /* explicitly shrink the vector - bits off * the end are now gone */ bv_setsize(&bv, i); CU_ASSERT_EQUAL(i, bv.length); CU_ASSERT_EQUAL(1, bv_isset(&bv, i-2)); CU_ASSERT_EQUAL(1, bv_isset(&bv, i-1)); CU_ASSERT_EQUAL(0, bv_isset(&bv, i)); CU_ASSERT_EQUAL(0, bv_isset(&bv, i+1)); CU_ASSERT_EQUAL(0, bv_isset(&bv, i+2)); /* implicitly expand the vector - old bits * do not come back */ bv_set(&bv, 58); CU_ASSERT_EQUAL(59, bv.length); CU_ASSERT_EQUAL(1, bv_isset(&bv, 0)); CU_ASSERT_EQUAL(1, bv_isset(&bv, i-2)); CU_ASSERT_EQUAL(1, bv_isset(&bv, i-1)); CU_ASSERT_EQUAL(0, bv_isset(&bv, i)); CU_ASSERT_EQUAL(0, bv_isset(&bv, i+1)); CU_ASSERT_EQUAL(0, bv_isset(&bv, i+2)); bv_setall(&bv); } bv_free(&bv); } static void test_copy(void) { bitvector_t dst = BV_INITIALIZER; bitvector_t src = BV_INITIALIZER; /* test copying of empty sets */ bv_copy(&dst, &src); CU_ASSERT_EQUAL(0, dst.length); /* set up some bits */ bv_set(&src, 0); bv_set(&src, 11); bv_set(&src, 23); CU_ASSERT_EQUAL(24, src.length); CU_ASSERT_EQUAL(1, bv_isset(&src, 0)); CU_ASSERT_EQUAL(0, bv_isset(&src, 1)); CU_ASSERT_EQUAL(0, bv_isset(&src, 10)); CU_ASSERT_EQUAL(1, bv_isset(&src, 11)); CU_ASSERT_EQUAL(0, bv_isset(&src, 12)); CU_ASSERT_EQUAL(0, bv_isset(&src, 22)); CU_ASSERT_EQUAL(1, bv_isset(&src, 23)); CU_ASSERT_EQUAL(0, bv_isset(&src, 24)); /* copy and check the bits are now in both */ bv_copy(&dst, &src); CU_ASSERT_EQUAL(24, dst.length); CU_ASSERT_EQUAL(1, bv_isset(&dst, 0)); CU_ASSERT_EQUAL(0, bv_isset(&dst, 1)); CU_ASSERT_EQUAL(0, bv_isset(&dst, 10)); CU_ASSERT_EQUAL(1, bv_isset(&dst, 11)); CU_ASSERT_EQUAL(0, bv_isset(&dst, 12)); CU_ASSERT_EQUAL(0, bv_isset(&dst, 22)); CU_ASSERT_EQUAL(1, bv_isset(&dst, 23)); CU_ASSERT_EQUAL(0, bv_isset(&dst, 24)); CU_ASSERT_EQUAL(24, src.length); CU_ASSERT_EQUAL(1, bv_isset(&src, 0)); CU_ASSERT_EQUAL(0, bv_isset(&src, 1)); CU_ASSERT_EQUAL(0, bv_isset(&src, 10)); CU_ASSERT_EQUAL(1, bv_isset(&src, 11)); CU_ASSERT_EQUAL(0, bv_isset(&src, 12)); CU_ASSERT_EQUAL(0, bv_isset(&src, 22)); CU_ASSERT_EQUAL(1, bv_isset(&src, 23)); CU_ASSERT_EQUAL(0, bv_isset(&src, 24)); bv_free(&dst); bv_free(&src); } static void test_cstring(void) { bitvector_t bv = BV_INITIALIZER; char *s; /* test empty set */ s = bv_cstring(&bv); CU_ASSERT_STRING_EQUAL(s, "[]"); free(s); /* set a bit */ bv_set(&bv, 11); s = bv_cstring(&bv); CU_ASSERT_STRING_EQUAL(s, "0008[11]"); free(s); /* set another bit, not adjacent */ bv_set(&bv, 3); s = bv_cstring(&bv); CU_ASSERT_STRING_EQUAL(s, "0808[3,11]"); free(s); /* set another bit, adjacent */ bv_clear(&bv, 3); bv_set(&bv, 10); s = bv_cstring(&bv); CU_ASSERT_STRING_EQUAL(s, "000c[10-11]"); free(s); /* set more bits, adjacent */ bv_set(&bv, 9); bv_set(&bv, 12); s = bv_cstring(&bv); CU_ASSERT_STRING_EQUAL(s, "001e[9-12]"); free(s); /* set a bit at the start */ bv_clearall(&bv); bv_set(&bv, 0); s = bv_cstring(&bv); CU_ASSERT_STRING_EQUAL(s, "0100[0]"); free(s); /* set another bit adjacent to the start */ bv_set(&bv, 1); s = bv_cstring(&bv); CU_ASSERT_STRING_EQUAL(s, "0300[0-1]"); free(s); /* set every 2nd bit */ bv_clearall(&bv); bv_set(&bv, 1); bv_set(&bv, 3); bv_set(&bv, 5); bv_set(&bv, 7); bv_set(&bv, 9); bv_set(&bv, 11); s = bv_cstring(&bv); CU_ASSERT_STRING_EQUAL(s, "aa0a[1,3,5,7,9,11]"); free(s); bv_free(&bv); } /* vim: set ft=c: */ cyrus-imapd-2.5.10/cunit/cunit.pl0000755000175000017500000007563313001236020013562 00000000000000#!/usr/bin/perl # # Build time front end for CUnit # # Copyright (c) 1994-2010 Carnegie Mellon University. All rights reserved. # # Redistribution and use in source and binary forms, with or without # modification, are permitted provided that the following conditions # are met: # # 1. Redistributions of source code must retain the above copyright # notice, this list of conditions and the following disclaimer. # # 2. Redistributions in binary form must reproduce the above copyright # notice, this list of conditions and the following disclaimer in # the documentation and/or other materials provided with the # distribution. # # 3. The name "Carnegie Mellon University" must not be used to # endorse or promote products derived from this software without # prior written permission. For permission or any legal # details, please contact # Carnegie Mellon University # Center for Technology Transfer and Enterprise Creation # 4615 Forbes Avenue # Suite 302 # Pittsburgh, PA 15213 # (412) 268-7393, fax: (412) 268-7395 # innovation@andrew.cmu.edu # # 4. Redistributions of any form whatsoever must retain the following # acknowledgment: # "This product includes software developed by Computing Services # at Carnegie Mellon University (http://www.cmu.edu/computing/)." # # CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO # THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY # AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE # FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES # WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN # AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING # OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. # use strict; use warnings; use Cwd; use File::Basename; use File::Compare; my $unitdir = dirname($0); my $project; my $DEFAULT_PROJECT = "default.cunit"; my @suites; my @libraries; my $here = getcwd(); my $verbose = 0; # # Emit a message if we're in verbose mode # Args: void # Returns: void # sub vmsg(@) { print STDERR "## ". join(' ', @_) . "\n" if ($verbose); } # # Given an absolute path, construct and return the simplest possible # absolute path that points to the same file, in particular by flattening # ".." components. Similar to the libc realpath() function but without # the behaviour of looking up symlinks. # Args: absolute pathname # Returns: absolute pathname # sub path_sanitise($) { my ($path) = @_; my @comps; die "$path: not an absolute path" unless ($path =~ m/^\//); foreach my $comp (split('/', $path)) { if ($comp eq "." || $comp eq "") { next; } elsif ($comp eq "..") { # Note: will silently fail if we try to pop more # components than we've added, which is exactly # the right behaviour for trying to walk past # the root directory with ".."s. pop(@comps); } else { push(@comps, $comp); } } return "/" . join("/",@comps); } # # Given a (sanitised) absolute path, calculate and return a path # relative to the given directory. # Args: absolute pathname, base directory # Returns: relative pathname # sub path_relativise($$) { my ($path, $base) = @_; my @pathcomps; my @basecomps; die "$path: not an absolute path" unless ($path =~ m/^\//); @pathcomps = split("/", $path); @basecomps = split("/", $base); # Remove the components of the common # ancestor of both paths while (defined $pathcomps[0] && defined $basecomps[0] && $pathcomps[0] eq $basecomps[0]) { shift(@pathcomps); shift(@basecomps); } # Prepend enough ".."s to the path # to reach the common ancestor while (defined $basecomps[0]) { shift(@basecomps); unshift(@pathcomps, ".."); } return join("/", @pathcomps); } # # Return the initial common subset of two sanitised paths # Args: absolute path, absolute path # Returns: absolute path # sub path_common($$) { my ($path1, $path2) = @_; my @path1comps; my @path2comps; my @common; die "$path1: not an absolute path" unless ($path1 =~ m/^\//); die "$path2: not an absolute path" unless ($path2 =~ m/^\//); @path1comps = split("/", $path1); @path2comps = split("/", $path2); # Remove the components of the common # ancestor of both paths while (defined $path1comps[0] && defined $path2comps[0] && $path1comps[0] eq $path2comps[0]) { push(@common, $path1comps[0]); shift(@path1comps); shift(@path2comps); } return join("/", @common); } # # Given either a relative or absolute path, # calculate and return both. # Args: pathname, directory to be relative to # Returns: absolute pathname, relative pathname # sub path_absrel($$) { my ($path, $basedir) = @_; my ($abspath, $relpath); if ($path =~ m/^\//) { # Given an absolute path $abspath = $path; # Calculate the relative path from the absolute path. # Note, this only gives a true relative path if we're # in the same directory. if (substr($abspath,0,length($basedir)+1) eq "$basedir/") { $relpath = substr($abspath,length($basedir)+1); } else { # Fallback $relpath = $abspath; } } else { # Given a relative path $relpath = $path; # Calculate the absolute path $abspath = "$basedir/$relpath"; } return (path_sanitise($abspath), $relpath); } # # Given a pathname of the C source file of a suite, return # the name by which the suite will be known to CUnit. # Args: absolute pathname # Returns: name # sub suite_path_to_name($) { my ($path) = @_; # Generate a path from the "top" directory down to this # C source file. The "top" directory should be something # like @top_srcdir@ in autoconf speak, but we have to # infer it from the location of the project file. my ($projdir, $whatever) = path_absrel($project, $here); my $topdir = path_common($path, $projdir); vmsg("inferred top_srcdir is \"$topdir\""); my $name = path_relativise($path, $topdir); $name =~ s/\.(testc|c)$//; $name =~ s/\/test_?/\//g; $name =~ s/_?test\//\//g; $name =~ s/\/+/\//g; $name =~ s/^\/+/\//; return $name; } # # Given a pathname (relative or absolute, doesn't matter) # of the C source file of a suite, return the relative # path of the wrapper C source file. This is always in # the basedir. # Args: pathname # Returns: pathname # sub suite_path_to_wrapper($) { my ($path) = @_; return $path . "-cunit.c"; } # # Given a pathname (relative or absolute, doesn't matter) # of the C source file of a suite, return the relative # path of the object file. This is always in the basedir. # Args: pathname # Returns: pathname # sub suite_path_to_object($) { my ($path) = @_; my $obj = basename($path); $obj =~ s/^/.cunit-/; $obj =~ s/\.c$/.o/; return $obj; } # # Given a suite name return the name of a C variable which will # be used to name the CU_SuiteInfo object. Only needed because # we allow test names to contain characters which are not legal # in C symbols, notably '/'. # Args: string name # Returns: string symbol name # sub suite_name_to_var($) { my ($name) = @_; $name =~ s/\W/_/g; $name =~ s/_+/_/g; $name = "__cunit_suite_" . $name; return $name; } # # Create a new suite hash. # # Note that we maintain the basedirectory and relative path # separately instead of taking the easy route of smooshing # them together. This allows us to handle the case where # the C source file for a suite is in a subdirectory relative # to the Makefile which is invoking us e.g. test/splunk.c # rather than test_splunk.c, without stuffing up and putting # the wrapper, object file, and archive in places where we # won't be able to find them again later. # # Args: relative path, directory the path is relative to. # Returns: ref to new suite hash # sub suite_new($$) { my ($relpath, $basedir) = @_; my ($abspath, $whatever) = path_absrel($relpath, $basedir); my $suite = { basedir => $basedir, relpath => $relpath, abspath => $abspath, name => suite_path_to_name($abspath), wrap => suite_path_to_wrapper($relpath), object => suite_path_to_object($relpath), setupfn => undef, teardownfn => undef, params => [], tests => [] }; $suite->{suitevar} = suite_name_to_var($suite->{name}); return $suite; } # # Compare two suite hashes; suitable for use as a sort function. # Args: ref to suite hash, ref to suite hash # Returns: 0 if the same, <0 or >0 if not the same. # sub suite_cmp($$) { my ($s1, $s2) = @_; return ($s1->{abspath} cmp $s2->{abspath}); } # # Return the linker argument for a suite hash, adjusted # to be relative to the current working directory if # appropriate. # Args: ref to suite hash # Returns: string linker argument # sub suite_get_linkable($) { my ($suite) = @_; return path_relativise($suite->{basedir} . "/" . $suite->{object}, $here); } # Any of these (case insensitive) names can be used as the setup function my %setup_names = ( 'setup' => 1, # standard name from Kent Beck's original paper 'set_up' => 1, # standard, C style with underscore 'init' => 1, # allowed in older versions of cunit.pl 'before' => 1, # like jUnit's @Before annotation ); # Any of these (case insensitive) names can be used as the teardown function my %teardown_names = ( 'teardown' => 1, # standard name from Kent Beck's original paper 'tear_down' => 1, # standard, C style with underscore 'cleanup' => 1, # allowed in older versions of cunit.pl 'after' => 1, # like jUnit's @After annotation ); # # Helper for suite_scan_for_tests # sub suite_found_function { my ($suite, $rtype, $fn) = @_; if (defined $teardown_names{lc($fn)} && (!defined($rtype) || $rtype eq 'int')) { vmsg("Found teardown function"); die "$suite->{abspath}: Too many teardown functions: " . "both \"$fn\" and \"$suite->{teardownfn}\" found" if defined($suite->{teardownfn}); $suite->{teardownfn} = $fn; } elsif (defined $setup_names{lc($fn)} && (!defined($rtype) || $rtype eq 'int')) { vmsg("Found setup function"); die "$suite->{abspath}: too many setup functions: both " . "\"$fn\" and \"$suite->{setupfn}\" found" if defined($suite->{setupfn}); $suite->{setupfn} = $fn; } else { my ($name) = ($fn =~ m/^test_*(\w+)/); if (defined $name && (!defined($rtype) || $rtype eq 'void')) { vmsg("Found test function \"$fn\" -> name \"$name\""); push(@{$suite->{tests}}, { name => $name, func => $fn }); } } } # # Helper for suite_scan_for_tests # sub suite_found_param { my ($suite, $param) = @_; die "$suite->{abspath}: parameter \"$param\" declared " . "more than once" if grep { $_ eq $param } @{$suite->{params}}; vmsg("Found parameter \"$param\""); # Note: we preserve the order of discovery in the # source file to provide a predictable order of # walking the parameter space at runtime. push (@{$suite->{params}}, $param); } # # Scan the C source file of the given suite for function # definitions of one of the signatures: # # [static] void test_WHATEVER(void) # we map this to a CUnit test called "WHATEVER" # # [static] void init(void) # we use this as the suite's initialisation function # # [static] void cleanup(void) # we use this as the suite's cleanup function # # The names of any such functions found are added to the # suite hash, using {setupfn}, {teardownfn} and {tests}. # # Also scan for variable declarations of the form # # [static] char * foo = CUNIT_PARAM("stringliteral"); # # and make them a parameter for the containing test suite. # # Args: ref to suite hash # Returns: number of tests found # sub suite_scan_for_tests($) { my ($suite) = @_; my $state = 0; my $fn; my $rtype; open FH,'<',$suite->{abspath} or die "Can't open $suite->{abspath} for reading: $!"; while () { chomp; if ($state == 0) { # Detect definitions of functions with the signature # void func(void), static void func(void), int func(void), # and static int func(void). ($rtype, $fn) = m/^(?:static\s+)(int|void)\s+(\w+)\s*\(\s*void\s*\)\s*$/; if (defined $fn) { suite_found_function($suite, $rtype, $fn); next; } ($fn) = m/^(\w+)\s*\(\s*void\s*\)\s*$/; if (defined $fn) { # old fashioned function declarations with no return type suite_found_function($suite, undef, $fn); next; } ($rtype) = m/^(?:static\s+)(int|void)\s*$/; if (defined $rtype) { $state = 1; next; } my ($param) = m/^(?:static\s+)char\s*\*\s*(\w+)\s*=\s*CUNIT_PARAM\s*\(/; if (defined $param) { suite_found_param($suite, $param); next; } } elsif ($state == 1) { # $rtype is left over from previous line ($fn) = m/^(\w+)\s*\(\s*void\s*\)\s*$/; if (defined $fn) { # split-line declaration of the form: # static void # test_foo(void) suite_found_function($suite, $rtype, $fn); next; } $state = 0; } } close FH; return scalar(@{$suite->{tests}}); } # # Return the subset of @suites located in or below the current directory. # Args: void # Returns: list refs to suite hash # sub suites_for_here() { my $heresl = "$here/"; my $l = length($heresl); return grep { substr($_->{abspath},0,$l) eq $heresl } @suites; } # # Return the suite which corresponds to the given C source file. # Args: C source file name # Returns: ref to suite hash, or undef if not found # sub suite_find($) { my ($path) = @_; foreach my $suite (@suites) { return $suite if ($suite->{relpath} eq $path); } return undef; } # # Create a new library hash. # # Note that we maintain the basedirectory and relative path # separately, like for suites, but only after partially # parsing the argument to see if comprises or contains # a path. # # Args: linker argument, directory which any path is relative to. # Returns: ref to new library hash # sub library_new($$) { my ($arg, $basedir) = @_; my $abspath; my $relpath; if ($arg =~ m/\.[oa]$/) { ($abspath, $relpath) = path_absrel($arg, $basedir); } elsif (my ($dir) = ($arg =~ m/^-L(.+)$/)) { ($abspath, $relpath) = path_absrel($dir, $basedir); } elsif (!($arg =~ m/^-[lBW]/)) { die "Don't know what to do with library \"$arg\""; } my $lib = { arg => $arg, basedir => $basedir, relpath => $relpath, # might be undef abspath => $abspath, # might be undef }; return $lib; } # # Compare two library hashes; suitable for use as a sort function. # Args: ref to library hash, ref to library hash # Returns: 0 if the same, <0 or >0 if not the same. # sub library_cmp($$) { my ($l1, $l2) = @_; return ($l1->{basedir} cmp $l2->{basedir} || $l1->{arg} cmp $l2->{arg}); } # # Return the linker argument for a library hash, adjusted # to be relative to the current working directory if # appropriate. # Args: ref to library hash # Returns: string linker argument # sub library_get_linkable($) { my ($lib) = @_; my $arg = $lib->{arg}; if ($arg =~ m/\.[oa]$/) { my ($abspath, $relpath) = path_absrel($arg, $lib->{basedir}); $arg = path_relativise($abspath, $here); } elsif (my ($dir) = ($arg =~ m/^-L(.+)$/)) { my ($abspath, $relpath) = path_absrel($dir, $lib->{basedir}); $arg = "-L" . path_relativise($abspath, $here); } return $arg; } # # Atomic rewrite: atomic update of file contents. # # We use the standard trick for POSIX filesystems of writing all # the data to a new file in the same directory, then renaming # (relying on the atomicity of the rename() system call). This # ensures that no process ever sees a partially updated version # of the file, without the use of POSIX file locking. # # The atomic_rewrite_begin() call just returns a new filename to # write to. Call this first, then open the returned filename # and write to it, then call atomic_rewrite_end() with your # original filename. # # Note: this relies on the PIDs being unique to avoid a race # between two writers, which is true on local filesystems. If # we were doing this properly we would use one of the library # routines for generating a temporary filename and opening it # atomically, then return a ref to a filehandle. # # Args: filename # Returns: temporary filename to actually write to. # sub atomic_rewrite_begin($) { my ($real) = @_; return "$real.$$.TMP"; } # # The second half of the atomic rewite; performs the comparison # of file contents and the rename. # Args: filename (the original one, not the temporary file) # Returns: 1 if the file was changed, 0 if not. # sub atomic_rewrite_end($) { my ($real) = @_; my $tmp = "$real.$$.TMP"; my $different = 1; if ( -f $real ) { $different = compare($real, $tmp); } if ($different == 1) { rename($tmp, $real) or die "Cannot rename $tmp to $real: $!"; vmsg("rewrote $real"); return 1; } else { unlink($tmp) or die "Cannot remove $tmp: $!"; return 0; } } # # Generate a C file which is used to wrap the C source file containing # a suite. The wrapper #includes the original C code and defines # CUnit data structures which describe the suite and all it's tests. # Uses atomic rewrite. # Args: ref to suite hash # Returns: void # sub suite_generate_wrap($) { my ($suite) = @_; my $file = atomic_rewrite_begin($suite->{wrap}); my $cfile = $suite->{abspath}; open WRAP,'>',$file or die "Cannot open $file for writing: $!"; print WRAP "/* Automatically generated by cunit.pl, do not edit */\n"; print WRAP "#include \"$suite->{relpath}\"\n"; print WRAP "#ifdef HAVE_CONFIG_H\n"; print WRAP "#include \n"; print WRAP "#endif\n"; if (scalar @{$suite->{params}}) { print WRAP "static struct cunit_param params[] = {\n"; map { print WRAP "__CUNIT_DECLARE_PARAM($_),\n"; } @{$suite->{params}}; print WRAP "__CUNIT_LAST_PARAM };\n"; } my $setupfn = $suite->{setupfn}; my $teardownfn = $suite->{teardownfn}; foreach my $test (@{$suite->{tests}}) { my $fn = $test->{func}; print WRAP "static void __cunit_$fn(void)\n"; print WRAP "{\n"; print WRAP "__cunit_params_begin(params);\ndo {\n" if (scalar @{$suite->{params}}); print WRAP " CU_syslogMatchReset();\n"; print WRAP " if (__cunit_wrap_fixture(" . "\"$cfile:$setupfn\", $setupfn)) " . "CU_FAIL_FATAL(\"$setupfn failed\");\n" if defined $setupfn; print WRAP " __cunit_wrap_test(\"$cfile:$fn\", $fn);\n"; print WRAP " if (__cunit_wrap_fixture(" . "\"$cfile:$teardownfn\", $teardownfn)) " . "CU_FAIL_FATAL(\"$teardownfn failed\");\n" if defined $teardownfn; print WRAP "} while (__cunit_params_next(params));\n__cunit_params_end();\n" if (scalar @{$suite->{params}}); print WRAP "}\n"; } print WRAP "static CU_TestInfo _tests[] = {\n"; foreach my $test (@{$suite->{tests}}) { print WRAP " { \"$test->{name}\", __cunit_$test->{func} },\n"; } print WRAP " CU_TEST_INFO_NULL\n};\n"; print WRAP "#ifdef HAVE_CU_SETUPFUNC\n"; print WRAP "const CU_SuiteInfo $suite->{suitevar} = {" . "\"$suite->{name}\", NULL, NULL, NULL, NULL, _tests};\n"; print WRAP "#else\n"; print WRAP "const CU_SuiteInfo $suite->{suitevar} = {" . "\"$suite->{name}\", NULL, NULL, _tests};\n"; print WRAP "#endif\n"; close WRAP; atomic_rewrite_end($suite->{wrap}); } # # Load the $project file into the arrays @suites and @libraries. # Args: void # Returns: void # sub project_load() { open PROJ,'<',$project or return; # TODO: should be silent on ENOENT only # TODO: should check file version header while () { chomp; next if (m/^#/); # skip comments my @a = split; if ($a[0] eq 'suite') { die "Invalid format" unless scalar(@a) == 3; push(@suites, suite_new($a[1], $a[2])); } elsif ($a[0] eq 'library') { die "Invalid format" unless scalar(@a) == 3; push(@libraries, library_new($a[1], $a[2])); } } close PROJ; vmsg("loaded project $project"); } # # Add a suite to @suites, if it's not already present. # Args: ref to a suite hash # Returns: void # sub project_add_suite($) { my ($suite) = @_; return if grep { !suite_cmp($_,$suite) } @suites; # # Note: appending is an important semantic. It ensures # that the order of suites in the CUnit run matches the # order in which test source is specified, in SUBDIRS # in the top-level Makefile and then in TESTSOURCES # in each Makefile below that. # vmsg("adding suite $suite->{relpath} $suite->{basedir}"); push(@suites, $suite); } # # Add a library to the @libraries if it's not already present. # Args: library string # Returns: void # sub project_add_library($) { my ($lib) = @_; @libraries = grep { library_cmp($_, $lib) } @libraries; vmsg("adding library $lib->{arg} $lib->{basedir}"); push(@libraries, $lib); } # # Save the @suites and @libraries arrays to the $project file # Uses atomic rewrite. # Args: void # Returns: void # sub project_save() { my $file = atomic_rewrite_begin($project); open PROJ,'>',$file or die "Failed to open $file for writing: $!"; print PROJ "#CUnitProject-1.0\n"; foreach my $suite (@suites) { print PROJ "suite $suite->{relpath} $suite->{basedir}\n"; } foreach my $lib (@libraries) { print PROJ "library $lib->{arg} $lib->{basedir}\n"; } close PROJ; atomic_rewrite_end($project); } # # Add the named test sources (which are C source files) to the # project, and rewrite the project file. Re-adding is deliberately # a harmless no-op; in particular the project file is not written # if it's contents would not change. # sub add_sources(@) { my (@args) = @_; project_load(); foreach my $path (@args) { die "$path: not a C source file" unless ($path =~ m/\.(test)?(c|C|cc|cxx|c\+\+)$/); project_add_suite(suite_new($path, $here)); } project_save(); } # # Add the named libraries (which may be object files, lib.a archives, # or -llibrary -Ldirectory -Bfoo -Wl,-foo ldflags, to the project, # and rewrite the project file. Re-adding is deliberately a harmless # no-op; in particular the project file is not written if it's contents # would not change. # sub add_libraries(@) { my (@args) = @_; project_load(); foreach my $arg (@args) { project_add_library(library_new($arg, $here)); } project_save(); } # # Generate a wrapper C source file for each of the suites # specified by their C source files on the commandline. # sub generate_wrapper(@) { my @args = @_; my $nfails = 0; project_load(); foreach my $a (@args) { my $suite = suite_find($a); if (!defined $suite) { print STDERR "$a: unknown suite, did you use --add-sources?\n"; $nfails++; next; } my $ntests = suite_scan_for_tests($suite); if ($ntests == 0) { vmsg("No tests in $suite->{relpath}"); if ( -f $suite->{wrap}) { vmsg("Removing stale $suite->{wrap}"); unlink($suite->wrap) or die "Cannot unlink $suite->{wrap}: $!"; } next; } suite_generate_wrap($suite); } exit 1 if ($nfails > 0); } # # Emit to the MAKE filehandle, a makefile fragment which contains # variable definitions which list the objects/libraries/linkflags # for the final link step, and which list the objects/libraries to # depend on for the final link step, assuming we want all the tests # in all the suites mentioned in the project. We rely on the calling # Makefile to define the actual link rule. # # Note that the order and uniqueness of @linkables matters # but not in obvious ways, and may interact in interesting # ways with weird linker switches. We try to optimise by # listing each individual linkable exactly once, so it's # only searched once. This will break if the libraries # have circular dependencies, so don't do stupid things # like that! To preserve link order semantics, the *last* # instance of each library seen is used. # # We should probably disable this optimisation if fancy # order-dependent options like -Bstatic were given. Also, # we don't handle GNU linker groups very well either. # # Args: void # Returns: void # sub emit_final_makefile_bits() { my ($makefile) = @_; my %seen; my @all_linkables; my @linkables; my @deplibs; push(@all_linkables, map { suite_get_linkable($_) } @suites ); push(@all_linkables, map { library_get_linkable($_) } @libraries ); map { $seen{$_}++ } @all_linkables; foreach my $arg (@all_linkables) { push (@linkables, $arg) if ($seen{$arg} == 1); $seen{$arg}--; } @deplibs = grep { m/\.[oa]$/ } @linkables; print MAKE "CUNIT_OBJECTS = " . join(' ', @linkables) . "\n"; print MAKE "CUNIT_DEPLIBS = " . join(' ', @deplibs) . "\n"; } # # Emit to the MAKE filehandle, a makefile fragment which contains # rules to build wrappers around each test source in this directory # or it's descendants, and to build object files from those wrappers. # # Args: name of output makefile # Returns: void # sub emit_partial_makefile_bits($) { my ($makefile) = @_; my $cunit; $cunit = "$0"; $cunit .= " --project $project" unless ($project eq $DEFAULT_PROJECT); print MAKE "CUNIT_TEST_WRAPS ="; foreach my $suite (suites_for_here()) { print MAKE " $suite->{wrap}"; } print MAKE "\n"; print MAKE "CUNIT_TEST_OBJS ="; foreach my $suite (suites_for_here()) { print MAKE " $suite->{object}"; } print MAKE "\n"; foreach my $suite (suites_for_here()) { print MAKE "$suite->{object}: $suite->{wrap} $suite->{relpath}\n"; } print MAKE "\n"; foreach my $suite (suites_for_here()) { print MAKE "$suite->{wrap}: $suite->{relpath}\n"; print MAKE "\t$cunit --generate-wrapper \$<\n"; } print MAKE "\n"; print MAKE "clean::\n"; print MAKE "\t\$(RM) -f \$(CUNIT_TEST_WRAPS) \$(CUNIT_TEST_OBJS) $makefile\n"; print MAKE "\n"; } # # Generate a makefile fragment which contains rules to build # wrappers around each test source in this directory or it's # descendants, and to build object files from those wrappers. # sub generate_partial_makefile(@) { my ($makefile) = @_; project_load(); my $file = atomic_rewrite_begin($makefile); open MAKE,'>',$file or die "Cannot open $file for writing: $!"; print MAKE "# Automatically generated by cunit.pl, do not edit\n"; print MAKE "\n"; emit_partial_makefile_bits($makefile); print MAKE "check:: \$(CUNIT_TEST_OBJS)\n"; print MAKE "\n"; atomic_rewrite_end($makefile); } # # Generate a makefile fragment which contains variable definitions # which list the objects/libraries/linkflags for the final link # step, and which list the objects/libraries to depend on for # the final link step, assuming we want all the tests in all the # suites mentioned in the project. We rely on the calling Makefile # to define the actual link rule. # sub generate_final_makefile(@) { my ($makefile) = @_; project_load(); my $file = atomic_rewrite_begin($makefile); open MAKE,'>',$file or die "Cannot open $file for writing: $!"; print MAKE "# Automatically generated by cunit.pl, do not edit\n"; print MAKE "\n"; emit_final_makefile_bits(); atomic_rewrite_end($makefile); } # # Generate a combined makefile fragment which does both the # partial and final stages. # sub generate_makefile(@) { my ($makefile) = @_; project_load(); my $file = atomic_rewrite_begin($makefile); open MAKE,'>',$file or die "Cannot open $file for writing: $!"; print MAKE "# Automatically generated by cunit.pl, do not edit\n"; print MAKE "\n"; emit_partial_makefile_bits($makefile); emit_final_makefile_bits(); atomic_rewrite_end($makefile); } # # Generate a file containing a C function register_cunit_suites() # which registers all the CUnit suites in the project. # sub generate_register_function(@) { my ($cfile) = @_; project_load(); my $file = atomic_rewrite_begin($cfile); open CFILE,'>',$file or die "Cannot open $file for writing: $!"; print CFILE "/* Automatically generated by cunit.pl, do not edit */\n"; foreach my $suite (@suites) { print CFILE "extern const CU_SuiteInfo $suite->{suitevar};\n"; } print CFILE "void register_cunit_suites(void)\n"; print CFILE "{\n"; print CFILE " CU_SuiteInfo ss[2] = { CU_SUITE_INFO_NULL, CU_SUITE_INFO_NULL };\n"; foreach my $suite (@suites) { print CFILE " ss[0] = $suite->{suitevar};\n"; print CFILE " CU_register_suites(ss);\n"; } print CFILE "}\n"; atomic_rewrite_end($cfile); } # # Parse arguments # sub usage() { print STDERR "Usage: cunit.pl [flags] --add-sources file.c ...\n"; print STDERR "Usage: cunit.pl [flags] --add-libraries [-llib|-Ldir] ...\n"; print STDERR " cunit.pl [flags] --generate-partial-makefile foo.mk\n"; print STDERR " cunit.pl [flags] --generate-wrapper testfoo.c\n"; print STDERR " cunit.pl [flags] --generate-final-makefile foo.mk\n"; print STDERR " cunit.pl [flags] --generate-makefile foo.mk\n"; print STDERR " cunit.pl [flags] --emit-register-function foo.c\n"; print STDERR "\n"; print STDERR "flags include:\n"; print STDERR " --project PROJ, -p PROJ specify the project file (default is \"$DEFAULT_PROJECT\")\n"; print STDERR " --verbose, -v be more verbose\n"; exit 1; } my $modefn = undef; my @args; my $want_args = 0; while (my $a = shift) { if ($a eq '--project' || $a eq '-p') { $project = shift; usage() unless defined $project; } elsif ($a eq '--add-sources' || $a eq '-a') { $modefn = \&add_sources; $want_args = 1; } elsif ($a eq '--add-libraries' || $a eq '-A') { $modefn = \&add_libraries; $want_args = 2; } elsif ($a eq '--generate-partial-makefile' || $a eq '-p') { $modefn = \&generate_partial_makefile; my $makefile = shift; usage() unless defined $makefile; push(@args, $makefile); } elsif ($a eq '--generate-final-makefile' || $a eq '-f') { $modefn = \&generate_final_makefile; my $makefile = shift; usage() unless defined $makefile; push(@args, $makefile); } elsif ($a eq '--generate-makefile' || $a eq '-m') { $modefn = \&generate_makefile; my $makefile = shift; usage() unless defined $makefile; push(@args, $makefile); } elsif ($a eq '--generate-wrapper' || $a eq '-w') { $modefn = \&generate_wrapper; $want_args = 1; } elsif ($a eq '--generate-register-function' || $a eq '-r') { $modefn = \&generate_register_function; my $cfile = shift; usage() unless defined $cfile; push(@args, $cfile); } elsif ($a eq '--verbose' || $a eq '-v') { $verbose++; } elsif ($a =~ /^-[lLBW]/ && $want_args == 2) { push(@args, $a); } elsif ($a =~ /^-/) { usage(); } elsif ($want_args) { push(@args, $a); } else { usage(); } } if (!defined $project) { $project = $DEFAULT_PROJECT; } elsif ( -d $project) { $project = "$project/$DEFAULT_PROJECT"; } # Actually run the selected mode usage() unless defined $modefn; $modefn->(@args); cyrus-imapd-2.5.10/cunit/times.testc0000644000175000017500000003407513001236020014260 00000000000000/* test_time.c -- regression test for cyrus time routines * * Copyright (c) 2010 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include #ifdef HAVE_UNISTD_H #include #endif #include #include #include #include #include "cunit/cunit.h" #include "times.h" #define TZ_UTC "UTC+00" #define TZ_NEWYORK "EST+05" #define TZ_MELBOURNE "AEST-11" #define UNINIT_TIMET ((time_t)0xdeadbeef) #define MAX_TZ_STACK 5 static int n_tz_stack = 0; static char *tz_stack[MAX_TZ_STACK]; static inline void xxputenv(char *s, const char *f) { if (verbose > 1) fprintf(stderr, "\n%s:putenv(\"%s\")\n", f, s); putenv(s); } #define putenv(s) xxputenv((s), __FUNCTION__) static char *stash_tz(const char *tz) { char *s = malloc(4+(tz == NULL ? 0 : strlen(tz))); assert(s); sprintf(s, "TZ=%s", (tz == NULL ? "" : tz)); assert(n_tz_stack < MAX_TZ_STACK-1); return tz_stack[n_tz_stack++] = s; } static void push_tz(const char *tz) { if (n_tz_stack == 0) stash_tz(getenv("TZ")); putenv(stash_tz(tz)); tzset(); } static void pop_tz(void) { char *old; assert(n_tz_stack > 1); old = tz_stack[--n_tz_stack]; putenv(tz_stack[n_tz_stack-1]); tzset(); free(old); } static int set_up(void) { /* * Ensure that libc's idea of which timezone we're in is * predictable, in case any of the tests here depend on * it. The timezone is faked up to simulate Australian * Eastern Standard time, only because I live there. */ push_tz(TZ_MELBOURNE); return 0; } static int tear_down(void) { pop_tz(); if (n_tz_stack != 1) return -1; return 0; } static void test_rfc3501(void) { time_t t; int r; /* Well-formed full RFC3501 format with 2-digit day * "dd-mmm-yyyy HH:MM:SS zzzzz" */ t = UNINIT_TIMET; r = time_from_rfc3501("15-Oct-2010 03:19:52 +1100", &t); CU_ASSERT_EQUAL(r, 26); CU_ASSERT_EQUAL(t, 1287073192); /* Well-formed full RFC3501 format with 1-digit day * " d-mmm-yyyy HH:MM:SS zzzzz" */ t = UNINIT_TIMET; r = time_from_rfc3501(" 5-Oct-2010 03:19:52 +1100", &t); CU_ASSERT_EQUAL(r, 26); CU_ASSERT_EQUAL(t, 1286209192); } static void test_military_timezones(void) { time_t t; int r; time_t zulu = 813727192; /* Well-formed legacy format with 2-digit day, 2-digit year, * uppercase 1-char timezone = UTC, "dd-mmm-yy HH:MM:SS-z" */ t = UNINIT_TIMET; r = time_from_rfc3501("15-Oct-95 03:19:52-Z", &t); CU_ASSERT_EQUAL(r, 20); CU_ASSERT_EQUAL(t, zulu); /* Well-formed legacy format with 2-digit day, 2-digit year, * lowercase 1-char timezone = UTC, "dd-mmm-yy HH:MM:SS-z" */ t = UNINIT_TIMET; r = time_from_rfc3501("15-Oct-95 03:19:52-z", &t); CU_ASSERT_EQUAL(r, 20); CU_ASSERT_EQUAL(t, zulu); /* Well-formed legacy format with 2-digit day, 2-digit year, * uppercase 1-char timezone = +0100, "dd-mmm-yy HH:MM:SS-z" */ t = UNINIT_TIMET; r = time_from_rfc3501("15-Oct-95 03:19:52-A", &t); CU_ASSERT_EQUAL(r, 20); CU_ASSERT_EQUAL(t, zulu-1*3600); /* Well-formed legacy format with 2-digit day, 2-digit year, * uppercase 1-char timezone = +0200, "dd-mmm-yy HH:MM:SS-z" */ t = UNINIT_TIMET; r = time_from_rfc3501("15-Oct-95 03:19:52-B", &t); CU_ASSERT_EQUAL(r, 20); CU_ASSERT_EQUAL(t, zulu-2*3600); /* Well-formed legacy format with 2-digit day, 2-digit year, * uppercase 1-char timezone = +0900, "dd-mmm-yy HH:MM:SS-z" */ t = UNINIT_TIMET; r = time_from_rfc3501("15-Oct-95 03:19:52-I", &t); CU_ASSERT_EQUAL(r, 20); CU_ASSERT_EQUAL(t, zulu-9*3600); /* Well-formed legacy format with 2-digit day, 2-digit year, * erroneous uppercase 1-char timezone, "dd-mmm-yy HH:MM:SS-z" */ t = UNINIT_TIMET; r = time_from_rfc3501("15-Oct-95 03:19:52-J", &t); CU_ASSERT_EQUAL(r, -1); CU_ASSERT_EQUAL(t, UNINIT_TIMET); /* Well-formed legacy format with 2-digit day, 2-digit year, * uppercase 1-char timezone = +1000, "dd-mmm-yy HH:MM:SS-z" */ t = UNINIT_TIMET; r = time_from_rfc3501("15-Oct-95 03:19:52-K", &t); CU_ASSERT_EQUAL(r, 20); CU_ASSERT_EQUAL(t, zulu-10*3600); /* Well-formed legacy format with 2-digit day, 2-digit year, * 1-char timezone = +1200, "dd-mmm-yy HH:MM:SS-z" */ t = UNINIT_TIMET; r = time_from_rfc3501("15-Oct-95 03:19:52-M", &t); CU_ASSERT_EQUAL(r, 20); CU_ASSERT_EQUAL(t, zulu-12*3600); /* Well-formed legacy format with 2-digit day, 2-digit year, * uppercase 1-char timezone = -0100, "dd-mmm-yy HH:MM:SS-z" */ t = UNINIT_TIMET; r = time_from_rfc3501("15-Oct-95 03:19:52-N", &t); CU_ASSERT_EQUAL(r, 20); CU_ASSERT_EQUAL(t, zulu+1*3600); /* Well-formed legacy format with 2-digit day, 2-digit year, * 1-char timezone = -1200, "dd-mmm-yy HH:MM:SS-z" */ t = UNINIT_TIMET; r = time_from_rfc3501("15-Oct-95 03:19:52-Y", &t); CU_ASSERT_EQUAL(r, 20); CU_ASSERT_EQUAL(t, zulu+12*3600); } /* " d-mmm-yy HH:MM:SS-z" */ /* "dd-mmm-yy HH:MM:SS-zz" */ /* " d-mmm-yy HH:MM:SS-zz" */ /* "dd-mmm-yy HH:MM:SS-zzz" */ /* " d-mmm-yy HH:MM:SS-zzz" */ /* * Test time_from_rfc822() */ static void test_parse_rfc822(void) { static const char DATETIME[] = "Tue, 16 Nov 2010 12:46:49 +1100"; static const time_t TIMET = 1289872009; time_t t; int r; /* * Convert the datetime string into a time_t, which is always * expressed in UTC regardless of the current timezone. */ t = UNINIT_TIMET; r = time_from_rfc822(DATETIME, &t); CU_ASSERT_EQUAL(r, 31); CU_ASSERT_EQUAL(t, TIMET); push_tz(TZ_UTC); t = UNINIT_TIMET; r = time_from_rfc822(DATETIME, &t); CU_ASSERT_EQUAL(r, 31); CU_ASSERT_EQUAL(t, TIMET); pop_tz(); push_tz(TZ_NEWYORK); t = UNINIT_TIMET; r = time_from_rfc822(DATETIME, &t); CU_ASSERT_EQUAL(r, 31); CU_ASSERT_EQUAL(t, TIMET); pop_tz(); } /* * Test time_to_rfc822() */ static void test_gen_rfc822(void) { static const char DATETIME_MEL[] = "Fri, 26 Nov 2010 14:22:02 +1100"; static const char DATETIME_UTC[] = "Fri, 26 Nov 2010 03:22:02 +0000"; static const char DATETIME_NYC[] = "Thu, 25 Nov 2010 22:22:02 -0500"; static const time_t TIMET = 1290741722; int r; char buf[RFC822_DATETIME_MAX+1]; memset(buf, 0x45, sizeof(buf)); r = time_to_rfc822(TIMET, buf, sizeof(buf)); CU_ASSERT_EQUAL(r, 31); CU_ASSERT_STRING_EQUAL(buf, DATETIME_MEL); push_tz(TZ_UTC); memset(buf, 0x45, sizeof(buf)); r = time_to_rfc822(TIMET, buf, sizeof(buf)); CU_ASSERT_EQUAL(r, 31); CU_ASSERT_STRING_EQUAL(buf, DATETIME_UTC); pop_tz(); push_tz(TZ_NEWYORK); memset(buf, 0x45, sizeof(buf)); r = time_to_rfc822(TIMET, buf, sizeof(buf)); CU_ASSERT_EQUAL(r, 31); CU_ASSERT_STRING_EQUAL(buf, DATETIME_NYC); pop_tz(); } static void test_ctime(void) { static const char DATETIME[] = "16-Nov-2010 13:15:25 +1100"; static const time_t TIMET = 1289873725; char buf[RFC3501_DATETIME_MAX+1]; memset(buf, 0, sizeof(buf)); time_to_rfc3501(TIMET, buf, sizeof(buf)); CU_ASSERT_STRING_EQUAL(buf, DATETIME); } /* * Seen in the wild, generated by Apple Mail: a date * which is a valid UNIX time_t because it's in the first * hour of 1970 in UTC, but expressed in a timezone which * makes it be in the last day of 1969. This is weird * and probably technically valid but does not need to * be supported, but we do need to fail gracefully. */ static void test_zerohour(void) { static const char DATETIME_NY[] = "Wed, 31 Dec 1969 19:36:29 -0500"; static const char DATETIME_MEL[] = " 1-Jan-1970 11:36:29 +1100"; static const time_t TIMET = 2189; time_t t; int r; char buf[RFC3501_DATETIME_MAX+1]; t = UNINIT_TIMET; r = time_from_rfc822(DATETIME_NY, &t); CU_ASSERT_EQUAL(r, -1); CU_ASSERT_EQUAL(t, UNINIT_TIMET); /* fail gracefully */ push_tz(TZ_UTC); t = UNINIT_TIMET; r = time_from_rfc822(DATETIME_NY, &t); CU_ASSERT_EQUAL(r, -1); CU_ASSERT_EQUAL(t, UNINIT_TIMET); /* fail gracefully */ pop_tz(); push_tz(TZ_NEWYORK); t = UNINIT_TIMET; r = time_from_rfc822(DATETIME_NY, &t); CU_ASSERT_EQUAL(r, -1); CU_ASSERT_EQUAL(t, UNINIT_TIMET); /* fail gracefully */ pop_tz(); memset(buf, 0, sizeof(buf)); time_to_rfc3501(TIMET, buf, sizeof(buf)); CU_ASSERT_STRING_EQUAL(buf, DATETIME_MEL); } static void test_parse_iso8601(void) { static const char DATETIME_MEL[] = "2010-11-26T14:22:02+11:00"; static const char DATETIME_UTC[] = "2010-11-26T03:22:02Z"; static const char DATETIME_NYC[] = "2010-11-25T22:22:02-05:00"; static const time_t TIMET = 1290741722; time_t t; int r; t = UNINIT_TIMET; r = time_from_iso8601(DATETIME_MEL, &t); CU_ASSERT_EQUAL(r, 25); CU_ASSERT_EQUAL(t, TIMET); t = UNINIT_TIMET; r = time_from_iso8601(DATETIME_UTC, &t); CU_ASSERT_EQUAL(r, 20); CU_ASSERT_EQUAL(t, TIMET); t = UNINIT_TIMET; r = time_from_iso8601(DATETIME_NYC, &t); CU_ASSERT_EQUAL(r, 25); CU_ASSERT_EQUAL(t, TIMET); } static void test_gen_iso8601(void) { static const char DATETIME_UTC[] = "2010-11-26T03:22:02Z"; static const time_t TIMET = 1290741722; char buf[30]; int r; r = time_to_iso8601(TIMET, buf, sizeof(buf)); CU_ASSERT_EQUAL(r, 20); CU_ASSERT_STRING_EQUAL(buf, DATETIME_UTC); } static void test_gen_iso8601_secfrac(void) { static const char DATETIME_STR[] = "2010-11-26T14:22:02.123+11:00"; static const struct timeval TIMEVAL = { 1290741722, 123456 }; char buf[33]; int r; r = timeval_to_iso8601(&TIMEVAL, timeval_ms, buf, sizeof(buf)); CU_ASSERT_EQUAL(r, strlen(DATETIME_STR)); CU_ASSERT_STRING_EQUAL(buf, DATETIME_STR); } /* Test that the 29 Feb works in some actual leap years, * and not in some not-leap years */ static void test_leapyear_rfc3501(void) { /* 2000 is a leapyear */ static const char FEB2000_STR[] = "29-Feb-2000 11:22:33 +1100"; static const time_t FEB2000_TIMET = 951783753; /* 2001 is not a leapyear */ static const char FEB2001_STR[] = "29-Feb-2001 11:22:33 +1100"; /* 2004 is a leapyear */ static const char FEB2004_STR[] = "29-Feb-2004 11:22:33 +1100"; static const time_t FEB2004_TIMET = 1078014153; time_t t; int r; t = UNINIT_TIMET; r = time_from_rfc3501(FEB2000_STR, &t); CU_ASSERT_EQUAL(r, 26); CU_ASSERT_EQUAL(t, FEB2000_TIMET); t = UNINIT_TIMET; r = time_from_rfc3501(FEB2001_STR, &t); CU_ASSERT_EQUAL(r, -1); CU_ASSERT_EQUAL(t, UNINIT_TIMET); t = UNINIT_TIMET; r = time_from_rfc3501(FEB2004_STR, &t); CU_ASSERT_EQUAL(r, 26); CU_ASSERT_EQUAL(t, FEB2004_TIMET); } static void test_leapyear_iso8601(void) { /* 2000 is a leapyear */ static const char FEB2000_STR[] = "2000-02-29T11:22:33+11:00"; static const time_t FEB2000_TIMET = 951783753; /* 2001 is not a leapyear */ static const char FEB2001_STR[] = "2001-02-29T11:22:33+11:00"; /* 2004 is a leapyear */ static const char FEB2004_STR[] = "2004-02-29T11:22:33+11:00"; static const time_t FEB2004_TIMET = 1078014153; time_t t; int r; t = UNINIT_TIMET; r = time_from_iso8601(FEB2000_STR, &t); CU_ASSERT_EQUAL(r, 25); CU_ASSERT_EQUAL(t, FEB2000_TIMET); t = UNINIT_TIMET; r = time_from_iso8601(FEB2001_STR, &t); CU_ASSERT_EQUAL(r, -1); CU_ASSERT_EQUAL(t, UNINIT_TIMET); t = UNINIT_TIMET; r = time_from_iso8601(FEB2004_STR, &t); CU_ASSERT_EQUAL(r, 25); CU_ASSERT_EQUAL(t, FEB2004_TIMET); } static void test_leapyear_rfc822(void) { /* 2000 is a leapyear */ static const char FEB2000_STR[] = "Tue, 29 Feb 2000 11:22:33 +1100"; static const time_t FEB2000_TIMET = 951783753; /* 2001 is not a leapyear */ static const char FEB2001_STR[] = "Thu, 29 Feb 2001 11:22:33 +1100"; /* 2004 is a leapyear */ static const char FEB2004_STR[] = "Sun, 29 Feb 2004 11:22:33 +1100"; static const time_t FEB2004_TIMET = 1078014153; time_t t; int r; t = UNINIT_TIMET; r = time_from_rfc822(FEB2000_STR, &t); CU_ASSERT_EQUAL(r, 31); CU_ASSERT_EQUAL(t, FEB2000_TIMET); t = UNINIT_TIMET; r = time_from_rfc822(FEB2001_STR, &t); CU_ASSERT_EQUAL(r, -1); CU_ASSERT_EQUAL(t, UNINIT_TIMET); t = UNINIT_TIMET; r = time_from_rfc822(FEB2004_STR, &t); CU_ASSERT_EQUAL(r, 31); CU_ASSERT_EQUAL(t, FEB2004_TIMET); } /* vim: set ft=c: */ cyrus-imapd-2.5.10/cunit/guid.testc0000644000175000017500000000447513001236020014070 00000000000000#include "cunit/cunit.h" #include "imap/message_guid.h" static void test_guid(void) { static const char TEXT[] = "lorem ipsum dolor sit amet, " "consectetur adipisicing elit\n"; static const unsigned char SHA1[20] = { 0xd1,0xb0,0x52,0xa0,0x12,0xcb,0xec,0xd5,0x42,0x5b, 0x23,0xf3,0x61,0x42,0x6f,0x24,0xdb,0x56,0xd7,0x45 }; struct message_guid guid; struct message_guid guid2; int r; message_guid_set_null(&guid); r = message_guid_isnull(&guid); CU_ASSERT_EQUAL(r, 1); r = message_guid_isnull(&guid); CU_ASSERT_EQUAL(r, 1); message_guid_generate(&guid, TEXT, sizeof(TEXT)-1); r = message_guid_isnull(&guid); CU_ASSERT_EQUAL(r, 0); r = message_guid_isnull(&guid); CU_ASSERT_EQUAL(r, 0); CU_ASSERT_EQUAL(memcmp(&guid.value, SHA1, sizeof(SHA1)), 0); memset(&guid2, 0x45, sizeof(guid2)); r = message_guid_equal(&guid, &guid2); CU_ASSERT_EQUAL(r, 0); message_guid_copy(&guid2, &guid); CU_ASSERT_EQUAL(memcmp(&guid2.value, SHA1, sizeof(SHA1)), 0); r = message_guid_equal(&guid, &guid2); CU_ASSERT_EQUAL(r, 1); } static void test_import(void) { static const unsigned char SHA1[20] = { 0xd1,0xb0,0x52,0xa0,0x12,0xcb,0xec,0xd5,0x42,0x5b, 0x23,0xf3,0x61,0x42,0x6f,0x24,0xdb,0x56,0xd7,0x45 }; struct message_guid guid; unsigned char buf[MESSAGE_GUID_SIZE]; int r; memset(&guid, 0x45, sizeof(guid)); message_guid_import(&guid, SHA1); r = message_guid_isnull(&guid); CU_ASSERT_EQUAL(r, 0); CU_ASSERT_EQUAL(memcmp(&guid.value, SHA1, sizeof(SHA1)), 0); memset(buf, 0x69, sizeof(buf)); message_guid_export(&guid, buf); CU_ASSERT_EQUAL(memcmp(buf, SHA1, sizeof(SHA1)), 0); } static void test_encode(void) { static const char SHA1HEX[41] = "d1b052a012cbecd5425b23f361426f24db56d745"; static const unsigned char SHA1BIN[20] = { 0xd1,0xb0,0x52,0xa0,0x12,0xcb,0xec,0xd5,0x42,0x5b, 0x23,0xf3,0x61,0x42,0x6f,0x24,0xdb,0x56,0xd7,0x45 }; struct message_guid guid; char *s; int r; memset(&guid, 0x45, sizeof(guid)); message_guid_decode(&guid, SHA1HEX); r = message_guid_isnull(&guid); CU_ASSERT_EQUAL(r, 0); CU_ASSERT_EQUAL(memcmp(&guid.value, SHA1BIN, sizeof(SHA1BIN)), 0); s = message_guid_encode(&guid); CU_ASSERT_STRING_EQUAL(s, SHA1HEX); } /* vim: set ft=c: */ cyrus-imapd-2.5.10/cunit/backend.testc0000644000175000017500000010426113001236020014521 00000000000000#if HAVE_CONFIG_H #include #endif #include #include #include #include #include "cunit/cunit.h" #include "imap/saslclient.h" #include #include #include "xmalloc.h" #include "imap/mutex.h" #include "prot.h" #include "imap/backend.h" struct server_config { int sasl_plain; int sasl_login; int sasl_digestmd5; int starttls; int deflate; int caps_one_per_line; }; /* * This is a useful hack. All the test server's state is * stored using this structure in an anonymous page which * is shared between the client and server. This lets the * test code in the client reach into the server state and * either tweak the behaviour via the config or do asserts * on the per-connection state (which makes integrating * with CUnit a whole lot easier, as CU asserts in a child * process are really not helpful). */ struct server_state { /* dynamic configuration */ struct server_config config; /* global state */ int rend_sock; /* per-connection state */ int is_connected; int is_authenticated; int is_tls; sasl_conn_t *saslconn; /* the sasl connection context */ #ifdef HAVE_SSL SSL *tls_conn; #endif struct protstream *in; struct protstream *out; }; #define HOST "localhost" #define SASLSERVICE "vorpal" #define USERID "fbloggs" #define PASSWORD "shibboleth" extern int verbose; static sasl_callback_t *callbacks; static struct server_state *server_state; static const struct server_config default_server_config = { .sasl_plain = 1, .sasl_login = 0, .sasl_digestmd5 = 0, .starttls = 0, .deflate = 0, .caps_one_per_line = 1 }; static const struct capa_t default_capa[] = { { "CCSASL", CAPA_AUTH }, { "CCSTARTTLS", CAPA_STARTTLS }, { "CCCOMPRESS=DEFLATE", CAPA_COMPRESS }, { NULL, 0 } }; static char default_service[32]; static int init_sasl(int isclient); static struct protocol_t test_prot = { /* .service is setup in default_conditions() */ .sasl_service = SASLSERVICE, .type = TYPE_STD, .u.std = { .banner = { .auto_capa = 1, .resp = "OK" }, .capa_cmd = { .cmd = "XXCAPABILITY", .arg = NULL, .resp = "OK", .postcapability = NULL, .formatflags = CAPAF_ONE_PER_LINE|CAPAF_SKIP_FIRST_WORD, /* .capa is setup in default_conditions() */ }, .tls_cmd = { .cmd = "XXSTARTTLS", .ok = "OK", .fail = "NO", .auto_capa = 0 }, .sasl_cmd = { .cmd = "XXAUTHENTICATE", .maxlen = USHRT_MAX, .quote = 0, .ok = "OK", .fail = "NO", .cont = "+ ", .cancel = "*", .parse_success = NULL, .auto_capa = 0 }, .compress_cmd = { .cmd = NULL, .unsol = NULL, .ok = NULL }, .ping_cmd = { .cmd = "XXNOOP", .unsol = NULL, .ok = "OK" }, .logout_cmd = { .cmd = "XXLOGOUT", .unsol = NULL, .ok = "OK" } } }; /* * Setup default test conditions, on both the client and server. */ static void default_conditions(void) { server_state->config = default_server_config; test_prot.service = default_service; memcpy(&test_prot.u.std.capa_cmd.capa, default_capa, sizeof(default_capa)); test_prot.u.std.capa_cmd.formatflags = CAPAF_ONE_PER_LINE|CAPAF_SKIP_FIRST_WORD; } /* ====================================================================== */ /* * Test connecting to a host which doesn't exist. */ static void test_badhost(void) { struct backend *be; const char *auth_status = NULL; default_conditions(); be = backend_connect(NULL, "nonexistanthost", &test_prot, USERID, callbacks, &auth_status, /*fd*/-1); CU_ASSERT_PTR_NULL(be); CU_ASSERT_EQUAL(server_state->is_connected, 0); } /* * Test connecting to the wrong port on the right host. */ static void test_badservice(void) { struct backend *be; const char *auth_status = NULL; default_conditions(); test_prot.service = "nonexistantservice"; be = backend_connect(NULL, HOST, &test_prot, USERID, callbacks, &auth_status, /*fd*/-1); CU_ASSERT_PTR_NULL(be); CU_ASSERT_EQUAL(server_state->is_connected, 0); } /* * Test authenticating with the PLAIN mechanism. */ static void test_sasl_plain(void) { struct backend *be; const char *auth_status = NULL; char *mechs; int r; default_conditions(); server_state->config.sasl_plain = 1; be = backend_connect(NULL, HOST, &test_prot, USERID, callbacks, &auth_status, /*fd*/-1); CU_ASSERT_PTR_NOT_NULL_FATAL(be); CU_ASSERT_EQUAL(server_state->is_connected, 1); CU_ASSERT_EQUAL(server_state->is_authenticated, 1); CU_ASSERT_EQUAL(server_state->is_tls, 0); mechs = backend_get_cap_params(be, CAPA_AUTH); CU_ASSERT_STRING_EQUAL(mechs, "PLAIN"); free(mechs); r = backend_ping(be, NULL); CU_ASSERT_EQUAL(r, 0); backend_disconnect(be); free(be); } #if 0 /* * Test authenticating with the LOGIN mechanism. * This test doesn't work for me. I have NFI why - gnb. */ static void not_test_sasl_login(void) { struct backend *be; const char *auth_status = NULL; char *mechs; int r; default_conditions(); server_state->config.sasl_plain = 0; server_state->config.sasl_login = 1; be = backend_connect(NULL, HOST, &test_prot, USERID, callbacks, &auth_status, /*fd*/-1); CU_ASSERT_PTR_NOT_NULL_FATAL(be); CU_ASSERT_EQUAL(server_state->is_connected, 1); CU_ASSERT_EQUAL(server_state->is_authenticated, 1); CU_ASSERT_EQUAL(server_state->is_tls, 0); mechs = backend_get_cap_params(be, CAPA_AUTH); CU_ASSERT_STRING_EQUAL(mechs, "LOGIN"); free(mechs); r = backend_ping(be); CU_ASSERT_EQUAL(r, 0); backend_disconnect(be); free(be); } #endif /* * Test authenticating with the DIGEST-MD5 mechanism. */ static void test_sasl_digestmd5(void) { struct backend *be; const char *auth_status = NULL; char *mechs; int r; default_conditions(); server_state->config.sasl_plain = 0; server_state->config.sasl_digestmd5 = 1; be = backend_connect(NULL, HOST, &test_prot, USERID, callbacks, &auth_status, /*fd*/-1); CU_ASSERT_PTR_NOT_NULL_FATAL(be); CU_ASSERT_EQUAL(server_state->is_connected, 1); CU_ASSERT_EQUAL(server_state->is_authenticated, 1); CU_ASSERT_EQUAL(server_state->is_tls, 0); mechs = backend_get_cap_params(be, CAPA_AUTH); CU_ASSERT_STRING_EQUAL(mechs, "DIGEST-MD5"); free(mechs); r = backend_ping(be, NULL); CU_ASSERT_EQUAL(r, 0); backend_disconnect(be); free(be); } /* Common routine to test the semantics of capabilities */ static void caps_common(void) { #define CAPA_FOO (1<<(CAPA_COMPRESS+1)) #define CAPA_BAZ (1<<(CAPA_COMPRESS+2)) #define CAPA_QUUX (1<<(CAPA_COMPRESS+3)) #define CAPA_FNORD (1<<(CAPA_COMPRESS+4)) #define CAPA_CAPITALS (1<<(CAPA_COMPRESS+5)) #define CAPA_MIA (1<<(CAPA_COMPRESS+6)) struct backend *be; const char *auth_status = NULL; char *params; int r; int n; static const struct capa_t extra_capa[] = { { "FOO", CAPA_FOO }, { "BAZ", CAPA_BAZ }, { "QUUX", CAPA_QUUX }, { "FNORD=BOO", CAPA_FNORD }, { "CAPITALS", CAPA_CAPITALS }, { "MIA", CAPA_MIA }, { NULL, 0 } /* No more room in the fixed size array, dammit */ }; /* append some extra capabilities */ n = sizeof(default_capa)/sizeof(default_capa[0]) - 1; CU_ASSERT_FATAL(n * sizeof(struct capa_t) + sizeof(extra_capa) <= sizeof(test_prot.u.std.capa_cmd.capa)); memcpy(&test_prot.u.std.capa_cmd.capa[n], extra_capa, sizeof(extra_capa)); be = backend_connect(NULL, HOST, &test_prot, USERID, callbacks, &auth_status, /*fd*/-1); CU_ASSERT_PTR_NOT_NULL_FATAL(be); CU_ASSERT_EQUAL(server_state->is_connected, 1); CU_ASSERT_EQUAL(server_state->is_authenticated, 1); CU_ASSERT_EQUAL(server_state->is_tls, 0); /* FOO is present, its parameter is BAR */ CU_ASSERT_EQUAL(!!CAPA(be, CAPA_FOO), 1); params = backend_get_cap_params(be, CAPA_FOO); CU_ASSERT_STRING_EQUAL(params, "BAR"); free(params); /* BAZ is present, it has no parameters */ CU_ASSERT_EQUAL(!!CAPA(be, CAPA_BAZ), 1); params = backend_get_cap_params(be, CAPA_BAZ); CU_ASSERT_PTR_NULL(params); /* QUUX is present, its parameters are FOONLY and FMEH */ CU_ASSERT_EQUAL(!!CAPA(be, CAPA_QUUX), 1); params = backend_get_cap_params(be, CAPA_QUUX); CU_ASSERT_STRING_EQUAL(params, "FOONLY FMEH"); free(params); /* FNORD is present, its parameters are BOO and GNERGH, * but we asked specifically for FNORD=BOO so CAPA() * should succeed but we should see no params. */ CU_ASSERT_EQUAL(!!CAPA(be, CAPA_FNORD), 1); params = backend_get_cap_params(be, CAPA_FNORD); CU_ASSERT_PTR_NULL(params); /* CAPITALS is present, its parameter is Oslo. Note the * name is matched case-insensitive but the parameters * are returned as seen on the wire. */ CU_ASSERT_EQUAL(!!CAPA(be, CAPA_CAPITALS), 1); params = backend_get_cap_params(be, CAPA_CAPITALS); CU_ASSERT_STRING_EQUAL(params, "Oslo"); free(params); /* MIA is missing in action */ CU_ASSERT_EQUAL(!!CAPA(be, CAPA_MIA), 0); params = backend_get_cap_params(be, CAPA_MIA); CU_ASSERT_PTR_NULL(params); r = backend_ping(be, NULL); CU_ASSERT_EQUAL(r, 0); backend_disconnect(be); free(be); #undef CAPA_FOO #undef CAPA_BAZ #undef CAPA_QUUX #undef CAPA_FNORD #undef CAPA_CAPITALS #undef CAPA_MIA } /* * Test parsing capabilities in multi-line format */ static void test_multiline_caps(void) { default_conditions(); server_state->config.caps_one_per_line = 1; test_prot.u.std.capa_cmd.formatflags = CAPAF_ONE_PER_LINE|CAPAF_SKIP_FIRST_WORD; caps_common(); } /* * Test parsing capabilities in one-line format */ static void test_oneline_caps(void) { default_conditions(); server_state->config.caps_one_per_line = 0; test_prot.u.std.capa_cmd.formatflags = CAPAF_MANY_PER_LINE; caps_common(); } #ifdef HAVE_SSL /* * Test STARTTLS */ static void test_starttls(void) { struct backend *be; const char *auth_status = NULL; char *mechs; int r; default_conditions(); server_state->config.sasl_plain = 1; server_state->config.starttls = 1; be = backend_connect(NULL, HOST, &test_prot, USERID, callbacks, &auth_status, /*fd*/-1); CU_ASSERT_PTR_NOT_NULL_FATAL(be); CU_ASSERT_EQUAL(server_state->is_connected, 1); CU_ASSERT_EQUAL(server_state->is_authenticated, 1); CU_ASSERT_EQUAL(server_state->is_tls, 1); mechs = backend_get_cap_params(be, CAPA_AUTH); CU_ASSERT_STRING_EQUAL(mechs, "PLAIN"); free(mechs); CU_ASSERT(CAPA(be, CAPA_STARTTLS)) r = backend_ping(be, NULL); CU_ASSERT_EQUAL(r, 0); backend_disconnect(be); free(be); } #else /* * cunit.pl doesn't process C macros, so it expects this to exist * regardless of the state of HAVE_SSL */ static void test_starttls(void) { } #endif /* TODO: test UNIX socket comms too */ /* TODO: test IPv6 socket comms too */ /* TODO: test connect() timeout */ /* ====================================================================== */ /* * Allocate, and return a mapped pointer to, an anonymous page in * memory (a non-heap non-text page with no backing file) which will be * shared across fork(). The page is assumed to be zeroed. */ static void *get_anonymous_page(void) { void *page; size_t pagesize = getpagesize(); #if defined(MAP_ANON) && !defined(MAP_ANONYMOUS) /* FreeBSD */ #define MAP_ANONYMOUS MAP_ANON #endif #ifdef MAP_ANONYMOUS /* Linux and Solaris */ page = mmap(NULL, pagesize, PROT_READ|PROT_WRITE, MAP_ANONYMOUS|MAP_SHARED, -1, 0); if (page == MAP_FAILED) { perror("mmap"); return NULL; } #else int fd; fd = open("/dev/zero", O_RDWR); if (fd < 0) { perror("/dev/zero"); return NULL; } page = mmap(NULL, pagesize, PROT_READ|PROT_WRITE, MAP_SHARED, fd, 0); if (page == MAP_FAILED) { perror("mmap"); page = NULL; } close(fd); #endif return page; } /* * Free an anonymous page returned from get_anonymous_page() */ static void free_anonymous_page(void *page) { munmap(page, getpagesize()); } /* * Create a bound and listening TCP4 server socket, bound to the IPv4 * loopback address and a port chosen by the kernel. * * Returns: socket, or -1 on error. *@portp is filled with the port * number. */ static int create_server_socket(int *portp) { int sock; struct sockaddr_in sin; int r; sock = socket(PF_INET, SOCK_STREAM, IPPROTO_TCP); if (sock < 0) { perror("socket(TCP)"); return -1; } memset(&sin, 0, sizeof(sin)); sin.sin_family = AF_INET; sin.sin_addr.s_addr = htonl(INADDR_LOOPBACK); if (*portp) sin.sin_port = htons(*portp); r = bind(sock, (struct sockaddr *)&sin, sizeof(sin)); if (r < 0) { perror("bind"); goto error; } r = listen(sock, 5); if (r < 0) { perror("listen"); goto error; } if (!*portp) { socklen_t len = sizeof(sin); r = getsockname(sock, (struct sockaddr *)&sin, &len); if (r < 0) { perror("getsockname"); goto error; } if (len != sizeof(sin) || sin.sin_family != AF_INET) { fprintf(stderr, "Bad address from getsockname()\n"); goto error; } *portp = ntohs(sin.sin_port); } return sock; error: close(sock); return -1; } /* * Block until an incoming connection is received, then establish the * connection and initialise per-connection state. On success, set * @state->is_connected. * * Returns 0 on success, -1 on failure (errors indicate some resource * limitation in the server, not any behaviour of the client, and * should be fatal). */ static int server_accept(struct server_state *state) { int conn_sock; int r; if (verbose > 1) fprintf(stderr, "Server waiting for connection\n"); conn_sock = accept(state->rend_sock, NULL, NULL); if (conn_sock < 0) { perror("accept"); return -1; } if (verbose > 1) fprintf(stderr, "Server accepted connection\n"); state->in = prot_new(conn_sock, /*read*/0); state->out = prot_new(dup(conn_sock), /*write*/1); if (!state->in || !state->out) { perror("prot_new"); return -1; } r = sasl_server_new(SASLSERVICE, HOST, /*user_realm*/NULL, /*iplocalport*/NULL, /*ipremoteport*/NULL, /*callbacks*/NULL, /*flags*/0, &state->saslconn); if (r != SASL_OK) { fprintf(stderr, "sasl_server_new() failed with error %d\n", r); return -1; } state->is_authenticated = 0; state->is_connected = 1; state->is_tls = 0; #ifdef HAVE_SSL state->tls_conn = NULL; #endif return 0; } /* * Handle the end of a connection, by cleaning up all the per-connection * state. In particular, clears @state->is_connected. */ static void server_unaccept(struct server_state *state) { prot_free(state->in); state->in = NULL; prot_free(state->out); state->out = NULL; sasl_dispose(&state->saslconn); state->is_connected = 0; state->is_tls = 0; #ifdef HAVE_SSL if (state->tls_conn) { tls_reset_servertls(&state->tls_conn); state->tls_conn = NULL; } #endif } /* * Main routine for pushing text back to the client. */ static void server_printf(struct server_state *, const char *fmt, ...) __attribute__((format(printf,2,3))); static void server_printf(struct server_state *state, const char *fmt, ...) { va_list args; int r; char buf[2048]; if (verbose > 1) { va_start(args, fmt); fprintf(stderr, "S: "); vfprintf(stderr, fmt, args); va_end(args); } va_start(args, fmt); r = vsnprintf(buf, sizeof(buf), fmt, args); assert(r < (int)sizeof(buf)); va_end(args); r = prot_write(state->out, buf, strlen(buf)); assert(r >= 0); } /* * Flush any pending output back to the client. */ static void server_flush(struct server_state *state) { prot_flush(state->out); } /* * Get a line of text from the client. Blocks until * a while line is available. * * Returns: 0 on success, -1 on error or end of file. */ static int server_getline(struct server_state *state, char *buf, int maxlen) { if (!prot_fgets(buf, maxlen, state->in)) return -1; if (verbose > 1) fprintf(stderr, "C: %s\n", buf); return 0; } /* * Emit to the client a banner including the server's capability * strings. This might be in response to the client connecting, or to * the client issuing the XXCAPABILITY command. Various flags in * @state->config control which of the magical caps known by the * backend.c client code are reported. Some other test capabilities are * always reported. Depending on @state->config.caps_one_per_line, the * caps are listed in a multi-line format, one cap per line (LMTP, POP3, * ManageSieve, and sync style) or a single-line, many caps per line * format (IMAP style). */ static void server_emit_caps(struct server_state *state) { const char *saslmechs = NULL; char *p; char *b; int n = 0; const char *name; const char *words[256]; /* array of: * NAME, VALUE, VALUE, NULL, * NAME, VALUE, NULL, * NULL */ char line[1024]; static const char banner[] = "Toy Test server v0.0.1"; /* * The ccSASL cap reports a list of SASL mechanism names. * Note that we suppress them all if STARTTLS is enabled. */ if (!state->config.starttls || state->is_tls) { int got_login = 0; int got_plain = 0; int got_digestmd5 = 0; /* First see what mechanisms SASL has; no point reporting * mechanisms which aren't actually available. */ sasl_listmech(state->saslconn, /*user*/NULL, /*prefix*/"", /*sep*/" ", /*suffix*/"", &saslmechs, /*plen*/NULL, /*pcount*/NULL); b = xstrdup(saslmechs); /* Build our own list of mechanisms, which is the intersection * of the ones configured in SASL and the ones our server config * allows us. */ words[n++] = "ccSASL"; for (p = strtok(b, " ") ; p ; p = strtok(NULL, " ")) { if (!strcasecmp(p, "LOGIN") && state->config.sasl_login) { words[n++] = "LOGIN"; got_login = 1; } if (!strcasecmp(p, "LOGIN") && state->config.sasl_plain) { words[n++] = "PLAIN"; got_plain = 1; } if (!strcasecmp(p, "DIGEST-MD5") && state->config.sasl_digestmd5) { words[n++] = "DIGEST-MD5"; got_digestmd5 = 1; } } words[n++] = NULL; free(b); if (state->config.sasl_login && !got_login) fprintf(stderr, "Server failed to find requested " "SASL mechanism \"LOGIN\"\n"); if (state->config.sasl_plain && !got_plain) fprintf(stderr, "Server failed to find requested " "SASL mechanism \"PLAIN\"\n"); if (state->config.sasl_digestmd5 && !got_digestmd5) fprintf(stderr, "Server failed to find requested " "SASL mechanism \"DIGEST-MD5\"\n"); } /* * The ccSTARTTLS cap reports the ability to do STARTTLS */ if (state->config.starttls) { words[n++] = "ccSTARTTLS"; words[n++] = NULL; } /* * The ccCOMPRESS=DEFLATE cap reports the ability to do Deflate * compression. */ if (state->config.deflate) { words[n++] = "ccCOMPRESS"; words[n++] = "DEFLATE"; words[n++] = NULL; } /* * Various test capabilities; the test code in the client knows what * to expect for these. */ words[n++] = "FOO"; words[n++] = "BAR"; words[n++] = NULL; words[n++] = "BAZ"; words[n++] = NULL; words[n++] = "QUUX"; words[n++] = "FOONLY"; words[n++] = "FMEH"; words[n++] = NULL; words[n++] = "FNORD"; words[n++] = "BOO"; words[n++] = "GNERGH"; words[n++] = NULL; words[n++] = "cApItAls"; words[n++] = "Oslo"; words[n++] = NULL; words[n++] = NULL; /* * Finally we have all the capability names and values, now * pull them out of words[] and emit lines to the client. */ n = 0; if (state->config.caps_one_per_line) { /* Multi-line, one cap and all its values on each line (LMTP, * ManageSieve, POP3 and sync style) */ while ((name = words[n++])) { line[0] = '\0'; for ( ; words[n] ; n++) { strcat(line, " "); strcat(line, words[n]); } n++; server_printf(state, "* %s%s\r\n", name, line); } server_printf(state, "OK %s\r\n", banner); } else { /* One-line, NAME=VALUE pairs inside IMAP-style response code */ line[0] = '\0'; while ((name = words[n++])) { if (words[n]) { for ( ; words[n] ; n++) { strcat(line, " "); strcat(line, name); strcat(line, "="); strcat(line, words[n]); } } else { strcat(line, " "); strcat(line, name); } n++; } server_printf(state, "OK [CAPABILITY%s] %s\r\n", line, banner); } server_flush(state); } /* * Handle the XXAUTHENTICATE command from the client. The 1st and 2nd * arguments to the command on wire are passed as @mech and * @initial_in_b64. Handles any SASL conversation with the client (e.g. * server challenges and client responses), and telling the client the * final status. If successful, sets @state->is_authenticated. */ static void cmd_authenticate(struct server_state *state, const char *mech, const char *initial_in_b64) { char *word; const char *server_out; unsigned int server_out_len; int r; unsigned int buflen = 0; char buf[21848]; static const char sep[] = " \t\r\n"; if (!mech) goto badsyntax; if (initial_in_b64) { r = sasl_decode64(initial_in_b64, strlen(initial_in_b64), buf, sizeof(buf), &buflen); if (r != SASL_OK) goto badsyntax; } else { buflen = 0; } server_out = NULL; server_out_len = 0; r = sasl_server_start(state->saslconn, mech, buf, buflen, &server_out, &server_out_len); while (r == SASL_CONTINUE) { if (server_out_len) sasl_encode64(server_out, server_out_len, buf, sizeof(buf), NULL); else strcpy(buf, "="); server_printf(state, "+ %s\n", buf); server_flush(state); if (server_getline(state, buf, sizeof(buf)) < 0) { fprintf(stderr, "No response to AUTH challenge\n"); return; } word = strtok(buf, sep); if (word) { r = sasl_decode64(word, strlen(word), buf, sizeof(buf), &buflen); if (r != SASL_OK) goto badsyntax; } else { buflen = 0; } server_out = NULL; server_out_len = 0; r = sasl_server_step(state->saslconn, buf, buflen, &server_out, &server_out_len); } if (r != SASL_OK) { server_printf(state, "BAD sasl error code %d\r\n", r); server_flush(state); return; } state->is_authenticated = 1; server_printf(state, "OK\r\n"); server_flush(state); return; badsyntax: server_printf(state, "BAD syntax\r\n"); server_flush(state); } /* * Handle the XXSTARTTLS command from the client. * If successful, sets @state->is_tls. */ static void cmd_starttls(struct server_state *state) { #ifdef HAVE_SSL int r; char *auth_id = NULL; SSL *tls_conn = NULL; sasl_ssf_t ssf; r = tls_init_serverengine("backend_test", /*verifydepth*/5, /*askcert*/1); if (r < 0) { server_printf(state, "BAD error initializing TLS\r\n"); server_flush(state); return; } server_printf(state, "OK Begin TLS negotiation now\r\n"); /* must flush our buffers before starting tls */ server_flush(state); r = tls_start_servertls(/*readfd*/state->in->fd, /*writefd*/state->out->fd, /*timeout_sec*/3000, (int *)&ssf, &auth_id, &tls_conn); if (r < 0) { server_printf(state, "BAD STARTTLS negotiation failed\r\n"); server_flush(state); return; } /* tell SASL about the negotiated layer */ r = sasl_setprop(state->saslconn, SASL_SSF_EXTERNAL, &ssf); if (r != SASL_OK) { server_printf(state, "BAD sasl_setprop(SASL_SSF_EXTERNAL) " "failed: cmd_starttls()\r\n"); server_flush(state); return; } r = sasl_setprop(state->saslconn, SASL_AUTH_EXTERNAL, auth_id); if (r != SASL_OK) { server_printf(state, "BAD sasl_setprop(SASL_AUTH_EXTERNAL) " "failed: cmd_starttls()\r\n"); server_flush(state); return; } /* tell the prot layer about our new layers */ prot_settls(state->in, tls_conn); prot_settls(state->out, tls_conn); state->tls_conn = tls_conn; state->is_tls = 1; #else server_printf(state, "BAD this server is not built with SSL\r\n"); server_flush(state); #endif } /* * Server main command loop for a single connection. Blocks waiting for * commands from the client, and handles each command. Returns when the * client sends a XXLOGOUT command or drops the connection. */ static void server_cmdloop(struct server_state *state) { char *command; char buf[1024]; static const char sep[] = " \t\r\n"; /* Emit the connection banner */ server_emit_caps(state); while (server_getline(state, buf, sizeof(buf)) == 0) { command = strtok(buf, sep); if (!command) { server_printf(state, "BAD command\r\n"); server_flush(state); continue; } if (!strcasecmp(command, "XXLOGOUT")) { /* graceful disconnect */ server_printf(state, "OK\r\n"); server_flush(state); break; } else if (!strcasecmp(command, "XXNOOP")) { server_printf(state, "OK\r\n"); server_flush(state); } else if (!strcasecmp(command, "XXCAPABILITY")) { server_emit_caps(state); } else if (!strcasecmp(command, "XXAUTHENTICATE")) { char *mech = strtok(NULL, sep); char *initial_in = strtok(NULL, sep); cmd_authenticate(state, mech, initial_in); } else if (!strcasecmp(command, "XXSTARTTLS")) { cmd_starttls(state); } else { server_printf(state, "BAD command\r\n"); server_flush(state); } } } /* * Start the server. Forks a child process, which does some once-off * server initialisation and then enters a service loop. The service * loop is very dumb: it serves a single connection at a time, with no * forking or threading or async request handling. * * Returns: pid of the child process, or -1 on error. */ static pid_t server_start(struct server_state *state) { pid_t pid; pid = fork(); if (pid < 0) { perror("fork"); return -1; } if (pid) { /* We are the parent process. We don't need to wait for the * child to finish starting, as we have a bound socket we can * connect immediately (it just might take the child a little * while to respond to the first command). */ close(state->rend_sock); return pid; } /* We are the child process. */ if (init_sasl(/*client*/0) < 0) exit(1); /* Main connection loop. This is a toy, single-threaded server * which handles one connection at a time. */ for (;;) { /* Wait for a connection */ if (server_accept(state) < 0) exit(1); /* Run the main command loop for this connection */ server_cmdloop(state); /* Forget the per-connection state */ server_unaccept(state); } } /* * Shut down the server, given it's PID. It's pretty simple and brutal: * we just send it SIGTERM and wait to reap it. */ static void server_shutdown(pid_t pid) { int status; pid_t r; kill(pid, SIGTERM); for (;;) { r = waitpid(pid, &status, 0); if (r < 0) { if (errno == EINTR) continue; if (errno != ESRCH) perror("waitpid"); return; } if (r == pid) return; /* ok, killed it */ fprintf(stderr, "WTF? waitpid(%d) = %d?\n", pid, r); } } /* * Callback which we use to fakes server-side password checking for * those mechanisms where a plaintext password from the client is * available to the SASL server code, i.e. PLAIN and LOGIN. */ static int server_checkpass(sasl_conn_t *conn __attribute__((unused)), void *context __attribute__((unused)), const char *user, const char *pass, unsigned passlen, struct propctx *propctx __attribute__((unused))) { if (strcmp(user, USERID)) return SASL_NOUSER; if (passlen != strlen(PASSWORD) || strncmp(pass, PASSWORD, passlen)) return SASL_BADAUTH; return SASL_OK; } /* The auxprop API changed in commit a321326, Oct 2008 */ #if SASL_AUXPROP_PLUG_VERSION > 4 # define AUXPROP_RTYPE int # define AUXPROP_RET 0 #else # define AUXPROP_RTYPE void # define AUXPROP_RET #endif /* * Callback which we use to fake out server-side password checking for * those mechanisms where a plaintext password from the client is *NOT* * available, and so the SASL server code needs to retrieve the password * from an auxprop plugin. */ static AUXPROP_RTYPE server_auxprop_lookup(void *glob_context __attribute__((unused)), sasl_server_params_t *sparams, unsigned flags __attribute__((unused)), const char *user, unsigned ulen) { const struct propval *prop; if (ulen != strlen(USERID) || strncmp(user, USERID, ulen)) return AUXPROP_RET; prop = sparams->utils->prop_get(sparams->propctx); if (!prop) return AUXPROP_RET; for ( ; prop->name ; prop++) { if (!strcmp(prop->name, "*userPassword") || !strcmp(prop->name, "*cmusaslsecretDIGEST-MD5")) { if (prop->values) sparams->utils->prop_erase(sparams->propctx, prop->name); sparams->utils->prop_set(sparams->propctx, prop->name, PASSWORD, strlen(PASSWORD)); } } return AUXPROP_RET; } /* * Helps create a fake "auxiliary propert plugin" for the SASL library, * which is how we hook into the DIGEST-MD5 mechanism when it wants to * get a plaintext password to check aginst the hash received from the * client. */ static int server_auxprop_init(const sasl_utils_t *utils __attribute__((unused)), int max_version, int *out_version, sasl_auxprop_plug_t **plugp, const char *plugname __attribute__((unused))) { static sasl_auxprop_plug_t plug = { .features = 0, .auxprop_lookup = server_auxprop_lookup, .name = "testserver-hack" }; *out_version = max_version; *plugp = &plug; return SASL_OK; } /* * Initialise the SASL library, client or server. * * Returns: 0 on success, -ve on error. */ static int init_sasl(int isclient) { int r; /* set the SASL allocation functions */ sasl_set_alloc((sasl_malloc_t *)xmalloc, (sasl_calloc_t *)xcalloc, (sasl_realloc_t *)xrealloc, (sasl_free_t *)free); /* set the SASL mutex functions */ sasl_set_mutex(cyrus_mutex_alloc, cyrus_mutex_lock, cyrus_mutex_unlock, cyrus_mutex_free); if (isclient) { static const struct sasl_callback client_cb[] = { { SASL_CB_LIST_END, NULL, NULL } }; /* load the SASL client plugins */ if (sasl_client_init(client_cb)) { fprintf(stderr, "could not init sasl client\n"); return -1; } callbacks = mysasl_callbacks(USERID, USERID, NULL, PASSWORD); if (!callbacks) return -1; } else { static const struct sasl_callback server_cb[] = { { SASL_CB_SERVER_USERDB_CHECKPASS, (void *)&server_checkpass, NULL }, { SASL_CB_LIST_END, NULL, NULL } }; /* load the SASL server plugins */ r = sasl_server_init(server_cb, "testserver"); if (r != SASL_OK) { fprintf(stderr, "sasl_server_init() failed: error %d\n", r); return -1; } sasl_auxprop_add_plugin("testserver", server_auxprop_init); } return 0; } /* ====================================================================== */ static struct server_state *server_state; static pid_t server_pid; static int sasl_initialised; static int old_session_timeout; static char *old_config_dir; static char *old_tls_ca_file; static char *old_tls_cert_file; static char *old_tls_key_file; /* * Test suite setup function. Sets up the global * server_state page. Forks a server process which listens * on a TCP port, and writes the port number into default_service[] * so that the client code can connect to it. */ static int set_up(void) { int rend_sock, port = 0; char *sr; static char cwd[PATH_MAX]; if (verbose > 1) fprintf(stderr, "Starting server!\n"); sr = getcwd(cwd, sizeof(cwd)); if (!sr) { fprintf(stderr, "getcwd() failed: %s\n", strerror(errno)); return -1; } old_config_dir = (char *)config_dir; config_dir = xstrdup(cwd); old_tls_ca_file = (char *)imapopts[IMAPOPT_TLS_SERVER_CA_FILE].val.s; imapopts[IMAPOPT_TLS_SERVER_CA_FILE].val.s = strconcat(cwd, "/cacert.pem", (char *)NULL); old_tls_cert_file = (char *)imapopts[IMAPOPT_TLS_SERVER_CERT].val.s; imapopts[IMAPOPT_TLS_SERVER_CERT].val.s = strconcat(cwd, "/cert.pem", (char *)NULL); old_tls_key_file = (char *)imapopts[IMAPOPT_TLS_SERVER_KEY].val.s; imapopts[IMAPOPT_TLS_SERVER_KEY].val.s = strconcat(cwd, "/key.pem", (char *)NULL); /* disable SSL session caching */ old_session_timeout = imapopts[IMAPOPT_TLS_SESSION_TIMEOUT].val.i; imapopts[IMAPOPT_TLS_SESSION_TIMEOUT].val.i = 0; rend_sock = create_server_socket(&port); if (rend_sock < 0) return -1; server_state = get_anonymous_page(); if (!server_state) { close(rend_sock); return -1; } server_state->rend_sock = rend_sock; if (verbose > 1) fprintf(stderr, "Bound to port tcp/%u\n", port); snprintf(default_service, sizeof(default_service), "%d", port); server_pid = server_start(server_state); if (server_pid < 0) return -1; /* * Initialise the SASL library in the client process. This init * function can actually be called multiple times in the lifetime of * a test runner process, which is perhaps surprising, but we have * to deal with it. We do however seem to be able to get away with * initialising SASL multiple times as long as we call sasl_done() * after we're done. */ if (init_sasl(/*client*/1) < 0) return -1; sasl_initialised = 1; return 0; } /* * Test suite teardown function. Shuts down the server and * removes the global server_state page. */ static int tear_down(void) { if (verbose > 1) fprintf(stderr, "Cleaning up server! NOT.\n"); if (server_pid > 1) server_shutdown(server_pid); if (server_state) free_anonymous_page(server_state); if (callbacks) { free_callbacks(callbacks); callbacks = NULL; } if (sasl_initialised) { sasl_done(); sasl_initialised = 0; } free((char *)config_dir); config_dir = old_config_dir; imapopts[IMAPOPT_TLS_SESSION_TIMEOUT].val.i = old_session_timeout; free((char *)imapopts[IMAPOPT_TLS_SERVER_CA_FILE].val.s); imapopts[IMAPOPT_TLS_SERVER_CA_FILE].val.s = old_tls_ca_file; free((char *)imapopts[IMAPOPT_TLS_SERVER_CERT].val.s); imapopts[IMAPOPT_TLS_SERVER_CERT].val.s = old_tls_cert_file; free((char *)imapopts[IMAPOPT_TLS_SERVER_KEY].val.s); imapopts[IMAPOPT_TLS_SERVER_KEY].val.s = old_tls_key_file; return 0; } /* ====================================================================== */ /* vim: set ft=c: */ cyrus-imapd-2.5.10/cunit/charset.testc0000644000175000017500000001373313001236020014566 00000000000000#include #include "cunit/cunit.h" #include "charset.h" #define UTF8_REPLACEMENT "\357\277\275" static void test_lookupname(void) { int cs, cs2; /* us-ascii must exist */ cs = charset_lookupname("us-ascii"); CU_ASSERT(cs >= 0); /* names are case-insensitive */ cs2 = charset_lookupname("US-ASCII"); CU_ASSERT(cs2 >= 0); CU_ASSERT_EQUAL(cs, cs2); cs2 = charset_lookupname("Us-AsCiI"); CU_ASSERT(cs2 >= 0); CU_ASSERT_EQUAL(cs, cs2); /* some others must also exist */ cs = charset_lookupname("utf-8"); CU_ASSERT(cs >= 0); cs = charset_lookupname("utf-7"); CU_ASSERT(cs >= 0); cs = charset_lookupname("iso-8859-1"); CU_ASSERT(cs >= 0); } static void test_to_utf8(void) { int cs; char *s; static const char ASCII_1[] = "Hello World"; static const char ASCII_2[] = "Hello W\370rld"; static const char UTF8_2[] = "Hello W" UTF8_REPLACEMENT "rld"; static const char BASE64_3[] = "SGVsbG8gV29ybGQ="; static const char QP_4[] = "If you believe that truth=3Dbeauty, then surely=20=\r\n" "mathematics is the most beautiful branch of philosophy.\r\n"; static const char ASCII_4[] = "If you believe that truth=beauty, then surely " "mathematics is the most beautiful branch of philosophy.\r\n"; cs = charset_lookupname("us-ascii"); CU_ASSERT(cs >= 0); /* zero length input */ s = charset_to_utf8("", 0, cs, ENCODING_NONE); CU_ASSERT_PTR_NOT_NULL(s); CU_ASSERT_STRING_EQUAL(s, ""); free(s); /* invalid encoding */ s = charset_to_utf8(ASCII_1, sizeof(ASCII_1), cs, 0xdeadbeef); CU_ASSERT_PTR_NULL(s); /* invalid charset */ s = charset_to_utf8(ASCII_1, sizeof(ASCII_1), 0xdeadbeef, ENCODING_NONE); CU_ASSERT_PTR_NULL(s); /* simple ASCII string */ s = charset_to_utf8(ASCII_1, sizeof(ASCII_1)-1, cs, ENCODING_NONE); CU_ASSERT_PTR_NOT_NULL(s); CU_ASSERT_STRING_EQUAL(s, ASCII_1); free(s); /* ASCII string with an invalid character */ s = charset_to_utf8(ASCII_2, sizeof(ASCII_2)-1, cs, ENCODING_NONE); CU_ASSERT_PTR_NOT_NULL(s); CU_ASSERT_STRING_EQUAL(s, UTF8_2); free(s); /* base64 encoding */ s = charset_to_utf8(BASE64_3, sizeof(BASE64_3)-1, cs, ENCODING_BASE64); CU_ASSERT_PTR_NOT_NULL(s); CU_ASSERT_STRING_EQUAL(s, ASCII_1); free(s); /* Quoted-printable encoding */ s = charset_to_utf8(QP_4, sizeof(QP_4)-1, cs, ENCODING_QP); CU_ASSERT_PTR_NOT_NULL(s); CU_ASSERT_STRING_EQUAL(s, ASCII_4); free(s); } static void test_decode_mimeheader(void) { char *s; static const char ASCII_1[] = "Lorem IPSUM dolor \t \t sit amet"; static const char SEARCH_1[] = "LOREM IPSUM DOLOR SIT AMET"; static const char ASCII_B64_2[] = "Lorem =?us-ascii?q?ipsum?= dolor " "=?US-ASCII?Q?sit amet?="; static const char ASCII_B64_3[] = "Lorem =?iso-8859-1?q?ips=fcm?= \t" "DOLOR =?iso-8859-1?Q?s=eft am=ebt?="; static const char SEARCH_3[] = "LOREM IPSUM DOLOR SIT AMET"; static const char SEARCH_3b[] = "LOREM IPSÜM DOLOR SÏT AMËT"; static const char SEARCH_3c[] = "LOREMIPSUMDOLORSITAMET"; static const char SEARCH_3d[] = "LOREMIPSÜMDOLORSÏTAMËT"; static const char SEARCH_3e[] = "LOREM IPSÜM DOLOR SÏT AMËT"; int flags = CHARSET_SKIPDIACRIT | CHARSET_MERGESPACE; /* default */ s = charset_decode_mimeheader(NULL, flags); CU_ASSERT_PTR_NULL(s); free(s); s = charset_decode_mimeheader("", flags); CU_ASSERT_PTR_NOT_NULL(s); CU_ASSERT_STRING_EQUAL(s, ""); free(s); s = charset_decode_mimeheader(ASCII_1, flags); CU_ASSERT_PTR_NOT_NULL(s); CU_ASSERT_STRING_EQUAL(s, SEARCH_1); free(s); s = charset_decode_mimeheader(ASCII_B64_2, flags); CU_ASSERT_PTR_NOT_NULL(s); CU_ASSERT_STRING_EQUAL(s, SEARCH_1); free(s); s = charset_decode_mimeheader(ASCII_B64_3, flags); CU_ASSERT_PTR_NOT_NULL(s); CU_ASSERT_STRING_EQUAL(s, SEARCH_3); free(s); flags = CHARSET_MERGESPACE; s = charset_decode_mimeheader(ASCII_B64_3, flags); CU_ASSERT_PTR_NOT_NULL(s); CU_ASSERT_STRING_EQUAL(s, SEARCH_3b); free(s); flags = CHARSET_SKIPSPACE | CHARSET_SKIPDIACRIT; s = charset_decode_mimeheader(ASCII_B64_3, flags); CU_ASSERT_PTR_NOT_NULL(s); CU_ASSERT_STRING_EQUAL(s, SEARCH_3c); free(s); flags = CHARSET_SKIPSPACE; s = charset_decode_mimeheader(ASCII_B64_3, flags); CU_ASSERT_PTR_NOT_NULL(s); CU_ASSERT_STRING_EQUAL(s, SEARCH_3d); free(s); flags = 0; s = charset_decode_mimeheader(ASCII_B64_3, flags); CU_ASSERT_PTR_NOT_NULL(s); CU_ASSERT_STRING_EQUAL(s, SEARCH_3e); free(s); } static void test_search_mimeheader(void) { char *s; comp_pat *pat; static const char SUBJECT_CP1252[] = "=?Cp1252?Q?Herzlichen_Gl=FCckwunsch,_der_Artikel_Canon_Ob?= " "=?Cp1252?Q?jektiv_EF-S_18-55_mm_1:3,5-5,6_geh=F6rt_Ihnen!?="; static const char SEARCH_CP1252[] = "Herzlichen"; int flags = CHARSET_SKIPDIACRIT | CHARSET_MERGESPACE; /* default */ s = charset_convert(SEARCH_CP1252, 0, flags); pat = charset_compilepat(s); CU_ASSERT(charset_search_mimeheader(s, pat, SUBJECT_CP1252, flags)); charset_freepat(pat); free(s); } static void test_rfc5051(void) { /* Example: codepoint U+01C4 (LATIN CAPITAL LETTER DZ WITH CARON) * has a titlecase property of U+01C5 (LATIN CAPITAL LETTER D * WITH SMALL LETTER Z WITH CARON). Codepoint U+01C5 has a * decomposition property of U+0044 (LATIN CAPITAL LETTER D) * U+017E (LATIN SMALL LETTER Z WITH CARON). U+017E has a * decomposition property of U+007A (LATIN SMALL LETTER Z) U+030c */ char *s; static const char STR_RFC5051[] = {0xc7, 0x84, 0}; static const char RES_RFC5051[] = {'D', 'z', 0xcc, 0x8c, 0}; int flags = 0; /* super complient */ s = charset_convert(STR_RFC5051, charset_lookupname("utf-8"), flags); CU_ASSERT_PTR_NOT_NULL(s); CU_ASSERT_STRING_EQUAL(s, RES_RFC5051); free(s); } /* vim: set ft=c: */ cyrus-imapd-2.5.10/cunit/quota.testc0000644000175000017500000007417313001236020014273 00000000000000#include #include #include "config.h" #include "cunit/cunit.h" #include "imap/quota.h" #include "xmalloc.h" #include "retry.h" #include "imap/global.h" #include "imap/imap_err.h" #include "cyrusdb.h" #include "libcyr_cfg.h" #include "libconfig.h" #include "hash.h" #define DBDIR "test-mb-dbdir" #define QUOTAROOT "user.smurf" #define QUOTAROOT_NONEXISTANT "no-such-quotaroot" static char *backend = CUNIT_PARAM("quotalegacy,skiplist"); static void test_names(void) { int r; CU_ASSERT_STRING_EQUAL(quota_names[QUOTA_STORAGE], "STORAGE"); r = quota_name_to_resource("STORAGE"); CU_ASSERT_EQUAL(r, QUOTA_STORAGE); r = quota_name_to_resource("storage"); CU_ASSERT_EQUAL(r, QUOTA_STORAGE); r = quota_name_to_resource("StOrAge"); CU_ASSERT_EQUAL(r, QUOTA_STORAGE); CU_ASSERT_STRING_EQUAL(quota_names[QUOTA_ANNOTSTORAGE], "X-ANNOTATION-STORAGE"); r = quota_name_to_resource("X-ANNOTATION-STORAGE"); CU_ASSERT_EQUAL(r, QUOTA_ANNOTSTORAGE); r = quota_name_to_resource("x-annotation-storage"); CU_ASSERT_EQUAL(r, QUOTA_ANNOTSTORAGE); r = quota_name_to_resource("X-AnNotAtiOn-StOragE"); CU_ASSERT_EQUAL(r, QUOTA_ANNOTSTORAGE); r = quota_name_to_resource("nonesuch"); CU_ASSERT_EQUAL(r, -1); } /* * Trying to read quota for a quotaroot which is NULL, an empty string, * or a string which is not found in the database. */ static void test_read_no_root(void) { struct quota q; struct txn *txn = NULL; int r; q.root = NULL; r = quota_read(&q, NULL, 0); CU_ASSERT_EQUAL(r, IMAP_QUOTAROOT_NONEXISTENT); q.root = ""; r = quota_read(&q, NULL, 0); CU_ASSERT_EQUAL(r, IMAP_QUOTAROOT_NONEXISTENT); /* Also, for NULL or "" no txn is started */ q.root = NULL; r = quota_read(&q, &txn, 1); CU_ASSERT_EQUAL(r, IMAP_QUOTAROOT_NONEXISTENT); CU_ASSERT_PTR_NULL(txn); q.root = ""; r = quota_read(&q, &txn, 1); CU_ASSERT_EQUAL(r, IMAP_QUOTAROOT_NONEXISTENT); CU_ASSERT_PTR_NULL(txn); q.root = QUOTAROOT_NONEXISTANT; r = quota_read(&q, NULL, 0); CU_ASSERT_EQUAL(r, IMAP_QUOTAROOT_NONEXISTENT); } static void test_write_no_root(void) { struct quota q; struct txn *txn = NULL; int r; q.root = NULL; r = quota_write(&q, NULL); CU_ASSERT_EQUAL(r, IMAP_QUOTAROOT_NONEXISTENT); q.root = ""; r = quota_write(&q, NULL); CU_ASSERT_EQUAL(r, IMAP_QUOTAROOT_NONEXISTENT); /* Also, for NULL or "" no txn is started */ q.root = NULL; r = quota_write(&q, &txn); CU_ASSERT_EQUAL(r, IMAP_QUOTAROOT_NONEXISTENT); CU_ASSERT_PTR_NULL(txn); q.root = ""; r = quota_write(&q, &txn); CU_ASSERT_EQUAL(r, IMAP_QUOTAROOT_NONEXISTENT); CU_ASSERT_PTR_NULL(txn); } static void test_read_write(void) { struct quota q; struct quota q2; struct txn *txn = NULL; struct txn *oldtxn = NULL; int res; int r; memset(&q, 0, sizeof(q)); q.root = QUOTAROOT; r = quota_read(&q, &txn, 1); CU_ASSERT_EQUAL(r, IMAP_QUOTAROOT_NONEXISTENT); /* we went to the db and started a transaction */ CU_ASSERT_PTR_NOT_NULL(txn); q.useds[QUOTA_STORAGE] = 12345; q.limits[QUOTA_STORAGE] = 678; q.useds[QUOTA_MESSAGE] = 2345; q.limits[QUOTA_MESSAGE] = 78; q.useds[QUOTA_ANNOTSTORAGE] = 345; q.limits[QUOTA_ANNOTSTORAGE] = 8; oldtxn = txn; r = quota_write(&q, &txn); CU_ASSERT_EQUAL(r, 0); CU_ASSERT_PTR_NOT_NULL(txn); CU_ASSERT_PTR_EQUAL(oldtxn, txn); /* reading in the same txn gets the new values */ memset(&q2, 0, sizeof(q2)); q2.root = QUOTAROOT; r = quota_read(&q2, &txn, 0); CU_ASSERT_EQUAL(r, 0); for (res = 0; res < QUOTA_NUMRESOURCES; res++) { CU_ASSERT_EQUAL(q2.useds[res], q.useds[res]); CU_ASSERT_EQUAL(q2.limits[res], q.limits[res]); } /* commit the txn */ quota_commit(&txn); CU_ASSERT_PTR_NULL(txn); /* reading in a new txn gets the new values */ memset(&q2, 0, sizeof(q2)); q2.root = QUOTAROOT; r = quota_read(&q2, &txn, 0); CU_ASSERT_EQUAL(r, 0); CU_ASSERT_PTR_NOT_NULL(txn); for (res = 0; res < QUOTA_NUMRESOURCES; res++) { CU_ASSERT_EQUAL(q2.useds[res], q.useds[res]); CU_ASSERT_EQUAL(q2.limits[res], q.limits[res]); } quota_commit(&txn); CU_ASSERT_PTR_NULL(txn); } static void test_abort(void) { struct quota q; struct quota q2; struct txn *txn = NULL; struct txn *oldtxn = NULL; int r; memset(&q, 0, sizeof(q)); q.root = QUOTAROOT; r = quota_read(&q, &txn, 1); CU_ASSERT_EQUAL(r, IMAP_QUOTAROOT_NONEXISTENT); /* we went to the db and started a transaction */ CU_ASSERT_PTR_NOT_NULL(txn); q.useds[QUOTA_STORAGE] = 12345; q.limits[QUOTA_STORAGE] = 678; oldtxn = txn; r = quota_write(&q, &txn); CU_ASSERT_EQUAL(r, 0); CU_ASSERT_PTR_NOT_NULL(txn); CU_ASSERT_PTR_EQUAL(oldtxn, txn); /* reading in the same txn gets the new values */ memset(&q2, 0, sizeof(q2)); q2.root = QUOTAROOT; r = quota_read(&q2, &txn, 0); CU_ASSERT_EQUAL(r, 0); CU_ASSERT_EQUAL(q2.useds[QUOTA_STORAGE], q.useds[QUOTA_STORAGE]); CU_ASSERT_EQUAL(q2.limits[QUOTA_STORAGE], q.limits[QUOTA_STORAGE]); /* abort the txn */ quota_abort(&txn); CU_ASSERT_PTR_NULL(txn); /* reading in a new txn gets no result */ memset(&q2, 0, sizeof(q2)); q2.root = QUOTAROOT; r = quota_read(&q2, &txn, 0); CU_ASSERT_EQUAL(r, IMAP_QUOTAROOT_NONEXISTENT); CU_ASSERT_PTR_NOT_NULL(txn); quota_commit(&txn); CU_ASSERT_PTR_NULL(txn); } static void test_abort2(void) { struct quota q; struct quota oldq; struct quota q2; struct txn *txn = NULL; int r; memset(&q, 0, sizeof(q)); q.root = QUOTAROOT; r = quota_read(&q, &txn, 1); CU_ASSERT_EQUAL(r, IMAP_QUOTAROOT_NONEXISTENT); /* we went to the db and started a transaction */ CU_ASSERT_PTR_NOT_NULL(txn); q.useds[QUOTA_STORAGE] = 12345; q.limits[QUOTA_STORAGE] = 678; r = quota_write(&q, &txn); CU_ASSERT_EQUAL(r, 0); CU_ASSERT_PTR_NOT_NULL(txn); /* commit some old values */ quota_commit(&txn); CU_ASSERT_PTR_NULL(txn); /* write some new values */ oldq = q; q.useds[QUOTA_STORAGE] = 23456; q.limits[QUOTA_STORAGE] = 789; r = quota_write(&q, &txn); CU_ASSERT_EQUAL(r, 0); /* reading in the same txn gets the new values */ memset(&q2, 0, sizeof(q2)); q2.root = QUOTAROOT; r = quota_read(&q2, &txn, 0); CU_ASSERT_EQUAL(r, 0); CU_ASSERT_EQUAL(q2.useds[QUOTA_STORAGE], q.useds[QUOTA_STORAGE]); CU_ASSERT_EQUAL(q2.limits[QUOTA_STORAGE], q.limits[QUOTA_STORAGE]); /* abort the txn */ quota_abort(&txn); CU_ASSERT_PTR_NULL(txn); /* reading in a new txn gets old values */ memset(&q2, 0, sizeof(q2)); q2.root = QUOTAROOT; r = quota_read(&q2, &txn, 0); CU_ASSERT_EQUAL(r, 0); CU_ASSERT_PTR_NOT_NULL(txn); CU_ASSERT_EQUAL(q2.useds[QUOTA_STORAGE], oldq.useds[QUOTA_STORAGE]); CU_ASSERT_EQUAL(q2.limits[QUOTA_STORAGE], oldq.limits[QUOTA_STORAGE]); quota_commit(&txn); CU_ASSERT_PTR_NULL(txn); } static void test_check_use(void) { struct quota q; unsigned int i; int r; memset(&q, 0, sizeof(q)); q.root = QUOTAROOT; q.limits[QUOTA_STORAGE] = 100; for (i = 1 ; i <= 63 ; i++) { quota_t diff = (1ULL< 100*1024 ? IMAP_QUOTA_EXCEEDED : 0)); CU_ASSERT_EQUAL(q.useds[QUOTA_STORAGE], 0); } r = quota_check(&q, QUOTA_STORAGE, 10*1024); CU_ASSERT_EQUAL(r, 0); CU_ASSERT_EQUAL(q.useds[QUOTA_STORAGE], 0); quota_use(&q, QUOTA_STORAGE, 10*1024); CU_ASSERT_EQUAL(q.useds[QUOTA_STORAGE], 10*1024); r = quota_check(&q, QUOTA_STORAGE, 80*1024); CU_ASSERT_EQUAL(r, 0); CU_ASSERT_EQUAL(q.useds[QUOTA_STORAGE], 10*1024); quota_use(&q, QUOTA_STORAGE, 80*1024); CU_ASSERT_EQUAL(q.useds[QUOTA_STORAGE], (10+80)*1024); r = quota_check(&q, QUOTA_STORAGE, 15*1024); CU_ASSERT_EQUAL(r, IMAP_QUOTA_EXCEEDED); CU_ASSERT_EQUAL(q.useds[QUOTA_STORAGE], (10+80)*1024); /* test the zero limit */ memset(&q, 0, sizeof(q)); q.root = QUOTAROOT; q.limits[QUOTA_STORAGE] = 0; r = quota_check(&q, QUOTA_STORAGE, 15*1024); CU_ASSERT_EQUAL(r, IMAP_QUOTA_EXCEEDED); CU_ASSERT_EQUAL(q.useds[QUOTA_STORAGE], 0); r = quota_check(&q, QUOTA_STORAGE, 1); CU_ASSERT_EQUAL(r, IMAP_QUOTA_EXCEEDED); CU_ASSERT_EQUAL(q.useds[QUOTA_STORAGE], 0); /* test the special limit QUOTA_UNLIMITED */ memset(&q, 0, sizeof(q)); q.root = QUOTAROOT; q.limits[QUOTA_STORAGE] = QUOTA_UNLIMITED; for (i = 1 ; i <= 63 ; i++) { quota_t diff = (1ULL<root, exphash); CU_ASSERT_PTR_NOT_NULL(expected); CU_ASSERT_STRING_EQUAL(q->root, expected->root); CU_ASSERT_EQUAL(q->useds[QUOTA_STORAGE], expected->useds[QUOTA_STORAGE]); CU_ASSERT_EQUAL(q->limits[QUOTA_STORAGE], expected->limits[QUOTA_STORAGE]); hash_del(q->root, exphash); return 0; } #define FOREACH_PRECONDITION(condition, expcount) \ { \ unsigned int nsubset = 0; \ unsigned int i; \ for (i = 0 ; i <= MAXN ; i++) { \ if ((condition)) { \ hash_insert(expected[i].root, &expected[i], &exphash); \ nsubset++; \ } \ } \ CU_ASSERT_EQUAL(nsubset, expcount); \ CU_ASSERT_EQUAL(hash_count(&exphash), nsubset); \ } #define FOREACH_POSTCONDITION() \ CU_ASSERT_EQUAL(r, 0); \ CU_ASSERT_EQUAL(hash_count(&exphash), 0); #define FOREACH_TEST(prefix, condition, expcount) \ FOREACH_PRECONDITION(condition, expcount); \ r = quota_foreach(prefix, found_cb, &exphash, NULL); \ FOREACH_POSTCONDITION() static void notest_foreach(void) { struct quota q; struct quota q2; struct txn *txn = NULL; unsigned int n; struct quota *expected; hash_table exphash = HASH_TABLE_INITIALIZER; #define MAXN 4095 int r; expected = (struct quota *)xzmalloc((MAXN+1) * sizeof(struct quota)); for (n = 0 ; n <= MAXN ; n++) { expected[n].root = xstrdup(nth_quotaroot(n)); expected[n].useds[QUOTA_STORAGE] = nth_used(n); expected[n].limits[QUOTA_STORAGE] = nth_limit(n); } construct_hash_table(&exphash, (MAXN+1)*4, 0); /* add records to the db */ for (n = 0 ; n <= MAXN ; n++) { q = expected[n]; r = quota_write(&q, &txn); CU_ASSERT_EQUAL(r, 0); CU_ASSERT_PTR_NOT_NULL(txn); } quota_commit(&txn); CU_ASSERT_PTR_NULL(txn); /* check the records all made it */ for (n = 0 ; n <= MAXN ; n++) { memset(&q2, 0, sizeof(q2)); q2.root = nth_quotaroot(n); r = quota_read(&q2, NULL, 0); CU_ASSERT_EQUAL(r, 0); CU_ASSERT_EQUAL(q2.useds[QUOTA_STORAGE], expected[n].useds[QUOTA_STORAGE]); CU_ASSERT_EQUAL(q2.limits[QUOTA_STORAGE], expected[n].limits[QUOTA_STORAGE]); } /* prefix=NULL: iterate all the records */ FOREACH_TEST(NULL, 1, MAXN+1); /* prefix="": iterate all the records */ FOREACH_TEST("", 1, MAXN+1); /* prefix=a common prefix: iterate all the records */ FOREACH_TEST("user.", 1, MAXN+1); /* prefix=an uncommon prefix: iterate some of the records */ FOREACH_TEST("user.epilogs", i / 1000 == 1, 1000); /* delete records one by one, checking that foreach * walks over the expected number at each point */ for (n = 0 ; n <= MAXN ; n++) { r = quota_deleteroot(nth_quotaroot(n)); CU_ASSERT_EQUAL(r, 0); if (n && n % 301 == 0) { FOREACH_TEST("user.", i > n, MAXN-n); } } free_hash_table(&exphash, NULL); for (n = 0 ; n <= MAXN ; n++) free((char *)expected[n].root); free(expected); #undef MAXN } #endif /* * TODO: should test for quota_foreach() iteration order, * with and without IMAPOPT_IMPROVED_MBOXLIST_SORT set. * There is code that depends on it, e.g. for quota -f. */ /* Note that quota_findroot() returns 0 (not found) * or 1 (found) and never an error code. */ #define TESTCASE(in, exp) \ { \ const char *expected = (exp); \ int r; \ char res[1024]; \ r = quota_findroot(res, sizeof(res), (in)); \ if (expected) { \ CU_ASSERT_EQUAL(r, 1); \ CU_ASSERT_STRING_EQUAL(res, expected); \ } \ else { \ CU_ASSERT_EQUAL(r, 0); \ /* contents of res[] not defined */ \ } \ } static void test_findroot(void) { struct quota q; struct txn *txn = NULL; int r; memset(&q, 0, sizeof(q)); q.useds[QUOTA_STORAGE] = 123; q.limits[QUOTA_STORAGE] = 456; /* * behaviour when the database is empty: * there is no root to be found */ TESTCASE("user.foo.bar.baz", NULL); TESTCASE("user.foo.quux", NULL); TESTCASE("user.foo", NULL); TESTCASE("user.foonly", NULL); TESTCASE("user.fo", NULL); TESTCASE("user.smeg", NULL); TESTCASE("user.smeg.fridge", NULL); TESTCASE("user.farnarkle", NULL); /* add some db entries, but not the "user." */ q.root = "user.foo"; r = quota_write(&q, &txn); CU_ASSERT_EQUAL(r, 0); q.root = "user.smeg"; r = quota_write(&q, &txn); CU_ASSERT_EQUAL(r, 0); CU_ASSERT_PTR_NOT_NULL(txn); quota_commit(&txn); CU_ASSERT_PTR_NULL(txn); /* * behaviour with these new entries */ /* "user.foo" and its subfolders match the "user.foo" root */ TESTCASE("user.foo.bar.baz", "user.foo"); TESTCASE("user.foo.quux", "user.foo"); TESTCASE("user.foo", "user.foo"); /* "user.foonly" doesn't match "user.foo" despite the leading * 8 characters being the same */ TESTCASE("user.foonly", NULL); /* "user.fo" doesn't match "user.foo" despite the leading * 7 characters being the same */ TESTCASE("user.fo", NULL); /* "user.smeg" and its subfolders matches the "user.smeg" root */ TESTCASE("user.smeg", "user.smeg"); TESTCASE("user.smeg.fridge", "user.smeg"); /* no root matches at all for "user.farnarkle" */ TESTCASE("user.farnarkle", NULL); /* add a catch-all "user" record */ q.root = "user"; r = quota_write(&q, &txn); CU_ASSERT_EQUAL(r, 0); CU_ASSERT_PTR_NOT_NULL(txn); quota_commit(&txn); CU_ASSERT_PTR_NULL(txn); /* * behaviour with these new entries */ /* "user.foo" unchanged */ TESTCASE("user.foo.bar.baz", "user.foo"); TESTCASE("user.foo.quux", "user.foo"); TESTCASE("user.foo", "user.foo"); /* "user.foonly" matches the catch-all */ TESTCASE("user.foonly", "user"); /* "user.fo" ditto */ TESTCASE("user.fo", "user"); /* "user.smeg" unchanged */ TESTCASE("user.smeg", "user.smeg"); TESTCASE("user.smeg.fridge", "user.smeg"); /* "user.farnarkle" matches the catch-all */ TESTCASE("user.farnarkle", "user"); } static void test_findroot_virtdomains(void) { struct quota q; struct txn *txn = NULL; int r; config_virtdomains = IMAP_ENUM_VIRTDOMAINS_ON; /* this shouldn't matter, quota_findroot() doesn't use it */ config_defdomain = "smaak.nl"; memset(&q, 0, sizeof(q)); q.useds[QUOTA_STORAGE] = 123; q.limits[QUOTA_STORAGE] = 456; /* * behaviour when the database is empty: * there is no root to be found */ TESTCASE("bloggs.com!user.foo.bar.baz", NULL); TESTCASE("bloggs.com!user.foo.quux", NULL); TESTCASE("bloggs.com!user.foo", NULL); TESTCASE("fnarp.org!user.foo.bar.baz", NULL); TESTCASE("fnarp.org!user.foo.quux", NULL); TESTCASE("fnarp.org!user.foo", NULL); TESTCASE("user.foo.bar.baz", NULL); TESTCASE("user.foo.quux", NULL); TESTCASE("user.foo", NULL); TESTCASE("bloggs.com!user.smeg", NULL); TESTCASE("bloggs.com!user.smeg.fridge", NULL); TESTCASE("fnarp.org!user.smeg", NULL); TESTCASE("fnarp.org!user.smeg.fridge", NULL); TESTCASE("user.smeg", NULL); TESTCASE("user.smeg.fridge", NULL); TESTCASE("bloggs.com!user.farnarkle", NULL); TESTCASE("fnarp.org!user.farnarkle", NULL); TESTCASE("user.farnarkle", NULL); /* add some db entries for bloggs.com, but not fnarp.org, * not the default domain, and not the "user." */ q.root = "bloggs.com!user.foo"; r = quota_write(&q, &txn); CU_ASSERT_EQUAL(r, 0); q.root = "bloggs.com!user.smeg"; r = quota_write(&q, &txn); CU_ASSERT_EQUAL(r, 0); CU_ASSERT_PTR_NOT_NULL(txn); quota_commit(&txn); CU_ASSERT_PTR_NULL(txn); /* * behaviour with these new entries */ /* foo@bloggs.com's home and its subfolders match * the "bloggs.com!user.foo" root */ TESTCASE("bloggs.com!user.foo.bar.baz", "bloggs.com!user.foo"); TESTCASE("bloggs.com!user.foo.quux", "bloggs.com!user.foo"); TESTCASE("bloggs.com!user.foo", "bloggs.com!user.foo"); /* foo@fnarp.org's home and its subfolders don't match anything */ TESTCASE("fnarp.org!user.foo.bar.baz", NULL); TESTCASE("fnarp.org!user.foo.quux", NULL); TESTCASE("fnarp.org!user.foo", NULL); /* foo's home and its subfolders don't match anything */ TESTCASE("user.foo.bar.baz", NULL); TESTCASE("user.foo.quux", NULL); TESTCASE("user.foo", NULL); /* smeg@bloggs.com's home and its subfolders match * the "bloggs.com!user.smeg" root */ TESTCASE("bloggs.com!user.smeg", "bloggs.com!user.smeg"); TESTCASE("bloggs.com!user.smeg.fridge", "bloggs.com!user.smeg"); /* smeg@fnarp.org's home and its subfolders don't match anything */ TESTCASE("fnarp.org!user.smeg", NULL); TESTCASE("fnarp.org!user.smeg.fridge", NULL); /* smeg's home and its subfolders don't match anything */ TESTCASE("user.smeg", NULL); TESTCASE("user.smeg.fridge", NULL); /* no root matches at all for "user.farnarkle" in any domain */ TESTCASE("bloggs.com!user.farnarkle", NULL); TESTCASE("fnarp.org!user.farnarkle", NULL); TESTCASE("user.farnarkle", NULL); /* add a catch-all "bloggs.com" record */ q.root = "bloggs.com!"; r = quota_write(&q, &txn); CU_ASSERT_EQUAL(r, 0); CU_ASSERT_PTR_NOT_NULL(txn); quota_commit(&txn); CU_ASSERT_PTR_NULL(txn); /* * behaviour with these new entries */ /* foo@bloggs.com unchanged */ TESTCASE("bloggs.com!user.foo.bar.baz", "bloggs.com!user.foo"); TESTCASE("bloggs.com!user.foo.quux", "bloggs.com!user.foo"); TESTCASE("bloggs.com!user.foo", "bloggs.com!user.foo"); /* foo@fnarp.org's unchanged */ TESTCASE("fnarp.org!user.foo.bar.baz", NULL); TESTCASE("fnarp.org!user.foo.quux", NULL); TESTCASE("fnarp.org!user.foo", NULL); /* foo unchanged */ TESTCASE("user.foo.bar.baz", NULL); TESTCASE("user.foo.quux", NULL); TESTCASE("user.foo", NULL); /* smeg@bloggs.com unchanged */ TESTCASE("bloggs.com!user.smeg", "bloggs.com!user.smeg"); TESTCASE("bloggs.com!user.smeg.fridge", "bloggs.com!user.smeg"); /* smeg@fnarp.org unchanged */ TESTCASE("fnarp.org!user.smeg", NULL); TESTCASE("fnarp.org!user.smeg.fridge", NULL); /* smeg unchanged */ TESTCASE("user.smeg", NULL); TESTCASE("user.smeg.fridge", NULL); /* farnarkle@bloggs.com matches the bloggs.com catch-all */ TESTCASE("bloggs.com!user.farnarkle", "bloggs.com!"); /* farnarkle at other domains unchanged */ TESTCASE("fnarp.org!user.farnarkle", NULL); TESTCASE("user.farnarkle", NULL); /* add a catch-all "fnarp.org!user" record */ q.root = "fnarp.org!user"; r = quota_write(&q, &txn); CU_ASSERT_EQUAL(r, 0); CU_ASSERT_PTR_NOT_NULL(txn); quota_commit(&txn); CU_ASSERT_PTR_NULL(txn); /* * behaviour with these new entries */ /* foo@bloggs.com unchanged */ TESTCASE("bloggs.com!user.foo.bar.baz", "bloggs.com!user.foo"); TESTCASE("bloggs.com!user.foo.quux", "bloggs.com!user.foo"); TESTCASE("bloggs.com!user.foo", "bloggs.com!user.foo"); /* foo@fnarp.org's matches the fnarp.org catch-all */ TESTCASE("fnarp.org!user.foo.bar.baz", "fnarp.org!user"); TESTCASE("fnarp.org!user.foo.quux", "fnarp.org!user"); TESTCASE("fnarp.org!user.foo", "fnarp.org!user"); /* foo unchanged */ TESTCASE("user.foo.bar.baz", NULL); TESTCASE("user.foo.quux", NULL); TESTCASE("user.foo", NULL); /* smeg@bloggs.com unchanged */ TESTCASE("bloggs.com!user.smeg", "bloggs.com!user.smeg"); TESTCASE("bloggs.com!user.smeg.fridge", "bloggs.com!user.smeg"); /* smeg@fnarp.org matches the fnarp.org catch-all */ TESTCASE("fnarp.org!user.smeg", "fnarp.org!user"); TESTCASE("fnarp.org!user.smeg.fridge", "fnarp.org!user"); /* smeg unchanged */ TESTCASE("user.smeg", NULL); TESTCASE("user.smeg.fridge", NULL); /* farnarkle@bloggs.com matches the bloggs.com catch-all */ TESTCASE("bloggs.com!user.farnarkle", "bloggs.com!"); /* farnarkle@fnarp.org matches the fnarp.org catch-all */ TESTCASE("fnarp.org!user.farnarkle", "fnarp.org!user"); /* farnarkle in the default domain unchanged */ TESTCASE("user.farnarkle", NULL); } #undef TESTCASE static void config_read_string(const char *s) { char *fname = xstrdup("/tmp/cyrus-cunit-configXXXXXX"); int fd = mkstemp(fname); retry_write(fd, s, strlen(s)); config_reset(); config_read(fname, 0); unlink(fname); free(fname); close(fd); } static int set_up(void) { int r; const char * const *d; static const char * const dirs[] = { DBDIR, DBDIR"/db", NULL }; r = system("rm -rf " DBDIR); if (r) return r; for (d = dirs ; *d ; d++) { r = mkdir(*d, 0777); if (r < 0) { int e = errno; perror(*d); return e; } } libcyrus_config_setstring(CYRUSOPT_CONFIG_DIR, DBDIR); config_read_string( "configdirectory: "DBDIR"/conf\n" ); cyrusdb_init(); config_quota_db = "skiplist"; quotadb_init(0); quotadb_open(NULL); return 0; } static int tear_down(void) { int r; quotadb_close(); quotadb_done(); cyrusdb_done(); config_quota_db = NULL; config_reset(); r = system("rm -rf " DBDIR); if (r) r = -1; return r; } /* vim: set ft=c: */ cyrus-imapd-2.5.10/cunit/crc32.testc0000644000175000017500000000135313001236020014044 00000000000000/* Unit test for lib/crc32.c */ #include "cunit/cunit.h" #include "crc32.h" static void test_map(void) { static const char TEXT[] = "lorem ipsum"; static uint32_t CRC32 = 0x72d7748e; uint32_t c; c = crc32_map(TEXT, sizeof(TEXT)-1); CU_ASSERT_EQUAL(c, CRC32); } static void test_iovec(void) { static const char TEXT1[] = "lorem"; static const char TEXT2[] = " ipsum"; static uint32_t CRC32 = 0x72d7748e; uint32_t c; struct iovec iov[2]; memset(iov, 0, sizeof(iov)); iov[0].iov_base = (char *)TEXT1; iov[0].iov_len = sizeof(TEXT1)-1; iov[1].iov_base = (char *)TEXT2; iov[1].iov_len = sizeof(TEXT2)-1; c = crc32_iovec(iov, 2); CU_ASSERT_EQUAL(c, CRC32); } /* vim: set ft=c: */ cyrus-imapd-2.5.10/cunit/prot.testc0000644000175000017500000001334513001236020014120 00000000000000#include "config.h" #include "cunit/cunit.h" #include #include "xmalloc.h" #include "prot.h" #include "imap/global.h" #define PROLOG \ char *_fname = xstrdup("/tmp/cyrus-protXXXXXX"); \ int _fd = mkstemp(_fname) #define BEGIN \ { \ int r = ftruncate(_fd, 0); \ CU_ASSERT_EQUAL_FATAL(r, 0); \ lseek(_fd, (off_t)0, SEEK_SET); \ } #define END(b, n) \ { \ struct stat _sb; \ lseek(_fd, (off_t)0, SEEK_SET); \ if (fstat(_fd, &_sb) < 0) CU_FAIL_FATAL("fstat"); \ (n) = read(_fd, (b), _sb.st_size); \ if ((n) < _sb.st_size) CU_FAIL_FATAL("short read"); \ if ((n) >= 0) (b)[(n)] = '\0'; \ } #define EPILOG \ unlink(_fname); \ free(_fname); \ close(_fd) static void test_printstring(void) { PROLOG; struct protstream *p; int len; struct buf b = BUF_INITIALIZER; int i; char str[2600]; p = prot_new(_fd, 1); CU_ASSERT_PTR_NOT_NULL_FATAL(p); /* NULL string */ BEGIN; prot_printstring(p, NULL); prot_flush(p); END(str, len); CU_ASSERT_EQUAL(len, 3); CU_ASSERT_STRING_EQUAL(str, "NIL"); /* Zero length string */ BEGIN; prot_printstring(p, ""); prot_flush(p); END(str, len); CU_ASSERT_EQUAL(len, 2); CU_ASSERT_STRING_EQUAL(str, "\"\""); /* Boring string */ BEGIN; prot_printstring(p, "Hello"); prot_flush(p); END(str, len); CU_ASSERT_EQUAL(len, 7); CU_ASSERT_STRING_EQUAL(str, "\"Hello\""); /* String with non-dangerous whitespace */ BEGIN; prot_printstring(p, "Hello World\tagain"); prot_flush(p); END(str, len); CU_ASSERT_EQUAL(len, 19); CU_ASSERT_STRING_EQUAL(str, "\"Hello World\tagain\""); /* String with dangerous whitespace */ BEGIN; prot_printstring(p, "Good\rBye\nEarth"); prot_flush(p); END(str, len); CU_ASSERT_EQUAL(len, 20); CU_ASSERT_STRING_EQUAL(str, "{14}\r\nGood\rBye\nEarth"); /* String with embedded dquote */ BEGIN; prot_printstring(p, "Quot\"able"); prot_flush(p); END(str, len); CU_ASSERT_EQUAL(len, 14); CU_ASSERT_STRING_EQUAL(str, "{9}\r\nQuot\"able"); /* String with embedded percent */ BEGIN; prot_printstring(p, "per%ent"); prot_flush(p); END(str, len); CU_ASSERT_EQUAL(len, 12); CU_ASSERT(!strcmp(str, "{7}\r\nper%ent")); /* String with embedded backslash */ BEGIN; prot_printstring(p, "slash\\dot"); prot_flush(p); END(str, len); CU_ASSERT_EQUAL(len, 14); CU_ASSERT_STRING_EQUAL(str, "{9}\r\nslash\\dot"); /* String with embedded 8-bit chars */ BEGIN; prot_printstring(p, "Hi I'm \330l\345f"); prot_flush(p); END(str, len); CU_ASSERT_EQUAL(len, 17); CU_ASSERT_STRING_EQUAL(str, "{11}\r\nHi I'm \330l\345f"); /* Boring but overly long string */ for (i = 0 ; i<500 ; i++) buf_appendcstr(&b, "blah "); buf_cstring(&b); BEGIN; prot_printstring(p, b.s); prot_flush(p); END(str, len); CU_ASSERT_EQUAL(len, b.len+8); CU_ASSERT_STRING_EQUAL(str+8, b.s); str[8] = '\0'; CU_ASSERT_STRING_EQUAL(str, "{2500}\r\n"); buf_free(&b); prot_free(p); EPILOG; } static void test_printmap(void) { PROLOG; struct protstream *p; int len; struct buf b = BUF_INITIALIZER; int i; char str[2600]; p = prot_new(_fd, 1); CU_ASSERT_PTR_NOT_NULL_FATAL(p); /* NULL string */ BEGIN; prot_printmap(p, NULL, 0); prot_flush(p); END(str, len); CU_ASSERT_EQUAL(len, 3); CU_ASSERT_STRING_EQUAL(str, "NIL"); /* Zero length string */ BEGIN; prot_printmap(p, "", 0); prot_flush(p); END(str, len); CU_ASSERT_EQUAL(len, 2); CU_ASSERT_STRING_EQUAL(str, "\"\""); /* Boring string */ BEGIN; prot_printmap(p, "Hello", 5); prot_flush(p); END(str, len); CU_ASSERT_EQUAL(len, 7); CU_ASSERT_STRING_EQUAL(str, "\"Hello\""); /* Boring string with short length */ BEGIN; prot_printmap(p, "Hello", 3); prot_flush(p); END(str, len); CU_ASSERT_EQUAL(len, 5); CU_ASSERT_STRING_EQUAL(str, "\"Hel\""); /* String with non-dangerous whitespace */ BEGIN; prot_printmap(p, "Hello World\tagain", 17); prot_flush(p); END(str, len); CU_ASSERT_EQUAL(len, 19); CU_ASSERT_STRING_EQUAL(str, "\"Hello World\tagain\""); /* String with dangerous whitespace */ BEGIN; prot_printmap(p, "Good\rBye\nEarth", 14); prot_flush(p); END(str, len); CU_ASSERT_EQUAL(len, 20); CU_ASSERT_STRING_EQUAL(str, "{14}\r\nGood\rBye\nEarth"); /* String with embedded dquote */ BEGIN; prot_printmap(p, "Quot\"able", 9); prot_flush(p); END(str, len); CU_ASSERT_EQUAL(len, 14); CU_ASSERT_STRING_EQUAL(str, "{9}\r\nQuot\"able"); /* String with embedded percent */ BEGIN; prot_printmap(p, "per%ent", 7); prot_flush(p); END(str, len); CU_ASSERT_EQUAL(len, 12); CU_ASSERT(!strcmp(str, "{7}\r\nper%ent")); /* String with embedded backslash */ BEGIN; prot_printmap(p, "slash\\dot", 9); prot_flush(p); END(str, len); CU_ASSERT_EQUAL(len, 14); CU_ASSERT_STRING_EQUAL(str, "{9}\r\nslash\\dot"); /* String with embedded 8-bit chars */ BEGIN; prot_printmap(p, "Hi I'm \330l\345f", 11); prot_flush(p); END(str, len); CU_ASSERT_EQUAL(len, 17); CU_ASSERT_STRING_EQUAL(str, "{11}\r\nHi I'm \330l\345f"); /* Boring but overly long string */ for (i = 0 ; i<500 ; i++) buf_appendcstr(&b, "blah "); buf_cstring(&b); BEGIN; prot_printmap(p, b.s, b.len); prot_flush(p); END(str, len); CU_ASSERT_EQUAL(len, b.len+8); CU_ASSERT_STRING_EQUAL(str+8, b.s); str[8] = '\0'; CU_ASSERT_STRING_EQUAL(str, "{2500}\r\n"); buf_free(&b); prot_free(p); EPILOG; } /* vim: set ft=c: */ cyrus-imapd-2.5.10/cunit/message.testc0000644000175000017500000006541713001236020014567 00000000000000#if HAVE_CONFIG_H #include #endif #include "cunit/cunit.h" #include "parseaddr.h" #include "util.h" #include "imap/message.h" static void test_parse_trivial(void) { static const char msg[] = "From: Fred Bloggs \r\n" "To: Sarah Jane Smith \r\n" "Date: Wed, 27 Oct 2010 18:37:26 +1100\r\n" "Subject: Trivial testing email\r\n" "Message-ID: \r\n" "X-Mailer: Norman\r\n" "\r\n" "Hello, World\n"; int r; struct body body; memset(&body, 0x45, sizeof(body)); r = message_parse_mapped(msg, sizeof(msg)-1, &body); CU_ASSERT_EQUAL(r, 0); /* From: Fred Bloggs */ CU_ASSERT_PTR_NOT_NULL_FATAL(body.from); CU_ASSERT_STRING_EQUAL(body.from->name, "Fred Bloggs"); CU_ASSERT_STRING_EQUAL(body.from->mailbox, "fbloggs"); CU_ASSERT_STRING_EQUAL(body.from->domain, "fastmail.fm"); CU_ASSERT_PTR_NULL(body.from->next); CU_ASSERT_PTR_NULL(body.reply_to); /* To: Sarah Jane Smith */ CU_ASSERT_PTR_NOT_NULL_FATAL(body.to); CU_ASSERT_STRING_EQUAL(body.to->name, "Sarah Jane Smith"); CU_ASSERT_STRING_EQUAL(body.to->mailbox, "sjsmith"); CU_ASSERT_STRING_EQUAL(body.to->domain, "gmail.com"); CU_ASSERT_PTR_NULL(body.to->next); CU_ASSERT_PTR_NULL(body.cc); CU_ASSERT_PTR_NULL(body.bcc); /* Date: Wed, 27 Oct 2010 18:37:26 +1100 */ CU_ASSERT_STRING_EQUAL(body.date, "Wed, 27 Oct 2010 18:37:26 +1100"); /* Subject: Trivial testing email */ CU_ASSERT_STRING_EQUAL(body.subject, "Trivial testing email"); /* Content-Type not specified, this is the default */ CU_ASSERT_STRING_EQUAL(body.type, "TEXT"); CU_ASSERT_STRING_EQUAL(body.subtype, "PLAIN"); CU_ASSERT_PTR_NOT_NULL(body.params); CU_ASSERT_STRING_EQUAL(body.params->attribute, "CHARSET"); CU_ASSERT_STRING_EQUAL(body.params->value, "us-ascii"); CU_ASSERT_PTR_NULL(body.params->next); CU_ASSERT_PTR_NULL(body.language); /* Message-ID: */ CU_ASSERT_STRING_EQUAL(body.message_id, ""); CU_ASSERT_PTR_NULL(body.in_reply_to); CU_ASSERT_PTR_NULL(body.references); CU_ASSERT_PTR_NULL(body.received_date); /* simple body */ CU_ASSERT_EQUAL(body.numparts, 0); CU_ASSERT_PTR_NULL(body.subpart); /* check cacheheaders */ CU_ASSERT_PTR_NOT_NULL_FATAL(body.cacheheaders.s); CU_ASSERT(strstr(body.cacheheaders.s, "Norman") != NULL); message_free_body(&body); } static void test_parse_simple(void) { static const char msg[] = "From: Fred Bloggs \r\n" "Reply-To: \r\n" "To: Sarah Jane Smith \r\n" "Cc: Al Capone \r\n" "Bcc: Bugsy Moran \r\n" "Date: Thu, 28 Oct 2010 18:37:26 +1100\r\n" "Subject: Simple testing email\r\n" "Content-Type: text/plain; charset=\"utf-8\"\r\n" "Content-Language: en\r\n" "Message-ID: \r\n" "X-Mailer: Norman\r\n" "In-Reply-To: \r\n" "Received: from foo.fastmail.fm (foo.fastmail.fm [10.0.0.1])\r\n" "\tby bar.gmail.com (Software); Thu, 28 Oct 2010 18:55:54 +1100\r\n" "\r\n" "Hello, World\n"; int r; struct body body; memset(&body, 0x45, sizeof(body)); r = message_parse_mapped(msg, sizeof(msg)-1, &body); CU_ASSERT_EQUAL(r, 0); /* From: Fred Bloggs */ CU_ASSERT_PTR_NOT_NULL_FATAL(body.from); CU_ASSERT_STRING_EQUAL(body.from->name, "Fred Bloggs"); CU_ASSERT_STRING_EQUAL(body.from->mailbox, "fbloggs"); CU_ASSERT_STRING_EQUAL(body.from->domain, "fastmail.fm"); CU_ASSERT_PTR_NULL(body.from->next); /* Reply-To: */ CU_ASSERT_PTR_NOT_NULL_FATAL(body.reply_to); CU_ASSERT_PTR_NULL(body.reply_to->name); CU_ASSERT_STRING_EQUAL(body.reply_to->mailbox, "bounce.me.harder"); CU_ASSERT_STRING_EQUAL(body.reply_to->domain, "fastmail.fm"); CU_ASSERT_PTR_NULL(body.reply_to->next); /* To: Sarah Jane Smith */ CU_ASSERT_PTR_NOT_NULL_FATAL(body.to); CU_ASSERT_STRING_EQUAL(body.to->name, "Sarah Jane Smith"); CU_ASSERT_STRING_EQUAL(body.to->mailbox, "sjsmith"); CU_ASSERT_STRING_EQUAL(body.to->domain, "gmail.com"); CU_ASSERT_PTR_NULL(body.to->next); /* Cc: Al Capone */ CU_ASSERT_PTR_NOT_NULL_FATAL(body.cc); CU_ASSERT_STRING_EQUAL(body.cc->name, "Al Capone"); CU_ASSERT_STRING_EQUAL(body.cc->mailbox, "al"); CU_ASSERT_STRING_EQUAL(body.cc->domain, "speakeasy.com"); CU_ASSERT_PTR_NULL(body.cc->next); /* Bcc: Bugsy Moran */ CU_ASSERT_PTR_NOT_NULL_FATAL(body.bcc); CU_ASSERT_STRING_EQUAL(body.bcc->name, "Bugsy Moran"); CU_ASSERT_STRING_EQUAL(body.bcc->mailbox, "bugsy"); CU_ASSERT_STRING_EQUAL(body.bcc->domain, "garage.com"); CU_ASSERT_PTR_NULL(body.bcc->next); /* Date: Thu, 28 Oct 2010 18:37:26 +1100 */ CU_ASSERT_STRING_EQUAL(body.date, "Thu, 28 Oct 2010 18:37:26 +1100"); /* Subject: Simple testing email */ CU_ASSERT_STRING_EQUAL(body.subject, "Simple testing email"); /* Content-Type: text/plain; charset="utf-8" */ CU_ASSERT_STRING_EQUAL(body.type, "TEXT"); CU_ASSERT_STRING_EQUAL(body.subtype, "PLAIN"); CU_ASSERT_PTR_NOT_NULL(body.params); CU_ASSERT_STRING_EQUAL(body.params->attribute, "CHARSET"); CU_ASSERT_STRING_EQUAL(body.params->value, "utf-8"); CU_ASSERT_PTR_NULL(body.params->next); /* Content-Language: en */ CU_ASSERT_PTR_NOT_NULL(body.language); CU_ASSERT_PTR_NULL(body.language->attribute); CU_ASSERT_STRING_EQUAL(body.language->value, "EN"); CU_ASSERT_PTR_NULL(body.language->next); /* Message-ID: */ CU_ASSERT_STRING_EQUAL(body.message_id, ""); /* In-Reply-To: */ CU_ASSERT_STRING_EQUAL(body.in_reply_to, ""); CU_ASSERT_PTR_NULL(body.references); /* Received: from foo.fastmail.fm (foo.fastmail.fm [10.0.0.1]) ... */ CU_ASSERT_STRING_EQUAL(body.received_date, "Thu, 28 Oct 2010 18:55:54 +1100"); /* simple body */ CU_ASSERT_EQUAL(body.numparts, 0); CU_ASSERT_PTR_NULL(body.subpart); /* check cacheheaders */ CU_ASSERT_PTR_NOT_NULL_FATAL(body.cacheheaders.s); CU_ASSERT(strstr(body.cacheheaders.s, "Norman") != NULL); message_free_body(&body); } /* * There are two different headers from which we can extract * the body.received_date field. Test that the rules for * choosing which date are correctly applied. */ static void test_parse_rxdate(void) { #define DELIVERED "Fri, 29 Oct 2010 13:07:07 +1100" #define FIRST_RX "Fri, 29 Oct 2010 13:05:01 +1100" #define SECOND_RX "Fri, 29 Oct 2010 13:03:03 +1100" #define THIRD_RX "Fri, 29 Oct 2010 13:01:01 +1100" #define SENT "Thu, 28 Oct 2010 18:37:26 +1100" /* Message has neither Received: nor X-DeliveredInternalDate headers. */ static const char msg_neither[] = "From: Fred Bloggs \r\n" "To: Sarah Jane Smith \r\n" "Date: " SENT "\r\n" "Subject: Simple testing email\r\n" "Message-ID: \r\n" "\r\n" "Hello, World\n"; /* Message has only Received: headers. */ static const char msg_only_received[] = "From: Fred Bloggs \r\n" "To: Sarah Jane Smith \r\n" "Date: " SENT "\r\n" "Subject: Simple testing email\r\n" "Message-ID: \r\n" "Received: from mail.quux.com (mail.quux.com [10.0.0.1])\r\n" "\tby mail.gmail.com (Software); " FIRST_RX "\r\n" "Received: from mail.bar.com (mail.bar.com [10.0.0.1])\r\n" "\tby mail.quux.com (Software); " SECOND_RX "\r\n" "Received: from mail.fastmail.fm (mail.fastmail.fm [10.0.0.1])\r\n" "\tby mail.bar.com (Software); " THIRD_RX "\r\n" "\r\n" "Hello, World\n"; /* Message has only X-DeliveredInternalDate (weird!) */ static const char msg_only_xdid[] = "From: Fred Bloggs \r\n" "To: Sarah Jane Smith \r\n" "Date: " SENT "\r\n" "Subject: Simple testing email\r\n" "Message-ID: \r\n" "X-Deliveredinternaldate: " DELIVERED "\r\n" "\r\n" "Hello, World\n"; /* Message has both Received and X-DeliveredInternalDate in that order */ static const char msg_received_then_xdid[] = "From: Fred Bloggs \r\n" "To: Sarah Jane Smith \r\n" "Date: " SENT "\r\n" "Subject: Simple testing email\r\n" "Message-ID: \r\n" "Received: from mail.quux.com (mail.quux.com [10.0.0.1])\r\n" "\tby mail.gmail.com (Software); " FIRST_RX "\r\n" "Received: from mail.bar.com (mail.bar.com [10.0.0.1])\r\n" "\tby mail.quux.com (Software); " SECOND_RX "\r\n" "Received: from mail.fastmail.fm (mail.fastmail.fm [10.0.0.1])\r\n" "\tby mail.bar.com (Software); " THIRD_RX "\r\n" "X-Deliveredinternaldate: " DELIVERED "\r\n" "\r\n" "Hello, World\n"; /* Message has both X-DeliveredInternalDate and Received in that order */ static const char msg_xdid_then_received[] = "From: Fred Bloggs \r\n" "To: Sarah Jane Smith \r\n" "Date: " SENT "\r\n" "Subject: Simple testing email\r\n" "Message-ID: \r\n" "X-Deliveredinternaldate: " DELIVERED "\r\n" "Received: from mail.quux.com (mail.quux.com [10.0.0.1])\r\n" "\tby mail.gmail.com (Software); " FIRST_RX "\r\n" "Received: from mail.bar.com (mail.bar.com [10.0.0.1])\r\n" "\tby mail.quux.com (Software); " SECOND_RX "\r\n" "Received: from mail.fastmail.fm (mail.fastmail.fm [10.0.0.1])\r\n" "\tby mail.bar.com (Software); " THIRD_RX "\r\n" "\r\n" "Hello, World\n"; int r; struct body body; /* Neither: no received_date */ memset(&body, 0x45, sizeof(body)); r = message_parse_mapped(msg_neither, sizeof(msg_neither)-1, &body); CU_ASSERT_EQUAL(r, 0); CU_ASSERT_PTR_NULL(body.received_date); message_free_body(&body); /* Received only: first seen Received */ memset(&body, 0x45, sizeof(body)); r = message_parse_mapped(msg_only_received, sizeof(msg_only_received)-1, &body); CU_ASSERT_EQUAL(r, 0); CU_ASSERT_STRING_EQUAL(body.received_date, FIRST_RX); message_free_body(&body); /* X-DeliveredInternalDate only: use that */ memset(&body, 0x45, sizeof(body)); r = message_parse_mapped(msg_only_xdid, sizeof(msg_only_xdid)-1, &body); CU_ASSERT_EQUAL(r, 0); CU_ASSERT_STRING_EQUAL(body.received_date, DELIVERED); message_free_body(&body); /* both, Received first: use X-DeliveredInternalDate */ memset(&body, 0x45, sizeof(body)); r = message_parse_mapped(msg_received_then_xdid, sizeof(msg_received_then_xdid)-1, &body); CU_ASSERT_EQUAL(r, 0); CU_ASSERT_STRING_EQUAL(body.received_date, DELIVERED); message_free_body(&body); /* both, X-DeliveredInternalDate first: use X-DeliveredInternalDate */ memset(&body, 0x45, sizeof(body)); r = message_parse_mapped(msg_xdid_then_received, sizeof(msg_xdid_then_received)-1, &body); CU_ASSERT_EQUAL(r, 0); CU_ASSERT_STRING_EQUAL(body.received_date, DELIVERED); message_free_body(&body); } static void test_mime_trivial(void) { static const char msg[] = "From: Fred Bloggs \r\n" "Reply-To: \r\n" "To: Sarah Jane Smith \r\n" "Date: Thu, 28 Oct 2010 18:37:26 +1100\r\n" "Subject: MIME testing email\r\n" "X-Mailer: Norman\r\n" "MIME-Version: 1.0\r\n" "Content-Type: multipart/mixed; boundary=\"2b47bc7b64285b8be25dcdca86fbc501b048eab1\"\r\n" "Content-Language: en\r\n" "Message-ID: \r\n" "\r\n" "--2b47bc7b64285b8be25dcdca86fbc501b048eab1\r\n" "\r\n" "Hello, World\n" "\r\n--2b47bc7b64285b8be25dcdca86fbc501b048eab1--\r\n"; int r; struct body body; memset(&body, 0x45, sizeof(body)); r = message_parse_mapped(msg, sizeof(msg)-1, &body); CU_ASSERT_EQUAL(r, 0); /* Content-Type: */ CU_ASSERT_STRING_EQUAL(body.type, "MULTIPART"); CU_ASSERT_STRING_EQUAL(body.subtype, "MIXED"); CU_ASSERT_PTR_NOT_NULL(body.params); CU_ASSERT_STRING_EQUAL(body.params->attribute, "BOUNDARY"); CU_ASSERT_STRING_EQUAL(body.params->value, "2b47bc7b64285b8be25dcdca86fbc501b048eab1"); CU_ASSERT_PTR_NULL(body.params->next); /* * RFC2046 says that all headers and in particular the Content-Type: * header may be missing in an entity, and if so the default * Content-Type is text/plain;charset="us-ascii" */ /* simple body */ CU_ASSERT_EQUAL(body.numparts, 1); CU_ASSERT_PTR_NOT_NULL(body.subpart); CU_ASSERT_STRING_EQUAL(body.subpart[0].type, "TEXT"); CU_ASSERT_STRING_EQUAL(body.subpart[0].subtype, "PLAIN"); CU_ASSERT_PTR_NOT_NULL(body.subpart[0].params); CU_ASSERT_STRING_EQUAL(body.subpart[0].params->attribute, "CHARSET"); CU_ASSERT_STRING_EQUAL(body.subpart[0].params->value, "us-ascii"); CU_ASSERT_PTR_NULL(body.subpart[0].params->next); /* check cacheheaders */ CU_ASSERT_PTR_NOT_NULL_FATAL(body.cacheheaders.s); CU_ASSERT(strstr(body.cacheheaders.s, "Norman") != NULL); CU_ASSERT_PTR_NULL(body.subpart[0].cacheheaders.s); message_free_body(&body); } static void test_mime_multiple(void) { #define TEXT_PART \ "Hello, World" #define HTML_PART \ "Hello, World\r\n" \ "\r\n" \ "

    Hello, World

    \r\n" \ "" static const char msg[] = "From: Fred Bloggs \r\n" "Reply-To: \r\n" "To: Sarah Jane Smith \r\n" "Date: Thu, 28 Oct 2010 18:37:26 +1100\r\n" "Subject: MIME testing email\r\n" "X-Mailer: Norman\r\n" "MIME-Version: 1.0\r\n" "Content-Type: multipart/mixed; boundary=\"7225e50d962de81173be22223f706458743c3a9a\"\r\n" "Content-Language: en\r\n" "Message-ID: \r\n" "\r\n" "--7225e50d962de81173be22223f706458743c3a9a\r\n" "Content-Type: text/plain; charset=\"us-ascii\"\r\n" "\r\n" TEXT_PART "\r\n" "--7225e50d962de81173be22223f706458743c3a9a\r\n" "Content-Type: text/html; charset=\"us-ascii\"\r\n" "\r\n" HTML_PART "\r\n" "--7225e50d962de81173be22223f706458743c3a9a\r\n" "Content-Type: image/png\r\n" "Content-Disposition: attachment; filename=cyrus-favicon.png\r\n" "Content-Transfer-Encoding: base64\r\n" "\r\n" "iVBORw0KGgoAAAANSUhEUgAAABAAAAAQCAYAAAAf8/9hAAAAAXNSR0IArs4c6QAAAAZiS0dEAP8A\r\n" "/wD/oL2nkwAAAAlwSFlzAAALEwAACxMBAJqcGAAAAAd0SU1FB9sBEQEMHNieJnIAAAIsSURBVDjL\r\n" "tZNPSNNhGMc/r+xSUY4hbHO1LYyRSXRw4iaSRVFCiNBf8BA/mwWVB1sQFGgdgqjfph6i0EEUXaxJ\r\n" "3tTmkA6zQxieVlR0GP0xy7n9Ftipng6/NZMM6dBzenmf5/083+d53gf+l42Njkm1zychTZPZ2Vn5\r\n" "p8dRPSIuu0NcdodsdDgl4K+TqVRqRYj6dZhKpaQv2kuhYJBOp0GKXgGlzLBAMAjAdV2nakuVWka6\r\n" "3N0tyYkJWc2G43GJ6vpyNbGBQXHZHZJMJFYFJBMJqfb55MHQkABYQpomV3p6QKmSVIC+SATD+AqA\r\n" "x7OJ9o6OYtGKglEg3HWOkKYJle7N0hgIynA8LtlsdlUF2WxWkomENAYbxGV3iGXR6SHl38ePWwN4\r\n" "vV5sNhsA/dEo+byBUgq3e0lBPpej55rOU38L5d/HwVrfJDx8JegjUrHdL726/tfsd2Ix8TTsFvQR\r\n" "If5arPW7pAwUKAWebcyfv0144hnHDh0hl8uV+rGwsMDJ9hOcvT9C5tQN8NaAmIMoE5HizBWsK4e2\r\n" "Czx+/4U9O5uYTCZ5Pj1N64EWRief8O1o2IwpNlNEsJS+kwhkXlAe78eo2sHM1lraOrsAmOu4CpmX\r\n" "VAxeZL75ONTtL6kzAQKM34UPbzHOREpZ5i7dM8FrN4C3hvmmw/DoJryZgdbTvwEyaajdC82aWYoU\r\n" "qWvWL//xAhzshMUCfH5neqp9PvlodS4tR7G2P5ZmhfvK/Cd+At3OXF7AwYF1AAAAAElFTkSuQmCC\r\n" "\r\n--7225e50d962de81173be22223f706458743c3a9a--\r\n"; int r; struct body body; struct body *part; struct message_content mcontent; const char *types[2] = { NULL, NULL }; struct bodypart **parts = NULL; memset(&body, 0x45, sizeof(body)); r = message_parse_mapped(msg, sizeof(msg)-1, &body); CU_ASSERT_EQUAL(r, 0); /* Content-Type: */ CU_ASSERT_STRING_EQUAL(body.type, "MULTIPART"); CU_ASSERT_STRING_EQUAL(body.subtype, "MIXED"); CU_ASSERT_PTR_NOT_NULL(body.params); CU_ASSERT_STRING_EQUAL(body.params->attribute, "BOUNDARY"); CU_ASSERT_STRING_EQUAL(body.params->value, "7225e50d962de81173be22223f706458743c3a9a"); CU_ASSERT_PTR_NULL(body.params->next); CU_ASSERT_EQUAL(body.numparts, 3); CU_ASSERT_PTR_NOT_NULL(body.subpart); part = &body.subpart[0]; CU_ASSERT_PTR_NOT_NULL(part); CU_ASSERT_STRING_EQUAL(part->type, "TEXT"); CU_ASSERT_STRING_EQUAL(part->subtype, "PLAIN"); CU_ASSERT_PTR_NOT_NULL(part->params); CU_ASSERT_STRING_EQUAL(part->params->attribute, "CHARSET"); CU_ASSERT_STRING_EQUAL(part->params->value, "us-ascii"); CU_ASSERT_PTR_NULL(part->params->next); CU_ASSERT_PTR_NULL(part->disposition); CU_ASSERT_PTR_NULL(part->encoding); part = &body.subpart[1]; CU_ASSERT_PTR_NOT_NULL(part); CU_ASSERT_STRING_EQUAL(part->type, "TEXT"); CU_ASSERT_STRING_EQUAL(part->subtype, "HTML"); CU_ASSERT_PTR_NOT_NULL(part->params); CU_ASSERT_STRING_EQUAL(part->params->attribute, "CHARSET"); CU_ASSERT_STRING_EQUAL(part->params->value, "us-ascii"); CU_ASSERT_PTR_NULL(part->params->next); CU_ASSERT_PTR_NULL(part->disposition); CU_ASSERT_PTR_NULL(part->encoding); part = &body.subpart[2]; CU_ASSERT_PTR_NOT_NULL(part); CU_ASSERT_STRING_EQUAL(part->type, "IMAGE"); CU_ASSERT_STRING_EQUAL(part->subtype, "PNG"); CU_ASSERT_PTR_NULL(part->params); CU_ASSERT_STRING_EQUAL(part->disposition, "ATTACHMENT"); CU_ASSERT_STRING_EQUAL(part->encoding, "BASE64"); mcontent.base = msg; mcontent.len = sizeof(msg)-1; mcontent.body = &body; types[0] = "TEXT/PLAIN"; parts = NULL; message_fetch_part(&mcontent, types, &parts); CU_ASSERT_PTR_NOT_NULL(parts); if (parts) { CU_ASSERT_PTR_NOT_NULL(parts[0]); CU_ASSERT_PTR_NULL(parts[1]); CU_ASSERT_STRING_EQUAL(parts[0]->decoded_body, TEXT_PART); free(parts[0]); free(parts); parts = NULL; } types[0] = "TEXT/HTML"; parts = NULL; message_fetch_part(&mcontent, types, &parts); CU_ASSERT_PTR_NOT_NULL(parts); if (parts) { CU_ASSERT_PTR_NOT_NULL(parts[0]); CU_ASSERT_PTR_NULL(parts[1]); CU_ASSERT_STRING_EQUAL(parts[0]->decoded_body, HTML_PART); free(parts[0]); free(parts); parts = NULL; } /* check cacheheaders */ CU_ASSERT_PTR_NOT_NULL_FATAL(body.cacheheaders.s); CU_ASSERT(strstr(body.cacheheaders.s, "Norman") != NULL); CU_ASSERT_PTR_NULL(body.subpart[0].cacheheaders.s); CU_ASSERT_PTR_NULL(body.subpart[1].cacheheaders.s); CU_ASSERT_PTR_NULL(body.subpart[2].cacheheaders.s); message_free_body(&body); #undef TEXT_PART #undef HTML_PART } /* * RFC2231 specifies, amongst other things, a method for * breaking up across multiple lines, long parameter values * which cannot have whitespace inserted into them. */ static void test_rfc2231_continuations(void) { static const char msg[] = "From: Fred Bloggs \r\n" "To: Sarah Jane Smith \r\n" "Date: Wed, 27 Oct 2010 18:37:26 +1100\r\n" /* This example based on one in RFC2231 */ "Content-Type: message/external-body; access-type=URL;\r\n" "\tURL*0=\"ftp://\";\r\n" "\tURL*1=\"cs.utk.edu/pub/moore/\";\r\n" "\tURL*2=\"bulk-mailer/bulk-mailer.tar\"\r\n" "Subject: RFC2231 continuation testing email\r\n" "Message-ID: \r\n" "\r\n" "Hello, World\n"; int r; static const char URL[] = "ftp://cs.utk.edu/pub/moore/bulk-mailer/bulk-mailer.tar"; struct body body; memset(&body, 0x45, sizeof(body)); r = message_parse_mapped(msg, sizeof(msg)-1, &body); CU_ASSERT_EQUAL(r, 0); /* Date: Wed, 27 Oct 2010 18:37:26 +1100 */ CU_ASSERT_STRING_EQUAL(body.date, "Wed, 27 Oct 2010 18:37:26 +1100"); /* Subject: Trivial testing email */ CU_ASSERT_STRING_EQUAL(body.subject, "RFC2231 continuation testing email"); CU_ASSERT_STRING_EQUAL(body.type, "MESSAGE"); CU_ASSERT_STRING_EQUAL(body.subtype, "EXTERNAL-BODY"); CU_ASSERT_PTR_NOT_NULL(body.params); CU_ASSERT_STRING_EQUAL(body.params->attribute, "ACCESS-TYPE"); CU_ASSERT_STRING_EQUAL(body.params->value, "URL"); CU_ASSERT_PTR_NOT_NULL(body.params->next); CU_ASSERT_STRING_EQUAL(body.params->next->attribute, "URL"); CU_ASSERT_STRING_EQUAL(body.params->next->value, URL); CU_ASSERT_PTR_NULL(body.params->next->next); message_free_body(&body); } /* * RFC2231 has a second syntax for continuations, which * indicates the language & charset info may be encoded * in the value and allows for %xx encoded chars. */ static void test_rfc2231_extended_continuations(void) { static const char msg[] = "From: Fred Bloggs \r\n" "To: Sarah Jane Smith \r\n" "Date: Wed, 27 Oct 2010 18:37:26 +1100\r\n" /* This example also loosely based on one in RFC2231 */ "Content-Type: application/x-stuff;\r\n" "\ttitle*0*=us-ascii'en'This%20is%20even%20more%20;\r\n" "\ttitle*1*=%2A%2A%2Afun%2A%2A%2A%20;\r\n" "\ttitle*2=\"isn't it!\"\r\n" "Subject: RFC2231 extended continuation testing email\r\n" "Message-ID: \r\n" "\r\n" "Hello, World\n"; int r; static const char TITLE[] = "us-ascii'en'This%20is%20even%20more%20%2A%2A%2Afun%2A%2A%2A%20isn%27t%20it!"; struct body body; memset(&body, 0x45, sizeof(body)); r = message_parse_mapped(msg, sizeof(msg)-1, &body); CU_ASSERT_EQUAL(r, 0); /* Date: Wed, 27 Oct 2010 18:37:26 +1100 */ CU_ASSERT_STRING_EQUAL(body.date, "Wed, 27 Oct 2010 18:37:26 +1100"); /* Subject: Trivial testing email */ CU_ASSERT_STRING_EQUAL(body.subject, "RFC2231 extended continuation testing email"); CU_ASSERT_STRING_EQUAL(body.type, "APPLICATION"); CU_ASSERT_STRING_EQUAL(body.subtype, "X-STUFF"); CU_ASSERT_PTR_NOT_NULL_FATAL(body.params); CU_ASSERT_STRING_EQUAL(body.params->attribute, "TITLE*"); CU_ASSERT_STRING_EQUAL(body.params->value, TITLE); CU_ASSERT_PTR_NULL(body.params->next); message_free_body(&body); } static void test_references(void) { static const char msg[] = "From: Fred Bloggs \r\n" "To: Sarah Jane Smith \r\n" "Date: Wed, 27 Oct 2010 18:37:26 +1100\r\n" "Subject: Trivial testing email\r\n" "Message-ID: \r\n" "In-Reply-To: \r\n" "References: \r\n" "\t\t(Hey ignore me I'm a comment) \r\n" "\t\r\n" "\r\n" "Hello, World\n"; int r; struct body body; memset(&body, 0x45, sizeof(body)); r = message_parse_mapped(msg, sizeof(msg)-1, &body); CU_ASSERT_EQUAL(r, 0); /* Message-ID: */ CU_ASSERT_STRING_EQUAL(body.message_id, ""); /* In_Reply-To: */ CU_ASSERT_STRING_EQUAL(body.in_reply_to, ""); CU_ASSERT_PTR_NOT_NULL(strstr(body.references, "")); CU_ASSERT_PTR_NOT_NULL(strstr(body.references, "")); CU_ASSERT_PTR_NOT_NULL(strstr(body.references, "")); CU_ASSERT_PTR_NOT_NULL(strstr(body.references, "")); CU_ASSERT_PTR_NOT_NULL(strstr(body.references, "")); message_free_body(&body); } #undef TESTCASE #define TESTCASE(input, explen, expout) \ buf_reset(&b); \ message_write_nstring(&b, input); \ buf_cstring(&b); \ CU_ASSERT_EQUAL(b.len, explen); \ CU_ASSERT(!strcmp(b.s, expout)) static void test_write_nstring(void) { struct buf b = BUF_INITIALIZER; /* NULL string */ TESTCASE(0, 3, "NIL"); /* Zero length string */ TESTCASE("", 2, "\"\""); /* Boring string */ TESTCASE("Hello", 7, "\"Hello\""); /* String with non-dangerous whitespace */ TESTCASE("Hello World\tagain", 19, "\"Hello World\tagain\""); /* String with dangerous whitespace */ TESTCASE("Good\rBye\nEarth", 20, "{14}\r\nGood\rBye\nEarth"); /* String with embedded dquote */ TESTCASE("Quot\"able", 14, "{9}\r\nQuot\"able"); /* String with embedded percent */ TESTCASE("per%ent", 12, "{7}\r\nper%ent"); /* String with embedded backslash */ TESTCASE("slash\\dot", 14, "{9}\r\nslash\\dot"); /* String with embedded 8-bit chars */ TESTCASE("Hi I'm \330l\345f", 17, "{11}\r\nHi I'm \330l\345f"); /* Boring but overly long string */ { struct buf llb = BUF_INITIALIZER; int i; for (i = 0 ; i<500 ; i++) buf_appendcstr(&llb, "blah "); buf_cstring(&llb); buf_reset(&b); message_write_nstring(&b, llb.s); buf_cstring(&b); CU_ASSERT_EQUAL(b.len, llb.len+8); \ CU_ASSERT_STRING_EQUAL(b.s+8, llb.s); b.s[8] = '\0'; CU_ASSERT_STRING_EQUAL(b.s, "{2500}\r\n"); buf_free(&llb); } /* embedded NULs not handled in message_write_nstring */ TESTCASE("Hello\0World", 7, "\"Hello\""); /* embedded NULs in message_write_nstring_map */ buf_reset(&b); message_write_nstring_map(&b, "Hello\0World", 11); buf_cstring(&b); CU_ASSERT_EQUAL(b.len, 17); CU_ASSERT(!memcmp(b.s, "{11}\r\nHello\0World", 17)); buf_free(&b); } #undef TESTPARSE #define TESTPARSE(expout, explen, input) \ buf_setcstr(&b, input); \ buf_putc(&b, ')'); \ ptr = b.s; \ output = parse_nstring(&ptr); \ CU_ASSERT(!memcmp(output, expout, explen)) static void test_parse_nstring(void) { struct buf b = BUF_INITIALIZER; char *output; char *ptr; /* NULL string */ buf_setcstr(&b, "NIL)"); ptr = b.s; output = parse_nstring(&ptr); CU_ASSERT_PTR_NULL(output); /* Zero length string */ TESTPARSE("", 0, "\"\""); /* Boring string */ TESTPARSE("Hello", 5, "\"Hello\""); /* String with non-dangerous whitespace */ TESTPARSE("Hello World\tagain", 17, "\"Hello World\tagain\""); /* String with dangerous whitespace */ TESTPARSE("Good\rBye\nEarth", 14, "{14}\r\nGood\rBye\nEarth"); /* String with embedded dquote */ TESTPARSE("Quot\"able", 9, "{9}\r\nQuot\"able"); /* String with embedded percent */ TESTPARSE("per%ent", 7, "{7}\r\nper%ent"); /* String with embedded backslash */ TESTPARSE("slash\\dot", 9, "{9}\r\nslash\\dot"); /* String with embedded 8-bit chars */ TESTPARSE("Hi I'm \330l\345f", 11, "{11}\r\nHi I'm \330l\345f"); /* And some stuff seen in the wild */ TESTPARSE("Lloyd Burns\\\"", 13, "\"Lloyd Burns\\\"\" NIL \"MariogenoaRobertson\" \"fiftyfoureleven.com\")"); buf_free(&b); } #undef TESTCASE #define TESTCASE(input, expout) \ buf_reset(&b); \ buf_init_ro(&s, input, sizeof(input)-1); \ message_write_xdrstring(&b, &s); \ CU_ASSERT_EQUAL(b.len, sizeof(expout)-1); \ CU_ASSERT(!memcmp(b.s, expout, sizeof(expout)-1)) static void test_write_xdrstring(void) { struct buf b = BUF_INITIALIZER; struct buf s = BUF_INITIALIZER; /* Zero length string */ TESTCASE("", "\0\0\0\0"); /* 1-length string */ TESTCASE("H", "\0\0\0\001H\0\0\0"); /* 2-length string */ TESTCASE("He", "\0\0\0\002He\0\0"); /* 3-length string */ TESTCASE("Hel", "\0\0\0\003Hel\0"); /* 4-length string */ TESTCASE("Hell", "\0\0\0\004Hell"); /* 5-length string */ TESTCASE("Hello", "\0\0\0\005Hello\0\0\0"); buf_free(&b); buf_free(&s); } #undef TESTCASE /* vim: set ft=c: */ cyrus-imapd-2.5.10/cunit/timeout.h0000644000175000017500000000401312772415051013740 00000000000000/* * Copyright (c) 1994-2011 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #ifndef __CUNIT_TIMEOUT_H__ #define __CUNIT_TIMEOUT_H__ 1 extern int timeout_init(void (*cb)(void)); extern int timeout_begin(int millisec); extern int timeout_end(void); extern void timeout_fini(void); #endif /* __CUNIT_TIMEOUT_H__ */ cyrus-imapd-2.5.10/cunit/cunit-to-junit.pl0000755000175000017500000001170513001236020015317 00000000000000#!/usr/bin/perl use strict; use warnings; use XML::DOM; use File::Path qw(mkpath rmtree); use File::Basename qw(dirname); use Data::Dumper; use Carp; my $verbose = 0; my $infile = 'CUnitAutomated-Results.xml'; my $outbase = 'reports/TEST-'; sub get_child { my ($node, $name) = @_; croak "Invalid document" unless defined $node; my $kids = $node->getElementsByTagName($name, 0); croak "Invalid document: name=$name" unless (defined $kids && $kids->getLength == 1); return $kids->item(0); } sub get_child_maybe { my ($node, $name) = @_; croak "Invalid document" unless defined $node; my $kids = $node->getElementsByTagName($name, 0); return undef if !defined $kids; return undef if $kids->getLength == 0; croak "Invalid document" if $kids->getLength > 1; return $kids->item(0); } sub get_children { my ($node, $name) = @_; croak "Invalid document" unless defined $node; return ( $node->getElementsByTagName($name, 0) ); } sub get_content { my ($node, $name) = @_; croak "Invalid document" unless defined $node; my $s = $node->getFirstChild->getData; if (defined $s) { $s =~ s/^\s+//; $s =~ s/\s+$//; } return $s; } my @suites; sub get_suite { my ($sname) = @_; printf STDERR "Suite \"%s\"\n", $sname if $verbose; my @existing = grep { $_->{name} eq $sname; } @suites; return $existing[0] if scalar @existing; my $s = { name => $sname, nerrors => 0, tests => [], tests_by_name => {}, }; push(@suites, $s); return $s; } sub _add_test { my ($s, $tname) = @_; my $t = $s->{tests_by_name}->{$tname}; if (!defined $t) { $t = { name => $tname, errors => [], }; push(@{$s->{tests}}, $t); $s->{tests_by_name}->{$tname} = $t; } return $t; } sub add_pass { my ($s, $tname) = @_; printf STDERR " Test \"%s\": pass\n", $tname if $verbose; _add_test($s, $tname); } sub add_fail { my ($s, $tname, $msg) = @_; printf STDERR " Test \"%s\": fail\n %s\n", $tname, $msg if $verbose; my $t = _add_test($s, $tname); push(@{$t->{errors}}, $msg); $s->{nerrors}++; } my $parser = new XML::DOM::Parser; my $doc = $parser->parsefile($infile); my $root = get_child($doc, 'CUNIT_TEST_RUN_REPORT'); my $result = get_child($root, 'CUNIT_RESULT_LISTING'); foreach my $suite (get_children($result, 'CUNIT_RUN_SUITE')) { my $succ = get_child_maybe($suite, 'CUNIT_RUN_SUITE_SUCCESS'); my $fail = get_child_maybe($suite, 'CUNIT_RUN_SUITE_FAILURE'); if (defined $succ) { my $s = get_suite(get_content(get_child($succ, 'SUITE_NAME'))); foreach my $record (get_children($succ, 'CUNIT_RUN_TEST_RECORD')) { my $tr; $tr = get_child_maybe($record, 'CUNIT_RUN_TEST_SUCCESS'); if (defined $tr) { my $tname = get_content(get_child($tr, 'TEST_NAME')); add_pass($s, $tname); next; } foreach $tr (get_children($record, 'CUNIT_RUN_TEST_FAILURE')) { my $tname = get_content(get_child($tr, 'TEST_NAME')); my $fname = get_content(get_child($tr, 'FILE_NAME')); my $lineno = get_content(get_child($tr, 'LINE_NUMBER')); my $cond = get_content(get_child($tr, 'CONDITION')); add_fail($s, $tname, "$fname:$lineno: $cond"); next; } } } elsif (defined $fail) { # TODO: there must be a way in the jUnit output format # to report a failure of the suite fixture code, but # I have no idea what it is. Instead use a fake test name. my $s = get_suite(get_content(get_child($fail, 'SUITE_NAME'))); my $reason = get_content(get_child($fail, 'FAILURE_REASON')); my $tname = '__wtf'; if ($reason =~ m/cleanup/i) { $tname = '__cleanup'; } elsif ($reason =~ m/initialization/i) { $tname = '__cleanup'; } add_fail($s, $tname, $reason); } else { carp "Neither a CUNIT_RUN_SUITE_SUCCESS nor a " . "CUNIT_RUN_SUITE_FAILURE child are present"; } } my $dir = dirname($outbase . 'foo'); rmtree($dir) if (defined $dir && $dir ne '.'); my $nrun = 0; my $nfailed = 0; foreach my $s (@suites) { my $sdoc = XML::DOM::Document->new(); $nfailed += $s->{nerrors}; my $selt = $sdoc->createElement('testsuite'); $selt->setAttribute(failures => 0); $selt->setAttribute(errors => $s->{nerrors}); $selt->setAttribute(time => "0.001"); $selt->setAttribute(tests => scalar @{$s->{tests}}); $selt->setAttribute(name => $s->{name}); $sdoc->appendChild($selt); foreach my $t (@{$s->{tests}}) { $nrun++; my $telt = $sdoc->createElement('testcase'); $telt->setAttribute(time => "0.001"); $telt->setAttribute(name => $t->{name}); $selt->appendChild($telt); foreach my $e (@{$t->{errors}}) { my $eelt = $sdoc->createElement('error'); $eelt->appendChild($sdoc->createTextNode($e)); $telt->appendChild($eelt); } } my $fname = $outbase . $s->{name} . '.xml'; mkpath(dirname($fname)); $sdoc->printToFile($fname); } print "$0: ran $nrun tests, $nfailed failed\n"; exit(1) if ($nfailed > 0); cyrus-imapd-2.5.10/cunit/msgid.testc0000644000175000017500000003257713001236020014247 00000000000000#if HAVE_CONFIG_H #include #endif #include "cunit/cunit.h" #include "imap/global.h" static void test_simple(void) { #define C_MSGID1 "<001.02.00003@example.com>" static const char C_MSGIDS[] = C_MSGID1; char *buf; char *s; char *m; buf = strdup(C_MSGIDS); CU_ASSERT_PTR_NOT_NULL_FATAL(buf); s = buf; /* first call returns a newly allocated string which is the * only msgid in the input */ m = find_msgid(s, &s); CU_ASSERT_PTR_NOT_NULL(m); CU_ASSERT_PTR_NOT_EQUAL(m, s); CU_ASSERT_PTR_NOT_EQUAL(m, buf); CU_ASSERT_STRING_EQUAL(m, C_MSGID1); /* 's' should point somewhere into the buffer */ CU_ASSERT(s >= buf && s <= buf+sizeof(C_MSGIDS)); /* the buffer should be unmolested */ CU_ASSERT(memcmp(buf, C_MSGIDS, sizeof(C_MSGIDS)) == 0); free(m); /* second call returns NULL, there are no more msgids */ m = find_msgid(s, &s); CU_ASSERT_PTR_NULL(m); free(buf); #undef C_MSGID1 } /* multiple msgids separated by a single space */ static void test_multiple(void) { #define C_MSGID1 "<004.05.00006@example.com>" #define C_MSGID2 "<007.08.09@gmail.com>" #define C_MSGID3 "<0000A-0B-0000C@apple.com>" #define C_MSGID4 "<010309849374836@fastmail.fm>" static const char C_MSGIDS[] = C_MSGID1 " " C_MSGID2 " " C_MSGID3 " " C_MSGID4; char *s; char *m1; char *m2; char *m3; char *m4; char *m5; /* We checked in the "simple" test that buffers are unmolested, * so this time just pass find_msgid() a const variable */ s = (char *)C_MSGIDS; /* each call should returns a separate newly allocated string * which is the next msgid in the input */ m1 = find_msgid(s, &s); CU_ASSERT_PTR_NOT_NULL(m1); CU_ASSERT_STRING_EQUAL(m1, C_MSGID1); CU_ASSERT(s >= C_MSGIDS && s <= C_MSGIDS+sizeof(C_MSGIDS)); m2 = find_msgid(s, &s); CU_ASSERT_PTR_NOT_NULL(m2); CU_ASSERT_STRING_EQUAL(m2, C_MSGID2); CU_ASSERT(s >= C_MSGIDS && s <= C_MSGIDS+sizeof(C_MSGIDS)); m3 = find_msgid(s, &s); CU_ASSERT_PTR_NOT_NULL(m3); CU_ASSERT_STRING_EQUAL(m3, C_MSGID3); CU_ASSERT(s >= C_MSGIDS && s <= C_MSGIDS+sizeof(C_MSGIDS)); m4 = find_msgid(s, &s); CU_ASSERT_PTR_NOT_NULL(m4); CU_ASSERT_STRING_EQUAL(m4, C_MSGID4); CU_ASSERT(s >= C_MSGIDS && s <= C_MSGIDS+sizeof(C_MSGIDS)); /* last call returns NULL, there are no more msgids */ m5 = find_msgid(s, &s); CU_ASSERT_PTR_NULL(m5); /* check the returned msgids are all distinct */ CU_ASSERT_PTR_NOT_EQUAL(m1, m2); CU_ASSERT_PTR_NOT_EQUAL(m1, m3); CU_ASSERT_PTR_NOT_EQUAL(m1, m4); CU_ASSERT_PTR_NOT_EQUAL(m2, m3); CU_ASSERT_PTR_NOT_EQUAL(m2, m4); CU_ASSERT_PTR_NOT_EQUAL(m3, m4); free(m1); free(m2); free(m3); free(m4); #undef C_MSGID1 #undef C_MSGID2 #undef C_MSGID3 #undef C_MSGID4 } /* multiple msgids separated by more interesting whitespace */ static void test_whitespace(void) { #define C_MSGID1 "<104.05.00006@example.com>" #define C_MSGID2 "<107.08.09@gmail.com>" #define C_MSGID3 "<1000A-0B-0000C@apple.com>" #define C_MSGID4 "<110309849374836@fastmail.fm>" static const char C_MSGIDS[] = C_MSGID1 " " C_MSGID2 "\t" C_MSGID3 "\t\r\n\t" C_MSGID4 "\r\n"; char *s; char *m1; char *m2; char *m3; char *m4; char *m5; /* We checked in the "simple" test that buffers are unmolested, * so this time just pass find_msgid() a const variable */ s = (char *)C_MSGIDS; /* each call should returns a separate newly allocated string * which is the next msgid in the input */ m1 = find_msgid(s, &s); CU_ASSERT_PTR_NOT_NULL(m1); CU_ASSERT_STRING_EQUAL(m1, C_MSGID1); CU_ASSERT(s >= C_MSGIDS && s <= C_MSGIDS+sizeof(C_MSGIDS)); m2 = find_msgid(s, &s); CU_ASSERT_PTR_NOT_NULL(m2); CU_ASSERT_STRING_EQUAL(m2, C_MSGID2); CU_ASSERT(s >= C_MSGIDS && s <= C_MSGIDS+sizeof(C_MSGIDS)); m3 = find_msgid(s, &s); CU_ASSERT_PTR_NOT_NULL(m3); CU_ASSERT_STRING_EQUAL(m3, C_MSGID3); CU_ASSERT(s >= C_MSGIDS && s <= C_MSGIDS+sizeof(C_MSGIDS)); m4 = find_msgid(s, &s); CU_ASSERT_PTR_NOT_NULL(m4); CU_ASSERT_STRING_EQUAL(m4, C_MSGID4); CU_ASSERT(s >= C_MSGIDS && s <= C_MSGIDS+sizeof(C_MSGIDS)); /* last call returns NULL, there are no more msgids */ m5 = find_msgid(s, &s); CU_ASSERT_PTR_NULL(m5); /* check the returned msgids are all distinct */ CU_ASSERT_PTR_NOT_EQUAL(m1, m2); CU_ASSERT_PTR_NOT_EQUAL(m1, m3); CU_ASSERT_PTR_NOT_EQUAL(m1, m4); CU_ASSERT_PTR_NOT_EQUAL(m2, m3); CU_ASSERT_PTR_NOT_EQUAL(m2, m4); CU_ASSERT_PTR_NOT_EQUAL(m3, m4); free(m1); free(m2); free(m3); free(m4); #undef C_MSGID1 #undef C_MSGID2 #undef C_MSGID3 #undef C_MSGID4 } /* duplicate msgids are returned, not elided */ static void test_dups(void) { #define C_MSGID1 "<204.05.00006@example.com>" #define C_MSGID2 "<207.08.09@gmail.com>" static const char C_MSGIDS[] = C_MSGID1 " " C_MSGID2 " " C_MSGID2 " " C_MSGID1; char *s; char *m1; char *m2; char *m3; char *m4; char *m5; /* We checked in the "simple" test that buffers are unmolested, * so this time just pass find_msgid() a const variable */ s = (char *)C_MSGIDS; /* each call should returns a separate newly allocated string * which is the next msgid in the input */ m1 = find_msgid(s, &s); CU_ASSERT_PTR_NOT_NULL(m1); CU_ASSERT_STRING_EQUAL(m1, C_MSGID1); CU_ASSERT(s >= C_MSGIDS && s <= C_MSGIDS+sizeof(C_MSGIDS)); m2 = find_msgid(s, &s); CU_ASSERT_PTR_NOT_NULL(m2); CU_ASSERT_STRING_EQUAL(m2, C_MSGID2); CU_ASSERT(s >= C_MSGIDS && s <= C_MSGIDS+sizeof(C_MSGIDS)); m3 = find_msgid(s, &s); CU_ASSERT_PTR_NOT_NULL(m3); CU_ASSERT_STRING_EQUAL(m3, C_MSGID2); CU_ASSERT(s >= C_MSGIDS && s <= C_MSGIDS+sizeof(C_MSGIDS)); m4 = find_msgid(s, &s); CU_ASSERT_PTR_NOT_NULL(m4); CU_ASSERT_STRING_EQUAL(m4, C_MSGID1); CU_ASSERT(s >= C_MSGIDS && s <= C_MSGIDS+sizeof(C_MSGIDS)); /* last call returns NULL, there are no more msgids */ m5 = find_msgid(s, &s); CU_ASSERT_PTR_NULL(m5); /* check the returned msgids are all distinct */ CU_ASSERT_PTR_NOT_EQUAL(m1, m2); CU_ASSERT_PTR_NOT_EQUAL(m1, m3); CU_ASSERT_PTR_NOT_EQUAL(m1, m4); CU_ASSERT_PTR_NOT_EQUAL(m2, m3); CU_ASSERT_PTR_NOT_EQUAL(m2, m4); CU_ASSERT_PTR_NOT_EQUAL(m3, m4); free(m1); free(m2); free(m3); free(m4); #undef C_MSGID1 #undef C_MSGID2 } /* a CRLF followed by a non WS marks the end of the header */ static void test_eol(void) { #define C_MSGID1 "<304.05.00006@example.com>" #define C_MSGID2 "<307.08.09@gmail.com>" #define C_MSGID3 "<3000A-0B-0000C@apple.com>" #define C_MSGID4 "<310309849374836@fastmail.fm>" static const char C_MSGIDS[] = C_MSGID1 "\r\n" " " C_MSGID2 "\r\n" "In-Reply-To: " C_MSGID3 "\r\n" "Message-Id: " C_MSGID4 "\r\n" "\r\n"; char *s; char *m1; char *m2; char *m3; /* We checked in the "simple" test that buffers are unmolested, * so this time just pass find_msgid() a const variable */ s = (char *)C_MSGIDS; /* each call should returns a separate newly allocated string * which is the next msgid in the input */ m1 = find_msgid(s, &s); CU_ASSERT_PTR_NOT_NULL(m1); CU_ASSERT_STRING_EQUAL(m1, C_MSGID1); CU_ASSERT(s >= C_MSGIDS && s <= C_MSGIDS+sizeof(C_MSGIDS)); m2 = find_msgid(s, &s); CU_ASSERT_PTR_NOT_NULL(m2); CU_ASSERT_STRING_EQUAL(m2, C_MSGID2); CU_ASSERT(s >= C_MSGIDS && s <= C_MSGIDS+sizeof(C_MSGIDS)); /* we stop seeing msgids after the end of the first header */ m3 = find_msgid(s, &s); CU_ASSERT_PTR_NULL(m3); /* check the returned msgids are all distinct */ CU_ASSERT_PTR_NOT_EQUAL(m1, m2); free(m1); free(m2); #undef C_MSGID1 #undef C_MSGID2 #undef C_MSGID3 #undef C_MSGID4 } /* ignore a malformed msgid with no @ sign */ static void test_noatsign(void) { #define C_MSGID1 "<404.05.00006@example.com>" #define C_MSGID2 "<407.08.09-no-at-here-gmail.com>" #define C_MSGID3 "<4000A-0B-0000C@apple.com>" static const char C_MSGIDS[] = C_MSGID1 " " C_MSGID2 " " C_MSGID3; char *s; char *m1; char *m2; char *m3; /* We checked in the "simple" test that buffers are unmolested, * so this time just pass find_msgid() a const variable */ s = (char *)C_MSGIDS; /* each call should returns a separate newly allocated string * which is the next msgid in the input */ m1 = find_msgid(s, &s); CU_ASSERT_PTR_NOT_NULL(m1); CU_ASSERT_STRING_EQUAL(m1, C_MSGID1); CU_ASSERT(s >= C_MSGIDS && s <= C_MSGIDS+sizeof(C_MSGIDS)); m2 = find_msgid(s, &s); CU_ASSERT_PTR_NOT_NULL(m2); CU_ASSERT_STRING_EQUAL(m2, C_MSGID3); CU_ASSERT(s >= C_MSGIDS && s <= C_MSGIDS+sizeof(C_MSGIDS)); /* we stop seeing msgids after 2nd msgid */ m3 = find_msgid(s, &s); CU_ASSERT_PTR_NULL(m3); /* check the returned msgids are all distinct */ CU_ASSERT_PTR_NOT_EQUAL(m1, m2); free(m1); free(m2); #undef C_MSGID1 #undef C_MSGID2 #undef C_MSGID3 } /* handle a msgid with a quoted localpart */ static void test_quoted_localpart(void) { #define C_MSGID1 "<504.05.00006@example.com>" #define C_MSGID2 "<\"507>0 8@09\"@gmail.com>" #define C_MSGID2ret "<507>0 8@09@gmail.com>" #define C_MSGID3 "<5000A-0B-0000C@apple.com>" static const char C_MSGIDS[] = C_MSGID1 " " C_MSGID2 " " C_MSGID3; char *s; char *m1; char *m2; char *m3; char *m4; /* We checked in the "simple" test that buffers are unmolested, * so this time just pass find_msgid() a const variable */ s = (char *)C_MSGIDS; /* each call should returns a separate newly allocated string * which is the next msgid in the input */ m1 = find_msgid(s, &s); CU_ASSERT_PTR_NOT_NULL(m1); CU_ASSERT_STRING_EQUAL(m1, C_MSGID1); CU_ASSERT(s >= C_MSGIDS && s <= C_MSGIDS+sizeof(C_MSGIDS)); m2 = find_msgid(s, &s); CU_ASSERT_PTR_NOT_NULL(m2); CU_ASSERT_STRING_EQUAL(m2, C_MSGID2ret); CU_ASSERT(s >= C_MSGIDS && s <= C_MSGIDS+sizeof(C_MSGIDS)); m3 = find_msgid(s, &s); CU_ASSERT_PTR_NOT_NULL(m3); CU_ASSERT_STRING_EQUAL(m3, C_MSGID3); CU_ASSERT(s >= C_MSGIDS && s <= C_MSGIDS+sizeof(C_MSGIDS)); /* we stop seeing msgids after 2nd msgid */ m4 = find_msgid(s, &s); CU_ASSERT_PTR_NULL(m4); /* check the returned msgids are all distinct */ CU_ASSERT_PTR_NOT_EQUAL(m1, m2); CU_ASSERT_PTR_NOT_EQUAL(m1, m3); CU_ASSERT_PTR_NOT_EQUAL(m2, m3); free(m1); free(m2); free(m3); #undef C_MSGID1 #undef C_MSGID2 #undef C_MSGID2ret #undef C_MSGID3 } /* handle a msgid with a quoted localpart containing an escaped quote */ static void test_escaped_quoted_localpart(void) { #define C_MSGID1 "<504.05.00006@example.com>" #define C_MSGID2 "<\"507>0\\\"8@09\"@gmail.com>" #define C_MSGID2ret "<507>0\"8@09@gmail.com>" #define C_MSGID3 "<5000A-0B-0000C@apple.com>" static const char C_MSGIDS[] = C_MSGID1 " " C_MSGID2 " " C_MSGID3; char *s; char *m1; char *m2; char *m3; char *m4; /* We checked in the "simple" test that buffers are unmolested, * so this time just pass find_msgid() a const variable */ s = (char *)C_MSGIDS; /* each call should returns a separate newly allocated string * which is the next msgid in the input */ m1 = find_msgid(s, &s); CU_ASSERT_PTR_NOT_NULL(m1); CU_ASSERT_STRING_EQUAL(m1, C_MSGID1); CU_ASSERT(s >= C_MSGIDS && s <= C_MSGIDS+sizeof(C_MSGIDS)); m2 = find_msgid(s, &s); CU_ASSERT_PTR_NOT_NULL(m2); CU_ASSERT_STRING_EQUAL(m2, C_MSGID2ret); CU_ASSERT(s >= C_MSGIDS && s <= C_MSGIDS+sizeof(C_MSGIDS)); m3 = find_msgid(s, &s); CU_ASSERT_PTR_NOT_NULL(m3); CU_ASSERT_STRING_EQUAL(m3, C_MSGID3); CU_ASSERT(s >= C_MSGIDS && s <= C_MSGIDS+sizeof(C_MSGIDS)); /* we stop seeing msgids after 2nd msgid */ m4 = find_msgid(s, &s); CU_ASSERT_PTR_NULL(m4); /* check the returned msgids are all distinct */ CU_ASSERT_PTR_NOT_EQUAL(m1, m2); CU_ASSERT_PTR_NOT_EQUAL(m1, m3); CU_ASSERT_PTR_NOT_EQUAL(m2, m3); free(m1); free(m2); free(m3); #undef C_MSGID1 #undef C_MSGID2 #undef C_MSGID2ret #undef C_MSGID3 } /* handle a msgid with malformed <> */ static void test_malformed_angles(void) { #define C_MSGID1 "<604.05.00006@example.com>" #define C_MSGID2 "<607.08.09@gmail.com" #define C_MSGID3 "<6000A-0B-0000C@apple.com>" static const char C_MSGIDS[] = C_MSGID1 " " C_MSGID2 " " C_MSGID3; char *s; char *m1; char *m2; char *m3; /* We checked in the "simple" test that buffers are unmolested, * so this time just pass find_msgid() a const variable */ s = (char *)C_MSGIDS; /* each call should returns a separate newly allocated string * which is the next msgid in the input */ m1 = find_msgid(s, &s); CU_ASSERT_PTR_NOT_NULL(m1); CU_ASSERT_STRING_EQUAL(m1, C_MSGID1); CU_ASSERT(s >= C_MSGIDS && s <= C_MSGIDS+sizeof(C_MSGIDS)); m2 = find_msgid(s, &s); CU_ASSERT_PTR_NOT_NULL(m2); CU_ASSERT_STRING_EQUAL(m2, C_MSGID3); CU_ASSERT(s >= C_MSGIDS && s <= C_MSGIDS+sizeof(C_MSGIDS)); /* we stop seeing msgids after 2nd msgid */ m3 = find_msgid(s, &s); CU_ASSERT_PTR_NULL(m3); /* check the returned msgids are all distinct */ CU_ASSERT_PTR_NOT_EQUAL(m1, m2); free(m1); free(m2); #undef C_MSGID1 #undef C_MSGID2 #undef C_MSGID3 } /* vim: set ft=c: */ cyrus-imapd-2.5.10/cunit/key.pem0000644000175000017500000000156712772415051013407 00000000000000-----BEGIN RSA PRIVATE KEY----- MIICXAIBAAKBgQDyzJYnkpOtVpx4hWjQvQAAYnrVIrNU8EobvBiNfjcfy7AEq9iR VTfIiXkvlM0C0zQPScpogByLm75DxI+hUwSoNbeN2GfskjCJh1ULqZ1FN4iv6plk EZxewtWVF983I/EMdekLth6wgH2g2odsgD9zcvTUtF1UeAdr739/CgiEuwIDAQAB AoGAD31X0vx56WQOJW41aqO0HVIrDe/hyvhtcemFE3nK4H9pIlMoRNVP8r46efuf PJ/mwVbuz83khE+SStZ+Z0dZk5XPa+12Zm/Se9OEvTRlIO/Owph191HZN6UgvlQv hbMEpYd/olrVQGC37byf+sC8ZbBOeNgUJ4OsOd7t/7FQOCECQQD/4JB5jwxA+bQp GOtVva/Ff8LUe/7YKDI83J/wnbKJ6hdxltBJyCnf71w6IpCplVbstIuTs8esKFwl /P12uVmRAkEA8upqXanrYtpmDY+o+75wOM3QqZT9ZAlcE9ExGerDVCSuWWuHYVc/ a1QiLoZT/Ox1Q4//QFFnlFopIGb53z0ziwJAa1Vk5UjnJ/5W34JvfWjzaZJdRMq6 rSu3XyZhBQrxkL6clO5hcwG+5wu+ETjcm/ZkHyjg/9VDJelMNjc4j2vSsQJAKYVL /QqIQ3NVMkg1+CHLCMqVOgdPcIPxCyocnHN2Q7GpY3tvvoGtQ2k0FoO7Y2X/fTbl yFahv8fRc8pmN3Q8lQJBALHR6t9w5pHa4OykBGiho2HjnFJLgU0lbHfCr0jWZHgN dZ4rE6d7bq5NvjaKxUk5nO/Flx2A6AkkxtJwFr8VYsA= -----END RSA PRIVATE KEY----- cyrus-imapd-2.5.10/cunit/timeout.c0000644000175000017500000001333113001236020013715 00000000000000/* * Copyright (c) 1994-2011 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include #include #include #include #include #include #include #include #include "timeout.h" static void (*timeout_callback)(void); static pid_t timeout_pid = -1; static int timeout_fd = -1; #define PIPE_READ 0 #define PIPE_WRITE 1 #define CMD_BEGIN 'B' #define CMD_END 'E' static void sigusr1_handler(int sig __attribute__((unused))) { // fprintf(stderr, "timeout: received SIGUSR1\n"); if (timeout_callback) timeout_callback(); } static void timeout_mainloop(int fd, pid_t pid) { struct pollfd pfd; char c; int r; int timeout = -1; for (;;) { memset(&pfd, 0, sizeof(pfd)); pfd.fd = fd; pfd.events = POLLIN; // if (timeout < 0) // fprintf(stderr, "timeout: waiting for command\n"); // else // fprintf(stderr, "timeout: waiting for command or %d.%03d sec\n", timeout/1000, timeout % 1000); /* wait for command from the parent or timeout */ r = poll(&pfd, 1, timeout); // fprintf(stderr, "timeout: awoke, r=%d\n", r); if (r < 0) { perror("timeout: poll"); exit(1); } if (r == 0) { /* timed out */ // fprintf(stderr, "timeout: sending USR1 to %d\n", (int)pid); kill(pid, SIGUSR1); timeout = -1; continue; } if (r != 1 || !pfd.revents) { /* WTF?? */ fprintf(stderr, "timeout: weirdness from poll: " "r=%d pfd.revents=%d\n", r, pfd.revents); exit(1); } r = read(fd, &c, 1); if (r < 0) { perror("timeout: read"); exit(1); } if (r == 0) { /* EOF: parent closed pipe */ exit(0); } if (r != 1) { fprintf(stderr, "timeout: short read\n"); exit(1); } switch (c) { case CMD_BEGIN: timeout = -1; r = read(fd, &timeout, sizeof(timeout)); if (r < 0) { perror("timeout: read"); exit(1); } if (r == 0) { /* EOF: parent closed pipe */ exit(0); } if (r != sizeof(timeout)) { fprintf(stderr, "timeout: short read\n"); exit(1); } break; case CMD_END: timeout = -1; break; default: fprintf(stderr, "timeout: Unknown command '%c'\n", c); exit(1); } } } int timeout_init(void (*cb)(void)) { int pipefd[2]; pid_t pid; struct sigaction sa; int r; timeout_callback = cb; /* set up a pipe to communicate with the * timeout process */ r = pipe(pipefd); if (r < 0) { perror("timeout: pipe"); return -1; } /* fork the timeout process */ pid = fork(); if (pid < 0) { perror("timeout: fork"); return -1; } if (pid) { /* parent */ timeout_pid = pid; timeout_fd = dup2(pipefd[PIPE_WRITE], 253); if (timeout_fd < 0) { perror("timeout: dup2"); return -1; } close(pipefd[PIPE_READ]); close(pipefd[PIPE_WRITE]); memset(&sa, 0, sizeof(sa)); sa.sa_handler = sigusr1_handler; sa.sa_flags = SA_NODEFER; sigaction(SIGUSR1, &sa, NULL); } else { /* child */ close(pipefd[PIPE_WRITE]); timeout_mainloop(pipefd[PIPE_READ], getppid()); exit(0); } return 0; } int timeout_begin(int millisec) { int c; int r; // fprintf(stderr, "timeout_begin\n"); if (timeout_fd < 0) return -1; c = CMD_BEGIN; r = write(timeout_fd, &c, 1); if (r < 0) { perror("timeout: write"); return -1; } r = write(timeout_fd, &millisec, sizeof(millisec)); if (r < 0) { perror("timeout: write"); return -1; } return 0; } int timeout_end(void) { int c; int r; // fprintf(stderr, "timeout_end\n"); if (timeout_fd < 0) return -1; c = CMD_END; r = write(timeout_fd, &c, 1); if (r < 0) { perror("timeout: write"); return -1; } return 0; } void timeout_fini(void) { int r; int status; if (timeout_fd >= 0) { close(timeout_fd); timeout_fd = -1; } if (timeout_pid > 0) { r = kill(timeout_pid, SIGTERM); if (r < 0 && errno != ESRCH) perror("timeout: kill"); else waitpid(timeout_pid, &status, 0); timeout_pid = -1; } signal(SIGUSR1, SIG_IGN); } cyrus-imapd-2.5.10/cunit/binhex.testc0000644000175000017500000001062713001236020014411 00000000000000#include "cunit/cunit.h" #include "util.h" static void test_bin_to_hex(void) { static const unsigned char BIN[4] = { 0xca, 0xfe, 0xba, 0xbe }; static const char HEX[9] = "cafebabe"; int r; char hex[9]; memset(hex, 0x45, sizeof(hex)); r = bin_to_hex(BIN, sizeof(BIN), hex, BH_LOWER); CU_ASSERT_EQUAL(r, sizeof(hex)-1); CU_ASSERT_STRING_EQUAL(hex, HEX); } static void test_bin_to_hex_long(void) { static const unsigned char BIN[20] = { 0x33,0xac,0x18,0xb6,0xdc,0x74,0x6e,0x9a,0xd7,0xbd, 0x6f,0x9f,0xfa,0x77,0xe4,0x04,0x84,0x04,0xa0,0x02 }; static const char HEX[41] = "33ac18b6dc746e9ad7bd6f9ffa77e4048404a002"; int r; char hex[41]; memset(hex, 0x45, sizeof(hex)); r = bin_to_hex(BIN, sizeof(BIN), hex, BH_LOWER); CU_ASSERT_EQUAL(r, sizeof(hex)-1); CU_ASSERT_STRING_EQUAL(hex, HEX); } static void test_bin_to_hex_short(void) { static const unsigned char BIN[1] = { 0x42 }; static const char HEX[3] = "42"; int r; char hex[3]; memset(hex, 0x45, sizeof(hex)); r = bin_to_hex(BIN, sizeof(BIN), hex, BH_LOWER); CU_ASSERT_EQUAL(r, sizeof(hex)-1); CU_ASSERT_STRING_EQUAL(hex, HEX); } static void test_bin_to_hex_sep(void) { static const unsigned char BIN[4] = { 0xca, 0xfe, 0xba, 0xbe }; static const char HEX[12] = "ca:fe:ba:be"; int r; char hex[12]; memset(hex, 0x45, sizeof(hex)); r = bin_to_hex(BIN, sizeof(BIN), hex, BH_LOWER|BH_SEPARATOR(':')); CU_ASSERT_EQUAL(r, sizeof(hex)-1); CU_ASSERT_STRING_EQUAL(hex, HEX); } static void test_hex_to_bin(void) { static const char HEX[9] = "cafebabe"; static const unsigned char BIN[4] = { 0xca, 0xfe, 0xba, 0xbe }; int r; char bin[4]; memset(bin, 0xff, sizeof(bin)); r = hex_to_bin(HEX, sizeof(HEX)-1, bin); CU_ASSERT_EQUAL(r, sizeof(bin)); CU_ASSERT_EQUAL(memcmp(bin, BIN, sizeof(bin)), 0); } static void test_hex_to_bin_short(void) { static const char HEX[3] = "42"; static const unsigned char BIN[1] = { 0x42 }; int r; char bin[1]; memset(bin, 0xff, sizeof(bin)); r = hex_to_bin(HEX, sizeof(HEX)-1, bin); CU_ASSERT_EQUAL(r, sizeof(bin)); CU_ASSERT_EQUAL(memcmp(bin, BIN, sizeof(bin)), 0); } static void test_hex_to_bin_long(void) { static const char HEX[41] = "33ac18b6dc746e9ad7bd6f9ffa77e4048404a002"; static const unsigned char BIN[20] = { 0x33,0xac,0x18,0xb6,0xdc,0x74,0x6e,0x9a,0xd7,0xbd, 0x6f,0x9f,0xfa,0x77,0xe4,0x04,0x84,0x04,0xa0,0x02 }; int r; char bin[20]; memset(bin, 0xff, sizeof(bin)); r = hex_to_bin(HEX, sizeof(HEX)-1, bin); CU_ASSERT_EQUAL(r, sizeof(bin)); CU_ASSERT_EQUAL(memcmp(bin, BIN, sizeof(bin)), 0); } static void test_hex_to_bin_capitals(void) { static const char HEX[9] = "CAFEBABE"; static const unsigned char BIN[4] = { 0xca, 0xfe, 0xba, 0xbe }; int r; char bin[4]; memset(bin, 0xff, sizeof(bin)); r = hex_to_bin(HEX, sizeof(HEX)-1, bin); CU_ASSERT_EQUAL(r, sizeof(bin)); CU_ASSERT_EQUAL(memcmp(bin, BIN, sizeof(bin)), 0); } static void test_hex_to_bin_odd(void) { static const char HEX[8] = "cafebab"; int r; unsigned char bin[4]; memset(bin, 0xff, sizeof(bin)); r = hex_to_bin(HEX, sizeof(HEX)-1, bin); CU_ASSERT_EQUAL(r, -1); CU_ASSERT_EQUAL(bin[0], 0xff); CU_ASSERT_EQUAL(bin[1], 0xff); CU_ASSERT_EQUAL(bin[2], 0xff); CU_ASSERT_EQUAL(bin[3], 0xff); } static void test_hex_to_bin_nonxdigit(void) { static const char HEX[9] = "foobarly"; int r; char bin[4]; memset(bin, 0xff, sizeof(bin)); r = hex_to_bin(HEX, sizeof(HEX)-1, bin); CU_ASSERT_EQUAL(r, -1); } static void test_hex_to_bin_whitespace(void) { static const char HEX[13] = " cafebabe "; int r; char bin[4]; memset(bin, 0xff, sizeof(bin)); r = hex_to_bin(HEX, sizeof(HEX)-1, bin); CU_ASSERT_EQUAL(r, -1); } static void test_hex_to_bin_nolength(void) { static const char HEX[9] = "cafebabe"; static const unsigned char BIN[4] = { 0xca, 0xfe, 0xba, 0xbe }; int r; char bin[4]; memset(bin, 0xff, sizeof(bin)); r = hex_to_bin(HEX, 0, bin); CU_ASSERT_EQUAL(r, sizeof(bin)); CU_ASSERT_EQUAL(memcmp(bin, BIN, sizeof(bin)), 0); } static void test_hex_to_bin_null(void) { int r; unsigned char bin[1]; memset(bin, 0xff, sizeof(bin)); r = hex_to_bin(NULL, 0, bin); CU_ASSERT_EQUAL(r, -1); CU_ASSERT_EQUAL(bin[0], 0xff); } /* vim: set ft=c: */ cyrus-imapd-2.5.10/cunit/strarray.testc0000644000175000017500000014172413001236020015006 00000000000000#include "cunit/cunit.h" #include "xmalloc.h" #include "bsearch.h" #include "strarray.h" static void test_fini_null(void) { /* _fini(NULL) is harmless */ strarray_fini(NULL); /* _free(NULL) is harmless */ strarray_free(NULL); } static void test_auto(void) { strarray_t sa = STRARRAY_INITIALIZER; char *s1; char *s2; CU_ASSERT_EQUAL(strarray_size(&sa), 0); CU_ASSERT(sa.alloc >= strarray_size(&sa)); CU_ASSERT_PTR_NULL(strarray_nth(&sa, 0)); CU_ASSERT_PTR_NULL(strarray_nth(&sa, -1)); s1 = xstrdup("lorem ipsum"); strarray_appendm(&sa, s1); CU_ASSERT_EQUAL(strarray_size(&sa), 1); CU_ASSERT(sa.alloc >= strarray_size(&sa)); CU_ASSERT_PTR_NOT_NULL(sa.data); CU_ASSERT_PTR_EQUAL((char *)strarray_nth(&sa, 0), s1); CU_ASSERT_PTR_EQUAL((char *)strarray_nth(&sa, -1), s1); s2 = xstrdup("dolor sit"); strarray_appendm(&sa, s2); CU_ASSERT_EQUAL(strarray_size(&sa), 2); CU_ASSERT(sa.alloc >= strarray_size(&sa)); CU_ASSERT_PTR_NOT_NULL(sa.data); CU_ASSERT_PTR_EQUAL((char *)strarray_nth(&sa, 0), s1); CU_ASSERT_PTR_EQUAL((char *)strarray_nth(&sa, 1), s2); CU_ASSERT_PTR_EQUAL((char *)strarray_nth(&sa, -1), s2); strarray_fini(&sa); CU_ASSERT_EQUAL(strarray_size(&sa), 0); CU_ASSERT_EQUAL(sa.alloc, 0); CU_ASSERT_PTR_NULL(sa.data); } static void test_heap(void) { strarray_t *sa = strarray_new(); char *s1; char *s2; CU_ASSERT_EQUAL(sa->count, 0); CU_ASSERT(sa->alloc >= sa->count); CU_ASSERT_PTR_NULL((char *)strarray_nth(sa, 0)); CU_ASSERT_PTR_NULL((char *)strarray_nth(sa, -1)); s1 = xstrdup("lorem ipsum"); strarray_appendm(sa, s1); CU_ASSERT_EQUAL(sa->count, 1); CU_ASSERT(sa->alloc >= sa->count); CU_ASSERT_PTR_NOT_NULL(sa->data); CU_ASSERT_PTR_EQUAL((char *)strarray_nth(sa, 0), s1); CU_ASSERT_PTR_EQUAL((char *)strarray_nth(sa, -1), s1); s2 = xstrdup("dolor sit"); strarray_appendm(sa, s2); CU_ASSERT_EQUAL(sa->count, 2); CU_ASSERT(sa->alloc >= sa->count); CU_ASSERT_PTR_NOT_NULL(sa->data); CU_ASSERT_PTR_EQUAL((char *)strarray_nth(sa, 0), s1); CU_ASSERT_PTR_EQUAL((char *)strarray_nth(sa, 1), s2); CU_ASSERT_PTR_EQUAL((char *)strarray_nth(sa, -1), s2); strarray_free(sa); } static void test_set(void) { strarray_t sa = STRARRAY_INITIALIZER; #define WORD0 "lorem" #define WORD0REP "DeLorean" #define WORD0REP2 "Jiggawatts" #define WORD1 "ipsum" #define WORD2 "dolor" #define WORD2REP "DOLORES" #define WORD3 "sit" #define WORD4 "amet" CU_ASSERT_EQUAL(strarray_size(&sa), 0); CU_ASSERT(sa.alloc >= strarray_size(&sa)); CU_ASSERT_PTR_NULL(strarray_nth(&sa, 0)); CU_ASSERT_PTR_NULL(strarray_nth(&sa, -1)); strarray_append(&sa, WORD0); CU_ASSERT_EQUAL(strarray_size(&sa), 1); CU_ASSERT(sa.alloc >= strarray_size(&sa)); CU_ASSERT_PTR_NOT_NULL(sa.data); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 0), WORD0); strarray_set(&sa, 0, WORD0REP); CU_ASSERT_EQUAL(strarray_size(&sa), 1); CU_ASSERT(sa.alloc >= strarray_size(&sa)); CU_ASSERT_PTR_NOT_NULL(sa.data); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 0), WORD0REP); strarray_set(&sa, -1, WORD0REP2); CU_ASSERT_EQUAL(strarray_size(&sa), 1); CU_ASSERT(sa.alloc >= strarray_size(&sa)); CU_ASSERT_PTR_NOT_NULL(sa.data); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 0), WORD0REP2); strarray_append(&sa, WORD1); strarray_append(&sa, WORD2); strarray_append(&sa, WORD3); strarray_append(&sa, WORD4); CU_ASSERT_EQUAL(strarray_size(&sa), 5); CU_ASSERT(sa.alloc >= strarray_size(&sa)); CU_ASSERT_PTR_NOT_NULL(sa.data); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 0), WORD0REP2); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 1), WORD1); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 2), WORD2); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 3), WORD3); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 4), WORD4); strarray_set(&sa, 2, WORD2REP); CU_ASSERT_EQUAL(strarray_size(&sa), 5); CU_ASSERT(sa.alloc >= strarray_size(&sa)); CU_ASSERT_PTR_NOT_NULL(sa.data); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 0), WORD0REP2); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 1), WORD1); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 2), WORD2REP); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 3), WORD3); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 4), WORD4); strarray_fini(&sa); #undef WORD0 #undef WORD0REP #undef WORD0REP2 #undef WORD1 #undef WORD2 #undef WORD2REP #undef WORD3 #undef WORD4 } static void test_setm(void) { strarray_t sa = STRARRAY_INITIALIZER; #define WORD0 "lorem" #define WORD0REP "DeLorean" #define WORD0REP2 "Jiggawatts" #define WORD1 "ipsum" #define WORD2 "dolor" #define WORD2REP "DOLORES" #define WORD3 "sit" #define WORD4 "amet" CU_ASSERT_EQUAL(strarray_size(&sa), 0); CU_ASSERT(sa.alloc >= strarray_size(&sa)); CU_ASSERT_PTR_NULL(strarray_nth(&sa, 0)); CU_ASSERT_PTR_NULL(strarray_nth(&sa, -1)); strarray_appendm(&sa, xstrdup(WORD0)); CU_ASSERT_EQUAL(strarray_size(&sa), 1); CU_ASSERT(sa.alloc >= strarray_size(&sa)); CU_ASSERT_PTR_NOT_NULL(sa.data); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 0), WORD0); strarray_setm(&sa, 0, xstrdup(WORD0REP)); CU_ASSERT_EQUAL(strarray_size(&sa), 1); CU_ASSERT(sa.alloc >= strarray_size(&sa)); CU_ASSERT_PTR_NOT_NULL(sa.data); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 0), WORD0REP); strarray_setm(&sa, -1, xstrdup(WORD0REP2)); CU_ASSERT_EQUAL(strarray_size(&sa), 1); CU_ASSERT(sa.alloc >= strarray_size(&sa)); CU_ASSERT_PTR_NOT_NULL(sa.data); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 0), WORD0REP2); strarray_appendm(&sa, xstrdup(WORD1)); strarray_appendm(&sa, xstrdup(WORD2)); strarray_appendm(&sa, xstrdup(WORD3)); strarray_appendm(&sa, xstrdup(WORD4)); CU_ASSERT_EQUAL(strarray_size(&sa), 5); CU_ASSERT(sa.alloc >= strarray_size(&sa)); CU_ASSERT_PTR_NOT_NULL(sa.data); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 0), WORD0REP2); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 1), WORD1); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 2), WORD2); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 3), WORD3); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 4), WORD4); strarray_setm(&sa, 2, xstrdup(WORD2REP)); CU_ASSERT_EQUAL(strarray_size(&sa), 5); CU_ASSERT(sa.alloc >= strarray_size(&sa)); CU_ASSERT_PTR_NOT_NULL(sa.data); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 0), WORD0REP2); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 1), WORD1); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 2), WORD2REP); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 3), WORD3); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 4), WORD4); strarray_fini(&sa); #undef WORD0 #undef WORD0REP #undef WORD0REP2 #undef WORD1 #undef WORD2 #undef WORD2REP #undef WORD3 #undef WORD4 } static void test_insert(void) { strarray_t sa = STRARRAY_INITIALIZER; #define WORD0 "lorem" #define WORD1 "ipsum" #define WORD2 "dolor" #define WORD3 "sit" #define WORD4 "amet" CU_ASSERT_EQUAL(strarray_size(&sa), 0); CU_ASSERT(sa.alloc >= strarray_size(&sa)); CU_ASSERT_PTR_NULL(strarray_nth(&sa, 0)); CU_ASSERT_PTR_NULL(strarray_nth(&sa, -1)); strarray_insert(&sa, 0, WORD0); CU_ASSERT_EQUAL(strarray_size(&sa), 1); CU_ASSERT(sa.alloc >= strarray_size(&sa)); CU_ASSERT_PTR_NOT_NULL(sa.data); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 0), WORD0); strarray_insert(&sa, -1, WORD1); CU_ASSERT_EQUAL(strarray_size(&sa), 2); CU_ASSERT(sa.alloc >= strarray_size(&sa)); CU_ASSERT_PTR_NOT_NULL(sa.data); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 0), WORD1); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 1), WORD0); strarray_insert(&sa, 0, WORD2); CU_ASSERT_EQUAL(strarray_size(&sa), 3); CU_ASSERT(sa.alloc >= strarray_size(&sa)); CU_ASSERT_PTR_NOT_NULL(sa.data); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 0), WORD2); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 1), WORD1); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 2), WORD0); strarray_insert(&sa, -1, WORD3); CU_ASSERT_EQUAL(strarray_size(&sa), 4); CU_ASSERT(sa.alloc >= strarray_size(&sa)); CU_ASSERT_PTR_NOT_NULL(sa.data); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 0), WORD2); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 1), WORD1); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 2), WORD3); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 3), WORD0); strarray_insert(&sa, 2, WORD4); CU_ASSERT_EQUAL(strarray_size(&sa), 5); CU_ASSERT(sa.alloc >= strarray_size(&sa)); CU_ASSERT_PTR_NOT_NULL(sa.data); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 0), WORD2); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 1), WORD1); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 2), WORD4); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 3), WORD3); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 4), WORD0); strarray_fini(&sa); #undef WORD0 #undef WORD1 #undef WORD2 #undef WORD3 #undef WORD4 } static void test_insertm(void) { strarray_t sa = STRARRAY_INITIALIZER; #define WORD0 "lorem" #define WORD1 "ipsum" #define WORD2 "dolor" #define WORD3 "sit" #define WORD4 "amet" CU_ASSERT_EQUAL(strarray_size(&sa), 0); CU_ASSERT(sa.alloc >= strarray_size(&sa)); CU_ASSERT_PTR_NULL(strarray_nth(&sa, 0)); CU_ASSERT_PTR_NULL(strarray_nth(&sa, -1)); strarray_insertm(&sa, 0, xstrdup(WORD0)); CU_ASSERT_EQUAL(strarray_size(&sa), 1); CU_ASSERT(sa.alloc >= strarray_size(&sa)); CU_ASSERT_PTR_NOT_NULL(sa.data); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 0), WORD0); strarray_insertm(&sa, -1, xstrdup(WORD1)); CU_ASSERT_EQUAL(strarray_size(&sa), 2); CU_ASSERT(sa.alloc >= strarray_size(&sa)); CU_ASSERT_PTR_NOT_NULL(sa.data); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 0), WORD1); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 1), WORD0); strarray_insertm(&sa, 0, xstrdup(WORD2)); CU_ASSERT_EQUAL(strarray_size(&sa), 3); CU_ASSERT(sa.alloc >= strarray_size(&sa)); CU_ASSERT_PTR_NOT_NULL(sa.data); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 0), WORD2); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 1), WORD1); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 2), WORD0); strarray_insertm(&sa, -1, xstrdup(WORD3)); CU_ASSERT_EQUAL(strarray_size(&sa), 4); CU_ASSERT(sa.alloc >= strarray_size(&sa)); CU_ASSERT_PTR_NOT_NULL(sa.data); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 0), WORD2); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 1), WORD1); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 2), WORD3); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 3), WORD0); strarray_insertm(&sa, 2, xstrdup(WORD4)); CU_ASSERT_EQUAL(strarray_size(&sa), 5); CU_ASSERT(sa.alloc >= strarray_size(&sa)); CU_ASSERT_PTR_NOT_NULL(sa.data); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 0), WORD2); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 1), WORD1); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 2), WORD4); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 3), WORD3); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 4), WORD0); strarray_fini(&sa); #undef WORD0 #undef WORD1 #undef WORD2 #undef WORD3 #undef WORD4 } /* test that _set(), _setm(), _insert() and _insertm() of a bad * index will fail silently and leave no side effects including * memory leaks */ static void test_bad_index(void) { strarray_t sa = STRARRAY_INITIALIZER; #define WORD0 "lorem" #define WORD1 "ipsum" #define WORD2 "dolor" char *s = xstrdup(WORD0); CU_ASSERT_EQUAL(strarray_size(&sa), 0); CU_ASSERT(sa.alloc >= strarray_size(&sa)); CU_ASSERT_PTR_NULL(strarray_nth(&sa, 0)); CU_ASSERT_PTR_NULL(strarray_nth(&sa, -1)); /* when the strarray is empty, -1 is a bad index */ strarray_setm(&sa, -1, s); CU_ASSERT_EQUAL(strarray_size(&sa), 0); CU_ASSERT_PTR_NULL(strarray_nth(&sa, 0)); CU_ASSERT_PTR_NULL(strarray_nth(&sa, -1)); strarray_set(&sa, -1, WORD0); CU_ASSERT_EQUAL(strarray_size(&sa), 0); CU_ASSERT_PTR_NULL(strarray_nth(&sa, 0)); CU_ASSERT_PTR_NULL(strarray_nth(&sa, -1)); strarray_insertm(&sa, -1, s); CU_ASSERT_EQUAL(strarray_size(&sa), 0); CU_ASSERT_PTR_NULL(strarray_nth(&sa, 0)); CU_ASSERT_PTR_NULL(strarray_nth(&sa, -1)); strarray_insert(&sa, -1, WORD0); CU_ASSERT_EQUAL(strarray_size(&sa), 0); CU_ASSERT_PTR_NULL(strarray_nth(&sa, 0)); CU_ASSERT_PTR_NULL(strarray_nth(&sa, -1)); /* a negative number larger than the (non-zero) count is a bad index */ strarray_append(&sa, WORD1); strarray_append(&sa, WORD2); strarray_setm(&sa, -4, s); CU_ASSERT_EQUAL(strarray_size(&sa), 2); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 0), WORD1); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, -1), WORD2); strarray_set(&sa, -4, WORD0); CU_ASSERT_EQUAL(strarray_size(&sa), 2); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 0), WORD1); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, -1), WORD2); strarray_insertm(&sa, -4, s); CU_ASSERT_EQUAL(strarray_size(&sa), 2); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 0), WORD1); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, -1), WORD2); strarray_insert(&sa, -4, WORD0); CU_ASSERT_EQUAL(strarray_size(&sa), 2); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 0), WORD1); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, -1), WORD2); free(s); strarray_fini(&sa); #undef WORD0 #undef WORD1 #undef WORD2 } /* test building a sparse array with _set() and _setm() */ static void test_sparse_set(void) { strarray_t sa = STRARRAY_INITIALIZER; #define WORD0 "lorem" #define WORD1 "ipsum" #define WORD2 "dolor" CU_ASSERT_EQUAL(strarray_size(&sa), 0); CU_ASSERT(sa.alloc >= strarray_size(&sa)); CU_ASSERT_PTR_NULL(strarray_nth(&sa, 0)); CU_ASSERT_PTR_NULL(strarray_nth(&sa, -1)); strarray_set(&sa, 3, WORD0); CU_ASSERT_EQUAL(strarray_size(&sa), 4); CU_ASSERT(sa.alloc >= strarray_size(&sa)); CU_ASSERT_PTR_NULL(strarray_nth(&sa, 0)); CU_ASSERT_PTR_NULL(strarray_nth(&sa, 1)); CU_ASSERT_PTR_NULL(strarray_nth(&sa, 2)); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 3), WORD0); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, -1), WORD0); strarray_fini(&sa); #undef WORD0 #undef WORD1 #undef WORD2 } static void test_join(void) { strarray_t sa = STRARRAY_INITIALIZER; char *s; #define WORD0 "lorem" #define WORD1 "ipsum" #define WORD2 "dolor" #define WORD3 "sit" #define WORD4 "amet" CU_ASSERT_EQUAL(strarray_size(&sa), 0); CU_ASSERT(sa.alloc >= strarray_size(&sa)); CU_ASSERT_PTR_NULL(strarray_nth(&sa, 0)); CU_ASSERT_PTR_NULL(strarray_nth(&sa, -1)); s = strarray_join(&sa, NULL); CU_ASSERT_PTR_NULL(s); s = strarray_join(&sa, " "); CU_ASSERT_PTR_NULL(s); strarray_append(&sa, WORD0); strarray_append(&sa, WORD1); strarray_append(&sa, WORD2); strarray_append(&sa, WORD3); strarray_append(&sa, WORD4); CU_ASSERT_EQUAL(strarray_size(&sa), 5); CU_ASSERT(sa.alloc >= strarray_size(&sa)); CU_ASSERT_PTR_NOT_NULL(sa.data); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 0), WORD0); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 1), WORD1); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 2), WORD2); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 3), WORD3); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 4), WORD4); s = strarray_join(&sa, NULL); CU_ASSERT_STRING_EQUAL(s, WORD0""WORD1""WORD2""WORD3""WORD4); free(s); s = strarray_join(&sa, " "); CU_ASSERT_STRING_EQUAL(s, WORD0" "WORD1" "WORD2" "WORD3" "WORD4); free(s); s = strarray_join(&sa, "-X-"); CU_ASSERT_STRING_EQUAL(s, WORD0"-X-"WORD1"-X-"WORD2"-X-"WORD3"-X-"WORD4); free(s); /* check that sa is unharmed by the join */ CU_ASSERT_EQUAL(strarray_size(&sa), 5); CU_ASSERT(sa.alloc >= strarray_size(&sa)); CU_ASSERT_PTR_NOT_NULL(sa.data); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 0), WORD0); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 1), WORD1); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 2), WORD2); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 3), WORD3); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 4), WORD4); strarray_fini(&sa); #undef WORD0 #undef WORD1 #undef WORD2 #undef WORD3 #undef WORD4 } /* regression test for a bug discovered while reading the * strarray source when triaging Coverity defects. */ static void test_join_initial_null(void) { strarray_t sa = STRARRAY_INITIALIZER; char *s; #define WORD0 "lorem" #define WORD1 "ipsum" CU_ASSERT_EQUAL(strarray_size(&sa), 0); CU_ASSERT(sa.alloc >= strarray_size(&sa)); CU_ASSERT_PTR_NULL(strarray_nth(&sa, 0)); CU_ASSERT_PTR_NULL(strarray_nth(&sa, -1)); /* [0] element is NULL */ strarray_set(&sa, 1, WORD0); strarray_set(&sa, 2, WORD1); CU_ASSERT_EQUAL(strarray_size(&sa), 3); CU_ASSERT(sa.alloc >= strarray_size(&sa)); CU_ASSERT_PTR_NOT_NULL(sa.data); CU_ASSERT_PTR_NULL(strarray_nth(&sa, 0)); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 1), WORD0); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 2), WORD1); s = strarray_join(&sa, NULL); CU_ASSERT_STRING_EQUAL(s, WORD0""WORD1); free(s); s = strarray_join(&sa, " "); CU_ASSERT_STRING_EQUAL(s, WORD0" "WORD1); free(s); s = strarray_join(&sa, "-X-"); CU_ASSERT_STRING_EQUAL(s, WORD0"-X-"WORD1); free(s); /* check that sa is unharmed by the join */ CU_ASSERT_EQUAL(strarray_size(&sa), 3); CU_ASSERT(sa.alloc >= strarray_size(&sa)); CU_ASSERT_PTR_NOT_NULL(sa.data); CU_ASSERT_PTR_NULL(strarray_nth(&sa, 0)); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 1), WORD0); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 2), WORD1); strarray_fini(&sa); #undef WORD0 #undef WORD1 } static void test_split(void) { strarray_t *sa; #define WORD0 "lorem" #define WORD1 "ipsum" #define WORD2 "dolor" #define WORD3 "sit" #define WORD4 "amet" /* 5 words, space separator */ sa = strarray_split(WORD0" "WORD1" "WORD2" "WORD3" "WORD4, " ", 0); CU_ASSERT_PTR_NOT_NULL(sa); CU_ASSERT_EQUAL(sa->count, 5); CU_ASSERT(sa->alloc >= sa->count); CU_ASSERT_PTR_NOT_NULL(sa->data); CU_ASSERT_STRING_EQUAL(strarray_nth(sa, 0), WORD0); CU_ASSERT_STRING_EQUAL(strarray_nth(sa, 1), WORD1); CU_ASSERT_STRING_EQUAL(strarray_nth(sa, 2), WORD2); CU_ASSERT_STRING_EQUAL(strarray_nth(sa, 3), WORD3); CU_ASSERT_STRING_EQUAL(strarray_nth(sa, 4), WORD4); strarray_free(sa); /* 5 words, NULL separator (whitespace) */ sa = strarray_split(WORD0" "WORD1"\t"WORD2"\r"WORD3"\n"WORD4, NULL, 0); CU_ASSERT_PTR_NOT_NULL(sa); CU_ASSERT_EQUAL(sa->count, 5); CU_ASSERT(sa->alloc >= sa->count); CU_ASSERT_PTR_NOT_NULL(sa->data); CU_ASSERT_STRING_EQUAL(strarray_nth(sa, 0), WORD0); CU_ASSERT_STRING_EQUAL(strarray_nth(sa, 1), WORD1); CU_ASSERT_STRING_EQUAL(strarray_nth(sa, 2), WORD2); CU_ASSERT_STRING_EQUAL(strarray_nth(sa, 3), WORD3); CU_ASSERT_STRING_EQUAL(strarray_nth(sa, 4), WORD4); strarray_free(sa); /* 5 words, several separators */ sa = strarray_split(WORD0"("WORD1")"WORD2"["WORD3"]"WORD4, "[]()", 0); CU_ASSERT_PTR_NOT_NULL(sa); CU_ASSERT_EQUAL(sa->count, 5); CU_ASSERT(sa->alloc >= sa->count); CU_ASSERT_PTR_NOT_NULL(sa->data); CU_ASSERT_STRING_EQUAL(strarray_nth(sa, 0), WORD0); CU_ASSERT_STRING_EQUAL(strarray_nth(sa, 1), WORD1); CU_ASSERT_STRING_EQUAL(strarray_nth(sa, 2), WORD2); CU_ASSERT_STRING_EQUAL(strarray_nth(sa, 3), WORD3); CU_ASSERT_STRING_EQUAL(strarray_nth(sa, 4), WORD4); strarray_free(sa); /* splitm - takes ownership of a strdup()d argument */ sa = strarray_splitm(xstrdup(WORD0" "WORD1" "WORD2" "WORD3" "WORD4), " ", 0); CU_ASSERT_PTR_NOT_NULL(sa); CU_ASSERT_EQUAL(sa->count, 5); CU_ASSERT(sa->alloc >= sa->count); CU_ASSERT_PTR_NOT_NULL(sa->data); CU_ASSERT_STRING_EQUAL(strarray_nth(sa, 0), WORD0); CU_ASSERT_STRING_EQUAL(strarray_nth(sa, 1), WORD1); CU_ASSERT_STRING_EQUAL(strarray_nth(sa, 2), WORD2); CU_ASSERT_STRING_EQUAL(strarray_nth(sa, 3), WORD3); CU_ASSERT_STRING_EQUAL(strarray_nth(sa, 4), WORD4); strarray_free(sa); /* nsplit - specify a byte range to copy and split */ sa = strarray_nsplit(WORD0" "WORD1" "WORD2" "WORD3" "WORD4, sizeof(WORD0)+sizeof(WORD1)+sizeof(WORD2), " ", 0); CU_ASSERT_PTR_NOT_NULL(sa); CU_ASSERT_EQUAL(sa->count, 3); CU_ASSERT(sa->alloc >= sa->count); CU_ASSERT_PTR_NOT_NULL(sa->data); CU_ASSERT_STRING_EQUAL(strarray_nth(sa, 0), WORD0); CU_ASSERT_STRING_EQUAL(strarray_nth(sa, 1), WORD1); CU_ASSERT_STRING_EQUAL(strarray_nth(sa, 2), WORD2); strarray_free(sa); /* split with surrounding whitespace */ sa = strarray_split(WORD0"| "WORD1" | "WORD2" |"WORD3" | "WORD4"| ", "|", 0); CU_ASSERT_PTR_NOT_NULL(sa); CU_ASSERT_EQUAL(sa->count, 6); CU_ASSERT(sa->alloc >= sa->count); CU_ASSERT_PTR_NOT_NULL(sa->data); CU_ASSERT_STRING_EQUAL(strarray_nth(sa, 0), WORD0); CU_ASSERT_STRING_EQUAL(strarray_nth(sa, 1), " "WORD1" "); CU_ASSERT_STRING_EQUAL(strarray_nth(sa, 2), " "WORD2" "); CU_ASSERT_STRING_EQUAL(strarray_nth(sa, 3), WORD3" "); CU_ASSERT_STRING_EQUAL(strarray_nth(sa, 4), " "WORD4); CU_ASSERT_STRING_EQUAL(strarray_nth(sa, 5), " "); strarray_free(sa); /* trim surrounding whitespace */ sa = strarray_split(WORD0"| "WORD1" | "WORD2" |"WORD3" | "WORD4"| ", "|", STRARRAY_TRIM); CU_ASSERT_PTR_NOT_NULL(sa); CU_ASSERT_EQUAL(sa->count, 5); CU_ASSERT(sa->alloc >= sa->count); CU_ASSERT_PTR_NOT_NULL(sa->data); CU_ASSERT_STRING_EQUAL(strarray_nth(sa, 0), WORD0); CU_ASSERT_STRING_EQUAL(strarray_nth(sa, 1), WORD1); CU_ASSERT_STRING_EQUAL(strarray_nth(sa, 2), WORD2); CU_ASSERT_STRING_EQUAL(strarray_nth(sa, 3), WORD3); CU_ASSERT_STRING_EQUAL(strarray_nth(sa, 4), WORD4); strarray_free(sa); #undef WORD0 #undef WORD1 #undef WORD2 #undef WORD3 #undef WORD4 } static void test_remove(void) { strarray_t sa = STRARRAY_INITIALIZER; char *s; #define WORD0 "lorem" #define WORD1 "ipsum" #define WORD2 "dolor" #define WORD3 "sit" #define WORD4 "amet" CU_ASSERT_EQUAL(strarray_size(&sa), 0); CU_ASSERT(sa.alloc >= strarray_size(&sa)); CU_ASSERT_PTR_NULL(strarray_nth(&sa, 0)); CU_ASSERT_PTR_NULL(strarray_nth(&sa, -1)); strarray_append(&sa, WORD0); strarray_append(&sa, WORD1); strarray_append(&sa, WORD2); strarray_append(&sa, WORD3); strarray_append(&sa, WORD4); CU_ASSERT_EQUAL(strarray_size(&sa), 5); CU_ASSERT(sa.alloc >= strarray_size(&sa)); CU_ASSERT_PTR_NOT_NULL(sa.data); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 0), WORD0); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 1), WORD1); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 2), WORD2); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 3), WORD3); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 4), WORD4); s = strarray_remove(&sa, 2); CU_ASSERT_STRING_EQUAL(s, WORD2); free(s); CU_ASSERT_EQUAL(strarray_size(&sa), 4); CU_ASSERT(sa.alloc >= strarray_size(&sa)); CU_ASSERT_PTR_NOT_NULL(sa.data); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 0), WORD0); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 1), WORD1); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 2), WORD3); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 3), WORD4); s = strarray_remove(&sa, 0); CU_ASSERT_STRING_EQUAL(s, WORD0); free(s); CU_ASSERT_EQUAL(strarray_size(&sa), 3); CU_ASSERT(sa.alloc >= strarray_size(&sa)); CU_ASSERT_PTR_NOT_NULL(sa.data); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 0), WORD1); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 1), WORD3); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 2), WORD4); s = strarray_remove(&sa, -1); CU_ASSERT_STRING_EQUAL(s, WORD4); free(s); CU_ASSERT_EQUAL(strarray_size(&sa), 2); CU_ASSERT(sa.alloc >= strarray_size(&sa)); CU_ASSERT_PTR_NOT_NULL(sa.data); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 0), WORD1); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 1), WORD3); s = strarray_remove(&sa, 1); CU_ASSERT_STRING_EQUAL(s, WORD3); free(s); CU_ASSERT_EQUAL(strarray_size(&sa), 1); CU_ASSERT(sa.alloc >= strarray_size(&sa)); CU_ASSERT_PTR_NOT_NULL(sa.data); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 0), WORD1); s = strarray_remove(&sa, 0); CU_ASSERT_STRING_EQUAL(s, WORD1); free(s); CU_ASSERT_EQUAL(strarray_size(&sa), 0); CU_ASSERT(sa.alloc >= strarray_size(&sa)); CU_ASSERT_PTR_NOT_NULL(sa.data); CU_ASSERT_PTR_NULL(strarray_nth(&sa, 0)); s = strarray_remove(&sa, 0); CU_ASSERT_PTR_NULL(s); strarray_fini(&sa); #undef WORD0 #undef WORD1 #undef WORD2 #undef WORD3 #undef WORD4 } static void test_takevf(void) { strarray_t *sa; char **ss; #define WORD0 "lorem" #define WORD1 "ipsum" #define WORD2 "dolor" #define WORD3 "sit" #define WORD4 "amet" /* 5 words, space separator */ sa = strarray_split(WORD0" "WORD1" "WORD2" "WORD3" "WORD4, " ", 0); CU_ASSERT_PTR_NOT_NULL(sa); CU_ASSERT_EQUAL(sa->count, 5); CU_ASSERT(sa->alloc >= sa->count); CU_ASSERT_PTR_NOT_NULL(sa->data); CU_ASSERT_STRING_EQUAL(strarray_nth(sa, 0), WORD0); CU_ASSERT_STRING_EQUAL(strarray_nth(sa, 1), WORD1); CU_ASSERT_STRING_EQUAL(strarray_nth(sa, 2), WORD2); CU_ASSERT_STRING_EQUAL(strarray_nth(sa, 3), WORD3); CU_ASSERT_STRING_EQUAL(strarray_nth(sa, 4), WORD4); ss = strarray_takevf(sa); /* note: takevf frees the strarray itself */ CU_ASSERT_PTR_NOT_NULL(ss); CU_ASSERT_STRING_EQUAL(ss[0], WORD0); CU_ASSERT_STRING_EQUAL(ss[1], WORD1); CU_ASSERT_STRING_EQUAL(ss[2], WORD2); CU_ASSERT_STRING_EQUAL(ss[3], WORD3); CU_ASSERT_STRING_EQUAL(ss[4], WORD4); CU_ASSERT_PTR_NULL(ss[5]); free(ss[0]); free(ss[1]); free(ss[2]); free(ss[3]); free(ss[4]); free(ss); #undef WORD0 #undef WORD1 #undef WORD2 #undef WORD3 #undef WORD4 } static void test_truncate(void) { strarray_t sa = STRARRAY_INITIALIZER; #define WORD0 "lorem" #define WORD1 "ipsum" #define WORD2 "dolor" #define WORD3 "sit" #define WORD4 "amet" CU_ASSERT_EQUAL(strarray_size(&sa), 0); CU_ASSERT(sa.alloc >= strarray_size(&sa)); CU_ASSERT_PTR_NULL(strarray_nth(&sa, 0)); CU_ASSERT_PTR_NULL(strarray_nth(&sa, -1)); strarray_append(&sa, WORD0); strarray_append(&sa, WORD1); strarray_append(&sa, WORD2); strarray_append(&sa, WORD3); strarray_append(&sa, WORD4); CU_ASSERT_EQUAL(strarray_size(&sa), 5); CU_ASSERT(sa.alloc >= strarray_size(&sa)); CU_ASSERT_PTR_NOT_NULL(sa.data); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 0), WORD0); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 1), WORD1); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 2), WORD2); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 3), WORD3); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 4), WORD4); /* expand the array */ strarray_truncate(&sa, 7); CU_ASSERT_EQUAL(strarray_size(&sa), 7); CU_ASSERT(sa.alloc >= strarray_size(&sa)); CU_ASSERT_PTR_NOT_NULL(sa.data); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 0), WORD0); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 1), WORD1); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 2), WORD2); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 3), WORD3); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 4), WORD4); CU_ASSERT_PTR_NULL(strarray_nth(&sa, 5)); CU_ASSERT_PTR_NULL(strarray_nth(&sa, 6)); /* shrink the array */ strarray_truncate(&sa, 4); CU_ASSERT_EQUAL(strarray_size(&sa), 4); CU_ASSERT(sa.alloc >= strarray_size(&sa)); CU_ASSERT_PTR_NOT_NULL(sa.data); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 0), WORD0); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 1), WORD1); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 2), WORD2); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 3), WORD3); /* shrink the array harder */ strarray_truncate(&sa, 3); CU_ASSERT_EQUAL(strarray_size(&sa), 3); CU_ASSERT(sa.alloc >= strarray_size(&sa)); CU_ASSERT_PTR_NOT_NULL(sa.data); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 0), WORD0); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 1), WORD1); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 2), WORD2); /* shrink the array to nothing */ strarray_truncate(&sa, 0); CU_ASSERT_EQUAL(strarray_size(&sa), 0); CU_ASSERT(sa.alloc >= strarray_size(&sa)); /* whether sa.data is NULL is undefined at this time */ CU_ASSERT_PTR_NULL(strarray_nth(&sa, 0)); CU_ASSERT_PTR_NULL(strarray_nth(&sa, -1)); strarray_fini(&sa); #undef WORD0 #undef WORD1 #undef WORD2 #undef WORD3 #undef WORD4 } static void test_find(void) { strarray_t sa = STRARRAY_INITIALIZER; int i; #define WORD0 "lorem" #define WORD0 "lorem" #define WORD1 "ipsum" #define WORD1u "IPSUM" #define WORD1c "Ipsum" #define WORD2 "dolor" #define WORD3 "sit" #define WORD4 "amet" CU_ASSERT_EQUAL(strarray_size(&sa), 0); CU_ASSERT(sa.alloc >= strarray_size(&sa)); CU_ASSERT_PTR_NULL(strarray_nth(&sa, 0)); CU_ASSERT_PTR_NULL(strarray_nth(&sa, -1)); strarray_append(&sa, WORD0); strarray_append(&sa, WORD1); strarray_append(&sa, WORD2); strarray_append(&sa, WORD3); strarray_append(&sa, WORD0); strarray_append(&sa, WORD4); CU_ASSERT_EQUAL(strarray_size(&sa), 6); CU_ASSERT(sa.alloc >= strarray_size(&sa)); CU_ASSERT_PTR_NOT_NULL(sa.data); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 0), WORD0); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 1), WORD1); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 2), WORD2); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 3), WORD3); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 4), WORD0); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 5), WORD4); /* search for something which isn't there */ i = strarray_find(&sa, "NotHere", 0); CU_ASSERT_EQUAL(i, -1); /* search for something which isn't there, starting off the end */ i = strarray_find(&sa, "NotHere", 7); CU_ASSERT_EQUAL(i, -1); /* search for something which is there */ i = strarray_find(&sa, WORD1, 0); CU_ASSERT_EQUAL(i, 1); i = strarray_find(&sa, WORD1, i+1); CU_ASSERT_EQUAL(i, -1); /* search for something which isn't there but whose case analogue is */ i = strarray_find(&sa, WORD1u, 0); CU_ASSERT_EQUAL(i, -1); i = strarray_find(&sa, WORD1c, 0); CU_ASSERT_EQUAL(i, -1); /* search for something which is there, starting off the end */ i = strarray_find(&sa, WORD1, 7); CU_ASSERT_EQUAL(i, -1); /* search for something which is there multiple times */ i = strarray_find(&sa, WORD0, 0); CU_ASSERT_EQUAL(i, 0); i = strarray_find(&sa, WORD0, i+1); CU_ASSERT_EQUAL(i, 4); i = strarray_find(&sa, WORD0, i+1); CU_ASSERT_EQUAL(i, -1); strarray_fini(&sa); #undef WORD0 #undef WORD1 #undef WORD1u #undef WORD1c #undef WORD2 #undef WORD3 #undef WORD4 } static void test_find_case(void) { strarray_t sa = STRARRAY_INITIALIZER; int i; #define WORD0 "Lorem" #define WORD0u "LOREM" #define WORD0l "lorem" #define WORD0i "lOREM" #define WORD1 "iPSum" #define WORD1u "IPSUM" #define WORD1l "ipsum" #define WORD1i "IpsUM" #define WORD2 "DOLOR" #define WORD3 "sit" #define WORD4 "ameT" CU_ASSERT_EQUAL(strarray_size(&sa), 0); CU_ASSERT(sa.alloc >= strarray_size(&sa)); CU_ASSERT_PTR_NULL(strarray_nth(&sa, 0)); CU_ASSERT_PTR_NULL(strarray_nth(&sa, -1)); strarray_append(&sa, WORD0); strarray_append(&sa, WORD1); strarray_append(&sa, WORD2); strarray_append(&sa, WORD3); strarray_append(&sa, WORD0); strarray_append(&sa, WORD4); CU_ASSERT_EQUAL(strarray_size(&sa), 6); CU_ASSERT(sa.alloc >= strarray_size(&sa)); CU_ASSERT_PTR_NOT_NULL(sa.data); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 0), WORD0); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 1), WORD1); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 2), WORD2); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 3), WORD3); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 4), WORD0); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 5), WORD4); /* search for something which isn't there */ i = strarray_find_case(&sa, "NotHere", 0); CU_ASSERT_EQUAL(i, -1); /* search for something which isn't there, starting off the end */ i = strarray_find_case(&sa, "NotHere", 7); CU_ASSERT_EQUAL(i, -1); /* search for something which is there ... */ /* ... original capitalisation */ i = strarray_find_case(&sa, WORD1, 0); CU_ASSERT_EQUAL(i, 1); i = strarray_find_case(&sa, WORD1, i+1); CU_ASSERT_EQUAL(i, -1); /* ... lowercase key */ i = strarray_find_case(&sa, WORD1l, 0); CU_ASSERT_EQUAL(i, 1); i = strarray_find_case(&sa, WORD1l, i+1); CU_ASSERT_EQUAL(i, -1); /* ... uppercase key */ i = strarray_find_case(&sa, WORD1u, 0); CU_ASSERT_EQUAL(i, 1); i = strarray_find_case(&sa, WORD1u, i+1); CU_ASSERT_EQUAL(i, -1); /* ... inverted case key */ i = strarray_find_case(&sa, WORD1i, 0); CU_ASSERT_EQUAL(i, 1); i = strarray_find_case(&sa, WORD1i, i+1); CU_ASSERT_EQUAL(i, -1); /* search for something which is there, starting off the end ... */ /* ... original capitalisation */ i = strarray_find_case(&sa, WORD1, 7); CU_ASSERT_EQUAL(i, -1); /* ... lowercase key */ i = strarray_find_case(&sa, WORD1u, 7); CU_ASSERT_EQUAL(i, -1); /* ... uppercase key */ i = strarray_find_case(&sa, WORD1l, 7); CU_ASSERT_EQUAL(i, -1); /* ... inverted case key */ i = strarray_find_case(&sa, WORD1i, 7); CU_ASSERT_EQUAL(i, -1); /* search for something which is there multiple times ... */ /* ... original capitalisation */ i = strarray_find_case(&sa, WORD0, 0); CU_ASSERT_EQUAL(i, 0); i = strarray_find_case(&sa, WORD0, i+1); CU_ASSERT_EQUAL(i, 4); i = strarray_find_case(&sa, WORD0, i+1); CU_ASSERT_EQUAL(i, -1); /* ... lowercase key */ i = strarray_find_case(&sa, WORD0u, 0); CU_ASSERT_EQUAL(i, 0); i = strarray_find_case(&sa, WORD0u, i+1); CU_ASSERT_EQUAL(i, 4); i = strarray_find_case(&sa, WORD0u, i+1); CU_ASSERT_EQUAL(i, -1); /* ... uppercase key */ i = strarray_find_case(&sa, WORD0l, 0); CU_ASSERT_EQUAL(i, 0); i = strarray_find_case(&sa, WORD0l, i+1); CU_ASSERT_EQUAL(i, 4); i = strarray_find_case(&sa, WORD0l, i+1); CU_ASSERT_EQUAL(i, -1); /* ... inverted case key */ i = strarray_find_case(&sa, WORD0i, 0); CU_ASSERT_EQUAL(i, 0); i = strarray_find_case(&sa, WORD0i, i+1); CU_ASSERT_EQUAL(i, 4); i = strarray_find_case(&sa, WORD0i, i+1); CU_ASSERT_EQUAL(i, -1); strarray_fini(&sa); #undef WORD0 #undef WORD0u #undef WORD0l #undef WORD0i #undef WORD1 #undef WORD1u #undef WORD1l #undef WORD1i #undef WORD2 #undef WORD3 #undef WORD4 } static void test_dup(void) { strarray_t sa = STRARRAY_INITIALIZER; strarray_t *dup; #define WORD0 "lorem" #define WORD1 "ipsum" #define WORD2 "dolor" #define WORD3 "sit" #define WORD4 "amet" CU_ASSERT_EQUAL(strarray_size(&sa), 0); CU_ASSERT(sa.alloc >= strarray_size(&sa)); /* dup an empty array */ dup = strarray_dup(&sa); CU_ASSERT_PTR_NOT_NULL(dup); CU_ASSERT_PTR_NOT_EQUAL(dup, &sa); CU_ASSERT_EQUAL(dup->count, 0); CU_ASSERT(dup->alloc >= dup->count); strarray_free(dup); /* dup a non-empty array */ strarray_append(&sa, WORD0); strarray_append(&sa, WORD1); strarray_append(&sa, WORD2); strarray_append(&sa, WORD3); strarray_append(&sa, WORD0); strarray_append(&sa, WORD4); CU_ASSERT_EQUAL(strarray_size(&sa), 6); CU_ASSERT(sa.alloc >= strarray_size(&sa)); CU_ASSERT_PTR_NOT_NULL(sa.data); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 0), WORD0); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 1), WORD1); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 2), WORD2); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 3), WORD3); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 4), WORD0); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 5), WORD4); dup = strarray_dup(&sa); CU_ASSERT_PTR_NOT_NULL(dup); CU_ASSERT_PTR_NOT_EQUAL(dup, &sa); CU_ASSERT_EQUAL(dup->count, 6); CU_ASSERT(dup->alloc >= dup->count); CU_ASSERT_PTR_NOT_NULL(dup->data); CU_ASSERT_STRING_EQUAL(strarray_nth(dup, 0), WORD0); CU_ASSERT_PTR_NOT_EQUAL((void *)strarray_nth(dup, 0), (void *)strarray_nth(&sa, 0)); CU_ASSERT_STRING_EQUAL(strarray_nth(dup, 1), WORD1); CU_ASSERT_PTR_NOT_EQUAL((void *)strarray_nth(dup, 1), (void *)strarray_nth(&sa, 1)); CU_ASSERT_STRING_EQUAL(strarray_nth(dup, 2), WORD2); CU_ASSERT_PTR_NOT_EQUAL((void *)strarray_nth(dup, 2), (void *)strarray_nth(&sa, 2)); CU_ASSERT_STRING_EQUAL(strarray_nth(dup, 3), WORD3); CU_ASSERT_PTR_NOT_EQUAL((void *)strarray_nth(dup, 3), (void *)strarray_nth(&sa, 3)); CU_ASSERT_STRING_EQUAL(strarray_nth(dup, 4), WORD0); CU_ASSERT_PTR_NOT_EQUAL((void *)strarray_nth(dup, 4), (void *)strarray_nth(&sa, 4)); CU_ASSERT_STRING_EQUAL(strarray_nth(dup, 5), WORD4); CU_ASSERT_PTR_NOT_EQUAL((void *)strarray_nth(dup, 5), (void *)strarray_nth(&sa, 5)); strarray_free(dup); strarray_fini(&sa); #undef WORD0 #undef WORD1 #undef WORD2 #undef WORD3 #undef WORD4 } static void test_remove_all(void) { strarray_t sa = STRARRAY_INITIALIZER; #define WORD0 "lorem" #define WORD1 "ipsum" #define WORD2 "dolor" #define WORD3 "sit" #define WORD4 "amet" CU_ASSERT_EQUAL(strarray_size(&sa), 0); CU_ASSERT(sa.alloc >= strarray_size(&sa)); /* removing from an empty array */ strarray_remove_all(&sa, WORD0); CU_ASSERT_EQUAL(strarray_size(&sa), 0); CU_ASSERT(sa.alloc >= strarray_size(&sa)); /* removing a single item from a non-empty array */ strarray_append(&sa, WORD0); strarray_append(&sa, WORD1); strarray_append(&sa, WORD2); strarray_append(&sa, WORD3); strarray_append(&sa, WORD0); strarray_append(&sa, WORD4); CU_ASSERT_EQUAL(strarray_size(&sa), 6); CU_ASSERT(sa.alloc >= strarray_size(&sa)); CU_ASSERT_PTR_NOT_NULL(sa.data); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 0), WORD0); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 1), WORD1); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 2), WORD2); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 3), WORD3); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 4), WORD0); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 5), WORD4); strarray_remove_all(&sa, WORD1); CU_ASSERT_EQUAL(strarray_size(&sa), 5); CU_ASSERT(sa.alloc >= strarray_size(&sa)); CU_ASSERT_PTR_NOT_NULL(sa.data); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 0), WORD0); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 1), WORD2); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 2), WORD3); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 3), WORD0); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 4), WORD4); /* removing an item that appears more than once */ strarray_remove_all(&sa, WORD0); CU_ASSERT_EQUAL(strarray_size(&sa), 3); CU_ASSERT(sa.alloc >= strarray_size(&sa)); CU_ASSERT_PTR_NOT_NULL(sa.data); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 0), WORD2); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 1), WORD3); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 2), WORD4); strarray_fini(&sa); #undef WORD0 #undef WORD1 #undef WORD2 #undef WORD3 #undef WORD4 } static void test_pop(void) { strarray_t sa = STRARRAY_INITIALIZER; char *s; #define WORD0 "lorem" #define WORD1 "ipsum" #define WORD2 "dolor" #define WORD3 "sit" #define WORD4 "amet" CU_ASSERT_EQUAL(strarray_size(&sa), 0); CU_ASSERT(sa.alloc >= strarray_size(&sa)); /* pop from an empty array */ s = strarray_pop(&sa); CU_ASSERT_PTR_NULL(s); CU_ASSERT_EQUAL(strarray_size(&sa), 0); CU_ASSERT(sa.alloc >= strarray_size(&sa)); /* popping items from a non-empty array */ strarray_append(&sa, WORD0); strarray_append(&sa, WORD1); strarray_append(&sa, WORD2); strarray_append(&sa, WORD3); strarray_append(&sa, WORD0); strarray_append(&sa, WORD4); CU_ASSERT_EQUAL(strarray_size(&sa), 6); CU_ASSERT(sa.alloc >= strarray_size(&sa)); CU_ASSERT_PTR_NOT_NULL(sa.data); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 0), WORD0); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 1), WORD1); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 2), WORD2); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 3), WORD3); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 4), WORD0); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 5), WORD4); s = strarray_pop(&sa); CU_ASSERT_PTR_NOT_NULL(s); CU_ASSERT_EQUAL(strarray_size(&sa), 5); CU_ASSERT(sa.alloc >= strarray_size(&sa)); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 0), WORD0); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 1), WORD1); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 2), WORD2); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 3), WORD3); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 4), WORD0); CU_ASSERT_STRING_EQUAL(s, WORD4); free(s); s = strarray_pop(&sa); CU_ASSERT_PTR_NOT_NULL(s); CU_ASSERT_EQUAL(strarray_size(&sa), 4); CU_ASSERT(sa.alloc >= strarray_size(&sa)); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 0), WORD0); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 1), WORD1); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 2), WORD2); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 3), WORD3); CU_ASSERT_STRING_EQUAL(s, WORD0); free(s); s = strarray_pop(&sa); CU_ASSERT_PTR_NOT_NULL(s); CU_ASSERT_EQUAL(strarray_size(&sa), 3); CU_ASSERT(sa.alloc >= strarray_size(&sa)); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 0), WORD0); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 1), WORD1); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 2), WORD2); CU_ASSERT_STRING_EQUAL(s, WORD3); free(s); s = strarray_pop(&sa); CU_ASSERT_PTR_NOT_NULL(s); CU_ASSERT_EQUAL(strarray_size(&sa), 2); CU_ASSERT(sa.alloc >= strarray_size(&sa)); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 0), WORD0); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 1), WORD1); CU_ASSERT_STRING_EQUAL(s, WORD2); free(s); s = strarray_pop(&sa); CU_ASSERT_PTR_NOT_NULL(s); CU_ASSERT_EQUAL(strarray_size(&sa), 1); CU_ASSERT(sa.alloc >= strarray_size(&sa)); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 0), WORD0); CU_ASSERT_STRING_EQUAL(s, WORD1); free(s); s = strarray_pop(&sa); CU_ASSERT_PTR_NOT_NULL(s); CU_ASSERT_EQUAL(strarray_size(&sa), 0); CU_ASSERT(sa.alloc >= strarray_size(&sa)); CU_ASSERT_STRING_EQUAL(s, WORD0); free(s); s = strarray_pop(&sa); CU_ASSERT_PTR_NULL(s); CU_ASSERT_EQUAL(strarray_size(&sa), 0); CU_ASSERT(sa.alloc >= strarray_size(&sa)); strarray_fini(&sa); #undef WORD0 #undef WORD1 #undef WORD2 #undef WORD3 #undef WORD4 } static void test_sortuniq(void) { strarray_t sa = STRARRAY_INITIALIZER; #define WORD0 "INBOX" #define WORD1 "INBOX.a folder" #define WORD2 "INBOX.a.sub" #define WORD3 "INBOX.a.aaa" /* initialise */ CU_ASSERT_EQUAL(strarray_size(&sa), 0); strarray_append(&sa, WORD0); strarray_append(&sa, WORD1); strarray_append(&sa, WORD2); strarray_append(&sa, WORD3); /* duplicates */ strarray_append(&sa, WORD0); strarray_append(&sa, WORD2); strarray_append(&sa, WORD1); CU_ASSERT_EQUAL(strarray_size(&sa), 7); /* normal sort */ strarray_sort(&sa, cmpstringp_raw); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 0), WORD0); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 1), WORD0); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 2), WORD1); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 3), WORD1); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 4), WORD3); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 5), WORD2); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 6), WORD2); /* mbox order sort */ strarray_sort(&sa, cmpstringp_mbox); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 0), WORD0); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 1), WORD0); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 2), WORD3); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 3), WORD2); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 4), WORD2); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 5), WORD1); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 6), WORD1); strarray_uniq(&sa); CU_ASSERT_EQUAL(strarray_size(&sa), 4); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 0), WORD0); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 1), WORD3); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 2), WORD2); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 3), WORD1); #undef WORD0 #undef WORD1 #undef WORD2 #undef WORD3 } static void test_add(void) { strarray_t sa = STRARRAY_INITIALIZER; #define WORD0 "lorem" #define WORD0u "LOREM" #define WORD1 "ipsum" CU_ASSERT_EQUAL(strarray_size(&sa), 0); CU_ASSERT(sa.alloc >= strarray_size(&sa)); CU_ASSERT_PTR_NULL(strarray_nth(&sa, 0)); CU_ASSERT_PTR_NULL(strarray_nth(&sa, -1)); /* _add() on an empty array appends */ strarray_add(&sa, WORD0); CU_ASSERT_EQUAL(strarray_size(&sa), 1); CU_ASSERT(sa.alloc >= strarray_size(&sa)); CU_ASSERT_PTR_NOT_NULL(sa.data); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 0), WORD0); /* _add() of an item already present is a no-op */ strarray_add(&sa, WORD0); CU_ASSERT_EQUAL(strarray_size(&sa), 1); CU_ASSERT(sa.alloc >= strarray_size(&sa)); CU_ASSERT_PTR_NOT_NULL(sa.data); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 0), WORD0); /* _add() of an item not already present (but whose case * analogue is present) appends */ strarray_add(&sa, WORD0u); CU_ASSERT_EQUAL(strarray_size(&sa), 2); CU_ASSERT(sa.alloc >= strarray_size(&sa)); CU_ASSERT_PTR_NOT_NULL(sa.data); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 0), WORD0); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 1), WORD0u); /* _add() of an item not already present appends */ strarray_add(&sa, WORD1); CU_ASSERT_EQUAL(strarray_size(&sa), 3); CU_ASSERT(sa.alloc >= strarray_size(&sa)); CU_ASSERT_PTR_NOT_NULL(sa.data); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 0), WORD0); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 1), WORD0u); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 2), WORD1); /* _add() of an item already present is a no-op */ strarray_add(&sa, WORD0); CU_ASSERT_EQUAL(strarray_size(&sa), 3); CU_ASSERT(sa.alloc >= strarray_size(&sa)); CU_ASSERT_PTR_NOT_NULL(sa.data); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 0), WORD0); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 1), WORD0u); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 2), WORD1); strarray_add(&sa, WORD0u); CU_ASSERT_EQUAL(strarray_size(&sa), 3); CU_ASSERT(sa.alloc >= strarray_size(&sa)); CU_ASSERT_PTR_NOT_NULL(sa.data); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 0), WORD0); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 1), WORD0u); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 2), WORD1); strarray_add(&sa, WORD1); CU_ASSERT_EQUAL(strarray_size(&sa), 3); CU_ASSERT(sa.alloc >= strarray_size(&sa)); CU_ASSERT_PTR_NOT_NULL(sa.data); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 0), WORD0); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 1), WORD0u); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 2), WORD1); strarray_fini(&sa); #undef WORD0 #undef WORD0u #undef WORD1 } static void test_add_case(void) { strarray_t sa = STRARRAY_INITIALIZER; #define WORD0 "lorem" #define WORD0u "LOREM" #define WORD1 "ipsum" CU_ASSERT_EQUAL(strarray_size(&sa), 0); CU_ASSERT(sa.alloc >= strarray_size(&sa)); CU_ASSERT_PTR_NULL(strarray_nth(&sa, 0)); CU_ASSERT_PTR_NULL(strarray_nth(&sa, -1)); /* _add_case() on an empty array appends */ strarray_add_case(&sa, WORD0); CU_ASSERT_EQUAL(strarray_size(&sa), 1); CU_ASSERT(sa.alloc >= strarray_size(&sa)); CU_ASSERT_PTR_NOT_NULL(sa.data); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 0), WORD0); /* _add_case() of an item already present is a no-op */ strarray_add_case(&sa, WORD0); CU_ASSERT_EQUAL(strarray_size(&sa), 1); CU_ASSERT(sa.alloc >= strarray_size(&sa)); CU_ASSERT_PTR_NOT_NULL(sa.data); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 0), WORD0); /* _add_case() of an item not already present (but whose case * analogue is present) is a no-op */ strarray_add_case(&sa, WORD0u); CU_ASSERT_EQUAL(strarray_size(&sa), 1); CU_ASSERT(sa.alloc >= strarray_size(&sa)); CU_ASSERT_PTR_NOT_NULL(sa.data); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 0), WORD0); /* _add_case() of an item not already present appends */ strarray_add_case(&sa, WORD1); CU_ASSERT_EQUAL(strarray_size(&sa), 2); CU_ASSERT(sa.alloc >= strarray_size(&sa)); CU_ASSERT_PTR_NOT_NULL(sa.data); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 0), WORD0); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 1), WORD1); /* _add_case() of an item already present is a no-op */ strarray_add_case(&sa, WORD0); CU_ASSERT_EQUAL(strarray_size(&sa), 2); CU_ASSERT(sa.alloc >= strarray_size(&sa)); CU_ASSERT_PTR_NOT_NULL(sa.data); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 0), WORD0); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 1), WORD1); strarray_add_case(&sa, WORD0u); CU_ASSERT_EQUAL(strarray_size(&sa), 2); CU_ASSERT(sa.alloc >= strarray_size(&sa)); CU_ASSERT_PTR_NOT_NULL(sa.data); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 0), WORD0); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 1), WORD1); strarray_add_case(&sa, WORD1); CU_ASSERT_EQUAL(strarray_size(&sa), 2); CU_ASSERT(sa.alloc >= strarray_size(&sa)); CU_ASSERT_PTR_NOT_NULL(sa.data); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 0), WORD0); CU_ASSERT_STRING_EQUAL(strarray_nth(&sa, 1), WORD1); strarray_fini(&sa); #undef WORD0 #undef WORD0u #undef WORD1 } /* vim: set ft=c: */ cyrus-imapd-2.5.10/cunit/unit.c0000644000175000017500000003022013001236020013202 00000000000000/* * Copyright (c) 1994-2010 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include #include #include #include #include #include #include #include #if HAVE_VALGRIND_VALGRIND_H #include #endif #include #include "timeout.h" #include "cunit.h" #include "xmalloc.h" #include "registers.h" int verbose = 0; int num_testspecs = 0; const char **testspecs; enum { RUN, LIST } mode = RUN; int xml_flag = 0; int timeouts_flag = 1; #if HAVE_VALGRIND_VALGRIND_H #define log1(fmt, a1) \ VALGRIND_PRINTF_BACKTRACE(fmt"\n", (a1)) #define log2(fmt, a1, a2) \ VALGRIND_PRINTF_BACKTRACE(fmt"\n", (a1), (a2)) #else #define log1(fmt, a1) \ fprintf(stderr, "\nunit: "fmt"\n", (a1)) #define log2(fmt, a1, a2) \ fprintf(stderr, "\nunit: "fmt"\n", (a1), (a2)) #endif EXPORTED void fatal(const char *s, int code __attribute__((unused))) { log1("fatal(%s)", s); exit(1); } /* * Accumulate the RunSummary between tests. We need to do this * only because all the external CUnit interfaces for running * tests will explicitly zero the summary first. Meh. * * Fortunately we don't need to accumulate the failure records * between test runs, as the Basic interface's all_complete * handler does nothing with them anyway. */ static void accumulate_summary(CU_RunSummary *summp) { const CU_RunSummary *ss = CU_get_run_summary(); summp->nSuitesRun += ss->nSuitesRun; summp->nSuitesFailed += ss->nSuitesFailed; summp->nTestsRun += ss->nTestsRun; summp->nTestsFailed += ss->nTestsFailed; summp->nAsserts += ss->nAsserts; summp->nAssertsFailed += ss->nAssertsFailed; summp->nFailureRecords += ss->nFailureRecords; } /* Each test gets a maximum of 20 seconds. */ #define TEST_TIMEOUT_MS (20*1000) static jmp_buf jbuf; static const char *code; static enum { IDLE, INTEST, INFIXTURE } running = IDLE; static struct cunit_param *current_params; void exit(int status) { switch (running) { case IDLE: break; case INTEST: log2("code under test (%s) exited with status %d", code, status); running = IDLE; CU_FAIL_FATAL("Code under test exited"); break; case INFIXTURE: log2("fixture code (%s) exited with status %d", code, status); running = IDLE; longjmp(jbuf, status); break; } /* had atexit() handlers? stiff! */ _exit(status); } static void handle_timeout(void) { switch (running) { case INTEST: log1("code under test (%s) timed out", code); running = IDLE; CU_FAIL_FATAL("Code under test timed out"); break; case INFIXTURE: log1("fixture code (%s) timed out", code); running = IDLE; longjmp(jbuf, -1); break; default: log1("unexpected timeout running=%d", running); _exit(1); } } void __cunit_wrap_test(const char *name, void (*fn)(void)) { code = name; running = INTEST; if (timeouts_flag && timeout_begin(TEST_TIMEOUT_MS) < 0) exit(1); fn(); if (timeouts_flag && timeout_end() < 0) exit(1); running = IDLE; } int __cunit_wrap_fixture(const char *name, int (*fn)(void)) { int r = setjmp(jbuf); if (r) return r; code = name; running = INFIXTURE; if (timeouts_flag && timeout_begin(TEST_TIMEOUT_MS) < 0) exit(1); r = fn(); if (timeouts_flag && timeout_end() < 0) exit(1); running = IDLE; return r; } static void describe_params(const struct cunit_param *params, char *buf, int maxlen) { const struct cunit_param *p; int n; if (maxlen <= 4) return; if (!params || !params->name) return; for (p = params ; p->name ; p++) { n = snprintf(buf, maxlen, "%s%s=%s", (p == params ? "" : ","), p->name, p->values[p->idx]); if (n >= maxlen) { /* truncated */ strcpy(buf+maxlen-4, "..."); return; } buf += n; maxlen -= n; } } static void params_assign(struct cunit_param *params) { struct cunit_param *p; for (p = params ; p->name ; p++) *(p->variable) = p->values[p->idx]; if (verbose) { char buf[1024]; buf[0] = '\0'; describe_params(params, buf, sizeof(buf)); fprintf(stderr, "[%s] ", buf); fflush(stderr); } } void __cunit_params_begin(struct cunit_param *params) { struct cunit_param *p; if (!params || !params[0].name) return; if (!params[0].values) { /* first call: split the original value of the * variable up into the ->values[] array */ for (p = params ; p->name ; p++) { char *v; static const char sep[] = ","; p->freeme1 = xstrdup(*(p->variable)); for (v = strtok(p->freeme1, sep) ; v ; v = strtok(NULL, sep)) { p->values = (p->nvalues ? xrealloc(p->values, sizeof(char*) * (p->nvalues+1)) : xmalloc(sizeof(char *))); p->values[p->nvalues++] = v; } } } for (p = params ; p->name ; p++) p->idx = 0; params_assign(params); current_params = params; } int __cunit_params_next(struct cunit_param *params) { struct cunit_param *p; if (!params || !params[0].name) return 0; for (p = params ; p->name ; p++) { if (++p->idx < p->nvalues) break; p->idx = 0; } if (!p->name) return 0; /* incremented off the end */ params_assign(params); return 1; } void __cunit_params_end(void) { current_params = NULL; } CU_BOOL CU_assertFormatImplementation( CU_BOOL bValue, unsigned int uiLine, char strFile[], char strFunction[], CU_BOOL bFatal, char strConditionFormat[], ...) { va_list args; char buf[1024]; va_start(args, strConditionFormat); vsnprintf(buf, sizeof(buf), strConditionFormat, args); va_end(args); if (current_params) { strncat(buf, " [", sizeof(buf)-strlen(buf)-1); describe_params(current_params, buf+strlen(buf), sizeof(buf)-strlen(buf)-1); strncat(buf, "]", sizeof(buf)-strlen(buf)-1); buf[sizeof(buf)-1] = '\0'; } if (verbose > 1 && bValue) fprintf(stderr, " %s:%u %s\n", strFile, uiLine, buf); return CU_assertImplementation(bValue, uiLine, buf, strFile, strFunction, bFatal); } static void run_tests(void) { int i; CU_Suite *suite; CU_Test *test; CU_ErrorCode err; int failed = 0; char *testname; char suitename[256]; CU_RunSummary summ; CU_FailureRecord *failures = NULL; CU_AllTestsCompleteMessageHandler all_complete; /* Setup to catch long-running tests. This seems to be * particularly a problem on CentOS 5.5. */ if (timeouts_flag && timeout_init(handle_timeout) < 0) exit(1); if (xml_flag) { if (num_testspecs == 0) { /* not specified: run all tests in order listed */ CU_automated_run_tests(); if (timeouts_flag) timeout_fini(); return; } fprintf(stderr, "unit: test specifications not " "supported in XML mode, sorry\n"); exit(1); } if (verbose) CU_basic_set_mode(CU_BRM_VERBOSE); if (num_testspecs == 0) { /* not specified: run all tests in order listed */ err = CU_basic_run_tests(); running = IDLE; /* Just In Case */ if (timeouts_flag) timeout_fini(); if (err != CUE_SUCCESS || CU_get_run_summary()->nAssertsFailed) exit(1); return; } /* * Run the specified suites and/or tests. * * Newer versions of CUnit have an 'active' flag in the suite * and test structures which could be used to implement this * behaviour. However, this method works with older CUnits * and also allows the user to specify that a test be run * multiple times, which I think is a useful feature. */ /* This is a hack: it runs no tests but has the side effects * of emitting the CUnit blurb and initialising the Basic * interface's global callbacks. */ CU_basic_run_suite(NULL); /* More hackery: disable the all_complete handler temporarily */ all_complete = CU_get_all_test_complete_handler(); CU_set_all_test_complete_handler(NULL); memset(&summ, 0, sizeof(summ)); for (i = 0 ; i < num_testspecs ; i++) { strncpy(suitename, testspecs[i], sizeof(suitename)); if ((testname = strchr(suitename, ':')) != NULL) { *testname++ = '\0'; if (*testname == '\0') testname = NULL; } suite = CU_get_suite_by_name(suitename, CU_get_registry()); if (suite == NULL) { fprintf(stderr, "unit: no such suite \"%s\"\n", suitename); failed++; continue; } if (testname == NULL) { /* Run each test */ for (test = suite->pTest ; test != NULL ; test = test->pNext) { err = CU_run_test(suite, test); running = IDLE; /* Just In Case */ accumulate_summary(&summ); if (err != CUE_SUCCESS) failed++; } } else { /* run the named test in the named suite */ test = CU_get_test_by_name(testname, suite); if (test == NULL) { fprintf(stderr, "unit: no such test \"%s\" in suite \"%s\"\n", testname, suitename); err = CUE_NOTEST; } else { err = CU_run_test(suite, test); running = IDLE; /* Just In Case */ accumulate_summary(&summ); } if (err != CUE_SUCCESS) failed++; } } if (timeouts_flag) timeout_fini(); *(CU_RunSummary *)CU_get_run_summary() = summ; if (all_complete) all_complete(failures); if (failed || summ.nAssertsFailed) exit(1); } static void list_tests(void) { CU_Suite *suite; CU_Test *test; for (suite = CU_get_registry()->pSuite ; suite != NULL ; suite = suite->pNext) { for (test = suite->pTest ; test != NULL ; test = test->pNext) { printf("%s:%s\n", suite->pName, test->pName); } } } static void usage(int ec) __attribute__((noreturn)); static void usage(int ec) { static const char usage_str[] = "Usage: cunit/unit [options] [suite|suite:test ...]\n" "options are:\n" " -l list all tests\n" " -t disable per-test timeouts\n" " -v be more verbose\n" " -h print this message\n" ; fputs(usage_str, stderr); fflush(stderr); exit(ec); } static void parse_args(int argc, char **argv) { int c; while ((c = getopt(argc, argv, "hltvx")) > 0) { switch (c) { case 'h': usage(0); break; case 'l': mode = LIST; break; case 't': timeouts_flag = 0; break; case 'v': verbose++; break; case 'x': xml_flag = 1; break; case '?': usage(1); exit(1); } } num_testspecs = argc - optind; testspecs = (const char **)(argv + optind); } int main(int argc, char **argv) { CU_initialize_registry(); register_cunit_suites(); parse_args(argc, argv); switch (mode) { case RUN: run_tests(); break; case LIST: list_tests(); break; } return 0; } cyrus-imapd-2.5.10/cmulocal/0000755000175000017500000000000013001246663012635 500000000000000cyrus-imapd-2.5.10/cmulocal/sasl2.m40000644000175000017500000004302213001236020014026 00000000000000# sasl2.m4--sasl2 libraries and includes # Rob Siemborski # SASL2_CRYPT_CHK # --------------- AC_DEFUN([SASL_GSSAPI_CHK], [AC_REQUIRE([SASL2_CRYPT_CHK]) AC_REQUIRE([CMU_SOCKETS]) AC_ARG_ENABLE([gssapi], [AC_HELP_STRING([--enable-gssapi=], [enable GSSAPI authentication [yes]])], [gssapi=$enableval], [gssapi=yes]) AC_ARG_WITH([gss_impl], [AC_HELP_STRING([--with-gss_impl={heimdal|mit|cybersafe|seam|auto}], [choose specific GSSAPI implementation [[auto]]])], [gss_impl=$withval], [gss_impl=auto]) if test "$gssapi" != no; then platform= case "${host}" in *-*-linux*) platform=__linux ;; *-*-hpux*) platform=__hpux ;; *-*-irix*) platform=__irix ;; *-*-solaris2*) # When should we use __sunos? platform=__solaris ;; *-*-aix*) ###_AIX platform=__aix ;; *) AC_WARN([The system type is not recognized. If you believe that CyberSafe GSSAPI works on this platform, please update the configure script]) if test "$gss_impl" = "cybersafe"; then AC_MSG_ERROR([CyberSafe was forced, cannot continue as platform is not supported]) fi ;; esac cmu_saved_CPPFLAGS=$CPPFLAGS if test -d ${gssapi}; then CPPFLAGS="$CPPFLAGS -I$gssapi/include" # We want to keep -I in our CPPFLAGS, but only if we succeed cmu_saved_CPPFLAGS=$CPPFLAGS ### I am not sure how useful is this (and whether this is required at all ### especially when we have to provide two -L flags for new CyberSafe LDFLAGS="$LDFLAGS -L$gssapi/lib" if test -n "$platform"; then if test "$gss_impl" = "auto" -o "$gss_impl" = "cybersafe"; then CPPFLAGS="$CPPFLAGS -D$platform" if test -d "${gssapi}/appsec-sdk/include"; then CPPFLAGS="$CPPFLAGS -I${gssapi}/appsec-sdk/include" fi fi fi fi AC_CHECK_HEADER([gssapi.h],, [AC_CHECK_HEADER([gssapi/gssapi.h],, [gssapi=no])]) AC_CHECK_HEADERS(gssapi/gssapi_ext.h) CPPFLAGS=$cmu_saved_CPPFLAGS fi if test "$gssapi" != no; then if test "$ac_cv_header_gssapi_h" = "yes" -o "$ac_cv_header_gssapi_gssapi_h" = "yes"; then AC_DEFINE(HAVE_GSSAPI_H,,[Define if you have the gssapi.h header file]) fi # We need to find out which gssapi implementation we are # using. Supported alternatives are: MIT Kerberos 5, # Heimdal Kerberos 5 (http://www.pdc.kth.se/heimdal), # CyberSafe Kerberos 5 (http://www.cybersafe.com/) # and Sun SEAM (http://wwws.sun.com/software/security/kerberos/) # # The choice is reflected in GSSAPIBASE_LIBS AC_CHECK_LIB(resolv,res_search) if test -d ${gssapi}; then gssapi_dir="${gssapi}/lib" GSSAPIBASE_LIBS="-L$gssapi_dir" GSSAPIBASE_STATIC_LIBS="-L$gssapi_dir" else # FIXME: This is only used for building cyrus, and then only as # a real hack. it needs to be fixed. gssapi_dir="/usr/local/lib" fi # Check a full link against the Heimdal libraries. # If this fails, check a full link against the MIT libraries. # If this fails, check a full link against the CyberSafe libraries. # If this fails, check a full link against the Solaris 8 and up libgss. if test "$gss_impl" = "auto" -o "$gss_impl" = "heimdal"; then gss_failed=0 AC_CHECK_LIB(gssapi,gss_unwrap,gss_impl="heimdal",gss_failed=1, ${GSSAPIBASE_LIBS} -lgssapi -lkrb5 -lasn1 -lroken ${LIB_CRYPT} ${LIB_DES} -lcom_err ${LIB_SOCKET}) if test "$gss_impl" != "auto" -a "$gss_failed" = "1"; then gss_impl="failed" fi fi if test "$gss_impl" = "auto" -o "$gss_impl" = "mit"; then # check for libkrb5support first AC_CHECK_LIB(krb5support,krb5int_getspecific,K5SUP=-lkrb5support K5SUPSTATIC=$gssapi_dir/libkrb5support.a,,${LIB_SOCKET}) gss_failed=0 AC_CHECK_LIB(gssapi_krb5,gss_unwrap,gss_impl="mit",gss_failed=1, ${GSSAPIBASE_LIBS} -lgssapi_krb5 -lkrb5 -lk5crypto -lcom_err ${K5SUP} ${LIB_SOCKET}) if test "$gss_impl" != "auto" -a "$gss_failed" = "1"; then gss_impl="failed" fi fi # For Cybersafe one has to set a platform define in order to make compilation work if test "$gss_impl" = "auto" -o "$gss_impl" = "cybersafe"; then cmu_saved_CPPFLAGS=$CPPFLAGS cmu_saved_GSSAPIBASE_LIBS=$GSSAPIBASE_LIBS # FIXME - Note that the libraries are in .../lib64 for 64bit kernels if test -d "${gssapi}/appsec-rt/lib"; then GSSAPIBASE_LIBS="$GSSAPIBASE_LIBS -L${gssapi}/appsec-rt/lib" fi CPPFLAGS="$CPPFLAGS -D$platform" if test -d "${gssapi}/appsec-sdk/include"; then CPPFLAGS="$CPPFLAGS -I${gssapi}/appsec-sdk/include" fi gss_failed=0 # Check for CyberSafe with two libraries first, than fall back to a single # library (older CyberSafe) unset ac_cv_lib_gss_csf_gss_acq_user AC_CHECK_LIB(gss,csf_gss_acq_user,gss_impl="cybersafe03", [unset ac_cv_lib_gss_csf_gss_acq_user; AC_CHECK_LIB(gss,csf_gss_acq_user,gss_impl="cybersafe", gss_failed=1,$GSSAPIBASE_LIBS -lgss)], [${GSSAPIBASE_LIBS} -lgss -lcstbk5]) if test "$gss_failed" = "1"; then # Restore variables GSSAPIBASE_LIBS=$cmu_saved_GSSAPIBASE_LIBS CPPFLAGS=$cmu_saved_CPPFLAGS if test "$gss_impl" != "auto"; then gss_impl="failed" fi fi fi if test "$gss_impl" = "auto" -o "$gss_impl" = "seam"; then gss_failed=0 AC_CHECK_LIB(gss,gss_unwrap,gss_impl="seam",gss_failed=1,-lgss) if test "$gss_impl" != "auto" -a "$gss_failed" = "1"; then gss_impl="failed" fi fi if test "$gss_impl" = "mit"; then GSSAPIBASE_LIBS="$GSSAPIBASE_LIBS -lgssapi_krb5 -lkrb5 -lk5crypto -lcom_err ${K5SUP}" GSSAPIBASE_STATIC_LIBS="$GSSAPIBASE_LIBS $gssapi_dir/libgssapi_krb5.a $gssapi_dir/libkrb5.a $gssapi_dir/libk5crypto.a $gssapi_dir/libcom_err.a ${K5SUPSTATIC}" elif test "$gss_impl" = "heimdal"; then CPPFLAGS="$CPPFLAGS -DKRB5_HEIMDAL" GSSAPIBASE_LIBS="$GSSAPIBASE_LIBS -lgssapi -lkrb5 -lasn1 -lroken ${LIB_CRYPT} ${LIB_DES} -lcom_err" GSSAPIBASE_STATIC_LIBS="$GSSAPIBASE_STATIC_LIBS $gssapi_dir/libgssapi.a $gssapi_dir/libkrb5.a $gssapi_dir/libasn1.a $gssapi_dir/libroken.a $gssapi_dir/libcom_err.a ${LIB_CRYPT}" elif test "$gss_impl" = "cybersafe03"; then # Version of CyberSafe with two libraries CPPFLAGS="$CPPFLAGS -D$platform -I${gssapi}/appsec-sdk/include" GSSAPIBASE_LIBS="$GSSAPIBASE_LIBS -lgss -lcstbk5" # there is no static libgss for CyberSafe GSSAPIBASE_STATIC_LIBS=none elif test "$gss_impl" = "cybersafe"; then CPPFLAGS="$CPPFLAGS -D$platform -I${gssapi}/appsec-sdk/include" GSSAPIBASE_LIBS="$GSSAPIBASE_LIBS -lgss" # there is no static libgss for CyberSafe GSSAPIBASE_STATIC_LIBS=none elif test "$gss_impl" = "seam"; then GSSAPIBASE_LIBS=-lgss # there is no static libgss on Solaris 8 and up GSSAPIBASE_STATIC_LIBS=none elif test "$gss_impl" = "failed"; then gssapi="no" GSSAPIBASE_LIBS= GSSAPIBASE_STATIC_LIBS= AC_WARN([Disabling GSSAPI - specified library not found]) else gssapi="no" GSSAPIBASE_LIBS= GSSAPIBASE_STATIC_LIBS= AC_WARN([Disabling GSSAPI - no library]) fi fi # # Cybersafe defines both GSS_C_NT_HOSTBASED_SERVICE and GSS_C_NT_USER_NAME # in gssapi\rfckrb5.h # if test "$gssapi" != "no"; then if test "$gss_impl" = "cybersafe" -o "$gss_impl" = "cybersafe03"; then AC_EGREP_CPP(hostbased_service_gss_nt_yes, [#include #ifdef GSS_C_NT_HOSTBASED_SERVICE hostbased_service_gss_nt_yes #endif], [AC_DEFINE(HAVE_GSS_C_NT_HOSTBASED_SERVICE,, [Define if your GSSAPI implementation defines GSS_C_NT_HOSTBASED_SERVICE])], [AC_WARN([Cybersafe define not found])]) elif test "$ac_cv_header_gssapi_h" = "yes"; then AC_EGREP_HEADER(GSS_C_NT_HOSTBASED_SERVICE, gssapi.h, [AC_DEFINE(HAVE_GSS_C_NT_HOSTBASED_SERVICE,, [Define if your GSSAPI implementation defines GSS_C_NT_HOSTBASED_SERVICE])]) elif test "$ac_cv_header_gssapi_gssapi_h"; then AC_EGREP_HEADER(GSS_C_NT_HOSTBASED_SERVICE, gssapi/gssapi.h, [AC_DEFINE(HAVE_GSS_C_NT_HOSTBASED_SERVICE,, [Define if your GSSAPI implementation defines GSS_C_NT_HOSTBASED_SERVICE])]) fi if test "$gss_impl" = "cybersafe" -o "$gss_impl" = "cybersafe03"; then AC_EGREP_CPP(user_name_yes_gss_nt, [#include #ifdef GSS_C_NT_USER_NAME user_name_yes_gss_nt #endif], [AC_DEFINE(HAVE_GSS_C_NT_USER_NAME,, [Define if your GSSAPI implementation defines GSS_C_NT_USER_NAME])], [AC_WARN([Cybersafe define not found])]) elif test "$ac_cv_header_gssapi_h" = "yes"; then AC_EGREP_HEADER(GSS_C_NT_USER_NAME, gssapi.h, [AC_DEFINE(HAVE_GSS_C_NT_USER_NAME,, [Define if your GSSAPI implementation defines GSS_C_NT_USER_NAME])]) AC_EGREP_HEADER(gss_inquire_attrs_for_mech, gssapi.h, rfc5587=yes) AC_EGREP_HEADER(gss_inquire_mech_for_saslname, gssapi.h, rfc5801=yes) elif test "$ac_cv_header_gssapi_gssapi_h"; then AC_EGREP_HEADER(GSS_C_NT_USER_NAME, gssapi/gssapi.h, [AC_DEFINE(HAVE_GSS_C_NT_USER_NAME,, [Define if your GSSAPI implementation defines GSS_C_NT_USER_NAME])]) AC_EGREP_HEADER(gss_inquire_attrs_for_mech, gssapi/gssapi.h, rfc5587=yes) AC_EGREP_HEADER(gss_inquire_mech_for_saslname, gssapi.h, rfc5801=yes) fi fi AC_MSG_CHECKING([GSSAPI]) if test "$gssapi" != no; then AC_MSG_RESULT([with implementation ${gss_impl}]) AC_CHECK_LIB(resolv,res_search,GSSAPIBASE_LIBS="$GSSAPIBASE_LIBS -lresolv") SASL_MECHS="$SASL_MECHS libgssapiv2.la" SASL_STATIC_OBJS="$SASL_STATIC_OBJS gssapi.o" SASL_STATIC_SRCS="$SASL_STATIC_SRCS \$(top_srcdir)/plugins/gssapi.c" if test "$rfc5587" = "yes" -a "$rfc5801" = "yes"; then SASL_MECHS="$SASL_MECHS libgs2.la" SASL_STATIC_OBJS="$SASL_STATIC_OBJS gs2.o" SASL_STATIC_SRCS="$SASL_STATIC_SRCS \$(top_srcdir)/plugins/gs2.c" fi cmu_save_LIBS="$LIBS" LIBS="$LIBS $GSSAPIBASE_LIBS" AC_CHECK_FUNCS(gsskrb5_register_acceptor_identity) AC_CHECK_FUNCS(gss_decapsulate_token) AC_CHECK_FUNCS(gss_encapsulate_token) AC_CHECK_FUNCS(gss_oid_equal) LIBS="$cmu_save_LIBS" cmu_save_LIBS="$LIBS" LIBS="$LIBS $GSSAPIBASE_LIBS" AC_CHECK_FUNCS(gss_get_name_attribute) LIBS="$cmu_save_LIBS" cmu_save_LIBS="$LIBS" LIBS="$LIBS $GSSAPIBASE_LIBS" AC_MSG_CHECKING([for SPNEGO support in GSSAPI libraries]) AC_TRY_RUN([ #ifdef HAVE_GSSAPI_H #include #else #include #endif int main(void) { gss_OID_desc spnego_oid = { 6, (void *) "\x2b\x06\x01\x05\x05\x02" }; gss_OID_set mech_set; OM_uint32 min_stat; int have_spnego = 0; if (gss_indicate_mechs(&min_stat, &mech_set) == GSS_S_COMPLETE) { gss_test_oid_set_member(&min_stat, &spnego_oid, mech_set, &have_spnego); gss_release_oid_set(&min_stat, &mech_set); } return (!have_spnego); // 0 = success, 1 = failure } ], [ AC_DEFINE(HAVE_GSS_SPNEGO,,[Define if your GSSAPI implementation supports SPNEGO]) AC_MSG_RESULT(yes) ], AC_MSG_RESULT(no)) LIBS="$cmu_save_LIBS" else AC_MSG_RESULT([disabled]) fi AC_SUBST(GSSAPIBASE_LIBS) ])# SASL_GSSAPI_CHK # SASL_SET_GSSAPI_LIBS # -------------------- AC_DEFUN([SASL_SET_GSSAPI_LIBS], [SASL_GSSAPI_LIBS_SET="yes" ]) # CMU_SASL2 # --------- # What we want to do here is setup LIB_SASL with what one would # generally want to have (e.g. if static is requested, make it that, # otherwise make it dynamic. # # We also want to create LIB_DYN_SASL and DYNSASLFLAGS. # # Also sets using_static_sasl to "no" "static" or "staticonly" # AC_DEFUN([CMU_SASL2], [AC_REQUIRE([SASL_GSSAPI_CHK]) AC_ARG_WITH(sasl, [AC_HELP_STRING([--with-sasl=DIR],[Compile with libsasl2 in ])], with_sasl="$withval", with_sasl="yes") AC_ARG_WITH(staticsasl, [AC_HELP_STRING([--with-staticsasl=DIR], [Compile with staticly linked libsasl2 in ])], [with_staticsasl="$withval"; if test $with_staticsasl != "no"; then using_static_sasl="static" fi], [with_staticsasl="no"; using_static_sasl="no"]) SASLFLAGS="" LIB_SASL="" cmu_saved_CPPFLAGS=$CPPFLAGS cmu_saved_LDFLAGS=$LDFLAGS cmu_saved_LIBS=$LIBS if test ${with_staticsasl} != "no"; then if test -d ${with_staticsasl}; then if test -d ${with_staticsasl}/lib64 ; then ac_cv_sasl_where_lib=${with_staticsasl}/lib64 else ac_cv_sasl_where_lib=${with_staticsasl}/lib fi ac_cv_sasl_where_lib=${with_staticsasl}/lib ac_cv_sasl_where_inc=${with_staticsasl}/include SASLFLAGS="-I$ac_cv_sasl_where_inc" LIB_SASL="-L$ac_cv_sasl_where_lib" CPPFLAGS="${cmu_saved_CPPFLAGS} -I${ac_cv_sasl_where_inc}" LDFLAGS="${cmu_saved_LDFLAGS} -L${ac_cv_sasl_where_lib}" else with_staticsasl="/usr" fi AC_CHECK_HEADER(sasl/sasl.h, [AC_CHECK_HEADER(sasl/saslutil.h, [for i42 in lib64 lib; do if test -r ${with_staticsasl}/$i42/libsasl2.a; then ac_cv_found_sasl=yes AC_MSG_CHECKING([for static libsasl]) LIB_SASL="$LIB_SASL ${with_staticsasl}/$i42/libsasl2.a" fi done AC_CHECK_FUNC(dlopen,,[AC_CHECK_LIB(dl, dlopen, [LIB_SASL+="$LIB_SASL -ldl"])]) if test ! "$ac_cv_found_sasl" = "yes"; then AC_MSG_CHECKING([for static libsasl]) AC_MSG_ERROR([Could not find ${with_staticsasl}/lib*/libsasl2.a]) fi])]) AC_MSG_RESULT([found]) if test "x$SASL_GSSAPI_LIBS_SET" = "x"; then LIB_SASL="$LIB_SASL $GSSAPIBASE_STATIC_LIBS" else SASL_GSSAPI_LIBS_SET="" cmu_saved_LIBS="$GSSAPIBASE_STATIC_LIBS $cmu_saved_LIBS" fi fi if test -d ${with_sasl}; then ac_cv_sasl_where_lib=${with_sasl}/lib ac_cv_sasl_where_inc=${with_sasl}/include DYNSASLFLAGS="-I$ac_cv_sasl_where_inc" if test "$ac_cv_sasl_where_lib" != ""; then CMU_ADD_LIBPATH_TO($ac_cv_sasl_where_lib, LIB_DYN_SASL) fi LIB_DYN_SASL="$LIB_DYN_SASL -lsasl2" CPPFLAGS="${cmu_saved_CPPFLAGS} -I${ac_cv_sasl_where_inc}" LDFLAGS="${cmu_saved_LDFLAGS} -L${ac_cv_sasl_where_lib}" fi # be sure to check for a SASLv2 specific function AC_CHECK_HEADER(sasl/sasl.h, [AC_CHECK_HEADER(sasl/saslutil.h, [AC_CHECK_LIB(sasl2, prop_get, ac_cv_found_sasl=yes, ac_cv_found_sasl=no)], ac_cv_found_sasl=no)], ac_cv_found_sasl=no) if test "$ac_cv_found_sasl" = "yes"; then if test "$ac_cv_sasl_where_lib" != ""; then CMU_ADD_LIBPATH_TO($ac_cv_sasl_where_lib, DYNLIB_SASL) fi DYNLIB_SASL="$DYNLIB_SASL -lsasl2" if test "$using_static_sasl" != "static"; then LIB_SASL=$DYNLIB_SASL SASLFLAGS=$DYNSASLFLAGS fi else DYNLIB_SASL="" DYNSASLFLAGS="" using_static_sasl="staticonly" fi if test "x$SASL_GSSAPI_LIBS_SET" != "x"; then SASL_GSSAPI_LIBS_SET="" cmu_saved_LIBS="$GSSAPIBASE_LIBS $cmu_saved_LIBS" fi LIBS="$cmu_saved_LIBS" LDFLAGS="$cmu_saved_LDFLAGS" CPPFLAGS="$cmu_saved_CPPFLAGS" AC_SUBST(LIB_DYN_SASL) AC_SUBST(DYNSASLFLAGS) AC_SUBST(LIB_SASL) AC_SUBST(SASLFLAGS) ])# CMU_SASL2 # CMU_SASL2_REQUIRED # ------------------ AC_DEFUN([CMU_SASL2_REQUIRED], [AC_REQUIRE([CMU_SASL2]) if test "$ac_cv_found_sasl" != "yes"; then AC_MSG_ERROR([Cannot continue without libsasl2. Get it from ftp://ftp.andrew.cmu.edu/pub/cyrus-mail/.]) fi]) # CMU_SASL2_REQUIRE_VER # --------------------- AC_DEFUN([CMU_SASL2_REQUIRE_VER], [AC_REQUIRE([CMU_SASL2_REQUIRED]) cmu_saved_CPPFLAGS=$CPPFLAGS CPPFLAGS="$CPPFLAGS $SASLFLAGS" AC_TRY_CPP([ #include #ifndef SASL_VERSION_MAJOR #error SASL_VERSION_MAJOR not defined #endif #ifndef SASL_VERSION_MINOR #error SASL_VERSION_MINOR not defined #endif #ifndef SASL_VERSION_STEP #error SASL_VERSION_STEP not defined #endif #if SASL_VERSION_MAJOR < $1 || SASL_VERSION_MINOR < $2 || SASL_VERSION_STEP < $3 #error SASL version is less than $1.$2.$3 #endif ],, [AC_MSG_ERROR([Incorrect SASL headers found. This package requires SASL $1.$2.$3 or newer.])]) CPPFLAGS=$cmu_saved_CPPFLAGS ])# CMU_SASL2_REQUIRE_VER # CMU_SASL2_CHECKAPOP_REQUIRED # ---------------------------- AC_DEFUN([CMU_SASL2_CHECKAPOP_REQUIRED], [AC_REQUIRE([CMU_SASL2_REQUIRED]) cmu_saved_LDFLAGS=$LDFLAGS LDFLAGS="$LDFLAGS $LIB_SASL" AC_CHECK_LIB(sasl2, sasl_checkapop, [AC_DEFINE(HAVE_APOP,[],[Does SASL support APOP?])], [AC_MSG_ERROR([libsasl2 without working sasl_checkapop. Cannot continue.])]) LDFLAGS=$cmu_saved_LDFLAGS ])# CMU_SASL2_CHECKAPOP_REQUIRED # SASL2_CRYPT_CHK # --------------- AC_DEFUN([SASL2_CRYPT_CHK], [AC_CHECK_FUNC(crypt, cmu_have_crypt=yes, [AC_CHECK_LIB(crypt, crypt, LIB_CRYPT="-lcrypt"; cmu_have_crypt=yes, cmu_have_crypt=no)]) AC_SUBST(LIB_CRYPT) ])# SASL2_CRYPT_CHK cyrus-imapd-2.5.10/cmulocal/cyrus.m40000644000175000017500000000251513001236017014157 00000000000000dnl dnl Additional macros for configure.in packaged up for easier theft. dnl tjs@andrew.cmu.edu 6-may-1998 dnl dnl It would be good if ANDREW_ADD_LIBPATH could detect if something was dnl already there and not redundantly add it if it is. dnl add -L(arg), and possibly (runpath switch)(arg), to LDFLAGS dnl (so the runpath for shared libraries is set). AC_DEFUN([CMU_ADD_LIBPATH], [ # this is CMU ADD LIBPATH if test "$andrew_cv_runpath_switch" = "none" ; then LDFLAGS="-L$1 ${LDFLAGS}" else LDFLAGS="-L$1 $andrew_cv_runpath_switch$1 ${LDFLAGS}" fi ]) dnl add -L(1st arg), and possibly (runpath switch)(1st arg), to (2nd arg) dnl (so the runpath for shared libraries is set). AC_DEFUN([CMU_ADD_LIBPATH_TO], [ # this is CMU ADD LIBPATH TO if test "$andrew_cv_runpath_switch" = "none" ; then $2="-L$1 ${$2}" else $2="-L$1 ${$2} $andrew_cv_runpath_switch$1" fi ]) dnl runpath initialization AC_DEFUN([CMU_GUESS_RUNPATH_SWITCH], [ # CMU GUESS RUNPATH SWITCH AC_CACHE_CHECK(for runpath switch, andrew_cv_runpath_switch, [ # first, try -R SAVE_LDFLAGS="${LDFLAGS}" LDFLAGS="-R /usr/lib" AC_TRY_LINK([],[],[andrew_cv_runpath_switch="-R"], [ LDFLAGS="-Wl,-rpath,/usr/lib" AC_TRY_LINK([],[],[andrew_cv_runpath_switch="-Wl,-rpath,"], [andrew_cv_runpath_switch="none"]) ]) LDFLAGS="${SAVE_LDFLAGS}" ])]) cyrus-imapd-2.5.10/cmulocal/bsd_sockets.m40000644000175000017500000000202013001236017015304 00000000000000dnl bsd_sockets.m4--which socket libraries do we need? dnl Derrick Brashear dnl from Zephyr dnl Hacked on by Rob Earhart to not just toss stuff in LIBS dnl It now puts everything required for sockets into LIB_SOCKET AC_DEFUN([CMU_SOCKETS], [ save_LIBS="$LIBS" LIB_SOCKET="" AC_CHECK_FUNC(connect, :, [AC_CHECK_LIB(nsl, gethostbyname, LIB_SOCKET="-lnsl $LIB_SOCKET") AC_CHECK_LIB(socket, connect, LIB_SOCKET="-lsocket $LIB_SOCKET")] ) LIBS="$LIB_SOCKET $save_LIBS" AC_CHECK_FUNC(res_search, :, [LIBS="-lresolv $LIB_SOCKET $save_LIBS" AC_TRY_LINK([[ #include #include #include #ifdef HAVE_ARPA_NAMESER_COMPAT_H #include #endif #include ]],[[ const char host[12]="openafs.org"; u_char ans[1024]; res_search( host, C_IN, T_MX, (u_char *)&ans, sizeof(ans)); return 0; ]], LIB_SOCKET="-lresolv $LIB_SOCKET") ]) LIBS="$LIB_SOCKET $save_LIBS" AC_CHECK_FUNCS(dn_expand dns_lookup) LIBS="$save_LIBS" AC_SUBST(LIB_SOCKET) ]) cyrus-imapd-2.5.10/cmulocal/sql.m40000644000175000017500000001317313001236020013605 00000000000000dnl These are the Cyrus MySQL macros. dnl They are here so that they can be shared between Cyrus IMAPd dnl and Cyrus SASL with relative ease. dnl When we're done, there will be a MYSQL_LIBADD and a MYSQL_INCADD which dnl should dnl be used when necessary. dnl We should probably be smarter about our RPATH dnl handling. dnl Call these with CYRUS_MYSQL_CHK. dnl We will also set $mysqllib to "yes" if we are successful, "no" otherwise. AC_DEFUN([CYRUS_MYSQL_CHK_LIB], [ MYSQL_SAVE_LDFLAGS=$LDFLAGS if test -d $with_mysql_lib; then CMU_ADD_LIBPATH_TO($with_mysql_lib, LDFLAGS) CMU_ADD_LIBPATH_TO($with_mysql_lib, MYSQL_LIBADD) else MYSQL_LIBADD="" fi saved_LIBS=$LIBS for libname in ${with_mysql} mysqlclient do LIBS="$saved_LIBS -l$libname" AC_TRY_LINK([#include #include ], [mysql_select_db(NULL, NULL);], MYSQL_LIBADD="$MYSQL_LIBADD -l$libname"; mysqllib="yes", mysqllib="no") if test "$mysqllib" = "yes"; then break; fi done LIBS=$saved_LIBS LDFLAGS=$MYSQL_SAVE_LDFLAGS ]) AC_DEFUN([CYRUS_MYSQL_OPTS], [ AC_ARG_WITH(mysql-libdir, [AS_HELP_STRING([--with-mysql-libdir=DIR], [MySQL lib files are in DIR])], with_mysql_lib=$withval, [ test "${with_mysql_lib+set}" = set || with_mysql_lib=none]) AC_ARG_WITH(mysql-incdir, [AS_HELP_STRING([--with-mysql-incdir=DIR], [MySQL include files are in DIR])], with_mysql_inc=$withval, [ test "${with_mysql_inc+set}" = set || with_mysql_inc=none ]) ]) AC_DEFUN([CYRUS_MYSQL_CHK], [ AC_REQUIRE([CYRUS_MYSQL_OPTS]) cmu_save_CPPFLAGS=$CPPFLAGS if test -d $with_mysql_inc; then CPPFLAGS="$CPPFLAGS -I$with_mysql_inc" MYSQL_INCADD="-I$with_mysql_inc" else MYSQL_INCADD="" fi AC_CHECK_HEADER(mysql.h, [CYRUS_MYSQL_CHK_LIB()], mysqllib="no") CPPFLAGS=$cmu_save_CPPFLAGS ]) dnl These are the Cyrus PgSQL macros. dnl They are here so that they can be shared between Cyrus IMAPd dnl and Cyrus SASL with relative ease. dnl When we're done, there will be a PGSQL_LIBADD and a PGSQL_INCADD which dnl should dnl be used when necessary. dnl We should probably be smarter about our RPATH dnl handling. dnl Call these with CYRUS_PGSQL_CHK. dnl We will also set $pgsqllib to "yes" if we are successful, "no" otherwise. AC_DEFUN([CYRUS_PGSQL_CHK_LIB], [ PGSQL_SAVE_LDFLAGS=$LDFLAGS if test -d $with_pgsql_lib; then CMU_ADD_LIBPATH_TO($with_pgsql_lib, LDFLAGS) CMU_ADD_LIBPATH_TO($with_pgsql_lib, PGSQL_LIBADD) else PGSQL_LIBADD="" fi saved_LIBS=$LIBS for libname in ${with_pgsql} pq do LIBS="$saved_LIBS -l$libname" AC_TRY_LINK([#include #include ], [PQconnectdb(NULL);], PGSQL_LIBADD="$PGSQL_LIBADD -l$libname"; pgsqllib="yes", pgsqllib="no") if test "$pgsqllib" = "yes"; then break; fi done LIBS=$saved_LIBS LDFLAGS=$PGSQL_SAVE_LDFLAGS ]) AC_DEFUN([CYRUS_PGSQL_OPTS], [ AC_ARG_WITH(pgsql-libdir, [AS_HELP_STRING([--with-pgsql-libdir=DIR], [Pgsql lib files are in DIR])], with_pgsql_lib=$withval, [ test "${with_pgsql_lib+set}" = set || with_pgsql_lib=none]) AC_ARG_WITH(pgsql-incdir, [AS_HELP_STRING([--with-pgsql-incdir=DIR], [Pgsql include files are in DIR])], with_pgsql_inc=$withval, [ test "${with_pgsql_inc+set}" = set || with_pgsql_inc=none ]) ]) AC_DEFUN([CYRUS_PGSQL_CHK], [ AC_REQUIRE([CYRUS_PGSQL_OPTS]) cmu_save_CPPFLAGS=$CPPFLAGS if test -d $with_pgsql_inc; then CPPFLAGS="$CPPFLAGS -I$with_pgsql_inc" PGSQL_INCADD="-I$with_pgsql_inc" else PGSQL_INCADD="" fi AC_CHECK_HEADER(libpq-fe.h, [CYRUS_PGSQL_CHK_LIB()], pgsqllib="no") CPPFLAGS=$cmu_save_CPPFLAGS ]) dnl These are the Cyrus SQLite macros. dnl They are here so that they can be shared between Cyrus IMAPd dnl and Cyrus SASL with relative ease. dnl When we're done, there will be a SQLITE_LIBADD and a SQLITE_INCADD which dnl should dnl be used when necessary. dnl We should probably be smarter about our RPATH dnl handling. dnl Call these with CYRUS_SQLITE_CHK. dnl We will also set $sqlitelib to "yes" if we are successful, "no" otherwise. AC_DEFUN([CYRUS_SQLITE_CHK_LIB], [ SQLITE_SAVE_LDFLAGS=$LDFLAGS if test -d $with_sqlite_lib; then CMU_ADD_LIBPATH_TO($with_sqlite_lib, LDFLAGS) CMU_ADD_LIBPATH_TO($with_sqlite_lib, SQLITE_LIBADD) else SQLITE_LIBADD="" fi saved_LIBS=$LIBS for libname in ${with_sqlite} sqlite3 do LIBS="$saved_LIBS -l$libname" AC_TRY_LINK([#include #include ], [sqlite3_open(NULL, NULL);], SQLITE_LIBADD="$SQLITE_LIBADD -l$libname"; sqlitelib="yes", sqlitelib="no") if test "$sqlitelib" = "yes"; then break; fi done LIBS=$saved_LIBS LDFLAGS=$SQLITE_SAVE_LDFLAGS ]) AC_DEFUN([CYRUS_SQLITE_OPTS], [ AC_ARG_WITH(sqlite-libdir, [AS_HELP_STRING([--with-sqlite-libdir=DIR], [SQLite lib files are in DIR])], with_sqlite_lib=$withval, [ test "${with_sqlite_lib+set}" = set || with_sqlite_lib=none]) AC_ARG_WITH(sqlite-incdir, [AS_HELP_STRING([--with-sqlite-incdir=DIR], [SQLite include files are in DIR])], with_sqlite_inc=$withval, [ test "${with_sqlite_inc+set}" = set || with_sqlite_inc=none ]) ]) AC_DEFUN([CYRUS_SQLITE_CHK], [ AC_REQUIRE([CYRUS_SQLITE_OPTS]) cmu_save_CPPFLAGS=$CPPFLAGS if test -d $with_sqlite_inc; then CPPFLAGS="$CPPFLAGS -I$with_sqlite_inc" SQLITE_INCADD="-I$with_sqlite_inc" else SQLITE_INCADD="" fi AC_CHECK_HEADER(sqlite3.h, [CYRUS_SQLITE_CHK_LIB()], sqlitelib="no") CPPFLAGS=$cmu_save_CPPFLAGS ]) cyrus-imapd-2.5.10/cmulocal/perlmake.m40000644000175000017500000000406113001236020014602 00000000000000# perlmake.m4 - Perl MakeMaker support # # Copyright (c) 1994-2012 Carnegie Mellon University. All rights reserved. # # Redistribution and use in source and binary forms, with or without # modification, are permitted provided that the following conditions # are met: # # 1. Redistributions of source code must retain the above copyright # notice, this list of conditions and the following disclaimer. # # 2. Redistributions in binary form must reproduce the above copyright # notice, this list of conditions and the following disclaimer in # the documentation and/or other materials provided with the # distribution. # # 3. The name "Carnegie Mellon University" must not be used to # endorse or promote products derived from this software without # prior written permission. For permission or any legal # details, please contact # Carnegie Mellon University # Center for Technology Transfer and Enterprise Creation # 4615 Forbes Avenue # Suite 302 # Pittsburgh, PA 15213 # (412) 268-7393, fax: (412) 268-7395 # innovation@andrew.cmu.edu # # 4. Redistributions of any form whatsoever must retain the following # acknowledgment: # "This product includes software developed by Computing Services # at Carnegie Mellon University (http://www.cmu.edu/computing/)." # # CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO # THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY # AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE # FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES # WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN # AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING # OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. # # CMU_PERL_MAKEMAKER # ------------------ AC_DEFUN([CMU_PERL_MAKEMAKER],[ AC_CONFIG_FILES([$1/Makefile.PL]) AC_CONFIG_COMMANDS($1/Makefile,[ ( cd $1; $PERL Makefile.PL $MAKE_MAKER_ARGS ) ],[ PERL="${PERL}" MAKE_MAKER_ARGS="PREFIX=${prefix}" ]) ])#CMU_PERL_MAKEMAKER cyrus-imapd-2.5.10/cmulocal/ucdsnmp.m40000644000175000017500000000407213001236020014455 00000000000000dnl look for the (ucd|net)snmp libraries AC_DEFUN([CMU_UCDSNMP], [ AC_REQUIRE([CMU_FIND_LIB_SUBDIR]) AC_REQUIRE([CMU_SOCKETS]) AC_ARG_WITH(snmp, [AS_HELP_STRING([--with-snmp=DIR], [use ucd|net snmp (rooted in DIR) [yes]])], with_snmp=$withval, with_snmp=yes) dnl dnl Maintain backwards compatibility with old --with-ucdsnmp option dnl AC_ARG_WITH(ucdsnmp,, with_snmp=$withval,) if test "$with_snmp" != "no"; then dnl dnl Try net-snmp first dnl if test "$with_snmp" = "yes"; then AC_PATH_PROG(SNMP_CONFIG,net-snmp-config,,[/usr/local/bin:$PATH]) else SNMP_CONFIG="$with_snmp/bin/net-snmp-config" fi if test -x "$SNMP_CONFIG"; then AC_MSG_CHECKING(NET SNMP libraries) SNMP_LIBS=`$SNMP_CONFIG --agent-libs` SNMP_PREFIX=`$SNMP_CONFIG --prefix` if test -n "$SNMP_LIBS" && test -n "$SNMP_PREFIX"; then CPPFLAGS="$CPPFLAGS -I${SNMP_PREFIX}/include" LIB_UCDSNMP=$SNMP_LIBS AC_DEFINE(HAVE_NETSNMP,1,[Do we have Net-SNMP support?]) AC_SUBST(LIB_UCDSNMP) AC_MSG_RESULT(yes) AC_CHECK_HEADERS(net-snmp/agent/agent_module_config.h,,) else AC_MSG_RESULT(no) AC_MSG_WARN([Could not find the required paths. Please check your net-snmp installation.]) fi else dnl dnl Try ucd-snmp if net-snmp test failed dnl if test "$with_snmp" != no; then if test -d "$with_snmp"; then CPPFLAGS="$CPPFLAGS -I${with_snmp}/include" LDFLAGS="$LDFLAGS -L${with_snmp}/$CMU_LIB_SUBDIR" fi cmu_save_LIBS="$LIBS" AC_CHECK_LIB(snmp, sprint_objid, [ AC_CHECK_HEADER(ucd-snmp/version.h,, with_snmp=no)], with_snmp=no, ${LIB_SOCKET}) LIBS="$cmu_save_LIBS" fi AC_MSG_CHECKING(UCD SNMP libraries) AC_MSG_RESULT($with_snmp) LIB_UCDSNMP="" if test "$with_snmp" != no; then AC_DEFINE(HAVE_UCDSNMP,1,[Do we have UCD-SNMP support?]) LIB_UCDSNMP="-lucdagent -lucdmibs -lsnmp" AC_CHECK_LIB(rpm, rpmdbOpen, LIB_UCDSNMP="${LIB_UCDSNMP} -lrpm -lpopt",,-lpopt) fi AC_SUBST(LIB_UCDSNMP) fi fi ]) cyrus-imapd-2.5.10/cmulocal/ltsugar.m40000644000175000017500000001044012756047127014511 00000000000000# ltsugar.m4 -- libtool m4 base layer. -*-Autoconf-*- # # Copyright (C) 2004-2005, 2007-2008, 2011-2015 Free Software # Foundation, Inc. # Written by Gary V. Vaughan, 2004 # # This file is free software; the Free Software Foundation gives # unlimited permission to copy and/or distribute it, with or without # modifications, as long as this notice is preserved. # serial 6 ltsugar.m4 # This is to help aclocal find these macros, as it can't see m4_define. AC_DEFUN([LTSUGAR_VERSION], [m4_if([0.1])]) # lt_join(SEP, ARG1, [ARG2...]) # ----------------------------- # Produce ARG1SEPARG2...SEPARGn, omitting [] arguments and their # associated separator. # Needed until we can rely on m4_join from Autoconf 2.62, since all earlier # versions in m4sugar had bugs. m4_define([lt_join], [m4_if([$#], [1], [], [$#], [2], [[$2]], [m4_if([$2], [], [], [[$2]_])$0([$1], m4_shift(m4_shift($@)))])]) m4_define([_lt_join], [m4_if([$#$2], [2], [], [m4_if([$2], [], [], [[$1$2]])$0([$1], m4_shift(m4_shift($@)))])]) # lt_car(LIST) # lt_cdr(LIST) # ------------ # Manipulate m4 lists. # These macros are necessary as long as will still need to support # Autoconf-2.59, which quotes differently. m4_define([lt_car], [[$1]]) m4_define([lt_cdr], [m4_if([$#], 0, [m4_fatal([$0: cannot be called without arguments])], [$#], 1, [], [m4_dquote(m4_shift($@))])]) m4_define([lt_unquote], $1) # lt_append(MACRO-NAME, STRING, [SEPARATOR]) # ------------------------------------------ # Redefine MACRO-NAME to hold its former content plus 'SEPARATOR''STRING'. # Note that neither SEPARATOR nor STRING are expanded; they are appended # to MACRO-NAME as is (leaving the expansion for when MACRO-NAME is invoked). # No SEPARATOR is output if MACRO-NAME was previously undefined (different # than defined and empty). # # This macro is needed until we can rely on Autoconf 2.62, since earlier # versions of m4sugar mistakenly expanded SEPARATOR but not STRING. m4_define([lt_append], [m4_define([$1], m4_ifdef([$1], [m4_defn([$1])[$3]])[$2])]) # lt_combine(SEP, PREFIX-LIST, INFIX, SUFFIX1, [SUFFIX2...]) # ---------------------------------------------------------- # Produce a SEP delimited list of all paired combinations of elements of # PREFIX-LIST with SUFFIX1 through SUFFIXn. Each element of the list # has the form PREFIXmINFIXSUFFIXn. # Needed until we can rely on m4_combine added in Autoconf 2.62. m4_define([lt_combine], [m4_if(m4_eval([$# > 3]), [1], [m4_pushdef([_Lt_sep], [m4_define([_Lt_sep], m4_defn([lt_car]))])]]dnl [[m4_foreach([_Lt_prefix], [$2], [m4_foreach([_Lt_suffix], ]m4_dquote(m4_dquote(m4_shift(m4_shift(m4_shift($@)))))[, [_Lt_sep([$1])[]m4_defn([_Lt_prefix])[$3]m4_defn([_Lt_suffix])])])])]) # lt_if_append_uniq(MACRO-NAME, VARNAME, [SEPARATOR], [UNIQ], [NOT-UNIQ]) # ----------------------------------------------------------------------- # Iff MACRO-NAME does not yet contain VARNAME, then append it (delimited # by SEPARATOR if supplied) and expand UNIQ, else NOT-UNIQ. m4_define([lt_if_append_uniq], [m4_ifdef([$1], [m4_if(m4_index([$3]m4_defn([$1])[$3], [$3$2$3]), [-1], [lt_append([$1], [$2], [$3])$4], [$5])], [lt_append([$1], [$2], [$3])$4])]) # lt_dict_add(DICT, KEY, VALUE) # ----------------------------- m4_define([lt_dict_add], [m4_define([$1($2)], [$3])]) # lt_dict_add_subkey(DICT, KEY, SUBKEY, VALUE) # -------------------------------------------- m4_define([lt_dict_add_subkey], [m4_define([$1($2:$3)], [$4])]) # lt_dict_fetch(DICT, KEY, [SUBKEY]) # ---------------------------------- m4_define([lt_dict_fetch], [m4_ifval([$3], m4_ifdef([$1($2:$3)], [m4_defn([$1($2:$3)])]), m4_ifdef([$1($2)], [m4_defn([$1($2)])]))]) # lt_if_dict_fetch(DICT, KEY, [SUBKEY], VALUE, IF-TRUE, [IF-FALSE]) # ----------------------------------------------------------------- m4_define([lt_if_dict_fetch], [m4_if(lt_dict_fetch([$1], [$2], [$3]), [$4], [$5], [$6])]) # lt_dict_filter(DICT, [SUBKEY], VALUE, [SEPARATOR], KEY, [...]) # -------------------------------------------------------------- m4_define([lt_dict_filter], [m4_if([$5], [], [], [lt_join(m4_quote(m4_default([$4], [[, ]])), lt_unquote(m4_split(m4_normalize(m4_foreach(_Lt_key, lt_car([m4_shiftn(4, $@)]), [lt_if_dict_fetch([$1], _Lt_key, [$2], [$3], [_Lt_key ])])))))])[]dnl ]) cyrus-imapd-2.5.10/cmulocal/ipv6.m40000644000175000017500000000617013001236017013677 00000000000000dnl See whether we can use IPv6 related functions dnl contributed by Hajimu UMEMOTO AC_DEFUN([IPv6_CHECK_FUNC], [ AC_CHECK_FUNC($1, [dnl ac_cv_lib_socket_$1=no ac_cv_lib_inet6_$1=no ], [dnl AC_CHECK_LIB(socket, $1, [dnl LIBS="$LIBS -lsocket" ac_cv_lib_inet6_$1=no ], [dnl AC_MSG_CHECKING([whether your system has IPv6 directory]) AC_CACHE_VAL(ipv6_cv_dir, [dnl for ipv6_cv_dir in /usr/local/v6 /usr/inet6 no; do if test $ipv6_cv_dir = no -o -d $ipv6_cv_dir; then break fi done])dnl AC_MSG_RESULT($ipv6_cv_dir) if test $ipv6_cv_dir = no; then ac_cv_lib_inet6_$1=no else if test x$ipv6_libinet6 = x; then ipv6_libinet6=no SAVELDFLAGS="$LDFLAGS" LDFLAGS="$LDFLAGS -L$ipv6_cv_dir/lib" fi AC_CHECK_LIB(inet6, $1, [dnl if test $ipv6_libinet6 = no; then ipv6_libinet6=yes LIBS="$LIBS -linet6" fi],)dnl if test $ipv6_libinet6 = no; then LDFLAGS="$SAVELDFLAGS" fi fi])dnl ])dnl ipv6_cv_$1=no if test $ac_cv_func_$1 = yes -o $ac_cv_lib_socket_$1 = yes \ -o $ac_cv_lib_inet6_$1 = yes then ipv6_cv_$1=yes fi if test $ipv6_cv_$1 = no; then if test $1 = getaddrinfo; then for ipv6_cv_pfx in o n; do AC_EGREP_HEADER(${ipv6_cv_pfx}$1, netdb.h, [AC_CHECK_FUNC(${ipv6_cv_pfx}$1)]) if eval test X\$ac_cv_func_${ipv6_cv_pfx}$1 = Xyes; then AC_DEFINE(HAVE_GETADDRINFO,[],[Do we have a getaddrinfo?]) ipv6_cv_$1=yes break fi done fi fi if test $ipv6_cv_$1 = yes; then ifelse([$2], , :, [$2]) else ifelse([$3], , :, [$3]) fi]) dnl See whether we have ss_family in sockaddr_storage AC_DEFUN([IPv6_CHECK_SS_FAMILY], [ AC_MSG_CHECKING([whether you have ss_family in struct sockaddr_storage]) AC_CACHE_VAL(ipv6_cv_ss_family, [dnl AC_TRY_COMPILE([#include #include ], [struct sockaddr_storage ss; int i = ss.ss_family;], [ipv6_cv_ss_family=yes], [ipv6_cv_ss_family=no])])dnl if test $ipv6_cv_ss_family = yes; then ifelse([$1], , AC_DEFINE(HAVE_SS_FAMILY,[],[Is there an ss_family in sockaddr_storage?]), [$1]) else ifelse([$2], , :, [$2]) fi AC_MSG_RESULT($ipv6_cv_ss_family)]) dnl whether you have sa_len in struct sockaddr AC_DEFUN([IPv6_CHECK_SA_LEN], [ AC_MSG_CHECKING([whether you have sa_len in struct sockaddr]) AC_CACHE_VAL(ipv6_cv_sa_len, [dnl AC_TRY_COMPILE([#include #include ], [struct sockaddr sa; int i = sa.sa_len;], [ipv6_cv_sa_len=yes], [ipv6_cv_sa_len=no])])dnl if test $ipv6_cv_sa_len = yes; then ifelse([$1], , AC_DEFINE(HAVE_SOCKADDR_SA_LEN,[],[Does sockaddr have an sa_len?]), [$1]) else ifelse([$2], , :, [$2]) fi AC_MSG_RESULT($ipv6_cv_sa_len)]) dnl See whether sys/socket.h has socklen_t AC_DEFUN([IPv6_CHECK_SOCKLEN_T], [ AC_MSG_CHECKING(for socklen_t) AC_CACHE_VAL(ipv6_cv_socklen_t, [dnl AC_TRY_LINK([#include #include ], [socklen_t len = 0;], [ipv6_cv_socklen_t=yes], [ipv6_cv_socklen_t=no])])dnl if test $ipv6_cv_socklen_t = yes; then ifelse([$1], , AC_DEFINE(HAVE_SOCKLEN_T,[],[Do we have a socklen_t?]), [$1]) else ifelse([$2], , :, [$2]) fi AC_MSG_RESULT($ipv6_cv_socklen_t)]) cyrus-imapd-2.5.10/cmulocal/libwrap.m40000644000175000017500000000174213001236020014445 00000000000000dnl libwrap.m4 --- do we have libwrap, the access control library? AC_DEFUN([CMU_LIBWRAP], [ AC_REQUIRE([CMU_FIND_LIB_SUBDIR]) AC_REQUIRE([CMU_SOCKETS]) AC_ARG_WITH(libwrap, [AS_HELP_STRING([--with-libwrap=DIR], [use libwrap (rooted in DIR) [yes] ])], with_libwrap=$withval, with_libwrap=yes) if test "$with_libwrap" != no; then if test -d "$with_libwrap"; then CPPFLAGS="$CPPFLAGS -I${with_libwrap}/include" LDFLAGS="$LDFLAGS -L${with_libwrap}/$CMU_LIB_SUBDIR" fi cmu_save_LIBS="$LIBS" AC_CHECK_LIB(wrap, request_init, [ AC_CHECK_HEADER(tcpd.h,, with_libwrap=no)], with_libwrap=no, ${LIB_SOCKET}) LIBS="$cmu_save_LIBS" fi AC_MSG_CHECKING(libwrap support) AC_MSG_RESULT($with_libwrap) LIB_WRAP="" if test "$with_libwrap" != no; then AC_DEFINE(HAVE_LIBWRAP,[],[Do we have TCP wrappers?]) LIB_WRAP="-lwrap" AC_CHECK_LIB(nsl, yp_get_default_domain, LIB_WRAP="${LIB_WRAP} -lnsl") fi AC_SUBST(LIB_WRAP) ]) cyrus-imapd-2.5.10/cmulocal/berkdb.m40000644000175000017500000001667113001236017014253 00000000000000AC_DEFUN([CMU_DB_INC_WHERE1], [ saved_CPPFLAGS=$CPPFLAGS CPPFLAGS="$saved_CPPFLAGS -I$1" AC_TRY_COMPILE([#include ], [DB *db; db_create(&db, NULL, 0); db->open(db, "foo.db", NULL, DB_UNKNOWN, DB_RDONLY, 0644);], ac_cv_found_db_inc=yes, ac_cv_found_db_inc=no) CPPFLAGS=$saved_CPPFLAGS ]) AC_DEFUN([CMU_DB_INC_WHERE], [ for i in $1; do AC_MSG_CHECKING(for db headers in $i) CMU_DB_INC_WHERE1($i) CMU_TEST_INCPATH($i, db) if test "$ac_cv_found_db_inc" = "yes"; then ac_cv_db_where_inc=$i AC_MSG_RESULT(found) break else AC_MSG_RESULT(not found) fi done ]) # # Test for lib files # AC_DEFUN([CMU_DB3_LIB_WHERE1], [ AC_REQUIRE([CMU_AFS]) AC_REQUIRE([CMU_KRB4]) saved_LIBS=$LIBS LIBS="$saved_LIBS -L$1 -ldb-3" AC_TRY_LINK([#include ], [db_env_create(NULL, 0);], [ac_cv_found_db_3_lib=yes], ac_cv_found_db_3_lib=no) LIBS=$saved_LIBS ]) AC_DEFUN([CMU_DB4_LIB_WHERE1], [ AC_REQUIRE([CMU_AFS]) AC_REQUIRE([CMU_KRB4]) saved_LIBS=$LIBS LIBS="$saved_LIBS -L$1 -ldb-4" AC_TRY_LINK([#include ], [db_env_create(NULL, 0);], [ac_cv_found_db_4_lib=yes], ac_cv_found_db_4_lib=no) LIBS=$saved_LIBS ]) AC_DEFUN([CMU_DB_LIB_WHERE], [ for i in $1; do AC_MSG_CHECKING(for db libraries in $i) if test "$enable_db4" = "yes"; then CMU_DB4_LIB_WHERE1($i) CMU_TEST_LIBPATH($i, [db-4]) ac_cv_found_db_lib=$ac_cv_found_db_4_lib else CMU_DB3_LIB_WHERE1($i) CMU_TEST_LIBPATH($i, [db-3]) ac_cv_found_db_lib=$ac_cv_found_db_3_lib fi if test "$ac_cv_found_db_lib" = "yes" ; then ac_cv_db_where_lib=$i AC_MSG_RESULT(found) break else AC_MSG_RESULT(not found) fi done ]) AC_DEFUN([CMU_USE_DB], [ AC_REQUIRE([CMU_FIND_LIB_SUBDIR]) AC_ARG_WITH(db, [ --with-db=PREFIX Compile with db support], [if test "X$with_db" = "X"; then with_db=yes fi]) AC_ARG_WITH(db-lib, [ --with-db-lib=dir use db libraries in dir], [if test "$withval" = "yes" -o "$withval" = "no"; then AC_MSG_ERROR([No argument for --with-db-lib]) fi]) AC_ARG_WITH(db-include, [ --with-db-include=dir use db headers in dir], [if test "$withval" = "yes" -o "$withval" = "no"; then AC_MSG_ERROR([No argument for --with-db-include]) fi]) AC_ARG_ENABLE(db4, [ --enable-db4 use db 4.x libraries]) if test "X$with_db" != "X"; then if test "$with_db" != "yes"; then ac_cv_db_where_lib=$with_db/$CMU_LIB_SUBDIR ac_cv_db_where_inc=$with_db/include fi fi if test "X$with_db_lib" != "X"; then ac_cv_db_where_lib=$with_db_lib fi if test "X$ac_cv_db_where_lib" = "X"; then CMU_DB_LIB_WHERE(/usr/athena/$CMU_LIB_SUBDIR /usr/$CMU_LIB_SUBDIR /usr/local/$CMU_LIB_SUBDIR) fi if test "X$with_db_include" != "X"; then ac_cv_db_where_inc=$with_db_include fi if test "X$ac_cv_db_where_inc" = "X"; then CMU_DB_INC_WHERE(/usr/athena/include /usr/local/include) fi AC_MSG_CHECKING(whether to include db) if test "X$ac_cv_db_where_lib" = "X" -o "X$ac_cv_db_where_inc" = "X"; then ac_cv_found_db=no AC_MSG_RESULT(no) else ac_cv_found_db=yes AC_MSG_RESULT(yes) DB_INC_DIR=$ac_cv_db_where_inc DB_LIB_DIR=$ac_cv_db_where_lib DB_INC_FLAGS="-I${DB_INC_DIR}" if test "$enable_db4" = "yes"; then DB_LIB_FLAGS="-L${DB_LIB_DIR} -ldb-4" else DB_LIB_FLAGS="-L${DB_LIB_DIR} -ldb-3" fi dnl Do not force configure.in to put these in CFLAGS and LIBS unconditionally dnl Allow makefile substitutions.... AC_SUBST(DB_INC_FLAGS) AC_SUBST(DB_LIB_FLAGS) if test "X$RPATH" = "X"; then RPATH="" fi case "${host}" in *-*-linux*) if test "X$RPATH" = "X"; then RPATH="-Wl,-rpath,${DB_LIB_DIR}" else RPATH="${RPATH}:${DB_LIB_DIR}" fi ;; *-*-hpux*) if test "X$RPATH" = "X"; then RPATH="-Wl,+b${DB_LIB_DIR}" else RPATH="${RPATH}:${DB_LIB_DIR}" fi ;; *-*-irix*) if test "X$RPATH" = "X"; then RPATH="-Wl,-rpath,${DB_LIB_DIR}" else RPATH="${RPATH}:${DB_LIB_DIR}" fi ;; *-*-solaris2*) if test "$ac_cv_prog_gcc" = yes; then if test "X$RPATH" = "X"; then RPATH="-Wl,-R${DB_LIB_DIR}" else RPATH="${RPATH}:${DB_LIB_DIR}" fi else RPATH="${RPATH} -R${DB_LIB_DIR}" fi ;; esac AC_SUBST(RPATH) fi ]) dnl ---- CUT HERE --- dnl These are the Cyrus Berkeley DB macros. In an ideal world these would be dnl identical to the above. dnl They are here so that they can be shared between Cyrus IMAPd dnl and Cyrus SASL with relative ease. dnl The big difference between this and the ones above is that we don't assume dnl that we know the name of the library, and we try a lot of permutations dnl instead. We also assume that DB4 is acceptable. dnl When we're done, there will be a BDB_LIBADD and a BDB_INCADD which should dnl be used when necessary. We should probably be smarter about our RPATH dnl handling. dnl Call these with BERKELEY_DB_CHK. dnl We will also set $dblib to "berkeley" if we are successful, "no" otherwise. dnl this is unbelievably painful due to confusion over what db-3 should be dnl named and where the db-3 header file is located. arg. AC_DEFUN([CYRUS_BERKELEY_DB_CHK_LIB], [ BDB_SAVE_LDFLAGS=$LDFLAGS if test -d $with_bdb_lib; then CMU_ADD_LIBPATH_TO($with_bdb_lib, LDFLAGS) CMU_ADD_LIBPATH_TO($with_bdb_lib, BDB_LIBADD) else BDB_LIBADD="" fi saved_LIBS=$LIBS for dbname in ${with_bdb} \ db-5.3 db5.3 db53 \ db-5.2 db5.2 db52 \ db-5.1 db5.2 db51 \ db-5.0 db5.2 db50 db-5 db5 \ db-4.8 db4.8 db48 \ db-4.7 db4.7 db47 \ db-4.6 db4.6 db46 \ db-4.5 db4.5 db45 \ db-4.4 db4.4 db44 \ db-4.3 db4.3 db43 \ db-4.2 db4.2 db42 \ db-4.1 db4.1 db41 \ db-4.0 db4.0 db40 db-4 db4 \ db-3.3 db3.3 db33 \ db-3.2 db3.2 db32 \ db-3.1 db3.1 db31 \ db-3.0 db3.0 db30 db-3 db3 \ db do LIBS="$saved_LIBS -l$dbname" AC_TRY_LINK([#include #include ], [db_create(NULL, NULL, 0);], BDB_LIBADD="$BDB_LIBADD -l$dbname"; dblib="berkeley"; dbname=db, dblib="no") if test "$dblib" = "berkeley"; then break; fi done if test "$dblib" = "no"; then LIBS="$saved_LIBS -ldb" AC_TRY_LINK([#include #include ], [db_create(NULL, NULL, 0);], BDB_LIBADD="$BDB_LIBADD -ldb"; dblib="berkeley"; dbname=db, dblib="no") fi LIBS=$saved_LIBS LDFLAGS=$BDB_SAVE_LDFLAGS ]) AC_DEFUN([CYRUS_BERKELEY_DB_OPTS], [ AC_ARG_WITH(bdb-libdir, [ --with-bdb-libdir=DIR Berkeley DB lib files are in DIR], with_bdb_lib=$withval, [ test "${with_bdb_lib+set}" = set || with_bdb_lib=none]) AC_ARG_WITH(bdb-incdir, [ --with-bdb-incdir=DIR Berkeley DB include files are in DIR], with_bdb_inc=$withval, [ test "${with_bdb_inc+set}" = set || with_bdb_inc=none ]) ]) AC_DEFUN([CYRUS_BERKELEY_DB_CHK], [ AC_REQUIRE([CYRUS_BERKELEY_DB_OPTS]) cmu_save_CPPFLAGS=$CPPFLAGS if test -d $with_bdb_inc; then CPPFLAGS="$CPPFLAGS -I$with_bdb_inc" BDB_INCADD="-I$with_bdb_inc" else BDB_INCADD="" fi dnl Note that FreeBSD puts it in a wierd place dnl (but they should use with-bdb-incdir) AC_CHECK_HEADER(db.h, [CYRUS_BERKELEY_DB_CHK_LIB()], dblib="no") CPPFLAGS=$cmu_save_CPPFLAGS ]) cyrus-imapd-2.5.10/cmulocal/c-fpic.m40000644000175000017500000000064713001236017014157 00000000000000dnl dnl Test for -fPIC dnl AC_DEFUN([CMU_C_FPIC], [ AC_MSG_CHECKING(if compiler supports -fPIC) AC_CACHE_VAL(ac_cv_fpic, [ save_CFLAGS=$CFLAGS CFLAGS="${CFLAGS} -fPIC" AC_TRY_COMPILE([ #include static void foo(void) { exit(1); } ], [ ], ac_cv_fpic=yes, ac_cv_fpic=no) CFLAGS=$save_CFLAGS ]) if test "$ac_cv_fpic" = "yes"; then FPIC_CFLAGS="-fPIC" else FPIC_CFLAGS="" fi AC_MSG_RESULT($ac_cv_fpic) ]) cyrus-imapd-2.5.10/cmulocal/ltversion.m40000644000175000017500000000127312756047127015061 00000000000000# ltversion.m4 -- version numbers -*- Autoconf -*- # # Copyright (C) 2004, 2011-2015 Free Software Foundation, Inc. # Written by Scott James Remnant, 2004 # # This file is free software; the Free Software Foundation gives # unlimited permission to copy and/or distribute it, with or without # modifications, as long as this notice is preserved. # @configure_input@ # serial 4179 ltversion.m4 # This file is part of GNU Libtool m4_define([LT_PACKAGE_VERSION], [2.4.6]) m4_define([LT_PACKAGE_REVISION], [2.4.6]) AC_DEFUN([LTVERSION_VERSION], [macro_version='2.4.6' macro_revision='2.4.6' _LT_DECL(, macro_version, 0, [Which release of libtool.m4 was used?]) _LT_DECL(, macro_revision, 0) ]) cyrus-imapd-2.5.10/cmulocal/common.m40000644000175000017500000000344112772415051014314 00000000000000AC_DEFUN([CMU_TEST_LIBPATH], [ changequote(<<, >>) define(<>, translit(ac_cv_found_$2_lib, <<- *>>, <<__p>>)) changequote([, ]) if test "$CMU_AC_CV_FOUND" = "yes"; then if test \! -r "$1/lib$2.a" -a \! -r "$1/lib$2.so" -a \! -r "$1/lib$2.sl" -a \! -r "$1/lib$2.dylib"; then CMU_AC_CV_FOUND=no fi fi ]) AC_DEFUN([CMU_TEST_INCPATH], [ changequote(<<, >>) define(<>, translit(ac_cv_found_$2_inc, [ *], [_p])) changequote([, ]) if test "$CMU_AC_CV_FOUND" = "yes"; then if test \! -r "$1/$2.h"; then CMU_AC_CV_FOUND=no fi fi ]) dnl CMU_CHECK_HEADER_NOCACHE(HEADER-FILE, [ACTION-IF-FOUND [, ACTION-IF-NOT-FOUND]]) AC_DEFUN([CMU_CHECK_HEADER_NOCACHE], [dnl Do the transliteration at runtime so arg 1 can be a shell variable. ac_safe=`echo "$1" | sed 'y%./+-%__p_%'` AC_MSG_CHECKING([for $1]) AC_TRY_CPP([#include <$1>], eval "ac_cv_header_$ac_safe=yes", eval "ac_cv_header_$ac_safe=no") if eval "test \"`echo '$ac_cv_header_'$ac_safe`\" = yes"; then AC_MSG_RESULT(yes) ifelse([$2], , :, [$2]) else AC_MSG_RESULT(no) ifelse([$3], , , [$3 ])dnl fi ]) AC_DEFUN([CMU_FIND_LIB_SUBDIR], [dnl AC_ARG_WITH([lib-subdir], AC_HELP_STRING([--with-lib-subdir=DIR],[Find libraries in DIR instead of lib])) AC_CHECK_SIZEOF(long) AC_CACHE_CHECK([what directory libraries are found in], [ac_cv_cmu_lib_subdir], [test "X$with_lib_subdir" = "Xyes" && with_lib_subdir= test "X$with_lib_subdir" = "Xno" && with_lib_subdir= if test "X$with_lib_subdir" = "X" ; then ac_cv_cmu_lib_subdir=lib if test $ac_cv_sizeof_long -eq 4 ; then test -d /usr/lib32 && ac_cv_cmu_lib_subdir=lib32 fi if test $ac_cv_sizeof_long -eq 8 ; then test -d /usr/lib64 && ac_cv_cmu_lib_subdir=lib64 fi else ac_cv_cmu_lib_subdir=$with_lib_subdir fi]) AC_SUBST(CMU_LIB_SUBDIR, $ac_cv_cmu_lib_subdir) ]) cyrus-imapd-2.5.10/cmulocal/lt~obsolete.m40000644000175000017500000001377412756047127015417 00000000000000# lt~obsolete.m4 -- aclocal satisfying obsolete definitions. -*-Autoconf-*- # # Copyright (C) 2004-2005, 2007, 2009, 2011-2015 Free Software # Foundation, Inc. # Written by Scott James Remnant, 2004. # # This file is free software; the Free Software Foundation gives # unlimited permission to copy and/or distribute it, with or without # modifications, as long as this notice is preserved. # serial 5 lt~obsolete.m4 # These exist entirely to fool aclocal when bootstrapping libtool. # # In the past libtool.m4 has provided macros via AC_DEFUN (or AU_DEFUN), # which have later been changed to m4_define as they aren't part of the # exported API, or moved to Autoconf or Automake where they belong. # # The trouble is, aclocal is a bit thick. It'll see the old AC_DEFUN # in /usr/share/aclocal/libtool.m4 and remember it, then when it sees us # using a macro with the same name in our local m4/libtool.m4 it'll # pull the old libtool.m4 in (it doesn't see our shiny new m4_define # and doesn't know about Autoconf macros at all.) # # So we provide this file, which has a silly filename so it's always # included after everything else. This provides aclocal with the # AC_DEFUNs it wants, but when m4 processes it, it doesn't do anything # because those macros already exist, or will be overwritten later. # We use AC_DEFUN over AU_DEFUN for compatibility with aclocal-1.6. # # Anytime we withdraw an AC_DEFUN or AU_DEFUN, remember to add it here. # Yes, that means every name once taken will need to remain here until # we give up compatibility with versions before 1.7, at which point # we need to keep only those names which we still refer to. # This is to help aclocal find these macros, as it can't see m4_define. AC_DEFUN([LTOBSOLETE_VERSION], [m4_if([1])]) m4_ifndef([AC_LIBTOOL_LINKER_OPTION], [AC_DEFUN([AC_LIBTOOL_LINKER_OPTION])]) m4_ifndef([AC_PROG_EGREP], [AC_DEFUN([AC_PROG_EGREP])]) m4_ifndef([_LT_AC_PROG_ECHO_BACKSLASH], [AC_DEFUN([_LT_AC_PROG_ECHO_BACKSLASH])]) m4_ifndef([_LT_AC_SHELL_INIT], [AC_DEFUN([_LT_AC_SHELL_INIT])]) m4_ifndef([_LT_AC_SYS_LIBPATH_AIX], [AC_DEFUN([_LT_AC_SYS_LIBPATH_AIX])]) m4_ifndef([_LT_PROG_LTMAIN], [AC_DEFUN([_LT_PROG_LTMAIN])]) m4_ifndef([_LT_AC_TAGVAR], [AC_DEFUN([_LT_AC_TAGVAR])]) m4_ifndef([AC_LTDL_ENABLE_INSTALL], [AC_DEFUN([AC_LTDL_ENABLE_INSTALL])]) m4_ifndef([AC_LTDL_PREOPEN], [AC_DEFUN([AC_LTDL_PREOPEN])]) m4_ifndef([_LT_AC_SYS_COMPILER], [AC_DEFUN([_LT_AC_SYS_COMPILER])]) m4_ifndef([_LT_AC_LOCK], [AC_DEFUN([_LT_AC_LOCK])]) m4_ifndef([AC_LIBTOOL_SYS_OLD_ARCHIVE], [AC_DEFUN([AC_LIBTOOL_SYS_OLD_ARCHIVE])]) m4_ifndef([_LT_AC_TRY_DLOPEN_SELF], [AC_DEFUN([_LT_AC_TRY_DLOPEN_SELF])]) m4_ifndef([AC_LIBTOOL_PROG_CC_C_O], [AC_DEFUN([AC_LIBTOOL_PROG_CC_C_O])]) m4_ifndef([AC_LIBTOOL_SYS_HARD_LINK_LOCKS], [AC_DEFUN([AC_LIBTOOL_SYS_HARD_LINK_LOCKS])]) m4_ifndef([AC_LIBTOOL_OBJDIR], [AC_DEFUN([AC_LIBTOOL_OBJDIR])]) m4_ifndef([AC_LTDL_OBJDIR], [AC_DEFUN([AC_LTDL_OBJDIR])]) m4_ifndef([AC_LIBTOOL_PROG_LD_HARDCODE_LIBPATH], [AC_DEFUN([AC_LIBTOOL_PROG_LD_HARDCODE_LIBPATH])]) m4_ifndef([AC_LIBTOOL_SYS_LIB_STRIP], [AC_DEFUN([AC_LIBTOOL_SYS_LIB_STRIP])]) m4_ifndef([AC_PATH_MAGIC], [AC_DEFUN([AC_PATH_MAGIC])]) m4_ifndef([AC_PROG_LD_GNU], [AC_DEFUN([AC_PROG_LD_GNU])]) m4_ifndef([AC_PROG_LD_RELOAD_FLAG], [AC_DEFUN([AC_PROG_LD_RELOAD_FLAG])]) m4_ifndef([AC_DEPLIBS_CHECK_METHOD], [AC_DEFUN([AC_DEPLIBS_CHECK_METHOD])]) m4_ifndef([AC_LIBTOOL_PROG_COMPILER_NO_RTTI], [AC_DEFUN([AC_LIBTOOL_PROG_COMPILER_NO_RTTI])]) m4_ifndef([AC_LIBTOOL_SYS_GLOBAL_SYMBOL_PIPE], [AC_DEFUN([AC_LIBTOOL_SYS_GLOBAL_SYMBOL_PIPE])]) m4_ifndef([AC_LIBTOOL_PROG_COMPILER_PIC], [AC_DEFUN([AC_LIBTOOL_PROG_COMPILER_PIC])]) m4_ifndef([AC_LIBTOOL_PROG_LD_SHLIBS], [AC_DEFUN([AC_LIBTOOL_PROG_LD_SHLIBS])]) m4_ifndef([AC_LIBTOOL_POSTDEP_PREDEP], [AC_DEFUN([AC_LIBTOOL_POSTDEP_PREDEP])]) m4_ifndef([LT_AC_PROG_EGREP], [AC_DEFUN([LT_AC_PROG_EGREP])]) m4_ifndef([LT_AC_PROG_SED], [AC_DEFUN([LT_AC_PROG_SED])]) m4_ifndef([_LT_CC_BASENAME], [AC_DEFUN([_LT_CC_BASENAME])]) m4_ifndef([_LT_COMPILER_BOILERPLATE], [AC_DEFUN([_LT_COMPILER_BOILERPLATE])]) m4_ifndef([_LT_LINKER_BOILERPLATE], [AC_DEFUN([_LT_LINKER_BOILERPLATE])]) m4_ifndef([_AC_PROG_LIBTOOL], [AC_DEFUN([_AC_PROG_LIBTOOL])]) m4_ifndef([AC_LIBTOOL_SETUP], [AC_DEFUN([AC_LIBTOOL_SETUP])]) m4_ifndef([_LT_AC_CHECK_DLFCN], [AC_DEFUN([_LT_AC_CHECK_DLFCN])]) m4_ifndef([AC_LIBTOOL_SYS_DYNAMIC_LINKER], [AC_DEFUN([AC_LIBTOOL_SYS_DYNAMIC_LINKER])]) m4_ifndef([_LT_AC_TAGCONFIG], [AC_DEFUN([_LT_AC_TAGCONFIG])]) m4_ifndef([AC_DISABLE_FAST_INSTALL], [AC_DEFUN([AC_DISABLE_FAST_INSTALL])]) m4_ifndef([_LT_AC_LANG_CXX], [AC_DEFUN([_LT_AC_LANG_CXX])]) m4_ifndef([_LT_AC_LANG_F77], [AC_DEFUN([_LT_AC_LANG_F77])]) m4_ifndef([_LT_AC_LANG_GCJ], [AC_DEFUN([_LT_AC_LANG_GCJ])]) m4_ifndef([AC_LIBTOOL_LANG_C_CONFIG], [AC_DEFUN([AC_LIBTOOL_LANG_C_CONFIG])]) m4_ifndef([_LT_AC_LANG_C_CONFIG], [AC_DEFUN([_LT_AC_LANG_C_CONFIG])]) m4_ifndef([AC_LIBTOOL_LANG_CXX_CONFIG], [AC_DEFUN([AC_LIBTOOL_LANG_CXX_CONFIG])]) m4_ifndef([_LT_AC_LANG_CXX_CONFIG], [AC_DEFUN([_LT_AC_LANG_CXX_CONFIG])]) m4_ifndef([AC_LIBTOOL_LANG_F77_CONFIG], [AC_DEFUN([AC_LIBTOOL_LANG_F77_CONFIG])]) m4_ifndef([_LT_AC_LANG_F77_CONFIG], [AC_DEFUN([_LT_AC_LANG_F77_CONFIG])]) m4_ifndef([AC_LIBTOOL_LANG_GCJ_CONFIG], [AC_DEFUN([AC_LIBTOOL_LANG_GCJ_CONFIG])]) m4_ifndef([_LT_AC_LANG_GCJ_CONFIG], [AC_DEFUN([_LT_AC_LANG_GCJ_CONFIG])]) m4_ifndef([AC_LIBTOOL_LANG_RC_CONFIG], [AC_DEFUN([AC_LIBTOOL_LANG_RC_CONFIG])]) m4_ifndef([_LT_AC_LANG_RC_CONFIG], [AC_DEFUN([_LT_AC_LANG_RC_CONFIG])]) m4_ifndef([AC_LIBTOOL_CONFIG], [AC_DEFUN([AC_LIBTOOL_CONFIG])]) m4_ifndef([_LT_AC_FILE_LTDLL_C], [AC_DEFUN([_LT_AC_FILE_LTDLL_C])]) m4_ifndef([_LT_REQUIRED_DARWIN_CHECKS], [AC_DEFUN([_LT_REQUIRED_DARWIN_CHECKS])]) m4_ifndef([_LT_AC_PROG_CXXCPP], [AC_DEFUN([_LT_AC_PROG_CXXCPP])]) m4_ifndef([_LT_PREPARE_SED_QUOTE_VARS], [AC_DEFUN([_LT_PREPARE_SED_QUOTE_VARS])]) m4_ifndef([_LT_PROG_ECHO_BACKSLASH], [AC_DEFUN([_LT_PROG_ECHO_BACKSLASH])]) m4_ifndef([_LT_PROG_F77], [AC_DEFUN([_LT_PROG_F77])]) m4_ifndef([_LT_PROG_FC], [AC_DEFUN([_LT_PROG_FC])]) m4_ifndef([_LT_PROG_CXX], [AC_DEFUN([_LT_PROG_CXX])]) cyrus-imapd-2.5.10/cmulocal/visibility.m40000644000175000017500000000642712772415051015222 00000000000000# visibility.m4 serial 5 (gettext-0.18.2) dnl Copyright (C) 2005, 2008, 2010-2012 Free Software Foundation, Inc. dnl This file is free software; the Free Software Foundation dnl gives unlimited permission to copy and/or distribute it, dnl with or without modifications, as long as this notice is preserved. dnl From Bruno Haible. dnl Tests whether the compiler supports the command-line option dnl -fvisibility=hidden and the function and variable attributes dnl __attribute__((__visibility__("hidden"))) and dnl __attribute__((__visibility__("default"))). dnl Does *not* test for __visibility__("protected") - which has tricky dnl semantics (see the 'vismain' test in glibc) and does not exist e.g. on dnl Mac OS X. dnl Does *not* test for __visibility__("internal") - which has processor dnl dependent semantics. dnl Does *not* test for #pragma GCC visibility push(hidden) - which is dnl "really only recommended for legacy code". dnl Set the variable CFLAG_VISIBILITY. dnl Defines and sets the variable HAVE_VISIBILITY. AC_DEFUN([gl_VISIBILITY], [ AC_REQUIRE([AC_PROG_CC]) CFLAG_VISIBILITY= HAVE_VISIBILITY=0 if test -n "$GCC"; then dnl First, check whether -Werror can be added to the command line, or dnl whether it leads to an error because of some other option that the dnl user has put into $CC $CFLAGS $CPPFLAGS. AC_MSG_CHECKING([whether the -Werror option is usable]) AC_CACHE_VAL([gl_cv_cc_vis_werror], [ gl_save_CFLAGS="$CFLAGS" CFLAGS="$CFLAGS -Werror" AC_COMPILE_IFELSE( [AC_LANG_PROGRAM([[]], [[]])], [gl_cv_cc_vis_werror=yes], [gl_cv_cc_vis_werror=no]) CFLAGS="$gl_save_CFLAGS"]) AC_MSG_RESULT([$gl_cv_cc_vis_werror]) dnl Now check whether visibility declarations are supported. AC_MSG_CHECKING([for simple visibility declarations]) AC_CACHE_VAL([gl_cv_cc_visibility], [ gl_save_CFLAGS="$CFLAGS" CFLAGS="$CFLAGS -fvisibility=hidden" dnl We use the option -Werror and a function dummyfunc, because on some dnl platforms (Cygwin 1.7) the use of -fvisibility triggers a warning dnl "visibility attribute not supported in this configuration; ignored" dnl at the first function definition in every compilation unit, and we dnl don't want to use the option in this case. if test $gl_cv_cc_vis_werror = yes; then CFLAGS="$CFLAGS -Werror" fi AC_COMPILE_IFELSE( [AC_LANG_PROGRAM( [[extern __attribute__((__visibility__("hidden"))) int hiddenvar; extern __attribute__((__visibility__("default"))) int exportedvar; extern __attribute__((__visibility__("hidden"))) int hiddenfunc (void); extern __attribute__((__visibility__("default"))) int exportedfunc (void); void dummyfunc (void) {} ]], [[]])], [gl_cv_cc_visibility=yes], [gl_cv_cc_visibility=no]) CFLAGS="$gl_save_CFLAGS"]) AC_MSG_RESULT([$gl_cv_cc_visibility]) if test $gl_cv_cc_visibility = yes; then CFLAG_VISIBILITY="-fvisibility=hidden" HAVE_VISIBILITY=1 fi fi AC_SUBST([CFLAG_VISIBILITY]) AC_SUBST([HAVE_VISIBILITY]) AC_DEFINE_UNQUOTED([HAVE_VISIBILITY], [$HAVE_VISIBILITY], [Define to 1 or 0, depending whether the compiler supports simple visibility declarations.]) ]) cyrus-imapd-2.5.10/cmulocal/zlib.m40000644000175000017500000000140013001236020013734 00000000000000dnl dnl macros for configure.in to detect zlib dnl AC_DEFUN([CMU_HAVE_ZLIB], [ AC_REQUIRE([CMU_FIND_LIB_SUBDIR]) AC_ARG_WITH(zlib, [AS_HELP_STRING([--with-zlib=DIR],[use zlib from DIR])], with_zlib=$withval, with_zlib="yes") save_CPPFLAGS=$CPPFLAGS save_LDFLAGS=$LDFLAGS if test -d $with_zlib; then CPPFLAGS="${CPPFLAGS} -I${with_lib}/include" CMU_ADD_LIBPATH(${with_zlib}/$CMU_LIB_SUBDIR) fi ZLIB="" case "$with_zlib" in no) with_zlib="no";; *) AC_CHECK_HEADER(zlib.h, [ AC_CHECK_LIB(z, deflate, LIBS="${LIBS} -lz"; with_zlib="yes", with_zlib="no",)], with_zlib=no) ;; esac if test "$with_zlib" != "no"; then AC_DEFINE(HAVE_ZLIB,[],[Do we have zlib?]) ZLIB="-lz" else CPPFLAGS=$save_CPPFLAGS LDFLAGS=$save_LDFLAGS fi ]) cyrus-imapd-2.5.10/cmulocal/libtool.m40000644000175000017500000112617112756047127014506 00000000000000# libtool.m4 - Configure libtool for the host system. -*-Autoconf-*- # # Copyright (C) 1996-2001, 2003-2015 Free Software Foundation, Inc. # Written by Gordon Matzigkeit, 1996 # # This file is free software; the Free Software Foundation gives # unlimited permission to copy and/or distribute it, with or without # modifications, as long as this notice is preserved. m4_define([_LT_COPYING], [dnl # Copyright (C) 2014 Free Software Foundation, Inc. # This is free software; see the source for copying conditions. There is NO # warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. # GNU Libtool is free software; you can redistribute it and/or modify # it under the terms of the GNU General Public License as published by # the Free Software Foundation; either version 2 of of the License, or # (at your option) any later version. # # As a special exception to the GNU General Public License, if you # distribute this file as part of a program or library that is built # using GNU Libtool, you may include this file under the same # distribution terms that you use for the rest of that program. # # GNU Libtool is distributed in the hope that it will be useful, but # WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the # GNU General Public License for more details. # # You should have received a copy of the GNU General Public License # along with this program. If not, see . ]) # serial 58 LT_INIT # LT_PREREQ(VERSION) # ------------------ # Complain and exit if this libtool version is less that VERSION. m4_defun([LT_PREREQ], [m4_if(m4_version_compare(m4_defn([LT_PACKAGE_VERSION]), [$1]), -1, [m4_default([$3], [m4_fatal([Libtool version $1 or higher is required], 63)])], [$2])]) # _LT_CHECK_BUILDDIR # ------------------ # Complain if the absolute build directory name contains unusual characters m4_defun([_LT_CHECK_BUILDDIR], [case `pwd` in *\ * | *\ *) AC_MSG_WARN([Libtool does not cope well with whitespace in `pwd`]) ;; esac ]) # LT_INIT([OPTIONS]) # ------------------ AC_DEFUN([LT_INIT], [AC_PREREQ([2.62])dnl We use AC_PATH_PROGS_FEATURE_CHECK AC_REQUIRE([AC_CONFIG_AUX_DIR_DEFAULT])dnl AC_BEFORE([$0], [LT_LANG])dnl AC_BEFORE([$0], [LT_OUTPUT])dnl AC_BEFORE([$0], [LTDL_INIT])dnl m4_require([_LT_CHECK_BUILDDIR])dnl dnl Autoconf doesn't catch unexpanded LT_ macros by default: m4_pattern_forbid([^_?LT_[A-Z_]+$])dnl m4_pattern_allow([^(_LT_EOF|LT_DLGLOBAL|LT_DLLAZY_OR_NOW|LT_MULTI_MODULE)$])dnl dnl aclocal doesn't pull ltoptions.m4, ltsugar.m4, or ltversion.m4 dnl unless we require an AC_DEFUNed macro: AC_REQUIRE([LTOPTIONS_VERSION])dnl AC_REQUIRE([LTSUGAR_VERSION])dnl AC_REQUIRE([LTVERSION_VERSION])dnl AC_REQUIRE([LTOBSOLETE_VERSION])dnl m4_require([_LT_PROG_LTMAIN])dnl _LT_SHELL_INIT([SHELL=${CONFIG_SHELL-/bin/sh}]) dnl Parse OPTIONS _LT_SET_OPTIONS([$0], [$1]) # This can be used to rebuild libtool when needed LIBTOOL_DEPS=$ltmain # Always use our own libtool. LIBTOOL='$(SHELL) $(top_builddir)/libtool' AC_SUBST(LIBTOOL)dnl _LT_SETUP # Only expand once: m4_define([LT_INIT]) ])# LT_INIT # Old names: AU_ALIAS([AC_PROG_LIBTOOL], [LT_INIT]) AU_ALIAS([AM_PROG_LIBTOOL], [LT_INIT]) dnl aclocal-1.4 backwards compatibility: dnl AC_DEFUN([AC_PROG_LIBTOOL], []) dnl AC_DEFUN([AM_PROG_LIBTOOL], []) # _LT_PREPARE_CC_BASENAME # ----------------------- m4_defun([_LT_PREPARE_CC_BASENAME], [ # Calculate cc_basename. Skip known compiler wrappers and cross-prefix. func_cc_basename () { for cc_temp in @S|@*""; do case $cc_temp in compile | *[[\\/]]compile | ccache | *[[\\/]]ccache ) ;; distcc | *[[\\/]]distcc | purify | *[[\\/]]purify ) ;; \-*) ;; *) break;; esac done func_cc_basename_result=`$ECHO "$cc_temp" | $SED "s%.*/%%; s%^$host_alias-%%"` } ])# _LT_PREPARE_CC_BASENAME # _LT_CC_BASENAME(CC) # ------------------- # It would be clearer to call AC_REQUIREs from _LT_PREPARE_CC_BASENAME, # but that macro is also expanded into generated libtool script, which # arranges for $SED and $ECHO to be set by different means. m4_defun([_LT_CC_BASENAME], [m4_require([_LT_PREPARE_CC_BASENAME])dnl AC_REQUIRE([_LT_DECL_SED])dnl AC_REQUIRE([_LT_PROG_ECHO_BACKSLASH])dnl func_cc_basename $1 cc_basename=$func_cc_basename_result ]) # _LT_FILEUTILS_DEFAULTS # ---------------------- # It is okay to use these file commands and assume they have been set # sensibly after 'm4_require([_LT_FILEUTILS_DEFAULTS])'. m4_defun([_LT_FILEUTILS_DEFAULTS], [: ${CP="cp -f"} : ${MV="mv -f"} : ${RM="rm -f"} ])# _LT_FILEUTILS_DEFAULTS # _LT_SETUP # --------- m4_defun([_LT_SETUP], [AC_REQUIRE([AC_CANONICAL_HOST])dnl AC_REQUIRE([AC_CANONICAL_BUILD])dnl AC_REQUIRE([_LT_PREPARE_SED_QUOTE_VARS])dnl AC_REQUIRE([_LT_PROG_ECHO_BACKSLASH])dnl _LT_DECL([], [PATH_SEPARATOR], [1], [The PATH separator for the build system])dnl dnl _LT_DECL([], [host_alias], [0], [The host system])dnl _LT_DECL([], [host], [0])dnl _LT_DECL([], [host_os], [0])dnl dnl _LT_DECL([], [build_alias], [0], [The build system])dnl _LT_DECL([], [build], [0])dnl _LT_DECL([], [build_os], [0])dnl dnl AC_REQUIRE([AC_PROG_CC])dnl AC_REQUIRE([LT_PATH_LD])dnl AC_REQUIRE([LT_PATH_NM])dnl dnl AC_REQUIRE([AC_PROG_LN_S])dnl test -z "$LN_S" && LN_S="ln -s" _LT_DECL([], [LN_S], [1], [Whether we need soft or hard links])dnl dnl AC_REQUIRE([LT_CMD_MAX_LEN])dnl _LT_DECL([objext], [ac_objext], [0], [Object file suffix (normally "o")])dnl _LT_DECL([], [exeext], [0], [Executable file suffix (normally "")])dnl dnl m4_require([_LT_FILEUTILS_DEFAULTS])dnl m4_require([_LT_CHECK_SHELL_FEATURES])dnl m4_require([_LT_PATH_CONVERSION_FUNCTIONS])dnl m4_require([_LT_CMD_RELOAD])dnl m4_require([_LT_CHECK_MAGIC_METHOD])dnl m4_require([_LT_CHECK_SHAREDLIB_FROM_LINKLIB])dnl m4_require([_LT_CMD_OLD_ARCHIVE])dnl m4_require([_LT_CMD_GLOBAL_SYMBOLS])dnl m4_require([_LT_WITH_SYSROOT])dnl m4_require([_LT_CMD_TRUNCATE])dnl _LT_CONFIG_LIBTOOL_INIT([ # See if we are running on zsh, and set the options that allow our # commands through without removal of \ escapes INIT. if test -n "\${ZSH_VERSION+set}"; then setopt NO_GLOB_SUBST fi ]) if test -n "${ZSH_VERSION+set}"; then setopt NO_GLOB_SUBST fi _LT_CHECK_OBJDIR m4_require([_LT_TAG_COMPILER])dnl case $host_os in aix3*) # AIX sometimes has problems with the GCC collect2 program. For some # reason, if we set the COLLECT_NAMES environment variable, the problems # vanish in a puff of smoke. if test set != "${COLLECT_NAMES+set}"; then COLLECT_NAMES= export COLLECT_NAMES fi ;; esac # Global variables: ofile=libtool can_build_shared=yes # All known linkers require a '.a' archive for static linking (except MSVC, # which needs '.lib'). libext=a with_gnu_ld=$lt_cv_prog_gnu_ld old_CC=$CC old_CFLAGS=$CFLAGS # Set sane defaults for various variables test -z "$CC" && CC=cc test -z "$LTCC" && LTCC=$CC test -z "$LTCFLAGS" && LTCFLAGS=$CFLAGS test -z "$LD" && LD=ld test -z "$ac_objext" && ac_objext=o _LT_CC_BASENAME([$compiler]) # Only perform the check for file, if the check method requires it test -z "$MAGIC_CMD" && MAGIC_CMD=file case $deplibs_check_method in file_magic*) if test "$file_magic_cmd" = '$MAGIC_CMD'; then _LT_PATH_MAGIC fi ;; esac # Use C for the default configuration in the libtool script LT_SUPPORTED_TAG([CC]) _LT_LANG_C_CONFIG _LT_LANG_DEFAULT_CONFIG _LT_CONFIG_COMMANDS ])# _LT_SETUP # _LT_PREPARE_SED_QUOTE_VARS # -------------------------- # Define a few sed substitution that help us do robust quoting. m4_defun([_LT_PREPARE_SED_QUOTE_VARS], [# Backslashify metacharacters that are still active within # double-quoted strings. sed_quote_subst='s/\([["`$\\]]\)/\\\1/g' # Same as above, but do not quote variable references. double_quote_subst='s/\([["`\\]]\)/\\\1/g' # Sed substitution to delay expansion of an escaped shell variable in a # double_quote_subst'ed string. delay_variable_subst='s/\\\\\\\\\\\$/\\\\\\$/g' # Sed substitution to delay expansion of an escaped single quote. delay_single_quote_subst='s/'\''/'\'\\\\\\\'\''/g' # Sed substitution to avoid accidental globbing in evaled expressions no_glob_subst='s/\*/\\\*/g' ]) # _LT_PROG_LTMAIN # --------------- # Note that this code is called both from 'configure', and 'config.status' # now that we use AC_CONFIG_COMMANDS to generate libtool. Notably, # 'config.status' has no value for ac_aux_dir unless we are using Automake, # so we pass a copy along to make sure it has a sensible value anyway. m4_defun([_LT_PROG_LTMAIN], [m4_ifdef([AC_REQUIRE_AUX_FILE], [AC_REQUIRE_AUX_FILE([ltmain.sh])])dnl _LT_CONFIG_LIBTOOL_INIT([ac_aux_dir='$ac_aux_dir']) ltmain=$ac_aux_dir/ltmain.sh ])# _LT_PROG_LTMAIN ## ------------------------------------- ## ## Accumulate code for creating libtool. ## ## ------------------------------------- ## # So that we can recreate a full libtool script including additional # tags, we accumulate the chunks of code to send to AC_CONFIG_COMMANDS # in macros and then make a single call at the end using the 'libtool' # label. # _LT_CONFIG_LIBTOOL_INIT([INIT-COMMANDS]) # ---------------------------------------- # Register INIT-COMMANDS to be passed to AC_CONFIG_COMMANDS later. m4_define([_LT_CONFIG_LIBTOOL_INIT], [m4_ifval([$1], [m4_append([_LT_OUTPUT_LIBTOOL_INIT], [$1 ])])]) # Initialize. m4_define([_LT_OUTPUT_LIBTOOL_INIT]) # _LT_CONFIG_LIBTOOL([COMMANDS]) # ------------------------------ # Register COMMANDS to be passed to AC_CONFIG_COMMANDS later. m4_define([_LT_CONFIG_LIBTOOL], [m4_ifval([$1], [m4_append([_LT_OUTPUT_LIBTOOL_COMMANDS], [$1 ])])]) # Initialize. m4_define([_LT_OUTPUT_LIBTOOL_COMMANDS]) # _LT_CONFIG_SAVE_COMMANDS([COMMANDS], [INIT_COMMANDS]) # ----------------------------------------------------- m4_defun([_LT_CONFIG_SAVE_COMMANDS], [_LT_CONFIG_LIBTOOL([$1]) _LT_CONFIG_LIBTOOL_INIT([$2]) ]) # _LT_FORMAT_COMMENT([COMMENT]) # ----------------------------- # Add leading comment marks to the start of each line, and a trailing # full-stop to the whole comment if one is not present already. m4_define([_LT_FORMAT_COMMENT], [m4_ifval([$1], [ m4_bpatsubst([m4_bpatsubst([$1], [^ *], [# ])], [['`$\]], [\\\&])]m4_bmatch([$1], [[!?.]$], [], [.]) )]) ## ------------------------ ## ## FIXME: Eliminate VARNAME ## ## ------------------------ ## # _LT_DECL([CONFIGNAME], VARNAME, VALUE, [DESCRIPTION], [IS-TAGGED?]) # ------------------------------------------------------------------- # CONFIGNAME is the name given to the value in the libtool script. # VARNAME is the (base) name used in the configure script. # VALUE may be 0, 1 or 2 for a computed quote escaped value based on # VARNAME. Any other value will be used directly. m4_define([_LT_DECL], [lt_if_append_uniq([lt_decl_varnames], [$2], [, ], [lt_dict_add_subkey([lt_decl_dict], [$2], [libtool_name], [m4_ifval([$1], [$1], [$2])]) lt_dict_add_subkey([lt_decl_dict], [$2], [value], [$3]) m4_ifval([$4], [lt_dict_add_subkey([lt_decl_dict], [$2], [description], [$4])]) lt_dict_add_subkey([lt_decl_dict], [$2], [tagged?], [m4_ifval([$5], [yes], [no])])]) ]) # _LT_TAGDECL([CONFIGNAME], VARNAME, VALUE, [DESCRIPTION]) # -------------------------------------------------------- m4_define([_LT_TAGDECL], [_LT_DECL([$1], [$2], [$3], [$4], [yes])]) # lt_decl_tag_varnames([SEPARATOR], [VARNAME1...]) # ------------------------------------------------ m4_define([lt_decl_tag_varnames], [_lt_decl_filter([tagged?], [yes], $@)]) # _lt_decl_filter(SUBKEY, VALUE, [SEPARATOR], [VARNAME1..]) # --------------------------------------------------------- m4_define([_lt_decl_filter], [m4_case([$#], [0], [m4_fatal([$0: too few arguments: $#])], [1], [m4_fatal([$0: too few arguments: $#: $1])], [2], [lt_dict_filter([lt_decl_dict], [$1], [$2], [], lt_decl_varnames)], [3], [lt_dict_filter([lt_decl_dict], [$1], [$2], [$3], lt_decl_varnames)], [lt_dict_filter([lt_decl_dict], $@)])[]dnl ]) # lt_decl_quote_varnames([SEPARATOR], [VARNAME1...]) # -------------------------------------------------- m4_define([lt_decl_quote_varnames], [_lt_decl_filter([value], [1], $@)]) # lt_decl_dquote_varnames([SEPARATOR], [VARNAME1...]) # --------------------------------------------------- m4_define([lt_decl_dquote_varnames], [_lt_decl_filter([value], [2], $@)]) # lt_decl_varnames_tagged([SEPARATOR], [VARNAME1...]) # --------------------------------------------------- m4_define([lt_decl_varnames_tagged], [m4_assert([$# <= 2])dnl _$0(m4_quote(m4_default([$1], [[, ]])), m4_ifval([$2], [[$2]], [m4_dquote(lt_decl_tag_varnames)]), m4_split(m4_normalize(m4_quote(_LT_TAGS)), [ ]))]) m4_define([_lt_decl_varnames_tagged], [m4_ifval([$3], [lt_combine([$1], [$2], [_], $3)])]) # lt_decl_all_varnames([SEPARATOR], [VARNAME1...]) # ------------------------------------------------ m4_define([lt_decl_all_varnames], [_$0(m4_quote(m4_default([$1], [[, ]])), m4_if([$2], [], m4_quote(lt_decl_varnames), m4_quote(m4_shift($@))))[]dnl ]) m4_define([_lt_decl_all_varnames], [lt_join($@, lt_decl_varnames_tagged([$1], lt_decl_tag_varnames([[, ]], m4_shift($@))))dnl ]) # _LT_CONFIG_STATUS_DECLARE([VARNAME]) # ------------------------------------ # Quote a variable value, and forward it to 'config.status' so that its # declaration there will have the same value as in 'configure'. VARNAME # must have a single quote delimited value for this to work. m4_define([_LT_CONFIG_STATUS_DECLARE], [$1='`$ECHO "$][$1" | $SED "$delay_single_quote_subst"`']) # _LT_CONFIG_STATUS_DECLARATIONS # ------------------------------ # We delimit libtool config variables with single quotes, so when # we write them to config.status, we have to be sure to quote all # embedded single quotes properly. In configure, this macro expands # each variable declared with _LT_DECL (and _LT_TAGDECL) into: # # ='`$ECHO "$" | $SED "$delay_single_quote_subst"`' m4_defun([_LT_CONFIG_STATUS_DECLARATIONS], [m4_foreach([_lt_var], m4_quote(lt_decl_all_varnames), [m4_n([_LT_CONFIG_STATUS_DECLARE(_lt_var)])])]) # _LT_LIBTOOL_TAGS # ---------------- # Output comment and list of tags supported by the script m4_defun([_LT_LIBTOOL_TAGS], [_LT_FORMAT_COMMENT([The names of the tagged configurations supported by this script])dnl available_tags='_LT_TAGS'dnl ]) # _LT_LIBTOOL_DECLARE(VARNAME, [TAG]) # ----------------------------------- # Extract the dictionary values for VARNAME (optionally with TAG) and # expand to a commented shell variable setting: # # # Some comment about what VAR is for. # visible_name=$lt_internal_name m4_define([_LT_LIBTOOL_DECLARE], [_LT_FORMAT_COMMENT(m4_quote(lt_dict_fetch([lt_decl_dict], [$1], [description])))[]dnl m4_pushdef([_libtool_name], m4_quote(lt_dict_fetch([lt_decl_dict], [$1], [libtool_name])))[]dnl m4_case(m4_quote(lt_dict_fetch([lt_decl_dict], [$1], [value])), [0], [_libtool_name=[$]$1], [1], [_libtool_name=$lt_[]$1], [2], [_libtool_name=$lt_[]$1], [_libtool_name=lt_dict_fetch([lt_decl_dict], [$1], [value])])[]dnl m4_ifval([$2], [_$2])[]m4_popdef([_libtool_name])[]dnl ]) # _LT_LIBTOOL_CONFIG_VARS # ----------------------- # Produce commented declarations of non-tagged libtool config variables # suitable for insertion in the LIBTOOL CONFIG section of the 'libtool' # script. Tagged libtool config variables (even for the LIBTOOL CONFIG # section) are produced by _LT_LIBTOOL_TAG_VARS. m4_defun([_LT_LIBTOOL_CONFIG_VARS], [m4_foreach([_lt_var], m4_quote(_lt_decl_filter([tagged?], [no], [], lt_decl_varnames)), [m4_n([_LT_LIBTOOL_DECLARE(_lt_var)])])]) # _LT_LIBTOOL_TAG_VARS(TAG) # ------------------------- m4_define([_LT_LIBTOOL_TAG_VARS], [m4_foreach([_lt_var], m4_quote(lt_decl_tag_varnames), [m4_n([_LT_LIBTOOL_DECLARE(_lt_var, [$1])])])]) # _LT_TAGVAR(VARNAME, [TAGNAME]) # ------------------------------ m4_define([_LT_TAGVAR], [m4_ifval([$2], [$1_$2], [$1])]) # _LT_CONFIG_COMMANDS # ------------------- # Send accumulated output to $CONFIG_STATUS. Thanks to the lists of # variables for single and double quote escaping we saved from calls # to _LT_DECL, we can put quote escaped variables declarations # into 'config.status', and then the shell code to quote escape them in # for loops in 'config.status'. Finally, any additional code accumulated # from calls to _LT_CONFIG_LIBTOOL_INIT is expanded. m4_defun([_LT_CONFIG_COMMANDS], [AC_PROVIDE_IFELSE([LT_OUTPUT], dnl If the libtool generation code has been placed in $CONFIG_LT, dnl instead of duplicating it all over again into config.status, dnl then we will have config.status run $CONFIG_LT later, so it dnl needs to know what name is stored there: [AC_CONFIG_COMMANDS([libtool], [$SHELL $CONFIG_LT || AS_EXIT(1)], [CONFIG_LT='$CONFIG_LT'])], dnl If the libtool generation code is destined for config.status, dnl expand the accumulated commands and init code now: [AC_CONFIG_COMMANDS([libtool], [_LT_OUTPUT_LIBTOOL_COMMANDS], [_LT_OUTPUT_LIBTOOL_COMMANDS_INIT])]) ])#_LT_CONFIG_COMMANDS # Initialize. m4_define([_LT_OUTPUT_LIBTOOL_COMMANDS_INIT], [ # The HP-UX ksh and POSIX shell print the target directory to stdout # if CDPATH is set. (unset CDPATH) >/dev/null 2>&1 && unset CDPATH sed_quote_subst='$sed_quote_subst' double_quote_subst='$double_quote_subst' delay_variable_subst='$delay_variable_subst' _LT_CONFIG_STATUS_DECLARATIONS LTCC='$LTCC' LTCFLAGS='$LTCFLAGS' compiler='$compiler_DEFAULT' # A function that is used when there is no print builtin or printf. func_fallback_echo () { eval 'cat <<_LTECHO_EOF \$[]1 _LTECHO_EOF' } # Quote evaled strings. for var in lt_decl_all_varnames([[ \ ]], lt_decl_quote_varnames); do case \`eval \\\\\$ECHO \\\\""\\\\\$\$var"\\\\"\` in *[[\\\\\\\`\\"\\\$]]*) eval "lt_\$var=\\\\\\"\\\`\\\$ECHO \\"\\\$\$var\\" | \\\$SED \\"\\\$sed_quote_subst\\"\\\`\\\\\\"" ## exclude from sc_prohibit_nested_quotes ;; *) eval "lt_\$var=\\\\\\"\\\$\$var\\\\\\"" ;; esac done # Double-quote double-evaled strings. for var in lt_decl_all_varnames([[ \ ]], lt_decl_dquote_varnames); do case \`eval \\\\\$ECHO \\\\""\\\\\$\$var"\\\\"\` in *[[\\\\\\\`\\"\\\$]]*) eval "lt_\$var=\\\\\\"\\\`\\\$ECHO \\"\\\$\$var\\" | \\\$SED -e \\"\\\$double_quote_subst\\" -e \\"\\\$sed_quote_subst\\" -e \\"\\\$delay_variable_subst\\"\\\`\\\\\\"" ## exclude from sc_prohibit_nested_quotes ;; *) eval "lt_\$var=\\\\\\"\\\$\$var\\\\\\"" ;; esac done _LT_OUTPUT_LIBTOOL_INIT ]) # _LT_GENERATED_FILE_INIT(FILE, [COMMENT]) # ------------------------------------ # Generate a child script FILE with all initialization necessary to # reuse the environment learned by the parent script, and make the # file executable. If COMMENT is supplied, it is inserted after the # '#!' sequence but before initialization text begins. After this # macro, additional text can be appended to FILE to form the body of # the child script. The macro ends with non-zero status if the # file could not be fully written (such as if the disk is full). m4_ifdef([AS_INIT_GENERATED], [m4_defun([_LT_GENERATED_FILE_INIT],[AS_INIT_GENERATED($@)])], [m4_defun([_LT_GENERATED_FILE_INIT], [m4_require([AS_PREPARE])]dnl [m4_pushdef([AS_MESSAGE_LOG_FD])]dnl [lt_write_fail=0 cat >$1 <<_ASEOF || lt_write_fail=1 #! $SHELL # Generated by $as_me. $2 SHELL=\${CONFIG_SHELL-$SHELL} export SHELL _ASEOF cat >>$1 <<\_ASEOF || lt_write_fail=1 AS_SHELL_SANITIZE _AS_PREPARE exec AS_MESSAGE_FD>&1 _ASEOF test 0 = "$lt_write_fail" && chmod +x $1[]dnl m4_popdef([AS_MESSAGE_LOG_FD])])])# _LT_GENERATED_FILE_INIT # LT_OUTPUT # --------- # This macro allows early generation of the libtool script (before # AC_OUTPUT is called), incase it is used in configure for compilation # tests. AC_DEFUN([LT_OUTPUT], [: ${CONFIG_LT=./config.lt} AC_MSG_NOTICE([creating $CONFIG_LT]) _LT_GENERATED_FILE_INIT(["$CONFIG_LT"], [# Run this file to recreate a libtool stub with the current configuration.]) cat >>"$CONFIG_LT" <<\_LTEOF lt_cl_silent=false exec AS_MESSAGE_LOG_FD>>config.log { echo AS_BOX([Running $as_me.]) } >&AS_MESSAGE_LOG_FD lt_cl_help="\ '$as_me' creates a local libtool stub from the current configuration, for use in further configure time tests before the real libtool is generated. Usage: $[0] [[OPTIONS]] -h, --help print this help, then exit -V, --version print version number, then exit -q, --quiet do not print progress messages -d, --debug don't remove temporary files Report bugs to ." lt_cl_version="\ m4_ifset([AC_PACKAGE_NAME], [AC_PACKAGE_NAME ])config.lt[]dnl m4_ifset([AC_PACKAGE_VERSION], [ AC_PACKAGE_VERSION]) configured by $[0], generated by m4_PACKAGE_STRING. Copyright (C) 2011 Free Software Foundation, Inc. This config.lt script is free software; the Free Software Foundation gives unlimited permision to copy, distribute and modify it." while test 0 != $[#] do case $[1] in --version | --v* | -V ) echo "$lt_cl_version"; exit 0 ;; --help | --h* | -h ) echo "$lt_cl_help"; exit 0 ;; --debug | --d* | -d ) debug=: ;; --quiet | --q* | --silent | --s* | -q ) lt_cl_silent=: ;; -*) AC_MSG_ERROR([unrecognized option: $[1] Try '$[0] --help' for more information.]) ;; *) AC_MSG_ERROR([unrecognized argument: $[1] Try '$[0] --help' for more information.]) ;; esac shift done if $lt_cl_silent; then exec AS_MESSAGE_FD>/dev/null fi _LTEOF cat >>"$CONFIG_LT" <<_LTEOF _LT_OUTPUT_LIBTOOL_COMMANDS_INIT _LTEOF cat >>"$CONFIG_LT" <<\_LTEOF AC_MSG_NOTICE([creating $ofile]) _LT_OUTPUT_LIBTOOL_COMMANDS AS_EXIT(0) _LTEOF chmod +x "$CONFIG_LT" # configure is writing to config.log, but config.lt does its own redirection, # appending to config.log, which fails on DOS, as config.log is still kept # open by configure. Here we exec the FD to /dev/null, effectively closing # config.log, so it can be properly (re)opened and appended to by config.lt. lt_cl_success=: test yes = "$silent" && lt_config_lt_args="$lt_config_lt_args --quiet" exec AS_MESSAGE_LOG_FD>/dev/null $SHELL "$CONFIG_LT" $lt_config_lt_args || lt_cl_success=false exec AS_MESSAGE_LOG_FD>>config.log $lt_cl_success || AS_EXIT(1) ])# LT_OUTPUT # _LT_CONFIG(TAG) # --------------- # If TAG is the built-in tag, create an initial libtool script with a # default configuration from the untagged config vars. Otherwise add code # to config.status for appending the configuration named by TAG from the # matching tagged config vars. m4_defun([_LT_CONFIG], [m4_require([_LT_FILEUTILS_DEFAULTS])dnl _LT_CONFIG_SAVE_COMMANDS([ m4_define([_LT_TAG], m4_if([$1], [], [C], [$1]))dnl m4_if(_LT_TAG, [C], [ # See if we are running on zsh, and set the options that allow our # commands through without removal of \ escapes. if test -n "${ZSH_VERSION+set}"; then setopt NO_GLOB_SUBST fi cfgfile=${ofile}T trap "$RM \"$cfgfile\"; exit 1" 1 2 15 $RM "$cfgfile" cat <<_LT_EOF >> "$cfgfile" #! $SHELL # Generated automatically by $as_me ($PACKAGE) $VERSION # NOTE: Changes made to this file will be lost: look at ltmain.sh. # Provide generalized library-building support services. # Written by Gordon Matzigkeit, 1996 _LT_COPYING _LT_LIBTOOL_TAGS # Configured defaults for sys_lib_dlsearch_path munging. : \${LT_SYS_LIBRARY_PATH="$configure_time_lt_sys_library_path"} # ### BEGIN LIBTOOL CONFIG _LT_LIBTOOL_CONFIG_VARS _LT_LIBTOOL_TAG_VARS # ### END LIBTOOL CONFIG _LT_EOF cat <<'_LT_EOF' >> "$cfgfile" # ### BEGIN FUNCTIONS SHARED WITH CONFIGURE _LT_PREPARE_MUNGE_PATH_LIST _LT_PREPARE_CC_BASENAME # ### END FUNCTIONS SHARED WITH CONFIGURE _LT_EOF case $host_os in aix3*) cat <<\_LT_EOF >> "$cfgfile" # AIX sometimes has problems with the GCC collect2 program. For some # reason, if we set the COLLECT_NAMES environment variable, the problems # vanish in a puff of smoke. if test set != "${COLLECT_NAMES+set}"; then COLLECT_NAMES= export COLLECT_NAMES fi _LT_EOF ;; esac _LT_PROG_LTMAIN # We use sed instead of cat because bash on DJGPP gets confused if # if finds mixed CR/LF and LF-only lines. Since sed operates in # text mode, it properly converts lines to CR/LF. This bash problem # is reportedly fixed, but why not run on old versions too? sed '$q' "$ltmain" >> "$cfgfile" \ || (rm -f "$cfgfile"; exit 1) mv -f "$cfgfile" "$ofile" || (rm -f "$ofile" && cp "$cfgfile" "$ofile" && rm -f "$cfgfile") chmod +x "$ofile" ], [cat <<_LT_EOF >> "$ofile" dnl Unfortunately we have to use $1 here, since _LT_TAG is not expanded dnl in a comment (ie after a #). # ### BEGIN LIBTOOL TAG CONFIG: $1 _LT_LIBTOOL_TAG_VARS(_LT_TAG) # ### END LIBTOOL TAG CONFIG: $1 _LT_EOF ])dnl /m4_if ], [m4_if([$1], [], [ PACKAGE='$PACKAGE' VERSION='$VERSION' RM='$RM' ofile='$ofile'], []) ])dnl /_LT_CONFIG_SAVE_COMMANDS ])# _LT_CONFIG # LT_SUPPORTED_TAG(TAG) # --------------------- # Trace this macro to discover what tags are supported by the libtool # --tag option, using: # autoconf --trace 'LT_SUPPORTED_TAG:$1' AC_DEFUN([LT_SUPPORTED_TAG], []) # C support is built-in for now m4_define([_LT_LANG_C_enabled], []) m4_define([_LT_TAGS], []) # LT_LANG(LANG) # ------------- # Enable libtool support for the given language if not already enabled. AC_DEFUN([LT_LANG], [AC_BEFORE([$0], [LT_OUTPUT])dnl m4_case([$1], [C], [_LT_LANG(C)], [C++], [_LT_LANG(CXX)], [Go], [_LT_LANG(GO)], [Java], [_LT_LANG(GCJ)], [Fortran 77], [_LT_LANG(F77)], [Fortran], [_LT_LANG(FC)], [Windows Resource], [_LT_LANG(RC)], [m4_ifdef([_LT_LANG_]$1[_CONFIG], [_LT_LANG($1)], [m4_fatal([$0: unsupported language: "$1"])])])dnl ])# LT_LANG # _LT_LANG(LANGNAME) # ------------------ m4_defun([_LT_LANG], [m4_ifdef([_LT_LANG_]$1[_enabled], [], [LT_SUPPORTED_TAG([$1])dnl m4_append([_LT_TAGS], [$1 ])dnl m4_define([_LT_LANG_]$1[_enabled], [])dnl _LT_LANG_$1_CONFIG($1)])dnl ])# _LT_LANG m4_ifndef([AC_PROG_GO], [ ############################################################ # NOTE: This macro has been submitted for inclusion into # # GNU Autoconf as AC_PROG_GO. When it is available in # # a released version of Autoconf we should remove this # # macro and use it instead. # ############################################################ m4_defun([AC_PROG_GO], [AC_LANG_PUSH(Go)dnl AC_ARG_VAR([GOC], [Go compiler command])dnl AC_ARG_VAR([GOFLAGS], [Go compiler flags])dnl _AC_ARG_VAR_LDFLAGS()dnl AC_CHECK_TOOL(GOC, gccgo) if test -z "$GOC"; then if test -n "$ac_tool_prefix"; then AC_CHECK_PROG(GOC, [${ac_tool_prefix}gccgo], [${ac_tool_prefix}gccgo]) fi fi if test -z "$GOC"; then AC_CHECK_PROG(GOC, gccgo, gccgo, false) fi ])#m4_defun ])#m4_ifndef # _LT_LANG_DEFAULT_CONFIG # ----------------------- m4_defun([_LT_LANG_DEFAULT_CONFIG], [AC_PROVIDE_IFELSE([AC_PROG_CXX], [LT_LANG(CXX)], [m4_define([AC_PROG_CXX], defn([AC_PROG_CXX])[LT_LANG(CXX)])]) AC_PROVIDE_IFELSE([AC_PROG_F77], [LT_LANG(F77)], [m4_define([AC_PROG_F77], defn([AC_PROG_F77])[LT_LANG(F77)])]) AC_PROVIDE_IFELSE([AC_PROG_FC], [LT_LANG(FC)], [m4_define([AC_PROG_FC], defn([AC_PROG_FC])[LT_LANG(FC)])]) dnl The call to [A][M_PROG_GCJ] is quoted like that to stop aclocal dnl pulling things in needlessly. AC_PROVIDE_IFELSE([AC_PROG_GCJ], [LT_LANG(GCJ)], [AC_PROVIDE_IFELSE([A][M_PROG_GCJ], [LT_LANG(GCJ)], [AC_PROVIDE_IFELSE([LT_PROG_GCJ], [LT_LANG(GCJ)], [m4_ifdef([AC_PROG_GCJ], [m4_define([AC_PROG_GCJ], defn([AC_PROG_GCJ])[LT_LANG(GCJ)])]) m4_ifdef([A][M_PROG_GCJ], [m4_define([A][M_PROG_GCJ], defn([A][M_PROG_GCJ])[LT_LANG(GCJ)])]) m4_ifdef([LT_PROG_GCJ], [m4_define([LT_PROG_GCJ], defn([LT_PROG_GCJ])[LT_LANG(GCJ)])])])])]) AC_PROVIDE_IFELSE([AC_PROG_GO], [LT_LANG(GO)], [m4_define([AC_PROG_GO], defn([AC_PROG_GO])[LT_LANG(GO)])]) AC_PROVIDE_IFELSE([LT_PROG_RC], [LT_LANG(RC)], [m4_define([LT_PROG_RC], defn([LT_PROG_RC])[LT_LANG(RC)])]) ])# _LT_LANG_DEFAULT_CONFIG # Obsolete macros: AU_DEFUN([AC_LIBTOOL_CXX], [LT_LANG(C++)]) AU_DEFUN([AC_LIBTOOL_F77], [LT_LANG(Fortran 77)]) AU_DEFUN([AC_LIBTOOL_FC], [LT_LANG(Fortran)]) AU_DEFUN([AC_LIBTOOL_GCJ], [LT_LANG(Java)]) AU_DEFUN([AC_LIBTOOL_RC], [LT_LANG(Windows Resource)]) dnl aclocal-1.4 backwards compatibility: dnl AC_DEFUN([AC_LIBTOOL_CXX], []) dnl AC_DEFUN([AC_LIBTOOL_F77], []) dnl AC_DEFUN([AC_LIBTOOL_FC], []) dnl AC_DEFUN([AC_LIBTOOL_GCJ], []) dnl AC_DEFUN([AC_LIBTOOL_RC], []) # _LT_TAG_COMPILER # ---------------- m4_defun([_LT_TAG_COMPILER], [AC_REQUIRE([AC_PROG_CC])dnl _LT_DECL([LTCC], [CC], [1], [A C compiler])dnl _LT_DECL([LTCFLAGS], [CFLAGS], [1], [LTCC compiler flags])dnl _LT_TAGDECL([CC], [compiler], [1], [A language specific compiler])dnl _LT_TAGDECL([with_gcc], [GCC], [0], [Is the compiler the GNU compiler?])dnl # If no C compiler was specified, use CC. LTCC=${LTCC-"$CC"} # If no C compiler flags were specified, use CFLAGS. LTCFLAGS=${LTCFLAGS-"$CFLAGS"} # Allow CC to be a program name with arguments. compiler=$CC ])# _LT_TAG_COMPILER # _LT_COMPILER_BOILERPLATE # ------------------------ # Check for compiler boilerplate output or warnings with # the simple compiler test code. m4_defun([_LT_COMPILER_BOILERPLATE], [m4_require([_LT_DECL_SED])dnl ac_outfile=conftest.$ac_objext echo "$lt_simple_compile_test_code" >conftest.$ac_ext eval "$ac_compile" 2>&1 >/dev/null | $SED '/^$/d; /^ *+/d' >conftest.err _lt_compiler_boilerplate=`cat conftest.err` $RM conftest* ])# _LT_COMPILER_BOILERPLATE # _LT_LINKER_BOILERPLATE # ---------------------- # Check for linker boilerplate output or warnings with # the simple link test code. m4_defun([_LT_LINKER_BOILERPLATE], [m4_require([_LT_DECL_SED])dnl ac_outfile=conftest.$ac_objext echo "$lt_simple_link_test_code" >conftest.$ac_ext eval "$ac_link" 2>&1 >/dev/null | $SED '/^$/d; /^ *+/d' >conftest.err _lt_linker_boilerplate=`cat conftest.err` $RM -r conftest* ])# _LT_LINKER_BOILERPLATE # _LT_REQUIRED_DARWIN_CHECKS # ------------------------- m4_defun_once([_LT_REQUIRED_DARWIN_CHECKS],[ case $host_os in rhapsody* | darwin*) AC_CHECK_TOOL([DSYMUTIL], [dsymutil], [:]) AC_CHECK_TOOL([NMEDIT], [nmedit], [:]) AC_CHECK_TOOL([LIPO], [lipo], [:]) AC_CHECK_TOOL([OTOOL], [otool], [:]) AC_CHECK_TOOL([OTOOL64], [otool64], [:]) _LT_DECL([], [DSYMUTIL], [1], [Tool to manipulate archived DWARF debug symbol files on Mac OS X]) _LT_DECL([], [NMEDIT], [1], [Tool to change global to local symbols on Mac OS X]) _LT_DECL([], [LIPO], [1], [Tool to manipulate fat objects and archives on Mac OS X]) _LT_DECL([], [OTOOL], [1], [ldd/readelf like tool for Mach-O binaries on Mac OS X]) _LT_DECL([], [OTOOL64], [1], [ldd/readelf like tool for 64 bit Mach-O binaries on Mac OS X 10.4]) AC_CACHE_CHECK([for -single_module linker flag],[lt_cv_apple_cc_single_mod], [lt_cv_apple_cc_single_mod=no if test -z "$LT_MULTI_MODULE"; then # By default we will add the -single_module flag. You can override # by either setting the environment variable LT_MULTI_MODULE # non-empty at configure time, or by adding -multi_module to the # link flags. rm -rf libconftest.dylib* echo "int foo(void){return 1;}" > conftest.c echo "$LTCC $LTCFLAGS $LDFLAGS -o libconftest.dylib \ -dynamiclib -Wl,-single_module conftest.c" >&AS_MESSAGE_LOG_FD $LTCC $LTCFLAGS $LDFLAGS -o libconftest.dylib \ -dynamiclib -Wl,-single_module conftest.c 2>conftest.err _lt_result=$? # If there is a non-empty error log, and "single_module" # appears in it, assume the flag caused a linker warning if test -s conftest.err && $GREP single_module conftest.err; then cat conftest.err >&AS_MESSAGE_LOG_FD # Otherwise, if the output was created with a 0 exit code from # the compiler, it worked. elif test -f libconftest.dylib && test 0 = "$_lt_result"; then lt_cv_apple_cc_single_mod=yes else cat conftest.err >&AS_MESSAGE_LOG_FD fi rm -rf libconftest.dylib* rm -f conftest.* fi]) AC_CACHE_CHECK([for -exported_symbols_list linker flag], [lt_cv_ld_exported_symbols_list], [lt_cv_ld_exported_symbols_list=no save_LDFLAGS=$LDFLAGS echo "_main" > conftest.sym LDFLAGS="$LDFLAGS -Wl,-exported_symbols_list,conftest.sym" AC_LINK_IFELSE([AC_LANG_PROGRAM([],[])], [lt_cv_ld_exported_symbols_list=yes], [lt_cv_ld_exported_symbols_list=no]) LDFLAGS=$save_LDFLAGS ]) AC_CACHE_CHECK([for -force_load linker flag],[lt_cv_ld_force_load], [lt_cv_ld_force_load=no cat > conftest.c << _LT_EOF int forced_loaded() { return 2;} _LT_EOF echo "$LTCC $LTCFLAGS -c -o conftest.o conftest.c" >&AS_MESSAGE_LOG_FD $LTCC $LTCFLAGS -c -o conftest.o conftest.c 2>&AS_MESSAGE_LOG_FD echo "$AR cru libconftest.a conftest.o" >&AS_MESSAGE_LOG_FD $AR cru libconftest.a conftest.o 2>&AS_MESSAGE_LOG_FD echo "$RANLIB libconftest.a" >&AS_MESSAGE_LOG_FD $RANLIB libconftest.a 2>&AS_MESSAGE_LOG_FD cat > conftest.c << _LT_EOF int main() { return 0;} _LT_EOF echo "$LTCC $LTCFLAGS $LDFLAGS -o conftest conftest.c -Wl,-force_load,./libconftest.a" >&AS_MESSAGE_LOG_FD $LTCC $LTCFLAGS $LDFLAGS -o conftest conftest.c -Wl,-force_load,./libconftest.a 2>conftest.err _lt_result=$? if test -s conftest.err && $GREP force_load conftest.err; then cat conftest.err >&AS_MESSAGE_LOG_FD elif test -f conftest && test 0 = "$_lt_result" && $GREP forced_load conftest >/dev/null 2>&1; then lt_cv_ld_force_load=yes else cat conftest.err >&AS_MESSAGE_LOG_FD fi rm -f conftest.err libconftest.a conftest conftest.c rm -rf conftest.dSYM ]) case $host_os in rhapsody* | darwin1.[[012]]) _lt_dar_allow_undefined='$wl-undefined ${wl}suppress' ;; darwin1.*) _lt_dar_allow_undefined='$wl-flat_namespace $wl-undefined ${wl}suppress' ;; darwin*) # darwin 5.x on # if running on 10.5 or later, the deployment target defaults # to the OS version, if on x86, and 10.4, the deployment # target defaults to 10.4. Don't you love it? case ${MACOSX_DEPLOYMENT_TARGET-10.0},$host in 10.0,*86*-darwin8*|10.0,*-darwin[[91]]*) _lt_dar_allow_undefined='$wl-undefined ${wl}dynamic_lookup' ;; 10.[[012]][[,.]]*) _lt_dar_allow_undefined='$wl-flat_namespace $wl-undefined ${wl}suppress' ;; 10.*) _lt_dar_allow_undefined='$wl-undefined ${wl}dynamic_lookup' ;; esac ;; esac if test yes = "$lt_cv_apple_cc_single_mod"; then _lt_dar_single_mod='$single_module' fi if test yes = "$lt_cv_ld_exported_symbols_list"; then _lt_dar_export_syms=' $wl-exported_symbols_list,$output_objdir/$libname-symbols.expsym' else _lt_dar_export_syms='~$NMEDIT -s $output_objdir/$libname-symbols.expsym $lib' fi if test : != "$DSYMUTIL" && test no = "$lt_cv_ld_force_load"; then _lt_dsymutil='~$DSYMUTIL $lib || :' else _lt_dsymutil= fi ;; esac ]) # _LT_DARWIN_LINKER_FEATURES([TAG]) # --------------------------------- # Checks for linker and compiler features on darwin m4_defun([_LT_DARWIN_LINKER_FEATURES], [ m4_require([_LT_REQUIRED_DARWIN_CHECKS]) _LT_TAGVAR(archive_cmds_need_lc, $1)=no _LT_TAGVAR(hardcode_direct, $1)=no _LT_TAGVAR(hardcode_automatic, $1)=yes _LT_TAGVAR(hardcode_shlibpath_var, $1)=unsupported if test yes = "$lt_cv_ld_force_load"; then _LT_TAGVAR(whole_archive_flag_spec, $1)='`for conv in $convenience\"\"; do test -n \"$conv\" && new_convenience=\"$new_convenience $wl-force_load,$conv\"; done; func_echo_all \"$new_convenience\"`' m4_case([$1], [F77], [_LT_TAGVAR(compiler_needs_object, $1)=yes], [FC], [_LT_TAGVAR(compiler_needs_object, $1)=yes]) else _LT_TAGVAR(whole_archive_flag_spec, $1)='' fi _LT_TAGVAR(link_all_deplibs, $1)=yes _LT_TAGVAR(allow_undefined_flag, $1)=$_lt_dar_allow_undefined case $cc_basename in ifort*|nagfor*) _lt_dar_can_shared=yes ;; *) _lt_dar_can_shared=$GCC ;; esac if test yes = "$_lt_dar_can_shared"; then output_verbose_link_cmd=func_echo_all _LT_TAGVAR(archive_cmds, $1)="\$CC -dynamiclib \$allow_undefined_flag -o \$lib \$libobjs \$deplibs \$compiler_flags -install_name \$rpath/\$soname \$verstring $_lt_dar_single_mod$_lt_dsymutil" _LT_TAGVAR(module_cmds, $1)="\$CC \$allow_undefined_flag -o \$lib -bundle \$libobjs \$deplibs \$compiler_flags$_lt_dsymutil" _LT_TAGVAR(archive_expsym_cmds, $1)="sed 's|^|_|' < \$export_symbols > \$output_objdir/\$libname-symbols.expsym~\$CC -dynamiclib \$allow_undefined_flag -o \$lib \$libobjs \$deplibs \$compiler_flags -install_name \$rpath/\$soname \$verstring $_lt_dar_single_mod$_lt_dar_export_syms$_lt_dsymutil" _LT_TAGVAR(module_expsym_cmds, $1)="sed -e 's|^|_|' < \$export_symbols > \$output_objdir/\$libname-symbols.expsym~\$CC \$allow_undefined_flag -o \$lib -bundle \$libobjs \$deplibs \$compiler_flags$_lt_dar_export_syms$_lt_dsymutil" m4_if([$1], [CXX], [ if test yes != "$lt_cv_apple_cc_single_mod"; then _LT_TAGVAR(archive_cmds, $1)="\$CC -r -keep_private_externs -nostdlib -o \$lib-master.o \$libobjs~\$CC -dynamiclib \$allow_undefined_flag -o \$lib \$lib-master.o \$deplibs \$compiler_flags -install_name \$rpath/\$soname \$verstring$_lt_dsymutil" _LT_TAGVAR(archive_expsym_cmds, $1)="sed 's|^|_|' < \$export_symbols > \$output_objdir/\$libname-symbols.expsym~\$CC -r -keep_private_externs -nostdlib -o \$lib-master.o \$libobjs~\$CC -dynamiclib \$allow_undefined_flag -o \$lib \$lib-master.o \$deplibs \$compiler_flags -install_name \$rpath/\$soname \$verstring$_lt_dar_export_syms$_lt_dsymutil" fi ],[]) else _LT_TAGVAR(ld_shlibs, $1)=no fi ]) # _LT_SYS_MODULE_PATH_AIX([TAGNAME]) # ---------------------------------- # Links a minimal program and checks the executable # for the system default hardcoded library path. In most cases, # this is /usr/lib:/lib, but when the MPI compilers are used # the location of the communication and MPI libs are included too. # If we don't find anything, use the default library path according # to the aix ld manual. # Store the results from the different compilers for each TAGNAME. # Allow to override them for all tags through lt_cv_aix_libpath. m4_defun([_LT_SYS_MODULE_PATH_AIX], [m4_require([_LT_DECL_SED])dnl if test set = "${lt_cv_aix_libpath+set}"; then aix_libpath=$lt_cv_aix_libpath else AC_CACHE_VAL([_LT_TAGVAR([lt_cv_aix_libpath_], [$1])], [AC_LINK_IFELSE([AC_LANG_PROGRAM],[ lt_aix_libpath_sed='[ /Import File Strings/,/^$/ { /^0/ { s/^0 *\([^ ]*\) *$/\1/ p } }]' _LT_TAGVAR([lt_cv_aix_libpath_], [$1])=`dump -H conftest$ac_exeext 2>/dev/null | $SED -n -e "$lt_aix_libpath_sed"` # Check for a 64-bit object if we didn't find anything. if test -z "$_LT_TAGVAR([lt_cv_aix_libpath_], [$1])"; then _LT_TAGVAR([lt_cv_aix_libpath_], [$1])=`dump -HX64 conftest$ac_exeext 2>/dev/null | $SED -n -e "$lt_aix_libpath_sed"` fi],[]) if test -z "$_LT_TAGVAR([lt_cv_aix_libpath_], [$1])"; then _LT_TAGVAR([lt_cv_aix_libpath_], [$1])=/usr/lib:/lib fi ]) aix_libpath=$_LT_TAGVAR([lt_cv_aix_libpath_], [$1]) fi ])# _LT_SYS_MODULE_PATH_AIX # _LT_SHELL_INIT(ARG) # ------------------- m4_define([_LT_SHELL_INIT], [m4_divert_text([M4SH-INIT], [$1 ])])# _LT_SHELL_INIT # _LT_PROG_ECHO_BACKSLASH # ----------------------- # Find how we can fake an echo command that does not interpret backslash. # In particular, with Autoconf 2.60 or later we add some code to the start # of the generated configure script that will find a shell with a builtin # printf (that we can use as an echo command). m4_defun([_LT_PROG_ECHO_BACKSLASH], [ECHO='\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\' ECHO=$ECHO$ECHO$ECHO$ECHO$ECHO ECHO=$ECHO$ECHO$ECHO$ECHO$ECHO$ECHO AC_MSG_CHECKING([how to print strings]) # Test print first, because it will be a builtin if present. if test "X`( print -r -- -n ) 2>/dev/null`" = X-n && \ test "X`print -r -- $ECHO 2>/dev/null`" = "X$ECHO"; then ECHO='print -r --' elif test "X`printf %s $ECHO 2>/dev/null`" = "X$ECHO"; then ECHO='printf %s\n' else # Use this function as a fallback that always works. func_fallback_echo () { eval 'cat <<_LTECHO_EOF $[]1 _LTECHO_EOF' } ECHO='func_fallback_echo' fi # func_echo_all arg... # Invoke $ECHO with all args, space-separated. func_echo_all () { $ECHO "$*" } case $ECHO in printf*) AC_MSG_RESULT([printf]) ;; print*) AC_MSG_RESULT([print -r]) ;; *) AC_MSG_RESULT([cat]) ;; esac m4_ifdef([_AS_DETECT_SUGGESTED], [_AS_DETECT_SUGGESTED([ test -n "${ZSH_VERSION+set}${BASH_VERSION+set}" || ( ECHO='\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\' ECHO=$ECHO$ECHO$ECHO$ECHO$ECHO ECHO=$ECHO$ECHO$ECHO$ECHO$ECHO$ECHO PATH=/empty FPATH=/empty; export PATH FPATH test "X`printf %s $ECHO`" = "X$ECHO" \ || test "X`print -r -- $ECHO`" = "X$ECHO" )])]) _LT_DECL([], [SHELL], [1], [Shell to use when invoking shell scripts]) _LT_DECL([], [ECHO], [1], [An echo program that protects backslashes]) ])# _LT_PROG_ECHO_BACKSLASH # _LT_WITH_SYSROOT # ---------------- AC_DEFUN([_LT_WITH_SYSROOT], [AC_MSG_CHECKING([for sysroot]) AC_ARG_WITH([sysroot], [AS_HELP_STRING([--with-sysroot@<:@=DIR@:>@], [Search for dependent libraries within DIR (or the compiler's sysroot if not specified).])], [], [with_sysroot=no]) dnl lt_sysroot will always be passed unquoted. We quote it here dnl in case the user passed a directory name. lt_sysroot= case $with_sysroot in #( yes) if test yes = "$GCC"; then lt_sysroot=`$CC --print-sysroot 2>/dev/null` fi ;; #( /*) lt_sysroot=`echo "$with_sysroot" | sed -e "$sed_quote_subst"` ;; #( no|'') ;; #( *) AC_MSG_RESULT([$with_sysroot]) AC_MSG_ERROR([The sysroot must be an absolute path.]) ;; esac AC_MSG_RESULT([${lt_sysroot:-no}]) _LT_DECL([], [lt_sysroot], [0], [The root where to search for ]dnl [dependent libraries, and where our libraries should be installed.])]) # _LT_ENABLE_LOCK # --------------- m4_defun([_LT_ENABLE_LOCK], [AC_ARG_ENABLE([libtool-lock], [AS_HELP_STRING([--disable-libtool-lock], [avoid locking (might break parallel builds)])]) test no = "$enable_libtool_lock" || enable_libtool_lock=yes # Some flags need to be propagated to the compiler or linker for good # libtool support. case $host in ia64-*-hpux*) # Find out what ABI is being produced by ac_compile, and set mode # options accordingly. echo 'int i;' > conftest.$ac_ext if AC_TRY_EVAL(ac_compile); then case `/usr/bin/file conftest.$ac_objext` in *ELF-32*) HPUX_IA64_MODE=32 ;; *ELF-64*) HPUX_IA64_MODE=64 ;; esac fi rm -rf conftest* ;; *-*-irix6*) # Find out what ABI is being produced by ac_compile, and set linker # options accordingly. echo '[#]line '$LINENO' "configure"' > conftest.$ac_ext if AC_TRY_EVAL(ac_compile); then if test yes = "$lt_cv_prog_gnu_ld"; then case `/usr/bin/file conftest.$ac_objext` in *32-bit*) LD="${LD-ld} -melf32bsmip" ;; *N32*) LD="${LD-ld} -melf32bmipn32" ;; *64-bit*) LD="${LD-ld} -melf64bmip" ;; esac else case `/usr/bin/file conftest.$ac_objext` in *32-bit*) LD="${LD-ld} -32" ;; *N32*) LD="${LD-ld} -n32" ;; *64-bit*) LD="${LD-ld} -64" ;; esac fi fi rm -rf conftest* ;; mips64*-*linux*) # Find out what ABI is being produced by ac_compile, and set linker # options accordingly. echo '[#]line '$LINENO' "configure"' > conftest.$ac_ext if AC_TRY_EVAL(ac_compile); then emul=elf case `/usr/bin/file conftest.$ac_objext` in *32-bit*) emul="${emul}32" ;; *64-bit*) emul="${emul}64" ;; esac case `/usr/bin/file conftest.$ac_objext` in *MSB*) emul="${emul}btsmip" ;; *LSB*) emul="${emul}ltsmip" ;; esac case `/usr/bin/file conftest.$ac_objext` in *N32*) emul="${emul}n32" ;; esac LD="${LD-ld} -m $emul" fi rm -rf conftest* ;; x86_64-*kfreebsd*-gnu|x86_64-*linux*|powerpc*-*linux*| \ s390*-*linux*|s390*-*tpf*|sparc*-*linux*) # Find out what ABI is being produced by ac_compile, and set linker # options accordingly. Note that the listed cases only cover the # situations where additional linker options are needed (such as when # doing 32-bit compilation for a host where ld defaults to 64-bit, or # vice versa); the common cases where no linker options are needed do # not appear in the list. echo 'int i;' > conftest.$ac_ext if AC_TRY_EVAL(ac_compile); then case `/usr/bin/file conftest.o` in *32-bit*) case $host in x86_64-*kfreebsd*-gnu) LD="${LD-ld} -m elf_i386_fbsd" ;; x86_64-*linux*) case `/usr/bin/file conftest.o` in *x86-64*) LD="${LD-ld} -m elf32_x86_64" ;; *) LD="${LD-ld} -m elf_i386" ;; esac ;; powerpc64le-*linux*) LD="${LD-ld} -m elf32lppclinux" ;; powerpc64-*linux*) LD="${LD-ld} -m elf32ppclinux" ;; s390x-*linux*) LD="${LD-ld} -m elf_s390" ;; sparc64-*linux*) LD="${LD-ld} -m elf32_sparc" ;; esac ;; *64-bit*) case $host in x86_64-*kfreebsd*-gnu) LD="${LD-ld} -m elf_x86_64_fbsd" ;; x86_64-*linux*) LD="${LD-ld} -m elf_x86_64" ;; powerpcle-*linux*) LD="${LD-ld} -m elf64lppc" ;; powerpc-*linux*) LD="${LD-ld} -m elf64ppc" ;; s390*-*linux*|s390*-*tpf*) LD="${LD-ld} -m elf64_s390" ;; sparc*-*linux*) LD="${LD-ld} -m elf64_sparc" ;; esac ;; esac fi rm -rf conftest* ;; *-*-sco3.2v5*) # On SCO OpenServer 5, we need -belf to get full-featured binaries. SAVE_CFLAGS=$CFLAGS CFLAGS="$CFLAGS -belf" AC_CACHE_CHECK([whether the C compiler needs -belf], lt_cv_cc_needs_belf, [AC_LANG_PUSH(C) AC_LINK_IFELSE([AC_LANG_PROGRAM([[]],[[]])],[lt_cv_cc_needs_belf=yes],[lt_cv_cc_needs_belf=no]) AC_LANG_POP]) if test yes != "$lt_cv_cc_needs_belf"; then # this is probably gcc 2.8.0, egcs 1.0 or newer; no need for -belf CFLAGS=$SAVE_CFLAGS fi ;; *-*solaris*) # Find out what ABI is being produced by ac_compile, and set linker # options accordingly. echo 'int i;' > conftest.$ac_ext if AC_TRY_EVAL(ac_compile); then case `/usr/bin/file conftest.o` in *64-bit*) case $lt_cv_prog_gnu_ld in yes*) case $host in i?86-*-solaris*|x86_64-*-solaris*) LD="${LD-ld} -m elf_x86_64" ;; sparc*-*-solaris*) LD="${LD-ld} -m elf64_sparc" ;; esac # GNU ld 2.21 introduced _sol2 emulations. Use them if available. if ${LD-ld} -V | grep _sol2 >/dev/null 2>&1; then LD=${LD-ld}_sol2 fi ;; *) if ${LD-ld} -64 -r -o conftest2.o conftest.o >/dev/null 2>&1; then LD="${LD-ld} -64" fi ;; esac ;; esac fi rm -rf conftest* ;; esac need_locks=$enable_libtool_lock ])# _LT_ENABLE_LOCK # _LT_PROG_AR # ----------- m4_defun([_LT_PROG_AR], [AC_CHECK_TOOLS(AR, [ar], false) : ${AR=ar} : ${AR_FLAGS=cru} _LT_DECL([], [AR], [1], [The archiver]) _LT_DECL([], [AR_FLAGS], [1], [Flags to create an archive]) AC_CACHE_CHECK([for archiver @FILE support], [lt_cv_ar_at_file], [lt_cv_ar_at_file=no AC_COMPILE_IFELSE([AC_LANG_PROGRAM], [echo conftest.$ac_objext > conftest.lst lt_ar_try='$AR $AR_FLAGS libconftest.a @conftest.lst >&AS_MESSAGE_LOG_FD' AC_TRY_EVAL([lt_ar_try]) if test 0 -eq "$ac_status"; then # Ensure the archiver fails upon bogus file names. rm -f conftest.$ac_objext libconftest.a AC_TRY_EVAL([lt_ar_try]) if test 0 -ne "$ac_status"; then lt_cv_ar_at_file=@ fi fi rm -f conftest.* libconftest.a ]) ]) if test no = "$lt_cv_ar_at_file"; then archiver_list_spec= else archiver_list_spec=$lt_cv_ar_at_file fi _LT_DECL([], [archiver_list_spec], [1], [How to feed a file listing to the archiver]) ])# _LT_PROG_AR # _LT_CMD_OLD_ARCHIVE # ------------------- m4_defun([_LT_CMD_OLD_ARCHIVE], [_LT_PROG_AR AC_CHECK_TOOL(STRIP, strip, :) test -z "$STRIP" && STRIP=: _LT_DECL([], [STRIP], [1], [A symbol stripping program]) AC_CHECK_TOOL(RANLIB, ranlib, :) test -z "$RANLIB" && RANLIB=: _LT_DECL([], [RANLIB], [1], [Commands used to install an old-style archive]) # Determine commands to create old-style static archives. old_archive_cmds='$AR $AR_FLAGS $oldlib$oldobjs' old_postinstall_cmds='chmod 644 $oldlib' old_postuninstall_cmds= if test -n "$RANLIB"; then case $host_os in bitrig* | openbsd*) old_postinstall_cmds="$old_postinstall_cmds~\$RANLIB -t \$tool_oldlib" ;; *) old_postinstall_cmds="$old_postinstall_cmds~\$RANLIB \$tool_oldlib" ;; esac old_archive_cmds="$old_archive_cmds~\$RANLIB \$tool_oldlib" fi case $host_os in darwin*) lock_old_archive_extraction=yes ;; *) lock_old_archive_extraction=no ;; esac _LT_DECL([], [old_postinstall_cmds], [2]) _LT_DECL([], [old_postuninstall_cmds], [2]) _LT_TAGDECL([], [old_archive_cmds], [2], [Commands used to build an old-style archive]) _LT_DECL([], [lock_old_archive_extraction], [0], [Whether to use a lock for old archive extraction]) ])# _LT_CMD_OLD_ARCHIVE # _LT_COMPILER_OPTION(MESSAGE, VARIABLE-NAME, FLAGS, # [OUTPUT-FILE], [ACTION-SUCCESS], [ACTION-FAILURE]) # ---------------------------------------------------------------- # Check whether the given compiler option works AC_DEFUN([_LT_COMPILER_OPTION], [m4_require([_LT_FILEUTILS_DEFAULTS])dnl m4_require([_LT_DECL_SED])dnl AC_CACHE_CHECK([$1], [$2], [$2=no m4_if([$4], , [ac_outfile=conftest.$ac_objext], [ac_outfile=$4]) echo "$lt_simple_compile_test_code" > conftest.$ac_ext lt_compiler_flag="$3" ## exclude from sc_useless_quotes_in_assignment # Insert the option either (1) after the last *FLAGS variable, or # (2) before a word containing "conftest.", or (3) at the end. # Note that $ac_compile itself does not contain backslashes and begins # with a dollar sign (not a hyphen), so the echo should work correctly. # The option is referenced via a variable to avoid confusing sed. lt_compile=`echo "$ac_compile" | $SED \ -e 's:.*FLAGS}\{0,1\} :&$lt_compiler_flag :; t' \ -e 's: [[^ ]]*conftest\.: $lt_compiler_flag&:; t' \ -e 's:$: $lt_compiler_flag:'` (eval echo "\"\$as_me:$LINENO: $lt_compile\"" >&AS_MESSAGE_LOG_FD) (eval "$lt_compile" 2>conftest.err) ac_status=$? cat conftest.err >&AS_MESSAGE_LOG_FD echo "$as_me:$LINENO: \$? = $ac_status" >&AS_MESSAGE_LOG_FD if (exit $ac_status) && test -s "$ac_outfile"; then # The compiler can only warn and ignore the option if not recognized # So say no if there are warnings other than the usual output. $ECHO "$_lt_compiler_boilerplate" | $SED '/^$/d' >conftest.exp $SED '/^$/d; /^ *+/d' conftest.err >conftest.er2 if test ! -s conftest.er2 || diff conftest.exp conftest.er2 >/dev/null; then $2=yes fi fi $RM conftest* ]) if test yes = "[$]$2"; then m4_if([$5], , :, [$5]) else m4_if([$6], , :, [$6]) fi ])# _LT_COMPILER_OPTION # Old name: AU_ALIAS([AC_LIBTOOL_COMPILER_OPTION], [_LT_COMPILER_OPTION]) dnl aclocal-1.4 backwards compatibility: dnl AC_DEFUN([AC_LIBTOOL_COMPILER_OPTION], []) # _LT_LINKER_OPTION(MESSAGE, VARIABLE-NAME, FLAGS, # [ACTION-SUCCESS], [ACTION-FAILURE]) # ---------------------------------------------------- # Check whether the given linker option works AC_DEFUN([_LT_LINKER_OPTION], [m4_require([_LT_FILEUTILS_DEFAULTS])dnl m4_require([_LT_DECL_SED])dnl AC_CACHE_CHECK([$1], [$2], [$2=no save_LDFLAGS=$LDFLAGS LDFLAGS="$LDFLAGS $3" echo "$lt_simple_link_test_code" > conftest.$ac_ext if (eval $ac_link 2>conftest.err) && test -s conftest$ac_exeext; then # The linker can only warn and ignore the option if not recognized # So say no if there are warnings if test -s conftest.err; then # Append any errors to the config.log. cat conftest.err 1>&AS_MESSAGE_LOG_FD $ECHO "$_lt_linker_boilerplate" | $SED '/^$/d' > conftest.exp $SED '/^$/d; /^ *+/d' conftest.err >conftest.er2 if diff conftest.exp conftest.er2 >/dev/null; then $2=yes fi else $2=yes fi fi $RM -r conftest* LDFLAGS=$save_LDFLAGS ]) if test yes = "[$]$2"; then m4_if([$4], , :, [$4]) else m4_if([$5], , :, [$5]) fi ])# _LT_LINKER_OPTION # Old name: AU_ALIAS([AC_LIBTOOL_LINKER_OPTION], [_LT_LINKER_OPTION]) dnl aclocal-1.4 backwards compatibility: dnl AC_DEFUN([AC_LIBTOOL_LINKER_OPTION], []) # LT_CMD_MAX_LEN #--------------- AC_DEFUN([LT_CMD_MAX_LEN], [AC_REQUIRE([AC_CANONICAL_HOST])dnl # find the maximum length of command line arguments AC_MSG_CHECKING([the maximum length of command line arguments]) AC_CACHE_VAL([lt_cv_sys_max_cmd_len], [dnl i=0 teststring=ABCD case $build_os in msdosdjgpp*) # On DJGPP, this test can blow up pretty badly due to problems in libc # (any single argument exceeding 2000 bytes causes a buffer overrun # during glob expansion). Even if it were fixed, the result of this # check would be larger than it should be. lt_cv_sys_max_cmd_len=12288; # 12K is about right ;; gnu*) # Under GNU Hurd, this test is not required because there is # no limit to the length of command line arguments. # Libtool will interpret -1 as no limit whatsoever lt_cv_sys_max_cmd_len=-1; ;; cygwin* | mingw* | cegcc*) # On Win9x/ME, this test blows up -- it succeeds, but takes # about 5 minutes as the teststring grows exponentially. # Worse, since 9x/ME are not pre-emptively multitasking, # you end up with a "frozen" computer, even though with patience # the test eventually succeeds (with a max line length of 256k). # Instead, let's just punt: use the minimum linelength reported by # all of the supported platforms: 8192 (on NT/2K/XP). lt_cv_sys_max_cmd_len=8192; ;; mint*) # On MiNT this can take a long time and run out of memory. lt_cv_sys_max_cmd_len=8192; ;; amigaos*) # On AmigaOS with pdksh, this test takes hours, literally. # So we just punt and use a minimum line length of 8192. lt_cv_sys_max_cmd_len=8192; ;; bitrig* | darwin* | dragonfly* | freebsd* | netbsd* | openbsd*) # This has been around since 386BSD, at least. Likely further. if test -x /sbin/sysctl; then lt_cv_sys_max_cmd_len=`/sbin/sysctl -n kern.argmax` elif test -x /usr/sbin/sysctl; then lt_cv_sys_max_cmd_len=`/usr/sbin/sysctl -n kern.argmax` else lt_cv_sys_max_cmd_len=65536 # usable default for all BSDs fi # And add a safety zone lt_cv_sys_max_cmd_len=`expr $lt_cv_sys_max_cmd_len \/ 4` lt_cv_sys_max_cmd_len=`expr $lt_cv_sys_max_cmd_len \* 3` ;; interix*) # We know the value 262144 and hardcode it with a safety zone (like BSD) lt_cv_sys_max_cmd_len=196608 ;; os2*) # The test takes a long time on OS/2. lt_cv_sys_max_cmd_len=8192 ;; osf*) # Dr. Hans Ekkehard Plesser reports seeing a kernel panic running configure # due to this test when exec_disable_arg_limit is 1 on Tru64. It is not # nice to cause kernel panics so lets avoid the loop below. # First set a reasonable default. lt_cv_sys_max_cmd_len=16384 # if test -x /sbin/sysconfig; then case `/sbin/sysconfig -q proc exec_disable_arg_limit` in *1*) lt_cv_sys_max_cmd_len=-1 ;; esac fi ;; sco3.2v5*) lt_cv_sys_max_cmd_len=102400 ;; sysv5* | sco5v6* | sysv4.2uw2*) kargmax=`grep ARG_MAX /etc/conf/cf.d/stune 2>/dev/null` if test -n "$kargmax"; then lt_cv_sys_max_cmd_len=`echo $kargmax | sed 's/.*[[ ]]//'` else lt_cv_sys_max_cmd_len=32768 fi ;; *) lt_cv_sys_max_cmd_len=`(getconf ARG_MAX) 2> /dev/null` if test -n "$lt_cv_sys_max_cmd_len" && \ test undefined != "$lt_cv_sys_max_cmd_len"; then lt_cv_sys_max_cmd_len=`expr $lt_cv_sys_max_cmd_len \/ 4` lt_cv_sys_max_cmd_len=`expr $lt_cv_sys_max_cmd_len \* 3` else # Make teststring a little bigger before we do anything with it. # a 1K string should be a reasonable start. for i in 1 2 3 4 5 6 7 8; do teststring=$teststring$teststring done SHELL=${SHELL-${CONFIG_SHELL-/bin/sh}} # If test is not a shell built-in, we'll probably end up computing a # maximum length that is only half of the actual maximum length, but # we can't tell. while { test X`env echo "$teststring$teststring" 2>/dev/null` \ = "X$teststring$teststring"; } >/dev/null 2>&1 && test 17 != "$i" # 1/2 MB should be enough do i=`expr $i + 1` teststring=$teststring$teststring done # Only check the string length outside the loop. lt_cv_sys_max_cmd_len=`expr "X$teststring" : ".*" 2>&1` teststring= # Add a significant safety factor because C++ compilers can tack on # massive amounts of additional arguments before passing them to the # linker. It appears as though 1/2 is a usable value. lt_cv_sys_max_cmd_len=`expr $lt_cv_sys_max_cmd_len \/ 2` fi ;; esac ]) if test -n "$lt_cv_sys_max_cmd_len"; then AC_MSG_RESULT($lt_cv_sys_max_cmd_len) else AC_MSG_RESULT(none) fi max_cmd_len=$lt_cv_sys_max_cmd_len _LT_DECL([], [max_cmd_len], [0], [What is the maximum length of a command?]) ])# LT_CMD_MAX_LEN # Old name: AU_ALIAS([AC_LIBTOOL_SYS_MAX_CMD_LEN], [LT_CMD_MAX_LEN]) dnl aclocal-1.4 backwards compatibility: dnl AC_DEFUN([AC_LIBTOOL_SYS_MAX_CMD_LEN], []) # _LT_HEADER_DLFCN # ---------------- m4_defun([_LT_HEADER_DLFCN], [AC_CHECK_HEADERS([dlfcn.h], [], [], [AC_INCLUDES_DEFAULT])dnl ])# _LT_HEADER_DLFCN # _LT_TRY_DLOPEN_SELF (ACTION-IF-TRUE, ACTION-IF-TRUE-W-USCORE, # ACTION-IF-FALSE, ACTION-IF-CROSS-COMPILING) # ---------------------------------------------------------------- m4_defun([_LT_TRY_DLOPEN_SELF], [m4_require([_LT_HEADER_DLFCN])dnl if test yes = "$cross_compiling"; then : [$4] else lt_dlunknown=0; lt_dlno_uscore=1; lt_dlneed_uscore=2 lt_status=$lt_dlunknown cat > conftest.$ac_ext <<_LT_EOF [#line $LINENO "configure" #include "confdefs.h" #if HAVE_DLFCN_H #include #endif #include #ifdef RTLD_GLOBAL # define LT_DLGLOBAL RTLD_GLOBAL #else # ifdef DL_GLOBAL # define LT_DLGLOBAL DL_GLOBAL # else # define LT_DLGLOBAL 0 # endif #endif /* We may have to define LT_DLLAZY_OR_NOW in the command line if we find out it does not work in some platform. */ #ifndef LT_DLLAZY_OR_NOW # ifdef RTLD_LAZY # define LT_DLLAZY_OR_NOW RTLD_LAZY # else # ifdef DL_LAZY # define LT_DLLAZY_OR_NOW DL_LAZY # else # ifdef RTLD_NOW # define LT_DLLAZY_OR_NOW RTLD_NOW # else # ifdef DL_NOW # define LT_DLLAZY_OR_NOW DL_NOW # else # define LT_DLLAZY_OR_NOW 0 # endif # endif # endif # endif #endif /* When -fvisibility=hidden is used, assume the code has been annotated correspondingly for the symbols needed. */ #if defined __GNUC__ && (((__GNUC__ == 3) && (__GNUC_MINOR__ >= 3)) || (__GNUC__ > 3)) int fnord () __attribute__((visibility("default"))); #endif int fnord () { return 42; } int main () { void *self = dlopen (0, LT_DLGLOBAL|LT_DLLAZY_OR_NOW); int status = $lt_dlunknown; if (self) { if (dlsym (self,"fnord")) status = $lt_dlno_uscore; else { if (dlsym( self,"_fnord")) status = $lt_dlneed_uscore; else puts (dlerror ()); } /* dlclose (self); */ } else puts (dlerror ()); return status; }] _LT_EOF if AC_TRY_EVAL(ac_link) && test -s "conftest$ac_exeext" 2>/dev/null; then (./conftest; exit; ) >&AS_MESSAGE_LOG_FD 2>/dev/null lt_status=$? case x$lt_status in x$lt_dlno_uscore) $1 ;; x$lt_dlneed_uscore) $2 ;; x$lt_dlunknown|x*) $3 ;; esac else : # compilation failed $3 fi fi rm -fr conftest* ])# _LT_TRY_DLOPEN_SELF # LT_SYS_DLOPEN_SELF # ------------------ AC_DEFUN([LT_SYS_DLOPEN_SELF], [m4_require([_LT_HEADER_DLFCN])dnl if test yes != "$enable_dlopen"; then enable_dlopen=unknown enable_dlopen_self=unknown enable_dlopen_self_static=unknown else lt_cv_dlopen=no lt_cv_dlopen_libs= case $host_os in beos*) lt_cv_dlopen=load_add_on lt_cv_dlopen_libs= lt_cv_dlopen_self=yes ;; mingw* | pw32* | cegcc*) lt_cv_dlopen=LoadLibrary lt_cv_dlopen_libs= ;; cygwin*) lt_cv_dlopen=dlopen lt_cv_dlopen_libs= ;; darwin*) # if libdl is installed we need to link against it AC_CHECK_LIB([dl], [dlopen], [lt_cv_dlopen=dlopen lt_cv_dlopen_libs=-ldl],[ lt_cv_dlopen=dyld lt_cv_dlopen_libs= lt_cv_dlopen_self=yes ]) ;; tpf*) # Don't try to run any link tests for TPF. We know it's impossible # because TPF is a cross-compiler, and we know how we open DSOs. lt_cv_dlopen=dlopen lt_cv_dlopen_libs= lt_cv_dlopen_self=no ;; *) AC_CHECK_FUNC([shl_load], [lt_cv_dlopen=shl_load], [AC_CHECK_LIB([dld], [shl_load], [lt_cv_dlopen=shl_load lt_cv_dlopen_libs=-ldld], [AC_CHECK_FUNC([dlopen], [lt_cv_dlopen=dlopen], [AC_CHECK_LIB([dl], [dlopen], [lt_cv_dlopen=dlopen lt_cv_dlopen_libs=-ldl], [AC_CHECK_LIB([svld], [dlopen], [lt_cv_dlopen=dlopen lt_cv_dlopen_libs=-lsvld], [AC_CHECK_LIB([dld], [dld_link], [lt_cv_dlopen=dld_link lt_cv_dlopen_libs=-ldld]) ]) ]) ]) ]) ]) ;; esac if test no = "$lt_cv_dlopen"; then enable_dlopen=no else enable_dlopen=yes fi case $lt_cv_dlopen in dlopen) save_CPPFLAGS=$CPPFLAGS test yes = "$ac_cv_header_dlfcn_h" && CPPFLAGS="$CPPFLAGS -DHAVE_DLFCN_H" save_LDFLAGS=$LDFLAGS wl=$lt_prog_compiler_wl eval LDFLAGS=\"\$LDFLAGS $export_dynamic_flag_spec\" save_LIBS=$LIBS LIBS="$lt_cv_dlopen_libs $LIBS" AC_CACHE_CHECK([whether a program can dlopen itself], lt_cv_dlopen_self, [dnl _LT_TRY_DLOPEN_SELF( lt_cv_dlopen_self=yes, lt_cv_dlopen_self=yes, lt_cv_dlopen_self=no, lt_cv_dlopen_self=cross) ]) if test yes = "$lt_cv_dlopen_self"; then wl=$lt_prog_compiler_wl eval LDFLAGS=\"\$LDFLAGS $lt_prog_compiler_static\" AC_CACHE_CHECK([whether a statically linked program can dlopen itself], lt_cv_dlopen_self_static, [dnl _LT_TRY_DLOPEN_SELF( lt_cv_dlopen_self_static=yes, lt_cv_dlopen_self_static=yes, lt_cv_dlopen_self_static=no, lt_cv_dlopen_self_static=cross) ]) fi CPPFLAGS=$save_CPPFLAGS LDFLAGS=$save_LDFLAGS LIBS=$save_LIBS ;; esac case $lt_cv_dlopen_self in yes|no) enable_dlopen_self=$lt_cv_dlopen_self ;; *) enable_dlopen_self=unknown ;; esac case $lt_cv_dlopen_self_static in yes|no) enable_dlopen_self_static=$lt_cv_dlopen_self_static ;; *) enable_dlopen_self_static=unknown ;; esac fi _LT_DECL([dlopen_support], [enable_dlopen], [0], [Whether dlopen is supported]) _LT_DECL([dlopen_self], [enable_dlopen_self], [0], [Whether dlopen of programs is supported]) _LT_DECL([dlopen_self_static], [enable_dlopen_self_static], [0], [Whether dlopen of statically linked programs is supported]) ])# LT_SYS_DLOPEN_SELF # Old name: AU_ALIAS([AC_LIBTOOL_DLOPEN_SELF], [LT_SYS_DLOPEN_SELF]) dnl aclocal-1.4 backwards compatibility: dnl AC_DEFUN([AC_LIBTOOL_DLOPEN_SELF], []) # _LT_COMPILER_C_O([TAGNAME]) # --------------------------- # Check to see if options -c and -o are simultaneously supported by compiler. # This macro does not hard code the compiler like AC_PROG_CC_C_O. m4_defun([_LT_COMPILER_C_O], [m4_require([_LT_DECL_SED])dnl m4_require([_LT_FILEUTILS_DEFAULTS])dnl m4_require([_LT_TAG_COMPILER])dnl AC_CACHE_CHECK([if $compiler supports -c -o file.$ac_objext], [_LT_TAGVAR(lt_cv_prog_compiler_c_o, $1)], [_LT_TAGVAR(lt_cv_prog_compiler_c_o, $1)=no $RM -r conftest 2>/dev/null mkdir conftest cd conftest mkdir out echo "$lt_simple_compile_test_code" > conftest.$ac_ext lt_compiler_flag="-o out/conftest2.$ac_objext" # Insert the option either (1) after the last *FLAGS variable, or # (2) before a word containing "conftest.", or (3) at the end. # Note that $ac_compile itself does not contain backslashes and begins # with a dollar sign (not a hyphen), so the echo should work correctly. lt_compile=`echo "$ac_compile" | $SED \ -e 's:.*FLAGS}\{0,1\} :&$lt_compiler_flag :; t' \ -e 's: [[^ ]]*conftest\.: $lt_compiler_flag&:; t' \ -e 's:$: $lt_compiler_flag:'` (eval echo "\"\$as_me:$LINENO: $lt_compile\"" >&AS_MESSAGE_LOG_FD) (eval "$lt_compile" 2>out/conftest.err) ac_status=$? cat out/conftest.err >&AS_MESSAGE_LOG_FD echo "$as_me:$LINENO: \$? = $ac_status" >&AS_MESSAGE_LOG_FD if (exit $ac_status) && test -s out/conftest2.$ac_objext then # The compiler can only warn and ignore the option if not recognized # So say no if there are warnings $ECHO "$_lt_compiler_boilerplate" | $SED '/^$/d' > out/conftest.exp $SED '/^$/d; /^ *+/d' out/conftest.err >out/conftest.er2 if test ! -s out/conftest.er2 || diff out/conftest.exp out/conftest.er2 >/dev/null; then _LT_TAGVAR(lt_cv_prog_compiler_c_o, $1)=yes fi fi chmod u+w . 2>&AS_MESSAGE_LOG_FD $RM conftest* # SGI C++ compiler will create directory out/ii_files/ for # template instantiation test -d out/ii_files && $RM out/ii_files/* && rmdir out/ii_files $RM out/* && rmdir out cd .. $RM -r conftest $RM conftest* ]) _LT_TAGDECL([compiler_c_o], [lt_cv_prog_compiler_c_o], [1], [Does compiler simultaneously support -c and -o options?]) ])# _LT_COMPILER_C_O # _LT_COMPILER_FILE_LOCKS([TAGNAME]) # ---------------------------------- # Check to see if we can do hard links to lock some files if needed m4_defun([_LT_COMPILER_FILE_LOCKS], [m4_require([_LT_ENABLE_LOCK])dnl m4_require([_LT_FILEUTILS_DEFAULTS])dnl _LT_COMPILER_C_O([$1]) hard_links=nottested if test no = "$_LT_TAGVAR(lt_cv_prog_compiler_c_o, $1)" && test no != "$need_locks"; then # do not overwrite the value of need_locks provided by the user AC_MSG_CHECKING([if we can lock with hard links]) hard_links=yes $RM conftest* ln conftest.a conftest.b 2>/dev/null && hard_links=no touch conftest.a ln conftest.a conftest.b 2>&5 || hard_links=no ln conftest.a conftest.b 2>/dev/null && hard_links=no AC_MSG_RESULT([$hard_links]) if test no = "$hard_links"; then AC_MSG_WARN(['$CC' does not support '-c -o', so 'make -j' may be unsafe]) need_locks=warn fi else need_locks=no fi _LT_DECL([], [need_locks], [1], [Must we lock files when doing compilation?]) ])# _LT_COMPILER_FILE_LOCKS # _LT_CHECK_OBJDIR # ---------------- m4_defun([_LT_CHECK_OBJDIR], [AC_CACHE_CHECK([for objdir], [lt_cv_objdir], [rm -f .libs 2>/dev/null mkdir .libs 2>/dev/null if test -d .libs; then lt_cv_objdir=.libs else # MS-DOS does not allow filenames that begin with a dot. lt_cv_objdir=_libs fi rmdir .libs 2>/dev/null]) objdir=$lt_cv_objdir _LT_DECL([], [objdir], [0], [The name of the directory that contains temporary libtool files])dnl m4_pattern_allow([LT_OBJDIR])dnl AC_DEFINE_UNQUOTED([LT_OBJDIR], "$lt_cv_objdir/", [Define to the sub-directory where libtool stores uninstalled libraries.]) ])# _LT_CHECK_OBJDIR # _LT_LINKER_HARDCODE_LIBPATH([TAGNAME]) # -------------------------------------- # Check hardcoding attributes. m4_defun([_LT_LINKER_HARDCODE_LIBPATH], [AC_MSG_CHECKING([how to hardcode library paths into programs]) _LT_TAGVAR(hardcode_action, $1)= if test -n "$_LT_TAGVAR(hardcode_libdir_flag_spec, $1)" || test -n "$_LT_TAGVAR(runpath_var, $1)" || test yes = "$_LT_TAGVAR(hardcode_automatic, $1)"; then # We can hardcode non-existent directories. if test no != "$_LT_TAGVAR(hardcode_direct, $1)" && # If the only mechanism to avoid hardcoding is shlibpath_var, we # have to relink, otherwise we might link with an installed library # when we should be linking with a yet-to-be-installed one ## test no != "$_LT_TAGVAR(hardcode_shlibpath_var, $1)" && test no != "$_LT_TAGVAR(hardcode_minus_L, $1)"; then # Linking always hardcodes the temporary library directory. _LT_TAGVAR(hardcode_action, $1)=relink else # We can link without hardcoding, and we can hardcode nonexisting dirs. _LT_TAGVAR(hardcode_action, $1)=immediate fi else # We cannot hardcode anything, or else we can only hardcode existing # directories. _LT_TAGVAR(hardcode_action, $1)=unsupported fi AC_MSG_RESULT([$_LT_TAGVAR(hardcode_action, $1)]) if test relink = "$_LT_TAGVAR(hardcode_action, $1)" || test yes = "$_LT_TAGVAR(inherit_rpath, $1)"; then # Fast installation is not supported enable_fast_install=no elif test yes = "$shlibpath_overrides_runpath" || test no = "$enable_shared"; then # Fast installation is not necessary enable_fast_install=needless fi _LT_TAGDECL([], [hardcode_action], [0], [How to hardcode a shared library path into an executable]) ])# _LT_LINKER_HARDCODE_LIBPATH # _LT_CMD_STRIPLIB # ---------------- m4_defun([_LT_CMD_STRIPLIB], [m4_require([_LT_DECL_EGREP]) striplib= old_striplib= AC_MSG_CHECKING([whether stripping libraries is possible]) if test -n "$STRIP" && $STRIP -V 2>&1 | $GREP "GNU strip" >/dev/null; then test -z "$old_striplib" && old_striplib="$STRIP --strip-debug" test -z "$striplib" && striplib="$STRIP --strip-unneeded" AC_MSG_RESULT([yes]) else # FIXME - insert some real tests, host_os isn't really good enough case $host_os in darwin*) if test -n "$STRIP"; then striplib="$STRIP -x" old_striplib="$STRIP -S" AC_MSG_RESULT([yes]) else AC_MSG_RESULT([no]) fi ;; *) AC_MSG_RESULT([no]) ;; esac fi _LT_DECL([], [old_striplib], [1], [Commands to strip libraries]) _LT_DECL([], [striplib], [1]) ])# _LT_CMD_STRIPLIB # _LT_PREPARE_MUNGE_PATH_LIST # --------------------------- # Make sure func_munge_path_list() is defined correctly. m4_defun([_LT_PREPARE_MUNGE_PATH_LIST], [[# func_munge_path_list VARIABLE PATH # ----------------------------------- # VARIABLE is name of variable containing _space_ separated list of # directories to be munged by the contents of PATH, which is string # having a format: # "DIR[:DIR]:" # string "DIR[ DIR]" will be prepended to VARIABLE # ":DIR[:DIR]" # string "DIR[ DIR]" will be appended to VARIABLE # "DIRP[:DIRP]::[DIRA:]DIRA" # string "DIRP[ DIRP]" will be prepended to VARIABLE and string # "DIRA[ DIRA]" will be appended to VARIABLE # "DIR[:DIR]" # VARIABLE will be replaced by "DIR[ DIR]" func_munge_path_list () { case x@S|@2 in x) ;; *:) eval @S|@1=\"`$ECHO @S|@2 | $SED 's/:/ /g'` \@S|@@S|@1\" ;; x:*) eval @S|@1=\"\@S|@@S|@1 `$ECHO @S|@2 | $SED 's/:/ /g'`\" ;; *::*) eval @S|@1=\"\@S|@@S|@1\ `$ECHO @S|@2 | $SED -e 's/.*:://' -e 's/:/ /g'`\" eval @S|@1=\"`$ECHO @S|@2 | $SED -e 's/::.*//' -e 's/:/ /g'`\ \@S|@@S|@1\" ;; *) eval @S|@1=\"`$ECHO @S|@2 | $SED 's/:/ /g'`\" ;; esac } ]])# _LT_PREPARE_PATH_LIST # _LT_SYS_DYNAMIC_LINKER([TAG]) # ----------------------------- # PORTME Fill in your ld.so characteristics m4_defun([_LT_SYS_DYNAMIC_LINKER], [AC_REQUIRE([AC_CANONICAL_HOST])dnl m4_require([_LT_DECL_EGREP])dnl m4_require([_LT_FILEUTILS_DEFAULTS])dnl m4_require([_LT_DECL_OBJDUMP])dnl m4_require([_LT_DECL_SED])dnl m4_require([_LT_CHECK_SHELL_FEATURES])dnl m4_require([_LT_PREPARE_MUNGE_PATH_LIST])dnl AC_MSG_CHECKING([dynamic linker characteristics]) m4_if([$1], [], [ if test yes = "$GCC"; then case $host_os in darwin*) lt_awk_arg='/^libraries:/,/LR/' ;; *) lt_awk_arg='/^libraries:/' ;; esac case $host_os in mingw* | cegcc*) lt_sed_strip_eq='s|=\([[A-Za-z]]:\)|\1|g' ;; *) lt_sed_strip_eq='s|=/|/|g' ;; esac lt_search_path_spec=`$CC -print-search-dirs | awk $lt_awk_arg | $SED -e "s/^libraries://" -e $lt_sed_strip_eq` case $lt_search_path_spec in *\;*) # if the path contains ";" then we assume it to be the separator # otherwise default to the standard path separator (i.e. ":") - it is # assumed that no part of a normal pathname contains ";" but that should # okay in the real world where ";" in dirpaths is itself problematic. lt_search_path_spec=`$ECHO "$lt_search_path_spec" | $SED 's/;/ /g'` ;; *) lt_search_path_spec=`$ECHO "$lt_search_path_spec" | $SED "s/$PATH_SEPARATOR/ /g"` ;; esac # Ok, now we have the path, separated by spaces, we can step through it # and add multilib dir if necessary... lt_tmp_lt_search_path_spec= lt_multi_os_dir=/`$CC $CPPFLAGS $CFLAGS $LDFLAGS -print-multi-os-directory 2>/dev/null` # ...but if some path component already ends with the multilib dir we assume # that all is fine and trust -print-search-dirs as is (GCC 4.2? or newer). case "$lt_multi_os_dir; $lt_search_path_spec " in "/; "* | "/.; "* | "/./; "* | *"$lt_multi_os_dir "* | *"$lt_multi_os_dir/ "*) lt_multi_os_dir= ;; esac for lt_sys_path in $lt_search_path_spec; do if test -d "$lt_sys_path$lt_multi_os_dir"; then lt_tmp_lt_search_path_spec="$lt_tmp_lt_search_path_spec $lt_sys_path$lt_multi_os_dir" elif test -n "$lt_multi_os_dir"; then test -d "$lt_sys_path" && \ lt_tmp_lt_search_path_spec="$lt_tmp_lt_search_path_spec $lt_sys_path" fi done lt_search_path_spec=`$ECHO "$lt_tmp_lt_search_path_spec" | awk ' BEGIN {RS = " "; FS = "/|\n";} { lt_foo = ""; lt_count = 0; for (lt_i = NF; lt_i > 0; lt_i--) { if ($lt_i != "" && $lt_i != ".") { if ($lt_i == "..") { lt_count++; } else { if (lt_count == 0) { lt_foo = "/" $lt_i lt_foo; } else { lt_count--; } } } } if (lt_foo != "") { lt_freq[[lt_foo]]++; } if (lt_freq[[lt_foo]] == 1) { print lt_foo; } }'` # AWK program above erroneously prepends '/' to C:/dos/paths # for these hosts. case $host_os in mingw* | cegcc*) lt_search_path_spec=`$ECHO "$lt_search_path_spec" |\ $SED 's|/\([[A-Za-z]]:\)|\1|g'` ;; esac sys_lib_search_path_spec=`$ECHO "$lt_search_path_spec" | $lt_NL2SP` else sys_lib_search_path_spec="/lib /usr/lib /usr/local/lib" fi]) library_names_spec= libname_spec='lib$name' soname_spec= shrext_cmds=.so postinstall_cmds= postuninstall_cmds= finish_cmds= finish_eval= shlibpath_var= shlibpath_overrides_runpath=unknown version_type=none dynamic_linker="$host_os ld.so" sys_lib_dlsearch_path_spec="/lib /usr/lib" need_lib_prefix=unknown hardcode_into_libs=no # when you set need_version to no, make sure it does not cause -set_version # flags to be left without arguments need_version=unknown AC_ARG_VAR([LT_SYS_LIBRARY_PATH], [User-defined run-time library search path.]) case $host_os in aix3*) version_type=linux # correct to gnu/linux during the next big refactor library_names_spec='$libname$release$shared_ext$versuffix $libname.a' shlibpath_var=LIBPATH # AIX 3 has no versioning support, so we append a major version to the name. soname_spec='$libname$release$shared_ext$major' ;; aix[[4-9]]*) version_type=linux # correct to gnu/linux during the next big refactor need_lib_prefix=no need_version=no hardcode_into_libs=yes if test ia64 = "$host_cpu"; then # AIX 5 supports IA64 library_names_spec='$libname$release$shared_ext$major $libname$release$shared_ext$versuffix $libname$shared_ext' shlibpath_var=LD_LIBRARY_PATH else # With GCC up to 2.95.x, collect2 would create an import file # for dependence libraries. The import file would start with # the line '#! .'. This would cause the generated library to # depend on '.', always an invalid library. This was fixed in # development snapshots of GCC prior to 3.0. case $host_os in aix4 | aix4.[[01]] | aix4.[[01]].*) if { echo '#if __GNUC__ > 2 || (__GNUC__ == 2 && __GNUC_MINOR__ >= 97)' echo ' yes ' echo '#endif'; } | $CC -E - | $GREP yes > /dev/null; then : else can_build_shared=no fi ;; esac # Using Import Files as archive members, it is possible to support # filename-based versioning of shared library archives on AIX. While # this would work for both with and without runtime linking, it will # prevent static linking of such archives. So we do filename-based # shared library versioning with .so extension only, which is used # when both runtime linking and shared linking is enabled. # Unfortunately, runtime linking may impact performance, so we do # not want this to be the default eventually. Also, we use the # versioned .so libs for executables only if there is the -brtl # linker flag in LDFLAGS as well, or --with-aix-soname=svr4 only. # To allow for filename-based versioning support, we need to create # libNAME.so.V as an archive file, containing: # *) an Import File, referring to the versioned filename of the # archive as well as the shared archive member, telling the # bitwidth (32 or 64) of that shared object, and providing the # list of exported symbols of that shared object, eventually # decorated with the 'weak' keyword # *) the shared object with the F_LOADONLY flag set, to really avoid # it being seen by the linker. # At run time we better use the real file rather than another symlink, # but for link time we create the symlink libNAME.so -> libNAME.so.V case $with_aix_soname,$aix_use_runtimelinking in # AIX (on Power*) has no versioning support, so currently we cannot hardcode correct # soname into executable. Probably we can add versioning support to # collect2, so additional links can be useful in future. aix,yes) # traditional libtool dynamic_linker='AIX unversionable lib.so' # If using run time linking (on AIX 4.2 or later) use lib.so # instead of lib.a to let people know that these are not # typical AIX shared libraries. library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext' ;; aix,no) # traditional AIX only dynamic_linker='AIX lib.a[(]lib.so.V[)]' # We preserve .a as extension for shared libraries through AIX4.2 # and later when we are not doing run time linking. library_names_spec='$libname$release.a $libname.a' soname_spec='$libname$release$shared_ext$major' ;; svr4,*) # full svr4 only dynamic_linker="AIX lib.so.V[(]$shared_archive_member_spec.o[)]" library_names_spec='$libname$release$shared_ext$major $libname$shared_ext' # We do not specify a path in Import Files, so LIBPATH fires. shlibpath_overrides_runpath=yes ;; *,yes) # both, prefer svr4 dynamic_linker="AIX lib.so.V[(]$shared_archive_member_spec.o[)], lib.a[(]lib.so.V[)]" library_names_spec='$libname$release$shared_ext$major $libname$shared_ext' # unpreferred sharedlib libNAME.a needs extra handling postinstall_cmds='test -n "$linkname" || linkname="$realname"~func_stripname "" ".so" "$linkname"~$install_shared_prog "$dir/$func_stripname_result.$libext" "$destdir/$func_stripname_result.$libext"~test -z "$tstripme" || test -z "$striplib" || $striplib "$destdir/$func_stripname_result.$libext"' postuninstall_cmds='for n in $library_names $old_library; do :; done~func_stripname "" ".so" "$n"~test "$func_stripname_result" = "$n" || func_append rmfiles " $odir/$func_stripname_result.$libext"' # We do not specify a path in Import Files, so LIBPATH fires. shlibpath_overrides_runpath=yes ;; *,no) # both, prefer aix dynamic_linker="AIX lib.a[(]lib.so.V[)], lib.so.V[(]$shared_archive_member_spec.o[)]" library_names_spec='$libname$release.a $libname.a' soname_spec='$libname$release$shared_ext$major' # unpreferred sharedlib libNAME.so.V and symlink libNAME.so need extra handling postinstall_cmds='test -z "$dlname" || $install_shared_prog $dir/$dlname $destdir/$dlname~test -z "$tstripme" || test -z "$striplib" || $striplib $destdir/$dlname~test -n "$linkname" || linkname=$realname~func_stripname "" ".a" "$linkname"~(cd "$destdir" && $LN_S -f $dlname $func_stripname_result.so)' postuninstall_cmds='test -z "$dlname" || func_append rmfiles " $odir/$dlname"~for n in $old_library $library_names; do :; done~func_stripname "" ".a" "$n"~func_append rmfiles " $odir/$func_stripname_result.so"' ;; esac shlibpath_var=LIBPATH fi ;; amigaos*) case $host_cpu in powerpc) # Since July 2007 AmigaOS4 officially supports .so libraries. # When compiling the executable, add -use-dynld -Lsobjs: to the compileline. library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext' ;; m68k) library_names_spec='$libname.ixlibrary $libname.a' # Create ${libname}_ixlibrary.a entries in /sys/libs. finish_eval='for lib in `ls $libdir/*.ixlibrary 2>/dev/null`; do libname=`func_echo_all "$lib" | $SED '\''s%^.*/\([[^/]]*\)\.ixlibrary$%\1%'\''`; $RM /sys/libs/${libname}_ixlibrary.a; $show "cd /sys/libs && $LN_S $lib ${libname}_ixlibrary.a"; cd /sys/libs && $LN_S $lib ${libname}_ixlibrary.a || exit 1; done' ;; esac ;; beos*) library_names_spec='$libname$shared_ext' dynamic_linker="$host_os ld.so" shlibpath_var=LIBRARY_PATH ;; bsdi[[45]]*) version_type=linux # correct to gnu/linux during the next big refactor need_version=no library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext' soname_spec='$libname$release$shared_ext$major' finish_cmds='PATH="\$PATH:/sbin" ldconfig $libdir' shlibpath_var=LD_LIBRARY_PATH sys_lib_search_path_spec="/shlib /usr/lib /usr/X11/lib /usr/contrib/lib /lib /usr/local/lib" sys_lib_dlsearch_path_spec="/shlib /usr/lib /usr/local/lib" # the default ld.so.conf also contains /usr/contrib/lib and # /usr/X11R6/lib (/usr/X11 is a link to /usr/X11R6), but let us allow # libtool to hard-code these into programs ;; cygwin* | mingw* | pw32* | cegcc*) version_type=windows shrext_cmds=.dll need_version=no need_lib_prefix=no case $GCC,$cc_basename in yes,*) # gcc library_names_spec='$libname.dll.a' # DLL is installed to $(libdir)/../bin by postinstall_cmds postinstall_cmds='base_file=`basename \$file`~ dlpath=`$SHELL 2>&1 -c '\''. $dir/'\''\$base_file'\''i; echo \$dlname'\''`~ dldir=$destdir/`dirname \$dlpath`~ test -d \$dldir || mkdir -p \$dldir~ $install_prog $dir/$dlname \$dldir/$dlname~ chmod a+x \$dldir/$dlname~ if test -n '\''$stripme'\'' && test -n '\''$striplib'\''; then eval '\''$striplib \$dldir/$dlname'\'' || exit \$?; fi' postuninstall_cmds='dldll=`$SHELL 2>&1 -c '\''. $file; echo \$dlname'\''`~ dlpath=$dir/\$dldll~ $RM \$dlpath' shlibpath_overrides_runpath=yes case $host_os in cygwin*) # Cygwin DLLs use 'cyg' prefix rather than 'lib' soname_spec='`echo $libname | sed -e 's/^lib/cyg/'``echo $release | $SED -e 's/[[.]]/-/g'`$versuffix$shared_ext' m4_if([$1], [],[ sys_lib_search_path_spec="$sys_lib_search_path_spec /usr/lib/w32api"]) ;; mingw* | cegcc*) # MinGW DLLs use traditional 'lib' prefix soname_spec='$libname`echo $release | $SED -e 's/[[.]]/-/g'`$versuffix$shared_ext' ;; pw32*) # pw32 DLLs use 'pw' prefix rather than 'lib' library_names_spec='`echo $libname | sed -e 's/^lib/pw/'``echo $release | $SED -e 's/[[.]]/-/g'`$versuffix$shared_ext' ;; esac dynamic_linker='Win32 ld.exe' ;; *,cl*) # Native MSVC libname_spec='$name' soname_spec='$libname`echo $release | $SED -e 's/[[.]]/-/g'`$versuffix$shared_ext' library_names_spec='$libname.dll.lib' case $build_os in mingw*) sys_lib_search_path_spec= lt_save_ifs=$IFS IFS=';' for lt_path in $LIB do IFS=$lt_save_ifs # Let DOS variable expansion print the short 8.3 style file name. lt_path=`cd "$lt_path" 2>/dev/null && cmd //C "for %i in (".") do @echo %~si"` sys_lib_search_path_spec="$sys_lib_search_path_spec $lt_path" done IFS=$lt_save_ifs # Convert to MSYS style. sys_lib_search_path_spec=`$ECHO "$sys_lib_search_path_spec" | sed -e 's|\\\\|/|g' -e 's| \\([[a-zA-Z]]\\):| /\\1|g' -e 's|^ ||'` ;; cygwin*) # Convert to unix form, then to dos form, then back to unix form # but this time dos style (no spaces!) so that the unix form looks # like /cygdrive/c/PROGRA~1:/cygdr... sys_lib_search_path_spec=`cygpath --path --unix "$LIB"` sys_lib_search_path_spec=`cygpath --path --dos "$sys_lib_search_path_spec" 2>/dev/null` sys_lib_search_path_spec=`cygpath --path --unix "$sys_lib_search_path_spec" | $SED -e "s/$PATH_SEPARATOR/ /g"` ;; *) sys_lib_search_path_spec=$LIB if $ECHO "$sys_lib_search_path_spec" | [$GREP ';[c-zC-Z]:/' >/dev/null]; then # It is most probably a Windows format PATH. sys_lib_search_path_spec=`$ECHO "$sys_lib_search_path_spec" | $SED -e 's/;/ /g'` else sys_lib_search_path_spec=`$ECHO "$sys_lib_search_path_spec" | $SED -e "s/$PATH_SEPARATOR/ /g"` fi # FIXME: find the short name or the path components, as spaces are # common. (e.g. "Program Files" -> "PROGRA~1") ;; esac # DLL is installed to $(libdir)/../bin by postinstall_cmds postinstall_cmds='base_file=`basename \$file`~ dlpath=`$SHELL 2>&1 -c '\''. $dir/'\''\$base_file'\''i; echo \$dlname'\''`~ dldir=$destdir/`dirname \$dlpath`~ test -d \$dldir || mkdir -p \$dldir~ $install_prog $dir/$dlname \$dldir/$dlname' postuninstall_cmds='dldll=`$SHELL 2>&1 -c '\''. $file; echo \$dlname'\''`~ dlpath=$dir/\$dldll~ $RM \$dlpath' shlibpath_overrides_runpath=yes dynamic_linker='Win32 link.exe' ;; *) # Assume MSVC wrapper library_names_spec='$libname`echo $release | $SED -e 's/[[.]]/-/g'`$versuffix$shared_ext $libname.lib' dynamic_linker='Win32 ld.exe' ;; esac # FIXME: first we should search . and the directory the executable is in shlibpath_var=PATH ;; darwin* | rhapsody*) dynamic_linker="$host_os dyld" version_type=darwin need_lib_prefix=no need_version=no library_names_spec='$libname$release$major$shared_ext $libname$shared_ext' soname_spec='$libname$release$major$shared_ext' shlibpath_overrides_runpath=yes shlibpath_var=DYLD_LIBRARY_PATH shrext_cmds='`test .$module = .yes && echo .so || echo .dylib`' m4_if([$1], [],[ sys_lib_search_path_spec="$sys_lib_search_path_spec /usr/local/lib"]) sys_lib_dlsearch_path_spec='/usr/local/lib /lib /usr/lib' ;; dgux*) version_type=linux # correct to gnu/linux during the next big refactor need_lib_prefix=no need_version=no library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext' soname_spec='$libname$release$shared_ext$major' shlibpath_var=LD_LIBRARY_PATH ;; freebsd* | dragonfly*) # DragonFly does not have aout. When/if they implement a new # versioning mechanism, adjust this. if test -x /usr/bin/objformat; then objformat=`/usr/bin/objformat` else case $host_os in freebsd[[23]].*) objformat=aout ;; *) objformat=elf ;; esac fi version_type=freebsd-$objformat case $version_type in freebsd-elf*) library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext' soname_spec='$libname$release$shared_ext$major' need_version=no need_lib_prefix=no ;; freebsd-*) library_names_spec='$libname$release$shared_ext$versuffix $libname$shared_ext$versuffix' need_version=yes ;; esac shlibpath_var=LD_LIBRARY_PATH case $host_os in freebsd2.*) shlibpath_overrides_runpath=yes ;; freebsd3.[[01]]* | freebsdelf3.[[01]]*) shlibpath_overrides_runpath=yes hardcode_into_libs=yes ;; freebsd3.[[2-9]]* | freebsdelf3.[[2-9]]* | \ freebsd4.[[0-5]] | freebsdelf4.[[0-5]] | freebsd4.1.1 | freebsdelf4.1.1) shlibpath_overrides_runpath=no hardcode_into_libs=yes ;; *) # from 4.6 on, and DragonFly shlibpath_overrides_runpath=yes hardcode_into_libs=yes ;; esac ;; haiku*) version_type=linux # correct to gnu/linux during the next big refactor need_lib_prefix=no need_version=no dynamic_linker="$host_os runtime_loader" library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext' soname_spec='$libname$release$shared_ext$major' shlibpath_var=LIBRARY_PATH shlibpath_overrides_runpath=no sys_lib_dlsearch_path_spec='/boot/home/config/lib /boot/common/lib /boot/system/lib' hardcode_into_libs=yes ;; hpux9* | hpux10* | hpux11*) # Give a soname corresponding to the major version so that dld.sl refuses to # link against other versions. version_type=sunos need_lib_prefix=no need_version=no case $host_cpu in ia64*) shrext_cmds='.so' hardcode_into_libs=yes dynamic_linker="$host_os dld.so" shlibpath_var=LD_LIBRARY_PATH shlibpath_overrides_runpath=yes # Unless +noenvvar is specified. library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext' soname_spec='$libname$release$shared_ext$major' if test 32 = "$HPUX_IA64_MODE"; then sys_lib_search_path_spec="/usr/lib/hpux32 /usr/local/lib/hpux32 /usr/local/lib" sys_lib_dlsearch_path_spec=/usr/lib/hpux32 else sys_lib_search_path_spec="/usr/lib/hpux64 /usr/local/lib/hpux64" sys_lib_dlsearch_path_spec=/usr/lib/hpux64 fi ;; hppa*64*) shrext_cmds='.sl' hardcode_into_libs=yes dynamic_linker="$host_os dld.sl" shlibpath_var=LD_LIBRARY_PATH # How should we handle SHLIB_PATH shlibpath_overrides_runpath=yes # Unless +noenvvar is specified. library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext' soname_spec='$libname$release$shared_ext$major' sys_lib_search_path_spec="/usr/lib/pa20_64 /usr/ccs/lib/pa20_64" sys_lib_dlsearch_path_spec=$sys_lib_search_path_spec ;; *) shrext_cmds='.sl' dynamic_linker="$host_os dld.sl" shlibpath_var=SHLIB_PATH shlibpath_overrides_runpath=no # +s is required to enable SHLIB_PATH library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext' soname_spec='$libname$release$shared_ext$major' ;; esac # HP-UX runs *really* slowly unless shared libraries are mode 555, ... postinstall_cmds='chmod 555 $lib' # or fails outright, so override atomically: install_override_mode=555 ;; interix[[3-9]]*) version_type=linux # correct to gnu/linux during the next big refactor need_lib_prefix=no need_version=no library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext' soname_spec='$libname$release$shared_ext$major' dynamic_linker='Interix 3.x ld.so.1 (PE, like ELF)' shlibpath_var=LD_LIBRARY_PATH shlibpath_overrides_runpath=no hardcode_into_libs=yes ;; irix5* | irix6* | nonstopux*) case $host_os in nonstopux*) version_type=nonstopux ;; *) if test yes = "$lt_cv_prog_gnu_ld"; then version_type=linux # correct to gnu/linux during the next big refactor else version_type=irix fi ;; esac need_lib_prefix=no need_version=no soname_spec='$libname$release$shared_ext$major' library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$release$shared_ext $libname$shared_ext' case $host_os in irix5* | nonstopux*) libsuff= shlibsuff= ;; *) case $LD in # libtool.m4 will add one of these switches to LD *-32|*"-32 "|*-melf32bsmip|*"-melf32bsmip ") libsuff= shlibsuff= libmagic=32-bit;; *-n32|*"-n32 "|*-melf32bmipn32|*"-melf32bmipn32 ") libsuff=32 shlibsuff=N32 libmagic=N32;; *-64|*"-64 "|*-melf64bmip|*"-melf64bmip ") libsuff=64 shlibsuff=64 libmagic=64-bit;; *) libsuff= shlibsuff= libmagic=never-match;; esac ;; esac shlibpath_var=LD_LIBRARY${shlibsuff}_PATH shlibpath_overrides_runpath=no sys_lib_search_path_spec="/usr/lib$libsuff /lib$libsuff /usr/local/lib$libsuff" sys_lib_dlsearch_path_spec="/usr/lib$libsuff /lib$libsuff" hardcode_into_libs=yes ;; # No shared lib support for Linux oldld, aout, or coff. linux*oldld* | linux*aout* | linux*coff*) dynamic_linker=no ;; linux*android*) version_type=none # Android doesn't support versioned libraries. need_lib_prefix=no need_version=no library_names_spec='$libname$release$shared_ext' soname_spec='$libname$release$shared_ext' finish_cmds= shlibpath_var=LD_LIBRARY_PATH shlibpath_overrides_runpath=yes # This implies no fast_install, which is unacceptable. # Some rework will be needed to allow for fast_install # before this can be enabled. hardcode_into_libs=yes dynamic_linker='Android linker' # Don't embed -rpath directories since the linker doesn't support them. _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='-L$libdir' ;; # This must be glibc/ELF. linux* | k*bsd*-gnu | kopensolaris*-gnu | gnu*) version_type=linux # correct to gnu/linux during the next big refactor need_lib_prefix=no need_version=no library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext' soname_spec='$libname$release$shared_ext$major' finish_cmds='PATH="\$PATH:/sbin" ldconfig -n $libdir' shlibpath_var=LD_LIBRARY_PATH shlibpath_overrides_runpath=no # Some binutils ld are patched to set DT_RUNPATH AC_CACHE_VAL([lt_cv_shlibpath_overrides_runpath], [lt_cv_shlibpath_overrides_runpath=no save_LDFLAGS=$LDFLAGS save_libdir=$libdir eval "libdir=/foo; wl=\"$_LT_TAGVAR(lt_prog_compiler_wl, $1)\"; \ LDFLAGS=\"\$LDFLAGS $_LT_TAGVAR(hardcode_libdir_flag_spec, $1)\"" AC_LINK_IFELSE([AC_LANG_PROGRAM([],[])], [AS_IF([ ($OBJDUMP -p conftest$ac_exeext) 2>/dev/null | grep "RUNPATH.*$libdir" >/dev/null], [lt_cv_shlibpath_overrides_runpath=yes])]) LDFLAGS=$save_LDFLAGS libdir=$save_libdir ]) shlibpath_overrides_runpath=$lt_cv_shlibpath_overrides_runpath # This implies no fast_install, which is unacceptable. # Some rework will be needed to allow for fast_install # before this can be enabled. hardcode_into_libs=yes # Ideally, we could use ldconfig to report *all* directores which are # searched for libraries, however this is still not possible. Aside from not # being certain /sbin/ldconfig is available, command # 'ldconfig -N -X -v | grep ^/' on 64bit Fedora does not report /usr/lib64, # even though it is searched at run-time. Try to do the best guess by # appending ld.so.conf contents (and includes) to the search path. if test -f /etc/ld.so.conf; then lt_ld_extra=`awk '/^include / { system(sprintf("cd /etc; cat %s 2>/dev/null", \[$]2)); skip = 1; } { if (!skip) print \[$]0; skip = 0; }' < /etc/ld.so.conf | $SED -e 's/#.*//;/^[ ]*hwcap[ ]/d;s/[:, ]/ /g;s/=[^=]*$//;s/=[^= ]* / /g;s/"//g;/^$/d' | tr '\n' ' '` sys_lib_dlsearch_path_spec="/lib /usr/lib $lt_ld_extra" fi # We used to test for /lib/ld.so.1 and disable shared libraries on # powerpc, because MkLinux only supported shared libraries with the # GNU dynamic linker. Since this was broken with cross compilers, # most powerpc-linux boxes support dynamic linking these days and # people can always --disable-shared, the test was removed, and we # assume the GNU/Linux dynamic linker is in use. dynamic_linker='GNU/Linux ld.so' ;; netbsdelf*-gnu) version_type=linux need_lib_prefix=no need_version=no library_names_spec='${libname}${release}${shared_ext}$versuffix ${libname}${release}${shared_ext}$major ${libname}${shared_ext}' soname_spec='${libname}${release}${shared_ext}$major' shlibpath_var=LD_LIBRARY_PATH shlibpath_overrides_runpath=no hardcode_into_libs=yes dynamic_linker='NetBSD ld.elf_so' ;; netbsd*) version_type=sunos need_lib_prefix=no need_version=no if echo __ELF__ | $CC -E - | $GREP __ELF__ >/dev/null; then library_names_spec='$libname$release$shared_ext$versuffix $libname$shared_ext$versuffix' finish_cmds='PATH="\$PATH:/sbin" ldconfig -m $libdir' dynamic_linker='NetBSD (a.out) ld.so' else library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext' soname_spec='$libname$release$shared_ext$major' dynamic_linker='NetBSD ld.elf_so' fi shlibpath_var=LD_LIBRARY_PATH shlibpath_overrides_runpath=yes hardcode_into_libs=yes ;; newsos6) version_type=linux # correct to gnu/linux during the next big refactor library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext' shlibpath_var=LD_LIBRARY_PATH shlibpath_overrides_runpath=yes ;; *nto* | *qnx*) version_type=qnx need_lib_prefix=no need_version=no library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext' soname_spec='$libname$release$shared_ext$major' shlibpath_var=LD_LIBRARY_PATH shlibpath_overrides_runpath=no hardcode_into_libs=yes dynamic_linker='ldqnx.so' ;; openbsd* | bitrig*) version_type=sunos sys_lib_dlsearch_path_spec=/usr/lib need_lib_prefix=no if test -z "`echo __ELF__ | $CC -E - | $GREP __ELF__`"; then need_version=no else need_version=yes fi library_names_spec='$libname$release$shared_ext$versuffix $libname$shared_ext$versuffix' finish_cmds='PATH="\$PATH:/sbin" ldconfig -m $libdir' shlibpath_var=LD_LIBRARY_PATH shlibpath_overrides_runpath=yes ;; os2*) libname_spec='$name' version_type=windows shrext_cmds=.dll need_version=no need_lib_prefix=no # OS/2 can only load a DLL with a base name of 8 characters or less. soname_spec='`test -n "$os2dllname" && libname="$os2dllname"; v=$($ECHO $release$versuffix | tr -d .-); n=$($ECHO $libname | cut -b -$((8 - ${#v})) | tr . _); $ECHO $n$v`$shared_ext' library_names_spec='${libname}_dll.$libext' dynamic_linker='OS/2 ld.exe' shlibpath_var=BEGINLIBPATH sys_lib_search_path_spec="/lib /usr/lib /usr/local/lib" sys_lib_dlsearch_path_spec=$sys_lib_search_path_spec postinstall_cmds='base_file=`basename \$file`~ dlpath=`$SHELL 2>&1 -c '\''. $dir/'\''\$base_file'\''i; $ECHO \$dlname'\''`~ dldir=$destdir/`dirname \$dlpath`~ test -d \$dldir || mkdir -p \$dldir~ $install_prog $dir/$dlname \$dldir/$dlname~ chmod a+x \$dldir/$dlname~ if test -n '\''$stripme'\'' && test -n '\''$striplib'\''; then eval '\''$striplib \$dldir/$dlname'\'' || exit \$?; fi' postuninstall_cmds='dldll=`$SHELL 2>&1 -c '\''. $file; $ECHO \$dlname'\''`~ dlpath=$dir/\$dldll~ $RM \$dlpath' ;; osf3* | osf4* | osf5*) version_type=osf need_lib_prefix=no need_version=no soname_spec='$libname$release$shared_ext$major' library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext' shlibpath_var=LD_LIBRARY_PATH sys_lib_search_path_spec="/usr/shlib /usr/ccs/lib /usr/lib/cmplrs/cc /usr/lib /usr/local/lib /var/shlib" sys_lib_dlsearch_path_spec=$sys_lib_search_path_spec ;; rdos*) dynamic_linker=no ;; solaris*) version_type=linux # correct to gnu/linux during the next big refactor need_lib_prefix=no need_version=no library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext' soname_spec='$libname$release$shared_ext$major' shlibpath_var=LD_LIBRARY_PATH shlibpath_overrides_runpath=yes hardcode_into_libs=yes # ldd complains unless libraries are executable postinstall_cmds='chmod +x $lib' ;; sunos4*) version_type=sunos library_names_spec='$libname$release$shared_ext$versuffix $libname$shared_ext$versuffix' finish_cmds='PATH="\$PATH:/usr/etc" ldconfig $libdir' shlibpath_var=LD_LIBRARY_PATH shlibpath_overrides_runpath=yes if test yes = "$with_gnu_ld"; then need_lib_prefix=no fi need_version=yes ;; sysv4 | sysv4.3*) version_type=linux # correct to gnu/linux during the next big refactor library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext' soname_spec='$libname$release$shared_ext$major' shlibpath_var=LD_LIBRARY_PATH case $host_vendor in sni) shlibpath_overrides_runpath=no need_lib_prefix=no runpath_var=LD_RUN_PATH ;; siemens) need_lib_prefix=no ;; motorola) need_lib_prefix=no need_version=no shlibpath_overrides_runpath=no sys_lib_search_path_spec='/lib /usr/lib /usr/ccs/lib' ;; esac ;; sysv4*MP*) if test -d /usr/nec; then version_type=linux # correct to gnu/linux during the next big refactor library_names_spec='$libname$shared_ext.$versuffix $libname$shared_ext.$major $libname$shared_ext' soname_spec='$libname$shared_ext.$major' shlibpath_var=LD_LIBRARY_PATH fi ;; sysv5* | sco3.2v5* | sco5v6* | unixware* | OpenUNIX* | sysv4*uw2*) version_type=sco need_lib_prefix=no need_version=no library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext $libname$shared_ext' soname_spec='$libname$release$shared_ext$major' shlibpath_var=LD_LIBRARY_PATH shlibpath_overrides_runpath=yes hardcode_into_libs=yes if test yes = "$with_gnu_ld"; then sys_lib_search_path_spec='/usr/local/lib /usr/gnu/lib /usr/ccs/lib /usr/lib /lib' else sys_lib_search_path_spec='/usr/ccs/lib /usr/lib' case $host_os in sco3.2v5*) sys_lib_search_path_spec="$sys_lib_search_path_spec /lib" ;; esac fi sys_lib_dlsearch_path_spec='/usr/lib' ;; tpf*) # TPF is a cross-target only. Preferred cross-host = GNU/Linux. version_type=linux # correct to gnu/linux during the next big refactor need_lib_prefix=no need_version=no library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext' shlibpath_var=LD_LIBRARY_PATH shlibpath_overrides_runpath=no hardcode_into_libs=yes ;; uts4*) version_type=linux # correct to gnu/linux during the next big refactor library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext' soname_spec='$libname$release$shared_ext$major' shlibpath_var=LD_LIBRARY_PATH ;; *) dynamic_linker=no ;; esac AC_MSG_RESULT([$dynamic_linker]) test no = "$dynamic_linker" && can_build_shared=no variables_saved_for_relink="PATH $shlibpath_var $runpath_var" if test yes = "$GCC"; then variables_saved_for_relink="$variables_saved_for_relink GCC_EXEC_PREFIX COMPILER_PATH LIBRARY_PATH" fi if test set = "${lt_cv_sys_lib_search_path_spec+set}"; then sys_lib_search_path_spec=$lt_cv_sys_lib_search_path_spec fi if test set = "${lt_cv_sys_lib_dlsearch_path_spec+set}"; then sys_lib_dlsearch_path_spec=$lt_cv_sys_lib_dlsearch_path_spec fi # remember unaugmented sys_lib_dlsearch_path content for libtool script decls... configure_time_dlsearch_path=$sys_lib_dlsearch_path_spec # ... but it needs LT_SYS_LIBRARY_PATH munging for other configure-time code func_munge_path_list sys_lib_dlsearch_path_spec "$LT_SYS_LIBRARY_PATH" # to be used as default LT_SYS_LIBRARY_PATH value in generated libtool configure_time_lt_sys_library_path=$LT_SYS_LIBRARY_PATH _LT_DECL([], [variables_saved_for_relink], [1], [Variables whose values should be saved in libtool wrapper scripts and restored at link time]) _LT_DECL([], [need_lib_prefix], [0], [Do we need the "lib" prefix for modules?]) _LT_DECL([], [need_version], [0], [Do we need a version for libraries?]) _LT_DECL([], [version_type], [0], [Library versioning type]) _LT_DECL([], [runpath_var], [0], [Shared library runtime path variable]) _LT_DECL([], [shlibpath_var], [0],[Shared library path variable]) _LT_DECL([], [shlibpath_overrides_runpath], [0], [Is shlibpath searched before the hard-coded library search path?]) _LT_DECL([], [libname_spec], [1], [Format of library name prefix]) _LT_DECL([], [library_names_spec], [1], [[List of archive names. First name is the real one, the rest are links. The last name is the one that the linker finds with -lNAME]]) _LT_DECL([], [soname_spec], [1], [[The coded name of the library, if different from the real name]]) _LT_DECL([], [install_override_mode], [1], [Permission mode override for installation of shared libraries]) _LT_DECL([], [postinstall_cmds], [2], [Command to use after installation of a shared archive]) _LT_DECL([], [postuninstall_cmds], [2], [Command to use after uninstallation of a shared archive]) _LT_DECL([], [finish_cmds], [2], [Commands used to finish a libtool library installation in a directory]) _LT_DECL([], [finish_eval], [1], [[As "finish_cmds", except a single script fragment to be evaled but not shown]]) _LT_DECL([], [hardcode_into_libs], [0], [Whether we should hardcode library paths into libraries]) _LT_DECL([], [sys_lib_search_path_spec], [2], [Compile-time system search path for libraries]) _LT_DECL([sys_lib_dlsearch_path_spec], [configure_time_dlsearch_path], [2], [Detected run-time system search path for libraries]) _LT_DECL([], [configure_time_lt_sys_library_path], [2], [Explicit LT_SYS_LIBRARY_PATH set during ./configure time]) ])# _LT_SYS_DYNAMIC_LINKER # _LT_PATH_TOOL_PREFIX(TOOL) # -------------------------- # find a file program that can recognize shared library AC_DEFUN([_LT_PATH_TOOL_PREFIX], [m4_require([_LT_DECL_EGREP])dnl AC_MSG_CHECKING([for $1]) AC_CACHE_VAL(lt_cv_path_MAGIC_CMD, [case $MAGIC_CMD in [[\\/*] | ?:[\\/]*]) lt_cv_path_MAGIC_CMD=$MAGIC_CMD # Let the user override the test with a path. ;; *) lt_save_MAGIC_CMD=$MAGIC_CMD lt_save_ifs=$IFS; IFS=$PATH_SEPARATOR dnl $ac_dummy forces splitting on constant user-supplied paths. dnl POSIX.2 word splitting is done only on the output of word expansions, dnl not every word. This closes a longstanding sh security hole. ac_dummy="m4_if([$2], , $PATH, [$2])" for ac_dir in $ac_dummy; do IFS=$lt_save_ifs test -z "$ac_dir" && ac_dir=. if test -f "$ac_dir/$1"; then lt_cv_path_MAGIC_CMD=$ac_dir/"$1" if test -n "$file_magic_test_file"; then case $deplibs_check_method in "file_magic "*) file_magic_regex=`expr "$deplibs_check_method" : "file_magic \(.*\)"` MAGIC_CMD=$lt_cv_path_MAGIC_CMD if eval $file_magic_cmd \$file_magic_test_file 2> /dev/null | $EGREP "$file_magic_regex" > /dev/null; then : else cat <<_LT_EOF 1>&2 *** Warning: the command libtool uses to detect shared libraries, *** $file_magic_cmd, produces output that libtool cannot recognize. *** The result is that libtool may fail to recognize shared libraries *** as such. This will affect the creation of libtool libraries that *** depend on shared libraries, but programs linked with such libtool *** libraries will work regardless of this problem. Nevertheless, you *** may want to report the problem to your system manager and/or to *** bug-libtool@gnu.org _LT_EOF fi ;; esac fi break fi done IFS=$lt_save_ifs MAGIC_CMD=$lt_save_MAGIC_CMD ;; esac]) MAGIC_CMD=$lt_cv_path_MAGIC_CMD if test -n "$MAGIC_CMD"; then AC_MSG_RESULT($MAGIC_CMD) else AC_MSG_RESULT(no) fi _LT_DECL([], [MAGIC_CMD], [0], [Used to examine libraries when file_magic_cmd begins with "file"])dnl ])# _LT_PATH_TOOL_PREFIX # Old name: AU_ALIAS([AC_PATH_TOOL_PREFIX], [_LT_PATH_TOOL_PREFIX]) dnl aclocal-1.4 backwards compatibility: dnl AC_DEFUN([AC_PATH_TOOL_PREFIX], []) # _LT_PATH_MAGIC # -------------- # find a file program that can recognize a shared library m4_defun([_LT_PATH_MAGIC], [_LT_PATH_TOOL_PREFIX(${ac_tool_prefix}file, /usr/bin$PATH_SEPARATOR$PATH) if test -z "$lt_cv_path_MAGIC_CMD"; then if test -n "$ac_tool_prefix"; then _LT_PATH_TOOL_PREFIX(file, /usr/bin$PATH_SEPARATOR$PATH) else MAGIC_CMD=: fi fi ])# _LT_PATH_MAGIC # LT_PATH_LD # ---------- # find the pathname to the GNU or non-GNU linker AC_DEFUN([LT_PATH_LD], [AC_REQUIRE([AC_PROG_CC])dnl AC_REQUIRE([AC_CANONICAL_HOST])dnl AC_REQUIRE([AC_CANONICAL_BUILD])dnl m4_require([_LT_DECL_SED])dnl m4_require([_LT_DECL_EGREP])dnl m4_require([_LT_PROG_ECHO_BACKSLASH])dnl AC_ARG_WITH([gnu-ld], [AS_HELP_STRING([--with-gnu-ld], [assume the C compiler uses GNU ld @<:@default=no@:>@])], [test no = "$withval" || with_gnu_ld=yes], [with_gnu_ld=no])dnl ac_prog=ld if test yes = "$GCC"; then # Check if gcc -print-prog-name=ld gives a path. AC_MSG_CHECKING([for ld used by $CC]) case $host in *-*-mingw*) # gcc leaves a trailing carriage return, which upsets mingw ac_prog=`($CC -print-prog-name=ld) 2>&5 | tr -d '\015'` ;; *) ac_prog=`($CC -print-prog-name=ld) 2>&5` ;; esac case $ac_prog in # Accept absolute paths. [[\\/]]* | ?:[[\\/]]*) re_direlt='/[[^/]][[^/]]*/\.\./' # Canonicalize the pathname of ld ac_prog=`$ECHO "$ac_prog"| $SED 's%\\\\%/%g'` while $ECHO "$ac_prog" | $GREP "$re_direlt" > /dev/null 2>&1; do ac_prog=`$ECHO $ac_prog| $SED "s%$re_direlt%/%"` done test -z "$LD" && LD=$ac_prog ;; "") # If it fails, then pretend we aren't using GCC. ac_prog=ld ;; *) # If it is relative, then search for the first ld in PATH. with_gnu_ld=unknown ;; esac elif test yes = "$with_gnu_ld"; then AC_MSG_CHECKING([for GNU ld]) else AC_MSG_CHECKING([for non-GNU ld]) fi AC_CACHE_VAL(lt_cv_path_LD, [if test -z "$LD"; then lt_save_ifs=$IFS; IFS=$PATH_SEPARATOR for ac_dir in $PATH; do IFS=$lt_save_ifs test -z "$ac_dir" && ac_dir=. if test -f "$ac_dir/$ac_prog" || test -f "$ac_dir/$ac_prog$ac_exeext"; then lt_cv_path_LD=$ac_dir/$ac_prog # Check to see if the program is GNU ld. I'd rather use --version, # but apparently some variants of GNU ld only accept -v. # Break only if it was the GNU/non-GNU ld that we prefer. case `"$lt_cv_path_LD" -v 2>&1 &1 conftest.i cat conftest.i conftest.i >conftest2.i : ${lt_DD:=$DD} AC_PATH_PROGS_FEATURE_CHECK([lt_DD], [dd], [if "$ac_path_lt_DD" bs=32 count=1 conftest.out 2>/dev/null; then cmp -s conftest.i conftest.out \ && ac_cv_path_lt_DD="$ac_path_lt_DD" ac_path_lt_DD_found=: fi]) rm -f conftest.i conftest2.i conftest.out]) ])# _LT_PATH_DD # _LT_CMD_TRUNCATE # ---------------- # find command to truncate a binary pipe m4_defun([_LT_CMD_TRUNCATE], [m4_require([_LT_PATH_DD]) AC_CACHE_CHECK([how to truncate binary pipes], [lt_cv_truncate_bin], [printf 0123456789abcdef0123456789abcdef >conftest.i cat conftest.i conftest.i >conftest2.i lt_cv_truncate_bin= if "$ac_cv_path_lt_DD" bs=32 count=1 conftest.out 2>/dev/null; then cmp -s conftest.i conftest.out \ && lt_cv_truncate_bin="$ac_cv_path_lt_DD bs=4096 count=1" fi rm -f conftest.i conftest2.i conftest.out test -z "$lt_cv_truncate_bin" && lt_cv_truncate_bin="$SED -e 4q"]) _LT_DECL([lt_truncate_bin], [lt_cv_truncate_bin], [1], [Command to truncate a binary pipe]) ])# _LT_CMD_TRUNCATE # _LT_CHECK_MAGIC_METHOD # ---------------------- # how to check for library dependencies # -- PORTME fill in with the dynamic library characteristics m4_defun([_LT_CHECK_MAGIC_METHOD], [m4_require([_LT_DECL_EGREP]) m4_require([_LT_DECL_OBJDUMP]) AC_CACHE_CHECK([how to recognize dependent libraries], lt_cv_deplibs_check_method, [lt_cv_file_magic_cmd='$MAGIC_CMD' lt_cv_file_magic_test_file= lt_cv_deplibs_check_method='unknown' # Need to set the preceding variable on all platforms that support # interlibrary dependencies. # 'none' -- dependencies not supported. # 'unknown' -- same as none, but documents that we really don't know. # 'pass_all' -- all dependencies passed with no checks. # 'test_compile' -- check by making test program. # 'file_magic [[regex]]' -- check by looking for files in library path # that responds to the $file_magic_cmd with a given extended regex. # If you have 'file' or equivalent on your system and you're not sure # whether 'pass_all' will *always* work, you probably want this one. case $host_os in aix[[4-9]]*) lt_cv_deplibs_check_method=pass_all ;; beos*) lt_cv_deplibs_check_method=pass_all ;; bsdi[[45]]*) lt_cv_deplibs_check_method='file_magic ELF [[0-9]][[0-9]]*-bit [[ML]]SB (shared object|dynamic lib)' lt_cv_file_magic_cmd='/usr/bin/file -L' lt_cv_file_magic_test_file=/shlib/libc.so ;; cygwin*) # func_win32_libid is a shell function defined in ltmain.sh lt_cv_deplibs_check_method='file_magic ^x86 archive import|^x86 DLL' lt_cv_file_magic_cmd='func_win32_libid' ;; mingw* | pw32*) # Base MSYS/MinGW do not provide the 'file' command needed by # func_win32_libid shell function, so use a weaker test based on 'objdump', # unless we find 'file', for example because we are cross-compiling. if ( file / ) >/dev/null 2>&1; then lt_cv_deplibs_check_method='file_magic ^x86 archive import|^x86 DLL' lt_cv_file_magic_cmd='func_win32_libid' else # Keep this pattern in sync with the one in func_win32_libid. lt_cv_deplibs_check_method='file_magic file format (pei*-i386(.*architecture: i386)?|pe-arm-wince|pe-x86-64)' lt_cv_file_magic_cmd='$OBJDUMP -f' fi ;; cegcc*) # use the weaker test based on 'objdump'. See mingw*. lt_cv_deplibs_check_method='file_magic file format pe-arm-.*little(.*architecture: arm)?' lt_cv_file_magic_cmd='$OBJDUMP -f' ;; darwin* | rhapsody*) lt_cv_deplibs_check_method=pass_all ;; freebsd* | dragonfly*) if echo __ELF__ | $CC -E - | $GREP __ELF__ > /dev/null; then case $host_cpu in i*86 ) # Not sure whether the presence of OpenBSD here was a mistake. # Let's accept both of them until this is cleared up. lt_cv_deplibs_check_method='file_magic (FreeBSD|OpenBSD|DragonFly)/i[[3-9]]86 (compact )?demand paged shared library' lt_cv_file_magic_cmd=/usr/bin/file lt_cv_file_magic_test_file=`echo /usr/lib/libc.so.*` ;; esac else lt_cv_deplibs_check_method=pass_all fi ;; haiku*) lt_cv_deplibs_check_method=pass_all ;; hpux10.20* | hpux11*) lt_cv_file_magic_cmd=/usr/bin/file case $host_cpu in ia64*) lt_cv_deplibs_check_method='file_magic (s[[0-9]][[0-9]][[0-9]]|ELF-[[0-9]][[0-9]]) shared object file - IA64' lt_cv_file_magic_test_file=/usr/lib/hpux32/libc.so ;; hppa*64*) [lt_cv_deplibs_check_method='file_magic (s[0-9][0-9][0-9]|ELF[ -][0-9][0-9])(-bit)?( [LM]SB)? shared object( file)?[, -]* PA-RISC [0-9]\.[0-9]'] lt_cv_file_magic_test_file=/usr/lib/pa20_64/libc.sl ;; *) lt_cv_deplibs_check_method='file_magic (s[[0-9]][[0-9]][[0-9]]|PA-RISC[[0-9]]\.[[0-9]]) shared library' lt_cv_file_magic_test_file=/usr/lib/libc.sl ;; esac ;; interix[[3-9]]*) # PIC code is broken on Interix 3.x, that's why |\.a not |_pic\.a here lt_cv_deplibs_check_method='match_pattern /lib[[^/]]+(\.so|\.a)$' ;; irix5* | irix6* | nonstopux*) case $LD in *-32|*"-32 ") libmagic=32-bit;; *-n32|*"-n32 ") libmagic=N32;; *-64|*"-64 ") libmagic=64-bit;; *) libmagic=never-match;; esac lt_cv_deplibs_check_method=pass_all ;; # This must be glibc/ELF. linux* | k*bsd*-gnu | kopensolaris*-gnu | gnu*) lt_cv_deplibs_check_method=pass_all ;; netbsd* | netbsdelf*-gnu) if echo __ELF__ | $CC -E - | $GREP __ELF__ > /dev/null; then lt_cv_deplibs_check_method='match_pattern /lib[[^/]]+(\.so\.[[0-9]]+\.[[0-9]]+|_pic\.a)$' else lt_cv_deplibs_check_method='match_pattern /lib[[^/]]+(\.so|_pic\.a)$' fi ;; newos6*) lt_cv_deplibs_check_method='file_magic ELF [[0-9]][[0-9]]*-bit [[ML]]SB (executable|dynamic lib)' lt_cv_file_magic_cmd=/usr/bin/file lt_cv_file_magic_test_file=/usr/lib/libnls.so ;; *nto* | *qnx*) lt_cv_deplibs_check_method=pass_all ;; openbsd* | bitrig*) if test -z "`echo __ELF__ | $CC -E - | $GREP __ELF__`"; then lt_cv_deplibs_check_method='match_pattern /lib[[^/]]+(\.so\.[[0-9]]+\.[[0-9]]+|\.so|_pic\.a)$' else lt_cv_deplibs_check_method='match_pattern /lib[[^/]]+(\.so\.[[0-9]]+\.[[0-9]]+|_pic\.a)$' fi ;; osf3* | osf4* | osf5*) lt_cv_deplibs_check_method=pass_all ;; rdos*) lt_cv_deplibs_check_method=pass_all ;; solaris*) lt_cv_deplibs_check_method=pass_all ;; sysv5* | sco3.2v5* | sco5v6* | unixware* | OpenUNIX* | sysv4*uw2*) lt_cv_deplibs_check_method=pass_all ;; sysv4 | sysv4.3*) case $host_vendor in motorola) lt_cv_deplibs_check_method='file_magic ELF [[0-9]][[0-9]]*-bit [[ML]]SB (shared object|dynamic lib) M[[0-9]][[0-9]]* Version [[0-9]]' lt_cv_file_magic_test_file=`echo /usr/lib/libc.so*` ;; ncr) lt_cv_deplibs_check_method=pass_all ;; sequent) lt_cv_file_magic_cmd='/bin/file' lt_cv_deplibs_check_method='file_magic ELF [[0-9]][[0-9]]*-bit [[LM]]SB (shared object|dynamic lib )' ;; sni) lt_cv_file_magic_cmd='/bin/file' lt_cv_deplibs_check_method="file_magic ELF [[0-9]][[0-9]]*-bit [[LM]]SB dynamic lib" lt_cv_file_magic_test_file=/lib/libc.so ;; siemens) lt_cv_deplibs_check_method=pass_all ;; pc) lt_cv_deplibs_check_method=pass_all ;; esac ;; tpf*) lt_cv_deplibs_check_method=pass_all ;; os2*) lt_cv_deplibs_check_method=pass_all ;; esac ]) file_magic_glob= want_nocaseglob=no if test "$build" = "$host"; then case $host_os in mingw* | pw32*) if ( shopt | grep nocaseglob ) >/dev/null 2>&1; then want_nocaseglob=yes else file_magic_glob=`echo aAbBcCdDeEfFgGhHiIjJkKlLmMnNoOpPqQrRsStTuUvVwWxXyYzZ | $SED -e "s/\(..\)/s\/[[\1]]\/[[\1]]\/g;/g"` fi ;; esac fi file_magic_cmd=$lt_cv_file_magic_cmd deplibs_check_method=$lt_cv_deplibs_check_method test -z "$deplibs_check_method" && deplibs_check_method=unknown _LT_DECL([], [deplibs_check_method], [1], [Method to check whether dependent libraries are shared objects]) _LT_DECL([], [file_magic_cmd], [1], [Command to use when deplibs_check_method = "file_magic"]) _LT_DECL([], [file_magic_glob], [1], [How to find potential files when deplibs_check_method = "file_magic"]) _LT_DECL([], [want_nocaseglob], [1], [Find potential files using nocaseglob when deplibs_check_method = "file_magic"]) ])# _LT_CHECK_MAGIC_METHOD # LT_PATH_NM # ---------- # find the pathname to a BSD- or MS-compatible name lister AC_DEFUN([LT_PATH_NM], [AC_REQUIRE([AC_PROG_CC])dnl AC_CACHE_CHECK([for BSD- or MS-compatible name lister (nm)], lt_cv_path_NM, [if test -n "$NM"; then # Let the user override the test. lt_cv_path_NM=$NM else lt_nm_to_check=${ac_tool_prefix}nm if test -n "$ac_tool_prefix" && test "$build" = "$host"; then lt_nm_to_check="$lt_nm_to_check nm" fi for lt_tmp_nm in $lt_nm_to_check; do lt_save_ifs=$IFS; IFS=$PATH_SEPARATOR for ac_dir in $PATH /usr/ccs/bin/elf /usr/ccs/bin /usr/ucb /bin; do IFS=$lt_save_ifs test -z "$ac_dir" && ac_dir=. tmp_nm=$ac_dir/$lt_tmp_nm if test -f "$tmp_nm" || test -f "$tmp_nm$ac_exeext"; then # Check to see if the nm accepts a BSD-compat flag. # Adding the 'sed 1q' prevents false positives on HP-UX, which says: # nm: unknown option "B" ignored # Tru64's nm complains that /dev/null is an invalid object file # MSYS converts /dev/null to NUL, MinGW nm treats NUL as empty case $build_os in mingw*) lt_bad_file=conftest.nm/nofile ;; *) lt_bad_file=/dev/null ;; esac case `"$tmp_nm" -B $lt_bad_file 2>&1 | sed '1q'` in *$lt_bad_file* | *'Invalid file or object type'*) lt_cv_path_NM="$tmp_nm -B" break 2 ;; *) case `"$tmp_nm" -p /dev/null 2>&1 | sed '1q'` in */dev/null*) lt_cv_path_NM="$tmp_nm -p" break 2 ;; *) lt_cv_path_NM=${lt_cv_path_NM="$tmp_nm"} # keep the first match, but continue # so that we can try to find one that supports BSD flags ;; esac ;; esac fi done IFS=$lt_save_ifs done : ${lt_cv_path_NM=no} fi]) if test no != "$lt_cv_path_NM"; then NM=$lt_cv_path_NM else # Didn't find any BSD compatible name lister, look for dumpbin. if test -n "$DUMPBIN"; then : # Let the user override the test. else AC_CHECK_TOOLS(DUMPBIN, [dumpbin "link -dump"], :) case `$DUMPBIN -symbols -headers /dev/null 2>&1 | sed '1q'` in *COFF*) DUMPBIN="$DUMPBIN -symbols -headers" ;; *) DUMPBIN=: ;; esac fi AC_SUBST([DUMPBIN]) if test : != "$DUMPBIN"; then NM=$DUMPBIN fi fi test -z "$NM" && NM=nm AC_SUBST([NM]) _LT_DECL([], [NM], [1], [A BSD- or MS-compatible name lister])dnl AC_CACHE_CHECK([the name lister ($NM) interface], [lt_cv_nm_interface], [lt_cv_nm_interface="BSD nm" echo "int some_variable = 0;" > conftest.$ac_ext (eval echo "\"\$as_me:$LINENO: $ac_compile\"" >&AS_MESSAGE_LOG_FD) (eval "$ac_compile" 2>conftest.err) cat conftest.err >&AS_MESSAGE_LOG_FD (eval echo "\"\$as_me:$LINENO: $NM \\\"conftest.$ac_objext\\\"\"" >&AS_MESSAGE_LOG_FD) (eval "$NM \"conftest.$ac_objext\"" 2>conftest.err > conftest.out) cat conftest.err >&AS_MESSAGE_LOG_FD (eval echo "\"\$as_me:$LINENO: output\"" >&AS_MESSAGE_LOG_FD) cat conftest.out >&AS_MESSAGE_LOG_FD if $GREP 'External.*some_variable' conftest.out > /dev/null; then lt_cv_nm_interface="MS dumpbin" fi rm -f conftest*]) ])# LT_PATH_NM # Old names: AU_ALIAS([AM_PROG_NM], [LT_PATH_NM]) AU_ALIAS([AC_PROG_NM], [LT_PATH_NM]) dnl aclocal-1.4 backwards compatibility: dnl AC_DEFUN([AM_PROG_NM], []) dnl AC_DEFUN([AC_PROG_NM], []) # _LT_CHECK_SHAREDLIB_FROM_LINKLIB # -------------------------------- # how to determine the name of the shared library # associated with a specific link library. # -- PORTME fill in with the dynamic library characteristics m4_defun([_LT_CHECK_SHAREDLIB_FROM_LINKLIB], [m4_require([_LT_DECL_EGREP]) m4_require([_LT_DECL_OBJDUMP]) m4_require([_LT_DECL_DLLTOOL]) AC_CACHE_CHECK([how to associate runtime and link libraries], lt_cv_sharedlib_from_linklib_cmd, [lt_cv_sharedlib_from_linklib_cmd='unknown' case $host_os in cygwin* | mingw* | pw32* | cegcc*) # two different shell functions defined in ltmain.sh; # decide which one to use based on capabilities of $DLLTOOL case `$DLLTOOL --help 2>&1` in *--identify-strict*) lt_cv_sharedlib_from_linklib_cmd=func_cygming_dll_for_implib ;; *) lt_cv_sharedlib_from_linklib_cmd=func_cygming_dll_for_implib_fallback ;; esac ;; *) # fallback: assume linklib IS sharedlib lt_cv_sharedlib_from_linklib_cmd=$ECHO ;; esac ]) sharedlib_from_linklib_cmd=$lt_cv_sharedlib_from_linklib_cmd test -z "$sharedlib_from_linklib_cmd" && sharedlib_from_linklib_cmd=$ECHO _LT_DECL([], [sharedlib_from_linklib_cmd], [1], [Command to associate shared and link libraries]) ])# _LT_CHECK_SHAREDLIB_FROM_LINKLIB # _LT_PATH_MANIFEST_TOOL # ---------------------- # locate the manifest tool m4_defun([_LT_PATH_MANIFEST_TOOL], [AC_CHECK_TOOL(MANIFEST_TOOL, mt, :) test -z "$MANIFEST_TOOL" && MANIFEST_TOOL=mt AC_CACHE_CHECK([if $MANIFEST_TOOL is a manifest tool], [lt_cv_path_mainfest_tool], [lt_cv_path_mainfest_tool=no echo "$as_me:$LINENO: $MANIFEST_TOOL '-?'" >&AS_MESSAGE_LOG_FD $MANIFEST_TOOL '-?' 2>conftest.err > conftest.out cat conftest.err >&AS_MESSAGE_LOG_FD if $GREP 'Manifest Tool' conftest.out > /dev/null; then lt_cv_path_mainfest_tool=yes fi rm -f conftest*]) if test yes != "$lt_cv_path_mainfest_tool"; then MANIFEST_TOOL=: fi _LT_DECL([], [MANIFEST_TOOL], [1], [Manifest tool])dnl ])# _LT_PATH_MANIFEST_TOOL # _LT_DLL_DEF_P([FILE]) # --------------------- # True iff FILE is a Windows DLL '.def' file. # Keep in sync with func_dll_def_p in the libtool script AC_DEFUN([_LT_DLL_DEF_P], [dnl test DEF = "`$SED -n dnl -e '\''s/^[[ ]]*//'\'' dnl Strip leading whitespace -e '\''/^\(;.*\)*$/d'\'' dnl Delete empty lines and comments -e '\''s/^\(EXPORTS\|LIBRARY\)\([[ ]].*\)*$/DEF/p'\'' dnl -e q dnl Only consider the first "real" line $1`" dnl ])# _LT_DLL_DEF_P # LT_LIB_M # -------- # check for math library AC_DEFUN([LT_LIB_M], [AC_REQUIRE([AC_CANONICAL_HOST])dnl LIBM= case $host in *-*-beos* | *-*-cegcc* | *-*-cygwin* | *-*-haiku* | *-*-pw32* | *-*-darwin*) # These system don't have libm, or don't need it ;; *-ncr-sysv4.3*) AC_CHECK_LIB(mw, _mwvalidcheckl, LIBM=-lmw) AC_CHECK_LIB(m, cos, LIBM="$LIBM -lm") ;; *) AC_CHECK_LIB(m, cos, LIBM=-lm) ;; esac AC_SUBST([LIBM]) ])# LT_LIB_M # Old name: AU_ALIAS([AC_CHECK_LIBM], [LT_LIB_M]) dnl aclocal-1.4 backwards compatibility: dnl AC_DEFUN([AC_CHECK_LIBM], []) # _LT_COMPILER_NO_RTTI([TAGNAME]) # ------------------------------- m4_defun([_LT_COMPILER_NO_RTTI], [m4_require([_LT_TAG_COMPILER])dnl _LT_TAGVAR(lt_prog_compiler_no_builtin_flag, $1)= if test yes = "$GCC"; then case $cc_basename in nvcc*) _LT_TAGVAR(lt_prog_compiler_no_builtin_flag, $1)=' -Xcompiler -fno-builtin' ;; *) _LT_TAGVAR(lt_prog_compiler_no_builtin_flag, $1)=' -fno-builtin' ;; esac _LT_COMPILER_OPTION([if $compiler supports -fno-rtti -fno-exceptions], lt_cv_prog_compiler_rtti_exceptions, [-fno-rtti -fno-exceptions], [], [_LT_TAGVAR(lt_prog_compiler_no_builtin_flag, $1)="$_LT_TAGVAR(lt_prog_compiler_no_builtin_flag, $1) -fno-rtti -fno-exceptions"]) fi _LT_TAGDECL([no_builtin_flag], [lt_prog_compiler_no_builtin_flag], [1], [Compiler flag to turn off builtin functions]) ])# _LT_COMPILER_NO_RTTI # _LT_CMD_GLOBAL_SYMBOLS # ---------------------- m4_defun([_LT_CMD_GLOBAL_SYMBOLS], [AC_REQUIRE([AC_CANONICAL_HOST])dnl AC_REQUIRE([AC_PROG_CC])dnl AC_REQUIRE([AC_PROG_AWK])dnl AC_REQUIRE([LT_PATH_NM])dnl AC_REQUIRE([LT_PATH_LD])dnl m4_require([_LT_DECL_SED])dnl m4_require([_LT_DECL_EGREP])dnl m4_require([_LT_TAG_COMPILER])dnl # Check for command to grab the raw symbol name followed by C symbol from nm. AC_MSG_CHECKING([command to parse $NM output from $compiler object]) AC_CACHE_VAL([lt_cv_sys_global_symbol_pipe], [ # These are sane defaults that work on at least a few old systems. # [They come from Ultrix. What could be older than Ultrix?!! ;)] # Character class describing NM global symbol codes. symcode='[[BCDEGRST]]' # Regexp to match symbols that can be accessed directly from C. sympat='\([[_A-Za-z]][[_A-Za-z0-9]]*\)' # Define system-specific variables. case $host_os in aix*) symcode='[[BCDT]]' ;; cygwin* | mingw* | pw32* | cegcc*) symcode='[[ABCDGISTW]]' ;; hpux*) if test ia64 = "$host_cpu"; then symcode='[[ABCDEGRST]]' fi ;; irix* | nonstopux*) symcode='[[BCDEGRST]]' ;; osf*) symcode='[[BCDEGQRST]]' ;; solaris*) symcode='[[BDRT]]' ;; sco3.2v5*) symcode='[[DT]]' ;; sysv4.2uw2*) symcode='[[DT]]' ;; sysv5* | sco5v6* | unixware* | OpenUNIX*) symcode='[[ABDT]]' ;; sysv4) symcode='[[DFNSTU]]' ;; esac # If we're using GNU nm, then use its standard symbol codes. case `$NM -V 2>&1` in *GNU* | *'with BFD'*) symcode='[[ABCDGIRSTW]]' ;; esac if test "$lt_cv_nm_interface" = "MS dumpbin"; then # Gets list of data symbols to import. lt_cv_sys_global_symbol_to_import="sed -n -e 's/^I .* \(.*\)$/\1/p'" # Adjust the below global symbol transforms to fixup imported variables. lt_cdecl_hook=" -e 's/^I .* \(.*\)$/extern __declspec(dllimport) char \1;/p'" lt_c_name_hook=" -e 's/^I .* \(.*\)$/ {\"\1\", (void *) 0},/p'" lt_c_name_lib_hook="\ -e 's/^I .* \(lib.*\)$/ {\"\1\", (void *) 0},/p'\ -e 's/^I .* \(.*\)$/ {\"lib\1\", (void *) 0},/p'" else # Disable hooks by default. lt_cv_sys_global_symbol_to_import= lt_cdecl_hook= lt_c_name_hook= lt_c_name_lib_hook= fi # Transform an extracted symbol line into a proper C declaration. # Some systems (esp. on ia64) link data and code symbols differently, # so use this general approach. lt_cv_sys_global_symbol_to_cdecl="sed -n"\ $lt_cdecl_hook\ " -e 's/^T .* \(.*\)$/extern int \1();/p'"\ " -e 's/^$symcode$symcode* .* \(.*\)$/extern char \1;/p'" # Transform an extracted symbol line into symbol name and symbol address lt_cv_sys_global_symbol_to_c_name_address="sed -n"\ $lt_c_name_hook\ " -e 's/^: \(.*\) .*$/ {\"\1\", (void *) 0},/p'"\ " -e 's/^$symcode$symcode* .* \(.*\)$/ {\"\1\", (void *) \&\1},/p'" # Transform an extracted symbol line into symbol name with lib prefix and # symbol address. lt_cv_sys_global_symbol_to_c_name_address_lib_prefix="sed -n"\ $lt_c_name_lib_hook\ " -e 's/^: \(.*\) .*$/ {\"\1\", (void *) 0},/p'"\ " -e 's/^$symcode$symcode* .* \(lib.*\)$/ {\"\1\", (void *) \&\1},/p'"\ " -e 's/^$symcode$symcode* .* \(.*\)$/ {\"lib\1\", (void *) \&\1},/p'" # Handle CRLF in mingw tool chain opt_cr= case $build_os in mingw*) opt_cr=`$ECHO 'x\{0,1\}' | tr x '\015'` # option cr in regexp ;; esac # Try without a prefix underscore, then with it. for ac_symprfx in "" "_"; do # Transform symcode, sympat, and symprfx into a raw symbol and a C symbol. symxfrm="\\1 $ac_symprfx\\2 \\2" # Write the raw and C identifiers. if test "$lt_cv_nm_interface" = "MS dumpbin"; then # Fake it for dumpbin and say T for any non-static function, # D for any global variable and I for any imported variable. # Also find C++ and __fastcall symbols from MSVC++, # which start with @ or ?. lt_cv_sys_global_symbol_pipe="$AWK ['"\ " {last_section=section; section=\$ 3};"\ " /^COFF SYMBOL TABLE/{for(i in hide) delete hide[i]};"\ " /Section length .*#relocs.*(pick any)/{hide[last_section]=1};"\ " /^ *Symbol name *: /{split(\$ 0,sn,\":\"); si=substr(sn[2],2)};"\ " /^ *Type *: code/{print \"T\",si,substr(si,length(prfx))};"\ " /^ *Type *: data/{print \"I\",si,substr(si,length(prfx))};"\ " \$ 0!~/External *\|/{next};"\ " / 0+ UNDEF /{next}; / UNDEF \([^|]\)*()/{next};"\ " {if(hide[section]) next};"\ " {f=\"D\"}; \$ 0~/\(\).*\|/{f=\"T\"};"\ " {split(\$ 0,a,/\||\r/); split(a[2],s)};"\ " s[1]~/^[@?]/{print f,s[1],s[1]; next};"\ " s[1]~prfx {split(s[1],t,\"@\"); print f,t[1],substr(t[1],length(prfx))}"\ " ' prfx=^$ac_symprfx]" else lt_cv_sys_global_symbol_pipe="sed -n -e 's/^.*[[ ]]\($symcode$symcode*\)[[ ]][[ ]]*$ac_symprfx$sympat$opt_cr$/$symxfrm/p'" fi lt_cv_sys_global_symbol_pipe="$lt_cv_sys_global_symbol_pipe | sed '/ __gnu_lto/d'" # Check to see that the pipe works correctly. pipe_works=no rm -f conftest* cat > conftest.$ac_ext <<_LT_EOF #ifdef __cplusplus extern "C" { #endif char nm_test_var; void nm_test_func(void); void nm_test_func(void){} #ifdef __cplusplus } #endif int main(){nm_test_var='a';nm_test_func();return(0);} _LT_EOF if AC_TRY_EVAL(ac_compile); then # Now try to grab the symbols. nlist=conftest.nm if AC_TRY_EVAL(NM conftest.$ac_objext \| "$lt_cv_sys_global_symbol_pipe" \> $nlist) && test -s "$nlist"; then # Try sorting and uniquifying the output. if sort "$nlist" | uniq > "$nlist"T; then mv -f "$nlist"T "$nlist" else rm -f "$nlist"T fi # Make sure that we snagged all the symbols we need. if $GREP ' nm_test_var$' "$nlist" >/dev/null; then if $GREP ' nm_test_func$' "$nlist" >/dev/null; then cat <<_LT_EOF > conftest.$ac_ext /* Keep this code in sync between libtool.m4, ltmain, lt_system.h, and tests. */ #if defined _WIN32 || defined __CYGWIN__ || defined _WIN32_WCE /* DATA imports from DLLs on WIN32 can't be const, because runtime relocations are performed -- see ld's documentation on pseudo-relocs. */ # define LT@&t@_DLSYM_CONST #elif defined __osf__ /* This system does not cope well with relocations in const data. */ # define LT@&t@_DLSYM_CONST #else # define LT@&t@_DLSYM_CONST const #endif #ifdef __cplusplus extern "C" { #endif _LT_EOF # Now generate the symbol file. eval "$lt_cv_sys_global_symbol_to_cdecl"' < "$nlist" | $GREP -v main >> conftest.$ac_ext' cat <<_LT_EOF >> conftest.$ac_ext /* The mapping between symbol names and symbols. */ LT@&t@_DLSYM_CONST struct { const char *name; void *address; } lt__PROGRAM__LTX_preloaded_symbols[[]] = { { "@PROGRAM@", (void *) 0 }, _LT_EOF $SED "s/^$symcode$symcode* .* \(.*\)$/ {\"\1\", (void *) \&\1},/" < "$nlist" | $GREP -v main >> conftest.$ac_ext cat <<\_LT_EOF >> conftest.$ac_ext {0, (void *) 0} }; /* This works around a problem in FreeBSD linker */ #ifdef FREEBSD_WORKAROUND static const void *lt_preloaded_setup() { return lt__PROGRAM__LTX_preloaded_symbols; } #endif #ifdef __cplusplus } #endif _LT_EOF # Now try linking the two files. mv conftest.$ac_objext conftstm.$ac_objext lt_globsym_save_LIBS=$LIBS lt_globsym_save_CFLAGS=$CFLAGS LIBS=conftstm.$ac_objext CFLAGS="$CFLAGS$_LT_TAGVAR(lt_prog_compiler_no_builtin_flag, $1)" if AC_TRY_EVAL(ac_link) && test -s conftest$ac_exeext; then pipe_works=yes fi LIBS=$lt_globsym_save_LIBS CFLAGS=$lt_globsym_save_CFLAGS else echo "cannot find nm_test_func in $nlist" >&AS_MESSAGE_LOG_FD fi else echo "cannot find nm_test_var in $nlist" >&AS_MESSAGE_LOG_FD fi else echo "cannot run $lt_cv_sys_global_symbol_pipe" >&AS_MESSAGE_LOG_FD fi else echo "$progname: failed program was:" >&AS_MESSAGE_LOG_FD cat conftest.$ac_ext >&5 fi rm -rf conftest* conftst* # Do not use the global_symbol_pipe unless it works. if test yes = "$pipe_works"; then break else lt_cv_sys_global_symbol_pipe= fi done ]) if test -z "$lt_cv_sys_global_symbol_pipe"; then lt_cv_sys_global_symbol_to_cdecl= fi if test -z "$lt_cv_sys_global_symbol_pipe$lt_cv_sys_global_symbol_to_cdecl"; then AC_MSG_RESULT(failed) else AC_MSG_RESULT(ok) fi # Response file support. if test "$lt_cv_nm_interface" = "MS dumpbin"; then nm_file_list_spec='@' elif $NM --help 2>/dev/null | grep '[[@]]FILE' >/dev/null; then nm_file_list_spec='@' fi _LT_DECL([global_symbol_pipe], [lt_cv_sys_global_symbol_pipe], [1], [Take the output of nm and produce a listing of raw symbols and C names]) _LT_DECL([global_symbol_to_cdecl], [lt_cv_sys_global_symbol_to_cdecl], [1], [Transform the output of nm in a proper C declaration]) _LT_DECL([global_symbol_to_import], [lt_cv_sys_global_symbol_to_import], [1], [Transform the output of nm into a list of symbols to manually relocate]) _LT_DECL([global_symbol_to_c_name_address], [lt_cv_sys_global_symbol_to_c_name_address], [1], [Transform the output of nm in a C name address pair]) _LT_DECL([global_symbol_to_c_name_address_lib_prefix], [lt_cv_sys_global_symbol_to_c_name_address_lib_prefix], [1], [Transform the output of nm in a C name address pair when lib prefix is needed]) _LT_DECL([nm_interface], [lt_cv_nm_interface], [1], [The name lister interface]) _LT_DECL([], [nm_file_list_spec], [1], [Specify filename containing input files for $NM]) ]) # _LT_CMD_GLOBAL_SYMBOLS # _LT_COMPILER_PIC([TAGNAME]) # --------------------------- m4_defun([_LT_COMPILER_PIC], [m4_require([_LT_TAG_COMPILER])dnl _LT_TAGVAR(lt_prog_compiler_wl, $1)= _LT_TAGVAR(lt_prog_compiler_pic, $1)= _LT_TAGVAR(lt_prog_compiler_static, $1)= m4_if([$1], [CXX], [ # C++ specific cases for pic, static, wl, etc. if test yes = "$GXX"; then _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,' _LT_TAGVAR(lt_prog_compiler_static, $1)='-static' case $host_os in aix*) # All AIX code is PIC. if test ia64 = "$host_cpu"; then # AIX 5 now supports IA64 processor _LT_TAGVAR(lt_prog_compiler_static, $1)='-Bstatic' fi _LT_TAGVAR(lt_prog_compiler_pic, $1)='-fPIC' ;; amigaos*) case $host_cpu in powerpc) # see comment about AmigaOS4 .so support _LT_TAGVAR(lt_prog_compiler_pic, $1)='-fPIC' ;; m68k) # FIXME: we need at least 68020 code to build shared libraries, but # adding the '-m68020' flag to GCC prevents building anything better, # like '-m68040'. _LT_TAGVAR(lt_prog_compiler_pic, $1)='-m68020 -resident32 -malways-restore-a4' ;; esac ;; beos* | irix5* | irix6* | nonstopux* | osf3* | osf4* | osf5*) # PIC is the default for these OSes. ;; mingw* | cygwin* | os2* | pw32* | cegcc*) # This hack is so that the source file can tell whether it is being # built for inclusion in a dll (and should export symbols for example). # Although the cygwin gcc ignores -fPIC, still need this for old-style # (--disable-auto-import) libraries m4_if([$1], [GCJ], [], [_LT_TAGVAR(lt_prog_compiler_pic, $1)='-DDLL_EXPORT']) case $host_os in os2*) _LT_TAGVAR(lt_prog_compiler_static, $1)='$wl-static' ;; esac ;; darwin* | rhapsody*) # PIC is the default on this platform # Common symbols not allowed in MH_DYLIB files _LT_TAGVAR(lt_prog_compiler_pic, $1)='-fno-common' ;; *djgpp*) # DJGPP does not support shared libraries at all _LT_TAGVAR(lt_prog_compiler_pic, $1)= ;; haiku*) # PIC is the default for Haiku. # The "-static" flag exists, but is broken. _LT_TAGVAR(lt_prog_compiler_static, $1)= ;; interix[[3-9]]*) # Interix 3.x gcc -fpic/-fPIC options generate broken code. # Instead, we relocate shared libraries at runtime. ;; sysv4*MP*) if test -d /usr/nec; then _LT_TAGVAR(lt_prog_compiler_pic, $1)=-Kconform_pic fi ;; hpux*) # PIC is the default for 64-bit PA HP-UX, but not for 32-bit # PA HP-UX. On IA64 HP-UX, PIC is the default but the pic flag # sets the default TLS model and affects inlining. case $host_cpu in hppa*64*) ;; *) _LT_TAGVAR(lt_prog_compiler_pic, $1)='-fPIC' ;; esac ;; *qnx* | *nto*) # QNX uses GNU C++, but need to define -shared option too, otherwise # it will coredump. _LT_TAGVAR(lt_prog_compiler_pic, $1)='-fPIC -shared' ;; *) _LT_TAGVAR(lt_prog_compiler_pic, $1)='-fPIC' ;; esac else case $host_os in aix[[4-9]]*) # All AIX code is PIC. if test ia64 = "$host_cpu"; then # AIX 5 now supports IA64 processor _LT_TAGVAR(lt_prog_compiler_static, $1)='-Bstatic' else _LT_TAGVAR(lt_prog_compiler_static, $1)='-bnso -bI:/lib/syscalls.exp' fi ;; chorus*) case $cc_basename in cxch68*) # Green Hills C++ Compiler # _LT_TAGVAR(lt_prog_compiler_static, $1)="--no_auto_instantiation -u __main -u __premain -u _abort -r $COOL_DIR/lib/libOrb.a $MVME_DIR/lib/CC/libC.a $MVME_DIR/lib/classix/libcx.s.a" ;; esac ;; mingw* | cygwin* | os2* | pw32* | cegcc*) # This hack is so that the source file can tell whether it is being # built for inclusion in a dll (and should export symbols for example). m4_if([$1], [GCJ], [], [_LT_TAGVAR(lt_prog_compiler_pic, $1)='-DDLL_EXPORT']) ;; dgux*) case $cc_basename in ec++*) _LT_TAGVAR(lt_prog_compiler_pic, $1)='-KPIC' ;; ghcx*) # Green Hills C++ Compiler _LT_TAGVAR(lt_prog_compiler_pic, $1)='-pic' ;; *) ;; esac ;; freebsd* | dragonfly*) # FreeBSD uses GNU C++ ;; hpux9* | hpux10* | hpux11*) case $cc_basename in CC*) _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,' _LT_TAGVAR(lt_prog_compiler_static, $1)='$wl-a ${wl}archive' if test ia64 != "$host_cpu"; then _LT_TAGVAR(lt_prog_compiler_pic, $1)='+Z' fi ;; aCC*) _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,' _LT_TAGVAR(lt_prog_compiler_static, $1)='$wl-a ${wl}archive' case $host_cpu in hppa*64*|ia64*) # +Z the default ;; *) _LT_TAGVAR(lt_prog_compiler_pic, $1)='+Z' ;; esac ;; *) ;; esac ;; interix*) # This is c89, which is MS Visual C++ (no shared libs) # Anyone wants to do a port? ;; irix5* | irix6* | nonstopux*) case $cc_basename in CC*) _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,' _LT_TAGVAR(lt_prog_compiler_static, $1)='-non_shared' # CC pic flag -KPIC is the default. ;; *) ;; esac ;; linux* | k*bsd*-gnu | kopensolaris*-gnu | gnu*) case $cc_basename in KCC*) # KAI C++ Compiler _LT_TAGVAR(lt_prog_compiler_wl, $1)='--backend -Wl,' _LT_TAGVAR(lt_prog_compiler_pic, $1)='-fPIC' ;; ecpc* ) # old Intel C++ for x86_64, which still supported -KPIC. _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,' _LT_TAGVAR(lt_prog_compiler_pic, $1)='-KPIC' _LT_TAGVAR(lt_prog_compiler_static, $1)='-static' ;; icpc* ) # Intel C++, used to be incompatible with GCC. # ICC 10 doesn't accept -KPIC any more. _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,' _LT_TAGVAR(lt_prog_compiler_pic, $1)='-fPIC' _LT_TAGVAR(lt_prog_compiler_static, $1)='-static' ;; pgCC* | pgcpp*) # Portland Group C++ compiler _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,' _LT_TAGVAR(lt_prog_compiler_pic, $1)='-fpic' _LT_TAGVAR(lt_prog_compiler_static, $1)='-Bstatic' ;; cxx*) # Compaq C++ # Make sure the PIC flag is empty. It appears that all Alpha # Linux and Compaq Tru64 Unix objects are PIC. _LT_TAGVAR(lt_prog_compiler_pic, $1)= _LT_TAGVAR(lt_prog_compiler_static, $1)='-non_shared' ;; xlc* | xlC* | bgxl[[cC]]* | mpixl[[cC]]*) # IBM XL 8.0, 9.0 on PPC and BlueGene _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,' _LT_TAGVAR(lt_prog_compiler_pic, $1)='-qpic' _LT_TAGVAR(lt_prog_compiler_static, $1)='-qstaticlink' ;; *) case `$CC -V 2>&1 | sed 5q` in *Sun\ C*) # Sun C++ 5.9 _LT_TAGVAR(lt_prog_compiler_pic, $1)='-KPIC' _LT_TAGVAR(lt_prog_compiler_static, $1)='-Bstatic' _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Qoption ld ' ;; esac ;; esac ;; lynxos*) ;; m88k*) ;; mvs*) case $cc_basename in cxx*) _LT_TAGVAR(lt_prog_compiler_pic, $1)='-W c,exportall' ;; *) ;; esac ;; netbsd* | netbsdelf*-gnu) ;; *qnx* | *nto*) # QNX uses GNU C++, but need to define -shared option too, otherwise # it will coredump. _LT_TAGVAR(lt_prog_compiler_pic, $1)='-fPIC -shared' ;; osf3* | osf4* | osf5*) case $cc_basename in KCC*) _LT_TAGVAR(lt_prog_compiler_wl, $1)='--backend -Wl,' ;; RCC*) # Rational C++ 2.4.1 _LT_TAGVAR(lt_prog_compiler_pic, $1)='-pic' ;; cxx*) # Digital/Compaq C++ _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,' # Make sure the PIC flag is empty. It appears that all Alpha # Linux and Compaq Tru64 Unix objects are PIC. _LT_TAGVAR(lt_prog_compiler_pic, $1)= _LT_TAGVAR(lt_prog_compiler_static, $1)='-non_shared' ;; *) ;; esac ;; psos*) ;; solaris*) case $cc_basename in CC* | sunCC*) # Sun C++ 4.2, 5.x and Centerline C++ _LT_TAGVAR(lt_prog_compiler_pic, $1)='-KPIC' _LT_TAGVAR(lt_prog_compiler_static, $1)='-Bstatic' _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Qoption ld ' ;; gcx*) # Green Hills C++ Compiler _LT_TAGVAR(lt_prog_compiler_pic, $1)='-PIC' ;; *) ;; esac ;; sunos4*) case $cc_basename in CC*) # Sun C++ 4.x _LT_TAGVAR(lt_prog_compiler_pic, $1)='-pic' _LT_TAGVAR(lt_prog_compiler_static, $1)='-Bstatic' ;; lcc*) # Lucid _LT_TAGVAR(lt_prog_compiler_pic, $1)='-pic' ;; *) ;; esac ;; sysv5* | unixware* | sco3.2v5* | sco5v6* | OpenUNIX*) case $cc_basename in CC*) _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,' _LT_TAGVAR(lt_prog_compiler_pic, $1)='-KPIC' _LT_TAGVAR(lt_prog_compiler_static, $1)='-Bstatic' ;; esac ;; tandem*) case $cc_basename in NCC*) # NonStop-UX NCC 3.20 _LT_TAGVAR(lt_prog_compiler_pic, $1)='-KPIC' ;; *) ;; esac ;; vxworks*) ;; *) _LT_TAGVAR(lt_prog_compiler_can_build_shared, $1)=no ;; esac fi ], [ if test yes = "$GCC"; then _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,' _LT_TAGVAR(lt_prog_compiler_static, $1)='-static' case $host_os in aix*) # All AIX code is PIC. if test ia64 = "$host_cpu"; then # AIX 5 now supports IA64 processor _LT_TAGVAR(lt_prog_compiler_static, $1)='-Bstatic' fi _LT_TAGVAR(lt_prog_compiler_pic, $1)='-fPIC' ;; amigaos*) case $host_cpu in powerpc) # see comment about AmigaOS4 .so support _LT_TAGVAR(lt_prog_compiler_pic, $1)='-fPIC' ;; m68k) # FIXME: we need at least 68020 code to build shared libraries, but # adding the '-m68020' flag to GCC prevents building anything better, # like '-m68040'. _LT_TAGVAR(lt_prog_compiler_pic, $1)='-m68020 -resident32 -malways-restore-a4' ;; esac ;; beos* | irix5* | irix6* | nonstopux* | osf3* | osf4* | osf5*) # PIC is the default for these OSes. ;; mingw* | cygwin* | pw32* | os2* | cegcc*) # This hack is so that the source file can tell whether it is being # built for inclusion in a dll (and should export symbols for example). # Although the cygwin gcc ignores -fPIC, still need this for old-style # (--disable-auto-import) libraries m4_if([$1], [GCJ], [], [_LT_TAGVAR(lt_prog_compiler_pic, $1)='-DDLL_EXPORT']) case $host_os in os2*) _LT_TAGVAR(lt_prog_compiler_static, $1)='$wl-static' ;; esac ;; darwin* | rhapsody*) # PIC is the default on this platform # Common symbols not allowed in MH_DYLIB files _LT_TAGVAR(lt_prog_compiler_pic, $1)='-fno-common' ;; haiku*) # PIC is the default for Haiku. # The "-static" flag exists, but is broken. _LT_TAGVAR(lt_prog_compiler_static, $1)= ;; hpux*) # PIC is the default for 64-bit PA HP-UX, but not for 32-bit # PA HP-UX. On IA64 HP-UX, PIC is the default but the pic flag # sets the default TLS model and affects inlining. case $host_cpu in hppa*64*) # +Z the default ;; *) _LT_TAGVAR(lt_prog_compiler_pic, $1)='-fPIC' ;; esac ;; interix[[3-9]]*) # Interix 3.x gcc -fpic/-fPIC options generate broken code. # Instead, we relocate shared libraries at runtime. ;; msdosdjgpp*) # Just because we use GCC doesn't mean we suddenly get shared libraries # on systems that don't support them. _LT_TAGVAR(lt_prog_compiler_can_build_shared, $1)=no enable_shared=no ;; *nto* | *qnx*) # QNX uses GNU C++, but need to define -shared option too, otherwise # it will coredump. _LT_TAGVAR(lt_prog_compiler_pic, $1)='-fPIC -shared' ;; sysv4*MP*) if test -d /usr/nec; then _LT_TAGVAR(lt_prog_compiler_pic, $1)=-Kconform_pic fi ;; *) _LT_TAGVAR(lt_prog_compiler_pic, $1)='-fPIC' ;; esac case $cc_basename in nvcc*) # Cuda Compiler Driver 2.2 _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Xlinker ' if test -n "$_LT_TAGVAR(lt_prog_compiler_pic, $1)"; then _LT_TAGVAR(lt_prog_compiler_pic, $1)="-Xcompiler $_LT_TAGVAR(lt_prog_compiler_pic, $1)" fi ;; esac else # PORTME Check for flag to pass linker flags through the system compiler. case $host_os in aix*) _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,' if test ia64 = "$host_cpu"; then # AIX 5 now supports IA64 processor _LT_TAGVAR(lt_prog_compiler_static, $1)='-Bstatic' else _LT_TAGVAR(lt_prog_compiler_static, $1)='-bnso -bI:/lib/syscalls.exp' fi ;; darwin* | rhapsody*) # PIC is the default on this platform # Common symbols not allowed in MH_DYLIB files _LT_TAGVAR(lt_prog_compiler_pic, $1)='-fno-common' case $cc_basename in nagfor*) # NAG Fortran compiler _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,-Wl,,' _LT_TAGVAR(lt_prog_compiler_pic, $1)='-PIC' _LT_TAGVAR(lt_prog_compiler_static, $1)='-Bstatic' ;; esac ;; mingw* | cygwin* | pw32* | os2* | cegcc*) # This hack is so that the source file can tell whether it is being # built for inclusion in a dll (and should export symbols for example). m4_if([$1], [GCJ], [], [_LT_TAGVAR(lt_prog_compiler_pic, $1)='-DDLL_EXPORT']) case $host_os in os2*) _LT_TAGVAR(lt_prog_compiler_static, $1)='$wl-static' ;; esac ;; hpux9* | hpux10* | hpux11*) _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,' # PIC is the default for IA64 HP-UX and 64-bit HP-UX, but # not for PA HP-UX. case $host_cpu in hppa*64*|ia64*) # +Z the default ;; *) _LT_TAGVAR(lt_prog_compiler_pic, $1)='+Z' ;; esac # Is there a better lt_prog_compiler_static that works with the bundled CC? _LT_TAGVAR(lt_prog_compiler_static, $1)='$wl-a ${wl}archive' ;; irix5* | irix6* | nonstopux*) _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,' # PIC (with -KPIC) is the default. _LT_TAGVAR(lt_prog_compiler_static, $1)='-non_shared' ;; linux* | k*bsd*-gnu | kopensolaris*-gnu | gnu*) case $cc_basename in # old Intel for x86_64, which still supported -KPIC. ecc*) _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,' _LT_TAGVAR(lt_prog_compiler_pic, $1)='-KPIC' _LT_TAGVAR(lt_prog_compiler_static, $1)='-static' ;; # icc used to be incompatible with GCC. # ICC 10 doesn't accept -KPIC any more. icc* | ifort*) _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,' _LT_TAGVAR(lt_prog_compiler_pic, $1)='-fPIC' _LT_TAGVAR(lt_prog_compiler_static, $1)='-static' ;; # Lahey Fortran 8.1. lf95*) _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,' _LT_TAGVAR(lt_prog_compiler_pic, $1)='--shared' _LT_TAGVAR(lt_prog_compiler_static, $1)='--static' ;; nagfor*) # NAG Fortran compiler _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,-Wl,,' _LT_TAGVAR(lt_prog_compiler_pic, $1)='-PIC' _LT_TAGVAR(lt_prog_compiler_static, $1)='-Bstatic' ;; tcc*) # Fabrice Bellard et al's Tiny C Compiler _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,' _LT_TAGVAR(lt_prog_compiler_pic, $1)='-fPIC' _LT_TAGVAR(lt_prog_compiler_static, $1)='-static' ;; pgcc* | pgf77* | pgf90* | pgf95* | pgfortran*) # Portland Group compilers (*not* the Pentium gcc compiler, # which looks to be a dead project) _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,' _LT_TAGVAR(lt_prog_compiler_pic, $1)='-fpic' _LT_TAGVAR(lt_prog_compiler_static, $1)='-Bstatic' ;; ccc*) _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,' # All Alpha code is PIC. _LT_TAGVAR(lt_prog_compiler_static, $1)='-non_shared' ;; xl* | bgxl* | bgf* | mpixl*) # IBM XL C 8.0/Fortran 10.1, 11.1 on PPC and BlueGene _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,' _LT_TAGVAR(lt_prog_compiler_pic, $1)='-qpic' _LT_TAGVAR(lt_prog_compiler_static, $1)='-qstaticlink' ;; *) case `$CC -V 2>&1 | sed 5q` in *Sun\ Ceres\ Fortran* | *Sun*Fortran*\ [[1-7]].* | *Sun*Fortran*\ 8.[[0-3]]*) # Sun Fortran 8.3 passes all unrecognized flags to the linker _LT_TAGVAR(lt_prog_compiler_pic, $1)='-KPIC' _LT_TAGVAR(lt_prog_compiler_static, $1)='-Bstatic' _LT_TAGVAR(lt_prog_compiler_wl, $1)='' ;; *Sun\ F* | *Sun*Fortran*) _LT_TAGVAR(lt_prog_compiler_pic, $1)='-KPIC' _LT_TAGVAR(lt_prog_compiler_static, $1)='-Bstatic' _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Qoption ld ' ;; *Sun\ C*) # Sun C 5.9 _LT_TAGVAR(lt_prog_compiler_pic, $1)='-KPIC' _LT_TAGVAR(lt_prog_compiler_static, $1)='-Bstatic' _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,' ;; *Intel*\ [[CF]]*Compiler*) _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,' _LT_TAGVAR(lt_prog_compiler_pic, $1)='-fPIC' _LT_TAGVAR(lt_prog_compiler_static, $1)='-static' ;; *Portland\ Group*) _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,' _LT_TAGVAR(lt_prog_compiler_pic, $1)='-fpic' _LT_TAGVAR(lt_prog_compiler_static, $1)='-Bstatic' ;; esac ;; esac ;; newsos6) _LT_TAGVAR(lt_prog_compiler_pic, $1)='-KPIC' _LT_TAGVAR(lt_prog_compiler_static, $1)='-Bstatic' ;; *nto* | *qnx*) # QNX uses GNU C++, but need to define -shared option too, otherwise # it will coredump. _LT_TAGVAR(lt_prog_compiler_pic, $1)='-fPIC -shared' ;; osf3* | osf4* | osf5*) _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,' # All OSF/1 code is PIC. _LT_TAGVAR(lt_prog_compiler_static, $1)='-non_shared' ;; rdos*) _LT_TAGVAR(lt_prog_compiler_static, $1)='-non_shared' ;; solaris*) _LT_TAGVAR(lt_prog_compiler_pic, $1)='-KPIC' _LT_TAGVAR(lt_prog_compiler_static, $1)='-Bstatic' case $cc_basename in f77* | f90* | f95* | sunf77* | sunf90* | sunf95*) _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Qoption ld ';; *) _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,';; esac ;; sunos4*) _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Qoption ld ' _LT_TAGVAR(lt_prog_compiler_pic, $1)='-PIC' _LT_TAGVAR(lt_prog_compiler_static, $1)='-Bstatic' ;; sysv4 | sysv4.2uw2* | sysv4.3*) _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,' _LT_TAGVAR(lt_prog_compiler_pic, $1)='-KPIC' _LT_TAGVAR(lt_prog_compiler_static, $1)='-Bstatic' ;; sysv4*MP*) if test -d /usr/nec; then _LT_TAGVAR(lt_prog_compiler_pic, $1)='-Kconform_pic' _LT_TAGVAR(lt_prog_compiler_static, $1)='-Bstatic' fi ;; sysv5* | unixware* | sco3.2v5* | sco5v6* | OpenUNIX*) _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,' _LT_TAGVAR(lt_prog_compiler_pic, $1)='-KPIC' _LT_TAGVAR(lt_prog_compiler_static, $1)='-Bstatic' ;; unicos*) _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,' _LT_TAGVAR(lt_prog_compiler_can_build_shared, $1)=no ;; uts4*) _LT_TAGVAR(lt_prog_compiler_pic, $1)='-pic' _LT_TAGVAR(lt_prog_compiler_static, $1)='-Bstatic' ;; *) _LT_TAGVAR(lt_prog_compiler_can_build_shared, $1)=no ;; esac fi ]) case $host_os in # For platforms that do not support PIC, -DPIC is meaningless: *djgpp*) _LT_TAGVAR(lt_prog_compiler_pic, $1)= ;; *) _LT_TAGVAR(lt_prog_compiler_pic, $1)="$_LT_TAGVAR(lt_prog_compiler_pic, $1)@&t@m4_if([$1],[],[ -DPIC],[m4_if([$1],[CXX],[ -DPIC],[])])" ;; esac AC_CACHE_CHECK([for $compiler option to produce PIC], [_LT_TAGVAR(lt_cv_prog_compiler_pic, $1)], [_LT_TAGVAR(lt_cv_prog_compiler_pic, $1)=$_LT_TAGVAR(lt_prog_compiler_pic, $1)]) _LT_TAGVAR(lt_prog_compiler_pic, $1)=$_LT_TAGVAR(lt_cv_prog_compiler_pic, $1) # # Check to make sure the PIC flag actually works. # if test -n "$_LT_TAGVAR(lt_prog_compiler_pic, $1)"; then _LT_COMPILER_OPTION([if $compiler PIC flag $_LT_TAGVAR(lt_prog_compiler_pic, $1) works], [_LT_TAGVAR(lt_cv_prog_compiler_pic_works, $1)], [$_LT_TAGVAR(lt_prog_compiler_pic, $1)@&t@m4_if([$1],[],[ -DPIC],[m4_if([$1],[CXX],[ -DPIC],[])])], [], [case $_LT_TAGVAR(lt_prog_compiler_pic, $1) in "" | " "*) ;; *) _LT_TAGVAR(lt_prog_compiler_pic, $1)=" $_LT_TAGVAR(lt_prog_compiler_pic, $1)" ;; esac], [_LT_TAGVAR(lt_prog_compiler_pic, $1)= _LT_TAGVAR(lt_prog_compiler_can_build_shared, $1)=no]) fi _LT_TAGDECL([pic_flag], [lt_prog_compiler_pic], [1], [Additional compiler flags for building library objects]) _LT_TAGDECL([wl], [lt_prog_compiler_wl], [1], [How to pass a linker flag through the compiler]) # # Check to make sure the static flag actually works. # wl=$_LT_TAGVAR(lt_prog_compiler_wl, $1) eval lt_tmp_static_flag=\"$_LT_TAGVAR(lt_prog_compiler_static, $1)\" _LT_LINKER_OPTION([if $compiler static flag $lt_tmp_static_flag works], _LT_TAGVAR(lt_cv_prog_compiler_static_works, $1), $lt_tmp_static_flag, [], [_LT_TAGVAR(lt_prog_compiler_static, $1)=]) _LT_TAGDECL([link_static_flag], [lt_prog_compiler_static], [1], [Compiler flag to prevent dynamic linking]) ])# _LT_COMPILER_PIC # _LT_LINKER_SHLIBS([TAGNAME]) # ---------------------------- # See if the linker supports building shared libraries. m4_defun([_LT_LINKER_SHLIBS], [AC_REQUIRE([LT_PATH_LD])dnl AC_REQUIRE([LT_PATH_NM])dnl m4_require([_LT_PATH_MANIFEST_TOOL])dnl m4_require([_LT_FILEUTILS_DEFAULTS])dnl m4_require([_LT_DECL_EGREP])dnl m4_require([_LT_DECL_SED])dnl m4_require([_LT_CMD_GLOBAL_SYMBOLS])dnl m4_require([_LT_TAG_COMPILER])dnl AC_MSG_CHECKING([whether the $compiler linker ($LD) supports shared libraries]) m4_if([$1], [CXX], [ _LT_TAGVAR(export_symbols_cmds, $1)='$NM $libobjs $convenience | $global_symbol_pipe | $SED '\''s/.* //'\'' | sort | uniq > $export_symbols' _LT_TAGVAR(exclude_expsyms, $1)=['_GLOBAL_OFFSET_TABLE_|_GLOBAL__F[ID]_.*'] case $host_os in aix[[4-9]]*) # If we're using GNU nm, then we don't want the "-C" option. # -C means demangle to GNU nm, but means don't demangle to AIX nm. # Without the "-l" option, or with the "-B" option, AIX nm treats # weak defined symbols like other global defined symbols, whereas # GNU nm marks them as "W". # While the 'weak' keyword is ignored in the Export File, we need # it in the Import File for the 'aix-soname' feature, so we have # to replace the "-B" option with "-P" for AIX nm. if $NM -V 2>&1 | $GREP 'GNU' > /dev/null; then _LT_TAGVAR(export_symbols_cmds, $1)='$NM -Bpg $libobjs $convenience | awk '\''{ if (((\$ 2 == "T") || (\$ 2 == "D") || (\$ 2 == "B") || (\$ 2 == "W")) && ([substr](\$ 3,1,1) != ".")) { if (\$ 2 == "W") { print \$ 3 " weak" } else { print \$ 3 } } }'\'' | sort -u > $export_symbols' else _LT_TAGVAR(export_symbols_cmds, $1)='`func_echo_all $NM | $SED -e '\''s/B\([[^B]]*\)$/P\1/'\''` -PCpgl $libobjs $convenience | awk '\''{ if (((\$ 2 == "T") || (\$ 2 == "D") || (\$ 2 == "B") || (\$ 2 == "W") || (\$ 2 == "V") || (\$ 2 == "Z")) && ([substr](\$ 1,1,1) != ".")) { if ((\$ 2 == "W") || (\$ 2 == "V") || (\$ 2 == "Z")) { print \$ 1 " weak" } else { print \$ 1 } } }'\'' | sort -u > $export_symbols' fi ;; pw32*) _LT_TAGVAR(export_symbols_cmds, $1)=$ltdll_cmds ;; cygwin* | mingw* | cegcc*) case $cc_basename in cl*) _LT_TAGVAR(exclude_expsyms, $1)='_NULL_IMPORT_DESCRIPTOR|_IMPORT_DESCRIPTOR_.*' ;; *) _LT_TAGVAR(export_symbols_cmds, $1)='$NM $libobjs $convenience | $global_symbol_pipe | $SED -e '\''/^[[BCDGRS]][[ ]]/s/.*[[ ]]\([[^ ]]*\)/\1 DATA/;s/^.*[[ ]]__nm__\([[^ ]]*\)[[ ]][[^ ]]*/\1 DATA/;/^I[[ ]]/d;/^[[AITW]][[ ]]/s/.* //'\'' | sort | uniq > $export_symbols' _LT_TAGVAR(exclude_expsyms, $1)=['[_]+GLOBAL_OFFSET_TABLE_|[_]+GLOBAL__[FID]_.*|[_]+head_[A-Za-z0-9_]+_dll|[A-Za-z0-9_]+_dll_iname'] ;; esac ;; linux* | k*bsd*-gnu | gnu*) _LT_TAGVAR(link_all_deplibs, $1)=no ;; *) _LT_TAGVAR(export_symbols_cmds, $1)='$NM $libobjs $convenience | $global_symbol_pipe | $SED '\''s/.* //'\'' | sort | uniq > $export_symbols' ;; esac ], [ runpath_var= _LT_TAGVAR(allow_undefined_flag, $1)= _LT_TAGVAR(always_export_symbols, $1)=no _LT_TAGVAR(archive_cmds, $1)= _LT_TAGVAR(archive_expsym_cmds, $1)= _LT_TAGVAR(compiler_needs_object, $1)=no _LT_TAGVAR(enable_shared_with_static_runtimes, $1)=no _LT_TAGVAR(export_dynamic_flag_spec, $1)= _LT_TAGVAR(export_symbols_cmds, $1)='$NM $libobjs $convenience | $global_symbol_pipe | $SED '\''s/.* //'\'' | sort | uniq > $export_symbols' _LT_TAGVAR(hardcode_automatic, $1)=no _LT_TAGVAR(hardcode_direct, $1)=no _LT_TAGVAR(hardcode_direct_absolute, $1)=no _LT_TAGVAR(hardcode_libdir_flag_spec, $1)= _LT_TAGVAR(hardcode_libdir_separator, $1)= _LT_TAGVAR(hardcode_minus_L, $1)=no _LT_TAGVAR(hardcode_shlibpath_var, $1)=unsupported _LT_TAGVAR(inherit_rpath, $1)=no _LT_TAGVAR(link_all_deplibs, $1)=unknown _LT_TAGVAR(module_cmds, $1)= _LT_TAGVAR(module_expsym_cmds, $1)= _LT_TAGVAR(old_archive_from_new_cmds, $1)= _LT_TAGVAR(old_archive_from_expsyms_cmds, $1)= _LT_TAGVAR(thread_safe_flag_spec, $1)= _LT_TAGVAR(whole_archive_flag_spec, $1)= # include_expsyms should be a list of space-separated symbols to be *always* # included in the symbol list _LT_TAGVAR(include_expsyms, $1)= # exclude_expsyms can be an extended regexp of symbols to exclude # it will be wrapped by ' (' and ')$', so one must not match beginning or # end of line. Example: 'a|bc|.*d.*' will exclude the symbols 'a' and 'bc', # as well as any symbol that contains 'd'. _LT_TAGVAR(exclude_expsyms, $1)=['_GLOBAL_OFFSET_TABLE_|_GLOBAL__F[ID]_.*'] # Although _GLOBAL_OFFSET_TABLE_ is a valid symbol C name, most a.out # platforms (ab)use it in PIC code, but their linkers get confused if # the symbol is explicitly referenced. Since portable code cannot # rely on this symbol name, it's probably fine to never include it in # preloaded symbol tables. # Exclude shared library initialization/finalization symbols. dnl Note also adjust exclude_expsyms for C++ above. extract_expsyms_cmds= case $host_os in cygwin* | mingw* | pw32* | cegcc*) # FIXME: the MSVC++ port hasn't been tested in a loooong time # When not using gcc, we currently assume that we are using # Microsoft Visual C++. if test yes != "$GCC"; then with_gnu_ld=no fi ;; interix*) # we just hope/assume this is gcc and not c89 (= MSVC++) with_gnu_ld=yes ;; openbsd* | bitrig*) with_gnu_ld=no ;; linux* | k*bsd*-gnu | gnu*) _LT_TAGVAR(link_all_deplibs, $1)=no ;; esac _LT_TAGVAR(ld_shlibs, $1)=yes # On some targets, GNU ld is compatible enough with the native linker # that we're better off using the native interface for both. lt_use_gnu_ld_interface=no if test yes = "$with_gnu_ld"; then case $host_os in aix*) # The AIX port of GNU ld has always aspired to compatibility # with the native linker. However, as the warning in the GNU ld # block says, versions before 2.19.5* couldn't really create working # shared libraries, regardless of the interface used. case `$LD -v 2>&1` in *\ \(GNU\ Binutils\)\ 2.19.5*) ;; *\ \(GNU\ Binutils\)\ 2.[[2-9]]*) ;; *\ \(GNU\ Binutils\)\ [[3-9]]*) ;; *) lt_use_gnu_ld_interface=yes ;; esac ;; *) lt_use_gnu_ld_interface=yes ;; esac fi if test yes = "$lt_use_gnu_ld_interface"; then # If archive_cmds runs LD, not CC, wlarc should be empty wlarc='$wl' # Set some defaults for GNU ld with shared library support. These # are reset later if shared libraries are not supported. Putting them # here allows them to be overridden if necessary. runpath_var=LD_RUN_PATH _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl-rpath $wl$libdir' _LT_TAGVAR(export_dynamic_flag_spec, $1)='$wl--export-dynamic' # ancient GNU ld didn't support --whole-archive et. al. if $LD --help 2>&1 | $GREP 'no-whole-archive' > /dev/null; then _LT_TAGVAR(whole_archive_flag_spec, $1)=$wlarc'--whole-archive$convenience '$wlarc'--no-whole-archive' else _LT_TAGVAR(whole_archive_flag_spec, $1)= fi supports_anon_versioning=no case `$LD -v | $SED -e 's/([^)]\+)\s\+//' 2>&1` in *GNU\ gold*) supports_anon_versioning=yes ;; *\ [[01]].* | *\ 2.[[0-9]].* | *\ 2.10.*) ;; # catch versions < 2.11 *\ 2.11.93.0.2\ *) supports_anon_versioning=yes ;; # RH7.3 ... *\ 2.11.92.0.12\ *) supports_anon_versioning=yes ;; # Mandrake 8.2 ... *\ 2.11.*) ;; # other 2.11 versions *) supports_anon_versioning=yes ;; esac # See if GNU ld supports shared libraries. case $host_os in aix[[3-9]]*) # On AIX/PPC, the GNU linker is very broken if test ia64 != "$host_cpu"; then _LT_TAGVAR(ld_shlibs, $1)=no cat <<_LT_EOF 1>&2 *** Warning: the GNU linker, at least up to release 2.19, is reported *** to be unable to reliably create shared libraries on AIX. *** Therefore, libtool is disabling shared libraries support. If you *** really care for shared libraries, you may want to install binutils *** 2.20 or above, or modify your PATH so that a non-GNU linker is found. *** You will then need to restart the configuration process. _LT_EOF fi ;; amigaos*) case $host_cpu in powerpc) # see comment about AmigaOS4 .so support _LT_TAGVAR(archive_cmds, $1)='$CC -shared $libobjs $deplibs $compiler_flags $wl-soname $wl$soname -o $lib' _LT_TAGVAR(archive_expsym_cmds, $1)='' ;; m68k) _LT_TAGVAR(archive_cmds, $1)='$RM $output_objdir/a2ixlibrary.data~$ECHO "#define NAME $libname" > $output_objdir/a2ixlibrary.data~$ECHO "#define LIBRARY_ID 1" >> $output_objdir/a2ixlibrary.data~$ECHO "#define VERSION $major" >> $output_objdir/a2ixlibrary.data~$ECHO "#define REVISION $revision" >> $output_objdir/a2ixlibrary.data~$AR $AR_FLAGS $lib $libobjs~$RANLIB $lib~(cd $output_objdir && a2ixlibrary -32)' _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='-L$libdir' _LT_TAGVAR(hardcode_minus_L, $1)=yes ;; esac ;; beos*) if $LD --help 2>&1 | $GREP ': supported targets:.* elf' > /dev/null; then _LT_TAGVAR(allow_undefined_flag, $1)=unsupported # Joseph Beckenbach says some releases of gcc # support --undefined. This deserves some investigation. FIXME _LT_TAGVAR(archive_cmds, $1)='$CC -nostart $libobjs $deplibs $compiler_flags $wl-soname $wl$soname -o $lib' else _LT_TAGVAR(ld_shlibs, $1)=no fi ;; cygwin* | mingw* | pw32* | cegcc*) # _LT_TAGVAR(hardcode_libdir_flag_spec, $1) is actually meaningless, # as there is no search path for DLLs. _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='-L$libdir' _LT_TAGVAR(export_dynamic_flag_spec, $1)='$wl--export-all-symbols' _LT_TAGVAR(allow_undefined_flag, $1)=unsupported _LT_TAGVAR(always_export_symbols, $1)=no _LT_TAGVAR(enable_shared_with_static_runtimes, $1)=yes _LT_TAGVAR(export_symbols_cmds, $1)='$NM $libobjs $convenience | $global_symbol_pipe | $SED -e '\''/^[[BCDGRS]][[ ]]/s/.*[[ ]]\([[^ ]]*\)/\1 DATA/;s/^.*[[ ]]__nm__\([[^ ]]*\)[[ ]][[^ ]]*/\1 DATA/;/^I[[ ]]/d;/^[[AITW]][[ ]]/s/.* //'\'' | sort | uniq > $export_symbols' _LT_TAGVAR(exclude_expsyms, $1)=['[_]+GLOBAL_OFFSET_TABLE_|[_]+GLOBAL__[FID]_.*|[_]+head_[A-Za-z0-9_]+_dll|[A-Za-z0-9_]+_dll_iname'] if $LD --help 2>&1 | $GREP 'auto-import' > /dev/null; then _LT_TAGVAR(archive_cmds, $1)='$CC -shared $libobjs $deplibs $compiler_flags -o $output_objdir/$soname $wl--enable-auto-image-base -Xlinker --out-implib -Xlinker $lib' # If the export-symbols file already is a .def file, use it as # is; otherwise, prepend EXPORTS... _LT_TAGVAR(archive_expsym_cmds, $1)='if _LT_DLL_DEF_P([$export_symbols]); then cp $export_symbols $output_objdir/$soname.def; else echo EXPORTS > $output_objdir/$soname.def; cat $export_symbols >> $output_objdir/$soname.def; fi~ $CC -shared $output_objdir/$soname.def $libobjs $deplibs $compiler_flags -o $output_objdir/$soname $wl--enable-auto-image-base -Xlinker --out-implib -Xlinker $lib' else _LT_TAGVAR(ld_shlibs, $1)=no fi ;; haiku*) _LT_TAGVAR(archive_cmds, $1)='$CC -shared $libobjs $deplibs $compiler_flags $wl-soname $wl$soname -o $lib' _LT_TAGVAR(link_all_deplibs, $1)=yes ;; os2*) _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='-L$libdir' _LT_TAGVAR(hardcode_minus_L, $1)=yes _LT_TAGVAR(allow_undefined_flag, $1)=unsupported shrext_cmds=.dll _LT_TAGVAR(archive_cmds, $1)='$ECHO "LIBRARY ${soname%$shared_ext} INITINSTANCE TERMINSTANCE" > $output_objdir/$libname.def~ $ECHO "DESCRIPTION \"$libname\"" >> $output_objdir/$libname.def~ $ECHO "DATA MULTIPLE NONSHARED" >> $output_objdir/$libname.def~ $ECHO EXPORTS >> $output_objdir/$libname.def~ emxexp $libobjs | $SED /"_DLL_InitTerm"/d >> $output_objdir/$libname.def~ $CC -Zdll -Zcrtdll -o $output_objdir/$soname $libobjs $deplibs $compiler_flags $output_objdir/$libname.def~ emximp -o $lib $output_objdir/$libname.def' _LT_TAGVAR(archive_expsym_cmds, $1)='$ECHO "LIBRARY ${soname%$shared_ext} INITINSTANCE TERMINSTANCE" > $output_objdir/$libname.def~ $ECHO "DESCRIPTION \"$libname\"" >> $output_objdir/$libname.def~ $ECHO "DATA MULTIPLE NONSHARED" >> $output_objdir/$libname.def~ $ECHO EXPORTS >> $output_objdir/$libname.def~ prefix_cmds="$SED"~ if test EXPORTS = "`$SED 1q $export_symbols`"; then prefix_cmds="$prefix_cmds -e 1d"; fi~ prefix_cmds="$prefix_cmds -e \"s/^\(.*\)$/_\1/g\""~ cat $export_symbols | $prefix_cmds >> $output_objdir/$libname.def~ $CC -Zdll -Zcrtdll -o $output_objdir/$soname $libobjs $deplibs $compiler_flags $output_objdir/$libname.def~ emximp -o $lib $output_objdir/$libname.def' _LT_TAGVAR(old_archive_From_new_cmds, $1)='emximp -o $output_objdir/${libname}_dll.a $output_objdir/$libname.def' _LT_TAGVAR(enable_shared_with_static_runtimes, $1)=yes ;; interix[[3-9]]*) _LT_TAGVAR(hardcode_direct, $1)=no _LT_TAGVAR(hardcode_shlibpath_var, $1)=no _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl-rpath,$libdir' _LT_TAGVAR(export_dynamic_flag_spec, $1)='$wl-E' # Hack: On Interix 3.x, we cannot compile PIC because of a broken gcc. # Instead, shared libraries are loaded at an image base (0x10000000 by # default) and relocated if they conflict, which is a slow very memory # consuming and fragmenting process. To avoid this, we pick a random, # 256 KiB-aligned image base between 0x50000000 and 0x6FFC0000 at link # time. Moving up from 0x10000000 also allows more sbrk(2) space. _LT_TAGVAR(archive_cmds, $1)='$CC -shared $pic_flag $libobjs $deplibs $compiler_flags $wl-h,$soname $wl--image-base,`expr ${RANDOM-$$} % 4096 / 2 \* 262144 + 1342177280` -o $lib' _LT_TAGVAR(archive_expsym_cmds, $1)='sed "s|^|_|" $export_symbols >$output_objdir/$soname.expsym~$CC -shared $pic_flag $libobjs $deplibs $compiler_flags $wl-h,$soname $wl--retain-symbols-file,$output_objdir/$soname.expsym $wl--image-base,`expr ${RANDOM-$$} % 4096 / 2 \* 262144 + 1342177280` -o $lib' ;; gnu* | linux* | tpf* | k*bsd*-gnu | kopensolaris*-gnu) tmp_diet=no if test linux-dietlibc = "$host_os"; then case $cc_basename in diet\ *) tmp_diet=yes;; # linux-dietlibc with static linking (!diet-dyn) esac fi if $LD --help 2>&1 | $EGREP ': supported targets:.* elf' > /dev/null \ && test no = "$tmp_diet" then tmp_addflag=' $pic_flag' tmp_sharedflag='-shared' case $cc_basename,$host_cpu in pgcc*) # Portland Group C compiler _LT_TAGVAR(whole_archive_flag_spec, $1)='$wl--whole-archive`for conv in $convenience\"\"; do test -n \"$conv\" && new_convenience=\"$new_convenience,$conv\"; done; func_echo_all \"$new_convenience\"` $wl--no-whole-archive' tmp_addflag=' $pic_flag' ;; pgf77* | pgf90* | pgf95* | pgfortran*) # Portland Group f77 and f90 compilers _LT_TAGVAR(whole_archive_flag_spec, $1)='$wl--whole-archive`for conv in $convenience\"\"; do test -n \"$conv\" && new_convenience=\"$new_convenience,$conv\"; done; func_echo_all \"$new_convenience\"` $wl--no-whole-archive' tmp_addflag=' $pic_flag -Mnomain' ;; ecc*,ia64* | icc*,ia64*) # Intel C compiler on ia64 tmp_addflag=' -i_dynamic' ;; efc*,ia64* | ifort*,ia64*) # Intel Fortran compiler on ia64 tmp_addflag=' -i_dynamic -nofor_main' ;; ifc* | ifort*) # Intel Fortran compiler tmp_addflag=' -nofor_main' ;; lf95*) # Lahey Fortran 8.1 _LT_TAGVAR(whole_archive_flag_spec, $1)= tmp_sharedflag='--shared' ;; nagfor*) # NAGFOR 5.3 tmp_sharedflag='-Wl,-shared' ;; xl[[cC]]* | bgxl[[cC]]* | mpixl[[cC]]*) # IBM XL C 8.0 on PPC (deal with xlf below) tmp_sharedflag='-qmkshrobj' tmp_addflag= ;; nvcc*) # Cuda Compiler Driver 2.2 _LT_TAGVAR(whole_archive_flag_spec, $1)='$wl--whole-archive`for conv in $convenience\"\"; do test -n \"$conv\" && new_convenience=\"$new_convenience,$conv\"; done; func_echo_all \"$new_convenience\"` $wl--no-whole-archive' _LT_TAGVAR(compiler_needs_object, $1)=yes ;; esac case `$CC -V 2>&1 | sed 5q` in *Sun\ C*) # Sun C 5.9 _LT_TAGVAR(whole_archive_flag_spec, $1)='$wl--whole-archive`new_convenience=; for conv in $convenience\"\"; do test -z \"$conv\" || new_convenience=\"$new_convenience,$conv\"; done; func_echo_all \"$new_convenience\"` $wl--no-whole-archive' _LT_TAGVAR(compiler_needs_object, $1)=yes tmp_sharedflag='-G' ;; *Sun\ F*) # Sun Fortran 8.3 tmp_sharedflag='-G' ;; esac _LT_TAGVAR(archive_cmds, $1)='$CC '"$tmp_sharedflag""$tmp_addflag"' $libobjs $deplibs $compiler_flags $wl-soname $wl$soname -o $lib' if test yes = "$supports_anon_versioning"; then _LT_TAGVAR(archive_expsym_cmds, $1)='echo "{ global:" > $output_objdir/$libname.ver~ cat $export_symbols | sed -e "s/\(.*\)/\1;/" >> $output_objdir/$libname.ver~ echo "local: *; };" >> $output_objdir/$libname.ver~ $CC '"$tmp_sharedflag""$tmp_addflag"' $libobjs $deplibs $compiler_flags $wl-soname $wl$soname $wl-version-script $wl$output_objdir/$libname.ver -o $lib' fi case $cc_basename in tcc*) _LT_TAGVAR(export_dynamic_flag_spec, $1)='-rdynamic' ;; xlf* | bgf* | bgxlf* | mpixlf*) # IBM XL Fortran 10.1 on PPC cannot create shared libs itself _LT_TAGVAR(whole_archive_flag_spec, $1)='--whole-archive$convenience --no-whole-archive' _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl-rpath $wl$libdir' _LT_TAGVAR(archive_cmds, $1)='$LD -shared $libobjs $deplibs $linker_flags -soname $soname -o $lib' if test yes = "$supports_anon_versioning"; then _LT_TAGVAR(archive_expsym_cmds, $1)='echo "{ global:" > $output_objdir/$libname.ver~ cat $export_symbols | sed -e "s/\(.*\)/\1;/" >> $output_objdir/$libname.ver~ echo "local: *; };" >> $output_objdir/$libname.ver~ $LD -shared $libobjs $deplibs $linker_flags -soname $soname -version-script $output_objdir/$libname.ver -o $lib' fi ;; esac else _LT_TAGVAR(ld_shlibs, $1)=no fi ;; netbsd* | netbsdelf*-gnu) if echo __ELF__ | $CC -E - | $GREP __ELF__ >/dev/null; then _LT_TAGVAR(archive_cmds, $1)='$LD -Bshareable $libobjs $deplibs $linker_flags -o $lib' wlarc= else _LT_TAGVAR(archive_cmds, $1)='$CC -shared $pic_flag $libobjs $deplibs $compiler_flags $wl-soname $wl$soname -o $lib' _LT_TAGVAR(archive_expsym_cmds, $1)='$CC -shared $pic_flag $libobjs $deplibs $compiler_flags $wl-soname $wl$soname $wl-retain-symbols-file $wl$export_symbols -o $lib' fi ;; solaris*) if $LD -v 2>&1 | $GREP 'BFD 2\.8' > /dev/null; then _LT_TAGVAR(ld_shlibs, $1)=no cat <<_LT_EOF 1>&2 *** Warning: The releases 2.8.* of the GNU linker cannot reliably *** create shared libraries on Solaris systems. Therefore, libtool *** is disabling shared libraries support. We urge you to upgrade GNU *** binutils to release 2.9.1 or newer. Another option is to modify *** your PATH or compiler configuration so that the native linker is *** used, and then restart. _LT_EOF elif $LD --help 2>&1 | $GREP ': supported targets:.* elf' > /dev/null; then _LT_TAGVAR(archive_cmds, $1)='$CC -shared $pic_flag $libobjs $deplibs $compiler_flags $wl-soname $wl$soname -o $lib' _LT_TAGVAR(archive_expsym_cmds, $1)='$CC -shared $pic_flag $libobjs $deplibs $compiler_flags $wl-soname $wl$soname $wl-retain-symbols-file $wl$export_symbols -o $lib' else _LT_TAGVAR(ld_shlibs, $1)=no fi ;; sysv5* | sco3.2v5* | sco5v6* | unixware* | OpenUNIX*) case `$LD -v 2>&1` in *\ [[01]].* | *\ 2.[[0-9]].* | *\ 2.1[[0-5]].*) _LT_TAGVAR(ld_shlibs, $1)=no cat <<_LT_EOF 1>&2 *** Warning: Releases of the GNU linker prior to 2.16.91.0.3 cannot *** reliably create shared libraries on SCO systems. Therefore, libtool *** is disabling shared libraries support. We urge you to upgrade GNU *** binutils to release 2.16.91.0.3 or newer. Another option is to modify *** your PATH or compiler configuration so that the native linker is *** used, and then restart. _LT_EOF ;; *) # For security reasons, it is highly recommended that you always # use absolute paths for naming shared libraries, and exclude the # DT_RUNPATH tag from executables and libraries. But doing so # requires that you compile everything twice, which is a pain. if $LD --help 2>&1 | $GREP ': supported targets:.* elf' > /dev/null; then _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl-rpath $wl$libdir' _LT_TAGVAR(archive_cmds, $1)='$CC -shared $libobjs $deplibs $compiler_flags $wl-soname $wl$soname -o $lib' _LT_TAGVAR(archive_expsym_cmds, $1)='$CC -shared $libobjs $deplibs $compiler_flags $wl-soname $wl$soname $wl-retain-symbols-file $wl$export_symbols -o $lib' else _LT_TAGVAR(ld_shlibs, $1)=no fi ;; esac ;; sunos4*) _LT_TAGVAR(archive_cmds, $1)='$LD -assert pure-text -Bshareable -o $lib $libobjs $deplibs $linker_flags' wlarc= _LT_TAGVAR(hardcode_direct, $1)=yes _LT_TAGVAR(hardcode_shlibpath_var, $1)=no ;; *) if $LD --help 2>&1 | $GREP ': supported targets:.* elf' > /dev/null; then _LT_TAGVAR(archive_cmds, $1)='$CC -shared $pic_flag $libobjs $deplibs $compiler_flags $wl-soname $wl$soname -o $lib' _LT_TAGVAR(archive_expsym_cmds, $1)='$CC -shared $pic_flag $libobjs $deplibs $compiler_flags $wl-soname $wl$soname $wl-retain-symbols-file $wl$export_symbols -o $lib' else _LT_TAGVAR(ld_shlibs, $1)=no fi ;; esac if test no = "$_LT_TAGVAR(ld_shlibs, $1)"; then runpath_var= _LT_TAGVAR(hardcode_libdir_flag_spec, $1)= _LT_TAGVAR(export_dynamic_flag_spec, $1)= _LT_TAGVAR(whole_archive_flag_spec, $1)= fi else # PORTME fill in a description of your system's linker (not GNU ld) case $host_os in aix3*) _LT_TAGVAR(allow_undefined_flag, $1)=unsupported _LT_TAGVAR(always_export_symbols, $1)=yes _LT_TAGVAR(archive_expsym_cmds, $1)='$LD -o $output_objdir/$soname $libobjs $deplibs $linker_flags -bE:$export_symbols -T512 -H512 -bM:SRE~$AR $AR_FLAGS $lib $output_objdir/$soname' # Note: this linker hardcodes the directories in LIBPATH if there # are no directories specified by -L. _LT_TAGVAR(hardcode_minus_L, $1)=yes if test yes = "$GCC" && test -z "$lt_prog_compiler_static"; then # Neither direct hardcoding nor static linking is supported with a # broken collect2. _LT_TAGVAR(hardcode_direct, $1)=unsupported fi ;; aix[[4-9]]*) if test ia64 = "$host_cpu"; then # On IA64, the linker does run time linking by default, so we don't # have to do anything special. aix_use_runtimelinking=no exp_sym_flag='-Bexport' no_entry_flag= else # If we're using GNU nm, then we don't want the "-C" option. # -C means demangle to GNU nm, but means don't demangle to AIX nm. # Without the "-l" option, or with the "-B" option, AIX nm treats # weak defined symbols like other global defined symbols, whereas # GNU nm marks them as "W". # While the 'weak' keyword is ignored in the Export File, we need # it in the Import File for the 'aix-soname' feature, so we have # to replace the "-B" option with "-P" for AIX nm. if $NM -V 2>&1 | $GREP 'GNU' > /dev/null; then _LT_TAGVAR(export_symbols_cmds, $1)='$NM -Bpg $libobjs $convenience | awk '\''{ if (((\$ 2 == "T") || (\$ 2 == "D") || (\$ 2 == "B") || (\$ 2 == "W")) && ([substr](\$ 3,1,1) != ".")) { if (\$ 2 == "W") { print \$ 3 " weak" } else { print \$ 3 } } }'\'' | sort -u > $export_symbols' else _LT_TAGVAR(export_symbols_cmds, $1)='`func_echo_all $NM | $SED -e '\''s/B\([[^B]]*\)$/P\1/'\''` -PCpgl $libobjs $convenience | awk '\''{ if (((\$ 2 == "T") || (\$ 2 == "D") || (\$ 2 == "B") || (\$ 2 == "W") || (\$ 2 == "V") || (\$ 2 == "Z")) && ([substr](\$ 1,1,1) != ".")) { if ((\$ 2 == "W") || (\$ 2 == "V") || (\$ 2 == "Z")) { print \$ 1 " weak" } else { print \$ 1 } } }'\'' | sort -u > $export_symbols' fi aix_use_runtimelinking=no # Test if we are trying to use run time linking or normal # AIX style linking. If -brtl is somewhere in LDFLAGS, we # have runtime linking enabled, and use it for executables. # For shared libraries, we enable/disable runtime linking # depending on the kind of the shared library created - # when "with_aix_soname,aix_use_runtimelinking" is: # "aix,no" lib.a(lib.so.V) shared, rtl:no, for executables # "aix,yes" lib.so shared, rtl:yes, for executables # lib.a static archive # "both,no" lib.so.V(shr.o) shared, rtl:yes # lib.a(lib.so.V) shared, rtl:no, for executables # "both,yes" lib.so.V(shr.o) shared, rtl:yes, for executables # lib.a(lib.so.V) shared, rtl:no # "svr4,*" lib.so.V(shr.o) shared, rtl:yes, for executables # lib.a static archive case $host_os in aix4.[[23]]|aix4.[[23]].*|aix[[5-9]]*) for ld_flag in $LDFLAGS; do if (test x-brtl = "x$ld_flag" || test x-Wl,-brtl = "x$ld_flag"); then aix_use_runtimelinking=yes break fi done if test svr4,no = "$with_aix_soname,$aix_use_runtimelinking"; then # With aix-soname=svr4, we create the lib.so.V shared archives only, # so we don't have lib.a shared libs to link our executables. # We have to force runtime linking in this case. aix_use_runtimelinking=yes LDFLAGS="$LDFLAGS -Wl,-brtl" fi ;; esac exp_sym_flag='-bexport' no_entry_flag='-bnoentry' fi # When large executables or shared objects are built, AIX ld can # have problems creating the table of contents. If linking a library # or program results in "error TOC overflow" add -mminimal-toc to # CXXFLAGS/CFLAGS for g++/gcc. In the cases where that is not # enough to fix the problem, add -Wl,-bbigtoc to LDFLAGS. _LT_TAGVAR(archive_cmds, $1)='' _LT_TAGVAR(hardcode_direct, $1)=yes _LT_TAGVAR(hardcode_direct_absolute, $1)=yes _LT_TAGVAR(hardcode_libdir_separator, $1)=':' _LT_TAGVAR(link_all_deplibs, $1)=yes _LT_TAGVAR(file_list_spec, $1)='$wl-f,' case $with_aix_soname,$aix_use_runtimelinking in aix,*) ;; # traditional, no import file svr4,* | *,yes) # use import file # The Import File defines what to hardcode. _LT_TAGVAR(hardcode_direct, $1)=no _LT_TAGVAR(hardcode_direct_absolute, $1)=no ;; esac if test yes = "$GCC"; then case $host_os in aix4.[[012]]|aix4.[[012]].*) # We only want to do this on AIX 4.2 and lower, the check # below for broken collect2 doesn't work under 4.3+ collect2name=`$CC -print-prog-name=collect2` if test -f "$collect2name" && strings "$collect2name" | $GREP resolve_lib_name >/dev/null then # We have reworked collect2 : else # We have old collect2 _LT_TAGVAR(hardcode_direct, $1)=unsupported # It fails to find uninstalled libraries when the uninstalled # path is not listed in the libpath. Setting hardcode_minus_L # to unsupported forces relinking _LT_TAGVAR(hardcode_minus_L, $1)=yes _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='-L$libdir' _LT_TAGVAR(hardcode_libdir_separator, $1)= fi ;; esac shared_flag='-shared' if test yes = "$aix_use_runtimelinking"; then shared_flag="$shared_flag "'$wl-G' fi # Need to ensure runtime linking is disabled for the traditional # shared library, or the linker may eventually find shared libraries # /with/ Import File - we do not want to mix them. shared_flag_aix='-shared' shared_flag_svr4='-shared $wl-G' else # not using gcc if test ia64 = "$host_cpu"; then # VisualAge C++, Version 5.5 for AIX 5L for IA-64, Beta 3 Release # chokes on -Wl,-G. The following line is correct: shared_flag='-G' else if test yes = "$aix_use_runtimelinking"; then shared_flag='$wl-G' else shared_flag='$wl-bM:SRE' fi shared_flag_aix='$wl-bM:SRE' shared_flag_svr4='$wl-G' fi fi _LT_TAGVAR(export_dynamic_flag_spec, $1)='$wl-bexpall' # It seems that -bexpall does not export symbols beginning with # underscore (_), so it is better to generate a list of symbols to export. _LT_TAGVAR(always_export_symbols, $1)=yes if test aix,yes = "$with_aix_soname,$aix_use_runtimelinking"; then # Warning - without using the other runtime loading flags (-brtl), # -berok will link without error, but may produce a broken library. _LT_TAGVAR(allow_undefined_flag, $1)='-berok' # Determine the default libpath from the value encoded in an # empty executable. _LT_SYS_MODULE_PATH_AIX([$1]) _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl-blibpath:$libdir:'"$aix_libpath" _LT_TAGVAR(archive_expsym_cmds, $1)='$CC -o $output_objdir/$soname $libobjs $deplibs $wl'$no_entry_flag' $compiler_flags `if test -n "$allow_undefined_flag"; then func_echo_all "$wl$allow_undefined_flag"; else :; fi` $wl'$exp_sym_flag:\$export_symbols' '$shared_flag else if test ia64 = "$host_cpu"; then _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl-R $libdir:/usr/lib:/lib' _LT_TAGVAR(allow_undefined_flag, $1)="-z nodefs" _LT_TAGVAR(archive_expsym_cmds, $1)="\$CC $shared_flag"' -o $output_objdir/$soname $libobjs $deplibs '"\$wl$no_entry_flag"' $compiler_flags $wl$allow_undefined_flag '"\$wl$exp_sym_flag:\$export_symbols" else # Determine the default libpath from the value encoded in an # empty executable. _LT_SYS_MODULE_PATH_AIX([$1]) _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl-blibpath:$libdir:'"$aix_libpath" # Warning - without using the other run time loading flags, # -berok will link without error, but may produce a broken library. _LT_TAGVAR(no_undefined_flag, $1)=' $wl-bernotok' _LT_TAGVAR(allow_undefined_flag, $1)=' $wl-berok' if test yes = "$with_gnu_ld"; then # We only use this code for GNU lds that support --whole-archive. _LT_TAGVAR(whole_archive_flag_spec, $1)='$wl--whole-archive$convenience $wl--no-whole-archive' else # Exported symbols can be pulled into shared objects from archives _LT_TAGVAR(whole_archive_flag_spec, $1)='$convenience' fi _LT_TAGVAR(archive_cmds_need_lc, $1)=yes _LT_TAGVAR(archive_expsym_cmds, $1)='$RM -r $output_objdir/$realname.d~$MKDIR $output_objdir/$realname.d' # -brtl affects multiple linker settings, -berok does not and is overridden later compiler_flags_filtered='`func_echo_all "$compiler_flags " | $SED -e "s%-brtl\\([[, ]]\\)%-berok\\1%g"`' if test svr4 != "$with_aix_soname"; then # This is similar to how AIX traditionally builds its shared libraries. _LT_TAGVAR(archive_expsym_cmds, $1)="$_LT_TAGVAR(archive_expsym_cmds, $1)"'~$CC '$shared_flag_aix' -o $output_objdir/$realname.d/$soname $libobjs $deplibs $wl-bnoentry '$compiler_flags_filtered'$wl-bE:$export_symbols$allow_undefined_flag~$AR $AR_FLAGS $output_objdir/$libname$release.a $output_objdir/$realname.d/$soname' fi if test aix != "$with_aix_soname"; then _LT_TAGVAR(archive_expsym_cmds, $1)="$_LT_TAGVAR(archive_expsym_cmds, $1)"'~$CC '$shared_flag_svr4' -o $output_objdir/$realname.d/$shared_archive_member_spec.o $libobjs $deplibs $wl-bnoentry '$compiler_flags_filtered'$wl-bE:$export_symbols$allow_undefined_flag~$STRIP -e $output_objdir/$realname.d/$shared_archive_member_spec.o~( func_echo_all "#! $soname($shared_archive_member_spec.o)"; if test shr_64 = "$shared_archive_member_spec"; then func_echo_all "# 64"; else func_echo_all "# 32"; fi; cat $export_symbols ) > $output_objdir/$realname.d/$shared_archive_member_spec.imp~$AR $AR_FLAGS $output_objdir/$soname $output_objdir/$realname.d/$shared_archive_member_spec.o $output_objdir/$realname.d/$shared_archive_member_spec.imp' else # used by -dlpreopen to get the symbols _LT_TAGVAR(archive_expsym_cmds, $1)="$_LT_TAGVAR(archive_expsym_cmds, $1)"'~$MV $output_objdir/$realname.d/$soname $output_objdir' fi _LT_TAGVAR(archive_expsym_cmds, $1)="$_LT_TAGVAR(archive_expsym_cmds, $1)"'~$RM -r $output_objdir/$realname.d' fi fi ;; amigaos*) case $host_cpu in powerpc) # see comment about AmigaOS4 .so support _LT_TAGVAR(archive_cmds, $1)='$CC -shared $libobjs $deplibs $compiler_flags $wl-soname $wl$soname -o $lib' _LT_TAGVAR(archive_expsym_cmds, $1)='' ;; m68k) _LT_TAGVAR(archive_cmds, $1)='$RM $output_objdir/a2ixlibrary.data~$ECHO "#define NAME $libname" > $output_objdir/a2ixlibrary.data~$ECHO "#define LIBRARY_ID 1" >> $output_objdir/a2ixlibrary.data~$ECHO "#define VERSION $major" >> $output_objdir/a2ixlibrary.data~$ECHO "#define REVISION $revision" >> $output_objdir/a2ixlibrary.data~$AR $AR_FLAGS $lib $libobjs~$RANLIB $lib~(cd $output_objdir && a2ixlibrary -32)' _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='-L$libdir' _LT_TAGVAR(hardcode_minus_L, $1)=yes ;; esac ;; bsdi[[45]]*) _LT_TAGVAR(export_dynamic_flag_spec, $1)=-rdynamic ;; cygwin* | mingw* | pw32* | cegcc*) # When not using gcc, we currently assume that we are using # Microsoft Visual C++. # hardcode_libdir_flag_spec is actually meaningless, as there is # no search path for DLLs. case $cc_basename in cl*) # Native MSVC _LT_TAGVAR(hardcode_libdir_flag_spec, $1)=' ' _LT_TAGVAR(allow_undefined_flag, $1)=unsupported _LT_TAGVAR(always_export_symbols, $1)=yes _LT_TAGVAR(file_list_spec, $1)='@' # Tell ltmain to make .lib files, not .a files. libext=lib # Tell ltmain to make .dll files, not .so files. shrext_cmds=.dll # FIXME: Setting linknames here is a bad hack. _LT_TAGVAR(archive_cmds, $1)='$CC -o $output_objdir/$soname $libobjs $compiler_flags $deplibs -Wl,-DLL,-IMPLIB:"$tool_output_objdir$libname.dll.lib"~linknames=' _LT_TAGVAR(archive_expsym_cmds, $1)='if _LT_DLL_DEF_P([$export_symbols]); then cp "$export_symbols" "$output_objdir/$soname.def"; echo "$tool_output_objdir$soname.def" > "$output_objdir/$soname.exp"; else $SED -e '\''s/^/-link -EXPORT:/'\'' < $export_symbols > $output_objdir/$soname.exp; fi~ $CC -o $tool_output_objdir$soname $libobjs $compiler_flags $deplibs "@$tool_output_objdir$soname.exp" -Wl,-DLL,-IMPLIB:"$tool_output_objdir$libname.dll.lib"~ linknames=' # The linker will not automatically build a static lib if we build a DLL. # _LT_TAGVAR(old_archive_from_new_cmds, $1)='true' _LT_TAGVAR(enable_shared_with_static_runtimes, $1)=yes _LT_TAGVAR(exclude_expsyms, $1)='_NULL_IMPORT_DESCRIPTOR|_IMPORT_DESCRIPTOR_.*' _LT_TAGVAR(export_symbols_cmds, $1)='$NM $libobjs $convenience | $global_symbol_pipe | $SED -e '\''/^[[BCDGRS]][[ ]]/s/.*[[ ]]\([[^ ]]*\)/\1,DATA/'\'' | $SED -e '\''/^[[AITW]][[ ]]/s/.*[[ ]]//'\'' | sort | uniq > $export_symbols' # Don't use ranlib _LT_TAGVAR(old_postinstall_cmds, $1)='chmod 644 $oldlib' _LT_TAGVAR(postlink_cmds, $1)='lt_outputfile="@OUTPUT@"~ lt_tool_outputfile="@TOOL_OUTPUT@"~ case $lt_outputfile in *.exe|*.EXE) ;; *) lt_outputfile=$lt_outputfile.exe lt_tool_outputfile=$lt_tool_outputfile.exe ;; esac~ if test : != "$MANIFEST_TOOL" && test -f "$lt_outputfile.manifest"; then $MANIFEST_TOOL -manifest "$lt_tool_outputfile.manifest" -outputresource:"$lt_tool_outputfile" || exit 1; $RM "$lt_outputfile.manifest"; fi' ;; *) # Assume MSVC wrapper _LT_TAGVAR(hardcode_libdir_flag_spec, $1)=' ' _LT_TAGVAR(allow_undefined_flag, $1)=unsupported # Tell ltmain to make .lib files, not .a files. libext=lib # Tell ltmain to make .dll files, not .so files. shrext_cmds=.dll # FIXME: Setting linknames here is a bad hack. _LT_TAGVAR(archive_cmds, $1)='$CC -o $lib $libobjs $compiler_flags `func_echo_all "$deplibs" | $SED '\''s/ -lc$//'\''` -link -dll~linknames=' # The linker will automatically build a .lib file if we build a DLL. _LT_TAGVAR(old_archive_from_new_cmds, $1)='true' # FIXME: Should let the user specify the lib program. _LT_TAGVAR(old_archive_cmds, $1)='lib -OUT:$oldlib$oldobjs$old_deplibs' _LT_TAGVAR(enable_shared_with_static_runtimes, $1)=yes ;; esac ;; darwin* | rhapsody*) _LT_DARWIN_LINKER_FEATURES($1) ;; dgux*) _LT_TAGVAR(archive_cmds, $1)='$LD -G -h $soname -o $lib $libobjs $deplibs $linker_flags' _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='-L$libdir' _LT_TAGVAR(hardcode_shlibpath_var, $1)=no ;; # FreeBSD 2.2.[012] allows us to include c++rt0.o to get C++ constructor # support. Future versions do this automatically, but an explicit c++rt0.o # does not break anything, and helps significantly (at the cost of a little # extra space). freebsd2.2*) _LT_TAGVAR(archive_cmds, $1)='$LD -Bshareable -o $lib $libobjs $deplibs $linker_flags /usr/lib/c++rt0.o' _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='-R$libdir' _LT_TAGVAR(hardcode_direct, $1)=yes _LT_TAGVAR(hardcode_shlibpath_var, $1)=no ;; # Unfortunately, older versions of FreeBSD 2 do not have this feature. freebsd2.*) _LT_TAGVAR(archive_cmds, $1)='$LD -Bshareable -o $lib $libobjs $deplibs $linker_flags' _LT_TAGVAR(hardcode_direct, $1)=yes _LT_TAGVAR(hardcode_minus_L, $1)=yes _LT_TAGVAR(hardcode_shlibpath_var, $1)=no ;; # FreeBSD 3 and greater uses gcc -shared to do shared libraries. freebsd* | dragonfly*) _LT_TAGVAR(archive_cmds, $1)='$CC -shared $pic_flag -o $lib $libobjs $deplibs $compiler_flags' _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='-R$libdir' _LT_TAGVAR(hardcode_direct, $1)=yes _LT_TAGVAR(hardcode_shlibpath_var, $1)=no ;; hpux9*) if test yes = "$GCC"; then _LT_TAGVAR(archive_cmds, $1)='$RM $output_objdir/$soname~$CC -shared $pic_flag $wl+b $wl$install_libdir -o $output_objdir/$soname $libobjs $deplibs $compiler_flags~test "x$output_objdir/$soname" = "x$lib" || mv $output_objdir/$soname $lib' else _LT_TAGVAR(archive_cmds, $1)='$RM $output_objdir/$soname~$LD -b +b $install_libdir -o $output_objdir/$soname $libobjs $deplibs $linker_flags~test "x$output_objdir/$soname" = "x$lib" || mv $output_objdir/$soname $lib' fi _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl+b $wl$libdir' _LT_TAGVAR(hardcode_libdir_separator, $1)=: _LT_TAGVAR(hardcode_direct, $1)=yes # hardcode_minus_L: Not really in the search PATH, # but as the default location of the library. _LT_TAGVAR(hardcode_minus_L, $1)=yes _LT_TAGVAR(export_dynamic_flag_spec, $1)='$wl-E' ;; hpux10*) if test yes,no = "$GCC,$with_gnu_ld"; then _LT_TAGVAR(archive_cmds, $1)='$CC -shared $pic_flag $wl+h $wl$soname $wl+b $wl$install_libdir -o $lib $libobjs $deplibs $compiler_flags' else _LT_TAGVAR(archive_cmds, $1)='$LD -b +h $soname +b $install_libdir -o $lib $libobjs $deplibs $linker_flags' fi if test no = "$with_gnu_ld"; then _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl+b $wl$libdir' _LT_TAGVAR(hardcode_libdir_separator, $1)=: _LT_TAGVAR(hardcode_direct, $1)=yes _LT_TAGVAR(hardcode_direct_absolute, $1)=yes _LT_TAGVAR(export_dynamic_flag_spec, $1)='$wl-E' # hardcode_minus_L: Not really in the search PATH, # but as the default location of the library. _LT_TAGVAR(hardcode_minus_L, $1)=yes fi ;; hpux11*) if test yes,no = "$GCC,$with_gnu_ld"; then case $host_cpu in hppa*64*) _LT_TAGVAR(archive_cmds, $1)='$CC -shared $wl+h $wl$soname -o $lib $libobjs $deplibs $compiler_flags' ;; ia64*) _LT_TAGVAR(archive_cmds, $1)='$CC -shared $pic_flag $wl+h $wl$soname $wl+nodefaultrpath -o $lib $libobjs $deplibs $compiler_flags' ;; *) _LT_TAGVAR(archive_cmds, $1)='$CC -shared $pic_flag $wl+h $wl$soname $wl+b $wl$install_libdir -o $lib $libobjs $deplibs $compiler_flags' ;; esac else case $host_cpu in hppa*64*) _LT_TAGVAR(archive_cmds, $1)='$CC -b $wl+h $wl$soname -o $lib $libobjs $deplibs $compiler_flags' ;; ia64*) _LT_TAGVAR(archive_cmds, $1)='$CC -b $wl+h $wl$soname $wl+nodefaultrpath -o $lib $libobjs $deplibs $compiler_flags' ;; *) m4_if($1, [], [ # Older versions of the 11.00 compiler do not understand -b yet # (HP92453-01 A.11.01.20 doesn't, HP92453-01 B.11.X.35175-35176.GP does) _LT_LINKER_OPTION([if $CC understands -b], _LT_TAGVAR(lt_cv_prog_compiler__b, $1), [-b], [_LT_TAGVAR(archive_cmds, $1)='$CC -b $wl+h $wl$soname $wl+b $wl$install_libdir -o $lib $libobjs $deplibs $compiler_flags'], [_LT_TAGVAR(archive_cmds, $1)='$LD -b +h $soname +b $install_libdir -o $lib $libobjs $deplibs $linker_flags'])], [_LT_TAGVAR(archive_cmds, $1)='$CC -b $wl+h $wl$soname $wl+b $wl$install_libdir -o $lib $libobjs $deplibs $compiler_flags']) ;; esac fi if test no = "$with_gnu_ld"; then _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl+b $wl$libdir' _LT_TAGVAR(hardcode_libdir_separator, $1)=: case $host_cpu in hppa*64*|ia64*) _LT_TAGVAR(hardcode_direct, $1)=no _LT_TAGVAR(hardcode_shlibpath_var, $1)=no ;; *) _LT_TAGVAR(hardcode_direct, $1)=yes _LT_TAGVAR(hardcode_direct_absolute, $1)=yes _LT_TAGVAR(export_dynamic_flag_spec, $1)='$wl-E' # hardcode_minus_L: Not really in the search PATH, # but as the default location of the library. _LT_TAGVAR(hardcode_minus_L, $1)=yes ;; esac fi ;; irix5* | irix6* | nonstopux*) if test yes = "$GCC"; then _LT_TAGVAR(archive_cmds, $1)='$CC -shared $pic_flag $libobjs $deplibs $compiler_flags $wl-soname $wl$soname `test -n "$verstring" && func_echo_all "$wl-set_version $wl$verstring"` $wl-update_registry $wl$output_objdir/so_locations -o $lib' # Try to use the -exported_symbol ld option, if it does not # work, assume that -exports_file does not work either and # implicitly export all symbols. # This should be the same for all languages, so no per-tag cache variable. AC_CACHE_CHECK([whether the $host_os linker accepts -exported_symbol], [lt_cv_irix_exported_symbol], [save_LDFLAGS=$LDFLAGS LDFLAGS="$LDFLAGS -shared $wl-exported_symbol ${wl}foo $wl-update_registry $wl/dev/null" AC_LINK_IFELSE( [AC_LANG_SOURCE( [AC_LANG_CASE([C], [[int foo (void) { return 0; }]], [C++], [[int foo (void) { return 0; }]], [Fortran 77], [[ subroutine foo end]], [Fortran], [[ subroutine foo end]])])], [lt_cv_irix_exported_symbol=yes], [lt_cv_irix_exported_symbol=no]) LDFLAGS=$save_LDFLAGS]) if test yes = "$lt_cv_irix_exported_symbol"; then _LT_TAGVAR(archive_expsym_cmds, $1)='$CC -shared $pic_flag $libobjs $deplibs $compiler_flags $wl-soname $wl$soname `test -n "$verstring" && func_echo_all "$wl-set_version $wl$verstring"` $wl-update_registry $wl$output_objdir/so_locations $wl-exports_file $wl$export_symbols -o $lib' fi _LT_TAGVAR(link_all_deplibs, $1)=no else _LT_TAGVAR(archive_cmds, $1)='$CC -shared $libobjs $deplibs $compiler_flags -soname $soname `test -n "$verstring" && func_echo_all "-set_version $verstring"` -update_registry $output_objdir/so_locations -o $lib' _LT_TAGVAR(archive_expsym_cmds, $1)='$CC -shared $libobjs $deplibs $compiler_flags -soname $soname `test -n "$verstring" && func_echo_all "-set_version $verstring"` -update_registry $output_objdir/so_locations -exports_file $export_symbols -o $lib' fi _LT_TAGVAR(archive_cmds_need_lc, $1)='no' _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl-rpath $wl$libdir' _LT_TAGVAR(hardcode_libdir_separator, $1)=: _LT_TAGVAR(inherit_rpath, $1)=yes _LT_TAGVAR(link_all_deplibs, $1)=yes ;; linux*) case $cc_basename in tcc*) # Fabrice Bellard et al's Tiny C Compiler _LT_TAGVAR(ld_shlibs, $1)=yes _LT_TAGVAR(archive_cmds, $1)='$CC -shared $pic_flag -o $lib $libobjs $deplibs $compiler_flags' ;; esac ;; netbsd* | netbsdelf*-gnu) if echo __ELF__ | $CC -E - | $GREP __ELF__ >/dev/null; then _LT_TAGVAR(archive_cmds, $1)='$LD -Bshareable -o $lib $libobjs $deplibs $linker_flags' # a.out else _LT_TAGVAR(archive_cmds, $1)='$LD -shared -o $lib $libobjs $deplibs $linker_flags' # ELF fi _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='-R$libdir' _LT_TAGVAR(hardcode_direct, $1)=yes _LT_TAGVAR(hardcode_shlibpath_var, $1)=no ;; newsos6) _LT_TAGVAR(archive_cmds, $1)='$LD -G -h $soname -o $lib $libobjs $deplibs $linker_flags' _LT_TAGVAR(hardcode_direct, $1)=yes _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl-rpath $wl$libdir' _LT_TAGVAR(hardcode_libdir_separator, $1)=: _LT_TAGVAR(hardcode_shlibpath_var, $1)=no ;; *nto* | *qnx*) ;; openbsd* | bitrig*) if test -f /usr/libexec/ld.so; then _LT_TAGVAR(hardcode_direct, $1)=yes _LT_TAGVAR(hardcode_shlibpath_var, $1)=no _LT_TAGVAR(hardcode_direct_absolute, $1)=yes if test -z "`echo __ELF__ | $CC -E - | $GREP __ELF__`"; then _LT_TAGVAR(archive_cmds, $1)='$CC -shared $pic_flag -o $lib $libobjs $deplibs $compiler_flags' _LT_TAGVAR(archive_expsym_cmds, $1)='$CC -shared $pic_flag -o $lib $libobjs $deplibs $compiler_flags $wl-retain-symbols-file,$export_symbols' _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl-rpath,$libdir' _LT_TAGVAR(export_dynamic_flag_spec, $1)='$wl-E' else _LT_TAGVAR(archive_cmds, $1)='$CC -shared $pic_flag -o $lib $libobjs $deplibs $compiler_flags' _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl-rpath,$libdir' fi else _LT_TAGVAR(ld_shlibs, $1)=no fi ;; os2*) _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='-L$libdir' _LT_TAGVAR(hardcode_minus_L, $1)=yes _LT_TAGVAR(allow_undefined_flag, $1)=unsupported shrext_cmds=.dll _LT_TAGVAR(archive_cmds, $1)='$ECHO "LIBRARY ${soname%$shared_ext} INITINSTANCE TERMINSTANCE" > $output_objdir/$libname.def~ $ECHO "DESCRIPTION \"$libname\"" >> $output_objdir/$libname.def~ $ECHO "DATA MULTIPLE NONSHARED" >> $output_objdir/$libname.def~ $ECHO EXPORTS >> $output_objdir/$libname.def~ emxexp $libobjs | $SED /"_DLL_InitTerm"/d >> $output_objdir/$libname.def~ $CC -Zdll -Zcrtdll -o $output_objdir/$soname $libobjs $deplibs $compiler_flags $output_objdir/$libname.def~ emximp -o $lib $output_objdir/$libname.def' _LT_TAGVAR(archive_expsym_cmds, $1)='$ECHO "LIBRARY ${soname%$shared_ext} INITINSTANCE TERMINSTANCE" > $output_objdir/$libname.def~ $ECHO "DESCRIPTION \"$libname\"" >> $output_objdir/$libname.def~ $ECHO "DATA MULTIPLE NONSHARED" >> $output_objdir/$libname.def~ $ECHO EXPORTS >> $output_objdir/$libname.def~ prefix_cmds="$SED"~ if test EXPORTS = "`$SED 1q $export_symbols`"; then prefix_cmds="$prefix_cmds -e 1d"; fi~ prefix_cmds="$prefix_cmds -e \"s/^\(.*\)$/_\1/g\""~ cat $export_symbols | $prefix_cmds >> $output_objdir/$libname.def~ $CC -Zdll -Zcrtdll -o $output_objdir/$soname $libobjs $deplibs $compiler_flags $output_objdir/$libname.def~ emximp -o $lib $output_objdir/$libname.def' _LT_TAGVAR(old_archive_From_new_cmds, $1)='emximp -o $output_objdir/${libname}_dll.a $output_objdir/$libname.def' _LT_TAGVAR(enable_shared_with_static_runtimes, $1)=yes ;; osf3*) if test yes = "$GCC"; then _LT_TAGVAR(allow_undefined_flag, $1)=' $wl-expect_unresolved $wl\*' _LT_TAGVAR(archive_cmds, $1)='$CC -shared$allow_undefined_flag $libobjs $deplibs $compiler_flags $wl-soname $wl$soname `test -n "$verstring" && func_echo_all "$wl-set_version $wl$verstring"` $wl-update_registry $wl$output_objdir/so_locations -o $lib' else _LT_TAGVAR(allow_undefined_flag, $1)=' -expect_unresolved \*' _LT_TAGVAR(archive_cmds, $1)='$CC -shared$allow_undefined_flag $libobjs $deplibs $compiler_flags -soname $soname `test -n "$verstring" && func_echo_all "-set_version $verstring"` -update_registry $output_objdir/so_locations -o $lib' fi _LT_TAGVAR(archive_cmds_need_lc, $1)='no' _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl-rpath $wl$libdir' _LT_TAGVAR(hardcode_libdir_separator, $1)=: ;; osf4* | osf5*) # as osf3* with the addition of -msym flag if test yes = "$GCC"; then _LT_TAGVAR(allow_undefined_flag, $1)=' $wl-expect_unresolved $wl\*' _LT_TAGVAR(archive_cmds, $1)='$CC -shared$allow_undefined_flag $pic_flag $libobjs $deplibs $compiler_flags $wl-msym $wl-soname $wl$soname `test -n "$verstring" && func_echo_all "$wl-set_version $wl$verstring"` $wl-update_registry $wl$output_objdir/so_locations -o $lib' _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl-rpath $wl$libdir' else _LT_TAGVAR(allow_undefined_flag, $1)=' -expect_unresolved \*' _LT_TAGVAR(archive_cmds, $1)='$CC -shared$allow_undefined_flag $libobjs $deplibs $compiler_flags -msym -soname $soname `test -n "$verstring" && func_echo_all "-set_version $verstring"` -update_registry $output_objdir/so_locations -o $lib' _LT_TAGVAR(archive_expsym_cmds, $1)='for i in `cat $export_symbols`; do printf "%s %s\\n" -exported_symbol "\$i" >> $lib.exp; done; printf "%s\\n" "-hidden">> $lib.exp~ $CC -shared$allow_undefined_flag $wl-input $wl$lib.exp $compiler_flags $libobjs $deplibs -soname $soname `test -n "$verstring" && $ECHO "-set_version $verstring"` -update_registry $output_objdir/so_locations -o $lib~$RM $lib.exp' # Both c and cxx compiler support -rpath directly _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='-rpath $libdir' fi _LT_TAGVAR(archive_cmds_need_lc, $1)='no' _LT_TAGVAR(hardcode_libdir_separator, $1)=: ;; solaris*) _LT_TAGVAR(no_undefined_flag, $1)=' -z defs' if test yes = "$GCC"; then wlarc='$wl' _LT_TAGVAR(archive_cmds, $1)='$CC -shared $pic_flag $wl-z ${wl}text $wl-h $wl$soname -o $lib $libobjs $deplibs $compiler_flags' _LT_TAGVAR(archive_expsym_cmds, $1)='echo "{ global:" > $lib.exp~cat $export_symbols | $SED -e "s/\(.*\)/\1;/" >> $lib.exp~echo "local: *; };" >> $lib.exp~ $CC -shared $pic_flag $wl-z ${wl}text $wl-M $wl$lib.exp $wl-h $wl$soname -o $lib $libobjs $deplibs $compiler_flags~$RM $lib.exp' else case `$CC -V 2>&1` in *"Compilers 5.0"*) wlarc='' _LT_TAGVAR(archive_cmds, $1)='$LD -G$allow_undefined_flag -h $soname -o $lib $libobjs $deplibs $linker_flags' _LT_TAGVAR(archive_expsym_cmds, $1)='echo "{ global:" > $lib.exp~cat $export_symbols | $SED -e "s/\(.*\)/\1;/" >> $lib.exp~echo "local: *; };" >> $lib.exp~ $LD -G$allow_undefined_flag -M $lib.exp -h $soname -o $lib $libobjs $deplibs $linker_flags~$RM $lib.exp' ;; *) wlarc='$wl' _LT_TAGVAR(archive_cmds, $1)='$CC -G$allow_undefined_flag -h $soname -o $lib $libobjs $deplibs $compiler_flags' _LT_TAGVAR(archive_expsym_cmds, $1)='echo "{ global:" > $lib.exp~cat $export_symbols | $SED -e "s/\(.*\)/\1;/" >> $lib.exp~echo "local: *; };" >> $lib.exp~ $CC -G$allow_undefined_flag -M $lib.exp -h $soname -o $lib $libobjs $deplibs $compiler_flags~$RM $lib.exp' ;; esac fi _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='-R$libdir' _LT_TAGVAR(hardcode_shlibpath_var, $1)=no case $host_os in solaris2.[[0-5]] | solaris2.[[0-5]].*) ;; *) # The compiler driver will combine and reorder linker options, # but understands '-z linker_flag'. GCC discards it without '$wl', # but is careful enough not to reorder. # Supported since Solaris 2.6 (maybe 2.5.1?) if test yes = "$GCC"; then _LT_TAGVAR(whole_archive_flag_spec, $1)='$wl-z ${wl}allextract$convenience $wl-z ${wl}defaultextract' else _LT_TAGVAR(whole_archive_flag_spec, $1)='-z allextract$convenience -z defaultextract' fi ;; esac _LT_TAGVAR(link_all_deplibs, $1)=yes ;; sunos4*) if test sequent = "$host_vendor"; then # Use $CC to link under sequent, because it throws in some extra .o # files that make .init and .fini sections work. _LT_TAGVAR(archive_cmds, $1)='$CC -G $wl-h $soname -o $lib $libobjs $deplibs $compiler_flags' else _LT_TAGVAR(archive_cmds, $1)='$LD -assert pure-text -Bstatic -o $lib $libobjs $deplibs $linker_flags' fi _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='-L$libdir' _LT_TAGVAR(hardcode_direct, $1)=yes _LT_TAGVAR(hardcode_minus_L, $1)=yes _LT_TAGVAR(hardcode_shlibpath_var, $1)=no ;; sysv4) case $host_vendor in sni) _LT_TAGVAR(archive_cmds, $1)='$LD -G -h $soname -o $lib $libobjs $deplibs $linker_flags' _LT_TAGVAR(hardcode_direct, $1)=yes # is this really true??? ;; siemens) ## LD is ld it makes a PLAMLIB ## CC just makes a GrossModule. _LT_TAGVAR(archive_cmds, $1)='$LD -G -o $lib $libobjs $deplibs $linker_flags' _LT_TAGVAR(reload_cmds, $1)='$CC -r -o $output$reload_objs' _LT_TAGVAR(hardcode_direct, $1)=no ;; motorola) _LT_TAGVAR(archive_cmds, $1)='$LD -G -h $soname -o $lib $libobjs $deplibs $linker_flags' _LT_TAGVAR(hardcode_direct, $1)=no #Motorola manual says yes, but my tests say they lie ;; esac runpath_var='LD_RUN_PATH' _LT_TAGVAR(hardcode_shlibpath_var, $1)=no ;; sysv4.3*) _LT_TAGVAR(archive_cmds, $1)='$LD -G -h $soname -o $lib $libobjs $deplibs $linker_flags' _LT_TAGVAR(hardcode_shlibpath_var, $1)=no _LT_TAGVAR(export_dynamic_flag_spec, $1)='-Bexport' ;; sysv4*MP*) if test -d /usr/nec; then _LT_TAGVAR(archive_cmds, $1)='$LD -G -h $soname -o $lib $libobjs $deplibs $linker_flags' _LT_TAGVAR(hardcode_shlibpath_var, $1)=no runpath_var=LD_RUN_PATH hardcode_runpath_var=yes _LT_TAGVAR(ld_shlibs, $1)=yes fi ;; sysv4*uw2* | sysv5OpenUNIX* | sysv5UnixWare7.[[01]].[[10]]* | unixware7* | sco3.2v5.0.[[024]]*) _LT_TAGVAR(no_undefined_flag, $1)='$wl-z,text' _LT_TAGVAR(archive_cmds_need_lc, $1)=no _LT_TAGVAR(hardcode_shlibpath_var, $1)=no runpath_var='LD_RUN_PATH' if test yes = "$GCC"; then _LT_TAGVAR(archive_cmds, $1)='$CC -shared $wl-h,$soname -o $lib $libobjs $deplibs $compiler_flags' _LT_TAGVAR(archive_expsym_cmds, $1)='$CC -shared $wl-Bexport:$export_symbols $wl-h,$soname -o $lib $libobjs $deplibs $compiler_flags' else _LT_TAGVAR(archive_cmds, $1)='$CC -G $wl-h,$soname -o $lib $libobjs $deplibs $compiler_flags' _LT_TAGVAR(archive_expsym_cmds, $1)='$CC -G $wl-Bexport:$export_symbols $wl-h,$soname -o $lib $libobjs $deplibs $compiler_flags' fi ;; sysv5* | sco3.2v5* | sco5v6*) # Note: We CANNOT use -z defs as we might desire, because we do not # link with -lc, and that would cause any symbols used from libc to # always be unresolved, which means just about no library would # ever link correctly. If we're not using GNU ld we use -z text # though, which does catch some bad symbols but isn't as heavy-handed # as -z defs. _LT_TAGVAR(no_undefined_flag, $1)='$wl-z,text' _LT_TAGVAR(allow_undefined_flag, $1)='$wl-z,nodefs' _LT_TAGVAR(archive_cmds_need_lc, $1)=no _LT_TAGVAR(hardcode_shlibpath_var, $1)=no _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl-R,$libdir' _LT_TAGVAR(hardcode_libdir_separator, $1)=':' _LT_TAGVAR(link_all_deplibs, $1)=yes _LT_TAGVAR(export_dynamic_flag_spec, $1)='$wl-Bexport' runpath_var='LD_RUN_PATH' if test yes = "$GCC"; then _LT_TAGVAR(archive_cmds, $1)='$CC -shared $wl-h,$soname -o $lib $libobjs $deplibs $compiler_flags' _LT_TAGVAR(archive_expsym_cmds, $1)='$CC -shared $wl-Bexport:$export_symbols $wl-h,$soname -o $lib $libobjs $deplibs $compiler_flags' else _LT_TAGVAR(archive_cmds, $1)='$CC -G $wl-h,$soname -o $lib $libobjs $deplibs $compiler_flags' _LT_TAGVAR(archive_expsym_cmds, $1)='$CC -G $wl-Bexport:$export_symbols $wl-h,$soname -o $lib $libobjs $deplibs $compiler_flags' fi ;; uts4*) _LT_TAGVAR(archive_cmds, $1)='$LD -G -h $soname -o $lib $libobjs $deplibs $linker_flags' _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='-L$libdir' _LT_TAGVAR(hardcode_shlibpath_var, $1)=no ;; *) _LT_TAGVAR(ld_shlibs, $1)=no ;; esac if test sni = "$host_vendor"; then case $host in sysv4 | sysv4.2uw2* | sysv4.3* | sysv5*) _LT_TAGVAR(export_dynamic_flag_spec, $1)='$wl-Blargedynsym' ;; esac fi fi ]) AC_MSG_RESULT([$_LT_TAGVAR(ld_shlibs, $1)]) test no = "$_LT_TAGVAR(ld_shlibs, $1)" && can_build_shared=no _LT_TAGVAR(with_gnu_ld, $1)=$with_gnu_ld _LT_DECL([], [libext], [0], [Old archive suffix (normally "a")])dnl _LT_DECL([], [shrext_cmds], [1], [Shared library suffix (normally ".so")])dnl _LT_DECL([], [extract_expsyms_cmds], [2], [The commands to extract the exported symbol list from a shared archive]) # # Do we need to explicitly link libc? # case "x$_LT_TAGVAR(archive_cmds_need_lc, $1)" in x|xyes) # Assume -lc should be added _LT_TAGVAR(archive_cmds_need_lc, $1)=yes if test yes,yes = "$GCC,$enable_shared"; then case $_LT_TAGVAR(archive_cmds, $1) in *'~'*) # FIXME: we may have to deal with multi-command sequences. ;; '$CC '*) # Test whether the compiler implicitly links with -lc since on some # systems, -lgcc has to come before -lc. If gcc already passes -lc # to ld, don't add -lc before -lgcc. AC_CACHE_CHECK([whether -lc should be explicitly linked in], [lt_cv_]_LT_TAGVAR(archive_cmds_need_lc, $1), [$RM conftest* echo "$lt_simple_compile_test_code" > conftest.$ac_ext if AC_TRY_EVAL(ac_compile) 2>conftest.err; then soname=conftest lib=conftest libobjs=conftest.$ac_objext deplibs= wl=$_LT_TAGVAR(lt_prog_compiler_wl, $1) pic_flag=$_LT_TAGVAR(lt_prog_compiler_pic, $1) compiler_flags=-v linker_flags=-v verstring= output_objdir=. libname=conftest lt_save_allow_undefined_flag=$_LT_TAGVAR(allow_undefined_flag, $1) _LT_TAGVAR(allow_undefined_flag, $1)= if AC_TRY_EVAL(_LT_TAGVAR(archive_cmds, $1) 2\>\&1 \| $GREP \" -lc \" \>/dev/null 2\>\&1) then lt_cv_[]_LT_TAGVAR(archive_cmds_need_lc, $1)=no else lt_cv_[]_LT_TAGVAR(archive_cmds_need_lc, $1)=yes fi _LT_TAGVAR(allow_undefined_flag, $1)=$lt_save_allow_undefined_flag else cat conftest.err 1>&5 fi $RM conftest* ]) _LT_TAGVAR(archive_cmds_need_lc, $1)=$lt_cv_[]_LT_TAGVAR(archive_cmds_need_lc, $1) ;; esac fi ;; esac _LT_TAGDECL([build_libtool_need_lc], [archive_cmds_need_lc], [0], [Whether or not to add -lc for building shared libraries]) _LT_TAGDECL([allow_libtool_libs_with_static_runtimes], [enable_shared_with_static_runtimes], [0], [Whether or not to disallow shared libs when runtime libs are static]) _LT_TAGDECL([], [export_dynamic_flag_spec], [1], [Compiler flag to allow reflexive dlopens]) _LT_TAGDECL([], [whole_archive_flag_spec], [1], [Compiler flag to generate shared objects directly from archives]) _LT_TAGDECL([], [compiler_needs_object], [1], [Whether the compiler copes with passing no objects directly]) _LT_TAGDECL([], [old_archive_from_new_cmds], [2], [Create an old-style archive from a shared archive]) _LT_TAGDECL([], [old_archive_from_expsyms_cmds], [2], [Create a temporary old-style archive to link instead of a shared archive]) _LT_TAGDECL([], [archive_cmds], [2], [Commands used to build a shared archive]) _LT_TAGDECL([], [archive_expsym_cmds], [2]) _LT_TAGDECL([], [module_cmds], [2], [Commands used to build a loadable module if different from building a shared archive.]) _LT_TAGDECL([], [module_expsym_cmds], [2]) _LT_TAGDECL([], [with_gnu_ld], [1], [Whether we are building with GNU ld or not]) _LT_TAGDECL([], [allow_undefined_flag], [1], [Flag that allows shared libraries with undefined symbols to be built]) _LT_TAGDECL([], [no_undefined_flag], [1], [Flag that enforces no undefined symbols]) _LT_TAGDECL([], [hardcode_libdir_flag_spec], [1], [Flag to hardcode $libdir into a binary during linking. This must work even if $libdir does not exist]) _LT_TAGDECL([], [hardcode_libdir_separator], [1], [Whether we need a single "-rpath" flag with a separated argument]) _LT_TAGDECL([], [hardcode_direct], [0], [Set to "yes" if using DIR/libNAME$shared_ext during linking hardcodes DIR into the resulting binary]) _LT_TAGDECL([], [hardcode_direct_absolute], [0], [Set to "yes" if using DIR/libNAME$shared_ext during linking hardcodes DIR into the resulting binary and the resulting library dependency is "absolute", i.e impossible to change by setting $shlibpath_var if the library is relocated]) _LT_TAGDECL([], [hardcode_minus_L], [0], [Set to "yes" if using the -LDIR flag during linking hardcodes DIR into the resulting binary]) _LT_TAGDECL([], [hardcode_shlibpath_var], [0], [Set to "yes" if using SHLIBPATH_VAR=DIR during linking hardcodes DIR into the resulting binary]) _LT_TAGDECL([], [hardcode_automatic], [0], [Set to "yes" if building a shared library automatically hardcodes DIR into the library and all subsequent libraries and executables linked against it]) _LT_TAGDECL([], [inherit_rpath], [0], [Set to yes if linker adds runtime paths of dependent libraries to runtime path list]) _LT_TAGDECL([], [link_all_deplibs], [0], [Whether libtool must link a program against all its dependency libraries]) _LT_TAGDECL([], [always_export_symbols], [0], [Set to "yes" if exported symbols are required]) _LT_TAGDECL([], [export_symbols_cmds], [2], [The commands to list exported symbols]) _LT_TAGDECL([], [exclude_expsyms], [1], [Symbols that should not be listed in the preloaded symbols]) _LT_TAGDECL([], [include_expsyms], [1], [Symbols that must always be exported]) _LT_TAGDECL([], [prelink_cmds], [2], [Commands necessary for linking programs (against libraries) with templates]) _LT_TAGDECL([], [postlink_cmds], [2], [Commands necessary for finishing linking programs]) _LT_TAGDECL([], [file_list_spec], [1], [Specify filename containing input files]) dnl FIXME: Not yet implemented dnl _LT_TAGDECL([], [thread_safe_flag_spec], [1], dnl [Compiler flag to generate thread safe objects]) ])# _LT_LINKER_SHLIBS # _LT_LANG_C_CONFIG([TAG]) # ------------------------ # Ensure that the configuration variables for a C compiler are suitably # defined. These variables are subsequently used by _LT_CONFIG to write # the compiler configuration to 'libtool'. m4_defun([_LT_LANG_C_CONFIG], [m4_require([_LT_DECL_EGREP])dnl lt_save_CC=$CC AC_LANG_PUSH(C) # Source file extension for C test sources. ac_ext=c # Object file extension for compiled C test sources. objext=o _LT_TAGVAR(objext, $1)=$objext # Code to be used in simple compile tests lt_simple_compile_test_code="int some_variable = 0;" # Code to be used in simple link tests lt_simple_link_test_code='int main(){return(0);}' _LT_TAG_COMPILER # Save the default compiler, since it gets overwritten when the other # tags are being tested, and _LT_TAGVAR(compiler, []) is a NOP. compiler_DEFAULT=$CC # save warnings/boilerplate of simple test code _LT_COMPILER_BOILERPLATE _LT_LINKER_BOILERPLATE ## CAVEAT EMPTOR: ## There is no encapsulation within the following macros, do not change ## the running order or otherwise move them around unless you know exactly ## what you are doing... if test -n "$compiler"; then _LT_COMPILER_NO_RTTI($1) _LT_COMPILER_PIC($1) _LT_COMPILER_C_O($1) _LT_COMPILER_FILE_LOCKS($1) _LT_LINKER_SHLIBS($1) _LT_SYS_DYNAMIC_LINKER($1) _LT_LINKER_HARDCODE_LIBPATH($1) LT_SYS_DLOPEN_SELF _LT_CMD_STRIPLIB # Report what library types will actually be built AC_MSG_CHECKING([if libtool supports shared libraries]) AC_MSG_RESULT([$can_build_shared]) AC_MSG_CHECKING([whether to build shared libraries]) test no = "$can_build_shared" && enable_shared=no # On AIX, shared libraries and static libraries use the same namespace, and # are all built from PIC. case $host_os in aix3*) test yes = "$enable_shared" && enable_static=no if test -n "$RANLIB"; then archive_cmds="$archive_cmds~\$RANLIB \$lib" postinstall_cmds='$RANLIB $lib' fi ;; aix[[4-9]]*) if test ia64 != "$host_cpu"; then case $enable_shared,$with_aix_soname,$aix_use_runtimelinking in yes,aix,yes) ;; # shared object as lib.so file only yes,svr4,*) ;; # shared object as lib.so archive member only yes,*) enable_static=no ;; # shared object in lib.a archive as well esac fi ;; esac AC_MSG_RESULT([$enable_shared]) AC_MSG_CHECKING([whether to build static libraries]) # Make sure either enable_shared or enable_static is yes. test yes = "$enable_shared" || enable_static=yes AC_MSG_RESULT([$enable_static]) _LT_CONFIG($1) fi AC_LANG_POP CC=$lt_save_CC ])# _LT_LANG_C_CONFIG # _LT_LANG_CXX_CONFIG([TAG]) # -------------------------- # Ensure that the configuration variables for a C++ compiler are suitably # defined. These variables are subsequently used by _LT_CONFIG to write # the compiler configuration to 'libtool'. m4_defun([_LT_LANG_CXX_CONFIG], [m4_require([_LT_FILEUTILS_DEFAULTS])dnl m4_require([_LT_DECL_EGREP])dnl m4_require([_LT_PATH_MANIFEST_TOOL])dnl if test -n "$CXX" && ( test no != "$CXX" && ( (test g++ = "$CXX" && `g++ -v >/dev/null 2>&1` ) || (test g++ != "$CXX"))); then AC_PROG_CXXCPP else _lt_caught_CXX_error=yes fi AC_LANG_PUSH(C++) _LT_TAGVAR(archive_cmds_need_lc, $1)=no _LT_TAGVAR(allow_undefined_flag, $1)= _LT_TAGVAR(always_export_symbols, $1)=no _LT_TAGVAR(archive_expsym_cmds, $1)= _LT_TAGVAR(compiler_needs_object, $1)=no _LT_TAGVAR(export_dynamic_flag_spec, $1)= _LT_TAGVAR(hardcode_direct, $1)=no _LT_TAGVAR(hardcode_direct_absolute, $1)=no _LT_TAGVAR(hardcode_libdir_flag_spec, $1)= _LT_TAGVAR(hardcode_libdir_separator, $1)= _LT_TAGVAR(hardcode_minus_L, $1)=no _LT_TAGVAR(hardcode_shlibpath_var, $1)=unsupported _LT_TAGVAR(hardcode_automatic, $1)=no _LT_TAGVAR(inherit_rpath, $1)=no _LT_TAGVAR(module_cmds, $1)= _LT_TAGVAR(module_expsym_cmds, $1)= _LT_TAGVAR(link_all_deplibs, $1)=unknown _LT_TAGVAR(old_archive_cmds, $1)=$old_archive_cmds _LT_TAGVAR(reload_flag, $1)=$reload_flag _LT_TAGVAR(reload_cmds, $1)=$reload_cmds _LT_TAGVAR(no_undefined_flag, $1)= _LT_TAGVAR(whole_archive_flag_spec, $1)= _LT_TAGVAR(enable_shared_with_static_runtimes, $1)=no # Source file extension for C++ test sources. ac_ext=cpp # Object file extension for compiled C++ test sources. objext=o _LT_TAGVAR(objext, $1)=$objext # No sense in running all these tests if we already determined that # the CXX compiler isn't working. Some variables (like enable_shared) # are currently assumed to apply to all compilers on this platform, # and will be corrupted by setting them based on a non-working compiler. if test yes != "$_lt_caught_CXX_error"; then # Code to be used in simple compile tests lt_simple_compile_test_code="int some_variable = 0;" # Code to be used in simple link tests lt_simple_link_test_code='int main(int, char *[[]]) { return(0); }' # ltmain only uses $CC for tagged configurations so make sure $CC is set. _LT_TAG_COMPILER # save warnings/boilerplate of simple test code _LT_COMPILER_BOILERPLATE _LT_LINKER_BOILERPLATE # Allow CC to be a program name with arguments. lt_save_CC=$CC lt_save_CFLAGS=$CFLAGS lt_save_LD=$LD lt_save_GCC=$GCC GCC=$GXX lt_save_with_gnu_ld=$with_gnu_ld lt_save_path_LD=$lt_cv_path_LD if test -n "${lt_cv_prog_gnu_ldcxx+set}"; then lt_cv_prog_gnu_ld=$lt_cv_prog_gnu_ldcxx else $as_unset lt_cv_prog_gnu_ld fi if test -n "${lt_cv_path_LDCXX+set}"; then lt_cv_path_LD=$lt_cv_path_LDCXX else $as_unset lt_cv_path_LD fi test -z "${LDCXX+set}" || LD=$LDCXX CC=${CXX-"c++"} CFLAGS=$CXXFLAGS compiler=$CC _LT_TAGVAR(compiler, $1)=$CC _LT_CC_BASENAME([$compiler]) if test -n "$compiler"; then # We don't want -fno-exception when compiling C++ code, so set the # no_builtin_flag separately if test yes = "$GXX"; then _LT_TAGVAR(lt_prog_compiler_no_builtin_flag, $1)=' -fno-builtin' else _LT_TAGVAR(lt_prog_compiler_no_builtin_flag, $1)= fi if test yes = "$GXX"; then # Set up default GNU C++ configuration LT_PATH_LD # Check if GNU C++ uses GNU ld as the underlying linker, since the # archiving commands below assume that GNU ld is being used. if test yes = "$with_gnu_ld"; then _LT_TAGVAR(archive_cmds, $1)='$CC $pic_flag -shared -nostdlib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags $wl-soname $wl$soname -o $lib' _LT_TAGVAR(archive_expsym_cmds, $1)='$CC $pic_flag -shared -nostdlib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags $wl-soname $wl$soname $wl-retain-symbols-file $wl$export_symbols -o $lib' _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl-rpath $wl$libdir' _LT_TAGVAR(export_dynamic_flag_spec, $1)='$wl--export-dynamic' # If archive_cmds runs LD, not CC, wlarc should be empty # XXX I think wlarc can be eliminated in ltcf-cxx, but I need to # investigate it a little bit more. (MM) wlarc='$wl' # ancient GNU ld didn't support --whole-archive et. al. if eval "`$CC -print-prog-name=ld` --help 2>&1" | $GREP 'no-whole-archive' > /dev/null; then _LT_TAGVAR(whole_archive_flag_spec, $1)=$wlarc'--whole-archive$convenience '$wlarc'--no-whole-archive' else _LT_TAGVAR(whole_archive_flag_spec, $1)= fi else with_gnu_ld=no wlarc= # A generic and very simple default shared library creation # command for GNU C++ for the case where it uses the native # linker, instead of GNU ld. If possible, this setting should # overridden to take advantage of the native linker features on # the platform it is being used on. _LT_TAGVAR(archive_cmds, $1)='$CC -shared -nostdlib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags -o $lib' fi # Commands to make compiler produce verbose output that lists # what "hidden" libraries, object files and flags are used when # linking a shared library. output_verbose_link_cmd='$CC -shared $CFLAGS -v conftest.$objext 2>&1 | $GREP -v "^Configured with:" | $GREP "\-L"' else GXX=no with_gnu_ld=no wlarc= fi # PORTME: fill in a description of your system's C++ link characteristics AC_MSG_CHECKING([whether the $compiler linker ($LD) supports shared libraries]) _LT_TAGVAR(ld_shlibs, $1)=yes case $host_os in aix3*) # FIXME: insert proper C++ library support _LT_TAGVAR(ld_shlibs, $1)=no ;; aix[[4-9]]*) if test ia64 = "$host_cpu"; then # On IA64, the linker does run time linking by default, so we don't # have to do anything special. aix_use_runtimelinking=no exp_sym_flag='-Bexport' no_entry_flag= else aix_use_runtimelinking=no # Test if we are trying to use run time linking or normal # AIX style linking. If -brtl is somewhere in LDFLAGS, we # have runtime linking enabled, and use it for executables. # For shared libraries, we enable/disable runtime linking # depending on the kind of the shared library created - # when "with_aix_soname,aix_use_runtimelinking" is: # "aix,no" lib.a(lib.so.V) shared, rtl:no, for executables # "aix,yes" lib.so shared, rtl:yes, for executables # lib.a static archive # "both,no" lib.so.V(shr.o) shared, rtl:yes # lib.a(lib.so.V) shared, rtl:no, for executables # "both,yes" lib.so.V(shr.o) shared, rtl:yes, for executables # lib.a(lib.so.V) shared, rtl:no # "svr4,*" lib.so.V(shr.o) shared, rtl:yes, for executables # lib.a static archive case $host_os in aix4.[[23]]|aix4.[[23]].*|aix[[5-9]]*) for ld_flag in $LDFLAGS; do case $ld_flag in *-brtl*) aix_use_runtimelinking=yes break ;; esac done if test svr4,no = "$with_aix_soname,$aix_use_runtimelinking"; then # With aix-soname=svr4, we create the lib.so.V shared archives only, # so we don't have lib.a shared libs to link our executables. # We have to force runtime linking in this case. aix_use_runtimelinking=yes LDFLAGS="$LDFLAGS -Wl,-brtl" fi ;; esac exp_sym_flag='-bexport' no_entry_flag='-bnoentry' fi # When large executables or shared objects are built, AIX ld can # have problems creating the table of contents. If linking a library # or program results in "error TOC overflow" add -mminimal-toc to # CXXFLAGS/CFLAGS for g++/gcc. In the cases where that is not # enough to fix the problem, add -Wl,-bbigtoc to LDFLAGS. _LT_TAGVAR(archive_cmds, $1)='' _LT_TAGVAR(hardcode_direct, $1)=yes _LT_TAGVAR(hardcode_direct_absolute, $1)=yes _LT_TAGVAR(hardcode_libdir_separator, $1)=':' _LT_TAGVAR(link_all_deplibs, $1)=yes _LT_TAGVAR(file_list_spec, $1)='$wl-f,' case $with_aix_soname,$aix_use_runtimelinking in aix,*) ;; # no import file svr4,* | *,yes) # use import file # The Import File defines what to hardcode. _LT_TAGVAR(hardcode_direct, $1)=no _LT_TAGVAR(hardcode_direct_absolute, $1)=no ;; esac if test yes = "$GXX"; then case $host_os in aix4.[[012]]|aix4.[[012]].*) # We only want to do this on AIX 4.2 and lower, the check # below for broken collect2 doesn't work under 4.3+ collect2name=`$CC -print-prog-name=collect2` if test -f "$collect2name" && strings "$collect2name" | $GREP resolve_lib_name >/dev/null then # We have reworked collect2 : else # We have old collect2 _LT_TAGVAR(hardcode_direct, $1)=unsupported # It fails to find uninstalled libraries when the uninstalled # path is not listed in the libpath. Setting hardcode_minus_L # to unsupported forces relinking _LT_TAGVAR(hardcode_minus_L, $1)=yes _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='-L$libdir' _LT_TAGVAR(hardcode_libdir_separator, $1)= fi esac shared_flag='-shared' if test yes = "$aix_use_runtimelinking"; then shared_flag=$shared_flag' $wl-G' fi # Need to ensure runtime linking is disabled for the traditional # shared library, or the linker may eventually find shared libraries # /with/ Import File - we do not want to mix them. shared_flag_aix='-shared' shared_flag_svr4='-shared $wl-G' else # not using gcc if test ia64 = "$host_cpu"; then # VisualAge C++, Version 5.5 for AIX 5L for IA-64, Beta 3 Release # chokes on -Wl,-G. The following line is correct: shared_flag='-G' else if test yes = "$aix_use_runtimelinking"; then shared_flag='$wl-G' else shared_flag='$wl-bM:SRE' fi shared_flag_aix='$wl-bM:SRE' shared_flag_svr4='$wl-G' fi fi _LT_TAGVAR(export_dynamic_flag_spec, $1)='$wl-bexpall' # It seems that -bexpall does not export symbols beginning with # underscore (_), so it is better to generate a list of symbols to # export. _LT_TAGVAR(always_export_symbols, $1)=yes if test aix,yes = "$with_aix_soname,$aix_use_runtimelinking"; then # Warning - without using the other runtime loading flags (-brtl), # -berok will link without error, but may produce a broken library. # The "-G" linker flag allows undefined symbols. _LT_TAGVAR(no_undefined_flag, $1)='-bernotok' # Determine the default libpath from the value encoded in an empty # executable. _LT_SYS_MODULE_PATH_AIX([$1]) _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl-blibpath:$libdir:'"$aix_libpath" _LT_TAGVAR(archive_expsym_cmds, $1)='$CC -o $output_objdir/$soname $libobjs $deplibs $wl'$no_entry_flag' $compiler_flags `if test -n "$allow_undefined_flag"; then func_echo_all "$wl$allow_undefined_flag"; else :; fi` $wl'$exp_sym_flag:\$export_symbols' '$shared_flag else if test ia64 = "$host_cpu"; then _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl-R $libdir:/usr/lib:/lib' _LT_TAGVAR(allow_undefined_flag, $1)="-z nodefs" _LT_TAGVAR(archive_expsym_cmds, $1)="\$CC $shared_flag"' -o $output_objdir/$soname $libobjs $deplibs '"\$wl$no_entry_flag"' $compiler_flags $wl$allow_undefined_flag '"\$wl$exp_sym_flag:\$export_symbols" else # Determine the default libpath from the value encoded in an # empty executable. _LT_SYS_MODULE_PATH_AIX([$1]) _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl-blibpath:$libdir:'"$aix_libpath" # Warning - without using the other run time loading flags, # -berok will link without error, but may produce a broken library. _LT_TAGVAR(no_undefined_flag, $1)=' $wl-bernotok' _LT_TAGVAR(allow_undefined_flag, $1)=' $wl-berok' if test yes = "$with_gnu_ld"; then # We only use this code for GNU lds that support --whole-archive. _LT_TAGVAR(whole_archive_flag_spec, $1)='$wl--whole-archive$convenience $wl--no-whole-archive' else # Exported symbols can be pulled into shared objects from archives _LT_TAGVAR(whole_archive_flag_spec, $1)='$convenience' fi _LT_TAGVAR(archive_cmds_need_lc, $1)=yes _LT_TAGVAR(archive_expsym_cmds, $1)='$RM -r $output_objdir/$realname.d~$MKDIR $output_objdir/$realname.d' # -brtl affects multiple linker settings, -berok does not and is overridden later compiler_flags_filtered='`func_echo_all "$compiler_flags " | $SED -e "s%-brtl\\([[, ]]\\)%-berok\\1%g"`' if test svr4 != "$with_aix_soname"; then # This is similar to how AIX traditionally builds its shared # libraries. Need -bnortl late, we may have -brtl in LDFLAGS. _LT_TAGVAR(archive_expsym_cmds, $1)="$_LT_TAGVAR(archive_expsym_cmds, $1)"'~$CC '$shared_flag_aix' -o $output_objdir/$realname.d/$soname $libobjs $deplibs $wl-bnoentry '$compiler_flags_filtered'$wl-bE:$export_symbols$allow_undefined_flag~$AR $AR_FLAGS $output_objdir/$libname$release.a $output_objdir/$realname.d/$soname' fi if test aix != "$with_aix_soname"; then _LT_TAGVAR(archive_expsym_cmds, $1)="$_LT_TAGVAR(archive_expsym_cmds, $1)"'~$CC '$shared_flag_svr4' -o $output_objdir/$realname.d/$shared_archive_member_spec.o $libobjs $deplibs $wl-bnoentry '$compiler_flags_filtered'$wl-bE:$export_symbols$allow_undefined_flag~$STRIP -e $output_objdir/$realname.d/$shared_archive_member_spec.o~( func_echo_all "#! $soname($shared_archive_member_spec.o)"; if test shr_64 = "$shared_archive_member_spec"; then func_echo_all "# 64"; else func_echo_all "# 32"; fi; cat $export_symbols ) > $output_objdir/$realname.d/$shared_archive_member_spec.imp~$AR $AR_FLAGS $output_objdir/$soname $output_objdir/$realname.d/$shared_archive_member_spec.o $output_objdir/$realname.d/$shared_archive_member_spec.imp' else # used by -dlpreopen to get the symbols _LT_TAGVAR(archive_expsym_cmds, $1)="$_LT_TAGVAR(archive_expsym_cmds, $1)"'~$MV $output_objdir/$realname.d/$soname $output_objdir' fi _LT_TAGVAR(archive_expsym_cmds, $1)="$_LT_TAGVAR(archive_expsym_cmds, $1)"'~$RM -r $output_objdir/$realname.d' fi fi ;; beos*) if $LD --help 2>&1 | $GREP ': supported targets:.* elf' > /dev/null; then _LT_TAGVAR(allow_undefined_flag, $1)=unsupported # Joseph Beckenbach says some releases of gcc # support --undefined. This deserves some investigation. FIXME _LT_TAGVAR(archive_cmds, $1)='$CC -nostart $libobjs $deplibs $compiler_flags $wl-soname $wl$soname -o $lib' else _LT_TAGVAR(ld_shlibs, $1)=no fi ;; chorus*) case $cc_basename in *) # FIXME: insert proper C++ library support _LT_TAGVAR(ld_shlibs, $1)=no ;; esac ;; cygwin* | mingw* | pw32* | cegcc*) case $GXX,$cc_basename in ,cl* | no,cl*) # Native MSVC # hardcode_libdir_flag_spec is actually meaningless, as there is # no search path for DLLs. _LT_TAGVAR(hardcode_libdir_flag_spec, $1)=' ' _LT_TAGVAR(allow_undefined_flag, $1)=unsupported _LT_TAGVAR(always_export_symbols, $1)=yes _LT_TAGVAR(file_list_spec, $1)='@' # Tell ltmain to make .lib files, not .a files. libext=lib # Tell ltmain to make .dll files, not .so files. shrext_cmds=.dll # FIXME: Setting linknames here is a bad hack. _LT_TAGVAR(archive_cmds, $1)='$CC -o $output_objdir/$soname $libobjs $compiler_flags $deplibs -Wl,-DLL,-IMPLIB:"$tool_output_objdir$libname.dll.lib"~linknames=' _LT_TAGVAR(archive_expsym_cmds, $1)='if _LT_DLL_DEF_P([$export_symbols]); then cp "$export_symbols" "$output_objdir/$soname.def"; echo "$tool_output_objdir$soname.def" > "$output_objdir/$soname.exp"; else $SED -e '\''s/^/-link -EXPORT:/'\'' < $export_symbols > $output_objdir/$soname.exp; fi~ $CC -o $tool_output_objdir$soname $libobjs $compiler_flags $deplibs "@$tool_output_objdir$soname.exp" -Wl,-DLL,-IMPLIB:"$tool_output_objdir$libname.dll.lib"~ linknames=' # The linker will not automatically build a static lib if we build a DLL. # _LT_TAGVAR(old_archive_from_new_cmds, $1)='true' _LT_TAGVAR(enable_shared_with_static_runtimes, $1)=yes # Don't use ranlib _LT_TAGVAR(old_postinstall_cmds, $1)='chmod 644 $oldlib' _LT_TAGVAR(postlink_cmds, $1)='lt_outputfile="@OUTPUT@"~ lt_tool_outputfile="@TOOL_OUTPUT@"~ case $lt_outputfile in *.exe|*.EXE) ;; *) lt_outputfile=$lt_outputfile.exe lt_tool_outputfile=$lt_tool_outputfile.exe ;; esac~ func_to_tool_file "$lt_outputfile"~ if test : != "$MANIFEST_TOOL" && test -f "$lt_outputfile.manifest"; then $MANIFEST_TOOL -manifest "$lt_tool_outputfile.manifest" -outputresource:"$lt_tool_outputfile" || exit 1; $RM "$lt_outputfile.manifest"; fi' ;; *) # g++ # _LT_TAGVAR(hardcode_libdir_flag_spec, $1) is actually meaningless, # as there is no search path for DLLs. _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='-L$libdir' _LT_TAGVAR(export_dynamic_flag_spec, $1)='$wl--export-all-symbols' _LT_TAGVAR(allow_undefined_flag, $1)=unsupported _LT_TAGVAR(always_export_symbols, $1)=no _LT_TAGVAR(enable_shared_with_static_runtimes, $1)=yes if $LD --help 2>&1 | $GREP 'auto-import' > /dev/null; then _LT_TAGVAR(archive_cmds, $1)='$CC -shared -nostdlib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags -o $output_objdir/$soname $wl--enable-auto-image-base -Xlinker --out-implib -Xlinker $lib' # If the export-symbols file already is a .def file, use it as # is; otherwise, prepend EXPORTS... _LT_TAGVAR(archive_expsym_cmds, $1)='if _LT_DLL_DEF_P([$export_symbols]); then cp $export_symbols $output_objdir/$soname.def; else echo EXPORTS > $output_objdir/$soname.def; cat $export_symbols >> $output_objdir/$soname.def; fi~ $CC -shared -nostdlib $output_objdir/$soname.def $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags -o $output_objdir/$soname $wl--enable-auto-image-base -Xlinker --out-implib -Xlinker $lib' else _LT_TAGVAR(ld_shlibs, $1)=no fi ;; esac ;; darwin* | rhapsody*) _LT_DARWIN_LINKER_FEATURES($1) ;; os2*) _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='-L$libdir' _LT_TAGVAR(hardcode_minus_L, $1)=yes _LT_TAGVAR(allow_undefined_flag, $1)=unsupported shrext_cmds=.dll _LT_TAGVAR(archive_cmds, $1)='$ECHO "LIBRARY ${soname%$shared_ext} INITINSTANCE TERMINSTANCE" > $output_objdir/$libname.def~ $ECHO "DESCRIPTION \"$libname\"" >> $output_objdir/$libname.def~ $ECHO "DATA MULTIPLE NONSHARED" >> $output_objdir/$libname.def~ $ECHO EXPORTS >> $output_objdir/$libname.def~ emxexp $libobjs | $SED /"_DLL_InitTerm"/d >> $output_objdir/$libname.def~ $CC -Zdll -Zcrtdll -o $output_objdir/$soname $libobjs $deplibs $compiler_flags $output_objdir/$libname.def~ emximp -o $lib $output_objdir/$libname.def' _LT_TAGVAR(archive_expsym_cmds, $1)='$ECHO "LIBRARY ${soname%$shared_ext} INITINSTANCE TERMINSTANCE" > $output_objdir/$libname.def~ $ECHO "DESCRIPTION \"$libname\"" >> $output_objdir/$libname.def~ $ECHO "DATA MULTIPLE NONSHARED" >> $output_objdir/$libname.def~ $ECHO EXPORTS >> $output_objdir/$libname.def~ prefix_cmds="$SED"~ if test EXPORTS = "`$SED 1q $export_symbols`"; then prefix_cmds="$prefix_cmds -e 1d"; fi~ prefix_cmds="$prefix_cmds -e \"s/^\(.*\)$/_\1/g\""~ cat $export_symbols | $prefix_cmds >> $output_objdir/$libname.def~ $CC -Zdll -Zcrtdll -o $output_objdir/$soname $libobjs $deplibs $compiler_flags $output_objdir/$libname.def~ emximp -o $lib $output_objdir/$libname.def' _LT_TAGVAR(old_archive_From_new_cmds, $1)='emximp -o $output_objdir/${libname}_dll.a $output_objdir/$libname.def' _LT_TAGVAR(enable_shared_with_static_runtimes, $1)=yes ;; dgux*) case $cc_basename in ec++*) # FIXME: insert proper C++ library support _LT_TAGVAR(ld_shlibs, $1)=no ;; ghcx*) # Green Hills C++ Compiler # FIXME: insert proper C++ library support _LT_TAGVAR(ld_shlibs, $1)=no ;; *) # FIXME: insert proper C++ library support _LT_TAGVAR(ld_shlibs, $1)=no ;; esac ;; freebsd2.*) # C++ shared libraries reported to be fairly broken before # switch to ELF _LT_TAGVAR(ld_shlibs, $1)=no ;; freebsd-elf*) _LT_TAGVAR(archive_cmds_need_lc, $1)=no ;; freebsd* | dragonfly*) # FreeBSD 3 and later use GNU C++ and GNU ld with standard ELF # conventions _LT_TAGVAR(ld_shlibs, $1)=yes ;; haiku*) _LT_TAGVAR(archive_cmds, $1)='$CC -shared $libobjs $deplibs $compiler_flags $wl-soname $wl$soname -o $lib' _LT_TAGVAR(link_all_deplibs, $1)=yes ;; hpux9*) _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl+b $wl$libdir' _LT_TAGVAR(hardcode_libdir_separator, $1)=: _LT_TAGVAR(export_dynamic_flag_spec, $1)='$wl-E' _LT_TAGVAR(hardcode_direct, $1)=yes _LT_TAGVAR(hardcode_minus_L, $1)=yes # Not in the search PATH, # but as the default # location of the library. case $cc_basename in CC*) # FIXME: insert proper C++ library support _LT_TAGVAR(ld_shlibs, $1)=no ;; aCC*) _LT_TAGVAR(archive_cmds, $1)='$RM $output_objdir/$soname~$CC -b $wl+b $wl$install_libdir -o $output_objdir/$soname $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags~test "x$output_objdir/$soname" = "x$lib" || mv $output_objdir/$soname $lib' # Commands to make compiler produce verbose output that lists # what "hidden" libraries, object files and flags are used when # linking a shared library. # # There doesn't appear to be a way to prevent this compiler from # explicitly linking system object files so we need to strip them # from the output so that they don't get included in the library # dependencies. output_verbose_link_cmd='templist=`($CC -b $CFLAGS -v conftest.$objext 2>&1) | $EGREP "\-L"`; list= ; for z in $templist; do case $z in conftest.$objext) list="$list $z";; *.$objext);; *) list="$list $z";;esac; done; func_echo_all "$list"' ;; *) if test yes = "$GXX"; then _LT_TAGVAR(archive_cmds, $1)='$RM $output_objdir/$soname~$CC -shared -nostdlib $pic_flag $wl+b $wl$install_libdir -o $output_objdir/$soname $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags~test "x$output_objdir/$soname" = "x$lib" || mv $output_objdir/$soname $lib' else # FIXME: insert proper C++ library support _LT_TAGVAR(ld_shlibs, $1)=no fi ;; esac ;; hpux10*|hpux11*) if test no = "$with_gnu_ld"; then _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl+b $wl$libdir' _LT_TAGVAR(hardcode_libdir_separator, $1)=: case $host_cpu in hppa*64*|ia64*) ;; *) _LT_TAGVAR(export_dynamic_flag_spec, $1)='$wl-E' ;; esac fi case $host_cpu in hppa*64*|ia64*) _LT_TAGVAR(hardcode_direct, $1)=no _LT_TAGVAR(hardcode_shlibpath_var, $1)=no ;; *) _LT_TAGVAR(hardcode_direct, $1)=yes _LT_TAGVAR(hardcode_direct_absolute, $1)=yes _LT_TAGVAR(hardcode_minus_L, $1)=yes # Not in the search PATH, # but as the default # location of the library. ;; esac case $cc_basename in CC*) # FIXME: insert proper C++ library support _LT_TAGVAR(ld_shlibs, $1)=no ;; aCC*) case $host_cpu in hppa*64*) _LT_TAGVAR(archive_cmds, $1)='$CC -b $wl+h $wl$soname -o $lib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags' ;; ia64*) _LT_TAGVAR(archive_cmds, $1)='$CC -b $wl+h $wl$soname $wl+nodefaultrpath -o $lib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags' ;; *) _LT_TAGVAR(archive_cmds, $1)='$CC -b $wl+h $wl$soname $wl+b $wl$install_libdir -o $lib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags' ;; esac # Commands to make compiler produce verbose output that lists # what "hidden" libraries, object files and flags are used when # linking a shared library. # # There doesn't appear to be a way to prevent this compiler from # explicitly linking system object files so we need to strip them # from the output so that they don't get included in the library # dependencies. output_verbose_link_cmd='templist=`($CC -b $CFLAGS -v conftest.$objext 2>&1) | $GREP "\-L"`; list= ; for z in $templist; do case $z in conftest.$objext) list="$list $z";; *.$objext);; *) list="$list $z";;esac; done; func_echo_all "$list"' ;; *) if test yes = "$GXX"; then if test no = "$with_gnu_ld"; then case $host_cpu in hppa*64*) _LT_TAGVAR(archive_cmds, $1)='$CC -shared -nostdlib -fPIC $wl+h $wl$soname -o $lib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags' ;; ia64*) _LT_TAGVAR(archive_cmds, $1)='$CC -shared -nostdlib $pic_flag $wl+h $wl$soname $wl+nodefaultrpath -o $lib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags' ;; *) _LT_TAGVAR(archive_cmds, $1)='$CC -shared -nostdlib $pic_flag $wl+h $wl$soname $wl+b $wl$install_libdir -o $lib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags' ;; esac fi else # FIXME: insert proper C++ library support _LT_TAGVAR(ld_shlibs, $1)=no fi ;; esac ;; interix[[3-9]]*) _LT_TAGVAR(hardcode_direct, $1)=no _LT_TAGVAR(hardcode_shlibpath_var, $1)=no _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl-rpath,$libdir' _LT_TAGVAR(export_dynamic_flag_spec, $1)='$wl-E' # Hack: On Interix 3.x, we cannot compile PIC because of a broken gcc. # Instead, shared libraries are loaded at an image base (0x10000000 by # default) and relocated if they conflict, which is a slow very memory # consuming and fragmenting process. To avoid this, we pick a random, # 256 KiB-aligned image base between 0x50000000 and 0x6FFC0000 at link # time. Moving up from 0x10000000 also allows more sbrk(2) space. _LT_TAGVAR(archive_cmds, $1)='$CC -shared $pic_flag $libobjs $deplibs $compiler_flags $wl-h,$soname $wl--image-base,`expr ${RANDOM-$$} % 4096 / 2 \* 262144 + 1342177280` -o $lib' _LT_TAGVAR(archive_expsym_cmds, $1)='sed "s|^|_|" $export_symbols >$output_objdir/$soname.expsym~$CC -shared $pic_flag $libobjs $deplibs $compiler_flags $wl-h,$soname $wl--retain-symbols-file,$output_objdir/$soname.expsym $wl--image-base,`expr ${RANDOM-$$} % 4096 / 2 \* 262144 + 1342177280` -o $lib' ;; irix5* | irix6*) case $cc_basename in CC*) # SGI C++ _LT_TAGVAR(archive_cmds, $1)='$CC -shared -all -multigot $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags -soname $soname `test -n "$verstring" && func_echo_all "-set_version $verstring"` -update_registry $output_objdir/so_locations -o $lib' # Archives containing C++ object files must be created using # "CC -ar", where "CC" is the IRIX C++ compiler. This is # necessary to make sure instantiated templates are included # in the archive. _LT_TAGVAR(old_archive_cmds, $1)='$CC -ar -WR,-u -o $oldlib $oldobjs' ;; *) if test yes = "$GXX"; then if test no = "$with_gnu_ld"; then _LT_TAGVAR(archive_cmds, $1)='$CC -shared $pic_flag -nostdlib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags $wl-soname $wl$soname `test -n "$verstring" && func_echo_all "$wl-set_version $wl$verstring"` $wl-update_registry $wl$output_objdir/so_locations -o $lib' else _LT_TAGVAR(archive_cmds, $1)='$CC -shared $pic_flag -nostdlib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags $wl-soname $wl$soname `test -n "$verstring" && func_echo_all "$wl-set_version $wl$verstring"` -o $lib' fi fi _LT_TAGVAR(link_all_deplibs, $1)=yes ;; esac _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl-rpath $wl$libdir' _LT_TAGVAR(hardcode_libdir_separator, $1)=: _LT_TAGVAR(inherit_rpath, $1)=yes ;; linux* | k*bsd*-gnu | kopensolaris*-gnu | gnu*) case $cc_basename in KCC*) # Kuck and Associates, Inc. (KAI) C++ Compiler # KCC will only create a shared library if the output file # ends with ".so" (or ".sl" for HP-UX), so rename the library # to its proper name (with version) after linking. _LT_TAGVAR(archive_cmds, $1)='tempext=`echo $shared_ext | $SED -e '\''s/\([[^()0-9A-Za-z{}]]\)/\\\\\1/g'\''`; templib=`echo $lib | $SED -e "s/\$tempext\..*/.so/"`; $CC $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags --soname $soname -o \$templib; mv \$templib $lib' _LT_TAGVAR(archive_expsym_cmds, $1)='tempext=`echo $shared_ext | $SED -e '\''s/\([[^()0-9A-Za-z{}]]\)/\\\\\1/g'\''`; templib=`echo $lib | $SED -e "s/\$tempext\..*/.so/"`; $CC $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags --soname $soname -o \$templib $wl-retain-symbols-file,$export_symbols; mv \$templib $lib' # Commands to make compiler produce verbose output that lists # what "hidden" libraries, object files and flags are used when # linking a shared library. # # There doesn't appear to be a way to prevent this compiler from # explicitly linking system object files so we need to strip them # from the output so that they don't get included in the library # dependencies. output_verbose_link_cmd='templist=`$CC $CFLAGS -v conftest.$objext -o libconftest$shared_ext 2>&1 | $GREP "ld"`; rm -f libconftest$shared_ext; list= ; for z in $templist; do case $z in conftest.$objext) list="$list $z";; *.$objext);; *) list="$list $z";;esac; done; func_echo_all "$list"' _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl-rpath,$libdir' _LT_TAGVAR(export_dynamic_flag_spec, $1)='$wl--export-dynamic' # Archives containing C++ object files must be created using # "CC -Bstatic", where "CC" is the KAI C++ compiler. _LT_TAGVAR(old_archive_cmds, $1)='$CC -Bstatic -o $oldlib $oldobjs' ;; icpc* | ecpc* ) # Intel C++ with_gnu_ld=yes # version 8.0 and above of icpc choke on multiply defined symbols # if we add $predep_objects and $postdep_objects, however 7.1 and # earlier do not add the objects themselves. case `$CC -V 2>&1` in *"Version 7."*) _LT_TAGVAR(archive_cmds, $1)='$CC -shared $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags $wl-soname $wl$soname -o $lib' _LT_TAGVAR(archive_expsym_cmds, $1)='$CC -shared $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags $wl-soname $wl$soname $wl-retain-symbols-file $wl$export_symbols -o $lib' ;; *) # Version 8.0 or newer tmp_idyn= case $host_cpu in ia64*) tmp_idyn=' -i_dynamic';; esac _LT_TAGVAR(archive_cmds, $1)='$CC -shared'"$tmp_idyn"' $libobjs $deplibs $compiler_flags $wl-soname $wl$soname -o $lib' _LT_TAGVAR(archive_expsym_cmds, $1)='$CC -shared'"$tmp_idyn"' $libobjs $deplibs $compiler_flags $wl-soname $wl$soname $wl-retain-symbols-file $wl$export_symbols -o $lib' ;; esac _LT_TAGVAR(archive_cmds_need_lc, $1)=no _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl-rpath,$libdir' _LT_TAGVAR(export_dynamic_flag_spec, $1)='$wl--export-dynamic' _LT_TAGVAR(whole_archive_flag_spec, $1)='$wl--whole-archive$convenience $wl--no-whole-archive' ;; pgCC* | pgcpp*) # Portland Group C++ compiler case `$CC -V` in *pgCC\ [[1-5]].* | *pgcpp\ [[1-5]].*) _LT_TAGVAR(prelink_cmds, $1)='tpldir=Template.dir~ rm -rf $tpldir~ $CC --prelink_objects --instantiation_dir $tpldir $objs $libobjs $compile_deplibs~ compile_command="$compile_command `find $tpldir -name \*.o | sort | $NL2SP`"' _LT_TAGVAR(old_archive_cmds, $1)='tpldir=Template.dir~ rm -rf $tpldir~ $CC --prelink_objects --instantiation_dir $tpldir $oldobjs$old_deplibs~ $AR $AR_FLAGS $oldlib$oldobjs$old_deplibs `find $tpldir -name \*.o | sort | $NL2SP`~ $RANLIB $oldlib' _LT_TAGVAR(archive_cmds, $1)='tpldir=Template.dir~ rm -rf $tpldir~ $CC --prelink_objects --instantiation_dir $tpldir $predep_objects $libobjs $deplibs $convenience $postdep_objects~ $CC -shared $pic_flag $predep_objects $libobjs $deplibs `find $tpldir -name \*.o | sort | $NL2SP` $postdep_objects $compiler_flags $wl-soname $wl$soname -o $lib' _LT_TAGVAR(archive_expsym_cmds, $1)='tpldir=Template.dir~ rm -rf $tpldir~ $CC --prelink_objects --instantiation_dir $tpldir $predep_objects $libobjs $deplibs $convenience $postdep_objects~ $CC -shared $pic_flag $predep_objects $libobjs $deplibs `find $tpldir -name \*.o | sort | $NL2SP` $postdep_objects $compiler_flags $wl-soname $wl$soname $wl-retain-symbols-file $wl$export_symbols -o $lib' ;; *) # Version 6 and above use weak symbols _LT_TAGVAR(archive_cmds, $1)='$CC -shared $pic_flag $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags $wl-soname $wl$soname -o $lib' _LT_TAGVAR(archive_expsym_cmds, $1)='$CC -shared $pic_flag $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags $wl-soname $wl$soname $wl-retain-symbols-file $wl$export_symbols -o $lib' ;; esac _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl--rpath $wl$libdir' _LT_TAGVAR(export_dynamic_flag_spec, $1)='$wl--export-dynamic' _LT_TAGVAR(whole_archive_flag_spec, $1)='$wl--whole-archive`for conv in $convenience\"\"; do test -n \"$conv\" && new_convenience=\"$new_convenience,$conv\"; done; func_echo_all \"$new_convenience\"` $wl--no-whole-archive' ;; cxx*) # Compaq C++ _LT_TAGVAR(archive_cmds, $1)='$CC -shared $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags $wl-soname $wl$soname -o $lib' _LT_TAGVAR(archive_expsym_cmds, $1)='$CC -shared $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags $wl-soname $wl$soname -o $lib $wl-retain-symbols-file $wl$export_symbols' runpath_var=LD_RUN_PATH _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='-rpath $libdir' _LT_TAGVAR(hardcode_libdir_separator, $1)=: # Commands to make compiler produce verbose output that lists # what "hidden" libraries, object files and flags are used when # linking a shared library. # # There doesn't appear to be a way to prevent this compiler from # explicitly linking system object files so we need to strip them # from the output so that they don't get included in the library # dependencies. output_verbose_link_cmd='templist=`$CC -shared $CFLAGS -v conftest.$objext 2>&1 | $GREP "ld"`; templist=`func_echo_all "$templist" | $SED "s/\(^.*ld.*\)\( .*ld .*$\)/\1/"`; list= ; for z in $templist; do case $z in conftest.$objext) list="$list $z";; *.$objext);; *) list="$list $z";;esac; done; func_echo_all "X$list" | $Xsed' ;; xl* | mpixl* | bgxl*) # IBM XL 8.0 on PPC, with GNU ld _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl-rpath $wl$libdir' _LT_TAGVAR(export_dynamic_flag_spec, $1)='$wl--export-dynamic' _LT_TAGVAR(archive_cmds, $1)='$CC -qmkshrobj $libobjs $deplibs $compiler_flags $wl-soname $wl$soname -o $lib' if test yes = "$supports_anon_versioning"; then _LT_TAGVAR(archive_expsym_cmds, $1)='echo "{ global:" > $output_objdir/$libname.ver~ cat $export_symbols | sed -e "s/\(.*\)/\1;/" >> $output_objdir/$libname.ver~ echo "local: *; };" >> $output_objdir/$libname.ver~ $CC -qmkshrobj $libobjs $deplibs $compiler_flags $wl-soname $wl$soname $wl-version-script $wl$output_objdir/$libname.ver -o $lib' fi ;; *) case `$CC -V 2>&1 | sed 5q` in *Sun\ C*) # Sun C++ 5.9 _LT_TAGVAR(no_undefined_flag, $1)=' -zdefs' _LT_TAGVAR(archive_cmds, $1)='$CC -G$allow_undefined_flag -h$soname -o $lib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags' _LT_TAGVAR(archive_expsym_cmds, $1)='$CC -G$allow_undefined_flag -h$soname -o $lib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags $wl-retain-symbols-file $wl$export_symbols' _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='-R$libdir' _LT_TAGVAR(whole_archive_flag_spec, $1)='$wl--whole-archive`new_convenience=; for conv in $convenience\"\"; do test -z \"$conv\" || new_convenience=\"$new_convenience,$conv\"; done; func_echo_all \"$new_convenience\"` $wl--no-whole-archive' _LT_TAGVAR(compiler_needs_object, $1)=yes # Not sure whether something based on # $CC $CFLAGS -v conftest.$objext -o libconftest$shared_ext 2>&1 # would be better. output_verbose_link_cmd='func_echo_all' # Archives containing C++ object files must be created using # "CC -xar", where "CC" is the Sun C++ compiler. This is # necessary to make sure instantiated templates are included # in the archive. _LT_TAGVAR(old_archive_cmds, $1)='$CC -xar -o $oldlib $oldobjs' ;; esac ;; esac ;; lynxos*) # FIXME: insert proper C++ library support _LT_TAGVAR(ld_shlibs, $1)=no ;; m88k*) # FIXME: insert proper C++ library support _LT_TAGVAR(ld_shlibs, $1)=no ;; mvs*) case $cc_basename in cxx*) # FIXME: insert proper C++ library support _LT_TAGVAR(ld_shlibs, $1)=no ;; *) # FIXME: insert proper C++ library support _LT_TAGVAR(ld_shlibs, $1)=no ;; esac ;; netbsd*) if echo __ELF__ | $CC -E - | $GREP __ELF__ >/dev/null; then _LT_TAGVAR(archive_cmds, $1)='$LD -Bshareable -o $lib $predep_objects $libobjs $deplibs $postdep_objects $linker_flags' wlarc= _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='-R$libdir' _LT_TAGVAR(hardcode_direct, $1)=yes _LT_TAGVAR(hardcode_shlibpath_var, $1)=no fi # Workaround some broken pre-1.5 toolchains output_verbose_link_cmd='$CC -shared $CFLAGS -v conftest.$objext 2>&1 | $GREP conftest.$objext | $SED -e "s:-lgcc -lc -lgcc::"' ;; *nto* | *qnx*) _LT_TAGVAR(ld_shlibs, $1)=yes ;; openbsd* | bitrig*) if test -f /usr/libexec/ld.so; then _LT_TAGVAR(hardcode_direct, $1)=yes _LT_TAGVAR(hardcode_shlibpath_var, $1)=no _LT_TAGVAR(hardcode_direct_absolute, $1)=yes _LT_TAGVAR(archive_cmds, $1)='$CC -shared $pic_flag $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags -o $lib' _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl-rpath,$libdir' if test -z "`echo __ELF__ | $CC -E - | grep __ELF__`"; then _LT_TAGVAR(archive_expsym_cmds, $1)='$CC -shared $pic_flag $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags $wl-retain-symbols-file,$export_symbols -o $lib' _LT_TAGVAR(export_dynamic_flag_spec, $1)='$wl-E' _LT_TAGVAR(whole_archive_flag_spec, $1)=$wlarc'--whole-archive$convenience '$wlarc'--no-whole-archive' fi output_verbose_link_cmd=func_echo_all else _LT_TAGVAR(ld_shlibs, $1)=no fi ;; osf3* | osf4* | osf5*) case $cc_basename in KCC*) # Kuck and Associates, Inc. (KAI) C++ Compiler # KCC will only create a shared library if the output file # ends with ".so" (or ".sl" for HP-UX), so rename the library # to its proper name (with version) after linking. _LT_TAGVAR(archive_cmds, $1)='tempext=`echo $shared_ext | $SED -e '\''s/\([[^()0-9A-Za-z{}]]\)/\\\\\1/g'\''`; templib=`echo "$lib" | $SED -e "s/\$tempext\..*/.so/"`; $CC $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags --soname $soname -o \$templib; mv \$templib $lib' _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl-rpath,$libdir' _LT_TAGVAR(hardcode_libdir_separator, $1)=: # Archives containing C++ object files must be created using # the KAI C++ compiler. case $host in osf3*) _LT_TAGVAR(old_archive_cmds, $1)='$CC -Bstatic -o $oldlib $oldobjs' ;; *) _LT_TAGVAR(old_archive_cmds, $1)='$CC -o $oldlib $oldobjs' ;; esac ;; RCC*) # Rational C++ 2.4.1 # FIXME: insert proper C++ library support _LT_TAGVAR(ld_shlibs, $1)=no ;; cxx*) case $host in osf3*) _LT_TAGVAR(allow_undefined_flag, $1)=' $wl-expect_unresolved $wl\*' _LT_TAGVAR(archive_cmds, $1)='$CC -shared$allow_undefined_flag $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags $wl-soname $soname `test -n "$verstring" && func_echo_all "$wl-set_version $verstring"` -update_registry $output_objdir/so_locations -o $lib' _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl-rpath $wl$libdir' ;; *) _LT_TAGVAR(allow_undefined_flag, $1)=' -expect_unresolved \*' _LT_TAGVAR(archive_cmds, $1)='$CC -shared$allow_undefined_flag $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags -msym -soname $soname `test -n "$verstring" && func_echo_all "-set_version $verstring"` -update_registry $output_objdir/so_locations -o $lib' _LT_TAGVAR(archive_expsym_cmds, $1)='for i in `cat $export_symbols`; do printf "%s %s\\n" -exported_symbol "\$i" >> $lib.exp; done~ echo "-hidden">> $lib.exp~ $CC -shared$allow_undefined_flag $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags -msym -soname $soname $wl-input $wl$lib.exp `test -n "$verstring" && $ECHO "-set_version $verstring"` -update_registry $output_objdir/so_locations -o $lib~ $RM $lib.exp' _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='-rpath $libdir' ;; esac _LT_TAGVAR(hardcode_libdir_separator, $1)=: # Commands to make compiler produce verbose output that lists # what "hidden" libraries, object files and flags are used when # linking a shared library. # # There doesn't appear to be a way to prevent this compiler from # explicitly linking system object files so we need to strip them # from the output so that they don't get included in the library # dependencies. output_verbose_link_cmd='templist=`$CC -shared $CFLAGS -v conftest.$objext 2>&1 | $GREP "ld" | $GREP -v "ld:"`; templist=`func_echo_all "$templist" | $SED "s/\(^.*ld.*\)\( .*ld.*$\)/\1/"`; list= ; for z in $templist; do case $z in conftest.$objext) list="$list $z";; *.$objext);; *) list="$list $z";;esac; done; func_echo_all "$list"' ;; *) if test yes,no = "$GXX,$with_gnu_ld"; then _LT_TAGVAR(allow_undefined_flag, $1)=' $wl-expect_unresolved $wl\*' case $host in osf3*) _LT_TAGVAR(archive_cmds, $1)='$CC -shared -nostdlib $allow_undefined_flag $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags $wl-soname $wl$soname `test -n "$verstring" && func_echo_all "$wl-set_version $wl$verstring"` $wl-update_registry $wl$output_objdir/so_locations -o $lib' ;; *) _LT_TAGVAR(archive_cmds, $1)='$CC -shared $pic_flag -nostdlib $allow_undefined_flag $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags $wl-msym $wl-soname $wl$soname `test -n "$verstring" && func_echo_all "$wl-set_version $wl$verstring"` $wl-update_registry $wl$output_objdir/so_locations -o $lib' ;; esac _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl-rpath $wl$libdir' _LT_TAGVAR(hardcode_libdir_separator, $1)=: # Commands to make compiler produce verbose output that lists # what "hidden" libraries, object files and flags are used when # linking a shared library. output_verbose_link_cmd='$CC -shared $CFLAGS -v conftest.$objext 2>&1 | $GREP -v "^Configured with:" | $GREP "\-L"' else # FIXME: insert proper C++ library support _LT_TAGVAR(ld_shlibs, $1)=no fi ;; esac ;; psos*) # FIXME: insert proper C++ library support _LT_TAGVAR(ld_shlibs, $1)=no ;; sunos4*) case $cc_basename in CC*) # Sun C++ 4.x # FIXME: insert proper C++ library support _LT_TAGVAR(ld_shlibs, $1)=no ;; lcc*) # Lucid # FIXME: insert proper C++ library support _LT_TAGVAR(ld_shlibs, $1)=no ;; *) # FIXME: insert proper C++ library support _LT_TAGVAR(ld_shlibs, $1)=no ;; esac ;; solaris*) case $cc_basename in CC* | sunCC*) # Sun C++ 4.2, 5.x and Centerline C++ _LT_TAGVAR(archive_cmds_need_lc,$1)=yes _LT_TAGVAR(no_undefined_flag, $1)=' -zdefs' _LT_TAGVAR(archive_cmds, $1)='$CC -G$allow_undefined_flag -h$soname -o $lib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags' _LT_TAGVAR(archive_expsym_cmds, $1)='echo "{ global:" > $lib.exp~cat $export_symbols | $SED -e "s/\(.*\)/\1;/" >> $lib.exp~echo "local: *; };" >> $lib.exp~ $CC -G$allow_undefined_flag $wl-M $wl$lib.exp -h$soname -o $lib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags~$RM $lib.exp' _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='-R$libdir' _LT_TAGVAR(hardcode_shlibpath_var, $1)=no case $host_os in solaris2.[[0-5]] | solaris2.[[0-5]].*) ;; *) # The compiler driver will combine and reorder linker options, # but understands '-z linker_flag'. # Supported since Solaris 2.6 (maybe 2.5.1?) _LT_TAGVAR(whole_archive_flag_spec, $1)='-z allextract$convenience -z defaultextract' ;; esac _LT_TAGVAR(link_all_deplibs, $1)=yes output_verbose_link_cmd='func_echo_all' # Archives containing C++ object files must be created using # "CC -xar", where "CC" is the Sun C++ compiler. This is # necessary to make sure instantiated templates are included # in the archive. _LT_TAGVAR(old_archive_cmds, $1)='$CC -xar -o $oldlib $oldobjs' ;; gcx*) # Green Hills C++ Compiler _LT_TAGVAR(archive_cmds, $1)='$CC -shared $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags $wl-h $wl$soname -o $lib' # The C++ compiler must be used to create the archive. _LT_TAGVAR(old_archive_cmds, $1)='$CC $LDFLAGS -archive -o $oldlib $oldobjs' ;; *) # GNU C++ compiler with Solaris linker if test yes,no = "$GXX,$with_gnu_ld"; then _LT_TAGVAR(no_undefined_flag, $1)=' $wl-z ${wl}defs' if $CC --version | $GREP -v '^2\.7' > /dev/null; then _LT_TAGVAR(archive_cmds, $1)='$CC -shared $pic_flag -nostdlib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags $wl-h $wl$soname -o $lib' _LT_TAGVAR(archive_expsym_cmds, $1)='echo "{ global:" > $lib.exp~cat $export_symbols | $SED -e "s/\(.*\)/\1;/" >> $lib.exp~echo "local: *; };" >> $lib.exp~ $CC -shared $pic_flag -nostdlib $wl-M $wl$lib.exp $wl-h $wl$soname -o $lib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags~$RM $lib.exp' # Commands to make compiler produce verbose output that lists # what "hidden" libraries, object files and flags are used when # linking a shared library. output_verbose_link_cmd='$CC -shared $CFLAGS -v conftest.$objext 2>&1 | $GREP -v "^Configured with:" | $GREP "\-L"' else # g++ 2.7 appears to require '-G' NOT '-shared' on this # platform. _LT_TAGVAR(archive_cmds, $1)='$CC -G -nostdlib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags $wl-h $wl$soname -o $lib' _LT_TAGVAR(archive_expsym_cmds, $1)='echo "{ global:" > $lib.exp~cat $export_symbols | $SED -e "s/\(.*\)/\1;/" >> $lib.exp~echo "local: *; };" >> $lib.exp~ $CC -G -nostdlib $wl-M $wl$lib.exp $wl-h $wl$soname -o $lib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags~$RM $lib.exp' # Commands to make compiler produce verbose output that lists # what "hidden" libraries, object files and flags are used when # linking a shared library. output_verbose_link_cmd='$CC -G $CFLAGS -v conftest.$objext 2>&1 | $GREP -v "^Configured with:" | $GREP "\-L"' fi _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl-R $wl$libdir' case $host_os in solaris2.[[0-5]] | solaris2.[[0-5]].*) ;; *) _LT_TAGVAR(whole_archive_flag_spec, $1)='$wl-z ${wl}allextract$convenience $wl-z ${wl}defaultextract' ;; esac fi ;; esac ;; sysv4*uw2* | sysv5OpenUNIX* | sysv5UnixWare7.[[01]].[[10]]* | unixware7* | sco3.2v5.0.[[024]]*) _LT_TAGVAR(no_undefined_flag, $1)='$wl-z,text' _LT_TAGVAR(archive_cmds_need_lc, $1)=no _LT_TAGVAR(hardcode_shlibpath_var, $1)=no runpath_var='LD_RUN_PATH' case $cc_basename in CC*) _LT_TAGVAR(archive_cmds, $1)='$CC -G $wl-h,$soname -o $lib $libobjs $deplibs $compiler_flags' _LT_TAGVAR(archive_expsym_cmds, $1)='$CC -G $wl-Bexport:$export_symbols $wl-h,$soname -o $lib $libobjs $deplibs $compiler_flags' ;; *) _LT_TAGVAR(archive_cmds, $1)='$CC -shared $wl-h,$soname -o $lib $libobjs $deplibs $compiler_flags' _LT_TAGVAR(archive_expsym_cmds, $1)='$CC -shared $wl-Bexport:$export_symbols $wl-h,$soname -o $lib $libobjs $deplibs $compiler_flags' ;; esac ;; sysv5* | sco3.2v5* | sco5v6*) # Note: We CANNOT use -z defs as we might desire, because we do not # link with -lc, and that would cause any symbols used from libc to # always be unresolved, which means just about no library would # ever link correctly. If we're not using GNU ld we use -z text # though, which does catch some bad symbols but isn't as heavy-handed # as -z defs. _LT_TAGVAR(no_undefined_flag, $1)='$wl-z,text' _LT_TAGVAR(allow_undefined_flag, $1)='$wl-z,nodefs' _LT_TAGVAR(archive_cmds_need_lc, $1)=no _LT_TAGVAR(hardcode_shlibpath_var, $1)=no _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl-R,$libdir' _LT_TAGVAR(hardcode_libdir_separator, $1)=':' _LT_TAGVAR(link_all_deplibs, $1)=yes _LT_TAGVAR(export_dynamic_flag_spec, $1)='$wl-Bexport' runpath_var='LD_RUN_PATH' case $cc_basename in CC*) _LT_TAGVAR(archive_cmds, $1)='$CC -G $wl-h,$soname -o $lib $libobjs $deplibs $compiler_flags' _LT_TAGVAR(archive_expsym_cmds, $1)='$CC -G $wl-Bexport:$export_symbols $wl-h,$soname -o $lib $libobjs $deplibs $compiler_flags' _LT_TAGVAR(old_archive_cmds, $1)='$CC -Tprelink_objects $oldobjs~ '"$_LT_TAGVAR(old_archive_cmds, $1)" _LT_TAGVAR(reload_cmds, $1)='$CC -Tprelink_objects $reload_objs~ '"$_LT_TAGVAR(reload_cmds, $1)" ;; *) _LT_TAGVAR(archive_cmds, $1)='$CC -shared $wl-h,$soname -o $lib $libobjs $deplibs $compiler_flags' _LT_TAGVAR(archive_expsym_cmds, $1)='$CC -shared $wl-Bexport:$export_symbols $wl-h,$soname -o $lib $libobjs $deplibs $compiler_flags' ;; esac ;; tandem*) case $cc_basename in NCC*) # NonStop-UX NCC 3.20 # FIXME: insert proper C++ library support _LT_TAGVAR(ld_shlibs, $1)=no ;; *) # FIXME: insert proper C++ library support _LT_TAGVAR(ld_shlibs, $1)=no ;; esac ;; vxworks*) # FIXME: insert proper C++ library support _LT_TAGVAR(ld_shlibs, $1)=no ;; *) # FIXME: insert proper C++ library support _LT_TAGVAR(ld_shlibs, $1)=no ;; esac AC_MSG_RESULT([$_LT_TAGVAR(ld_shlibs, $1)]) test no = "$_LT_TAGVAR(ld_shlibs, $1)" && can_build_shared=no _LT_TAGVAR(GCC, $1)=$GXX _LT_TAGVAR(LD, $1)=$LD ## CAVEAT EMPTOR: ## There is no encapsulation within the following macros, do not change ## the running order or otherwise move them around unless you know exactly ## what you are doing... _LT_SYS_HIDDEN_LIBDEPS($1) _LT_COMPILER_PIC($1) _LT_COMPILER_C_O($1) _LT_COMPILER_FILE_LOCKS($1) _LT_LINKER_SHLIBS($1) _LT_SYS_DYNAMIC_LINKER($1) _LT_LINKER_HARDCODE_LIBPATH($1) _LT_CONFIG($1) fi # test -n "$compiler" CC=$lt_save_CC CFLAGS=$lt_save_CFLAGS LDCXX=$LD LD=$lt_save_LD GCC=$lt_save_GCC with_gnu_ld=$lt_save_with_gnu_ld lt_cv_path_LDCXX=$lt_cv_path_LD lt_cv_path_LD=$lt_save_path_LD lt_cv_prog_gnu_ldcxx=$lt_cv_prog_gnu_ld lt_cv_prog_gnu_ld=$lt_save_with_gnu_ld fi # test yes != "$_lt_caught_CXX_error" AC_LANG_POP ])# _LT_LANG_CXX_CONFIG # _LT_FUNC_STRIPNAME_CNF # ---------------------- # func_stripname_cnf prefix suffix name # strip PREFIX and SUFFIX off of NAME. # PREFIX and SUFFIX must not contain globbing or regex special # characters, hashes, percent signs, but SUFFIX may contain a leading # dot (in which case that matches only a dot). # # This function is identical to the (non-XSI) version of func_stripname, # except this one can be used by m4 code that may be executed by configure, # rather than the libtool script. m4_defun([_LT_FUNC_STRIPNAME_CNF],[dnl AC_REQUIRE([_LT_DECL_SED]) AC_REQUIRE([_LT_PROG_ECHO_BACKSLASH]) func_stripname_cnf () { case @S|@2 in .*) func_stripname_result=`$ECHO "@S|@3" | $SED "s%^@S|@1%%; s%\\\\@S|@2\$%%"`;; *) func_stripname_result=`$ECHO "@S|@3" | $SED "s%^@S|@1%%; s%@S|@2\$%%"`;; esac } # func_stripname_cnf ])# _LT_FUNC_STRIPNAME_CNF # _LT_SYS_HIDDEN_LIBDEPS([TAGNAME]) # --------------------------------- # Figure out "hidden" library dependencies from verbose # compiler output when linking a shared library. # Parse the compiler output and extract the necessary # objects, libraries and library flags. m4_defun([_LT_SYS_HIDDEN_LIBDEPS], [m4_require([_LT_FILEUTILS_DEFAULTS])dnl AC_REQUIRE([_LT_FUNC_STRIPNAME_CNF])dnl # Dependencies to place before and after the object being linked: _LT_TAGVAR(predep_objects, $1)= _LT_TAGVAR(postdep_objects, $1)= _LT_TAGVAR(predeps, $1)= _LT_TAGVAR(postdeps, $1)= _LT_TAGVAR(compiler_lib_search_path, $1)= dnl we can't use the lt_simple_compile_test_code here, dnl because it contains code intended for an executable, dnl not a library. It's possible we should let each dnl tag define a new lt_????_link_test_code variable, dnl but it's only used here... m4_if([$1], [], [cat > conftest.$ac_ext <<_LT_EOF int a; void foo (void) { a = 0; } _LT_EOF ], [$1], [CXX], [cat > conftest.$ac_ext <<_LT_EOF class Foo { public: Foo (void) { a = 0; } private: int a; }; _LT_EOF ], [$1], [F77], [cat > conftest.$ac_ext <<_LT_EOF subroutine foo implicit none integer*4 a a=0 return end _LT_EOF ], [$1], [FC], [cat > conftest.$ac_ext <<_LT_EOF subroutine foo implicit none integer a a=0 return end _LT_EOF ], [$1], [GCJ], [cat > conftest.$ac_ext <<_LT_EOF public class foo { private int a; public void bar (void) { a = 0; } }; _LT_EOF ], [$1], [GO], [cat > conftest.$ac_ext <<_LT_EOF package foo func foo() { } _LT_EOF ]) _lt_libdeps_save_CFLAGS=$CFLAGS case "$CC $CFLAGS " in #( *\ -flto*\ *) CFLAGS="$CFLAGS -fno-lto" ;; *\ -fwhopr*\ *) CFLAGS="$CFLAGS -fno-whopr" ;; *\ -fuse-linker-plugin*\ *) CFLAGS="$CFLAGS -fno-use-linker-plugin" ;; esac dnl Parse the compiler output and extract the necessary dnl objects, libraries and library flags. if AC_TRY_EVAL(ac_compile); then # Parse the compiler output and extract the necessary # objects, libraries and library flags. # Sentinel used to keep track of whether or not we are before # the conftest object file. pre_test_object_deps_done=no for p in `eval "$output_verbose_link_cmd"`; do case $prev$p in -L* | -R* | -l*) # Some compilers place space between "-{L,R}" and the path. # Remove the space. if test x-L = "$p" || test x-R = "$p"; then prev=$p continue fi # Expand the sysroot to ease extracting the directories later. if test -z "$prev"; then case $p in -L*) func_stripname_cnf '-L' '' "$p"; prev=-L; p=$func_stripname_result ;; -R*) func_stripname_cnf '-R' '' "$p"; prev=-R; p=$func_stripname_result ;; -l*) func_stripname_cnf '-l' '' "$p"; prev=-l; p=$func_stripname_result ;; esac fi case $p in =*) func_stripname_cnf '=' '' "$p"; p=$lt_sysroot$func_stripname_result ;; esac if test no = "$pre_test_object_deps_done"; then case $prev in -L | -R) # Internal compiler library paths should come after those # provided the user. The postdeps already come after the # user supplied libs so there is no need to process them. if test -z "$_LT_TAGVAR(compiler_lib_search_path, $1)"; then _LT_TAGVAR(compiler_lib_search_path, $1)=$prev$p else _LT_TAGVAR(compiler_lib_search_path, $1)="${_LT_TAGVAR(compiler_lib_search_path, $1)} $prev$p" fi ;; # The "-l" case would never come before the object being # linked, so don't bother handling this case. esac else if test -z "$_LT_TAGVAR(postdeps, $1)"; then _LT_TAGVAR(postdeps, $1)=$prev$p else _LT_TAGVAR(postdeps, $1)="${_LT_TAGVAR(postdeps, $1)} $prev$p" fi fi prev= ;; *.lto.$objext) ;; # Ignore GCC LTO objects *.$objext) # This assumes that the test object file only shows up # once in the compiler output. if test "$p" = "conftest.$objext"; then pre_test_object_deps_done=yes continue fi if test no = "$pre_test_object_deps_done"; then if test -z "$_LT_TAGVAR(predep_objects, $1)"; then _LT_TAGVAR(predep_objects, $1)=$p else _LT_TAGVAR(predep_objects, $1)="$_LT_TAGVAR(predep_objects, $1) $p" fi else if test -z "$_LT_TAGVAR(postdep_objects, $1)"; then _LT_TAGVAR(postdep_objects, $1)=$p else _LT_TAGVAR(postdep_objects, $1)="$_LT_TAGVAR(postdep_objects, $1) $p" fi fi ;; *) ;; # Ignore the rest. esac done # Clean up. rm -f a.out a.exe else echo "libtool.m4: error: problem compiling $1 test program" fi $RM -f confest.$objext CFLAGS=$_lt_libdeps_save_CFLAGS # PORTME: override above test on systems where it is broken m4_if([$1], [CXX], [case $host_os in interix[[3-9]]*) # Interix 3.5 installs completely hosed .la files for C++, so rather than # hack all around it, let's just trust "g++" to DTRT. _LT_TAGVAR(predep_objects,$1)= _LT_TAGVAR(postdep_objects,$1)= _LT_TAGVAR(postdeps,$1)= ;; esac ]) case " $_LT_TAGVAR(postdeps, $1) " in *" -lc "*) _LT_TAGVAR(archive_cmds_need_lc, $1)=no ;; esac _LT_TAGVAR(compiler_lib_search_dirs, $1)= if test -n "${_LT_TAGVAR(compiler_lib_search_path, $1)}"; then _LT_TAGVAR(compiler_lib_search_dirs, $1)=`echo " ${_LT_TAGVAR(compiler_lib_search_path, $1)}" | $SED -e 's! -L! !g' -e 's!^ !!'` fi _LT_TAGDECL([], [compiler_lib_search_dirs], [1], [The directories searched by this compiler when creating a shared library]) _LT_TAGDECL([], [predep_objects], [1], [Dependencies to place before and after the objects being linked to create a shared library]) _LT_TAGDECL([], [postdep_objects], [1]) _LT_TAGDECL([], [predeps], [1]) _LT_TAGDECL([], [postdeps], [1]) _LT_TAGDECL([], [compiler_lib_search_path], [1], [The library search path used internally by the compiler when linking a shared library]) ])# _LT_SYS_HIDDEN_LIBDEPS # _LT_LANG_F77_CONFIG([TAG]) # -------------------------- # Ensure that the configuration variables for a Fortran 77 compiler are # suitably defined. These variables are subsequently used by _LT_CONFIG # to write the compiler configuration to 'libtool'. m4_defun([_LT_LANG_F77_CONFIG], [AC_LANG_PUSH(Fortran 77) if test -z "$F77" || test no = "$F77"; then _lt_disable_F77=yes fi _LT_TAGVAR(archive_cmds_need_lc, $1)=no _LT_TAGVAR(allow_undefined_flag, $1)= _LT_TAGVAR(always_export_symbols, $1)=no _LT_TAGVAR(archive_expsym_cmds, $1)= _LT_TAGVAR(export_dynamic_flag_spec, $1)= _LT_TAGVAR(hardcode_direct, $1)=no _LT_TAGVAR(hardcode_direct_absolute, $1)=no _LT_TAGVAR(hardcode_libdir_flag_spec, $1)= _LT_TAGVAR(hardcode_libdir_separator, $1)= _LT_TAGVAR(hardcode_minus_L, $1)=no _LT_TAGVAR(hardcode_automatic, $1)=no _LT_TAGVAR(inherit_rpath, $1)=no _LT_TAGVAR(module_cmds, $1)= _LT_TAGVAR(module_expsym_cmds, $1)= _LT_TAGVAR(link_all_deplibs, $1)=unknown _LT_TAGVAR(old_archive_cmds, $1)=$old_archive_cmds _LT_TAGVAR(reload_flag, $1)=$reload_flag _LT_TAGVAR(reload_cmds, $1)=$reload_cmds _LT_TAGVAR(no_undefined_flag, $1)= _LT_TAGVAR(whole_archive_flag_spec, $1)= _LT_TAGVAR(enable_shared_with_static_runtimes, $1)=no # Source file extension for f77 test sources. ac_ext=f # Object file extension for compiled f77 test sources. objext=o _LT_TAGVAR(objext, $1)=$objext # No sense in running all these tests if we already determined that # the F77 compiler isn't working. Some variables (like enable_shared) # are currently assumed to apply to all compilers on this platform, # and will be corrupted by setting them based on a non-working compiler. if test yes != "$_lt_disable_F77"; then # Code to be used in simple compile tests lt_simple_compile_test_code="\ subroutine t return end " # Code to be used in simple link tests lt_simple_link_test_code="\ program t end " # ltmain only uses $CC for tagged configurations so make sure $CC is set. _LT_TAG_COMPILER # save warnings/boilerplate of simple test code _LT_COMPILER_BOILERPLATE _LT_LINKER_BOILERPLATE # Allow CC to be a program name with arguments. lt_save_CC=$CC lt_save_GCC=$GCC lt_save_CFLAGS=$CFLAGS CC=${F77-"f77"} CFLAGS=$FFLAGS compiler=$CC _LT_TAGVAR(compiler, $1)=$CC _LT_CC_BASENAME([$compiler]) GCC=$G77 if test -n "$compiler"; then AC_MSG_CHECKING([if libtool supports shared libraries]) AC_MSG_RESULT([$can_build_shared]) AC_MSG_CHECKING([whether to build shared libraries]) test no = "$can_build_shared" && enable_shared=no # On AIX, shared libraries and static libraries use the same namespace, and # are all built from PIC. case $host_os in aix3*) test yes = "$enable_shared" && enable_static=no if test -n "$RANLIB"; then archive_cmds="$archive_cmds~\$RANLIB \$lib" postinstall_cmds='$RANLIB $lib' fi ;; aix[[4-9]]*) if test ia64 != "$host_cpu"; then case $enable_shared,$with_aix_soname,$aix_use_runtimelinking in yes,aix,yes) ;; # shared object as lib.so file only yes,svr4,*) ;; # shared object as lib.so archive member only yes,*) enable_static=no ;; # shared object in lib.a archive as well esac fi ;; esac AC_MSG_RESULT([$enable_shared]) AC_MSG_CHECKING([whether to build static libraries]) # Make sure either enable_shared or enable_static is yes. test yes = "$enable_shared" || enable_static=yes AC_MSG_RESULT([$enable_static]) _LT_TAGVAR(GCC, $1)=$G77 _LT_TAGVAR(LD, $1)=$LD ## CAVEAT EMPTOR: ## There is no encapsulation within the following macros, do not change ## the running order or otherwise move them around unless you know exactly ## what you are doing... _LT_COMPILER_PIC($1) _LT_COMPILER_C_O($1) _LT_COMPILER_FILE_LOCKS($1) _LT_LINKER_SHLIBS($1) _LT_SYS_DYNAMIC_LINKER($1) _LT_LINKER_HARDCODE_LIBPATH($1) _LT_CONFIG($1) fi # test -n "$compiler" GCC=$lt_save_GCC CC=$lt_save_CC CFLAGS=$lt_save_CFLAGS fi # test yes != "$_lt_disable_F77" AC_LANG_POP ])# _LT_LANG_F77_CONFIG # _LT_LANG_FC_CONFIG([TAG]) # ------------------------- # Ensure that the configuration variables for a Fortran compiler are # suitably defined. These variables are subsequently used by _LT_CONFIG # to write the compiler configuration to 'libtool'. m4_defun([_LT_LANG_FC_CONFIG], [AC_LANG_PUSH(Fortran) if test -z "$FC" || test no = "$FC"; then _lt_disable_FC=yes fi _LT_TAGVAR(archive_cmds_need_lc, $1)=no _LT_TAGVAR(allow_undefined_flag, $1)= _LT_TAGVAR(always_export_symbols, $1)=no _LT_TAGVAR(archive_expsym_cmds, $1)= _LT_TAGVAR(export_dynamic_flag_spec, $1)= _LT_TAGVAR(hardcode_direct, $1)=no _LT_TAGVAR(hardcode_direct_absolute, $1)=no _LT_TAGVAR(hardcode_libdir_flag_spec, $1)= _LT_TAGVAR(hardcode_libdir_separator, $1)= _LT_TAGVAR(hardcode_minus_L, $1)=no _LT_TAGVAR(hardcode_automatic, $1)=no _LT_TAGVAR(inherit_rpath, $1)=no _LT_TAGVAR(module_cmds, $1)= _LT_TAGVAR(module_expsym_cmds, $1)= _LT_TAGVAR(link_all_deplibs, $1)=unknown _LT_TAGVAR(old_archive_cmds, $1)=$old_archive_cmds _LT_TAGVAR(reload_flag, $1)=$reload_flag _LT_TAGVAR(reload_cmds, $1)=$reload_cmds _LT_TAGVAR(no_undefined_flag, $1)= _LT_TAGVAR(whole_archive_flag_spec, $1)= _LT_TAGVAR(enable_shared_with_static_runtimes, $1)=no # Source file extension for fc test sources. ac_ext=${ac_fc_srcext-f} # Object file extension for compiled fc test sources. objext=o _LT_TAGVAR(objext, $1)=$objext # No sense in running all these tests if we already determined that # the FC compiler isn't working. Some variables (like enable_shared) # are currently assumed to apply to all compilers on this platform, # and will be corrupted by setting them based on a non-working compiler. if test yes != "$_lt_disable_FC"; then # Code to be used in simple compile tests lt_simple_compile_test_code="\ subroutine t return end " # Code to be used in simple link tests lt_simple_link_test_code="\ program t end " # ltmain only uses $CC for tagged configurations so make sure $CC is set. _LT_TAG_COMPILER # save warnings/boilerplate of simple test code _LT_COMPILER_BOILERPLATE _LT_LINKER_BOILERPLATE # Allow CC to be a program name with arguments. lt_save_CC=$CC lt_save_GCC=$GCC lt_save_CFLAGS=$CFLAGS CC=${FC-"f95"} CFLAGS=$FCFLAGS compiler=$CC GCC=$ac_cv_fc_compiler_gnu _LT_TAGVAR(compiler, $1)=$CC _LT_CC_BASENAME([$compiler]) if test -n "$compiler"; then AC_MSG_CHECKING([if libtool supports shared libraries]) AC_MSG_RESULT([$can_build_shared]) AC_MSG_CHECKING([whether to build shared libraries]) test no = "$can_build_shared" && enable_shared=no # On AIX, shared libraries and static libraries use the same namespace, and # are all built from PIC. case $host_os in aix3*) test yes = "$enable_shared" && enable_static=no if test -n "$RANLIB"; then archive_cmds="$archive_cmds~\$RANLIB \$lib" postinstall_cmds='$RANLIB $lib' fi ;; aix[[4-9]]*) if test ia64 != "$host_cpu"; then case $enable_shared,$with_aix_soname,$aix_use_runtimelinking in yes,aix,yes) ;; # shared object as lib.so file only yes,svr4,*) ;; # shared object as lib.so archive member only yes,*) enable_static=no ;; # shared object in lib.a archive as well esac fi ;; esac AC_MSG_RESULT([$enable_shared]) AC_MSG_CHECKING([whether to build static libraries]) # Make sure either enable_shared or enable_static is yes. test yes = "$enable_shared" || enable_static=yes AC_MSG_RESULT([$enable_static]) _LT_TAGVAR(GCC, $1)=$ac_cv_fc_compiler_gnu _LT_TAGVAR(LD, $1)=$LD ## CAVEAT EMPTOR: ## There is no encapsulation within the following macros, do not change ## the running order or otherwise move them around unless you know exactly ## what you are doing... _LT_SYS_HIDDEN_LIBDEPS($1) _LT_COMPILER_PIC($1) _LT_COMPILER_C_O($1) _LT_COMPILER_FILE_LOCKS($1) _LT_LINKER_SHLIBS($1) _LT_SYS_DYNAMIC_LINKER($1) _LT_LINKER_HARDCODE_LIBPATH($1) _LT_CONFIG($1) fi # test -n "$compiler" GCC=$lt_save_GCC CC=$lt_save_CC CFLAGS=$lt_save_CFLAGS fi # test yes != "$_lt_disable_FC" AC_LANG_POP ])# _LT_LANG_FC_CONFIG # _LT_LANG_GCJ_CONFIG([TAG]) # -------------------------- # Ensure that the configuration variables for the GNU Java Compiler compiler # are suitably defined. These variables are subsequently used by _LT_CONFIG # to write the compiler configuration to 'libtool'. m4_defun([_LT_LANG_GCJ_CONFIG], [AC_REQUIRE([LT_PROG_GCJ])dnl AC_LANG_SAVE # Source file extension for Java test sources. ac_ext=java # Object file extension for compiled Java test sources. objext=o _LT_TAGVAR(objext, $1)=$objext # Code to be used in simple compile tests lt_simple_compile_test_code="class foo {}" # Code to be used in simple link tests lt_simple_link_test_code='public class conftest { public static void main(String[[]] argv) {}; }' # ltmain only uses $CC for tagged configurations so make sure $CC is set. _LT_TAG_COMPILER # save warnings/boilerplate of simple test code _LT_COMPILER_BOILERPLATE _LT_LINKER_BOILERPLATE # Allow CC to be a program name with arguments. lt_save_CC=$CC lt_save_CFLAGS=$CFLAGS lt_save_GCC=$GCC GCC=yes CC=${GCJ-"gcj"} CFLAGS=$GCJFLAGS compiler=$CC _LT_TAGVAR(compiler, $1)=$CC _LT_TAGVAR(LD, $1)=$LD _LT_CC_BASENAME([$compiler]) # GCJ did not exist at the time GCC didn't implicitly link libc in. _LT_TAGVAR(archive_cmds_need_lc, $1)=no _LT_TAGVAR(old_archive_cmds, $1)=$old_archive_cmds _LT_TAGVAR(reload_flag, $1)=$reload_flag _LT_TAGVAR(reload_cmds, $1)=$reload_cmds ## CAVEAT EMPTOR: ## There is no encapsulation within the following macros, do not change ## the running order or otherwise move them around unless you know exactly ## what you are doing... if test -n "$compiler"; then _LT_COMPILER_NO_RTTI($1) _LT_COMPILER_PIC($1) _LT_COMPILER_C_O($1) _LT_COMPILER_FILE_LOCKS($1) _LT_LINKER_SHLIBS($1) _LT_LINKER_HARDCODE_LIBPATH($1) _LT_CONFIG($1) fi AC_LANG_RESTORE GCC=$lt_save_GCC CC=$lt_save_CC CFLAGS=$lt_save_CFLAGS ])# _LT_LANG_GCJ_CONFIG # _LT_LANG_GO_CONFIG([TAG]) # -------------------------- # Ensure that the configuration variables for the GNU Go compiler # are suitably defined. These variables are subsequently used by _LT_CONFIG # to write the compiler configuration to 'libtool'. m4_defun([_LT_LANG_GO_CONFIG], [AC_REQUIRE([LT_PROG_GO])dnl AC_LANG_SAVE # Source file extension for Go test sources. ac_ext=go # Object file extension for compiled Go test sources. objext=o _LT_TAGVAR(objext, $1)=$objext # Code to be used in simple compile tests lt_simple_compile_test_code="package main; func main() { }" # Code to be used in simple link tests lt_simple_link_test_code='package main; func main() { }' # ltmain only uses $CC for tagged configurations so make sure $CC is set. _LT_TAG_COMPILER # save warnings/boilerplate of simple test code _LT_COMPILER_BOILERPLATE _LT_LINKER_BOILERPLATE # Allow CC to be a program name with arguments. lt_save_CC=$CC lt_save_CFLAGS=$CFLAGS lt_save_GCC=$GCC GCC=yes CC=${GOC-"gccgo"} CFLAGS=$GOFLAGS compiler=$CC _LT_TAGVAR(compiler, $1)=$CC _LT_TAGVAR(LD, $1)=$LD _LT_CC_BASENAME([$compiler]) # Go did not exist at the time GCC didn't implicitly link libc in. _LT_TAGVAR(archive_cmds_need_lc, $1)=no _LT_TAGVAR(old_archive_cmds, $1)=$old_archive_cmds _LT_TAGVAR(reload_flag, $1)=$reload_flag _LT_TAGVAR(reload_cmds, $1)=$reload_cmds ## CAVEAT EMPTOR: ## There is no encapsulation within the following macros, do not change ## the running order or otherwise move them around unless you know exactly ## what you are doing... if test -n "$compiler"; then _LT_COMPILER_NO_RTTI($1) _LT_COMPILER_PIC($1) _LT_COMPILER_C_O($1) _LT_COMPILER_FILE_LOCKS($1) _LT_LINKER_SHLIBS($1) _LT_LINKER_HARDCODE_LIBPATH($1) _LT_CONFIG($1) fi AC_LANG_RESTORE GCC=$lt_save_GCC CC=$lt_save_CC CFLAGS=$lt_save_CFLAGS ])# _LT_LANG_GO_CONFIG # _LT_LANG_RC_CONFIG([TAG]) # ------------------------- # Ensure that the configuration variables for the Windows resource compiler # are suitably defined. These variables are subsequently used by _LT_CONFIG # to write the compiler configuration to 'libtool'. m4_defun([_LT_LANG_RC_CONFIG], [AC_REQUIRE([LT_PROG_RC])dnl AC_LANG_SAVE # Source file extension for RC test sources. ac_ext=rc # Object file extension for compiled RC test sources. objext=o _LT_TAGVAR(objext, $1)=$objext # Code to be used in simple compile tests lt_simple_compile_test_code='sample MENU { MENUITEM "&Soup", 100, CHECKED }' # Code to be used in simple link tests lt_simple_link_test_code=$lt_simple_compile_test_code # ltmain only uses $CC for tagged configurations so make sure $CC is set. _LT_TAG_COMPILER # save warnings/boilerplate of simple test code _LT_COMPILER_BOILERPLATE _LT_LINKER_BOILERPLATE # Allow CC to be a program name with arguments. lt_save_CC=$CC lt_save_CFLAGS=$CFLAGS lt_save_GCC=$GCC GCC= CC=${RC-"windres"} CFLAGS= compiler=$CC _LT_TAGVAR(compiler, $1)=$CC _LT_CC_BASENAME([$compiler]) _LT_TAGVAR(lt_cv_prog_compiler_c_o, $1)=yes if test -n "$compiler"; then : _LT_CONFIG($1) fi GCC=$lt_save_GCC AC_LANG_RESTORE CC=$lt_save_CC CFLAGS=$lt_save_CFLAGS ])# _LT_LANG_RC_CONFIG # LT_PROG_GCJ # ----------- AC_DEFUN([LT_PROG_GCJ], [m4_ifdef([AC_PROG_GCJ], [AC_PROG_GCJ], [m4_ifdef([A][M_PROG_GCJ], [A][M_PROG_GCJ], [AC_CHECK_TOOL(GCJ, gcj,) test set = "${GCJFLAGS+set}" || GCJFLAGS="-g -O2" AC_SUBST(GCJFLAGS)])])[]dnl ]) # Old name: AU_ALIAS([LT_AC_PROG_GCJ], [LT_PROG_GCJ]) dnl aclocal-1.4 backwards compatibility: dnl AC_DEFUN([LT_AC_PROG_GCJ], []) # LT_PROG_GO # ---------- AC_DEFUN([LT_PROG_GO], [AC_CHECK_TOOL(GOC, gccgo,) ]) # LT_PROG_RC # ---------- AC_DEFUN([LT_PROG_RC], [AC_CHECK_TOOL(RC, windres,) ]) # Old name: AU_ALIAS([LT_AC_PROG_RC], [LT_PROG_RC]) dnl aclocal-1.4 backwards compatibility: dnl AC_DEFUN([LT_AC_PROG_RC], []) # _LT_DECL_EGREP # -------------- # If we don't have a new enough Autoconf to choose the best grep # available, choose the one first in the user's PATH. m4_defun([_LT_DECL_EGREP], [AC_REQUIRE([AC_PROG_EGREP])dnl AC_REQUIRE([AC_PROG_FGREP])dnl test -z "$GREP" && GREP=grep _LT_DECL([], [GREP], [1], [A grep program that handles long lines]) _LT_DECL([], [EGREP], [1], [An ERE matcher]) _LT_DECL([], [FGREP], [1], [A literal string matcher]) dnl Non-bleeding-edge autoconf doesn't subst GREP, so do it here too AC_SUBST([GREP]) ]) # _LT_DECL_OBJDUMP # -------------- # If we don't have a new enough Autoconf to choose the best objdump # available, choose the one first in the user's PATH. m4_defun([_LT_DECL_OBJDUMP], [AC_CHECK_TOOL(OBJDUMP, objdump, false) test -z "$OBJDUMP" && OBJDUMP=objdump _LT_DECL([], [OBJDUMP], [1], [An object symbol dumper]) AC_SUBST([OBJDUMP]) ]) # _LT_DECL_DLLTOOL # ---------------- # Ensure DLLTOOL variable is set. m4_defun([_LT_DECL_DLLTOOL], [AC_CHECK_TOOL(DLLTOOL, dlltool, false) test -z "$DLLTOOL" && DLLTOOL=dlltool _LT_DECL([], [DLLTOOL], [1], [DLL creation program]) AC_SUBST([DLLTOOL]) ]) # _LT_DECL_SED # ------------ # Check for a fully-functional sed program, that truncates # as few characters as possible. Prefer GNU sed if found. m4_defun([_LT_DECL_SED], [AC_PROG_SED test -z "$SED" && SED=sed Xsed="$SED -e 1s/^X//" _LT_DECL([], [SED], [1], [A sed program that does not truncate output]) _LT_DECL([], [Xsed], ["\$SED -e 1s/^X//"], [Sed that helps us avoid accidentally triggering echo(1) options like -n]) ])# _LT_DECL_SED m4_ifndef([AC_PROG_SED], [ ############################################################ # NOTE: This macro has been submitted for inclusion into # # GNU Autoconf as AC_PROG_SED. When it is available in # # a released version of Autoconf we should remove this # # macro and use it instead. # ############################################################ m4_defun([AC_PROG_SED], [AC_MSG_CHECKING([for a sed that does not truncate output]) AC_CACHE_VAL(lt_cv_path_SED, [# Loop through the user's path and test for sed and gsed. # Then use that list of sed's as ones to test for truncation. as_save_IFS=$IFS; IFS=$PATH_SEPARATOR for as_dir in $PATH do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for lt_ac_prog in sed gsed; do for ac_exec_ext in '' $ac_executable_extensions; do if $as_executable_p "$as_dir/$lt_ac_prog$ac_exec_ext"; then lt_ac_sed_list="$lt_ac_sed_list $as_dir/$lt_ac_prog$ac_exec_ext" fi done done done IFS=$as_save_IFS lt_ac_max=0 lt_ac_count=0 # Add /usr/xpg4/bin/sed as it is typically found on Solaris # along with /bin/sed that truncates output. for lt_ac_sed in $lt_ac_sed_list /usr/xpg4/bin/sed; do test ! -f "$lt_ac_sed" && continue cat /dev/null > conftest.in lt_ac_count=0 echo $ECHO_N "0123456789$ECHO_C" >conftest.in # Check for GNU sed and select it if it is found. if "$lt_ac_sed" --version 2>&1 < /dev/null | grep 'GNU' > /dev/null; then lt_cv_path_SED=$lt_ac_sed break fi while true; do cat conftest.in conftest.in >conftest.tmp mv conftest.tmp conftest.in cp conftest.in conftest.nl echo >>conftest.nl $lt_ac_sed -e 's/a$//' < conftest.nl >conftest.out || break cmp -s conftest.out conftest.nl || break # 10000 chars as input seems more than enough test 10 -lt "$lt_ac_count" && break lt_ac_count=`expr $lt_ac_count + 1` if test "$lt_ac_count" -gt "$lt_ac_max"; then lt_ac_max=$lt_ac_count lt_cv_path_SED=$lt_ac_sed fi done done ]) SED=$lt_cv_path_SED AC_SUBST([SED]) AC_MSG_RESULT([$SED]) ])#AC_PROG_SED ])#m4_ifndef # Old name: AU_ALIAS([LT_AC_PROG_SED], [AC_PROG_SED]) dnl aclocal-1.4 backwards compatibility: dnl AC_DEFUN([LT_AC_PROG_SED], []) # _LT_CHECK_SHELL_FEATURES # ------------------------ # Find out whether the shell is Bourne or XSI compatible, # or has some other useful features. m4_defun([_LT_CHECK_SHELL_FEATURES], [if ( (MAIL=60; unset MAIL) || exit) >/dev/null 2>&1; then lt_unset=unset else lt_unset=false fi _LT_DECL([], [lt_unset], [0], [whether the shell understands "unset"])dnl # test EBCDIC or ASCII case `echo X|tr X '\101'` in A) # ASCII based system # \n is not interpreted correctly by Solaris 8 /usr/ucb/tr lt_SP2NL='tr \040 \012' lt_NL2SP='tr \015\012 \040\040' ;; *) # EBCDIC based system lt_SP2NL='tr \100 \n' lt_NL2SP='tr \r\n \100\100' ;; esac _LT_DECL([SP2NL], [lt_SP2NL], [1], [turn spaces into newlines])dnl _LT_DECL([NL2SP], [lt_NL2SP], [1], [turn newlines into spaces])dnl ])# _LT_CHECK_SHELL_FEATURES # _LT_PATH_CONVERSION_FUNCTIONS # ----------------------------- # Determine what file name conversion functions should be used by # func_to_host_file (and, implicitly, by func_to_host_path). These are needed # for certain cross-compile configurations and native mingw. m4_defun([_LT_PATH_CONVERSION_FUNCTIONS], [AC_REQUIRE([AC_CANONICAL_HOST])dnl AC_REQUIRE([AC_CANONICAL_BUILD])dnl AC_MSG_CHECKING([how to convert $build file names to $host format]) AC_CACHE_VAL(lt_cv_to_host_file_cmd, [case $host in *-*-mingw* ) case $build in *-*-mingw* ) # actually msys lt_cv_to_host_file_cmd=func_convert_file_msys_to_w32 ;; *-*-cygwin* ) lt_cv_to_host_file_cmd=func_convert_file_cygwin_to_w32 ;; * ) # otherwise, assume *nix lt_cv_to_host_file_cmd=func_convert_file_nix_to_w32 ;; esac ;; *-*-cygwin* ) case $build in *-*-mingw* ) # actually msys lt_cv_to_host_file_cmd=func_convert_file_msys_to_cygwin ;; *-*-cygwin* ) lt_cv_to_host_file_cmd=func_convert_file_noop ;; * ) # otherwise, assume *nix lt_cv_to_host_file_cmd=func_convert_file_nix_to_cygwin ;; esac ;; * ) # unhandled hosts (and "normal" native builds) lt_cv_to_host_file_cmd=func_convert_file_noop ;; esac ]) to_host_file_cmd=$lt_cv_to_host_file_cmd AC_MSG_RESULT([$lt_cv_to_host_file_cmd]) _LT_DECL([to_host_file_cmd], [lt_cv_to_host_file_cmd], [0], [convert $build file names to $host format])dnl AC_MSG_CHECKING([how to convert $build file names to toolchain format]) AC_CACHE_VAL(lt_cv_to_tool_file_cmd, [#assume ordinary cross tools, or native build. lt_cv_to_tool_file_cmd=func_convert_file_noop case $host in *-*-mingw* ) case $build in *-*-mingw* ) # actually msys lt_cv_to_tool_file_cmd=func_convert_file_msys_to_w32 ;; esac ;; esac ]) to_tool_file_cmd=$lt_cv_to_tool_file_cmd AC_MSG_RESULT([$lt_cv_to_tool_file_cmd]) _LT_DECL([to_tool_file_cmd], [lt_cv_to_tool_file_cmd], [0], [convert $build files to toolchain format])dnl ])# _LT_PATH_CONVERSION_FUNCTIONS cyrus-imapd-2.5.10/cmulocal/ltoptions.m40000644000175000017500000003426212756047127015073 00000000000000# Helper functions for option handling. -*- Autoconf -*- # # Copyright (C) 2004-2005, 2007-2009, 2011-2015 Free Software # Foundation, Inc. # Written by Gary V. Vaughan, 2004 # # This file is free software; the Free Software Foundation gives # unlimited permission to copy and/or distribute it, with or without # modifications, as long as this notice is preserved. # serial 8 ltoptions.m4 # This is to help aclocal find these macros, as it can't see m4_define. AC_DEFUN([LTOPTIONS_VERSION], [m4_if([1])]) # _LT_MANGLE_OPTION(MACRO-NAME, OPTION-NAME) # ------------------------------------------ m4_define([_LT_MANGLE_OPTION], [[_LT_OPTION_]m4_bpatsubst($1__$2, [[^a-zA-Z0-9_]], [_])]) # _LT_SET_OPTION(MACRO-NAME, OPTION-NAME) # --------------------------------------- # Set option OPTION-NAME for macro MACRO-NAME, and if there is a # matching handler defined, dispatch to it. Other OPTION-NAMEs are # saved as a flag. m4_define([_LT_SET_OPTION], [m4_define(_LT_MANGLE_OPTION([$1], [$2]))dnl m4_ifdef(_LT_MANGLE_DEFUN([$1], [$2]), _LT_MANGLE_DEFUN([$1], [$2]), [m4_warning([Unknown $1 option '$2'])])[]dnl ]) # _LT_IF_OPTION(MACRO-NAME, OPTION-NAME, IF-SET, [IF-NOT-SET]) # ------------------------------------------------------------ # Execute IF-SET if OPTION is set, IF-NOT-SET otherwise. m4_define([_LT_IF_OPTION], [m4_ifdef(_LT_MANGLE_OPTION([$1], [$2]), [$3], [$4])]) # _LT_UNLESS_OPTIONS(MACRO-NAME, OPTION-LIST, IF-NOT-SET) # ------------------------------------------------------- # Execute IF-NOT-SET unless all options in OPTION-LIST for MACRO-NAME # are set. m4_define([_LT_UNLESS_OPTIONS], [m4_foreach([_LT_Option], m4_split(m4_normalize([$2])), [m4_ifdef(_LT_MANGLE_OPTION([$1], _LT_Option), [m4_define([$0_found])])])[]dnl m4_ifdef([$0_found], [m4_undefine([$0_found])], [$3 ])[]dnl ]) # _LT_SET_OPTIONS(MACRO-NAME, OPTION-LIST) # ---------------------------------------- # OPTION-LIST is a space-separated list of Libtool options associated # with MACRO-NAME. If any OPTION has a matching handler declared with # LT_OPTION_DEFINE, dispatch to that macro; otherwise complain about # the unknown option and exit. m4_defun([_LT_SET_OPTIONS], [# Set options m4_foreach([_LT_Option], m4_split(m4_normalize([$2])), [_LT_SET_OPTION([$1], _LT_Option)]) m4_if([$1],[LT_INIT],[ dnl dnl Simply set some default values (i.e off) if boolean options were not dnl specified: _LT_UNLESS_OPTIONS([LT_INIT], [dlopen], [enable_dlopen=no ]) _LT_UNLESS_OPTIONS([LT_INIT], [win32-dll], [enable_win32_dll=no ]) dnl dnl If no reference was made to various pairs of opposing options, then dnl we run the default mode handler for the pair. For example, if neither dnl 'shared' nor 'disable-shared' was passed, we enable building of shared dnl archives by default: _LT_UNLESS_OPTIONS([LT_INIT], [shared disable-shared], [_LT_ENABLE_SHARED]) _LT_UNLESS_OPTIONS([LT_INIT], [static disable-static], [_LT_ENABLE_STATIC]) _LT_UNLESS_OPTIONS([LT_INIT], [pic-only no-pic], [_LT_WITH_PIC]) _LT_UNLESS_OPTIONS([LT_INIT], [fast-install disable-fast-install], [_LT_ENABLE_FAST_INSTALL]) _LT_UNLESS_OPTIONS([LT_INIT], [aix-soname=aix aix-soname=both aix-soname=svr4], [_LT_WITH_AIX_SONAME([aix])]) ]) ])# _LT_SET_OPTIONS ## --------------------------------- ## ## Macros to handle LT_INIT options. ## ## --------------------------------- ## # _LT_MANGLE_DEFUN(MACRO-NAME, OPTION-NAME) # ----------------------------------------- m4_define([_LT_MANGLE_DEFUN], [[_LT_OPTION_DEFUN_]m4_bpatsubst(m4_toupper([$1__$2]), [[^A-Z0-9_]], [_])]) # LT_OPTION_DEFINE(MACRO-NAME, OPTION-NAME, CODE) # ----------------------------------------------- m4_define([LT_OPTION_DEFINE], [m4_define(_LT_MANGLE_DEFUN([$1], [$2]), [$3])[]dnl ])# LT_OPTION_DEFINE # dlopen # ------ LT_OPTION_DEFINE([LT_INIT], [dlopen], [enable_dlopen=yes ]) AU_DEFUN([AC_LIBTOOL_DLOPEN], [_LT_SET_OPTION([LT_INIT], [dlopen]) AC_DIAGNOSE([obsolete], [$0: Remove this warning and the call to _LT_SET_OPTION when you put the 'dlopen' option into LT_INIT's first parameter.]) ]) dnl aclocal-1.4 backwards compatibility: dnl AC_DEFUN([AC_LIBTOOL_DLOPEN], []) # win32-dll # --------- # Declare package support for building win32 dll's. LT_OPTION_DEFINE([LT_INIT], [win32-dll], [enable_win32_dll=yes case $host in *-*-cygwin* | *-*-mingw* | *-*-pw32* | *-*-cegcc*) AC_CHECK_TOOL(AS, as, false) AC_CHECK_TOOL(DLLTOOL, dlltool, false) AC_CHECK_TOOL(OBJDUMP, objdump, false) ;; esac test -z "$AS" && AS=as _LT_DECL([], [AS], [1], [Assembler program])dnl test -z "$DLLTOOL" && DLLTOOL=dlltool _LT_DECL([], [DLLTOOL], [1], [DLL creation program])dnl test -z "$OBJDUMP" && OBJDUMP=objdump _LT_DECL([], [OBJDUMP], [1], [Object dumper program])dnl ])# win32-dll AU_DEFUN([AC_LIBTOOL_WIN32_DLL], [AC_REQUIRE([AC_CANONICAL_HOST])dnl _LT_SET_OPTION([LT_INIT], [win32-dll]) AC_DIAGNOSE([obsolete], [$0: Remove this warning and the call to _LT_SET_OPTION when you put the 'win32-dll' option into LT_INIT's first parameter.]) ]) dnl aclocal-1.4 backwards compatibility: dnl AC_DEFUN([AC_LIBTOOL_WIN32_DLL], []) # _LT_ENABLE_SHARED([DEFAULT]) # ---------------------------- # implement the --enable-shared flag, and supports the 'shared' and # 'disable-shared' LT_INIT options. # DEFAULT is either 'yes' or 'no'. If omitted, it defaults to 'yes'. m4_define([_LT_ENABLE_SHARED], [m4_define([_LT_ENABLE_SHARED_DEFAULT], [m4_if($1, no, no, yes)])dnl AC_ARG_ENABLE([shared], [AS_HELP_STRING([--enable-shared@<:@=PKGS@:>@], [build shared libraries @<:@default=]_LT_ENABLE_SHARED_DEFAULT[@:>@])], [p=${PACKAGE-default} case $enableval in yes) enable_shared=yes ;; no) enable_shared=no ;; *) enable_shared=no # Look at the argument we got. We use all the common list separators. lt_save_ifs=$IFS; IFS=$IFS$PATH_SEPARATOR, for pkg in $enableval; do IFS=$lt_save_ifs if test "X$pkg" = "X$p"; then enable_shared=yes fi done IFS=$lt_save_ifs ;; esac], [enable_shared=]_LT_ENABLE_SHARED_DEFAULT) _LT_DECL([build_libtool_libs], [enable_shared], [0], [Whether or not to build shared libraries]) ])# _LT_ENABLE_SHARED LT_OPTION_DEFINE([LT_INIT], [shared], [_LT_ENABLE_SHARED([yes])]) LT_OPTION_DEFINE([LT_INIT], [disable-shared], [_LT_ENABLE_SHARED([no])]) # Old names: AC_DEFUN([AC_ENABLE_SHARED], [_LT_SET_OPTION([LT_INIT], m4_if([$1], [no], [disable-])[shared]) ]) AC_DEFUN([AC_DISABLE_SHARED], [_LT_SET_OPTION([LT_INIT], [disable-shared]) ]) AU_DEFUN([AM_ENABLE_SHARED], [AC_ENABLE_SHARED($@)]) AU_DEFUN([AM_DISABLE_SHARED], [AC_DISABLE_SHARED($@)]) dnl aclocal-1.4 backwards compatibility: dnl AC_DEFUN([AM_ENABLE_SHARED], []) dnl AC_DEFUN([AM_DISABLE_SHARED], []) # _LT_ENABLE_STATIC([DEFAULT]) # ---------------------------- # implement the --enable-static flag, and support the 'static' and # 'disable-static' LT_INIT options. # DEFAULT is either 'yes' or 'no'. If omitted, it defaults to 'yes'. m4_define([_LT_ENABLE_STATIC], [m4_define([_LT_ENABLE_STATIC_DEFAULT], [m4_if($1, no, no, yes)])dnl AC_ARG_ENABLE([static], [AS_HELP_STRING([--enable-static@<:@=PKGS@:>@], [build static libraries @<:@default=]_LT_ENABLE_STATIC_DEFAULT[@:>@])], [p=${PACKAGE-default} case $enableval in yes) enable_static=yes ;; no) enable_static=no ;; *) enable_static=no # Look at the argument we got. We use all the common list separators. lt_save_ifs=$IFS; IFS=$IFS$PATH_SEPARATOR, for pkg in $enableval; do IFS=$lt_save_ifs if test "X$pkg" = "X$p"; then enable_static=yes fi done IFS=$lt_save_ifs ;; esac], [enable_static=]_LT_ENABLE_STATIC_DEFAULT) _LT_DECL([build_old_libs], [enable_static], [0], [Whether or not to build static libraries]) ])# _LT_ENABLE_STATIC LT_OPTION_DEFINE([LT_INIT], [static], [_LT_ENABLE_STATIC([yes])]) LT_OPTION_DEFINE([LT_INIT], [disable-static], [_LT_ENABLE_STATIC([no])]) # Old names: AC_DEFUN([AC_ENABLE_STATIC], [_LT_SET_OPTION([LT_INIT], m4_if([$1], [no], [disable-])[static]) ]) AC_DEFUN([AC_DISABLE_STATIC], [_LT_SET_OPTION([LT_INIT], [disable-static]) ]) AU_DEFUN([AM_ENABLE_STATIC], [AC_ENABLE_STATIC($@)]) AU_DEFUN([AM_DISABLE_STATIC], [AC_DISABLE_STATIC($@)]) dnl aclocal-1.4 backwards compatibility: dnl AC_DEFUN([AM_ENABLE_STATIC], []) dnl AC_DEFUN([AM_DISABLE_STATIC], []) # _LT_ENABLE_FAST_INSTALL([DEFAULT]) # ---------------------------------- # implement the --enable-fast-install flag, and support the 'fast-install' # and 'disable-fast-install' LT_INIT options. # DEFAULT is either 'yes' or 'no'. If omitted, it defaults to 'yes'. m4_define([_LT_ENABLE_FAST_INSTALL], [m4_define([_LT_ENABLE_FAST_INSTALL_DEFAULT], [m4_if($1, no, no, yes)])dnl AC_ARG_ENABLE([fast-install], [AS_HELP_STRING([--enable-fast-install@<:@=PKGS@:>@], [optimize for fast installation @<:@default=]_LT_ENABLE_FAST_INSTALL_DEFAULT[@:>@])], [p=${PACKAGE-default} case $enableval in yes) enable_fast_install=yes ;; no) enable_fast_install=no ;; *) enable_fast_install=no # Look at the argument we got. We use all the common list separators. lt_save_ifs=$IFS; IFS=$IFS$PATH_SEPARATOR, for pkg in $enableval; do IFS=$lt_save_ifs if test "X$pkg" = "X$p"; then enable_fast_install=yes fi done IFS=$lt_save_ifs ;; esac], [enable_fast_install=]_LT_ENABLE_FAST_INSTALL_DEFAULT) _LT_DECL([fast_install], [enable_fast_install], [0], [Whether or not to optimize for fast installation])dnl ])# _LT_ENABLE_FAST_INSTALL LT_OPTION_DEFINE([LT_INIT], [fast-install], [_LT_ENABLE_FAST_INSTALL([yes])]) LT_OPTION_DEFINE([LT_INIT], [disable-fast-install], [_LT_ENABLE_FAST_INSTALL([no])]) # Old names: AU_DEFUN([AC_ENABLE_FAST_INSTALL], [_LT_SET_OPTION([LT_INIT], m4_if([$1], [no], [disable-])[fast-install]) AC_DIAGNOSE([obsolete], [$0: Remove this warning and the call to _LT_SET_OPTION when you put the 'fast-install' option into LT_INIT's first parameter.]) ]) AU_DEFUN([AC_DISABLE_FAST_INSTALL], [_LT_SET_OPTION([LT_INIT], [disable-fast-install]) AC_DIAGNOSE([obsolete], [$0: Remove this warning and the call to _LT_SET_OPTION when you put the 'disable-fast-install' option into LT_INIT's first parameter.]) ]) dnl aclocal-1.4 backwards compatibility: dnl AC_DEFUN([AC_ENABLE_FAST_INSTALL], []) dnl AC_DEFUN([AM_DISABLE_FAST_INSTALL], []) # _LT_WITH_AIX_SONAME([DEFAULT]) # ---------------------------------- # implement the --with-aix-soname flag, and support the `aix-soname=aix' # and `aix-soname=both' and `aix-soname=svr4' LT_INIT options. DEFAULT # is either `aix', `both' or `svr4'. If omitted, it defaults to `aix'. m4_define([_LT_WITH_AIX_SONAME], [m4_define([_LT_WITH_AIX_SONAME_DEFAULT], [m4_if($1, svr4, svr4, m4_if($1, both, both, aix))])dnl shared_archive_member_spec= case $host,$enable_shared in power*-*-aix[[5-9]]*,yes) AC_MSG_CHECKING([which variant of shared library versioning to provide]) AC_ARG_WITH([aix-soname], [AS_HELP_STRING([--with-aix-soname=aix|svr4|both], [shared library versioning (aka "SONAME") variant to provide on AIX, @<:@default=]_LT_WITH_AIX_SONAME_DEFAULT[@:>@.])], [case $withval in aix|svr4|both) ;; *) AC_MSG_ERROR([Unknown argument to --with-aix-soname]) ;; esac lt_cv_with_aix_soname=$with_aix_soname], [AC_CACHE_VAL([lt_cv_with_aix_soname], [lt_cv_with_aix_soname=]_LT_WITH_AIX_SONAME_DEFAULT) with_aix_soname=$lt_cv_with_aix_soname]) AC_MSG_RESULT([$with_aix_soname]) if test aix != "$with_aix_soname"; then # For the AIX way of multilib, we name the shared archive member # based on the bitwidth used, traditionally 'shr.o' or 'shr_64.o', # and 'shr.imp' or 'shr_64.imp', respectively, for the Import File. # Even when GNU compilers ignore OBJECT_MODE but need '-maix64' flag, # the AIX toolchain works better with OBJECT_MODE set (default 32). if test 64 = "${OBJECT_MODE-32}"; then shared_archive_member_spec=shr_64 else shared_archive_member_spec=shr fi fi ;; *) with_aix_soname=aix ;; esac _LT_DECL([], [shared_archive_member_spec], [0], [Shared archive member basename, for filename based shared library versioning on AIX])dnl ])# _LT_WITH_AIX_SONAME LT_OPTION_DEFINE([LT_INIT], [aix-soname=aix], [_LT_WITH_AIX_SONAME([aix])]) LT_OPTION_DEFINE([LT_INIT], [aix-soname=both], [_LT_WITH_AIX_SONAME([both])]) LT_OPTION_DEFINE([LT_INIT], [aix-soname=svr4], [_LT_WITH_AIX_SONAME([svr4])]) # _LT_WITH_PIC([MODE]) # -------------------- # implement the --with-pic flag, and support the 'pic-only' and 'no-pic' # LT_INIT options. # MODE is either 'yes' or 'no'. If omitted, it defaults to 'both'. m4_define([_LT_WITH_PIC], [AC_ARG_WITH([pic], [AS_HELP_STRING([--with-pic@<:@=PKGS@:>@], [try to use only PIC/non-PIC objects @<:@default=use both@:>@])], [lt_p=${PACKAGE-default} case $withval in yes|no) pic_mode=$withval ;; *) pic_mode=default # Look at the argument we got. We use all the common list separators. lt_save_ifs=$IFS; IFS=$IFS$PATH_SEPARATOR, for lt_pkg in $withval; do IFS=$lt_save_ifs if test "X$lt_pkg" = "X$lt_p"; then pic_mode=yes fi done IFS=$lt_save_ifs ;; esac], [pic_mode=m4_default([$1], [default])]) _LT_DECL([], [pic_mode], [0], [What type of objects to build])dnl ])# _LT_WITH_PIC LT_OPTION_DEFINE([LT_INIT], [pic-only], [_LT_WITH_PIC([yes])]) LT_OPTION_DEFINE([LT_INIT], [no-pic], [_LT_WITH_PIC([no])]) # Old name: AU_DEFUN([AC_LIBTOOL_PICMODE], [_LT_SET_OPTION([LT_INIT], [pic-only]) AC_DIAGNOSE([obsolete], [$0: Remove this warning and the call to _LT_SET_OPTION when you put the 'pic-only' option into LT_INIT's first parameter.]) ]) dnl aclocal-1.4 backwards compatibility: dnl AC_DEFUN([AC_LIBTOOL_PICMODE], []) ## ----------------- ## ## LTDL_INIT Options ## ## ----------------- ## m4_define([_LTDL_MODE], []) LT_OPTION_DEFINE([LTDL_INIT], [nonrecursive], [m4_define([_LTDL_MODE], [nonrecursive])]) LT_OPTION_DEFINE([LTDL_INIT], [recursive], [m4_define([_LTDL_MODE], [recursive])]) LT_OPTION_DEFINE([LTDL_INIT], [subproject], [m4_define([_LTDL_MODE], [subproject])]) m4_define([_LTDL_TYPE], []) LT_OPTION_DEFINE([LTDL_INIT], [installable], [m4_define([_LTDL_TYPE], [installable])]) LT_OPTION_DEFINE([LTDL_INIT], [convenience], [m4_define([_LTDL_TYPE], [convenience])]) cyrus-imapd-2.5.10/sieve/0000755000175000017500000000000013001246664012152 500000000000000cyrus-imapd-2.5.10/sieve/comparator.c0000644000175000017500000002777413001236020014407 00000000000000/* comparator.c -- comparator functions * Larry Greenfield * Ken Murchison (rewritten to handle relational ops and non-terminated text) * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #ifdef HAVE_CONFIG_H #include #endif #include #include #include #include "comparator.h" #include "tree.h" #include "sieve/sieve_interface.h" #include "sieve/sieve.h" #include "bytecode.h" #include "util.h" /*!!! uses B_CONTAINS not CONTAINS, etc, only works with bytecode*/ typedef int (*compare_t)(const void *, size_t, const void *); /* --- relational comparators --- */ /* these are generic wrappers in which 'rock' is the compare function */ static int rel_eq(const char *text, size_t tlen, const char *pat, void *rock) { compare_t compar = (compare_t) rock; return (compar(text, tlen, pat) == 0); } static int rel_ne(const char *text, size_t tlen, const char *pat, void *rock) { compare_t compar = (compare_t) rock; return (compar(text, tlen, pat) != 0); } static int rel_gt(const char *text, size_t tlen, const char *pat, void *rock) { compare_t compar = (compare_t) rock; return (compar(text, tlen, pat) > 0); } static int rel_ge(const char *text, size_t tlen, const char *pat, void *rock) { compare_t compar = (compare_t) rock; return (compar(text, tlen, pat) >= 0); } static int rel_lt(const char *text, size_t tlen, const char *pat, void *rock) { compare_t compar = (compare_t) rock; return (compar(text, tlen, pat) < 0); } static int rel_le(const char *text, size_t tlen, const char *pat, void *rock) { compare_t compar = (compare_t) rock; return (compar(text, tlen, pat) <= 0); } /* --- i;octet comparators --- */ /* just compare the two; pat should be NULL terminated */ static int octet_cmp_(const char *text, size_t tlen, const char *pat, int casemap) { size_t plen, sl, i; int r = 0; plen = strlen(pat); sl = tlen < plen ? tlen : plen; for (i = 0; !r && i < sl; i++) { r = casemap ? toupper(text[i]) - toupper(pat[i]) : text[i] - pat[i]; } if (r == 0) return (tlen - plen); else return r; } static int octet_cmp(const char *text, size_t tlen, const char *pat) { return octet_cmp_(text, tlen, pat, 0); } /* we implement boyer-moore for hell of it, since this is probably not very useful for sieve */ #if 0 int boyer_moore(char *text, char *pat) { int i, j; /* indexes */ int M = strlen(pat); /* length of pattern */ int N = strlen(text); /* length of text */ int skip[256]; /* table of how much to skip, based on each character */ /* initialize skip table */ for (i = 0; i < 256; i++) skip[i] = M; for (i = 0; i < M; i++) skip[(int) pat[i]] = M-i-1; /* look for pat in text */ i = j = M-1; do { if (pat[j] == text[i]) { i--; j--; } else { if (M-j > skip[(int) text[i]]) { i = i + M - j; } else { i = i + skip[(int) text[i]]; } j = M-1; } } while (!((j < 0) || (i >= N))); /* i+1 is the position of the match if i < N */ return (i < N) ? 1 : 0; } #endif /* we do a brute force attack */ static int octet_contains_(const char *text, size_t tlen, const char *pat, int casemap) { int N = tlen; int M = strlen(pat); int i, j; i = 0, j = 0; while ((j < M) && (i < N)) { if ((text[i] == pat[j]) || (casemap && (toupper(text[i]) == toupper(pat[j])))) { i++; j++; } else { i = i - j + 1; j = 0; } } return (j == M); /* we found a match! */ } static int octet_contains(const char *text, size_t tlen, const char *pat, void *rock __attribute__((unused))) { return octet_contains_(text, tlen, pat, 0); } static int octet_matches_(const char *text, size_t tlen, const char *pat, int casemap) { const char *p; const char *t; char c; t = text; p = pat; for (;;) { if (*p == '\0') { /* ran out of pattern */ return (!tlen); } c = *p++; switch (c) { case '?': if (!tlen) { return 0; } t++; tlen--; break; case '*': while (*p == '*' || *p == '?') { if (*p == '?') { /* eat the character now */ if (!tlen) { return 0; } t++; tlen--; } /* coalesce into a single wildcard */ p++; } if (*p == '\0') { /* wildcard at end of string, any remaining text is ok */ return 1; } while (tlen) { /* recurse */ if (octet_matches_(t, tlen, p, casemap)) return 1; t++; tlen--; } break; case '\\': c = *p++; /* falls through */ default: if ((c == *t) || (casemap && (toupper(c) == toupper(*t)))) { t++; tlen--; } else { /* literal char doesn't match */ return 0; } } } /* never reaches */ } static int octet_matches(const char *text, size_t tlen, const char *pat, void *rock __attribute__((unused))) { return octet_matches_(text, tlen, pat, 0); } #ifdef ENABLE_REGEX static int octet_regex(const char *text, size_t tlen, const char *pat, void *rock __attribute__((unused))) { int r; #ifdef REG_STARTEND /* pcre, BSD, some linuxes support this handy trick */ regmatch_t pm[1]; pm[0].rm_so = 0; pm[0].rm_eo = tlen; r = !regexec((regex_t *) pat, text, 0, pm, REG_STARTEND); #else #ifdef HAVE_RX_POSIX_H /* rx provides regnexec, that will work too */ r = !regnexec((regex_t *) pat, text, tlen, 0, NULL, 0); #else /* regexec() requires a NUL-terminated string, and we have no * guarantee that "text" is one. Also, it may be only exactly * tlen's length, so we can't safely check. Always dup. */ char *buf = (char *) xstrndup(text, tlen); r = !regexec((regex_t *) pat, buf, 0, NULL, 0); free(buf); #endif /* HAVE_RX_POSIX_H */ #endif /* REG_STARTEND */ return r; } #endif /* --- i;ascii-casemap comparators --- */ static int ascii_casemap_cmp(const char *text, size_t tlen, const char *pat) { return octet_cmp_(text, tlen, pat, 1); } static int ascii_casemap_contains(const char *text, size_t tlen, const char *pat, void *rock __attribute__((unused))) { return octet_contains_(text, tlen, pat, 1); } static int ascii_casemap_matches(const char *text, size_t tlen, const char *pat, void *rock __attribute__((unused))) { return octet_matches_(text, tlen, pat, 1); } /* i;ascii-numeric; only supports relational tests * * A \ B number not-num * number A ? B A < B * not-num A > B A == B */ /* From RFC 2244: * * The i;ascii-numeric comparator interprets strings as decimal * positive integers represented as US-ASCII digits. All values * which do not begin with a US-ASCII digit are considered equal * with an ordinal value higher than all non-NIL single-valued * attributes. Otherwise, all US-ASCII digits (octet values * 0x30 to 0x39) are interpreted starting from the beginning of * the string to the first non-digit or the end of the string. */ static int ascii_numeric_cmp(const char *text, size_t tlen, const char *pat) { unsigned text_digit_len; unsigned pat_digit_len; if (Uisdigit(*pat)) { if (Uisdigit(*text)) { /* Count how many digits each string has */ for (text_digit_len = 0; tlen-- && Uisdigit(text[text_digit_len]); text_digit_len++); for (pat_digit_len = 0; Uisdigit(pat[pat_digit_len]); pat_digit_len++); if (text_digit_len < pat_digit_len) { /* Pad "text" with leading 0s */ while (pat_digit_len > text_digit_len) { /* "text" can only be less or equal to "pat" */ if ('0' < *pat) { return (-1); } pat++; pat_digit_len--; } } else if (text_digit_len > pat_digit_len) { /* Pad "pad" with leading 0s */ while (text_digit_len > pat_digit_len) { /* "pad" can only be greater or equal to "text" */ if (*text > '0') { return 1; } text++; text_digit_len--; } } /* CLAIM: If we here, we have two non-empty digital suffixes of equal length */ while (text_digit_len > 0) { if (*text < *pat) { return -1; } else if (*text > *pat) { return 1; } /* Characters are equal, carry on */ text++; pat++; text_digit_len--; } return (0); } else { return 1; } } else if (Uisdigit(*text)) { return -1; } else { return 0; /* both not digits */ } } static comparator_t *lookup_rel(int relation) { comparator_t *ret; ret = NULL; switch (relation) { case B_EQ: ret = &rel_eq; break; case B_NE: ret = &rel_ne; break; case B_GT: ret = &rel_gt; break; case B_GE: ret = &rel_ge; break; case B_LT: ret = &rel_lt; break; case B_LE: ret = &rel_le; } return ret; } EXPORTED comparator_t *lookup_comp(int comp, int mode, int relation, void **comprock) { comparator_t *ret; ret = NULL; *comprock = NULL; #if VERBOSE printf("comp%d mode%d relat%d \n", comp, mode, relation); #endif switch (comp) { case B_OCTET: switch (mode) { case B_IS: ret = &rel_eq; *comprock = (void **) &octet_cmp; break; case B_CONTAINS: ret = &octet_contains; break; case B_MATCHES: ret = &octet_matches; break; #ifdef ENABLE_REGEX case B_REGEX: ret = &octet_regex; break; #endif case B_VALUE: ret = lookup_rel(relation); *comprock = (void **) &octet_cmp; break; } break; /*end of octet */ case B_ASCIICASEMAP: switch (mode) { case B_IS: ret = &rel_eq; *comprock = (void **) &ascii_casemap_cmp; break; case B_CONTAINS: ret = &ascii_casemap_contains; break; case B_MATCHES: ret = &ascii_casemap_matches; break; #ifdef ENABLE_REGEX case B_REGEX: /* the ascii-casemap destinction is made during the compilation of the regex in verify_regex() */ ret = &octet_regex; break; #endif case B_VALUE: ret = lookup_rel(relation); *comprock = (void **) &ascii_casemap_cmp; break; } break;/*end of ascii casemap */ case B_ASCIINUMERIC: switch (mode) { case B_IS: ret = &rel_eq; *comprock = (void **) &ascii_numeric_cmp; break; case B_COUNT: case B_VALUE: ret = lookup_rel(relation); *comprock = (void **) &ascii_numeric_cmp; break; } break; } return ret; } cyrus-imapd-2.5.10/sieve/comparator.h0000644000175000017500000000504713001236020014401 00000000000000/* comparator.h * Larry Greenfield * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #ifndef COMPARATOR_H #define COMPARATOR_H #include #ifdef ENABLE_REGEX # ifdef HAVE_PCREPOSIX_H # include # include # else /* !HAVE_PCREPOSIX_H */ # ifdef HAVE_RXPOSIX_H # include # else /* !HAVE_RXPOSIX_H */ # include # endif /* HAVE_RXPOSIX_H */ # endif /* HAVE_PCREPOSIX_H */ #endif /* ENABLE_REGEX */ /* compares pat to text; returns 1 if it's true, 0 otherwise first arg is text, second arg is pat, third arg is rock */ typedef int comparator_t(const char *, size_t, const char *, void *); /* returns a pointer to a comparator function given it's name */ comparator_t *lookup_comp(int comp, int mode, int relation, void **rock); #endif /* COMPARATOR_H */ cyrus-imapd-2.5.10/sieve/sieve_err.et0000644000175000017500000000441312772415051014413 00000000000000# sieve_err.et -- Error codes for the Sieve subsystem # # Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. # # Redistribution and use in source and binary forms, with or without # modification, are permitted provided that the following conditions # are met: # # 1. Redistributions of source code must retain the above copyright # notice, this list of conditions and the following disclaimer. # # 2. Redistributions in binary form must reproduce the above copyright # notice, this list of conditions and the following disclaimer in # the documentation and/or other materials provided with the # distribution. # # 3. The name "Carnegie Mellon University" must not be used to # endorse or promote products derived from this software without # prior written permission. For permission or any legal # details, please contact # Carnegie Mellon University # Center for Technology Transfer and Enterprise Creation # 4615 Forbes Avenue # Suite 302 # Pittsburgh, PA 15213 # (412) 268-7393, fax: (412) 268-7395 # innovation@andrew.cmu.edu # # 4. Redistributions of any form whatsoever must retain the following # acknowledgment: # "This product includes software developed by Computing Services # at Carnegie Mellon University (http://www.cmu.edu/computing/)." # # CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO # THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY # AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE # FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES # WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN # AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING # OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. error_table siev ec SIEVE_FAIL, "Generic Sieve error" ec SIEVE_NOT_FINALIZED, "Sieve interpretor not finalized" ec SIEVE_PARSE_ERROR, "Parse error in Sieve script" ec SIEVE_RUN_ERROR, "Run-time error during Sieve execution" ec SIEVE_INTERNAL_ERROR, "Internal error in Sieve subsystem" ec SIEVE_NOMEM, "Memory exhausted in Sieve subsystem" ec SIEVE_DONE, "Sieve action already taken" ec SIEVE_SCRIPT_RELOADED, "Sieve script was loaded in the past" end cyrus-imapd-2.5.10/sieve/sieve-lex.l0000644000175000017500000001520513001236020014134 00000000000000%{ /* sieve.l -- sieve lexer * Larry Greenfield * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #ifdef HAVE_CONFIG_H #include #endif #include "xmalloc.h" #include "sieve/tree.h" #include "sieve/sieve_interface.h" #include "sieve/sieve.h" #define YY_NO_INPUT #define YY_DECL int yylex(YYSTYPE *yylval, sieve_script_t *parse_script) static int tonum(char *c); static char *chkstr(char *); static char *mlbuf; static int mlbufsz, mlcur; extern void sieveerror(sieve_script_t *, char *); %} %option yylineno %option noyywrap %option nounput %option prefix="sieve" outfile="lex.yy.c" ws [ \t]+ ident [a-zA-Z_][a-zA-Z_0-9]* CRLF (\r\n|\r|\n) %state MULTILINE %state QSTRING %% ^\.{CRLF} { BEGIN INITIAL; if (mlbuf) mlbuf[mlcur] = '\0'; yylval->sval = chkstr(mlbuf); return STRING; } ^\.\. { /* dot stuffing! we want one . */ yyless(1); } (.|\n) { if (mlcur == mlbufsz) mlbuf = xrealloc(mlbuf, 1 + (mlbufsz+=1024)); mlbuf[mlcur++] = yytext[0]; } <> { BEGIN INITIAL; sieveerror(parse_script, "unexpected end of file in string"); if (mlbuf) free(mlbuf); yyterminate(); } \" { BEGIN INITIAL; if (mlbuf) mlbuf[mlcur] = '\0'; yylval->sval = chkstr(mlbuf); return STRING; } \\. { if (mlcur == mlbufsz) mlbuf = xrealloc(mlbuf, 1 + (mlbufsz+=1024)); mlbuf[mlcur++] = yytext[1]; } (.|\n) { if (mlcur == mlbufsz) mlbuf = xrealloc(mlbuf, 1 + (mlbufsz+=1024)); mlbuf[mlcur++] = yytext[0]; } <> { sieveerror(parse_script, "unexpected end of file in string"); if (mlbuf) free(mlbuf); BEGIN INITIAL; yyterminate(); } text:{ws}?(#.*)?{CRLF} { BEGIN MULTILINE; mlcur = 0; mlbufsz = 0; mlbuf = NULL; } \" { BEGIN QSTRING; mlcur = 0; mlbufsz = 0; mlbuf = NULL; } [0-9]+[KMGkmg]? { yylval->nval = tonum(yytext); return NUMBER; } if return IF; elsif return ELSIF; else return ELSE; anyof return ANYOF; allof return ALLOF; exists return EXISTS; false return SFALSE; true return STRUE; address return ADDRESS; envelope return ENVELOPE; header return HEADER; body return BODY; not return NOT; size return SIZE; hasflag return HASFLAG; reject return REJCT; fileinto return FILEINTO; redirect return REDIRECT; keep return KEEP; require return REQUIRE; stop return STOP; discard return DISCARD; setflag return SETFLAG; addflag return ADDFLAG; removeflag return REMOVEFLAG; mark return MARK; unmark return UNMARK; notify return NOTIFY; denotify return DENOTIFY; :id return ID; :method return METHOD; :options return OPTIONS; :low return LOW; :normal return NORMAL; :high return HIGH; :message return MESSAGE; vacation return VACATION; :days return DAYS; :seconds return SECONDS; :addresses return ADDRESSES; :subject return SUBJECT; :from return FROM; :handle return HANDLE; :mime return MIME; :comparator return COMPARATOR; :is return IS; :contains return CONTAINS; :matches return MATCHES; :regex return REGEX; :count return COUNT; :value return VALUE; :over return OVER; :under return UNDER; :all return ALL; :localpart return LOCALPART; :domain return DOMAIN; :user return USER; :detail return DETAIL; :raw return RAW; :text return TEXT; :content return CONTENT; include return INCLUDE; :personal return PERSONAL; :global return GLOBAL; :optional return OPTIONAL; :once return ONCE; return return RETURN; :copy return COPY; date return DATE; currentdate return CURRENTDATE; :index return INDEX; :last return LAST; :zone return ZONE; :originalzone return ORIGINALZONE; :flags return FLAGS; [ \t\n\r] ; /* ignore whitespace */ #.* ; /* ignore hash comments */ "/*"([^\*]|\*[^\/])*\*?"*/" ; /* ignore bracket comments */ . return yytext[0]; %% /* */ static int tonum(char *c) { int val = atoi(c); switch (c[strlen(c)-1]) { case 'K': case 'k': val *= (1 << 10); break; case 'M': case 'm': val *= (1 << 20); break; case 'G': case 'g': val *= (1 << 30); break; default: break; } return val; } /* convert NULL strings to "" */ static char *chkstr(char *str) { if (!str) return xstrdup(""); else return str; } cyrus-imapd-2.5.10/sieve/sieve.y0000644000175000017500000015475313001236020013377 00000000000000%{ /* sieve.y -- sieve parser * Larry Greenfield * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #ifdef HAVE_CONFIG_H #include #endif #include #include #include #include "xmalloc.h" #include "sieve/comparator.h" #include "sieve/interp.h" #include "sieve/script.h" #include "sieve/tree.h" #include "sieve/flags.h" #include "imapurl.h" #include "lib/gmtoff.h" #include "util.h" #include "imparse.h" #include "libconfig.h" #include "times.h" #define ERR_BUF_SIZE 1024 /* definitions */ extern int addrparse(sieve_script_t*); typedef struct yy_buffer_state *YY_BUFFER_STATE; extern YY_BUFFER_STATE addr_scan_string(const char*); extern void addr_delete_buffer(YY_BUFFER_STATE); extern int sievelineno; struct vtags { int seconds; strarray_t *addresses; char *subject; char *from; char *handle; int mime; }; struct htags { int index; char *comparator; int comptag; int relation; }; struct aetags { int index; int addrtag; char *comparator; int comptag; int relation; }; struct btags { int transform; int offset; strarray_t *content_types; char *comparator; int comptag; int relation; }; struct ntags { char *method; char *id; strarray_t *options; int priority; char *message; }; struct dtags { int comptag; int relation; void *pattern; int priority; }; struct itags { int location; int once; int optional; }; struct dttags { int index; int zonetag; char *zone; int comptag; int relation; char *comparator; int date_part; }; static char *check_reqs(sieve_script_t *script, strarray_t *sl); struct ftags { int copy; strarray_t *flags; }; static test_t *build_address(int t, struct aetags *ae, strarray_t *sl, strarray_t *pl); static test_t *build_header(int t, struct htags *h, strarray_t *sl, strarray_t *pl); static test_t *build_body(int t, struct btags *b, strarray_t *pl); static test_t *build_date(int t, struct dttags *dt, char *hn, strarray_t *kl); static test_t *build_hasflag(int t, struct htags *h, strarray_t *pl); static commandlist_t *build_vacation(int t, struct vtags *h, char *s); static commandlist_t *build_notify(int t, struct ntags *n); static commandlist_t *build_denotify(int t, struct dtags *n); static commandlist_t *build_keep(int t, struct ftags *f); static commandlist_t *build_fileinto(int t, struct ftags *f, char *folder); static commandlist_t *build_redirect(int t, int c, char *a); static commandlist_t *build_include(int, struct itags *, char*); static struct aetags *new_aetags(void); static struct aetags *canon_aetags(struct aetags *ae); static void free_aetags(struct aetags *ae); static struct htags *new_htags(void); static struct htags *canon_htags(struct htags *h); static void free_htags(struct htags *h); static struct btags *new_btags(void); static struct btags *canon_btags(struct btags *b); static void free_btags(struct btags *b); static struct vtags *new_vtags(void); static struct vtags *canon_vtags(sieve_script_t *script, struct vtags *v); static void free_vtags(struct vtags *v); static struct ntags *new_ntags(void); static struct ntags *canon_ntags(struct ntags *n); static void free_ntags(struct ntags *n); static struct dtags *new_dtags(void); static struct dtags *canon_dtags(struct dtags *d); static void free_dtags(struct dtags *d); static struct itags *new_itags(void); static struct dttags *new_dttags(void); static struct dttags *canon_dttags(struct dttags *dt); static void free_dttags(struct dttags *b); static struct ftags *new_ftags(void); static struct ftags *canon_ftags(struct ftags *f); static void free_ftags(struct ftags *f); static int verify_stringlist(sieve_script_t*, strarray_t *sl, int (*verify)(sieve_script_t*, char *)); static int verify_mailbox(sieve_script_t*, char *s); static int verify_address(sieve_script_t*, char *s); static int verify_header(sieve_script_t*, char *s); static int verify_addrheader(sieve_script_t*, char *s); static int verify_envelope(sieve_script_t*, char *s); static int verify_relat(sieve_script_t*, char *s); static int verify_zone(sieve_script_t*, char *s); static int verify_date_part(sieve_script_t *parse_script, char *dp); #ifdef ENABLE_REGEX static int verify_regex(sieve_script_t*, char *s, int cflags); static int verify_regexs(sieve_script_t*,const strarray_t *sl, char *comp); #endif static int verify_utf8(sieve_script_t*, char *s); void yyerror(sieve_script_t*, const char *msg); extern int yylex(void*, sieve_script_t*); extern void sieverestart(FILE *f); #define YYERROR_VERBOSE /* i want better error messages! */ /* byacc default is 500, bison default is 10000 - go with the larger to support big sieve scripts (see Bug #3461) */ #define YYSTACKSIZE 10000 %} %union { int nval; char *sval; strarray_t *sl; test_t *test; testlist_t *testl; commandlist_t *cl; struct vtags *vtag; struct aetags *aetag; struct htags *htag; struct btags *btag; struct ntags *ntag; struct dtags *dtag; struct itags *itag; struct dttags *dttag; struct ftags *ftag; } %token NUMBER %token STRING %token IF ELSIF ELSE %token REJCT FILEINTO REDIRECT KEEP STOP DISCARD VACATION REQUIRE %token SETFLAG ADDFLAG REMOVEFLAG MARK UNMARK HASFLAG FLAGS %token NOTIFY DENOTIFY %token ANYOF ALLOF EXISTS SFALSE STRUE HEADER NOT SIZE ADDRESS ENVELOPE BODY %token COMPARATOR IS CONTAINS MATCHES REGEX COUNT VALUE OVER UNDER %token GT GE LT LE EQ NE %token ALL LOCALPART DOMAIN USER DETAIL %token RAW TEXT CONTENT %token DAYS ADDRESSES SUBJECT FROM HANDLE MIME SECONDS %token METHOD ID OPTIONS LOW NORMAL HIGH ANY MESSAGE %token INCLUDE PERSONAL GLOBAL RETURN OPTIONAL ONCE %token COPY %token DATE CURRENTDATE INDEX LAST ZONE ORIGINALZONE %token YEAR MONTH DAY JULIAN HOUR MINUTE SECOND TIME ISO8601 STD11 WEEKDAY %type commands command action elsif block %type stringlist strings %type test %type comptag relcomp sizetag addrparttag addrorenv copy rtags %type testlist tests %type htags %type aetags %type btags %type vtags %type ntags %type dtags %type itags %type dttags %type priority %type ftags %name-prefix="sieve" %defines %destructor { free_tree($$); } commands command action elsif block %parse-param{sieve_script_t *parse_script} %lex-param{sieve_script_t *parse_script} %pure_parser %% start: reqs { parse_script->cmds = NULL; } | reqs commands { parse_script->cmds = $2; } ; reqs: /* empty */ | require reqs ; require: REQUIRE stringlist ';' { char *err = check_reqs(parse_script, $2); if (err) { yyerror(parse_script, err); free(err); YYERROR; } } ; commands: command { $$ = $1; } | command commands { $1->next = $2; $$ = $1; } ; command: action ';' { $$ = $1; } | IF test block elsif { $$ = new_if($2, $3, $4); } | error ';' { $$ = new_command(STOP); } ; elsif: /* empty */ { $$ = NULL; } | ELSIF test block elsif { $$ = new_if($2, $3, $4); } | ELSE block { $$ = $2; } ; action: REJCT STRING { if (!parse_script->support.reject) { yyerror(parse_script, "reject MUST be enabled with \"require\""); YYERROR; } if (!verify_utf8(parse_script, $2)) { YYERROR; /* vu should call yyerror() */ } $$ = new_command(REJCT); $$->u.str = $2; } | FILEINTO ftags STRING { if (!parse_script->support.fileinto) { yyerror(parse_script, "fileinto MUST be enabled with \"require\""); YYERROR; } if (!verify_mailbox(parse_script, $3)) { YYERROR; /* vm should call yyerror() */ } $$ = build_fileinto(FILEINTO, canon_ftags($2), $3); } | REDIRECT rtags STRING { if (!verify_address(parse_script, $3)) { YYERROR; /* va should call yyerror() */ } $$ = build_redirect(REDIRECT, $2, $3); } | KEEP ftags { $$ = build_keep(KEEP,canon_ftags($2)); } | STOP { $$ = new_command(STOP); } | DISCARD { $$ = new_command(DISCARD); } | VACATION vtags STRING { if (!parse_script->support.vacation) { yyerror(parse_script, "vacation MUST be enabled with \"require\""); YYERROR; } if (($2->mime == -1) && !verify_utf8(parse_script, $3)) { YYERROR; /* vu should call yyerror() */ } $$ = build_vacation(VACATION, canon_vtags(parse_script, $2), $3); } | SETFLAG stringlist { if (!(parse_script->support.imapflags || parse_script->support.imap4flags)) { yyerror(parse_script, "imap4flags MUST be enabled with \"require\""); YYERROR; } verify_flaglist($2); if(!$2->count) { strarray_add($2, ""); } $$ = new_command(SETFLAG); $$->u.sl = $2; } | ADDFLAG stringlist { if (!(parse_script->support.imapflags || parse_script->support.imap4flags)) { yyerror(parse_script, "imap4flags MUST be enabled with \"require\""); YYERROR; } verify_flaglist($2); if(!$2->count) { strarray_add($2, ""); } $$ = new_command(ADDFLAG); $$->u.sl = $2; } | REMOVEFLAG stringlist { if (!(parse_script->support.imapflags || parse_script->support.imap4flags)) { yyerror(parse_script, "imap4flags MUST be enabled with \"require\""); YYERROR; } verify_flaglist($2); if(!$2->count) { strarray_add($2, ""); } $$ = new_command(REMOVEFLAG); $$->u.sl = $2; } | MARK { if (!parse_script->support.imapflags) { yyerror(parse_script, "imapflags MUST be enabled with \"require\""); YYERROR; } $$ = new_command(MARK); } | UNMARK { if (!parse_script->support.imapflags) { yyerror(parse_script, "imapflags MUST be enabled with \"require\""); YYERROR; } $$ = new_command(UNMARK); } | NOTIFY ntags { if (!parse_script->support.notify) { yyerror(parse_script, "notify MUST be enabled with \"require\""); $$ = new_command(NOTIFY); YYERROR; } else { $$ = build_notify(NOTIFY, canon_ntags($2)); } } | DENOTIFY dtags { if (!parse_script->support.notify) { yyerror(parse_script, "notify MUST be enabled with \"require\""); $$ = new_command(DENOTIFY); YYERROR; } else { $$ = build_denotify(DENOTIFY, canon_dtags($2)); if ($$ == NULL) { yyerror(parse_script, "unable to find a compatible comparator"); YYERROR; } } } | INCLUDE itags STRING { if (!parse_script->support.include) { yyerror(parse_script, "include MUST be enabled with \"require\""); YYERROR; } int i; for (i = 0; $3[i] != '\0'; i++) { if ($3[i] == '/') { yyerror(parse_script, "included script name must not contain slash"); YYERROR; break; } } $$ = build_include(INCLUDE, $2, $3); } | RETURN { if (!parse_script->support.include) { yyerror(parse_script, "include MUST be enabled with \"require\""); YYERROR; } $$ = new_command(RETURN); } ; itags: /* empty */ { $$ = new_itags(); } | itags PERSONAL { if ($$->location != -1) { yyerror(parse_script, "duplicate location (:personal or :global)"); YYERROR; } else { $$->location = PERSONAL; }} | itags GLOBAL { if ($$->location != -1) { yyerror(parse_script, "duplicate location (:personal or :global)"); YYERROR; } else { $$->location = GLOBAL; }} | itags ONCE { if ($$->once != -1) { yyerror(parse_script, "duplicate :once"); YYERROR; } else { $$->once = 1; }} | itags OPTIONAL { if ($$->optional != -1) { yyerror(parse_script, "duplicate :optional"); YYERROR; } else { $$->optional = 1; }} ; ntags: /* empty */ { $$ = new_ntags(); } | ntags ID STRING { if ($$->id != NULL) { yyerror(parse_script, "duplicate :method"); YYERROR; } else { $$->id = $3; } } | ntags METHOD STRING { if ($$->method != NULL) { yyerror(parse_script, "duplicate :method"); YYERROR; } else { $$->method = $3; } } | ntags OPTIONS stringlist { if ($$->options != NULL) { yyerror(parse_script, "duplicate :options"); YYERROR; } else { $$->options = $3; } } | ntags priority { if ($$->priority != -1) { yyerror(parse_script, "duplicate :priority"); YYERROR; } else { $$->priority = $2; } } | ntags MESSAGE STRING { if ($$->message != NULL) { yyerror(parse_script, "duplicate :message"); YYERROR; } else { $$->message = $3; } } ; dtags: /* empty */ { $$ = new_dtags(); } | dtags priority { if ($$->priority != -1) { yyerror(parse_script, "duplicate priority level"); YYERROR; } else { $$->priority = $2; } } | dtags comptag STRING { if ($$->comptag != -1) { yyerror(parse_script, "duplicate comparator type tag"); YYERROR; } $$->comptag = $2; #ifdef ENABLE_REGEX if ($$->comptag == REGEX) { int cflags = REG_EXTENDED | REG_NOSUB | REG_ICASE; if (!verify_regex(parse_script, $3, cflags)) { YYERROR; } } #endif $$->pattern = $3; } | dtags relcomp STRING { $$ = $1; if ($$->comptag != -1) { yyerror(parse_script, "duplicate comparator type tag"); YYERROR; } else { $$->comptag = $2; $$->relation = verify_relat(parse_script, $3); if ($$->relation==-1) {YYERROR; /*vr called yyerror()*/ } } } ; priority: LOW { $$ = LOW; } | NORMAL { $$ = NORMAL; } | HIGH { $$ = HIGH; } ; vtags: /* empty */ { $$ = new_vtags(); } | vtags DAYS NUMBER { if ($$->seconds != -1) { yyerror(parse_script, "duplicate :days or :seconds"); YYERROR; } else { $$->seconds = $3 * DAY2SEC; } } | vtags SECONDS NUMBER { if (!parse_script->support.vacation_seconds) { yyerror(parse_script, "vacation-seconds not required"); YYERROR; } if ($$->seconds != -1) { yyerror(parse_script, "duplicate :days or :seconds"); YYERROR; } else { $$->seconds = $3; } } | vtags ADDRESSES stringlist { if ($$->addresses != NULL) { yyerror(parse_script, "duplicate :addresses"); YYERROR; } else if (!verify_stringlist(parse_script, $3, verify_address)) { YYERROR; } else { $$->addresses = $3; } } | vtags SUBJECT STRING { if ($$->subject != NULL) { yyerror(parse_script, "duplicate :subject"); YYERROR; } else if (!verify_utf8(parse_script, $3)) { YYERROR; /* vu should call yyerror() */ } else { $$->subject = $3; } } | vtags FROM STRING { if ($$->from != NULL) { yyerror(parse_script, "duplicate :from"); YYERROR; } else if (!verify_address(parse_script, $3)) { YYERROR; /* va should call yyerror() */ } else { $$->from = $3; } } | vtags HANDLE STRING { if ($$->handle != NULL) { yyerror(parse_script, "duplicate :handle"); YYERROR; } else if (!verify_utf8(parse_script, $3)) { YYERROR; /* vu should call yyerror() */ } else { $$->handle = $3; } } | vtags MIME { if ($$->mime != -1) { yyerror(parse_script, "duplicate :mime"); YYERROR; } else { $$->mime = MIME; } } ; stringlist: '[' strings ']' { $$ = $2; } | STRING { $$ = strarray_new(); strarray_appendm($$, $1); } ; strings: STRING { $$ = strarray_new(); strarray_appendm($$, $1); } | strings ',' STRING { $$ = $1; strarray_appendm($$, $3); } ; block: '{' commands '}' { $$ = $2; } | '{' '}' { $$ = NULL; } ; test: ANYOF testlist { $$ = new_test(ANYOF); $$->u.tl = $2; } | ALLOF testlist { $$ = new_test(ALLOF); $$->u.tl = $2; } | EXISTS stringlist { $$ = new_test(EXISTS); $$->u.sl = $2; } | SFALSE { $$ = new_test(SFALSE); } | STRUE { $$ = new_test(STRUE); } | HEADER htags stringlist stringlist { if (!verify_stringlist(parse_script, $3, verify_header)) { YYERROR; /* vh should call yyerror() */ } if (!verify_stringlist(parse_script, $4, verify_utf8)) { YYERROR; /* vu should call yyerror() */ } $2 = canon_htags($2); #ifdef ENABLE_REGEX if ($2->comptag == REGEX) { if (!(verify_regexs(parse_script, $4, $2->comparator))) { YYERROR; } } #endif $$ = build_header(HEADER, $2, $3, $4); if ($$ == NULL) { yyerror(parse_script, "unable to find a compatible comparator"); YYERROR; } } | HASFLAG htags stringlist { if (!parse_script->support.imap4flags) { yyerror(parse_script, "imap4flags MUST be enabled with \"require\""); YYERROR; } $2 = canon_htags($2); #ifdef ENABLE_REGEX if ($2->comptag == REGEX) { if (!(verify_regexs(parse_script, $3, $2->comparator))) { YYERROR; } } #endif $$ = build_hasflag(HASFLAG, $2, $3); if ($$ == NULL) { yyerror(parse_script, "unable to find a compatible comparator"); YYERROR; } } | addrorenv aetags stringlist stringlist { if (($1 == ADDRESS) && !verify_stringlist(parse_script, $3, verify_addrheader)) { YYERROR; } else if (($1 == ENVELOPE) && !verify_stringlist(parse_script, $3, verify_envelope)) { YYERROR; } $2 = canon_aetags($2); #ifdef ENABLE_REGEX if ($2->comptag == REGEX) { if (!( verify_regexs(parse_script, $4, $2->comparator))) { YYERROR; } } #endif $$ = build_address($1, $2, $3, $4); if ($$ == NULL) { yyerror(parse_script, "unable to find a compatible comparator"); YYERROR; } } | BODY btags stringlist { if (!parse_script->support.body) { yyerror(parse_script, "body MUST be enabled with \"require\""); YYERROR; } if (!verify_stringlist(parse_script, $3, verify_utf8)) { YYERROR; /* vu should call yyerror() */ } $2 = canon_btags($2); #ifdef ENABLE_REGEX if ($2->comptag == REGEX) { if (!(verify_regexs(parse_script, $3, $2->comparator))) { YYERROR; } } #endif $$ = build_body(BODY, $2, $3); if ($$ == NULL) { yyerror(parse_script, "unable to find a compatible comparator"); YYERROR; } } | NOT test { $$ = new_test(NOT); $$->u.t = $2; } | SIZE sizetag NUMBER { $$ = new_test(SIZE); $$->u.sz.t = $2; $$->u.sz.n = $3; } | DATE dttags STRING STRING stringlist {if (!parse_script->support.date) { yyerror(parse_script, "date MUST be enabled with \"require\""); YYERROR; } $2->date_part = verify_date_part(parse_script, $4); if ($2->date_part == -1) { YYERROR; /*vr called yyerror()*/ } $2 = canon_dttags($2); $$ = build_date(DATE, $2, $3, $5); if ($$ == NULL) { yyerror(parse_script, "unable to find a compatible comparator"); YYERROR; } } | CURRENTDATE dttags STRING stringlist {if (!parse_script->support.date) { yyerror(parse_script, "date MUST be enabled with \"require\""); YYERROR; } if ($2->index != 0) { yyerror(parse_script, "index argument is not allowed in currentdate"); YYERROR; } if ($2->zonetag == ORIGINALZONE) { yyerror(parse_script, "originalzone argument is not allowed in currentdate"); YYERROR; } $2->date_part = verify_date_part(parse_script, $3); if ($2->date_part == -1) { YYERROR; /*vr called yyerror()*/ } $2 = canon_dttags($2); $$ = build_date(CURRENTDATE, $2, NULL, $4); if ($$ == NULL) { yyerror(parse_script, "unable to find a compatible comparator"); YYERROR; } } | error { $$ = NULL; } ; addrorenv: ADDRESS { $$ = ADDRESS; } | ENVELOPE {if (!parse_script->support.envelope) {yyerror(parse_script, "envelope MUST be enabled with \"require\""); YYERROR;} else{$$ = ENVELOPE; } } ; aetags: /* empty */ { $$ = new_aetags(); } | aetags addrparttag { $$ = $1; if ($$->addrtag != -1) { yyerror(parse_script, "duplicate or conflicting address part tag"); YYERROR; } else { $$->addrtag = $2; } } | aetags comptag { $$ = $1; if ($$->comptag != -1) { yyerror(parse_script, "duplicate comparator type tag"); YYERROR; } else { $$->comptag = $2; } } | aetags relcomp STRING{ $$ = $1; if ($$->comptag != -1) { yyerror(parse_script, "duplicate comparator type tag"); YYERROR; } else { $$->comptag = $2; $$->relation = verify_relat(parse_script, $3); if ($$->relation==-1) {YYERROR; /*vr called yyerror()*/ } } } | aetags COMPARATOR STRING { $$ = $1; if ($$->comparator != NULL) { yyerror(parse_script, "duplicate comparator tag"); YYERROR; } else if (!strcmp($3, "i;ascii-numeric") && !parse_script->support.i_ascii_numeric) { yyerror(parse_script, "comparator-i;ascii-numeric MUST be enabled with \"require\""); YYERROR; } else { $$->comparator = $3; } } | aetags INDEX NUMBER { $$ = $1; if (!parse_script->support.index) { yyerror(parse_script, "index MUST be enabled with \"require\""); YYERROR; } if ($$->index != 0) { yyerror(parse_script, "duplicate index argument"); YYERROR; } if ($3 <= 0) { yyerror(parse_script, "invalid index value"); YYERROR; } else { $$->index = $3; } } | aetags LAST { $$ = $1; if (!parse_script->support.index) { yyerror(parse_script, "index MUST be enabled with \"require\""); YYERROR; } if ($$->index == 0) { yyerror(parse_script, "index argument is required"); YYERROR; } else if ($$->index < 0) { yyerror(parse_script, "duplicate last argument"); YYERROR; } else { $$->index *= -1; } } ; htags: /* empty */ { $$ = new_htags(); } | htags comptag { $$ = $1; if ($$->comptag != -1) { yyerror(parse_script, "duplicate comparator type tag"); YYERROR; } else { $$->comptag = $2; } } | htags relcomp STRING { $$ = $1; if ($$->comptag != -1) { yyerror(parse_script, "duplicate comparator type tag"); YYERROR; } else { $$->comptag = $2; $$->relation = verify_relat(parse_script, $3); if ($$->relation==-1) {YYERROR; /*vr called yyerror()*/ } } } | htags COMPARATOR STRING { $$ = $1; if ($$->comparator != NULL) { yyerror(parse_script, "duplicate comparator tag"); YYERROR; } else if (!strcmp($3, "i;ascii-numeric") && !parse_script->support.i_ascii_numeric) { yyerror(parse_script, "comparator-i;ascii-numeric MUST be enabled with \"require\""); YYERROR; } else { $$->comparator = $3; } } | htags INDEX NUMBER { $$ = $1; if (!parse_script->support.index) { yyerror(parse_script, "index MUST be enabled with \"require\""); YYERROR; } if ($$->index != 0) { yyerror(parse_script, "duplicate index argument"); YYERROR; } if ($3 <= 0) { yyerror(parse_script, "invalid index value"); YYERROR; } else { $$->index = $3; } } | htags LAST { $$ = $1; if (!parse_script->support.index) { yyerror(parse_script, "index MUST be enabled with \"require\""); YYERROR; } if ($$->index == 0) { yyerror(parse_script, "index argument is required"); YYERROR; } else if ($$->index < 0) { yyerror(parse_script, "duplicate last argument"); YYERROR; } else { $$->index *= -1; } } ; btags: /* empty */ { $$ = new_btags(); } | btags RAW { $$ = $1; if ($$->transform != -1) { yyerror(parse_script, "duplicate or conflicting transform tag"); YYERROR; } else { $$->transform = RAW; } } | btags TEXT { $$ = $1; if ($$->transform != -1) { yyerror(parse_script, "duplicate or conflicting transform tag"); YYERROR; } else { $$->transform = TEXT; } } | btags CONTENT stringlist { $$ = $1; if ($$->transform != -1) { yyerror(parse_script, "duplicate or conflicting transform tag"); YYERROR; } else { $$->transform = CONTENT; $$->content_types = $3; } } | btags comptag { $$ = $1; if ($$->comptag != -1) { yyerror(parse_script, "duplicate comparator type tag"); YYERROR; } else { $$->comptag = $2; } } | btags relcomp STRING { $$ = $1; if ($$->comptag != -1) { yyerror(parse_script, "duplicate comparator type tag"); YYERROR; } else { $$->comptag = $2; $$->relation = verify_relat(parse_script, $3); if ($$->relation==-1) {YYERROR; /*vr called yyerror()*/ } } } | btags COMPARATOR STRING { $$ = $1; if ($$->comparator != NULL) { yyerror(parse_script, "duplicate comparator tag"); YYERROR; } else if (!strcmp($3, "i;ascii-numeric") && !parse_script->support.i_ascii_numeric) { yyerror(parse_script, "comparator-i;ascii-numeric MUST be enabled with \"require\""); YYERROR; } else { $$->comparator = $3; } } ; dttags: /* empty */ { $$ = new_dttags(); } | dttags comptag { $$ = $1; if ($$->comptag != -1) { yyerror(parse_script, "duplicate comparator type tag"); YYERROR; } else { $$->comptag = $2; } } | dttags relcomp STRING { $$ = $1; if ($$->comptag != -1) { yyerror(parse_script, "duplicate comparator type tag"); YYERROR; } else { $$->comptag = $2; $$->relation = verify_relat(parse_script, $3); if ($$->relation == -1) { YYERROR; /*vr called yyerror()*/ } } } | dttags COMPARATOR STRING { $$ = $1; if ($$->comparator != NULL) { yyerror(parse_script, "duplicate comparator tag"); YYERROR; } else if (!strcmp($3, "i;ascii-numeric") && !parse_script->support.i_ascii_numeric) { yyerror(parse_script, "comparator-i;ascii-numeric MUST be enabled with \"require\""); YYERROR; } else { $$->comparator = $3; } } | dttags INDEX NUMBER { $$ = $1; if (!parse_script->support.index) { yyerror(parse_script, "index MUST be enabled with \"require\""); YYERROR; } if ($$->index != 0) { yyerror(parse_script, "duplicate index argument"); YYERROR; } if ($3 <= 0) { yyerror(parse_script, "invalid index value"); YYERROR; } else { $$->index = $3; } } | dttags LAST { $$ = $1; if (!parse_script->support.index) { yyerror(parse_script, "index MUST be enabled with \"require\""); YYERROR; } if ($$->index == 0) { yyerror(parse_script, "index argument is required"); YYERROR; } else if ($$->index < 0) { yyerror(parse_script, "duplicate last argument"); YYERROR; } else { $$->index *= -1; } } | dttags ZONE STRING { $$ = $1; if ($$->zonetag != -1) { yyerror(parse_script, "duplicate zone tag"); YYERROR; } else { if (verify_zone(parse_script, $3) == -1) { YYERROR; /*vr called yyerror()*/ } else { $$->zone = $3; $$->zonetag = ZONE; } } } | dttags ORIGINALZONE { $$ = $1; if ($$->zonetag != -1) { yyerror(parse_script, "duplicate zone tag"); YYERROR; } else { $$->zonetag = ORIGINALZONE; } } ; addrparttag: ALL { $$ = ALL; } | LOCALPART { $$ = LOCALPART; } | DOMAIN { $$ = DOMAIN; } | USER { if (!parse_script->support.subaddress) { yyerror(parse_script, "subaddress MUST be enabled with \"require\""); YYERROR; } $$ = USER; } | DETAIL { if (!parse_script->support.subaddress) { yyerror(parse_script, "subaddress MUST be enabled with \"require\""); YYERROR; } $$ = DETAIL; } ; comptag: IS { $$ = IS; } | CONTAINS { $$ = CONTAINS; } | MATCHES { $$ = MATCHES; } | REGEX { if (!parse_script->support.regex) { yyerror(parse_script, "regex MUST be enabled with \"require\""); YYERROR; } $$ = REGEX; } ; relcomp: COUNT { if (!parse_script->support.relational) { yyerror(parse_script, "relational MUST be enabled with \"require\""); YYERROR; } $$ = COUNT; } | VALUE { if (!parse_script->support.relational) { yyerror(parse_script, "relational MUST be enabled with \"require\""); YYERROR; } $$ = VALUE; } ; sizetag: OVER { $$ = OVER; } | UNDER { $$ = UNDER; } ; copy: COPY { if (!parse_script->support.copy) { yyerror(parse_script, "copy MUST be enabled with \"require\""); YYERROR; } $$ = 1; } ; ftags: /* empty */ { $$ = new_ftags(); } | ftags copy { $$ = $1; if ($$->copy) { yyerror(parse_script, "duplicate copy tag"); YYERROR; } else { $$->copy = $2; } } | ftags FLAGS stringlist { if (!parse_script->support.imap4flags) { yyerror(parse_script, "imap4flags MUST be enabled with \"require\""); YYERROR; } $$ = $1; if ($$->flags != NULL) { yyerror(parse_script, "duplicate flags tag"); YYERROR; } else { verify_flaglist($3); if(!$3->count) { strarray_add($3, ""); } $$->flags = $3; } } ; rtags: /* empty */ { $$ = 0; } | rtags copy { $$ = $1; if ($$) { yyerror(parse_script, "duplicate copy tag"); YYERROR; } else { $$ = $2; } } ; testlist: '(' tests ')' { $$ = $2; } ; tests: test { $$ = new_testlist($1, NULL); } | test ',' tests { $$ = new_testlist($1, $3); } ; %% void yyerror(sieve_script_t *parse_script, const char *msg) { parse_script->err++; if (parse_script->interp.err) { parse_script->interp.err(sievelineno, msg, parse_script->interp.interp_context, parse_script->script_context); } } static char *check_reqs(sieve_script_t *parse_script, strarray_t *sa) { char *s; struct buf errs = BUF_INITIALIZER; char *res; while ((s = strarray_shift(sa))) { if (!script_require(parse_script, s)) { if (!errs.len) buf_printf(&errs, "Unsupported feature(s) in \"require\": \"%s\"", s); else buf_printf(&errs, ", \"%s\"", s); } free(s); } strarray_free(sa); res = buf_release(&errs); if (!res[0]) { free(res); return NULL; } return res; } static test_t *build_address(int t, struct aetags *ae, strarray_t *sl, strarray_t *pl) { test_t *ret = new_test(t); /* can be either ADDRESS or ENVELOPE */ assert((t == ADDRESS) || (t == ENVELOPE)); if (ret) { ret->u.ae.index = ae->index; ret->u.ae.comptag = ae->comptag; ret->u.ae.relation=ae->relation; ret->u.ae.comparator=xstrdup(ae->comparator); ret->u.ae.sl = sl; ret->u.ae.pl = pl; ret->u.ae.addrpart = ae->addrtag; free_aetags(ae); } return ret; } static test_t *build_header(int t, struct htags *h, strarray_t *sl, strarray_t *pl) { test_t *ret = new_test(t); /* can be HEADER or HASFLAG */ assert((t == HEADER) || (t == HASFLAG)); if (ret) { ret->u.h.index = h->index; ret->u.h.comptag = h->comptag; ret->u.h.relation=h->relation; ret->u.h.comparator=xstrdup(h->comparator); ret->u.h.sl = sl; ret->u.h.pl = pl; free_htags(h); } return ret; } static test_t *build_hasflag(int t, struct htags *h, strarray_t *pl) { return build_header(t,h,NULL,pl); } static test_t *build_body(int t, struct btags *b, strarray_t *pl) { test_t *ret = new_test(t); /* can be BODY */ assert(t == BODY); if (ret) { ret->u.b.comptag = b->comptag; ret->u.b.relation = b->relation; ret->u.b.comparator = xstrdup(b->comparator); ret->u.b.transform = b->transform; ret->u.b.offset = b->offset; ret->u.b.content_types = b->content_types; b->content_types = NULL; ret->u.b.pl = pl; free_btags(b); } return ret; } static commandlist_t *build_vacation(int t, struct vtags *v, char *reason) { commandlist_t *ret = new_command(t); assert(t == VACATION); if (ret) { ret->u.v.subject = v->subject; v->subject = NULL; ret->u.v.from = v->from; v->from = NULL; ret->u.v.handle = v->handle; v->handle = NULL; ret->u.v.seconds = v->seconds; ret->u.v.mime = v->mime; ret->u.v.addresses = v->addresses; v->addresses = NULL; free_vtags(v); ret->u.v.message = reason; } return ret; } static commandlist_t *build_notify(int t, struct ntags *n) { commandlist_t *ret = new_command(t); assert(t == NOTIFY); if (ret) { ret->u.n.method = n->method; n->method = NULL; ret->u.n.id = n->id; n->id = NULL; ret->u.n.options = n->options; n->options = NULL; ret->u.n.priority = n->priority; ret->u.n.message = n->message; n->message = NULL; free_ntags(n); } return ret; } static commandlist_t *build_denotify(int t, struct dtags *d) { commandlist_t *ret = new_command(t); assert(t == DENOTIFY); if (ret) { ret->u.d.comptag = d->comptag; ret->u.d.relation=d->relation; ret->u.d.pattern = d->pattern; d->pattern = NULL; ret->u.d.priority = d->priority; free_dtags(d); } return ret; } static commandlist_t *build_keep(int t, struct ftags *f) { commandlist_t *ret = new_command(t); assert(t == KEEP); if (ret) { ret->u.k.copy = f->copy; ret->u.k.flags = f->flags; f->flags = NULL; free_ftags(f); } return ret; } static commandlist_t *build_fileinto(int t, struct ftags *f, char *folder) { commandlist_t *ret = new_command(t); assert(t == FILEINTO); if (ret) { ret->u.f.copy = f->copy; ret->u.f.flags = f->flags; f->flags = NULL; if (config_getswitch(IMAPOPT_SIEVE_UTF8FILEINTO)) { ret->u.f.folder = xmalloc(5 * strlen(folder) + 1); UTF8_to_mUTF7(ret->u.f.folder, folder); free(folder); } else { ret->u.f.folder = folder; } free_ftags(f); } return ret; } static commandlist_t *build_redirect(int t, int copy, char *address) { commandlist_t *ret = new_command(t); assert(t == REDIRECT); if (ret) { ret->u.r.copy = copy; ret->u.r.address = address; } return ret; } static commandlist_t *build_include(int t, struct itags *i, char* script) { commandlist_t *ret = new_command(t); assert(t == INCLUDE); if (i->location == -1) i->location = PERSONAL; if (i->once == -1) i->once = 0; if (i->optional == -1) i->optional = 0; if (ret) { ret->u.inc.location = i->location; ret->u.inc.once = i->once; ret->u.inc.optional = i->optional; ret->u.inc.script = script; free(i); } return ret; } static test_t *build_date(int t, struct dttags *dt, char *hn, strarray_t *kl) { test_t *ret = new_test(t); assert(t == DATE || t == CURRENTDATE); if (ret) { ret->u.dt.index = dt->index; ret->u.dt.zone = (dt->zone ? xstrdup(dt->zone) : NULL); ret->u.dt.comparator = xstrdup(dt->comparator); ret->u.dt.zonetag = dt->zonetag; ret->u.dt.comptag = dt->comptag; ret->u.dt.relation = dt->relation; ret->u.dt.date_part = dt->date_part; ret->u.dt.header_name = (hn ? xstrdup(hn) : NULL); ret->u.dt.kl = kl; free_dttags(dt); } return ret; } static struct aetags *new_aetags(void) { struct aetags *r = (struct aetags *) xmalloc(sizeof(struct aetags)); r->index = 0; r->addrtag = r->comptag = r->relation=-1; r->comparator=NULL; return r; } static struct aetags *canon_aetags(struct aetags *ae) { if (ae->addrtag == -1) { ae->addrtag = ALL; } if (ae->comparator == NULL) { ae->comparator = xstrdup("i;ascii-casemap"); } if (ae->comptag == -1) { ae->comptag = IS; } return ae; } static void free_aetags(struct aetags *ae) { free(ae->comparator); free(ae); } static struct htags *new_htags(void) { struct htags *r = (struct htags *) xmalloc(sizeof(struct htags)); r->index = 0; r->comptag = r->relation= -1; r->comparator = NULL; return r; } static struct htags *canon_htags(struct htags *h) { if (h->comparator == NULL) { h->comparator = xstrdup("i;ascii-casemap"); } if (h->comptag == -1) { h->comptag = IS; } return h; } static void free_htags(struct htags *h) { free(h->comparator); free(h); } static struct btags *new_btags(void) { struct btags *r = (struct btags *) xmalloc(sizeof(struct btags)); r->transform = r->offset = r->comptag = r->relation = -1; r->content_types = NULL; r->comparator = NULL; return r; } static struct btags *canon_btags(struct btags *b) { if (b->transform == -1) { b->transform = TEXT; } if (b->content_types == NULL) { b->content_types = strarray_new(); if (b->transform == RAW) { strarray_append(b->content_types, ""); } else { strarray_append(b->content_types, "text"); } } if (b->offset == -1) { b->offset = 0; } if (b->comparator == NULL) { b->comparator = xstrdup("i;ascii-casemap"); } if (b->comptag == -1) { b->comptag = IS; } return b; } static void free_btags(struct btags *b) { if (b->content_types) { strarray_free(b->content_types); } free(b->comparator); free(b); } static struct vtags *new_vtags(void) { struct vtags *r = (struct vtags *) xmalloc(sizeof(struct vtags)); r->seconds = -1; r->addresses = NULL; r->subject = NULL; r->from = NULL; r->handle = NULL; r->mime = -1; return r; } static struct vtags *canon_vtags(sieve_script_t *parse_script, struct vtags *v) { assert(parse_script->interp.vacation != NULL); if (v->seconds == -1) { v->seconds = 7 * DAY2SEC; } if (v->seconds < parse_script->interp.vacation->min_response) { v->seconds = parse_script->interp.vacation->min_response; } if (v->seconds > parse_script->interp.vacation->max_response) { v->seconds = parse_script->interp.vacation->max_response; } if (v->mime == -1) { v->mime = 0; } return v; } static void free_vtags(struct vtags *v) { if (v->addresses) { strarray_free(v->addresses); } if (v->subject) { free(v->subject); } if (v->from) { free(v->from); } if (v->handle) { free(v->handle); } free(v); } static struct itags *new_itags() { struct itags *r = (struct itags *) xmalloc(sizeof(struct itags)); r->once = -1; r->location = -1; r->optional = -1; return r; } static struct dttags *new_dttags(void) { struct dttags *dt = (struct dttags *) xmalloc(sizeof(struct dttags)); dt->comptag = -1; dt->index = 0; dt->zonetag = -1; dt->relation = -1; dt->comparator = NULL; dt->zone = NULL; dt->date_part = -1; return dt; } static struct dttags *canon_dttags(struct dttags *dt) { char zone[6]; int gmoffset; int hours; int minutes; struct tm tm; time_t t; if (dt->comparator == NULL) { dt->comparator = xstrdup("i;ascii-casemap"); } if (dt->index == 0) { dt->index = 1; } if (dt->zonetag == -1) { t = time(NULL); localtime_r(&t, &tm); gmoffset = gmtoff_of(&tm, t) / 60; hours = abs(gmoffset) / 60; minutes = abs(gmoffset) % 60; snprintf(zone, 6, "%c%02d%02d", (gmoffset >= 0 ? '+' : '-'), hours, minutes); dt->zone = xstrdup(zone); dt->zonetag = ZONE; } if (dt->comptag == -1) { dt->comptag = IS; } return dt; } static void free_dttags(struct dttags *dt) { free(dt->comparator); free(dt->zone); free(dt); } static struct ntags *new_ntags(void) { struct ntags *r = (struct ntags *) xmalloc(sizeof(struct ntags)); r->method = NULL; r->id = NULL; r->options = NULL; r->priority = -1; r->message = NULL; return r; } static struct ntags *canon_ntags(struct ntags *n) { if (n->priority == -1) { n->priority = NORMAL; } if (n->message == NULL) { n->message = xstrdup("$from$: $subject$"); } if (n->method == NULL) { n->method = xstrdup("default"); } return n; } static struct dtags *canon_dtags(struct dtags *d) { if (d->priority == -1) { d->priority = ANY; } if (d->comptag == -1) { d->comptag = ANY; } return d; } static void free_ntags(struct ntags *n) { if (n->method) { free(n->method); } if (n->id) { free(n->id); } if (n->options) { strarray_free(n->options); } if (n->message) { free(n->message); } free(n); } static struct dtags *new_dtags(void) { struct dtags *r = (struct dtags *) xmalloc(sizeof(struct dtags)); r->comptag = r->priority= r->relation = -1; r->pattern = NULL; return r; } static void free_dtags(struct dtags *d) { if (d->pattern) free(d->pattern); free(d); } static struct ftags *new_ftags(void) { struct ftags *f = (struct ftags *) xmalloc(sizeof(struct ftags)); f->copy = 0; f->flags = NULL; return f; } static struct ftags *canon_ftags(struct ftags *f) { return f; } static void free_ftags(struct ftags *f) { if (f->flags) { strarray_free(f->flags); } free(f); } static int verify_stringlist(sieve_script_t *parse_script, strarray_t *sa, int (*verify)(sieve_script_t*, char *)) { int i; for (i = 0 ; i < sa->count ; i++) if (!verify(parse_script, sa->data[i])) return 0; return 1; } static int verify_address(sieve_script_t *parse_script, char *s) { parse_script->addrerr[0] = '\0'; /* paranoia */ YY_BUFFER_STATE buffer = addr_scan_string(s); if (addrparse(parse_script)) { snprintf(parse_script->sieveerr, ERR_BUF_SIZE, "address '%s': %s", s, parse_script->addrerr); yyerror(parse_script, parse_script->sieveerr); addr_delete_buffer(buffer); return 0; } addr_delete_buffer(buffer); return 1; } static int verify_mailbox(sieve_script_t *parse_script, char *s) { if (!verify_utf8(parse_script, s)) return 0; /* xxx if not a mailbox, call yyerror */ return 1; } static int verify_header(sieve_script_t *parse_script, char *hdr) { char *h = hdr; while (*h) { /* field-name = 1*ftext ftext = %d33-57 / %d59-126 ; Any character except ; controls, SP, and ; ":". */ if (!((*h >= 33 && *h <= 57) || (*h >= 59 && *h <= 126))) { snprintf(parse_script->sieveerr, ERR_BUF_SIZE, "header '%s': not a valid header", hdr); yyerror(parse_script, parse_script->sieveerr); return 0; } h++; } return 1; } static int verify_addrheader(sieve_script_t *parse_script, char *hdr) { const char **h, *hdrs[] = { "from", "sender", "reply-to", /* RFC2822 originator fields */ "to", "cc", "bcc", /* RFC2822 destination fields */ "resent-from", "resent-sender", /* RFC2822 resent fields */ "resent-to", "resent-cc", "resent-bcc", "return-path", /* RFC2822 trace fields */ "disposition-notification-to", /* RFC2298 MDN request fields */ "delivered-to", /* non-standard (loop detection) */ "approved", /* RFC1036 moderator/control fields */ NULL }; if (!config_getswitch(IMAPOPT_RFC3028_STRICT)) return verify_header(parse_script, hdr); for (lcase(hdr), h = hdrs; *h; h++) { if (!strcmp(*h, hdr)) return 1; } snprintf(parse_script->sieveerr, ERR_BUF_SIZE, "header '%s': not a valid header for an address test", hdr); yyerror(parse_script, parse_script->sieveerr); return 0; } static int verify_envelope(sieve_script_t *parse_script, char *env) { lcase(env); if (!config_getswitch(IMAPOPT_RFC3028_STRICT) || !strcmp(env, "from") || !strcmp(env, "to") || !strcmp(env, "auth")) { return 1; } snprintf(parse_script->sieveerr, ERR_BUF_SIZE, "env-part '%s': not a valid part for an envelope test", env); yyerror(parse_script, parse_script->sieveerr); return 0; } static int verify_relat(sieve_script_t *parse_script, char *r) {/* this really should have been a token to begin with.*/ lcase(r); if (!strcmp(r, "gt")) {return GT;} else if (!strcmp(r, "ge")) {return GE;} else if (!strcmp(r, "lt")) {return LT;} else if (!strcmp(r, "le")) {return LE;} else if (!strcmp(r, "ne")) {return NE;} else if (!strcmp(r, "eq")) {return EQ;} else{ snprintf(parse_script->sieveerr, ERR_BUF_SIZE, "flag '%s': not a valid relational operation", r); yyerror(parse_script, parse_script->sieveerr); return -1; } } static int verify_zone(sieve_script_t *parse_script, char *tz) { int valid = 0; unsigned hours; unsigned minutes; char sign; if (sscanf(tz, "%c%02u%02u", &sign, &hours, &minutes) != 3) { valid |= -1; } // test sign switch (sign) { case '+': case '-': break; default: valid |= -1; break; } // test minutes if (minutes > 59) { valid |= -1; } if (valid != 0) { snprintf(parse_script->sieveerr, ERR_BUF_SIZE, "flag '%s': not a valid timezone offset", tz); yyerror(parse_script, parse_script->sieveerr); } return valid; } static int verify_date_part(sieve_script_t *parse_script, char *dp) { lcase(dp); if (!strcmp(dp, "year")) { return YEAR; } else if (!strcmp(dp, "month")) { return MONTH; } else if (!strcmp(dp, "day")) { return DAY; } else if (!strcmp(dp, "date")) { return DATE; } else if (!strcmp(dp, "julian")) { return JULIAN; } else if (!strcmp(dp, "hour")) { return HOUR; } else if (!strcmp(dp, "minute")) { return MINUTE; } else if (!strcmp(dp, "second")) { return SECOND; } else if (!strcmp(dp, "time")) { return TIME; } else if (!strcmp(dp, "iso8601")) { return ISO8601; } else if (!strcmp(dp, "std11")) { return STD11; } else if (!strcmp(dp, "zone")) { return ZONE; } else if (!strcmp(dp, "weekday")) { return WEEKDAY; } else { snprintf(parse_script->sieveerr, ERR_BUF_SIZE, "flag '%s': not a valid relational operation", dp); yyerror(parse_script, parse_script->sieveerr); } return -1; } #ifdef ENABLE_REGEX static int verify_regex(sieve_script_t *parse_script, char *s, int cflags) { int ret; regex_t *reg = (regex_t *) xmalloc(sizeof(regex_t)); #ifdef HAVE_PCREPOSIX_H /* support UTF8 comparisons */ cflags |= REG_UTF8; #endif if ((ret = regcomp(reg, s, cflags)) != 0) { (void) regerror(ret, reg, parse_script->sieveerr, ERR_BUF_SIZE); yyerror(parse_script, parse_script->sieveerr); free(reg); return 0; } free(reg); return 1; } static int verify_regexs(sieve_script_t *parse_script, const strarray_t *sa, char *comp) { int i; int cflags = REG_EXTENDED | REG_NOSUB; if (!strcmp(comp, "i;ascii-casemap")) { cflags |= REG_ICASE; } for (i = 0 ; i < sa->count ; i++) { if ((verify_regex(parse_script, sa->data[i], cflags)) == 0) return 0; } return 1; } #endif /* * Valid UTF-8 check (from RFC 2640 Annex B.1) * * The following routine checks if a byte sequence is valid UTF-8. This * is done by checking for the proper tagging of the first and following * bytes to make sure they conform to the UTF-8 format. It then checks * to assure that the data part of the UTF-8 sequence conforms to the * proper range allowed by the encoding. Note: This routine will not * detect characters that have not been assigned and therefore do not * exist. */ static int verify_utf8(sieve_script_t *parse_script, char *s) { const char *buf = s; const char *endbuf = s + strlen(s); unsigned char byte2mask = 0x00, c; int trailing = 0; /* trailing (continuation) bytes to follow */ while (buf != endbuf) { c = *buf++; if (trailing) { if ((c & 0xC0) == 0x80) { /* Does trailing byte follow UTF-8 format? */ if (byte2mask) { /* Need to check 2nd byte for proper range? */ if (c & byte2mask) /* Are appropriate bits set? */ byte2mask = 0x00; else break; } trailing--; } else break; } else { if ((c & 0x80) == 0x00) /* valid 1 byte UTF-8 */ continue; else if ((c & 0xE0) == 0xC0) /* valid 2 byte UTF-8 */ if (c & 0x1E) { /* Is UTF-8 byte in proper range? */ trailing = 1; } else break; else if ((c & 0xF0) == 0xE0) { /* valid 3 byte UTF-8 */ if (!(c & 0x0F)) { /* Is UTF-8 byte in proper range? */ byte2mask = 0x20; /* If not, set mask to check next byte */ } trailing = 2; } else if ((c & 0xF8) == 0xF0) { /* valid 4 byte UTF-8 */ if (!(c & 0x07)) { /* Is UTF-8 byte in proper range? */ byte2mask = 0x30; /* If not, set mask to check next byte */ } trailing = 3; } else if ((c & 0xFC) == 0xF8) { /* valid 5 byte UTF-8 */ if (!(c & 0x03)) { /* Is UTF-8 byte in proper range? */ byte2mask = 0x38; /* If not, set mask to check next byte */ } trailing = 4; } else if ((c & 0xFE) == 0xFC) { /* valid 6 byte UTF-8 */ if (!(c & 0x01)) { /* Is UTF-8 byte in proper range? */ byte2mask = 0x3C; /* If not, set mask to check next byte */ } trailing = 5; } else break; } } if ((buf != endbuf) || trailing) { snprintf(parse_script->sieveerr, ERR_BUF_SIZE, "string '%s': not valid utf8", s); yyerror(parse_script, parse_script->sieveerr); return 0; } return 1; } cyrus-imapd-2.5.10/sieve/tree.h0000644000175000017500000001134013001236020013162 00000000000000/* tree.h -- abstract syntax tree * Larry Greenfield * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #ifndef TREE_H #define TREE_H #include "comparator.h" #include "strarray.h" /* abstract syntax tree for sieve */ typedef struct Commandlist commandlist_t; typedef struct Test test_t; typedef struct Testlist testlist_t; typedef struct Tag tag_t; typedef struct Taglist taglist_t; struct Tag { int type; char *arg; }; struct Taglist { tag_t *t; taglist_t *next; }; struct Test { int type; union { testlist_t *tl; /* anyof, allof */ strarray_t *sl; /* exists */ struct { /* it's a header or hasflag test */ int index; int comptag; char * comparator; int relation; void *comprock; strarray_t *sl; strarray_t *pl; } h; struct { /* it's an address or envelope test */ int index; int comptag; char * comparator; int relation; void *comprock; strarray_t *sl; strarray_t *pl; int addrpart; } ae; struct { /* it's a body test */ int comptag; int relation; char * comparator; void *comprock; int transform; int offset; strarray_t *content_types; strarray_t *pl; } b; test_t *t; /* not */ struct { /* size */ int t; /* tag */ int n; /* param */ } sz; struct { /* it's a date test */ int index; int zonetag; char *zone; int comptag; int relation; char *comparator; int date_part; char *header_name; strarray_t *kl; } dt; } u; }; struct Testlist { test_t *t; testlist_t *next; }; struct Commandlist { int type; union { char *str; strarray_t *sl; /* the parameters */ struct { /* it's an if statement */ test_t *t; commandlist_t *do_then; commandlist_t *do_else; } i; struct { /* it's an include action */ int location; int once; int optional; char *script; } inc; struct { /* it's a keep action */ int copy; strarray_t *flags; } k; struct { /* it's a fileinto action */ char *folder; int copy; strarray_t *flags; } f; struct { /* it's a redirect action */ char *address; int copy; } r; struct { /* it's a vacation action */ char *subject; int seconds; strarray_t *addresses; char *message; char *from; char *handle; int mime; } v; struct { /* it's a notify action */ char *method; char *id; strarray_t *options; int priority; char *message; } n; struct { /* it's a denotify action */ int comptag; int relation; void *comprock; void *pattern; int priority; } d; } u; struct Commandlist *next; }; tag_t *new_tag(int type, char *s); taglist_t *new_taglist(tag_t *t, taglist_t *n); test_t *new_test(int type); testlist_t *new_testlist(test_t *t, testlist_t *n); commandlist_t *new_command(int type); commandlist_t *new_if(test_t *t, commandlist_t *y, commandlist_t *n); void free_test(test_t *t); void free_tree(commandlist_t *cl); #endif cyrus-imapd-2.5.10/sieve/varlist.c0000644000175000017500000000260613001236020013707 00000000000000/* * varlist.c * * Created on: Sep 29, 2014 * Author: James Cassell */ #include "varlist.h" #include "xmalloc.h" EXPORTED variable_list_t *varlist_new(void) { variable_list_t *vl; vl = xzmalloc(sizeof(variable_list_t)); vl->var = strarray_new(); return vl; } EXPORTED variable_list_t *varlist_select(variable_list_t *vl, const char *name) { if (!vl) { return NULL; } if ((!name && !vl->name) || ((name && vl->name) && !strcasecmp(name, vl->name))) { return vl; } return varlist_select(vl->next, name); } EXPORTED variable_list_t *varlist_end(variable_list_t *vl) { if (!vl) { return NULL; } if (!vl->next) { return vl; } return varlist_end(vl->next); } EXPORTED variable_list_t *varlist_extend(variable_list_t *vl) { if (!vl) { return NULL; } return (varlist_end(vl))->next = varlist_new(); } EXPORTED void varlist_fini(variable_list_t *vl) { if (!vl) { return; } if (vl->name) { free(vl->name); vl->name = NULL; } if (vl->var) { strarray_fini(vl->var); vl->var = NULL; } varlist_free(vl->next); vl->next = NULL; } EXPORTED void varlist_free(variable_list_t *vl) { variable_list_t *next = NULL; if (!vl) { return; } next = vl->next; if (vl->name) { free(vl->name); } if (vl->var) { strarray_free(vl->var); } free(vl); varlist_free(next); } cyrus-imapd-2.5.10/sieve/addr.h0000644000175000017500000000416713001246643013162 00000000000000/* A Bison parser, made by GNU Bison 3.0.4. */ /* Bison interface for Yacc-like parsers in C Copyright (C) 1984, 1989-1990, 2000-2015 Free Software Foundation, Inc. This program is free software: you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation, either version 3 of the License, or (at your option) any later version. This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with this program. If not, see . */ /* As a special exception, you may create a larger work that contains part or all of the Bison parser skeleton and distribute that work under terms of your choice, so long as that work isn't itself a parser generator using the skeleton or a modified version thereof as a parser skeleton. Alternatively, if you modify or redistribute the parser skeleton itself, you may (at your option) remove this special exception, which will cause the skeleton and the resulting Bison output files to be licensed under the GNU General Public License without this special exception. This special exception was added by the Free Software Foundation in version 2.2 of Bison. */ #ifndef YY_ADDR_SIEVE_ADDR_H_INCLUDED # define YY_ADDR_SIEVE_ADDR_H_INCLUDED /* Debug traces. */ #ifndef YYDEBUG # define YYDEBUG 0 #endif #if YYDEBUG extern int addrdebug; #endif /* Token type. */ #ifndef YYTOKENTYPE # define YYTOKENTYPE enum yytokentype { ATOM = 258, QTEXT = 259, DTEXT = 260 }; #endif /* Tokens. */ #define ATOM 258 #define QTEXT 259 #define DTEXT 260 /* Value type. */ #if ! defined YYSTYPE && ! defined YYSTYPE_IS_DECLARED typedef int YYSTYPE; # define YYSTYPE_IS_TRIVIAL 1 # define YYSTYPE_IS_DECLARED 1 #endif int addrparse (sieve_script_t *parse_script); #endif /* !YY_ADDR_SIEVE_ADDR_H_INCLUDED */ cyrus-imapd-2.5.10/sieve/addr.c0000644000175000017500000013456213001246643013160 00000000000000/* A Bison parser, made by GNU Bison 3.0.4. */ /* Bison implementation for Yacc-like parsers in C Copyright (C) 1984, 1989-1990, 2000-2015 Free Software Foundation, Inc. This program is free software: you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation, either version 3 of the License, or (at your option) any later version. This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with this program. If not, see . */ /* As a special exception, you may create a larger work that contains part or all of the Bison parser skeleton and distribute that work under terms of your choice, so long as that work isn't itself a parser generator using the skeleton or a modified version thereof as a parser skeleton. Alternatively, if you modify or redistribute the parser skeleton itself, you may (at your option) remove this special exception, which will cause the skeleton and the resulting Bison output files to be licensed under the GNU General Public License without this special exception. This special exception was added by the Free Software Foundation in version 2.2 of Bison. */ /* C LALR(1) parser skeleton written by Richard Stallman, by simplifying the original so-called "semantic" parser. */ /* All symbols defined below should begin with yy or YY, to avoid infringing on user name space. This should be done even for local variables, as they might otherwise be expanded by user macros. There are some unavoidable exceptions within include files to define necessary library symbols; they are noted "INFRINGES ON USER NAME SPACE" below. */ /* Identify Bison output. */ #define YYBISON 1 /* Bison version. */ #define YYBISON_VERSION "3.0.4" /* Skeleton name. */ #define YYSKELETON_NAME "yacc.c" /* Pure parsers. */ #define YYPURE 1 /* Push parsers. */ #define YYPUSH 0 /* Pull parsers. */ #define YYPULL 1 /* Substitute the variable and function names. */ #define yyparse addrparse #define yylex addrlex #define yyerror addrerror #define yydebug addrdebug #define yynerrs addrnerrs /* Copy the first part of user declarations. */ #line 1 "sieve/addr.y" /* yacc.c:339 */ /* * addr.y -- RFC 822 address parser * Ken Murchison * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #ifdef HAVE_CONFIG_H #include #endif #include #include #include "sieve/script.h" #include "sieve/addr.h" #include "xstrlcpy.h" #define ADDRERR_SIZE 500 void yyerror(sieve_script_t*, const char *); extern int addrlex(YYSTYPE*, sieve_script_t*); #define YYERROR_VERBOSE /* i want better error messages! */ /* byacc default is 500, bison default is 10000 - go with the larger to support big sieve scripts (see Bug #3461) */ #define YYSTACKSIZE 10000 #line 140 "sieve/addr.c" /* yacc.c:339 */ # ifndef YY_NULLPTR # if defined __cplusplus && 201103L <= __cplusplus # define YY_NULLPTR nullptr # else # define YY_NULLPTR 0 # endif # endif /* Enabling verbose error messages. */ #ifdef YYERROR_VERBOSE # undef YYERROR_VERBOSE # define YYERROR_VERBOSE 1 #else # define YYERROR_VERBOSE 0 #endif /* In a future release of Bison, this section will be replaced by #include "y.tab.h". */ #ifndef YY_ADDR_SIEVE_ADDR_H_INCLUDED # define YY_ADDR_SIEVE_ADDR_H_INCLUDED /* Debug traces. */ #ifndef YYDEBUG # define YYDEBUG 0 #endif #if YYDEBUG extern int addrdebug; #endif /* Token type. */ #ifndef YYTOKENTYPE # define YYTOKENTYPE enum yytokentype { ATOM = 258, QTEXT = 259, DTEXT = 260 }; #endif /* Tokens. */ #define ATOM 258 #define QTEXT 259 #define DTEXT 260 /* Value type. */ #if ! defined YYSTYPE && ! defined YYSTYPE_IS_DECLARED typedef int YYSTYPE; # define YYSTYPE_IS_TRIVIAL 1 # define YYSTYPE_IS_DECLARED 1 #endif int addrparse (sieve_script_t *parse_script); #endif /* !YY_ADDR_SIEVE_ADDR_H_INCLUDED */ /* Copy the second part of user declarations. */ #line 200 "sieve/addr.c" /* yacc.c:358 */ #ifdef short # undef short #endif #ifdef YYTYPE_UINT8 typedef YYTYPE_UINT8 yytype_uint8; #else typedef unsigned char yytype_uint8; #endif #ifdef YYTYPE_INT8 typedef YYTYPE_INT8 yytype_int8; #else typedef signed char yytype_int8; #endif #ifdef YYTYPE_UINT16 typedef YYTYPE_UINT16 yytype_uint16; #else typedef unsigned short int yytype_uint16; #endif #ifdef YYTYPE_INT16 typedef YYTYPE_INT16 yytype_int16; #else typedef short int yytype_int16; #endif #ifndef YYSIZE_T # ifdef __SIZE_TYPE__ # define YYSIZE_T __SIZE_TYPE__ # elif defined size_t # define YYSIZE_T size_t # elif ! defined YYSIZE_T # include /* INFRINGES ON USER NAME SPACE */ # define YYSIZE_T size_t # else # define YYSIZE_T unsigned int # endif #endif #define YYSIZE_MAXIMUM ((YYSIZE_T) -1) #ifndef YY_ # if defined YYENABLE_NLS && YYENABLE_NLS # if ENABLE_NLS # include /* INFRINGES ON USER NAME SPACE */ # define YY_(Msgid) dgettext ("bison-runtime", Msgid) # endif # endif # ifndef YY_ # define YY_(Msgid) Msgid # endif #endif #ifndef YY_ATTRIBUTE # if (defined __GNUC__ \ && (2 < __GNUC__ || (__GNUC__ == 2 && 96 <= __GNUC_MINOR__))) \ || defined __SUNPRO_C && 0x5110 <= __SUNPRO_C # define YY_ATTRIBUTE(Spec) __attribute__(Spec) # else # define YY_ATTRIBUTE(Spec) /* empty */ # endif #endif #ifndef YY_ATTRIBUTE_PURE # define YY_ATTRIBUTE_PURE YY_ATTRIBUTE ((__pure__)) #endif #ifndef YY_ATTRIBUTE_UNUSED # define YY_ATTRIBUTE_UNUSED YY_ATTRIBUTE ((__unused__)) #endif #if !defined _Noreturn \ && (!defined __STDC_VERSION__ || __STDC_VERSION__ < 201112) # if defined _MSC_VER && 1200 <= _MSC_VER # define _Noreturn __declspec (noreturn) # else # define _Noreturn YY_ATTRIBUTE ((__noreturn__)) # endif #endif /* Suppress unused-variable warnings by "using" E. */ #if ! defined lint || defined __GNUC__ # define YYUSE(E) ((void) (E)) #else # define YYUSE(E) /* empty */ #endif #if defined __GNUC__ && 407 <= __GNUC__ * 100 + __GNUC_MINOR__ /* Suppress an incorrect diagnostic about yylval being uninitialized. */ # define YY_IGNORE_MAYBE_UNINITIALIZED_BEGIN \ _Pragma ("GCC diagnostic push") \ _Pragma ("GCC diagnostic ignored \"-Wuninitialized\"")\ _Pragma ("GCC diagnostic ignored \"-Wmaybe-uninitialized\"") # define YY_IGNORE_MAYBE_UNINITIALIZED_END \ _Pragma ("GCC diagnostic pop") #else # define YY_INITIAL_VALUE(Value) Value #endif #ifndef YY_IGNORE_MAYBE_UNINITIALIZED_BEGIN # define YY_IGNORE_MAYBE_UNINITIALIZED_BEGIN # define YY_IGNORE_MAYBE_UNINITIALIZED_END #endif #ifndef YY_INITIAL_VALUE # define YY_INITIAL_VALUE(Value) /* Nothing. */ #endif #if ! defined yyoverflow || YYERROR_VERBOSE /* The parser invokes alloca or malloc; define the necessary symbols. */ # ifdef YYSTACK_USE_ALLOCA # if YYSTACK_USE_ALLOCA # ifdef __GNUC__ # define YYSTACK_ALLOC __builtin_alloca # elif defined __BUILTIN_VA_ARG_INCR # include /* INFRINGES ON USER NAME SPACE */ # elif defined _AIX # define YYSTACK_ALLOC __alloca # elif defined _MSC_VER # include /* INFRINGES ON USER NAME SPACE */ # define alloca _alloca # else # define YYSTACK_ALLOC alloca # if ! defined _ALLOCA_H && ! defined EXIT_SUCCESS # include /* INFRINGES ON USER NAME SPACE */ /* Use EXIT_SUCCESS as a witness for stdlib.h. */ # ifndef EXIT_SUCCESS # define EXIT_SUCCESS 0 # endif # endif # endif # endif # endif # ifdef YYSTACK_ALLOC /* Pacify GCC's 'empty if-body' warning. */ # define YYSTACK_FREE(Ptr) do { /* empty */; } while (0) # ifndef YYSTACK_ALLOC_MAXIMUM /* The OS might guarantee only one guard page at the bottom of the stack, and a page size can be as small as 4096 bytes. So we cannot safely invoke alloca (N) if N exceeds 4096. Use a slightly smaller number to allow for a few compiler-allocated temporary stack slots. */ # define YYSTACK_ALLOC_MAXIMUM 4032 /* reasonable circa 2006 */ # endif # else # define YYSTACK_ALLOC YYMALLOC # define YYSTACK_FREE YYFREE # ifndef YYSTACK_ALLOC_MAXIMUM # define YYSTACK_ALLOC_MAXIMUM YYSIZE_MAXIMUM # endif # if (defined __cplusplus && ! defined EXIT_SUCCESS \ && ! ((defined YYMALLOC || defined malloc) \ && (defined YYFREE || defined free))) # include /* INFRINGES ON USER NAME SPACE */ # ifndef EXIT_SUCCESS # define EXIT_SUCCESS 0 # endif # endif # ifndef YYMALLOC # define YYMALLOC malloc # if ! defined malloc && ! defined EXIT_SUCCESS void *malloc (YYSIZE_T); /* INFRINGES ON USER NAME SPACE */ # endif # endif # ifndef YYFREE # define YYFREE free # if ! defined free && ! defined EXIT_SUCCESS void free (void *); /* INFRINGES ON USER NAME SPACE */ # endif # endif # endif #endif /* ! defined yyoverflow || YYERROR_VERBOSE */ #if (! defined yyoverflow \ && (! defined __cplusplus \ || (defined YYSTYPE_IS_TRIVIAL && YYSTYPE_IS_TRIVIAL))) /* A type that is properly aligned for any stack member. */ union yyalloc { yytype_int16 yyss_alloc; YYSTYPE yyvs_alloc; }; /* The size of the maximum gap between one aligned stack and the next. */ # define YYSTACK_GAP_MAXIMUM (sizeof (union yyalloc) - 1) /* The size of an array large to enough to hold all stacks, each with N elements. */ # define YYSTACK_BYTES(N) \ ((N) * (sizeof (yytype_int16) + sizeof (YYSTYPE)) \ + YYSTACK_GAP_MAXIMUM) # define YYCOPY_NEEDED 1 /* Relocate STACK from its old location to the new one. The local variables YYSIZE and YYSTACKSIZE give the old and new number of elements in the stack, and YYPTR gives the new location of the stack. Advance YYPTR to a properly aligned location for the next stack. */ # define YYSTACK_RELOCATE(Stack_alloc, Stack) \ do \ { \ YYSIZE_T yynewbytes; \ YYCOPY (&yyptr->Stack_alloc, Stack, yysize); \ Stack = &yyptr->Stack_alloc; \ yynewbytes = yystacksize * sizeof (*Stack) + YYSTACK_GAP_MAXIMUM; \ yyptr += yynewbytes / sizeof (*yyptr); \ } \ while (0) #endif #if defined YYCOPY_NEEDED && YYCOPY_NEEDED /* Copy COUNT objects from SRC to DST. The source and destination do not overlap. */ # ifndef YYCOPY # if defined __GNUC__ && 1 < __GNUC__ # define YYCOPY(Dst, Src, Count) \ __builtin_memcpy (Dst, Src, (Count) * sizeof (*(Src))) # else # define YYCOPY(Dst, Src, Count) \ do \ { \ YYSIZE_T yyi; \ for (yyi = 0; yyi < (Count); yyi++) \ (Dst)[yyi] = (Src)[yyi]; \ } \ while (0) # endif # endif #endif /* !YYCOPY_NEEDED */ /* YYFINAL -- State number of the termination state. */ #define YYFINAL 10 /* YYLAST -- Last index in YYTABLE. */ #define YYLAST 26 /* YYNTOKENS -- Number of terminals. */ #define YYNTOKENS 13 /* YYNNTS -- Number of nonterminals. */ #define YYNNTS 11 /* YYNRULES -- Number of rules. */ #define YYNRULES 17 /* YYNSTATES -- Number of states. */ #define YYNSTATES 31 /* YYTRANSLATE[YYX] -- Symbol number corresponding to YYX as returned by yylex, with out-of-bounds checking. */ #define YYUNDEFTOK 2 #define YYMAXUTOK 260 #define YYTRANSLATE(YYX) \ ((unsigned int) (YYX) <= YYMAXUTOK ? yytranslate[YYX] : YYUNDEFTOK) /* YYTRANSLATE[TOKEN-NUM] -- Symbol number corresponding to TOKEN-NUM as returned by yylex, without out-of-bounds checking. */ static const yytype_uint8 yytranslate[] = { 0, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 12, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 9, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 6, 2, 7, 2, 8, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 10, 2, 11, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 1, 2, 3, 4, 5 }; #if YYDEBUG /* YYRLINE[YYN] -- Source line where rule number YYN was defined. */ static const yytype_uint8 yyrline[] = { 0, 76, 76, 77, 80, 83, 84, 87, 88, 91, 92, 95, 98, 101, 102, 105, 106, 109 }; #endif #if YYDEBUG || YYERROR_VERBOSE || 0 /* YYTNAME[SYMBOL-NUM] -- String name of the symbol SYMBOL-NUM. First, the terminals, then, starting at YYNTOKENS, nonterminals. */ static const char *const yytname[] = { "$end", "error", "$undefined", "ATOM", "QTEXT", "DTEXT", "'<'", "'>'", "'@'", "'.'", "'['", "']'", "'\"'", "$accept", "sieve_address", "addrspec", "localpart", "domain", "subdomain", "domainref", "domainlit", "phrase", "word", "qstring", YY_NULLPTR }; #endif # ifdef YYPRINT /* YYTOKNUM[NUM] -- (External) token number corresponding to the (internal) symbol number NUM (which must be that of a token). */ static const yytype_uint16 yytoknum[] = { 0, 256, 257, 258, 259, 260, 60, 62, 64, 46, 91, 93, 34 }; # endif #define YYPACT_NINF -7 #define yypact_value_is_default(Yystate) \ (!!((Yystate) == (-7))) #define YYTABLE_NINF -14 #define yytable_value_is_error(Yytable_value) \ 0 /* YYPACT[STATE-NUM] -- Index in YYTABLE of the portion describing STATE-NUM. */ static const yytype_int8 yypact[] = { -1, -7, 1, 3, -7, 6, 10, -2, -7, -6, -7, 5, -1, -1, -7, -1, -7, -7, 4, -7, 8, -7, -7, 11, 12, -7, 9, 5, -7, -7, -7 }; /* YYDEFACT[STATE-NUM] -- Default reduction number in state STATE-NUM. Performed when YYTABLE does not specify something else to do. Zero means the default is an error. */ static const yytype_uint8 yydefact[] = { 0, 15, 0, 0, 2, 0, 0, 5, 16, 0, 1, 0, 0, 0, 14, 13, 17, 11, 0, 4, 7, 9, 10, 0, 5, 6, 0, 0, 3, 12, 8 }; /* YYPGOTO[NTERM-NUM]. */ static const yytype_int8 yypgoto[] = { -7, -7, 7, 13, -5, -7, -7, -7, 23, 0, -7 }; /* YYDEFGOTO[NTERM-NUM]. */ static const yytype_int8 yydefgoto[] = { -1, 3, 4, 5, 19, 20, 21, 22, 14, 15, 8 }; /* YYTABLE[YYPACT[STATE-NUM]] -- What to do in state STATE-NUM. If positive, shift that token. If negative, reduce the rule whose number is the opposite. If YYTABLE_NINF, syntax error. */ static const yytype_int8 yytable[] = { 7, 1, 1, 10, -13, 9, 16, 13, 17, 26, 2, 2, 24, 24, 11, 18, 12, 27, 28, 23, 29, 13, 30, 6, 0, 0, 25 }; static const yytype_int8 yycheck[] = { 0, 3, 3, 0, 6, 4, 12, 9, 3, 5, 12, 12, 12, 13, 8, 10, 6, 9, 7, 12, 11, 9, 27, 0, -1, -1, 13 }; /* YYSTOS[STATE-NUM] -- The (internal number of the) accessing symbol of state STATE-NUM. */ static const yytype_uint8 yystos[] = { 0, 3, 12, 14, 15, 16, 21, 22, 23, 4, 0, 8, 6, 9, 21, 22, 12, 3, 10, 17, 18, 19, 20, 15, 22, 16, 5, 9, 7, 11, 17 }; /* YYR1[YYN] -- Symbol number of symbol that rule YYN derives. */ static const yytype_uint8 yyr1[] = { 0, 13, 14, 14, 15, 16, 16, 17, 17, 18, 18, 19, 20, 21, 21, 22, 22, 23 }; /* YYR2[YYN] -- Number of symbols on the right hand side of rule YYN. */ static const yytype_uint8 yyr2[] = { 0, 2, 1, 4, 3, 1, 3, 1, 3, 1, 1, 1, 3, 1, 2, 1, 1, 3 }; #define yyerrok (yyerrstatus = 0) #define yyclearin (yychar = YYEMPTY) #define YYEMPTY (-2) #define YYEOF 0 #define YYACCEPT goto yyacceptlab #define YYABORT goto yyabortlab #define YYERROR goto yyerrorlab #define YYRECOVERING() (!!yyerrstatus) #define YYBACKUP(Token, Value) \ do \ if (yychar == YYEMPTY) \ { \ yychar = (Token); \ yylval = (Value); \ YYPOPSTACK (yylen); \ yystate = *yyssp; \ goto yybackup; \ } \ else \ { \ yyerror (parse_script, YY_("syntax error: cannot back up")); \ YYERROR; \ } \ while (0) /* Error token number */ #define YYTERROR 1 #define YYERRCODE 256 /* Enable debugging if requested. */ #if YYDEBUG # ifndef YYFPRINTF # include /* INFRINGES ON USER NAME SPACE */ # define YYFPRINTF fprintf # endif # define YYDPRINTF(Args) \ do { \ if (yydebug) \ YYFPRINTF Args; \ } while (0) /* This macro is provided for backward compatibility. */ #ifndef YY_LOCATION_PRINT # define YY_LOCATION_PRINT(File, Loc) ((void) 0) #endif # define YY_SYMBOL_PRINT(Title, Type, Value, Location) \ do { \ if (yydebug) \ { \ YYFPRINTF (stderr, "%s ", Title); \ yy_symbol_print (stderr, \ Type, Value, parse_script); \ YYFPRINTF (stderr, "\n"); \ } \ } while (0) /*----------------------------------------. | Print this symbol's value on YYOUTPUT. | `----------------------------------------*/ static void yy_symbol_value_print (FILE *yyoutput, int yytype, YYSTYPE const * const yyvaluep, sieve_script_t *parse_script) { FILE *yyo = yyoutput; YYUSE (yyo); YYUSE (parse_script); if (!yyvaluep) return; # ifdef YYPRINT if (yytype < YYNTOKENS) YYPRINT (yyoutput, yytoknum[yytype], *yyvaluep); # endif YYUSE (yytype); } /*--------------------------------. | Print this symbol on YYOUTPUT. | `--------------------------------*/ static void yy_symbol_print (FILE *yyoutput, int yytype, YYSTYPE const * const yyvaluep, sieve_script_t *parse_script) { YYFPRINTF (yyoutput, "%s %s (", yytype < YYNTOKENS ? "token" : "nterm", yytname[yytype]); yy_symbol_value_print (yyoutput, yytype, yyvaluep, parse_script); YYFPRINTF (yyoutput, ")"); } /*------------------------------------------------------------------. | yy_stack_print -- Print the state stack from its BOTTOM up to its | | TOP (included). | `------------------------------------------------------------------*/ static void yy_stack_print (yytype_int16 *yybottom, yytype_int16 *yytop) { YYFPRINTF (stderr, "Stack now"); for (; yybottom <= yytop; yybottom++) { int yybot = *yybottom; YYFPRINTF (stderr, " %d", yybot); } YYFPRINTF (stderr, "\n"); } # define YY_STACK_PRINT(Bottom, Top) \ do { \ if (yydebug) \ yy_stack_print ((Bottom), (Top)); \ } while (0) /*------------------------------------------------. | Report that the YYRULE is going to be reduced. | `------------------------------------------------*/ static void yy_reduce_print (yytype_int16 *yyssp, YYSTYPE *yyvsp, int yyrule, sieve_script_t *parse_script) { unsigned long int yylno = yyrline[yyrule]; int yynrhs = yyr2[yyrule]; int yyi; YYFPRINTF (stderr, "Reducing stack by rule %d (line %lu):\n", yyrule - 1, yylno); /* The symbols being reduced. */ for (yyi = 0; yyi < yynrhs; yyi++) { YYFPRINTF (stderr, " $%d = ", yyi + 1); yy_symbol_print (stderr, yystos[yyssp[yyi + 1 - yynrhs]], &(yyvsp[(yyi + 1) - (yynrhs)]) , parse_script); YYFPRINTF (stderr, "\n"); } } # define YY_REDUCE_PRINT(Rule) \ do { \ if (yydebug) \ yy_reduce_print (yyssp, yyvsp, Rule, parse_script); \ } while (0) /* Nonzero means print parse trace. It is left uninitialized so that multiple parsers can coexist. */ int yydebug; #else /* !YYDEBUG */ # define YYDPRINTF(Args) # define YY_SYMBOL_PRINT(Title, Type, Value, Location) # define YY_STACK_PRINT(Bottom, Top) # define YY_REDUCE_PRINT(Rule) #endif /* !YYDEBUG */ /* YYINITDEPTH -- initial size of the parser's stacks. */ #ifndef YYINITDEPTH # define YYINITDEPTH 200 #endif /* YYMAXDEPTH -- maximum size the stacks can grow to (effective only if the built-in stack extension method is used). Do not make this value too large; the results are undefined if YYSTACK_ALLOC_MAXIMUM < YYSTACK_BYTES (YYMAXDEPTH) evaluated with infinite-precision integer arithmetic. */ #ifndef YYMAXDEPTH # define YYMAXDEPTH 10000 #endif #if YYERROR_VERBOSE # ifndef yystrlen # if defined __GLIBC__ && defined _STRING_H # define yystrlen strlen # else /* Return the length of YYSTR. */ static YYSIZE_T yystrlen (const char *yystr) { YYSIZE_T yylen; for (yylen = 0; yystr[yylen]; yylen++) continue; return yylen; } # endif # endif # ifndef yystpcpy # if defined __GLIBC__ && defined _STRING_H && defined _GNU_SOURCE # define yystpcpy stpcpy # else /* Copy YYSRC to YYDEST, returning the address of the terminating '\0' in YYDEST. */ static char * yystpcpy (char *yydest, const char *yysrc) { char *yyd = yydest; const char *yys = yysrc; while ((*yyd++ = *yys++) != '\0') continue; return yyd - 1; } # endif # endif # ifndef yytnamerr /* Copy to YYRES the contents of YYSTR after stripping away unnecessary quotes and backslashes, so that it's suitable for yyerror. The heuristic is that double-quoting is unnecessary unless the string contains an apostrophe, a comma, or backslash (other than backslash-backslash). YYSTR is taken from yytname. If YYRES is null, do not copy; instead, return the length of what the result would have been. */ static YYSIZE_T yytnamerr (char *yyres, const char *yystr) { if (*yystr == '"') { YYSIZE_T yyn = 0; char const *yyp = yystr; for (;;) switch (*++yyp) { case '\'': case ',': goto do_not_strip_quotes; case '\\': if (*++yyp != '\\') goto do_not_strip_quotes; /* Fall through. */ default: if (yyres) yyres[yyn] = *yyp; yyn++; break; case '"': if (yyres) yyres[yyn] = '\0'; return yyn; } do_not_strip_quotes: ; } if (! yyres) return yystrlen (yystr); return yystpcpy (yyres, yystr) - yyres; } # endif /* Copy into *YYMSG, which is of size *YYMSG_ALLOC, an error message about the unexpected token YYTOKEN for the state stack whose top is YYSSP. Return 0 if *YYMSG was successfully written. Return 1 if *YYMSG is not large enough to hold the message. In that case, also set *YYMSG_ALLOC to the required number of bytes. Return 2 if the required number of bytes is too large to store. */ static int yysyntax_error (YYSIZE_T *yymsg_alloc, char **yymsg, yytype_int16 *yyssp, int yytoken) { YYSIZE_T yysize0 = yytnamerr (YY_NULLPTR, yytname[yytoken]); YYSIZE_T yysize = yysize0; enum { YYERROR_VERBOSE_ARGS_MAXIMUM = 5 }; /* Internationalized format string. */ const char *yyformat = YY_NULLPTR; /* Arguments of yyformat. */ char const *yyarg[YYERROR_VERBOSE_ARGS_MAXIMUM]; /* Number of reported tokens (one for the "unexpected", one per "expected"). */ int yycount = 0; /* There are many possibilities here to consider: - If this state is a consistent state with a default action, then the only way this function was invoked is if the default action is an error action. In that case, don't check for expected tokens because there are none. - The only way there can be no lookahead present (in yychar) is if this state is a consistent state with a default action. Thus, detecting the absence of a lookahead is sufficient to determine that there is no unexpected or expected token to report. In that case, just report a simple "syntax error". - Don't assume there isn't a lookahead just because this state is a consistent state with a default action. There might have been a previous inconsistent state, consistent state with a non-default action, or user semantic action that manipulated yychar. - Of course, the expected token list depends on states to have correct lookahead information, and it depends on the parser not to perform extra reductions after fetching a lookahead from the scanner and before detecting a syntax error. Thus, state merging (from LALR or IELR) and default reductions corrupt the expected token list. However, the list is correct for canonical LR with one exception: it will still contain any token that will not be accepted due to an error action in a later state. */ if (yytoken != YYEMPTY) { int yyn = yypact[*yyssp]; yyarg[yycount++] = yytname[yytoken]; if (!yypact_value_is_default (yyn)) { /* Start YYX at -YYN if negative to avoid negative indexes in YYCHECK. In other words, skip the first -YYN actions for this state because they are default actions. */ int yyxbegin = yyn < 0 ? -yyn : 0; /* Stay within bounds of both yycheck and yytname. */ int yychecklim = YYLAST - yyn + 1; int yyxend = yychecklim < YYNTOKENS ? yychecklim : YYNTOKENS; int yyx; for (yyx = yyxbegin; yyx < yyxend; ++yyx) if (yycheck[yyx + yyn] == yyx && yyx != YYTERROR && !yytable_value_is_error (yytable[yyx + yyn])) { if (yycount == YYERROR_VERBOSE_ARGS_MAXIMUM) { yycount = 1; yysize = yysize0; break; } yyarg[yycount++] = yytname[yyx]; { YYSIZE_T yysize1 = yysize + yytnamerr (YY_NULLPTR, yytname[yyx]); if (! (yysize <= yysize1 && yysize1 <= YYSTACK_ALLOC_MAXIMUM)) return 2; yysize = yysize1; } } } } switch (yycount) { # define YYCASE_(N, S) \ case N: \ yyformat = S; \ break YYCASE_(0, YY_("syntax error")); YYCASE_(1, YY_("syntax error, unexpected %s")); YYCASE_(2, YY_("syntax error, unexpected %s, expecting %s")); YYCASE_(3, YY_("syntax error, unexpected %s, expecting %s or %s")); YYCASE_(4, YY_("syntax error, unexpected %s, expecting %s or %s or %s")); YYCASE_(5, YY_("syntax error, unexpected %s, expecting %s or %s or %s or %s")); # undef YYCASE_ } { YYSIZE_T yysize1 = yysize + yystrlen (yyformat); if (! (yysize <= yysize1 && yysize1 <= YYSTACK_ALLOC_MAXIMUM)) return 2; yysize = yysize1; } if (*yymsg_alloc < yysize) { *yymsg_alloc = 2 * yysize; if (! (yysize <= *yymsg_alloc && *yymsg_alloc <= YYSTACK_ALLOC_MAXIMUM)) *yymsg_alloc = YYSTACK_ALLOC_MAXIMUM; return 1; } /* Avoid sprintf, as that infringes on the user's name space. Don't have undefined behavior even if the translation produced a string with the wrong number of "%s"s. */ { char *yyp = *yymsg; int yyi = 0; while ((*yyp = *yyformat) != '\0') if (*yyp == '%' && yyformat[1] == 's' && yyi < yycount) { yyp += yytnamerr (yyp, yyarg[yyi++]); yyformat += 2; } else { yyp++; yyformat++; } } return 0; } #endif /* YYERROR_VERBOSE */ /*-----------------------------------------------. | Release the memory associated to this symbol. | `-----------------------------------------------*/ static void yydestruct (const char *yymsg, int yytype, YYSTYPE *yyvaluep, sieve_script_t *parse_script) { YYUSE (yyvaluep); YYUSE (parse_script); if (!yymsg) yymsg = "Deleting"; YY_SYMBOL_PRINT (yymsg, yytype, yyvaluep, yylocationp); YY_IGNORE_MAYBE_UNINITIALIZED_BEGIN YYUSE (yytype); YY_IGNORE_MAYBE_UNINITIALIZED_END } /*----------. | yyparse. | `----------*/ int yyparse (sieve_script_t *parse_script) { /* The lookahead symbol. */ int yychar; /* The semantic value of the lookahead symbol. */ /* Default value used for initialization, for pacifying older GCCs or non-GCC compilers. */ YY_INITIAL_VALUE (static YYSTYPE yyval_default;) YYSTYPE yylval YY_INITIAL_VALUE (= yyval_default); /* Number of syntax errors so far. */ int yynerrs; int yystate; /* Number of tokens to shift before error messages enabled. */ int yyerrstatus; /* The stacks and their tools: 'yyss': related to states. 'yyvs': related to semantic values. Refer to the stacks through separate pointers, to allow yyoverflow to reallocate them elsewhere. */ /* The state stack. */ yytype_int16 yyssa[YYINITDEPTH]; yytype_int16 *yyss; yytype_int16 *yyssp; /* The semantic value stack. */ YYSTYPE yyvsa[YYINITDEPTH]; YYSTYPE *yyvs; YYSTYPE *yyvsp; YYSIZE_T yystacksize; int yyn; int yyresult; /* Lookahead token as an internal (translated) token number. */ int yytoken = 0; /* The variables used to return semantic value and location from the action routines. */ YYSTYPE yyval; #if YYERROR_VERBOSE /* Buffer for error messages, and its allocated size. */ char yymsgbuf[128]; char *yymsg = yymsgbuf; YYSIZE_T yymsg_alloc = sizeof yymsgbuf; #endif #define YYPOPSTACK(N) (yyvsp -= (N), yyssp -= (N)) /* The number of symbols on the RHS of the reduced rule. Keep to zero when no symbol should be popped. */ int yylen = 0; yyssp = yyss = yyssa; yyvsp = yyvs = yyvsa; yystacksize = YYINITDEPTH; YYDPRINTF ((stderr, "Starting parse\n")); yystate = 0; yyerrstatus = 0; yynerrs = 0; yychar = YYEMPTY; /* Cause a token to be read. */ goto yysetstate; /*------------------------------------------------------------. | yynewstate -- Push a new state, which is found in yystate. | `------------------------------------------------------------*/ yynewstate: /* In all cases, when you get here, the value and location stacks have just been pushed. So pushing a state here evens the stacks. */ yyssp++; yysetstate: *yyssp = yystate; if (yyss + yystacksize - 1 <= yyssp) { /* Get the current used size of the three stacks, in elements. */ YYSIZE_T yysize = yyssp - yyss + 1; #ifdef yyoverflow { /* Give user a chance to reallocate the stack. Use copies of these so that the &'s don't force the real ones into memory. */ YYSTYPE *yyvs1 = yyvs; yytype_int16 *yyss1 = yyss; /* Each stack pointer address is followed by the size of the data in use in that stack, in bytes. This used to be a conditional around just the two extra args, but that might be undefined if yyoverflow is a macro. */ yyoverflow (YY_("memory exhausted"), &yyss1, yysize * sizeof (*yyssp), &yyvs1, yysize * sizeof (*yyvsp), &yystacksize); yyss = yyss1; yyvs = yyvs1; } #else /* no yyoverflow */ # ifndef YYSTACK_RELOCATE goto yyexhaustedlab; # else /* Extend the stack our own way. */ if (YYMAXDEPTH <= yystacksize) goto yyexhaustedlab; yystacksize *= 2; if (YYMAXDEPTH < yystacksize) yystacksize = YYMAXDEPTH; { yytype_int16 *yyss1 = yyss; union yyalloc *yyptr = (union yyalloc *) YYSTACK_ALLOC (YYSTACK_BYTES (yystacksize)); if (! yyptr) goto yyexhaustedlab; YYSTACK_RELOCATE (yyss_alloc, yyss); YYSTACK_RELOCATE (yyvs_alloc, yyvs); # undef YYSTACK_RELOCATE if (yyss1 != yyssa) YYSTACK_FREE (yyss1); } # endif #endif /* no yyoverflow */ yyssp = yyss + yysize - 1; yyvsp = yyvs + yysize - 1; YYDPRINTF ((stderr, "Stack size increased to %lu\n", (unsigned long int) yystacksize)); if (yyss + yystacksize - 1 <= yyssp) YYABORT; } YYDPRINTF ((stderr, "Entering state %d\n", yystate)); if (yystate == YYFINAL) YYACCEPT; goto yybackup; /*-----------. | yybackup. | `-----------*/ yybackup: /* Do appropriate processing given the current state. Read a lookahead token if we need one and don't already have one. */ /* First try to decide what to do without reference to lookahead token. */ yyn = yypact[yystate]; if (yypact_value_is_default (yyn)) goto yydefault; /* Not known => get a lookahead token if don't already have one. */ /* YYCHAR is either YYEMPTY or YYEOF or a valid lookahead symbol. */ if (yychar == YYEMPTY) { YYDPRINTF ((stderr, "Reading a token: ")); yychar = yylex (&yylval, parse_script); } if (yychar <= YYEOF) { yychar = yytoken = YYEOF; YYDPRINTF ((stderr, "Now at end of input.\n")); } else { yytoken = YYTRANSLATE (yychar); YY_SYMBOL_PRINT ("Next token is", yytoken, &yylval, &yylloc); } /* If the proper action on seeing token YYTOKEN is to reduce or to detect an error, take that action. */ yyn += yytoken; if (yyn < 0 || YYLAST < yyn || yycheck[yyn] != yytoken) goto yydefault; yyn = yytable[yyn]; if (yyn <= 0) { if (yytable_value_is_error (yyn)) goto yyerrlab; yyn = -yyn; goto yyreduce; } /* Count tokens shifted since error; after three, turn off error status. */ if (yyerrstatus) yyerrstatus--; /* Shift the lookahead token. */ YY_SYMBOL_PRINT ("Shifting", yytoken, &yylval, &yylloc); /* Discard the shifted token. */ yychar = YYEMPTY; yystate = yyn; YY_IGNORE_MAYBE_UNINITIALIZED_BEGIN *++yyvsp = yylval; YY_IGNORE_MAYBE_UNINITIALIZED_END goto yynewstate; /*-----------------------------------------------------------. | yydefault -- do the default action for the current state. | `-----------------------------------------------------------*/ yydefault: yyn = yydefact[yystate]; if (yyn == 0) goto yyerrlab; goto yyreduce; /*-----------------------------. | yyreduce -- Do a reduction. | `-----------------------------*/ yyreduce: /* yyn is the number of a rule to reduce with. */ yylen = yyr2[yyn]; /* If YYLEN is nonzero, implement the default value of the action: '$$ = $1'. Otherwise, the following line sets YYVAL to garbage. This behavior is undocumented and Bison users should not rely upon it. Assigning to YYVAL unconditionally makes the parser a bit smaller, and it avoids a GCC warning that YYVAL may be used uninitialized. */ yyval = yyvsp[1-yylen]; YY_REDUCE_PRINT (yyn); switch (yyn) { #line 1291 "sieve/addr.c" /* yacc.c:1646 */ default: break; } /* User semantic actions sometimes alter yychar, and that requires that yytoken be updated with the new translation. We take the approach of translating immediately before every use of yytoken. One alternative is translating here after every semantic action, but that translation would be missed if the semantic action invokes YYABORT, YYACCEPT, or YYERROR immediately after altering yychar or if it invokes YYBACKUP. In the case of YYABORT or YYACCEPT, an incorrect destructor might then be invoked immediately. In the case of YYERROR or YYBACKUP, subsequent parser actions might lead to an incorrect destructor call or verbose syntax error message before the lookahead is translated. */ YY_SYMBOL_PRINT ("-> $$ =", yyr1[yyn], &yyval, &yyloc); YYPOPSTACK (yylen); yylen = 0; YY_STACK_PRINT (yyss, yyssp); *++yyvsp = yyval; /* Now 'shift' the result of the reduction. Determine what state that goes to, based on the state we popped back to and the rule number reduced by. */ yyn = yyr1[yyn]; yystate = yypgoto[yyn - YYNTOKENS] + *yyssp; if (0 <= yystate && yystate <= YYLAST && yycheck[yystate] == *yyssp) yystate = yytable[yystate]; else yystate = yydefgoto[yyn - YYNTOKENS]; goto yynewstate; /*--------------------------------------. | yyerrlab -- here on detecting error. | `--------------------------------------*/ yyerrlab: /* Make sure we have latest lookahead translation. See comments at user semantic actions for why this is necessary. */ yytoken = yychar == YYEMPTY ? YYEMPTY : YYTRANSLATE (yychar); /* If not already recovering from an error, report this error. */ if (!yyerrstatus) { ++yynerrs; #if ! YYERROR_VERBOSE yyerror (parse_script, YY_("syntax error")); #else # define YYSYNTAX_ERROR yysyntax_error (&yymsg_alloc, &yymsg, \ yyssp, yytoken) { char const *yymsgp = YY_("syntax error"); int yysyntax_error_status; yysyntax_error_status = YYSYNTAX_ERROR; if (yysyntax_error_status == 0) yymsgp = yymsg; else if (yysyntax_error_status == 1) { if (yymsg != yymsgbuf) YYSTACK_FREE (yymsg); yymsg = (char *) YYSTACK_ALLOC (yymsg_alloc); if (!yymsg) { yymsg = yymsgbuf; yymsg_alloc = sizeof yymsgbuf; yysyntax_error_status = 2; } else { yysyntax_error_status = YYSYNTAX_ERROR; yymsgp = yymsg; } } yyerror (parse_script, yymsgp); if (yysyntax_error_status == 2) goto yyexhaustedlab; } # undef YYSYNTAX_ERROR #endif } if (yyerrstatus == 3) { /* If just tried and failed to reuse lookahead token after an error, discard it. */ if (yychar <= YYEOF) { /* Return failure if at end of input. */ if (yychar == YYEOF) YYABORT; } else { yydestruct ("Error: discarding", yytoken, &yylval, parse_script); yychar = YYEMPTY; } } /* Else will try to reuse lookahead token after shifting the error token. */ goto yyerrlab1; /*---------------------------------------------------. | yyerrorlab -- error raised explicitly by YYERROR. | `---------------------------------------------------*/ yyerrorlab: /* Pacify compilers like GCC when the user code never invokes YYERROR and the label yyerrorlab therefore never appears in user code. */ if (/*CONSTCOND*/ 0) goto yyerrorlab; /* Do not reclaim the symbols of the rule whose action triggered this YYERROR. */ YYPOPSTACK (yylen); yylen = 0; YY_STACK_PRINT (yyss, yyssp); yystate = *yyssp; goto yyerrlab1; /*-------------------------------------------------------------. | yyerrlab1 -- common code for both syntax error and YYERROR. | `-------------------------------------------------------------*/ yyerrlab1: yyerrstatus = 3; /* Each real token shifted decrements this. */ for (;;) { yyn = yypact[yystate]; if (!yypact_value_is_default (yyn)) { yyn += YYTERROR; if (0 <= yyn && yyn <= YYLAST && yycheck[yyn] == YYTERROR) { yyn = yytable[yyn]; if (0 < yyn) break; } } /* Pop the current state because it cannot handle the error token. */ if (yyssp == yyss) YYABORT; yydestruct ("Error: popping", yystos[yystate], yyvsp, parse_script); YYPOPSTACK (1); yystate = *yyssp; YY_STACK_PRINT (yyss, yyssp); } YY_IGNORE_MAYBE_UNINITIALIZED_BEGIN *++yyvsp = yylval; YY_IGNORE_MAYBE_UNINITIALIZED_END /* Shift the error token. */ YY_SYMBOL_PRINT ("Shifting", yystos[yyn], yyvsp, yylsp); yystate = yyn; goto yynewstate; /*-------------------------------------. | yyacceptlab -- YYACCEPT comes here. | `-------------------------------------*/ yyacceptlab: yyresult = 0; goto yyreturn; /*-----------------------------------. | yyabortlab -- YYABORT comes here. | `-----------------------------------*/ yyabortlab: yyresult = 1; goto yyreturn; #if !defined yyoverflow || YYERROR_VERBOSE /*-------------------------------------------------. | yyexhaustedlab -- memory exhaustion comes here. | `-------------------------------------------------*/ yyexhaustedlab: yyerror (parse_script, YY_("memory exhausted")); yyresult = 2; /* Fall through. */ #endif yyreturn: if (yychar != YYEMPTY) { /* Make sure we have latest lookahead translation. See comments at user semantic actions for why this is necessary. */ yytoken = YYTRANSLATE (yychar); yydestruct ("Cleanup: discarding lookahead", yytoken, &yylval, parse_script); } /* Do not reclaim the symbols of the rule whose action triggered this YYABORT or YYACCEPT. */ YYPOPSTACK (yylen); YY_STACK_PRINT (yyss, yyssp); while (yyssp != yyss) { yydestruct ("Cleanup: popping", yystos[*yyssp], yyvsp, parse_script); YYPOPSTACK (1); } #ifndef yyoverflow if (yyss != yyssa) YYSTACK_FREE (yyss); #endif #if YYERROR_VERBOSE if (yymsg != yymsgbuf) YYSTACK_FREE (yymsg); #endif return yyresult; } #line 112 "sieve/addr.y" /* yacc.c:1906 */ /* copy address error message into buffer provided by sieve parser */ void yyerror(sieve_script_t *parse_script, const char *s) { strlcpy(parse_script->addrerr, s, ADDRERR_SIZE); } cyrus-imapd-2.5.10/sieve/bytecode.h0000644000175000017500000001762613001236020014036 00000000000000/* bytecode.h -- bytecode definition * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #ifndef SIEVE_BYTECODE_H #define SIEVE_BYTECODE_H /* for debugging*/ #define DUMPCODE 0 #define VERBOSE 0 /*for finding correctly aligned bytes on strings*/ /* bump to the next multiple of 4 bytes */ #define ROUNDUP(num) (((num) + 3) & 0xFFFFFFFC) /* yes, lots of these are superfluous, it's for clarity */ typedef union { int op; /* OPTYPE */ int value; int jump; int listlen; /* store strings (need 2 consecutive bytecodes) */ int len; char *str; } bytecode_t; struct bytecode_info { bytecode_t *data;/* pointer to almost-flat bytecode */ size_t scriptend; /* used by emit code to know final length of bytecode */ size_t reallen; /* allocated length of 'data' */ }; /* For sanity during input on 64-bit platforms. * str should only be accessed as (char *)&str, but given the use of * unwrap_string, this should be OK */ typedef union { int op; /* OPTYPE */ int value; int jump; int listlen; /* store strings (need 2 consecutive bytecodes) */ int len; int str; } bytecode_input_t; /* version 0x01 scripts were written in host byte order. * we don't want to use this version number again and cause a mess * this isn't a huge concern, since this is version ntohl(1), or 16777216 * * version 0x02 scripts started using network byte order (recompile) * version 0x03 scripts implemented short-circuiting of testlists (recompile) * version 0x04 scripts implemented BODY, INCLUDE and COPY extensions * version 0x05 scripts implemented updated VACATION (:from and :handle) * version 0x06 scripts implemented updated VACATION (:seconds) * version 0x07 scripts implemented updated INCLUDE (:once and :optional) * version 0x08 scripts implemented DATE and INDEX extensions * version 0x09 scripts implemented IMAP4FLAGS extension */ #define BYTECODE_VERSION 0x09 #define BYTECODE_MIN_VERSION 0x03 /* minimum supported version */ #define BYTECODE_MAGIC "CyrSBytecode" #define BYTECODE_MAGIC_LEN 12 /* Should be multiple of 4 */ /* IMPORTANT: To maintain forward compatibility of bytecode, please only add * new instructions to the end of these enums. (The reason these values * are all duplicated here is to avoid silliness if this caveat is forgotten * about in the other tables.) */ enum bytecode { B_STOP, B_KEEP_ORIG, /* legacy keep w/o support for :copy and :flags */ B_DISCARD, B_REJECT, /* require reject */ B_FILEINTO_ORIG, /* legacy fileinto w/o support for :copy */ B_REDIRECT_ORIG, /* legacy redirect w/o support for :copy */ B_IF, B_MARK, /* require imapflags */ B_UNMARK, /* require imapflags */ B_ADDFLAG, /* require imap4flags */ B_SETFLAG, /* require imap4flags */ B_REMOVEFLAG, /* require imap4flags */ B_NOTIFY, /* require notify */ B_DENOTIFY, /* require notify */ B_VACATION_ORIG, /* legacy vacation w/o support for :seconds */ B_NULL, B_JUMP, B_INCLUDE, /* require include */ B_RETURN, /* require include */ B_FILEINTO_COPY, /* legacy fileinto w/o support for :flags */ B_REDIRECT, B_VACATION, /* require vacation */ B_KEEP, B_FILEINTO /* require fileinto */ }; enum bytecode_comps { BC_FALSE, BC_TRUE, BC_NOT, BC_EXISTS, BC_SIZE, BC_ANYOF, BC_ALLOF, BC_ADDRESS_PRE_INDEX, BC_ENVELOPE, /* require envelope */ BC_HEADER_PRE_INDEX, BC_BODY, /* require body */ BC_DATE, /* require date */ BC_CURRENTDATE, /* require date */ BC_ADDRESS, BC_HEADER, BC_HASFLAG /* require imap4flags */ }; /* currently one enum so as to help determine where values are being misused. * we have left placeholders incase we need to add more later to the middle */ enum bytecode_tags { /* Size Tests */ B_OVER, B_UNDER, B_SIZE_PLACEHOLDER_1, B_SIZE_PLACEHOLDER_2, /* Relational Match Types */ B_GT, /* require relational */ B_GE, /* require relational */ B_LT, /* require relational */ B_LE, /* require relational */ B_EQ, /* require relational */ B_NE, /* require relational */ B_RELATIONAL_PLACEHOLDER_1, B_RELATIONAL_PLACEHOLDER_2, /* Priorities */ B_LOW, /* require notify */ B_NORMAL, /* require notify */ B_HIGH, /* require notify */ B_ANY, /* require notify */ B_PRIORITY_PLACEHOLDER_1, B_PRIORITY_PLACEHOLDER_2, B_PRIORITY_PLACEHOLDER_3, B_PRIORITY_PLACEHOLDER_4, /* Address Parts */ B_ALL, B_LOCALPART, B_DOMAIN, B_USER, /* require subaddress */ B_DETAIL, /* require subaddress */ B_ADDRESS_PLACEHOLDER_1, B_ADDRESS_PLACEHOLDER_2, B_ADDRESS_PLACEHOLDER_3, B_ADDRESS_PLACEHOLDER_4, /* Comparators */ B_ASCIICASEMAP, B_OCTET, B_ASCIINUMERIC, /* require comparator-i;ascii-numeric */ B_COMPARATOR_PLACEHOLDER_1, B_COMPARATOR_PLACEHOLDER_2, B_COMPARATOR_PLACEHOLDER_3, B_COMPARATOR_PLACEHOLDER_4, /* Match Types */ B_IS, B_CONTAINS, B_MATCHES, B_REGEX, /* require regex */ B_COUNT, /* require relational */ B_VALUE, /* require relational */ B_MATCH_PLACEHOLDER_1, B_MATCH_PLACEHOLDER_2, B_MATCH_PLACEHOLDER_3, B_MATCH_PLACEHOLDER_4, /* Body Transforms */ B_RAW, /* require body */ B_TEXT, /* require body */ B_CONTENT, /* require body */ B_TRANSFORM_PLACEHOLDER_1, B_TRANSFORM_PLACEHOLDER_2, B_TRANSFORM_PLACEHOLDER_3, B_TRANSFORM_PLACEHOLDER_4, B_TRANSFORM_PLACEHOLDER_5, /* Script locations */ B_PERSONAL, /* require include */ B_GLOBAL, /* require include */ B_LOCATION_PLACEHOLDER_1, B_LOCATION_PLACEHOLDER_2, B_LOCATION_PLACEHOLDER_3, B_LOCATION_PLACEHOLDER_4, /* Zones */ B_TIMEZONE, B_ORIGINALZONE, B_ZONE_PLACEHOLDER_1, B_ZONE_PLACEHOLDER_2, /* Date Parts */ B_YEAR, B_MONTH, B_DAY, B_DATE, B_JULIAN, B_HOUR, B_MINUTE, B_SECOND, B_TIME, B_ISO8601, B_STD11, B_ZONE, B_WEEKDAY, B_DATEPART_PLACEHOLDER_1, B_DATEPART_PLACEHOLDER_2, B_DATEPART_PLACEHOLDER_3, B_DATEPART_PLACEHOLDER_4 }; #endif cyrus-imapd-2.5.10/sieve/flags.h0000644000175000017500000000031712772415051013342 00000000000000/* * flags.h * * Created on: Oct 6, 2014 * Author: James Cassell */ #ifndef FLAGS_H_ #define FLAGS_H_ #include "strarray.h" EXPORTED int verify_flaglist(strarray_t *sl); #endif /* FLAGS_H_ */ cyrus-imapd-2.5.10/sieve/interp.c0000644000175000017500000001760113001236020013525 00000000000000/* interp.c -- sieve script interpretor builder * Larry Greenfield * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #ifdef HAVE_CONFIG_H #include #endif #include #include #include "xmalloc.h" #include "xstrlcat.h" #include "sieve_interface.h" #include "interp.h" #include "libconfig.h" #include "times.h" #define EXT_LEN 4096 /* build a sieve interpretor */ EXPORTED sieve_interp_t *sieve_interp_alloc(void *interp_context) { sieve_interp_t *i; static int initonce; if (!initonce) { initialize_siev_error_table(); initonce = 1; } i = (sieve_interp_t *) xmalloc(sizeof(sieve_interp_t)); i->redirect = i->discard = i->reject = i->fileinto = i->keep = NULL; i->getsize = NULL; i->getheader = NULL; i->getenvelope = NULL; i->getbody = NULL; i->getinclude = NULL; i->vacation = NULL; i->notify = NULL; i->markflags = NULL; i->interp_context = interp_context; i->err = NULL; i->lastitem = NULL; i->extensions[0] = '\0'; i->time = time(NULL); return i; } EXPORTED const char *sieve_listextensions(sieve_interp_t *i) { if (i->extensions[0] == '\0') { unsigned long config_sieve_extensions = config_getbitfield(IMAPOPT_SIEVE_EXTENSIONS); /* add comparators */ strlcat(i->extensions, "comparator-i;ascii-numeric", EXT_LEN); /* add actions */ if (i->fileinto && (config_sieve_extensions & IMAP_ENUM_SIEVE_EXTENSIONS_FILEINTO)) strlcat(i->extensions, " fileinto", EXT_LEN); if (i->reject && (config_sieve_extensions & IMAP_ENUM_SIEVE_EXTENSIONS_REJECT)) strlcat(i->extensions, " reject", EXT_LEN); if (i->vacation && (config_sieve_extensions & IMAP_ENUM_SIEVE_EXTENSIONS_VACATION_SECONDS)) strlcat(i->extensions, " vacation vacation-seconds", EXT_LEN); else if (i->vacation && (config_sieve_extensions & IMAP_ENUM_SIEVE_EXTENSIONS_VACATION)) strlcat(i->extensions, " vacation", EXT_LEN); if (i->markflags && (config_sieve_extensions & IMAP_ENUM_SIEVE_EXTENSIONS_IMAPFLAGS)) strlcat(i->extensions, " imapflags", EXT_LEN); if (i->notify && (config_sieve_extensions & IMAP_ENUM_SIEVE_EXTENSIONS_NOTIFY)) strlcat(i->extensions, " notify", EXT_LEN); if (i->getinclude && (config_sieve_extensions & IMAP_ENUM_SIEVE_EXTENSIONS_INCLUDE)) strlcat(i->extensions, " include", EXT_LEN); /* add tests */ if (i->getenvelope && (config_sieve_extensions & IMAP_ENUM_SIEVE_EXTENSIONS_ENVELOPE)) strlcat(i->extensions, " envelope", EXT_LEN); if (i->getbody && (config_sieve_extensions & IMAP_ENUM_SIEVE_EXTENSIONS_BODY)) strlcat(i->extensions, " body", EXT_LEN); if (config_sieve_extensions & IMAP_ENUM_SIEVE_EXTENSIONS_IMAP4FLAGS) strlcat(i->extensions, " imap4flags", EXT_LEN); /* add match-types */ if (config_sieve_extensions & IMAP_ENUM_SIEVE_EXTENSIONS_RELATIONAL) strlcat(i->extensions, " relational", EXT_LEN); #ifdef ENABLE_REGEX if (config_sieve_extensions & IMAP_ENUM_SIEVE_EXTENSIONS_REGEX) strlcat(i->extensions, " regex", EXT_LEN); #endif /* add misc extensions */ if (config_sieve_extensions & IMAP_ENUM_SIEVE_EXTENSIONS_SUBADDRESS) strlcat(i->extensions, " subaddress", EXT_LEN); if (config_sieve_extensions & IMAP_ENUM_SIEVE_EXTENSIONS_COPY) strlcat(i->extensions, " copy", EXT_LEN); if (config_sieve_extensions & IMAP_ENUM_SIEVE_EXTENSIONS_DATE) strlcat(i->extensions, " date", EXT_LEN); } return i->extensions; } EXPORTED int sieve_interp_free(sieve_interp_t **interp) { if (*interp) { free((*interp)->lastitem); free(*interp); *interp = NULL; } return SIEVE_OK; } /* add the callbacks */ EXPORTED void sieve_register_redirect(sieve_interp_t *interp, sieve_callback *f) { interp->redirect = f; } EXPORTED void sieve_register_discard(sieve_interp_t *interp, sieve_callback *f) { interp->discard = f; } EXPORTED void sieve_register_reject(sieve_interp_t *interp, sieve_callback *f) { interp->reject = f; } EXPORTED void sieve_register_fileinto(sieve_interp_t *interp, sieve_callback *f) { interp->fileinto = f; } EXPORTED void sieve_register_keep(sieve_interp_t *interp, sieve_callback *f) { interp->keep = f; } EXPORTED void sieve_register_imapflags(sieve_interp_t *interp, const strarray_t *mark) { static strarray_t default_mark = STRARRAY_INITIALIZER; if (!default_mark.count) strarray_append(&default_mark, "\\flagged"); interp->markflags = (mark && mark->data && mark->count) ? mark : &default_mark; } EXPORTED void sieve_register_notify(sieve_interp_t *interp, sieve_callback *f) { interp->notify = f; } /* add the callbacks for messages. again, undefined if used after sieve_script_parse */ EXPORTED void sieve_register_size(sieve_interp_t *interp, sieve_get_size *f) { interp->getsize = f; } EXPORTED void sieve_register_header(sieve_interp_t *interp, sieve_get_header *f) { interp->getheader = f; } EXPORTED void sieve_register_envelope(sieve_interp_t *interp, sieve_get_envelope *f) { interp->getenvelope = f; } EXPORTED void sieve_register_include(sieve_interp_t *interp, sieve_get_include *f) { interp->getinclude = f; } EXPORTED void sieve_register_body(sieve_interp_t *interp, sieve_get_body *f) { interp->getbody = f; } EXPORTED int sieve_register_vacation(sieve_interp_t *interp, sieve_vacation_t *v) { if (!interp->getenvelope) { return SIEVE_NOT_FINALIZED; /* we need envelope for vacation! */ } if (v->min_response == 0) v->min_response = config_getint(IMAPOPT_SIEVE_VACATION_MIN_RESPONSE); if (v->max_response == 0) v->max_response = config_getint(IMAPOPT_SIEVE_VACATION_MAX_RESPONSE); if (v->min_response < 0 || v->max_response < 7 * DAY2SEC || !v->autorespond || !v->send_response) { return SIEVE_FAIL; } interp->vacation = v; return SIEVE_OK; } EXPORTED void sieve_register_parse_error(sieve_interp_t *interp, sieve_parse_error *f) { interp->err = f; } EXPORTED void sieve_register_execute_error(sieve_interp_t *interp, sieve_execute_error *f) { interp->execute_err = f; } int interp_verify(sieve_interp_t *i) { if (i->redirect && i->keep && i->getsize && i->getheader) { return SIEVE_OK; } else { return SIEVE_NOT_FINALIZED; } } cyrus-imapd-2.5.10/sieve/sieve_interface.h0000644000175000017500000001623113001236020015362 00000000000000/* sieve_interface.h -- interface for deliver * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #ifndef SIEVE_H #define SIEVE_H #include #define SIEVE_VERSION "CMU Sieve 2.4" /* error codes */ #define SIEVE_OK (0) #include "strarray.h" #include "sieve/sieve_err.h" #include "varlist.h" /* external sieve types */ typedef struct sieve_interp sieve_interp_t; typedef struct sieve_script sieve_script_t; typedef struct sieve_execute sieve_execute_t; typedef struct bytecode_info bytecode_info_t; typedef int sieve_callback(void *action_context, void *interp_context, void *script_context, void *message_context, const char **errmsg); typedef int sieve_get_size(void *message_context, int *size); typedef int sieve_get_header(void *message_context, const char *header, const char ***contents); typedef int sieve_get_envelope(void *message_context, const char *field, const char ***contents); typedef int sieve_get_include(void *script_context, const char *script, int isglobal, char *fpath, size_t size); /* MUST keep this struct sync'd with bodypart in imap/message.h */ typedef struct sieve_bodypart { char section[128]; const char *decoded_body; } sieve_bodypart_t; typedef int sieve_get_body(void *message_context, const char **content_types, sieve_bodypart_t ***parts); typedef struct sieve_vacation { int min_response; /* 0 -> defaults to 3 days */ int max_response; /* 0 -> defaults to 90 days */ /* given a hash, say whether we've already responded to it in the last days days. return SIEVE_OK if we SHOULD autorespond (have not already) or SIEVE_DONE if we SHOULD NOT. */ sieve_callback *autorespond; /* mail the response */ sieve_callback *send_response; } sieve_vacation_t; /* sieve_imapflags: NULL -> defaults to \flagged */ typedef struct sieve_redirect_context { const char *addr; } sieve_redirect_context_t; typedef struct sieve_reject_context { const char *msg; } sieve_reject_context_t; typedef struct sieve_fileinto_context { const char *mailbox; strarray_t *imapflags; } sieve_fileinto_context_t; typedef struct sieve_keep_context { strarray_t *imapflags; } sieve_keep_context_t; typedef struct sieve_notify_context { const char *method; const char **options; const char *priority; const char *message; } sieve_notify_context_t; #define SIEVE_HASHLEN 16 typedef struct sieve_autorespond_context { unsigned char hash[SIEVE_HASHLEN]; int seconds; } sieve_autorespond_context_t; typedef struct sieve_send_response_context { char *addr; char *fromaddr; const char *msg; char *subj; int mime; } sieve_send_response_context_t; /* build a sieve interpretor */ sieve_interp_t *sieve_interp_alloc(void *interp_context); int sieve_interp_free(sieve_interp_t **interp); /* add the callbacks for actions. undefined behavior results if these are called after sieve_script_parse is called! */ void sieve_register_redirect(sieve_interp_t *interp, sieve_callback *f); void sieve_register_discard(sieve_interp_t *interp, sieve_callback *f); void sieve_register_reject(sieve_interp_t *interp, sieve_callback *f); void sieve_register_fileinto(sieve_interp_t *interp, sieve_callback *f); void sieve_register_keep(sieve_interp_t *interp, sieve_callback *f); int sieve_register_vacation(sieve_interp_t *interp, sieve_vacation_t *v); void sieve_register_imapflags(sieve_interp_t *interp, const strarray_t *mark); void sieve_register_notify(sieve_interp_t *interp, sieve_callback *f); void sieve_register_include(sieve_interp_t *interp, sieve_get_include *f); /* add the callbacks for messages. again, undefined if used after sieve_script_parse */ void sieve_register_size(sieve_interp_t *interp, sieve_get_size *f); void sieve_register_header(sieve_interp_t *interp, sieve_get_header *f); void sieve_register_envelope(sieve_interp_t *interp, sieve_get_envelope *f); void sieve_register_body(sieve_interp_t *interp, sieve_get_body *f); typedef int sieve_parse_error(int lineno, const char *msg, void *interp_context, void *script_context); void sieve_register_parse_error(sieve_interp_t *interp, sieve_parse_error *f); typedef int sieve_execute_error(const char *msg, void *interp_context, void *script_context, void *message_context); void sieve_register_execute_error(sieve_interp_t *interp, sieve_execute_error *f); /* given an interpretor and a script, produce an executable script */ int sieve_script_parse(sieve_interp_t *interp, FILE *script, void *script_context, sieve_script_t **ret); /* given a path to a bytecode file, load it into the sieve_execute_t */ int sieve_script_load(const char *fpath, sieve_execute_t **ret); /* Unload a sieve_bytecode_t */ int sieve_script_unload(sieve_execute_t **s); /* Free a sieve_script_t */ void sieve_script_free(sieve_script_t **s); /* execute bytecode on a message */ int sieve_execute_bytecode(sieve_execute_t *script, sieve_interp_t *interp, void *script_context, void *message_context); /* Get space separated list of extensions supported by the implementation */ const char *sieve_listextensions(sieve_interp_t *i); /* Create a bytecode structure given a parsed commandlist */ int sieve_generate_bytecode(bytecode_info_t **retval, sieve_script_t *s); /* Emit bytecode to a file descriptor */ int sieve_emit_bytecode(int fd, bytecode_info_t *bc); /* Free a bytecode_info_t */ void sieve_free_bytecode(bytecode_info_t **p); #endif cyrus-imapd-2.5.10/sieve/varlist.h0000644000175000017500000000126712772415051013737 00000000000000/* * varlist.h * * Created on: Sep 29, 2014 * Author: James Cassell */ #ifndef VARLIST_H_ #define VARLIST_H_ #include "strarray.h" typedef struct variable_list { char *name; strarray_t *var; struct variable_list *next; } variable_list_t; #define VARIABLE_LIST_INITIALIZER {NULL, NULL, NULL} EXPORTED variable_list_t *varlist_new(void); EXPORTED void varlist_fini(variable_list_t *vl); EXPORTED void varlist_free(variable_list_t *vl); EXPORTED variable_list_t *varlist_extend(variable_list_t *vl); EXPORTED variable_list_t *varlist_select(variable_list_t *vl, const char *name); EXPORTED variable_list_t *varlist_end(variable_list_t *vl); #endif /* VARLIST_H_ */ cyrus-imapd-2.5.10/sieve/sievec.c0000644000175000017500000001465513001236020013510 00000000000000/* sievec.c -- compile a sieve script to bytecode manually * Rob Siemborski * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #ifdef HAVE_CONFIG_H #include #endif #include "sieve_interface.h" #include #include "libconfig.h" #include "xmalloc.h" #include "script.h" #include "util.h" #include "assert.h" #include #include #include #include #include #include #include #include static int is_script_parsable(FILE *stream, char **errstr, sieve_script_t **ret); #define TIMSIEVE_FAIL -1 #define TIMSIEVE_OK 0 int main(int argc, char **argv) { FILE *instream; char *err = NULL; sieve_script_t *s; bytecode_info_t *bc; int c, fd, usage_error = 0; char *alt_config = NULL; while ((c = getopt(argc, argv, "C:")) != EOF) switch (c) { case 'C': /* alt config file */ alt_config = optarg; break; default: usage_error = 1; break; } if (usage_error || (argc - optind) < 2) { fprintf(stderr, "Syntax: %s [-C ] \n", argv[0]); exit(1); } instream = fopen(argv[optind++],"r"); if(instream == NULL) { fprintf(stderr, "Unable to open %s for reading\n", argv[1]); exit(1); } /* Load configuration file. */ config_read(alt_config, 0); if(is_script_parsable(instream, &err, &s) == TIMSIEVE_FAIL) { if(err) { fprintf(stderr, "Unable to parse script: %s\n", err); } else { fprintf(stderr, "Unable to parse script.\n"); } exit(1); } /* Now, generate the bytecode */ if(sieve_generate_bytecode(&bc, s) == -1) { fprintf(stderr, "bytecode generate failed\n"); exit(1); } /* Now, open the new file */ fd = open(argv[optind], O_CREAT | O_TRUNC | O_WRONLY, 0644); if(fd < 0) { fprintf(stderr, "couldn't open bytecode output file\n"); exit(1); } /* Now, emit the bytecode */ if(sieve_emit_bytecode(fd, bc) == -1) { fprintf(stderr, "bytecode emit failed\n"); exit(1); } close(fd); sieve_free_bytecode(&bc); sieve_script_free(&s); return 0; } /* to make larry's stupid functions happy :) */ static void foo(void) { fatal("stub function called", 0); } static sieve_vacation_t vacation = { 0, /* min response */ 0, /* max response */ (sieve_callback *) &foo, /* autorespond() */ (sieve_callback *) &foo /* send_response() */ }; static int sieve_notify(void *ac __attribute__((unused)), void *interp_context __attribute__((unused)), void *script_context __attribute__((unused)), void *message_context __attribute__((unused)), const char **errmsg __attribute__((unused))) { fatal("stub function called", 0); return SIEVE_FAIL; } static int mysieve_error(int lineno, const char *msg, void *i __attribute__((unused)), void *s) { struct buf *errors = (struct buf *)s; buf_printf(errors, "line %d: %s\r\n", lineno, msg); return SIEVE_OK; } EXPORTED void fatal(const char *s, int code) { fprintf(stderr, "Fatal error: %s (%d)\r\n", s, code); exit(1); } /* end the boilerplate */ /* returns TRUE or FALSE */ static int is_script_parsable(FILE *stream, char **errstr, sieve_script_t **ret) { sieve_interp_t *i; sieve_script_t *s; struct buf errors = BUF_INITIALIZER; int res; i = sieve_interp_alloc(NULL); assert(i != NULL); sieve_register_redirect(i, (sieve_callback *) &foo); sieve_register_discard(i, (sieve_callback *) &foo); sieve_register_reject(i, (sieve_callback *) &foo); sieve_register_fileinto(i, (sieve_callback *) &foo); sieve_register_keep(i, (sieve_callback *) &foo); sieve_register_imapflags(i, NULL); sieve_register_size(i, (sieve_get_size *) &foo); sieve_register_header(i, (sieve_get_header *) &foo); sieve_register_envelope(i, (sieve_get_envelope *) &foo); sieve_register_body(i, (sieve_get_body *) &foo); sieve_register_include(i, (sieve_get_include *) &foo); res = sieve_register_vacation(i, &vacation); if (res != SIEVE_OK) { syslog(LOG_ERR, "sieve_register_vacation() returns %d\n", res); goto done; } sieve_register_notify(i, &sieve_notify); sieve_register_parse_error(i, &mysieve_error); rewind(stream); buf_appendcstr(&errors, "script errors:\r\n"); *errstr = NULL; res = sieve_script_parse(i, stream, &errors, &s); if (res == SIEVE_OK) { if(ret) { *ret = s; } else { sieve_script_free(&s); } } else { sieve_script_free(&s); *errstr = buf_release(&errors); } buf_free(&errors); done: /* free interpreter */ sieve_interp_free(&i); return (res == SIEVE_OK) ? TIMSIEVE_OK : TIMSIEVE_FAIL; } cyrus-imapd-2.5.10/sieve/sieve.h0000644000175000017500000001346213001246644013362 00000000000000/* A Bison parser, made by GNU Bison 3.0.4. */ /* Bison interface for Yacc-like parsers in C Copyright (C) 1984, 1989-1990, 2000-2015 Free Software Foundation, Inc. This program is free software: you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation, either version 3 of the License, or (at your option) any later version. This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with this program. If not, see . */ /* As a special exception, you may create a larger work that contains part or all of the Bison parser skeleton and distribute that work under terms of your choice, so long as that work isn't itself a parser generator using the skeleton or a modified version thereof as a parser skeleton. Alternatively, if you modify or redistribute the parser skeleton itself, you may (at your option) remove this special exception, which will cause the skeleton and the resulting Bison output files to be licensed under the GNU General Public License without this special exception. This special exception was added by the Free Software Foundation in version 2.2 of Bison. */ #ifndef YY_SIEVE_SIEVE_SIEVE_H_INCLUDED # define YY_SIEVE_SIEVE_SIEVE_H_INCLUDED /* Debug traces. */ #ifndef YYDEBUG # define YYDEBUG 0 #endif #if YYDEBUG extern int sievedebug; #endif /* Token type. */ #ifndef YYTOKENTYPE # define YYTOKENTYPE enum yytokentype { NUMBER = 258, STRING = 259, IF = 260, ELSIF = 261, ELSE = 262, REJCT = 263, FILEINTO = 264, REDIRECT = 265, KEEP = 266, STOP = 267, DISCARD = 268, VACATION = 269, REQUIRE = 270, SETFLAG = 271, ADDFLAG = 272, REMOVEFLAG = 273, MARK = 274, UNMARK = 275, HASFLAG = 276, FLAGS = 277, NOTIFY = 278, DENOTIFY = 279, ANYOF = 280, ALLOF = 281, EXISTS = 282, SFALSE = 283, STRUE = 284, HEADER = 285, NOT = 286, SIZE = 287, ADDRESS = 288, ENVELOPE = 289, BODY = 290, COMPARATOR = 291, IS = 292, CONTAINS = 293, MATCHES = 294, REGEX = 295, COUNT = 296, VALUE = 297, OVER = 298, UNDER = 299, GT = 300, GE = 301, LT = 302, LE = 303, EQ = 304, NE = 305, ALL = 306, LOCALPART = 307, DOMAIN = 308, USER = 309, DETAIL = 310, RAW = 311, TEXT = 312, CONTENT = 313, DAYS = 314, ADDRESSES = 315, SUBJECT = 316, FROM = 317, HANDLE = 318, MIME = 319, SECONDS = 320, METHOD = 321, ID = 322, OPTIONS = 323, LOW = 324, NORMAL = 325, HIGH = 326, ANY = 327, MESSAGE = 328, INCLUDE = 329, PERSONAL = 330, GLOBAL = 331, RETURN = 332, OPTIONAL = 333, ONCE = 334, COPY = 335, DATE = 336, CURRENTDATE = 337, INDEX = 338, LAST = 339, ZONE = 340, ORIGINALZONE = 341, YEAR = 342, MONTH = 343, DAY = 344, JULIAN = 345, HOUR = 346, MINUTE = 347, SECOND = 348, TIME = 349, ISO8601 = 350, STD11 = 351, WEEKDAY = 352 }; #endif /* Tokens. */ #define NUMBER 258 #define STRING 259 #define IF 260 #define ELSIF 261 #define ELSE 262 #define REJCT 263 #define FILEINTO 264 #define REDIRECT 265 #define KEEP 266 #define STOP 267 #define DISCARD 268 #define VACATION 269 #define REQUIRE 270 #define SETFLAG 271 #define ADDFLAG 272 #define REMOVEFLAG 273 #define MARK 274 #define UNMARK 275 #define HASFLAG 276 #define FLAGS 277 #define NOTIFY 278 #define DENOTIFY 279 #define ANYOF 280 #define ALLOF 281 #define EXISTS 282 #define SFALSE 283 #define STRUE 284 #define HEADER 285 #define NOT 286 #define SIZE 287 #define ADDRESS 288 #define ENVELOPE 289 #define BODY 290 #define COMPARATOR 291 #define IS 292 #define CONTAINS 293 #define MATCHES 294 #define REGEX 295 #define COUNT 296 #define VALUE 297 #define OVER 298 #define UNDER 299 #define GT 300 #define GE 301 #define LT 302 #define LE 303 #define EQ 304 #define NE 305 #define ALL 306 #define LOCALPART 307 #define DOMAIN 308 #define USER 309 #define DETAIL 310 #define RAW 311 #define TEXT 312 #define CONTENT 313 #define DAYS 314 #define ADDRESSES 315 #define SUBJECT 316 #define FROM 317 #define HANDLE 318 #define MIME 319 #define SECONDS 320 #define METHOD 321 #define ID 322 #define OPTIONS 323 #define LOW 324 #define NORMAL 325 #define HIGH 326 #define ANY 327 #define MESSAGE 328 #define INCLUDE 329 #define PERSONAL 330 #define GLOBAL 331 #define RETURN 332 #define OPTIONAL 333 #define ONCE 334 #define COPY 335 #define DATE 336 #define CURRENTDATE 337 #define INDEX 338 #define LAST 339 #define ZONE 340 #define ORIGINALZONE 341 #define YEAR 342 #define MONTH 343 #define DAY 344 #define JULIAN 345 #define HOUR 346 #define MINUTE 347 #define SECOND 348 #define TIME 349 #define ISO8601 350 #define STD11 351 #define WEEKDAY 352 /* Value type. */ #if ! defined YYSTYPE && ! defined YYSTYPE_IS_DECLARED union YYSTYPE { #line 213 "sieve/sieve.y" /* yacc.c:1909 */ int nval; char *sval; strarray_t *sl; test_t *test; testlist_t *testl; commandlist_t *cl; struct vtags *vtag; struct aetags *aetag; struct htags *htag; struct btags *btag; struct ntags *ntag; struct dtags *dtag; struct itags *itag; struct dttags *dttag; struct ftags *ftag; #line 266 "sieve/sieve.h" /* yacc.c:1909 */ }; typedef union YYSTYPE YYSTYPE; # define YYSTYPE_IS_TRIVIAL 1 # define YYSTYPE_IS_DECLARED 1 #endif int sieveparse (sieve_script_t *parse_script); #endif /* !YY_SIEVE_SIEVE_SIEVE_H_INCLUDED */ cyrus-imapd-2.5.10/sieve/sieve.c0000644000175000017500000040455513001246644013364 00000000000000/* A Bison parser, made by GNU Bison 3.0.4. */ /* Bison implementation for Yacc-like parsers in C Copyright (C) 1984, 1989-1990, 2000-2015 Free Software Foundation, Inc. This program is free software: you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation, either version 3 of the License, or (at your option) any later version. This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with this program. If not, see . */ /* As a special exception, you may create a larger work that contains part or all of the Bison parser skeleton and distribute that work under terms of your choice, so long as that work isn't itself a parser generator using the skeleton or a modified version thereof as a parser skeleton. Alternatively, if you modify or redistribute the parser skeleton itself, you may (at your option) remove this special exception, which will cause the skeleton and the resulting Bison output files to be licensed under the GNU General Public License without this special exception. This special exception was added by the Free Software Foundation in version 2.2 of Bison. */ /* C LALR(1) parser skeleton written by Richard Stallman, by simplifying the original so-called "semantic" parser. */ /* All symbols defined below should begin with yy or YY, to avoid infringing on user name space. This should be done even for local variables, as they might otherwise be expanded by user macros. There are some unavoidable exceptions within include files to define necessary library symbols; they are noted "INFRINGES ON USER NAME SPACE" below. */ /* Identify Bison output. */ #define YYBISON 1 /* Bison version. */ #define YYBISON_VERSION "3.0.4" /* Skeleton name. */ #define YYSKELETON_NAME "yacc.c" /* Pure parsers. */ #define YYPURE 1 /* Push parsers. */ #define YYPUSH 0 /* Pull parsers. */ #define YYPULL 1 /* Substitute the variable and function names. */ #define yyparse sieveparse #define yylex sievelex #define yyerror sieveerror #define yydebug sievedebug #define yynerrs sievenerrs /* Copy the first part of user declarations. */ #line 1 "sieve/sieve.y" /* yacc.c:339 */ /* sieve.y -- sieve parser * Larry Greenfield * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #ifdef HAVE_CONFIG_H #include #endif #include #include #include #include "xmalloc.h" #include "sieve/comparator.h" #include "sieve/interp.h" #include "sieve/script.h" #include "sieve/tree.h" #include "sieve/flags.h" #include "imapurl.h" #include "lib/gmtoff.h" #include "util.h" #include "imparse.h" #include "libconfig.h" #include "times.h" #define ERR_BUF_SIZE 1024 /* definitions */ extern int addrparse(sieve_script_t*); typedef struct yy_buffer_state *YY_BUFFER_STATE; extern YY_BUFFER_STATE addr_scan_string(const char*); extern void addr_delete_buffer(YY_BUFFER_STATE); extern int sievelineno; struct vtags { int seconds; strarray_t *addresses; char *subject; char *from; char *handle; int mime; }; struct htags { int index; char *comparator; int comptag; int relation; }; struct aetags { int index; int addrtag; char *comparator; int comptag; int relation; }; struct btags { int transform; int offset; strarray_t *content_types; char *comparator; int comptag; int relation; }; struct ntags { char *method; char *id; strarray_t *options; int priority; char *message; }; struct dtags { int comptag; int relation; void *pattern; int priority; }; struct itags { int location; int once; int optional; }; struct dttags { int index; int zonetag; char *zone; int comptag; int relation; char *comparator; int date_part; }; static char *check_reqs(sieve_script_t *script, strarray_t *sl); struct ftags { int copy; strarray_t *flags; }; static test_t *build_address(int t, struct aetags *ae, strarray_t *sl, strarray_t *pl); static test_t *build_header(int t, struct htags *h, strarray_t *sl, strarray_t *pl); static test_t *build_body(int t, struct btags *b, strarray_t *pl); static test_t *build_date(int t, struct dttags *dt, char *hn, strarray_t *kl); static test_t *build_hasflag(int t, struct htags *h, strarray_t *pl); static commandlist_t *build_vacation(int t, struct vtags *h, char *s); static commandlist_t *build_notify(int t, struct ntags *n); static commandlist_t *build_denotify(int t, struct dtags *n); static commandlist_t *build_keep(int t, struct ftags *f); static commandlist_t *build_fileinto(int t, struct ftags *f, char *folder); static commandlist_t *build_redirect(int t, int c, char *a); static commandlist_t *build_include(int, struct itags *, char*); static struct aetags *new_aetags(void); static struct aetags *canon_aetags(struct aetags *ae); static void free_aetags(struct aetags *ae); static struct htags *new_htags(void); static struct htags *canon_htags(struct htags *h); static void free_htags(struct htags *h); static struct btags *new_btags(void); static struct btags *canon_btags(struct btags *b); static void free_btags(struct btags *b); static struct vtags *new_vtags(void); static struct vtags *canon_vtags(sieve_script_t *script, struct vtags *v); static void free_vtags(struct vtags *v); static struct ntags *new_ntags(void); static struct ntags *canon_ntags(struct ntags *n); static void free_ntags(struct ntags *n); static struct dtags *new_dtags(void); static struct dtags *canon_dtags(struct dtags *d); static void free_dtags(struct dtags *d); static struct itags *new_itags(void); static struct dttags *new_dttags(void); static struct dttags *canon_dttags(struct dttags *dt); static void free_dttags(struct dttags *b); static struct ftags *new_ftags(void); static struct ftags *canon_ftags(struct ftags *f); static void free_ftags(struct ftags *f); static int verify_stringlist(sieve_script_t*, strarray_t *sl, int (*verify)(sieve_script_t*, char *)); static int verify_mailbox(sieve_script_t*, char *s); static int verify_address(sieve_script_t*, char *s); static int verify_header(sieve_script_t*, char *s); static int verify_addrheader(sieve_script_t*, char *s); static int verify_envelope(sieve_script_t*, char *s); static int verify_relat(sieve_script_t*, char *s); static int verify_zone(sieve_script_t*, char *s); static int verify_date_part(sieve_script_t *parse_script, char *dp); #ifdef ENABLE_REGEX static int verify_regex(sieve_script_t*, char *s, int cflags); static int verify_regexs(sieve_script_t*,const strarray_t *sl, char *comp); #endif static int verify_utf8(sieve_script_t*, char *s); void yyerror(sieve_script_t*, const char *msg); extern int yylex(void*, sieve_script_t*); extern void sieverestart(FILE *f); #define YYERROR_VERBOSE /* i want better error messages! */ /* byacc default is 500, bison default is 10000 - go with the larger to support big sieve scripts (see Bug #3461) */ #define YYSTACKSIZE 10000 #line 284 "sieve/sieve.c" /* yacc.c:339 */ # ifndef YY_NULLPTR # if defined __cplusplus && 201103L <= __cplusplus # define YY_NULLPTR nullptr # else # define YY_NULLPTR 0 # endif # endif /* Enabling verbose error messages. */ #ifdef YYERROR_VERBOSE # undef YYERROR_VERBOSE # define YYERROR_VERBOSE 1 #else # define YYERROR_VERBOSE 0 #endif /* In a future release of Bison, this section will be replaced by #include "y.tab.h". */ #ifndef YY_SIEVE_SIEVE_SIEVE_H_INCLUDED # define YY_SIEVE_SIEVE_SIEVE_H_INCLUDED /* Debug traces. */ #ifndef YYDEBUG # define YYDEBUG 0 #endif #if YYDEBUG extern int sievedebug; #endif /* Token type. */ #ifndef YYTOKENTYPE # define YYTOKENTYPE enum yytokentype { NUMBER = 258, STRING = 259, IF = 260, ELSIF = 261, ELSE = 262, REJCT = 263, FILEINTO = 264, REDIRECT = 265, KEEP = 266, STOP = 267, DISCARD = 268, VACATION = 269, REQUIRE = 270, SETFLAG = 271, ADDFLAG = 272, REMOVEFLAG = 273, MARK = 274, UNMARK = 275, HASFLAG = 276, FLAGS = 277, NOTIFY = 278, DENOTIFY = 279, ANYOF = 280, ALLOF = 281, EXISTS = 282, SFALSE = 283, STRUE = 284, HEADER = 285, NOT = 286, SIZE = 287, ADDRESS = 288, ENVELOPE = 289, BODY = 290, COMPARATOR = 291, IS = 292, CONTAINS = 293, MATCHES = 294, REGEX = 295, COUNT = 296, VALUE = 297, OVER = 298, UNDER = 299, GT = 300, GE = 301, LT = 302, LE = 303, EQ = 304, NE = 305, ALL = 306, LOCALPART = 307, DOMAIN = 308, USER = 309, DETAIL = 310, RAW = 311, TEXT = 312, CONTENT = 313, DAYS = 314, ADDRESSES = 315, SUBJECT = 316, FROM = 317, HANDLE = 318, MIME = 319, SECONDS = 320, METHOD = 321, ID = 322, OPTIONS = 323, LOW = 324, NORMAL = 325, HIGH = 326, ANY = 327, MESSAGE = 328, INCLUDE = 329, PERSONAL = 330, GLOBAL = 331, RETURN = 332, OPTIONAL = 333, ONCE = 334, COPY = 335, DATE = 336, CURRENTDATE = 337, INDEX = 338, LAST = 339, ZONE = 340, ORIGINALZONE = 341, YEAR = 342, MONTH = 343, DAY = 344, JULIAN = 345, HOUR = 346, MINUTE = 347, SECOND = 348, TIME = 349, ISO8601 = 350, STD11 = 351, WEEKDAY = 352 }; #endif /* Tokens. */ #define NUMBER 258 #define STRING 259 #define IF 260 #define ELSIF 261 #define ELSE 262 #define REJCT 263 #define FILEINTO 264 #define REDIRECT 265 #define KEEP 266 #define STOP 267 #define DISCARD 268 #define VACATION 269 #define REQUIRE 270 #define SETFLAG 271 #define ADDFLAG 272 #define REMOVEFLAG 273 #define MARK 274 #define UNMARK 275 #define HASFLAG 276 #define FLAGS 277 #define NOTIFY 278 #define DENOTIFY 279 #define ANYOF 280 #define ALLOF 281 #define EXISTS 282 #define SFALSE 283 #define STRUE 284 #define HEADER 285 #define NOT 286 #define SIZE 287 #define ADDRESS 288 #define ENVELOPE 289 #define BODY 290 #define COMPARATOR 291 #define IS 292 #define CONTAINS 293 #define MATCHES 294 #define REGEX 295 #define COUNT 296 #define VALUE 297 #define OVER 298 #define UNDER 299 #define GT 300 #define GE 301 #define LT 302 #define LE 303 #define EQ 304 #define NE 305 #define ALL 306 #define LOCALPART 307 #define DOMAIN 308 #define USER 309 #define DETAIL 310 #define RAW 311 #define TEXT 312 #define CONTENT 313 #define DAYS 314 #define ADDRESSES 315 #define SUBJECT 316 #define FROM 317 #define HANDLE 318 #define MIME 319 #define SECONDS 320 #define METHOD 321 #define ID 322 #define OPTIONS 323 #define LOW 324 #define NORMAL 325 #define HIGH 326 #define ANY 327 #define MESSAGE 328 #define INCLUDE 329 #define PERSONAL 330 #define GLOBAL 331 #define RETURN 332 #define OPTIONAL 333 #define ONCE 334 #define COPY 335 #define DATE 336 #define CURRENTDATE 337 #define INDEX 338 #define LAST 339 #define ZONE 340 #define ORIGINALZONE 341 #define YEAR 342 #define MONTH 343 #define DAY 344 #define JULIAN 345 #define HOUR 346 #define MINUTE 347 #define SECOND 348 #define TIME 349 #define ISO8601 350 #define STD11 351 #define WEEKDAY 352 /* Value type. */ #if ! defined YYSTYPE && ! defined YYSTYPE_IS_DECLARED union YYSTYPE { #line 213 "sieve/sieve.y" /* yacc.c:355 */ int nval; char *sval; strarray_t *sl; test_t *test; testlist_t *testl; commandlist_t *cl; struct vtags *vtag; struct aetags *aetag; struct htags *htag; struct btags *btag; struct ntags *ntag; struct dtags *dtag; struct itags *itag; struct dttags *dttag; struct ftags *ftag; #line 536 "sieve/sieve.c" /* yacc.c:355 */ }; typedef union YYSTYPE YYSTYPE; # define YYSTYPE_IS_TRIVIAL 1 # define YYSTYPE_IS_DECLARED 1 #endif int sieveparse (sieve_script_t *parse_script); #endif /* !YY_SIEVE_SIEVE_SIEVE_H_INCLUDED */ /* Copy the second part of user declarations. */ #line 552 "sieve/sieve.c" /* yacc.c:358 */ #ifdef short # undef short #endif #ifdef YYTYPE_UINT8 typedef YYTYPE_UINT8 yytype_uint8; #else typedef unsigned char yytype_uint8; #endif #ifdef YYTYPE_INT8 typedef YYTYPE_INT8 yytype_int8; #else typedef signed char yytype_int8; #endif #ifdef YYTYPE_UINT16 typedef YYTYPE_UINT16 yytype_uint16; #else typedef unsigned short int yytype_uint16; #endif #ifdef YYTYPE_INT16 typedef YYTYPE_INT16 yytype_int16; #else typedef short int yytype_int16; #endif #ifndef YYSIZE_T # ifdef __SIZE_TYPE__ # define YYSIZE_T __SIZE_TYPE__ # elif defined size_t # define YYSIZE_T size_t # elif ! defined YYSIZE_T # include /* INFRINGES ON USER NAME SPACE */ # define YYSIZE_T size_t # else # define YYSIZE_T unsigned int # endif #endif #define YYSIZE_MAXIMUM ((YYSIZE_T) -1) #ifndef YY_ # if defined YYENABLE_NLS && YYENABLE_NLS # if ENABLE_NLS # include /* INFRINGES ON USER NAME SPACE */ # define YY_(Msgid) dgettext ("bison-runtime", Msgid) # endif # endif # ifndef YY_ # define YY_(Msgid) Msgid # endif #endif #ifndef YY_ATTRIBUTE # if (defined __GNUC__ \ && (2 < __GNUC__ || (__GNUC__ == 2 && 96 <= __GNUC_MINOR__))) \ || defined __SUNPRO_C && 0x5110 <= __SUNPRO_C # define YY_ATTRIBUTE(Spec) __attribute__(Spec) # else # define YY_ATTRIBUTE(Spec) /* empty */ # endif #endif #ifndef YY_ATTRIBUTE_PURE # define YY_ATTRIBUTE_PURE YY_ATTRIBUTE ((__pure__)) #endif #ifndef YY_ATTRIBUTE_UNUSED # define YY_ATTRIBUTE_UNUSED YY_ATTRIBUTE ((__unused__)) #endif #if !defined _Noreturn \ && (!defined __STDC_VERSION__ || __STDC_VERSION__ < 201112) # if defined _MSC_VER && 1200 <= _MSC_VER # define _Noreturn __declspec (noreturn) # else # define _Noreturn YY_ATTRIBUTE ((__noreturn__)) # endif #endif /* Suppress unused-variable warnings by "using" E. */ #if ! defined lint || defined __GNUC__ # define YYUSE(E) ((void) (E)) #else # define YYUSE(E) /* empty */ #endif #if defined __GNUC__ && 407 <= __GNUC__ * 100 + __GNUC_MINOR__ /* Suppress an incorrect diagnostic about yylval being uninitialized. */ # define YY_IGNORE_MAYBE_UNINITIALIZED_BEGIN \ _Pragma ("GCC diagnostic push") \ _Pragma ("GCC diagnostic ignored \"-Wuninitialized\"")\ _Pragma ("GCC diagnostic ignored \"-Wmaybe-uninitialized\"") # define YY_IGNORE_MAYBE_UNINITIALIZED_END \ _Pragma ("GCC diagnostic pop") #else # define YY_INITIAL_VALUE(Value) Value #endif #ifndef YY_IGNORE_MAYBE_UNINITIALIZED_BEGIN # define YY_IGNORE_MAYBE_UNINITIALIZED_BEGIN # define YY_IGNORE_MAYBE_UNINITIALIZED_END #endif #ifndef YY_INITIAL_VALUE # define YY_INITIAL_VALUE(Value) /* Nothing. */ #endif #if ! defined yyoverflow || YYERROR_VERBOSE /* The parser invokes alloca or malloc; define the necessary symbols. */ # ifdef YYSTACK_USE_ALLOCA # if YYSTACK_USE_ALLOCA # ifdef __GNUC__ # define YYSTACK_ALLOC __builtin_alloca # elif defined __BUILTIN_VA_ARG_INCR # include /* INFRINGES ON USER NAME SPACE */ # elif defined _AIX # define YYSTACK_ALLOC __alloca # elif defined _MSC_VER # include /* INFRINGES ON USER NAME SPACE */ # define alloca _alloca # else # define YYSTACK_ALLOC alloca # if ! defined _ALLOCA_H && ! defined EXIT_SUCCESS # include /* INFRINGES ON USER NAME SPACE */ /* Use EXIT_SUCCESS as a witness for stdlib.h. */ # ifndef EXIT_SUCCESS # define EXIT_SUCCESS 0 # endif # endif # endif # endif # endif # ifdef YYSTACK_ALLOC /* Pacify GCC's 'empty if-body' warning. */ # define YYSTACK_FREE(Ptr) do { /* empty */; } while (0) # ifndef YYSTACK_ALLOC_MAXIMUM /* The OS might guarantee only one guard page at the bottom of the stack, and a page size can be as small as 4096 bytes. So we cannot safely invoke alloca (N) if N exceeds 4096. Use a slightly smaller number to allow for a few compiler-allocated temporary stack slots. */ # define YYSTACK_ALLOC_MAXIMUM 4032 /* reasonable circa 2006 */ # endif # else # define YYSTACK_ALLOC YYMALLOC # define YYSTACK_FREE YYFREE # ifndef YYSTACK_ALLOC_MAXIMUM # define YYSTACK_ALLOC_MAXIMUM YYSIZE_MAXIMUM # endif # if (defined __cplusplus && ! defined EXIT_SUCCESS \ && ! ((defined YYMALLOC || defined malloc) \ && (defined YYFREE || defined free))) # include /* INFRINGES ON USER NAME SPACE */ # ifndef EXIT_SUCCESS # define EXIT_SUCCESS 0 # endif # endif # ifndef YYMALLOC # define YYMALLOC malloc # if ! defined malloc && ! defined EXIT_SUCCESS void *malloc (YYSIZE_T); /* INFRINGES ON USER NAME SPACE */ # endif # endif # ifndef YYFREE # define YYFREE free # if ! defined free && ! defined EXIT_SUCCESS void free (void *); /* INFRINGES ON USER NAME SPACE */ # endif # endif # endif #endif /* ! defined yyoverflow || YYERROR_VERBOSE */ #if (! defined yyoverflow \ && (! defined __cplusplus \ || (defined YYSTYPE_IS_TRIVIAL && YYSTYPE_IS_TRIVIAL))) /* A type that is properly aligned for any stack member. */ union yyalloc { yytype_int16 yyss_alloc; YYSTYPE yyvs_alloc; }; /* The size of the maximum gap between one aligned stack and the next. */ # define YYSTACK_GAP_MAXIMUM (sizeof (union yyalloc) - 1) /* The size of an array large to enough to hold all stacks, each with N elements. */ # define YYSTACK_BYTES(N) \ ((N) * (sizeof (yytype_int16) + sizeof (YYSTYPE)) \ + YYSTACK_GAP_MAXIMUM) # define YYCOPY_NEEDED 1 /* Relocate STACK from its old location to the new one. The local variables YYSIZE and YYSTACKSIZE give the old and new number of elements in the stack, and YYPTR gives the new location of the stack. Advance YYPTR to a properly aligned location for the next stack. */ # define YYSTACK_RELOCATE(Stack_alloc, Stack) \ do \ { \ YYSIZE_T yynewbytes; \ YYCOPY (&yyptr->Stack_alloc, Stack, yysize); \ Stack = &yyptr->Stack_alloc; \ yynewbytes = yystacksize * sizeof (*Stack) + YYSTACK_GAP_MAXIMUM; \ yyptr += yynewbytes / sizeof (*yyptr); \ } \ while (0) #endif #if defined YYCOPY_NEEDED && YYCOPY_NEEDED /* Copy COUNT objects from SRC to DST. The source and destination do not overlap. */ # ifndef YYCOPY # if defined __GNUC__ && 1 < __GNUC__ # define YYCOPY(Dst, Src, Count) \ __builtin_memcpy (Dst, Src, (Count) * sizeof (*(Src))) # else # define YYCOPY(Dst, Src, Count) \ do \ { \ YYSIZE_T yyi; \ for (yyi = 0; yyi < (Count); yyi++) \ (Dst)[yyi] = (Src)[yyi]; \ } \ while (0) # endif # endif #endif /* !YYCOPY_NEEDED */ /* YYFINAL -- State number of the termination state. */ #define YYFINAL 8 /* YYLAST -- Last index in YYTABLE. */ #define YYLAST 333 /* YYNTOKENS -- Number of terminals. */ #define YYNTOKENS 106 /* YYNNTS -- Number of nonterminals. */ #define YYNNTS 31 /* YYNRULES -- Number of rules. */ #define YYNRULES 128 /* YYNSTATES -- Number of states. */ #define YYNSTATES 202 /* YYTRANSLATE[YYX] -- Symbol number corresponding to YYX as returned by yylex, with out-of-bounds checking. */ #define YYUNDEFTOK 2 #define YYMAXUTOK 352 #define YYTRANSLATE(YYX) \ ((unsigned int) (YYX) <= YYMAXUTOK ? yytranslate[YYX] : YYUNDEFTOK) /* YYTRANSLATE[TOKEN-NUM] -- Symbol number corresponding to TOKEN-NUM as returned by yylex, without out-of-bounds checking. */ static const yytype_uint8 yytranslate[] = { 0, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 104, 105, 2, 2, 101, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 98, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 99, 2, 100, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 102, 2, 103, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20, 21, 22, 23, 24, 25, 26, 27, 28, 29, 30, 31, 32, 33, 34, 35, 36, 37, 38, 39, 40, 41, 42, 43, 44, 45, 46, 47, 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 58, 59, 60, 61, 62, 63, 64, 65, 66, 67, 68, 69, 70, 71, 72, 73, 74, 75, 76, 77, 78, 79, 80, 81, 82, 83, 84, 85, 86, 87, 88, 89, 90, 91, 92, 93, 94, 95, 96, 97 }; #if YYDEBUG /* YYRLINE[YYN] -- Source line where rule number YYN was defined. */ static const yytype_uint16 yyrline[] = { 0, 274, 274, 275, 278, 279, 282, 290, 291, 294, 295, 296, 299, 300, 301, 304, 313, 321, 325, 326, 327, 328, 337, 348, 359, 370, 375, 381, 389, 399, 412, 419, 420, 423, 426, 429, 434, 435, 438, 441, 444, 447, 452, 453, 456, 471, 481, 482, 483, 486, 487, 490, 497, 505, 511, 517, 523, 529, 530, 536, 540, 546, 547, 550, 551, 552, 553, 554, 555, 580, 602, 624, 650, 651, 653, 669, 693, 696, 697, 704, 705, 710, 714, 722, 730, 739, 750, 751, 755, 763, 771, 780, 791, 792, 797, 802, 810, 814, 822, 832, 833, 838, 847, 855, 865, 875, 884, 890, 891, 892, 893, 898, 904, 905, 906, 907, 914, 919, 927, 928, 931, 938, 939, 943, 959, 960, 966, 969, 970 }; #endif #if YYDEBUG || YYERROR_VERBOSE || 0 /* YYTNAME[SYMBOL-NUM] -- String name of the symbol SYMBOL-NUM. First, the terminals, then, starting at YYNTOKENS, nonterminals. */ static const char *const yytname[] = { "$end", "error", "$undefined", "NUMBER", "STRING", "IF", "ELSIF", "ELSE", "REJCT", "FILEINTO", "REDIRECT", "KEEP", "STOP", "DISCARD", "VACATION", "REQUIRE", "SETFLAG", "ADDFLAG", "REMOVEFLAG", "MARK", "UNMARK", "HASFLAG", "FLAGS", "NOTIFY", "DENOTIFY", "ANYOF", "ALLOF", "EXISTS", "SFALSE", "STRUE", "HEADER", "NOT", "SIZE", "ADDRESS", "ENVELOPE", "BODY", "COMPARATOR", "IS", "CONTAINS", "MATCHES", "REGEX", "COUNT", "VALUE", "OVER", "UNDER", "GT", "GE", "LT", "LE", "EQ", "NE", "ALL", "LOCALPART", "DOMAIN", "USER", "DETAIL", "RAW", "TEXT", "CONTENT", "DAYS", "ADDRESSES", "SUBJECT", "FROM", "HANDLE", "MIME", "SECONDS", "METHOD", "ID", "OPTIONS", "LOW", "NORMAL", "HIGH", "ANY", "MESSAGE", "INCLUDE", "PERSONAL", "GLOBAL", "RETURN", "OPTIONAL", "ONCE", "COPY", "DATE", "CURRENTDATE", "INDEX", "LAST", "ZONE", "ORIGINALZONE", "YEAR", "MONTH", "DAY", "JULIAN", "HOUR", "MINUTE", "SECOND", "TIME", "ISO8601", "STD11", "WEEKDAY", "';'", "'['", "']'", "','", "'{'", "'}'", "'('", "')'", "$accept", "start", "reqs", "require", "commands", "command", "elsif", "action", "itags", "ntags", "dtags", "priority", "vtags", "stringlist", "strings", "block", "test", "addrorenv", "aetags", "htags", "btags", "dttags", "addrparttag", "comptag", "relcomp", "sizetag", "copy", "ftags", "rtags", "testlist", "tests", YY_NULLPTR }; #endif # ifdef YYPRINT /* YYTOKNUM[NUM] -- (External) token number corresponding to the (internal) symbol number NUM (which must be that of a token). */ static const yytype_uint16 yytoknum[] = { 0, 256, 257, 258, 259, 260, 261, 262, 263, 264, 265, 266, 267, 268, 269, 270, 271, 272, 273, 274, 275, 276, 277, 278, 279, 280, 281, 282, 283, 284, 285, 286, 287, 288, 289, 290, 291, 292, 293, 294, 295, 296, 297, 298, 299, 300, 301, 302, 303, 304, 305, 306, 307, 308, 309, 310, 311, 312, 313, 314, 315, 316, 317, 318, 319, 320, 321, 322, 323, 324, 325, 326, 327, 328, 329, 330, 331, 332, 333, 334, 335, 336, 337, 338, 339, 340, 341, 342, 343, 344, 345, 346, 347, 348, 349, 350, 351, 352, 59, 91, 93, 44, 123, 125, 40, 41 }; # endif #define YYPACT_NINF -138 #define yypact_value_is_default(Yystate) \ (!!((Yystate) == (-138))) #define YYTABLE_NINF -8 #define yytable_value_is_error(Yytable_value) \ 0 /* YYPACT[STATE-NUM] -- Index in YYTABLE of the portion describing STATE-NUM. */ static const yytype_int16 yypact[] = { -5, -1, 13, 256, -5, -138, 32, -60, -138, -59, 181, 36, -138, -138, -138, -138, -138, -138, -1, -1, -1, -138, -138, -138, -138, -138, -138, -138, 6, -57, -138, -138, -73, -138, -138, -138, -138, -56, -56, -1, -138, -138, -138, 181, -12, -138, -138, -138, -138, -138, -52, -138, -138, 31, 4, -17, 109, -138, -138, -138, 215, 5, 68, -138, -138, -138, 47, 95, 181, -138, -138, -138, 95, -138, -138, -138, 49, 119, 148, 159, 77, 27, 66, -138, -1, -138, -138, -138, -138, -138, 53, -1, 54, 56, 58, -138, 62, 63, 64, -1, -138, -138, -138, 65, -138, -138, -138, -138, -138, -138, -138, -138, 67, 73, -138, -138, -138, -138, -138, -138, 75, 89, -138, -138, -138, 108, -44, 9, -1, -138, 112, -138, -138, -1, -138, -138, 118, 120, 121, 123, -138, 124, -138, -138, 125, -1, -138, 35, 181, -52, -138, 126, -138, -138, -138, -138, -138, 136, -138, -1, -138, -138, 141, -138, -138, -138, -138, -138, -138, -138, -138, -138, -138, -138, -138, -138, -138, -138, -138, 181, -138, -138, -138, -138, -138, -1, -138, -138, -138, -138, -138, -138, -52, -138, -138, -138, -138, -138, -138, -138, 27, -138 }; /* YYDEFACT[STATE-NUM] -- Default reduction number in state STATE-NUM. Performed when YYTABLE does not specify something else to do. Zero means the default is an error. */ static const yytype_uint8 yydefact[] = { 4, 0, 0, 0, 4, 58, 0, 0, 1, 0, 0, 0, 121, 124, 121, 19, 20, 49, 0, 0, 0, 25, 26, 36, 42, 31, 30, 3, 0, 0, 5, 59, 0, 6, 11, 76, 86, 0, 0, 0, 66, 67, 86, 0, 0, 77, 78, 92, 99, 99, 0, 79, 15, 0, 0, 18, 0, 22, 23, 24, 27, 28, 0, 8, 9, 57, 0, 0, 0, 63, 64, 65, 0, 72, 118, 119, 0, 0, 0, 0, 0, 12, 0, 16, 0, 120, 122, 17, 125, 21, 0, 0, 0, 0, 0, 56, 0, 0, 0, 0, 46, 47, 48, 0, 40, 112, 113, 114, 115, 116, 117, 43, 0, 0, 29, 32, 33, 35, 34, 60, 0, 0, 91, 69, 87, 0, 127, 0, 0, 73, 0, 93, 94, 0, 71, 96, 0, 0, 0, 0, 104, 0, 106, 100, 0, 0, 62, 0, 0, 0, 10, 0, 107, 108, 109, 110, 111, 0, 85, 0, 80, 81, 0, 123, 50, 52, 53, 54, 55, 51, 38, 37, 39, 41, 44, 45, 89, 90, 88, 0, 126, 68, 98, 95, 97, 0, 102, 103, 105, 101, 75, 61, 0, 14, 83, 84, 70, 82, 128, 74, 12, 13 }; /* YYPGOTO[NTERM-NUM]. */ static const yytype_int16 yypgoto[] = { -138, -138, 144, -138, -19, -138, -47, -138, -138, -138, -138, 79, -138, -18, -138, -137, -6, -138, -138, 122, -138, 113, -138, 142, 169, -138, 127, 152, -138, 145, 12 }; /* YYDEFGOTO[NTERM-NUM]. */ static const yytype_int16 yydefgoto[] = { -1, 2, 3, 4, 27, 28, 150, 29, 62, 60, 61, 104, 56, 7, 32, 81, 126, 51, 82, 67, 77, 78, 160, 124, 125, 76, 86, 53, 54, 69, 127 }; /* YYTABLE[YYPACT[STATE-NUM]] -- What to do in state STATE-NUM. If positive, shift that token. If negative, reduce the rule whose number is the opposite. If YYTABLE_NINF, syntax error. */ static const yytype_int16 yytable[] = { 57, 58, 59, 5, 50, 84, -7, 9, 87, 63, 1, 10, 193, 8, 11, 12, 13, 14, 15, 16, 17, 71, 18, 19, 20, 21, 22, 65, 66, 23, 24, 74, 75, 148, 149, 83, 31, 73, 33, 34, 52, 64, 105, 106, 107, 108, 109, 110, 68, 123, 80, 119, 129, 84, 128, 200, 164, 179, 166, 134, 167, 147, 168, 85, 159, 169, 163, 170, 171, 173, 5, 174, 114, 165, 100, 101, 102, 175, 9, 176, 25, 172, 10, 26, 85, 11, 12, 13, 14, 15, 16, 17, 177, 18, 19, 20, 21, 22, 6, 5, 23, 24, 151, 105, 106, 107, 108, 109, 110, -7, 181, 85, 178, 89, 180, 183, 182, 152, 153, 154, 155, 156, 184, 5, 185, 186, 187, 190, 188, 189, 194, 120, 105, 106, 107, 108, 109, 110, 191, 195, 111, 196, 192, 115, 116, 197, 117, 118, 30, 157, 158, 25, 137, 201, 26, 130, 105, 106, 107, 108, 109, 110, 79, 145, 72, 6, 55, 199, 90, 91, 92, 93, 94, 95, 96, 131, 132, 133, 121, 122, 146, 88, 35, 70, 138, 105, 106, 107, 108, 109, 110, 198, 0, 0, 6, 138, 105, 106, 107, 108, 109, 110, 36, 112, 0, 0, 37, 38, 39, 40, 41, 42, 43, 44, 45, 46, 47, 0, 6, 135, 143, 143, 0, 0, 161, 0, 0, 0, 0, 0, 113, 139, 140, 141, 142, 0, 0, 0, 0, 0, 0, 0, 139, 140, 141, 142, 136, 144, 144, 0, 0, 162, 0, 0, 0, 0, -2, 9, 0, 0, 0, 10, 48, 49, 11, 12, 13, 14, 15, 16, 17, 0, 18, 19, 20, 21, 22, 0, 0, 23, 24, 97, 98, 99, 100, 101, 102, 0, 103, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 25, 0, 0, 26 }; static const yytype_int16 yycheck[] = { 18, 19, 20, 4, 10, 22, 0, 1, 4, 28, 15, 5, 149, 0, 8, 9, 10, 11, 12, 13, 14, 39, 16, 17, 18, 19, 20, 100, 101, 23, 24, 43, 44, 6, 7, 4, 4, 43, 98, 98, 4, 98, 37, 38, 39, 40, 41, 42, 104, 67, 102, 4, 3, 22, 72, 192, 3, 101, 4, 77, 4, 80, 4, 80, 82, 3, 84, 4, 4, 4, 4, 4, 4, 91, 69, 70, 71, 4, 1, 4, 74, 99, 5, 77, 80, 8, 9, 10, 11, 12, 13, 14, 3, 16, 17, 18, 19, 20, 99, 4, 23, 24, 36, 37, 38, 39, 40, 41, 42, 103, 128, 80, 4, 4, 105, 133, 4, 51, 52, 53, 54, 55, 4, 4, 4, 4, 3, 145, 4, 4, 4, 36, 37, 38, 39, 40, 41, 42, 103, 3, 61, 159, 148, 75, 76, 4, 78, 79, 4, 83, 84, 74, 4, 200, 77, 36, 37, 38, 39, 40, 41, 42, 49, 4, 42, 99, 14, 185, 59, 60, 61, 62, 63, 64, 65, 56, 57, 58, 83, 84, 103, 54, 1, 38, 36, 37, 38, 39, 40, 41, 42, 179, -1, -1, 99, 36, 37, 38, 39, 40, 41, 42, 21, 61, -1, -1, 25, 26, 27, 28, 29, 30, 31, 32, 33, 34, 35, -1, 99, 77, 78, 79, -1, -1, 82, -1, -1, -1, -1, -1, 61, 83, 84, 85, 86, -1, -1, -1, -1, -1, -1, -1, 83, 84, 85, 86, 77, 78, 79, -1, -1, 82, -1, -1, -1, -1, 0, 1, -1, -1, -1, 5, 81, 82, 8, 9, 10, 11, 12, 13, 14, -1, 16, 17, 18, 19, 20, -1, -1, 23, 24, 66, 67, 68, 69, 70, 71, -1, 73, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, 74, -1, -1, 77 }; /* YYSTOS[STATE-NUM] -- The (internal number of the) accessing symbol of state STATE-NUM. */ static const yytype_uint8 yystos[] = { 0, 15, 107, 108, 109, 4, 99, 119, 0, 1, 5, 8, 9, 10, 11, 12, 13, 14, 16, 17, 18, 19, 20, 23, 24, 74, 77, 110, 111, 113, 108, 4, 120, 98, 98, 1, 21, 25, 26, 27, 28, 29, 30, 31, 32, 33, 34, 35, 81, 82, 122, 123, 4, 133, 134, 133, 118, 119, 119, 119, 115, 116, 114, 110, 98, 100, 101, 125, 104, 135, 135, 119, 125, 122, 43, 44, 131, 126, 127, 127, 102, 121, 124, 4, 22, 80, 132, 4, 132, 4, 59, 60, 61, 62, 63, 64, 65, 66, 67, 68, 69, 70, 71, 73, 117, 37, 38, 39, 40, 41, 42, 117, 129, 130, 4, 75, 76, 78, 79, 4, 36, 83, 84, 119, 129, 130, 122, 136, 119, 3, 36, 56, 57, 58, 119, 129, 130, 4, 36, 83, 84, 85, 86, 129, 130, 4, 103, 110, 6, 7, 112, 36, 51, 52, 53, 54, 55, 83, 84, 119, 128, 129, 130, 119, 3, 119, 4, 4, 4, 3, 4, 4, 119, 4, 4, 4, 4, 3, 4, 101, 105, 119, 4, 119, 4, 4, 4, 3, 4, 4, 119, 103, 122, 121, 4, 3, 119, 4, 136, 119, 121, 112 }; /* YYR1[YYN] -- Symbol number of symbol that rule YYN derives. */ static const yytype_uint8 yyr1[] = { 0, 106, 107, 107, 108, 108, 109, 110, 110, 111, 111, 111, 112, 112, 112, 113, 113, 113, 113, 113, 113, 113, 113, 113, 113, 113, 113, 113, 113, 113, 113, 114, 114, 114, 114, 114, 115, 115, 115, 115, 115, 115, 116, 116, 116, 116, 117, 117, 117, 118, 118, 118, 118, 118, 118, 118, 118, 119, 119, 120, 120, 121, 121, 122, 122, 122, 122, 122, 122, 122, 122, 122, 122, 122, 122, 122, 122, 123, 123, 124, 124, 124, 124, 124, 124, 124, 125, 125, 125, 125, 125, 125, 126, 126, 126, 126, 126, 126, 126, 127, 127, 127, 127, 127, 127, 127, 127, 128, 128, 128, 128, 128, 129, 129, 129, 129, 130, 130, 131, 131, 132, 133, 133, 133, 134, 134, 135, 136, 136 }; /* YYR2[YYN] -- Number of symbols on the right hand side of rule YYN. */ static const yytype_uint8 yyr2[] = { 0, 2, 1, 2, 0, 2, 3, 1, 2, 2, 4, 2, 0, 4, 2, 2, 3, 3, 2, 1, 1, 3, 2, 2, 2, 1, 1, 2, 2, 3, 1, 0, 2, 2, 2, 2, 0, 3, 3, 3, 2, 3, 0, 2, 3, 3, 1, 1, 1, 0, 3, 3, 3, 3, 3, 3, 2, 3, 1, 1, 3, 3, 2, 2, 2, 2, 1, 1, 4, 3, 4, 3, 2, 3, 5, 4, 1, 1, 1, 0, 2, 2, 3, 3, 3, 2, 0, 2, 3, 3, 3, 2, 0, 2, 2, 3, 2, 3, 3, 0, 2, 3, 3, 3, 2, 3, 2, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 2, 3, 0, 2, 3, 1, 3 }; #define yyerrok (yyerrstatus = 0) #define yyclearin (yychar = YYEMPTY) #define YYEMPTY (-2) #define YYEOF 0 #define YYACCEPT goto yyacceptlab #define YYABORT goto yyabortlab #define YYERROR goto yyerrorlab #define YYRECOVERING() (!!yyerrstatus) #define YYBACKUP(Token, Value) \ do \ if (yychar == YYEMPTY) \ { \ yychar = (Token); \ yylval = (Value); \ YYPOPSTACK (yylen); \ yystate = *yyssp; \ goto yybackup; \ } \ else \ { \ yyerror (parse_script, YY_("syntax error: cannot back up")); \ YYERROR; \ } \ while (0) /* Error token number */ #define YYTERROR 1 #define YYERRCODE 256 /* Enable debugging if requested. */ #if YYDEBUG # ifndef YYFPRINTF # include /* INFRINGES ON USER NAME SPACE */ # define YYFPRINTF fprintf # endif # define YYDPRINTF(Args) \ do { \ if (yydebug) \ YYFPRINTF Args; \ } while (0) /* This macro is provided for backward compatibility. */ #ifndef YY_LOCATION_PRINT # define YY_LOCATION_PRINT(File, Loc) ((void) 0) #endif # define YY_SYMBOL_PRINT(Title, Type, Value, Location) \ do { \ if (yydebug) \ { \ YYFPRINTF (stderr, "%s ", Title); \ yy_symbol_print (stderr, \ Type, Value, parse_script); \ YYFPRINTF (stderr, "\n"); \ } \ } while (0) /*----------------------------------------. | Print this symbol's value on YYOUTPUT. | `----------------------------------------*/ static void yy_symbol_value_print (FILE *yyoutput, int yytype, YYSTYPE const * const yyvaluep, sieve_script_t *parse_script) { FILE *yyo = yyoutput; YYUSE (yyo); YYUSE (parse_script); if (!yyvaluep) return; # ifdef YYPRINT if (yytype < YYNTOKENS) YYPRINT (yyoutput, yytoknum[yytype], *yyvaluep); # endif YYUSE (yytype); } /*--------------------------------. | Print this symbol on YYOUTPUT. | `--------------------------------*/ static void yy_symbol_print (FILE *yyoutput, int yytype, YYSTYPE const * const yyvaluep, sieve_script_t *parse_script) { YYFPRINTF (yyoutput, "%s %s (", yytype < YYNTOKENS ? "token" : "nterm", yytname[yytype]); yy_symbol_value_print (yyoutput, yytype, yyvaluep, parse_script); YYFPRINTF (yyoutput, ")"); } /*------------------------------------------------------------------. | yy_stack_print -- Print the state stack from its BOTTOM up to its | | TOP (included). | `------------------------------------------------------------------*/ static void yy_stack_print (yytype_int16 *yybottom, yytype_int16 *yytop) { YYFPRINTF (stderr, "Stack now"); for (; yybottom <= yytop; yybottom++) { int yybot = *yybottom; YYFPRINTF (stderr, " %d", yybot); } YYFPRINTF (stderr, "\n"); } # define YY_STACK_PRINT(Bottom, Top) \ do { \ if (yydebug) \ yy_stack_print ((Bottom), (Top)); \ } while (0) /*------------------------------------------------. | Report that the YYRULE is going to be reduced. | `------------------------------------------------*/ static void yy_reduce_print (yytype_int16 *yyssp, YYSTYPE *yyvsp, int yyrule, sieve_script_t *parse_script) { unsigned long int yylno = yyrline[yyrule]; int yynrhs = yyr2[yyrule]; int yyi; YYFPRINTF (stderr, "Reducing stack by rule %d (line %lu):\n", yyrule - 1, yylno); /* The symbols being reduced. */ for (yyi = 0; yyi < yynrhs; yyi++) { YYFPRINTF (stderr, " $%d = ", yyi + 1); yy_symbol_print (stderr, yystos[yyssp[yyi + 1 - yynrhs]], &(yyvsp[(yyi + 1) - (yynrhs)]) , parse_script); YYFPRINTF (stderr, "\n"); } } # define YY_REDUCE_PRINT(Rule) \ do { \ if (yydebug) \ yy_reduce_print (yyssp, yyvsp, Rule, parse_script); \ } while (0) /* Nonzero means print parse trace. It is left uninitialized so that multiple parsers can coexist. */ int yydebug; #else /* !YYDEBUG */ # define YYDPRINTF(Args) # define YY_SYMBOL_PRINT(Title, Type, Value, Location) # define YY_STACK_PRINT(Bottom, Top) # define YY_REDUCE_PRINT(Rule) #endif /* !YYDEBUG */ /* YYINITDEPTH -- initial size of the parser's stacks. */ #ifndef YYINITDEPTH # define YYINITDEPTH 200 #endif /* YYMAXDEPTH -- maximum size the stacks can grow to (effective only if the built-in stack extension method is used). Do not make this value too large; the results are undefined if YYSTACK_ALLOC_MAXIMUM < YYSTACK_BYTES (YYMAXDEPTH) evaluated with infinite-precision integer arithmetic. */ #ifndef YYMAXDEPTH # define YYMAXDEPTH 10000 #endif #if YYERROR_VERBOSE # ifndef yystrlen # if defined __GLIBC__ && defined _STRING_H # define yystrlen strlen # else /* Return the length of YYSTR. */ static YYSIZE_T yystrlen (const char *yystr) { YYSIZE_T yylen; for (yylen = 0; yystr[yylen]; yylen++) continue; return yylen; } # endif # endif # ifndef yystpcpy # if defined __GLIBC__ && defined _STRING_H && defined _GNU_SOURCE # define yystpcpy stpcpy # else /* Copy YYSRC to YYDEST, returning the address of the terminating '\0' in YYDEST. */ static char * yystpcpy (char *yydest, const char *yysrc) { char *yyd = yydest; const char *yys = yysrc; while ((*yyd++ = *yys++) != '\0') continue; return yyd - 1; } # endif # endif # ifndef yytnamerr /* Copy to YYRES the contents of YYSTR after stripping away unnecessary quotes and backslashes, so that it's suitable for yyerror. The heuristic is that double-quoting is unnecessary unless the string contains an apostrophe, a comma, or backslash (other than backslash-backslash). YYSTR is taken from yytname. If YYRES is null, do not copy; instead, return the length of what the result would have been. */ static YYSIZE_T yytnamerr (char *yyres, const char *yystr) { if (*yystr == '"') { YYSIZE_T yyn = 0; char const *yyp = yystr; for (;;) switch (*++yyp) { case '\'': case ',': goto do_not_strip_quotes; case '\\': if (*++yyp != '\\') goto do_not_strip_quotes; /* Fall through. */ default: if (yyres) yyres[yyn] = *yyp; yyn++; break; case '"': if (yyres) yyres[yyn] = '\0'; return yyn; } do_not_strip_quotes: ; } if (! yyres) return yystrlen (yystr); return yystpcpy (yyres, yystr) - yyres; } # endif /* Copy into *YYMSG, which is of size *YYMSG_ALLOC, an error message about the unexpected token YYTOKEN for the state stack whose top is YYSSP. Return 0 if *YYMSG was successfully written. Return 1 if *YYMSG is not large enough to hold the message. In that case, also set *YYMSG_ALLOC to the required number of bytes. Return 2 if the required number of bytes is too large to store. */ static int yysyntax_error (YYSIZE_T *yymsg_alloc, char **yymsg, yytype_int16 *yyssp, int yytoken) { YYSIZE_T yysize0 = yytnamerr (YY_NULLPTR, yytname[yytoken]); YYSIZE_T yysize = yysize0; enum { YYERROR_VERBOSE_ARGS_MAXIMUM = 5 }; /* Internationalized format string. */ const char *yyformat = YY_NULLPTR; /* Arguments of yyformat. */ char const *yyarg[YYERROR_VERBOSE_ARGS_MAXIMUM]; /* Number of reported tokens (one for the "unexpected", one per "expected"). */ int yycount = 0; /* There are many possibilities here to consider: - If this state is a consistent state with a default action, then the only way this function was invoked is if the default action is an error action. In that case, don't check for expected tokens because there are none. - The only way there can be no lookahead present (in yychar) is if this state is a consistent state with a default action. Thus, detecting the absence of a lookahead is sufficient to determine that there is no unexpected or expected token to report. In that case, just report a simple "syntax error". - Don't assume there isn't a lookahead just because this state is a consistent state with a default action. There might have been a previous inconsistent state, consistent state with a non-default action, or user semantic action that manipulated yychar. - Of course, the expected token list depends on states to have correct lookahead information, and it depends on the parser not to perform extra reductions after fetching a lookahead from the scanner and before detecting a syntax error. Thus, state merging (from LALR or IELR) and default reductions corrupt the expected token list. However, the list is correct for canonical LR with one exception: it will still contain any token that will not be accepted due to an error action in a later state. */ if (yytoken != YYEMPTY) { int yyn = yypact[*yyssp]; yyarg[yycount++] = yytname[yytoken]; if (!yypact_value_is_default (yyn)) { /* Start YYX at -YYN if negative to avoid negative indexes in YYCHECK. In other words, skip the first -YYN actions for this state because they are default actions. */ int yyxbegin = yyn < 0 ? -yyn : 0; /* Stay within bounds of both yycheck and yytname. */ int yychecklim = YYLAST - yyn + 1; int yyxend = yychecklim < YYNTOKENS ? yychecklim : YYNTOKENS; int yyx; for (yyx = yyxbegin; yyx < yyxend; ++yyx) if (yycheck[yyx + yyn] == yyx && yyx != YYTERROR && !yytable_value_is_error (yytable[yyx + yyn])) { if (yycount == YYERROR_VERBOSE_ARGS_MAXIMUM) { yycount = 1; yysize = yysize0; break; } yyarg[yycount++] = yytname[yyx]; { YYSIZE_T yysize1 = yysize + yytnamerr (YY_NULLPTR, yytname[yyx]); if (! (yysize <= yysize1 && yysize1 <= YYSTACK_ALLOC_MAXIMUM)) return 2; yysize = yysize1; } } } } switch (yycount) { # define YYCASE_(N, S) \ case N: \ yyformat = S; \ break YYCASE_(0, YY_("syntax error")); YYCASE_(1, YY_("syntax error, unexpected %s")); YYCASE_(2, YY_("syntax error, unexpected %s, expecting %s")); YYCASE_(3, YY_("syntax error, unexpected %s, expecting %s or %s")); YYCASE_(4, YY_("syntax error, unexpected %s, expecting %s or %s or %s")); YYCASE_(5, YY_("syntax error, unexpected %s, expecting %s or %s or %s or %s")); # undef YYCASE_ } { YYSIZE_T yysize1 = yysize + yystrlen (yyformat); if (! (yysize <= yysize1 && yysize1 <= YYSTACK_ALLOC_MAXIMUM)) return 2; yysize = yysize1; } if (*yymsg_alloc < yysize) { *yymsg_alloc = 2 * yysize; if (! (yysize <= *yymsg_alloc && *yymsg_alloc <= YYSTACK_ALLOC_MAXIMUM)) *yymsg_alloc = YYSTACK_ALLOC_MAXIMUM; return 1; } /* Avoid sprintf, as that infringes on the user's name space. Don't have undefined behavior even if the translation produced a string with the wrong number of "%s"s. */ { char *yyp = *yymsg; int yyi = 0; while ((*yyp = *yyformat) != '\0') if (*yyp == '%' && yyformat[1] == 's' && yyi < yycount) { yyp += yytnamerr (yyp, yyarg[yyi++]); yyformat += 2; } else { yyp++; yyformat++; } } return 0; } #endif /* YYERROR_VERBOSE */ /*-----------------------------------------------. | Release the memory associated to this symbol. | `-----------------------------------------------*/ static void yydestruct (const char *yymsg, int yytype, YYSTYPE *yyvaluep, sieve_script_t *parse_script) { YYUSE (yyvaluep); YYUSE (parse_script); if (!yymsg) yymsg = "Deleting"; YY_SYMBOL_PRINT (yymsg, yytype, yyvaluep, yylocationp); YY_IGNORE_MAYBE_UNINITIALIZED_BEGIN switch (yytype) { case 110: /* commands */ #line 267 "sieve/sieve.y" /* yacc.c:1257 */ { free_tree(((*yyvaluep).cl)); } #line 1571 "sieve/sieve.c" /* yacc.c:1257 */ break; case 111: /* command */ #line 267 "sieve/sieve.y" /* yacc.c:1257 */ { free_tree(((*yyvaluep).cl)); } #line 1577 "sieve/sieve.c" /* yacc.c:1257 */ break; case 112: /* elsif */ #line 267 "sieve/sieve.y" /* yacc.c:1257 */ { free_tree(((*yyvaluep).cl)); } #line 1583 "sieve/sieve.c" /* yacc.c:1257 */ break; case 113: /* action */ #line 267 "sieve/sieve.y" /* yacc.c:1257 */ { free_tree(((*yyvaluep).cl)); } #line 1589 "sieve/sieve.c" /* yacc.c:1257 */ break; case 121: /* block */ #line 267 "sieve/sieve.y" /* yacc.c:1257 */ { free_tree(((*yyvaluep).cl)); } #line 1595 "sieve/sieve.c" /* yacc.c:1257 */ break; default: break; } YY_IGNORE_MAYBE_UNINITIALIZED_END } /*----------. | yyparse. | `----------*/ int yyparse (sieve_script_t *parse_script) { /* The lookahead symbol. */ int yychar; /* The semantic value of the lookahead symbol. */ /* Default value used for initialization, for pacifying older GCCs or non-GCC compilers. */ YY_INITIAL_VALUE (static YYSTYPE yyval_default;) YYSTYPE yylval YY_INITIAL_VALUE (= yyval_default); /* Number of syntax errors so far. */ int yynerrs; int yystate; /* Number of tokens to shift before error messages enabled. */ int yyerrstatus; /* The stacks and their tools: 'yyss': related to states. 'yyvs': related to semantic values. Refer to the stacks through separate pointers, to allow yyoverflow to reallocate them elsewhere. */ /* The state stack. */ yytype_int16 yyssa[YYINITDEPTH]; yytype_int16 *yyss; yytype_int16 *yyssp; /* The semantic value stack. */ YYSTYPE yyvsa[YYINITDEPTH]; YYSTYPE *yyvs; YYSTYPE *yyvsp; YYSIZE_T yystacksize; int yyn; int yyresult; /* Lookahead token as an internal (translated) token number. */ int yytoken = 0; /* The variables used to return semantic value and location from the action routines. */ YYSTYPE yyval; #if YYERROR_VERBOSE /* Buffer for error messages, and its allocated size. */ char yymsgbuf[128]; char *yymsg = yymsgbuf; YYSIZE_T yymsg_alloc = sizeof yymsgbuf; #endif #define YYPOPSTACK(N) (yyvsp -= (N), yyssp -= (N)) /* The number of symbols on the RHS of the reduced rule. Keep to zero when no symbol should be popped. */ int yylen = 0; yyssp = yyss = yyssa; yyvsp = yyvs = yyvsa; yystacksize = YYINITDEPTH; YYDPRINTF ((stderr, "Starting parse\n")); yystate = 0; yyerrstatus = 0; yynerrs = 0; yychar = YYEMPTY; /* Cause a token to be read. */ goto yysetstate; /*------------------------------------------------------------. | yynewstate -- Push a new state, which is found in yystate. | `------------------------------------------------------------*/ yynewstate: /* In all cases, when you get here, the value and location stacks have just been pushed. So pushing a state here evens the stacks. */ yyssp++; yysetstate: *yyssp = yystate; if (yyss + yystacksize - 1 <= yyssp) { /* Get the current used size of the three stacks, in elements. */ YYSIZE_T yysize = yyssp - yyss + 1; #ifdef yyoverflow { /* Give user a chance to reallocate the stack. Use copies of these so that the &'s don't force the real ones into memory. */ YYSTYPE *yyvs1 = yyvs; yytype_int16 *yyss1 = yyss; /* Each stack pointer address is followed by the size of the data in use in that stack, in bytes. This used to be a conditional around just the two extra args, but that might be undefined if yyoverflow is a macro. */ yyoverflow (YY_("memory exhausted"), &yyss1, yysize * sizeof (*yyssp), &yyvs1, yysize * sizeof (*yyvsp), &yystacksize); yyss = yyss1; yyvs = yyvs1; } #else /* no yyoverflow */ # ifndef YYSTACK_RELOCATE goto yyexhaustedlab; # else /* Extend the stack our own way. */ if (YYMAXDEPTH <= yystacksize) goto yyexhaustedlab; yystacksize *= 2; if (YYMAXDEPTH < yystacksize) yystacksize = YYMAXDEPTH; { yytype_int16 *yyss1 = yyss; union yyalloc *yyptr = (union yyalloc *) YYSTACK_ALLOC (YYSTACK_BYTES (yystacksize)); if (! yyptr) goto yyexhaustedlab; YYSTACK_RELOCATE (yyss_alloc, yyss); YYSTACK_RELOCATE (yyvs_alloc, yyvs); # undef YYSTACK_RELOCATE if (yyss1 != yyssa) YYSTACK_FREE (yyss1); } # endif #endif /* no yyoverflow */ yyssp = yyss + yysize - 1; yyvsp = yyvs + yysize - 1; YYDPRINTF ((stderr, "Stack size increased to %lu\n", (unsigned long int) yystacksize)); if (yyss + yystacksize - 1 <= yyssp) YYABORT; } YYDPRINTF ((stderr, "Entering state %d\n", yystate)); if (yystate == YYFINAL) YYACCEPT; goto yybackup; /*-----------. | yybackup. | `-----------*/ yybackup: /* Do appropriate processing given the current state. Read a lookahead token if we need one and don't already have one. */ /* First try to decide what to do without reference to lookahead token. */ yyn = yypact[yystate]; if (yypact_value_is_default (yyn)) goto yydefault; /* Not known => get a lookahead token if don't already have one. */ /* YYCHAR is either YYEMPTY or YYEOF or a valid lookahead symbol. */ if (yychar == YYEMPTY) { YYDPRINTF ((stderr, "Reading a token: ")); yychar = yylex (&yylval, parse_script); } if (yychar <= YYEOF) { yychar = yytoken = YYEOF; YYDPRINTF ((stderr, "Now at end of input.\n")); } else { yytoken = YYTRANSLATE (yychar); YY_SYMBOL_PRINT ("Next token is", yytoken, &yylval, &yylloc); } /* If the proper action on seeing token YYTOKEN is to reduce or to detect an error, take that action. */ yyn += yytoken; if (yyn < 0 || YYLAST < yyn || yycheck[yyn] != yytoken) goto yydefault; yyn = yytable[yyn]; if (yyn <= 0) { if (yytable_value_is_error (yyn)) goto yyerrlab; yyn = -yyn; goto yyreduce; } /* Count tokens shifted since error; after three, turn off error status. */ if (yyerrstatus) yyerrstatus--; /* Shift the lookahead token. */ YY_SYMBOL_PRINT ("Shifting", yytoken, &yylval, &yylloc); /* Discard the shifted token. */ yychar = YYEMPTY; yystate = yyn; YY_IGNORE_MAYBE_UNINITIALIZED_BEGIN *++yyvsp = yylval; YY_IGNORE_MAYBE_UNINITIALIZED_END goto yynewstate; /*-----------------------------------------------------------. | yydefault -- do the default action for the current state. | `-----------------------------------------------------------*/ yydefault: yyn = yydefact[yystate]; if (yyn == 0) goto yyerrlab; goto yyreduce; /*-----------------------------. | yyreduce -- Do a reduction. | `-----------------------------*/ yyreduce: /* yyn is the number of a rule to reduce with. */ yylen = yyr2[yyn]; /* If YYLEN is nonzero, implement the default value of the action: '$$ = $1'. Otherwise, the following line sets YYVAL to garbage. This behavior is undocumented and Bison users should not rely upon it. Assigning to YYVAL unconditionally makes the parser a bit smaller, and it avoids a GCC warning that YYVAL may be used uninitialized. */ yyval = yyvsp[1-yylen]; YY_REDUCE_PRINT (yyn); switch (yyn) { case 2: #line 274 "sieve/sieve.y" /* yacc.c:1646 */ { parse_script->cmds = NULL; } #line 1863 "sieve/sieve.c" /* yacc.c:1646 */ break; case 3: #line 275 "sieve/sieve.y" /* yacc.c:1646 */ { parse_script->cmds = (yyvsp[0].cl); } #line 1869 "sieve/sieve.c" /* yacc.c:1646 */ break; case 6: #line 282 "sieve/sieve.y" /* yacc.c:1646 */ { char *err = check_reqs(parse_script, (yyvsp[-1].sl)); if (err) { yyerror(parse_script, err); free(err); YYERROR; } } #line 1880 "sieve/sieve.c" /* yacc.c:1646 */ break; case 7: #line 290 "sieve/sieve.y" /* yacc.c:1646 */ { (yyval.cl) = (yyvsp[0].cl); } #line 1886 "sieve/sieve.c" /* yacc.c:1646 */ break; case 8: #line 291 "sieve/sieve.y" /* yacc.c:1646 */ { (yyvsp[-1].cl)->next = (yyvsp[0].cl); (yyval.cl) = (yyvsp[-1].cl); } #line 1892 "sieve/sieve.c" /* yacc.c:1646 */ break; case 9: #line 294 "sieve/sieve.y" /* yacc.c:1646 */ { (yyval.cl) = (yyvsp[-1].cl); } #line 1898 "sieve/sieve.c" /* yacc.c:1646 */ break; case 10: #line 295 "sieve/sieve.y" /* yacc.c:1646 */ { (yyval.cl) = new_if((yyvsp[-2].test), (yyvsp[-1].cl), (yyvsp[0].cl)); } #line 1904 "sieve/sieve.c" /* yacc.c:1646 */ break; case 11: #line 296 "sieve/sieve.y" /* yacc.c:1646 */ { (yyval.cl) = new_command(STOP); } #line 1910 "sieve/sieve.c" /* yacc.c:1646 */ break; case 12: #line 299 "sieve/sieve.y" /* yacc.c:1646 */ { (yyval.cl) = NULL; } #line 1916 "sieve/sieve.c" /* yacc.c:1646 */ break; case 13: #line 300 "sieve/sieve.y" /* yacc.c:1646 */ { (yyval.cl) = new_if((yyvsp[-2].test), (yyvsp[-1].cl), (yyvsp[0].cl)); } #line 1922 "sieve/sieve.c" /* yacc.c:1646 */ break; case 14: #line 301 "sieve/sieve.y" /* yacc.c:1646 */ { (yyval.cl) = (yyvsp[0].cl); } #line 1928 "sieve/sieve.c" /* yacc.c:1646 */ break; case 15: #line 304 "sieve/sieve.y" /* yacc.c:1646 */ { if (!parse_script->support.reject) { yyerror(parse_script, "reject MUST be enabled with \"require\""); YYERROR; } if (!verify_utf8(parse_script, (yyvsp[0].sval))) { YYERROR; /* vu should call yyerror() */ } (yyval.cl) = new_command(REJCT); (yyval.cl)->u.str = (yyvsp[0].sval); } #line 1942 "sieve/sieve.c" /* yacc.c:1646 */ break; case 16: #line 313 "sieve/sieve.y" /* yacc.c:1646 */ { if (!parse_script->support.fileinto) { yyerror(parse_script, "fileinto MUST be enabled with \"require\""); YYERROR; } if (!verify_mailbox(parse_script, (yyvsp[0].sval))) { YYERROR; /* vm should call yyerror() */ } (yyval.cl) = build_fileinto(FILEINTO, canon_ftags((yyvsp[-1].ftag)), (yyvsp[0].sval)); } #line 1955 "sieve/sieve.c" /* yacc.c:1646 */ break; case 17: #line 321 "sieve/sieve.y" /* yacc.c:1646 */ { if (!verify_address(parse_script, (yyvsp[0].sval))) { YYERROR; /* va should call yyerror() */ } (yyval.cl) = build_redirect(REDIRECT, (yyvsp[-1].nval), (yyvsp[0].sval)); } #line 1964 "sieve/sieve.c" /* yacc.c:1646 */ break; case 18: #line 325 "sieve/sieve.y" /* yacc.c:1646 */ { (yyval.cl) = build_keep(KEEP,canon_ftags((yyvsp[0].ftag))); } #line 1970 "sieve/sieve.c" /* yacc.c:1646 */ break; case 19: #line 326 "sieve/sieve.y" /* yacc.c:1646 */ { (yyval.cl) = new_command(STOP); } #line 1976 "sieve/sieve.c" /* yacc.c:1646 */ break; case 20: #line 327 "sieve/sieve.y" /* yacc.c:1646 */ { (yyval.cl) = new_command(DISCARD); } #line 1982 "sieve/sieve.c" /* yacc.c:1646 */ break; case 21: #line 328 "sieve/sieve.y" /* yacc.c:1646 */ { if (!parse_script->support.vacation) { yyerror(parse_script, "vacation MUST be enabled with \"require\""); YYERROR; } if (((yyvsp[-1].vtag)->mime == -1) && !verify_utf8(parse_script, (yyvsp[0].sval))) { YYERROR; /* vu should call yyerror() */ } (yyval.cl) = build_vacation(VACATION, canon_vtags(parse_script, (yyvsp[-1].vtag)), (yyvsp[0].sval)); } #line 1996 "sieve/sieve.c" /* yacc.c:1646 */ break; case 22: #line 337 "sieve/sieve.y" /* yacc.c:1646 */ { if (!(parse_script->support.imapflags || parse_script->support.imap4flags)) { yyerror(parse_script, "imap4flags MUST be enabled with \"require\""); YYERROR; } verify_flaglist((yyvsp[0].sl)); if(!(yyvsp[0].sl)->count) { strarray_add((yyvsp[0].sl), ""); } (yyval.cl) = new_command(SETFLAG); (yyval.cl)->u.sl = (yyvsp[0].sl); } #line 2012 "sieve/sieve.c" /* yacc.c:1646 */ break; case 23: #line 348 "sieve/sieve.y" /* yacc.c:1646 */ { if (!(parse_script->support.imapflags || parse_script->support.imap4flags)) { yyerror(parse_script, "imap4flags MUST be enabled with \"require\""); YYERROR; } verify_flaglist((yyvsp[0].sl)); if(!(yyvsp[0].sl)->count) { strarray_add((yyvsp[0].sl), ""); } (yyval.cl) = new_command(ADDFLAG); (yyval.cl)->u.sl = (yyvsp[0].sl); } #line 2028 "sieve/sieve.c" /* yacc.c:1646 */ break; case 24: #line 359 "sieve/sieve.y" /* yacc.c:1646 */ { if (!(parse_script->support.imapflags || parse_script->support.imap4flags)) { yyerror(parse_script, "imap4flags MUST be enabled with \"require\""); YYERROR; } verify_flaglist((yyvsp[0].sl)); if(!(yyvsp[0].sl)->count) { strarray_add((yyvsp[0].sl), ""); } (yyval.cl) = new_command(REMOVEFLAG); (yyval.cl)->u.sl = (yyvsp[0].sl); } #line 2044 "sieve/sieve.c" /* yacc.c:1646 */ break; case 25: #line 370 "sieve/sieve.y" /* yacc.c:1646 */ { if (!parse_script->support.imapflags) { yyerror(parse_script, "imapflags MUST be enabled with \"require\""); YYERROR; } (yyval.cl) = new_command(MARK); } #line 2054 "sieve/sieve.c" /* yacc.c:1646 */ break; case 26: #line 375 "sieve/sieve.y" /* yacc.c:1646 */ { if (!parse_script->support.imapflags) { yyerror(parse_script, "imapflags MUST be enabled with \"require\""); YYERROR; } (yyval.cl) = new_command(UNMARK); } #line 2064 "sieve/sieve.c" /* yacc.c:1646 */ break; case 27: #line 381 "sieve/sieve.y" /* yacc.c:1646 */ { if (!parse_script->support.notify) { yyerror(parse_script, "notify MUST be enabled with \"require\""); (yyval.cl) = new_command(NOTIFY); YYERROR; } else { (yyval.cl) = build_notify(NOTIFY, canon_ntags((yyvsp[0].ntag))); } } #line 2077 "sieve/sieve.c" /* yacc.c:1646 */ break; case 28: #line 389 "sieve/sieve.y" /* yacc.c:1646 */ { if (!parse_script->support.notify) { yyerror(parse_script, "notify MUST be enabled with \"require\""); (yyval.cl) = new_command(DENOTIFY); YYERROR; } else { (yyval.cl) = build_denotify(DENOTIFY, canon_dtags((yyvsp[0].dtag))); if ((yyval.cl) == NULL) { yyerror(parse_script, "unable to find a compatible comparator"); YYERROR; } } } #line 2091 "sieve/sieve.c" /* yacc.c:1646 */ break; case 29: #line 399 "sieve/sieve.y" /* yacc.c:1646 */ { if (!parse_script->support.include) { yyerror(parse_script, "include MUST be enabled with \"require\""); YYERROR; } int i; for (i = 0; (yyvsp[0].sval)[i] != '\0'; i++) { if ((yyvsp[0].sval)[i] == '/') { yyerror(parse_script, "included script name must not contain slash"); YYERROR; break; } } (yyval.cl) = build_include(INCLUDE, (yyvsp[-1].itag), (yyvsp[0].sval)); } #line 2109 "sieve/sieve.c" /* yacc.c:1646 */ break; case 30: #line 412 "sieve/sieve.y" /* yacc.c:1646 */ { if (!parse_script->support.include) { yyerror(parse_script, "include MUST be enabled with \"require\""); YYERROR; } (yyval.cl) = new_command(RETURN); } #line 2119 "sieve/sieve.c" /* yacc.c:1646 */ break; case 31: #line 419 "sieve/sieve.y" /* yacc.c:1646 */ { (yyval.itag) = new_itags(); } #line 2125 "sieve/sieve.c" /* yacc.c:1646 */ break; case 32: #line 420 "sieve/sieve.y" /* yacc.c:1646 */ { if ((yyval.itag)->location != -1) { yyerror(parse_script, "duplicate location (:personal or :global)"); YYERROR; } else { (yyval.itag)->location = PERSONAL; }} #line 2133 "sieve/sieve.c" /* yacc.c:1646 */ break; case 33: #line 423 "sieve/sieve.y" /* yacc.c:1646 */ { if ((yyval.itag)->location != -1) { yyerror(parse_script, "duplicate location (:personal or :global)"); YYERROR; } else { (yyval.itag)->location = GLOBAL; }} #line 2141 "sieve/sieve.c" /* yacc.c:1646 */ break; case 34: #line 426 "sieve/sieve.y" /* yacc.c:1646 */ { if ((yyval.itag)->once != -1) { yyerror(parse_script, "duplicate :once"); YYERROR; } else { (yyval.itag)->once = 1; }} #line 2149 "sieve/sieve.c" /* yacc.c:1646 */ break; case 35: #line 429 "sieve/sieve.y" /* yacc.c:1646 */ { if ((yyval.itag)->optional != -1) { yyerror(parse_script, "duplicate :optional"); YYERROR; } else { (yyval.itag)->optional = 1; }} #line 2157 "sieve/sieve.c" /* yacc.c:1646 */ break; case 36: #line 434 "sieve/sieve.y" /* yacc.c:1646 */ { (yyval.ntag) = new_ntags(); } #line 2163 "sieve/sieve.c" /* yacc.c:1646 */ break; case 37: #line 435 "sieve/sieve.y" /* yacc.c:1646 */ { if ((yyval.ntag)->id != NULL) { yyerror(parse_script, "duplicate :method"); YYERROR; } else { (yyval.ntag)->id = (yyvsp[0].sval); } } #line 2171 "sieve/sieve.c" /* yacc.c:1646 */ break; case 38: #line 438 "sieve/sieve.y" /* yacc.c:1646 */ { if ((yyval.ntag)->method != NULL) { yyerror(parse_script, "duplicate :method"); YYERROR; } else { (yyval.ntag)->method = (yyvsp[0].sval); } } #line 2179 "sieve/sieve.c" /* yacc.c:1646 */ break; case 39: #line 441 "sieve/sieve.y" /* yacc.c:1646 */ { if ((yyval.ntag)->options != NULL) { yyerror(parse_script, "duplicate :options"); YYERROR; } else { (yyval.ntag)->options = (yyvsp[0].sl); } } #line 2187 "sieve/sieve.c" /* yacc.c:1646 */ break; case 40: #line 444 "sieve/sieve.y" /* yacc.c:1646 */ { if ((yyval.ntag)->priority != -1) { yyerror(parse_script, "duplicate :priority"); YYERROR; } else { (yyval.ntag)->priority = (yyvsp[0].nval); } } #line 2195 "sieve/sieve.c" /* yacc.c:1646 */ break; case 41: #line 447 "sieve/sieve.y" /* yacc.c:1646 */ { if ((yyval.ntag)->message != NULL) { yyerror(parse_script, "duplicate :message"); YYERROR; } else { (yyval.ntag)->message = (yyvsp[0].sval); } } #line 2203 "sieve/sieve.c" /* yacc.c:1646 */ break; case 42: #line 452 "sieve/sieve.y" /* yacc.c:1646 */ { (yyval.dtag) = new_dtags(); } #line 2209 "sieve/sieve.c" /* yacc.c:1646 */ break; case 43: #line 453 "sieve/sieve.y" /* yacc.c:1646 */ { if ((yyval.dtag)->priority != -1) { yyerror(parse_script, "duplicate priority level"); YYERROR; } else { (yyval.dtag)->priority = (yyvsp[0].nval); } } #line 2217 "sieve/sieve.c" /* yacc.c:1646 */ break; case 44: #line 456 "sieve/sieve.y" /* yacc.c:1646 */ { if ((yyval.dtag)->comptag != -1) { yyerror(parse_script, "duplicate comparator type tag"); YYERROR; } (yyval.dtag)->comptag = (yyvsp[-1].nval); #ifdef ENABLE_REGEX if ((yyval.dtag)->comptag == REGEX) { int cflags = REG_EXTENDED | REG_NOSUB | REG_ICASE; if (!verify_regex(parse_script, (yyvsp[0].sval), cflags)) { YYERROR; } } #endif (yyval.dtag)->pattern = (yyvsp[0].sval); } #line 2237 "sieve/sieve.c" /* yacc.c:1646 */ break; case 45: #line 471 "sieve/sieve.y" /* yacc.c:1646 */ { (yyval.dtag) = (yyvsp[-2].dtag); if ((yyval.dtag)->comptag != -1) { yyerror(parse_script, "duplicate comparator type tag"); YYERROR; } else { (yyval.dtag)->comptag = (yyvsp[-1].nval); (yyval.dtag)->relation = verify_relat(parse_script, (yyvsp[0].sval)); if ((yyval.dtag)->relation==-1) {YYERROR; /*vr called yyerror()*/ } } } #line 2250 "sieve/sieve.c" /* yacc.c:1646 */ break; case 46: #line 481 "sieve/sieve.y" /* yacc.c:1646 */ { (yyval.nval) = LOW; } #line 2256 "sieve/sieve.c" /* yacc.c:1646 */ break; case 47: #line 482 "sieve/sieve.y" /* yacc.c:1646 */ { (yyval.nval) = NORMAL; } #line 2262 "sieve/sieve.c" /* yacc.c:1646 */ break; case 48: #line 483 "sieve/sieve.y" /* yacc.c:1646 */ { (yyval.nval) = HIGH; } #line 2268 "sieve/sieve.c" /* yacc.c:1646 */ break; case 49: #line 486 "sieve/sieve.y" /* yacc.c:1646 */ { (yyval.vtag) = new_vtags(); } #line 2274 "sieve/sieve.c" /* yacc.c:1646 */ break; case 50: #line 487 "sieve/sieve.y" /* yacc.c:1646 */ { if ((yyval.vtag)->seconds != -1) { yyerror(parse_script, "duplicate :days or :seconds"); YYERROR; } else { (yyval.vtag)->seconds = (yyvsp[0].nval) * DAY2SEC; } } #line 2282 "sieve/sieve.c" /* yacc.c:1646 */ break; case 51: #line 490 "sieve/sieve.y" /* yacc.c:1646 */ { if (!parse_script->support.vacation_seconds) { yyerror(parse_script, "vacation-seconds not required"); YYERROR; } if ((yyval.vtag)->seconds != -1) { yyerror(parse_script, "duplicate :days or :seconds"); YYERROR; } else { (yyval.vtag)->seconds = (yyvsp[0].nval); } } #line 2294 "sieve/sieve.c" /* yacc.c:1646 */ break; case 52: #line 497 "sieve/sieve.y" /* yacc.c:1646 */ { if ((yyval.vtag)->addresses != NULL) { yyerror(parse_script, "duplicate :addresses"); YYERROR; } else if (!verify_stringlist(parse_script, (yyvsp[0].sl), verify_address)) { YYERROR; } else { (yyval.vtag)->addresses = (yyvsp[0].sl); } } #line 2307 "sieve/sieve.c" /* yacc.c:1646 */ break; case 53: #line 505 "sieve/sieve.y" /* yacc.c:1646 */ { if ((yyval.vtag)->subject != NULL) { yyerror(parse_script, "duplicate :subject"); YYERROR; } else if (!verify_utf8(parse_script, (yyvsp[0].sval))) { YYERROR; /* vu should call yyerror() */ } else { (yyval.vtag)->subject = (yyvsp[0].sval); } } #line 2318 "sieve/sieve.c" /* yacc.c:1646 */ break; case 54: #line 511 "sieve/sieve.y" /* yacc.c:1646 */ { if ((yyval.vtag)->from != NULL) { yyerror(parse_script, "duplicate :from"); YYERROR; } else if (!verify_address(parse_script, (yyvsp[0].sval))) { YYERROR; /* va should call yyerror() */ } else { (yyval.vtag)->from = (yyvsp[0].sval); } } #line 2329 "sieve/sieve.c" /* yacc.c:1646 */ break; case 55: #line 517 "sieve/sieve.y" /* yacc.c:1646 */ { if ((yyval.vtag)->handle != NULL) { yyerror(parse_script, "duplicate :handle"); YYERROR; } else if (!verify_utf8(parse_script, (yyvsp[0].sval))) { YYERROR; /* vu should call yyerror() */ } else { (yyval.vtag)->handle = (yyvsp[0].sval); } } #line 2340 "sieve/sieve.c" /* yacc.c:1646 */ break; case 56: #line 523 "sieve/sieve.y" /* yacc.c:1646 */ { if ((yyval.vtag)->mime != -1) { yyerror(parse_script, "duplicate :mime"); YYERROR; } else { (yyval.vtag)->mime = MIME; } } #line 2349 "sieve/sieve.c" /* yacc.c:1646 */ break; case 57: #line 529 "sieve/sieve.y" /* yacc.c:1646 */ { (yyval.sl) = (yyvsp[-1].sl); } #line 2355 "sieve/sieve.c" /* yacc.c:1646 */ break; case 58: #line 530 "sieve/sieve.y" /* yacc.c:1646 */ { (yyval.sl) = strarray_new(); strarray_appendm((yyval.sl), (yyvsp[0].sval)); } #line 2364 "sieve/sieve.c" /* yacc.c:1646 */ break; case 59: #line 536 "sieve/sieve.y" /* yacc.c:1646 */ { (yyval.sl) = strarray_new(); strarray_appendm((yyval.sl), (yyvsp[0].sval)); } #line 2373 "sieve/sieve.c" /* yacc.c:1646 */ break; case 60: #line 540 "sieve/sieve.y" /* yacc.c:1646 */ { (yyval.sl) = (yyvsp[-2].sl); strarray_appendm((yyval.sl), (yyvsp[0].sval)); } #line 2382 "sieve/sieve.c" /* yacc.c:1646 */ break; case 61: #line 546 "sieve/sieve.y" /* yacc.c:1646 */ { (yyval.cl) = (yyvsp[-1].cl); } #line 2388 "sieve/sieve.c" /* yacc.c:1646 */ break; case 62: #line 547 "sieve/sieve.y" /* yacc.c:1646 */ { (yyval.cl) = NULL; } #line 2394 "sieve/sieve.c" /* yacc.c:1646 */ break; case 63: #line 550 "sieve/sieve.y" /* yacc.c:1646 */ { (yyval.test) = new_test(ANYOF); (yyval.test)->u.tl = (yyvsp[0].testl); } #line 2400 "sieve/sieve.c" /* yacc.c:1646 */ break; case 64: #line 551 "sieve/sieve.y" /* yacc.c:1646 */ { (yyval.test) = new_test(ALLOF); (yyval.test)->u.tl = (yyvsp[0].testl); } #line 2406 "sieve/sieve.c" /* yacc.c:1646 */ break; case 65: #line 552 "sieve/sieve.y" /* yacc.c:1646 */ { (yyval.test) = new_test(EXISTS); (yyval.test)->u.sl = (yyvsp[0].sl); } #line 2412 "sieve/sieve.c" /* yacc.c:1646 */ break; case 66: #line 553 "sieve/sieve.y" /* yacc.c:1646 */ { (yyval.test) = new_test(SFALSE); } #line 2418 "sieve/sieve.c" /* yacc.c:1646 */ break; case 67: #line 554 "sieve/sieve.y" /* yacc.c:1646 */ { (yyval.test) = new_test(STRUE); } #line 2424 "sieve/sieve.c" /* yacc.c:1646 */ break; case 68: #line 556 "sieve/sieve.y" /* yacc.c:1646 */ { if (!verify_stringlist(parse_script, (yyvsp[-1].sl), verify_header)) { YYERROR; /* vh should call yyerror() */ } if (!verify_stringlist(parse_script, (yyvsp[0].sl), verify_utf8)) { YYERROR; /* vu should call yyerror() */ } (yyvsp[-2].htag) = canon_htags((yyvsp[-2].htag)); #ifdef ENABLE_REGEX if ((yyvsp[-2].htag)->comptag == REGEX) { if (!(verify_regexs(parse_script, (yyvsp[0].sl), (yyvsp[-2].htag)->comparator))) { YYERROR; } } #endif (yyval.test) = build_header(HEADER, (yyvsp[-2].htag), (yyvsp[-1].sl), (yyvsp[0].sl)); if ((yyval.test) == NULL) { yyerror(parse_script, "unable to find a compatible comparator"); YYERROR; } } #line 2450 "sieve/sieve.c" /* yacc.c:1646 */ break; case 69: #line 581 "sieve/sieve.y" /* yacc.c:1646 */ { if (!parse_script->support.imap4flags) { yyerror(parse_script, "imap4flags MUST be enabled with \"require\""); YYERROR; } (yyvsp[-1].htag) = canon_htags((yyvsp[-1].htag)); #ifdef ENABLE_REGEX if ((yyvsp[-1].htag)->comptag == REGEX) { if (!(verify_regexs(parse_script, (yyvsp[0].sl), (yyvsp[-1].htag)->comparator))) { YYERROR; } } #endif (yyval.test) = build_hasflag(HASFLAG, (yyvsp[-1].htag), (yyvsp[0].sl)); if ((yyval.test) == NULL) { yyerror(parse_script, "unable to find a compatible comparator"); YYERROR; } } #line 2474 "sieve/sieve.c" /* yacc.c:1646 */ break; case 70: #line 603 "sieve/sieve.y" /* yacc.c:1646 */ { if (((yyvsp[-3].nval) == ADDRESS) && !verify_stringlist(parse_script, (yyvsp[-1].sl), verify_addrheader)) { YYERROR; } else if (((yyvsp[-3].nval) == ENVELOPE) && !verify_stringlist(parse_script, (yyvsp[-1].sl), verify_envelope)) { YYERROR; } (yyvsp[-2].aetag) = canon_aetags((yyvsp[-2].aetag)); #ifdef ENABLE_REGEX if ((yyvsp[-2].aetag)->comptag == REGEX) { if (!( verify_regexs(parse_script, (yyvsp[0].sl), (yyvsp[-2].aetag)->comparator))) { YYERROR; } } #endif (yyval.test) = build_address((yyvsp[-3].nval), (yyvsp[-2].aetag), (yyvsp[-1].sl), (yyvsp[0].sl)); if ((yyval.test) == NULL) { yyerror(parse_script, "unable to find a compatible comparator"); YYERROR; } } #line 2499 "sieve/sieve.c" /* yacc.c:1646 */ break; case 71: #line 625 "sieve/sieve.y" /* yacc.c:1646 */ { if (!parse_script->support.body) { yyerror(parse_script, "body MUST be enabled with \"require\""); YYERROR; } if (!verify_stringlist(parse_script, (yyvsp[0].sl), verify_utf8)) { YYERROR; /* vu should call yyerror() */ } (yyvsp[-1].btag) = canon_btags((yyvsp[-1].btag)); #ifdef ENABLE_REGEX if ((yyvsp[-1].btag)->comptag == REGEX) { if (!(verify_regexs(parse_script, (yyvsp[0].sl), (yyvsp[-1].btag)->comparator))) { YYERROR; } } #endif (yyval.test) = build_body(BODY, (yyvsp[-1].btag), (yyvsp[0].sl)); if ((yyval.test) == NULL) { yyerror(parse_script, "unable to find a compatible comparator"); YYERROR; } } #line 2527 "sieve/sieve.c" /* yacc.c:1646 */ break; case 72: #line 650 "sieve/sieve.y" /* yacc.c:1646 */ { (yyval.test) = new_test(NOT); (yyval.test)->u.t = (yyvsp[0].test); } #line 2533 "sieve/sieve.c" /* yacc.c:1646 */ break; case 73: #line 651 "sieve/sieve.y" /* yacc.c:1646 */ { (yyval.test) = new_test(SIZE); (yyval.test)->u.sz.t = (yyvsp[-1].nval); (yyval.test)->u.sz.n = (yyvsp[0].nval); } #line 2540 "sieve/sieve.c" /* yacc.c:1646 */ break; case 74: #line 654 "sieve/sieve.y" /* yacc.c:1646 */ {if (!parse_script->support.date) { yyerror(parse_script, "date MUST be enabled with \"require\""); YYERROR; } (yyvsp[-3].dttag)->date_part = verify_date_part(parse_script, (yyvsp[-1].sval)); if ((yyvsp[-3].dttag)->date_part == -1) { YYERROR; /*vr called yyerror()*/ } (yyvsp[-3].dttag) = canon_dttags((yyvsp[-3].dttag)); (yyval.test) = build_date(DATE, (yyvsp[-3].dttag), (yyvsp[-2].sval), (yyvsp[0].sl)); if ((yyval.test) == NULL) { yyerror(parse_script, "unable to find a compatible comparator"); YYERROR; } } #line 2560 "sieve/sieve.c" /* yacc.c:1646 */ break; case 75: #line 670 "sieve/sieve.y" /* yacc.c:1646 */ {if (!parse_script->support.date) { yyerror(parse_script, "date MUST be enabled with \"require\""); YYERROR; } if ((yyvsp[-2].dttag)->index != 0) { yyerror(parse_script, "index argument is not allowed in currentdate"); YYERROR; } if ((yyvsp[-2].dttag)->zonetag == ORIGINALZONE) { yyerror(parse_script, "originalzone argument is not allowed in currentdate"); YYERROR; } (yyvsp[-2].dttag)->date_part = verify_date_part(parse_script, (yyvsp[-1].sval)); if ((yyvsp[-2].dttag)->date_part == -1) { YYERROR; /*vr called yyerror()*/ } (yyvsp[-2].dttag) = canon_dttags((yyvsp[-2].dttag)); (yyval.test) = build_date(CURRENTDATE, (yyvsp[-2].dttag), NULL, (yyvsp[0].sl)); if ((yyval.test) == NULL) { yyerror(parse_script, "unable to find a compatible comparator"); YYERROR; } } #line 2588 "sieve/sieve.c" /* yacc.c:1646 */ break; case 76: #line 693 "sieve/sieve.y" /* yacc.c:1646 */ { (yyval.test) = NULL; } #line 2594 "sieve/sieve.c" /* yacc.c:1646 */ break; case 77: #line 696 "sieve/sieve.y" /* yacc.c:1646 */ { (yyval.nval) = ADDRESS; } #line 2600 "sieve/sieve.c" /* yacc.c:1646 */ break; case 78: #line 697 "sieve/sieve.y" /* yacc.c:1646 */ {if (!parse_script->support.envelope) {yyerror(parse_script, "envelope MUST be enabled with \"require\""); YYERROR;} else{(yyval.nval) = ENVELOPE; } } #line 2609 "sieve/sieve.c" /* yacc.c:1646 */ break; case 79: #line 704 "sieve/sieve.y" /* yacc.c:1646 */ { (yyval.aetag) = new_aetags(); } #line 2615 "sieve/sieve.c" /* yacc.c:1646 */ break; case 80: #line 705 "sieve/sieve.y" /* yacc.c:1646 */ { (yyval.aetag) = (yyvsp[-1].aetag); if ((yyval.aetag)->addrtag != -1) { yyerror(parse_script, "duplicate or conflicting address part tag"); YYERROR; } else { (yyval.aetag)->addrtag = (yyvsp[0].nval); } } #line 2625 "sieve/sieve.c" /* yacc.c:1646 */ break; case 81: #line 710 "sieve/sieve.y" /* yacc.c:1646 */ { (yyval.aetag) = (yyvsp[-1].aetag); if ((yyval.aetag)->comptag != -1) { yyerror(parse_script, "duplicate comparator type tag"); YYERROR; } else { (yyval.aetag)->comptag = (yyvsp[0].nval); } } #line 2634 "sieve/sieve.c" /* yacc.c:1646 */ break; case 82: #line 714 "sieve/sieve.y" /* yacc.c:1646 */ { (yyval.aetag) = (yyvsp[-2].aetag); if ((yyval.aetag)->comptag != -1) { yyerror(parse_script, "duplicate comparator type tag"); YYERROR; } else { (yyval.aetag)->comptag = (yyvsp[-1].nval); (yyval.aetag)->relation = verify_relat(parse_script, (yyvsp[0].sval)); if ((yyval.aetag)->relation==-1) {YYERROR; /*vr called yyerror()*/ } } } #line 2647 "sieve/sieve.c" /* yacc.c:1646 */ break; case 83: #line 722 "sieve/sieve.y" /* yacc.c:1646 */ { (yyval.aetag) = (yyvsp[-2].aetag); if ((yyval.aetag)->comparator != NULL) { yyerror(parse_script, "duplicate comparator tag"); YYERROR; } else if (!strcmp((yyvsp[0].sval), "i;ascii-numeric") && !parse_script->support.i_ascii_numeric) { yyerror(parse_script, "comparator-i;ascii-numeric MUST be enabled with \"require\""); YYERROR; } else { (yyval.aetag)->comparator = (yyvsp[0].sval); } } #line 2660 "sieve/sieve.c" /* yacc.c:1646 */ break; case 84: #line 730 "sieve/sieve.y" /* yacc.c:1646 */ { (yyval.aetag) = (yyvsp[-2].aetag); if (!parse_script->support.index) { yyerror(parse_script, "index MUST be enabled with \"require\""); YYERROR; } if ((yyval.aetag)->index != 0) { yyerror(parse_script, "duplicate index argument"); YYERROR; } if ((yyvsp[0].nval) <= 0) { yyerror(parse_script, "invalid index value"); YYERROR; } else { (yyval.aetag)->index = (yyvsp[0].nval); } } #line 2674 "sieve/sieve.c" /* yacc.c:1646 */ break; case 85: #line 739 "sieve/sieve.y" /* yacc.c:1646 */ { (yyval.aetag) = (yyvsp[-1].aetag); if (!parse_script->support.index) { yyerror(parse_script, "index MUST be enabled with \"require\""); YYERROR; } if ((yyval.aetag)->index == 0) { yyerror(parse_script, "index argument is required"); YYERROR; } else if ((yyval.aetag)->index < 0) { yyerror(parse_script, "duplicate last argument"); YYERROR; } else { (yyval.aetag)->index *= -1; } } #line 2688 "sieve/sieve.c" /* yacc.c:1646 */ break; case 86: #line 750 "sieve/sieve.y" /* yacc.c:1646 */ { (yyval.htag) = new_htags(); } #line 2694 "sieve/sieve.c" /* yacc.c:1646 */ break; case 87: #line 751 "sieve/sieve.y" /* yacc.c:1646 */ { (yyval.htag) = (yyvsp[-1].htag); if ((yyval.htag)->comptag != -1) { yyerror(parse_script, "duplicate comparator type tag"); YYERROR; } else { (yyval.htag)->comptag = (yyvsp[0].nval); } } #line 2703 "sieve/sieve.c" /* yacc.c:1646 */ break; case 88: #line 755 "sieve/sieve.y" /* yacc.c:1646 */ { (yyval.htag) = (yyvsp[-2].htag); if ((yyval.htag)->comptag != -1) { yyerror(parse_script, "duplicate comparator type tag"); YYERROR; } else { (yyval.htag)->comptag = (yyvsp[-1].nval); (yyval.htag)->relation = verify_relat(parse_script, (yyvsp[0].sval)); if ((yyval.htag)->relation==-1) {YYERROR; /*vr called yyerror()*/ } } } #line 2716 "sieve/sieve.c" /* yacc.c:1646 */ break; case 89: #line 763 "sieve/sieve.y" /* yacc.c:1646 */ { (yyval.htag) = (yyvsp[-2].htag); if ((yyval.htag)->comparator != NULL) { yyerror(parse_script, "duplicate comparator tag"); YYERROR; } else if (!strcmp((yyvsp[0].sval), "i;ascii-numeric") && !parse_script->support.i_ascii_numeric) { yyerror(parse_script, "comparator-i;ascii-numeric MUST be enabled with \"require\""); YYERROR; } else { (yyval.htag)->comparator = (yyvsp[0].sval); } } #line 2729 "sieve/sieve.c" /* yacc.c:1646 */ break; case 90: #line 771 "sieve/sieve.y" /* yacc.c:1646 */ { (yyval.htag) = (yyvsp[-2].htag); if (!parse_script->support.index) { yyerror(parse_script, "index MUST be enabled with \"require\""); YYERROR; } if ((yyval.htag)->index != 0) { yyerror(parse_script, "duplicate index argument"); YYERROR; } if ((yyvsp[0].nval) <= 0) { yyerror(parse_script, "invalid index value"); YYERROR; } else { (yyval.htag)->index = (yyvsp[0].nval); } } #line 2743 "sieve/sieve.c" /* yacc.c:1646 */ break; case 91: #line 780 "sieve/sieve.y" /* yacc.c:1646 */ { (yyval.htag) = (yyvsp[-1].htag); if (!parse_script->support.index) { yyerror(parse_script, "index MUST be enabled with \"require\""); YYERROR; } if ((yyval.htag)->index == 0) { yyerror(parse_script, "index argument is required"); YYERROR; } else if ((yyval.htag)->index < 0) { yyerror(parse_script, "duplicate last argument"); YYERROR; } else { (yyval.htag)->index *= -1; } } #line 2757 "sieve/sieve.c" /* yacc.c:1646 */ break; case 92: #line 791 "sieve/sieve.y" /* yacc.c:1646 */ { (yyval.btag) = new_btags(); } #line 2763 "sieve/sieve.c" /* yacc.c:1646 */ break; case 93: #line 792 "sieve/sieve.y" /* yacc.c:1646 */ { (yyval.btag) = (yyvsp[-1].btag); if ((yyval.btag)->transform != -1) { yyerror(parse_script, "duplicate or conflicting transform tag"); YYERROR; } else { (yyval.btag)->transform = RAW; } } #line 2773 "sieve/sieve.c" /* yacc.c:1646 */ break; case 94: #line 797 "sieve/sieve.y" /* yacc.c:1646 */ { (yyval.btag) = (yyvsp[-1].btag); if ((yyval.btag)->transform != -1) { yyerror(parse_script, "duplicate or conflicting transform tag"); YYERROR; } else { (yyval.btag)->transform = TEXT; } } #line 2783 "sieve/sieve.c" /* yacc.c:1646 */ break; case 95: #line 802 "sieve/sieve.y" /* yacc.c:1646 */ { (yyval.btag) = (yyvsp[-2].btag); if ((yyval.btag)->transform != -1) { yyerror(parse_script, "duplicate or conflicting transform tag"); YYERROR; } else { (yyval.btag)->transform = CONTENT; (yyval.btag)->content_types = (yyvsp[0].sl); } } #line 2796 "sieve/sieve.c" /* yacc.c:1646 */ break; case 96: #line 810 "sieve/sieve.y" /* yacc.c:1646 */ { (yyval.btag) = (yyvsp[-1].btag); if ((yyval.btag)->comptag != -1) { yyerror(parse_script, "duplicate comparator type tag"); YYERROR; } else { (yyval.btag)->comptag = (yyvsp[0].nval); } } #line 2805 "sieve/sieve.c" /* yacc.c:1646 */ break; case 97: #line 814 "sieve/sieve.y" /* yacc.c:1646 */ { (yyval.btag) = (yyvsp[-2].btag); if ((yyval.btag)->comptag != -1) { yyerror(parse_script, "duplicate comparator type tag"); YYERROR; } else { (yyval.btag)->comptag = (yyvsp[-1].nval); (yyval.btag)->relation = verify_relat(parse_script, (yyvsp[0].sval)); if ((yyval.btag)->relation==-1) {YYERROR; /*vr called yyerror()*/ } } } #line 2818 "sieve/sieve.c" /* yacc.c:1646 */ break; case 98: #line 822 "sieve/sieve.y" /* yacc.c:1646 */ { (yyval.btag) = (yyvsp[-2].btag); if ((yyval.btag)->comparator != NULL) { yyerror(parse_script, "duplicate comparator tag"); YYERROR; } else if (!strcmp((yyvsp[0].sval), "i;ascii-numeric") && !parse_script->support.i_ascii_numeric) { yyerror(parse_script, "comparator-i;ascii-numeric MUST be enabled with \"require\""); YYERROR; } else { (yyval.btag)->comparator = (yyvsp[0].sval); } } #line 2831 "sieve/sieve.c" /* yacc.c:1646 */ break; case 99: #line 832 "sieve/sieve.y" /* yacc.c:1646 */ { (yyval.dttag) = new_dttags(); } #line 2837 "sieve/sieve.c" /* yacc.c:1646 */ break; case 100: #line 833 "sieve/sieve.y" /* yacc.c:1646 */ { (yyval.dttag) = (yyvsp[-1].dttag); if ((yyval.dttag)->comptag != -1) { yyerror(parse_script, "duplicate comparator type tag"); YYERROR; } else { (yyval.dttag)->comptag = (yyvsp[0].nval); } } #line 2846 "sieve/sieve.c" /* yacc.c:1646 */ break; case 101: #line 838 "sieve/sieve.y" /* yacc.c:1646 */ { (yyval.dttag) = (yyvsp[-2].dttag); if ((yyval.dttag)->comptag != -1) { yyerror(parse_script, "duplicate comparator type tag"); YYERROR; } else { (yyval.dttag)->comptag = (yyvsp[-1].nval); (yyval.dttag)->relation = verify_relat(parse_script, (yyvsp[0].sval)); if ((yyval.dttag)->relation == -1) { YYERROR; /*vr called yyerror()*/ } } } #line 2859 "sieve/sieve.c" /* yacc.c:1646 */ break; case 102: #line 847 "sieve/sieve.y" /* yacc.c:1646 */ { (yyval.dttag) = (yyvsp[-2].dttag); if ((yyval.dttag)->comparator != NULL) { yyerror(parse_script, "duplicate comparator tag"); YYERROR; } else if (!strcmp((yyvsp[0].sval), "i;ascii-numeric") && !parse_script->support.i_ascii_numeric) { yyerror(parse_script, "comparator-i;ascii-numeric MUST be enabled with \"require\""); YYERROR; } else { (yyval.dttag)->comparator = (yyvsp[0].sval); } } #line 2871 "sieve/sieve.c" /* yacc.c:1646 */ break; case 103: #line 855 "sieve/sieve.y" /* yacc.c:1646 */ { (yyval.dttag) = (yyvsp[-2].dttag); if (!parse_script->support.index) { yyerror(parse_script, "index MUST be enabled with \"require\""); YYERROR; } if ((yyval.dttag)->index != 0) { yyerror(parse_script, "duplicate index argument"); YYERROR; } if ((yyvsp[0].nval) <= 0) { yyerror(parse_script, "invalid index value"); YYERROR; } else { (yyval.dttag)->index = (yyvsp[0].nval); } } #line 2885 "sieve/sieve.c" /* yacc.c:1646 */ break; case 104: #line 865 "sieve/sieve.y" /* yacc.c:1646 */ { (yyval.dttag) = (yyvsp[-1].dttag); if (!parse_script->support.index) { yyerror(parse_script, "index MUST be enabled with \"require\""); YYERROR; } if ((yyval.dttag)->index == 0) { yyerror(parse_script, "index argument is required"); YYERROR; } else if ((yyval.dttag)->index < 0) { yyerror(parse_script, "duplicate last argument"); YYERROR; } else { (yyval.dttag)->index *= -1; } } #line 2899 "sieve/sieve.c" /* yacc.c:1646 */ break; case 105: #line 875 "sieve/sieve.y" /* yacc.c:1646 */ { (yyval.dttag) = (yyvsp[-2].dttag); if ((yyval.dttag)->zonetag != -1) { yyerror(parse_script, "duplicate zone tag"); YYERROR; } else { if (verify_zone(parse_script, (yyvsp[0].sval)) == -1) { YYERROR; /*vr called yyerror()*/ } else { (yyval.dttag)->zone = (yyvsp[0].sval); (yyval.dttag)->zonetag = ZONE; } } } #line 2912 "sieve/sieve.c" /* yacc.c:1646 */ break; case 106: #line 884 "sieve/sieve.y" /* yacc.c:1646 */ { (yyval.dttag) = (yyvsp[-1].dttag); if ((yyval.dttag)->zonetag != -1) { yyerror(parse_script, "duplicate zone tag"); YYERROR; } else { (yyval.dttag)->zonetag = ORIGINALZONE; } } #line 2921 "sieve/sieve.c" /* yacc.c:1646 */ break; case 107: #line 890 "sieve/sieve.y" /* yacc.c:1646 */ { (yyval.nval) = ALL; } #line 2927 "sieve/sieve.c" /* yacc.c:1646 */ break; case 108: #line 891 "sieve/sieve.y" /* yacc.c:1646 */ { (yyval.nval) = LOCALPART; } #line 2933 "sieve/sieve.c" /* yacc.c:1646 */ break; case 109: #line 892 "sieve/sieve.y" /* yacc.c:1646 */ { (yyval.nval) = DOMAIN; } #line 2939 "sieve/sieve.c" /* yacc.c:1646 */ break; case 110: #line 893 "sieve/sieve.y" /* yacc.c:1646 */ { if (!parse_script->support.subaddress) { yyerror(parse_script, "subaddress MUST be enabled with \"require\""); YYERROR; } (yyval.nval) = USER; } #line 2949 "sieve/sieve.c" /* yacc.c:1646 */ break; case 111: #line 898 "sieve/sieve.y" /* yacc.c:1646 */ { if (!parse_script->support.subaddress) { yyerror(parse_script, "subaddress MUST be enabled with \"require\""); YYERROR; } (yyval.nval) = DETAIL; } #line 2959 "sieve/sieve.c" /* yacc.c:1646 */ break; case 112: #line 904 "sieve/sieve.y" /* yacc.c:1646 */ { (yyval.nval) = IS; } #line 2965 "sieve/sieve.c" /* yacc.c:1646 */ break; case 113: #line 905 "sieve/sieve.y" /* yacc.c:1646 */ { (yyval.nval) = CONTAINS; } #line 2971 "sieve/sieve.c" /* yacc.c:1646 */ break; case 114: #line 906 "sieve/sieve.y" /* yacc.c:1646 */ { (yyval.nval) = MATCHES; } #line 2977 "sieve/sieve.c" /* yacc.c:1646 */ break; case 115: #line 907 "sieve/sieve.y" /* yacc.c:1646 */ { if (!parse_script->support.regex) { yyerror(parse_script, "regex MUST be enabled with \"require\""); YYERROR; } (yyval.nval) = REGEX; } #line 2987 "sieve/sieve.c" /* yacc.c:1646 */ break; case 116: #line 914 "sieve/sieve.y" /* yacc.c:1646 */ { if (!parse_script->support.relational) { yyerror(parse_script, "relational MUST be enabled with \"require\""); YYERROR; } (yyval.nval) = COUNT; } #line 2997 "sieve/sieve.c" /* yacc.c:1646 */ break; case 117: #line 919 "sieve/sieve.y" /* yacc.c:1646 */ { if (!parse_script->support.relational) { yyerror(parse_script, "relational MUST be enabled with \"require\""); YYERROR; } (yyval.nval) = VALUE; } #line 3007 "sieve/sieve.c" /* yacc.c:1646 */ break; case 118: #line 927 "sieve/sieve.y" /* yacc.c:1646 */ { (yyval.nval) = OVER; } #line 3013 "sieve/sieve.c" /* yacc.c:1646 */ break; case 119: #line 928 "sieve/sieve.y" /* yacc.c:1646 */ { (yyval.nval) = UNDER; } #line 3019 "sieve/sieve.c" /* yacc.c:1646 */ break; case 120: #line 931 "sieve/sieve.y" /* yacc.c:1646 */ { if (!parse_script->support.copy) { yyerror(parse_script, "copy MUST be enabled with \"require\""); YYERROR; } (yyval.nval) = 1; } #line 3029 "sieve/sieve.c" /* yacc.c:1646 */ break; case 121: #line 938 "sieve/sieve.y" /* yacc.c:1646 */ { (yyval.ftag) = new_ftags(); } #line 3035 "sieve/sieve.c" /* yacc.c:1646 */ break; case 122: #line 939 "sieve/sieve.y" /* yacc.c:1646 */ { (yyval.ftag) = (yyvsp[-1].ftag); if ((yyval.ftag)->copy) { yyerror(parse_script, "duplicate copy tag"); YYERROR; } else { (yyval.ftag)->copy = (yyvsp[0].nval); } } #line 3044 "sieve/sieve.c" /* yacc.c:1646 */ break; case 123: #line 943 "sieve/sieve.y" /* yacc.c:1646 */ { if (!parse_script->support.imap4flags) { yyerror(parse_script, "imap4flags MUST be enabled with \"require\""); YYERROR; } (yyval.ftag) = (yyvsp[-2].ftag); if ((yyval.ftag)->flags != NULL) { yyerror(parse_script, "duplicate flags tag"); YYERROR; } else { verify_flaglist((yyvsp[0].sl)); if(!(yyvsp[0].sl)->count) { strarray_add((yyvsp[0].sl), ""); } (yyval.ftag)->flags = (yyvsp[0].sl); } } #line 3063 "sieve/sieve.c" /* yacc.c:1646 */ break; case 124: #line 959 "sieve/sieve.y" /* yacc.c:1646 */ { (yyval.nval) = 0; } #line 3069 "sieve/sieve.c" /* yacc.c:1646 */ break; case 125: #line 960 "sieve/sieve.y" /* yacc.c:1646 */ { (yyval.nval) = (yyvsp[-1].nval); if ((yyval.nval)) { yyerror(parse_script, "duplicate copy tag"); YYERROR; } else { (yyval.nval) = (yyvsp[0].nval); } } #line 3078 "sieve/sieve.c" /* yacc.c:1646 */ break; case 126: #line 966 "sieve/sieve.y" /* yacc.c:1646 */ { (yyval.testl) = (yyvsp[-1].testl); } #line 3084 "sieve/sieve.c" /* yacc.c:1646 */ break; case 127: #line 969 "sieve/sieve.y" /* yacc.c:1646 */ { (yyval.testl) = new_testlist((yyvsp[0].test), NULL); } #line 3090 "sieve/sieve.c" /* yacc.c:1646 */ break; case 128: #line 970 "sieve/sieve.y" /* yacc.c:1646 */ { (yyval.testl) = new_testlist((yyvsp[-2].test), (yyvsp[0].testl)); } #line 3096 "sieve/sieve.c" /* yacc.c:1646 */ break; #line 3100 "sieve/sieve.c" /* yacc.c:1646 */ default: break; } /* User semantic actions sometimes alter yychar, and that requires that yytoken be updated with the new translation. We take the approach of translating immediately before every use of yytoken. One alternative is translating here after every semantic action, but that translation would be missed if the semantic action invokes YYABORT, YYACCEPT, or YYERROR immediately after altering yychar or if it invokes YYBACKUP. In the case of YYABORT or YYACCEPT, an incorrect destructor might then be invoked immediately. In the case of YYERROR or YYBACKUP, subsequent parser actions might lead to an incorrect destructor call or verbose syntax error message before the lookahead is translated. */ YY_SYMBOL_PRINT ("-> $$ =", yyr1[yyn], &yyval, &yyloc); YYPOPSTACK (yylen); yylen = 0; YY_STACK_PRINT (yyss, yyssp); *++yyvsp = yyval; /* Now 'shift' the result of the reduction. Determine what state that goes to, based on the state we popped back to and the rule number reduced by. */ yyn = yyr1[yyn]; yystate = yypgoto[yyn - YYNTOKENS] + *yyssp; if (0 <= yystate && yystate <= YYLAST && yycheck[yystate] == *yyssp) yystate = yytable[yystate]; else yystate = yydefgoto[yyn - YYNTOKENS]; goto yynewstate; /*--------------------------------------. | yyerrlab -- here on detecting error. | `--------------------------------------*/ yyerrlab: /* Make sure we have latest lookahead translation. See comments at user semantic actions for why this is necessary. */ yytoken = yychar == YYEMPTY ? YYEMPTY : YYTRANSLATE (yychar); /* If not already recovering from an error, report this error. */ if (!yyerrstatus) { ++yynerrs; #if ! YYERROR_VERBOSE yyerror (parse_script, YY_("syntax error")); #else # define YYSYNTAX_ERROR yysyntax_error (&yymsg_alloc, &yymsg, \ yyssp, yytoken) { char const *yymsgp = YY_("syntax error"); int yysyntax_error_status; yysyntax_error_status = YYSYNTAX_ERROR; if (yysyntax_error_status == 0) yymsgp = yymsg; else if (yysyntax_error_status == 1) { if (yymsg != yymsgbuf) YYSTACK_FREE (yymsg); yymsg = (char *) YYSTACK_ALLOC (yymsg_alloc); if (!yymsg) { yymsg = yymsgbuf; yymsg_alloc = sizeof yymsgbuf; yysyntax_error_status = 2; } else { yysyntax_error_status = YYSYNTAX_ERROR; yymsgp = yymsg; } } yyerror (parse_script, yymsgp); if (yysyntax_error_status == 2) goto yyexhaustedlab; } # undef YYSYNTAX_ERROR #endif } if (yyerrstatus == 3) { /* If just tried and failed to reuse lookahead token after an error, discard it. */ if (yychar <= YYEOF) { /* Return failure if at end of input. */ if (yychar == YYEOF) YYABORT; } else { yydestruct ("Error: discarding", yytoken, &yylval, parse_script); yychar = YYEMPTY; } } /* Else will try to reuse lookahead token after shifting the error token. */ goto yyerrlab1; /*---------------------------------------------------. | yyerrorlab -- error raised explicitly by YYERROR. | `---------------------------------------------------*/ yyerrorlab: /* Pacify compilers like GCC when the user code never invokes YYERROR and the label yyerrorlab therefore never appears in user code. */ if (/*CONSTCOND*/ 0) goto yyerrorlab; /* Do not reclaim the symbols of the rule whose action triggered this YYERROR. */ YYPOPSTACK (yylen); yylen = 0; YY_STACK_PRINT (yyss, yyssp); yystate = *yyssp; goto yyerrlab1; /*-------------------------------------------------------------. | yyerrlab1 -- common code for both syntax error and YYERROR. | `-------------------------------------------------------------*/ yyerrlab1: yyerrstatus = 3; /* Each real token shifted decrements this. */ for (;;) { yyn = yypact[yystate]; if (!yypact_value_is_default (yyn)) { yyn += YYTERROR; if (0 <= yyn && yyn <= YYLAST && yycheck[yyn] == YYTERROR) { yyn = yytable[yyn]; if (0 < yyn) break; } } /* Pop the current state because it cannot handle the error token. */ if (yyssp == yyss) YYABORT; yydestruct ("Error: popping", yystos[yystate], yyvsp, parse_script); YYPOPSTACK (1); yystate = *yyssp; YY_STACK_PRINT (yyss, yyssp); } YY_IGNORE_MAYBE_UNINITIALIZED_BEGIN *++yyvsp = yylval; YY_IGNORE_MAYBE_UNINITIALIZED_END /* Shift the error token. */ YY_SYMBOL_PRINT ("Shifting", yystos[yyn], yyvsp, yylsp); yystate = yyn; goto yynewstate; /*-------------------------------------. | yyacceptlab -- YYACCEPT comes here. | `-------------------------------------*/ yyacceptlab: yyresult = 0; goto yyreturn; /*-----------------------------------. | yyabortlab -- YYABORT comes here. | `-----------------------------------*/ yyabortlab: yyresult = 1; goto yyreturn; #if !defined yyoverflow || YYERROR_VERBOSE /*-------------------------------------------------. | yyexhaustedlab -- memory exhaustion comes here. | `-------------------------------------------------*/ yyexhaustedlab: yyerror (parse_script, YY_("memory exhausted")); yyresult = 2; /* Fall through. */ #endif yyreturn: if (yychar != YYEMPTY) { /* Make sure we have latest lookahead translation. See comments at user semantic actions for why this is necessary. */ yytoken = YYTRANSLATE (yychar); yydestruct ("Cleanup: discarding lookahead", yytoken, &yylval, parse_script); } /* Do not reclaim the symbols of the rule whose action triggered this YYABORT or YYACCEPT. */ YYPOPSTACK (yylen); YY_STACK_PRINT (yyss, yyssp); while (yyssp != yyss) { yydestruct ("Cleanup: popping", yystos[*yyssp], yyvsp, parse_script); YYPOPSTACK (1); } #ifndef yyoverflow if (yyss != yyssa) YYSTACK_FREE (yyss); #endif #if YYERROR_VERBOSE if (yymsg != yymsgbuf) YYSTACK_FREE (yymsg); #endif return yyresult; } #line 973 "sieve/sieve.y" /* yacc.c:1906 */ void yyerror(sieve_script_t *parse_script, const char *msg) { parse_script->err++; if (parse_script->interp.err) { parse_script->interp.err(sievelineno, msg, parse_script->interp.interp_context, parse_script->script_context); } } static char *check_reqs(sieve_script_t *parse_script, strarray_t *sa) { char *s; struct buf errs = BUF_INITIALIZER; char *res; while ((s = strarray_shift(sa))) { if (!script_require(parse_script, s)) { if (!errs.len) buf_printf(&errs, "Unsupported feature(s) in \"require\": \"%s\"", s); else buf_printf(&errs, ", \"%s\"", s); } free(s); } strarray_free(sa); res = buf_release(&errs); if (!res[0]) { free(res); return NULL; } return res; } static test_t *build_address(int t, struct aetags *ae, strarray_t *sl, strarray_t *pl) { test_t *ret = new_test(t); /* can be either ADDRESS or ENVELOPE */ assert((t == ADDRESS) || (t == ENVELOPE)); if (ret) { ret->u.ae.index = ae->index; ret->u.ae.comptag = ae->comptag; ret->u.ae.relation=ae->relation; ret->u.ae.comparator=xstrdup(ae->comparator); ret->u.ae.sl = sl; ret->u.ae.pl = pl; ret->u.ae.addrpart = ae->addrtag; free_aetags(ae); } return ret; } static test_t *build_header(int t, struct htags *h, strarray_t *sl, strarray_t *pl) { test_t *ret = new_test(t); /* can be HEADER or HASFLAG */ assert((t == HEADER) || (t == HASFLAG)); if (ret) { ret->u.h.index = h->index; ret->u.h.comptag = h->comptag; ret->u.h.relation=h->relation; ret->u.h.comparator=xstrdup(h->comparator); ret->u.h.sl = sl; ret->u.h.pl = pl; free_htags(h); } return ret; } static test_t *build_hasflag(int t, struct htags *h, strarray_t *pl) { return build_header(t,h,NULL,pl); } static test_t *build_body(int t, struct btags *b, strarray_t *pl) { test_t *ret = new_test(t); /* can be BODY */ assert(t == BODY); if (ret) { ret->u.b.comptag = b->comptag; ret->u.b.relation = b->relation; ret->u.b.comparator = xstrdup(b->comparator); ret->u.b.transform = b->transform; ret->u.b.offset = b->offset; ret->u.b.content_types = b->content_types; b->content_types = NULL; ret->u.b.pl = pl; free_btags(b); } return ret; } static commandlist_t *build_vacation(int t, struct vtags *v, char *reason) { commandlist_t *ret = new_command(t); assert(t == VACATION); if (ret) { ret->u.v.subject = v->subject; v->subject = NULL; ret->u.v.from = v->from; v->from = NULL; ret->u.v.handle = v->handle; v->handle = NULL; ret->u.v.seconds = v->seconds; ret->u.v.mime = v->mime; ret->u.v.addresses = v->addresses; v->addresses = NULL; free_vtags(v); ret->u.v.message = reason; } return ret; } static commandlist_t *build_notify(int t, struct ntags *n) { commandlist_t *ret = new_command(t); assert(t == NOTIFY); if (ret) { ret->u.n.method = n->method; n->method = NULL; ret->u.n.id = n->id; n->id = NULL; ret->u.n.options = n->options; n->options = NULL; ret->u.n.priority = n->priority; ret->u.n.message = n->message; n->message = NULL; free_ntags(n); } return ret; } static commandlist_t *build_denotify(int t, struct dtags *d) { commandlist_t *ret = new_command(t); assert(t == DENOTIFY); if (ret) { ret->u.d.comptag = d->comptag; ret->u.d.relation=d->relation; ret->u.d.pattern = d->pattern; d->pattern = NULL; ret->u.d.priority = d->priority; free_dtags(d); } return ret; } static commandlist_t *build_keep(int t, struct ftags *f) { commandlist_t *ret = new_command(t); assert(t == KEEP); if (ret) { ret->u.k.copy = f->copy; ret->u.k.flags = f->flags; f->flags = NULL; free_ftags(f); } return ret; } static commandlist_t *build_fileinto(int t, struct ftags *f, char *folder) { commandlist_t *ret = new_command(t); assert(t == FILEINTO); if (ret) { ret->u.f.copy = f->copy; ret->u.f.flags = f->flags; f->flags = NULL; if (config_getswitch(IMAPOPT_SIEVE_UTF8FILEINTO)) { ret->u.f.folder = xmalloc(5 * strlen(folder) + 1); UTF8_to_mUTF7(ret->u.f.folder, folder); free(folder); } else { ret->u.f.folder = folder; } free_ftags(f); } return ret; } static commandlist_t *build_redirect(int t, int copy, char *address) { commandlist_t *ret = new_command(t); assert(t == REDIRECT); if (ret) { ret->u.r.copy = copy; ret->u.r.address = address; } return ret; } static commandlist_t *build_include(int t, struct itags *i, char* script) { commandlist_t *ret = new_command(t); assert(t == INCLUDE); if (i->location == -1) i->location = PERSONAL; if (i->once == -1) i->once = 0; if (i->optional == -1) i->optional = 0; if (ret) { ret->u.inc.location = i->location; ret->u.inc.once = i->once; ret->u.inc.optional = i->optional; ret->u.inc.script = script; free(i); } return ret; } static test_t *build_date(int t, struct dttags *dt, char *hn, strarray_t *kl) { test_t *ret = new_test(t); assert(t == DATE || t == CURRENTDATE); if (ret) { ret->u.dt.index = dt->index; ret->u.dt.zone = (dt->zone ? xstrdup(dt->zone) : NULL); ret->u.dt.comparator = xstrdup(dt->comparator); ret->u.dt.zonetag = dt->zonetag; ret->u.dt.comptag = dt->comptag; ret->u.dt.relation = dt->relation; ret->u.dt.date_part = dt->date_part; ret->u.dt.header_name = (hn ? xstrdup(hn) : NULL); ret->u.dt.kl = kl; free_dttags(dt); } return ret; } static struct aetags *new_aetags(void) { struct aetags *r = (struct aetags *) xmalloc(sizeof(struct aetags)); r->index = 0; r->addrtag = r->comptag = r->relation=-1; r->comparator=NULL; return r; } static struct aetags *canon_aetags(struct aetags *ae) { if (ae->addrtag == -1) { ae->addrtag = ALL; } if (ae->comparator == NULL) { ae->comparator = xstrdup("i;ascii-casemap"); } if (ae->comptag == -1) { ae->comptag = IS; } return ae; } static void free_aetags(struct aetags *ae) { free(ae->comparator); free(ae); } static struct htags *new_htags(void) { struct htags *r = (struct htags *) xmalloc(sizeof(struct htags)); r->index = 0; r->comptag = r->relation= -1; r->comparator = NULL; return r; } static struct htags *canon_htags(struct htags *h) { if (h->comparator == NULL) { h->comparator = xstrdup("i;ascii-casemap"); } if (h->comptag == -1) { h->comptag = IS; } return h; } static void free_htags(struct htags *h) { free(h->comparator); free(h); } static struct btags *new_btags(void) { struct btags *r = (struct btags *) xmalloc(sizeof(struct btags)); r->transform = r->offset = r->comptag = r->relation = -1; r->content_types = NULL; r->comparator = NULL; return r; } static struct btags *canon_btags(struct btags *b) { if (b->transform == -1) { b->transform = TEXT; } if (b->content_types == NULL) { b->content_types = strarray_new(); if (b->transform == RAW) { strarray_append(b->content_types, ""); } else { strarray_append(b->content_types, "text"); } } if (b->offset == -1) { b->offset = 0; } if (b->comparator == NULL) { b->comparator = xstrdup("i;ascii-casemap"); } if (b->comptag == -1) { b->comptag = IS; } return b; } static void free_btags(struct btags *b) { if (b->content_types) { strarray_free(b->content_types); } free(b->comparator); free(b); } static struct vtags *new_vtags(void) { struct vtags *r = (struct vtags *) xmalloc(sizeof(struct vtags)); r->seconds = -1; r->addresses = NULL; r->subject = NULL; r->from = NULL; r->handle = NULL; r->mime = -1; return r; } static struct vtags *canon_vtags(sieve_script_t *parse_script, struct vtags *v) { assert(parse_script->interp.vacation != NULL); if (v->seconds == -1) { v->seconds = 7 * DAY2SEC; } if (v->seconds < parse_script->interp.vacation->min_response) { v->seconds = parse_script->interp.vacation->min_response; } if (v->seconds > parse_script->interp.vacation->max_response) { v->seconds = parse_script->interp.vacation->max_response; } if (v->mime == -1) { v->mime = 0; } return v; } static void free_vtags(struct vtags *v) { if (v->addresses) { strarray_free(v->addresses); } if (v->subject) { free(v->subject); } if (v->from) { free(v->from); } if (v->handle) { free(v->handle); } free(v); } static struct itags *new_itags() { struct itags *r = (struct itags *) xmalloc(sizeof(struct itags)); r->once = -1; r->location = -1; r->optional = -1; return r; } static struct dttags *new_dttags(void) { struct dttags *dt = (struct dttags *) xmalloc(sizeof(struct dttags)); dt->comptag = -1; dt->index = 0; dt->zonetag = -1; dt->relation = -1; dt->comparator = NULL; dt->zone = NULL; dt->date_part = -1; return dt; } static struct dttags *canon_dttags(struct dttags *dt) { char zone[6]; int gmoffset; int hours; int minutes; struct tm tm; time_t t; if (dt->comparator == NULL) { dt->comparator = xstrdup("i;ascii-casemap"); } if (dt->index == 0) { dt->index = 1; } if (dt->zonetag == -1) { t = time(NULL); localtime_r(&t, &tm); gmoffset = gmtoff_of(&tm, t) / 60; hours = abs(gmoffset) / 60; minutes = abs(gmoffset) % 60; snprintf(zone, 6, "%c%02d%02d", (gmoffset >= 0 ? '+' : '-'), hours, minutes); dt->zone = xstrdup(zone); dt->zonetag = ZONE; } if (dt->comptag == -1) { dt->comptag = IS; } return dt; } static void free_dttags(struct dttags *dt) { free(dt->comparator); free(dt->zone); free(dt); } static struct ntags *new_ntags(void) { struct ntags *r = (struct ntags *) xmalloc(sizeof(struct ntags)); r->method = NULL; r->id = NULL; r->options = NULL; r->priority = -1; r->message = NULL; return r; } static struct ntags *canon_ntags(struct ntags *n) { if (n->priority == -1) { n->priority = NORMAL; } if (n->message == NULL) { n->message = xstrdup("$from$: $subject$"); } if (n->method == NULL) { n->method = xstrdup("default"); } return n; } static struct dtags *canon_dtags(struct dtags *d) { if (d->priority == -1) { d->priority = ANY; } if (d->comptag == -1) { d->comptag = ANY; } return d; } static void free_ntags(struct ntags *n) { if (n->method) { free(n->method); } if (n->id) { free(n->id); } if (n->options) { strarray_free(n->options); } if (n->message) { free(n->message); } free(n); } static struct dtags *new_dtags(void) { struct dtags *r = (struct dtags *) xmalloc(sizeof(struct dtags)); r->comptag = r->priority= r->relation = -1; r->pattern = NULL; return r; } static void free_dtags(struct dtags *d) { if (d->pattern) free(d->pattern); free(d); } static struct ftags *new_ftags(void) { struct ftags *f = (struct ftags *) xmalloc(sizeof(struct ftags)); f->copy = 0; f->flags = NULL; return f; } static struct ftags *canon_ftags(struct ftags *f) { return f; } static void free_ftags(struct ftags *f) { if (f->flags) { strarray_free(f->flags); } free(f); } static int verify_stringlist(sieve_script_t *parse_script, strarray_t *sa, int (*verify)(sieve_script_t*, char *)) { int i; for (i = 0 ; i < sa->count ; i++) if (!verify(parse_script, sa->data[i])) return 0; return 1; } static int verify_address(sieve_script_t *parse_script, char *s) { parse_script->addrerr[0] = '\0'; /* paranoia */ YY_BUFFER_STATE buffer = addr_scan_string(s); if (addrparse(parse_script)) { snprintf(parse_script->sieveerr, ERR_BUF_SIZE, "address '%s': %s", s, parse_script->addrerr); yyerror(parse_script, parse_script->sieveerr); addr_delete_buffer(buffer); return 0; } addr_delete_buffer(buffer); return 1; } static int verify_mailbox(sieve_script_t *parse_script, char *s) { if (!verify_utf8(parse_script, s)) return 0; /* xxx if not a mailbox, call yyerror */ return 1; } static int verify_header(sieve_script_t *parse_script, char *hdr) { char *h = hdr; while (*h) { /* field-name = 1*ftext ftext = %d33-57 / %d59-126 ; Any character except ; controls, SP, and ; ":". */ if (!((*h >= 33 && *h <= 57) || (*h >= 59 && *h <= 126))) { snprintf(parse_script->sieveerr, ERR_BUF_SIZE, "header '%s': not a valid header", hdr); yyerror(parse_script, parse_script->sieveerr); return 0; } h++; } return 1; } static int verify_addrheader(sieve_script_t *parse_script, char *hdr) { const char **h, *hdrs[] = { "from", "sender", "reply-to", /* RFC2822 originator fields */ "to", "cc", "bcc", /* RFC2822 destination fields */ "resent-from", "resent-sender", /* RFC2822 resent fields */ "resent-to", "resent-cc", "resent-bcc", "return-path", /* RFC2822 trace fields */ "disposition-notification-to", /* RFC2298 MDN request fields */ "delivered-to", /* non-standard (loop detection) */ "approved", /* RFC1036 moderator/control fields */ NULL }; if (!config_getswitch(IMAPOPT_RFC3028_STRICT)) return verify_header(parse_script, hdr); for (lcase(hdr), h = hdrs; *h; h++) { if (!strcmp(*h, hdr)) return 1; } snprintf(parse_script->sieveerr, ERR_BUF_SIZE, "header '%s': not a valid header for an address test", hdr); yyerror(parse_script, parse_script->sieveerr); return 0; } static int verify_envelope(sieve_script_t *parse_script, char *env) { lcase(env); if (!config_getswitch(IMAPOPT_RFC3028_STRICT) || !strcmp(env, "from") || !strcmp(env, "to") || !strcmp(env, "auth")) { return 1; } snprintf(parse_script->sieveerr, ERR_BUF_SIZE, "env-part '%s': not a valid part for an envelope test", env); yyerror(parse_script, parse_script->sieveerr); return 0; } static int verify_relat(sieve_script_t *parse_script, char *r) {/* this really should have been a token to begin with.*/ lcase(r); if (!strcmp(r, "gt")) {return GT;} else if (!strcmp(r, "ge")) {return GE;} else if (!strcmp(r, "lt")) {return LT;} else if (!strcmp(r, "le")) {return LE;} else if (!strcmp(r, "ne")) {return NE;} else if (!strcmp(r, "eq")) {return EQ;} else{ snprintf(parse_script->sieveerr, ERR_BUF_SIZE, "flag '%s': not a valid relational operation", r); yyerror(parse_script, parse_script->sieveerr); return -1; } } static int verify_zone(sieve_script_t *parse_script, char *tz) { int valid = 0; unsigned hours; unsigned minutes; char sign; if (sscanf(tz, "%c%02u%02u", &sign, &hours, &minutes) != 3) { valid |= -1; } // test sign switch (sign) { case '+': case '-': break; default: valid |= -1; break; } // test minutes if (minutes > 59) { valid |= -1; } if (valid != 0) { snprintf(parse_script->sieveerr, ERR_BUF_SIZE, "flag '%s': not a valid timezone offset", tz); yyerror(parse_script, parse_script->sieveerr); } return valid; } static int verify_date_part(sieve_script_t *parse_script, char *dp) { lcase(dp); if (!strcmp(dp, "year")) { return YEAR; } else if (!strcmp(dp, "month")) { return MONTH; } else if (!strcmp(dp, "day")) { return DAY; } else if (!strcmp(dp, "date")) { return DATE; } else if (!strcmp(dp, "julian")) { return JULIAN; } else if (!strcmp(dp, "hour")) { return HOUR; } else if (!strcmp(dp, "minute")) { return MINUTE; } else if (!strcmp(dp, "second")) { return SECOND; } else if (!strcmp(dp, "time")) { return TIME; } else if (!strcmp(dp, "iso8601")) { return ISO8601; } else if (!strcmp(dp, "std11")) { return STD11; } else if (!strcmp(dp, "zone")) { return ZONE; } else if (!strcmp(dp, "weekday")) { return WEEKDAY; } else { snprintf(parse_script->sieveerr, ERR_BUF_SIZE, "flag '%s': not a valid relational operation", dp); yyerror(parse_script, parse_script->sieveerr); } return -1; } #ifdef ENABLE_REGEX static int verify_regex(sieve_script_t *parse_script, char *s, int cflags) { int ret; regex_t *reg = (regex_t *) xmalloc(sizeof(regex_t)); #ifdef HAVE_PCREPOSIX_H /* support UTF8 comparisons */ cflags |= REG_UTF8; #endif if ((ret = regcomp(reg, s, cflags)) != 0) { (void) regerror(ret, reg, parse_script->sieveerr, ERR_BUF_SIZE); yyerror(parse_script, parse_script->sieveerr); free(reg); return 0; } free(reg); return 1; } static int verify_regexs(sieve_script_t *parse_script, const strarray_t *sa, char *comp) { int i; int cflags = REG_EXTENDED | REG_NOSUB; if (!strcmp(comp, "i;ascii-casemap")) { cflags |= REG_ICASE; } for (i = 0 ; i < sa->count ; i++) { if ((verify_regex(parse_script, sa->data[i], cflags)) == 0) return 0; } return 1; } #endif /* * Valid UTF-8 check (from RFC 2640 Annex B.1) * * The following routine checks if a byte sequence is valid UTF-8. This * is done by checking for the proper tagging of the first and following * bytes to make sure they conform to the UTF-8 format. It then checks * to assure that the data part of the UTF-8 sequence conforms to the * proper range allowed by the encoding. Note: This routine will not * detect characters that have not been assigned and therefore do not * exist. */ static int verify_utf8(sieve_script_t *parse_script, char *s) { const char *buf = s; const char *endbuf = s + strlen(s); unsigned char byte2mask = 0x00, c; int trailing = 0; /* trailing (continuation) bytes to follow */ while (buf != endbuf) { c = *buf++; if (trailing) { if ((c & 0xC0) == 0x80) { /* Does trailing byte follow UTF-8 format? */ if (byte2mask) { /* Need to check 2nd byte for proper range? */ if (c & byte2mask) /* Are appropriate bits set? */ byte2mask = 0x00; else break; } trailing--; } else break; } else { if ((c & 0x80) == 0x00) /* valid 1 byte UTF-8 */ continue; else if ((c & 0xE0) == 0xC0) /* valid 2 byte UTF-8 */ if (c & 0x1E) { /* Is UTF-8 byte in proper range? */ trailing = 1; } else break; else if ((c & 0xF0) == 0xE0) { /* valid 3 byte UTF-8 */ if (!(c & 0x0F)) { /* Is UTF-8 byte in proper range? */ byte2mask = 0x20; /* If not, set mask to check next byte */ } trailing = 2; } else if ((c & 0xF8) == 0xF0) { /* valid 4 byte UTF-8 */ if (!(c & 0x07)) { /* Is UTF-8 byte in proper range? */ byte2mask = 0x30; /* If not, set mask to check next byte */ } trailing = 3; } else if ((c & 0xFC) == 0xF8) { /* valid 5 byte UTF-8 */ if (!(c & 0x03)) { /* Is UTF-8 byte in proper range? */ byte2mask = 0x38; /* If not, set mask to check next byte */ } trailing = 4; } else if ((c & 0xFE) == 0xFC) { /* valid 6 byte UTF-8 */ if (!(c & 0x01)) { /* Is UTF-8 byte in proper range? */ byte2mask = 0x3C; /* If not, set mask to check next byte */ } trailing = 5; } else break; } } if ((buf != endbuf) || trailing) { snprintf(parse_script->sieveerr, ERR_BUF_SIZE, "string '%s': not valid utf8", s); yyerror(parse_script, parse_script->sieveerr); return 0; } return 1; } cyrus-imapd-2.5.10/sieve/sieved.c0000644000175000017500000004534113001236020013505 00000000000000/* sieved.c -- bytecode decompiler * Jen Smith * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #ifdef HAVE_CONFIG_H #include #endif #include "sieve_interface.h" #include "bytecode.h" #include "script.h" #include "xmalloc.h" #include #include #include #include #include #include #include "map.h" static void dump2(bytecode_input_t *d, int len); static int dump2_test(bytecode_input_t * d, int i, int version); /* from bc_eval.c */ int unwrap_string(bytecode_input_t *bc, int pos, const char **str, int *len); /*this is called by xmalloc*/ EXPORTED void fatal(const char *s, int code) { fprintf(stderr, "Fatal error: %s (%d)\r\n", s, code); exit(1); } static int load(int fd, bytecode_input_t ** d) { const char * data=NULL; struct stat sbuf; size_t len=0; if (fstat(fd, &sbuf) == -1) { fprintf(stderr, "IOERROR: fstating sieve script: %m"); return SIEVE_FAIL; } /*this reads in data and length from file*/ map_refresh(fd, 1, &(data), &len, sbuf.st_size, "sievescript", ""); *d=(bytecode_input_t *)data; printf("\n"); return (len/sizeof(int)); } int main(int argc, char * argv[]) { bytecode_input_t *bc = NULL; int script_fd; unsigned long len; if (argc!=2) { fprintf(stderr, "usage:\n %s script\n", argv[0]); exit(1); } /*get script*/ script_fd = open(argv[1], O_RDONLY); if (script_fd == -1) { fprintf(stderr, "can not open script '%s'\n", argv[1]); exit(1); } len=load(script_fd,&bc); close(script_fd); if (bc) { dump2(bc, len ); exit(0); } else { exit(1); } } static int write_list(int list_len, int i, bytecode_input_t * d) { int x; i++; for (x=0; x= 0x05) { i = unwrap_string(d, i, &data, &len); printf("%d FROM({%d}%s) \n",i, len, (!data ? "[nil]" : data)); i = unwrap_string(d, i, &data, &len); printf("%d HANDLE({%d}%s) \n",i, len, (!data ? "[nil]" : data)); } break; case B_NULL:/*15*/ printf("NULL\n"); break; case B_JUMP:/*16*/ printf("JUMP %d\n", ntohl(d[i].jump)); i+=1; break; case B_INCLUDE:/*17*/ printf("INCLUDE "); switch (ntohl(d[i].value) & 63) { case B_PERSONAL: printf("Personal"); break; case B_GLOBAL: printf("Global"); break; } printf(" once:%s optional:%s", ntohl(d[i].value) & 64 ? "yes" : "no", ntohl(d[i].value) & 128 ? "yes" : "no"); i = unwrap_string(d, i+1, &data, &len); printf(" {%d}%s\n", len, data); break; case B_RETURN:/*18*/ printf("RETURN\n"); break; default: printf("%d (NOT AN OP)\n",ntohl(d[i-1].op)); exit(1); } } printf("full len is: %d\n", bc_len); } cyrus-imapd-2.5.10/sieve/addr-lex.l0000644000175000017500000000654313001236020013740 00000000000000%{ /* * addr-lex.l -- RFC 822 address lexer * Ken Murchison * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include "sieve/sieve_interface.h" #include "sieve/addr.h" void addrerror(void*, const char *); static int ncom; /* number of open comments */ #define YY_DECL int addrlex(YYSTYPE* addrlval __attribute__((unused)), void* parse_script) %} %option noyywrap %option nounput %option noinput %option prefix="addr" outfile="lex.yy.c" %x QSTRING DOMAINLIT COMMENT %% \" { BEGIN QSTRING; return yytext[0]; } \[ { BEGIN DOMAINLIT; return yytext[0]; } \( { ncom = 1; BEGIN COMMENT; } \) { addrerror(parse_script, "address parse error, " "unexpected `')'' " "(unbalanced comment)"); yyterminate(); } [^\(\)<>@,;:\\".\[\] \n\r]+ return ATOM; [\t \n\r]+ /* ignore whitespace */ . return yytext[0]; ([^\n\r"\\]|\\.)* return QTEXT; \" { BEGIN INITIAL; return yytext[0]; } <> { BEGIN INITIAL; addrerror(parse_script, "address parse error, expecting `'\"'' (unterminated string)"); yyterminate(); } ([^\[\]\n\r\\]|\\.)* return DTEXT; \] { BEGIN INITIAL; return yytext[0]; } <> { BEGIN INITIAL; addrerror(parse_script, "address parse error, expecting `']'' (unterminated domain literal)"); yyterminate(); } ([^\(\)\n\0\\]|\\.)* /* ignore comments */ \( ncom++; \) { ncom--; if (ncom == 0) BEGIN INITIAL; } <> { BEGIN INITIAL; addrerror(parse_script, "address parse error, " "expecting `')'' " "(unterminated comment)"); yyterminate(); } %% cyrus-imapd-2.5.10/sieve/tree.c0000644000175000017500000001267213001236020013166 00000000000000/* tree.c -- abstract syntax tree handling * Larry Greenfield * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #ifdef HAVE_CONFIG_H #include #endif #include #include "xmalloc.h" #include "tree.h" #include "sieve/sieve_interface.h" #include "sieve/sieve.h" tag_t *new_tag(int type, char *s) { tag_t *p = (tag_t *) xmalloc(sizeof(tag_t)); p->type = type; p->arg = s; return p; } taglist_t *new_taglist(tag_t *t, taglist_t *n) { taglist_t *p = (taglist_t *) xmalloc(sizeof(taglist_t)); p->t = t; p->next = n; return p; } test_t *new_test(int type) { test_t *p = (test_t *) xmalloc(sizeof(test_t)); p->type = type; return p; } testlist_t *new_testlist(test_t *t, testlist_t *n) { testlist_t *p = (testlist_t *) xmalloc(sizeof(testlist_t)); p->t = t; p->next = n; return p; } commandlist_t *new_command(int type) { commandlist_t *p = (commandlist_t *) xmalloc(sizeof(commandlist_t)); p->type = type; p->next = NULL; return p; } commandlist_t *new_if(test_t *t, commandlist_t *y, commandlist_t *n) { commandlist_t *p = (commandlist_t *) xmalloc(sizeof(commandlist_t)); p->type = IF; p->u.i.t = t; p->u.i.do_then = y; p->u.i.do_else = n; p->next = NULL; return p; } void free_test(test_t *t); static void free_tl(testlist_t *tl) { testlist_t *tl2; while (tl) { tl2 = tl->next; if (tl->t) free_test(tl->t); free(tl); tl = tl2; } } void free_test(test_t *t) { if (t == NULL) return; switch (t->type) { case ANYOF: case ALLOF: free_tl(t->u.tl); break; case EXISTS: strarray_free(t->u.sl); break; case SIZE: case SFALSE: case STRUE: break; case HASFLAG: case HEADER: free(t->u.h.comparator); strarray_free(t->u.h.sl); strarray_free(t->u.h.pl); break; case ADDRESS: case ENVELOPE: free(t->u.ae.comparator); strarray_free(t->u.ae.sl); strarray_free(t->u.ae.pl); break; case BODY: free(t->u.b.comparator); strarray_free(t->u.b.content_types); strarray_free(t->u.b.pl); break; case NOT: free_test(t->u.t); break; case DATE: free(t->u.dt.header_name); /* fall-through */ case CURRENTDATE: free(t->u.dt.comparator); free(t->u.dt.zone); strarray_free(t->u.dt.kl); break; } free(t); } void free_tree(commandlist_t *cl) { commandlist_t *cl2; while (cl != NULL) { cl2 = cl->next; switch (cl->type) { case IF: free_test(cl->u.i.t); free_tree(cl->u.i.do_then); free_tree(cl->u.i.do_else); break; case INCLUDE: if (cl->u.inc.script) free(cl->u.inc.script); break; case FILEINTO: if (cl->u.f.folder) free(cl->u.f.folder); if (cl->u.f.flags) strarray_free(cl->u.f.flags); break; case REDIRECT: if (cl->u.r.address) free(cl->u.r.address); break; case REJCT: if (cl->u.str) free(cl->u.str); break; case VACATION: if (cl->u.v.subject) free(cl->u.v.subject); if (cl->u.v.addresses) strarray_free(cl->u.v.addresses); if (cl->u.v.message) free(cl->u.v.message); break; case SETFLAG: case ADDFLAG: case REMOVEFLAG: strarray_free(cl->u.sl); break; case KEEP: if (cl->u.k.flags) strarray_free(cl->u.k.flags); break; case STOP: case DISCARD: case RETURN: break; case NOTIFY: if (cl->u.n.method) free(cl->u.n.method); if (cl->u.n.id) free(cl->u.n.id); if (cl->u.n.options) strarray_free(cl->u.n.options); if (cl->u.n.message) free(cl->u.n.message); break; case DENOTIFY: if (cl->u.d.pattern) { #ifdef ENABLE_REGEX if (cl->u.d.comptag == REGEX) { regfree((regex_t *) cl->u.d.pattern); } #endif free(cl->u.d.pattern); } break; } free(cl); cl = cl2; } } cyrus-imapd-2.5.10/sieve/bc_emit.c0000644000175000017500000005317313001236020013632 00000000000000/* bc_emit.c -- sieve bytecode - pass 2 of the compiler * Rob Siemborski * Jen Smith * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #ifdef HAVE_CONFIG_H #include #endif #include "sieve_interface.h" #include "bytecode.h" #include #include #include #if DUMPCODE void dump(bytecode_info_t *d, int level); #endif static inline int write_int (int fd, int x) { int y=htonl(x); return (write(fd, &y, sizeof(int))); } /* Pad null bytes onto the end of the string we just wrote */ /* returns -1 on failure or number of bytes written on success */ static int align_string(int fd, int string_len) { /* Keep in mind that we always want to pad a string with *at least* * one zero, that's why sometimes we have to pad with 4 */ int needed = sizeof(int) - (string_len % sizeof(int)); if (needed>= 0 && needed <=4) { if (write(fd, "\0\0\0\0", needed) == -1) return -1; } return needed; } /*all functions keep codep up to date as they use it. the amount that has been written to the file is maintained by the filelen variable in bc_action_emit the other bc_xxx_emit funtions keep track of how much they (and any functions they call) have written and return this value */ /* Write out a stringlist to a given file descriptor. * return # of bytes written on success and -1 on error */ /* stringlist: <# listitems> */ static int bc_stringlist_emit(int fd, int *codep, bytecode_info_t *bc) { int len = bc->data[(*codep)++].len; int i; int ret; int wrote = 2*sizeof(int); int begin,end; /* Write out number of items in the list */ if (write_int(fd, len)== -1) return -1 ; /* skip one spot end of list position*/ begin=lseek(fd,0,SEEK_CUR); lseek(fd,sizeof(int),SEEK_CUR); /* Loop through all the items of the list, writing out length and string * in sequence */ for(i=0; i < len; i++) { int datalen = bc->data[(*codep)++].len; if(write_int(fd, datalen) == -1) return -1; wrote += sizeof(int); if(write(fd, bc->data[(*codep)++].str, datalen) == -1) return -1; wrote += datalen; ret = align_string(fd,datalen); if(ret == -1) return -1; wrote+=ret; } end=lseek(fd,0,SEEK_CUR); if (end < 0) return -1; /* go back and write end of list position */ lseek(fd,begin,SEEK_SET); if(write_int(fd, end) == -1) return -1; /* return to the end */ lseek(fd,end,SEEK_SET); return wrote; } static int bc_test_emit(int fd, int *codep, bytecode_info_t *bc); /* Write out a testlist to a given file descriptor. * return # of bytes written on success and -1 on error */ static int bc_testlist_emit(int fd, int *codep, bytecode_info_t *bc) { int len = bc->data[(*codep)++].len; int i; int ret; int begin, end; int wrote = 2*sizeof(int); /* Write out number of items in the list */ if(write_int(fd, len)== -1) return -1; /* skip one spot for end of list position*/ begin = lseek(fd, 0, SEEK_CUR); lseek(fd, sizeof(int), SEEK_CUR); /* Loop through all the items of the list, writing out each * test as we reach it in sequence. */ for(i=0; i < len; i++) { int nextcodep = bc->data[(*codep)++].jump; ret = bc_test_emit(fd, codep, bc); if(ret < 0 ) return -1; wrote+=ret; *codep = nextcodep; } end = lseek(fd, 0, SEEK_CUR); if (end < 0) return -1; /* go back and write the end of list position */ lseek(fd,begin,SEEK_SET); if(write_int(fd, end) == -1) return -1; /*return to the end */ lseek(fd,end,SEEK_SET); return wrote; } /* emit the bytecode for a test. returns -1 on failure or size of * emitted bytecode on success */ static int bc_test_emit(int fd, int *codep, bytecode_info_t *bc) { int opcode; int wrote=0;/* Relative offset to account for interleaved strings */ int ret; /* Temporary Return Value Variable */ /* Output this opcode */ opcode = bc->data[(*codep)++].op; if(write_int(fd, opcode) == -1) return -1; wrote += sizeof(int); switch(opcode) { case BC_TRUE: case BC_FALSE: /* No parameter opcodes */ break; case BC_NOT: { /* Single parameter: another test */ ret = bc_test_emit(fd, codep, bc); if(ret < 0) return -1; else wrote+=ret; break; } case BC_ALLOF: case BC_ANYOF: /*where we jump to?*/ /* Just drop a testlist */ ret = bc_testlist_emit(fd, codep, bc); if(ret < 0) return -1; else wrote+=ret; break; case BC_SIZE: /* Drop tag and number */ if(write_int(fd, bc->data[(*codep)].value) == -1) return -1; if(write_int(fd, bc->data[(*codep)+1].value) == -1) return -1; wrote += 2 * sizeof(int); (*codep) += 2; break; case BC_EXISTS: { int ret; ret = bc_stringlist_emit(fd, codep, bc); if(ret < 0) return -1; wrote += ret; break; } case BC_HEADER: case BC_HASFLAG: { int ret; if (BC_HEADER == opcode) { /* drop index */ if(write_int(fd, bc->data[(*codep)].value) == -1) return -1; wrote += sizeof(int); (*codep)++; } /* Drop match type */ if(write_int(fd, bc->data[(*codep)].value) == -1) return -1; wrote += sizeof(int); (*codep)++; /*now drop relation*/ if(write_int(fd, bc->data[(*codep)].value) == -1) return -1; wrote += sizeof(int); (*codep)++; /*drop comparator */ if(write_int(fd, bc->data[(*codep)].value) == -1) return -1; wrote += sizeof(int); (*codep)++; /* Now drop haystacks */ ret = bc_stringlist_emit(fd, codep, bc); if(ret < 0) return -1; wrote+=ret; /* Now drop needles */ ret = bc_stringlist_emit(fd, codep, bc); if(ret < 0) return -1; wrote+=ret; break; } case BC_ADDRESS: /* drop index */ if(write_int(fd, bc->data[(*codep)].value) == -1) return -1; wrote += sizeof(int); (*codep)++; /* fall-through */ case BC_ENVELOPE: { int ret; /* Drop match type */ if(write_int(fd, bc->data[(*codep)].value) == -1) return -1; wrote += sizeof(int); (*codep)++; /*drop comparator */ if(write_int(fd, bc->data[(*codep)].value) == -1) return -1; wrote += sizeof(int); (*codep)++; /*now drop relation*/ if(write_int(fd, bc->data[(*codep)].value) == -1) return -1; wrote += sizeof(int); (*codep)++; /*now drop address part*/ if(write_int(fd, bc->data[(*codep)].value) == -1) return -1; wrote += sizeof(int); (*codep)++; /* Now drop headers */ ret = bc_stringlist_emit(fd, codep, bc); if(ret < 0) return -1; wrote+=ret; /* Now drop data */ ret = bc_stringlist_emit(fd, codep, bc); if(ret < 0) return -1; wrote+=ret; break; } case BC_BODY: { int ret; /* Drop match type */ if(write_int(fd, bc->data[(*codep)].value) == -1) return -1; wrote += sizeof(int); (*codep)++; /*drop comparator */ if(write_int(fd, bc->data[(*codep)].value) == -1) return -1; wrote += sizeof(int); (*codep)++; /*now drop relation*/ if(write_int(fd, bc->data[(*codep)].value) == -1) return -1; wrote += sizeof(int); (*codep)++; /*now drop transform*/ if(write_int(fd, bc->data[(*codep)].value) == -1) return -1; wrote += sizeof(int); (*codep)++; /*now drop offset*/ if(write_int(fd, bc->data[(*codep)].value) == -1) return -1; wrote += sizeof(int); (*codep)++; /*now drop content-types*/ ret = bc_stringlist_emit(fd, codep, bc); if(ret < 0) return -1; wrote+=ret; /* Now drop data */ ret = bc_stringlist_emit(fd, codep, bc); if(ret < 0) return -1; wrote+=ret; break; } case BC_DATE: case BC_CURRENTDATE: { int ret; int datalen; int tmp; /* drop index */ if(BC_DATE == opcode) { if(write_int(fd, bc->data[(*codep)].value) == -1) return -1; wrote += sizeof(int); (*codep)++; } /* drop zone tag */ tmp = bc->data[(*codep)].value; if(write_int(fd, bc->data[(*codep)].value) == -1) return -1; wrote += sizeof(int); (*codep)++; /* drop timezone offset */ if (tmp == B_TIMEZONE) { if(write_int(fd, bc->data[(*codep)].value) == -1) return -1; wrote += sizeof(int); (*codep)++; } /* drop match type */ if(write_int(fd, bc->data[(*codep)].value) == -1) return -1; wrote += sizeof(int); (*codep)++; /* drop relation */ if(write_int(fd, bc->data[(*codep)].value) == -1) return -1; wrote += sizeof(int); (*codep)++; /* drop comparator */ if(write_int(fd, bc->data[(*codep)].value) == -1) return -1; wrote += sizeof(int); (*codep)++; /* drop date-part */ if(write_int(fd, bc->data[(*codep)].value) == -1) return -1; wrote += sizeof(int); (*codep)++; if (BC_DATE == opcode) { /* drop header-name */ datalen = bc->data[(*codep)++].len; if(write_int(fd, datalen) == -1) return -1; wrote += sizeof(int); if(write(fd, bc->data[(*codep)++].str, datalen) == -1) return -1; wrote += datalen; ret = align_string(fd,datalen); if(ret == -1) return -1; wrote+=ret; } /* drop keywords */ ret = bc_stringlist_emit(fd, codep, bc); if(ret < 0) return -1; wrote+=ret; break; } default: /* Unknown testcode? */ return -1; } return wrote; } /* emit the bytecode to a file descriptor given a flattened parse tree * returns -1 on failure, size of emitted bytecode on success. * * this takes care of everything except the comparisons */ static int bc_action_emit(int fd, int codep, int stopcodep, bytecode_info_t *bc, int filelen) { int len; /* Temporary Length Variable */ int ret; /* Temporary Return Value Variable */ int start_filelen = filelen; int i; /*debugging variable to check filelen*/ /*int location;*/ syslog(LOG_DEBUG, "entered bc_action_emit with filelen: %d", filelen); /* All non-string data MUST be sizeof(int) byte alligned so the end of each string may require a pad */ /* * Note that for purposes of jumps you must multiply codep by sizeof(int) */ while(codep < stopcodep) { /* Output this opcode */ if(write_int(fd, bc->data[codep].op) == -1) return -1; filelen+=sizeof(int); switch(bc->data[codep++].op) { case B_IF: { /* IF * test * jump (false condition) * then * (if there is an else) jump(finish) * (if there is an else) else */ int testEndLoc=-1; int testdist, thendist, elsedist; int c; int jumpFalseLoc=-1;/*this is the location that is being reserved for the first jump command we jump to the false condition of the test*/ int jumpEndLoc=-1; /* this is the location that is being reserved for the optional jump command it jumps over the else statement to the end*/ int jumpto=-1; int jumpop= B_JUMP; /*leave space to store the location of end of the test*/ ret = lseek(fd, sizeof(int), SEEK_CUR); if(ret == -1) return ret; testEndLoc=filelen; filelen+=sizeof(int); /* spew the test */ c=codep+3; testdist = bc_test_emit(fd, &c, bc); if(testdist == -1)return -1; filelen +=testdist; /*store the location for the end of the test *this is important for short circuiting of allof/anyof*/ jumpto=filelen/4; if(lseek(fd, testEndLoc, SEEK_SET) == -1) return -1; if(write_int(fd,jumpto) == -1) return -1; if(lseek(fd,filelen,SEEK_SET) == -1) return -1; /* leave space for jump */ if(write_int(fd, jumpop) == -1) return -1; ret = lseek(fd, sizeof(int), SEEK_CUR); if(ret == -1) return ret; jumpFalseLoc=filelen+sizeof(int); filelen +=2*sizeof(int); /*jumpop + jump*/ /* spew the then code */ thendist = bc_action_emit(fd, bc->data[codep].value, bc->data[codep+1].value, bc, filelen); filelen+=thendist; /* there is an else case */ if(bc->data[codep+2].value != -1) { /* leave space for jump */ if(write_int(fd, jumpop) == -1) return -1; ret = lseek(fd, sizeof(int), SEEK_CUR); if(ret == -1) return ret; jumpEndLoc=filelen+sizeof(int); filelen+=2*sizeof(int);/*jumpop + jump*/ } /*put previous jump to the end of the then code, *or the end of the jump if there is an else case */ jumpto=filelen/4; if(lseek(fd, jumpFalseLoc, SEEK_SET) == -1) return -1; if(write_int(fd,jumpto) == -1) return -1; if(lseek(fd,filelen,SEEK_SET) == -1) return -1; /* there is an else case */ if(bc->data[codep+2].value != -1) { /* spew the else code */ elsedist = bc_action_emit(fd, bc->data[codep+1].value, bc->data[codep+2].value, bc, filelen); filelen+=elsedist; /*put jump to the end of the else code*/ jumpto=filelen/4; if(lseek(fd, jumpEndLoc, SEEK_SET) == -1) return -1; if(write_int(fd,jumpto) == -1) return -1; if(lseek(fd,filelen,SEEK_SET) == -1) return -1; codep = bc->data[codep+2].value; } else { codep = bc->data[codep+1].value; } break; } case B_KEEP: /* Flags Stringlist, Copy (word) */ /* Dump a stringlist of flags */ ret = bc_stringlist_emit(fd, &codep, bc); if(ret < 0) return -1; filelen += ret; if(write_int(fd,bc->data[codep++].value) == -1) return -1; filelen += sizeof(int); break; case B_FILEINTO: /* Flags Stringlist, Copy (word), Folder String */ /* Dump a stringlist of flags */ ret = bc_stringlist_emit(fd, &codep, bc); if(ret < 0) return -1; filelen += ret; /* Write Copy */ if(write_int(fd,bc->data[codep++].value) == -1) return -1; filelen += sizeof(int); /* Write string length of Folder */ len = bc->data[codep++].len; if(write_int(fd,len) == -1) return -1; filelen+=sizeof(int); /* Write Folder */ if(write(fd,bc->data[codep++].str,len) == -1) return -1; ret = align_string(fd, len); if(ret == -1) return -1; filelen += len + ret; break; case B_REDIRECT: /* Copy (word), Address String */ if(write_int(fd,bc->data[codep++].value) == -1) return -1; filelen += sizeof(int); len = bc->data[codep++].len; if(write_int(fd,len) == -1) return -1; filelen+=sizeof(int); if(write(fd,bc->data[codep++].str,len) == -1) return -1; ret = align_string(fd, len); if(ret == -1) return -1; filelen += len + ret; break; case B_REJECT: /*just a string*/ len = bc->data[codep++].len; if(write_int(fd,len) == -1) return -1; filelen+=sizeof(int); if(write(fd,bc->data[codep++].str,len) == -1) return -1; ret = align_string(fd, len); if(ret == -1) return -1; filelen += len + ret; break; case B_SETFLAG: case B_ADDFLAG: case B_REMOVEFLAG: /* Dump just a stringlist */ ret = bc_stringlist_emit(fd, &codep, bc); if(ret < 0) return -1; filelen += ret; break; case B_NOTIFY: /* method string, id string, options string list, priotity, Message String */ /*method and id*/ for(i=0; i<2; i++) { len = bc->data[codep++].len; if(write_int(fd,len) == -1) return -1; filelen += sizeof(int); if(len == -1) { /* this will probably only happen for the id */ /* this is a nil string */ /* skip the null pointer and make up for it * by adjusting the offset */ codep++; } else { if(write(fd,bc->data[codep++].str,len) == -1) return -1; ret = align_string(fd, len); if(ret == -1) return -1; filelen += len + ret; } } /*options */ ret = bc_stringlist_emit(fd, &codep, bc); if(ret < 0) return -1; filelen+=ret; /*priority*/ if(write_int(fd, bc->data[codep].value) == -1) return -1; codep++; filelen += sizeof(int); len = bc->data[codep++].len; if(write_int(fd,len) == -1) return -1; filelen += sizeof(int); if(write(fd,bc->data[codep++].str,len) == -1) return -1; ret = align_string(fd, len); if(ret == -1) return -1; filelen += len + ret; break; case B_DENOTIFY: /* priority num,comptype num,relat num, comp string*/ /* priority*/ if(write_int(fd, bc->data[codep].value) == -1) return -1; filelen += sizeof(int); codep++; /* comptype */ if(write_int(fd, bc->data[codep].value) == -1) return -1; filelen += sizeof(int); codep++; /* relational*/ if(write_int(fd, bc->data[codep].value) == -1) return -1; filelen += sizeof(int); codep++; /* comp string*/ len = bc->data[codep++].len; if(write_int(fd,len) == -1) return -1; filelen += sizeof(int); if(len == -1) { /* this is a nil string */ /* skip the null pointer and make up for it * by adjusting the offset */ codep++; } else { if(write(fd,bc->data[codep++].str,len) == -1) return -1; ret = align_string(fd, len); if(ret == -1) return -1; filelen += len + ret; } break; case B_VACATION: /* Address list, Subject String, Message String, Seconds (word), Mime (word), From String, Handle String */ /*new code-this might be broken*/ ret = bc_stringlist_emit(fd, &codep, bc); if(ret < 0) return -1; filelen += ret; /*end of new code*/ for(i=0; i<2; i++) {/*writing strings*/ /*write length of string*/ len = bc->data[codep++].len; if(write_int(fd,len) == -1) return -1; filelen += sizeof(int); if(len == -1) { /* this is a nil string */ /* skip the null pointer and make up for it * by adjusting the offset */ codep++; } else { /*write string*/ if(write(fd,bc->data[codep++].str,len) == -1) return -1; ret = align_string(fd, len); if(ret == -1) return -1; filelen += len + ret; } } /* Seconds*/ if(write_int(fd,bc->data[codep].value) == -1) return -1; codep++; filelen += sizeof(int); /*Mime */ if(write_int(fd,bc->data[codep].value) == -1) return -1; codep++; for(i=0; i<2; i++) {/*writing strings*/ /*write length of string*/ len = bc->data[codep++].len; if(write_int(fd,len) == -1) return -1; filelen += sizeof(int); if(len == -1) { /* this is a nil string */ /* skip the null pointer and make up for it * by adjusting the offset */ codep++; } else { /*write string*/ if(write(fd,bc->data[codep++].str,len) == -1) return -1; ret = align_string(fd, len); if(ret == -1) return -1; filelen += len + ret; } } filelen += sizeof(int); break; case B_INCLUDE: /* Location + (Once<<6) + (Optional<<7) (word), Filename String */ /* Location + (Once<<6) + (Optional<<7) */ if(write_int(fd, bc->data[codep].value) == -1) return -1; filelen += sizeof(int); codep++; /* Filename */ len = bc->data[codep++].len; if(write_int(fd,len) == -1) return -1; filelen += sizeof(int); if(write(fd,bc->data[codep++].str,len) == -1) return -1; ret = align_string(fd, len); if(ret == -1) return -1; filelen += len + ret; break; case B_NULL: case B_STOP: case B_DISCARD: case B_MARK: case B_UNMARK: case B_RETURN: /* No Parameters! */ break; default: /* Unknown opcode? */ return -1; } } return filelen - start_filelen; } /* spew the bytecode to disk */ EXPORTED int sieve_emit_bytecode(int fd, bytecode_info_t *bc) { /* First output version number (4 bytes) */ int data = BYTECODE_VERSION; /*this is a string, so it is happy*/ if(write(fd, BYTECODE_MAGIC, BYTECODE_MAGIC_LEN) == -1) return -1; if(write_int(fd, data) == -1) return -1; #if DUMPCODE dump(bc, 0); #endif /*the sizeof(int) is to account for the version # at the beginning*/ return bc_action_emit(fd, 0, bc->scriptend, bc, sizeof(int) + BYTECODE_MAGIC_LEN); } cyrus-imapd-2.5.10/sieve/bc_eval.c0000644000175000017500000013343313001236020013621 00000000000000/* bc_eval.c - evaluate the bytecode * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #ifdef HAVE_CONFIG_H #include #endif #include "sieve_interface.h" #include "interp.h" #include "message.h" #include "script.h" #include "parseaddr.h" #include "bytecode.h" #include "charset.h" #include "xmalloc.h" #include "xstrlcpy.h" #include "util.h" #include "times.h" #include /**************************************************************************/ /**************************************************************************/ /**************************************************************************/ /**************************EXECUTING BYTECODE******************************/ /**************************************************************************/ /**************************************************************************/ /**************************************************************************/ /**************************************************************************/ /* Given a bytecode_input_t at the beginning of a string (the len block), * return the string, the length, and the bytecode index of the NEXT * item */ EXPORTED int unwrap_string(bytecode_input_t *bc, int pos, const char **str, int *len) { int local_len = ntohl(bc[pos].value); pos++; if(local_len == -1) { /* -1 length indicates NULL */ *str = NULL; } else { /* This cast is ugly, but necessary */ *str = (const char *)&bc[pos].str; /* Compute the next index */ pos += ((ROUNDUP(local_len+1))/sizeof(bytecode_input_t)); } if(len) *len = local_len; return pos; } /* this is used by notify to pass the options list to do_notify * do_notify needs null-terminated (char *)[], * we have a stringlist, the beginning of which is pointed at by pos */ static const char ** bc_makeArray(bytecode_input_t *bc, int *pos) { int i; const char** array; int len = ntohl(bc[*pos].value); (*pos)+=2; /* Skip # Values and Total Byte Length */ array=(const char **)xmalloc((len+1) * sizeof(char *)); for (i=0; igetheader(m, list_fields[j], &body) == SIEVE_OK) goto out; } /* Implementations SHOULD NOT respond to any message that has an "Auto-submitted" header field with a value other than "no". This header field is described in [RFC3834]. */ if (interp->getheader(m, "auto-submitted", &body) == SIEVE_OK) { /* we don't deal with comments, etc. here */ /* skip leading white-space */ while (*body[0] && Uisspace(*body[0])) body[0]++; if (strcasecmp(body[0], "no")) goto out; } /* is there a Precedence keyword of "junk | bulk | list"? */ /* XXX non-standard header, but worth checking */ if (interp->getheader(m, "precedence", &body) == SIEVE_OK) { /* we don't deal with comments, etc. here */ /* skip leading white-space */ while (*body[0] && Uisspace(*body[0])) body[0]++; if (!strcasecmp(body[0], "junk") || !strcasecmp(body[0], "bulk") || !strcasecmp(body[0], "list")) goto out; } /* Note: the domain-part of all addresses are canonicalized */ /* grab my address from the envelope */ l = interp->getenvelope(m, "to", &body); if (l != SIEVE_OK) goto out; l = SIEVE_DONE; if (!body[0]) goto out; myaddr = address_canonicalise(body[0]); l = interp->getenvelope(m, "from", &body); if (l != SIEVE_OK) goto out; l = SIEVE_DONE; if (!body[0]) goto out; /* we have to parse this address & decide whether we want to respond to it */ reply_to = address_canonicalise(body[0]); /* first, is there a reply-to address? */ if (reply_to == NULL) goto out; /* is it from me? */ if (myaddr && !strcmp(myaddr, reply_to)) goto out; /* ok, is it any of the other addresses i've specified? */ curra=i; for(x=0; xgetheader(m, "to", &body) == SIEVE_OK) found = look_for_me(myaddr, numaddresses, bc, i, body); if (!found && interp->getheader(m, "cc", &body) == SIEVE_OK) found = look_for_me(myaddr, numaddresses, bc, i, body); if (!found && interp->getheader(m, "bcc", &body) == SIEVE_OK) found = look_for_me(myaddr, numaddresses, bc, i, body); if (!found && interp->getheader(m, "resent-to", &body) == SIEVE_OK) found = look_for_me(myaddr, numaddresses ,bc, i, body); if (!found && interp->getheader(m, "resent-cc", &body) == SIEVE_OK) found = look_for_me(myaddr, numaddresses, bc, i, body); if (!found && interp->getheader(m, "resent-bcc", &body) == SIEVE_OK) found = look_for_me(myaddr, numaddresses, bc, i, body); if (found) l = SIEVE_OK; /* ok, ok, if we got here maybe we should reply */ out: free(myaddr); if (l == SIEVE_OK) { *from = found; *to = reply_to; } else { free(found); free(reply_to); } return l; } /* Evaluate a bytecode test */ static int eval_bc_test(sieve_interp_t *interp, void* m, bytecode_input_t * bc, int * ip, strarray_t *workingflags, int version) { int res=0; int i=*ip; int x,y,z;/* loop variable */ int list_len; /* for allof/anyof/exists */ int list_end; /* for allof/anyof/exists */ int address=0;/*to differentiate between address and envelope*/ int has_index=0;/* used to differentiate between pre and post index tests */ comparator_t * comp=NULL; void * comprock=NULL; int op= ntohl(bc[i].op); #define SCOUNT_SIZE 20 char scount[SCOUNT_SIZE]; switch(op) { case BC_FALSE:/*0*/ res=0; i++; break; case BC_TRUE:/*1*/ res=1; i++; break; case BC_NOT:/*2*/ i+=1; res = eval_bc_test(interp, m, bc, &i, workingflags, version); if(res >= 0) res = !res; /* Only invert in non-error case */ break; case BC_EXISTS:/*3*/ { int headersi=i+1; const char** val; int currh; res=1; list_len=ntohl(bc[headersi].len); list_end=ntohl(bc[headersi+1].value)/4; currh=headersi+2; for(x=0; xgetheader(m,str, &val) != SIEVE_OK) res = 0; } i=list_end; /* adjust for short-circuit */ break; } case BC_SIZE:/*4*/ { int s; int sizevar=ntohl(bc[i+1].value); int x=ntohl(bc[i+2].value); if (interp->getsize(m, &s) != SIEVE_OK) break; if (sizevar ==B_OVER) { /* over */ res= s > x; } else { /* under */ res= s < x; } i+=3; break; } case BC_ANYOF:/*5*/ res = 0; list_len=ntohl(bc[i+1].len); list_end=ntohl(bc[i+2].len)/4; i+=3; /* need to process all of them, to ensure our instruction pointer stays * in the right place */ for (x=0; xgetheader(m, this_header, &val) != SIEVE_OK) continue; #if VERBOSE printf(" [%d] header %s is %s\n", x, this_header, val[0]); #endif } else { /* Envelope */ if(interp->getenvelope(m, this_header, &val) != SIEVE_OK) continue; } /* count results */ header_count = 0; while (val[header_count] != NULL) { ++header_count; } /* convert index argument value to array index */ if (index > 0) { --index; if (index >= header_count) { res = 0; break; } header_count = index + 1; } else if (index < 0) { index += header_count; if (index < 0) { res = 0; break; } header_count = index + 1; } /*header exists, now to test it*/ /*search through all the headers that match*/ for (y = index; y < header_count && !res; y++) { #if VERBOSE printf("about to parse %s\n", val[y]); #endif address_itr_init(&ai, val[y]); while (!res && (a = address_itr_next(&ai)) != NULL) { #if VERBOSE printf("working addr %s\n", (addr ? addr : "[nil]")); #endif /*find the part of the address that we want*/ switch(apart) { case B_ALL: addr = address_get_all(a, /*canon_domain*/0); break; case B_LOCALPART: addr = address_get_localpart(a); break; case B_DOMAIN: addr = address_get_domain(a, /*canon_domain*/0); break; case B_USER: addr = address_get_user(a); break; case B_DETAIL: addr = address_get_detail(a); break; default: /* this shouldn't happen with correct bytecode */ res = SIEVE_RUN_ERROR; goto envelope_err; } if (!addr) addr = xstrdup(""); if (match == B_COUNT) { count++; } else { /*search through all the data*/ currd=datai+2; for (z=0; zgetheader(m, this_header, &val) != SIEVE_OK) { continue; /*this header does not exist, search the next*/ } #if VERBOSE printf ("val %s %s %s\n", val[0], val[1], val[2]); #endif /* count results */ header_count = 0; while (val[header_count] != NULL) { ++header_count; } /* convert index argument value to array index */ if (index > 0) { --index; if (index >= header_count) { res = 0; break; } header_count = index + 1; } else if (index < 0) { index += header_count; if (index < 0) { res = 0; break; } header_count = index + 1; } /* search through all the headers that match */ for (y = index; y < header_count && !res; y++) { if (match == B_COUNT) { count++; } else { decoded_header = charset_parse_mimeheader(val[y]); /*search through all the data*/ currd=datai+2; for (z=0; zcount; snprintf(scount, SCOUNT_SIZE, "%u", count); /*search through all the data*/ currneedle=needlesi+2; for (z=0; zcount && !res; y++) { const char *active_flag; active_flag = workingflags->data[y]; if (isReg) { reg= bc_compile_regex(this_needle, ctag, errbuf, sizeof(errbuf)); if (!reg) { /* Oops */ res=-1; goto alldone; } res |= comp(active_flag, strlen(active_flag), (const char *)reg, comprock); free(reg); } else { res |= comp(active_flag, strlen(active_flag), this_needle, comprock); } } } } /* Update IP */ i=(ntohl(bc[needlesi+1].value)/4); break; } case BC_BODY:/*10*/ { sieve_bodypart_t ** val; const char **content_types = NULL; int typesi=i+6;/* the i value for the beginning of the content-types */ int datai=(ntohl(bc[typesi+1].value)/4); int numdata=ntohl(bc[datai].len); int currd; /* current data */ int match=ntohl(bc[i+1].value); int relation=ntohl(bc[i+2].value); int comparator=ntohl(bc[i+3].value); int transform=ntohl(bc[i+4].value); /* ntohl(bc[i+5].value) is the now unused 'offset' */ int count=0; int isReg = (match==B_REGEX); int ctag = 0; regex_t *reg; char errbuf[100]; /* Basically unused, as regexps are tested at compile */ /* set up variables needed for compiling regex */ if (isReg) { if (comparator== B_ASCIICASEMAP) { ctag = REG_EXTENDED | REG_NOSUB | REG_ICASE; } else { ctag = REG_EXTENDED | REG_NOSUB; } } /*find the correct comparator fcn*/ comp = lookup_comp(comparator, match, relation, &comprock); if(!comp) { res = SIEVE_RUN_ERROR; break; } if (transform == B_RAW) { /* XXX - we never handled this properly, it has to search the * RAW message body, totally un-decoded, as a single string * * ignore - or just search in the UTF-8. I think the UTF-8 makes more sense */ /* break; */ } /*find the part(s) of the body that we want*/ content_types = bc_makeArray(bc, &typesi); if(interp->getbody(m, content_types, &val) != SIEVE_OK) { res = SIEVE_RUN_ERROR; break; } free(content_types); /* bodypart(s) exist, now to test them */ for (y = 0; val && val[y] && !res; y++) { if (match == B_COUNT) { count++; } else if (val[y]->decoded_body) { const char *content = val[y]->decoded_body; /* search through all the data */ currd=datai+2; for (z=0; zgetheader(m, header_name, &headers) != SIEVE_OK) { res = 0; free(bc_makeArray(bc, &i)); break; } /* count results */ header_count = 0; while (headers[header_count] != NULL) { ++header_count; } /* convert index argument value to array index */ if (index > 0) { --index; if (index >= header_count) { res = 0; free(bc_makeArray(bc, &i)); break; } header_count = index + 1; } else if (index < 0) { index += header_count; if (index < 0) { res = 0; free(bc_makeArray(bc, &i)); break; } header_count = index + 1; } /* check if index is out of bounds */ if (index < 0 || index >= header_count) { res = 0; free(bc_makeArray(bc, &i)); break; } header = headers[index]; /* look for separator */ header_data = strrchr(header, ';'); if (header_data) { /* separator found, skip character and continue */ ++header_data; } else { /* separator not found, use full header */ header_data = header; } if (-1 == time_from_rfc822(header_data, &t)) { res = 0; free(bc_makeArray(bc, &i)); break; } /* timezone offset */ if (zone == B_ORIGINALZONE) { char *zone; char sign; int hours; int minutes; zone = strrchr(header, ' '); if (!zone || 3 != sscanf(zone + 1, "%c%02d%02d", &sign, &hours, &minutes)) { res = 0; free(bc_makeArray(bc, &i)); break; } timezone_offset = (sign == '-' ? -1 : 1) * ((hours * 60) + (minutes)); } } else { /* CURRENTDATE */ t = interp->time; } /* apply timezone_offset (if any) */ t += timezone_offset * 60; /* get tm struct */ gmtime_r(&t, &tm); /* * Tests */ if (match == B_COUNT) { res = SIEVE_OK; goto alldone; } keylist = bc_makeArray(bc, &i); for (key = keylist; *key; ++key) { switch (date_part) { case B_YEAR: snprintf(buffer, sizeof(buffer), "%04d", 1900 + tm.tm_year); break; case B_MONTH: snprintf(buffer, sizeof(buffer), "%02d", 1 + tm.tm_mon); break; case B_DAY: snprintf(buffer, sizeof(buffer), "%02d", tm.tm_mday); break; case B_DATE: snprintf(buffer, sizeof(buffer), "%04d-%02d-%02d", 1900 + tm.tm_year, 1 + tm.tm_mon, tm.tm_mday); break; case B_JULIAN: { int month, year; int c, ya; month = 1 + tm.tm_mon; year = 1900 + tm.tm_year; if (month > 2) { month -= 3; } else { month += 9; --year; } c = year / 100; ya = year - c * 100; snprintf(buffer, sizeof(buffer), "%d", (c * 146097 / 4 + ya * 1461 / 4 + (month * 153 + 2) / 5 + tm.tm_mday + 1721119)); } break; case B_HOUR: snprintf(buffer, sizeof(buffer), "%02d", tm.tm_hour); break; case B_MINUTE: snprintf(buffer, sizeof(buffer), "%02d", tm.tm_min); break; case B_SECOND: snprintf(buffer, sizeof(buffer), "%02d", tm.tm_sec); break; case B_TIME: snprintf(buffer, sizeof(buffer), "%02d:%02d:%02d", tm.tm_hour, tm.tm_min, tm.tm_sec); break; case B_ISO8601: time_to_iso8601(t, buffer, sizeof(buffer)); break; case B_STD11: time_to_rfc822(t, buffer, sizeof(buffer)); break; case B_ZONE: snprintf(buffer, sizeof(buffer), "%c%02d%02d", timezone_offset >= 0 ? '+' : '-', abs(timezone_offset) / 60, abs(timezone_offset) % 60); break; case B_WEEKDAY: snprintf(buffer, sizeof(buffer), "%1d", tm.tm_wday); break; } res |= comp(buffer, strlen(buffer), *key, comprock); } free(keylist); break; } default: #if VERBOSE printf("WERT, can't evaluate if statement. %d is not a valid command", op); #endif return SIEVE_RUN_ERROR; } alldone: *ip=i; return res; } /* The entrypoint for bytecode evaluation */ int sieve_eval_bc(sieve_execute_t *exe, int is_incl, sieve_interp_t *i, void *sc, void *m, variable_list_t *flagvars, action_list_t *actions, notify_list_t *notify_list, const char **errmsg, variable_list_t *workingvars) { const char *data; int res=0; int op; int version; sieve_bytecode_t *bc_cur = exe->bc_cur; bytecode_input_t *bc = (bytecode_input_t *) bc_cur->data; int ip = 0, ip_max = (bc_cur->len/sizeof(bytecode_input_t)); if (bc_cur->is_executing) { *errmsg = "Recursive Include"; return SIEVE_RUN_ERROR; } bc_cur->is_executing = 1; /* Check that we * a) have bytecode * b) it is atleast long enough for the magic number, the version * and one opcode */ if(!bc) return SIEVE_FAIL; if(bc_cur->len < (BYTECODE_MAGIC_LEN + 2*sizeof(bytecode_input_t))) return SIEVE_FAIL; if(memcmp(bc, BYTECODE_MAGIC, BYTECODE_MAGIC_LEN)) { *errmsg = "Not a bytecode file"; return SIEVE_FAIL; } ip = BYTECODE_MAGIC_LEN / sizeof(bytecode_input_t); version= ntohl(bc[ip].op); /* this is because there was a time where integers were not network byte order. all the scripts written then would have version 0x01 written in host byte order.*/ if(version == (int)ntohl(1)) { if(errmsg) { *errmsg = "Incorrect Bytecode Version, please recompile (use sievec)"; } return SIEVE_FAIL; } if((version < BYTECODE_MIN_VERSION) || (version > BYTECODE_VERSION)) { if(errmsg) { *errmsg = "Incorrect Bytecode Version, please recompile (use sievec)"; } return SIEVE_FAIL; } #if VERBOSE printf("version number %d\n",version); #endif for(ip++; ipvar; } for (x=0; xvar); if (res == SIEVE_RUN_ERROR) *errmsg = "Keep can not be used with Reject"; actionflags = NULL; break; case B_DISCARD:/*2*/ res=do_discard(actions); break; case B_REJECT:/*3*/ ip = unwrap_string(bc, ip, &data, NULL); res = do_reject(actions, data); if (res == SIEVE_RUN_ERROR) *errmsg = "Reject can not be used with any other action"; break; case B_FILEINTO:/*23*/ { int x; int list_len=ntohl(bc[ip].len); ip+=2; /* skip opcode, list_len, and list data len */ if (list_len) { actionflags = (varlist_extend(flagvars))->var; } for (x=0; xvar); if (res == SIEVE_RUN_ERROR) *errmsg = "Fileinto can not be used with Reject"; actionflags = NULL; break; } case B_REDIRECT:/*20*/ copy = ntohl(bc[ip].value); ip+=1; /* fall through */ case B_REDIRECT_ORIG:/*5*/ { ip = unwrap_string(bc, ip, &data, NULL); res = do_redirect(actions, data, !copy); if (res == SIEVE_RUN_ERROR) *errmsg = "Redirect can not be used with Reject"; break; } case B_IF:/*6*/ { int testend=ntohl(bc[ip].value); int result; ip+=1; result=eval_bc_test(i, m, bc, &ip, workingvars->var, version); if (result<0) { *errmsg = "Invalid test"; return SIEVE_FAIL; } else if (result) { /*skip over jump instruction*/ testend+=2; } ip=testend; break; } case B_MARK:/*7*/ res = do_mark(actions); { int n = i->markflags->count; while (n) { strarray_add_case(workingvars->var, i->markflags->data[--n]); } } break; case B_UNMARK:/*8*/ res = do_unmark(actions); { int n = i->markflags->count; while (n) { strarray_remove_all_case(workingvars->var, i->markflags->data[--n]); } } break; case B_ADDFLAG:/*9*/ { int x; int list_len=ntohl(bc[ip].len); ip+=2; /* skip opcode, list_len, and list data len */ for (x=0; xvar, data); if (res == SIEVE_RUN_ERROR) *errmsg = "addflag can not be used with Reject"; } break; } case B_SETFLAG:/*10*/ { int x; int list_len=ntohl(bc[ip].len); ip+=2; /* skip opcode, list_len, and list data len */ res = do_setflag(actions); strarray_truncate(workingvars->var, 0); if (res == SIEVE_RUN_ERROR) { *errmsg = "setflag can not be used with Reject"; } else { for (x=0; xvar, data); } if (res == SIEVE_RUN_ERROR) *errmsg = "setflag can not be used with Reject"; } } break; } case B_REMOVEFLAG:/*11*/ { int x; int list_len=ntohl(bc[ip].len); ip+=2; /* skip opcode, list_len, and list data len */ for (x=0; xvar, data); if (res == SIEVE_RUN_ERROR) *errmsg = "removeflag can not be used with Reject"; } break; } case B_NOTIFY:/*12*/ { const char * id; const char * method; const char **options = NULL; const char *priority = NULL; const char * message; int pri; /* method */ ip = unwrap_string(bc, ip, &method, NULL); /* id */ ip = unwrap_string(bc, ip, &id, NULL); /*options*/ options=bc_makeArray(bc, &ip); /* priority */ pri=ntohl(bc[ip].value); ip++; switch (pri) { case B_LOW: priority="low"; break; case B_NORMAL: priority="normal"; break; case B_HIGH: priority="high"; break; case B_ANY: priority="any"; break; default: res=SIEVE_RUN_ERROR; } /* message */ ip = unwrap_string(bc, ip, &message, NULL); res = do_notify(notify_list, id, method, options, priority, message); break; } case B_DENOTIFY:/*13*/ { /* * i really have no idea what the count matchtype should do here. * the sanest thing would be to use 1. * however that would require passing on the match type to do_notify. * -jsmith2 */ comparator_t *comp = NULL; const char *pattern; regex_t *reg; const char *priority = NULL; void *comprock = NULL; int comparator; int pri; pri=ntohl(bc[ip].value); ip++; switch (pri) { case B_LOW: priority="low"; break; case B_NORMAL: priority="normal"; break; case B_HIGH: priority="high"; break; case B_ANY: priority="any"; break; default: res=SIEVE_RUN_ERROR; } if(res == SIEVE_RUN_ERROR) break; comparator =ntohl( bc[ip].value); ip++; if (comparator == B_ANY) { ip++;/* skip placeholder this has no comparator function */ comp=NULL; } else { int x= ntohl(bc[ip].value); ip++; comp=lookup_comp(B_ASCIICASEMAP,comparator, x, &comprock); } ip = unwrap_string(bc, ip, &pattern, NULL); if (comparator == B_REGEX) { char errmsg[1024]; /* Basically unused */ reg=bc_compile_regex(pattern, REG_EXTENDED | REG_NOSUB | REG_ICASE, errmsg, sizeof(errmsg)); if (!reg) { res = SIEVE_RUN_ERROR; } else { res = do_denotify(notify_list, comp, reg, comprock, priority); free(reg); } } else { res = do_denotify(notify_list, comp, pattern, comprock, priority); } break; } case B_VACATION_ORIG:/*14*/ case B_VACATION:/*21*/ { int respond; char *fromaddr = NULL; /* relative to message we send */ char *toaddr = NULL; /* relative to message we send */ const char *handle = NULL; const char *message = NULL; int seconds, mime; char buf[128]; char subject[1024]; int x; x = ntohl(bc[ip].len); respond = shouldRespond(m, i, x, bc, ip+2, &fromaddr, &toaddr); ip = ntohl(bc[ip+1].value) / 4; if (respond==SIEVE_OK) { ip = unwrap_string(bc, ip, &data, NULL); if (!data) { /* we have to generate a subject */ const char **s; strlcpy(buf, "subject", sizeof(buf)); if (i->getheader(m, buf, &s) != SIEVE_OK || s[0] == NULL) { strlcpy(subject, "Automated reply", sizeof(subject)); } else { /* s[0] contains the original subject */ const char *origsubj = s[0]; snprintf(subject, sizeof(subject), "Auto: %s", origsubj); } } else { /* user specified subject */ strlcpy(subject, data, sizeof(subject)); } ip = unwrap_string(bc, ip, &message, NULL); seconds = ntohl(bc[ip].value); if (op == B_VACATION_ORIG) { seconds *= DAY2SEC; } mime = ntohl(bc[ip+1].value); ip+=2; if (version >= 0x05) { ip = unwrap_string(bc, ip, &data, NULL); if (data) { /* user specified from address */ free(fromaddr); fromaddr = xstrdup(data); } ip = unwrap_string(bc, ip, &data, NULL); if (data) { /* user specified handle */ handle = data; } } res = do_vacation(actions, toaddr, fromaddr, xstrdup(subject), message, seconds, mime, handle); if (res == SIEVE_RUN_ERROR) *errmsg = "Vacation can not be used with Reject or Vacation"; } else if (respond == SIEVE_DONE) { /* skip subject and message */ ip = unwrap_string(bc, ip, &data, NULL); ip = unwrap_string(bc, ip, &data, NULL); ip+=2;/*skip days and mime flag*/ if (version >= 0x05) { /* skip from and handle */ ip = unwrap_string(bc, ip, &data, NULL); ip = unwrap_string(bc, ip, &data, NULL); } } else { res = SIEVE_RUN_ERROR; /* something is bad */ } break; } case B_NULL:/*15*/ break; case B_JUMP:/*16*/ ip= ntohl(bc[ip].jump); break; case B_INCLUDE:/*17*/ { int isglobal = (ntohl(bc[ip].value) & 63) == B_GLOBAL; int once = ntohl(bc[ip].value) & 64 ? 1 : 0; int isoptional = ntohl(bc[ip].value) & 128 ? 1 : 0; char fpath[4096]; ip = unwrap_string(bc, ip+1, &data, NULL); res = i->getinclude(sc, data, isglobal, fpath, sizeof(fpath)); if (res != SIEVE_OK) { if (isoptional == 0) *errmsg = "Include can not find script"; else res = SIEVE_OK; break; } res = sieve_script_load(fpath, &exe); if (res == SIEVE_SCRIPT_RELOADED) { if (once == 1) { res = SIEVE_OK; break; } } else if (res != SIEVE_OK) { /* SIEVE_FAIL */ if (isoptional == 0) *errmsg = "Include can not load script"; else res = SIEVE_OK; break; } res = sieve_eval_bc(exe, 1, i, sc, m, flagvars, actions, notify_list, errmsg, workingvars); break; } case B_RETURN:/*18*/ if (is_incl) goto done; else res=1; break; default: if(errmsg) *errmsg = "Invalid sieve bytecode"; return SIEVE_FAIL; } if (res) /* we've either encountered an error or a stop */ break; } done: bc_cur->is_executing = 0; return res; } cyrus-imapd-2.5.10/sieve/sieve-lex.c0000644000175000017500000021371213001246644014143 00000000000000#line 2 "sieve/sieve-lex.c" #line 4 "sieve/sieve-lex.c" #define YY_INT_ALIGNED short int /* A lexical scanner generated by flex */ #define yy_create_buffer sieve_create_buffer #define yy_delete_buffer sieve_delete_buffer #define yy_flex_debug sieve_flex_debug #define yy_init_buffer sieve_init_buffer #define yy_flush_buffer sieve_flush_buffer #define yy_load_buffer_state sieve_load_buffer_state #define yy_switch_to_buffer sieve_switch_to_buffer #define yyin sievein #define yyleng sieveleng #define yylex sievelex #define yylineno sievelineno #define yyout sieveout #define yyrestart sieverestart #define yytext sievetext #define yywrap sievewrap #define yyalloc sievealloc #define yyrealloc sieverealloc #define yyfree sievefree #define FLEX_SCANNER #define YY_FLEX_MAJOR_VERSION 2 #define YY_FLEX_MINOR_VERSION 6 #define YY_FLEX_SUBMINOR_VERSION 1 #if YY_FLEX_SUBMINOR_VERSION > 0 #define FLEX_BETA #endif /* First, we deal with platform-specific or compiler-specific issues. */ /* begin standard C headers. */ #include #include #include #include /* end standard C headers. */ /* flex integer type definitions */ #ifndef FLEXINT_H #define FLEXINT_H /* C99 systems have . Non-C99 systems may or may not. */ #if defined (__STDC_VERSION__) && __STDC_VERSION__ >= 199901L /* C99 says to define __STDC_LIMIT_MACROS before including stdint.h, * if you want the limit (max/min) macros for int types. */ #ifndef __STDC_LIMIT_MACROS #define __STDC_LIMIT_MACROS 1 #endif #include typedef int8_t flex_int8_t; typedef uint8_t flex_uint8_t; typedef int16_t flex_int16_t; typedef uint16_t flex_uint16_t; typedef int32_t flex_int32_t; typedef uint32_t flex_uint32_t; #else typedef signed char flex_int8_t; typedef short int flex_int16_t; typedef int flex_int32_t; typedef unsigned char flex_uint8_t; typedef unsigned short int flex_uint16_t; typedef unsigned int flex_uint32_t; /* Limits of integral types. */ #ifndef INT8_MIN #define INT8_MIN (-128) #endif #ifndef INT16_MIN #define INT16_MIN (-32767-1) #endif #ifndef INT32_MIN #define INT32_MIN (-2147483647-1) #endif #ifndef INT8_MAX #define INT8_MAX (127) #endif #ifndef INT16_MAX #define INT16_MAX (32767) #endif #ifndef INT32_MAX #define INT32_MAX (2147483647) #endif #ifndef UINT8_MAX #define UINT8_MAX (255U) #endif #ifndef UINT16_MAX #define UINT16_MAX (65535U) #endif #ifndef UINT32_MAX #define UINT32_MAX (4294967295U) #endif #endif /* ! C99 */ #endif /* ! FLEXINT_H */ /* TODO: this is always defined, so inline it */ #define yyconst const #if defined(__GNUC__) && __GNUC__ >= 3 #define yynoreturn __attribute__((__noreturn__)) #else #define yynoreturn #endif /* Returned upon end-of-file. */ #define YY_NULL 0 /* Promotes a possibly negative, possibly signed char to an unsigned * integer for use as an array index. If the signed char is negative, * we want to instead treat it as an 8-bit unsigned char, hence the * double cast. */ #define YY_SC_TO_UI(c) ((unsigned int) (unsigned char) c) /* Enter a start condition. This macro really ought to take a parameter, * but we do it the disgusting crufty way forced on us by the ()-less * definition of BEGIN. */ #define BEGIN (yy_start) = 1 + 2 * /* Translate the current start state into a value that can be later handed * to BEGIN to return to the state. The YYSTATE alias is for lex * compatibility. */ #define YY_START (((yy_start) - 1) / 2) #define YYSTATE YY_START /* Action number for EOF rule of a given start state. */ #define YY_STATE_EOF(state) (YY_END_OF_BUFFER + state + 1) /* Special action meaning "start processing a new file". */ #define YY_NEW_FILE sieverestart(sievein ) #define YY_END_OF_BUFFER_CHAR 0 /* Size of default input buffer. */ #ifndef YY_BUF_SIZE #ifdef __ia64__ /* On IA-64, the buffer size is 16k, not 8k. * Moreover, YY_BUF_SIZE is 2*YY_READ_BUF_SIZE in the general case. * Ditto for the __ia64__ case accordingly. */ #define YY_BUF_SIZE 32768 #else #define YY_BUF_SIZE 16384 #endif /* __ia64__ */ #endif /* The state buf must be large enough to hold one state per character in the main buffer. */ #define YY_STATE_BUF_SIZE ((YY_BUF_SIZE + 2) * sizeof(yy_state_type)) #ifndef YY_TYPEDEF_YY_BUFFER_STATE #define YY_TYPEDEF_YY_BUFFER_STATE typedef struct yy_buffer_state *YY_BUFFER_STATE; #endif #ifndef YY_TYPEDEF_YY_SIZE_T #define YY_TYPEDEF_YY_SIZE_T typedef size_t yy_size_t; #endif extern int sieveleng; extern FILE *sievein, *sieveout; #define EOB_ACT_CONTINUE_SCAN 0 #define EOB_ACT_END_OF_FILE 1 #define EOB_ACT_LAST_MATCH 2 /* Note: We specifically omit the test for yy_rule_can_match_eol because it requires * access to the local variable yy_act. Since yyless() is a macro, it would break * existing scanners that call yyless() from OUTSIDE sievelex. * One obvious solution it to make yy_act a global. I tried that, and saw * a 5% performance hit in a non-sievelineno scanner, because yy_act is * normally declared as a register variable-- so it is not worth it. */ #define YY_LESS_LINENO(n) \ do { \ int yyl;\ for ( yyl = n; yyl < sieveleng; ++yyl )\ if ( sievetext[yyl] == '\n' )\ --sievelineno;\ }while(0) #define YY_LINENO_REWIND_TO(dst) \ do {\ const char *p;\ for ( p = yy_cp-1; p >= (dst); --p)\ if ( *p == '\n' )\ --sievelineno;\ }while(0) /* Return all but the first "n" matched characters back to the input stream. */ #define yyless(n) \ do \ { \ /* Undo effects of setting up sievetext. */ \ int yyless_macro_arg = (n); \ YY_LESS_LINENO(yyless_macro_arg);\ *yy_cp = (yy_hold_char); \ YY_RESTORE_YY_MORE_OFFSET \ (yy_c_buf_p) = yy_cp = yy_bp + yyless_macro_arg - YY_MORE_ADJ; \ YY_DO_BEFORE_ACTION; /* set up sievetext again */ \ } \ while ( 0 ) #define unput(c) yyunput( c, (yytext_ptr) ) #ifndef YY_STRUCT_YY_BUFFER_STATE #define YY_STRUCT_YY_BUFFER_STATE struct yy_buffer_state { FILE *yy_input_file; char *yy_ch_buf; /* input buffer */ char *yy_buf_pos; /* current position in input buffer */ /* Size of input buffer in bytes, not including room for EOB * characters. */ int yy_buf_size; /* Number of characters read into yy_ch_buf, not including EOB * characters. */ int yy_n_chars; /* Whether we "own" the buffer - i.e., we know we created it, * and can realloc() it to grow it, and should free() it to * delete it. */ int yy_is_our_buffer; /* Whether this is an "interactive" input source; if so, and * if we're using stdio for input, then we want to use getc() * instead of fread(), to make sure we stop fetching input after * each newline. */ int yy_is_interactive; /* Whether we're considered to be at the beginning of a line. * If so, '^' rules will be active on the next match, otherwise * not. */ int yy_at_bol; int yy_bs_lineno; /**< The line count. */ int yy_bs_column; /**< The column count. */ /* Whether to try to fill the input buffer when we reach the * end of it. */ int yy_fill_buffer; int yy_buffer_status; #define YY_BUFFER_NEW 0 #define YY_BUFFER_NORMAL 1 /* When an EOF's been seen but there's still some text to process * then we mark the buffer as YY_EOF_PENDING, to indicate that we * shouldn't try reading from the input source any more. We might * still have a bunch of tokens to match, though, because of * possible backing-up. * * When we actually see the EOF, we change the status to "new" * (via sieverestart()), so that the user can continue scanning by * just pointing sievein at a new input file. */ #define YY_BUFFER_EOF_PENDING 2 }; #endif /* !YY_STRUCT_YY_BUFFER_STATE */ /* Stack of input buffers. */ static size_t yy_buffer_stack_top = 0; /**< index of top of stack. */ static size_t yy_buffer_stack_max = 0; /**< capacity of stack. */ static YY_BUFFER_STATE * yy_buffer_stack = NULL; /**< Stack as an array. */ /* We provide macros for accessing buffer states in case in the * future we want to put the buffer states in a more general * "scanner state". * * Returns the top of the stack, or NULL. */ #define YY_CURRENT_BUFFER ( (yy_buffer_stack) \ ? (yy_buffer_stack)[(yy_buffer_stack_top)] \ : NULL) /* Same as previous macro, but useful when we know that the buffer stack is not * NULL or when we need an lvalue. For internal use only. */ #define YY_CURRENT_BUFFER_LVALUE (yy_buffer_stack)[(yy_buffer_stack_top)] /* yy_hold_char holds the character lost when sievetext is formed. */ static char yy_hold_char; static int yy_n_chars; /* number of characters read into yy_ch_buf */ int sieveleng; /* Points to current character in buffer. */ static char *yy_c_buf_p = NULL; static int yy_init = 0; /* whether we need to initialize */ static int yy_start = 0; /* start state number */ /* Flag which is used to allow sievewrap()'s to do buffer switches * instead of setting up a fresh sievein. A bit of a hack ... */ static int yy_did_buffer_switch_on_eof; void sieverestart (FILE *input_file ); void sieve_switch_to_buffer (YY_BUFFER_STATE new_buffer ); YY_BUFFER_STATE sieve_create_buffer (FILE *file,int size ); void sieve_delete_buffer (YY_BUFFER_STATE b ); void sieve_flush_buffer (YY_BUFFER_STATE b ); void sievepush_buffer_state (YY_BUFFER_STATE new_buffer ); void sievepop_buffer_state (void ); static void sieveensure_buffer_stack (void ); static void sieve_load_buffer_state (void ); static void sieve_init_buffer (YY_BUFFER_STATE b,FILE *file ); #define YY_FLUSH_BUFFER sieve_flush_buffer(YY_CURRENT_BUFFER ) YY_BUFFER_STATE sieve_scan_buffer (char *base,yy_size_t size ); YY_BUFFER_STATE sieve_scan_string (yyconst char *yy_str ); YY_BUFFER_STATE sieve_scan_bytes (yyconst char *bytes,int len ); void *sievealloc (yy_size_t ); void *sieverealloc (void *,yy_size_t ); void sievefree (void * ); #define yy_new_buffer sieve_create_buffer #define yy_set_interactive(is_interactive) \ { \ if ( ! YY_CURRENT_BUFFER ){ \ sieveensure_buffer_stack (); \ YY_CURRENT_BUFFER_LVALUE = \ sieve_create_buffer(sievein,YY_BUF_SIZE ); \ } \ YY_CURRENT_BUFFER_LVALUE->yy_is_interactive = is_interactive; \ } #define yy_set_bol(at_bol) \ { \ if ( ! YY_CURRENT_BUFFER ){\ sieveensure_buffer_stack (); \ YY_CURRENT_BUFFER_LVALUE = \ sieve_create_buffer(sievein,YY_BUF_SIZE ); \ } \ YY_CURRENT_BUFFER_LVALUE->yy_at_bol = at_bol; \ } #define YY_AT_BOL() (YY_CURRENT_BUFFER_LVALUE->yy_at_bol) /* Begin user sect3 */ #define sievewrap() (/*CONSTCOND*/1) #define YY_SKIP_YYWRAP typedef unsigned char YY_CHAR; FILE *sievein = NULL, *sieveout = NULL; typedef int yy_state_type; extern int sievelineno; int sievelineno = 1; extern char *sievetext; #ifdef yytext_ptr #undef yytext_ptr #endif #define yytext_ptr sievetext static yy_state_type yy_get_previous_state (void ); static yy_state_type yy_try_NUL_trans (yy_state_type current_state ); static int yy_get_next_buffer (void ); static void yynoreturn yy_fatal_error (yyconst char* msg ); /* Done after the current pattern has been matched and before the * corresponding action - sets up sievetext. */ #define YY_DO_BEFORE_ACTION \ (yytext_ptr) = yy_bp; \ sieveleng = (int) (yy_cp - yy_bp); \ (yy_hold_char) = *yy_cp; \ *yy_cp = '\0'; \ (yy_c_buf_p) = yy_cp; #define YY_NUM_RULES 89 #define YY_END_OF_BUFFER 90 /* This struct is not used in this scanner, but its presence is necessary. */ struct yy_trans_info { flex_int32_t yy_verify; flex_int32_t yy_nxt; }; static yyconst flex_int16_t yy_accept[416] = { 0, 0, 0, 0, 0, 0, 0, 90, 88, 85, 85, 8, 86, 88, 9, 88, 88, 88, 88, 88, 88, 88, 88, 88, 88, 88, 88, 88, 88, 88, 88, 88, 3, 3, 3, 6, 6, 4, 6, 86, 0, 9, 9, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 10, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 2, 5, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 39, 0, 55, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 22, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 87, 0, 63, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 42, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 68, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 21, 0, 78, 0, 0, 12, 0, 0, 0, 0, 0, 0, 0, 0, 28, 35, 0, 0, 0, 0, 0, 0, 0, 23, 30, 0, 17, 0, 0, 87, 0, 0, 0, 77, 0, 47, 0, 0, 0, 51, 0, 0, 44, 0, 81, 0, 0, 0, 0, 53, 0, 75, 0, 0, 61, 0, 0, 0, 0, 69, 0, 66, 0, 82, 0, 0, 14, 13, 0, 0, 0, 11, 0, 0, 16, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 59, 0, 0, 84, 0, 0, 80, 0, 0, 0, 0, 0, 0, 0, 0, 58, 0, 0, 62, 60, 0, 0, 0, 0, 0, 0, 15, 0, 0, 20, 0, 37, 0, 25, 0, 0, 76, 0, 0, 7, 7, 0, 36, 0, 0, 0, 0, 0, 67, 65, 73, 52, 0, 0, 0, 40, 43, 0, 0, 0, 0, 0, 33, 18, 0, 0, 31, 0, 0, 24, 71, 0, 0, 29, 32, 0, 7, 0, 0, 0, 0, 70, 0, 57, 45, 0, 41, 0, 0, 48, 50, 0, 38, 19, 26, 27, 0, 7, 46, 0, 0, 56, 0, 74, 0, 72, 0, 0, 49, 0, 64, 0, 0, 34, 54, 0, 79, 0, 83, 0 } ; static yyconst YY_CHAR yy_ec[256] = { 0, 1, 1, 1, 1, 1, 1, 1, 1, 2, 3, 1, 1, 4, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 2, 1, 5, 6, 1, 1, 1, 1, 1, 1, 7, 1, 1, 1, 8, 9, 10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 11, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 12, 1, 1, 1, 12, 1, 12, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 13, 1, 1, 1, 1, 14, 15, 16, 17, 18, 19, 20, 21, 22, 23, 24, 25, 26, 27, 28, 29, 30, 31, 32, 33, 34, 35, 36, 37, 38, 39, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1 } ; static yyconst YY_CHAR yy_meta[40] = { 0, 1, 1, 2, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1 } ; static yyconst flex_uint16_t yy_base[422] = { 0, 0, 0, 449, 37, 38, 39, 451, 453, 453, 453, 453, 0, 443, 36, 49, 30, 421, 414, 36, 60, 39, 72, 40, 429, 432, 417, 426, 71, 61, 416, 428, 453, 453, 91, 453, 453, 453, 0, 0, 434, 86, 453, 47, 412, 87, 77, 414, 89, 90, 86, 102, 410, 92, 419, 95, 100, 418, 98, 421, 406, 416, 407, 393, 413, 398, 395, 400, 394, 393, 389, 401, 397, 396, 388, 405, 453, 402, 399, 385, 382, 109, 381, 374, 384, 374, 376, 383, 392, 453, 404, 453, 453, 399, 122, 388, 379, 111, 365, 369, 375, 386, 371, 370, 370, 376, 453, 378, 453, 362, 112, 360, 111, 366, 360, 374, 356, 366, 369, 355, 349, 364, 367, 367, 344, 363, 361, 353, 350, 122, 348, 347, 336, 342, 354, 343, 354, 128, 351, 336, 335, 348, 346, 347, 338, 333, 337, 338, 337, 340, 329, 322, 321, 335, 335, 323, 318, 332, 335, 334, 140, 453, 316, 453, 317, 312, 306, 316, 310, 327, 326, 319, 312, 322, 319, 314, 316, 300, 318, 453, 315, 298, 308, 310, 301, 308, 303, 304, 292, 290, 453, 303, 292, 296, 285, 299, 285, 281, 296, 288, 294, 292, 291, 453, 291, 453, 275, 293, 453, 287, 280, 271, 285, 280, 276, 282, 265, 453, 453, 279, 266, 280, 260, 272, 262, 267, 453, 453, 280, 453, 259, 256, 281, 269, 272, 137, 453, 252, 453, 262, 261, 250, 453, 267, 255, 453, 242, 453, 253, 256, 262, 247, 453, 260, 453, 245, 250, 453, 243, 233, 242, 250, 453, 236, 453, 248, 453, 251, 232, 453, 453, 236, 240, 230, 453, 232, 227, 453, 231, 243, 225, 238, 216, 235, 219, 233, 219, 222, 234, 154, 223, 224, 213, 213, 221, 215, 453, 216, 213, 453, 214, 220, 453, 208, 218, 215, 217, 208, 205, 204, 203, 453, 212, 212, 453, 453, 207, 194, 192, 205, 206, 193, 453, 188, 200, 453, 201, 453, 202, 453, 198, 198, 453, 195, 159, 453, 211, 163, 453, 185, 180, 197, 183, 176, 453, 453, 453, 453, 194, 175, 188, 453, 453, 59, 191, 190, 171, 169, 453, 453, 184, 162, 453, 181, 170, 453, 453, 164, 171, 453, 453, 165, 167, 168, 176, 160, 160, 453, 160, 453, 453, 165, 453, 164, 163, 453, 453, 173, 453, 453, 453, 453, 172, 453, 453, 153, 156, 453, 150, 453, 143, 453, 148, 160, 453, 133, 453, 131, 136, 453, 453, 125, 453, 118, 453, 453, 171, 173, 132, 48, 175, 177 } ; static yyconst flex_int16_t yy_def[422] = { 0, 415, 1, 416, 416, 417, 417, 415, 415, 415, 415, 415, 418, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 419, 418, 420, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 420, 420, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 420, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 420, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 421, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 421, 421, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 0, 415, 415, 415, 415, 415, 415 } ; static yyconst flex_uint16_t yy_nxt[493] = { 0, 8, 9, 10, 9, 11, 12, 8, 8, 13, 14, 15, 8, 8, 16, 17, 18, 19, 20, 21, 8, 22, 23, 8, 24, 8, 25, 26, 8, 8, 8, 27, 28, 29, 30, 31, 8, 8, 8, 8, 33, 36, 36, 37, 37, 34, 41, 61, 42, 92, 66, 38, 38, 72, 67, 62, 42, 63, 68, 76, 42, 73, 42, 43, 95, 44, 45, 77, 46, 47, 48, 49, 96, 381, 50, 51, 52, 53, 54, 85, 55, 56, 57, 58, 59, 69, 74, 70, 60, 82, 75, 382, 86, 83, 89, 90, 41, 71, 42, 91, 109, 98, 101, 104, 84, 99, 42, 106, 102, 120, 42, 105, 42, 121, 110, 100, 111, 107, 122, 115, 112, 116, 108, 117, 113, 125, 148, 118, 178, 160, 126, 161, 149, 39, 123, 150, 414, 164, 165, 151, 166, 199, 152, 181, 182, 167, 208, 94, 179, 232, 209, 294, 413, 200, 412, 295, 334, 335, 336, 411, 337, 334, 335, 336, 410, 337, 335, 372, 335, 372, 393, 372, 32, 32, 35, 35, 93, 93, 371, 371, 409, 408, 407, 406, 405, 404, 403, 402, 401, 400, 399, 398, 397, 396, 395, 394, 392, 391, 390, 389, 388, 387, 386, 385, 384, 383, 380, 379, 378, 377, 376, 375, 374, 373, 335, 370, 369, 368, 367, 366, 365, 364, 363, 362, 361, 360, 359, 358, 357, 356, 355, 354, 353, 352, 351, 350, 349, 348, 347, 346, 345, 344, 343, 342, 341, 340, 339, 338, 333, 332, 331, 330, 329, 328, 327, 326, 325, 324, 323, 322, 321, 320, 319, 318, 317, 316, 315, 314, 313, 312, 311, 310, 309, 308, 307, 306, 305, 304, 303, 302, 301, 300, 299, 298, 297, 296, 293, 292, 94, 291, 290, 289, 288, 287, 286, 285, 284, 283, 282, 281, 280, 279, 278, 277, 276, 275, 274, 273, 272, 271, 270, 269, 268, 267, 266, 265, 264, 263, 262, 261, 260, 259, 258, 257, 256, 255, 254, 253, 252, 251, 250, 249, 248, 247, 246, 245, 244, 243, 242, 241, 240, 239, 238, 237, 236, 235, 234, 233, 231, 230, 229, 228, 227, 226, 225, 224, 223, 222, 221, 220, 219, 218, 217, 216, 215, 214, 213, 212, 211, 210, 207, 206, 205, 204, 203, 202, 201, 198, 197, 196, 195, 194, 193, 192, 191, 190, 189, 188, 187, 186, 185, 184, 183, 180, 177, 176, 175, 174, 173, 172, 171, 170, 169, 168, 163, 162, 94, 89, 159, 158, 157, 156, 155, 154, 153, 147, 146, 145, 144, 143, 142, 141, 140, 139, 138, 137, 136, 135, 134, 133, 132, 131, 130, 129, 128, 127, 124, 119, 114, 103, 97, 94, 88, 87, 81, 80, 79, 78, 65, 64, 40, 415, 33, 7, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415 } ; static yyconst flex_int16_t yy_chk[493] = { 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 4, 5, 6, 5, 6, 4, 14, 16, 14, 419, 19, 5, 6, 21, 19, 16, 14, 16, 19, 23, 14, 21, 14, 15, 43, 15, 15, 23, 15, 15, 15, 15, 43, 353, 15, 15, 15, 15, 15, 29, 15, 15, 15, 15, 15, 20, 22, 20, 15, 28, 22, 353, 29, 28, 34, 34, 41, 20, 41, 34, 50, 45, 46, 48, 28, 45, 41, 49, 46, 55, 41, 48, 41, 55, 50, 45, 51, 49, 56, 53, 51, 53, 49, 53, 51, 58, 81, 53, 110, 94, 58, 94, 81, 418, 56, 81, 413, 97, 97, 81, 97, 129, 81, 112, 112, 97, 137, 160, 110, 160, 137, 235, 411, 129, 408, 235, 289, 289, 289, 407, 289, 334, 334, 334, 405, 334, 337, 337, 371, 371, 372, 372, 416, 416, 417, 417, 420, 420, 421, 421, 403, 402, 400, 398, 396, 395, 392, 387, 384, 383, 381, 378, 376, 375, 374, 373, 368, 367, 364, 363, 361, 360, 357, 356, 355, 354, 350, 349, 348, 343, 342, 341, 340, 339, 336, 333, 331, 330, 328, 326, 324, 323, 321, 320, 319, 318, 317, 316, 313, 312, 310, 309, 308, 307, 306, 305, 304, 303, 301, 300, 298, 297, 295, 294, 293, 292, 291, 290, 288, 287, 286, 285, 284, 283, 282, 281, 280, 279, 278, 276, 275, 273, 272, 271, 268, 267, 265, 263, 261, 260, 259, 258, 256, 255, 253, 251, 250, 249, 248, 246, 244, 243, 241, 240, 239, 237, 234, 233, 232, 231, 230, 228, 225, 224, 223, 222, 221, 220, 219, 216, 215, 214, 213, 212, 211, 210, 209, 207, 206, 204, 202, 201, 200, 199, 198, 197, 196, 195, 194, 193, 192, 191, 189, 188, 187, 186, 185, 184, 183, 182, 181, 180, 178, 177, 176, 175, 174, 173, 172, 171, 170, 169, 168, 167, 166, 165, 164, 162, 159, 158, 157, 156, 155, 154, 153, 152, 151, 150, 149, 148, 147, 146, 145, 144, 143, 142, 141, 140, 139, 138, 136, 135, 134, 133, 132, 131, 130, 128, 127, 126, 125, 124, 123, 122, 121, 120, 119, 118, 117, 116, 115, 114, 113, 111, 109, 107, 105, 104, 103, 102, 101, 100, 99, 98, 96, 95, 93, 90, 88, 87, 86, 85, 84, 83, 82, 80, 79, 78, 77, 75, 74, 73, 72, 71, 70, 69, 68, 67, 66, 65, 64, 63, 62, 61, 60, 59, 57, 54, 52, 47, 44, 40, 31, 30, 27, 26, 25, 24, 18, 17, 13, 7, 3, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415, 415 } ; /* Table of booleans, true if rule could match eol. */ static yyconst flex_int32_t yy_rule_can_match_eol[90] = { 0, 1, 0, 1, 0, 0, 1, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 1, 0, 0, }; static yy_state_type yy_last_accepting_state; static char *yy_last_accepting_cpos; extern int sieve_flex_debug; int sieve_flex_debug = 0; /* The intent behind this definition is that it'll catch * any uses of REJECT which flex missed. */ #define REJECT reject_used_but_not_detected #define yymore() yymore_used_but_not_detected #define YY_MORE_ADJ 0 #define YY_RESTORE_YY_MORE_OFFSET char *sievetext; #line 1 "sieve/sieve-lex.l" #line 2 "sieve/sieve-lex.l" /* sieve.l -- sieve lexer * Larry Greenfield * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #ifdef HAVE_CONFIG_H #include #endif #include "xmalloc.h" #include "sieve/tree.h" #include "sieve/sieve_interface.h" #include "sieve/sieve.h" #define YY_NO_INPUT #define YY_DECL int sievelex(YYSTYPE *yylval,sieve_script_t *parse_script) static int tonum(char *c); static char *chkstr(char *); static char *mlbuf; static int mlbufsz, mlcur; extern void sieveerror(sieve_script_t *, char *); #line 813 "sieve/sieve-lex.c" #define INITIAL 0 #define MULTILINE 1 #define QSTRING 2 #ifndef YY_NO_UNISTD_H /* Special case for "unistd.h", since it is non-ANSI. We include it way * down here because we want the user's section 1 to have been scanned first. * The user has a chance to override it with an option. */ #include #endif #ifndef YY_EXTRA_TYPE #define YY_EXTRA_TYPE void * #endif static int yy_init_globals (void ); /* Accessor methods to globals. These are made visible to non-reentrant scanners for convenience. */ int sievelex_destroy (void ); int sieveget_debug (void ); void sieveset_debug (int debug_flag ); YY_EXTRA_TYPE sieveget_extra (void ); void sieveset_extra (YY_EXTRA_TYPE user_defined ); FILE *sieveget_in (void ); void sieveset_in (FILE * _in_str ); FILE *sieveget_out (void ); void sieveset_out (FILE * _out_str ); int sieveget_leng (void ); char *sieveget_text (void ); int sieveget_lineno (void ); void sieveset_lineno (int _line_number ); /* Macros after this point can all be overridden by user definitions in * section 1. */ #ifndef YY_SKIP_YYWRAP #ifdef __cplusplus extern "C" int sievewrap (void ); #else extern int sievewrap (void ); #endif #endif #ifndef YY_NO_UNPUT #endif #ifndef yytext_ptr static void yy_flex_strncpy (char *,yyconst char *,int ); #endif #ifdef YY_NEED_STRLEN static int yy_flex_strlen (yyconst char * ); #endif #ifndef YY_NO_INPUT #ifdef __cplusplus static int yyinput (void ); #else static int input (void ); #endif #endif /* Amount of stuff to slurp up with each read. */ #ifndef YY_READ_BUF_SIZE #ifdef __ia64__ /* On IA-64, the buffer size is 16k, not 8k */ #define YY_READ_BUF_SIZE 16384 #else #define YY_READ_BUF_SIZE 8192 #endif /* __ia64__ */ #endif /* Copy whatever the last rule matched to the standard output. */ #ifndef ECHO /* This used to be an fputs(), but since the string might contain NUL's, * we now use fwrite(). */ #define ECHO do { if (fwrite( sievetext, (size_t) sieveleng, 1, sieveout )) {} } while (0) #endif /* Gets input and stuffs it into "buf". number of characters read, or YY_NULL, * is returned in "result". */ #ifndef YY_INPUT #define YY_INPUT(buf,result,max_size) \ if ( YY_CURRENT_BUFFER_LVALUE->yy_is_interactive ) \ { \ int c = '*'; \ size_t n; \ for ( n = 0; n < max_size && \ (c = getc( sievein )) != EOF && c != '\n'; ++n ) \ buf[n] = (char) c; \ if ( c == '\n' ) \ buf[n++] = (char) c; \ if ( c == EOF && ferror( sievein ) ) \ YY_FATAL_ERROR( "input in flex scanner failed" ); \ result = n; \ } \ else \ { \ errno=0; \ while ( (result = (int) fread(buf, 1, max_size, sievein))==0 && ferror(sievein)) \ { \ if( errno != EINTR) \ { \ YY_FATAL_ERROR( "input in flex scanner failed" ); \ break; \ } \ errno=0; \ clearerr(sievein); \ } \ }\ \ #endif /* No semi-colon after return; correct usage is to write "yyterminate();" - * we don't want an extra ';' after the "return" because that will cause * some compilers to complain about unreachable statements. */ #ifndef yyterminate #define yyterminate() return YY_NULL #endif /* Number of entries by which start-condition stack grows. */ #ifndef YY_START_STACK_INCR #define YY_START_STACK_INCR 25 #endif /* Report a fatal error. */ #ifndef YY_FATAL_ERROR #define YY_FATAL_ERROR(msg) yy_fatal_error( msg ) #endif /* end tables serialization structures and prototypes */ /* Default declaration of generated scanner - a define so the user can * easily add parameters. */ #ifndef YY_DECL #define YY_DECL_IS_OURS 1 extern int sievelex (void); #define YY_DECL int sievelex (void) #endif /* !YY_DECL */ /* Code executed at the beginning of each rule, after sievetext and sieveleng * have been set up. */ #ifndef YY_USER_ACTION #define YY_USER_ACTION #endif /* Code executed at the end of each rule. */ #ifndef YY_BREAK #define YY_BREAK /*LINTED*/break; #endif #define YY_RULE_SETUP \ if ( sieveleng > 0 ) \ YY_CURRENT_BUFFER_LVALUE->yy_at_bol = \ (sievetext[sieveleng - 1] == '\n'); \ YY_USER_ACTION /** The main scanner function which does all the work. */ YY_DECL { yy_state_type yy_current_state; char *yy_cp, *yy_bp; int yy_act; if ( !(yy_init) ) { (yy_init) = 1; #ifdef YY_USER_INIT YY_USER_INIT; #endif if ( ! (yy_start) ) (yy_start) = 1; /* first start state */ if ( ! sievein ) sievein = stdin; if ( ! sieveout ) sieveout = stdout; if ( ! YY_CURRENT_BUFFER ) { sieveensure_buffer_stack (); YY_CURRENT_BUFFER_LVALUE = sieve_create_buffer(sievein,YY_BUF_SIZE ); } sieve_load_buffer_state( ); } { #line 77 "sieve/sieve-lex.l" #line 1036 "sieve/sieve-lex.c" while ( /*CONSTCOND*/1 ) /* loops until end-of-file is reached */ { yy_cp = (yy_c_buf_p); /* Support of sievetext. */ *yy_cp = (yy_hold_char); /* yy_bp points to the position in yy_ch_buf of the start of * the current run. */ yy_bp = yy_cp; yy_current_state = (yy_start); yy_current_state += YY_AT_BOL(); yy_match: do { YY_CHAR yy_c = yy_ec[YY_SC_TO_UI(*yy_cp)] ; if ( yy_accept[yy_current_state] ) { (yy_last_accepting_state) = yy_current_state; (yy_last_accepting_cpos) = yy_cp; } while ( yy_chk[yy_base[yy_current_state] + yy_c] != yy_current_state ) { yy_current_state = (int) yy_def[yy_current_state]; if ( yy_current_state >= 416 ) yy_c = yy_meta[(unsigned int) yy_c]; } yy_current_state = yy_nxt[yy_base[yy_current_state] + (flex_int16_t) yy_c]; ++yy_cp; } while ( yy_base[yy_current_state] != 453 ); yy_find_action: yy_act = yy_accept[yy_current_state]; if ( yy_act == 0 ) { /* have to back up */ yy_cp = (yy_last_accepting_cpos); yy_current_state = (yy_last_accepting_state); yy_act = yy_accept[yy_current_state]; } YY_DO_BEFORE_ACTION; if ( yy_act != YY_END_OF_BUFFER && yy_rule_can_match_eol[yy_act] ) { yy_size_t yyl; for ( yyl = 0; yyl < sieveleng; ++yyl ) if ( sievetext[yyl] == '\n' ) sievelineno++; ; } do_action: /* This label is used only to access EOF actions. */ switch ( yy_act ) { /* beginning of action switch */ case 0: /* must back up */ /* undo the effects of YY_DO_BEFORE_ACTION */ *yy_cp = (yy_hold_char); yy_cp = (yy_last_accepting_cpos); yy_current_state = (yy_last_accepting_state); goto yy_find_action; case 1: /* rule 1 can match eol */ YY_RULE_SETUP #line 78 "sieve/sieve-lex.l" { BEGIN INITIAL; if (mlbuf) mlbuf[mlcur] = '\0'; yylval->sval = chkstr(mlbuf); return STRING; } YY_BREAK case 2: YY_RULE_SETUP #line 81 "sieve/sieve-lex.l" { /* dot stuffing! we want one . */ yyless(1); } YY_BREAK case 3: /* rule 3 can match eol */ YY_RULE_SETUP #line 82 "sieve/sieve-lex.l" { if (mlcur == mlbufsz) mlbuf = xrealloc(mlbuf, 1 + (mlbufsz+=1024)); mlbuf[mlcur++] = sievetext[0]; } YY_BREAK case YY_STATE_EOF(MULTILINE): #line 85 "sieve/sieve-lex.l" { BEGIN INITIAL; sieveerror(parse_script, "unexpected end of file in string"); if (mlbuf) free(mlbuf); yyterminate(); } YY_BREAK case 4: YY_RULE_SETUP #line 89 "sieve/sieve-lex.l" { BEGIN INITIAL; if (mlbuf) mlbuf[mlcur] = '\0'; yylval->sval = chkstr(mlbuf); return STRING; } YY_BREAK case 5: YY_RULE_SETUP #line 92 "sieve/sieve-lex.l" { if (mlcur == mlbufsz) mlbuf = xrealloc(mlbuf, 1 + (mlbufsz+=1024)); mlbuf[mlcur++] = sievetext[1]; } YY_BREAK case 6: /* rule 6 can match eol */ YY_RULE_SETUP #line 95 "sieve/sieve-lex.l" { if (mlcur == mlbufsz) mlbuf = xrealloc(mlbuf, 1 + (mlbufsz+=1024)); mlbuf[mlcur++] = sievetext[0]; } YY_BREAK case YY_STATE_EOF(QSTRING): #line 98 "sieve/sieve-lex.l" { sieveerror(parse_script, "unexpected end of file in string"); if (mlbuf) free(mlbuf); BEGIN INITIAL; yyterminate(); } YY_BREAK case 7: /* rule 7 can match eol */ YY_RULE_SETUP #line 102 "sieve/sieve-lex.l" { BEGIN MULTILINE; mlcur = 0; mlbufsz = 0; mlbuf = NULL; } YY_BREAK case 8: YY_RULE_SETUP #line 104 "sieve/sieve-lex.l" { BEGIN QSTRING; mlcur = 0; mlbufsz = 0; mlbuf = NULL; } YY_BREAK case 9: YY_RULE_SETUP #line 106 "sieve/sieve-lex.l" { yylval->nval = tonum(sievetext); return NUMBER; } YY_BREAK case 10: YY_RULE_SETUP #line 107 "sieve/sieve-lex.l" return IF; YY_BREAK case 11: YY_RULE_SETUP #line 108 "sieve/sieve-lex.l" return ELSIF; YY_BREAK case 12: YY_RULE_SETUP #line 109 "sieve/sieve-lex.l" return ELSE; YY_BREAK case 13: YY_RULE_SETUP #line 110 "sieve/sieve-lex.l" return ANYOF; YY_BREAK case 14: YY_RULE_SETUP #line 111 "sieve/sieve-lex.l" return ALLOF; YY_BREAK case 15: YY_RULE_SETUP #line 112 "sieve/sieve-lex.l" return EXISTS; YY_BREAK case 16: YY_RULE_SETUP #line 113 "sieve/sieve-lex.l" return SFALSE; YY_BREAK case 17: YY_RULE_SETUP #line 114 "sieve/sieve-lex.l" return STRUE; YY_BREAK case 18: YY_RULE_SETUP #line 115 "sieve/sieve-lex.l" return ADDRESS; YY_BREAK case 19: YY_RULE_SETUP #line 116 "sieve/sieve-lex.l" return ENVELOPE; YY_BREAK case 20: YY_RULE_SETUP #line 117 "sieve/sieve-lex.l" return HEADER; YY_BREAK case 21: YY_RULE_SETUP #line 118 "sieve/sieve-lex.l" return BODY; YY_BREAK case 22: YY_RULE_SETUP #line 119 "sieve/sieve-lex.l" return NOT; YY_BREAK case 23: YY_RULE_SETUP #line 120 "sieve/sieve-lex.l" return SIZE; YY_BREAK case 24: YY_RULE_SETUP #line 121 "sieve/sieve-lex.l" return HASFLAG; YY_BREAK case 25: YY_RULE_SETUP #line 122 "sieve/sieve-lex.l" return REJCT; YY_BREAK case 26: YY_RULE_SETUP #line 123 "sieve/sieve-lex.l" return FILEINTO; YY_BREAK case 27: YY_RULE_SETUP #line 124 "sieve/sieve-lex.l" return REDIRECT; YY_BREAK case 28: YY_RULE_SETUP #line 125 "sieve/sieve-lex.l" return KEEP; YY_BREAK case 29: YY_RULE_SETUP #line 126 "sieve/sieve-lex.l" return REQUIRE; YY_BREAK case 30: YY_RULE_SETUP #line 127 "sieve/sieve-lex.l" return STOP; YY_BREAK case 31: YY_RULE_SETUP #line 128 "sieve/sieve-lex.l" return DISCARD; YY_BREAK case 32: YY_RULE_SETUP #line 129 "sieve/sieve-lex.l" return SETFLAG; YY_BREAK case 33: YY_RULE_SETUP #line 130 "sieve/sieve-lex.l" return ADDFLAG; YY_BREAK case 34: YY_RULE_SETUP #line 131 "sieve/sieve-lex.l" return REMOVEFLAG; YY_BREAK case 35: YY_RULE_SETUP #line 132 "sieve/sieve-lex.l" return MARK; YY_BREAK case 36: YY_RULE_SETUP #line 133 "sieve/sieve-lex.l" return UNMARK; YY_BREAK case 37: YY_RULE_SETUP #line 134 "sieve/sieve-lex.l" return NOTIFY; YY_BREAK case 38: YY_RULE_SETUP #line 135 "sieve/sieve-lex.l" return DENOTIFY; YY_BREAK case 39: YY_RULE_SETUP #line 136 "sieve/sieve-lex.l" return ID; YY_BREAK case 40: YY_RULE_SETUP #line 137 "sieve/sieve-lex.l" return METHOD; YY_BREAK case 41: YY_RULE_SETUP #line 138 "sieve/sieve-lex.l" return OPTIONS; YY_BREAK case 42: YY_RULE_SETUP #line 139 "sieve/sieve-lex.l" return LOW; YY_BREAK case 43: YY_RULE_SETUP #line 140 "sieve/sieve-lex.l" return NORMAL; YY_BREAK case 44: YY_RULE_SETUP #line 141 "sieve/sieve-lex.l" return HIGH; YY_BREAK case 45: YY_RULE_SETUP #line 142 "sieve/sieve-lex.l" return MESSAGE; YY_BREAK case 46: YY_RULE_SETUP #line 143 "sieve/sieve-lex.l" return VACATION; YY_BREAK case 47: YY_RULE_SETUP #line 144 "sieve/sieve-lex.l" return DAYS; YY_BREAK case 48: YY_RULE_SETUP #line 145 "sieve/sieve-lex.l" return SECONDS; YY_BREAK case 49: YY_RULE_SETUP #line 146 "sieve/sieve-lex.l" return ADDRESSES; YY_BREAK case 50: YY_RULE_SETUP #line 147 "sieve/sieve-lex.l" return SUBJECT; YY_BREAK case 51: YY_RULE_SETUP #line 148 "sieve/sieve-lex.l" return FROM; YY_BREAK case 52: YY_RULE_SETUP #line 149 "sieve/sieve-lex.l" return HANDLE; YY_BREAK case 53: YY_RULE_SETUP #line 150 "sieve/sieve-lex.l" return MIME; YY_BREAK case 54: YY_RULE_SETUP #line 151 "sieve/sieve-lex.l" return COMPARATOR; YY_BREAK case 55: YY_RULE_SETUP #line 152 "sieve/sieve-lex.l" return IS; YY_BREAK case 56: YY_RULE_SETUP #line 153 "sieve/sieve-lex.l" return CONTAINS; YY_BREAK case 57: YY_RULE_SETUP #line 154 "sieve/sieve-lex.l" return MATCHES; YY_BREAK case 58: YY_RULE_SETUP #line 155 "sieve/sieve-lex.l" return REGEX; YY_BREAK case 59: YY_RULE_SETUP #line 156 "sieve/sieve-lex.l" return COUNT; YY_BREAK case 60: YY_RULE_SETUP #line 157 "sieve/sieve-lex.l" return VALUE; YY_BREAK case 61: YY_RULE_SETUP #line 158 "sieve/sieve-lex.l" return OVER; YY_BREAK case 62: YY_RULE_SETUP #line 159 "sieve/sieve-lex.l" return UNDER; YY_BREAK case 63: YY_RULE_SETUP #line 160 "sieve/sieve-lex.l" return ALL; YY_BREAK case 64: YY_RULE_SETUP #line 161 "sieve/sieve-lex.l" return LOCALPART; YY_BREAK case 65: YY_RULE_SETUP #line 162 "sieve/sieve-lex.l" return DOMAIN; YY_BREAK case 66: YY_RULE_SETUP #line 163 "sieve/sieve-lex.l" return USER; YY_BREAK case 67: YY_RULE_SETUP #line 164 "sieve/sieve-lex.l" return DETAIL; YY_BREAK case 68: YY_RULE_SETUP #line 165 "sieve/sieve-lex.l" return RAW; YY_BREAK case 69: YY_RULE_SETUP #line 166 "sieve/sieve-lex.l" return TEXT; YY_BREAK case 70: YY_RULE_SETUP #line 167 "sieve/sieve-lex.l" return CONTENT; YY_BREAK case 71: YY_RULE_SETUP #line 168 "sieve/sieve-lex.l" return INCLUDE; YY_BREAK case 72: YY_RULE_SETUP #line 169 "sieve/sieve-lex.l" return PERSONAL; YY_BREAK case 73: YY_RULE_SETUP #line 170 "sieve/sieve-lex.l" return GLOBAL; YY_BREAK case 74: YY_RULE_SETUP #line 171 "sieve/sieve-lex.l" return OPTIONAL; YY_BREAK case 75: YY_RULE_SETUP #line 172 "sieve/sieve-lex.l" return ONCE; YY_BREAK case 76: YY_RULE_SETUP #line 173 "sieve/sieve-lex.l" return RETURN; YY_BREAK case 77: YY_RULE_SETUP #line 174 "sieve/sieve-lex.l" return COPY; YY_BREAK case 78: YY_RULE_SETUP #line 175 "sieve/sieve-lex.l" return DATE; YY_BREAK case 79: YY_RULE_SETUP #line 176 "sieve/sieve-lex.l" return CURRENTDATE; YY_BREAK case 80: YY_RULE_SETUP #line 177 "sieve/sieve-lex.l" return INDEX; YY_BREAK case 81: YY_RULE_SETUP #line 178 "sieve/sieve-lex.l" return LAST; YY_BREAK case 82: YY_RULE_SETUP #line 179 "sieve/sieve-lex.l" return ZONE; YY_BREAK case 83: YY_RULE_SETUP #line 180 "sieve/sieve-lex.l" return ORIGINALZONE; YY_BREAK case 84: YY_RULE_SETUP #line 181 "sieve/sieve-lex.l" return FLAGS; YY_BREAK case 85: /* rule 85 can match eol */ YY_RULE_SETUP #line 182 "sieve/sieve-lex.l" ; /* ignore whitespace */ YY_BREAK case 86: YY_RULE_SETUP #line 183 "sieve/sieve-lex.l" ; /* ignore hash comments */ YY_BREAK case 87: /* rule 87 can match eol */ YY_RULE_SETUP #line 184 "sieve/sieve-lex.l" ; /* ignore bracket comments */ YY_BREAK case 88: YY_RULE_SETUP #line 185 "sieve/sieve-lex.l" return sievetext[0]; YY_BREAK case 89: YY_RULE_SETUP #line 187 "sieve/sieve-lex.l" ECHO; YY_BREAK #line 1581 "sieve/sieve-lex.c" case YY_STATE_EOF(INITIAL): yyterminate(); case YY_END_OF_BUFFER: { /* Amount of text matched not including the EOB char. */ int yy_amount_of_matched_text = (int) (yy_cp - (yytext_ptr)) - 1; /* Undo the effects of YY_DO_BEFORE_ACTION. */ *yy_cp = (yy_hold_char); YY_RESTORE_YY_MORE_OFFSET if ( YY_CURRENT_BUFFER_LVALUE->yy_buffer_status == YY_BUFFER_NEW ) { /* We're scanning a new file or input source. It's * possible that this happened because the user * just pointed sievein at a new source and called * sievelex(). If so, then we have to assure * consistency between YY_CURRENT_BUFFER and our * globals. Here is the right place to do so, because * this is the first action (other than possibly a * back-up) that will match for the new input source. */ (yy_n_chars) = YY_CURRENT_BUFFER_LVALUE->yy_n_chars; YY_CURRENT_BUFFER_LVALUE->yy_input_file = sievein; YY_CURRENT_BUFFER_LVALUE->yy_buffer_status = YY_BUFFER_NORMAL; } /* Note that here we test for yy_c_buf_p "<=" to the position * of the first EOB in the buffer, since yy_c_buf_p will * already have been incremented past the NUL character * (since all states make transitions on EOB to the * end-of-buffer state). Contrast this with the test * in input(). */ if ( (yy_c_buf_p) <= &YY_CURRENT_BUFFER_LVALUE->yy_ch_buf[(yy_n_chars)] ) { /* This was really a NUL. */ yy_state_type yy_next_state; (yy_c_buf_p) = (yytext_ptr) + yy_amount_of_matched_text; yy_current_state = yy_get_previous_state( ); /* Okay, we're now positioned to make the NUL * transition. We couldn't have * yy_get_previous_state() go ahead and do it * for us because it doesn't know how to deal * with the possibility of jamming (and we don't * want to build jamming into it because then it * will run more slowly). */ yy_next_state = yy_try_NUL_trans( yy_current_state ); yy_bp = (yytext_ptr) + YY_MORE_ADJ; if ( yy_next_state ) { /* Consume the NUL. */ yy_cp = ++(yy_c_buf_p); yy_current_state = yy_next_state; goto yy_match; } else { yy_cp = (yy_c_buf_p); goto yy_find_action; } } else switch ( yy_get_next_buffer( ) ) { case EOB_ACT_END_OF_FILE: { (yy_did_buffer_switch_on_eof) = 0; if ( sievewrap( ) ) { /* Note: because we've taken care in * yy_get_next_buffer() to have set up * sievetext, we can now set up * yy_c_buf_p so that if some total * hoser (like flex itself) wants to * call the scanner after we return the * YY_NULL, it'll still work - another * YY_NULL will get returned. */ (yy_c_buf_p) = (yytext_ptr) + YY_MORE_ADJ; yy_act = YY_STATE_EOF(YY_START); goto do_action; } else { if ( ! (yy_did_buffer_switch_on_eof) ) YY_NEW_FILE; } break; } case EOB_ACT_CONTINUE_SCAN: (yy_c_buf_p) = (yytext_ptr) + yy_amount_of_matched_text; yy_current_state = yy_get_previous_state( ); yy_cp = (yy_c_buf_p); yy_bp = (yytext_ptr) + YY_MORE_ADJ; goto yy_match; case EOB_ACT_LAST_MATCH: (yy_c_buf_p) = &YY_CURRENT_BUFFER_LVALUE->yy_ch_buf[(yy_n_chars)]; yy_current_state = yy_get_previous_state( ); yy_cp = (yy_c_buf_p); yy_bp = (yytext_ptr) + YY_MORE_ADJ; goto yy_find_action; } break; } default: YY_FATAL_ERROR( "fatal flex scanner internal error--no action found" ); } /* end of action switch */ } /* end of scanning one token */ } /* end of user's declarations */ } /* end of sievelex */ /* yy_get_next_buffer - try to read in a new buffer * * Returns a code representing an action: * EOB_ACT_LAST_MATCH - * EOB_ACT_CONTINUE_SCAN - continue scanning from current position * EOB_ACT_END_OF_FILE - end of file */ static int yy_get_next_buffer (void) { char *dest = YY_CURRENT_BUFFER_LVALUE->yy_ch_buf; char *source = (yytext_ptr); yy_size_t number_to_move, i; int ret_val; if ( (yy_c_buf_p) > &YY_CURRENT_BUFFER_LVALUE->yy_ch_buf[(yy_n_chars) + 1] ) YY_FATAL_ERROR( "fatal flex scanner internal error--end of buffer missed" ); if ( YY_CURRENT_BUFFER_LVALUE->yy_fill_buffer == 0 ) { /* Don't try to fill the buffer, so this is an EOF. */ if ( (yy_c_buf_p) - (yytext_ptr) - YY_MORE_ADJ == 1 ) { /* We matched a single character, the EOB, so * treat this as a final EOF. */ return EOB_ACT_END_OF_FILE; } else { /* We matched some text prior to the EOB, first * process it. */ return EOB_ACT_LAST_MATCH; } } /* Try to read more data. */ /* First move last chars to start of buffer. */ number_to_move = (yy_size_t) ((yy_c_buf_p) - (yytext_ptr)) - 1; for ( i = 0; i < number_to_move; ++i ) *(dest++) = *(source++); if ( YY_CURRENT_BUFFER_LVALUE->yy_buffer_status == YY_BUFFER_EOF_PENDING ) /* don't do the read, it's not guaranteed to return an EOF, * just force an EOF */ YY_CURRENT_BUFFER_LVALUE->yy_n_chars = (yy_n_chars) = 0; else { int num_to_read = YY_CURRENT_BUFFER_LVALUE->yy_buf_size - number_to_move - 1; while ( num_to_read <= 0 ) { /* Not enough room in the buffer - grow it. */ /* just a shorter name for the current buffer */ YY_BUFFER_STATE b = YY_CURRENT_BUFFER_LVALUE; int yy_c_buf_p_offset = (int) ((yy_c_buf_p) - b->yy_ch_buf); if ( b->yy_is_our_buffer ) { int new_size = b->yy_buf_size * 2; if ( new_size <= 0 ) b->yy_buf_size += b->yy_buf_size / 8; else b->yy_buf_size *= 2; b->yy_ch_buf = (char *) /* Include room in for 2 EOB chars. */ sieverealloc((void *) b->yy_ch_buf,b->yy_buf_size + 2 ); } else /* Can't grow it, we don't own it. */ b->yy_ch_buf = NULL; if ( ! b->yy_ch_buf ) YY_FATAL_ERROR( "fatal error - scanner input buffer overflow" ); (yy_c_buf_p) = &b->yy_ch_buf[yy_c_buf_p_offset]; num_to_read = YY_CURRENT_BUFFER_LVALUE->yy_buf_size - number_to_move - 1; } if ( num_to_read > YY_READ_BUF_SIZE ) num_to_read = YY_READ_BUF_SIZE; /* Read in more data. */ YY_INPUT( (&YY_CURRENT_BUFFER_LVALUE->yy_ch_buf[number_to_move]), (yy_n_chars), num_to_read ); YY_CURRENT_BUFFER_LVALUE->yy_n_chars = (yy_n_chars); } if ( (yy_n_chars) == 0 ) { if ( number_to_move == YY_MORE_ADJ ) { ret_val = EOB_ACT_END_OF_FILE; sieverestart(sievein ); } else { ret_val = EOB_ACT_LAST_MATCH; YY_CURRENT_BUFFER_LVALUE->yy_buffer_status = YY_BUFFER_EOF_PENDING; } } else ret_val = EOB_ACT_CONTINUE_SCAN; if ((int) ((yy_n_chars) + number_to_move) > YY_CURRENT_BUFFER_LVALUE->yy_buf_size) { /* Extend the array by 50%, plus the number we really need. */ int new_size = (yy_n_chars) + number_to_move + ((yy_n_chars) >> 1); YY_CURRENT_BUFFER_LVALUE->yy_ch_buf = (char *) sieverealloc((void *) YY_CURRENT_BUFFER_LVALUE->yy_ch_buf,new_size ); if ( ! YY_CURRENT_BUFFER_LVALUE->yy_ch_buf ) YY_FATAL_ERROR( "out of dynamic memory in yy_get_next_buffer()" ); } (yy_n_chars) += number_to_move; YY_CURRENT_BUFFER_LVALUE->yy_ch_buf[(yy_n_chars)] = YY_END_OF_BUFFER_CHAR; YY_CURRENT_BUFFER_LVALUE->yy_ch_buf[(yy_n_chars) + 1] = YY_END_OF_BUFFER_CHAR; (yytext_ptr) = &YY_CURRENT_BUFFER_LVALUE->yy_ch_buf[0]; return ret_val; } /* yy_get_previous_state - get the state just before the EOB char was reached */ static yy_state_type yy_get_previous_state (void) { yy_state_type yy_current_state; char *yy_cp; yy_current_state = (yy_start); yy_current_state += YY_AT_BOL(); for ( yy_cp = (yytext_ptr) + YY_MORE_ADJ; yy_cp < (yy_c_buf_p); ++yy_cp ) { YY_CHAR yy_c = (*yy_cp ? yy_ec[YY_SC_TO_UI(*yy_cp)] : 1); if ( yy_accept[yy_current_state] ) { (yy_last_accepting_state) = yy_current_state; (yy_last_accepting_cpos) = yy_cp; } while ( yy_chk[yy_base[yy_current_state] + yy_c] != yy_current_state ) { yy_current_state = (int) yy_def[yy_current_state]; if ( yy_current_state >= 416 ) yy_c = yy_meta[(unsigned int) yy_c]; } yy_current_state = yy_nxt[yy_base[yy_current_state] + (flex_int16_t) yy_c]; } return yy_current_state; } /* yy_try_NUL_trans - try to make a transition on the NUL character * * synopsis * next_state = yy_try_NUL_trans( current_state ); */ static yy_state_type yy_try_NUL_trans (yy_state_type yy_current_state ) { int yy_is_jam; char *yy_cp = (yy_c_buf_p); YY_CHAR yy_c = 1; if ( yy_accept[yy_current_state] ) { (yy_last_accepting_state) = yy_current_state; (yy_last_accepting_cpos) = yy_cp; } while ( yy_chk[yy_base[yy_current_state] + yy_c] != yy_current_state ) { yy_current_state = (int) yy_def[yy_current_state]; if ( yy_current_state >= 416 ) yy_c = yy_meta[(unsigned int) yy_c]; } yy_current_state = yy_nxt[yy_base[yy_current_state] + (flex_int16_t) yy_c]; yy_is_jam = (yy_current_state == 415); return yy_is_jam ? 0 : yy_current_state; } #ifndef YY_NO_UNPUT #endif #ifndef YY_NO_INPUT #ifdef __cplusplus static int yyinput (void) #else static int input (void) #endif { int c; *(yy_c_buf_p) = (yy_hold_char); if ( *(yy_c_buf_p) == YY_END_OF_BUFFER_CHAR ) { /* yy_c_buf_p now points to the character we want to return. * If this occurs *before* the EOB characters, then it's a * valid NUL; if not, then we've hit the end of the buffer. */ if ( (yy_c_buf_p) < &YY_CURRENT_BUFFER_LVALUE->yy_ch_buf[(yy_n_chars)] ) /* This was really a NUL. */ *(yy_c_buf_p) = '\0'; else { /* need more input */ int offset = (yy_c_buf_p) - (yytext_ptr); ++(yy_c_buf_p); switch ( yy_get_next_buffer( ) ) { case EOB_ACT_LAST_MATCH: /* This happens because yy_g_n_b() * sees that we've accumulated a * token and flags that we need to * try matching the token before * proceeding. But for input(), * there's no matching to consider. * So convert the EOB_ACT_LAST_MATCH * to EOB_ACT_END_OF_FILE. */ /* Reset buffer status. */ sieverestart(sievein ); /*FALLTHROUGH*/ case EOB_ACT_END_OF_FILE: { if ( sievewrap( ) ) return 0; if ( ! (yy_did_buffer_switch_on_eof) ) YY_NEW_FILE; #ifdef __cplusplus return yyinput(); #else return input(); #endif } case EOB_ACT_CONTINUE_SCAN: (yy_c_buf_p) = (yytext_ptr) + offset; break; } } } c = *(unsigned char *) (yy_c_buf_p); /* cast for 8-bit char's */ *(yy_c_buf_p) = '\0'; /* preserve sievetext */ (yy_hold_char) = *++(yy_c_buf_p); YY_CURRENT_BUFFER_LVALUE->yy_at_bol = (c == '\n'); if ( YY_CURRENT_BUFFER_LVALUE->yy_at_bol ) sievelineno++; ; return c; } #endif /* ifndef YY_NO_INPUT */ /** Immediately switch to a different input stream. * @param input_file A readable stream. * * @note This function does not reset the start condition to @c INITIAL . */ void sieverestart (FILE * input_file ) { if ( ! YY_CURRENT_BUFFER ){ sieveensure_buffer_stack (); YY_CURRENT_BUFFER_LVALUE = sieve_create_buffer(sievein,YY_BUF_SIZE ); } sieve_init_buffer(YY_CURRENT_BUFFER,input_file ); sieve_load_buffer_state( ); } /** Switch to a different input buffer. * @param new_buffer The new input buffer. * */ void sieve_switch_to_buffer (YY_BUFFER_STATE new_buffer ) { /* TODO. We should be able to replace this entire function body * with * sievepop_buffer_state(); * sievepush_buffer_state(new_buffer); */ sieveensure_buffer_stack (); if ( YY_CURRENT_BUFFER == new_buffer ) return; if ( YY_CURRENT_BUFFER ) { /* Flush out information for old buffer. */ *(yy_c_buf_p) = (yy_hold_char); YY_CURRENT_BUFFER_LVALUE->yy_buf_pos = (yy_c_buf_p); YY_CURRENT_BUFFER_LVALUE->yy_n_chars = (yy_n_chars); } YY_CURRENT_BUFFER_LVALUE = new_buffer; sieve_load_buffer_state( ); /* We don't actually know whether we did this switch during * EOF (sievewrap()) processing, but the only time this flag * is looked at is after sievewrap() is called, so it's safe * to go ahead and always set it. */ (yy_did_buffer_switch_on_eof) = 1; } static void sieve_load_buffer_state (void) { (yy_n_chars) = YY_CURRENT_BUFFER_LVALUE->yy_n_chars; (yytext_ptr) = (yy_c_buf_p) = YY_CURRENT_BUFFER_LVALUE->yy_buf_pos; sievein = YY_CURRENT_BUFFER_LVALUE->yy_input_file; (yy_hold_char) = *(yy_c_buf_p); } /** Allocate and initialize an input buffer state. * @param file A readable stream. * @param size The character buffer size in bytes. When in doubt, use @c YY_BUF_SIZE. * * @return the allocated buffer state. */ YY_BUFFER_STATE sieve_create_buffer (FILE * file, int size ) { YY_BUFFER_STATE b; b = (YY_BUFFER_STATE) sievealloc(sizeof( struct yy_buffer_state ) ); if ( ! b ) YY_FATAL_ERROR( "out of dynamic memory in sieve_create_buffer()" ); b->yy_buf_size = (yy_size_t)size; /* yy_ch_buf has to be 2 characters longer than the size given because * we need to put in 2 end-of-buffer characters. */ b->yy_ch_buf = (char *) sievealloc(b->yy_buf_size + 2 ); if ( ! b->yy_ch_buf ) YY_FATAL_ERROR( "out of dynamic memory in sieve_create_buffer()" ); b->yy_is_our_buffer = 1; sieve_init_buffer(b,file ); return b; } /** Destroy the buffer. * @param b a buffer created with sieve_create_buffer() * */ void sieve_delete_buffer (YY_BUFFER_STATE b ) { if ( ! b ) return; if ( b == YY_CURRENT_BUFFER ) /* Not sure if we should pop here. */ YY_CURRENT_BUFFER_LVALUE = (YY_BUFFER_STATE) 0; if ( b->yy_is_our_buffer ) sievefree((void *) b->yy_ch_buf ); sievefree((void *) b ); } /* Initializes or reinitializes a buffer. * This function is sometimes called more than once on the same buffer, * such as during a sieverestart() or at EOF. */ static void sieve_init_buffer (YY_BUFFER_STATE b, FILE * file ) { int oerrno = errno; sieve_flush_buffer(b ); b->yy_input_file = file; b->yy_fill_buffer = 1; /* If b is the current buffer, then sieve_init_buffer was _probably_ * called from sieverestart() or through yy_get_next_buffer. * In that case, we don't want to reset the lineno or column. */ if (b != YY_CURRENT_BUFFER){ b->yy_bs_lineno = 1; b->yy_bs_column = 0; } b->yy_is_interactive = file ? (isatty( fileno(file) ) > 0) : 0; errno = oerrno; } /** Discard all buffered characters. On the next scan, YY_INPUT will be called. * @param b the buffer state to be flushed, usually @c YY_CURRENT_BUFFER. * */ void sieve_flush_buffer (YY_BUFFER_STATE b ) { if ( ! b ) return; b->yy_n_chars = 0; /* We always need two end-of-buffer characters. The first causes * a transition to the end-of-buffer state. The second causes * a jam in that state. */ b->yy_ch_buf[0] = YY_END_OF_BUFFER_CHAR; b->yy_ch_buf[1] = YY_END_OF_BUFFER_CHAR; b->yy_buf_pos = &b->yy_ch_buf[0]; b->yy_at_bol = 1; b->yy_buffer_status = YY_BUFFER_NEW; if ( b == YY_CURRENT_BUFFER ) sieve_load_buffer_state( ); } /** Pushes the new state onto the stack. The new state becomes * the current state. This function will allocate the stack * if necessary. * @param new_buffer The new state. * */ void sievepush_buffer_state (YY_BUFFER_STATE new_buffer ) { if (new_buffer == NULL) return; sieveensure_buffer_stack(); /* This block is copied from sieve_switch_to_buffer. */ if ( YY_CURRENT_BUFFER ) { /* Flush out information for old buffer. */ *(yy_c_buf_p) = (yy_hold_char); YY_CURRENT_BUFFER_LVALUE->yy_buf_pos = (yy_c_buf_p); YY_CURRENT_BUFFER_LVALUE->yy_n_chars = (yy_n_chars); } /* Only push if top exists. Otherwise, replace top. */ if (YY_CURRENT_BUFFER) (yy_buffer_stack_top)++; YY_CURRENT_BUFFER_LVALUE = new_buffer; /* copied from sieve_switch_to_buffer. */ sieve_load_buffer_state( ); (yy_did_buffer_switch_on_eof) = 1; } /** Removes and deletes the top of the stack, if present. * The next element becomes the new top. * */ void sievepop_buffer_state (void) { if (!YY_CURRENT_BUFFER) return; sieve_delete_buffer(YY_CURRENT_BUFFER ); YY_CURRENT_BUFFER_LVALUE = NULL; if ((yy_buffer_stack_top) > 0) --(yy_buffer_stack_top); if (YY_CURRENT_BUFFER) { sieve_load_buffer_state( ); (yy_did_buffer_switch_on_eof) = 1; } } /* Allocates the stack if it does not exist. * Guarantees space for at least one push. */ static void sieveensure_buffer_stack (void) { int num_to_alloc; if (!(yy_buffer_stack)) { /* First allocation is just for 2 elements, since we don't know if this * scanner will even need a stack. We use 2 instead of 1 to avoid an * immediate realloc on the next call. */ num_to_alloc = 1; /* After all that talk, this was set to 1 anyways... */ (yy_buffer_stack) = (struct yy_buffer_state**)sievealloc (num_to_alloc * sizeof(struct yy_buffer_state*) ); if ( ! (yy_buffer_stack) ) YY_FATAL_ERROR( "out of dynamic memory in sieveensure_buffer_stack()" ); memset((yy_buffer_stack), 0, num_to_alloc * sizeof(struct yy_buffer_state*)); (yy_buffer_stack_max) = num_to_alloc; (yy_buffer_stack_top) = 0; return; } if ((yy_buffer_stack_top) >= ((yy_buffer_stack_max)) - 1){ /* Increase the buffer to prepare for a possible push. */ yy_size_t grow_size = 8 /* arbitrary grow size */; num_to_alloc = (yy_buffer_stack_max) + grow_size; (yy_buffer_stack) = (struct yy_buffer_state**)sieverealloc ((yy_buffer_stack), num_to_alloc * sizeof(struct yy_buffer_state*) ); if ( ! (yy_buffer_stack) ) YY_FATAL_ERROR( "out of dynamic memory in sieveensure_buffer_stack()" ); /* zero only the new slots.*/ memset((yy_buffer_stack) + (yy_buffer_stack_max), 0, grow_size * sizeof(struct yy_buffer_state*)); (yy_buffer_stack_max) = num_to_alloc; } } /** Setup the input buffer state to scan directly from a user-specified character buffer. * @param base the character buffer * @param size the size in bytes of the character buffer * * @return the newly allocated buffer state object. */ YY_BUFFER_STATE sieve_scan_buffer (char * base, yy_size_t size ) { YY_BUFFER_STATE b; if ( size < 2 || base[size-2] != YY_END_OF_BUFFER_CHAR || base[size-1] != YY_END_OF_BUFFER_CHAR ) /* They forgot to leave room for the EOB's. */ return NULL; b = (YY_BUFFER_STATE) sievealloc(sizeof( struct yy_buffer_state ) ); if ( ! b ) YY_FATAL_ERROR( "out of dynamic memory in sieve_scan_buffer()" ); b->yy_buf_size = size - 2; /* "- 2" to take care of EOB's */ b->yy_buf_pos = b->yy_ch_buf = base; b->yy_is_our_buffer = 0; b->yy_input_file = NULL; b->yy_n_chars = b->yy_buf_size; b->yy_is_interactive = 0; b->yy_at_bol = 1; b->yy_fill_buffer = 0; b->yy_buffer_status = YY_BUFFER_NEW; sieve_switch_to_buffer(b ); return b; } /** Setup the input buffer state to scan a string. The next call to sievelex() will * scan from a @e copy of @a str. * @param yystr a NUL-terminated string to scan * * @return the newly allocated buffer state object. * @note If you want to scan bytes that may contain NUL values, then use * sieve_scan_bytes() instead. */ YY_BUFFER_STATE sieve_scan_string (yyconst char * yystr ) { return sieve_scan_bytes(yystr,(int) strlen(yystr) ); } /** Setup the input buffer state to scan the given bytes. The next call to sievelex() will * scan from a @e copy of @a bytes. * @param yybytes the byte buffer to scan * @param _yybytes_len the number of bytes in the buffer pointed to by @a bytes. * * @return the newly allocated buffer state object. */ YY_BUFFER_STATE sieve_scan_bytes (yyconst char * yybytes, int _yybytes_len ) { YY_BUFFER_STATE b; char *buf; yy_size_t n; yy_size_t i; /* Get memory for full buffer, including space for trailing EOB's. */ n = (yy_size_t) _yybytes_len + 2; buf = (char *) sievealloc(n ); if ( ! buf ) YY_FATAL_ERROR( "out of dynamic memory in sieve_scan_bytes()" ); for ( i = 0; i < _yybytes_len; ++i ) buf[i] = yybytes[i]; buf[_yybytes_len] = buf[_yybytes_len+1] = YY_END_OF_BUFFER_CHAR; b = sieve_scan_buffer(buf,n ); if ( ! b ) YY_FATAL_ERROR( "bad buffer in sieve_scan_bytes()" ); /* It's okay to grow etc. this buffer, and we should throw it * away when we're done. */ b->yy_is_our_buffer = 1; return b; } #ifndef YY_EXIT_FAILURE #define YY_EXIT_FAILURE 2 #endif static void yynoreturn yy_fatal_error (yyconst char* msg ) { (void) fprintf( stderr, "%s\n", msg ); exit( YY_EXIT_FAILURE ); } /* Redefine yyless() so it works in section 3 code. */ #undef yyless #define yyless(n) \ do \ { \ /* Undo effects of setting up sievetext. */ \ int yyless_macro_arg = (n); \ YY_LESS_LINENO(yyless_macro_arg);\ sievetext[sieveleng] = (yy_hold_char); \ (yy_c_buf_p) = sievetext + yyless_macro_arg; \ (yy_hold_char) = *(yy_c_buf_p); \ *(yy_c_buf_p) = '\0'; \ sieveleng = yyless_macro_arg; \ } \ while ( 0 ) /* Accessor methods (get/set functions) to struct members. */ /** Get the current line number. * */ int sieveget_lineno (void) { return sievelineno; } /** Get the input stream. * */ FILE *sieveget_in (void) { return sievein; } /** Get the output stream. * */ FILE *sieveget_out (void) { return sieveout; } /** Get the length of the current token. * */ int sieveget_leng (void) { return sieveleng; } /** Get the current token. * */ char *sieveget_text (void) { return sievetext; } /** Set the current line number. * @param _line_number line number * */ void sieveset_lineno (int _line_number ) { sievelineno = _line_number; } /** Set the input stream. This does not discard the current * input buffer. * @param _in_str A readable stream. * * @see sieve_switch_to_buffer */ void sieveset_in (FILE * _in_str ) { sievein = _in_str ; } void sieveset_out (FILE * _out_str ) { sieveout = _out_str ; } int sieveget_debug (void) { return sieve_flex_debug; } void sieveset_debug (int _bdebug ) { sieve_flex_debug = _bdebug ; } static int yy_init_globals (void) { /* Initialization is the same as for the non-reentrant scanner. * This function is called from sievelex_destroy(), so don't allocate here. */ /* We do not touch sievelineno unless the option is enabled. */ sievelineno = 1; (yy_buffer_stack) = NULL; (yy_buffer_stack_top) = 0; (yy_buffer_stack_max) = 0; (yy_c_buf_p) = NULL; (yy_init) = 0; (yy_start) = 0; /* Defined in main.c */ #ifdef YY_STDINIT sievein = stdin; sieveout = stdout; #else sievein = NULL; sieveout = NULL; #endif /* For future reference: Set errno on error, since we are called by * sievelex_init() */ return 0; } /* sievelex_destroy is for both reentrant and non-reentrant scanners. */ int sievelex_destroy (void) { /* Pop the buffer stack, destroying each element. */ while(YY_CURRENT_BUFFER){ sieve_delete_buffer(YY_CURRENT_BUFFER ); YY_CURRENT_BUFFER_LVALUE = NULL; sievepop_buffer_state(); } /* Destroy the stack itself. */ sievefree((yy_buffer_stack) ); (yy_buffer_stack) = NULL; /* Reset the globals. This is important in a non-reentrant scanner so the next time * sievelex() is called, initialization will occur. */ yy_init_globals( ); return 0; } /* * Internal utility routines. */ #ifndef yytext_ptr static void yy_flex_strncpy (char* s1, yyconst char * s2, int n ) { int i; for ( i = 0; i < n; ++i ) s1[i] = s2[i]; } #endif #ifdef YY_NEED_STRLEN static int yy_flex_strlen (yyconst char * s ) { int n; for ( n = 0; s[n]; ++n ) ; return n; } #endif void *sievealloc (yy_size_t size ) { return malloc(size); } void *sieverealloc (void * ptr, yy_size_t size ) { /* The cast to (char *) in the following accommodates both * implementations that use char* generic pointers, and those * that use void* generic pointers. It works with the latter * because both ANSI C and C++ allow castless assignment from * any pointer type to void*, and deal with argument conversions * as though doing an assignment. */ return realloc(ptr, size); } void sievefree (void * ptr ) { free( (char *) ptr ); /* see sieverealloc() for (char *) cast */ } #define YYTABLES_NAME "yytables" #line 187 "sieve/sieve-lex.l" /* */ static int tonum(char *c) { int val = atoi(c); switch (c[strlen(c)-1]) { case 'K': case 'k': val *= (1 << 10); break; case 'M': case 'm': val *= (1 << 20); break; case 'G': case 'g': val *= (1 << 30); break; default: break; } return val; } /* convert NULL strings to "" */ static char *chkstr(char *str) { if (!str) return xstrdup(""); else return str; } cyrus-imapd-2.5.10/sieve/flags.c0000644000175000017500000000262513001236020013320 00000000000000/* * flags.c * * Created on: Oct 6, 2014 * Author: James Cassell */ #include "flags.h" #include "imparse.h" #include "strarray.h" #include "util.h" #include "xmalloc.h" static int verify_flag(char *f) { if (f[0] == '\\') { lcase(f); if (strcmp(f, "\\seen") && strcmp(f, "\\answered") && strcmp(f, "\\flagged") && strcmp(f, "\\draft") && strcmp(f, "\\deleted")) { return 0; } return 1; } if (!imparse_isatom(f)) { return 0; } return 1; } EXPORTED int verify_flaglist(strarray_t *sl) { int i; char *joined; strarray_t *resplit; // Join all the flags, putting spaces between them joined = strarray_join(sl, " "); // Clear out the sl for reuse strarray_truncate(sl, 0); // Split the joined flag list at spaces resplit = strarray_split(joined, " ", STRARRAY_TRIM); // Perform duplicate elimination and flag verification for (i = 0; i < resplit->count ; i++) { // has the side effect of lower-casing system flags if (!verify_flag(resplit->data[i])) { /* [IMAP4FLAGS] Section 2 "General Requirements for Flag * Handling" says "If a flag validity check fails, the * flag MUST be ignored", which for us means that we * simply remove the invalid flag from the list. */ continue; } strarray_add_case(sl, resplit->data[i]); } strarray_free(resplit); free(joined); return sl->count; } cyrus-imapd-2.5.10/sieve/test.c0000644000175000017500000004056713001236020013212 00000000000000/*NEW * test.c -- tester for libcyrus_sieve * Larry Greenfield * * usage: "test message script" */ /* * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #ifdef HAVE_CONFIG_H #include #endif #include #include #include #include #include #include #include #include #include "assert.h" #include "sieve_interface.h" #include "bytecode.h" #include "comparator.h" #include "tree.h" #include "sieve/sieve.h" #include "imap/message.h" #include "util.h" #include "xmalloc.h" #include "xstrlcat.h" #include "xstrlcpy.h" #include "hash.h" #include "times.h" static char vacation_answer; typedef struct { char *name; FILE *data; int size; struct message_content content; int cache_full; struct hash_table cache; strarray_t *env_from; strarray_t *env_to; } message_data_t; /* take a list of headers, pull the first one out and return it in name and contents. returns 0 on success, negative on failure */ typedef enum { HDR_NAME_START, HDR_NAME, COLON, HDR_CONTENT_START, HDR_CONTENT } state; static int parseheader(FILE *f, char **headname, char **contents) { char c; static struct buf name = BUF_INITIALIZER; static struct buf body = BUF_INITIALIZER; state s = HDR_NAME_START; buf_reset(&name); buf_reset(&body); /* there are two ways out of this loop, both via gotos: either we successfully read a character (got_header) or we hit an error (ph_error) */ while ((c = getc(f))) { /* examine each character */ switch (s) { case HDR_NAME_START: if (c == '\r' || c == '\n') { /* no header here! */ goto ph_error; } if (!isalpha(c)) goto ph_error; buf_putc(&name, TOLOWER(c)); s = HDR_NAME; break; case HDR_NAME: if (c == ' ' || c == '\t' || c == ':') { buf_cstring(&name); s = (c == ':' ? HDR_CONTENT_START : COLON); break; } if (iscntrl(c)) { goto ph_error; } buf_putc(&name, TOLOWER(c)); break; case COLON: if (c == ':') { s = HDR_CONTENT_START; } else if (c != ' ' && c != '\t') { goto ph_error; } break; case HDR_CONTENT_START: if (c == ' ' || c == '\t') /* eat the whitespace */ break; buf_reset(&body); s = HDR_CONTENT; /* falls through! */ case HDR_CONTENT: if (c == '\r' || c == '\n') { int peek = getc(f); /* we should peek ahead to see if it's folded whitespace */ if (c == '\r' && peek == '\n') { c = getc(f); } else { c = peek; /* single newline seperator */ } if (c != ' ' && c != '\t') { /* this is the end of the header */ buf_cstring(&body); ungetc(c, f); goto got_header; } /* http://www.faqs.org/rfcs/rfc2822.html * * > Unfolding is accomplished by simply removing any CRLF * > that is immediately followed by WSP * * So keep the actual WSP character */ } /* just an ordinary character */ buf_putc(&body, c); break; } } /* if we fall off the end of the loop, we hit some sort of error condition */ ph_error: if (headname != NULL) *headname = NULL; if (contents != NULL) *contents = NULL; return -1; got_header: if (headname != NULL) *headname = xstrdup(name.s); if (contents != NULL) *contents = xstrdup(body.s); return 0; } static void fill_cache(message_data_t *m) { rewind(m->data); /* let's fill that header cache */ for (;;) { char *name, *body; strarray_t *contents; if (parseheader(m->data, &name, &body) < 0) { break; } /* put it in the hash table */ contents = (strarray_t *)hash_lookup(name, &m->cache); if (!contents) contents = hash_insert(name, strarray_new(), &m->cache); strarray_appendm(contents, body); free(name); } m->cache_full = 1; } /* we use the temp field in message_data to avoid having to malloc memory to return, and we also can't expose our the receipients to the message */ static int getenvelope(void *mc, const char *field, const char ***contents) { message_data_t *m = (message_data_t *)mc; if (!strcasecmp(field, "from")) { *contents = (const char **)m->env_from->data; return SIEVE_OK; } else if (!strcasecmp(field, "to")) { *contents = (const char **)m->env_to->data; return SIEVE_OK; } else { *contents = NULL; return SIEVE_FAIL; } } /* gets the header "head" from msg. */ static int getheader(void *v, const char *phead, const char ***body) { message_data_t *m = (message_data_t *) v; strarray_t *contents; char *head; *body = NULL; if (!m->cache_full) { fill_cache(m); } /* copy header parameter so we can mangle it */ head = xstrdup(phead); lcase(head); /* check the cache */ contents = (strarray_t *)hash_lookup(head, &m->cache); if (contents) *body = (const char **) contents->data; free(head); if (*body) { return SIEVE_OK; } else { return SIEVE_FAIL; } } static message_data_t *new_msg(FILE *msg, int size, const char *name) { message_data_t *m; m = xmalloc(sizeof(message_data_t)); m->data = msg; m->size = size; m->name = xstrdup(name); m->content.base = NULL; m->content.len = 0; m->content.body = NULL; construct_hash_table(&m->cache, 1000, 0); m->cache_full = 0; return m; } static void free_msg(message_data_t *m) { free_hash_table(&m->cache, (void(*)(void*))strarray_free); free(m->name); free(m); } static int getsize(void *mc, int *size) { message_data_t *m = (message_data_t *) mc; *size = m->size; return SIEVE_OK; } static int getbody(void *mc, const char **content_types, sieve_bodypart_t ***parts) { message_data_t *m = (message_data_t *) mc; int r = 0; if (!m->content.body) { /* parse the message body if we haven't already */ r = message_parse_file(m->data, &m->content.base, &m->content.len, &m->content.body); } /* XXX currently struct bodypart as defined in message.h is the same as sieve_bodypart_t as defined in sieve_interface.h, so we can typecast */ if (!r) message_fetch_part(&m->content, content_types, (struct bodypart ***) parts); return (!r ? SIEVE_OK : SIEVE_FAIL); } static int getinclude(void *sc __attribute__((unused)), const char *script, int isglobal __attribute__((unused)), char *fpath, size_t size) { strlcpy(fpath, script, size); strlcat(fpath, ".bc", size); return SIEVE_OK; } static int redirect(void *ac, void *ic, void *sc __attribute__((unused)), void *mc, const char **errmsg __attribute__((unused))) { sieve_redirect_context_t *rc = (sieve_redirect_context_t *) ac; message_data_t *m = (message_data_t *) mc; int *force_fail = (int*) ic; printf("redirecting message '%s' to '%s'\n", m->name, rc->addr); return (*force_fail ? SIEVE_FAIL : SIEVE_OK); } static int discard(void *ac __attribute__((unused)), void *ic, void *sc __attribute__((unused)), void *mc, const char **errmsg __attribute__((unused))) { message_data_t *m = (message_data_t *) mc; int *force_fail = (int*) ic; printf("discarding message '%s'\n", m->name); return (*force_fail ? SIEVE_FAIL : SIEVE_OK); } static int reject(void *ac, void *ic, void *sc __attribute__((unused)), void *mc, const char **errmsg __attribute__((unused))) { sieve_reject_context_t *rc = (sieve_reject_context_t *) ac; message_data_t *m = (message_data_t *) mc; int *force_fail = (int*) ic; printf("rejecting message '%s' with '%s'\n", m->name, rc->msg); return (*force_fail ? SIEVE_FAIL : SIEVE_OK); } static int fileinto(void *ac, void *ic, void *sc __attribute__((unused)), void *mc, const char **errmsg __attribute__((unused))) { sieve_fileinto_context_t *fc = (sieve_fileinto_context_t *) ac; message_data_t *m = (message_data_t *) mc; int *force_fail = (int*) ic; printf("filing message '%s' into '%s'\n", m->name, fc->mailbox); if (fc->imapflags->count) { char *s = strarray_join(fc->imapflags, "' '"); if (s) { printf("\twith flags '%s'\n", s); free(s); } } return (*force_fail ? SIEVE_FAIL : SIEVE_OK); } static int keep(void *ac, void *ic, void *sc __attribute__((unused)), void *mc, const char **errmsg __attribute__((unused))) { sieve_keep_context_t *kc = (sieve_keep_context_t *) ac; message_data_t *m = (message_data_t *) mc; int *force_fail = (int*) ic; printf("keeping message '%s'\n", m->name); if (kc->imapflags->count) { char *s = strarray_join(kc->imapflags, "' '"); if (s) { printf("\twith flags '%s'\n", s); free(s); } } return (*force_fail ? SIEVE_FAIL : SIEVE_OK); } static int notify(void *ac, void *ic, void *sc __attribute__((unused)), void *mc __attribute__((unused)), const char **errmsg __attribute__((unused))) { sieve_notify_context_t *nc = (sieve_notify_context_t *) ac; int *force_fail = (int*) ic; int flag = 0; printf("notify "); if (nc->method) { const char **opts = nc->options; printf("%s(", nc->method); while (opts && *opts) { if (flag) printf(", "); printf("%s", *opts); opts++; flag = 1; } printf("), "); } printf("msg = '%s' with priority = %s\n",nc->message, nc->priority); return (*force_fail ? SIEVE_FAIL : SIEVE_OK); } static int mysieve_error(int lineno, const char *msg, void *i __attribute__((unused)), void *s __attribute__((unused))) { fprintf(stderr, "line %d: %s\r\n", lineno, msg); return SIEVE_OK; } static int mysieve_execute_error(const char *msg, void *i __attribute__((unused)), void *s __attribute__((unused)), void *m __attribute__((unused))) { fprintf(stderr, "%s\r\n", msg); return SIEVE_OK; } static int autorespond(void *ac, void *ic __attribute__((unused)), void *sc __attribute__((unused)), void *mc __attribute__((unused)), const char **errmsg __attribute__((unused))) { sieve_autorespond_context_t *arc = (sieve_autorespond_context_t *) ac; char yn; int i; if (vacation_answer) yn = vacation_answer; else { printf("Have I already responded to '"); for (i = 0; i < SIEVE_HASHLEN; i++) { printf("%x", arc->hash[i]); } if (arc->seconds % DAY2SEC) printf("' in %d seconds? ", arc->seconds); else printf("' in %d days? ", arc->seconds / DAY2SEC); scanf(" %c", &yn); } if (TOLOWER(yn) == 'y') return SIEVE_DONE; if (TOLOWER(yn) == 'n') return SIEVE_OK; return SIEVE_FAIL; } static int send_response(void *ac, void *ic, void *sc __attribute__((unused)), void *mc, const char **errmsg __attribute__((unused))) { sieve_send_response_context_t *src = (sieve_send_response_context_t *) ac; message_data_t *m = (message_data_t *) mc; int *force_fail = (int*) ic; printf("echo '%s' | mail -s '%s' '%s' for message '%s' (from: %s)\n", src->msg, src->subj, src->addr, m->name, src->fromaddr); return (*force_fail ? SIEVE_FAIL : SIEVE_OK); } static sieve_vacation_t vacation = { 0, /* min response */ 0, /* max response */ &autorespond, /* autorespond() */ &send_response /* send_response() */ }; static int usage(const char *argv0) __attribute__((noreturn)); static int usage(const char *argv0) { fprintf(stderr, "usage:\n"); fprintf(stderr, "%s -v script\n", argv0); fprintf(stderr, "%s [opts] message script\n", argv0); fprintf(stderr, "\n"); fprintf(stderr, " -e envelope_from\n"); fprintf(stderr, " -t envelope_to\n"); fprintf(stderr, " -r y|n - have sent vacation response already? (if required)\n"); exit(1); } int main(int argc, char *argv[]) { sieve_interp_t *i; sieve_execute_t *exe = NULL; message_data_t *m = NULL; char *script = NULL, *message = NULL; int c, force_fail = 0; int fd, res; struct stat sbuf; static strarray_t mark = STRARRAY_INITIALIZER; static strarray_t e_from = STRARRAY_INITIALIZER; static strarray_t e_to = STRARRAY_INITIALIZER; /* prevent crashes if -e or -t aren't specified */ strarray_append(&e_from, ""); strarray_append(&e_to, ""); while ((c = getopt(argc, argv, "v:fe:t:r:")) != EOF) switch (c) { case 'v': script = optarg; break; case 'f': force_fail = 1; break; case 'e': strarray_fini(&e_from); strarray_append(&e_from, optarg); break; case 't': strarray_fini(&e_to); strarray_append(&e_to, optarg); break; case 'r': vacation_answer = optarg[0]; break; default: usage(argv[0]); break; } if (!script) { if ((argc - optind) < 2) usage(argv[0]); else { message = argv[optind]; script = argv[optind+1]; } } i = sieve_interp_alloc(&force_fail); assert(i != NULL); sieve_register_redirect(i, redirect); sieve_register_discard(i, discard); sieve_register_reject(i, reject); sieve_register_fileinto(i, fileinto); sieve_register_keep(i, keep); sieve_register_size(i, getsize); sieve_register_header(i, getheader); sieve_register_envelope(i, getenvelope); sieve_register_body(i, getbody); sieve_register_include(i, getinclude); res = sieve_register_vacation(i, &vacation); if (res != SIEVE_OK) { printf("sieve_register_vacation() returns %d\n", res); exit(1); } strarray_append(&mark, "\\flagged"); sieve_register_imapflags(i, &mark); sieve_register_notify(i, notify); sieve_register_parse_error(i, mysieve_error); sieve_register_execute_error(i, mysieve_execute_error); res = sieve_script_load(script, &exe); if (res != SIEVE_OK) { printf("sieve_script_load() returns %d\n", res); exit(1); } if (message) { FILE *f; fd = open(message, O_RDONLY); res = fstat(fd, &sbuf); if (res != 0) { perror("fstat"); } f = fdopen(fd, "r"); if (f) m = new_msg(f, sbuf.st_size, message); if (!f || !m) { printf("can not open message '%s'\n", message); exit(1); } m->env_from = &e_from; m->env_to = &e_to; res = sieve_execute_bytecode(exe, i, NULL, m); if (res != SIEVE_OK) { printf("sieve_execute_bytecode() returns %d\n", res); exit(1); } fclose(f); close(fd); } /*used to be sieve_script_free*/ res = sieve_script_unload(&exe); if (res != SIEVE_OK) { printf("sieve_script_unload() returns %d\n", res); exit(1); } res = sieve_interp_free(&i); if (res != SIEVE_OK) { printf("sieve_interp_free() returns %d\n", res); exit(1); } if (m) free_msg(m); strarray_fini(&e_from); strarray_fini(&e_to); strarray_fini(&mark); return 0; } EXPORTED void fatal(const char* message, int rc) { fprintf(stderr, "fatal error: %s\n", message); exit(rc); } cyrus-imapd-2.5.10/sieve/message.h0000644000175000017500000001062113001236020013650 00000000000000/* message.h * Larry Greenfield * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #ifndef MESSAGE_H #define MESSAGE_H #include "sieve_interface.h" /* for action contexts */ #include "tree.h" typedef struct Action action_list_t; typedef enum { ACTION_NULL = -1, ACTION_NONE = 0, ACTION_REJECT, ACTION_FILEINTO, ACTION_KEEP, ACTION_REDIRECT, ACTION_DISCARD, ACTION_VACATION, ACTION_SETFLAG, ACTION_ADDFLAG, ACTION_REMOVEFLAG, ACTION_MARK, ACTION_UNMARK, ACTION_NOTIFY, ACTION_DENOTIFY } action_t; /* information */ action_list_t *new_action_list(void); void free_action_list(action_list_t *actions); /* invariant: always have a dummy element when free_action_list, param and vac_subj are freed. none of the others are automatically freed. the do_action() functions should copy param */ struct Action { action_t a; int cancel_keep; union { sieve_reject_context_t rej; sieve_fileinto_context_t fil; sieve_keep_context_t keep; sieve_redirect_context_t red; struct { /* addr, fromaddr, subj - freed! */ sieve_send_response_context_t send; sieve_autorespond_context_t autoresp; } vac; struct { const char *flag; } fla; } u; char *param; /* freed! */ struct Action *next; char *vac_subj; /* freed! */ char *vac_msg; int vac_days; }; typedef struct notify_list_s { int isactive; const char *id; const char *method; const char **options; const char *priority; const char *message; struct notify_list_s *next; } notify_list_t; notify_list_t *new_notify_list(void); void free_notify_list(notify_list_t *n); /* actions; return negative on failure. * these don't actually perform the actions, they just add it to the * action list */ int do_reject(action_list_t *m, const char *msg); int do_fileinto(action_list_t *m, const char *mbox, int cancel_keep, strarray_t *imapflags); int do_redirect(action_list_t *m, const char *addr, int cancel_keep); int do_keep(action_list_t *m, int cancel_keep, strarray_t *imapflags); int do_discard(action_list_t *m); int do_vacation(action_list_t *m, char *addr, char *fromaddr, char *subj, const char *msg, int seconds, int mime, const char *handle); int do_setflag(action_list_t *m); int do_addflag(action_list_t *m, const char *flag); int do_removeflag(action_list_t *m, const char *flag); int do_mark(action_list_t *m); int do_unmark(action_list_t *m); int do_notify(notify_list_t *n, const char *id, const char *method, const char **options, const char *priority, const char *message); int do_denotify(notify_list_t *n, comparator_t *comp, const void *pat, void *comprock, const char *priority); #endif cyrus-imapd-2.5.10/sieve/tests/0000755000175000017500000000000013001246664013314 500000000000000cyrus-imapd-2.5.10/sieve/tests/README0000644000175000017500000000106213001236020014074 00000000000000there are four directories action (sieve actions) test (the test cases for if) action extension (extensons to sieve that are actions) testExtension (extensions to sieve that are tests) inside these directories is: XXXXX.s (sieve script) XXXXX.key (what this script should do with thest messages serverm (dir of messages- for testing the script using lmtp server) testm (dir of messages- for testing the script using sieve test program) the redirected messages are all being sent to me@blah.com. when using a lmpt server, change this to a real address firstcyrus-imapd-2.5.10/sieve/tests/actionExtensions/0000755000175000017500000000000013001236020016632 500000000000000cyrus-imapd-2.5.10/sieve/tests/actionExtensions/uberExtensionActionScript.s0000644000175000017500000000450513001236020024117 00000000000000require ["reject", "fileinto", "imapflags", "vacation", "notify", "vacation-seconds", "copy", "imap4flags", "relational", "comparator-i;ascii-numeric"]; #this is for the extra thigns we have added to sieve #action extensions #reject fileinto imapflags vacation notify #REJECT ############################################## if header :contains "subject" "reject" {reject "rejected";} #FILEINTO ############################################## if header :contains "subject" "fileinto" {fileinto "INBOX.good";} #IMAPFLAGS ############################################## #mark if header :contains "subject" "zmark" {mark;} #unmark if header :contains "subject" "unmark" {unmark;} #addflag if header :contains "subject" "aflag1" {addflag "\\seen";} #addflag if header :contains "subject" "aflag2" {addflag ["\\draft", "\\answered", "\\flagged"];} #setflag if header :contains "subject" "sflag1" {setflag "\\deleted";} #setflag if header :contains "subject" "sflag2" {setflag "\\draft";} #removeflag if header :contains "subject" "rflag" {removeflag "\\answered";} #IMAP4FLAGS# ############################################## if header :contains "subject" "imap4flags" { setflag "existing"; keep :flags "keepflag"; fileinto :flags ["fileinto f2"] "INBOX.fileinto.flags"; addflag ["flag0", "flag1"]; addflag ["my flag is here"]; removeflag ["is my"]; fileinto "INBOX.fileinto.internalflags"; fileinto :flags "" "INBOX.fileinto.nullflags"; } #VACATION ############################################# if header :contains "subject" "vacation" { vacation :days 5 :addresses ["me@blah.com" , "me@somewhereelse.com"] :subject "i'm at the beach" "I'll respond in a week or two, when i get back"; } #VACATION-SECONDS ############################################# if header :contains "subject" "vacation-seconds" { vacation :seconds 60 :addresses ["me@blah.com" , "me@somewhereelse.com"] :subject "i'm out of the room" "I'll respond in a minute, when i get back"; } #NOTIFY and DENOTIFY ############################################# if header :contains "subject" "notify" {notify :high :id "foobar" :message "whee: $subject$";} if header :contains "subject" "not" {denotify :is "foobar" :high; } if header :contains "subject" "n2" {notify :id "foobar" :message "whee: $subject$";} if header :contains "subject" "denotify" {denotify;} cyrus-imapd-2.5.10/sieve/tests/actionExtensions/serverm/0000755000175000017500000000000012746001136020332 500000000000000cyrus-imapd-2.5.10/sieve/tests/actionExtensions/serverm/ueamail-mark0000644000175000017500000000022312562247555022554 00000000000000MAIL FROM: RCPT TO: DATA Date: Mon, 25 Feb 2002 08:51:06 -0500 From: them To: you Subject: zmark blah . cyrus-imapd-2.5.10/sieve/tests/actionExtensions/serverm/ueamail-flag10000644000175000017500000000023612562247555022620 00000000000000MAIL FROM: RCPT TO: DATA Date: Mon, 25 Feb 2002 08:51:06 -0500 From: them To: you Subject: aflag1 should be seen . cyrus-imapd-2.5.10/sieve/tests/actionExtensions/serverm/ueamail-flag50000644000175000017500000000030312562247555022617 00000000000000MAIL FROM: RCPT TO: DATA Date: Mon, 25 Feb 2002 08:51:06 -0500 From: them To: you Subject: aflag1 aflag2 should be seen, flagged, draft, and answered . cyrus-imapd-2.5.10/sieve/tests/actionExtensions/serverm/ueamail-flag30000644000175000017500000000024612562247555022623 00000000000000MAIL FROM: RCPT TO: DATA Date: Mon, 25 Feb 2002 08:51:06 -0500 From: them To: you Subject: sflag1 sflag2 should be draft . cyrus-imapd-2.5.10/sieve/tests/actionExtensions/serverm/ueamail-notify0000644000175000017500000000022312562247555023132 00000000000000MAIL FROM: RCPT TO: DATA Date: Mon, 25 Feb 2002 08:51:06 -0500 From: them To: you Subject: notify blah . cyrus-imapd-2.5.10/sieve/tests/actionExtensions/serverm/ueamail-reject0000644000175000017500000000022312562247555023076 00000000000000MAIL FROM: RCPT TO: DATA Date: Mon, 25 Feb 2002 08:51:06 -0500 From: them To: you Subject: reject blah . cyrus-imapd-2.5.10/sieve/tests/actionExtensions/serverm/ueamail-unmark0000644000175000017500000000023212562247555023117 00000000000000MAIL FROM: RCPT TO: DATA Date: Mon, 25 Feb 2002 08:51:06 -0500 From: them To: you Subject: zmark unmark blah . cyrus-imapd-2.5.10/sieve/tests/actionExtensions/serverm/ueamail-notify20000644000175000017500000000023212562247555023214 00000000000000MAIL FROM: RCPT TO: DATA Date: Mon, 25 Feb 2002 08:51:06 -0500 From: them To: you Subject: not notify n2 blah . cyrus-imapd-2.5.10/sieve/tests/actionExtensions/serverm/ueamail-denotify0000644000175000017500000000022712562247555023447 00000000000000MAIL FROM: RCPT TO: DATA Date: Mon, 25 Feb 2002 08:51:06 -0500 From: them To: you Subject: not notify blah . cyrus-imapd-2.5.10/sieve/tests/actionExtensions/serverm/ueamail-fileinto0000644000175000017500000000022512562247555023435 00000000000000MAIL FROM: RCPT TO: DATA Date: Mon, 25 Feb 2002 08:51:06 -0500 From: them To: you Subject: fileinto blah . cyrus-imapd-2.5.10/sieve/tests/actionExtensions/serverm/ueamail-flag40000644000175000017500000000026112562247555022621 00000000000000MAIL FROM: RCPT TO: DATA Date: Mon, 25 Feb 2002 08:51:06 -0500 From: them To: you Subject: aflag2 rflag should be draft and flagged . cyrus-imapd-2.5.10/sieve/tests/actionExtensions/serverm/ueamail-imap4flags0000644000175000017500000000023612746001136023640 00000000000000MAIL FROM: RCPT TO: DATA Date: Mon, 25 Feb 2002 08:51:06 -0500 From: me To: you Subject: imap4flags hasflag test . cyrus-imapd-2.5.10/sieve/tests/actionExtensions/serverm/ueamail-flag20000644000175000017500000000025012562247555022615 00000000000000MAIL FROM: RCPT TO: DATA Date: Mon, 25 Feb 2002 08:51:06 -0500 From: them To: you Subject: aflag2 sflag1 should be deleted . cyrus-imapd-2.5.10/sieve/tests/actionExtensions/serverm/ueamail-vacation0000644000175000017500000000023512562247555023431 00000000000000MAIL FROM: RCPT TO: DATA Date: Mon, 25 Feb 2002 08:51:06 -0500 From: them To: me@blah.com Subject: vacation blah . cyrus-imapd-2.5.10/sieve/tests/actionExtensions/serverm/ueamail-denotify20000644000175000017500000000023712562247555023532 00000000000000MAIL FROM: RCPT TO: DATA Date: Mon, 25 Feb 2002 08:51:06 -0500 From: them To: you Subject: denotify notify n2 blah . cyrus-imapd-2.5.10/sieve/tests/actionExtensions/uberExtensionActionScript.key0000644000175000017500000000320313001236020024437 00000000000000'ueatest-denotify' keep message 'ueatest-denotify2' notify default(), msg = 'whee: denotify notify n2 Action(s) taken: ' with priority = normal keep message 'ueatest-fileinto' file message into 'INBOX.good' 'ueatest-flag1' keep message with flags '\seen' 'ueatest-flag2' keep message with flags '\deleted 'ueatest-flag3' keep message with flags '\draft' 'ueatest-flag4' keep message with flags '\draft' '\flagged' 'ueatest-flag5' keep message with flags '\seen' '\draft' '\answered' '\flagged 'ueatest-mark' keep message with flags '\flagged' 'ueatest-unmark' keep message 'ueatest-vacation' Envelope body of 'to'? you Envelope body of 'from'? me Have I already responded to '373d72afbd3cbfcb7a7922d70d5dd6e' in 5 days? no echo 'I'll respond in a week or two, when i get back' | mail -s 'i'm at the beach' 'me@unspecified-domain' for message '/afs/andrew/system/src/local/cyrus/046/sieve/tests/actionExtensions/testm/ueatest-vacation' keep message 'ueatest-vacation-seconds' Envelope body of 'to'? you Envelope body of 'from'? me Have I already responded to '373d72afbd3cbfcb7a7922d70d5dd6e' in 60 seconds? no echo 'I'll respond in a minute, when i get back' | mail -s 'i'm out of the room' 'me@unspecified-domain' for message '/afs/andrew/system/src/local/cyrus/046/sieve/tests/actionExtensions/testm/ueatest-vacation' keep message 'ueatest-imap4flags' keeping message with flags 'keepflag' filing message into 'INBOX.fileinto.flags' with flags 'fileinto' 'f2' filing message into 'INBOX.fileinto.internalflags' with flags 'existing' 'flag0' 'flag1' 'flag' 'here' filing message into 'INBOX.fileinto.nullflags' cyrus-imapd-2.5.10/sieve/tests/actionExtensions/testm/0000755000175000017500000000000012746001136020003 500000000000000cyrus-imapd-2.5.10/sieve/tests/actionExtensions/testm/ueatest-notify0000644000175000017500000000011612562247555022641 00000000000000Date: Mon, 25 Feb 2002 08:51:06 -0500 From: them To: you Subject: notify blah cyrus-imapd-2.5.10/sieve/tests/actionExtensions/testm/ueatest-flag50000644000175000017500000000017712562247555022336 00000000000000Date: Mon, 25 Feb 2002 08:51:06 -0500 From: them To: you Subject: aflag1 aflag2 should be seen, flagged, draft, and answered cyrus-imapd-2.5.10/sieve/tests/actionExtensions/testm/ueatest-unmark0000644000175000017500000000012612562247555022627 00000000000000Date: Mon, 25 Feb 2002 08:51:06 -0500 From: them To: you Subject: zmark unmark blah cyrus-imapd-2.5.10/sieve/tests/actionExtensions/testm/ueatest-imap4flags0000644000175000017500000000014712746001136023347 00000000000000Date: Mon, 25 Feb 2002 08:51:06 -0500 From: them To: you Subject: imap4flags imap4flags test message cyrus-imapd-2.5.10/sieve/tests/actionExtensions/testm/ueatest-denotify20000644000175000017500000000013212562247555023232 00000000000000Date: Mon, 25 Feb 2002 08:51:06 -0500 From: them To: you Subject: denotify notify n2 blah cyrus-imapd-2.5.10/sieve/tests/actionExtensions/testm/ueatest-mark0000644000175000017500000000011712562247555022264 00000000000000Date: Mon, 25 Feb 2002 08:51:06 -0500 From: them To: you Subject: zmark blah cyrus-imapd-2.5.10/sieve/tests/actionExtensions/testm/ueatest-flag20000644000175000017500000000014412562247555022325 00000000000000Date: Mon, 25 Feb 2002 08:51:06 -0500 From: them To: you Subject: aflag2 sflag1 should be deleted cyrus-imapd-2.5.10/sieve/tests/actionExtensions/testm/ueatest-flag10000644000175000017500000000013212562247555022321 00000000000000Date: Mon, 25 Feb 2002 08:51:06 -0500 From: them To: you Subject: aflag1 should be seen cyrus-imapd-2.5.10/sieve/tests/actionExtensions/testm/ueatest-fileinto0000644000175000017500000000012112562247555023136 00000000000000Date: Mon, 25 Feb 2002 08:51:06 -0500 From: them To: you Subject: fileinto blah cyrus-imapd-2.5.10/sieve/tests/actionExtensions/testm/ueatest-notify20000644000175000017500000000012512562247555022723 00000000000000Date: Mon, 25 Feb 2002 08:51:06 -0500 From: them To: you Subject: not notify n2 blah cyrus-imapd-2.5.10/sieve/tests/actionExtensions/testm/ueatest-flag30000644000175000017500000000014212562247555022324 00000000000000Date: Mon, 25 Feb 2002 08:51:06 -0500 From: them To: you Subject: sflag1 sflag2 should be draft cyrus-imapd-2.5.10/sieve/tests/actionExtensions/testm/ueatest-reject0000644000175000017500000000011712562247555022606 00000000000000Date: Mon, 25 Feb 2002 08:51:06 -0500 From: them To: you Subject: reject blah cyrus-imapd-2.5.10/sieve/tests/actionExtensions/testm/ueatest-vacation0000644000175000017500000000013312562247555023134 00000000000000Date: Mon, 25 Feb 2002 08:51:06 -0500 From: them To: me@blah.com Subject: vacation blah . cyrus-imapd-2.5.10/sieve/tests/actionExtensions/testm/ueatest-denotify0000644000175000017500000000012212562247555023147 00000000000000Date: Mon, 25 Feb 2002 08:51:06 -0500 From: them To: you Subject: not notify blah cyrus-imapd-2.5.10/sieve/tests/actionExtensions/testm/ueatest-flag40000644000175000017500000000015512562247555022331 00000000000000Date: Mon, 25 Feb 2002 08:51:06 -0500 From: them To: you Subject: aflag2 rflag should be draft and flagged cyrus-imapd-2.5.10/sieve/tests/testExtension/0000755000175000017500000000000013001236020016151 500000000000000cyrus-imapd-2.5.10/sieve/tests/testExtension/uberExtensionTestScript.s0000644000175000017500000001536713001236020023150 00000000000000require ["regex", "relational", "comparator-i;ascii-numeric", "subaddress", "envelope", "date", "index", "imap4flags"]; #this is for the extra thigns we have added to sieve #test extensions #envelope regex relational comparators subaddress(user and detail) #need better relational and comparator tests... if header :value "gt" :comparator "i;ascii-numeric" ["number"] ["10"] {redirect "me+numberover10@blah.com";} if header :count "gt" :comparator "i;ascii-numeric" ["X"] ["3"] {redirect "me+X@blah.com";} #header regex if header :regex "Date" "Tue,(.*)Feb(.*)" {redirect "me+goodheaderregex@blah.com";} #address Regex if address :all :regex "from" "cook(.)Monster(\\+.*)@cookie\\...." {redirect "me+goodaallregex@blah.com";} if address :domain :regex "from" "c..kie\\.com" {redirect "me+goodadomainregex@blah.com";} if address :localpart :regex "from" "c.{2,4}Monster(\\+.*)" {redirect "me+goodalocalpartregex@blah.com";} if address :user :regex "from" "cookyM.....r" {redirect "me+goodauserregex@blah.com";} if address :detail :regex "from" "whe*" {redirect "me+goodadetailregex@blah.com";} #address user if address :user :is "from" "mymonster" {redirect "me+goodauseris@blah.com";} if address :user :contains "from" "mym" {redirect "me+goodausercontains@blah.com";} if address :user :matches "from" "my*r" {redirect "me+goodausermatches@blah.com";} #address detail if address :detail :is "from" "underbed" {redirect "me+goodadetailis@blah.com";} if address :detail :contains "from" "bed" {redirect "me+goodadetailcontains@blah.com";} if address :detail :matches "from" "under*" {redirect "me+goodadetailmatches@blah.com";} ###################################################################### #ENVELOPE ###################################################################### #envelope all if envelope :all :is "from" "WERT+erk@true.com" {redirect "me+eallis@blah.com";} if envelope :all :contains "from" "true.com" {redirect "me+eallcontains@blah.com";} if envelope :all :matches "from" "WERT*.com" {redirect "me+eallmatches@blah.com";} #envelope domain if envelope :domain :is "from" "true.com" {redirect "me+edomainis@blah.com";} if envelope :domain :contains "from" "true" {redirect "me+edomaincontains@blah.com";} if envelope :domain :matches "from" "*true.com" {redirect "me+edomainmatches@blah.com";} #envelope localpart if envelope :localpart :is "from" "WERT+erk" {redirect "me+elocalpartis@blah.com";} if envelope :localpart :contains "from" "WE" {redirect "me+elocalpartcontains@blah.com";} if envelope :localpart :matches "from" "WE?T*" {redirect "me+elocalpartmatches@blah.com";} #envelope regex if envelope :all :regex "from" "true.com" {redirect "me+goodeallregex@blah.com";} if envelope :domain :regex "from" "true.com" {redirect "me+goodedomainregex@blah.com";} if envelope :localpart :regex "from" "true.com" {redirect "me+goodelocalpartregex@blah.com";} if envelope :user :regex "from" "true.com" {redirect "me+goodeuserregex@blah.com";} if envelope :detail :regex "from" "true.com" {redirect "me+goodedetailregex@blah.com";} #envelope user if envelope :user :is "from" "WERT" {redirect "me+goodeuseris@blah.com";} if envelope :user :contains "from" "WE" {redirect "me+goodeusercontains@blah.com";} if envelope :user :matches "from" "*RT" {redirect "me+goodeusermatches@blah.com";} #envelope detail if envelope :detail :is "from" "erk" {redirect "me+goodedetailis@blah.com";} if envelope :detail :contains "from" "k" {redirect "me+goodedetailcontains@blah.com";} if envelope :detail :matches "from" "e*k" {redirect "me+goodedetailmatches@blah.com";} ###################################################################### #DATE ###################################################################### if allof(header :is "from" "boss@example.com", date :value "ge" :originalzone "date" "hour" "09", date :value "lt" :originalzone "date" "hour" "17") {redirect "me+urgent@blah.com";} if anyof(date :is "received" "weekday" "0", date :is "received" "weekday" "6") {redirect "me+weekend@blah.com";} if anyof(date :is :zone "-0800" "received" "weekday" "0", date :is :zone "-0800" "received" "weekday" "6") {redirect "me+weekend(pst)@blah.com";} if date :is "received" "year" [ "1983", "1993", "2003", "2013" ] {redirect "me+yearsofthree@blah.com";} if date :is :index 2 "received" "day" "01" {redirect "me+firstofthemonth@blah.com";} if date :is :index 1 :last "received" "day" "01" {redirect "me+firstofthemonth@blah.com";} if currentdate :zone "-0800" :is "year" ["2003", "2013", "2023"] {redirect "me+currentdateis@blah.com";} if allof(currentdate :value "ge" "date" "2014-01-01", currentdate :value "lt" "date" "2015-01-01") {redirect "me+cd2014@blah.com";} ###################################################################### #HASFLAG ###################################################################### if header :contains "subject" "imap4flags" { # # Positive :count tests # setflag ""; if hasflag :count "lt" :comparator "i;ascii-numeric" ["1"] {redirect "me+good.hasflag.count.lt.1.pos@blah.com";} else {redirect "me+bad.hasflag.count.lt.1.pos@blah.com";} if hasflag :count "le" :comparator "i;ascii-numeric" ["0"] {redirect "me+good.hasflag.count.le.0.pos@blah.com";} else {redirect "me+bad.hasflag.count.le.0.pos@blah.com";} setflag "flag1 flag2"; if hasflag :count "le" :comparator "i;ascii-numeric" ["2"] {redirect "me+good.hasflag.count.le.2.pos@blah.com";} else {redirect "me+bad.hasflag.count.le.2.pos@blah.com";} # # Negative :count tests # setflag ""; if hasflag :count "lt" :comparator "i;ascii-numeric" ["0"] {redirect "me+bad.hasflag.count.lt.0.neg@blah.com";} else {redirect "me+good.hasflag.count.lt.0.neg@blah.com";} if hasflag :count "ge" :comparator "i;ascii-numeric" ["1"] {redirect "me+bad.hasflag.count.ge.1.neg@blah.com";} else {redirect "me+good.hasflag.count.ge.1.neg@blah.com";} setflag "flag1 flag2"; if hasflag :count "lt" :comparator "i;ascii-numeric" ["2"] {redirect "me+bad.hasflag.count.lt.2.neg@blah.com";} else {redirect "me+good.hasflag.count.lt.2.neg@blah.com";} # # Positive tests # setflag "there"; if hasflag :contains ["myflag", "here"] {redirect "me+good.hasflag.contains.pos@blah.com";} else {redirect "me+bad.hasflag.contains.pos@blah.com";} if hasflag :contains "" {redirect "me+good.hasflag.contains.null.pos@blah.com";} else {redirect "me+bad.hasflag.contains.null.pos@blah.com";} # # Negative tests # setflag "flag"; if hasflag "" {redirect "me+bad.hasflag.null.neg@blah.com";} else {redirect "me+good.hasflag.null.neg@blah.com";} if hasflag :contains "flags" {redirect "me+bad.hasflag.contains.neg@blah.com";} else {redirect "me+good.hasflag.contains.neg@blah.com";} if hasflag "lag" {redirect "me+bad.hasflag.neg@blah.com";} else {redirect "me+good.hasflag.neg@blah.com";} } cyrus-imapd-2.5.10/sieve/tests/testExtension/uberExtensionTestScript.key0000644000175000017500000000355113001236020023466 00000000000000 uetest-value should be redirected to 'me+numberover10@blah.com' uetest-value2 should just be kept uetest-count should be redirected to 'me+X@blah.com' uetest-count2 should just be kept uetest-hreg should be redirected to 'me+goodheaderregex@blah.com' uetest-areg should be redirected to 'me+goodaallregex@blah.com' 'me+goodadomainregex@blah.com' 'me+goodalocalpartregex@blah.com' 'me+goodauserregex@blah.com' 'me+goodadetailregex@blah.com' uetest-asub should be redirected to 'me+goodauseris@blah.com' 'me+goodausercontains@blah.com' 'me+goodausermatches@blah.com' 'me+goodadetailis@blah.com' 'me+goodadetailcontains@blah.com' 'me+goodadetailmatches@blah.com' utest-envelope with an envelope body of from= "WERT+erk@true.com" should be redirected to: 'me+eallis@blah.com' 'me+eallcontains@blah.com' 'me+eallmatches@blah.com' 'me+edomainis@blah.com' 'me+edomaincontains@blah.com' 'me+edomainmatches@blah.com' 'me+elocalpartis@blah.com' 'me+elocalpartcontains@blah.com' 'me+elocalpartmatches@blah.com' 'me+goodeallregex@blah.com' 'me+goodedomainregex@blah.com' 'me+goodelocalpartregex@blah.com' 'me+goodeuserregex@blah.com' 'me+goodedetailregex@blah.com' 'me+goodeuseris@blah.com' 'me+goodeusercontains@blah.com' 'me+goodeusermatches@blah.com' 'me+goodedetailis@blah.com' 'me+goodedetailcontains@blah.com' 'me+goodedetailmatches@blah.com' uetest-hasflag should be redirected to: 'me+good.hasflag.count.lt.1.pos@blah.com' 'me+good.hasflag.count.le.0.pos@blah.com' 'me+good.hasflag.count.le.2.pos@blah.com' 'me+good.hasflag.count.lt.0.neg@blah.com' 'me+good.hasflag.count.ge.1.neg@blah.com' 'me+good.hasflag.count.lt.2.neg@blah.com' 'me+good.hasflag.contains.pos@blah.com' 'me+good.hasflag.contains.null.pos@blah.com' 'me+good.hasflag.null.neg@blah.com' 'me+good.hasflag.contains.neg@blah.com' 'me+good.hasflag.neg@blah.com' cyrus-imapd-2.5.10/sieve/tests/testExtension/serverm/0000755000175000017500000000000012746001136017651 500000000000000cyrus-imapd-2.5.10/sieve/tests/testExtension/serverm/uetmail-asub0000644000175000017500000000030112562247555022113 00000000000000MAIL FROM: RCPT TO: DATA Date: Mon, 25 Feb 2002 08:51:06 -0500 From: mymonster+underbed@x.com To: you Subject: a simple address subaddress test blah . cyrus-imapd-2.5.10/sieve/tests/testExtension/serverm/uetmail-value0000644000175000017500000000026312562247555022304 00000000000000MAIL FROM: RCPT TO: DATA Date: Mon, 25 Feb 2002 08:51:06 -0500 From: me To: you Number:11 Subject: a simple relational value test blah . cyrus-imapd-2.5.10/sieve/tests/testExtension/serverm/uetmail-hreg0000644000175000017500000000024512562247555022115 00000000000000MAIL FROM: RCPT TO: DATA Date: Tue, 25 Feb 2002 08:51:06 -0500 From: me To: you Subject: a simple header regex test blah . cyrus-imapd-2.5.10/sieve/tests/testExtension/serverm/uetmail-count0000644000175000017500000000027512562247555022323 00000000000000MAIL FROM: RCPT TO: DATA Date: Mon, 25 Feb 2002 08:51:06 -0500 From: me To: you X:1 X:2 X:3 X:4 X:5 Subject: a simple relational count test blah . cyrus-imapd-2.5.10/sieve/tests/testExtension/serverm/uetmail-envelope0000644000175000017500000000022212562247555023000 00000000000000MAIL FROM: RCPT TO: DATA Date: Mon, 25 Jan 2003 08:51:06 -0500 From: it To: you Subject: simple envelope test blah . cyrus-imapd-2.5.10/sieve/tests/testExtension/serverm/uetmail-count20000644000175000017500000000026112562247555022400 00000000000000MAIL FROM: RCPT TO: DATA Date: Mon, 25 Feb 2002 08:51:06 -0500 From: me To: you X:4 X:5 Subject: a simple relational count test blah . cyrus-imapd-2.5.10/sieve/tests/testExtension/serverm/uetmail-value20000644000175000017500000000026212562247555022365 00000000000000MAIL FROM: RCPT TO: DATA Date: Mon, 25 Feb 2002 08:51:06 -0500 From: me To: you Number:8 Subject: a simple relational value test blah . cyrus-imapd-2.5.10/sieve/tests/testExtension/serverm/uetmail-areg0000644000175000017500000000030112562247555022077 00000000000000MAIL FROM: RCPT TO: DATA Date: Mon, 25 Feb 2002 08:51:06 -0500 From: cookyMonster+wheee@cookie.com To: you Subject: a simple address regex test blah . cyrus-imapd-2.5.10/sieve/tests/testExtension/serverm/uetmail-hasflag0000644000175000017500000000023612746001136022560 00000000000000MAIL FROM: RCPT TO: DATA Date: Mon, 25 Feb 2002 08:51:06 -0500 From: me To: you Subject: imap4flags hasflag test . cyrus-imapd-2.5.10/sieve/tests/testExtension/testm/0000755000175000017500000000000013001236020017305 500000000000000cyrus-imapd-2.5.10/sieve/tests/testExtension/testm/uetest-count0000644000175000017500000000017112562247555021640 00000000000000Date: Mon, 25 Feb 2002 08:51:06 -0500 From: me To: you X:1 X:2 X:3 X:4 X:5 Subject: a simple relational count test blah cyrus-imapd-2.5.10/sieve/tests/testExtension/testm/uetest-value0000644000175000017500000000015712562247555021630 00000000000000Date: Mon, 25 Feb 2002 08:51:06 -0500 From: me To: you Number:11 Subject: a simple relational value test blah cyrus-imapd-2.5.10/sieve/tests/testExtension/testm/uetest-areg0000644000175000017500000000017213001236020021375 00000000000000Date: Mon, 25 Feb 2002 08:51:06 -0500 From: cookyMonster+wheee@cookie.com To: you Subject: a simple address regex test cyrus-imapd-2.5.10/sieve/tests/testExtension/testm/uetest-hasflag0000644000175000017500000000013212746001136022075 00000000000000Date: Mon, 25 Feb 2002 08:51:06 -0500 From: me To: you Subject: imap4flags hasflag test cyrus-imapd-2.5.10/sieve/tests/testExtension/testm/uetest-asub0000644000175000017500000000017213001236020021411 00000000000000Date: Mon, 25 Feb 2002 08:51:06 -0500 From: mymonster+underbed@x.com To: you Subject: a simple address subaddress test cyrus-imapd-2.5.10/sieve/tests/testExtension/testm/uetest-envelope0000644000175000017500000000013312562247555022323 00000000000000Date: Mon, 25 Jan 2003 08:51:06 -0500 From: it To: you Subject: simple envelope test blah cyrus-imapd-2.5.10/sieve/tests/testExtension/testm/uetest-hreg0000644000175000017500000000013613001236020021404 00000000000000Date: Tue, 25 Feb 2002 08:51:06 -0500 From: me To: you Subject: a simple header regex test cyrus-imapd-2.5.10/sieve/tests/test/0000755000175000017500000000000013001236020014254 500000000000000cyrus-imapd-2.5.10/sieve/tests/test/uberTestScript.key0000644000175000017500000000165013001236020017672 00000000000000utest-address should be redirected to: 'me+aallis@blah.com' 'me+aallcontains@blah.com' 'me+aallmatches@blah.com' 'me+adomainis@blah.com' 'me+adomaincontains@blah.com' 'me+adomainmatches@blah.com' 'me+alocalpartis@blah.com' 'me+alocalpartcontains@blah.com' 'me+alocalpartmatches@blah.com' utest-header should be redirected to: 'me+headercontains@blah.com' 'me+headeris@blah.com' 'me+headermatches@blah.com' both of those messages should also be redirected to 'me+exists@blah.com' 'me+under1k@blah.com' any message at all should be redirected to 'me+goodtrue@blah.com' 'me+goodnot@good.com' 'me+goodif@good.com' 'me+goodelseif@good.com' 'me+goodelse@good.com' 'me+goodnull@good.com' 'me+goodnesting@good.com' 'me+goodallof@blah.com' 'me+goodallof@blah.com' 'me+goodallof@blah.com' 'me+goodallof@blah.com' 'me+goodanyof@blah.com' 'me+goodanyof@blah.com' 'me+goodanyof@blah.com' 'me+goodanyof@blah.com' cyrus-imapd-2.5.10/sieve/tests/test/serverm/0000755000175000017500000000000012562247555015771 500000000000000cyrus-imapd-2.5.10/sieve/tests/test/serverm/utmail-address0000644000175000017500000000025012562247555020547 00000000000000MAIL FROM: RCPT TO: DATA Date: Mon, 25 Jan 2003 08:51:06 -0500 From: zme@true.com To: you Subject: simple address test blah . cyrus-imapd-2.5.10/sieve/tests/test/serverm/utmail-header0000644000175000017500000000023412562247555020354 00000000000000MAIL FROM: RCPT TO: DATA Date: Mon, 25 Feb 2002 08:51:06 -0500 From: it To: me Subject: simple header test blah . cyrus-imapd-2.5.10/sieve/tests/test/uberTestScript.s0000644000175000017500000000704513001236020017350 00000000000000/*using redirect to test if, elsif, and else, along with all of the tests that can be inside this is still being added to, there are almost certaintly conditions not being tested */ #address all if address :all :is "from" "zme@true.com" {redirect "me+aallis@blah.com";} if address :all :contains "from" "true.com" {redirect "me+aallcontains@blah.com";} if address :all :matches "from" "*true.com" {redirect "me+aallmatches@blah.com";} #address domain if address :domain :is "from" "true.com" {redirect "me+adomainis@blah.com";} if address :domain :contains "from" "true.com" {redirect "me+adomaincontains@blah.com";} if address :domain :matches "from" "*true*" {redirect "me+adomainmatches@blah.com";} #address localpart if address :localpart :is "from" "zme" {redirect "me+alocalpartis@blah.com";} if address :localpart :contains "from" "z" {redirect "me+alocalpartcontains@blah.com";} if address :localpart :matches "from" "z*" {redirect "me+alocalpartmatches@blah.com";} #add tests/messages that differentiate between header/address. #need to write messages and to tweak tests to make sure everyhting works #as expected if header :contains "Date" "Feb" {redirect "me+headercontains@blah.com";} if header :is "Date" "Mon, 25 Feb 2002 08:51:06 -0500" {redirect "me+headeris@blah.com";} if header :matches "Date" "Mon, 25 Feb *" {redirect "me+headermatches@blah.com";} ########################################################################## #this stuff will be true for a lot of messages # ########################################################################## #stop if exists "To" {redirect "me+toexists@blah.com";} if exists "flooglewart" {redirect "me+badexists@blah.com";} if size :over 10K {redirect "me+over10k@blah.com";} if size :over 1M {redirect "me+over1m@blah.com";} if size :under 1K {redirect "me+under1k@blah.com";} ######################################################################### #this stuff will work for any message. # ######################################################################### #stop if true {redirect "me+goodtrue@blah.com";} if false {redirect "me+badfalse@blah.com";} if not false {redirect "me+goodnot@blah.com";} if true {redirect "me+goodif@blah.com";} else {redirect "me+badif@blah.com";} if false {redirect "me+badelseif@blah.com";} elsif true {redirect "me+goodelseif@blah.com";} else {redirect "me+badelseif@blah.com";} if false {redirect "me+badelse@blah.com";} elsif false {redirect "me+badelse@blah.com";} else {redirect "me+goodelse@blah.com";} if false {} else {redirect "me+goodnull@blah.com";} if true {if true {if true {redirect "me+goodnesting@blah.com";} } } #ALLOF(and) if allof(false, false) {redirect "me+badallof(ff)@blah.com";} else {redirect "me+goodallof@blah.com";} if allof(false, true) {redirect "me+badallof(ft)@blah.com";} else {redirect "me+goodallof@blah.com";} if allof(true, false) {redirect "me+badallof(tf)@blah.com";} else {redirect "me+goodallof@blah.com";} if allof(true, true) {redirect "me+goodallof@blah.com";} else {redirect "me+badallof(tt)@blah.com";} #ANYOF(or) if anyof(false, false) {redirect "me+badanyof(ff)@blah.com";} else {redirect "me+goodanyof@blah.com";} if anyof(false,true) {redirect "me+goodanyof@blah.com";} else {redirect "me+badanyof(ft)@blah.com";} if anyof(true, false) {redirect "me+goodanyof@blah.com";} else {redirect "me+badanyof(tf)@blah.com";} if anyof(true, true) {redirect "me+goodanyof@blah.com";} else {redirect "me+badanyof(tt)@blah.com";} cyrus-imapd-2.5.10/sieve/tests/test/testm/0000755000175000017500000000000012562247555015442 500000000000000cyrus-imapd-2.5.10/sieve/tests/test/testm/utest-header0000644000175000017500000000013012562247555017671 00000000000000Date: Mon, 25 Feb 2002 08:51:06 -0500 From: it To: me Subject: simple header test blah cyrus-imapd-2.5.10/sieve/tests/test/testm/utest-address0000644000175000017500000000014412562247555020073 00000000000000Date: Mon, 25 Jan 2003 08:51:06 -0500 From: zme@true.com To: you Subject: simple address test blah cyrus-imapd-2.5.10/sieve/tests/action/0000755000175000017500000000000013001236020014552 500000000000000cyrus-imapd-2.5.10/sieve/tests/action/serverm/0000755000175000017500000000000012562247555016267 500000000000000cyrus-imapd-2.5.10/sieve/tests/action/serverm/uamail-stop20000644000175000017500000000023112562247555020443 00000000000000MAIL FROM: RCPT TO: DATA Date: Mon, 25 Feb 2003 08:51:06 -0500 From: them To: you Subject: stop discard blah . cyrus-imapd-2.5.10/sieve/tests/action/serverm/uamail-discard0000644000175000017500000000022412562247555021007 00000000000000MAIL FROM: RCPT TO: DATA Date: Mon, 25 Feb 2003 08:51:06 -0500 From: them To: you Subject: discard blah . cyrus-imapd-2.5.10/sieve/tests/action/serverm/uamail-redirect0000644000175000017500000000022512562247555021200 00000000000000MAIL FROM: RCPT TO: DATA Date: Mon, 25 Feb 2003 08:51:06 -0500 From: them To: you Subject: redirect blah . cyrus-imapd-2.5.10/sieve/tests/action/serverm/uamail-stop0000644000175000017500000000022112562247555020360 00000000000000MAIL FROM: RCPT TO: DATA Date: Mon, 25 Feb 2003 08:51:06 -0500 From: them To: you Subject: stop blah . cyrus-imapd-2.5.10/sieve/tests/action/serverm/uamail-keep0000644000175000017500000000022112562247555020317 00000000000000MAIL FROM: RCPT TO: DATA Date: Mon, 25 Feb 2003 08:51:06 -0500 From: them To: you Subject: keep blah . cyrus-imapd-2.5.10/sieve/tests/action/uberActionScript.key0000644000175000017500000000021113001236020020456 00000000000000 discarding message 'uatest-discard' keeping messages 'uatest-keep' 'uatest-stop' 'uatest-stop2' redirecting message 'uatest-redirect'cyrus-imapd-2.5.10/sieve/tests/action/uberActionScript.s0000644000175000017500000000060013001236020020132 00000000000000#this test should be run after ubertestscript. #this depends on ifs and testing to be working properly if header :contains "subject" "stop" {stop;} if header :contains "subject" "keep" {keep;} if header :contains "subject" "discard" {discard;} #this one is already tested by the ubertest script... if header :contains "subject" "redirect" {redirect "me+goodredirect@blah.com";} cyrus-imapd-2.5.10/sieve/tests/action/testm/0000755000175000017500000000000012562247555015740 500000000000000cyrus-imapd-2.5.10/sieve/tests/action/testm/uatest-redirect0000644000175000017500000000012112562247555020701 00000000000000Date: Mon, 25 Feb 2003 08:51:06 -0500 From: them To: you Subject: redirect blah cyrus-imapd-2.5.10/sieve/tests/action/testm/uatest-stop20000644000175000017500000000012512562247555020153 00000000000000Date: Mon, 25 Feb 2003 08:51:06 -0500 From: them To: you Subject: stop discard blah cyrus-imapd-2.5.10/sieve/tests/action/testm/uatest-discard0000644000175000017500000000012012562247555020510 00000000000000Date: Mon, 25 Feb 2003 08:51:06 -0500 From: them To: you Subject: discard blah cyrus-imapd-2.5.10/sieve/tests/action/testm/uatest-keep0000644000175000017500000000011512562247555020027 00000000000000Date: Mon, 25 Feb 2003 08:51:06 -0500 From: them To: you Subject: keep blah cyrus-imapd-2.5.10/sieve/tests/action/testm/uatest-stop0000644000175000017500000000011512562247555020070 00000000000000Date: Mon, 25 Feb 2003 08:51:06 -0500 From: them To: you Subject: stop blah cyrus-imapd-2.5.10/sieve/script.h0000644000175000017500000000625713001236020013542 00000000000000/* script.h -- script definition * Larry Greenfield * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #ifndef SIEVE_SCRIPT_H #define SIEVE_SCRIPT_H #include #include "sieve_interface.h" #include "interp.h" #include "tree.h" struct sieve_script { sieve_interp_t interp; /* was a "require" done for these? */ struct sieve_support { int fileinto : 1; int reject : 1; int envelope : 1; int body : 1; int vacation : 1; int imapflags : 1; int notify : 1; int regex : 1; int subaddress : 1; int relational : 1; int i_ascii_numeric: 1; int include : 1; int copy : 1; int date : 1; int index : 1; int vacation_seconds: 1; int imap4flags : 1; } support; void *script_context; commandlist_t *cmds; int err; char addrerr[500]; /* buffer for address parser error messages */ char sieveerr[1024]; }; typedef struct sieve_bytecode sieve_bytecode_t; struct sieve_bytecode { ino_t inode; /* used to prevent mmapping the same script */ const char *data; size_t len; int fd; int is_executing; /* used to prevent recursive INCLUDEs */ sieve_bytecode_t *next; }; struct sieve_execute { sieve_bytecode_t *bc_list; /* list of loaded bytecode buffers */ sieve_bytecode_t *bc_cur; /* currently active bytecode buffer */ }; int script_require(sieve_script_t *s, char *req); #endif cyrus-imapd-2.5.10/sieve/bc_dump.c0000644000175000017500000002651613001236020013642 00000000000000/* bc_dump.c -- sieve bytecode- dump almost flattened bytecode that was * generated by bc_generate.c * * Rob Siemborski * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #ifdef HAVE_CONFIG_H #include #endif #include "sieve_interface.h" #include "bytecode.h" #if DUMPCODE /*this would work a lot better if we actually could tell how many levels deep in if statements we were. currently it doesn't know*/ static void print_spaces(int n) { int temp_n=0; while(temp_n++ < (n)) { putchar(' '); putchar(' '); putchar(' '); putchar(' '); } } /* Dump a stringlist. Return the last address used by the list */ static int dump_sl(bytecode_info_t *d, int ip, int level) { int numstr = d->data[ip].listlen; int i; for(i=0; idata[++ip].len); printf("%s\n",d->data[++ip].str); } return ip; } static int dump_test(bytecode_info_t *d, int ip, int level); /* Dump a testlist. Return the last address used by the list */ static int dump_tl(bytecode_info_t *d, int ip, int level) { int numtest = d->data[ip].listlen; int i; for(i=0; idata[++ip].jump); ip = dump_test(d, ++ip, level); } return ip; } /* Dump a test, return the last address used by the test */ static int dump_test(bytecode_info_t *d, int ip, int level ) { int has_index=0; const int opcode = d->data[ip].op; print_spaces(level); switch(opcode) { case BC_TRUE: printf("%d: TRUE\n",ip); break; case BC_FALSE: printf("%d: FALSE\n",ip); break; case BC_NOT: printf("%d: NOT TEST(\n",ip++); /* printf(" (until %d)\n", d->data[ip++].jump);*/ ip = dump_test(d,ip, level); print_spaces(level); printf(" )\n"); break; case BC_SIZE: printf("%d: SIZE TAG(%d) NUM(%d)\n",ip, d->data[ip+1].value, d->data[ip+2].value); ip+=2; break; case BC_EXISTS: printf("%d: EXISTS\n",ip++); ip = dump_sl(d,ip,level); break; case BC_ALLOF: case BC_ANYOF: printf("%d: %s (\n",ip, d->data[ip++].op == BC_ALLOF ? "ALLOF" : "ANYOF"); ip = dump_tl(d,ip,level); print_spaces(level); printf(")\n"); break; case BC_HEADER: has_index=1; printf("%d: HEADER (\n",ip++); if (has_index) { print_spaces(level); printf(" INDEX:%d\n", d->data[ip++].value); } print_spaces(level); if (d->data[ip].value == B_COUNT || d->data[ip].value == B_VALUE) { printf(" MATCH:%d RELATION:%d COMP:%d HEADERS:\n", d->data[ip].value, d->data[ip+1].value,d->data[ip+2].value); } else { printf(" MATCH:%d COMP:%d HEADERS:\n",d->data[ip].value, d->data[ip+2].value); } ip+=3; ip = dump_sl(d,ip,level); ip++; print_spaces(level); printf(" DATA:\n"); ip = dump_sl(d,ip,level); break; case BC_HASFLAG: printf("%d: HASFLAG (\n",ip++); print_spaces(level); if (d->data[ip].value == B_COUNT || d->data[ip].value == B_VALUE) { printf(" MATCH:%d RELATION:%d COMP:%d FLAG-VARS:\n", d->data[ip].value, d->data[ip+1].value,d->data[ip+2].value); } else { printf(" MATCH:%d COMP:%d FLAG-VARS:\n",d->data[ip].value, d->data[ip+2].value); } ip+=3; ip = dump_sl(d,ip,level); ip++; print_spaces(level); printf(" DATA:\n"); ip = dump_sl(d,ip,level); break; case BC_ADDRESS: has_index = 1; case BC_ENVELOPE: if (d->data[ip].op == BC_ADDRESS) { printf("%d: ADDRESS (\n",ip++); } else { printf("%d: ENVELOPE (\n",ip++); } if (has_index) { print_spaces(level); printf(" INDEX:%d\n", d->data[ip++].value); } print_spaces(level); if (d->data[ip].value == B_COUNT || d->data[ip].value == B_VALUE) { printf(" MATCH:%d RELATION:%d COMP: %d TYPE: %d HEADERS:\n", d->data[ip].value, d->data[ip+1].value, d->data[ip+2].value, d->data[ip+3].value); } else { printf(" MATCH:%d COMP:%d TYPE:%d HEADERS:\n", d->data[ip].value,d->data[ip+1].value,d->data[ip+3].value); } ip+=4; ip = dump_sl(d,ip,level); ip++; print_spaces(level); printf(" DATA:\n"); ip = dump_sl(d,ip,level); break; case BC_BODY: printf("%d: BODY (\n",ip++); print_spaces(level); if (d->data[ip].value == B_COUNT || d->data[ip].value == B_VALUE) { printf(" MATCH:%d RELATION: %d COMP: %d TRANSFORM: %d OFFSET: %d CONTENT-TYPES:\n", d->data[ip].value,d->data[ip+1].value,d->data[ip+2].value, d->data[ip+3].value,d->data[ip+4].value); } else { printf(" MATCH:%d COMP:%d TRANSFORM:%d OFFSET: %d CONTENT-TYPES:\n", d->data[ip].value,d->data[ip+1].value,d->data[ip+3].value, d->data[ip+4].value); } ip+=5; ip = dump_sl(d,ip,level); ip++; print_spaces(level); printf(" DATA:\n"); ip = dump_sl(d,ip,level); break; case BC_DATE: has_index=1; case BC_CURRENTDATE: if (BC_DATE == opcode) { printf("%d: DATE (\n", ip++); } else { printf("%d: CURRENTDATE (\n", ip++); } /* index */ if (has_index) { print_spaces(level); printf(" INDEX:%d\n", d->data[ip++].value); } /* zone tag */ print_spaces(level); printf(" ZONE-TAG:%d ", d->data[ip].value); switch (d->data[ip++].value) { case B_TIMEZONE: printf("TIMEZONE:%d\n", d->data[ip++].value); break; case B_ORIGINALZONE: printf("ORIGINALZONE\n"); break; } /* comparison */ print_spaces(level); if (d->data[ip].value == B_COUNT || d->data[ip].value == B_VALUE) { printf(" MATCH:%d RELATION:%d COMP:%d\n", d->data[ip].value, d->data[ip+1].value, d->data[ip+2].value); } else { printf(" MATCH:%d COMP:%d\n", d->data[ip].value, d->data[ip+2].value); } ip+=3; /* date type */ print_spaces(level); printf(" DATE-TYPE:%d\n", d->data[ip++].value); /* header name */ if (BC_DATE == opcode) { print_spaces(level); printf(" HEADER NAME: {%d}", d->data[ip++].len); printf("%s\n",d->data[ip++].str); } print_spaces(level); printf(" KEY LIST:\n"); ip = dump_sl(d,ip,level); break; break; default: printf("%d: TEST(%d)\n",ip,d->data[ip].op); break; } return ip; } void dump(bytecode_info_t *d, int level) { int i; printf("Dumping almost flattened bytecode\n\n"); if(!d) return; for(i=0; iscriptend; i++) { print_spaces(level); switch(d->data[i].op) { case B_REJECT: printf("%d: REJECT {%d}%s\n",i, d->data[i+1].len,d->data[i+2].str); i+=2; break; case B_IF: if (d->data[i+3].jump== -1) { printf("%d: IF THEN(%d) POST(%d) TEST(\n",i, d->data[i+1].jump,d->data[i+2].jump); } else { printf("%d: IF THEN(%d) ELSE(%d) POST(%d) TEST(\n",i, d->data[i+1].jump,d->data[i+2].jump, d->data[i+3].jump); } i = dump_test(d,i+4, level+1); printf(")\n"); break; case B_STOP: printf("%d: STOP\n",i); break; case B_DISCARD: printf("%d: DISCARD\n",i); break; case B_KEEP: printf("%d: KEEP FLAGS:\n",i++); i = dump_sl(d,i,level+1); i++; print_spaces(level+1); printf("COPY(%d)\n",i, d->data[i].value); break; case B_MARK: printf("%d: MARK\n",i); break; case B_UNMARK: printf("%d: UNMARK\n",i); break; case B_FILEINTO: printf("%d: FILEINTO FLAGS:\n",i++); i = dump_sl(d,i,level+1); print_spaces(level+1); printf("COPY(%d) FOLDER({%d}%s)\n", d->data[i+1].value,d->data[i+2].len,d->data[i+3].str); i+=3; break; case B_REDIRECT: printf("%d: REDIRECT COPY(%d) ADDRESS({%d}%s)\n",i, d->data[i+1].value,d->data[i+2].len,d->data[i+3].str); i+=3; break; case B_SETFLAG: printf("%d: SETFLAG\n",i); i=dump_sl(d,++i, level); break; case B_ADDFLAG: printf("%d: ADDFLAG\n",i); i=dump_sl(d,++i,level); break; case B_REMOVEFLAG: printf("%d: REMOVEFLAG\n",i); i=dump_sl(d,++i,level); break; case B_DENOTIFY: printf("%d: DENOTIFY priority %d,comp %d %d %s\n", i, d->data[i+1].value, d->data[i+2].value, d->data[i+3].value, (d->data[i+4].len == -1 ? "[nil]" : d->data[i+5].str)); i+=5; break; case B_NOTIFY: printf("%d: NOTIFY\n METHOD(%s),\n ID(%s),\n OPTIONS", i, d->data[i+2].str, (d->data[i+3].len == -1 ? "[nil]" : d->data[i+4].str)); i+=5; i=dump_sl(d,i,level); printf(" PRIORITY(%d),\n MESSAGE({%d}%s)\n", d->data[i+1].value, d->data[i+2].len,d->data[i+3].str); i+=3; break; case B_VACATION_ORIG: case B_VACATION: printf("%d:VACATION\n",i); i++; i=dump_sl(d,i,level); printf("SUBJ({%d}%s) MESG({%d}%s)\n SECONDS(%d) MIME(%d)\n" " FROM({%d}%s) HANDLE({%d}%s)\n", d->data[i+1].len, (d->data[i+1].len == -1 ? "[nil]" : d->data[i+2].str), d->data[i+3].len, (d->data[i+3].len == -1 ? "[nil]" : d->data[i+4].str), d->data[i+5].value * (d->data[i].op == B_VACATION ? 1 : (24 * 60 * 60 /* 1 day */)), d->data[i+6].value, d->data[i+7].len, (d->data[i+7].len == -1 ? "[nil]" : d->data[i+8].str), d->data[i+9].len, (d->data[i+9].len == -1 ? "[nil]" : d->data[i+10].str)); i+=10; break; case B_JUMP: printf("%d: JUMP HUH? this shouldn't be here>?!",i); break; case B_NULL: printf("%d: NULL\n",i); break; case B_INCLUDE: printf("%d: INCLUDE ONCE:%s OPTIONAL:%s LOCATION:%s {%d}%s\n",i, d->data[i+1].value & 64 ? "yes" : "no", d->data[i+1].value & 128 ? "yes" : "no", (d->data[i+1].value & 63) == B_GLOBAL ? "global" : "local", d->data[i+2].len,d->data[i+3].str); i+=3; break; case B_RETURN: printf("%d: RETURN\n",i); break; default: printf("%d: %d\n",i,d->data[i].op); break; } } printf("full len is: %d\n", d->scriptend); } #endif cyrus-imapd-2.5.10/sieve/addr.y0000644000175000017500000000620713001236020013164 00000000000000%{ /* * addr.y -- RFC 822 address parser * Ken Murchison * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #ifdef HAVE_CONFIG_H #include #endif #include #include #include "sieve/script.h" #include "sieve/addr.h" #include "xstrlcpy.h" #define ADDRERR_SIZE 500 void yyerror(sieve_script_t*, const char *); extern int addrlex(YYSTYPE*, sieve_script_t*); #define YYERROR_VERBOSE /* i want better error messages! */ /* byacc default is 500, bison default is 10000 - go with the larger to support big sieve scripts (see Bug #3461) */ #define YYSTACKSIZE 10000 %} %token ATOM QTEXT DTEXT %name-prefix="addr" %defines %parse-param {sieve_script_t *parse_script} %lex-param {sieve_script_t *parse_script} %pure_parser %% sieve_address: addrspec /* simple address */ | phrase '<' addrspec '>' /* name & addr-spec */ ; addrspec: localpart '@' domain /* global-address */ ; localpart: word /* uninterpreted, case-preserved */ | word '.' localpart ; domain: subdomain | subdomain '.' domain ; subdomain: domainref | domainlit ; domainref: ATOM /* symbolic reference */ ; domainlit: '[' DTEXT ']' ; phrase: word | word phrase ; word: ATOM | qstring ; qstring: '"' QTEXT '"' ; %% /* copy address error message into buffer provided by sieve parser */ void yyerror(sieve_script_t *parse_script, const char *s) { strlcpy(parse_script->addrerr, s, ADDRERR_SIZE); } cyrus-imapd-2.5.10/sieve/bc_generate.c0000644000175000017500000006161313001236020014464 00000000000000/* bc_generate.c -- sieve bytecode- almost flattened bytecode * Rob Siemborski * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #ifdef HAVE_CONFIG_H #include #endif #include "xmalloc.h" #include "sieve_interface.h" #include "script.h" #include "tree.h" #include "sieve/sieve.h" #include "bytecode.h" #include "assert.h" #include static int bc_test_generate(int codep, bytecode_info_t *retval, test_t *t); /* returns false if the request can't be satisfied, true if it can. */ static int atleast(bytecode_info_t *arr, size_t len) { if(arr->reallen < len) { /* too small; double if that's big enough, otherwise increase to the requested size. */ arr->reallen = (len > arr->reallen * 2 ? len : arr->reallen * 2); arr->data = xrealloc(arr->data, arr->reallen*sizeof(bytecode_t)); if(!arr->data) { /* out of memory? */ return 0; } } return 1; } /* * functions of the form bc_XXX_generate have the following properties: * on success they return an int that corresponds to the next empty location * for code, and on failure they return -1. * * they will take a bytecode_info_t as a parameter and modify it by * making it larger and adding more bytecommands in the pass 1 form */ /* given a location and a string list, compile it into almost-flat form. * etc... */ static int bc_stringlist_generate(int codep, bytecode_info_t *retval, strarray_t *sa) { int len_codep = codep; int strcount = 0; int i; codep++; /* Bounds check the string list length */ if(!atleast(retval,codep+1)) return -1; if (sa) { for (i = 0 ; i < sa->count ; i++) { char *s = sa->data[i]; strcount++; assert(s!=NULL); /* Bounds check for each string before we allocate it */ if(!atleast(retval,codep+2)) return -1; retval->data[codep++].len = strlen(s); retval->data[codep++].str = s; } } retval->data[len_codep].listlen = strcount; return codep; } /* write a list of tests into almost-flat form, starting at codep. * returns the next code location, -1 on error. */ /* ... */ static int bc_testlist_generate(int codep, bytecode_info_t *retval, testlist_t *tl) { int len_codep = codep; int testcount = 0; testlist_t *cur; codep++; /* Bounds check the test list length */ if(!atleast(retval,codep+1)) return -1; for(cur=tl; cur; cur=cur->next) { int oldcodep = codep; /* Make room for tail marker */ if(!atleast(retval,codep+1)) return -1; testcount++; codep = bc_test_generate(codep+1, retval, cur->t); retval->data[oldcodep].jump = codep; } retval->data[len_codep].listlen = testcount; return codep; } /* output a relation into almost-flat form at codep. * returns new codep on success, -1 on failure. */ static int bc_relation_generate(int codep, bytecode_info_t *retval, int relat) { if (!atleast(retval, codep + 1)) return -1; switch (relat) { case GT: retval->data[codep++].value= B_GT; break; case GE: retval->data[codep++].value= B_GE; break; case LT: retval->data[codep++].value= B_LT; break; case LE: retval->data[codep++].value= B_LE; break; case EQ: retval->data[codep++].value= B_EQ; break; case NE: retval->data[codep++].value= B_NE; break; default: /* comparator has no relational field */ retval->data[codep++].value= -1; break; } return codep; } /* writes a single comparator into almost-flat form starting at codep. * will always write out 3 words * returns the next code location or -1 on error. */ static int bc_comparator_generate(int codep, bytecode_info_t *retval, int comptag, int relat, const char *comparator) { assert(retval != NULL); /* comptag */ if (!atleast(retval, codep + 1)) return -1; switch (comptag) { case IS: retval->data[codep++].value = B_IS; break; case CONTAINS: retval->data[codep++].value = B_CONTAINS; break; case MATCHES: retval->data[codep++].value = B_MATCHES; break; #ifdef ENABLE_REGEX case REGEX: retval->data[codep++].value = B_REGEX; break; #endif case COUNT: retval->data[codep++].value = B_COUNT; break; case VALUE: retval->data[codep++].value = B_VALUE; break; default: return -1; } /*relation*/ codep = bc_relation_generate(codep, retval, relat); /* comparator (value specified with :comparator) */ if (!atleast(retval, codep + 1)) return -1; /* xxx perhaps extend comparator.h to have lookup_comp return an index, and then lookup_by_index return the actual comparator? we can then eliminate the comptag above, too. */ if (!strcmp (comparator, "i;octet")) retval->data[codep++].value = B_OCTET; else if (!strcmp (comparator, "i;ascii-casemap")) retval->data[codep++].value = B_ASCIICASEMAP; else if (!strcmp (comparator, "i;ascii-numeric")) retval->data[codep++].value = B_ASCIINUMERIC; return codep; } static int bc_zone_generate(int codep, bytecode_info_t *retval, int zonetag, const char *zone) { unsigned hours; unsigned minutes; char sign; assert(retval != NULL); /* zonetag */ if (!atleast(retval, codep + 1)) return -1; switch (zonetag) { case ZONE: retval->data[codep++].value = B_TIMEZONE; /* time-zone offset in minutes */ if (!atleast(retval, codep + 1) || sscanf(zone, "%c%02u%02u", &sign, &hours, &minutes) != 3) return -1; retval->data[codep++].value = (sign == '-' ? -1 : 1) * (hours * 60) + minutes; break; case ORIGINALZONE: retval->data[codep++].value = B_ORIGINALZONE; break; default: return -1; } return codep; } /* writes a single test into almost-flat form starting at codep. * returns the next code location or -1 on error. */ static int bc_test_generate(int codep, bytecode_info_t *retval, test_t *t) { if(!retval) return -1; switch(t->type) { case STRUE: /* BC_TRUE */ if(!atleast(retval,codep+1)) return -1; retval->data[codep++].op = BC_TRUE; break; case SFALSE:/* BC_FALSE */ if(!atleast(retval,codep+1)) return -1; retval->data[codep++].op = BC_FALSE; break; case NOT: /* BC_NOT {subtest : test} */ if(!atleast(retval,codep+1)) return -1; retval->data[codep++].op = BC_NOT; codep = bc_test_generate(codep, retval, t->u.t); if (codep == -1) return -1; break; case SIZE: /* BC_SIZE (B_OVER | B_UNDER) {size : int} */ if(!atleast(retval,codep+3)) return -1; retval->data[codep++].op = BC_SIZE; retval->data[codep++].value = (t->u.sz.t == OVER ? B_OVER : B_UNDER); retval->data[codep++].value = t->u.sz.n; break; case EXISTS:/* BC_EXISTS { headers : string list } */ if(!atleast(retval,codep+1)) return -1; retval->data[codep++].op = BC_EXISTS; codep= bc_stringlist_generate(codep, retval, t->u.sl); break; case ANYOF:/* BC_ANYOF { tests : test list } */ if(!atleast(retval,codep+1)) return -1; retval->data[codep++].op = BC_ANYOF; codep=bc_testlist_generate(codep, retval, t->u.tl); if (codep == -1) return -1; break; case ALLOF: /* BC_ALLOF { tests : test list } */ if(!atleast(retval,codep+1)) return -1; retval->data[codep++].op = BC_ALLOF; codep= bc_testlist_generate(codep, retval, t->u.tl); if (codep == -1) return -1; break; case HEADER: case HASFLAG: /* BC_HEADER { i: index } { c: comparator } * { haystacks : string list } { patterns : string list } * * BC_HASFLAG { c: comparator } * { haystacks : string list } { patterns : string list } */ if(!atleast(retval,codep + 1)) return -1; retval->data[codep++].op = (t->type == HEADER) ? BC_HEADER : BC_HASFLAG; if (t->type == HEADER) { /* index */ if(!atleast(retval,codep + 1)) return -1; retval->data[codep++].value = t->u.h.index; } /* comparator */ codep = bc_comparator_generate(codep, retval, t->u.h.comptag, t->u.h.relation, t->u.h.comparator); if (codep == -1) return -1; /* haystacks */ codep = bc_stringlist_generate(codep, retval, t->u.h.sl); if (codep == -1) return -1; /* pattern */ codep = bc_stringlist_generate(codep, retval, t->u.h.pl); if (codep == -1) return -1; break; case ADDRESS: case ENVELOPE: /* BC_ADDRESS {i : index } {c : comparator} (B_ALL | B_LOCALPART | ...) { header : string list } { pattern : string list } BC_ENVELOPE {c : comparator} (B_ALL | B_LOCALPART | ...) { header : string list } { pattern : string list } */ if(!atleast(retval,codep+1)) return -1; retval->data[codep++].op = (t->type == ADDRESS) ? BC_ADDRESS : BC_ENVELOPE; /* index */ if (t->type == ADDRESS) { if(!atleast(retval,codep+1)) return -1; retval->data[codep++].value = t->u.ae.index; } codep = bc_comparator_generate(codep, retval,t->u.ae.comptag, t->u.ae.relation, t->u.ae.comparator); if (codep == -1) return -1; if(!atleast(retval,codep+1)) return -1; /*address part*/ switch(t->u.ae.addrpart) { case ALL: retval->data[codep++].value = B_ALL; break; case LOCALPART: retval->data[codep++].value = B_LOCALPART; break; case DOMAIN: retval->data[codep++].value = B_DOMAIN; break; case USER: retval->data[codep++].value = B_USER; break; case DETAIL: retval->data[codep++].value = B_DETAIL; break; default: return -1; } /*headers*/ codep = bc_stringlist_generate(codep, retval, t->u.ae.sl); if (codep == -1) return -1; /*patterns*/ codep = bc_stringlist_generate(codep, retval, t->u.ae.pl); if (codep == -1) return -1; break; case BODY: /* BC_BODY {c : comparator} (B_RAW | B_TEXT | ...) { content-types : stringlist } { offset : int } { pattern : string list } */ if(!atleast(retval,codep+1)) return -1; retval->data[codep++].op = BC_BODY; codep = bc_comparator_generate(codep, retval,t->u.b.comptag, t->u.b.relation, t->u.b.comparator); if (codep == -1) return -1; if(!atleast(retval,codep+2)) return -1; /*transform*/ switch(t->u.b.transform) { case RAW: retval->data[codep++].value = B_RAW; break; case TEXT: retval->data[codep++].value = B_TEXT; break; case CONTENT: retval->data[codep++].value = B_CONTENT; break; default: return -1; } /*offset*/ retval->data[codep++].value = t->u.b.offset; /*content-types*/ codep = bc_stringlist_generate(codep, retval, t->u.b.content_types); if (codep == -1) return -1; /*patterns*/ codep = bc_stringlist_generate(codep, retval, t->u.b.pl); if (codep == -1) return -1; break; case DATE: case CURRENTDATE: /* BC_DATE { i: index } { time-zone: string} { c: comparator } * { header-name : string } { date-part: string } * { key-list : string list } * * BC_CURRENTDATE { time-zone: string} { c: comparator } * { date-part: string } { key-list : string list } */ if(!atleast(retval,codep + 1)) return -1; retval->data[codep++].op = (DATE == t->type) ? BC_DATE : BC_CURRENTDATE; /* index */ if (DATE == t->type) { if(!atleast(retval,codep + 1)) return -1; retval->data[codep++].value = t->u.dt.index; } /* zone */ codep = bc_zone_generate(codep, retval, t->u.dt.zonetag, t->u.dt.zone); if (codep == -1) return -1; /* comparator */ codep = bc_comparator_generate(codep, retval, t->u.dt.comptag, t->u.dt.relation, t->u.dt.comparator); if (codep == -1) return -1; /* date-part */ if(!atleast(retval,codep + 1)) return -1; switch (t->u.dt.date_part) { case YEAR: retval->data[codep++].value = B_YEAR; break; case MONTH: retval->data[codep++].value = B_MONTH; break; case DAY: retval->data[codep++].value = B_DAY; break; case DATE: retval->data[codep++].value = B_DATE; break; case JULIAN: retval->data[codep++].value = B_JULIAN; break; case HOUR: retval->data[codep++].value = B_HOUR; break; case MINUTE: retval->data[codep++].value = B_MINUTE; break; case SECOND: retval->data[codep++].value = B_SECOND; break; case TIME: retval->data[codep++].value = B_TIME; break; case ISO8601: retval->data[codep++].value = B_ISO8601; break; case STD11: retval->data[codep++].value = B_STD11; break; case ZONE: retval->data[codep++].value = B_ZONE; break; case WEEKDAY: retval->data[codep++].value = B_WEEKDAY; break; } if (DATE == t->type) { /* header-name */ if(!atleast(retval,codep + 2)) return -1; retval->data[codep++].len = strlen(t->u.dt.header_name); retval->data[codep++].str = t->u.dt.header_name; } /* keywords */ codep = bc_stringlist_generate(codep, retval, t->u.dt.kl); if (codep == -1) return -1; break; default: return -1; } return codep; } /* generate a not-quite-flattened bytecode */ /* returns address of next instruction or -1 on error*/ /* needs current instruction, buffer for the code, and a current parse tree */ /* sieve is cool because everything is immediate! */ static int bc_action_generate(int codep, bytecode_info_t *retval, commandlist_t *c) { int jumploc; if (!retval) return -1; if (c == NULL) { if (!atleast(retval, codep+1)) return -1; retval->data[codep++].op = B_NULL; } else { do { switch(c->type) { case STOP: /* STOP (no arguments) */ if (!atleast(retval, codep+1)) return -1; retval->data[codep++].op = B_STOP; break; case DISCARD: /* DISCARD (no arguments) */ if (!atleast(retval, codep+1)) return -1; retval->data[codep++].op = B_DISCARD; break; case KEEP: /* KEEP STRINGLIST flags VALUE copy */ if (!atleast(retval, codep+1)) return -1; retval->data[codep++].op = B_KEEP; codep = bc_stringlist_generate(codep,retval,c->u.k.flags); if (codep == -1) return -1; if(!atleast(retval,codep+1)) return -1; retval->data[codep++].value = c->u.k.copy; break; case MARK: /* MARK (no arguments) */ if (!atleast(retval, codep+1)) return -1; retval->data[codep++].op = B_MARK; break; case UNMARK: /* UNMARK (no arguments) */ if (!atleast(retval, codep+1)) return -1; retval->data[codep++].op = B_UNMARK; break; case RETURN: /* RETURN (no arguments) */ if (!atleast(retval, codep+1)) return -1; retval->data[codep++].op = B_RETURN; break; case DENOTIFY: /* DENOTIFY */ if (!atleast(retval, codep+6)) return -1; retval->data[codep++].op = B_DENOTIFY; switch(c->u.d.priority) { case LOW: retval->data[codep++].value = B_LOW; break; case NORMAL: retval->data[codep++].value = B_NORMAL; break; case HIGH: retval->data[codep++].value = B_HIGH; break; case ANY: retval->data[codep++].value = B_ANY; break; default: return -1; } switch(c->u.d.comptag) { case IS: retval->data[codep++].value = B_IS; break; case CONTAINS: retval->data[codep++].value = B_CONTAINS; break; case MATCHES: retval->data[codep++].value = B_MATCHES; break; #ifdef ENABLE_REGEX case REGEX: retval->data[codep++].value = B_REGEX; break; #endif case ANY: retval->data[codep++].value = B_ANY; break; default: return -1; } codep = bc_relation_generate(codep, retval, c->u.d.relation); if(c->u.d.pattern) { retval->data[codep++].len = strlen(c->u.d.pattern); retval->data[codep++].str = c->u.d.pattern; } else { retval->data[codep++].len = -1; retval->data[codep++].str = NULL; } break; case REJCT: /* REJECT (STRING: len + dataptr) */ if (!atleast(retval, codep+3)) return -1; retval->data[codep++].op = B_REJECT; retval->data[codep++].len = strlen(c->u.str); retval->data[codep++].str = c->u.str; break; case FILEINTO: /* FILEINTO STRINGLIST flags VALUE copy STRING folder */ if (!atleast(retval, codep+1)) return -1; retval->data[codep++].op = B_FILEINTO; codep = bc_stringlist_generate(codep, retval, c->u.f.flags); if(codep == -1) return -1; if (!atleast(retval, codep+3)) return -1; retval->data[codep++].value = c->u.f.copy; retval->data[codep++].len = strlen(c->u.f.folder); retval->data[codep++].str = c->u.f.folder; break; case REDIRECT: /* REDIRECT VALUE copy STRING address */ if (!atleast(retval, codep+4)) return -1; retval->data[codep++].op = B_REDIRECT; retval->data[codep++].value = c->u.r.copy; retval->data[codep++].len = strlen(c->u.r.address); retval->data[codep++].str = c->u.r.address; break; case ADDFLAG: /* ADDFLAG stringlist */ if (!atleast(retval, codep+1)) return -1; retval->data[codep++].op = B_ADDFLAG; codep = bc_stringlist_generate(codep,retval,c->u.sl); if (codep == -1) return -1; break; case SETFLAG: /* SETFLAG stringlist */ if (!atleast(retval, codep+1)) return -1; retval->data[codep++].op = B_SETFLAG; codep = bc_stringlist_generate(codep,retval,c->u.sl); if (codep == -1) return -1; break; case REMOVEFLAG: /* REMOVEFLAG stringlist */ if (!atleast(retval, codep+1)) return -1; retval->data[codep++].op = B_REMOVEFLAG; codep = bc_stringlist_generate(codep,retval,c->u.sl); if (codep == -1) return -1; break; case NOTIFY: /* NOTIFY (STRING: len + dataptr) (STRING: len + dataptr) stringlist (STRING: len + dataptr) (STRING: len + dataptr) method/id /options list/priority/message */ if (!atleast(retval, codep+5)) return -1; retval->data[codep++].op = B_NOTIFY; retval->data[codep++].len = strlen(c->u.n.method); retval->data[codep++].str = c->u.n.method; if (c->u.n.id) { retval->data[codep++].len = strlen(c->u.n.id); retval->data[codep++].str = c->u.n.id; } else { retval->data[codep++].len = -1; retval->data[codep++].str = NULL; } codep = bc_stringlist_generate(codep,retval,c->u.n.options); if (codep == -1) return -1; if (!atleast(retval, codep+3)) return -1; switch(c->u.n.priority) { case LOW: retval->data[codep++].value = B_LOW; break; case NORMAL: retval->data[codep++].value = B_NORMAL; break; case HIGH: retval->data[codep++].value = B_HIGH; break; case ANY: retval->data[codep++].value = B_ANY; break; default: return -1; } retval->data[codep++].len = strlen(c->u.n.message); retval->data[codep++].str = c->u.n.message; break; case VACATION: /* VACATION STRINGLIST addresses STRING subject (if len is -1, then subject was NULL) STRING message (again, len == -1 means message was NULL) VALUE seconds VALUE mime STRING from (if len is -1, then from was NULL) STRING handle (again, len == -1 means handle was NULL) */ if (!atleast(retval, codep+1)) return -1; retval->data[codep++].op = B_VACATION; codep = bc_stringlist_generate(codep,retval,c->u.v.addresses); if (codep == -1) return -1; if (!atleast(retval, codep+2)) return -1; if (c->u.v.subject) { retval->data[codep++].len = strlen(c->u.v.subject); retval->data[codep++].str = c->u.v.subject; } else { retval->data[codep++].len = -1; retval->data[codep++].str = NULL; } if (!atleast(retval, codep+2)) return -1; if (c->u.v.message) { retval->data[codep++].len = strlen(c->u.v.message); retval->data[codep++].str = c->u.v.message; } else { retval->data[codep++].len = -1; retval->data[codep++].str = NULL; } if (!atleast(retval, codep+2)) return -1; retval->data[codep++].value = c->u.v.seconds; retval->data[codep++].value = c->u.v.mime; if (!atleast(retval, codep+2)) return -1; if (c->u.v.from) { retval->data[codep++].len = strlen(c->u.v.from); retval->data[codep++].str = c->u.v.from; } else { retval->data[codep++].len = -1; retval->data[codep++].str = NULL; } if (!atleast(retval, codep+2)) return -1; if (c->u.v.handle) { retval->data[codep++].len = strlen(c->u.v.handle); retval->data[codep++].str = c->u.v.handle; } else { retval->data[codep++].len = -1; retval->data[codep++].str = NULL; } if (codep == -1) return -1; break; case INCLUDE: /* INCLUDE VALUE location + (once << 6) + (optional << 7) STRING filename */ if (!atleast(retval, codep+4)) return -1; retval->data[codep++].op = B_INCLUDE; switch(c->u.inc.location) { case PERSONAL: retval->data[codep].value = B_PERSONAL; break; case GLOBAL: retval->data[codep].value = B_GLOBAL; break; default: return -1; } retval->data[codep++].value |= (c->u.inc.once << 6) | (c->u.inc.optional << 7); retval->data[codep++].len = strlen(c->u.inc.script); retval->data[codep++].str = c->u.inc.script; break; case IF: { int jumpVal; /* IF (int: begin then block) (int: end then block/begin else block) (int:end else block) (-1 if no else block) (test) (then block) (else block)(optional) */ /* Allocate operator + jump table offsets */ if (!atleast(retval, codep+4)) return -1; jumploc = codep+4; retval->data[codep++].op = B_IF; /* begining of then code */ jumpVal = bc_test_generate(jumploc,retval,c->u.i.t); if (jumpVal == -1) return -1; else { retval->data[codep].jump = jumpVal; codep++; } /* find then code and offset to else code, * we want to write this code starting at the offset we * just found */ jumpVal = bc_action_generate(jumpVal,retval, c->u.i.do_then); if (jumpVal == -1) return -1; else retval->data[codep].jump = jumpVal; codep++; /* write else code if its there*/ if (c->u.i.do_else) { jumpVal = bc_action_generate(jumpVal,retval, c->u.i.do_else); if(jumpVal == -1) return -1; else retval->data[codep].jump = jumpVal; /* Update code pointer to end of else code */ codep = retval->data[codep].jump; } else { /*there is no else block, so its -1*/ retval->data[codep].jump = -1; /* Update code pointer to end of then code */ codep = retval->data[codep-1].jump; } } break; default: /* no such action known */ return -1; } /* generate from next command */ c = c->next; } while(c); } /* scriptend may be updated before the end, but it will be * updated at the end, which is what matters. */ retval->scriptend = codep; return codep; } /* Entry point to the bytecode emitter module */ EXPORTED int sieve_generate_bytecode(bytecode_info_t **retval, sieve_script_t *s) { commandlist_t *c; if(!retval) return -1; if(!s) return -1; c = s->cmds; /* if c is NULL, it is handled in bc_action_generate and a script with only BC_NULL is returned */ *retval = xmalloc(sizeof(bytecode_info_t)); if(!(*retval)) return -1; memset(*retval, 0, sizeof(bytecode_info_t)); return bc_action_generate(0, *retval, c); } EXPORTED void sieve_free_bytecode(bytecode_info_t **p) { if(!p || !*p) return; if((*p)->data) free((*p)->data); free(*p); *p = NULL; } cyrus-imapd-2.5.10/sieve/script.c0000644000175000017500000005667513001236020013546 00000000000000/* script.c -- sieve script functions * Larry Greenfield * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #ifdef HAVE_CONFIG_H #include #endif #include #include #include #include #include #include #include #include "assert.h" #include "charset.h" #include "xmalloc.h" #include "sieve_interface.h" #include "interp.h" #include "script.h" #include "tree.h" #include "map.h" #include "util.h" #include "sieve/sieve.h" #include "message.h" #include "bytecode.h" #include "libconfig.h" /* generated by the yacc script */ int sieveparse(sieve_script_t *script); void sieverestart (FILE *input_file); #define ERR_BUF_SIZE 1024 /* does this interpretor support this requirement? */ int script_require(sieve_script_t *s, char *req) { unsigned long config_sieve_extensions = config_getbitfield(IMAPOPT_SIEVE_EXTENSIONS); if (!strcmp("fileinto", req)) { if (s->interp.fileinto && (config_sieve_extensions & IMAP_ENUM_SIEVE_EXTENSIONS_FILEINTO)) { s->support.fileinto = 1; return 1; } else { return 0; } } else if (!strcmp("reject", req)) { if (s->interp.reject && (config_sieve_extensions & IMAP_ENUM_SIEVE_EXTENSIONS_REJECT)) { s->support.reject = 1; return 1; } else { return 0; } } else if (!strcmp("envelope", req)) { if (s->interp.getenvelope && (config_sieve_extensions & IMAP_ENUM_SIEVE_EXTENSIONS_ENVELOPE)) { s->support.envelope = 1; return 1; } else { return 0; } } else if (!strcmp("body", req)) { if (s->interp.getbody && (config_sieve_extensions & IMAP_ENUM_SIEVE_EXTENSIONS_BODY)) { s->support.body = 1; return 1; } else { return 0; } } else if (!strcmp("vacation", req)) { if (s->interp.vacation && (config_sieve_extensions & IMAP_ENUM_SIEVE_EXTENSIONS_VACATION)) { s->support.vacation = 1; return 1; } else { return 0; } } else if (!strcmp("vacation-seconds", req)) { if (s->interp.vacation && (config_sieve_extensions & IMAP_ENUM_SIEVE_EXTENSIONS_VACATION_SECONDS)) { /* Note that "vacation-seconds" implies "vacation", and a script * with "vacation-seconds" in a "require" list MAY omit "vacation" * from that list. */ s->support.vacation = 1; s->support.vacation_seconds = 1; return 1; } else { return 0; } } else if (!strcmp("imapflags", req)) { if (s->interp.markflags->count && (config_sieve_extensions & IMAP_ENUM_SIEVE_EXTENSIONS_IMAPFLAGS)) { s->support.imapflags = 1; return 1; } else { return 0; } } else if (!strcmp("imap4flags", req) && (config_sieve_extensions & IMAP_ENUM_SIEVE_EXTENSIONS_IMAP4FLAGS)) { s->support.imap4flags = 1; return 1; } else if (!strcmp("notify",req)) { if (s->interp.notify && (config_sieve_extensions & IMAP_ENUM_SIEVE_EXTENSIONS_NOTIFY)) { s->support.notify = 1; return 1; } else { return 0; } } else if (!strcmp("include", req)) { if (s->interp.getinclude && (config_sieve_extensions & IMAP_ENUM_SIEVE_EXTENSIONS_INCLUDE)) { s->support.include = 1; return 1; } else { return 0; } #ifdef ENABLE_REGEX } else if (!strcmp("regex", req) && (config_sieve_extensions & IMAP_ENUM_SIEVE_EXTENSIONS_REGEX)) { s->support.regex = 1; return 1; #endif } else if (!strcmp("subaddress", req) && (config_sieve_extensions & IMAP_ENUM_SIEVE_EXTENSIONS_SUBADDRESS)) { s->support.subaddress = 1; return 1; } else if (!strcmp("relational", req) && (config_sieve_extensions & IMAP_ENUM_SIEVE_EXTENSIONS_RELATIONAL)) { s->support.relational = 1; return 1; } else if (!strcmp("comparator-i;octet", req)) { return 1; } else if (!strcmp("comparator-i;ascii-casemap", req)) { return 1; } else if (!strcmp("comparator-i;ascii-numeric", req)) { s->support.i_ascii_numeric = 1; return 1; } else if (!strcmp("copy", req) && (config_sieve_extensions & IMAP_ENUM_SIEVE_EXTENSIONS_COPY)) { s->support.copy = 1; return 1; } else if (!strcmp("date", req) && (config_sieve_extensions & IMAP_ENUM_SIEVE_EXTENSIONS_DATE)) { s->support.date = 1; return 1; } else if (!strcmp("index", req) && (config_sieve_extensions & IMAP_ENUM_SIEVE_EXTENSIONS_INDEX)) { s->support.index = 1; return 1; } return 0; } /* given an interpretor and a script, produce an executable script */ EXPORTED int sieve_script_parse(sieve_interp_t *interp, FILE *script, void *script_context, sieve_script_t **ret) { sieve_script_t *s; int res = SIEVE_OK; res = interp_verify(interp); if (res != SIEVE_OK) { return res; } s = (sieve_script_t *) xmalloc(sizeof(sieve_script_t)); s->interp = *interp; s->script_context = script_context; /* clear all support bits */ memset(&s->support, 0, sizeof(struct sieve_support)); s->err = 0; sieverestart(script); s->cmds = NULL; extern int sievelineno; sievelineno = 1; /* reset line number */ if (sieveparse(s)) { free_tree(s->cmds); s->cmds = NULL; } if (s->err > 0) { sieve_script_free(&s); res = SIEVE_PARSE_ERROR; } *ret = s; return res; } EXPORTED void sieve_script_free(sieve_script_t **s) { if (*s) { if ((*s)->cmds) free_tree((*s)->cmds); free(*s); *s = NULL; } } static void add_header(sieve_interp_t *i, int isenv, char *header, void *message_context, struct buf *out) { const char **h; char *decoded_header; /* get header value */ if (isenv) i->getenvelope(message_context, header, &h); else i->getheader(message_context, header, &h); if (!h || !h[0]) return; decoded_header = charset_parse_mimeheader(h[0]); buf_appendcstr(out, decoded_header); free(decoded_header); } static int build_notify_message(sieve_interp_t *i, const char *msg, void *message_context, struct buf *out) { const char *c; size_t n; if (msg == NULL) return SIEVE_OK; /* construct the message */ c = msg; while (*c) { /* expand variables */ if (!strncasecmp(c, "$from$", 6)) { add_header(i, 0 ,"From", message_context, out); c += 6; } else if (!strncasecmp(c, "$env-from$", 10)) { add_header(i, 1, "From", message_context, out); c += 10; } else if (!strncasecmp(c, "$subject$", 9)) { add_header(i, 0, "Subject", message_context, out); c += 9; } else if (i->getbody && !strncasecmp(c, "$text", 5) && (c[5] == '[' || c[5] == '$')) { const char *content_types[] = { "text", NULL }; sieve_bodypart_t **parts = NULL; c += 5; n = 0; if (*c++ == '[') { while (*c != ']') n = n * 10 + (*c++ - '0'); c += 2; /* skip ]$ */ } i->getbody(message_context, content_types, &parts); /* we only use the first text part */ if (parts && parts[0] && parts[0]->decoded_body) { size_t size = strlen(parts[0]->decoded_body); if (n && size > n) size = n; buf_appendmap(out, parts[0]->decoded_body, size); } /* free the results */ if (parts) { sieve_bodypart_t **p; for (p = parts; *p; p++) free(*p); free(parts); } } else { /* find length of plaintext up to next potential variable */ n = strcspn(c+1, "$") + 1; /* skip opening '$' */ buf_appendmap(out, c, n); c += n; } } buf_cstring(out); return SIEVE_OK; } static int send_notify_callback(sieve_interp_t *interp, void *message_context, void * script_context, notify_list_t *notify, char *actions_string, const char **errmsg) { sieve_notify_context_t nc; struct buf out = BUF_INITIALIZER; int ret; assert(notify->isactive); if (!notify->method || !notify->options || !notify->priority || !notify->message) { return SIEVE_RUN_ERROR; } nc.method = notify->method; nc.options = notify->options ? notify->options : NULL; nc.priority = notify->priority; if(nc.options && !strcmp(nc.method,"mailto")) if(!strcmp("$env-from$",*nc.options)) interp->getenvelope(message_context, "From", &nc.options); build_notify_message(interp, notify->message, message_context, &out); buf_appendcstr(&out, "\n\n"); buf_appendcstr(&out, actions_string); nc.message = buf_cstring(&out); ret = interp->notify(&nc, interp->interp_context, script_context, message_context, errmsg); buf_free(&out); return ret; } static char *action_to_string(action_t action) { switch(action) { case ACTION_NULL: return "NULL"; case ACTION_NONE: return "None"; case ACTION_REJECT: return "Reject"; case ACTION_FILEINTO: return "Fileinto"; case ACTION_KEEP: return "Keep"; case ACTION_REDIRECT: return "Redirect"; case ACTION_DISCARD: return "Discard"; case ACTION_VACATION: return "Vacation"; case ACTION_SETFLAG: return "Setflag"; case ACTION_ADDFLAG: return "Addflag"; case ACTION_REMOVEFLAG: return "Removeflag"; case ACTION_MARK: return "Mark"; case ACTION_UNMARK: return "Unmark"; case ACTION_NOTIFY: return "Notify"; case ACTION_DENOTIFY: return "Denotify"; default: return "Unknown"; } /* never reached */ } static char *sieve_errstr(int code) { switch (code) { case SIEVE_FAIL: return "Generic Error"; case SIEVE_NOT_FINALIZED: return "Sieve not finalized"; case SIEVE_PARSE_ERROR: return "Parse error"; case SIEVE_RUN_ERROR: return "Run error"; case SIEVE_INTERNAL_ERROR: return "Internal Error"; case SIEVE_NOMEM: return "No memory"; default: return "Unknown error"; } /* never reached */ } /******************************bytecode functions***************************** *****************************************************************************/ /* Load a compiled script */ EXPORTED int sieve_script_load(const char *fname, sieve_execute_t **ret) { struct stat sbuf; sieve_execute_t *ex; sieve_bytecode_t *bc; int dofree = 0; if (!fname || !ret) return SIEVE_FAIL; if (stat(fname, &sbuf) == -1) { if (errno == ENOENT) { syslog(LOG_DEBUG, "WARNING: sieve script %s doesn't exist: %m", fname); } else { syslog(LOG_DEBUG, "IOERROR: fstating sieve script %s: %m", fname); } return SIEVE_FAIL; } if (!*ret) { /* new sieve_bytecode_t */ ex = (sieve_execute_t *) xzmalloc(sizeof(sieve_execute_t)); dofree = 1; } else { /* existing sieve_execute_t (INCLUDE) */ ex = *ret; } /* see if we already have this script loaded */ bc = ex->bc_list; while (bc) { if (sbuf.st_ino == bc->inode) break; bc = bc->next; } if (!bc) { int fd; /* new script -- load it */ fd = open(fname, O_RDONLY); if (fd == -1) { syslog(LOG_ERR, "IOERROR: can not open sieve script %s: %m", fname); if (dofree) free(ex); return SIEVE_FAIL; } if (fstat(fd, &sbuf) == -1) { syslog(LOG_ERR, "IOERROR: fstating sieve script %s: %m", fname); close(fd); if (dofree) free(ex); return SIEVE_FAIL; } bc = (sieve_bytecode_t *) xzmalloc(sizeof(sieve_bytecode_t)); bc->fd = fd; bc->inode = sbuf.st_ino; map_refresh(fd, 1, &bc->data, &bc->len, sbuf.st_size, fname, "sievescript"); /* add buffer to list */ bc->next = ex->bc_list; ex->bc_list = bc; ex->bc_cur = bc; *ret = ex; return SIEVE_OK; } else { // script was loaded in the past ex->bc_cur = bc; *ret = ex; return SIEVE_SCRIPT_RELOADED; } } EXPORTED int sieve_script_unload(sieve_execute_t **s) { if(s && *s) { sieve_bytecode_t *bc = (*s)->bc_list; sieve_bytecode_t *nextbc; /* free each bytecode buffer in the linked list */ while (bc) { map_free(&(bc->data), &(bc->len)); close(bc->fd); nextbc = bc->next; free(bc); bc = nextbc; } free(*s); *s = NULL; } /*i added this else, i'm not sure why, but this function always returned SIEVE_FAIL*/ else return SIEVE_FAIL; return SIEVE_OK; } #define ACTIONS_STRING_LEN 4096 static int do_sieve_error(int ret, sieve_interp_t *interp, void *script_context, void *message_context, strarray_t *imapflags, action_list_t *actions, notify_list_t *notify_list, /* notify_action_t *notify_action,*/ int lastaction, int implicit_keep, char *actions_string, const char *errmsg ) { if (ret != SIEVE_OK) { if (lastaction == -1) /* we never executed an action */ snprintf(actions_string+strlen(actions_string), ACTIONS_STRING_LEN-strlen(actions_string), "script execution failed: %s\n", errmsg ? errmsg : sieve_errstr(ret)); else snprintf(actions_string+strlen(actions_string), ACTIONS_STRING_LEN-strlen(actions_string), "%s action failed: %s\n", action_to_string(lastaction), errmsg ? errmsg : sieve_errstr(ret)); } /* Process notify actions */ if (interp->notify && notify_list) { notify_list_t *n = notify_list; int notify_ret = SIEVE_OK; while (n != NULL) { if (n->isactive) { lastaction = ACTION_NOTIFY; notify_ret = send_notify_callback(interp, message_context, script_context,n, actions_string, &errmsg); ret |= notify_ret; } n = n->next; } if (notify_list) free_notify_list(notify_list); notify_list = NULL; /* don't try any notifications again */ if (notify_ret != SIEVE_OK) return do_sieve_error(ret, interp, script_context, message_context, imapflags, actions, notify_list, lastaction, implicit_keep, actions_string, errmsg); } if ((ret != SIEVE_OK) && interp->execute_err) { char buf[ERR_BUF_SIZE]; if (lastaction == -1) /* we never executed an action */ snprintf(buf, ERR_BUF_SIZE, "%s", errmsg ? errmsg : sieve_errstr(ret)); else { if (interp->lastitem) { snprintf(buf, ERR_BUF_SIZE, "%s (%s): %s", action_to_string(lastaction), interp->lastitem, errmsg ? errmsg : sieve_errstr(ret)); } else { snprintf(buf, ERR_BUF_SIZE, "%s: %s", action_to_string(lastaction), errmsg ? errmsg : sieve_errstr(ret)); } } ret |= interp->execute_err(buf, interp->interp_context, script_context, message_context); } if (implicit_keep) { sieve_keep_context_t keep_context; int keep_ret; keep_context.imapflags = imapflags; lastaction = ACTION_KEEP; keep_ret = interp->keep(&keep_context, interp->interp_context, script_context, message_context, &errmsg); ret |= keep_ret; if (keep_ret == SIEVE_OK) snprintf(actions_string+strlen(actions_string), ACTIONS_STRING_LEN-strlen(actions_string), "Kept\n"); else { implicit_keep = 0; /* don't try an implicit keep again */ return do_sieve_error(ret, interp, script_context, message_context, imapflags, actions, notify_list, lastaction, implicit_keep, actions_string, errmsg); } } if (actions) free_action_list(actions); return ret; } static int do_action_list(sieve_interp_t *interp, void *script_context, void *message_context, strarray_t *imapflags, action_list_t *actions, notify_list_t *notify_list, /* notify_action_t *notify_action,*/ char *actions_string, const char *errmsg) { action_list_t *a; action_t lastaction = -1; int ret = 0; int implicit_keep = 1; strcpy(actions_string,"Action(s) taken:\n"); /* now perform actions attached to m */ a = actions; while (a != NULL) { lastaction = a->a; errmsg = NULL; implicit_keep = implicit_keep && !a->cancel_keep; switch (a->a) { case ACTION_REJECT: if (!interp->reject) return SIEVE_INTERNAL_ERROR; ret = interp->reject(&a->u.rej, interp->interp_context, script_context, message_context, &errmsg); free(interp->lastitem); interp->lastitem = xstrdup(a->u.rej.msg); if (ret == SIEVE_OK) snprintf(actions_string+strlen(actions_string), ACTIONS_STRING_LEN-strlen(actions_string), "Rejected with: %s\n", a->u.rej.msg); break; case ACTION_FILEINTO: if (!interp->fileinto) return SIEVE_INTERNAL_ERROR; ret = interp->fileinto(&a->u.fil, interp->interp_context, script_context, message_context, &errmsg); free(interp->lastitem); interp->lastitem = xstrdup(a->u.fil.mailbox); if (ret == SIEVE_OK) snprintf(actions_string+strlen(actions_string), ACTIONS_STRING_LEN-strlen(actions_string), "Filed into: %s\n",a->u.fil.mailbox); break; case ACTION_KEEP: if (!interp->keep) return SIEVE_INTERNAL_ERROR; ret = interp->keep(&a->u.keep, interp->interp_context, script_context, message_context, &errmsg); free(interp->lastitem); interp->lastitem = NULL; if (ret == SIEVE_OK) snprintf(actions_string+strlen(actions_string), ACTIONS_STRING_LEN-strlen(actions_string), "Kept\n"); break; case ACTION_REDIRECT: if (!interp->redirect) return SIEVE_INTERNAL_ERROR; ret = interp->redirect(&a->u.red, interp->interp_context, script_context, message_context, &errmsg); free(interp->lastitem); interp->lastitem = xstrdup(a->u.red.addr); if (ret == SIEVE_OK) snprintf(actions_string+strlen(actions_string), ACTIONS_STRING_LEN-strlen(actions_string), "Redirected to %s\n", a->u.red.addr); break; case ACTION_DISCARD: if (interp->discard) /* discard is optional */ ret = interp->discard(NULL, interp->interp_context, script_context, message_context, &errmsg); free(interp->lastitem); interp->lastitem = NULL; if (ret == SIEVE_OK) snprintf(actions_string+strlen(actions_string), ACTIONS_STRING_LEN-strlen(actions_string), "Discarded\n"); break; case ACTION_VACATION: { if (!interp->vacation) return SIEVE_INTERNAL_ERROR; /* first, let's figure out if we should respond to this */ ret = interp->vacation->autorespond(&a->u.vac.autoresp, interp->interp_context, script_context, message_context, &errmsg); free(interp->lastitem); interp->lastitem = NULL; if (ret == SIEVE_OK) { /* send the response */ ret = interp->vacation->send_response(&a->u.vac.send, interp->interp_context, script_context, message_context, &errmsg); if (ret == SIEVE_OK) snprintf(actions_string+strlen(actions_string), ACTIONS_STRING_LEN-strlen(actions_string), "Sent vacation reply\n"); } else if (ret == SIEVE_DONE) { snprintf(actions_string+strlen(actions_string), ACTIONS_STRING_LEN-strlen(actions_string), "Vacation reply suppressed\n"); ret = SIEVE_OK; } break; } case ACTION_SETFLAG: strarray_fini(imapflags); break; case ACTION_ADDFLAG: strarray_add_case(imapflags, a->u.fla.flag); free(interp->lastitem); interp->lastitem = xstrdup(a->u.fla.flag); break; case ACTION_REMOVEFLAG: strarray_remove_all_case(imapflags, a->u.fla.flag); free(interp->lastitem); interp->lastitem = xstrdup(a->u.fla.flag); break; case ACTION_MARK: { int n = interp->markflags->count; ret = SIEVE_OK; while (n) { strarray_add_case(imapflags, interp->markflags->data[--n]); } free(interp->lastitem); interp->lastitem = NULL; break; } case ACTION_UNMARK: { int n = interp->markflags->count; ret = SIEVE_OK; while (n) { strarray_remove_all_case(imapflags, interp->markflags->data[--n]); } free(interp->lastitem); interp->lastitem = NULL; break; } case ACTION_NONE: break; default: ret = SIEVE_INTERNAL_ERROR; break; } a = a->next; if (ret != SIEVE_OK) { /* uh oh! better bail! */ break; } } return do_sieve_error(ret, interp, script_context, message_context, imapflags, actions, notify_list, lastaction, implicit_keep, actions_string, errmsg); } /* execute some bytecode */ int sieve_eval_bc(sieve_execute_t *exe, int is_incl, sieve_interp_t *i, void *sc, void *m, variable_list_t * flagvars, action_list_t *actions, notify_list_t *notify_list, const char **errmsg, variable_list_t *workingvars); EXPORTED int sieve_execute_bytecode(sieve_execute_t *exe, sieve_interp_t *interp, void *script_context, void *message_context) { action_list_t *actions = NULL; notify_list_t *notify_list = NULL; /* notify_action_t *notify_action;*/ action_t lastaction = -1; int ret; char actions_string[ACTIONS_STRING_LEN] = ""; const char *errmsg = NULL; strarray_t imapflags = STRARRAY_INITIALIZER; strarray_t workingflags = STRARRAY_INITIALIZER; variable_list_t flagvars = VARIABLE_LIST_INITIALIZER; variable_list_t workingvars = VARIABLE_LIST_INITIALIZER; flagvars.var = &imapflags; workingvars.var = &workingflags; if (!interp) return SIEVE_FAIL; if (interp->notify) { notify_list = new_notify_list(); if (notify_list == NULL) { return do_sieve_error(SIEVE_NOMEM, interp, script_context, message_context, &imapflags, actions, notify_list, lastaction, 0, actions_string, errmsg); } } actions = new_action_list(); if (actions == NULL) { ret = do_sieve_error(SIEVE_NOMEM, interp, script_context, message_context, &imapflags, actions, notify_list, lastaction, 0, actions_string, errmsg); } else { ret = sieve_eval_bc(exe, 0, interp, script_context, message_context, &flagvars, actions, notify_list, &errmsg, &workingvars); if (ret < 0) { ret = do_sieve_error(SIEVE_RUN_ERROR, interp, script_context, message_context, &imapflags, actions, notify_list, lastaction, 0, actions_string, errmsg); } else { ret = do_action_list(interp, script_context, message_context, &imapflags, actions, notify_list, actions_string, errmsg); } } varlist_fini(&flagvars); varlist_fini(&workingvars); return ret; } cyrus-imapd-2.5.10/sieve/message.c0000644000175000017500000003066313001236020013653 00000000000000/* message.c -- message parsing functions * Larry Greenfield * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #ifdef HAVE_CONFIG_H #include #endif #include #include #include "md5.h" #include "sieve_interface.h" #include "interp.h" #include "message.h" #include "xmalloc.h" #include "util.h" /* reject message m with message msg * * incompatible with: fileinto, redirect */ int do_reject(action_list_t *a, const char *msg) { action_list_t *b = NULL; /* see if this conflicts with any previous actions taken on this message */ while (a != NULL) { b = a; if (a->a == ACTION_FILEINTO || a->a == ACTION_KEEP || a->a == ACTION_REDIRECT || a->a == ACTION_REJECT || a->a == ACTION_VACATION || a->a == ACTION_SETFLAG || a->a == ACTION_ADDFLAG || a->a == ACTION_REMOVEFLAG || a->a == ACTION_MARK || a->a == ACTION_UNMARK ) return SIEVE_RUN_ERROR; a = a->next; } /* add to the action list */ a = (action_list_t *) xmalloc(sizeof(action_list_t)); if (a == NULL) return SIEVE_NOMEM; a->a = ACTION_REJECT; a->cancel_keep = 1; a->u.rej.msg = msg; b->next = a; a->next = NULL; return 0; } /* fileinto message m into mailbox * * incompatible with: reject */ int do_fileinto(action_list_t *a, const char *mbox, int cancel_keep, strarray_t *imapflags) { action_list_t *b = NULL; /* see if this conflicts with any previous actions taken on this message */ while (a != NULL) { if (a->a == ACTION_REJECT) return SIEVE_RUN_ERROR; if (a->a == ACTION_FILEINTO && !strcmp(a->u.fil.mailbox, mbox)) { /* don't bother doing it twice */ /* check that we have a valid action */ if (b == NULL) { return SIEVE_INTERNAL_ERROR; } /* cut this action out of the list */ b->next = a->next; a->next = NULL; /* find the end of the list */ while (b->next != NULL) { b = b-> next; } /* add the action to the end of the list */ b->next = a; break; } b = a; a = a->next; } if (a == NULL) { /* add to the action list */ a = new_action_list(); if (a == NULL) return SIEVE_NOMEM; b->next = a; } a->a = ACTION_FILEINTO; a->cancel_keep |= cancel_keep; a->u.fil.mailbox = mbox; a->u.fil.imapflags = imapflags; return 0; } /* redirect message m to to addr * * incompatible with: reject */ int do_redirect(action_list_t *a, const char *addr, int cancel_keep) { action_list_t *b = NULL; /* xxx we should validate addr */ /* see if this conflicts with any previous actions taken on this message */ while (a != NULL) { b = a; if (a->a == ACTION_REJECT) return SIEVE_RUN_ERROR; a = a->next; } /* add to the action list */ a = (action_list_t *) xmalloc(sizeof(action_list_t)); if (a == NULL) return SIEVE_NOMEM; a->a = ACTION_REDIRECT; a->cancel_keep = cancel_keep; a->u.red.addr = addr; a->next = NULL; b->next = a; return 0; } /* keep message * * incompatible with: reject */ int do_keep(action_list_t *a, int cancel_keep, strarray_t *imapflags) { action_list_t *b = NULL; /* see if this conflicts with any previous actions taken on this message */ while (a != NULL) { if (a->a == ACTION_REJECT) return SIEVE_RUN_ERROR; if (a->a == ACTION_KEEP) { /* don't bother doing it twice */ /* check that we have a valid action */ if (b == NULL) { return SIEVE_INTERNAL_ERROR; } /* cut this action out of the list */ b->next = a->next; a->next = NULL; /* find the end of the list */ while (b->next != NULL) { b = b-> next; } /* add the action to the end of the list */ b->next = a; break; } b = a; a = a->next; } if(a == NULL) { /* add to the action list */ a = new_action_list(); if (a == NULL) return SIEVE_NOMEM; a->next = NULL; b->next = a; } a->a = ACTION_KEEP; a->cancel_keep |= cancel_keep; a->u.keep.imapflags = imapflags; return 0; } /* discard message m * * incompatible with: nothing---it doesn't cancel any actions */ int do_discard(action_list_t *a) { action_list_t *b = NULL; /* see if this conflicts with any previous actions taken on this message */ while (a != NULL) { b = a; if (a->a == ACTION_DISCARD) /* don't bother doing twice */ return 0; a = a->next; } /* add to the action list */ a = (action_list_t *) xmalloc(sizeof(action_list_t)); if (a == NULL) return SIEVE_NOMEM; a->a = ACTION_DISCARD; a->cancel_keep = 1; a->next = NULL; b->next = a; return 0; } static int makehash(unsigned char hash[], const char *s1, const char *s2, const char *s3) { MD5_CTX ctx; MD5Init(&ctx); MD5Update(&ctx, s1, strlen(s1)); MD5Update(&ctx, s2, strlen(s2)); if (s3) MD5Update(&ctx, s3, strlen(s3)); MD5Final(hash, &ctx); return SIEVE_OK; } int do_vacation(action_list_t *a, char *addr, char *fromaddr, char *subj, const char *msg, int seconds, int mime, const char *handle) { action_list_t *b = NULL; /* see if this conflicts with any previous actions taken on this message */ while (a != NULL) { b = a; if (a->a == ACTION_REJECT || a->a == ACTION_VACATION) /* vacation can't be used twice */ return SIEVE_RUN_ERROR; a = a->next; } /* add to the action list */ a = (action_list_t *) xmalloc(sizeof(action_list_t)); if (a == NULL) return SIEVE_NOMEM; a->a = ACTION_VACATION; a->cancel_keep = 0; a->u.vac.send.addr = addr; a->u.vac.send.fromaddr = fromaddr; a->u.vac.send.subj = subj; /* user specified subject */ a->u.vac.send.msg = msg; a->u.vac.send.mime = mime; if (handle) makehash(a->u.vac.autoresp.hash, addr, handle, NULL); else makehash(a->u.vac.autoresp.hash, addr, fromaddr, msg); a->u.vac.autoresp.seconds = seconds; a->next = NULL; b->next = a; return 0; } /* setflag f on message m * * incompatible with: reject */ int do_setflag(action_list_t *a) { action_list_t *b = NULL; /* see if this conflicts with any previous actions taken on this message */ while (a != NULL) { b = a; if (a->a == ACTION_REJECT) return SIEVE_RUN_ERROR; a = a->next; } /* add to the action list */ a = (action_list_t *) xmalloc(sizeof(action_list_t)); if (a == NULL) return SIEVE_NOMEM; a->a = ACTION_SETFLAG; a->cancel_keep = 0; b->next = a; a->next = NULL; return 0; } /* addflag f on message m * * incompatible with: reject */ int do_addflag(action_list_t *a, const char *flag) { action_list_t *b = NULL; /* see if this conflicts with any previous actions taken on this message */ while (a != NULL) { b = a; if (a->a == ACTION_REJECT) return SIEVE_RUN_ERROR; a = a->next; } /* add to the action list */ a = (action_list_t *) xmalloc(sizeof(action_list_t)); if (a == NULL) return SIEVE_NOMEM; a->a = ACTION_ADDFLAG; a->cancel_keep = 0; a->u.fla.flag = flag; b->next = a; a->next = NULL; return 0; } /* removeflag f on message m * * incompatible with: reject */ int do_removeflag(action_list_t *a, const char *flag) { action_list_t *b = NULL; /* see if this conflicts with any previous actions taken on this message */ while (a != NULL) { b = a; if (a->a == ACTION_REJECT) return SIEVE_RUN_ERROR; a = a->next; } /* add to the action list */ a = (action_list_t *) xmalloc(sizeof(action_list_t)); if (a == NULL) return SIEVE_NOMEM; a->a = ACTION_REMOVEFLAG; a->cancel_keep = 0; a->u.fla.flag = flag; b->next = a; a->next = NULL; return 0; } /* mark message m * * incompatible with: reject */ int do_mark(action_list_t *a) { action_list_t *b = NULL; /* see if this conflicts with any previous actions taken on this message */ while (a != NULL) { b = a; if (a->a == ACTION_REJECT) return SIEVE_RUN_ERROR; a = a->next; } /* add to the action list */ a = (action_list_t *) xmalloc(sizeof(action_list_t)); if (a == NULL) return SIEVE_NOMEM; a->a = ACTION_MARK; a->cancel_keep = 0; b->next = a; a->next = NULL; return 0; } /* unmark message m * * incompatible with: reject */ int do_unmark(action_list_t *a) { action_list_t *b = NULL; /* see if this conflicts with any previous actions taken on this message */ while (a != NULL) { b = a; if (a->a == ACTION_REJECT) return SIEVE_RUN_ERROR; a = a->next; } /* add to the action list */ a = (action_list_t *) xmalloc(sizeof(action_list_t)); if (a == NULL) return SIEVE_NOMEM; a->a = ACTION_UNMARK; a->cancel_keep = 0; b->next = a; a->next = NULL; return 0; } /* notify * * incompatible with: none */ int do_notify(notify_list_t *a, const char *id, const char *method, const char **options, const char *priority, const char *message) { notify_list_t *b = NULL; /* find the end of the notify list */ while (a != NULL) { b = a; a = a->next; } /* add to the notify list */ a = (notify_list_t *) xmalloc(sizeof(notify_list_t)); if (a == NULL) return SIEVE_NOMEM; b->next = a; a->isactive = 1; a->id = id; a->method = method; a->options = options; a->priority = priority; a->message = message; a->next = NULL; return 0; } /* denotify * * incomaptible with: none */ int do_denotify(notify_list_t *n, comparator_t *comp, const void *pat, void *comprock, const char *priority) { while (n != NULL) { if (n->isactive && (!priority || !strcasecmp(n->priority, priority)) && (!comp || (n->id && comp(n->id, strlen(n->id), pat, comprock)))) { n->isactive = 0; } n = n->next; } return 0; } notify_list_t *new_notify_list(void) { notify_list_t *ret = xmalloc(sizeof(notify_list_t)); if (ret != NULL) { ret->isactive = 0; ret->id = NULL; ret->method = NULL; ret->options = NULL; ret->priority = NULL; ret->message = NULL; ret->next = NULL; } return ret; } void free_notify_list(notify_list_t *n) { while (n) { notify_list_t *b = n->next; free(n->options); /* strings live in bytecode, only free the array */ free(n); n = b; } } action_list_t *new_action_list(void) { action_list_t *ret = xmalloc(sizeof(action_list_t)); if (ret != NULL) { ret->a = ACTION_NONE; ret->param = NULL; ret->next = NULL; ret->cancel_keep = 0; } return ret; } void free_action_list(action_list_t *a) { while (a) { action_list_t *b = a->next; if(a->a == ACTION_VACATION) { if(a->u.vac.send.subj) free(a->u.vac.send.subj); if(a->u.vac.send.addr) free(a->u.vac.send.addr); if(a->u.vac.send.fromaddr) free(a->u.vac.send.fromaddr); } free(a); a = b; } } cyrus-imapd-2.5.10/sieve/interp.h0000644000175000017500000000523013001236020013525 00000000000000/* interp.h -- interpretor definition * Larry Greenfield * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #ifndef SIEVE_INTERP_H #define SIEVE_INTERP_H #include "sieve_interface.h" struct sieve_interp { /* standard callbacks for actions */ sieve_callback *redirect, *discard, *reject, *fileinto, *keep; sieve_callback *notify; sieve_vacation_t *vacation; sieve_get_size *getsize; sieve_get_header *getheader; sieve_get_envelope *getenvelope; sieve_get_body *getbody; sieve_get_include *getinclude; sieve_parse_error *err; /* site-specific imapflags for mark/unmark */ const strarray_t *markflags; sieve_execute_error *execute_err; char *lastitem; /* context to pass along */ void *interp_context; char extensions[4096];//the number comes from interp.c EXT_LEN /* time when allocated */ time_t time; }; int interp_verify(sieve_interp_t *interp); #endif cyrus-imapd-2.5.10/sieve/addr-lex.c0000644000175000017500000014426113001246643013743 00000000000000#line 2 "sieve/addr-lex.c" #line 4 "sieve/addr-lex.c" #define YY_INT_ALIGNED short int /* A lexical scanner generated by flex */ #define yy_create_buffer addr_create_buffer #define yy_delete_buffer addr_delete_buffer #define yy_flex_debug addr_flex_debug #define yy_init_buffer addr_init_buffer #define yy_flush_buffer addr_flush_buffer #define yy_load_buffer_state addr_load_buffer_state #define yy_switch_to_buffer addr_switch_to_buffer #define yyin addrin #define yyleng addrleng #define yylex addrlex #define yylineno addrlineno #define yyout addrout #define yyrestart addrrestart #define yytext addrtext #define yywrap addrwrap #define yyalloc addralloc #define yyrealloc addrrealloc #define yyfree addrfree #define FLEX_SCANNER #define YY_FLEX_MAJOR_VERSION 2 #define YY_FLEX_MINOR_VERSION 6 #define YY_FLEX_SUBMINOR_VERSION 1 #if YY_FLEX_SUBMINOR_VERSION > 0 #define FLEX_BETA #endif /* First, we deal with platform-specific or compiler-specific issues. */ /* begin standard C headers. */ #include #include #include #include /* end standard C headers. */ /* flex integer type definitions */ #ifndef FLEXINT_H #define FLEXINT_H /* C99 systems have . Non-C99 systems may or may not. */ #if defined (__STDC_VERSION__) && __STDC_VERSION__ >= 199901L /* C99 says to define __STDC_LIMIT_MACROS before including stdint.h, * if you want the limit (max/min) macros for int types. */ #ifndef __STDC_LIMIT_MACROS #define __STDC_LIMIT_MACROS 1 #endif #include typedef int8_t flex_int8_t; typedef uint8_t flex_uint8_t; typedef int16_t flex_int16_t; typedef uint16_t flex_uint16_t; typedef int32_t flex_int32_t; typedef uint32_t flex_uint32_t; #else typedef signed char flex_int8_t; typedef short int flex_int16_t; typedef int flex_int32_t; typedef unsigned char flex_uint8_t; typedef unsigned short int flex_uint16_t; typedef unsigned int flex_uint32_t; /* Limits of integral types. */ #ifndef INT8_MIN #define INT8_MIN (-128) #endif #ifndef INT16_MIN #define INT16_MIN (-32767-1) #endif #ifndef INT32_MIN #define INT32_MIN (-2147483647-1) #endif #ifndef INT8_MAX #define INT8_MAX (127) #endif #ifndef INT16_MAX #define INT16_MAX (32767) #endif #ifndef INT32_MAX #define INT32_MAX (2147483647) #endif #ifndef UINT8_MAX #define UINT8_MAX (255U) #endif #ifndef UINT16_MAX #define UINT16_MAX (65535U) #endif #ifndef UINT32_MAX #define UINT32_MAX (4294967295U) #endif #endif /* ! C99 */ #endif /* ! FLEXINT_H */ /* TODO: this is always defined, so inline it */ #define yyconst const #if defined(__GNUC__) && __GNUC__ >= 3 #define yynoreturn __attribute__((__noreturn__)) #else #define yynoreturn #endif /* Returned upon end-of-file. */ #define YY_NULL 0 /* Promotes a possibly negative, possibly signed char to an unsigned * integer for use as an array index. If the signed char is negative, * we want to instead treat it as an 8-bit unsigned char, hence the * double cast. */ #define YY_SC_TO_UI(c) ((unsigned int) (unsigned char) c) /* Enter a start condition. This macro really ought to take a parameter, * but we do it the disgusting crufty way forced on us by the ()-less * definition of BEGIN. */ #define BEGIN (yy_start) = 1 + 2 * /* Translate the current start state into a value that can be later handed * to BEGIN to return to the state. The YYSTATE alias is for lex * compatibility. */ #define YY_START (((yy_start) - 1) / 2) #define YYSTATE YY_START /* Action number for EOF rule of a given start state. */ #define YY_STATE_EOF(state) (YY_END_OF_BUFFER + state + 1) /* Special action meaning "start processing a new file". */ #define YY_NEW_FILE addrrestart(addrin ) #define YY_END_OF_BUFFER_CHAR 0 /* Size of default input buffer. */ #ifndef YY_BUF_SIZE #ifdef __ia64__ /* On IA-64, the buffer size is 16k, not 8k. * Moreover, YY_BUF_SIZE is 2*YY_READ_BUF_SIZE in the general case. * Ditto for the __ia64__ case accordingly. */ #define YY_BUF_SIZE 32768 #else #define YY_BUF_SIZE 16384 #endif /* __ia64__ */ #endif /* The state buf must be large enough to hold one state per character in the main buffer. */ #define YY_STATE_BUF_SIZE ((YY_BUF_SIZE + 2) * sizeof(yy_state_type)) #ifndef YY_TYPEDEF_YY_BUFFER_STATE #define YY_TYPEDEF_YY_BUFFER_STATE typedef struct yy_buffer_state *YY_BUFFER_STATE; #endif #ifndef YY_TYPEDEF_YY_SIZE_T #define YY_TYPEDEF_YY_SIZE_T typedef size_t yy_size_t; #endif extern int addrleng; extern FILE *addrin, *addrout; #define EOB_ACT_CONTINUE_SCAN 0 #define EOB_ACT_END_OF_FILE 1 #define EOB_ACT_LAST_MATCH 2 #define YY_LESS_LINENO(n) #define YY_LINENO_REWIND_TO(ptr) /* Return all but the first "n" matched characters back to the input stream. */ #define yyless(n) \ do \ { \ /* Undo effects of setting up addrtext. */ \ int yyless_macro_arg = (n); \ YY_LESS_LINENO(yyless_macro_arg);\ *yy_cp = (yy_hold_char); \ YY_RESTORE_YY_MORE_OFFSET \ (yy_c_buf_p) = yy_cp = yy_bp + yyless_macro_arg - YY_MORE_ADJ; \ YY_DO_BEFORE_ACTION; /* set up addrtext again */ \ } \ while ( 0 ) #define unput(c) yyunput( c, (yytext_ptr) ) #ifndef YY_STRUCT_YY_BUFFER_STATE #define YY_STRUCT_YY_BUFFER_STATE struct yy_buffer_state { FILE *yy_input_file; char *yy_ch_buf; /* input buffer */ char *yy_buf_pos; /* current position in input buffer */ /* Size of input buffer in bytes, not including room for EOB * characters. */ int yy_buf_size; /* Number of characters read into yy_ch_buf, not including EOB * characters. */ int yy_n_chars; /* Whether we "own" the buffer - i.e., we know we created it, * and can realloc() it to grow it, and should free() it to * delete it. */ int yy_is_our_buffer; /* Whether this is an "interactive" input source; if so, and * if we're using stdio for input, then we want to use getc() * instead of fread(), to make sure we stop fetching input after * each newline. */ int yy_is_interactive; /* Whether we're considered to be at the beginning of a line. * If so, '^' rules will be active on the next match, otherwise * not. */ int yy_at_bol; int yy_bs_lineno; /**< The line count. */ int yy_bs_column; /**< The column count. */ /* Whether to try to fill the input buffer when we reach the * end of it. */ int yy_fill_buffer; int yy_buffer_status; #define YY_BUFFER_NEW 0 #define YY_BUFFER_NORMAL 1 /* When an EOF's been seen but there's still some text to process * then we mark the buffer as YY_EOF_PENDING, to indicate that we * shouldn't try reading from the input source any more. We might * still have a bunch of tokens to match, though, because of * possible backing-up. * * When we actually see the EOF, we change the status to "new" * (via addrrestart()), so that the user can continue scanning by * just pointing addrin at a new input file. */ #define YY_BUFFER_EOF_PENDING 2 }; #endif /* !YY_STRUCT_YY_BUFFER_STATE */ /* Stack of input buffers. */ static size_t yy_buffer_stack_top = 0; /**< index of top of stack. */ static size_t yy_buffer_stack_max = 0; /**< capacity of stack. */ static YY_BUFFER_STATE * yy_buffer_stack = NULL; /**< Stack as an array. */ /* We provide macros for accessing buffer states in case in the * future we want to put the buffer states in a more general * "scanner state". * * Returns the top of the stack, or NULL. */ #define YY_CURRENT_BUFFER ( (yy_buffer_stack) \ ? (yy_buffer_stack)[(yy_buffer_stack_top)] \ : NULL) /* Same as previous macro, but useful when we know that the buffer stack is not * NULL or when we need an lvalue. For internal use only. */ #define YY_CURRENT_BUFFER_LVALUE (yy_buffer_stack)[(yy_buffer_stack_top)] /* yy_hold_char holds the character lost when addrtext is formed. */ static char yy_hold_char; static int yy_n_chars; /* number of characters read into yy_ch_buf */ int addrleng; /* Points to current character in buffer. */ static char *yy_c_buf_p = NULL; static int yy_init = 0; /* whether we need to initialize */ static int yy_start = 0; /* start state number */ /* Flag which is used to allow addrwrap()'s to do buffer switches * instead of setting up a fresh addrin. A bit of a hack ... */ static int yy_did_buffer_switch_on_eof; void addrrestart (FILE *input_file ); void addr_switch_to_buffer (YY_BUFFER_STATE new_buffer ); YY_BUFFER_STATE addr_create_buffer (FILE *file,int size ); void addr_delete_buffer (YY_BUFFER_STATE b ); void addr_flush_buffer (YY_BUFFER_STATE b ); void addrpush_buffer_state (YY_BUFFER_STATE new_buffer ); void addrpop_buffer_state (void ); static void addrensure_buffer_stack (void ); static void addr_load_buffer_state (void ); static void addr_init_buffer (YY_BUFFER_STATE b,FILE *file ); #define YY_FLUSH_BUFFER addr_flush_buffer(YY_CURRENT_BUFFER ) YY_BUFFER_STATE addr_scan_buffer (char *base,yy_size_t size ); YY_BUFFER_STATE addr_scan_string (yyconst char *yy_str ); YY_BUFFER_STATE addr_scan_bytes (yyconst char *bytes,int len ); void *addralloc (yy_size_t ); void *addrrealloc (void *,yy_size_t ); void addrfree (void * ); #define yy_new_buffer addr_create_buffer #define yy_set_interactive(is_interactive) \ { \ if ( ! YY_CURRENT_BUFFER ){ \ addrensure_buffer_stack (); \ YY_CURRENT_BUFFER_LVALUE = \ addr_create_buffer(addrin,YY_BUF_SIZE ); \ } \ YY_CURRENT_BUFFER_LVALUE->yy_is_interactive = is_interactive; \ } #define yy_set_bol(at_bol) \ { \ if ( ! YY_CURRENT_BUFFER ){\ addrensure_buffer_stack (); \ YY_CURRENT_BUFFER_LVALUE = \ addr_create_buffer(addrin,YY_BUF_SIZE ); \ } \ YY_CURRENT_BUFFER_LVALUE->yy_at_bol = at_bol; \ } #define YY_AT_BOL() (YY_CURRENT_BUFFER_LVALUE->yy_at_bol) /* Begin user sect3 */ #define addrwrap() (/*CONSTCOND*/1) #define YY_SKIP_YYWRAP typedef unsigned char YY_CHAR; FILE *addrin = NULL, *addrout = NULL; typedef int yy_state_type; extern int addrlineno; int addrlineno = 1; extern char *addrtext; #ifdef yytext_ptr #undef yytext_ptr #endif #define yytext_ptr addrtext static yy_state_type yy_get_previous_state (void ); static yy_state_type yy_try_NUL_trans (yy_state_type current_state ); static int yy_get_next_buffer (void ); static void yynoreturn yy_fatal_error (yyconst char* msg ); /* Done after the current pattern has been matched and before the * corresponding action - sets up addrtext. */ #define YY_DO_BEFORE_ACTION \ (yytext_ptr) = yy_bp; \ addrleng = (int) (yy_cp - yy_bp); \ (yy_hold_char) = *yy_cp; \ *yy_cp = '\0'; \ (yy_c_buf_p) = yy_cp; #define YY_NUM_RULES 15 #define YY_END_OF_BUFFER 16 /* This struct is not used in this scanner, but its presence is necessary. */ struct yy_trans_info { flex_int32_t yy_verify; flex_int32_t yy_nxt; }; static yyconst flex_int16_t yy_accept[40] = { 0, 0, 0, 8, 8, 10, 10, 12, 12, 16, 5, 5, 6, 6, 1, 3, 4, 7, 2, 8, 15, 9, 15, 10, 15, 11, 12, 13, 14, 15, 5, 5, 6, 8, 0, 10, 0, 12, 0, 0 } ; static yyconst YY_CHAR yy_ec[256] = { 0, 1, 1, 1, 1, 1, 1, 1, 1, 2, 3, 1, 1, 4, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 5, 1, 6, 1, 1, 1, 1, 1, 7, 8, 1, 1, 9, 1, 9, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 9, 9, 9, 1, 9, 1, 9, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 10, 11, 12, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1 } ; static yyconst YY_CHAR yy_meta[14] = { 0, 1, 2, 3, 4, 5, 6, 7, 7, 8, 9, 8, 9, 10 } ; static yyconst flex_uint16_t yy_base[48] = { 0, 0, 0, 11, 20, 29, 39, 49, 60, 27, 0, 73, 0, 0, 182, 182, 182, 182, 182, 14, 182, 182, 83, 10, 86, 182, 9, 182, 182, 92, 0, 0, 0, 8, 102, 7, 0, 5, 0, 182, 108, 118, 128, 138, 147, 152, 162, 172 } ; static yyconst flex_int16_t yy_def[48] = { 0, 39, 1, 40, 40, 41, 41, 42, 42, 39, 43, 39, 44, 44, 39, 39, 39, 39, 39, 45, 39, 39, 45, 46, 46, 39, 47, 39, 39, 47, 43, 11, 44, 45, 45, 46, 24, 47, 29, 0, 39, 39, 39, 39, 39, 39, 39, 39 } ; static yyconst flex_uint16_t yy_nxt[196] = { 0, 10, 11, 12, 13, 13, 14, 15, 16, 17, 18, 17, 17, 10, 20, 20, 38, 21, 36, 34, 38, 36, 22, 20, 20, 34, 21, 39, 39, 39, 39, 22, 20, 20, 39, 39, 39, 39, 39, 20, 24, 25, 20, 20, 39, 39, 39, 39, 39, 20, 24, 25, 20, 39, 39, 39, 27, 28, 39, 39, 29, 39, 20, 20, 39, 39, 39, 27, 28, 39, 39, 29, 39, 20, 30, 31, 32, 32, 32, 39, 39, 39, 39, 39, 39, 39, 30, 33, 39, 33, 35, 39, 39, 39, 39, 39, 35, 39, 35, 37, 37, 39, 39, 39, 39, 37, 33, 39, 33, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 23, 23, 23, 23, 23, 23, 23, 23, 23, 23, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 30, 30, 39, 39, 39, 39, 39, 39, 39, 30, 32, 32, 32, 32, 33, 33, 39, 39, 33, 39, 33, 33, 33, 33, 35, 35, 39, 39, 35, 35, 35, 35, 39, 35, 37, 37, 39, 37, 37, 37, 39, 37, 37, 9, 39, 39, 39, 39, 39, 39, 39, 39, 39, 39, 39, 39, 39 } ; static yyconst flex_int16_t yy_chk[196] = { 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 3, 3, 37, 3, 35, 33, 26, 23, 3, 4, 4, 19, 4, 9, 0, 0, 0, 4, 5, 5, 0, 0, 0, 0, 0, 5, 5, 5, 6, 6, 0, 0, 0, 0, 0, 6, 6, 6, 7, 0, 0, 0, 7, 7, 0, 0, 7, 0, 7, 8, 0, 0, 0, 8, 8, 0, 0, 8, 0, 8, 11, 11, 11, 11, 11, 0, 0, 0, 0, 0, 0, 0, 11, 22, 0, 22, 24, 0, 0, 0, 0, 0, 24, 0, 24, 29, 29, 0, 0, 0, 0, 29, 34, 0, 34, 40, 40, 40, 40, 40, 40, 40, 40, 40, 40, 41, 41, 41, 41, 41, 41, 41, 41, 41, 41, 42, 42, 42, 42, 42, 42, 42, 42, 42, 42, 43, 43, 0, 0, 0, 0, 0, 0, 0, 43, 44, 44, 44, 44, 45, 45, 0, 0, 45, 0, 45, 45, 45, 45, 46, 46, 0, 0, 46, 46, 46, 46, 0, 46, 47, 47, 0, 47, 47, 47, 0, 47, 47, 39, 39, 39, 39, 39, 39, 39, 39, 39, 39, 39, 39, 39, 39 } ; static yy_state_type yy_last_accepting_state; static char *yy_last_accepting_cpos; extern int addr_flex_debug; int addr_flex_debug = 0; /* The intent behind this definition is that it'll catch * any uses of REJECT which flex missed. */ #define REJECT reject_used_but_not_detected #define yymore() yymore_used_but_not_detected #define YY_MORE_ADJ 0 #define YY_RESTORE_YY_MORE_OFFSET char *addrtext; #line 1 "sieve/addr-lex.l" #line 2 "sieve/addr-lex.l" /* * addr-lex.l -- RFC 822 address lexer * Ken Murchison * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include "sieve/sieve_interface.h" #include "sieve/addr.h" void addrerror(void*, const char *); static int ncom; /* number of open comments */ #define YY_DECL int addrlex(YYSTYPE* addrlval __attribute__((unused)), void* parse_script) #define YY_NO_INPUT 1 #line 581 "sieve/addr-lex.c" #define INITIAL 0 #define QSTRING 1 #define DOMAINLIT 2 #define COMMENT 3 #ifndef YY_NO_UNISTD_H /* Special case for "unistd.h", since it is non-ANSI. We include it way * down here because we want the user's section 1 to have been scanned first. * The user has a chance to override it with an option. */ #include #endif #ifndef YY_EXTRA_TYPE #define YY_EXTRA_TYPE void * #endif static int yy_init_globals (void ); /* Accessor methods to globals. These are made visible to non-reentrant scanners for convenience. */ int addrlex_destroy (void ); int addrget_debug (void ); void addrset_debug (int debug_flag ); YY_EXTRA_TYPE addrget_extra (void ); void addrset_extra (YY_EXTRA_TYPE user_defined ); FILE *addrget_in (void ); void addrset_in (FILE * _in_str ); FILE *addrget_out (void ); void addrset_out (FILE * _out_str ); int addrget_leng (void ); char *addrget_text (void ); int addrget_lineno (void ); void addrset_lineno (int _line_number ); /* Macros after this point can all be overridden by user definitions in * section 1. */ #ifndef YY_SKIP_YYWRAP #ifdef __cplusplus extern "C" int addrwrap (void ); #else extern int addrwrap (void ); #endif #endif #ifndef YY_NO_UNPUT #endif #ifndef yytext_ptr static void yy_flex_strncpy (char *,yyconst char *,int ); #endif #ifdef YY_NEED_STRLEN static int yy_flex_strlen (yyconst char * ); #endif #ifndef YY_NO_INPUT #ifdef __cplusplus static int yyinput (void ); #else static int input (void ); #endif #endif /* Amount of stuff to slurp up with each read. */ #ifndef YY_READ_BUF_SIZE #ifdef __ia64__ /* On IA-64, the buffer size is 16k, not 8k */ #define YY_READ_BUF_SIZE 16384 #else #define YY_READ_BUF_SIZE 8192 #endif /* __ia64__ */ #endif /* Copy whatever the last rule matched to the standard output. */ #ifndef ECHO /* This used to be an fputs(), but since the string might contain NUL's, * we now use fwrite(). */ #define ECHO do { if (fwrite( addrtext, (size_t) addrleng, 1, addrout )) {} } while (0) #endif /* Gets input and stuffs it into "buf". number of characters read, or YY_NULL, * is returned in "result". */ #ifndef YY_INPUT #define YY_INPUT(buf,result,max_size) \ if ( YY_CURRENT_BUFFER_LVALUE->yy_is_interactive ) \ { \ int c = '*'; \ size_t n; \ for ( n = 0; n < max_size && \ (c = getc( addrin )) != EOF && c != '\n'; ++n ) \ buf[n] = (char) c; \ if ( c == '\n' ) \ buf[n++] = (char) c; \ if ( c == EOF && ferror( addrin ) ) \ YY_FATAL_ERROR( "input in flex scanner failed" ); \ result = n; \ } \ else \ { \ errno=0; \ while ( (result = (int) fread(buf, 1, max_size, addrin))==0 && ferror(addrin)) \ { \ if( errno != EINTR) \ { \ YY_FATAL_ERROR( "input in flex scanner failed" ); \ break; \ } \ errno=0; \ clearerr(addrin); \ } \ }\ \ #endif /* No semi-colon after return; correct usage is to write "yyterminate();" - * we don't want an extra ';' after the "return" because that will cause * some compilers to complain about unreachable statements. */ #ifndef yyterminate #define yyterminate() return YY_NULL #endif /* Number of entries by which start-condition stack grows. */ #ifndef YY_START_STACK_INCR #define YY_START_STACK_INCR 25 #endif /* Report a fatal error. */ #ifndef YY_FATAL_ERROR #define YY_FATAL_ERROR(msg) yy_fatal_error( msg ) #endif /* end tables serialization structures and prototypes */ /* Default declaration of generated scanner - a define so the user can * easily add parameters. */ #ifndef YY_DECL #define YY_DECL_IS_OURS 1 extern int addrlex (void); #define YY_DECL int addrlex (void) #endif /* !YY_DECL */ /* Code executed at the beginning of each rule, after addrtext and addrleng * have been set up. */ #ifndef YY_USER_ACTION #define YY_USER_ACTION #endif /* Code executed at the end of each rule. */ #ifndef YY_BREAK #define YY_BREAK /*LINTED*/break; #endif #define YY_RULE_SETUP \ YY_USER_ACTION /** The main scanner function which does all the work. */ YY_DECL { yy_state_type yy_current_state; char *yy_cp, *yy_bp; int yy_act; if ( !(yy_init) ) { (yy_init) = 1; #ifdef YY_USER_INIT YY_USER_INIT; #endif if ( ! (yy_start) ) (yy_start) = 1; /* first start state */ if ( ! addrin ) addrin = stdin; if ( ! addrout ) addrout = stdout; if ( ! YY_CURRENT_BUFFER ) { addrensure_buffer_stack (); YY_CURRENT_BUFFER_LVALUE = addr_create_buffer(addrin,YY_BUF_SIZE ); } addr_load_buffer_state( ); } { #line 62 "sieve/addr-lex.l" #line 803 "sieve/addr-lex.c" while ( /*CONSTCOND*/1 ) /* loops until end-of-file is reached */ { yy_cp = (yy_c_buf_p); /* Support of addrtext. */ *yy_cp = (yy_hold_char); /* yy_bp points to the position in yy_ch_buf of the start of * the current run. */ yy_bp = yy_cp; yy_current_state = (yy_start); yy_match: do { YY_CHAR yy_c = yy_ec[YY_SC_TO_UI(*yy_cp)] ; if ( yy_accept[yy_current_state] ) { (yy_last_accepting_state) = yy_current_state; (yy_last_accepting_cpos) = yy_cp; } while ( yy_chk[yy_base[yy_current_state] + yy_c] != yy_current_state ) { yy_current_state = (int) yy_def[yy_current_state]; if ( yy_current_state >= 40 ) yy_c = yy_meta[(unsigned int) yy_c]; } yy_current_state = yy_nxt[yy_base[yy_current_state] + (flex_int16_t) yy_c]; ++yy_cp; } while ( yy_base[yy_current_state] != 182 ); yy_find_action: yy_act = yy_accept[yy_current_state]; if ( yy_act == 0 ) { /* have to back up */ yy_cp = (yy_last_accepting_cpos); yy_current_state = (yy_last_accepting_state); yy_act = yy_accept[yy_current_state]; } YY_DO_BEFORE_ACTION; do_action: /* This label is used only to access EOF actions. */ switch ( yy_act ) { /* beginning of action switch */ case 0: /* must back up */ /* undo the effects of YY_DO_BEFORE_ACTION */ *yy_cp = (yy_hold_char); yy_cp = (yy_last_accepting_cpos); yy_current_state = (yy_last_accepting_state); goto yy_find_action; case 1: YY_RULE_SETUP #line 64 "sieve/addr-lex.l" { BEGIN QSTRING; return addrtext[0]; } YY_BREAK case 2: YY_RULE_SETUP #line 65 "sieve/addr-lex.l" { BEGIN DOMAINLIT; return addrtext[0]; } YY_BREAK case 3: YY_RULE_SETUP #line 66 "sieve/addr-lex.l" { ncom = 1; BEGIN COMMENT; } YY_BREAK case 4: YY_RULE_SETUP #line 67 "sieve/addr-lex.l" { addrerror(parse_script, "address parse error, " "unexpected `')'' " "(unbalanced comment)"); yyterminate(); } YY_BREAK case 5: YY_RULE_SETUP #line 72 "sieve/addr-lex.l" return ATOM; YY_BREAK case 6: /* rule 6 can match eol */ YY_RULE_SETUP #line 74 "sieve/addr-lex.l" /* ignore whitespace */ YY_BREAK case 7: YY_RULE_SETUP #line 75 "sieve/addr-lex.l" return addrtext[0]; YY_BREAK case 8: YY_RULE_SETUP #line 77 "sieve/addr-lex.l" return QTEXT; YY_BREAK case 9: YY_RULE_SETUP #line 78 "sieve/addr-lex.l" { BEGIN INITIAL; return addrtext[0]; } YY_BREAK case YY_STATE_EOF(QSTRING): #line 79 "sieve/addr-lex.l" { BEGIN INITIAL; addrerror(parse_script, "address parse error, expecting `'\"'' (unterminated string)"); yyterminate(); } YY_BREAK case 10: YY_RULE_SETUP #line 83 "sieve/addr-lex.l" return DTEXT; YY_BREAK case 11: YY_RULE_SETUP #line 84 "sieve/addr-lex.l" { BEGIN INITIAL; return addrtext[0]; } YY_BREAK case YY_STATE_EOF(DOMAINLIT): #line 85 "sieve/addr-lex.l" { BEGIN INITIAL; addrerror(parse_script, "address parse error, expecting `']'' (unterminated domain literal)"); yyterminate(); } YY_BREAK case 12: YY_RULE_SETUP #line 91 "sieve/addr-lex.l" /* ignore comments */ YY_BREAK case 13: YY_RULE_SETUP #line 92 "sieve/addr-lex.l" ncom++; YY_BREAK case 14: YY_RULE_SETUP #line 93 "sieve/addr-lex.l" { ncom--; if (ncom == 0) BEGIN INITIAL; } YY_BREAK case YY_STATE_EOF(COMMENT): #line 94 "sieve/addr-lex.l" { BEGIN INITIAL; addrerror(parse_script, "address parse error, " "expecting `')'' " "(unterminated comment)"); yyterminate(); } YY_BREAK case 15: YY_RULE_SETUP #line 100 "sieve/addr-lex.l" ECHO; YY_BREAK #line 959 "sieve/addr-lex.c" case YY_STATE_EOF(INITIAL): yyterminate(); case YY_END_OF_BUFFER: { /* Amount of text matched not including the EOB char. */ int yy_amount_of_matched_text = (int) (yy_cp - (yytext_ptr)) - 1; /* Undo the effects of YY_DO_BEFORE_ACTION. */ *yy_cp = (yy_hold_char); YY_RESTORE_YY_MORE_OFFSET if ( YY_CURRENT_BUFFER_LVALUE->yy_buffer_status == YY_BUFFER_NEW ) { /* We're scanning a new file or input source. It's * possible that this happened because the user * just pointed addrin at a new source and called * addrlex(). If so, then we have to assure * consistency between YY_CURRENT_BUFFER and our * globals. Here is the right place to do so, because * this is the first action (other than possibly a * back-up) that will match for the new input source. */ (yy_n_chars) = YY_CURRENT_BUFFER_LVALUE->yy_n_chars; YY_CURRENT_BUFFER_LVALUE->yy_input_file = addrin; YY_CURRENT_BUFFER_LVALUE->yy_buffer_status = YY_BUFFER_NORMAL; } /* Note that here we test for yy_c_buf_p "<=" to the position * of the first EOB in the buffer, since yy_c_buf_p will * already have been incremented past the NUL character * (since all states make transitions on EOB to the * end-of-buffer state). Contrast this with the test * in input(). */ if ( (yy_c_buf_p) <= &YY_CURRENT_BUFFER_LVALUE->yy_ch_buf[(yy_n_chars)] ) { /* This was really a NUL. */ yy_state_type yy_next_state; (yy_c_buf_p) = (yytext_ptr) + yy_amount_of_matched_text; yy_current_state = yy_get_previous_state( ); /* Okay, we're now positioned to make the NUL * transition. We couldn't have * yy_get_previous_state() go ahead and do it * for us because it doesn't know how to deal * with the possibility of jamming (and we don't * want to build jamming into it because then it * will run more slowly). */ yy_next_state = yy_try_NUL_trans( yy_current_state ); yy_bp = (yytext_ptr) + YY_MORE_ADJ; if ( yy_next_state ) { /* Consume the NUL. */ yy_cp = ++(yy_c_buf_p); yy_current_state = yy_next_state; goto yy_match; } else { yy_cp = (yy_c_buf_p); goto yy_find_action; } } else switch ( yy_get_next_buffer( ) ) { case EOB_ACT_END_OF_FILE: { (yy_did_buffer_switch_on_eof) = 0; if ( addrwrap( ) ) { /* Note: because we've taken care in * yy_get_next_buffer() to have set up * addrtext, we can now set up * yy_c_buf_p so that if some total * hoser (like flex itself) wants to * call the scanner after we return the * YY_NULL, it'll still work - another * YY_NULL will get returned. */ (yy_c_buf_p) = (yytext_ptr) + YY_MORE_ADJ; yy_act = YY_STATE_EOF(YY_START); goto do_action; } else { if ( ! (yy_did_buffer_switch_on_eof) ) YY_NEW_FILE; } break; } case EOB_ACT_CONTINUE_SCAN: (yy_c_buf_p) = (yytext_ptr) + yy_amount_of_matched_text; yy_current_state = yy_get_previous_state( ); yy_cp = (yy_c_buf_p); yy_bp = (yytext_ptr) + YY_MORE_ADJ; goto yy_match; case EOB_ACT_LAST_MATCH: (yy_c_buf_p) = &YY_CURRENT_BUFFER_LVALUE->yy_ch_buf[(yy_n_chars)]; yy_current_state = yy_get_previous_state( ); yy_cp = (yy_c_buf_p); yy_bp = (yytext_ptr) + YY_MORE_ADJ; goto yy_find_action; } break; } default: YY_FATAL_ERROR( "fatal flex scanner internal error--no action found" ); } /* end of action switch */ } /* end of scanning one token */ } /* end of user's declarations */ } /* end of addrlex */ /* yy_get_next_buffer - try to read in a new buffer * * Returns a code representing an action: * EOB_ACT_LAST_MATCH - * EOB_ACT_CONTINUE_SCAN - continue scanning from current position * EOB_ACT_END_OF_FILE - end of file */ static int yy_get_next_buffer (void) { char *dest = YY_CURRENT_BUFFER_LVALUE->yy_ch_buf; char *source = (yytext_ptr); yy_size_t number_to_move, i; int ret_val; if ( (yy_c_buf_p) > &YY_CURRENT_BUFFER_LVALUE->yy_ch_buf[(yy_n_chars) + 1] ) YY_FATAL_ERROR( "fatal flex scanner internal error--end of buffer missed" ); if ( YY_CURRENT_BUFFER_LVALUE->yy_fill_buffer == 0 ) { /* Don't try to fill the buffer, so this is an EOF. */ if ( (yy_c_buf_p) - (yytext_ptr) - YY_MORE_ADJ == 1 ) { /* We matched a single character, the EOB, so * treat this as a final EOF. */ return EOB_ACT_END_OF_FILE; } else { /* We matched some text prior to the EOB, first * process it. */ return EOB_ACT_LAST_MATCH; } } /* Try to read more data. */ /* First move last chars to start of buffer. */ number_to_move = (yy_size_t) ((yy_c_buf_p) - (yytext_ptr)) - 1; for ( i = 0; i < number_to_move; ++i ) *(dest++) = *(source++); if ( YY_CURRENT_BUFFER_LVALUE->yy_buffer_status == YY_BUFFER_EOF_PENDING ) /* don't do the read, it's not guaranteed to return an EOF, * just force an EOF */ YY_CURRENT_BUFFER_LVALUE->yy_n_chars = (yy_n_chars) = 0; else { int num_to_read = YY_CURRENT_BUFFER_LVALUE->yy_buf_size - number_to_move - 1; while ( num_to_read <= 0 ) { /* Not enough room in the buffer - grow it. */ /* just a shorter name for the current buffer */ YY_BUFFER_STATE b = YY_CURRENT_BUFFER_LVALUE; int yy_c_buf_p_offset = (int) ((yy_c_buf_p) - b->yy_ch_buf); if ( b->yy_is_our_buffer ) { int new_size = b->yy_buf_size * 2; if ( new_size <= 0 ) b->yy_buf_size += b->yy_buf_size / 8; else b->yy_buf_size *= 2; b->yy_ch_buf = (char *) /* Include room in for 2 EOB chars. */ addrrealloc((void *) b->yy_ch_buf,b->yy_buf_size + 2 ); } else /* Can't grow it, we don't own it. */ b->yy_ch_buf = NULL; if ( ! b->yy_ch_buf ) YY_FATAL_ERROR( "fatal error - scanner input buffer overflow" ); (yy_c_buf_p) = &b->yy_ch_buf[yy_c_buf_p_offset]; num_to_read = YY_CURRENT_BUFFER_LVALUE->yy_buf_size - number_to_move - 1; } if ( num_to_read > YY_READ_BUF_SIZE ) num_to_read = YY_READ_BUF_SIZE; /* Read in more data. */ YY_INPUT( (&YY_CURRENT_BUFFER_LVALUE->yy_ch_buf[number_to_move]), (yy_n_chars), num_to_read ); YY_CURRENT_BUFFER_LVALUE->yy_n_chars = (yy_n_chars); } if ( (yy_n_chars) == 0 ) { if ( number_to_move == YY_MORE_ADJ ) { ret_val = EOB_ACT_END_OF_FILE; addrrestart(addrin ); } else { ret_val = EOB_ACT_LAST_MATCH; YY_CURRENT_BUFFER_LVALUE->yy_buffer_status = YY_BUFFER_EOF_PENDING; } } else ret_val = EOB_ACT_CONTINUE_SCAN; if ((int) ((yy_n_chars) + number_to_move) > YY_CURRENT_BUFFER_LVALUE->yy_buf_size) { /* Extend the array by 50%, plus the number we really need. */ int new_size = (yy_n_chars) + number_to_move + ((yy_n_chars) >> 1); YY_CURRENT_BUFFER_LVALUE->yy_ch_buf = (char *) addrrealloc((void *) YY_CURRENT_BUFFER_LVALUE->yy_ch_buf,new_size ); if ( ! YY_CURRENT_BUFFER_LVALUE->yy_ch_buf ) YY_FATAL_ERROR( "out of dynamic memory in yy_get_next_buffer()" ); } (yy_n_chars) += number_to_move; YY_CURRENT_BUFFER_LVALUE->yy_ch_buf[(yy_n_chars)] = YY_END_OF_BUFFER_CHAR; YY_CURRENT_BUFFER_LVALUE->yy_ch_buf[(yy_n_chars) + 1] = YY_END_OF_BUFFER_CHAR; (yytext_ptr) = &YY_CURRENT_BUFFER_LVALUE->yy_ch_buf[0]; return ret_val; } /* yy_get_previous_state - get the state just before the EOB char was reached */ static yy_state_type yy_get_previous_state (void) { yy_state_type yy_current_state; char *yy_cp; yy_current_state = (yy_start); for ( yy_cp = (yytext_ptr) + YY_MORE_ADJ; yy_cp < (yy_c_buf_p); ++yy_cp ) { YY_CHAR yy_c = (*yy_cp ? yy_ec[YY_SC_TO_UI(*yy_cp)] : 13); if ( yy_accept[yy_current_state] ) { (yy_last_accepting_state) = yy_current_state; (yy_last_accepting_cpos) = yy_cp; } while ( yy_chk[yy_base[yy_current_state] + yy_c] != yy_current_state ) { yy_current_state = (int) yy_def[yy_current_state]; if ( yy_current_state >= 40 ) yy_c = yy_meta[(unsigned int) yy_c]; } yy_current_state = yy_nxt[yy_base[yy_current_state] + (flex_int16_t) yy_c]; } return yy_current_state; } /* yy_try_NUL_trans - try to make a transition on the NUL character * * synopsis * next_state = yy_try_NUL_trans( current_state ); */ static yy_state_type yy_try_NUL_trans (yy_state_type yy_current_state ) { int yy_is_jam; char *yy_cp = (yy_c_buf_p); YY_CHAR yy_c = 13; if ( yy_accept[yy_current_state] ) { (yy_last_accepting_state) = yy_current_state; (yy_last_accepting_cpos) = yy_cp; } while ( yy_chk[yy_base[yy_current_state] + yy_c] != yy_current_state ) { yy_current_state = (int) yy_def[yy_current_state]; if ( yy_current_state >= 40 ) yy_c = yy_meta[(unsigned int) yy_c]; } yy_current_state = yy_nxt[yy_base[yy_current_state] + (flex_int16_t) yy_c]; yy_is_jam = (yy_current_state == 39); return yy_is_jam ? 0 : yy_current_state; } #ifndef YY_NO_UNPUT #endif #ifndef YY_NO_INPUT #ifdef __cplusplus static int yyinput (void) #else static int input (void) #endif { int c; *(yy_c_buf_p) = (yy_hold_char); if ( *(yy_c_buf_p) == YY_END_OF_BUFFER_CHAR ) { /* yy_c_buf_p now points to the character we want to return. * If this occurs *before* the EOB characters, then it's a * valid NUL; if not, then we've hit the end of the buffer. */ if ( (yy_c_buf_p) < &YY_CURRENT_BUFFER_LVALUE->yy_ch_buf[(yy_n_chars)] ) /* This was really a NUL. */ *(yy_c_buf_p) = '\0'; else { /* need more input */ int offset = (yy_c_buf_p) - (yytext_ptr); ++(yy_c_buf_p); switch ( yy_get_next_buffer( ) ) { case EOB_ACT_LAST_MATCH: /* This happens because yy_g_n_b() * sees that we've accumulated a * token and flags that we need to * try matching the token before * proceeding. But for input(), * there's no matching to consider. * So convert the EOB_ACT_LAST_MATCH * to EOB_ACT_END_OF_FILE. */ /* Reset buffer status. */ addrrestart(addrin ); /*FALLTHROUGH*/ case EOB_ACT_END_OF_FILE: { if ( addrwrap( ) ) return 0; if ( ! (yy_did_buffer_switch_on_eof) ) YY_NEW_FILE; #ifdef __cplusplus return yyinput(); #else return input(); #endif } case EOB_ACT_CONTINUE_SCAN: (yy_c_buf_p) = (yytext_ptr) + offset; break; } } } c = *(unsigned char *) (yy_c_buf_p); /* cast for 8-bit char's */ *(yy_c_buf_p) = '\0'; /* preserve addrtext */ (yy_hold_char) = *++(yy_c_buf_p); return c; } #endif /* ifndef YY_NO_INPUT */ /** Immediately switch to a different input stream. * @param input_file A readable stream. * * @note This function does not reset the start condition to @c INITIAL . */ void addrrestart (FILE * input_file ) { if ( ! YY_CURRENT_BUFFER ){ addrensure_buffer_stack (); YY_CURRENT_BUFFER_LVALUE = addr_create_buffer(addrin,YY_BUF_SIZE ); } addr_init_buffer(YY_CURRENT_BUFFER,input_file ); addr_load_buffer_state( ); } /** Switch to a different input buffer. * @param new_buffer The new input buffer. * */ void addr_switch_to_buffer (YY_BUFFER_STATE new_buffer ) { /* TODO. We should be able to replace this entire function body * with * addrpop_buffer_state(); * addrpush_buffer_state(new_buffer); */ addrensure_buffer_stack (); if ( YY_CURRENT_BUFFER == new_buffer ) return; if ( YY_CURRENT_BUFFER ) { /* Flush out information for old buffer. */ *(yy_c_buf_p) = (yy_hold_char); YY_CURRENT_BUFFER_LVALUE->yy_buf_pos = (yy_c_buf_p); YY_CURRENT_BUFFER_LVALUE->yy_n_chars = (yy_n_chars); } YY_CURRENT_BUFFER_LVALUE = new_buffer; addr_load_buffer_state( ); /* We don't actually know whether we did this switch during * EOF (addrwrap()) processing, but the only time this flag * is looked at is after addrwrap() is called, so it's safe * to go ahead and always set it. */ (yy_did_buffer_switch_on_eof) = 1; } static void addr_load_buffer_state (void) { (yy_n_chars) = YY_CURRENT_BUFFER_LVALUE->yy_n_chars; (yytext_ptr) = (yy_c_buf_p) = YY_CURRENT_BUFFER_LVALUE->yy_buf_pos; addrin = YY_CURRENT_BUFFER_LVALUE->yy_input_file; (yy_hold_char) = *(yy_c_buf_p); } /** Allocate and initialize an input buffer state. * @param file A readable stream. * @param size The character buffer size in bytes. When in doubt, use @c YY_BUF_SIZE. * * @return the allocated buffer state. */ YY_BUFFER_STATE addr_create_buffer (FILE * file, int size ) { YY_BUFFER_STATE b; b = (YY_BUFFER_STATE) addralloc(sizeof( struct yy_buffer_state ) ); if ( ! b ) YY_FATAL_ERROR( "out of dynamic memory in addr_create_buffer()" ); b->yy_buf_size = (yy_size_t)size; /* yy_ch_buf has to be 2 characters longer than the size given because * we need to put in 2 end-of-buffer characters. */ b->yy_ch_buf = (char *) addralloc(b->yy_buf_size + 2 ); if ( ! b->yy_ch_buf ) YY_FATAL_ERROR( "out of dynamic memory in addr_create_buffer()" ); b->yy_is_our_buffer = 1; addr_init_buffer(b,file ); return b; } /** Destroy the buffer. * @param b a buffer created with addr_create_buffer() * */ void addr_delete_buffer (YY_BUFFER_STATE b ) { if ( ! b ) return; if ( b == YY_CURRENT_BUFFER ) /* Not sure if we should pop here. */ YY_CURRENT_BUFFER_LVALUE = (YY_BUFFER_STATE) 0; if ( b->yy_is_our_buffer ) addrfree((void *) b->yy_ch_buf ); addrfree((void *) b ); } /* Initializes or reinitializes a buffer. * This function is sometimes called more than once on the same buffer, * such as during a addrrestart() or at EOF. */ static void addr_init_buffer (YY_BUFFER_STATE b, FILE * file ) { int oerrno = errno; addr_flush_buffer(b ); b->yy_input_file = file; b->yy_fill_buffer = 1; /* If b is the current buffer, then addr_init_buffer was _probably_ * called from addrrestart() or through yy_get_next_buffer. * In that case, we don't want to reset the lineno or column. */ if (b != YY_CURRENT_BUFFER){ b->yy_bs_lineno = 1; b->yy_bs_column = 0; } b->yy_is_interactive = file ? (isatty( fileno(file) ) > 0) : 0; errno = oerrno; } /** Discard all buffered characters. On the next scan, YY_INPUT will be called. * @param b the buffer state to be flushed, usually @c YY_CURRENT_BUFFER. * */ void addr_flush_buffer (YY_BUFFER_STATE b ) { if ( ! b ) return; b->yy_n_chars = 0; /* We always need two end-of-buffer characters. The first causes * a transition to the end-of-buffer state. The second causes * a jam in that state. */ b->yy_ch_buf[0] = YY_END_OF_BUFFER_CHAR; b->yy_ch_buf[1] = YY_END_OF_BUFFER_CHAR; b->yy_buf_pos = &b->yy_ch_buf[0]; b->yy_at_bol = 1; b->yy_buffer_status = YY_BUFFER_NEW; if ( b == YY_CURRENT_BUFFER ) addr_load_buffer_state( ); } /** Pushes the new state onto the stack. The new state becomes * the current state. This function will allocate the stack * if necessary. * @param new_buffer The new state. * */ void addrpush_buffer_state (YY_BUFFER_STATE new_buffer ) { if (new_buffer == NULL) return; addrensure_buffer_stack(); /* This block is copied from addr_switch_to_buffer. */ if ( YY_CURRENT_BUFFER ) { /* Flush out information for old buffer. */ *(yy_c_buf_p) = (yy_hold_char); YY_CURRENT_BUFFER_LVALUE->yy_buf_pos = (yy_c_buf_p); YY_CURRENT_BUFFER_LVALUE->yy_n_chars = (yy_n_chars); } /* Only push if top exists. Otherwise, replace top. */ if (YY_CURRENT_BUFFER) (yy_buffer_stack_top)++; YY_CURRENT_BUFFER_LVALUE = new_buffer; /* copied from addr_switch_to_buffer. */ addr_load_buffer_state( ); (yy_did_buffer_switch_on_eof) = 1; } /** Removes and deletes the top of the stack, if present. * The next element becomes the new top. * */ void addrpop_buffer_state (void) { if (!YY_CURRENT_BUFFER) return; addr_delete_buffer(YY_CURRENT_BUFFER ); YY_CURRENT_BUFFER_LVALUE = NULL; if ((yy_buffer_stack_top) > 0) --(yy_buffer_stack_top); if (YY_CURRENT_BUFFER) { addr_load_buffer_state( ); (yy_did_buffer_switch_on_eof) = 1; } } /* Allocates the stack if it does not exist. * Guarantees space for at least one push. */ static void addrensure_buffer_stack (void) { int num_to_alloc; if (!(yy_buffer_stack)) { /* First allocation is just for 2 elements, since we don't know if this * scanner will even need a stack. We use 2 instead of 1 to avoid an * immediate realloc on the next call. */ num_to_alloc = 1; /* After all that talk, this was set to 1 anyways... */ (yy_buffer_stack) = (struct yy_buffer_state**)addralloc (num_to_alloc * sizeof(struct yy_buffer_state*) ); if ( ! (yy_buffer_stack) ) YY_FATAL_ERROR( "out of dynamic memory in addrensure_buffer_stack()" ); memset((yy_buffer_stack), 0, num_to_alloc * sizeof(struct yy_buffer_state*)); (yy_buffer_stack_max) = num_to_alloc; (yy_buffer_stack_top) = 0; return; } if ((yy_buffer_stack_top) >= ((yy_buffer_stack_max)) - 1){ /* Increase the buffer to prepare for a possible push. */ yy_size_t grow_size = 8 /* arbitrary grow size */; num_to_alloc = (yy_buffer_stack_max) + grow_size; (yy_buffer_stack) = (struct yy_buffer_state**)addrrealloc ((yy_buffer_stack), num_to_alloc * sizeof(struct yy_buffer_state*) ); if ( ! (yy_buffer_stack) ) YY_FATAL_ERROR( "out of dynamic memory in addrensure_buffer_stack()" ); /* zero only the new slots.*/ memset((yy_buffer_stack) + (yy_buffer_stack_max), 0, grow_size * sizeof(struct yy_buffer_state*)); (yy_buffer_stack_max) = num_to_alloc; } } /** Setup the input buffer state to scan directly from a user-specified character buffer. * @param base the character buffer * @param size the size in bytes of the character buffer * * @return the newly allocated buffer state object. */ YY_BUFFER_STATE addr_scan_buffer (char * base, yy_size_t size ) { YY_BUFFER_STATE b; if ( size < 2 || base[size-2] != YY_END_OF_BUFFER_CHAR || base[size-1] != YY_END_OF_BUFFER_CHAR ) /* They forgot to leave room for the EOB's. */ return NULL; b = (YY_BUFFER_STATE) addralloc(sizeof( struct yy_buffer_state ) ); if ( ! b ) YY_FATAL_ERROR( "out of dynamic memory in addr_scan_buffer()" ); b->yy_buf_size = size - 2; /* "- 2" to take care of EOB's */ b->yy_buf_pos = b->yy_ch_buf = base; b->yy_is_our_buffer = 0; b->yy_input_file = NULL; b->yy_n_chars = b->yy_buf_size; b->yy_is_interactive = 0; b->yy_at_bol = 1; b->yy_fill_buffer = 0; b->yy_buffer_status = YY_BUFFER_NEW; addr_switch_to_buffer(b ); return b; } /** Setup the input buffer state to scan a string. The next call to addrlex() will * scan from a @e copy of @a str. * @param yystr a NUL-terminated string to scan * * @return the newly allocated buffer state object. * @note If you want to scan bytes that may contain NUL values, then use * addr_scan_bytes() instead. */ YY_BUFFER_STATE addr_scan_string (yyconst char * yystr ) { return addr_scan_bytes(yystr,(int) strlen(yystr) ); } /** Setup the input buffer state to scan the given bytes. The next call to addrlex() will * scan from a @e copy of @a bytes. * @param yybytes the byte buffer to scan * @param _yybytes_len the number of bytes in the buffer pointed to by @a bytes. * * @return the newly allocated buffer state object. */ YY_BUFFER_STATE addr_scan_bytes (yyconst char * yybytes, int _yybytes_len ) { YY_BUFFER_STATE b; char *buf; yy_size_t n; yy_size_t i; /* Get memory for full buffer, including space for trailing EOB's. */ n = (yy_size_t) _yybytes_len + 2; buf = (char *) addralloc(n ); if ( ! buf ) YY_FATAL_ERROR( "out of dynamic memory in addr_scan_bytes()" ); for ( i = 0; i < _yybytes_len; ++i ) buf[i] = yybytes[i]; buf[_yybytes_len] = buf[_yybytes_len+1] = YY_END_OF_BUFFER_CHAR; b = addr_scan_buffer(buf,n ); if ( ! b ) YY_FATAL_ERROR( "bad buffer in addr_scan_bytes()" ); /* It's okay to grow etc. this buffer, and we should throw it * away when we're done. */ b->yy_is_our_buffer = 1; return b; } #ifndef YY_EXIT_FAILURE #define YY_EXIT_FAILURE 2 #endif static void yynoreturn yy_fatal_error (yyconst char* msg ) { (void) fprintf( stderr, "%s\n", msg ); exit( YY_EXIT_FAILURE ); } /* Redefine yyless() so it works in section 3 code. */ #undef yyless #define yyless(n) \ do \ { \ /* Undo effects of setting up addrtext. */ \ int yyless_macro_arg = (n); \ YY_LESS_LINENO(yyless_macro_arg);\ addrtext[addrleng] = (yy_hold_char); \ (yy_c_buf_p) = addrtext + yyless_macro_arg; \ (yy_hold_char) = *(yy_c_buf_p); \ *(yy_c_buf_p) = '\0'; \ addrleng = yyless_macro_arg; \ } \ while ( 0 ) /* Accessor methods (get/set functions) to struct members. */ /** Get the current line number. * */ int addrget_lineno (void) { return addrlineno; } /** Get the input stream. * */ FILE *addrget_in (void) { return addrin; } /** Get the output stream. * */ FILE *addrget_out (void) { return addrout; } /** Get the length of the current token. * */ int addrget_leng (void) { return addrleng; } /** Get the current token. * */ char *addrget_text (void) { return addrtext; } /** Set the current line number. * @param _line_number line number * */ void addrset_lineno (int _line_number ) { addrlineno = _line_number; } /** Set the input stream. This does not discard the current * input buffer. * @param _in_str A readable stream. * * @see addr_switch_to_buffer */ void addrset_in (FILE * _in_str ) { addrin = _in_str ; } void addrset_out (FILE * _out_str ) { addrout = _out_str ; } int addrget_debug (void) { return addr_flex_debug; } void addrset_debug (int _bdebug ) { addr_flex_debug = _bdebug ; } static int yy_init_globals (void) { /* Initialization is the same as for the non-reentrant scanner. * This function is called from addrlex_destroy(), so don't allocate here. */ (yy_buffer_stack) = NULL; (yy_buffer_stack_top) = 0; (yy_buffer_stack_max) = 0; (yy_c_buf_p) = NULL; (yy_init) = 0; (yy_start) = 0; /* Defined in main.c */ #ifdef YY_STDINIT addrin = stdin; addrout = stdout; #else addrin = NULL; addrout = NULL; #endif /* For future reference: Set errno on error, since we are called by * addrlex_init() */ return 0; } /* addrlex_destroy is for both reentrant and non-reentrant scanners. */ int addrlex_destroy (void) { /* Pop the buffer stack, destroying each element. */ while(YY_CURRENT_BUFFER){ addr_delete_buffer(YY_CURRENT_BUFFER ); YY_CURRENT_BUFFER_LVALUE = NULL; addrpop_buffer_state(); } /* Destroy the stack itself. */ addrfree((yy_buffer_stack) ); (yy_buffer_stack) = NULL; /* Reset the globals. This is important in a non-reentrant scanner so the next time * addrlex() is called, initialization will occur. */ yy_init_globals( ); return 0; } /* * Internal utility routines. */ #ifndef yytext_ptr static void yy_flex_strncpy (char* s1, yyconst char * s2, int n ) { int i; for ( i = 0; i < n; ++i ) s1[i] = s2[i]; } #endif #ifdef YY_NEED_STRLEN static int yy_flex_strlen (yyconst char * s ) { int n; for ( n = 0; s[n]; ++n ) ; return n; } #endif void *addralloc (yy_size_t size ) { return malloc(size); } void *addrrealloc (void * ptr, yy_size_t size ) { /* The cast to (char *) in the following accommodates both * implementations that use char* generic pointers, and those * that use void* generic pointers. It works with the latter * because both ANSI C and C++ allow castless assignment from * any pointer type to void*, and deal with argument conversions * as though doing an assignment. */ return realloc(ptr, size); } void addrfree (void * ptr ) { free( (char *) ptr ); /* see addrrealloc() for (char *) cast */ } #define YYTABLES_NAME "yytables" #line 100 "sieve/addr-lex.l" cyrus-imapd-2.5.10/config.h.in0000644000175000017500000004444213001246601013001 00000000000000/* config.h.in. Generated from configure.ac by autoheader. */ /* * Copyright (c) 1994-2012 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #ifndef _CYRUS_IMAPD_CONFIG_H_ #define _CYRUS_IMAPD_CONFIG_H_ /* Define if building universal (internal helper macro) */ #undef AC_APPLE_UNIVERSAL_BUILD /* Should the AFS PTS plugin use krb5? */ #undef AFSPTS_USE_KRB5 /* Where will we be installed? */ #undef CYRUS_PATH /* What user will we run as? */ #undef CYRUS_USER /* Alternative to /dev/urandom? */ #undef EGD_SOCKET /* Build with support of mailbox event notification */ #undef ENABLE_MBOXEVENT /* Do we have a regex library? */ #undef ENABLE_REGEX /* Enable Netscape Menu Option Hack? */ #undef ENABLE_X_NETSCAPE_HACK /* Extra version information for imap/version.h */ #undef EXTRA_IDENT /* Do we have strerror()? */ #undef HAS_STRERROR /* Should we build afskrb pts module? */ #undef HAVE_AFSKRB /* Does SASL support APOP? */ #undef HAVE_APOP /* Build in Berkeley DB support? */ #undef HAVE_BDB /* Do we have ClamAV? */ #undef HAVE_CLAMAV /* Do we have CU_SetUpFunc? */ #undef HAVE_CU_SETUPFUNC /* Define to 1 if you have the `daemon' function. */ #undef HAVE_DAEMON /* Define to 1 if you have the declaration of `tzname', and to 0 if you don't. */ #undef HAVE_DECL_TZNAME /* Define to 1 if you have the header file, and it defines `DIR'. */ #undef HAVE_DIRENT_H /* Define to 1 if you have the header file. */ #undef HAVE_DLFCN_H /* Define to 1 if you have the `dns_lookup' function. */ #undef HAVE_DNS_LOOKUP /* Define to 1 if you have the `dn_expand' function. */ #undef HAVE_DN_EXPAND /* Define to 1 if you don't have `vprintf' but do have `_doprnt.' */ #undef HAVE_DOPRNT /* We need et/com_err.h */ #undef HAVE_ET_COM_ERR_H /* Do we have fdatasync()? */ #undef HAVE_FDATASYNC /* Define to 1 if you have the `fmemopen' function. */ #undef HAVE_FMEMOPEN /* Define to 1 if you have the `ftruncate' function. */ #undef HAVE_FTRUNCATE /* Do we have a getaddrinfo? */ #undef HAVE_GETADDRINFO /* Define to 1 if you have the `getdtablesize' function. */ #undef HAVE_GETDTABLESIZE /* Define to 1 if you have the `getgrouplist' function. */ #undef HAVE_GETGROUPLIST /* Do we have a getnameinfo? */ #undef HAVE_GETNAMEINFO /* Define to 1 if you have the `getpassphrase' function. */ #undef HAVE_GETPASSPHRASE /* Define to 1 if you have the `getrlimit' function. */ #undef HAVE_GETRLIMIT /* Define to 1 if you have the header file. */ #undef HAVE_GSSAPI_GSSAPI_EXT_H /* Define if you have the gssapi.h header file */ #undef HAVE_GSSAPI_H /* Define to 1 if you have the `gsskrb5_register_acceptor_identity' function. */ #undef HAVE_GSSKRB5_REGISTER_ACCEPTOR_IDENTITY /* Define if your GSSAPI implementation defines GSS_C_NT_HOSTBASED_SERVICE */ #undef HAVE_GSS_C_NT_HOSTBASED_SERVICE /* Define if your GSSAPI implementation defines GSS_C_NT_USER_NAME */ #undef HAVE_GSS_C_NT_USER_NAME /* Define to 1 if you have the `gss_decapsulate_token' function. */ #undef HAVE_GSS_DECAPSULATE_TOKEN /* Define to 1 if you have the `gss_encapsulate_token' function. */ #undef HAVE_GSS_ENCAPSULATE_TOKEN /* Define to 1 if you have the `gss_get_name_attribute' function. */ #undef HAVE_GSS_GET_NAME_ATTRIBUTE /* Define to 1 if you have the `gss_oid_equal' function. */ #undef HAVE_GSS_OID_EQUAL /* Define if your GSSAPI implementation supports SPNEGO */ #undef HAVE_GSS_SPNEGO /* Do we have support for IANA params? */ #undef HAVE_IANA_PARAMS /* Build in ical support? */ #undef HAVE_ICAL /* Define to 1 if you have the header file. */ #undef HAVE_INTTYPES_H /* Support for Kerberos? */ #undef HAVE_KRB /* Should we build the LDAP pts module? */ #undef HAVE_LDAP /* Do we have libcap system capabilities handling (Linux systems only)? */ #undef HAVE_LIBCAP /* Define to 1 if you have the `resolv' library (-lresolv). */ #undef HAVE_LIBRESOLV /* Do we have the uuid library */ #undef HAVE_LIBUUID /* Do we have TCP wrappers? */ #undef HAVE_LIBWRAP /* Define to 1 if you support file names longer than 14 characters. */ #undef HAVE_LONG_FILE_NAMES /* Define to 1 if you have the `memmem' function. */ #undef HAVE_MEMMEM /* Define to 1 if you have the `memmove' function. */ #undef HAVE_MEMMOVE /* Define to 1 if you have the header file. */ #undef HAVE_MEMORY_H /* Build in MySQL support? */ #undef HAVE_MYSQL /* Define to 1 if you have the header file, and it defines `DIR'. */ #undef HAVE_NDIR_H /* Do we have Net-SNMP support? */ #undef HAVE_NETSNMP /* Define to 1 if you have the header file. */ #undef HAVE_NET_SNMP_AGENT_AGENT_MODULE_CONFIG_H /* Do we have usable pcre library? */ #undef HAVE_PCREPOSIX_H /* Build in PgSQL support? */ #undef HAVE_PGSQL /* Define to 1 if you have the `posix_fadvise' function. */ #undef HAVE_POSIX_FADVISE /* Define to 1 if you have the `pselect' function. */ #undef HAVE_PSELECT /* Do we have an rlim_t? */ #undef HAVE_RLIM_T /* Build RSCALE support into httpd? */ #undef HAVE_RSCALE /* Define to 1 if you have the header file. */ #undef HAVE_RXPOSIX_H /* Do we have built-in support for scheduling params? */ #undef HAVE_SCHEDULING_PARAMS /* Define to 1 if you have the `setrlimit' function. */ #undef HAVE_SETRLIMIT /* Define to 1 if you have the `setsid' function. */ #undef HAVE_SETSID /* Define to 1 if you have the `shutdown' function. */ #undef HAVE_SHUTDOWN /* Does sockaddr have an sa_len? */ #undef HAVE_SOCKADDR_SA_LEN /* Do we have a socklen_t? */ #undef HAVE_SOCKLEN_T /* Build in SQLite support? */ #undef HAVE_SQLITE /* Build in SQLite support? */ #undef HAVE_SQLITE3 /* Build with SSL support? */ #undef HAVE_SSL /* Is there an ss_family in sockaddr_storage? */ #undef HAVE_SS_FAMILY /* Define to 1 if you have the header file. */ #undef HAVE_STDARG_H /* Define to 1 if you have the header file. */ #undef HAVE_STDINT_H /* Define to 1 if you have the header file. */ #undef HAVE_STDLIB_H /* Define to 1 if you have the `strcasecmp' function. */ #undef HAVE_STRCASECMP /* Define to 1 if you have the `strerror' function. */ #undef HAVE_STRERROR /* Define to 1 if you have the header file. */ #undef HAVE_STRINGS_H /* Define to 1 if you have the header file. */ #undef HAVE_STRING_H /* Define to 1 if you have the `strlcat' function. */ #undef HAVE_STRLCAT /* Define to 1 if you have the `strlcpy' function. */ #undef HAVE_STRLCPY /* Define to 1 if you have the `strsep' function. */ #undef HAVE_STRSEP /* Do we have a sockaddr_storage? */ #undef HAVE_STRUCT_SOCKADDR_STORAGE /* Define to 1 if `tm_zone' is a member of `struct tm'. */ #undef HAVE_STRUCT_TM_TM_ZONE /* Define to 1 if you have the header file. */ #undef HAVE_SYS_CAPABILITY_H /* Define to 1 if you have the header file, and it defines `DIR'. */ #undef HAVE_SYS_DIR_H /* Define to 1 if you have the header file, and it defines `DIR'. */ #undef HAVE_SYS_NDIR_H /* Define to 1 if you have the header file. */ #undef HAVE_SYS_PARAM_H /* Define to 1 if you have the header file. */ #undef HAVE_SYS_PRCTL_H /* Define to 1 if you have the header file. */ #undef HAVE_SYS_RESOURCE_H /* Define to 1 if you have the header file. */ #undef HAVE_SYS_SELECT_H /* Define to 1 if you have the header file. */ #undef HAVE_SYS_SOCKIO_H /* Define to 1 if you have the header file. */ #undef HAVE_SYS_STAT_H /* Define to 1 if you have the header file. */ #undef HAVE_SYS_TIME_H /* Define to 1 if you have the header file. */ #undef HAVE_SYS_TYPES_H /* Define to 1 if you have the `timegm' function. */ #undef HAVE_TIMEGM /* Define to 1 if your `struct tm' has `tm_zone'. Deprecated, use `HAVE_STRUCT_TM_TM_ZONE' instead. */ #undef HAVE_TM_ZONE /* Do we have built-in support for TZdist props? */ #undef HAVE_TZDIST_PROPS /* Define to 1 if you don't have `tm_zone' but do have the external array `tzname'. */ #undef HAVE_TZNAME /* Build TZ by ref support into httpd? */ #undef HAVE_TZ_BY_REF /* Do we have UCD-SNMP support? */ #undef HAVE_UCDSNMP /* Define to 1 if you have the header file. */ #undef HAVE_UNISTD_H /* Define to 1 if you have the header file. */ #undef HAVE_VALGRIND_VALGRIND_H /* Build VAVAILABILITY support into httpd? */ #undef HAVE_VAVAILABILITY /* Define to 1 or 0, depending whether the compiler supports simple visibility declarations. */ #undef HAVE_VISIBILITY /* Build VPOLL support into httpd? */ #undef HAVE_VPOLL /* Define to 1 if you have the `vprintf' function. */ #undef HAVE_VPRINTF /* Build in libxml support? */ #undef HAVE_XML2 /* Build with Zephyr support? */ #undef HAVE_ZEPHYR /* Do we have zlib? */ #undef HAVE_ZLIB /* Define to the sub-directory where libtool stores uninstalled libraries. */ #undef LT_OBJDIR /* Name of the pidfile for master */ #undef MASTER_PIDFILE /* Do we have a sys_errlist? */ #undef NEED_SYS_ERRLIST /* Use "imap" as sieve service name? */ #undef OLD_SIEVE_SERVICE_NAME /* Configure OpenSSL to provide krb4-compatible legacy des apis */ #undef OPENSSL_DES_LIBDES_COMPATIBILITY /* Configure OpenSSL to provide legacy des apis */ #undef OPENSSL_ENABLE_OLD_DES_SUPPORT /* Name of package */ #undef PACKAGE /* Define to the address where bug reports for this package should be sent. */ #undef PACKAGE_BUGREPORT /* Define to the full name of this package. */ #undef PACKAGE_NAME /* Define to the full name and version of this package. */ #undef PACKAGE_STRING /* Define to the one symbol short name of this package. */ #undef PACKAGE_TARNAME /* Define to the home page for this package. */ #undef PACKAGE_URL /* Define to the version of this package. */ #undef PACKAGE_VERSION /* Directory to use for service binaries */ #undef SERVICE_DIR /* The size of `int', as computed by sizeof. */ #undef SIZEOF_INT /* The size of `long', as computed by sizeof. */ #undef SIZEOF_LONG /* The size of `long long int', as computed by sizeof. */ #undef SIZEOF_LONG_LONG_INT /* The size of `off_t', as computed by sizeof. */ #undef SIZEOF_OFF_T /* The size of `size_t', as computed by sizeof. */ #undef SIZEOF_SIZE_T /* The size of `unsigned long long int', as computed by sizeof. */ #undef SIZEOF_UNSIGNED_LONG_LONG_INT /* Do we already have setproctitle? */ #undef SPT_TYPE /* Define to 1 if you have the ANSI C header files. */ #undef STDC_HEADERS /* Config File Location */ #undef SYSCONFDIR /* Syslog facility to use. */ #undef SYSLOG_FACILITY /* Define to 1 if you can safely include both and . */ #undef TIME_WITH_SYS_TIME /* Define to 1 if your declares `struct tm'. */ #undef TM_IN_SYS_TIME /* Build with autocreate functionality */ #undef USE_AUTOCREATE /* Build in Sieve support? */ #undef USE_SIEVE /* Enable extensions on AIX 3, Interix. */ #ifndef _ALL_SOURCE # undef _ALL_SOURCE #endif /* Enable GNU extensions on systems that have them. */ #ifndef _GNU_SOURCE # undef _GNU_SOURCE #endif /* Enable threading extensions on Solaris. */ #ifndef _POSIX_PTHREAD_SEMANTICS # undef _POSIX_PTHREAD_SEMANTICS #endif /* Enable extensions on HP NonStop. */ #ifndef _TANDEM_SOURCE # undef _TANDEM_SOURCE #endif /* Enable general extensions on Solaris. */ #ifndef __EXTENSIONS__ # undef __EXTENSIONS__ #endif /* Version number of package */ #undef VERSION /* Build DAV support into httpd? */ #undef WITH_DAV /* Build DKIM support into iSchedule? */ #undef WITH_DKIM /* Build jCal/jCard/TZdist support into httpd? */ #undef WITH_JSON /* Define WORDS_BIGENDIAN to 1 if your processor stores words with the most significant byte first (like Motorola and SPARC, unlike Intel). */ #if defined AC_APPLE_UNIVERSAL_BUILD # if defined __BIG_ENDIAN__ # define WORDS_BIGENDIAN 1 # endif #else # ifndef WORDS_BIGENDIAN # undef WORDS_BIGENDIAN # endif #endif /* Define to 1 if `lex' declares `yytext' as a `char *' by default, not a `char[]'. */ #undef YYTEXT_POINTER /* Define to 1 if on MINIX. */ #undef _MINIX /* Define to 2 if the system does not provide POSIX.1 features except with this defined. */ #undef _POSIX_1_SOURCE /* Define to 1 if you need to in order for `stat' and other things to work. */ #undef _POSIX_SOURCE /* Define to empty if `const' does not conform to ANSI C. */ #undef const /* Define to `__inline__' or `__inline' if that's what the C compiler calls it, or to nothing if 'inline' is not supported under any name. */ #ifndef __cplusplus #undef inline #endif #if HAVE_VISIBILITY #define EXPORTED __attribute__((__visibility__("default"))) #define HIDDEN __attribute__((__visibility__("hidden"))) #else #define EXPORTED #define HIDDEN #endif /* time.h */ #if TIME_WITH_SYS_TIME # include # include #else # if HAVE_SYS_TIME_H # include # else # include # endif #endif /* com_err.h, as needed */ #ifndef IN_COM_ERR #ifdef HAVE_ET_COM_ERR_H #include #else #include #endif /* HAVE_ET_COM_ERR_H */ #endif /* IN_COM_ERR */ /* This allows us to work even when we don't have an fdatasync */ #ifndef HAVE_FDATASYNC #define fdatasync(fd) fsync(fd) #endif /* A similar setup for not having O_DSYNC */ #include #ifndef O_DSYNC # ifdef O_SYNC # define O_DSYNC O_SYNC /* POSIX */ # else # define O_DSYNC O_FSYNC /* BSD */ # endif #endif #ifndef HAVE_SOCKLEN_T typedef unsigned int socklen_t; #endif #ifndef HAVE_RLIM_T typedef int rlim_t; #endif /* some potentially memory saving tradeoffs, preconfigured in memory-saving mode */ /* save the cmdlines for the ID command */ #undef ID_SAVE_CMDLINE /* IPv6 things */ #include #include #include #include #ifndef HAVE_STRUCT_SOCKADDR_STORAGE #define _SS_MAXSIZE 128 /* Implementation specific max size */ #define _SS_PADSIZE (_SS_MAXSIZE - sizeof (struct sockaddr)) struct sockaddr_storage { struct sockaddr ss_sa; char __ss_pad2[_SS_PADSIZE]; }; # define ss_family ss_sa.sa_family # define HAVE_SS_FAMILY #endif /* !HAVE_STRUCT_SOCKADDR_STORAGE */ #ifndef AF_INET6 /* Define it to something that should never appear */ #define AF_INET6 AF_MAX #endif #if !defined(HAVE_GETADDRINFO) || !defined(HAVE_GETNAMEINFO) #include "gai.h" #endif /* End IPv6 things */ #ifdef OLD_SIEVE_SERVICE_NAME #define SIEVE_SERVICE_NAME "imap" #else #define SIEVE_SERVICE_NAME "sieve" #endif /* filenames */ #define FNAME_DBDIR "/db" #define FNAME_USERDIR "/user/" #define FNAME_DOMAINDIR "/domain/" #define FNAME_LOGDIR "/log/" #define FNAME_PTSDB "/ptclient/ptscache.db" #define CONFIG_FILENAME (SYSCONFDIR "/imapd.conf") #define DEFAULT_MASTER_CONFIG_FILENAME (SYSCONFDIR "/cyrus.conf") #ifndef HAVE_SHUTDOWN #define shutdown(fd, mode) 0 #endif /* *printf() macros */ #if (SIZEOF_SIZE_T == SIZEOF_INT) #define SIZE_T_FMT "%u" #elif (SIZEOF_SIZE_T == SIZEOF_LONG) #define SIZE_T_FMT "%lu" #elif (SIZEOF_SIZE_T == SIZEOF_LONG_LONG_INT) #define SIZE_T_FMT "%llu" #else #error dont know what to use for SIZE_T_FMT #endif #if (SIZEOF_OFF_T == SIZEOF_LONG) #define OFF_T_FMT "%ld" #define strtoofft(nptr, endptr, base) strtol(nptr, endptr, base) #elif (SIZEOF_OFF_T == SIZEOF_LONG_LONG_INT) #define OFF_T_FMT "%lld" #define strtoofft(nptr, endptr, base) strtoll(nptr, endptr, base) #else #error dont know what to use for OFF_T_FMT #endif #ifndef HAVE_POSIX_FADVISE #define POSIX_FADV_WILLNEED 0 extern int posix_fadvise(int fd, off_t offset, off_t len, int advice); #endif #ifndef HAVE_STRSEP extern char *strsep(char **, const char *); #endif #ifndef HAVE_MEMMEM extern void *memmem(const void *, size_t, const void *, size_t); #endif /* compile time options; think carefully before modifying */ enum { /* should we send an UNAVAILABLE message to master when * a service is exiting (master is already going to be * informed of the exit by the SIGCHLD signal anyway) ? */ MESSAGE_MASTER_ON_EXIT = 0, /* should a hierarchical rename stop on error? */ RENAME_STOP_ON_ERROR = 1, /* should we call fsync() to maybe help with softupdates? (it should) */ APPEND_ULTRA_PARANOID = 1, /* should we log extra information at the DEBUG level for DB stuff? * 0 -> nothing; 1 -> some; higher -> even more */ CONFIG_DB_VERBOSE = 1, /* log timing information to LOG_DEBUG */ CONFIG_TIMING_VERBOSE = 0, /* should we be pedantic about namespace or sleezy? */ SLEEZY_NAMESPACE = 1, /* should we do a fast TLS session shutdown? */ TLS_FAST_SHUTDOWN = 1, /* should we use the SQUAT engine to accelerate SEARCH? */ SQUAT_ENGINE = 1, /* should we have long LMTP error messages? */ LMTP_LONG_ERROR_MSGS = 1 }; #endif /* _CYRUS_IMAPD_CONFIG_H_ */ cyrus-imapd-2.5.10/depot/0000755000175000017500000000000013001246663012151 500000000000000cyrus-imapd-2.5.10/depot/rc.local.ptclient0000644000175000017500000000051112562247554015342 00000000000000#!/bin/sh echo -n "Starting ptclient" > /dev/console ptscache="/var/ptclient/ptscache.db" /usr/local/bin/db_load -T -t hash -f /dev/null $ptscache touch $ptscache chown cyrus $ptscache chgrp mail $ptscache chmod 660 $ptscache /bin/su postman -c 'exec /usr/cyrus/bin/doptclient' > /dev/console 2>&1 & echo "." > /dev/console cyrus-imapd-2.5.10/depot/rc.local.imap0000644000175000017500000000021312562247554014445 00000000000000#!/bin/sh if [ -d /tmpfs ]; then mkdir /tmpfs/proc chown cyrus /tmpfs/proc fi echo "starting Cyrus system..." /usr/cyrus/bin/master & cyrus-imapd-2.5.10/README0000644000175000017500000000246613001236017011636 00000000000000This is the Carnegie Mellon University Cyrus IMAP Server. The 2.5 series contains numerous features and better standards support than previous versions. No further development work will progress on anything older than version 2.2. Versions 2.2 and 2.3 still receive security updates, but new features or non-security bugfixes are unlikely to be backported. If you continue to install this software PLEASE be sure to read the documentation (located in the doc/ subdirectory). Many common questions can be answered just by carefully following the documentation. Please also refer to http://bugzilla.cyrusimap.org for any outstanding bugs. Note that CMU only provides a source distribution. If you run into problems with any binary distribution, please contact the source of the binary distribution. ---------------------------------------------------------------------- * For the real README file, please see doc/readme.html. * To install the software, please read doc/install.html (but please read doc/readme.html first!). * To see the changes since previous versions, check doc/changes.html, and if upgrading look at doc/install-upgrade.html as well. * To obtain updates to this software, visit the web page http://www.cyrusimap.org/ or ftp directly from ftp://ftp.cyrusimap.org/cyrus-imapd/ cyrus-imapd-2.5.10/master/0000755000175000017500000000000013001246664012332 500000000000000cyrus-imapd-2.5.10/master/service.h0000644000175000017500000000460312772415051014070 00000000000000/* * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #ifndef SERVICE_H #define SERVICE_H enum { STATUS_FD = 3, LISTEN_FD = 4 }; enum { MASTER_SERVICE_AVAILABLE = 0x01, MASTER_SERVICE_UNAVAILABLE = 0x02, MASTER_SERVICE_CONNECTION = 0x03, MASTER_SERVICE_CONNECTION_MULTI = 0x04 }; extern int service_init(int argc, char **argv, char **envp); extern int service_main(int argc, char **argv, char **envp); extern int service_main_fd(int fd, int argc, char **argv, char **envp); extern void service_abort(int error); enum { MAX_USE = 250, REUSE_TIMEOUT = 60 }; struct notify_message { int message; pid_t service_pid; }; #endif cyrus-imapd-2.5.10/master/cyrusMasterMIB.h0000644000175000017500000000073012562247555015307 00000000000000/* This file was generated by mib2c and is intended for use as a mib module for the ucd-snmp snmpd agent. */ #ifndef _MIBGROUP_CYRUSMASTERMIB_H #define _MIBGROUP_CYRUSMASTERMIB_H /* we may use header_generic and header_simple_table from the util_funcs module */ config_require(util_funcs) /* function prototypes */ void init_cyrusMasterMIB(void); FindVarMethod var_cyrusMasterMIB; FindVarMethod var_serviceTable; #endif /* _MIBGROUP_CYRUSMASTERMIB_H */ cyrus-imapd-2.5.10/master/cyrusMasterMIB.c0000644000175000017500000001601713001236020015255 00000000000000 /* This file was generated by mib2c and is intended for use as a mib module for the ucd-snmp snmpd agent. */ /* This should always be included first before anything else */ #include #if defined(HAVE_UCDSNMP) || defined(HAVE_NETSNMP) #include "xstrlcpy.h" #include "xstrlcat.h" #ifdef HAVE_NETSNMP #include #include #include #include extern int header_generic(struct variable *, oid *, size_t *, int, size_t *, WriteMethod **); extern int header_simple_table(struct variable *, oid *, size_t *, int, size_t *, WriteMethod **, int); #else #ifdef IN_UCD_SNMP_SOURCE /* If we're compiling this file inside the ucd-snmp source tree */ /* minimal include directives */ #include "mibincl.h" #include "util_funcs.h" #else /* !IN_UCD_SNMP_SOURCE */ #include #include #include #include #endif /* !IN_UCD_SNMP_SOURCE */ #endif /* HAVE_NETSNMP */ #include #include #include #include "cyrusMasterMIB.h" #include "master.h" #include "../xversion.h" /* * cyrusMasterMIB_variables_oid: * this is the top level oid that we want to register under. This * is essentially a prefix, with the suffix appearing in the * variable below. */ oid cyrusMasterMIB_variables_oid[] = { 1,3,6,1,4,1,3,6,1 }; /* * variable4 cyrusMasterMIB_variables: * this variable defines function callbacks and type return information * for the cyrusMasterMIB mib section */ struct variable4 cyrusMasterMIB_variables[] = { /* magic number , variable type , ro/rw , callback fn , L, oidsuffix */ #define CYRUSMASTERINFODESCR 1 { CYRUSMASTERINFODESCR, ASN_OCTET_STR , RONLY , var_cyrusMasterMIB, 2, { 1,1 } }, #define CYRUSMASTERINFOVERS 2 { CYRUSMASTERINFOVERS , ASN_OCTET_STR , RONLY , var_cyrusMasterMIB, 2, { 1,2 } }, #define CYRUSMASTERINFOUPTIME 3 { CYRUSMASTERINFOUPTIME , ASN_TIMETICKS , RONLY , var_cyrusMasterMIB, 2, { 1,3 } }, #define SERVICEFORKS 5 { SERVICEFORKS , ASN_COUNTER , RONLY , var_serviceTable, 3, { 2,1,1 } }, #define SERVICEACTIVE 6 { SERVICEACTIVE , ASN_GAUGE , RONLY , var_serviceTable, 3, { 2,1,2 } }, #define SERVICENAME 7 { SERVICENAME , ASN_OCTET_STR , RONLY , var_serviceTable, 3, { 2,1,3 } }, #define SERVICEID 8 { SERVICEID , ASN_INTEGER , NOACCESS , var_serviceTable, 3, { 2,1,4 } }, #define SERVICECONNS 9 { SERVICECONNS , ASN_COUNTER , NOACCESS , var_serviceTable, 3, { 2,1,5 } }, }; /* (L = length of the oidsuffix) */ static time_t startTime = 0; /* * init_cyrusMasterMIB(): * Initialization routine. This is called when the agent starts up. * At a minimum, registration of your variables should take place here. */ void init_cyrusMasterMIB(void) { /* register ourselves with the agent to handle our mib tree */ REGISTER_MIB("cyrusMasterMIB", cyrusMasterMIB_variables, variable4, cyrusMasterMIB_variables_oid); /* place any other initialization junk you need here */ if (!startTime) { startTime = time(NULL); } } /* * var_cyrusMasterMIB(): * This function is called every time the agent gets a request for * a scalar variable that might be found within your mib section * registered above. It is up to you to do the right thing and * return the correct value. * You should also correct the value of "var_len" if necessary. * * Please see the documentation for more information about writing * module extensions, and check out the examples in the examples * and mibII directories. */ unsigned char * var_cyrusMasterMIB(struct variable *vp, oid *name, size_t *length, int exact, size_t *var_len, WriteMethod **write_method) { /* variables we may use later */ static long long_ret; static char string[SPRINT_MAX_LEN]; /* static oid objid[MAX_OID_LEN]; */ /* static struct counter64 c64; */ if (header_generic(vp,name,length,exact,var_len,write_method) == MATCH_FAILED ) return NULL; /* * this is where we do the value assignments for the mib results. */ switch(vp->magic) { case CYRUSMASTERINFODESCR: strlcpy(string, "Cyrus IMAP server master process", sizeof(string)); *var_len = strlen(string); return (unsigned char *) string; case CYRUSMASTERINFOVERS: strlcpy(string, _CYRUS_VERSION, sizeof(string)); *var_len = strlen(string); return (unsigned char *) string; case CYRUSMASTERINFOUPTIME: long_ret = 100 * (time(NULL) - startTime); return (unsigned char *) &long_ret; default: ERROR_MSG(""); } return NULL; } /* * var_serviceTable(): * Handle this table separately from the scalar value case. * The workings of this are basically the same as for var_cyrusMasterMIB above. */ unsigned char * var_serviceTable(struct variable *vp, oid *name, size_t *length, int exact, size_t *var_len, WriteMethod **write_method) { /* variables we may use later */ static long long_ret; static char string[SPRINT_MAX_LEN]; /* static oid objid[MAX_OID_LEN]; */ /* static struct counter64 c64; */ int index; /* * This assumes that the table is a 'simple' table. * See the implementation documentation for the meaning of this. * You will need to provide the correct value for the TABLE_SIZE parameter * * If this table does not meet the requirements for a simple table, * you will need to provide the replacement code yourself. * Mib2c is not smart enough to write this for you. * Again, see the implementation documentation for what is required. */ if (header_simple_table(vp,name,length,exact,var_len,write_method, nservices) == MATCH_FAILED ) return NULL; index = name[*length - 1]; /* * this is where we do the value assignments for the mib results. */ switch(vp->magic) { case SERVICEFORKS: long_ret = Services[index - 1].nforks; return (unsigned char *) &long_ret; case SERVICEACTIVE: long_ret = Services[index - 1].nactive; return (unsigned char *) &long_ret; case SERVICENAME: if (Services[index - 1].name != NULL) { strlcpy(string, Services[index - 1].name, sizeof(string)); if (Services[index - 1].family == AF_INET6) { strlcat(string, "[v6]", sizeof(string)); } } else { strlcpy(string, "", sizeof(string)); } *var_len = strlen(string); return (unsigned char *) string; case SERVICEID: long_ret = index; return (unsigned char *) &long_ret; case SERVICECONNS: long_ret = Services[index - 1].nconnections; return (unsigned char *) &long_ret; default: ERROR_MSG(""); } return NULL; } #endif /* HAVE_UCDSNMP || HAVE_NETSNMP */ cyrus-imapd-2.5.10/master/README0000644000175000017500000000177113001236020013121 00000000000000# standard standalone server implementation START { # do not delete this entry! recover cmd="ctl_cyrusdb -r" # this is only necessary if using idled for IMAP IDLE # idled cmd="idled" } # UNIX sockets start with a slash and are absolute paths SERVICES { # add or remove based on preferences imap cmd="imapd" listen="imap" prefork=1 pop3 cmd="pop3d" listen="pop3" prefork=0 # nntp cmd="nntpd" listen="nntp" prefork=0 sieve cmd="timsieved" listen="sieve" prefork=0 # at least one LMTP is required for delivery lmtp cmd="lmtpd" listen="lmtp" prefork=0 # lmtpunix cmd="lmtpd" listen="/lmtp" prefork=0 # this is only necessary if using notifications # notify cmd="notifyd" listen="/notify" proto="udp" prefork=1 } EVENTS { # this is required checkpoint cmd="ctl_cyrusdb -c" period=30 # this is only necessary if using duplicate delivery suppression delprune cmd="ctl_deliver -E 3" at=0400 # this is only necessary if caching TLS sessions tlsprune cmd="tls_prune" at=0400 } cyrus-imapd-2.5.10/master/service.c0000644000175000017500000004366013001236020014050 00000000000000/* service.c -- skeleton for Cyrus service; calls the real main * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include #include #include #include #include #ifdef HAVE_UNISTD_H #include #endif #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include "service.h" #include "libconfig.h" #include "xmalloc.h" #include "xstrlcpy.h" #include "strarray.h" #include "signals.h" #ifndef PATH_MAX #define PATH_MAX 4096 #endif extern int optind, opterr; extern char *optarg; /* number of times this service has been used */ static int use_count = 0; static int verbose = 0; static int lockfd = -1; static int newfile = 0; void notify_master(int fd, int msg) { struct notify_message notifymsg; if (verbose) syslog(LOG_DEBUG, "telling master %x", msg); notifymsg.message = msg; notifymsg.service_pid = getpid(); if (write(fd, ¬ifymsg, sizeof(notifymsg)) != sizeof(notifymsg)) { syslog(LOG_ERR, "unable to tell master %x: %m", msg); } } #ifdef HAVE_LIBWRAP #include int allow_severity = LOG_DEBUG; int deny_severity = LOG_ERR; static void libwrap_init(struct request_info *req, char *service) { request_init(req, RQ_DAEMON, service, 0); } static int libwrap_ask(struct request_info *req, int fd) { struct sockaddr_storage sin_storage; struct sockaddr *sin = (struct sockaddr *)&sin_storage; socklen_t sinlen; int a; /* XXX: old FreeBSD didn't fill sockaddr correctly against AF_UNIX */ sin->sa_family = AF_UNIX; /* is this a connection from the local host? */ sinlen = sizeof(struct sockaddr_storage); if (getpeername(fd, sin, &sinlen) == 0) { if (sin->sa_family == AF_UNIX) { return 1; } } /* i hope using the sock_* functions are legal; it certainly makes this code very easy! */ request_set(req, RQ_FILE, fd, 0); sock_host(req); a = hosts_access(req); if (!a) { syslog(deny_severity, "refused connection from %s", eval_client(req)); } return a; } #else struct request_info { int x; }; static void libwrap_init(struct request_info *r __attribute__((unused)), char *service __attribute__((unused))) { } static int libwrap_ask(struct request_info *r __attribute__((unused)), int fd __attribute__((unused))) { return 1; } #endif extern void cyrus_init(const char *, const char *, unsigned, int); static int getlockfd(char *service, int id) { char lockfile[1024]; int fd; snprintf(lockfile, sizeof(lockfile), "%s/socket/%s-%d.lock", config_dir, service, id); fd = open(lockfile, O_CREAT | O_RDWR, 0600); if (fd < 0) { syslog(LOG_ERR, "locking disabled: couldn't open socket lockfile %s: %m", lockfile); lockfd = -1; return -1; } lockfd = fd; return 0; } static int lockaccept(void) { struct flock alockinfo; int rc; /* setup the alockinfo structure */ alockinfo.l_start = 0; alockinfo.l_len = 0; alockinfo.l_whence = SEEK_SET; if (lockfd != -1) { alockinfo.l_type = F_WRLCK; while ((rc = fcntl(lockfd, F_SETLKW, &alockinfo)) < 0 && errno == EINTR && !signals_poll()) /* noop */; if (rc < 0 && signals_poll()) { if (MESSAGE_MASTER_ON_EXIT) notify_master(STATUS_FD, MASTER_SERVICE_UNAVAILABLE); service_abort(0); return -1; } if (rc < 0) { syslog(LOG_ERR, "fcntl: F_SETLKW: error getting accept lock: %m"); if (MESSAGE_MASTER_ON_EXIT) notify_master(STATUS_FD, MASTER_SERVICE_UNAVAILABLE); service_abort(EX_OSERR); return -1; } } return 0; } static int unlockaccept(void) { struct flock alockinfo; int rc; /* setup the alockinfo structure */ alockinfo.l_start = 0; alockinfo.l_len = 0; alockinfo.l_whence = SEEK_SET; if (lockfd != -1) { alockinfo.l_type = F_UNLCK; while ((rc = fcntl(lockfd, F_SETLKW, &alockinfo)) < 0 && errno == EINTR && !signals_poll()) /* noop */; if (rc < 0) { syslog(LOG_ERR, "fcntl: F_SETLKW: error releasing accept lock: %m"); if (MESSAGE_MASTER_ON_EXIT) notify_master(STATUS_FD, MASTER_SERVICE_UNAVAILABLE); service_abort(EX_OSERR); return -1; } } return 0; } static int safe_wait_readable(int fd) { fd_set rfds; int r; FD_ZERO(&rfds); FD_SET(fd, &rfds); /* Waiting for incoming connection, we want to leave as soon as * possible upon SIGHUP. Julien explains: * * The thing is SIGHUP handler is set as restartable, which is a good thing * when we have received a connection and are processing client commands: * we don't want to be interrupted by that signal. * * On the other hand, when we are waiting to receive a new connection, I * needed a way to make the service instance holding the lock react faster. * Without resetting SIGHUP as not restartable, the instance would just * keep on waiting for a new connection (while the other instances - * waiting for the lock - had received and processed the signal right * away). * * Now that we have safe_wait_readable, Linux systems already react faster * because there select/pselect always returns -1/EINTR even if SA_RESTART * is set. But that may not be the case in other OSes (POSIX spec says it * is implementation-defined whether it does restart or return -1/EINTR * when SA_RESTART is set). */ signals_reset_sighup_handler(0); r = signals_select(fd+1, &rfds, NULL, NULL, NULL); /* we don't want to be interrupted by SIGHUP anymore */ signals_reset_sighup_handler(1); return r; } int main(int argc, char **argv, char **envp) { int fdflags; int fd; char *p = NULL, *service; struct request_info request; int opt; char *alt_config = NULL; int call_debugger = 0; int max_use = MAX_USE; int reuse_timeout = REUSE_TIMEOUT; int soctype; socklen_t typelen = sizeof(soctype); int id; char path[PATH_MAX]; struct stat sbuf; ino_t start_ino; off_t start_size; time_t start_mtime; /* * service_init and service_main need argv and argc, so they can process * service-specific options. They need argv[0] to point into the real argv * memory space, so that setproctitle can work its magic. But they also * need the generic options handled here to be removed, because they don't * know how to handle them. * * So, we create a strarray_t "service_argv", and populate it with the * options that we aren't handling here, using strarray_appendm (which * simply ptr-copies its argument), and pass that through, and everything * is happy. * * Note that we don't need to strarray_free service_argv, because it * doesn't contain any malloced memory. */ strarray_t service_argv = STRARRAY_INITIALIZER; strarray_appendm(&service_argv, argv[0]); opterr = 0; /* disable error reporting, since we don't know about service-specific options */ while ((opt = getopt(argc, argv, "C:U:T:D")) != EOF) { if (argv[optind-1][0] == '-' && strlen(argv[optind-1]) > 2) { /* we have merged options */ syslog(LOG_ERR, "options and arguments MUST be separated by whitespace"); exit(EX_USAGE); } switch (opt) { case 'C': /* alt config file */ alt_config = optarg; break; case 'U': /* maximum uses */ max_use = atoi(optarg); if (max_use < 0) max_use = 0; break; case 'T': /* reuse timeout */ reuse_timeout = atoi(optarg); if (reuse_timeout < 0) reuse_timeout = 0; break; case 'D': call_debugger = 1; break; default: strarray_appendm(&service_argv, argv[optind-1]); /* option has an argument */ if (optind < argc && argv[optind][0] != '-') strarray_appendm(&service_argv, argv[optind++]); break; } } /* grab the remaining arguments */ for (; optind < argc; optind++) strarray_appendm(&service_argv, argv[optind]); opterr = 1; /* enable error reporting */ optind = 1; /* reset the option index for parsing by the service */ p = getenv("CYRUS_VERBOSE"); if (p) verbose = atoi(p) + 1; if (verbose > 30) { syslog(LOG_DEBUG, "waiting 15 seconds for debugger"); sleep(15); } p = getenv("CYRUS_SERVICE"); if (p == NULL) { syslog(LOG_ERR, "could not getenv(CYRUS_SERVICE); exiting"); exit(EX_SOFTWARE); } service = xstrdup(p); p = getenv("CYRUS_ID"); if (p == NULL) { syslog(LOG_ERR, "could not getenv(CYRUS_ID); exiting"); exit(EX_SOFTWARE); } id = atoi(p); srand(time(NULL) * getpid()); /* if timeout is enabled, pick a random timeout between reuse_timeout * and 2*reuse_timeout to avoid massive IO overload if the network * connection goes away */ if (reuse_timeout) reuse_timeout = reuse_timeout + (rand() % reuse_timeout); extern const int config_need_data; cyrus_init(alt_config, service, 0, config_need_data); if (call_debugger) { char debugbuf[1024]; int ret; const char *debugger = config_getstring(IMAPOPT_DEBUG_COMMAND); if (debugger) { snprintf(debugbuf, sizeof(debugbuf), debugger, argv[0], getpid(), service); syslog(LOG_DEBUG, "running external debugger: %s", debugbuf); ret = system(debugbuf); /* run debugger */ syslog(LOG_DEBUG, "debugger returned exit status: %d", ret); } } syslog(LOG_DEBUG, "executed"); /* set close on exec */ fdflags = fcntl(LISTEN_FD, F_GETFD, 0); if (fdflags != -1) fdflags = fcntl(LISTEN_FD, F_SETFD, fdflags | FD_CLOEXEC); if (fdflags == -1) { syslog(LOG_ERR, "unable to set close on exec: %m"); if (MESSAGE_MASTER_ON_EXIT) notify_master(STATUS_FD, MASTER_SERVICE_UNAVAILABLE); return 1; } fdflags = fcntl(STATUS_FD, F_GETFD, 0); if (fdflags != -1) fdflags = fcntl(STATUS_FD, F_SETFD, fdflags | FD_CLOEXEC); if (fdflags == -1) { syslog(LOG_ERR, "unable to set close on exec: %m"); if (MESSAGE_MASTER_ON_EXIT) notify_master(STATUS_FD, MASTER_SERVICE_UNAVAILABLE); return 1; } /* figure out what sort of socket this is */ if (getsockopt(LISTEN_FD, SOL_SOCKET, SO_TYPE, (char *) &soctype, &typelen) < 0) { syslog(LOG_ERR, "getsockopt: SOL_SOCKET: failed to get type: %m"); if (MESSAGE_MASTER_ON_EXIT) notify_master(STATUS_FD, MASTER_SERVICE_UNAVAILABLE); return 1; } if (service_init(service_argv.count, service_argv.data, envp) != 0) { if (MESSAGE_MASTER_ON_EXIT) notify_master(STATUS_FD, MASTER_SERVICE_UNAVAILABLE); return 1; } /* determine initial process file inode, size and mtime */ if (service_argv.data[0][0] == '/') strlcpy(path, service_argv.data[0], sizeof(path)); else snprintf(path, sizeof(path), "%s/%s", SERVICE_DIR, service_argv.data[0]); stat(path, &sbuf); start_ino= sbuf.st_ino; start_size = sbuf.st_size; start_mtime = sbuf.st_mtime; getlockfd(service, id); for (;;) { /* ok, listen to this socket until someone talks to us */ /* (re)set signal handlers, including SIGALRM */ signals_add_handlers(SIGALRM); if (use_count > 0) { /* we want to time out after 60 seconds, set an alarm */ alarm(reuse_timeout); } /* lock */ lockaccept(); fd = -1; while (fd < 0 && !signals_poll()) { /* loop until we succeed */ /* check current process file inode, size and mtime */ int r = stat(path, &sbuf); if (r < 0) { /* This might happen transiently during a package * upgrade or permanently after package removal. * In either case, it's time to die. */ syslog(LOG_INFO, "cannot stat process file: %m"); break; } if (sbuf.st_ino != start_ino || sbuf.st_size != start_size || sbuf.st_mtime != start_mtime) { syslog(LOG_INFO, "process file has changed"); newfile = 1; break; } if (soctype == SOCK_STREAM) { /* Wait for the file descriptor to be connected to, in a * signal-safe manner. This ensures the accept() does * not block and we don't need to make it signal-safe. */ if (safe_wait_readable(LISTEN_FD) < 0) continue; fd = accept(LISTEN_FD, NULL, NULL); if (fd < 0) { switch (errno) { case EINTR: signals_poll(); case ENETDOWN: #ifdef EPROTO case EPROTO: #endif case ENOPROTOOPT: case EHOSTDOWN: #ifdef ENONET case ENONET: #endif case EHOSTUNREACH: case EOPNOTSUPP: case ENETUNREACH: case EAGAIN: break; case EINVAL: if (signals_poll() == SIGHUP) break; default: syslog(LOG_ERR, "accept failed: %m"); if (MESSAGE_MASTER_ON_EXIT) notify_master(STATUS_FD, MASTER_SERVICE_UNAVAILABLE); service_abort(EX_OSERR); } } } else { /* udp */ struct sockaddr_storage from; socklen_t fromlen; char ch; int r; if (safe_wait_readable(LISTEN_FD) < 0) continue; fromlen = sizeof(from); r = recvfrom(LISTEN_FD, (void *) &ch, 1, MSG_PEEK, (struct sockaddr *) &from, &fromlen); if (r == -1) { if (signals_poll() == SIGHUP) break; syslog(LOG_ERR, "recvfrom failed: %m"); if (MESSAGE_MASTER_ON_EXIT) notify_master(STATUS_FD, MASTER_SERVICE_UNAVAILABLE); service_abort(EX_OSERR); } fd = LISTEN_FD; } } /* unlock */ unlockaccept(); if (fd < 0 && (signals_poll() || newfile)) { /* timed out (SIGALRM), SIGHUP, or new process file */ if (MESSAGE_MASTER_ON_EXIT) notify_master(STATUS_FD, MASTER_SERVICE_UNAVAILABLE); service_abort(0); } if (fd < 0) { /* how did this happen? - we might have caught a signal. */ syslog(LOG_ERR, "accept() failed but we didn't catch it?"); if (MESSAGE_MASTER_ON_EXIT) notify_master(STATUS_FD, MASTER_SERVICE_UNAVAILABLE); service_abort(EX_SOFTWARE); } /* cancel the alarm */ alarm(0); /* tcp only */ if(soctype == SOCK_STREAM) { libwrap_init(&request, service); if (!libwrap_ask(&request, fd)) { /* connection denied! */ shutdown(fd, SHUT_RDWR); close(fd); continue; } /* turn on TCP keepalive if set */ if (config_getswitch(IMAPOPT_TCP_KEEPALIVE)) { int r; int optval = 1; socklen_t optlen = sizeof(optval); struct protoent *proto = getprotobyname("TCP"); r = setsockopt(fd, SOL_SOCKET, SO_KEEPALIVE, &optval, optlen); if (r < 0) { syslog(LOG_ERR, "unable to setsocketopt(SO_KEEPALIVE): %m"); } #ifdef TCP_KEEPCNT optval = config_getint(IMAPOPT_TCP_KEEPALIVE_CNT); if (optval) { r = setsockopt(fd, proto->p_proto, TCP_KEEPCNT, &optval, optlen); if (r < 0) { syslog(LOG_ERR, "unable to setsocketopt(TCP_KEEPCNT): %m"); } } #endif #ifdef TCP_KEEPIDLE optval = config_getint(IMAPOPT_TCP_KEEPALIVE_IDLE); if (optval) { r = setsockopt(fd, proto->p_proto, TCP_KEEPIDLE, &optval, optlen); if (r < 0) { syslog(LOG_ERR, "unable to setsocketopt(TCP_KEEPIDLE): %m"); } } #endif #ifdef TCP_KEEPINTVL optval = config_getint(IMAPOPT_TCP_KEEPALIVE_INTVL); if (optval) { r = setsockopt(fd, proto->p_proto, TCP_KEEPINTVL, &optval, optlen); if (r < 0) { syslog(LOG_ERR, "unable to setsocketopt(TCP_KEEPINTVL): %m"); } } #endif } } notify_master(STATUS_FD, MASTER_SERVICE_UNAVAILABLE); syslog(LOG_DEBUG, "accepted connection"); if (fd != 0 && dup2(fd, 0) < 0) { syslog(LOG_ERR, "can't duplicate accepted socket: %m"); service_abort(EX_OSERR); } if (fd != 1 && dup2(fd, 1) < 0) { syslog(LOG_ERR, "can't duplicate accepted socket: %m"); service_abort(EX_OSERR); } if (fd != 2 && dup2(fd, 2) < 0) { syslog(LOG_ERR, "can't duplicate accepted socket: %m"); service_abort(EX_OSERR); } /* tcp only */ if(soctype == SOCK_STREAM) { if (fd > 2) close(fd); } notify_master(STATUS_FD, MASTER_SERVICE_CONNECTION); use_count++; service_main(service_argv.count, service_argv.data, envp); /* if we returned, we can service another client with this process */ if (signals_poll() || use_count >= max_use) { /* caught SIGHUP or exceeded max use count */ break; } notify_master(STATUS_FD, MASTER_SERVICE_AVAILABLE); } service_abort(0); return 0; } cyrus-imapd-2.5.10/master/service-thread.c0000644000175000017500000002153313001236020015310 00000000000000/* service-thread.c -- skeleton for Cyrus service; calls the real main * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include #include #include #include #include #ifdef HAVE_UNISTD_H #include #endif #include #include #include #include #include #include #include #include #include #include #include #include #include #include "service.h" #include "libconfig.h" #include "xmalloc.h" #include "strarray.h" #include "signals.h" extern int optind; extern char *optarg; /* number of times this service has been used */ static int use_count = 0; static int verbose = 0; void notify_master(int fd, int msg) { struct notify_message notifymsg; if (verbose) syslog(LOG_DEBUG, "telling master %x", msg); notifymsg.message = msg; notifymsg.service_pid = getpid(); if (write(fd, ¬ifymsg, sizeof(notifymsg)) != sizeof(notifymsg)) { syslog(LOG_ERR, "unable to tell master %x: %m", msg); } } #ifdef HAVE_LIBWRAP #include int allow_severity = LOG_DEBUG; int deny_severity = LOG_ERR; static void libwrap_init(struct request_info *req, char *service) { request_init(req, RQ_DAEMON, service, 0); } static int libwrap_ask(struct request_info *req, int fd) { struct sockaddr_storage sin_storage; struct sockaddr *sin = (struct sockaddr *)&sin_storage; socklen_t sinlen; int a; /* XXX: old FreeBSD didn't fill sockaddr correctly against AF_UNIX */ sin->sa_family = AF_UNIX; /* is this a connection from the local host? */ sinlen = sizeof(struct sockaddr_storage); if (getpeername(fd, sin, &sinlen) == 0) { if (sin->sa_family == AF_UNIX) { return 1; } } /* i hope using the sock_* functions are legal; it certainly makes this code very easy! */ request_set(req, RQ_FILE, fd, 0); sock_host(req); a = hosts_access(req); if (!a) { syslog(deny_severity, "refused connection from %s", eval_client(req)); } return a; } #else struct request_info { int x; }; static void libwrap_init(struct request_info *r __attribute__((unused)), char *service __attribute__((unused))) { } static int libwrap_ask(struct request_info *r __attribute__((unused)), int fd __attribute__((unused))) { return 1; } #endif extern void cyrus_init(const char *, const char *, unsigned, int); int main(int argc, char **argv, char **envp) { int fdflags; int fd; char *p = NULL, *service; struct request_info request; int opt; char *alt_config = NULL; int call_debugger = 0; /* * service_init and service_main need argv and argc, so they can process * service-specific options. They need argv[0] to point into the real argv * memory space, so that setproctitle can work its magic. But they also * need the generic options handled here to be removed, because they don't * know how to handle them. * * So, we create a strarray_t "service_argv", and populate it with the * options that we aren't handling here, using strarray_appendm (which * simply ptr-copies its argument), and pass that through, and everything * is happy. * * Note that we don't need to strarray_free service_argv, because it * doesn't contain any malloced memory. */ strarray_t service_argv = STRARRAY_INITIALIZER; strarray_appendm(&service_argv, argv[0]); opterr = 0; /* disable error reporting, since we don't know about service-specific options */ while ((opt = getopt(argc, argv, "C:D")) != EOF) { switch (opt) { case 'C': /* alt config file */ alt_config = optarg; break; case 'D': call_debugger = 1; break; default: strarray_appendm(&service_argv, argv[optind-1]); /* option has an argument */ if (optind < argc && argv[optind][0] != '-') strarray_appendm(&service_argv, argv[optind++]); break; } } /* grab the remaining arguments */ for (; optind < argc; optind++) strarray_appendm(&service_argv, argv[optind]); opterr = 1; /* enable error reporting */ optind = 1; /* reset the option index for parsing by the service */ p = getenv("CYRUS_VERBOSE"); if (p) verbose = atoi(p) + 1; if (verbose > 30) { syslog(LOG_DEBUG, "waiting 15 seconds for debugger"); sleep(15); } p = getenv("CYRUS_SERVICE"); if (p == NULL) { syslog(LOG_ERR, "could not getenv(CYRUS_SERVICE); exiting"); exit(EX_SOFTWARE); } service = xstrdup(p); extern const int config_need_data; cyrus_init(alt_config, service, 0, config_need_data); if (call_debugger) { char debugbuf[1024]; int ret; const char *debugger = config_getstring(IMAPOPT_DEBUG_COMMAND); if (debugger) { snprintf(debugbuf, sizeof(debugbuf), debugger, argv[0], getpid(), service); syslog(LOG_DEBUG, "running external debugger: %s", debugbuf); ret = system(debugbuf); /* run debugger */ syslog(LOG_DEBUG, "debugger returned exit status: %d", ret); } } syslog(LOG_DEBUG, "executed"); /* set close on exec */ fdflags = fcntl(LISTEN_FD, F_GETFD, 0); if (fdflags != -1) fdflags = fcntl(LISTEN_FD, F_SETFD, fdflags | FD_CLOEXEC); if (fdflags == -1) { syslog(LOG_ERR, "unable to set close on exec: %m"); if (MESSAGE_MASTER_ON_EXIT) notify_master(STATUS_FD, MASTER_SERVICE_UNAVAILABLE); return 1; } fdflags = fcntl(STATUS_FD, F_GETFD, 0); if (fdflags != -1) fdflags = fcntl(STATUS_FD, F_SETFD, fdflags | FD_CLOEXEC); if (fdflags == -1) { syslog(LOG_ERR, "unable to set close on exec: %m"); if (MESSAGE_MASTER_ON_EXIT) notify_master(STATUS_FD, MASTER_SERVICE_UNAVAILABLE); return 1; } if (service_init(service_argv.count, service_argv.data, envp) != 0) { if (MESSAGE_MASTER_ON_EXIT) notify_master(STATUS_FD, MASTER_SERVICE_UNAVAILABLE); return 1; } for (;;) { /* ok, listen to this socket until someone talks to us */ fd = -1; while (fd < 0) { /* loop until we succeed */ fd = accept(LISTEN_FD, NULL, NULL); if (fd < 0) { switch (errno) { case EINTR: signals_poll(); case ENETDOWN: #ifdef EPROTO case EPROTO: #endif case ENOPROTOOPT: case EHOSTDOWN: #ifdef ENONET case ENONET: #endif case EHOSTUNREACH: case EOPNOTSUPP: case ENETUNREACH: case EAGAIN: case ECONNABORTED: break; default: syslog(LOG_ERR, "accept failed: %m"); if (MESSAGE_MASTER_ON_EXIT) notify_master(STATUS_FD, MASTER_SERVICE_UNAVAILABLE); service_abort(EX_OSERR); } } } libwrap_init(&request, getenv("CYRUS_SERVICE")); if (!libwrap_ask(&request, fd)) { /* connection denied! */ shutdown(fd, SHUT_RDWR); close(fd); continue; } syslog(LOG_DEBUG, "accepted connection"); use_count++; notify_master(STATUS_FD, MASTER_SERVICE_CONNECTION_MULTI); if (service_main_fd(fd, service_argv.count, service_argv.data, envp) < 0) { break; } } if (MESSAGE_MASTER_ON_EXIT) notify_master(STATUS_FD, MASTER_SERVICE_UNAVAILABLE); service_abort(0); return 0; } cyrus-imapd-2.5.10/master/master.h0000644000175000017500000000613413001236020013703 00000000000000#ifndef HAVE_MASTER_H #define HAVE_MASTER_H #include #include /* for rlim_t */ #include "libconfig.h" /* for config_dir and IMAPOPT_SYNC_MACHINEID */ #include "strarray.h" /* needed for possible SNMP monitoring */ struct service { char *name; /* name of service */ char *listen; /* port/socket to listen to */ char *proto; /* protocol to accept */ strarray_t *exec; /* command (with args) to execute */ int babysit; /* babysit this service? */ /* multiple address family support */ int associate; /* are we primary or additional instance? */ int family; /* address family */ const char *familyname; /* address family name */ /* communication info */ int socket; /* client/child communication channel */ int stat[2]; /* master/child communication channel */ /* limits */ int desired_workers; /* num child processes to have ready */ int max_workers; /* max num child processes to spawn */ rlim_t maxfds; /* max num file descriptors to use */ unsigned int maxforkrate; /* max rate to spawn children */ /* stats */ int ready_workers; /* num child processes ready for service */ int nforks; /* num child processes spawned */ int nactive; /* num children servicing clients */ int nconnections; /* num connections made to children */ double forkrate; /* rate at which we're spawning children */ int nreadyfails; /* number of failures in READY state */ /* fork rate computation */ struct timeval last_interval_start; unsigned int interval_forks; }; extern struct service *Services; extern int nservices; /* * Description of multiple address family support from * Hajimu UMEMOTO : * * In service_create(), master tries to listen each address family which * getaddrinfo() returns. With existing implementation of getaddrinfo(), * when a protocol is not specified exactly by proto= in cyrus.conf and a * platform supports an IPv4 and an IPv6, getaddrinfo() returns two * struct addrinfo chain which contain INADDR_ANY (0.0.0.0; IPv4) and * IN6ADDR_ANY (::; IPv6), then master will listen an IPv4 and an IPv6. * * As a result, one SERVICE entry in cyrus.conf may correspond to two * Service memory blocks; one is for an IPv6 and the other is for an * IPv4. The associate field was introduced to intend to distinguish * whether the entry is primary or not. The associate field of primary * block is 0, 2nd is 1, 3rd is 2, ... * The blocks share same memory area of name, listen and proto. * * +----------------+ * | Service[i] | * | associate: 0 | * | name | --------------> name * | listen | ----- /- -----> listen * | proto | ---- /- / ----> proto * +----------------+ / / / * | Service[j] | / / / * | associate: 1 | / / / * | name |--/ / / * | listen |----/ / * | proto |-----/ * +----------------+ * * This field is intended to avoid duplicate free by doing free only when * associate is zero. * */ #endif /* HAVE_MASTER_H */ cyrus-imapd-2.5.10/master/masterconf.h0000644000175000017500000000530113001236020014544 00000000000000/* config.h -- Configuration routines * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #ifndef INCLUDED_MASTERCONF_H #define INCLUDED_MASTERCONF_H extern int masterconf_init(const char *ident, const char *alt_config); struct entry; extern const char *masterconf_getstring(struct entry *e, const char *key, const char *def); extern int masterconf_getint(struct entry *e, const char *key, int def); extern int masterconf_getswitch(struct entry *e, const char *key, int def); /* entry values are good until the next call */ typedef void masterconf_process(const char *name, struct entry *e, void *rock); extern void masterconf_getsection(const char *section, masterconf_process *f, void *rock); /* fatalf() is like fatal() but takes a printf-like * format string which goes to syslog(). */ extern void fatalf(int code, const char *fmt, ...) __attribute__ ((format (printf, 2, 3))) __attribute__((noreturn)); #endif /* INCLUDED_MASTERCONF_H */ cyrus-imapd-2.5.10/master/CYRUS-MASTER.mib0000644000175000017500000001133113001236020014621 00000000000000CYRUS-MASTER-MIB DEFINITIONS ::= BEGIN IMPORTS MODULE-IDENTITY, OBJECT-TYPE, Counter32 FROM SNMPv2-SMI DisplayString FROM SNMPv2-TC cmuCyrus FROM CMU-MIB; cyrusMasterMIB MODULE-IDENTITY LAST-UPDATED "0010312300Z" -- 2000 Oct 31 ORGANIZATION "CMU Project Cyrus" CONTACT-INFO " Email: cyrus-bugs@andrew.cmu.edu Project Cyrus Computing Services Carnegie Mellon University Pittsburgh PA. 15213 " DESCRIPTION "A simple MIB for application status of the Cyrus master process. " ::= { cmuCyrus 1 } -- cmuCyrus = .1.3.6.1.4.1.3.6 -- cyrusMasterMIB = .1.3.6.1.4.1.3.6.1 -- general information cyrusMasterInfo OBJECT IDENTIFIER ::= { cyrusMasterMIB 1 } -- version information cyrusMasterInfoDescr OBJECT-TYPE SYNTAX DisplayString (SIZE (0..255)) ACCESS read-only STATUS mandatory DESCRIPTION "A general textual description of the Cyrus server." ::= { cyrusMasterInfo 1 } cyrusMasterInfoVers OBJECT-TYPE SYNTAX DisplayString (SIZE (0..255)) ACCESS read-only STATUS mandatory DESCRIPTION "The version of the Cyrus server." ::= { cyrusMasterInfo 2 } cyrusMasterInfoUptime OBJECT-TYPE SYNTAX TimeTicks ACCESS read-only STATUS current DESCRIPTION "The amount of time since the master process was last started." ::= { cyrusMasterInfo 3 } -- service table serviceTable OBJECT-TYPE SYNTAX SEQUENCE OF serviceEntry ACCESS not-accessible STATUS mandatory ::= { cyrusMasterMIB 2 } serviceEntry OBJECT-TYPE SYNTAX ServiceEntry ACCESS not-accessible STATUS mandatory INDEX { serviceId } ::= { serviceTable 1 } ServiceEntry ::= SEQUENCE { serviceForks Counter32, serviceActive Gauge32, serviceName DisplayString (SIZE (0..255)), serviceId INTEGER, serviceConnections Counter32 } -- forks since startup serviceForks OBJECT-TYPE SYNTAX Counter32 ACCESS read-only STATUS mandatory DESCRIPTION "The total number of forks for this service since initialization." ::= { serviceEntry 1 } -- active children serviceActive OBJECT-TYPE SYNTAX Gauge32 ACCESS read-only STATUS mandatory DESCRIPTION "The total number of children currently active." ::= { serviceEntry 2 } serviceName OBJECT-TYPE SYNTAX DisplayString (SIZE (0..255)) ACCESS read-only STATUS mandatory DESCRIPTION "The name of this service." ::= { serviceEntry 3 } serviceId OBJECT-TYPE SYNTAX INTEGER ACCESS not-accessible STATUS mandatory DESCRIPTION "The id of the service as configured." ::= { serviceEntry 4 } -- connections since startup serviceConnections OBJECT-TYPE SYNTAX Counter32 ACCESS read-only STATUS mandatory DESCRIPTION "The total number of connections for this service since initialization." ::= { serviceEntry 5 } -- event table -- eventTable OBJECT-TYPE -- SYNTAX SEQUENCE OF eventEntry -- ACCESS not-accessible -- STATUS mandatory -- ::= { cyrusMasterMIB 3 } END cyrus-imapd-2.5.10/master/masterconf.c0000644000175000017500000002012713001236020014542 00000000000000/* masterconfig.c -- Configuration routines for master process * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include #include #include #include #include #include #include #include #include "util.h" #include "libconfig.h" #include "xmalloc.h" #include "xstrlcat.h" #include "xstrlcpy.h" #if HAVE_UNISTD_H # include #endif #include "masterconf.h" extern const char *MASTER_CONFIG_FILENAME; struct configlist { char *key; char *value; }; extern void fatal(const char *buf, int code) __attribute__((noreturn)); void fatalf(int code, const char *fmt, ...) { va_list args; char buf[2048]; va_start(args, fmt); vsnprintf(buf, sizeof(buf), fmt, args); va_end(args); fatal(buf, code); } int masterconf_init(const char *ident, const char *alt_config) { char *buf; const char *prefix; /* Open the log file with the appropriate facility so we * correctly log any config errors */ openlog(ident, LOG_PID, SYSLOG_FACILITY); config_ident = ident; config_read(alt_config, 0); prefix = config_getstring(IMAPOPT_SYSLOG_PREFIX); if (prefix) { int size = strlen(prefix) + 1 + strlen(ident) + 1; buf = xmalloc(size); strlcpy(buf, prefix, size); strlcat(buf, "/", size); strlcat(buf, ident, size); /* Reopen the log with the new prefix */ closelog(); openlog(buf, LOG_PID, SYSLOG_FACILITY); /* don't free the openlog() string! */ } else { closelog(); openlog(ident, LOG_PID, SYSLOG_FACILITY); } /* drop debug messages locally */ if (!config_debug) setlogmask(~LOG_MASK(LOG_DEBUG)); return 0; } struct entry { #define MAXARGS 64 int nargs; struct { char *key; char *value; } args[MAXARGS]; int lineno; }; const char *masterconf_getstring(struct entry *e, const char *key, const char *def) { int i; for (i = 0 ; i < e->nargs ; i++) { if (!strcmp(key, e->args[i].key)) return e->args[i].value; } return def; } int masterconf_getint(struct entry *e, const char *key, int def) { const char *val = masterconf_getstring(e, key, NULL); if (!val) return def; if (!Uisdigit(*val) && (*val != '-' || !Uisdigit(val[1]))) { syslog(LOG_DEBUG, "value '%s' for '%s' does not look like a number.", val, key); return def; } return atoi(val); } int masterconf_getswitch(struct entry *e, const char *key, int def) { const char *val = masterconf_getstring(e, key, NULL); if (!val) return def; if (val[0] == '0' || val[0] == 'n' || (val[0] == 'o' && val[1] == 'f') || val[0] == 'f') { return 0; } else if (val[0] == '1' || val[0] == 'y' || (val[0] == 'o' && val[1] == 'n') || val[0] == 't') { return 1; } syslog(LOG_DEBUG, "cannot interpret value '%s' for key '%s'. use y/n.", val, key); return def; } static void split_args(struct entry *e, char *buf) { char *p = buf, *q; char *key, *value; for (;;) { /* skip whitespace before arg */ while (Uisspace(*p)) p++; if (!*p) return; key = p; /* parse the key */ for (q = p ; Uisalnum(*q) ; q++) ; if (*q != '=') fatalf(EX_CONFIG, "configuration file %s: " "bad character '%c' in argument on line %d", MASTER_CONFIG_FILENAME, *q, e->lineno); *q++ = '\0'; /* parse the value */ if (*q == '"') { /* quoted string */ value = ++q; q = strchr(q, '"'); if (!q) fatalf(EX_CONFIG, "configuration file %s: missing \" on line %d", MASTER_CONFIG_FILENAME, e->lineno); *q++ = '\0'; } else { /* simple word */ value = q; while (*q && !Uisspace(*q)) q++; if (*q) *q++ = '\0'; } if (e->nargs == MAXARGS) fatalf(EX_CONFIG, "configuration file %s: too many arguments on line %d", MASTER_CONFIG_FILENAME, e->lineno); e->args[e->nargs].key = key; e->args[e->nargs].value = value; e->nargs++; p = q; } } static void process_section(FILE *f, int *lnptr, masterconf_process *func, void *rock) { struct entry e; char buf[4096]; int lineno = *lnptr; while (fgets(buf, sizeof(buf), f)) { char *p, *q; lineno++; /* remove EOL character */ if (buf[strlen(buf)-1] == '\n') buf[strlen(buf)-1] = '\0'; /* remove starting whitespace */ for (p = buf; *p && Uisspace(*p); p++); /* remove comments */ q = strchr(p, '#'); if (q) *q = '\0'; /* skip empty lines or all comment lines */ if (!*p) continue; if (*p == '}') break; for (q = p; Uisalnum(*q); q++) ; if (*q) { if (q > p && !Uisspace(*q)) fatalf(EX_CONFIG, "configuration file %s: " "bad character '%c' in name on line %d", MASTER_CONFIG_FILENAME, *q, lineno); *q++ = '\0'; } if (q - p > 0) { /* there's a value on this line */ memset(&e, 0, sizeof(e)); e.lineno = lineno; split_args(&e, q); func(p, &e, rock); } /* end of section? */ if (strchr(q, '}')) break; } *lnptr = lineno; } void masterconf_getsection(const char *section, masterconf_process *f, void *rock) { FILE *infile = NULL; int seclen = strlen(section); int level = 0; int lineno = 0; char buf[4096]; const char *cyrus_path; /* try loading the copy inside CYRUS_PREFIX first */ cyrus_path = getenv("CYRUS_PREFIX"); if (cyrus_path) { strlcpy(buf, cyrus_path, sizeof(buf)); strlcat(buf, MASTER_CONFIG_FILENAME, sizeof(buf)); infile = fopen(buf, "r"); } if (!infile) infile = fopen(MASTER_CONFIG_FILENAME, "r"); if (!infile) fatalf(EX_CONFIG, "can't open configuration file %s: %m", MASTER_CONFIG_FILENAME); while (fgets(buf, sizeof(buf), infile)) { char *p, *q; lineno++; if (buf[strlen(buf)-1] == '\n') buf[strlen(buf)-1] = '\0'; for (p = buf; *p && Uisspace(*p); p++); /* remove comments */ q = strchr(p, '#'); if (q) *q = '\0'; /* skip empty lines or all comment lines */ if (!*p) continue; if (level == 0 && *p == *section && !strncasecmp(p, section, seclen) && !Uisalnum(p[seclen])) { for (p += seclen; *p; p++) { if (*p == '{') level++; if (*p == '}') level--; } /* valid opening; process the section */ if (level == 1) process_section(infile, &lineno, f, rock); continue; } for (; *p; p++) { if (*p == '{') level++; if (*p == '}') level--; } } fclose(infile); } cyrus-imapd-2.5.10/master/conf/0000755000175000017500000000000013001246664013257 500000000000000cyrus-imapd-2.5.10/master/conf/small.conf0000644000175000017500000000202613001236020015137 00000000000000# standard standalone server implementation START { # do not delete this entry! recover cmd="ctl_cyrusdb -r" # this is only necessary if using idled for IMAP IDLE # idled cmd="idled" } # UNIX sockets start with a slash and are put into /var/imap/sockets SERVICES { # add or remove based on preferences imap cmd="imapd" listen="imap" prefork=0 pop3 cmd="pop3d" listen="pop3" prefork=0 # LMTP is required for delivery lmtpunix cmd="lmtpd" listen="/var/imap/socket/lmtp" prefork=0 # this is only necessary if using notifications # notify cmd="notifyd" listen="/var/imap/socket/notify" proto="udp" prefork=1 } EVENTS { # this is required checkpoint cmd="ctl_cyrusdb -c" period=30 # this is only necessary if using duplicate delivery suppression delprune cmd="ctl_deliver -E 3" at=0400 # Expire data older than 28 days. deleteprune cmd="cyr_expire -E 4 -D 28" at=0430 expungeprune cmd="cyr_expire -E 4 -X 28" at=0445 # this is only necessary if caching TLS sessions tlsprune cmd="tls_prune" at=0400 } cyrus-imapd-2.5.10/master/conf/normal.conf0000644000175000017500000000307213001236020015321 00000000000000# standard standalone server implementation START { # do not delete this entry! recover cmd="ctl_cyrusdb -r" # this is only necessary if using idled for IMAP IDLE # idled cmd="idled" } # UNIX sockets start with a slash and are put into /var/imap/socket SERVICES { # add or remove based on preferences imap cmd="imapd" listen="imap" prefork=0 imaps cmd="imapd -s" listen="imaps" prefork=0 pop3 cmd="pop3d" listen="pop3" prefork=0 pop3s cmd="pop3d -s" listen="pop3s" prefork=0 sieve cmd="timsieved" listen="sieve" prefork=0 # these are only necessary if receiving/exporting usenet via NNTP # nntp cmd="nntpd" listen="nntp" prefork=0 # nntps cmd="nntpd -s" listen="nntps" prefork=0 # these are only necessary if using HTTP for CalDAV, CardDAV, or RSS # http cmd="httpd" listen="http" prefork=0 # https cmd="httpd -s" listen="https" prefork=0 # at least one LMTP is required for delivery # lmtp cmd="lmtpd" listen="lmtp" prefork=0 lmtpunix cmd="lmtpd" listen="/var/imap/socket/lmtp" prefork=0 # this is required if using notifications # notify cmd="notifyd" listen="/var/imap/socket/notify" proto="udp" prefork=1 } EVENTS { # this is required checkpoint cmd="ctl_cyrusdb -c" period=30 # this is only necessary if using duplicate delivery suppression, # Sieve or NNTP delprune cmd="cyr_expire -E 3" at=0400 # Expire data older than 28 days. deleteprune cmd="cyr_expire -E 4 -D 28" at=0430 expungeprune cmd="cyr_expire -E 4 -X 28" at=0445 # this is only necessary if caching TLS sessions tlsprune cmd="tls_prune" at=0400 } cyrus-imapd-2.5.10/master/conf/cmu-backend.conf0000644000175000017500000000305113001236020016177 00000000000000# xxx where is ptloader? # xxx is this how we actually are doing auth? afs tokens? START { auth cmd="/usr/local/bin/ksrvtgt -l 3600 imap @SHORTHOST@ ANDREW.CMU.EDU /imap/conf/srvtab" recover cmd="ctl_cyrusdb -r" mupdatepush cmd="ctl_mboxlist -m" } # UNIX sockets start with a slash and are put into /var/imap/sockets SERVICES { # add or remove based on preferences imap cmd="imapd" listen="imap" prefork=5 imaps cmd="imapd -s" listen="imaps" prefork=1 pop3 cmd="pop3d" listen="pop3" prefork=0 pop3s cmd="pop3d -s" listen="pop3s" prefork=0 kpop cmd="pop3d -k" listen="kpop" prefork=0 sieve cmd="timsieved" listen="sieve" prefork=0 # fud fud cmd="fud" listen="fud" prefork=1 proto="udp" notifyd cmd="notifyd" listen="/imap/conf/socket/notifyd" proto="udp" prefork=1 # at least one LMTP is required for delivery lmtp cmd="lmtpd" listen="lmtp" prefork=2 lmtpunix cmd="lmtpd" listen="/imap/conf/socket/lmtp" prefork=0 # ptloading ptloader cmd="ptloader" listen="/imap/conf/ptclient/ptsock" prefork=1 } EVENTS { # this is required checkpoint cmd="ctl_cyrusdb -c" period=5 # this is only necessary if using duplicate delivery suppression delprune cmd="ctl_deliver -E 3" at=0400 # Expire data older than 28 days. deleteprune cmd="cyr_expire -E 4 -D 28" at=0430 expungeprune cmd="cyr_expire -E 4 -X 28" at=0445 # this is only necessary if caching TLS sessions tlsprune cmd="tls_prune" at=0400 reauth cmd="/usr/local/bin/ksrvtgt -l 3600 imap @SHORTHOST@ ANDREW.CMU.EDU /imap/conf/srvtab" period=30 } cyrus-imapd-2.5.10/master/conf/cmu-frontend.conf0000644000175000017500000000216013001236020016427 00000000000000START { auth cmd="/usr/local/bin/ksrvtgt -l 3600 imap @SHORTHOST@ ANDREW.CMU.EDU /imap/conf/srvtab" mboxlist cmd="ctl_cyrusdb -r" } # UNIX sockets start with a slash and are put into /var/imap/sockets SERVICES { # mupdate database service - must prefork atleast 1 mupdate cmd="/usr/cyrus/bin/mupdate" listen=2004 prefork=1 # add or remove based on preferences imap cmd="proxyd" listen="imap" prefork=5 imaps cmd="proxyd -s" listen="imaps" prefork=1 pop3 cmd="pop3d" listen="pop3" prefork=0 pop3s cmd="pop3d -s" listen="pop3s" prefork=0 kpop cmd="pop3d -k" listen="kpop" prefork=0 sieve cmd="timsieved" listen="sieve" prefork=0 # fud fud cmd="fud" listen="fud" prefork=1 proto="udp" # relay mail correctly lmtpunix cmd="lmtpproxyd" listen="/imap/conf/socket/lmtpproxy" prefork=1 # ptloading ptloader cmd="ptloader" listen="/imap/conf/ptclient/ptsock" prefork=1 } EVENTS { # this is required checkpoint cmd="ctl_cyrusdb -c" period=5 reauth cmd="/usr/local/bin/ksrvtgt -l 3600 imap @SHORTHOST@ ANDREW.CMU.EDU /imap/conf/srvtab" period=30 } cyrus-imapd-2.5.10/master/conf/prefork.conf0000644000175000017500000000310113001236020015472 00000000000000# standard standalone server implementation START { # do not delete this entry! recover cmd="ctl_cyrusdb -r" # this is only necessary if using idled for IMAP IDLE # idled cmd="idled" } # UNIX sockets start with a slash and are put into /var/imap/sockets SERVICES { # add or remove based on preferences imap cmd="imapd" listen="imap" prefork=5 imaps cmd="imapd -s" listen="imaps" prefork=1 pop3 cmd="pop3d" listen="pop3" prefork=3 pop3s cmd="pop3d -s" listen="pop3s" prefork=1 sieve cmd="timsieved" listen="sieve" prefork=0 # these are only necessary if receiving/exporting usenet via NNTP # nntp cmd="nntpd" listen="nntp" prefork=3 # nntps cmd="nntpd -s" listen="nntps" prefork=1 # these are only necessary if using HTTP for CalDAV, CardDAV, or RSS # http cmd="httpd" listen="http" prefork=3 # https cmd="httpd -s" listen="https" prefork=1 # at least one LMTP is required for delivery # lmtp cmd="lmtpd" listen="lmtp" prefork=0 lmtpunix cmd="lmtpd" listen="/var/imap/socket/lmtp" prefork=1 # this is only necessary if using notifications # notify cmd="notifyd" listen="/var/imap/socket/notify" proto="udp" prefork=1 } EVENTS { # this is required checkpoint cmd="ctl_cyrusdb -c" period=30 # this is only necessary if using duplicate delivery suppression, # Sieve or NNTP delprune cmd="cyr_expire -E 3" at=0400 # Expire data older than 28 days. deleteprune cmd="cyr_expire -E 4 -D 28" at=0430 expungeprune cmd="cyr_expire -E 4 -X 28" at=0445 # this is only necessary if caching TLS sessions tlsprune cmd="tls_prune" at=0400 } cyrus-imapd-2.5.10/master/master.c0000644000175000017500000020622713001236020013703 00000000000000/* master.c -- IMAP master process to handle recovery, checkpointing, spawning * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include #include #include #include #include #include #include #include #ifdef HAVE_UNISTD_H #include #endif #ifdef HAVE_SYS_RESOURCE_H #include #endif #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #ifndef PATH_MAX #define PATH_MAX 4096 #endif #ifndef INADDR_NONE #define INADDR_NONE 0xffffffff #endif #ifndef INADDR_ANY #define INADDR_ANY 0x00000000 #endif #if !defined(IPV6_V6ONLY) && defined(IPV6_BINDV6ONLY) #define IPV6_V6ONLY IPV6_BINDV6ONLY #endif #if defined(HAVE_NETSNMP) #include #include #include #if defined(HAVE_NET_SNMP_AGENT_AGENT_MODULE_CONFIG_H) #include #endif #include "cyrusMasterMIB.h" /* Use our own definitions for these */ #undef TOUPPER #undef TOLOWER #elif defined(HAVE_UCDSNMP) #include #include #include #include "cyrusMasterMIB.h" int allow_severity = LOG_DEBUG; int deny_severity = LOG_ERR; #endif #include "masterconf.h" #include "master.h" #include "service.h" #include "cyr_lock.h" #include "util.h" #include "xmalloc.h" #include "strarray.h" enum { child_table_size = 10000, child_table_inc = 100 }; static int verbose = 0; static int listen_queue_backlog = 32; static int pidfd = -1; static int in_shutdown = 0; const char *MASTER_CONFIG_FILENAME = DEFAULT_MASTER_CONFIG_FILENAME; #define SERVICE_NONE -1 #define SERVICE_MAX INT_MAX-10 #define SERVICEPARAM(x) ((x) ? x : "unknown") #define MAX_READY_FAILS 5 struct service *Services = NULL; static int allocservices = 0; int nservices = 0; struct event { char *name; struct timeval mark; time_t period; int hour; int min; int periodic; strarray_t *exec; struct event *next; }; static struct event *schedule = NULL; enum sstate { SERVICE_STATE_UNKNOWN = 0, /* duh */ SERVICE_STATE_INIT = 1, /* Service forked - UNUSED */ SERVICE_STATE_READY = 2, /* Service told us it is ready */ /* or it just forked and has not * talked to us yet */ SERVICE_STATE_BUSY = 3, /* Service told us it is not ready */ SERVICE_STATE_DEAD = 4 /* We received a sigchld from this service */ }; struct centry { pid_t pid; enum sstate service_state; /* SERVICE_STATE_* */ time_t janitor_deadline; /* cleanup deadline */ int si; /* Services[] index */ char *desc; /* human readable description for logging */ struct timeval spawntime; /* when the centry was allocated */ time_t sighuptime; /* when did we send a SIGHUP */; struct centry *next; }; static struct centry *ctable[child_table_size]; static int janitor_frequency = 1; /* Janitor sweeps per second */ static int janitor_position; /* Entry to begin at in next sweep */ static struct timeval janitor_mark; /* Last time janitor did a sweep */ static void limit_fds(rlim_t); static void schedule_event(struct event *a); static void child_sighandler_setup(void); #if HAVE_PSELECT static sigset_t pselect_sigmask; #endif static int myselect(int nfds, fd_set *rfds, fd_set *wfds, fd_set *efds, struct timeval *tout) { #if HAVE_PSELECT /* pselect() closes the race between SIGCHLD arriving * and select() sleeping for up to 10 seconds. */ struct timespec ts, *tsptr = NULL; if (tout) { ts.tv_sec = tout->tv_sec; ts.tv_nsec = tout->tv_usec * 1000; tsptr = &ts; } return pselect(nfds, rfds, wfds, efds, tsptr, &pselect_sigmask); #else return select(nfds, rfds, wfds, efds, tout); #endif } EXPORTED void fatal(const char *msg, int code) { syslog(LOG_CRIT, "%s", msg); syslog(LOG_NOTICE, "exiting"); exit(code); } static void event_free(struct event *a) { if (a->exec) { strarray_free(a->exec); a->exec = NULL; } free(a->name); free(a); } static void get_prog(char *path, size_t size, const strarray_t *cmd) { if (!size) return; if (cmd->data[0][0] == '/') { /* master lacks strlcpy, due to no libcyrus */ strncpy(path, cmd->data[0], size - 1); } else snprintf(path, size, "%s/%s", SERVICE_DIR, cmd->data[0]); path[size-1] = '\0'; } static void get_statsock(int filedes[2]) { int r, fdflags; r = pipe(filedes); if (r != 0) fatalf(1, "couldn't create status socket: %m"); /* we don't want the master blocking on reads */ fdflags = fcntl(filedes[0], F_GETFL, 0); if (fdflags != -1) fdflags = fcntl(filedes[0], F_SETFL, fdflags | O_NONBLOCK); if (fdflags == -1) fatalf(1, "unable to set non-blocking: %m"); /* we don't want the services to be able to read from it */ fdflags = fcntl(filedes[0], F_GETFD, 0); if (fdflags != -1) fdflags = fcntl(filedes[0], F_SETFD, fdflags | FD_CLOEXEC); if (fdflags == -1) fatalf(1, "unable to set close-on-exec: %m"); } static int cap_bind(int socket, struct sockaddr *addr, socklen_t length) { int r; set_caps(BEFORE_BIND, /*is_master*/1); r = bind(socket, addr, length); set_caps(AFTER_BIND, /*is_master*/1); return r; } /* Return a new 'centry', by malloc'ing it. */ static struct centry *centry_alloc(void) { struct centry *t; t = xzmalloc(sizeof(*t)); t->si = SERVICE_NONE; gettimeofday(&t->spawntime, NULL); t->sighuptime = (time_t)-1; return t; } static void centry_set_name(struct centry *c, const char *type, const char *name, const char *path) { free(c->desc); if (name && path) c->desc = strconcat("type:", type, " name:", name, " path:", path, NULL); else c->desc = strconcat("type:", type, NULL); } static char *centry_describe(const struct centry *c, pid_t pid) { struct buf desc = BUF_INITIALIZER; if (!c) { buf_appendcstr(&desc, "unknown process"); } else { struct timeval now; gettimeofday(&now, NULL); buf_printf(&desc, "process %s age:%.3fs", c->desc, timesub(&c->spawntime, &now)); } buf_printf(&desc, " pid:%d", (int)pid); return buf_release(&desc); } /* free a centry */ static void centry_free(struct centry *c) { free(c->desc); free(c); } /* add a centry to the global table of all * centries, using the given pid as the key */ static void centry_add(struct centry *c, pid_t p) { c->pid = p; c->next = ctable[p % child_table_size]; ctable[p % child_table_size] = c; } /* find a centry in the global table, using the * given pid as the key. Returns NULL if not * found. */ static struct centry *centry_find(pid_t p) { struct centry *c; c = ctable[p % child_table_size]; while (c && c->pid != p) c = c->next; return c; } static void centry_set_state(struct centry *c, enum sstate state) { c->service_state = state; if (state == SERVICE_STATE_DEAD) c->janitor_deadline = time(NULL) + 2; } /* * Parse the "listen" parameter as one of the forms: * * hostname * hostname ':' port * ipv4-address * ipv4-address ':' port * '[' ipv4-address ']' * '[' ipv4-address ']' ':' port * '[' ipv6-address ']' * '[' ipv6-address ']' ':' port * * Returns 0 on success with one or more of *@hostp and *@portp set * to new strings which must be free()d by the caller, or -1 on error. */ static int parse_inet_listen(const char *listen, char **hostp, char **portp) { const char *cp; *portp = NULL; *hostp = NULL; if (listen[0] == '[') { cp = strrchr(listen, ']'); if (!cp) return -1; cp++; if (*cp == ':') { if (!cp[1]) return -1; *hostp = xstrndup(listen+1, (cp - listen - 2)); *portp = xstrdup(cp+1); return 0; } if (!*cp) { *hostp = xstrndup(listen+1, (cp - listen - 2)); /* no port specified */ return 0; } return -1; } cp = strrchr(listen, ':'); if (cp) { if (!cp[1]) return -1; *hostp = xstrndup(listen, (cp - listen)); *portp = xstrdup(cp+1); return 0; } /* no host specified */ *portp = xstrdup(listen); return 0; } static int verify_service_file(const strarray_t *filename) { char path[PATH_MAX]; struct stat statbuf; get_prog(path, sizeof(path), filename); if (stat(path, &statbuf)) return 0; if (! S_ISREG(statbuf.st_mode)) return 0; return statbuf.st_mode & S_IXUSR; } static void service_forget_exec(struct service *s) { if (s->exec) { /* Only free the service info on the primary */ if (s->associate == 0) { strarray_free(s->exec); } s->exec = NULL; } } static struct service *service_add(const struct service *proto) { struct service *s; if (nservices == allocservices) { if (allocservices > SERVICE_MAX - 5) fatal("out of service structures, please restart", EX_UNAVAILABLE); Services = xrealloc(Services, (allocservices+=5) * sizeof(struct service)); } s = &Services[nservices++]; if (proto) memcpy(s, proto, sizeof(struct service)); else { memset(s, 0, sizeof(struct service)); s->socket = -1; s->stat[0] = -1; s->stat[1] = -1; } return s; } static void service_create(struct service *s) { struct service service0, service; struct addrinfo hints, *res0, *res; int error, nsocket = 0; struct sockaddr_un sunsock; mode_t oldumask; int on = 1; int res0_is_local = 0; int r; if (s->associate > 0) return; /* service is already activated */ if (!s->listen) return; /* service is a daemon, no listener */ if (!s->name) fatal("Serious software bug found: service_create() called on unnamed service!", EX_SOFTWARE); if (s->listen[0] == '/') { /* unix socket */ res0_is_local = 1; res0 = (struct addrinfo *)xzmalloc(sizeof(struct addrinfo)); res0->ai_flags = AI_PASSIVE; res0->ai_family = PF_UNIX; if(!strcmp(s->proto, "tcp")) { res0->ai_socktype = SOCK_STREAM; } else { /* udp */ res0->ai_socktype = SOCK_DGRAM; } res0->ai_addr = (struct sockaddr *)&sunsock; res0->ai_addrlen = sizeof(sunsock.sun_family) + strlen(s->listen) + 1; #ifdef SIN6_LEN res0->ai_addrlen += sizeof(sunsock.sun_len); sunsock.sun_len = res0->ai_addrlen; #endif sunsock.sun_family = AF_UNIX; strcpy(sunsock.sun_path, s->listen); unlink(s->listen); } else { /* inet socket */ char *port; char *listen_addr; memset(&hints, 0, sizeof(hints)); hints.ai_flags = AI_PASSIVE; if (!strcmp(s->proto, "tcp")) { hints.ai_family = PF_UNSPEC; hints.ai_socktype = SOCK_STREAM; } else if (!strcmp(s->proto, "tcp4")) { hints.ai_family = PF_INET; hints.ai_socktype = SOCK_STREAM; #ifdef PF_INET6 } else if (!strcmp(s->proto, "tcp6")) { hints.ai_family = PF_INET6; hints.ai_socktype = SOCK_STREAM; #endif } else if (!strcmp(s->proto, "udp")) { hints.ai_family = PF_UNSPEC; hints.ai_socktype = SOCK_DGRAM; } else if (!strcmp(s->proto, "udp4")) { hints.ai_family = PF_INET; hints.ai_socktype = SOCK_DGRAM; #ifdef PF_INET6 } else if (!strcmp(s->proto, "udp6")) { hints.ai_family = PF_INET6; hints.ai_socktype = SOCK_DGRAM; #endif } else { syslog(LOG_INFO, "invalid proto '%s', disabling %s", s->proto, s->name); service_forget_exec(s); return; } if (parse_inet_listen(s->listen, &listen_addr, &port) < 0) { syslog(LOG_ERR, "invalid listen '%s', disabling %s", s->listen, s->name); service_forget_exec(s); return; } error = getaddrinfo(listen_addr, port, &hints, &res0); free(listen_addr); free(port); if (error) { syslog(LOG_INFO, "%s, disabling %s", gai_strerror(error), s->name); service_forget_exec(s); return; } } memcpy(&service0, s, sizeof(struct service)); for (res = res0; res; res = res->ai_next) { if (s->socket >= 0) { memcpy(&service, &service0, sizeof(struct service)); s = &service; } s->family = res->ai_family; switch (s->family) { case AF_UNIX: s->familyname = "unix"; break; case AF_INET: s->familyname = "ipv4"; break; case AF_INET6: s->familyname = "ipv6"; break; default: s->familyname = "unknown"; break; } if (verbose > 2) { syslog(LOG_DEBUG, "activating service %s/%s", s->name, s->familyname); } s->socket = socket(res->ai_family, res->ai_socktype, res->ai_protocol); if (s->socket < 0) { syslog(LOG_ERR, "unable to open %s/%s socket: %m", s->name, s->familyname); continue; } /* allow reuse of address */ r = setsockopt(s->socket, SOL_SOCKET, SO_REUSEADDR, (void *) &on, sizeof(on)); if (r < 0) { syslog(LOG_ERR, "unable to setsocketopt(SO_REUSEADDR) service %s/%s: %m", s->name, s->familyname); } #if defined(IPV6_V6ONLY) && !(defined(__FreeBSD__) && __FreeBSD__ < 3) if (res->ai_family == AF_INET6) { r = setsockopt(s->socket, IPPROTO_IPV6, IPV6_V6ONLY, (void *) &on, sizeof(on)); if (r < 0) { syslog(LOG_ERR, "unable to setsocketopt(IPV6_V6ONLY) service %s/%s: %m", s->name, s->familyname); } } #endif /* set IP ToS if supported */ #if defined(SOL_IP) && defined(IP_TOS) r = setsockopt(s->socket, SOL_IP, IP_TOS, (void *) &config_qosmarking, sizeof(config_qosmarking)); if (r < 0) { syslog(LOG_WARNING, "unable to setsocketopt(IP_TOS) service %s/%s: %m", s->name, s->familyname); } #endif oldumask = umask((mode_t) 0); /* for linux */ r = cap_bind(s->socket, res->ai_addr, res->ai_addrlen); umask(oldumask); if (r < 0) { syslog(LOG_ERR, "unable to bind to %s/%s socket: %m", s->name, s->familyname); xclose(s->socket); continue; } if (s->listen[0] == '/') { /* unix socket */ /* for DUX, where this isn't the default. (harmlessly fails on some systems) */ chmod(s->listen, (mode_t) 0777); } if ((!strcmp(s->proto, "tcp") || !strcmp(s->proto, "tcp4") || !strcmp(s->proto, "tcp6")) && listen(s->socket, listen_queue_backlog) < 0) { syslog(LOG_ERR, "unable to listen to %s/%s socket: %m", s->name, s->familyname); xclose(s->socket); continue; } s->ready_workers = 0; s->associate = nsocket; get_statsock(s->stat); if (s == &service) service_add(s); nsocket++; } if (res0) { if(res0_is_local) free(res0); else freeaddrinfo(res0); } if (nsocket <= 0) { syslog(LOG_ERR, "unable to create %s listener socket: %m", s->name); service_forget_exec(s); return; } } static int decode_wait_status(struct centry *c, pid_t pid, int status) { int failed = 0; char *desc = centry_describe(c, pid); if (WIFEXITED(status)) { if (!WEXITSTATUS(status)) { syslog(LOG_DEBUG, "%s exited normally", desc); } else { syslog(LOG_ERR, "%s exited, status %d", desc, WEXITSTATUS(status)); failed = 1; } } if (WIFSIGNALED(status)) { const char *signame = strsignal(WTERMSIG(status)); if (!signame) signame = "unknown signal"; #ifdef WCOREDUMP syslog(LOG_ERR, "%s signaled to death by signal %d (%s%s)", desc, WTERMSIG(status), signame, WCOREDUMP(status) ? ", core dumped" : ""); failed = WCOREDUMP(status) ? 2 : 1; #else syslog(LOG_ERR, "%s signaled to death by %s %d", desc, signame, WTERMSIG(status)); failed = 1; #endif } free(desc); return failed; } static void run_startup(const char *name, const strarray_t *cmd) { pid_t pid; int status; struct centry *c; char path[PATH_MAX]; get_prog(path, sizeof(path), cmd); switch (pid = fork()) { case -1: fatalf(1, "can't fork process to run startup: %m"); break; case 0: /* Child - Release our pidfile lock. */ xclose(pidfd); set_caps(AFTER_FORK, /*is_master*/1); child_sighandler_setup(); limit_fds(256); syslog(LOG_DEBUG, "about to exec %s", path); execv(path, cmd->data); fatalf(EX_OSERR, "can't exec %s for startup: %m", path); default: /* parent */ if (waitpid(pid, &status, 0) < 0) { syslog(LOG_ERR, "waitpid(): %m"); return; } c = centry_alloc(); centry_set_name(c, "START", name, path); if (decode_wait_status(c, pid, status)) fatal("can't run startup", 1); centry_free(c); break; } } static void fcntl_unset(int fd, int flag) { int fdflags = fcntl(fd, F_GETFD, 0); if (fdflags != -1) fdflags = fcntl(STATUS_FD, F_SETFD, fdflags & ~flag); if (fdflags == -1) { syslog(LOG_ERR, "fcntl(): unable to unset %d: %m", flag); } } static int service_is_fork_limited(struct service *s) { /* The longest period for which we will ignore the service */ #define FORKRATE_INTERVAL 0.4 /* seconds */ /* How much the forkrate estimator decays, as a proportion, per second */ #define FORKRATE_ALPHA 0.5 /* per second */ struct timeval now; double interval; if (!s->maxforkrate) return 0; gettimeofday(&now, 0); interval = timesub(&s->last_interval_start, &now); /* update our fork rate */ if (interval > 0.0) { double f = pow(FORKRATE_ALPHA, interval); s->forkrate = f * s->forkrate + (1.0-f) * (s->interval_forks/interval); s->interval_forks = 0; s->last_interval_start = now; } else if (interval < 0.0) { /* * NTP or similar moved the time-of-day clock backwards more * than the interval we asked to be delayed for. Given that, we * have no basis for updating forkrate and must reset our rate * estimating state. Let's just hope this is a rare event. */ s->interval_forks = 0; s->last_interval_start = now; syslog(LOG_WARNING, "time of day clock went backwards"); } /* If we've been busy lately, we will refuse to fork! */ /* (We schedule a wakeup call for sometime soon though to be * sure that we don't wait to do the fork that is required forever! */ if ((unsigned int)s->forkrate >= s->maxforkrate) { struct event *evt = (struct event *) xzmalloc(sizeof(struct event)); evt->name = xstrdup("forkrate wakeup call"); evt->mark = now; timeval_add_double(&evt->mark, FORKRATE_INTERVAL); schedule_event(evt); return 1; } return 0; } static void spawn_service(int si) { pid_t p; int i; char path[PATH_MAX]; static char name_env[100], name_env2[100], name_env3[100]; struct centry *c; struct service *s = &Services[si]; if (!s->name) { fatal("Serious software bug found: spawn_service() called on unnamed service!", EX_SOFTWARE); } if (service_is_fork_limited(s)) return; get_prog(path, sizeof(path), s->exec); switch (p = fork()) { case -1: syslog(LOG_ERR, "can't fork process to run service %s/%s: %m", s->name, s->familyname); break; case 0: if (verbose > 2) { syslog(LOG_DEBUG, "forked process to run service %s/%s", s->name, s->familyname); } /* Child - Release our pidfile lock. */ xclose(pidfd); set_caps(AFTER_FORK, /*is_master*/1); child_sighandler_setup(); if (s->listen) { if (dup2(s->stat[1], STATUS_FD) < 0) { syslog(LOG_ERR, "can't duplicate status fd: %m"); exit(1); } if (dup2(s->socket, LISTEN_FD) < 0) { syslog(LOG_ERR, "can't duplicate listener fd: %m"); exit(1); } fcntl_unset(STATUS_FD, FD_CLOEXEC); fcntl_unset(LISTEN_FD, FD_CLOEXEC); } else { snprintf(name_env3, sizeof(name_env3), "CYRUS_ISDAEMON=1"); putenv(name_env3); } limit_fds(s->maxfds); /* close all listeners */ for (i = 0; i < nservices; i++) { xclose(Services[i].socket); xclose(Services[i].stat[0]); xclose(Services[i].stat[1]); } syslog(LOG_DEBUG, "about to exec %s", path); /* add service name to environment */ snprintf(name_env, sizeof(name_env), "CYRUS_SERVICE=%s", s->name); putenv(name_env); snprintf(name_env2, sizeof(name_env2), "CYRUS_ID=%d", s->associate); putenv(name_env2); execv(path, s->exec->data); syslog(LOG_ERR, "couldn't exec %s: %m", path); exit(EX_OSERR); default: /* parent */ s->ready_workers++; s->interval_forks++; s->nforks++; s->nactive++; /* add to child table */ c = centry_alloc(); centry_set_name(c, s->listen ? "SERVICE" : "DAEMON", s->name, path); c->si = si; centry_set_state(c, SERVICE_STATE_READY); centry_add(c, p); break; } } static void schedule_event(struct event *a) { struct event *ptr; if (! a->name) fatal("Serious software bug found: schedule_event() called on unnamed event!", EX_SOFTWARE); if (!schedule || timesub(&schedule->mark, &a->mark) < 0.0) { a->next = schedule; schedule = a; return; } for (ptr = schedule; ptr->next && timesub(&a->mark, &ptr->next->mark) <= 0.0; ptr = ptr->next) ; /* insert a */ a->next = ptr->next; ptr->next = a; } static void spawn_schedule(struct timeval now) { struct event *a, *b; int i; char path[PATH_MAX]; pid_t p; struct centry *c; a = NULL; /* update schedule accordingly */ while (schedule && timesub(&now, &schedule->mark) <= 0.0) { /* delete from schedule, insert into a */ struct event *ptr = schedule; /* delete */ schedule = schedule->next; /* insert */ ptr->next = a; a = ptr; } /* run all events */ while (a && a != schedule) { /* if a->exec is NULL, we just used the event to wake up, * so we actually don't need to exec anything at the moment */ if(a->exec) { get_prog(path, sizeof(path), a->exec); switch (p = fork()) { case -1: syslog(LOG_CRIT, "can't fork process to run event %s", a->name); break; case 0: /* Child - Release our pidfile lock. */ xclose(pidfd); set_caps(AFTER_FORK, /*is_master*/1); /* close all listeners */ for (i = 0; i < nservices; i++) { xclose(Services[i].socket); xclose(Services[i].stat[0]); xclose(Services[i].stat[1]); } limit_fds(256); syslog(LOG_DEBUG, "about to exec %s", path); execv(path, a->exec->data); syslog(LOG_ERR, "can't exec %s on schedule: %m", path); exit(EX_OSERR); break; default: /* we don't wait for it to complete */ /* add to child table */ c = centry_alloc(); centry_set_name(c, "EVENT", a->name, path); centry_set_state(c, SERVICE_STATE_READY); centry_add(c, p); break; } } /* a->exec */ /* reschedule as needed */ b = a->next; if (a->period) { if(a->periodic) { a->mark = now; a->mark.tv_sec += a->period; } else { struct tm *tm; int delta; /* Daily Event */ while (timesub(&now, &a->mark) <= 0.0) a->mark.tv_sec += a->period; /* check for daylight savings fuzz... */ tm = localtime(&a->mark.tv_sec); if (tm->tm_hour != a->hour || tm->tm_min != a->min) { /* calculate the same time on the new day */ tm->tm_hour = a->hour; tm->tm_min = a->min; delta = mktime(tm) - a->mark.tv_sec; /* bring it within half a period either way */ while (delta > (a->period/2)) delta -= a->period; while (delta < -(a->period/2)) delta += a->period; /* update the time */ a->mark.tv_sec += delta; /* and let us know about the change */ syslog(LOG_NOTICE, "timezone shift for %s - altering schedule by %d seconds", a->name, delta); } } /* reschedule a */ schedule_event(a); } else { event_free(a); } /* examine next event */ a = b; } } static void reap_child(void) { int status; pid_t pid; struct centry *c; struct service *s; int failed; while ((pid = waitpid((pid_t) -1, &status, WNOHANG)) > 0) { /* account for the child */ c = centry_find(pid); failed = decode_wait_status(c, pid, status); if (c) { s = ((c->si) != SERVICE_NONE) ? &Services[c->si] : NULL; /* paranoia */ switch (c->service_state) { case SERVICE_STATE_READY: case SERVICE_STATE_BUSY: case SERVICE_STATE_UNKNOWN: case SERVICE_STATE_DEAD: break; default: syslog(LOG_CRIT, "service %s/%s pid %d in ILLEGAL STATE: exited. Serious " "software bug or memory corruption detected!", s ? SERVICEPARAM(s->name) : "unknown", s ? SERVICEPARAM(s->familyname) : "unknown", pid); centry_set_state(c, SERVICE_STATE_UNKNOWN); } if (s) { /* update counters for known services */ switch (c->service_state) { case SERVICE_STATE_READY: s->nactive--; s->ready_workers--; if (!in_shutdown && failed) { syslog(LOG_WARNING, "service %s/%s pid %d in READY state: " "terminated abnormally", SERVICEPARAM(s->name), SERVICEPARAM(s->familyname), pid); if (++s->nreadyfails >= MAX_READY_FAILS && s->exec) { syslog(LOG_ERR, "too many failures for " "service %s/%s, disabling until next SIGHUP", SERVICEPARAM(s->name), SERVICEPARAM(s->familyname)); service_forget_exec(s); xclose(s->socket); } } break; case SERVICE_STATE_DEAD: /* uh? either we got duplicate signals, or we are now MT */ syslog(LOG_WARNING, "service %s/%s pid %d in DEAD state: " "receiving duplicate signals", SERVICEPARAM(s->name), SERVICEPARAM(s->familyname), pid); break; case SERVICE_STATE_BUSY: s->nactive--; if (!in_shutdown && failed) { syslog(LOG_DEBUG, "service %s/%s pid %d in BUSY state: " "terminated abnormally", SERVICEPARAM(s->name), SERVICEPARAM(s->familyname), pid); } break; case SERVICE_STATE_UNKNOWN: s->nactive--; syslog(LOG_WARNING, "service %s/%s pid %d in UNKNOWN state: exited", SERVICEPARAM(s->name), SERVICEPARAM(s->familyname), pid); break; default: /* Shouldn't get here */ break; } } else { /* children from spawn_schedule (events) or * children of services removed by reread_conf() */ if (c->service_state != SERVICE_STATE_READY) { syslog(LOG_WARNING, "unknown service pid %d in state %d: exited " "(maybe using a service as an event, " "or a service was removed by SIGHUP?)", pid, c->service_state); } } centry_set_state(c, SERVICE_STATE_DEAD); } else { /* Are we multithreaded now? we don't know this child */ syslog(LOG_ERR, "received SIGCHLD from unknown child pid %d, ignoring", pid); /* FIXME: is this something we should take lightly? */ } if (verbose && c && (c->si != SERVICE_NONE)) syslog(LOG_DEBUG, "service %s/%s now has %d ready workers", SERVICEPARAM(Services[c->si].name), SERVICEPARAM(Services[c->si].familyname), Services[c->si].ready_workers); } } static void init_janitor(struct timeval now) { struct event *evt = (struct event *) xzmalloc(sizeof(struct event)); janitor_mark = now; janitor_position = 0; evt->name = xstrdup("janitor periodic wakeup call"); evt->period = 10; evt->periodic = 1; evt->mark = janitor_mark; schedule_event(evt); } static void child_janitor(struct timeval now) { int i; struct centry **p; struct centry *c; /* Estimate the number of entries to clean up in this sweep */ if (now.tv_sec > janitor_mark.tv_sec + 1) { /* overflow protection */ i = child_table_size; } else { double n; n = child_table_size * janitor_frequency * timesub(&janitor_mark, &now); if (n < child_table_size) { i = n; } else { i = child_table_size; } } while (i-- > 0) { p = &ctable[janitor_position++]; janitor_position = janitor_position % child_table_size; while (*p) { c = *p; if (c->service_state == SERVICE_STATE_DEAD) { if (c->janitor_deadline < now.tv_sec) { *p = c->next; centry_free(c); } else { p = &((*p)->next); } } else { time_t delay = (c->sighuptime != (time_t)-1) ? time(NULL) - c->sighuptime : 0; if (delay >= 30) { /* client not yet logged out ? */ struct service *s = ((c->si) != SERVICE_NONE) ? &Services[c->si] : NULL; syslog(LOG_INFO, "service %s/%s pid %d in state %d has not " "yet been recycled since SIGHUP was sent (%ds ago)", s ? SERVICEPARAM(s->name) : "unknown", s ? SERVICEPARAM(s->familyname) : "unknown", c->pid, c->service_state, (int)delay); /* no need to log it more than once */ c->sighuptime = (time_t)-1; } p = &((*p)->next); } } } } /* Allow a clean shutdown on SIGQUIT, SIGTERM or SIGINT */ static volatile sig_atomic_t gotsigquit = 0; static void sigquit_handler(int sig __attribute__((unused))) { gotsigquit = 1; } static void begin_shutdown(void) { /* Set a flag so main loop knows to shut down when all children have exited. Note, we will be called twice as we send SIGTERM to our own process group. */ if (in_shutdown) return; in_shutdown = 1; syslog(LOG_INFO, "attempting clean shutdown on signal"); #if defined(HAVE_UCDSNMP) || defined(HAVE_NETSNMP) /* tell master agent we're exiting */ snmp_shutdown("cyrusMaster"); #endif /* send our process group a SIGTERM */ if (kill(0, SIGTERM) < 0) { syslog(LOG_ERR, "begin_shutdown: kill(0, SIGTERM): %m"); } } static volatile sig_atomic_t gotsigchld = 0; static void sigchld_handler(int sig __attribute__((unused))) { gotsigchld = 1; } static volatile int gotsighup = 0; static void sighup_handler(int sig __attribute__((unused))) { gotsighup = 1; } static void sigalrm_handler(int sig __attribute__((unused))) { return; } static void sighandler_setup(void) { struct sigaction action; sigset_t siglist; memset(&siglist, 0, sizeof(siglist)); sigemptyset(&siglist); sigaddset(&siglist, SIGHUP); sigaddset(&siglist, SIGALRM); sigaddset(&siglist, SIGQUIT); sigaddset(&siglist, SIGTERM); sigaddset(&siglist, SIGINT); sigaddset(&siglist, SIGCHLD); sigprocmask(SIG_UNBLOCK, &siglist, NULL); memset(&action, 0, sizeof(action)); sigemptyset(&action.sa_mask); action.sa_handler = sighup_handler; #ifdef SA_RESTART action.sa_flags |= SA_RESTART; #endif if (sigaction(SIGHUP, &action, NULL) < 0) fatalf(1, "unable to install signal handler for SIGHUP: %m"); action.sa_handler = sigalrm_handler; if (sigaction(SIGALRM, &action, NULL) < 0) fatalf(1, "unable to install signal handler for SIGALRM: %m"); /* Allow a clean shutdown on any of SIGQUIT, SIGINT or SIGTERM */ action.sa_handler = sigquit_handler; if (sigaction(SIGQUIT, &action, NULL) < 0) fatalf(1, "unable to install signal handler for SIGQUIT: %m"); if (sigaction(SIGTERM, &action, NULL) < 0) fatalf(1, "unable to install signal handler for SIGTERM: %m"); if (sigaction(SIGINT, &action, NULL) < 0) fatalf(1, "unable to install signal handler for SIGINT: %m"); action.sa_flags |= SA_NOCLDSTOP; action.sa_handler = sigchld_handler; if (sigaction(SIGCHLD, &action, NULL) < 0) fatalf(1, "unable to install signal handler for SIGCHLD: %m"); #if HAVE_PSELECT /* block SIGCHLD, and set up pselect_sigmask so SIGCHLD * will be unblocked again inside pselect(). Ditto SIGQUIT. */ sigemptyset(&siglist); sigaddset(&siglist, SIGCHLD); sigaddset(&siglist, SIGQUIT); sigaddset(&siglist, SIGINT); sigaddset(&siglist, SIGTERM); sigprocmask(SIG_BLOCK, &siglist, &pselect_sigmask); #endif } static void child_sighandler_setup(void) { #if HAVE_PSELECT /* * We need to explicitly reset our SIGQUIT handler to the default * action. This happens at execv() time, but in the small window * between fork() and execv() any SIGQUIT signal delivered will be * caught, and the gotsigquit flag set, but that flag is then * completely ignored. Ditto SIGINT and SIGTERM. */ struct sigaction action; memset(&action, 0, sizeof(action)); sigemptyset(&action.sa_mask); action.sa_handler = SIG_DFL; if (sigaction(SIGQUIT, &action, NULL) < 0) { syslog(LOG_ERR, "unable to remove signal handler for SIGQUIT: %m"); exit(EX_TEMPFAIL); } if (sigaction(SIGINT, &action, NULL) < 0) { syslog(LOG_ERR, "unable to remove signal handler for SIGINT: %m"); exit(EX_TEMPFAIL); } if (sigaction(SIGTERM, &action, NULL) < 0) { syslog(LOG_ERR, "unable to remove signal handler for SIGTERM: %m"); exit(EX_TEMPFAIL); } /* Unblock SIGCHLD et al in the child */ sigprocmask(SIG_SETMASK, &pselect_sigmask, NULL); #endif } /* * Receives a message from a service. * * Returns zero if all goes well * 1 if no msg available * 2 if bad message received (incorrectly sized) * -1 on error (errno set) * * TODO: should use retry_read() which has almost the * exact same semantics apart from the return value. */ static int read_msg(int fd, struct notify_message *msg) { ssize_t r = 0; size_t off = 0; int s = sizeof(struct notify_message); while (s > 0) { do r = read(fd, ((char *)msg) + off, s); while ((r == -1) && (errno == EINTR)); if (r <= 0) break; s -= r; off += r; } if ( ((r == 0) && (off == 0)) || ((r == -1) && (errno == EAGAIN)) ) return 1; if (r == -1) return -1; if (s != 0) return 2; return 0; } static void process_msg(int si, struct notify_message *msg) { struct centry *c; /* si must NOT point to an invalid service */ struct service *s = &Services[si]; c = centry_find(msg->service_pid); /* Did we find it? */ if (!c) { /* If we don't know about the child, that means it has expired from * the child list, due to large message delivery delays. This is * indeed possible, although it is rare (Debian bug report). * * Note that this analysis depends on master's single-threaded * nature */ syslog(LOG_WARNING, "service %s/%s pid %d: receiving messages from long dead children", SERVICEPARAM(s->name), SERVICEPARAM(s->familyname), msg->service_pid); /* re-add child to list */ c = centry_alloc(); centry_set_name(c, "ZOMBIE", NULL, NULL); c->si = si; centry_set_state(c, SERVICE_STATE_DEAD); centry_add(c, msg->service_pid); } /* paranoia */ if (si != c->si) { syslog(LOG_ERR, "service %s/%s pid %d: changing from service %s/%s due to received message", SERVICEPARAM(s->name), SERVICEPARAM(s->familyname), c->pid, ((c->si != SERVICE_NONE) ? SERVICEPARAM(Services[c->si].name) : "unknown"), ((c->si != SERVICE_NONE) ? SERVICEPARAM(Services[c->si].familyname) : "unknown")); c->si = si; } switch (c->service_state) { case SERVICE_STATE_UNKNOWN: syslog(LOG_WARNING, "service %s/%s pid %d in UNKNOWN state: processing message 0x%x", SERVICEPARAM(s->name), SERVICEPARAM(s->familyname), c->pid, msg->message); break; case SERVICE_STATE_READY: case SERVICE_STATE_BUSY: case SERVICE_STATE_DEAD: break; default: syslog(LOG_CRIT, "service %s/%s pid %d in ILLEGAL state: detected. Serious software bug or memory corruption uncloaked while processing message 0x%x from child!", SERVICEPARAM(s->name), SERVICEPARAM(s->familyname), c->pid, msg->message); centry_set_state(c, SERVICE_STATE_UNKNOWN); break; } /* process message, according to state machine */ switch (msg->message) { case MASTER_SERVICE_AVAILABLE: switch (c->service_state) { case SERVICE_STATE_READY: /* duplicate message? */ syslog(LOG_WARNING, "service %s/%s pid %d in READY state: sent available message but it is already ready", SERVICEPARAM(s->name), SERVICEPARAM(s->familyname), c->pid); break; case SERVICE_STATE_UNKNOWN: /* since state is unknwon, error in non-DoS way, i.e. * we don't increment ready_workers */ syslog(LOG_DEBUG, "service %s/%s pid %d in UNKNOWN state: now available and in READY state", SERVICEPARAM(s->name), SERVICEPARAM(s->familyname), c->pid); centry_set_state(c, SERVICE_STATE_READY); break; case SERVICE_STATE_BUSY: if (verbose) syslog(LOG_DEBUG, "service %s/%s pid %d in BUSY state: now available and in READY state", SERVICEPARAM(s->name), SERVICEPARAM(s->familyname), c->pid); centry_set_state(c, SERVICE_STATE_READY); s->ready_workers++; break; case SERVICE_STATE_DEAD: /* echoes from the past... just ignore */ break; default: /* Shouldn't get here */ break; } break; case MASTER_SERVICE_UNAVAILABLE: switch (c->service_state) { case SERVICE_STATE_BUSY: /* duplicate message? */ syslog(LOG_WARNING, "service %s/%s pid %d in BUSY state: sent unavailable message but it is already busy", SERVICEPARAM(s->name), SERVICEPARAM(s->familyname), c->pid); break; case SERVICE_STATE_UNKNOWN: syslog(LOG_DEBUG, "service %s/%s pid %d in UNKNOWN state: now unavailable and in BUSY state", SERVICEPARAM(s->name), SERVICEPARAM(s->familyname), c->pid); centry_set_state(c, SERVICE_STATE_BUSY); break; case SERVICE_STATE_READY: if (verbose) syslog(LOG_DEBUG, "service %s/%s pid %d in READY state: now unavailable and in BUSY state", SERVICEPARAM(s->name), SERVICEPARAM(s->familyname), c->pid); centry_set_state(c, SERVICE_STATE_BUSY); s->ready_workers--; break; case SERVICE_STATE_DEAD: /* echoes from the past... just ignore */ break; default: /* Shouldn't get here */ break; } break; case MASTER_SERVICE_CONNECTION: switch (c->service_state) { case SERVICE_STATE_BUSY: s->nconnections++; if (verbose) syslog(LOG_DEBUG, "service %s/%s pid %d in BUSY state: now serving connection", SERVICEPARAM(s->name), SERVICEPARAM(s->familyname), c->pid); break; case SERVICE_STATE_UNKNOWN: s->nconnections++; centry_set_state(c, SERVICE_STATE_BUSY); syslog(LOG_DEBUG, "service %s/%s pid %d in UNKNOWN state: now in BUSY state and serving connection", SERVICEPARAM(s->name), SERVICEPARAM(s->familyname), c->pid); break; case SERVICE_STATE_READY: syslog(LOG_ERR, "service %s/%s pid %d in READY state: reported new connection, forced to BUSY state", SERVICEPARAM(s->name), SERVICEPARAM(s->familyname), c->pid); /* be resilient on face of a bogon source, so lets err to the side * of non-denial-of-service */ centry_set_state(c, SERVICE_STATE_BUSY); s->nconnections++; s->ready_workers--; break; case SERVICE_STATE_DEAD: /* echoes from the past... do the accounting */ s->nconnections++; break; default: /* Shouldn't get here */ break; } break; case MASTER_SERVICE_CONNECTION_MULTI: switch (c->service_state) { case SERVICE_STATE_READY: s->nconnections++; if (verbose) syslog(LOG_DEBUG, "service %s/%s pid %d in READY state: serving one more multi-threaded connection", SERVICEPARAM(s->name), SERVICEPARAM(s->familyname), c->pid); break; case SERVICE_STATE_BUSY: syslog(LOG_ERR, "service %s/%s pid %d in BUSY state: serving one more multi-threaded connection, forced to READY state", SERVICEPARAM(s->name), SERVICEPARAM(s->familyname), c->pid); /* be resilient on face of a bogon source, so lets err to the side * of non-denial-of-service */ centry_set_state(c, SERVICE_STATE_READY); s->nconnections++; s->ready_workers++; break; case SERVICE_STATE_UNKNOWN: s->nconnections++; centry_set_state(c, SERVICE_STATE_READY); syslog(LOG_ERR, "service %s/%s pid %d in UNKNOWN state: serving one more multi-threaded connection, forced to READY state", SERVICEPARAM(s->name), SERVICEPARAM(s->familyname), c->pid); break; case SERVICE_STATE_DEAD: /* echoes from the past... do the accounting */ s->nconnections++; break; default: /* Shouldn't get here */ break; } break; default: syslog(LOG_CRIT, "service %s/%s pid %d: Software bug: unrecognized message 0x%x", SERVICEPARAM(s->name), SERVICEPARAM(s->familyname), c->pid, msg->message); break; } if (verbose) syslog(LOG_DEBUG, "service %s/%s now has %d ready workers", SERVICEPARAM(s->name), SERVICEPARAM(s->familyname), s->ready_workers); } static void add_start(const char *name, struct entry *e, void *rock __attribute__((unused))) { const char *cmd = masterconf_getstring(e, "cmd", ""); strarray_t *tok; if (!strcmp(cmd,"")) fatalf(EX_CONFIG, "unable to find command for %s", name); tok = strarray_split(cmd, NULL, 0); run_startup(name, tok); strarray_free(tok); } static void add_daemon(const char *name, struct entry *e, void *rock) { int ignore_err = rock ? 1 : 0; char *cmd = xstrdup(masterconf_getstring(e, "cmd", "")); rlim_t maxfds = (rlim_t) masterconf_getint(e, "maxfds", 256); int maxforkrate = masterconf_getint(e, "maxforkrate", 0); int reconfig = 0; int i; if (maxforkrate == 0) maxforkrate = 10; /* reasonable safety */ if (!strcmp(cmd, "")) { char buf[256]; snprintf(buf, sizeof(buf), "unable to find command or port for service '%s'", name); if (ignore_err) { syslog(LOG_WARNING, "WARNING: %s -- ignored", buf); goto done; } fatal(buf, EX_CONFIG); } /* see if we have an existing entry that can be reused */ for (i = 0; i < nservices; i++) { /* skip non-primary instances */ if (Services[i].associate > 0) continue; if (!strcmpsafe(Services[i].name, name) && Services[i].exec) { /* we have duplicate service names in the config file */ char buf[256]; snprintf(buf, sizeof(buf), "multiple entries for service '%s'", name); if (ignore_err) { syslog(LOG_WARNING, "WARNING: %s -- ignored", buf); goto done; } fatal(buf, EX_CONFIG); } /* must have empty/same service name, listen and proto */ if (!Services[i].name || !strcmp(Services[i].name, name)) break; } if (i == nservices) { /* we don't have an existing one, so create a new service */ struct service *s = service_add(NULL); gettimeofday(&s->last_interval_start, 0); } else reconfig = 1; if (!Services[i].name) Services[i].name = xstrdup(name); strarray_free(Services[i].exec); Services[i].exec = strarray_split(cmd, NULL, 0); /* is this daemon actually there? */ if (!verify_service_file(Services[i].exec)) { fatalf(EX_CONFIG, "cannot find executable for daemon '%s'", name); /* if it is not, we're misconfigured, die. */ } Services[i].maxforkrate = maxforkrate; Services[i].maxfds = maxfds; Services[i].babysit = 1; Services[i].max_workers = 1; Services[i].desired_workers = 1; Services[i].familyname = "daemon"; if (verbose > 2) syslog(LOG_DEBUG, "%s: daemon '%s' (%s, %d)", reconfig ? "reconfig" : "add", Services[i].name, cmd, (int) Services[i].maxfds); done: free(cmd); return; } static void add_service(const char *name, struct entry *e, void *rock) { int ignore_err = rock ? 1 : 0; char *cmd = xstrdup(masterconf_getstring(e, "cmd", "")); int prefork = masterconf_getint(e, "prefork", 0); int babysit = masterconf_getswitch(e, "babysit", 0); int maxforkrate = masterconf_getint(e, "maxforkrate", 0); char *listen = xstrdup(masterconf_getstring(e, "listen", "")); char *proto = xstrdup(masterconf_getstring(e, "proto", "tcp")); char *max = xstrdup(masterconf_getstring(e, "maxchild", "-1")); rlim_t maxfds = (rlim_t) masterconf_getint(e, "maxfds", 256); int reconfig = 0; int i, j; if(babysit && prefork == 0) prefork = 1; if(babysit && maxforkrate == 0) maxforkrate = 10; /* reasonable safety */ if (!strcmp(cmd,"") || !strcmp(listen,"")) { char buf[256]; snprintf(buf, sizeof(buf), "unable to find command or port for service '%s'", name); if (ignore_err) { syslog(LOG_WARNING, "WARNING: %s -- ignored", buf); goto done; } fatal(buf, EX_CONFIG); } /* see if we have an existing entry that can be reused */ for (i = 0; i < nservices; i++) { /* skip non-primary instances */ if (Services[i].associate > 0) continue; if (!strcmpsafe(Services[i].name, name) && Services[i].exec) { /* we have duplicate service names in the config file */ char buf[256]; snprintf(buf, sizeof(buf), "multiple entries for service '%s'", name); if (ignore_err) { syslog(LOG_WARNING, "WARNING: %s -- ignored", buf); goto done; } fatal(buf, EX_CONFIG); } /* must have empty/same service name, listen and proto */ if ((!Services[i].name || !strcmp(Services[i].name, name)) && (!Services[i].listen || !strcmp(Services[i].listen, listen)) && (!Services[i].proto || !strcmp(Services[i].proto, proto))) break; } if (i == nservices) { /* either we don't have an existing entry or we are changing * the port parameters, so create a new service */ struct service *s = service_add(NULL); gettimeofday(&s->last_interval_start, 0); } else if (Services[i].listen) reconfig = 1; if (!Services[i].name) Services[i].name = xstrdup(name); if (Services[i].listen) free(Services[i].listen); Services[i].listen = listen; listen = NULL; /* avoid freeing it */ if (Services[i].proto) free(Services[i].proto); Services[i].proto = proto; proto = NULL; /* avoid freeing it */ strarray_free(Services[i].exec); Services[i].exec = strarray_split(cmd, NULL, 0); /* is this service actually there? */ if (!verify_service_file(Services[i].exec)) { fatalf(EX_CONFIG, "cannot find executable for service '%s'", name); /* if it is not, we're misconfigured, die. */ } Services[i].maxforkrate = maxforkrate; Services[i].maxfds = maxfds; if (!strcmp(Services[i].proto, "tcp") || !strcmp(Services[i].proto, "tcp4") || !strcmp(Services[i].proto, "tcp6")) { Services[i].desired_workers = prefork; Services[i].babysit = babysit; Services[i].max_workers = atoi(max); if (Services[i].max_workers < 0) { Services[i].max_workers = INT_MAX; } } else { /* udp */ if (prefork > 1) prefork = 1; Services[i].desired_workers = prefork; Services[i].max_workers = 1; } if (reconfig) { /* reconfiguring an existing service, update any other instances */ for (j = 0; j < nservices; j++) { if (Services[j].associate > 0 && Services[j].listen && Services[j].name && !strcmp(Services[j].name, name)) { Services[j].maxforkrate = Services[i].maxforkrate; Services[j].exec = Services[i].exec; Services[j].desired_workers = Services[i].desired_workers; Services[j].babysit = Services[i].babysit; Services[j].max_workers = Services[i].max_workers; } } } if (verbose > 2) syslog(LOG_DEBUG, "%s: service '%s' (%s, %s:%s, %d, %d, %d)", reconfig ? "reconfig" : "add", Services[i].name, cmd, Services[i].proto, Services[i].listen, Services[i].desired_workers, Services[i].max_workers, (int) Services[i].maxfds); done: free(cmd); free(listen); free(proto); free(max); return; } static void add_event(const char *name, struct entry *e, void *rock) { int ignore_err = rock ? 1 : 0; /* Note: masterconf_getstring() shares a static buffer with * masterconf_getint() so we *must* strdup here */ char *cmd = xstrdup(masterconf_getstring(e, "cmd", "")); int period = 60 * masterconf_getint(e, "period", 0); int at = masterconf_getint(e, "at", -1), hour, min; struct timeval now; struct event *evt; gettimeofday(&now, 0); if (!strcmp(cmd,"")) { char buf[256]; snprintf(buf, sizeof(buf), "unable to find command or port for event '%s'", name); if (ignore_err) { syslog(LOG_WARNING, "WARNING: %s -- ignored", buf); free(cmd); return; } fatal(buf, EX_CONFIG); } evt = (struct event *) xzmalloc(sizeof(struct event)); evt->name = xstrdup(name); if (at >= 0 && ((hour = at / 100) <= 23) && ((min = at % 100) <= 59)) { struct tm *tm = localtime(&now.tv_sec); period = 86400; /* 24 hours */ evt->periodic = 0; evt->hour = hour; evt->min = min; tm->tm_hour = hour; tm->tm_min = min; tm->tm_sec = 0; evt->mark.tv_sec = mktime(tm); evt->mark.tv_usec = 0; if (timesub(&now, &evt->mark) < 0.0) { /* already missed it, so schedule for next day */ evt->mark.tv_sec += period; } } else { evt->periodic = 1; evt->mark = now; } evt->period = period; evt->exec = strarray_splitm(cmd, NULL, 0); schedule_event(evt); } #ifdef HAVE_SETRLIMIT #ifdef RLIMIT_NOFILE # define RLIMIT_NUMFDS RLIMIT_NOFILE #else # ifdef RLIMIT_OFILE # define RLIMIT_NUMFDS RLIMIT_OFILE # endif #endif static void limit_fds(rlim_t x) { struct rlimit rl; #ifdef HAVE_GETRLIMIT if (!getrlimit(RLIMIT_NUMFDS, &rl)) { if (x != RLIM_INFINITY && rl.rlim_max != RLIM_INFINITY && x > rl.rlim_max) { syslog(LOG_WARNING, "limit_fds: requested %" PRIu64 ", but capped to %" PRIu64, (uint64_t) x, (uint64_t) rl.rlim_max); } rl.rlim_cur = (x == RLIM_INFINITY || x > rl.rlim_max) ? rl.rlim_max : x; } else #endif /* HAVE_GETRLIMIT */ { rl.rlim_cur = rl.rlim_max = x; } if (verbose > 1) { syslog(LOG_DEBUG, "set maximum file descriptors to %ld/%ld", rl.rlim_cur, rl.rlim_max); } if (setrlimit(RLIMIT_NUMFDS, &rl) < 0) { syslog(LOG_ERR, "setrlimit: Unable to set file descriptors limit to %ld: %m", rl.rlim_cur); } } #else static void limit_fds(rlim_t x) { } #endif /* HAVE_SETRLIMIT */ static void reread_conf(struct timeval now) { int i,j; struct event *ptr; struct centry *c; /* disable all services - they will be re-enabled if they appear in config file */ for (i = 0; i < nservices; i++) service_forget_exec(&Services[i]); /* read services */ masterconf_getsection("SERVICES", &add_service, (void*) 1); masterconf_getsection("DAEMON", &add_daemon, (void *)1); for (i = 0; i < nservices; i++) { /* Send SIGHUP to all children: * - for services being added, there are still no children * - for services being disabled, we need to terminate the children * - otherwise (remaining services) we want to recycle children * Note that for services being disabled, it is important to first * signal them before shutting down their socket. */ for (j = 0 ; j < child_table_size ; j++ ) { c = ctable[j]; while (c != NULL) { if ((c->si == i) && (c->service_state != SERVICE_STATE_DEAD)) { kill(c->pid, SIGHUP); c->sighuptime = time(NULL); } c = c->next; } } if (!Services[i].exec && (Services[i].socket >= 0)) { /* cleanup newly disabled services */ if (verbose > 2) syslog(LOG_DEBUG, "disable: service %s/%s socket %d pipe %d %d", Services[i].name, Services[i].familyname, Services[i].socket, Services[i].stat[0], Services[i].stat[1]); /* Only free the service info on the primary */ if(Services[i].associate == 0) { free(Services[i].listen); free(Services[i].proto); } Services[i].listen = NULL; Services[i].proto = NULL; Services[i].desired_workers = 0; /* close all listeners */ shutdown(Services[i].socket, SHUT_RDWR); xclose(Services[i].socket); } else if (Services[i].exec && (Services[i].socket < 0)) { /* initialize new services */ service_create(&Services[i]); if (verbose > 2) syslog(LOG_DEBUG, "init: service %s/%s socket %d pipe %d %d", Services[i].name, Services[i].familyname, Services[i].socket, Services[i].stat[0], Services[i].stat[1]); } } /* remove existing events */ while (schedule) { ptr = schedule; schedule = schedule->next; event_free(ptr); } schedule = NULL; /* read events */ masterconf_getsection("EVENTS", &add_event, (void*) 1); /* reinit child janitor */ init_janitor(now); /* send some feedback to admin */ syslog(LOG_NOTICE, "Services reconfigured. %d out of %d (max %d) services structures are now in use", nservices, allocservices, SERVICE_MAX); } int main(int argc, char **argv) { static const char lock_suffix[] = ".lock"; const char *pidfile = MASTER_PIDFILE; char *pidfile_lock = NULL; int startup_pipe[2] = { -1, -1 }; int pidlock_fd = -1; int i, opt, close_std = 1, daemon_mode = 0; const char *error_log = NULL; extern char *optarg; char *alt_config = NULL; int fd; fd_set rfds; char *p = NULL; int r = 0; #ifdef HAVE_NETSNMP char *agentxsocket = NULL; int agentxpinginterval = -1; #endif struct timeval now; p = getenv("CYRUS_VERBOSE"); if (p) verbose = atoi(p) + 1; #ifdef HAVE_NETSNMP while ((opt = getopt(argc, argv, "C:L:M:p:l:Ddj:vVP:x:")) != EOF) { #else while ((opt = getopt(argc, argv, "C:L:M:p:l:Ddj:vV")) != EOF) { #endif switch (opt) { case 'C': /* alt imapd.conf file */ alt_config = optarg; break; case 'M': /* alt cyrus.conf file */ MASTER_CONFIG_FILENAME = optarg; break; case 'l': /* user defined listen queue backlog */ listen_queue_backlog = atoi(optarg); break; case 'p': /* Set the pidfile name */ pidfile = optarg; break; case 'd': /* Daemon Mode */ daemon_mode = 1; break; case 'D': /* Debug Mode */ close_std = 0; break; case 'L': /* error log */ error_log = optarg; break; case 'j': /* Janitor frequency */ janitor_frequency = atoi(optarg); if(janitor_frequency < 1) fatal("The janitor period must be at least 1 second", EX_CONFIG); break; #ifdef HAVE_NETSNMP case 'P': /* snmp AgentXPingInterval */ agentxpinginterval = atoi(optarg); break; case 'x': /* snmp AgentXSocket */ agentxsocket = optarg; break; #endif case 'v': verbose++; break; case 'V': /* print version information and exit */ /* XXX can't just call cyrus_version() because that would require * XXX linking against libcyrus_imap */ printf("%s %s%s\n", PACKAGE_NAME, PACKAGE_VERSION, #ifdef EXTRA_IDENT "-" EXTRA_IDENT #else "" #endif ); return 0; default: break; } } if (daemon_mode && !close_std) fatal("Unable to be both debug and daemon mode", EX_CONFIG); masterconf_init("master", alt_config); if (close_std || error_log) { /* close stdin/out/err */ for (fd = 0; fd < 3; fd++) { const char *file = (error_log && fd > 0 ? error_log : "/dev/null"); int mode = (fd > 0 ? O_WRONLY : O_RDWR) | (error_log && fd > 0 ? O_CREAT|O_APPEND : 0); close(fd); if (open(file, mode, 0666) != fd) fatalf(2, "couldn't open %s: %m", file); } } /* we reserve fds 3 and 4 for children to communicate with us, so they better be available. */ for (fd = 3; fd < 5; fd++) { close(fd); if (dup(0) != fd) fatalf(2, "couldn't dup fd 0: %m"); } /* Pidfile Algorithm in Daemon Mode. This is a little subtle because * we want to ensure that we can report an error to our parent if the * child fails to lock the pidfile. * * [A] Create/lock pidfile.lock. If locked, exit(failure). * [A] Create a pipe * [A] Fork [B] * [A] Block on reading exit code from pipe * [B] Create/lock pidfile. If locked, write failure code to pipe and * exit(failure) * [B] write pid to pidfile * [B] write success code to pipe & finish starting up * [A] unlink pidfile.lock and exit(code read from pipe) * */ if(daemon_mode) { /* Daemonize */ pid_t pid = -1; pidfile_lock = strconcat(pidfile, lock_suffix, (char *)NULL); pidlock_fd = open(pidfile_lock, O_CREAT|O_TRUNC|O_RDWR, 0644); if(pidlock_fd == -1) { syslog(LOG_ERR, "can't open pidfile lock: %s (%m)", pidfile_lock); exit(EX_OSERR); } else { if(lock_nonblocking(pidlock_fd, pidfile)) { syslog(LOG_ERR, "can't get exclusive lock on %s", pidfile_lock); exit(EX_TEMPFAIL); } } if(pipe(startup_pipe) == -1) { syslog(LOG_ERR, "can't create startup pipe (%m)"); exit(EX_OSERR); } /* Set the current working directory where cores can go to die. */ const char *path = config_getstring(IMAPOPT_CONFIGDIRECTORY); if (path == NULL) { path = getenv("TMPDIR"); if (path == NULL) path = "/tmp"; } (void) chdir(path); (void) chdir("cores"); do { pid = fork(); if ((pid == -1) && (errno == EAGAIN)) { syslog(LOG_WARNING, "master fork failed (sleeping): %m"); sleep(5); } } while ((pid == -1) && (errno == EAGAIN)); if (pid == -1) { fatal("fork error", EX_OSERR); } else if (pid != 0) { int exit_code; /* Parent, wait for child */ if(read(startup_pipe[0], &exit_code, sizeof(exit_code)) == -1) { syslog(LOG_ERR, "could not read from startup_pipe (%m)"); unlink(pidfile_lock); exit(EX_OSERR); } else { unlink(pidfile_lock); exit(exit_code); } } /* Child! */ close(startup_pipe[0]); free(pidfile_lock); /* * We're now running in the child. Lose our controlling terminal * and obtain a new process group. */ if (setsid() == -1) { int exit_result = EX_OSERR; /* Tell our parent that we failed. */ r = write(startup_pipe[1], &exit_result, sizeof(exit_result)); fatal("setsid failure", EX_OSERR); } } limit_fds(1024); /* Write out the pidfile */ pidfd = open(pidfile, O_CREAT|O_RDWR, 0644); if(pidfd == -1) { int exit_result = EX_OSERR; /* Tell our parent that we failed. */ r = write(startup_pipe[1], &exit_result, sizeof(exit_result)); syslog(LOG_ERR, "can't open pidfile: %m"); exit(EX_OSERR); } else { char buf[100]; if(lock_nonblocking(pidfd, pidfile)) { int exit_result = EX_OSERR; /* Tell our parent that we failed. */ r = write(startup_pipe[1], &exit_result, sizeof(exit_result)); fatal("cannot get exclusive lock on pidfile (is another master still running?)", EX_OSERR); } else { int pidfd_flags = fcntl(pidfd, F_GETFD, 0); if (pidfd_flags != -1) pidfd_flags = fcntl(pidfd, F_SETFD, pidfd_flags | FD_CLOEXEC); if (pidfd_flags == -1) { int exit_result = EX_OSERR; /* Tell our parent that we failed. */ r = write(startup_pipe[1], &exit_result, sizeof(exit_result)); fatalf(EX_OSERR, "unable to set close-on-exec for pidfile: %m"); } /* Write PID */ snprintf(buf, sizeof(buf), "%lu\n", (unsigned long int)getpid()); if(lseek(pidfd, 0, SEEK_SET) == -1 || ftruncate(pidfd, 0) == -1 || write(pidfd, buf, strlen(buf)) == -1) { int exit_result = EX_OSERR; /* Tell our parent that we failed. */ r = write(startup_pipe[1], &exit_result, sizeof(exit_result)); fatalf(EX_OSERR, "unable to write to pidfile: %m"); } if (fsync(pidfd)) fatalf(EX_OSERR, "unable to sync pidfile: %m"); } } if(daemon_mode) { int exit_result = 0; /* success! */ if (write(startup_pipe[1], &exit_result, sizeof(exit_result)) == -1) fatalf(EX_OSERR, "could not write success result to startup pipe (%m)"); close(startup_pipe[1]); xclose(pidlock_fd); } syslog(LOG_DEBUG, "process started"); #if defined(HAVE_UCDSNMP) || defined(HAVE_NETSNMP) /* initialize SNMP agent */ /* make us a agentx client. */ #ifdef HAVE_NETSNMP netsnmp_enable_subagent(); netsnmp_ds_set_boolean(NETSNMP_DS_LIBRARY_ID, NETSNMP_DS_LIB_ALARM_DONT_USE_SIG, 1); if (agentxpinginterval >= 0) netsnmp_ds_set_int(NETSNMP_DS_APPLICATION_ID, NETSNMP_DS_AGENT_AGENTX_PING_INTERVAL, agentxpinginterval); if (agentxsocket != NULL) netsnmp_ds_set_string(NETSNMP_DS_APPLICATION_ID, NETSNMP_DS_AGENT_X_SOCKET, agentxsocket); #else ds_set_boolean(DS_APPLICATION_ID, DS_AGENT_ROLE, 1); #endif /* initialize the agent library */ init_agent("cyrusMaster"); init_cyrusMasterMIB(); init_snmp("cyrusMaster"); #endif #if defined(__linux__) && defined(HAVE_LIBCAP) if (become_cyrus(/*is_master*/1) != 0) { syslog(LOG_ERR, "can't change to the cyrus user: %m"); exit(1); } #endif masterconf_getsection("START", &add_start, NULL); masterconf_getsection("SERVICES", &add_service, NULL); masterconf_getsection("EVENTS", &add_event, NULL); masterconf_getsection("DAEMON", &add_daemon, NULL); /* set signal handlers */ sighandler_setup(); /* initialize services */ for (i = 0; i < nservices; i++) { service_create(&Services[i]); if (verbose > 2) syslog(LOG_DEBUG, "init: service %s/%s socket %d pipe %d %d", Services[i].name, Services[i].familyname, Services[i].socket, Services[i].stat[0], Services[i].stat[1]); } #if !defined(__linux__) || !defined(HAVE_LIBCAP) if (become_cyrus(/*is_master*/1) != 0) { syslog(LOG_ERR, "can't change to the cyrus user: %m"); exit(1); } #endif /* init ctable janitor */ gettimeofday(&now, 0); init_janitor(now); /* ok, we're going to start spawning like mad now */ syslog(LOG_DEBUG, "ready for work"); for (;;) { int r, i, maxfd, total_children = 0; struct timeval tv, *tvptr; struct notify_message msg; #if defined(HAVE_UCDSNMP) || defined(HAVE_NETSNMP) int blockp = 0; #endif if (gotsigquit) { gotsigquit = 0; begin_shutdown(); } /* run any scheduled processes */ if (!in_shutdown) spawn_schedule(now); /* reap first, that way if we need to babysit we will */ if (gotsigchld) { /* order matters here */ gotsigchld = 0; reap_child(); } /* do we have any services undermanned? */ for (i = 0; i < nservices; i++) { total_children += Services[i].nactive; if (!in_shutdown) { if (Services[i].exec /* enabled */ && (Services[i].nactive < Services[i].max_workers) && (Services[i].ready_workers < Services[i].desired_workers)) { /* bring us up to desired_workers */ int j = Services[i].desired_workers - Services[i].ready_workers; if (verbose) { syslog(LOG_DEBUG, "service %s/%s needs %d more ready workers", Services[i].name, Services[i].familyname, j); } while (j-- > 0) { spawn_service(i); } } else if (Services[i].exec && Services[i].babysit && Services[i].nactive == 0) { syslog(LOG_ERR, "lost all children for service: %s/%s. " \ "Applying babysitter.", Services[i].name, Services[i].familyname); spawn_service(i); } else if (!Services[i].exec /* disabled */ && Services[i].name /* not yet removed */ && Services[i].nactive == 0) { if (verbose > 2) syslog(LOG_DEBUG, "remove: service %s/%s pipe %d %d", Services[i].name, Services[i].familyname, Services[i].stat[0], Services[i].stat[1]); /* Only free the service info on the primary */ if (Services[i].associate == 0) { free(Services[i].name); } Services[i].name = NULL; Services[i].nforks = 0; Services[i].nactive = 0; Services[i].nconnections = 0; Services[i].associate = 0; xclose(Services[i].stat[0]); xclose(Services[i].stat[1]); } } } if (in_shutdown && total_children == 0) { syslog(LOG_NOTICE, "All children have exited, closing down"); exit(0); } if (gotsighup) { syslog(LOG_NOTICE, "got SIGHUP"); gotsighup = 0; reread_conf(now); } FD_ZERO(&rfds); maxfd = 0; for (i = 0; i < nservices; i++) { int x = Services[i].stat[0]; int y = Services[i].socket; /* messages */ if (x >= 0) { if (verbose > 2) syslog(LOG_DEBUG, "listening for messages from %s/%s", Services[i].name, Services[i].familyname); FD_SET(x, &rfds); } if (x > maxfd) maxfd = x; /* connections */ if (y >= 0 && Services[i].ready_workers == 0 && Services[i].nactive < Services[i].max_workers && !service_is_fork_limited(&Services[i])) { if (verbose > 2) syslog(LOG_DEBUG, "listening for connections for %s/%s", Services[i].name, Services[i].familyname); FD_SET(y, &rfds); if (y > maxfd) maxfd = y; } /* paranoia */ if (Services[i].ready_workers < 0) { syslog(LOG_ERR, "%s/%s has %d workers?!?", Services[i].name, Services[i].familyname, Services[i].ready_workers); } } maxfd++; /* need 1 greater than maxfd */ int interrupted = 0; do { /* how long to wait? - do now so that any scheduled wakeup * calls get accounted for*/ gettimeofday(&now, 0); tvptr = NULL; if (schedule && !in_shutdown) { double delay = timesub(&now, &schedule->mark); if (!interrupted && delay > 0.0) { timeval_set_double(&tv, delay); } else { tv.tv_sec = 0; tv.tv_usec = 0; } tvptr = &tv; } #if defined(HAVE_UCDSNMP) || defined(HAVE_NETSNMP) if (tvptr == NULL) blockp = 1; snmp_select_info(&maxfd, &rfds, tvptr, &blockp); #endif errno = 0; r = myselect(maxfd, &rfds, NULL, NULL, tvptr); if (r == -1) { switch (errno) { case EAGAIN: case EINTR: /* Try again to get valid rfds, this time without blocking so we * will definitely process messages without getting interrupted * again. */ interrupted++; if (interrupted > 5) { syslog(LOG_WARNING, "Repeatedly interrupted, too many signals?"); /* Fake a timeout */ r = 0; FD_ZERO(&rfds); } break; default: /* uh oh */ fatalf(1, "select failed: %m"); } } } while (!in_shutdown && r == -1); #if defined(HAVE_UCDSNMP) || defined(HAVE_NETSNMP) /* check for SNMP queries */ snmp_read(&rfds); snmp_timeout(); #endif for (i = 0; i < nservices; i++) { int x = Services[i].stat[0]; int y = Services[i].socket; if ((x >= 0) && FD_ISSET(x, &rfds)) { while ((r = read_msg(x, &msg)) == 0) process_msg(i, &msg); if (r == 2) { syslog(LOG_ERR, "got incorrectly sized response from child: %x", i); continue; } if (r < 0) { syslog(LOG_ERR, "error while receiving message from child %x: %m", i); continue; } } if (!in_shutdown && Services[i].exec && Services[i].nactive < Services[i].max_workers && Services[i].ready_workers == 0 && y >= 0 && FD_ISSET(y, &rfds)) { /* huh, someone wants to talk to us */ spawn_service(i); } } gettimeofday(&now, 0); child_janitor(now); #ifdef HAVE_NETSNMP run_alarms(); #endif } /* never reached */ return r; } cyrus-imapd-2.5.10/snmp/0000755000175000017500000000000013001246663012013 500000000000000cyrus-imapd-2.5.10/snmp/snmpgen0000755000175000017500000003076513001236020013325 00000000000000#!/bin/sh # # Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. # # Redistribution and use in source and binary forms, with or without # modification, are permitted provided that the following conditions # are met: # # 1. Redistributions of source code must retain the above copyright # notice, this list of conditions and the following disclaimer. # # 2. Redistributions in binary form must reproduce the above copyright # notice, this list of conditions and the following disclaimer in # the documentation and/or other materials provided with the # distribution. # # 3. The name "Carnegie Mellon University" must not be used to # endorse or promote products derived from this software without # prior written permission. For permission or any legal # details, please contact # Carnegie Mellon University # Center for Technology Transfer and Enterprise Creation # 4615 Forbes Avenue # Suite 302 # Pittsburgh, PA 15213 # (412) 268-7393, fax: (412) 268-7395 # innovation@andrew.cmu.edu # # 4. Redistributions of any form whatsoever must retain the following # acknowledgment: # "This product includes software developed by Computing Services # at Carnegie Mellon University (http://www.cmu.edu/computing/)." # # CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO # THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY # AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE # FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES # WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN # AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING # OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. exec perl -x -S $0 ${1+"$@"} # -*-perl-*- #!perl -w if ($] !~ /^5\..*/) { # uh-oh. this isn't perl 5. foreach (split(/:/, $ENV{PATH})) { # try to find "perl5". exec("$_/perl5", "-w", "-x", "-S", $0, @ARGV) if (-x "$_/perl5"); } # we failed. bail. die "Your perl is too old; I need perl 5.\n"; } # load the real script. this is isolated in an 'eval' so perl4 won't # choke on the perl5-isms. eval join("\n", ); if ($@) { die "$@"; } __END__ require 5; #Tim Martin # 2/10/2000 use Getopt::Long; my $opt_extra = undef; $ret = GetOptions("extra:s"); if (!$ret || $#ARGV != 0) { print STDERR "snmpgen [--extra=trailer.in] app.snmp\n"; exit; } $infile = $ARGV[0]; if ($infile =~ m|.*/(.*)\.snmp|) { $basename = $1; } elsif ($infile =~ m|(.*)\.snmp|) { $basename = $1; } else { $basename = $infile; } print "basename $basename\n"; $outheader = "$basename.h"; $outprog = "$basename.c"; open (INPUT,"<$infile"); my $linenum = 0; my $found = 0; my $base = "NOT"; my $num_cmds = 0; my %T; # maps names to types my %D; # maps names to descs my %O; # maps names to oids push @Varlist, "LISTEND"; #first find the BASE while (defined ($line = )) { $linenum++; if ($line =~ /^#/) { # comment next; } if ($line =~ /^\s*$/) { # just whitespace. ignore next; } if ($line =~ /^define\s+(\w+)\s+((\d|\.|\[\w+\])+)/) { $defname = $1; $defoid = $2; #resolve definitions while ($defoid =~ /(\[(\w+)\])/) { my $f = 0; foreach my $a (keys %Definelist) { if ($a eq $2) { $defoid =~ s/\[\w+\]/$Definelist{$a}/; $f = 1; } } if ($f == 0) { die "Unable to resolve definition $2"; } } $Definelist{$defname} = $defoid; next; } if ($line =~ /^var\s+(\w+)/) { push @Varlist, $1; next; } if ($line =~ /^BASE\s+((\d+|\.|\{\w+\}|\[\w+\])+)/) { $base = $1; #resolve definitions while ($base =~ /(\[(\w+)\])/) { my $f = 0; foreach my $a (keys %Definelist) { if ($a eq $2) { $base =~ s/\[\w+\]/$Definelist{$a}/; $f = 1; } } if ($f == 0) { die "Unable to resolve definition $2"; } } #add lowest base to register list if ($base =~ /((\d+\.)+\d+)/) { push @Registerlist, $1; } undef @baseVlist; #xxx check all vars in varlist while ($base =~ /(\{(\w+)\})/) { push @baseVlist, $2; $base =~ s/\{\w+\}/%d/; } $basecount = 0; next; } chomp $line; ($type, $name, $desc, $oid, $dummy) = split(/\s*,\s*/, $line, 5); if (!(defined $oid) || (defined $dummy)) { die "syntax error on line $linenum\n"; } if ($oid eq "auto") { $oid = $base . ".$basecount"; $basecount++; } else { $oid = $base . "." . $oid; } $T{$name} = $type; $D{$name} = $desc; $O{$name} = $oid; $Ovlist{$name} = [ @baseVlist ]; } open (OUTPUT_H, ">$outheader"); print OUTPUT_H <$outprog"); print OUTPUT_C < #endif #include #include #include #include #include #include #include #include #include #include "index.h" #include "$outheader" extern int close(int); int variable_value[$#Varlist+1]; int variable_tmpvalue[$#Varlist+1]; int varvalue(${basename}_variable_t var) { if (variable_tmpvalue[var]!=-1) return variable_tmpvalue[var]; return variable_value[var]; } const char *snmp_getdescription(${basename}_t evt) { switch (evt) { EOF ; foreach my $a (keys %T) { print OUTPUT_C " case $a: return $D{$a};\n"; } print OUTPUT_C < -1) close(mysock); return 0; } int snmp_increment_args(${basename}_t cmd, int incr, ...) { char tosend[256]; /* xxx UDP max size??? */ char buf[256]; va_list ap; /* varargs thing */ ${basename}_variable_t vval; int ival; if (mysock == -1) return 1; va_start(ap, incr); do { vval = va_arg(ap, ${basename}_variable_t); /* get the next arg */ if (vval!=VARIABLE_LISTEND) { ival = va_arg(ap, int); /* get the next arg */ variable_tmpvalue[vval] = ival; } } while ( vval != VARIABLE_LISTEND); va_end(ap); snprintf(tosend, sizeof(tosend),"C %s %d\\n",snmp_getoid(NULL,cmd,buf,sizeof(buf)), incr); if (sendto(mysock, tosend, strlen(tosend), 0, (struct sockaddr *) &remote, sockaddr_len) == -1) { return 1; } /* set tmp variables back */ va_start(ap, incr); do { vval = va_arg(ap, ${basename}_variable_t); /* get the next arg */ if (vval!=VARIABLE_LISTEND) { ival = va_arg(ap, int); /* get the next arg */ variable_tmpvalue[vval] = -1; } } while ( vval != VARIABLE_LISTEND); va_end(ap); return 0; } int snmp_increment(${basename}_t cmd, int incr) { char tosend[256]; /* xxx UDP max size??? */ char buf[256]; if (mysock == -1) return 1; snprintf(tosend, sizeof(tosend),"C %s %d\\n",snmp_getoid(NULL,cmd,buf,sizeof(buf)), incr); if (sendto(mysock, tosend, strlen(tosend), 0, (struct sockaddr *) &remote, sockaddr_len) == -1) { return 1; } return 0; } int snmp_set(${basename}_t cmd, int value) { char tosend[256]; char buf[256]; if (mysock == -1) return 1; snprintf(tosend, sizeof(tosend),"I %s %d\\n",snmp_getoid(NULL,cmd,buf,sizeof(buf)), value); if (sendto(mysock, tosend, strlen(tosend), 0, (struct sockaddr *) &remote, sockaddr_len) == -1) { return 1; } return 1; } int snmp_set_str(${basename}_t cmd, char *value) { char tosend[256]; char buf[256]; if (mysock == -1) return 1; snprintf(tosend, sizeof(tosend),"S %s %s\\n",snmp_getoid(NULL,cmd,buf,sizeof(buf)), value); if (sendto(mysock, tosend, strlen(tosend), 0, (struct sockaddr *) &remote, sockaddr_len) == -1) { return 1; } return 1; } int snmp_set_time(${basename}_t cmd, time_t t) { char tosend[256]; char buf[256]; if (mysock == -1) return 1; snprintf(tosend, sizeof(tosend),"T %s %lu\\n",snmp_getoid(NULL,cmd,buf,sizeof(buf)), t); if (sendto(mysock, tosend, strlen(tosend), 0, (struct sockaddr *) &remote, sockaddr_len) == -1) { return 1; } return 1; } /* should use SNMPDEFINE's as parameter */ int snmp_set_oid(${basename}_t cmd, char *str) { return snmp_set_str(cmd,str); } void snmp_setvariable(${basename}_variable_t name, int value) { variable_value[name] = value; } #endif EOF ; if (defined $opt_extra) { open (INPUT_IN,"<$opt_extra"); while( ) { print OUTPUT_C; } close INPUT_IN; } close OUTPUT_C; cyrus-imapd-2.5.10/configure0000755000175000017500000244461013001246601012670 00000000000000#! /bin/sh # Guess values for system-dependent variables and create Makefiles. # Generated by GNU Autoconf 2.69 for cyrus-imapd 2.5.10. # # Report bugs to . # # # Copyright (C) 1992-1996, 1998-2012 Free Software Foundation, Inc. # # # This configure script is free software; the Free Software Foundation # gives unlimited permission to copy, distribute and modify it. ## -------------------- ## ## M4sh Initialization. ## ## -------------------- ## # Be more Bourne compatible DUALCASE=1; export DUALCASE # for MKS sh if test -n "${ZSH_VERSION+set}" && (emulate sh) >/dev/null 2>&1; then : emulate sh NULLCMD=: # Pre-4.2 versions of Zsh do word splitting on ${1+"$@"}, which # is contrary to our usage. Disable this feature. alias -g '${1+"$@"}'='"$@"' setopt NO_GLOB_SUBST else case `(set -o) 2>/dev/null` in #( *posix*) : set -o posix ;; #( *) : ;; esac fi as_nl=' ' export as_nl # Printing a long string crashes Solaris 7 /usr/bin/printf. as_echo='\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\' as_echo=$as_echo$as_echo$as_echo$as_echo$as_echo as_echo=$as_echo$as_echo$as_echo$as_echo$as_echo$as_echo # Prefer a ksh shell builtin over an external printf program on Solaris, # but without wasting forks for bash or zsh. if test -z "$BASH_VERSION$ZSH_VERSION" \ && (test "X`print -r -- $as_echo`" = "X$as_echo") 2>/dev/null; then as_echo='print -r --' as_echo_n='print -rn --' elif (test "X`printf %s $as_echo`" = "X$as_echo") 2>/dev/null; then as_echo='printf %s\n' as_echo_n='printf %s' else if test "X`(/usr/ucb/echo -n -n $as_echo) 2>/dev/null`" = "X-n $as_echo"; then as_echo_body='eval /usr/ucb/echo -n "$1$as_nl"' as_echo_n='/usr/ucb/echo -n' else as_echo_body='eval expr "X$1" : "X\\(.*\\)"' as_echo_n_body='eval arg=$1; case $arg in #( *"$as_nl"*) expr "X$arg" : "X\\(.*\\)$as_nl"; arg=`expr "X$arg" : ".*$as_nl\\(.*\\)"`;; esac; expr "X$arg" : "X\\(.*\\)" | tr -d "$as_nl" ' export as_echo_n_body as_echo_n='sh -c $as_echo_n_body as_echo' fi export as_echo_body as_echo='sh -c $as_echo_body as_echo' fi # The user is always right. if test "${PATH_SEPARATOR+set}" != set; then PATH_SEPARATOR=: (PATH='/bin;/bin'; FPATH=$PATH; sh -c :) >/dev/null 2>&1 && { (PATH='/bin:/bin'; FPATH=$PATH; sh -c :) >/dev/null 2>&1 || PATH_SEPARATOR=';' } fi # IFS # We need space, tab and new line, in precisely that order. Quoting is # there to prevent editors from complaining about space-tab. # (If _AS_PATH_WALK were called with IFS unset, it would disable word # splitting by setting IFS to empty value.) IFS=" "" $as_nl" # Find who we are. Look in the path if we contain no directory separator. as_myself= case $0 in #(( *[\\/]* ) as_myself=$0 ;; *) as_save_IFS=$IFS; IFS=$PATH_SEPARATOR for as_dir in $PATH do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. test -r "$as_dir/$0" && as_myself=$as_dir/$0 && break done IFS=$as_save_IFS ;; esac # We did not find ourselves, most probably we were run as `sh COMMAND' # in which case we are not to be found in the path. if test "x$as_myself" = x; then as_myself=$0 fi if test ! -f "$as_myself"; then $as_echo "$as_myself: error: cannot find myself; rerun with an absolute file name" >&2 exit 1 fi # Unset variables that we do not need and which cause bugs (e.g. in # pre-3.0 UWIN ksh). But do not cause bugs in bash 2.01; the "|| exit 1" # suppresses any "Segmentation fault" message there. '((' could # trigger a bug in pdksh 5.2.14. for as_var in BASH_ENV ENV MAIL MAILPATH do eval test x\${$as_var+set} = xset \ && ( (unset $as_var) || exit 1) >/dev/null 2>&1 && unset $as_var || : done PS1='$ ' PS2='> ' PS4='+ ' # NLS nuisances. LC_ALL=C export LC_ALL LANGUAGE=C export LANGUAGE # CDPATH. (unset CDPATH) >/dev/null 2>&1 && unset CDPATH # Use a proper internal environment variable to ensure we don't fall # into an infinite loop, continuously re-executing ourselves. if test x"${_as_can_reexec}" != xno && test "x$CONFIG_SHELL" != x; then _as_can_reexec=no; export _as_can_reexec; # We cannot yet assume a decent shell, so we have to provide a # neutralization value for shells without unset; and this also # works around shells that cannot unset nonexistent variables. # Preserve -v and -x to the replacement shell. BASH_ENV=/dev/null ENV=/dev/null (unset BASH_ENV) >/dev/null 2>&1 && unset BASH_ENV ENV case $- in # (((( *v*x* | *x*v* ) as_opts=-vx ;; *v* ) as_opts=-v ;; *x* ) as_opts=-x ;; * ) as_opts= ;; esac exec $CONFIG_SHELL $as_opts "$as_myself" ${1+"$@"} # Admittedly, this is quite paranoid, since all the known shells bail # out after a failed `exec'. $as_echo "$0: could not re-execute with $CONFIG_SHELL" >&2 as_fn_exit 255 fi # We don't want this to propagate to other subprocesses. { _as_can_reexec=; unset _as_can_reexec;} if test "x$CONFIG_SHELL" = x; then as_bourne_compatible="if test -n \"\${ZSH_VERSION+set}\" && (emulate sh) >/dev/null 2>&1; then : emulate sh NULLCMD=: # Pre-4.2 versions of Zsh do word splitting on \${1+\"\$@\"}, which # is contrary to our usage. Disable this feature. alias -g '\${1+\"\$@\"}'='\"\$@\"' setopt NO_GLOB_SUBST else case \`(set -o) 2>/dev/null\` in #( *posix*) : set -o posix ;; #( *) : ;; esac fi " as_required="as_fn_return () { (exit \$1); } as_fn_success () { as_fn_return 0; } as_fn_failure () { as_fn_return 1; } as_fn_ret_success () { return 0; } as_fn_ret_failure () { return 1; } exitcode=0 as_fn_success || { exitcode=1; echo as_fn_success failed.; } as_fn_failure && { exitcode=1; echo as_fn_failure succeeded.; } as_fn_ret_success || { exitcode=1; echo as_fn_ret_success failed.; } as_fn_ret_failure && { exitcode=1; echo as_fn_ret_failure succeeded.; } if ( set x; as_fn_ret_success y && test x = \"\$1\" ); then : else exitcode=1; echo positional parameters were not saved. fi test x\$exitcode = x0 || exit 1 test -x / || exit 1" as_suggested=" as_lineno_1=";as_suggested=$as_suggested$LINENO;as_suggested=$as_suggested" as_lineno_1a=\$LINENO as_lineno_2=";as_suggested=$as_suggested$LINENO;as_suggested=$as_suggested" as_lineno_2a=\$LINENO eval 'test \"x\$as_lineno_1'\$as_run'\" != \"x\$as_lineno_2'\$as_run'\" && test \"x\`expr \$as_lineno_1'\$as_run' + 1\`\" = \"x\$as_lineno_2'\$as_run'\"' || exit 1 test \$(( 1 + 1 )) = 2 || exit 1 test -n \"\${ZSH_VERSION+set}\${BASH_VERSION+set}\" || ( ECHO='\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\' ECHO=\$ECHO\$ECHO\$ECHO\$ECHO\$ECHO ECHO=\$ECHO\$ECHO\$ECHO\$ECHO\$ECHO\$ECHO PATH=/empty FPATH=/empty; export PATH FPATH test \"X\`printf %s \$ECHO\`\" = \"X\$ECHO\" \\ || test \"X\`print -r -- \$ECHO\`\" = \"X\$ECHO\" ) || exit 1" if (eval "$as_required") 2>/dev/null; then : as_have_required=yes else as_have_required=no fi if test x$as_have_required = xyes && (eval "$as_suggested") 2>/dev/null; then : else as_save_IFS=$IFS; IFS=$PATH_SEPARATOR as_found=false for as_dir in /bin$PATH_SEPARATOR/usr/bin$PATH_SEPARATOR$PATH do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. as_found=: case $as_dir in #( /*) for as_base in sh bash ksh sh5; do # Try only shells that exist, to save several forks. as_shell=$as_dir/$as_base if { test -f "$as_shell" || test -f "$as_shell.exe"; } && { $as_echo "$as_bourne_compatible""$as_required" | as_run=a "$as_shell"; } 2>/dev/null; then : CONFIG_SHELL=$as_shell as_have_required=yes if { $as_echo "$as_bourne_compatible""$as_suggested" | as_run=a "$as_shell"; } 2>/dev/null; then : break 2 fi fi done;; esac as_found=false done $as_found || { if { test -f "$SHELL" || test -f "$SHELL.exe"; } && { $as_echo "$as_bourne_compatible""$as_required" | as_run=a "$SHELL"; } 2>/dev/null; then : CONFIG_SHELL=$SHELL as_have_required=yes fi; } IFS=$as_save_IFS if test "x$CONFIG_SHELL" != x; then : export CONFIG_SHELL # We cannot yet assume a decent shell, so we have to provide a # neutralization value for shells without unset; and this also # works around shells that cannot unset nonexistent variables. # Preserve -v and -x to the replacement shell. BASH_ENV=/dev/null ENV=/dev/null (unset BASH_ENV) >/dev/null 2>&1 && unset BASH_ENV ENV case $- in # (((( *v*x* | *x*v* ) as_opts=-vx ;; *v* ) as_opts=-v ;; *x* ) as_opts=-x ;; * ) as_opts= ;; esac exec $CONFIG_SHELL $as_opts "$as_myself" ${1+"$@"} # Admittedly, this is quite paranoid, since all the known shells bail # out after a failed `exec'. $as_echo "$0: could not re-execute with $CONFIG_SHELL" >&2 exit 255 fi if test x$as_have_required = xno; then : $as_echo "$0: This script requires a shell more modern than all" $as_echo "$0: the shells that I found on your system." if test x${ZSH_VERSION+set} = xset ; then $as_echo "$0: In particular, zsh $ZSH_VERSION has bugs and should" $as_echo "$0: be upgraded to zsh 4.3.4 or later." else $as_echo "$0: Please tell bug-autoconf@gnu.org and $0: https://github.com/cyrusimap/cyrus-imapd/issues about $0: your system, including any error possibly output before $0: this message. Then install a modern shell, or manually $0: run the script under such a shell if you do have one." fi exit 1 fi fi fi SHELL=${CONFIG_SHELL-/bin/sh} export SHELL # Unset more variables known to interfere with behavior of common tools. CLICOLOR_FORCE= GREP_OPTIONS= unset CLICOLOR_FORCE GREP_OPTIONS ## --------------------- ## ## M4sh Shell Functions. ## ## --------------------- ## # as_fn_unset VAR # --------------- # Portably unset VAR. as_fn_unset () { { eval $1=; unset $1;} } as_unset=as_fn_unset # as_fn_set_status STATUS # ----------------------- # Set $? to STATUS, without forking. as_fn_set_status () { return $1 } # as_fn_set_status # as_fn_exit STATUS # ----------------- # Exit the shell with STATUS, even in a "trap 0" or "set -e" context. as_fn_exit () { set +e as_fn_set_status $1 exit $1 } # as_fn_exit # as_fn_mkdir_p # ------------- # Create "$as_dir" as a directory, including parents if necessary. as_fn_mkdir_p () { case $as_dir in #( -*) as_dir=./$as_dir;; esac test -d "$as_dir" || eval $as_mkdir_p || { as_dirs= while :; do case $as_dir in #( *\'*) as_qdir=`$as_echo "$as_dir" | sed "s/'/'\\\\\\\\''/g"`;; #'( *) as_qdir=$as_dir;; esac as_dirs="'$as_qdir' $as_dirs" as_dir=`$as_dirname -- "$as_dir" || $as_expr X"$as_dir" : 'X\(.*[^/]\)//*[^/][^/]*/*$' \| \ X"$as_dir" : 'X\(//\)[^/]' \| \ X"$as_dir" : 'X\(//\)$' \| \ X"$as_dir" : 'X\(/\)' \| . 2>/dev/null || $as_echo X"$as_dir" | sed '/^X\(.*[^/]\)\/\/*[^/][^/]*\/*$/{ s//\1/ q } /^X\(\/\/\)[^/].*/{ s//\1/ q } /^X\(\/\/\)$/{ s//\1/ q } /^X\(\/\).*/{ s//\1/ q } s/.*/./; q'` test -d "$as_dir" && break done test -z "$as_dirs" || eval "mkdir $as_dirs" } || test -d "$as_dir" || as_fn_error $? "cannot create directory $as_dir" } # as_fn_mkdir_p # as_fn_executable_p FILE # ----------------------- # Test if FILE is an executable regular file. as_fn_executable_p () { test -f "$1" && test -x "$1" } # as_fn_executable_p # as_fn_append VAR VALUE # ---------------------- # Append the text in VALUE to the end of the definition contained in VAR. Take # advantage of any shell optimizations that allow amortized linear growth over # repeated appends, instead of the typical quadratic growth present in naive # implementations. if (eval "as_var=1; as_var+=2; test x\$as_var = x12") 2>/dev/null; then : eval 'as_fn_append () { eval $1+=\$2 }' else as_fn_append () { eval $1=\$$1\$2 } fi # as_fn_append # as_fn_arith ARG... # ------------------ # Perform arithmetic evaluation on the ARGs, and store the result in the # global $as_val. Take advantage of shells that can avoid forks. The arguments # must be portable across $(()) and expr. if (eval "test \$(( 1 + 1 )) = 2") 2>/dev/null; then : eval 'as_fn_arith () { as_val=$(( $* )) }' else as_fn_arith () { as_val=`expr "$@" || test $? -eq 1` } fi # as_fn_arith # as_fn_error STATUS ERROR [LINENO LOG_FD] # ---------------------------------------- # Output "`basename $0`: error: ERROR" to stderr. If LINENO and LOG_FD are # provided, also output the error to LOG_FD, referencing LINENO. Then exit the # script with STATUS, using 1 if that was 0. as_fn_error () { as_status=$1; test $as_status -eq 0 && as_status=1 if test "$4"; then as_lineno=${as_lineno-"$3"} as_lineno_stack=as_lineno_stack=$as_lineno_stack $as_echo "$as_me:${as_lineno-$LINENO}: error: $2" >&$4 fi $as_echo "$as_me: error: $2" >&2 as_fn_exit $as_status } # as_fn_error if expr a : '\(a\)' >/dev/null 2>&1 && test "X`expr 00001 : '.*\(...\)'`" = X001; then as_expr=expr else as_expr=false fi if (basename -- /) >/dev/null 2>&1 && test "X`basename -- / 2>&1`" = "X/"; then as_basename=basename else as_basename=false fi if (as_dir=`dirname -- /` && test "X$as_dir" = X/) >/dev/null 2>&1; then as_dirname=dirname else as_dirname=false fi as_me=`$as_basename -- "$0" || $as_expr X/"$0" : '.*/\([^/][^/]*\)/*$' \| \ X"$0" : 'X\(//\)$' \| \ X"$0" : 'X\(/\)' \| . 2>/dev/null || $as_echo X/"$0" | sed '/^.*\/\([^/][^/]*\)\/*$/{ s//\1/ q } /^X\/\(\/\/\)$/{ s//\1/ q } /^X\/\(\/\).*/{ s//\1/ q } s/.*/./; q'` # Avoid depending upon Character Ranges. as_cr_letters='abcdefghijklmnopqrstuvwxyz' as_cr_LETTERS='ABCDEFGHIJKLMNOPQRSTUVWXYZ' as_cr_Letters=$as_cr_letters$as_cr_LETTERS as_cr_digits='0123456789' as_cr_alnum=$as_cr_Letters$as_cr_digits as_lineno_1=$LINENO as_lineno_1a=$LINENO as_lineno_2=$LINENO as_lineno_2a=$LINENO eval 'test "x$as_lineno_1'$as_run'" != "x$as_lineno_2'$as_run'" && test "x`expr $as_lineno_1'$as_run' + 1`" = "x$as_lineno_2'$as_run'"' || { # Blame Lee E. McMahon (1931-1989) for sed's syntax. :-) sed -n ' p /[$]LINENO/= ' <$as_myself | sed ' s/[$]LINENO.*/&-/ t lineno b :lineno N :loop s/[$]LINENO\([^'$as_cr_alnum'_].*\n\)\(.*\)/\2\1\2/ t loop s/-\n.*// ' >$as_me.lineno && chmod +x "$as_me.lineno" || { $as_echo "$as_me: error: cannot create $as_me.lineno; rerun with a POSIX shell" >&2; as_fn_exit 1; } # If we had to re-execute with $CONFIG_SHELL, we're ensured to have # already done that, so ensure we don't try to do so again and fall # in an infinite loop. This has already happened in practice. _as_can_reexec=no; export _as_can_reexec # Don't try to exec as it changes $[0], causing all sort of problems # (the dirname of $[0] is not the place where we might find the # original and so on. Autoconf is especially sensitive to this). . "./$as_me.lineno" # Exit status is that of the last command. exit } ECHO_C= ECHO_N= ECHO_T= case `echo -n x` in #((((( -n*) case `echo 'xy\c'` in *c*) ECHO_T=' ';; # ECHO_T is single tab character. xy) ECHO_C='\c';; *) echo `echo ksh88 bug on AIX 6.1` > /dev/null ECHO_T=' ';; esac;; *) ECHO_N='-n';; esac rm -f conf$$ conf$$.exe conf$$.file if test -d conf$$.dir; then rm -f conf$$.dir/conf$$.file else rm -f conf$$.dir mkdir conf$$.dir 2>/dev/null fi if (echo >conf$$.file) 2>/dev/null; then if ln -s conf$$.file conf$$ 2>/dev/null; then as_ln_s='ln -s' # ... but there are two gotchas: # 1) On MSYS, both `ln -s file dir' and `ln file dir' fail. # 2) DJGPP < 2.04 has no symlinks; `ln -s' creates a wrapper executable. # In both cases, we have to default to `cp -pR'. ln -s conf$$.file conf$$.dir 2>/dev/null && test ! -f conf$$.exe || as_ln_s='cp -pR' elif ln conf$$.file conf$$ 2>/dev/null; then as_ln_s=ln else as_ln_s='cp -pR' fi else as_ln_s='cp -pR' fi rm -f conf$$ conf$$.exe conf$$.dir/conf$$.file conf$$.file rmdir conf$$.dir 2>/dev/null if mkdir -p . 2>/dev/null; then as_mkdir_p='mkdir -p "$as_dir"' else test -d ./-p && rmdir ./-p as_mkdir_p=false fi as_test_x='test -x' as_executable_p=as_fn_executable_p # Sed expression to map a string onto a valid CPP name. as_tr_cpp="eval sed 'y%*$as_cr_letters%P$as_cr_LETTERS%;s%[^_$as_cr_alnum]%_%g'" # Sed expression to map a string onto a valid variable name. as_tr_sh="eval sed 'y%*+%pp%;s%[^_$as_cr_alnum]%_%g'" SHELL=${CONFIG_SHELL-/bin/sh} test -n "$DJDIR" || exec 7<&0 &1 # Name of the host. # hostname on some systems (SVR3.2, old GNU/Linux) returns a bogus exit status, # so uname gets run too. ac_hostname=`(hostname || uname -n) 2>/dev/null | sed 1q` # # Initializations. # ac_default_prefix=/usr/local ac_clean_files= ac_config_libobj_dir=. LIBOBJS= cross_compiling=no subdirs= MFLAGS= MAKEFLAGS= # Identity of this package. PACKAGE_NAME='cyrus-imapd' PACKAGE_TARNAME='cyrus-imapd' PACKAGE_VERSION='2.5.10' PACKAGE_STRING='cyrus-imapd 2.5.10' PACKAGE_BUGREPORT='https://github.com/cyrusimap/cyrus-imapd/issues' PACKAGE_URL='https://www.cyrusimap.org' ac_unique_file="imap/imapd.c" ac_config_libobj_dir=lib # Factoring default headers for most tests. ac_includes_default="\ #include #ifdef HAVE_SYS_TYPES_H # include #endif #ifdef HAVE_SYS_STAT_H # include #endif #ifdef STDC_HEADERS # include # include #else # ifdef HAVE_STDLIB_H # include # endif #endif #ifdef HAVE_STRING_H # if !defined STDC_HEADERS && defined HAVE_MEMORY_H # include # endif # include #endif #ifdef HAVE_STRINGS_H # include #endif #ifdef HAVE_INTTYPES_H # include #endif #ifdef HAVE_STDINT_H # include #endif #ifdef HAVE_UNISTD_H # include #endif" ac_subst_vars='am__EXEEXT_FALSE am__EXEEXT_TRUE LTLIBOBJS CUNIT_FALSE CUNIT_TRUE LIB_UUID LIB_RT LIB_UCDSNMP SNMP_CONFIG LIB_WRAP PERL_PREINSTALL PERL_CCCDLFLAGS PERL_FALSE PERL_TRUE PERL SASLFLAGS LIB_SASL DYNSASLFLAGS LIB_DYN_SASL GSSAPIBASE_LIBS LIB_CRYPT CMULOCAL_FALSE CMULOCAL_TRUE GPERF COM_ERR_CPPFLAGS COM_ERR_LIBS PKG_CONFIG_COM_ERR_LIB COM_ERR_FALSE COM_ERR_TRUE COMPILE_ET REPLICATION_FALSE REPLICATION_TRUE HTTP_LIBS HTTP_CPPFLAGS ICU_LIBS ICU_CFLAGS DKIM_LIBS DKIM_CFLAGS JSON_LIBS JSON_CFLAGS SQLITE3_LIBS SQLITE3_CFLAGS ICAL_LIBS ICAL_CFLAGS XML2_LIBS XML2_CFLAGS HTTPD_FALSE HTTPD_TRUE MURDER_FALSE MURDER_TRUE NNTPD_FALSE NNTPD_TRUE IDLED_FALSE IDLED_TRUE AUTOCREATE_FALSE AUTOCREATE_TRUE JANSSON_FALSE JANSSON_TRUE JANSSON_LIBS JANSSON_CFLAGS ZEPHYR_FALSE ZEPHYR_TRUE ZEPHYR_LIBS ZLIB CMU_LIB_SUBDIR SSL_LIBS SSL_CPPFLAGS HAVE_SSL_FALSE HAVE_SSL_TRUE OPENSSL_LIBS OPENSSL_CFLAGS SERVER_FALSE SERVER_TRUE HAVE_CLAMAV_FALSE HAVE_CLAMAV_TRUE LIB_CLAMAV PTCLIENT_FALSE PTCLIENT_TRUE HAVE_LDAP_FALSE HAVE_LDAP_TRUE LDAP_LIBS LDAP_LDFLAGS LDAP_CPPFLAGS USE_AFSKRB_FALSE USE_AFSKRB_TRUE AFS_LIBS AFS_LDFLAGS cyrus_cv_sigveclib LOCK_FCNTL_FALSE LOCK_FCNTL_TRUE MAP_STUPIDSHARED_FALSE MAP_STUPIDSHARED_TRUE MAP_SHARED_FALSE MAP_SHARED_TRUE GMTOFF_TM_FALSE GMTOFF_TM_TRUE NONBLOCK_FCNTL_FALSE NONBLOCK_FCNTL_TRUE SIEVE_FALSE SIEVE_TRUE LEXLIB LEX_OUTPUT_ROOT LEX YFLAGS YACC USE_SQL_FALSE USE_SQL_TRUE USE_BERKELEY_FALSE USE_BERKELEY_TRUE BDB_LIB BDB_INC LOCALDEFS IPV6_noGETNAMEINFO_FALSE IPV6_noGETNAMEINFO_TRUE IPV6_noGETADDRINFO_FALSE IPV6_noGETADDRINFO_TRUE LIB_SOCKET LIBOBJS LIBTOOL_DEPS LT_SYS_LIBRARY_PATH OTOOL64 OTOOL LIPO NMEDIT DSYMUTIL MANIFEST_TOOL RANLIB ac_ct_AR AR DLLTOOL OBJDUMP NM ac_ct_DUMPBIN DUMPBIN LD FGREP SED LIBTOOL HAVE_VISIBILITY CFLAG_VISIBILITY EGREP GREP CPP LN_S am__fastdepCC_FALSE am__fastdepCC_TRUE CCDEPMODE am__nodep AMDEPBACKSLASH AMDEP_FALSE AMDEP_TRUE am__quote am__include DEPDIR OBJEXT EXEEXT ac_ct_CC CPPFLAGS LDFLAGS CFLAGS CC cyrus_group cyrus_user servicedir userdir COV_LDFLAGS COV_CFLAGS MAINT MAINTAINER_MODE_FALSE MAINTAINER_MODE_TRUE AM_BACKSLASH AM_DEFAULT_VERBOSITY AM_DEFAULT_V AM_V am__untar am__tar AMTAR am__leading_dot SET_MAKE AWK mkdir_p MKDIR_P INSTALL_STRIP_PROGRAM STRIP install_sh MAKEINFO AUTOHEADER AUTOMAKE AUTOCONF ACLOCAL VERSION PACKAGE CYGPATH_W am__isrc INSTALL_DATA INSTALL_SCRIPT INSTALL_PROGRAM PKG_CONFIG_LIBDIR PKG_CONFIG_PATH PKG_CONFIG target_os target_vendor target_cpu target host_os host_vendor host_cpu host build_os build_vendor build_cpu build target_alias host_alias build_alias LIBS ECHO_T ECHO_N ECHO_C DEFS mandir localedir libdir psdir pdfdir dvidir htmldir infodir docdir oldincludedir includedir runstatedir localstatedir sharedstatedir sysconfdir datadir datarootdir libexecdir sbindir bindir program_transform_name prefix exec_prefix PACKAGE_URL PACKAGE_BUGREPORT PACKAGE_STRING PACKAGE_VERSION PACKAGE_TARNAME PACKAGE_NAME PATH_SEPARATOR SHELL' ac_subst_files='' ac_user_opts=' enable_option_checking enable_silent_rules with_extraident enable_maintainer_mode enable_coverage with_login with_cyrus_prefix with_service_path with_cyrus_user with_cyrus_group enable_dependency_tracking enable_static enable_shared with_pic enable_fast_install with_aix_soname with_gnu_ld with_sysroot enable_libtool_lock with_bdb with_dbdir with_bdb_libdir with_bdb_incdir with_mysql_libdir with_mysql_incdir with_mysql with_pgsql with_pgsql_libdir with_pgsql_incdir with_sqlite with_sqlite_libdir with_sqlite_incdir enable_sieve enable_pcre with_mmap with_lock enable_afs with_afs_libdir with_afs_incdir with_ldap enable_krb5afspts with_clamav enable_server with_krb with_krbimpl enable_statickrb with_krbdes with_openssl with_egd_socket with_lib_subdir with_zlib with_zephyr with_libcap enable_event_notification with_pidfile enable_autocreate enable_idled enable_nntp enable_murder enable_http enable_replication with_com_err with_syslogfacility enable_cmulocal enable_oldsievename enable_netscapehack enable_gssapi with_gss_impl with_sasl with_staticsasl with_perl with_libwrap with_snmp with_ucdsnmp enable_unit_tests ' ac_precious_vars='build_alias host_alias target_alias PKG_CONFIG PKG_CONFIG_PATH PKG_CONFIG_LIBDIR CC CFLAGS LDFLAGS LIBS CPPFLAGS CPP LT_SYS_LIBRARY_PATH YACC YFLAGS OPENSSL_CFLAGS OPENSSL_LIBS JANSSON_CFLAGS JANSSON_LIBS XML2_CFLAGS XML2_LIBS ICAL_CFLAGS ICAL_LIBS SQLITE3_CFLAGS SQLITE3_LIBS JSON_CFLAGS JSON_LIBS ICU_CFLAGS ICU_LIBS' # Initialize some variables set by options. ac_init_help= ac_init_version=false ac_unrecognized_opts= ac_unrecognized_sep= # The variables have the same names as the options, with # dashes changed to underlines. cache_file=/dev/null exec_prefix=NONE no_create= no_recursion= prefix=NONE program_prefix=NONE program_suffix=NONE program_transform_name=s,x,x, silent= site= srcdir= verbose= x_includes=NONE x_libraries=NONE # Installation directory options. # These are left unexpanded so users can "make install exec_prefix=/foo" # and all the variables that are supposed to be based on exec_prefix # by default will actually change. # Use braces instead of parens because sh, perl, etc. also accept them. # (The list follows the same order as the GNU Coding Standards.) bindir='${exec_prefix}/bin' sbindir='${exec_prefix}/sbin' libexecdir='${exec_prefix}/libexec' datarootdir='${prefix}/share' datadir='${datarootdir}' sysconfdir='${prefix}/etc' sharedstatedir='${prefix}/com' localstatedir='${prefix}/var' runstatedir='${localstatedir}/run' includedir='${prefix}/include' oldincludedir='/usr/include' docdir='${datarootdir}/doc/${PACKAGE_TARNAME}' infodir='${datarootdir}/info' htmldir='${docdir}' dvidir='${docdir}' pdfdir='${docdir}' psdir='${docdir}' libdir='${exec_prefix}/lib' localedir='${datarootdir}/locale' mandir='${datarootdir}/man' ac_prev= ac_dashdash= for ac_option do # If the previous option needs an argument, assign it. if test -n "$ac_prev"; then eval $ac_prev=\$ac_option ac_prev= continue fi case $ac_option in *=?*) ac_optarg=`expr "X$ac_option" : '[^=]*=\(.*\)'` ;; *=) ac_optarg= ;; *) ac_optarg=yes ;; esac # Accept the important Cygnus configure options, so we can diagnose typos. case $ac_dashdash$ac_option in --) ac_dashdash=yes ;; -bindir | --bindir | --bindi | --bind | --bin | --bi) ac_prev=bindir ;; -bindir=* | --bindir=* | --bindi=* | --bind=* | --bin=* | --bi=*) bindir=$ac_optarg ;; -build | --build | --buil | --bui | --bu) ac_prev=build_alias ;; -build=* | --build=* | --buil=* | --bui=* | --bu=*) build_alias=$ac_optarg ;; -cache-file | --cache-file | --cache-fil | --cache-fi \ | --cache-f | --cache- | --cache | --cach | --cac | --ca | --c) ac_prev=cache_file ;; -cache-file=* | --cache-file=* | --cache-fil=* | --cache-fi=* \ | --cache-f=* | --cache-=* | --cache=* | --cach=* | --cac=* | --ca=* | --c=*) cache_file=$ac_optarg ;; --config-cache | -C) cache_file=config.cache ;; -datadir | --datadir | --datadi | --datad) ac_prev=datadir ;; -datadir=* | --datadir=* | --datadi=* | --datad=*) datadir=$ac_optarg ;; -datarootdir | --datarootdir | --datarootdi | --datarootd | --dataroot \ | --dataroo | --dataro | --datar) ac_prev=datarootdir ;; -datarootdir=* | --datarootdir=* | --datarootdi=* | --datarootd=* \ | --dataroot=* | --dataroo=* | --dataro=* | --datar=*) datarootdir=$ac_optarg ;; -disable-* | --disable-*) ac_useropt=`expr "x$ac_option" : 'x-*disable-\(.*\)'` # Reject names that are not valid shell variable names. expr "x$ac_useropt" : ".*[^-+._$as_cr_alnum]" >/dev/null && as_fn_error $? "invalid feature name: $ac_useropt" ac_useropt_orig=$ac_useropt ac_useropt=`$as_echo "$ac_useropt" | sed 's/[-+.]/_/g'` case $ac_user_opts in *" "enable_$ac_useropt" "*) ;; *) ac_unrecognized_opts="$ac_unrecognized_opts$ac_unrecognized_sep--disable-$ac_useropt_orig" ac_unrecognized_sep=', ';; esac eval enable_$ac_useropt=no ;; -docdir | --docdir | --docdi | --doc | --do) ac_prev=docdir ;; -docdir=* | --docdir=* | --docdi=* | --doc=* | --do=*) docdir=$ac_optarg ;; -dvidir | --dvidir | --dvidi | --dvid | --dvi | --dv) ac_prev=dvidir ;; -dvidir=* | --dvidir=* | --dvidi=* | --dvid=* | --dvi=* | --dv=*) dvidir=$ac_optarg ;; -enable-* | --enable-*) ac_useropt=`expr "x$ac_option" : 'x-*enable-\([^=]*\)'` # Reject names that are not valid shell variable names. expr "x$ac_useropt" : ".*[^-+._$as_cr_alnum]" >/dev/null && as_fn_error $? "invalid feature name: $ac_useropt" ac_useropt_orig=$ac_useropt ac_useropt=`$as_echo "$ac_useropt" | sed 's/[-+.]/_/g'` case $ac_user_opts in *" "enable_$ac_useropt" "*) ;; *) ac_unrecognized_opts="$ac_unrecognized_opts$ac_unrecognized_sep--enable-$ac_useropt_orig" ac_unrecognized_sep=', ';; esac eval enable_$ac_useropt=\$ac_optarg ;; -exec-prefix | --exec_prefix | --exec-prefix | --exec-prefi \ | --exec-pref | --exec-pre | --exec-pr | --exec-p | --exec- \ | --exec | --exe | --ex) ac_prev=exec_prefix ;; -exec-prefix=* | --exec_prefix=* | --exec-prefix=* | --exec-prefi=* \ | --exec-pref=* | --exec-pre=* | --exec-pr=* | --exec-p=* | --exec-=* \ | --exec=* | --exe=* | --ex=*) exec_prefix=$ac_optarg ;; -gas | --gas | --ga | --g) # Obsolete; use --with-gas. with_gas=yes ;; -help | --help | --hel | --he | -h) ac_init_help=long ;; -help=r* | --help=r* | --hel=r* | --he=r* | -hr*) ac_init_help=recursive ;; -help=s* | --help=s* | --hel=s* | --he=s* | -hs*) ac_init_help=short ;; -host | --host | --hos | --ho) ac_prev=host_alias ;; -host=* | --host=* | --hos=* | --ho=*) host_alias=$ac_optarg ;; -htmldir | --htmldir | --htmldi | --htmld | --html | --htm | --ht) ac_prev=htmldir ;; -htmldir=* | --htmldir=* | --htmldi=* | --htmld=* | --html=* | --htm=* \ | --ht=*) htmldir=$ac_optarg ;; -includedir | --includedir | --includedi | --included | --include \ | --includ | --inclu | --incl | --inc) ac_prev=includedir ;; -includedir=* | --includedir=* | --includedi=* | --included=* | --include=* \ | --includ=* | --inclu=* | --incl=* | --inc=*) includedir=$ac_optarg ;; -infodir | --infodir | --infodi | --infod | --info | --inf) ac_prev=infodir ;; -infodir=* | --infodir=* | --infodi=* | --infod=* | --info=* | --inf=*) infodir=$ac_optarg ;; -libdir | --libdir | --libdi | --libd) ac_prev=libdir ;; -libdir=* | --libdir=* | --libdi=* | --libd=*) libdir=$ac_optarg ;; -libexecdir | --libexecdir | --libexecdi | --libexecd | --libexec \ | --libexe | --libex | --libe) ac_prev=libexecdir ;; -libexecdir=* | --libexecdir=* | --libexecdi=* | --libexecd=* | --libexec=* \ | --libexe=* | --libex=* | --libe=*) libexecdir=$ac_optarg ;; -localedir | --localedir | --localedi | --localed | --locale) ac_prev=localedir ;; -localedir=* | --localedir=* | --localedi=* | --localed=* | --locale=*) localedir=$ac_optarg ;; -localstatedir | --localstatedir | --localstatedi | --localstated \ | --localstate | --localstat | --localsta | --localst | --locals) ac_prev=localstatedir ;; -localstatedir=* | --localstatedir=* | --localstatedi=* | --localstated=* \ | --localstate=* | --localstat=* | --localsta=* | --localst=* | --locals=*) localstatedir=$ac_optarg ;; -mandir | --mandir | --mandi | --mand | --man | --ma | --m) ac_prev=mandir ;; -mandir=* | --mandir=* | --mandi=* | --mand=* | --man=* | --ma=* | --m=*) mandir=$ac_optarg ;; -nfp | --nfp | --nf) # Obsolete; use --without-fp. with_fp=no ;; -no-create | --no-create | --no-creat | --no-crea | --no-cre \ | --no-cr | --no-c | -n) no_create=yes ;; -no-recursion | --no-recursion | --no-recursio | --no-recursi \ | --no-recurs | --no-recur | --no-recu | --no-rec | --no-re | --no-r) no_recursion=yes ;; -oldincludedir | --oldincludedir | --oldincludedi | --oldincluded \ | --oldinclude | --oldinclud | --oldinclu | --oldincl | --oldinc \ | --oldin | --oldi | --old | --ol | --o) ac_prev=oldincludedir ;; -oldincludedir=* | --oldincludedir=* | --oldincludedi=* | --oldincluded=* \ | --oldinclude=* | --oldinclud=* | --oldinclu=* | --oldincl=* | --oldinc=* \ | --oldin=* | --oldi=* | --old=* | --ol=* | --o=*) oldincludedir=$ac_optarg ;; -prefix | --prefix | --prefi | --pref | --pre | --pr | --p) ac_prev=prefix ;; -prefix=* | --prefix=* | --prefi=* | --pref=* | --pre=* | --pr=* | --p=*) prefix=$ac_optarg ;; -program-prefix | --program-prefix | --program-prefi | --program-pref \ | --program-pre | --program-pr | --program-p) ac_prev=program_prefix ;; -program-prefix=* | --program-prefix=* | --program-prefi=* \ | --program-pref=* | --program-pre=* | --program-pr=* | --program-p=*) program_prefix=$ac_optarg ;; -program-suffix | --program-suffix | --program-suffi | --program-suff \ | --program-suf | --program-su | --program-s) ac_prev=program_suffix ;; -program-suffix=* | --program-suffix=* | --program-suffi=* \ | --program-suff=* | --program-suf=* | --program-su=* | --program-s=*) program_suffix=$ac_optarg ;; -program-transform-name | --program-transform-name \ | --program-transform-nam | --program-transform-na \ | --program-transform-n | --program-transform- \ | --program-transform | --program-transfor \ | --program-transfo | --program-transf \ | --program-trans | --program-tran \ | --progr-tra | --program-tr | --program-t) ac_prev=program_transform_name ;; -program-transform-name=* | --program-transform-name=* \ | --program-transform-nam=* | --program-transform-na=* \ | --program-transform-n=* | --program-transform-=* \ | --program-transform=* | --program-transfor=* \ | --program-transfo=* | --program-transf=* \ | --program-trans=* | --program-tran=* \ | --progr-tra=* | --program-tr=* | --program-t=*) program_transform_name=$ac_optarg ;; -pdfdir | --pdfdir | --pdfdi | --pdfd | --pdf | --pd) ac_prev=pdfdir ;; -pdfdir=* | --pdfdir=* | --pdfdi=* | --pdfd=* | --pdf=* | --pd=*) pdfdir=$ac_optarg ;; -psdir | --psdir | --psdi | --psd | --ps) ac_prev=psdir ;; -psdir=* | --psdir=* | --psdi=* | --psd=* | --ps=*) psdir=$ac_optarg ;; -q | -quiet | --quiet | --quie | --qui | --qu | --q \ | -silent | --silent | --silen | --sile | --sil) silent=yes ;; -runstatedir | --runstatedir | --runstatedi | --runstated \ | --runstate | --runstat | --runsta | --runst | --runs \ | --run | --ru | --r) ac_prev=runstatedir ;; -runstatedir=* | --runstatedir=* | --runstatedi=* | --runstated=* \ | --runstate=* | --runstat=* | --runsta=* | --runst=* | --runs=* \ | --run=* | --ru=* | --r=*) runstatedir=$ac_optarg ;; -sbindir | --sbindir | --sbindi | --sbind | --sbin | --sbi | --sb) ac_prev=sbindir ;; -sbindir=* | --sbindir=* | --sbindi=* | --sbind=* | --sbin=* \ | --sbi=* | --sb=*) sbindir=$ac_optarg ;; -sharedstatedir | --sharedstatedir | --sharedstatedi \ | --sharedstated | --sharedstate | --sharedstat | --sharedsta \ | --sharedst | --shareds | --shared | --share | --shar \ | --sha | --sh) ac_prev=sharedstatedir ;; -sharedstatedir=* | --sharedstatedir=* | --sharedstatedi=* \ | --sharedstated=* | --sharedstate=* | --sharedstat=* | --sharedsta=* \ | --sharedst=* | --shareds=* | --shared=* | --share=* | --shar=* \ | --sha=* | --sh=*) sharedstatedir=$ac_optarg ;; -site | --site | --sit) ac_prev=site ;; -site=* | --site=* | --sit=*) site=$ac_optarg ;; -srcdir | --srcdir | --srcdi | --srcd | --src | --sr) ac_prev=srcdir ;; -srcdir=* | --srcdir=* | --srcdi=* | --srcd=* | --src=* | --sr=*) srcdir=$ac_optarg ;; -sysconfdir | --sysconfdir | --sysconfdi | --sysconfd | --sysconf \ | --syscon | --sysco | --sysc | --sys | --sy) ac_prev=sysconfdir ;; -sysconfdir=* | --sysconfdir=* | --sysconfdi=* | --sysconfd=* | --sysconf=* \ | --syscon=* | --sysco=* | --sysc=* | --sys=* | --sy=*) sysconfdir=$ac_optarg ;; -target | --target | --targe | --targ | --tar | --ta | --t) ac_prev=target_alias ;; -target=* | --target=* | --targe=* | --targ=* | --tar=* | --ta=* | --t=*) target_alias=$ac_optarg ;; -v | -verbose | --verbose | --verbos | --verbo | --verb) verbose=yes ;; -version | --version | --versio | --versi | --vers | -V) ac_init_version=: ;; -with-* | --with-*) ac_useropt=`expr "x$ac_option" : 'x-*with-\([^=]*\)'` # Reject names that are not valid shell variable names. expr "x$ac_useropt" : ".*[^-+._$as_cr_alnum]" >/dev/null && as_fn_error $? "invalid package name: $ac_useropt" ac_useropt_orig=$ac_useropt ac_useropt=`$as_echo "$ac_useropt" | sed 's/[-+.]/_/g'` case $ac_user_opts in *" "with_$ac_useropt" "*) ;; *) ac_unrecognized_opts="$ac_unrecognized_opts$ac_unrecognized_sep--with-$ac_useropt_orig" ac_unrecognized_sep=', ';; esac eval with_$ac_useropt=\$ac_optarg ;; -without-* | --without-*) ac_useropt=`expr "x$ac_option" : 'x-*without-\(.*\)'` # Reject names that are not valid shell variable names. expr "x$ac_useropt" : ".*[^-+._$as_cr_alnum]" >/dev/null && as_fn_error $? "invalid package name: $ac_useropt" ac_useropt_orig=$ac_useropt ac_useropt=`$as_echo "$ac_useropt" | sed 's/[-+.]/_/g'` case $ac_user_opts in *" "with_$ac_useropt" "*) ;; *) ac_unrecognized_opts="$ac_unrecognized_opts$ac_unrecognized_sep--without-$ac_useropt_orig" ac_unrecognized_sep=', ';; esac eval with_$ac_useropt=no ;; --x) # Obsolete; use --with-x. with_x=yes ;; -x-includes | --x-includes | --x-include | --x-includ | --x-inclu \ | --x-incl | --x-inc | --x-in | --x-i) ac_prev=x_includes ;; -x-includes=* | --x-includes=* | --x-include=* | --x-includ=* | --x-inclu=* \ | --x-incl=* | --x-inc=* | --x-in=* | --x-i=*) x_includes=$ac_optarg ;; -x-libraries | --x-libraries | --x-librarie | --x-librari \ | --x-librar | --x-libra | --x-libr | --x-lib | --x-li | --x-l) ac_prev=x_libraries ;; -x-libraries=* | --x-libraries=* | --x-librarie=* | --x-librari=* \ | --x-librar=* | --x-libra=* | --x-libr=* | --x-lib=* | --x-li=* | --x-l=*) x_libraries=$ac_optarg ;; -*) as_fn_error $? "unrecognized option: \`$ac_option' Try \`$0 --help' for more information" ;; *=*) ac_envvar=`expr "x$ac_option" : 'x\([^=]*\)='` # Reject names that are not valid shell variable names. case $ac_envvar in #( '' | [0-9]* | *[!_$as_cr_alnum]* ) as_fn_error $? "invalid variable name: \`$ac_envvar'" ;; esac eval $ac_envvar=\$ac_optarg export $ac_envvar ;; *) # FIXME: should be removed in autoconf 3.0. $as_echo "$as_me: WARNING: you should use --build, --host, --target" >&2 expr "x$ac_option" : ".*[^-._$as_cr_alnum]" >/dev/null && $as_echo "$as_me: WARNING: invalid host type: $ac_option" >&2 : "${build_alias=$ac_option} ${host_alias=$ac_option} ${target_alias=$ac_option}" ;; esac done if test -n "$ac_prev"; then ac_option=--`echo $ac_prev | sed 's/_/-/g'` as_fn_error $? "missing argument to $ac_option" fi if test -n "$ac_unrecognized_opts"; then case $enable_option_checking in no) ;; fatal) as_fn_error $? "unrecognized options: $ac_unrecognized_opts" ;; *) $as_echo "$as_me: WARNING: unrecognized options: $ac_unrecognized_opts" >&2 ;; esac fi # Check all directory arguments for consistency. for ac_var in exec_prefix prefix bindir sbindir libexecdir datarootdir \ datadir sysconfdir sharedstatedir localstatedir includedir \ oldincludedir docdir infodir htmldir dvidir pdfdir psdir \ libdir localedir mandir runstatedir do eval ac_val=\$$ac_var # Remove trailing slashes. case $ac_val in */ ) ac_val=`expr "X$ac_val" : 'X\(.*[^/]\)' \| "X$ac_val" : 'X\(.*\)'` eval $ac_var=\$ac_val;; esac # Be sure to have absolute directory names. case $ac_val in [\\/$]* | ?:[\\/]* ) continue;; NONE | '' ) case $ac_var in *prefix ) continue;; esac;; esac as_fn_error $? "expected an absolute directory name for --$ac_var: $ac_val" done # There might be people who depend on the old broken behavior: `$host' # used to hold the argument of --host etc. # FIXME: To remove some day. build=$build_alias host=$host_alias target=$target_alias # FIXME: To remove some day. if test "x$host_alias" != x; then if test "x$build_alias" = x; then cross_compiling=maybe elif test "x$build_alias" != "x$host_alias"; then cross_compiling=yes fi fi ac_tool_prefix= test -n "$host_alias" && ac_tool_prefix=$host_alias- test "$silent" = yes && exec 6>/dev/null ac_pwd=`pwd` && test -n "$ac_pwd" && ac_ls_di=`ls -di .` && ac_pwd_ls_di=`cd "$ac_pwd" && ls -di .` || as_fn_error $? "working directory cannot be determined" test "X$ac_ls_di" = "X$ac_pwd_ls_di" || as_fn_error $? "pwd does not report name of working directory" # Find the source files, if location was not specified. if test -z "$srcdir"; then ac_srcdir_defaulted=yes # Try the directory containing this script, then the parent directory. ac_confdir=`$as_dirname -- "$as_myself" || $as_expr X"$as_myself" : 'X\(.*[^/]\)//*[^/][^/]*/*$' \| \ X"$as_myself" : 'X\(//\)[^/]' \| \ X"$as_myself" : 'X\(//\)$' \| \ X"$as_myself" : 'X\(/\)' \| . 2>/dev/null || $as_echo X"$as_myself" | sed '/^X\(.*[^/]\)\/\/*[^/][^/]*\/*$/{ s//\1/ q } /^X\(\/\/\)[^/].*/{ s//\1/ q } /^X\(\/\/\)$/{ s//\1/ q } /^X\(\/\).*/{ s//\1/ q } s/.*/./; q'` srcdir=$ac_confdir if test ! -r "$srcdir/$ac_unique_file"; then srcdir=.. fi else ac_srcdir_defaulted=no fi if test ! -r "$srcdir/$ac_unique_file"; then test "$ac_srcdir_defaulted" = yes && srcdir="$ac_confdir or .." as_fn_error $? "cannot find sources ($ac_unique_file) in $srcdir" fi ac_msg="sources are in $srcdir, but \`cd $srcdir' does not work" ac_abs_confdir=`( cd "$srcdir" && test -r "./$ac_unique_file" || as_fn_error $? "$ac_msg" pwd)` # When building in place, set srcdir=. if test "$ac_abs_confdir" = "$ac_pwd"; then srcdir=. fi # Remove unnecessary trailing slashes from srcdir. # Double slashes in file names in object file debugging info # mess up M-x gdb in Emacs. case $srcdir in */) srcdir=`expr "X$srcdir" : 'X\(.*[^/]\)' \| "X$srcdir" : 'X\(.*\)'`;; esac for ac_var in $ac_precious_vars; do eval ac_env_${ac_var}_set=\${${ac_var}+set} eval ac_env_${ac_var}_value=\$${ac_var} eval ac_cv_env_${ac_var}_set=\${${ac_var}+set} eval ac_cv_env_${ac_var}_value=\$${ac_var} done # # Report the --help message. # if test "$ac_init_help" = "long"; then # Omit some internal or obsolete options to make the list less imposing. # This message is too long to be a string in the A/UX 3.1 sh. cat <<_ACEOF \`configure' configures cyrus-imapd 2.5.10 to adapt to many kinds of systems. Usage: $0 [OPTION]... [VAR=VALUE]... To assign environment variables (e.g., CC, CFLAGS...), specify them as VAR=VALUE. See below for descriptions of some of the useful variables. Defaults for the options are specified in brackets. Configuration: -h, --help display this help and exit --help=short display options specific to this package --help=recursive display the short help of all the included packages -V, --version display version information and exit -q, --quiet, --silent do not print \`checking ...' messages --cache-file=FILE cache test results in FILE [disabled] -C, --config-cache alias for \`--cache-file=config.cache' -n, --no-create do not create output files --srcdir=DIR find the sources in DIR [configure dir or \`..'] Installation directories: --prefix=PREFIX install architecture-independent files in PREFIX [$ac_default_prefix] --exec-prefix=EPREFIX install architecture-dependent files in EPREFIX [PREFIX] By default, \`make install' will install all the files in \`$ac_default_prefix/bin', \`$ac_default_prefix/lib' etc. You can specify an installation prefix other than \`$ac_default_prefix' using \`--prefix', for instance \`--prefix=\$HOME'. For better control, use the options below. Fine tuning of the installation directories: --bindir=DIR user executables [EPREFIX/bin] --sbindir=DIR system admin executables [EPREFIX/sbin] --libexecdir=DIR program executables [EPREFIX/libexec] --sysconfdir=DIR read-only single-machine data [PREFIX/etc] --sharedstatedir=DIR modifiable architecture-independent data [PREFIX/com] --localstatedir=DIR modifiable single-machine data [PREFIX/var] --runstatedir=DIR modifiable per-process data [LOCALSTATEDIR/run] --libdir=DIR object code libraries [EPREFIX/lib] --includedir=DIR C header files [PREFIX/include] --oldincludedir=DIR C header files for non-gcc [/usr/include] --datarootdir=DIR read-only arch.-independent data root [PREFIX/share] --datadir=DIR read-only architecture-independent data [DATAROOTDIR] --infodir=DIR info documentation [DATAROOTDIR/info] --localedir=DIR locale-dependent data [DATAROOTDIR/locale] --mandir=DIR man documentation [DATAROOTDIR/man] --docdir=DIR documentation root [DATAROOTDIR/doc/cyrus-imapd] --htmldir=DIR html documentation [DOCDIR] --dvidir=DIR dvi documentation [DOCDIR] --pdfdir=DIR pdf documentation [DOCDIR] --psdir=DIR ps documentation [DOCDIR] _ACEOF cat <<\_ACEOF Program names: --program-prefix=PREFIX prepend PREFIX to installed program names --program-suffix=SUFFIX append SUFFIX to installed program names --program-transform-name=PROGRAM run sed PROGRAM on installed program names System types: --build=BUILD configure for building on BUILD [guessed] --host=HOST cross-compile to build programs to run on HOST [BUILD] --target=TARGET configure for building compilers for TARGET [HOST] _ACEOF fi if test -n "$ac_init_help"; then case $ac_init_help in short | recursive ) echo "Configuration of cyrus-imapd 2.5.10:";; esac cat <<\_ACEOF Optional Features: --disable-option-checking ignore unrecognized --enable/--with options --disable-FEATURE do not include FEATURE (same as --enable-FEATURE=no) --enable-FEATURE[=ARG] include FEATURE [ARG=yes] --enable-silent-rules less verbose build output (undo: "make V=1") --disable-silent-rules verbose build output (undo: "make V=0") --enable-maintainer-mode enable make rules and dependencies not useful (and sometimes confusing) to the casual installer --enable-coverage enable C test coverage --enable-dependency-tracking do not reject slow dependency extractors --disable-dependency-tracking speeds up one-time build --enable-static[=PKGS] build static libraries [default=no] --enable-shared[=PKGS] build shared libraries [default=yes] --enable-fast-install[=PKGS] optimize for fast installation [default=yes] --disable-libtool-lock avoid locking (might break parallel builds) --disable-sieve disable Sieve support --disable-pcre disable PCRE library --enable-afs Enable AFS with ptloader --enable-krb5afspts compile afskrb PTS module with krb5 support --disable-server disable compiling servers --enable-statickrb link Kerberos statically --disable-event-notification disable compiling of mailbox event notification (that needs jansson library) --enable-autocreate enable autocreate support --enable-idled enable IMAP idled support --enable-nntp enable NNTP support --enable-murder enable IMAP Murder support --enable-http enable HTTP support --enable-replication enable replication support (experimental) --enable-cmulocal enable CMU-specific local support --enable-oldsievename enable the use of 'imap' as the sieve service name --enable-netscapehack enable Netscape hack for the menu option in Communicator to Administrate Mail --enable-gssapi= enable GSSAPI authentication [yes] --enable-unit-tests enable CUnit-based unit regression tests Optional Packages: --with-PACKAGE[=ARG] use PACKAGE [ARG=yes] --without-PACKAGE do not use PACKAGE (same as --with-PACKAGE=no) --with-extraident=STRING use STRING as extra version information --with-cyrus-prefix=DIR use DIR as cyrus server install directory [PREFIX/cyrus] --with-service-path=DIR use DIR as service install directory [CYRUSPREFIX/bin] --with-cyrus-user=USERID use USERID cyrus userid --with-cyrus-group=GROUPID use GROUPID cyrus group --with-pic[=PKGS] try to use only PIC/non-PIC objects [default=use both] --with-aix-soname=aix|svr4|both shared library versioning (aka "SONAME") variant to provide on AIX, [default=aix]. --with-gnu-ld assume the C compiler uses GNU ld [default=no] --with-sysroot[=DIR] Search for dependent libraries within DIR (or the compiler's sysroot if not specified). --with-bdb=DIR use Berkeley DB (in DIR) [yes] --with-bdb-libdir=DIR Berkeley DB lib files are in DIR --with-bdb-incdir=DIR Berkeley DB include files are in DIR --with-mysql-libdir=DIR MySQL lib files are in DIR --with-mysql-incdir=DIR MySQL include files are in DIR --with-mysql=DIR use MySQL (in DIR) [no] --with-pgsql=DIR use PostgreSQL (in DIR) [no] --with-pgsql-libdir=DIR Pgsql lib files are in DIR --with-pgsql-incdir=DIR Pgsql include files are in DIR --with-sqlite=DIR use SQLite (in DIR) [no] --with-sqlite-libdir=DIR SQLite lib files are in DIR --with-sqlite-incdir=DIR SQLite include files are in DIR --with-mmap=TYPE force shared/stupidshared/nommap - JUST FOR TESTING --with-lock=METHOD force use of METHOD for locking (flock or fcntl) --with-afs-libdir=DIR use AFS libraries from DIR [/usr/lib] --with-afs-incdir=DIR use AFS headers from DIR [/usr/include] --with-ldap=DIR use LDAP (in DIR) (experimental) [/usr/local] --with-clamav=DIR use ClamAV from PATH (yes) --with-krb=DIR use Kerberos from DIR --with-krbimpl=kth|mit assume Kerberos 4 from KTH or MIT --with-krbdes use Kerberos DES implementation [yes] --with-openssl=DIR use OpenSSL from DIR --with-egd-socket=FILE Entropy Gathering Daemon socket pathname for systems without /dev/urandom --with-lib-subdir=DIR Find libraries in DIR instead of lib --with-zlib=DIR use zlib from DIR --with-zephyr=DIR enable Zephyr notification (installed on DIR) --with-libcap Enable libcap system capabilities handling (Linux systems only) --with-pidfile=DIR pidfile in DIR [/var/run/cyrus-master.pid] --with-com_err=DIR use com_err from path -- includes in DIR/include, libs in DIR/lib, and compile_et in DIR/bin --with-syslogfacility=FACILITY set the syslog facility to use (default LOCAL6) --with-gss_impl={heimdal|mit|cybersafe|seam|auto} choose specific GSSAPI implementation [[auto]] --with-sasl=DIR Compile with libsasl2 in --with-staticsasl=DIR Compile with staticly linked libsasl2 in --with-perl=PERL use PERL for perl --with-libwrap=DIR use libwrap (rooted in DIR) [yes] --with-snmp=DIR use ucd|net snmp (rooted in DIR) [yes] Some influential environment variables: PKG_CONFIG path to pkg-config utility PKG_CONFIG_PATH directories to add to pkg-config's search path PKG_CONFIG_LIBDIR path overriding pkg-config's built-in search path CC C compiler command CFLAGS C compiler flags LDFLAGS linker flags, e.g. -L if you have libraries in a nonstandard directory LIBS libraries to pass to the linker, e.g. -l CPPFLAGS (Objective) C/C++ preprocessor flags, e.g. -I if you have headers in a nonstandard directory CPP C preprocessor LT_SYS_LIBRARY_PATH User-defined run-time library search path. YACC The `Yet Another Compiler Compiler' implementation to use. Defaults to the first program found out of: `bison -y', `byacc', `yacc'. YFLAGS The list of arguments that will be passed by default to $YACC. This script will default YFLAGS to the empty string to avoid a default value of `-d' given by some make applications. OPENSSL_CFLAGS C compiler flags for OPENSSL, overriding pkg-config OPENSSL_LIBS linker flags for OPENSSL, overriding pkg-config JANSSON_CFLAGS C compiler flags for JANSSON, overriding pkg-config JANSSON_LIBS linker flags for JANSSON, overriding pkg-config XML2_CFLAGS C compiler flags for XML2, overriding pkg-config XML2_LIBS linker flags for XML2, overriding pkg-config ICAL_CFLAGS C compiler flags for ICAL, overriding pkg-config ICAL_LIBS linker flags for ICAL, overriding pkg-config SQLITE3_CFLAGS C compiler flags for SQLITE3, overriding pkg-config SQLITE3_LIBS linker flags for SQLITE3, overriding pkg-config JSON_CFLAGS C compiler flags for JSON, overriding pkg-config JSON_LIBS linker flags for JSON, overriding pkg-config ICU_CFLAGS C compiler flags for ICU, overriding pkg-config ICU_LIBS linker flags for ICU, overriding pkg-config Use these variables to override the choices made by `configure' or to help it to find libraries and programs with nonstandard names/locations. Report bugs to . cyrus-imapd home page: . _ACEOF ac_status=$? fi if test "$ac_init_help" = "recursive"; then # If there are subdirs, report their specific --help. for ac_dir in : $ac_subdirs_all; do test "x$ac_dir" = x: && continue test -d "$ac_dir" || { cd "$srcdir" && ac_pwd=`pwd` && srcdir=. && test -d "$ac_dir"; } || continue ac_builddir=. case "$ac_dir" in .) ac_dir_suffix= ac_top_builddir_sub=. ac_top_build_prefix= ;; *) ac_dir_suffix=/`$as_echo "$ac_dir" | sed 's|^\.[\\/]||'` # A ".." for each directory in $ac_dir_suffix. ac_top_builddir_sub=`$as_echo "$ac_dir_suffix" | sed 's|/[^\\/]*|/..|g;s|/||'` case $ac_top_builddir_sub in "") ac_top_builddir_sub=. ac_top_build_prefix= ;; *) ac_top_build_prefix=$ac_top_builddir_sub/ ;; esac ;; esac ac_abs_top_builddir=$ac_pwd ac_abs_builddir=$ac_pwd$ac_dir_suffix # for backward compatibility: ac_top_builddir=$ac_top_build_prefix case $srcdir in .) # We are building in place. ac_srcdir=. ac_top_srcdir=$ac_top_builddir_sub ac_abs_top_srcdir=$ac_pwd ;; [\\/]* | ?:[\\/]* ) # Absolute name. ac_srcdir=$srcdir$ac_dir_suffix; ac_top_srcdir=$srcdir ac_abs_top_srcdir=$srcdir ;; *) # Relative name. ac_srcdir=$ac_top_build_prefix$srcdir$ac_dir_suffix ac_top_srcdir=$ac_top_build_prefix$srcdir ac_abs_top_srcdir=$ac_pwd/$srcdir ;; esac ac_abs_srcdir=$ac_abs_top_srcdir$ac_dir_suffix cd "$ac_dir" || { ac_status=$?; continue; } # Check for guested configure. if test -f "$ac_srcdir/configure.gnu"; then echo && $SHELL "$ac_srcdir/configure.gnu" --help=recursive elif test -f "$ac_srcdir/configure"; then echo && $SHELL "$ac_srcdir/configure" --help=recursive else $as_echo "$as_me: WARNING: no configuration information is in $ac_dir" >&2 fi || ac_status=$? cd "$ac_pwd" || { ac_status=$?; break; } done fi test -n "$ac_init_help" && exit $ac_status if $ac_init_version; then cat <<\_ACEOF cyrus-imapd configure 2.5.10 generated by GNU Autoconf 2.69 Copyright (C) 2012 Free Software Foundation, Inc. This configure script is free software; the Free Software Foundation gives unlimited permission to copy, distribute and modify it. _ACEOF exit fi ## ------------------------ ## ## Autoconf initialization. ## ## ------------------------ ## # ac_fn_c_try_compile LINENO # -------------------------- # Try to compile conftest.$ac_ext, and return whether this succeeded. ac_fn_c_try_compile () { as_lineno=${as_lineno-"$1"} as_lineno_stack=as_lineno_stack=$as_lineno_stack rm -f conftest.$ac_objext if { { ac_try="$ac_compile" case "(($ac_try" in *\"* | *\`* | *\\*) ac_try_echo=\$ac_try;; *) ac_try_echo=$ac_try;; esac eval ac_try_echo="\"\$as_me:${as_lineno-$LINENO}: $ac_try_echo\"" $as_echo "$ac_try_echo"; } >&5 (eval "$ac_compile") 2>conftest.err ac_status=$? if test -s conftest.err; then grep -v '^ *+' conftest.err >conftest.er1 cat conftest.er1 >&5 mv -f conftest.er1 conftest.err fi $as_echo "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 test $ac_status = 0; } && { test -z "$ac_c_werror_flag" || test ! -s conftest.err } && test -s conftest.$ac_objext; then : ac_retval=0 else $as_echo "$as_me: failed program was:" >&5 sed 's/^/| /' conftest.$ac_ext >&5 ac_retval=1 fi eval $as_lineno_stack; ${as_lineno_stack:+:} unset as_lineno as_fn_set_status $ac_retval } # ac_fn_c_try_compile # ac_fn_c_try_cpp LINENO # ---------------------- # Try to preprocess conftest.$ac_ext, and return whether this succeeded. ac_fn_c_try_cpp () { as_lineno=${as_lineno-"$1"} as_lineno_stack=as_lineno_stack=$as_lineno_stack if { { ac_try="$ac_cpp conftest.$ac_ext" case "(($ac_try" in *\"* | *\`* | *\\*) ac_try_echo=\$ac_try;; *) ac_try_echo=$ac_try;; esac eval ac_try_echo="\"\$as_me:${as_lineno-$LINENO}: $ac_try_echo\"" $as_echo "$ac_try_echo"; } >&5 (eval "$ac_cpp conftest.$ac_ext") 2>conftest.err ac_status=$? if test -s conftest.err; then grep -v '^ *+' conftest.err >conftest.er1 cat conftest.er1 >&5 mv -f conftest.er1 conftest.err fi $as_echo "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 test $ac_status = 0; } > conftest.i && { test -z "$ac_c_preproc_warn_flag$ac_c_werror_flag" || test ! -s conftest.err }; then : ac_retval=0 else $as_echo "$as_me: failed program was:" >&5 sed 's/^/| /' conftest.$ac_ext >&5 ac_retval=1 fi eval $as_lineno_stack; ${as_lineno_stack:+:} unset as_lineno as_fn_set_status $ac_retval } # ac_fn_c_try_cpp # ac_fn_c_check_header_mongrel LINENO HEADER VAR INCLUDES # ------------------------------------------------------- # Tests whether HEADER exists, giving a warning if it cannot be compiled using # the include files in INCLUDES and setting the cache variable VAR # accordingly. ac_fn_c_check_header_mongrel () { as_lineno=${as_lineno-"$1"} as_lineno_stack=as_lineno_stack=$as_lineno_stack if eval \${$3+:} false; then : { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $2" >&5 $as_echo_n "checking for $2... " >&6; } if eval \${$3+:} false; then : $as_echo_n "(cached) " >&6 fi eval ac_res=\$$3 { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_res" >&5 $as_echo "$ac_res" >&6; } else # Is the header compilable? { $as_echo "$as_me:${as_lineno-$LINENO}: checking $2 usability" >&5 $as_echo_n "checking $2 usability... " >&6; } cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ $4 #include <$2> _ACEOF if ac_fn_c_try_compile "$LINENO"; then : ac_header_compiler=yes else ac_header_compiler=no fi rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_header_compiler" >&5 $as_echo "$ac_header_compiler" >&6; } # Is the header present? { $as_echo "$as_me:${as_lineno-$LINENO}: checking $2 presence" >&5 $as_echo_n "checking $2 presence... " >&6; } cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ #include <$2> _ACEOF if ac_fn_c_try_cpp "$LINENO"; then : ac_header_preproc=yes else ac_header_preproc=no fi rm -f conftest.err conftest.i conftest.$ac_ext { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_header_preproc" >&5 $as_echo "$ac_header_preproc" >&6; } # So? What about this header? case $ac_header_compiler:$ac_header_preproc:$ac_c_preproc_warn_flag in #(( yes:no: ) { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: $2: accepted by the compiler, rejected by the preprocessor!" >&5 $as_echo "$as_me: WARNING: $2: accepted by the compiler, rejected by the preprocessor!" >&2;} { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: $2: proceeding with the compiler's result" >&5 $as_echo "$as_me: WARNING: $2: proceeding with the compiler's result" >&2;} ;; no:yes:* ) { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: $2: present but cannot be compiled" >&5 $as_echo "$as_me: WARNING: $2: present but cannot be compiled" >&2;} { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: $2: check for missing prerequisite headers?" >&5 $as_echo "$as_me: WARNING: $2: check for missing prerequisite headers?" >&2;} { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: $2: see the Autoconf documentation" >&5 $as_echo "$as_me: WARNING: $2: see the Autoconf documentation" >&2;} { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: $2: section \"Present But Cannot Be Compiled\"" >&5 $as_echo "$as_me: WARNING: $2: section \"Present But Cannot Be Compiled\"" >&2;} { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: $2: proceeding with the compiler's result" >&5 $as_echo "$as_me: WARNING: $2: proceeding with the compiler's result" >&2;} ( $as_echo "## -------------------------------------------------------------- ## ## Report this to https://github.com/cyrusimap/cyrus-imapd/issues ## ## -------------------------------------------------------------- ##" ) | sed "s/^/$as_me: WARNING: /" >&2 ;; esac { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $2" >&5 $as_echo_n "checking for $2... " >&6; } if eval \${$3+:} false; then : $as_echo_n "(cached) " >&6 else eval "$3=\$ac_header_compiler" fi eval ac_res=\$$3 { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_res" >&5 $as_echo "$ac_res" >&6; } fi eval $as_lineno_stack; ${as_lineno_stack:+:} unset as_lineno } # ac_fn_c_check_header_mongrel # ac_fn_c_try_run LINENO # ---------------------- # Try to link conftest.$ac_ext, and return whether this succeeded. Assumes # that executables *can* be run. ac_fn_c_try_run () { as_lineno=${as_lineno-"$1"} as_lineno_stack=as_lineno_stack=$as_lineno_stack if { { ac_try="$ac_link" case "(($ac_try" in *\"* | *\`* | *\\*) ac_try_echo=\$ac_try;; *) ac_try_echo=$ac_try;; esac eval ac_try_echo="\"\$as_me:${as_lineno-$LINENO}: $ac_try_echo\"" $as_echo "$ac_try_echo"; } >&5 (eval "$ac_link") 2>&5 ac_status=$? $as_echo "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 test $ac_status = 0; } && { ac_try='./conftest$ac_exeext' { { case "(($ac_try" in *\"* | *\`* | *\\*) ac_try_echo=\$ac_try;; *) ac_try_echo=$ac_try;; esac eval ac_try_echo="\"\$as_me:${as_lineno-$LINENO}: $ac_try_echo\"" $as_echo "$ac_try_echo"; } >&5 (eval "$ac_try") 2>&5 ac_status=$? $as_echo "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 test $ac_status = 0; }; }; then : ac_retval=0 else $as_echo "$as_me: program exited with status $ac_status" >&5 $as_echo "$as_me: failed program was:" >&5 sed 's/^/| /' conftest.$ac_ext >&5 ac_retval=$ac_status fi rm -rf conftest.dSYM conftest_ipa8_conftest.oo eval $as_lineno_stack; ${as_lineno_stack:+:} unset as_lineno as_fn_set_status $ac_retval } # ac_fn_c_try_run # ac_fn_c_check_header_compile LINENO HEADER VAR INCLUDES # ------------------------------------------------------- # Tests whether HEADER exists and can be compiled using the include files in # INCLUDES, setting the cache variable VAR accordingly. ac_fn_c_check_header_compile () { as_lineno=${as_lineno-"$1"} as_lineno_stack=as_lineno_stack=$as_lineno_stack { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $2" >&5 $as_echo_n "checking for $2... " >&6; } if eval \${$3+:} false; then : $as_echo_n "(cached) " >&6 else cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ $4 #include <$2> _ACEOF if ac_fn_c_try_compile "$LINENO"; then : eval "$3=yes" else eval "$3=no" fi rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext fi eval ac_res=\$$3 { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_res" >&5 $as_echo "$ac_res" >&6; } eval $as_lineno_stack; ${as_lineno_stack:+:} unset as_lineno } # ac_fn_c_check_header_compile # ac_fn_c_try_link LINENO # ----------------------- # Try to link conftest.$ac_ext, and return whether this succeeded. ac_fn_c_try_link () { as_lineno=${as_lineno-"$1"} as_lineno_stack=as_lineno_stack=$as_lineno_stack rm -f conftest.$ac_objext conftest$ac_exeext if { { ac_try="$ac_link" case "(($ac_try" in *\"* | *\`* | *\\*) ac_try_echo=\$ac_try;; *) ac_try_echo=$ac_try;; esac eval ac_try_echo="\"\$as_me:${as_lineno-$LINENO}: $ac_try_echo\"" $as_echo "$ac_try_echo"; } >&5 (eval "$ac_link") 2>conftest.err ac_status=$? if test -s conftest.err; then grep -v '^ *+' conftest.err >conftest.er1 cat conftest.er1 >&5 mv -f conftest.er1 conftest.err fi $as_echo "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 test $ac_status = 0; } && { test -z "$ac_c_werror_flag" || test ! -s conftest.err } && test -s conftest$ac_exeext && { test "$cross_compiling" = yes || test -x conftest$ac_exeext }; then : ac_retval=0 else $as_echo "$as_me: failed program was:" >&5 sed 's/^/| /' conftest.$ac_ext >&5 ac_retval=1 fi # Delete the IPA/IPO (Inter Procedural Analysis/Optimization) information # created by the PGI compiler (conftest_ipa8_conftest.oo), as it would # interfere with the next link command; also delete a directory that is # left behind by Apple's compiler. We do this before executing the actions. rm -rf conftest.dSYM conftest_ipa8_conftest.oo eval $as_lineno_stack; ${as_lineno_stack:+:} unset as_lineno as_fn_set_status $ac_retval } # ac_fn_c_try_link # ac_fn_c_check_func LINENO FUNC VAR # ---------------------------------- # Tests whether FUNC exists, setting the cache variable VAR accordingly ac_fn_c_check_func () { as_lineno=${as_lineno-"$1"} as_lineno_stack=as_lineno_stack=$as_lineno_stack { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $2" >&5 $as_echo_n "checking for $2... " >&6; } if eval \${$3+:} false; then : $as_echo_n "(cached) " >&6 else cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ /* Define $2 to an innocuous variant, in case declares $2. For example, HP-UX 11i declares gettimeofday. */ #define $2 innocuous_$2 /* System header to define __stub macros and hopefully few prototypes, which can conflict with char $2 (); below. Prefer to if __STDC__ is defined, since exists even on freestanding compilers. */ #ifdef __STDC__ # include #else # include #endif #undef $2 /* Override any GCC internal prototype to avoid an error. Use char because int might match the return type of a GCC builtin and then its argument prototype would still apply. */ #ifdef __cplusplus extern "C" #endif char $2 (); /* The GNU C library defines this for functions which it implements to always fail with ENOSYS. Some functions are actually named something starting with __ and the normal name is an alias. */ #if defined __stub_$2 || defined __stub___$2 choke me #endif int main () { return $2 (); ; return 0; } _ACEOF if ac_fn_c_try_link "$LINENO"; then : eval "$3=yes" else eval "$3=no" fi rm -f core conftest.err conftest.$ac_objext \ conftest$ac_exeext conftest.$ac_ext fi eval ac_res=\$$3 { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_res" >&5 $as_echo "$ac_res" >&6; } eval $as_lineno_stack; ${as_lineno_stack:+:} unset as_lineno } # ac_fn_c_check_func # ac_fn_c_compute_int LINENO EXPR VAR INCLUDES # -------------------------------------------- # Tries to find the compile-time value of EXPR in a program that includes # INCLUDES, setting VAR accordingly. Returns whether the value could be # computed ac_fn_c_compute_int () { as_lineno=${as_lineno-"$1"} as_lineno_stack=as_lineno_stack=$as_lineno_stack if test "$cross_compiling" = yes; then # Depending upon the size, compute the lo and hi bounds. cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ $4 int main () { static int test_array [1 - 2 * !(($2) >= 0)]; test_array [0] = 0; return test_array [0]; ; return 0; } _ACEOF if ac_fn_c_try_compile "$LINENO"; then : ac_lo=0 ac_mid=0 while :; do cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ $4 int main () { static int test_array [1 - 2 * !(($2) <= $ac_mid)]; test_array [0] = 0; return test_array [0]; ; return 0; } _ACEOF if ac_fn_c_try_compile "$LINENO"; then : ac_hi=$ac_mid; break else as_fn_arith $ac_mid + 1 && ac_lo=$as_val if test $ac_lo -le $ac_mid; then ac_lo= ac_hi= break fi as_fn_arith 2 '*' $ac_mid + 1 && ac_mid=$as_val fi rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext done else cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ $4 int main () { static int test_array [1 - 2 * !(($2) < 0)]; test_array [0] = 0; return test_array [0]; ; return 0; } _ACEOF if ac_fn_c_try_compile "$LINENO"; then : ac_hi=-1 ac_mid=-1 while :; do cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ $4 int main () { static int test_array [1 - 2 * !(($2) >= $ac_mid)]; test_array [0] = 0; return test_array [0]; ; return 0; } _ACEOF if ac_fn_c_try_compile "$LINENO"; then : ac_lo=$ac_mid; break else as_fn_arith '(' $ac_mid ')' - 1 && ac_hi=$as_val if test $ac_mid -le $ac_hi; then ac_lo= ac_hi= break fi as_fn_arith 2 '*' $ac_mid && ac_mid=$as_val fi rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext done else ac_lo= ac_hi= fi rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext fi rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext # Binary search between lo and hi bounds. while test "x$ac_lo" != "x$ac_hi"; do as_fn_arith '(' $ac_hi - $ac_lo ')' / 2 + $ac_lo && ac_mid=$as_val cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ $4 int main () { static int test_array [1 - 2 * !(($2) <= $ac_mid)]; test_array [0] = 0; return test_array [0]; ; return 0; } _ACEOF if ac_fn_c_try_compile "$LINENO"; then : ac_hi=$ac_mid else as_fn_arith '(' $ac_mid ')' + 1 && ac_lo=$as_val fi rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext done case $ac_lo in #(( ?*) eval "$3=\$ac_lo"; ac_retval=0 ;; '') ac_retval=1 ;; esac else cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ $4 static long int longval () { return $2; } static unsigned long int ulongval () { return $2; } #include #include int main () { FILE *f = fopen ("conftest.val", "w"); if (! f) return 1; if (($2) < 0) { long int i = longval (); if (i != ($2)) return 1; fprintf (f, "%ld", i); } else { unsigned long int i = ulongval (); if (i != ($2)) return 1; fprintf (f, "%lu", i); } /* Do not output a trailing newline, as this causes \r\n confusion on some platforms. */ return ferror (f) || fclose (f) != 0; ; return 0; } _ACEOF if ac_fn_c_try_run "$LINENO"; then : echo >>conftest.val; read $3 &5 $as_echo_n "checking for $2.$3... " >&6; } if eval \${$4+:} false; then : $as_echo_n "(cached) " >&6 else cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ $5 int main () { static $2 ac_aggr; if (ac_aggr.$3) return 0; ; return 0; } _ACEOF if ac_fn_c_try_compile "$LINENO"; then : eval "$4=yes" else cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ $5 int main () { static $2 ac_aggr; if (sizeof ac_aggr.$3) return 0; ; return 0; } _ACEOF if ac_fn_c_try_compile "$LINENO"; then : eval "$4=yes" else eval "$4=no" fi rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext fi rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext fi eval ac_res=\$$4 { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_res" >&5 $as_echo "$ac_res" >&6; } eval $as_lineno_stack; ${as_lineno_stack:+:} unset as_lineno } # ac_fn_c_check_member # ac_fn_c_check_decl LINENO SYMBOL VAR INCLUDES # --------------------------------------------- # Tests whether SYMBOL is declared in INCLUDES, setting cache variable VAR # accordingly. ac_fn_c_check_decl () { as_lineno=${as_lineno-"$1"} as_lineno_stack=as_lineno_stack=$as_lineno_stack as_decl_name=`echo $2|sed 's/ *(.*//'` as_decl_use=`echo $2|sed -e 's/(/((/' -e 's/)/) 0&/' -e 's/,/) 0& (/g'` { $as_echo "$as_me:${as_lineno-$LINENO}: checking whether $as_decl_name is declared" >&5 $as_echo_n "checking whether $as_decl_name is declared... " >&6; } if eval \${$3+:} false; then : $as_echo_n "(cached) " >&6 else cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ $4 int main () { #ifndef $as_decl_name #ifdef __cplusplus (void) $as_decl_use; #else (void) $as_decl_name; #endif #endif ; return 0; } _ACEOF if ac_fn_c_try_compile "$LINENO"; then : eval "$3=yes" else eval "$3=no" fi rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext fi eval ac_res=\$$3 { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_res" >&5 $as_echo "$ac_res" >&6; } eval $as_lineno_stack; ${as_lineno_stack:+:} unset as_lineno } # ac_fn_c_check_decl cat >config.log <<_ACEOF This file contains any messages produced by compilers while running configure, to aid debugging if configure makes a mistake. It was created by cyrus-imapd $as_me 2.5.10, which was generated by GNU Autoconf 2.69. Invocation command line was $ $0 $@ _ACEOF exec 5>>config.log { cat <<_ASUNAME ## --------- ## ## Platform. ## ## --------- ## hostname = `(hostname || uname -n) 2>/dev/null | sed 1q` uname -m = `(uname -m) 2>/dev/null || echo unknown` uname -r = `(uname -r) 2>/dev/null || echo unknown` uname -s = `(uname -s) 2>/dev/null || echo unknown` uname -v = `(uname -v) 2>/dev/null || echo unknown` /usr/bin/uname -p = `(/usr/bin/uname -p) 2>/dev/null || echo unknown` /bin/uname -X = `(/bin/uname -X) 2>/dev/null || echo unknown` /bin/arch = `(/bin/arch) 2>/dev/null || echo unknown` /usr/bin/arch -k = `(/usr/bin/arch -k) 2>/dev/null || echo unknown` /usr/convex/getsysinfo = `(/usr/convex/getsysinfo) 2>/dev/null || echo unknown` /usr/bin/hostinfo = `(/usr/bin/hostinfo) 2>/dev/null || echo unknown` /bin/machine = `(/bin/machine) 2>/dev/null || echo unknown` /usr/bin/oslevel = `(/usr/bin/oslevel) 2>/dev/null || echo unknown` /bin/universe = `(/bin/universe) 2>/dev/null || echo unknown` _ASUNAME as_save_IFS=$IFS; IFS=$PATH_SEPARATOR for as_dir in $PATH do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. $as_echo "PATH: $as_dir" done IFS=$as_save_IFS } >&5 cat >&5 <<_ACEOF ## ----------- ## ## Core tests. ## ## ----------- ## _ACEOF # Keep a trace of the command line. # Strip out --no-create and --no-recursion so they do not pile up. # Strip out --silent because we don't want to record it for future runs. # Also quote any args containing shell meta-characters. # Make two passes to allow for proper duplicate-argument suppression. ac_configure_args= ac_configure_args0= ac_configure_args1= ac_must_keep_next=false for ac_pass in 1 2 do for ac_arg do case $ac_arg in -no-create | --no-c* | -n | -no-recursion | --no-r*) continue ;; -q | -quiet | --quiet | --quie | --qui | --qu | --q \ | -silent | --silent | --silen | --sile | --sil) continue ;; *\'*) ac_arg=`$as_echo "$ac_arg" | sed "s/'/'\\\\\\\\''/g"` ;; esac case $ac_pass in 1) as_fn_append ac_configure_args0 " '$ac_arg'" ;; 2) as_fn_append ac_configure_args1 " '$ac_arg'" if test $ac_must_keep_next = true; then ac_must_keep_next=false # Got value, back to normal. else case $ac_arg in *=* | --config-cache | -C | -disable-* | --disable-* \ | -enable-* | --enable-* | -gas | --g* | -nfp | --nf* \ | -q | -quiet | --q* | -silent | --sil* | -v | -verb* \ | -with-* | --with-* | -without-* | --without-* | --x) case "$ac_configure_args0 " in "$ac_configure_args1"*" '$ac_arg' "* ) continue ;; esac ;; -* ) ac_must_keep_next=true ;; esac fi as_fn_append ac_configure_args " '$ac_arg'" ;; esac done done { ac_configure_args0=; unset ac_configure_args0;} { ac_configure_args1=; unset ac_configure_args1;} # When interrupted or exit'd, cleanup temporary files, and complete # config.log. We remove comments because anyway the quotes in there # would cause problems or look ugly. # WARNING: Use '\'' to represent an apostrophe within the trap. # WARNING: Do not start the trap code with a newline, due to a FreeBSD 4.0 bug. trap 'exit_status=$? # Save into config.log some information that might help in debugging. { echo $as_echo "## ---------------- ## ## Cache variables. ## ## ---------------- ##" echo # The following way of writing the cache mishandles newlines in values, ( for ac_var in `(set) 2>&1 | sed -n '\''s/^\([a-zA-Z_][a-zA-Z0-9_]*\)=.*/\1/p'\''`; do eval ac_val=\$$ac_var case $ac_val in #( *${as_nl}*) case $ac_var in #( *_cv_*) { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: cache variable $ac_var contains a newline" >&5 $as_echo "$as_me: WARNING: cache variable $ac_var contains a newline" >&2;} ;; esac case $ac_var in #( _ | IFS | as_nl) ;; #( BASH_ARGV | BASH_SOURCE) eval $ac_var= ;; #( *) { eval $ac_var=; unset $ac_var;} ;; esac ;; esac done (set) 2>&1 | case $as_nl`(ac_space='\'' '\''; set) 2>&1` in #( *${as_nl}ac_space=\ *) sed -n \ "s/'\''/'\''\\\\'\'''\''/g; s/^\\([_$as_cr_alnum]*_cv_[_$as_cr_alnum]*\\)=\\(.*\\)/\\1='\''\\2'\''/p" ;; #( *) sed -n "/^[_$as_cr_alnum]*_cv_[_$as_cr_alnum]*=/p" ;; esac | sort ) echo $as_echo "## ----------------- ## ## Output variables. ## ## ----------------- ##" echo for ac_var in $ac_subst_vars do eval ac_val=\$$ac_var case $ac_val in *\'\''*) ac_val=`$as_echo "$ac_val" | sed "s/'\''/'\''\\\\\\\\'\'''\''/g"`;; esac $as_echo "$ac_var='\''$ac_val'\''" done | sort echo if test -n "$ac_subst_files"; then $as_echo "## ------------------- ## ## File substitutions. ## ## ------------------- ##" echo for ac_var in $ac_subst_files do eval ac_val=\$$ac_var case $ac_val in *\'\''*) ac_val=`$as_echo "$ac_val" | sed "s/'\''/'\''\\\\\\\\'\'''\''/g"`;; esac $as_echo "$ac_var='\''$ac_val'\''" done | sort echo fi if test -s confdefs.h; then $as_echo "## ----------- ## ## confdefs.h. ## ## ----------- ##" echo cat confdefs.h echo fi test "$ac_signal" != 0 && $as_echo "$as_me: caught signal $ac_signal" $as_echo "$as_me: exit $exit_status" } >&5 rm -f core *.core core.conftest.* && rm -f -r conftest* confdefs* conf$$* $ac_clean_files && exit $exit_status ' 0 for ac_signal in 1 2 13 15; do trap 'ac_signal='$ac_signal'; as_fn_exit 1' $ac_signal done ac_signal=0 # confdefs.h avoids OS command line length limits that DEFS can exceed. rm -f -r conftest* confdefs.h $as_echo "/* confdefs.h */" > confdefs.h # Predefined preprocessor variables. cat >>confdefs.h <<_ACEOF #define PACKAGE_NAME "$PACKAGE_NAME" _ACEOF cat >>confdefs.h <<_ACEOF #define PACKAGE_TARNAME "$PACKAGE_TARNAME" _ACEOF cat >>confdefs.h <<_ACEOF #define PACKAGE_VERSION "$PACKAGE_VERSION" _ACEOF cat >>confdefs.h <<_ACEOF #define PACKAGE_STRING "$PACKAGE_STRING" _ACEOF cat >>confdefs.h <<_ACEOF #define PACKAGE_BUGREPORT "$PACKAGE_BUGREPORT" _ACEOF cat >>confdefs.h <<_ACEOF #define PACKAGE_URL "$PACKAGE_URL" _ACEOF # Let the site file select an alternate cache file if it wants to. # Prefer an explicitly selected file to automatically selected ones. ac_site_file1=NONE ac_site_file2=NONE if test -n "$CONFIG_SITE"; then # We do not want a PATH search for config.site. case $CONFIG_SITE in #(( -*) ac_site_file1=./$CONFIG_SITE;; */*) ac_site_file1=$CONFIG_SITE;; *) ac_site_file1=./$CONFIG_SITE;; esac elif test "x$prefix" != xNONE; then ac_site_file1=$prefix/share/config.site ac_site_file2=$prefix/etc/config.site else ac_site_file1=$ac_default_prefix/share/config.site ac_site_file2=$ac_default_prefix/etc/config.site fi for ac_site_file in "$ac_site_file1" "$ac_site_file2" do test "x$ac_site_file" = xNONE && continue if test /dev/null != "$ac_site_file" && test -r "$ac_site_file"; then { $as_echo "$as_me:${as_lineno-$LINENO}: loading site script $ac_site_file" >&5 $as_echo "$as_me: loading site script $ac_site_file" >&6;} sed 's/^/| /' "$ac_site_file" >&5 . "$ac_site_file" \ || { { $as_echo "$as_me:${as_lineno-$LINENO}: error: in \`$ac_pwd':" >&5 $as_echo "$as_me: error: in \`$ac_pwd':" >&2;} as_fn_error $? "failed to load site script $ac_site_file See \`config.log' for more details" "$LINENO" 5; } fi done if test -r "$cache_file"; then # Some versions of bash will fail to source /dev/null (special files # actually), so we avoid doing that. DJGPP emulates it as a regular file. if test /dev/null != "$cache_file" && test -f "$cache_file"; then { $as_echo "$as_me:${as_lineno-$LINENO}: loading cache $cache_file" >&5 $as_echo "$as_me: loading cache $cache_file" >&6;} case $cache_file in [\\/]* | ?:[\\/]* ) . "$cache_file";; *) . "./$cache_file";; esac fi else { $as_echo "$as_me:${as_lineno-$LINENO}: creating cache $cache_file" >&5 $as_echo "$as_me: creating cache $cache_file" >&6;} >$cache_file fi # Check that the precious variables saved in the cache have kept the same # value. ac_cache_corrupted=false for ac_var in $ac_precious_vars; do eval ac_old_set=\$ac_cv_env_${ac_var}_set eval ac_new_set=\$ac_env_${ac_var}_set eval ac_old_val=\$ac_cv_env_${ac_var}_value eval ac_new_val=\$ac_env_${ac_var}_value case $ac_old_set,$ac_new_set in set,) { $as_echo "$as_me:${as_lineno-$LINENO}: error: \`$ac_var' was set to \`$ac_old_val' in the previous run" >&5 $as_echo "$as_me: error: \`$ac_var' was set to \`$ac_old_val' in the previous run" >&2;} ac_cache_corrupted=: ;; ,set) { $as_echo "$as_me:${as_lineno-$LINENO}: error: \`$ac_var' was not set in the previous run" >&5 $as_echo "$as_me: error: \`$ac_var' was not set in the previous run" >&2;} ac_cache_corrupted=: ;; ,);; *) if test "x$ac_old_val" != "x$ac_new_val"; then # differences in whitespace do not lead to failure. ac_old_val_w=`echo x $ac_old_val` ac_new_val_w=`echo x $ac_new_val` if test "$ac_old_val_w" != "$ac_new_val_w"; then { $as_echo "$as_me:${as_lineno-$LINENO}: error: \`$ac_var' has changed since the previous run:" >&5 $as_echo "$as_me: error: \`$ac_var' has changed since the previous run:" >&2;} ac_cache_corrupted=: else { $as_echo "$as_me:${as_lineno-$LINENO}: warning: ignoring whitespace changes in \`$ac_var' since the previous run:" >&5 $as_echo "$as_me: warning: ignoring whitespace changes in \`$ac_var' since the previous run:" >&2;} eval $ac_var=\$ac_old_val fi { $as_echo "$as_me:${as_lineno-$LINENO}: former value: \`$ac_old_val'" >&5 $as_echo "$as_me: former value: \`$ac_old_val'" >&2;} { $as_echo "$as_me:${as_lineno-$LINENO}: current value: \`$ac_new_val'" >&5 $as_echo "$as_me: current value: \`$ac_new_val'" >&2;} fi;; esac # Pass precious variables to config.status. if test "$ac_new_set" = set; then case $ac_new_val in *\'*) ac_arg=$ac_var=`$as_echo "$ac_new_val" | sed "s/'/'\\\\\\\\''/g"` ;; *) ac_arg=$ac_var=$ac_new_val ;; esac case " $ac_configure_args " in *" '$ac_arg' "*) ;; # Avoid dups. Use of quotes ensures accuracy. *) as_fn_append ac_configure_args " '$ac_arg'" ;; esac fi done if $ac_cache_corrupted; then { $as_echo "$as_me:${as_lineno-$LINENO}: error: in \`$ac_pwd':" >&5 $as_echo "$as_me: error: in \`$ac_pwd':" >&2;} { $as_echo "$as_me:${as_lineno-$LINENO}: error: changes in the environment can compromise the build" >&5 $as_echo "$as_me: error: changes in the environment can compromise the build" >&2;} as_fn_error $? "run \`make distclean' and/or \`rm $cache_file' and start over" "$LINENO" 5 fi ## -------------------- ## ## Main body of script. ## ## -------------------- ## ac_ext=c ac_cpp='$CPP $CPPFLAGS' ac_compile='$CC -c $CFLAGS $CPPFLAGS conftest.$ac_ext >&5' ac_link='$CC -o conftest$ac_exeext $CFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS >&5' ac_compiler_gnu=$ac_cv_c_compiler_gnu ac_config_headers="$ac_config_headers config.h" ac_aux_dir= for ac_dir in "$srcdir" "$srcdir/.." "$srcdir/../.."; do if test -f "$ac_dir/install-sh"; then ac_aux_dir=$ac_dir ac_install_sh="$ac_aux_dir/install-sh -c" break elif test -f "$ac_dir/install.sh"; then ac_aux_dir=$ac_dir ac_install_sh="$ac_aux_dir/install.sh -c" break elif test -f "$ac_dir/shtool"; then ac_aux_dir=$ac_dir ac_install_sh="$ac_aux_dir/shtool install -c" break fi done if test -z "$ac_aux_dir"; then as_fn_error $? "cannot find install-sh, install.sh, or shtool in \"$srcdir\" \"$srcdir/..\" \"$srcdir/../..\"" "$LINENO" 5 fi # These three variables are undocumented and unsupported, # and are intended to be withdrawn in a future Autoconf release. # They can cause serious problems if a builder's source tree is in a directory # whose full name contains unusual characters. ac_config_guess="$SHELL $ac_aux_dir/config.guess" # Please don't use this var. ac_config_sub="$SHELL $ac_aux_dir/config.sub" # Please don't use this var. ac_configure="$SHELL $ac_aux_dir/configure" # Please don't use this var. # Make sure we can run config.sub. $SHELL "$ac_aux_dir/config.sub" sun4 >/dev/null 2>&1 || as_fn_error $? "cannot run $SHELL $ac_aux_dir/config.sub" "$LINENO" 5 { $as_echo "$as_me:${as_lineno-$LINENO}: checking build system type" >&5 $as_echo_n "checking build system type... " >&6; } if ${ac_cv_build+:} false; then : $as_echo_n "(cached) " >&6 else ac_build_alias=$build_alias test "x$ac_build_alias" = x && ac_build_alias=`$SHELL "$ac_aux_dir/config.guess"` test "x$ac_build_alias" = x && as_fn_error $? "cannot guess build type; you must specify one" "$LINENO" 5 ac_cv_build=`$SHELL "$ac_aux_dir/config.sub" $ac_build_alias` || as_fn_error $? "$SHELL $ac_aux_dir/config.sub $ac_build_alias failed" "$LINENO" 5 fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_build" >&5 $as_echo "$ac_cv_build" >&6; } case $ac_cv_build in *-*-*) ;; *) as_fn_error $? "invalid value of canonical build" "$LINENO" 5;; esac build=$ac_cv_build ac_save_IFS=$IFS; IFS='-' set x $ac_cv_build shift build_cpu=$1 build_vendor=$2 shift; shift # Remember, the first character of IFS is used to create $*, # except with old shells: build_os=$* IFS=$ac_save_IFS case $build_os in *\ *) build_os=`echo "$build_os" | sed 's/ /-/g'`;; esac { $as_echo "$as_me:${as_lineno-$LINENO}: checking host system type" >&5 $as_echo_n "checking host system type... " >&6; } if ${ac_cv_host+:} false; then : $as_echo_n "(cached) " >&6 else if test "x$host_alias" = x; then ac_cv_host=$ac_cv_build else ac_cv_host=`$SHELL "$ac_aux_dir/config.sub" $host_alias` || as_fn_error $? "$SHELL $ac_aux_dir/config.sub $host_alias failed" "$LINENO" 5 fi fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_host" >&5 $as_echo "$ac_cv_host" >&6; } case $ac_cv_host in *-*-*) ;; *) as_fn_error $? "invalid value of canonical host" "$LINENO" 5;; esac host=$ac_cv_host ac_save_IFS=$IFS; IFS='-' set x $ac_cv_host shift host_cpu=$1 host_vendor=$2 shift; shift # Remember, the first character of IFS is used to create $*, # except with old shells: host_os=$* IFS=$ac_save_IFS case $host_os in *\ *) host_os=`echo "$host_os" | sed 's/ /-/g'`;; esac { $as_echo "$as_me:${as_lineno-$LINENO}: checking target system type" >&5 $as_echo_n "checking target system type... " >&6; } if ${ac_cv_target+:} false; then : $as_echo_n "(cached) " >&6 else if test "x$target_alias" = x; then ac_cv_target=$ac_cv_host else ac_cv_target=`$SHELL "$ac_aux_dir/config.sub" $target_alias` || as_fn_error $? "$SHELL $ac_aux_dir/config.sub $target_alias failed" "$LINENO" 5 fi fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_target" >&5 $as_echo "$ac_cv_target" >&6; } case $ac_cv_target in *-*-*) ;; *) as_fn_error $? "invalid value of canonical target" "$LINENO" 5;; esac target=$ac_cv_target ac_save_IFS=$IFS; IFS='-' set x $ac_cv_target shift target_cpu=$1 target_vendor=$2 shift; shift # Remember, the first character of IFS is used to create $*, # except with old shells: target_os=$* IFS=$ac_save_IFS case $target_os in *\ *) target_os=`echo "$target_os" | sed 's/ /-/g'`;; esac # The aliases save the names the user supplied, while $host etc. # will get canonicalized. test -n "$target_alias" && test "$program_prefix$program_suffix$program_transform_name" = \ NONENONEs,x,x, && program_prefix=${target_alias}- if test "x$ac_cv_env_PKG_CONFIG_set" != "xset"; then if test -n "$ac_tool_prefix"; then # Extract the first word of "${ac_tool_prefix}pkg-config", so it can be a program name with args. set dummy ${ac_tool_prefix}pkg-config; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } if ${ac_cv_path_PKG_CONFIG+:} false; then : $as_echo_n "(cached) " >&6 else case $PKG_CONFIG in [\\/]* | ?:[\\/]*) ac_cv_path_PKG_CONFIG="$PKG_CONFIG" # Let the user override the test with a path. ;; *) as_save_IFS=$IFS; IFS=$PATH_SEPARATOR for as_dir in $PATH do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_path_PKG_CONFIG="$as_dir/$ac_word$ac_exec_ext" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 fi done done IFS=$as_save_IFS ;; esac fi PKG_CONFIG=$ac_cv_path_PKG_CONFIG if test -n "$PKG_CONFIG"; then { $as_echo "$as_me:${as_lineno-$LINENO}: result: $PKG_CONFIG" >&5 $as_echo "$PKG_CONFIG" >&6; } else { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 $as_echo "no" >&6; } fi fi if test -z "$ac_cv_path_PKG_CONFIG"; then ac_pt_PKG_CONFIG=$PKG_CONFIG # Extract the first word of "pkg-config", so it can be a program name with args. set dummy pkg-config; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } if ${ac_cv_path_ac_pt_PKG_CONFIG+:} false; then : $as_echo_n "(cached) " >&6 else case $ac_pt_PKG_CONFIG in [\\/]* | ?:[\\/]*) ac_cv_path_ac_pt_PKG_CONFIG="$ac_pt_PKG_CONFIG" # Let the user override the test with a path. ;; *) as_save_IFS=$IFS; IFS=$PATH_SEPARATOR for as_dir in $PATH do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_path_ac_pt_PKG_CONFIG="$as_dir/$ac_word$ac_exec_ext" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 fi done done IFS=$as_save_IFS ;; esac fi ac_pt_PKG_CONFIG=$ac_cv_path_ac_pt_PKG_CONFIG if test -n "$ac_pt_PKG_CONFIG"; then { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_pt_PKG_CONFIG" >&5 $as_echo "$ac_pt_PKG_CONFIG" >&6; } else { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 $as_echo "no" >&6; } fi if test "x$ac_pt_PKG_CONFIG" = x; then PKG_CONFIG="" else case $cross_compiling:$ac_tool_warned in yes:) { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: using cross tools not prefixed with host triplet" >&5 $as_echo "$as_me: WARNING: using cross tools not prefixed with host triplet" >&2;} ac_tool_warned=yes ;; esac PKG_CONFIG=$ac_pt_PKG_CONFIG fi else PKG_CONFIG="$ac_cv_path_PKG_CONFIG" fi fi if test -n "$PKG_CONFIG"; then _pkg_min_version=0.9.0 { $as_echo "$as_me:${as_lineno-$LINENO}: checking pkg-config is at least version $_pkg_min_version" >&5 $as_echo_n "checking pkg-config is at least version $_pkg_min_version... " >&6; } if $PKG_CONFIG --atleast-pkgconfig-version $_pkg_min_version; then { $as_echo "$as_me:${as_lineno-$LINENO}: result: yes" >&5 $as_echo "yes" >&6; } else { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 $as_echo "no" >&6; } PKG_CONFIG="" fi fi am__api_version='1.15' # Find a good install program. We prefer a C program (faster), # so one script is as good as another. But avoid the broken or # incompatible versions: # SysV /etc/install, /usr/sbin/install # SunOS /usr/etc/install # IRIX /sbin/install # AIX /bin/install # AmigaOS /C/install, which installs bootblocks on floppy discs # AIX 4 /usr/bin/installbsd, which doesn't work without a -g flag # AFS /usr/afsws/bin/install, which mishandles nonexistent args # SVR4 /usr/ucb/install, which tries to use the nonexistent group "staff" # OS/2's system install, which has a completely different semantic # ./install, which can be erroneously created by make from ./install.sh. # Reject install programs that cannot install multiple files. { $as_echo "$as_me:${as_lineno-$LINENO}: checking for a BSD-compatible install" >&5 $as_echo_n "checking for a BSD-compatible install... " >&6; } if test -z "$INSTALL"; then if ${ac_cv_path_install+:} false; then : $as_echo_n "(cached) " >&6 else as_save_IFS=$IFS; IFS=$PATH_SEPARATOR for as_dir in $PATH do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. # Account for people who put trailing slashes in PATH elements. case $as_dir/ in #(( ./ | .// | /[cC]/* | \ /etc/* | /usr/sbin/* | /usr/etc/* | /sbin/* | /usr/afsws/bin/* | \ ?:[\\/]os2[\\/]install[\\/]* | ?:[\\/]OS2[\\/]INSTALL[\\/]* | \ /usr/ucb/* ) ;; *) # OSF1 and SCO ODT 3.0 have their own names for install. # Don't use installbsd from OSF since it installs stuff as root # by default. for ac_prog in ginstall scoinst install; do for ac_exec_ext in '' $ac_executable_extensions; do if as_fn_executable_p "$as_dir/$ac_prog$ac_exec_ext"; then if test $ac_prog = install && grep dspmsg "$as_dir/$ac_prog$ac_exec_ext" >/dev/null 2>&1; then # AIX install. It has an incompatible calling convention. : elif test $ac_prog = install && grep pwplus "$as_dir/$ac_prog$ac_exec_ext" >/dev/null 2>&1; then # program-specific install script used by HP pwplus--don't use. : else rm -rf conftest.one conftest.two conftest.dir echo one > conftest.one echo two > conftest.two mkdir conftest.dir if "$as_dir/$ac_prog$ac_exec_ext" -c conftest.one conftest.two "`pwd`/conftest.dir" && test -s conftest.one && test -s conftest.two && test -s conftest.dir/conftest.one && test -s conftest.dir/conftest.two then ac_cv_path_install="$as_dir/$ac_prog$ac_exec_ext -c" break 3 fi fi fi done done ;; esac done IFS=$as_save_IFS rm -rf conftest.one conftest.two conftest.dir fi if test "${ac_cv_path_install+set}" = set; then INSTALL=$ac_cv_path_install else # As a last resort, use the slow shell script. Don't cache a # value for INSTALL within a source directory, because that will # break other packages using the cache if that directory is # removed, or if the value is a relative name. INSTALL=$ac_install_sh fi fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $INSTALL" >&5 $as_echo "$INSTALL" >&6; } # Use test -z because SunOS4 sh mishandles braces in ${var-val}. # It thinks the first close brace ends the variable substitution. test -z "$INSTALL_PROGRAM" && INSTALL_PROGRAM='${INSTALL}' test -z "$INSTALL_SCRIPT" && INSTALL_SCRIPT='${INSTALL}' test -z "$INSTALL_DATA" && INSTALL_DATA='${INSTALL} -m 644' { $as_echo "$as_me:${as_lineno-$LINENO}: checking whether build environment is sane" >&5 $as_echo_n "checking whether build environment is sane... " >&6; } # Reject unsafe characters in $srcdir or the absolute working directory # name. Accept space and tab only in the latter. am_lf=' ' case `pwd` in *[\\\"\#\$\&\'\`$am_lf]*) as_fn_error $? "unsafe absolute working directory name" "$LINENO" 5;; esac case $srcdir in *[\\\"\#\$\&\'\`$am_lf\ \ ]*) as_fn_error $? "unsafe srcdir value: '$srcdir'" "$LINENO" 5;; esac # Do 'set' in a subshell so we don't clobber the current shell's # arguments. Must try -L first in case configure is actually a # symlink; some systems play weird games with the mod time of symlinks # (eg FreeBSD returns the mod time of the symlink's containing # directory). if ( am_has_slept=no for am_try in 1 2; do echo "timestamp, slept: $am_has_slept" > conftest.file set X `ls -Lt "$srcdir/configure" conftest.file 2> /dev/null` if test "$*" = "X"; then # -L didn't work. set X `ls -t "$srcdir/configure" conftest.file` fi if test "$*" != "X $srcdir/configure conftest.file" \ && test "$*" != "X conftest.file $srcdir/configure"; then # If neither matched, then we have a broken ls. This can happen # if, for instance, CONFIG_SHELL is bash and it inherits a # broken ls alias from the environment. This has actually # happened. Such a system could not be considered "sane". as_fn_error $? "ls -t appears to fail. Make sure there is not a broken alias in your environment" "$LINENO" 5 fi if test "$2" = conftest.file || test $am_try -eq 2; then break fi # Just in case. sleep 1 am_has_slept=yes done test "$2" = conftest.file ) then # Ok. : else as_fn_error $? "newly created file is older than distributed files! Check your system clock" "$LINENO" 5 fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: yes" >&5 $as_echo "yes" >&6; } # If we didn't sleep, we still need to ensure time stamps of config.status and # generated files are strictly newer. am_sleep_pid= if grep 'slept: no' conftest.file >/dev/null 2>&1; then ( sleep 1 ) & am_sleep_pid=$! fi rm -f conftest.file test "$program_prefix" != NONE && program_transform_name="s&^&$program_prefix&;$program_transform_name" # Use a double $ so make ignores it. test "$program_suffix" != NONE && program_transform_name="s&\$&$program_suffix&;$program_transform_name" # Double any \ or $. # By default was `s,x,x', remove it if useless. ac_script='s/[\\$]/&&/g;s/;s,x,x,$//' program_transform_name=`$as_echo "$program_transform_name" | sed "$ac_script"` # Expand $ac_aux_dir to an absolute path. am_aux_dir=`cd "$ac_aux_dir" && pwd` if test x"${MISSING+set}" != xset; then case $am_aux_dir in *\ * | *\ *) MISSING="\${SHELL} \"$am_aux_dir/missing\"" ;; *) MISSING="\${SHELL} $am_aux_dir/missing" ;; esac fi # Use eval to expand $SHELL if eval "$MISSING --is-lightweight"; then am_missing_run="$MISSING " else am_missing_run= { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: 'missing' script is too old or missing" >&5 $as_echo "$as_me: WARNING: 'missing' script is too old or missing" >&2;} fi if test x"${install_sh+set}" != xset; then case $am_aux_dir in *\ * | *\ *) install_sh="\${SHELL} '$am_aux_dir/install-sh'" ;; *) install_sh="\${SHELL} $am_aux_dir/install-sh" esac fi # Installed binaries are usually stripped using 'strip' when the user # run "make install-strip". However 'strip' might not be the right # tool to use in cross-compilation environments, therefore Automake # will honor the 'STRIP' environment variable to overrule this program. if test "$cross_compiling" != no; then if test -n "$ac_tool_prefix"; then # Extract the first word of "${ac_tool_prefix}strip", so it can be a program name with args. set dummy ${ac_tool_prefix}strip; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } if ${ac_cv_prog_STRIP+:} false; then : $as_echo_n "(cached) " >&6 else if test -n "$STRIP"; then ac_cv_prog_STRIP="$STRIP" # Let the user override the test. else as_save_IFS=$IFS; IFS=$PATH_SEPARATOR for as_dir in $PATH do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_prog_STRIP="${ac_tool_prefix}strip" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 fi done done IFS=$as_save_IFS fi fi STRIP=$ac_cv_prog_STRIP if test -n "$STRIP"; then { $as_echo "$as_me:${as_lineno-$LINENO}: result: $STRIP" >&5 $as_echo "$STRIP" >&6; } else { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 $as_echo "no" >&6; } fi fi if test -z "$ac_cv_prog_STRIP"; then ac_ct_STRIP=$STRIP # Extract the first word of "strip", so it can be a program name with args. set dummy strip; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } if ${ac_cv_prog_ac_ct_STRIP+:} false; then : $as_echo_n "(cached) " >&6 else if test -n "$ac_ct_STRIP"; then ac_cv_prog_ac_ct_STRIP="$ac_ct_STRIP" # Let the user override the test. else as_save_IFS=$IFS; IFS=$PATH_SEPARATOR for as_dir in $PATH do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_prog_ac_ct_STRIP="strip" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 fi done done IFS=$as_save_IFS fi fi ac_ct_STRIP=$ac_cv_prog_ac_ct_STRIP if test -n "$ac_ct_STRIP"; then { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_ct_STRIP" >&5 $as_echo "$ac_ct_STRIP" >&6; } else { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 $as_echo "no" >&6; } fi if test "x$ac_ct_STRIP" = x; then STRIP=":" else case $cross_compiling:$ac_tool_warned in yes:) { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: using cross tools not prefixed with host triplet" >&5 $as_echo "$as_me: WARNING: using cross tools not prefixed with host triplet" >&2;} ac_tool_warned=yes ;; esac STRIP=$ac_ct_STRIP fi else STRIP="$ac_cv_prog_STRIP" fi fi INSTALL_STRIP_PROGRAM="\$(install_sh) -c -s" { $as_echo "$as_me:${as_lineno-$LINENO}: checking for a thread-safe mkdir -p" >&5 $as_echo_n "checking for a thread-safe mkdir -p... " >&6; } if test -z "$MKDIR_P"; then if ${ac_cv_path_mkdir+:} false; then : $as_echo_n "(cached) " >&6 else as_save_IFS=$IFS; IFS=$PATH_SEPARATOR for as_dir in $PATH$PATH_SEPARATOR/opt/sfw/bin do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_prog in mkdir gmkdir; do for ac_exec_ext in '' $ac_executable_extensions; do as_fn_executable_p "$as_dir/$ac_prog$ac_exec_ext" || continue case `"$as_dir/$ac_prog$ac_exec_ext" --version 2>&1` in #( 'mkdir (GNU coreutils) '* | \ 'mkdir (coreutils) '* | \ 'mkdir (fileutils) '4.1*) ac_cv_path_mkdir=$as_dir/$ac_prog$ac_exec_ext break 3;; esac done done done IFS=$as_save_IFS fi test -d ./--version && rmdir ./--version if test "${ac_cv_path_mkdir+set}" = set; then MKDIR_P="$ac_cv_path_mkdir -p" else # As a last resort, use the slow shell script. Don't cache a # value for MKDIR_P within a source directory, because that will # break other packages using the cache if that directory is # removed, or if the value is a relative name. MKDIR_P="$ac_install_sh -d" fi fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $MKDIR_P" >&5 $as_echo "$MKDIR_P" >&6; } for ac_prog in gawk mawk nawk awk do # Extract the first word of "$ac_prog", so it can be a program name with args. set dummy $ac_prog; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } if ${ac_cv_prog_AWK+:} false; then : $as_echo_n "(cached) " >&6 else if test -n "$AWK"; then ac_cv_prog_AWK="$AWK" # Let the user override the test. else as_save_IFS=$IFS; IFS=$PATH_SEPARATOR for as_dir in $PATH do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_prog_AWK="$ac_prog" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 fi done done IFS=$as_save_IFS fi fi AWK=$ac_cv_prog_AWK if test -n "$AWK"; then { $as_echo "$as_me:${as_lineno-$LINENO}: result: $AWK" >&5 $as_echo "$AWK" >&6; } else { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 $as_echo "no" >&6; } fi test -n "$AWK" && break done { $as_echo "$as_me:${as_lineno-$LINENO}: checking whether ${MAKE-make} sets \$(MAKE)" >&5 $as_echo_n "checking whether ${MAKE-make} sets \$(MAKE)... " >&6; } set x ${MAKE-make} ac_make=`$as_echo "$2" | sed 's/+/p/g; s/[^a-zA-Z0-9_]/_/g'` if eval \${ac_cv_prog_make_${ac_make}_set+:} false; then : $as_echo_n "(cached) " >&6 else cat >conftest.make <<\_ACEOF SHELL = /bin/sh all: @echo '@@@%%%=$(MAKE)=@@@%%%' _ACEOF # GNU make sometimes prints "make[1]: Entering ...", which would confuse us. case `${MAKE-make} -f conftest.make 2>/dev/null` in *@@@%%%=?*=@@@%%%*) eval ac_cv_prog_make_${ac_make}_set=yes;; *) eval ac_cv_prog_make_${ac_make}_set=no;; esac rm -f conftest.make fi if eval test \$ac_cv_prog_make_${ac_make}_set = yes; then { $as_echo "$as_me:${as_lineno-$LINENO}: result: yes" >&5 $as_echo "yes" >&6; } SET_MAKE= else { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 $as_echo "no" >&6; } SET_MAKE="MAKE=${MAKE-make}" fi rm -rf .tst 2>/dev/null mkdir .tst 2>/dev/null if test -d .tst; then am__leading_dot=. else am__leading_dot=_ fi rmdir .tst 2>/dev/null # Check whether --enable-silent-rules was given. if test "${enable_silent_rules+set}" = set; then : enableval=$enable_silent_rules; fi case $enable_silent_rules in # ((( yes) AM_DEFAULT_VERBOSITY=0;; no) AM_DEFAULT_VERBOSITY=1;; *) AM_DEFAULT_VERBOSITY=1;; esac am_make=${MAKE-make} { $as_echo "$as_me:${as_lineno-$LINENO}: checking whether $am_make supports nested variables" >&5 $as_echo_n "checking whether $am_make supports nested variables... " >&6; } if ${am_cv_make_support_nested_variables+:} false; then : $as_echo_n "(cached) " >&6 else if $as_echo 'TRUE=$(BAR$(V)) BAR0=false BAR1=true V=1 am__doit: @$(TRUE) .PHONY: am__doit' | $am_make -f - >/dev/null 2>&1; then am_cv_make_support_nested_variables=yes else am_cv_make_support_nested_variables=no fi fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $am_cv_make_support_nested_variables" >&5 $as_echo "$am_cv_make_support_nested_variables" >&6; } if test $am_cv_make_support_nested_variables = yes; then AM_V='$(V)' AM_DEFAULT_V='$(AM_DEFAULT_VERBOSITY)' else AM_V=$AM_DEFAULT_VERBOSITY AM_DEFAULT_V=$AM_DEFAULT_VERBOSITY fi AM_BACKSLASH='\' if test "`cd $srcdir && pwd`" != "`pwd`"; then # Use -I$(srcdir) only when $(srcdir) != ., so that make's output # is not polluted with repeated "-I." am__isrc=' -I$(srcdir)' # test to see if srcdir already configured if test -f $srcdir/config.status; then as_fn_error $? "source directory already configured; run \"make distclean\" there first" "$LINENO" 5 fi fi # test whether we have cygpath if test -z "$CYGPATH_W"; then if (cygpath --version) >/dev/null 2>/dev/null; then CYGPATH_W='cygpath -w' else CYGPATH_W=echo fi fi # Define the identity of the package. PACKAGE='cyrus-imapd' VERSION='2.5.10' cat >>confdefs.h <<_ACEOF #define PACKAGE "$PACKAGE" _ACEOF cat >>confdefs.h <<_ACEOF #define VERSION "$VERSION" _ACEOF # Some tools Automake needs. ACLOCAL=${ACLOCAL-"${am_missing_run}aclocal-${am__api_version}"} AUTOCONF=${AUTOCONF-"${am_missing_run}autoconf"} AUTOMAKE=${AUTOMAKE-"${am_missing_run}automake-${am__api_version}"} AUTOHEADER=${AUTOHEADER-"${am_missing_run}autoheader"} MAKEINFO=${MAKEINFO-"${am_missing_run}makeinfo"} # For better backward compatibility. To be removed once Automake 1.9.x # dies out for good. For more background, see: # # mkdir_p='$(MKDIR_P)' # We need awk for the "check" target (and possibly the TAP driver). The # system "awk" is bad on some platforms. # Always define AMTAR for backward compatibility. Yes, it's still used # in the wild :-( We should find a proper way to deprecate it ... AMTAR='$${TAR-tar}' # We'll loop over all known methods to create a tar archive until one works. _am_tools='gnutar pax cpio none' am__tar='$${TAR-tar} chof - "$$tardir"' am__untar='$${TAR-tar} xf -' # POSIX will say in a future version that running "rm -f" with no argument # is OK; and we want to be able to make that assumption in our Makefile # recipes. So use an aggressive probe to check that the usage we want is # actually supported "in the wild" to an acceptable degree. # See automake bug#10828. # To make any issue more visible, cause the running configure to be aborted # by default if the 'rm' program in use doesn't match our expectations; the # user can still override this though. if rm -f && rm -fr && rm -rf; then : OK; else cat >&2 <<'END' Oops! Your 'rm' program seems unable to run without file operands specified on the command line, even when the '-f' option is present. This is contrary to the behaviour of most rm programs out there, and not conforming with the upcoming POSIX standard: Please tell bug-automake@gnu.org about your system, including the value of your $PATH and any error possibly output before this message. This can help us improve future automake versions. END if test x"$ACCEPT_INFERIOR_RM_PROGRAM" = x"yes"; then echo 'Configuration will proceed anyway, since you have set the' >&2 echo 'ACCEPT_INFERIOR_RM_PROGRAM variable to "yes"' >&2 echo >&2 else cat >&2 <<'END' Aborting the configuration process, to ensure you take notice of the issue. You can download and install GNU coreutils to get an 'rm' implementation that behaves properly: . If you want to complete the configuration process using your problematic 'rm' anyway, export the environment variable ACCEPT_INFERIOR_RM_PROGRAM to "yes", and re-run configure. END as_fn_error $? "Your 'rm' program is bad, sorry." "$LINENO" 5 fi fi # Check whether --with-extraident was given. if test "${with_extraident+set}" = set; then : withval=$with_extraident; cat >>confdefs.h <<_ACEOF #define EXTRA_IDENT "$withval" _ACEOF fi { $as_echo "$as_me:${as_lineno-$LINENO}: checking whether to enable maintainer-specific portions of Makefiles" >&5 $as_echo_n "checking whether to enable maintainer-specific portions of Makefiles... " >&6; } # Check whether --enable-maintainer-mode was given. if test "${enable_maintainer_mode+set}" = set; then : enableval=$enable_maintainer_mode; USE_MAINTAINER_MODE=$enableval else USE_MAINTAINER_MODE=no fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $USE_MAINTAINER_MODE" >&5 $as_echo "$USE_MAINTAINER_MODE" >&6; } if test $USE_MAINTAINER_MODE = yes; then MAINTAINER_MODE_TRUE= MAINTAINER_MODE_FALSE='#' else MAINTAINER_MODE_TRUE='#' MAINTAINER_MODE_FALSE= fi MAINT=$MAINTAINER_MODE_TRUE COV_CFLAGS= COV_LDFLAGS= # Check whether --enable-coverage was given. if test "${enable_coverage+set}" = set; then : enableval=$enable_coverage; fi if test "x$enable_coverage" = "xyes"; then : COV_CFLAGS="--coverage" COV_LDFLAGS="--coverage" fi # Check whether --with-login was given. if test "${with_login+set}" = set; then : withval=$with_login; as_fn_error $? "--with-login is no longer supported. Configure SASL appropriately instead." "$LINENO" 5 fi if test "x$prefix" = "xNONE"; then myprefix="$ac_default_prefix" else myprefix="$prefix" fi # Check whether --with-cyrus-prefix was given. if test "${with_cyrus_prefix+set}" = set; then : withval=$with_cyrus_prefix; cyrus_prefix="$withval" else cyrus_prefix="$myprefix/cyrus" fi cat >>confdefs.h <<_ACEOF #define CYRUS_PATH "$cyrus_prefix" _ACEOF # Check whether --with-service-path was given. if test "${with_service_path+set}" = set; then : withval=$with_service_path; servicedir="$withval" else servicedir="$cyrus_prefix/bin" fi userdir=$servicedir cat >>confdefs.h <<_ACEOF #define SERVICE_DIR "$servicedir" _ACEOF # Check whether --with-cyrus-user was given. if test "${with_cyrus_user+set}" = set; then : withval=$with_cyrus_user; cyrus_user="$withval" else cyrus_user="cyrus" fi cat >>confdefs.h <<_ACEOF #define CYRUS_USER "$cyrus_user" _ACEOF # Check whether --with-cyrus-group was given. if test "${with_cyrus_group+set}" = set; then : withval=$with_cyrus_group; cyrus_group="$withval" else cyrus_group="mail" fi if test $sysconfdir = '${prefix}/etc'; then sysconfdir="/etc" fi cat >>confdefs.h <<_ACEOF #define SYSCONFDIR "$sysconfdir" _ACEOF ac_ext=c ac_cpp='$CPP $CPPFLAGS' ac_compile='$CC -c $CFLAGS $CPPFLAGS conftest.$ac_ext >&5' ac_link='$CC -o conftest$ac_exeext $CFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS >&5' ac_compiler_gnu=$ac_cv_c_compiler_gnu if test -n "$ac_tool_prefix"; then # Extract the first word of "${ac_tool_prefix}gcc", so it can be a program name with args. set dummy ${ac_tool_prefix}gcc; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } if ${ac_cv_prog_CC+:} false; then : $as_echo_n "(cached) " >&6 else if test -n "$CC"; then ac_cv_prog_CC="$CC" # Let the user override the test. else as_save_IFS=$IFS; IFS=$PATH_SEPARATOR for as_dir in $PATH do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_prog_CC="${ac_tool_prefix}gcc" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 fi done done IFS=$as_save_IFS fi fi CC=$ac_cv_prog_CC if test -n "$CC"; then { $as_echo "$as_me:${as_lineno-$LINENO}: result: $CC" >&5 $as_echo "$CC" >&6; } else { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 $as_echo "no" >&6; } fi fi if test -z "$ac_cv_prog_CC"; then ac_ct_CC=$CC # Extract the first word of "gcc", so it can be a program name with args. set dummy gcc; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } if ${ac_cv_prog_ac_ct_CC+:} false; then : $as_echo_n "(cached) " >&6 else if test -n "$ac_ct_CC"; then ac_cv_prog_ac_ct_CC="$ac_ct_CC" # Let the user override the test. else as_save_IFS=$IFS; IFS=$PATH_SEPARATOR for as_dir in $PATH do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_prog_ac_ct_CC="gcc" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 fi done done IFS=$as_save_IFS fi fi ac_ct_CC=$ac_cv_prog_ac_ct_CC if test -n "$ac_ct_CC"; then { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_ct_CC" >&5 $as_echo "$ac_ct_CC" >&6; } else { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 $as_echo "no" >&6; } fi if test "x$ac_ct_CC" = x; then CC="" else case $cross_compiling:$ac_tool_warned in yes:) { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: using cross tools not prefixed with host triplet" >&5 $as_echo "$as_me: WARNING: using cross tools not prefixed with host triplet" >&2;} ac_tool_warned=yes ;; esac CC=$ac_ct_CC fi else CC="$ac_cv_prog_CC" fi if test -z "$CC"; then if test -n "$ac_tool_prefix"; then # Extract the first word of "${ac_tool_prefix}cc", so it can be a program name with args. set dummy ${ac_tool_prefix}cc; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } if ${ac_cv_prog_CC+:} false; then : $as_echo_n "(cached) " >&6 else if test -n "$CC"; then ac_cv_prog_CC="$CC" # Let the user override the test. else as_save_IFS=$IFS; IFS=$PATH_SEPARATOR for as_dir in $PATH do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_prog_CC="${ac_tool_prefix}cc" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 fi done done IFS=$as_save_IFS fi fi CC=$ac_cv_prog_CC if test -n "$CC"; then { $as_echo "$as_me:${as_lineno-$LINENO}: result: $CC" >&5 $as_echo "$CC" >&6; } else { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 $as_echo "no" >&6; } fi fi fi if test -z "$CC"; then # Extract the first word of "cc", so it can be a program name with args. set dummy cc; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } if ${ac_cv_prog_CC+:} false; then : $as_echo_n "(cached) " >&6 else if test -n "$CC"; then ac_cv_prog_CC="$CC" # Let the user override the test. else ac_prog_rejected=no as_save_IFS=$IFS; IFS=$PATH_SEPARATOR for as_dir in $PATH do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then if test "$as_dir/$ac_word$ac_exec_ext" = "/usr/ucb/cc"; then ac_prog_rejected=yes continue fi ac_cv_prog_CC="cc" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 fi done done IFS=$as_save_IFS if test $ac_prog_rejected = yes; then # We found a bogon in the path, so make sure we never use it. set dummy $ac_cv_prog_CC shift if test $# != 0; then # We chose a different compiler from the bogus one. # However, it has the same basename, so the bogon will be chosen # first if we set CC to just the basename; use the full file name. shift ac_cv_prog_CC="$as_dir/$ac_word${1+' '}$@" fi fi fi fi CC=$ac_cv_prog_CC if test -n "$CC"; then { $as_echo "$as_me:${as_lineno-$LINENO}: result: $CC" >&5 $as_echo "$CC" >&6; } else { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 $as_echo "no" >&6; } fi fi if test -z "$CC"; then if test -n "$ac_tool_prefix"; then for ac_prog in cl.exe do # Extract the first word of "$ac_tool_prefix$ac_prog", so it can be a program name with args. set dummy $ac_tool_prefix$ac_prog; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } if ${ac_cv_prog_CC+:} false; then : $as_echo_n "(cached) " >&6 else if test -n "$CC"; then ac_cv_prog_CC="$CC" # Let the user override the test. else as_save_IFS=$IFS; IFS=$PATH_SEPARATOR for as_dir in $PATH do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_prog_CC="$ac_tool_prefix$ac_prog" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 fi done done IFS=$as_save_IFS fi fi CC=$ac_cv_prog_CC if test -n "$CC"; then { $as_echo "$as_me:${as_lineno-$LINENO}: result: $CC" >&5 $as_echo "$CC" >&6; } else { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 $as_echo "no" >&6; } fi test -n "$CC" && break done fi if test -z "$CC"; then ac_ct_CC=$CC for ac_prog in cl.exe do # Extract the first word of "$ac_prog", so it can be a program name with args. set dummy $ac_prog; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } if ${ac_cv_prog_ac_ct_CC+:} false; then : $as_echo_n "(cached) " >&6 else if test -n "$ac_ct_CC"; then ac_cv_prog_ac_ct_CC="$ac_ct_CC" # Let the user override the test. else as_save_IFS=$IFS; IFS=$PATH_SEPARATOR for as_dir in $PATH do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_prog_ac_ct_CC="$ac_prog" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 fi done done IFS=$as_save_IFS fi fi ac_ct_CC=$ac_cv_prog_ac_ct_CC if test -n "$ac_ct_CC"; then { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_ct_CC" >&5 $as_echo "$ac_ct_CC" >&6; } else { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 $as_echo "no" >&6; } fi test -n "$ac_ct_CC" && break done if test "x$ac_ct_CC" = x; then CC="" else case $cross_compiling:$ac_tool_warned in yes:) { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: using cross tools not prefixed with host triplet" >&5 $as_echo "$as_me: WARNING: using cross tools not prefixed with host triplet" >&2;} ac_tool_warned=yes ;; esac CC=$ac_ct_CC fi fi fi test -z "$CC" && { { $as_echo "$as_me:${as_lineno-$LINENO}: error: in \`$ac_pwd':" >&5 $as_echo "$as_me: error: in \`$ac_pwd':" >&2;} as_fn_error $? "no acceptable C compiler found in \$PATH See \`config.log' for more details" "$LINENO" 5; } # Provide some information about the compiler. $as_echo "$as_me:${as_lineno-$LINENO}: checking for C compiler version" >&5 set X $ac_compile ac_compiler=$2 for ac_option in --version -v -V -qversion; do { { ac_try="$ac_compiler $ac_option >&5" case "(($ac_try" in *\"* | *\`* | *\\*) ac_try_echo=\$ac_try;; *) ac_try_echo=$ac_try;; esac eval ac_try_echo="\"\$as_me:${as_lineno-$LINENO}: $ac_try_echo\"" $as_echo "$ac_try_echo"; } >&5 (eval "$ac_compiler $ac_option >&5") 2>conftest.err ac_status=$? if test -s conftest.err; then sed '10a\ ... rest of stderr output deleted ... 10q' conftest.err >conftest.er1 cat conftest.er1 >&5 fi rm -f conftest.er1 conftest.err $as_echo "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 test $ac_status = 0; } done cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ int main () { ; return 0; } _ACEOF ac_clean_files_save=$ac_clean_files ac_clean_files="$ac_clean_files a.out a.out.dSYM a.exe b.out" # Try to create an executable without -o first, disregard a.out. # It will help us diagnose broken compilers, and finding out an intuition # of exeext. { $as_echo "$as_me:${as_lineno-$LINENO}: checking whether the C compiler works" >&5 $as_echo_n "checking whether the C compiler works... " >&6; } ac_link_default=`$as_echo "$ac_link" | sed 's/ -o *conftest[^ ]*//'` # The possible output files: ac_files="a.out conftest.exe conftest a.exe a_out.exe b.out conftest.*" ac_rmfiles= for ac_file in $ac_files do case $ac_file in *.$ac_ext | *.xcoff | *.tds | *.d | *.pdb | *.xSYM | *.bb | *.bbg | *.map | *.inf | *.dSYM | *.o | *.obj ) ;; * ) ac_rmfiles="$ac_rmfiles $ac_file";; esac done rm -f $ac_rmfiles if { { ac_try="$ac_link_default" case "(($ac_try" in *\"* | *\`* | *\\*) ac_try_echo=\$ac_try;; *) ac_try_echo=$ac_try;; esac eval ac_try_echo="\"\$as_me:${as_lineno-$LINENO}: $ac_try_echo\"" $as_echo "$ac_try_echo"; } >&5 (eval "$ac_link_default") 2>&5 ac_status=$? $as_echo "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 test $ac_status = 0; }; then : # Autoconf-2.13 could set the ac_cv_exeext variable to `no'. # So ignore a value of `no', otherwise this would lead to `EXEEXT = no' # in a Makefile. We should not override ac_cv_exeext if it was cached, # so that the user can short-circuit this test for compilers unknown to # Autoconf. for ac_file in $ac_files '' do test -f "$ac_file" || continue case $ac_file in *.$ac_ext | *.xcoff | *.tds | *.d | *.pdb | *.xSYM | *.bb | *.bbg | *.map | *.inf | *.dSYM | *.o | *.obj ) ;; [ab].out ) # We found the default executable, but exeext='' is most # certainly right. break;; *.* ) if test "${ac_cv_exeext+set}" = set && test "$ac_cv_exeext" != no; then :; else ac_cv_exeext=`expr "$ac_file" : '[^.]*\(\..*\)'` fi # We set ac_cv_exeext here because the later test for it is not # safe: cross compilers may not add the suffix if given an `-o' # argument, so we may need to know it at that point already. # Even if this section looks crufty: it has the advantage of # actually working. break;; * ) break;; esac done test "$ac_cv_exeext" = no && ac_cv_exeext= else ac_file='' fi if test -z "$ac_file"; then : { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 $as_echo "no" >&6; } $as_echo "$as_me: failed program was:" >&5 sed 's/^/| /' conftest.$ac_ext >&5 { { $as_echo "$as_me:${as_lineno-$LINENO}: error: in \`$ac_pwd':" >&5 $as_echo "$as_me: error: in \`$ac_pwd':" >&2;} as_fn_error 77 "C compiler cannot create executables See \`config.log' for more details" "$LINENO" 5; } else { $as_echo "$as_me:${as_lineno-$LINENO}: result: yes" >&5 $as_echo "yes" >&6; } fi { $as_echo "$as_me:${as_lineno-$LINENO}: checking for C compiler default output file name" >&5 $as_echo_n "checking for C compiler default output file name... " >&6; } { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_file" >&5 $as_echo "$ac_file" >&6; } ac_exeext=$ac_cv_exeext rm -f -r a.out a.out.dSYM a.exe conftest$ac_cv_exeext b.out ac_clean_files=$ac_clean_files_save { $as_echo "$as_me:${as_lineno-$LINENO}: checking for suffix of executables" >&5 $as_echo_n "checking for suffix of executables... " >&6; } if { { ac_try="$ac_link" case "(($ac_try" in *\"* | *\`* | *\\*) ac_try_echo=\$ac_try;; *) ac_try_echo=$ac_try;; esac eval ac_try_echo="\"\$as_me:${as_lineno-$LINENO}: $ac_try_echo\"" $as_echo "$ac_try_echo"; } >&5 (eval "$ac_link") 2>&5 ac_status=$? $as_echo "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 test $ac_status = 0; }; then : # If both `conftest.exe' and `conftest' are `present' (well, observable) # catch `conftest.exe'. For instance with Cygwin, `ls conftest' will # work properly (i.e., refer to `conftest.exe'), while it won't with # `rm'. for ac_file in conftest.exe conftest conftest.*; do test -f "$ac_file" || continue case $ac_file in *.$ac_ext | *.xcoff | *.tds | *.d | *.pdb | *.xSYM | *.bb | *.bbg | *.map | *.inf | *.dSYM | *.o | *.obj ) ;; *.* ) ac_cv_exeext=`expr "$ac_file" : '[^.]*\(\..*\)'` break;; * ) break;; esac done else { { $as_echo "$as_me:${as_lineno-$LINENO}: error: in \`$ac_pwd':" >&5 $as_echo "$as_me: error: in \`$ac_pwd':" >&2;} as_fn_error $? "cannot compute suffix of executables: cannot compile and link See \`config.log' for more details" "$LINENO" 5; } fi rm -f conftest conftest$ac_cv_exeext { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_exeext" >&5 $as_echo "$ac_cv_exeext" >&6; } rm -f conftest.$ac_ext EXEEXT=$ac_cv_exeext ac_exeext=$EXEEXT cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ #include int main () { FILE *f = fopen ("conftest.out", "w"); return ferror (f) || fclose (f) != 0; ; return 0; } _ACEOF ac_clean_files="$ac_clean_files conftest.out" # Check that the compiler produces executables we can run. If not, either # the compiler is broken, or we cross compile. { $as_echo "$as_me:${as_lineno-$LINENO}: checking whether we are cross compiling" >&5 $as_echo_n "checking whether we are cross compiling... " >&6; } if test "$cross_compiling" != yes; then { { ac_try="$ac_link" case "(($ac_try" in *\"* | *\`* | *\\*) ac_try_echo=\$ac_try;; *) ac_try_echo=$ac_try;; esac eval ac_try_echo="\"\$as_me:${as_lineno-$LINENO}: $ac_try_echo\"" $as_echo "$ac_try_echo"; } >&5 (eval "$ac_link") 2>&5 ac_status=$? $as_echo "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 test $ac_status = 0; } if { ac_try='./conftest$ac_cv_exeext' { { case "(($ac_try" in *\"* | *\`* | *\\*) ac_try_echo=\$ac_try;; *) ac_try_echo=$ac_try;; esac eval ac_try_echo="\"\$as_me:${as_lineno-$LINENO}: $ac_try_echo\"" $as_echo "$ac_try_echo"; } >&5 (eval "$ac_try") 2>&5 ac_status=$? $as_echo "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 test $ac_status = 0; }; }; then cross_compiling=no else if test "$cross_compiling" = maybe; then cross_compiling=yes else { { $as_echo "$as_me:${as_lineno-$LINENO}: error: in \`$ac_pwd':" >&5 $as_echo "$as_me: error: in \`$ac_pwd':" >&2;} as_fn_error $? "cannot run C compiled programs. If you meant to cross compile, use \`--host'. See \`config.log' for more details" "$LINENO" 5; } fi fi fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $cross_compiling" >&5 $as_echo "$cross_compiling" >&6; } rm -f conftest.$ac_ext conftest$ac_cv_exeext conftest.out ac_clean_files=$ac_clean_files_save { $as_echo "$as_me:${as_lineno-$LINENO}: checking for suffix of object files" >&5 $as_echo_n "checking for suffix of object files... " >&6; } if ${ac_cv_objext+:} false; then : $as_echo_n "(cached) " >&6 else cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ int main () { ; return 0; } _ACEOF rm -f conftest.o conftest.obj if { { ac_try="$ac_compile" case "(($ac_try" in *\"* | *\`* | *\\*) ac_try_echo=\$ac_try;; *) ac_try_echo=$ac_try;; esac eval ac_try_echo="\"\$as_me:${as_lineno-$LINENO}: $ac_try_echo\"" $as_echo "$ac_try_echo"; } >&5 (eval "$ac_compile") 2>&5 ac_status=$? $as_echo "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 test $ac_status = 0; }; then : for ac_file in conftest.o conftest.obj conftest.*; do test -f "$ac_file" || continue; case $ac_file in *.$ac_ext | *.xcoff | *.tds | *.d | *.pdb | *.xSYM | *.bb | *.bbg | *.map | *.inf | *.dSYM ) ;; *) ac_cv_objext=`expr "$ac_file" : '.*\.\(.*\)'` break;; esac done else $as_echo "$as_me: failed program was:" >&5 sed 's/^/| /' conftest.$ac_ext >&5 { { $as_echo "$as_me:${as_lineno-$LINENO}: error: in \`$ac_pwd':" >&5 $as_echo "$as_me: error: in \`$ac_pwd':" >&2;} as_fn_error $? "cannot compute suffix of object files: cannot compile See \`config.log' for more details" "$LINENO" 5; } fi rm -f conftest.$ac_cv_objext conftest.$ac_ext fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_objext" >&5 $as_echo "$ac_cv_objext" >&6; } OBJEXT=$ac_cv_objext ac_objext=$OBJEXT { $as_echo "$as_me:${as_lineno-$LINENO}: checking whether we are using the GNU C compiler" >&5 $as_echo_n "checking whether we are using the GNU C compiler... " >&6; } if ${ac_cv_c_compiler_gnu+:} false; then : $as_echo_n "(cached) " >&6 else cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ int main () { #ifndef __GNUC__ choke me #endif ; return 0; } _ACEOF if ac_fn_c_try_compile "$LINENO"; then : ac_compiler_gnu=yes else ac_compiler_gnu=no fi rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext ac_cv_c_compiler_gnu=$ac_compiler_gnu fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_c_compiler_gnu" >&5 $as_echo "$ac_cv_c_compiler_gnu" >&6; } if test $ac_compiler_gnu = yes; then GCC=yes else GCC= fi ac_test_CFLAGS=${CFLAGS+set} ac_save_CFLAGS=$CFLAGS { $as_echo "$as_me:${as_lineno-$LINENO}: checking whether $CC accepts -g" >&5 $as_echo_n "checking whether $CC accepts -g... " >&6; } if ${ac_cv_prog_cc_g+:} false; then : $as_echo_n "(cached) " >&6 else ac_save_c_werror_flag=$ac_c_werror_flag ac_c_werror_flag=yes ac_cv_prog_cc_g=no CFLAGS="-g" cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ int main () { ; return 0; } _ACEOF if ac_fn_c_try_compile "$LINENO"; then : ac_cv_prog_cc_g=yes else CFLAGS="" cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ int main () { ; return 0; } _ACEOF if ac_fn_c_try_compile "$LINENO"; then : else ac_c_werror_flag=$ac_save_c_werror_flag CFLAGS="-g" cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ int main () { ; return 0; } _ACEOF if ac_fn_c_try_compile "$LINENO"; then : ac_cv_prog_cc_g=yes fi rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext fi rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext fi rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext ac_c_werror_flag=$ac_save_c_werror_flag fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_prog_cc_g" >&5 $as_echo "$ac_cv_prog_cc_g" >&6; } if test "$ac_test_CFLAGS" = set; then CFLAGS=$ac_save_CFLAGS elif test $ac_cv_prog_cc_g = yes; then if test "$GCC" = yes; then CFLAGS="-g -O2" else CFLAGS="-g" fi else if test "$GCC" = yes; then CFLAGS="-O2" else CFLAGS= fi fi { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $CC option to accept ISO C89" >&5 $as_echo_n "checking for $CC option to accept ISO C89... " >&6; } if ${ac_cv_prog_cc_c89+:} false; then : $as_echo_n "(cached) " >&6 else ac_cv_prog_cc_c89=no ac_save_CC=$CC cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ #include #include struct stat; /* Most of the following tests are stolen from RCS 5.7's src/conf.sh. */ struct buf { int x; }; FILE * (*rcsopen) (struct buf *, struct stat *, int); static char *e (p, i) char **p; int i; { return p[i]; } static char *f (char * (*g) (char **, int), char **p, ...) { char *s; va_list v; va_start (v,p); s = g (p, va_arg (v,int)); va_end (v); return s; } /* OSF 4.0 Compaq cc is some sort of almost-ANSI by default. It has function prototypes and stuff, but not '\xHH' hex character constants. These don't provoke an error unfortunately, instead are silently treated as 'x'. The following induces an error, until -std is added to get proper ANSI mode. Curiously '\x00'!='x' always comes out true, for an array size at least. It's necessary to write '\x00'==0 to get something that's true only with -std. */ int osf4_cc_array ['\x00' == 0 ? 1 : -1]; /* IBM C 6 for AIX is almost-ANSI by default, but it replaces macro parameters inside strings and character constants. */ #define FOO(x) 'x' int xlc6_cc_array[FOO(a) == 'x' ? 1 : -1]; int test (int i, double x); struct s1 {int (*f) (int a);}; struct s2 {int (*f) (double a);}; int pairnames (int, char **, FILE *(*)(struct buf *, struct stat *, int), int, int); int argc; char **argv; int main () { return f (e, argv, 0) != argv[0] || f (e, argv, 1) != argv[1]; ; return 0; } _ACEOF for ac_arg in '' -qlanglvl=extc89 -qlanglvl=ansi -std \ -Ae "-Aa -D_HPUX_SOURCE" "-Xc -D__EXTENSIONS__" do CC="$ac_save_CC $ac_arg" if ac_fn_c_try_compile "$LINENO"; then : ac_cv_prog_cc_c89=$ac_arg fi rm -f core conftest.err conftest.$ac_objext test "x$ac_cv_prog_cc_c89" != "xno" && break done rm -f conftest.$ac_ext CC=$ac_save_CC fi # AC_CACHE_VAL case "x$ac_cv_prog_cc_c89" in x) { $as_echo "$as_me:${as_lineno-$LINENO}: result: none needed" >&5 $as_echo "none needed" >&6; } ;; xno) { $as_echo "$as_me:${as_lineno-$LINENO}: result: unsupported" >&5 $as_echo "unsupported" >&6; } ;; *) CC="$CC $ac_cv_prog_cc_c89" { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_prog_cc_c89" >&5 $as_echo "$ac_cv_prog_cc_c89" >&6; } ;; esac if test "x$ac_cv_prog_cc_c89" != xno; then : fi ac_ext=c ac_cpp='$CPP $CPPFLAGS' ac_compile='$CC -c $CFLAGS $CPPFLAGS conftest.$ac_ext >&5' ac_link='$CC -o conftest$ac_exeext $CFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS >&5' ac_compiler_gnu=$ac_cv_c_compiler_gnu ac_ext=c ac_cpp='$CPP $CPPFLAGS' ac_compile='$CC -c $CFLAGS $CPPFLAGS conftest.$ac_ext >&5' ac_link='$CC -o conftest$ac_exeext $CFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS >&5' ac_compiler_gnu=$ac_cv_c_compiler_gnu { $as_echo "$as_me:${as_lineno-$LINENO}: checking whether $CC understands -c and -o together" >&5 $as_echo_n "checking whether $CC understands -c and -o together... " >&6; } if ${am_cv_prog_cc_c_o+:} false; then : $as_echo_n "(cached) " >&6 else cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ int main () { ; return 0; } _ACEOF # Make sure it works both with $CC and with simple cc. # Following AC_PROG_CC_C_O, we do the test twice because some # compilers refuse to overwrite an existing .o file with -o, # though they will create one. am_cv_prog_cc_c_o=yes for am_i in 1 2; do if { echo "$as_me:$LINENO: $CC -c conftest.$ac_ext -o conftest2.$ac_objext" >&5 ($CC -c conftest.$ac_ext -o conftest2.$ac_objext) >&5 2>&5 ac_status=$? echo "$as_me:$LINENO: \$? = $ac_status" >&5 (exit $ac_status); } \ && test -f conftest2.$ac_objext; then : OK else am_cv_prog_cc_c_o=no break fi done rm -f core conftest* unset am_i fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $am_cv_prog_cc_c_o" >&5 $as_echo "$am_cv_prog_cc_c_o" >&6; } if test "$am_cv_prog_cc_c_o" != yes; then # Losing compiler, so override with the script. # FIXME: It is wrong to rewrite CC. # But if we don't then we get into trouble of one sort or another. # A longer-term fix would be to have automake use am__CC in this case, # and then we could set am__CC="\$(top_srcdir)/compile \$(CC)" CC="$am_aux_dir/compile $CC" fi ac_ext=c ac_cpp='$CPP $CPPFLAGS' ac_compile='$CC -c $CFLAGS $CPPFLAGS conftest.$ac_ext >&5' ac_link='$CC -o conftest$ac_exeext $CFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS >&5' ac_compiler_gnu=$ac_cv_c_compiler_gnu DEPDIR="${am__leading_dot}deps" ac_config_commands="$ac_config_commands depfiles" am_make=${MAKE-make} cat > confinc << 'END' am__doit: @echo this is the am__doit target .PHONY: am__doit END # If we don't find an include directive, just comment out the code. { $as_echo "$as_me:${as_lineno-$LINENO}: checking for style of include used by $am_make" >&5 $as_echo_n "checking for style of include used by $am_make... " >&6; } am__include="#" am__quote= _am_result=none # First try GNU make style include. echo "include confinc" > confmf # Ignore all kinds of additional output from 'make'. case `$am_make -s -f confmf 2> /dev/null` in #( *the\ am__doit\ target*) am__include=include am__quote= _am_result=GNU ;; esac # Now try BSD make style include. if test "$am__include" = "#"; then echo '.include "confinc"' > confmf case `$am_make -s -f confmf 2> /dev/null` in #( *the\ am__doit\ target*) am__include=.include am__quote="\"" _am_result=BSD ;; esac fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $_am_result" >&5 $as_echo "$_am_result" >&6; } rm -f confinc confmf # Check whether --enable-dependency-tracking was given. if test "${enable_dependency_tracking+set}" = set; then : enableval=$enable_dependency_tracking; fi if test "x$enable_dependency_tracking" != xno; then am_depcomp="$ac_aux_dir/depcomp" AMDEPBACKSLASH='\' am__nodep='_no' fi if test "x$enable_dependency_tracking" != xno; then AMDEP_TRUE= AMDEP_FALSE='#' else AMDEP_TRUE='#' AMDEP_FALSE= fi depcc="$CC" am_compiler_list= { $as_echo "$as_me:${as_lineno-$LINENO}: checking dependency style of $depcc" >&5 $as_echo_n "checking dependency style of $depcc... " >&6; } if ${am_cv_CC_dependencies_compiler_type+:} false; then : $as_echo_n "(cached) " >&6 else if test -z "$AMDEP_TRUE" && test -f "$am_depcomp"; then # We make a subdir and do the tests there. Otherwise we can end up # making bogus files that we don't know about and never remove. For # instance it was reported that on HP-UX the gcc test will end up # making a dummy file named 'D' -- because '-MD' means "put the output # in D". rm -rf conftest.dir mkdir conftest.dir # Copy depcomp to subdir because otherwise we won't find it if we're # using a relative directory. cp "$am_depcomp" conftest.dir cd conftest.dir # We will build objects and dependencies in a subdirectory because # it helps to detect inapplicable dependency modes. For instance # both Tru64's cc and ICC support -MD to output dependencies as a # side effect of compilation, but ICC will put the dependencies in # the current directory while Tru64 will put them in the object # directory. mkdir sub am_cv_CC_dependencies_compiler_type=none if test "$am_compiler_list" = ""; then am_compiler_list=`sed -n 's/^#*\([a-zA-Z0-9]*\))$/\1/p' < ./depcomp` fi am__universal=false case " $depcc " in #( *\ -arch\ *\ -arch\ *) am__universal=true ;; esac for depmode in $am_compiler_list; do # Setup a source with many dependencies, because some compilers # like to wrap large dependency lists on column 80 (with \), and # we should not choose a depcomp mode which is confused by this. # # We need to recreate these files for each test, as the compiler may # overwrite some of them when testing with obscure command lines. # This happens at least with the AIX C compiler. : > sub/conftest.c for i in 1 2 3 4 5 6; do echo '#include "conftst'$i'.h"' >> sub/conftest.c # Using ": > sub/conftst$i.h" creates only sub/conftst1.h with # Solaris 10 /bin/sh. echo '/* dummy */' > sub/conftst$i.h done echo "${am__include} ${am__quote}sub/conftest.Po${am__quote}" > confmf # We check with '-c' and '-o' for the sake of the "dashmstdout" # mode. It turns out that the SunPro C++ compiler does not properly # handle '-M -o', and we need to detect this. Also, some Intel # versions had trouble with output in subdirs. am__obj=sub/conftest.${OBJEXT-o} am__minus_obj="-o $am__obj" case $depmode in gcc) # This depmode causes a compiler race in universal mode. test "$am__universal" = false || continue ;; nosideeffect) # After this tag, mechanisms are not by side-effect, so they'll # only be used when explicitly requested. if test "x$enable_dependency_tracking" = xyes; then continue else break fi ;; msvc7 | msvc7msys | msvisualcpp | msvcmsys) # This compiler won't grok '-c -o', but also, the minuso test has # not run yet. These depmodes are late enough in the game, and # so weak that their functioning should not be impacted. am__obj=conftest.${OBJEXT-o} am__minus_obj= ;; none) break ;; esac if depmode=$depmode \ source=sub/conftest.c object=$am__obj \ depfile=sub/conftest.Po tmpdepfile=sub/conftest.TPo \ $SHELL ./depcomp $depcc -c $am__minus_obj sub/conftest.c \ >/dev/null 2>conftest.err && grep sub/conftst1.h sub/conftest.Po > /dev/null 2>&1 && grep sub/conftst6.h sub/conftest.Po > /dev/null 2>&1 && grep $am__obj sub/conftest.Po > /dev/null 2>&1 && ${MAKE-make} -s -f confmf > /dev/null 2>&1; then # icc doesn't choke on unknown options, it will just issue warnings # or remarks (even with -Werror). So we grep stderr for any message # that says an option was ignored or not supported. # When given -MP, icc 7.0 and 7.1 complain thusly: # icc: Command line warning: ignoring option '-M'; no argument required # The diagnosis changed in icc 8.0: # icc: Command line remark: option '-MP' not supported if (grep 'ignoring option' conftest.err || grep 'not supported' conftest.err) >/dev/null 2>&1; then :; else am_cv_CC_dependencies_compiler_type=$depmode break fi fi done cd .. rm -rf conftest.dir else am_cv_CC_dependencies_compiler_type=none fi fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $am_cv_CC_dependencies_compiler_type" >&5 $as_echo "$am_cv_CC_dependencies_compiler_type" >&6; } CCDEPMODE=depmode=$am_cv_CC_dependencies_compiler_type if test "x$enable_dependency_tracking" != xno \ && test "$am_cv_CC_dependencies_compiler_type" = gcc3; then am__fastdepCC_TRUE= am__fastdepCC_FALSE='#' else am__fastdepCC_TRUE='#' am__fastdepCC_FALSE= fi { $as_echo "$as_me:${as_lineno-$LINENO}: checking whether ln -s works" >&5 $as_echo_n "checking whether ln -s works... " >&6; } LN_S=$as_ln_s if test "$LN_S" = "ln -s"; then { $as_echo "$as_me:${as_lineno-$LINENO}: result: yes" >&5 $as_echo "yes" >&6; } else { $as_echo "$as_me:${as_lineno-$LINENO}: result: no, using $LN_S" >&5 $as_echo "no, using $LN_S" >&6; } fi { $as_echo "$as_me:${as_lineno-$LINENO}: checking whether ${MAKE-make} sets \$(MAKE)" >&5 $as_echo_n "checking whether ${MAKE-make} sets \$(MAKE)... " >&6; } set x ${MAKE-make} ac_make=`$as_echo "$2" | sed 's/+/p/g; s/[^a-zA-Z0-9_]/_/g'` if eval \${ac_cv_prog_make_${ac_make}_set+:} false; then : $as_echo_n "(cached) " >&6 else cat >conftest.make <<\_ACEOF SHELL = /bin/sh all: @echo '@@@%%%=$(MAKE)=@@@%%%' _ACEOF # GNU make sometimes prints "make[1]: Entering ...", which would confuse us. case `${MAKE-make} -f conftest.make 2>/dev/null` in *@@@%%%=?*=@@@%%%*) eval ac_cv_prog_make_${ac_make}_set=yes;; *) eval ac_cv_prog_make_${ac_make}_set=no;; esac rm -f conftest.make fi if eval test \$ac_cv_prog_make_${ac_make}_set = yes; then { $as_echo "$as_me:${as_lineno-$LINENO}: result: yes" >&5 $as_echo "yes" >&6; } SET_MAKE= else { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 $as_echo "no" >&6; } SET_MAKE="MAKE=${MAKE-make}" fi ac_ext=c ac_cpp='$CPP $CPPFLAGS' ac_compile='$CC -c $CFLAGS $CPPFLAGS conftest.$ac_ext >&5' ac_link='$CC -o conftest$ac_exeext $CFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS >&5' ac_compiler_gnu=$ac_cv_c_compiler_gnu { $as_echo "$as_me:${as_lineno-$LINENO}: checking how to run the C preprocessor" >&5 $as_echo_n "checking how to run the C preprocessor... " >&6; } # On Suns, sometimes $CPP names a directory. if test -n "$CPP" && test -d "$CPP"; then CPP= fi if test -z "$CPP"; then if ${ac_cv_prog_CPP+:} false; then : $as_echo_n "(cached) " >&6 else # Double quotes because CPP needs to be expanded for CPP in "$CC -E" "$CC -E -traditional-cpp" "/lib/cpp" do ac_preproc_ok=false for ac_c_preproc_warn_flag in '' yes do # Use a header file that comes with gcc, so configuring glibc # with a fresh cross-compiler works. # Prefer to if __STDC__ is defined, since # exists even on freestanding compilers. # On the NeXT, cc -E runs the code through the compiler's parser, # not just through cpp. "Syntax error" is here to catch this case. cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ #ifdef __STDC__ # include #else # include #endif Syntax error _ACEOF if ac_fn_c_try_cpp "$LINENO"; then : else # Broken: fails on valid input. continue fi rm -f conftest.err conftest.i conftest.$ac_ext # OK, works on sane cases. Now check whether nonexistent headers # can be detected and how. cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ #include _ACEOF if ac_fn_c_try_cpp "$LINENO"; then : # Broken: success on invalid input. continue else # Passes both tests. ac_preproc_ok=: break fi rm -f conftest.err conftest.i conftest.$ac_ext done # Because of `break', _AC_PREPROC_IFELSE's cleaning code was skipped. rm -f conftest.i conftest.err conftest.$ac_ext if $ac_preproc_ok; then : break fi done ac_cv_prog_CPP=$CPP fi CPP=$ac_cv_prog_CPP else ac_cv_prog_CPP=$CPP fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $CPP" >&5 $as_echo "$CPP" >&6; } ac_preproc_ok=false for ac_c_preproc_warn_flag in '' yes do # Use a header file that comes with gcc, so configuring glibc # with a fresh cross-compiler works. # Prefer to if __STDC__ is defined, since # exists even on freestanding compilers. # On the NeXT, cc -E runs the code through the compiler's parser, # not just through cpp. "Syntax error" is here to catch this case. cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ #ifdef __STDC__ # include #else # include #endif Syntax error _ACEOF if ac_fn_c_try_cpp "$LINENO"; then : else # Broken: fails on valid input. continue fi rm -f conftest.err conftest.i conftest.$ac_ext # OK, works on sane cases. Now check whether nonexistent headers # can be detected and how. cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ #include _ACEOF if ac_fn_c_try_cpp "$LINENO"; then : # Broken: success on invalid input. continue else # Passes both tests. ac_preproc_ok=: break fi rm -f conftest.err conftest.i conftest.$ac_ext done # Because of `break', _AC_PREPROC_IFELSE's cleaning code was skipped. rm -f conftest.i conftest.err conftest.$ac_ext if $ac_preproc_ok; then : else { { $as_echo "$as_me:${as_lineno-$LINENO}: error: in \`$ac_pwd':" >&5 $as_echo "$as_me: error: in \`$ac_pwd':" >&2;} as_fn_error $? "C preprocessor \"$CPP\" fails sanity check See \`config.log' for more details" "$LINENO" 5; } fi ac_ext=c ac_cpp='$CPP $CPPFLAGS' ac_compile='$CC -c $CFLAGS $CPPFLAGS conftest.$ac_ext >&5' ac_link='$CC -o conftest$ac_exeext $CFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS >&5' ac_compiler_gnu=$ac_cv_c_compiler_gnu { $as_echo "$as_me:${as_lineno-$LINENO}: checking for grep that handles long lines and -e" >&5 $as_echo_n "checking for grep that handles long lines and -e... " >&6; } if ${ac_cv_path_GREP+:} false; then : $as_echo_n "(cached) " >&6 else if test -z "$GREP"; then ac_path_GREP_found=false # Loop through the user's path and test for each of PROGNAME-LIST as_save_IFS=$IFS; IFS=$PATH_SEPARATOR for as_dir in $PATH$PATH_SEPARATOR/usr/xpg4/bin do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_prog in grep ggrep; do for ac_exec_ext in '' $ac_executable_extensions; do ac_path_GREP="$as_dir/$ac_prog$ac_exec_ext" as_fn_executable_p "$ac_path_GREP" || continue # Check for GNU ac_path_GREP and select it if it is found. # Check for GNU $ac_path_GREP case `"$ac_path_GREP" --version 2>&1` in *GNU*) ac_cv_path_GREP="$ac_path_GREP" ac_path_GREP_found=:;; *) ac_count=0 $as_echo_n 0123456789 >"conftest.in" while : do cat "conftest.in" "conftest.in" >"conftest.tmp" mv "conftest.tmp" "conftest.in" cp "conftest.in" "conftest.nl" $as_echo 'GREP' >> "conftest.nl" "$ac_path_GREP" -e 'GREP$' -e '-(cannot match)-' < "conftest.nl" >"conftest.out" 2>/dev/null || break diff "conftest.out" "conftest.nl" >/dev/null 2>&1 || break as_fn_arith $ac_count + 1 && ac_count=$as_val if test $ac_count -gt ${ac_path_GREP_max-0}; then # Best one so far, save it but keep looking for a better one ac_cv_path_GREP="$ac_path_GREP" ac_path_GREP_max=$ac_count fi # 10*(2^10) chars as input seems more than enough test $ac_count -gt 10 && break done rm -f conftest.in conftest.tmp conftest.nl conftest.out;; esac $ac_path_GREP_found && break 3 done done done IFS=$as_save_IFS if test -z "$ac_cv_path_GREP"; then as_fn_error $? "no acceptable grep could be found in $PATH$PATH_SEPARATOR/usr/xpg4/bin" "$LINENO" 5 fi else ac_cv_path_GREP=$GREP fi fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_path_GREP" >&5 $as_echo "$ac_cv_path_GREP" >&6; } GREP="$ac_cv_path_GREP" { $as_echo "$as_me:${as_lineno-$LINENO}: checking for egrep" >&5 $as_echo_n "checking for egrep... " >&6; } if ${ac_cv_path_EGREP+:} false; then : $as_echo_n "(cached) " >&6 else if echo a | $GREP -E '(a|b)' >/dev/null 2>&1 then ac_cv_path_EGREP="$GREP -E" else if test -z "$EGREP"; then ac_path_EGREP_found=false # Loop through the user's path and test for each of PROGNAME-LIST as_save_IFS=$IFS; IFS=$PATH_SEPARATOR for as_dir in $PATH$PATH_SEPARATOR/usr/xpg4/bin do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_prog in egrep; do for ac_exec_ext in '' $ac_executable_extensions; do ac_path_EGREP="$as_dir/$ac_prog$ac_exec_ext" as_fn_executable_p "$ac_path_EGREP" || continue # Check for GNU ac_path_EGREP and select it if it is found. # Check for GNU $ac_path_EGREP case `"$ac_path_EGREP" --version 2>&1` in *GNU*) ac_cv_path_EGREP="$ac_path_EGREP" ac_path_EGREP_found=:;; *) ac_count=0 $as_echo_n 0123456789 >"conftest.in" while : do cat "conftest.in" "conftest.in" >"conftest.tmp" mv "conftest.tmp" "conftest.in" cp "conftest.in" "conftest.nl" $as_echo 'EGREP' >> "conftest.nl" "$ac_path_EGREP" 'EGREP$' < "conftest.nl" >"conftest.out" 2>/dev/null || break diff "conftest.out" "conftest.nl" >/dev/null 2>&1 || break as_fn_arith $ac_count + 1 && ac_count=$as_val if test $ac_count -gt ${ac_path_EGREP_max-0}; then # Best one so far, save it but keep looking for a better one ac_cv_path_EGREP="$ac_path_EGREP" ac_path_EGREP_max=$ac_count fi # 10*(2^10) chars as input seems more than enough test $ac_count -gt 10 && break done rm -f conftest.in conftest.tmp conftest.nl conftest.out;; esac $ac_path_EGREP_found && break 3 done done done IFS=$as_save_IFS if test -z "$ac_cv_path_EGREP"; then as_fn_error $? "no acceptable egrep could be found in $PATH$PATH_SEPARATOR/usr/xpg4/bin" "$LINENO" 5 fi else ac_cv_path_EGREP=$EGREP fi fi fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_path_EGREP" >&5 $as_echo "$ac_cv_path_EGREP" >&6; } EGREP="$ac_cv_path_EGREP" { $as_echo "$as_me:${as_lineno-$LINENO}: checking for ANSI C header files" >&5 $as_echo_n "checking for ANSI C header files... " >&6; } if ${ac_cv_header_stdc+:} false; then : $as_echo_n "(cached) " >&6 else cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ #include #include #include #include int main () { ; return 0; } _ACEOF if ac_fn_c_try_compile "$LINENO"; then : ac_cv_header_stdc=yes else ac_cv_header_stdc=no fi rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext if test $ac_cv_header_stdc = yes; then # SunOS 4.x string.h does not declare mem*, contrary to ANSI. cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ #include _ACEOF if (eval "$ac_cpp conftest.$ac_ext") 2>&5 | $EGREP "memchr" >/dev/null 2>&1; then : else ac_cv_header_stdc=no fi rm -f conftest* fi if test $ac_cv_header_stdc = yes; then # ISC 2.0.2 stdlib.h does not declare free, contrary to ANSI. cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ #include _ACEOF if (eval "$ac_cpp conftest.$ac_ext") 2>&5 | $EGREP "free" >/dev/null 2>&1; then : else ac_cv_header_stdc=no fi rm -f conftest* fi if test $ac_cv_header_stdc = yes; then # /bin/cc in Irix-4.0.5 gets non-ANSI ctype macros unless using -ansi. if test "$cross_compiling" = yes; then : : else cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ #include #include #if ((' ' & 0x0FF) == 0x020) # define ISLOWER(c) ('a' <= (c) && (c) <= 'z') # define TOUPPER(c) (ISLOWER(c) ? 'A' + ((c) - 'a') : (c)) #else # define ISLOWER(c) \ (('a' <= (c) && (c) <= 'i') \ || ('j' <= (c) && (c) <= 'r') \ || ('s' <= (c) && (c) <= 'z')) # define TOUPPER(c) (ISLOWER(c) ? ((c) | 0x40) : (c)) #endif #define XOR(e, f) (((e) && !(f)) || (!(e) && (f))) int main () { int i; for (i = 0; i < 256; i++) if (XOR (islower (i), ISLOWER (i)) || toupper (i) != TOUPPER (i)) return 2; return 0; } _ACEOF if ac_fn_c_try_run "$LINENO"; then : else ac_cv_header_stdc=no fi rm -f core *.core core.conftest.* gmon.out bb.out conftest$ac_exeext \ conftest.$ac_objext conftest.beam conftest.$ac_ext fi fi fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_header_stdc" >&5 $as_echo "$ac_cv_header_stdc" >&6; } if test $ac_cv_header_stdc = yes; then $as_echo "#define STDC_HEADERS 1" >>confdefs.h fi # On IRIX 5.3, sys/types and inttypes.h are conflicting. for ac_header in sys/types.h sys/stat.h stdlib.h string.h memory.h strings.h \ inttypes.h stdint.h unistd.h do : as_ac_Header=`$as_echo "ac_cv_header_$ac_header" | $as_tr_sh` ac_fn_c_check_header_compile "$LINENO" "$ac_header" "$as_ac_Header" "$ac_includes_default " if eval test \"x\$"$as_ac_Header"\" = x"yes"; then : cat >>confdefs.h <<_ACEOF #define `$as_echo "HAVE_$ac_header" | $as_tr_cpp` 1 _ACEOF fi done ac_fn_c_check_header_mongrel "$LINENO" "minix/config.h" "ac_cv_header_minix_config_h" "$ac_includes_default" if test "x$ac_cv_header_minix_config_h" = xyes; then : MINIX=yes else MINIX= fi if test "$MINIX" = yes; then $as_echo "#define _POSIX_SOURCE 1" >>confdefs.h $as_echo "#define _POSIX_1_SOURCE 2" >>confdefs.h $as_echo "#define _MINIX 1" >>confdefs.h fi { $as_echo "$as_me:${as_lineno-$LINENO}: checking whether it is safe to define __EXTENSIONS__" >&5 $as_echo_n "checking whether it is safe to define __EXTENSIONS__... " >&6; } if ${ac_cv_safe_to_define___extensions__+:} false; then : $as_echo_n "(cached) " >&6 else cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ # define __EXTENSIONS__ 1 $ac_includes_default int main () { ; return 0; } _ACEOF if ac_fn_c_try_compile "$LINENO"; then : ac_cv_safe_to_define___extensions__=yes else ac_cv_safe_to_define___extensions__=no fi rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_safe_to_define___extensions__" >&5 $as_echo "$ac_cv_safe_to_define___extensions__" >&6; } test $ac_cv_safe_to_define___extensions__ = yes && $as_echo "#define __EXTENSIONS__ 1" >>confdefs.h $as_echo "#define _ALL_SOURCE 1" >>confdefs.h $as_echo "#define _GNU_SOURCE 1" >>confdefs.h $as_echo "#define _POSIX_PTHREAD_SEMANTICS 1" >>confdefs.h $as_echo "#define _TANDEM_SOURCE 1" >>confdefs.h { $as_echo "$as_me:${as_lineno-$LINENO}: checking for library containing strerror" >&5 $as_echo_n "checking for library containing strerror... " >&6; } if ${ac_cv_search_strerror+:} false; then : $as_echo_n "(cached) " >&6 else ac_func_search_save_LIBS=$LIBS cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ /* Override any GCC internal prototype to avoid an error. Use char because int might match the return type of a GCC builtin and then its argument prototype would still apply. */ #ifdef __cplusplus extern "C" #endif char strerror (); int main () { return strerror (); ; return 0; } _ACEOF for ac_lib in '' cposix; do if test -z "$ac_lib"; then ac_res="none required" else ac_res=-l$ac_lib LIBS="-l$ac_lib $ac_func_search_save_LIBS" fi if ac_fn_c_try_link "$LINENO"; then : ac_cv_search_strerror=$ac_res fi rm -f core conftest.err conftest.$ac_objext \ conftest$ac_exeext if ${ac_cv_search_strerror+:} false; then : break fi done if ${ac_cv_search_strerror+:} false; then : else ac_cv_search_strerror=no fi rm conftest.$ac_ext LIBS=$ac_func_search_save_LIBS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_search_strerror" >&5 $as_echo "$ac_cv_search_strerror" >&6; } ac_res=$ac_cv_search_strerror if test "$ac_res" != no; then : test "$ac_res" = "none required" || LIBS="$ac_res $LIBS" fi for ac_prog in gawk mawk nawk awk do # Extract the first word of "$ac_prog", so it can be a program name with args. set dummy $ac_prog; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } if ${ac_cv_prog_AWK+:} false; then : $as_echo_n "(cached) " >&6 else if test -n "$AWK"; then ac_cv_prog_AWK="$AWK" # Let the user override the test. else as_save_IFS=$IFS; IFS=$PATH_SEPARATOR for as_dir in $PATH do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_prog_AWK="$ac_prog" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 fi done done IFS=$as_save_IFS fi fi AWK=$ac_cv_prog_AWK if test -n "$AWK"; then { $as_echo "$as_me:${as_lineno-$LINENO}: result: $AWK" >&5 $as_echo "$AWK" >&6; } else { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 $as_echo "no" >&6; } fi test -n "$AWK" && break done { $as_echo "$as_me:${as_lineno-$LINENO}: checking for an ANSI C-conforming const" >&5 $as_echo_n "checking for an ANSI C-conforming const... " >&6; } if ${ac_cv_c_const+:} false; then : $as_echo_n "(cached) " >&6 else cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ int main () { #ifndef __cplusplus /* Ultrix mips cc rejects this sort of thing. */ typedef int charset[2]; const charset cs = { 0, 0 }; /* SunOS 4.1.1 cc rejects this. */ char const *const *pcpcc; char **ppc; /* NEC SVR4.0.2 mips cc rejects this. */ struct point {int x, y;}; static struct point const zero = {0,0}; /* AIX XL C 1.02.0.0 rejects this. It does not let you subtract one const X* pointer from another in an arm of an if-expression whose if-part is not a constant expression */ const char *g = "string"; pcpcc = &g + (g ? g-g : 0); /* HPUX 7.0 cc rejects these. */ ++pcpcc; ppc = (char**) pcpcc; pcpcc = (char const *const *) ppc; { /* SCO 3.2v4 cc rejects this sort of thing. */ char tx; char *t = &tx; char const *s = 0 ? (char *) 0 : (char const *) 0; *t++ = 0; if (s) return 0; } { /* Someone thinks the Sun supposedly-ANSI compiler will reject this. */ int x[] = {25, 17}; const int *foo = &x[0]; ++foo; } { /* Sun SC1.0 ANSI compiler rejects this -- but not the above. */ typedef const int *iptr; iptr p = 0; ++p; } { /* AIX XL C 1.02.0.0 rejects this sort of thing, saying "k.c", line 2.27: 1506-025 (S) Operand must be a modifiable lvalue. */ struct s { int j; const int *ap[3]; } bx; struct s *b = &bx; b->j = 5; } { /* ULTRIX-32 V3.1 (Rev 9) vcc rejects this */ const int foo = 10; if (!foo) return 0; } return !cs[0] && !zero.x; #endif ; return 0; } _ACEOF if ac_fn_c_try_compile "$LINENO"; then : ac_cv_c_const=yes else ac_cv_c_const=no fi rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_c_const" >&5 $as_echo "$ac_cv_c_const" >&6; } if test $ac_cv_c_const = no; then $as_echo "#define const /**/" >>confdefs.h fi { $as_echo "$as_me:${as_lineno-$LINENO}: checking for long file names" >&5 $as_echo_n "checking for long file names... " >&6; } if ${ac_cv_sys_long_file_names+:} false; then : $as_echo_n "(cached) " >&6 else ac_cv_sys_long_file_names=yes # Test for long file names in all the places we know might matter: # . the current directory, where building will happen # $prefix/lib where we will be installing things # $exec_prefix/lib likewise # $TMPDIR if set, where it might want to write temporary files # /tmp where it might want to write temporary files # /var/tmp likewise # /usr/tmp likewise for ac_dir in . "$TMPDIR" /tmp /var/tmp /usr/tmp "$prefix/lib" "$exec_prefix/lib"; do # Skip $TMPDIR if it is empty or bogus, and skip $exec_prefix/lib # in the usual case where exec_prefix is '${prefix}'. case $ac_dir in #( . | /* | ?:[\\/]*) ;; #( *) continue;; esac test -w "$ac_dir/." || continue # It is less confusing to not echo anything here. ac_xdir=$ac_dir/cf$$ (umask 077 && mkdir "$ac_xdir" 2>/dev/null) || continue ac_tf1=$ac_xdir/conftest9012345 ac_tf2=$ac_xdir/conftest9012346 touch "$ac_tf1" 2>/dev/null && test -f "$ac_tf1" && test ! -f "$ac_tf2" || ac_cv_sys_long_file_names=no rm -f -r "$ac_xdir" 2>/dev/null test $ac_cv_sys_long_file_names = no && break done fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_sys_long_file_names" >&5 $as_echo "$ac_cv_sys_long_file_names" >&6; } if test $ac_cv_sys_long_file_names = yes; then $as_echo "#define HAVE_LONG_FILE_NAMES 1" >>confdefs.h fi if test $ac_cv_sys_long_file_names = no; then as_fn_error $? "The Cyrus IMAPD requires support for long file names" "$LINENO" 5 fi { $as_echo "$as_me:${as_lineno-$LINENO}: checking for inline" >&5 $as_echo_n "checking for inline... " >&6; } if ${ac_cv_c_inline+:} false; then : $as_echo_n "(cached) " >&6 else ac_cv_c_inline=no for ac_kw in inline __inline__ __inline; do cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ #ifndef __cplusplus typedef int foo_t; static $ac_kw foo_t static_foo () {return 0; } $ac_kw foo_t foo () {return 0; } #endif _ACEOF if ac_fn_c_try_compile "$LINENO"; then : ac_cv_c_inline=$ac_kw fi rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext test "$ac_cv_c_inline" != no && break done fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_c_inline" >&5 $as_echo "$ac_cv_c_inline" >&6; } case $ac_cv_c_inline in inline | yes) ;; *) case $ac_cv_c_inline in no) ac_val=;; *) ac_val=$ac_cv_c_inline;; esac cat >>confdefs.h <<_ACEOF #ifndef __cplusplus #define inline $ac_val #endif _ACEOF ;; esac CFLAG_VISIBILITY= HAVE_VISIBILITY=0 if test -n "$GCC"; then { $as_echo "$as_me:${as_lineno-$LINENO}: checking whether the -Werror option is usable" >&5 $as_echo_n "checking whether the -Werror option is usable... " >&6; } if ${gl_cv_cc_vis_werror+:} false; then : $as_echo_n "(cached) " >&6 else gl_save_CFLAGS="$CFLAGS" CFLAGS="$CFLAGS -Werror" cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ int main () { ; return 0; } _ACEOF if ac_fn_c_try_compile "$LINENO"; then : gl_cv_cc_vis_werror=yes else gl_cv_cc_vis_werror=no fi rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext CFLAGS="$gl_save_CFLAGS" fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $gl_cv_cc_vis_werror" >&5 $as_echo "$gl_cv_cc_vis_werror" >&6; } { $as_echo "$as_me:${as_lineno-$LINENO}: checking for simple visibility declarations" >&5 $as_echo_n "checking for simple visibility declarations... " >&6; } if ${gl_cv_cc_visibility+:} false; then : $as_echo_n "(cached) " >&6 else gl_save_CFLAGS="$CFLAGS" CFLAGS="$CFLAGS -fvisibility=hidden" if test $gl_cv_cc_vis_werror = yes; then CFLAGS="$CFLAGS -Werror" fi cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ extern __attribute__((__visibility__("hidden"))) int hiddenvar; extern __attribute__((__visibility__("default"))) int exportedvar; extern __attribute__((__visibility__("hidden"))) int hiddenfunc (void); extern __attribute__((__visibility__("default"))) int exportedfunc (void); void dummyfunc (void) {} int main () { ; return 0; } _ACEOF if ac_fn_c_try_compile "$LINENO"; then : gl_cv_cc_visibility=yes else gl_cv_cc_visibility=no fi rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext CFLAGS="$gl_save_CFLAGS" fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $gl_cv_cc_visibility" >&5 $as_echo "$gl_cv_cc_visibility" >&6; } if test $gl_cv_cc_visibility = yes; then CFLAG_VISIBILITY="-fvisibility=hidden" HAVE_VISIBILITY=1 fi fi cat >>confdefs.h <<_ACEOF #define HAVE_VISIBILITY $HAVE_VISIBILITY _ACEOF case `pwd` in *\ * | *\ *) { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: Libtool does not cope well with whitespace in \`pwd\`" >&5 $as_echo "$as_me: WARNING: Libtool does not cope well with whitespace in \`pwd\`" >&2;} ;; esac macro_version='2.4.6' macro_revision='2.4.6' ltmain=$ac_aux_dir/ltmain.sh # Backslashify metacharacters that are still active within # double-quoted strings. sed_quote_subst='s/\(["`$\\]\)/\\\1/g' # Same as above, but do not quote variable references. double_quote_subst='s/\(["`\\]\)/\\\1/g' # Sed substitution to delay expansion of an escaped shell variable in a # double_quote_subst'ed string. delay_variable_subst='s/\\\\\\\\\\\$/\\\\\\$/g' # Sed substitution to delay expansion of an escaped single quote. delay_single_quote_subst='s/'\''/'\'\\\\\\\'\''/g' # Sed substitution to avoid accidental globbing in evaled expressions no_glob_subst='s/\*/\\\*/g' ECHO='\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\' ECHO=$ECHO$ECHO$ECHO$ECHO$ECHO ECHO=$ECHO$ECHO$ECHO$ECHO$ECHO$ECHO { $as_echo "$as_me:${as_lineno-$LINENO}: checking how to print strings" >&5 $as_echo_n "checking how to print strings... " >&6; } # Test print first, because it will be a builtin if present. if test "X`( print -r -- -n ) 2>/dev/null`" = X-n && \ test "X`print -r -- $ECHO 2>/dev/null`" = "X$ECHO"; then ECHO='print -r --' elif test "X`printf %s $ECHO 2>/dev/null`" = "X$ECHO"; then ECHO='printf %s\n' else # Use this function as a fallback that always works. func_fallback_echo () { eval 'cat <<_LTECHO_EOF $1 _LTECHO_EOF' } ECHO='func_fallback_echo' fi # func_echo_all arg... # Invoke $ECHO with all args, space-separated. func_echo_all () { $ECHO "" } case $ECHO in printf*) { $as_echo "$as_me:${as_lineno-$LINENO}: result: printf" >&5 $as_echo "printf" >&6; } ;; print*) { $as_echo "$as_me:${as_lineno-$LINENO}: result: print -r" >&5 $as_echo "print -r" >&6; } ;; *) { $as_echo "$as_me:${as_lineno-$LINENO}: result: cat" >&5 $as_echo "cat" >&6; } ;; esac { $as_echo "$as_me:${as_lineno-$LINENO}: checking for a sed that does not truncate output" >&5 $as_echo_n "checking for a sed that does not truncate output... " >&6; } if ${ac_cv_path_SED+:} false; then : $as_echo_n "(cached) " >&6 else ac_script=s/aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa/bbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbb/ for ac_i in 1 2 3 4 5 6 7; do ac_script="$ac_script$as_nl$ac_script" done echo "$ac_script" 2>/dev/null | sed 99q >conftest.sed { ac_script=; unset ac_script;} if test -z "$SED"; then ac_path_SED_found=false # Loop through the user's path and test for each of PROGNAME-LIST as_save_IFS=$IFS; IFS=$PATH_SEPARATOR for as_dir in $PATH do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_prog in sed gsed; do for ac_exec_ext in '' $ac_executable_extensions; do ac_path_SED="$as_dir/$ac_prog$ac_exec_ext" as_fn_executable_p "$ac_path_SED" || continue # Check for GNU ac_path_SED and select it if it is found. # Check for GNU $ac_path_SED case `"$ac_path_SED" --version 2>&1` in *GNU*) ac_cv_path_SED="$ac_path_SED" ac_path_SED_found=:;; *) ac_count=0 $as_echo_n 0123456789 >"conftest.in" while : do cat "conftest.in" "conftest.in" >"conftest.tmp" mv "conftest.tmp" "conftest.in" cp "conftest.in" "conftest.nl" $as_echo '' >> "conftest.nl" "$ac_path_SED" -f conftest.sed < "conftest.nl" >"conftest.out" 2>/dev/null || break diff "conftest.out" "conftest.nl" >/dev/null 2>&1 || break as_fn_arith $ac_count + 1 && ac_count=$as_val if test $ac_count -gt ${ac_path_SED_max-0}; then # Best one so far, save it but keep looking for a better one ac_cv_path_SED="$ac_path_SED" ac_path_SED_max=$ac_count fi # 10*(2^10) chars as input seems more than enough test $ac_count -gt 10 && break done rm -f conftest.in conftest.tmp conftest.nl conftest.out;; esac $ac_path_SED_found && break 3 done done done IFS=$as_save_IFS if test -z "$ac_cv_path_SED"; then as_fn_error $? "no acceptable sed could be found in \$PATH" "$LINENO" 5 fi else ac_cv_path_SED=$SED fi fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_path_SED" >&5 $as_echo "$ac_cv_path_SED" >&6; } SED="$ac_cv_path_SED" rm -f conftest.sed test -z "$SED" && SED=sed Xsed="$SED -e 1s/^X//" { $as_echo "$as_me:${as_lineno-$LINENO}: checking for fgrep" >&5 $as_echo_n "checking for fgrep... " >&6; } if ${ac_cv_path_FGREP+:} false; then : $as_echo_n "(cached) " >&6 else if echo 'ab*c' | $GREP -F 'ab*c' >/dev/null 2>&1 then ac_cv_path_FGREP="$GREP -F" else if test -z "$FGREP"; then ac_path_FGREP_found=false # Loop through the user's path and test for each of PROGNAME-LIST as_save_IFS=$IFS; IFS=$PATH_SEPARATOR for as_dir in $PATH$PATH_SEPARATOR/usr/xpg4/bin do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_prog in fgrep; do for ac_exec_ext in '' $ac_executable_extensions; do ac_path_FGREP="$as_dir/$ac_prog$ac_exec_ext" as_fn_executable_p "$ac_path_FGREP" || continue # Check for GNU ac_path_FGREP and select it if it is found. # Check for GNU $ac_path_FGREP case `"$ac_path_FGREP" --version 2>&1` in *GNU*) ac_cv_path_FGREP="$ac_path_FGREP" ac_path_FGREP_found=:;; *) ac_count=0 $as_echo_n 0123456789 >"conftest.in" while : do cat "conftest.in" "conftest.in" >"conftest.tmp" mv "conftest.tmp" "conftest.in" cp "conftest.in" "conftest.nl" $as_echo 'FGREP' >> "conftest.nl" "$ac_path_FGREP" FGREP < "conftest.nl" >"conftest.out" 2>/dev/null || break diff "conftest.out" "conftest.nl" >/dev/null 2>&1 || break as_fn_arith $ac_count + 1 && ac_count=$as_val if test $ac_count -gt ${ac_path_FGREP_max-0}; then # Best one so far, save it but keep looking for a better one ac_cv_path_FGREP="$ac_path_FGREP" ac_path_FGREP_max=$ac_count fi # 10*(2^10) chars as input seems more than enough test $ac_count -gt 10 && break done rm -f conftest.in conftest.tmp conftest.nl conftest.out;; esac $ac_path_FGREP_found && break 3 done done done IFS=$as_save_IFS if test -z "$ac_cv_path_FGREP"; then as_fn_error $? "no acceptable fgrep could be found in $PATH$PATH_SEPARATOR/usr/xpg4/bin" "$LINENO" 5 fi else ac_cv_path_FGREP=$FGREP fi fi fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_path_FGREP" >&5 $as_echo "$ac_cv_path_FGREP" >&6; } FGREP="$ac_cv_path_FGREP" test -z "$GREP" && GREP=grep # Check whether --with-gnu-ld was given. if test "${with_gnu_ld+set}" = set; then : withval=$with_gnu_ld; test no = "$withval" || with_gnu_ld=yes else with_gnu_ld=no fi ac_prog=ld if test yes = "$GCC"; then # Check if gcc -print-prog-name=ld gives a path. { $as_echo "$as_me:${as_lineno-$LINENO}: checking for ld used by $CC" >&5 $as_echo_n "checking for ld used by $CC... " >&6; } case $host in *-*-mingw*) # gcc leaves a trailing carriage return, which upsets mingw ac_prog=`($CC -print-prog-name=ld) 2>&5 | tr -d '\015'` ;; *) ac_prog=`($CC -print-prog-name=ld) 2>&5` ;; esac case $ac_prog in # Accept absolute paths. [\\/]* | ?:[\\/]*) re_direlt='/[^/][^/]*/\.\./' # Canonicalize the pathname of ld ac_prog=`$ECHO "$ac_prog"| $SED 's%\\\\%/%g'` while $ECHO "$ac_prog" | $GREP "$re_direlt" > /dev/null 2>&1; do ac_prog=`$ECHO $ac_prog| $SED "s%$re_direlt%/%"` done test -z "$LD" && LD=$ac_prog ;; "") # If it fails, then pretend we aren't using GCC. ac_prog=ld ;; *) # If it is relative, then search for the first ld in PATH. with_gnu_ld=unknown ;; esac elif test yes = "$with_gnu_ld"; then { $as_echo "$as_me:${as_lineno-$LINENO}: checking for GNU ld" >&5 $as_echo_n "checking for GNU ld... " >&6; } else { $as_echo "$as_me:${as_lineno-$LINENO}: checking for non-GNU ld" >&5 $as_echo_n "checking for non-GNU ld... " >&6; } fi if ${lt_cv_path_LD+:} false; then : $as_echo_n "(cached) " >&6 else if test -z "$LD"; then lt_save_ifs=$IFS; IFS=$PATH_SEPARATOR for ac_dir in $PATH; do IFS=$lt_save_ifs test -z "$ac_dir" && ac_dir=. if test -f "$ac_dir/$ac_prog" || test -f "$ac_dir/$ac_prog$ac_exeext"; then lt_cv_path_LD=$ac_dir/$ac_prog # Check to see if the program is GNU ld. I'd rather use --version, # but apparently some variants of GNU ld only accept -v. # Break only if it was the GNU/non-GNU ld that we prefer. case `"$lt_cv_path_LD" -v 2>&1 &5 $as_echo "$LD" >&6; } else { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 $as_echo "no" >&6; } fi test -z "$LD" && as_fn_error $? "no acceptable ld found in \$PATH" "$LINENO" 5 { $as_echo "$as_me:${as_lineno-$LINENO}: checking if the linker ($LD) is GNU ld" >&5 $as_echo_n "checking if the linker ($LD) is GNU ld... " >&6; } if ${lt_cv_prog_gnu_ld+:} false; then : $as_echo_n "(cached) " >&6 else # I'd rather use --version here, but apparently some GNU lds only accept -v. case `$LD -v 2>&1 &5 $as_echo "$lt_cv_prog_gnu_ld" >&6; } with_gnu_ld=$lt_cv_prog_gnu_ld { $as_echo "$as_me:${as_lineno-$LINENO}: checking for BSD- or MS-compatible name lister (nm)" >&5 $as_echo_n "checking for BSD- or MS-compatible name lister (nm)... " >&6; } if ${lt_cv_path_NM+:} false; then : $as_echo_n "(cached) " >&6 else if test -n "$NM"; then # Let the user override the test. lt_cv_path_NM=$NM else lt_nm_to_check=${ac_tool_prefix}nm if test -n "$ac_tool_prefix" && test "$build" = "$host"; then lt_nm_to_check="$lt_nm_to_check nm" fi for lt_tmp_nm in $lt_nm_to_check; do lt_save_ifs=$IFS; IFS=$PATH_SEPARATOR for ac_dir in $PATH /usr/ccs/bin/elf /usr/ccs/bin /usr/ucb /bin; do IFS=$lt_save_ifs test -z "$ac_dir" && ac_dir=. tmp_nm=$ac_dir/$lt_tmp_nm if test -f "$tmp_nm" || test -f "$tmp_nm$ac_exeext"; then # Check to see if the nm accepts a BSD-compat flag. # Adding the 'sed 1q' prevents false positives on HP-UX, which says: # nm: unknown option "B" ignored # Tru64's nm complains that /dev/null is an invalid object file # MSYS converts /dev/null to NUL, MinGW nm treats NUL as empty case $build_os in mingw*) lt_bad_file=conftest.nm/nofile ;; *) lt_bad_file=/dev/null ;; esac case `"$tmp_nm" -B $lt_bad_file 2>&1 | sed '1q'` in *$lt_bad_file* | *'Invalid file or object type'*) lt_cv_path_NM="$tmp_nm -B" break 2 ;; *) case `"$tmp_nm" -p /dev/null 2>&1 | sed '1q'` in */dev/null*) lt_cv_path_NM="$tmp_nm -p" break 2 ;; *) lt_cv_path_NM=${lt_cv_path_NM="$tmp_nm"} # keep the first match, but continue # so that we can try to find one that supports BSD flags ;; esac ;; esac fi done IFS=$lt_save_ifs done : ${lt_cv_path_NM=no} fi fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $lt_cv_path_NM" >&5 $as_echo "$lt_cv_path_NM" >&6; } if test no != "$lt_cv_path_NM"; then NM=$lt_cv_path_NM else # Didn't find any BSD compatible name lister, look for dumpbin. if test -n "$DUMPBIN"; then : # Let the user override the test. else if test -n "$ac_tool_prefix"; then for ac_prog in dumpbin "link -dump" do # Extract the first word of "$ac_tool_prefix$ac_prog", so it can be a program name with args. set dummy $ac_tool_prefix$ac_prog; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } if ${ac_cv_prog_DUMPBIN+:} false; then : $as_echo_n "(cached) " >&6 else if test -n "$DUMPBIN"; then ac_cv_prog_DUMPBIN="$DUMPBIN" # Let the user override the test. else as_save_IFS=$IFS; IFS=$PATH_SEPARATOR for as_dir in $PATH do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_prog_DUMPBIN="$ac_tool_prefix$ac_prog" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 fi done done IFS=$as_save_IFS fi fi DUMPBIN=$ac_cv_prog_DUMPBIN if test -n "$DUMPBIN"; then { $as_echo "$as_me:${as_lineno-$LINENO}: result: $DUMPBIN" >&5 $as_echo "$DUMPBIN" >&6; } else { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 $as_echo "no" >&6; } fi test -n "$DUMPBIN" && break done fi if test -z "$DUMPBIN"; then ac_ct_DUMPBIN=$DUMPBIN for ac_prog in dumpbin "link -dump" do # Extract the first word of "$ac_prog", so it can be a program name with args. set dummy $ac_prog; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } if ${ac_cv_prog_ac_ct_DUMPBIN+:} false; then : $as_echo_n "(cached) " >&6 else if test -n "$ac_ct_DUMPBIN"; then ac_cv_prog_ac_ct_DUMPBIN="$ac_ct_DUMPBIN" # Let the user override the test. else as_save_IFS=$IFS; IFS=$PATH_SEPARATOR for as_dir in $PATH do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_prog_ac_ct_DUMPBIN="$ac_prog" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 fi done done IFS=$as_save_IFS fi fi ac_ct_DUMPBIN=$ac_cv_prog_ac_ct_DUMPBIN if test -n "$ac_ct_DUMPBIN"; then { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_ct_DUMPBIN" >&5 $as_echo "$ac_ct_DUMPBIN" >&6; } else { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 $as_echo "no" >&6; } fi test -n "$ac_ct_DUMPBIN" && break done if test "x$ac_ct_DUMPBIN" = x; then DUMPBIN=":" else case $cross_compiling:$ac_tool_warned in yes:) { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: using cross tools not prefixed with host triplet" >&5 $as_echo "$as_me: WARNING: using cross tools not prefixed with host triplet" >&2;} ac_tool_warned=yes ;; esac DUMPBIN=$ac_ct_DUMPBIN fi fi case `$DUMPBIN -symbols -headers /dev/null 2>&1 | sed '1q'` in *COFF*) DUMPBIN="$DUMPBIN -symbols -headers" ;; *) DUMPBIN=: ;; esac fi if test : != "$DUMPBIN"; then NM=$DUMPBIN fi fi test -z "$NM" && NM=nm { $as_echo "$as_me:${as_lineno-$LINENO}: checking the name lister ($NM) interface" >&5 $as_echo_n "checking the name lister ($NM) interface... " >&6; } if ${lt_cv_nm_interface+:} false; then : $as_echo_n "(cached) " >&6 else lt_cv_nm_interface="BSD nm" echo "int some_variable = 0;" > conftest.$ac_ext (eval echo "\"\$as_me:$LINENO: $ac_compile\"" >&5) (eval "$ac_compile" 2>conftest.err) cat conftest.err >&5 (eval echo "\"\$as_me:$LINENO: $NM \\\"conftest.$ac_objext\\\"\"" >&5) (eval "$NM \"conftest.$ac_objext\"" 2>conftest.err > conftest.out) cat conftest.err >&5 (eval echo "\"\$as_me:$LINENO: output\"" >&5) cat conftest.out >&5 if $GREP 'External.*some_variable' conftest.out > /dev/null; then lt_cv_nm_interface="MS dumpbin" fi rm -f conftest* fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $lt_cv_nm_interface" >&5 $as_echo "$lt_cv_nm_interface" >&6; } # find the maximum length of command line arguments { $as_echo "$as_me:${as_lineno-$LINENO}: checking the maximum length of command line arguments" >&5 $as_echo_n "checking the maximum length of command line arguments... " >&6; } if ${lt_cv_sys_max_cmd_len+:} false; then : $as_echo_n "(cached) " >&6 else i=0 teststring=ABCD case $build_os in msdosdjgpp*) # On DJGPP, this test can blow up pretty badly due to problems in libc # (any single argument exceeding 2000 bytes causes a buffer overrun # during glob expansion). Even if it were fixed, the result of this # check would be larger than it should be. lt_cv_sys_max_cmd_len=12288; # 12K is about right ;; gnu*) # Under GNU Hurd, this test is not required because there is # no limit to the length of command line arguments. # Libtool will interpret -1 as no limit whatsoever lt_cv_sys_max_cmd_len=-1; ;; cygwin* | mingw* | cegcc*) # On Win9x/ME, this test blows up -- it succeeds, but takes # about 5 minutes as the teststring grows exponentially. # Worse, since 9x/ME are not pre-emptively multitasking, # you end up with a "frozen" computer, even though with patience # the test eventually succeeds (with a max line length of 256k). # Instead, let's just punt: use the minimum linelength reported by # all of the supported platforms: 8192 (on NT/2K/XP). lt_cv_sys_max_cmd_len=8192; ;; mint*) # On MiNT this can take a long time and run out of memory. lt_cv_sys_max_cmd_len=8192; ;; amigaos*) # On AmigaOS with pdksh, this test takes hours, literally. # So we just punt and use a minimum line length of 8192. lt_cv_sys_max_cmd_len=8192; ;; bitrig* | darwin* | dragonfly* | freebsd* | netbsd* | openbsd*) # This has been around since 386BSD, at least. Likely further. if test -x /sbin/sysctl; then lt_cv_sys_max_cmd_len=`/sbin/sysctl -n kern.argmax` elif test -x /usr/sbin/sysctl; then lt_cv_sys_max_cmd_len=`/usr/sbin/sysctl -n kern.argmax` else lt_cv_sys_max_cmd_len=65536 # usable default for all BSDs fi # And add a safety zone lt_cv_sys_max_cmd_len=`expr $lt_cv_sys_max_cmd_len \/ 4` lt_cv_sys_max_cmd_len=`expr $lt_cv_sys_max_cmd_len \* 3` ;; interix*) # We know the value 262144 and hardcode it with a safety zone (like BSD) lt_cv_sys_max_cmd_len=196608 ;; os2*) # The test takes a long time on OS/2. lt_cv_sys_max_cmd_len=8192 ;; osf*) # Dr. Hans Ekkehard Plesser reports seeing a kernel panic running configure # due to this test when exec_disable_arg_limit is 1 on Tru64. It is not # nice to cause kernel panics so lets avoid the loop below. # First set a reasonable default. lt_cv_sys_max_cmd_len=16384 # if test -x /sbin/sysconfig; then case `/sbin/sysconfig -q proc exec_disable_arg_limit` in *1*) lt_cv_sys_max_cmd_len=-1 ;; esac fi ;; sco3.2v5*) lt_cv_sys_max_cmd_len=102400 ;; sysv5* | sco5v6* | sysv4.2uw2*) kargmax=`grep ARG_MAX /etc/conf/cf.d/stune 2>/dev/null` if test -n "$kargmax"; then lt_cv_sys_max_cmd_len=`echo $kargmax | sed 's/.*[ ]//'` else lt_cv_sys_max_cmd_len=32768 fi ;; *) lt_cv_sys_max_cmd_len=`(getconf ARG_MAX) 2> /dev/null` if test -n "$lt_cv_sys_max_cmd_len" && \ test undefined != "$lt_cv_sys_max_cmd_len"; then lt_cv_sys_max_cmd_len=`expr $lt_cv_sys_max_cmd_len \/ 4` lt_cv_sys_max_cmd_len=`expr $lt_cv_sys_max_cmd_len \* 3` else # Make teststring a little bigger before we do anything with it. # a 1K string should be a reasonable start. for i in 1 2 3 4 5 6 7 8; do teststring=$teststring$teststring done SHELL=${SHELL-${CONFIG_SHELL-/bin/sh}} # If test is not a shell built-in, we'll probably end up computing a # maximum length that is only half of the actual maximum length, but # we can't tell. while { test X`env echo "$teststring$teststring" 2>/dev/null` \ = "X$teststring$teststring"; } >/dev/null 2>&1 && test 17 != "$i" # 1/2 MB should be enough do i=`expr $i + 1` teststring=$teststring$teststring done # Only check the string length outside the loop. lt_cv_sys_max_cmd_len=`expr "X$teststring" : ".*" 2>&1` teststring= # Add a significant safety factor because C++ compilers can tack on # massive amounts of additional arguments before passing them to the # linker. It appears as though 1/2 is a usable value. lt_cv_sys_max_cmd_len=`expr $lt_cv_sys_max_cmd_len \/ 2` fi ;; esac fi if test -n "$lt_cv_sys_max_cmd_len"; then { $as_echo "$as_me:${as_lineno-$LINENO}: result: $lt_cv_sys_max_cmd_len" >&5 $as_echo "$lt_cv_sys_max_cmd_len" >&6; } else { $as_echo "$as_me:${as_lineno-$LINENO}: result: none" >&5 $as_echo "none" >&6; } fi max_cmd_len=$lt_cv_sys_max_cmd_len : ${CP="cp -f"} : ${MV="mv -f"} : ${RM="rm -f"} if ( (MAIL=60; unset MAIL) || exit) >/dev/null 2>&1; then lt_unset=unset else lt_unset=false fi # test EBCDIC or ASCII case `echo X|tr X '\101'` in A) # ASCII based system # \n is not interpreted correctly by Solaris 8 /usr/ucb/tr lt_SP2NL='tr \040 \012' lt_NL2SP='tr \015\012 \040\040' ;; *) # EBCDIC based system lt_SP2NL='tr \100 \n' lt_NL2SP='tr \r\n \100\100' ;; esac { $as_echo "$as_me:${as_lineno-$LINENO}: checking how to convert $build file names to $host format" >&5 $as_echo_n "checking how to convert $build file names to $host format... " >&6; } if ${lt_cv_to_host_file_cmd+:} false; then : $as_echo_n "(cached) " >&6 else case $host in *-*-mingw* ) case $build in *-*-mingw* ) # actually msys lt_cv_to_host_file_cmd=func_convert_file_msys_to_w32 ;; *-*-cygwin* ) lt_cv_to_host_file_cmd=func_convert_file_cygwin_to_w32 ;; * ) # otherwise, assume *nix lt_cv_to_host_file_cmd=func_convert_file_nix_to_w32 ;; esac ;; *-*-cygwin* ) case $build in *-*-mingw* ) # actually msys lt_cv_to_host_file_cmd=func_convert_file_msys_to_cygwin ;; *-*-cygwin* ) lt_cv_to_host_file_cmd=func_convert_file_noop ;; * ) # otherwise, assume *nix lt_cv_to_host_file_cmd=func_convert_file_nix_to_cygwin ;; esac ;; * ) # unhandled hosts (and "normal" native builds) lt_cv_to_host_file_cmd=func_convert_file_noop ;; esac fi to_host_file_cmd=$lt_cv_to_host_file_cmd { $as_echo "$as_me:${as_lineno-$LINENO}: result: $lt_cv_to_host_file_cmd" >&5 $as_echo "$lt_cv_to_host_file_cmd" >&6; } { $as_echo "$as_me:${as_lineno-$LINENO}: checking how to convert $build file names to toolchain format" >&5 $as_echo_n "checking how to convert $build file names to toolchain format... " >&6; } if ${lt_cv_to_tool_file_cmd+:} false; then : $as_echo_n "(cached) " >&6 else #assume ordinary cross tools, or native build. lt_cv_to_tool_file_cmd=func_convert_file_noop case $host in *-*-mingw* ) case $build in *-*-mingw* ) # actually msys lt_cv_to_tool_file_cmd=func_convert_file_msys_to_w32 ;; esac ;; esac fi to_tool_file_cmd=$lt_cv_to_tool_file_cmd { $as_echo "$as_me:${as_lineno-$LINENO}: result: $lt_cv_to_tool_file_cmd" >&5 $as_echo "$lt_cv_to_tool_file_cmd" >&6; } { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $LD option to reload object files" >&5 $as_echo_n "checking for $LD option to reload object files... " >&6; } if ${lt_cv_ld_reload_flag+:} false; then : $as_echo_n "(cached) " >&6 else lt_cv_ld_reload_flag='-r' fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $lt_cv_ld_reload_flag" >&5 $as_echo "$lt_cv_ld_reload_flag" >&6; } reload_flag=$lt_cv_ld_reload_flag case $reload_flag in "" | " "*) ;; *) reload_flag=" $reload_flag" ;; esac reload_cmds='$LD$reload_flag -o $output$reload_objs' case $host_os in cygwin* | mingw* | pw32* | cegcc*) if test yes != "$GCC"; then reload_cmds=false fi ;; darwin*) if test yes = "$GCC"; then reload_cmds='$LTCC $LTCFLAGS -nostdlib $wl-r -o $output$reload_objs' else reload_cmds='$LD$reload_flag -o $output$reload_objs' fi ;; esac if test -n "$ac_tool_prefix"; then # Extract the first word of "${ac_tool_prefix}objdump", so it can be a program name with args. set dummy ${ac_tool_prefix}objdump; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } if ${ac_cv_prog_OBJDUMP+:} false; then : $as_echo_n "(cached) " >&6 else if test -n "$OBJDUMP"; then ac_cv_prog_OBJDUMP="$OBJDUMP" # Let the user override the test. else as_save_IFS=$IFS; IFS=$PATH_SEPARATOR for as_dir in $PATH do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_prog_OBJDUMP="${ac_tool_prefix}objdump" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 fi done done IFS=$as_save_IFS fi fi OBJDUMP=$ac_cv_prog_OBJDUMP if test -n "$OBJDUMP"; then { $as_echo "$as_me:${as_lineno-$LINENO}: result: $OBJDUMP" >&5 $as_echo "$OBJDUMP" >&6; } else { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 $as_echo "no" >&6; } fi fi if test -z "$ac_cv_prog_OBJDUMP"; then ac_ct_OBJDUMP=$OBJDUMP # Extract the first word of "objdump", so it can be a program name with args. set dummy objdump; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } if ${ac_cv_prog_ac_ct_OBJDUMP+:} false; then : $as_echo_n "(cached) " >&6 else if test -n "$ac_ct_OBJDUMP"; then ac_cv_prog_ac_ct_OBJDUMP="$ac_ct_OBJDUMP" # Let the user override the test. else as_save_IFS=$IFS; IFS=$PATH_SEPARATOR for as_dir in $PATH do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_prog_ac_ct_OBJDUMP="objdump" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 fi done done IFS=$as_save_IFS fi fi ac_ct_OBJDUMP=$ac_cv_prog_ac_ct_OBJDUMP if test -n "$ac_ct_OBJDUMP"; then { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_ct_OBJDUMP" >&5 $as_echo "$ac_ct_OBJDUMP" >&6; } else { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 $as_echo "no" >&6; } fi if test "x$ac_ct_OBJDUMP" = x; then OBJDUMP="false" else case $cross_compiling:$ac_tool_warned in yes:) { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: using cross tools not prefixed with host triplet" >&5 $as_echo "$as_me: WARNING: using cross tools not prefixed with host triplet" >&2;} ac_tool_warned=yes ;; esac OBJDUMP=$ac_ct_OBJDUMP fi else OBJDUMP="$ac_cv_prog_OBJDUMP" fi test -z "$OBJDUMP" && OBJDUMP=objdump { $as_echo "$as_me:${as_lineno-$LINENO}: checking how to recognize dependent libraries" >&5 $as_echo_n "checking how to recognize dependent libraries... " >&6; } if ${lt_cv_deplibs_check_method+:} false; then : $as_echo_n "(cached) " >&6 else lt_cv_file_magic_cmd='$MAGIC_CMD' lt_cv_file_magic_test_file= lt_cv_deplibs_check_method='unknown' # Need to set the preceding variable on all platforms that support # interlibrary dependencies. # 'none' -- dependencies not supported. # 'unknown' -- same as none, but documents that we really don't know. # 'pass_all' -- all dependencies passed with no checks. # 'test_compile' -- check by making test program. # 'file_magic [[regex]]' -- check by looking for files in library path # that responds to the $file_magic_cmd with a given extended regex. # If you have 'file' or equivalent on your system and you're not sure # whether 'pass_all' will *always* work, you probably want this one. case $host_os in aix[4-9]*) lt_cv_deplibs_check_method=pass_all ;; beos*) lt_cv_deplibs_check_method=pass_all ;; bsdi[45]*) lt_cv_deplibs_check_method='file_magic ELF [0-9][0-9]*-bit [ML]SB (shared object|dynamic lib)' lt_cv_file_magic_cmd='/usr/bin/file -L' lt_cv_file_magic_test_file=/shlib/libc.so ;; cygwin*) # func_win32_libid is a shell function defined in ltmain.sh lt_cv_deplibs_check_method='file_magic ^x86 archive import|^x86 DLL' lt_cv_file_magic_cmd='func_win32_libid' ;; mingw* | pw32*) # Base MSYS/MinGW do not provide the 'file' command needed by # func_win32_libid shell function, so use a weaker test based on 'objdump', # unless we find 'file', for example because we are cross-compiling. if ( file / ) >/dev/null 2>&1; then lt_cv_deplibs_check_method='file_magic ^x86 archive import|^x86 DLL' lt_cv_file_magic_cmd='func_win32_libid' else # Keep this pattern in sync with the one in func_win32_libid. lt_cv_deplibs_check_method='file_magic file format (pei*-i386(.*architecture: i386)?|pe-arm-wince|pe-x86-64)' lt_cv_file_magic_cmd='$OBJDUMP -f' fi ;; cegcc*) # use the weaker test based on 'objdump'. See mingw*. lt_cv_deplibs_check_method='file_magic file format pe-arm-.*little(.*architecture: arm)?' lt_cv_file_magic_cmd='$OBJDUMP -f' ;; darwin* | rhapsody*) lt_cv_deplibs_check_method=pass_all ;; freebsd* | dragonfly*) if echo __ELF__ | $CC -E - | $GREP __ELF__ > /dev/null; then case $host_cpu in i*86 ) # Not sure whether the presence of OpenBSD here was a mistake. # Let's accept both of them until this is cleared up. lt_cv_deplibs_check_method='file_magic (FreeBSD|OpenBSD|DragonFly)/i[3-9]86 (compact )?demand paged shared library' lt_cv_file_magic_cmd=/usr/bin/file lt_cv_file_magic_test_file=`echo /usr/lib/libc.so.*` ;; esac else lt_cv_deplibs_check_method=pass_all fi ;; haiku*) lt_cv_deplibs_check_method=pass_all ;; hpux10.20* | hpux11*) lt_cv_file_magic_cmd=/usr/bin/file case $host_cpu in ia64*) lt_cv_deplibs_check_method='file_magic (s[0-9][0-9][0-9]|ELF-[0-9][0-9]) shared object file - IA64' lt_cv_file_magic_test_file=/usr/lib/hpux32/libc.so ;; hppa*64*) lt_cv_deplibs_check_method='file_magic (s[0-9][0-9][0-9]|ELF[ -][0-9][0-9])(-bit)?( [LM]SB)? shared object( file)?[, -]* PA-RISC [0-9]\.[0-9]' lt_cv_file_magic_test_file=/usr/lib/pa20_64/libc.sl ;; *) lt_cv_deplibs_check_method='file_magic (s[0-9][0-9][0-9]|PA-RISC[0-9]\.[0-9]) shared library' lt_cv_file_magic_test_file=/usr/lib/libc.sl ;; esac ;; interix[3-9]*) # PIC code is broken on Interix 3.x, that's why |\.a not |_pic\.a here lt_cv_deplibs_check_method='match_pattern /lib[^/]+(\.so|\.a)$' ;; irix5* | irix6* | nonstopux*) case $LD in *-32|*"-32 ") libmagic=32-bit;; *-n32|*"-n32 ") libmagic=N32;; *-64|*"-64 ") libmagic=64-bit;; *) libmagic=never-match;; esac lt_cv_deplibs_check_method=pass_all ;; # This must be glibc/ELF. linux* | k*bsd*-gnu | kopensolaris*-gnu | gnu*) lt_cv_deplibs_check_method=pass_all ;; netbsd* | netbsdelf*-gnu) if echo __ELF__ | $CC -E - | $GREP __ELF__ > /dev/null; then lt_cv_deplibs_check_method='match_pattern /lib[^/]+(\.so\.[0-9]+\.[0-9]+|_pic\.a)$' else lt_cv_deplibs_check_method='match_pattern /lib[^/]+(\.so|_pic\.a)$' fi ;; newos6*) lt_cv_deplibs_check_method='file_magic ELF [0-9][0-9]*-bit [ML]SB (executable|dynamic lib)' lt_cv_file_magic_cmd=/usr/bin/file lt_cv_file_magic_test_file=/usr/lib/libnls.so ;; *nto* | *qnx*) lt_cv_deplibs_check_method=pass_all ;; openbsd* | bitrig*) if test -z "`echo __ELF__ | $CC -E - | $GREP __ELF__`"; then lt_cv_deplibs_check_method='match_pattern /lib[^/]+(\.so\.[0-9]+\.[0-9]+|\.so|_pic\.a)$' else lt_cv_deplibs_check_method='match_pattern /lib[^/]+(\.so\.[0-9]+\.[0-9]+|_pic\.a)$' fi ;; osf3* | osf4* | osf5*) lt_cv_deplibs_check_method=pass_all ;; rdos*) lt_cv_deplibs_check_method=pass_all ;; solaris*) lt_cv_deplibs_check_method=pass_all ;; sysv5* | sco3.2v5* | sco5v6* | unixware* | OpenUNIX* | sysv4*uw2*) lt_cv_deplibs_check_method=pass_all ;; sysv4 | sysv4.3*) case $host_vendor in motorola) lt_cv_deplibs_check_method='file_magic ELF [0-9][0-9]*-bit [ML]SB (shared object|dynamic lib) M[0-9][0-9]* Version [0-9]' lt_cv_file_magic_test_file=`echo /usr/lib/libc.so*` ;; ncr) lt_cv_deplibs_check_method=pass_all ;; sequent) lt_cv_file_magic_cmd='/bin/file' lt_cv_deplibs_check_method='file_magic ELF [0-9][0-9]*-bit [LM]SB (shared object|dynamic lib )' ;; sni) lt_cv_file_magic_cmd='/bin/file' lt_cv_deplibs_check_method="file_magic ELF [0-9][0-9]*-bit [LM]SB dynamic lib" lt_cv_file_magic_test_file=/lib/libc.so ;; siemens) lt_cv_deplibs_check_method=pass_all ;; pc) lt_cv_deplibs_check_method=pass_all ;; esac ;; tpf*) lt_cv_deplibs_check_method=pass_all ;; os2*) lt_cv_deplibs_check_method=pass_all ;; esac fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $lt_cv_deplibs_check_method" >&5 $as_echo "$lt_cv_deplibs_check_method" >&6; } file_magic_glob= want_nocaseglob=no if test "$build" = "$host"; then case $host_os in mingw* | pw32*) if ( shopt | grep nocaseglob ) >/dev/null 2>&1; then want_nocaseglob=yes else file_magic_glob=`echo aAbBcCdDeEfFgGhHiIjJkKlLmMnNoOpPqQrRsStTuUvVwWxXyYzZ | $SED -e "s/\(..\)/s\/[\1]\/[\1]\/g;/g"` fi ;; esac fi file_magic_cmd=$lt_cv_file_magic_cmd deplibs_check_method=$lt_cv_deplibs_check_method test -z "$deplibs_check_method" && deplibs_check_method=unknown if test -n "$ac_tool_prefix"; then # Extract the first word of "${ac_tool_prefix}dlltool", so it can be a program name with args. set dummy ${ac_tool_prefix}dlltool; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } if ${ac_cv_prog_DLLTOOL+:} false; then : $as_echo_n "(cached) " >&6 else if test -n "$DLLTOOL"; then ac_cv_prog_DLLTOOL="$DLLTOOL" # Let the user override the test. else as_save_IFS=$IFS; IFS=$PATH_SEPARATOR for as_dir in $PATH do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_prog_DLLTOOL="${ac_tool_prefix}dlltool" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 fi done done IFS=$as_save_IFS fi fi DLLTOOL=$ac_cv_prog_DLLTOOL if test -n "$DLLTOOL"; then { $as_echo "$as_me:${as_lineno-$LINENO}: result: $DLLTOOL" >&5 $as_echo "$DLLTOOL" >&6; } else { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 $as_echo "no" >&6; } fi fi if test -z "$ac_cv_prog_DLLTOOL"; then ac_ct_DLLTOOL=$DLLTOOL # Extract the first word of "dlltool", so it can be a program name with args. set dummy dlltool; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } if ${ac_cv_prog_ac_ct_DLLTOOL+:} false; then : $as_echo_n "(cached) " >&6 else if test -n "$ac_ct_DLLTOOL"; then ac_cv_prog_ac_ct_DLLTOOL="$ac_ct_DLLTOOL" # Let the user override the test. else as_save_IFS=$IFS; IFS=$PATH_SEPARATOR for as_dir in $PATH do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_prog_ac_ct_DLLTOOL="dlltool" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 fi done done IFS=$as_save_IFS fi fi ac_ct_DLLTOOL=$ac_cv_prog_ac_ct_DLLTOOL if test -n "$ac_ct_DLLTOOL"; then { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_ct_DLLTOOL" >&5 $as_echo "$ac_ct_DLLTOOL" >&6; } else { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 $as_echo "no" >&6; } fi if test "x$ac_ct_DLLTOOL" = x; then DLLTOOL="false" else case $cross_compiling:$ac_tool_warned in yes:) { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: using cross tools not prefixed with host triplet" >&5 $as_echo "$as_me: WARNING: using cross tools not prefixed with host triplet" >&2;} ac_tool_warned=yes ;; esac DLLTOOL=$ac_ct_DLLTOOL fi else DLLTOOL="$ac_cv_prog_DLLTOOL" fi test -z "$DLLTOOL" && DLLTOOL=dlltool { $as_echo "$as_me:${as_lineno-$LINENO}: checking how to associate runtime and link libraries" >&5 $as_echo_n "checking how to associate runtime and link libraries... " >&6; } if ${lt_cv_sharedlib_from_linklib_cmd+:} false; then : $as_echo_n "(cached) " >&6 else lt_cv_sharedlib_from_linklib_cmd='unknown' case $host_os in cygwin* | mingw* | pw32* | cegcc*) # two different shell functions defined in ltmain.sh; # decide which one to use based on capabilities of $DLLTOOL case `$DLLTOOL --help 2>&1` in *--identify-strict*) lt_cv_sharedlib_from_linklib_cmd=func_cygming_dll_for_implib ;; *) lt_cv_sharedlib_from_linklib_cmd=func_cygming_dll_for_implib_fallback ;; esac ;; *) # fallback: assume linklib IS sharedlib lt_cv_sharedlib_from_linklib_cmd=$ECHO ;; esac fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $lt_cv_sharedlib_from_linklib_cmd" >&5 $as_echo "$lt_cv_sharedlib_from_linklib_cmd" >&6; } sharedlib_from_linklib_cmd=$lt_cv_sharedlib_from_linklib_cmd test -z "$sharedlib_from_linklib_cmd" && sharedlib_from_linklib_cmd=$ECHO if test -n "$ac_tool_prefix"; then for ac_prog in ar do # Extract the first word of "$ac_tool_prefix$ac_prog", so it can be a program name with args. set dummy $ac_tool_prefix$ac_prog; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } if ${ac_cv_prog_AR+:} false; then : $as_echo_n "(cached) " >&6 else if test -n "$AR"; then ac_cv_prog_AR="$AR" # Let the user override the test. else as_save_IFS=$IFS; IFS=$PATH_SEPARATOR for as_dir in $PATH do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_prog_AR="$ac_tool_prefix$ac_prog" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 fi done done IFS=$as_save_IFS fi fi AR=$ac_cv_prog_AR if test -n "$AR"; then { $as_echo "$as_me:${as_lineno-$LINENO}: result: $AR" >&5 $as_echo "$AR" >&6; } else { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 $as_echo "no" >&6; } fi test -n "$AR" && break done fi if test -z "$AR"; then ac_ct_AR=$AR for ac_prog in ar do # Extract the first word of "$ac_prog", so it can be a program name with args. set dummy $ac_prog; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } if ${ac_cv_prog_ac_ct_AR+:} false; then : $as_echo_n "(cached) " >&6 else if test -n "$ac_ct_AR"; then ac_cv_prog_ac_ct_AR="$ac_ct_AR" # Let the user override the test. else as_save_IFS=$IFS; IFS=$PATH_SEPARATOR for as_dir in $PATH do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_prog_ac_ct_AR="$ac_prog" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 fi done done IFS=$as_save_IFS fi fi ac_ct_AR=$ac_cv_prog_ac_ct_AR if test -n "$ac_ct_AR"; then { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_ct_AR" >&5 $as_echo "$ac_ct_AR" >&6; } else { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 $as_echo "no" >&6; } fi test -n "$ac_ct_AR" && break done if test "x$ac_ct_AR" = x; then AR="false" else case $cross_compiling:$ac_tool_warned in yes:) { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: using cross tools not prefixed with host triplet" >&5 $as_echo "$as_me: WARNING: using cross tools not prefixed with host triplet" >&2;} ac_tool_warned=yes ;; esac AR=$ac_ct_AR fi fi : ${AR=ar} : ${AR_FLAGS=cru} { $as_echo "$as_me:${as_lineno-$LINENO}: checking for archiver @FILE support" >&5 $as_echo_n "checking for archiver @FILE support... " >&6; } if ${lt_cv_ar_at_file+:} false; then : $as_echo_n "(cached) " >&6 else lt_cv_ar_at_file=no cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ int main () { ; return 0; } _ACEOF if ac_fn_c_try_compile "$LINENO"; then : echo conftest.$ac_objext > conftest.lst lt_ar_try='$AR $AR_FLAGS libconftest.a @conftest.lst >&5' { { eval echo "\"\$as_me\":${as_lineno-$LINENO}: \"$lt_ar_try\""; } >&5 (eval $lt_ar_try) 2>&5 ac_status=$? $as_echo "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 test $ac_status = 0; } if test 0 -eq "$ac_status"; then # Ensure the archiver fails upon bogus file names. rm -f conftest.$ac_objext libconftest.a { { eval echo "\"\$as_me\":${as_lineno-$LINENO}: \"$lt_ar_try\""; } >&5 (eval $lt_ar_try) 2>&5 ac_status=$? $as_echo "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 test $ac_status = 0; } if test 0 -ne "$ac_status"; then lt_cv_ar_at_file=@ fi fi rm -f conftest.* libconftest.a fi rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $lt_cv_ar_at_file" >&5 $as_echo "$lt_cv_ar_at_file" >&6; } if test no = "$lt_cv_ar_at_file"; then archiver_list_spec= else archiver_list_spec=$lt_cv_ar_at_file fi if test -n "$ac_tool_prefix"; then # Extract the first word of "${ac_tool_prefix}strip", so it can be a program name with args. set dummy ${ac_tool_prefix}strip; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } if ${ac_cv_prog_STRIP+:} false; then : $as_echo_n "(cached) " >&6 else if test -n "$STRIP"; then ac_cv_prog_STRIP="$STRIP" # Let the user override the test. else as_save_IFS=$IFS; IFS=$PATH_SEPARATOR for as_dir in $PATH do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_prog_STRIP="${ac_tool_prefix}strip" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 fi done done IFS=$as_save_IFS fi fi STRIP=$ac_cv_prog_STRIP if test -n "$STRIP"; then { $as_echo "$as_me:${as_lineno-$LINENO}: result: $STRIP" >&5 $as_echo "$STRIP" >&6; } else { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 $as_echo "no" >&6; } fi fi if test -z "$ac_cv_prog_STRIP"; then ac_ct_STRIP=$STRIP # Extract the first word of "strip", so it can be a program name with args. set dummy strip; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } if ${ac_cv_prog_ac_ct_STRIP+:} false; then : $as_echo_n "(cached) " >&6 else if test -n "$ac_ct_STRIP"; then ac_cv_prog_ac_ct_STRIP="$ac_ct_STRIP" # Let the user override the test. else as_save_IFS=$IFS; IFS=$PATH_SEPARATOR for as_dir in $PATH do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_prog_ac_ct_STRIP="strip" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 fi done done IFS=$as_save_IFS fi fi ac_ct_STRIP=$ac_cv_prog_ac_ct_STRIP if test -n "$ac_ct_STRIP"; then { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_ct_STRIP" >&5 $as_echo "$ac_ct_STRIP" >&6; } else { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 $as_echo "no" >&6; } fi if test "x$ac_ct_STRIP" = x; then STRIP=":" else case $cross_compiling:$ac_tool_warned in yes:) { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: using cross tools not prefixed with host triplet" >&5 $as_echo "$as_me: WARNING: using cross tools not prefixed with host triplet" >&2;} ac_tool_warned=yes ;; esac STRIP=$ac_ct_STRIP fi else STRIP="$ac_cv_prog_STRIP" fi test -z "$STRIP" && STRIP=: if test -n "$ac_tool_prefix"; then # Extract the first word of "${ac_tool_prefix}ranlib", so it can be a program name with args. set dummy ${ac_tool_prefix}ranlib; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } if ${ac_cv_prog_RANLIB+:} false; then : $as_echo_n "(cached) " >&6 else if test -n "$RANLIB"; then ac_cv_prog_RANLIB="$RANLIB" # Let the user override the test. else as_save_IFS=$IFS; IFS=$PATH_SEPARATOR for as_dir in $PATH do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_prog_RANLIB="${ac_tool_prefix}ranlib" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 fi done done IFS=$as_save_IFS fi fi RANLIB=$ac_cv_prog_RANLIB if test -n "$RANLIB"; then { $as_echo "$as_me:${as_lineno-$LINENO}: result: $RANLIB" >&5 $as_echo "$RANLIB" >&6; } else { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 $as_echo "no" >&6; } fi fi if test -z "$ac_cv_prog_RANLIB"; then ac_ct_RANLIB=$RANLIB # Extract the first word of "ranlib", so it can be a program name with args. set dummy ranlib; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } if ${ac_cv_prog_ac_ct_RANLIB+:} false; then : $as_echo_n "(cached) " >&6 else if test -n "$ac_ct_RANLIB"; then ac_cv_prog_ac_ct_RANLIB="$ac_ct_RANLIB" # Let the user override the test. else as_save_IFS=$IFS; IFS=$PATH_SEPARATOR for as_dir in $PATH do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_prog_ac_ct_RANLIB="ranlib" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 fi done done IFS=$as_save_IFS fi fi ac_ct_RANLIB=$ac_cv_prog_ac_ct_RANLIB if test -n "$ac_ct_RANLIB"; then { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_ct_RANLIB" >&5 $as_echo "$ac_ct_RANLIB" >&6; } else { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 $as_echo "no" >&6; } fi if test "x$ac_ct_RANLIB" = x; then RANLIB=":" else case $cross_compiling:$ac_tool_warned in yes:) { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: using cross tools not prefixed with host triplet" >&5 $as_echo "$as_me: WARNING: using cross tools not prefixed with host triplet" >&2;} ac_tool_warned=yes ;; esac RANLIB=$ac_ct_RANLIB fi else RANLIB="$ac_cv_prog_RANLIB" fi test -z "$RANLIB" && RANLIB=: # Determine commands to create old-style static archives. old_archive_cmds='$AR $AR_FLAGS $oldlib$oldobjs' old_postinstall_cmds='chmod 644 $oldlib' old_postuninstall_cmds= if test -n "$RANLIB"; then case $host_os in bitrig* | openbsd*) old_postinstall_cmds="$old_postinstall_cmds~\$RANLIB -t \$tool_oldlib" ;; *) old_postinstall_cmds="$old_postinstall_cmds~\$RANLIB \$tool_oldlib" ;; esac old_archive_cmds="$old_archive_cmds~\$RANLIB \$tool_oldlib" fi case $host_os in darwin*) lock_old_archive_extraction=yes ;; *) lock_old_archive_extraction=no ;; esac # If no C compiler was specified, use CC. LTCC=${LTCC-"$CC"} # If no C compiler flags were specified, use CFLAGS. LTCFLAGS=${LTCFLAGS-"$CFLAGS"} # Allow CC to be a program name with arguments. compiler=$CC # Check for command to grab the raw symbol name followed by C symbol from nm. { $as_echo "$as_me:${as_lineno-$LINENO}: checking command to parse $NM output from $compiler object" >&5 $as_echo_n "checking command to parse $NM output from $compiler object... " >&6; } if ${lt_cv_sys_global_symbol_pipe+:} false; then : $as_echo_n "(cached) " >&6 else # These are sane defaults that work on at least a few old systems. # [They come from Ultrix. What could be older than Ultrix?!! ;)] # Character class describing NM global symbol codes. symcode='[BCDEGRST]' # Regexp to match symbols that can be accessed directly from C. sympat='\([_A-Za-z][_A-Za-z0-9]*\)' # Define system-specific variables. case $host_os in aix*) symcode='[BCDT]' ;; cygwin* | mingw* | pw32* | cegcc*) symcode='[ABCDGISTW]' ;; hpux*) if test ia64 = "$host_cpu"; then symcode='[ABCDEGRST]' fi ;; irix* | nonstopux*) symcode='[BCDEGRST]' ;; osf*) symcode='[BCDEGQRST]' ;; solaris*) symcode='[BDRT]' ;; sco3.2v5*) symcode='[DT]' ;; sysv4.2uw2*) symcode='[DT]' ;; sysv5* | sco5v6* | unixware* | OpenUNIX*) symcode='[ABDT]' ;; sysv4) symcode='[DFNSTU]' ;; esac # If we're using GNU nm, then use its standard symbol codes. case `$NM -V 2>&1` in *GNU* | *'with BFD'*) symcode='[ABCDGIRSTW]' ;; esac if test "$lt_cv_nm_interface" = "MS dumpbin"; then # Gets list of data symbols to import. lt_cv_sys_global_symbol_to_import="sed -n -e 's/^I .* \(.*\)$/\1/p'" # Adjust the below global symbol transforms to fixup imported variables. lt_cdecl_hook=" -e 's/^I .* \(.*\)$/extern __declspec(dllimport) char \1;/p'" lt_c_name_hook=" -e 's/^I .* \(.*\)$/ {\"\1\", (void *) 0},/p'" lt_c_name_lib_hook="\ -e 's/^I .* \(lib.*\)$/ {\"\1\", (void *) 0},/p'\ -e 's/^I .* \(.*\)$/ {\"lib\1\", (void *) 0},/p'" else # Disable hooks by default. lt_cv_sys_global_symbol_to_import= lt_cdecl_hook= lt_c_name_hook= lt_c_name_lib_hook= fi # Transform an extracted symbol line into a proper C declaration. # Some systems (esp. on ia64) link data and code symbols differently, # so use this general approach. lt_cv_sys_global_symbol_to_cdecl="sed -n"\ $lt_cdecl_hook\ " -e 's/^T .* \(.*\)$/extern int \1();/p'"\ " -e 's/^$symcode$symcode* .* \(.*\)$/extern char \1;/p'" # Transform an extracted symbol line into symbol name and symbol address lt_cv_sys_global_symbol_to_c_name_address="sed -n"\ $lt_c_name_hook\ " -e 's/^: \(.*\) .*$/ {\"\1\", (void *) 0},/p'"\ " -e 's/^$symcode$symcode* .* \(.*\)$/ {\"\1\", (void *) \&\1},/p'" # Transform an extracted symbol line into symbol name with lib prefix and # symbol address. lt_cv_sys_global_symbol_to_c_name_address_lib_prefix="sed -n"\ $lt_c_name_lib_hook\ " -e 's/^: \(.*\) .*$/ {\"\1\", (void *) 0},/p'"\ " -e 's/^$symcode$symcode* .* \(lib.*\)$/ {\"\1\", (void *) \&\1},/p'"\ " -e 's/^$symcode$symcode* .* \(.*\)$/ {\"lib\1\", (void *) \&\1},/p'" # Handle CRLF in mingw tool chain opt_cr= case $build_os in mingw*) opt_cr=`$ECHO 'x\{0,1\}' | tr x '\015'` # option cr in regexp ;; esac # Try without a prefix underscore, then with it. for ac_symprfx in "" "_"; do # Transform symcode, sympat, and symprfx into a raw symbol and a C symbol. symxfrm="\\1 $ac_symprfx\\2 \\2" # Write the raw and C identifiers. if test "$lt_cv_nm_interface" = "MS dumpbin"; then # Fake it for dumpbin and say T for any non-static function, # D for any global variable and I for any imported variable. # Also find C++ and __fastcall symbols from MSVC++, # which start with @ or ?. lt_cv_sys_global_symbol_pipe="$AWK '"\ " {last_section=section; section=\$ 3};"\ " /^COFF SYMBOL TABLE/{for(i in hide) delete hide[i]};"\ " /Section length .*#relocs.*(pick any)/{hide[last_section]=1};"\ " /^ *Symbol name *: /{split(\$ 0,sn,\":\"); si=substr(sn[2],2)};"\ " /^ *Type *: code/{print \"T\",si,substr(si,length(prfx))};"\ " /^ *Type *: data/{print \"I\",si,substr(si,length(prfx))};"\ " \$ 0!~/External *\|/{next};"\ " / 0+ UNDEF /{next}; / UNDEF \([^|]\)*()/{next};"\ " {if(hide[section]) next};"\ " {f=\"D\"}; \$ 0~/\(\).*\|/{f=\"T\"};"\ " {split(\$ 0,a,/\||\r/); split(a[2],s)};"\ " s[1]~/^[@?]/{print f,s[1],s[1]; next};"\ " s[1]~prfx {split(s[1],t,\"@\"); print f,t[1],substr(t[1],length(prfx))}"\ " ' prfx=^$ac_symprfx" else lt_cv_sys_global_symbol_pipe="sed -n -e 's/^.*[ ]\($symcode$symcode*\)[ ][ ]*$ac_symprfx$sympat$opt_cr$/$symxfrm/p'" fi lt_cv_sys_global_symbol_pipe="$lt_cv_sys_global_symbol_pipe | sed '/ __gnu_lto/d'" # Check to see that the pipe works correctly. pipe_works=no rm -f conftest* cat > conftest.$ac_ext <<_LT_EOF #ifdef __cplusplus extern "C" { #endif char nm_test_var; void nm_test_func(void); void nm_test_func(void){} #ifdef __cplusplus } #endif int main(){nm_test_var='a';nm_test_func();return(0);} _LT_EOF if { { eval echo "\"\$as_me\":${as_lineno-$LINENO}: \"$ac_compile\""; } >&5 (eval $ac_compile) 2>&5 ac_status=$? $as_echo "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 test $ac_status = 0; }; then # Now try to grab the symbols. nlist=conftest.nm if { { eval echo "\"\$as_me\":${as_lineno-$LINENO}: \"$NM conftest.$ac_objext \| "$lt_cv_sys_global_symbol_pipe" \> $nlist\""; } >&5 (eval $NM conftest.$ac_objext \| "$lt_cv_sys_global_symbol_pipe" \> $nlist) 2>&5 ac_status=$? $as_echo "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 test $ac_status = 0; } && test -s "$nlist"; then # Try sorting and uniquifying the output. if sort "$nlist" | uniq > "$nlist"T; then mv -f "$nlist"T "$nlist" else rm -f "$nlist"T fi # Make sure that we snagged all the symbols we need. if $GREP ' nm_test_var$' "$nlist" >/dev/null; then if $GREP ' nm_test_func$' "$nlist" >/dev/null; then cat <<_LT_EOF > conftest.$ac_ext /* Keep this code in sync between libtool.m4, ltmain, lt_system.h, and tests. */ #if defined _WIN32 || defined __CYGWIN__ || defined _WIN32_WCE /* DATA imports from DLLs on WIN32 can't be const, because runtime relocations are performed -- see ld's documentation on pseudo-relocs. */ # define LT_DLSYM_CONST #elif defined __osf__ /* This system does not cope well with relocations in const data. */ # define LT_DLSYM_CONST #else # define LT_DLSYM_CONST const #endif #ifdef __cplusplus extern "C" { #endif _LT_EOF # Now generate the symbol file. eval "$lt_cv_sys_global_symbol_to_cdecl"' < "$nlist" | $GREP -v main >> conftest.$ac_ext' cat <<_LT_EOF >> conftest.$ac_ext /* The mapping between symbol names and symbols. */ LT_DLSYM_CONST struct { const char *name; void *address; } lt__PROGRAM__LTX_preloaded_symbols[] = { { "@PROGRAM@", (void *) 0 }, _LT_EOF $SED "s/^$symcode$symcode* .* \(.*\)$/ {\"\1\", (void *) \&\1},/" < "$nlist" | $GREP -v main >> conftest.$ac_ext cat <<\_LT_EOF >> conftest.$ac_ext {0, (void *) 0} }; /* This works around a problem in FreeBSD linker */ #ifdef FREEBSD_WORKAROUND static const void *lt_preloaded_setup() { return lt__PROGRAM__LTX_preloaded_symbols; } #endif #ifdef __cplusplus } #endif _LT_EOF # Now try linking the two files. mv conftest.$ac_objext conftstm.$ac_objext lt_globsym_save_LIBS=$LIBS lt_globsym_save_CFLAGS=$CFLAGS LIBS=conftstm.$ac_objext CFLAGS="$CFLAGS$lt_prog_compiler_no_builtin_flag" if { { eval echo "\"\$as_me\":${as_lineno-$LINENO}: \"$ac_link\""; } >&5 (eval $ac_link) 2>&5 ac_status=$? $as_echo "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 test $ac_status = 0; } && test -s conftest$ac_exeext; then pipe_works=yes fi LIBS=$lt_globsym_save_LIBS CFLAGS=$lt_globsym_save_CFLAGS else echo "cannot find nm_test_func in $nlist" >&5 fi else echo "cannot find nm_test_var in $nlist" >&5 fi else echo "cannot run $lt_cv_sys_global_symbol_pipe" >&5 fi else echo "$progname: failed program was:" >&5 cat conftest.$ac_ext >&5 fi rm -rf conftest* conftst* # Do not use the global_symbol_pipe unless it works. if test yes = "$pipe_works"; then break else lt_cv_sys_global_symbol_pipe= fi done fi if test -z "$lt_cv_sys_global_symbol_pipe"; then lt_cv_sys_global_symbol_to_cdecl= fi if test -z "$lt_cv_sys_global_symbol_pipe$lt_cv_sys_global_symbol_to_cdecl"; then { $as_echo "$as_me:${as_lineno-$LINENO}: result: failed" >&5 $as_echo "failed" >&6; } else { $as_echo "$as_me:${as_lineno-$LINENO}: result: ok" >&5 $as_echo "ok" >&6; } fi # Response file support. if test "$lt_cv_nm_interface" = "MS dumpbin"; then nm_file_list_spec='@' elif $NM --help 2>/dev/null | grep '[@]FILE' >/dev/null; then nm_file_list_spec='@' fi { $as_echo "$as_me:${as_lineno-$LINENO}: checking for sysroot" >&5 $as_echo_n "checking for sysroot... " >&6; } # Check whether --with-sysroot was given. if test "${with_sysroot+set}" = set; then : withval=$with_sysroot; else with_sysroot=no fi lt_sysroot= case $with_sysroot in #( yes) if test yes = "$GCC"; then lt_sysroot=`$CC --print-sysroot 2>/dev/null` fi ;; #( /*) lt_sysroot=`echo "$with_sysroot" | sed -e "$sed_quote_subst"` ;; #( no|'') ;; #( *) { $as_echo "$as_me:${as_lineno-$LINENO}: result: $with_sysroot" >&5 $as_echo "$with_sysroot" >&6; } as_fn_error $? "The sysroot must be an absolute path." "$LINENO" 5 ;; esac { $as_echo "$as_me:${as_lineno-$LINENO}: result: ${lt_sysroot:-no}" >&5 $as_echo "${lt_sysroot:-no}" >&6; } { $as_echo "$as_me:${as_lineno-$LINENO}: checking for a working dd" >&5 $as_echo_n "checking for a working dd... " >&6; } if ${ac_cv_path_lt_DD+:} false; then : $as_echo_n "(cached) " >&6 else printf 0123456789abcdef0123456789abcdef >conftest.i cat conftest.i conftest.i >conftest2.i : ${lt_DD:=$DD} if test -z "$lt_DD"; then ac_path_lt_DD_found=false # Loop through the user's path and test for each of PROGNAME-LIST as_save_IFS=$IFS; IFS=$PATH_SEPARATOR for as_dir in $PATH do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_prog in dd; do for ac_exec_ext in '' $ac_executable_extensions; do ac_path_lt_DD="$as_dir/$ac_prog$ac_exec_ext" as_fn_executable_p "$ac_path_lt_DD" || continue if "$ac_path_lt_DD" bs=32 count=1 conftest.out 2>/dev/null; then cmp -s conftest.i conftest.out \ && ac_cv_path_lt_DD="$ac_path_lt_DD" ac_path_lt_DD_found=: fi $ac_path_lt_DD_found && break 3 done done done IFS=$as_save_IFS if test -z "$ac_cv_path_lt_DD"; then : fi else ac_cv_path_lt_DD=$lt_DD fi rm -f conftest.i conftest2.i conftest.out fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_path_lt_DD" >&5 $as_echo "$ac_cv_path_lt_DD" >&6; } { $as_echo "$as_me:${as_lineno-$LINENO}: checking how to truncate binary pipes" >&5 $as_echo_n "checking how to truncate binary pipes... " >&6; } if ${lt_cv_truncate_bin+:} false; then : $as_echo_n "(cached) " >&6 else printf 0123456789abcdef0123456789abcdef >conftest.i cat conftest.i conftest.i >conftest2.i lt_cv_truncate_bin= if "$ac_cv_path_lt_DD" bs=32 count=1 conftest.out 2>/dev/null; then cmp -s conftest.i conftest.out \ && lt_cv_truncate_bin="$ac_cv_path_lt_DD bs=4096 count=1" fi rm -f conftest.i conftest2.i conftest.out test -z "$lt_cv_truncate_bin" && lt_cv_truncate_bin="$SED -e 4q" fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $lt_cv_truncate_bin" >&5 $as_echo "$lt_cv_truncate_bin" >&6; } # Calculate cc_basename. Skip known compiler wrappers and cross-prefix. func_cc_basename () { for cc_temp in $*""; do case $cc_temp in compile | *[\\/]compile | ccache | *[\\/]ccache ) ;; distcc | *[\\/]distcc | purify | *[\\/]purify ) ;; \-*) ;; *) break;; esac done func_cc_basename_result=`$ECHO "$cc_temp" | $SED "s%.*/%%; s%^$host_alias-%%"` } # Check whether --enable-libtool-lock was given. if test "${enable_libtool_lock+set}" = set; then : enableval=$enable_libtool_lock; fi test no = "$enable_libtool_lock" || enable_libtool_lock=yes # Some flags need to be propagated to the compiler or linker for good # libtool support. case $host in ia64-*-hpux*) # Find out what ABI is being produced by ac_compile, and set mode # options accordingly. echo 'int i;' > conftest.$ac_ext if { { eval echo "\"\$as_me\":${as_lineno-$LINENO}: \"$ac_compile\""; } >&5 (eval $ac_compile) 2>&5 ac_status=$? $as_echo "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 test $ac_status = 0; }; then case `/usr/bin/file conftest.$ac_objext` in *ELF-32*) HPUX_IA64_MODE=32 ;; *ELF-64*) HPUX_IA64_MODE=64 ;; esac fi rm -rf conftest* ;; *-*-irix6*) # Find out what ABI is being produced by ac_compile, and set linker # options accordingly. echo '#line '$LINENO' "configure"' > conftest.$ac_ext if { { eval echo "\"\$as_me\":${as_lineno-$LINENO}: \"$ac_compile\""; } >&5 (eval $ac_compile) 2>&5 ac_status=$? $as_echo "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 test $ac_status = 0; }; then if test yes = "$lt_cv_prog_gnu_ld"; then case `/usr/bin/file conftest.$ac_objext` in *32-bit*) LD="${LD-ld} -melf32bsmip" ;; *N32*) LD="${LD-ld} -melf32bmipn32" ;; *64-bit*) LD="${LD-ld} -melf64bmip" ;; esac else case `/usr/bin/file conftest.$ac_objext` in *32-bit*) LD="${LD-ld} -32" ;; *N32*) LD="${LD-ld} -n32" ;; *64-bit*) LD="${LD-ld} -64" ;; esac fi fi rm -rf conftest* ;; mips64*-*linux*) # Find out what ABI is being produced by ac_compile, and set linker # options accordingly. echo '#line '$LINENO' "configure"' > conftest.$ac_ext if { { eval echo "\"\$as_me\":${as_lineno-$LINENO}: \"$ac_compile\""; } >&5 (eval $ac_compile) 2>&5 ac_status=$? $as_echo "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 test $ac_status = 0; }; then emul=elf case `/usr/bin/file conftest.$ac_objext` in *32-bit*) emul="${emul}32" ;; *64-bit*) emul="${emul}64" ;; esac case `/usr/bin/file conftest.$ac_objext` in *MSB*) emul="${emul}btsmip" ;; *LSB*) emul="${emul}ltsmip" ;; esac case `/usr/bin/file conftest.$ac_objext` in *N32*) emul="${emul}n32" ;; esac LD="${LD-ld} -m $emul" fi rm -rf conftest* ;; x86_64-*kfreebsd*-gnu|x86_64-*linux*|powerpc*-*linux*| \ s390*-*linux*|s390*-*tpf*|sparc*-*linux*) # Find out what ABI is being produced by ac_compile, and set linker # options accordingly. Note that the listed cases only cover the # situations where additional linker options are needed (such as when # doing 32-bit compilation for a host where ld defaults to 64-bit, or # vice versa); the common cases where no linker options are needed do # not appear in the list. echo 'int i;' > conftest.$ac_ext if { { eval echo "\"\$as_me\":${as_lineno-$LINENO}: \"$ac_compile\""; } >&5 (eval $ac_compile) 2>&5 ac_status=$? $as_echo "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 test $ac_status = 0; }; then case `/usr/bin/file conftest.o` in *32-bit*) case $host in x86_64-*kfreebsd*-gnu) LD="${LD-ld} -m elf_i386_fbsd" ;; x86_64-*linux*) case `/usr/bin/file conftest.o` in *x86-64*) LD="${LD-ld} -m elf32_x86_64" ;; *) LD="${LD-ld} -m elf_i386" ;; esac ;; powerpc64le-*linux*) LD="${LD-ld} -m elf32lppclinux" ;; powerpc64-*linux*) LD="${LD-ld} -m elf32ppclinux" ;; s390x-*linux*) LD="${LD-ld} -m elf_s390" ;; sparc64-*linux*) LD="${LD-ld} -m elf32_sparc" ;; esac ;; *64-bit*) case $host in x86_64-*kfreebsd*-gnu) LD="${LD-ld} -m elf_x86_64_fbsd" ;; x86_64-*linux*) LD="${LD-ld} -m elf_x86_64" ;; powerpcle-*linux*) LD="${LD-ld} -m elf64lppc" ;; powerpc-*linux*) LD="${LD-ld} -m elf64ppc" ;; s390*-*linux*|s390*-*tpf*) LD="${LD-ld} -m elf64_s390" ;; sparc*-*linux*) LD="${LD-ld} -m elf64_sparc" ;; esac ;; esac fi rm -rf conftest* ;; *-*-sco3.2v5*) # On SCO OpenServer 5, we need -belf to get full-featured binaries. SAVE_CFLAGS=$CFLAGS CFLAGS="$CFLAGS -belf" { $as_echo "$as_me:${as_lineno-$LINENO}: checking whether the C compiler needs -belf" >&5 $as_echo_n "checking whether the C compiler needs -belf... " >&6; } if ${lt_cv_cc_needs_belf+:} false; then : $as_echo_n "(cached) " >&6 else ac_ext=c ac_cpp='$CPP $CPPFLAGS' ac_compile='$CC -c $CFLAGS $CPPFLAGS conftest.$ac_ext >&5' ac_link='$CC -o conftest$ac_exeext $CFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS >&5' ac_compiler_gnu=$ac_cv_c_compiler_gnu cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ int main () { ; return 0; } _ACEOF if ac_fn_c_try_link "$LINENO"; then : lt_cv_cc_needs_belf=yes else lt_cv_cc_needs_belf=no fi rm -f core conftest.err conftest.$ac_objext \ conftest$ac_exeext conftest.$ac_ext ac_ext=c ac_cpp='$CPP $CPPFLAGS' ac_compile='$CC -c $CFLAGS $CPPFLAGS conftest.$ac_ext >&5' ac_link='$CC -o conftest$ac_exeext $CFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS >&5' ac_compiler_gnu=$ac_cv_c_compiler_gnu fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $lt_cv_cc_needs_belf" >&5 $as_echo "$lt_cv_cc_needs_belf" >&6; } if test yes != "$lt_cv_cc_needs_belf"; then # this is probably gcc 2.8.0, egcs 1.0 or newer; no need for -belf CFLAGS=$SAVE_CFLAGS fi ;; *-*solaris*) # Find out what ABI is being produced by ac_compile, and set linker # options accordingly. echo 'int i;' > conftest.$ac_ext if { { eval echo "\"\$as_me\":${as_lineno-$LINENO}: \"$ac_compile\""; } >&5 (eval $ac_compile) 2>&5 ac_status=$? $as_echo "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 test $ac_status = 0; }; then case `/usr/bin/file conftest.o` in *64-bit*) case $lt_cv_prog_gnu_ld in yes*) case $host in i?86-*-solaris*|x86_64-*-solaris*) LD="${LD-ld} -m elf_x86_64" ;; sparc*-*-solaris*) LD="${LD-ld} -m elf64_sparc" ;; esac # GNU ld 2.21 introduced _sol2 emulations. Use them if available. if ${LD-ld} -V | grep _sol2 >/dev/null 2>&1; then LD=${LD-ld}_sol2 fi ;; *) if ${LD-ld} -64 -r -o conftest2.o conftest.o >/dev/null 2>&1; then LD="${LD-ld} -64" fi ;; esac ;; esac fi rm -rf conftest* ;; esac need_locks=$enable_libtool_lock if test -n "$ac_tool_prefix"; then # Extract the first word of "${ac_tool_prefix}mt", so it can be a program name with args. set dummy ${ac_tool_prefix}mt; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } if ${ac_cv_prog_MANIFEST_TOOL+:} false; then : $as_echo_n "(cached) " >&6 else if test -n "$MANIFEST_TOOL"; then ac_cv_prog_MANIFEST_TOOL="$MANIFEST_TOOL" # Let the user override the test. else as_save_IFS=$IFS; IFS=$PATH_SEPARATOR for as_dir in $PATH do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_prog_MANIFEST_TOOL="${ac_tool_prefix}mt" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 fi done done IFS=$as_save_IFS fi fi MANIFEST_TOOL=$ac_cv_prog_MANIFEST_TOOL if test -n "$MANIFEST_TOOL"; then { $as_echo "$as_me:${as_lineno-$LINENO}: result: $MANIFEST_TOOL" >&5 $as_echo "$MANIFEST_TOOL" >&6; } else { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 $as_echo "no" >&6; } fi fi if test -z "$ac_cv_prog_MANIFEST_TOOL"; then ac_ct_MANIFEST_TOOL=$MANIFEST_TOOL # Extract the first word of "mt", so it can be a program name with args. set dummy mt; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } if ${ac_cv_prog_ac_ct_MANIFEST_TOOL+:} false; then : $as_echo_n "(cached) " >&6 else if test -n "$ac_ct_MANIFEST_TOOL"; then ac_cv_prog_ac_ct_MANIFEST_TOOL="$ac_ct_MANIFEST_TOOL" # Let the user override the test. else as_save_IFS=$IFS; IFS=$PATH_SEPARATOR for as_dir in $PATH do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_prog_ac_ct_MANIFEST_TOOL="mt" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 fi done done IFS=$as_save_IFS fi fi ac_ct_MANIFEST_TOOL=$ac_cv_prog_ac_ct_MANIFEST_TOOL if test -n "$ac_ct_MANIFEST_TOOL"; then { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_ct_MANIFEST_TOOL" >&5 $as_echo "$ac_ct_MANIFEST_TOOL" >&6; } else { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 $as_echo "no" >&6; } fi if test "x$ac_ct_MANIFEST_TOOL" = x; then MANIFEST_TOOL=":" else case $cross_compiling:$ac_tool_warned in yes:) { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: using cross tools not prefixed with host triplet" >&5 $as_echo "$as_me: WARNING: using cross tools not prefixed with host triplet" >&2;} ac_tool_warned=yes ;; esac MANIFEST_TOOL=$ac_ct_MANIFEST_TOOL fi else MANIFEST_TOOL="$ac_cv_prog_MANIFEST_TOOL" fi test -z "$MANIFEST_TOOL" && MANIFEST_TOOL=mt { $as_echo "$as_me:${as_lineno-$LINENO}: checking if $MANIFEST_TOOL is a manifest tool" >&5 $as_echo_n "checking if $MANIFEST_TOOL is a manifest tool... " >&6; } if ${lt_cv_path_mainfest_tool+:} false; then : $as_echo_n "(cached) " >&6 else lt_cv_path_mainfest_tool=no echo "$as_me:$LINENO: $MANIFEST_TOOL '-?'" >&5 $MANIFEST_TOOL '-?' 2>conftest.err > conftest.out cat conftest.err >&5 if $GREP 'Manifest Tool' conftest.out > /dev/null; then lt_cv_path_mainfest_tool=yes fi rm -f conftest* fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $lt_cv_path_mainfest_tool" >&5 $as_echo "$lt_cv_path_mainfest_tool" >&6; } if test yes != "$lt_cv_path_mainfest_tool"; then MANIFEST_TOOL=: fi case $host_os in rhapsody* | darwin*) if test -n "$ac_tool_prefix"; then # Extract the first word of "${ac_tool_prefix}dsymutil", so it can be a program name with args. set dummy ${ac_tool_prefix}dsymutil; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } if ${ac_cv_prog_DSYMUTIL+:} false; then : $as_echo_n "(cached) " >&6 else if test -n "$DSYMUTIL"; then ac_cv_prog_DSYMUTIL="$DSYMUTIL" # Let the user override the test. else as_save_IFS=$IFS; IFS=$PATH_SEPARATOR for as_dir in $PATH do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_prog_DSYMUTIL="${ac_tool_prefix}dsymutil" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 fi done done IFS=$as_save_IFS fi fi DSYMUTIL=$ac_cv_prog_DSYMUTIL if test -n "$DSYMUTIL"; then { $as_echo "$as_me:${as_lineno-$LINENO}: result: $DSYMUTIL" >&5 $as_echo "$DSYMUTIL" >&6; } else { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 $as_echo "no" >&6; } fi fi if test -z "$ac_cv_prog_DSYMUTIL"; then ac_ct_DSYMUTIL=$DSYMUTIL # Extract the first word of "dsymutil", so it can be a program name with args. set dummy dsymutil; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } if ${ac_cv_prog_ac_ct_DSYMUTIL+:} false; then : $as_echo_n "(cached) " >&6 else if test -n "$ac_ct_DSYMUTIL"; then ac_cv_prog_ac_ct_DSYMUTIL="$ac_ct_DSYMUTIL" # Let the user override the test. else as_save_IFS=$IFS; IFS=$PATH_SEPARATOR for as_dir in $PATH do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_prog_ac_ct_DSYMUTIL="dsymutil" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 fi done done IFS=$as_save_IFS fi fi ac_ct_DSYMUTIL=$ac_cv_prog_ac_ct_DSYMUTIL if test -n "$ac_ct_DSYMUTIL"; then { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_ct_DSYMUTIL" >&5 $as_echo "$ac_ct_DSYMUTIL" >&6; } else { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 $as_echo "no" >&6; } fi if test "x$ac_ct_DSYMUTIL" = x; then DSYMUTIL=":" else case $cross_compiling:$ac_tool_warned in yes:) { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: using cross tools not prefixed with host triplet" >&5 $as_echo "$as_me: WARNING: using cross tools not prefixed with host triplet" >&2;} ac_tool_warned=yes ;; esac DSYMUTIL=$ac_ct_DSYMUTIL fi else DSYMUTIL="$ac_cv_prog_DSYMUTIL" fi if test -n "$ac_tool_prefix"; then # Extract the first word of "${ac_tool_prefix}nmedit", so it can be a program name with args. set dummy ${ac_tool_prefix}nmedit; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } if ${ac_cv_prog_NMEDIT+:} false; then : $as_echo_n "(cached) " >&6 else if test -n "$NMEDIT"; then ac_cv_prog_NMEDIT="$NMEDIT" # Let the user override the test. else as_save_IFS=$IFS; IFS=$PATH_SEPARATOR for as_dir in $PATH do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_prog_NMEDIT="${ac_tool_prefix}nmedit" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 fi done done IFS=$as_save_IFS fi fi NMEDIT=$ac_cv_prog_NMEDIT if test -n "$NMEDIT"; then { $as_echo "$as_me:${as_lineno-$LINENO}: result: $NMEDIT" >&5 $as_echo "$NMEDIT" >&6; } else { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 $as_echo "no" >&6; } fi fi if test -z "$ac_cv_prog_NMEDIT"; then ac_ct_NMEDIT=$NMEDIT # Extract the first word of "nmedit", so it can be a program name with args. set dummy nmedit; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } if ${ac_cv_prog_ac_ct_NMEDIT+:} false; then : $as_echo_n "(cached) " >&6 else if test -n "$ac_ct_NMEDIT"; then ac_cv_prog_ac_ct_NMEDIT="$ac_ct_NMEDIT" # Let the user override the test. else as_save_IFS=$IFS; IFS=$PATH_SEPARATOR for as_dir in $PATH do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_prog_ac_ct_NMEDIT="nmedit" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 fi done done IFS=$as_save_IFS fi fi ac_ct_NMEDIT=$ac_cv_prog_ac_ct_NMEDIT if test -n "$ac_ct_NMEDIT"; then { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_ct_NMEDIT" >&5 $as_echo "$ac_ct_NMEDIT" >&6; } else { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 $as_echo "no" >&6; } fi if test "x$ac_ct_NMEDIT" = x; then NMEDIT=":" else case $cross_compiling:$ac_tool_warned in yes:) { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: using cross tools not prefixed with host triplet" >&5 $as_echo "$as_me: WARNING: using cross tools not prefixed with host triplet" >&2;} ac_tool_warned=yes ;; esac NMEDIT=$ac_ct_NMEDIT fi else NMEDIT="$ac_cv_prog_NMEDIT" fi if test -n "$ac_tool_prefix"; then # Extract the first word of "${ac_tool_prefix}lipo", so it can be a program name with args. set dummy ${ac_tool_prefix}lipo; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } if ${ac_cv_prog_LIPO+:} false; then : $as_echo_n "(cached) " >&6 else if test -n "$LIPO"; then ac_cv_prog_LIPO="$LIPO" # Let the user override the test. else as_save_IFS=$IFS; IFS=$PATH_SEPARATOR for as_dir in $PATH do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_prog_LIPO="${ac_tool_prefix}lipo" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 fi done done IFS=$as_save_IFS fi fi LIPO=$ac_cv_prog_LIPO if test -n "$LIPO"; then { $as_echo "$as_me:${as_lineno-$LINENO}: result: $LIPO" >&5 $as_echo "$LIPO" >&6; } else { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 $as_echo "no" >&6; } fi fi if test -z "$ac_cv_prog_LIPO"; then ac_ct_LIPO=$LIPO # Extract the first word of "lipo", so it can be a program name with args. set dummy lipo; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } if ${ac_cv_prog_ac_ct_LIPO+:} false; then : $as_echo_n "(cached) " >&6 else if test -n "$ac_ct_LIPO"; then ac_cv_prog_ac_ct_LIPO="$ac_ct_LIPO" # Let the user override the test. else as_save_IFS=$IFS; IFS=$PATH_SEPARATOR for as_dir in $PATH do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_prog_ac_ct_LIPO="lipo" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 fi done done IFS=$as_save_IFS fi fi ac_ct_LIPO=$ac_cv_prog_ac_ct_LIPO if test -n "$ac_ct_LIPO"; then { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_ct_LIPO" >&5 $as_echo "$ac_ct_LIPO" >&6; } else { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 $as_echo "no" >&6; } fi if test "x$ac_ct_LIPO" = x; then LIPO=":" else case $cross_compiling:$ac_tool_warned in yes:) { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: using cross tools not prefixed with host triplet" >&5 $as_echo "$as_me: WARNING: using cross tools not prefixed with host triplet" >&2;} ac_tool_warned=yes ;; esac LIPO=$ac_ct_LIPO fi else LIPO="$ac_cv_prog_LIPO" fi if test -n "$ac_tool_prefix"; then # Extract the first word of "${ac_tool_prefix}otool", so it can be a program name with args. set dummy ${ac_tool_prefix}otool; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } if ${ac_cv_prog_OTOOL+:} false; then : $as_echo_n "(cached) " >&6 else if test -n "$OTOOL"; then ac_cv_prog_OTOOL="$OTOOL" # Let the user override the test. else as_save_IFS=$IFS; IFS=$PATH_SEPARATOR for as_dir in $PATH do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_prog_OTOOL="${ac_tool_prefix}otool" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 fi done done IFS=$as_save_IFS fi fi OTOOL=$ac_cv_prog_OTOOL if test -n "$OTOOL"; then { $as_echo "$as_me:${as_lineno-$LINENO}: result: $OTOOL" >&5 $as_echo "$OTOOL" >&6; } else { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 $as_echo "no" >&6; } fi fi if test -z "$ac_cv_prog_OTOOL"; then ac_ct_OTOOL=$OTOOL # Extract the first word of "otool", so it can be a program name with args. set dummy otool; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } if ${ac_cv_prog_ac_ct_OTOOL+:} false; then : $as_echo_n "(cached) " >&6 else if test -n "$ac_ct_OTOOL"; then ac_cv_prog_ac_ct_OTOOL="$ac_ct_OTOOL" # Let the user override the test. else as_save_IFS=$IFS; IFS=$PATH_SEPARATOR for as_dir in $PATH do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_prog_ac_ct_OTOOL="otool" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 fi done done IFS=$as_save_IFS fi fi ac_ct_OTOOL=$ac_cv_prog_ac_ct_OTOOL if test -n "$ac_ct_OTOOL"; then { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_ct_OTOOL" >&5 $as_echo "$ac_ct_OTOOL" >&6; } else { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 $as_echo "no" >&6; } fi if test "x$ac_ct_OTOOL" = x; then OTOOL=":" else case $cross_compiling:$ac_tool_warned in yes:) { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: using cross tools not prefixed with host triplet" >&5 $as_echo "$as_me: WARNING: using cross tools not prefixed with host triplet" >&2;} ac_tool_warned=yes ;; esac OTOOL=$ac_ct_OTOOL fi else OTOOL="$ac_cv_prog_OTOOL" fi if test -n "$ac_tool_prefix"; then # Extract the first word of "${ac_tool_prefix}otool64", so it can be a program name with args. set dummy ${ac_tool_prefix}otool64; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } if ${ac_cv_prog_OTOOL64+:} false; then : $as_echo_n "(cached) " >&6 else if test -n "$OTOOL64"; then ac_cv_prog_OTOOL64="$OTOOL64" # Let the user override the test. else as_save_IFS=$IFS; IFS=$PATH_SEPARATOR for as_dir in $PATH do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_prog_OTOOL64="${ac_tool_prefix}otool64" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 fi done done IFS=$as_save_IFS fi fi OTOOL64=$ac_cv_prog_OTOOL64 if test -n "$OTOOL64"; then { $as_echo "$as_me:${as_lineno-$LINENO}: result: $OTOOL64" >&5 $as_echo "$OTOOL64" >&6; } else { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 $as_echo "no" >&6; } fi fi if test -z "$ac_cv_prog_OTOOL64"; then ac_ct_OTOOL64=$OTOOL64 # Extract the first word of "otool64", so it can be a program name with args. set dummy otool64; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } if ${ac_cv_prog_ac_ct_OTOOL64+:} false; then : $as_echo_n "(cached) " >&6 else if test -n "$ac_ct_OTOOL64"; then ac_cv_prog_ac_ct_OTOOL64="$ac_ct_OTOOL64" # Let the user override the test. else as_save_IFS=$IFS; IFS=$PATH_SEPARATOR for as_dir in $PATH do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_prog_ac_ct_OTOOL64="otool64" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 fi done done IFS=$as_save_IFS fi fi ac_ct_OTOOL64=$ac_cv_prog_ac_ct_OTOOL64 if test -n "$ac_ct_OTOOL64"; then { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_ct_OTOOL64" >&5 $as_echo "$ac_ct_OTOOL64" >&6; } else { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 $as_echo "no" >&6; } fi if test "x$ac_ct_OTOOL64" = x; then OTOOL64=":" else case $cross_compiling:$ac_tool_warned in yes:) { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: using cross tools not prefixed with host triplet" >&5 $as_echo "$as_me: WARNING: using cross tools not prefixed with host triplet" >&2;} ac_tool_warned=yes ;; esac OTOOL64=$ac_ct_OTOOL64 fi else OTOOL64="$ac_cv_prog_OTOOL64" fi { $as_echo "$as_me:${as_lineno-$LINENO}: checking for -single_module linker flag" >&5 $as_echo_n "checking for -single_module linker flag... " >&6; } if ${lt_cv_apple_cc_single_mod+:} false; then : $as_echo_n "(cached) " >&6 else lt_cv_apple_cc_single_mod=no if test -z "$LT_MULTI_MODULE"; then # By default we will add the -single_module flag. You can override # by either setting the environment variable LT_MULTI_MODULE # non-empty at configure time, or by adding -multi_module to the # link flags. rm -rf libconftest.dylib* echo "int foo(void){return 1;}" > conftest.c echo "$LTCC $LTCFLAGS $LDFLAGS -o libconftest.dylib \ -dynamiclib -Wl,-single_module conftest.c" >&5 $LTCC $LTCFLAGS $LDFLAGS -o libconftest.dylib \ -dynamiclib -Wl,-single_module conftest.c 2>conftest.err _lt_result=$? # If there is a non-empty error log, and "single_module" # appears in it, assume the flag caused a linker warning if test -s conftest.err && $GREP single_module conftest.err; then cat conftest.err >&5 # Otherwise, if the output was created with a 0 exit code from # the compiler, it worked. elif test -f libconftest.dylib && test 0 = "$_lt_result"; then lt_cv_apple_cc_single_mod=yes else cat conftest.err >&5 fi rm -rf libconftest.dylib* rm -f conftest.* fi fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $lt_cv_apple_cc_single_mod" >&5 $as_echo "$lt_cv_apple_cc_single_mod" >&6; } { $as_echo "$as_me:${as_lineno-$LINENO}: checking for -exported_symbols_list linker flag" >&5 $as_echo_n "checking for -exported_symbols_list linker flag... " >&6; } if ${lt_cv_ld_exported_symbols_list+:} false; then : $as_echo_n "(cached) " >&6 else lt_cv_ld_exported_symbols_list=no save_LDFLAGS=$LDFLAGS echo "_main" > conftest.sym LDFLAGS="$LDFLAGS -Wl,-exported_symbols_list,conftest.sym" cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ int main () { ; return 0; } _ACEOF if ac_fn_c_try_link "$LINENO"; then : lt_cv_ld_exported_symbols_list=yes else lt_cv_ld_exported_symbols_list=no fi rm -f core conftest.err conftest.$ac_objext \ conftest$ac_exeext conftest.$ac_ext LDFLAGS=$save_LDFLAGS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $lt_cv_ld_exported_symbols_list" >&5 $as_echo "$lt_cv_ld_exported_symbols_list" >&6; } { $as_echo "$as_me:${as_lineno-$LINENO}: checking for -force_load linker flag" >&5 $as_echo_n "checking for -force_load linker flag... " >&6; } if ${lt_cv_ld_force_load+:} false; then : $as_echo_n "(cached) " >&6 else lt_cv_ld_force_load=no cat > conftest.c << _LT_EOF int forced_loaded() { return 2;} _LT_EOF echo "$LTCC $LTCFLAGS -c -o conftest.o conftest.c" >&5 $LTCC $LTCFLAGS -c -o conftest.o conftest.c 2>&5 echo "$AR cru libconftest.a conftest.o" >&5 $AR cru libconftest.a conftest.o 2>&5 echo "$RANLIB libconftest.a" >&5 $RANLIB libconftest.a 2>&5 cat > conftest.c << _LT_EOF int main() { return 0;} _LT_EOF echo "$LTCC $LTCFLAGS $LDFLAGS -o conftest conftest.c -Wl,-force_load,./libconftest.a" >&5 $LTCC $LTCFLAGS $LDFLAGS -o conftest conftest.c -Wl,-force_load,./libconftest.a 2>conftest.err _lt_result=$? if test -s conftest.err && $GREP force_load conftest.err; then cat conftest.err >&5 elif test -f conftest && test 0 = "$_lt_result" && $GREP forced_load conftest >/dev/null 2>&1; then lt_cv_ld_force_load=yes else cat conftest.err >&5 fi rm -f conftest.err libconftest.a conftest conftest.c rm -rf conftest.dSYM fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $lt_cv_ld_force_load" >&5 $as_echo "$lt_cv_ld_force_load" >&6; } case $host_os in rhapsody* | darwin1.[012]) _lt_dar_allow_undefined='$wl-undefined ${wl}suppress' ;; darwin1.*) _lt_dar_allow_undefined='$wl-flat_namespace $wl-undefined ${wl}suppress' ;; darwin*) # darwin 5.x on # if running on 10.5 or later, the deployment target defaults # to the OS version, if on x86, and 10.4, the deployment # target defaults to 10.4. Don't you love it? case ${MACOSX_DEPLOYMENT_TARGET-10.0},$host in 10.0,*86*-darwin8*|10.0,*-darwin[91]*) _lt_dar_allow_undefined='$wl-undefined ${wl}dynamic_lookup' ;; 10.[012][,.]*) _lt_dar_allow_undefined='$wl-flat_namespace $wl-undefined ${wl}suppress' ;; 10.*) _lt_dar_allow_undefined='$wl-undefined ${wl}dynamic_lookup' ;; esac ;; esac if test yes = "$lt_cv_apple_cc_single_mod"; then _lt_dar_single_mod='$single_module' fi if test yes = "$lt_cv_ld_exported_symbols_list"; then _lt_dar_export_syms=' $wl-exported_symbols_list,$output_objdir/$libname-symbols.expsym' else _lt_dar_export_syms='~$NMEDIT -s $output_objdir/$libname-symbols.expsym $lib' fi if test : != "$DSYMUTIL" && test no = "$lt_cv_ld_force_load"; then _lt_dsymutil='~$DSYMUTIL $lib || :' else _lt_dsymutil= fi ;; esac # func_munge_path_list VARIABLE PATH # ----------------------------------- # VARIABLE is name of variable containing _space_ separated list of # directories to be munged by the contents of PATH, which is string # having a format: # "DIR[:DIR]:" # string "DIR[ DIR]" will be prepended to VARIABLE # ":DIR[:DIR]" # string "DIR[ DIR]" will be appended to VARIABLE # "DIRP[:DIRP]::[DIRA:]DIRA" # string "DIRP[ DIRP]" will be prepended to VARIABLE and string # "DIRA[ DIRA]" will be appended to VARIABLE # "DIR[:DIR]" # VARIABLE will be replaced by "DIR[ DIR]" func_munge_path_list () { case x$2 in x) ;; *:) eval $1=\"`$ECHO $2 | $SED 's/:/ /g'` \$$1\" ;; x:*) eval $1=\"\$$1 `$ECHO $2 | $SED 's/:/ /g'`\" ;; *::*) eval $1=\"\$$1\ `$ECHO $2 | $SED -e 's/.*:://' -e 's/:/ /g'`\" eval $1=\"`$ECHO $2 | $SED -e 's/::.*//' -e 's/:/ /g'`\ \$$1\" ;; *) eval $1=\"`$ECHO $2 | $SED 's/:/ /g'`\" ;; esac } for ac_header in dlfcn.h do : ac_fn_c_check_header_compile "$LINENO" "dlfcn.h" "ac_cv_header_dlfcn_h" "$ac_includes_default " if test "x$ac_cv_header_dlfcn_h" = xyes; then : cat >>confdefs.h <<_ACEOF #define HAVE_DLFCN_H 1 _ACEOF fi done # Set options # Check whether --enable-static was given. if test "${enable_static+set}" = set; then : enableval=$enable_static; p=${PACKAGE-default} case $enableval in yes) enable_static=yes ;; no) enable_static=no ;; *) enable_static=no # Look at the argument we got. We use all the common list separators. lt_save_ifs=$IFS; IFS=$IFS$PATH_SEPARATOR, for pkg in $enableval; do IFS=$lt_save_ifs if test "X$pkg" = "X$p"; then enable_static=yes fi done IFS=$lt_save_ifs ;; esac else enable_static=no fi enable_dlopen=no enable_win32_dll=no # Check whether --enable-shared was given. if test "${enable_shared+set}" = set; then : enableval=$enable_shared; p=${PACKAGE-default} case $enableval in yes) enable_shared=yes ;; no) enable_shared=no ;; *) enable_shared=no # Look at the argument we got. We use all the common list separators. lt_save_ifs=$IFS; IFS=$IFS$PATH_SEPARATOR, for pkg in $enableval; do IFS=$lt_save_ifs if test "X$pkg" = "X$p"; then enable_shared=yes fi done IFS=$lt_save_ifs ;; esac else enable_shared=yes fi # Check whether --with-pic was given. if test "${with_pic+set}" = set; then : withval=$with_pic; lt_p=${PACKAGE-default} case $withval in yes|no) pic_mode=$withval ;; *) pic_mode=default # Look at the argument we got. We use all the common list separators. lt_save_ifs=$IFS; IFS=$IFS$PATH_SEPARATOR, for lt_pkg in $withval; do IFS=$lt_save_ifs if test "X$lt_pkg" = "X$lt_p"; then pic_mode=yes fi done IFS=$lt_save_ifs ;; esac else pic_mode=default fi # Check whether --enable-fast-install was given. if test "${enable_fast_install+set}" = set; then : enableval=$enable_fast_install; p=${PACKAGE-default} case $enableval in yes) enable_fast_install=yes ;; no) enable_fast_install=no ;; *) enable_fast_install=no # Look at the argument we got. We use all the common list separators. lt_save_ifs=$IFS; IFS=$IFS$PATH_SEPARATOR, for pkg in $enableval; do IFS=$lt_save_ifs if test "X$pkg" = "X$p"; then enable_fast_install=yes fi done IFS=$lt_save_ifs ;; esac else enable_fast_install=yes fi shared_archive_member_spec= case $host,$enable_shared in power*-*-aix[5-9]*,yes) { $as_echo "$as_me:${as_lineno-$LINENO}: checking which variant of shared library versioning to provide" >&5 $as_echo_n "checking which variant of shared library versioning to provide... " >&6; } # Check whether --with-aix-soname was given. if test "${with_aix_soname+set}" = set; then : withval=$with_aix_soname; case $withval in aix|svr4|both) ;; *) as_fn_error $? "Unknown argument to --with-aix-soname" "$LINENO" 5 ;; esac lt_cv_with_aix_soname=$with_aix_soname else if ${lt_cv_with_aix_soname+:} false; then : $as_echo_n "(cached) " >&6 else lt_cv_with_aix_soname=aix fi with_aix_soname=$lt_cv_with_aix_soname fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $with_aix_soname" >&5 $as_echo "$with_aix_soname" >&6; } if test aix != "$with_aix_soname"; then # For the AIX way of multilib, we name the shared archive member # based on the bitwidth used, traditionally 'shr.o' or 'shr_64.o', # and 'shr.imp' or 'shr_64.imp', respectively, for the Import File. # Even when GNU compilers ignore OBJECT_MODE but need '-maix64' flag, # the AIX toolchain works better with OBJECT_MODE set (default 32). if test 64 = "${OBJECT_MODE-32}"; then shared_archive_member_spec=shr_64 else shared_archive_member_spec=shr fi fi ;; *) with_aix_soname=aix ;; esac # This can be used to rebuild libtool when needed LIBTOOL_DEPS=$ltmain # Always use our own libtool. LIBTOOL='$(SHELL) $(top_builddir)/libtool' test -z "$LN_S" && LN_S="ln -s" if test -n "${ZSH_VERSION+set}"; then setopt NO_GLOB_SUBST fi { $as_echo "$as_me:${as_lineno-$LINENO}: checking for objdir" >&5 $as_echo_n "checking for objdir... " >&6; } if ${lt_cv_objdir+:} false; then : $as_echo_n "(cached) " >&6 else rm -f .libs 2>/dev/null mkdir .libs 2>/dev/null if test -d .libs; then lt_cv_objdir=.libs else # MS-DOS does not allow filenames that begin with a dot. lt_cv_objdir=_libs fi rmdir .libs 2>/dev/null fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $lt_cv_objdir" >&5 $as_echo "$lt_cv_objdir" >&6; } objdir=$lt_cv_objdir cat >>confdefs.h <<_ACEOF #define LT_OBJDIR "$lt_cv_objdir/" _ACEOF case $host_os in aix3*) # AIX sometimes has problems with the GCC collect2 program. For some # reason, if we set the COLLECT_NAMES environment variable, the problems # vanish in a puff of smoke. if test set != "${COLLECT_NAMES+set}"; then COLLECT_NAMES= export COLLECT_NAMES fi ;; esac # Global variables: ofile=libtool can_build_shared=yes # All known linkers require a '.a' archive for static linking (except MSVC, # which needs '.lib'). libext=a with_gnu_ld=$lt_cv_prog_gnu_ld old_CC=$CC old_CFLAGS=$CFLAGS # Set sane defaults for various variables test -z "$CC" && CC=cc test -z "$LTCC" && LTCC=$CC test -z "$LTCFLAGS" && LTCFLAGS=$CFLAGS test -z "$LD" && LD=ld test -z "$ac_objext" && ac_objext=o func_cc_basename $compiler cc_basename=$func_cc_basename_result # Only perform the check for file, if the check method requires it test -z "$MAGIC_CMD" && MAGIC_CMD=file case $deplibs_check_method in file_magic*) if test "$file_magic_cmd" = '$MAGIC_CMD'; then { $as_echo "$as_me:${as_lineno-$LINENO}: checking for ${ac_tool_prefix}file" >&5 $as_echo_n "checking for ${ac_tool_prefix}file... " >&6; } if ${lt_cv_path_MAGIC_CMD+:} false; then : $as_echo_n "(cached) " >&6 else case $MAGIC_CMD in [\\/*] | ?:[\\/]*) lt_cv_path_MAGIC_CMD=$MAGIC_CMD # Let the user override the test with a path. ;; *) lt_save_MAGIC_CMD=$MAGIC_CMD lt_save_ifs=$IFS; IFS=$PATH_SEPARATOR ac_dummy="/usr/bin$PATH_SEPARATOR$PATH" for ac_dir in $ac_dummy; do IFS=$lt_save_ifs test -z "$ac_dir" && ac_dir=. if test -f "$ac_dir/${ac_tool_prefix}file"; then lt_cv_path_MAGIC_CMD=$ac_dir/"${ac_tool_prefix}file" if test -n "$file_magic_test_file"; then case $deplibs_check_method in "file_magic "*) file_magic_regex=`expr "$deplibs_check_method" : "file_magic \(.*\)"` MAGIC_CMD=$lt_cv_path_MAGIC_CMD if eval $file_magic_cmd \$file_magic_test_file 2> /dev/null | $EGREP "$file_magic_regex" > /dev/null; then : else cat <<_LT_EOF 1>&2 *** Warning: the command libtool uses to detect shared libraries, *** $file_magic_cmd, produces output that libtool cannot recognize. *** The result is that libtool may fail to recognize shared libraries *** as such. This will affect the creation of libtool libraries that *** depend on shared libraries, but programs linked with such libtool *** libraries will work regardless of this problem. Nevertheless, you *** may want to report the problem to your system manager and/or to *** bug-libtool@gnu.org _LT_EOF fi ;; esac fi break fi done IFS=$lt_save_ifs MAGIC_CMD=$lt_save_MAGIC_CMD ;; esac fi MAGIC_CMD=$lt_cv_path_MAGIC_CMD if test -n "$MAGIC_CMD"; then { $as_echo "$as_me:${as_lineno-$LINENO}: result: $MAGIC_CMD" >&5 $as_echo "$MAGIC_CMD" >&6; } else { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 $as_echo "no" >&6; } fi if test -z "$lt_cv_path_MAGIC_CMD"; then if test -n "$ac_tool_prefix"; then { $as_echo "$as_me:${as_lineno-$LINENO}: checking for file" >&5 $as_echo_n "checking for file... " >&6; } if ${lt_cv_path_MAGIC_CMD+:} false; then : $as_echo_n "(cached) " >&6 else case $MAGIC_CMD in [\\/*] | ?:[\\/]*) lt_cv_path_MAGIC_CMD=$MAGIC_CMD # Let the user override the test with a path. ;; *) lt_save_MAGIC_CMD=$MAGIC_CMD lt_save_ifs=$IFS; IFS=$PATH_SEPARATOR ac_dummy="/usr/bin$PATH_SEPARATOR$PATH" for ac_dir in $ac_dummy; do IFS=$lt_save_ifs test -z "$ac_dir" && ac_dir=. if test -f "$ac_dir/file"; then lt_cv_path_MAGIC_CMD=$ac_dir/"file" if test -n "$file_magic_test_file"; then case $deplibs_check_method in "file_magic "*) file_magic_regex=`expr "$deplibs_check_method" : "file_magic \(.*\)"` MAGIC_CMD=$lt_cv_path_MAGIC_CMD if eval $file_magic_cmd \$file_magic_test_file 2> /dev/null | $EGREP "$file_magic_regex" > /dev/null; then : else cat <<_LT_EOF 1>&2 *** Warning: the command libtool uses to detect shared libraries, *** $file_magic_cmd, produces output that libtool cannot recognize. *** The result is that libtool may fail to recognize shared libraries *** as such. This will affect the creation of libtool libraries that *** depend on shared libraries, but programs linked with such libtool *** libraries will work regardless of this problem. Nevertheless, you *** may want to report the problem to your system manager and/or to *** bug-libtool@gnu.org _LT_EOF fi ;; esac fi break fi done IFS=$lt_save_ifs MAGIC_CMD=$lt_save_MAGIC_CMD ;; esac fi MAGIC_CMD=$lt_cv_path_MAGIC_CMD if test -n "$MAGIC_CMD"; then { $as_echo "$as_me:${as_lineno-$LINENO}: result: $MAGIC_CMD" >&5 $as_echo "$MAGIC_CMD" >&6; } else { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 $as_echo "no" >&6; } fi else MAGIC_CMD=: fi fi fi ;; esac # Use C for the default configuration in the libtool script lt_save_CC=$CC ac_ext=c ac_cpp='$CPP $CPPFLAGS' ac_compile='$CC -c $CFLAGS $CPPFLAGS conftest.$ac_ext >&5' ac_link='$CC -o conftest$ac_exeext $CFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS >&5' ac_compiler_gnu=$ac_cv_c_compiler_gnu # Source file extension for C test sources. ac_ext=c # Object file extension for compiled C test sources. objext=o objext=$objext # Code to be used in simple compile tests lt_simple_compile_test_code="int some_variable = 0;" # Code to be used in simple link tests lt_simple_link_test_code='int main(){return(0);}' # If no C compiler was specified, use CC. LTCC=${LTCC-"$CC"} # If no C compiler flags were specified, use CFLAGS. LTCFLAGS=${LTCFLAGS-"$CFLAGS"} # Allow CC to be a program name with arguments. compiler=$CC # Save the default compiler, since it gets overwritten when the other # tags are being tested, and _LT_TAGVAR(compiler, []) is a NOP. compiler_DEFAULT=$CC # save warnings/boilerplate of simple test code ac_outfile=conftest.$ac_objext echo "$lt_simple_compile_test_code" >conftest.$ac_ext eval "$ac_compile" 2>&1 >/dev/null | $SED '/^$/d; /^ *+/d' >conftest.err _lt_compiler_boilerplate=`cat conftest.err` $RM conftest* ac_outfile=conftest.$ac_objext echo "$lt_simple_link_test_code" >conftest.$ac_ext eval "$ac_link" 2>&1 >/dev/null | $SED '/^$/d; /^ *+/d' >conftest.err _lt_linker_boilerplate=`cat conftest.err` $RM -r conftest* ## CAVEAT EMPTOR: ## There is no encapsulation within the following macros, do not change ## the running order or otherwise move them around unless you know exactly ## what you are doing... if test -n "$compiler"; then lt_prog_compiler_no_builtin_flag= if test yes = "$GCC"; then case $cc_basename in nvcc*) lt_prog_compiler_no_builtin_flag=' -Xcompiler -fno-builtin' ;; *) lt_prog_compiler_no_builtin_flag=' -fno-builtin' ;; esac { $as_echo "$as_me:${as_lineno-$LINENO}: checking if $compiler supports -fno-rtti -fno-exceptions" >&5 $as_echo_n "checking if $compiler supports -fno-rtti -fno-exceptions... " >&6; } if ${lt_cv_prog_compiler_rtti_exceptions+:} false; then : $as_echo_n "(cached) " >&6 else lt_cv_prog_compiler_rtti_exceptions=no ac_outfile=conftest.$ac_objext echo "$lt_simple_compile_test_code" > conftest.$ac_ext lt_compiler_flag="-fno-rtti -fno-exceptions" ## exclude from sc_useless_quotes_in_assignment # Insert the option either (1) after the last *FLAGS variable, or # (2) before a word containing "conftest.", or (3) at the end. # Note that $ac_compile itself does not contain backslashes and begins # with a dollar sign (not a hyphen), so the echo should work correctly. # The option is referenced via a variable to avoid confusing sed. lt_compile=`echo "$ac_compile" | $SED \ -e 's:.*FLAGS}\{0,1\} :&$lt_compiler_flag :; t' \ -e 's: [^ ]*conftest\.: $lt_compiler_flag&:; t' \ -e 's:$: $lt_compiler_flag:'` (eval echo "\"\$as_me:$LINENO: $lt_compile\"" >&5) (eval "$lt_compile" 2>conftest.err) ac_status=$? cat conftest.err >&5 echo "$as_me:$LINENO: \$? = $ac_status" >&5 if (exit $ac_status) && test -s "$ac_outfile"; then # The compiler can only warn and ignore the option if not recognized # So say no if there are warnings other than the usual output. $ECHO "$_lt_compiler_boilerplate" | $SED '/^$/d' >conftest.exp $SED '/^$/d; /^ *+/d' conftest.err >conftest.er2 if test ! -s conftest.er2 || diff conftest.exp conftest.er2 >/dev/null; then lt_cv_prog_compiler_rtti_exceptions=yes fi fi $RM conftest* fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $lt_cv_prog_compiler_rtti_exceptions" >&5 $as_echo "$lt_cv_prog_compiler_rtti_exceptions" >&6; } if test yes = "$lt_cv_prog_compiler_rtti_exceptions"; then lt_prog_compiler_no_builtin_flag="$lt_prog_compiler_no_builtin_flag -fno-rtti -fno-exceptions" else : fi fi lt_prog_compiler_wl= lt_prog_compiler_pic= lt_prog_compiler_static= if test yes = "$GCC"; then lt_prog_compiler_wl='-Wl,' lt_prog_compiler_static='-static' case $host_os in aix*) # All AIX code is PIC. if test ia64 = "$host_cpu"; then # AIX 5 now supports IA64 processor lt_prog_compiler_static='-Bstatic' fi lt_prog_compiler_pic='-fPIC' ;; amigaos*) case $host_cpu in powerpc) # see comment about AmigaOS4 .so support lt_prog_compiler_pic='-fPIC' ;; m68k) # FIXME: we need at least 68020 code to build shared libraries, but # adding the '-m68020' flag to GCC prevents building anything better, # like '-m68040'. lt_prog_compiler_pic='-m68020 -resident32 -malways-restore-a4' ;; esac ;; beos* | irix5* | irix6* | nonstopux* | osf3* | osf4* | osf5*) # PIC is the default for these OSes. ;; mingw* | cygwin* | pw32* | os2* | cegcc*) # This hack is so that the source file can tell whether it is being # built for inclusion in a dll (and should export symbols for example). # Although the cygwin gcc ignores -fPIC, still need this for old-style # (--disable-auto-import) libraries lt_prog_compiler_pic='-DDLL_EXPORT' case $host_os in os2*) lt_prog_compiler_static='$wl-static' ;; esac ;; darwin* | rhapsody*) # PIC is the default on this platform # Common symbols not allowed in MH_DYLIB files lt_prog_compiler_pic='-fno-common' ;; haiku*) # PIC is the default for Haiku. # The "-static" flag exists, but is broken. lt_prog_compiler_static= ;; hpux*) # PIC is the default for 64-bit PA HP-UX, but not for 32-bit # PA HP-UX. On IA64 HP-UX, PIC is the default but the pic flag # sets the default TLS model and affects inlining. case $host_cpu in hppa*64*) # +Z the default ;; *) lt_prog_compiler_pic='-fPIC' ;; esac ;; interix[3-9]*) # Interix 3.x gcc -fpic/-fPIC options generate broken code. # Instead, we relocate shared libraries at runtime. ;; msdosdjgpp*) # Just because we use GCC doesn't mean we suddenly get shared libraries # on systems that don't support them. lt_prog_compiler_can_build_shared=no enable_shared=no ;; *nto* | *qnx*) # QNX uses GNU C++, but need to define -shared option too, otherwise # it will coredump. lt_prog_compiler_pic='-fPIC -shared' ;; sysv4*MP*) if test -d /usr/nec; then lt_prog_compiler_pic=-Kconform_pic fi ;; *) lt_prog_compiler_pic='-fPIC' ;; esac case $cc_basename in nvcc*) # Cuda Compiler Driver 2.2 lt_prog_compiler_wl='-Xlinker ' if test -n "$lt_prog_compiler_pic"; then lt_prog_compiler_pic="-Xcompiler $lt_prog_compiler_pic" fi ;; esac else # PORTME Check for flag to pass linker flags through the system compiler. case $host_os in aix*) lt_prog_compiler_wl='-Wl,' if test ia64 = "$host_cpu"; then # AIX 5 now supports IA64 processor lt_prog_compiler_static='-Bstatic' else lt_prog_compiler_static='-bnso -bI:/lib/syscalls.exp' fi ;; darwin* | rhapsody*) # PIC is the default on this platform # Common symbols not allowed in MH_DYLIB files lt_prog_compiler_pic='-fno-common' case $cc_basename in nagfor*) # NAG Fortran compiler lt_prog_compiler_wl='-Wl,-Wl,,' lt_prog_compiler_pic='-PIC' lt_prog_compiler_static='-Bstatic' ;; esac ;; mingw* | cygwin* | pw32* | os2* | cegcc*) # This hack is so that the source file can tell whether it is being # built for inclusion in a dll (and should export symbols for example). lt_prog_compiler_pic='-DDLL_EXPORT' case $host_os in os2*) lt_prog_compiler_static='$wl-static' ;; esac ;; hpux9* | hpux10* | hpux11*) lt_prog_compiler_wl='-Wl,' # PIC is the default for IA64 HP-UX and 64-bit HP-UX, but # not for PA HP-UX. case $host_cpu in hppa*64*|ia64*) # +Z the default ;; *) lt_prog_compiler_pic='+Z' ;; esac # Is there a better lt_prog_compiler_static that works with the bundled CC? lt_prog_compiler_static='$wl-a ${wl}archive' ;; irix5* | irix6* | nonstopux*) lt_prog_compiler_wl='-Wl,' # PIC (with -KPIC) is the default. lt_prog_compiler_static='-non_shared' ;; linux* | k*bsd*-gnu | kopensolaris*-gnu | gnu*) case $cc_basename in # old Intel for x86_64, which still supported -KPIC. ecc*) lt_prog_compiler_wl='-Wl,' lt_prog_compiler_pic='-KPIC' lt_prog_compiler_static='-static' ;; # icc used to be incompatible with GCC. # ICC 10 doesn't accept -KPIC any more. icc* | ifort*) lt_prog_compiler_wl='-Wl,' lt_prog_compiler_pic='-fPIC' lt_prog_compiler_static='-static' ;; # Lahey Fortran 8.1. lf95*) lt_prog_compiler_wl='-Wl,' lt_prog_compiler_pic='--shared' lt_prog_compiler_static='--static' ;; nagfor*) # NAG Fortran compiler lt_prog_compiler_wl='-Wl,-Wl,,' lt_prog_compiler_pic='-PIC' lt_prog_compiler_static='-Bstatic' ;; tcc*) # Fabrice Bellard et al's Tiny C Compiler lt_prog_compiler_wl='-Wl,' lt_prog_compiler_pic='-fPIC' lt_prog_compiler_static='-static' ;; pgcc* | pgf77* | pgf90* | pgf95* | pgfortran*) # Portland Group compilers (*not* the Pentium gcc compiler, # which looks to be a dead project) lt_prog_compiler_wl='-Wl,' lt_prog_compiler_pic='-fpic' lt_prog_compiler_static='-Bstatic' ;; ccc*) lt_prog_compiler_wl='-Wl,' # All Alpha code is PIC. lt_prog_compiler_static='-non_shared' ;; xl* | bgxl* | bgf* | mpixl*) # IBM XL C 8.0/Fortran 10.1, 11.1 on PPC and BlueGene lt_prog_compiler_wl='-Wl,' lt_prog_compiler_pic='-qpic' lt_prog_compiler_static='-qstaticlink' ;; *) case `$CC -V 2>&1 | sed 5q` in *Sun\ Ceres\ Fortran* | *Sun*Fortran*\ [1-7].* | *Sun*Fortran*\ 8.[0-3]*) # Sun Fortran 8.3 passes all unrecognized flags to the linker lt_prog_compiler_pic='-KPIC' lt_prog_compiler_static='-Bstatic' lt_prog_compiler_wl='' ;; *Sun\ F* | *Sun*Fortran*) lt_prog_compiler_pic='-KPIC' lt_prog_compiler_static='-Bstatic' lt_prog_compiler_wl='-Qoption ld ' ;; *Sun\ C*) # Sun C 5.9 lt_prog_compiler_pic='-KPIC' lt_prog_compiler_static='-Bstatic' lt_prog_compiler_wl='-Wl,' ;; *Intel*\ [CF]*Compiler*) lt_prog_compiler_wl='-Wl,' lt_prog_compiler_pic='-fPIC' lt_prog_compiler_static='-static' ;; *Portland\ Group*) lt_prog_compiler_wl='-Wl,' lt_prog_compiler_pic='-fpic' lt_prog_compiler_static='-Bstatic' ;; esac ;; esac ;; newsos6) lt_prog_compiler_pic='-KPIC' lt_prog_compiler_static='-Bstatic' ;; *nto* | *qnx*) # QNX uses GNU C++, but need to define -shared option too, otherwise # it will coredump. lt_prog_compiler_pic='-fPIC -shared' ;; osf3* | osf4* | osf5*) lt_prog_compiler_wl='-Wl,' # All OSF/1 code is PIC. lt_prog_compiler_static='-non_shared' ;; rdos*) lt_prog_compiler_static='-non_shared' ;; solaris*) lt_prog_compiler_pic='-KPIC' lt_prog_compiler_static='-Bstatic' case $cc_basename in f77* | f90* | f95* | sunf77* | sunf90* | sunf95*) lt_prog_compiler_wl='-Qoption ld ';; *) lt_prog_compiler_wl='-Wl,';; esac ;; sunos4*) lt_prog_compiler_wl='-Qoption ld ' lt_prog_compiler_pic='-PIC' lt_prog_compiler_static='-Bstatic' ;; sysv4 | sysv4.2uw2* | sysv4.3*) lt_prog_compiler_wl='-Wl,' lt_prog_compiler_pic='-KPIC' lt_prog_compiler_static='-Bstatic' ;; sysv4*MP*) if test -d /usr/nec; then lt_prog_compiler_pic='-Kconform_pic' lt_prog_compiler_static='-Bstatic' fi ;; sysv5* | unixware* | sco3.2v5* | sco5v6* | OpenUNIX*) lt_prog_compiler_wl='-Wl,' lt_prog_compiler_pic='-KPIC' lt_prog_compiler_static='-Bstatic' ;; unicos*) lt_prog_compiler_wl='-Wl,' lt_prog_compiler_can_build_shared=no ;; uts4*) lt_prog_compiler_pic='-pic' lt_prog_compiler_static='-Bstatic' ;; *) lt_prog_compiler_can_build_shared=no ;; esac fi case $host_os in # For platforms that do not support PIC, -DPIC is meaningless: *djgpp*) lt_prog_compiler_pic= ;; *) lt_prog_compiler_pic="$lt_prog_compiler_pic -DPIC" ;; esac { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $compiler option to produce PIC" >&5 $as_echo_n "checking for $compiler option to produce PIC... " >&6; } if ${lt_cv_prog_compiler_pic+:} false; then : $as_echo_n "(cached) " >&6 else lt_cv_prog_compiler_pic=$lt_prog_compiler_pic fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $lt_cv_prog_compiler_pic" >&5 $as_echo "$lt_cv_prog_compiler_pic" >&6; } lt_prog_compiler_pic=$lt_cv_prog_compiler_pic # # Check to make sure the PIC flag actually works. # if test -n "$lt_prog_compiler_pic"; then { $as_echo "$as_me:${as_lineno-$LINENO}: checking if $compiler PIC flag $lt_prog_compiler_pic works" >&5 $as_echo_n "checking if $compiler PIC flag $lt_prog_compiler_pic works... " >&6; } if ${lt_cv_prog_compiler_pic_works+:} false; then : $as_echo_n "(cached) " >&6 else lt_cv_prog_compiler_pic_works=no ac_outfile=conftest.$ac_objext echo "$lt_simple_compile_test_code" > conftest.$ac_ext lt_compiler_flag="$lt_prog_compiler_pic -DPIC" ## exclude from sc_useless_quotes_in_assignment # Insert the option either (1) after the last *FLAGS variable, or # (2) before a word containing "conftest.", or (3) at the end. # Note that $ac_compile itself does not contain backslashes and begins # with a dollar sign (not a hyphen), so the echo should work correctly. # The option is referenced via a variable to avoid confusing sed. lt_compile=`echo "$ac_compile" | $SED \ -e 's:.*FLAGS}\{0,1\} :&$lt_compiler_flag :; t' \ -e 's: [^ ]*conftest\.: $lt_compiler_flag&:; t' \ -e 's:$: $lt_compiler_flag:'` (eval echo "\"\$as_me:$LINENO: $lt_compile\"" >&5) (eval "$lt_compile" 2>conftest.err) ac_status=$? cat conftest.err >&5 echo "$as_me:$LINENO: \$? = $ac_status" >&5 if (exit $ac_status) && test -s "$ac_outfile"; then # The compiler can only warn and ignore the option if not recognized # So say no if there are warnings other than the usual output. $ECHO "$_lt_compiler_boilerplate" | $SED '/^$/d' >conftest.exp $SED '/^$/d; /^ *+/d' conftest.err >conftest.er2 if test ! -s conftest.er2 || diff conftest.exp conftest.er2 >/dev/null; then lt_cv_prog_compiler_pic_works=yes fi fi $RM conftest* fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $lt_cv_prog_compiler_pic_works" >&5 $as_echo "$lt_cv_prog_compiler_pic_works" >&6; } if test yes = "$lt_cv_prog_compiler_pic_works"; then case $lt_prog_compiler_pic in "" | " "*) ;; *) lt_prog_compiler_pic=" $lt_prog_compiler_pic" ;; esac else lt_prog_compiler_pic= lt_prog_compiler_can_build_shared=no fi fi # # Check to make sure the static flag actually works. # wl=$lt_prog_compiler_wl eval lt_tmp_static_flag=\"$lt_prog_compiler_static\" { $as_echo "$as_me:${as_lineno-$LINENO}: checking if $compiler static flag $lt_tmp_static_flag works" >&5 $as_echo_n "checking if $compiler static flag $lt_tmp_static_flag works... " >&6; } if ${lt_cv_prog_compiler_static_works+:} false; then : $as_echo_n "(cached) " >&6 else lt_cv_prog_compiler_static_works=no save_LDFLAGS=$LDFLAGS LDFLAGS="$LDFLAGS $lt_tmp_static_flag" echo "$lt_simple_link_test_code" > conftest.$ac_ext if (eval $ac_link 2>conftest.err) && test -s conftest$ac_exeext; then # The linker can only warn and ignore the option if not recognized # So say no if there are warnings if test -s conftest.err; then # Append any errors to the config.log. cat conftest.err 1>&5 $ECHO "$_lt_linker_boilerplate" | $SED '/^$/d' > conftest.exp $SED '/^$/d; /^ *+/d' conftest.err >conftest.er2 if diff conftest.exp conftest.er2 >/dev/null; then lt_cv_prog_compiler_static_works=yes fi else lt_cv_prog_compiler_static_works=yes fi fi $RM -r conftest* LDFLAGS=$save_LDFLAGS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $lt_cv_prog_compiler_static_works" >&5 $as_echo "$lt_cv_prog_compiler_static_works" >&6; } if test yes = "$lt_cv_prog_compiler_static_works"; then : else lt_prog_compiler_static= fi { $as_echo "$as_me:${as_lineno-$LINENO}: checking if $compiler supports -c -o file.$ac_objext" >&5 $as_echo_n "checking if $compiler supports -c -o file.$ac_objext... " >&6; } if ${lt_cv_prog_compiler_c_o+:} false; then : $as_echo_n "(cached) " >&6 else lt_cv_prog_compiler_c_o=no $RM -r conftest 2>/dev/null mkdir conftest cd conftest mkdir out echo "$lt_simple_compile_test_code" > conftest.$ac_ext lt_compiler_flag="-o out/conftest2.$ac_objext" # Insert the option either (1) after the last *FLAGS variable, or # (2) before a word containing "conftest.", or (3) at the end. # Note that $ac_compile itself does not contain backslashes and begins # with a dollar sign (not a hyphen), so the echo should work correctly. lt_compile=`echo "$ac_compile" | $SED \ -e 's:.*FLAGS}\{0,1\} :&$lt_compiler_flag :; t' \ -e 's: [^ ]*conftest\.: $lt_compiler_flag&:; t' \ -e 's:$: $lt_compiler_flag:'` (eval echo "\"\$as_me:$LINENO: $lt_compile\"" >&5) (eval "$lt_compile" 2>out/conftest.err) ac_status=$? cat out/conftest.err >&5 echo "$as_me:$LINENO: \$? = $ac_status" >&5 if (exit $ac_status) && test -s out/conftest2.$ac_objext then # The compiler can only warn and ignore the option if not recognized # So say no if there are warnings $ECHO "$_lt_compiler_boilerplate" | $SED '/^$/d' > out/conftest.exp $SED '/^$/d; /^ *+/d' out/conftest.err >out/conftest.er2 if test ! -s out/conftest.er2 || diff out/conftest.exp out/conftest.er2 >/dev/null; then lt_cv_prog_compiler_c_o=yes fi fi chmod u+w . 2>&5 $RM conftest* # SGI C++ compiler will create directory out/ii_files/ for # template instantiation test -d out/ii_files && $RM out/ii_files/* && rmdir out/ii_files $RM out/* && rmdir out cd .. $RM -r conftest $RM conftest* fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $lt_cv_prog_compiler_c_o" >&5 $as_echo "$lt_cv_prog_compiler_c_o" >&6; } { $as_echo "$as_me:${as_lineno-$LINENO}: checking if $compiler supports -c -o file.$ac_objext" >&5 $as_echo_n "checking if $compiler supports -c -o file.$ac_objext... " >&6; } if ${lt_cv_prog_compiler_c_o+:} false; then : $as_echo_n "(cached) " >&6 else lt_cv_prog_compiler_c_o=no $RM -r conftest 2>/dev/null mkdir conftest cd conftest mkdir out echo "$lt_simple_compile_test_code" > conftest.$ac_ext lt_compiler_flag="-o out/conftest2.$ac_objext" # Insert the option either (1) after the last *FLAGS variable, or # (2) before a word containing "conftest.", or (3) at the end. # Note that $ac_compile itself does not contain backslashes and begins # with a dollar sign (not a hyphen), so the echo should work correctly. lt_compile=`echo "$ac_compile" | $SED \ -e 's:.*FLAGS}\{0,1\} :&$lt_compiler_flag :; t' \ -e 's: [^ ]*conftest\.: $lt_compiler_flag&:; t' \ -e 's:$: $lt_compiler_flag:'` (eval echo "\"\$as_me:$LINENO: $lt_compile\"" >&5) (eval "$lt_compile" 2>out/conftest.err) ac_status=$? cat out/conftest.err >&5 echo "$as_me:$LINENO: \$? = $ac_status" >&5 if (exit $ac_status) && test -s out/conftest2.$ac_objext then # The compiler can only warn and ignore the option if not recognized # So say no if there are warnings $ECHO "$_lt_compiler_boilerplate" | $SED '/^$/d' > out/conftest.exp $SED '/^$/d; /^ *+/d' out/conftest.err >out/conftest.er2 if test ! -s out/conftest.er2 || diff out/conftest.exp out/conftest.er2 >/dev/null; then lt_cv_prog_compiler_c_o=yes fi fi chmod u+w . 2>&5 $RM conftest* # SGI C++ compiler will create directory out/ii_files/ for # template instantiation test -d out/ii_files && $RM out/ii_files/* && rmdir out/ii_files $RM out/* && rmdir out cd .. $RM -r conftest $RM conftest* fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $lt_cv_prog_compiler_c_o" >&5 $as_echo "$lt_cv_prog_compiler_c_o" >&6; } hard_links=nottested if test no = "$lt_cv_prog_compiler_c_o" && test no != "$need_locks"; then # do not overwrite the value of need_locks provided by the user { $as_echo "$as_me:${as_lineno-$LINENO}: checking if we can lock with hard links" >&5 $as_echo_n "checking if we can lock with hard links... " >&6; } hard_links=yes $RM conftest* ln conftest.a conftest.b 2>/dev/null && hard_links=no touch conftest.a ln conftest.a conftest.b 2>&5 || hard_links=no ln conftest.a conftest.b 2>/dev/null && hard_links=no { $as_echo "$as_me:${as_lineno-$LINENO}: result: $hard_links" >&5 $as_echo "$hard_links" >&6; } if test no = "$hard_links"; then { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: '$CC' does not support '-c -o', so 'make -j' may be unsafe" >&5 $as_echo "$as_me: WARNING: '$CC' does not support '-c -o', so 'make -j' may be unsafe" >&2;} need_locks=warn fi else need_locks=no fi { $as_echo "$as_me:${as_lineno-$LINENO}: checking whether the $compiler linker ($LD) supports shared libraries" >&5 $as_echo_n "checking whether the $compiler linker ($LD) supports shared libraries... " >&6; } runpath_var= allow_undefined_flag= always_export_symbols=no archive_cmds= archive_expsym_cmds= compiler_needs_object=no enable_shared_with_static_runtimes=no export_dynamic_flag_spec= export_symbols_cmds='$NM $libobjs $convenience | $global_symbol_pipe | $SED '\''s/.* //'\'' | sort | uniq > $export_symbols' hardcode_automatic=no hardcode_direct=no hardcode_direct_absolute=no hardcode_libdir_flag_spec= hardcode_libdir_separator= hardcode_minus_L=no hardcode_shlibpath_var=unsupported inherit_rpath=no link_all_deplibs=unknown module_cmds= module_expsym_cmds= old_archive_from_new_cmds= old_archive_from_expsyms_cmds= thread_safe_flag_spec= whole_archive_flag_spec= # include_expsyms should be a list of space-separated symbols to be *always* # included in the symbol list include_expsyms= # exclude_expsyms can be an extended regexp of symbols to exclude # it will be wrapped by ' (' and ')$', so one must not match beginning or # end of line. Example: 'a|bc|.*d.*' will exclude the symbols 'a' and 'bc', # as well as any symbol that contains 'd'. exclude_expsyms='_GLOBAL_OFFSET_TABLE_|_GLOBAL__F[ID]_.*' # Although _GLOBAL_OFFSET_TABLE_ is a valid symbol C name, most a.out # platforms (ab)use it in PIC code, but their linkers get confused if # the symbol is explicitly referenced. Since portable code cannot # rely on this symbol name, it's probably fine to never include it in # preloaded symbol tables. # Exclude shared library initialization/finalization symbols. extract_expsyms_cmds= case $host_os in cygwin* | mingw* | pw32* | cegcc*) # FIXME: the MSVC++ port hasn't been tested in a loooong time # When not using gcc, we currently assume that we are using # Microsoft Visual C++. if test yes != "$GCC"; then with_gnu_ld=no fi ;; interix*) # we just hope/assume this is gcc and not c89 (= MSVC++) with_gnu_ld=yes ;; openbsd* | bitrig*) with_gnu_ld=no ;; linux* | k*bsd*-gnu | gnu*) link_all_deplibs=no ;; esac ld_shlibs=yes # On some targets, GNU ld is compatible enough with the native linker # that we're better off using the native interface for both. lt_use_gnu_ld_interface=no if test yes = "$with_gnu_ld"; then case $host_os in aix*) # The AIX port of GNU ld has always aspired to compatibility # with the native linker. However, as the warning in the GNU ld # block says, versions before 2.19.5* couldn't really create working # shared libraries, regardless of the interface used. case `$LD -v 2>&1` in *\ \(GNU\ Binutils\)\ 2.19.5*) ;; *\ \(GNU\ Binutils\)\ 2.[2-9]*) ;; *\ \(GNU\ Binutils\)\ [3-9]*) ;; *) lt_use_gnu_ld_interface=yes ;; esac ;; *) lt_use_gnu_ld_interface=yes ;; esac fi if test yes = "$lt_use_gnu_ld_interface"; then # If archive_cmds runs LD, not CC, wlarc should be empty wlarc='$wl' # Set some defaults for GNU ld with shared library support. These # are reset later if shared libraries are not supported. Putting them # here allows them to be overridden if necessary. runpath_var=LD_RUN_PATH hardcode_libdir_flag_spec='$wl-rpath $wl$libdir' export_dynamic_flag_spec='$wl--export-dynamic' # ancient GNU ld didn't support --whole-archive et. al. if $LD --help 2>&1 | $GREP 'no-whole-archive' > /dev/null; then whole_archive_flag_spec=$wlarc'--whole-archive$convenience '$wlarc'--no-whole-archive' else whole_archive_flag_spec= fi supports_anon_versioning=no case `$LD -v | $SED -e 's/(^)\+)\s\+//' 2>&1` in *GNU\ gold*) supports_anon_versioning=yes ;; *\ [01].* | *\ 2.[0-9].* | *\ 2.10.*) ;; # catch versions < 2.11 *\ 2.11.93.0.2\ *) supports_anon_versioning=yes ;; # RH7.3 ... *\ 2.11.92.0.12\ *) supports_anon_versioning=yes ;; # Mandrake 8.2 ... *\ 2.11.*) ;; # other 2.11 versions *) supports_anon_versioning=yes ;; esac # See if GNU ld supports shared libraries. case $host_os in aix[3-9]*) # On AIX/PPC, the GNU linker is very broken if test ia64 != "$host_cpu"; then ld_shlibs=no cat <<_LT_EOF 1>&2 *** Warning: the GNU linker, at least up to release 2.19, is reported *** to be unable to reliably create shared libraries on AIX. *** Therefore, libtool is disabling shared libraries support. If you *** really care for shared libraries, you may want to install binutils *** 2.20 or above, or modify your PATH so that a non-GNU linker is found. *** You will then need to restart the configuration process. _LT_EOF fi ;; amigaos*) case $host_cpu in powerpc) # see comment about AmigaOS4 .so support archive_cmds='$CC -shared $libobjs $deplibs $compiler_flags $wl-soname $wl$soname -o $lib' archive_expsym_cmds='' ;; m68k) archive_cmds='$RM $output_objdir/a2ixlibrary.data~$ECHO "#define NAME $libname" > $output_objdir/a2ixlibrary.data~$ECHO "#define LIBRARY_ID 1" >> $output_objdir/a2ixlibrary.data~$ECHO "#define VERSION $major" >> $output_objdir/a2ixlibrary.data~$ECHO "#define REVISION $revision" >> $output_objdir/a2ixlibrary.data~$AR $AR_FLAGS $lib $libobjs~$RANLIB $lib~(cd $output_objdir && a2ixlibrary -32)' hardcode_libdir_flag_spec='-L$libdir' hardcode_minus_L=yes ;; esac ;; beos*) if $LD --help 2>&1 | $GREP ': supported targets:.* elf' > /dev/null; then allow_undefined_flag=unsupported # Joseph Beckenbach says some releases of gcc # support --undefined. This deserves some investigation. FIXME archive_cmds='$CC -nostart $libobjs $deplibs $compiler_flags $wl-soname $wl$soname -o $lib' else ld_shlibs=no fi ;; cygwin* | mingw* | pw32* | cegcc*) # _LT_TAGVAR(hardcode_libdir_flag_spec, ) is actually meaningless, # as there is no search path for DLLs. hardcode_libdir_flag_spec='-L$libdir' export_dynamic_flag_spec='$wl--export-all-symbols' allow_undefined_flag=unsupported always_export_symbols=no enable_shared_with_static_runtimes=yes export_symbols_cmds='$NM $libobjs $convenience | $global_symbol_pipe | $SED -e '\''/^[BCDGRS][ ]/s/.*[ ]\([^ ]*\)/\1 DATA/;s/^.*[ ]__nm__\([^ ]*\)[ ][^ ]*/\1 DATA/;/^I[ ]/d;/^[AITW][ ]/s/.* //'\'' | sort | uniq > $export_symbols' exclude_expsyms='[_]+GLOBAL_OFFSET_TABLE_|[_]+GLOBAL__[FID]_.*|[_]+head_[A-Za-z0-9_]+_dll|[A-Za-z0-9_]+_dll_iname' if $LD --help 2>&1 | $GREP 'auto-import' > /dev/null; then archive_cmds='$CC -shared $libobjs $deplibs $compiler_flags -o $output_objdir/$soname $wl--enable-auto-image-base -Xlinker --out-implib -Xlinker $lib' # If the export-symbols file already is a .def file, use it as # is; otherwise, prepend EXPORTS... archive_expsym_cmds='if test DEF = "`$SED -n -e '\''s/^[ ]*//'\'' -e '\''/^\(;.*\)*$/d'\'' -e '\''s/^\(EXPORTS\|LIBRARY\)\([ ].*\)*$/DEF/p'\'' -e q $export_symbols`" ; then cp $export_symbols $output_objdir/$soname.def; else echo EXPORTS > $output_objdir/$soname.def; cat $export_symbols >> $output_objdir/$soname.def; fi~ $CC -shared $output_objdir/$soname.def $libobjs $deplibs $compiler_flags -o $output_objdir/$soname $wl--enable-auto-image-base -Xlinker --out-implib -Xlinker $lib' else ld_shlibs=no fi ;; haiku*) archive_cmds='$CC -shared $libobjs $deplibs $compiler_flags $wl-soname $wl$soname -o $lib' link_all_deplibs=yes ;; os2*) hardcode_libdir_flag_spec='-L$libdir' hardcode_minus_L=yes allow_undefined_flag=unsupported shrext_cmds=.dll archive_cmds='$ECHO "LIBRARY ${soname%$shared_ext} INITINSTANCE TERMINSTANCE" > $output_objdir/$libname.def~ $ECHO "DESCRIPTION \"$libname\"" >> $output_objdir/$libname.def~ $ECHO "DATA MULTIPLE NONSHARED" >> $output_objdir/$libname.def~ $ECHO EXPORTS >> $output_objdir/$libname.def~ emxexp $libobjs | $SED /"_DLL_InitTerm"/d >> $output_objdir/$libname.def~ $CC -Zdll -Zcrtdll -o $output_objdir/$soname $libobjs $deplibs $compiler_flags $output_objdir/$libname.def~ emximp -o $lib $output_objdir/$libname.def' archive_expsym_cmds='$ECHO "LIBRARY ${soname%$shared_ext} INITINSTANCE TERMINSTANCE" > $output_objdir/$libname.def~ $ECHO "DESCRIPTION \"$libname\"" >> $output_objdir/$libname.def~ $ECHO "DATA MULTIPLE NONSHARED" >> $output_objdir/$libname.def~ $ECHO EXPORTS >> $output_objdir/$libname.def~ prefix_cmds="$SED"~ if test EXPORTS = "`$SED 1q $export_symbols`"; then prefix_cmds="$prefix_cmds -e 1d"; fi~ prefix_cmds="$prefix_cmds -e \"s/^\(.*\)$/_\1/g\""~ cat $export_symbols | $prefix_cmds >> $output_objdir/$libname.def~ $CC -Zdll -Zcrtdll -o $output_objdir/$soname $libobjs $deplibs $compiler_flags $output_objdir/$libname.def~ emximp -o $lib $output_objdir/$libname.def' old_archive_From_new_cmds='emximp -o $output_objdir/${libname}_dll.a $output_objdir/$libname.def' enable_shared_with_static_runtimes=yes ;; interix[3-9]*) hardcode_direct=no hardcode_shlibpath_var=no hardcode_libdir_flag_spec='$wl-rpath,$libdir' export_dynamic_flag_spec='$wl-E' # Hack: On Interix 3.x, we cannot compile PIC because of a broken gcc. # Instead, shared libraries are loaded at an image base (0x10000000 by # default) and relocated if they conflict, which is a slow very memory # consuming and fragmenting process. To avoid this, we pick a random, # 256 KiB-aligned image base between 0x50000000 and 0x6FFC0000 at link # time. Moving up from 0x10000000 also allows more sbrk(2) space. archive_cmds='$CC -shared $pic_flag $libobjs $deplibs $compiler_flags $wl-h,$soname $wl--image-base,`expr ${RANDOM-$$} % 4096 / 2 \* 262144 + 1342177280` -o $lib' archive_expsym_cmds='sed "s|^|_|" $export_symbols >$output_objdir/$soname.expsym~$CC -shared $pic_flag $libobjs $deplibs $compiler_flags $wl-h,$soname $wl--retain-symbols-file,$output_objdir/$soname.expsym $wl--image-base,`expr ${RANDOM-$$} % 4096 / 2 \* 262144 + 1342177280` -o $lib' ;; gnu* | linux* | tpf* | k*bsd*-gnu | kopensolaris*-gnu) tmp_diet=no if test linux-dietlibc = "$host_os"; then case $cc_basename in diet\ *) tmp_diet=yes;; # linux-dietlibc with static linking (!diet-dyn) esac fi if $LD --help 2>&1 | $EGREP ': supported targets:.* elf' > /dev/null \ && test no = "$tmp_diet" then tmp_addflag=' $pic_flag' tmp_sharedflag='-shared' case $cc_basename,$host_cpu in pgcc*) # Portland Group C compiler whole_archive_flag_spec='$wl--whole-archive`for conv in $convenience\"\"; do test -n \"$conv\" && new_convenience=\"$new_convenience,$conv\"; done; func_echo_all \"$new_convenience\"` $wl--no-whole-archive' tmp_addflag=' $pic_flag' ;; pgf77* | pgf90* | pgf95* | pgfortran*) # Portland Group f77 and f90 compilers whole_archive_flag_spec='$wl--whole-archive`for conv in $convenience\"\"; do test -n \"$conv\" && new_convenience=\"$new_convenience,$conv\"; done; func_echo_all \"$new_convenience\"` $wl--no-whole-archive' tmp_addflag=' $pic_flag -Mnomain' ;; ecc*,ia64* | icc*,ia64*) # Intel C compiler on ia64 tmp_addflag=' -i_dynamic' ;; efc*,ia64* | ifort*,ia64*) # Intel Fortran compiler on ia64 tmp_addflag=' -i_dynamic -nofor_main' ;; ifc* | ifort*) # Intel Fortran compiler tmp_addflag=' -nofor_main' ;; lf95*) # Lahey Fortran 8.1 whole_archive_flag_spec= tmp_sharedflag='--shared' ;; nagfor*) # NAGFOR 5.3 tmp_sharedflag='-Wl,-shared' ;; xl[cC]* | bgxl[cC]* | mpixl[cC]*) # IBM XL C 8.0 on PPC (deal with xlf below) tmp_sharedflag='-qmkshrobj' tmp_addflag= ;; nvcc*) # Cuda Compiler Driver 2.2 whole_archive_flag_spec='$wl--whole-archive`for conv in $convenience\"\"; do test -n \"$conv\" && new_convenience=\"$new_convenience,$conv\"; done; func_echo_all \"$new_convenience\"` $wl--no-whole-archive' compiler_needs_object=yes ;; esac case `$CC -V 2>&1 | sed 5q` in *Sun\ C*) # Sun C 5.9 whole_archive_flag_spec='$wl--whole-archive`new_convenience=; for conv in $convenience\"\"; do test -z \"$conv\" || new_convenience=\"$new_convenience,$conv\"; done; func_echo_all \"$new_convenience\"` $wl--no-whole-archive' compiler_needs_object=yes tmp_sharedflag='-G' ;; *Sun\ F*) # Sun Fortran 8.3 tmp_sharedflag='-G' ;; esac archive_cmds='$CC '"$tmp_sharedflag""$tmp_addflag"' $libobjs $deplibs $compiler_flags $wl-soname $wl$soname -o $lib' if test yes = "$supports_anon_versioning"; then archive_expsym_cmds='echo "{ global:" > $output_objdir/$libname.ver~ cat $export_symbols | sed -e "s/\(.*\)/\1;/" >> $output_objdir/$libname.ver~ echo "local: *; };" >> $output_objdir/$libname.ver~ $CC '"$tmp_sharedflag""$tmp_addflag"' $libobjs $deplibs $compiler_flags $wl-soname $wl$soname $wl-version-script $wl$output_objdir/$libname.ver -o $lib' fi case $cc_basename in tcc*) export_dynamic_flag_spec='-rdynamic' ;; xlf* | bgf* | bgxlf* | mpixlf*) # IBM XL Fortran 10.1 on PPC cannot create shared libs itself whole_archive_flag_spec='--whole-archive$convenience --no-whole-archive' hardcode_libdir_flag_spec='$wl-rpath $wl$libdir' archive_cmds='$LD -shared $libobjs $deplibs $linker_flags -soname $soname -o $lib' if test yes = "$supports_anon_versioning"; then archive_expsym_cmds='echo "{ global:" > $output_objdir/$libname.ver~ cat $export_symbols | sed -e "s/\(.*\)/\1;/" >> $output_objdir/$libname.ver~ echo "local: *; };" >> $output_objdir/$libname.ver~ $LD -shared $libobjs $deplibs $linker_flags -soname $soname -version-script $output_objdir/$libname.ver -o $lib' fi ;; esac else ld_shlibs=no fi ;; netbsd* | netbsdelf*-gnu) if echo __ELF__ | $CC -E - | $GREP __ELF__ >/dev/null; then archive_cmds='$LD -Bshareable $libobjs $deplibs $linker_flags -o $lib' wlarc= else archive_cmds='$CC -shared $pic_flag $libobjs $deplibs $compiler_flags $wl-soname $wl$soname -o $lib' archive_expsym_cmds='$CC -shared $pic_flag $libobjs $deplibs $compiler_flags $wl-soname $wl$soname $wl-retain-symbols-file $wl$export_symbols -o $lib' fi ;; solaris*) if $LD -v 2>&1 | $GREP 'BFD 2\.8' > /dev/null; then ld_shlibs=no cat <<_LT_EOF 1>&2 *** Warning: The releases 2.8.* of the GNU linker cannot reliably *** create shared libraries on Solaris systems. Therefore, libtool *** is disabling shared libraries support. We urge you to upgrade GNU *** binutils to release 2.9.1 or newer. Another option is to modify *** your PATH or compiler configuration so that the native linker is *** used, and then restart. _LT_EOF elif $LD --help 2>&1 | $GREP ': supported targets:.* elf' > /dev/null; then archive_cmds='$CC -shared $pic_flag $libobjs $deplibs $compiler_flags $wl-soname $wl$soname -o $lib' archive_expsym_cmds='$CC -shared $pic_flag $libobjs $deplibs $compiler_flags $wl-soname $wl$soname $wl-retain-symbols-file $wl$export_symbols -o $lib' else ld_shlibs=no fi ;; sysv5* | sco3.2v5* | sco5v6* | unixware* | OpenUNIX*) case `$LD -v 2>&1` in *\ [01].* | *\ 2.[0-9].* | *\ 2.1[0-5].*) ld_shlibs=no cat <<_LT_EOF 1>&2 *** Warning: Releases of the GNU linker prior to 2.16.91.0.3 cannot *** reliably create shared libraries on SCO systems. Therefore, libtool *** is disabling shared libraries support. We urge you to upgrade GNU *** binutils to release 2.16.91.0.3 or newer. Another option is to modify *** your PATH or compiler configuration so that the native linker is *** used, and then restart. _LT_EOF ;; *) # For security reasons, it is highly recommended that you always # use absolute paths for naming shared libraries, and exclude the # DT_RUNPATH tag from executables and libraries. But doing so # requires that you compile everything twice, which is a pain. if $LD --help 2>&1 | $GREP ': supported targets:.* elf' > /dev/null; then hardcode_libdir_flag_spec='$wl-rpath $wl$libdir' archive_cmds='$CC -shared $libobjs $deplibs $compiler_flags $wl-soname $wl$soname -o $lib' archive_expsym_cmds='$CC -shared $libobjs $deplibs $compiler_flags $wl-soname $wl$soname $wl-retain-symbols-file $wl$export_symbols -o $lib' else ld_shlibs=no fi ;; esac ;; sunos4*) archive_cmds='$LD -assert pure-text -Bshareable -o $lib $libobjs $deplibs $linker_flags' wlarc= hardcode_direct=yes hardcode_shlibpath_var=no ;; *) if $LD --help 2>&1 | $GREP ': supported targets:.* elf' > /dev/null; then archive_cmds='$CC -shared $pic_flag $libobjs $deplibs $compiler_flags $wl-soname $wl$soname -o $lib' archive_expsym_cmds='$CC -shared $pic_flag $libobjs $deplibs $compiler_flags $wl-soname $wl$soname $wl-retain-symbols-file $wl$export_symbols -o $lib' else ld_shlibs=no fi ;; esac if test no = "$ld_shlibs"; then runpath_var= hardcode_libdir_flag_spec= export_dynamic_flag_spec= whole_archive_flag_spec= fi else # PORTME fill in a description of your system's linker (not GNU ld) case $host_os in aix3*) allow_undefined_flag=unsupported always_export_symbols=yes archive_expsym_cmds='$LD -o $output_objdir/$soname $libobjs $deplibs $linker_flags -bE:$export_symbols -T512 -H512 -bM:SRE~$AR $AR_FLAGS $lib $output_objdir/$soname' # Note: this linker hardcodes the directories in LIBPATH if there # are no directories specified by -L. hardcode_minus_L=yes if test yes = "$GCC" && test -z "$lt_prog_compiler_static"; then # Neither direct hardcoding nor static linking is supported with a # broken collect2. hardcode_direct=unsupported fi ;; aix[4-9]*) if test ia64 = "$host_cpu"; then # On IA64, the linker does run time linking by default, so we don't # have to do anything special. aix_use_runtimelinking=no exp_sym_flag='-Bexport' no_entry_flag= else # If we're using GNU nm, then we don't want the "-C" option. # -C means demangle to GNU nm, but means don't demangle to AIX nm. # Without the "-l" option, or with the "-B" option, AIX nm treats # weak defined symbols like other global defined symbols, whereas # GNU nm marks them as "W". # While the 'weak' keyword is ignored in the Export File, we need # it in the Import File for the 'aix-soname' feature, so we have # to replace the "-B" option with "-P" for AIX nm. if $NM -V 2>&1 | $GREP 'GNU' > /dev/null; then export_symbols_cmds='$NM -Bpg $libobjs $convenience | awk '\''{ if (((\$ 2 == "T") || (\$ 2 == "D") || (\$ 2 == "B") || (\$ 2 == "W")) && (substr(\$ 3,1,1) != ".")) { if (\$ 2 == "W") { print \$ 3 " weak" } else { print \$ 3 } } }'\'' | sort -u > $export_symbols' else export_symbols_cmds='`func_echo_all $NM | $SED -e '\''s/B\([^B]*\)$/P\1/'\''` -PCpgl $libobjs $convenience | awk '\''{ if (((\$ 2 == "T") || (\$ 2 == "D") || (\$ 2 == "B") || (\$ 2 == "W") || (\$ 2 == "V") || (\$ 2 == "Z")) && (substr(\$ 1,1,1) != ".")) { if ((\$ 2 == "W") || (\$ 2 == "V") || (\$ 2 == "Z")) { print \$ 1 " weak" } else { print \$ 1 } } }'\'' | sort -u > $export_symbols' fi aix_use_runtimelinking=no # Test if we are trying to use run time linking or normal # AIX style linking. If -brtl is somewhere in LDFLAGS, we # have runtime linking enabled, and use it for executables. # For shared libraries, we enable/disable runtime linking # depending on the kind of the shared library created - # when "with_aix_soname,aix_use_runtimelinking" is: # "aix,no" lib.a(lib.so.V) shared, rtl:no, for executables # "aix,yes" lib.so shared, rtl:yes, for executables # lib.a static archive # "both,no" lib.so.V(shr.o) shared, rtl:yes # lib.a(lib.so.V) shared, rtl:no, for executables # "both,yes" lib.so.V(shr.o) shared, rtl:yes, for executables # lib.a(lib.so.V) shared, rtl:no # "svr4,*" lib.so.V(shr.o) shared, rtl:yes, for executables # lib.a static archive case $host_os in aix4.[23]|aix4.[23].*|aix[5-9]*) for ld_flag in $LDFLAGS; do if (test x-brtl = "x$ld_flag" || test x-Wl,-brtl = "x$ld_flag"); then aix_use_runtimelinking=yes break fi done if test svr4,no = "$with_aix_soname,$aix_use_runtimelinking"; then # With aix-soname=svr4, we create the lib.so.V shared archives only, # so we don't have lib.a shared libs to link our executables. # We have to force runtime linking in this case. aix_use_runtimelinking=yes LDFLAGS="$LDFLAGS -Wl,-brtl" fi ;; esac exp_sym_flag='-bexport' no_entry_flag='-bnoentry' fi # When large executables or shared objects are built, AIX ld can # have problems creating the table of contents. If linking a library # or program results in "error TOC overflow" add -mminimal-toc to # CXXFLAGS/CFLAGS for g++/gcc. In the cases where that is not # enough to fix the problem, add -Wl,-bbigtoc to LDFLAGS. archive_cmds='' hardcode_direct=yes hardcode_direct_absolute=yes hardcode_libdir_separator=':' link_all_deplibs=yes file_list_spec='$wl-f,' case $with_aix_soname,$aix_use_runtimelinking in aix,*) ;; # traditional, no import file svr4,* | *,yes) # use import file # The Import File defines what to hardcode. hardcode_direct=no hardcode_direct_absolute=no ;; esac if test yes = "$GCC"; then case $host_os in aix4.[012]|aix4.[012].*) # We only want to do this on AIX 4.2 and lower, the check # below for broken collect2 doesn't work under 4.3+ collect2name=`$CC -print-prog-name=collect2` if test -f "$collect2name" && strings "$collect2name" | $GREP resolve_lib_name >/dev/null then # We have reworked collect2 : else # We have old collect2 hardcode_direct=unsupported # It fails to find uninstalled libraries when the uninstalled # path is not listed in the libpath. Setting hardcode_minus_L # to unsupported forces relinking hardcode_minus_L=yes hardcode_libdir_flag_spec='-L$libdir' hardcode_libdir_separator= fi ;; esac shared_flag='-shared' if test yes = "$aix_use_runtimelinking"; then shared_flag="$shared_flag "'$wl-G' fi # Need to ensure runtime linking is disabled for the traditional # shared library, or the linker may eventually find shared libraries # /with/ Import File - we do not want to mix them. shared_flag_aix='-shared' shared_flag_svr4='-shared $wl-G' else # not using gcc if test ia64 = "$host_cpu"; then # VisualAge C++, Version 5.5 for AIX 5L for IA-64, Beta 3 Release # chokes on -Wl,-G. The following line is correct: shared_flag='-G' else if test yes = "$aix_use_runtimelinking"; then shared_flag='$wl-G' else shared_flag='$wl-bM:SRE' fi shared_flag_aix='$wl-bM:SRE' shared_flag_svr4='$wl-G' fi fi export_dynamic_flag_spec='$wl-bexpall' # It seems that -bexpall does not export symbols beginning with # underscore (_), so it is better to generate a list of symbols to export. always_export_symbols=yes if test aix,yes = "$with_aix_soname,$aix_use_runtimelinking"; then # Warning - without using the other runtime loading flags (-brtl), # -berok will link without error, but may produce a broken library. allow_undefined_flag='-berok' # Determine the default libpath from the value encoded in an # empty executable. if test set = "${lt_cv_aix_libpath+set}"; then aix_libpath=$lt_cv_aix_libpath else if ${lt_cv_aix_libpath_+:} false; then : $as_echo_n "(cached) " >&6 else cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ int main () { ; return 0; } _ACEOF if ac_fn_c_try_link "$LINENO"; then : lt_aix_libpath_sed=' /Import File Strings/,/^$/ { /^0/ { s/^0 *\([^ ]*\) *$/\1/ p } }' lt_cv_aix_libpath_=`dump -H conftest$ac_exeext 2>/dev/null | $SED -n -e "$lt_aix_libpath_sed"` # Check for a 64-bit object if we didn't find anything. if test -z "$lt_cv_aix_libpath_"; then lt_cv_aix_libpath_=`dump -HX64 conftest$ac_exeext 2>/dev/null | $SED -n -e "$lt_aix_libpath_sed"` fi fi rm -f core conftest.err conftest.$ac_objext \ conftest$ac_exeext conftest.$ac_ext if test -z "$lt_cv_aix_libpath_"; then lt_cv_aix_libpath_=/usr/lib:/lib fi fi aix_libpath=$lt_cv_aix_libpath_ fi hardcode_libdir_flag_spec='$wl-blibpath:$libdir:'"$aix_libpath" archive_expsym_cmds='$CC -o $output_objdir/$soname $libobjs $deplibs $wl'$no_entry_flag' $compiler_flags `if test -n "$allow_undefined_flag"; then func_echo_all "$wl$allow_undefined_flag"; else :; fi` $wl'$exp_sym_flag:\$export_symbols' '$shared_flag else if test ia64 = "$host_cpu"; then hardcode_libdir_flag_spec='$wl-R $libdir:/usr/lib:/lib' allow_undefined_flag="-z nodefs" archive_expsym_cmds="\$CC $shared_flag"' -o $output_objdir/$soname $libobjs $deplibs '"\$wl$no_entry_flag"' $compiler_flags $wl$allow_undefined_flag '"\$wl$exp_sym_flag:\$export_symbols" else # Determine the default libpath from the value encoded in an # empty executable. if test set = "${lt_cv_aix_libpath+set}"; then aix_libpath=$lt_cv_aix_libpath else if ${lt_cv_aix_libpath_+:} false; then : $as_echo_n "(cached) " >&6 else cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ int main () { ; return 0; } _ACEOF if ac_fn_c_try_link "$LINENO"; then : lt_aix_libpath_sed=' /Import File Strings/,/^$/ { /^0/ { s/^0 *\([^ ]*\) *$/\1/ p } }' lt_cv_aix_libpath_=`dump -H conftest$ac_exeext 2>/dev/null | $SED -n -e "$lt_aix_libpath_sed"` # Check for a 64-bit object if we didn't find anything. if test -z "$lt_cv_aix_libpath_"; then lt_cv_aix_libpath_=`dump -HX64 conftest$ac_exeext 2>/dev/null | $SED -n -e "$lt_aix_libpath_sed"` fi fi rm -f core conftest.err conftest.$ac_objext \ conftest$ac_exeext conftest.$ac_ext if test -z "$lt_cv_aix_libpath_"; then lt_cv_aix_libpath_=/usr/lib:/lib fi fi aix_libpath=$lt_cv_aix_libpath_ fi hardcode_libdir_flag_spec='$wl-blibpath:$libdir:'"$aix_libpath" # Warning - without using the other run time loading flags, # -berok will link without error, but may produce a broken library. no_undefined_flag=' $wl-bernotok' allow_undefined_flag=' $wl-berok' if test yes = "$with_gnu_ld"; then # We only use this code for GNU lds that support --whole-archive. whole_archive_flag_spec='$wl--whole-archive$convenience $wl--no-whole-archive' else # Exported symbols can be pulled into shared objects from archives whole_archive_flag_spec='$convenience' fi archive_cmds_need_lc=yes archive_expsym_cmds='$RM -r $output_objdir/$realname.d~$MKDIR $output_objdir/$realname.d' # -brtl affects multiple linker settings, -berok does not and is overridden later compiler_flags_filtered='`func_echo_all "$compiler_flags " | $SED -e "s%-brtl\\([, ]\\)%-berok\\1%g"`' if test svr4 != "$with_aix_soname"; then # This is similar to how AIX traditionally builds its shared libraries. archive_expsym_cmds="$archive_expsym_cmds"'~$CC '$shared_flag_aix' -o $output_objdir/$realname.d/$soname $libobjs $deplibs $wl-bnoentry '$compiler_flags_filtered'$wl-bE:$export_symbols$allow_undefined_flag~$AR $AR_FLAGS $output_objdir/$libname$release.a $output_objdir/$realname.d/$soname' fi if test aix != "$with_aix_soname"; then archive_expsym_cmds="$archive_expsym_cmds"'~$CC '$shared_flag_svr4' -o $output_objdir/$realname.d/$shared_archive_member_spec.o $libobjs $deplibs $wl-bnoentry '$compiler_flags_filtered'$wl-bE:$export_symbols$allow_undefined_flag~$STRIP -e $output_objdir/$realname.d/$shared_archive_member_spec.o~( func_echo_all "#! $soname($shared_archive_member_spec.o)"; if test shr_64 = "$shared_archive_member_spec"; then func_echo_all "# 64"; else func_echo_all "# 32"; fi; cat $export_symbols ) > $output_objdir/$realname.d/$shared_archive_member_spec.imp~$AR $AR_FLAGS $output_objdir/$soname $output_objdir/$realname.d/$shared_archive_member_spec.o $output_objdir/$realname.d/$shared_archive_member_spec.imp' else # used by -dlpreopen to get the symbols archive_expsym_cmds="$archive_expsym_cmds"'~$MV $output_objdir/$realname.d/$soname $output_objdir' fi archive_expsym_cmds="$archive_expsym_cmds"'~$RM -r $output_objdir/$realname.d' fi fi ;; amigaos*) case $host_cpu in powerpc) # see comment about AmigaOS4 .so support archive_cmds='$CC -shared $libobjs $deplibs $compiler_flags $wl-soname $wl$soname -o $lib' archive_expsym_cmds='' ;; m68k) archive_cmds='$RM $output_objdir/a2ixlibrary.data~$ECHO "#define NAME $libname" > $output_objdir/a2ixlibrary.data~$ECHO "#define LIBRARY_ID 1" >> $output_objdir/a2ixlibrary.data~$ECHO "#define VERSION $major" >> $output_objdir/a2ixlibrary.data~$ECHO "#define REVISION $revision" >> $output_objdir/a2ixlibrary.data~$AR $AR_FLAGS $lib $libobjs~$RANLIB $lib~(cd $output_objdir && a2ixlibrary -32)' hardcode_libdir_flag_spec='-L$libdir' hardcode_minus_L=yes ;; esac ;; bsdi[45]*) export_dynamic_flag_spec=-rdynamic ;; cygwin* | mingw* | pw32* | cegcc*) # When not using gcc, we currently assume that we are using # Microsoft Visual C++. # hardcode_libdir_flag_spec is actually meaningless, as there is # no search path for DLLs. case $cc_basename in cl*) # Native MSVC hardcode_libdir_flag_spec=' ' allow_undefined_flag=unsupported always_export_symbols=yes file_list_spec='@' # Tell ltmain to make .lib files, not .a files. libext=lib # Tell ltmain to make .dll files, not .so files. shrext_cmds=.dll # FIXME: Setting linknames here is a bad hack. archive_cmds='$CC -o $output_objdir/$soname $libobjs $compiler_flags $deplibs -Wl,-DLL,-IMPLIB:"$tool_output_objdir$libname.dll.lib"~linknames=' archive_expsym_cmds='if test DEF = "`$SED -n -e '\''s/^[ ]*//'\'' -e '\''/^\(;.*\)*$/d'\'' -e '\''s/^\(EXPORTS\|LIBRARY\)\([ ].*\)*$/DEF/p'\'' -e q $export_symbols`" ; then cp "$export_symbols" "$output_objdir/$soname.def"; echo "$tool_output_objdir$soname.def" > "$output_objdir/$soname.exp"; else $SED -e '\''s/^/-link -EXPORT:/'\'' < $export_symbols > $output_objdir/$soname.exp; fi~ $CC -o $tool_output_objdir$soname $libobjs $compiler_flags $deplibs "@$tool_output_objdir$soname.exp" -Wl,-DLL,-IMPLIB:"$tool_output_objdir$libname.dll.lib"~ linknames=' # The linker will not automatically build a static lib if we build a DLL. # _LT_TAGVAR(old_archive_from_new_cmds, )='true' enable_shared_with_static_runtimes=yes exclude_expsyms='_NULL_IMPORT_DESCRIPTOR|_IMPORT_DESCRIPTOR_.*' export_symbols_cmds='$NM $libobjs $convenience | $global_symbol_pipe | $SED -e '\''/^[BCDGRS][ ]/s/.*[ ]\([^ ]*\)/\1,DATA/'\'' | $SED -e '\''/^[AITW][ ]/s/.*[ ]//'\'' | sort | uniq > $export_symbols' # Don't use ranlib old_postinstall_cmds='chmod 644 $oldlib' postlink_cmds='lt_outputfile="@OUTPUT@"~ lt_tool_outputfile="@TOOL_OUTPUT@"~ case $lt_outputfile in *.exe|*.EXE) ;; *) lt_outputfile=$lt_outputfile.exe lt_tool_outputfile=$lt_tool_outputfile.exe ;; esac~ if test : != "$MANIFEST_TOOL" && test -f "$lt_outputfile.manifest"; then $MANIFEST_TOOL -manifest "$lt_tool_outputfile.manifest" -outputresource:"$lt_tool_outputfile" || exit 1; $RM "$lt_outputfile.manifest"; fi' ;; *) # Assume MSVC wrapper hardcode_libdir_flag_spec=' ' allow_undefined_flag=unsupported # Tell ltmain to make .lib files, not .a files. libext=lib # Tell ltmain to make .dll files, not .so files. shrext_cmds=.dll # FIXME: Setting linknames here is a bad hack. archive_cmds='$CC -o $lib $libobjs $compiler_flags `func_echo_all "$deplibs" | $SED '\''s/ -lc$//'\''` -link -dll~linknames=' # The linker will automatically build a .lib file if we build a DLL. old_archive_from_new_cmds='true' # FIXME: Should let the user specify the lib program. old_archive_cmds='lib -OUT:$oldlib$oldobjs$old_deplibs' enable_shared_with_static_runtimes=yes ;; esac ;; darwin* | rhapsody*) archive_cmds_need_lc=no hardcode_direct=no hardcode_automatic=yes hardcode_shlibpath_var=unsupported if test yes = "$lt_cv_ld_force_load"; then whole_archive_flag_spec='`for conv in $convenience\"\"; do test -n \"$conv\" && new_convenience=\"$new_convenience $wl-force_load,$conv\"; done; func_echo_all \"$new_convenience\"`' else whole_archive_flag_spec='' fi link_all_deplibs=yes allow_undefined_flag=$_lt_dar_allow_undefined case $cc_basename in ifort*|nagfor*) _lt_dar_can_shared=yes ;; *) _lt_dar_can_shared=$GCC ;; esac if test yes = "$_lt_dar_can_shared"; then output_verbose_link_cmd=func_echo_all archive_cmds="\$CC -dynamiclib \$allow_undefined_flag -o \$lib \$libobjs \$deplibs \$compiler_flags -install_name \$rpath/\$soname \$verstring $_lt_dar_single_mod$_lt_dsymutil" module_cmds="\$CC \$allow_undefined_flag -o \$lib -bundle \$libobjs \$deplibs \$compiler_flags$_lt_dsymutil" archive_expsym_cmds="sed 's|^|_|' < \$export_symbols > \$output_objdir/\$libname-symbols.expsym~\$CC -dynamiclib \$allow_undefined_flag -o \$lib \$libobjs \$deplibs \$compiler_flags -install_name \$rpath/\$soname \$verstring $_lt_dar_single_mod$_lt_dar_export_syms$_lt_dsymutil" module_expsym_cmds="sed -e 's|^|_|' < \$export_symbols > \$output_objdir/\$libname-symbols.expsym~\$CC \$allow_undefined_flag -o \$lib -bundle \$libobjs \$deplibs \$compiler_flags$_lt_dar_export_syms$_lt_dsymutil" else ld_shlibs=no fi ;; dgux*) archive_cmds='$LD -G -h $soname -o $lib $libobjs $deplibs $linker_flags' hardcode_libdir_flag_spec='-L$libdir' hardcode_shlibpath_var=no ;; # FreeBSD 2.2.[012] allows us to include c++rt0.o to get C++ constructor # support. Future versions do this automatically, but an explicit c++rt0.o # does not break anything, and helps significantly (at the cost of a little # extra space). freebsd2.2*) archive_cmds='$LD -Bshareable -o $lib $libobjs $deplibs $linker_flags /usr/lib/c++rt0.o' hardcode_libdir_flag_spec='-R$libdir' hardcode_direct=yes hardcode_shlibpath_var=no ;; # Unfortunately, older versions of FreeBSD 2 do not have this feature. freebsd2.*) archive_cmds='$LD -Bshareable -o $lib $libobjs $deplibs $linker_flags' hardcode_direct=yes hardcode_minus_L=yes hardcode_shlibpath_var=no ;; # FreeBSD 3 and greater uses gcc -shared to do shared libraries. freebsd* | dragonfly*) archive_cmds='$CC -shared $pic_flag -o $lib $libobjs $deplibs $compiler_flags' hardcode_libdir_flag_spec='-R$libdir' hardcode_direct=yes hardcode_shlibpath_var=no ;; hpux9*) if test yes = "$GCC"; then archive_cmds='$RM $output_objdir/$soname~$CC -shared $pic_flag $wl+b $wl$install_libdir -o $output_objdir/$soname $libobjs $deplibs $compiler_flags~test "x$output_objdir/$soname" = "x$lib" || mv $output_objdir/$soname $lib' else archive_cmds='$RM $output_objdir/$soname~$LD -b +b $install_libdir -o $output_objdir/$soname $libobjs $deplibs $linker_flags~test "x$output_objdir/$soname" = "x$lib" || mv $output_objdir/$soname $lib' fi hardcode_libdir_flag_spec='$wl+b $wl$libdir' hardcode_libdir_separator=: hardcode_direct=yes # hardcode_minus_L: Not really in the search PATH, # but as the default location of the library. hardcode_minus_L=yes export_dynamic_flag_spec='$wl-E' ;; hpux10*) if test yes,no = "$GCC,$with_gnu_ld"; then archive_cmds='$CC -shared $pic_flag $wl+h $wl$soname $wl+b $wl$install_libdir -o $lib $libobjs $deplibs $compiler_flags' else archive_cmds='$LD -b +h $soname +b $install_libdir -o $lib $libobjs $deplibs $linker_flags' fi if test no = "$with_gnu_ld"; then hardcode_libdir_flag_spec='$wl+b $wl$libdir' hardcode_libdir_separator=: hardcode_direct=yes hardcode_direct_absolute=yes export_dynamic_flag_spec='$wl-E' # hardcode_minus_L: Not really in the search PATH, # but as the default location of the library. hardcode_minus_L=yes fi ;; hpux11*) if test yes,no = "$GCC,$with_gnu_ld"; then case $host_cpu in hppa*64*) archive_cmds='$CC -shared $wl+h $wl$soname -o $lib $libobjs $deplibs $compiler_flags' ;; ia64*) archive_cmds='$CC -shared $pic_flag $wl+h $wl$soname $wl+nodefaultrpath -o $lib $libobjs $deplibs $compiler_flags' ;; *) archive_cmds='$CC -shared $pic_flag $wl+h $wl$soname $wl+b $wl$install_libdir -o $lib $libobjs $deplibs $compiler_flags' ;; esac else case $host_cpu in hppa*64*) archive_cmds='$CC -b $wl+h $wl$soname -o $lib $libobjs $deplibs $compiler_flags' ;; ia64*) archive_cmds='$CC -b $wl+h $wl$soname $wl+nodefaultrpath -o $lib $libobjs $deplibs $compiler_flags' ;; *) # Older versions of the 11.00 compiler do not understand -b yet # (HP92453-01 A.11.01.20 doesn't, HP92453-01 B.11.X.35175-35176.GP does) { $as_echo "$as_me:${as_lineno-$LINENO}: checking if $CC understands -b" >&5 $as_echo_n "checking if $CC understands -b... " >&6; } if ${lt_cv_prog_compiler__b+:} false; then : $as_echo_n "(cached) " >&6 else lt_cv_prog_compiler__b=no save_LDFLAGS=$LDFLAGS LDFLAGS="$LDFLAGS -b" echo "$lt_simple_link_test_code" > conftest.$ac_ext if (eval $ac_link 2>conftest.err) && test -s conftest$ac_exeext; then # The linker can only warn and ignore the option if not recognized # So say no if there are warnings if test -s conftest.err; then # Append any errors to the config.log. cat conftest.err 1>&5 $ECHO "$_lt_linker_boilerplate" | $SED '/^$/d' > conftest.exp $SED '/^$/d; /^ *+/d' conftest.err >conftest.er2 if diff conftest.exp conftest.er2 >/dev/null; then lt_cv_prog_compiler__b=yes fi else lt_cv_prog_compiler__b=yes fi fi $RM -r conftest* LDFLAGS=$save_LDFLAGS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $lt_cv_prog_compiler__b" >&5 $as_echo "$lt_cv_prog_compiler__b" >&6; } if test yes = "$lt_cv_prog_compiler__b"; then archive_cmds='$CC -b $wl+h $wl$soname $wl+b $wl$install_libdir -o $lib $libobjs $deplibs $compiler_flags' else archive_cmds='$LD -b +h $soname +b $install_libdir -o $lib $libobjs $deplibs $linker_flags' fi ;; esac fi if test no = "$with_gnu_ld"; then hardcode_libdir_flag_spec='$wl+b $wl$libdir' hardcode_libdir_separator=: case $host_cpu in hppa*64*|ia64*) hardcode_direct=no hardcode_shlibpath_var=no ;; *) hardcode_direct=yes hardcode_direct_absolute=yes export_dynamic_flag_spec='$wl-E' # hardcode_minus_L: Not really in the search PATH, # but as the default location of the library. hardcode_minus_L=yes ;; esac fi ;; irix5* | irix6* | nonstopux*) if test yes = "$GCC"; then archive_cmds='$CC -shared $pic_flag $libobjs $deplibs $compiler_flags $wl-soname $wl$soname `test -n "$verstring" && func_echo_all "$wl-set_version $wl$verstring"` $wl-update_registry $wl$output_objdir/so_locations -o $lib' # Try to use the -exported_symbol ld option, if it does not # work, assume that -exports_file does not work either and # implicitly export all symbols. # This should be the same for all languages, so no per-tag cache variable. { $as_echo "$as_me:${as_lineno-$LINENO}: checking whether the $host_os linker accepts -exported_symbol" >&5 $as_echo_n "checking whether the $host_os linker accepts -exported_symbol... " >&6; } if ${lt_cv_irix_exported_symbol+:} false; then : $as_echo_n "(cached) " >&6 else save_LDFLAGS=$LDFLAGS LDFLAGS="$LDFLAGS -shared $wl-exported_symbol ${wl}foo $wl-update_registry $wl/dev/null" cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ int foo (void) { return 0; } _ACEOF if ac_fn_c_try_link "$LINENO"; then : lt_cv_irix_exported_symbol=yes else lt_cv_irix_exported_symbol=no fi rm -f core conftest.err conftest.$ac_objext \ conftest$ac_exeext conftest.$ac_ext LDFLAGS=$save_LDFLAGS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $lt_cv_irix_exported_symbol" >&5 $as_echo "$lt_cv_irix_exported_symbol" >&6; } if test yes = "$lt_cv_irix_exported_symbol"; then archive_expsym_cmds='$CC -shared $pic_flag $libobjs $deplibs $compiler_flags $wl-soname $wl$soname `test -n "$verstring" && func_echo_all "$wl-set_version $wl$verstring"` $wl-update_registry $wl$output_objdir/so_locations $wl-exports_file $wl$export_symbols -o $lib' fi link_all_deplibs=no else archive_cmds='$CC -shared $libobjs $deplibs $compiler_flags -soname $soname `test -n "$verstring" && func_echo_all "-set_version $verstring"` -update_registry $output_objdir/so_locations -o $lib' archive_expsym_cmds='$CC -shared $libobjs $deplibs $compiler_flags -soname $soname `test -n "$verstring" && func_echo_all "-set_version $verstring"` -update_registry $output_objdir/so_locations -exports_file $export_symbols -o $lib' fi archive_cmds_need_lc='no' hardcode_libdir_flag_spec='$wl-rpath $wl$libdir' hardcode_libdir_separator=: inherit_rpath=yes link_all_deplibs=yes ;; linux*) case $cc_basename in tcc*) # Fabrice Bellard et al's Tiny C Compiler ld_shlibs=yes archive_cmds='$CC -shared $pic_flag -o $lib $libobjs $deplibs $compiler_flags' ;; esac ;; netbsd* | netbsdelf*-gnu) if echo __ELF__ | $CC -E - | $GREP __ELF__ >/dev/null; then archive_cmds='$LD -Bshareable -o $lib $libobjs $deplibs $linker_flags' # a.out else archive_cmds='$LD -shared -o $lib $libobjs $deplibs $linker_flags' # ELF fi hardcode_libdir_flag_spec='-R$libdir' hardcode_direct=yes hardcode_shlibpath_var=no ;; newsos6) archive_cmds='$LD -G -h $soname -o $lib $libobjs $deplibs $linker_flags' hardcode_direct=yes hardcode_libdir_flag_spec='$wl-rpath $wl$libdir' hardcode_libdir_separator=: hardcode_shlibpath_var=no ;; *nto* | *qnx*) ;; openbsd* | bitrig*) if test -f /usr/libexec/ld.so; then hardcode_direct=yes hardcode_shlibpath_var=no hardcode_direct_absolute=yes if test -z "`echo __ELF__ | $CC -E - | $GREP __ELF__`"; then archive_cmds='$CC -shared $pic_flag -o $lib $libobjs $deplibs $compiler_flags' archive_expsym_cmds='$CC -shared $pic_flag -o $lib $libobjs $deplibs $compiler_flags $wl-retain-symbols-file,$export_symbols' hardcode_libdir_flag_spec='$wl-rpath,$libdir' export_dynamic_flag_spec='$wl-E' else archive_cmds='$CC -shared $pic_flag -o $lib $libobjs $deplibs $compiler_flags' hardcode_libdir_flag_spec='$wl-rpath,$libdir' fi else ld_shlibs=no fi ;; os2*) hardcode_libdir_flag_spec='-L$libdir' hardcode_minus_L=yes allow_undefined_flag=unsupported shrext_cmds=.dll archive_cmds='$ECHO "LIBRARY ${soname%$shared_ext} INITINSTANCE TERMINSTANCE" > $output_objdir/$libname.def~ $ECHO "DESCRIPTION \"$libname\"" >> $output_objdir/$libname.def~ $ECHO "DATA MULTIPLE NONSHARED" >> $output_objdir/$libname.def~ $ECHO EXPORTS >> $output_objdir/$libname.def~ emxexp $libobjs | $SED /"_DLL_InitTerm"/d >> $output_objdir/$libname.def~ $CC -Zdll -Zcrtdll -o $output_objdir/$soname $libobjs $deplibs $compiler_flags $output_objdir/$libname.def~ emximp -o $lib $output_objdir/$libname.def' archive_expsym_cmds='$ECHO "LIBRARY ${soname%$shared_ext} INITINSTANCE TERMINSTANCE" > $output_objdir/$libname.def~ $ECHO "DESCRIPTION \"$libname\"" >> $output_objdir/$libname.def~ $ECHO "DATA MULTIPLE NONSHARED" >> $output_objdir/$libname.def~ $ECHO EXPORTS >> $output_objdir/$libname.def~ prefix_cmds="$SED"~ if test EXPORTS = "`$SED 1q $export_symbols`"; then prefix_cmds="$prefix_cmds -e 1d"; fi~ prefix_cmds="$prefix_cmds -e \"s/^\(.*\)$/_\1/g\""~ cat $export_symbols | $prefix_cmds >> $output_objdir/$libname.def~ $CC -Zdll -Zcrtdll -o $output_objdir/$soname $libobjs $deplibs $compiler_flags $output_objdir/$libname.def~ emximp -o $lib $output_objdir/$libname.def' old_archive_From_new_cmds='emximp -o $output_objdir/${libname}_dll.a $output_objdir/$libname.def' enable_shared_with_static_runtimes=yes ;; osf3*) if test yes = "$GCC"; then allow_undefined_flag=' $wl-expect_unresolved $wl\*' archive_cmds='$CC -shared$allow_undefined_flag $libobjs $deplibs $compiler_flags $wl-soname $wl$soname `test -n "$verstring" && func_echo_all "$wl-set_version $wl$verstring"` $wl-update_registry $wl$output_objdir/so_locations -o $lib' else allow_undefined_flag=' -expect_unresolved \*' archive_cmds='$CC -shared$allow_undefined_flag $libobjs $deplibs $compiler_flags -soname $soname `test -n "$verstring" && func_echo_all "-set_version $verstring"` -update_registry $output_objdir/so_locations -o $lib' fi archive_cmds_need_lc='no' hardcode_libdir_flag_spec='$wl-rpath $wl$libdir' hardcode_libdir_separator=: ;; osf4* | osf5*) # as osf3* with the addition of -msym flag if test yes = "$GCC"; then allow_undefined_flag=' $wl-expect_unresolved $wl\*' archive_cmds='$CC -shared$allow_undefined_flag $pic_flag $libobjs $deplibs $compiler_flags $wl-msym $wl-soname $wl$soname `test -n "$verstring" && func_echo_all "$wl-set_version $wl$verstring"` $wl-update_registry $wl$output_objdir/so_locations -o $lib' hardcode_libdir_flag_spec='$wl-rpath $wl$libdir' else allow_undefined_flag=' -expect_unresolved \*' archive_cmds='$CC -shared$allow_undefined_flag $libobjs $deplibs $compiler_flags -msym -soname $soname `test -n "$verstring" && func_echo_all "-set_version $verstring"` -update_registry $output_objdir/so_locations -o $lib' archive_expsym_cmds='for i in `cat $export_symbols`; do printf "%s %s\\n" -exported_symbol "\$i" >> $lib.exp; done; printf "%s\\n" "-hidden">> $lib.exp~ $CC -shared$allow_undefined_flag $wl-input $wl$lib.exp $compiler_flags $libobjs $deplibs -soname $soname `test -n "$verstring" && $ECHO "-set_version $verstring"` -update_registry $output_objdir/so_locations -o $lib~$RM $lib.exp' # Both c and cxx compiler support -rpath directly hardcode_libdir_flag_spec='-rpath $libdir' fi archive_cmds_need_lc='no' hardcode_libdir_separator=: ;; solaris*) no_undefined_flag=' -z defs' if test yes = "$GCC"; then wlarc='$wl' archive_cmds='$CC -shared $pic_flag $wl-z ${wl}text $wl-h $wl$soname -o $lib $libobjs $deplibs $compiler_flags' archive_expsym_cmds='echo "{ global:" > $lib.exp~cat $export_symbols | $SED -e "s/\(.*\)/\1;/" >> $lib.exp~echo "local: *; };" >> $lib.exp~ $CC -shared $pic_flag $wl-z ${wl}text $wl-M $wl$lib.exp $wl-h $wl$soname -o $lib $libobjs $deplibs $compiler_flags~$RM $lib.exp' else case `$CC -V 2>&1` in *"Compilers 5.0"*) wlarc='' archive_cmds='$LD -G$allow_undefined_flag -h $soname -o $lib $libobjs $deplibs $linker_flags' archive_expsym_cmds='echo "{ global:" > $lib.exp~cat $export_symbols | $SED -e "s/\(.*\)/\1;/" >> $lib.exp~echo "local: *; };" >> $lib.exp~ $LD -G$allow_undefined_flag -M $lib.exp -h $soname -o $lib $libobjs $deplibs $linker_flags~$RM $lib.exp' ;; *) wlarc='$wl' archive_cmds='$CC -G$allow_undefined_flag -h $soname -o $lib $libobjs $deplibs $compiler_flags' archive_expsym_cmds='echo "{ global:" > $lib.exp~cat $export_symbols | $SED -e "s/\(.*\)/\1;/" >> $lib.exp~echo "local: *; };" >> $lib.exp~ $CC -G$allow_undefined_flag -M $lib.exp -h $soname -o $lib $libobjs $deplibs $compiler_flags~$RM $lib.exp' ;; esac fi hardcode_libdir_flag_spec='-R$libdir' hardcode_shlibpath_var=no case $host_os in solaris2.[0-5] | solaris2.[0-5].*) ;; *) # The compiler driver will combine and reorder linker options, # but understands '-z linker_flag'. GCC discards it without '$wl', # but is careful enough not to reorder. # Supported since Solaris 2.6 (maybe 2.5.1?) if test yes = "$GCC"; then whole_archive_flag_spec='$wl-z ${wl}allextract$convenience $wl-z ${wl}defaultextract' else whole_archive_flag_spec='-z allextract$convenience -z defaultextract' fi ;; esac link_all_deplibs=yes ;; sunos4*) if test sequent = "$host_vendor"; then # Use $CC to link under sequent, because it throws in some extra .o # files that make .init and .fini sections work. archive_cmds='$CC -G $wl-h $soname -o $lib $libobjs $deplibs $compiler_flags' else archive_cmds='$LD -assert pure-text -Bstatic -o $lib $libobjs $deplibs $linker_flags' fi hardcode_libdir_flag_spec='-L$libdir' hardcode_direct=yes hardcode_minus_L=yes hardcode_shlibpath_var=no ;; sysv4) case $host_vendor in sni) archive_cmds='$LD -G -h $soname -o $lib $libobjs $deplibs $linker_flags' hardcode_direct=yes # is this really true??? ;; siemens) ## LD is ld it makes a PLAMLIB ## CC just makes a GrossModule. archive_cmds='$LD -G -o $lib $libobjs $deplibs $linker_flags' reload_cmds='$CC -r -o $output$reload_objs' hardcode_direct=no ;; motorola) archive_cmds='$LD -G -h $soname -o $lib $libobjs $deplibs $linker_flags' hardcode_direct=no #Motorola manual says yes, but my tests say they lie ;; esac runpath_var='LD_RUN_PATH' hardcode_shlibpath_var=no ;; sysv4.3*) archive_cmds='$LD -G -h $soname -o $lib $libobjs $deplibs $linker_flags' hardcode_shlibpath_var=no export_dynamic_flag_spec='-Bexport' ;; sysv4*MP*) if test -d /usr/nec; then archive_cmds='$LD -G -h $soname -o $lib $libobjs $deplibs $linker_flags' hardcode_shlibpath_var=no runpath_var=LD_RUN_PATH hardcode_runpath_var=yes ld_shlibs=yes fi ;; sysv4*uw2* | sysv5OpenUNIX* | sysv5UnixWare7.[01].[10]* | unixware7* | sco3.2v5.0.[024]*) no_undefined_flag='$wl-z,text' archive_cmds_need_lc=no hardcode_shlibpath_var=no runpath_var='LD_RUN_PATH' if test yes = "$GCC"; then archive_cmds='$CC -shared $wl-h,$soname -o $lib $libobjs $deplibs $compiler_flags' archive_expsym_cmds='$CC -shared $wl-Bexport:$export_symbols $wl-h,$soname -o $lib $libobjs $deplibs $compiler_flags' else archive_cmds='$CC -G $wl-h,$soname -o $lib $libobjs $deplibs $compiler_flags' archive_expsym_cmds='$CC -G $wl-Bexport:$export_symbols $wl-h,$soname -o $lib $libobjs $deplibs $compiler_flags' fi ;; sysv5* | sco3.2v5* | sco5v6*) # Note: We CANNOT use -z defs as we might desire, because we do not # link with -lc, and that would cause any symbols used from libc to # always be unresolved, which means just about no library would # ever link correctly. If we're not using GNU ld we use -z text # though, which does catch some bad symbols but isn't as heavy-handed # as -z defs. no_undefined_flag='$wl-z,text' allow_undefined_flag='$wl-z,nodefs' archive_cmds_need_lc=no hardcode_shlibpath_var=no hardcode_libdir_flag_spec='$wl-R,$libdir' hardcode_libdir_separator=':' link_all_deplibs=yes export_dynamic_flag_spec='$wl-Bexport' runpath_var='LD_RUN_PATH' if test yes = "$GCC"; then archive_cmds='$CC -shared $wl-h,$soname -o $lib $libobjs $deplibs $compiler_flags' archive_expsym_cmds='$CC -shared $wl-Bexport:$export_symbols $wl-h,$soname -o $lib $libobjs $deplibs $compiler_flags' else archive_cmds='$CC -G $wl-h,$soname -o $lib $libobjs $deplibs $compiler_flags' archive_expsym_cmds='$CC -G $wl-Bexport:$export_symbols $wl-h,$soname -o $lib $libobjs $deplibs $compiler_flags' fi ;; uts4*) archive_cmds='$LD -G -h $soname -o $lib $libobjs $deplibs $linker_flags' hardcode_libdir_flag_spec='-L$libdir' hardcode_shlibpath_var=no ;; *) ld_shlibs=no ;; esac if test sni = "$host_vendor"; then case $host in sysv4 | sysv4.2uw2* | sysv4.3* | sysv5*) export_dynamic_flag_spec='$wl-Blargedynsym' ;; esac fi fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ld_shlibs" >&5 $as_echo "$ld_shlibs" >&6; } test no = "$ld_shlibs" && can_build_shared=no with_gnu_ld=$with_gnu_ld # # Do we need to explicitly link libc? # case "x$archive_cmds_need_lc" in x|xyes) # Assume -lc should be added archive_cmds_need_lc=yes if test yes,yes = "$GCC,$enable_shared"; then case $archive_cmds in *'~'*) # FIXME: we may have to deal with multi-command sequences. ;; '$CC '*) # Test whether the compiler implicitly links with -lc since on some # systems, -lgcc has to come before -lc. If gcc already passes -lc # to ld, don't add -lc before -lgcc. { $as_echo "$as_me:${as_lineno-$LINENO}: checking whether -lc should be explicitly linked in" >&5 $as_echo_n "checking whether -lc should be explicitly linked in... " >&6; } if ${lt_cv_archive_cmds_need_lc+:} false; then : $as_echo_n "(cached) " >&6 else $RM conftest* echo "$lt_simple_compile_test_code" > conftest.$ac_ext if { { eval echo "\"\$as_me\":${as_lineno-$LINENO}: \"$ac_compile\""; } >&5 (eval $ac_compile) 2>&5 ac_status=$? $as_echo "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 test $ac_status = 0; } 2>conftest.err; then soname=conftest lib=conftest libobjs=conftest.$ac_objext deplibs= wl=$lt_prog_compiler_wl pic_flag=$lt_prog_compiler_pic compiler_flags=-v linker_flags=-v verstring= output_objdir=. libname=conftest lt_save_allow_undefined_flag=$allow_undefined_flag allow_undefined_flag= if { { eval echo "\"\$as_me\":${as_lineno-$LINENO}: \"$archive_cmds 2\>\&1 \| $GREP \" -lc \" \>/dev/null 2\>\&1\""; } >&5 (eval $archive_cmds 2\>\&1 \| $GREP \" -lc \" \>/dev/null 2\>\&1) 2>&5 ac_status=$? $as_echo "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 test $ac_status = 0; } then lt_cv_archive_cmds_need_lc=no else lt_cv_archive_cmds_need_lc=yes fi allow_undefined_flag=$lt_save_allow_undefined_flag else cat conftest.err 1>&5 fi $RM conftest* fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $lt_cv_archive_cmds_need_lc" >&5 $as_echo "$lt_cv_archive_cmds_need_lc" >&6; } archive_cmds_need_lc=$lt_cv_archive_cmds_need_lc ;; esac fi ;; esac { $as_echo "$as_me:${as_lineno-$LINENO}: checking dynamic linker characteristics" >&5 $as_echo_n "checking dynamic linker characteristics... " >&6; } if test yes = "$GCC"; then case $host_os in darwin*) lt_awk_arg='/^libraries:/,/LR/' ;; *) lt_awk_arg='/^libraries:/' ;; esac case $host_os in mingw* | cegcc*) lt_sed_strip_eq='s|=\([A-Za-z]:\)|\1|g' ;; *) lt_sed_strip_eq='s|=/|/|g' ;; esac lt_search_path_spec=`$CC -print-search-dirs | awk $lt_awk_arg | $SED -e "s/^libraries://" -e $lt_sed_strip_eq` case $lt_search_path_spec in *\;*) # if the path contains ";" then we assume it to be the separator # otherwise default to the standard path separator (i.e. ":") - it is # assumed that no part of a normal pathname contains ";" but that should # okay in the real world where ";" in dirpaths is itself problematic. lt_search_path_spec=`$ECHO "$lt_search_path_spec" | $SED 's/;/ /g'` ;; *) lt_search_path_spec=`$ECHO "$lt_search_path_spec" | $SED "s/$PATH_SEPARATOR/ /g"` ;; esac # Ok, now we have the path, separated by spaces, we can step through it # and add multilib dir if necessary... lt_tmp_lt_search_path_spec= lt_multi_os_dir=/`$CC $CPPFLAGS $CFLAGS $LDFLAGS -print-multi-os-directory 2>/dev/null` # ...but if some path component already ends with the multilib dir we assume # that all is fine and trust -print-search-dirs as is (GCC 4.2? or newer). case "$lt_multi_os_dir; $lt_search_path_spec " in "/; "* | "/.; "* | "/./; "* | *"$lt_multi_os_dir "* | *"$lt_multi_os_dir/ "*) lt_multi_os_dir= ;; esac for lt_sys_path in $lt_search_path_spec; do if test -d "$lt_sys_path$lt_multi_os_dir"; then lt_tmp_lt_search_path_spec="$lt_tmp_lt_search_path_spec $lt_sys_path$lt_multi_os_dir" elif test -n "$lt_multi_os_dir"; then test -d "$lt_sys_path" && \ lt_tmp_lt_search_path_spec="$lt_tmp_lt_search_path_spec $lt_sys_path" fi done lt_search_path_spec=`$ECHO "$lt_tmp_lt_search_path_spec" | awk ' BEGIN {RS = " "; FS = "/|\n";} { lt_foo = ""; lt_count = 0; for (lt_i = NF; lt_i > 0; lt_i--) { if ($lt_i != "" && $lt_i != ".") { if ($lt_i == "..") { lt_count++; } else { if (lt_count == 0) { lt_foo = "/" $lt_i lt_foo; } else { lt_count--; } } } } if (lt_foo != "") { lt_freq[lt_foo]++; } if (lt_freq[lt_foo] == 1) { print lt_foo; } }'` # AWK program above erroneously prepends '/' to C:/dos/paths # for these hosts. case $host_os in mingw* | cegcc*) lt_search_path_spec=`$ECHO "$lt_search_path_spec" |\ $SED 's|/\([A-Za-z]:\)|\1|g'` ;; esac sys_lib_search_path_spec=`$ECHO "$lt_search_path_spec" | $lt_NL2SP` else sys_lib_search_path_spec="/lib /usr/lib /usr/local/lib" fi library_names_spec= libname_spec='lib$name' soname_spec= shrext_cmds=.so postinstall_cmds= postuninstall_cmds= finish_cmds= finish_eval= shlibpath_var= shlibpath_overrides_runpath=unknown version_type=none dynamic_linker="$host_os ld.so" sys_lib_dlsearch_path_spec="/lib /usr/lib" need_lib_prefix=unknown hardcode_into_libs=no # when you set need_version to no, make sure it does not cause -set_version # flags to be left without arguments need_version=unknown case $host_os in aix3*) version_type=linux # correct to gnu/linux during the next big refactor library_names_spec='$libname$release$shared_ext$versuffix $libname.a' shlibpath_var=LIBPATH # AIX 3 has no versioning support, so we append a major version to the name. soname_spec='$libname$release$shared_ext$major' ;; aix[4-9]*) version_type=linux # correct to gnu/linux during the next big refactor need_lib_prefix=no need_version=no hardcode_into_libs=yes if test ia64 = "$host_cpu"; then # AIX 5 supports IA64 library_names_spec='$libname$release$shared_ext$major $libname$release$shared_ext$versuffix $libname$shared_ext' shlibpath_var=LD_LIBRARY_PATH else # With GCC up to 2.95.x, collect2 would create an import file # for dependence libraries. The import file would start with # the line '#! .'. This would cause the generated library to # depend on '.', always an invalid library. This was fixed in # development snapshots of GCC prior to 3.0. case $host_os in aix4 | aix4.[01] | aix4.[01].*) if { echo '#if __GNUC__ > 2 || (__GNUC__ == 2 && __GNUC_MINOR__ >= 97)' echo ' yes ' echo '#endif'; } | $CC -E - | $GREP yes > /dev/null; then : else can_build_shared=no fi ;; esac # Using Import Files as archive members, it is possible to support # filename-based versioning of shared library archives on AIX. While # this would work for both with and without runtime linking, it will # prevent static linking of such archives. So we do filename-based # shared library versioning with .so extension only, which is used # when both runtime linking and shared linking is enabled. # Unfortunately, runtime linking may impact performance, so we do # not want this to be the default eventually. Also, we use the # versioned .so libs for executables only if there is the -brtl # linker flag in LDFLAGS as well, or --with-aix-soname=svr4 only. # To allow for filename-based versioning support, we need to create # libNAME.so.V as an archive file, containing: # *) an Import File, referring to the versioned filename of the # archive as well as the shared archive member, telling the # bitwidth (32 or 64) of that shared object, and providing the # list of exported symbols of that shared object, eventually # decorated with the 'weak' keyword # *) the shared object with the F_LOADONLY flag set, to really avoid # it being seen by the linker. # At run time we better use the real file rather than another symlink, # but for link time we create the symlink libNAME.so -> libNAME.so.V case $with_aix_soname,$aix_use_runtimelinking in # AIX (on Power*) has no versioning support, so currently we cannot hardcode correct # soname into executable. Probably we can add versioning support to # collect2, so additional links can be useful in future. aix,yes) # traditional libtool dynamic_linker='AIX unversionable lib.so' # If using run time linking (on AIX 4.2 or later) use lib.so # instead of lib.a to let people know that these are not # typical AIX shared libraries. library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext' ;; aix,no) # traditional AIX only dynamic_linker='AIX lib.a(lib.so.V)' # We preserve .a as extension for shared libraries through AIX4.2 # and later when we are not doing run time linking. library_names_spec='$libname$release.a $libname.a' soname_spec='$libname$release$shared_ext$major' ;; svr4,*) # full svr4 only dynamic_linker="AIX lib.so.V($shared_archive_member_spec.o)" library_names_spec='$libname$release$shared_ext$major $libname$shared_ext' # We do not specify a path in Import Files, so LIBPATH fires. shlibpath_overrides_runpath=yes ;; *,yes) # both, prefer svr4 dynamic_linker="AIX lib.so.V($shared_archive_member_spec.o), lib.a(lib.so.V)" library_names_spec='$libname$release$shared_ext$major $libname$shared_ext' # unpreferred sharedlib libNAME.a needs extra handling postinstall_cmds='test -n "$linkname" || linkname="$realname"~func_stripname "" ".so" "$linkname"~$install_shared_prog "$dir/$func_stripname_result.$libext" "$destdir/$func_stripname_result.$libext"~test -z "$tstripme" || test -z "$striplib" || $striplib "$destdir/$func_stripname_result.$libext"' postuninstall_cmds='for n in $library_names $old_library; do :; done~func_stripname "" ".so" "$n"~test "$func_stripname_result" = "$n" || func_append rmfiles " $odir/$func_stripname_result.$libext"' # We do not specify a path in Import Files, so LIBPATH fires. shlibpath_overrides_runpath=yes ;; *,no) # both, prefer aix dynamic_linker="AIX lib.a(lib.so.V), lib.so.V($shared_archive_member_spec.o)" library_names_spec='$libname$release.a $libname.a' soname_spec='$libname$release$shared_ext$major' # unpreferred sharedlib libNAME.so.V and symlink libNAME.so need extra handling postinstall_cmds='test -z "$dlname" || $install_shared_prog $dir/$dlname $destdir/$dlname~test -z "$tstripme" || test -z "$striplib" || $striplib $destdir/$dlname~test -n "$linkname" || linkname=$realname~func_stripname "" ".a" "$linkname"~(cd "$destdir" && $LN_S -f $dlname $func_stripname_result.so)' postuninstall_cmds='test -z "$dlname" || func_append rmfiles " $odir/$dlname"~for n in $old_library $library_names; do :; done~func_stripname "" ".a" "$n"~func_append rmfiles " $odir/$func_stripname_result.so"' ;; esac shlibpath_var=LIBPATH fi ;; amigaos*) case $host_cpu in powerpc) # Since July 2007 AmigaOS4 officially supports .so libraries. # When compiling the executable, add -use-dynld -Lsobjs: to the compileline. library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext' ;; m68k) library_names_spec='$libname.ixlibrary $libname.a' # Create ${libname}_ixlibrary.a entries in /sys/libs. finish_eval='for lib in `ls $libdir/*.ixlibrary 2>/dev/null`; do libname=`func_echo_all "$lib" | $SED '\''s%^.*/\([^/]*\)\.ixlibrary$%\1%'\''`; $RM /sys/libs/${libname}_ixlibrary.a; $show "cd /sys/libs && $LN_S $lib ${libname}_ixlibrary.a"; cd /sys/libs && $LN_S $lib ${libname}_ixlibrary.a || exit 1; done' ;; esac ;; beos*) library_names_spec='$libname$shared_ext' dynamic_linker="$host_os ld.so" shlibpath_var=LIBRARY_PATH ;; bsdi[45]*) version_type=linux # correct to gnu/linux during the next big refactor need_version=no library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext' soname_spec='$libname$release$shared_ext$major' finish_cmds='PATH="\$PATH:/sbin" ldconfig $libdir' shlibpath_var=LD_LIBRARY_PATH sys_lib_search_path_spec="/shlib /usr/lib /usr/X11/lib /usr/contrib/lib /lib /usr/local/lib" sys_lib_dlsearch_path_spec="/shlib /usr/lib /usr/local/lib" # the default ld.so.conf also contains /usr/contrib/lib and # /usr/X11R6/lib (/usr/X11 is a link to /usr/X11R6), but let us allow # libtool to hard-code these into programs ;; cygwin* | mingw* | pw32* | cegcc*) version_type=windows shrext_cmds=.dll need_version=no need_lib_prefix=no case $GCC,$cc_basename in yes,*) # gcc library_names_spec='$libname.dll.a' # DLL is installed to $(libdir)/../bin by postinstall_cmds postinstall_cmds='base_file=`basename \$file`~ dlpath=`$SHELL 2>&1 -c '\''. $dir/'\''\$base_file'\''i; echo \$dlname'\''`~ dldir=$destdir/`dirname \$dlpath`~ test -d \$dldir || mkdir -p \$dldir~ $install_prog $dir/$dlname \$dldir/$dlname~ chmod a+x \$dldir/$dlname~ if test -n '\''$stripme'\'' && test -n '\''$striplib'\''; then eval '\''$striplib \$dldir/$dlname'\'' || exit \$?; fi' postuninstall_cmds='dldll=`$SHELL 2>&1 -c '\''. $file; echo \$dlname'\''`~ dlpath=$dir/\$dldll~ $RM \$dlpath' shlibpath_overrides_runpath=yes case $host_os in cygwin*) # Cygwin DLLs use 'cyg' prefix rather than 'lib' soname_spec='`echo $libname | sed -e 's/^lib/cyg/'``echo $release | $SED -e 's/[.]/-/g'`$versuffix$shared_ext' sys_lib_search_path_spec="$sys_lib_search_path_spec /usr/lib/w32api" ;; mingw* | cegcc*) # MinGW DLLs use traditional 'lib' prefix soname_spec='$libname`echo $release | $SED -e 's/[.]/-/g'`$versuffix$shared_ext' ;; pw32*) # pw32 DLLs use 'pw' prefix rather than 'lib' library_names_spec='`echo $libname | sed -e 's/^lib/pw/'``echo $release | $SED -e 's/[.]/-/g'`$versuffix$shared_ext' ;; esac dynamic_linker='Win32 ld.exe' ;; *,cl*) # Native MSVC libname_spec='$name' soname_spec='$libname`echo $release | $SED -e 's/[.]/-/g'`$versuffix$shared_ext' library_names_spec='$libname.dll.lib' case $build_os in mingw*) sys_lib_search_path_spec= lt_save_ifs=$IFS IFS=';' for lt_path in $LIB do IFS=$lt_save_ifs # Let DOS variable expansion print the short 8.3 style file name. lt_path=`cd "$lt_path" 2>/dev/null && cmd //C "for %i in (".") do @echo %~si"` sys_lib_search_path_spec="$sys_lib_search_path_spec $lt_path" done IFS=$lt_save_ifs # Convert to MSYS style. sys_lib_search_path_spec=`$ECHO "$sys_lib_search_path_spec" | sed -e 's|\\\\|/|g' -e 's| \\([a-zA-Z]\\):| /\\1|g' -e 's|^ ||'` ;; cygwin*) # Convert to unix form, then to dos form, then back to unix form # but this time dos style (no spaces!) so that the unix form looks # like /cygdrive/c/PROGRA~1:/cygdr... sys_lib_search_path_spec=`cygpath --path --unix "$LIB"` sys_lib_search_path_spec=`cygpath --path --dos "$sys_lib_search_path_spec" 2>/dev/null` sys_lib_search_path_spec=`cygpath --path --unix "$sys_lib_search_path_spec" | $SED -e "s/$PATH_SEPARATOR/ /g"` ;; *) sys_lib_search_path_spec=$LIB if $ECHO "$sys_lib_search_path_spec" | $GREP ';[c-zC-Z]:/' >/dev/null; then # It is most probably a Windows format PATH. sys_lib_search_path_spec=`$ECHO "$sys_lib_search_path_spec" | $SED -e 's/;/ /g'` else sys_lib_search_path_spec=`$ECHO "$sys_lib_search_path_spec" | $SED -e "s/$PATH_SEPARATOR/ /g"` fi # FIXME: find the short name or the path components, as spaces are # common. (e.g. "Program Files" -> "PROGRA~1") ;; esac # DLL is installed to $(libdir)/../bin by postinstall_cmds postinstall_cmds='base_file=`basename \$file`~ dlpath=`$SHELL 2>&1 -c '\''. $dir/'\''\$base_file'\''i; echo \$dlname'\''`~ dldir=$destdir/`dirname \$dlpath`~ test -d \$dldir || mkdir -p \$dldir~ $install_prog $dir/$dlname \$dldir/$dlname' postuninstall_cmds='dldll=`$SHELL 2>&1 -c '\''. $file; echo \$dlname'\''`~ dlpath=$dir/\$dldll~ $RM \$dlpath' shlibpath_overrides_runpath=yes dynamic_linker='Win32 link.exe' ;; *) # Assume MSVC wrapper library_names_spec='$libname`echo $release | $SED -e 's/[.]/-/g'`$versuffix$shared_ext $libname.lib' dynamic_linker='Win32 ld.exe' ;; esac # FIXME: first we should search . and the directory the executable is in shlibpath_var=PATH ;; darwin* | rhapsody*) dynamic_linker="$host_os dyld" version_type=darwin need_lib_prefix=no need_version=no library_names_spec='$libname$release$major$shared_ext $libname$shared_ext' soname_spec='$libname$release$major$shared_ext' shlibpath_overrides_runpath=yes shlibpath_var=DYLD_LIBRARY_PATH shrext_cmds='`test .$module = .yes && echo .so || echo .dylib`' sys_lib_search_path_spec="$sys_lib_search_path_spec /usr/local/lib" sys_lib_dlsearch_path_spec='/usr/local/lib /lib /usr/lib' ;; dgux*) version_type=linux # correct to gnu/linux during the next big refactor need_lib_prefix=no need_version=no library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext' soname_spec='$libname$release$shared_ext$major' shlibpath_var=LD_LIBRARY_PATH ;; freebsd* | dragonfly*) # DragonFly does not have aout. When/if they implement a new # versioning mechanism, adjust this. if test -x /usr/bin/objformat; then objformat=`/usr/bin/objformat` else case $host_os in freebsd[23].*) objformat=aout ;; *) objformat=elf ;; esac fi version_type=freebsd-$objformat case $version_type in freebsd-elf*) library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext' soname_spec='$libname$release$shared_ext$major' need_version=no need_lib_prefix=no ;; freebsd-*) library_names_spec='$libname$release$shared_ext$versuffix $libname$shared_ext$versuffix' need_version=yes ;; esac shlibpath_var=LD_LIBRARY_PATH case $host_os in freebsd2.*) shlibpath_overrides_runpath=yes ;; freebsd3.[01]* | freebsdelf3.[01]*) shlibpath_overrides_runpath=yes hardcode_into_libs=yes ;; freebsd3.[2-9]* | freebsdelf3.[2-9]* | \ freebsd4.[0-5] | freebsdelf4.[0-5] | freebsd4.1.1 | freebsdelf4.1.1) shlibpath_overrides_runpath=no hardcode_into_libs=yes ;; *) # from 4.6 on, and DragonFly shlibpath_overrides_runpath=yes hardcode_into_libs=yes ;; esac ;; haiku*) version_type=linux # correct to gnu/linux during the next big refactor need_lib_prefix=no need_version=no dynamic_linker="$host_os runtime_loader" library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext' soname_spec='$libname$release$shared_ext$major' shlibpath_var=LIBRARY_PATH shlibpath_overrides_runpath=no sys_lib_dlsearch_path_spec='/boot/home/config/lib /boot/common/lib /boot/system/lib' hardcode_into_libs=yes ;; hpux9* | hpux10* | hpux11*) # Give a soname corresponding to the major version so that dld.sl refuses to # link against other versions. version_type=sunos need_lib_prefix=no need_version=no case $host_cpu in ia64*) shrext_cmds='.so' hardcode_into_libs=yes dynamic_linker="$host_os dld.so" shlibpath_var=LD_LIBRARY_PATH shlibpath_overrides_runpath=yes # Unless +noenvvar is specified. library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext' soname_spec='$libname$release$shared_ext$major' if test 32 = "$HPUX_IA64_MODE"; then sys_lib_search_path_spec="/usr/lib/hpux32 /usr/local/lib/hpux32 /usr/local/lib" sys_lib_dlsearch_path_spec=/usr/lib/hpux32 else sys_lib_search_path_spec="/usr/lib/hpux64 /usr/local/lib/hpux64" sys_lib_dlsearch_path_spec=/usr/lib/hpux64 fi ;; hppa*64*) shrext_cmds='.sl' hardcode_into_libs=yes dynamic_linker="$host_os dld.sl" shlibpath_var=LD_LIBRARY_PATH # How should we handle SHLIB_PATH shlibpath_overrides_runpath=yes # Unless +noenvvar is specified. library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext' soname_spec='$libname$release$shared_ext$major' sys_lib_search_path_spec="/usr/lib/pa20_64 /usr/ccs/lib/pa20_64" sys_lib_dlsearch_path_spec=$sys_lib_search_path_spec ;; *) shrext_cmds='.sl' dynamic_linker="$host_os dld.sl" shlibpath_var=SHLIB_PATH shlibpath_overrides_runpath=no # +s is required to enable SHLIB_PATH library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext' soname_spec='$libname$release$shared_ext$major' ;; esac # HP-UX runs *really* slowly unless shared libraries are mode 555, ... postinstall_cmds='chmod 555 $lib' # or fails outright, so override atomically: install_override_mode=555 ;; interix[3-9]*) version_type=linux # correct to gnu/linux during the next big refactor need_lib_prefix=no need_version=no library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext' soname_spec='$libname$release$shared_ext$major' dynamic_linker='Interix 3.x ld.so.1 (PE, like ELF)' shlibpath_var=LD_LIBRARY_PATH shlibpath_overrides_runpath=no hardcode_into_libs=yes ;; irix5* | irix6* | nonstopux*) case $host_os in nonstopux*) version_type=nonstopux ;; *) if test yes = "$lt_cv_prog_gnu_ld"; then version_type=linux # correct to gnu/linux during the next big refactor else version_type=irix fi ;; esac need_lib_prefix=no need_version=no soname_spec='$libname$release$shared_ext$major' library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$release$shared_ext $libname$shared_ext' case $host_os in irix5* | nonstopux*) libsuff= shlibsuff= ;; *) case $LD in # libtool.m4 will add one of these switches to LD *-32|*"-32 "|*-melf32bsmip|*"-melf32bsmip ") libsuff= shlibsuff= libmagic=32-bit;; *-n32|*"-n32 "|*-melf32bmipn32|*"-melf32bmipn32 ") libsuff=32 shlibsuff=N32 libmagic=N32;; *-64|*"-64 "|*-melf64bmip|*"-melf64bmip ") libsuff=64 shlibsuff=64 libmagic=64-bit;; *) libsuff= shlibsuff= libmagic=never-match;; esac ;; esac shlibpath_var=LD_LIBRARY${shlibsuff}_PATH shlibpath_overrides_runpath=no sys_lib_search_path_spec="/usr/lib$libsuff /lib$libsuff /usr/local/lib$libsuff" sys_lib_dlsearch_path_spec="/usr/lib$libsuff /lib$libsuff" hardcode_into_libs=yes ;; # No shared lib support for Linux oldld, aout, or coff. linux*oldld* | linux*aout* | linux*coff*) dynamic_linker=no ;; linux*android*) version_type=none # Android doesn't support versioned libraries. need_lib_prefix=no need_version=no library_names_spec='$libname$release$shared_ext' soname_spec='$libname$release$shared_ext' finish_cmds= shlibpath_var=LD_LIBRARY_PATH shlibpath_overrides_runpath=yes # This implies no fast_install, which is unacceptable. # Some rework will be needed to allow for fast_install # before this can be enabled. hardcode_into_libs=yes dynamic_linker='Android linker' # Don't embed -rpath directories since the linker doesn't support them. hardcode_libdir_flag_spec='-L$libdir' ;; # This must be glibc/ELF. linux* | k*bsd*-gnu | kopensolaris*-gnu | gnu*) version_type=linux # correct to gnu/linux during the next big refactor need_lib_prefix=no need_version=no library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext' soname_spec='$libname$release$shared_ext$major' finish_cmds='PATH="\$PATH:/sbin" ldconfig -n $libdir' shlibpath_var=LD_LIBRARY_PATH shlibpath_overrides_runpath=no # Some binutils ld are patched to set DT_RUNPATH if ${lt_cv_shlibpath_overrides_runpath+:} false; then : $as_echo_n "(cached) " >&6 else lt_cv_shlibpath_overrides_runpath=no save_LDFLAGS=$LDFLAGS save_libdir=$libdir eval "libdir=/foo; wl=\"$lt_prog_compiler_wl\"; \ LDFLAGS=\"\$LDFLAGS $hardcode_libdir_flag_spec\"" cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ int main () { ; return 0; } _ACEOF if ac_fn_c_try_link "$LINENO"; then : if ($OBJDUMP -p conftest$ac_exeext) 2>/dev/null | grep "RUNPATH.*$libdir" >/dev/null; then : lt_cv_shlibpath_overrides_runpath=yes fi fi rm -f core conftest.err conftest.$ac_objext \ conftest$ac_exeext conftest.$ac_ext LDFLAGS=$save_LDFLAGS libdir=$save_libdir fi shlibpath_overrides_runpath=$lt_cv_shlibpath_overrides_runpath # This implies no fast_install, which is unacceptable. # Some rework will be needed to allow for fast_install # before this can be enabled. hardcode_into_libs=yes # Ideally, we could use ldconfig to report *all* directores which are # searched for libraries, however this is still not possible. Aside from not # being certain /sbin/ldconfig is available, command # 'ldconfig -N -X -v | grep ^/' on 64bit Fedora does not report /usr/lib64, # even though it is searched at run-time. Try to do the best guess by # appending ld.so.conf contents (and includes) to the search path. if test -f /etc/ld.so.conf; then lt_ld_extra=`awk '/^include / { system(sprintf("cd /etc; cat %s 2>/dev/null", \$2)); skip = 1; } { if (!skip) print \$0; skip = 0; }' < /etc/ld.so.conf | $SED -e 's/#.*//;/^[ ]*hwcap[ ]/d;s/[:, ]/ /g;s/=[^=]*$//;s/=[^= ]* / /g;s/"//g;/^$/d' | tr '\n' ' '` sys_lib_dlsearch_path_spec="/lib /usr/lib $lt_ld_extra" fi # We used to test for /lib/ld.so.1 and disable shared libraries on # powerpc, because MkLinux only supported shared libraries with the # GNU dynamic linker. Since this was broken with cross compilers, # most powerpc-linux boxes support dynamic linking these days and # people can always --disable-shared, the test was removed, and we # assume the GNU/Linux dynamic linker is in use. dynamic_linker='GNU/Linux ld.so' ;; netbsdelf*-gnu) version_type=linux need_lib_prefix=no need_version=no library_names_spec='${libname}${release}${shared_ext}$versuffix ${libname}${release}${shared_ext}$major ${libname}${shared_ext}' soname_spec='${libname}${release}${shared_ext}$major' shlibpath_var=LD_LIBRARY_PATH shlibpath_overrides_runpath=no hardcode_into_libs=yes dynamic_linker='NetBSD ld.elf_so' ;; netbsd*) version_type=sunos need_lib_prefix=no need_version=no if echo __ELF__ | $CC -E - | $GREP __ELF__ >/dev/null; then library_names_spec='$libname$release$shared_ext$versuffix $libname$shared_ext$versuffix' finish_cmds='PATH="\$PATH:/sbin" ldconfig -m $libdir' dynamic_linker='NetBSD (a.out) ld.so' else library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext' soname_spec='$libname$release$shared_ext$major' dynamic_linker='NetBSD ld.elf_so' fi shlibpath_var=LD_LIBRARY_PATH shlibpath_overrides_runpath=yes hardcode_into_libs=yes ;; newsos6) version_type=linux # correct to gnu/linux during the next big refactor library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext' shlibpath_var=LD_LIBRARY_PATH shlibpath_overrides_runpath=yes ;; *nto* | *qnx*) version_type=qnx need_lib_prefix=no need_version=no library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext' soname_spec='$libname$release$shared_ext$major' shlibpath_var=LD_LIBRARY_PATH shlibpath_overrides_runpath=no hardcode_into_libs=yes dynamic_linker='ldqnx.so' ;; openbsd* | bitrig*) version_type=sunos sys_lib_dlsearch_path_spec=/usr/lib need_lib_prefix=no if test -z "`echo __ELF__ | $CC -E - | $GREP __ELF__`"; then need_version=no else need_version=yes fi library_names_spec='$libname$release$shared_ext$versuffix $libname$shared_ext$versuffix' finish_cmds='PATH="\$PATH:/sbin" ldconfig -m $libdir' shlibpath_var=LD_LIBRARY_PATH shlibpath_overrides_runpath=yes ;; os2*) libname_spec='$name' version_type=windows shrext_cmds=.dll need_version=no need_lib_prefix=no # OS/2 can only load a DLL with a base name of 8 characters or less. soname_spec='`test -n "$os2dllname" && libname="$os2dllname"; v=$($ECHO $release$versuffix | tr -d .-); n=$($ECHO $libname | cut -b -$((8 - ${#v})) | tr . _); $ECHO $n$v`$shared_ext' library_names_spec='${libname}_dll.$libext' dynamic_linker='OS/2 ld.exe' shlibpath_var=BEGINLIBPATH sys_lib_search_path_spec="/lib /usr/lib /usr/local/lib" sys_lib_dlsearch_path_spec=$sys_lib_search_path_spec postinstall_cmds='base_file=`basename \$file`~ dlpath=`$SHELL 2>&1 -c '\''. $dir/'\''\$base_file'\''i; $ECHO \$dlname'\''`~ dldir=$destdir/`dirname \$dlpath`~ test -d \$dldir || mkdir -p \$dldir~ $install_prog $dir/$dlname \$dldir/$dlname~ chmod a+x \$dldir/$dlname~ if test -n '\''$stripme'\'' && test -n '\''$striplib'\''; then eval '\''$striplib \$dldir/$dlname'\'' || exit \$?; fi' postuninstall_cmds='dldll=`$SHELL 2>&1 -c '\''. $file; $ECHO \$dlname'\''`~ dlpath=$dir/\$dldll~ $RM \$dlpath' ;; osf3* | osf4* | osf5*) version_type=osf need_lib_prefix=no need_version=no soname_spec='$libname$release$shared_ext$major' library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext' shlibpath_var=LD_LIBRARY_PATH sys_lib_search_path_spec="/usr/shlib /usr/ccs/lib /usr/lib/cmplrs/cc /usr/lib /usr/local/lib /var/shlib" sys_lib_dlsearch_path_spec=$sys_lib_search_path_spec ;; rdos*) dynamic_linker=no ;; solaris*) version_type=linux # correct to gnu/linux during the next big refactor need_lib_prefix=no need_version=no library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext' soname_spec='$libname$release$shared_ext$major' shlibpath_var=LD_LIBRARY_PATH shlibpath_overrides_runpath=yes hardcode_into_libs=yes # ldd complains unless libraries are executable postinstall_cmds='chmod +x $lib' ;; sunos4*) version_type=sunos library_names_spec='$libname$release$shared_ext$versuffix $libname$shared_ext$versuffix' finish_cmds='PATH="\$PATH:/usr/etc" ldconfig $libdir' shlibpath_var=LD_LIBRARY_PATH shlibpath_overrides_runpath=yes if test yes = "$with_gnu_ld"; then need_lib_prefix=no fi need_version=yes ;; sysv4 | sysv4.3*) version_type=linux # correct to gnu/linux during the next big refactor library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext' soname_spec='$libname$release$shared_ext$major' shlibpath_var=LD_LIBRARY_PATH case $host_vendor in sni) shlibpath_overrides_runpath=no need_lib_prefix=no runpath_var=LD_RUN_PATH ;; siemens) need_lib_prefix=no ;; motorola) need_lib_prefix=no need_version=no shlibpath_overrides_runpath=no sys_lib_search_path_spec='/lib /usr/lib /usr/ccs/lib' ;; esac ;; sysv4*MP*) if test -d /usr/nec; then version_type=linux # correct to gnu/linux during the next big refactor library_names_spec='$libname$shared_ext.$versuffix $libname$shared_ext.$major $libname$shared_ext' soname_spec='$libname$shared_ext.$major' shlibpath_var=LD_LIBRARY_PATH fi ;; sysv5* | sco3.2v5* | sco5v6* | unixware* | OpenUNIX* | sysv4*uw2*) version_type=sco need_lib_prefix=no need_version=no library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext $libname$shared_ext' soname_spec='$libname$release$shared_ext$major' shlibpath_var=LD_LIBRARY_PATH shlibpath_overrides_runpath=yes hardcode_into_libs=yes if test yes = "$with_gnu_ld"; then sys_lib_search_path_spec='/usr/local/lib /usr/gnu/lib /usr/ccs/lib /usr/lib /lib' else sys_lib_search_path_spec='/usr/ccs/lib /usr/lib' case $host_os in sco3.2v5*) sys_lib_search_path_spec="$sys_lib_search_path_spec /lib" ;; esac fi sys_lib_dlsearch_path_spec='/usr/lib' ;; tpf*) # TPF is a cross-target only. Preferred cross-host = GNU/Linux. version_type=linux # correct to gnu/linux during the next big refactor need_lib_prefix=no need_version=no library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext' shlibpath_var=LD_LIBRARY_PATH shlibpath_overrides_runpath=no hardcode_into_libs=yes ;; uts4*) version_type=linux # correct to gnu/linux during the next big refactor library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext' soname_spec='$libname$release$shared_ext$major' shlibpath_var=LD_LIBRARY_PATH ;; *) dynamic_linker=no ;; esac { $as_echo "$as_me:${as_lineno-$LINENO}: result: $dynamic_linker" >&5 $as_echo "$dynamic_linker" >&6; } test no = "$dynamic_linker" && can_build_shared=no variables_saved_for_relink="PATH $shlibpath_var $runpath_var" if test yes = "$GCC"; then variables_saved_for_relink="$variables_saved_for_relink GCC_EXEC_PREFIX COMPILER_PATH LIBRARY_PATH" fi if test set = "${lt_cv_sys_lib_search_path_spec+set}"; then sys_lib_search_path_spec=$lt_cv_sys_lib_search_path_spec fi if test set = "${lt_cv_sys_lib_dlsearch_path_spec+set}"; then sys_lib_dlsearch_path_spec=$lt_cv_sys_lib_dlsearch_path_spec fi # remember unaugmented sys_lib_dlsearch_path content for libtool script decls... configure_time_dlsearch_path=$sys_lib_dlsearch_path_spec # ... but it needs LT_SYS_LIBRARY_PATH munging for other configure-time code func_munge_path_list sys_lib_dlsearch_path_spec "$LT_SYS_LIBRARY_PATH" # to be used as default LT_SYS_LIBRARY_PATH value in generated libtool configure_time_lt_sys_library_path=$LT_SYS_LIBRARY_PATH { $as_echo "$as_me:${as_lineno-$LINENO}: checking how to hardcode library paths into programs" >&5 $as_echo_n "checking how to hardcode library paths into programs... " >&6; } hardcode_action= if test -n "$hardcode_libdir_flag_spec" || test -n "$runpath_var" || test yes = "$hardcode_automatic"; then # We can hardcode non-existent directories. if test no != "$hardcode_direct" && # If the only mechanism to avoid hardcoding is shlibpath_var, we # have to relink, otherwise we might link with an installed library # when we should be linking with a yet-to-be-installed one ## test no != "$_LT_TAGVAR(hardcode_shlibpath_var, )" && test no != "$hardcode_minus_L"; then # Linking always hardcodes the temporary library directory. hardcode_action=relink else # We can link without hardcoding, and we can hardcode nonexisting dirs. hardcode_action=immediate fi else # We cannot hardcode anything, or else we can only hardcode existing # directories. hardcode_action=unsupported fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $hardcode_action" >&5 $as_echo "$hardcode_action" >&6; } if test relink = "$hardcode_action" || test yes = "$inherit_rpath"; then # Fast installation is not supported enable_fast_install=no elif test yes = "$shlibpath_overrides_runpath" || test no = "$enable_shared"; then # Fast installation is not necessary enable_fast_install=needless fi if test yes != "$enable_dlopen"; then enable_dlopen=unknown enable_dlopen_self=unknown enable_dlopen_self_static=unknown else lt_cv_dlopen=no lt_cv_dlopen_libs= case $host_os in beos*) lt_cv_dlopen=load_add_on lt_cv_dlopen_libs= lt_cv_dlopen_self=yes ;; mingw* | pw32* | cegcc*) lt_cv_dlopen=LoadLibrary lt_cv_dlopen_libs= ;; cygwin*) lt_cv_dlopen=dlopen lt_cv_dlopen_libs= ;; darwin*) # if libdl is installed we need to link against it { $as_echo "$as_me:${as_lineno-$LINENO}: checking for dlopen in -ldl" >&5 $as_echo_n "checking for dlopen in -ldl... " >&6; } if ${ac_cv_lib_dl_dlopen+:} false; then : $as_echo_n "(cached) " >&6 else ac_check_lib_save_LIBS=$LIBS LIBS="-ldl $LIBS" cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ /* Override any GCC internal prototype to avoid an error. Use char because int might match the return type of a GCC builtin and then its argument prototype would still apply. */ #ifdef __cplusplus extern "C" #endif char dlopen (); int main () { return dlopen (); ; return 0; } _ACEOF if ac_fn_c_try_link "$LINENO"; then : ac_cv_lib_dl_dlopen=yes else ac_cv_lib_dl_dlopen=no fi rm -f core conftest.err conftest.$ac_objext \ conftest$ac_exeext conftest.$ac_ext LIBS=$ac_check_lib_save_LIBS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_dl_dlopen" >&5 $as_echo "$ac_cv_lib_dl_dlopen" >&6; } if test "x$ac_cv_lib_dl_dlopen" = xyes; then : lt_cv_dlopen=dlopen lt_cv_dlopen_libs=-ldl else lt_cv_dlopen=dyld lt_cv_dlopen_libs= lt_cv_dlopen_self=yes fi ;; tpf*) # Don't try to run any link tests for TPF. We know it's impossible # because TPF is a cross-compiler, and we know how we open DSOs. lt_cv_dlopen=dlopen lt_cv_dlopen_libs= lt_cv_dlopen_self=no ;; *) ac_fn_c_check_func "$LINENO" "shl_load" "ac_cv_func_shl_load" if test "x$ac_cv_func_shl_load" = xyes; then : lt_cv_dlopen=shl_load else { $as_echo "$as_me:${as_lineno-$LINENO}: checking for shl_load in -ldld" >&5 $as_echo_n "checking for shl_load in -ldld... " >&6; } if ${ac_cv_lib_dld_shl_load+:} false; then : $as_echo_n "(cached) " >&6 else ac_check_lib_save_LIBS=$LIBS LIBS="-ldld $LIBS" cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ /* Override any GCC internal prototype to avoid an error. Use char because int might match the return type of a GCC builtin and then its argument prototype would still apply. */ #ifdef __cplusplus extern "C" #endif char shl_load (); int main () { return shl_load (); ; return 0; } _ACEOF if ac_fn_c_try_link "$LINENO"; then : ac_cv_lib_dld_shl_load=yes else ac_cv_lib_dld_shl_load=no fi rm -f core conftest.err conftest.$ac_objext \ conftest$ac_exeext conftest.$ac_ext LIBS=$ac_check_lib_save_LIBS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_dld_shl_load" >&5 $as_echo "$ac_cv_lib_dld_shl_load" >&6; } if test "x$ac_cv_lib_dld_shl_load" = xyes; then : lt_cv_dlopen=shl_load lt_cv_dlopen_libs=-ldld else ac_fn_c_check_func "$LINENO" "dlopen" "ac_cv_func_dlopen" if test "x$ac_cv_func_dlopen" = xyes; then : lt_cv_dlopen=dlopen else { $as_echo "$as_me:${as_lineno-$LINENO}: checking for dlopen in -ldl" >&5 $as_echo_n "checking for dlopen in -ldl... " >&6; } if ${ac_cv_lib_dl_dlopen+:} false; then : $as_echo_n "(cached) " >&6 else ac_check_lib_save_LIBS=$LIBS LIBS="-ldl $LIBS" cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ /* Override any GCC internal prototype to avoid an error. Use char because int might match the return type of a GCC builtin and then its argument prototype would still apply. */ #ifdef __cplusplus extern "C" #endif char dlopen (); int main () { return dlopen (); ; return 0; } _ACEOF if ac_fn_c_try_link "$LINENO"; then : ac_cv_lib_dl_dlopen=yes else ac_cv_lib_dl_dlopen=no fi rm -f core conftest.err conftest.$ac_objext \ conftest$ac_exeext conftest.$ac_ext LIBS=$ac_check_lib_save_LIBS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_dl_dlopen" >&5 $as_echo "$ac_cv_lib_dl_dlopen" >&6; } if test "x$ac_cv_lib_dl_dlopen" = xyes; then : lt_cv_dlopen=dlopen lt_cv_dlopen_libs=-ldl else { $as_echo "$as_me:${as_lineno-$LINENO}: checking for dlopen in -lsvld" >&5 $as_echo_n "checking for dlopen in -lsvld... " >&6; } if ${ac_cv_lib_svld_dlopen+:} false; then : $as_echo_n "(cached) " >&6 else ac_check_lib_save_LIBS=$LIBS LIBS="-lsvld $LIBS" cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ /* Override any GCC internal prototype to avoid an error. Use char because int might match the return type of a GCC builtin and then its argument prototype would still apply. */ #ifdef __cplusplus extern "C" #endif char dlopen (); int main () { return dlopen (); ; return 0; } _ACEOF if ac_fn_c_try_link "$LINENO"; then : ac_cv_lib_svld_dlopen=yes else ac_cv_lib_svld_dlopen=no fi rm -f core conftest.err conftest.$ac_objext \ conftest$ac_exeext conftest.$ac_ext LIBS=$ac_check_lib_save_LIBS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_svld_dlopen" >&5 $as_echo "$ac_cv_lib_svld_dlopen" >&6; } if test "x$ac_cv_lib_svld_dlopen" = xyes; then : lt_cv_dlopen=dlopen lt_cv_dlopen_libs=-lsvld else { $as_echo "$as_me:${as_lineno-$LINENO}: checking for dld_link in -ldld" >&5 $as_echo_n "checking for dld_link in -ldld... " >&6; } if ${ac_cv_lib_dld_dld_link+:} false; then : $as_echo_n "(cached) " >&6 else ac_check_lib_save_LIBS=$LIBS LIBS="-ldld $LIBS" cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ /* Override any GCC internal prototype to avoid an error. Use char because int might match the return type of a GCC builtin and then its argument prototype would still apply. */ #ifdef __cplusplus extern "C" #endif char dld_link (); int main () { return dld_link (); ; return 0; } _ACEOF if ac_fn_c_try_link "$LINENO"; then : ac_cv_lib_dld_dld_link=yes else ac_cv_lib_dld_dld_link=no fi rm -f core conftest.err conftest.$ac_objext \ conftest$ac_exeext conftest.$ac_ext LIBS=$ac_check_lib_save_LIBS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_dld_dld_link" >&5 $as_echo "$ac_cv_lib_dld_dld_link" >&6; } if test "x$ac_cv_lib_dld_dld_link" = xyes; then : lt_cv_dlopen=dld_link lt_cv_dlopen_libs=-ldld fi fi fi fi fi fi ;; esac if test no = "$lt_cv_dlopen"; then enable_dlopen=no else enable_dlopen=yes fi case $lt_cv_dlopen in dlopen) save_CPPFLAGS=$CPPFLAGS test yes = "$ac_cv_header_dlfcn_h" && CPPFLAGS="$CPPFLAGS -DHAVE_DLFCN_H" save_LDFLAGS=$LDFLAGS wl=$lt_prog_compiler_wl eval LDFLAGS=\"\$LDFLAGS $export_dynamic_flag_spec\" save_LIBS=$LIBS LIBS="$lt_cv_dlopen_libs $LIBS" { $as_echo "$as_me:${as_lineno-$LINENO}: checking whether a program can dlopen itself" >&5 $as_echo_n "checking whether a program can dlopen itself... " >&6; } if ${lt_cv_dlopen_self+:} false; then : $as_echo_n "(cached) " >&6 else if test yes = "$cross_compiling"; then : lt_cv_dlopen_self=cross else lt_dlunknown=0; lt_dlno_uscore=1; lt_dlneed_uscore=2 lt_status=$lt_dlunknown cat > conftest.$ac_ext <<_LT_EOF #line $LINENO "configure" #include "confdefs.h" #if HAVE_DLFCN_H #include #endif #include #ifdef RTLD_GLOBAL # define LT_DLGLOBAL RTLD_GLOBAL #else # ifdef DL_GLOBAL # define LT_DLGLOBAL DL_GLOBAL # else # define LT_DLGLOBAL 0 # endif #endif /* We may have to define LT_DLLAZY_OR_NOW in the command line if we find out it does not work in some platform. */ #ifndef LT_DLLAZY_OR_NOW # ifdef RTLD_LAZY # define LT_DLLAZY_OR_NOW RTLD_LAZY # else # ifdef DL_LAZY # define LT_DLLAZY_OR_NOW DL_LAZY # else # ifdef RTLD_NOW # define LT_DLLAZY_OR_NOW RTLD_NOW # else # ifdef DL_NOW # define LT_DLLAZY_OR_NOW DL_NOW # else # define LT_DLLAZY_OR_NOW 0 # endif # endif # endif # endif #endif /* When -fvisibility=hidden is used, assume the code has been annotated correspondingly for the symbols needed. */ #if defined __GNUC__ && (((__GNUC__ == 3) && (__GNUC_MINOR__ >= 3)) || (__GNUC__ > 3)) int fnord () __attribute__((visibility("default"))); #endif int fnord () { return 42; } int main () { void *self = dlopen (0, LT_DLGLOBAL|LT_DLLAZY_OR_NOW); int status = $lt_dlunknown; if (self) { if (dlsym (self,"fnord")) status = $lt_dlno_uscore; else { if (dlsym( self,"_fnord")) status = $lt_dlneed_uscore; else puts (dlerror ()); } /* dlclose (self); */ } else puts (dlerror ()); return status; } _LT_EOF if { { eval echo "\"\$as_me\":${as_lineno-$LINENO}: \"$ac_link\""; } >&5 (eval $ac_link) 2>&5 ac_status=$? $as_echo "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 test $ac_status = 0; } && test -s "conftest$ac_exeext" 2>/dev/null; then (./conftest; exit; ) >&5 2>/dev/null lt_status=$? case x$lt_status in x$lt_dlno_uscore) lt_cv_dlopen_self=yes ;; x$lt_dlneed_uscore) lt_cv_dlopen_self=yes ;; x$lt_dlunknown|x*) lt_cv_dlopen_self=no ;; esac else : # compilation failed lt_cv_dlopen_self=no fi fi rm -fr conftest* fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $lt_cv_dlopen_self" >&5 $as_echo "$lt_cv_dlopen_self" >&6; } if test yes = "$lt_cv_dlopen_self"; then wl=$lt_prog_compiler_wl eval LDFLAGS=\"\$LDFLAGS $lt_prog_compiler_static\" { $as_echo "$as_me:${as_lineno-$LINENO}: checking whether a statically linked program can dlopen itself" >&5 $as_echo_n "checking whether a statically linked program can dlopen itself... " >&6; } if ${lt_cv_dlopen_self_static+:} false; then : $as_echo_n "(cached) " >&6 else if test yes = "$cross_compiling"; then : lt_cv_dlopen_self_static=cross else lt_dlunknown=0; lt_dlno_uscore=1; lt_dlneed_uscore=2 lt_status=$lt_dlunknown cat > conftest.$ac_ext <<_LT_EOF #line $LINENO "configure" #include "confdefs.h" #if HAVE_DLFCN_H #include #endif #include #ifdef RTLD_GLOBAL # define LT_DLGLOBAL RTLD_GLOBAL #else # ifdef DL_GLOBAL # define LT_DLGLOBAL DL_GLOBAL # else # define LT_DLGLOBAL 0 # endif #endif /* We may have to define LT_DLLAZY_OR_NOW in the command line if we find out it does not work in some platform. */ #ifndef LT_DLLAZY_OR_NOW # ifdef RTLD_LAZY # define LT_DLLAZY_OR_NOW RTLD_LAZY # else # ifdef DL_LAZY # define LT_DLLAZY_OR_NOW DL_LAZY # else # ifdef RTLD_NOW # define LT_DLLAZY_OR_NOW RTLD_NOW # else # ifdef DL_NOW # define LT_DLLAZY_OR_NOW DL_NOW # else # define LT_DLLAZY_OR_NOW 0 # endif # endif # endif # endif #endif /* When -fvisibility=hidden is used, assume the code has been annotated correspondingly for the symbols needed. */ #if defined __GNUC__ && (((__GNUC__ == 3) && (__GNUC_MINOR__ >= 3)) || (__GNUC__ > 3)) int fnord () __attribute__((visibility("default"))); #endif int fnord () { return 42; } int main () { void *self = dlopen (0, LT_DLGLOBAL|LT_DLLAZY_OR_NOW); int status = $lt_dlunknown; if (self) { if (dlsym (self,"fnord")) status = $lt_dlno_uscore; else { if (dlsym( self,"_fnord")) status = $lt_dlneed_uscore; else puts (dlerror ()); } /* dlclose (self); */ } else puts (dlerror ()); return status; } _LT_EOF if { { eval echo "\"\$as_me\":${as_lineno-$LINENO}: \"$ac_link\""; } >&5 (eval $ac_link) 2>&5 ac_status=$? $as_echo "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 test $ac_status = 0; } && test -s "conftest$ac_exeext" 2>/dev/null; then (./conftest; exit; ) >&5 2>/dev/null lt_status=$? case x$lt_status in x$lt_dlno_uscore) lt_cv_dlopen_self_static=yes ;; x$lt_dlneed_uscore) lt_cv_dlopen_self_static=yes ;; x$lt_dlunknown|x*) lt_cv_dlopen_self_static=no ;; esac else : # compilation failed lt_cv_dlopen_self_static=no fi fi rm -fr conftest* fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $lt_cv_dlopen_self_static" >&5 $as_echo "$lt_cv_dlopen_self_static" >&6; } fi CPPFLAGS=$save_CPPFLAGS LDFLAGS=$save_LDFLAGS LIBS=$save_LIBS ;; esac case $lt_cv_dlopen_self in yes|no) enable_dlopen_self=$lt_cv_dlopen_self ;; *) enable_dlopen_self=unknown ;; esac case $lt_cv_dlopen_self_static in yes|no) enable_dlopen_self_static=$lt_cv_dlopen_self_static ;; *) enable_dlopen_self_static=unknown ;; esac fi striplib= old_striplib= { $as_echo "$as_me:${as_lineno-$LINENO}: checking whether stripping libraries is possible" >&5 $as_echo_n "checking whether stripping libraries is possible... " >&6; } if test -n "$STRIP" && $STRIP -V 2>&1 | $GREP "GNU strip" >/dev/null; then test -z "$old_striplib" && old_striplib="$STRIP --strip-debug" test -z "$striplib" && striplib="$STRIP --strip-unneeded" { $as_echo "$as_me:${as_lineno-$LINENO}: result: yes" >&5 $as_echo "yes" >&6; } else # FIXME - insert some real tests, host_os isn't really good enough case $host_os in darwin*) if test -n "$STRIP"; then striplib="$STRIP -x" old_striplib="$STRIP -S" { $as_echo "$as_me:${as_lineno-$LINENO}: result: yes" >&5 $as_echo "yes" >&6; } else { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 $as_echo "no" >&6; } fi ;; *) { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 $as_echo "no" >&6; } ;; esac fi # Report what library types will actually be built { $as_echo "$as_me:${as_lineno-$LINENO}: checking if libtool supports shared libraries" >&5 $as_echo_n "checking if libtool supports shared libraries... " >&6; } { $as_echo "$as_me:${as_lineno-$LINENO}: result: $can_build_shared" >&5 $as_echo "$can_build_shared" >&6; } { $as_echo "$as_me:${as_lineno-$LINENO}: checking whether to build shared libraries" >&5 $as_echo_n "checking whether to build shared libraries... " >&6; } test no = "$can_build_shared" && enable_shared=no # On AIX, shared libraries and static libraries use the same namespace, and # are all built from PIC. case $host_os in aix3*) test yes = "$enable_shared" && enable_static=no if test -n "$RANLIB"; then archive_cmds="$archive_cmds~\$RANLIB \$lib" postinstall_cmds='$RANLIB $lib' fi ;; aix[4-9]*) if test ia64 != "$host_cpu"; then case $enable_shared,$with_aix_soname,$aix_use_runtimelinking in yes,aix,yes) ;; # shared object as lib.so file only yes,svr4,*) ;; # shared object as lib.so archive member only yes,*) enable_static=no ;; # shared object in lib.a archive as well esac fi ;; esac { $as_echo "$as_me:${as_lineno-$LINENO}: result: $enable_shared" >&5 $as_echo "$enable_shared" >&6; } { $as_echo "$as_me:${as_lineno-$LINENO}: checking whether to build static libraries" >&5 $as_echo_n "checking whether to build static libraries... " >&6; } # Make sure either enable_shared or enable_static is yes. test yes = "$enable_shared" || enable_static=yes { $as_echo "$as_me:${as_lineno-$LINENO}: result: $enable_static" >&5 $as_echo "$enable_static" >&6; } fi ac_ext=c ac_cpp='$CPP $CPPFLAGS' ac_compile='$CC -c $CFLAGS $CPPFLAGS conftest.$ac_ext >&5' ac_link='$CC -o conftest$ac_exeext $CFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS >&5' ac_compiler_gnu=$ac_cv_c_compiler_gnu CC=$lt_save_CC ac_config_commands="$ac_config_commands libtool" # Only expand once: # The cast to long int works around a bug in the HP C Compiler # version HP92453-01 B.11.11.23709.GP, which incorrectly rejects # declarations like `int a3[[(sizeof (unsigned char)) >= 0]];'. # This bug is HP SR number 8606223364. { $as_echo "$as_me:${as_lineno-$LINENO}: checking size of int" >&5 $as_echo_n "checking size of int... " >&6; } if ${ac_cv_sizeof_int+:} false; then : $as_echo_n "(cached) " >&6 else if ac_fn_c_compute_int "$LINENO" "(long int) (sizeof (int))" "ac_cv_sizeof_int" "$ac_includes_default"; then : else if test "$ac_cv_type_int" = yes; then { { $as_echo "$as_me:${as_lineno-$LINENO}: error: in \`$ac_pwd':" >&5 $as_echo "$as_me: error: in \`$ac_pwd':" >&2;} as_fn_error 77 "cannot compute sizeof (int) See \`config.log' for more details" "$LINENO" 5; } else ac_cv_sizeof_int=0 fi fi fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_sizeof_int" >&5 $as_echo "$ac_cv_sizeof_int" >&6; } cat >>confdefs.h <<_ACEOF #define SIZEOF_INT $ac_cv_sizeof_int _ACEOF # The cast to long int works around a bug in the HP C Compiler # version HP92453-01 B.11.11.23709.GP, which incorrectly rejects # declarations like `int a3[[(sizeof (unsigned char)) >= 0]];'. # This bug is HP SR number 8606223364. { $as_echo "$as_me:${as_lineno-$LINENO}: checking size of long" >&5 $as_echo_n "checking size of long... " >&6; } if ${ac_cv_sizeof_long+:} false; then : $as_echo_n "(cached) " >&6 else if ac_fn_c_compute_int "$LINENO" "(long int) (sizeof (long))" "ac_cv_sizeof_long" "$ac_includes_default"; then : else if test "$ac_cv_type_long" = yes; then { { $as_echo "$as_me:${as_lineno-$LINENO}: error: in \`$ac_pwd':" >&5 $as_echo "$as_me: error: in \`$ac_pwd':" >&2;} as_fn_error 77 "cannot compute sizeof (long) See \`config.log' for more details" "$LINENO" 5; } else ac_cv_sizeof_long=0 fi fi fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_sizeof_long" >&5 $as_echo "$ac_cv_sizeof_long" >&6; } cat >>confdefs.h <<_ACEOF #define SIZEOF_LONG $ac_cv_sizeof_long _ACEOF # The cast to long int works around a bug in the HP C Compiler # version HP92453-01 B.11.11.23709.GP, which incorrectly rejects # declarations like `int a3[[(sizeof (unsigned char)) >= 0]];'. # This bug is HP SR number 8606223364. { $as_echo "$as_me:${as_lineno-$LINENO}: checking size of size_t" >&5 $as_echo_n "checking size of size_t... " >&6; } if ${ac_cv_sizeof_size_t+:} false; then : $as_echo_n "(cached) " >&6 else if ac_fn_c_compute_int "$LINENO" "(long int) (sizeof (size_t))" "ac_cv_sizeof_size_t" "$ac_includes_default"; then : else if test "$ac_cv_type_size_t" = yes; then { { $as_echo "$as_me:${as_lineno-$LINENO}: error: in \`$ac_pwd':" >&5 $as_echo "$as_me: error: in \`$ac_pwd':" >&2;} as_fn_error 77 "cannot compute sizeof (size_t) See \`config.log' for more details" "$LINENO" 5; } else ac_cv_sizeof_size_t=0 fi fi fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_sizeof_size_t" >&5 $as_echo "$ac_cv_sizeof_size_t" >&6; } cat >>confdefs.h <<_ACEOF #define SIZEOF_SIZE_T $ac_cv_sizeof_size_t _ACEOF # The cast to long int works around a bug in the HP C Compiler # version HP92453-01 B.11.11.23709.GP, which incorrectly rejects # declarations like `int a3[[(sizeof (unsigned char)) >= 0]];'. # This bug is HP SR number 8606223364. { $as_echo "$as_me:${as_lineno-$LINENO}: checking size of off_t" >&5 $as_echo_n "checking size of off_t... " >&6; } if ${ac_cv_sizeof_off_t+:} false; then : $as_echo_n "(cached) " >&6 else if ac_fn_c_compute_int "$LINENO" "(long int) (sizeof (off_t))" "ac_cv_sizeof_off_t" "$ac_includes_default"; then : else if test "$ac_cv_type_off_t" = yes; then { { $as_echo "$as_me:${as_lineno-$LINENO}: error: in \`$ac_pwd':" >&5 $as_echo "$as_me: error: in \`$ac_pwd':" >&2;} as_fn_error 77 "cannot compute sizeof (off_t) See \`config.log' for more details" "$LINENO" 5; } else ac_cv_sizeof_off_t=0 fi fi fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_sizeof_off_t" >&5 $as_echo "$ac_cv_sizeof_off_t" >&6; } cat >>confdefs.h <<_ACEOF #define SIZEOF_OFF_T $ac_cv_sizeof_off_t _ACEOF # The cast to long int works around a bug in the HP C Compiler # version HP92453-01 B.11.11.23709.GP, which incorrectly rejects # declarations like `int a3[[(sizeof (unsigned char)) >= 0]];'. # This bug is HP SR number 8606223364. { $as_echo "$as_me:${as_lineno-$LINENO}: checking size of long long int" >&5 $as_echo_n "checking size of long long int... " >&6; } if ${ac_cv_sizeof_long_long_int+:} false; then : $as_echo_n "(cached) " >&6 else if ac_fn_c_compute_int "$LINENO" "(long int) (sizeof (long long int))" "ac_cv_sizeof_long_long_int" "$ac_includes_default"; then : else if test "$ac_cv_type_long_long_int" = yes; then { { $as_echo "$as_me:${as_lineno-$LINENO}: error: in \`$ac_pwd':" >&5 $as_echo "$as_me: error: in \`$ac_pwd':" >&2;} as_fn_error 77 "cannot compute sizeof (long long int) See \`config.log' for more details" "$LINENO" 5; } else ac_cv_sizeof_long_long_int=0 fi fi fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_sizeof_long_long_int" >&5 $as_echo "$ac_cv_sizeof_long_long_int" >&6; } cat >>confdefs.h <<_ACEOF #define SIZEOF_LONG_LONG_INT $ac_cv_sizeof_long_long_int _ACEOF # The cast to long int works around a bug in the HP C Compiler # version HP92453-01 B.11.11.23709.GP, which incorrectly rejects # declarations like `int a3[[(sizeof (unsigned char)) >= 0]];'. # This bug is HP SR number 8606223364. { $as_echo "$as_me:${as_lineno-$LINENO}: checking size of unsigned long long int" >&5 $as_echo_n "checking size of unsigned long long int... " >&6; } if ${ac_cv_sizeof_unsigned_long_long_int+:} false; then : $as_echo_n "(cached) " >&6 else if ac_fn_c_compute_int "$LINENO" "(long int) (sizeof (unsigned long long int))" "ac_cv_sizeof_unsigned_long_long_int" "$ac_includes_default"; then : else if test "$ac_cv_type_unsigned_long_long_int" = yes; then { { $as_echo "$as_me:${as_lineno-$LINENO}: error: in \`$ac_pwd':" >&5 $as_echo "$as_me: error: in \`$ac_pwd':" >&2;} as_fn_error 77 "cannot compute sizeof (unsigned long long int) See \`config.log' for more details" "$LINENO" 5; } else ac_cv_sizeof_unsigned_long_long_int=0 fi fi fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_sizeof_unsigned_long_long_int" >&5 $as_echo "$ac_cv_sizeof_unsigned_long_long_int" >&6; } cat >>confdefs.h <<_ACEOF #define SIZEOF_UNSIGNED_LONG_LONG_INT $ac_cv_sizeof_unsigned_long_long_int _ACEOF if test "$ac_cv_sizeof_long_long_int" -eq 8 -a \ "$ac_cv_sizeof_unsigned_long_long_int" -eq 8; then { $as_echo "$as_me:${as_lineno-$LINENO}: checking whether byte ordering is bigendian" >&5 $as_echo_n "checking whether byte ordering is bigendian... " >&6; } if ${ac_cv_c_bigendian+:} false; then : $as_echo_n "(cached) " >&6 else ac_cv_c_bigendian=unknown # See if we're dealing with a universal compiler. cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ #ifndef __APPLE_CC__ not a universal capable compiler #endif typedef int dummy; _ACEOF if ac_fn_c_try_compile "$LINENO"; then : # Check for potential -arch flags. It is not universal unless # there are at least two -arch flags with different values. ac_arch= ac_prev= for ac_word in $CC $CFLAGS $CPPFLAGS $LDFLAGS; do if test -n "$ac_prev"; then case $ac_word in i?86 | x86_64 | ppc | ppc64) if test -z "$ac_arch" || test "$ac_arch" = "$ac_word"; then ac_arch=$ac_word else ac_cv_c_bigendian=universal break fi ;; esac ac_prev= elif test "x$ac_word" = "x-arch"; then ac_prev=arch fi done fi rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext if test $ac_cv_c_bigendian = unknown; then # See if sys/param.h defines the BYTE_ORDER macro. cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ #include #include int main () { #if ! (defined BYTE_ORDER && defined BIG_ENDIAN \ && defined LITTLE_ENDIAN && BYTE_ORDER && BIG_ENDIAN \ && LITTLE_ENDIAN) bogus endian macros #endif ; return 0; } _ACEOF if ac_fn_c_try_compile "$LINENO"; then : # It does; now see whether it defined to BIG_ENDIAN or not. cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ #include #include int main () { #if BYTE_ORDER != BIG_ENDIAN not big endian #endif ; return 0; } _ACEOF if ac_fn_c_try_compile "$LINENO"; then : ac_cv_c_bigendian=yes else ac_cv_c_bigendian=no fi rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext fi rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext fi if test $ac_cv_c_bigendian = unknown; then # See if defines _LITTLE_ENDIAN or _BIG_ENDIAN (e.g., Solaris). cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ #include int main () { #if ! (defined _LITTLE_ENDIAN || defined _BIG_ENDIAN) bogus endian macros #endif ; return 0; } _ACEOF if ac_fn_c_try_compile "$LINENO"; then : # It does; now see whether it defined to _BIG_ENDIAN or not. cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ #include int main () { #ifndef _BIG_ENDIAN not big endian #endif ; return 0; } _ACEOF if ac_fn_c_try_compile "$LINENO"; then : ac_cv_c_bigendian=yes else ac_cv_c_bigendian=no fi rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext fi rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext fi if test $ac_cv_c_bigendian = unknown; then # Compile a test program. if test "$cross_compiling" = yes; then : # Try to guess by grepping values from an object file. cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ short int ascii_mm[] = { 0x4249, 0x4765, 0x6E44, 0x6961, 0x6E53, 0x7953, 0 }; short int ascii_ii[] = { 0x694C, 0x5454, 0x656C, 0x6E45, 0x6944, 0x6E61, 0 }; int use_ascii (int i) { return ascii_mm[i] + ascii_ii[i]; } short int ebcdic_ii[] = { 0x89D3, 0xE3E3, 0x8593, 0x95C5, 0x89C4, 0x9581, 0 }; short int ebcdic_mm[] = { 0xC2C9, 0xC785, 0x95C4, 0x8981, 0x95E2, 0xA8E2, 0 }; int use_ebcdic (int i) { return ebcdic_mm[i] + ebcdic_ii[i]; } extern int foo; int main () { return use_ascii (foo) == use_ebcdic (foo); ; return 0; } _ACEOF if ac_fn_c_try_compile "$LINENO"; then : if grep BIGenDianSyS conftest.$ac_objext >/dev/null; then ac_cv_c_bigendian=yes fi if grep LiTTleEnDian conftest.$ac_objext >/dev/null ; then if test "$ac_cv_c_bigendian" = unknown; then ac_cv_c_bigendian=no else # finding both strings is unlikely to happen, but who knows? ac_cv_c_bigendian=unknown fi fi fi rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext else cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ $ac_includes_default int main () { /* Are we little or big endian? From Harbison&Steele. */ union { long int l; char c[sizeof (long int)]; } u; u.l = 1; return u.c[sizeof (long int) - 1] == 1; ; return 0; } _ACEOF if ac_fn_c_try_run "$LINENO"; then : ac_cv_c_bigendian=no else ac_cv_c_bigendian=yes fi rm -f core *.core core.conftest.* gmon.out bb.out conftest$ac_exeext \ conftest.$ac_objext conftest.beam conftest.$ac_ext fi fi fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_c_bigendian" >&5 $as_echo "$ac_cv_c_bigendian" >&6; } case $ac_cv_c_bigendian in #( yes) $as_echo "#define WORDS_BIGENDIAN 1" >>confdefs.h ;; #( no) ;; #( universal) $as_echo "#define AC_APPLE_UNIVERSAL_BUILD 1" >>confdefs.h ;; #( *) as_fn_error $? "unknown endianness presetting ac_cv_c_bigendian=no (or yes) will help" "$LINENO" 5 ;; esac else as_fn_error $? "The Cyrus IMAPD requires support for long long int" "$LINENO" 5 fi { $as_echo "$as_me:${as_lineno-$LINENO}: checking if compiler supports -fPIC" >&5 $as_echo_n "checking if compiler supports -fPIC... " >&6; } if ${ac_cv_fpic+:} false; then : $as_echo_n "(cached) " >&6 else save_CFLAGS=$CFLAGS CFLAGS="${CFLAGS} -fPIC" cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ #include static void foo(void) { exit(1); } int main () { ; return 0; } _ACEOF if ac_fn_c_try_compile "$LINENO"; then : ac_cv_fpic=yes else ac_cv_fpic=no fi rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext CFLAGS=$save_CFLAGS fi if test "$ac_cv_fpic" = "yes"; then FPIC_CFLAGS="-fPIC" else FPIC_CFLAGS="" fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_fpic" >&5 $as_echo "$ac_cv_fpic" >&6; } # CMU GUESS RUNPATH SWITCH { $as_echo "$as_me:${as_lineno-$LINENO}: checking for runpath switch" >&5 $as_echo_n "checking for runpath switch... " >&6; } if ${andrew_cv_runpath_switch+:} false; then : $as_echo_n "(cached) " >&6 else # first, try -R SAVE_LDFLAGS="${LDFLAGS}" LDFLAGS="-R /usr/lib" cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ int main () { ; return 0; } _ACEOF if ac_fn_c_try_link "$LINENO"; then : andrew_cv_runpath_switch="-R" else LDFLAGS="-Wl,-rpath,/usr/lib" cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ int main () { ; return 0; } _ACEOF if ac_fn_c_try_link "$LINENO"; then : andrew_cv_runpath_switch="-Wl,-rpath," else andrew_cv_runpath_switch="none" fi rm -f core conftest.err conftest.$ac_objext \ conftest$ac_exeext conftest.$ac_ext fi rm -f core conftest.err conftest.$ac_objext \ conftest$ac_exeext conftest.$ac_ext LDFLAGS="${SAVE_LDFLAGS}" fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $andrew_cv_runpath_switch" >&5 $as_echo "$andrew_cv_runpath_switch" >&6; } for ac_header in unistd.h sys/select.h sys/param.h stdarg.h do : as_ac_Header=`$as_echo "ac_cv_header_$ac_header" | $as_tr_sh` ac_fn_c_check_header_mongrel "$LINENO" "$ac_header" "$as_ac_Header" "$ac_includes_default" if eval test \"x\$"$as_ac_Header"\" = x"yes"; then : cat >>confdefs.h <<_ACEOF #define `$as_echo "HAVE_$ac_header" | $as_tr_cpp` 1 _ACEOF fi done ac_fn_c_check_func "$LINENO" "memmove" "ac_cv_func_memmove" if test "x$ac_cv_func_memmove" = xyes; then : $as_echo "#define HAVE_MEMMOVE 1" >>confdefs.h else case " $LIBOBJS " in *" memmove.$ac_objext "* ) ;; *) LIBOBJS="$LIBOBJS memmove.$ac_objext" ;; esac fi ac_fn_c_check_func "$LINENO" "strcasecmp" "ac_cv_func_strcasecmp" if test "x$ac_cv_func_strcasecmp" = xyes; then : $as_echo "#define HAVE_STRCASECMP 1" >>confdefs.h else case " $LIBOBJS " in *" strcasecmp.$ac_objext "* ) ;; *) LIBOBJS="$LIBOBJS strcasecmp.$ac_objext" ;; esac fi ac_fn_c_check_func "$LINENO" "ftruncate" "ac_cv_func_ftruncate" if test "x$ac_cv_func_ftruncate" = xyes; then : $as_echo "#define HAVE_FTRUNCATE 1" >>confdefs.h else case " $LIBOBJS " in *" ftruncate.$ac_objext "* ) ;; *) LIBOBJS="$LIBOBJS ftruncate.$ac_objext" ;; esac fi ac_fn_c_check_func "$LINENO" "strerror" "ac_cv_func_strerror" if test "x$ac_cv_func_strerror" = xyes; then : $as_echo "#define HAVE_STRERROR 1" >>confdefs.h else case " $LIBOBJS " in *" strerror.$ac_objext "* ) ;; *) LIBOBJS="$LIBOBJS strerror.$ac_objext" ;; esac fi ac_fn_c_check_func "$LINENO" "posix_fadvise" "ac_cv_func_posix_fadvise" if test "x$ac_cv_func_posix_fadvise" = xyes; then : $as_echo "#define HAVE_POSIX_FADVISE 1" >>confdefs.h else case " $LIBOBJS " in *" posix_fadvise.$ac_objext "* ) ;; *) LIBOBJS="$LIBOBJS posix_fadvise.$ac_objext" ;; esac fi ac_fn_c_check_func "$LINENO" "strsep" "ac_cv_func_strsep" if test "x$ac_cv_func_strsep" = xyes; then : $as_echo "#define HAVE_STRSEP 1" >>confdefs.h else case " $LIBOBJS " in *" strsep.$ac_objext "* ) ;; *) LIBOBJS="$LIBOBJS strsep.$ac_objext" ;; esac fi ac_fn_c_check_func "$LINENO" "memmem" "ac_cv_func_memmem" if test "x$ac_cv_func_memmem" = xyes; then : $as_echo "#define HAVE_MEMMEM 1" >>confdefs.h else case " $LIBOBJS " in *" memmem.$ac_objext "* ) ;; *) LIBOBJS="$LIBOBJS memmem.$ac_objext" ;; esac fi for ac_func in strlcat strlcpy getgrouplist fmemopen pselect do : as_ac_var=`$as_echo "ac_cv_func_$ac_func" | $as_tr_sh` ac_fn_c_check_func "$LINENO" "$ac_func" "$as_ac_var" if eval test \"x\$"$as_ac_var"\" = x"yes"; then : cat >>confdefs.h <<_ACEOF #define `$as_echo "HAVE_$ac_func" | $as_tr_cpp` 1 _ACEOF fi done ac_header_dirent=no for ac_hdr in dirent.h sys/ndir.h sys/dir.h ndir.h; do as_ac_Header=`$as_echo "ac_cv_header_dirent_$ac_hdr" | $as_tr_sh` { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_hdr that defines DIR" >&5 $as_echo_n "checking for $ac_hdr that defines DIR... " >&6; } if eval \${$as_ac_Header+:} false; then : $as_echo_n "(cached) " >&6 else cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ #include #include <$ac_hdr> int main () { if ((DIR *) 0) return 0; ; return 0; } _ACEOF if ac_fn_c_try_compile "$LINENO"; then : eval "$as_ac_Header=yes" else eval "$as_ac_Header=no" fi rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext fi eval ac_res=\$$as_ac_Header { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_res" >&5 $as_echo "$ac_res" >&6; } if eval test \"x\$"$as_ac_Header"\" = x"yes"; then : cat >>confdefs.h <<_ACEOF #define `$as_echo "HAVE_$ac_hdr" | $as_tr_cpp` 1 _ACEOF ac_header_dirent=$ac_hdr; break fi done # Two versions of opendir et al. are in -ldir and -lx on SCO Xenix. if test $ac_header_dirent = dirent.h; then { $as_echo "$as_me:${as_lineno-$LINENO}: checking for library containing opendir" >&5 $as_echo_n "checking for library containing opendir... " >&6; } if ${ac_cv_search_opendir+:} false; then : $as_echo_n "(cached) " >&6 else ac_func_search_save_LIBS=$LIBS cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ /* Override any GCC internal prototype to avoid an error. Use char because int might match the return type of a GCC builtin and then its argument prototype would still apply. */ #ifdef __cplusplus extern "C" #endif char opendir (); int main () { return opendir (); ; return 0; } _ACEOF for ac_lib in '' dir; do if test -z "$ac_lib"; then ac_res="none required" else ac_res=-l$ac_lib LIBS="-l$ac_lib $ac_func_search_save_LIBS" fi if ac_fn_c_try_link "$LINENO"; then : ac_cv_search_opendir=$ac_res fi rm -f core conftest.err conftest.$ac_objext \ conftest$ac_exeext if ${ac_cv_search_opendir+:} false; then : break fi done if ${ac_cv_search_opendir+:} false; then : else ac_cv_search_opendir=no fi rm conftest.$ac_ext LIBS=$ac_func_search_save_LIBS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_search_opendir" >&5 $as_echo "$ac_cv_search_opendir" >&6; } ac_res=$ac_cv_search_opendir if test "$ac_res" != no; then : test "$ac_res" = "none required" || LIBS="$ac_res $LIBS" fi else { $as_echo "$as_me:${as_lineno-$LINENO}: checking for library containing opendir" >&5 $as_echo_n "checking for library containing opendir... " >&6; } if ${ac_cv_search_opendir+:} false; then : $as_echo_n "(cached) " >&6 else ac_func_search_save_LIBS=$LIBS cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ /* Override any GCC internal prototype to avoid an error. Use char because int might match the return type of a GCC builtin and then its argument prototype would still apply. */ #ifdef __cplusplus extern "C" #endif char opendir (); int main () { return opendir (); ; return 0; } _ACEOF for ac_lib in '' x; do if test -z "$ac_lib"; then ac_res="none required" else ac_res=-l$ac_lib LIBS="-l$ac_lib $ac_func_search_save_LIBS" fi if ac_fn_c_try_link "$LINENO"; then : ac_cv_search_opendir=$ac_res fi rm -f core conftest.err conftest.$ac_objext \ conftest$ac_exeext if ${ac_cv_search_opendir+:} false; then : break fi done if ${ac_cv_search_opendir+:} false; then : else ac_cv_search_opendir=no fi rm conftest.$ac_ext LIBS=$ac_func_search_save_LIBS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_search_opendir" >&5 $as_echo "$ac_cv_search_opendir" >&6; } ac_res=$ac_cv_search_opendir if test "$ac_res" != no; then : test "$ac_res" = "none required" || LIBS="$ac_res $LIBS" fi fi for ac_header in stdlib.h do : ac_fn_c_check_header_mongrel "$LINENO" "stdlib.h" "ac_cv_header_stdlib_h" "$ac_includes_default" if test "x$ac_cv_header_stdlib_h" = xyes; then : cat >>confdefs.h <<_ACEOF #define HAVE_STDLIB_H 1 _ACEOF fi done for ac_func in getpassphrase do : ac_fn_c_check_func "$LINENO" "getpassphrase" "ac_cv_func_getpassphrase" if test "x$ac_cv_func_getpassphrase" = xyes; then : cat >>confdefs.h <<_ACEOF #define HAVE_GETPASSPHRASE 1 _ACEOF fi done save_LIBS="$LIBS" LIB_SOCKET="" ac_fn_c_check_func "$LINENO" "connect" "ac_cv_func_connect" if test "x$ac_cv_func_connect" = xyes; then : : else { $as_echo "$as_me:${as_lineno-$LINENO}: checking for gethostbyname in -lnsl" >&5 $as_echo_n "checking for gethostbyname in -lnsl... " >&6; } if ${ac_cv_lib_nsl_gethostbyname+:} false; then : $as_echo_n "(cached) " >&6 else ac_check_lib_save_LIBS=$LIBS LIBS="-lnsl $LIBS" cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ /* Override any GCC internal prototype to avoid an error. Use char because int might match the return type of a GCC builtin and then its argument prototype would still apply. */ #ifdef __cplusplus extern "C" #endif char gethostbyname (); int main () { return gethostbyname (); ; return 0; } _ACEOF if ac_fn_c_try_link "$LINENO"; then : ac_cv_lib_nsl_gethostbyname=yes else ac_cv_lib_nsl_gethostbyname=no fi rm -f core conftest.err conftest.$ac_objext \ conftest$ac_exeext conftest.$ac_ext LIBS=$ac_check_lib_save_LIBS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_nsl_gethostbyname" >&5 $as_echo "$ac_cv_lib_nsl_gethostbyname" >&6; } if test "x$ac_cv_lib_nsl_gethostbyname" = xyes; then : LIB_SOCKET="-lnsl $LIB_SOCKET" fi { $as_echo "$as_me:${as_lineno-$LINENO}: checking for connect in -lsocket" >&5 $as_echo_n "checking for connect in -lsocket... " >&6; } if ${ac_cv_lib_socket_connect+:} false; then : $as_echo_n "(cached) " >&6 else ac_check_lib_save_LIBS=$LIBS LIBS="-lsocket $LIBS" cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ /* Override any GCC internal prototype to avoid an error. Use char because int might match the return type of a GCC builtin and then its argument prototype would still apply. */ #ifdef __cplusplus extern "C" #endif char connect (); int main () { return connect (); ; return 0; } _ACEOF if ac_fn_c_try_link "$LINENO"; then : ac_cv_lib_socket_connect=yes else ac_cv_lib_socket_connect=no fi rm -f core conftest.err conftest.$ac_objext \ conftest$ac_exeext conftest.$ac_ext LIBS=$ac_check_lib_save_LIBS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_socket_connect" >&5 $as_echo "$ac_cv_lib_socket_connect" >&6; } if test "x$ac_cv_lib_socket_connect" = xyes; then : LIB_SOCKET="-lsocket $LIB_SOCKET" fi fi LIBS="$LIB_SOCKET $save_LIBS" ac_fn_c_check_func "$LINENO" "res_search" "ac_cv_func_res_search" if test "x$ac_cv_func_res_search" = xyes; then : : else LIBS="-lresolv $LIB_SOCKET $save_LIBS" cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ [ #include #include #include #ifdef HAVE_ARPA_NAMESER_COMPAT_H #include #endif #include ] int main () { [ const char host[12]="openafs.org"; u_char ans[1024]; res_search( host, C_IN, T_MX, (u_char *)&ans, sizeof(ans)); return 0; ] ; return 0; } _ACEOF if ac_fn_c_try_link "$LINENO"; then : LIB_SOCKET="-lresolv $LIB_SOCKET" fi rm -f core conftest.err conftest.$ac_objext \ conftest$ac_exeext conftest.$ac_ext fi LIBS="$LIB_SOCKET $save_LIBS" for ac_func in dn_expand dns_lookup do : as_ac_var=`$as_echo "ac_cv_func_$ac_func" | $as_tr_sh` ac_fn_c_check_func "$LINENO" "$ac_func" "$as_ac_var" if eval test \"x\$"$as_ac_var"\" = x"yes"; then : cat >>confdefs.h <<_ACEOF #define `$as_echo "HAVE_$ac_func" | $as_tr_cpp` 1 _ACEOF fi done LIBS="$save_LIBS" LIBS="$LIBS ${LIB_SOCKET}" cyrus_cv_getaddrinfo=yes ac_fn_c_check_func "$LINENO" "getaddrinfo" "ac_cv_func_getaddrinfo" if test "x$ac_cv_func_getaddrinfo" = xyes; then : ac_cv_lib_socket_getaddrinfo=no ac_cv_lib_inet6_getaddrinfo=no else { $as_echo "$as_me:${as_lineno-$LINENO}: checking for getaddrinfo in -lsocket" >&5 $as_echo_n "checking for getaddrinfo in -lsocket... " >&6; } if ${ac_cv_lib_socket_getaddrinfo+:} false; then : $as_echo_n "(cached) " >&6 else ac_check_lib_save_LIBS=$LIBS LIBS="-lsocket $LIBS" cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ /* Override any GCC internal prototype to avoid an error. Use char because int might match the return type of a GCC builtin and then its argument prototype would still apply. */ #ifdef __cplusplus extern "C" #endif char getaddrinfo (); int main () { return getaddrinfo (); ; return 0; } _ACEOF if ac_fn_c_try_link "$LINENO"; then : ac_cv_lib_socket_getaddrinfo=yes else ac_cv_lib_socket_getaddrinfo=no fi rm -f core conftest.err conftest.$ac_objext \ conftest$ac_exeext conftest.$ac_ext LIBS=$ac_check_lib_save_LIBS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_socket_getaddrinfo" >&5 $as_echo "$ac_cv_lib_socket_getaddrinfo" >&6; } if test "x$ac_cv_lib_socket_getaddrinfo" = xyes; then : LIBS="$LIBS -lsocket" ac_cv_lib_inet6_getaddrinfo=no else { $as_echo "$as_me:${as_lineno-$LINENO}: checking whether your system has IPv6 directory" >&5 $as_echo_n "checking whether your system has IPv6 directory... " >&6; } if ${ipv6_cv_dir+:} false; then : $as_echo_n "(cached) " >&6 else for ipv6_cv_dir in /usr/local/v6 /usr/inet6 no; do if test $ipv6_cv_dir = no -o -d $ipv6_cv_dir; then break fi done fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ipv6_cv_dir" >&5 $as_echo "$ipv6_cv_dir" >&6; } if test $ipv6_cv_dir = no; then ac_cv_lib_inet6_getaddrinfo=no else if test x$ipv6_libinet6 = x; then ipv6_libinet6=no SAVELDFLAGS="$LDFLAGS" LDFLAGS="$LDFLAGS -L$ipv6_cv_dir/lib" fi { $as_echo "$as_me:${as_lineno-$LINENO}: checking for getaddrinfo in -linet6" >&5 $as_echo_n "checking for getaddrinfo in -linet6... " >&6; } if ${ac_cv_lib_inet6_getaddrinfo+:} false; then : $as_echo_n "(cached) " >&6 else ac_check_lib_save_LIBS=$LIBS LIBS="-linet6 $LIBS" cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ /* Override any GCC internal prototype to avoid an error. Use char because int might match the return type of a GCC builtin and then its argument prototype would still apply. */ #ifdef __cplusplus extern "C" #endif char getaddrinfo (); int main () { return getaddrinfo (); ; return 0; } _ACEOF if ac_fn_c_try_link "$LINENO"; then : ac_cv_lib_inet6_getaddrinfo=yes else ac_cv_lib_inet6_getaddrinfo=no fi rm -f core conftest.err conftest.$ac_objext \ conftest$ac_exeext conftest.$ac_ext LIBS=$ac_check_lib_save_LIBS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_inet6_getaddrinfo" >&5 $as_echo "$ac_cv_lib_inet6_getaddrinfo" >&6; } if test "x$ac_cv_lib_inet6_getaddrinfo" = xyes; then : if test $ipv6_libinet6 = no; then ipv6_libinet6=yes LIBS="$LIBS -linet6" fi fi if test $ipv6_libinet6 = no; then LDFLAGS="$SAVELDFLAGS" fi fi fi fi ipv6_cv_getaddrinfo=no if test $ac_cv_func_getaddrinfo = yes -o $ac_cv_lib_socket_getaddrinfo = yes \ -o $ac_cv_lib_inet6_getaddrinfo = yes then ipv6_cv_getaddrinfo=yes fi if test $ipv6_cv_getaddrinfo = no; then if test getaddrinfo = getaddrinfo; then for ipv6_cv_pfx in o n; do cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ #include _ACEOF if (eval "$ac_cpp conftest.$ac_ext") 2>&5 | $EGREP "${ipv6_cv_pfx}getaddrinfo" >/dev/null 2>&1; then : as_ac_var=`$as_echo "ac_cv_func_${ipv6_cv_pfx}getaddrinfo" | $as_tr_sh` ac_fn_c_check_func "$LINENO" "${ipv6_cv_pfx}getaddrinfo" "$as_ac_var" if eval test \"x\$"$as_ac_var"\" = x"yes"; then : fi fi rm -f conftest* if eval test X\$ac_cv_func_${ipv6_cv_pfx}getaddrinfo = Xyes; then $as_echo "#define HAVE_GETADDRINFO /**/" >>confdefs.h ipv6_cv_getaddrinfo=yes break fi done fi fi if test $ipv6_cv_getaddrinfo = yes; then ac_fn_c_check_func "$LINENO" "gai_strerror" "ac_cv_func_gai_strerror" if test "x$ac_cv_func_gai_strerror" = xyes; then : ac_cv_lib_socket_gai_strerror=no ac_cv_lib_inet6_gai_strerror=no else { $as_echo "$as_me:${as_lineno-$LINENO}: checking for gai_strerror in -lsocket" >&5 $as_echo_n "checking for gai_strerror in -lsocket... " >&6; } if ${ac_cv_lib_socket_gai_strerror+:} false; then : $as_echo_n "(cached) " >&6 else ac_check_lib_save_LIBS=$LIBS LIBS="-lsocket $LIBS" cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ /* Override any GCC internal prototype to avoid an error. Use char because int might match the return type of a GCC builtin and then its argument prototype would still apply. */ #ifdef __cplusplus extern "C" #endif char gai_strerror (); int main () { return gai_strerror (); ; return 0; } _ACEOF if ac_fn_c_try_link "$LINENO"; then : ac_cv_lib_socket_gai_strerror=yes else ac_cv_lib_socket_gai_strerror=no fi rm -f core conftest.err conftest.$ac_objext \ conftest$ac_exeext conftest.$ac_ext LIBS=$ac_check_lib_save_LIBS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_socket_gai_strerror" >&5 $as_echo "$ac_cv_lib_socket_gai_strerror" >&6; } if test "x$ac_cv_lib_socket_gai_strerror" = xyes; then : LIBS="$LIBS -lsocket" ac_cv_lib_inet6_gai_strerror=no else { $as_echo "$as_me:${as_lineno-$LINENO}: checking whether your system has IPv6 directory" >&5 $as_echo_n "checking whether your system has IPv6 directory... " >&6; } if ${ipv6_cv_dir+:} false; then : $as_echo_n "(cached) " >&6 else for ipv6_cv_dir in /usr/local/v6 /usr/inet6 no; do if test $ipv6_cv_dir = no -o -d $ipv6_cv_dir; then break fi done fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ipv6_cv_dir" >&5 $as_echo "$ipv6_cv_dir" >&6; } if test $ipv6_cv_dir = no; then ac_cv_lib_inet6_gai_strerror=no else if test x$ipv6_libinet6 = x; then ipv6_libinet6=no SAVELDFLAGS="$LDFLAGS" LDFLAGS="$LDFLAGS -L$ipv6_cv_dir/lib" fi { $as_echo "$as_me:${as_lineno-$LINENO}: checking for gai_strerror in -linet6" >&5 $as_echo_n "checking for gai_strerror in -linet6... " >&6; } if ${ac_cv_lib_inet6_gai_strerror+:} false; then : $as_echo_n "(cached) " >&6 else ac_check_lib_save_LIBS=$LIBS LIBS="-linet6 $LIBS" cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ /* Override any GCC internal prototype to avoid an error. Use char because int might match the return type of a GCC builtin and then its argument prototype would still apply. */ #ifdef __cplusplus extern "C" #endif char gai_strerror (); int main () { return gai_strerror (); ; return 0; } _ACEOF if ac_fn_c_try_link "$LINENO"; then : ac_cv_lib_inet6_gai_strerror=yes else ac_cv_lib_inet6_gai_strerror=no fi rm -f core conftest.err conftest.$ac_objext \ conftest$ac_exeext conftest.$ac_ext LIBS=$ac_check_lib_save_LIBS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_inet6_gai_strerror" >&5 $as_echo "$ac_cv_lib_inet6_gai_strerror" >&6; } if test "x$ac_cv_lib_inet6_gai_strerror" = xyes; then : if test $ipv6_libinet6 = no; then ipv6_libinet6=yes LIBS="$LIBS -linet6" fi fi if test $ipv6_libinet6 = no; then LDFLAGS="$SAVELDFLAGS" fi fi fi fi ipv6_cv_gai_strerror=no if test $ac_cv_func_gai_strerror = yes -o $ac_cv_lib_socket_gai_strerror = yes \ -o $ac_cv_lib_inet6_gai_strerror = yes then ipv6_cv_gai_strerror=yes fi if test $ipv6_cv_gai_strerror = no; then if test gai_strerror = getaddrinfo; then for ipv6_cv_pfx in o n; do cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ #include _ACEOF if (eval "$ac_cpp conftest.$ac_ext") 2>&5 | $EGREP "${ipv6_cv_pfx}gai_strerror" >/dev/null 2>&1; then : as_ac_var=`$as_echo "ac_cv_func_${ipv6_cv_pfx}gai_strerror" | $as_tr_sh` ac_fn_c_check_func "$LINENO" "${ipv6_cv_pfx}gai_strerror" "$as_ac_var" if eval test \"x\$"$as_ac_var"\" = x"yes"; then : fi fi rm -f conftest* if eval test X\$ac_cv_func_${ipv6_cv_pfx}gai_strerror = Xyes; then $as_echo "#define HAVE_GETADDRINFO /**/" >>confdefs.h ipv6_cv_gai_strerror=yes break fi done fi fi if test $ipv6_cv_gai_strerror = yes; then $as_echo "#define HAVE_GETADDRINFO /**/" >>confdefs.h else cyrus_cv_getaddrinfo=no fi else cyrus_cv_getaddrinfo=no fi cyrus_cv_getnameinfo=yes ac_fn_c_check_func "$LINENO" "getnameinfo" "ac_cv_func_getnameinfo" if test "x$ac_cv_func_getnameinfo" = xyes; then : ac_cv_lib_socket_getnameinfo=no ac_cv_lib_inet6_getnameinfo=no else { $as_echo "$as_me:${as_lineno-$LINENO}: checking for getnameinfo in -lsocket" >&5 $as_echo_n "checking for getnameinfo in -lsocket... " >&6; } if ${ac_cv_lib_socket_getnameinfo+:} false; then : $as_echo_n "(cached) " >&6 else ac_check_lib_save_LIBS=$LIBS LIBS="-lsocket $LIBS" cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ /* Override any GCC internal prototype to avoid an error. Use char because int might match the return type of a GCC builtin and then its argument prototype would still apply. */ #ifdef __cplusplus extern "C" #endif char getnameinfo (); int main () { return getnameinfo (); ; return 0; } _ACEOF if ac_fn_c_try_link "$LINENO"; then : ac_cv_lib_socket_getnameinfo=yes else ac_cv_lib_socket_getnameinfo=no fi rm -f core conftest.err conftest.$ac_objext \ conftest$ac_exeext conftest.$ac_ext LIBS=$ac_check_lib_save_LIBS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_socket_getnameinfo" >&5 $as_echo "$ac_cv_lib_socket_getnameinfo" >&6; } if test "x$ac_cv_lib_socket_getnameinfo" = xyes; then : LIBS="$LIBS -lsocket" ac_cv_lib_inet6_getnameinfo=no else { $as_echo "$as_me:${as_lineno-$LINENO}: checking whether your system has IPv6 directory" >&5 $as_echo_n "checking whether your system has IPv6 directory... " >&6; } if ${ipv6_cv_dir+:} false; then : $as_echo_n "(cached) " >&6 else for ipv6_cv_dir in /usr/local/v6 /usr/inet6 no; do if test $ipv6_cv_dir = no -o -d $ipv6_cv_dir; then break fi done fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ipv6_cv_dir" >&5 $as_echo "$ipv6_cv_dir" >&6; } if test $ipv6_cv_dir = no; then ac_cv_lib_inet6_getnameinfo=no else if test x$ipv6_libinet6 = x; then ipv6_libinet6=no SAVELDFLAGS="$LDFLAGS" LDFLAGS="$LDFLAGS -L$ipv6_cv_dir/lib" fi { $as_echo "$as_me:${as_lineno-$LINENO}: checking for getnameinfo in -linet6" >&5 $as_echo_n "checking for getnameinfo in -linet6... " >&6; } if ${ac_cv_lib_inet6_getnameinfo+:} false; then : $as_echo_n "(cached) " >&6 else ac_check_lib_save_LIBS=$LIBS LIBS="-linet6 $LIBS" cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ /* Override any GCC internal prototype to avoid an error. Use char because int might match the return type of a GCC builtin and then its argument prototype would still apply. */ #ifdef __cplusplus extern "C" #endif char getnameinfo (); int main () { return getnameinfo (); ; return 0; } _ACEOF if ac_fn_c_try_link "$LINENO"; then : ac_cv_lib_inet6_getnameinfo=yes else ac_cv_lib_inet6_getnameinfo=no fi rm -f core conftest.err conftest.$ac_objext \ conftest$ac_exeext conftest.$ac_ext LIBS=$ac_check_lib_save_LIBS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_inet6_getnameinfo" >&5 $as_echo "$ac_cv_lib_inet6_getnameinfo" >&6; } if test "x$ac_cv_lib_inet6_getnameinfo" = xyes; then : if test $ipv6_libinet6 = no; then ipv6_libinet6=yes LIBS="$LIBS -linet6" fi fi if test $ipv6_libinet6 = no; then LDFLAGS="$SAVELDFLAGS" fi fi fi fi ipv6_cv_getnameinfo=no if test $ac_cv_func_getnameinfo = yes -o $ac_cv_lib_socket_getnameinfo = yes \ -o $ac_cv_lib_inet6_getnameinfo = yes then ipv6_cv_getnameinfo=yes fi if test $ipv6_cv_getnameinfo = no; then if test getnameinfo = getaddrinfo; then for ipv6_cv_pfx in o n; do cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ #include _ACEOF if (eval "$ac_cpp conftest.$ac_ext") 2>&5 | $EGREP "${ipv6_cv_pfx}getnameinfo" >/dev/null 2>&1; then : as_ac_var=`$as_echo "ac_cv_func_${ipv6_cv_pfx}getnameinfo" | $as_tr_sh` ac_fn_c_check_func "$LINENO" "${ipv6_cv_pfx}getnameinfo" "$as_ac_var" if eval test \"x\$"$as_ac_var"\" = x"yes"; then : fi fi rm -f conftest* if eval test X\$ac_cv_func_${ipv6_cv_pfx}getnameinfo = Xyes; then $as_echo "#define HAVE_GETADDRINFO /**/" >>confdefs.h ipv6_cv_getnameinfo=yes break fi done fi fi if test $ipv6_cv_getnameinfo = yes; then $as_echo "#define HAVE_GETNAMEINFO /**/" >>confdefs.h else cyrus_cv_getnameinfo=no fi if test $cyrus_cv_getaddrinfo = no; then IPV6_noGETADDRINFO_TRUE= IPV6_noGETADDRINFO_FALSE='#' else IPV6_noGETADDRINFO_TRUE='#' IPV6_noGETADDRINFO_FALSE= fi if test $cyrus_cv_getnameinfo = no; then IPV6_noGETNAMEINFO_TRUE= IPV6_noGETNAMEINFO_FALSE='#' else IPV6_noGETNAMEINFO_TRUE='#' IPV6_noGETNAMEINFO_FALSE= fi { $as_echo "$as_me:${as_lineno-$LINENO}: checking whether you have ss_family in struct sockaddr_storage" >&5 $as_echo_n "checking whether you have ss_family in struct sockaddr_storage... " >&6; } if ${ipv6_cv_ss_family+:} false; then : $as_echo_n "(cached) " >&6 else cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ #include #include int main () { struct sockaddr_storage ss; int i = ss.ss_family; ; return 0; } _ACEOF if ac_fn_c_try_compile "$LINENO"; then : ipv6_cv_ss_family=yes else ipv6_cv_ss_family=no fi rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext fi if test $ipv6_cv_ss_family = yes; then $as_echo "#define HAVE_SS_FAMILY /**/" >>confdefs.h else : fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ipv6_cv_ss_family" >&5 $as_echo "$ipv6_cv_ss_family" >&6; } { $as_echo "$as_me:${as_lineno-$LINENO}: checking whether you have sa_len in struct sockaddr" >&5 $as_echo_n "checking whether you have sa_len in struct sockaddr... " >&6; } if ${ipv6_cv_sa_len+:} false; then : $as_echo_n "(cached) " >&6 else cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ #include #include int main () { struct sockaddr sa; int i = sa.sa_len; ; return 0; } _ACEOF if ac_fn_c_try_compile "$LINENO"; then : ipv6_cv_sa_len=yes else ipv6_cv_sa_len=no fi rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext fi if test $ipv6_cv_sa_len = yes; then $as_echo "#define HAVE_SOCKADDR_SA_LEN /**/" >>confdefs.h else : fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ipv6_cv_sa_len" >&5 $as_echo "$ipv6_cv_sa_len" >&6; } for ac_header in sys/time.h do : ac_fn_c_check_header_mongrel "$LINENO" "sys/time.h" "ac_cv_header_sys_time_h" "$ac_includes_default" if test "x$ac_cv_header_sys_time_h" = xyes; then : cat >>confdefs.h <<_ACEOF #define HAVE_SYS_TIME_H 1 _ACEOF fi done { $as_echo "$as_me:${as_lineno-$LINENO}: checking whether time.h and sys/time.h may both be included" >&5 $as_echo_n "checking whether time.h and sys/time.h may both be included... " >&6; } if ${ac_cv_header_time+:} false; then : $as_echo_n "(cached) " >&6 else cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ #include #include #include int main () { if ((struct tm *) 0) return 0; ; return 0; } _ACEOF if ac_fn_c_try_compile "$LINENO"; then : ac_cv_header_time=yes else ac_cv_header_time=no fi rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_header_time" >&5 $as_echo "$ac_cv_header_time" >&6; } if test $ac_cv_header_time = yes; then $as_echo "#define TIME_WITH_SYS_TIME 1" >>confdefs.h fi { $as_echo "$as_me:${as_lineno-$LINENO}: checking whether struct tm is in sys/time.h or time.h" >&5 $as_echo_n "checking whether struct tm is in sys/time.h or time.h... " >&6; } if ${ac_cv_struct_tm+:} false; then : $as_echo_n "(cached) " >&6 else cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ #include #include int main () { struct tm tm; int *p = &tm.tm_sec; return !p; ; return 0; } _ACEOF if ac_fn_c_try_compile "$LINENO"; then : ac_cv_struct_tm=time.h else ac_cv_struct_tm=sys/time.h fi rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_struct_tm" >&5 $as_echo "$ac_cv_struct_tm" >&6; } if test $ac_cv_struct_tm = sys/time.h; then $as_echo "#define TM_IN_SYS_TIME 1" >>confdefs.h fi ac_fn_c_check_member "$LINENO" "struct tm" "tm_zone" "ac_cv_member_struct_tm_tm_zone" "#include #include <$ac_cv_struct_tm> " if test "x$ac_cv_member_struct_tm_tm_zone" = xyes; then : cat >>confdefs.h <<_ACEOF #define HAVE_STRUCT_TM_TM_ZONE 1 _ACEOF fi if test "$ac_cv_member_struct_tm_tm_zone" = yes; then $as_echo "#define HAVE_TM_ZONE 1" >>confdefs.h else ac_fn_c_check_decl "$LINENO" "tzname" "ac_cv_have_decl_tzname" "#include " if test "x$ac_cv_have_decl_tzname" = xyes; then : ac_have_decl=1 else ac_have_decl=0 fi cat >>confdefs.h <<_ACEOF #define HAVE_DECL_TZNAME $ac_have_decl _ACEOF { $as_echo "$as_me:${as_lineno-$LINENO}: checking for tzname" >&5 $as_echo_n "checking for tzname... " >&6; } if ${ac_cv_var_tzname+:} false; then : $as_echo_n "(cached) " >&6 else cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ #include #if !HAVE_DECL_TZNAME extern char *tzname[]; #endif int main () { return tzname[0][0]; ; return 0; } _ACEOF if ac_fn_c_try_link "$LINENO"; then : ac_cv_var_tzname=yes else ac_cv_var_tzname=no fi rm -f core conftest.err conftest.$ac_objext \ conftest$ac_exeext conftest.$ac_ext fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_var_tzname" >&5 $as_echo "$ac_cv_var_tzname" >&6; } if test $ac_cv_var_tzname = yes; then $as_echo "#define HAVE_TZNAME 1" >>confdefs.h fi fi for ac_func in timegm do : ac_fn_c_check_func "$LINENO" "timegm" "ac_cv_func_timegm" if test "x$ac_cv_func_timegm" = xyes; then : cat >>confdefs.h <<_ACEOF #define HAVE_TIMEGM 1 _ACEOF fi done for ac_func in vprintf do : ac_fn_c_check_func "$LINENO" "vprintf" "ac_cv_func_vprintf" if test "x$ac_cv_func_vprintf" = xyes; then : cat >>confdefs.h <<_ACEOF #define HAVE_VPRINTF 1 _ACEOF ac_fn_c_check_func "$LINENO" "_doprnt" "ac_cv_func__doprnt" if test "x$ac_cv_func__doprnt" = xyes; then : $as_echo "#define HAVE_DOPRNT 1" >>confdefs.h fi fi done # Check whether --with-bdb was given. if test "${with_bdb+set}" = set; then : withval=$with_bdb; with_bdb=$withval else with_bdb="yes" fi # Check whether --with-dbdir was given. if test "${with_dbdir+set}" = set; then : withval=$with_dbdir; with_bdb=$withval fi case "$with_bdb" in no) use_berkeley="no" ;; yes) use_berkeley="yes" with_bdb_lib=none with_bdb_inc=none ;; *) use_berkeley="yes" with_bdb_lib="$with_bdb/lib" with_bdb_inc="$with_bdb/include" ;; esac if test "$use_berkeley" != "no"; then # Check whether --with-bdb-libdir was given. if test "${with_bdb_libdir+set}" = set; then : withval=$with_bdb_libdir; with_bdb_lib=$withval else test "${with_bdb_lib+set}" = set || with_bdb_lib=none fi # Check whether --with-bdb-incdir was given. if test "${with_bdb_incdir+set}" = set; then : withval=$with_bdb_incdir; with_bdb_inc=$withval else test "${with_bdb_inc+set}" = set || with_bdb_inc=none fi cmu_save_CPPFLAGS=$CPPFLAGS if test -d $with_bdb_inc; then CPPFLAGS="$CPPFLAGS -I$with_bdb_inc" BDB_INCADD="-I$with_bdb_inc" else BDB_INCADD="" fi ac_fn_c_check_header_mongrel "$LINENO" "db.h" "ac_cv_header_db_h" "$ac_includes_default" if test "x$ac_cv_header_db_h" = xyes; then : BDB_SAVE_LDFLAGS=$LDFLAGS if test -d $with_bdb_lib; then # this is CMU ADD LIBPATH TO if test "$andrew_cv_runpath_switch" = "none" ; then LDFLAGS="-L$with_bdb_lib ${LDFLAGS}" else LDFLAGS="-L$with_bdb_lib ${LDFLAGS} $andrew_cv_runpath_switch$with_bdb_lib" fi # this is CMU ADD LIBPATH TO if test "$andrew_cv_runpath_switch" = "none" ; then BDB_LIBADD="-L$with_bdb_lib ${BDB_LIBADD}" else BDB_LIBADD="-L$with_bdb_lib ${BDB_LIBADD} $andrew_cv_runpath_switch$with_bdb_lib" fi else BDB_LIBADD="" fi saved_LIBS=$LIBS for dbname in ${with_bdb} \ db-5.3 db5.3 db53 \ db-5.2 db5.2 db52 \ db-5.1 db5.2 db51 \ db-5.0 db5.2 db50 db-5 db5 \ db-4.8 db4.8 db48 \ db-4.7 db4.7 db47 \ db-4.6 db4.6 db46 \ db-4.5 db4.5 db45 \ db-4.4 db4.4 db44 \ db-4.3 db4.3 db43 \ db-4.2 db4.2 db42 \ db-4.1 db4.1 db41 \ db-4.0 db4.0 db40 db-4 db4 \ db-3.3 db3.3 db33 \ db-3.2 db3.2 db32 \ db-3.1 db3.1 db31 \ db-3.0 db3.0 db30 db-3 db3 \ db do LIBS="$saved_LIBS -l$dbname" cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ #include #include int main () { db_create(NULL, NULL, 0); ; return 0; } _ACEOF if ac_fn_c_try_link "$LINENO"; then : BDB_LIBADD="$BDB_LIBADD -l$dbname"; dblib="berkeley"; dbname=db else dblib="no" fi rm -f core conftest.err conftest.$ac_objext \ conftest$ac_exeext conftest.$ac_ext if test "$dblib" = "berkeley"; then break; fi done if test "$dblib" = "no"; then LIBS="$saved_LIBS -ldb" cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ #include #include int main () { db_create(NULL, NULL, 0); ; return 0; } _ACEOF if ac_fn_c_try_link "$LINENO"; then : BDB_LIBADD="$BDB_LIBADD -ldb"; dblib="berkeley"; dbname=db else dblib="no" fi rm -f core conftest.err conftest.$ac_objext \ conftest$ac_exeext conftest.$ac_ext fi LIBS=$saved_LIBS LDFLAGS=$BDB_SAVE_LDFLAGS else dblib="no" fi CPPFLAGS=$cmu_save_CPPFLAGS if test "$dblib" = "no"; then as_fn_error $? "Berkeley DB 3.x or later was not found. You may need to supply the --with-bdb-libdir or --with-bdb-incdir configure options." "$LINENO" 5 fi if test "$with_bdb_lib" != "none"; then # this is CMU ADD LIBPATH if test "$andrew_cv_runpath_switch" = "none" ; then LDFLAGS="-L$with_bdb_lib ${LDFLAGS}" else LDFLAGS="-L$with_bdb_lib $andrew_cv_runpath_switch$with_bdb_lib ${LDFLAGS}" fi fi BDB_INC=${BDB_INCADD} BDB_LIB=${BDB_LIBADD} LIBS="${LIBS} ${BDB_LIBADD}" CPPFLAGS="${BDB_INCADD} ${CPPFLAGS}" $as_echo "#define HAVE_BDB /**/" >>confdefs.h fi if test "$use_berkeley" != "no"; then USE_BERKELEY_TRUE= USE_BERKELEY_FALSE='#' else USE_BERKELEY_TRUE='#' USE_BERKELEY_FALSE= fi HAVE_SQL=0 # Check whether --with-mysql-libdir was given. if test "${with_mysql_libdir+set}" = set; then : withval=$with_mysql_libdir; with_mysql_lib=$withval else test "${with_mysql_lib+set}" = set || with_mysql_lib=none fi # Check whether --with-mysql-incdir was given. if test "${with_mysql_incdir+set}" = set; then : withval=$with_mysql_incdir; with_mysql_inc=$withval else test "${with_mysql_inc+set}" = set || with_mysql_inc=none fi if test "$with_mysql_lib" != none ; then { $as_echo "$as_me:${as_lineno-$LINENO}: Legacy option --with-mysql-libdir=DIR detected. You may wish to change to --with-mysql which works now." >&5 $as_echo "$as_me: Legacy option --with-mysql-libdir=DIR detected. You may wish to change to --with-mysql which works now." >&6;} withval="$with_mysql_lib/.." else withval="no" fi { $as_echo "$as_me:${as_lineno-$LINENO}: checking whether to use MySQL" >&5 $as_echo_n "checking whether to use MySQL... " >&6; } # Check whether --with-mysql was given. if test "${with_mysql+set}" = set; then : withval=$with_mysql; fi with_mysql=$withval case "$with_mysql" in no) # Explicitly disable MySQL ;; yes) # Find mysql_config in $PATH mysql_config=mysql_config ;; *) # Find mysql_config in the specified directory mysql_config="$with_mysql/bin/mysql_config" if test ! -x "$mysql_config" ; then as_fn_error $? "The mysql_config program was not found in $with_mysql/bin, disabling MySQL support" "$LINENO" 5 with_mysql="no" fi ;; esac if test "$with_mysql" != "no"; then MYSQL_LIBADD=`$mysql_config --libs` MYSQL_INCADD=`$mysql_config --cflags` HAVE_SQL=1 LIBS="${LIBS} ${MYSQL_LIBADD}" CPPFLAGS="${MYSQL_INCADD} ${CPPFLAGS}" $as_echo "#define HAVE_MYSQL /**/" >>confdefs.h fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $with_mysql" >&5 $as_echo "$with_mysql" >&6; } # Check whether --with-pgsql was given. if test "${with_pgsql+set}" = set; then : withval=$with_pgsql; with_pgsql=$withval else with_pgsql="no" fi case "$with_pgsql" in no) use_pgsql="no" ;; yes) use_pgsql="yes" with_pgsql_lib=none with_pgsql_inc=none ;; *) use_pgsql="yes" with_pgsql_lib="$with_pgsql/lib" with_pgsql_inc="$with_pgsql/include" ;; esac if test "$use_pgsql" != "no"; then # Check whether --with-pgsql-libdir was given. if test "${with_pgsql_libdir+set}" = set; then : withval=$with_pgsql_libdir; with_pgsql_lib=$withval else test "${with_pgsql_lib+set}" = set || with_pgsql_lib=none fi # Check whether --with-pgsql-incdir was given. if test "${with_pgsql_incdir+set}" = set; then : withval=$with_pgsql_incdir; with_pgsql_inc=$withval else test "${with_pgsql_inc+set}" = set || with_pgsql_inc=none fi cmu_save_CPPFLAGS=$CPPFLAGS if test -d $with_pgsql_inc; then CPPFLAGS="$CPPFLAGS -I$with_pgsql_inc" PGSQL_INCADD="-I$with_pgsql_inc" else PGSQL_INCADD="" fi ac_fn_c_check_header_mongrel "$LINENO" "libpq-fe.h" "ac_cv_header_libpq_fe_h" "$ac_includes_default" if test "x$ac_cv_header_libpq_fe_h" = xyes; then : PGSQL_SAVE_LDFLAGS=$LDFLAGS if test -d $with_pgsql_lib; then # this is CMU ADD LIBPATH TO if test "$andrew_cv_runpath_switch" = "none" ; then LDFLAGS="-L$with_pgsql_lib ${LDFLAGS}" else LDFLAGS="-L$with_pgsql_lib ${LDFLAGS} $andrew_cv_runpath_switch$with_pgsql_lib" fi # this is CMU ADD LIBPATH TO if test "$andrew_cv_runpath_switch" = "none" ; then PGSQL_LIBADD="-L$with_pgsql_lib ${PGSQL_LIBADD}" else PGSQL_LIBADD="-L$with_pgsql_lib ${PGSQL_LIBADD} $andrew_cv_runpath_switch$with_pgsql_lib" fi else PGSQL_LIBADD="" fi saved_LIBS=$LIBS for libname in ${with_pgsql} pq do LIBS="$saved_LIBS -l$libname" cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ #include #include int main () { PQconnectdb(NULL); ; return 0; } _ACEOF if ac_fn_c_try_link "$LINENO"; then : PGSQL_LIBADD="$PGSQL_LIBADD -l$libname"; pgsqllib="yes" else pgsqllib="no" fi rm -f core conftest.err conftest.$ac_objext \ conftest$ac_exeext conftest.$ac_ext if test "$pgsqllib" = "yes"; then break; fi done LIBS=$saved_LIBS LDFLAGS=$PGSQL_SAVE_LDFLAGS else pgsqllib="no" fi CPPFLAGS=$cmu_save_CPPFLAGS if test "$pgsqllib" = "no"; then as_fn_error $? "PgSQL was not found. You may need to supply the --with-pgsql-libdir or --with-pgsql-incdir configure options." "$LINENO" 5 else HAVE_SQL=1 fi if test "$with_pgsql_lib" != "none"; then # this is CMU ADD LIBPATH if test "$andrew_cv_runpath_switch" = "none" ; then LDFLAGS="-L$with_pgsql_lib ${LDFLAGS}" else LDFLAGS="-L$with_pgsql_lib $andrew_cv_runpath_switch$with_pgsql_lib ${LDFLAGS}" fi fi LIBS="${LIBS} ${PGSQL_LIBADD}" CPPFLAGS="${PGSQL_INCADD} ${CPPFLAGS}" $as_echo "#define HAVE_PGSQL /**/" >>confdefs.h fi # Check whether --with-sqlite was given. if test "${with_sqlite+set}" = set; then : withval=$with_sqlite; with_sqlite=$withval else with_sqlite=no fi case "$with_sqlite" in no) use_sqlite="no" ;; yes) use_sqlite="yes" with_sqlite_lib=none with_sqlite_inc=none ;; *) use_sqlite="yes" with_sqlite_lib="$with_sqlite/lib" with_sqlite_inc="$with_sqlite/include" ;; esac if test "$use_sqlite" != "no"; then # Check whether --with-sqlite-libdir was given. if test "${with_sqlite_libdir+set}" = set; then : withval=$with_sqlite_libdir; with_sqlite_lib=$withval else test "${with_sqlite_lib+set}" = set || with_sqlite_lib=none fi # Check whether --with-sqlite-incdir was given. if test "${with_sqlite_incdir+set}" = set; then : withval=$with_sqlite_incdir; with_sqlite_inc=$withval else test "${with_sqlite_inc+set}" = set || with_sqlite_inc=none fi cmu_save_CPPFLAGS=$CPPFLAGS if test -d $with_sqlite_inc; then CPPFLAGS="$CPPFLAGS -I$with_sqlite_inc" SQLITE_INCADD="-I$with_sqlite_inc" else SQLITE_INCADD="" fi ac_fn_c_check_header_mongrel "$LINENO" "sqlite3.h" "ac_cv_header_sqlite3_h" "$ac_includes_default" if test "x$ac_cv_header_sqlite3_h" = xyes; then : SQLITE_SAVE_LDFLAGS=$LDFLAGS if test -d $with_sqlite_lib; then # this is CMU ADD LIBPATH TO if test "$andrew_cv_runpath_switch" = "none" ; then LDFLAGS="-L$with_sqlite_lib ${LDFLAGS}" else LDFLAGS="-L$with_sqlite_lib ${LDFLAGS} $andrew_cv_runpath_switch$with_sqlite_lib" fi # this is CMU ADD LIBPATH TO if test "$andrew_cv_runpath_switch" = "none" ; then SQLITE_LIBADD="-L$with_sqlite_lib ${SQLITE_LIBADD}" else SQLITE_LIBADD="-L$with_sqlite_lib ${SQLITE_LIBADD} $andrew_cv_runpath_switch$with_sqlite_lib" fi else SQLITE_LIBADD="" fi saved_LIBS=$LIBS for libname in ${with_sqlite} sqlite3 do LIBS="$saved_LIBS -l$libname" cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ #include #include int main () { sqlite3_open(NULL, NULL); ; return 0; } _ACEOF if ac_fn_c_try_link "$LINENO"; then : SQLITE_LIBADD="$SQLITE_LIBADD -l$libname"; sqlitelib="yes" else sqlitelib="no" fi rm -f core conftest.err conftest.$ac_objext \ conftest$ac_exeext conftest.$ac_ext if test "$sqlitelib" = "yes"; then break; fi done LIBS=$saved_LIBS LDFLAGS=$SQLITE_SAVE_LDFLAGS else sqlitelib="no" fi CPPFLAGS=$cmu_save_CPPFLAGS if test "$sqlitelib" = "no"; then as_fn_error $? "Sqlite was not found. You may need to supply the --with-sqlite-libdir or --with-sqlite-incdir configure options." "$LINENO" 5 else HAVE_SQL=1 fi if test "$with_sqlite_lib" != "none"; then # this is CMU ADD LIBPATH if test "$andrew_cv_runpath_switch" = "none" ; then LDFLAGS="-L$with_sqlite_lib ${LDFLAGS}" else LDFLAGS="-L$with_sqlite_lib $andrew_cv_runpath_switch$with_sqlite_lib ${LDFLAGS}" fi fi LIBS="${LIBS} ${SQLITE_LIBADD}" CPPFLAGS="${SQLITE_INCADD} ${CPPFLAGS}" $as_echo "#define HAVE_SQLITE /**/" >>confdefs.h fi if test $HAVE_SQL = 1; then USE_SQL_TRUE= USE_SQL_FALSE='#' else USE_SQL_TRUE='#' USE_SQL_FALSE= fi # Check whether --enable-sieve was given. if test "${enable_sieve+set}" = set; then : enableval=$enable_sieve; else enable_sieve="yes"; fi # Check whether --enable-pcre was given. if test "${enable_pcre+set}" = set; then : enableval=$enable_pcre; fi if test "$enable_sieve" != "no"; then $as_echo "#define USE_SIEVE /**/" >>confdefs.h for ac_prog in 'bison -y' byacc do # Extract the first word of "$ac_prog", so it can be a program name with args. set dummy $ac_prog; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } if ${ac_cv_prog_YACC+:} false; then : $as_echo_n "(cached) " >&6 else if test -n "$YACC"; then ac_cv_prog_YACC="$YACC" # Let the user override the test. else as_save_IFS=$IFS; IFS=$PATH_SEPARATOR for as_dir in $PATH do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_prog_YACC="$ac_prog" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 fi done done IFS=$as_save_IFS fi fi YACC=$ac_cv_prog_YACC if test -n "$YACC"; then { $as_echo "$as_me:${as_lineno-$LINENO}: result: $YACC" >&5 $as_echo "$YACC" >&6; } else { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 $as_echo "no" >&6; } fi test -n "$YACC" && break done test -n "$YACC" || YACC="yacc" for ac_prog in flex lex do # Extract the first word of "$ac_prog", so it can be a program name with args. set dummy $ac_prog; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } if ${ac_cv_prog_LEX+:} false; then : $as_echo_n "(cached) " >&6 else if test -n "$LEX"; then ac_cv_prog_LEX="$LEX" # Let the user override the test. else as_save_IFS=$IFS; IFS=$PATH_SEPARATOR for as_dir in $PATH do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_prog_LEX="$ac_prog" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 fi done done IFS=$as_save_IFS fi fi LEX=$ac_cv_prog_LEX if test -n "$LEX"; then { $as_echo "$as_me:${as_lineno-$LINENO}: result: $LEX" >&5 $as_echo "$LEX" >&6; } else { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 $as_echo "no" >&6; } fi test -n "$LEX" && break done test -n "$LEX" || LEX=":" if test "x$LEX" != "x:"; then cat >conftest.l <<_ACEOF %% a { ECHO; } b { REJECT; } c { yymore (); } d { yyless (1); } e { /* IRIX 6.5 flex 2.5.4 underquotes its yyless argument. */ yyless ((input () != 0)); } f { unput (yytext[0]); } . { BEGIN INITIAL; } %% #ifdef YYTEXT_POINTER extern char *yytext; #endif int main (void) { return ! yylex () + ! yywrap (); } _ACEOF { { ac_try="$LEX conftest.l" case "(($ac_try" in *\"* | *\`* | *\\*) ac_try_echo=\$ac_try;; *) ac_try_echo=$ac_try;; esac eval ac_try_echo="\"\$as_me:${as_lineno-$LINENO}: $ac_try_echo\"" $as_echo "$ac_try_echo"; } >&5 (eval "$LEX conftest.l") 2>&5 ac_status=$? $as_echo "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 test $ac_status = 0; } { $as_echo "$as_me:${as_lineno-$LINENO}: checking lex output file root" >&5 $as_echo_n "checking lex output file root... " >&6; } if ${ac_cv_prog_lex_root+:} false; then : $as_echo_n "(cached) " >&6 else if test -f lex.yy.c; then ac_cv_prog_lex_root=lex.yy elif test -f lexyy.c; then ac_cv_prog_lex_root=lexyy else as_fn_error $? "cannot find output from $LEX; giving up" "$LINENO" 5 fi fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_prog_lex_root" >&5 $as_echo "$ac_cv_prog_lex_root" >&6; } LEX_OUTPUT_ROOT=$ac_cv_prog_lex_root if test -z "${LEXLIB+set}"; then { $as_echo "$as_me:${as_lineno-$LINENO}: checking lex library" >&5 $as_echo_n "checking lex library... " >&6; } if ${ac_cv_lib_lex+:} false; then : $as_echo_n "(cached) " >&6 else ac_save_LIBS=$LIBS ac_cv_lib_lex='none needed' for ac_lib in '' -lfl -ll; do LIBS="$ac_lib $ac_save_LIBS" cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ `cat $LEX_OUTPUT_ROOT.c` _ACEOF if ac_fn_c_try_link "$LINENO"; then : ac_cv_lib_lex=$ac_lib fi rm -f core conftest.err conftest.$ac_objext \ conftest$ac_exeext conftest.$ac_ext test "$ac_cv_lib_lex" != 'none needed' && break done LIBS=$ac_save_LIBS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_lex" >&5 $as_echo "$ac_cv_lib_lex" >&6; } test "$ac_cv_lib_lex" != 'none needed' && LEXLIB=$ac_cv_lib_lex fi { $as_echo "$as_me:${as_lineno-$LINENO}: checking whether yytext is a pointer" >&5 $as_echo_n "checking whether yytext is a pointer... " >&6; } if ${ac_cv_prog_lex_yytext_pointer+:} false; then : $as_echo_n "(cached) " >&6 else # POSIX says lex can declare yytext either as a pointer or an array; the # default is implementation-dependent. Figure out which it is, since # not all implementations provide the %pointer and %array declarations. ac_cv_prog_lex_yytext_pointer=no ac_save_LIBS=$LIBS LIBS="$LEXLIB $ac_save_LIBS" cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ #define YYTEXT_POINTER 1 `cat $LEX_OUTPUT_ROOT.c` _ACEOF if ac_fn_c_try_link "$LINENO"; then : ac_cv_prog_lex_yytext_pointer=yes fi rm -f core conftest.err conftest.$ac_objext \ conftest$ac_exeext conftest.$ac_ext LIBS=$ac_save_LIBS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_prog_lex_yytext_pointer" >&5 $as_echo "$ac_cv_prog_lex_yytext_pointer" >&6; } if test $ac_cv_prog_lex_yytext_pointer = yes; then $as_echo "#define YYTEXT_POINTER 1" >>confdefs.h fi rm -f conftest.l $LEX_OUTPUT_ROOT.c fi if test "$LEX" = :; then LEX=${am_missing_run}flex fi if test "$enable_pcre" != "no"; then ac_fn_c_check_header_mongrel "$LINENO" "pcreposix.h" "ac_cv_header_pcreposix_h" "$ac_includes_default" if test "x$ac_cv_header_pcreposix_h" = xyes; then : fi if test "$ac_cv_header_pcreposix_h" = "yes"; then { $as_echo "$as_me:${as_lineno-$LINENO}: checking for utf8 enabled pcre" >&5 $as_echo_n "checking for utf8 enabled pcre... " >&6; } if ${cyrus_cv_pcre_utf8+:} false; then : $as_echo_n "(cached) " >&6 else cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ #include #ifndef REG_UTF8 #include #endif _ACEOF if ac_fn_c_try_cpp "$LINENO"; then : cyrus_cv_pcre_utf8=yes else cyrus_cv_pcre_utf8=no fi rm -f conftest.err conftest.i conftest.$ac_ext fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $cyrus_cv_pcre_utf8" >&5 $as_echo "$cyrus_cv_pcre_utf8" >&6; } else cyrus_cv_pcre_utf8="no" fi fi if test "$cyrus_cv_pcre_utf8" = "yes"; then LIBS="$LIBS -lpcre -lpcreposix"; $as_echo "#define ENABLE_REGEX /**/" >>confdefs.h $as_echo "#define HAVE_PCREPOSIX_H /**/" >>confdefs.h else for ac_header in rxposix.h do : ac_fn_c_check_header_mongrel "$LINENO" "rxposix.h" "ac_cv_header_rxposix_h" "$ac_includes_default" if test "x$ac_cv_header_rxposix_h" = xyes; then : cat >>confdefs.h <<_ACEOF #define HAVE_RXPOSIX_H 1 _ACEOF fi done if test "$ac_cv_header_rxposix_h" = "yes"; then LIBS="$LIBS -lrx" $as_echo "#define ENABLE_REGEX /**/" >>confdefs.h else { $as_echo "$as_me:${as_lineno-$LINENO}: checking for library containing regcomp" >&5 $as_echo_n "checking for library containing regcomp... " >&6; } if ${ac_cv_search_regcomp+:} false; then : $as_echo_n "(cached) " >&6 else ac_func_search_save_LIBS=$LIBS cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ /* Override any GCC internal prototype to avoid an error. Use char because int might match the return type of a GCC builtin and then its argument prototype would still apply. */ #ifdef __cplusplus extern "C" #endif char regcomp (); int main () { return regcomp (); ; return 0; } _ACEOF for ac_lib in '' regex; do if test -z "$ac_lib"; then ac_res="none required" else ac_res=-l$ac_lib LIBS="-l$ac_lib $ac_func_search_save_LIBS" fi if ac_fn_c_try_link "$LINENO"; then : ac_cv_search_regcomp=$ac_res fi rm -f core conftest.err conftest.$ac_objext \ conftest$ac_exeext if ${ac_cv_search_regcomp+:} false; then : break fi done if ${ac_cv_search_regcomp+:} false; then : else ac_cv_search_regcomp=no fi rm conftest.$ac_ext LIBS=$ac_func_search_save_LIBS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_search_regcomp" >&5 $as_echo "$ac_cv_search_regcomp" >&6; } ac_res=$ac_cv_search_regcomp if test "$ac_res" != no; then : test "$ac_res" = "none required" || LIBS="$ac_res $LIBS" $as_echo "#define ENABLE_REGEX /**/" >>confdefs.h fi fi fi fi if test "${enable_sieve}" != "no"; then SIEVE_TRUE= SIEVE_FALSE='#' else SIEVE_TRUE='#' SIEVE_FALSE= fi ac_fn_c_check_func "$LINENO" "strerror" "ac_cv_func_strerror" if test "x$ac_cv_func_strerror" = xyes; then : $as_echo "#define HAS_STRERROR /**/" >>confdefs.h else $as_echo "#define NEED_SYS_ERRLIST /**/" >>confdefs.h fi for ac_header in sys/resource.h do : ac_fn_c_check_header_mongrel "$LINENO" "sys/resource.h" "ac_cv_header_sys_resource_h" "$ac_includes_default" if test "x$ac_cv_header_sys_resource_h" = xyes; then : cat >>confdefs.h <<_ACEOF #define HAVE_SYS_RESOURCE_H 1 _ACEOF fi done for ac_func in setrlimit do : ac_fn_c_check_func "$LINENO" "setrlimit" "ac_cv_func_setrlimit" if test "x$ac_cv_func_setrlimit" = xyes; then : cat >>confdefs.h <<_ACEOF #define HAVE_SETRLIMIT 1 _ACEOF fi done for ac_func in getrlimit do : ac_fn_c_check_func "$LINENO" "getrlimit" "ac_cv_func_getrlimit" if test "x$ac_cv_func_getrlimit" = xyes; then : cat >>confdefs.h <<_ACEOF #define HAVE_GETRLIMIT 1 _ACEOF fi done for ac_func in daemon setsid do : as_ac_var=`$as_echo "ac_cv_func_$ac_func" | $as_tr_sh` ac_fn_c_check_func "$LINENO" "$ac_func" "$as_ac_var" if eval test \"x\$"$as_ac_var"\" = x"yes"; then : cat >>confdefs.h <<_ACEOF #define `$as_echo "HAVE_$ac_func" | $as_tr_cpp` 1 _ACEOF fi done for ac_func in shutdown do : ac_fn_c_check_func "$LINENO" "shutdown" "ac_cv_func_shutdown" if test "x$ac_cv_func_shutdown" = xyes; then : cat >>confdefs.h <<_ACEOF #define HAVE_SHUTDOWN 1 _ACEOF fi done cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ #include _ACEOF if (eval "$ac_cpp conftest.$ac_ext") 2>&5 | $EGREP "socklen_t" >/dev/null 2>&1; then : $as_echo "#define HAVE_SOCKLEN_T /**/" >>confdefs.h fi rm -f conftest* cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ #include _ACEOF if (eval "$ac_cpp conftest.$ac_ext") 2>&5 | $EGREP "sockaddr_storage" >/dev/null 2>&1; then : $as_echo "#define HAVE_STRUCT_SOCKADDR_STORAGE /**/" >>confdefs.h fi rm -f conftest* cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ #include _ACEOF if (eval "$ac_cpp conftest.$ac_ext") 2>&5 | $EGREP "rlim_t" >/dev/null 2>&1; then : $as_echo "#define HAVE_RLIM_T /**/" >>confdefs.h fi rm -f conftest* spt_type="" ac_fn_c_check_func "$LINENO" "setproctitle" "ac_cv_func_setproctitle" if test "x$ac_cv_func_setproctitle" = xyes; then : spt_type=SPT_BUILTIN fi if test "$spt_type" = ""; then { $as_echo "$as_me:${as_lineno-$LINENO}: checking for setproctitle in -lutil" >&5 $as_echo_n "checking for setproctitle in -lutil... " >&6; } if ${ac_cv_lib_util_setproctitle+:} false; then : $as_echo_n "(cached) " >&6 else ac_check_lib_save_LIBS=$LIBS LIBS="-lutil $LIBS" cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ /* Override any GCC internal prototype to avoid an error. Use char because int might match the return type of a GCC builtin and then its argument prototype would still apply. */ #ifdef __cplusplus extern "C" #endif char setproctitle (); int main () { return setproctitle (); ; return 0; } _ACEOF if ac_fn_c_try_link "$LINENO"; then : ac_cv_lib_util_setproctitle=yes else ac_cv_lib_util_setproctitle=no fi rm -f core conftest.err conftest.$ac_objext \ conftest$ac_exeext conftest.$ac_ext LIBS=$ac_check_lib_save_LIBS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_util_setproctitle" >&5 $as_echo "$ac_cv_lib_util_setproctitle" >&6; } if test "x$ac_cv_lib_util_setproctitle" = xyes; then : spt_type=SPT_BUILTIN LIBS="${LIBS} -lutil" fi fi if test "$spt_type" = ""; then ac_fn_c_check_header_mongrel "$LINENO" "sys/pstat.h" "ac_cv_header_sys_pstat_h" "$ac_includes_default" if test "x$ac_cv_header_sys_pstat_h" = xyes; then : spt_type=SPT_PSTAT fi fi if test "$spt_type" = ""; then ac_fn_c_check_header_mongrel "$LINENO" "sys/sysnews.h" "ac_cv_header_sys_sysnews_h" "$ac_includes_default" if test "x$ac_cv_header_sys_sysnews_h" = xyes; then : spt_type=SPT_SYSMIPS fi fi if test "$spt_type" = ""; then { $as_echo "$as_me:${as_lineno-$LINENO}: checking for PS_STRINGS" >&5 $as_echo_n "checking for PS_STRINGS... " >&6; } if ${cyrus_cv_sys_psstrings+:} false; then : $as_echo_n "(cached) " >&6 else cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ #include #include void *p = PS_STRINGS; _ACEOF if ac_fn_c_try_compile "$LINENO"; then : cyrus_cv_sys_psstrings=yes else cyrus_cv_sys_psstrings=no fi rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext fi if test $cyrus_cv_sys_psstrings = yes; then spt_type=SPT_PSSTRINGS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $cyrus_cv_sys_psstrings" >&5 $as_echo "$cyrus_cv_sys_psstrings" >&6; } fi if test "$spt_type" = ""; then { $as_echo "$as_me:${as_lineno-$LINENO}: checking for SCO" >&5 $as_echo_n "checking for SCO... " >&6; } if ${cyrus_cv_sys_sco+:} false; then : $as_echo_n "(cached) " >&6 else cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ #ifndef _SCO_unix_ #include #endif _ACEOF if ac_fn_c_try_cpp "$LINENO"; then : cyrus_cv_sys_sco=yes else cyrus_cv_sys_sco=no fi rm -f conftest.err conftest.i conftest.$ac_ext fi if test $cyrus_cv_sys_sco = yes; then spt_type=SPT_SCO fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $cyrus_cv_sys_sco" >&5 $as_echo "$cyrus_cv_sys_sco" >&6; } fi if test "$spt_type" = ""; then { $as_echo "$as_me:${as_lineno-$LINENO}: checking for setproctitle usability" >&5 $as_echo_n "checking for setproctitle usability... " >&6; } if ${cyrus_cv_sys_setproctitle+:} false; then : $as_echo_n "(cached) " >&6 else cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ #if defined(DGUX) || defined(_SEQUENT_) || defined(apollo) #include #endif _ACEOF if ac_fn_c_try_cpp "$LINENO"; then : cyrus_cv_sys_setproctitle=yes else cyrus_cv_sys_setproctitle=no fi rm -f conftest.err conftest.i conftest.$ac_ext fi if test $cyrus_cv_sys_setproctitle = no; then spt_type=SPT_NONE fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $cyrus_cv_sys_setproctitle" >&5 $as_echo "$cyrus_cv_sys_setproctitle" >&6; } fi if test "$spt_type" != ""; then cat >>confdefs.h <<_ACEOF #define SPT_TYPE $spt_type _ACEOF fi { $as_echo "$as_me:${as_lineno-$LINENO}: checking nonblocking method" >&5 $as_echo_n "checking nonblocking method... " >&6; } if ${cyrus_cv_sys_nonblock+:} false; then : $as_echo_n "(cached) " >&6 else cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ #include #include #include #ifndef FNDELAY #define FNDELAY O_NDELAY #endif int main () { fcntl(0, F_GETFL, 0)&FNDELAY ; return 0; } _ACEOF if ac_fn_c_try_link "$LINENO"; then : cyrus_cv_sys_nonblock=fcntl else cyrus_cv_sys_nonblock=ioctl fi rm -f core conftest.err conftest.$ac_objext \ conftest$ac_exeext conftest.$ac_ext fi if test "$cyrus_cv_sys_nonblock" = "fcntl"; then NONBLOCK_FCNTL_TRUE= NONBLOCK_FCNTL_FALSE='#' else NONBLOCK_FCNTL_TRUE='#' NONBLOCK_FCNTL_FALSE= fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $cyrus_cv_sys_nonblock" >&5 $as_echo "$cyrus_cv_sys_nonblock" >&6; } { $as_echo "$as_me:${as_lineno-$LINENO}: checking timezone GMT offset method" >&5 $as_echo_n "checking timezone GMT offset method... " >&6; } if ${cyrus_cv_struct_sys_gmtoff+:} false; then : $as_echo_n "(cached) " >&6 else cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ #include int main () { struct tm tm; tm.tm_gmtoff = 0; ; return 0; } _ACEOF if ac_fn_c_try_compile "$LINENO"; then : cyrus_cv_struct_sys_gmtoff=tm else cyrus_cv_struct_sys_gmtoff=gmtime fi rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext fi if test "$cyrus_cv_struct_sys_gmtoff" = "tm"; then GMTOFF_TM_TRUE= GMTOFF_TM_FALSE='#' else GMTOFF_TM_TRUE='#' GMTOFF_TM_FALSE= fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $cyrus_cv_struct_sys_gmtoff" >&5 $as_echo "$cyrus_cv_struct_sys_gmtoff" >&6; } { $as_echo "$as_me:${as_lineno-$LINENO}: checking for shared mmap" >&5 $as_echo_n "checking for shared mmap... " >&6; } if ${cyrus_cv_func_mmap_shared+:} false; then : $as_echo_n "(cached) " >&6 else if test "$cross_compiling" = yes; then : cyrus_cv_func_mmap_shared=no else cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ #include #include #include #include #include int main() { char *base; int mmapflags = MAP_SHARED; int fd = open("conftestmmap", O_RDWR|O_CREAT|O_TRUNC, 0666); if (fd == -1) return 1; if (write(fd, "test", 4) != 4) return 1; fsync(fd); #ifdef MAP_FILE mmapflags |= MAP_FILE; #endif #ifdef MAP_VARIABLE mmapflags |= MAP_VARIABLE; #endif base = mmap((caddr_t)0, 100, PROT_READ, mmapflags, fd, 0L); if (base == (caddr_t)-1) return 1; if (memcmp(base, "test", 4) != 0) return 1; if (write(fd, "test", 4) != 4) return 1; fsync(fd); if (memcmp(base+4, "test", 4) != 0) return 1; return 0; } _ACEOF if ac_fn_c_try_run "$LINENO"; then : cyrus_cv_func_mmap_shared=yes else cyrus_cv_func_mmap_shared=no fi rm -f core *.core core.conftest.* gmon.out bb.out conftest$ac_exeext \ conftest.$ac_objext conftest.beam conftest.$ac_ext fi fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $cyrus_cv_func_mmap_shared" >&5 $as_echo "$cyrus_cv_func_mmap_shared" >&6; } if test $cyrus_cv_func_mmap_shared = yes; then found_map="shared" else { $as_echo "$as_me:${as_lineno-$LINENO}: checking for stupid shared mmap" >&5 $as_echo_n "checking for stupid shared mmap... " >&6; } if ${cyrus_cv_func_mmap_stupidshared+:} false; then : $as_echo_n "(cached) " >&6 else if test "$cross_compiling" = yes; then : cyrus_cv_func_mmap_stupidshared=no else cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ #include #include #include #include #include int main() { char *base; int fd = open("conftestmmap", O_RDWR|O_CREAT|O_TRUNC, 0666); int mmapflags = MAP_SHARED; if (fd == -1) return 1; if (write(fd, "test", 4) != 4) return 1; fsync(fd); #ifdef MAP_FILE mmapflags |= MAP_FILE; #endif #ifdef MAP_VARIABLE mmapflags |= MAP_VARIABLE; #endif base = mmap((caddr_t)0, 4, PROT_READ, mmapflags, fd, 0L); if (base == (caddr_t)-1) return 1; if (memcmp(base, "test", 4) != 0) return 1; lseek(fd, 0L, 0); if (write(fd, "xyzz", 4) != 4) return 1; fsync(fd); if (memcmp(base, "xyzz", 4) != 0) return 1; return 0; } _ACEOF if ac_fn_c_try_run "$LINENO"; then : cyrus_cv_func_mmap_stupidshared=yes else cyrus_cv_func_mmap_stupidshared=no fi rm -f core *.core core.conftest.* gmon.out bb.out conftest$ac_exeext \ conftest.$ac_objext conftest.beam conftest.$ac_ext fi fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $cyrus_cv_func_mmap_stupidshared" >&5 $as_echo "$cyrus_cv_func_mmap_stupidshared" >&6; } if test $cyrus_cv_func_mmap_stupidshared = yes; then found_map="stupidshared" else { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: *** This system does not have a working mmap()" >&5 $as_echo "$as_me: WARNING: *** This system does not have a working mmap()" >&2;} { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: *** Expect a considerable performance penalty" >&5 $as_echo "$as_me: WARNING: *** Expect a considerable performance penalty" >&2;} found_map=nommap fi fi # Check whether --with-mmap was given. if test "${with_mmap+set}" = set; then : withval=$with_mmap; WITH_MAP="$withval" else WITH_MAP="$found_map" fi if test "$WITH_MAP" = "shared"; then MAP_SHARED_TRUE= MAP_SHARED_FALSE='#' else MAP_SHARED_TRUE='#' MAP_SHARED_FALSE= fi if test "$WITH_MAP" = "stupidshared"; then MAP_STUPIDSHARED_TRUE= MAP_STUPIDSHARED_FALSE='#' else MAP_STUPIDSHARED_TRUE='#' MAP_STUPIDSHARED_FALSE= fi # Check whether --with-lock was given. if test "${with_lock+set}" = set; then : withval=$with_lock; WITH_LOCK="$withval" else ac_fn_c_check_func "$LINENO" "fcntl" "ac_cv_func_fcntl" if test "x$ac_cv_func_fcntl" = xyes; then : WITH_LOCK="fcntl" else ac_fn_c_check_func "$LINENO" "flock" "ac_cv_func_flock" if test "x$ac_cv_func_flock" = xyes; then : WITH_LOCK="flock" else as_fn_error $? "unable to detect locking method" "$LINENO" 5 fi fi fi if test $WITH_LOCK = "fcntl"; then LOCK_FCNTL_TRUE= LOCK_FCNTL_FALSE='#' else LOCK_FCNTL_TRUE='#' LOCK_FCNTL_FALSE= fi LIB_RT="" ac_fn_c_check_func "$LINENO" "fdatasync" "ac_cv_func_fdatasync" if test "x$ac_cv_func_fdatasync" = xyes; then : $as_echo "#define HAVE_FDATASYNC /**/" >>confdefs.h else { $as_echo "$as_me:${as_lineno-$LINENO}: checking for fdatasync in -lrt" >&5 $as_echo_n "checking for fdatasync in -lrt... " >&6; } if ${ac_cv_lib_rt_fdatasync+:} false; then : $as_echo_n "(cached) " >&6 else ac_check_lib_save_LIBS=$LIBS LIBS="-lrt $LIBS" cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ /* Override any GCC internal prototype to avoid an error. Use char because int might match the return type of a GCC builtin and then its argument prototype would still apply. */ #ifdef __cplusplus extern "C" #endif char fdatasync (); int main () { return fdatasync (); ; return 0; } _ACEOF if ac_fn_c_try_link "$LINENO"; then : ac_cv_lib_rt_fdatasync=yes else ac_cv_lib_rt_fdatasync=no fi rm -f core conftest.err conftest.$ac_objext \ conftest$ac_exeext conftest.$ac_ext LIBS=$ac_check_lib_save_LIBS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_rt_fdatasync" >&5 $as_echo "$ac_cv_lib_rt_fdatasync" >&6; } if test "x$ac_cv_lib_rt_fdatasync" = xyes; then : LIB_RT="-lrt" $as_echo "#define HAVE_FDATASYNC /**/" >>confdefs.h fi fi LIB_UUID= { $as_echo "$as_me:${as_lineno-$LINENO}: checking for uuid_generate in -luuid" >&5 $as_echo_n "checking for uuid_generate in -luuid... " >&6; } if ${ac_cv_lib_uuid_uuid_generate+:} false; then : $as_echo_n "(cached) " >&6 else ac_check_lib_save_LIBS=$LIBS LIBS="-luuid $LIBS" cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ /* Override any GCC internal prototype to avoid an error. Use char because int might match the return type of a GCC builtin and then its argument prototype would still apply. */ #ifdef __cplusplus extern "C" #endif char uuid_generate (); int main () { return uuid_generate (); ; return 0; } _ACEOF if ac_fn_c_try_link "$LINENO"; then : ac_cv_lib_uuid_uuid_generate=yes else ac_cv_lib_uuid_uuid_generate=no fi rm -f core conftest.err conftest.$ac_objext \ conftest$ac_exeext conftest.$ac_ext LIBS=$ac_check_lib_save_LIBS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_uuid_uuid_generate" >&5 $as_echo "$ac_cv_lib_uuid_uuid_generate" >&6; } if test "x$ac_cv_lib_uuid_uuid_generate" = xyes; then : LIB_UUID="-luuid" $as_echo "#define HAVE_LIBUUID /**/" >>confdefs.h fi cant_find_sigvec=no if ${cyrus_cv_sigveclib+:} false; then : $as_echo_n "(cached) " >&6 else ac_fn_c_check_func "$LINENO" "sigvec" "ac_cv_func_sigvec" if test "x$ac_cv_func_sigvec" = xyes; then : cyrus_cv_sigveclib="" else { $as_echo "$as_me:${as_lineno-$LINENO}: checking for sigvec in -lBSD" >&5 $as_echo_n "checking for sigvec in -lBSD... " >&6; } if ${ac_cv_lib_BSD_sigvec+:} false; then : $as_echo_n "(cached) " >&6 else ac_check_lib_save_LIBS=$LIBS LIBS="-lBSD $LIBS" cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ /* Override any GCC internal prototype to avoid an error. Use char because int might match the return type of a GCC builtin and then its argument prototype would still apply. */ #ifdef __cplusplus extern "C" #endif char sigvec (); int main () { return sigvec (); ; return 0; } _ACEOF if ac_fn_c_try_link "$LINENO"; then : ac_cv_lib_BSD_sigvec=yes else ac_cv_lib_BSD_sigvec=no fi rm -f core conftest.err conftest.$ac_objext \ conftest$ac_exeext conftest.$ac_ext LIBS=$ac_check_lib_save_LIBS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_BSD_sigvec" >&5 $as_echo "$ac_cv_lib_BSD_sigvec" >&6; } if test "x$ac_cv_lib_BSD_sigvec" = xyes; then : cyrus_cv_sigveclib="-lBSD" else SAVE_LDFLAGS="$LDFLAGS" LDFLAGS="-L/usr/ucblib -R/usr/ucblib $LDFLAGS" { $as_echo "$as_me:${as_lineno-$LINENO}: checking for sigvec in -lucb" >&5 $as_echo_n "checking for sigvec in -lucb... " >&6; } if ${ac_cv_lib_ucb_sigvec+:} false; then : $as_echo_n "(cached) " >&6 else ac_check_lib_save_LIBS=$LIBS LIBS="-lucb $LIBS" cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ /* Override any GCC internal prototype to avoid an error. Use char because int might match the return type of a GCC builtin and then its argument prototype would still apply. */ #ifdef __cplusplus extern "C" #endif char sigvec (); int main () { return sigvec (); ; return 0; } _ACEOF if ac_fn_c_try_link "$LINENO"; then : ac_cv_lib_ucb_sigvec=yes else ac_cv_lib_ucb_sigvec=no fi rm -f core conftest.err conftest.$ac_objext \ conftest$ac_exeext conftest.$ac_ext LIBS=$ac_check_lib_save_LIBS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_ucb_sigvec" >&5 $as_echo "$ac_cv_lib_ucb_sigvec" >&6; } if test "x$ac_cv_lib_ucb_sigvec" = xyes; then : cyrus_cv_sigveclib="-lc -L/usr/ucblib -R/usr/ucblib -lucb" else cant_find_sigvec=yes fi LDFLAGS="$SAVE_LDFLAGS" fi fi fi # ok, we still look for this stuff because of checking groups, but # all authentication goes through SASL # Check whether --enable-afs was given. if test "${enable_afs+set}" = set; then : enableval=$enable_afs; fi # Check whether --with-afs-libdir was given. if test "${with_afs_libdir+set}" = set; then : withval=$with_afs_libdir; afs_libdir="${withval}" else afs_libdir="/usr/lib" fi # Check whether --with-afs-incdir was given. if test "${with_afs_incdir+set}" = set; then : withval=$with_afs_incdir; afs_incdir="${withval}" else afs_incdir="/usr/include" fi # Check whether --with-ldap was given. if test "${with_ldap+set}" = set; then : withval=$with_ldap; with_ldap="${withval}" else with_ldap="no" fi # Check whether --enable-krb5afspts was given. if test "${enable_krb5afspts+set}" = set; then : enableval=$enable_krb5afspts; fi if test "x$enable_afs" = "xyes"; then # krb5afspts is only valid if AFS is enabled, so check inside here. if test "x$enable_krb5afspts" = "xyes"; then : SASL_GSSAPI_LIBS_SET="yes" $as_echo "#define AFSPTS_USE_KRB5 /**/" >>confdefs.h fi CFLAGS="${CFLAGS} -I${with_afs_incdir}" AFS_LIBS="${with_afs_libdir}/afs/libkauth.a ${with_afs_libdir}/afs/libprot.a ${with_afs_libdir}/afs/libauth.a ${with_afs_libdir}/afs/libsys.a ${with_afs_libdir}/librxkad.a ${with_afs_libdir}/librx.a ${with_afs_libdir}/afs/libsys.a ${with_afs_libdir}/libubik.a ${with_afs_libdir}/afs/liblwp.a ${with_afs_libdir}/afs/util.a ${with_afs_libdir}/afs/libafscom_err.a -lresolv" if test -f ${with_afs_libdir}/afs/libaudit.a; then AFS_LIBS="$AFS_LIBS ${with_afs_libdir}/afs/libaudit.a" fi if test -f /usr/ucblib/libucb.a; then # this is CMU ADD LIBPATH TO if test "$andrew_cv_runpath_switch" = "none" ; then AFS_LDFLAGS="-L/usr/ucblib ${AFS_LDFLAGS}" else AFS_LDFLAGS="-L/usr/ucblib ${AFS_LDFLAGS} $andrew_cv_runpath_switch/usr/ucblib" fi AFS_LIBS="$AFS_LIBS -lc -lucb" fi if test -f ${with_afs_libdir}/afs/libdes.a; then AFS_LIBS="$AFS_LIBS ${with_afs_libdir}/afs/libdes.a" else AFS_LIBS="$AFS_LIBS -ldes" fi if ${cyrus_cv_afs_sigvec+:} false; then : $as_echo_n "(cached) " >&6 else SAVE_LIBS="$LIBS" LIBS="${with_afs_libdir}/liblwp.a" { $as_echo "$as_me:${as_lineno-$LINENO}: checking if AFS libraries need sigvec" >&5 $as_echo_n "checking if AFS libraries need sigvec... " >&6; } cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ IOMGR_Initialize(); int main () { IOMGR_Initialize() ; return 0; } _ACEOF if ac_fn_c_try_link "$LINENO"; then : { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 $as_echo "no" >&6; } cyrus_cv_afs_sigvec="no" else { $as_echo "$as_me:${as_lineno-$LINENO}: result: yes" >&5 $as_echo "yes" >&6; } cyrus_cv_afs_sigvec="yes" fi rm -f core conftest.err conftest.$ac_objext \ conftest$ac_exeext conftest.$ac_ext fi if test "$cyrus_cv_afs_sigvec" = yes; then if test "$cant_find_sigvec" = yes; then { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: Can not find a sigvec for AFS libraries which seem to need one." >&5 $as_echo "$as_me: WARNING: Can not find a sigvec for AFS libraries which seem to need one." >&2;} else AFS_LIBS="${AFS_LIBS} $cyrus_cv_sigveclib" $as_echo "#define HAVE_AFSKRB /**/" >>confdefs.h fi else AFS_LIBS="${AFS_LIBS}" $as_echo "#define HAVE_AFSKRB /**/" >>confdefs.h fi LIBS="$SAVE_LIBS" fi if grep HAVE_AFSKRB confdefs.h >/dev/null; then USE_AFSKRB_TRUE= USE_AFSKRB_FALSE='#' else USE_AFSKRB_TRUE='#' USE_AFSKRB_FALSE= fi have_ldap=no LDAP_CPPFLAGS= LDAP_LDFLAGS= LDAP_LIBS= case "x$with_ldap" in xno) # default args or --without-ldap # do not try to enable ;; xyes) # --with-ldap # try to enable, search in default system directories ldap_cppflags= ldap_ldflags= ;; *) # --with-ldap=DIR # try to enable, search in given install directory if test "x$with_ldap" != "x" -a -d "$with_ldap"; then ldap_cppflags="-I${with_ldap}/include" ldap_ldflags="-L${with_ldap}/lib" with_ldap=yes else { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: Disabling LDAP - no include files found" >&5 $as_echo "$as_me: WARNING: Disabling LDAP - no include files found" >&2;} with_ldap=no fi esac if test $with_ldap = yes; then save_CPPFLAGS="$CPPFLAGS" save_LDFLAGS="$LDFLAGS" CPPFLAGS="$CPPFLAGS $ldap_cppflags" LDFLAGS="$LDFLAGS $ldap_ldflags" { $as_echo "$as_me:${as_lineno-$LINENO}: checking for ldap_initialize in -lldap" >&5 $as_echo_n "checking for ldap_initialize in -lldap... " >&6; } if ${ac_cv_lib_ldap_ldap_initialize+:} false; then : $as_echo_n "(cached) " >&6 else ac_check_lib_save_LIBS=$LIBS LIBS="-lldap -llber $LIBS" cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ /* Override any GCC internal prototype to avoid an error. Use char because int might match the return type of a GCC builtin and then its argument prototype would still apply. */ #ifdef __cplusplus extern "C" #endif char ldap_initialize (); int main () { return ldap_initialize (); ; return 0; } _ACEOF if ac_fn_c_try_link "$LINENO"; then : ac_cv_lib_ldap_ldap_initialize=yes else ac_cv_lib_ldap_ldap_initialize=no fi rm -f core conftest.err conftest.$ac_objext \ conftest$ac_exeext conftest.$ac_ext LIBS=$ac_check_lib_save_LIBS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_ldap_ldap_initialize" >&5 $as_echo "$ac_cv_lib_ldap_ldap_initialize" >&6; } if test "x$ac_cv_lib_ldap_ldap_initialize" = xyes; then : $as_echo "#define HAVE_LDAP /**/" >>confdefs.h LDAP_CPPFLAGS="$ldap_cppflags" LDAP_LDFLAGS="$ldap_ldflags" LDAP_LIBS="-lldap -llber" have_ldap=yes fi CPPFLAGS="$save_CPPFLAGS" LDFLAGS="$save_LDFLAGS" fi if test "$have_ldap" = "yes"; then HAVE_LDAP_TRUE= HAVE_LDAP_FALSE='#' else HAVE_LDAP_TRUE='#' HAVE_LDAP_FALSE= fi if test "x$enable_afs" = "xyes" -o "$have_ldap" = "yes"; then PTCLIENT_TRUE= PTCLIENT_FALSE='#' else PTCLIENT_TRUE='#' PTCLIENT_FALSE= fi # Check whether --with-clamav was given. if test "${with_clamav+set}" = set; then : withval=$with_clamav; with_clamav=$withval else with_clamav=yes fi if test "$with_clamav" != no; then if test -d $with_clamav; then save_CPPFLAGS="$CPPFLAGS" save_LDFLAGS="$LDFLAGS" save_LIBS="$LIBS" CPPFLAGS="${CPPFLAGS} -I${with_clamav}/include" LDFLAGS="$LDFLAGS -L${with_clamav}/$CMU_LIB_SUBDIR" { $as_echo "$as_me:${as_lineno-$LINENO}: checking for request_init in -lwrap" >&5 $as_echo_n "checking for request_init in -lwrap... " >&6; } if ${ac_cv_lib_wrap_request_init+:} false; then : $as_echo_n "(cached) " >&6 else ac_check_lib_save_LIBS=$LIBS LIBS="-lwrap $LIBS" cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ /* Override any GCC internal prototype to avoid an error. Use char because int might match the return type of a GCC builtin and then its argument prototype would still apply. */ #ifdef __cplusplus extern "C" #endif char request_init (); int main () { return request_init (); ; return 0; } _ACEOF if ac_fn_c_try_link "$LINENO"; then : ac_cv_lib_wrap_request_init=yes else ac_cv_lib_wrap_request_init=no fi rm -f core conftest.err conftest.$ac_objext \ conftest$ac_exeext conftest.$ac_ext LIBS=$ac_check_lib_save_LIBS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_wrap_request_init" >&5 $as_echo "$ac_cv_lib_wrap_request_init" >&6; } if test "x$ac_cv_lib_wrap_request_init" = xyes; then : ac_fn_c_check_header_mongrel "$LINENO" "clamav.h" "ac_cv_header_clamav_h" "$ac_includes_default" if test "x$ac_cv_header_clamav_h" = xyes; then : else with_clamav=no fi else with_clamav=no fi CPPFLAGS="$save_CPPFLAGS" LDFLAGS="$save_LDFLAGS" LIBS="$save_LIBS" fi fi { $as_echo "$as_me:${as_lineno-$LINENO}: checking ClamAV support" >&5 $as_echo_n "checking ClamAV support... " >&6; } { $as_echo "$as_me:${as_lineno-$LINENO}: result: $with_clamav" >&5 $as_echo "$with_clamav" >&6; } LIB_CLAMAV="" if test "$with_clamav" != "no"; then $as_echo "#define HAVE_CLAMAV /**/" >>confdefs.h if test -d "$with_clamav"; then CPPFLAGS="${CPPFLAGS} -I${with_clamav}/include" LIB_CLAMAV="-L${with_clamav}/$CMU_LIB_SUBDIR -lclamav" else LIB_CLAMAV="-lclamav" fi fi if test "$have_clamav" = "yes"; then HAVE_CLAMAV_TRUE= HAVE_CLAMAV_FALSE='#' else HAVE_CLAMAV_TRUE='#' HAVE_CLAMAV_FALSE= fi # Check whether --enable-server was given. if test "${enable_server+set}" = set; then : enableval=$enable_server; fi if test "$enable_server" != "no"; then SERVER_TRUE= SERVER_FALSE='#' else SERVER_TRUE='#' SERVER_FALSE= fi # We always output a server makefile (just because we can) # Check whether --with-krb was given. if test "${with_krb+set}" = set; then : withval=$with_krb; with_krb="$withval" else with_krb="no" fi # Check whether --with-krbimpl was given. if test "${with_krbimpl+set}" = set; then : withval=$with_krbimpl; with_krbimpl="$withval" else with_krbimpl="kth" fi # Check whether --enable-statickrb was given. if test "${enable_statickrb+set}" = set; then : enableval=$enable_statickrb; with_statickrb="yes" else with_statickrb="no" fi { $as_echo "$as_me:${as_lineno-$LINENO}: checking for res_search in -lresolv" >&5 $as_echo_n "checking for res_search in -lresolv... " >&6; } if ${ac_cv_lib_resolv_res_search+:} false; then : $as_echo_n "(cached) " >&6 else ac_check_lib_save_LIBS=$LIBS LIBS="-lresolv $LIBS" cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ /* Override any GCC internal prototype to avoid an error. Use char because int might match the return type of a GCC builtin and then its argument prototype would still apply. */ #ifdef __cplusplus extern "C" #endif char res_search (); int main () { return res_search (); ; return 0; } _ACEOF if ac_fn_c_try_link "$LINENO"; then : ac_cv_lib_resolv_res_search=yes else ac_cv_lib_resolv_res_search=no fi rm -f core conftest.err conftest.$ac_objext \ conftest$ac_exeext conftest.$ac_ext LIBS=$ac_check_lib_save_LIBS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_resolv_res_search" >&5 $as_echo "$ac_cv_lib_resolv_res_search" >&6; } if test "x$ac_cv_lib_resolv_res_search" = xyes; then : cat >>confdefs.h <<_ACEOF #define HAVE_LIBRESOLV 1 _ACEOF LIBS="-lresolv $LIBS" fi if test "$with_statickrb" = "yes" -a ! -d "$with_krb"; then as_fn_error $? "--enable-statickrb specified but --with-krb did not specify a valid directory" "$LINENO" 5 fi if test "$with_krb" != "no"; then # Check whether --with-krbdes was given. if test "${with_krbdes+set}" = set; then : withval=$with_krbdes; with_krbdes="$withval" else with_krbdes="yes" fi if test "$with_krbdes" = "yes"; then { $as_echo "$as_me:${as_lineno-$LINENO}: checking for des_ecb_encrypt in -ldes" >&5 $as_echo_n "checking for des_ecb_encrypt in -ldes... " >&6; } if ${ac_cv_lib_des_des_ecb_encrypt+:} false; then : $as_echo_n "(cached) " >&6 else ac_check_lib_save_LIBS=$LIBS LIBS="-ldes $LIBS" cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ /* Override any GCC internal prototype to avoid an error. Use char because int might match the return type of a GCC builtin and then its argument prototype would still apply. */ #ifdef __cplusplus extern "C" #endif char des_ecb_encrypt (); int main () { return des_ecb_encrypt (); ; return 0; } _ACEOF if ac_fn_c_try_link "$LINENO"; then : ac_cv_lib_des_des_ecb_encrypt=yes else ac_cv_lib_des_des_ecb_encrypt=no fi rm -f core conftest.err conftest.$ac_objext \ conftest$ac_exeext conftest.$ac_ext LIBS=$ac_check_lib_save_LIBS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_des_des_ecb_encrypt" >&5 $as_echo "$ac_cv_lib_des_des_ecb_encrypt" >&6; } if test "x$ac_cv_lib_des_des_ecb_encrypt" = xyes; then : if test "$with_statickrb" = "yes"; then KRB_LIBS="$with_krb/lib/libdes.a" else KRB_LIBS="-ldes" fi else as_fn_error $? "The Kerberos DES library is required for Kerberos support. You might want --with-auth=unix." "$LINENO" 5 fi fi fi if test -d ${with_krb}; then { $as_echo "$as_me:${as_lineno-$LINENO}: checking for Kerberos includes" >&5 $as_echo_n "checking for Kerberos includes... " >&6; } if ${cyrus_cv_krbinclude+:} false; then : $as_echo_n "(cached) " >&6 else for krbhloc in include/kerberosIV include do if test -f ${with_krb}/${krbhloc}/krb.h ; then cyrus_cv_krbinclude=${with_krb}/${krbhloc} break fi done fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $cyrus_cv_krbinclude" >&5 $as_echo "$cyrus_cv_krbinclude" >&6; } if test -n "${cyrus_cv_krbinclude}"; then CPPFLAGS="$CPPFLAGS -I${cyrus_cv_krbinclude}" fi # this is CMU ADD LIBPATH if test "$andrew_cv_runpath_switch" = "none" ; then LDFLAGS="-L${with_krb}/lib ${LDFLAGS}" else LDFLAGS="-L${with_krb}/lib $andrew_cv_runpath_switch${with_krb}/lib ${LDFLAGS}" fi fi if test "$with_krbimpl" != "kth"; then KRBLIB="krb4" else KRBLIB="krb" fi if test "$with_des" != no; then ac_fn_c_check_header_mongrel "$LINENO" "krb.h" "ac_cv_header_krb_h" "$ac_includes_default" if test "x$ac_cv_header_krb_h" = xyes; then : as_ac_Lib=`$as_echo "ac_cv_lib_${KRBLIB}''_krb_mk_priv" | $as_tr_sh` { $as_echo "$as_me:${as_lineno-$LINENO}: checking for krb_mk_priv in -l${KRBLIB}" >&5 $as_echo_n "checking for krb_mk_priv in -l${KRBLIB}... " >&6; } if eval \${$as_ac_Lib+:} false; then : $as_echo_n "(cached) " >&6 else ac_check_lib_save_LIBS=$LIBS LIBS="-l${KRBLIB} $KRB_LIBS $LIBS" cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ /* Override any GCC internal prototype to avoid an error. Use char because int might match the return type of a GCC builtin and then its argument prototype would still apply. */ #ifdef __cplusplus extern "C" #endif char krb_mk_priv (); int main () { return krb_mk_priv (); ; return 0; } _ACEOF if ac_fn_c_try_link "$LINENO"; then : eval "$as_ac_Lib=yes" else eval "$as_ac_Lib=no" fi rm -f core conftest.err conftest.$ac_objext \ conftest$ac_exeext conftest.$ac_ext LIBS=$ac_check_lib_save_LIBS fi eval ac_res=\$$as_ac_Lib { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_res" >&5 $as_echo "$ac_res" >&6; } if eval test \"x\$"$as_ac_Lib"\" = x"yes"; then : if test "$with_statickrb" = "yes"; then KRB_LIBS="$KRB_LIBS $with_krb/lib/lib${KRBLIB}.a" else KRB_LIBS="$KRB_LIBS -l${KRBLIB}" fi else { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: No Kerberos V4 found" >&5 $as_echo "$as_me: WARNING: No Kerberos V4 found" >&2;}; krb4=no fi else krb4=no fi else { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: No DES library found for Kerberos V4 support" >&5 $as_echo "$as_me: WARNING: No DES library found for Kerberos V4 support" >&2;} krb4=no fi if test "${krb4}" != no; then $as_echo "#define HAVE_KRB /**/" >>confdefs.h fi LIBS="$KRB_LIBS $LIBS" SASL_GSSAPI_LIBS_SET="yes" # Check whether --with-openssl was given. if test "${with_openssl+set}" = set; then : withval=$with_openssl; with_ssl="${withval}" fi SSL_CPPFLAGS= SSL_LIBS= case "x$with_ssl" in xno) # --without-openssl # do not try to enable ;; x|xyes) # default args or --with-openssl # # Try pkg-config - OpenSSL >= 0.9.6 has openssl.pc pkg_failed=no { $as_echo "$as_me:${as_lineno-$LINENO}: checking for OPENSSL" >&5 $as_echo_n "checking for OPENSSL... " >&6; } if test -n "$OPENSSL_CFLAGS"; then pkg_cv_OPENSSL_CFLAGS="$OPENSSL_CFLAGS" elif test -n "$PKG_CONFIG"; then if test -n "$PKG_CONFIG" && \ { { $as_echo "$as_me:${as_lineno-$LINENO}: \$PKG_CONFIG --exists --print-errors \"openssl\""; } >&5 ($PKG_CONFIG --exists --print-errors "openssl") 2>&5 ac_status=$? $as_echo "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 test $ac_status = 0; }; then pkg_cv_OPENSSL_CFLAGS=`$PKG_CONFIG --cflags "openssl" 2>/dev/null` test "x$?" != "x0" && pkg_failed=yes else pkg_failed=yes fi else pkg_failed=untried fi if test -n "$OPENSSL_LIBS"; then pkg_cv_OPENSSL_LIBS="$OPENSSL_LIBS" elif test -n "$PKG_CONFIG"; then if test -n "$PKG_CONFIG" && \ { { $as_echo "$as_me:${as_lineno-$LINENO}: \$PKG_CONFIG --exists --print-errors \"openssl\""; } >&5 ($PKG_CONFIG --exists --print-errors "openssl") 2>&5 ac_status=$? $as_echo "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 test $ac_status = 0; }; then pkg_cv_OPENSSL_LIBS=`$PKG_CONFIG --libs "openssl" 2>/dev/null` test "x$?" != "x0" && pkg_failed=yes else pkg_failed=yes fi else pkg_failed=untried fi if test $pkg_failed = yes; then { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 $as_echo "no" >&6; } if $PKG_CONFIG --atleast-pkgconfig-version 0.20; then _pkg_short_errors_supported=yes else _pkg_short_errors_supported=no fi if test $_pkg_short_errors_supported = yes; then OPENSSL_PKG_ERRORS=`$PKG_CONFIG --short-errors --print-errors --cflags --libs "openssl" 2>&1` else OPENSSL_PKG_ERRORS=`$PKG_CONFIG --print-errors --cflags --libs "openssl" 2>&1` fi # Put the nasty error message in config.log where it belongs echo "$OPENSSL_PKG_ERRORS" >&5 as_fn_error $? "Package requirements (openssl) were not met: $OPENSSL_PKG_ERRORS Consider adjusting the PKG_CONFIG_PATH environment variable if you installed software in a non-standard prefix. Alternatively, you may set the environment variables OPENSSL_CFLAGS and OPENSSL_LIBS to avoid the need to call pkg-config. See the pkg-config man page for more details." "$LINENO" 5 elif test $pkg_failed = untried; then { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 $as_echo "no" >&6; } { { $as_echo "$as_me:${as_lineno-$LINENO}: error: in \`$ac_pwd':" >&5 $as_echo "$as_me: error: in \`$ac_pwd':" >&2;} as_fn_error $? "The pkg-config script could not be found or is too old. Make sure it is in your PATH or set the PKG_CONFIG environment variable to the full path to pkg-config. Alternatively, you may set the environment variables OPENSSL_CFLAGS and OPENSSL_LIBS to avoid the need to call pkg-config. See the pkg-config man page for more details. To get pkg-config, see . See \`config.log' for more details" "$LINENO" 5; } else OPENSSL_CFLAGS=$pkg_cv_OPENSSL_CFLAGS OPENSSL_LIBS=$pkg_cv_OPENSSL_LIBS { $as_echo "$as_me:${as_lineno-$LINENO}: result: yes" >&5 $as_echo "yes" >&6; } with_ssl=yes fi ssl_cppflags="$OPENSSL_CFLAGS" ssl_ldflags="$OPENSSL_LIBS" # # If pkg-config doesn't work, search in default system directories ;; *) # --with-openssl=DIR # try to enable, search in given install directory if test -d "$with_ssl"; then ssl_cppflags="-I${with_ssl}/include" ssl_ldflags= if test -d "${with_ssl}/lib64"; then # this is CMU ADD LIBPATH TO if test "$andrew_cv_runpath_switch" = "none" ; then ssl_ldflags="-L${with_ssl}/lib64 ${ssl_ldflags}" else ssl_ldflags="-L${with_ssl}/lib64 ${ssl_ldflags} $andrew_cv_runpath_switch${with_ssl}/lib64" fi else # this is CMU ADD LIBPATH TO if test "$andrew_cv_runpath_switch" = "none" ; then ssl_ldflags="-L${with_ssl}/lib ${ssl_ldflags}" else ssl_ldflags="-L${with_ssl}/lib ${ssl_ldflags} $andrew_cv_runpath_switch${with_ssl}/lib" fi fi with_ssl=yes else { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: Disabling OpenSSL - no include files found" >&5 $as_echo "$as_me: WARNING: Disabling OpenSSL - no include files found" >&2;} with_ssl=no fi esac if test "$with_ssl" != "no"; then save_CPPFLAGS="$CPPFLAGS" save_LDFLAGS="$LDFLAGS" CPPFLAGS="$CPPFLAGS $ssl_cppflags" LDFLAGS="$LDFLAGS $ssl_ldflags" ac_fn_c_check_header_mongrel "$LINENO" "openssl/evp.h" "ac_cv_header_openssl_evp_h" "$ac_includes_default" if test "x$ac_cv_header_openssl_evp_h" = xyes; then : with_ssl=yes else with_ssl=no fi ssl_libs= { $as_echo "$as_me:${as_lineno-$LINENO}: checking for RSAPublicEncrypt in -lrsaref" >&5 $as_echo_n "checking for RSAPublicEncrypt in -lrsaref... " >&6; } if ${ac_cv_lib_rsaref_RSAPublicEncrypt+:} false; then : $as_echo_n "(cached) " >&6 else ac_check_lib_save_LIBS=$LIBS LIBS="-lrsaref $LIBS" cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ /* Override any GCC internal prototype to avoid an error. Use char because int might match the return type of a GCC builtin and then its argument prototype would still apply. */ #ifdef __cplusplus extern "C" #endif char RSAPublicEncrypt (); int main () { return RSAPublicEncrypt (); ; return 0; } _ACEOF if ac_fn_c_try_link "$LINENO"; then : ac_cv_lib_rsaref_RSAPublicEncrypt=yes else ac_cv_lib_rsaref_RSAPublicEncrypt=no fi rm -f core conftest.err conftest.$ac_objext \ conftest$ac_exeext conftest.$ac_ext LIBS=$ac_check_lib_save_LIBS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_rsaref_RSAPublicEncrypt" >&5 $as_echo "$ac_cv_lib_rsaref_RSAPublicEncrypt" >&6; } if test "x$ac_cv_lib_rsaref_RSAPublicEncrypt" = xyes; then : ssl_libs="-lRSAglue -lrsaref" else # whatever, we do not care : fi { $as_echo "$as_me:${as_lineno-$LINENO}: checking for BIO_accept in -lcrypto" >&5 $as_echo_n "checking for BIO_accept in -lcrypto... " >&6; } if ${ac_cv_lib_crypto_BIO_accept+:} false; then : $as_echo_n "(cached) " >&6 else ac_check_lib_save_LIBS=$LIBS LIBS="-lcrypto $ssl_libs $LIBS" cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ /* Override any GCC internal prototype to avoid an error. Use char because int might match the return type of a GCC builtin and then its argument prototype would still apply. */ #ifdef __cplusplus extern "C" #endif char BIO_accept (); int main () { return BIO_accept (); ; return 0; } _ACEOF if ac_fn_c_try_link "$LINENO"; then : ac_cv_lib_crypto_BIO_accept=yes else ac_cv_lib_crypto_BIO_accept=no fi rm -f core conftest.err conftest.$ac_objext \ conftest$ac_exeext conftest.$ac_ext LIBS=$ac_check_lib_save_LIBS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_crypto_BIO_accept" >&5 $as_echo "$ac_cv_lib_crypto_BIO_accept" >&6; } if test "x$ac_cv_lib_crypto_BIO_accept" = xyes; then : ssl_libs="-lcrypto $ssl_libs" else with_ssl=no fi { $as_echo "$as_me:${as_lineno-$LINENO}: checking for SSL_CTX_new in -lssl" >&5 $as_echo_n "checking for SSL_CTX_new in -lssl... " >&6; } if ${ac_cv_lib_ssl_SSL_CTX_new+:} false; then : $as_echo_n "(cached) " >&6 else ac_check_lib_save_LIBS=$LIBS LIBS="-lssl $ssl_libs $LIBS" cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ /* Override any GCC internal prototype to avoid an error. Use char because int might match the return type of a GCC builtin and then its argument prototype would still apply. */ #ifdef __cplusplus extern "C" #endif char SSL_CTX_new (); int main () { return SSL_CTX_new (); ; return 0; } _ACEOF if ac_fn_c_try_link "$LINENO"; then : ac_cv_lib_ssl_SSL_CTX_new=yes else ac_cv_lib_ssl_SSL_CTX_new=no fi rm -f core conftest.err conftest.$ac_objext \ conftest$ac_exeext conftest.$ac_ext LIBS=$ac_check_lib_save_LIBS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_ssl_SSL_CTX_new" >&5 $as_echo "$ac_cv_lib_ssl_SSL_CTX_new" >&6; } if test "x$ac_cv_lib_ssl_SSL_CTX_new" = xyes; then : ssl_libs="-lssl $ssl_libs" else with_ssl=no fi if test "$with_ssl" = "no"; then { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: Disabling SSL - no library files found" >&5 $as_echo "$as_me: WARNING: Disabling SSL - no library files found" >&2;} fi CPPFLAGS="$save_CPPFLAGS" LDFLAGS="$save_LDFLAGS" fi { $as_echo "$as_me:${as_lineno-$LINENO}: checking for ssl" >&5 $as_echo_n "checking for ssl... " >&6; } { $as_echo "$as_me:${as_lineno-$LINENO}: result: $with_ssl" >&5 $as_echo "$with_ssl" >&6; } if test "$with_ssl" != "no"; then SSL_CPPFLAGS="$ssl_cppflags" SSL_LIBS="$ssl_ldflags $ssl_libs" $as_echo "#define HAVE_SSL /**/" >>confdefs.h if test "${krb4}" != no; then $as_echo "#define OPENSSL_ENABLE_OLD_DES_SUPPORT /**/" >>confdefs.h $as_echo "#define OPENSSL_DES_LIBDES_COMPATIBILITY /**/" >>confdefs.h fi fi if test "$with_ssl" != "no"; then HAVE_SSL_TRUE= HAVE_SSL_FALSE='#' else HAVE_SSL_TRUE='#' HAVE_SSL_FALSE= fi # Check whether --with-egd-socket was given. if test "${with_egd_socket+set}" = set; then : withval=$with_egd_socket; EGD_SOCKET="$withval" fi if test -n "$EGD_SOCKET" ; then cat >>confdefs.h <<_ACEOF #define EGD_SOCKET "$EGD_SOCKET" _ACEOF fi # Check whether --with-lib-subdir was given. if test "${with_lib_subdir+set}" = set; then : withval=$with_lib_subdir; fi # The cast to long int works around a bug in the HP C Compiler # version HP92453-01 B.11.11.23709.GP, which incorrectly rejects # declarations like `int a3[[(sizeof (unsigned char)) >= 0]];'. # This bug is HP SR number 8606223364. { $as_echo "$as_me:${as_lineno-$LINENO}: checking size of long" >&5 $as_echo_n "checking size of long... " >&6; } if ${ac_cv_sizeof_long+:} false; then : $as_echo_n "(cached) " >&6 else if ac_fn_c_compute_int "$LINENO" "(long int) (sizeof (long))" "ac_cv_sizeof_long" "$ac_includes_default"; then : else if test "$ac_cv_type_long" = yes; then { { $as_echo "$as_me:${as_lineno-$LINENO}: error: in \`$ac_pwd':" >&5 $as_echo "$as_me: error: in \`$ac_pwd':" >&2;} as_fn_error 77 "cannot compute sizeof (long) See \`config.log' for more details" "$LINENO" 5; } else ac_cv_sizeof_long=0 fi fi fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_sizeof_long" >&5 $as_echo "$ac_cv_sizeof_long" >&6; } cat >>confdefs.h <<_ACEOF #define SIZEOF_LONG $ac_cv_sizeof_long _ACEOF { $as_echo "$as_me:${as_lineno-$LINENO}: checking what directory libraries are found in" >&5 $as_echo_n "checking what directory libraries are found in... " >&6; } if ${ac_cv_cmu_lib_subdir+:} false; then : $as_echo_n "(cached) " >&6 else test "X$with_lib_subdir" = "Xyes" && with_lib_subdir= test "X$with_lib_subdir" = "Xno" && with_lib_subdir= if test "X$with_lib_subdir" = "X" ; then ac_cv_cmu_lib_subdir=lib if test $ac_cv_sizeof_long -eq 4 ; then test -d /usr/lib32 && ac_cv_cmu_lib_subdir=lib32 fi if test $ac_cv_sizeof_long -eq 8 ; then test -d /usr/lib64 && ac_cv_cmu_lib_subdir=lib64 fi else ac_cv_cmu_lib_subdir=$with_lib_subdir fi fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_cmu_lib_subdir" >&5 $as_echo "$ac_cv_cmu_lib_subdir" >&6; } CMU_LIB_SUBDIR=$ac_cv_cmu_lib_subdir # Check whether --with-zlib was given. if test "${with_zlib+set}" = set; then : withval=$with_zlib; with_zlib=$withval else with_zlib="yes" fi save_CPPFLAGS=$CPPFLAGS save_LDFLAGS=$LDFLAGS if test -d $with_zlib; then CPPFLAGS="${CPPFLAGS} -I${with_lib}/include" # this is CMU ADD LIBPATH if test "$andrew_cv_runpath_switch" = "none" ; then LDFLAGS="-L${with_zlib}/$CMU_LIB_SUBDIR ${LDFLAGS}" else LDFLAGS="-L${with_zlib}/$CMU_LIB_SUBDIR $andrew_cv_runpath_switch${with_zlib}/$CMU_LIB_SUBDIR ${LDFLAGS}" fi fi ZLIB="" case "$with_zlib" in no) with_zlib="no";; *) ac_fn_c_check_header_mongrel "$LINENO" "zlib.h" "ac_cv_header_zlib_h" "$ac_includes_default" if test "x$ac_cv_header_zlib_h" = xyes; then : { $as_echo "$as_me:${as_lineno-$LINENO}: checking for deflate in -lz" >&5 $as_echo_n "checking for deflate in -lz... " >&6; } if ${ac_cv_lib_z_deflate+:} false; then : $as_echo_n "(cached) " >&6 else ac_check_lib_save_LIBS=$LIBS LIBS="-lz $LIBS" cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ /* Override any GCC internal prototype to avoid an error. Use char because int might match the return type of a GCC builtin and then its argument prototype would still apply. */ #ifdef __cplusplus extern "C" #endif char deflate (); int main () { return deflate (); ; return 0; } _ACEOF if ac_fn_c_try_link "$LINENO"; then : ac_cv_lib_z_deflate=yes else ac_cv_lib_z_deflate=no fi rm -f core conftest.err conftest.$ac_objext \ conftest$ac_exeext conftest.$ac_ext LIBS=$ac_check_lib_save_LIBS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_z_deflate" >&5 $as_echo "$ac_cv_lib_z_deflate" >&6; } if test "x$ac_cv_lib_z_deflate" = xyes; then : LIBS="${LIBS} -lz"; with_zlib="yes" else with_zlib="no" fi else with_zlib=no fi ;; esac if test "$with_zlib" != "no"; then $as_echo "#define HAVE_ZLIB /**/" >>confdefs.h ZLIB="-lz" else CPPFLAGS=$save_CPPFLAGS LDFLAGS=$save_LDFLAGS fi { $as_echo "$as_me:${as_lineno-$LINENO}: checking for zlib" >&5 $as_echo_n "checking for zlib... " >&6; } { $as_echo "$as_me:${as_lineno-$LINENO}: result: $with_zlib" >&5 $as_echo "$with_zlib" >&6; } # Check whether --with-zephyr was given. if test "${with_zephyr+set}" = set; then : withval=$with_zephyr; with_zephyr="${withval}" fi if test -z "$with_zephyr"; then if test -f /usr/local/lib/libzephyr.a; then with_zephyr="/usr/local" elif test -f /usr/lib/libzephyr.a; then with_zephyr="/usr" fi fi ZEPHYR_LIBS="" case "$with_zephyr" in no) true;; ""|yes) { $as_echo "$as_me:${as_lineno-$LINENO}: checking for ZInitialize in -lzephyr" >&5 $as_echo_n "checking for ZInitialize in -lzephyr... " >&6; } if ${ac_cv_lib_zephyr_ZInitialize+:} false; then : $as_echo_n "(cached) " >&6 else ac_check_lib_save_LIBS=$LIBS LIBS="-lzephyr $LIBS" cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ /* Override any GCC internal prototype to avoid an error. Use char because int might match the return type of a GCC builtin and then its argument prototype would still apply. */ #ifdef __cplusplus extern "C" #endif char ZInitialize (); int main () { return ZInitialize (); ; return 0; } _ACEOF if ac_fn_c_try_link "$LINENO"; then : ac_cv_lib_zephyr_ZInitialize=yes else ac_cv_lib_zephyr_ZInitialize=no fi rm -f core conftest.err conftest.$ac_objext \ conftest$ac_exeext conftest.$ac_ext LIBS=$ac_check_lib_save_LIBS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_zephyr_ZInitialize" >&5 $as_echo "$ac_cv_lib_zephyr_ZInitialize" >&6; } if test "x$ac_cv_lib_zephyr_ZInitialize" = xyes; then : ZEPHYR_LIBS="-lzephyr" else with_zephyr="no" fi ;; *) ZEPHYR_LIBS="-lzephyr";; esac if test "$with_zephyr" != "no"; then $as_echo "#define HAVE_ZEPHYR /**/" >>confdefs.h fi if test "$with_zephyr" != "no"; then ZEPHYR_TRUE= ZEPHYR_FALSE='#' else ZEPHYR_TRUE='#' ZEPHYR_FALSE= fi # Check whether --with-libcap was given. if test "${with_libcap+set}" = set; then : withval=$with_libcap; with_libcap="${withval}" fi have_libcap=no case $host_os in linux*) if test "x$with_libcap" = "xyes"; then { $as_echo "$as_me:${as_lineno-$LINENO}: checking for cap_get_proc in -lcap" >&5 $as_echo_n "checking for cap_get_proc in -lcap... " >&6; } if ${ac_cv_lib_cap_cap_get_proc+:} false; then : $as_echo_n "(cached) " >&6 else ac_check_lib_save_LIBS=$LIBS LIBS="-lcap $LIBS" cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ /* Override any GCC internal prototype to avoid an error. Use char because int might match the return type of a GCC builtin and then its argument prototype would still apply. */ #ifdef __cplusplus extern "C" #endif char cap_get_proc (); int main () { return cap_get_proc (); ; return 0; } _ACEOF if ac_fn_c_try_link "$LINENO"; then : ac_cv_lib_cap_cap_get_proc=yes else ac_cv_lib_cap_cap_get_proc=no fi rm -f core conftest.err conftest.$ac_objext \ conftest$ac_exeext conftest.$ac_ext LIBS=$ac_check_lib_save_LIBS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_cap_cap_get_proc" >&5 $as_echo "$ac_cv_lib_cap_cap_get_proc" >&6; } if test "x$ac_cv_lib_cap_cap_get_proc" = xyes; then : have_libcap=yes else have_libcap=no fi for ac_header in sys/capability.h sys/prctl.h do : as_ac_Header=`$as_echo "ac_cv_header_$ac_header" | $as_tr_sh` ac_fn_c_check_header_mongrel "$LINENO" "$ac_header" "$as_ac_Header" "$ac_includes_default" if eval test \"x\$"$as_ac_Header"\" = x"yes"; then : cat >>confdefs.h <<_ACEOF #define `$as_echo "HAVE_$ac_header" | $as_tr_cpp` 1 _ACEOF else have_libcap=no fi done if test "$have_libcap" = "yes"; then $as_echo "#define HAVE_LIBCAP /**/" >>confdefs.h LIBS="$LIBS -lcap" fi fi ;; *) ;; esac { $as_echo "$as_me:${as_lineno-$LINENO}: checking for libcap" >&5 $as_echo_n "checking for libcap... " >&6; } { $as_echo "$as_me:${as_lineno-$LINENO}: result: $have_libcap" >&5 $as_echo "$have_libcap" >&6; } # Check whether --enable-event-notification was given. if test "${enable_event_notification+set}" = set; then : enableval=$enable_event_notification; else enable_event_notification="yes"; fi if test "$enable_event_notification" != "no"; then pkg_failed=no { $as_echo "$as_me:${as_lineno-$LINENO}: checking for JANSSON" >&5 $as_echo_n "checking for JANSSON... " >&6; } if test -n "$JANSSON_CFLAGS"; then pkg_cv_JANSSON_CFLAGS="$JANSSON_CFLAGS" elif test -n "$PKG_CONFIG"; then if test -n "$PKG_CONFIG" && \ { { $as_echo "$as_me:${as_lineno-$LINENO}: \$PKG_CONFIG --exists --print-errors \"jansson >= 2.0\""; } >&5 ($PKG_CONFIG --exists --print-errors "jansson >= 2.0") 2>&5 ac_status=$? $as_echo "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 test $ac_status = 0; }; then pkg_cv_JANSSON_CFLAGS=`$PKG_CONFIG --cflags "jansson >= 2.0" 2>/dev/null` test "x$?" != "x0" && pkg_failed=yes else pkg_failed=yes fi else pkg_failed=untried fi if test -n "$JANSSON_LIBS"; then pkg_cv_JANSSON_LIBS="$JANSSON_LIBS" elif test -n "$PKG_CONFIG"; then if test -n "$PKG_CONFIG" && \ { { $as_echo "$as_me:${as_lineno-$LINENO}: \$PKG_CONFIG --exists --print-errors \"jansson >= 2.0\""; } >&5 ($PKG_CONFIG --exists --print-errors "jansson >= 2.0") 2>&5 ac_status=$? $as_echo "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 test $ac_status = 0; }; then pkg_cv_JANSSON_LIBS=`$PKG_CONFIG --libs "jansson >= 2.0" 2>/dev/null` test "x$?" != "x0" && pkg_failed=yes else pkg_failed=yes fi else pkg_failed=untried fi if test $pkg_failed = yes; then { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 $as_echo "no" >&6; } if $PKG_CONFIG --atleast-pkgconfig-version 0.20; then _pkg_short_errors_supported=yes else _pkg_short_errors_supported=no fi if test $_pkg_short_errors_supported = yes; then JANSSON_PKG_ERRORS=`$PKG_CONFIG --short-errors --print-errors --cflags --libs "jansson >= 2.0" 2>&1` else JANSSON_PKG_ERRORS=`$PKG_CONFIG --print-errors --cflags --libs "jansson >= 2.0" 2>&1` fi # Put the nasty error message in config.log where it belongs echo "$JANSSON_PKG_ERRORS" >&5 check_jansson=false { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: jansson 2.0 or later was not found, but is required to enable mailbox event notification" >&5 $as_echo "$as_me: WARNING: jansson 2.0 or later was not found, but is required to enable mailbox event notification" >&2;} enable_event_notification="no" elif test $pkg_failed = untried; then { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 $as_echo "no" >&6; } check_jansson=false { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: jansson 2.0 or later was not found, but is required to enable mailbox event notification" >&5 $as_echo "$as_me: WARNING: jansson 2.0 or later was not found, but is required to enable mailbox event notification" >&2;} enable_event_notification="no" else JANSSON_CFLAGS=$pkg_cv_JANSSON_CFLAGS JANSSON_LIBS=$pkg_cv_JANSSON_LIBS { $as_echo "$as_me:${as_lineno-$LINENO}: result: yes" >&5 $as_echo "yes" >&6; } check_jansson=true $as_echo "#define ENABLE_MBOXEVENT /**/" >>confdefs.h fi fi if test x$check_jansson = xtrue; then JANSSON_TRUE= JANSSON_FALSE='#' else JANSSON_TRUE='#' JANSSON_FALSE= fi # Check whether --with-pidfile was given. if test "${with_pidfile+set}" = set; then : withval=$with_pidfile; MASTERPIDFILE="$withval" else MASTERPIDFILE="/var/run/cyrus-master.pid" fi MASTERPIDFILE="\"$MASTERPIDFILE\"" cat >>confdefs.h <<_ACEOF #define MASTER_PIDFILE $MASTERPIDFILE _ACEOF # Check whether --enable-autocreate was given. if test "${enable_autocreate+set}" = set; then : enableval=$enable_autocreate; else enable_autocreate="no"; fi if test "$enable_autocreate" != "no"; then AUTOCREATE_TRUE= AUTOCREATE_FALSE='#' else AUTOCREATE_TRUE='#' AUTOCREATE_FALSE= fi if test "x$enable_autocreate" = "xyes"; then $as_echo "#define USE_AUTOCREATE /**/" >>confdefs.h fi # Check whether --enable-idled was given. if test "${enable_idled+set}" = set; then : enableval=$enable_idled; else enable_idled="no"; fi if test "$enable_idled" != "no"; then IDLED_TRUE= IDLED_FALSE='#' else IDLED_TRUE='#' IDLED_FALSE= fi # Check whether --enable-nntp was given. if test "${enable_nntp+set}" = set; then : enableval=$enable_nntp; else enable_nntp="no"; fi if test "$enable_nntp" != "no"; then NNTPD_TRUE= NNTPD_FALSE='#' else NNTPD_TRUE='#' NNTPD_FALSE= fi # Check whether --enable-murder was given. if test "${enable_murder+set}" = set; then : enableval=$enable_murder; else enable_murder="no"; fi if test "$enable_murder" != "no"; then MURDER_TRUE= MURDER_FALSE='#' else MURDER_TRUE='#' MURDER_FALSE= fi if test "$enable_murder" != no; then # for master/slave auto-selection for ac_header in sys/sockio.h do : ac_fn_c_check_header_mongrel "$LINENO" "sys/sockio.h" "ac_cv_header_sys_sockio_h" "$ac_includes_default" if test "x$ac_cv_header_sys_sockio_h" = xyes; then : cat >>confdefs.h <<_ACEOF #define HAVE_SYS_SOCKIO_H 1 _ACEOF fi done fi ENABLE_HTTP=no # Check whether --enable-http was given. if test "${enable_http+set}" = set; then : enableval=$enable_http; else enable_http="no"; fi if test "$enable_http" != "no"; then HTTPD_TRUE= HTTPD_FALSE='#' else HTTPD_TRUE='#' HTTPD_FALSE= fi HTTP_CPPFLAGS= HTTP_LIBS= if test "$enable_http" != no; then ENABLE_RSS=yes ENABLE_DAV=yes pkg_failed=no { $as_echo "$as_me:${as_lineno-$LINENO}: checking for XML2" >&5 $as_echo_n "checking for XML2... " >&6; } if test -n "$XML2_CFLAGS"; then pkg_cv_XML2_CFLAGS="$XML2_CFLAGS" elif test -n "$PKG_CONFIG"; then if test -n "$PKG_CONFIG" && \ { { $as_echo "$as_me:${as_lineno-$LINENO}: \$PKG_CONFIG --exists --print-errors \"libxml-2.0\""; } >&5 ($PKG_CONFIG --exists --print-errors "libxml-2.0") 2>&5 ac_status=$? $as_echo "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 test $ac_status = 0; }; then pkg_cv_XML2_CFLAGS=`$PKG_CONFIG --cflags "libxml-2.0" 2>/dev/null` test "x$?" != "x0" && pkg_failed=yes else pkg_failed=yes fi else pkg_failed=untried fi if test -n "$XML2_LIBS"; then pkg_cv_XML2_LIBS="$XML2_LIBS" elif test -n "$PKG_CONFIG"; then if test -n "$PKG_CONFIG" && \ { { $as_echo "$as_me:${as_lineno-$LINENO}: \$PKG_CONFIG --exists --print-errors \"libxml-2.0\""; } >&5 ($PKG_CONFIG --exists --print-errors "libxml-2.0") 2>&5 ac_status=$? $as_echo "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 test $ac_status = 0; }; then pkg_cv_XML2_LIBS=`$PKG_CONFIG --libs "libxml-2.0" 2>/dev/null` test "x$?" != "x0" && pkg_failed=yes else pkg_failed=yes fi else pkg_failed=untried fi if test $pkg_failed = yes; then { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 $as_echo "no" >&6; } if $PKG_CONFIG --atleast-pkgconfig-version 0.20; then _pkg_short_errors_supported=yes else _pkg_short_errors_supported=no fi if test $_pkg_short_errors_supported = yes; then XML2_PKG_ERRORS=`$PKG_CONFIG --short-errors --print-errors --cflags --libs "libxml-2.0" 2>&1` else XML2_PKG_ERRORS=`$PKG_CONFIG --print-errors --cflags --libs "libxml-2.0" 2>&1` fi # Put the nasty error message in config.log where it belongs echo "$XML2_PKG_ERRORS" >&5 as_fn_error $? "Need libxml-2.0 for http" "$LINENO" 5 elif test $pkg_failed = untried; then { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 $as_echo "no" >&6; } as_fn_error $? "Need libxml-2.0 for http" "$LINENO" 5 else XML2_CFLAGS=$pkg_cv_XML2_CFLAGS XML2_LIBS=$pkg_cv_XML2_LIBS { $as_echo "$as_me:${as_lineno-$LINENO}: result: yes" >&5 $as_echo "yes" >&6; } fi pkg_failed=no { $as_echo "$as_me:${as_lineno-$LINENO}: checking for ICAL" >&5 $as_echo_n "checking for ICAL... " >&6; } if test -n "$ICAL_CFLAGS"; then pkg_cv_ICAL_CFLAGS="$ICAL_CFLAGS" elif test -n "$PKG_CONFIG"; then if test -n "$PKG_CONFIG" && \ { { $as_echo "$as_me:${as_lineno-$LINENO}: \$PKG_CONFIG --exists --print-errors \"libical\""; } >&5 ($PKG_CONFIG --exists --print-errors "libical") 2>&5 ac_status=$? $as_echo "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 test $ac_status = 0; }; then pkg_cv_ICAL_CFLAGS=`$PKG_CONFIG --cflags "libical" 2>/dev/null` test "x$?" != "x0" && pkg_failed=yes else pkg_failed=yes fi else pkg_failed=untried fi if test -n "$ICAL_LIBS"; then pkg_cv_ICAL_LIBS="$ICAL_LIBS" elif test -n "$PKG_CONFIG"; then if test -n "$PKG_CONFIG" && \ { { $as_echo "$as_me:${as_lineno-$LINENO}: \$PKG_CONFIG --exists --print-errors \"libical\""; } >&5 ($PKG_CONFIG --exists --print-errors "libical") 2>&5 ac_status=$? $as_echo "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 test $ac_status = 0; }; then pkg_cv_ICAL_LIBS=`$PKG_CONFIG --libs "libical" 2>/dev/null` test "x$?" != "x0" && pkg_failed=yes else pkg_failed=yes fi else pkg_failed=untried fi if test $pkg_failed = yes; then { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 $as_echo "no" >&6; } if $PKG_CONFIG --atleast-pkgconfig-version 0.20; then _pkg_short_errors_supported=yes else _pkg_short_errors_supported=no fi if test $_pkg_short_errors_supported = yes; then ICAL_PKG_ERRORS=`$PKG_CONFIG --short-errors --print-errors --cflags --libs "libical" 2>&1` else ICAL_PKG_ERRORS=`$PKG_CONFIG --print-errors --cflags --libs "libical" 2>&1` fi # Put the nasty error message in config.log where it belongs echo "$ICAL_PKG_ERRORS" >&5 as_fn_error $? "Need libical for http" "$LINENO" 5 elif test $pkg_failed = untried; then { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 $as_echo "no" >&6; } as_fn_error $? "Need libical for http" "$LINENO" 5 else ICAL_CFLAGS=$pkg_cv_ICAL_CFLAGS ICAL_LIBS=$pkg_cv_ICAL_LIBS { $as_echo "$as_me:${as_lineno-$LINENO}: result: yes" >&5 $as_echo "yes" >&6; } fi pkg_failed=no { $as_echo "$as_me:${as_lineno-$LINENO}: checking for SQLITE3" >&5 $as_echo_n "checking for SQLITE3... " >&6; } if test -n "$SQLITE3_CFLAGS"; then pkg_cv_SQLITE3_CFLAGS="$SQLITE3_CFLAGS" elif test -n "$PKG_CONFIG"; then if test -n "$PKG_CONFIG" && \ { { $as_echo "$as_me:${as_lineno-$LINENO}: \$PKG_CONFIG --exists --print-errors \"sqlite3\""; } >&5 ($PKG_CONFIG --exists --print-errors "sqlite3") 2>&5 ac_status=$? $as_echo "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 test $ac_status = 0; }; then pkg_cv_SQLITE3_CFLAGS=`$PKG_CONFIG --cflags "sqlite3" 2>/dev/null` test "x$?" != "x0" && pkg_failed=yes else pkg_failed=yes fi else pkg_failed=untried fi if test -n "$SQLITE3_LIBS"; then pkg_cv_SQLITE3_LIBS="$SQLITE3_LIBS" elif test -n "$PKG_CONFIG"; then if test -n "$PKG_CONFIG" && \ { { $as_echo "$as_me:${as_lineno-$LINENO}: \$PKG_CONFIG --exists --print-errors \"sqlite3\""; } >&5 ($PKG_CONFIG --exists --print-errors "sqlite3") 2>&5 ac_status=$? $as_echo "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 test $ac_status = 0; }; then pkg_cv_SQLITE3_LIBS=`$PKG_CONFIG --libs "sqlite3" 2>/dev/null` test "x$?" != "x0" && pkg_failed=yes else pkg_failed=yes fi else pkg_failed=untried fi if test $pkg_failed = yes; then { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 $as_echo "no" >&6; } if $PKG_CONFIG --atleast-pkgconfig-version 0.20; then _pkg_short_errors_supported=yes else _pkg_short_errors_supported=no fi if test $_pkg_short_errors_supported = yes; then SQLITE3_PKG_ERRORS=`$PKG_CONFIG --short-errors --print-errors --cflags --libs "sqlite3" 2>&1` else SQLITE3_PKG_ERRORS=`$PKG_CONFIG --print-errors --cflags --libs "sqlite3" 2>&1` fi # Put the nasty error message in config.log where it belongs echo "$SQLITE3_PKG_ERRORS" >&5 as_fn_error $? "Need sqlite3 for http" "$LINENO" 5 elif test $pkg_failed = untried; then { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 $as_echo "no" >&6; } as_fn_error $? "Need sqlite3 for http" "$LINENO" 5 else SQLITE3_CFLAGS=$pkg_cv_SQLITE3_CFLAGS SQLITE3_LIBS=$pkg_cv_SQLITE3_LIBS { $as_echo "$as_me:${as_lineno-$LINENO}: result: yes" >&5 $as_echo "yes" >&6; } fi pkg_failed=no { $as_echo "$as_me:${as_lineno-$LINENO}: checking for JSON" >&5 $as_echo_n "checking for JSON... " >&6; } if test -n "$JSON_CFLAGS"; then pkg_cv_JSON_CFLAGS="$JSON_CFLAGS" elif test -n "$PKG_CONFIG"; then if test -n "$PKG_CONFIG" && \ { { $as_echo "$as_me:${as_lineno-$LINENO}: \$PKG_CONFIG --exists --print-errors \"jansson\""; } >&5 ($PKG_CONFIG --exists --print-errors "jansson") 2>&5 ac_status=$? $as_echo "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 test $ac_status = 0; }; then pkg_cv_JSON_CFLAGS=`$PKG_CONFIG --cflags "jansson" 2>/dev/null` test "x$?" != "x0" && pkg_failed=yes else pkg_failed=yes fi else pkg_failed=untried fi if test -n "$JSON_LIBS"; then pkg_cv_JSON_LIBS="$JSON_LIBS" elif test -n "$PKG_CONFIG"; then if test -n "$PKG_CONFIG" && \ { { $as_echo "$as_me:${as_lineno-$LINENO}: \$PKG_CONFIG --exists --print-errors \"jansson\""; } >&5 ($PKG_CONFIG --exists --print-errors "jansson") 2>&5 ac_status=$? $as_echo "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 test $ac_status = 0; }; then pkg_cv_JSON_LIBS=`$PKG_CONFIG --libs "jansson" 2>/dev/null` test "x$?" != "x0" && pkg_failed=yes else pkg_failed=yes fi else pkg_failed=untried fi if test $pkg_failed = yes; then { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 $as_echo "no" >&6; } if $PKG_CONFIG --atleast-pkgconfig-version 0.20; then _pkg_short_errors_supported=yes else _pkg_short_errors_supported=no fi if test $_pkg_short_errors_supported = yes; then JSON_PKG_ERRORS=`$PKG_CONFIG --short-errors --print-errors --cflags --libs "jansson" 2>&1` else JSON_PKG_ERRORS=`$PKG_CONFIG --print-errors --cflags --libs "jansson" 2>&1` fi # Put the nasty error message in config.log where it belongs echo "$JSON_PKG_ERRORS" >&5 as_fn_error $? "Need jansson for http" "$LINENO" 5 elif test $pkg_failed = untried; then { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 $as_echo "no" >&6; } as_fn_error $? "Need jansson for http" "$LINENO" 5 else JSON_CFLAGS=$pkg_cv_JSON_CFLAGS JSON_LIBS=$pkg_cv_JSON_LIBS { $as_echo "$as_me:${as_lineno-$LINENO}: result: yes" >&5 $as_echo "yes" >&6; } fi HTTP_LIBS="${XML2_LIBS} ${ICAL_LIBS} ${SQLITE3_LIBS} ${JSON_LIBS}" HTTP_CPPFLAGS="${JSON_CFLAGS} ${SQLITE3_CFLAGS} ${ICAL_CFLAGS} ${XML2_CFLAGS}" saved_LIBS=${LIBS} saved_CPPFLAGS="${CPPFLAGS}" LIBS="${LIBS} ${HTTP_LIBS}" CPPFLAGS="${CPPFLAGS} ${HTTP_CPPFLAGS}" $as_echo "#define HAVE_XML2 /**/" >>confdefs.h $as_echo "#define HAVE_ICAL /**/" >>confdefs.h $as_echo "#define HAVE_SQLITE3 /**/" >>confdefs.h $as_echo "#define WITH_DAV /**/" >>confdefs.h $as_echo "#define WITH_JSON /**/" >>confdefs.h { $as_echo "$as_me:${as_lineno-$LINENO}: checking for icaltimezone_set_builtin_tzdata in -lical" >&5 $as_echo_n "checking for icaltimezone_set_builtin_tzdata in -lical... " >&6; } if ${ac_cv_lib_ical_icaltimezone_set_builtin_tzdata+:} false; then : $as_echo_n "(cached) " >&6 else ac_check_lib_save_LIBS=$LIBS LIBS="-lical $LIBS" cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ /* Override any GCC internal prototype to avoid an error. Use char because int might match the return type of a GCC builtin and then its argument prototype would still apply. */ #ifdef __cplusplus extern "C" #endif char icaltimezone_set_builtin_tzdata (); int main () { return icaltimezone_set_builtin_tzdata (); ; return 0; } _ACEOF if ac_fn_c_try_link "$LINENO"; then : ac_cv_lib_ical_icaltimezone_set_builtin_tzdata=yes else ac_cv_lib_ical_icaltimezone_set_builtin_tzdata=no fi rm -f core conftest.err conftest.$ac_objext \ conftest$ac_exeext conftest.$ac_ext LIBS=$ac_check_lib_save_LIBS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_ical_icaltimezone_set_builtin_tzdata" >&5 $as_echo "$ac_cv_lib_ical_icaltimezone_set_builtin_tzdata" >&6; } if test "x$ac_cv_lib_ical_icaltimezone_set_builtin_tzdata" = xyes; then : $as_echo "#define HAVE_TZ_BY_REF /**/" >>confdefs.h fi cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ #include _ACEOF if (eval "$ac_cpp conftest.$ac_ext") 2>&5 | $EGREP "ICAL_TZUNTIL_PROPERTY" >/dev/null 2>&1; then : $as_echo "#define HAVE_TZDIST_PROPS /**/" >>confdefs.h fi rm -f conftest* CYRUS_OPENDKIM_CHK() if test "$opendkimlib" = "yes"; then $as_echo "#define WITH_DKIM /**/" >>confdefs.h fi cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ #include _ACEOF if (eval "$ac_cpp conftest.$ac_ext") 2>&5 | $EGREP "ICAL_IANA_PARAMETER" >/dev/null 2>&1; then : $as_echo "#define HAVE_IANA_PARAMS /**/" >>confdefs.h else { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: Your version of libical can not support scheduling or managed attachments. Consider upgrading to libical >= 0.48" >&5 $as_echo "$as_me: WARNING: Your version of libical can not support scheduling or managed attachments. Consider upgrading to libical >= 0.48" >&2;} fi rm -f conftest* cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ #include _ACEOF if (eval "$ac_cpp conftest.$ac_ext") 2>&5 | $EGREP "ICAL_SCHEDULESTATUS_PARAMETER" >/dev/null 2>&1; then : $as_echo "#define HAVE_SCHEDULING_PARAMS /**/" >>confdefs.h fi rm -f conftest* cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ #include _ACEOF if (eval "$ac_cpp conftest.$ac_ext") 2>&5 | $EGREP "ICAL_VAVAILABILITY_COMPONENT" >/dev/null 2>&1; then : $as_echo "#define HAVE_VAVAILABILITY /**/" >>confdefs.h fi rm -f conftest* cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ #include _ACEOF if (eval "$ac_cpp conftest.$ac_ext") 2>&5 | $EGREP "ICAL_VPOLL_COMPONENT" >/dev/null 2>&1; then : $as_echo "#define HAVE_VPOLL /**/" >>confdefs.h fi rm -f conftest* ENABLE_RSCALE=yes pkg_failed=no { $as_echo "$as_me:${as_lineno-$LINENO}: checking for ICU" >&5 $as_echo_n "checking for ICU... " >&6; } if test -n "$ICU_CFLAGS"; then pkg_cv_ICU_CFLAGS="$ICU_CFLAGS" elif test -n "$PKG_CONFIG"; then if test -n "$PKG_CONFIG" && \ { { $as_echo "$as_me:${as_lineno-$LINENO}: \$PKG_CONFIG --exists --print-errors \"icu-i18n\""; } >&5 ($PKG_CONFIG --exists --print-errors "icu-i18n") 2>&5 ac_status=$? $as_echo "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 test $ac_status = 0; }; then pkg_cv_ICU_CFLAGS=`$PKG_CONFIG --cflags "icu-i18n" 2>/dev/null` test "x$?" != "x0" && pkg_failed=yes else pkg_failed=yes fi else pkg_failed=untried fi if test -n "$ICU_LIBS"; then pkg_cv_ICU_LIBS="$ICU_LIBS" elif test -n "$PKG_CONFIG"; then if test -n "$PKG_CONFIG" && \ { { $as_echo "$as_me:${as_lineno-$LINENO}: \$PKG_CONFIG --exists --print-errors \"icu-i18n\""; } >&5 ($PKG_CONFIG --exists --print-errors "icu-i18n") 2>&5 ac_status=$? $as_echo "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 test $ac_status = 0; }; then pkg_cv_ICU_LIBS=`$PKG_CONFIG --libs "icu-i18n" 2>/dev/null` test "x$?" != "x0" && pkg_failed=yes else pkg_failed=yes fi else pkg_failed=untried fi if test $pkg_failed = yes; then { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 $as_echo "no" >&6; } if $PKG_CONFIG --atleast-pkgconfig-version 0.20; then _pkg_short_errors_supported=yes else _pkg_short_errors_supported=no fi if test $_pkg_short_errors_supported = yes; then ICU_PKG_ERRORS=`$PKG_CONFIG --short-errors --print-errors --cflags --libs "icu-i18n" 2>&1` else ICU_PKG_ERRORS=`$PKG_CONFIG --print-errors --cflags --libs "icu-i18n" 2>&1` fi # Put the nasty error message in config.log where it belongs echo "$ICU_PKG_ERRORS" >&5 ENABLE_RSCALE=no elif test $pkg_failed = untried; then { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 $as_echo "no" >&6; } ENABLE_RSCALE=no else ICU_CFLAGS=$pkg_cv_ICU_CFLAGS ICU_LIBS=$pkg_cv_ICU_LIBS { $as_echo "$as_me:${as_lineno-$LINENO}: result: yes" >&5 $as_echo "yes" >&6; } fi if test "$ENABLE_RSCALE" != no; then { $as_echo "$as_me:${as_lineno-$LINENO}: checking for icalrecurrencetype_rscale_is_supported in -lical" >&5 $as_echo_n "checking for icalrecurrencetype_rscale_is_supported in -lical... " >&6; } if ${ac_cv_lib_ical_icalrecurrencetype_rscale_is_supported+:} false; then : $as_echo_n "(cached) " >&6 else ac_check_lib_save_LIBS=$LIBS LIBS="-lical $LIBS" cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ /* Override any GCC internal prototype to avoid an error. Use char because int might match the return type of a GCC builtin and then its argument prototype would still apply. */ #ifdef __cplusplus extern "C" #endif char icalrecurrencetype_rscale_is_supported (); int main () { return icalrecurrencetype_rscale_is_supported (); ; return 0; } _ACEOF if ac_fn_c_try_link "$LINENO"; then : ac_cv_lib_ical_icalrecurrencetype_rscale_is_supported=yes else ac_cv_lib_ical_icalrecurrencetype_rscale_is_supported=no fi rm -f core conftest.err conftest.$ac_objext \ conftest$ac_exeext conftest.$ac_ext LIBS=$ac_check_lib_save_LIBS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_ical_icalrecurrencetype_rscale_is_supported" >&5 $as_echo "$ac_cv_lib_ical_icalrecurrencetype_rscale_is_supported" >&6; } if test "x$ac_cv_lib_ical_icalrecurrencetype_rscale_is_supported" = xyes; then : $as_echo "#define HAVE_RSCALE /**/" >>confdefs.h fi fi LIBS="${saved_LIBS}" CPPFLAGS="${saved_CPPFLAGS}" fi # Check whether --enable-replication was given. if test "${enable_replication+set}" = set; then : enableval=$enable_replication; else enable_replication="no"; fi if test "$enable_replication" != no; then REPLICATION_TRUE= REPLICATION_FALSE='#' else REPLICATION_TRUE='#' REPLICATION_FALSE= fi # Check whether --with-com_err was given. if test "${with_com_err+set}" = set; then : withval=$with_com_err; fi if test -z "$with_com_err"; then # no value supplied { $as_echo "$as_me:${as_lineno-$LINENO}: checking for com_err in -lcom_err" >&5 $as_echo_n "checking for com_err in -lcom_err... " >&6; } if ${ac_cv_lib_com_err_com_err+:} false; then : $as_echo_n "(cached) " >&6 else ac_check_lib_save_LIBS=$LIBS LIBS="-lcom_err $LIBS" cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ /* Override any GCC internal prototype to avoid an error. Use char because int might match the return type of a GCC builtin and then its argument prototype would still apply. */ #ifdef __cplusplus extern "C" #endif char com_err (); int main () { return com_err (); ; return 0; } _ACEOF if ac_fn_c_try_link "$LINENO"; then : ac_cv_lib_com_err_com_err=yes else ac_cv_lib_com_err_com_err=no fi rm -f core conftest.err conftest.$ac_objext \ conftest$ac_exeext conftest.$ac_ext LIBS=$ac_check_lib_save_LIBS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_com_err_com_err" >&5 $as_echo "$ac_cv_lib_com_err_com_err" >&6; } if test "x$ac_cv_lib_com_err_com_err" = xyes; then : # com_err is already in library path # guess we're okay # can use system com_err with_com_err="" ac_fn_c_check_header_mongrel "$LINENO" "et/com_err.h" "ac_cv_header_et_com_err_h" "$ac_includes_default" if test "x$ac_cv_header_et_com_err_h" = xyes; then : $as_echo "#define HAVE_ET_COM_ERR_H /**/" >>confdefs.h else ac_fn_c_check_header_mongrel "$LINENO" "com_err.h" "ac_cv_header_com_err_h" "$ac_includes_default" if test "x$ac_cv_header_com_err_h" = xyes; then : else as_fn_error $? "cannot locate com_err.h" "$LINENO" 5 fi fi # Extract the first word of "compile_et", so it can be a program name with args. set dummy compile_et; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } if ${ac_cv_path_COMPILE_ET+:} false; then : $as_echo_n "(cached) " >&6 else case $COMPILE_ET in [\\/]* | ?:[\\/]*) ac_cv_path_COMPILE_ET="$COMPILE_ET" # Let the user override the test with a path. ;; *) as_save_IFS=$IFS; IFS=$PATH_SEPARATOR for as_dir in $PATH do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_path_COMPILE_ET="$as_dir/$ac_word$ac_exec_ext" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 fi done done IFS=$as_save_IFS test -z "$ac_cv_path_COMPILE_ET" && ac_cv_path_COMPILE_ET="no compile et" ;; esac fi COMPILE_ET=$ac_cv_path_COMPILE_ET if test -n "$COMPILE_ET"; then { $as_echo "$as_me:${as_lineno-$LINENO}: result: $COMPILE_ET" >&5 $as_echo "$COMPILE_ET" >&6; } else { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 $as_echo "no" >&6; } fi else if test -f /usr/local/include/com_err.h -o -f /usr/local/include/et/com_err.h; then with_com_err="/usr/local" # Extract the first word of "/usr/local/bin/compile_et", so it can be a program name with args. set dummy /usr/local/bin/compile_et; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } if ${ac_cv_path_COMPILE_ET+:} false; then : $as_echo_n "(cached) " >&6 else case $COMPILE_ET in [\\/]* | ?:[\\/]*) ac_cv_path_COMPILE_ET="$COMPILE_ET" # Let the user override the test with a path. ;; *) as_save_IFS=$IFS; IFS=$PATH_SEPARATOR for as_dir in $PATH do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_path_COMPILE_ET="$as_dir/$ac_word$ac_exec_ext" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 fi done done IFS=$as_save_IFS test -z "$ac_cv_path_COMPILE_ET" && ac_cv_path_COMPILE_ET="no compile et" ;; esac fi COMPILE_ET=$ac_cv_path_COMPILE_ET if test -n "$COMPILE_ET"; then { $as_echo "$as_me:${as_lineno-$LINENO}: result: $COMPILE_ET" >&5 $as_echo "$COMPILE_ET" >&6; } else { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 $as_echo "no" >&6; } fi elif test -f /usr/include/com_err.h -o -f /usr/include/et/com_err.h; then with_com_err="/usr" # Extract the first word of "/usr/bin/compile_et", so it can be a program name with args. set dummy /usr/bin/compile_et; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } if ${ac_cv_path_COMPILE_ET+:} false; then : $as_echo_n "(cached) " >&6 else case $COMPILE_ET in [\\/]* | ?:[\\/]*) ac_cv_path_COMPILE_ET="$COMPILE_ET" # Let the user override the test with a path. ;; *) as_save_IFS=$IFS; IFS=$PATH_SEPARATOR for as_dir in $PATH do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_path_COMPILE_ET="$as_dir/$ac_word$ac_exec_ext" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 fi done done IFS=$as_save_IFS test -z "$ac_cv_path_COMPILE_ET" && ac_cv_path_COMPILE_ET="no compile et" ;; esac fi COMPILE_ET=$ac_cv_path_COMPILE_ET if test -n "$COMPILE_ET"; then { $as_echo "$as_me:${as_lineno-$LINENO}: result: $COMPILE_ET" >&5 $as_echo "$COMPILE_ET" >&6; } else { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 $as_echo "no" >&6; } fi else # use ours with_com_err=yes fi fi if test "${with_com_err}" = "no"; then { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: com_err is required; included version will be used." >&5 $as_echo "$as_me: WARNING: com_err is required; included version will be used." >&2;} with_com_err="yes" fi if test "${COMPILE_ET}" = "no compile et" -o "${COMPILE_ET}" = ""; then { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: Parts of com_err distribuion were found, but not compile_et." >&5 $as_echo "$as_me: WARNING: Parts of com_err distribuion were found, but not compile_et." >&2;} { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: Will build com_err from included sources." >&5 $as_echo "$as_me: WARNING: Will build com_err from included sources." >&2;} with_com_err="yes" # build it ourselves fi fi case "$with_com_err" in # built-in et yes) # use the com_err we're gonna build COMPILE_ET="\${abs_top_builddir}/com_err/et/compile_et" ;; "") # no problem, we already have it in the paths # we do nothing to pick it up ;; *) # use whatever they told us, or whatever we found COMPILE_ET="${with_com_err}/bin/compile_et" ;; esac if test "$with_com_err" != yes ; then TEST1=".cyrus-configure-test-$$" /bin/rm -f $TEST1.et $TEST1.h $TEST1.c echo "error_table imap" >> $TEST1.et echo "ec IMAP_TESTING," >> $TEST1.et echo " \"Testing\"" >> $TEST1.et echo "end" >> $TEST1.et "${COMPILE_ET}" $TEST1.et > /dev/null compile_et_ok=no if test -f $TEST1.h ; then if test `awk '/IMAP_TESTING/{print $3}' $TEST1.h 2>/dev/null` = "(-1904809472L)" ; then compile_et_ok=yes fi fi /bin/rm -f $TEST1.et $TEST1.h $TEST1.c if test "$compile_et_ok" = no ; then # revert to the built-in compile_et { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: It seems $COMPILE_ET is buggy, building our own" >&5 $as_echo "$as_me: WARNING: It seems $COMPILE_ET is buggy, building our own" >&2;} with_com_err=yes COMPILE_ET="\${abs_top_builddir}/com_err/et/compile_et" fi fi case "$with_com_err" in # built-in et yes) # use the com_err we're gonna build COM_ERR_LIBS="com_err/et/libcyrus_com_err.la" COM_ERR_CPPFLAGS="-I\${top_srcdir}/com_err/et" ;; "") # no problem, we already have it in the paths # we do nothing to pick it up COM_ERR_LIBS="-lcom_err" # hope it's not shared # we already set COMPILE_ET, or we didn't get here COM_ERR_CPPFLAGS="" ;; *) # use whatever they told us, or whatever we found COM_ERR_LIBS="${with_com_err}/lib/libcom_err.a" COM_ERR_CPPFLAGS="-I${with_com_err}/include" # Ever get the feeling people hide this stuff on purpose? if test -d "${with_com_err}/include/et" ; then COM_ERR_CPPFLAGS="-I${with_com_err}/include/et" fi esac if test "$with_com_err" = "yes"; then COM_ERR_TRUE= COM_ERR_FALSE='#' else COM_ERR_TRUE='#' COM_ERR_FALSE= fi if test "$with_com_err" = "yes"; then PKG_CONFIG_COM_ERR_LIB="-lcyrus_com_err" fi if test "$USE_MAINTAINER_MODE" = "yes" ; then # Extract the first word of "gperf", so it can be a program name with args. set dummy gperf; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } if ${ac_cv_prog_GPERF+:} false; then : $as_echo_n "(cached) " >&6 else if test -n "$GPERF"; then ac_cv_prog_GPERF="$GPERF" # Let the user override the test. else as_save_IFS=$IFS; IFS=$PATH_SEPARATOR for as_dir in $PATH do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_prog_GPERF="yes" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 fi done done IFS=$as_save_IFS test -z "$ac_cv_prog_GPERF" && ac_cv_prog_GPERF="no" fi fi GPERF=$ac_cv_prog_GPERF if test -n "$GPERF"; then { $as_echo "$as_me:${as_lineno-$LINENO}: result: $GPERF" >&5 $as_echo "$GPERF" >&6; } else { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 $as_echo "no" >&6; } fi if test "$GPERF" != "yes"; then as_fn_error $? "gperf is not installed on this system, but is required for maintainer mode build rules" "$LINENO" 5 fi fi { $as_echo "$as_me:${as_lineno-$LINENO}: checking for modern syslog" >&5 $as_echo_n "checking for modern syslog... " >&6; } if ${cyrus_cv_lib_syslog+:} false; then : $as_echo_n "(cached) " >&6 else cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ #include #ifndef LOG_LOCAL6 #include #endif _ACEOF if ac_fn_c_try_cpp "$LINENO"; then : cyrus_cv_lib_syslog=yes else cyrus_cv_lib_syslog=no fi rm -f conftest.err conftest.i conftest.$ac_ext fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $cyrus_cv_lib_syslog" >&5 $as_echo "$cyrus_cv_lib_syslog" >&6; } { $as_echo "$as_me:${as_lineno-$LINENO}: checking which syslog facility to use" >&5 $as_echo_n "checking which syslog facility to use... " >&6; } SYSLOG_FACILITY=LOG_LOCAL6 # Check whether --with-syslogfacility was given. if test "${with_syslogfacility+set}" = set; then : withval=$with_syslogfacility; if test "$withval" != "yes" -a "$withval" != "no" ; then SYSLOG_FACILITY=LOG_$withval fi; fi cat >>confdefs.h <<_ACEOF #define SYSLOG_FACILITY $SYSLOG_FACILITY _ACEOF { $as_echo "$as_me:${as_lineno-$LINENO}: result: $SYSLOG_FACILITY" >&5 $as_echo "$SYSLOG_FACILITY" >&6; } ac_fn_c_check_func "$LINENO" "getdtablesize" "ac_cv_func_getdtablesize" if test "x$ac_cv_func_getdtablesize" = xyes; then : $as_echo "#define HAVE_GETDTABLESIZE 1" >>confdefs.h else case " $LIBOBJS " in *" getdtablesize.$ac_objext "* ) ;; *) LIBOBJS="$LIBOBJS getdtablesize.$ac_objext" ;; esac fi # Check whether --enable-cmulocal was given. if test "${enable_cmulocal+set}" = set; then : enableval=$enable_cmulocal; fi if test "$enable_cmulocal" = "yes"; then CMULOCAL_TRUE= CMULOCAL_FALSE='#' else CMULOCAL_TRUE='#' CMULOCAL_FALSE= fi { $as_echo "$as_me:${as_lineno-$LINENO}: checking to use old sieve service name" >&5 $as_echo_n "checking to use old sieve service name... " >&6; } # Check whether --enable-oldsievename was given. if test "${enable_oldsievename+set}" = set; then : enableval=$enable_oldsievename; if test "$enableval" = yes; then { $as_echo "$as_me:${as_lineno-$LINENO}: result: yes" >&5 $as_echo "yes" >&6; } $as_echo "#define OLD_SIEVE_SERVICE_NAME /**/" >>confdefs.h else { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 $as_echo "no" >&6; } fi else { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 $as_echo "no" >&6; } fi # Check whether --enable-netscapehack was given. if test "${enable_netscapehack+set}" = set; then : enableval=$enable_netscapehack; if test "$enableval" = yes; then $as_echo "#define ENABLE_X_NETSCAPE_HACK /**/" >>confdefs.h fi fi ac_fn_c_check_func "$LINENO" "crypt" "ac_cv_func_crypt" if test "x$ac_cv_func_crypt" = xyes; then : cmu_have_crypt=yes else { $as_echo "$as_me:${as_lineno-$LINENO}: checking for crypt in -lcrypt" >&5 $as_echo_n "checking for crypt in -lcrypt... " >&6; } if ${ac_cv_lib_crypt_crypt+:} false; then : $as_echo_n "(cached) " >&6 else ac_check_lib_save_LIBS=$LIBS LIBS="-lcrypt $LIBS" cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ /* Override any GCC internal prototype to avoid an error. Use char because int might match the return type of a GCC builtin and then its argument prototype would still apply. */ #ifdef __cplusplus extern "C" #endif char crypt (); int main () { return crypt (); ; return 0; } _ACEOF if ac_fn_c_try_link "$LINENO"; then : ac_cv_lib_crypt_crypt=yes else ac_cv_lib_crypt_crypt=no fi rm -f core conftest.err conftest.$ac_objext \ conftest$ac_exeext conftest.$ac_ext LIBS=$ac_check_lib_save_LIBS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_crypt_crypt" >&5 $as_echo "$ac_cv_lib_crypt_crypt" >&6; } if test "x$ac_cv_lib_crypt_crypt" = xyes; then : LIB_CRYPT="-lcrypt"; cmu_have_crypt=yes else cmu_have_crypt=no fi fi # Check whether --enable-gssapi was given. if test "${enable_gssapi+set}" = set; then : enableval=$enable_gssapi; gssapi=$enableval else gssapi=yes fi # Check whether --with-gss_impl was given. if test "${with_gss_impl+set}" = set; then : withval=$with_gss_impl; gss_impl=$withval else gss_impl=auto fi if test "$gssapi" != no; then platform= case "${host}" in *-*-linux*) platform=__linux ;; *-*-hpux*) platform=__hpux ;; *-*-irix*) platform=__irix ;; *-*-solaris2*) # When should we use __sunos? platform=__solaris ;; *-*-aix*) ###_AIX platform=__aix ;; *) { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: The system type is not recognized. If you believe that CyberSafe GSSAPI works on this platform, please update the configure script" >&5 $as_echo "$as_me: WARNING: The system type is not recognized. If you believe that CyberSafe GSSAPI works on this platform, please update the configure script" >&2;} if test "$gss_impl" = "cybersafe"; then as_fn_error $? "CyberSafe was forced, cannot continue as platform is not supported" "$LINENO" 5 fi ;; esac cmu_saved_CPPFLAGS=$CPPFLAGS if test -d ${gssapi}; then CPPFLAGS="$CPPFLAGS -I$gssapi/include" # We want to keep -I in our CPPFLAGS, but only if we succeed cmu_saved_CPPFLAGS=$CPPFLAGS ### I am not sure how useful is this (and whether this is required at all ### especially when we have to provide two -L flags for new CyberSafe LDFLAGS="$LDFLAGS -L$gssapi/lib" if test -n "$platform"; then if test "$gss_impl" = "auto" -o "$gss_impl" = "cybersafe"; then CPPFLAGS="$CPPFLAGS -D$platform" if test -d "${gssapi}/appsec-sdk/include"; then CPPFLAGS="$CPPFLAGS -I${gssapi}/appsec-sdk/include" fi fi fi fi ac_fn_c_check_header_mongrel "$LINENO" "gssapi.h" "ac_cv_header_gssapi_h" "$ac_includes_default" if test "x$ac_cv_header_gssapi_h" = xyes; then : else ac_fn_c_check_header_mongrel "$LINENO" "gssapi/gssapi.h" "ac_cv_header_gssapi_gssapi_h" "$ac_includes_default" if test "x$ac_cv_header_gssapi_gssapi_h" = xyes; then : else gssapi=no fi fi for ac_header in gssapi/gssapi_ext.h do : ac_fn_c_check_header_mongrel "$LINENO" "gssapi/gssapi_ext.h" "ac_cv_header_gssapi_gssapi_ext_h" "$ac_includes_default" if test "x$ac_cv_header_gssapi_gssapi_ext_h" = xyes; then : cat >>confdefs.h <<_ACEOF #define HAVE_GSSAPI_GSSAPI_EXT_H 1 _ACEOF fi done CPPFLAGS=$cmu_saved_CPPFLAGS fi if test "$gssapi" != no; then if test "$ac_cv_header_gssapi_h" = "yes" -o "$ac_cv_header_gssapi_gssapi_h" = "yes"; then $as_echo "#define HAVE_GSSAPI_H /**/" >>confdefs.h fi # We need to find out which gssapi implementation we are # using. Supported alternatives are: MIT Kerberos 5, # Heimdal Kerberos 5 (http://www.pdc.kth.se/heimdal), # CyberSafe Kerberos 5 (http://www.cybersafe.com/) # and Sun SEAM (http://wwws.sun.com/software/security/kerberos/) # # The choice is reflected in GSSAPIBASE_LIBS { $as_echo "$as_me:${as_lineno-$LINENO}: checking for res_search in -lresolv" >&5 $as_echo_n "checking for res_search in -lresolv... " >&6; } if ${ac_cv_lib_resolv_res_search+:} false; then : $as_echo_n "(cached) " >&6 else ac_check_lib_save_LIBS=$LIBS LIBS="-lresolv $LIBS" cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ /* Override any GCC internal prototype to avoid an error. Use char because int might match the return type of a GCC builtin and then its argument prototype would still apply. */ #ifdef __cplusplus extern "C" #endif char res_search (); int main () { return res_search (); ; return 0; } _ACEOF if ac_fn_c_try_link "$LINENO"; then : ac_cv_lib_resolv_res_search=yes else ac_cv_lib_resolv_res_search=no fi rm -f core conftest.err conftest.$ac_objext \ conftest$ac_exeext conftest.$ac_ext LIBS=$ac_check_lib_save_LIBS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_resolv_res_search" >&5 $as_echo "$ac_cv_lib_resolv_res_search" >&6; } if test "x$ac_cv_lib_resolv_res_search" = xyes; then : cat >>confdefs.h <<_ACEOF #define HAVE_LIBRESOLV 1 _ACEOF LIBS="-lresolv $LIBS" fi if test -d ${gssapi}; then gssapi_dir="${gssapi}/lib" GSSAPIBASE_LIBS="-L$gssapi_dir" GSSAPIBASE_STATIC_LIBS="-L$gssapi_dir" else # FIXME: This is only used for building cyrus, and then only as # a real hack. it needs to be fixed. gssapi_dir="/usr/local/lib" fi # Check a full link against the Heimdal libraries. # If this fails, check a full link against the MIT libraries. # If this fails, check a full link against the CyberSafe libraries. # If this fails, check a full link against the Solaris 8 and up libgss. if test "$gss_impl" = "auto" -o "$gss_impl" = "heimdal"; then gss_failed=0 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for gss_unwrap in -lgssapi" >&5 $as_echo_n "checking for gss_unwrap in -lgssapi... " >&6; } if ${ac_cv_lib_gssapi_gss_unwrap+:} false; then : $as_echo_n "(cached) " >&6 else ac_check_lib_save_LIBS=$LIBS LIBS="-lgssapi ${GSSAPIBASE_LIBS} -lgssapi -lkrb5 -lasn1 -lroken ${LIB_CRYPT} ${LIB_DES} -lcom_err ${LIB_SOCKET} $LIBS" cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ /* Override any GCC internal prototype to avoid an error. Use char because int might match the return type of a GCC builtin and then its argument prototype would still apply. */ #ifdef __cplusplus extern "C" #endif char gss_unwrap (); int main () { return gss_unwrap (); ; return 0; } _ACEOF if ac_fn_c_try_link "$LINENO"; then : ac_cv_lib_gssapi_gss_unwrap=yes else ac_cv_lib_gssapi_gss_unwrap=no fi rm -f core conftest.err conftest.$ac_objext \ conftest$ac_exeext conftest.$ac_ext LIBS=$ac_check_lib_save_LIBS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_gssapi_gss_unwrap" >&5 $as_echo "$ac_cv_lib_gssapi_gss_unwrap" >&6; } if test "x$ac_cv_lib_gssapi_gss_unwrap" = xyes; then : gss_impl="heimdal" else gss_failed=1 fi if test "$gss_impl" != "auto" -a "$gss_failed" = "1"; then gss_impl="failed" fi fi if test "$gss_impl" = "auto" -o "$gss_impl" = "mit"; then # check for libkrb5support first { $as_echo "$as_me:${as_lineno-$LINENO}: checking for krb5int_getspecific in -lkrb5support" >&5 $as_echo_n "checking for krb5int_getspecific in -lkrb5support... " >&6; } if ${ac_cv_lib_krb5support_krb5int_getspecific+:} false; then : $as_echo_n "(cached) " >&6 else ac_check_lib_save_LIBS=$LIBS LIBS="-lkrb5support ${LIB_SOCKET} $LIBS" cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ /* Override any GCC internal prototype to avoid an error. Use char because int might match the return type of a GCC builtin and then its argument prototype would still apply. */ #ifdef __cplusplus extern "C" #endif char krb5int_getspecific (); int main () { return krb5int_getspecific (); ; return 0; } _ACEOF if ac_fn_c_try_link "$LINENO"; then : ac_cv_lib_krb5support_krb5int_getspecific=yes else ac_cv_lib_krb5support_krb5int_getspecific=no fi rm -f core conftest.err conftest.$ac_objext \ conftest$ac_exeext conftest.$ac_ext LIBS=$ac_check_lib_save_LIBS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_krb5support_krb5int_getspecific" >&5 $as_echo "$ac_cv_lib_krb5support_krb5int_getspecific" >&6; } if test "x$ac_cv_lib_krb5support_krb5int_getspecific" = xyes; then : K5SUP=-lkrb5support K5SUPSTATIC=$gssapi_dir/libkrb5support.a fi gss_failed=0 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for gss_unwrap in -lgssapi_krb5" >&5 $as_echo_n "checking for gss_unwrap in -lgssapi_krb5... " >&6; } if ${ac_cv_lib_gssapi_krb5_gss_unwrap+:} false; then : $as_echo_n "(cached) " >&6 else ac_check_lib_save_LIBS=$LIBS LIBS="-lgssapi_krb5 ${GSSAPIBASE_LIBS} -lgssapi_krb5 -lkrb5 -lk5crypto -lcom_err ${K5SUP} ${LIB_SOCKET} $LIBS" cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ /* Override any GCC internal prototype to avoid an error. Use char because int might match the return type of a GCC builtin and then its argument prototype would still apply. */ #ifdef __cplusplus extern "C" #endif char gss_unwrap (); int main () { return gss_unwrap (); ; return 0; } _ACEOF if ac_fn_c_try_link "$LINENO"; then : ac_cv_lib_gssapi_krb5_gss_unwrap=yes else ac_cv_lib_gssapi_krb5_gss_unwrap=no fi rm -f core conftest.err conftest.$ac_objext \ conftest$ac_exeext conftest.$ac_ext LIBS=$ac_check_lib_save_LIBS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_gssapi_krb5_gss_unwrap" >&5 $as_echo "$ac_cv_lib_gssapi_krb5_gss_unwrap" >&6; } if test "x$ac_cv_lib_gssapi_krb5_gss_unwrap" = xyes; then : gss_impl="mit" else gss_failed=1 fi if test "$gss_impl" != "auto" -a "$gss_failed" = "1"; then gss_impl="failed" fi fi # For Cybersafe one has to set a platform define in order to make compilation work if test "$gss_impl" = "auto" -o "$gss_impl" = "cybersafe"; then cmu_saved_CPPFLAGS=$CPPFLAGS cmu_saved_GSSAPIBASE_LIBS=$GSSAPIBASE_LIBS # FIXME - Note that the libraries are in .../lib64 for 64bit kernels if test -d "${gssapi}/appsec-rt/lib"; then GSSAPIBASE_LIBS="$GSSAPIBASE_LIBS -L${gssapi}/appsec-rt/lib" fi CPPFLAGS="$CPPFLAGS -D$platform" if test -d "${gssapi}/appsec-sdk/include"; then CPPFLAGS="$CPPFLAGS -I${gssapi}/appsec-sdk/include" fi gss_failed=0 # Check for CyberSafe with two libraries first, than fall back to a single # library (older CyberSafe) unset ac_cv_lib_gss_csf_gss_acq_user { $as_echo "$as_me:${as_lineno-$LINENO}: checking for csf_gss_acq_user in -lgss" >&5 $as_echo_n "checking for csf_gss_acq_user in -lgss... " >&6; } if ${ac_cv_lib_gss_csf_gss_acq_user+:} false; then : $as_echo_n "(cached) " >&6 else ac_check_lib_save_LIBS=$LIBS LIBS="-lgss ${GSSAPIBASE_LIBS} -lgss -lcstbk5 $LIBS" cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ /* Override any GCC internal prototype to avoid an error. Use char because int might match the return type of a GCC builtin and then its argument prototype would still apply. */ #ifdef __cplusplus extern "C" #endif char csf_gss_acq_user (); int main () { return csf_gss_acq_user (); ; return 0; } _ACEOF if ac_fn_c_try_link "$LINENO"; then : ac_cv_lib_gss_csf_gss_acq_user=yes else ac_cv_lib_gss_csf_gss_acq_user=no fi rm -f core conftest.err conftest.$ac_objext \ conftest$ac_exeext conftest.$ac_ext LIBS=$ac_check_lib_save_LIBS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_gss_csf_gss_acq_user" >&5 $as_echo "$ac_cv_lib_gss_csf_gss_acq_user" >&6; } if test "x$ac_cv_lib_gss_csf_gss_acq_user" = xyes; then : gss_impl="cybersafe03" else unset ac_cv_lib_gss_csf_gss_acq_user; { $as_echo "$as_me:${as_lineno-$LINENO}: checking for csf_gss_acq_user in -lgss" >&5 $as_echo_n "checking for csf_gss_acq_user in -lgss... " >&6; } if ${ac_cv_lib_gss_csf_gss_acq_user+:} false; then : $as_echo_n "(cached) " >&6 else ac_check_lib_save_LIBS=$LIBS LIBS="-lgss $GSSAPIBASE_LIBS -lgss $LIBS" cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ /* Override any GCC internal prototype to avoid an error. Use char because int might match the return type of a GCC builtin and then its argument prototype would still apply. */ #ifdef __cplusplus extern "C" #endif char csf_gss_acq_user (); int main () { return csf_gss_acq_user (); ; return 0; } _ACEOF if ac_fn_c_try_link "$LINENO"; then : ac_cv_lib_gss_csf_gss_acq_user=yes else ac_cv_lib_gss_csf_gss_acq_user=no fi rm -f core conftest.err conftest.$ac_objext \ conftest$ac_exeext conftest.$ac_ext LIBS=$ac_check_lib_save_LIBS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_gss_csf_gss_acq_user" >&5 $as_echo "$ac_cv_lib_gss_csf_gss_acq_user" >&6; } if test "x$ac_cv_lib_gss_csf_gss_acq_user" = xyes; then : gss_impl="cybersafe" else gss_failed=1 fi fi if test "$gss_failed" = "1"; then # Restore variables GSSAPIBASE_LIBS=$cmu_saved_GSSAPIBASE_LIBS CPPFLAGS=$cmu_saved_CPPFLAGS if test "$gss_impl" != "auto"; then gss_impl="failed" fi fi fi if test "$gss_impl" = "auto" -o "$gss_impl" = "seam"; then gss_failed=0 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for gss_unwrap in -lgss" >&5 $as_echo_n "checking for gss_unwrap in -lgss... " >&6; } if ${ac_cv_lib_gss_gss_unwrap+:} false; then : $as_echo_n "(cached) " >&6 else ac_check_lib_save_LIBS=$LIBS LIBS="-lgss -lgss $LIBS" cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ /* Override any GCC internal prototype to avoid an error. Use char because int might match the return type of a GCC builtin and then its argument prototype would still apply. */ #ifdef __cplusplus extern "C" #endif char gss_unwrap (); int main () { return gss_unwrap (); ; return 0; } _ACEOF if ac_fn_c_try_link "$LINENO"; then : ac_cv_lib_gss_gss_unwrap=yes else ac_cv_lib_gss_gss_unwrap=no fi rm -f core conftest.err conftest.$ac_objext \ conftest$ac_exeext conftest.$ac_ext LIBS=$ac_check_lib_save_LIBS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_gss_gss_unwrap" >&5 $as_echo "$ac_cv_lib_gss_gss_unwrap" >&6; } if test "x$ac_cv_lib_gss_gss_unwrap" = xyes; then : gss_impl="seam" else gss_failed=1 fi if test "$gss_impl" != "auto" -a "$gss_failed" = "1"; then gss_impl="failed" fi fi if test "$gss_impl" = "mit"; then GSSAPIBASE_LIBS="$GSSAPIBASE_LIBS -lgssapi_krb5 -lkrb5 -lk5crypto -lcom_err ${K5SUP}" GSSAPIBASE_STATIC_LIBS="$GSSAPIBASE_LIBS $gssapi_dir/libgssapi_krb5.a $gssapi_dir/libkrb5.a $gssapi_dir/libk5crypto.a $gssapi_dir/libcom_err.a ${K5SUPSTATIC}" elif test "$gss_impl" = "heimdal"; then CPPFLAGS="$CPPFLAGS -DKRB5_HEIMDAL" GSSAPIBASE_LIBS="$GSSAPIBASE_LIBS -lgssapi -lkrb5 -lasn1 -lroken ${LIB_CRYPT} ${LIB_DES} -lcom_err" GSSAPIBASE_STATIC_LIBS="$GSSAPIBASE_STATIC_LIBS $gssapi_dir/libgssapi.a $gssapi_dir/libkrb5.a $gssapi_dir/libasn1.a $gssapi_dir/libroken.a $gssapi_dir/libcom_err.a ${LIB_CRYPT}" elif test "$gss_impl" = "cybersafe03"; then # Version of CyberSafe with two libraries CPPFLAGS="$CPPFLAGS -D$platform -I${gssapi}/appsec-sdk/include" GSSAPIBASE_LIBS="$GSSAPIBASE_LIBS -lgss -lcstbk5" # there is no static libgss for CyberSafe GSSAPIBASE_STATIC_LIBS=none elif test "$gss_impl" = "cybersafe"; then CPPFLAGS="$CPPFLAGS -D$platform -I${gssapi}/appsec-sdk/include" GSSAPIBASE_LIBS="$GSSAPIBASE_LIBS -lgss" # there is no static libgss for CyberSafe GSSAPIBASE_STATIC_LIBS=none elif test "$gss_impl" = "seam"; then GSSAPIBASE_LIBS=-lgss # there is no static libgss on Solaris 8 and up GSSAPIBASE_STATIC_LIBS=none elif test "$gss_impl" = "failed"; then gssapi="no" GSSAPIBASE_LIBS= GSSAPIBASE_STATIC_LIBS= { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: Disabling GSSAPI - specified library not found" >&5 $as_echo "$as_me: WARNING: Disabling GSSAPI - specified library not found" >&2;} else gssapi="no" GSSAPIBASE_LIBS= GSSAPIBASE_STATIC_LIBS= { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: Disabling GSSAPI - no library" >&5 $as_echo "$as_me: WARNING: Disabling GSSAPI - no library" >&2;} fi fi # # Cybersafe defines both GSS_C_NT_HOSTBASED_SERVICE and GSS_C_NT_USER_NAME # in gssapi\rfckrb5.h # if test "$gssapi" != "no"; then if test "$gss_impl" = "cybersafe" -o "$gss_impl" = "cybersafe03"; then cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ #include #ifdef GSS_C_NT_HOSTBASED_SERVICE hostbased_service_gss_nt_yes #endif _ACEOF if (eval "$ac_cpp conftest.$ac_ext") 2>&5 | $EGREP "hostbased_service_gss_nt_yes" >/dev/null 2>&1; then : $as_echo "#define HAVE_GSS_C_NT_HOSTBASED_SERVICE /**/" >>confdefs.h else { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: Cybersafe define not found" >&5 $as_echo "$as_me: WARNING: Cybersafe define not found" >&2;} fi rm -f conftest* elif test "$ac_cv_header_gssapi_h" = "yes"; then cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ #include _ACEOF if (eval "$ac_cpp conftest.$ac_ext") 2>&5 | $EGREP "GSS_C_NT_HOSTBASED_SERVICE" >/dev/null 2>&1; then : $as_echo "#define HAVE_GSS_C_NT_HOSTBASED_SERVICE /**/" >>confdefs.h fi rm -f conftest* elif test "$ac_cv_header_gssapi_gssapi_h"; then cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ #include _ACEOF if (eval "$ac_cpp conftest.$ac_ext") 2>&5 | $EGREP "GSS_C_NT_HOSTBASED_SERVICE" >/dev/null 2>&1; then : $as_echo "#define HAVE_GSS_C_NT_HOSTBASED_SERVICE /**/" >>confdefs.h fi rm -f conftest* fi if test "$gss_impl" = "cybersafe" -o "$gss_impl" = "cybersafe03"; then cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ #include #ifdef GSS_C_NT_USER_NAME user_name_yes_gss_nt #endif _ACEOF if (eval "$ac_cpp conftest.$ac_ext") 2>&5 | $EGREP "user_name_yes_gss_nt" >/dev/null 2>&1; then : $as_echo "#define HAVE_GSS_C_NT_USER_NAME /**/" >>confdefs.h else { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: Cybersafe define not found" >&5 $as_echo "$as_me: WARNING: Cybersafe define not found" >&2;} fi rm -f conftest* elif test "$ac_cv_header_gssapi_h" = "yes"; then cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ #include _ACEOF if (eval "$ac_cpp conftest.$ac_ext") 2>&5 | $EGREP "GSS_C_NT_USER_NAME" >/dev/null 2>&1; then : $as_echo "#define HAVE_GSS_C_NT_USER_NAME /**/" >>confdefs.h fi rm -f conftest* cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ #include _ACEOF if (eval "$ac_cpp conftest.$ac_ext") 2>&5 | $EGREP "gss_inquire_attrs_for_mech" >/dev/null 2>&1; then : rfc5587=yes fi rm -f conftest* cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ #include _ACEOF if (eval "$ac_cpp conftest.$ac_ext") 2>&5 | $EGREP "gss_inquire_mech_for_saslname" >/dev/null 2>&1; then : rfc5801=yes fi rm -f conftest* elif test "$ac_cv_header_gssapi_gssapi_h"; then cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ #include _ACEOF if (eval "$ac_cpp conftest.$ac_ext") 2>&5 | $EGREP "GSS_C_NT_USER_NAME" >/dev/null 2>&1; then : $as_echo "#define HAVE_GSS_C_NT_USER_NAME /**/" >>confdefs.h fi rm -f conftest* cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ #include _ACEOF if (eval "$ac_cpp conftest.$ac_ext") 2>&5 | $EGREP "gss_inquire_attrs_for_mech" >/dev/null 2>&1; then : rfc5587=yes fi rm -f conftest* cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ #include _ACEOF if (eval "$ac_cpp conftest.$ac_ext") 2>&5 | $EGREP "gss_inquire_mech_for_saslname" >/dev/null 2>&1; then : rfc5801=yes fi rm -f conftest* fi fi { $as_echo "$as_me:${as_lineno-$LINENO}: checking GSSAPI" >&5 $as_echo_n "checking GSSAPI... " >&6; } if test "$gssapi" != no; then { $as_echo "$as_me:${as_lineno-$LINENO}: result: with implementation ${gss_impl}" >&5 $as_echo "with implementation ${gss_impl}" >&6; } { $as_echo "$as_me:${as_lineno-$LINENO}: checking for res_search in -lresolv" >&5 $as_echo_n "checking for res_search in -lresolv... " >&6; } if ${ac_cv_lib_resolv_res_search+:} false; then : $as_echo_n "(cached) " >&6 else ac_check_lib_save_LIBS=$LIBS LIBS="-lresolv $LIBS" cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ /* Override any GCC internal prototype to avoid an error. Use char because int might match the return type of a GCC builtin and then its argument prototype would still apply. */ #ifdef __cplusplus extern "C" #endif char res_search (); int main () { return res_search (); ; return 0; } _ACEOF if ac_fn_c_try_link "$LINENO"; then : ac_cv_lib_resolv_res_search=yes else ac_cv_lib_resolv_res_search=no fi rm -f core conftest.err conftest.$ac_objext \ conftest$ac_exeext conftest.$ac_ext LIBS=$ac_check_lib_save_LIBS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_resolv_res_search" >&5 $as_echo "$ac_cv_lib_resolv_res_search" >&6; } if test "x$ac_cv_lib_resolv_res_search" = xyes; then : GSSAPIBASE_LIBS="$GSSAPIBASE_LIBS -lresolv" fi SASL_MECHS="$SASL_MECHS libgssapiv2.la" SASL_STATIC_OBJS="$SASL_STATIC_OBJS gssapi.o" SASL_STATIC_SRCS="$SASL_STATIC_SRCS \$(top_srcdir)/plugins/gssapi.c" if test "$rfc5587" = "yes" -a "$rfc5801" = "yes"; then SASL_MECHS="$SASL_MECHS libgs2.la" SASL_STATIC_OBJS="$SASL_STATIC_OBJS gs2.o" SASL_STATIC_SRCS="$SASL_STATIC_SRCS \$(top_srcdir)/plugins/gs2.c" fi cmu_save_LIBS="$LIBS" LIBS="$LIBS $GSSAPIBASE_LIBS" for ac_func in gsskrb5_register_acceptor_identity do : ac_fn_c_check_func "$LINENO" "gsskrb5_register_acceptor_identity" "ac_cv_func_gsskrb5_register_acceptor_identity" if test "x$ac_cv_func_gsskrb5_register_acceptor_identity" = xyes; then : cat >>confdefs.h <<_ACEOF #define HAVE_GSSKRB5_REGISTER_ACCEPTOR_IDENTITY 1 _ACEOF fi done for ac_func in gss_decapsulate_token do : ac_fn_c_check_func "$LINENO" "gss_decapsulate_token" "ac_cv_func_gss_decapsulate_token" if test "x$ac_cv_func_gss_decapsulate_token" = xyes; then : cat >>confdefs.h <<_ACEOF #define HAVE_GSS_DECAPSULATE_TOKEN 1 _ACEOF fi done for ac_func in gss_encapsulate_token do : ac_fn_c_check_func "$LINENO" "gss_encapsulate_token" "ac_cv_func_gss_encapsulate_token" if test "x$ac_cv_func_gss_encapsulate_token" = xyes; then : cat >>confdefs.h <<_ACEOF #define HAVE_GSS_ENCAPSULATE_TOKEN 1 _ACEOF fi done for ac_func in gss_oid_equal do : ac_fn_c_check_func "$LINENO" "gss_oid_equal" "ac_cv_func_gss_oid_equal" if test "x$ac_cv_func_gss_oid_equal" = xyes; then : cat >>confdefs.h <<_ACEOF #define HAVE_GSS_OID_EQUAL 1 _ACEOF fi done LIBS="$cmu_save_LIBS" cmu_save_LIBS="$LIBS" LIBS="$LIBS $GSSAPIBASE_LIBS" for ac_func in gss_get_name_attribute do : ac_fn_c_check_func "$LINENO" "gss_get_name_attribute" "ac_cv_func_gss_get_name_attribute" if test "x$ac_cv_func_gss_get_name_attribute" = xyes; then : cat >>confdefs.h <<_ACEOF #define HAVE_GSS_GET_NAME_ATTRIBUTE 1 _ACEOF fi done LIBS="$cmu_save_LIBS" cmu_save_LIBS="$LIBS" LIBS="$LIBS $GSSAPIBASE_LIBS" { $as_echo "$as_me:${as_lineno-$LINENO}: checking for SPNEGO support in GSSAPI libraries" >&5 $as_echo_n "checking for SPNEGO support in GSSAPI libraries... " >&6; } if test "$cross_compiling" = yes; then : { { $as_echo "$as_me:${as_lineno-$LINENO}: error: in \`$ac_pwd':" >&5 $as_echo "$as_me: error: in \`$ac_pwd':" >&2;} as_fn_error $? "cannot run test program while cross compiling See \`config.log' for more details" "$LINENO" 5; } else cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ #ifdef HAVE_GSSAPI_H #include #else #include #endif int main(void) { gss_OID_desc spnego_oid = { 6, (void *) "\x2b\x06\x01\x05\x05\x02" }; gss_OID_set mech_set; OM_uint32 min_stat; int have_spnego = 0; if (gss_indicate_mechs(&min_stat, &mech_set) == GSS_S_COMPLETE) { gss_test_oid_set_member(&min_stat, &spnego_oid, mech_set, &have_spnego); gss_release_oid_set(&min_stat, &mech_set); } return (!have_spnego); // 0 = success, 1 = failure } _ACEOF if ac_fn_c_try_run "$LINENO"; then : $as_echo "#define HAVE_GSS_SPNEGO /**/" >>confdefs.h { $as_echo "$as_me:${as_lineno-$LINENO}: result: yes" >&5 $as_echo "yes" >&6; } else { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 $as_echo "no" >&6; } fi rm -f core *.core core.conftest.* gmon.out bb.out conftest$ac_exeext \ conftest.$ac_objext conftest.beam conftest.$ac_ext fi LIBS="$cmu_save_LIBS" else { $as_echo "$as_me:${as_lineno-$LINENO}: result: disabled" >&5 $as_echo "disabled" >&6; } fi # Check whether --with-sasl was given. if test "${with_sasl+set}" = set; then : withval=$with_sasl; with_sasl="$withval" else with_sasl="yes" fi # Check whether --with-staticsasl was given. if test "${with_staticsasl+set}" = set; then : withval=$with_staticsasl; with_staticsasl="$withval"; if test $with_staticsasl != "no"; then using_static_sasl="static" fi else with_staticsasl="no"; using_static_sasl="no" fi SASLFLAGS="" LIB_SASL="" cmu_saved_CPPFLAGS=$CPPFLAGS cmu_saved_LDFLAGS=$LDFLAGS cmu_saved_LIBS=$LIBS if test ${with_staticsasl} != "no"; then if test -d ${with_staticsasl}; then if test -d ${with_staticsasl}/lib64 ; then ac_cv_sasl_where_lib=${with_staticsasl}/lib64 else ac_cv_sasl_where_lib=${with_staticsasl}/lib fi ac_cv_sasl_where_lib=${with_staticsasl}/lib ac_cv_sasl_where_inc=${with_staticsasl}/include SASLFLAGS="-I$ac_cv_sasl_where_inc" LIB_SASL="-L$ac_cv_sasl_where_lib" CPPFLAGS="${cmu_saved_CPPFLAGS} -I${ac_cv_sasl_where_inc}" LDFLAGS="${cmu_saved_LDFLAGS} -L${ac_cv_sasl_where_lib}" else with_staticsasl="/usr" fi ac_fn_c_check_header_mongrel "$LINENO" "sasl/sasl.h" "ac_cv_header_sasl_sasl_h" "$ac_includes_default" if test "x$ac_cv_header_sasl_sasl_h" = xyes; then : ac_fn_c_check_header_mongrel "$LINENO" "sasl/saslutil.h" "ac_cv_header_sasl_saslutil_h" "$ac_includes_default" if test "x$ac_cv_header_sasl_saslutil_h" = xyes; then : for i42 in lib64 lib; do if test -r ${with_staticsasl}/$i42/libsasl2.a; then ac_cv_found_sasl=yes { $as_echo "$as_me:${as_lineno-$LINENO}: checking for static libsasl" >&5 $as_echo_n "checking for static libsasl... " >&6; } LIB_SASL="$LIB_SASL ${with_staticsasl}/$i42/libsasl2.a" fi done ac_fn_c_check_func "$LINENO" "dlopen" "ac_cv_func_dlopen" if test "x$ac_cv_func_dlopen" = xyes; then : else { $as_echo "$as_me:${as_lineno-$LINENO}: checking for dlopen in -ldl" >&5 $as_echo_n "checking for dlopen in -ldl... " >&6; } if ${ac_cv_lib_dl_dlopen+:} false; then : $as_echo_n "(cached) " >&6 else ac_check_lib_save_LIBS=$LIBS LIBS="-ldl $LIBS" cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ /* Override any GCC internal prototype to avoid an error. Use char because int might match the return type of a GCC builtin and then its argument prototype would still apply. */ #ifdef __cplusplus extern "C" #endif char dlopen (); int main () { return dlopen (); ; return 0; } _ACEOF if ac_fn_c_try_link "$LINENO"; then : ac_cv_lib_dl_dlopen=yes else ac_cv_lib_dl_dlopen=no fi rm -f core conftest.err conftest.$ac_objext \ conftest$ac_exeext conftest.$ac_ext LIBS=$ac_check_lib_save_LIBS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_dl_dlopen" >&5 $as_echo "$ac_cv_lib_dl_dlopen" >&6; } if test "x$ac_cv_lib_dl_dlopen" = xyes; then : LIB_SASL+="$LIB_SASL -ldl" fi fi if test ! "$ac_cv_found_sasl" = "yes"; then { $as_echo "$as_me:${as_lineno-$LINENO}: checking for static libsasl" >&5 $as_echo_n "checking for static libsasl... " >&6; } as_fn_error $? "Could not find ${with_staticsasl}/lib*/libsasl2.a" "$LINENO" 5 fi fi fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: found" >&5 $as_echo "found" >&6; } if test "x$SASL_GSSAPI_LIBS_SET" = "x"; then LIB_SASL="$LIB_SASL $GSSAPIBASE_STATIC_LIBS" else SASL_GSSAPI_LIBS_SET="" cmu_saved_LIBS="$GSSAPIBASE_STATIC_LIBS $cmu_saved_LIBS" fi fi if test -d ${with_sasl}; then ac_cv_sasl_where_lib=${with_sasl}/lib ac_cv_sasl_where_inc=${with_sasl}/include DYNSASLFLAGS="-I$ac_cv_sasl_where_inc" if test "$ac_cv_sasl_where_lib" != ""; then # this is CMU ADD LIBPATH TO if test "$andrew_cv_runpath_switch" = "none" ; then LIB_DYN_SASL="-L$ac_cv_sasl_where_lib ${LIB_DYN_SASL}" else LIB_DYN_SASL="-L$ac_cv_sasl_where_lib ${LIB_DYN_SASL} $andrew_cv_runpath_switch$ac_cv_sasl_where_lib" fi fi LIB_DYN_SASL="$LIB_DYN_SASL -lsasl2" CPPFLAGS="${cmu_saved_CPPFLAGS} -I${ac_cv_sasl_where_inc}" LDFLAGS="${cmu_saved_LDFLAGS} -L${ac_cv_sasl_where_lib}" fi # be sure to check for a SASLv2 specific function ac_fn_c_check_header_mongrel "$LINENO" "sasl/sasl.h" "ac_cv_header_sasl_sasl_h" "$ac_includes_default" if test "x$ac_cv_header_sasl_sasl_h" = xyes; then : ac_fn_c_check_header_mongrel "$LINENO" "sasl/saslutil.h" "ac_cv_header_sasl_saslutil_h" "$ac_includes_default" if test "x$ac_cv_header_sasl_saslutil_h" = xyes; then : { $as_echo "$as_me:${as_lineno-$LINENO}: checking for prop_get in -lsasl2" >&5 $as_echo_n "checking for prop_get in -lsasl2... " >&6; } if ${ac_cv_lib_sasl2_prop_get+:} false; then : $as_echo_n "(cached) " >&6 else ac_check_lib_save_LIBS=$LIBS LIBS="-lsasl2 $LIBS" cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ /* Override any GCC internal prototype to avoid an error. Use char because int might match the return type of a GCC builtin and then its argument prototype would still apply. */ #ifdef __cplusplus extern "C" #endif char prop_get (); int main () { return prop_get (); ; return 0; } _ACEOF if ac_fn_c_try_link "$LINENO"; then : ac_cv_lib_sasl2_prop_get=yes else ac_cv_lib_sasl2_prop_get=no fi rm -f core conftest.err conftest.$ac_objext \ conftest$ac_exeext conftest.$ac_ext LIBS=$ac_check_lib_save_LIBS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_sasl2_prop_get" >&5 $as_echo "$ac_cv_lib_sasl2_prop_get" >&6; } if test "x$ac_cv_lib_sasl2_prop_get" = xyes; then : ac_cv_found_sasl=yes else ac_cv_found_sasl=no fi else ac_cv_found_sasl=no fi else ac_cv_found_sasl=no fi if test "$ac_cv_found_sasl" = "yes"; then if test "$ac_cv_sasl_where_lib" != ""; then # this is CMU ADD LIBPATH TO if test "$andrew_cv_runpath_switch" = "none" ; then DYNLIB_SASL="-L$ac_cv_sasl_where_lib ${DYNLIB_SASL}" else DYNLIB_SASL="-L$ac_cv_sasl_where_lib ${DYNLIB_SASL} $andrew_cv_runpath_switch$ac_cv_sasl_where_lib" fi fi DYNLIB_SASL="$DYNLIB_SASL -lsasl2" if test "$using_static_sasl" != "static"; then LIB_SASL=$DYNLIB_SASL SASLFLAGS=$DYNSASLFLAGS fi else DYNLIB_SASL="" DYNSASLFLAGS="" using_static_sasl="staticonly" fi if test "x$SASL_GSSAPI_LIBS_SET" != "x"; then SASL_GSSAPI_LIBS_SET="" cmu_saved_LIBS="$GSSAPIBASE_LIBS $cmu_saved_LIBS" fi LIBS="$cmu_saved_LIBS" LDFLAGS="$cmu_saved_LDFLAGS" CPPFLAGS="$cmu_saved_CPPFLAGS" if test "$ac_cv_found_sasl" != "yes"; then as_fn_error $? "Cannot continue without libsasl2. Get it from ftp://ftp.andrew.cmu.edu/pub/cyrus-mail/." "$LINENO" 5 fi cmu_saved_CPPFLAGS=$CPPFLAGS CPPFLAGS="$CPPFLAGS $SASLFLAGS" cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ #include #ifndef SASL_VERSION_MAJOR #error SASL_VERSION_MAJOR not defined #endif #ifndef SASL_VERSION_MINOR #error SASL_VERSION_MINOR not defined #endif #ifndef SASL_VERSION_STEP #error SASL_VERSION_STEP not defined #endif #if SASL_VERSION_MAJOR < 2 || SASL_VERSION_MINOR < 1 || SASL_VERSION_STEP < 7 #error SASL version is less than 2.1.7 #endif _ACEOF if ac_fn_c_try_cpp "$LINENO"; then : else as_fn_error $? "Incorrect SASL headers found. This package requires SASL 2.1.7 or newer." "$LINENO" 5 fi rm -f conftest.err conftest.i conftest.$ac_ext CPPFLAGS=$cmu_saved_CPPFLAGS cmu_saved_LDFLAGS=$LDFLAGS LDFLAGS="$LDFLAGS $LIB_SASL" { $as_echo "$as_me:${as_lineno-$LINENO}: checking for sasl_checkapop in -lsasl2" >&5 $as_echo_n "checking for sasl_checkapop in -lsasl2... " >&6; } if ${ac_cv_lib_sasl2_sasl_checkapop+:} false; then : $as_echo_n "(cached) " >&6 else ac_check_lib_save_LIBS=$LIBS LIBS="-lsasl2 $LIBS" cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ /* Override any GCC internal prototype to avoid an error. Use char because int might match the return type of a GCC builtin and then its argument prototype would still apply. */ #ifdef __cplusplus extern "C" #endif char sasl_checkapop (); int main () { return sasl_checkapop (); ; return 0; } _ACEOF if ac_fn_c_try_link "$LINENO"; then : ac_cv_lib_sasl2_sasl_checkapop=yes else ac_cv_lib_sasl2_sasl_checkapop=no fi rm -f core conftest.err conftest.$ac_objext \ conftest$ac_exeext conftest.$ac_ext LIBS=$ac_check_lib_save_LIBS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_sasl2_sasl_checkapop" >&5 $as_echo "$ac_cv_lib_sasl2_sasl_checkapop" >&6; } if test "x$ac_cv_lib_sasl2_sasl_checkapop" = xyes; then : $as_echo "#define HAVE_APOP /**/" >>confdefs.h else as_fn_error $? "libsasl2 without working sasl_checkapop. Cannot continue." "$LINENO" 5 fi LDFLAGS=$cmu_saved_LDFLAGS # Check whether --with-perl was given. if test "${with_perl+set}" = set; then : withval=$with_perl; with_perl="$withval" else with_perl="perl" fi if test "${with_perl}" = yes; then with_perl="perl" fi if test "${with_perl}" != no; then if test ${using_static_sasl} = "staticonly"; then { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: Cannot compile perl utilities using static libsasl" >&5 $as_echo "$as_me: WARNING: Cannot compile perl utilities using static libsasl" >&2;} with_perl="no" else for ac_prog in ${with_perl} perl do # Extract the first word of "$ac_prog", so it can be a program name with args. set dummy $ac_prog; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } if ${ac_cv_prog_PERL+:} false; then : $as_echo_n "(cached) " >&6 else if test -n "$PERL"; then ac_cv_prog_PERL="$PERL" # Let the user override the test. else as_save_IFS=$IFS; IFS=$PATH_SEPARATOR for as_dir in $PATH do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_prog_PERL="$ac_prog" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 fi done done IFS=$as_save_IFS fi fi PERL=$ac_cv_prog_PERL if test -n "$PERL"; then { $as_echo "$as_me:${as_lineno-$LINENO}: result: $PERL" >&5 $as_echo "$PERL" >&6; } else { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 $as_echo "no" >&6; } fi test -n "$PERL" && break done test -n "$PERL" || PERL="with_perl=notfound" fi fi if test "$with_perl" != "no" -a "$with_perl" != "notfound"; then PERL_TRUE= PERL_FALSE='#' else PERL_TRUE='#' PERL_FALSE= fi srctoolsdir=`cd ${srcdir};pwd`/tools if test "$with_perl" = "notfound"; then { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: Perl not found: Administrative tools will not be available" >&5 $as_echo "$as_me: WARNING: Perl not found: Administrative tools will not be available" >&2;} elif test "${with_perl}" != "no"; then PERL="${with_perl}" case "${target_os}" in linux*|netbsd*|freebsd*|dragonfly*) { $as_echo "$as_me:${as_lineno-$LINENO}: checking for perl cccdlflags needed on \"${target_os}\"" >&5 $as_echo_n "checking for perl cccdlflags needed on \"${target_os}\"... " >&6; } eval `${PERL} -V:cccdlflags` PERL_CCCDLFLAGS="$cccdlflags" { $as_echo "$as_me:${as_lineno-$LINENO}: result: $PERL_CCCDLFLAGS" >&5 $as_echo "$PERL_CCCDLFLAGS" >&6; } ;; *) { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: skipping check for perl cccdlflags on \"${target_os}\"" >&5 $as_echo "$as_me: WARNING: skipping check for perl cccdlflags on \"${target_os}\"" >&2;} esac PERL_PREINSTALL="${PERL} ${srctoolsdir}/fixsearchpath.pl ${cyrus_prefix} ${bindir}" fi # Check whether --with-libwrap was given. if test "${with_libwrap+set}" = set; then : withval=$with_libwrap; with_libwrap=$withval else with_libwrap=yes fi if test "$with_libwrap" != no; then if test -d "$with_libwrap"; then CPPFLAGS="$CPPFLAGS -I${with_libwrap}/include" LDFLAGS="$LDFLAGS -L${with_libwrap}/$CMU_LIB_SUBDIR" fi cmu_save_LIBS="$LIBS" { $as_echo "$as_me:${as_lineno-$LINENO}: checking for request_init in -lwrap" >&5 $as_echo_n "checking for request_init in -lwrap... " >&6; } if ${ac_cv_lib_wrap_request_init+:} false; then : $as_echo_n "(cached) " >&6 else ac_check_lib_save_LIBS=$LIBS LIBS="-lwrap ${LIB_SOCKET} $LIBS" cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ /* Override any GCC internal prototype to avoid an error. Use char because int might match the return type of a GCC builtin and then its argument prototype would still apply. */ #ifdef __cplusplus extern "C" #endif char request_init (); int main () { return request_init (); ; return 0; } _ACEOF if ac_fn_c_try_link "$LINENO"; then : ac_cv_lib_wrap_request_init=yes else ac_cv_lib_wrap_request_init=no fi rm -f core conftest.err conftest.$ac_objext \ conftest$ac_exeext conftest.$ac_ext LIBS=$ac_check_lib_save_LIBS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_wrap_request_init" >&5 $as_echo "$ac_cv_lib_wrap_request_init" >&6; } if test "x$ac_cv_lib_wrap_request_init" = xyes; then : ac_fn_c_check_header_mongrel "$LINENO" "tcpd.h" "ac_cv_header_tcpd_h" "$ac_includes_default" if test "x$ac_cv_header_tcpd_h" = xyes; then : else with_libwrap=no fi else with_libwrap=no fi LIBS="$cmu_save_LIBS" fi { $as_echo "$as_me:${as_lineno-$LINENO}: checking libwrap support" >&5 $as_echo_n "checking libwrap support... " >&6; } { $as_echo "$as_me:${as_lineno-$LINENO}: result: $with_libwrap" >&5 $as_echo "$with_libwrap" >&6; } LIB_WRAP="" if test "$with_libwrap" != no; then $as_echo "#define HAVE_LIBWRAP /**/" >>confdefs.h LIB_WRAP="-lwrap" { $as_echo "$as_me:${as_lineno-$LINENO}: checking for yp_get_default_domain in -lnsl" >&5 $as_echo_n "checking for yp_get_default_domain in -lnsl... " >&6; } if ${ac_cv_lib_nsl_yp_get_default_domain+:} false; then : $as_echo_n "(cached) " >&6 else ac_check_lib_save_LIBS=$LIBS LIBS="-lnsl $LIBS" cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ /* Override any GCC internal prototype to avoid an error. Use char because int might match the return type of a GCC builtin and then its argument prototype would still apply. */ #ifdef __cplusplus extern "C" #endif char yp_get_default_domain (); int main () { return yp_get_default_domain (); ; return 0; } _ACEOF if ac_fn_c_try_link "$LINENO"; then : ac_cv_lib_nsl_yp_get_default_domain=yes else ac_cv_lib_nsl_yp_get_default_domain=no fi rm -f core conftest.err conftest.$ac_objext \ conftest$ac_exeext conftest.$ac_ext LIBS=$ac_check_lib_save_LIBS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_nsl_yp_get_default_domain" >&5 $as_echo "$ac_cv_lib_nsl_yp_get_default_domain" >&6; } if test "x$ac_cv_lib_nsl_yp_get_default_domain" = xyes; then : LIB_WRAP="${LIB_WRAP} -lnsl" fi fi # Check whether --with-snmp was given. if test "${with_snmp+set}" = set; then : withval=$with_snmp; with_snmp=$withval else with_snmp=yes fi # Check whether --with-ucdsnmp was given. if test "${with_ucdsnmp+set}" = set; then : withval=$with_ucdsnmp; with_snmp=$withval fi if test "$with_snmp" != "no"; then if test "$with_snmp" = "yes"; then # Extract the first word of "net-snmp-config", so it can be a program name with args. set dummy net-snmp-config; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } if ${ac_cv_path_SNMP_CONFIG+:} false; then : $as_echo_n "(cached) " >&6 else case $SNMP_CONFIG in [\\/]* | ?:[\\/]*) ac_cv_path_SNMP_CONFIG="$SNMP_CONFIG" # Let the user override the test with a path. ;; *) as_save_IFS=$IFS; IFS=$PATH_SEPARATOR as_dummy="/usr/local/bin:$PATH" for as_dir in $as_dummy do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_path_SNMP_CONFIG="$as_dir/$ac_word$ac_exec_ext" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 fi done done IFS=$as_save_IFS ;; esac fi SNMP_CONFIG=$ac_cv_path_SNMP_CONFIG if test -n "$SNMP_CONFIG"; then { $as_echo "$as_me:${as_lineno-$LINENO}: result: $SNMP_CONFIG" >&5 $as_echo "$SNMP_CONFIG" >&6; } else { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 $as_echo "no" >&6; } fi else SNMP_CONFIG="$with_snmp/bin/net-snmp-config" fi if test -x "$SNMP_CONFIG"; then { $as_echo "$as_me:${as_lineno-$LINENO}: checking NET SNMP libraries" >&5 $as_echo_n "checking NET SNMP libraries... " >&6; } SNMP_LIBS=`$SNMP_CONFIG --agent-libs` SNMP_PREFIX=`$SNMP_CONFIG --prefix` if test -n "$SNMP_LIBS" && test -n "$SNMP_PREFIX"; then CPPFLAGS="$CPPFLAGS -I${SNMP_PREFIX}/include" LIB_UCDSNMP=$SNMP_LIBS $as_echo "#define HAVE_NETSNMP 1" >>confdefs.h { $as_echo "$as_me:${as_lineno-$LINENO}: result: yes" >&5 $as_echo "yes" >&6; } for ac_header in net-snmp/agent/agent_module_config.h do : ac_fn_c_check_header_mongrel "$LINENO" "net-snmp/agent/agent_module_config.h" "ac_cv_header_net_snmp_agent_agent_module_config_h" "$ac_includes_default" if test "x$ac_cv_header_net_snmp_agent_agent_module_config_h" = xyes; then : cat >>confdefs.h <<_ACEOF #define HAVE_NET_SNMP_AGENT_AGENT_MODULE_CONFIG_H 1 _ACEOF fi done else { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 $as_echo "no" >&6; } { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: Could not find the required paths. Please check your net-snmp installation." >&5 $as_echo "$as_me: WARNING: Could not find the required paths. Please check your net-snmp installation." >&2;} fi else if test "$with_snmp" != no; then if test -d "$with_snmp"; then CPPFLAGS="$CPPFLAGS -I${with_snmp}/include" LDFLAGS="$LDFLAGS -L${with_snmp}/$CMU_LIB_SUBDIR" fi cmu_save_LIBS="$LIBS" { $as_echo "$as_me:${as_lineno-$LINENO}: checking for sprint_objid in -lsnmp" >&5 $as_echo_n "checking for sprint_objid in -lsnmp... " >&6; } if ${ac_cv_lib_snmp_sprint_objid+:} false; then : $as_echo_n "(cached) " >&6 else ac_check_lib_save_LIBS=$LIBS LIBS="-lsnmp ${LIB_SOCKET} $LIBS" cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ /* Override any GCC internal prototype to avoid an error. Use char because int might match the return type of a GCC builtin and then its argument prototype would still apply. */ #ifdef __cplusplus extern "C" #endif char sprint_objid (); int main () { return sprint_objid (); ; return 0; } _ACEOF if ac_fn_c_try_link "$LINENO"; then : ac_cv_lib_snmp_sprint_objid=yes else ac_cv_lib_snmp_sprint_objid=no fi rm -f core conftest.err conftest.$ac_objext \ conftest$ac_exeext conftest.$ac_ext LIBS=$ac_check_lib_save_LIBS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_snmp_sprint_objid" >&5 $as_echo "$ac_cv_lib_snmp_sprint_objid" >&6; } if test "x$ac_cv_lib_snmp_sprint_objid" = xyes; then : ac_fn_c_check_header_mongrel "$LINENO" "ucd-snmp/version.h" "ac_cv_header_ucd_snmp_version_h" "$ac_includes_default" if test "x$ac_cv_header_ucd_snmp_version_h" = xyes; then : else with_snmp=no fi else with_snmp=no fi LIBS="$cmu_save_LIBS" fi { $as_echo "$as_me:${as_lineno-$LINENO}: checking UCD SNMP libraries" >&5 $as_echo_n "checking UCD SNMP libraries... " >&6; } { $as_echo "$as_me:${as_lineno-$LINENO}: result: $with_snmp" >&5 $as_echo "$with_snmp" >&6; } LIB_UCDSNMP="" if test "$with_snmp" != no; then $as_echo "#define HAVE_UCDSNMP 1" >>confdefs.h LIB_UCDSNMP="-lucdagent -lucdmibs -lsnmp" { $as_echo "$as_me:${as_lineno-$LINENO}: checking for rpmdbOpen in -lrpm" >&5 $as_echo_n "checking for rpmdbOpen in -lrpm... " >&6; } if ${ac_cv_lib_rpm_rpmdbOpen+:} false; then : $as_echo_n "(cached) " >&6 else ac_check_lib_save_LIBS=$LIBS LIBS="-lrpm -lpopt $LIBS" cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ /* Override any GCC internal prototype to avoid an error. Use char because int might match the return type of a GCC builtin and then its argument prototype would still apply. */ #ifdef __cplusplus extern "C" #endif char rpmdbOpen (); int main () { return rpmdbOpen (); ; return 0; } _ACEOF if ac_fn_c_try_link "$LINENO"; then : ac_cv_lib_rpm_rpmdbOpen=yes else ac_cv_lib_rpm_rpmdbOpen=no fi rm -f core conftest.err conftest.$ac_objext \ conftest$ac_exeext conftest.$ac_ext LIBS=$ac_check_lib_save_LIBS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_rpm_rpmdbOpen" >&5 $as_echo "$ac_cv_lib_rpm_rpmdbOpen" >&6; } if test "x$ac_cv_lib_rpm_rpmdbOpen" = xyes; then : LIB_UCDSNMP="${LIB_UCDSNMP} -lrpm -lpopt" fi fi fi fi # Figure out what directories we're linking against. # Lots of fun for the whole family. # This probably chokes on anything with spaces in it. # All we want is the list of -L directories, and -L may or may not be # followed by a space. isdir=no libpath="" #echo "debug ldflags: << ${ldflags} >>" #echo "debug default_ldflags: << ${default_ldflags} >>" for flag in ${ldflags} ${default_ldflags}; do case $flag in -L) # it's a split -L option, we'll mark the next option as a dir. isdir=yes ;; -L*) # attached -L option: split off the directory larg=`echo $flag | sed -e 's:-L\(..*\):\1:'` libpath="${libpath} ${larg}" ;; *) if test $isdir = yes ; then libpath="${libpath} ${flag}" isdir=no fi esac done # Check whether --enable-unit-tests was given. if test "${enable_unit_tests+set}" = set; then : enableval=$enable_unit_tests; fi if test "$enable_unit_tests" = "yes" ; then { $as_echo "$as_me:${as_lineno-$LINENO}: checking for CU_initialize_registry in -lcunit" >&5 $as_echo_n "checking for CU_initialize_registry in -lcunit... " >&6; } if ${ac_cv_lib_cunit_CU_initialize_registry+:} false; then : $as_echo_n "(cached) " >&6 else ac_check_lib_save_LIBS=$LIBS LIBS="-lcunit $LIBS" cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ /* Override any GCC internal prototype to avoid an error. Use char because int might match the return type of a GCC builtin and then its argument prototype would still apply. */ #ifdef __cplusplus extern "C" #endif char CU_initialize_registry (); int main () { return CU_initialize_registry (); ; return 0; } _ACEOF if ac_fn_c_try_link "$LINENO"; then : ac_cv_lib_cunit_CU_initialize_registry=yes else ac_cv_lib_cunit_CU_initialize_registry=no fi rm -f core conftest.err conftest.$ac_objext \ conftest$ac_exeext conftest.$ac_ext LIBS=$ac_check_lib_save_LIBS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_cunit_CU_initialize_registry" >&5 $as_echo "$ac_cv_lib_cunit_CU_initialize_registry" >&6; } if test "x$ac_cv_lib_cunit_CU_initialize_registry" = xyes; then : found_lib=yes else found_lib=no fi ac_fn_c_check_header_mongrel "$LINENO" "CUnit/CUnit.h" "ac_cv_header_CUnit_CUnit_h" "$ac_includes_default" if test "x$ac_cv_header_CUnit_CUnit_h" = xyes; then : found_hdr=yes else found_hdr=no fi if test "$found_lib$found_hdr" != "yesyes" ; then { $as_echo "$as_me:${as_lineno-$LINENO}: Disabling unit tests because the required CUnit library is not installed" >&5 $as_echo "$as_me: Disabling unit tests because the required CUnit library is not installed" >&6;} enable_unit_tests=no fi ac_fn_c_check_header_mongrel "$LINENO" "CUnit/Basic.h" "ac_cv_header_CUnit_Basic_h" "$ac_includes_default" if test "x$ac_cv_header_CUnit_Basic_h" = xyes; then : # ac_fn_c_check_type LINENO TYPE VAR INCLUDES # ------------------------------------------- # Tests whether TYPE exists after having included INCLUDES, setting cache # variable VAR accordingly. ac_fn_c_check_type () { as_lineno=${as_lineno-"$1"} as_lineno_stack=as_lineno_stack=$as_lineno_stack { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $2" >&5 $as_echo_n "checking for $2... " >&6; } if eval \${$3+:} false; then : $as_echo_n "(cached) " >&6 else eval "$3=no" cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ $4 int main () { if (sizeof ($2)) return 0; ; return 0; } _ACEOF if ac_fn_c_try_compile "$LINENO"; then : cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ $4 int main () { if (sizeof (($2))) return 0; ; return 0; } _ACEOF if ac_fn_c_try_compile "$LINENO"; then : else eval "$3=yes" fi rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext fi rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext fi eval ac_res=\$$3 { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_res" >&5 $as_echo "$ac_res" >&6; } eval $as_lineno_stack; ${as_lineno_stack:+:} unset as_lineno } # ac_fn_c_check_type ac_fn_c_check_type "$LINENO" "CU_SetUpFunc" "ac_cv_type_CU_SetUpFunc" "#include " if test "x$ac_cv_type_CU_SetUpFunc" = xyes; then : $as_echo "#define HAVE_CU_SETUPFUNC /**/" >>confdefs.h fi fi fi if test "$enable_unit_tests" = "yes" ; then for ac_header in valgrind/valgrind.h do : ac_fn_c_check_header_mongrel "$LINENO" "valgrind/valgrind.h" "ac_cv_header_valgrind_valgrind_h" "$ac_includes_default" if test "x$ac_cv_header_valgrind_valgrind_h" = xyes; then : cat >>confdefs.h <<_ACEOF #define HAVE_VALGRIND_VALGRIND_H 1 _ACEOF fi done USE_MAINTAINER_MODE=yes fi if test "$enable_unit_tests" = "yes"; then CUNIT_TRUE= CUNIT_FALSE='#' else CUNIT_TRUE='#' CUNIT_FALSE= fi ac_config_files="$ac_config_files libcyrus_min.pc libcyrus.pc libcyrus_sieve.pc Makefile" if test "$with_perl" != "no" -a "$with_perl" != "notfound" ; then ac_config_files="$ac_config_files perl/annotator/Makefile.PL" ac_config_commands="$ac_config_commands perl/annotator/Makefile" ac_config_files="$ac_config_files perl/imap/Makefile.PL" ac_config_commands="$ac_config_commands perl/imap/Makefile" ac_config_files="$ac_config_files perl/sieve/managesieve/Makefile.PL" ac_config_commands="$ac_config_commands perl/sieve/managesieve/Makefile" fi cat >confcache <<\_ACEOF # This file is a shell script that caches the results of configure # tests run on this system so they can be shared between configure # scripts and configure runs, see configure's option --config-cache. # It is not useful on other systems. If it contains results you don't # want to keep, you may remove or edit it. # # config.status only pays attention to the cache file if you give it # the --recheck option to rerun configure. # # `ac_cv_env_foo' variables (set or unset) will be overridden when # loading this file, other *unset* `ac_cv_foo' will be assigned the # following values. _ACEOF # The following way of writing the cache mishandles newlines in values, # but we know of no workaround that is simple, portable, and efficient. # So, we kill variables containing newlines. # Ultrix sh set writes to stderr and can't be redirected directly, # and sets the high bit in the cache file unless we assign to the vars. ( for ac_var in `(set) 2>&1 | sed -n 's/^\([a-zA-Z_][a-zA-Z0-9_]*\)=.*/\1/p'`; do eval ac_val=\$$ac_var case $ac_val in #( *${as_nl}*) case $ac_var in #( *_cv_*) { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: cache variable $ac_var contains a newline" >&5 $as_echo "$as_me: WARNING: cache variable $ac_var contains a newline" >&2;} ;; esac case $ac_var in #( _ | IFS | as_nl) ;; #( BASH_ARGV | BASH_SOURCE) eval $ac_var= ;; #( *) { eval $ac_var=; unset $ac_var;} ;; esac ;; esac done (set) 2>&1 | case $as_nl`(ac_space=' '; set) 2>&1` in #( *${as_nl}ac_space=\ *) # `set' does not quote correctly, so add quotes: double-quote # substitution turns \\\\ into \\, and sed turns \\ into \. sed -n \ "s/'/'\\\\''/g; s/^\\([_$as_cr_alnum]*_cv_[_$as_cr_alnum]*\\)=\\(.*\\)/\\1='\\2'/p" ;; #( *) # `set' quotes correctly as required by POSIX, so do not add quotes. sed -n "/^[_$as_cr_alnum]*_cv_[_$as_cr_alnum]*=/p" ;; esac | sort ) | sed ' /^ac_cv_env_/b end t clear :clear s/^\([^=]*\)=\(.*[{}].*\)$/test "${\1+set}" = set || &/ t end s/^\([^=]*\)=\(.*\)$/\1=${\1=\2}/ :end' >>confcache if diff "$cache_file" confcache >/dev/null 2>&1; then :; else if test -w "$cache_file"; then if test "x$cache_file" != "x/dev/null"; then { $as_echo "$as_me:${as_lineno-$LINENO}: updating cache $cache_file" >&5 $as_echo "$as_me: updating cache $cache_file" >&6;} if test ! -f "$cache_file" || test -h "$cache_file"; then cat confcache >"$cache_file" else case $cache_file in #( */* | ?:*) mv -f confcache "$cache_file"$$ && mv -f "$cache_file"$$ "$cache_file" ;; #( *) mv -f confcache "$cache_file" ;; esac fi fi else { $as_echo "$as_me:${as_lineno-$LINENO}: not updating unwritable cache $cache_file" >&5 $as_echo "$as_me: not updating unwritable cache $cache_file" >&6;} fi fi rm -f confcache test "x$prefix" = xNONE && prefix=$ac_default_prefix # Let make expand exec_prefix. test "x$exec_prefix" = xNONE && exec_prefix='${prefix}' DEFS=-DHAVE_CONFIG_H ac_libobjs= ac_ltlibobjs= U= for ac_i in : $LIBOBJS; do test "x$ac_i" = x: && continue # 1. Remove the extension, and $U if already installed. ac_script='s/\$U\././;s/\.o$//;s/\.obj$//' ac_i=`$as_echo "$ac_i" | sed "$ac_script"` # 2. Prepend LIBOBJDIR. When used with automake>=1.10 LIBOBJDIR # will be set to the directory where LIBOBJS objects are built. as_fn_append ac_libobjs " \${LIBOBJDIR}$ac_i\$U.$ac_objext" as_fn_append ac_ltlibobjs " \${LIBOBJDIR}$ac_i"'$U.lo' done LIBOBJS=$ac_libobjs LTLIBOBJS=$ac_ltlibobjs { $as_echo "$as_me:${as_lineno-$LINENO}: checking that generated files are newer than configure" >&5 $as_echo_n "checking that generated files are newer than configure... " >&6; } if test -n "$am_sleep_pid"; then # Hide warnings about reused PIDs. wait $am_sleep_pid 2>/dev/null fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: done" >&5 $as_echo "done" >&6; } if test -n "$EXEEXT"; then am__EXEEXT_TRUE= am__EXEEXT_FALSE='#' else am__EXEEXT_TRUE='#' am__EXEEXT_FALSE= fi if test -z "${MAINTAINER_MODE_TRUE}" && test -z "${MAINTAINER_MODE_FALSE}"; then as_fn_error $? "conditional \"MAINTAINER_MODE\" was never defined. Usually this means the macro was only invoked conditionally." "$LINENO" 5 fi if test -z "${AMDEP_TRUE}" && test -z "${AMDEP_FALSE}"; then as_fn_error $? "conditional \"AMDEP\" was never defined. Usually this means the macro was only invoked conditionally." "$LINENO" 5 fi if test -z "${am__fastdepCC_TRUE}" && test -z "${am__fastdepCC_FALSE}"; then as_fn_error $? "conditional \"am__fastdepCC\" was never defined. Usually this means the macro was only invoked conditionally." "$LINENO" 5 fi if test -z "${IPV6_noGETADDRINFO_TRUE}" && test -z "${IPV6_noGETADDRINFO_FALSE}"; then as_fn_error $? "conditional \"IPV6_noGETADDRINFO\" was never defined. Usually this means the macro was only invoked conditionally." "$LINENO" 5 fi if test -z "${IPV6_noGETNAMEINFO_TRUE}" && test -z "${IPV6_noGETNAMEINFO_FALSE}"; then as_fn_error $? "conditional \"IPV6_noGETNAMEINFO\" was never defined. Usually this means the macro was only invoked conditionally." "$LINENO" 5 fi if test -z "${USE_BERKELEY_TRUE}" && test -z "${USE_BERKELEY_FALSE}"; then as_fn_error $? "conditional \"USE_BERKELEY\" was never defined. Usually this means the macro was only invoked conditionally." "$LINENO" 5 fi if test -z "${USE_SQL_TRUE}" && test -z "${USE_SQL_FALSE}"; then as_fn_error $? "conditional \"USE_SQL\" was never defined. Usually this means the macro was only invoked conditionally." "$LINENO" 5 fi if test -z "${SIEVE_TRUE}" && test -z "${SIEVE_FALSE}"; then as_fn_error $? "conditional \"SIEVE\" was never defined. Usually this means the macro was only invoked conditionally." "$LINENO" 5 fi if test -z "${NONBLOCK_FCNTL_TRUE}" && test -z "${NONBLOCK_FCNTL_FALSE}"; then as_fn_error $? "conditional \"NONBLOCK_FCNTL\" was never defined. Usually this means the macro was only invoked conditionally." "$LINENO" 5 fi if test -z "${GMTOFF_TM_TRUE}" && test -z "${GMTOFF_TM_FALSE}"; then as_fn_error $? "conditional \"GMTOFF_TM\" was never defined. Usually this means the macro was only invoked conditionally." "$LINENO" 5 fi if test -z "${MAP_SHARED_TRUE}" && test -z "${MAP_SHARED_FALSE}"; then as_fn_error $? "conditional \"MAP_SHARED\" was never defined. Usually this means the macro was only invoked conditionally." "$LINENO" 5 fi if test -z "${MAP_STUPIDSHARED_TRUE}" && test -z "${MAP_STUPIDSHARED_FALSE}"; then as_fn_error $? "conditional \"MAP_STUPIDSHARED\" was never defined. Usually this means the macro was only invoked conditionally." "$LINENO" 5 fi if test -z "${LOCK_FCNTL_TRUE}" && test -z "${LOCK_FCNTL_FALSE}"; then as_fn_error $? "conditional \"LOCK_FCNTL\" was never defined. Usually this means the macro was only invoked conditionally." "$LINENO" 5 fi if test -z "${USE_AFSKRB_TRUE}" && test -z "${USE_AFSKRB_FALSE}"; then as_fn_error $? "conditional \"USE_AFSKRB\" was never defined. Usually this means the macro was only invoked conditionally." "$LINENO" 5 fi if test -z "${HAVE_LDAP_TRUE}" && test -z "${HAVE_LDAP_FALSE}"; then as_fn_error $? "conditional \"HAVE_LDAP\" was never defined. Usually this means the macro was only invoked conditionally." "$LINENO" 5 fi if test -z "${PTCLIENT_TRUE}" && test -z "${PTCLIENT_FALSE}"; then as_fn_error $? "conditional \"PTCLIENT\" was never defined. Usually this means the macro was only invoked conditionally." "$LINENO" 5 fi if test -z "${HAVE_CLAMAV_TRUE}" && test -z "${HAVE_CLAMAV_FALSE}"; then as_fn_error $? "conditional \"HAVE_CLAMAV\" was never defined. Usually this means the macro was only invoked conditionally." "$LINENO" 5 fi if test -z "${SERVER_TRUE}" && test -z "${SERVER_FALSE}"; then as_fn_error $? "conditional \"SERVER\" was never defined. Usually this means the macro was only invoked conditionally." "$LINENO" 5 fi if test -z "${HAVE_SSL_TRUE}" && test -z "${HAVE_SSL_FALSE}"; then as_fn_error $? "conditional \"HAVE_SSL\" was never defined. Usually this means the macro was only invoked conditionally." "$LINENO" 5 fi if test -z "${ZEPHYR_TRUE}" && test -z "${ZEPHYR_FALSE}"; then as_fn_error $? "conditional \"ZEPHYR\" was never defined. Usually this means the macro was only invoked conditionally." "$LINENO" 5 fi if test -z "${JANSSON_TRUE}" && test -z "${JANSSON_FALSE}"; then as_fn_error $? "conditional \"JANSSON\" was never defined. Usually this means the macro was only invoked conditionally." "$LINENO" 5 fi if test -z "${AUTOCREATE_TRUE}" && test -z "${AUTOCREATE_FALSE}"; then as_fn_error $? "conditional \"AUTOCREATE\" was never defined. Usually this means the macro was only invoked conditionally." "$LINENO" 5 fi if test -z "${IDLED_TRUE}" && test -z "${IDLED_FALSE}"; then as_fn_error $? "conditional \"IDLED\" was never defined. Usually this means the macro was only invoked conditionally." "$LINENO" 5 fi if test -z "${NNTPD_TRUE}" && test -z "${NNTPD_FALSE}"; then as_fn_error $? "conditional \"NNTPD\" was never defined. Usually this means the macro was only invoked conditionally." "$LINENO" 5 fi if test -z "${MURDER_TRUE}" && test -z "${MURDER_FALSE}"; then as_fn_error $? "conditional \"MURDER\" was never defined. Usually this means the macro was only invoked conditionally." "$LINENO" 5 fi if test -z "${HTTPD_TRUE}" && test -z "${HTTPD_FALSE}"; then as_fn_error $? "conditional \"HTTPD\" was never defined. Usually this means the macro was only invoked conditionally." "$LINENO" 5 fi if test -z "${REPLICATION_TRUE}" && test -z "${REPLICATION_FALSE}"; then as_fn_error $? "conditional \"REPLICATION\" was never defined. Usually this means the macro was only invoked conditionally." "$LINENO" 5 fi if test -z "${COM_ERR_TRUE}" && test -z "${COM_ERR_FALSE}"; then as_fn_error $? "conditional \"COM_ERR\" was never defined. Usually this means the macro was only invoked conditionally." "$LINENO" 5 fi if test -z "${CMULOCAL_TRUE}" && test -z "${CMULOCAL_FALSE}"; then as_fn_error $? "conditional \"CMULOCAL\" was never defined. Usually this means the macro was only invoked conditionally." "$LINENO" 5 fi if test -z "${PERL_TRUE}" && test -z "${PERL_FALSE}"; then as_fn_error $? "conditional \"PERL\" was never defined. Usually this means the macro was only invoked conditionally." "$LINENO" 5 fi if test -z "${CUNIT_TRUE}" && test -z "${CUNIT_FALSE}"; then as_fn_error $? "conditional \"CUNIT\" was never defined. Usually this means the macro was only invoked conditionally." "$LINENO" 5 fi : "${CONFIG_STATUS=./config.status}" ac_write_fail=0 ac_clean_files_save=$ac_clean_files ac_clean_files="$ac_clean_files $CONFIG_STATUS" { $as_echo "$as_me:${as_lineno-$LINENO}: creating $CONFIG_STATUS" >&5 $as_echo "$as_me: creating $CONFIG_STATUS" >&6;} as_write_fail=0 cat >$CONFIG_STATUS <<_ASEOF || as_write_fail=1 #! $SHELL # Generated by $as_me. # Run this file to recreate the current configuration. # Compiler output produced by configure, useful for debugging # configure, is in config.log if it exists. debug=false ac_cs_recheck=false ac_cs_silent=false SHELL=\${CONFIG_SHELL-$SHELL} export SHELL _ASEOF cat >>$CONFIG_STATUS <<\_ASEOF || as_write_fail=1 ## -------------------- ## ## M4sh Initialization. ## ## -------------------- ## # Be more Bourne compatible DUALCASE=1; export DUALCASE # for MKS sh if test -n "${ZSH_VERSION+set}" && (emulate sh) >/dev/null 2>&1; then : emulate sh NULLCMD=: # Pre-4.2 versions of Zsh do word splitting on ${1+"$@"}, which # is contrary to our usage. Disable this feature. alias -g '${1+"$@"}'='"$@"' setopt NO_GLOB_SUBST else case `(set -o) 2>/dev/null` in #( *posix*) : set -o posix ;; #( *) : ;; esac fi as_nl=' ' export as_nl # Printing a long string crashes Solaris 7 /usr/bin/printf. as_echo='\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\' as_echo=$as_echo$as_echo$as_echo$as_echo$as_echo as_echo=$as_echo$as_echo$as_echo$as_echo$as_echo$as_echo # Prefer a ksh shell builtin over an external printf program on Solaris, # but without wasting forks for bash or zsh. if test -z "$BASH_VERSION$ZSH_VERSION" \ && (test "X`print -r -- $as_echo`" = "X$as_echo") 2>/dev/null; then as_echo='print -r --' as_echo_n='print -rn --' elif (test "X`printf %s $as_echo`" = "X$as_echo") 2>/dev/null; then as_echo='printf %s\n' as_echo_n='printf %s' else if test "X`(/usr/ucb/echo -n -n $as_echo) 2>/dev/null`" = "X-n $as_echo"; then as_echo_body='eval /usr/ucb/echo -n "$1$as_nl"' as_echo_n='/usr/ucb/echo -n' else as_echo_body='eval expr "X$1" : "X\\(.*\\)"' as_echo_n_body='eval arg=$1; case $arg in #( *"$as_nl"*) expr "X$arg" : "X\\(.*\\)$as_nl"; arg=`expr "X$arg" : ".*$as_nl\\(.*\\)"`;; esac; expr "X$arg" : "X\\(.*\\)" | tr -d "$as_nl" ' export as_echo_n_body as_echo_n='sh -c $as_echo_n_body as_echo' fi export as_echo_body as_echo='sh -c $as_echo_body as_echo' fi # The user is always right. if test "${PATH_SEPARATOR+set}" != set; then PATH_SEPARATOR=: (PATH='/bin;/bin'; FPATH=$PATH; sh -c :) >/dev/null 2>&1 && { (PATH='/bin:/bin'; FPATH=$PATH; sh -c :) >/dev/null 2>&1 || PATH_SEPARATOR=';' } fi # IFS # We need space, tab and new line, in precisely that order. Quoting is # there to prevent editors from complaining about space-tab. # (If _AS_PATH_WALK were called with IFS unset, it would disable word # splitting by setting IFS to empty value.) IFS=" "" $as_nl" # Find who we are. Look in the path if we contain no directory separator. as_myself= case $0 in #(( *[\\/]* ) as_myself=$0 ;; *) as_save_IFS=$IFS; IFS=$PATH_SEPARATOR for as_dir in $PATH do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. test -r "$as_dir/$0" && as_myself=$as_dir/$0 && break done IFS=$as_save_IFS ;; esac # We did not find ourselves, most probably we were run as `sh COMMAND' # in which case we are not to be found in the path. if test "x$as_myself" = x; then as_myself=$0 fi if test ! -f "$as_myself"; then $as_echo "$as_myself: error: cannot find myself; rerun with an absolute file name" >&2 exit 1 fi # Unset variables that we do not need and which cause bugs (e.g. in # pre-3.0 UWIN ksh). But do not cause bugs in bash 2.01; the "|| exit 1" # suppresses any "Segmentation fault" message there. '((' could # trigger a bug in pdksh 5.2.14. for as_var in BASH_ENV ENV MAIL MAILPATH do eval test x\${$as_var+set} = xset \ && ( (unset $as_var) || exit 1) >/dev/null 2>&1 && unset $as_var || : done PS1='$ ' PS2='> ' PS4='+ ' # NLS nuisances. LC_ALL=C export LC_ALL LANGUAGE=C export LANGUAGE # CDPATH. (unset CDPATH) >/dev/null 2>&1 && unset CDPATH # as_fn_error STATUS ERROR [LINENO LOG_FD] # ---------------------------------------- # Output "`basename $0`: error: ERROR" to stderr. If LINENO and LOG_FD are # provided, also output the error to LOG_FD, referencing LINENO. Then exit the # script with STATUS, using 1 if that was 0. as_fn_error () { as_status=$1; test $as_status -eq 0 && as_status=1 if test "$4"; then as_lineno=${as_lineno-"$3"} as_lineno_stack=as_lineno_stack=$as_lineno_stack $as_echo "$as_me:${as_lineno-$LINENO}: error: $2" >&$4 fi $as_echo "$as_me: error: $2" >&2 as_fn_exit $as_status } # as_fn_error # as_fn_set_status STATUS # ----------------------- # Set $? to STATUS, without forking. as_fn_set_status () { return $1 } # as_fn_set_status # as_fn_exit STATUS # ----------------- # Exit the shell with STATUS, even in a "trap 0" or "set -e" context. as_fn_exit () { set +e as_fn_set_status $1 exit $1 } # as_fn_exit # as_fn_unset VAR # --------------- # Portably unset VAR. as_fn_unset () { { eval $1=; unset $1;} } as_unset=as_fn_unset # as_fn_append VAR VALUE # ---------------------- # Append the text in VALUE to the end of the definition contained in VAR. Take # advantage of any shell optimizations that allow amortized linear growth over # repeated appends, instead of the typical quadratic growth present in naive # implementations. if (eval "as_var=1; as_var+=2; test x\$as_var = x12") 2>/dev/null; then : eval 'as_fn_append () { eval $1+=\$2 }' else as_fn_append () { eval $1=\$$1\$2 } fi # as_fn_append # as_fn_arith ARG... # ------------------ # Perform arithmetic evaluation on the ARGs, and store the result in the # global $as_val. Take advantage of shells that can avoid forks. The arguments # must be portable across $(()) and expr. if (eval "test \$(( 1 + 1 )) = 2") 2>/dev/null; then : eval 'as_fn_arith () { as_val=$(( $* )) }' else as_fn_arith () { as_val=`expr "$@" || test $? -eq 1` } fi # as_fn_arith if expr a : '\(a\)' >/dev/null 2>&1 && test "X`expr 00001 : '.*\(...\)'`" = X001; then as_expr=expr else as_expr=false fi if (basename -- /) >/dev/null 2>&1 && test "X`basename -- / 2>&1`" = "X/"; then as_basename=basename else as_basename=false fi if (as_dir=`dirname -- /` && test "X$as_dir" = X/) >/dev/null 2>&1; then as_dirname=dirname else as_dirname=false fi as_me=`$as_basename -- "$0" || $as_expr X/"$0" : '.*/\([^/][^/]*\)/*$' \| \ X"$0" : 'X\(//\)$' \| \ X"$0" : 'X\(/\)' \| . 2>/dev/null || $as_echo X/"$0" | sed '/^.*\/\([^/][^/]*\)\/*$/{ s//\1/ q } /^X\/\(\/\/\)$/{ s//\1/ q } /^X\/\(\/\).*/{ s//\1/ q } s/.*/./; q'` # Avoid depending upon Character Ranges. as_cr_letters='abcdefghijklmnopqrstuvwxyz' as_cr_LETTERS='ABCDEFGHIJKLMNOPQRSTUVWXYZ' as_cr_Letters=$as_cr_letters$as_cr_LETTERS as_cr_digits='0123456789' as_cr_alnum=$as_cr_Letters$as_cr_digits ECHO_C= ECHO_N= ECHO_T= case `echo -n x` in #((((( -n*) case `echo 'xy\c'` in *c*) ECHO_T=' ';; # ECHO_T is single tab character. xy) ECHO_C='\c';; *) echo `echo ksh88 bug on AIX 6.1` > /dev/null ECHO_T=' ';; esac;; *) ECHO_N='-n';; esac rm -f conf$$ conf$$.exe conf$$.file if test -d conf$$.dir; then rm -f conf$$.dir/conf$$.file else rm -f conf$$.dir mkdir conf$$.dir 2>/dev/null fi if (echo >conf$$.file) 2>/dev/null; then if ln -s conf$$.file conf$$ 2>/dev/null; then as_ln_s='ln -s' # ... but there are two gotchas: # 1) On MSYS, both `ln -s file dir' and `ln file dir' fail. # 2) DJGPP < 2.04 has no symlinks; `ln -s' creates a wrapper executable. # In both cases, we have to default to `cp -pR'. ln -s conf$$.file conf$$.dir 2>/dev/null && test ! -f conf$$.exe || as_ln_s='cp -pR' elif ln conf$$.file conf$$ 2>/dev/null; then as_ln_s=ln else as_ln_s='cp -pR' fi else as_ln_s='cp -pR' fi rm -f conf$$ conf$$.exe conf$$.dir/conf$$.file conf$$.file rmdir conf$$.dir 2>/dev/null # as_fn_mkdir_p # ------------- # Create "$as_dir" as a directory, including parents if necessary. as_fn_mkdir_p () { case $as_dir in #( -*) as_dir=./$as_dir;; esac test -d "$as_dir" || eval $as_mkdir_p || { as_dirs= while :; do case $as_dir in #( *\'*) as_qdir=`$as_echo "$as_dir" | sed "s/'/'\\\\\\\\''/g"`;; #'( *) as_qdir=$as_dir;; esac as_dirs="'$as_qdir' $as_dirs" as_dir=`$as_dirname -- "$as_dir" || $as_expr X"$as_dir" : 'X\(.*[^/]\)//*[^/][^/]*/*$' \| \ X"$as_dir" : 'X\(//\)[^/]' \| \ X"$as_dir" : 'X\(//\)$' \| \ X"$as_dir" : 'X\(/\)' \| . 2>/dev/null || $as_echo X"$as_dir" | sed '/^X\(.*[^/]\)\/\/*[^/][^/]*\/*$/{ s//\1/ q } /^X\(\/\/\)[^/].*/{ s//\1/ q } /^X\(\/\/\)$/{ s//\1/ q } /^X\(\/\).*/{ s//\1/ q } s/.*/./; q'` test -d "$as_dir" && break done test -z "$as_dirs" || eval "mkdir $as_dirs" } || test -d "$as_dir" || as_fn_error $? "cannot create directory $as_dir" } # as_fn_mkdir_p if mkdir -p . 2>/dev/null; then as_mkdir_p='mkdir -p "$as_dir"' else test -d ./-p && rmdir ./-p as_mkdir_p=false fi # as_fn_executable_p FILE # ----------------------- # Test if FILE is an executable regular file. as_fn_executable_p () { test -f "$1" && test -x "$1" } # as_fn_executable_p as_test_x='test -x' as_executable_p=as_fn_executable_p # Sed expression to map a string onto a valid CPP name. as_tr_cpp="eval sed 'y%*$as_cr_letters%P$as_cr_LETTERS%;s%[^_$as_cr_alnum]%_%g'" # Sed expression to map a string onto a valid variable name. as_tr_sh="eval sed 'y%*+%pp%;s%[^_$as_cr_alnum]%_%g'" exec 6>&1 ## ----------------------------------- ## ## Main body of $CONFIG_STATUS script. ## ## ----------------------------------- ## _ASEOF test $as_write_fail = 0 && chmod +x $CONFIG_STATUS || ac_write_fail=1 cat >>$CONFIG_STATUS <<\_ACEOF || ac_write_fail=1 # Save the log message, to keep $0 and so on meaningful, and to # report actual input values of CONFIG_FILES etc. instead of their # values after options handling. ac_log=" This file was extended by cyrus-imapd $as_me 2.5.10, which was generated by GNU Autoconf 2.69. Invocation command line was CONFIG_FILES = $CONFIG_FILES CONFIG_HEADERS = $CONFIG_HEADERS CONFIG_LINKS = $CONFIG_LINKS CONFIG_COMMANDS = $CONFIG_COMMANDS $ $0 $@ on `(hostname || uname -n) 2>/dev/null | sed 1q` " _ACEOF case $ac_config_files in *" "*) set x $ac_config_files; shift; ac_config_files=$*;; esac case $ac_config_headers in *" "*) set x $ac_config_headers; shift; ac_config_headers=$*;; esac cat >>$CONFIG_STATUS <<_ACEOF || ac_write_fail=1 # Files that config.status was made for. config_files="$ac_config_files" config_headers="$ac_config_headers" config_commands="$ac_config_commands" _ACEOF cat >>$CONFIG_STATUS <<\_ACEOF || ac_write_fail=1 ac_cs_usage="\ \`$as_me' instantiates files and other configuration actions from templates according to the current configuration. Unless the files and actions are specified as TAGs, all are instantiated by default. Usage: $0 [OPTION]... [TAG]... -h, --help print this help, then exit -V, --version print version number and configuration settings, then exit --config print configuration, then exit -q, --quiet, --silent do not print progress messages -d, --debug don't remove temporary files --recheck update $as_me by reconfiguring in the same conditions --file=FILE[:TEMPLATE] instantiate the configuration file FILE --header=FILE[:TEMPLATE] instantiate the configuration header FILE Configuration files: $config_files Configuration headers: $config_headers Configuration commands: $config_commands Report bugs to . cyrus-imapd home page: ." _ACEOF cat >>$CONFIG_STATUS <<_ACEOF || ac_write_fail=1 ac_cs_config="`$as_echo "$ac_configure_args" | sed 's/^ //; s/[\\""\`\$]/\\\\&/g'`" ac_cs_version="\\ cyrus-imapd config.status 2.5.10 configured by $0, generated by GNU Autoconf 2.69, with options \\"\$ac_cs_config\\" Copyright (C) 2012 Free Software Foundation, Inc. This config.status script is free software; the Free Software Foundation gives unlimited permission to copy, distribute and modify it." ac_pwd='$ac_pwd' srcdir='$srcdir' INSTALL='$INSTALL' MKDIR_P='$MKDIR_P' AWK='$AWK' test -n "\$AWK" || AWK=awk _ACEOF cat >>$CONFIG_STATUS <<\_ACEOF || ac_write_fail=1 # The default lists apply if the user does not specify any file. ac_need_defaults=: while test $# != 0 do case $1 in --*=?*) ac_option=`expr "X$1" : 'X\([^=]*\)='` ac_optarg=`expr "X$1" : 'X[^=]*=\(.*\)'` ac_shift=: ;; --*=) ac_option=`expr "X$1" : 'X\([^=]*\)='` ac_optarg= ac_shift=: ;; *) ac_option=$1 ac_optarg=$2 ac_shift=shift ;; esac case $ac_option in # Handling of the options. -recheck | --recheck | --rechec | --reche | --rech | --rec | --re | --r) ac_cs_recheck=: ;; --version | --versio | --versi | --vers | --ver | --ve | --v | -V ) $as_echo "$ac_cs_version"; exit ;; --config | --confi | --conf | --con | --co | --c ) $as_echo "$ac_cs_config"; exit ;; --debug | --debu | --deb | --de | --d | -d ) debug=: ;; --file | --fil | --fi | --f ) $ac_shift case $ac_optarg in *\'*) ac_optarg=`$as_echo "$ac_optarg" | sed "s/'/'\\\\\\\\''/g"` ;; '') as_fn_error $? "missing file argument" ;; esac as_fn_append CONFIG_FILES " '$ac_optarg'" ac_need_defaults=false;; --header | --heade | --head | --hea ) $ac_shift case $ac_optarg in *\'*) ac_optarg=`$as_echo "$ac_optarg" | sed "s/'/'\\\\\\\\''/g"` ;; esac as_fn_append CONFIG_HEADERS " '$ac_optarg'" ac_need_defaults=false;; --he | --h) # Conflict between --help and --header as_fn_error $? "ambiguous option: \`$1' Try \`$0 --help' for more information.";; --help | --hel | -h ) $as_echo "$ac_cs_usage"; exit ;; -q | -quiet | --quiet | --quie | --qui | --qu | --q \ | -silent | --silent | --silen | --sile | --sil | --si | --s) ac_cs_silent=: ;; # This is an error. -*) as_fn_error $? "unrecognized option: \`$1' Try \`$0 --help' for more information." ;; *) as_fn_append ac_config_targets " $1" ac_need_defaults=false ;; esac shift done ac_configure_extra_args= if $ac_cs_silent; then exec 6>/dev/null ac_configure_extra_args="$ac_configure_extra_args --silent" fi _ACEOF cat >>$CONFIG_STATUS <<_ACEOF || ac_write_fail=1 if \$ac_cs_recheck; then set X $SHELL '$0' $ac_configure_args \$ac_configure_extra_args --no-create --no-recursion shift \$as_echo "running CONFIG_SHELL=$SHELL \$*" >&6 CONFIG_SHELL='$SHELL' export CONFIG_SHELL exec "\$@" fi _ACEOF cat >>$CONFIG_STATUS <<\_ACEOF || ac_write_fail=1 exec 5>>config.log { echo sed 'h;s/./-/g;s/^.../## /;s/...$/ ##/;p;x;p;x' <<_ASBOX ## Running $as_me. ## _ASBOX $as_echo "$ac_log" } >&5 _ACEOF cat >>$CONFIG_STATUS <<_ACEOF || ac_write_fail=1 # # INIT-COMMANDS # AMDEP_TRUE="$AMDEP_TRUE" ac_aux_dir="$ac_aux_dir" # The HP-UX ksh and POSIX shell print the target directory to stdout # if CDPATH is set. (unset CDPATH) >/dev/null 2>&1 && unset CDPATH sed_quote_subst='$sed_quote_subst' double_quote_subst='$double_quote_subst' delay_variable_subst='$delay_variable_subst' macro_version='`$ECHO "$macro_version" | $SED "$delay_single_quote_subst"`' macro_revision='`$ECHO "$macro_revision" | $SED "$delay_single_quote_subst"`' enable_static='`$ECHO "$enable_static" | $SED "$delay_single_quote_subst"`' enable_shared='`$ECHO "$enable_shared" | $SED "$delay_single_quote_subst"`' pic_mode='`$ECHO "$pic_mode" | $SED "$delay_single_quote_subst"`' enable_fast_install='`$ECHO "$enable_fast_install" | $SED "$delay_single_quote_subst"`' shared_archive_member_spec='`$ECHO "$shared_archive_member_spec" | $SED "$delay_single_quote_subst"`' SHELL='`$ECHO "$SHELL" | $SED "$delay_single_quote_subst"`' ECHO='`$ECHO "$ECHO" | $SED "$delay_single_quote_subst"`' PATH_SEPARATOR='`$ECHO "$PATH_SEPARATOR" | $SED "$delay_single_quote_subst"`' host_alias='`$ECHO "$host_alias" | $SED "$delay_single_quote_subst"`' host='`$ECHO "$host" | $SED "$delay_single_quote_subst"`' host_os='`$ECHO "$host_os" | $SED "$delay_single_quote_subst"`' build_alias='`$ECHO "$build_alias" | $SED "$delay_single_quote_subst"`' build='`$ECHO "$build" | $SED "$delay_single_quote_subst"`' build_os='`$ECHO "$build_os" | $SED "$delay_single_quote_subst"`' SED='`$ECHO "$SED" | $SED "$delay_single_quote_subst"`' Xsed='`$ECHO "$Xsed" | $SED "$delay_single_quote_subst"`' GREP='`$ECHO "$GREP" | $SED "$delay_single_quote_subst"`' EGREP='`$ECHO "$EGREP" | $SED "$delay_single_quote_subst"`' FGREP='`$ECHO "$FGREP" | $SED "$delay_single_quote_subst"`' LD='`$ECHO "$LD" | $SED "$delay_single_quote_subst"`' NM='`$ECHO "$NM" | $SED "$delay_single_quote_subst"`' LN_S='`$ECHO "$LN_S" | $SED "$delay_single_quote_subst"`' max_cmd_len='`$ECHO "$max_cmd_len" | $SED "$delay_single_quote_subst"`' ac_objext='`$ECHO "$ac_objext" | $SED "$delay_single_quote_subst"`' exeext='`$ECHO "$exeext" | $SED "$delay_single_quote_subst"`' lt_unset='`$ECHO "$lt_unset" | $SED "$delay_single_quote_subst"`' lt_SP2NL='`$ECHO "$lt_SP2NL" | $SED "$delay_single_quote_subst"`' lt_NL2SP='`$ECHO "$lt_NL2SP" | $SED "$delay_single_quote_subst"`' lt_cv_to_host_file_cmd='`$ECHO "$lt_cv_to_host_file_cmd" | $SED "$delay_single_quote_subst"`' lt_cv_to_tool_file_cmd='`$ECHO "$lt_cv_to_tool_file_cmd" | $SED "$delay_single_quote_subst"`' reload_flag='`$ECHO "$reload_flag" | $SED "$delay_single_quote_subst"`' reload_cmds='`$ECHO "$reload_cmds" | $SED "$delay_single_quote_subst"`' OBJDUMP='`$ECHO "$OBJDUMP" | $SED "$delay_single_quote_subst"`' deplibs_check_method='`$ECHO "$deplibs_check_method" | $SED "$delay_single_quote_subst"`' file_magic_cmd='`$ECHO "$file_magic_cmd" | $SED "$delay_single_quote_subst"`' file_magic_glob='`$ECHO "$file_magic_glob" | $SED "$delay_single_quote_subst"`' want_nocaseglob='`$ECHO "$want_nocaseglob" | $SED "$delay_single_quote_subst"`' DLLTOOL='`$ECHO "$DLLTOOL" | $SED "$delay_single_quote_subst"`' sharedlib_from_linklib_cmd='`$ECHO "$sharedlib_from_linklib_cmd" | $SED "$delay_single_quote_subst"`' AR='`$ECHO "$AR" | $SED "$delay_single_quote_subst"`' AR_FLAGS='`$ECHO "$AR_FLAGS" | $SED "$delay_single_quote_subst"`' archiver_list_spec='`$ECHO "$archiver_list_spec" | $SED "$delay_single_quote_subst"`' STRIP='`$ECHO "$STRIP" | $SED "$delay_single_quote_subst"`' RANLIB='`$ECHO "$RANLIB" | $SED "$delay_single_quote_subst"`' old_postinstall_cmds='`$ECHO "$old_postinstall_cmds" | $SED "$delay_single_quote_subst"`' old_postuninstall_cmds='`$ECHO "$old_postuninstall_cmds" | $SED "$delay_single_quote_subst"`' old_archive_cmds='`$ECHO "$old_archive_cmds" | $SED "$delay_single_quote_subst"`' lock_old_archive_extraction='`$ECHO "$lock_old_archive_extraction" | $SED "$delay_single_quote_subst"`' CC='`$ECHO "$CC" | $SED "$delay_single_quote_subst"`' CFLAGS='`$ECHO "$CFLAGS" | $SED "$delay_single_quote_subst"`' compiler='`$ECHO "$compiler" | $SED "$delay_single_quote_subst"`' GCC='`$ECHO "$GCC" | $SED "$delay_single_quote_subst"`' lt_cv_sys_global_symbol_pipe='`$ECHO "$lt_cv_sys_global_symbol_pipe" | $SED "$delay_single_quote_subst"`' lt_cv_sys_global_symbol_to_cdecl='`$ECHO "$lt_cv_sys_global_symbol_to_cdecl" | $SED "$delay_single_quote_subst"`' lt_cv_sys_global_symbol_to_import='`$ECHO "$lt_cv_sys_global_symbol_to_import" | $SED "$delay_single_quote_subst"`' lt_cv_sys_global_symbol_to_c_name_address='`$ECHO "$lt_cv_sys_global_symbol_to_c_name_address" | $SED "$delay_single_quote_subst"`' lt_cv_sys_global_symbol_to_c_name_address_lib_prefix='`$ECHO "$lt_cv_sys_global_symbol_to_c_name_address_lib_prefix" | $SED "$delay_single_quote_subst"`' lt_cv_nm_interface='`$ECHO "$lt_cv_nm_interface" | $SED "$delay_single_quote_subst"`' nm_file_list_spec='`$ECHO "$nm_file_list_spec" | $SED "$delay_single_quote_subst"`' lt_sysroot='`$ECHO "$lt_sysroot" | $SED "$delay_single_quote_subst"`' lt_cv_truncate_bin='`$ECHO "$lt_cv_truncate_bin" | $SED "$delay_single_quote_subst"`' objdir='`$ECHO "$objdir" | $SED "$delay_single_quote_subst"`' MAGIC_CMD='`$ECHO "$MAGIC_CMD" | $SED "$delay_single_quote_subst"`' lt_prog_compiler_no_builtin_flag='`$ECHO "$lt_prog_compiler_no_builtin_flag" | $SED "$delay_single_quote_subst"`' lt_prog_compiler_pic='`$ECHO "$lt_prog_compiler_pic" | $SED "$delay_single_quote_subst"`' lt_prog_compiler_wl='`$ECHO "$lt_prog_compiler_wl" | $SED "$delay_single_quote_subst"`' lt_prog_compiler_static='`$ECHO "$lt_prog_compiler_static" | $SED "$delay_single_quote_subst"`' lt_cv_prog_compiler_c_o='`$ECHO "$lt_cv_prog_compiler_c_o" | $SED "$delay_single_quote_subst"`' need_locks='`$ECHO "$need_locks" | $SED "$delay_single_quote_subst"`' MANIFEST_TOOL='`$ECHO "$MANIFEST_TOOL" | $SED "$delay_single_quote_subst"`' DSYMUTIL='`$ECHO "$DSYMUTIL" | $SED "$delay_single_quote_subst"`' NMEDIT='`$ECHO "$NMEDIT" | $SED "$delay_single_quote_subst"`' LIPO='`$ECHO "$LIPO" | $SED "$delay_single_quote_subst"`' OTOOL='`$ECHO "$OTOOL" | $SED "$delay_single_quote_subst"`' OTOOL64='`$ECHO "$OTOOL64" | $SED "$delay_single_quote_subst"`' libext='`$ECHO "$libext" | $SED "$delay_single_quote_subst"`' shrext_cmds='`$ECHO "$shrext_cmds" | $SED "$delay_single_quote_subst"`' extract_expsyms_cmds='`$ECHO "$extract_expsyms_cmds" | $SED "$delay_single_quote_subst"`' archive_cmds_need_lc='`$ECHO "$archive_cmds_need_lc" | $SED "$delay_single_quote_subst"`' enable_shared_with_static_runtimes='`$ECHO "$enable_shared_with_static_runtimes" | $SED "$delay_single_quote_subst"`' export_dynamic_flag_spec='`$ECHO "$export_dynamic_flag_spec" | $SED "$delay_single_quote_subst"`' whole_archive_flag_spec='`$ECHO "$whole_archive_flag_spec" | $SED "$delay_single_quote_subst"`' compiler_needs_object='`$ECHO "$compiler_needs_object" | $SED "$delay_single_quote_subst"`' old_archive_from_new_cmds='`$ECHO "$old_archive_from_new_cmds" | $SED "$delay_single_quote_subst"`' old_archive_from_expsyms_cmds='`$ECHO "$old_archive_from_expsyms_cmds" | $SED "$delay_single_quote_subst"`' archive_cmds='`$ECHO "$archive_cmds" | $SED "$delay_single_quote_subst"`' archive_expsym_cmds='`$ECHO "$archive_expsym_cmds" | $SED "$delay_single_quote_subst"`' module_cmds='`$ECHO "$module_cmds" | $SED "$delay_single_quote_subst"`' module_expsym_cmds='`$ECHO "$module_expsym_cmds" | $SED "$delay_single_quote_subst"`' with_gnu_ld='`$ECHO "$with_gnu_ld" | $SED "$delay_single_quote_subst"`' allow_undefined_flag='`$ECHO "$allow_undefined_flag" | $SED "$delay_single_quote_subst"`' no_undefined_flag='`$ECHO "$no_undefined_flag" | $SED "$delay_single_quote_subst"`' hardcode_libdir_flag_spec='`$ECHO "$hardcode_libdir_flag_spec" | $SED "$delay_single_quote_subst"`' hardcode_libdir_separator='`$ECHO "$hardcode_libdir_separator" | $SED "$delay_single_quote_subst"`' hardcode_direct='`$ECHO "$hardcode_direct" | $SED "$delay_single_quote_subst"`' hardcode_direct_absolute='`$ECHO "$hardcode_direct_absolute" | $SED "$delay_single_quote_subst"`' hardcode_minus_L='`$ECHO "$hardcode_minus_L" | $SED "$delay_single_quote_subst"`' hardcode_shlibpath_var='`$ECHO "$hardcode_shlibpath_var" | $SED "$delay_single_quote_subst"`' hardcode_automatic='`$ECHO "$hardcode_automatic" | $SED "$delay_single_quote_subst"`' inherit_rpath='`$ECHO "$inherit_rpath" | $SED "$delay_single_quote_subst"`' link_all_deplibs='`$ECHO "$link_all_deplibs" | $SED "$delay_single_quote_subst"`' always_export_symbols='`$ECHO "$always_export_symbols" | $SED "$delay_single_quote_subst"`' export_symbols_cmds='`$ECHO "$export_symbols_cmds" | $SED "$delay_single_quote_subst"`' exclude_expsyms='`$ECHO "$exclude_expsyms" | $SED "$delay_single_quote_subst"`' include_expsyms='`$ECHO "$include_expsyms" | $SED "$delay_single_quote_subst"`' prelink_cmds='`$ECHO "$prelink_cmds" | $SED "$delay_single_quote_subst"`' postlink_cmds='`$ECHO "$postlink_cmds" | $SED "$delay_single_quote_subst"`' file_list_spec='`$ECHO "$file_list_spec" | $SED "$delay_single_quote_subst"`' variables_saved_for_relink='`$ECHO "$variables_saved_for_relink" | $SED "$delay_single_quote_subst"`' need_lib_prefix='`$ECHO "$need_lib_prefix" | $SED "$delay_single_quote_subst"`' need_version='`$ECHO "$need_version" | $SED "$delay_single_quote_subst"`' version_type='`$ECHO "$version_type" | $SED "$delay_single_quote_subst"`' runpath_var='`$ECHO "$runpath_var" | $SED "$delay_single_quote_subst"`' shlibpath_var='`$ECHO "$shlibpath_var" | $SED "$delay_single_quote_subst"`' shlibpath_overrides_runpath='`$ECHO "$shlibpath_overrides_runpath" | $SED "$delay_single_quote_subst"`' libname_spec='`$ECHO "$libname_spec" | $SED "$delay_single_quote_subst"`' library_names_spec='`$ECHO "$library_names_spec" | $SED "$delay_single_quote_subst"`' soname_spec='`$ECHO "$soname_spec" | $SED "$delay_single_quote_subst"`' install_override_mode='`$ECHO "$install_override_mode" | $SED "$delay_single_quote_subst"`' postinstall_cmds='`$ECHO "$postinstall_cmds" | $SED "$delay_single_quote_subst"`' postuninstall_cmds='`$ECHO "$postuninstall_cmds" | $SED "$delay_single_quote_subst"`' finish_cmds='`$ECHO "$finish_cmds" | $SED "$delay_single_quote_subst"`' finish_eval='`$ECHO "$finish_eval" | $SED "$delay_single_quote_subst"`' hardcode_into_libs='`$ECHO "$hardcode_into_libs" | $SED "$delay_single_quote_subst"`' sys_lib_search_path_spec='`$ECHO "$sys_lib_search_path_spec" | $SED "$delay_single_quote_subst"`' configure_time_dlsearch_path='`$ECHO "$configure_time_dlsearch_path" | $SED "$delay_single_quote_subst"`' configure_time_lt_sys_library_path='`$ECHO "$configure_time_lt_sys_library_path" | $SED "$delay_single_quote_subst"`' hardcode_action='`$ECHO "$hardcode_action" | $SED "$delay_single_quote_subst"`' enable_dlopen='`$ECHO "$enable_dlopen" | $SED "$delay_single_quote_subst"`' enable_dlopen_self='`$ECHO "$enable_dlopen_self" | $SED "$delay_single_quote_subst"`' enable_dlopen_self_static='`$ECHO "$enable_dlopen_self_static" | $SED "$delay_single_quote_subst"`' old_striplib='`$ECHO "$old_striplib" | $SED "$delay_single_quote_subst"`' striplib='`$ECHO "$striplib" | $SED "$delay_single_quote_subst"`' LTCC='$LTCC' LTCFLAGS='$LTCFLAGS' compiler='$compiler_DEFAULT' # A function that is used when there is no print builtin or printf. func_fallback_echo () { eval 'cat <<_LTECHO_EOF \$1 _LTECHO_EOF' } # Quote evaled strings. for var in SHELL \ ECHO \ PATH_SEPARATOR \ SED \ GREP \ EGREP \ FGREP \ LD \ NM \ LN_S \ lt_SP2NL \ lt_NL2SP \ reload_flag \ OBJDUMP \ deplibs_check_method \ file_magic_cmd \ file_magic_glob \ want_nocaseglob \ DLLTOOL \ sharedlib_from_linklib_cmd \ AR \ AR_FLAGS \ archiver_list_spec \ STRIP \ RANLIB \ CC \ CFLAGS \ compiler \ lt_cv_sys_global_symbol_pipe \ lt_cv_sys_global_symbol_to_cdecl \ lt_cv_sys_global_symbol_to_import \ lt_cv_sys_global_symbol_to_c_name_address \ lt_cv_sys_global_symbol_to_c_name_address_lib_prefix \ lt_cv_nm_interface \ nm_file_list_spec \ lt_cv_truncate_bin \ lt_prog_compiler_no_builtin_flag \ lt_prog_compiler_pic \ lt_prog_compiler_wl \ lt_prog_compiler_static \ lt_cv_prog_compiler_c_o \ need_locks \ MANIFEST_TOOL \ DSYMUTIL \ NMEDIT \ LIPO \ OTOOL \ OTOOL64 \ shrext_cmds \ export_dynamic_flag_spec \ whole_archive_flag_spec \ compiler_needs_object \ with_gnu_ld \ allow_undefined_flag \ no_undefined_flag \ hardcode_libdir_flag_spec \ hardcode_libdir_separator \ exclude_expsyms \ include_expsyms \ file_list_spec \ variables_saved_for_relink \ libname_spec \ library_names_spec \ soname_spec \ install_override_mode \ finish_eval \ old_striplib \ striplib; do case \`eval \\\\\$ECHO \\\\""\\\\\$\$var"\\\\"\` in *[\\\\\\\`\\"\\\$]*) eval "lt_\$var=\\\\\\"\\\`\\\$ECHO \\"\\\$\$var\\" | \\\$SED \\"\\\$sed_quote_subst\\"\\\`\\\\\\"" ## exclude from sc_prohibit_nested_quotes ;; *) eval "lt_\$var=\\\\\\"\\\$\$var\\\\\\"" ;; esac done # Double-quote double-evaled strings. for var in reload_cmds \ old_postinstall_cmds \ old_postuninstall_cmds \ old_archive_cmds \ extract_expsyms_cmds \ old_archive_from_new_cmds \ old_archive_from_expsyms_cmds \ archive_cmds \ archive_expsym_cmds \ module_cmds \ module_expsym_cmds \ export_symbols_cmds \ prelink_cmds \ postlink_cmds \ postinstall_cmds \ postuninstall_cmds \ finish_cmds \ sys_lib_search_path_spec \ configure_time_dlsearch_path \ configure_time_lt_sys_library_path; do case \`eval \\\\\$ECHO \\\\""\\\\\$\$var"\\\\"\` in *[\\\\\\\`\\"\\\$]*) eval "lt_\$var=\\\\\\"\\\`\\\$ECHO \\"\\\$\$var\\" | \\\$SED -e \\"\\\$double_quote_subst\\" -e \\"\\\$sed_quote_subst\\" -e \\"\\\$delay_variable_subst\\"\\\`\\\\\\"" ## exclude from sc_prohibit_nested_quotes ;; *) eval "lt_\$var=\\\\\\"\\\$\$var\\\\\\"" ;; esac done ac_aux_dir='$ac_aux_dir' # See if we are running on zsh, and set the options that allow our # commands through without removal of \ escapes INIT. if test -n "\${ZSH_VERSION+set}"; then setopt NO_GLOB_SUBST fi PACKAGE='$PACKAGE' VERSION='$VERSION' RM='$RM' ofile='$ofile' PERL="${PERL}" MAKE_MAKER_ARGS="PREFIX=${prefix}" PERL="${PERL}" MAKE_MAKER_ARGS="PREFIX=${prefix}" PERL="${PERL}" MAKE_MAKER_ARGS="PREFIX=${prefix}" _ACEOF cat >>$CONFIG_STATUS <<\_ACEOF || ac_write_fail=1 # Handling of arguments. for ac_config_target in $ac_config_targets do case $ac_config_target in "config.h") CONFIG_HEADERS="$CONFIG_HEADERS config.h" ;; "depfiles") CONFIG_COMMANDS="$CONFIG_COMMANDS depfiles" ;; "libtool") CONFIG_COMMANDS="$CONFIG_COMMANDS libtool" ;; "libcyrus_min.pc") CONFIG_FILES="$CONFIG_FILES libcyrus_min.pc" ;; "libcyrus.pc") CONFIG_FILES="$CONFIG_FILES libcyrus.pc" ;; "libcyrus_sieve.pc") CONFIG_FILES="$CONFIG_FILES libcyrus_sieve.pc" ;; "Makefile") CONFIG_FILES="$CONFIG_FILES Makefile" ;; "perl/annotator/Makefile.PL") CONFIG_FILES="$CONFIG_FILES perl/annotator/Makefile.PL" ;; "perl/annotator/Makefile") CONFIG_COMMANDS="$CONFIG_COMMANDS perl/annotator/Makefile" ;; "perl/imap/Makefile.PL") CONFIG_FILES="$CONFIG_FILES perl/imap/Makefile.PL" ;; "perl/imap/Makefile") CONFIG_COMMANDS="$CONFIG_COMMANDS perl/imap/Makefile" ;; "perl/sieve/managesieve/Makefile.PL") CONFIG_FILES="$CONFIG_FILES perl/sieve/managesieve/Makefile.PL" ;; "perl/sieve/managesieve/Makefile") CONFIG_COMMANDS="$CONFIG_COMMANDS perl/sieve/managesieve/Makefile" ;; *) as_fn_error $? "invalid argument: \`$ac_config_target'" "$LINENO" 5;; esac done # If the user did not use the arguments to specify the items to instantiate, # then the envvar interface is used. Set only those that are not. # We use the long form for the default assignment because of an extremely # bizarre bug on SunOS 4.1.3. if $ac_need_defaults; then test "${CONFIG_FILES+set}" = set || CONFIG_FILES=$config_files test "${CONFIG_HEADERS+set}" = set || CONFIG_HEADERS=$config_headers test "${CONFIG_COMMANDS+set}" = set || CONFIG_COMMANDS=$config_commands fi # Have a temporary directory for convenience. Make it in the build tree # simply because there is no reason against having it here, and in addition, # creating and moving files from /tmp can sometimes cause problems. # Hook for its removal unless debugging. # Note that there is a small window in which the directory will not be cleaned: # after its creation but before its name has been assigned to `$tmp'. $debug || { tmp= ac_tmp= trap 'exit_status=$? : "${ac_tmp:=$tmp}" { test ! -d "$ac_tmp" || rm -fr "$ac_tmp"; } && exit $exit_status ' 0 trap 'as_fn_exit 1' 1 2 13 15 } # Create a (secure) tmp directory for tmp files. { tmp=`(umask 077 && mktemp -d "./confXXXXXX") 2>/dev/null` && test -d "$tmp" } || { tmp=./conf$$-$RANDOM (umask 077 && mkdir "$tmp") } || as_fn_error $? "cannot create a temporary directory in ." "$LINENO" 5 ac_tmp=$tmp # Set up the scripts for CONFIG_FILES section. # No need to generate them if there are no CONFIG_FILES. # This happens for instance with `./config.status config.h'. if test -n "$CONFIG_FILES"; then ac_cr=`echo X | tr X '\015'` # On cygwin, bash can eat \r inside `` if the user requested igncr. # But we know of no other shell where ac_cr would be empty at this # point, so we can use a bashism as a fallback. if test "x$ac_cr" = x; then eval ac_cr=\$\'\\r\' fi ac_cs_awk_cr=`$AWK 'BEGIN { print "a\rb" }' /dev/null` if test "$ac_cs_awk_cr" = "a${ac_cr}b"; then ac_cs_awk_cr='\\r' else ac_cs_awk_cr=$ac_cr fi echo 'BEGIN {' >"$ac_tmp/subs1.awk" && _ACEOF { echo "cat >conf$$subs.awk <<_ACEOF" && echo "$ac_subst_vars" | sed 's/.*/&!$&$ac_delim/' && echo "_ACEOF" } >conf$$subs.sh || as_fn_error $? "could not make $CONFIG_STATUS" "$LINENO" 5 ac_delim_num=`echo "$ac_subst_vars" | grep -c '^'` ac_delim='%!_!# ' for ac_last_try in false false false false false :; do . ./conf$$subs.sh || as_fn_error $? "could not make $CONFIG_STATUS" "$LINENO" 5 ac_delim_n=`sed -n "s/.*$ac_delim\$/X/p" conf$$subs.awk | grep -c X` if test $ac_delim_n = $ac_delim_num; then break elif $ac_last_try; then as_fn_error $? "could not make $CONFIG_STATUS" "$LINENO" 5 else ac_delim="$ac_delim!$ac_delim _$ac_delim!! " fi done rm -f conf$$subs.sh cat >>$CONFIG_STATUS <<_ACEOF || ac_write_fail=1 cat >>"\$ac_tmp/subs1.awk" <<\\_ACAWK && _ACEOF sed -n ' h s/^/S["/; s/!.*/"]=/ p g s/^[^!]*!// :repl t repl s/'"$ac_delim"'$// t delim :nl h s/\(.\{148\}\)..*/\1/ t more1 s/["\\]/\\&/g; s/^/"/; s/$/\\n"\\/ p n b repl :more1 s/["\\]/\\&/g; s/^/"/; s/$/"\\/ p g s/.\{148\}// t nl :delim h s/\(.\{148\}\)..*/\1/ t more2 s/["\\]/\\&/g; s/^/"/; s/$/"/ p b :more2 s/["\\]/\\&/g; s/^/"/; s/$/"\\/ p g s/.\{148\}// t delim ' >$CONFIG_STATUS || ac_write_fail=1 rm -f conf$$subs.awk cat >>$CONFIG_STATUS <<_ACEOF || ac_write_fail=1 _ACAWK cat >>"\$ac_tmp/subs1.awk" <<_ACAWK && for (key in S) S_is_set[key] = 1 FS = "" } { line = $ 0 nfields = split(line, field, "@") substed = 0 len = length(field[1]) for (i = 2; i < nfields; i++) { key = field[i] keylen = length(key) if (S_is_set[key]) { value = S[key] line = substr(line, 1, len) "" value "" substr(line, len + keylen + 3) len += length(value) + length(field[++i]) substed = 1 } else len += 1 + keylen } print line } _ACAWK _ACEOF cat >>$CONFIG_STATUS <<\_ACEOF || ac_write_fail=1 if sed "s/$ac_cr//" < /dev/null > /dev/null 2>&1; then sed "s/$ac_cr\$//; s/$ac_cr/$ac_cs_awk_cr/g" else cat fi < "$ac_tmp/subs1.awk" > "$ac_tmp/subs.awk" \ || as_fn_error $? "could not setup config files machinery" "$LINENO" 5 _ACEOF # VPATH may cause trouble with some makes, so we remove sole $(srcdir), # ${srcdir} and @srcdir@ entries from VPATH if srcdir is ".", strip leading and # trailing colons and then remove the whole line if VPATH becomes empty # (actually we leave an empty line to preserve line numbers). if test "x$srcdir" = x.; then ac_vpsub='/^[ ]*VPATH[ ]*=[ ]*/{ h s/// s/^/:/ s/[ ]*$/:/ s/:\$(srcdir):/:/g s/:\${srcdir}:/:/g s/:@srcdir@:/:/g s/^:*// s/:*$// x s/\(=[ ]*\).*/\1/ G s/\n// s/^[^=]*=[ ]*$// }' fi cat >>$CONFIG_STATUS <<\_ACEOF || ac_write_fail=1 fi # test -n "$CONFIG_FILES" # Set up the scripts for CONFIG_HEADERS section. # No need to generate them if there are no CONFIG_HEADERS. # This happens for instance with `./config.status Makefile'. if test -n "$CONFIG_HEADERS"; then cat >"$ac_tmp/defines.awk" <<\_ACAWK || BEGIN { _ACEOF # Transform confdefs.h into an awk script `defines.awk', embedded as # here-document in config.status, that substitutes the proper values into # config.h.in to produce config.h. # Create a delimiter string that does not exist in confdefs.h, to ease # handling of long lines. ac_delim='%!_!# ' for ac_last_try in false false :; do ac_tt=`sed -n "/$ac_delim/p" confdefs.h` if test -z "$ac_tt"; then break elif $ac_last_try; then as_fn_error $? "could not make $CONFIG_HEADERS" "$LINENO" 5 else ac_delim="$ac_delim!$ac_delim _$ac_delim!! " fi done # For the awk script, D is an array of macro values keyed by name, # likewise P contains macro parameters if any. Preserve backslash # newline sequences. ac_word_re=[_$as_cr_Letters][_$as_cr_alnum]* sed -n ' s/.\{148\}/&'"$ac_delim"'/g t rset :rset s/^[ ]*#[ ]*define[ ][ ]*/ / t def d :def s/\\$// t bsnl s/["\\]/\\&/g s/^ \('"$ac_word_re"'\)\(([^()]*)\)[ ]*\(.*\)/P["\1"]="\2"\ D["\1"]=" \3"/p s/^ \('"$ac_word_re"'\)[ ]*\(.*\)/D["\1"]=" \2"/p d :bsnl s/["\\]/\\&/g s/^ \('"$ac_word_re"'\)\(([^()]*)\)[ ]*\(.*\)/P["\1"]="\2"\ D["\1"]=" \3\\\\\\n"\\/p t cont s/^ \('"$ac_word_re"'\)[ ]*\(.*\)/D["\1"]=" \2\\\\\\n"\\/p t cont d :cont n s/.\{148\}/&'"$ac_delim"'/g t clear :clear s/\\$// t bsnlc s/["\\]/\\&/g; s/^/"/; s/$/"/p d :bsnlc s/["\\]/\\&/g; s/^/"/; s/$/\\\\\\n"\\/p b cont ' >$CONFIG_STATUS || ac_write_fail=1 cat >>$CONFIG_STATUS <<_ACEOF || ac_write_fail=1 for (key in D) D_is_set[key] = 1 FS = "" } /^[\t ]*#[\t ]*(define|undef)[\t ]+$ac_word_re([\t (]|\$)/ { line = \$ 0 split(line, arg, " ") if (arg[1] == "#") { defundef = arg[2] mac1 = arg[3] } else { defundef = substr(arg[1], 2) mac1 = arg[2] } split(mac1, mac2, "(") #) macro = mac2[1] prefix = substr(line, 1, index(line, defundef) - 1) if (D_is_set[macro]) { # Preserve the white space surrounding the "#". print prefix "define", macro P[macro] D[macro] next } else { # Replace #undef with comments. This is necessary, for example, # in the case of _POSIX_SOURCE, which is predefined and required # on some systems where configure will not decide to define it. if (defundef == "undef") { print "/*", prefix defundef, macro, "*/" next } } } { print } _ACAWK _ACEOF cat >>$CONFIG_STATUS <<\_ACEOF || ac_write_fail=1 as_fn_error $? "could not setup config headers machinery" "$LINENO" 5 fi # test -n "$CONFIG_HEADERS" eval set X " :F $CONFIG_FILES :H $CONFIG_HEADERS :C $CONFIG_COMMANDS" shift for ac_tag do case $ac_tag in :[FHLC]) ac_mode=$ac_tag; continue;; esac case $ac_mode$ac_tag in :[FHL]*:*);; :L* | :C*:*) as_fn_error $? "invalid tag \`$ac_tag'" "$LINENO" 5;; :[FH]-) ac_tag=-:-;; :[FH]*) ac_tag=$ac_tag:$ac_tag.in;; esac ac_save_IFS=$IFS IFS=: set x $ac_tag IFS=$ac_save_IFS shift ac_file=$1 shift case $ac_mode in :L) ac_source=$1;; :[FH]) ac_file_inputs= for ac_f do case $ac_f in -) ac_f="$ac_tmp/stdin";; *) # Look for the file first in the build tree, then in the source tree # (if the path is not absolute). The absolute path cannot be DOS-style, # because $ac_f cannot contain `:'. test -f "$ac_f" || case $ac_f in [\\/$]*) false;; *) test -f "$srcdir/$ac_f" && ac_f="$srcdir/$ac_f";; esac || as_fn_error 1 "cannot find input file: \`$ac_f'" "$LINENO" 5;; esac case $ac_f in *\'*) ac_f=`$as_echo "$ac_f" | sed "s/'/'\\\\\\\\''/g"`;; esac as_fn_append ac_file_inputs " '$ac_f'" done # Let's still pretend it is `configure' which instantiates (i.e., don't # use $as_me), people would be surprised to read: # /* config.h. Generated by config.status. */ configure_input='Generated from '` $as_echo "$*" | sed 's|^[^:]*/||;s|:[^:]*/|, |g' `' by configure.' if test x"$ac_file" != x-; then configure_input="$ac_file. $configure_input" { $as_echo "$as_me:${as_lineno-$LINENO}: creating $ac_file" >&5 $as_echo "$as_me: creating $ac_file" >&6;} fi # Neutralize special characters interpreted by sed in replacement strings. case $configure_input in #( *\&* | *\|* | *\\* ) ac_sed_conf_input=`$as_echo "$configure_input" | sed 's/[\\\\&|]/\\\\&/g'`;; #( *) ac_sed_conf_input=$configure_input;; esac case $ac_tag in *:-:* | *:-) cat >"$ac_tmp/stdin" \ || as_fn_error $? "could not create $ac_file" "$LINENO" 5 ;; esac ;; esac ac_dir=`$as_dirname -- "$ac_file" || $as_expr X"$ac_file" : 'X\(.*[^/]\)//*[^/][^/]*/*$' \| \ X"$ac_file" : 'X\(//\)[^/]' \| \ X"$ac_file" : 'X\(//\)$' \| \ X"$ac_file" : 'X\(/\)' \| . 2>/dev/null || $as_echo X"$ac_file" | sed '/^X\(.*[^/]\)\/\/*[^/][^/]*\/*$/{ s//\1/ q } /^X\(\/\/\)[^/].*/{ s//\1/ q } /^X\(\/\/\)$/{ s//\1/ q } /^X\(\/\).*/{ s//\1/ q } s/.*/./; q'` as_dir="$ac_dir"; as_fn_mkdir_p ac_builddir=. case "$ac_dir" in .) ac_dir_suffix= ac_top_builddir_sub=. ac_top_build_prefix= ;; *) ac_dir_suffix=/`$as_echo "$ac_dir" | sed 's|^\.[\\/]||'` # A ".." for each directory in $ac_dir_suffix. ac_top_builddir_sub=`$as_echo "$ac_dir_suffix" | sed 's|/[^\\/]*|/..|g;s|/||'` case $ac_top_builddir_sub in "") ac_top_builddir_sub=. ac_top_build_prefix= ;; *) ac_top_build_prefix=$ac_top_builddir_sub/ ;; esac ;; esac ac_abs_top_builddir=$ac_pwd ac_abs_builddir=$ac_pwd$ac_dir_suffix # for backward compatibility: ac_top_builddir=$ac_top_build_prefix case $srcdir in .) # We are building in place. ac_srcdir=. ac_top_srcdir=$ac_top_builddir_sub ac_abs_top_srcdir=$ac_pwd ;; [\\/]* | ?:[\\/]* ) # Absolute name. ac_srcdir=$srcdir$ac_dir_suffix; ac_top_srcdir=$srcdir ac_abs_top_srcdir=$srcdir ;; *) # Relative name. ac_srcdir=$ac_top_build_prefix$srcdir$ac_dir_suffix ac_top_srcdir=$ac_top_build_prefix$srcdir ac_abs_top_srcdir=$ac_pwd/$srcdir ;; esac ac_abs_srcdir=$ac_abs_top_srcdir$ac_dir_suffix case $ac_mode in :F) # # CONFIG_FILE # case $INSTALL in [\\/$]* | ?:[\\/]* ) ac_INSTALL=$INSTALL ;; *) ac_INSTALL=$ac_top_build_prefix$INSTALL ;; esac ac_MKDIR_P=$MKDIR_P case $MKDIR_P in [\\/$]* | ?:[\\/]* ) ;; */*) ac_MKDIR_P=$ac_top_build_prefix$MKDIR_P ;; esac _ACEOF cat >>$CONFIG_STATUS <<\_ACEOF || ac_write_fail=1 # If the template does not know about datarootdir, expand it. # FIXME: This hack should be removed a few years after 2.60. ac_datarootdir_hack=; ac_datarootdir_seen= ac_sed_dataroot=' /datarootdir/ { p q } /@datadir@/p /@docdir@/p /@infodir@/p /@localedir@/p /@mandir@/p' case `eval "sed -n \"\$ac_sed_dataroot\" $ac_file_inputs"` in *datarootdir*) ac_datarootdir_seen=yes;; *@datadir@*|*@docdir@*|*@infodir@*|*@localedir@*|*@mandir@*) { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: $ac_file_inputs seems to ignore the --datarootdir setting" >&5 $as_echo "$as_me: WARNING: $ac_file_inputs seems to ignore the --datarootdir setting" >&2;} _ACEOF cat >>$CONFIG_STATUS <<_ACEOF || ac_write_fail=1 ac_datarootdir_hack=' s&@datadir@&$datadir&g s&@docdir@&$docdir&g s&@infodir@&$infodir&g s&@localedir@&$localedir&g s&@mandir@&$mandir&g s&\\\${datarootdir}&$datarootdir&g' ;; esac _ACEOF # Neutralize VPATH when `$srcdir' = `.'. # Shell code in configure.ac might set extrasub. # FIXME: do we really want to maintain this feature? cat >>$CONFIG_STATUS <<_ACEOF || ac_write_fail=1 ac_sed_extra="$ac_vpsub $extrasub _ACEOF cat >>$CONFIG_STATUS <<\_ACEOF || ac_write_fail=1 :t /@[a-zA-Z_][a-zA-Z_0-9]*@/!b s|@configure_input@|$ac_sed_conf_input|;t t s&@top_builddir@&$ac_top_builddir_sub&;t t s&@top_build_prefix@&$ac_top_build_prefix&;t t s&@srcdir@&$ac_srcdir&;t t s&@abs_srcdir@&$ac_abs_srcdir&;t t s&@top_srcdir@&$ac_top_srcdir&;t t s&@abs_top_srcdir@&$ac_abs_top_srcdir&;t t s&@builddir@&$ac_builddir&;t t s&@abs_builddir@&$ac_abs_builddir&;t t s&@abs_top_builddir@&$ac_abs_top_builddir&;t t s&@INSTALL@&$ac_INSTALL&;t t s&@MKDIR_P@&$ac_MKDIR_P&;t t $ac_datarootdir_hack " eval sed \"\$ac_sed_extra\" "$ac_file_inputs" | $AWK -f "$ac_tmp/subs.awk" \ >$ac_tmp/out || as_fn_error $? "could not create $ac_file" "$LINENO" 5 test -z "$ac_datarootdir_hack$ac_datarootdir_seen" && { ac_out=`sed -n '/\${datarootdir}/p' "$ac_tmp/out"`; test -n "$ac_out"; } && { ac_out=`sed -n '/^[ ]*datarootdir[ ]*:*=/p' \ "$ac_tmp/out"`; test -z "$ac_out"; } && { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: $ac_file contains a reference to the variable \`datarootdir' which seems to be undefined. Please make sure it is defined" >&5 $as_echo "$as_me: WARNING: $ac_file contains a reference to the variable \`datarootdir' which seems to be undefined. Please make sure it is defined" >&2;} rm -f "$ac_tmp/stdin" case $ac_file in -) cat "$ac_tmp/out" && rm -f "$ac_tmp/out";; *) rm -f "$ac_file" && mv "$ac_tmp/out" "$ac_file";; esac \ || as_fn_error $? "could not create $ac_file" "$LINENO" 5 ;; :H) # # CONFIG_HEADER # if test x"$ac_file" != x-; then { $as_echo "/* $configure_input */" \ && eval '$AWK -f "$ac_tmp/defines.awk"' "$ac_file_inputs" } >"$ac_tmp/config.h" \ || as_fn_error $? "could not create $ac_file" "$LINENO" 5 if diff "$ac_file" "$ac_tmp/config.h" >/dev/null 2>&1; then { $as_echo "$as_me:${as_lineno-$LINENO}: $ac_file is unchanged" >&5 $as_echo "$as_me: $ac_file is unchanged" >&6;} else rm -f "$ac_file" mv "$ac_tmp/config.h" "$ac_file" \ || as_fn_error $? "could not create $ac_file" "$LINENO" 5 fi else $as_echo "/* $configure_input */" \ && eval '$AWK -f "$ac_tmp/defines.awk"' "$ac_file_inputs" \ || as_fn_error $? "could not create -" "$LINENO" 5 fi # Compute "$ac_file"'s index in $config_headers. _am_arg="$ac_file" _am_stamp_count=1 for _am_header in $config_headers :; do case $_am_header in $_am_arg | $_am_arg:* ) break ;; * ) _am_stamp_count=`expr $_am_stamp_count + 1` ;; esac done echo "timestamp for $_am_arg" >`$as_dirname -- "$_am_arg" || $as_expr X"$_am_arg" : 'X\(.*[^/]\)//*[^/][^/]*/*$' \| \ X"$_am_arg" : 'X\(//\)[^/]' \| \ X"$_am_arg" : 'X\(//\)$' \| \ X"$_am_arg" : 'X\(/\)' \| . 2>/dev/null || $as_echo X"$_am_arg" | sed '/^X\(.*[^/]\)\/\/*[^/][^/]*\/*$/{ s//\1/ q } /^X\(\/\/\)[^/].*/{ s//\1/ q } /^X\(\/\/\)$/{ s//\1/ q } /^X\(\/\).*/{ s//\1/ q } s/.*/./; q'`/stamp-h$_am_stamp_count ;; :C) { $as_echo "$as_me:${as_lineno-$LINENO}: executing $ac_file commands" >&5 $as_echo "$as_me: executing $ac_file commands" >&6;} ;; esac case $ac_file$ac_mode in "depfiles":C) test x"$AMDEP_TRUE" != x"" || { # Older Autoconf quotes --file arguments for eval, but not when files # are listed without --file. Let's play safe and only enable the eval # if we detect the quoting. case $CONFIG_FILES in *\'*) eval set x "$CONFIG_FILES" ;; *) set x $CONFIG_FILES ;; esac shift for mf do # Strip MF so we end up with the name of the file. mf=`echo "$mf" | sed -e 's/:.*$//'` # Check whether this is an Automake generated Makefile or not. # We used to match only the files named 'Makefile.in', but # some people rename them; so instead we look at the file content. # Grep'ing the first line is not enough: some people post-process # each Makefile.in and add a new line on top of each file to say so. # Grep'ing the whole file is not good either: AIX grep has a line # limit of 2048, but all sed's we know have understand at least 4000. if sed -n 's,^#.*generated by automake.*,X,p' "$mf" | grep X >/dev/null 2>&1; then dirpart=`$as_dirname -- "$mf" || $as_expr X"$mf" : 'X\(.*[^/]\)//*[^/][^/]*/*$' \| \ X"$mf" : 'X\(//\)[^/]' \| \ X"$mf" : 'X\(//\)$' \| \ X"$mf" : 'X\(/\)' \| . 2>/dev/null || $as_echo X"$mf" | sed '/^X\(.*[^/]\)\/\/*[^/][^/]*\/*$/{ s//\1/ q } /^X\(\/\/\)[^/].*/{ s//\1/ q } /^X\(\/\/\)$/{ s//\1/ q } /^X\(\/\).*/{ s//\1/ q } s/.*/./; q'` else continue fi # Extract the definition of DEPDIR, am__include, and am__quote # from the Makefile without running 'make'. DEPDIR=`sed -n 's/^DEPDIR = //p' < "$mf"` test -z "$DEPDIR" && continue am__include=`sed -n 's/^am__include = //p' < "$mf"` test -z "$am__include" && continue am__quote=`sed -n 's/^am__quote = //p' < "$mf"` # Find all dependency output files, they are included files with # $(DEPDIR) in their names. We invoke sed twice because it is the # simplest approach to changing $(DEPDIR) to its actual value in the # expansion. for file in `sed -n " s/^$am__include $am__quote\(.*(DEPDIR).*\)$am__quote"'$/\1/p' <"$mf" | \ sed -e 's/\$(DEPDIR)/'"$DEPDIR"'/g'`; do # Make sure the directory exists. test -f "$dirpart/$file" && continue fdir=`$as_dirname -- "$file" || $as_expr X"$file" : 'X\(.*[^/]\)//*[^/][^/]*/*$' \| \ X"$file" : 'X\(//\)[^/]' \| \ X"$file" : 'X\(//\)$' \| \ X"$file" : 'X\(/\)' \| . 2>/dev/null || $as_echo X"$file" | sed '/^X\(.*[^/]\)\/\/*[^/][^/]*\/*$/{ s//\1/ q } /^X\(\/\/\)[^/].*/{ s//\1/ q } /^X\(\/\/\)$/{ s//\1/ q } /^X\(\/\).*/{ s//\1/ q } s/.*/./; q'` as_dir=$dirpart/$fdir; as_fn_mkdir_p # echo "creating $dirpart/$file" echo '# dummy' > "$dirpart/$file" done done } ;; "libtool":C) # See if we are running on zsh, and set the options that allow our # commands through without removal of \ escapes. if test -n "${ZSH_VERSION+set}"; then setopt NO_GLOB_SUBST fi cfgfile=${ofile}T trap "$RM \"$cfgfile\"; exit 1" 1 2 15 $RM "$cfgfile" cat <<_LT_EOF >> "$cfgfile" #! $SHELL # Generated automatically by $as_me ($PACKAGE) $VERSION # NOTE: Changes made to this file will be lost: look at ltmain.sh. # Provide generalized library-building support services. # Written by Gordon Matzigkeit, 1996 # Copyright (C) 2014 Free Software Foundation, Inc. # This is free software; see the source for copying conditions. There is NO # warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. # GNU Libtool is free software; you can redistribute it and/or modify # it under the terms of the GNU General Public License as published by # the Free Software Foundation; either version 2 of of the License, or # (at your option) any later version. # # As a special exception to the GNU General Public License, if you # distribute this file as part of a program or library that is built # using GNU Libtool, you may include this file under the same # distribution terms that you use for the rest of that program. # # GNU Libtool is distributed in the hope that it will be useful, but # WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the # GNU General Public License for more details. # # You should have received a copy of the GNU General Public License # along with this program. If not, see . # The names of the tagged configurations supported by this script. available_tags='' # Configured defaults for sys_lib_dlsearch_path munging. : \${LT_SYS_LIBRARY_PATH="$configure_time_lt_sys_library_path"} # ### BEGIN LIBTOOL CONFIG # Which release of libtool.m4 was used? macro_version=$macro_version macro_revision=$macro_revision # Whether or not to build static libraries. build_old_libs=$enable_static # Whether or not to build shared libraries. build_libtool_libs=$enable_shared # What type of objects to build. pic_mode=$pic_mode # Whether or not to optimize for fast installation. fast_install=$enable_fast_install # Shared archive member basename,for filename based shared library versioning on AIX. shared_archive_member_spec=$shared_archive_member_spec # Shell to use when invoking shell scripts. SHELL=$lt_SHELL # An echo program that protects backslashes. ECHO=$lt_ECHO # The PATH separator for the build system. PATH_SEPARATOR=$lt_PATH_SEPARATOR # The host system. host_alias=$host_alias host=$host host_os=$host_os # The build system. build_alias=$build_alias build=$build build_os=$build_os # A sed program that does not truncate output. SED=$lt_SED # Sed that helps us avoid accidentally triggering echo(1) options like -n. Xsed="\$SED -e 1s/^X//" # A grep program that handles long lines. GREP=$lt_GREP # An ERE matcher. EGREP=$lt_EGREP # A literal string matcher. FGREP=$lt_FGREP # A BSD- or MS-compatible name lister. NM=$lt_NM # Whether we need soft or hard links. LN_S=$lt_LN_S # What is the maximum length of a command? max_cmd_len=$max_cmd_len # Object file suffix (normally "o"). objext=$ac_objext # Executable file suffix (normally ""). exeext=$exeext # whether the shell understands "unset". lt_unset=$lt_unset # turn spaces into newlines. SP2NL=$lt_lt_SP2NL # turn newlines into spaces. NL2SP=$lt_lt_NL2SP # convert \$build file names to \$host format. to_host_file_cmd=$lt_cv_to_host_file_cmd # convert \$build files to toolchain format. to_tool_file_cmd=$lt_cv_to_tool_file_cmd # An object symbol dumper. OBJDUMP=$lt_OBJDUMP # Method to check whether dependent libraries are shared objects. deplibs_check_method=$lt_deplibs_check_method # Command to use when deplibs_check_method = "file_magic". file_magic_cmd=$lt_file_magic_cmd # How to find potential files when deplibs_check_method = "file_magic". file_magic_glob=$lt_file_magic_glob # Find potential files using nocaseglob when deplibs_check_method = "file_magic". want_nocaseglob=$lt_want_nocaseglob # DLL creation program. DLLTOOL=$lt_DLLTOOL # Command to associate shared and link libraries. sharedlib_from_linklib_cmd=$lt_sharedlib_from_linklib_cmd # The archiver. AR=$lt_AR # Flags to create an archive. AR_FLAGS=$lt_AR_FLAGS # How to feed a file listing to the archiver. archiver_list_spec=$lt_archiver_list_spec # A symbol stripping program. STRIP=$lt_STRIP # Commands used to install an old-style archive. RANLIB=$lt_RANLIB old_postinstall_cmds=$lt_old_postinstall_cmds old_postuninstall_cmds=$lt_old_postuninstall_cmds # Whether to use a lock for old archive extraction. lock_old_archive_extraction=$lock_old_archive_extraction # A C compiler. LTCC=$lt_CC # LTCC compiler flags. LTCFLAGS=$lt_CFLAGS # Take the output of nm and produce a listing of raw symbols and C names. global_symbol_pipe=$lt_lt_cv_sys_global_symbol_pipe # Transform the output of nm in a proper C declaration. global_symbol_to_cdecl=$lt_lt_cv_sys_global_symbol_to_cdecl # Transform the output of nm into a list of symbols to manually relocate. global_symbol_to_import=$lt_lt_cv_sys_global_symbol_to_import # Transform the output of nm in a C name address pair. global_symbol_to_c_name_address=$lt_lt_cv_sys_global_symbol_to_c_name_address # Transform the output of nm in a C name address pair when lib prefix is needed. global_symbol_to_c_name_address_lib_prefix=$lt_lt_cv_sys_global_symbol_to_c_name_address_lib_prefix # The name lister interface. nm_interface=$lt_lt_cv_nm_interface # Specify filename containing input files for \$NM. nm_file_list_spec=$lt_nm_file_list_spec # The root where to search for dependent libraries,and where our libraries should be installed. lt_sysroot=$lt_sysroot # Command to truncate a binary pipe. lt_truncate_bin=$lt_lt_cv_truncate_bin # The name of the directory that contains temporary libtool files. objdir=$objdir # Used to examine libraries when file_magic_cmd begins with "file". MAGIC_CMD=$MAGIC_CMD # Must we lock files when doing compilation? need_locks=$lt_need_locks # Manifest tool. MANIFEST_TOOL=$lt_MANIFEST_TOOL # Tool to manipulate archived DWARF debug symbol files on Mac OS X. DSYMUTIL=$lt_DSYMUTIL # Tool to change global to local symbols on Mac OS X. NMEDIT=$lt_NMEDIT # Tool to manipulate fat objects and archives on Mac OS X. LIPO=$lt_LIPO # ldd/readelf like tool for Mach-O binaries on Mac OS X. OTOOL=$lt_OTOOL # ldd/readelf like tool for 64 bit Mach-O binaries on Mac OS X 10.4. OTOOL64=$lt_OTOOL64 # Old archive suffix (normally "a"). libext=$libext # Shared library suffix (normally ".so"). shrext_cmds=$lt_shrext_cmds # The commands to extract the exported symbol list from a shared archive. extract_expsyms_cmds=$lt_extract_expsyms_cmds # Variables whose values should be saved in libtool wrapper scripts and # restored at link time. variables_saved_for_relink=$lt_variables_saved_for_relink # Do we need the "lib" prefix for modules? need_lib_prefix=$need_lib_prefix # Do we need a version for libraries? need_version=$need_version # Library versioning type. version_type=$version_type # Shared library runtime path variable. runpath_var=$runpath_var # Shared library path variable. shlibpath_var=$shlibpath_var # Is shlibpath searched before the hard-coded library search path? shlibpath_overrides_runpath=$shlibpath_overrides_runpath # Format of library name prefix. libname_spec=$lt_libname_spec # List of archive names. First name is the real one, the rest are links. # The last name is the one that the linker finds with -lNAME library_names_spec=$lt_library_names_spec # The coded name of the library, if different from the real name. soname_spec=$lt_soname_spec # Permission mode override for installation of shared libraries. install_override_mode=$lt_install_override_mode # Command to use after installation of a shared archive. postinstall_cmds=$lt_postinstall_cmds # Command to use after uninstallation of a shared archive. postuninstall_cmds=$lt_postuninstall_cmds # Commands used to finish a libtool library installation in a directory. finish_cmds=$lt_finish_cmds # As "finish_cmds", except a single script fragment to be evaled but # not shown. finish_eval=$lt_finish_eval # Whether we should hardcode library paths into libraries. hardcode_into_libs=$hardcode_into_libs # Compile-time system search path for libraries. sys_lib_search_path_spec=$lt_sys_lib_search_path_spec # Detected run-time system search path for libraries. sys_lib_dlsearch_path_spec=$lt_configure_time_dlsearch_path # Explicit LT_SYS_LIBRARY_PATH set during ./configure time. configure_time_lt_sys_library_path=$lt_configure_time_lt_sys_library_path # Whether dlopen is supported. dlopen_support=$enable_dlopen # Whether dlopen of programs is supported. dlopen_self=$enable_dlopen_self # Whether dlopen of statically linked programs is supported. dlopen_self_static=$enable_dlopen_self_static # Commands to strip libraries. old_striplib=$lt_old_striplib striplib=$lt_striplib # The linker used to build libraries. LD=$lt_LD # How to create reloadable object files. reload_flag=$lt_reload_flag reload_cmds=$lt_reload_cmds # Commands used to build an old-style archive. old_archive_cmds=$lt_old_archive_cmds # A language specific compiler. CC=$lt_compiler # Is the compiler the GNU compiler? with_gcc=$GCC # Compiler flag to turn off builtin functions. no_builtin_flag=$lt_lt_prog_compiler_no_builtin_flag # Additional compiler flags for building library objects. pic_flag=$lt_lt_prog_compiler_pic # How to pass a linker flag through the compiler. wl=$lt_lt_prog_compiler_wl # Compiler flag to prevent dynamic linking. link_static_flag=$lt_lt_prog_compiler_static # Does compiler simultaneously support -c and -o options? compiler_c_o=$lt_lt_cv_prog_compiler_c_o # Whether or not to add -lc for building shared libraries. build_libtool_need_lc=$archive_cmds_need_lc # Whether or not to disallow shared libs when runtime libs are static. allow_libtool_libs_with_static_runtimes=$enable_shared_with_static_runtimes # Compiler flag to allow reflexive dlopens. export_dynamic_flag_spec=$lt_export_dynamic_flag_spec # Compiler flag to generate shared objects directly from archives. whole_archive_flag_spec=$lt_whole_archive_flag_spec # Whether the compiler copes with passing no objects directly. compiler_needs_object=$lt_compiler_needs_object # Create an old-style archive from a shared archive. old_archive_from_new_cmds=$lt_old_archive_from_new_cmds # Create a temporary old-style archive to link instead of a shared archive. old_archive_from_expsyms_cmds=$lt_old_archive_from_expsyms_cmds # Commands used to build a shared archive. archive_cmds=$lt_archive_cmds archive_expsym_cmds=$lt_archive_expsym_cmds # Commands used to build a loadable module if different from building # a shared archive. module_cmds=$lt_module_cmds module_expsym_cmds=$lt_module_expsym_cmds # Whether we are building with GNU ld or not. with_gnu_ld=$lt_with_gnu_ld # Flag that allows shared libraries with undefined symbols to be built. allow_undefined_flag=$lt_allow_undefined_flag # Flag that enforces no undefined symbols. no_undefined_flag=$lt_no_undefined_flag # Flag to hardcode \$libdir into a binary during linking. # This must work even if \$libdir does not exist hardcode_libdir_flag_spec=$lt_hardcode_libdir_flag_spec # Whether we need a single "-rpath" flag with a separated argument. hardcode_libdir_separator=$lt_hardcode_libdir_separator # Set to "yes" if using DIR/libNAME\$shared_ext during linking hardcodes # DIR into the resulting binary. hardcode_direct=$hardcode_direct # Set to "yes" if using DIR/libNAME\$shared_ext during linking hardcodes # DIR into the resulting binary and the resulting library dependency is # "absolute",i.e impossible to change by setting \$shlibpath_var if the # library is relocated. hardcode_direct_absolute=$hardcode_direct_absolute # Set to "yes" if using the -LDIR flag during linking hardcodes DIR # into the resulting binary. hardcode_minus_L=$hardcode_minus_L # Set to "yes" if using SHLIBPATH_VAR=DIR during linking hardcodes DIR # into the resulting binary. hardcode_shlibpath_var=$hardcode_shlibpath_var # Set to "yes" if building a shared library automatically hardcodes DIR # into the library and all subsequent libraries and executables linked # against it. hardcode_automatic=$hardcode_automatic # Set to yes if linker adds runtime paths of dependent libraries # to runtime path list. inherit_rpath=$inherit_rpath # Whether libtool must link a program against all its dependency libraries. link_all_deplibs=$link_all_deplibs # Set to "yes" if exported symbols are required. always_export_symbols=$always_export_symbols # The commands to list exported symbols. export_symbols_cmds=$lt_export_symbols_cmds # Symbols that should not be listed in the preloaded symbols. exclude_expsyms=$lt_exclude_expsyms # Symbols that must always be exported. include_expsyms=$lt_include_expsyms # Commands necessary for linking programs (against libraries) with templates. prelink_cmds=$lt_prelink_cmds # Commands necessary for finishing linking programs. postlink_cmds=$lt_postlink_cmds # Specify filename containing input files. file_list_spec=$lt_file_list_spec # How to hardcode a shared library path into an executable. hardcode_action=$hardcode_action # ### END LIBTOOL CONFIG _LT_EOF cat <<'_LT_EOF' >> "$cfgfile" # ### BEGIN FUNCTIONS SHARED WITH CONFIGURE # func_munge_path_list VARIABLE PATH # ----------------------------------- # VARIABLE is name of variable containing _space_ separated list of # directories to be munged by the contents of PATH, which is string # having a format: # "DIR[:DIR]:" # string "DIR[ DIR]" will be prepended to VARIABLE # ":DIR[:DIR]" # string "DIR[ DIR]" will be appended to VARIABLE # "DIRP[:DIRP]::[DIRA:]DIRA" # string "DIRP[ DIRP]" will be prepended to VARIABLE and string # "DIRA[ DIRA]" will be appended to VARIABLE # "DIR[:DIR]" # VARIABLE will be replaced by "DIR[ DIR]" func_munge_path_list () { case x$2 in x) ;; *:) eval $1=\"`$ECHO $2 | $SED 's/:/ /g'` \$$1\" ;; x:*) eval $1=\"\$$1 `$ECHO $2 | $SED 's/:/ /g'`\" ;; *::*) eval $1=\"\$$1\ `$ECHO $2 | $SED -e 's/.*:://' -e 's/:/ /g'`\" eval $1=\"`$ECHO $2 | $SED -e 's/::.*//' -e 's/:/ /g'`\ \$$1\" ;; *) eval $1=\"`$ECHO $2 | $SED 's/:/ /g'`\" ;; esac } # Calculate cc_basename. Skip known compiler wrappers and cross-prefix. func_cc_basename () { for cc_temp in $*""; do case $cc_temp in compile | *[\\/]compile | ccache | *[\\/]ccache ) ;; distcc | *[\\/]distcc | purify | *[\\/]purify ) ;; \-*) ;; *) break;; esac done func_cc_basename_result=`$ECHO "$cc_temp" | $SED "s%.*/%%; s%^$host_alias-%%"` } # ### END FUNCTIONS SHARED WITH CONFIGURE _LT_EOF case $host_os in aix3*) cat <<\_LT_EOF >> "$cfgfile" # AIX sometimes has problems with the GCC collect2 program. For some # reason, if we set the COLLECT_NAMES environment variable, the problems # vanish in a puff of smoke. if test set != "${COLLECT_NAMES+set}"; then COLLECT_NAMES= export COLLECT_NAMES fi _LT_EOF ;; esac ltmain=$ac_aux_dir/ltmain.sh # We use sed instead of cat because bash on DJGPP gets confused if # if finds mixed CR/LF and LF-only lines. Since sed operates in # text mode, it properly converts lines to CR/LF. This bash problem # is reportedly fixed, but why not run on old versions too? sed '$q' "$ltmain" >> "$cfgfile" \ || (rm -f "$cfgfile"; exit 1) mv -f "$cfgfile" "$ofile" || (rm -f "$ofile" && cp "$cfgfile" "$ofile" && rm -f "$cfgfile") chmod +x "$ofile" ;; "perl/annotator/Makefile":C) ( cd perl/annotator; $PERL Makefile.PL $MAKE_MAKER_ARGS ) ;; "perl/imap/Makefile":C) ( cd perl/imap; $PERL Makefile.PL $MAKE_MAKER_ARGS ) ;; "perl/sieve/managesieve/Makefile":C) ( cd perl/sieve/managesieve; $PERL Makefile.PL $MAKE_MAKER_ARGS ) ;; esac done # for ac_tag as_fn_exit 0 _ACEOF ac_clean_files=$ac_clean_files_save test $ac_write_fail = 0 || as_fn_error $? "write failure creating $CONFIG_STATUS" "$LINENO" 5 # configure is writing to config.log, and then calls config.status. # config.status does its own redirection, appending to config.log. # Unfortunately, on DOS this fails, as config.log is still kept open # by configure, so config.status won't be able to write to it; its # output is simply discarded. So we exec the FD to /dev/null, # effectively closing config.log, so it can be properly (re)opened and # appended to by config.status. When coming back to configure, we # need to make the FD available again. if test "$no_create" != yes; then ac_cs_success=: ac_config_status_args= test "$silent" = yes && ac_config_status_args="$ac_config_status_args --quiet" exec 5>/dev/null $SHELL $CONFIG_STATUS $ac_config_status_args || ac_cs_success=false exec 5>>config.log # Use ||, not &&, to avoid exiting from the if with $? = 1, which # would make configure fail if this is the last instruction. $ac_cs_success || as_fn_exit 1 fi if test -n "$ac_unrecognized_opts" && test "$enable_option_checking" != no; then { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: unrecognized options: $ac_unrecognized_opts" >&5 $as_echo "$as_me: WARNING: unrecognized options: $ac_unrecognized_opts" >&2;} fi echo " Cyrus Imapd configured components event notification: $enable_event_notification gssapi: $gssapi autocreate: $enable_autocreate idled: $enable_idled http: $enable_http kerberos V4: $krb4 murder: $enable_murder nntpd: $enable_nntp replication: $enable_replication sieve: $enable_sieve External dependencies: ldap: $have_ldap openssl: $with_ssl pcre: $cyrus_cv_pcre_utf8 Database support: bdb: $use_berkeley mysql: $with_mysql postgresql: $use_pgsql sqlite: $use_sqlite " cyrus-imapd-2.5.10/tools/0000755000175000017500000000000013001246664012177 500000000000000cyrus-imapd-2.5.10/tools/mupdate-loadgen.pl0000755000175000017500000000101213001236020015500 00000000000000#!/usr/bin/perl $prefix = "test.mupdate-load."; $lups = 150; $lookups = 10; srand(time()); @thelist = (); for($i=0; $i<=$lups; $i++) { push @thelist, $prefix . $$ . ".$i"; } $tag = 0; foreach $item (@thelist) { print $tag++ . " RESERVE \"" . $item . "\" \"borked.andrew.cmu.edu\"\r\n"; $todo = int(rand $lookups) + 1; for($i=1; $i<$todo; $i++) { print $tag++ . " FIND \"" . $thelist[int(rand scalar @thelist)] . "\"\r\n"; } } foreach $item (@thelist) { print $tag++ . " DELETE \"" . $item . "\"\r\n"; } cyrus-imapd-2.5.10/tools/dohash0000755000175000017500000001634013001236020013300 00000000000000#!/bin/sh # # Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. # # Redistribution and use in source and binary forms, with or without # modification, are permitted provided that the following conditions # are met: # # 1. Redistributions of source code must retain the above copyright # notice, this list of conditions and the following disclaimer. # # 2. Redistributions in binary form must reproduce the above copyright # notice, this list of conditions and the following disclaimer in # the documentation and/or other materials provided with the # distribution. # # 3. The name "Carnegie Mellon University" must not be used to # endorse or promote products derived from this software without # prior written permission. For permission or any legal # details, please contact # Carnegie Mellon University # Center for Technology Transfer and Enterprise Creation # 4615 Forbes Avenue # Suite 302 # Pittsburgh, PA 15213 # (412) 268-7393, fax: (412) 268-7395 # innovation@andrew.cmu.edu # # 4. Redistributions of any form whatsoever must retain the following # acknowledgment: # "This product includes software developed by Computing Services # at Carnegie Mellon University (http://www.cmu.edu/computing/)." # # CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO # THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY # AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE # FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES # WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN # AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING # OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. exec perl -x -S $0 ${1+"$@"} # -*-perl-*- #!perl -w # script to upgrade from versions of imapd previous to 1.6.2 # make sure you run it as the cyrus user if ($] !~ /^5\..*/) { # uh-oh. this isn't perl 5. foreach (split(/:/, $ENV{PATH})) { # try to find "perl5". exec("$_/perl5", "-x", "-S", $0, @ARGV) if (-x "$_/perl5"); } # we failed. bail. die "Your perl is too old; I need perl 5.\n"; } # load the real script. this is isolated in an 'eval' so perl4 won't # choke on the perl5-isms. eval join("\n", ); if ($@) { die "$@"; } __END__ require 5; $| = 1; if ("-i" eq $ARGV[0]) { $interactive = 1; shift @ARGV; } if ("-f" eq $ARGV[0]) { $force = 1; shift @ARGV; } if ("-h" eq $ARGV[0] || $#ARGV > 0) { print "usage: dohash [-i] [-f] [imapd.conf]\n"; print " -i interactive\n"; print " -f keep going on errors\n"; exit; } sub ouch { my $msg = shift; if ($force) { print "fatal error: $msg\n"; } else { print "error: $msg\n"; exit 1; } } sub read_conf { my $file = shift; open CONF, $file or die "can't open $file"; while () { if (/^#/) { next; } if (/\@include:\s+(.*)$/) { push @configs, $1; } if (/^configdirectory:\s+(.*)$/) { $confdir = $1; } if (/^(?:meta)?partition-.*:\s+(.*)$/) { if (grep /$1/, @parts) { next; } push @parts, $1; } if (/^hashimapspool:\s*(1|t|yes|on)/) { $hashispool = 1; print "i will also hash partitions.\n"; } } close CONF; } $imapdconf = shift || "/etc/imapd.conf"; $yn = "y"; $hashispool = 0; push @configs, $imapdconf; while ($conf = shift @configs) { read_conf($conf); } if (! $confdir) { $confdir = "/var/imap"; } if ($interactive) { print "upgrade $confdir? "; $yn = ; } if ($yn =~ /^y/) { print "upgrading configuration directory $confdir..."; chdir $confdir or die "couldn't change to $confdir"; # *** user subdirectory; holds subscription files print "user "; chdir "user" or die "couldn't change to user subdir"; foreach $i ("a".."z") { mkdir ("$i", 0755) or ouch "couldn't create $i"; } # any remaining sub's go into 'q' opendir (USER, "."); while ($f = readdir USER) { print; if ($f =~ /(.).*\.sub/s) { print; $h = lc($1); if (!($h =~ /[a-z]/)) { $h = 'q'; } rename ($f, "$h/$f") or ouch "couldn't move $f into $h"; } } closedir USER; chdir ".."; # *** quota subdirectory; holds quota files for each quotaroot print "quota "; chdir "quota" or die "couldn't change to quota subdir"; # first, create directories we know can't conflict with existing files foreach $i ("a".."z") { mkdir (".$i", 0755) or ouch "couldn't create .$i"; } # now for each file, move it into the appropriate directory opendir QUOTA, "."; while ($mbox = readdir QUOTA) { if ($mbox =~ /^\./s) { next; } if ($mbox =~ /^.*\.(.).*$/s) { # hash is $1 $h = lc($1); if ($h =~ /[a-z]/) { rename($mbox, ".$h/$mbox") or ouch "couldn't move $mbox into $h"; } else { rename($mbox, ".q/$mbox") or ouch "couldn't move $mbox into q"; } next; } # we should try to hash on the first letter if ($mbox =~ /(.).*/) { $h = lc($1); if ($h =~ /[a-z]/) { rename($mbox, ".$h/$mbox") or ouch "couldn't move $mbox into $h"; } else { rename($mbox, ".q/$mbox") or ouch "couldn't move $mbox into q"; } next; } print "weird mailbox '$mbox'?\n"; } closedir QUOTA; # now move each temporary directory to the right place foreach $i ("a".."z") { rename (".$i", $i) or ouch "couldn't rename $i into place"; } print "done\n"; } # *** now for each data partition while ($part = shift @parts) { if ($interactive) { print "upgrade $part? "; $yn = ; } if ($yn =~ /^y/) { print "upgrading data partition $part..."; chdir $part or die "couldn't chdir to $part"; if ($hashispool) { foreach $i ("a".."z") { mkdir (".$i", 0755) or ouch "couldn't create .$i"; } opendir PART, "."; while ($dir = readdir PART) { if ($dir =~ /^\./s) { next; } if ($dir eq "lost+found") { next; } # process $dir print "$dir "; opendir DIR, $dir; $ismbox = 0; while ($sub = readdir DIR) { if ($sub =~ /^\./s) { next; } # if there's a dot in this, we're a mbox and # this isn't a child if ($sub =~ /(.*)\.(.*)/) { $ismbox = 1; next; } if ($sub =~ /^(.).*$/s) { $h = lc($1); if (!($h =~ /[a-z]/)) { $h = 'q'; } mkdir (".$h/$dir", 0755); # might already be there rename("$dir/$sub", ".$h/$dir/$sub") or ouch "couldn't move $dir/$sub into $h"; } else { print "weird mailbox '$dir/$sub'?\n"; } } closedir DIR; # if $ismbox is set, then $dir is a mailbox of it's own right if ($ismbox && $dir =~ /^(.).*/s) { $h = lc($1); if (!($h =~ /[a-z]/)) { $h = 'q'; } mkdir (".$h/$dir", 0755); # might already be there opendir DIR, $dir; while ($sub = readdir DIR) { if ($sub =~ /^\./s) { next; } rename("$dir/$sub", ".$h/$dir/$sub") or ouch "couldn't move $dir into $h"; } closedir DIR; } rmdir $dir or print "\ncouldn't remove '$dir'??\n"; } closedir PART; foreach $i ("a".."z") { rename (".$i", $i) or ouch "couldn't rename .$i to $i"; } } chdir $part or die "couldn't chdir to $part"; mkdir "stage.", 0755; print "done\n"; } } cyrus-imapd-2.5.10/tools/jenkins-build.sh0000755000175000017500000001713713001236020015206 00000000000000#!/bin/bash # # Copyright (c) 1994-2012 Carnegie Mellon University. All rights reserved. # # Redistribution and use in source and binary forms, with or without # modification, are permitted provided that the following conditions # are met: # # 1. Redistributions of source code must retain the above copyright # notice, this list of conditions and the following disclaimer. # # 2. Redistributions in binary form must reproduce the above copyright # notice, this list of conditions and the following disclaimer in # the documentation and/or other materials provided with the # distribution. # # 3. The name "Carnegie Mellon University" must not be used to # endorse or promote products derived from this software without # prior written permission. For permission or any legal # details, please contact # Carnegie Mellon University # Center for Technology Transfer and Enterprise Creation # 4615 Forbes Avenue # Suite 302 # Pittsburgh, PA 15213 # (412) 268-7393, fax: (412) 268-7395 # innovation@andrew.cmu.edu # # 4. Redistributions of any form whatsoever must retain the following # acknowledgment: # "This product includes software developed by Computing Services # at Carnegie Mellon University (http://www.cmu.edu/computing/)." # # CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO # THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY # AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE # FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES # WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN # AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING # OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. # # # Script to configure and build Cyrus from a new git checkout, # and run some tests. Designed to be used from the Jenkins CI # server as a build script. # function fatal() { echo "$0: $*" 1>&2 exit 1 } ## Ensure $PATH is right PATH=/usr/bin:/bin:/usr/sbin:/usr/local/bin:$PATH echo "==================== CYRUS IMAPD ====================" if [ -n "$JENKINS_HOME" -a -n "$BUILD_ID" -a -n "$WORKSPACE" ] ; then echo "Invoked from Jenkins" CYRUS_SRC="$WORKSPACE/imapd" CYRUS_INST="$WORKSPACE/inst" CASSANDANE_SRC="$WORKSPACE/cassandane" # We want new files to be group-writable # so that the Cassandane tests running # as user 'cyrus' can write them umask 002 else [ -n "$CYRUS_YES_I_KNOW_WHAT_IM_DOING" ] || \ fatal "Do not run $0 manually, use autoreconf -vi ; ./configure ; make" echo "Invoked manually" echo "(assumed, as one of \$JENKINS_HOME \$BUILD_ID or \$WORKSPACE is missing)" BUILD_ID=build$(date +%Y%m%dT%H%M%S) WORKSPACE=$(cd .. ; /bin/pwd) CYRUS_SRC=$(/bin/pwd) CYRUS_INST=$(cd ../inst ; /bin/pwd) CASSANDANE_SRC=$(cd ../cassandane ; /bin/pwd) fi echo "Build ID is $BUILD_ID" echo "Workspace is $WORKSPACE" echo " - Cyrus IMAPD source in $CYRUS_SRC" echo " - Temporary Cyrus IMAPD installation will be in $CYRUS_INST" echo " - Cassandane test suite expected in $CASSANDANE_SRC" TGGCOV=$(which tggcov 2>/dev/null) HISTCOV=$(which git-history-coverage 2>/dev/null) if [ -n "$TGGCOV" -a -x "$TGGCOV" ]; then echo "Found coverage tools, enabling coverage" echo " - tggcov: $TGGCOV" echo " - git-history-coverage: $HISTCOV" COVERAGE=--enable-coverage else echo "No coverage tools found, disabling coverage" echo "(ggcov may be downloaded from ggcov.sourceforge.net)" fi COPTIMISEFLAGS="-O0" CONFIGURE_ARGS="\ --prefix=/usr/cyrus \ --with-cyrus-prefix=/usr/cyrus \ --with-ldap \ --with-openssl \ --disable-event-notification \ --enable-sieve \ --enable-idled \ --enable-nntp \ --enable-murder \ --enable-replication \ --enable-unit-tests \ --enable-maintainer-mode \ $COVERAGE \ " NCPUS=$(grep '^processor' /proc/cpuinfo | wc -l) [ $NCPUS -ge 1 ] || fatal "Can't get number of CPUs" [ -d "$CYRUS_SRC" ] || fatal "$CYRUS_SRC: no such directory" cd "$CYRUS_SRC" || fatal "$CYRUS_SRC: cannot cd" [ -d .git ] || fatal "$CYRUS_SRC: not a git repository" nfiles=$(git ls-files|wc -l) [ $nfiles -gt 0 ] || fatal "$CYRUS_SRC: cannot list git controlled files" BRANCH=$(git branch | sed -n -e 's/^\*[ \t]\+//p') [ -n "$BRANCH" ] || fatal "Can't get git branch" [ "$BRANCH" != "(no branch)" ] || fatal "Not on any git branch" COMMIT=$(git log --pretty='format:%h' HEAD^..HEAD|head -1) [ -n "$COMMIT" ] || fatal "Can't get git top commit" echo "Building on git branch $BRANCH, top commit $COMMIT" CONFIGURE_ARGS="--with-extraident=$BRANCH-$COMMIT $CONFIGURE_ARGS" set -x git ls-files -o git status # do the whole autotools dance [ -f Makefile ] && make maintainer-clean autoreconf -i -f -v || fatal "Can't run autoreconf" [ -f configure ] || fatal "autoconf did not produce a configure script" CFLAGS="-g -W -Wall -Wextra" ./configure $CONFIGURE_ARGS || fatal "Cannot run configure" [ -f config.status ] || fatal "configure did not produce a config.status script" # Tweak makefiles for optimisation flags perl -p -i.orig -e 's/^(CFLAGS\s*=\s*.*)\s+-O2/\1 '"$COPTIMISEFLAGS"'/' $mf $(find . -name Makefile) # Finally the actual build make -j$NCPUS all || fatal "Can't make all" # Run CUnit based unit tests # [ -n "$COVERAGE" ] && find . -name '*.gcda' -exec rm '{}' \; make CUFORMAT=junit check || fatal "Can't make check" # Do a temporary install for Cassandane [ -d $CYRUS_INST.old ] && rm -rf $CYRUS_INST.old [ -d $CYRUS_INST ] && mv -f $CYRUS_INST $CYRUS_INST.old mkdir -p $CYRUS_INST || fatal "$CYRUS_INST: can't mkdir" make DESTDIR=$CYRUS_INST install || fatal "Can't install" exitcode=0 # Run Cassandane tests if [ -d $CASSANDANE_SRC ]; then ## Not needed anymore, user cyrus is in group tomcat # if [ -n "$COVERAGE" ]; then # chmod 666 $(find . -type f -name '*.gcda') # fi # Shoot down any leftover processes - Cassandane sometimes # leaks these under mysterious circumstances. Sadly this means # we cannot run two autobuilds in parallel, oh well :( # The -n is to prevent sudo going interactive. sudo -n /usr/bin/killall -u cyrus # TODO: factor this out into a shell function cd "$CASSANDANE_SRC" || fatal "$CASSANDANE_SRC: cannot cd" [ -d .git ] || fatal "$CASSANDANE_SRC: not a git repository" nfiles=$(git ls-files|wc -l) [ $nfiles -gt 0 ] || fatal "$CASSANDANE_SRC: cannot list git controlled files" git ls-files -o git status make || fatal "Can't make in cassandane/"; # Build cassandane.ini sed -e 's|^##destdir =.*$|destdir = '$CYRUS_INST'|' \ -e 's|^##pwcheck = .*$|pwcheck = sasldb|' \ < cassandane.ini.example \ > cassandane.ini rm -rf reports.old mv -f reports reports.old mkdir -m 0777 reports || fatal "Can't mkdir reports" ./testrunner.pl --cleanup -f xml -v > cass.errs 2>&1 || exitcode=1 [ -x jenkins-xml-summary.pl ] && ./jenkins-xml-summary.pl ${BUILD_URL:+--build-url=$BUILD_URL} # Shoot down leftover processes again ps -u cyrus sudo -n /usr/bin/killall -u cyrus cd "$CYRUS_SRC" fi # Report on coverage # [ -n "$COVERAGE" ] && $TGGCOV --report=summary_all -r . 2>/dev/null [ -n "$COVERAGE" ] && $TGGCOV --report=cobertura -r . 2>/dev/null > coverage.xml # The first line in this file is like # Changes in branch origin/for-upstream, between $SHA and $SHA if [ -n "$JENKINS_HOME" ] ; then revlist=$(perl \ -n \ -e 's/^Changes .*between ([[:xdigit:]]{40}) and ([[:xdigit:]]{40})/\1..\2/; print; exit 0;' \ $WORKSPACE/../builds/$BUILD_ID/changelog.xml \ 2>/dev/null) [ -n "$revlist" ] && $HISTCOV $revlist 2>/dev/null fi exit $exitcode cyrus-imapd-2.5.10/tools/mkimap0000755000175000017500000000731413001236020013311 00000000000000#!/bin/sh # # Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. # # Redistribution and use in source and binary forms, with or without # modification, are permitted provided that the following conditions # are met: # # 1. Redistributions of source code must retain the above copyright # notice, this list of conditions and the following disclaimer. # # 2. Redistributions in binary form must reproduce the above copyright # notice, this list of conditions and the following disclaimer in # the documentation and/or other materials provided with the # distribution. # # 3. The name "Carnegie Mellon University" must not be used to # endorse or promote products derived from this software without # prior written permission. For permission or any legal # details, please contact # Carnegie Mellon University # Center for Technology Transfer and Enterprise Creation # 4615 Forbes Avenue # Suite 302 # Pittsburgh, PA 15213 # (412) 268-7393, fax: (412) 268-7395 # innovation@andrew.cmu.edu # # 4. Redistributions of any form whatsoever must retain the following # acknowledgment: # "This product includes software developed by Computing Services # at Carnegie Mellon University (http://www.cmu.edu/computing/)." # # CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO # THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY # AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE # FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES # WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN # AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING # OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. exec perl -x -S $0 ${1+"$@"} # -*-perl-*- #!perl -w if ($] !~ /^5\..*/) { # uh-oh. this isn't perl 5. foreach (split(/:/, $ENV{PATH})) { # try to find "perl5". exec("$_/perl5", "-x", "-S", $0, @ARGV) if (-x "$_/perl5"); } # we failed. bail. die "Your perl is too old; I need perl 5.\n"; } # load the real script. this is isolated in an 'eval' so perl4 won't # choke on the perl5-isms. eval join("\n", ); if ($@) { die "$@"; } __END__ require 5; sub read_conf { my $file = shift; open CONF, $file or die "can't open $file"; print "reading configure file $file...\n"; while () { if (/^#/) { next; } if (/\@include:\s+(.*)$/) { print "i will include configure file $1.\n"; push @configs, $1; } if (/^configdirectory:\s+(.*)$/) { $confdir = $1; print "i will configure directory $confdir.\n"; } if (/^(?:meta)?partition-.*:\s+(.*)$/) { if (grep /$1/, @parts) { next; } print "i saw partition $1.\n"; push @parts, $1; } } print "done\n"; close CONF; } $imapdconf = shift || "/etc/imapd.conf"; push @configs, $imapdconf; while ($conf = shift @configs) { read_conf($conf); } $d = $confdir; print "configuring $d...\n"; chdir $d or die "couldn't change to $d"; mkdir "proc", 0755 || warn "can't create $d/proc: $!"; mkdir "db", 0755 || warn "can't create $d/db: $!"; mkdir "socket", 0755 || warn "can't create $d/socket: $!"; mkdir "log", 0755 || warn "can't create $d/log: $!"; mkdir "msg", 0755 || warn "can't create $d/msg: $!"; mkdir "ptclient", 0755 || warn "can't create $d/ptclient: $!"; mkdir "sync", 0755 || warn "can't create $d/sync: $!"; while ($part = shift @parts) { print "creating $part...\n"; mkdir $part, 0755 || warn "can't create $part: $!"; chdir $part or die "couldn't change to partition $part"; mkdir "stage.", 0755 || warn "can't create $part/stage.: $!"; mkdir "sync.", 0755 || warn "can't create $part/sync.: $!"; } print "done\n"; cyrus-imapd-2.5.10/tools/migrate-metadata0000755000175000017500000001226213001236020015237 00000000000000#!/bin/sh # # Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. # # Redistribution and use in source and binary forms, with or without # modification, are permitted provided that the following conditions # are met: # # 1. Redistributions of source code must retain the above copyright # notice, this list of conditions and the following disclaimer. # # 2. Redistributions in binary form must reproduce the above copyright # notice, this list of conditions and the following disclaimer in # the documentation and/or other materials provided with the # distribution. # # 3. The name "Carnegie Mellon University" must not be used to # endorse or promote products derived from this software without # prior written permission. For permission or any legal # details, please contact # Carnegie Mellon University # Center for Technology Transfer and Enterprise Creation # 4615 Forbes Avenue # Suite 302 # Pittsburgh, PA 15213 # (412) 268-7393, fax: (412) 268-7395 # innovation@andrew.cmu.edu # # 4. Redistributions of any form whatsoever must retain the following # acknowledgment: # "This product includes software developed by Computing Services # at Carnegie Mellon University (http://www.cmu.edu/computing/)." # # CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO # THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY # AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE # FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES # WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN # AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING # OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. exec perl -x -S $0 ${1+"$@"} # -*-perl-*- #!perl -w # script to upgrade from versions of imapd previous to 1.6.2 # make sure you run it as the cyrus user if ($] !~ /^5\..*/) { # uh-oh. this isn't perl 5. foreach (split(/:/, $ENV{PATH})) { # try to find "perl5". exec("$_/perl5", "-x", "-S", $0, @ARGV) if (-x "$_/perl5"); } # we failed. bail. die "Your perl is too old; I need perl 5.\n"; } # load the real script. this is isolated in an 'eval' so perl4 won't # choke on the perl5-isms. eval join("\n", ); if ($@) { die "$@"; } __END__ require 5; use File::Copy $| = 1; if ($#ARGV > -1 && "-i" eq $ARGV[0]) { $interactive = 1; shift @ARGV; } if ($#ARGV > -1 && "-f" eq $ARGV[0]) { $force = 1; shift @ARGV; } if (($#ARGV > -1 && "-h" eq $ARGV[0]) || $#ARGV > 0) { print "usage: migrate-metadata [-i] [-f] [imapd.conf]\n"; print " -i interactive\n"; print " -f keep going on errors\n"; exit; } sub ouch { my $msg = shift; if ($force) { print "fatal error: $msg\n"; } else { print "error: $msg\n"; exit 1; } } sub read_conf { my $file = shift; open CONF, $file or die "can't open $file"; print "reading configure file $file...\n"; while () { if (/^#/) { next; } if (/\@include:\s+(.*)$/) { push @configs, $1; } if (/^partition-(.*):\s*(.*)$/) { $parts{$1} = $2; } if (/^metapartition-(.*):\s*(.*)$/) { $mparts{$1} = $2; } if (/^metapartition_files:\s*(.*)$/) { # split the list of files and make a hash @metafiles = split(/\s+/, $1); foreach $file (@metafiles) { $mfiles{$file} = 1; } } } print "done\n"; close CONF; } $imapdconf = shift || "/etc/imapd.conf"; $yn = "y"; %parts = (); # start with empty partition hash %mparts = (); # start with empty metapartition hash %mfiles = (); # start with empty metapartition_files hash push @configs, $imapdconf; while ($conf = shift @configs) { read_conf($conf); } if (!keys(%mfiles)) { print "no metapartition_files option in $imapdconf\n"; exit 1; } # process each subdir, recursing if necessary sub migrate { my $part = shift; my $mpart = shift; my $path = shift; local *DIR; opendir DIR, $part . $path; while ($subdir = readdir DIR) { my $subpath = $path . "/" . $subdir; # skip message files, '.' and '..' next if ( $subdir =~ /^[0-9]+\.$/ || $subdir =~ /^\.\.$/ || $subdir =~ /^\.$/ ); # skip special subdirs next if ( $subpath =~ /^\/socket$/ || $subpath =~ /^\/stage\.$/ || $subpath =~ /^\/sync\.$/ ); if ($subdir =~ /^cyrus\.(.+)/s) { # cyrus.* file, see if we should migrate it if (defined($mfiles{$1})) { copy($part . $subpath, $mpart . $subpath) || ouch "couldn't copy $part$subpath to $mpart$subpath"; unlink($part . $subpath) || ouch "couldn't delete $part$subpath"; } } else { # this is a mailbox subdir, process it mkdir($mpart . $subpath, 0700) || ouch "couldn't create $mpart$subpath"; migrate($part, $mpart, $subpath); } } closedir DIR; } # *** now for each data partition while (($name,$part) = each(%parts)) { my $mpart = $mparts{$name}; if (!defined($mpart)) { next; } # no corresponding metapartition, skip it if ($interactive) { print "upgrade $part? "; $yn = ; } if ($yn =~ /^y/) { print "upgrading data partition $part..."; migrate($part, $mpart, ""); } print "done\n"; } cyrus-imapd-2.5.10/tools/fixsearchpath.pl0000755000175000017500000000727613001236020015305 00000000000000#!/usr/bin/perl # # Copyright (c) 1994-2012 Carnegie Mellon University. All rights reserved. # # Redistribution and use in source and binary forms, with or without # modification, are permitted provided that the following conditions # are met: # # 1. Redistributions of source code must retain the above copyright # notice, this list of conditions and the following disclaimer. # # 2. Redistributions in binary form must reproduce the above copyright # notice, this list of conditions and the following disclaimer in # the documentation and/or other materials provided with the # distribution. # # 3. The name "Carnegie Mellon University" must not be used to # endorse or promote products derived from this software without # prior written permission. For permission or any legal # details, please contact # Carnegie Mellon University # Center for Technology Transfer and Enterprise Creation # 4615 Forbes Avenue # Suite 302 # Pittsburgh, PA 15213 # (412) 268-7393, fax: (412) 268-7395 # innovation@andrew.cmu.edu # # 4. Redistributions of any form whatsoever must retain the following # acknowledgment: # "This product includes software developed by Computing Services # at Carnegie Mellon University (http://www.cmu.edu/computing/)." # # CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO # THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY # AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE # FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES # WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN # AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING # OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. # use strict; use warnings; use Config; sub normalise { my $s = shift; $s =~ s/\/+$//; return $s; } sub quote { my $s = shift; return "'$s'"; } sub usage { die "Usage: $0 cyrus_prefix cyrus_bindir"; } my $cyrus_prefix = normalise(shift || usage); my $cyrus_bindir = normalise(shift || usage); my $perl_prefix = normalise($Config{prefix}); # These directories are listed in the reverse of the order that we want # them searched, assuming that we will emit multiple "use lib" # directives each of which *prepends* its argument to @INC. my @dirvars = ( { dir => 'installvendorlib', prefix => 'vendorprefix' }, { dir => 'installvendorarch', prefix => 'vendorprefix' }, { dir => 'installsitelib', prefix => 'siteprefix' }, { dir => 'installsitearch', prefix => 'siteprefix' }, ); my $boilerplate = << 'EOT' ## Boilerplate added by Cyrus fixsearchpath.pl my $__cyrus_destdir = ''; BEGIN { if ($0 =~ m/\//) { my $d = $0; EOT ; $boilerplate .= " my \$bindir = " . quote($cyrus_bindir) . ";\n"; $boilerplate .= << 'EOT' # remove the filename, $d is now the installed bindir $d =~ s/\/[^\/]+$//; # check if the path ends in the configured bindir my $len = length($d)-length($bindir); if (substr($d, $len) eq $bindir) { # if so then the installed destdir is what remains $__cyrus_destdir = substr($d, 0, $len); } } }; EOT ; foreach my $dv (@dirvars) { my $dir = $Config{$dv->{dir}}; if ($cyrus_prefix ne $perl_prefix) { # Expect to be installed into a non-default location # because Cyrus was built with a non-default --prefix my $install_prefix = normalise($Config{$dv->{prefix}}); $dir = $cyrus_prefix . substr($dir, length($install_prefix)) } $boilerplate .= 'use lib $__cyrus_destdir . ' . quote($dir) . ";\n"; } $boilerplate .= "##\n\n"; # Filter stdin to stdout while () { if (defined $boilerplate && m/^use\s/) { print $boilerplate; $boilerplate = undef; } print $_; } cyrus-imapd-2.5.10/tools/config2header0000755000175000017500000002041513001236020014530 00000000000000#!/bin/sh # # Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. # # Redistribution and use in source and binary forms, with or without # modification, are permitted provided that the following conditions # are met: # # 1. Redistributions of source code must retain the above copyright # notice, this list of conditions and the following disclaimer. # # 2. Redistributions in binary form must reproduce the above copyright # notice, this list of conditions and the following disclaimer in # the documentation and/or other materials provided with the # distribution. # # 3. The name "Carnegie Mellon University" must not be used to # endorse or promote products derived from this software without # prior written permission. For permission or any legal # details, please contact # Carnegie Mellon University # Center for Technology Transfer and Enterprise Creation # 4615 Forbes Avenue # Suite 302 # Pittsburgh, PA 15213 # (412) 268-7393, fax: (412) 268-7395 # innovation@andrew.cmu.edu # # 4. Redistributions of any form whatsoever must retain the following # acknowledgment: # "This product includes software developed by Computing Services # at Carnegie Mellon University (http://www.cmu.edu/computing/)." # # CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO # THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY # AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE # FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES # WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN # AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING # OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. exec perl -x -S $0 ${1+"$@"} # -*-perl-*- #!perl -w if ($] !~ /^5\..*/) { # uh-oh. this isn't perl 5. foreach (split(/:/, $ENV{PATH})) { # try to find "perl5". exec("$_/perl5", "-x", "-S", $0, @ARGV) if (-x "$_/perl5"); } # we failed. bail. die "Your perl is too old; I need perl 5.\n"; } # load the real script. this is isolated in an 'eval' so perl4 won't # choke on the perl5-isms. eval join("\n", ); if ($@) { die "$@"; } __END__ require 5; use strict; my $enum_size = 0; my @enum_values = (); my $CC; # # Look for CC=xxx "assigments" in the argument list. # while ($#ARGV >= 0) { last unless ($ARGV[0] =~ m/^(\S+)=(.*)$/); eval "\$$1='$2';"; die "$@" if ($@); shift @ARGV; } my $use_gcc_extension = ($CC and $CC eq 'gcc'); die "wrong number of arguments" if ($#ARGV != 1); my ($cfile, $hfile) = @ARGV; open CFILE, ">$cfile"; open HFILE, ">$hfile"; my $blank = ""; my $version = "\$Revision: 1.17 $blank"; $version =~ s/.Revision: (.*) /$1/; print HFILE "/* auto-generated by config2header $version */\n"; print CFILE "/* auto-generated by config2header $version */\n"; print HFILE "#ifndef INCLUDED_IMAPOPTS_H\n"; print HFILE "#define INCLUDED_IMAPOPTS_H\n"; print HFILE "\n"; # prototypes my @opttype = ("OPT_NOTOPT","OPT_STRING","OPT_INT","OPT_SWITCH", "OPT_ENUM","OPT_STRINGLIST","OPT_BITFIELD"); print HFILE "enum opttype {\n"; while (my $opt = pop (@opttype)) { if ($#opttype == -1) { print HFILE " $opt\n"; } else { print HFILE " $opt,\n"; } } print HFILE "};\n\n"; print HFILE < #include #ifdef HAVE_UNISTD_H #include #endif #include #include #include "imapopts.h" /* * Sun C Compilers are more strict than GNU and won't allow type * casting to a union */ #if defined(__SUNPRO_C) || defined(__SUNPRO_CC) #define U_CFG_V #else #define U_CFG_V (union config_value) #endif EXPORTED struct imapopt_s imapopts[] = { { IMAPOPT_ZERO, "", 0, OPT_NOTOPT, { NULL }, { NULL }, { { NULL, IMAP_ENUM_ZERO } } }, EOF ; # output enumeration while () { next if (/^\#/); # look for { option, default, type [enums] } # Note that the code we output has to play interesting games to get # the union to initialize itself in a syntacticly valid manner. # Namely, we need to initialize the union itself, not the members of # the union, and we need to ensure we are initilizing the union with # something of a type that is in the union. if (m|{\s*\"(.*?)\"\s*,\s*(\"?.*?\"?)\s*,\s*(.*?)\s*(\(.*\))?\s*}|) { my $opt = $1; my $def; my $enums = ""; print HFILE " IMAPOPT_", uc($opt), ",\n"; if ($3 eq "STRING") { $def = $use_gcc_extension ? "U_CFG_V((const char *) $2)" : "{(void *)($2)}"; } elsif ($3 eq "ENUM") { my @values = eval $4; my $e; my $v; my $count = 0; # strip quotes from default value $def = substr($2, 1, -1); $e = "IMAP_ENUM_" . uc($opt) . "_" . uc($def); $e =~ s/[^0-9A-Z_a-z]/_/g; $def = $use_gcc_extension ? "U_CFG_V((enum enum_value) $e)" : "{(void *)($e)}"; # output the enum_options foreach $v (@values) { $e = "IMAP_ENUM_" . uc($opt) . "_" . uc($v); $e =~ s/[^0-9A-Z_a-z]/_/g; $enums .= " { \"$v\" , $e },\n "; # if this is the first enum value, normalize to zero if (!$count) { $e .= " = 0"; } # add this enum to enum_values push(@enum_values, $e); $count += 1; # count the number of values } # [re]set the size of the enum_options array if ($count > $enum_size) { $enum_size = $count; } } elsif ($3 eq "STRINGLIST") { my @values = eval $4; my $v; my $count = 0; $def = $use_gcc_extension ? "U_CFG_V((const char *) $2)" : "{(void*)($2)}"; # output the enum_options foreach $v (@values) { $enums .= " { \"$v\" , IMAP_ENUM_ZERO },\n "; $count += 1; # count the number of values } # [re]set the size of the enum_options array if ($count > $enum_size) { $enum_size = $count; } } elsif ($3 eq "BITFIELD") { my @values; my $e; my $v; my $count = 0; # strip quotes from default value $def = substr($2, 1, -1); # build the bitwise-or of the defaults @values = split(' ', $def); $e = ""; foreach $v (@values) { my $ev = "IMAP_ENUM_" . uc($opt) . "_" . uc($v); $ev =~ s/[^0-9A-Z_a-z]/_/g; $e .= "$ev\n\t\t\t | "; } $e .= "0"; $def = $use_gcc_extension ? "U_CFG_V((unsigned long) $e)" : "{(void *)($e)}"; # output the enum_options @values = eval $4; foreach $v (@values) { $e = "IMAP_ENUM_" . uc($opt) . "_" . uc($v); $e =~ s/[^0-9A-Z_a-z]/_/g; $enums .= " { \"$v\" , $e },\n "; # add the corresponding bit value $e .= " = (1<<$count)"; # add this enum to enum_values push(@enum_values, $e); $count += 1; # count the number of values } # [re]set the size of the enum_options array if ($count > $enum_size) { $enum_size = $count; } } else { $def = $use_gcc_extension ? "U_CFG_V((long) $2)" : "{(void*)$2}"; } print CFILE " { IMAPOPT_", uc($opt), ", \"$1\", 0, OPT_$3,\n", " $def,\n $def,\n {$enums { NULL, IMAP_ENUM_ZERO } } },\n"; } else { #chomp; #print "rejected '$_'\n"; } } print HFILE <); if ($@) { die "$@"; } __END__ require 5; $| = 1; if (($#ARGV > -1) && ("-f" eq $ARGV[0])) { $force = 1; shift @ARGV; } if ((($#ARGV > -1) && ($ARGV[0] eq "-h")) || ($#ARGV > 0)) { print "usage: upgradesieve [-f] [imapd.conf]\n"; print " -f keep going on errors\n"; exit; } sub ouch { my $msg = shift; if ($force) { print "error: $msg\n"; } else { print "fatal error: $msg\n"; exit 1; } } sub read_conf { my $file = shift; open CONF, $file or die "can't open $file"; while () { if (/^#/) { next; } if (/\@include:\s+(.*)$/) { push @configs, $1; } if (/^sievedir:\s+(.*)$/) { $sievedir = $1; print "you are using $sievedir as your sieve directory.\n"; } } close CONF; } $imapdconf = shift || "/etc/imapd.conf"; $sievedir = "/usr/sieve"; push @configs, $imapdconf; while ($conf = shift @configs) { read_conf($conf); } print "upgrading sievedir $sievedir..."; chdir $sievedir or die "couldn't change to $sievedir"; foreach $i ("a".."z") { print "$i "; if (! chdir $i) { ouch "couldn't chdir to $i"; next; } # upgrade single file to directory opendir (D, "."); while ($f = readdir D) { next if ($f =~ /^\./s); next if (-d $f); rename($f, ".$f") or ouch "couldn't move $f to .$f"; mkdir ($f, 0755) or ouch "couldn't mkdir $f"; rename(".$f", "$f/$f.script") or ouch "couldn't move .$f to $f/$f.script"; link("$f/$f.script", "$f/default") or ouch "couldn't link $f.script to default"; } closedir D; # upgrade hard links to symlinks opendir (D, "."); while ($d = readdir D) { next if ($d =~ /^\./s); if (! -d $d) { ouch "expected $d to be a directory"; next; } if (! chdir $d) { ouch "couldn't chdir to $d"; next; } opendir DIR, "."; while ($file = readdir DIR) { next if (!($file =~ /\.script$/)); # print "considering $file... "; ($dev, $ino, $mode, $nlink, @rest) = stat $file; if ($nlink == 2) { # print "making active... "; symlink $file, "default.NEW"; rename "default.NEW", "default"; } # print "\n"; } closedir DIR; chdir ".."; } closedir D; # back to "/usr/sieve" chdir ".."; } print "done\n"; cyrus-imapd-2.5.10/tools/vzic/0000755000175000017500000000000013001246664013152 500000000000000cyrus-imapd-2.5.10/tools/vzic/vzic-dump.c0000644000175000017500000002412213001236020015136 00000000000000/* * Vzic - a program to convert Olson timezone database files into VZTIMEZONE * files compatible with the iCalendar specification (RFC2445). * * Copyright (C) 2000-2001 Ximian, Inc. * Copyright (C) 2003 Damon Chaplin. * * Author: Damon Chaplin * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307, USA. */ /* * These functions are for dumping all the parsed Zones and Rules to * files, to be compared with the output of vzic-dump.pl to check our parsing * code is OK. Some of the functions are also used for producing debugging * output. */ #include #include #include #include "vzic.h" #include "vzic-dump.h" static void dump_add_rule (char *name, GArray *rule_array, GPtrArray *name_array); static int dump_compare_strings (const void *arg1, const void *arg2); void dump_zone_data (GArray *zone_data, char *filename) { static char *months[] = { "Jan", "Feb", "Mar", "Apr", "May", "Jun", "Jul", "Aug", "Sep", "Oct", "Nov", "Dec" }; FILE *fp; ZoneData *zone; ZoneLineData *zone_line; int i, j; gboolean output_month, output_day, output_time; fp = fopen (filename, "w"); if (!fp) { fprintf (stderr, "Couldn't create file: %s\n", filename); exit (1); } for (i = 0; i < zone_data->len; i++) { zone = &g_array_index (zone_data, ZoneData, i); fprintf (fp, "Zone\t%s\t", zone->zone_name); for (j = 0; j < zone->zone_line_data->len; j++) { zone_line = &g_array_index (zone->zone_line_data, ZoneLineData, j); if (j != 0) fprintf (fp, "\t\t\t"); fprintf (fp, "%s\t", dump_time (zone_line->stdoff_seconds, TIME_WALL, FALSE)); if (zone_line->rules) fprintf (fp, "%s\t", zone_line->rules); else if (zone_line->save_seconds != 0) fprintf (fp, "%s\t", dump_time (zone_line->save_seconds, TIME_WALL, FALSE)); else fprintf (fp, "-\t"); fprintf (fp, "%s\t", zone_line->format ? zone_line->format : "-"); if (zone_line->until_set) { fprintf (fp, "%s\t", dump_year (zone_line->until_year)); output_month = output_day = output_time = FALSE; if (zone_line->until_time_code != TIME_WALL || zone_line->until_time_seconds != 0) output_month = output_day = output_time = TRUE; else if (zone_line->until_day_code != DAY_SIMPLE || zone_line->until_day_number != 1) output_month = output_day = TRUE; else if (zone_line->until_month != 0) output_month = TRUE; if (output_month) fprintf (fp, "%s", months[zone_line->until_month]); fprintf (fp, "\t"); if (output_day) fprintf (fp, "%s", dump_day_coded (zone_line->until_day_code, zone_line->until_day_number, zone_line->until_day_weekday)); fprintf (fp, "\t"); if (output_time) fprintf (fp, "%s", dump_time (zone_line->until_time_seconds, zone_line->until_time_code, FALSE)); } else { fprintf (fp, "\t\t\t"); } fprintf (fp, "\n"); } } fclose (fp); } void dump_rule_data (GHashTable *rule_data, char *filename) { FILE *fp; GPtrArray *name_array; GArray *rule_array; int i; char *name; fp = fopen (filename, "w"); if (!fp) { fprintf (stderr, "Couldn't create file: %s\n", filename); exit (1); } /* We need to sort the rules by their names, so they are in the same order as the Perl output. So we place all the names in a temporary GPtrArray, sort it, then output them. */ name_array = g_ptr_array_new (); g_hash_table_foreach (rule_data, (GHFunc) dump_add_rule, name_array); qsort (name_array->pdata, name_array->len, sizeof (char*), dump_compare_strings); for (i = 0; i < name_array->len; i++) { name = g_ptr_array_index (name_array, i); rule_array = g_hash_table_lookup (rule_data, name); if (!rule_array) { fprintf (stderr, "Couldn't access rules: %s\n", name); exit (1); } dump_rule_array (name, rule_array, fp); } g_ptr_array_free (name_array, TRUE); fclose (fp); } static void dump_add_rule (char *name, GArray *rule_array, GPtrArray *name_array) { g_ptr_array_add (name_array, name); } static int dump_compare_strings (const void *arg1, const void *arg2) { char **a, **b; a = (char**) arg1; b = (char**) arg2; return strcmp (*a, *b); } void dump_rule_array (char *name, GArray *rule_array, FILE *fp) { static char *months[] = { "Jan", "Feb", "Mar", "Apr", "May", "Jun", "Jul", "Aug", "Sep", "Oct", "Nov", "Dec" }; RuleData *rule; int i; #if 0 fprintf (fp, "\n# Rule NAME FROM TO TYPE IN ON AT SAVE LETTER/S"); #endif for (i = 0; i < rule_array->len; i++) { rule = &g_array_index (rule_array, RuleData, i); fprintf (fp, "Rule\t%s\t%s\t", name, dump_year (rule->from_year)); if (rule->to_year == rule->from_year) fprintf (fp, "only\t"); else fprintf (fp, "%s\t", dump_year (rule->to_year)); fprintf (fp, "%s\t", rule->type ? rule->type : "-"); fprintf (fp, "%s\t", months[rule->in_month]); fprintf (fp, "%s\t", dump_day_coded (rule->on_day_code, rule->on_day_number, rule->on_day_weekday)); fprintf (fp, "%s\t", dump_time (rule->at_time_seconds, rule->at_time_code, FALSE)); fprintf (fp, "%s\t", dump_time (rule->save_seconds, TIME_WALL, TRUE)); fprintf (fp, "%s", rule->letter_s ? rule->letter_s : "-"); fprintf (fp, "\n"); } } char* dump_time (int seconds, TimeCode time_code, gboolean use_zero) { static char buffer[256], *sign; int hours, minutes; char *code; if (time_code == TIME_STANDARD) code = "s"; else if (time_code == TIME_UNIVERSAL) code = "u"; else code = ""; if (seconds < 0) { seconds = -seconds; sign = "-"; } else { sign = ""; } hours = seconds / 3600; minutes = (seconds % 3600) / 60; seconds = seconds % 60; if (use_zero && hours == 0 && minutes == 0 && seconds == 0) return "0"; else if (seconds == 0) sprintf (buffer, "%s%i:%02i%s", sign, hours, minutes, code); else sprintf (buffer, "%s%i:%02i:%02i%s", sign, hours, minutes, seconds, code); return buffer; } char* dump_day_coded (DayCode day_code, int day_number, int day_weekday) { static char buffer[256]; static char *weekdays[] = { "Sun", "Mon", "Tue", "Wed", "Thu", "Fri", "Sat" }; switch (day_code) { case DAY_SIMPLE: sprintf (buffer, "%i", day_number); break; case DAY_WEEKDAY_ON_OR_AFTER: sprintf (buffer, "%s>=%i", weekdays[day_weekday], day_number); break; case DAY_WEEKDAY_ON_OR_BEFORE: sprintf (buffer, "%s<=%i", weekdays[day_weekday], day_number); break; case DAY_LAST_WEEKDAY: sprintf (buffer, "last%s", weekdays[day_weekday]); break; default: fprintf (stderr, "Invalid day code: %i\n", day_code); exit (1); } return buffer; } char* dump_year (int year) { static char buffer[256]; if (year == YEAR_MINIMUM) return "min"; if (year == YEAR_MAXIMUM) return "max"; sprintf (buffer, "%i", year); return buffer; } void dump_time_zone_names (GList *names, char *output_dir, GHashTable *zones_hash) { char filename[PATHNAME_BUFFER_SIZE], *zone_name, *zone_name_in_hash = NULL; char strings_filename[PATHNAME_BUFFER_SIZE]; FILE *fp, *strings_fp = NULL; GList *elem; ZoneDescription *zone_desc; sprintf (filename, "%s/zones.tab", output_dir); sprintf (strings_filename, "%s/zones.h", output_dir); fp = fopen (filename, "w"); if (!fp) { fprintf (stderr, "Couldn't create file: %s\n", filename); exit (1); } if (VzicDumpZoneTranslatableStrings) { strings_fp = fopen (strings_filename, "w"); if (!strings_fp) { fprintf (stderr, "Couldn't create file: %s\n", strings_filename); exit (1); } } names = g_list_sort (names, (GCompareFunc) strcmp); elem = names; while (elem) { zone_name = (char*) elem->data; zone_desc = g_hash_table_lookup (zones_hash, zone_name); /* SPECIAL CASES: These timezones are links from other zones and are almost exactly the same - they are basically there so users can find them a bit easier. But they don't have entries in the zone.tab file, so we use the entry from the timezone linked from. */ if (!zone_desc) { if (!strcmp (zone_name, "America/Indiana/Indianapolis")) zone_name_in_hash = "America/Indianapolis"; else if (!strcmp (zone_name, "America/Kentucky/Louisville")) zone_name_in_hash = "America/Louisville"; else if (!strcmp (zone_name, "Asia/Istanbul")) zone_name_in_hash = "Europe/Istanbul"; else if (!strcmp (zone_name, "Europe/Nicosia")) zone_name_in_hash = "Asia/Nicosia"; if (zone_name_in_hash) zone_desc = g_hash_table_lookup (zones_hash, zone_name_in_hash); } if (zone_desc) { fprintf (fp, "%+04i%02i%02i %+04i%02i%02i %s\n", zone_desc->latitude[0], zone_desc->latitude[1], zone_desc->latitude[2], zone_desc->longitude[0], zone_desc->longitude[1], zone_desc->longitude[2], zone_name); } else { g_print ("Zone description not found for: %s\n", zone_name); fprintf (fp, "%s\n", zone_name); } if (VzicDumpZoneTranslatableStrings) { #if 0 char zone_name_buffer[1024], *src, *dest; for (src = zone_name, dest = zone_name_buffer; *src; src++, dest++) *dest = (*src == '_') ? ' ' : *src; *dest = '\0'; #endif fprintf (strings_fp, "N_(\"%s\");\n", zone_name); } elem = elem->next; } fclose (fp); if (VzicDumpZoneTranslatableStrings) fclose (strings_fp); } cyrus-imapd-2.5.10/tools/vzic/vzic-output.h0000644000175000017500000000247213001236020015542 00000000000000/* * Vzic - a program to convert Olson timezone database files into VZTIMEZONE * files compatible with the iCalendar specification (RFC2445). * * Copyright (C) 2000-2001 Ximian, Inc. * Copyright (C) 2003 Damon Chaplin. * * Author: Damon Chaplin * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307, USA. */ #ifndef _VZIC_OUTPUT_H_ #define _VZIC_OUTPUT_H_ #include void output_vtimezone_files (char *directory, GArray *zone_data, GHashTable *rule_data, GHashTable *link_data, GHashTable *zones_hash, int max_until_year); void ensure_directory_exists (char *directory); #endif /* _VZIC_OUTPUT_H_ */ cyrus-imapd-2.5.10/tools/vzic/README0000644000175000017500000001617713001236020013747 00000000000000 VZIC README =========== This is 'vzic', a program to convert the Olson timezone database files into VTIMEZONE files compatible with the iCalendar specification (RFC2445). (The name is based on the 'zic' program which converts the Olson files into time zone information files used by several Unix C libraries, including glibc. See zic(8) and tzfile(5).) REQUIREMENTS ============ You need the Olson timezone database files, which can be found at: ftp://elsie.nci.nih.gov/pub/ (Old versions can be found at ftp://munnari.oz.au/pub/oldtz/) Vzic also uses the GLib library (for hash tables, dynamic arrays, and date calculations). You need version 2.0 or higher. You can get this from: http://www.gtk.org BUILDING ======== Edit the Makefile to set the OLSON_DIR, PRODUCT_ID and TZID_PREFIX variables. Then run 'make'. RUNNING ======= Run 'vzic'. The output is placed in the zoneinfo subdirectory by default, but you can use the --output-dir options to set another toplevel output directory. By default it outputs VTIMEZONEs that try to be compatible with Outlook (2000, at least). Outlook can't handle certain iCalendar constructs in VTIMEZONEs, such as RRULEs using BYMONTHDAY, so it has to adjust the RRULEs slightly to get Outlook to parse them. Unfortunately this means they are slightly wrong. If given the --pure option, vzic outputs the exact data, without worrying about compatability. NOTE: We don't convert all the Olson files. We skip 'backward', 'etcetera', 'leapseconds', 'pacificnew', 'solar87', 'solar88' and 'solar89', 'factory' and 'systemv', since these don't really provide any useful timezones. See vzic.c. MERGING CHANGES INTO A MASTER SET OF VTIMEZONES =============================================== The Olson timezone files are updated fairly often, so we need to build new sets of VTIMEZONE files. Though we have to be careful to ensure that the TZID of updated timezones is also updated, since it must remain unique. We use a version number on the end of the TZID prefix (see the TZIDPrefix variable in vzic-output.c) to ensure this uniqueness. But we don't want to update the version numbers of VTIMEZONEs which have not changed. So we use the vzic-merge.pl Perl script. This merges in the new set of VTIMEZONEs with a 'master' set. It compares each new VTIMEZONE file with the one in the master set (ignoring changes to the TZID). If the new VTIMEZONE file is different, it copies it to the master set and sets the version number to the old VTIMEZONE's version number + 1. To use vzic-merge.pl you must change the $MASTER_ZONEINFO_DIR and $NEW_ZONEINFO_DIR variables at the top of the file to point to your 2 sets of VTIMEZONEs. You then just run the script. (I recommend you keep a backup of the old master VTIMEZONE files, and use diff to compare the new master set with the old one, in case anything goes wrong.) You must merge in changes to the zones.tab file by hand. Note that some timezones are renamed or removed occasionally, so applications should be able to cope with this. COMPATABILITY NOTES =================== It seems that Microsoft Outlook is very picky about the iCalendar files it will accept. (I've been testing with Outlook 2000. I hope the other versions are no worse.) Here's a few problems we've had with the VTIMEZONEs: o Outlook doesn't like any years before 1600. We were using '1st Jan 0001' in all VTIMEZONEs to specify the first UTC offset known for the timezone. (The Olson data does not give a start date for this.) Now we just skip this first component for most timezones. The UTC offset can still be found from the TZOFFSETFROM property of the first component. Though some timezones only specify one UTC offset that applies forever, so in these cases we output '1st Jan 1970' (Indian/Cocos, Pacific/Johnston). o Outlook doesn't like the BYMONTHDAY specifier in RRULEs. We have changed most of the VTIMEZONEs to use things like 'BYDAY=2SU' rather than 'BYMONTHDAY=8,9,10,11,12,13,14;BYDAY=SU', though some of them were impossible to convert correctly so they are not always correct. o Outlook doesn't like TZOFFSETFROM/TZOFFSETTO properties which include a seconds component, e.g. 'TZOFFSETFROM:+110628'. Quite a lot of the Olson timezones include seconds in their UTC offsets, though no timezones currently have a UTC offset that uses the seconds value. We've rounded all UTC offsets to the nearest minute. Since all timezone offsets currently used have '00' as the seconds offset, this doesn't lose us much. o Outlook doesn't like lines being split in certain places, even though the iCalendar spec says they can be split anywhere. o Outlook can only handle one RDATE or a pair of RRULEs. So we had to remove all historical data. TESTING ======= Do a 'make test-vic', then run ./test-vic. The test-vzic program compares our libical code and VTIMEZONE data against the Unix functions like mktime(). It steps over a period of time (1970-2037) converting from UTC to a given timezone and back again every 15 minutes. Any differences are output into the test-output directory. The output matches for all of the timezones, except in a few places where the result can't be determined. So I think we can be fairly confident that the VTIMEZONEs are correct. Note that you must use the same Olson data in libical that the OS is using for mktime() etc. For example, I am using RedHat 9 which uses tzdata2002d, so I converted this to VTIMEZONE files and installed it into the libical timezone data directory before testing. (You need to use '--pure' when creating the VTIMEZONE files as well.) Testing the Parsing Code ------------------------ Run 'make test-parse'. This runs 'vzic --dump' and 'perl-dump' and compares the output. The diff commands should not produce any output. 'vzic --dump' dumps all the parsed data out in the original Olson format, but without comments. The files are written into the ZonesVzic and RulesVzic subdirectories of the zoneinfo directory. 'make perl-dump' runs the vzic-dump.pl perl script which outputs the files in the same format as 'vzic --dump' in the ZonesPerl and RulesPerl subdirectories. The perl script doesn't actually parse the fields; it only strips comments and massages the fields so we have the same output format. Currently they both produce exactly the same output so we know the parsing code is OK. Testing the VTIMEZONE Files --------------------------- Run 'make test-changes'. This runs 'vzic --dump-changes' and 'test-vzic --dump-changes' and compares the output. The diff command should not produce any output. Both commands output timezone changes for each zone up to a specific year (2030) into files for each timezone. It outputs the timezone changes in a list in this format: Timezone Name Date and Time of Change in UTC New Offset from UTC America/Dawson 26 Oct 1986 2:00:00 -0800 Unfortunately there are some differences here, but they all happen before 1970 so it doesn't matter too much. It looks like the libical code has problems determining things like 'last Sunday of the month' before 1970. This is because it uses mktime() etc. which can't really handle dates before 1970. Damon Chaplin , 25 Oct 2003. cyrus-imapd-2.5.10/tools/vzic/test-vzic.c0000644000175000017500000002645113001236020015157 00000000000000/* * Vzic - a program to convert Olson timezone database files into VZTIMEZONE * files compatible with the iCalendar specification (RFC2445). * * Copyright (C) 2000-2001 Ximian, Inc. * Copyright (C) 2003 Damon Chaplin. * * Author: Damon Chaplin * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307, USA. */ /* * test-vzic.c - test vzic + libical against mktime() and friends. * * Note that when we output VCALENDAR data compatible with Outlook the * results aren't all correct. * * We have to modify some RRULEs which makes these timezones incorrect: * * Africa/Cairo * America/Godthab * America/Santiago * Antarctica/Palmer * Asia/Baghdad * Asia/Damascus * Asia/Jerusalem * * Also, we can only output one RDATE or a pair of RRULEs which may make some * other timezones incorrect sometimes (e.g. if they change). */ #include #include #include #include #include /*#include */ #define CHANGES_MAX_YEAR 2030 /* These are the years between which we test against the Unix timezone functions, inclusive. When using 'vzic --pure' you can test the full range from 1970 to 2037 and it should match against mktime() etc. (assuming you are using the same Olson timezone data for both). But when using VTIMEZONE's that are compatible with Outlook, it is only worth testing times in the future. There will be lots of differences in the past, since we can't include any historical changes in the files. */ #if 1 #define DUMP_START_YEAR 2003 #define DUMP_END_YEAR 2038 #else #define DUMP_START_YEAR 1970 #define DUMP_END_YEAR 2038 #endif /* The maximum size of any complete pathname. */ #define PATHNAME_BUFFER_SIZE 1024 #ifndef FALSE #define FALSE (0) #endif #ifndef TRUE #define TRUE (!FALSE) #endif int VzicDumpChanges = FALSE; /* We output beneath the current directory for now. */ char *directory = "test-output"; static void usage (void); static int parse_zone_name (char *name, char **directory, char **subdirectory, char **filename); static void ensure_directory_exists (char *directory); static void dump_local_times (icaltimezone *zone, FILE *fp); int main(int argc, char* argv[]) { icalarray *zones; icaltimezone *zone; char *zone_directory, *zone_subdirectory, *zone_filename, *location; char output_directory[PATHNAME_BUFFER_SIZE]; char filename[PATHNAME_BUFFER_SIZE]; FILE *fp; int i; int skipping = TRUE; /* * Command-Line Option Parsing. */ for (i = 1; i < argc; i++) { /* --dump-changes: Dumps a list of times when each timezone changed, and the new local time offset from UTC. */ if (!strcmp (argv[i], "--dump-changes")) VzicDumpChanges = TRUE; else usage (); } zones = icaltimezone_get_builtin_timezones (); ensure_directory_exists (directory); for (i = 0; i < zones->num_elements; i++) { zone = icalarray_element_at (zones, i); location = icaltimezone_get_location (zone); #if 0 /* Use this to start at a certain zone. */ if (skipping && strcmp (location, "America/Boise")) continue; #endif skipping = FALSE; /* Use this to only output data for certain timezones. */ #if 0 if (strcmp (location, "America/Cancun") && strcmp (location, "Asia/Baku") && strcmp (location, "Asia/Nicosia") && strcmp (location, "Asia/Novosibirsk") && strcmp (location, "Asia/Samarkand") && strcmp (location, "Asia/Tashkent") && strcmp (location, "Asia/Tbilisi") && strcmp (location, "Asia/Yerevan") && strcmp (location, "Australia/Broken_Hill") && strcmp (location, "Europe/Simferopol") && strcmp (location, "Europe/Tallinn") && strcmp (location, "Europe/Zaporozhye") ) continue; #endif #if 0 printf ("%s\n", location); #endif parse_zone_name (location, &zone_directory, &zone_subdirectory, &zone_filename); sprintf (output_directory, "%s/%s", directory, zone_directory); ensure_directory_exists (output_directory); sprintf (filename, "%s/%s", output_directory, zone_filename); if (zone_subdirectory) { sprintf (output_directory, "%s/%s/%s", directory, zone_directory, zone_subdirectory); ensure_directory_exists (output_directory); sprintf (filename, "%s/%s", output_directory, zone_filename); } fp = fopen (filename, "w"); if (!fp) { fprintf (stderr, "Couldn't create file: %s\n", filename); exit (1); } /* We can run 2 different tests - output all changes for each zone, or test against mktime()/localtime(). Should have a command-line option or something. */ if (VzicDumpChanges) icaltimezone_dump_changes (zone, CHANGES_MAX_YEAR, fp); else dump_local_times (zone, fp); if (ferror (fp)) { fprintf (stderr, "Error writing file: %s\n", filename); exit (1); } fclose (fp); } return 0; } static void usage (void) { fprintf (stderr, "Usage: test-vzic [--dump-changes]\n"); exit (1); } /* This checks that the Zone name only uses the characters in [-+_/a-zA-Z0-9], and outputs a warning if it isn't. */ static int parse_zone_name (char *name, char **directory, char **subdirectory, char **filename) { static int invalid_zone_num = 1; char *p, ch, *first_slash_pos = NULL, *second_slash_pos = NULL; int invalid = FALSE; for (p = name; (ch = *p) != 0; p++) { if ((ch < 'a' || ch > 'z') && (ch < 'A' || ch > 'Z') && (ch < '0' || ch > '9') && ch != '/' && ch != '_' && ch != '-' && ch != '+') { fprintf (stderr, "Warning: Unusual Zone name: %s\n", name); invalid = TRUE; break; } if (ch == '/') { if (!first_slash_pos) { first_slash_pos = p; } else if (!second_slash_pos) { second_slash_pos = p; } else { fprintf (stderr, "Warning: More than 2 '/' characters in Zone name: %s\n", name); invalid = TRUE; break; } } } if (!first_slash_pos) { fprintf (stderr, "No '/' character in Zone name: %s. Skipping.\n", name); return FALSE; } if (invalid) { fprintf (stderr, "Invalid zone name: %s\n", name); exit (0); } else { *first_slash_pos = '\0'; *directory = icalmemory_strdup (name); *first_slash_pos = '/'; if (second_slash_pos) { *second_slash_pos = '\0'; *subdirectory = icalmemory_strdup (first_slash_pos + 1); *second_slash_pos = '/'; *filename = icalmemory_strdup (second_slash_pos + 1); } else { *subdirectory = NULL; *filename = icalmemory_strdup (first_slash_pos + 1); } } } static void ensure_directory_exists (char *directory) { struct stat filestat; if (stat (directory, &filestat) != 0) { /* If the directory doesn't exist, try to create it. */ if (errno == ENOENT) { if (mkdir (directory, 0777) != 0) { fprintf (stderr, "Can't create directory: %s\n", directory); exit (1); } } else { fprintf (stderr, "Error calling stat() on directory: %s\n", directory); exit (1); } } else if (!S_ISDIR (filestat.st_mode)) { fprintf (stderr, "Can't create directory, already exists: %s\n", directory); exit (1); } } static void dump_local_times (icaltimezone *zone, FILE *fp) { static char *months[] = { "Jan", "Feb", "Mar", "Apr", "May", "Jun", "Jul", "Aug", "Sep", "Oct", "Nov", "Dec" }; icaltimezone *utc_timezone; struct icaltimetype tt, tt_copy; struct tm tm, local_tm; time_t t; char tzstring[256], *location; int last_year_output = 0; int total_error = 0, total_error2 = 0; utc_timezone = icaltimezone_get_utc_timezone (); /* This is our UTC time that we will use to iterate over the period. */ tt.year = DUMP_START_YEAR; tt.month = 1; tt.day = 1; tt.hour = 0; tt.minute = 0; tt.second = 0; tt.is_utc = 0; tt.is_date = 0; tt.zone = ""; tm.tm_year = tt.year - 1900; tm.tm_mon = tt.month - 1; tm.tm_mday = tt.day; tm.tm_hour = tt.hour; tm.tm_min = tt.minute; tm.tm_sec = tt.second; tm.tm_isdst = -1; /* Convert it to a time_t by saying it is in UTC. */ putenv ("TZ=UTC"); t = mktime (&tm); location = icaltimezone_get_location (zone); sprintf (tzstring, "TZ=%s", location); /*printf ("Zone: %s\n", location);*/ putenv (tzstring); /* Loop around converting the UTC time to local time, outputting it, and then adding on 15 minutes to the UTC time. */ while (tt.year <= DUMP_END_YEAR) { if (tt.year > last_year_output) { last_year_output = tt.year; #if 0 printf (" %i\n", last_year_output); fprintf (fp, " %i\n", last_year_output); #endif } #if 1 /* First use the Unix functions. */ /* Now convert it to a local time in the given timezone. */ local_tm = *localtime (&t); #endif #if 1 /* Now use libical. */ tt_copy = tt; icaltimezone_convert_time (&tt_copy, utc_timezone, zone); #endif #if 1 if (local_tm.tm_year + 1900 != tt_copy.year || local_tm.tm_mon + 1 != tt_copy.month || local_tm.tm_mday != tt_copy.day || local_tm.tm_hour != tt_copy.hour || local_tm.tm_min != tt_copy.minute || local_tm.tm_sec != tt_copy.second) { /* The error format is: ERROR: Original-UTC-Time Local-Time-From-mktime Local-Time-From-Libical */ total_error++; fprintf (fp, "ERROR:%2i %s %04i %2i:%02i:%02i UTC", tt.day, months[tt.month - 1], tt.year, tt.hour, tt.minute, tt.second); fprintf (fp, " ->%2i %s %04i %2i:%02i:%02i", local_tm.tm_mday, months[local_tm.tm_mon], local_tm.tm_year + 1900, local_tm.tm_hour, local_tm.tm_min, local_tm.tm_sec); fprintf (fp, " Us:%2i %s %04i %2i:%02i:%02i\n", tt_copy.day, months[tt_copy.month - 1], tt_copy.year, tt_copy.hour, tt_copy.minute, tt_copy.second); } #endif /* Now convert it back, and check we get the original time. */ icaltimezone_convert_time (&tt_copy, zone, utc_timezone); if (tt.year != tt_copy.year || tt.month != tt_copy.month || tt.day != tt_copy.day || tt.hour != tt_copy.hour || tt.minute != tt_copy.minute || tt.second != tt_copy.second) { total_error2++; fprintf (fp, "ERROR 2: %2i %s %04i %2i:%02i:%02i UTC", tt.day, months[tt.month - 1], tt.year, tt.hour, tt.minute, tt.second); fprintf (fp, " Us:%2i %s %04i %2i:%02i:%02i UTC\n", tt_copy.day, months[tt_copy.month - 1], tt_copy.year, tt_copy.hour, tt_copy.minute, tt_copy.second); } /* Increment the time. */ icaltime_adjust (&tt, 0, 0, 15, 0); /* We assume leap seconds are not included in time_t values, which should be true on POSIX systems. */ t += 15 * 60; } printf ("Zone: %40s Errors: %i (%i)\n", icaltimezone_get_location (zone), total_error, total_error2); } cyrus-imapd-2.5.10/tools/vzic/vzic.c0000644000175000017500000002133013001236020014171 00000000000000/* * Vzic - a program to convert Olson timezone database files into VZTIMEZONE * files compatible with the iCalendar specification (RFC2445). * * Copyright (C) 2000-2001 Ximian, Inc. * Copyright (C) 2003 Damon Chaplin. * * Author: Damon Chaplin * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307, USA. */ #include #include #include #include "vzic.h" #include "vzic-parse.h" #include "vzic-dump.h" #include "vzic-output.h" /* * Global command-line options. */ /* By default we output Outlook-compatible output. If --pure is used we output pure output, with no changes to be compatible with Outlook. */ gboolean VzicPureOutput = FALSE; gboolean VzicDumpOutput = FALSE; gboolean VzicDumpChanges = FALSE; gboolean VzicDumpZoneNamesAndCoords = TRUE; gboolean VzicDumpZoneTranslatableStrings= FALSE; gboolean VzicNoRRules = FALSE; gboolean VzicNoRDates = FALSE; char* VzicOutputDir = "zoneinfo"; char* VzicUrlPrefix = NULL; char* VzicOlsonDir = OLSON_DIR; GList* VzicTimeZoneNames = NULL; static void convert_olson_file (char *olson_file, GHashTable *zones_hash); static void usage (void); static void free_zone_data (GArray *zone_data); static void free_rule_array (gpointer key, gpointer value, gpointer data); static void free_link_data (gpointer key, gpointer value, gpointer data); int main (int argc, char *argv[]) { int i; char directory[PATHNAME_BUFFER_SIZE]; char filename[PATHNAME_BUFFER_SIZE]; GHashTable *zones_hash; /* * Command-Line Option Parsing. */ for (i = 1; i < argc; i++) { /* * User Options. */ /* --pure: Output the perfect VCALENDAR data, which Outlook won't parse as it has problems with certain iCalendar constructs. */ if (!strcmp (argv[i], "--pure")) VzicPureOutput = TRUE; /* --output-dir: specify where to output all the files beneath. The default is the current directory. */ else if (argc > i + 1 && !strcmp (argv[i], "--output-dir")) VzicOutputDir = argv[++i]; /* --url-prefix: Used as the base for the TZURL property in each VTIMEZONE. The default is to not output TZURL properties. */ else if (argc > i + 1 && !strcmp (argv[i], "--url-prefix")) { int length; VzicUrlPrefix = argv[++i]; /* remove the trailing '/' if there is one */ length = strlen (VzicUrlPrefix); if (VzicUrlPrefix[length - 1] == '/') VzicUrlPrefix[length - 1] = '\0'; } else if (argc > i + 1 && !strcmp (argv[i], "--olson-dir")) { VzicOlsonDir = argv[++i]; } /* * Debugging Options. */ /* --dump: Dump the Rule and Zone data that we parsed from the Olson timezone files. This is used to test the parsing code. */ else if (!strcmp (argv[i], "--dump")) VzicDumpOutput = TRUE; /* --dump-changes: Dumps a list of times when each timezone changed, and the new local time offset from UTC. */ else if (!strcmp (argv[i], "--dump-changes")) VzicDumpChanges = TRUE; /* --no-rrules: Don't output RRULE properties in the VTIMEZONEs. Instead it will just output RDATEs for each year up to a certain year. */ else if (!strcmp (argv[i], "--no-rrules")) VzicNoRRules = TRUE; /* --no-rdates: Don't output multiple RDATEs in a single VTIMEZONE component. Instead they will be output separately. */ else if (!strcmp (argv[i], "--no-rdates")) VzicNoRDates = TRUE; else usage (); } /* * Create any necessary directories. */ ensure_directory_exists (VzicOutputDir); if (VzicDumpOutput) { /* Create the directories for the dump output, if they don't exist. */ sprintf (directory, "%s/ZonesVzic", VzicOutputDir); ensure_directory_exists (directory); sprintf (directory, "%s/RulesVzic", VzicOutputDir); ensure_directory_exists (directory); } if (VzicDumpChanges) { /* Create the directory for the changes output, if it doesn't exist. */ sprintf (directory, "%s/ChangesVzic", VzicOutputDir); ensure_directory_exists (directory); } sprintf (filename, "%s/zone.tab", VzicOlsonDir); zones_hash = parse_zone_tab (filename); /* * Convert the Olson timezone files. */ convert_olson_file ("africa", zones_hash); convert_olson_file ("antarctica", zones_hash); convert_olson_file ("asia", zones_hash); convert_olson_file ("australasia", zones_hash); convert_olson_file ("europe", zones_hash); convert_olson_file ("northamerica", zones_hash); convert_olson_file ("southamerica", zones_hash); /* These are backwards-compatability and weird stuff. */ convert_olson_file ("backward", zones_hash); convert_olson_file ("etcetera", zones_hash); #if 0 convert_olson_file ("leapseconds", zones_hash); convert_olson_file ("pacificnew", zones_hash); convert_olson_file ("solar87", zones_hash); convert_olson_file ("solar88", zones_hash); convert_olson_file ("solar89", zones_hash); #endif /* This doesn't really do anything and it messes up vzic-dump.pl so we don't bother. */ #if 0 convert_olson_file ("factory", zones_hash); #endif /* This is old System V stuff, which we don't currently support since it uses 'min' as a Rule FROM value which messes up our algorithm, making it too slow and use too much memory. */ #if 0 convert_olson_file ("systemv", zones_hash); #endif /* Output the timezone names and coordinates in a zone.tab file, and the translatable strings to feed to gettext. */ if (VzicDumpZoneNamesAndCoords) { dump_time_zone_names (VzicTimeZoneNames, VzicOutputDir, zones_hash); } return 0; } static void convert_olson_file (char *olson_file, GHashTable *zones_hash) { char input_filename[PATHNAME_BUFFER_SIZE]; GArray *zone_data; GHashTable *rule_data, *link_data; char dump_filename[PATHNAME_BUFFER_SIZE]; ZoneData *zone; int i, max_until_year; sprintf (input_filename, "%s/%s", VzicOlsonDir, olson_file); parse_olson_file (input_filename, &zone_data, &rule_data, &link_data, &max_until_year); if (VzicDumpOutput) { sprintf (dump_filename, "%s/ZonesVzic/%s", VzicOutputDir, olson_file); dump_zone_data (zone_data, dump_filename); sprintf (dump_filename, "%s/RulesVzic/%s", VzicOutputDir, olson_file); dump_rule_data (rule_data, dump_filename); } output_vtimezone_files (VzicOutputDir, zone_data, rule_data, link_data, zones_hash, max_until_year); free_zone_data (zone_data); g_hash_table_foreach (rule_data, free_rule_array, NULL); g_hash_table_destroy (rule_data); g_hash_table_foreach (link_data, free_link_data, NULL); g_hash_table_destroy (link_data); } static void usage (void) { fprintf (stderr, "Usage: vzic [--dump] [--dump-changes] [--no-rrules] [--no-rdates] [--pure] [--output-dir ] [--url-prefix ] [--olson-dir ]\n"); exit (1); } /* * Functions to free the data structures. */ static void free_zone_data (GArray *zone_data) { ZoneData *zone; ZoneLineData *zone_line; int i, j; for (i = 0; i < zone_data->len; i++) { zone = &g_array_index (zone_data, ZoneData, i); g_free (zone->zone_name); for (j = 0; j < zone->zone_line_data->len; j++) { zone_line = &g_array_index (zone->zone_line_data, ZoneLineData, j); g_free (zone_line->rules); g_free (zone_line->format); } g_array_free (zone->zone_line_data, TRUE); } g_array_free (zone_data, TRUE); } static void free_rule_array (gpointer key, gpointer value, gpointer data) { char *name = key; GArray *rule_array = value; RuleData *rule; int i; for (i = 0; i < rule_array->len; i++) { rule = &g_array_index (rule_array, RuleData, i); if (!rule->is_shallow_copy) { g_free (rule->type); g_free (rule->letter_s); } } g_array_free (rule_array, TRUE); g_free (name); } static void free_link_data (gpointer key, gpointer value, gpointer data) { GList *link = data; g_free (key); while (link) { g_free (link->data); link = link->next; } g_list_free (data); } cyrus-imapd-2.5.10/tools/vzic/vzic-output.c0000644000175000017500000021113413001236020015532 00000000000000/* * Vzic - a program to convert Olson timezone database files into VZTIMEZONE * files compatible with the iCalendar specification (RFC2445). * * Copyright (C) 2000-2001 Ximian, Inc. * Copyright (C) 2003 Damon Chaplin. * * Author: Damon Chaplin * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307, USA. */ /* ALGORITHM: * * First we expand all the Rule arrays, so that each element only represents 1 * year. If a Rule extends to infinity we expand it up to a few years past the * maximum UNTIL year used in any of the timezones. We do this to make sure * that the last of the expanded Rules (which may be infinite) is only used * in the last of the time periods (i.e. the last Zone line). * * The Rule arrays are also sorted by the start time (FROM + IN + ON + AT). * Doing all this makes it much easier to find which rules apply to which * periods. * * For each timezone (i.e. ZoneData element), we step through each of the * time periods, the ZoneLineData elements (which represent each Zone line * from the Olson file.) * * We calculate the start & end time of the period. * - For the first line the start time is -infinity. * - For the last line the end time is +infinity. * - The end time of each line is also the start time of the next. * * We create an array of time changes which occur in this period, including * the one implied by the Zone line itself (though this is later taken out * if it is found to be at exactly the same time as the first Rule). * * Now we iterate over the time changes, outputting them as STANDARD or * DAYLIGHT components. We also try to merge them together into RRULEs or * use RDATEs. */ #include #include #include #include #include #include #include #include "vzic.h" #include "vzic-output.h" #include "vzic-dump.h" #include "xversion.h" /* These come from the Makefile. See the comments there. */ char *ProductID = PRODUCT_ID; char *TZIDPrefix = TZID_PREFIX; /* We expand the TZIDPrefix, replacing %D with the date, in here. */ char TZIDPrefixExpanded[1024]; /* We only use RRULEs if there are at least MIN_RRULE_OCCURRENCES occurrences, since otherwise RDATEs are more efficient. Actually, I've set this high so we only use RRULEs for infinite recurrences. Since expanding RRULEs is very time-consuming, this seems sensible. */ #define MIN_RRULE_OCCURRENCES 3 /* The year we go up to when dumping the list of timezone changes (used for testing & debugging). */ #define MAX_CHANGES_YEAR 2030 /* This is the maximum year that time_t value can typically hold on 32-bit systems. */ #define MAX_TIME_T_YEAR 2038 /* The year we use to start RRULEs. */ #define RRULE_START_YEAR 1970 /* The year we use for RDATEs. */ #define RDATE_YEAR 1970 static char *WeekDays[] = { "SU", "MO", "TU", "WE", "TH", "FR", "SA" }; static int DaysInMonth[] = { 31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31 }; char *CurrentZoneName; typedef struct _VzicTime VzicTime; struct _VzicTime { /* Normal years, e.g. 2001. */ int year; /* 0 (Jan) to 11 (Dec). */ int month; /* The day, either a simple month day number, 1-31, or a rule such as the last Sunday, or the first Monday on or after the 8th. */ DayCode day_code; int day_number; /* 1 to 31. */ int day_weekday; /* 0 (Sun) to 6 (Sat). */ /* The time, in seconds from midnight. The code specifies whether the time is a wall clock time, local standard time, or universal time. */ int time_seconds; TimeCode time_code; /* The offset from UTC for local standard time. */ int stdoff; /* The offset from UTC for local wall clock time. If this is different to stdoff then this is a DAYLIGHT component. This is TZOFFSETTO. */ int walloff; /* TRUE if the time change recurs every year to infinity. */ gboolean is_infinite; /* The last instance of a recurring time change, if not infinite */ VzicTime *until; /* TRUE if the change has already been output. */ gboolean output; /* These are the offsets of the previous VzicTime, and are used when calculating the time of the change. We place them here in output_zone_components() to simplify the output code. */ int prev_stdoff; int prev_walloff; /* The abbreviated form of the timezone name. Note that this may not be unique. */ char *tzname; }; static void expand_and_sort_rule_array (gpointer key, gpointer value, gpointer data); static int rule_sort_func (const void *arg1, const void *arg2); static void output_zone (char *directory, ZoneData *zone, char *zone_name, ZoneDescription *zone_desc, GHashTable *rule_data); static gboolean parse_zone_name (char *name, char **directory, char **subdirectory, char **filename); static void output_zone_to_files (ZoneData *zone, char *zone_name, ZoneDescription *zone_desc, GHashTable *rule_data, FILE *fp, FILE *changes_fp); static gboolean add_rule_changes (ZoneLineData *zone_line, char *zone_name, GArray *changes, GHashTable *rule_data, VzicTime *start, VzicTime *end, char **start_letter_s, int *save_seconds); static char* expand_tzname (char *zone_name, char *format, gboolean have_letter_s, char *letter_s, gboolean is_daylight); static int compare_times (VzicTime *time1, int stdoff1, int walloff1, VzicTime *time2, int stdoff2, int walloff2); static gboolean times_match (VzicTime *time1, int stdoff1, int walloff1, VzicTime *time2, int stdoff2, int walloff2); static void output_zone_components (FILE *fp, char *name, ZoneDescription *zone_desc, GArray *changes); static void set_previous_offsets (GArray *changes); static gboolean check_for_recurrence (FILE *fp, GArray *changes, int idx); static void check_for_rdates (FILE *fp, GArray *changes, int idx); static gboolean timezones_match (char *tzname1, char *tzname2); static int output_component_start (char *buffer, VzicTime *vzictime, gboolean output_rdate, gboolean use_same_tz_offset); static void output_component_end (FILE *fp, VzicTime *vzictime); static void vzictime_init (VzicTime *vzictime); static int calculate_actual_time (VzicTime *vzictime, TimeCode time_code, int stdoff, int walloff); static int calculate_wall_time (int time, TimeCode time_code, int stdoff, int walloff, int *day_offset); static int calculate_until_time (int time, TimeCode time_code, int stdoff, int walloff, int *year, int *month, int *day); static void fix_time_overflow (int *year, int *month, int *day, int day_offset); static char* format_time (int year, int month, int day, int time); static char* format_tz_offset (int tz_offset, gboolean round_seconds); static gboolean output_rrule (char *rrule_buffer, int month, DayCode day_code, int day_number, int day_weekday, int day_offset, char *until); static gboolean output_rrule_2 (char *buffer, int month, int day_number, int day_weekday); static char* format_vzictime (VzicTime *vzictime); static void dump_changes (FILE *fp, char *zone_name, GArray *changes); static void dump_change (FILE *fp, char *zone_name, VzicTime *vzictime, int year); static void expand_tzid_prefix (void); void output_vtimezone_files (char *directory, GArray *zone_data, GHashTable *rule_data, GHashTable *link_data, GHashTable *zones_hash, int max_until_year) { ZoneData *zone; ZoneDescription *zone_desc; GList *links; char *link_to; int i; /* Insert today's date into the TZIDs we output. */ expand_tzid_prefix (); /* Expand the rule data so that each entry specifies only one year, and sort it so we can easily find the rules applicable to each Zone span. */ g_hash_table_foreach (rule_data, expand_and_sort_rule_array, GINT_TO_POINTER (max_until_year)); /* Output each timezone. */ for (i = 0; i < zone_data->len; i++) { zone = &g_array_index (zone_data, ZoneData, i); zone_desc = g_hash_table_lookup (zones_hash, zone->zone_name); output_zone (directory, zone, zone->zone_name, zone_desc, rule_data); /* Look for any links from this zone. */ links = g_hash_table_lookup (link_data, zone->zone_name); while (links) { link_to = links->data; /* We ignore Links that don't have a '/' in them (things like 'EST5EDT'). */ if (strchr (link_to, '/')) { output_zone (directory, zone, link_to, NULL, rule_data); } links = links->next; } } } static void expand_and_sort_rule_array (gpointer key, gpointer value, gpointer data) { char *name = key; GArray *rule_array = value; RuleData *rule, tmp_rule; int len, max_year, i, from, to, year; gboolean is_infinite; /* We expand the rule data to a year greater than any year used in a Zone UNTIL value. This is so that we can easily get parts of the array to use for each Zone line. */ max_year = GPOINTER_TO_INT (data) + 2; /* If any of the rules apply to several years, we turn it into a single rule for each year. If the Rule is infinite we go up to max_year. We change the FROM field in the copies of the Rule, setting it to each of the years, and set TO to FROM, except if TO was YEAR_MAXIMUM we set the last TO to YEAR_MAXIMUM, so we still know the Rule is infinite. */ len = rule_array->len; for (i = 0; i < len; i++) { rule = &g_array_index (rule_array, RuleData, i); /* None of the Rules currently use the TYPE field, but we'd better check. */ if (rule->type) { fprintf (stderr, "Rules %s has a TYPE: %s\n", name, rule->type); exit (1); } if (rule->from_year != rule->to_year) { from = rule->from_year; to = rule->to_year; tmp_rule = *rule; /* Flag that this is a shallow copy so we don't free anything twice. */ tmp_rule.is_shallow_copy = TRUE; /* See if it is an infinite Rule. */ if (to == YEAR_MAXIMUM) { is_infinite = TRUE; to = max_year; if (from < to) rule->to_year = rule->from_year; } else { is_infinite = FALSE; } /* Create a copy of the Rule for each year. */ for (year = from + 1; year <= to; year++) { tmp_rule.from_year = year; /* If the Rule is infinite, mark the last copy as infinite. */ if (year == to && is_infinite) tmp_rule.to_year = YEAR_MAXIMUM; else tmp_rule.to_year = year; g_array_append_val (rule_array, tmp_rule); } } } /* Now sort the rules. */ qsort (rule_array->data, rule_array->len, sizeof (RuleData), rule_sort_func); #if 0 dump_rule_array (name, rule_array, stdout); #endif } /* This is used to sort the rules, after the rules have all been expanded so that each one is only for one year. */ static int rule_sort_func (const void *arg1, const void *arg2) { RuleData *rule1, *rule2; int time1_year, time1_month, time1_day; int time2_year, time2_month, time2_day; int month_diff, result; VzicTime t1, t2; rule1 = (RuleData*) arg1; rule2 = (RuleData*) arg2; time1_year = rule1->from_year; time1_month = rule1->in_month; time2_year = rule2->from_year; time2_month = rule2->in_month; /* If there is more that one month difference we don't need to calculate the day or time. */ month_diff = (time1_year - time2_year) * 12 + time1_month - time2_month; if (month_diff > 1) return 1; if (month_diff < -1) return -1; /* Now we have to calculate the day and time of the Rule start and the VzicTime, using the given offsets. */ t1.year = time1_year; t1.month = time1_month; t1.day_code = rule1->on_day_code; t1.day_number = rule1->on_day_number; t1.day_weekday = rule1->on_day_weekday; t1.time_code = rule1->at_time_code; t1.time_seconds = rule1->at_time_seconds; t2.year = time2_year; t2.month = time2_month; t2.day_code = rule2->on_day_code; t2.day_number = rule2->on_day_number; t2.day_weekday = rule2->on_day_weekday; t2.time_code = rule2->at_time_code; t2.time_seconds = rule2->at_time_seconds; /* FIXME: We don't know the offsets yet, but I don't think any Rules are close enough together that the offsets can make a difference. Should check this. */ calculate_actual_time (&t1, TIME_WALL, 0, 0); calculate_actual_time (&t2, TIME_WALL, 0, 0); /* Now we can compare the entire time. */ if (t1.year > t2.year) result = 1; else if (t1.year < t2.year) result = -1; else if (t1.month > t2.month) result = 1; else if (t1.month < t2.month) result = -1; else if (t1.day_number > t2.day_number) result = 1; else if (t1.day_number < t2.day_number) result = -1; else if (t1.time_seconds > t2.time_seconds) result = 1; else if (t1.time_seconds < t2.time_seconds) result = -1; else { printf ("WARNING: Rule dates matched.\n"); result = 0; } return result; } static void output_zone (char *directory, ZoneData *zone, char *zone_name, ZoneDescription *zone_desc, GHashTable *rule_data) { FILE *fp, *changes_fp = NULL; char output_directory[PATHNAME_BUFFER_SIZE]; char filename[PATHNAME_BUFFER_SIZE]; char changes_filename[PATHNAME_BUFFER_SIZE]; char *zone_directory, *zone_subdirectory, *zone_filename; /* Set a global for the zone_name, to be used only for debug messages. */ CurrentZoneName = zone_name; /* Use this to only output a particular zone. */ #if 0 if (strcmp (zone_name, "Atlantic/Azores")) return; #endif #if 0 printf ("Outputting Zone: %s\n", zone_name); #endif if (!parse_zone_name (zone_name, &zone_directory, &zone_subdirectory, &zone_filename)) return; if (VzicDumpZoneNamesAndCoords) { VzicTimeZoneNames = g_list_prepend (VzicTimeZoneNames, g_strdup (zone_name)); } if (zone_subdirectory) { sprintf (output_directory, "%s/%s/%s", directory, zone_directory, zone_subdirectory); ensure_directory_exists (output_directory); sprintf (filename, "%s/%s.ics", output_directory, zone_filename); if (VzicDumpChanges) { sprintf (output_directory, "%s/ChangesVzic/%s/%s", directory, zone_directory, zone_subdirectory); ensure_directory_exists (output_directory); sprintf (changes_filename, "%s/%s", output_directory, zone_filename); } } else if (zone_directory) { sprintf (output_directory, "%s/%s", directory, zone_directory); ensure_directory_exists (output_directory); sprintf (filename, "%s/%s.ics", output_directory, zone_filename); if (VzicDumpChanges) { sprintf (output_directory, "%s/ChangesVzic/%s", directory, zone_directory); ensure_directory_exists (output_directory); sprintf (changes_filename, "%s/%s", output_directory, zone_filename); } } else { sprintf (output_directory, "%s", directory); ensure_directory_exists (output_directory); sprintf (filename, "%s/%s.ics", output_directory, zone_filename); if (VzicDumpChanges) { sprintf (output_directory, "%s/ChangesVzic", directory); ensure_directory_exists (output_directory); sprintf (changes_filename, "%s/%s", output_directory, zone_filename); } } /* Create the files. */ fp = fopen (filename, "w"); if (!fp) { fprintf (stderr, "Couldn't create file: %s\n", filename); exit (1); } if (VzicDumpChanges) { changes_fp = fopen (changes_filename, "w"); if (!changes_fp) { fprintf (stderr, "Couldn't create file: %s\n", changes_filename); exit (1); } } fprintf (fp, "BEGIN:VCALENDAR\r\nPRODID:"); fprintf (fp, ProductID, _CYRUS_VERSION); fprintf (fp, "\r\nVERSION:2.0\r\n"); output_zone_to_files (zone, zone_name, zone_desc, rule_data, fp, changes_fp); if (ferror (fp)) { fprintf (stderr, "Error writing file: %s\n", filename); exit (1); } fprintf (fp, "END:VCALENDAR\r\n"); fclose (fp); g_free (zone_directory); g_free (zone_subdirectory); g_free (zone_filename); } /* This checks that the Zone name only uses the characters in [-+_/a-zA-Z0-9], and outputs a warning if it isn't. */ static gboolean parse_zone_name (char *name, char **directory, char **subdirectory, char **filename) { static int invalid_zone_num = 1; char *p, ch, *first_slash_pos = NULL, *second_slash_pos = NULL; gboolean invalid = FALSE; for (p = name; (ch = *p) != 0; p++) { if ((ch < 'a' || ch > 'z') && (ch < 'A' || ch > 'Z') && (ch < '0' || ch > '9') && ch != '/' && ch != '_' && ch != '-' && ch != '+') { fprintf (stderr, "WARNING: Unusual Zone name: %s\n", name); invalid = TRUE; break; } if (ch == '/') { if (!first_slash_pos) { first_slash_pos = p; } else if (!second_slash_pos) { second_slash_pos = p; } else { fprintf (stderr, "WARNING: More than 2 '/' characters in Zone name: %s\n", name); invalid = TRUE; break; } } } #if 0 if (!first_slash_pos) { #if 0 fprintf (stderr, "No '/' character in Zone name: %s. Skipping.\n", name); #endif return FALSE; } #endif if (invalid) { *directory = g_strdup ("Invalid"); *filename = g_strdup_printf ("Zone%i", invalid_zone_num++); } else if (!first_slash_pos) { *directory = NULL; *subdirectory = NULL; *filename = g_strdup (name); } else { *first_slash_pos = '\0'; *directory = g_strdup (name); *first_slash_pos = '/'; if (second_slash_pos) { *second_slash_pos = '\0'; *subdirectory = g_strdup (first_slash_pos + 1); *second_slash_pos = '/'; *filename = g_strdup (second_slash_pos + 1); } else { *subdirectory = NULL; *filename = g_strdup (first_slash_pos + 1); } } return invalid ? FALSE : TRUE; } static void output_zone_to_files (ZoneData *zone, char *zone_name, ZoneDescription *zone_desc, GHashTable *rule_data, FILE *fp, FILE *changes_fp) { ZoneLineData *zone_line; GArray *changes; int i, stdoff, walloff, start_index, save_seconds; VzicTime start, end, *vzictime_start, *vzictime, *vzictime_first_rule_change; gboolean is_daylight, found_letter_s; char *start_letter_s; changes = g_array_new (FALSE, FALSE, sizeof (VzicTime)); vzictime_init (&start); vzictime_init (&end); /* The first period starts at -infinity. */ start.year = YEAR_MINIMUM; for (i = 0; i < zone->zone_line_data->len; i++) { zone_line = &g_array_index (zone->zone_line_data, ZoneLineData, i); /* This is the local standard time offset from GMT for this period. */ start.stdoff = stdoff = zone_line->stdoff_seconds; start.walloff = walloff = stdoff + zone_line->save_seconds; if (zone_line->until_set) { end.year = zone_line->until_year; end.month = zone_line->until_month; end.day_code = zone_line->until_day_code; end.day_number = zone_line->until_day_number; end.day_weekday = zone_line->until_day_weekday; end.time_seconds = zone_line->until_time_seconds; end.time_code = zone_line->until_time_code; } else { /* The last period ends at +infinity. */ end.year = YEAR_MAXIMUM; } /* Add a time change for the start of the period. This may be removed later if one of the rules expands to exactly the same time. */ start_index = changes->len; g_array_append_val (changes, start); /* If there are Rules associated with this period, add all the relevant time changes. */ save_seconds = 0; if (zone_line->rules) found_letter_s = add_rule_changes (zone_line, zone_name, changes, rule_data, &start, &end, &start_letter_s, &save_seconds); else found_letter_s = FALSE; /* FIXME: I'm not really sure what to do about finding a LETTER_S for the first part of the period (i.e. before the first Rule comes into effect). Currently we try to use the same LETTER_S as the first Rule of the period which is in local standard time. */ if (zone_line->save_seconds) save_seconds = zone_line->save_seconds; is_daylight = save_seconds ? TRUE : FALSE; vzictime_start = &g_array_index (changes, VzicTime, start_index); walloff = vzictime_start->walloff = stdoff + save_seconds; /* TEST: See if the first Rule time is exactly the same as the change from the Zone line. In which case we can remove the Zone line change. */ if (changes->len > start_index + 1) { int prev_stdoff, prev_walloff; if (start_index > 0) { VzicTime *v = &g_array_index (changes, VzicTime, start_index - 1); prev_stdoff = v->stdoff; prev_walloff = v->walloff; } else { prev_stdoff = 0; prev_walloff = 0; } vzictime_first_rule_change = &g_array_index (changes, VzicTime, start_index + 1); if (times_match (vzictime_start, prev_stdoff, prev_walloff, vzictime_first_rule_change, stdoff, walloff)) { #if 0 printf ("Removing zone-line change (using new offsets)\n"); #endif g_array_remove_index (changes, start_index); vzictime_start = NULL; } else if (times_match (vzictime_start, prev_stdoff, prev_walloff, vzictime_first_rule_change, prev_stdoff, prev_walloff)) { #if 0 printf ("Removing zone-line change (using previous offsets)\n"); #endif g_array_remove_index (changes, start_index); vzictime_start = NULL; } } if (vzictime_start) { vzictime_start->tzname = expand_tzname (zone_name, zone_line->format, found_letter_s, start_letter_s, is_daylight); } /* The start of the next Zone line is the end time of this one. */ start = end; } set_previous_offsets (changes); output_zone_components (fp, zone_name, zone_desc, changes); if (VzicDumpChanges) dump_changes (changes_fp, zone_name, changes); /* Free all the TZNAME fields. */ for (i = 0; i < changes->len; i++) { vzictime = &g_array_index (changes, VzicTime, i); g_free (vzictime->tzname); } g_array_free (changes, TRUE); } /* This appends any timezone changes specified by the rules associated with the timezone, that happen between the start and end times. It returns the letter_s field of the first STANDARD rule found in the search. We need this to fill in any %s in the FORMAT field of the first component of the time period (the Zone line). */ static gboolean add_rule_changes (ZoneLineData *zone_line, char *zone_name, GArray *changes, GHashTable *rule_data, VzicTime *start, VzicTime *end, char **start_letter_s, int *save_seconds) { GArray *rule_array; RuleData *rule, *prev_rule = NULL; int stdoff, walloff, i, prev_stdoff, prev_walloff; VzicTime vzictime; gboolean is_daylight, found_start_letter_s = FALSE; gboolean checked_for_previous = FALSE; *save_seconds = 0; rule_array = g_hash_table_lookup (rule_data, zone_line->rules); if (!rule_array) { fprintf (stderr, "Couldn't access rules: %s\n", zone_line->rules); exit (1); } /* The stdoff is the same for all the rules. */ stdoff = start->stdoff; /* The walloff changes as we go through the rules. */ walloff = start->walloff; /* Get the stdoff & walloff from the last change before this period. */ if (changes->len >= 2) { VzicTime *change = &g_array_index (changes, VzicTime, changes->len - 2); prev_stdoff = change->stdoff; prev_walloff = change->walloff; } else { prev_stdoff = prev_walloff = 0; } for (i = 0; i < rule_array->len; i++) { rule = &g_array_index (rule_array, RuleData, i); is_daylight = rule->save_seconds != 0 ? TRUE : FALSE; vzictime_init (&vzictime); vzictime.year = rule->from_year; vzictime.month = rule->in_month; vzictime.day_code = rule->on_day_code; vzictime.day_number = rule->on_day_number; vzictime.day_weekday = rule->on_day_weekday; vzictime.time_seconds = rule->at_time_seconds; vzictime.time_code = rule->at_time_code; vzictime.stdoff = stdoff; vzictime.walloff = stdoff + rule->save_seconds; vzictime.is_infinite = (rule->to_year == YEAR_MAXIMUM) ? TRUE : FALSE; /* If the rule time is before or on the given start time, skip it. */ if (compare_times (&vzictime, stdoff, walloff, start, prev_stdoff, prev_walloff) <= 0) { /* Our next rule may start while this one is in effect so we keep track of its name. This seems to eliminate the need to guess in expand_tzname() but hasn't had enough testing to prove foolproof as of yet. */ found_start_letter_s = TRUE; *start_letter_s = rule->letter_s; continue; } /* If the previous Rule was a daylight Rule, then we may want to use the walloff from that. */ if (!checked_for_previous) { checked_for_previous = TRUE; if (i > 0) { prev_rule = &g_array_index (rule_array, RuleData, i - 1); if (prev_rule->save_seconds) { walloff = start->walloff = stdoff + prev_rule->save_seconds; *save_seconds = prev_rule->save_seconds; found_start_letter_s = TRUE; *start_letter_s = prev_rule->letter_s; #if 0 printf ("Could use save_seconds from previous Rule: %s\n", zone_name); #endif } } } /* If an end time has been given, then if the rule time is on or after it break out of the loop. */ if (end->year != YEAR_MAXIMUM && compare_times (&vzictime, stdoff, walloff, end, stdoff, walloff) >= 0) break; vzictime.tzname = expand_tzname (zone_name, zone_line->format, TRUE, rule->letter_s, is_daylight); g_array_append_val (changes, vzictime); /* When we find the first STANDARD time we set letter_s. */ if (!found_start_letter_s && !is_daylight) { found_start_letter_s = TRUE; *start_letter_s = rule->letter_s; } /* Now that we have added the Rule, the new walloff comes into effect for any following Rules. */ walloff = vzictime.walloff; } return found_start_letter_s; } /* This expands the Zone line FORMAT field, using the given LETTER_S from a Rule line. There are 3 types of FORMAT field: 1. a string with an %s in, e.g. "WE%sT". The %s is replaced with LETTER_S. 2. a string with an '/' in, e.g. "CAT/CAWT". The first part is used for standard time and the second part for when daylight-saving is in effect. 3. a plain string, e.g. "LMT", which we leave as-is. Note that (1) is the only type in which letter_s is required. */ static char* expand_tzname (char *zone_name, char *format, gboolean have_letter_s, char *letter_s, gboolean is_daylight) { char *p, buffer[256], *guess = NULL; int len; #if 0 printf ("Expanding %s with %s\n", format, letter_s); #endif if (!format || !format[0]) { fprintf (stderr, "Missing FORMAT\n"); exit (1); } /* 1. Look for a "%s". */ p = strchr (format, '%'); if (p && *(p + 1) == 's') { if (!have_letter_s) { /* NOTE: These are a few hard-coded TZNAMEs that I've looked up myself. These are needed in a few places where a Zone line comes into effect but no Rule has been found, so we have no LETTER_S to use. I've tried to use whatever is the normal LETTER_S in the Rules for the particular zone, in local standard time. */ if (!strcmp (zone_name, "Asia/Macao") && !strcmp (format, "C%sT")) guess = "CST"; else if (!strcmp (zone_name, "Asia/Macau") && !strcmp (format, "C%sT")) guess = "CST"; else if (!strcmp (zone_name, "Asia/Ashgabat") && !strcmp (format, "ASH%sT")) guess = "ASHT"; else if (!strcmp (zone_name, "Asia/Ashgabat") && !strcmp (format, "TM%sT")) guess = "TMT"; else if (!strcmp (zone_name, "Asia/Samarkand") && !strcmp (format, "TAS%sT")) guess = "TAST"; else if (!strcmp (zone_name, "Atlantic/Azores") && !strcmp (format, "WE%sT")) guess = "WET"; else if (!strcmp (zone_name, "Europe/Paris") && !strcmp (format, "WE%sT")) guess = "WET"; else if (!strcmp (zone_name, "Europe/Warsaw") && !strcmp (format, "CE%sT")) guess = "CET"; else if (!strcmp (zone_name, "America/Phoenix") && !strcmp (format, "M%sT")) guess = "MST"; else if (!strcmp (zone_name, "America/Nome") && !strcmp (format, "Y%sT")) guess = "YST"; if (guess) { #if 0 fprintf (stderr, "WARNING: Couldn't find a LETTER_S to use in FORMAT: %s in Zone: %s Guessing: %s\n", format, zone_name, guess); #endif return g_strdup (guess); } #if 1 fprintf (stderr, "WARNING: Couldn't find a LETTER_S to use in FORMAT: %s in Zone: %s Leaving TZNAME empty\n", format, zone_name); #endif #if 0 /* This is useful to spot exactly which component had a problem. */ sprintf (buffer, "FIXME: %s", format); return g_strdup (buffer); #else /* We give up and don't output a TZNAME. */ return NULL; #endif } sprintf (buffer, format, letter_s ? letter_s : ""); return g_strdup (buffer); } /* 2. Look for a "/". */ p = strchr (format, '/'); if (p) { if (is_daylight) { return g_strdup (p + 1); } else { len = p - format; strncpy (buffer, format, len); buffer[len] = '\0'; return g_strdup (buffer); } } /* 3. Just use format as it is. */ return g_strdup (format); } /* Compares 2 VzicTimes, returning strcmp()-like values, i.e. 0 if equal, 1 if the 1st is after the 2nd and -1 if the 1st is before the 2nd. */ static int compare_times (VzicTime *time1, int stdoff1, int walloff1, VzicTime *time2, int stdoff2, int walloff2) { VzicTime t1, t2; int result; t1 = *time1; t2 = *time2; calculate_actual_time (&t1, TIME_UNIVERSAL, stdoff1, walloff1); calculate_actual_time (&t2, TIME_UNIVERSAL, stdoff2, walloff2); /* Now we can compare the entire time. */ if (t1.year > t2.year) result = 1; else if (t1.year < t2.year) result = -1; else if (t1.month > t2.month) result = 1; else if (t1.month < t2.month) result = -1; else if (t1.day_number > t2.day_number) result = 1; else if (t1.day_number < t2.day_number) result = -1; else if (t1.time_seconds > t2.time_seconds) result = 1; else if (t1.time_seconds < t2.time_seconds) result = -1; else result = 0; #if 0 printf ("%i/%i/%i %i <=> %i/%i/%i %i -> %i\n", t1.day_number, t1.month + 1, t1.year, t1.time_seconds, t2.day_number, t2.month + 1, t2.year, t2.time_seconds, result); #endif return result; } /* Returns TRUE if the 2 times are exactly the same. It will calculate the actual day, but doesn't convert times. */ static gboolean times_match (VzicTime *time1, int stdoff1, int walloff1, VzicTime *time2, int stdoff2, int walloff2) { VzicTime t1, t2; t1 = *time1; t2 = *time2; calculate_actual_time (&t1, TIME_UNIVERSAL, stdoff1, walloff1); calculate_actual_time (&t2, TIME_UNIVERSAL, stdoff2, walloff2); if (t1.year == t2.year && t1.month == t2.month && t1.day_number == t2.day_number && t1.time_seconds == t2.time_seconds) return TRUE; return FALSE; } /* Convert degrees-minutes-seconds into decimal degrees */ static float dms_to_dd (int dms[]) { return dms[0] + dms[1]/60.0 + dms[2]/3600.0; } static void output_zone_components (FILE *fp, char *name, ZoneDescription *zone_desc, GArray *changes) { VzicTime *vzictime; int i, start_index = 0; gboolean only_one_change = FALSE; char start_buffer[1024]; time_t now = time(0); struct tm *tm = gmtime(&now); fprintf (fp, "BEGIN:VTIMEZONE\r\nTZID:%s%s\r\n", TZIDPrefixExpanded, name); if (zone_desc) { /* Add COMMENT */ fprintf (fp, "COMMENT:[%.2s] ", zone_desc->country_code); if (zone_desc->comment) { const char *p; for (p = zone_desc->comment; *p; p++) { switch (*p) { case '\\': case ',': case ';': fprintf (fp, "\\"); break; } fprintf (fp, "%c", *p); } } fprintf (fp, "\r\n"); #if 0 /* Add GEO */ fprintf (fp, "GEO:%+.6f,%+.6f\r\n", dms_to_dd(zone_desc->latitude), dms_to_dd(zone_desc->longitude)); #endif } /* Use current time as LAST-MODIFIED */ fprintf (fp, "LAST-MODIFIED:%04i%02i%02iT%02i%02i%02iZ\r\n", tm->tm_year + 1900, tm->tm_mon + 1, tm->tm_mday, tm->tm_hour, tm->tm_min, tm->tm_sec); if (VzicUrlPrefix != NULL) fprintf (fp, "TZURL:%s/%s\r\n", VzicUrlPrefix, name); /* We use an 'X-' property to place the city name in. */ fprintf (fp, "X-LIC-LOCATION:%s\r\n", name); /* We use an 'X-' property to place the proleptic tzname in. */ vzictime = &g_array_index (changes, VzicTime, 0); if (vzictime->tzname) fprintf( fp, "X-PROLEPTIC-TZNAME:%s\r\n", vzictime->tzname); /* We try to find any recurring components first, or they may get output as lots of RDATES instead. */ if (!VzicNoRRules) { int num_rrules_output = 0; for (i = 1; i < changes->len; i++) { if (check_for_recurrence (fp, changes, i)) { num_rrules_output++; } } #if 0 printf ("Zone: %s had %i infinite RRULEs\n", CurrentZoneName, num_rrules_output); #endif if (!VzicPureOutput && num_rrules_output == 2) { #if 0 printf ("Zone: %s using 2 RRULEs\n", CurrentZoneName); #endif fprintf (fp, "END:VTIMEZONE\r\n"); return; } } /* We skip the first change, which starts at -infinity, unless it is the only change for the timezone. */ if (changes->len > 1) start_index = 1; else only_one_change = TRUE; /* For pure output, we start at the start of the array and step through it outputting RDATEs. For Outlook-compatible output we start at the end and step backwards to find the first STANDARD time to output. */ if (VzicPureOutput) i = start_index - 1; else i = changes->len; for (;;) { if (VzicPureOutput) i++; else i--; if (VzicPureOutput) { if (i >= changes->len) break; } else { if (i < start_index) break; } vzictime = &g_array_index (changes, VzicTime, i); /* If this has been flagged as an RRULE, then output it now */ if (vzictime->until) { char until[256], rrule_buffer[2048]; VzicTime vzictime_start_copy; int day_offset; if (vzictime->until->is_infinite) { until[0] = '\0'; } else { VzicTime t1 = *vzictime->until; calculate_actual_time (&t1, TIME_UNIVERSAL, vzictime->prev_stdoff, vzictime->prev_walloff); /* Output UNTIL, in UTC. */ sprintf (until, ";UNTIL=%sZ", format_time (t1.year, t1.month, t1.day_number, t1.time_seconds)); } /* Change the year to our minimum start year. */ vzictime_start_copy = *vzictime; if (!VzicPureOutput) vzictime_start_copy.year = RRULE_START_YEAR; day_offset = output_component_start (start_buffer, &vzictime_start_copy, FALSE, FALSE); fprintf (fp, "%s", start_buffer); if (output_rrule (rrule_buffer, vzictime_start_copy.month, vzictime_start_copy.day_code, vzictime_start_copy.day_number, vzictime_start_copy.day_weekday, day_offset, until)) { fprintf (fp, "%s", rrule_buffer); } output_component_end (fp, vzictime); continue; } /* If we have already output this component as part of an RRULE or RDATE, then we skip it. */ if (vzictime->output) continue; /* For Outlook-compatible output we only want to output the last STANDARD time as a DTSTART, so skip any DAYLIGHT changes. */ if (!VzicPureOutput && vzictime->stdoff != vzictime->walloff) { printf ("Skipping DAYLIGHT change\n"); continue; } #if 0 printf ("Zone: %s using DTSTART Year: %i\n", CurrentZoneName, vzictime->year); #endif if (VzicPureOutput) { output_component_start (start_buffer, vzictime, TRUE, only_one_change); } else { /* For Outlook compatability we don't output the RDATE and use the same TZOFFSET for TZOFFSETFROM and TZOFFSETTO. */ vzictime->year = RDATE_YEAR; vzictime->month = 0; vzictime->day_code = DAY_SIMPLE; vzictime->day_number = 1; vzictime->time_code = TIME_WALL; vzictime->time_seconds = 0; output_component_start (start_buffer, vzictime, FALSE, TRUE); } fprintf (fp, "%s", start_buffer); /* This will look for matching components and output them as RDATEs instead of separate components. */ if (VzicPureOutput && !VzicNoRDates) check_for_rdates (fp, changes, i); output_component_end (fp, vzictime); vzictime->output = TRUE; if (!VzicPureOutput) break; } fprintf (fp, "END:VTIMEZONE\r\n"); } /* This sets the prev_stdoff and prev_walloff (i.e. the TZOFFSETFROM) of each VzicTime, using the stdoff and walloff of the previous VzicTime. It makes the rest of the code much simpler. */ static void set_previous_offsets (GArray *changes) { VzicTime *vzictime, *prev_vzictime; int i; prev_vzictime = &g_array_index (changes, VzicTime, 0); prev_vzictime->prev_stdoff = 0; prev_vzictime->prev_walloff = 0; for (i = 1; i < changes->len; i++) { vzictime = &g_array_index (changes, VzicTime, i); vzictime->prev_stdoff = prev_vzictime->stdoff; vzictime->prev_walloff = prev_vzictime->walloff; prev_vzictime = vzictime; } } /* Returns TRUE if we output an infinite recurrence. */ static gboolean check_for_recurrence (FILE *fp, GArray *changes, int idx) { VzicTime *vzictime_start, *vzictime; gboolean is_daylight_start, is_daylight; int last_match, i, next_year; GList *matching_elements = NULL, *elem; vzictime_start = &g_array_index (changes, VzicTime, idx); /* If this change has already been output, skip it. */ if (vzictime_start->output) return FALSE; /* There can't possibly be an RRULE starting from YEAR_MINIMUM. */ if (vzictime_start->year == YEAR_MINIMUM) return FALSE; is_daylight_start = (vzictime_start->stdoff != vzictime_start->walloff) ? TRUE : FALSE; #if 0 printf ("\nChecking: %s OFFSETFROM: %i %s\n", format_vzictime (vzictime_start), vzictime_start->prev_walloff, is_daylight_start ? "DAYLIGHT" : ""); #endif /* If this is an infinitely recurring change, output the RRULE and return. There won't be any changes after it that we could merge. */ if (vzictime_start->is_infinite) { vzictime_start->until = vzictime_start; vzictime_start->output = TRUE; return TRUE; } last_match = idx; next_year = vzictime_start->year + 1; for (i = idx + 1; i < changes->len; i++) { vzictime = &g_array_index (changes, VzicTime, i); is_daylight = (vzictime->stdoff != vzictime->walloff) ? TRUE : FALSE; if (vzictime->output) continue; #if 0 printf (" %s OFFSETFROM: %i %s\n", format_vzictime (vzictime), vzictime->prev_walloff, is_daylight ? "DAYLIGHT" : ""); #endif /* If it is more than one year ahead, we are finished, since we want consecutive years. */ if (vzictime->year > next_year) { break; } /* It must be the same type of component - STANDARD or DAYLIGHT. */ if (is_daylight != is_daylight_start) { continue; } /* It must be the following year, with the same month, day & time. It is possible that the time has a different code but does in fact match when normalized, but we don't care (for now at least). */ if (vzictime->year != next_year || vzictime->month != vzictime_start->month || vzictime->day_code != vzictime_start->day_code || vzictime->day_number != vzictime_start->day_number || vzictime->day_weekday != vzictime_start->day_weekday || vzictime->time_seconds != vzictime_start->time_seconds || vzictime->time_code != vzictime_start->time_code) { continue; } /* The TZOFFSETFROM and TZOFFSETTO must match. */ if (vzictime->prev_walloff != vzictime_start->prev_walloff) { continue; } if (vzictime->walloff != vzictime_start->walloff) { continue; } /* TZNAME must match. */ if (!timezones_match (vzictime->tzname, vzictime_start->tzname)) { continue; } /* We have a match. */ last_match = i; next_year = vzictime->year + 1; matching_elements = g_list_prepend (matching_elements, vzictime); } if (last_match == idx) return FALSE; #if 0 printf ("Found recurrence %i - %i!!!\n", vzictime_start->year, next_year - 1); #endif vzictime = &g_array_index (changes, VzicTime, last_match); /* We only use RRULEs if there are at least MIN_RRULE_OCCURRENCES occurrences, since otherwise RDATEs are more efficient. */ if (!vzictime->is_infinite) { int years = vzictime->year - vzictime_start->year + 1; #if 0 printf ("RRULE Years: %i\n", years); #endif if (years < MIN_RRULE_OCCURRENCES) return FALSE; } vzictime_start->until = vzictime; /* Mark all the changes as output. */ vzictime_start->output = TRUE; for (elem = matching_elements; elem; elem = elem->next) { vzictime = elem->data; vzictime->output = TRUE; } g_list_free (matching_elements); return TRUE; } static void check_for_rdates (FILE *fp, GArray *changes, int idx) { VzicTime *vzictime_start, *vzictime, tmp_vzictime; gboolean is_daylight_start, is_daylight; int i, year, month, day, time; vzictime_start = &g_array_index (changes, VzicTime, idx); is_daylight_start = (vzictime_start->stdoff != vzictime_start->walloff) ? TRUE : FALSE; #if 0 printf ("\nChecking: %s OFFSETFROM: %i %s\n", format_vzictime (vzictime_start), vzictime_start->prev_walloff, is_daylight_start ? "DAYLIGHT" : ""); #endif /* We want to go backwards through the array now, for Outlook compatability. (It only looks at the first DTSTART/RDATE.) */ for (i = idx + 1; i < changes->len; i++) { vzictime = &g_array_index (changes, VzicTime, i); is_daylight = (vzictime->stdoff != vzictime->walloff) ? TRUE : FALSE; if (vzictime->output) continue; #if 0 printf (" %s OFFSETFROM: %i %s\n", format_vzictime (vzictime), vzictime->prev_walloff, is_daylight ? "DAYLIGHT" : ""); #endif /* It must be the same type of component - STANDARD or DAYLIGHT. */ if (is_daylight != is_daylight_start) { continue; } /* The TZOFFSETFROM and TZOFFSETTO must match. */ if (vzictime->prev_walloff != vzictime_start->prev_walloff) { continue; } if (vzictime->walloff != vzictime_start->walloff) { continue; } /* TZNAME must match. */ if (!timezones_match (vzictime->tzname, vzictime_start->tzname)) { continue; } /* We have a match. */ tmp_vzictime = *vzictime; calculate_actual_time (&tmp_vzictime, TIME_WALL, vzictime->prev_stdoff, vzictime->prev_walloff); fprintf (fp, "RDATE:%s\r\n", format_time (tmp_vzictime.year, tmp_vzictime.month, tmp_vzictime.day_number, tmp_vzictime.time_seconds)); vzictime->output = TRUE; } } static gboolean timezones_match (char *tzname1, char *tzname2) { if (tzname1 && tzname2 && !strcmp (tzname1, tzname2)) return TRUE; if (!tzname1 && !tzname2) return TRUE; return FALSE; } /* Outputs the start of a VTIMEZONE component, with the BEGIN line, the DTSTART, TZOFFSETFROM, TZOFFSETTO & TZNAME properties. */ static int output_component_start (char *buffer, VzicTime *vzictime, gboolean output_rdate, gboolean use_same_tz_offset) { gboolean is_daylight, skip_day_offset = FALSE; gint year, month, day, time, day_offset = 0; GDate old_date, new_date; char *formatted_time; char line1[1024], line2[1024], line3[1024]; char line4[1024], line5[1024], line6[1024]; VzicTime tmp_vzictime; int prev_walloff; is_daylight = (vzictime->stdoff != vzictime->walloff) ? TRUE : FALSE; tmp_vzictime = *vzictime; day_offset = calculate_actual_time (&tmp_vzictime, TIME_WALL, vzictime->prev_stdoff, vzictime->prev_walloff); sprintf (line1, "BEGIN:%s\r\n", is_daylight ? "DAYLIGHT" : "STANDARD"); /* If the timezone only has one change, that means it uses the same offset forever, so we use the same TZOFFSETFROM as the TZOFFSETTO. (If the zone has more than one change, we don't output the first one.) */ if (use_same_tz_offset) prev_walloff = vzictime->walloff; else prev_walloff = vzictime->prev_walloff; if (vzictime->tzname) sprintf (line2, "TZNAME:%s\r\n", vzictime->tzname); else line2[0] = '\0'; sprintf (line3, "TZOFFSETFROM:%s\r\n", format_tz_offset (prev_walloff, !VzicPureOutput)); sprintf (line4, "TZOFFSETTO:%s\r\n", format_tz_offset (vzictime->walloff, !VzicPureOutput)); formatted_time = format_time (tmp_vzictime.year, tmp_vzictime.month, tmp_vzictime.day_number, tmp_vzictime.time_seconds); sprintf (line5, "DTSTART:%s\r\n", formatted_time); #if 0 /* The RDATE matching DTSTART is unnecessary */ if (output_rdate) sprintf (line6, "RDATE:%s\r\n", formatted_time); else #endif line6[0] = '\0'; sprintf (buffer, "%s%s%s%s%s%s", line1, line2, line3, line4, line5, line6); return day_offset; } /* Outputs the END line of the VTIMEZONE component. */ static void output_component_end (FILE *fp, VzicTime *vzictime) { gboolean is_daylight; is_daylight = (vzictime->stdoff != vzictime->walloff) ? TRUE : FALSE; fprintf (fp, "END:%s\r\n", is_daylight ? "DAYLIGHT" : "STANDARD"); } /* Initializes a VzicTime to 1st Jan in YEAR_MINIMUM at midnight, with all offsets set to 0. */ static void vzictime_init (VzicTime *vzictime) { vzictime->year = YEAR_MINIMUM; vzictime->month = 0; vzictime->day_code = DAY_SIMPLE; vzictime->day_number = 1; vzictime->day_weekday = 0; vzictime->time_seconds = 0; vzictime->time_code = TIME_UNIVERSAL; vzictime->stdoff = 0; vzictime->walloff = 0; vzictime->is_infinite = FALSE; vzictime->until = NULL; vzictime->output = FALSE; vzictime->prev_stdoff = 0; vzictime->prev_walloff = 0; vzictime->tzname = NULL; } /* This calculates the actual local time that a change will occur, given the offsets from standard and wall-clock time. It returns -1 or 1 if it had to move backwards or forwards one day while converting to local time. If it does this then we need to change the RRULEs we output. */ static int calculate_actual_time (VzicTime *vzictime, TimeCode time_code, int stdoff, int walloff) { GDate date; gint day_offset, days_in_month, weekday, offset, result; vzictime->time_seconds = calculate_wall_time (vzictime->time_seconds, vzictime->time_code, stdoff, walloff, &day_offset); if (vzictime->day_code != DAY_SIMPLE) { if (vzictime->year == YEAR_MINIMUM || vzictime->year == YEAR_MAXIMUM) { fprintf (stderr, "In calculate_actual_time: invalid year\n"); exit (0); } g_date_clear (&date, 1); days_in_month = g_date_days_in_month (vzictime->month + 1, vzictime->year); /* Note that the day_code refers to the date before we convert it to a wall-clock date and time. So we find the day it was referring to, then make any adjustments needed due to converting the time. */ if (vzictime->day_code == DAY_LAST_WEEKDAY) { /* Find out what day the last day of the month is. */ g_date_set_dmy (&date, days_in_month, vzictime->month + 1, vzictime->year); weekday = g_date_weekday (&date) % 7; /* Calculate how many days we have to go back to get to day_weekday. */ offset = (weekday + 7 - vzictime->day_weekday) % 7; vzictime->day_number = days_in_month - offset; } else { /* Find out what day day_number actually is. */ g_date_set_dmy (&date, vzictime->day_number, vzictime->month + 1, vzictime->year); weekday = g_date_weekday (&date) % 7; if (vzictime->day_code == DAY_WEEKDAY_ON_OR_AFTER) offset = (vzictime->day_weekday + 7 - weekday) % 7; else offset = - ((weekday + 7 - vzictime->day_weekday) % 7); vzictime->day_number = vzictime->day_number + offset; } vzictime->day_code = DAY_SIMPLE; if (vzictime->day_number <= 0 || vzictime->day_number > days_in_month) { fprintf (stderr, "Day overflow: %i\n", vzictime->day_number); exit (1); } } #if 0 fprintf (stderr, "%s -> %i/%i/%i\n", dump_day_coded (vzictime->day_code, vzictime->day_number, vzictime->day_weekday), vzictime->day_number, vzictime->month + 1, vzictime->year); #endif fix_time_overflow (&vzictime->year, &vzictime->month, &vzictime->day_number, day_offset); /* If we want UTC time, we have to convert it now. */ if (time_code == TIME_UNIVERSAL) { vzictime->time_seconds = calculate_until_time (vzictime->time_seconds, TIME_WALL, stdoff, walloff, &vzictime->year, &vzictime->month, &vzictime->day_number); } return day_offset; } /* This converts the given time into universal time (UTC), to be used in the UNTIL property. */ static int calculate_until_time (int time, TimeCode time_code, int stdoff, int walloff, int *year, int *month, int *day) { int result, day_offset; day_offset = 0; switch (time_code) { case TIME_WALL: result = time - walloff; break; case TIME_STANDARD: result = time - stdoff; break; case TIME_UNIVERSAL: return time; default: fprintf (stderr, "Invalid time code\n"); exit (1); } if (result < 0) { result += 24 * 60 * 60; day_offset = -1; } else if (result >= 24 * 60 * 60) { result -= 24 * 60 * 60; day_offset = 1; } /* Sanity check - we shouldn't have an overflow any more. */ if (result < 0 || result >= 24 * 60 * 60) { fprintf (stderr, "Time overflow: %i\n", result); abort (); } fix_time_overflow (year, month, day, day_offset); return result; } /* This converts the given time into wall clock time (the local standard time with any adjustment for daylight-saving). */ static int calculate_wall_time (int time, TimeCode time_code, int stdoff, int walloff, int *day_offset) { int result; *day_offset = 0; switch (time_code) { case TIME_WALL: /* We don't just return here so we can handle 24:00:00 below */ result = time; break; case TIME_STANDARD: /* We have a local standard time, so we have to subtract stdoff to get back to UTC, then add walloff to get wall time. */ result = time - stdoff + walloff; break; case TIME_UNIVERSAL: result = time + walloff; break; default: fprintf (stderr, "Invalid time code\n"); exit (1); } if (result < 0) { result += 24 * 60 * 60; *day_offset = -1; } else if (result >= 24 * 60 * 60) { result -= 24 * 60 * 60; *day_offset = 1; } /* Sanity check - we shouldn't have an overflow any more. */ if (result < 0 || result >= 24 * 60 * 60) { fprintf (stderr, "Time overflow: %i\n", result); exit (1); } #if 0 printf ("%s -> ", dump_time (time, time_code, TRUE)); printf ("%s (%i)\n", dump_time (result, TIME_WALL, TRUE), *day_offset); #endif return result; } static void fix_time_overflow (int *year, int *month, int *day, int day_offset) { if (day_offset == -1) { *day = *day - 1; if (*day == 0) { *month = *month - 1; if (*month == -1) { *month = 11; *year = *year - 1; } *day = g_date_days_in_month (*month + 1, *year); } } else if (day_offset == 1) { *day = *day + 1; if (*day > g_date_days_in_month (*month + 1, *year)) { *month = *month + 1; if (*month == 12) { *month = 0; *year = *year + 1; } *day = 1; } } } static char* format_time (int year, int month, int day, int time) { static char buffer[128]; int hour, minute, second; /* When we are outputting the first component year will be YEAR_MINIMUM. We used to use 1 when outputting this, but Outlook doesn't like any years less that 1600, so we use 1600 instead. We don't output the first change for most zones now, so it doesn't matter too much. */ if (year == YEAR_MINIMUM) year = 1601; /* We just use 9999 here, so we keep to 4 characters. But this should only be needed when debugging - it shouldn't be needed in the VTIMEZONEs. */ if (year == YEAR_MAXIMUM) { fprintf (stderr, "format_time: YEAR_MAXIMUM used\n"); year = 9999; } hour = time / 3600; minute = (time % 3600) / 60; second = time % 60; sprintf (buffer, "%04i%02i%02iT%02i%02i%02i", year, month + 1, day, hour, minute, second); return buffer; } /* Outlook doesn't support 6-digit values, i.e. including the seconds, so we round to the nearest minute. No current offsets use the seconds value, so we aren't losing much. */ static char* format_tz_offset (int tz_offset, gboolean round_seconds) { static char buffer[128]; char *sign = "+"; int hours, minutes, seconds; if (tz_offset < 0) { tz_offset = -tz_offset; sign = "-"; } if (round_seconds) tz_offset += 30; hours = tz_offset / 3600; minutes = (tz_offset % 3600) / 60; seconds = tz_offset % 60; if (round_seconds) seconds = 0; /* Sanity check. Standard timezone offsets shouldn't be much more than 12 hours, and daylight saving shouldn't change it by more than a few hours. (The maximum offset is 15 hours 56 minutes at present.) */ if (hours < 0 || hours >= 24 || minutes < 0 || minutes >= 60 || seconds < 0 || seconds >= 60) { fprintf (stderr, "WARNING: Strange timezone offset: H:%i M:%i S:%i\n", hours, minutes, seconds); } if (seconds == 0) sprintf (buffer, "%s%02i%02i", sign, hours, minutes); else sprintf (buffer, "%s%02i%02i%02i", sign, hours, minutes, seconds); return buffer; } static gboolean output_rrule (char *rrule_buffer, int month, DayCode day_code, int day_number, int day_weekday, int day_offset, char *until) { char buffer[1024], buffer2[1024]; buffer[0] = '\0'; if (day_offset > 1 || day_offset < -1) { fprintf (stderr, "Invalid day_offset: %i\n", day_offset); exit (0); } /* If the DTSTART time was moved to another day when converting to local time, we need to adjust the RRULE accordingly. e.g. If the original RRULE was on the 19th of the month, but DTSTART was moved 1 day forward, then we output the 20th of the month instead. */ if (day_offset == 1) { if (day_code != DAY_LAST_WEEKDAY) day_number++; day_weekday = (day_weekday + 1) % 7; /* Check we don't use February 29th. */ if (month == 1 && day_number > 28) { fprintf (stderr, "Can't format RRULE - out of bounds. Month: %i Day number: %i\n", month + 1, day_number); exit (0); } /* If we go past the end of the month, move to the next month. */ if (day_code != DAY_LAST_WEEKDAY && day_number > DaysInMonth[month]) { month++; day_number = 1; } } else if (day_offset == -1) { if (day_code != DAY_LAST_WEEKDAY) day_number--; day_weekday = (day_weekday + 6) % 7; if (day_code != DAY_LAST_WEEKDAY && day_number < 1) fprintf (stderr, "Month: %i Day number: %i\n", month + 1, day_number); } switch (day_code) { case DAY_SIMPLE: /* Outlook (2000) will not parse the simple YEARLY RRULEs in VTIMEZONEs, or BYMONTHDAY, or BYYEARDAY, which makes this option difficult! Currently we use something like BYDAY=1SU, which will be incorrect at times. This only affects Asia/Baghdad, Asia/Gaza, Asia/Jerusalem & Asia/Damascus at present (and Jerusalem doesn't have specific rules at the moment anyway, so that isn't a big loss). */ if (!VzicPureOutput) { if (day_number < 8) { printf ("WARNING: %s: Outputting BYDAY=1SU instead of BYMONTHDAY=1-7 for Outlook compatability\n", CurrentZoneName); sprintf (buffer, "RRULE:FREQ=YEARLY;BYMONTH=%i;BYDAY=1SU", month + 1); } else if (day_number < 15) { printf ("WARNING: %s: Outputting BYDAY=2SU instead of BYMONTHDAY=8-14 for Outlook compatability\n", CurrentZoneName); sprintf (buffer, "RRULE:FREQ=YEARLY;BYMONTH=%i;BYDAY=2SU", month + 1); } else if (day_number < 22) { printf ("WARNING: %s: Outputting BYDAY=3SU instead of BYMONTHDAY=15-21 for Outlook compatability\n", CurrentZoneName); sprintf (buffer, "RRULE:FREQ=YEARLY;BYMONTH=%i;BYDAY=3SU", month + 1); } else { printf ("ERROR: %s: Couldn't output RRULE (day=%i) compatible with Outlook\n", CurrentZoneName, day_number); exit (1); } } else { sprintf (buffer, "RRULE:FREQ=YEARLY"); } break; case DAY_WEEKDAY_ON_OR_AFTER: if (day_number > DaysInMonth[month] - 6) { /* This isn't actually needed at present. */ #if 0 fprintf (stderr, "DAY_WEEKDAY_ON_OR_AFTER: %i %i\n", day_number, month + 1); #endif if (!VzicPureOutput) { printf ("ERROR: %s: Couldn't output RRULE (day>=x) compatible with Outlook\n", CurrentZoneName); exit (1); } else { /* We do 6 days at the end of this month, and 1 at the start of the next. We can't do this if we want Outlook compatability, as it needs BYMONTHDAY, which Outlook doesn't support. */ /* sprintf (buffer, "RRULE:FREQ=YEARLY;BYMONTH=%i;BYMONTHDAY=%i,%i,%i,%i,%i,%i;BYDAY=%s", month + 1, day_number, day_number + 1, day_number + 2, day_number + 3, day_number + 4, day_number + 5, WeekDays[day_weekday]); sprintf (buffer2, "RRULE:FREQ=YEARLY;BYMONTH=%i;BYMONTHDAY=1;BYDAY=%s", (month + 1) % 12 + 1, WeekDays[day_weekday]); sprintf (rrule_buffer, "%s%s\n%s%s\r\n", buffer, until, buffer2, until); */ /* Multiple RRULEs within the component are illegal according to new iCal RFC 5545, so combine the above RRULEs (commented) into a single RRULE using BYYEARDAY */ day_number = 0; int i; for (i = month+1; i < 12; i++) { day_number += DaysInMonth[i]; } sprintf (rrule_buffer, "RRULE:FREQ=YEARLY;BYYEARDAY=-%i,-%i,-%i,-%i,-%i,-%i,-%i;BYDAY=%s%s\r\n", day_number, day_number+1, day_number+2, day_number+3, day_number+4, day_number+5, day_number+6, WeekDays[day_weekday], until); return TRUE; } } if (!output_rrule_2 (buffer, month, day_number, day_weekday)) return FALSE; break; case DAY_WEEKDAY_ON_OR_BEFORE: if (day_number < 7) { /* FIXME: This is unimplemented, but it isn't needed at present anway. */ fprintf (stderr, "DAY_WEEKDAY_ON_OR_BEFORE: %i. Unimplemented. Exiting...\n", day_number); exit (0); } if (!output_rrule_2 (buffer, month, day_number - 6, day_weekday)) return FALSE; break; case DAY_LAST_WEEKDAY: if (day_offset == 1) { if (month == 1) { fprintf (stderr, "DAY_LAST_WEEKDAY - day moved, in February - can't fix\n"); exit (0); } /* This is only used once at present, for Africa/Cairo. */ #if 0 fprintf (stderr, "DAY_LAST_WEEKDAY - day moved\n"); #endif if (!VzicPureOutput) { printf ("WARNING: %s: Modifying RRULE (last weekday) for Outlook compatability\n", CurrentZoneName); sprintf (buffer, "RRULE:FREQ=YEARLY;BYMONTH=%i;BYDAY=-1%s", month + 1, WeekDays[day_weekday]); printf (" Outputting: %s\n", buffer); } else { /* We do 6 days at the end of this month, and 1 at the start of the next. We can't do this if we want Outlook compatability, as it needs BYMONTHDAY, which Outlook doesn't support. */ /* day_number = DaysInMonth[month]; sprintf (buffer, "RRULE:FREQ=YEARLY;BYMONTH=%i;BYMONTHDAY=%i,%i,%i,%i,%i,%i;BYDAY=%s", month + 1, day_number - 5, day_number - 4, day_number - 3, day_number - 2, day_number - 1, day_number, WeekDays[day_weekday]); sprintf (buffer2, "RRULE:FREQ=YEARLY;BYMONTH=%i;BYMONTHDAY=1;BYDAY=%s", (month + 1) % 12 + 1, WeekDays[day_weekday]); sprintf (rrule_buffer, "%s%s\r\n%s%s\r\n", buffer, until, buffer2, until); */ /* Multiple RRULEs within the component are illegal according to new iCal RFC 5545, so combine the above RRULEs (commented) into a single RRULE using BYYEARDAY */ day_number = 0; int i; for (i = month+1; i < 12; i++) { day_number += DaysInMonth[i]; } sprintf (rrule_buffer, "RRULE:FREQ=YEARLY;BYYEARDAY=-%i,-%i,-%i,-%i,-%i,-%i,-%i;BYDAY=%s%s\r\n", day_number, day_number+1, day_number+2, day_number+3, day_number+4, day_number+5, day_number+6, WeekDays[day_weekday], until); return TRUE; } } else if (day_offset == -1) { /* We do 7 days 1 day before the end of this month. */ day_number = DaysInMonth[month]; if (!output_rrule_2 (buffer, month, day_number - 7, day_weekday)) return FALSE; sprintf (rrule_buffer, "%s%s\r\n", buffer, until); return TRUE; } sprintf (buffer, "RRULE:FREQ=YEARLY;BYMONTH=%i;BYDAY=-1%s", month + 1, WeekDays[day_weekday]); break; default: fprintf (stderr, "Invalid day code\n"); exit (1); } sprintf (rrule_buffer, "%s%s\r\n", buffer, until); return TRUE; } /* This tries to convert a RRULE like 'BYMONTHDAY=8,9,10,11,12,13,14;BYDAY=FR' into 'BYDAY=2FR'. We need this since Outlook doesn't accept BYMONTHDAY. It returns FALSE if conversion is not possible. */ static gboolean output_rrule_2 (char *buffer, int month, int day_number, int day_weekday) { if (day_number == 1) { /* Convert it to a BYDAY=1SU type of RRULE. */ sprintf (buffer, "RRULE:FREQ=YEARLY;BYMONTH=%i;BYDAY=1%s", month + 1, WeekDays[day_weekday]); } else if (day_number == 8) { /* Convert it to a BYDAY=2SU type of RRULE. */ sprintf (buffer, "RRULE:FREQ=YEARLY;BYMONTH=%i;BYDAY=2%s", month + 1, WeekDays[day_weekday]); } else if (day_number == 15) { /* Convert it to a BYDAY=3SU type of RRULE. */ sprintf (buffer, "RRULE:FREQ=YEARLY;BYMONTH=%i;BYDAY=3%s", month + 1, WeekDays[day_weekday]); } else if (day_number == 22) { /* Convert it to a BYDAY=4SU type of RRULE. (Currently not used.) */ sprintf (buffer, "RRULE:FREQ=YEARLY;BYMONTH=%i;BYDAY=4%s", month + 1, WeekDays[day_weekday]); } else if (month != 1 && day_number == DaysInMonth[month] - 6) { /* Convert it to a BYDAY=-1SU type of RRULE. (But never for February.) */ sprintf (buffer, "RRULE:FREQ=YEARLY;BYMONTH=%i;BYDAY=-1%s", month + 1, WeekDays[day_weekday]); } else { /* Can't convert to a correct RRULE. If we want Outlook compatability we have to use a slightly incorrect RRULE, so the time change will be 1 week out every 7 or so years. Alternatively we could possibly move the change by an hour or so so we would always be 1 or 2 hours out, but never 1 week out. Yes, that sounds a better idea. */ if (!VzicPureOutput) { printf ("WARNING: %s: Modifying RRULE to be compatible with Outlook (day >= %i, month = %i)\n", CurrentZoneName, day_number, month + 1); if (day_number == 2) { /* Convert it to a BYDAY=1SU type of RRULE. This is needed for Asia/Karachi. */ sprintf (buffer, "RRULE:FREQ=YEARLY;BYMONTH=%i;BYDAY=1%s", month + 1, WeekDays[day_weekday]); } else if (day_number == 9) { /* Convert it to a BYDAY=2SU type of RRULE. This is needed for Antarctica/Palmer & America/Santiago. */ sprintf (buffer, "RRULE:FREQ=YEARLY;BYMONTH=%i;BYDAY=2%s", month + 1, WeekDays[day_weekday]); } else if (month != 1 && day_number <= DaysInMonth[month] - 7 && day_number > DaysInMonth[month] - 14) { /* Convert it to a BYDAY=-1SU type of RRULE. (But never for February.) This is needed for America/Godthab. */ sprintf (buffer, "RRULE:FREQ=YEARLY;BYMONTH=%i;BYDAY=-1%s", month + 1, WeekDays[day_weekday]); } else { printf ("ERROR: %s: Couldn't modify RRULE to be compatible with Outlook (day >= %i, month = %i)\n", CurrentZoneName, day_number, month + 1); exit (1); } } else { sprintf (buffer, "RRULE:FREQ=YEARLY;BYMONTH=%i;BYMONTHDAY=%i,%i,%i,%i,%i,%i,%i;BYDAY=%s", month + 1, day_number, day_number + 1, day_number + 2, day_number + 3, day_number + 4, day_number + 5, day_number + 6, WeekDays[day_weekday]); } } return TRUE; } static char* format_vzictime (VzicTime *vzictime) { static char buffer[1024]; sprintf (buffer, "%s %2i %s %s %i %i %s", dump_year (vzictime->year), vzictime->month + 1, dump_day_coded (vzictime->day_code, vzictime->day_number, vzictime->day_weekday), dump_time (vzictime->time_seconds, vzictime->time_code, TRUE), vzictime->stdoff, vzictime->walloff, vzictime->is_infinite ? "INFINITE" : ""); return buffer; } static void dump_changes (FILE *fp, char *zone_name, GArray *changes) { VzicTime *vzictime, *vzictime2 = NULL; int i, year_offset, year; for (i = 0; i < changes->len; i++) { vzictime = &g_array_index (changes, VzicTime, i); if (vzictime->year > MAX_CHANGES_YEAR) return; dump_change (fp, zone_name, vzictime, vzictime->year); } if (changes->len < 2) return; /* Now see if the changes array ends with a pair of recurring changes. */ vzictime = &g_array_index (changes, VzicTime, changes->len - 2); vzictime2 = &g_array_index (changes, VzicTime, changes->len - 1); if (!vzictime->is_infinite || !vzictime2->is_infinite) return; year_offset = 1; for (;;) { year = vzictime->year + year_offset; if (year > MAX_CHANGES_YEAR) break; dump_change (fp, zone_name, vzictime, year); year = vzictime2->year + year_offset; if (year > MAX_CHANGES_YEAR) break; dump_change (fp, zone_name, vzictime2, year); year_offset++; } } static void dump_change (FILE *fp, char *zone_name, VzicTime *vzictime, int year) { int hour, minute, second; VzicTime tmp_vzictime; static char *months[] = { "Jan", "Feb", "Mar", "Apr", "May", "Jun", "Jul", "Aug", "Sep", "Oct", "Nov", "Dec" }; /* Output format is: Zone-Name [tab] Date [tab] Time [tab] UTC-Offset The Date and Time fields specify the time change in UTC. The UTC Offset is for local (wall-clock) time. It is the amount of time to add to UTC to get local time. */ fprintf (fp, "%s\t", zone_name); if (year == YEAR_MINIMUM) { fprintf (fp, " 1 Jan 0001\t 0:00:00", zone_name); } else if (year == YEAR_MAXIMUM) { fprintf (stderr, "Maximum year found in change time\n"); exit (1); } else { tmp_vzictime = *vzictime; tmp_vzictime.year = year; calculate_actual_time (&tmp_vzictime, TIME_UNIVERSAL, vzictime->prev_stdoff, vzictime->prev_walloff); hour = tmp_vzictime.time_seconds / 3600; minute = (tmp_vzictime.time_seconds % 3600) / 60; second = tmp_vzictime.time_seconds % 60; fprintf (fp, "%2i %s %04i\t%2i:%02i:%02i", tmp_vzictime.day_number, months[tmp_vzictime.month], tmp_vzictime.year, hour, minute, second); } fprintf (fp, "\t%s", format_tz_offset (vzictime->walloff, FALSE)); fprintf (fp, "\r\n"); } void ensure_directory_exists (char *directory) { struct stat filestat; if (stat (directory, &filestat) != 0) { /* If the directory doesn't exist, try to create it. */ if (errno == ENOENT) { if (mkdir (directory, 0777) != 0) { fprintf (stderr, "Can't create directory: %s\n", directory); exit (1); } } else { fprintf (stderr, "Error calling stat() on directory: %s\n", directory); exit (1); } } else if (!S_ISDIR (filestat.st_mode)) { fprintf (stderr, "Can't create directory, already exists: %s\n", directory); exit (1); } } static void expand_tzid_prefix (void) { char *src, *dest; char date_buf[16]; char ch1, ch2; time_t t; struct tm *tm; /* Get today's date as a string in the format "YYYYMMDD". */ t = time (NULL); tm = localtime (&t); sprintf (date_buf, "%4i%02i%02i", tm->tm_year + 1900, tm->tm_mon + 1, tm->tm_mday); src = TZIDPrefix; dest = TZIDPrefixExpanded; while (ch1 = *src++) { /* Look for a '%'. */ if (ch1 == '%') { ch2 = *src++; if (ch2 == 'D') { /* '%D' gets expanded into the date string. */ strcpy (dest, date_buf); dest += strlen (dest); } else if (ch2 == '%') { /* '%%' gets converted into one '%'. */ *dest++ = '%'; } else { /* Anything else is output as is. */ *dest++ = '%'; *dest++ = ch2; } } else { *dest++ = ch1; } } #if 0 printf ("TZID : %s\n", TZIDPrefix); printf ("Expanded: %s\n", TZIDPrefixExpanded); #endif } cyrus-imapd-2.5.10/tools/vzic/vzic-test.pl0000755000175000017500000001032313001236020015342 00000000000000#!/usr/bin/perl -w # # Vzic - a program to convert Olson timezone database files into VZTIMEZONE # files compatible with the iCalendar specification (RFC2445). # # Copyright (C) 2001 Ximian, Inc. # Copyright (C) 2003 Damon Chaplin. # # Author: Damon Chaplin # # This program is free software; you can redistribute it and/or modify # it under the terms of the GNU General Public License as published by # the Free Software Foundation; either version 2 of the License, or # (at your option) any later version. # # This program is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the # GNU General Public License for more details. # # You should have received a copy of the GNU General Public License # along with this program; if not, write to the Free Software # Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307, USA. # # # This outputs an iCalendar file containing one event in each timezone, # as well as all the VTIMEZONEs. We use it for testing compatability with # other iCalendar apps like Outlook, by trying to import it there. # # Currently we have 377 timezones (with tzdata2001d). # # Set this to the toplevel directory of the VTIMEZONE files. $ZONEINFO_DIR = "/home/damon/src/zoneinfo"; $output_file = "calendar.ics"; # Save this so we can restore it later. $input_record_separator = $/; chdir $ZONEINFO_DIR || die "Can't cd to $ZONEINFO_DIR"; # Create the output file, to contain all the VEVENTs & VTIMEZONEs. open (OUTPUTFILE, ">$output_file") || die "Can't create file: $output_file"; # Output the standard header. print OUTPUTFILE <; $/ = $input_record_separator; close (ZONEFILE); # Strip the stuff before and after the VTIMEZONE component $vtimezone =~ s/^.*BEGIN:VTIMEZONE/BEGIN:VTIMEZONE/s; $vtimezone =~ s/END:VTIMEZONE.*$/END:VTIMEZONE\n/s; print OUTPUTFILE $vtimezone; # Find the TZID. $vtimezone =~ m/TZID:(.*)/; $tzid = $1; # print "TZID: $tzid\n"; # Find the location. $file =~ m/(.*)\.ics/; $location = $1; # print "LOCATION: $location\n"; # Try to find the current UTC offset that Outlook will use. # If there is an RRULE, we look for the first 2 TZOFFSETTO properties, # else we just get the first one. if ($vtimezone =~ m/RRULE/) { $vtimezone =~ m/TZOFFSETTO:([+-]?\d+)/; $tzoffsetto = $1; $vtimezone =~ m/TZOFFSETFROM:([+-]?\d+)/; $tzoffsetfrom = $1; $tzoffset = "$tzoffsetfrom/$tzoffsetto"; } else { $vtimezone =~ m/TZOFFSETTO:([+-]?\d+)/s; $tzoffset = $1; } # print "TZOFFSET: $tzoffset\n"; # We put each event on a separate day in 2001 and Jan 2002. $day_num = $zone_num; if ($day_num >= 365) { $year = 2002; $day_num -= 365; } else { $year = 2001; } $month = -1; for ($i = 0; $i < 12; $i++) { if ($day_num < $days_in_month[$i]) { $month = $i; last; } $day_num -= $days_in_month[$i] } if ($month == -1) { die "month = -1"; } $month++; $day_num++; $date = sprintf ("%i%02i%02i", $year, $month, $day_num); # print "Date: $date\n"; # Output a VEVENT using the timezone. print OUTPUTFILE < # # This program is free software; you can redistribute it and/or modify # it under the terms of the GNU General Public License as published by # the Free Software Foundation; either version 2 of the License, or # (at your option) any later version. # # This program is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the # GNU General Public License for more details. # # You should have received a copy of the GNU General Public License # along with this program; if not, write to the Free Software # Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307, USA. # # # This reads the Olson timezone files, strips any comments, and outputs them # in a very simple format with tab-separated fields. It is used to compare # with the output of dump_zone_data() and dump_rule_data() to double-check # that we have parsed the files correctly. # my $zones_fh = "zonesfile"; my $rules_fh = "rulesfile"; my %Rules; if ($#ARGV != 0) { die "Usage: $0 "; } my $OLSON_DIR = $ARGV[0]; # We place output in subdirectories of the current directory. my $OUTPUT_DIR = "zoneinfo"; if (! -d "$OUTPUT_DIR") { mkdir ("$OUTPUT_DIR", 0777) || die "Can't create directory: $OUTPUT_DIR"; } if (! -d "$OUTPUT_DIR/ZonesPerl") { mkdir ("$OUTPUT_DIR/ZonesPerl", 0777) || die "Can't create directory: $OUTPUT_DIR/ZonesPerl"; } if (! -d "$OUTPUT_DIR/RulesPerl") { mkdir ("$OUTPUT_DIR/RulesPerl", 0777) || die "Can't create directory: $OUTPUT_DIR/RulesPerl"; } &ReadOlsonFile ("africa"); &ReadOlsonFile ("antarctica"); &ReadOlsonFile ("asia"); &ReadOlsonFile ("australasia"); &ReadOlsonFile ("europe"); &ReadOlsonFile ("northamerica"); &ReadOlsonFile ("southamerica"); # These are backwards-compatability and weird stuff. #&ReadOlsonFile ("backward"); #&ReadOlsonFile ("etcetera"); #&ReadOlsonFile ("leapseconds"); #&ReadOlsonFile ("pacificnew"); #&ReadOlsonFile ("solar87"); #&ReadOlsonFile ("solar88"); #&ReadOlsonFile ("solar89"); # We don't do this one since it is not useful and the use of '"' in the Zone # line messes up our split() command. #&ReadOlsonFile ("factory"); # We don't do this since the vzic program can't do it. #&ReadOlsonFile ("systemv"); 1; sub ReadOlsonFile { my ($file) = @_; # print ("Reading olson file: $file\n"); open (OLSONFILE, "$OLSON_DIR/$file") || die "Can't open file: $file"; open ($zones_fh, ">$OUTPUT_DIR/ZonesPerl/$file") || die "Can't open file: $OUTPUT_DIR/ZonesPerl/$file"; open ($rules_fh, ">$OUTPUT_DIR/RulesPerl/$file") || die "Can't open file: $OUTPUT_DIR/RulesPerl/$file"; %Rules = (); my $zone_continues = 0; while () { next if (m/^#/); # '#' characters can appear in strings, but the Olson files don't use # that feature at present so we treat all '#' as comments for now. s/#.*//; next if (m/^\s*$/); if ($zone_continues) { $zone_continues = &ReadZoneContinuationLine; } elsif (m/^Rule\s/) { &ReadRuleLine; } elsif (m/^Zone\s/) { $zone_continues = &ReadZoneLine; } elsif (m/^Link\s/) { # print "Link: $link_from, $link_to\n"; } elsif (m/^Leap\s/) { # print "Leap\n"; } else { die "Invalid line: $_"; } } # print ("Read olson file: $file\n"); foreach $key (sort (keys (%Rules))) { print $rules_fh "$Rules{$key}" } close ($zones_fh); close ($rules_fh); close (OLSONFILE); } sub ReadZoneLine { my ($zone, $name, $gmtoff, $rules_save, $format, $until_year, $until_month, $until_day, $until_time, $remainder) = split ' ', $_, 10; return &ReadZoneLineCommon ($zone, $name, $gmtoff, $rules_save, $format, $until_year, $until_month, $until_day, $until_time); } sub ReadZoneContinuationLine { my ($gmtoff, $rules_save, $format, $until_year, $until_month, $until_day, $until_time, $remainder) = split ' ', $_, 8; return &ReadZoneLineCommon ("", "", $gmtoff, $rules_save, $format, $until_year, $until_month, $until_day, $until_time); } sub ReadZoneLineCommon { my ($zone, $name, $gmtoff, $rules_save, $format, $until_year, $until_month, $until_day, $until_time) = @_; if (!defined ($until_year)) { $until_year = ""; } if (!defined ($until_month)) { $until_month = ""; } if (!defined ($until_day)) { $until_day = ""; } if (!defined ($until_time)) { $until_time = ""; } # A few of the gmtoffsets have an unnecessary :00 seconds. $gmtoff =~ s/(\d+):(\d+):00/$1:$2/; # Make sure the gmtoff does have minutes. $gmtoff =~ s/^(-?\d+)$/$1:00/; # Fix a few other bits so they all use the same format. if ($gmtoff eq "0") { $gmtoff = "0:00"; } $until_time =~ s/^0(\d):/$1:/; if ($until_time eq "0:00") { $until_time = ""; } if ($until_day eq "1" && $until_time eq "") { $until_day = ""; } if ($until_month eq "Jan" && $until_day eq "" && $until_time eq "") { $until_month = ""; } # For Zone continuation lines we need to insert an extra TAB. if (!$zone) { $zone = "\t" }; print $zones_fh "$zone\t$name\t$gmtoff\t$rules_save\t$format\t$until_year\t$until_month\t$until_day\t$until_time\n"; if (defined ($until_year) && $until_year) { return 1; } else { return 0; } } sub ReadRuleLine { my ($rule, $name, $from, $to, $type, $in, $on, $at, $save, $letter_s, $remainder) = split; $at =~ s/(\d+:\d+):00/$1/; $save =~ s/(\d+:\d+):00/$1/; if ($save eq "0:00") { $save = "0"; } $Rules{$name} .= "$rule\t$name\t$from\t$to\t$type\t$in\t$on\t$at\t$save\t$letter_s\n"; # print $rules_fh "$rule\t$name\t$from\t$to\t$type\t$in\t$on\t$at\t$save\t$letter_s\n"; } cyrus-imapd-2.5.10/tools/vzic/ChangeLog0000644000175000017500000000377013001236020014634 000000000000002006-03-18 Damon Chaplin * Released Vzic 1.3 2006-03-18 Damon Chaplin * vzic-output.c (expand_tzname): added special case for America/Nome. (output_rrule): made hacks a bit more general, to handle Asia/Gaza which now has a day=4 rule. At some point we should check what newer versions of Outlook can handle so we can be more accurate. * vzic-dump.c (dump_time_zone_names): try looking for timezone info using original and linked name. * README, *.c: fixed spelling 'compatable' -> 'compatible'. * vzic.c: patch from Jonathan Guthrie to support a --olson-dir option. 2003-10-25 Damon Chaplin * Released Vzic 1.2 2003-10-25 Damon Chaplin * vzic-output.c: * Makefile: moved the PRODUCT_ID and TZID_PREFIX settings to the Makefile and changed the default so people don't accidentally use the same IDs as Evolution. * vzic-parse.c (parse_time): substitute 23:59:59 when we read a time of 24:00:00. This is a bit of a kludge to avoid problems, since 24:00:00 is not a valid iCalendar time. Since 24:00:00 is only used for a few timezones in the 1930s it doesn't matter too much. To write a correct fix we'd need to review all the code that deals with times to see if it would be affected, e.g. a time of 24:00 on one day should be considered equal to 0:00 the next day. We'd also need to adjust the output times to use 0:00 the next day rather than 24:00. If we need to output recurrence rules that would be a problem, since 'last saturday at 24:00' can't be easily converted to another rule that uses 0:00 instead. 2003-10-22 Damon Chaplin * Released Vzic 1.1 2003-10-22 Damon Chaplin * vzic-parse.c (parse_time): allow a time of 24:00, as used in the America/Montreal and America/Toronto rules in the 1930s! I'm not 100% sure the rest of the code will handle this OK, but it only affects the 'pure' output. 2003-09-01 Damon Chaplin * Released Vzic 1.0 cyrus-imapd-2.5.10/tools/vzic/Makefile0000644000175000017500000000535712772415051014546 00000000000000 # # You will need to set this to the directory that the Olson timezone data # files are in. # OLSON_DIR = . # This is used as the PRODID property on the iCalendar files output. # It identifies the product which created the iCalendar objects. # So you need to substitute your own organization name and product. PRODUCT_ID = -//CyrusIMAP.org//Cyrus %s//EN # This is what libical-evolution uses. #PRODUCT_ID = -//Ximian//NONSGML Evolution Olson-VTIMEZONE Converter//EN # This is used to create unique IDs for each VTIMEZONE component. # The prefix is put before each timezone city name. It should start and end # with a '/'. The first part, i.e. 'myorganization.org' below, should be # a unique vendor ID, e.g. use a hostname. The part after that can be # anything you want. We use a date and version number for libical. The %D # gets expanded to today's date. There is also a vzic-merge.pl which can be # used to merge changes into a master set of VTIMEZONEs. If a VTIMEZONE has # changed, it bumps the version number on the end of this prefix. */ #TZID_PREFIX = /myorganization.org/%D_1/ TZID_PREFIX = # This is what libical-evolution uses. #TZID_PREFIX = /softwarestudio.org/Olson_%D_1/ # Set any -I include directories to find the libical header files, and the # libical library to link with. You only need these if you want to run the # tests. You may need to change the '#include ' line at the top of # test-vzic.c as well. LIBICAL_CFLAGS = LIBICAL_LDADD = -lical # # You shouldn't need to change the rest of the file. # GLIB_CFLAGS = `pkg-config --cflags glib-2.0` GLIB_LDADD = `pkg-config --libs glib-2.0` CFLAGS = -g -I../.. -DOLSON_DIR=\"$(OLSON_DIR)\" -DPRODUCT_ID='"$(PRODUCT_ID)"' -DTZID_PREFIX='"$(TZID_PREFIX)"' $(GLIB_CFLAGS) $(LIBICAL_CFLAGS) OBJECTS = vzic.o vzic-parse.o vzic-dump.o vzic-output.o all: vzic vzic: $(OBJECTS) $(CC) $(OBJECTS) $(GLIB_LDADD) -o vzic test-vzic: test-vzic.o $(CC) test-vzic.o $(LIBICAL_LDADD) -o test-vzic # Dependencies. $(OBJECTS): vzic.h vzic.o vzic-parse.o: vzic-parse.h vzic.o vzic-dump.o: vzic-dump.h vzic.o vzic-output.o: vzic-output.h test-parse: vzic ./vzic-dump.pl $(OLSON_DIR) ./vzic --dump --pure @echo @echo "#" @echo "# If either of these diff commands outputs anything there may be a problem." @echo "#" diff -ru zoneinfo/ZonesPerl zoneinfo/ZonesVzic diff -ru zoneinfo/RulesPerl zoneinfo/RulesVzic test-changes: vzic test-vzic ./test-vzic --dump-changes ./vzic --dump-changes --pure @echo @echo "#" @echo "# If this diff command outputs anything there may be a problem." @echo "#" diff -ru zoneinfo/ChangesVzic test-output check: clean: -rm -rf vzic $(OBJECTS) *~ ChangesVzic RulesVzic ZonesVzic RulesPerl ZonesPerl test-vzic test-vzic.o install: .PHONY: clean perl-dump test-parse check cyrus-imapd-2.5.10/tools/vzic/vzic-parse.c0000644000175000017500000005637613001236020015323 00000000000000/* * Vzic - a program to convert Olson timezone database files into VZTIMEZONE * files compatible with the iCalendar specification (RFC2445). * * Copyright (C) 2000-2001 Ximian, Inc. * Copyright (C) 2003 Damon Chaplin. * * Author: Damon Chaplin * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307, USA. */ #include #include #include #include #include #include #include #include "vzic.h" #include "vzic-parse.h" /* This is the maximum line length we allow. */ #define MAX_LINE_LEN 1024 /* The maximum number of fields on a line. */ #define MAX_FIELDS 12 #define CREATE_SYMLINK 1 typedef enum { ZONE_ID = 0, /* The 'Zone' at the start of the line. */ ZONE_NAME = 1, ZONE_GMTOFF = 2, ZONE_RULES_SAVE = 3, ZONE_FORMAT = 4, ZONE_UNTIL_YEAR = 5, ZONE_UNTIL_MONTH = 6, ZONE_UNTIL_DAY = 7, ZONE_UNTIL_TIME = 8 } ZoneFieldNumber; typedef enum { RULE_ID = 0, /* The 'Rule' at the start of the line. */ RULE_NAME = 1, RULE_FROM = 2, RULE_TO = 3, RULE_TYPE = 4, RULE_IN = 5, RULE_ON = 6, RULE_AT = 7, RULE_SAVE = 8, RULE_LETTER_S = 9 } RuleFieldNumber; typedef enum { LINK_ID = 0, /* The 'Link' at the start of the line. */ LINK_FROM = 1, LINK_TO = 2 } LinkFieldNumber; /* This struct contains information used while parsing the files, and is passed to most parsing functions. */ typedef struct _ParsingData ParsingData; struct _ParsingData { /* This is the line being parsed. buffer is a copy that we break into fields and sub-fields as it is parsed. */ char line[MAX_LINE_LEN]; char buffer[MAX_LINE_LEN]; /* These are pointers to the start of each field in buffer. */ char *fields[MAX_FIELDS]; int num_fields; /* These are just for producing error messages. */ char *filename; int line_number; /* This is an array of ZoneData structs, 1 for each timezone read. */ GArray *zone_data; /* This is a hash table of arrays of RuleData structs. As each Rule line is read in, a new RuleData struct is filled in and appended to the appropriate GArray in the hash table. */ GHashTable *rule_data; /* A hash containing data on the Link lines. The keys are the timezones where the link is from (i.e. the timezone we will be outputting anyway) and the data is a GList of timezones to link to (where we will copy the timezone data to). */ GHashTable *link_data; int max_until_year; }; /* * Parsing functions, used when reading the Olson timezone data file. */ static void parse_fields (ParsingData *data); static gboolean parse_zone_line (ParsingData *data); static gboolean parse_zone_continuation_line (ParsingData *data); static gboolean parse_zone_common (ParsingData *data, int offset); static void parse_rule_line (ParsingData *data); static void parse_link_line (ParsingData *data); static int parse_year (ParsingData *data, char *field, gboolean accept_only, int only_value); static int parse_month (ParsingData *data, char *field); static DayCode parse_day (ParsingData *data, char *field, int *day, int *weekday); static int parse_weekday (ParsingData *data, char *field); static int parse_time (ParsingData *data, char *field, TimeCode *time_code); static int parse_number (ParsingData *data, char **num); static int parse_rules_save (ParsingData *data, char *field, char **rules); static void parse_coord (char *coord, int len, int *result); void parse_olson_file (char *filename, GArray **zone_data, GHashTable **rule_data, GHashTable **link_data, int *max_until_year) { ParsingData data; FILE *fp; int zone_continues = 0; *zone_data = g_array_new (FALSE, FALSE, sizeof (ZoneData)); *rule_data = g_hash_table_new (g_str_hash, g_str_equal); *link_data = g_hash_table_new (g_str_hash, g_str_equal); fp = fopen (filename, "r"); if (!fp) { fprintf (stderr, "Couldn't open file: %s\n", filename); exit (1); } data.filename = filename; data.zone_data = *zone_data; data.rule_data = *rule_data; data.link_data = *link_data; data.max_until_year = 0; for (data.line_number = 0; ; data.line_number++) { if (fgets (data.line, sizeof (data.line), fp) != data.line) break; strcpy (data.buffer, data.line); parse_fields (&data); if (data.num_fields == 0) continue; if (zone_continues) { zone_continues = parse_zone_continuation_line (&data); } else if (!strcmp (data.fields[0], "Zone")) { zone_continues = parse_zone_line (&data); } else if (!strcmp (data.fields[0], "Rule")) { parse_rule_line (&data); } else if (!strcmp (data.fields[0], "Link")) { parse_link_line (&data); } else if (!strcmp (data.fields[0], "Leap")) { /* We don't care about Leap lines. */ } else { fprintf (stderr, "%s:%i: Invalid line.\n%s\n", filename, data.line_number, data.line); exit (1); } } if (ferror (fp)) { fprintf (stderr, "Error reading file: %s\n", filename); exit (1); } if (zone_continues) { fprintf (stderr, "%s:%i: Zone continuation line expected.\n%s\n", filename, data.line_number, data.line); exit (1); } fclose (fp); #if 0 printf ("Max UNTIL year: %i\n", data.max_until_year); #endif *max_until_year = data.max_until_year; } /* Converts the line into fields. */ static void parse_fields (ParsingData *data) { int i; char *p, *s, ch; /* Reset all fields to NULL. */ for (i = 0; i < MAX_FIELDS; i++) data->fields[i] = 0; data->num_fields = 0; p = data->buffer; for (;;) { /* Skip whitespace. */ while (isspace (*p)) p++; /* See if we have reached the end of the line or a comment. */ if (*p == '\0' || *p == '#') break; /* We must have another field, so save the start position. */ data->fields[data->num_fields++] = p; /* Now find the end of the field. If the field contains '"' characters they are removed and we have to move the rest of the chars back. */ s = p; for (;;) { ch = *p; if (ch == '\0' || ch == '#') { /* Don't move p on since this is the end of the line. */ *s = '\0'; break; } else if (isspace (ch)) { *s = '\0'; p++; break; } else if (ch == '"') { p++; for (;;) { ch = *p; if (ch == '\0') { fprintf (stderr, "%s:%i: Closing quote character ('\"') missing.\n%s\n", data->filename, data->line_number, data->line); exit (1); } else if (ch == '"') { p++; break; } else { *s++ = ch; } p++; } } else { *s++ = ch; } p++; } } #if 0 printf ("%i fields: ", data->num_fields); for (i = 0; i < data->num_fields; i++) printf ("'%s' ", data->fields[i]); printf ("\n"); #endif } static gboolean parse_zone_line (ParsingData *data) { ZoneData zone; /* All 5 fields up to FORMAT must be present. */ if (data->num_fields < 5 || data->num_fields > 9) { fprintf (stderr, "%s:%i: Invalid Zone line - %i fields.\n%s\n", data->filename, data->line_number, data->num_fields, data->line); exit (1); } zone.zone_name = g_strdup (data->fields[ZONE_NAME]); zone.zone_line_data = g_array_new (FALSE, FALSE, sizeof (ZoneLineData)); g_array_append_val (data->zone_data, zone); return parse_zone_common (data, 0); } static gboolean parse_zone_continuation_line (ParsingData *data) { /* All 3 fields up to FORMAT must be present. */ if (data->num_fields < 3 || data->num_fields > 7) { fprintf (stderr, "%s:%i: Invalid Zone continuation line - %i fields.\n%s\n", data->filename, data->line_number, data->num_fields, data->line); exit (1); } return parse_zone_common (data, -2); } static gboolean parse_zone_common (ParsingData *data, int offset) { ZoneData *zone; ZoneLineData zone_line; TimeCode time_code; zone_line.stdoff_seconds = parse_time (data, data->fields[ZONE_GMTOFF + offset], &time_code); zone_line.save_seconds = parse_rules_save (data, data->fields[ZONE_RULES_SAVE + offset], &zone_line.rules); if (!VzicPureOutput) { /* We round the UTC offsets to the nearest minute, to be compatible with Outlook. This also works with -ve numbers, I think. -56 % 60 = -59. -61 % 60 = -1. */ if (zone_line.stdoff_seconds >= 0) zone_line.stdoff_seconds += 30; else zone_line.stdoff_seconds -= 29; zone_line.stdoff_seconds -= zone_line.stdoff_seconds % 60; if (zone_line.save_seconds >= 0) zone_line.save_seconds += 30; else zone_line.save_seconds -= 29; zone_line.save_seconds -= zone_line.save_seconds % 60; } zone_line.format = g_strdup (data->fields[ZONE_FORMAT + offset]); if (data->num_fields - offset >= 6) { zone_line.until_set = TRUE; zone_line.until_year = parse_year (data, data->fields[ZONE_UNTIL_YEAR + offset], FALSE, 0); zone_line.until_month = parse_month (data, data->fields[ZONE_UNTIL_MONTH + offset]); zone_line.until_day_code = parse_day (data, data->fields[ZONE_UNTIL_DAY + offset], &zone_line.until_day_number, &zone_line.until_day_weekday); zone_line.until_time_seconds = parse_time (data, data->fields[ZONE_UNTIL_TIME + offset], &zone_line.until_time_code); /* We also want to know the maximum year used in any UNTIL value, so we know where to expand all the infinite Rule data to. */ if (zone_line.until_year != YEAR_MAXIMUM && zone_line.until_year != YEAR_MINIMUM) data->max_until_year = MAX (data->max_until_year, zone_line.until_year); } else { zone_line.until_set = FALSE; } /* Append it to the last Zone, since that is the one we are currently reading. */ zone = &g_array_index (data->zone_data, ZoneData, data->zone_data->len - 1); g_array_append_val (zone->zone_line_data, zone_line); return zone_line.until_set; } static void parse_rule_line (ParsingData *data) { GArray *rule_array; RuleData rule; char *name; TimeCode time_code; /* All 10 fields must be present. */ if (data->num_fields != 10) { fprintf (stderr, "%s:%i: Invalid Rule line - %i fields.\n%s\n", data->filename, data->line_number, data->num_fields, data->line); exit (1); } name = data->fields[RULE_NAME]; /* Create the GArray and add it to the hash table if it doesn't already exist. */ rule_array = g_hash_table_lookup (data->rule_data, name); if (!rule_array) { rule_array = g_array_new (FALSE, FALSE, sizeof (RuleData)); g_hash_table_insert (data->rule_data, g_strdup (name), rule_array); } rule.from_year = parse_year (data, data->fields[RULE_FROM], FALSE, 0); if (rule.from_year == YEAR_MAXIMUM) { fprintf (stderr, "%s:%i: Invalid Rule FROM value: '%s'\n", data->filename, data->line_number, data->fields[RULE_FROM]); exit (1); } rule.to_year = parse_year (data, data->fields[RULE_TO], TRUE, rule.from_year); if (rule.to_year == YEAR_MINIMUM) { fprintf (stderr, "%s:%i: Invalid Rule TO value: %s\n", data->filename, data->line_number, data->fields[RULE_TO]); exit (1); } /* We also want to know the maximum year used in any TO/FROM value, so we know where to expand all the infinite Rule data to. */ if (rule.to_year != YEAR_MAXIMUM) data->max_until_year = MAX (data->max_until_year, rule.to_year); else if (rule.from_year != YEAR_MINIMUM) data->max_until_year = MAX (data->max_until_year, rule.from_year); if (!strcmp (data->fields[RULE_TYPE], "-")) rule.type = NULL; else { printf ("Type: %s\n", data->fields[RULE_TYPE]); rule.type = g_strdup (data->fields[RULE_TYPE]); } rule.in_month = parse_month (data, data->fields[RULE_IN]); rule.on_day_code = parse_day (data, data->fields[RULE_ON], &rule.on_day_number, &rule.on_day_weekday); rule.at_time_seconds = parse_time (data, data->fields[RULE_AT], &rule.at_time_code); rule.save_seconds = parse_time (data, data->fields[RULE_SAVE], &time_code); if (!strcmp (data->fields[RULE_LETTER_S], "-")) { rule.letter_s = NULL; } else { rule.letter_s = g_strdup (data->fields[RULE_LETTER_S]); } rule.is_shallow_copy = FALSE; g_array_append_val (rule_array, rule); } static void parse_link_line (ParsingData *data) { char *from, *to, *old_from; GList *zone_list; /* We must have 3 fields for a Link. */ if (data->num_fields != 3) { fprintf (stderr, "%s:%i: Invalid Rule line - %i fields.\n%s\n", data->filename, data->line_number, data->num_fields, data->line); exit (1); } from = data->fields[LINK_FROM]; to = data->fields[LINK_TO]; #if 0 printf ("LINK FROM: %s\tTO: %s\n", from, to); #endif #if CREATE_SYMLINK { int len = strnlen(to,254); int dirs = 0; int i; for (i = 0; i < len; i++) { dirs += to[i] == '/' ? 1 : 0; } if (dirs >= 0) { char rel_from[255]; char to_dir[255]; char to_path[255]; if (dirs == 0) { sprintf(rel_from, "%s.ics", from); } else if (dirs == 1) { sprintf(rel_from, "../%s.ics", from); } else if (dirs == 2) { sprintf(rel_from, "../../%s.ics", from); } else { return; } sprintf(to_path, "%s/%s.ics", VzicOutputDir, to); strncpy(to_dir, to_path, 254); ensure_directory_exists(dirname(to_dir)); //printf("Creating symlink from %s to %s\n", rel_from, to_path); symlink(rel_from, to_path); } } #else if (g_hash_table_lookup_extended (data->link_data, from, (gpointer) &old_from, (gpointer) &zone_list)) { from = old_from; } else { from = g_strdup (from); zone_list = NULL; } zone_list = g_list_prepend (zone_list, g_strdup (to)); g_hash_table_insert (data->link_data, from, zone_list); #endif } static int parse_year (ParsingData *data, char *field, gboolean accept_only, int only_value) { int len, year = 0; char *p; if (!field) { fprintf (stderr, "%s:%i: Missing year.\n%s\n", data->filename, data->line_number, data->line); exit (1); } len = strlen (field); if (accept_only && !strncmp (field, "only", len)) return only_value; if (len >= 2) { if (!strncmp (field, "maximum", len)) return YEAR_MAXIMUM; else if (!strncmp (field, "minimum", len)) return YEAR_MINIMUM; } for (p = field; *p; p++) { if (*p < '0' || *p > '9') { fprintf (stderr, "%s:%i: Invalid year: %s\n%s\n", data->filename, data->line_number, field, data->line); exit (1); } year = year * 10 + *p - '0'; } if (year < 1000 || year > 2038) { fprintf (stderr, "%s:%i: Strange year: %s\n%s\n", data->filename, data->line_number, field, data->line); exit (1); } return year; } /* Parses a month name, returning 0 (Jan) to 11 (Dec). */ static int parse_month (ParsingData *data, char *field) { static char* months[] = { "january", "february", "march", "april", "may", "june", "july", "august", "september", "october", "november", "december" }; char *p; int len, i; /* If the field is missing, it must be the optional UNTIL month, so we return 0 for January. */ if (!field) return 0; for (p = field, len = 0; *p; p++, len++) { *p = tolower (*p); } for (i = 0; i < 12; i++) { if (!strncmp (field, months[i], len)) return i; } fprintf (stderr, "%s:%i: Invalid month: %s\n%s\n", data->filename, data->line_number, field, data->line); exit (1); } /* Parses a day specifier, returning a code representing the type of match together with a day of the month and a weekday number (0=Sun). */ static DayCode parse_day (ParsingData *data, char *field, int *day, int *weekday) { char *day_part, *p; DayCode day_code; if (!field) { *day = 1; return DAY_SIMPLE; } *day = *weekday = 0; if (!strncmp (field, "last", 4)) { *weekday = parse_weekday (data, field + 4); /* We set the day to the end of the month to make sorting Rules easy. */ *day = 31; return DAY_LAST_WEEKDAY; } day_part = field; day_code = DAY_SIMPLE; for (p = field; *p; p++) { if (*p == '<' || *p == '>') { if (*(p + 1) == '=') { day_code = (*p == '<') ? DAY_WEEKDAY_ON_OR_BEFORE : DAY_WEEKDAY_ON_OR_AFTER; *p = '\0'; *weekday = parse_weekday (data, field); day_part = p + 2; break; } fprintf (stderr, "%s:%i: Invalid day: %s\n%s\n", data->filename, data->line_number, field, data->line); exit (1); } } for (p = day_part; *p; p++) { if (*p < '0' || *p > '9') { fprintf (stderr, "%s:%i: Invalid day: %s\n%s\n", data->filename, data->line_number, field, data->line); exit (1); } *day = *day * 10 + *p - '0'; } if (*day < 1 || *day > 31) { fprintf (stderr, "%s:%i: Invalid day: %s\n%s\n", data->filename, data->line_number, field, data->line); exit (1); } return day_code; } /* Parses a weekday name, returning 0 (Sun) to 6 (Sat). */ static int parse_weekday (ParsingData *data, char *field) { static char* weekdays[] = { "sunday", "monday", "tuesday", "wednesday", "thursday", "friday", "saturday" }; char *p; int len, i; for (p = field, len = 0; *p; p++, len++) { *p = tolower (*p); } for (i = 0; i < 7; i++) { if (!strncmp (field, weekdays[i], len)) return i; } fprintf (stderr, "%s:%i: Invalid weekday: %s\n%s\n", data->filename, data->line_number, field, data->line); exit (1); } /* Parses a time (hour + minute + second) and returns the result in seconds, together with a time code specifying whether it is Wall clock time, local standard time, or universal time. The time can start with a '-' in which case it will be negative. */ static int parse_time (ParsingData *data, char *field, TimeCode *time_code) { char *p; int hours = 0, minutes = 0, seconds = 0, result, negative = 0; if (!field) { *time_code = TIME_WALL; return 0; } p = field; if (*p == '-') { p++; negative = 1; } hours = parse_number (data, &p); if (*p == ':') { p++; minutes = parse_number (data, &p); if (*p == ':') { p++; seconds = parse_number (data, &p); } } if (hours < 0 || hours > 24 || minutes < 0 || minutes > 59 || seconds < 0 || seconds > 59 || (hours == 24 && (minutes != 0 || seconds != 0))) { fprintf (stderr, "%s:%i: Invalid time: %s\n%s\n", data->filename, data->line_number, field, data->line); exit (1); } #if 0 /* Hack to work around older libical that doesn't support BYDAY + BYYEARDAY */ if (hours == 24) { hours = 23; minutes = 59; seconds = 59; } #endif #if 0 printf ("Time: %s -> %i:%02i:%02i\n", field, hours, minutes, seconds); #endif result = hours * 3600 + minutes * 60 + seconds; if (negative) result = -result; if (*p == '\0') { *time_code = TIME_WALL; return result; } if (*(p + 1) == '\0') { if (*p == 'w') { *time_code = TIME_WALL; return result; } else if (*p == 's') { *time_code = TIME_STANDARD; return result; } else if (*p == 'u' || *p == 'g' || *p == 'z') { *time_code = TIME_UNIVERSAL; return result; } } fprintf (stderr, "%s:%i: Invalid time: %s\n%s\n", data->filename, data->line_number, field, data->line); exit (1); } /* Parses a simple number and returns the result. The pointer argument is moved to the first character after the number. */ static int parse_number (ParsingData *data, char **num) { char *p; int result; p = *num; #if 0 printf ("In parse_number p:%s\n", p); #endif // potential null value where '-' is specified. assume zero. if (!p || !*p) { return 0; } if (*p < '0' || *p > '9') { fprintf (stderr, "%s:%i: Invalid number: %s\n%s\n", data->filename, data->line_number, *num, data->line); exit (1); } result = *p++ - '0'; while (*p >= '0' && *p <= '9') result = result * 10 + *p++ - '0'; *num = p; return result; } static int parse_rules_save (ParsingData *data, char *field, char **rules) { TimeCode time_code; *rules = NULL; /* Check for just "-". */ if (field[0] == '-' && field[1] == '\0') return 0; /* Check for a time to add to local standard time. We don't care about a time code here, since it is just an offset. */ if (*field == '-' || (*field >= '0' && *field <= '9')) return parse_time (data, field, &time_code); /* It must be a rules name. */ *rules = g_strdup (field); return 0; } GHashTable* parse_zone_tab (char *filename) { GHashTable *zones_hash; ZoneDescription *zone_desc; FILE *fp; char buf[4096]; gchar **fields, *zone_name, *latitude, *longitude, *p; fp = fopen (filename, "r"); if (!fp) { fprintf (stderr, "Couldn't open file: %s\n", filename); exit (1); } zones_hash = g_hash_table_new (g_str_hash, g_str_equal); while (fgets (buf, sizeof(buf), fp)) { if (*buf == '#') continue; g_strchomp (buf); fields = g_strsplit (buf,"\t", 4); if (strlen (fields[0]) != 2) { fprintf (stderr, "Invalid zone description line: %s\n", buf); exit (1); } zone_name = g_strdup (fields[2]); zone_desc = g_new (ZoneDescription, 1); zone_desc->country_code[0] = fields[0][0]; zone_desc->country_code[1] = fields[0][1]; zone_desc->comment = (fields[3] && fields[3][0]) ? g_strdup (fields[3]) : NULL; /* Now parse the latitude and longitude. */ latitude = fields[1]; longitude = latitude + 1; while (*longitude != '+' && *longitude != '-') longitude++; parse_coord (latitude, longitude - latitude, zone_desc->latitude); parse_coord (longitude, strlen (longitude), zone_desc->longitude); g_hash_table_insert (zones_hash, zone_name, zone_desc); #if 0 g_print ("Found zone: %s %i %02i %02i,%i %02i %02i\n", zone_name, zone_desc->latitude[0], zone_desc->latitude[1], zone_desc->latitude[2], zone_desc->longitude[0], zone_desc->longitude[1], zone_desc->longitude[2]); #endif } fclose (fp); return zones_hash; } static void parse_coord (char *coord, int len, int *result) { int degrees = 0, minutes = 0, seconds = 0; if (len == 5) sscanf (coord + 1, "%2d%2d", °rees, &minutes); else if (len == 6) sscanf (coord + 1, "%3d%2d", °rees, &minutes); else if (len == 7) sscanf (coord + 1, "%2d%2d%2d", °rees, &minutes, &seconds); else if (len == 8) sscanf (coord + 1, "%3d%2d%2d", °rees, &minutes, &seconds); else { fprintf (stderr, "Invalid coordinate: %s\n", coord); exit (1); } if (coord[0] == '-') degrees = -degrees; result[0] = degrees; result[1] = minutes; result[2] = seconds; } cyrus-imapd-2.5.10/tools/vzic/vzic-dump.h0000644000175000017500000000351713001236020015150 00000000000000/* * Vzic - a program to convert Olson timezone database files into VZTIMEZONE * files compatible with the iCalendar specification (RFC2445). * * Copyright (C) 2000-2001 Ximian, Inc. * Copyright (C) 2003 Damon Chaplin. * * Author: Damon Chaplin * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307, USA. */ /* * These functions are for dumping all the parsed Zones and Rules to * files, to be compared with the output of vzic-dump.pl to check our parsing * code is OK. Some of the functions are also used for producing debugging * output. */ #ifndef _VZIC_DUMP_H_ #define _VZIC_DUMP_H_ #include void dump_zone_data (GArray *zone_data, char *filename); void dump_rule_data (GHashTable *rule_data, char *filename); void dump_rule_array (char *name, GArray *rule_array, FILE *fp); char* dump_year (int year); char* dump_day_coded (DayCode day_code, int day_number, int day_weekday); char* dump_time (int seconds, TimeCode time_code, gboolean use_zero); void dump_time_zone_names (GList *names, char *output_dir, GHashTable *zones_hash); #endif /* _VZIC_DUMP_H_ */ cyrus-imapd-2.5.10/tools/vzic/vzic-parse.h0000644000175000017500000000243513001236020015313 00000000000000/* * Vzic - a program to convert Olson timezone database files into VZTIMEZONE * files compatible with the iCalendar specification (RFC2445). * * Copyright (C) 2000-2001 Ximian, Inc. * Copyright (C) 2003 Damon Chaplin. * * Author: Damon Chaplin * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307, USA. */ #ifndef _VZIC_PARSE_H_ #define _VZIC_PARSE_H_ #include void parse_olson_file (char *filename, GArray **zone_data, GHashTable **rule_data, GHashTable **link_data, int *max_until_year); GHashTable* parse_zone_tab (char *filename); #endif /* _VZIC_PARSE_H_ */ cyrus-imapd-2.5.10/tools/vzic/vzic.h0000644000175000017500000001402613001236020014202 00000000000000/* * Vzic - a program to convert Olson timezone database files into VZTIMEZONE * files compatible with the iCalendar specification (RFC2445). * * Copyright (C) 2000-2001 Ximian, Inc. * Copyright (C) 2003 Damon Chaplin. * * Author: Damon Chaplin * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 2 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307, USA. */ #ifndef _VZIC_H_ #define _VZIC_H_ #include /* * Global command-line options. */ /* By default we output Outlook-compatible output. If --pure is used we output pure output, with no changes to be compatible with Outlook. */ extern gboolean VzicPureOutput; extern gboolean VzicDumpOutput; extern gboolean VzicDumpChanges; extern gboolean VzicDumpZoneNamesAndCoords; extern gboolean VzicDumpZoneTranslatableStrings; extern gboolean VzicNoRRules; extern gboolean VzicNoRDates; extern char* VzicUrlPrefix; extern char* VzicOutputDir; extern GList* VzicTimeZoneNames; /* The minimum & maximum years we can use. */ #define YEAR_MINIMUM G_MININT #define YEAR_MAXIMUM G_MAXINT /* The maximum size of any complete pathname. */ #define PATHNAME_BUFFER_SIZE 1024 /* Days can be expressed either as a simple month day number, 1-31, or a rule such as the last Sunday, or the first Monday on or after the 8th. */ typedef enum { DAY_SIMPLE, DAY_WEEKDAY_ON_OR_AFTER, DAY_WEEKDAY_ON_OR_BEFORE, DAY_LAST_WEEKDAY } DayCode; /* Times can be given either as universal time (UTC), local standard time (without daylight-saving adjustments) or wall clock time (local standard time plus daylight-saving adjustments, i.e. what you would see on a clock on the wall!). */ typedef enum { TIME_WALL, TIME_STANDARD, TIME_UNIVERSAL } TimeCode; /* This represents one timezone, e.g. "Africa/Algiers". It contains the timezone name, and an array of ZoneLineData structs which hold data from each Zone line, including the continuation lines. */ typedef struct _ZoneData ZoneData; struct _ZoneData { char *zone_name; /* An array of ZoneLineData, one for each Zone & Zone continuation line read in. */ GArray *zone_line_data; }; typedef struct _ZoneLineData ZoneLineData; struct _ZoneLineData { /* The amount of time to add to UTC to get local standard time for the current time range, in seconds. */ int stdoff_seconds; /* Either rules is set to the name of a set of rules, or rules is NULL and save is set to the time to add to local standard time to get wall time, in seconds. If save is 0 as well, then standard time always applies. */ char *rules; int save_seconds; /* The format to use for the abbreviated timezone name, e.g. WE%sT. The %s is replaced by variable part of the name. (See the letter_s field in the RuleData struct below). */ char *format; /* TRUE if an UNTIL time is given. */ gboolean until_set; /* The UNTIL year, e.g. 2000. */ int until_year; /* The UNTIL month 0 (Jan) to 11 (Dec). */ int until_month; /* The UNTIL day, either a simple month day number, 1-31, or a rule such as the last Sunday, or the first Monday on or after the 8th. */ DayCode until_day_code; int until_day_number; /* 1 to 31. */ int until_day_weekday; /* 0 (Sun) to 6 (Sat). */ /* The UNTIL time, in seconds from midnight. The code specifies whether the time is a wall clock time, local standard time, or universal time. */ int until_time_seconds; TimeCode until_time_code; }; typedef struct _RuleData RuleData; struct _RuleData { /* The first year that the rule applies to, e.g. 1996. Can also be YEAR_MINIMUM. */ int from_year; /* The last year that the rule applies to, e.g. 1996. Can also be YEAR_MAXIMUM. */ int to_year; /* A string used to only match certain years between from and to. The rule only applies to the years which match. If type is NULL the rule applies to all years betweeen from and to. zic uses an external program called yearistype to check the string. Currently it is not used in the Olson database. */ char *type; /* The month of the rule 0 (Jan) to 11 (Dec). */ int in_month; /* The day, either a simple month day number, 1-31, or a rule such as the last Sunday, or the first Monday on or after the 8th. */ DayCode on_day_code; int on_day_number; int on_day_weekday; /* 0 (Sun) to 6 (Sat). */ /* The time, in seconds from midnight. The code specifies whether the time is a wall clock time, local standard time, or universal time. */ int at_time_seconds; TimeCode at_time_code; /* The amount of time to add to local standard time when the rule is in effect, in seconds. If this is not 0 then it must be a daylight-saving time. */ int save_seconds; /* The letter(s) to use as the variable part in the abbreviated timezone name. If this is NULL then no variable part is used. (See the format field in the ZoneLineData struct above.) */ char *letter_s; /* This is set to TRUE if this element is a shallow copy of another one, in which case we don't free any of the fields. */ gboolean is_shallow_copy; }; typedef struct _ZoneDescription ZoneDescription; struct _ZoneDescription { /* 2-letter ISO 3166 country code. */ char country_code[2]; /* latitude and longitude in degrees, minutes & seconds. The degrees value holds the sign of the entire latitude/longitude. */ int latitude[3]; int longitude[3]; char *comment; }; #endif /* _VZIC_H_ */ cyrus-imapd-2.5.10/tools/vzic/vzic-merge.pl0000755000175000017500000001113613001236020015465 00000000000000#!/usr/bin/perl -w # # Vzic - a program to convert Olson timezone database files into VZTIMEZONE # files compatible with the iCalendar specification (RFC2445). # # Copyright (C) 2001 Ximian, Inc. # Copyright (C) 2003 Damon Chaplin. # # Author: Damon Chaplin # # This program is free software; you can redistribute it and/or modify # it under the terms of the GNU General Public License as published by # the Free Software Foundation; either version 2 of the License, or # (at your option) any later version. # # This program is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the # GNU General Public License for more details. # # You should have received a copy of the GNU General Public License # along with this program; if not, write to the Free Software # Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307, USA. # # # This merges in a new set of VTIMEZONE files with the 'master' set. It only # updates the files in the master set if the VTIMEZONE component has really # been changes. Note that the TZID normally includes the date the VTIMEZONE # file was generated on, so we have to ignore this when comparing the files. # # Set these to the toplevel directories of the 2 sets of VTIMEZONE files. $NEW_ZONEINFO_DIR = "zoneinfo"; # Set this to 1 if you have version numbers in the TZID like libical. $LIBICAL_VERSIONING = 0; # Set this to 0 for dry-runs, and 1 to actually update. $DO_UPDATES = 1; # Save this so we can restore it later. $input_record_separator = $/; sub read_conf { my $file = shift; open CONF, $file or die "can't open $file"; while () { if (/^#/) { next; } if (/\@include:\s+(.*)$/) { push @configs, $1; } if (/^configdirectory:\s+(.*)$/) { $confdir = $1; } } close CONF; } $imapdconf = shift || "/etc/imapd.conf"; push @configs, $imapdconf; while ($conf = shift @configs) { read_conf($conf); } if (! $confdir) { $confdir = "/var/imap"; } $MASTER_ZONEINFO_DIR = $confdir . "/zoneinfo"; chdir $NEW_ZONEINFO_DIR || die "Can't cd to $NEW_ZONEINFO_DIR"; foreach $new_file (`find -name "*.ics"`) { # Get rid of './' at start and whitespace at end. $new_file =~ s/^\.\///; $new_file =~ s/\s+$//; # print "File: $new_file\n"; open (NEWZONEFILE, "$new_file") || die "Can't open file: $NEW_ZONEINFO_DIR/$new_file"; undef $/; $new_contents = ; $/ = $input_record_separator; close (NEWZONEFILE); $master_file = $MASTER_ZONEINFO_DIR . "/$new_file"; # print "Master File: $master_file\n"; $copy_to_master = 0; # If the ics file exists in the master copy we have to compare them, # otherwise we can just copy the new file into the master directory. if (-l $new_file) { $link_to = readlink($new_file); if (! -e $master_file || ! -l $master_file || (readlink($master_file) ne $link_to)) { print "Linking $new_file to $link_to...\n"; if ($DO_UPDATES) { unlink($master_file); symlink($link_to, $master_file); } } } elsif (-e $master_file) { open (MASTERZONEFILE, "$master_file") || die "Can't open file: $master_file"; undef $/; $master_contents = ; $/ = $input_record_separator; close (MASTERZONEFILE); $new_contents_copy = $new_contents; # Strip the TZID from both contents. # $new_contents_copy =~ s/^TZID:\S+\r$//m; # $new_tzid = $&; # $master_contents =~ s/^TZID:\S+\r$//m; # $master_tzid = $&; # Strip the PRODID from both contents. $new_contents_copy =~ s/^PRODID:.*$//m; $master_contents =~ s/^PRODID:.*$//m; # Strip the LAST-MODIFIED from both contents. $new_contents_copy =~ s/^LAST-MODIFIED:(\S+)\r$//m; $master_contents =~ s/^LAST-MODIFIED:(\S+)\r$//m; # print "Matched: $master_tzid\n"; if ($new_contents_copy ne $master_contents) { print "$new_file has changed. Updating...\n"; $copy_to_master = 1; if ($LIBICAL_VERSIONING) { # We bump the version number in the new file. # $master_tzid =~ m%_(\d+)/%; $version_num = $1; # print "Version: $version_num\n"; $version_num++; $new_tzid =~ s%_(\d+)/%_$version_num/%; # print "New TZID: $new_tzid\n"; $new_contents =~ s/^TZID:\S+$/$new_tzid/m; } } } else { print "$new_file doesn't exist in master directory. Copying...\n"; $copy_to_master = 1; } if ($copy_to_master) { # print "Updating: $new_file\n"; if ($DO_UPDATES) { open (MASTERZONEFILE, ">$master_file") || die "Can't create file: $master_file"; print MASTERZONEFILE $new_contents; close (MASTERZONEFILE); } } } cyrus-imapd-2.5.10/tools/arbitronsort.pl0000755000175000017500000000114512734634210015210 00000000000000#!/usr/bin/perl # # This script takes the output of arbitron (run without the -o option) # and prints out first # a ranking of mailboxes by # of people who selected the mailbox # and then a ranking of mailbox by # of subscribers. # %data = (); %subs = (); while(<>) { /^(.*) (\d+) (\d+)$/; $data{$1} = $2; $subs{$1} = $3; } $rank = 1; foreach $key (sort { $data{$b} <=> $data{$a} } (sort keys %data)) { print $rank++ . ": $key - $data{$key}\n"; } print "\n\n"; $rank = 1; foreach $key (sort { $subs{$b} <=> $subs{$a} } (sort keys %subs)) { print $rank++ . ": $key - $subs{$key}\n"; } cyrus-imapd-2.5.10/tools/translatesieve0000755000175000017500000001321513001236020015061 00000000000000#!/bin/sh exec perl -x -S $0 ${1+"$@"} # -*-perl-*- #!perl -w # script to translate sieve scripts to use unixhierarchysep and/or altnamespace # make sure you run it as the cyrus user #!/usr/bin/perl # # Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. # # Redistribution and use in source and binary forms, with or without # modification, are permitted provided that the following conditions # are met: # # 1. Redistributions of source code must retain the above copyright # notice, this list of conditions and the following disclaimer. # # 2. Redistributions in binary form must reproduce the above copyright # notice, this list of conditions and the following disclaimer in # the documentation and/or other materials provided with the # distribution. # # 3. The name "Carnegie Mellon University" must not be used to # endorse or promote products derived from this software without # prior written permission. For permission or any legal # details, please contact # Carnegie Mellon University # Center for Technology Transfer and Enterprise Creation # 4615 Forbes Avenue # Suite 302 # Pittsburgh, PA 15213 # (412) 268-7393, fax: (412) 268-7395 # innovation@andrew.cmu.edu # # 4. Redistributions of any form whatsoever must retain the following # acknowledgment: # "This product includes software developed by Computing Services # at Carnegie Mellon University (http://www.cmu.edu/computing/)." # # CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO # THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY # AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE # FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES # WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN # AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING # OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. if ($] !~ /^5\..*/) { # uh-oh. this isn't perl 5. foreach (split(/:/, $ENV{PATH})) { # try to find "perl5". exec("$_/perl5", "-x", "-S", $0, @ARGV) if (-x "$_/perl5"); } # we failed. bail. die "Your perl is too old; I need perl 5.\n"; } # load the real script. this is isolated in an 'eval' so perl4 won't # choke on the perl5-isms. eval join("\n", ); if ($@) { die "$@"; } __END__ require 5; $| = 1; if (($#ARGV > -1) && ("-f" eq $ARGV[0])) { $force = 1; shift @ARGV; } if ((($#ARGV > -1) && ($ARGV[0] eq "-h")) || ($#ARGV > 0)) { print "usage: translatesieve [-f] [imapd.conf]\n"; print " -f keep going on errors\n"; exit; } sub ouch { my $msg = shift; if ($force) { print "error: $msg\n"; } else { print "fatal error: $msg\n"; exit 1; } } sub read_conf { my $file = shift; open CONF, $file or die "can't open $file"; while () { if (/^#/) { next; } if (/\@include:\s+(.*)$/) { push @configs, $1; } if (/^sievedir:\s+(.*)$/) { $sievedir = $1; print "you are using $sievedir as your sieve directory.\n"; } if (/^unixhierarchysep:\s*(1|t|yes|on)/) { $unixhierarchysep = 1; } if (/^altnamespace:\s*(1|t|yes|on)/) { $altnamespace = 1; } if (/^userprefix:\s*(.*)$/) { $userprefix = $1; print "you are using $userprefix as your other users prefix.\n"; } if (/^sharedprefix:\s*(.*)$/) { $sharedprefix = $1; print "you are using $sharedprefix as your shared prefix.\n"; } } close CONF; } $imapdconf = shift || "/etc/imapd.conf"; $sievedir = "/usr/sieve"; $unixhierarchysep = 0; $altnamespace = 0; $userprefix = "Other Users"; $sharedprefix = "Shared Folders"; push @configs, $imapdconf; while ($conf = shift @configs) { read_conf($conf); } unless ($unixhierarchysep || $altnamespace) { ouch "you are not using the Unix hierarchy separator or the alternate namespace"; exit; } print "translating sievedir $sievedir... "; chdir $sievedir or die "couldn't change to $sievedir"; foreach $i ("a".."z") { print "$i "; if (! chdir $i) { ouch "couldn't chdir to $i"; next; } # translate the scripts user by user opendir (D, "."); while ($d = readdir D) { next if ($d =~ /^\./s); if (! -d $d) { ouch "expected $d to be a directory"; next; } if (! chdir $d) { ouch "couldn't chdir to $d"; next; } # translate all of the user's scripts opendir DIR, "."; while ($file = readdir DIR) { next if (!($file =~ /\.script$/)); # print "translating $file... "; if (!open(IN, $file)) { ouch "cannot open $file for reading: $!"; next; } if (!open(OUT, ">.$file")) { close(IN); ouch "cannot create /.$file: $!"; next; } $inbox = "[Ii][Nn][Bb][Oo][Xx]"; while () { # Alternate namespace if ($altnamespace) { # INBOX if (/\s+fileinto\s+"$inbox"\s*;/) { # do nothing } # Personal namespace elsif (/\s+fileinto\s+"($inbox\.[^"]*)"\s*;/) { substr($_, index($_, $1), 6) = ""; } # Other Users namespace elsif (/\s+fileinto\s+"(user\.[^"]*)"\s*;/) { substr($_, index($_, $1), 4) = $userprefix; } # Shared namespace elsif (/\s+fileinto\s+"([^"]*)"\s*;/) { substr($_, index($_, $1), 0) = $sharedprefix . "."; } } # Hierarchy separator if ($unixhierarchysep) { if (/\s+fileinto\s+"([^"]*)"\s*;/) { substr($_, index($_, $1)) =~ s~\.~/~g; } } print OUT $_; } close(IN); close(OUT); rename(".$file", "$file") or ouch "couldn't move .$file to $file"; # print "\n"; } closedir DIR; chdir ".."; } closedir D; # back to "/usr/sieve" chdir ".."; } print "done\n"; cyrus-imapd-2.5.10/tools/compile_st.pl0000755000175000017500000001611013001236020014575 00000000000000#!/usr/bin/perl # # compile_st.pl - compile string table into .h and .c files # # Copyright (c) 1994-2010 Carnegie Mellon University. All rights reserved. # # Redistribution and use in source and binary forms, with or without # modification, are permitted provided that the following conditions # are met: # # 1. Redistributions of source code must retain the above copyright # notice, this list of conditions and the following disclaimer. # # 2. Redistributions in binary form must reproduce the above copyright # notice, this list of conditions and the following disclaimer in # the documentation and/or other materials provided with the # distribution. # # 3. The name "Carnegie Mellon University" must not be used to # endorse or promote products derived from this software without # prior written permission. For permission or any legal # details, please contact # Carnegie Mellon University # Center for Technology Transfer and Enterprise Creation # 4615 Forbes Avenue # Suite 302 # Pittsburgh, PA 15213 # (412) 268-7393, fax: (412) 268-7395 # innovation@andrew.cmu.edu # # 4. Redistributions of any form whatsoever must retain the following # acknowledgment: # "This product includes software developed by Computing Services # at Carnegie Mellon University (http://www.cmu.edu/computing/)." # # CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO # THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY # AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE # FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES # WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN # AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING # OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. # use strict; use warnings; use File::Temp qw/ tempfile /; my $c_flag = 0; my $h_flag = 0; my $infile; sub usage() { print STDERR "Usage: compile_st.pl -c input.st | gperf > output.c\n"; print STDERR " compile_st.pl -h input.st > output.h\n"; exit 1; } while (my $a = shift) { if ($a eq "-c") { $c_flag = 1; } elsif ($a eq "-h") { $h_flag = 1; } elsif ($a eq "--help") { usage(); } elsif ($a =~ m/^-/) { usage(); } else { usage() if defined $infile; $infile = $a; } } usage() unless defined $infile; die "Please specify exactly one of -c or -h" unless ($c_flag + $h_flag == 1); # variables containing the logical contents of the string table file my @gperf_directives = ( "includes", "compare-strncmp", "language=ANSI-C", "readonly-tables", "struct-type" ); my $name; my $unknown; my $next_unknown = -1; my $next_known = 0; my @entries; # # Slurp the .st stringtab file into variables. # open ST,'<',$infile or die "Cannot open $infile for reading: $!"; while () { chomp; next if m/^\s*#/; # skip comments next if m/^\s*$/; # skip empty lines my @a = split; if ($a[0] eq "%ignore-case" && scalar(@a) == 1) { push(@gperf_directives, "ignore-case"); } elsif ($a[0] =~ m/^%/) { die "Unrecognised gperf declaration \"$_\""; } elsif ($a[0] eq "table") { die "Wrong number of arguments for \"table\"" unless scalar(@a) == 2; $name = $a[1]; } elsif ($a[0] eq "ent") { my $enum; my $string; my $value; ($enum) = m/^\s*ent\s+([A-Za-z_][A-Za-z_0-9]*)\s*$/; if (!defined $enum) { ($enum, $string) = m/^\s*ent\s+([A-Za-z_][A-Za-z_0-9]*)\s+"([^"]+)"\s*$/; die "Bad syntax for \"ent\" at or near \"$_\"" unless defined $string; } if (!defined $string) { $value = $next_unknown; $next_unknown--; $unknown = $enum unless defined $unknown; } else { $value = $next_known; $next_known++; } push(@entries, { enum => $enum, value => $value, string => $string }); } else { die "Unrecognised keyword at or near \"$_\""; } } close ST; die "No table name defined in $infile" unless defined $name; die "No string entries defined" unless scalar(@entries) > 0; $unknown = "-1" unless defined $unknown; # Emit the C header file is requested if ($h_flag) { printf "/* Automatically generated by compile_st.pl, do not edit */\n"; printf "#ifndef __STRING_TABLE_%s_H_\n", $name; printf "#define __STRING_TABLE_%s_H_ 1\n", $name; printf "\n"; printf "#include \n"; printf "\n"; printf "enum %s {\n", $name; foreach my $e (@entries) { printf " %s", $e->{enum}; printf "=%d", $e->{value} if defined $e->{value}; printf ",\n" } printf "};\n"; printf "extern enum %s %s_from_string(const char *s);\n", $name, $name; printf "extern enum %s %s_from_string_len(const char *s, size_t len);\n", $name, $name; printf "extern const char *%s_to_string(enum %s v);\n", $name, $name; printf "\n"; printf "#endif /* __STRING_TABLE_%s_H_ */\n", $name; } # Emit the gperf source file if requested if ($c_flag) { my ($fh, $filename) = tempfile('compile_st_XXXXXX', TMPDIR => 1, SUFFIX => '.gperf'); printf $fh "%%define lookup-function-name __%s_lookup\n", $name; foreach my $d (@gperf_directives) { printf $fh "%%%s\n", $d; } printf $fh "%%{\n"; printf $fh "/* Automatically generated by compile_st.pl, do not edit */\n"; printf $fh "#include \"%s.h\"\n", $name; printf $fh "%%}\n"; printf $fh "struct %s_desc { const char *name; enum %s value; };\n", $name, $name; printf $fh "%%%%\n"; foreach my $e (@entries) { next unless defined $e->{string}; printf $fh "%s, %s\n", $e->{string}, $e->{enum}; } printf $fh "%%%%\n"; printf $fh "enum %s %s_from_string(const char *s)\n", $name, $name; printf $fh "{\n"; printf $fh " const struct %s_desc *d = __%s_lookup(s, strlen(s));\n", $name, $name; printf $fh " return (d == NULL ? %s : d->value);\n", $unknown; printf $fh "}\n"; printf $fh "\n"; printf $fh "enum %s %s_from_string_len(const char *s, size_t len)\n", $name, $name; printf $fh "{\n"; printf $fh " const struct %s_desc *d = __%s_lookup(s, len);\n", $name, $name; printf $fh " return (d == NULL ? %s : d->value);\n", $unknown; printf $fh "}\n"; printf $fh "\n"; printf $fh "const char *%s_to_string(enum %s v)\n", $name, $name; printf $fh "{\n"; printf $fh " static const char * const strs[] = {\n"; foreach my $e (@entries) { next unless defined $e->{string}; printf $fh "\t\"%s\", /* %s */\n", $e->{string}, $e->{enum}; } printf $fh " };\n"; printf $fh " return (v >= 0 && v < (int)(sizeof(strs)/sizeof(strs[0])) ? strs[v] : NULL);\n"; printf $fh "}\n"; close $fh; my @cmd = ( 'gperf', $filename ); open GPERF,'-|',@cmd or die "Couldn't run gperf"; # Post-process to fix warnings due to missing # initializers in the wordlist. my $s = 0; while () { chomp; next if m/^#line/; s/{""}/{"", 0}/g if ($s); $s = 1 if m/wordlist/; $s = 0 if ($s && m/};/); print "$_\n"; } close GPERF; unlink($filename); } cyrus-imapd-2.5.10/tools/undohash0000755000175000017500000001035313001236020013641 00000000000000#!/usr/bin/perl # script to downgrade from cyrus imapd 1.6.2+ to earlier. # do NOT run this script while imapd's are running # # Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. # # Redistribution and use in source and binary forms, with or without # modification, are permitted provided that the following conditions # are met: # # 1. Redistributions of source code must retain the above copyright # notice, this list of conditions and the following disclaimer. # # 2. Redistributions in binary form must reproduce the above copyright # notice, this list of conditions and the following disclaimer in # the documentation and/or other materials provided with the # distribution. # # 3. The name "Carnegie Mellon University" must not be used to # endorse or promote products derived from this software without # prior written permission. For permission or any legal # details, please contact # Carnegie Mellon University # Center for Technology Transfer and Enterprise Creation # 4615 Forbes Avenue # Suite 302 # Pittsburgh, PA 15213 # (412) 268-7393, fax: (412) 268-7395 # innovation@andrew.cmu.edu # # 4. Redistributions of any form whatsoever must retain the following # acknowledgment: # "This product includes software developed by Computing Services # at Carnegie Mellon University (http://www.cmu.edu/computing/)." # # CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO # THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY # AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE # FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES # WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN # AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING # OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. require 5; $| = 1; sub read_conf { my $file = shift; open CONF, $file or die "can't open $file"; while () { if (/^#/) { next; } if (/\@include:\s+(.*)$/) { push @configs, $1; } if (/^configdirectory:\s+(.*)$/) { $confdir = $1; } if (/^(?:meta)?partition-.*:\s+(.*)$/) { if (grep /$1/, @parts) { next; } push @parts, $1; } if (/^hashimapspool:\s*(1|t|yes|on)/) { $hashispool = 1; print "i will also hash partitions.\n"; } } close CONF; } $imapdconf = shift || "/etc/imapd.conf"; $hashispool = 0; push @configs, $imapdconf; while ($conf = shift @configs) { read_conf($conf); } print "downgrading configuration directory $confdir..."; chdir $confdir or die "couldn't change to $confdir"; # *** user subdirectory; holds subscription files print "user "; chdir "user" or die "couldn't change to user subdir"; foreach $i ("a".."z") { opendir SUB, $i; while ($s = readdir SUB) { if ($s =~ /^\./s) { next; } rename("$i/$s", "$s") or die "couldn't move $s back!"; } closedir SUB; rmdir "$i" or die "couldn't remove $i"; } chdir ".."; # *** quota subdirectory; holds quota files for each quotaroot print "quota "; chdir "quota" or die "couldn't change to quota subdir"; # first, create directories we know can't conflict with existing files foreach $i ("a".."z") { rename ($i, ".$i") or die "couldn't rename $i to .$i"; opendir SUB, ".$i"; while ($s = readdir SUB) { if ($s =~ /^\./s) { next; } rename(".$i/$s", $s) or die "couldn't move $s back!"; } closedir SUB; rmdir ".$i" or die "couldn't remove .$i"; } chdir ".."; print "done\n"; # *** now for each data partition while ($hashispool && ($part = shift @parts)) { print "downgrading data partition $part..."; chdir $part or die "couldn't chdir to $part"; foreach $i ("a".."z") { rename ("$i", ".$i") or die "couldn't rename $i to .$i"; } # process each subdir foreach $i ("a".."z") { print "$i "; opendir SUB, ".$i"; while ($s = readdir SUB) { if ($s =~ /^\./s) { next; } mkdir $s, 0755; # ignore errors as it might already exist opendir MV, ".$i/$s"; while ($t = readdir MV) { if ($t =~ /^\./s) { next; } rename (".$i/$s/$t", "$s/$t") or die "couldn't rename .$i/$s/$t to $s/$t"; } closedir MV; } closedir SUB; rmdir ".$i"; } print "done\n"; } cyrus-imapd-2.5.10/tools/git-version.sh0000755000175000017500000000430712777273522014744 00000000000000#!/bin/bash # Generate a version string for cyrus-imapd # # Copyright (c) 1994-2016 Carnegie Mellon University. All rights reserved. # # Redistribution and use in source and binary forms, with or without # modification, are permitted provided that the following conditions # are met: # # 1. Redistributions of source code must retain the above copyright # notice, this list of conditions and the following disclaimer. # # 2. Redistributions in binary form must reproduce the above copyright # notice, this list of conditions and the following disclaimer in # the documentation and/or other materials provided with the # distribution. # # 3. The name "Carnegie Mellon University" must not be used to # endorse or promote products derived from this software without # prior written permission. For permission or any legal # details, please contact # Carnegie Mellon University # Center for Technology Transfer and Enterprise Creation # 4615 Forbes Avenue # Suite 302 # Pittsburgh, PA 15213 # (412) 268-7393, fax: (412) 268-7395 # innovation@andrew.cmu.edu # # 4. Redistributions of any form whatsoever must retain the following # acknowledgment: # "This product includes software developed by Computing Services # at Carnegie Mellon University (http://www.cmu.edu/computing/)." # # CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO # THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY # AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE # FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES # WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN # AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING # OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. # # first try: based on annotated git tags (real releases) version=$(git describe --dirty=-dirty 2>/dev/null) test -n "$version" && version=$(echo "$version" | sed -e 's/^cyrus-imapd-//') # second try: lightweight git tags test -z "$version" && version=$(git describe --dirty=-dirty --tags 2>/dev/null) # third try: probably not a git repository test -z "$version" && version=unknown echo $version cyrus-imapd-2.5.10/tools/masssievec0000755000175000017500000001144713001236020014177 00000000000000#!/bin/sh # # Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. # # Redistribution and use in source and binary forms, with or without # modification, are permitted provided that the following conditions # are met: # # 1. Redistributions of source code must retain the above copyright # notice, this list of conditions and the following disclaimer. # # 2. Redistributions in binary form must reproduce the above copyright # notice, this list of conditions and the following disclaimer in # the documentation and/or other materials provided with the # distribution. # # 3. The name "Carnegie Mellon University" must not be used to # endorse or promote products derived from this software without # prior written permission. For permission or any legal # details, please contact # Carnegie Mellon University # Center for Technology Transfer and Enterprise Creation # 4615 Forbes Avenue # Suite 302 # Pittsburgh, PA 15213 # (412) 268-7393, fax: (412) 268-7395 # innovation@andrew.cmu.edu # # 4. Redistributions of any form whatsoever must retain the following # acknowledgment: # "This product includes software developed by Computing Services # at Carnegie Mellon University (http://www.cmu.edu/computing/)." # # CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO # THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY # AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE # FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES # WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN # AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING # OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. exec perl -x -S $0 ${1+"$@"} # -*-perl-*- #!perl -w # # Script for mass compilation of sieve scripts. if ($] !~ /^5\..*/) { # uh-oh. this isn't perl 5. foreach (split(/:/, $ENV{PATH})) { # try to find "perl5". exec("$_/perl5", "-x", "-S", $0, @ARGV) if (-x "$_/perl5"); } # we failed. bail. die "Your perl is too old; I need perl 5.\n"; } # load the real script. this is isolated in an 'eval' so perl4 won't # choke on the perl5-isms. eval join("\n", ); if ($@) { die "$@"; } __END__ require 5; $| = 1; die "must not run as root" if ($< == 0); if(@ARGV < 1) { print "usage: masssievec [imapd.conf]\n"; exit; } $SIEVEC = shift @ARGV; $imapdconf = shift @ARGV; if(!defined($imapdconf)) { $imapdconf = "/etc/imapd.conf"; } $sievedir = "/usr/sieve"; if(! -x $SIEVEC) { print "$SIEVEC is not executable\n"; exit; } if($SIEVEC !~ /^\//) { print "$SIEVEC is not an absolute path\n"; exit; } sub read_conf { my $file = shift; open CONF, $file or die "can't open $file"; while () { if (/^#/) { next; } if (/\@include:\s+(.*)$/) { push @configs, $1; } if (/^sieveusehomedir:\s+(1|t|yes|on)/) { $nosievedir = 1; print "you are storing sieve scripts in user's home directories, this script cannot deal with that\n"; exit; } if (/^sievedir:\s+(.*)$/) { $sievedir = $1; } } close CONF; } push @configs, $imapdconf; while ($conf = shift @configs) { read_conf($conf); } print "you are using $sievedir as your sieve directory.\n"; opendir TOP, $sievedir; while (defined($s = readdir TOP)) { next if ($s eq "." || $s eq ".."); chdir $sievedir . "/$s"; opendir THISONE, "."; while(defined($t = readdir THISONE)) { next if ($t eq "." || $t eq ".."); print "processing user $t\n"; chdir $t; opendir USER, "."; while(defined($u = readdir USER)) { next if ($u eq "." || $u eq ".."); if($u eq "default" && -l $u) { # special case $dest = readlink $u; next unless($dest =~ m/\.script$/); $dest =~ s/\.script$//; symlink "$dest.bc", "defaultbc" || warn "can't symlink $dest.bc to defaultbc: $!"; unlink ("default"); } elsif ($u eq "default.bc" && -l $u) { # slightly different upgrade foramt $dest = readlink $u; next unless($dest =~ m/\.bc$/ && $dest ne "default.bc"); symlink "$dest", "defaultbc" || warn "can't symlink $dest to defaultbc: $!"; unlink ("default.bc"); } elsif ($u eq "default" || $u eq "default.bc") { warn "$u is not a symlink"; } else { next unless($u =~ m/\.script$/); $out = $u; $out =~ s/\.script$//; FORK: { if($pid = fork()) { #parent, do nothing waitpid $pid, 0; } elsif (defined $pid) { # child exec $SIEVEC, $u, "$out.bc"; die "souldn't be here"; } elsif ($! =~ /No more process/) { # EAGAIN sleep 5; redo FORK; } else { die "cant fork: $!"; } } $rc = $? & 0xff00; $rc >>= 8; if($rc) { print "got error compiling $u.\n"; } } } chdir $sievedir . "/$s"; } closedir THISONE; } closedir TOP cyrus-imapd-2.5.10/tools/htmlstrip.c0000644000175000017500000002623313001236020014300 00000000000000/* htmlstrip.c -- HTML to text converter * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include #include #include #include #include #define MODE_PRE 1 /* Preformatted */ #define MODE_IGNORETXT 2 /* Discard text */ #define FLAG_NOPUSH 1 /* Has no end marker, don't push on stack */ #define FLAG_BREAK 2 /* Breaks a line */ #define FLAG_PARAGRAPH 4 /* Breaks a paragraph */ struct mode { char *name; int indent; int listnum; int flags; int mode; int startline; }; struct mode modestack[100] = {{"TOPLEVEL", 4, 0, 0, 0, 0}}; int curmode = 0; int didparagraph = 1; struct tag { char *name; int flags; int mode; int indent; }; struct tag cmds[] = { { "!--", FLAG_NOPUSH, 0, 0, }, { "!DOCTYPE", FLAG_NOPUSH, 0, 0, }, { "link", FLAG_NOPUSH, 0, 0, }, { "html", 0, 0, 0, }, { "head", 0, MODE_IGNORETXT, 0, }, { "title", 0, MODE_IGNORETXT, 0, }, { "body", 0, 0, 0, }, { "p", FLAG_PARAGRAPH|FLAG_NOPUSH, 0, 0, }, { "pre", FLAG_PARAGRAPH, MODE_PRE, 0, }, { "a", 0, 0, 0, }, /* KLUDGE: we set MODE_PRE on

    to fake centering it ourselves */ { "h1", FLAG_PARAGRAPH, MODE_PRE, -4, }, { "h2", FLAG_PARAGRAPH, 0, -4, }, { "h3", FLAG_PARAGRAPH, 0, -4, }, { "h4", FLAG_PARAGRAPH, 0, -4, }, { "h5", FLAG_PARAGRAPH, 0, -4, }, { "h6", FLAG_PARAGRAPH, 0, -4, }, { "em", 0, 0, 0, }, { "strong", 0, 0, 0, }, { "code", 0, 0, 0, }, { "samp", 0, 0, 0, }, { "kbd", 0, 0, 0, }, { "var", 0, 0, 0, }, { "dfn", 0, 0, 0, }, { "cite", 0, 0, 0, }, { "blockquote", FLAG_PARAGRAPH, 0, 4, }, { "b", 0, 0, 0, }, { "i", 0, 0, 0, }, { "u", 0, 0, 0, }, { "tt", 0, 0, 0, }, { "dl", FLAG_PARAGRAPH, 0, 8, }, { "dt", FLAG_BREAK|FLAG_NOPUSH, 0, -8, }, { "dd", FLAG_NOPUSH, 0, 0, }, { "ul", FLAG_PARAGRAPH, 0, 4, }, { "ol", FLAG_PARAGRAPH, 0, 4, }, { "li", FLAG_BREAK|FLAG_NOPUSH, 0, -4, }, { "br", FLAG_BREAK|FLAG_NOPUSH, 0, 0, }, { "hr", FLAG_BREAK|FLAG_NOPUSH, 0, 0, }, { "meta", FLAG_NOPUSH, 0, 0, }, { "table", 0, 0, 0, }, { "tr", FLAG_PARAGRAPH, 0, 0, }, { "td", 0, 0, 0, }, }; static void parse(FILE *infile); static int lex(FILE *infile, int *cmdptr, int *endtagptr, int *linenoptr); int main(int argc, char **argv) { FILE *infile; if (argc != 2) { fprintf(stderr, "usage: %s file\n", argv[0]); exit(1); } infile = fopen(argv[1], "r"); if (!infile) { perror(argv[1]); exit(1); } parse(infile); exit(0); } static void parse(FILE *infile) { char outputbuf[1024]; int outpos = 0; int c; int cmd; int endtag; int lineno = 1; int i; char *p; while ((c = lex(infile, &cmd, &endtag, &lineno)) != EOF) { if (!c) { if (endtag) { if (cmds[cmd].flags & FLAG_NOPUSH) { /* ignore */ } else if (strcmp(cmds[cmd].name, modestack[curmode].name)!=0) { fprintf(stderr, "<%s> line %d mismatched with on line %d\n", modestack[curmode].name, modestack[curmode].startline, cmds[cmd].name, lineno); exit(1); } else { if ((modestack[curmode].flags & FLAG_PARAGRAPH) && !(modestack[curmode].mode & MODE_IGNORETXT)) { if (outpos) { outputbuf[outpos++] = '\n'; outputbuf[outpos++] = '\0'; fputs(outputbuf, stdout); outpos = 0; } if (!didparagraph) { putc('\n', stdout); didparagraph = 1; } } curmode--; } } else { if (!(modestack[curmode].mode & MODE_IGNORETXT)) { if (cmds[cmd].flags & (FLAG_PARAGRAPH|FLAG_BREAK)) { if (outpos) { outputbuf[outpos++] = '\n'; outputbuf[outpos++] = '\0'; fputs(outputbuf, stdout); outpos = 0; } } if ((cmds[cmd].flags & FLAG_PARAGRAPH) && !didparagraph) { putc('\n', stdout); didparagraph = 1; } } if (cmds[cmd].flags & FLAG_NOPUSH) { if (!strcmp(cmds[cmd].name, "dt")) { while (outpos < modestack[curmode].indent - 8) { outputbuf[outpos++] = ' '; } } if (!strcmp(cmds[cmd].name, "dd")) { if (outpos-1 >= modestack[curmode].indent) { /* Break line */ outputbuf[outpos++] = '\n'; outputbuf[outpos++] = '\0'; fputs(outputbuf, stdout); outpos = 0; } /* Indent line */ while (outpos < modestack[curmode].indent) { outputbuf[outpos++] = ' '; } } if (!strcmp(cmds[cmd].name, "li")) { if (modestack[curmode].listnum == 0) { fprintf(stderr, "
  • inside a <%s> on line %d\n", modestack[curmode].name, lineno); exit(1); } while (outpos < modestack[curmode].indent - 4) { outputbuf[outpos++] = ' '; } if (modestack[curmode].listnum < 0) { outputbuf[outpos++] = ' '; outputbuf[outpos++] = ' '; outputbuf[outpos++] = '*'; outputbuf[outpos++] = ' '; } else { if (modestack[curmode].listnum >=100) { fprintf(stderr, "too many
  • items on line %d\n", lineno); exit(1); } outputbuf[outpos++] = modestack[curmode].listnum > 9 ? modestack[curmode].listnum/10 + '0' : ' '; outputbuf[outpos++] = modestack[curmode].listnum%10 + '0'; outputbuf[outpos++] = '.'; outputbuf[outpos++] = ' '; modestack[curmode].listnum++; } } if (!strcmp(cmds[cmd].name, "hr")) { /* XXX hack */ modestack[curmode].mode |= MODE_IGNORETXT; } } else { curmode++; if (curmode >= 100) { fprintf(stderr, "too many nested tags on line %d\n", lineno); exit(1); } modestack[curmode].name = cmd[cmds].name; modestack[curmode].indent = modestack[curmode-1].indent + cmd[cmds].indent; modestack[curmode].listnum = 0; modestack[curmode].flags = cmd[cmds].flags; modestack[curmode].mode = modestack[curmode-1].mode | cmd[cmds].mode; modestack[curmode].startline = lineno; if (!strcmp(cmds[cmd].name, "ul")) { modestack[curmode].listnum = -1; } if (!strcmp(cmds[cmd].name, "ol")) { modestack[curmode].listnum = 1; } } } } else if (modestack[curmode].mode & MODE_IGNORETXT) { /* do nothing */ } else if (isspace(c) && !(modestack[curmode].mode & MODE_PRE)) { /* Only emit space if previous char not a space */ if (outpos && !isspace(outputbuf[outpos-1])) { outputbuf[outpos++] = ' '; } } else if (c == '\n') { /* Newline inside MODE_PRE. Emit current line */ if (outpos || !didparagraph) { outputbuf[outpos++] = '\n'; outputbuf[outpos++] = '\0'; fputs(outputbuf, stdout); outpos = 0; didparagraph = 0; } } else { didparagraph = 0; if (!outpos) { /* Indent line */ for (i = 0; i < modestack[curmode].indent; i++) { outputbuf[outpos++] = ' '; } } outputbuf[outpos++] = c; /* Check for line wrapping */ if (outpos > 75 && !(modestack[curmode].mode & MODE_PRE)) { outputbuf[outpos] = '\0'; p = strrchr(outputbuf, ' '); if (p && p-outputbuf > modestack[curmode].indent) { *p++ = '\0'; fputs(outputbuf, stdout); putc('\n', stdout); outpos = 0; if (*p) { for (i = 0; i < modestack[curmode].indent; i++) { outputbuf[outpos++] = ' '; } while (*p) { outputbuf[outpos++] = *p++; } } } } } } /* Write out last line of output */; if (outpos) { outputbuf[outpos++] = '\n'; outputbuf[outpos++] = '\0'; fputs(outputbuf, stdout); } } static int lex(FILE *infile, int *cmdptr, int *endtagptr, int *linenoptr) { int c; static char buf[1024]; unsigned int i = 0; int lineno = *linenoptr; char *p; c = getc(infile); if (c == '&') { while ((c = getc(infile)) != EOF && c != ';') { buf[i++] = c; if (c == '\n' || i > 1000) { fprintf(stderr, "unterminated entity on line %d\n", lineno); exit(1); } } if (c == EOF) { fprintf(stderr, "unexpected EOF on line %d\n", lineno); exit(1); } buf[i] = '\0'; if (!strcasecmp(buf, "amp")) return '&'; if (!strcasecmp(buf, "lt")) return '<'; if (!strcasecmp(buf, "gt")) return '>'; if (!strcasecmp(buf, "quot")) return '"'; if (!strcasecmp(buf, "nbsp")) return ' '; fprintf(stderr, "unrecognized entity '%s' on line %d\n", buf, lineno); exit(1); } if (!c) { fprintf(stderr, "NUL character on line %d\n", lineno); exit(1); } if (c == '\n') (*linenoptr)++; if (c != '<') return c; while (i<=1000 && (c = getc(infile)) != EOF && c != '>') { if (c == '\n') (*linenoptr)++; if (isspace(c)) c = ' '; buf[i++] = c; if (c == '\"') { while (i<=1000 && (c = getc(infile)) != EOF && c != '\"') { if (c == '\n') (*linenoptr)++; buf[i++] = c; } if (c == EOF || i > 1000) { fprintf(stderr, "unterminated string in tag starting on line %d\n", lineno); exit(1); } buf[i++] = c; } } buf[i] = '\0'; if (c == EOF || i > 1000) { fprintf(stderr, "unterminated tag starting on line %d\n", lineno); exit(1); } if ((p = strchr(buf, ' '))) *p = '\0'; p = buf; if (*p == '/') { *endtagptr = 1; p++; } else { *endtagptr = 0; } for (i = 0; i<(sizeof(cmds)/sizeof(*cmds)); i++) { if (!strcasecmp(p, cmds[i].name)) { *cmdptr = i; return 0; } } fprintf(stderr, "unknown tag <%s> starting on line %d\n", buf, lineno); exit(1); } cyrus-imapd-2.5.10/tools/mknewsgroups0000755000175000017500000001340613001236020014576 00000000000000#!/bin/sh # # Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. # # Redistribution and use in source and binary forms, with or without # modification, are permitted provided that the following conditions # are met: # # 1. Redistributions of source code must retain the above copyright # notice, this list of conditions and the following disclaimer. # # 2. Redistributions in binary form must reproduce the above copyright # notice, this list of conditions and the following disclaimer in # the documentation and/or other materials provided with the # distribution. # # 3. The name "Carnegie Mellon University" must not be used to # endorse or promote products derived from this software without # prior written permission. For permission or any legal # details, please contact # Carnegie Mellon University # Center for Technology Transfer and Enterprise Creation # 4615 Forbes Avenue # Suite 302 # Pittsburgh, PA 15213 # (412) 268-7393, fax: (412) 268-7395 # innovation@andrew.cmu.edu # # 4. Redistributions of any form whatsoever must retain the following # acknowledgment: # "This product includes software developed by Computing Services # at Carnegie Mellon University (http://www.cmu.edu/computing/)." # # CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO # THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY # AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE # FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES # WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN # AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING # OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. exec perl -x -S $0 ${1+"$@"} # -*-perl-*- #!perl -w # # Create newsgroups on imap server # Based on the make_fromactive.pl script by Tim Martin if ($] !~ /^5\..*/) { # uh-oh. this isn't perl 5. foreach (split(/:/, $ENV{PATH})) { # try to find "perl5". exec("$_/perl5", "-x", "-S", $0, @ARGV) if (-x "$_/perl5"); } # we failed. bail. die "Your perl is too old; I need perl 5.\n"; } # load the real script. this is isolated in an 'eval' so perl4 won't # choke on the perl5-isms. eval join("\n", ); if ($@) { die "$@"; } __END__ require 5; use Getopt::Long; use Cyrus::IMAP; use Cyrus::IMAP::Admin; $| = 1; my ($help, $noop, $config, $active, $user, $wild, $part, $acl, $pause) = (0, 0, "/etc/imapd.conf", "./active", $ENV{USER}, "*", undef, "", 0); GetOptions("h|help!" => \$help, "n|noop!" => \$noop, "C|config=s" => \$config, "f|active=s" => \$active, "u|user=s" => \$user, "w|wild=s" => \$wild, "p|part=s" => \$part, "a|acl=s" => \$acl, "pause=s" => \$pause); if ($help || !($server = shift)) { print "\n"; print "mknewsgroups [-h] [-n] [-C ] [-f ] [-u ]\n"; print " [-w ] [-p ] [-a ] \n"; print "\n"; print "\t-h print this help message\n"; print "\t-n print the IMAP commands, but don't execute them\n"; print "\t-C use the config in instead of /etc/imapd.conf\n"; print "\t-f use the newsgroups in instead of ./active\n"; print "\t (get current file from ftp://ftp.isc.org/usenet/CONFIG/active)\n"; print "\t-u authenticate as instead of the current shell user\n"; print "\t-w only create the newsgroups specified by . \n"; print "\t is a comma-separated list of wildmat pattern (eg, \"*,!alt.*\")\n"; print "\t-p create the newsgroup mailboxes on partition \n"; print "\t-a set on the newsgroup. is a whitespace-separated list\n"; print "\t of cyradm-style userid/rights pairs (eg, \"anyone +p news write\")\n"; print "\n"; exit; } # convert wildmat to regex $wild =~ s/\./\\./g; $wild =~ s/\?/\./g; $wild =~ s/\*/\.\*/g; # split acl into a hash of ids and rights while ($acl =~ /^\s*([^\s]+)\s+([^\s]+)/) { $aclhash{$1} = $2; $acl =~ s/^\s*([^\s]+)\s+([^\s]+)//; # skip this id/rights pair } my ($newsprefix, $unixhiersep) = (undef, 0); open CONF, $config or die "can't open $config"; print "reading configure file...\n"; while () { if (/^#/) { next; } if (/^newsprefix:\s+(.*)$/) { $newsprefix = $1; print "you are using \"$newsprefix\" as your news prefix.\n"; } if (/^unixhierarchysep:\s+(1|t|yes|on)/) { $unixhiersep = 1; print "i will deal with unix hierarchy separator.\n"; } } print "done\n"; close CONF; my $client; if (!$noop) { print "connecting... "; $client = Cyrus::IMAP::Admin->new($server); print "authenticating... "; $client->authenticate(-user => $user); print "done\n"; } open (INPUT,"<$active"); while( ) { chop; my $g; if (/((\w|\.|\-|\+)+)\s+(.*)/) { $mbox = $1; # compare group to each part of wildmat my $match = 0; foreach my $w (split(/,/, $wild)) { my $not = substr($w, 0, 1) eq "!"; $w = substr($w, 1) if ($not); $match = !$not if ($mbox =~ /^$w$/); } if ($match) { # add newsprefix if necessary $mbox = $newsprefix . "." . $mbox if (defined($newsprefix)); # switch to unixhiersep if necessary $mbox =~ s^\.^/^g if ($unixhiersep); if ($noop) { $part = "" if (!defined($part)); print "C01 CREATE \"$mbox\" $part\n"; my $n = 1; while (($id,$rights) = each(%aclhash)) { printf "S%02d SETACL \"$mbox\" $id $rights\n", $n++; } } else { $g = 0; print "creating $mbox... "; if ($client->create($mbox, $part)) { while (($id,$rights) = each(%aclhash)) { $client->setacl($mbox, $id => $rights); } $g = 1; } print "done\n"; sleep($pause) if ($g); } } } } close(INPUT); cyrus-imapd-2.5.10/tools/config2man0000755000175000017500000000747113001236020014062 00000000000000#!/bin/sh # # Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. # # Redistribution and use in source and binary forms, with or without # modification, are permitted provided that the following conditions # are met: # # 1. Redistributions of source code must retain the above copyright # notice, this list of conditions and the following disclaimer. # # 2. Redistributions in binary form must reproduce the above copyright # notice, this list of conditions and the following disclaimer in # the documentation and/or other materials provided with the # distribution. # # 3. The name "Carnegie Mellon University" must not be used to # endorse or promote products derived from this software without # prior written permission. For permission or any legal # details, please contact # Carnegie Mellon University # Center for Technology Transfer and Enterprise Creation # 4615 Forbes Avenue # Suite 302 # Pittsburgh, PA 15213 # (412) 268-7393, fax: (412) 268-7395 # innovation@andrew.cmu.edu # # 4. Redistributions of any form whatsoever must retain the following # acknowledgment: # "This product includes software developed by Computing Services # at Carnegie Mellon University (http://www.cmu.edu/computing/)." # # CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO # THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY # AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE # FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES # WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN # AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING # OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. exec perl -x -S $0 ${1+"$@"} # -*-perl-*- #!perl -w if ($] !~ /^5\..*/) { # uh-oh. this isn't perl 5. foreach (split(/:/, $ENV{PATH})) { # try to find "perl5". exec("$_/perl5", "-x", "-S", $0, @ARGV) if (-x "$_/perl5"); } # we failed. bail. die "Your perl is too old; I need perl 5.\n"; } # load the real script. this is isolated in an 'eval' so perl4 won't # choke on the perl5-isms. eval join("\n", ); if ($@) { die "$@"; } __END__ require 5; use strict; sub print_values { my @values = eval $_[0]; my $v; my $sep = " "; print "\nAllowed values:"; foreach $v (@values) { print "$sep\\fI$v\\fR"; $sep = ", "; } print "\n"; } my $mode = 0; my $save = ""; my $enums = ""; my $opt; my $blank = ""; my $version = "\$Revision: 1.6 $blank"; $version =~ s/.Revision: (.*) /$1/; print ".\\\" -*- nroff -*-\n"; print ".\\\" auto-generated by config2man $version\n"; while (<>) { if ($mode == 0) { # look for { option, default, type [enums] }; don't output until we # hit a comment if (m|{\s*\"(.*?)\"\s*,\s*\"?(.*?)\"?\s*,\s*(.*?)\s*(\(.*\))?\s*}|) { $opt = $1; my $def = $2 eq "NULL" ? "" : $2; if ($def eq "") { $def = "" } $save = ".IP \"\\fB$1:\\fR $def\" 5\n"; $enums = $4; } # look for single-line comment elsif (m|/\*\s*(.*)\s*\*/|) { print $save; $save = ""; print "$1\n"; if ($enums) { print_values($enums); } $opt = undef; } # look for /* to shift into passthrough mode; print current # cached option header if any elsif (m|/\*\s*(.*)|) { print $save; $save = ""; if (defined $opt) { print ".RS 5\n"; } print $1; print "\n"; # add LF so lines don't run together $mode = 1; } else { chomp; #print "ignoring '$_'\n"; } } elsif ($mode == 1) { # passthru; look for */ to end if (m|\s*(.*)\*/|) { print $1; print "\n"; if ($enums) { print_values($enums); } $mode = 0; # back to search mode if (defined $opt) { print ".RE\n"; } $opt = undef; } elsif (m|\s*(.*)\s*|) { print "$1\n"; } } } cyrus-imapd-2.5.10/tools/rehash0000755000175000017500000002763013001236020013310 00000000000000#!/usr/bin/env perl # # Copyright (c) 1994-2012 Carnegie Mellon University. All rights reserved. # # Redistribution and use in source and binary forms, with or without # modification, are permitted provided that the following conditions # are met: # # 1. Redistributions of source code must retain the above copyright # notice, this list of conditions and the following disclaimer. # # 2. Redistributions in binary form must reproduce the above copyright # notice, this list of conditions and the following disclaimer in # the documentation and/or other materials provided with the # distribution. # # 3. The name "Carnegie Mellon University" must not be used to # endorse or promote products derived from this software without # prior written permission. For permission or any legal # details, please contact # Carnegie Mellon University # Center for Technology Transfer and Enterprise Creation # 4615 Forbes Avenue # Suite 302 # Pittsburgh, PA 15213 # (412) 268-7393, fax: (412) 268-7395 # innovation@andrew.cmu.edu # # 4. Redistributions of any form whatsoever must retain the following # acknowledgment: # "This product includes software developed by Computing Services # at Carnegie Mellon University (http://www.cmu.edu/computing/)." # # CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO # THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY # AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE # FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES # WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN # AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING # OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. use strict; use warnings; use Getopt::Std; my %Opts; getopts('vnhfFiI', \%Opts); usage() if $Opts{h}; my $OPT_NoAction = $Opts{n}; my $OPT_Verbose = $Opts{v} || $Opts{n}; # non-buffered output $| = 1; # XXX - actually read the cyrus username from the imapd.conf and # change ownership as appropriate? die "must not run as root" if ($< == 0); my $imapdconf = shift || usage(); my @bdirs = ("a".."z"); my @fdirs = ("A".."W"); my %ishash = map { $_ => 1 } (@bdirs, @fdirs); # evil globals my @configs = ($imapdconf); my $confdir = "/var/imap"; my @parts; my $yn = "y"; my $sievedir = "/usr/sieve"; my $nosievedir = 0; my $hashimapspool = 0; my $fulldirhash = 0; my $virtdomains = 0; while (my $conf = shift @configs) { read_conf($conf); } $fulldirhash = 0 if $Opts{f}; $fulldirhash = 1 if $Opts{F}; $hashimapspool = 0 if $Opts{i}; $hashimapspool = 1 if $Opts{I}; print "converting configuration directory $confdir... "; foreach my $i ("user", "proc", "lock", "db", "socket", "log", "msg", "quota") { ensure_dir("$confdir/$i"); } # *** rehash the domain subdirectory to the new format, # don't worry about internal format yet if ($virtdomains) { print "domain "; ensure_dir("$confdir/domain"); move_domains("$confdir/domain", 'conf'); } # *** user subdirectory; holds subscription files print "user "; move_users("$confdir/user"); # *** quota subdirectory; holds quota files for each quotaroot print "quota "; move_quotas("$confdir/quota"); print "done\n"; # create the sieve stuff unless ($nosievedir) { print "sieve $sievedir... "; ensure_dir($sievedir); move_sieve($sievedir); print "done\n"; } # *** now for each data partition while (my $part = shift @parts) { print "partition $part... "; ensure_dir($part); # stage is good too ensure_dir("$part/stage."); move_part($part); print "done\n"; } sub usage { die <> 5)) ^ ord($b); $n &= 4294967295; # UINT32_MAX } $h = chr(ord('A') + ($n % 23)); return $h; } else { $h = lc(substr($name, 0, 1)); if (!($h =~ /[a-z]/)) { $h = 'q'; } return $h; } } sub hash_path { my $path = shift; my $item = shift; my $isspool = shift; my $skiptochar = shift; return "$path/$item" unless ($hashimapspool or not $isspool); my $tohash = $item; if ($skiptochar) { # strip up to and including the character $tohash =~ s/^.*?\Q$skiptochar//; if ($skiptochar eq '/' and $tohash =~ m/\./) { # we've got a top level directory, oops $tohash = $item; $tohash =~ s{/.*$}{}; } } return "$path/" . dir_hash_c($tohash) . "/$item"; } sub read_conf { my $file = shift; open CONF, $file or die "can't open $file"; while () { if (/^#/) { next; } if (/\@include:\s+(.*)$/) { push @configs, $1; } if (/^configdirectory:\s+(.*)$/) { $confdir = $1; } if (/^(?:meta)?partition-.*:\s+(.*)$/) { if (grep /$1/, @parts) { next; } push @parts, $1; } if (/^hashimapspool:\s*(1|t|yes|on)/) { $hashimapspool = 1; print "i will also hash partitions.\n"; } if (/^fulldirhash/) { $fulldirhash = 1; } if (/^sieveusehomedir:\s+(1|t|yes|on)/) { $nosievedir = 1; print "you are storing sieve scripts in user's home directories.\n"; } if (/^sievedir:\s+(.*)$/) { $sievedir = $1; print "you are using $sievedir as your sieve directory.\n"; } if (/^virtdomains:\s+(1|t|yes|on|userid)/) { $virtdomains = 1; print "i will deal with virtual domains.\n"; } } close CONF; } sub add_found { # here be dragons, eep my $type = shift; my $found = shift; my $name = shift; my $location = shift; if ($type ne 'part') { if ($found->{$name}) { die "FOUND BOTH $found->{$name} and $location - you need to fix this by hand\n"; } $found->{$name} = $location; return; } unless (opendir(SUB, $location)) { print "Failed to open directory $location\n"; die unless $OPT_NoAction; return; } while (my $sub = readdir SUB) { next if $sub =~ m/^\./; my $key = "$name/$sub"; if ($found->{$key}) { die "FOUND BOTH $found->{$key} and $location/$sub - you need to fix this by hand\n"; } $found->{$key} = "$location/$sub"; } closedir(SUB); } sub find_items { my $path = shift; my $type = shift; my %found; my @subs; unless (opendir(ITEMS, $path)) { print "Failed to open directory $path\n"; die unless $OPT_NoAction; return; } while (my $item = readdir ITEMS) { # guaranteed evil next if $item =~ m/^\./; next if $item eq 'lost+found'; next if $item eq 'stage.'; next if $item eq 'sync.'; next if $item eq 'domain'; # this is just stupid, it should at LEAST have a dot if ($ishash{$item}) { push @subs, $item; } else { add_found($type, \%found, $item, "$path/$item"); } } closedir(ITEMS); foreach my $sub (@subs) { next unless opendir(ITEMS, "$path/$sub"); while (my $item = readdir ITEMS) { next if $item =~ m/^\./; # we can't fix duplicate directories ourselves! add_found($type, \%found, $item, "$path/$sub/$item"); } closedir(ITEMS); } return %found; } sub do_moves { my $path = shift; my $isspool = shift; my $skiptochar = shift; my %found = @_; foreach my $item (sort keys %found) { my $src = $found{$item}; my $dst = hash_path($path, $item, $isspool, $skiptochar); if ($src ne $dst) { ensure_parent($dst); print "rename $src to $dst: " if $OPT_Verbose; if ($OPT_NoAction) { print "skipped\n" if $OPT_Verbose; next; } rename($src, $dst) or die "failed to rename $src to $dst"; print "done\n" if $OPT_Verbose; } } } sub move_domains { my $path = shift; my $type_of_move = shift || die "move_domains called badly"; my $isspool = ($type_of_move eq 'part'); my %found = find_items($path, 'domain'); # let's do the subdirs first, then move the top levels foreach my $item (sort keys %found) { if ($type_of_move eq 'conf') { if (-d "$found{$item}/quota") { move_quotas("$found{$item}/quota"); } if (-d "$found{$item}/user") { move_users("$found{$item}/user"); } } elsif ($type_of_move eq 'sieve') { move_sieve($found{$item}, 1); } elsif ($type_of_move eq 'part') { move_part($found{$item}, 1); } else { die "bad domain move mode: $type_of_move"; } } do_moves($path, $isspool, undef, %found); tidy_up($path, $isspool, 0); } sub move_users { my $path = shift; my %found = find_items($path, 'user'); do_moves($path, 0, undef, %found); tidy_up($path, 0, 0); } sub move_quotas { my $path = shift; my %found = find_items($path, 'quota'); do_moves($path, 0, '.', %found); tidy_up($path, 0, 0); } sub move_sieve { my $path = shift; my $indomain = shift; my %found = find_items($path, 'sieve'); if ($virtdomains and not $indomain) { ensure_dir("$path/domain"); move_domains("$path/domain", 'sieve'); } do_moves($path, 0, undef, %found); tidy_up($path, 0, 0); } # could be data or meta sub move_part { my $path = shift; my $indomain = shift; # let's just assume nobody is being stupid and creating 1 character toplevel names my %found = find_items($path, 'part'); if ($virtdomains and not $indomain) { ensure_dir("$path/domain"); move_domains("$path/domain", 'part'); } do_moves($path, 1, '/', %found); tidy_up($path, 1, 1); } sub ensure_dir { my $dir = shift; unless (-d $dir) { ensure_parent($dir); print "mkdir $dir: " if $OPT_Verbose; if ($OPT_NoAction) { print "skipped\n" if $OPT_Verbose; return; } mkdir($dir, 0755) || die "Failed to create $dir: $!"; print "done\n" if $OPT_Verbose; } return 1; } sub ensure_parent { my $path = shift; $path =~ s{/[^/]+$}{}; return ensure_dir($path); } sub remove_dir { my $dir = shift; return 1 unless -d $dir; print "rmdir $dir: " if $OPT_Verbose; if ($OPT_NoAction) { print "skipped\n" if $OPT_Verbose; return; } if (opendir(DH, $dir)) { my @extra; while (my $item = readdir(DH)) { next if $item eq '.'; next if $item eq '..'; push @extra, $item; } closedir(DH); if (@extra) { my $num = @extra; my $s = $num == 1 ? '' : 's'; print "skipped, $num extra item$s found, including $dir/$extra[0]\n"; return; } } rmdir($dir) || die "Failed to remove $dir: $!"; print "done\n" if $OPT_Verbose; return 1; } sub tidydir { my $dir = shift; my $onemore = shift; if ($onemore) { if (opendir(DIR, $dir)) { while (my $item = readdir DIR) { next if $item =~ m/^\./; remove_dir("$dir/$item"); } closedir(DIR); } } remove_dir($dir); } sub tidy_up { my $path = shift; my $isspool = shift; my $onemore = shift; unless (not $fulldirhash and (not $isspool or $hashimapspool)) { tidydir("$path/$_", $onemore) for @bdirs; } unless ($fulldirhash and (not $isspool or $hashimapspool)) { tidydir("$path/$_", $onemore) for @fdirs; } } cyrus-imapd-2.5.10/tools/convert-sieve.pl0000644000175000017500000000060313001236020015225 00000000000000#!/usr/bin/perl # # Run this script in your sievedir to fix the names of people's sieve # directories to conform with the altnamespace format. # $|++; foreach $file (glob "?/*.*") { print "Converting $file..."; $oldfile = $file; $file =~ s/\./^/g; print "to $file..."; if (rename $oldfile, $file) { print "Done.\n"; } else { print "Error: $!\n"; } } cyrus-imapd-2.5.10/com_err/0000755000175000017500000000000013001246663012464 500000000000000cyrus-imapd-2.5.10/com_err/et/0000755000175000017500000000000013001246664013075 500000000000000cyrus-imapd-2.5.10/com_err/et/compile_et.sh0000755000175000017500000000367612772415051015512 00000000000000#!/bin/sh # # Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. # # Redistribution and use in source and binary forms, with or without # modification, are permitted provided that the following conditions # are met: # # 1. Redistributions of source code must retain the above copyright # notice, this list of conditions and the following disclaimer. # # 2. Redistributions in binary form must reproduce the above copyright # notice, this list of conditions and the following disclaimer in # the documentation and/or other materials provided with the # distribution. # # 3. The name "Carnegie Mellon University" must not be used to # endorse or promote products derived from this software without # prior written permission. For permission or any legal # details, please contact # Carnegie Mellon University # Center for Technology Transfer and Enterprise Creation # 4615 Forbes Avenue # Suite 302 # Pittsburgh, PA 15213 # (412) 268-7393, fax: (412) 268-7395 # innovation@andrew.cmu.edu # # 4. Redistributions of any form whatsoever must retain the following # acknowledgment: # "This product includes software developed by Computing Services # at Carnegie Mellon University (http://www.cmu.edu/computing/)." # # CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO # THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY # AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE # FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES # WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN # AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING # OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. AWK=@AWK@ DIR=@DIR@ ROOT=`echo $1 | sed -e s/.et$//` BASE=`echo $ROOT | sed -e 's;.*/;;'` $AWK -f ${DIR}/et_h.awk outfile=${BASE}.h $ROOT.et $AWK -f ${DIR}/et_c.awk outfile=${BASE}.c $ROOT.et cyrus-imapd-2.5.10/com_err/et/et_c.awk0000644000175000017500000001005213001236020014412 00000000000000BEGIN { char_shift=64 ## "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789_"; c2n["A"]=1 c2n["B"]=2 c2n["C"]=3 c2n["D"]=4 c2n["E"]=5 c2n["F"]=6 c2n["G"]=7 c2n["H"]=8 c2n["I"]=9 c2n["J"]=10 c2n["K"]=11 c2n["L"]=12 c2n["M"]=13 c2n["N"]=14 c2n["O"]=15 c2n["P"]=16 c2n["Q"]=17 c2n["R"]=18 c2n["S"]=19 c2n["T"]=20 c2n["U"]=21 c2n["V"]=22 c2n["W"]=23 c2n["X"]=24 c2n["Y"]=25 c2n["Z"]=26 c2n["a"]=27 c2n["b"]=28 c2n["c"]=29 c2n["d"]=30 c2n["e"]=31 c2n["f"]=32 c2n["g"]=33 c2n["h"]=34 c2n["i"]=35 c2n["j"]=36 c2n["k"]=37 c2n["l"]=38 c2n["m"]=39 c2n["n"]=40 c2n["o"]=41 c2n["p"]=42 c2n["q"]=43 c2n["r"]=44 c2n["s"]=45 c2n["t"]=46 c2n["u"]=47 c2n["v"]=48 c2n["w"]=49 c2n["x"]=50 c2n["y"]=51 c2n["z"]=52 c2n["0"]=53 c2n["1"]=54 c2n["2"]=55 c2n["3"]=56 c2n["4"]=57 c2n["5"]=58 c2n["6"]=59 c2n["7"]=60 c2n["8"]=61 c2n["9"]=62 c2n["_"]=63 } /^#/ { next } /^[ \t]*(error_table|et)[ \t]+[a-zA-Z][a-zA-Z0-9_]+/ { table_number = 0 table_name = $2 mod_base = 1000000 for(i=1; i<=length(table_name); i++) { table_number=(table_number*char_shift)+c2n[substr(table_name,i,1)] } # We start playing *_high, *low games here because the some # awk programs do not have the necessary precision (sigh) tab_base_low = table_number % mod_base tab_base_high = int(table_number / mod_base) tab_base_sign = 1; # figure out: table_number_base=table_number*256 tab_base_low = tab_base_low * 256 tab_base_high = (tab_base_high * 256) + \ int(tab_base_low / mod_base) tab_base_low = tab_base_low % mod_base if (table_number > 128*256*256) { # figure out: table_number_base -= 256*256*256*256 # sub_high, sub_low is 256*256*256*256 sub_low = 256*256*256 % mod_base sub_high = int(256*256*256 / mod_base) sub_low = sub_low * 256 sub_high = (sub_high * 256) + int(sub_low / mod_base) sub_low = sub_low % mod_base tab_base_low = sub_low - tab_base_low; tab_base_high = sub_high - tab_base_high; tab_base_sign = -1; if (tab_base_low < 0) { tab_base_low = tab_base_low + mod_base tab_base_high-- } } print "/*" > outfile print " * " outfile ":" > outfile print " * This file is automatically generated; please do not edit it." > outfile print " */" > outfile print "#if defined(__STDC__) || defined(_WINDOWS)" > outfile print "#define NOARGS void" > outfile print "#else" > outfile print "#define NOARGS" > outfile print "#define const" > outfile print "#endif" > outfile print "" > outfile print "static const char * const text[] = {" > outfile table_item_count = 0 } /^[ \t]*(error_code|ec)[ \t]+[A-Z_0-9]+,[ \t]*$/ { skipone=1 next } /^[ \t]*(error_code|ec)[ \t]+[A-Z_0-9]+,[ \t]*".*"[ \t]*$/ { text="" for (i=3; i<=NF; i++) { text = text FS $i } text=substr(text,2,length(text)-1); printf "\t%s,\n", text > outfile table_item_count++ } { if (skipone) { printf "\t%s,\n", $0 > outfile table_item_count++ } skipone=0 } END { print " 0" > outfile print "};" > outfile print "" > outfile print "struct error_table {" > outfile print " char const * const * msgs;" > outfile print " long base;" > outfile print " int n_msgs;" > outfile print "};" > outfile print "struct et_list {" > outfile print " struct et_list *next;" > outfile print " const struct error_table * table;" > outfile print "};" > outfile print "extern struct et_list *_et_list;" > outfile print "" > outfile if (tab_base_high == 0) { print "static const struct error_table et = { text, " \ sprintf("%dL, %d };", tab_base_sign*tab_base_low, \ table_item_count) > outfile } else { print "static const struct error_table et = { text, " \ sprintf("%d%06dL, %d };", tab_base_sign*tab_base_high, \ tab_base_low, table_item_count) > outfile } print "" > outfile print "static struct et_list link = { 0, 0 };" > outfile print "" > outfile print "void initialize_" table_name "_error_table (NOARGS) {" > outfile print " if (!link.table) {" > outfile print " link.next = _et_list;" > outfile print " link.table = &et;" > outfile print " _et_list = &link;" > outfile print " }" > outfile print "}" > outfile } cyrus-imapd-2.5.10/com_err/et/internal.h0000644000175000017500000000411612772415051015006 00000000000000/* internal include file for com_err package * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include "mit-sipb-copyright.h" #include #ifdef NEED_SYS_ERRLIST extern char const * const sys_errlist[]; extern const int sys_nerr; #endif #if defined(__STDC__) && !defined(HDR_HAS_PERROR) && !defined(_WINDOWS) void perror (const char *); #endif cyrus-imapd-2.5.10/com_err/et/test1.et0000644000175000017500000000215113001236020014367 00000000000000 error_table krb error_code KRB_MK_AP_TKFIL, "Can't read ticket file" ec KRB_MK_AP_NOTKT, "Can't find ticket or TGT" ec KRB_MK_AP_TGTEXP, "TGT expired" ec KRB_RD_AP_UNDEC, "Can't decode authenticator" ec KRB_RD_AP_EXP, "Ticket expired" ec KRB_RD_AP_REPEAT, "Repeated request" ec KRB_RD_AP_NOT_US, "The ticket isn't for us" ec KRB_RD_AP_INCON, "Request is inconsistent" ec KRB_RD_AP_TIME, "Delta-T too big" ec KRB_RD_AP_BADD, "Incorrect net address" ec KRB_RD_AP_VERSION, "Protocol version mismatch" ec KRB_RD_AP_MSG_TYPE, "Invalid message type" ec KRB_RD_AP_MODIFIED, "Message stream modified" ec KRB_RD_AP_ORDER, "Message out of order" ec KRB_RD_AP_UNAUTHOR, "Unauthorized request" ec KRB_GT_PW_NULL, "Current password is null" ec KRB_GT_PW_BADPW, "Incorrect current password" ec KRB_GT_PW_PROT, "Protocol error" ec KRB_GT_PW_KDCERR, "Error returned by KDC" ec KRB_GT_PW_NULLTKT, "Null ticket returned by KDC" ec KRB_SKDC_RETRY, "Retry count exceeded" ec KRB_SKDC_CANT, "Can't send request" end cyrus-imapd-2.5.10/com_err/et/error_message.c0000644000175000017500000000675713001236020016016 00000000000000/* error_message.c * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. * * Copyright 1987 by the Student Information Processing Board * of the Massachusetts Institute of Technology * * For copyright info, see "mit-sipb-copyright.h". */ #define IN_COM_ERR #include #include #include #include #include "error_table.h" #include "mit-sipb-copyright.h" #include "internal.h" static const char copyright[] __attribute__((__unused__)) = "Copyright 1986, 1987, 1988 by the Student Information Processing Board\nand the department of Information Systems\nof the Massachusetts Institute of Technology"; static char buffer[25]; extern struct et_list * _et_list; EXPORTED const char * INTERFACE error_message (code) long code; { int offset; long l_offset; struct et_list *et; long table_num; int started = 0; char *cp; l_offset = code & ((1<next) { if (et->table->base == table_num) { /* This is the right table */ if (et->table->n_msgs <= offset) goto oops; return(et->table->msgs[offset]); } } oops: strcpy (buffer, "Unknown code "); if (table_num) { strcat (buffer, error_table_name (table_num)); strcat (buffer, " "); } for (cp = buffer; *cp; cp++) ; if (offset >= 100) { *cp++ = '0' + offset / 100; offset %= 100; started++; } if (started || offset >= 10) { *cp++ = '0' + offset / 10; offset %= 10; } *cp++ = '0' + offset; *cp = '\0'; return(buffer); } cyrus-imapd-2.5.10/com_err/et/test_et.c0000644000175000017500000000340613001236020014614 00000000000000#include #include #include "com_err.h" #include "test1.h" #include "test2.h" extern int sys_nerr, errno; main() { printf("Before initiating error table:\n\n"); printf("Table name '%s'\n", error_table_name(KRB_MK_AP_TGTEXP)); printf("UNIX name '%s'\n", error_table_name(EPERM)); printf("Msg TGT-expired is '%s'\n", error_message(KRB_MK_AP_TGTEXP)); printf("Msg EPERM is '%s'\n", error_message(EPERM)); printf("Msg FOO_ERR is '%s'\n", error_message(FOO_ERR)); printf("Msg {sys_nerr-1} is '%s'\n", error_message(sys_nerr-1)); printf("Msg {sys_nerr} is '%s'\n", error_message(sys_nerr)); printf("With 0: tgt-expired -> %s\n", error_message(KRB_MK_AP_TGTEXP)); initialize_krb_error_table(); printf("KRB error table initialized: base %d (%s), name %s\n", ERROR_TABLE_BASE_krb, error_message(ERROR_TABLE_BASE_krb), error_table_name(ERROR_TABLE_BASE_krb)); initialize_krb_error_table(); printf("With krb: tgt-expired -> %s\n", error_message(KRB_MK_AP_TGTEXP)); initialize_quux_error_table(); printf("QUUX error table initialized: base %d (%s), name %s\n", ERROR_TABLE_BASE_quux, error_message(ERROR_TABLE_BASE_quux), error_table_name(ERROR_TABLE_BASE_quux)); printf("Msg for TGT-expired is '%s'\n", error_message(KRB_MK_AP_TGTEXP)); printf("Msg {sys_nerr-1} is '%s'\n", error_message(sys_nerr-1)); printf("Msg FOO_ERR is '%s'\n", error_message(FOO_ERR)); printf("Msg KRB_SKDC_CANT is '%s'\n", error_message(KRB_SKDC_CANT)); printf("Msg 1e6 (8B 64) is '%s'\n", error_message(1000000)); printf("\n\nCOM_ERR tests:\n"); com_err("whoami", FOO_ERR, (char *)NULL); com_err("whoami", FOO_ERR, " -- message goes %s", "here"); com_err("whoami", 0, (char *)0); com_err("whoami", 0, "error number %d\n", 0); } cyrus-imapd-2.5.10/com_err/et/config_script0000755000175000017500000000431613001236020015561 00000000000000#!/bin/sh # # Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. # # Redistribution and use in source and binary forms, with or without # modification, are permitted provided that the following conditions # are met: # # 1. Redistributions of source code must retain the above copyright # notice, this list of conditions and the following disclaimer. # # 2. Redistributions in binary form must reproduce the above copyright # notice, this list of conditions and the following disclaimer in # the documentation and/or other materials provided with the # distribution. # # 3. The name "Carnegie Mellon University" must not be used to # endorse or promote products derived from this software without # prior written permission. For permission or any legal # details, please contact # Carnegie Mellon University # Center for Technology Transfer and Enterprise Creation # 4615 Forbes Avenue # Suite 302 # Pittsburgh, PA 15213 # (412) 268-7393, fax: (412) 268-7395 # innovation@andrew.cmu.edu # # 4. Redistributions of any form whatsoever must retain the following # acknowledgment: # "This product includes software developed by Computing Services # at Carnegie Mellon University (http://www.cmu.edu/computing/)." # # CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO # THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY # AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE # FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES # WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN # AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING # OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. # # This program takes a shell script and configures for the following # variables: @DIR@ # @AWK@ # @SED@ # # Usage: config_script [] [] # FILE=$1 AWK=$2 SED=$3 # Grr.... not all Unix's have the dirname command TMP=`echo $1 | sed -e 's;[^/]*$;;' -e 's/^$/./'` DIR=`cd ${TMP}; pwd` if test "${AWK}x" = "x" ; then AWK=awk fi if test "${SED}x" = "x" ; then SED=sed fi sed -e "s;@DIR@;${DIR};" -e "s;@AWK@;${AWK};" -e "s;@SED@;${SED};" $FILE cyrus-imapd-2.5.10/com_err/et/mit-sipb-copyright.h0000644000175000017500000000140113001236020016675 00000000000000/* Copyright 1987, 1988 by the Student Information Processing Board of the Massachusetts Institute of Technology Permission to use, copy, modify, and distribute this software and its documentation for any purpose and without fee is hereby granted, provided that the above copyright notice appear in all copies and that both that copyright notice and this permission notice appear in supporting documentation, and that the names of M.I.T. and the M.I.T. S.I.P.B. not be used in advertising or publicity pertaining to distribution of the software without specific, written prior permission. M.I.T. and the M.I.T. S.I.P.B. make no representations about the suitability of this software for any purpose. It is provided "as is" without express or implied warranty. */ cyrus-imapd-2.5.10/com_err/et/et_name.c0000644000175000017500000000541713001236020014561 00000000000000/* * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. * * Copyright 1987 by MIT Student Information Processing Board * * For copyright info, see mit-sipb-copyright.h. */ #include "error_table.h" #include "mit-sipb-copyright.h" #include "internal.h" #ifndef lint static const char copyright[] __attribute__((__unused__)) = "Copyright 1987,1988 by Student Information Processing Board, Massachusetts Institute of Technology"; #endif static const char char_set[] = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789_"; static char buf[6]; const char * error_table_name (num) long num; { long ch; int i; char *p; /* num = aa aaa abb bbb bcc ccc cdd ddd d?? ??? ??? */ p = buf; num >>= ERRCODE_RANGE; /* num = ?? ??? ??? aaa aaa bbb bbb ccc ccc ddd ddd */ num &= 077777777; /* num = 00 000 000 aaa aaa bbb bbb ccc ccc ddd ddd */ for (i = 4; i >= 0; i--) { ch = (num >> BITS_PER_CHAR * i) & ((1 << BITS_PER_CHAR) - 1); if (ch != 0) *p++ = char_set[ch-1]; } *p = '\0'; return(buf); } cyrus-imapd-2.5.10/com_err/et/error_table.h0000644000175000017500000000616313001236020015455 00000000000000/* * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. * * Copyright 1988 by the Student Information Processing Board of the * Massachusetts Institute of Technology. * * For copyright info, see mit-sipb-copyright.h. */ #ifndef _ET_H /* This directory doesn't really know about the krb5 world. The following windows defines are usually hidden in k5-config.h. For now I'll just place here what is needed from that file. Later we may decide to do it differently. */ #ifdef _WINDOWS #define INTERFACE __far __export __pascal #define INTERFACE_C __far __export __cdecl #define sys_nerr _sys_nerr #define sys_errlist _sys_errlist int __far __pascal MessageBox (void __far *, const char __far*, const char __far*, unsigned int); #define MB_ICONEXCLAMATION 0x0030 #else #define INTERFACE #define INTERFACE_C #include #endif struct error_table { char const * const * msgs; long base; int n_msgs; }; struct et_list { struct et_list *next; const struct error_table *table; }; extern struct et_list * _et_list; #define ERRCODE_RANGE 8 /* # of bits to shift table number */ #define BITS_PER_CHAR 6 /* # bits to shift per character in name */ #if defined(__STDC__) || defined(KRB5_PROVIDE_PROTOTYPES) || defined(_WINDOWS) extern const char *error_table_name (long); #else extern const char *error_table_name (); #endif #define _ET_H #endif cyrus-imapd-2.5.10/com_err/et/init_et.c0000644000175000017500000000517613001236020014606 00000000000000/* init_et.c * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. * * Copyright 1986, 1987, 1988 by MIT Information Systems and * the MIT Student Information Processing Board. * * For copyright info, see mit-sipb-copyright.h. */ #include #include #include "error_table.h" #include "mit-sipb-copyright.h" struct foobar { struct et_list etl; struct error_table et; }; extern struct et_list * _et_list; int init_error_table(msgs, base, count) const char * const * msgs; int base; int count; { struct foobar * new_et; if (!base || !count || !msgs) return 0; new_et = (struct foobar *) malloc(sizeof(struct foobar)); if (!new_et) return errno; /* oops */ new_et->etl.table = &new_et->et; new_et->et.msgs = msgs; new_et->et.base = base; new_et->et.n_msgs= count; new_et->etl.next = _et_list; _et_list = &new_et->etl; return 0; } cyrus-imapd-2.5.10/com_err/et/com_err.c0000644000175000017500000001156213001236020014575 00000000000000/* * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. * * Copyright 1987, 1988 by MIT Student Information Processing Board. * * For copyright info, see mit-sipb-copyright.h. */ #define IN_COM_ERR #include #include #include #include "mit-sipb-copyright.h" #if defined(HAVE_STDARG_H) || defined(_WINDOWS) #include #else #include #define VARARGS #endif #include "error_table.h" #include "internal.h" EXPORTED struct et_list * _et_list = (struct et_list *) NULL; #ifdef notdef /* * Protect us from header version (externally visible) of com_err, so * we can survive in a environment. I think. */ #define com_err com_err_external #include "com_err.h" #undef com_err #endif /* We have problems with varargs definitions if we include com_err.h */ /* * XXX for now, we define error_message by hand. Ultimately, we * should fix up com_err.h so that it's safe to #include here * directly. */ #if defined(__STDC__) || defined(_WINDOWS) extern char const * INTERFACE error_message (long); #else extern char * INTERFACE error_message (); #endif static void #if defined(__STDC__) || defined(_WINDOWS) default_com_err_proc (const char *whoami, long code, const char *fmt, va_list args) #else default_com_err_proc (whoami, code, fmt, args) const char *whoami; long code; const char *fmt; va_list args; #endif { static char errbuf[1024]; /* For those w/o stdio */ *errbuf = '\0'; if (whoami) { strcat (errbuf, whoami); strcat (errbuf, ": "); } if (code) { strcat (errbuf, error_message(code)); strcat (errbuf, " "); } if (fmt) { vsprintf (errbuf + strlen (errbuf), fmt, args); } #ifdef _WINDOWS MessageBox (NULL, errbuf, "Kerboros", MB_ICONEXCLAMATION); #else fputs (errbuf, stderr); /* should do this only on a tty in raw mode */ putc('\r', stderr); putc('\n', stderr); fflush(stderr); #endif } #if defined(__STDC__) || defined(_WINDOWS) typedef void (*errf) (const char *, long, const char *, va_list); #else typedef void (*errf) (); #endif errf com_err_hook = default_com_err_proc; void com_err_va (whoami, code, fmt, args) const char *whoami; long code; const char *fmt; va_list args; { (*com_err_hook) (whoami, code, fmt, args); } #ifndef VARARGS EXPORTED void INTERFACE_C com_err (const char *whoami, long code, const char *fmt, ...) { #else EXPORTED void INTERFACE_C com_err (va_alist) va_dcl { const char *whoami, *fmt; long code; #endif va_list pvar; if (!com_err_hook) com_err_hook = default_com_err_proc; #ifdef VARARGS va_start (pvar); whoami = va_arg (pvar, const char *); code = va_arg (pvar, long); fmt = va_arg (pvar, const char *); #else va_start(pvar, fmt); #endif com_err_va (whoami, code, fmt, pvar); va_end(pvar); } errf set_com_err_hook (new_proc) errf new_proc; { errf x = com_err_hook; if (new_proc) com_err_hook = new_proc; else com_err_hook = default_com_err_proc; return x; } errf reset_com_err_hook () { errf x = com_err_hook; com_err_hook = default_com_err_proc; return x; } cyrus-imapd-2.5.10/com_err/et/et_h.awk0000644000175000017500000000641513001236020014427 00000000000000BEGIN { char_shift=64 ## "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789_"; c2n["A"]=1 c2n["B"]=2 c2n["C"]=3 c2n["D"]=4 c2n["E"]=5 c2n["F"]=6 c2n["G"]=7 c2n["H"]=8 c2n["I"]=9 c2n["J"]=10 c2n["K"]=11 c2n["L"]=12 c2n["M"]=13 c2n["N"]=14 c2n["O"]=15 c2n["P"]=16 c2n["Q"]=17 c2n["R"]=18 c2n["S"]=19 c2n["T"]=20 c2n["U"]=21 c2n["V"]=22 c2n["W"]=23 c2n["X"]=24 c2n["Y"]=25 c2n["Z"]=26 c2n["a"]=27 c2n["b"]=28 c2n["c"]=29 c2n["d"]=30 c2n["e"]=31 c2n["f"]=32 c2n["g"]=33 c2n["h"]=34 c2n["i"]=35 c2n["j"]=36 c2n["k"]=37 c2n["l"]=38 c2n["m"]=39 c2n["n"]=40 c2n["o"]=41 c2n["p"]=42 c2n["q"]=43 c2n["r"]=44 c2n["s"]=45 c2n["t"]=46 c2n["u"]=47 c2n["v"]=48 c2n["w"]=49 c2n["x"]=50 c2n["y"]=51 c2n["z"]=52 c2n["0"]=53 c2n["1"]=54 c2n["2"]=55 c2n["3"]=56 c2n["4"]=57 c2n["5"]=58 c2n["6"]=59 c2n["7"]=60 c2n["8"]=61 c2n["9"]=62 c2n["_"]=63 } /^#/ { next } /^[ \t]*(error_table|et)[ \t]+[a-zA-Z][a-zA-Z0-9_]+/ { table_number = 0 table_name = $2 mod_base = 1000000 for(i=1; i<=length(table_name); i++) { table_number=(table_number*char_shift)+c2n[substr(table_name,i,1)] } # We start playing *_high, *low games here because the some # awk programs do not have the necessary precision (sigh) tab_base_low = table_number % mod_base tab_base_high = int(table_number / mod_base) tab_base_sign = 1; # figure out: table_number_base=table_number*256 tab_base_low = tab_base_low * 256 tab_base_high = (tab_base_high * 256) + \ int(tab_base_low / mod_base) tab_base_low = tab_base_low % mod_base if (table_number > 128*256*256) { # figure out: table_number_base -= 256*256*256*256 # sub_high, sub_low is 256*256*256*256 sub_low = 256*256*256 % mod_base sub_high = int(256*256*256 / mod_base) sub_low = sub_low * 256 sub_high = (sub_high * 256) + int(sub_low / mod_base) sub_low = sub_low % mod_base tab_base_low = sub_low - tab_base_low; tab_base_high = sub_high - tab_base_high; tab_base_sign = -1; if (tab_base_low < 0) { tab_base_low = tab_base_low + mod_base tab_base_high-- } } curr_low = tab_base_low curr_high = tab_base_high curr_sign = tab_base_sign print "/*" > outfile print " * " outfile ":" > outfile print " * This file is automatically generated; please do not edit it." > outfile print " */" > outfile } /^[ \t]*(error_code|ec)[ \t]+[A-Z_0-9]+,/ { tag=substr($2,1,length($2)-1) if (curr_high == 0) { printf "#define %-40s (%dL)\n", tag, \ curr_sign*curr_low > outfile } else { printf "#define %-40s (%d%06dL)\n", tag, curr_high*curr_sign, \ curr_low > outfile } curr_low += curr_sign; if (curr_low >= mod_base) { curr_low -= mod_base; curr_high++ } if (curr_low < 0) { cur_low += mod_base cur_high-- } } END { print "extern void initialize_" table_name "_error_table ();" > outfile if (tab_base_high == 0) { print "#define ERROR_TABLE_BASE_" table_name " (" \ sprintf("%d", tab_base_sign*tab_base_low) \ "L)" > outfile } else { print "#define ERROR_TABLE_BASE_" table_name " (" \ sprintf("%d%06d", tab_base_sign*tab_base_high, \ tab_base_low) "L)" > outfile } print "" > outfile print "/* for compatibility with older versions... */" > outfile print "#define init_" table_name "_err_tbl initialize_" table_name "_error_table" > outfile print "#define " table_name "_err_base ERROR_TABLE_BASE_" table_name > outfile } cyrus-imapd-2.5.10/com_err/et/test2.et0000644000175000017500000000012513001236020014367 00000000000000 error_table quux ec FOO_ERR, "foo" ec BAR_ERR, "bar" ec BAZ_ERR, "meow" end cyrus-imapd-2.5.10/com_err/et/com_err.h0000644000175000017500000000677313001236020014612 00000000000000/* * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ /* * Header file for common error description library. * * Copyright 1988, Student Information Processing Board of the * Massachusetts Institute of Technology. * * Copyright 1995 by Cygnus Support. * * For copyright and distribution info, see the documentation supplied * with this package. */ #ifndef __COM_ERR_H #ifndef HAVE_STDARG_H /* End-user programs may need this -- oh well */ #if defined(__STDC__) || defined(_WINDOWS) #define HAVE_STDARG_H 1 #endif #endif #ifdef HAVE_STDARG_H #include #else #include #endif #include "error_table.h" /* This should be part of k5-config.h but many application * programs are not including that file. We probably want to * come up with a better way of handling this problem. */ #ifndef INTERFACE #ifdef _WINDOWS #define INTERFACE __far __export __pascal #define INTERFACE_C __far __export __cdecl #else #define INTERFACE #define INTERFACE_C #endif #endif #ifndef FAR #define FAR #endif #if defined(__STDC__) || defined(_WINDOWS) /* ANSI C -- use prototypes etc */ extern void INTERFACE_C com_err (const char FAR *, long, const char FAR *, ...); extern char const FAR * INTERFACE error_message (long); extern void (*com_err_hook) (const char *, long, const char *, va_list); extern void (*set_com_err_hook (void (*) (const char *, long, const char *, va_list))) (const char *, long, const char *, va_list); extern void (*reset_com_err_hook ()) (const char *, long, const char *, va_list); #else /* no prototypes */ extern void INTERFACE_C com_err (); extern char * INTERFACE error_message (); extern void (*com_err_hook) (); extern void (*set_com_err_hook ()) (); extern void (*reset_com_err_hook ()) (); #endif #define __COM_ERR_H #endif /* ! defined(__COM_ERR_H) */ cyrus-imapd-2.5.10/configure.ac0000644000175000017500000015317713001236020013244 00000000000000dnl Process this file with autoconf to produce a configure script. dnl dnl Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. dnl dnl Redistribution and use in source and binary forms, with or without dnl modification, are permitted provided that the following conditions dnl are met: dnl dnl 1. Redistributions of source code must retain the above copyright dnl notice, this list of conditions and the following disclaimer. dnl dnl 2. Redistributions in binary form must reproduce the above copyright dnl notice, this list of conditions and the following disclaimer in dnl the documentation and/or other materials provided with the dnl distribution. dnl dnl 3. The name "Carnegie Mellon University" must not be used to dnl endorse or promote products derived from this software without dnl prior written permission. For permission or any legal dnl details, please contact dnl Carnegie Mellon University dnl Center for Technology Transfer and Enterprise Creation dnl 4615 Forbes Avenue dnl Suite 302 dnl Pittsburgh, PA 15213 dnl (412) 268-7393, fax: (412) 268-7395 dnl innovation@andrew.cmu.edu dnl dnl 4. Redistributions of any form whatsoever must retain the following dnl acknowledgment: dnl "This product includes software developed by Computing Services dnl at Carnegie Mellon University (http://www.cmu.edu/computing/)." dnl dnl CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO dnl THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY dnl AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE dnl FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES dnl WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN dnl AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING dnl OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. dnl dnl configure.ac for the Cyrus imapd dnl AC_INIT([cyrus-imapd], m4_esyscmd(printf '%s' $(tools/git-version.sh)), [https://github.com/cyrusimap/cyrus-imapd/issues], , [https://www.cyrusimap.org]) AC_PREREQ([2.63]) AC_CONFIG_SRCDIR([imap/imapd.c]) AC_CONFIG_HEADERS(config.h) AC_CONFIG_MACRO_DIR([cmulocal]) AC_CANONICAL_SYSTEM dnl in case the first use of PKG_CHECK_MODULES is inside a conditional PKG_PROG_PKG_CONFIG AM_INIT_AUTOMAKE([-Wall -Werror -Wno-portability foreign dist-bzip2 no-installinfo subdir-objects]) AC_CONFIG_LIBOBJ_DIR([lib]) dnl Useful hook for distributions AC_ARG_WITH(extraident, [AS_HELP_STRING([--with-extraident=STRING],[use STRING as extra version information])], [AC_DEFINE_UNQUOTED(EXTRA_IDENT,"$withval", [Extra version information for imap/version.h])]) AM_MAINTAINER_MODE dnl Coverage (disabled by default) COV_CFLAGS= COV_LDFLAGS= AC_ARG_ENABLE(coverage, AS_HELP_STRING([--enable-coverage],[enable C test coverage]) ) AS_IF([test "x$enable_coverage" = "xyes"], [ COV_CFLAGS="--coverage" COV_LDFLAGS="--coverage" ]) AC_SUBST(COV_CFLAGS) AC_SUBST(COV_LDFLAGS) AC_ARG_WITH(login,,AC_MSG_ERROR([--with-login is no longer supported. Configure SASL appropriately instead.])) dnl We need to derive default values for --with-cyrus-prefix and dnl --with-service-path based on $prefix, but $prefix may currently dnl be set to "NONE" for autoconf reasons, so work around that. if test "x$prefix" = "xNONE"; then myprefix="$ac_default_prefix" else myprefix="$prefix" fi AC_ARG_WITH(cyrus-prefix, [AS_HELP_STRING([--with-cyrus-prefix=DIR], [use DIR as cyrus server install directory [PREFIX/cyrus]])], cyrus_prefix="$withval",cyrus_prefix="$myprefix/cyrus") AC_DEFINE_UNQUOTED(CYRUS_PATH,"$cyrus_prefix",[Where will we be installed?]) AC_ARG_WITH(service-path, [AS_HELP_STRING([--with-service-path=DIR], [use DIR as service install directory [CYRUSPREFIX/bin]])], servicedir="$withval",servicedir="$cyrus_prefix/bin") userdir=$servicedir AC_SUBST(userdir) AC_SUBST(servicedir) AC_DEFINE_UNQUOTED(SERVICE_DIR,"$servicedir",[Directory to use for service binaries]) AC_ARG_WITH(cyrus-user, [AS_HELP_STRING([--with-cyrus-user=USERID], [use USERID cyrus userid])], cyrus_user="$withval",cyrus_user="cyrus") AC_SUBST(cyrus_user) AC_DEFINE_UNQUOTED(CYRUS_USER, "$cyrus_user",[What user will we run as?]) AC_ARG_WITH(cyrus-group, [AS_HELP_STRING([--with-cyrus-group=GROUPID], [use GROUPID cyrus group])], cyrus_group="$withval",cyrus_group="mail") AC_SUBST(cyrus_group) dnl allow users to override $sysconfdir, but retain old default (/etc) dnl if not specified if test $sysconfdir = '${prefix}/etc'; then sysconfdir="/etc" fi AC_DEFINE_UNQUOTED(SYSCONFDIR,"$sysconfdir",[Config File Location]) AC_PROG_CC AM_PROG_CC_C_O AC_PROG_LN_S AC_PROG_MAKE_SET AC_PROG_INSTALL AC_USE_SYSTEM_EXTENSIONS AC_ISC_POSIX AC_PROG_AWK AC_C_CONST AC_SYS_LONG_FILE_NAMES if test $ac_cv_sys_long_file_names = no; then AC_MSG_ERROR(The Cyrus IMAPD requires support for long file names) fi AC_C_INLINE gl_VISIBILITY AH_BOTTOM([#if HAVE_VISIBILITY #define EXPORTED __attribute__((__visibility__("default"))) #define HIDDEN __attribute__((__visibility__("hidden"))) #else #define EXPORTED #define HIDDEN #endif]) LT_PREREQ([2.2.6]) LT_INIT([disable-static]) AC_SUBST([LIBTOOL_DEPS]) dnl Check the size of various types AC_CHECK_SIZEOF(int) AC_CHECK_SIZEOF(long) AC_CHECK_SIZEOF(size_t) AC_CHECK_SIZEOF(off_t) dnl Check that `long long int' is available AC_CHECK_SIZEOF(long long int) AC_CHECK_SIZEOF(unsigned long long int) if test "$ac_cv_sizeof_long_long_int" -eq 8 -a \ "$ac_cv_sizeof_unsigned_long_long_int" -eq 8; then AC_C_BIGENDIAN else AC_MSG_ERROR(The Cyrus IMAPD requires support for long long int) fi CMU_C_FPIC dnl check for -R, etc. switch CMU_GUESS_RUNPATH_SWITCH AC_CHECK_HEADERS(unistd.h sys/select.h sys/param.h stdarg.h) AC_REPLACE_FUNCS(memmove strcasecmp ftruncate strerror posix_fadvise strsep memmem) AC_CHECK_FUNCS(strlcat strlcpy getgrouplist fmemopen pselect) AC_HEADER_DIRENT dnl check whether to use getpassphrase or getpass AC_CHECK_HEADERS(stdlib.h) AC_CHECK_FUNCS(getpassphrase) dnl do this before Berkeley DB/IPv6 detection CMU_SOCKETS LIBS="$LIBS ${LIB_SOCKET}" dnl check for IPv6 functions (fall back to sasl's if we don't have them) cyrus_cv_getaddrinfo=yes IPv6_CHECK_FUNC(getaddrinfo, [IPv6_CHECK_FUNC(gai_strerror, AC_DEFINE(HAVE_GETADDRINFO,[],[Do we have a getaddrinfo?]), cyrus_cv_getaddrinfo=no)], cyrus_cv_getaddrinfo=no) cyrus_cv_getnameinfo=yes IPv6_CHECK_FUNC(getnameinfo, AC_DEFINE(HAVE_GETNAMEINFO,[],[Do we have a getnameinfo?]), cyrus_cv_getnameinfo=no) AM_CONDITIONAL([IPV6_noGETADDRINFO], [test $cyrus_cv_getaddrinfo = no]) AM_CONDITIONAL([IPV6_noGETNAMEINFO], [test $cyrus_cv_getnameinfo = no]) IPv6_CHECK_SS_FAMILY() IPv6_CHECK_SA_LEN() dnl this is to check for time things AC_CHECK_HEADERS(sys/time.h) AC_HEADER_TIME AC_STRUCT_TM AC_STRUCT_TIMEZONE AC_CHECK_FUNCS(timegm) AC_SUBST(CPPFLAGS) AC_SUBST(LOCALDEFS) AC_FUNC_VPRINTF dnl function for doing each of the database backends dnl parameters: backend name, variable to set, withval dnl Berkeley DB Detection AC_ARG_WITH(bdb, [AS_HELP_STRING([--with-bdb=DIR], [use Berkeley DB (in DIR) [yes]])], with_bdb=$withval, with_bdb="yes") dnl support old-style AC_ARG_WITH(dbdir,, with_bdb=$withval) case "$with_bdb" in no) use_berkeley="no" ;; yes) use_berkeley="yes" with_bdb_lib=none with_bdb_inc=none ;; *) use_berkeley="yes" with_bdb_lib="$with_bdb/lib" with_bdb_inc="$with_bdb/include" ;; esac if test "$use_berkeley" != "no"; then CYRUS_BERKELEY_DB_CHK() if test "$dblib" = "no"; then AC_MSG_ERROR([Berkeley DB 3.x or later was not found. You may need to supply the --with-bdb-libdir or --with-bdb-incdir configure options.]) fi if test "$with_bdb_lib" != "none"; then CMU_ADD_LIBPATH($with_bdb_lib) fi BDB_INC=${BDB_INCADD} BDB_LIB=${BDB_LIBADD} AC_SUBST(BDB_INC) AC_SUBST(BDB_LIB) LIBS="${LIBS} ${BDB_LIBADD}" CPPFLAGS="${BDB_INCADD} ${CPPFLAGS}" AC_DEFINE(HAVE_BDB,[],[Build in Berkeley DB support?]) fi AM_CONDITIONAL([USE_BERKELEY], [test "$use_berkeley" != "no"]) dnl End Berkeley DB Detection dnl SQL DB Detection HAVE_SQL=0 dnl MySQL Detection dnl legacy options --with-mysql-libdir and --with-mysql-incdir CYRUS_MYSQL_OPTS if test "$with_mysql_lib" != none ; then AC_MSG_NOTICE([Legacy option --with-mysql-libdir=DIR detected.] [You may wish to change to --with-mysql which works now.]) withval="$with_mysql_lib/.." else withval="no" fi AC_MSG_CHECKING([whether to use MySQL]) AC_ARG_WITH(mysql, [AS_HELP_STRING([--with-mysql=DIR], [use MySQL (in DIR) [no]])]) with_mysql=$withval case "$with_mysql" in no) # Explicitly disable MySQL ;; yes) # Find mysql_config in $PATH mysql_config=mysql_config ;; *) # Find mysql_config in the specified directory mysql_config="$with_mysql/bin/mysql_config" if test ! -x "$mysql_config" ; then AC_MSG_ERROR([The mysql_config program was not found] [in $with_mysql/bin, disabling MySQL support]) with_mysql="no" fi ;; esac if test "$with_mysql" != "no"; then MYSQL_LIBADD=`$mysql_config --libs` MYSQL_INCADD=`$mysql_config --cflags` HAVE_SQL=1 LIBS="${LIBS} ${MYSQL_LIBADD}" CPPFLAGS="${MYSQL_INCADD} ${CPPFLAGS}" AC_DEFINE(HAVE_MYSQL,[],[Build in MySQL support?]) fi AC_MSG_RESULT($with_mysql) dnl End MySQL Detection dnl PgSQL Detection AC_ARG_WITH(pgsql, [AS_HELP_STRING([--with-pgsql=DIR], [use PostgreSQL (in DIR) [no]])], with_pgsql=$withval, with_pgsql="no") case "$with_pgsql" in no) use_pgsql="no" ;; yes) use_pgsql="yes" with_pgsql_lib=none with_pgsql_inc=none ;; *) use_pgsql="yes" with_pgsql_lib="$with_pgsql/lib" with_pgsql_inc="$with_pgsql/include" ;; esac if test "$use_pgsql" != "no"; then CYRUS_PGSQL_CHK() if test "$pgsqllib" = "no"; then AC_MSG_ERROR([PgSQL was not found. You may need to supply the --with-pgsql-libdir or --with-pgsql-incdir configure options.]) else HAVE_SQL=1 fi if test "$with_pgsql_lib" != "none"; then CMU_ADD_LIBPATH($with_pgsql_lib) fi LIBS="${LIBS} ${PGSQL_LIBADD}" CPPFLAGS="${PGSQL_INCADD} ${CPPFLAGS}" AC_DEFINE(HAVE_PGSQL,[],[Build in PgSQL support?]) fi dnl End PgSQL Detection dnl SQLite Detection AC_ARG_WITH(sqlite, [AS_HELP_STRING([--with-sqlite=DIR], [use SQLite (in DIR) [no]])], with_sqlite=$withval, with_sqlite=no) case "$with_sqlite" in no) use_sqlite="no" ;; yes) use_sqlite="yes" with_sqlite_lib=none with_sqlite_inc=none ;; *) use_sqlite="yes" with_sqlite_lib="$with_sqlite/lib" with_sqlite_inc="$with_sqlite/include" ;; esac if test "$use_sqlite" != "no"; then CYRUS_SQLITE_CHK() if test "$sqlitelib" = "no"; then AC_MSG_ERROR([Sqlite was not found. You may need to supply the --with-sqlite-libdir or --with-sqlite-incdir configure options.]) else HAVE_SQL=1 fi if test "$with_sqlite_lib" != "none"; then CMU_ADD_LIBPATH($with_sqlite_lib) fi LIBS="${LIBS} ${SQLITE_LIBADD}" CPPFLAGS="${SQLITE_INCADD} ${CPPFLAGS}" AC_DEFINE(HAVE_SQLITE,[],[Build in SQLite support?]) fi dnl End SQLite Detection AM_CONDITIONAL([USE_SQL], [test $HAVE_SQL = 1]) dnl End SQL DB Detection AC_ARG_ENABLE(sieve, [AS_HELP_STRING([--disable-sieve], [disable Sieve support])],,[enable_sieve="yes";]) AC_ARG_ENABLE(pcre, [AS_HELP_STRING([--disable-pcre], [disable PCRE library])]) if test "$enable_sieve" != "no"; then AC_DEFINE(USE_SIEVE,[],[Build in Sieve support?]) dnl Sieve configure stuff AC_PROG_YACC AM_PROG_LEX if test "$enable_pcre" != "no"; then AC_CHECK_HEADER(pcreposix.h) if test "$ac_cv_header_pcreposix_h" = "yes"; then AC_MSG_CHECKING(for utf8 enabled pcre) AC_CACHE_VAL(cyrus_cv_pcre_utf8, AC_TRY_CPP([#include #ifndef REG_UTF8 #include #endif],cyrus_cv_pcre_utf8=yes,cyrus_cv_pcre_utf8=no)) AC_MSG_RESULT($cyrus_cv_pcre_utf8) else cyrus_cv_pcre_utf8="no" fi fi if test "$cyrus_cv_pcre_utf8" = "yes"; then LIBS="$LIBS -lpcre -lpcreposix"; AC_DEFINE(ENABLE_REGEX, [], [Do we have a regex library?]) AC_DEFINE(HAVE_PCREPOSIX_H, [], [Do we have usable pcre library?]) else AC_CHECK_HEADERS(rxposix.h) if test "$ac_cv_header_rxposix_h" = "yes"; then LIBS="$LIBS -lrx" AC_DEFINE(ENABLE_REGEX, [], [Do we have a regex library?]) else AC_SEARCH_LIBS(regcomp, regex, AC_DEFINE(ENABLE_REGEX, [], [Do we have a regex library?]), []) fi fi fi AM_CONDITIONAL([SIEVE], [test "${enable_sieve}" != "no"]) dnl for et routines AC_FUNC_CHECK(strerror,AC_DEFINE(HAS_STRERROR,[],[Do we have strerror()?]), AC_DEFINE(NEED_SYS_ERRLIST,[],[Do we have a sys_errlist?])) dnl for master fd limits AC_CHECK_HEADERS(sys/resource.h) AC_CHECK_FUNCS(setrlimit) AC_CHECK_FUNCS(getrlimit) dnl for detaching terminal AC_CHECK_FUNCS(daemon setsid) dnl for turning off sockets AC_CHECK_FUNCS(shutdown) AC_EGREP_HEADER(socklen_t, sys/socket.h, AC_DEFINE(HAVE_SOCKLEN_T,[],[Do we have a socklen_t?])) AC_EGREP_HEADER(sockaddr_storage, sys/socket.h, AC_DEFINE(HAVE_STRUCT_SOCKADDR_STORAGE,[],[Do we have a sockaddr_storage?])) AC_EGREP_HEADER(rlim_t, sys/resource.h, AC_DEFINE(HAVE_RLIM_T,[],[Do we have an rlim_t?])) dnl Bunch of setproctitle stuff spt_type="" AC_CHECK_FUNC(setproctitle,spt_type=SPT_BUILTIN) if test "$spt_type" = ""; then dnl BSD/OS and FreeBSD put it in -lutil AC_CHECK_LIB(util,setproctitle,spt_type=SPT_BUILTIN LIBS="${LIBS} -lutil") fi if test "$spt_type" = ""; then AC_CHECK_HEADER(sys/pstat.h,spt_type=SPT_PSTAT) fi if test "$spt_type" = ""; then AC_CHECK_HEADER(sys/sysnews.h,spt_type=SPT_SYSMIPS) fi if test "$spt_type" = ""; then AC_MSG_CHECKING(for PS_STRINGS) AC_CACHE_VAL(cyrus_cv_sys_psstrings, AC_COMPILE_IFELSE([AC_LANG_SOURCE([ #include #include void *p = PS_STRINGS; ])],cyrus_cv_sys_psstrings=yes,cyrus_cv_sys_psstrings=no)) if test $cyrus_cv_sys_psstrings = yes; then spt_type=SPT_PSSTRINGS fi AC_MSG_RESULT($cyrus_cv_sys_psstrings) fi if test "$spt_type" = ""; then AC_MSG_CHECKING(for SCO) AC_CACHE_VAL(cyrus_cv_sys_sco, AC_TRY_CPP([ #ifndef _SCO_unix_ #include #endif],cyrus_cv_sys_sco=yes,cyrus_cv_sys_sco=no)) if test $cyrus_cv_sys_sco = yes; then spt_type=SPT_SCO fi AC_MSG_RESULT($cyrus_cv_sys_sco) fi if test "$spt_type" = ""; then AC_MSG_CHECKING(for setproctitle usability) AC_CACHE_VAL(cyrus_cv_sys_setproctitle, AC_TRY_CPP([ #if defined(DGUX) || defined(_SEQUENT_) || defined(apollo) #include #endif],cyrus_cv_sys_setproctitle=yes,cyrus_cv_sys_setproctitle=no)) if test $cyrus_cv_sys_setproctitle = no; then spt_type=SPT_NONE fi AC_MSG_RESULT($cyrus_cv_sys_setproctitle) fi if test "$spt_type" != ""; then AC_DEFINE_UNQUOTED(SPT_TYPE,$spt_type,[Do we already have setproctitle?]) fi AC_MSG_CHECKING(nonblocking method) AC_CACHE_VAL(cyrus_cv_sys_nonblock,AC_TRY_LINK([#include #include #include #ifndef FNDELAY #define FNDELAY O_NDELAY #endif],[fcntl(0, F_GETFL, 0)&FNDELAY], cyrus_cv_sys_nonblock=fcntl,cyrus_cv_sys_nonblock=ioctl)) AM_CONDITIONAL([NONBLOCK_FCNTL], [test "$cyrus_cv_sys_nonblock" = "fcntl"]) AC_MSG_RESULT($cyrus_cv_sys_nonblock) AC_MSG_CHECKING(timezone GMT offset method) AC_CACHE_VAL(cyrus_cv_struct_sys_gmtoff,AC_TRY_COMPILE([ #include ],[struct tm tm; tm.tm_gmtoff = 0; ],cyrus_cv_struct_sys_gmtoff=tm,cyrus_cv_struct_sys_gmtoff=gmtime)) AM_CONDITIONAL([GMTOFF_TM], [test "$cyrus_cv_struct_sys_gmtoff" = "tm"]) AC_MSG_RESULT($cyrus_cv_struct_sys_gmtoff) AC_MSG_CHECKING(for shared mmap) AC_CACHE_VAL(cyrus_cv_func_mmap_shared,AC_TRY_RUN([ #include #include #include #include #include int main() { char *base; int mmapflags = MAP_SHARED; int fd = open("conftestmmap", O_RDWR|O_CREAT|O_TRUNC, 0666); if (fd == -1) return 1; if (write(fd, "test", 4) != 4) return 1; fsync(fd); #ifdef MAP_FILE mmapflags |= MAP_FILE; #endif #ifdef MAP_VARIABLE mmapflags |= MAP_VARIABLE; #endif base = mmap((caddr_t)0, 100, PROT_READ, mmapflags, fd, 0L); if (base == (caddr_t)-1) return 1; if (memcmp(base, "test", 4) != 0) return 1; if (write(fd, "test", 4) != 4) return 1; fsync(fd); if (memcmp(base+4, "test", 4) != 0) return 1; return 0; } ],cyrus_cv_func_mmap_shared=yes,cyrus_cv_func_mmap_shared=no, cyrus_cv_func_mmap_shared=no)) AC_MSG_RESULT($cyrus_cv_func_mmap_shared) if test $cyrus_cv_func_mmap_shared = yes; then found_map="shared" else AC_MSG_CHECKING(for stupid shared mmap) AC_CACHE_VAL(cyrus_cv_func_mmap_stupidshared,AC_TRY_RUN([ #include #include #include #include #include int main() { char *base; int fd = open("conftestmmap", O_RDWR|O_CREAT|O_TRUNC, 0666); int mmapflags = MAP_SHARED; if (fd == -1) return 1; if (write(fd, "test", 4) != 4) return 1; fsync(fd); #ifdef MAP_FILE mmapflags |= MAP_FILE; #endif #ifdef MAP_VARIABLE mmapflags |= MAP_VARIABLE; #endif base = mmap((caddr_t)0, 4, PROT_READ, mmapflags, fd, 0L); if (base == (caddr_t)-1) return 1; if (memcmp(base, "test", 4) != 0) return 1; lseek(fd, 0L, 0); if (write(fd, "xyzz", 4) != 4) return 1; fsync(fd); if (memcmp(base, "xyzz", 4) != 0) return 1; return 0; } ],cyrus_cv_func_mmap_stupidshared=yes,cyrus_cv_func_mmap_stupidshared=no, cyrus_cv_func_mmap_stupidshared=no)) AC_MSG_RESULT($cyrus_cv_func_mmap_stupidshared) if test $cyrus_cv_func_mmap_stupidshared = yes; then found_map="stupidshared" else AC_MSG_WARN([*** This system does not have a working mmap()]) AC_MSG_WARN(*** Expect a considerable performance penalty) found_map=nommap fi fi AC_ARG_WITH(mmap, [AS_HELP_STRING([--with-mmap=TYPE], [force shared/stupidshared/nommap - JUST FOR TESTING])], WITH_MAP="$withval",WITH_MAP="$found_map") AM_CONDITIONAL([MAP_SHARED], [test "$WITH_MAP" = "shared"]) AM_CONDITIONAL([MAP_STUPIDSHARED], [test "$WITH_MAP" = "stupidshared"]) AC_ARG_WITH(lock, [AS_HELP_STRING([--with-lock=METHOD], [force use of METHOD for locking (flock or fcntl)])], WITH_LOCK="$withval", [ AC_CHECK_FUNC(fcntl,WITH_LOCK="fcntl",[ AC_CHECK_FUNC(flock,WITH_LOCK="flock",[ AC_MSG_ERROR(unable to detect locking method) ]) ]) ]) AM_CONDITIONAL([LOCK_FCNTL], [test $WITH_LOCK = "fcntl"]) dnl check for fdatasync (used by cyrusdb_skiplist) LIB_RT="" AC_CHECK_FUNC(fdatasync, AC_DEFINE(HAVE_FDATASYNC,[],[Do we have fdatasync()?]), [ AC_CHECK_LIB(rt, fdatasync, [ LIB_RT="-lrt" AC_DEFINE(HAVE_FDATASYNC,[],[Do we have fdatasync()?]) ]) ]) dnl check for libuuid (used when generating mailbox uniqueids) LIB_UUID= AC_CHECK_LIB(uuid, uuid_generate,[ LIB_UUID="-luuid" AC_DEFINE(HAVE_LIBUUID,[],[Do we have the uuid library]) ]) dnl for AFS. cant_find_sigvec=no AC_CACHE_VAL(cyrus_cv_sigveclib,[ dnl bsd classic flavor AC_CHECK_FUNC(sigvec, [ cyrus_cv_sigveclib="" ], [ dnl hp flavor AC_CHECK_LIB(BSD, sigvec, cyrus_cv_sigveclib="-lBSD", [ dnl not hp flavor SAVE_LDFLAGS="$LDFLAGS" dnl solaris flavor LDFLAGS="-L/usr/ucblib -R/usr/ucblib $LDFLAGS" AC_CHECK_LIB(ucb, sigvec, [ dnl more solaris flavor cyrus_cv_sigveclib="-lc -L/usr/ucblib -R/usr/ucblib -lucb"], [ cant_find_sigvec=yes ]) LDFLAGS="$SAVE_LDFLAGS"]) ]) ]) AC_SUBST(cyrus_cv_sigveclib) # ok, we still look for this stuff because of checking groups, but # all authentication goes through SASL AC_ARG_ENABLE([afs], [AS_HELP_STRING([--enable-afs], [Enable AFS with ptloader])]) AC_ARG_WITH(afs-libdir, [AS_HELP_STRING([--with-afs-libdir=DIR], [use AFS libraries from DIR [/usr/lib]])], afs_libdir="${withval}", afs_libdir="/usr/lib") AC_ARG_WITH(afs-incdir, [AS_HELP_STRING([--with-afs-incdir=DIR], [use AFS headers from DIR [/usr/include]])], afs_incdir="${withval}", afs_incdir="/usr/include") AC_ARG_WITH(ldap, [AS_HELP_STRING([--with-ldap=DIR], [use LDAP (in DIR) (experimental) [/usr/local]])], with_ldap="${withval}", with_ldap="no") dnl select mode of afspts AC_ARG_ENABLE(krb5afspts, [AS_HELP_STRING([--enable-krb5afspts], [compile afskrb PTS module with krb5 support])]) if test "x$enable_afs" = "xyes"; then # krb5afspts is only valid if AFS is enabled, so check inside here. AS_IF([test "x$enable_krb5afspts" = "xyes"], [SASL_SET_GSSAPI_LIBS AC_DEFINE(AFSPTS_USE_KRB5,[],[Should the AFS PTS plugin use krb5?]) ]) CFLAGS="${CFLAGS} -I${with_afs_incdir}" AFS_LIBS="${with_afs_libdir}/afs/libkauth.a ${with_afs_libdir}/afs/libprot.a ${with_afs_libdir}/afs/libauth.a ${with_afs_libdir}/afs/libsys.a ${with_afs_libdir}/librxkad.a ${with_afs_libdir}/librx.a ${with_afs_libdir}/afs/libsys.a ${with_afs_libdir}/libubik.a ${with_afs_libdir}/afs/liblwp.a ${with_afs_libdir}/afs/util.a ${with_afs_libdir}/afs/libafscom_err.a -lresolv" if test -f ${with_afs_libdir}/afs/libaudit.a; then AFS_LIBS="$AFS_LIBS ${with_afs_libdir}/afs/libaudit.a" fi if test -f /usr/ucblib/libucb.a; then CMU_ADD_LIBPATH_TO(/usr/ucblib, AFS_LDFLAGS) AFS_LIBS="$AFS_LIBS -lc -lucb" fi if test -f ${with_afs_libdir}/afs/libdes.a; then AFS_LIBS="$AFS_LIBS ${with_afs_libdir}/afs/libdes.a" else AFS_LIBS="$AFS_LIBS -ldes" fi AC_CACHE_VAL(cyrus_cv_afs_sigvec,[ SAVE_LIBS="$LIBS" LIBS="${with_afs_libdir}/liblwp.a" AC_MSG_CHECKING(if AFS libraries need sigvec) dnl Does AFS need sigvec? We have to link against lwp and see dnl if IOMGR_Initialize wants it AC_TRY_LINK([IOMGR_Initialize();], [IOMGR_Initialize()], [ dnl it linked; don't need it AC_MSG_RESULT(no) cyrus_cv_afs_sigvec="no" ], [ dnl didn't link; pick up sigvec AC_MSG_RESULT(yes) cyrus_cv_afs_sigvec="yes" ]) ]) if test "$cyrus_cv_afs_sigvec" = yes; then if test "$cant_find_sigvec" = yes; then AC_MSG_WARN([Can not find a sigvec for AFS libraries which seem to need one.]) else AFS_LIBS="${AFS_LIBS} $cyrus_cv_sigveclib" AC_DEFINE(HAVE_AFSKRB,[],[Should we build afskrb pts module?]) fi else AFS_LIBS="${AFS_LIBS}" AC_DEFINE(HAVE_AFSKRB,[],[Should we build afskrb pts module?]) fi LIBS="$SAVE_LIBS" AC_SUBST(AFS_LDFLAGS) AC_SUBST(AFS_LIBS) fi AM_CONDITIONAL([USE_AFSKRB], [grep HAVE_AFSKRB confdefs.h >/dev/null]) have_ldap=no LDAP_CPPFLAGS= LDAP_LDFLAGS= LDAP_LIBS= case "x$with_ldap" in xno) # default args or --without-ldap # do not try to enable ;; xyes) # --with-ldap # try to enable, search in default system directories ldap_cppflags= ldap_ldflags= ;; *) # --with-ldap=DIR # try to enable, search in given install directory if test "x$with_ldap" != "x" -a -d "$with_ldap"; then ldap_cppflags="-I${with_ldap}/include" ldap_ldflags="-L${with_ldap}/lib" with_ldap=yes else AC_WARN([Disabling LDAP - no include files found]) with_ldap=no fi esac if test $with_ldap = yes; then save_CPPFLAGS="$CPPFLAGS" save_LDFLAGS="$LDFLAGS" CPPFLAGS="$CPPFLAGS $ldap_cppflags" LDFLAGS="$LDFLAGS $ldap_ldflags" AC_CHECK_LIB(ldap, ldap_initialize, [ AC_DEFINE(HAVE_LDAP,[],[Should we build the LDAP pts module?]) LDAP_CPPFLAGS="$ldap_cppflags" LDAP_LDFLAGS="$ldap_ldflags" LDAP_LIBS="-lldap -llber" have_ldap=yes ],,-llber) CPPFLAGS="$save_CPPFLAGS" LDFLAGS="$save_LDFLAGS" fi AC_SUBST(LDAP_CPPFLAGS) AC_SUBST(LDAP_LDFLAGS) AC_SUBST(LDAP_LIBS) AM_CONDITIONAL([HAVE_LDAP], [test "$have_ldap" = "yes"]) AM_CONDITIONAL([PTCLIENT], [test "x$enable_afs" = "xyes" -o "$have_ldap" = "yes"]) AC_ARG_WITH( clamav, [ --with-clamav=DIR use ClamAV from PATH (yes)], with_clamav=$withval, with_clamav=yes ) if test "$with_clamav" != no; then if test -d $with_clamav; then save_CPPFLAGS="$CPPFLAGS" save_LDFLAGS="$LDFLAGS" save_LIBS="$LIBS" CPPFLAGS="${CPPFLAGS} -I${with_clamav}/include" LDFLAGS="$LDFLAGS -L${with_clamav}/$CMU_LIB_SUBDIR" AC_CHECK_LIB( wrap, request_init, [AC_CHECK_HEADER(clamav.h,, with_clamav=no)], with_clamav=no ) CPPFLAGS="$save_CPPFLAGS" LDFLAGS="$save_LDFLAGS" LIBS="$save_LIBS" fi fi AC_MSG_CHECKING(ClamAV support) AC_MSG_RESULT($with_clamav) LIB_CLAMAV="" if test "$with_clamav" != "no"; then AC_DEFINE(HAVE_CLAMAV,[],[Do we have ClamAV?]) if test -d "$with_clamav"; then CPPFLAGS="${CPPFLAGS} -I${with_clamav}/include" LIB_CLAMAV="-L${with_clamav}/$CMU_LIB_SUBDIR -lclamav" else LIB_CLAMAV="-lclamav" fi fi AC_SUBST(LIB_CLAMAV) AM_CONDITIONAL([HAVE_CLAMAV], [test "$have_clamav" = "yes"]) AC_ARG_ENABLE(server, [AS_HELP_STRING([--disable-server], [disable compiling servers])]) AM_CONDITIONAL([SERVER], [test "$enable_server" != "no"]) # We always output a server makefile (just because we can) dnl this is the new simple check for kerberos; since the person had to dnl compile SASL, we might as well use the same checks. AC_ARG_WITH(krb, [AS_HELP_STRING([--with-krb=DIR], [use Kerberos from DIR])], with_krb="$withval", with_krb="no") AC_ARG_WITH(krbimpl, [AS_HELP_STRING([--with-krbimpl=kth|mit], [assume Kerberos 4 from KTH or MIT])], with_krbimpl="$withval", with_krbimpl="kth") AC_ARG_ENABLE(statickrb, [AS_HELP_STRING([--enable-statickrb], [link Kerberos statically])], with_statickrb="yes", with_statickrb="no") dnl In order to compile kerberos4, we need libkrb and libdes. dnl we might need -lresolv for kerberos AC_CHECK_LIB(resolv,res_search) if test "$with_statickrb" = "yes" -a ! -d "$with_krb"; then AC_MSG_ERROR([--enable-statickrb specified but --with-krb did not specify a valid directory]) fi if test "$with_krb" != "no"; then dnl Do we need DES for kerberos? AC_ARG_WITH(krbdes, [AS_HELP_STRING([--with-krbdes], [use Kerberos DES implementation [yes]])], with_krbdes="$withval", with_krbdes="yes") if test "$with_krbdes" = "yes"; then AC_CHECK_LIB(des,des_ecb_encrypt, if test "$with_statickrb" = "yes"; then KRB_LIBS="$with_krb/lib/libdes.a" else KRB_LIBS="-ldes" fi, AC_MSG_ERROR([The Kerberos DES library is required for Kerberos support. You might want --with-auth=unix.])) fi fi dnl if we were ambitious, we'd look more aggressively for the dnl krb4 install if test -d ${with_krb}; then AC_CACHE_CHECK(for Kerberos includes, cyrus_cv_krbinclude, [ for krbhloc in include/kerberosIV include do if test -f ${with_krb}/${krbhloc}/krb.h ; then cyrus_cv_krbinclude=${with_krb}/${krbhloc} break fi done ]) if test -n "${cyrus_cv_krbinclude}"; then CPPFLAGS="$CPPFLAGS -I${cyrus_cv_krbinclude}" fi CMU_ADD_LIBPATH(${with_krb}/lib) fi if test "$with_krbimpl" != "kth"; then KRBLIB="krb4" else KRBLIB="krb" fi if test "$with_des" != no; then AC_CHECK_HEADER(krb.h, AC_CHECK_LIB(${KRBLIB}, krb_mk_priv, if test "$with_statickrb" = "yes"; then KRB_LIBS="$KRB_LIBS $with_krb/lib/lib${KRBLIB}.a" else KRB_LIBS="$KRB_LIBS -l${KRBLIB}" fi, AC_WARN(No Kerberos V4 found); krb4=no, $KRB_LIBS), krb4=no) else AC_WARN(No DES library found for Kerberos V4 support) krb4=no fi if test "${krb4}" != no; then AC_DEFINE(HAVE_KRB,[],[Support for Kerberos?]) fi LIBS="$KRB_LIBS $LIBS" SASL_SET_GSSAPI_LIBS dnl dnl Test for OpenSSL dnl AC_ARG_WITH(openssl, [AS_HELP_STRING([--with-openssl=DIR], [use OpenSSL from DIR])], with_ssl="${withval}") SSL_CPPFLAGS= SSL_LIBS= case "x$with_ssl" in xno) # --without-openssl # do not try to enable ;; x|xyes) # default args or --with-openssl # # Try pkg-config - OpenSSL >= 0.9.6 has openssl.pc PKG_CHECK_MODULES(OPENSSL, openssl, [with_ssl=yes]) ssl_cppflags="$OPENSSL_CFLAGS" ssl_ldflags="$OPENSSL_LIBS" # # If pkg-config doesn't work, search in default system directories ;; *) # --with-openssl=DIR # try to enable, search in given install directory if test -d "$with_ssl"; then ssl_cppflags="-I${with_ssl}/include" ssl_ldflags= if test -d "${with_ssl}/lib64"; then CMU_ADD_LIBPATH_TO(${with_ssl}/lib64, ssl_ldflags) else CMU_ADD_LIBPATH_TO(${with_ssl}/lib, ssl_ldflags) fi with_ssl=yes else AC_WARN([Disabling OpenSSL - no include files found]) with_ssl=no fi esac if test "$with_ssl" != "no"; then save_CPPFLAGS="$CPPFLAGS" save_LDFLAGS="$LDFLAGS" CPPFLAGS="$CPPFLAGS $ssl_cppflags" LDFLAGS="$LDFLAGS $ssl_ldflags" AC_CHECK_HEADER(openssl/evp.h, [ with_ssl=yes ],[ with_ssl=no ]) dnl if openssl has been compiled with the rsaref2 libraries, dnl we need to include the rsaref libraries in the crypto check ssl_libs= AC_CHECK_LIB(rsaref, RSAPublicEncrypt,[ ssl_libs="-lRSAglue -lrsaref" ],[ # whatever, we do not care : ]) AC_CHECK_LIB(crypto, BIO_accept,[ ssl_libs="-lcrypto $ssl_libs" ],[ with_ssl=no ], $ssl_libs) AC_CHECK_LIB(ssl, SSL_CTX_new, [ ssl_libs="-lssl $ssl_libs" ],[ with_ssl=no ], $ssl_libs) if test "$with_ssl" = "no"; then AC_WARN([Disabling SSL - no library files found]) fi CPPFLAGS="$save_CPPFLAGS" LDFLAGS="$save_LDFLAGS" fi AC_MSG_CHECKING(for ssl) AC_MSG_RESULT($with_ssl) if test "$with_ssl" != "no"; then SSL_CPPFLAGS="$ssl_cppflags" SSL_LIBS="$ssl_ldflags $ssl_libs" AC_DEFINE(HAVE_SSL,[],[Build with SSL support?]) if test "${krb4}" != no; then AC_DEFINE(OPENSSL_ENABLE_OLD_DES_SUPPORT,[],[Configure OpenSSL to provide legacy des apis]) AC_DEFINE(OPENSSL_DES_LIBDES_COMPATIBILITY,[],[Configure OpenSSL to provide krb4-compatible legacy des apis]) fi fi AM_CONDITIONAL([HAVE_SSL], [test "$with_ssl" != "no"]) AC_SUBST(SSL_CPPFLAGS) AC_SUBST(SSL_LIBS) dnl dnl Allow for setting EGD socket file on systems without /dev/*random. dnl AC_ARG_WITH(egd-socket, [AC_HELP_STRING([--with-egd-socket=FILE], [Entropy Gathering Daemon socket pathname for systems without /dev/urandom])], [ EGD_SOCKET="$withval" ] ) if test -n "$EGD_SOCKET" ; then AC_DEFINE_UNQUOTED(EGD_SOCKET, "$EGD_SOCKET", [Alternative to /dev/urandom?]) fi dnl dnl Test for zlib dnl CMU_HAVE_ZLIB AC_MSG_CHECKING(for zlib) AC_MSG_RESULT($with_zlib) AC_SUBST(ZLIB) dnl dnl Test for Zephyr dnl AC_ARG_WITH(zephyr, [AS_HELP_STRING([--with-zephyr=DIR], [enable Zephyr notification (installed on DIR)])], with_zephyr="${withval}") if test -z "$with_zephyr"; then if test -f /usr/local/lib/libzephyr.a; then with_zephyr="/usr/local" elif test -f /usr/lib/libzephyr.a; then with_zephyr="/usr" fi fi ZEPHYR_LIBS="" case "$with_zephyr" in no) true;; ""|yes) AC_CHECK_LIB(zephyr,ZInitialize,ZEPHYR_LIBS="-lzephyr", with_zephyr="no",);; *) ZEPHYR_LIBS="-lzephyr";; esac AC_SUBST(ZEPHYR_LIBS) if test "$with_zephyr" != "no"; then AC_DEFINE(HAVE_ZEPHYR,[],[Build with Zephyr support?]) fi AM_CONDITIONAL([ZEPHYR], [test "$with_zephyr" != "no"]) dnl dnl Test for libcap (POSIX.1e - security API) on Linux systems dnl AC_ARG_WITH([libcap], AS_HELP_STRING([--with-libcap], [Enable libcap system capabilities handling (Linux systems only)]), with_libcap="${withval}") have_libcap=no case $host_os in linux*) if test "x$with_libcap" = "xyes"; then AC_CHECK_LIB([cap], [cap_get_proc], have_libcap=yes, have_libcap=no) AC_CHECK_HEADERS([sys/capability.h sys/prctl.h], , have_libcap=no) if test "$have_libcap" = "yes"; then AC_DEFINE(HAVE_LIBCAP, [], [Do we have libcap system capabilities handling (Linux systems only)?]) LIBS="$LIBS -lcap" fi fi ;; *) ;; esac AC_MSG_CHECKING(for libcap) AC_MSG_RESULT($have_libcap) dnl dnl Test for mailbox event notification dnl enable requires the installation of jansson library dnl AC_ARG_ENABLE(event-notification, [AS_HELP_STRING([--disable-event-notification], [disable compiling of mailbox event notification (that needs jansson library)])],, [enable_event_notification="yes";]) if test "$enable_event_notification" != "no"; then PKG_CHECK_MODULES([JANSSON], [jansson >= 2.0], [check_jansson=true] dnl call AC_SUBST macro to support pkg-config version older that 0.24 without any bad consequence for recent version [AC_SUBST([JANSSON_LIBS])] [AC_SUBST([JANSSON_CFLAGS])] [AC_DEFINE(ENABLE_MBOXEVENT,[],[Build with support of mailbox event notification])], [check_jansson=false] [AC_MSG_WARN([jansson 2.0 or later was not found, but is required to enable mailbox event notification])] enable_event_notification="no") fi AM_CONDITIONAL(JANSSON, test x$check_jansson = xtrue) dnl dnl Set pidfile location dnl AC_ARG_WITH(pidfile, [AS_HELP_STRING([--with-pidfile=DIR], [pidfile in DIR [/var/run/cyrus-master.pid]])], [MASTERPIDFILE="$withval"], [MASTERPIDFILE="/var/run/cyrus-master.pid"]) MASTERPIDFILE="\"$MASTERPIDFILE\"" AC_DEFINE_UNQUOTED(MASTER_PIDFILE, $MASTERPIDFILE,[Name of the pidfile for master]) dnl dnl see if we're compiling with autocreate support dnl AC_ARG_ENABLE(autocreate, [AS_HELP_STRING([--enable-autocreate], [enable autocreate support])],,[enable_autocreate="no";]) AM_CONDITIONAL([AUTOCREATE], [test "$enable_autocreate" != "no"]) if test "x$enable_autocreate" = "xyes"; then AC_DEFINE(USE_AUTOCREATE,[],[Build with autocreate functionality]) fi dnl dnl see if we're compiling with IMAP idled support dnl AC_ARG_ENABLE(idled, [AS_HELP_STRING([--enable-idled], [enable IMAP idled support])],,[enable_idled="no";]) AM_CONDITIONAL([IDLED], [test "$enable_idled" != "no"]) dnl dnl see if we're compiling with NNTP support dnl AC_ARG_ENABLE(nntp, [AS_HELP_STRING([--enable-nntp], [enable NNTP support])],,[enable_nntp="no";]) AM_CONDITIONAL([NNTPD], [test "$enable_nntp" != "no"]) dnl dnl see if we're compiling the Murder support programs dnl AC_ARG_ENABLE(murder, [AS_HELP_STRING([--enable-murder], [enable IMAP Murder support])],, [enable_murder="no";]) AM_CONDITIONAL([MURDER], [test "$enable_murder" != "no"]) if test "$enable_murder" != no; then # for master/slave auto-selection AC_CHECK_HEADERS(sys/sockio.h) fi dnl dnl see if we're compiling with HTTP support dnl ENABLE_HTTP=no AC_ARG_ENABLE(http, [AS_HELP_STRING([--enable-http], [enable HTTP support])],, [enable_http="no";]) AM_CONDITIONAL([HTTPD], [test "$enable_http" != "no"]) HTTP_CPPFLAGS= HTTP_LIBS= if test "$enable_http" != no; then dnl dnl make sure all the modules we need are present dnl ENABLE_RSS=yes ENABLE_DAV=yes PKG_CHECK_MODULES([XML2], [libxml-2.0],,AC_MSG_ERROR([Need libxml-2.0 for http])) PKG_CHECK_MODULES([ICAL], [libical],,AC_MSG_ERROR([Need libical for http])) PKG_CHECK_MODULES([SQLITE3], [sqlite3],,AC_MSG_ERROR([Need sqlite3 for http])) PKG_CHECK_MODULES([JSON], [jansson],,AC_MSG_ERROR([Need jansson for http])) HTTP_LIBS="${XML2_LIBS} ${ICAL_LIBS} ${SQLITE3_LIBS} ${JSON_LIBS}" HTTP_CPPFLAGS="${JSON_CFLAGS} ${SQLITE3_CFLAGS} ${ICAL_CFLAGS} ${XML2_CFLAGS}" saved_LIBS=${LIBS} saved_CPPFLAGS="${CPPFLAGS}" LIBS="${LIBS} ${HTTP_LIBS}" CPPFLAGS="${CPPFLAGS} ${HTTP_CPPFLAGS}" AC_DEFINE(HAVE_XML2,[],[Build in libxml support?]) AC_DEFINE(HAVE_ICAL,[],[Build in ical support?]) AC_DEFINE(HAVE_SQLITE3,[],[Build in SQLite support?]) AC_DEFINE(WITH_DAV,[],[Build DAV support into httpd?]) AC_DEFINE(WITH_JSON,[],[Build jCal/jCard/TZdist support into httpd?]) AC_CHECK_LIB(ical, icaltimezone_set_builtin_tzdata, AC_DEFINE(HAVE_TZ_BY_REF,[], [Build TZ by ref support into httpd?])) AC_EGREP_HEADER(ICAL_TZUNTIL_PROPERTY, [libical/ical.h], AC_DEFINE(HAVE_TZDIST_PROPS,[], [Do we have built-in support for TZdist props?])) CYRUS_OPENDKIM_CHK() if test "$opendkimlib" = "yes"; then AC_SUBST(DKIM_CFLAGS) AC_SUBST(DKIM_LIBS) AC_DEFINE(WITH_DKIM,[],[Build DKIM support into iSchedule?]) fi AC_EGREP_HEADER(ICAL_IANA_PARAMETER, [libical/ical.h], AC_DEFINE(HAVE_IANA_PARAMS,[], [Do we have support for IANA params?]), AC_MSG_WARN([Your version of libical can not support scheduling or managed attachments. Consider upgrading to libical >= 0.48])) AC_EGREP_HEADER(ICAL_SCHEDULESTATUS_PARAMETER, [libical/ical.h], AC_DEFINE(HAVE_SCHEDULING_PARAMS,[], [Do we have built-in support for scheduling params?])) AC_EGREP_HEADER(ICAL_VAVAILABILITY_COMPONENT, [libical/ical.h], AC_DEFINE(HAVE_VAVAILABILITY,[], [Build VAVAILABILITY support into httpd?])) AC_EGREP_HEADER(ICAL_VPOLL_COMPONENT, [libical/ical.h], AC_DEFINE(HAVE_VPOLL,[], [Build VPOLL support into httpd?])) ENABLE_RSCALE=yes PKG_CHECK_MODULES([ICU], [icu-i18n],, ENABLE_RSCALE=no) if test "$ENABLE_RSCALE" != no; then AC_SUBST(ICU_CFLAGS) AC_SUBST(ICU_LIBS) AC_CHECK_LIB(ical, icalrecurrencetype_rscale_is_supported, AC_DEFINE(HAVE_RSCALE,[], [Build RSCALE support into httpd?])) fi LIBS="${saved_LIBS}" CPPFLAGS="${saved_CPPFLAGS}" fi AC_SUBST(HTTP_CPPFLAGS) AC_SUBST(HTTP_LIBS) dnl dnl see if we're compiling replication support programs dnl AC_ARG_ENABLE(replication, [AS_HELP_STRING([--enable-replication], [enable replication support (experimental)])],,[enable_replication="no";]) AM_CONDITIONAL([REPLICATION], [test "$enable_replication" != no]) dnl dnl Try and find a system version of com_err. dnl If we see something that looks a little wacky, ignore it (there are many dnl deficient installs of com_err, unfortunately, which leave out compile_et) dnl There is also a broken re-implementation of compile_et, apparently derived dnl from the Kerberos project, being shipped in /usr/bin on MacOS X, see Bug #3711. dnl AC_ARG_WITH(com_err, [AS_HELP_STRING([--with-com_err=DIR], [use com_err from path -- includes in DIR/include, libs in DIR/lib, and compile_et in DIR/bin])]) if test -z "$with_com_err"; then # no value supplied AC_CHECK_LIB(com_err, com_err, [ # com_err is already in library path # guess we're okay # can use system com_err with_com_err="" AC_CHECK_HEADER(et/com_err.h, [AC_DEFINE(HAVE_ET_COM_ERR_H,[],[We need et/com_err.h])], [AC_CHECK_HEADER(com_err.h,[],[AC_MSG_ERROR([cannot locate com_err.h])])]) AC_PATH_PROG(COMPILE_ET, compile_et, [no compile et]) ], [ if test -f /usr/local/include/com_err.h -o -f /usr/local/include/et/com_err.h; then with_com_err="/usr/local" AC_PATH_PROG(COMPILE_ET, /usr/local/bin/compile_et, [no compile et]) elif test -f /usr/include/com_err.h -o -f /usr/include/et/com_err.h; then with_com_err="/usr" AC_PATH_PROG(COMPILE_ET, /usr/bin/compile_et, [no compile et]) else # use ours with_com_err=yes fi ]) if test "${with_com_err}" = "no"; then AC_MSG_WARN([com_err is required; included version will be used.]) with_com_err="yes" fi if test "${COMPILE_ET}" = "no compile et" -o "${COMPILE_ET}" = ""; then AC_MSG_WARN([Parts of com_err distribuion were found, but not compile_et.]) AC_MSG_WARN([Will build com_err from included sources.]) with_com_err="yes" # build it ourselves fi fi dnl Set up $COMPILE_ET first, we need to test it case "$with_com_err" in # built-in et yes) # use the com_err we're gonna build COMPILE_ET="\${abs_top_builddir}/com_err/et/compile_et" ;; "") # no problem, we already have it in the paths # we do nothing to pick it up ;; *) # use whatever they told us, or whatever we found COMPILE_ET="${with_com_err}/bin/compile_et" ;; esac if test "$with_com_err" != yes ; then dnl Test that the specified compile_et produces correct output dnl See bug #3711 for why this is necessary TEST1=".cyrus-configure-test-$$" /bin/rm -f $TEST1.et $TEST1.h $TEST1.c echo "error_table imap" >> $TEST1.et echo "ec IMAP_TESTING," >> $TEST1.et echo " \"Testing\"" >> $TEST1.et echo "end" >> $TEST1.et "${COMPILE_ET}" $TEST1.et > /dev/null compile_et_ok=no if test -f $TEST1.h ; then if test `awk '/IMAP_TESTING/{print $3}' $TEST1.h 2>/dev/null` = "(-1904809472L)" ; then compile_et_ok=yes fi dnl Broken compile_et produces (2390157824L) fi /bin/rm -f $TEST1.et $TEST1.h $TEST1.c if test "$compile_et_ok" = no ; then # revert to the built-in compile_et AC_MSG_WARN([It seems $COMPILE_ET is buggy, building our own]) with_com_err=yes COMPILE_ET="\${abs_top_builddir}/com_err/et/compile_et" fi fi case "$with_com_err" in # built-in et yes) # use the com_err we're gonna build COM_ERR_LIBS="com_err/et/libcyrus_com_err.la" COM_ERR_CPPFLAGS="-I\${top_srcdir}/com_err/et" ;; "") # no problem, we already have it in the paths # we do nothing to pick it up COM_ERR_LIBS="-lcom_err" # hope it's not shared # we already set COMPILE_ET, or we didn't get here COM_ERR_CPPFLAGS="" ;; *) # use whatever they told us, or whatever we found COM_ERR_LIBS="${with_com_err}/lib/libcom_err.a" COM_ERR_CPPFLAGS="-I${with_com_err}/include" # Ever get the feeling people hide this stuff on purpose? if test -d "${with_com_err}/include/et" ; then COM_ERR_CPPFLAGS="-I${with_com_err}/include/et" fi esac AM_CONDITIONAL([COM_ERR], [test "$with_com_err" = "yes"]) if test "$with_com_err" = "yes"; then PKG_CONFIG_COM_ERR_LIB="-lcyrus_com_err" fi AC_SUBST(PKG_CONFIG_COM_ERR_LIB) AC_SUBST(COMPILE_ET) AC_SUBST(COM_ERR_LIBS) AC_SUBST(COM_ERR_CPPFLAGS) if test "$USE_MAINTAINER_MODE" = "yes" ; then AC_CHECK_PROG(GPERF,gperf,yes,no) if test "$GPERF" != "yes"; then AC_MSG_ERROR([gperf is not installed on this system, but is required for maintainer mode build rules]) fi fi AC_MSG_CHECKING(for modern syslog) AC_CACHE_VAL(cyrus_cv_lib_syslog, AC_TRY_CPP([#include #ifndef LOG_LOCAL6 #include #endif],cyrus_cv_lib_syslog=yes,cyrus_cv_lib_syslog=no)) AC_MSG_RESULT($cyrus_cv_lib_syslog) AC_MSG_CHECKING(which syslog facility to use) SYSLOG_FACILITY=LOG_LOCAL6 AC_ARG_WITH(syslogfacility, [AS_HELP_STRING([--with-syslogfacility=FACILITY], [set the syslog facility to use (default LOCAL6)])], [ if test "$withval" != "yes" -a "$withval" != "no" ; then SYSLOG_FACILITY=LOG_$withval fi; ]) AC_DEFINE_UNQUOTED(SYSLOG_FACILITY, $SYSLOG_FACILITY, [Syslog facility to use.]) AC_MSG_RESULT($SYSLOG_FACILITY) dnl Have to check getdtabalesize after adding ossup, as some ossups define it AC_REPLACE_FUNCS(getdtablesize) AC_ARG_ENABLE(cmulocal, [AS_HELP_STRING([--enable-cmulocal], [enable CMU-specific local support])]) AM_CONDITIONAL([CMULOCAL], [test "$enable_cmulocal" = "yes"]) AC_MSG_CHECKING(to use old sieve service name) AC_ARG_ENABLE(oldsievename, [AS_HELP_STRING([--enable-oldsievename], [enable the use of 'imap' as the sieve service name])], if test "$enableval" = yes; then AC_MSG_RESULT(yes) AC_DEFINE(OLD_SIEVE_SERVICE_NAME,[],[Use "imap" as sieve service name?]) else AC_MSG_RESULT(no) fi, AC_MSG_RESULT(no)) AC_ARG_ENABLE(netscapehack, [AS_HELP_STRING([--enable-netscapehack], [enable Netscape hack for the menu option in Communicator to Administrate Mail])], if test "$enableval" = yes; then AC_DEFINE(ENABLE_X_NETSCAPE_HACK,[],[Enable Netscape Menu Option Hack?]) fi) CMU_SASL2_REQUIRE_VER(2,1,7) CMU_SASL2_CHECKAPOP_REQUIRED AC_ARG_WITH(perl, [AS_HELP_STRING([--with-perl=PERL], [use PERL for perl])], with_perl="$withval", with_perl="perl") if test "${with_perl}" = yes; then with_perl="perl" fi if test "${with_perl}" != no; then if test ${using_static_sasl} = "staticonly"; then AC_MSG_WARN([Cannot compile perl utilities using static libsasl]) with_perl="no" else AC_CHECK_PROGS(PERL, ${with_perl} perl, with_perl=notfound) fi fi AM_CONDITIONAL([PERL], [test "$with_perl" != "no" -a "$with_perl" != "notfound"]) srctoolsdir=`cd ${srcdir};pwd`/tools if test "$with_perl" = "notfound"; then AC_MSG_WARN(Perl not found: Administrative tools will not be available) elif test "${with_perl}" != "no"; then dnl compile perl stuff and perl/cyradm PERL="${with_perl}" dnl add perl cccdlflags when building libraries -- this ensures that the dnl libraries will be compiled as PIC if perl requires PIC objects dnl -- this is needed on NetBSD and Linux, but seems to cause problems on atleast Solaris -- case "${target_os}" in linux*|netbsd*|freebsd*|dragonfly*) AC_MSG_CHECKING(for perl cccdlflags needed on "${target_os}") eval `${PERL} -V:cccdlflags` PERL_CCCDLFLAGS="$cccdlflags" AC_SUBST(PERL_CCCDLFLAGS) AC_MSG_RESULT($PERL_CCCDLFLAGS) ;; *) AC_MSG_WARN(skipping check for perl cccdlflags on "${target_os}") esac PERL_PREINSTALL="${PERL} ${srctoolsdir}/fixsearchpath.pl ${cyrus_prefix} ${bindir}" AC_SUBST(PERL_PREINSTALL) fi CMU_LIBWRAP CMU_UCDSNMP # Figure out what directories we're linking against. # Lots of fun for the whole family. # This probably chokes on anything with spaces in it. # All we want is the list of -L directories, and -L may or may not be # followed by a space. isdir=no libpath="" #echo "debug ldflags: << ${ldflags} >>" #echo "debug default_ldflags: << ${default_ldflags} >>" for flag in ${ldflags} ${default_ldflags}; do case $flag in -L) # it's a split -L option, we'll mark the next option as a dir. isdir=yes ;; -L*) # attached -L option: split off the directory larg=`echo $flag | sed -e 's:-L\(..*\):\1:'` libpath="${libpath} ${larg}" ;; *) if test $isdir = yes ; then libpath="${libpath} ${flag}" isdir=no fi esac done AC_SUBST(LIB_SASL) AC_SUBST(LIB_RT) AC_SUBST(LIB_UUID) AC_SUBST(PERL) dnl dnl Enable/disable unit tests. These are disabled by default, as dnl they require an additional library (the CUnit library). dnl AC_ARG_ENABLE(unit-tests, [AS_HELP_STRING([--enable-unit-tests], [enable CUnit-based unit regression tests])]) dnl Unit tests need the CUnit library, so check if we dnl have both the header and the library. if test "$enable_unit_tests" = "yes" ; then AC_CHECK_LIB(cunit,CU_initialize_registry,found_lib=yes,found_lib=no) AC_CHECK_HEADER([CUnit/CUnit.h],found_hdr=yes,found_hdr=no) if test "$found_lib$found_hdr" != "yesyes" ; then AC_MSG_NOTICE([Disabling unit tests because the required CUnit library is not installed]) enable_unit_tests=no fi AC_CHECK_HEADER([CUnit/Basic.h], AC_CHECK_TYPE([CU_SetUpFunc],AC_DEFINE(HAVE_CU_SETUPFUNC,[],[Do we have CU_SetUpFunc?]),, [#include ]) ,) fi if test "$enable_unit_tests" = "yes" ; then dnl Valgrind is an amazingly useful tool for running tests. It doesn't dnl need the program under test to be modified in any way, but it we can dnl optionally use some magic in it's header file to compensate for some dnl of the shortcomings of a C development environment by giving error dnl messages with backtraces. This is so enormously useful for the unit dnl tests that want to enable it if possible, but we can struggle on dnl without it. Besides, on many platforms the header file is in a dnl different package to the main valgrind binary, and so might not be dnl installed. AC_CHECK_HEADERS([valgrind/valgrind.h]) USE_MAINTAINER_MODE=yes fi AM_CONDITIONAL([CUNIT], [test "$enable_unit_tests" = "yes"]) AH_TOP([ /* * Copyright (c) 1994-2012 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #ifndef _CYRUS_IMAPD_CONFIG_H_ #define _CYRUS_IMAPD_CONFIG_H_ ]) AH_BOTTOM([ /* time.h */ #if TIME_WITH_SYS_TIME # include # include #else # if HAVE_SYS_TIME_H # include # else # include # endif #endif /* com_err.h, as needed */ #ifndef IN_COM_ERR #ifdef HAVE_ET_COM_ERR_H #include #else #include #endif /* HAVE_ET_COM_ERR_H */ #endif /* IN_COM_ERR */ /* This allows us to work even when we don't have an fdatasync */ #ifndef HAVE_FDATASYNC #define fdatasync(fd) fsync(fd) #endif /* A similar setup for not having O_DSYNC */ #include #ifndef O_DSYNC # ifdef O_SYNC # define O_DSYNC O_SYNC /* POSIX */ # else # define O_DSYNC O_FSYNC /* BSD */ # endif #endif #ifndef HAVE_SOCKLEN_T typedef unsigned int socklen_t; #endif #ifndef HAVE_RLIM_T typedef int rlim_t; #endif /* some potentially memory saving tradeoffs, preconfigured in memory-saving mode */ /* save the cmdlines for the ID command */ #undef ID_SAVE_CMDLINE /* IPv6 things */ #include #include #include #include #ifndef HAVE_STRUCT_SOCKADDR_STORAGE #define _SS_MAXSIZE 128 /* Implementation specific max size */ #define _SS_PADSIZE (_SS_MAXSIZE - sizeof (struct sockaddr)) struct sockaddr_storage { struct sockaddr ss_sa; char __ss_pad2[_SS_PADSIZE]; }; # define ss_family ss_sa.sa_family # define HAVE_SS_FAMILY #endif /* !HAVE_STRUCT_SOCKADDR_STORAGE */ #ifndef AF_INET6 /* Define it to something that should never appear */ #define AF_INET6 AF_MAX #endif #if !defined(HAVE_GETADDRINFO) || !defined(HAVE_GETNAMEINFO) #include "gai.h" #endif /* End IPv6 things */ #ifdef OLD_SIEVE_SERVICE_NAME #define SIEVE_SERVICE_NAME "imap" #else #define SIEVE_SERVICE_NAME "sieve" #endif /* filenames */ #define FNAME_DBDIR "/db" #define FNAME_USERDIR "/user/" #define FNAME_DOMAINDIR "/domain/" #define FNAME_LOGDIR "/log/" #define FNAME_PTSDB "/ptclient/ptscache.db" #define CONFIG_FILENAME (SYSCONFDIR "/imapd.conf") #define DEFAULT_MASTER_CONFIG_FILENAME (SYSCONFDIR "/cyrus.conf") #ifndef HAVE_SHUTDOWN #define shutdown(fd, mode) 0 #endif /* *printf() macros */ #if (SIZEOF_SIZE_T == SIZEOF_INT) #define SIZE_T_FMT "%u" #elif (SIZEOF_SIZE_T == SIZEOF_LONG) #define SIZE_T_FMT "%lu" #elif (SIZEOF_SIZE_T == SIZEOF_LONG_LONG_INT) #define SIZE_T_FMT "%llu" #else #error dont know what to use for SIZE_T_FMT #endif #if (SIZEOF_OFF_T == SIZEOF_LONG) #define OFF_T_FMT "%ld" #define strtoofft(nptr, endptr, base) strtol(nptr, endptr, base) #elif (SIZEOF_OFF_T == SIZEOF_LONG_LONG_INT) #define OFF_T_FMT "%lld" #define strtoofft(nptr, endptr, base) strtoll(nptr, endptr, base) #else #error dont know what to use for OFF_T_FMT #endif #ifndef HAVE_POSIX_FADVISE #define POSIX_FADV_WILLNEED 0 extern int posix_fadvise(int fd, off_t offset, off_t len, int advice); #endif #ifndef HAVE_STRSEP extern char *strsep(char **, const char *); #endif #ifndef HAVE_MEMMEM extern void *memmem(const void *, size_t, const void *, size_t); #endif /* compile time options; think carefully before modifying */ enum { /* should we send an UNAVAILABLE message to master when * a service is exiting (master is already going to be * informed of the exit by the SIGCHLD signal anyway) ? */ MESSAGE_MASTER_ON_EXIT = 0, /* should a hierarchical rename stop on error? */ RENAME_STOP_ON_ERROR = 1, /* should we call fsync() to maybe help with softupdates? (it should) */ APPEND_ULTRA_PARANOID = 1, /* should we log extra information at the DEBUG level for DB stuff? * 0 -> nothing; 1 -> some; higher -> even more */ CONFIG_DB_VERBOSE = 1, /* log timing information to LOG_DEBUG */ CONFIG_TIMING_VERBOSE = 0, /* should we be pedantic about namespace or sleezy? */ SLEEZY_NAMESPACE = 1, /* should we do a fast TLS session shutdown? */ TLS_FAST_SHUTDOWN = 1, /* should we use the SQUAT engine to accelerate SEARCH? */ SQUAT_ENGINE = 1, /* should we have long LMTP error messages? */ LMTP_LONG_ERROR_MSGS = 1 }; #endif /* _CYRUS_IMAPD_CONFIG_H_ */ ]) dnl make sure that Makefile is the last thing output AC_CONFIG_FILES([ libcyrus_min.pc libcyrus.pc libcyrus_sieve.pc Makefile ]) if test "$with_perl" != "no" -a "$with_perl" != "notfound" ; then CMU_PERL_MAKEMAKER(perl/annotator) CMU_PERL_MAKEMAKER(perl/imap) CMU_PERL_MAKEMAKER(perl/sieve/managesieve) fi AC_OUTPUT echo " Cyrus Imapd configured components event notification: $enable_event_notification gssapi: $gssapi autocreate: $enable_autocreate idled: $enable_idled http: $enable_http kerberos V4: $krb4 murder: $enable_murder nntpd: $enable_nntp replication: $enable_replication sieve: $enable_sieve External dependencies: ldap: $have_ldap openssl: $with_ssl pcre: $cyrus_cv_pcre_utf8 Database support: bdb: $use_berkeley mysql: $with_mysql postgresql: $use_pgsql sqlite: $use_sqlite " cyrus-imapd-2.5.10/install-sh0000755000175000017500000003546312657715017013007 00000000000000#!/bin/sh # install - install a program, script, or datafile scriptversion=2014-09-12.12; # UTC # This originates from X11R5 (mit/util/scripts/install.sh), which was # later released in X11R6 (xc/config/util/install.sh) with the # following copyright and license. # # Copyright (C) 1994 X Consortium # # Permission is hereby granted, free of charge, to any person obtaining a copy # of this software and associated documentation files (the "Software"), to # deal in the Software without restriction, including without limitation the # rights to use, copy, modify, merge, publish, distribute, sublicense, and/or # sell copies of the Software, and to permit persons to whom the Software is # furnished to do so, subject to the following conditions: # # The above copyright notice and this permission notice shall be included in # all copies or substantial portions of the Software. # # THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR # IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, # FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE # X CONSORTIUM BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN # AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNEC- # TION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. # # Except as contained in this notice, the name of the X Consortium shall not # be used in advertising or otherwise to promote the sale, use or other deal- # ings in this Software without prior written authorization from the X Consor- # tium. # # # FSF changes to this file are in the public domain. # # Calling this script install-sh is preferred over install.sh, to prevent # 'make' implicit rules from creating a file called install from it # when there is no Makefile. # # This script is compatible with the BSD install script, but was written # from scratch. tab=' ' nl=' ' IFS=" $tab$nl" # Set DOITPROG to "echo" to test this script. doit=${DOITPROG-} doit_exec=${doit:-exec} # Put in absolute file names if you don't have them in your path; # or use environment vars. chgrpprog=${CHGRPPROG-chgrp} chmodprog=${CHMODPROG-chmod} chownprog=${CHOWNPROG-chown} cmpprog=${CMPPROG-cmp} cpprog=${CPPROG-cp} mkdirprog=${MKDIRPROG-mkdir} mvprog=${MVPROG-mv} rmprog=${RMPROG-rm} stripprog=${STRIPPROG-strip} posix_mkdir= # Desired mode of installed file. mode=0755 chgrpcmd= chmodcmd=$chmodprog chowncmd= mvcmd=$mvprog rmcmd="$rmprog -f" stripcmd= src= dst= dir_arg= dst_arg= copy_on_change=false is_target_a_directory=possibly usage="\ Usage: $0 [OPTION]... [-T] SRCFILE DSTFILE or: $0 [OPTION]... SRCFILES... DIRECTORY or: $0 [OPTION]... -t DIRECTORY SRCFILES... or: $0 [OPTION]... -d DIRECTORIES... In the 1st form, copy SRCFILE to DSTFILE. In the 2nd and 3rd, copy all SRCFILES to DIRECTORY. In the 4th, create DIRECTORIES. Options: --help display this help and exit. --version display version info and exit. -c (ignored) -C install only if different (preserve the last data modification time) -d create directories instead of installing files. -g GROUP $chgrpprog installed files to GROUP. -m MODE $chmodprog installed files to MODE. -o USER $chownprog installed files to USER. -s $stripprog installed files. -t DIRECTORY install into DIRECTORY. -T report an error if DSTFILE is a directory. Environment variables override the default commands: CHGRPPROG CHMODPROG CHOWNPROG CMPPROG CPPROG MKDIRPROG MVPROG RMPROG STRIPPROG " while test $# -ne 0; do case $1 in -c) ;; -C) copy_on_change=true;; -d) dir_arg=true;; -g) chgrpcmd="$chgrpprog $2" shift;; --help) echo "$usage"; exit $?;; -m) mode=$2 case $mode in *' '* | *"$tab"* | *"$nl"* | *'*'* | *'?'* | *'['*) echo "$0: invalid mode: $mode" >&2 exit 1;; esac shift;; -o) chowncmd="$chownprog $2" shift;; -s) stripcmd=$stripprog;; -t) is_target_a_directory=always dst_arg=$2 # Protect names problematic for 'test' and other utilities. case $dst_arg in -* | [=\(\)!]) dst_arg=./$dst_arg;; esac shift;; -T) is_target_a_directory=never;; --version) echo "$0 $scriptversion"; exit $?;; --) shift break;; -*) echo "$0: invalid option: $1" >&2 exit 1;; *) break;; esac shift done # We allow the use of options -d and -T together, by making -d # take the precedence; this is for compatibility with GNU install. if test -n "$dir_arg"; then if test -n "$dst_arg"; then echo "$0: target directory not allowed when installing a directory." >&2 exit 1 fi fi if test $# -ne 0 && test -z "$dir_arg$dst_arg"; then # When -d is used, all remaining arguments are directories to create. # When -t is used, the destination is already specified. # Otherwise, the last argument is the destination. Remove it from $@. for arg do if test -n "$dst_arg"; then # $@ is not empty: it contains at least $arg. set fnord "$@" "$dst_arg" shift # fnord fi shift # arg dst_arg=$arg # Protect names problematic for 'test' and other utilities. case $dst_arg in -* | [=\(\)!]) dst_arg=./$dst_arg;; esac done fi if test $# -eq 0; then if test -z "$dir_arg"; then echo "$0: no input file specified." >&2 exit 1 fi # It's OK to call 'install-sh -d' without argument. # This can happen when creating conditional directories. exit 0 fi if test -z "$dir_arg"; then if test $# -gt 1 || test "$is_target_a_directory" = always; then if test ! -d "$dst_arg"; then echo "$0: $dst_arg: Is not a directory." >&2 exit 1 fi fi fi if test -z "$dir_arg"; then do_exit='(exit $ret); exit $ret' trap "ret=129; $do_exit" 1 trap "ret=130; $do_exit" 2 trap "ret=141; $do_exit" 13 trap "ret=143; $do_exit" 15 # Set umask so as not to create temps with too-generous modes. # However, 'strip' requires both read and write access to temps. case $mode in # Optimize common cases. *644) cp_umask=133;; *755) cp_umask=22;; *[0-7]) if test -z "$stripcmd"; then u_plus_rw= else u_plus_rw='% 200' fi cp_umask=`expr '(' 777 - $mode % 1000 ')' $u_plus_rw`;; *) if test -z "$stripcmd"; then u_plus_rw= else u_plus_rw=,u+rw fi cp_umask=$mode$u_plus_rw;; esac fi for src do # Protect names problematic for 'test' and other utilities. case $src in -* | [=\(\)!]) src=./$src;; esac if test -n "$dir_arg"; then dst=$src dstdir=$dst test -d "$dstdir" dstdir_status=$? else # Waiting for this to be detected by the "$cpprog $src $dsttmp" command # might cause directories to be created, which would be especially bad # if $src (and thus $dsttmp) contains '*'. if test ! -f "$src" && test ! -d "$src"; then echo "$0: $src does not exist." >&2 exit 1 fi if test -z "$dst_arg"; then echo "$0: no destination specified." >&2 exit 1 fi dst=$dst_arg # If destination is a directory, append the input filename; won't work # if double slashes aren't ignored. if test -d "$dst"; then if test "$is_target_a_directory" = never; then echo "$0: $dst_arg: Is a directory" >&2 exit 1 fi dstdir=$dst dst=$dstdir/`basename "$src"` dstdir_status=0 else dstdir=`dirname "$dst"` test -d "$dstdir" dstdir_status=$? fi fi obsolete_mkdir_used=false if test $dstdir_status != 0; then case $posix_mkdir in '') # Create intermediate dirs using mode 755 as modified by the umask. # This is like FreeBSD 'install' as of 1997-10-28. umask=`umask` case $stripcmd.$umask in # Optimize common cases. *[2367][2367]) mkdir_umask=$umask;; .*0[02][02] | .[02][02] | .[02]) mkdir_umask=22;; *[0-7]) mkdir_umask=`expr $umask + 22 \ - $umask % 100 % 40 + $umask % 20 \ - $umask % 10 % 4 + $umask % 2 `;; *) mkdir_umask=$umask,go-w;; esac # With -d, create the new directory with the user-specified mode. # Otherwise, rely on $mkdir_umask. if test -n "$dir_arg"; then mkdir_mode=-m$mode else mkdir_mode= fi posix_mkdir=false case $umask in *[123567][0-7][0-7]) # POSIX mkdir -p sets u+wx bits regardless of umask, which # is incompatible with FreeBSD 'install' when (umask & 300) != 0. ;; *) # $RANDOM is not portable (e.g. dash); use it when possible to # lower collision chance tmpdir=${TMPDIR-/tmp}/ins$RANDOM-$$ trap 'ret=$?; rmdir "$tmpdir/a/b" "$tmpdir/a" "$tmpdir" 2>/dev/null; exit $ret' 0 # As "mkdir -p" follows symlinks and we work in /tmp possibly; so # create the $tmpdir first (and fail if unsuccessful) to make sure # that nobody tries to guess the $tmpdir name. if (umask $mkdir_umask && $mkdirprog $mkdir_mode "$tmpdir" && exec $mkdirprog $mkdir_mode -p -- "$tmpdir/a/b") >/dev/null 2>&1 then if test -z "$dir_arg" || { # Check for POSIX incompatibilities with -m. # HP-UX 11.23 and IRIX 6.5 mkdir -m -p sets group- or # other-writable bit of parent directory when it shouldn't. # FreeBSD 6.1 mkdir -m -p sets mode of existing directory. test_tmpdir="$tmpdir/a" ls_ld_tmpdir=`ls -ld "$test_tmpdir"` case $ls_ld_tmpdir in d????-?r-*) different_mode=700;; d????-?--*) different_mode=755;; *) false;; esac && $mkdirprog -m$different_mode -p -- "$test_tmpdir" && { ls_ld_tmpdir_1=`ls -ld "$test_tmpdir"` test "$ls_ld_tmpdir" = "$ls_ld_tmpdir_1" } } then posix_mkdir=: fi rmdir "$tmpdir/a/b" "$tmpdir/a" "$tmpdir" else # Remove any dirs left behind by ancient mkdir implementations. rmdir ./$mkdir_mode ./-p ./-- "$tmpdir" 2>/dev/null fi trap '' 0;; esac;; esac if $posix_mkdir && ( umask $mkdir_umask && $doit_exec $mkdirprog $mkdir_mode -p -- "$dstdir" ) then : else # The umask is ridiculous, or mkdir does not conform to POSIX, # or it failed possibly due to a race condition. Create the # directory the slow way, step by step, checking for races as we go. case $dstdir in /*) prefix='/';; [-=\(\)!]*) prefix='./';; *) prefix='';; esac oIFS=$IFS IFS=/ set -f set fnord $dstdir shift set +f IFS=$oIFS prefixes= for d do test X"$d" = X && continue prefix=$prefix$d if test -d "$prefix"; then prefixes= else if $posix_mkdir; then (umask=$mkdir_umask && $doit_exec $mkdirprog $mkdir_mode -p -- "$dstdir") && break # Don't fail if two instances are running concurrently. test -d "$prefix" || exit 1 else case $prefix in *\'*) qprefix=`echo "$prefix" | sed "s/'/'\\\\\\\\''/g"`;; *) qprefix=$prefix;; esac prefixes="$prefixes '$qprefix'" fi fi prefix=$prefix/ done if test -n "$prefixes"; then # Don't fail if two instances are running concurrently. (umask $mkdir_umask && eval "\$doit_exec \$mkdirprog $prefixes") || test -d "$dstdir" || exit 1 obsolete_mkdir_used=true fi fi fi if test -n "$dir_arg"; then { test -z "$chowncmd" || $doit $chowncmd "$dst"; } && { test -z "$chgrpcmd" || $doit $chgrpcmd "$dst"; } && { test "$obsolete_mkdir_used$chowncmd$chgrpcmd" = false || test -z "$chmodcmd" || $doit $chmodcmd $mode "$dst"; } || exit 1 else # Make a couple of temp file names in the proper directory. dsttmp=$dstdir/_inst.$$_ rmtmp=$dstdir/_rm.$$_ # Trap to clean up those temp files at exit. trap 'ret=$?; rm -f "$dsttmp" "$rmtmp" && exit $ret' 0 # Copy the file name to the temp name. (umask $cp_umask && $doit_exec $cpprog "$src" "$dsttmp") && # and set any options; do chmod last to preserve setuid bits. # # If any of these fail, we abort the whole thing. If we want to # ignore errors from any of these, just make sure not to ignore # errors from the above "$doit $cpprog $src $dsttmp" command. # { test -z "$chowncmd" || $doit $chowncmd "$dsttmp"; } && { test -z "$chgrpcmd" || $doit $chgrpcmd "$dsttmp"; } && { test -z "$stripcmd" || $doit $stripcmd "$dsttmp"; } && { test -z "$chmodcmd" || $doit $chmodcmd $mode "$dsttmp"; } && # If -C, don't bother to copy if it wouldn't change the file. if $copy_on_change && old=`LC_ALL=C ls -dlL "$dst" 2>/dev/null` && new=`LC_ALL=C ls -dlL "$dsttmp" 2>/dev/null` && set -f && set X $old && old=:$2:$4:$5:$6 && set X $new && new=:$2:$4:$5:$6 && set +f && test "$old" = "$new" && $cmpprog "$dst" "$dsttmp" >/dev/null 2>&1 then rm -f "$dsttmp" else # Rename the file to the real destination. $doit $mvcmd -f "$dsttmp" "$dst" 2>/dev/null || # The rename failed, perhaps because mv can't rename something else # to itself, or perhaps because mv is so ancient that it does not # support -f. { # Now remove or move aside any old file at destination location. # We try this two ways since rm can't unlink itself on some # systems and the destination file might be busy for other # reasons. In this case, the final cleanup might fail but the new # file should still install successfully. { test ! -f "$dst" || $doit $rmcmd -f "$dst" 2>/dev/null || { $doit $mvcmd -f "$dst" "$rmtmp" 2>/dev/null && { $doit $rmcmd -f "$rmtmp" 2>/dev/null; :; } } || { echo "$0: cannot unlink or rename $dst" >&2 (exit 1); exit 1 } } && # Now rename the file to the real destination. $doit $mvcmd "$dsttmp" "$dst" } fi || exit 1 trap '' 0 fi done # Local variables: # eval: (add-hook 'write-file-hooks 'time-stamp) # time-stamp-start: "scriptversion=" # time-stamp-format: "%:y-%02m-%02d.%02H" # time-stamp-time-zone: "UTC" # time-stamp-end: "; # UTC" # End: cyrus-imapd-2.5.10/libcyrus.pc.in0000644000175000017500000000042312772415051013545 00000000000000Name: Cyrus Imapd libcyrus Description: libcyrus library of Cyrus Imapd URL: http://www.cyrusimap.org/ Cflags: @SSL_CPPFLAGS@ @SASLFLAGS@ Version: @PACKAGE_VERSION@ Requires.private: libcyrus_min = @PACKAGE_VERSION@ Libs: -lcyrus Libs.private: @LIB_RT@ @LIB_SASL@ @SSL_LIBS@ cyrus-imapd-2.5.10/timsieved/0000755000175000017500000000000013001246664013030 500000000000000cyrus-imapd-2.5.10/timsieved/codes.h0000644000175000017500000000413412772415051014222 00000000000000/* codes.h -- error codes functions in timsieved may return * Tim Martin * 9/21/99 * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #ifndef _CODES_H_ #define _CODES_H_ #define TIMSIEVE_OK 0 #define TIMSIEVE_FAIL -10 #define TIMSIEVE_NOMEM -2 #define TIMSIEVE_BADPORT -5 #define TIMSIEVE_NOEXIST -6 #define TRUE 1 #define FALSE 0 #define BLOCKSIZE 1024 #endif cyrus-imapd-2.5.10/timsieved/scripttest.c0000644000175000017500000001111713001236020015302 00000000000000/* scripttest.c -- test wheather the sieve script is valid * Tim Martin * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #ifdef HAVE_CONFIG_H #include #endif #include #include #include #include "assert.h" #include "util.h" #include "xmalloc.h" #include "timsieved/codes.h" #include "timsieved/scripttest.h" /* to make larry's stupid functions happy :) */ static void foo(void) { fatal("stub function called", 0); } static sieve_vacation_t vacation = { 0, /* min response */ 0, /* max response */ (sieve_callback *) &foo, /* autorespond() */ (sieve_callback *) &foo /* send_response() */ }; static int sieve_notify(void *ac __attribute__((unused)), void *interp_context __attribute__((unused)), void *script_context __attribute__((unused)), void *message_context __attribute__((unused)), const char **errmsg __attribute__((unused))) { fatal("stub function called", 0); return SIEVE_FAIL; } static int mysieve_error(int lineno, const char *msg, void *i __attribute__((unused)), void *s) { struct buf *errors = (struct buf *)s; buf_printf(errors, "line %d: %s\r\n", lineno, msg); return SIEVE_OK; } /* returns TRUE or FALSE */ int build_sieve_interp(void) { int res; interp = sieve_interp_alloc(NULL); assert(interp != NULL); sieve_register_redirect(interp, (sieve_callback *) &foo); sieve_register_discard(interp, (sieve_callback *) &foo); sieve_register_reject(interp, (sieve_callback *) &foo); sieve_register_fileinto(interp, (sieve_callback *) &foo); sieve_register_keep(interp, (sieve_callback *) &foo); sieve_register_imapflags(interp, NULL); sieve_register_size(interp, (sieve_get_size *) &foo); sieve_register_header(interp, (sieve_get_header *) &foo); sieve_register_envelope(interp, (sieve_get_envelope *) &foo); sieve_register_body(interp, (sieve_get_body *) &foo); sieve_register_include(interp, (sieve_get_include *) &foo); res = sieve_register_vacation(interp, &vacation); if (res != SIEVE_OK) { syslog(LOG_ERR, "sieve_register_vacation() returns %d\n", res); return TIMSIEVE_FAIL; } sieve_register_notify(interp, &sieve_notify); sieve_register_parse_error(interp, &mysieve_error); return TIMSIEVE_OK; } /* returns TRUE or FALSE */ int is_script_parsable(FILE *stream, char **errstr, sieve_script_t **ret) { sieve_script_t *s; int res; struct buf errors = BUF_INITIALIZER; rewind(stream); buf_appendcstr(&errors, "script errors:\r\n"); *errstr = NULL; res = sieve_script_parse(interp, stream, &errors, &s); if (res == SIEVE_OK) { if(ret) { *ret = s; } else { sieve_script_free(&s); } } else { sieve_script_free(&s); *errstr = buf_release(&errors); } buf_free(&errors); return (res == SIEVE_OK) ? TIMSIEVE_OK : TIMSIEVE_FAIL; } cyrus-imapd-2.5.10/timsieved/actions.h0000644000175000017500000000627212772415051014572 00000000000000/* actions.h -- executes the commands (creating, deleting scripts etc..) for timsieved * Tim Martin * 9/21/99 * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #ifndef _ACTIONS_H_ #define _ACTIONS_H_ #include "prot.h" #include "util.h" extern int sieved_tls_required; /* * Get the list of capabilities * */ int capabilities(struct protstream *conn, sasl_conn_t *saslconn, int starttls_done, int authenticated, sasl_ssf_t sasl_ssf); /* * Get a sieve script with name "name" and output it's contents * */ int getscript(struct protstream *conn, const struct buf *name); /* * Put a scripts in the server with 'name' whose contents should be 'data' * */ int putscript(struct protstream *conn, const struct buf *name, const struct buf *data, int verify_only); /* * Delete the script with name 'name' * */ int deletescript(struct protstream *conn, const struct buf *name); /* * Is there space for this script? * */ int cmd_havespace(struct protstream *sieved_out, const struct buf *sieve_name, unsigned long num); /* * List all the scripts for the user. place a '*' next to the active one * if there is one * */ int listscripts(struct protstream *conn); /* * Set 'name' as the active sieve script * */ int setactive(struct protstream *conn, const struct buf *name); /* * Initialize * */ int actions_init(void); /* * Set user after sucessful authentication * */ int actions_setuser(const char *userid); #endif cyrus-imapd-2.5.10/timsieved/parser.h0000644000175000017500000000373613001236020014407 00000000000000/* parser.h * Tim Martin * 9/21/99 * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #ifndef PARSER_H #define PARSER_H #include "prot.h" int parser(struct protstream *sieved_out, struct protstream *sieved_in); #endif /* PARSER_H */ cyrus-imapd-2.5.10/timsieved/lex.c0000644000175000017500000002017713001236020013674 00000000000000/* lex.c -- lexer for timsieved * Tim Martin * 9/21/99 * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #ifdef HAVE_CONFIG_H #include #endif #include #include #include #include #include "libconfig.h" #include "xmalloc.h" #include "imap/global.h" #include "imap/tls.h" #include "timsieved/codes.h" #include "timsieved/lex.h" static int token_lookup(const char *str) { switch (*str) { case 'a': if (strcmp(str, "authenticate")==0) return AUTHENTICATE; break; case 'c': if (strcmp(str, "capability")==0) return CAPABILITY; if (strcmp(str, "checkscript")==0) return CHECKSCRIPT; break; case 'd': if (strcmp(str, "deletescript")==0) return DELETESCRIPT; break; case 'g': if (strcmp(str, "getscript")==0) return GETSCRIPT; break; case 'h': if (strcmp(str, "havespace")==0) return HAVESPACE; break; case 'l': if (strcmp(str, "listscripts")==0) return LISTSCRIPTS; if (strcmp(str, "logout")==0) return LOGOUT; break; case 'n': if (strcmp(str, "noop")==0) return NOOP; break; case 'p': if (strcmp(str, "putscript")==0) return PUTSCRIPT; break; case 'r': if (strcmp(str, "renamescript")==0) return RENAMESCRIPT; break; case 's': if (strcmp(str, "setactive")==0) return SETACTIVE; if (strcmp(str, "starttls")==0 && tls_enabled()) return STARTTLS; break; case 'u': if (strcmp(str, "unauthenticate")==0) return UNAUTHENTICATE; break; } /* error, nothing matched */ return -1; } /* current state the lexer is in */ static int lexer_state = LEXER_STATE_NORMAL; static unsigned long maxscriptsize=0; static char *buffer; #define ERR() { \ lexer_state=LEXER_STATE_RECOVER; \ return TIMSIEVE_FAIL; \ } #define ERR_PUSHBACK() { \ prot_ungetc(ch, stream); \ ERR(); \ } void lex_setrecovering(void) { lexer_state = LEXER_STATE_RECOVER; } int lex_init(void) { maxscriptsize = config_getint(IMAPOPT_SIEVE_MAXSCRIPTSIZE); maxscriptsize *= 1024; buffer = (char *) xmalloc(maxscriptsize); return 0; } /** * if outstr is NULL it isn't filled in */ int timlex(struct buf *outstr, unsigned long *outnum, struct protstream *stream) { int ch; char *buff_ptr; char *buff_end; unsigned long tmpnum = 0; unsigned long count=0; int result = TIMSIEVE_OK; buff_ptr = buffer; /* ptr into the buffer */ buff_end = buffer + maxscriptsize - 10; /* ptr to end of buffer */ while (1) { /* get a character this may block on a read if there is nothing in the buffer */ ch=prot_getc(stream); if (ch==EOF) { /* Lost connection */ return EOF; } switch (lexer_state) { case LEXER_STATE_RECOVER: if (ch == '\n') { lexer_state=LEXER_STATE_NORMAL; } if (ch == '\r') lexer_state=LEXER_STATE_RECOVER_CR; break; case LEXER_STATE_RECOVER_CR: if (ch == '\n') lexer_state=LEXER_STATE_NORMAL; break; case LEXER_STATE_CR: if (ch == '\n') { lexer_state=LEXER_STATE_NORMAL; return EOL; } /* otherwise, life is bad */ ERR_PUSHBACK(); case LEXER_STATE_QSTR: if (ch == '\"') { /* End of the string */ /*} */ if (outstr) { buf_appendmap(outstr, buffer, buff_ptr-buffer); buf_cstring(outstr); } lexer_state=LEXER_STATE_NORMAL; return STRING; } /* illegal character */ if (ch == '\0' || ch == '\r' || ch == '\n' || 0x7F < ((unsigned char)ch)) { ERR_PUSHBACK(); } /* Otherwise, we're appending a character */ if (buff_end <= buff_ptr) ERR_PUSHBACK(); /* too long! */ if (ch == '\\') { ch=prot_getc(stream); if (result != TIMSIEVE_OK) ERR(); if (ch != '\"' && ch != '\\') ERR_PUSHBACK(); } *buff_ptr++ = ch; break; case LEXER_STATE_LITERAL: if (('0' <= ch) && (ch <= '9')) { unsigned long newcount = count * 10 + (ch - '0'); if (newcount < count) ERR_PUSHBACK(); /* overflow */ /* * XXX This should be fatal if non-synchronizing. */ count = newcount; break; } if (ch != '+') ERR_PUSHBACK(); ch=prot_getc(stream); if (ch != '}') ERR_PUSHBACK(); ch=prot_getc(stream); if (ch < 0) ERR(); if (ch != '\r') ERR_PUSHBACK(); ch=prot_getc(stream); if (ch < 0) ERR(); if (ch != '\n') ERR_PUSHBACK(); if (count > maxscriptsize) { /* too big, eat the input */ for(;count > 0;count--) { if(prot_getc(stream)==EOF) break; } ERR(); } /* there is a literal string on the wire. let's read it */ if (outstr) { for (;count > 0;count--) { ch = prot_getc(stream); if (ch == EOF) break; buf_putc(outstr, ch); } buf_cstring(outstr); } else { /* just read the chars and throw them away */ unsigned long lup; for (lup=0;lup #endif #include #include #include #include #include #include #include #include #include #include #include #include #include "libconfig.h" #include "xmalloc.h" #include "xstrlcat.h" #include "xstrlcpy.h" #include "imap/global.h" #include "imap/sync_log.h" #include "imap/tls.h" #include "imap/version.h" #include "timsieved/actions.h" #include "timsieved/codes.h" #include "timsieved/scripttest.h" /* after a user has authentication, our current directory is their Sieve directory! */ extern int sieved_userisadmin; static char *sieve_dir_config = NULL; static const char *sieved_userid = NULL; int actions_init(void) { int sieve_usehomedir = 0; sieve_usehomedir = config_getswitch(IMAPOPT_SIEVEUSEHOMEDIR); if (!sieve_usehomedir) { sieve_dir_config = (char *) config_getstring(IMAPOPT_SIEVEDIR); } else { /* can't use home directories with timsieved */ syslog(LOG_ERR, "can't use home directories"); return TIMSIEVE_FAIL; } return TIMSIEVE_OK; } int actions_setuser(const char *userid) { char userbuf[1024], *user, *domain = NULL; size_t size = 1024, len; int result; char *sieve_dir = (char *) xzmalloc(size+1); sieved_userid = xstrdup(userid); user = (char *) userid; if (config_virtdomains && strchr(user, '@')) { /* split the user and domain */ strlcpy(userbuf, userid, sizeof(userbuf)); user = userbuf; if ((domain = strrchr(user, '@'))) *domain++ = '\0'; } len = strlcpy(sieve_dir, sieve_dir_config, size); if (domain) { char dhash = (char) dir_hash_c(domain, config_fulldirhash); len += snprintf(sieve_dir+len, size-len, "%s%c/%s", FNAME_DOMAINDIR, dhash, domain); } if (sieved_userisadmin) { strlcat(sieve_dir, "/global", size); } else { char hash = (char) dir_hash_c(user, config_fulldirhash); snprintf(sieve_dir+len, size-len, "/%c/%s", hash, user); } result = chdir(sieve_dir); if (result != 0) { result = cyrus_mkdir(sieve_dir, 0755); if (!result) result = mkdir(sieve_dir, 0755); if (!result) result = chdir(sieve_dir); if (result) { syslog(LOG_ERR, "mkdir %s: %m", sieve_dir); free(sieve_dir); return TIMSIEVE_FAIL; } } free(sieve_dir); return TIMSIEVE_OK; } /* * * Everything but '/' and '\0' are valid. * */ static int scriptname_valid(const struct buf *name) { unsigned int lup; char *ptr; /* must be at least one character long */ if (name->len < 1) return TIMSIEVE_FAIL; ptr = name->s; for (lup=0;luplen;lup++) { if ((ptr[lup]=='/') || (ptr[lup]=='\0')) return TIMSIEVE_FAIL; } return TIMSIEVE_OK; } int capabilities(struct protstream *conn, sasl_conn_t *saslconn, int starttls_done, int authenticated, sasl_ssf_t sasl_ssf) { const char *sasllist; int mechcount; /* implementation */ if (config_serverinfo == IMAP_ENUM_SERVERINFO_ON) { prot_printf(conn, "\"IMPLEMENTATION\" \"Cyrus timsieved%s %s\"\r\n", config_mupdate_server ? " (Murder)" : "", cyrus_version()); } else if (config_serverinfo == IMAP_ENUM_SERVERINFO_MIN) { prot_printf(conn, "\"IMPLEMENTATION\" \"Cyrus timsieved%s\"\r\n", config_mupdate_server ? " (Murder)" : ""); } else { /* IMAP_ENUM_SERVERINFO_OFF */ prot_printf(conn, "\"IMPLEMENTATION\" \"ManageSieve\"\r\n"); } /* SASL */ if (!sieved_tls_required && (!authenticated || sasl_ssf) && sasl_listmech(saslconn, NULL, "\"SASL\" \"", " ", "\"\r\n", &sasllist, NULL, &mechcount) == SASL_OK/* && mechcount > 0*/) { prot_printf(conn,"%s",sasllist); } /* Sieve capabilities */ prot_printf(conn,"\"SIEVE\" \"%s\"\r\n",sieve_listextensions(interp)); if (tls_enabled() && !starttls_done && !authenticated) { prot_printf(conn, "\"STARTTLS\"\r\n"); } prot_printf(conn, "\"UNAUTHENTICATE\"\r\n"); prot_printf(conn,"OK\r\n"); return TIMSIEVE_OK; } int getscript(struct protstream *conn, const struct buf *name) { FILE *stream; struct stat filestats; /* returned by stat */ int size; /* size of the file */ int result; int cnt; char path[1024]; result = scriptname_valid(name); if (result!=TIMSIEVE_OK) { prot_printf(conn,"NO \"Invalid script name\"\r\n"); return result; } snprintf(path, 1023, "%s.script", name->s); result = stat(path, &filestats); if (result != 0) { prot_printf(conn,"NO (NONEXISTENT) \"Script doesn't exist\"\r\n"); return TIMSIEVE_NOEXIST; } size = filestats.st_size; stream = fopen(path, "r"); if (stream == NULL) { prot_printf(conn,"NO \"fopen failed\"\r\n"); return TIMSIEVE_NOEXIST; } prot_printf(conn, "{%d}\r\n", size); cnt = 0; while (cnt < size) { char buf[BLOCKSIZE]; int amount=BLOCKSIZE; if (size-cnt < BLOCKSIZE) amount=size-cnt; if (fread(buf, 1, BLOCKSIZE, stream) == 0) { if (ferror(stream)) { fatal("fatal error (fread)", 0); } } prot_write(conn, buf, amount); cnt += amount; } prot_printf(conn,"\r\n"); prot_printf(conn, "OK\r\n"); fclose(stream); return TIMSIEVE_OK; } /* counts the number of scripts user has that are DIFFERENT from name. used for enforcing quotas */ static int countscripts(char *name) { DIR *dp; struct dirent *dir; size_t length; int number=0; char myname[1024]; snprintf(myname, 1023, "%s.script", name); if ((dp = opendir(".")) == NULL) { return -1; } while ((dir=readdir(dp)) != NULL) { length=strlen(dir->d_name); if (length >= strlen(".script") && (strcmp(dir->d_name + (length - 7), ".script") == 0)) { /* this is a sieve script */ if (strcmp(myname, dir->d_name) != 0) { /* and it's different from me */ number++; } } } closedir(dp); return number; } /* save name as a sieve script */ int putscript(struct protstream *conn, const struct buf *name, const struct buf *data, int verify_only) { FILE *stream; const char *dataptr; char *errstr; unsigned int i; int last_was_r = 0; int result; char path[1024], p2[1024]; char bc_path[1024], bc_p2[1024]; int maxscripts; sieve_script_t *s; result = scriptname_valid(name); if (result!=TIMSIEVE_OK) { prot_printf(conn,"NO \"Invalid script name\"\r\n"); return result; } if (verify_only) stream = tmpfile(); else { /* see if this would put the user over quota */ maxscripts = config_getint(IMAPOPT_SIEVE_MAXSCRIPTS); if (countscripts(name->s)+1 > maxscripts) { prot_printf(conn, "NO (QUOTA/MAXSCRIPTS) \"You are only allowed %d scripts on this server\"\r\n", maxscripts); return TIMSIEVE_FAIL; } snprintf(path, 1023, "%s.script.NEW", name->s); stream = fopen(path, "w+"); } if (stream == NULL) { prot_printf(conn, "NO \"Unable to open script for writing (%s)\"\r\n", path); return TIMSIEVE_NOEXIST; } dataptr = data->s; /* copy data to file - replacing any lone \r or \n with the * \r\n pair so notify messages are SMTP compatible */ for (i = 0; i < data->len; i++) { if (last_was_r) { if (dataptr[i] != '\n') putc('\n', stream); } else { if (dataptr[i] == '\n') putc('\r', stream); } putc(dataptr[i], stream); last_was_r = (dataptr[i] == '\r'); } if (last_was_r) putc('\n', stream); /* let's make sure this is a valid script (no parse errors) */ result = is_script_parsable(stream, &errstr, &s); if (result != TIMSIEVE_OK) { if (errstr && *errstr) { prot_printf(conn, "NO "); prot_printstring(conn, errstr); prot_printf(conn, "\r\n"); } else { prot_printf(conn, "NO \"parse failed\"\r\n"); } free(errstr); fclose(stream); unlink(path); return result; } fflush(stream); fclose(stream); if (!verify_only) { int fd; bytecode_info_t *bc; /* Now, generate the bytecode */ if(sieve_generate_bytecode(&bc, s) == -1) { unlink(path); sieve_script_free(&s); prot_printf(conn, "NO \"bytecode generate failed\"\r\n"); return TIMSIEVE_FAIL; } /* Now, open the new file */ snprintf(bc_path, 1023, "%s.bc.NEW", name->s); fd = open(bc_path, O_CREAT | O_TRUNC | O_WRONLY, 0600); if(fd < 0) { unlink(path); sieve_free_bytecode(&bc); sieve_script_free(&s); prot_printf(conn, "NO \"couldn't open bytecode file\"\r\n"); return TIMSIEVE_FAIL; } /* Now, emit the bytecode */ if(sieve_emit_bytecode(fd, bc) == -1) { close(fd); unlink(path); unlink(bc_path); sieve_free_bytecode(&bc); sieve_script_free(&s); prot_printf(conn, "NO \"bytecode emit failed\"\r\n"); return TIMSIEVE_FAIL; } sieve_free_bytecode(&bc); sieve_script_free(&s); close(fd); /* Now, rename! */ snprintf(p2, 1023, "%s.script", name->s); snprintf(bc_p2, 1023, "%s.bc", name->s); rename(path, p2); rename(bc_path, bc_p2); } prot_printf(conn, "OK\r\n"); sync_log_sieve(sieved_userid); return TIMSIEVE_OK; } /* delete the active script */ static int deleteactive(struct protstream *conn) { if (unlink("defaultbc") != 0) { if (errno == ENOENT) { /* RFC 5804, 2.8 SETACTIVE Command: * Disabling an active script when there is no script active is * not an error and MUST result in an OK reply. */ return TIMSIEVE_OK; } prot_printf(conn,"NO \"Unable to unlink active script\"\r\n"); return TIMSIEVE_FAIL; } sync_log_sieve(sieved_userid); return TIMSIEVE_OK; } /* is this the active script? */ static int isactive(char *name) { char filename[1024]; char activelink[1024]; ssize_t link_len; snprintf(filename, 1023, "%s.bc", name); memset(activelink, 0, sizeof(activelink)); link_len = readlink("defaultbc", activelink, sizeof(activelink)-1); if (link_len == -1) { if (errno != ENOENT) syslog(LOG_ERR, "readlink(defaultbc): %m"); return FALSE; } activelink[link_len] = '\0'; if (!strcmp(filename, activelink)) { return TRUE; } else { return FALSE; } } /* delete a sieve script */ int deletescript(struct protstream *conn, const struct buf *name) { int result; char path[1024]; result = scriptname_valid(name); if (result!=TIMSIEVE_OK) { prot_printf(conn,"NO \"Invalid script name\"\r\n"); return result; } snprintf(path, 1023, "%s.script", name->s); if (isactive(name->s)) { prot_printf(conn, "NO (ACTIVE) \"Active script cannot be deleted\"\r\n"); return TIMSIEVE_FAIL; } result = unlink(path); if (result != 0) { if (result == ENOENT) prot_printf(conn, "NO (NONEXISTENT) \"Script %s does not exist.\"\r\n", name->s); else prot_printf(conn,"NO \"Error deleting script\"\r\n"); return TIMSIEVE_FAIL; } snprintf(path, 1023, "%s.bc", name->s); result = unlink(path); if (result != 0) { prot_printf(conn,"NO \"Error deleting bytecode\"\r\n"); return TIMSIEVE_FAIL; } sync_log_sieve(sieved_userid); prot_printf(conn,"OK\r\n"); return TIMSIEVE_OK; } /* list the scripts user has available */ int listscripts(struct protstream *conn) { DIR *dp; struct dirent *dir; size_t length; /* open the directory */ dp=opendir("."); if (dp==NULL) { prot_printf(conn,"NO \"Error opening directory\"\r\n"); return TIMSIEVE_FAIL; } while ((dir=readdir(dp)) != NULL) /* while there are files here */ { length=strlen(dir->d_name); if (length >= strlen(".script")) /* if ends in .script */ { if (strcmp(dir->d_name + (length - 7), ".script")==0) { char *namewo = xstrndup(dir->d_name, length-7); if (isactive(namewo)) prot_printf(conn,"\"%s\" ACTIVE\r\n", namewo); else prot_printf(conn,"\"%s\"\r\n", namewo); free(namewo); } } } closedir(dp); prot_printf(conn,"OK\r\n"); return TIMSIEVE_OK; } /* does the script 'str' exist return TRUE | FALSE */ static int exists(char *str) { char filename[1024]; struct stat filestats; /* returned by stat */ int result; snprintf(filename, 1023, "%s.script", str); result = stat(filename,&filestats); if (result != 0) { return FALSE; } return TRUE; } /* set the sieve script 'name' to be the active script */ int setactive(struct protstream *conn, const struct buf *name) { int result; char filename[1024]; /* if string name is empty, disable active script */ if (!name->len) { if (deleteactive(conn) != TIMSIEVE_OK) return TIMSIEVE_FAIL; prot_printf(conn,"OK\r\n"); return TIMSIEVE_OK; } result = scriptname_valid(name); if (result!=TIMSIEVE_OK) { prot_printf(conn,"NO \"Invalid script name\"\r\n"); return result; } if (exists(name->s)==FALSE) { prot_printf(conn,"NO (NONEXISTENT) \"Script does not exist\"\r\n"); return TIMSIEVE_NOEXIST; } /* if script already is the active one just say ok */ if (isactive(name->s)==TRUE) { prot_printf(conn,"OK\r\n"); return TIMSIEVE_OK; } /* get the name of the active sieve script */ snprintf(filename, sizeof(filename), "%s.bc", name->s); /* ok we want to do this atomically so let's - make .NEW as a hard link - rename it to */ result = symlink(filename, "defaultbc.NEW"); if (result) { syslog(LOG_ERR, "symlink(%s, defaultbc.NEW): %m", filename); prot_printf(conn, "NO \"Can't make link\"\r\n"); return TIMSIEVE_FAIL; } result = rename("defaultbc.NEW", "defaultbc"); if (result) { unlink("defaultbc.NEW"); syslog(LOG_ERR, "rename(defaultbc.NEW, defaultbc): %m"); prot_printf(conn,"NO \"Error renaming\"\r\n"); return TIMSIEVE_FAIL; } sync_log_sieve(sieved_userid); prot_printf(conn,"OK\r\n"); return TIMSIEVE_OK; } int cmd_havespace(struct protstream *conn, const struct buf *sieve_name, unsigned long num) { int result; int maxscripts; unsigned long maxscriptsize; result = scriptname_valid(sieve_name); if (result!=TIMSIEVE_OK) { prot_printf(conn,"NO \"Invalid script name\"\r\n"); return result; } /* see if the size of the script is too big */ maxscriptsize = config_getint(IMAPOPT_SIEVE_MAXSCRIPTSIZE); maxscriptsize *= 1024; if (num > maxscriptsize) { prot_printf(conn, "NO (QUOTA/MAXSIZE) \"Script size is too large. " "Max script size is %ld bytes\"\r\n", maxscriptsize); return TIMSIEVE_FAIL; } /* see if this would put the user over quota */ maxscripts = config_getint(IMAPOPT_SIEVE_MAXSCRIPTS); if (countscripts(sieve_name->s)+1 > maxscripts) { prot_printf(conn, "NO (QUOTA/MAXSCRIPTS) \"You are only allowed %d scripts on this server\"\r\n", maxscripts); return TIMSIEVE_FAIL; } prot_printf(conn,"OK\r\n"); return TIMSIEVE_OK; } cyrus-imapd-2.5.10/timsieved/parser.c0000644000175000017500000005731213001236020014401 00000000000000/* parser.c -- parser used by timsieved * Tim Martin * 9/21/99 * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #ifdef HAVE_CONFIG_H #include #endif #include #include #include #ifdef HAVE_UNISTD_H #include #endif #include #include #include #include "assert.h" #include "exitcodes.h" #include "libconfig.h" #include "xmalloc.h" #include "xstrlcpy.h" #include "imap/backend.h" #include "imap/global.h" #include "imap/mboxlist.h" #include "imap/mboxname.h" #include "imap/telemetry.h" #include "imap/tls.h" #include "timsieved/actions.h" #include "timsieved/codes.h" #include "timsieved/lex.h" extern const char *sieved_clienthost; extern int sieved_domainfromip; extern int sieved_userisadmin; /* xxx these are both leaked, but we only handle one connection at a * time... */ extern sasl_conn_t *sieved_saslconn; /* the sasl connection context */ static const char *referral_host = NULL; int authenticated = 0; int verify_only = 0; int starttls_done = 0; sasl_ssf_t sasl_ssf = 0; #ifdef HAVE_SSL /* our tls connection, if any */ static SSL *tls_conn = NULL; #endif /* HAVE_SSL */ extern int sieved_timeout; /* from elsewhere */ void fatal(const char *s, int code); extern int sieved_logfd; extern struct backend *backend; /* forward declarations */ static void cmd_logout(struct protstream *sieved_out, struct protstream *sieved_in); static int cmd_authenticate(struct protstream *sieved_out, struct protstream *sieved_in, const char *mech, const struct buf *initial_challenge, const char **errmsg); static void cmd_unauthenticate(struct protstream *sieved_out, struct protstream *sieved_in); static int cmd_starttls(struct protstream *sieved_out, struct protstream *sieved_in); static char *sieve_parsesuccess(char *str, const char **status) { char *success = NULL, *tmp; if (!strncmp(str, "OK (", 4) && (tmp = strstr(str+4, "SASL \"")) != NULL) { success = tmp+6; /* skip SASL " */ tmp = strstr(success, "\""); if (tmp) *tmp = '\0'; /* clip " */ } if (status) *status = NULL; return success; } static struct protocol_t sieve_protocol = { "sieve", SIEVE_SERVICE_NAME, TYPE_STD, { { { 1, "OK" }, { "CAPABILITY", NULL, "OK", NULL, CAPAF_ONE_PER_LINE|CAPAF_QUOTE_WORDS, { { "SASL", CAPA_AUTH }, { "STARTTLS", CAPA_STARTTLS }, { NULL, 0 } } }, { "STARTTLS", "OK", "NO", 1 }, { "AUTHENTICATE", USHRT_MAX, 1, "OK", "NO", NULL, "*", &sieve_parsesuccess, AUTO_CAPA_AUTH_SSF }, { NULL, NULL, NULL }, { NULL, NULL, NULL }, { "LOGOUT", NULL, "OK" } } } }; /* Returns TRUE if we are done */ int parser(struct protstream *sieved_out, struct protstream *sieved_in) { int token = EOL; const char *error_msg = "Generic Error"; struct buf mechanism_name = BUF_INITIALIZER; struct buf initial_challenge = BUF_INITIALIZER; struct buf sieve_name = BUF_INITIALIZER; struct buf sieve_data = BUF_INITIALIZER; unsigned long num; int ret = FALSE; /* get one token from the lexer */ while(token == EOL) token = timlex(NULL, NULL, sieved_in); if (!authenticated && (token > 255) && (token!=AUTHENTICATE) && (token!=LOGOUT) && (token!=CAPABILITY) && (token!=NOOP) && (token!=CHECKSCRIPT) && (!tls_enabled() || (token!=STARTTLS))) { error_msg = "Authenticate first"; if (token!=EOL) lex_setrecovering(); goto error; } if (verify_only && (token > 255) && (token!=CHECKSCRIPT) && (token!=PUTSCRIPT) && (token!=LOGOUT)) { error_msg = "Script verification only"; if (token!=EOL) lex_setrecovering(); goto error; } switch (token) { case EOF: /* timlex() will return EOF when the remote disconnects badly */ syslog(LOG_WARNING, "Lost connection to client -- exiting"); prot_printf(sieved_out, "BYE \"Shutdown TCP timeout\"\r\n"); ret = TRUE; goto done; break; case AUTHENTICATE: if (sieved_tls_required) { error_msg = "AUTHENTICATE only available under a layer"; goto error; } if (timlex(NULL, NULL, sieved_in)!=SPACE) { error_msg = "SPACE must occur after AUTHENTICATE"; goto error; } if (timlex(&mechanism_name, NULL, sieved_in)!=STRING) { error_msg = "Did not specify mechanism name"; goto error; } token = timlex(NULL, NULL, sieved_in); if (token != EOL) { /* optional client first challenge */ if (token!=SPACE) { error_msg = "Expected SPACE"; goto error; } if (timlex(&initial_challenge, NULL, sieved_in)!=STRING) { error_msg = "Expected string"; goto error; } token = timlex(NULL, NULL, sieved_in); } if (token != EOL) { error_msg = "Expected EOL"; goto error; } if (authenticated) prot_printf(sieved_out, "NO \"Already authenticated\"\r\n"); else if (cmd_authenticate(sieved_out, sieved_in, mechanism_name.s, &initial_challenge, &error_msg)==FALSE) { error_msg = "Authentication Error"; goto error; } #if 0 /* XXX - not implemented in sieveshell*/ /* referral_host is non-null only once we are authenticated */ if(referral_host) goto do_referral; #endif break; case CAPABILITY: if (timlex(NULL, NULL, sieved_in)!=EOL) { error_msg = "Expected EOL"; goto error; } if(referral_host) goto do_referral; capabilities(sieved_out, sieved_saslconn, starttls_done, authenticated, sasl_ssf); break; case CHECKSCRIPT: if (timlex(NULL, NULL, sieved_in)!=SPACE) { error_msg = "SPACE must occur after CHECKSCRIPT"; goto error; } if (timlex(&sieve_data, NULL, sieved_in)!=STRING) { error_msg = "Expected script content as second parameter"; goto error; } if (timlex(NULL, NULL, sieved_in)!=EOL) { error_msg = "Expected EOL"; goto error; } /* f stands for "f"aked name, it could be any valid script name */ buf_reset(&sieve_name); buf_appendcstr(&sieve_name, "f"); putscript(sieved_out, &sieve_name, &sieve_data, /* verify_only */ 1); break; case HAVESPACE: if (timlex(NULL, NULL, sieved_in)!=SPACE) { error_msg = "SPACE must occur after HAVESPACE"; goto error; } if (timlex(&sieve_name, NULL, sieved_in)!=STRING) { error_msg = "Did not specify script name"; goto error; } if (timlex(NULL, NULL, sieved_in)!=SPACE) { error_msg = "Expected SPACE after SCRIPTNAME"; goto error; } if (timlex(NULL, &num, sieved_in)!=NUMBER) { error_msg = "Expected Number"; goto error; } if (timlex(NULL, NULL, sieved_in)!=EOL) { error_msg = "Expected EOL"; goto error; } if(referral_host) goto do_referral; cmd_havespace(sieved_out, &sieve_name, num); break; case LOGOUT: token = timlex(NULL, NULL, sieved_in); /* timlex() will return LOGOUT when the remote disconnects badly */ if (token!=EOL && token!=EOF && token!=LOGOUT) { error_msg = "Garbage after logout command"; goto error; } /* no referral for logout */ cmd_logout(sieved_out, sieved_in); ret = TRUE; goto done; break; case GETSCRIPT: if (timlex(NULL, NULL, sieved_in)!=SPACE) { error_msg = "SPACE must occur after GETSCRIPT"; goto error; } if (timlex(&sieve_name, NULL, sieved_in)!=STRING) { error_msg = "Did not specify script name"; goto error; } if (timlex(NULL, NULL, sieved_in)!=EOL) { error_msg = "Expected EOL"; goto error; } if(referral_host) goto do_referral; getscript(sieved_out, &sieve_name); break; case PUTSCRIPT: if (timlex(NULL, NULL, sieved_in)!=SPACE) { error_msg = "SPACE must occur after PUTSCRIPT"; goto error; } if (timlex(&sieve_name, NULL, sieved_in)!=STRING) { error_msg = "Did not specify script name"; goto error; } if (timlex(NULL, NULL, sieved_in)!=SPACE) { error_msg = "Expected SPACE"; goto error; } if (timlex(&sieve_data, NULL, sieved_in)!=STRING) { error_msg = "Did not specify legal script data length"; goto error; } if (timlex(NULL, NULL, sieved_in)!=EOL) { error_msg = "Expected EOL"; goto error; } if(referral_host) goto do_referral; putscript(sieved_out, &sieve_name, &sieve_data, verify_only); break; case SETACTIVE: if (timlex(NULL, NULL, sieved_in)!=SPACE) { error_msg = "SPACE must occur after SETACTIVE"; goto error; } if (timlex(&sieve_name, NULL, sieved_in)!=STRING) { error_msg = "Did not specify script name"; goto error; } if (timlex(NULL, NULL, sieved_in)!=EOL) { error_msg = "Expected EOL"; goto error; } if(referral_host) goto do_referral; setactive(sieved_out, &sieve_name); break; case DELETESCRIPT: if (timlex(NULL, NULL, sieved_in)!=SPACE) { error_msg = "SPACE must occur after DELETESCRIPT"; goto error; } if (timlex(&sieve_name, NULL, sieved_in)!=STRING) { error_msg = "Did not specify script name"; goto error; } if (timlex(NULL, NULL, sieved_in)!=EOL) { error_msg = "Expected EOL"; goto error; } if(referral_host) goto do_referral; deletescript(sieved_out, &sieve_name); break; case LISTSCRIPTS: if (timlex(NULL, NULL, sieved_in)!=EOL) { error_msg = "Expected EOL"; goto error; } if(referral_host) goto do_referral; listscripts(sieved_out); break; case STARTTLS: if (timlex(NULL, NULL, sieved_in)!=EOL) { error_msg = "Expected EOL"; goto error; } /* XXX discard any input pipelined after STARTTLS */ prot_flush(sieved_in); if(referral_host) goto do_referral; cmd_starttls(sieved_out, sieved_in); break; case NOOP: token = timlex(NULL, NULL, sieved_in); if (token != EOL) { /* optional string parameter */ if (token!=SPACE) { error_msg = "Expected SPACE"; goto error; } if (timlex(&sieve_name, NULL, sieved_in)!=STRING) { error_msg = "Expected string"; goto error; } token = timlex(NULL, NULL, sieved_in); } if (token != EOL) { error_msg = "Expected EOL"; goto error; } if (sieve_name.len) { prot_printf(sieved_out, "OK (TAG "); prot_printliteral(sieved_out, sieve_name.s, sieve_name.len); prot_printf(sieved_out, ") \"Done\"\r\n"); } else prot_printf(sieved_out, "OK \"Done\"\r\n"); break; case UNAUTHENTICATE: if (timlex(NULL, NULL, sieved_in)!=EOL) { error_msg = "Expected EOL"; goto error; } cmd_unauthenticate(sieved_out, sieved_in); break; default: error_msg="Expected a command. Got something else."; goto error; break; } done: /* free memory */ buf_free(&mechanism_name); buf_free(&initial_challenge); buf_free(&sieve_name); buf_free(&sieve_data); prot_flush(sieved_out); return ret; error: /* free memory */ buf_free(&mechanism_name); buf_free(&initial_challenge); buf_free(&sieve_name); buf_free(&sieve_data); prot_printf(sieved_out, "NO \"%s\"\r\n",error_msg); prot_flush(sieved_out); return FALSE; do_referral: { char buf[4096]; char *c; /* Truncate the hostname if necessary */ strlcpy(buf, referral_host, sizeof(buf)); c = strchr(buf, '!'); if(c) *c = '\0'; prot_printf(sieved_out, "BYE (REFERRAL \"sieve://%s\") \"Try Remote.\"\r\n", buf); ret = TRUE; goto done; } } void cmd_logout(struct protstream *sieved_out, struct protstream *sieved_in __attribute__((unused))) { prot_printf(sieved_out, "OK \"Logout Complete\"\r\n"); prot_flush(sieved_out); } static sasl_ssf_t ssf = 0; static char *authid = NULL; extern int reset_saslconn(sasl_conn_t **conn, sasl_ssf_t ssf, char *authid); static void cmd_unauthenticate(struct protstream *sieved_out, struct protstream *sieved_in) { if (chdir("/tmp/")) syslog(LOG_ERR, "Failed to chdir to /tmp/"); reset_saslconn(&sieved_saslconn, sieved_in->saslssf, authid); prot_unsetsasl(sieved_out); prot_unsetsasl(sieved_in); prot_printf(sieved_out, "OK\r\n"); authenticated = 0; } static int cmd_authenticate(struct protstream *sieved_out, struct protstream *sieved_in, const char *mech, const struct buf *initial_challenge, const char **errmsg) { int sasl_result; char *clientin = NULL; unsigned int clientinlen = 0; const char *serverout=NULL; unsigned int serveroutlen; const void *canon_user, *val; char *username = NULL; int ret = TRUE; mbentry_t *mbentry = NULL; assert(initial_challenge); if (initial_challenge->s) { /* a value was provided on the wire, possibly of zero length */ clientin = xmalloc(initial_challenge->len*2); if (initial_challenge->len) { sasl_result=sasl_decode64(initial_challenge->s, initial_challenge->len, clientin, initial_challenge->len*2, &clientinlen); } else { clientinlen = 0; sasl_result = SASL_OK; } if (sasl_result!=SASL_OK) { *errmsg="error base64 decoding string"; syslog(LOG_NOTICE, "badlogin: %s %s %s", sieved_clienthost, mech, "error base64 decoding string"); goto reset; } } sasl_result = sasl_server_start(sieved_saslconn, mech, clientin, clientinlen, &serverout, &serveroutlen); while (sasl_result==SASL_CONTINUE) { int token1; int token2; struct buf str = BUF_INITIALIZER, blahstr = BUF_INITIALIZER; char *inbase64; unsigned int inbase64len; /* convert to base64 */ inbase64 = xmalloc(serveroutlen*2+1); sasl_encode64(serverout, serveroutlen, inbase64, serveroutlen*2+1, &inbase64len); /* send out the string always as a literal */ prot_printf(sieved_out, "{%d}\r\n",inbase64len); prot_write(sieved_out,inbase64,inbase64len); prot_printf(sieved_out,"\r\n"); free(inbase64); token1 = timlex(&str, NULL, sieved_in); if (token1==STRING) { free(clientin); clientin = xmalloc(str.len*2); if (str.len) { sasl_result=sasl_decode64(str.s, str.len, clientin, str.len*2, &clientinlen); } else { clientinlen = 0; sasl_result = SASL_OK; } buf_free(&str); if (sasl_result!=SASL_OK) { *errmsg="error base64 decoding string"; syslog(LOG_NOTICE, "badlogin: %s %s %s", sieved_clienthost, mech, "error base64 decoding string"); goto reset; } } else { *errmsg="Expected STRING-xxx1"; goto reset; } token2 = timlex(&blahstr, NULL, sieved_in); /* we want to see a STRING followed by EOL */ if ((token1==STRING) && (token2==EOL)) { sasl_result = sasl_server_step(sieved_saslconn, clientin, clientinlen, &serverout, &serveroutlen); } else { *errmsg = "expected a STRING followed by an EOL"; syslog(LOG_NOTICE, "badlogin: %s %s %s", sieved_clienthost, mech, "expected string"); goto reset; } } if (sasl_result!=SASL_OK) { /* convert to user error code */ if(sasl_result == SASL_NOUSER) sasl_result = SASL_BADAUTH; *errmsg = (const char *) sasl_errstring(sasl_result,NULL,NULL); syslog(LOG_NOTICE, "badlogin: %s %s %s", sieved_clienthost, mech, *errmsg); goto reset; } /* get the userid from SASL */ sasl_result=sasl_getprop(sieved_saslconn, SASL_USERNAME, &canon_user); if (sasl_result!=SASL_OK) { *errmsg = "Internal SASL error"; syslog(LOG_ERR, "SASL: sasl_getprop SASL_USERNAME: %s", sasl_errstring(sasl_result, NULL, NULL)); goto reset; } username = xstrdup((const char *) canon_user); verify_only = !strcmp(username, "anonymous"); if (!verify_only) { /* Check for a remote mailbox (should we setup a redirect?) */ struct namespace sieved_namespace; char inboxname[MAX_MAILBOX_BUFFER]; int r; /* Set namespace */ if ((r = mboxname_init_namespace(&sieved_namespace, 0)) != 0) { syslog(LOG_ERR, "%s", error_message(r)); fatal(error_message(r), EC_CONFIG); } /* Translate any separators in userid */ mboxname_hiersep_tointernal(&sieved_namespace, username, config_virtdomains ? strcspn(username, "@") : 0); (*sieved_namespace.mboxname_tointernal)(&sieved_namespace, "INBOX", username, inboxname); r = mboxlist_lookup(inboxname, &mbentry, NULL); if(r && !sieved_userisadmin) { /* lookup error */ syslog(LOG_ERR, "%s", error_message(r)); goto reset; } if (mbentry && mbentry->mbtype & MBTYPE_REMOTE) { /* It's a remote mailbox */ if (config_getswitch(IMAPOPT_SIEVE_ALLOWREFERRALS)) { /* We want to set up a referral */ if (sieved_domainfromip) { char *authname, *p; /* get a new copy of the userid */ free(username); username = xstrdup((const char *) canon_user); /* get the authid from SASL */ sasl_result=sasl_getprop(sieved_saslconn, SASL_AUTHUSER, &canon_user); if (sasl_result!=SASL_OK) { *errmsg = "Internal SASL error"; syslog(LOG_ERR, "SASL: sasl_getprop SASL_AUTHUSER: %s", sasl_errstring(sasl_result, NULL, NULL)); goto reset; } authname = xstrdup((const char *) canon_user); if ((p = strchr(authname, '@'))) *p = '%'; if ((p = strchr(username, '@'))) *p = '%'; referral_host = (char*) xmalloc(strlen(authname)+1+strlen(username)+1+ strlen(mbentry->server)+1); sprintf((char*) referral_host, "%s;%s@%s", authname, username, mbentry->server); free(authname); } else referral_host = xstrdup(mbentry->server); } else { /* We want to set up a connection to the backend for proxying */ const char *statusline = NULL; /* get a new copy of the userid */ free(username); username = xstrdup((const char *) canon_user); backend = backend_connect(NULL, mbentry->server, &sieve_protocol, username, NULL, &statusline, -1); if (!backend) { syslog(LOG_ERR, "couldn't authenticate to backend server"); prot_printf(sieved_out, "NO \"%s\"\r\n", statusline ? statusline : "Authentication to backend server failed"); prot_flush(sieved_out); goto cleanup; } } } else if (actions_setuser(username) != TIMSIEVE_OK) { *errmsg = "internal error"; syslog(LOG_ERR, "error in actions_setuser()"); goto reset; } } /* Yay! authenticated */ if(serverout) { char *inbase64; unsigned int inbase64len; /* convert to base64 */ inbase64 = xmalloc(serveroutlen*2+1); sasl_encode64(serverout, serveroutlen, inbase64, serveroutlen*2+1, &inbase64len); prot_printf(sieved_out, "OK (SASL \"%s\")\r\n", inbase64); free(inbase64); } else { prot_printf(sieved_out, "OK\r\n"); } syslog(LOG_NOTICE, "login: %s %s %s%s %s", sieved_clienthost, username, mech, starttls_done ? "+TLS" : "", "User logged in"); authenticated = 1; prot_setsasl(sieved_in, sieved_saslconn); prot_setsasl(sieved_out, sieved_saslconn); sasl_getprop(sieved_saslconn, SASL_SSF, &val); sasl_ssf = *((sasl_ssf_t *) val); if (sasl_ssf && config_getswitch(IMAPOPT_SIEVE_SASL_SEND_UNSOLICITED_CAPABILITY)) { capabilities(sieved_out, sieved_saslconn, starttls_done, authenticated, sasl_ssf); prot_flush(sieved_out); } /* Create telemetry log */ sieved_logfd = telemetry_log(username, sieved_in, sieved_out, 0); cleanup: /* free memory */ mboxlist_entry_free(&mbentry); free(username); free(clientin); return ret; reset: if(reset_saslconn(&sieved_saslconn, ssf, authid) != SASL_OK) fatal("could not reset the sasl_conn_t after failure", EC_TEMPFAIL); ret = FALSE; goto cleanup; } #ifdef HAVE_SSL static int cmd_starttls(struct protstream *sieved_out, struct protstream *sieved_in) { int result; int *layerp; /* SASL and openssl have different ideas about whether ssf is signed */ layerp = (int *) &ssf; if (starttls_done == 1) { prot_printf(sieved_out, "NO \"TLS already active\"\r\n"); return TIMSIEVE_FAIL; } result=tls_init_serverengine("sieve", 5, /* depth to verify */ 1); /* can client auth? */ if (result == -1) { syslog(LOG_ERR, "error initializing TLS"); prot_printf(sieved_out, "NO \"Error initializing TLS\"\r\n"); return TIMSIEVE_FAIL; } prot_printf(sieved_out, "OK \"Begin TLS negotiation now\"\r\n"); /* must flush our buffers before starting tls */ prot_flush(sieved_out); result=tls_start_servertls(0, /* read */ 1, /* write */ sieved_timeout, layerp, &authid, &tls_conn); /* if error */ if (result==-1) { prot_printf(sieved_out, "NO \"Starttls failed\"\r\n"); syslog(LOG_NOTICE, "STARTTLS failed: %s", sieved_clienthost); return TIMSIEVE_FAIL; } /* tell SASL about the negotiated layer */ result = sasl_setprop(sieved_saslconn, SASL_SSF_EXTERNAL, &ssf); if (result != SASL_OK) { fatal("sasl_setprop() failed: cmd_starttls()", EC_TEMPFAIL); } result = sasl_setprop(sieved_saslconn, SASL_AUTH_EXTERNAL, authid); if (result != SASL_OK) { fatal("sasl_setprop() failed: cmd_starttls()", EC_TEMPFAIL); } /* tell the prot layer about our new layers */ prot_settls(sieved_in, tls_conn); prot_settls(sieved_out, tls_conn); starttls_done = 1; sieved_tls_required = 0; return capabilities(sieved_out, sieved_saslconn, starttls_done, authenticated, sasl_ssf); } #else static int cmd_starttls(struct protstream *sieved_out, struct protstream *sieved_in) { fatal("cmd_starttls() called, but no OpenSSL", EC_SOFTWARE); } #endif /* HAVE_SSL */ cyrus-imapd-2.5.10/timsieved/timsieved.c0000644000175000017500000002314113001236020015067 00000000000000/* timsieved.c -- main file for timsieved (sieve script accepting program) * Tim Martin * 9/21/99 * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #ifdef HAVE_CONFIG_H #include #endif #include #include #include #include #include #include /* yay! sasl */ #include #include #include #include #include #include #include #include #include #include "auth.h" #include "exitcodes.h" #include "libconfig.h" #include "xmalloc.h" #include "imap/backend.h" #include "imap/global.h" #include "imap/mboxlist.h" #include "imap/proxy.h" #include "imap/sync_log.h" #include "timsieved/actions.h" #include "timsieved/codes.h" #include "timsieved/parser.h" #include "timsieved/scripttest.h" #include "timsieved/lex.h" /* global state */ const int config_need_data = 0; int sieved_tls_required = 0; sieve_interp_t *interp = NULL; static struct { char *ipremoteport; char *iplocalport; } saslprops = {NULL,NULL}; sasl_conn_t *sieved_saslconn; /* the sasl connection context */ static struct auth_state *sieved_authstate = 0; int sieved_timeout; struct protstream *sieved_out; struct protstream *sieved_in; int sieved_logfd = -1; const char *sieved_clienthost = "[local]"; int sieved_userisadmin; int sieved_domainfromip = 0; /* the sasl proxy policy context */ static struct proxy_context sieved_proxyctx = { 1, 1, &sieved_authstate, &sieved_userisadmin, NULL }; /* PROXY stuff */ struct backend *backend = NULL; static void bitpipe(void); /* end PROXY stuff */ /* * Cleanly shut down and exit */ void shut_down(int code) __attribute__ ((noreturn)); void shut_down(int code) { /* free interpreter */ if (interp) sieve_interp_free(&interp); /* close backend connection */ if (backend) { backend_disconnect(backend); free(backend); } /* close mailboxes */ mboxlist_close(); mboxlist_done(); /* cleanup */ if (sieved_out) { prot_flush(sieved_out); prot_free(sieved_out); } if (sieved_in) prot_free(sieved_in); if (sieved_logfd != -1) close(sieved_logfd); #ifdef HAVE_SSL tls_shutdown_serverengine(); #endif cyrus_done(); cyrus_reset_stdio(); /* done */ exit(code); } static void cmdloop(void) { int ret = FALSE; if (chdir("/tmp/")) { syslog(LOG_ERR, "Failed to chdir to /tmp/"); ret = TRUE; /* exit immediately */ } capabilities(sieved_out, sieved_saslconn, 0, 0, 0); /* initialize lexer */ lex_init(); while (ret != TRUE) { if (backend) { /* create a pipe from client to backend */ bitpipe(); /* pipe has been closed */ return; } ret = parser(sieved_out, sieved_in); } sync_log_done(); /* done */ shut_down(0); } EXPORTED void fatal(const char *s, int code) { static int recurse_code = 0; if (recurse_code) { /* We were called recursively. Just give up */ exit(recurse_code); } recurse_code = code; prot_printf(sieved_out, "NO Fatal error: %s\r\n", s); prot_flush(sieved_out); shut_down(EC_TEMPFAIL); } static struct sasl_callback mysasl_cb[] = { { SASL_CB_GETOPT, (mysasl_cb_ft *) &mysasl_config, NULL }, { SASL_CB_PROXY_POLICY, (mysasl_cb_ft *) &mysasl_proxy_policy, (void*) &sieved_proxyctx }, { SASL_CB_CANON_USER, (mysasl_cb_ft *) &mysasl_canon_user, (void*) &sieved_domainfromip }, { SASL_CB_LIST_END, NULL, NULL } }; EXPORTED int service_init(int argc __attribute__((unused)), char **argv __attribute__((unused)), char **envp __attribute__((unused))) { global_sasl_init(1, 1, mysasl_cb); /* open mailboxes */ mboxlist_init(0); mboxlist_open(NULL); if (build_sieve_interp() != TIMSIEVE_OK) shut_down(EX_SOFTWARE); return 0; } /* Called by service API to shut down the service */ EXPORTED void service_abort(int error) { shut_down(error); } EXPORTED int service_main(int argc __attribute__((unused)), char **argv __attribute__((unused)), char **envp __attribute__((unused))) { const char *remoteip, *localip; sasl_security_properties_t *secprops = NULL; sync_log_init(); /* set up the prot streams */ sieved_in = prot_new(0, 0); sieved_out = prot_new(1, 1); sieved_timeout = config_getint(IMAPOPT_TIMEOUT); if (sieved_timeout < 10) sieved_timeout = 10; sieved_timeout *= 60; prot_settimeout(sieved_in, sieved_timeout); prot_setflushonread(sieved_in, sieved_out); signal(SIGPIPE, SIG_IGN); if (geteuid() == 0) fatal("must run as the Cyrus user", -6); /* Find out name of client host */ sieved_clienthost = get_clienthost(0, &localip, &remoteip); /* other params should be filled in */ if (sasl_server_new(SIEVE_SERVICE_NAME, config_servername, NULL, NULL, NULL, NULL, SASL_SUCCESS_DATA, &sieved_saslconn) != SASL_OK) fatal("SASL failed initializing: sasl_server_new()", -1); if (remoteip) { sasl_setprop(sieved_saslconn, SASL_IPREMOTEPORT, remoteip); saslprops.ipremoteport = xstrdup(remoteip); } if (localip) { sasl_setprop(sieved_saslconn, SASL_IPLOCALPORT, localip); saslprops.iplocalport = xstrdup(localip); } /* will always return something valid */ secprops = mysasl_secprops(0); sasl_setprop(sieved_saslconn, SASL_SEC_PROPS, secprops); if (actions_init() != TIMSIEVE_OK) fatal("Error initializing actions",-1); sieved_tls_required = config_getswitch(IMAPOPT_TLS_REQUIRED); cmdloop(); /* never reaches */ exit(EC_SOFTWARE); } /* Reset the given sasl_conn_t to a sane state */ int reset_saslconn(sasl_conn_t **conn, sasl_ssf_t ssf, char *authid) { int ret = 0; sasl_security_properties_t *secprops = NULL; sasl_dispose(conn); /* do initialization typical of service_main */ ret = sasl_server_new(SIEVE_SERVICE_NAME, config_servername, NULL, NULL, NULL, NULL, SASL_SUCCESS_DATA, conn); if(ret != SASL_OK) return ret; if(saslprops.ipremoteport) ret = sasl_setprop(*conn, SASL_IPREMOTEPORT, saslprops.ipremoteport); if(ret != SASL_OK) return ret; if(saslprops.iplocalport) ret = sasl_setprop(*conn, SASL_IPLOCALPORT, saslprops.iplocalport); if(ret != SASL_OK) return ret; secprops = mysasl_secprops(0); ret = sasl_setprop(*conn, SASL_SEC_PROPS, secprops); if(ret != SASL_OK) return ret; /* end of service_main initialization excepting SSF */ /* If we have TLS/SSL info, set it */ if(ssf) { ret = sasl_setprop(*conn, SASL_SSF_EXTERNAL, &ssf); if(ret != SASL_OK) return ret; } if(authid) { ret = sasl_setprop(*conn, SASL_AUTH_EXTERNAL, authid); if(ret != SASL_OK) return ret; } /* End TLS/SSL Info */ return SASL_OK; } /* we've authenticated the client, we've connected to the backend. now it's all up to them */ static void bitpipe(void) { struct protgroup *protin = protgroup_new(2); int shutdown = 0; char buf[4096]; protgroup_insert(protin, sieved_in); protgroup_insert(protin, backend->in); do { /* Flush any buffered output */ prot_flush(sieved_out); prot_flush(backend->out); /* check for shutdown file */ if (shutdown_file(buf, sizeof(buf))) { shutdown = 1; goto done; } } while (!proxy_check_input(protin, sieved_in, sieved_out, backend->in, backend->out, 0)); done: /* ok, we're done. */ protgroup_free(protin); if (shutdown) prot_printf(sieved_out, "NO \"%s\"\r\n", buf); return; } cyrus-imapd-2.5.10/timsieved/TODO0000644000175000017500000000023613001236020013422 00000000000000does authenticating leak memory? (mechanism name parameter in yacc not freed?) - leg 9/29/99 document the sieve quotas in: sieve.html (yet to be written) cyrus-imapd-2.5.10/timsieved/lex.h0000644000175000017500000000547212772415051013723 00000000000000/* lex.h -- lexer for timsieved * Tim Martin * 9/21/99 * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #ifndef _LEX_H_ #define _LEX_H_ #include "prot.h" #include "util.h" #define LEXER_STATE_RECOVER 61 #define LEXER_STATE_RECOVER_CR 62 #define LEXER_STATE_CR 63 #define LEXER_STATE_QSTR 64 #define LEXER_STATE_LITERAL 65 #define LEXER_STATE_NUMBER 66 #define LEXER_STATE_NORMAL 67 #define LEXER_STATE_ATOM 68 /* possible tokens */ #define SPACE 32 /* these must be above 255 */ #define EOL 300 #define STRING 301 #define NUMBER 302 #define AUTHENTICATE 400 #define LOGOUT 401 #define GETSCRIPT 402 #define PUTSCRIPT 403 #define SETACTIVE 404 #define LISTSCRIPTS 405 #define DELETESCRIPT 406 #define CAPABILITY 407 #define HAVESPACE 408 #define STARTTLS 409 #define NOOP 410 #define UNAUTHENTICATE 411 #define CHECKSCRIPT 412 #define RENAMESCRIPT 413 int lex_init(void); int timlex(struct buf *outstr, unsigned long *outnum, struct protstream *stream); void lex_setrecovering(void); #endif cyrus-imapd-2.5.10/timsieved/scripttest.h0000644000175000017500000000412213001236020015305 00000000000000/* scripttest.h -- test whether the sieve script is valid * Tim Martin * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #ifndef INCLUDE_SCRIPTTEST_H_ #define INCLUDE_SCRIPTTEST_H_ #include "sieve/sieve_interface.h" extern sieve_interp_t *interp; int build_sieve_interp(void); int is_script_parsable(FILE *f, char **errstr, sieve_script_t **ret); #endif cyrus-imapd-2.5.10/ptclient/0000755000175000017500000000000013001246664012661 500000000000000cyrus-imapd-2.5.10/ptclient/README0000644000175000017500000000054612772415051013470 00000000000000This directory contains support programs for various protection database authorization modules (ptloader for AFS PTS groups, and LDAP). This code links against the rest of the cyrus libraries. The files to care about: ptloader: the AFS pts server loader service ptexpire: program to expire pts entries on command ptdump: program to dump the current cache cyrus-imapd-2.5.10/ptclient/ldap.c0000644000175000017500000012712713001236020013660 00000000000000/* ldap.c - LDAP Backend to ptloader * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include #include #include "ptloader.h" #include "exitcodes.h" #include "util.h" #include "assert.h" #ifdef HAVE_LDAP #include #include #include #include #include #include #include #include #include #include #include #include /* Functions like ldap_bind() have been deprecated in OpenLDAP 2.3 */ #define LDAP_DEPRECATED 1 #include #include /* libimap */ #include "imap/global.h" /* libconfig */ #include "libconfig.h" /* libcyrus */ #include "auth_pts.h" #include "strhash.h" #include "xmalloc.h" #include "xstrlcat.h" /* xxx this just uses the UNIX canonicalization semantics, which is * most likely wrong */ /* Map of which characters are allowed by auth_canonifyid. * Key: 0 -> not allowed (special, ctrl, or would confuse Unix or imapd) * 1 -> allowed, but requires an alpha somewhere else in the string * 2 -> allowed, and is an alpha * * At least one character must be an alpha. * * This may not be restrictive enough. * Here are the reasons for the restrictions: * * & forbidden because of MUTF-7. (This could be fixed.) * : forbidden because it's special in /etc/passwd * / forbidden because it can't be used in a mailbox name * * % forbidden because they're IMAP magic in the LIST/LSUB commands * ? it just scares me * ctrl chars, DEL * can't send them as IMAP characters in plain folder names, I think * 80-FF forbidden because you can't send them in IMAP anyway * (and they're forbidden as folder names). (This could be fixed.) * * + and - are *allowed* although '+' is probably used for userid+detail * subaddressing and qmail users use '-' for subaddressing. * * Identifiers don't require a digit, really, so that should probably be * relaxed, too. */ static char allowedchars[256] = { /* 0 1 2 3 4 5 6 7 8 9 A B C D E F */ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, /* 00-0F */ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, /* 10-1F */ 1, 1, 1, 1, 1, 0, 0, 1, 1, 1, 0, 1, 1, 1, 1, 0, /* 20-2F */ 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 1, 1, 1, 1, 0, /* 30-3F */ 1, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, /* 40-4F */ 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 1, 1, 1, 1, 1, /* 50-5F */ 1, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, /* 60-6F */ 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 1, 1, 1, 1, 0, /* 70-7F */ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }; typedef struct _ptsm { const char *uri; int version; struct timeval timeout; int size_limit; int time_limit; int deref; int referrals; int restart; int scope; const char *base; int sasl; const char *id; const char *bind_dn; const char *password; const char *authz; const char *mech; const char *realm; const char *filter; const char *sasl_secprops; int start_tls; int tls_check_peer; const char *tls_cacert_file; const char *tls_cacert_dir; const char *tls_ciphers; const char *tls_cert; const char *tls_key; int member_method; const char *user_attribute; const char *member_attribute; const char *member_filter; const char *member_base; int member_scope; const char *group_filter; const char *group_base; int group_scope; /* Used for domain name space -> root dn discovery */ const char *domain_base_dn; const char *domain_filter; const char *domain_name_attribute; int domain_scope; const char *domain_result_attribute; LDAP *ld; } t_ptsm; #define PTSM_OK 0 #define PTSM_FAIL -1 #define PTSM_NOMEM -2 #define PTSM_RETRY -3 #define PTSM_MEMBER_METHOD_ATTRIBUTE 0 #define PTSM_MEMBER_METHOD_FILTER 1 #define ISSET(x) ((x != NULL) && (*(x) != '\0')) #define EMPTY(x) ((x == NULL) || (*(x) == '\0')) static t_ptsm *ptsm = NULL; static int ptsmodule_interact( LDAP *ld __attribute__((unused)), unsigned flags __attribute__((unused)), void *def, void *inter) { sasl_interact_t *in = inter; const char *p; t_ptsm *ptsmdef = def; for (;in->id != SASL_CB_LIST_END;in++) { p = NULL; switch(in->id) { case SASL_CB_AUTHNAME: if (ISSET(ptsmdef->id)) p = ptsmdef->id; break; case SASL_CB_USER: if (ISSET(ptsmdef->authz)) p = ptsmdef->authz; break; case SASL_CB_GETREALM: if (ISSET(ptsmdef->realm)) p = ptsmdef->realm; break; case SASL_CB_PASS: if (ISSET(ptsmdef->password)) p = ptsmdef->password; break; } in->result = p ? p : ""; in->len = strlen(in->result); } return LDAP_SUCCESS; } /* * Convert 'identifier' into canonical form. * Returns a pointer to a static buffer containing the canonical form * or NULL if 'identifier' is invalid. * * XXX If any of the characters marked with 0 are valid and are cropping up, * the right thing to do is probably to canonicalize the identifier to two * representations: one for getpwent calls and one for folder names. The * latter canonicalizes to a MUTF7 representation. */ static char *ptsmodule_canonifyid(const char *identifier, size_t len) { static char retbuf[81]; char sawalpha; char *p; int username_tolower = 0; int i = 0; if(!len) len = strlen(identifier); if(len >= sizeof(retbuf)) return NULL; memcpy(retbuf, identifier, len); retbuf[len] = '\0'; if (!strncmp(retbuf, "group:", 6)) i = 6; /* Copy the string and look up values in the allowedchars array above. * If we see any we don't like, reject the string. * Lowercase usernames if requested. */ username_tolower = config_getswitch(IMAPOPT_USERNAME_TOLOWER); sawalpha = 0; for(p = retbuf+i; *p; p++) { if (username_tolower && Uisupper(*p)) *p = tolower((unsigned char)*p); switch (allowedchars[*(unsigned char*) p]) { case 0: return NULL; case 2: sawalpha = 1; /* FALL THROUGH */ default: ; } } if (!sawalpha) return NULL; /* has to be one alpha char */ return retbuf; } static int ptsmodule_connect(void) { int rc = 0; if (ptsm == NULL) // Sanity Check return PTSM_FAIL; if (ptsm->ld != NULL) return PTSM_OK; if (ISSET(ptsm->tls_cacert_file)) { rc = ldap_set_option (NULL, LDAP_OPT_X_TLS_CACERTFILE, ptsm->tls_cacert_file); if (rc != LDAP_SUCCESS) { syslog (LOG_WARNING, "Unable to set LDAP_OPT_X_TLS_CACERTFILE (%s).", ldap_err2string (rc)); } } if (ISSET(ptsm->tls_cacert_dir)) { rc = ldap_set_option (NULL, LDAP_OPT_X_TLS_CACERTDIR, ptsm->tls_cacert_dir); if (rc != LDAP_SUCCESS) { syslog (LOG_WARNING, "Unable to set LDAP_OPT_X_TLS_CACERTDIR (%s).", ldap_err2string (rc)); } } if (ptsm->tls_check_peer != 0) { rc = ldap_set_option(NULL, LDAP_OPT_X_TLS_REQUIRE_CERT, &ptsm->tls_check_peer); if (rc != LDAP_SUCCESS) { syslog (LOG_WARNING, "Unable to set LDAP_OPT_X_TLS_REQUIRE_CERT (%s).", ldap_err2string (rc)); } } if (ISSET(ptsm->tls_ciphers)) { /* set cipher suite, certificate and private key: */ rc = ldap_set_option(NULL, LDAP_OPT_X_TLS_CIPHER_SUITE, ptsm->tls_ciphers); if (rc != LDAP_SUCCESS) { syslog (LOG_WARNING, "Unable to set LDAP_OPT_X_TLS_CIPHER_SUITE (%s).", ldap_err2string (rc)); } } if (ISSET(ptsm->tls_cert)) { rc = ldap_set_option(NULL, LDAP_OPT_X_TLS_CERTFILE, ptsm->tls_cert); if (rc != LDAP_SUCCESS) { syslog (LOG_WARNING, "Unable to set LDAP_OPT_X_TLS_CERTFILE (%s).", ldap_err2string (rc)); } } if (ISSET(ptsm->tls_key)) { rc = ldap_set_option(NULL, LDAP_OPT_X_TLS_KEYFILE, ptsm->tls_key); if (rc != LDAP_SUCCESS) { syslog (LOG_WARNING, "Unable to set LDAP_OPT_X_TLS_KEYFILE (%s).", ldap_err2string (rc)); } } rc = ldap_initialize(&ptsm->ld, ptsm->uri); if (rc != LDAP_SUCCESS) { syslog(LOG_ERR, "ldap_initialize failed (%s)", ptsm->uri); return PTSM_FAIL; } rc = ldap_set_option(ptsm->ld, LDAP_OPT_PROTOCOL_VERSION, &(ptsm->version)); if (rc != LDAP_OPT_SUCCESS) { if (ptsm->sasl || ptsm->start_tls) { syslog(LOG_ERR, "Failed to set LDAP_OPT_PROTOCOL_VERSION %d, required for ldap_start_tls and ldap_sasl.", ptsm->version); ldap_unbind(ptsm->ld); ptsm->ld = NULL; return PTSM_FAIL; } else syslog(LOG_WARNING, "Unable to set LDAP_OPT_PROTOCOL_VERSION %d.", ptsm->version); ptsm->version = LDAP_VERSION2; } rc = ldap_set_option(ptsm->ld, LDAP_OPT_NETWORK_TIMEOUT, &(ptsm->timeout)); if (rc != LDAP_OPT_SUCCESS) { syslog(LOG_WARNING, "Unable to set LDAP_OPT_NETWORK_TIMEOUT %ld.%06d.", (long)ptsm->timeout.tv_sec, (int)ptsm->timeout.tv_usec); } rc = ldap_set_option(ptsm->ld, LDAP_OPT_TIMELIMIT, &(ptsm->time_limit)); if (rc != LDAP_OPT_SUCCESS) { syslog(LOG_WARNING, "Unable to set LDAP_OPT_TIMELIMIT %d.", ptsm->time_limit); } rc = ldap_set_option(ptsm->ld, LDAP_OPT_DEREF, &(ptsm->deref)); if (rc != LDAP_OPT_SUCCESS) { syslog(LOG_WARNING, "Unable to set LDAP_OPT_DEREF %d.", ptsm->deref); } rc = ldap_set_option(ptsm->ld, LDAP_OPT_REFERRALS, ptsm->referrals ? LDAP_OPT_ON : LDAP_OPT_OFF); if (rc != LDAP_OPT_SUCCESS) { syslog(LOG_WARNING, "Unable to set LDAP_OPT_REFERRALS."); } rc = ldap_set_option(ptsm->ld, LDAP_OPT_SIZELIMIT, &(ptsm->size_limit)); if (rc != LDAP_OPT_SUCCESS) syslog(LOG_WARNING, "Unable to set LDAP_OPT_SIZELIMIT %d.", ptsm->size_limit); rc = ldap_set_option(ptsm->ld, LDAP_OPT_RESTART, ptsm->restart ? LDAP_OPT_ON : LDAP_OPT_OFF); if (rc != LDAP_OPT_SUCCESS) { syslog(LOG_WARNING, "Unable to set LDAP_OPT_RESTART."); } if (ptsm->start_tls) { rc = ldap_start_tls_s(ptsm->ld, NULL, NULL); if (rc != LDAP_SUCCESS) { syslog(LOG_ERR, "start tls failed (%s).", ldap_err2string(rc)); ldap_unbind(ptsm->ld); ptsm->ld = NULL; return PTSM_FAIL; } } if (ptsm->sasl) { if (EMPTY(ptsm->mech)) ldap_get_option(ptsm->ld, LDAP_OPT_X_SASL_MECH, &(ptsm->mech)); if (EMPTY(ptsm->realm)) ldap_get_option(ptsm->ld, LDAP_OPT_X_SASL_REALM, &(ptsm->realm)); if (ISSET(ptsm->sasl_secprops)) { rc = ldap_set_option(ptsm->ld, LDAP_OPT_X_SASL_SECPROPS, (void *) ptsm->sasl_secprops); if( rc != LDAP_OPT_SUCCESS ) { syslog(LOG_ERR, "Unable to set LDAP_OPT_X_SASL_SECPROPS."); ldap_unbind(ptsm->ld); ptsm->ld = NULL; return PTSM_FAIL; } } rc = ldap_sasl_interactive_bind_s( ptsm->ld, ptsm->bind_dn, ptsm->mech, NULL, NULL, LDAP_SASL_QUIET, ptsmodule_interact, ptsm); } else rc = ldap_simple_bind_s(ptsm->ld, ptsm->bind_dn, ptsm->password); if (rc != LDAP_SUCCESS) { syslog(LOG_ERR, (ptsm->sasl ? "ldap_sasl_interactive_bind() failed %d (%s)." : "ldap_simple_bind() failed %d (%s)."), rc, ldap_err2string(rc)); ldap_unbind(ptsm->ld); ptsm->ld = NULL; return (rc == LDAP_SERVER_DOWN ? PTSM_RETRY : PTSM_FAIL); } return PTSM_OK; } /* API */ static void myinit(void) { const char *p = NULL; if (ptsm) return; // Already configured ptsm = xmalloc(sizeof(t_ptsm)); if (ptsm == NULL) { fatal("xmalloc() failed", EC_CONFIG); } ptsm->uri = (config_getstring(IMAPOPT_LDAP_URI) ? config_getstring(IMAPOPT_LDAP_URI) : config_getstring(IMAPOPT_LDAP_SERVERS)); ptsm->version = (config_getint(IMAPOPT_LDAP_VERSION) == 2 ? LDAP_VERSION2 : LDAP_VERSION3); ptsm->timeout.tv_sec = config_getint(IMAPOPT_LDAP_TIMEOUT); ptsm->timeout.tv_usec = 0; ptsm->restart = config_getswitch(IMAPOPT_LDAP_RESTART); p = config_getstring(IMAPOPT_LDAP_DEREF); if (!strcasecmp(p, "search")) { ptsm->deref = LDAP_DEREF_SEARCHING; } else if (!strcasecmp(p, "find")) { ptsm->deref = LDAP_DEREF_FINDING; } else if (!strcasecmp(p, "always")) { ptsm->deref = LDAP_DEREF_ALWAYS; } else { ptsm->deref = LDAP_DEREF_NEVER; } ptsm->referrals = config_getswitch(IMAPOPT_LDAP_REFERRALS); ptsm->size_limit = config_getint(IMAPOPT_LDAP_SIZE_LIMIT); ptsm->time_limit = config_getint(IMAPOPT_LDAP_TIME_LIMIT); p = config_getstring(IMAPOPT_LDAP_SCOPE); if (!strcasecmp(p, "one")) { ptsm->scope = LDAP_SCOPE_ONELEVEL; } else if (!strcasecmp(p, "base")) { ptsm->scope = LDAP_SCOPE_BASE; } else { ptsm->scope = LDAP_SCOPE_SUBTREE; } ptsm->bind_dn = config_getstring(IMAPOPT_LDAP_BIND_DN); ptsm->sasl = config_getswitch(IMAPOPT_LDAP_SASL); ptsm->id = (config_getstring(IMAPOPT_LDAP_ID) ? config_getstring(IMAPOPT_LDAP_ID) : config_getstring(IMAPOPT_LDAP_SASL_AUTHC)); ptsm->authz = (config_getstring(IMAPOPT_LDAP_AUTHZ) ? config_getstring(IMAPOPT_LDAP_AUTHZ) : config_getstring(IMAPOPT_LDAP_SASL_AUTHZ)); ptsm->mech = (config_getstring(IMAPOPT_LDAP_MECH) ? config_getstring(IMAPOPT_LDAP_MECH) : config_getstring(IMAPOPT_LDAP_SASL_MECH)); ptsm->realm = (config_getstring(IMAPOPT_LDAP_REALM) ? config_getstring(IMAPOPT_LDAP_REALM) : config_getstring(IMAPOPT_LDAP_SASL_REALM)); ptsm->password = (config_getstring(IMAPOPT_LDAP_PASSWORD) ? config_getstring(IMAPOPT_LDAP_PASSWORD) : config_getstring(IMAPOPT_LDAP_SASL_PASSWORD)); ptsm->start_tls = config_getswitch(IMAPOPT_LDAP_START_TLS); ptsm->tls_check_peer = config_getswitch(IMAPOPT_LDAP_VERIFY_PEER); ptsm->tls_cacert_file = config_getstring(IMAPOPT_LDAP_CA_FILE); ptsm->tls_cacert_dir = config_getstring(IMAPOPT_LDAP_CA_DIR); ptsm->tls_ciphers = config_getstring(IMAPOPT_LDAP_CIPHERS); ptsm->tls_cert = config_getstring(IMAPOPT_LDAP_CLIENT_CERT); ptsm->tls_key = config_getstring(IMAPOPT_LDAP_CLIENT_KEY); p = config_getstring(IMAPOPT_LDAP_MEMBER_METHOD); if (!strcasecmp(p, "filter")) { ptsm->member_method = PTSM_MEMBER_METHOD_FILTER; } else { ptsm->member_method = PTSM_MEMBER_METHOD_ATTRIBUTE; } p = config_getstring(IMAPOPT_LDAP_MEMBER_SCOPE); if (!strcasecmp(p, "one")) { ptsm->member_scope = LDAP_SCOPE_ONELEVEL; } else if (!strcasecmp(p, "base")) { ptsm->member_scope = LDAP_SCOPE_BASE; } else { ptsm->member_scope = LDAP_SCOPE_SUBTREE; } ptsm->member_filter = config_getstring(IMAPOPT_LDAP_MEMBER_FILTER); ptsm->member_base = config_getstring(IMAPOPT_LDAP_MEMBER_BASE); ptsm->member_attribute = (config_getstring(IMAPOPT_LDAP_MEMBER_ATTRIBUTE) ? config_getstring(IMAPOPT_LDAP_MEMBER_ATTRIBUTE) : config_getstring(IMAPOPT_LDAP_MEMBER_ATTRIBUTE)); ptsm->user_attribute = (config_getstring(IMAPOPT_LDAP_USER_ATTRIBUTE) ? config_getstring(IMAPOPT_LDAP_USER_ATTRIBUTE) : config_getstring(IMAPOPT_LDAP_USER_ATTRIBUTE)); p = config_getstring(IMAPOPT_LDAP_GROUP_SCOPE); if (!strcasecmp(p, "one")) { ptsm->group_scope = LDAP_SCOPE_ONELEVEL; } else if (!strcasecmp(p, "base")) { ptsm->group_scope = LDAP_SCOPE_BASE; } else { ptsm->group_scope = LDAP_SCOPE_SUBTREE; } ptsm->group_filter = config_getstring(IMAPOPT_LDAP_GROUP_FILTER); ptsm->group_base = config_getstring(IMAPOPT_LDAP_GROUP_BASE); ptsm->filter = config_getstring(IMAPOPT_LDAP_FILTER); ptsm->base = config_getstring(IMAPOPT_LDAP_BASE); if (ptsm->version != LDAP_VERSION3 && (ptsm->sasl || ptsm->start_tls)) ptsm->version = LDAP_VERSION3; ptsm->domain_base_dn = config_getstring(IMAPOPT_LDAP_DOMAIN_BASE_DN); ptsm->domain_filter = config_getstring(IMAPOPT_LDAP_DOMAIN_FILTER); ptsm->domain_name_attribute = config_getstring(IMAPOPT_LDAP_DOMAIN_NAME_ATTRIBUTE); p = config_getstring(IMAPOPT_LDAP_DOMAIN_SCOPE); if (!strcasecmp(p, "one")) { ptsm->domain_scope = LDAP_SCOPE_ONELEVEL; } else if (!strcasecmp(p, "base")) { ptsm->domain_scope = LDAP_SCOPE_BASE; } else { ptsm->domain_scope = LDAP_SCOPE_SUBTREE; } ptsm->domain_result_attribute = config_getstring(IMAPOPT_LDAP_DOMAIN_RESULT_ATTRIBUTE); ptsm->ld = NULL; } /* * Note: calling function must free memory. */ static int ptsmodule_escape( const char *s, const unsigned int n, char **result) { char *buf; char *end, *ptr, *temp; if (n > strlen(s)) // Sanity check, just in case return PTSM_FAIL; buf = xmalloc(n * 5 + 1); if (buf == NULL) { return PTSM_NOMEM; } buf[0] = '\0'; ptr = (char *)s; end = ptr + n; while (((temp = strpbrk(ptr, "*()\\\0"))!=NULL) && (tempptr) strncat(buf, ptr, temp-ptr); switch (*temp) { case '*': strcat(buf, "\\2a"); break; case '(': strcat(buf, "\\28"); break; case ')': strcat(buf, "\\29"); break; case '\\': strcat(buf, "\\5c"); break; case '\0': strcat(buf, "\\00"); break; } ptr=temp+1; } if (ptr nt) { free(s); return PTSM_FAIL; } i = nt - n; s1 = (char *)strtok_r(s, ".", &lasts); while(s1) { if (i == 0) { rc = ptsmodule_escape(s1, strlen(s1), result); free(s); return rc; } s1 = (char *)strtok_r(NULL, ".", &lasts); i--; } free(s); return PTSM_FAIL; } #define PTSM_MAX(a,b) (a>b?a:b) /* * ptsmodule_expand_tokens * Parts with the strings provided. * %% = % * %u = user * %U = user part of %u * %d = domain part of %u if available, othwise same as %r * %R = prepend '@' to domain * %1-9 = domain tokens (%1 = tld, %2 = domain when %d = domain.tld) * %D = user DN * Note: calling function must free memory. */ static int ptsmodule_expand_tokens( const char *pattern, const char *username, const char *dn, char **result) { char *buf; char *end, *ptr, *temp; char *ebuf, *user; char *domain; int rc; /* to permit multiple occurences of username and/or realm in filter */ /* and avoid memory overflow in filter build [eg: (|(uid=%u)(userid=%u)) ] */ int percents, user_len, dn_len, maxparamlength; if (pattern == NULL) { syslog(LOG_ERR, "filter pattern not setup"); return PTSM_FAIL; } /* find the longest param of username and realm, do not worry about domain because it is always shorter then username */ user_len = username ? strlen(username) : 0; dn_len = dn ? strlen(dn) : 0; maxparamlength = PTSM_MAX(user_len+1, dn_len); /* +1 for %R when '@' is prepended */ /* find the number of occurences of percent sign in filter */ for (percents=0, buf=(char *)pattern; *buf; buf++) { if (*buf == '%') percents++; } /* percents * 3 * maxparamlength because we need to account for * an entirely-escaped worst-case-length parameter */ buf = xmalloc(strlen(pattern) + (percents * 3 * maxparamlength) +1); if (buf == NULL) return PTSM_NOMEM; buf[0] = '\0'; ptr = (char *)pattern; end = ptr + strlen(ptr); while ((temp=strchr(ptr,'%')) != NULL) { if ((temp-ptr) > 0) strncat(buf, ptr, temp-ptr); if ((temp+1) >= end) { syslog(LOG_DEBUG, "Incomplete lookup substitution format"); break; } switch (*(temp+1)) { case '%': strncat(buf,temp+1,1); break; case 'u': if (ISSET(username)) { rc = ptsmodule_escape(username, strlen(username), &ebuf); if (rc == PTSM_OK) { strcat(buf,ebuf); free(ebuf); } } else syslog(LOG_DEBUG, "Username not available."); break; case 'U': if (ISSET(username)) { user = strchr(username, '@'); rc = ptsmodule_escape(username, (user ? (unsigned char)(user - username) : strlen(username)), &ebuf); if (rc == PTSM_OK) { strcat(buf,ebuf); free(ebuf); } } else syslog(LOG_DEBUG, "Username not available."); break; case '1': case '2': case '3': case '4': case '5': case '6': case '7': case '8': case '9': if (ISSET(username) && (domain = strchr(username, '@')) && domain[1]!='\0') { rc=ptsmodule_tokenize_domains(domain+1, (int) *(temp+1)-48, &ebuf); if (rc == PTSM_OK) { strcat(buf,ebuf); free(ebuf); } } else syslog(LOG_DEBUG, "Domain tokens not available."); break; case 'R': case 'd': if (ISSET(username) && (domain = strchr(username, '@')) && domain[1]!='\0') { rc=ptsmodule_escape(domain+1, strlen(domain+1), &ebuf); if (rc == PTSM_OK) { if (*(temp+1) == 'R') strcat(buf,"@"); strcat(buf,ebuf); free(ebuf); } break; } break; case 'D': if (ISSET(dn)) { rc = ptsmodule_escape(dn, strlen(dn), &ebuf); if (rc == PTSM_OK) { strcat(buf,ebuf); free(ebuf); } } else syslog(LOG_DEBUG, "dn not available."); break; default: break; } ptr=temp+2; } if (temp= 20125 struct berval *dn = NULL; LDAPControl c; LDAPControl *ctrl[2]; char *authzid; #endif char *base = NULL, *filter = NULL; char *domain = NULL; char domain_filter[1024]; char *attrs[] = {LDAP_NO_ATTRS,NULL}; //do not return all attrs! char *domain_attrs[] = {(char *)ptsm->domain_name_attribute,(char *)ptsm->domain_result_attribute,NULL}; LDAPMessage *res; LDAPMessage *entry; char **vals; /* unused: BerElement *ber; */ *ret = NULL; if (ptsm->ld == NULL) return PTSM_FAIL; #if LDAP_VENDOR_VERSION >= 20125 if (ptsm->sasl) { authzid = xmalloc(size + sizeof("u:")); if (authzid == NULL) return PTSM_NOMEM; strcpy(authzid, "u:"); strcpy(authzid+2, canon_id); c.ldctl_oid = LDAP_CONTROL_PROXY_AUTHZ; c.ldctl_value.bv_val = authzid; c.ldctl_value.bv_len = size + 2; c.ldctl_iscritical = 1; ctrl[0] = &c; ctrl[1] = NULL; rc = ldap_whoami_s(ptsm->ld, &dn, ctrl, NULL); free(authzid); if ( rc != LDAP_SUCCESS || !dn ) { if (rc == LDAP_SERVER_DOWN) { ldap_unbind(ptsm->ld); ptsm->ld = NULL; return PTSM_RETRY; } return PTSM_FAIL; } if ( dn->bv_val && !strncmp(dn->bv_val, "dn:", 3) ) *ret = strdup(dn->bv_val+3); ber_bvfree(dn); } else #endif { rc = ptsmodule_expand_tokens(ptsm->filter, canon_id, NULL, &filter); if (rc != PTSM_OK) return rc; if (ptsm->domain_base_dn && ptsm->domain_base_dn[0] != '\0' && (strrchr(canon_id, '@') != NULL)) { syslog(LOG_DEBUG, "Attempting to get domain for %s from %s", canon_id, ptsm->domain_base_dn); /* Get the base dn to search from domain_base_dn searched on domain_scope with domain_filter */ domain = strrchr(canon_id, '@'); /* Strip the first character which is a '@' */ domain = domain+1; snprintf(domain_filter, sizeof(domain_filter), ptsm->domain_filter, domain); syslog(LOG_DEBUG, "Domain filter: %s", domain_filter); rc = ldap_search_st(ptsm->ld, ptsm->domain_base_dn, ptsm->domain_scope, domain_filter, domain_attrs, 0, &(ptsm->timeout), &res); if (rc != LDAP_SUCCESS) { if (rc == LDAP_SERVER_DOWN) { syslog(LOG_ERR, "LDAP not available: %s", ldap_err2string(rc)); ldap_unbind(ptsm->ld); ptsm->ld = NULL; return PTSM_RETRY; } syslog(LOG_ERR, "LDAP search for domain failed: %s", ldap_err2string(rc)); return PTSM_FAIL; } if (ldap_count_entries(ptsm->ld, res) < 1) { syslog(LOG_ERR, "No domain %s found", domain); return PTSM_FAIL; } else if (ldap_count_entries(ptsm->ld, res) > 1) { syslog(LOG_ERR, "Multiple domains %s found", domain); return PTSM_FAIL; } else { if ((entry = ldap_first_entry(ptsm->ld, res)) != NULL) { if ((vals = ldap_get_values(ptsm->ld, entry, ptsm->domain_result_attribute)) != NULL) { syslog(LOG_DEBUG, "Root DN for domain %s is %s", domain, vals[0]); ptsm->base = vals[0]; rc = PTSM_OK; } else if ((vals = ldap_get_values(ptsm->ld, entry, ptsm->domain_name_attribute)) != NULL) { syslog(LOG_DEBUG, "Domain %s is an alias domain for parent domain %s", domain, vals[0]); rc = ptsmodule_standard_root_dn(vals[0], &ptsm->base); } else { rc = ptsmodule_standard_root_dn(domain, &ptsm->base); } if (rc != PTSM_OK) { return rc; } else { base = xstrdup(ptsm->base); syslog(LOG_DEBUG, "Continuing with ptsm->base: %s", ptsm->base); } } } } else { rc = ptsmodule_expand_tokens(ptsm->base, canon_id, NULL, &base); if (rc != PTSM_OK) return rc; } rc = ldap_search_st(ptsm->ld, base, ptsm->scope, filter, attrs, 0, &(ptsm->timeout), &res); if (rc != LDAP_SUCCESS) { syslog(LOG_DEBUG, "Searching %s with %s failed", base, base); free(filter); free(base); if (rc == LDAP_SERVER_DOWN) { ldap_unbind(ptsm->ld); ptsm->ld = NULL; return PTSM_RETRY; } return PTSM_FAIL; } free(filter); free(base); /* * We don't want to return the *first* entry found, we want to return * the *only* entry found. */ if (ldap_count_entries(ptsm->ld, res) < 1) { syslog(LOG_ERR, "No entries found"); } else if (ldap_count_entries(ptsm->ld, res) > 1) { syslog(LOG_ERR, "Multiple entries found: %d", ldap_count_entries(ptsm->ld, res)); } else { /* if ( ldap_count_entries(ptsm->ld, res) == 1 ) { */ if ((entry = ldap_first_entry(ptsm->ld, res)) != NULL) { *ret = ldap_get_dn(ptsm->ld, entry); } } ldap_msgfree(res); res = NULL; } return (*ret ? PTSM_OK : PTSM_FAIL); } static int ptsmodule_make_authstate_attribute( const char *canon_id, size_t size, const char **reply, int *dsize, struct auth_state **newstate) { char *dn = NULL; LDAPMessage *res = NULL; LDAPMessage *entry = NULL; char **vals = NULL; char **rdn = NULL; int rc; char *attrs[] = {(char *)ptsm->member_attribute,(char *)ptsm->user_attribute,NULL}; rc = ptsmodule_connect(); if (rc != PTSM_OK) { *reply = "ptsmodule_connect() failed"; return rc; } rc = ptsmodule_get_dn(canon_id, size, &dn); if (rc != PTSM_OK) { *reply = "identifier not found"; goto done; } rc = ldap_search_st(ptsm->ld, dn, LDAP_SCOPE_BASE, "(objectclass=*)", attrs, 0, &(ptsm->timeout), &res); if ( rc != LDAP_SUCCESS ) { *reply = "ldap_search(attribute) failed"; if ( rc == LDAP_SERVER_DOWN ) { ldap_unbind(ptsm->ld); ptsm->ld = NULL; rc = PTSM_RETRY; } else rc = PTSM_FAIL; goto done; } if ((entry = ldap_first_entry(ptsm->ld, res)) != NULL) { int i, numvals; vals = ldap_get_values(ptsm->ld, entry, (char *)ptsm->member_attribute); if (vals != NULL) { numvals = ldap_count_values( vals ); *dsize = sizeof(struct auth_state) + (numvals * sizeof(struct auth_ident)); *newstate = xmalloc(*dsize); if (*newstate == NULL) { *reply = "no memory"; rc = PTSM_FAIL; goto done; } (*newstate)->ngroups = numvals; (*newstate)->userid.id[0] = '\0'; for (i = 0; i < numvals; i++) { unsigned int j; strcpy((*newstate)->groups[i].id, "group:"); rdn = ldap_explode_rdn(vals[i],1); for (j = 0; j < strlen(rdn[0]); j++) { if (Uisupper(rdn[0][j])) rdn[0][j]=tolower(rdn[0][j]); } strlcat((*newstate)->groups[i].id, rdn[0], sizeof((*newstate)->groups[i].id)); (*newstate)->groups[i].hash = strhash((*newstate)->groups[i].id); } ldap_value_free(rdn); ldap_value_free(vals); vals = NULL; } if ((char *)ptsm->user_attribute) { vals = ldap_get_values(ptsm->ld, entry, (char *)ptsm->user_attribute); if (vals != NULL) { numvals = ldap_count_values( vals ); if (numvals==1) { if(!*newstate) { *dsize = sizeof(struct auth_state); *newstate = xmalloc(*dsize); if (*newstate == NULL) { *reply = "no memory"; rc = PTSM_FAIL; goto done; } (*newstate)->ngroups = 0; } size=strlen(vals[0]); strcpy((*newstate)->userid.id, ptsmodule_canonifyid(vals[0],size)); (*newstate)->userid.hash = strhash((*newstate)->userid.id); } ldap_value_free(vals); vals = NULL; } } } if(!*newstate) { *dsize = sizeof(struct auth_state); *newstate = xmalloc(*dsize); if (*newstate == NULL) { *reply = "no memory"; rc = PTSM_FAIL; goto done; } (*newstate)->ngroups = 0; (*newstate)->userid.id[0] = '\0'; } /* fill in the rest of our new state structure */ if ((*newstate)->userid.id[0]=='\0') { strcpy((*newstate)->userid.id, canon_id); (*newstate)->userid.hash = strhash(canon_id); } (*newstate)->mark = time(0); rc = PTSM_OK; done:; if (res) ldap_msgfree(res); if (vals) ldap_value_free(vals); if (dn) free(dn); return rc; } static int ptsmodule_make_authstate_filter( const char *canon_id, size_t size, const char **reply, int *dsize, struct auth_state **newstate) { char *base = NULL, *filter = NULL; int rc; int i; int n; LDAPMessage *res = NULL; LDAPMessage *entry = NULL; char **vals = NULL; char *attrs[] = {(char *)ptsm->member_attribute,NULL}; char *dn = NULL; rc = ptsmodule_connect(); if (rc != PTSM_OK) { *reply = "ptsmodule_connect() failed"; return rc; } rc = ptsmodule_get_dn(canon_id, size, &dn); if (rc != PTSM_OK) { *reply = "identifier not found"; return rc; } rc = ptsmodule_expand_tokens(ptsm->member_filter, canon_id, dn, &filter); if (rc != PTSM_OK) { *reply = "ptsmodule_expand_tokens() failed for member filter"; goto done; } rc = ptsmodule_expand_tokens(ptsm->member_base, canon_id, dn, &base); if (rc != PTSM_OK) { *reply = "ptsmodule_expand_tokens() failed for member search base"; goto done; } rc = ldap_search_st(ptsm->ld, base, ptsm->member_scope, filter, attrs, 0, &(ptsm->timeout), &res); if (rc != LDAP_SUCCESS) { *reply = "ldap_search(filter) failed"; if (rc == LDAP_SERVER_DOWN) { ldap_unbind(ptsm->ld); ptsm->ld = NULL; rc = PTSM_RETRY; } else rc = PTSM_FAIL; goto done; } n = ldap_count_entries(ptsm->ld, res); if (n < 0) { *reply = "ldap_count_entries() failed"; rc = PTSM_FAIL; goto done; } *dsize = sizeof(struct auth_state) + (n * sizeof(struct auth_ident)); *newstate = xmalloc(*dsize); if (*newstate == NULL) { *reply = "no memory"; rc = PTSM_FAIL; goto done; } (*newstate)->ngroups = n; strcpy((*newstate)->userid.id, canon_id); (*newstate)->userid.hash = strhash(canon_id); (*newstate)->mark = time(0); for (i = 0, entry = ldap_first_entry(ptsm->ld, res); entry != NULL; i++, entry = ldap_next_entry(ptsm->ld, entry)) { vals = ldap_get_values(ptsm->ld, entry, (char *)ptsm->member_attribute); if (vals == NULL) continue; if ( ldap_count_values( vals ) != 1 ) { *reply = "too many values"; rc = PTSM_FAIL; ldap_value_free(vals); vals = NULL; goto done; } strcpy((*newstate)->groups[i].id, "group:"); unsigned int j; for (j =0; j < strlen(vals[0]); j++) { if(Uisupper(vals[0][j])) vals[0][j]=tolower(vals[0][j]); } strlcat((*newstate)->groups[i].id, vals[0], sizeof((*newstate)->groups[i].id)); (*newstate)->groups[i].hash = strhash((*newstate)->groups[i].id); ldap_value_free(vals); vals = NULL; } rc = PTSM_OK; done:; if (res) ldap_msgfree(res); if (dn) free(dn); if (filter) free(filter); if (base) free(base); return rc; } static int ptsmodule_make_authstate_group( const char *canon_id, size_t size __attribute__((unused)), const char **reply, int *dsize, struct auth_state **newstate) { char *base = NULL, *filter = NULL; char *domain = NULL; char domain_filter[1024]; char *domain_attrs[] = {(char *)ptsm->domain_name_attribute,(char *)ptsm->domain_result_attribute,NULL}; int rc; int n; LDAPMessage *res = NULL; LDAPMessage *entry = NULL; char **vals = NULL; char *attrs[] = {NULL}; if (strncmp(canon_id, "group:", 6)) { // Sanity check *reply = "not a group identifier"; return PTSM_FAIL; } rc = ptsmodule_connect(); if (rc != PTSM_OK) { *reply = "ptsmodule_connect() failed"; return rc; } rc = ptsmodule_expand_tokens(ptsm->group_filter, canon_id+6, NULL, &filter); if (rc != PTSM_OK) { *reply = "ptsmodule_expand_tokens() failed for group filter"; goto done; } if (ptsm->domain_base_dn && (strrchr(canon_id, '@') != NULL)) { syslog(LOG_DEBUG, "(groups) Attempting to get domain for %s from %s", canon_id, ptsm->domain_base_dn); /* Get the base dn to search from domain_base_dn searched on domain_scope with domain_filter */ domain = strrchr(canon_id, '@'); syslog(LOG_DEBUG, "(groups) Input domain would be %s", domain); /* Strip the first character which is a '@' AM: assuming ASCII */ domain = domain+1; syslog(LOG_DEBUG, "(groups) Input domain would be %s", domain); snprintf(domain_filter, sizeof(domain_filter), ptsm->domain_filter, domain); syslog(LOG_DEBUG, "(groups) Domain filter: %s", domain_filter); rc = ldap_search_st(ptsm->ld, ptsm->domain_base_dn, ptsm->domain_scope, domain_filter, domain_attrs, 0, &(ptsm->timeout), &res); if (rc != LDAP_SUCCESS) { syslog(LOG_DEBUG, "(groups) Result from domain query not OK"); return rc; } else { syslog(LOG_DEBUG, "(groups) Result from domain query OK"); } if (ldap_count_entries(ptsm->ld, res) < 1) { syslog(LOG_ERR, "(groups) No domain %s found", domain); return PTSM_FAIL; } else if (ldap_count_entries(ptsm->ld, res) > 1) { syslog(LOG_ERR, "(groups) Multiple domains %s found", domain); return PTSM_FAIL; } else { syslog(LOG_DEBUG, "(groups) Domain %s found", domain); if ((entry = ldap_first_entry(ptsm->ld, res)) != NULL) { if ((vals = ldap_get_values(ptsm->ld, entry, ptsm->domain_result_attribute)) != NULL) { ptsm->group_base = vals[0]; rc = PTSM_OK; } else if ((vals = ldap_get_values(ptsm->ld, entry, ptsm->domain_name_attribute)) != NULL) { char *new_domain = xstrdup(vals[0]); syslog(LOG_DEBUG, "(groups) Domain %s is now domain %s", domain, new_domain); rc = ptsmodule_standard_root_dn(new_domain, &ptsm->group_base); free(new_domain); } else { rc = ptsmodule_standard_root_dn(domain, &ptsm->group_base); } if (rc != PTSM_OK) { return rc; } else { base = xstrdup(ptsm->group_base); syslog(LOG_DEBUG, "Continuing with ptsm->group_base: %s", ptsm->group_base); } } } } else { rc = ptsmodule_expand_tokens(ptsm->group_base, canon_id, NULL, &base); if (rc != PTSM_OK) return rc; } syslog(LOG_DEBUG, "(groups) about to search %s for %s", base, filter); rc = ptsmodule_expand_tokens(ptsm->group_base, canon_id+6, NULL, &base); if (rc != PTSM_OK) { *reply = "ptsmodule_expand_tokens() failed for group search base"; goto done; } rc = ldap_search_st(ptsm->ld, base, ptsm->group_scope, filter, attrs, 0, &(ptsm->timeout), &res); if (rc != LDAP_SUCCESS) { *reply = "ldap_search(group) failed"; if (rc == LDAP_SERVER_DOWN) { ldap_unbind(ptsm->ld); ptsm->ld = NULL; rc = PTSM_RETRY; } else rc = PTSM_FAIL; goto done; } n = ldap_count_entries(ptsm->ld, res); if (n != 1) { *reply = "group identifier not found"; rc = PTSM_FAIL; goto done; } *dsize = sizeof(struct auth_state) + (n * sizeof(struct auth_ident)); *newstate = xmalloc(*dsize); if (*newstate == NULL) { *reply = "no memory"; rc = PTSM_FAIL; goto done; } (*newstate)->ngroups = 0; strcpy((*newstate)->userid.id, canon_id); (*newstate)->userid.hash = strhash(canon_id); (*newstate)->mark = time(0); rc = PTSM_OK; done:; if (res) ldap_msgfree(res); if (filter) free(filter); if (base) free(base); return rc; } static struct auth_state *myauthstate( const char *identifier, size_t size, const char **reply, int *dsize) { const char *canon_id; struct auth_state *newstate = NULL; int rc; int retries = 1; canon_id = ptsmodule_canonifyid(identifier, size); if (EMPTY(canon_id)) { *reply = "ptsmodule_canonifyid() failed"; return NULL; } size = strlen(canon_id); retry:; *reply = NULL; if (!strncmp(canon_id, "group:", 6)) rc = ptsmodule_make_authstate_group(canon_id, size, reply, dsize, &newstate); else { if (ptsm->member_method == PTSM_MEMBER_METHOD_ATTRIBUTE) rc = ptsmodule_make_authstate_attribute(canon_id, size, reply, dsize, &newstate); else rc = ptsmodule_make_authstate_filter(canon_id, size, reply, dsize, &newstate); } if (rc == PTSM_RETRY && retries) { retries--; goto retry; } return newstate; } #else /* HAVE_LDAP */ static void myinit(void) { fatal("PTS module (ldap) not compiled in", EC_CONFIG); } static struct auth_state *myauthstate( const char *identifier __attribute__((unused)), size_t size __attribute__((unused)), const char **reply __attribute__((unused)), int *dsize __attribute__((unused))) { fatal("PTS module (ldap) not compiled in", EC_CONFIG); } #endif /* HAVE_LDAP */ struct pts_module pts_ldap = { "ldap", /* name */ &myinit, &myauthstate, }; cyrus-imapd-2.5.10/ptclient/afskrb.c0000644000175000017500000003545713001236020014214 00000000000000/* afskrb.c - AFS PTS Group (Kerberos Canonicalization) Backend to ptloader * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include #include #include #include "ptloader.h" #include "exitcodes.h" #include "util.h" #include "xmalloc.h" #ifdef HAVE_AFSKRB #include #include #include #include #include #include #include #include #include #include #include #ifdef AFSPTS_USE_KRB5 #include #else #include #endif #include "auth_pts.h" #include "libconfig.h" #include "strhash.h" /* AFS stuff */ #include #include #include #include #include #include /* blame transarc i've been told */ #ifndef AFSCONF_CLIENTNAME #include #define AFSCONF_CLIENTNAME AFSDIR_CLIENT_ETC_DIRPATH #endif /* Sanity Check */ #if PTS_DB_KEYSIZE < PR_MAXNAMELEN #error PTS_DB_KEYSIZE is smaller than PR_MAXNAMELEN #endif static const char *localrealms = NULL; int is_local_realm(const char *realm) { const char *val = localrealms; if(!val || !realm) return 0; while (*val) { char buf[1024]; size_t len; char *p; for (p = (char *) val; *p && !Uisspace(*p); p++); len = p-val; if(len >= sizeof(buf)) len = sizeof(buf) - 1; memcpy(buf, val, len); buf[len] = '\0'; if (!strcasecmp(realm,buf)) { return 1; } val = p; while (*val && Uisspace(*val)) val++; } return 0; } #ifdef AFSPTS_USE_KRB5 /* * Convert 'identifier' into canonical form. * Returns a pointer to a static buffer containing the canonical form * or NULL if 'identifier' is invalid. */ static char *afspts_canonifyid(const char *identifier, size_t len) { static char *retbuf = NULL; char *tmp = NULL; krb5_context context; krb5_principal princ, princ_dummy; char *realm; char *realmbegin; int striprealm = 0; char *identifier2; if(retbuf) free(retbuf); retbuf = NULL; if(!identifier) return NULL; if(!len) len = strlen(identifier); if (strcasecmp(identifier, "anonymous") == 0) return "anonymous"; if (strcasecmp(identifier, "anyone") == 0) return "anyone"; identifier2 = strdup(identifier); if (tmp = strchr(identifier2, '+')) { syslog(LOG_DEBUG, "afspts_canonifyid stripping: %s", identifier2); tmp[0] = 0; syslog(LOG_DEBUG, "afspts_canonifyid stripped: %s", identifier2); } if (krb5_init_context(&context)) { syslog(LOG_ERR, "afspts_canonifyid krb5_init_context failed"); return NULL; } if (krb5_parse_name(context,identifier2,&princ)) { krb5_free_context(context); free(identifier2); syslog(LOG_ERR, "afspts_canonifyid krb5_parse_name failed"); return NULL; } free(identifier2); if(config_getswitch(IMAPOPT_PTSKRB5_STRIP_DEFAULT_REALM)) { /* get local realm */ if (krb5_get_default_realm(context,&realm)) { krb5_free_principal(context,princ); krb5_free_context(context); syslog(LOG_ERR, "afspts_canonifyid krb5_get_default_realm failed"); return NULL; } /* build dummy princ to compare realms */ if (krb5_build_principal(context,&princ_dummy, strlen(realm),realm,"dummy",0)) { krb5_free_principal(context,princ); krb5_free_context(context); free(realm); syslog(LOG_ERR, "afspts_canonifyid krb5_build_principal failed"); return NULL; } /* is this principal local ? */ if (krb5_realm_compare(context,princ,princ_dummy)) { striprealm = 1; } /* done w/ dummy princ free it & realm */ krb5_free_principal(context,princ_dummy); free(realm); } if (config_getswitch(IMAPOPT_PTSKRB5_CONVERT524)) { char nbuf[64], ibuf[64], rbuf[64]; if (krb5_524_conv_principal(context, princ, nbuf, ibuf, rbuf)) { krb5_free_principal(context,princ); krb5_free_context(context); return NULL; } retbuf = xmalloc(3*64 + 3); sprintf(retbuf, "%s%s%s%s%s", nbuf, ibuf[0] ? "." : "", ibuf, rbuf[0] ? "@" : "", rbuf); } else { /* get the text version of princ */ if (krb5_unparse_name(context,princ,&retbuf)) { krb5_free_principal(context,princ); krb5_free_context(context); syslog(LOG_ERR, "afspts_canonifyid krb5_unparse_name failed"); return NULL; } } /* we have the canonical name pointed to by p -- strip realm if local */ realmbegin = strrchr(retbuf, '@'); if(realmbegin) { if(!striprealm) { realm = realmbegin+1; if(is_local_realm(realm)) striprealm = 1; } if(striprealm) { *realmbegin = '\0'; } else { /* Force realm to uppercase */ while(*(++realmbegin)) { *realmbegin = toupper(*realmbegin); } } } krb5_free_principal(context,princ); krb5_free_context(context); return retbuf; } #else /* AFSPTS_USE_KRB5 not defined */ /* Sanity Check */ # if PTS_DB_KEYSIZE < MAX_K_NAME_SZ # error PTS_DB_KEYSIZE is smaller than MAX_K_NAME_SZ # endif /* where is krb.equiv? */ # ifndef KRB_MAPNAME # define KRB_MAPNAME (SYSCONFDIR "/krb.equiv") # endif /* * Parse a line 'src' from an /etc/krb.equiv file. * Sets the buffer pointed to by 'principal' to be the kerberos * identity and sets the buffer pointed to by 'localuser' to * be the local user. Both buffers must be of size one larger than * MAX_K_NAME_SZ. Returns 1 on success, 0 on failure. */ static int parse_krbequiv_line(const char *src, char *principal, char *localuser) { int i; while (Uisspace(*src)) src++; if (!*src) return 0; for (i = 0; *src && !Uisspace(*src); i++) { if (i >= MAX_K_NAME_SZ) return 0; *principal++ = *src++; } *principal = 0; if (!Uisspace(*src)) return 0; /* Need at least one separator */ while (Uisspace(*src)) src++; if (!*src) return 0; for (i = 0; *src && !Uisspace(*src); i++) { if (i >= MAX_K_NAME_SZ) return 0; *localuser++ = *src++; } *localuser = 0; return 1; } /* * Map a remote kerberos principal to a local username. If a mapping * is found, a pointer to the local username is returned. Otherwise, * a NULL pointer is returned. * Eventually, this may be more sophisticated than a simple file scan. */ static char *auth_map_krbid(const char *real_aname, const char *real_inst, const char *real_realm) { static char localuser[MAX_K_NAME_SZ + 1]; char principal[MAX_K_NAME_SZ + 1]; char aname[ANAME_SZ]; char inst[INST_SZ]; char realm[REALM_SZ]; char lrealm[REALM_SZ]; char krbhst[MAX_HSTNM]; char *p; char buf[1024]; FILE *mapfile; if (!(mapfile = fopen(KRB_MAPNAME, "r"))) { /* If the file can't be opened, don't do mappings */ return 0; } for (;;) { if (!fgets(buf, sizeof(buf), mapfile)) break; if (parse_krbequiv_line(buf, principal, localuser) == 0 || kname_parse(aname, inst, realm, principal) != 0) { /* Ignore badly formed lines */ continue; } if (!strcmp(aname, real_aname) && !strcmp(inst, real_inst) && !strcmp(realm, real_realm)) { fclose(mapfile); aname[0] = inst[0] = realm[0] = '\0'; if (kname_parse(aname, inst, realm, localuser) != 0) { return 0; } /* Upcase realm name */ for (p = realm; *p; p++) { if (Uislower(*p)) *p = toupper(*p); } if (*realm) { if (krb_get_lrealm(lrealm,1) == 0 && strcmp(lrealm, realm) == 0) { *realm = 0; } else if (krb_get_krbhst(krbhst, realm, 1)) { return 0; /* Unknown realm */ } } strcpy(localuser, aname); if (*inst) { strcat(localuser, "."); strcat(localuser, inst); } if (*realm) { strcat(localuser, "@"); strcat(localuser, realm); } return localuser; } } fclose(mapfile); return 0; } /* * Convert 'identifier' into canonical form. * Returns a pointer to a static buffer containing the canonical form * or NULL if 'identifier' is invalid. */ static char *afspts_canonifyid(const char *identifier, size_t len) { static char retbuf[MAX_K_NAME_SZ+1]; char aname[ANAME_SZ]; char inst[INST_SZ]; char realm[REALM_SZ]; char lrealm[REALM_SZ]; char krbhst[MAX_HSTNM]; char *canon_buf; char *p; if(!len) len = strlen(identifier); canon_buf = xmalloc(len + 1); memcpy(canon_buf, identifier, len); canon_buf[len] = '\0'; aname[0] = inst[0] = realm[0] = '\0'; if (kname_parse(aname, inst, realm, canon_buf) != 0) { free(canon_buf); return 0; } free(canon_buf); /* Upcase realm name */ for (p = realm; *p; p++) { if (Uislower(*p)) *p = toupper(*p); } if (*realm) { if (krb_get_lrealm(lrealm,1) == 0 && strcmp(lrealm, realm) == 0) { *realm = 0; } else if (krb_get_krbhst(krbhst, realm, 1)) { return 0; /* Unknown realm */ } } /* Check for krb.equiv remappings. */ p = auth_map_krbid(aname, inst, realm); if (p) { strcpy(retbuf, p); return retbuf; } strcpy(retbuf, aname); if (*inst) { strcat(retbuf, "."); strcat(retbuf, inst); } if (*realm && !is_local_realm(realm)) { strcat(retbuf, "@"); strcat(retbuf, realm); } return retbuf; } #endif /* AFSPTS_USE_KRB5 */ /* API */ static void myinit(void) { int r = pr_Initialize (1L, AFSCONF_CLIENTNAME, config_getstring(IMAPOPT_AFSPTS_MYCELL)); if (r) { syslog(LOG_DEBUG, "pr_Initialize failed: %d", r); fatal("pr_initialize failed", EC_TEMPFAIL); } localrealms = config_getstring(IMAPOPT_AFSPTS_LOCALREALMS); return; } static struct auth_state *myauthstate(const char *identifier, size_t size, const char **reply, int *dsize) { const char *canon_id = afspts_canonifyid(identifier, size); char canon_id_tmp[PTS_DB_KEYSIZE+1]; namelist groups; int i, rc; struct auth_state *newstate; if (canon_id == NULL) { syslog(LOG_ERR, "afspts_canonifyid failed for %s", identifier); return NULL; } *reply = NULL; size = strlen(canon_id); memset(&groups, 0, sizeof(groups)); groups.namelist_len = 0; groups.namelist_val = NULL; /* canon_id_tmp is used because AFS would otherwise trample * on our nice canonical user id */ strlcpy(canon_id_tmp,canon_id,sizeof(canon_id_tmp)); if ((rc = pr_ListMembers(canon_id_tmp, &groups))) { /* Failure may indicate that we need new tokens */ pr_End(); rc = pr_Initialize (1L, AFSCONF_CLIENTNAME, config_getstring(IMAPOPT_AFSPTS_MYCELL)); if (rc) { syslog(LOG_DEBUG, "pr_Initialize failed: %d", rc); fatal("pr_Initialize failed", EC_TEMPFAIL); } /* Okay, rerun it now */ rc = pr_ListMembers(canon_id_tmp, &groups); } /* Don't die because of afs, but log the error */ if(rc) { syslog(LOG_ERR, "pr_ListMembers %s: %s", canon_id, error_message(rc)); } /* fill in our new state structure */ *dsize = sizeof(struct auth_state) + (groups.namelist_len * sizeof(struct auth_ident)); newstate = (struct auth_state *) xzmalloc(*dsize); strcpy(newstate->userid.id, canon_id); newstate->userid.hash = strhash(canon_id); /* If we get a permission error, assume it may be temporary authentication problem, and cache only for a minute. Should negative cache time be configurable? */ if (rc == PRPERM) { newstate->mark = time(0) + 60 - (config_getint(IMAPOPT_PTSCACHE_TIMEOUT) > 60)? config_getint(IMAPOPT_PTSCACHE_TIMEOUT) : 60; } else newstate->mark = time(0); newstate->ngroups = groups.namelist_len; /* store group list in contiguous array for easy storage in the database */ memset(newstate->groups, 0, newstate->ngroups * sizeof(struct auth_ident)); for (i = 0; i < newstate->ngroups; i++) { strlcpy(newstate->groups[i].id, groups.namelist_val[i], sizeof(newstate->groups[i].id)); newstate->groups[i].hash = strhash(groups.namelist_val[i]); /* don't free groups.namelist_val[i]. Something else currently * takes care of that data. */ } if (groups.namelist_val != NULL) { free(groups.namelist_val); } return newstate; } #else /* HAVE_AFSKRB */ static void myinit(void) { fatal("PTS module (afskrb) not compiled in", EC_CONFIG); } static struct auth_state *myauthstate( const char *identifier __attribute__((unused)), size_t size __attribute__((unused)), const char **reply __attribute__((unused)), int *dsize __attribute__((unused))) { fatal("PTS module (afskrb) not compiled in", EC_CONFIG); return NULL; } #endif /* HAVE_AFSKRB */ struct pts_module pts_afskrb = { "afskrb", /* name */ &myinit, &myauthstate, }; cyrus-imapd-2.5.10/ptclient/ptexpire.c0000644000175000017500000001164513001236020014575 00000000000000/* * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ /* This program purges old entries from the database. It holds an exclusive * lock throughout the process. * * NOTE: by adding the alt_file flag, we let exit() handle the cleanup of * the lock file's fd. That's bad in principal but not in practice. We do * to make the code easier to read. */ #include #include #ifndef MAXPATHLEN #define MAXPATHLEN MAXPATHNAMELEN #endif #include #include #include #include #include #include #include #include "auth_pts.h" #include "cyrusdb.h" #include "exitcodes.h" #include "imap/global.h" #include "libconfig.h" #include "xmalloc.h" #include "xversion.h" /* global */ time_t timenow; time_t expire_time = (3*60*60); /* 3 Hours */ static int expire_p(void *rockp __attribute__((unused)), const char *key __attribute__((unused)), size_t keylen __attribute__((unused)), const char *data, size_t datalen __attribute__((unused))) { struct auth_state *authstate = (struct auth_state *)data; if (authstate->mark + expire_time < timenow) { return 1; } return 0; /* skip this one */ } static int expire_cb(void *rockp, const char *key, size_t keylen, const char *data __attribute__((unused)), size_t datalen __attribute__((unused))) { /* We only get called when we want to delete it */ syslog(LOG_DEBUG, "deleteing entry for %s", key); /* xxx maybe we should use transactions for this */ cyrusdb_delete((struct db *)rockp, key, keylen, NULL, 0); return 0; } int main(int argc, char *argv[]) { struct db *ptdb; char fnamebuf[1024]; extern char *optarg; int opt; int r; char *alt_config = NULL; if ((geteuid()) == 0 && (become_cyrus(/*is_master*/0) != 0)) { fatal("must run as the Cyrus user", EC_USAGE); } openlog("ptexpire", LOG_PID, SYSLOG_FACILITY); while ((opt = getopt(argc, argv, "C:E:")) != EOF) { switch (opt) { case 'C': /* alt config file */ alt_config = optarg; break; case 'E': expire_time = atoi(optarg); break; default: fprintf(stderr,"usage: [-C filename] [-E time]" "\n\t-C \tAlternate Config File" "\n\t-E \tExpiration time" "\n"); syslog(LOG_ERR, "Invalid command line option"); exit(-1); break; /* just pass through */ } } cyrus_init(alt_config, "ptexpire", 0, 0); timenow = time(0); syslog(LOG_INFO, "Expiring entries older than %d seconds (currently %d)", (int)expire_time, (int)timenow); syslog(LOG_DEBUG, "%s", "ptexpire.c,v " _CYRUS_VERSION " " CYRUS_GITVERSION); /* open database */ strcpy(fnamebuf, config_dir); strcat(fnamebuf, PTS_DBFIL); r = cyrusdb_open(config_ptscache_db, fnamebuf, CYRUSDB_CREATE, &ptdb); if(r != CYRUSDB_OK) { syslog(LOG_ERR, "error opening %s (%s)", fnamebuf, cyrusdb_strerror(r)); exit(1); } /* iterate through db, wiping expired entries */ cyrusdb_foreach(ptdb, "", 0, expire_p, expire_cb, ptdb, NULL); cyrusdb_close(ptdb); cyrus_done(); syslog(LOG_INFO, "finished"); return 0; } cyrus-imapd-2.5.10/ptclient/ptloader.h0000644000175000017500000000501113001236020014542 00000000000000/* ptloader.h -- Site authorization module * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #ifndef INCLUDED_PTLOADER_H #define INCLUDED_PTLOADER_H struct auth_state; struct pts_module { const char *name; void (*init)(void); struct auth_state *(*make_authstate)(const char *identifier, size_t size, const char **reply, int *dsize); }; extern struct pts_module *pts_modules[]; /* Note that some of these may be undefined symbols * if libcyrus was not built with support for them */ extern struct pts_module pts_ldap; extern struct pts_module pts_afskrb; struct auth_state *ptsmodule_make_authstate(const char *identifier, size_t size, const char **reply, int *dsize); void ptsmodule_init(void); #endif /* INCLUDED_PTLOADER_H */ cyrus-imapd-2.5.10/ptclient/ptdump.c0000644000175000017500000000665313001236020014251 00000000000000/* * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include #include #include #include #include "auth_pts.h" #include "cyrusdb.h" #include "imap/global.h" #include "libconfig.h" static int dump_cb(void *rockp __attribute__((unused)), const char *key, size_t keylen, const char *data, size_t datalen __attribute__((unused))) { struct auth_state *authstate = (struct auth_state *)data; int i; printf("user: "); fwrite(key, keylen, 1, stdout); printf(" time: %d groups: %d\n", (unsigned)authstate->mark, (unsigned)authstate->ngroups); for (i=0; i < authstate->ngroups; i++) printf(" %s\n",authstate->groups[i].id); return 0; } int main(int argc, char *argv[]) { struct db *ptdb; char fnamebuf[1024]; extern char *optarg; int opt; int r; char *alt_config = NULL; while ((opt = getopt(argc, argv, "C:")) != EOF) { switch (opt) { case 'C': /* alt config file */ alt_config = optarg; break; default: fprintf(stderr,"usage: [-C filename]" "\n\t-C \tAlternate Config File" "\n"); exit(-1); break; /* just pass through */ } } cyrus_init(alt_config, "ptdump", 0, 0); /* open database */ strcpy(fnamebuf, config_dir); strcat(fnamebuf, PTS_DBFIL); r = cyrusdb_open(config_ptscache_db, fnamebuf, CYRUSDB_CREATE, &ptdb); if(r != CYRUSDB_OK) { fprintf(stderr,"error opening %s (%s)", fnamebuf, cyrusdb_strerror(r)); exit(1); } /* iterate through db, wiping expired entries */ cyrusdb_foreach(ptdb, "", 0, NULL, dump_cb, ptdb, NULL); cyrusdb_close(ptdb); cyrus_done(); return 0; } cyrus-imapd-2.5.10/ptclient/test.c0000644000175000017500000000476513001236020013721 00000000000000/* * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include #include #include #include #include "config.h" int main(int argc, char **argv) { char *cacheid; char cache[16]; if (argc < 3 || argc > 4) { printf("Usage: pttset user group [cachearg]\n"); exit(1); } if (argc == 4) { memset(cache,0,16); strncpy(cache,argv[3],16); cacheid=cache; } else cacheid=NULL; openlog("pttest", LOG_PID, SYSLOG_FACILITY); if (!auth_setid(argv[1],cacheid)) printf ("Auth_memberof(%s,%s) is %d\n", argv[1], argv[2], auth_memberof(argv[2])); else printf ("Auth_setid(%s) failed\n", argv[1]); } int fatal(char *foo) { fprintf(stderr, "Fatal error: %s\n", foo); exit(1); } cyrus-imapd-2.5.10/ptclient/ptloader.c0000644000175000017500000001524213001236020014544 00000000000000/* ptloader.c -- group loader daemon * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include #include #include #include #include #include #include #include #include #include #include #include #include #include "auth_pts.h" #include "cyrusdb.h" #include "exitcodes.h" #include "imap/global.h" #include "libconfig.h" #include "retry.h" #include "xmalloc.h" #include "ptloader.h" #include "xversion.h" struct pts_module *pts_modules[] = { #ifdef HAVE_LDAP &pts_ldap, #endif #ifdef HAVE_AFSKRB &pts_afskrb, #endif NULL }; extern void setproctitle_init(int argc, char **argv, char **envp); static struct pts_module *pts_fromname() { int i; const char *name = config_getstring(IMAPOPT_PTS_MODULE); static struct pts_module *pts = NULL; if (pts) return pts; for (i = 0; pts_modules[i]; i++) { if (!strcmp(pts_modules[i]->name, name)) { pts = pts_modules[i]; break; } } if (!pts) { char errbuf[1024]; snprintf(errbuf, sizeof(errbuf), "PTS module %s not supported", name); fatal(errbuf, EC_CONFIG); } return pts; } void ptsmodule_init(void) { struct pts_module *pts = pts_fromname(); pts->init(); } struct auth_state *ptsmodule_make_authstate(const char *identifier, size_t size, const char **reply, int *dsize) { struct pts_module *pts = pts_fromname(); return pts->make_authstate(identifier, size, reply, dsize); } /* config.c info (libimap) */ const int config_need_data = 0; /* Globals */ #define DB (config_ptscache_db) static char ptclient_debug = 0; struct db *ptsdb = NULL; int service_init(int argc, char *argv[], char **envp __attribute__((unused))) { int r; int opt; char fnamebuf[1024]; extern char *optarg; if (geteuid() == 0) fatal("must run as the Cyrus user", EC_USAGE); setproctitle_init(argc, argv, envp); /* set signal handlers */ signal(SIGPIPE, SIG_IGN); syslog(LOG_NOTICE, "starting: ptloader.c,v " _CYRUS_VERSION " " CYRUS_GITVERSION); while ((opt = getopt(argc, argv, "d:")) != EOF) { switch (opt) { case 'd': ptclient_debug = atoi(optarg); if (ptclient_debug < 1) { ptclient_debug = 1; } break; default: syslog(LOG_ERR, "invalid command line option specified"); break; /* just pass through */ } } strcpy(fnamebuf, config_dir); strcat(fnamebuf, PTS_DBFIL); r = cyrusdb_open(DB, fnamebuf, CYRUSDB_CREATE, &ptsdb); if (r != 0) { syslog(LOG_ERR, "DBERROR: opening %s: %s", fnamebuf, cyrusdb_strerror(ret)); fatal("can't read pts database", EC_TEMPFAIL); } ptsmodule_init(); return 0; } /* Called by service API to shut down the service */ void service_abort(int error) { int r; r = cyrusdb_close(ptsdb); if (r) { syslog(LOG_ERR, "DBERROR: error closing ptsdb: %s", cyrusdb_strerror(r)); } cyrusdb_done(); exit(error); } /* we're a 'threaded' service, but since we never fork or create any threads, we're just one-person-at-a-time based */ int service_main_fd(int c, int argc __attribute__((unused)), char **argv __attribute__((unused)), char **envp __attribute__((unused))) { const char *reply = NULL; char user[PTS_DB_KEYSIZE]; int rc, dsize; size_t size; struct auth_state *newstate; (void)memset(&size, 0, sizeof(size)); if (read(c, &size, sizeof(size_t)) < 0) { syslog(LOG_ERR, "socket (size): %m"); reply = "Error reading request (size)"; goto sendreply; } if (size > PTS_DB_KEYSIZE) { syslog(LOG_ERR, "size sent %d is greater than buffer size %d", (int)size, PTS_DB_KEYSIZE); reply = "Error: invalid request size"; goto sendreply; } if (size == 0) { syslog(LOG_ERR, "size sent is 0"); reply = "Error: zero request size"; goto sendreply; } memset(&user, 0, sizeof(user)); if (read(c, &user, size) < 0) { syslog(LOG_ERR, "socket(user; size = %d): %m", (int)size); reply = "Error reading request (user)"; goto sendreply; } if (ptclient_debug) { syslog(LOG_DEBUG, "user %s", user); } newstate = ptsmodule_make_authstate(user, size, &reply, &dsize); if(newstate) { /* Success! */ rc = cyrusdb_store(ptsdb, user, size, (void *)newstate, dsize, NULL); (void)rc; free(newstate); /* and we're done */ reply = "OK"; } else { /* Failure */ if ( reply == NULL ) { reply = "Error making authstate"; } } sendreply: if (retry_write(c, reply, strlen(reply) + 1) <0) { syslog(LOG_WARNING, "retry_write: %m"); } close(c); return 0; } /* we need to have this function here 'cause libcyrus.la * makes calls to this function. */ EXPORTED void fatal(const char *msg, int exitcode) { syslog(LOG_ERR, "%s", msg); exit(exitcode); } cyrus-imapd-2.5.10/ptclient/test2.c0000644000175000017500000000434513001236020013775 00000000000000/* * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include "config.h" #include #include int main(void) { char cacheid[16]="4224423"; openlog("testr", LOG_PID, SYSLOG_FACILITY); if (!auth_setid("cg2v@club.cc.cmu.edu",cacheid)) printf ("Auth_memberof(cg2v,cg2v:me) is %d\n", auth_memberof("cg2v:me")); else printf ("Auth_setid(cg2v@club.cc.cmu.edu) failed\n"); } int fatal(char *foo) { fprintf(stderr, "Fatal error: %s\n", foo); exit(1); } cyrus-imapd-2.5.10/notifyd/0000755000175000017500000000000013001246664012513 500000000000000cyrus-imapd-2.5.10/notifyd/notify_log.h0000644000175000017500000000410613001236020014737 00000000000000/* notify_log.h -- syslog notification method * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #ifndef _NOTIFY_LOG_H_ #define _NOTIFY_LOG_H_ #include char* notify_log(const char *class, const char *priority, const char *user, const char *mailbox, int nopt, char **options, const char *message); #endif /* _NOTIFY_LOG_H_ */ cyrus-imapd-2.5.10/notifyd/notify_zephyr.c0000644000175000017500000001052713001236020015476 00000000000000/* notify_zephyr.c -- zephyr notification method * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include #ifdef HAVE_UNISTD_H #include #endif #include #include #include #include #include #ifdef HAVE_KRB #include #include #endif #include #include #include "xmalloc.h" #include "util.h" #ifndef MAIL_CLASS #define MAIL_CLASS "MAIL" #endif #ifndef HOST_NAME_MAX #define HOST_NAME_MAX 256 #endif #include "notify_zephyr.h" char* notify_zephyr(const char *class, const char *priority, const char *user, const char *mailbox, int nopt, char **options, const char *message) { ZNotice_t notice; int retval; char myhost[HOST_NAME_MAX], *mysender = NULL; struct buf msgbody = BUF_INITIALIZER; char *lines[2]; char *mykrbhost = NULL; if (!*user) return xstrdup("NO zephyr recipient not specified"); if ((retval = ZInitialize()) != ZERR_NONE) { syslog(LOG_ERR, "IOERROR: cannot initialize zephyr: %m"); return xstrdup("NO cannot initialize zephyr"); } if (gethostname(myhost,sizeof(myhost)) == -1) { syslog(LOG_ERR, "IOERROR: cannot get hostname: %m"); return xstrdup("NO zephyr cannot get hostname"); } myhost[sizeof(myhost)-1] = '\0'; #ifdef HAVE_KRB mykrbhost = krb_get_phost(myhost); #endif if (*mailbox) { buf_printf(&msgbody, "You have new mail in %s.\n\n", mailbox); } if (*message) { buf_appendcstr(&msgbody, message); buf_putc(&msgbody, '\n'); } lines[0] = myhost; lines[1] = (char *)buf_cstring(&msgbody); mysender = strconcat("imap", mykrbhost ? "." : "", mykrbhost ? mykrbhost : "", "@", ZGetRealm(), (char *)NULL); memset((char *)¬ice, 0, sizeof(notice)); notice.z_kind = UNSAFE; notice.z_class = *class ? (char *) class : MAIL_CLASS; notice.z_class_inst = *priority ? (char *) priority : *mailbox ? (char *) mailbox : "INBOX"; notice.z_opcode = ""; notice.z_sender = mysender; notice.z_default_format = "From Post Office $1:\n$2"; notice.z_recipient = (char *) user; retval = ZSendList(¬ice,lines,2,ZNOAUTH); /* do any additional users */ while (retval == ZERR_NONE && nopt) { notice.z_recipient = (char *) options[--nopt]; retval = ZSendList(¬ice,lines,2,ZNOAUTH); } buf_free(&msgbody); free(mysender); if (retval != ZERR_NONE) { syslog(LOG_ERR, "IOERROR: cannot send zephyr notice: %m"); return xstrdup("NO cannot send zephyr notice"); } return xstrdup("OK zephyr notification successful"); } cyrus-imapd-2.5.10/notifyd/notify_null.c0000644000175000017500000000443113001236020015124 00000000000000/* notify_null.c -- NULL notification method * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include #include "notify_null.h" #include char* notify_null(const char *class __attribute__((unused)), const char *priority __attribute__((unused)), const char *user __attribute__((unused)), const char *mailbox __attribute__((unused)), int nopt __attribute__((unused)), char **options __attribute__((unused)), const char *message __attribute__((unused))) { return strdup("OK null notification successful"); } cyrus-imapd-2.5.10/notifyd/notify_log.c0000644000175000017500000000517513001236020014741 00000000000000/* notify_log.c -- syslog notification method * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include #include "notify_log.h" #include #include #include char* notify_log(const char *class, const char *priority, const char *user, const char *mailbox, int nopt, char **options, const char *message) { char opt_str[1024] = ""; char *sep = ""; int i; if (nopt) { strcpy(opt_str, "("); for (i = 0; i < nopt; i++, sep = ", ") { snprintf(opt_str+strlen(opt_str), sizeof(opt_str) - 2, "%s%s", sep, options[i]); } strcat(opt_str, ")"); } /* Not needed, we opened the log file in cyrus_init */ /* openlog("notifyd", LOG_PID, SYSLOG_FACILITY); */ syslog(LOG_INFO, "%s, %s, %s, %s, %s \"%s\"", class, priority, user, mailbox, opt_str, message); closelog(); return strdup("OK log notification successful"); } cyrus-imapd-2.5.10/notifyd/notify_mailto.c0000644000175000017500000001126213001236020015437 00000000000000/* notify_mailto.c -- email notification method * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include #include "notify_mailto.h" #include #include #include #include #include #include #include "imap/global.h" #include "libconfig.h" #include "sieve/sieve_interface.h" #include "times.h" static int contains_8bit(const char *msg); static int global_outgoing_count = 0; char* notify_mailto(const char *class, const char *priority __attribute__((unused)), const char *user __attribute__((unused)), const char *mailbox __attribute__((unused)), int nopt, char **options, const char *message) { FILE *sm; const char *smbuf[7]; char outmsgid[256]; int sm_stat; time_t t; char datestr[RFC822_DATETIME_MAX+1]; pid_t sm_pid; int fds[2]; /* XXX check/parse options (mailto URI) */ if (nopt < 1) return strdup("NO mailto URI not specified"); smbuf[0] = "sendmail"; smbuf[1] = "-i"; /* ignore dots */ smbuf[2] = "-f"; smbuf[3] = "<>"; /* XXX do we want a return-path? */ smbuf[4] = "--"; smbuf[5] = options[0]; smbuf[6] = NULL; if (pipe(fds)) return strdup("NO mailto could not open pipe"); if ((sm_pid = fork()) == 0) { /* i'm the child! run sendmail! */ close(fds[1]); /* make the pipe be stdin */ dup2(fds[0], 0); execv(config_getstring(IMAPOPT_SENDMAIL), (char **) smbuf); /* if we're here we suck */ return strdup("NO mailto couldn't exec"); } /* i'm the parent */ close(fds[0]); sm = fdopen(fds[1], "w"); if (!sm) return strdup("NO mailto could not spawn sendmail process"); t = time(NULL); snprintf(outmsgid, sizeof(outmsgid), "", (int) sm_pid, t, global_outgoing_count++, config_servername); fprintf(sm, "Message-ID: %s\r\n", outmsgid); time_to_rfc822(t, datestr, sizeof(datestr)); fprintf(sm, "Date: %s\r\n", datestr); fprintf(sm, "X-Sieve: %s\r\n", SIEVE_VERSION); fprintf(sm, "From: Mail Sieve Subsystem <%s>\r\n", config_getstring(IMAPOPT_POSTMASTER)); fprintf(sm, "To: <%s>\r\n", options[0]); fprintf(sm, "Subject: [%s] New mail notification\r\n", class); if (contains_8bit(message)) { fprintf(sm, "MIME-Version: 1.0\r\n"); fprintf(sm, "Content-Type: text/plain; charset=UTF-8\r\n"); fprintf(sm, "Content-Transfer-Encoding: 8BIT\r\n"); } fprintf(sm, "\r\n"); fprintf(sm, "%s\r\n", message); fclose(sm); while (waitpid(sm_pid, &sm_stat, 0) < 0); /* XXX check for sendmail exit code */ /* XXX add outmsgid to duplicate delivery database to prevent loop */ return strdup("OK mailto notification successful"); } static int contains_8bit(const char * msg) { int result = 0; if (msg) { const unsigned char *s = (const unsigned char *)msg; while (*s) { if (0 != (*s & 0x80)) { result = 1; break ; } s++; } } return result; } cyrus-imapd-2.5.10/notifyd/notifyd.h0000644000175000017500000000531413001236020014244 00000000000000/* notifyd.h -- notification method definitions * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include #include "notify_null.h" #include "notify_log.h" #include "notify_mailto.h" #include "notify_zephyr.h" #include "notify_external.h" /* Notify method dispatch table definition */ typedef struct { const char *name; /* name of the method */ char *(*notify)(const char *class, const char *priority, const char *user, const char *mailbox, int nopt, char **options, const char *message); /* notification function */ } notifymethod_t; /* array of supported notification methods */ static notifymethod_t methods[] = { { "null", notify_null }, /* do nothing */ { "log", notify_log }, /* use syslog (for testing) */ { "mailto", notify_mailto }, /* send an email */ #ifdef HAVE_ZEPHYR { "zephyr", notify_zephyr }, /* send a zephyrgram */ #endif { "external", notify_external }, /* send via external program */ { NULL, NULL } }; cyrus-imapd-2.5.10/notifyd/notifyd.c0000644000175000017500000001433413001236020014241 00000000000000/* notifyd.c -- main file for notifyd (notify script notification program) * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #ifdef HAVE_CONFIG_H #include #endif #include #include #include #include #include #include #include #include #ifdef HAVE_UNISTD_H # include #endif #include #include #include "notifyd.h" #include "exitcodes.h" #include "imap/global.h" #include "libconfig.h" #include "xmalloc.h" #include "strarray.h" /* global state */ const int config_need_data = 0; static int soc = 0; /* master has handed us the port as stdin */ static notifymethod_t *default_method; /* default method daemon is using */ /* Cleanly shut down and exit */ void shut_down(int code) __attribute__ ((noreturn)); EXPORTED void shut_down(int code) { in_shutdown = 1; cyrus_done(); /* done */ exit(code); } static char *fetch_arg(char *head, char* tail) { char *cp; for (cp = head; *cp && cp < tail; cp++); return (cp == tail ? NULL : cp + 1); } #define NOTIFY_MAXSIZE 8192 static int do_notify(void) { struct sockaddr_un sun_data; socklen_t sunlen = sizeof(sun_data); char buf[NOTIFY_MAXSIZE+1], *cp, *tail; int r, i; char *method, *class, *priority, *user, *mailbox, *message; strarray_t options = STRARRAY_INITIALIZER; long nopt; char *reply; notifymethod_t *nmethod; while (1) { method = class = priority = user = mailbox = message = reply = NULL; nopt = 0; if (signals_poll() == SIGHUP) { /* caught a SIGHUP, return */ return 0; } r = recvfrom(soc, buf, NOTIFY_MAXSIZE, 0, (struct sockaddr *) &sun_data, &sunlen); if (r == -1) { return (errno); } buf[r] = '\0'; tail = buf + r - 1; /* * parse request of the form: * * method NUL class NUL priority NUL user NUL mailbox NUL * nopt NUL N(option NUL) message NUL */ method = (cp = buf); if (cp) class = (cp = fetch_arg(cp, tail)); if (cp) priority = (cp = fetch_arg(cp, tail)); if (cp) user = (cp = fetch_arg(cp, tail)); if (cp) mailbox = (cp = fetch_arg(cp, tail)); if (cp) cp = fetch_arg(cp, tail); /* skip to nopt */ if (cp) nopt = strtol(cp, NULL, 10); if (nopt < 0 || errno == ERANGE) cp = NULL; for (i = 0; cp && i < nopt; i++) strarray_appendm(&options, cp = fetch_arg(cp, tail)); if (cp) message = (cp = fetch_arg(cp, tail)); if (!message) { syslog(LOG_ERR, "malformed notify request"); strarray_fini(&options); return 0; } if (!*method) nmethod = default_method; else { nmethod = methods; while (nmethod->name) { if (!strcasecmp(nmethod->name, method)) break; nmethod++; } } syslog(LOG_DEBUG, "do_notify using method '%s'", nmethod->name ? nmethod->name: "unknown"); if (nmethod->name) { reply = nmethod->notify(class, priority, user, mailbox, nopt, options.data, message); } #if 0 /* we don't care about responses right now */ else { reply = strdup("NO unknown notification method"); if (!reply) { fatal("strdup failed", EC_OSERR); } } #endif free(reply); strarray_fini(&options); } /* never reached */ } EXPORTED void fatal(const char *s, int code) { static int recurse_code = 0; if (recurse_code) { /* We were called recursively. Just give up */ exit(recurse_code); } recurse_code = code; syslog(LOG_ERR, "Fatal error: %s", s); shut_down(code); } static void usage(void) { syslog(LOG_ERR, "usage: notifyd [-C ]"); exit(EC_USAGE); } EXPORTED int service_init(int argc, char **argv, char **envp __attribute__((unused))) { int opt; char *method = "null"; if (geteuid() == 0) fatal("must run as the Cyrus user", EC_USAGE); while ((opt = getopt(argc, argv, "m:")) != EOF) { switch(opt) { case 'm': method = optarg; break; default: usage(); } } default_method = methods; while (default_method->name) { if (!strcasecmp(default_method->name, method)) break; default_method++; } if (!default_method) fatal("unknown notification method %s", EC_USAGE); signals_set_shutdown(&shut_down); return 0; } /* Called by service API to shut down the service */ EXPORTED void service_abort(int error) { shut_down(error); } EXPORTED int service_main(int argc __attribute__((unused)), char **argv __attribute__((unused)), char **envp __attribute__((unused))) { int r = 0; r = do_notify(); shut_down(r); return 0; } cyrus-imapd-2.5.10/notifyd/notify_null.h0000644000175000017500000000440013001236020015125 00000000000000/* notify_null.h -- NULL notification method * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #ifndef _NOTIFY_NULL_H_ #define _NOTIFY_NULL_H_ #include char* notify_null(const char *class __attribute__((unused)), const char *priority __attribute__((unused)), const char *user __attribute__((unused)), const char *mailbox __attribute__((unused)), int nopt __attribute__((unused)), char **options __attribute__((unused)), const char *message __attribute__((unused))); #endif /* _NOTIFY_NULL_H_ */ cyrus-imapd-2.5.10/notifyd/notifytest.c0000644000175000017500000001261113001236020014771 00000000000000/* notifytest.c: notifyd test utility * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #ifdef HAVE_CONFIG_H #include #endif #include #include #include #include #include #include #include #ifdef HAVE_UNISTD_H # include #endif #define MAX_OPT 10 #define MAXSIZE 8192 /* generic fatal() routine for command line utilities it is here, because libcyrus requires a global function fatal */ EXPORTED void fatal(const char *message, int code) { static int recurse_code = 0; if (recurse_code) { exit(code); } recurse_code = code; fprintf(stderr, "fatal error: %s\n", message); exit(code); } static int add_arg(char *buf, int max_size, const char *arg, int *buflen) { const char *myarg = (arg ? arg : ""); int len = strlen(myarg) + 1; if (*buflen + len > max_size) return -1; strcat(buf+*buflen, myarg); *buflen += len; return 0; } static int notify(const char *notifyd_path, const char *method, const char *class, const char *priority, const char *user, const char *mailbox, int nopt, char **options, const char *message) { int soc; struct sockaddr_un sun; char buf[MAXSIZE] = "", noptstr[20]; int buflen = 0; int i, r = 0; soc = socket(AF_UNIX, SOCK_DGRAM, 0); if (soc == -1) { perror("socket() "); return -1; } memset((char *)&sun, 0, sizeof(sun)); sun.sun_family = AF_UNIX; strncpy(sun.sun_path, notifyd_path, sizeof(sun.sun_path)); /* * build request of the form: * * method NUL class NUL priority NUL user NUL mailbox NUL * nopt NUL N(option NUL) NUL message NUL */ r = add_arg(buf, MAXSIZE, method, &buflen); if (!r) r = add_arg(buf, MAXSIZE, class, &buflen); if (!r) r = add_arg(buf, MAXSIZE, priority, &buflen); if (!r) r = add_arg(buf, MAXSIZE, user, &buflen); if (!r) r = add_arg(buf, MAXSIZE, mailbox, &buflen); snprintf(noptstr, sizeof(noptstr), "%d", nopt); if (!r) r = add_arg(buf, MAXSIZE, noptstr, &buflen); for (i = 0; !r && i < nopt; i++) { r = add_arg(buf, MAXSIZE, options[i], &buflen); } if (!r) r = add_arg(buf, MAXSIZE, message, &buflen); if (r) { perror("dgram too big"); return -1; } r = sendto(soc, buf, buflen, 0, (struct sockaddr *) &sun, sizeof(sun)); if (r < buflen) { perror("sendto() "); return -1; } return 0; } int main(int argc, char *argv[]) { const char *method = "", *priority = "normal"; const char *class = "MESSAGE", *user = "", *mailbox = NULL; const char *message = NULL, *path = NULL; int c; int flag_error = 0; while ((c = getopt(argc, argv, "f:n:c:p:u:m:t:")) != EOF) switch (c) { case 'f': path = optarg; break; case 'n': method = optarg; break; case 'c': class = optarg; break; case 'p': priority = optarg; break; case 'u': user = optarg; break; case 'm': mailbox = optarg; break; case 't': message = optarg; break; default: flag_error = 1; break; } if (!path || !message) flag_error = 1; if (flag_error) { (void)fprintf(stderr, "%s: usage: %s -f socket_path -t text [-n method]\n" " [-c class] [-p priority]\n" " [-u user] [-m mailbox]\n" " [option ...]\n", argv[0], argv[0]); exit(1); } if ((argc - optind) > 10) { fprintf(stderr,"too many options (> %d)\n", MAX_OPT); exit(1); } if (!*user) user = getpwuid(getuid())->pw_name; return notify(path, method, class, priority, user, mailbox, argc - optind, argv+optind, message); } cyrus-imapd-2.5.10/notifyd/notify_zephyr.h0000644000175000017500000000425213001236020015501 00000000000000/* notify_zephyr.h -- zephyr notification method * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #ifndef _NOTIFY_ZEPHYR_H_ #define _NOTIFY_ZEPHYR_H_ #include /* the options should be a list of users to notify in addition to 'user' */ char* notify_zephyr(const char *class, const char *priority, const char *user, const char *mailbox, int nopt, char **options, const char *message); #endif /* _NOTIFY_ZEPHYR_H_ */ cyrus-imapd-2.5.10/notifyd/notify_external.c0000644000175000017500000000723313001236020015777 00000000000000/* notify_external.c -- external notification method * * Copyright (c) 1994-2010 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. * * $Id$ */ #include #include #include #include #include #include #include #include #include "imap/global.h" #include "libconfig.h" #include "notify_external.h" char* notify_external(const char *class, const char *priority, const char *user, const char *mailbox, int nopt __attribute__((unused)), char **options __attribute__((unused)), const char *message) { const char *notify; const char *buf[10]; int fds[2], status; pid_t child_pid; FILE *stream; /* check/parse options */ if (!(notify = config_getstring(IMAPOPT_NOTIFY_EXTERNAL))) { syslog(LOG_ERR, "ERROR: no external recipient (program) specified"); return strdup("NO Recipient unspecified"); } buf[0] = notify; buf[1] = "-c"; buf[2] = class; buf[3] = "-p"; buf[4] = priority; buf[5] = "-u"; buf[6] = user; buf[7] = "-m"; buf[8] = mailbox; buf[9] = NULL; if (pipe(fds) < 0) { syslog(LOG_ERR, "notify_external: pipe() returned %s\n", strerror(errno)); return strdup("NO notify_external pipe failed"); } if ((child_pid = fork()) == 0) { /* i'm the child! run notify */ close(fds[1]); /* make the pipe be stdin */ dup2(fds[0], 0); execv(notify, (char **) buf); /* should never reach here */ syslog(LOG_ERR, "notify_external: exec returned %s", strerror(errno)); return strdup("NO notify_external exec failed"); } /* i'm the parent */ close(fds[0]); stream = fdopen(fds[1], "w"); if (!stream) { return strdup("NO notify_external could not open stream"); } fprintf(stream, "%s\n", message); fclose(stream); while (waitpid(child_pid, &status, 0) < 0); return strdup("OK notify_external notification successful"); } cyrus-imapd-2.5.10/notifyd/notify_mailto.h0000644000175000017500000000436613001236020015453 00000000000000/* notify_mailto.h -- email notification method * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #ifndef _NOTIFY_MAILTO_H_ #define _NOTIFY_MAILTO_H_ #include /* the only option should be a mailto URI */ char* notify_mailto(const char *class __attribute__((unused)), const char *priority __attribute__((unused)), const char *user __attribute__((unused)), const char *mailbox __attribute__((unused)), int nopt, char **options, const char *message); #endif /* _NOTIFY_MAILTO_H_ */ cyrus-imapd-2.5.10/notifyd/notify_external.h0000644000175000017500000000416113001236020016001 00000000000000/* notify_external.h -- external notification method * * Copyright (c) 1994-2010 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. * * $Id$ */ #ifndef _NOTIFY_EXTERNAL_H #define _NOTIFY_EXTERNAL_H #include char* notify_external(const char *class, const char *priority, const char *user, const char *mailbox, int nopt, char **options, const char *message); #endif /* _NOTIFY_EXTERNAL_H */ cyrus-imapd-2.5.10/imtest/0000755000175000017500000000000013001246664012344 500000000000000cyrus-imapd-2.5.10/imtest/imtest.c0000644000175000017500000021712713001236020013730 00000000000000/* imtest.c -- IMAP/POP3/NNTP/LMTP/SMTP/MUPDATE/MANAGESIEVE test client * Ken Murchison (multi-protocol implementation) * Tim Martin (SASL implementation) * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include "config.h" #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include "hash.h" #include "imparse.h" #include "iptostring.h" #include "md5.h" #include "prot.h" #include "retry.h" #include "strarray.h" #include "stristr.h" #include "util.h" #include "xmalloc.h" #include "xstrlcat.h" #include "xstrlcpy.h" #ifdef HAVE_SSL #include static SSL_CTX *tls_ctx = NULL; static SSL *tls_conn = NULL; static SSL_SESSION *tls_sess = NULL; #endif /* HAVE_SSL */ #define IMTEST_OK 0 #define IMTEST_FAIL -1 #define IMTEST_CLOSEME -2 typedef enum { STAT_CONT = 0, STAT_NO = 1, STAT_OK = 2 } imt_stat; /* global vars */ static sasl_conn_t *conn; static int sock; /* socket descriptor */ static int verbose=0; static struct protstream *pout, *pin; static char *authname = NULL; static char *username = NULL; static char *realm = NULL; static char *cmdline_password = NULL; static char *output_socket = NULL; static int output_socket_opened = 0; static ino_t output_socket_ino = 0; #define CONFIGHASHSIZE 30 /* relatively small */ static struct hash_table confighash; static int mysasl_config(void*, const char*, const char*, const char**, unsigned*); extern int _sasl_debug; extern char *optarg; static strarray_t stashed_strings = STRARRAY_INITIALIZER; /* callbacks we support */ static sasl_callback_t callbacks[] = { { SASL_CB_ECHOPROMPT, NULL, NULL }, { SASL_CB_NOECHOPROMPT, NULL, NULL }, { #ifdef SASL_CB_GETREALM SASL_CB_GETREALM, NULL, NULL }, { #endif SASL_CB_USER, NULL, NULL }, { SASL_CB_AUTHNAME, NULL, NULL }, { SASL_CB_PASS, NULL, NULL }, { SASL_CB_GETOPT, (int (*)(void))&mysasl_config, NULL }, { SASL_CB_LIST_END, NULL, NULL } }; struct protocol_t; struct banner_t { u_char is_capa; /* banner is capability response */ char *resp; /* end of banner response */ void *(*parse_banner)(char *str); /* [OPTIONAL] parse banner, returns 'rock' */ }; struct capa_cmd_t { char *cmd; /* capability command string (NULL = no capa cmd) */ char *resp; /* end of capability response */ char *tls; /* [OPTIONAL] TLS capability string */ char *login; /* [OPTIONAL] plaintext login cmd capability string */ char *auth; /* [OPTIONAL] AUTH (SASL) capability string */ char *compress; /* [OPTIONAL] COMPRESS capability string */ char *(*parse_mechlist)(const char *str, struct protocol_t *prot); /* [OPTIONAL] parse capability string, returns space-separated list of mechs */ }; struct tls_cmd_t { char *cmd; /* tls command string */ char *ok; /* start tls prompt */ char *fail; /* failure response */ u_char auto_capa; /* capability response sent automatically after TLS */ }; struct sasl_cmd_t { char *cmd; /* auth command string */ u_short maxlen; /* maximum command line length, (0 = initial response unsupported by protocol) */ u_char quote; /* quote arguments (literal for base64 data) */ char *ok; /* success response string */ char *fail; /* failure response string */ char *cont; /* continue response string (NULL = send/receive literals) */ char *cancel; /* cancel auth string */ char *(*parse_success)(char *str); /* [OPTIONAL] parse response for success data */ u_char auto_capa; /* capability response sent automatically after AUTH with SASL security layer */ }; struct compress_cmd_t { char *cmd; /* compress command string */ char *ok; /* success response string */ char *fail; /* failure response string */ }; struct logout_cmd_t { char *cmd; /* logout command string */ char *resp; /* logout response */ }; struct protocol_t { char *protocol; /* protocol service name */ char *sprotocol; /* SSL-wrapped service name (NULL = unsupported) */ char *service; /* SASL service name */ int login_enabled; /* [OPTIONAL] login command on/off by default; toggled by capability string */ struct banner_t banner; struct capa_cmd_t capa_cmd; struct tls_cmd_t tls_cmd; struct sasl_cmd_t sasl_cmd; struct compress_cmd_t compress_cmd; int (*do_auth)(struct sasl_cmd_t *sasl_cmd, void *rock, int login_enabled, char *mech, char *mechlist); /* [OPTIONAL] perform protocol-specific authentication; based on rock, login_enabled, mech, mechlist */ struct logout_cmd_t logout_cmd; /* these 3 are used for maintaining connection state */ void *(*init_conn)(void); /* generate a context (if needed). This context * must be malloc()ed and will be freed by * interactive() as each connection is reused */ int (*pipe)(char *buf, int len, void *rock); /* pipe a buffer to pout * may be necessary to keep * connection state */ int (*reset)(void *rock); /* perform any protocol-specific reset when we * lose connection on a unix domain socket * during interactive mode. If this is NULL we * assume that we should not attempt to reuse * connections (and just die at the end of one) */ }; static void imtest_fatal(const char *msg, ...) __attribute__((noreturn)); static void imtest_fatal(const char *msg, ...) { struct stat sbuf; if (output_socket && output_socket_opened && stat(output_socket, &sbuf) != -1 && sbuf.st_ino == output_socket_ino) { unlink(output_socket); } if (msg != NULL) { va_list ap; va_start(ap, msg); fprintf(stderr, "failure: "); vfprintf(stderr, msg, ap); fprintf(stderr, "\n"); va_end(ap); } exit(1); } /* libcyrus makes us define this */ EXPORTED void fatal(const char *msg, int code __attribute__((unused))) { imtest_fatal(msg); } int mysasl_config(void *context __attribute__((unused)), const char *plugin_name, const char *option, const char **result, unsigned *len) { *result = NULL; if (plugin_name) { /* first try it with the plugin name */ char opt[1024]; strlcpy(opt, plugin_name, sizeof(opt)); strlcat(opt, "_", sizeof(opt)); strlcat(opt, option, sizeof(opt)); *result = hash_lookup(opt, &confighash); } if (*result == NULL) { /* try without the plugin name */ *result = hash_lookup(option, &confighash); } if (*result != NULL) { if (len) { *len = strlen(*result); } return SASL_OK; } return SASL_FAIL; } #ifdef HAVE_SSL static int verify_depth; static int verify_error = X509_V_OK; static int do_dump = 0; #define CCERT_BUFSIZ 256 static char peer_CN[CCERT_BUFSIZ]; static char issuer_CN[CCERT_BUFSIZ]; static char *tls_peer_CN = NULL; static char *tls_issuer_CN = NULL; static const char *tls_protocol = NULL; static const char *tls_cipher_name = NULL; static int tls_cipher_usebits = 0; static int tls_cipher_algbits = 0; /* * Set up the cert things on the server side. We do need both the * private key (in key_file) and the cert (in cert_file). * Both files may be identical. * * This function is taken from OpenSSL apps/s_cb.c */ static int set_cert_stuff(SSL_CTX * ctx, char *cert_file, char *key_file) { if (cert_file != NULL) { if (SSL_CTX_use_certificate_chain_file(ctx, cert_file) <= 0) { printf("unable to get certificate from '%s'\n", cert_file); return (0); } if (key_file == NULL) key_file = cert_file; if (SSL_CTX_use_PrivateKey_file(ctx, key_file, SSL_FILETYPE_PEM) <= 0) { printf("unable to get private key from '%s'\n", key_file); return (0); } /* Now we know that a key and cert have been set against * the SSL context */ if (!SSL_CTX_check_private_key(ctx)) { printf("Private key does not match the certificate public key\n"); return (0); } } return (1); } /* taken from OpenSSL apps/s_cb.c */ static int verify_callback(int ok, X509_STORE_CTX * ctx) { char buf[256]; X509 *err_cert; int err; int depth; err_cert = X509_STORE_CTX_get_current_cert(ctx); err = X509_STORE_CTX_get_error(ctx); depth = X509_STORE_CTX_get_error_depth(ctx); X509_NAME_oneline(X509_get_subject_name(err_cert), buf, 256); if (verbose==1) printf("Peer cert verify depth=%d %s\n", depth, buf); if (!ok) { printf("verify error:num=%d:%s\n", err, X509_verify_cert_error_string(err)); if (verify_depth >= depth) { ok = 1; verify_error = X509_V_OK; } else { ok = 0; verify_error = X509_V_ERR_CERT_CHAIN_TOO_LONG; } } switch (err) { case X509_V_ERR_UNABLE_TO_GET_ISSUER_CERT: X509_NAME_oneline(X509_get_issuer_name(err_cert), buf, 256); printf("issuer= %s\n", buf); break; case X509_V_ERR_CERT_NOT_YET_VALID: case X509_V_ERR_ERROR_IN_CERT_NOT_BEFORE_FIELD: printf("cert not yet valid\n"); break; case X509_V_ERR_CERT_HAS_EXPIRED: case X509_V_ERR_ERROR_IN_CERT_NOT_AFTER_FIELD: printf("cert has expired\n"); break; } if (verbose==1) printf("verify return:%d\n", ok); return (ok); } #if OPENSSL_VERSION_NUMBER < 0x10100000L /* taken from OpenSSL apps/s_cb.c */ static RSA *tmp_rsa_cb(SSL * s __attribute__((unused)), int export __attribute__((unused)), int keylength) { static RSA *rsa_tmp = NULL; if (rsa_tmp == NULL) { rsa_tmp = RSA_generate_key(keylength, RSA_F4, NULL, NULL); } return (rsa_tmp); } #endif /* taken from OpenSSL apps/s_cb.c * tim - this seems to just be giving logging messages */ static void apps_ssl_info_callback(const SSL * s, int where, int ret) { char *str; int w; if (verbose==0) return; w = where & ~SSL_ST_MASK; if (w & SSL_ST_CONNECT) str = "SSL_connect"; else if (w & SSL_ST_ACCEPT) str = "SSL_accept"; else str = "undefined"; if (where & SSL_CB_LOOP) { printf("%s:%s\n", str, SSL_state_string_long(s)); } else if (where & SSL_CB_ALERT) { str = (where & SSL_CB_READ) ? "read" : "write"; if ((ret & 0xff) != SSL3_AD_CLOSE_NOTIFY) printf("SSL3 alert %s:%s:%s\n", str, SSL_alert_type_string_long(ret), SSL_alert_desc_string_long(ret)); } else if (where & SSL_CB_EXIT) { if (ret == 0) printf("%s:failed in %s\n", str, SSL_state_string_long(s)); else if (ret < 0) { printf("%s:error in %s %i\n", str, SSL_state_string_long(s),ret); } } } /* * Seed the random number generator. */ static int tls_rand_init(void) { #ifdef EGD_SOCKET return (RAND_egd(EGD_SOCKET)); #else /* otherwise let OpenSSL do it internally */ return 0; #endif } static char *var_tls_CAfile=""; static char *var_tls_CApath=""; /* * This is the setup routine for the SSL client. * * The skeleton of this function is taken from OpenSSL apps/s_client.c. */ static int tls_init_clientengine(int verifydepth, char *var_tls_cert_file, char *var_tls_key_file) { int off = 0; int verify_flags = SSL_VERIFY_NONE; char *CApath; char *CAfile; char *c_cert_file; char *c_key_file; if (verbose==1) printf("starting TLS engine\n"); SSL_load_error_strings(); SSLeay_add_ssl_algorithms(); if (tls_rand_init() == -1) { printf("TLS engine: cannot seed PRNG\n"); return IMTEST_FAIL; } #if (OPENSSL_VERSION_NUMBER >= 0x10100000L) tls_ctx = SSL_CTX_new(TLS_client_method()); #else tls_ctx = SSL_CTX_new(SSLv23_client_method()); #endif if (tls_ctx == NULL) { return IMTEST_FAIL; }; off |= SSL_OP_ALL; /* Work around all known bugs */ off |= SSL_OP_NO_SSLv2; /* Disable insecure SSLv2 */ off |= SSL_OP_NO_SSLv3; /* Disable insecure SSLv3 */ off |= SSL_OP_NO_COMPRESSION; /* Disable TLS compression */ SSL_CTX_set_options(tls_ctx, off); SSL_CTX_set_info_callback(tls_ctx, apps_ssl_info_callback); if (strlen(var_tls_CAfile) == 0) CAfile = NULL; else CAfile = var_tls_CAfile; if (strlen(var_tls_CApath) == 0) CApath = NULL; else CApath = var_tls_CApath; if (CAfile || CApath) if ((!SSL_CTX_load_verify_locations(tls_ctx, CAfile, CApath)) || (!SSL_CTX_set_default_verify_paths(tls_ctx))) { printf("TLS engine: cannot load CA data\n"); return IMTEST_FAIL; } if (strlen(var_tls_cert_file) == 0) c_cert_file = NULL; else c_cert_file = var_tls_cert_file; if (strlen(var_tls_key_file) == 0) c_key_file = NULL; else c_key_file = var_tls_key_file; if (c_cert_file || c_key_file) if (!set_cert_stuff(tls_ctx, c_cert_file, c_key_file)) { printf("TLS engine: cannot load cert/key data, may be a cert/key mismatch?\n"); return IMTEST_FAIL; } #if OPENSSL_VERSION_NUMBER < 0x10100000L SSL_CTX_set_tmp_rsa_callback(tls_ctx, tmp_rsa_cb); #endif verify_depth = verifydepth; SSL_CTX_set_verify(tls_ctx, verify_flags, verify_callback); return IMTEST_OK; } /* * taken from OpenSSL crypto/bio/b_dump.c, modified to save a lot of strcpy * and strcat by Matti Aarnio. */ #define TRUNCATE #define DUMP_WIDTH 16 static int tls_dump(const char *s, int len) { int ret = 0; char buf[160 + 1]; char *ss; int i; int j; int rows; int trunc; unsigned char ch; trunc = 0; #ifdef TRUNCATE for (; (len > 0) && ((s[len - 1] == ' ') || (s[len - 1] == '\0')); len--) trunc++; #endif rows = (len / DUMP_WIDTH); if ((rows * DUMP_WIDTH) < len) rows++; for (i = 0; i < rows; i++) { buf[0] = '\0'; /* start with empty string */ ss = buf; sprintf(ss, "%04x ", i * DUMP_WIDTH); ss += strlen(ss); for (j = 0; j < DUMP_WIDTH; j++) { if (((i * DUMP_WIDTH) + j) >= len) { strcpy(ss, " "); } else { ch = ((unsigned char) *((char *) (s) + i * DUMP_WIDTH + j)) & 0xff; sprintf(ss, "%02x%c", ch, j == 7 ? '|' : ' '); ss += 3; } } ss += strlen(ss); *ss+= ' '; for (j = 0; j < DUMP_WIDTH; j++) { if (((i * DUMP_WIDTH) + j) >= len) break; ch = ((unsigned char) *((char *) (s) + i * DUMP_WIDTH + j)) & 0xff; *ss+= (((ch >= ' ') && (ch <= '~')) ? ch : '.'); if (j == 7) *ss+= ' '; } *ss = 0; /* * if this is the last call then update the ddt_dump thing so that * we will move the selection point in the debug window */ printf("%s\n", buf); ret += strlen(buf); } #ifdef TRUNCATE if (trunc > 0) { sprintf(buf, "%04x - \n", len+ trunc); printf("%s\n", buf); ret += strlen(buf); } #endif return (ret); } /* taken from OpenSSL apps/s_cb.c */ static long bio_dump_cb(BIO * bio, int cmd, const char *argp, int argi, long argl __attribute__((unused)), long ret) { if (!do_dump) return (ret); if (cmd == (BIO_CB_READ | BIO_CB_RETURN)) { printf("read from %08lX [%08lX] (%d bytes => %ld (0x%lX))\n", (unsigned long) bio, (unsigned long) argp, argi, ret, ret); tls_dump(argp, (int) ret); return (ret); } else if (cmd == (BIO_CB_WRITE | BIO_CB_RETURN)) { printf("write to %08lX [%08lX] (%d bytes => %ld (0x%lX))\n", (unsigned long) bio, (unsigned long) argp, argi, ret, ret); tls_dump(argp, (int) ret); } return (ret); } static int tls_start_clienttls(unsigned *layer, char **authid) { int sts; const SSL_CIPHER *cipher; X509 *peer; if (verbose==1) printf("setting up TLS connection\n"); if (tls_conn == NULL) { tls_conn = (SSL *) SSL_new(tls_ctx); } if (tls_conn == NULL) { printf("Could not allocate 'con' with SSL_new()\n"); return IMTEST_FAIL; } SSL_clear(tls_conn); if (!SSL_set_fd(tls_conn, sock)) { printf("SSL_set_fd failed\n"); return IMTEST_FAIL; } /* * This is the actual handshake routine. It will do all the negotiations * and will check the client cert etc. */ SSL_set_connect_state(tls_conn); /* * We do have an SSL_set_fd() and now suddenly a BIO_ routine is called? * Well there is a BIO below the SSL routines that is automatically * created for us, so we can use it for debugging purposes. */ if (verbose==1) BIO_set_callback(SSL_get_rbio(tls_conn), bio_dump_cb); /* Dump the negotiation for loglevels 3 and 4 */ if (verbose==1) do_dump = 1; if (tls_sess) /* Reuse a session if we have one */ SSL_set_session(tls_conn, tls_sess); if ((sts = SSL_connect(tls_conn)) <= 0) { printf("SSL_connect error %d\n", sts); tls_sess = SSL_get_session(tls_conn); if (tls_sess) { SSL_CTX_remove_session(tls_ctx, tls_sess); tls_sess = NULL; printf("SSL session removed\n"); } if (tls_conn!=NULL) SSL_free(tls_conn); tls_conn = NULL; return IMTEST_FAIL; } /* * Lets see, whether a peer certificate is available and what is * the actual information. We want to save it for later use. */ peer = SSL_get_peer_certificate(tls_conn); if (peer != NULL) { X509_NAME_get_text_by_NID(X509_get_subject_name(peer), NID_commonName, peer_CN, CCERT_BUFSIZ); tls_peer_CN = peer_CN; X509_NAME_get_text_by_NID(X509_get_issuer_name(peer), NID_commonName, issuer_CN, CCERT_BUFSIZ); if (verbose==1) printf("subject_CN=%s, issuer_CN=%s\n", peer_CN, issuer_CN); tls_issuer_CN = issuer_CN; } tls_protocol = SSL_get_version(tls_conn); cipher = SSL_get_current_cipher(tls_conn); tls_cipher_name = SSL_CIPHER_get_name(cipher); tls_cipher_usebits = SSL_CIPHER_get_bits(cipher, &tls_cipher_algbits); if (layer!=NULL) *layer = tls_cipher_usebits; if (authid!=NULL) *authid = tls_peer_CN; printf("TLS connection established: %s with cipher %s (%d/%d bits)\n", tls_protocol, tls_cipher_name, tls_cipher_usebits, tls_cipher_algbits); return IMTEST_OK; } static void do_starttls(int ssl, char *keyfile, unsigned *ssf) { int result; char *auth_id; result=tls_init_clientengine(10, keyfile, keyfile); if (result!=IMTEST_OK) { if (ssl) { imtest_fatal("Start TLS engine failed\n"); } else { printf("Start TLS engine failed\n"); return; } } else { result=tls_start_clienttls(ssf, &auth_id); if (result!=IMTEST_OK) imtest_fatal("TLS negotiation failed!\n"); } /* TLS negotiation suceeded */ tls_sess = SSL_get_session(tls_conn); /* Save the session for reuse */ /* tell SASL about the negotiated layer */ result=sasl_setprop(conn, SASL_SSF_EXTERNAL, ssf); if (result!=SASL_OK) imtest_fatal("Error setting SASL property (external ssf)"); result=sasl_setprop(conn, SASL_AUTH_EXTERNAL, auth_id); if (result!=SASL_OK) imtest_fatal("Error setting SASL property (external auth_id)"); prot_settls (pin, tls_conn); prot_settls (pout, tls_conn); } #endif /* HAVE_SSL */ static sasl_security_properties_t *make_secprops(int min,int max) { sasl_security_properties_t *ret=(sasl_security_properties_t *) malloc(sizeof(sasl_security_properties_t)); ret->maxbufsize=1024; ret->min_ssf=min; ret->max_ssf=max; ret->security_flags=0; ret->property_names=NULL; ret->property_values=NULL; return ret; } /* * Initialize SASL and set necessary options */ static int init_sasl(char *service, char *serverFQDN, int minssf, int maxssf, unsigned flags) { int saslresult; sasl_security_properties_t *secprops=NULL; socklen_t addrsize; char localip[60], remoteip[60]; struct sockaddr_storage saddr_l; struct sockaddr_storage saddr_r; addrsize=sizeof(struct sockaddr_storage); if (getpeername(sock,(struct sockaddr *)&saddr_r,&addrsize)!=0) return IMTEST_FAIL; addrsize=sizeof(struct sockaddr_storage); if (getsockname(sock,(struct sockaddr *)&saddr_l,&addrsize)!=0) return IMTEST_FAIL; if(iptostring((struct sockaddr *)&saddr_l, addrsize, localip, 60)) return IMTEST_FAIL; if(iptostring((struct sockaddr *)&saddr_r, addrsize, remoteip, 60)) return IMTEST_FAIL; /* client new connection */ saslresult=sasl_client_new(service, serverFQDN, localip, remoteip, NULL, flags, &conn); if (saslresult!=SASL_OK) return IMTEST_FAIL; /* create a security structure and give it to sasl */ secprops = make_secprops(minssf, maxssf); if (secprops != NULL) { sasl_setprop(conn, SASL_SEC_PROPS, secprops); free(secprops); } return IMTEST_OK; } #define BUFSIZE 16384 static imt_stat getauthline(struct sasl_cmd_t *sasl_cmd, char **line, int *linelen) { char buf[BUFSIZE]; int saslresult; unsigned len; char *str=(char *) buf; int ret = STAT_CONT; *line = NULL; *linelen = 0; do { str = prot_fgets(str, BUFSIZE, pin); if (str == NULL) imtest_fatal("prot layer failure"); printf("S: %s",str); } while(str[0] == '*'); /* Ignore potential untagged responses */ if (!strncasecmp(str, sasl_cmd->ok, strlen(sasl_cmd->ok))) { if (sasl_cmd->parse_success) { str = sasl_cmd->parse_success(str); if (!str) return STAT_OK; ret = STAT_OK; } else { return STAT_OK; } } else if (!strncasecmp(str, sasl_cmd->fail, strlen(sasl_cmd->fail))) { return STAT_NO; } else if (sasl_cmd->cont) { str += strlen(sasl_cmd->cont); /* jump past the continuation */ } else { /* literal */ len = atoi(str+1); str = prot_fgets(str, BUFSIZE, pin); if (str == NULL || strlen(str) < len) imtest_fatal("prot layer failure"); printf("S: %s", str); } if (*str != '\r') { /* trim CRLF */ char *p = str + strlen(str) - 1; if (p >= str && *p == '\n') *p-- = '\0'; if (p >= str && *p == '\r') *p-- = '\0'; /* alloc space for decoded response */ len = strlen(str) + 1; *line = malloc(len); if ((*line) == NULL) { return STAT_NO; } /* decode this line */ saslresult = sasl_decode64(str, strlen(str), *line, len, (unsigned *) linelen); if (saslresult != SASL_OK) { printf("base64 decoding error\n"); return STAT_NO; } } else { /* this is a blank */ *line = NULL; *linelen = 0; } return ret; } static void interaction (int id, const char *challenge, const char *prompt, char **tresult, unsigned int *tlen) { char *s; char result[1024]; if (id==SASL_CB_PASS && !cmdline_password) { printf("%s: ", prompt); s = xstrdup(cyrus_getpass("")); strarray_appendm(&stashed_strings, s); *tlen = strlen(s); *tresult = s; return; } else if (id==SASL_CB_PASS && cmdline_password) { strcpy(result, cmdline_password); } else if (id==SASL_CB_USER) { if (username != NULL) { strcpy(result, username); } else { strcpy(result, ""); } } else if (id==SASL_CB_AUTHNAME) { if (authname != NULL) { strcpy(result, authname); } else { strcpy(result, getpwuid(getuid())->pw_name); } #ifdef SASL_CB_GETREALM } else if ((id==SASL_CB_GETREALM) && (realm != NULL)) { strcpy(result, realm); #endif } else { int c; if (((id==SASL_CB_ECHOPROMPT) || (id==SASL_CB_NOECHOPROMPT)) && (challenge != NULL)) { printf("Server challenge: %s\n", challenge); } printf("%s: ",prompt); if (id==SASL_CB_NOECHOPROMPT) { strcpy(result, cyrus_getpass("")); } else { result[0] = '\0'; if (fgets(result, sizeof(result) - 1, stdin) != NULL) { c = strlen(result); result[c - 1] = '\0'; } } } s = xstrdup(result); strarray_appendm(&stashed_strings, s); *tlen = strlen(s); *tresult = s; } static void fillin_interactions(sasl_interact_t *tlist) { while (tlist->id!=SASL_CB_LIST_END) { interaction(tlist->id, tlist->challenge, tlist->prompt, (void *) &(tlist->result), &(tlist->len)); tlist++; } } static char *waitfor(char *tag, char *tag2, int echo) { static char str[1024]; do { if (prot_fgets(str, sizeof(str), pin) == NULL) { imtest_fatal("prot layer failure"); } if(echo) printf("S: %s", str); } while (strncmp(str, tag, strlen(tag)) && (tag2 ? strncmp(str, tag2, strlen(tag2)) : 1)); return str; } static int auth_sasl(struct sasl_cmd_t *sasl_cmd, char *mechlist) { sasl_interact_t *client_interact = NULL; int saslresult; const char *out = NULL; unsigned int outlen = 0; char *in; int inlen; const char *mechusing; char inbase64[4096]; int inbase64len; char cmdbuf[40]; int sendliteral; int initial_response = 1; imt_stat status; if (!sasl_cmd || !sasl_cmd->cmd) return IMTEST_FAIL; sendliteral = sasl_cmd->quote; do { /* start authentication */ saslresult = sasl_client_start(conn, mechlist, &client_interact, /* do we support initial response? */ sasl_cmd->maxlen ? &out : NULL, &outlen, &mechusing); if (saslresult == SASL_INTERACT) fillin_interactions(client_interact); /* fill in prompts */ } while (saslresult == SASL_INTERACT); if ((saslresult != SASL_OK) && (saslresult != SASL_CONTINUE)) { return saslresult; } /* build the auth command */ if (sasl_cmd->quote) { sprintf(cmdbuf, "%s \"%s\"", sasl_cmd->cmd, mechusing); } else { sprintf(cmdbuf, "%s %s", sasl_cmd->cmd, mechusing); } printf("C: %s", cmdbuf); prot_printf(pout, "%s", cmdbuf); if (out) { /* initial response */ if (!outlen) { /* empty initial response */ printf(" ="); prot_printf(pout, " ="); out = NULL; } else if (!sendliteral && ((int) (strlen(cmdbuf) + outlen + 3) > sasl_cmd->maxlen)) { /* initial response is too long for auth command, so wait for a server challenge before sending it */ goto noinitresp; } else { /* full response -- encoded below */ printf(" "); prot_printf(pout, " "); } } else { goto noinitresp; } do { if (out) { /* response */ /* convert to base64 */ saslresult = sasl_encode64(out, outlen, inbase64, sizeof(inbase64), (unsigned *) &inbase64len); if (saslresult != SASL_OK) return saslresult; /* send to server */ if (sendliteral) { printf("%s{%d+}\r\n", initial_response ? "" : "C: ", inbase64len); prot_printf(pout, "{%d+}\r\n", inbase64len); prot_flush(pout); } printf("%s%s", initial_response ? "" : "C: ", inbase64); prot_write(pout, inbase64, inbase64len); out = NULL; } else if (sendliteral) { /* If we had no response, we still need to send the empty literal in this case */ printf("{0+}\r\nC: "); prot_printf(pout, "{0+}\r\n"); } else if (!initial_response) { printf("C: "); } noinitresp: initial_response = 0; printf("\r\n"); prot_printf(pout, "\r\n"); prot_flush(pout); /* get challenge/reply from the server */ status = getauthline(sasl_cmd, &in, &inlen); if ((status == STAT_CONT || (status == STAT_OK && in)) && (inlen || !out)) { /* no delayed initial response */ do { /* do the next step */ saslresult = sasl_client_step(conn, in, inlen, &client_interact, &out, &outlen); if (saslresult == SASL_INTERACT) fillin_interactions(client_interact); /* fill in prompts */ } while (saslresult == SASL_INTERACT); if (in) free(in); } if ((saslresult != SASL_OK) && (saslresult != SASL_CONTINUE)) { /* cancel the exchange */ printf("C: %s\r\n", sasl_cmd->cancel); prot_printf(pout, "%s\r\n", sasl_cmd->cancel); prot_flush(pout); return saslresult; } sendliteral = !sasl_cmd->cont; } while (status == STAT_CONT); return (status == STAT_OK) ? IMTEST_OK : IMTEST_FAIL; } /* initialize the network */ static int init_net(char *serverFQDN, char *port) { struct addrinfo hints, *res0 = NULL, *res; int err; memset(&hints, 0, sizeof(hints)); hints.ai_family = PF_UNSPEC; hints.ai_socktype = SOCK_STREAM; hints.ai_flags = AI_CANONNAME; if ((err = getaddrinfo(serverFQDN, port, &hints, &res0)) != 0) { fprintf(stderr, "getaddrinfo: %s\n", gai_strerror(err)); return IMTEST_FAIL; } if (res0->ai_canonname) strncpy(serverFQDN, res0->ai_canonname, 1023); for (res = res0; res; res = res->ai_next) { sock = socket(res->ai_family, res->ai_socktype, res->ai_protocol); if (sock < 0) continue; if (connect(sock, res->ai_addr, res->ai_addrlen) >= 0) break; close(sock); sock = -1; } freeaddrinfo(res0); if(sock < 0) { perror("connect"); return IMTEST_FAIL; } return IMTEST_OK; } static void logout(struct logout_cmd_t *logout_cmd, int wait) { printf("C: %s\r\n", logout_cmd->cmd); prot_printf(pout, "%s\r\n", logout_cmd->cmd); prot_flush(pout); /* only wait if we are explicitly told to */ if(wait) waitfor(logout_cmd->resp, NULL, 1); } static int gotsigint = 0; static void sigint_handler(int sig __attribute__((unused))) { gotsigint = 1; } static int haveinput(struct protstream *s) { /* Is something currently pending in our protstream's buffer? */ #ifdef HAVE_SSL if (s->cnt == 0 && s->tls_conn != NULL) { /* Maybe there's data pending in the SSL buffer? */ int n = SSL_pending(s->tls_conn); if (verbose) printf("SSL_pending=%d\n", n); return n; } #endif return s->cnt; } /* This needs to support 3 modes: * * 1. Terminal Interface Only * 2. File input * 3. Redirect to a unix socket - This mode needs to be sure that the * IMAP session is in an unselected state whenever the unix socket is * disconnected. * */ static void interactive(struct protocol_t *protocol, char *filename) { char buf[2048]; fd_set read_set, rset; fd_set write_set, wset; fd_set accept_set, aset; int nfds; int nfound; int count; int fd = 0, fd_out = 1, listen_sock = -1; void *rock = NULL; int donewritingfile = 0; struct sockaddr_un sunsock; int salen; /* open the file if available */ if (filename != NULL) { if ((fd = open(filename, O_RDONLY)) == -1) { fprintf(stderr,"Unable to open file: %s:", filename); perror(""); exit(1); } } else if(output_socket) { struct timeval tv; struct stat sbuf; /* can't have this and a file for input */ sunsock.sun_family = AF_UNIX; strlcpy(sunsock.sun_path, output_socket, sizeof(sunsock.sun_path)); unlink(output_socket); listen_sock = socket(AF_UNIX, SOCK_STREAM, 0); if(listen_sock < 0) imtest_fatal("could not create output socket"); salen = sizeof(sunsock.sun_family) + strlen(sunsock.sun_path) + 1; if((bind(listen_sock, (struct sockaddr *)&sunsock, salen)) < 0) { imtest_fatal("could not bind output socket"); } if((listen(listen_sock, 5)) < 0) { imtest_fatal("could not listen to output socket"); } if(stat(output_socket, &sbuf) == -1) { imtest_fatal("could not stat output socket"); } output_socket_opened = 1; output_socket_ino = sbuf.st_ino; FD_ZERO(&accept_set); FD_SET(listen_sock, &accept_set); accept_again: if(rock) { free(rock); rock = NULL; } tv.tv_sec = 600; /* 10 minute timeout - xxx protocol specific? */ tv.tv_usec = 0; aset = accept_set; /* Have the separate select so that signals will wake us up * and we get a timeout to use on our own imap connection */ if(select(listen_sock + 1, &aset, NULL, NULL, &tv) <= 0) { /* either we timed out or had an error */ goto cleanup; } fd = fd_out = accept(listen_sock, NULL, NULL); if(fd < 0) imtest_fatal("accept failure"); if(protocol->init_conn) rock = protocol->init_conn(); } FD_ZERO(&read_set); FD_SET(fd, &read_set); /* In the terminal case fd == 0 */ FD_SET(sock, &read_set); FD_ZERO(&write_set); FD_SET(fd_out, &write_set); FD_SET(sock, &write_set); nfds = fd; if (nfds < sock) nfds = sock; if (nfds < fd_out) nfds = fd_out; nfds++; if (filename != NULL) { donewritingfile = 0; } /* add handler for SIGINT */ signal(SIGINT, sigint_handler); /* loop reading from network and from stdin as applicable */ while (1) { rset = read_set; wset = write_set; nfound = select(nfds, &rset, &wset, NULL, NULL); if (nfound < 0) { perror("select"); imtest_fatal("select"); } if (!output_socket && (FD_ISSET(0, &rset)) && (FD_ISSET(sock, &wset))) { /* There is explicit terminal input -- note this is only possible * if fd is 0 (and we are in terminal mode!). * We need to use stream API for this, which is why it * is different */ if (fgets(buf, sizeof (buf) - 1, stdin) == NULL) { logout(&protocol->logout_cmd, 0); FD_CLR(0, &read_set); } else { count = strlen(buf); /* If we read a full line, translate the newline * if necessary. */ if (buf[count - 1] == '\n' && (count < 2 || buf[count - 2] != '\r')) { buf[count - 1] = '\r'; buf[count] = '\n'; buf[count + 1] = '\0'; count++; } prot_write(pout, buf, count); } prot_flush(pout); } else if (FD_ISSET(sock, &rset) && (FD_ISSET(fd_out, &wset))) { /* This does input from remote for all modes */ do { count = prot_read(pin, buf, sizeof (buf) - 1); if (count == 0) { const char *str = prot_error(pin); if (str && strcmp(str, PROT_EOF_STRING)) { printf("Protection error: %s\n", prot_error(pin)); } close(sock); printf("Connection closed.\n"); return; } if (count < 0) { perror("read"); imtest_fatal("prot_read"); } if(output_socket) retry_write(fd_out, buf, count); else { /* use the stream API */ buf[count] = '\0'; printf("%s", buf); } } while (haveinput(pin) > 0); } else if ((FD_ISSET(fd, &rset)) && (FD_ISSET(sock, &wset)) && (donewritingfile == 0)) { /* This does input for both socket and file modes */ int numr = read(fd, buf, sizeof(buf)); /* and send out over wire */ if (numr < 0) { perror("read"); imtest_fatal("read"); } else if (numr==0) { if(output_socket) { if(protocol->reset) { if(protocol->reset(rock) != IMTEST_OK) goto cleanup; } else /* no protocol->reset, we're done */ goto cleanup; close(fd); fd = 0; fd_out = 1; goto accept_again; } else { /* we're done, cleanup */ donewritingfile = 1; FD_CLR(fd,&read_set); /* send LOGOUT */ logout(&protocol->logout_cmd, 0); } } else { if (!output_socket) { /* echo for the user - if not in socket mode */ retry_write(1, buf, numr); } if (output_socket && protocol->pipe) { if(protocol->pipe(buf, numr, rock) == IMTEST_CLOSEME) { if(protocol->reset) { if(protocol->reset(rock) != IMTEST_OK) goto cleanup; } else /* no protocol->reset, we're done */ goto cleanup; close(fd); fd = 0; fd_out = 1; goto accept_again; } } else { /* echo to remote */ prot_write(pout, buf, numr); prot_flush(pout); } } } else { /* if can't do anything else sleep */ usleep(1000); } /* received interrupt signal, logout */ if (gotsigint) goto cleanup; } cleanup: if(rock) free(rock); if(output_socket && output_socket_opened) { struct stat sbuf; close(fd); if (listen_sock != -1) close(listen_sock); if(stat(output_socket, &sbuf) != -1 && sbuf.st_ino == output_socket_ino) { unlink(output_socket); } } logout(&protocol->logout_cmd, 0); close(sock); printf("Connection closed.\n"); /* remove handler for SIGINT */ signal(SIGINT, SIG_DFL); return; } enum { AUTO_BANNER = -1, AUTO_NO = 0, AUTO_YES = 1 }; enum { CAPA_LOGIN = (1 << 0), CAPA_STARTTLS = (1 << 1), CAPA_COMPRESS = (1 << 2) }; static char *ask_capability(struct protocol_t *prot, unsigned long *capabilities, int automatic) { char str[1024] = ""; char *ret = NULL, *tmp, *resp; /* default state of login command unless toggled by capabilities */ *capabilities = prot->login_enabled; resp = (automatic == AUTO_BANNER) ? prot->banner.resp : prot->capa_cmd.resp; if (!automatic) { /* no capability command */ if (!prot->capa_cmd.cmd) return NULL; /* request capabilities of server */ printf("C: %s\r\n", prot->capa_cmd.cmd); prot_printf(pout, "%s\r\n", prot->capa_cmd.cmd); prot_flush(pout); } do { /* look for the end of the capabilities */ if (prot_fgets(str, sizeof(str), pin) == NULL) { if (!*str) imtest_fatal("prot layer failure"); else break; } printf("S: %s", str); /* check for login - toggles existing state */ if (prot->capa_cmd.login && strstr(str, prot->capa_cmd.login) != NULL) { *capabilities ^= CAPA_LOGIN; } /* check for starttls */ if (prot->capa_cmd.tls && strstr(str, prot->capa_cmd.tls) != NULL) { *capabilities |= CAPA_STARTTLS; } /* check for compress */ if (prot->capa_cmd.compress && strstr(str, prot->capa_cmd.compress) != NULL) { *capabilities |= CAPA_COMPRESS; } /* check for auth */ if (prot->capa_cmd.auth && (tmp = strstr(str, prot->capa_cmd.auth)) != NULL) { if (ret) free(ret); if (prot->capa_cmd.parse_mechlist) ret = prot->capa_cmd.parse_mechlist(str, prot); else ret = strdup(tmp+strlen(prot->capa_cmd.auth)); } if (!resp) { /* multiline response with no distinct end (IMAP banner) */ prot_NONBLOCK(pin); } /* look for the end of the capabilities */ } while (!resp || strncasecmp(str, resp, strlen(resp))); prot_BLOCK(pin); return ret; } /* generic pipe functionality - break it into one line at a time, and * pass that into a per-protocol pipe function. */ struct generic_context_t { int (*pipe_oneline)(char *buf, int len, void *rock); void *rock; /* Deal with half-finished lines */ char *midLine; size_t midLineLen; }; static int generic_pipe(char *buf, int len, void *rock) { struct generic_context_t *text = (struct generic_context_t *)rock; char *toWrite = NULL, *toSend = NULL; int toWriteLen = 0; char *lineEnd = NULL; int ret = IMTEST_OK; /* do we have leftovers? -- if so, we append the new stuff */ if(text->midLine) { text->midLine = (char *)xrealloc(text->midLine, text->midLineLen+len+1); memcpy(text->midLine+text->midLineLen, buf, len); text->midLineLen += len; text->midLine[text->midLineLen] = '\0'; toWrite = text->midLine; toWriteLen = text->midLineLen; } else { toWrite = buf; toWriteLen = len; } /* one line at a time now */ while(toWrite && (lineEnd = memchr(toWrite, '\n', toWriteLen)) != NULL) { size_t len_todo; len_todo = lineEnd - toWrite + 1; /* +1 is to include the newline! */ toSend = (char *)xrealloc(toSend, len_todo + 1); memcpy(toSend, toWrite, len_todo); toSend[len_todo] = '\0'; ret = text->pipe_oneline(toSend, len_todo, text->rock); if(ret != IMTEST_OK) break; toWrite = lineEnd+1; /* +1 is to skip the newline! */ toWriteLen -= len_todo; if(toWriteLen <= 0) toWrite = NULL; } if(toWrite && ret == IMTEST_OK) { char *newMidLine; /* we need to save the leftover for next time */ newMidLine = (char *)xmalloc(toWriteLen); memcpy(newMidLine, toWrite, toWriteLen); if(text->midLine) free(text->midLine); text->midLine = newMidLine; text->midLineLen = toWriteLen; } else if (text->midLine || ret != IMTEST_OK) { free(text->midLine); text->midLine = NULL; text->midLineLen = 0; } free(toSend); return ret; } /*********************************** IMAP ************************************/ /* * Parse a mech list of the form: ... AUTH=foo AUTH=bar ... * * Return: string with mechs separated by spaces * */ static char *imap_parse_mechlist(const char *str, struct protocol_t *prot) { char *ret = xzmalloc(strlen(str)+1); char *tmp; int num = 0; if (strstr(str, " SASL-IR")) { /* server supports initial response in AUTHENTICATE command */ prot->sasl_cmd.maxlen = USHRT_MAX; } while ((tmp = strstr(str, " AUTH="))) { char *end = (tmp += 6); while((*end != ' ') && (*end != '\0')) end++; /* add entry to list */ if (num++ > 0) strcat(ret, " "); strlcat(ret, tmp, strlen(ret) + (end - tmp) + 1); /* reset the string */ str = end; } return ret; } static int auth_imap(void) { char str[1024]; /* we need username and password to do "login" */ char *username; unsigned int userlen; char *pass; unsigned int passlen; char *tag = "L01 "; str[0] = '\0'; interaction(SASL_CB_AUTHNAME, NULL, "Authname", &username, &userlen); interaction(SASL_CB_PASS, NULL, "Please enter your password", &pass, &passlen); printf("C: %sLOGIN %s {%d}\r\n", tag, username, passlen); prot_printf(pout,"%sLOGIN %s {%d}\r\n", tag, username, passlen); prot_flush(pout); if (!strncmp(waitfor("+", tag, 1), "+", 1)) { printf("C: \r\n"); prot_printf(pout,"%s\r\n", pass); prot_flush(pout); do { if (prot_fgets(str, sizeof(str), pin) == NULL) { imtest_fatal("prot layer failure"); } printf("S: %s", str); } while (strncmp(str, tag, strlen(tag))); } if (!strncasecmp(str+strlen(tag), "OK", 2)) { return IMTEST_OK; } else { return IMTEST_FAIL; } } static int imap_do_auth(struct sasl_cmd_t *sasl_cmd, void *rock __attribute__((unused)), int login_enabled, char *mech, char *mechlist) { int result = IMTEST_FAIL; if (mech) { if (!strcasecmp(mech, "login")) { if (!login_enabled) { printf("[Server advertised LOGINDISABLED]\n"); } else { result = auth_imap(); } } else if (!mechlist || !stristr(mechlist, mech)) { printf("[Server did not advertise AUTH=%s]\n", ucase(mech)); } else { result = auth_sasl(sasl_cmd, mech); } } else { if (mechlist) { result = auth_sasl(sasl_cmd, mechlist); } else if (login_enabled) { result = auth_imap(); } } return result; } struct imap_context_t { int inLiteral; }; static int imap_pipe_oneline(char *buf, int len, void *rock) { struct imap_context_t *text = (struct imap_context_t *)rock; int add_crlf = 0; /* hack for terminals */ if(text->inLiteral) { if(len <= text->inLiteral) { text->inLiteral -= len; } else { prot_write(pout, buf, text->inLiteral); buf += text->inLiteral; len -= text->inLiteral; text->inLiteral = 0; } } if(!text->inLiteral) { char c, *tag, *cmd, *tmp, *sparebuf = (char *)xstrdup(buf); int i; tmp = sparebuf; if(len > 4 && buf[len-1] == '\n' && buf[len-1] == '\r' && buf[len-2] == '}') { /* possible literal, with \r */ i = len-4; while(i > 0 && buf[i] != '{' && Uisdigit(buf[i])) i--; if(buf[i] == '{') text->inLiteral = atoi(buf + i + 1); } else if(len > 3 && buf[len-1] == '\n' && buf[len-2] == '}') { /* possible literal, no \r -- hack for terminals*/ i = len-3; while(i > 0 && buf[i] != '{' && Uisdigit(buf[i])) i--; if(buf[i] == '{') text->inLiteral = atoi(buf + i + 1); } /* We could still have another special case! */ c = imparse_word(&tmp, &tag); if(c == ' ') { c = imparse_word(&tmp, &cmd); if(c == '\n' || (c == '\r' && *tmp == '\n')){ /* Are we logging out? */ if(!strncasecmp(cmd, "LOGOUT", 6)) { free(sparebuf); return IMTEST_CLOSEME; } } } free(sparebuf); /* If the remote is sending only \n, clean it up for them */ if((len == 1 && buf[0] == '\n') || (len >= 2 && buf[len-2] != '\r')) { len -= 1; /* truncate \n */ add_crlf = 1; } } prot_write(pout, buf, len); if(add_crlf) prot_write(pout, "\r\n", 2); prot_flush(pout); return IMTEST_OK; } static void * imap_init_conn(void) { struct generic_context_t *ret; ret = (void *)xmalloc(sizeof(struct generic_context_t)); memset(ret, 0, sizeof(struct generic_context_t)); ret->rock = (void *)xmalloc(sizeof(struct imap_context_t)); memset(ret->rock, 0, sizeof(struct imap_context_t)); ret->pipe_oneline = &imap_pipe_oneline; return ret; } static int imap_reset(void *rock) { struct generic_context_t *gentext = (struct generic_context_t *)rock; struct imap_context_t *text = (struct imap_context_t *)gentext->rock; char tag[64]; static int i=0; if(text->inLiteral || gentext->midLine) return IMTEST_FAIL; snprintf(tag, sizeof(tag) - 1, "UN%d", i); prot_printf(pout, "%s UNSELECT\r\n", tag); prot_flush(pout); waitfor(tag, NULL, 0); return IMTEST_OK; } #define HEADERS "Date: Mon, 7 Feb 1994 21:52:25 -0800 (PST)\r\n \ From: Fred Foobar \r\n \ Subject: afternoon meeting\r\n \ To: mooch@owatagu.siam.edu\r\n \ Message-Id: \r\n \ MIME-Version: 1.0\r\n \ Content-Type: TEXT/PLAIN; CHARSET=US-ASCII\r\n\r\n" static int append_msg(char *mbox, int size) { int lup; prot_printf(pout,"A003 APPEND %s (\\Seen) {" SIZE_T_FMT "}\r\n", mbox,size+strlen(HEADERS)); /* do normal header foo */ prot_printf(pout,HEADERS); for (lup=0;lup' */ cp = str+3; while (cp && (start = strchr(cp, '<'))) { cp = start + 1; while (*cp && *cp != '@' && *cp != '<' && *cp != '>') cp++; if (*cp != '@') continue; while (*cp && *cp != '<' && *cp != '>') cp++; if (*cp == '>') { *(++cp) = '\0'; chal = strdup(start); if (!chal) imtest_fatal("memory error"); break; } } return chal; } static int auth_pop(void) { char str[1024]; /* we need username and password to do USER/PASS */ char *username; unsigned int userlen; char *pass; unsigned int passlen; interaction(SASL_CB_AUTHNAME, NULL, "Authname", &username, &userlen); printf("C: USER %s\r\n", username); prot_printf(pout,"USER %s\r\n", username); prot_flush(pout); if (prot_fgets(str, 1024, pin) == NULL) { imtest_fatal("prot layer failure"); } printf("S: %s", str); if (strncasecmp(str, "+OK", 3)) return IMTEST_FAIL; interaction(SASL_CB_PASS, NULL, "Please enter your password", &pass, &passlen); printf("C: PASS \r\n"); prot_printf(pout,"PASS %s\r\n",pass); prot_flush(pout); if (prot_fgets(str, 1024, pin) == NULL) { imtest_fatal("prot layer failure"); } printf("S: %s", str); if (!strncasecmp(str, "+OK", 3)) { return IMTEST_OK; } else { return IMTEST_FAIL; } } static int auth_apop(char *apop_chal) { char str[1024]; /* we need username and password to do "APOP" */ char *username; unsigned int userlen; char *pass; unsigned int passlen; int i; MD5_CTX ctx; unsigned char digest[MD5_DIGEST_LENGTH]; char digeststr[2*MD5_DIGEST_LENGTH+1]; interaction(SASL_CB_AUTHNAME, NULL, "Authname", &username, &userlen); interaction(SASL_CB_PASS,NULL, "Please enter your password", &pass, &passlen); MD5Init(&ctx); MD5Update(&ctx,apop_chal,strlen(apop_chal)); MD5Update(&ctx,pass,passlen); MD5Final(digest, &ctx); /* convert digest from binary to ASCII hex */ for (i = 0; i < 16; i++) sprintf(digeststr + (i*2), "%02x", digest[i]); printf("C: APOP %s %s\r\n", username, digeststr); prot_printf(pout,"APOP %s %s\r\n", username, digeststr); prot_flush(pout); if(prot_fgets(str, 1024, pin) == NULL) { imtest_fatal("prot layer failure"); } printf("S: %s", str); if (!strncasecmp(str, "+OK", 3)) { return IMTEST_OK; } else { return IMTEST_FAIL; } } static int pop3_do_auth(struct sasl_cmd_t *sasl_cmd, void *apop_chal, int user_enabled, char *mech, char *mechlist) { int result = IMTEST_FAIL; if (mech) { if (!strcasecmp(mech, "apop")) { if (!apop_chal) { printf("[Server did not advertise APOP challenge]\n"); } else { result = auth_apop((char *) apop_chal); } } else if (!strcasecmp(mech, "user")) { if (!user_enabled) { printf("[Server did not advertise USER]\n"); } else { result = auth_pop(); } } else if (!mechlist || !stristr(mechlist, mech)) { printf("[Server did not advertise SASL %s]\n", ucase(mech)); } else { result = auth_sasl(sasl_cmd, mech); } } else { if (mechlist) { result = auth_sasl(sasl_cmd, mechlist); } else if (apop_chal) { result = auth_apop((char *) apop_chal); } else if (user_enabled) { result = auth_pop(); } } return result; } /********************************** NNTP *************************************/ static int auth_nntp() { char str[1024]; /* we need username and password to do AUTHINFO USER/PASS */ char *username; unsigned int userlen; char *pass; unsigned int passlen; interaction(SASL_CB_AUTHNAME, NULL, "Authname", &username, &userlen); printf("C: AUTHINFO USER %s\r\n", username); prot_printf(pout,"AUTHINFO USER %s\r\n", username); prot_flush(pout); if (prot_fgets(str, 1024, pin) == NULL) { imtest_fatal("prot layer failure"); } printf("S: %s", str); if (!strncmp(str, "381", 3)) { interaction(SASL_CB_PASS, NULL, "Please enter your password", &pass, &passlen); printf("C: AUTHINFO PASS \r\n"); prot_printf(pout,"AUTHINFO PASS %s\r\n",pass); prot_flush(pout); if (prot_fgets(str, 1024, pin) == NULL) { imtest_fatal("prot layer failure"); } printf("S: %s", str); } if (!strncmp(str, "281", 3)) { return IMTEST_OK; } else { return IMTEST_FAIL; } } static int nntp_do_auth(struct sasl_cmd_t *sasl_cmd, void *rock __attribute__((unused)), int user_enabled, char *mech, char *mechlist) { int result = IMTEST_OK; if (mech) { if (!strcasecmp(mech, "user")) { if (!user_enabled) { printf("[Server did not advertise AUTHINFO USER]\n"); result = IMTEST_FAIL; } else { result = auth_nntp(); } } else if (!mechlist || !stristr(mechlist, mech)) { printf("[Server did not advertise SASL %s]\n", ucase(mech)); result = IMTEST_FAIL; } else { result = auth_sasl(sasl_cmd, mech); } } else { if (mechlist) { result = auth_sasl(sasl_cmd, mechlist); } else if (user_enabled) { result = auth_nntp(); } } return result; } static char *nntp_parse_success(char *str) { char *success = NULL, *tmp; if (!strncmp(str, "283 ", 4)) { success = str+4; if ((tmp = strchr(success, ' '))) *tmp = '\0'; /* clip trailing comment */ } return success; } /******************************** LMTP/SMTP **********************************/ static int xmtp_do_auth(struct sasl_cmd_t *sasl_cmd, void *rock __attribute__((unused)), int login_enabled __attribute__((unused)), char *mech, char *mechlist) { int result = IMTEST_OK; if (mech) { result = auth_sasl(sasl_cmd, mech); } else if (mechlist) { result = auth_sasl(sasl_cmd, mechlist); } return result; } struct xmtp_context_t { int inData; }; /* This takes a NUL-terminated full line (including any trailing \r\n) */ static int xmtp_pipe_oneline(char *buf, int len, void *rock) { struct xmtp_context_t *text = (struct xmtp_context_t *)rock; if(text->inData && len <= 3) { if(buf[0] == '.' && (buf[1] == '\n' || (buf[1] == '\r' && buf[2] == '\n'))) { text->inData = 0; } } else if(!text->inData && len > 4 && len <= 6) { if(!strncasecmp(buf, "DATA", 4) && (buf[4] == '\n' || (buf[4] == '\r' && buf[5] == '\n'))) { text->inData = 1; } else if(!strncasecmp(buf, "QUIT", 4) && (buf[4] == '\n' || (buf[4] == '\r' && buf[5] == '\n'))) { return IMTEST_CLOSEME; } } prot_write(pout, buf, len); prot_flush(pout); return IMTEST_OK; } static void *xmtp_init_conn(void) { struct generic_context_t *ret; ret = (void *)xmalloc(sizeof(struct generic_context_t)); memset(ret, 0, sizeof(struct generic_context_t)); ret->rock = (void *)xmalloc(sizeof(struct xmtp_context_t)); memset(ret->rock, 0, sizeof(struct xmtp_context_t)); ret->pipe_oneline = &xmtp_pipe_oneline; return ret; } static int xmtp_reset(void *rock) { struct generic_context_t *gentext = (struct generic_context_t *)rock; struct xmtp_context_t *text = (struct xmtp_context_t *)gentext->rock; if(text->inData || gentext->midLine) return IMTEST_FAIL; prot_printf(pout, "RSET\r\n"); prot_flush(pout); waitfor("250", NULL, 1); return IMTEST_OK; } /******************************** MUPDATE ************************************/ /********************************* SIEVE *************************************/ static char *sieve_parse_success(char *str) { char *success = NULL, *tmp; if (!strncmp(str, "OK (", 4) && (tmp = strstr(str+4, "SASL \"")) != NULL) { success = tmp+6; /* skip SASL " */ tmp = strstr(success, "\""); if (tmp) *tmp = '\0'; /* clip " */ } return success; } /*****************************************************************************/ /* didn't give correct parameters; let's exit */ static void usage(char *prog, char *prot) { printf("Usage: %s [options] hostname\n", prog); printf(" -p port : port to use (default=standard port for protocol)\n"); if (!strcasecmp(prot, "imap")) printf(" -z : timing test\n"); printf(" -k # : minimum protection layer required\n"); printf(" -l # : max protection layer (0=none; 1=integrity; etc)\n"); printf(" -u user : authorization name to use\n"); printf(" -a user : authentication name to use\n"); printf(" -w pass : password to use (if not supplied, we will prompt)\n"); printf(" -v : verbose\n"); printf(" -m mech : SASL mechanism to use\n"); if (!strcasecmp(prot, "imap")) printf(" (\"login\" for IMAP LOGIN)\n"); else if (!strcasecmp(prot, "pop3")) printf(" (\"user\" for USER/PASS, \"apop\" for APOP)\n"); else if (!strcasecmp(prot, "nntp")) printf(" (\"user\" for AUTHINFO USER/PASS\n"); printf(" -f file : pipe file into connection after authentication\n"); printf(" -r realm : realm\n"); #ifdef HAVE_SSL if (!strcasecmp(prot, "imap") || !strcasecmp(prot, "pop3") || !strcasecmp(prot, "nntp") || !strcasecmp(prot, "smtp")) printf(" -s : Enable %s over SSL (%ss)\n", prot, prot); if (strcasecmp(prot, "mupdate")) printf(" -t file : Enable TLS. file has the TLS public and private keys\n" " (specify \"\" to not use TLS for authentication)\n"); #endif /* HAVE_SSL */ #ifdef HAVE_ZLIB if (!strcasecmp(prot, "imap") || !strcasecmp(prot, "mupdate") || !strcasecmp(prot, "csync")) { printf(" -q : Enable %s COMPRESSion" " (before last authentication attempt)\n", prot); } #endif /* HAVE_ZLIB */ printf(" -c : enable challenge prompt callbacks\n" " (enter one-time password instead of secret pass-phrase)\n"); printf(" -n : number of auth attempts (default=1)\n"); printf(" -I file : output my PID to (file) (useful with -X)\n"); printf(" -x file : open the named socket for the interactive portion\n"); printf(" -X file : same as -X, except close all file descriptors & dameonize\n"); exit(1); } static struct protocol_t protocols[] = { { "imap", "imaps", "imap", 1, /* LOGIN available until LOGINDISABLED */ { 1, NULL, NULL }, { "C01 CAPABILITY", "C01 ", " STARTTLS", " LOGINDISABLED", " AUTH=", " COMPRESS=DEFLATE", &imap_parse_mechlist }, { "S01 STARTTLS", "S01 OK", "S01 NO", 0 }, { "A01 AUTHENTICATE", 0, /* no init resp until SASL-IR advertised */ 0, "A01 OK", "A01 NO", "+ ", "*", NULL, 0 }, { "Z01 COMPRESS DEFLATE", "Z01 OK", "Z01 NO" }, &imap_do_auth, { "Q01 LOGOUT", "Q01 " }, &imap_init_conn, &generic_pipe, &imap_reset }, { "pop3", "pop3s", "pop", 0, /* USER unavailable until advertised */ { 0, "+OK", &pop3_parse_banner }, { "CAPA", ".", "STLS", "USER", "SASL ", NULL, NULL }, { "STLS", "+OK", "-ERR", 0 }, { "AUTH", 255, 0, "+OK", "-ERR", "+ ", "*", NULL, 0 }, { NULL, NULL, NULL, }, &pop3_do_auth, { "QUIT", "+OK" }, NULL, NULL, NULL }, { "nntp", "nntps", "nntp", 0, /* AUTHINFO USER unavail until advertised */ { 0, "20", NULL }, { "CAPABILITIES", ".", "STARTTLS", "AUTHINFO USER", "SASL ", NULL, NULL }, { "STARTTLS", "382", "580", 0 }, { "AUTHINFO SASL", 512, 0, "28", "48", "383 ", "*", &nntp_parse_success, 0 }, { NULL, NULL, NULL, }, &nntp_do_auth, { "QUIT", "205" }, NULL, NULL, NULL }, { "lmtp", NULL, "lmtp", 0, { 0, "220 ", NULL }, { "LHLO lmtptest", "250 ", "STARTTLS", NULL, "AUTH ", NULL, NULL }, { "STARTTLS", "220", "454", 0 }, { "AUTH", 512, 0, "235", "5", "334 ", "*", NULL, 0 }, { NULL, NULL, NULL, }, &xmtp_do_auth, { "QUIT", "221" }, &xmtp_init_conn, &generic_pipe, &xmtp_reset }, { "smtp", "smtps", "smtp", 0, { 0, "220 ", NULL }, { "EHLO smtptest", "250 ", "STARTTLS", NULL, "AUTH ", NULL, NULL }, { "STARTTLS", "220", "454", 0 }, { "AUTH", 512, 0, "235", "5", "334 ", "*", NULL, 0 }, { NULL, NULL, NULL, }, &xmtp_do_auth, { "QUIT", "221" }, &xmtp_init_conn, &generic_pipe, &xmtp_reset }, { "mupdate", NULL, "mupdate", 0, { 1, "* OK", NULL }, { NULL , "* OK", "* STARTTLS", NULL, "* AUTH ", "* COMPRESS \"DEFLATE\"", NULL }, { "S01 STARTTLS", "S01 OK", "S01 NO", 1 }, { "A01 AUTHENTICATE", USHRT_MAX, 1, "A01 OK", "A01 NO", "", "*", NULL, 0 }, { "Z01 COMPRESS \"DEFLATE\"", "Z01 OK", "Z01 NO" }, NULL, { "Q01 LOGOUT", "Q01 " }, NULL, NULL, NULL }, { "sieve", NULL, SIEVE_SERVICE_NAME, 0, { 1, "OK", NULL }, { "CAPABILITY", "OK", "\"STARTTLS\"", NULL, "\"SASL\" ", NULL, NULL }, { "STARTTLS", "OK", "NO", 1 }, { "AUTHENTICATE", USHRT_MAX, 1, "OK", "NO", NULL, "*", &sieve_parse_success, 1 }, { NULL, NULL, NULL, }, NULL, { "LOGOUT", "OK" }, NULL, NULL, NULL }, { "csync", NULL, "csync", 0, { 1, "* OK", NULL }, { NULL , "* OK", "* STARTTLS", NULL, "* SASL ", "* COMPRESS DEFLATE", NULL }, { "STARTTLS", "OK", "NO", 1 }, { "AUTHENTICATE", USHRT_MAX, 0, "OK", "NO", "+ ", "*", NULL, 0 }, { "COMPRESS DEFLATE", "OK", "NO" }, NULL, { "EXIT", "OK" }, NULL, NULL, NULL }, { NULL, NULL, NULL, 0, { 0, NULL, NULL }, { NULL, NULL, NULL, NULL, NULL, NULL, NULL }, { NULL, NULL, NULL, 0 }, { NULL, 0, 0, NULL, NULL, NULL, NULL, NULL, 0 }, { NULL, NULL, NULL, }, NULL, { NULL, NULL }, NULL, NULL, NULL } }; int main(int argc, char **argv) { struct protocol_t *protocol; char *mechanism = NULL; char servername[1024]; char *filename=NULL; char *mechlist = NULL; unsigned ext_ssf = 0; const void *ssfp; sasl_ssf_t ssf; int maxssf = 128; int minssf = 0; int c; int result; int errflg = 0; char *prog; char *tls_keyfile=""; char *port = "", *prot = ""; int run_stress_test=0; int dotls=0, dossl=0, docompress=0; unsigned long capabilities = 0; char str[1024]; const char *pidfile = NULL; void *rock = NULL; int reauth = 1; int dochallenge = 0, noinitresp = 0; char *val; if (!construct_hash_table(&confighash, CONFIGHASHSIZE, 1)) { imtest_fatal("could not construct config hash table"); } /* do not buffer */ setbuf(stdin, NULL); setbuf(stdout, NULL); setbuf(stderr, NULL); prog = strrchr(argv[0], '/') ? strrchr(argv[0], '/')+1 : argv[0]; /* look at all the extra args */ while ((c = getopt(argc, argv, "P:qscizvk:l:p:u:a:m:f:r:t:n:I:x:X:w:o:?h")) != EOF) switch (c) { case 'P': prot = optarg; break; case 'q': #ifdef HAVE_ZLIB docompress=1; #else imtest_fatal("imtest was not compiled with zlib support\n"); #endif break; case 's': #ifdef HAVE_SSL dossl=1; #else imtest_fatal("imtest was not compiled with SSL/TLS support\n"); #endif break; case 'c': dochallenge=1; break; case 'i': noinitresp=1; break; case 'z': run_stress_test=1; break; case 'v': verbose=1; break; case 'k': minssf=atoi(optarg); break; case 'l': maxssf=atoi(optarg); break; case 'p': port = optarg; break; case 'u': username = optarg; break; case 'a': authname = optarg; break; case 'w': cmdline_password = optarg; break; case 'm': mechanism=optarg; break; case 'f': if(output_socket) imtest_fatal("cannot pipe a file when using unix domain socket output"); filename=optarg; break; case 'r': realm=optarg; break; case 't': #ifdef HAVE_SSL dotls=1; tls_keyfile=optarg; #else imtest_fatal("imtest was not compiled with SSL/TLS support\n"); #endif break; case 'n': reauth = atoi(optarg); if (reauth <= 0) imtest_fatal("number of auth attempts must be > 0\n"); break; case 'I': pidfile = optarg; break; case 'X': case 'x': if(filename) imtest_fatal("cannot pipe a file when using unix domain socket output"); if(output_socket) imtest_fatal("cannot specify both -X and -x"); output_socket = optarg; if(c == 'X'){ /* close all already-open file descriptors that are * not stdin/stdout/stderr */ int i, dsize = getdtablesize(); /* close all file descriptors */ for(i=0; iprotocol && strcasecmp(prot, protocol->protocol)) protocol++; if (!protocol->protocol) imtest_fatal("unknown protocol\n"); if (dossl && !protocol->sprotocol) imtest_fatal("protocol cannot be SSL-wrapped\n"); if (run_stress_test && strcmp(protocol->protocol, "imap")) imtest_fatal("stress test can only be run for IMAP\n"); if (errflg) { usage(prog, protocol->protocol); } if (!*port) { if (dossl) { port=protocol->sprotocol; } else { port=protocol->protocol; } } /* last arg is server name */ if (optind < argc) strncpy(servername, argv[optind], 1023); else { fprintf(stderr, "WARNING: no hostname supplied, assuming localhost\n\n"); strncpy(servername, "localhost", 1023); } if(pidfile) { FILE *pf; pf = fopen(pidfile, "w"); if(!pf) { fprintf(stderr, "could not open %s for writing\n",pidfile); perror("error"); exit(1); } fprintf(pf, "%d", getpid()); fclose(pf); } /* attempt to start sasl */ if (sasl_client_init(callbacks+(!dochallenge ? 2 : 0)) != IMTEST_OK) { imtest_fatal("SASL initialization"); } conn = NULL; do { if (conn) { /* send LOGOUT */ logout(&protocol->logout_cmd, 1); printf("Connection closed.\n\n"); prot_free(pin); prot_free(pout); #ifdef HAVE_SSL /* Properly shutdown TLS so that session can be reused */ if (tls_conn) { SSL_shutdown(tls_conn); SSL_set_shutdown(tls_conn, SSL_SENT_SHUTDOWN|SSL_RECEIVED_SHUTDOWN); } #endif close(sock); sasl_dispose(&conn); } if (init_net(servername, port) != IMTEST_OK) { imtest_fatal("Network initialization - cannot connect to %s:%s", servername, port); } if (init_sasl(protocol->service, servername, minssf, maxssf, protocol->sasl_cmd.parse_success ? SASL_SUCCESS_DATA : 0) != IMTEST_OK) { imtest_fatal("SASL initialization"); } /* set up the prot layer */ pin = prot_new(sock, 0); pout = prot_new(sock, 1); #ifdef HAVE_SSL if (dossl==1) { do_starttls(1, "", &ext_ssf); } #endif /* HAVE_SSL */ if (protocol->banner.is_capa) { /* try to get the capabilities from the banner */ mechlist = ask_capability(protocol, &capabilities, AUTO_BANNER); if (!mechlist && !(capabilities & CAPA_STARTTLS)) { /* found no capabilities in banner -> get them explicitly */ protocol->banner.is_capa = 0; } } else { do { /* look for the banner response */ if (prot_fgets(str, sizeof(str), pin) == NULL) { imtest_fatal("prot layer failure"); } printf("S: %s", str); /* parse it if need be */ if (protocol->banner.parse_banner) rock = protocol->banner.parse_banner(str); } while (strncasecmp(str, protocol->banner.resp, strlen(protocol->banner.resp))); } if (!protocol->banner.is_capa) { mechlist = ask_capability(protocol, &capabilities, AUTO_NO); } #ifdef HAVE_SSL if ((dossl==0) && (dotls==1) && (capabilities & CAPA_STARTTLS)) { char *resp; printf("C: %s\r\n", protocol->tls_cmd.cmd); prot_printf(pout, "%s\r\n", protocol->tls_cmd.cmd); prot_flush(pout); resp = waitfor(protocol->tls_cmd.ok, protocol->tls_cmd.fail, 1); if (!strncasecmp(resp, protocol->tls_cmd.ok, strlen(protocol->tls_cmd.ok))) { do_starttls(0, tls_keyfile, &ext_ssf); /* ask for the capabilities again */ if (verbose==1) printf("Asking for capabilities again " "since they might have changed\n"); if (mechlist) free(mechlist); mechlist = ask_capability(protocol, &capabilities, protocol->tls_cmd.auto_capa); } } else if ((dotls==1) && !(capabilities & CAPA_STARTTLS)) { imtest_fatal("STARTTLS not supported by the server!\n"); } #endif /* HAVE_SSL */ #ifdef HAVE_ZLIB if ((reauth == 1) && (docompress==1) && (capabilities & CAPA_COMPRESS)) { char *resp; printf("C: %s\r\n", protocol->compress_cmd.cmd); prot_printf(pout, "%s\r\n", protocol->compress_cmd.cmd); prot_flush(pout); resp = waitfor(protocol->compress_cmd.ok, protocol->compress_cmd.fail, 1); if (!strncasecmp(resp, protocol->compress_cmd.ok, strlen(protocol->compress_cmd.ok))) { prot_setcompress(pin); prot_setcompress(pout); } } #endif /* HAVE_ZLIB */ if (noinitresp) { /* don't use an initial response, even if its supported */ protocol->sasl_cmd.maxlen = 0; } if (protocol->do_auth) result = protocol->do_auth(&protocol->sasl_cmd, rock, capabilities & CAPA_LOGIN, mechanism, mechlist); else { if (mechanism) { result = auth_sasl(&protocol->sasl_cmd, mechanism); } else if (mechlist) { result = auth_sasl(&protocol->sasl_cmd, mechlist); } else { result = IMTEST_FAIL; } } if (rock) free(rock); if (result == IMTEST_OK) { printf("Authenticated.\n"); /* turn on layer if need be */ prot_setsasl(pin, conn); prot_setsasl(pout, conn); } else { const char *s = sasl_errstring(result, NULL, NULL); printf("Authentication failed. %s\n", s); } result = sasl_getprop(conn, SASL_SSF, &ssfp); ssf = *((sasl_ssf_t *) ssfp); if (result != SASL_OK) { printf("SSF: unable to determine (SASL ERROR %d)\n", result); } else { printf("Security strength factor: %d\n", ext_ssf + ssf); if (ssf) { /* ask for the capabilities again */ char *new_mechlist; if (verbose==1) printf("Asking for capabilities again " "since they might have changed\n"); if (!strcmp(protocol->protocol, "sieve")) { /* XXX Hack to handle ManageSieve servers. * No way to tell from protocol if server will * automatically send capabilities, so we treat it * as optional. */ char ch; /* wait and probe for possible auto-capability response*/ usleep(250000); prot_NONBLOCK(pin); if ((ch = prot_getc(pin)) != EOF) { prot_ungetc(ch, pin); } else { protocol->sasl_cmd.auto_capa = 0; } prot_BLOCK(pin); } new_mechlist = ask_capability(protocol, &capabilities, protocol->sasl_cmd.auto_capa); if (new_mechlist && strcmp(new_mechlist, mechlist)) { printf("WARNING: possible MITM attack: " "list of available SASL mechanisms changed\n"); free(new_mechlist); } } } if (mechlist) free(mechlist); } while (--reauth); if (run_stress_test == 1) { send_recv_test(); } else { /* else run in interactive mode or pipe in a filename if applicable */ interactive(protocol, filename); } while (stashed_strings.count) free(strarray_pop(&stashed_strings)); free_hash_table(&confighash, free); exit(0); } cyrus-imapd-2.5.10/xversion.h0000644000175000017500000000015113001246644013000 00000000000000/* Development version */ #define _CYRUS_VERSION "2.5.10" #define CYRUS_GITVERSION "be9a1799 2016-10-18" cyrus-imapd-2.5.10/lib/0000755000175000017500000000000013001246664011605 500000000000000cyrus-imapd-2.5.10/lib/ptrarray.c0000644000175000017500000001275013001236020013523 00000000000000/* ptrarray.c -- an expanding array of pointers * * Copyright (c) 1994-2011 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. * * Author: Greg Banks * Start Date: 2011/01/11 */ #include "ptrarray.h" #include #include "xmalloc.h" EXPORTED ptrarray_t *ptrarray_new(void) { return xzmalloc(sizeof(ptrarray_t)); } EXPORTED void ptrarray_fini(ptrarray_t *pa) { if (!pa) return; memset(pa->data, 0, sizeof(void *) * pa->count); free(pa->data); pa->data = NULL; pa->count = 0; pa->alloc = 0; } EXPORTED void ptrarray_free(ptrarray_t *pa) { if (!pa) return; ptrarray_fini(pa); free(pa); } /* * Ensure the index @idx exists in the array, if necessary expanding the * array, and if necessary NULL-filling all the intervening elements. * Note that we always ensure an empty slot past the last reported * index, so that we can pass data[] to execve() or other routines that * assume a NULL terminator. */ #define QUANTUM 16 static void ensure_alloc(ptrarray_t *pa, int newalloc) { if (newalloc) newalloc++; if (newalloc <= pa->alloc) return; newalloc = ((newalloc + QUANTUM-1) / QUANTUM) * QUANTUM; pa->data = xrealloc(pa->data, sizeof(void *) * newalloc); memset(pa->data+pa->alloc, 0, sizeof(void *) * (newalloc-pa->alloc)); pa->alloc = newalloc; } static inline int adjust_index_ro(const ptrarray_t *pa, int idx) { if (idx >= pa->count) return -1; else if (idx < 0) idx += pa->count; return idx; } static inline int adjust_index_rw(ptrarray_t *pa, int idx, int len) { if (idx >= pa->count) { ensure_alloc(pa, idx+len); } else if (idx < 0) { idx += pa->count; if (idx >= 0 && len) ensure_alloc(pa, pa->count+len); } else if (len) { ensure_alloc(pa, pa->count+len); } return idx; } EXPORTED void ptrarray_add(ptrarray_t *pa, void *p) { if (ptrarray_find(pa, p, 0) < 0) ptrarray_append(pa, p); } EXPORTED void ptrarray_append(ptrarray_t *pa, void *p) { ensure_alloc(pa, pa->count+1); pa->data[pa->count++] = p; } EXPORTED void ptrarray_set(ptrarray_t *pa, int idx, void *p) { if ((idx = adjust_index_rw(pa, idx, 0)) < 0) return; pa->data[idx] = p; } static inline void _ptrarray_insert(ptrarray_t *pa, int idx, void *p) { if (idx < pa->count) memmove(pa->data+idx+1, pa->data+idx, sizeof(void *) * (pa->count-idx)); pa->data[idx] = p; pa->count++; } EXPORTED void ptrarray_insert(ptrarray_t *pa, int idx, void *p) { if ((idx = adjust_index_rw(pa, idx, 1)) < 0) return; _ptrarray_insert(pa, idx, p); } EXPORTED void *ptrarray_remove(ptrarray_t *pa, int idx) { void *p; if ((idx = adjust_index_ro(pa, idx)) < 0) return NULL; p = pa->data[idx]; pa->count--; if (idx < pa->count) memmove(pa->data+idx, pa->data+idx+1, sizeof(void *) * (pa->count-idx)); return p; } EXPORTED void ptrarray_truncate(ptrarray_t *pa, int newlen) { int i; if (newlen == pa->count) return; if (newlen > pa->count) { ensure_alloc(pa, newlen); } else { for (i = newlen ; i < pa->count ; i++) { pa->data[i] = NULL; } } pa->count = newlen; } EXPORTED void *ptrarray_nth(const ptrarray_t *pa, int idx) { if ((idx = adjust_index_ro(pa, idx)) < 0) return NULL; return pa->data[idx]; } EXPORTED void **ptrarray_takevf(ptrarray_t *pa) { void **d = pa->data; pa->data = NULL; pa->count = pa->alloc = 0; ptrarray_free(pa); return d; } EXPORTED int ptrarray_find(const ptrarray_t *pa, void *match, int starting) { int i; for (i = starting ; i < pa->count ; i++) if (match == pa->data[i]) return i; return -1; } EXPORTED void ptrarray_sort(ptrarray_t *pa, int (*compare)(const void **, const void **)) { qsort(pa->data, pa->count, sizeof(void*), (int (*)(const void *, const void *))compare); } cyrus-imapd-2.5.10/lib/auth.h0000644000175000017500000000600713001236020012623 00000000000000/* auth.h -- Site authorization module * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #ifndef INCLUDED_AUTH_H #define INCLUDED_AUTH_H struct auth_state; struct auth_mech { const char *name; const char *(*canonifyid)(const char *identifier, size_t len); int (*memberof)(struct auth_state *auth_state, const char *identifier); struct auth_state *(*newstate)(const char *identifier); void (*freestate)(struct auth_state *auth_state); }; extern struct auth_mech *auth_mechs[]; /* Note that some of these may be undefined symbols * if libcyrus was not built with support for them */ extern struct auth_mech auth_unix; extern struct auth_mech auth_pts; extern struct auth_mech auth_krb; extern struct auth_mech auth_krb5; /* auth_canonifyid: canonify the given identifier and return a pointer * to a static buffer with the canonified ID, or NULL on * failure */ /* identifier: id to canonify */ /* len: length of id, or 0 to do strlen(identifier) */ const char *auth_canonifyid(const char *identifier, size_t len); int auth_memberof(struct auth_state *auth_state, const char *identifier); struct auth_state *auth_newstate(const char *identifier); void auth_freestate(struct auth_state *auth_state); #endif /* INCLUDED_AUTH_H */ cyrus-imapd-2.5.10/lib/strarray.h0000644000175000017500000001001613001236020013524 00000000000000/* strarray.h -- an expanding array of strings * * Copyright (c) 1994-2011 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. * * Author: Greg Banks * Start Date: 2011/01/11 */ #ifndef __CYRUS_STRARRAY_H__ #define __CYRUS_STRARRAY_H__ #include #include #include "util.h" typedef struct { int count; int alloc; char **data; } strarray_t; #define STRARRAY_INITIALIZER { 0, 0, NULL } #define strarray_init(sa) (memset((sa), 0, sizeof(strarray_t))) void strarray_fini(strarray_t *); strarray_t *strarray_new(void); void strarray_free(strarray_t *); int strarray_append(strarray_t *, const char *); int strarray_add(strarray_t *, const char *); int strarray_add_case(strarray_t *, const char *); int strarray_appendm(strarray_t *, char *); void strarray_set(strarray_t *, int idx, const char *); void strarray_setm(strarray_t *, int idx, char *); void strarray_insert(strarray_t *, int idx, const char *); void strarray_insertm(strarray_t *, int idx, char *); char *strarray_remove(strarray_t *, int idx); void strarray_remove_all(strarray_t *sa, const char *s); void strarray_remove_all_case(strarray_t *sa, const char *s); const char *strarray_nth(const strarray_t *sa, int idx); void strarray_truncate(strarray_t *sa, int newlen); strarray_t *strarray_dup(const strarray_t *); #define strarray_shift(sa) strarray_remove((sa), 0) #define strarray_unshift(sa, s) strarray_insert((sa), 0, (s)) #define strarray_unshiftm(sa, s) strarray_insertm((sa), 0, (s)) #define strarray_pop(sa) strarray_remove((sa), -1) #define strarray_push(sa, s) strarray_append((sa), (s)) #define strarray_pushm(sa, s) strarray_appendm((sa), (s)) char *strarray_join(const strarray_t *, const char *sep); #define STRARRAY_TRIM (1<<0) strarray_t *strarray_splitm(char *buf, const char *sep, int flags); strarray_t *strarray_split(const char *buf, const char *sep, int flags); strarray_t *strarray_nsplit(const char *buf, size_t len, const char *sep, int flags); void strarray_sort(strarray_t *, compar_t *); void strarray_uniq(strarray_t *); char **strarray_takevf(strarray_t *sa); int strarray_find(const strarray_t *sa, const char *match, int starting); int strarray_find_case(const strarray_t *sa, const char *match, int starting); int strarray_size(const strarray_t *sa); #endif /* __CYRUS_STRARRAY_H__ */ cyrus-imapd-2.5.10/lib/prot.c0000644000175000017500000013047213001236020012645 00000000000000/* prot.c -- stdio-like module that handles SASL protection mechanisms * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include #include #include #include #include #include #include #ifdef HAVE_UNISTD_H #include #endif #include #include #include #ifdef HAVE_SYS_SELECT_H #include #endif #include "assert.h" #include "exitcodes.h" #include "imparse.h" #include "libcyr_cfg.h" #include "map.h" #include "nonblock.h" #include "prot.h" #include "signals.h" #include "util.h" #include "xmalloc.h" /* Transparant protgroup structure */ struct protgroup { size_t nalloced; /* Number of nodes in the group */ size_t next_element; /* Node number of next group member */ struct protstream **group; }; /* * Create a new protection stream for file descriptor 'fd'. Stream * will be used for writing iff 'write' is nonzero. */ EXPORTED struct protstream *prot_new(int fd, int write) { struct protstream *newstream; newstream = (struct protstream *) xzmalloc(sizeof(struct protstream)); newstream->buf = (unsigned char *) xmalloc(sizeof(char) * (PROT_BUFSIZE)); newstream->buf_size = PROT_BUFSIZE; newstream->ptr = newstream->buf; newstream->maxplain = PROT_BUFSIZE; newstream->fd = fd; newstream->write = write; newstream->logfd = PROT_NO_FD; newstream->big_buffer = PROT_NO_FD; if(write) newstream->cnt = PROT_BUFSIZE; return newstream; } EXPORTED struct protstream *prot_writebuf(struct buf *buf) { struct protstream *newstream; newstream = (struct protstream *) xzmalloc(sizeof(struct protstream)); /* dodgy, but the alternative is two pointers */ newstream->buf = (unsigned char *) xmalloc(sizeof(char) * (PROT_BUFSIZE)); newstream->buf_size = PROT_BUFSIZE; newstream->ptr = newstream->buf; newstream->cnt = PROT_BUFSIZE; newstream->maxplain = PROT_BUFSIZE; newstream->write = 1; newstream->writetobuf = buf; newstream->fd = PROT_NO_FD; newstream->logfd = PROT_NO_FD; newstream->big_buffer = PROT_NO_FD; return newstream; } /* Create a protstream which is just an interface to a mapped piece of * memory, allowing prot commands to be used to read from it */ EXPORTED struct protstream *prot_readmap(const char *base, uint32_t len) { struct protstream *newstream; newstream = (struct protstream *) xzmalloc(sizeof(struct protstream)); /* dodgy, but the alternative is two pointers */ newstream->ptr = (unsigned char *)base; newstream->cnt = len; newstream->fixedsize = 1; newstream->fd = PROT_NO_FD; newstream->logfd = PROT_NO_FD; newstream->big_buffer = PROT_NO_FD; return newstream; } /* * Free a protection stream */ EXPORTED int prot_free(struct protstream *s) { if (s->error) free(s->error); free(s->buf); if(s->big_buffer != PROT_NO_FD) { map_free(&(s->bigbuf_base), &(s->bigbuf_siz)); close(s->big_buffer); } #ifdef HAVE_ZLIB if (s->zstrm) { if (s->write) deflateEnd(s->zstrm); else inflateEnd(s->zstrm); free(s->zstrm); } if (s->zbuf) free(s->zbuf); #endif free(s); return 0; } /* * Set the logging file descriptor for stream 's' to be 'fd'. */ EXPORTED int prot_setlog(struct protstream *s, int fd) { s->logfd = fd; return 0; } EXPORTED int prot_setisclient(struct protstream *s, int val) { s->isclient = val; return 0; } #ifdef HAVE_SSL /* * Turn on TLS for this connection */ EXPORTED int prot_settls(struct protstream *s, SSL *tlsconn) { s->tls_conn = tlsconn; /* Make nonblocking stuff to work similar to write() */ SSL_set_mode(tlsconn, SSL_MODE_ENABLE_PARTIAL_WRITE | SSL_MODE_ACCEPT_MOVING_WRITE_BUFFER); return 0; } #endif /* HAVE_SSL */ /* * Decode data sent via a SASL security layer. Returns EOF on error. */ static int prot_sasldecode(struct protstream *s, int n) { int result; const char *out; unsigned outlen; assert(!s->write); /* decode the input */ result = sasl_decode(s->conn, (const char *) s->buf, n, &out, &outlen); if (result != SASL_OK) { char errbuf[256]; const char *ed = sasl_errdetail(s->conn); snprintf(errbuf, 256, "decoding error: %s; %s", sasl_errstring(result, NULL, NULL), ed ? ed : "no detail"); s->error = xstrdup(errbuf); return EOF; } if (outlen > 0) { /* The contents of 'out' is static until next call to sasl_decode(), so serve data directly from 'out' */ s->ptr = (unsigned char *) out; s->cnt = outlen; } else { /* didn't decode anything */ s->cnt = 0; } return 0; } /* * Turn on SASL for this connection */ EXPORTED int prot_setsasl(struct protstream *s, sasl_conn_t *conn) { const void *ssfp; int result; if (s->write && s->ptr != s->buf) { /* flush any pending output */ if (prot_flush_internal(s, 0) == EOF) return EOF; } s->conn = conn; result = sasl_getprop(conn, SASL_SSF, &ssfp); if (result != SASL_OK) { return -1; } s->saslssf = *((const int *) ssfp); if (s->write) { const void *maxp; unsigned int max; /* ask SASL for layer max */ result = sasl_getprop(conn, SASL_MAXOUTBUF, &maxp); max = *((const unsigned int *) maxp); if (result != SASL_OK) { return -1; } if (max == 0 || max > PROT_BUFSIZE) { /* max = 0 means unlimited, and we can't go bigger */ max = PROT_BUFSIZE; } s->maxplain = max; s->cnt = max; } else if (s->cnt) { /* decode any pending input */ if (prot_sasldecode(s, s->cnt) == EOF) return EOF; } return 0; } /* * Turn off SASL for this connection */ EXPORTED void prot_unsetsasl(struct protstream *s) { s->conn = NULL; s->maxplain = PROT_BUFSIZE; s->saslssf = 0; } #ifdef HAVE_ZLIB #define ZLARGE_DIFF_CHUNK (5120) /* 5K */ /* Wrappers for our memory management functions */ static voidpf zalloc(voidpf opaque __attribute__((unused)), uInt items, uInt size) { return (voidpf) xmalloc(items * size); } static void zfree(voidpf opaque __attribute__((unused)), voidpf address) { free(address); } /* * Turn on (de)compression for this connection * If its an output stream, initialize a compressor, * otherwise initialize a decompressor. */ EXPORTED int prot_setcompress(struct protstream *s) { int zr = Z_OK; z_stream *zstrm = (z_stream *) xmalloc(sizeof(z_stream)); zstrm->zalloc = zalloc; zstrm->zfree = zfree; zstrm->opaque = Z_NULL; if (s->write) { if (s->ptr != s->buf) { /* flush any pending output */ if (prot_flush_internal(s, 0) == EOF) goto error; } s->zlevel = Z_DEFAULT_COMPRESSION; zr = deflateInit2(zstrm, s->zlevel, Z_DEFLATED, -MAX_WBITS, /* raw deflate */ MAX_MEM_LEVEL, Z_DEFAULT_STRATEGY); } else { zstrm->next_in = Z_NULL; zstrm->avail_in = 0; zr = inflateInit2(zstrm, -MAX_WBITS); /* raw inflate */ } if (zr != Z_OK) goto error; /* RFC 1951 says: * A simple counting argument shows that no lossless compression * algorithm can compress every possible input data set. For the * format defined here, the worst case expansion is 5 bytes per 32K- * byte block, i.e., a size increase of 0.015% for large data sets. * * We say: maxplain can never be bigger than PROT_BUFSIZE, which * is currently 4096, so adding 5 bytes will do it! * * Add another spare byte and we'll never totally fill the buffer, * which saves a loop. * * NOTE: we do double check and handle buffer filling gracefully * anyway, but starting with the right size is good. */ s->zbuf_size = s->maxplain + 6; s->zbuf = (unsigned char *) xmalloc(sizeof(unsigned char) * s->zbuf_size); syslog(LOG_DEBUG, "created %scompress buffer of %u bytes", s->write ? "" : "de", s->zbuf_size); s->zstrm = zstrm; return 0; error: syslog(LOG_NOTICE, "failed to start %scompression", s->write ? "" : "de"); free(zstrm); return EOF; } /* Table of incompressible file type signatures */ static struct file_sig { const char *type; size_t len; const char *sig; } sig_tbl[] = { { "GIF87a", 6, "GIF87a" }, { "GIF89a", 6, "GIF89a" }, { "GZIP", 2, "\x1F\x8B" }, { "JPEG", 4, "\xFF\xD8\xFF\xE0" }, { "PNG", 8, "\x89\x50\x4E\x47\x0D\x0A\x1A\x0A" }, { NULL, 0, NULL } }; /* Check if a chunk of data is incompressible */ static int is_incompressible(const char *p, size_t n) { struct file_sig *sig = sig_tbl; /* is it worth checking? */ if (n < ZLARGE_DIFF_CHUNK) return 0; while (sig->type) { if (n >= sig->len && !memcmp(p, sig->sig, sig->len)) { syslog(LOG_DEBUG, "data is %s", sig->type); return 1; } sig++; } return 0; } #endif /* HAVE_ZLIB */ /* Tell the protstream that the type of data is about to change. * Since we might want to look at the data, we only set a flag and delay * any changes to the stream layers until the next prot_write(). */ EXPORTED int prot_data_boundary(struct protstream *s) { s->boundary = 1; return 0; } /* * Set the read timeout for the stream 's' to 'timeout' seconds. * 's' must have been created for reading. */ EXPORTED int prot_settimeout(struct protstream *s, int timeout) { assert(!s->write); s->read_timeout = timeout; s->timeout_mark = time(NULL) + timeout; return 0; } /* * Reset the read timeout_mark for the stream 's'. * 'S' must have been created for reading. */ EXPORTED int prot_resettimeout(struct protstream *s) { assert(!s->write); s->timeout_mark = time(NULL) + s->read_timeout; return 0; } /* * Set the stream 's' to flush the stream 'flushs' before * blocking for reading. 's' must have been created for reading, * 'flushs' for writing. */ EXPORTED int prot_setflushonread(struct protstream *s, struct protstream *flushs) { assert(!s->write); if(flushs) assert(flushs->write); s->flushonread = flushs; return 0; } /* * Set on stream 's' the callback 'proc' and 'rock' * to make the next time we have to wait for input. */ int prot_setreadcallback(struct protstream *s, prot_readcallback_t *proc, void *rock) { assert(!s->write); s->readcallback_proc = proc; s->readcallback_rock = rock; return 0; } /* * Add an event on stream 's' so that the callback 'proc' taking * argument 'rock' will be called at 'mark' (in seconds) while * waiting for input. */ EXPORTED struct prot_waitevent *prot_addwaitevent(struct protstream *s, time_t mark, prot_waiteventcallback_t *proc, void *rock) { struct prot_waitevent *new, *cur; /* if we aren't passed a callback function, don't bother */ if (!proc) return s->waitevent; /* create new timer struct */ new = (struct prot_waitevent *) xmalloc(sizeof(struct prot_waitevent)); new->mark = mark; new->proc = proc; new->rock = rock; new->next = NULL; /* add the new event to the end of the list */ if (!s->waitevent) s->waitevent = new; else { cur = s->waitevent; while (cur && cur->next) cur = cur->next; cur->next = new; } return new; } /* * Remove 'event' from stream 's'. */ EXPORTED void prot_removewaitevent(struct protstream *s, struct prot_waitevent *event) { struct prot_waitevent *prev, *cur; prev = NULL; cur = s->waitevent; while (cur && cur != event) { prev = cur; cur = cur->next; } if (!cur) return; if (!prev) s->waitevent = cur->next; else prev->next = cur->next; free(cur); } /* * Return a pointer to a statically-allocated string describing the * error encountered on 's'. If there is no error condition, return a * null pointer. */ EXPORTED const char *prot_error(struct protstream *s) { if(!s) return "bad protstream passed to prot_error"; else if(s->error) return s->error; else if(s->eof) return PROT_EOF_STRING; else return NULL; } /* * Rewind the stream 's'. 's' must have been created for reading. */ EXPORTED int prot_rewind(struct protstream *s) { assert(!s->write); if (lseek(s->fd, 0L, 0) == -1) { s->error = xstrdup(strerror(errno)); return EOF; } s->cnt = 0; s->error = 0; s->eof = 0; s->can_unget = 0; s->bytes_in = 0; return 0; } /* * Read data into the empty buffer for the stream 's' and return the * first character. Returns EOF on EOF or error. */ EXPORTED int prot_fill(struct protstream *s) { int n; unsigned char *ptr; int left; int r; struct timeval timeout; fd_set rfds; int haveinput; time_t read_timeout; struct prot_waitevent *event, *next; assert(!s->write); /* Zero errno just in case */ errno = 0; if (s->fixedsize) s->eof = 1; if (s->eof || s->error) return EOF; do { #ifdef HAVE_ZLIB /* check if there's anything in the zlib buffer already */ if (s->zstrm && s->zstrm->avail_in) { /* Decompress the data */ int zr = Z_OK; s->zstrm->next_out = s->zbuf; s->zstrm->avail_out = s->zbuf_size; zr = inflate(s->zstrm, Z_SYNC_FLUSH); if (!(zr == Z_OK || zr == Z_BUF_ERROR || zr == Z_STREAM_END)) { /* Error decompressing */ syslog(LOG_ERR, "zlib inflate error: %d %s", zr, s->zstrm->msg); s->error = xstrdup("Error decompressing data"); return EOF; } if (s->zstrm->avail_out < s->zbuf_size) { /* inflated some data */ s->ptr = s->zbuf; s->cnt = s->zbuf_size - s->zstrm->avail_out; /* drop straight to logging and returning the first char */ break; } } #endif /* wait until get input */ haveinput = 0; #ifdef HAVE_SSL /* maybe there's data stuck in the SSL buffer? */ if (s->tls_conn != NULL) { haveinput = SSL_pending(s->tls_conn); } #endif /* if we've promised to call something before blocking or flush an output stream, check to see if we're going to block */ if (s->readcallback_proc || (s->flushonread && s->flushonread->ptr != s->flushonread->buf)) { timeout.tv_sec = timeout.tv_usec = 0; FD_ZERO(&rfds); FD_SET(s->fd, &rfds); if (!haveinput && (signals_select(s->fd + 1, &rfds, (fd_set *)0, (fd_set *)0, &timeout) <= 0)) { if (s->readcallback_proc) { (*s->readcallback_proc)(s, s->readcallback_rock); s->readcallback_proc = 0; s->readcallback_rock = 0; } /* Request a flush of the buffer. If we are a blocking read stream, force the flush */ if (s->flushonread) prot_flush_internal(s->flushonread, !s->dontblock); } else { haveinput = 1; } } if (!haveinput && (s->read_timeout || s->dontblock)) { time_t now = time(NULL); time_t sleepfor; read_timeout = s->dontblock ? now : s->timeout_mark; do { if (read_timeout < now) sleepfor = 0; else sleepfor = read_timeout - now; /* execute each callback that has timed out */ for (event = s->waitevent; event; event = next) { next = event->next; if (now >= event->mark) { event = (*event->proc)(s, event, event->rock); } /* if event == NULL, the callback has removed itself */ if (event && sleepfor > (event->mark - now)) { sleepfor = event->mark - now; } } /* check for input */ timeout.tv_sec = sleepfor; timeout.tv_usec = 0; FD_ZERO(&rfds); FD_SET(s->fd, &rfds); r = signals_select(s->fd + 1, &rfds, (fd_set *)0, (fd_set *)0, &timeout); now = time(NULL); } while ((r == 0 || (r == -1 && errno == EINTR && !signals_poll())) && (now < read_timeout)); if ((r == 0) || /* ignore EINTR if we've timed out */ (r == -1 && errno == EINTR && !signals_poll() && now >= read_timeout)) { if (!s->dontblock) { s->error = xstrdup("idle for too long"); return EOF; } else { errno = EAGAIN; return EOF; } } else if (r == -1) { syslog(LOG_ERR, "select() failed: %m"); s->error = xstrdup(strerror(errno)); return EOF; } } /* we have data, reset the timeout_mark */ prot_resettimeout(s); do { cmdtime_netstart(); #ifdef HAVE_SSL /* just do a SSL read instead if we're under a tls layer */ if (s->tls_conn != NULL) { n = SSL_read(s->tls_conn, (char *) s->buf, PROT_BUFSIZE); } else { n = read(s->fd, s->buf, PROT_BUFSIZE); } #else /* HAVE_SSL */ n = read(s->fd, s->buf, PROT_BUFSIZE); #endif /* HAVE_SSL */ cmdtime_netend(); } while (n == -1 && errno == EINTR && !signals_poll()); if (n <= 0) { if (n) s->error = xstrdup(strerror(errno)); else s->eof = 1; return EOF; } if (s->saslssf) { /* decode it */ if (prot_sasldecode(s, n) == EOF) return EOF; } else { /* No protection function, just use the raw data */ s->ptr = s->buf; s->cnt = n; } #ifdef HAVE_ZLIB if (s->zstrm) { /* transfer the data we have to the input of * the z_stream and loop to process it */ s->zstrm->next_in = s->ptr; s->zstrm->avail_in = s->cnt; s->cnt = 0; } #endif /* HAVE_ZLIB */ } while (!s->cnt); if (s->logfd != -1) { time_t newtime; char timebuf[20]; time(&newtime); snprintf(timebuf, sizeof(timebuf), "<%ld<", newtime); n = write(s->logfd, timebuf, strlen(timebuf)); left = s->cnt; ptr = s->ptr; do { n = write(s->logfd, ptr, left); if (n == -1 && (errno != EINTR || signals_poll())) { break; } if (n > 0) { ptr += n; left -= n; } } while (left); } s->cnt--; /* we return the first char */ s->can_unget = 1; s->bytes_in++; return *s->ptr++; } /* * If 's' is an input stream, discard any pending/buffered data. Otherwise, * Write out any buffered data in the stream 's' */ EXPORTED int prot_flush(struct protstream *s) { if (!s->write) { int c, save_dontblock = s->dontblock; /* Set stream to nonblocking mode */ if (!save_dontblock) nonblock(s->fd, (s->dontblock = 1)); /* Ingest any pending input */ while ((c = prot_fill(s)) != EOF); /* Reset stream to previous blocking mode */ if (!save_dontblock) nonblock(s->fd, (s->dontblock = 0)); /* Discard any buffered input */ s->cnt = 0; s->can_unget = 0; return 0; } return prot_flush_internal(s, 1); } /* Do the logging part of prot_flush */ static void prot_flush_log(struct protstream *s) { if(s->logfd != PROT_NO_FD) { unsigned char *ptr = s->buf; int left = s->ptr - s->buf; int n; time_t newtime; char timebuf[20]; time(&newtime); snprintf(timebuf, sizeof(timebuf), ">%ld>", newtime); n = write(s->logfd, timebuf, strlen(timebuf)); do { n = write(s->logfd, ptr, left); if (n == -1 && (errno != EINTR || signals_poll())) { break; } if (n > 0) { ptr += n; left -= n; } } while (left); /* we don't care THAT much about logs * (void)fsync(s->logfd); */ } } /* Do the encoding part of prot_flush */ static int prot_flush_encode(struct protstream *s, const char **output_buf, unsigned *output_len) { unsigned char *ptr = s->buf; int left = s->ptr - s->buf; #ifdef HAVE_ZLIB if (s->zstrm) { /* Compress the data */ int zr = Z_OK; s->zstrm->next_in = ptr; s->zstrm->avail_in = left; s->zstrm->next_out = s->zbuf; s->zstrm->avail_out = s->zbuf_size; do { /* should never be needed, but it's better to always check! */ if (!s->zstrm->avail_out) { syslog(LOG_DEBUG, "growing compress buffer from %u to %u bytes", s->zbuf_size, s->zbuf_size + PROT_BUFSIZE); s->zbuf = (unsigned char *) xrealloc(s->zbuf, s->zbuf_size + PROT_BUFSIZE); s->zstrm->next_out = s->zbuf + s->zbuf_size; s->zstrm->avail_out = PROT_BUFSIZE; s->zbuf_size += PROT_BUFSIZE; } zr = deflate(s->zstrm, Z_SYNC_FLUSH); if (!(zr == Z_OK || zr == Z_STREAM_END || zr == Z_BUF_ERROR)) { /* something went wrong */ syslog(LOG_ERR, "zlib deflate error: %d %s", zr, s->zstrm->msg); s->error = xstrdup("Error compressing data"); return EOF; } /* http://www.zlib.net/manual.html says: * If deflate returns with avail_out == 0, this function must be * called again with the same value of the flush parameter and * more output space (updated avail_out), until the flush is * complete (deflate returns with non-zero avail_out). */ } while (!s->zstrm->avail_out); ptr = s->zbuf; left = s->zbuf_size - s->zstrm->avail_out; } #endif /* HAVE_ZLIB */ if (s->saslssf != 0) { /* encode the data */ int result = sasl_encode(s->conn, (char *) ptr, left, output_buf, output_len); if (result != SASL_OK) { char errbuf[256]; const char *ed = sasl_errdetail(s->conn); snprintf(errbuf, 256, "encoding error: %s; %s", sasl_errstring(result, NULL, NULL), ed ? ed : "no detail"); s->error = xstrdup(errbuf); return EOF; } } else { *output_buf = (char *) ptr; *output_len = left; } return 0; } /* A wrapper for write() that handles SSL and EINTR */ static int prot_flush_writebuffer(struct protstream *s, const char *buf, size_t len) { int n; do { cmdtime_netstart(); #ifdef HAVE_SSL if (s->tls_conn != NULL) { n = SSL_write(s->tls_conn, (char *)buf, len); } else { n = write(s->fd, buf, len); } #else /* HAVE_SSL */ n = write(s->fd, buf, len); #endif /* HAVE_SSL */ cmdtime_netend(); } while (n == -1 && errno == EINTR && !signals_poll()); return n; } int prot_flush_internal(struct protstream *s, int force) { int n; int save_dontblock = s->dontblock; const char *ptr = (char *) s->buf; /* Memory buffer info */ unsigned left = s->ptr - s->buf; assert(s->write); /* Is this protstream finished? */ if (s->eof || s->error) { s->ptr = s->buf; s->cnt = 1; return EOF; } /* make sure that the main file descriptor is set up to * be blocking or nonblocking based on the configuration of the * protstream and the force flag */ if(force) s->dontblock = 0; if(s->dontblock != s->dontblock_isset) { nonblock(s->fd,s->dontblock); s->dontblock_isset = s->dontblock; } /* end protstream setup */ /* if writing to a buffer, just append the lot. Always works */ if (s->writetobuf) { buf_appendmap(s->writetobuf, ptr, left); } /* If we're doing a blocking write, flush the buffers, bigbuffer first */ else if (!s->dontblock) { if(s->big_buffer != PROT_NO_FD) { /* Write the bigbuffer */ do { n = prot_flush_writebuffer(s, s->bigbuf_base + s->bigbuf_pos, s->bigbuf_len - s->bigbuf_pos); if(n == -1) { s->error = xstrdup(strerror(errno)); goto done; } else if (n > 0) { s->bigbuf_pos += n; } } while(s->bigbuf_len != s->bigbuf_pos); /* Free the bigbuffer */ map_free(&(s->bigbuf_base), &(s->bigbuf_siz)); close(s->big_buffer); s->bigbuf_len = s->bigbuf_pos = 0; s->big_buffer = PROT_NO_FD; } /* Is there anything in the memory buffer? */ if(!left) { goto done; } /* Do a regular write of whatever is left */ /* Log and Encode it */ prot_flush_log(s); if(prot_flush_encode(s, &ptr, &left) == EOF) { /* s->error set by prot_flush_encode */ goto done; } /* Write it to descriptor */ do { n = prot_flush_writebuffer(s, ptr, left); if(n == -1) { s->error = xstrdup(strerror(errno)); goto done; } else if (n > 0) { ptr += n; left -= n; } } while(left); } /* Nonblocking */ else { /* If we've been feeding a bigbuffer, write out from the current * position as much as we can */ if (s->big_buffer != PROT_NO_FD) { /* Write what we can. */ n = prot_flush_writebuffer(s, s->bigbuf_base + s->bigbuf_pos, s->bigbuf_len - s->bigbuf_pos); if(n == -1 && errno == EAGAIN) { /* No room in the pipe, but we don't care */ n = 0; } else if(n == -1) { s->error = xstrdup(strerror(errno)); goto done; } if (n > 0) { s->bigbuf_pos += n; } } /* If there isn't anything in the memory buffer, we're done now */ if(!left) { goto done; } /* Prepare the data in the memory buffer */ prot_flush_log(s); /* Encode it */ if(prot_flush_encode(s, &ptr, &left) == EOF) { /* prot_flush_encode set s->error */ goto done; } if(s->big_buffer == PROT_NO_FD || s->bigbuf_pos == s->bigbuf_len) { /* No bigbuffer currently open (or we've written the current one to its entirety), so write what we can from memory */ n = prot_flush_writebuffer(s, ptr, left); if(n == -1 && errno == EAGAIN) { /* No room in the pipe, but we don't care */ n = 0; } else if(n == -1) { s->error = xstrdup(strerror(errno)); goto done; } if(n > 0) { ptr += n; left -= n; } } /* if there is data still to send, it needs to go to the bigbuffer */ if(left) { struct stat sbuf; if(s->big_buffer == PROT_NO_FD) { /* open new bigbuffer */ int fd = create_tempfile(libcyrus_config_getstring(CYRUSOPT_TEMP_PATH)); if(fd == -1) { s->error = xstrdup(strerror(errno)); goto done; } s->big_buffer = fd; } do { n = write(s->big_buffer, ptr, left); if (n == -1 && (errno != EINTR || signals_poll())) { syslog(LOG_ERR, "write to protstream buffer failed: %s", strerror(errno)); fatal("write to big buffer failed", EC_OSFILE); } if (n > 0) { ptr += n; left -= n; } } while (left); /* We did a write to the bigbuffer, refresh the memory map */ if (fstat(s->big_buffer, &sbuf) == -1) { syslog(LOG_ERR, "IOERROR: fstating temp protlayer buffer: %m"); fatal("failed to fstat protlayer buffer", EC_IOERR); } s->bigbuf_len = sbuf.st_size; map_refresh(s->big_buffer, 0, &(s->bigbuf_base), &(s->bigbuf_siz), s->bigbuf_len, "temp protlayer buffer", NULL); } } /* end of blocking/nonblocking if statment */ /* Reset the memory buffer -- should be done on EOF or on success. */ s->ptr = s->buf; s->cnt = s->maxplain; done: /* are we done with the big buffer? If so, free it. This includes * when we exit with error */ if (s->big_buffer != PROT_NO_FD && (s->bigbuf_pos == s->bigbuf_len || s->error)) { map_free(&(s->bigbuf_base), &(s->bigbuf_siz)); close(s->big_buffer); s->bigbuf_len = s->bigbuf_pos = 0; s->big_buffer = PROT_NO_FD; } if (force) { /* we don't need to call nonblock() again, because it will be * set correctly on the next prot_flush_internal() anyway */ s->dontblock = save_dontblock; } /* If we are exiting with an error, we should clear our memory buffer * and set our return code */ if(s->error) { s->ptr = s->buf; s->cnt = s->maxplain; return EOF; } return 0; } /* * Write to the output stream 's' the 'len' bytes of data at 'buf' */ EXPORTED int prot_write(struct protstream *s, const char *buf, unsigned len) { assert(s->write); if(s->error || s->eof) return EOF; if(len == 0) return 0; /* Different type of data, adjust layers accordingly */ if (s->boundary) { #ifdef HAVE_ZLIB if (s->zstrm) { int zr = Z_OK; int zlevel = Z_DEFAULT_COMPRESSION; if (is_incompressible(buf, len)) zlevel = Z_NO_COMPRESSION; if (zlevel != s->zlevel) { s->zlevel = zlevel; /* flush any pending data */ if (s->ptr != s->buf) { if (prot_flush_internal(s, 1) == EOF) return EOF; } /* Set new compression level */ zr = deflateParams(s->zstrm, s->zlevel, Z_DEFAULT_STRATEGY); if (zr != Z_OK) { s->error = xstrdup("Error setting compression level"); return EOF; } } } #endif /* HAVE_ZLIB */ s->boundary = 0; } while (len >= s->cnt) { /* XXX can we manage to write data from 'buf' without copying it to s->ptr ? */ memcpy(s->ptr, buf, s->cnt); s->ptr += s->cnt; buf += s->cnt; len -= s->cnt; s->cnt = 0; if (prot_flush_internal(s,0) == EOF) return EOF; } memcpy(s->ptr, buf, len); s->ptr += len; s->cnt -= len; s->bytes_out += len; if (s->error || s->eof) return EOF; assert(s->cnt > 0); return 0; } EXPORTED int prot_putbuf(struct protstream *s, struct buf *buf) { return prot_write(s, buf->s, buf->len); } EXPORTED int prot_puts(struct protstream *s, const char *str) { return prot_write(s, str, strlen(str)); } /* * Stripped-down version of printf() that works on protection streams * Only understands '%lld', '%llu', '%llx', '%ld', '%lu', '%lx', * '%d', %u', '%x', '%s', '%tu', '%td', '%c', and '%%' * in the format string. */ EXPORTED int prot_printf(struct protstream *s, const char *fmt, ...) { va_list pvar; int r; va_start(pvar, fmt); r = prot_vprintf(s, fmt, pvar); va_end(pvar); return r; } EXPORTED int prot_vprintf(struct protstream *s, const char *fmt, va_list pvar) { char *percent, *p; long l; unsigned long ul; int i; unsigned u; char buf[30]; assert(s->write); while ((percent = strchr(fmt, '%')) != 0) { prot_write(s, fmt, percent-fmt); switch (*++percent) { case '%': (void)prot_putc('%', s); break; case 'l': switch (*++percent) { case 'd': l = va_arg(pvar, long); snprintf(buf, sizeof(buf), "%ld", l); prot_write(s, buf, strlen(buf)); break; case 'u': ul = va_arg(pvar, long); snprintf(buf, sizeof(buf), "%lu", ul); prot_write(s, buf, strlen(buf)); break; case 'x': l = va_arg(pvar, long); snprintf(buf, sizeof(buf), "%lx", l); prot_write(s, buf, strlen(buf)); break; case 'l': { long long int ll; unsigned long long int ull; switch (*++percent) { case 'd': ll = va_arg(pvar, long long int); snprintf(buf, sizeof(buf), "%lld", ll); prot_write(s, buf, strlen(buf)); break; case 'u': ull = va_arg(pvar, unsigned long long int); snprintf(buf, sizeof(buf), "%llu", ull); prot_write(s, buf, strlen(buf)); break; case 'x': ll = va_arg(pvar, long long int); snprintf(buf, sizeof(buf), "%llx", ll); prot_write(s, buf, strlen(buf)); break; default: abort(); } break; } default: abort(); } break; case 'd': i = va_arg(pvar, int); snprintf(buf, sizeof(buf), "%d", i); prot_write(s, buf, strlen(buf)); break; case 'u': u = va_arg(pvar, unsigned); snprintf(buf, sizeof(buf), "%u", u); prot_write(s, buf, strlen(buf)); break; case 'x': i = va_arg(pvar, int); snprintf(buf, sizeof(buf), "%x", i); prot_write(s, buf, strlen(buf)); break; /* according to linux 'man 3 printf' this is supposed to be * of type "ptrdiff_t", not "size_t" - but don't want to break * running code! */ case 't': { size_t tu; ssize_t td; switch (*++percent) { case 'u': tu = va_arg(pvar, size_t); snprintf(buf, sizeof(buf), "%tu", tu); prot_write(s, buf, strlen(buf)); break; case 'd': td = va_arg(pvar, ssize_t); snprintf(buf, sizeof(buf), "%td", td); prot_write(s, buf, strlen(buf)); break; default: abort(); } break; } case 's': p = va_arg(pvar, char *); prot_write(s, p, strlen(p)); break; case 'c': i = va_arg(pvar, int); (void)prot_putc(i, s); break; case 'z': { size_t zu; ssize_t zd; switch (*++percent) { case 'u': zu = va_arg(pvar, size_t); snprintf(buf, sizeof(buf), "%zu", zu); prot_write(s, buf, strlen(buf)); break; case 'd': zd = va_arg(pvar, ssize_t); snprintf(buf, sizeof(buf), "%zd", zd); prot_write(s, buf, strlen(buf)); break; default: abort(); } break; } default: abort(); } fmt = percent+1; } prot_write(s, fmt, strlen(fmt)); if (s->error || s->eof) return EOF; return 0; } EXPORTED int prot_printliteral(struct protstream *out, const char *s, size_t size) { int r; if (out->isclient) r = prot_printf(out, "{" SIZE_T_FMT "+}\r\n", size); else r = prot_printf(out, "{" SIZE_T_FMT "}\r\n", size); if (r) return r; return prot_write(out, s, size); } #define isQCHAR(c) \ (!((c) & 0x80 || *p == '\r' || (c) == '\n' \ || (c) == '\"' || (c) == '%' || (c) == '\\')) #define MAXQSTRING 1024 /* * Print 's' as a quoted-string or literal (but not an atom) */ EXPORTED int prot_printstring(struct protstream *out, const char *s) { const char *p; if (!s) return prot_printf(out, "NIL"); /* Look for any non-QCHAR characters */ for (p = s; *p && (p-s) < MAXQSTRING; p++) { if (!isQCHAR(*p)) break; } /* if it's too long, literal it */ if (*p || (p-s) >= MAXQSTRING) { return prot_printliteral(out, s, strlen(s)); } return prot_printf(out, "\"%s\"", s); } /* * Print the @n bytes at @s as a quoted-string or literal. * Handles embedded NULs. */ EXPORTED int prot_printmap(struct protstream *out, const char *s, size_t n) { const char *p; int r; if (!s) return prot_printf(out, "NIL"); /* if it's too long, literal it */ if (n >= MAXQSTRING) return prot_printliteral(out, s, n); /* Look for NULs or any non-QCHAR characters */ for (p = s; (size_t)(p-s) < n; p++) { if (!*p || !isQCHAR(*p)) return prot_printliteral(out, s, n); } prot_putc('"', out); r = prot_write(out, s, n); if (r < 0) return r; prot_putc('"', out); return r+2; } /* * Print the @n bytes at @s as an atom, quoted-string or literal. * Handles embedded NULs. */ EXPORTED int prot_printamap(struct protstream *out, const char *s, size_t n) { const char *p; int r; if (!s) return prot_printf(out, "NIL"); if (imparse_isnatom(s, n) && (n != 3 || memcmp(s, "NIL", 3))) return prot_write(out, s, n); /* if it's too long, literal it */ if (n >= MAXQSTRING) return prot_printliteral(out, s, n); /* Look for NULs or any non-QCHAR characters */ for (p = s; (size_t)(p-s) < n; p++) { if (!*p || !isQCHAR(*p)) return prot_printliteral(out, s, n); } prot_putc('"', out); r = prot_write(out, s, n); if (r < 0) return r; prot_putc('"', out); return r+2; } /* * Print 's' as an atom, quoted-string, or literal */ EXPORTED int prot_printastring(struct protstream *out, const char *s) { if (!s) return prot_printf(out, "NIL"); /* special cases for atoms */ if (!*s) return prot_printf(out, "\"\""); if (imparse_isatom(s) && strcmp(s, "NIL")) return prot_printf(out, "%s", s); /* not an atom, so pass to printstring */ return prot_printstring(out, s); } /* * Read from the protections stream 's' up to 'size' bytes into the buffer * 'buf'. Returns the number of bytes read, or 0 for some error. */ EXPORTED int prot_read(struct protstream *s, char *buf, unsigned size) { int c; assert(!s->write); if (!size) return 0; /* If no data in the input buffer, get some */ if (!s->cnt) { c = prot_fill(s); if (c == EOF) return 0; prot_ungetc(c, s); } if (size > s->cnt) size = s->cnt; memcpy(buf, s->ptr, size); s->ptr += size; s->cnt -= size; s->can_unget += size; s->bytes_in += size; /* prot_fill added the 1 already */ return size; } /* * Read from the protections stream 's' up to 'size' bytes, and append them * to the buffer 'buf'. Returns the number of bytes read, or 0 for some error. */ EXPORTED int prot_readbuf(struct protstream *s, struct buf *buf, unsigned size) { buf_ensure(buf, size); size = prot_read(s, buf->s + buf->len, size); buf->len += size; return size; } /* * select() for protection streams, read only * Also supports selecting on an extra file descriptor * * returns # of protstreams with pending data (including the extra fd) * * Only works for readable protstreams */ EXPORTED int prot_select(struct protgroup *readstreams, int extra_read_fd, struct protgroup **out, int *extra_read_flag, struct timeval *timeout) { struct protstream *s, *timeout_prot = NULL; struct protgroup *retval = NULL; int max_fd, found_fds = 0; unsigned i; fd_set rfds; int have_readtimeout = 0; struct timeval my_timeout; struct prot_waitevent *event; time_t now = time(NULL); time_t read_timeout = 0; assert(readstreams || extra_read_fd != PROT_NO_FD); assert(extra_read_fd == PROT_NO_FD || extra_read_flag); assert(out); /* Initialize things we might use */ errno = 0; found_fds = 0; FD_ZERO(&rfds); /* If extra_read_fd is PROT_NO_FD, then the first protstream * will override it */ max_fd = extra_read_fd; for(i = 0; inext_element; i++) { int have_thistimeout = 0; /* used to compute the minimal timeout for */ time_t this_timeout = 0; /* this stream */ s = readstreams->group[i]; if (!s) continue; assert(!s->write); /* scan for waitevent callbacks */ for (event = s->waitevent; event; event = event->next) { if(!have_thistimeout || event->mark - now < this_timeout) { this_timeout = event->mark - now; have_thistimeout = 1; } } /* check the idle timeout on this one as well */ if(s->read_timeout && (!have_thistimeout || s->timeout_mark - now < this_timeout)) { this_timeout = s->timeout_mark - now; have_thistimeout = 1; } if(!s->dontblock && have_thistimeout && (!have_readtimeout || now + this_timeout < read_timeout)) { read_timeout = now + this_timeout; have_readtimeout = 1; if(!timeout || this_timeout <= timeout->tv_sec) timeout_prot = s; } FD_SET(s->fd, &rfds); if(s->fd > max_fd) max_fd = s->fd; /* Is something currently pending in our protstream's buffer? */ if(s->cnt > 0) { found_fds++; if(!retval) retval = protgroup_new(readstreams->next_element + 1); protgroup_insert(retval, s); } #ifdef HAVE_SSL else if(s->tls_conn != NULL && SSL_pending(s->tls_conn)) { found_fds++; if(!retval) retval = protgroup_new(readstreams->next_element + 1); protgroup_insert(retval, s); } #endif } /* xxx we should probably do a nonblocking select on the remaining * protstreams instead of skipping this part entirely */ if(!retval) { time_t sleepfor; /* do a select */ if(extra_read_fd != PROT_NO_FD) { /* max_fd started with atleast extra_read_fd */ FD_SET(extra_read_fd, &rfds); } if(read_timeout < now) sleepfor = 0; else sleepfor = read_timeout - now; /* If we don't have a timeout structure, and we need one, use * a local version. Otherwise, make sure that we are timing out * for the right reason */ if(have_readtimeout && (!timeout || sleepfor < timeout->tv_sec)) { if(!timeout) timeout = &my_timeout; timeout->tv_sec = sleepfor; timeout->tv_usec = 0; } if(signals_select(max_fd + 1, &rfds, NULL, NULL, timeout) == -1) return -1; /* Reset now */ now = time(NULL); if(extra_read_fd != PROT_NO_FD && FD_ISSET(extra_read_fd, &rfds)) { *extra_read_flag = 1; found_fds++; } else if(extra_read_flag) { *extra_read_flag = 0; } for(i = 0; inext_element; i++) { s = readstreams->group[i]; if (!s) continue; if(FD_ISSET(s->fd, &rfds)) { found_fds++; if(!retval) retval = protgroup_new(readstreams->next_element + 1); protgroup_insert(retval, s); } else if(s == timeout_prot && now >= read_timeout) { /* If we timed out, be sure to add the protstream we were * waiting for, even if it didn't show up */ found_fds++; if(!retval) retval = protgroup_new(readstreams->next_element + 1); protgroup_insert(retval, s); } } } *out = retval; return found_fds; } /* * Version of fgets() that works with protection streams. */ EXPORTED char *prot_fgets(char *buf, unsigned size, struct protstream *s) { char *p = buf; int c; assert(!s->write); if (size < 2 || s->eof) return 0; size--; while (size && (c = prot_getc(s)) != EOF) { size--; *p++ = c; s->bytes_in++; if (c == '\n') break; } if (p == buf) return 0; *p++ = '\0'; return buf; } /* Handle protgroups */ /* Create a new protgroup of the given size, or 32 if size is 0 */ EXPORTED struct protgroup *protgroup_new(size_t size) { struct protgroup *ret = xmalloc(sizeof(struct protgroup)); if(!size) size = PROTGROUP_SIZE_DEFAULT; ret->nalloced = size; ret->next_element = 0; ret->group = xzmalloc(size * sizeof(struct protstream *)); return ret; } struct protgroup *protgroup_copy(struct protgroup *src) { struct protgroup *dest; assert(src); dest = protgroup_new(src->nalloced); if(src->next_element) { memcpy(dest->group, src->group, src->next_element * sizeof(struct protstream *)); } return dest; } EXPORTED void protgroup_reset(struct protgroup *group) { if(group) { memset(group->group, 0, group->nalloced * sizeof(struct protstream *)); group->next_element = 0; } } EXPORTED void protgroup_free(struct protgroup *group) { if(group) { assert(group->group); free(group->group); free(group); } } EXPORTED void protgroup_insert(struct protgroup *group, struct protstream *item) { unsigned i, empty; assert(group); assert(item); /* See if we already have this protstream */ for (i = 0, empty = group->next_element; i < group->next_element; i++) { if (!group->group[i]) empty = i; else if (group->group[i] == item) return; } /* Double size of the protgroup if we're at our limit */ if (empty == group->next_element && group->next_element++ == group->nalloced) { group->nalloced *= 2; group->group = xrealloc(group->group, group->nalloced * sizeof(struct protstream *)); } /* Insert the item at the empty location */ group->group[empty] = item; } EXPORTED void protgroup_delete(struct protgroup *group, struct protstream *item) { unsigned i; assert(group); assert(item); /* find the protstream */ for (i = 0; i < group->next_element; i++) { if (group->group[i] == item) { /* slide all remaining elements down one slot */ group->next_element--; for (; i < group->next_element; i++) { group->group[i] = group->group[i+1]; } group->group[i] = NULL; return; } } syslog(LOG_ERR, "protgroup_delete(): can't find protstream in group"); } EXPORTED struct protstream *protgroup_getelement(struct protgroup *group, size_t element) { assert(group); if (element >= group->next_element) return NULL; return group->group[element]; } EXPORTED int prot_getc(struct protstream *s) { assert(!s->write); if (s->cnt > 0) { --s->cnt; s->can_unget++; s->bytes_in++; return *(s->ptr)++; } return prot_fill(s); } EXPORTED int prot_ungetc(int c, struct protstream *s) { assert(!s->write); if (c == EOF) return EOF; if (!s->can_unget) fatal("Can't unwind any more", EC_SOFTWARE); s->cnt++; s->can_unget--; s->bytes_in--; s->ptr--; if (*s->ptr != c) fatal("Trying to unput wrong character", EC_SOFTWARE); return c; } EXPORTED int prot_putc(int c, struct protstream *s) { assert(s->write); assert(s->cnt > 0); *s->ptr++ = c; s->bytes_out++; if (--s->cnt == 0) return prot_flush_internal(s,0); return 0; } cyrus-imapd-2.5.10/lib/imapurl.c0000644000175000017500000003577413001236020013343 00000000000000/* * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. * * derived from chris newman's code */ #include #include #include #include #include #include #include "imapurl.h" #include "xmalloc.h" #include "times.h" #include "util.h" /* URL unsafe printable characters */ static const char urlunsafe[] = " \"#%&+:;<=>?@[\\]^`{|}"; /* UTF7 modified base64 alphabet */ static const char base64chars[] = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+,"; #define UNDEFINED 64 /* UTF16 definitions */ #define UTF16MASK 0x03FFUL #define UTF16SHIFT 10 #define UTF16BASE 0x10000UL #define UTF16HIGHSTART 0xD800UL #define UTF16HIGHEND 0xDBFFUL #define UTF16LOSTART 0xDC00UL #define UTF16LOEND 0xDFFFUL /* Convert an IMAP mailbox to a URL path * dst needs to have roughly 4 times the storage space of src * Hex encoding can triple the size of the input * UTF-7 can be slightly denser than UTF-8 * (worst case: 8 octets UTF-7 becomes 9 octets UTF-8) */ static void MailboxToURL(char *dst, const char *src) { unsigned char c, i, bitcount; unsigned long ucs4, utf16, bitbuf; unsigned char base64[256], utf8[6]; /* initialize modified base64 decoding table */ memset(base64, UNDEFINED, sizeof (base64)); for (i = 0; i < sizeof (base64chars); ++i) { base64[(int) base64chars[i]] = i; } /* loop until end of string */ while (*src != '\0') { c = *src++; /* deal with literal characters and &- */ if (c != '&' || *src == '-') { if (c < ' ' || c > '~' || strchr(urlunsafe, c) != NULL) { /* hex encode if necessary */ *dst++ = '%'; dst += bin_to_hex(&c, 1, dst, BH_UPPER); } else { /* encode literally */ *dst++ = c; } /* skip over the '-' if this is an &- sequence */ if (c == '&') ++src; } else { /* convert modified UTF-7 -> UTF-16 -> UCS-4 -> UTF-8 -> HEX */ bitbuf = 0; bitcount = 0; ucs4 = 0; while ((c = base64[(unsigned char) *src]) != UNDEFINED) { ++src; bitbuf = (bitbuf << 6) | c; bitcount += 6; /* enough bits for a UTF-16 character? */ if (bitcount >= 16) { bitcount -= 16; utf16 = (bitcount ? bitbuf >> bitcount : bitbuf) & 0xffff; /* convert UTF16 to UCS4 */ if (utf16 >= UTF16HIGHSTART && utf16 <= UTF16HIGHEND) { ucs4 = (utf16 - UTF16HIGHSTART) << UTF16SHIFT; continue; } else if (utf16 >= UTF16LOSTART && utf16 <= UTF16LOEND) { ucs4 += utf16 - UTF16LOSTART + UTF16BASE; } else { ucs4 = utf16; } /* convert UTF-16 range of UCS4 to UTF-8 */ if (ucs4 <= 0x7fUL) { utf8[0] = ucs4; i = 1; } else if (ucs4 <= 0x7ffUL) { utf8[0] = 0xc0 | (ucs4 >> 6); utf8[1] = 0x80 | (ucs4 & 0x3f); i = 2; } else if (ucs4 <= 0xffffUL) { utf8[0] = 0xe0 | (ucs4 >> 12); utf8[1] = 0x80 | ((ucs4 >> 6) & 0x3f); utf8[2] = 0x80 | (ucs4 & 0x3f); i = 3; } else { utf8[0] = 0xf0 | (ucs4 >> 18); utf8[1] = 0x80 | ((ucs4 >> 12) & 0x3f); utf8[2] = 0x80 | ((ucs4 >> 6) & 0x3f); utf8[3] = 0x80 | (ucs4 & 0x3f); i = 4; } /* convert utf8 to hex. * RFC3986 says: For consistency, URI producers and * normalizers should use uppercase hexadecimal digits * for all percent-encodings. */ *dst++ = '%'; dst += bin_to_hex(utf8, i, dst, BH_UPPER|BH_SEPARATOR('%')); } } /* skip over trailing '-' in modified UTF-7 encoding */ if (*src == '-') ++src; } } /* terminate destination string */ *dst = '\0'; } /* Convert hex coded UTF-8 URL path to modified UTF-7 IMAP mailbox * dst should be about twice the length of src to deal with non-hex * coded URLs */ EXPORTED int URLtoMailbox(char *dst, const char *src) { unsigned char c; unsigned int utf8pos = 0, utf8total, utf7mode, bitstogo, utf16flag; unsigned long ucs4 = 0, bitbuf = 0; utf7mode = 0; /* is the output UTF7 currently in base64 mode? */ utf8total = 0; /* how many octets is the current input UTF-8 char; 0 == between characters */ bitstogo = 0; /* bits that need to be encoded into base64; if bitstogo != 0 then utf7mode == 1 */ while ((c = (unsigned char)*src) != '\0') { ++src; /* undo hex-encoding */ if (c == '%' && src[0] != '\0' && src[1] != '\0') { if (hex_to_bin(src, 2, &c) != 1) return -1; src += 2; } /* normal character? */ if (c >= ' ' && c <= '~') { /* switch out of UTF-7 mode */ if (utf7mode) { if (bitstogo) { *dst++ = base64chars[(bitbuf << (6 - bitstogo)) & 0x3F]; } *dst++ = '-'; utf7mode = 0; bitstogo = bitbuf = 0; } *dst++ = c; /* encode '&' as '&-' */ if (c == '&') { *dst++ = '-'; } continue; } /* switch to UTF-7 mode */ if (!utf7mode) { *dst++ = '&'; utf7mode = 1; } /* Encode US-ASCII characters as themselves */ if (c < 0x80) { ucs4 = c; utf8total = 1; } else if (utf8total) { /* this is a subsequent octet of a multi-octet character */ /* save UTF8 bits into UCS4 */ ucs4 = (ucs4 << 6) | (c & 0x3FUL); if (++utf8pos < utf8total) { continue; } } else { /* this is the first octet of a multi-octet character */ utf8pos = 1; if (c < 0xE0) { utf8total = 2; ucs4 = c & 0x1F; } else if (c < 0xF0) { utf8total = 3; ucs4 = c & 0x0F; } else { /* NOTE: can't convert UTF8 sequences longer than 4 */ utf8total = 4; ucs4 = c & 0x03; } continue; } /* finished with UTF-8 character. make sure it isn't an overlong sequence. if it is, drop that character */ if ((ucs4 < 0x80 && utf8total > 1) || (ucs4 < 0x0800 && utf8total > 2) || (ucs4 < 0x00010000 && utf8total > 3) || (ucs4 < 0x00200000 && utf8total > 4) || (ucs4 < 0x04000000 && utf8total > 5) || (ucs4 < 0x80000000 && utf8total > 6)) { utf8total = 0; continue; } utf8total = 0; /* loop to split ucs4 into two utf16 chars if necessary */ do { if (ucs4 >= UTF16BASE) { ucs4 -= UTF16BASE; bitbuf = (bitbuf << 16) | ((ucs4 >> UTF16SHIFT) + UTF16HIGHSTART); ucs4 = (ucs4 & UTF16MASK) + UTF16LOSTART; utf16flag = 1; } else { bitbuf = (bitbuf << 16) | ucs4; utf16flag = 0; } bitstogo += 16; /* spew out base64 */ while (bitstogo >= 6) { bitstogo -= 6; *dst++ = base64chars[(bitstogo ? (bitbuf >> bitstogo) : bitbuf) & 0x3F]; } } while (utf16flag); } /* if in UTF-7 mode, finish in ASCII */ if (utf7mode) { if (bitstogo) { *dst++ = base64chars[(bitbuf << (6 - bitstogo)) & 0x3F]; } *dst++ = '-'; } /* tie off string */ *dst = '\0'; return 0; } /* Decode hex coded url * dst can be the same location as src, * since the decoded length will be shorter than the encoded length */ static int decode_url(char *dst, const char *src) { unsigned char c; while ((c = (unsigned char)*src) != '\0') { ++src; /* undo hex-encoding */ if (c == '%' && src[0] != '\0' && src[1] != '\0') { if (hex_to_bin(src, 2, &c) != 1) return -1; src += 2; } *dst++ = (char) c; } /* tie off string */ *dst = '\0'; return 0; } EXPORTED int imapurl_fromURL(struct imapurl *url, const char *s) { char *src; int step = 0; /* used to force correct ordering of url parts */ memset(url, 0, sizeof(struct imapurl)); url->freeme = xmalloc(6 * strlen(s) + 3); /* space for copy of URL + decoded mailbox */ src = strcpy(url->freeme, s); if (src[0] == '{') { /* c-client style */ char *se; src++; se = strchr(src, '}'); if (se == NULL) return -1; *se = '\0'; url->server = src; url->mailbox = se + 1; } else { /* IMAP URL */ int r; char *se; char *at; char *mbox = NULL; if (!strncmp(src, "imap://", 7)) { /* absolute URL */ src += 7; /* skip imap:// */ se = strchr(src, '/'); if (se == NULL) return -1; at = strchr(src, '@'); if (at) { *at = '\0'; r = decode_url(src, src); url->user = src; if (r) return r; src = at + 1; } *se = '\0'; url->server = src; src = mbox = ++se; } else { /* relative URL */ if (*src == '/') src++; mbox = src; } /* parse options */ errno = 0; while (src && (src = strchr(src, ';'))) { unsigned long ul; char *endp; if (src[-1] == '/') src[-1] = '\0'; /* trim mailbox at /; */ *src++ = '\0'; /* break url at ; */ if (step == 0 && !strncasecmp(src, "uidvalidity=", 12)) { src += 12; /* skip uidvalidity= */ ul = strtoul(src, &endp, 10); /* ends at '/' or '\0' */ if (errno || endp == src) return -1; url->uidvalidity = ul; step = 1; } else if (step <= 1 && !strncasecmp(src, "uid=", 4)) { src += 4; /* skip uid= */ ul = strtoul(src, &endp, 10); /* ends at '/' or '\0' */ if (errno || endp == src) return -1; url->uid = ul; step = 2; } else if (step == 2 && !strncasecmp(src, "section=", 8)) { src += 8; /* skip section= */ url->section = src; /* ends at ';' (next pass) or '\0' */ step = 3; } else if (step >= 2 && step <= 3 && !strncasecmp(src, "partial=", 8)) { src += 8; /* skip partial= */ ul = strtoul(src, &endp, 10); /* ends at '.', '/' or '\0' */ if (errno || endp == src) return -1; url->start_octet = ul; if (*endp == '.') { src = endp+1; /* skip . */ ul = strtoul(src, &endp, 10); /* ends at '/' or '\0' */ if (errno || endp == src) return -1; url->octet_count = ul; } step = 4; } else if (step >= 2 && step < 5 && !strncasecmp(src, "expire=", 7)) { int n; src += 7; /* skip expire= */ n = time_from_iso8601(src, &url->urlauth.expire); if (n < 0) return -1; src += n; step = 5; } else if (step >= 2 && step < 6 && !strncasecmp(src, "urlauth=", 8)) { char *u; src += 8; /* skip urlauth= */ url->urlauth.access = src; if ((u = strchr(src, ':'))) { url->urlauth.rump_len = (u - url->freeme); *u++ = '\0'; /* break urlauth at : */ url->urlauth.mech = u; if ((u = strchr(u, ':'))) { *u++ = '\0'; /* break urlauth at : */ url->urlauth.token = u; } src = u; } else { url->urlauth.rump_len = strlen(s); } step = 6; } else { return -1; } } if (mbox && *mbox) { url->mailbox = url->freeme + strlen(s) + 1; return URLtoMailbox((char *)url->mailbox, mbox); } } return 0; } EXPORTED void imapurl_toURL(char *dst, const struct imapurl *url) { if (url->server) { dst += sprintf(dst, "imap://"); if (url->user) dst += sprintf(dst, "%s", url->user); if (url->auth) dst += sprintf(dst, ";AUTH=%s", url->auth); if (url->user || url->auth) *dst++ = '@'; dst += sprintf(dst, "%s", url->server); } if (url->mailbox) { *dst++ = '/'; MailboxToURL(dst, url->mailbox); dst += strlen(dst); } if (url->uidvalidity) dst += sprintf(dst, ";UIDVALIDITY=%lu", url->uidvalidity); if (url->uid) { dst += sprintf(dst, "/;UID=%lu", url->uid); if (url->section) dst += sprintf(dst, "/;SECTION=%s", url->section); if (url->start_octet || url->octet_count) { dst += sprintf(dst, "/;PARTIAL=%lu", url->start_octet); if (url->octet_count) dst += sprintf(dst, ".%lu", url->octet_count); } } if (url->urlauth.access) { if (url->urlauth.expire) { strcpy(dst, ";EXPIRE="); dst += strlen(dst); dst += time_to_iso8601(url->urlauth.expire, dst, INT_MAX); } dst += sprintf(dst, ";URLAUTH=%s", url->urlauth.access); if (url->urlauth.mech) { dst += sprintf(dst, ":%s", url->urlauth.mech); if (url->urlauth.token) dst += sprintf(dst, ":%s", url->urlauth.token); } } } cyrus-imapd-2.5.10/lib/map_nommap.c0000644000175000017500000000700513001236020014000 00000000000000/* map_nommap.c -- dummy memory-mapping routines. * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include #include #include #include #include #include #include "xmalloc.h" #include "map.h" #include "exitcodes.h" #define SLOP (4*1024) EXPORTED const char *map_method_desc = "nommap"; /* * Create/refresh mapping of file */ void EXPORTED map_refresh(int fd, int onceonly, const char **base, size_t *len, size_t newlen, const char *name, const char *mboxname) { char *p; int n, left; struct stat sbuf; char buf[80]; if (newlen == MAP_UNKNOWN_LEN) { if (fstat(fd, &sbuf) == -1) { syslog(LOG_ERR, "IOERROR: fstating %s file%s%s: %m", name, mboxname ? " for " : "", mboxname ? mboxname : ""); snprintf(buf, sizeof(buf), "failed to fstat %s file", name); fatal(buf, EC_IOERR); } newlen = sbuf.st_size; } /* Need a larger buffer */ if (*len < newlen) { if (*len) free((char *)*base); *len = newlen + (onceonly ? 0 : SLOP); *base = xmalloc(*len); } lseek(fd, 0L, 0); left = newlen; p = (char*) *base; while (left) { n = read(fd, p, left); if (n <= 0) { if (n == 0) { syslog(LOG_ERR, "IOERROR: reading %s file%s%s: end of file", name, mboxname ? " for " : "", mboxname ? mboxname : ""); } else { syslog(LOG_ERR, "IOERROR: reading %s file%s%s: %m", name, mboxname ? " for " : "", mboxname ? mboxname : ""); } snprintf(buf, sizeof(buf), "failed to read %s file", name); fatal(buf, EC_IOERR); } p += n; left -= n; } } /* * Destroy mapping of file */ void EXPORTED map_free(const char **base, size_t *len) { if (*len) free((char *)*base); *base = 0; *len = 0; } cyrus-imapd-2.5.10/lib/xstrlcat.h0000644000175000017500000000424212772415051013546 00000000000000/* xmalloc.h -- Allocation package that calls fatal() when out of memory * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #ifndef INCLUDED_XSTRLCAT_H #define INCLUDED_XSTRLCAT_H #include /* for size_t */ #include /* for free() */ #include /* for strlen() */ #include #ifndef HAVE_STRLCAT extern size_t strlcat(char *dst, const char *src, size_t len); #endif #endif /* INCLUDED_XSTRLCAT_H */ cyrus-imapd-2.5.10/lib/prot.h0000644000175000017500000002431113001236020012644 00000000000000/* prot.h -- stdio-like module that handles buffering, SASL, and TLS * details for I/O over sockets * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #ifndef INCLUDED_PROT_H #define INCLUDED_PROT_H #include #include #include #include #include #ifdef HAVE_SSL #include #endif /* HAVE_SSL */ #ifdef HAVE_ZLIB #include #endif /* HAVE_ZLIB */ #include "util.h" #define PROT_BUFSIZE 4096 /* #define PROT_BUFSIZE 8192 */ #define PROT_NO_FD -1 struct protstream; struct prot_waitevent; typedef void prot_readcallback_t(struct protstream *s, void *rock); struct protstream { /* The Buffer */ unsigned char *buf; unsigned buf_size; unsigned char *ptr; /* The end of data in the buffer */ unsigned cnt; /* Space Remaining in buffer */ /* File Descriptors */ int fd; /* The Socket */ int logfd; /* The Telemetry Log (or PROT_NO_FD) */ int big_buffer; /* The Big Buffer (or PROT_NO_FD) */ /* SASL / TLS */ sasl_conn_t *conn; int saslssf; int maxplain; #ifdef HAVE_SSL SSL *tls_conn; #endif /* HAVE_SSL */ #ifdef HAVE_ZLIB /* (De)compress stream */ z_stream *zstrm; /* (De)compress buffer */ unsigned char *zbuf; unsigned int zbuf_size; /* Compress parameters */ int zlevel; int zflush; #endif /* HAVE_ZLIB */ /* Big Buffer Information */ const char *bigbuf_base; /* Base Pointer */ size_t bigbuf_siz; /* Overall Size of Buffer */ size_t bigbuf_len; /* Length of mapped file */ size_t bigbuf_pos; /* Current Position */ /* Status Flags */ int eof; int boundary; /* Type of data is about to change */ int fixedsize; char *error; /* Parameters */ int write; int dontblock; /* Application requested nonblocking */ int dontblock_isset; /* write only, we've fcntl(O_NONBLOCK)'d */ int read_timeout; time_t timeout_mark; struct protstream *flushonread; /* hack to write to an in-memory-string */ struct buf *writetobuf; int can_unget; int bytes_in; int bytes_out; int isclient; /* Events */ prot_readcallback_t *readcallback_proc; void *readcallback_rock; struct prot_waitevent *waitevent; /* For use by applications */ void *userdata; }; typedef struct prot_waitevent *prot_waiteventcallback_t(struct protstream *s, struct prot_waitevent *ev, void *rock); struct prot_waitevent { time_t mark; prot_waiteventcallback_t *proc; void *rock; struct prot_waitevent *next; }; /* Not for use by applications directly, but needed by the macros. */ int prot_flush_internal(struct protstream *s, int force); #define PROT_EOF_STRING "end of file reached" #define PROTGROUP_SIZE_DEFAULT 32 struct protgroup; /* Opaque protgroup structure */ extern int prot_getc(struct protstream *s); extern int prot_ungetc(int c, struct protstream *s); extern int prot_putc(int c, struct protstream *s); /* The following two macros control the blocking nature of * the protstream. * * For a read stream, the non-blocking behavior is that for the * reading functions (prot_read, prot_getc, etc) we will return EOF and * set errno = EAGAIN if no data was pending. * * For a write stream, it's a bit more complicated. When a nonblocking * write stream is flushed, a nonblocking write to the network is attempted. * if it cannot write all of its data, the remaining data is flushed to a * "bigbuffer" temporary file. (When the next flush occurs, this temporary * buffer is flushed first, and additional data is appended to it if necessary) * Note that this means that in the telemetry logs, only the time of the * first prot_flush_internal() call is logged, not the call for when the data * actually is flushed to the network successfully. */ #define prot_BLOCK(s) ((s)->dontblock = 0) #define prot_NONBLOCK(s) ((s)->dontblock = 1) #define prot_IS_BLOCKING(s) ((s)->dontblock == 0) /* Allocate/free the protstream structure */ extern struct protstream *prot_new(int fd, int write); extern struct protstream *prot_writebuf(struct buf *buf); extern struct protstream *prot_readmap(const char *base, uint32_t len); extern int prot_free(struct protstream *s); /* Set the telemetry logfile for a given protstream */ extern int prot_setlog(struct protstream *s, int fd); /* Get traffic counts */ extern int prot_bytes_in(struct protstream *s); extern int prot_bytes_out(struct protstream *s); #define prot_bytes_in(s) ((s)->bytes_in) #define prot_bytes_out(s) ((s)->bytes_out) /* Set the SASL options for a protstream (requires authentication to * be complete for the given sasl_conn_t */ extern int prot_setsasl(struct protstream *s, sasl_conn_t *conn); extern void prot_unsetsasl(struct protstream *s); #ifdef HAVE_SSL /* Set TLS options for a given protstream (requires a completed tls * negotiation */ extern int prot_settls(struct protstream *s, SSL *tlsconn); #endif /* HAVE_SSL */ /* Mark this protstream as a "client" for the purpose of generating * or consuming literals (thanks LITERAL+) */ int prot_setisclient(struct protstream *s, int val); #ifdef HAVE_ZLIB /* Enable (de)compression for a given protstream */ int prot_setcompress(struct protstream *s); #endif /* HAVE_ZLIB */ /* Tell the protstream that the type of data is about to change. */ int prot_data_boundary(struct protstream *s); /* Set a timeout for the connection (in seconds) */ extern int prot_settimeout(struct protstream *s, int timeout); /* Reset the timeout timer for the connection (in seconds) */ extern int prot_resettimeout(struct protstream *s); /* Connect two streams so that when you block on reading s, the layer * will automaticly flush flushs */ extern int prot_setflushonread(struct protstream *s, struct protstream *flushs); int prot_setreadcallback(struct protstream *s, prot_readcallback_t *proc, void *rock); extern struct prot_waitevent *prot_addwaitevent(struct protstream *s, time_t mark, prot_waiteventcallback_t *proc, void *rock); extern void prot_removewaitevent(struct protstream *s, struct prot_waitevent *event); extern const char *prot_error(struct protstream *s); extern int prot_rewind(struct protstream *s); /* Fill the buffer for a read stream with waiting data (may block) */ extern int prot_fill(struct protstream *s); /* Force a flush of an output stream */ extern int prot_flush(struct protstream *s); /* These are protlayer versions of the specified functions */ extern int prot_write(struct protstream *s, const char *buf, unsigned len); extern int prot_putbuf(struct protstream *s, struct buf *buf); extern int prot_puts(struct protstream *s, const char *str); extern int prot_vprintf(struct protstream *, const char *, va_list); extern int prot_printf(struct protstream *, const char *, ...) #ifdef __GNUC__ __attribute__ ((format (printf, 2, 3))); #else ; #endif extern int prot_printliteral(struct protstream *out, const char *s, size_t size); extern int prot_printstring(struct protstream *out, const char *s); extern int prot_printmap(struct protstream *out, const char *s, size_t n); extern int prot_printamap(struct protstream *out, const char *s, size_t n); extern int prot_printastring(struct protstream *out, const char *s); extern int prot_read(struct protstream *s, char *buf, unsigned size); extern int prot_readbuf(struct protstream *s, struct buf *buf, unsigned size); extern char *prot_fgets(char *buf, unsigned size, struct protstream *s); /* select() for protstreams */ extern int prot_select(struct protgroup *readstreams, int extra_read_fd, struct protgroup **out, int *extra_read_flag, struct timeval *timeout); /* Protgroup manipulations */ /* Create a new protgroup of a certain size or as a copy of another * protgroup */ struct protgroup *protgroup_new(size_t size); struct protgroup *protgroup_copy(struct protgroup *src); /* Cleanup a protgroup but don't release the allocated memory (so it can * be reused) */ void protgroup_reset(struct protgroup *group); /* Release memory for a protgroup */ void protgroup_free(struct protgroup *group); /* Insert an element into a protgroup */ void protgroup_insert(struct protgroup *group, struct protstream *item); /* Delete an element from a protgroup */ void protgroup_delete(struct protgroup *group, struct protstream *item); /* Returns the protstream at that position in the protgroup, or NULL if * an invalid element is requested */ struct protstream *protgroup_getelement(struct protgroup *group, size_t element); #endif /* INCLUDED_PROT_H */ cyrus-imapd-2.5.10/lib/bitvector.c0000644000175000017500000001330213001236020013652 00000000000000/* bitvector.c -- bit vector functions * * Copyright (c) 1994-2012 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include #include #include #include #include "xmalloc.h" #include "bitvector.h" #include "util.h" #ifndef MAX #define MAX(a,b) ((a)>(b)?(a):(b)) #endif #define vidx(x) ((x) >> 3) #define vmask(x) (1 << ((x) & 0x7)) #define vtailmask(x) ((unsigned char)(0xff << ((x) & 0x7))) #define vlen(x) vidx((x)+7) #define QUANTUM (256) EXPORTED void bv_init(bitvector_t *bv) { memset(bv, 0, sizeof(*bv)); } /* Ensure that the array contains enough memory for @len * bits, expanding the bitvector if necessary */ static void bv_ensure(bitvector_t *bv, unsigned int len) { len = vlen(len); /* now number of bytes */ if (len > bv->alloc) { unsigned int newalloc = ((len + QUANTUM-1) / QUANTUM) * QUANTUM; bv->bits = (unsigned char *)xrealloc(bv->bits, newalloc); memset(bv->bits + bv->alloc, 0, newalloc - bv->alloc); bv->alloc = newalloc; } } EXPORTED void bv_setsize(bitvector_t *bv, unsigned int len) { bv_ensure(bv, len); if (len < bv->length) { /* shrinking - need to clear old bits */ memset(bv->bits+vlen(len), 0, vlen(bv->length) - vlen(len)); bv->bits[vidx(len)] &= ~vtailmask(len); } bv->length = len; } EXPORTED void bv_prealloc(bitvector_t *bv, unsigned int len) { bv_ensure(bv, len); } EXPORTED void bv_copy(bitvector_t *to, const bitvector_t *from) { bv_setsize(to, from->length); memcpy(to->bits, from->bits, vlen(from->length)); } EXPORTED void bv_clearall(bitvector_t *bv) { if (bv->length) memset(bv->bits, 0, vlen(bv->length)); } EXPORTED void bv_setall(bitvector_t *bv) { if (bv->length) memset(bv->bits, 0xff, vlen(bv->length)); } EXPORTED int bv_isset(const bitvector_t *bv, unsigned int i) { if (i >= bv->length) return 0; return !!(bv->bits[vidx(i)] & vmask(i)); } EXPORTED void bv_set(bitvector_t *bv, unsigned int i) { bv_ensure(bv, i+1); bv->bits[vidx(i)] |= vmask(i); if (i >= bv->length) bv->length = i+1; } EXPORTED void bv_clear(bitvector_t *bv, unsigned int i) { if (i < bv->length) { bv_ensure(bv, i+1); bv->bits[vidx(i)] &= ~vmask(i); } } EXPORTED void bv_andeq(bitvector_t *a, const bitvector_t *b) { unsigned int n; unsigned int i; bv_ensure(a, b->length); if (!a->length) return; n = vlen(b->length+1); for (i = 0 ; i <= n ; i++) a->bits[i] &= b->bits[i]; n = vlen(a->length); for ( ; i <= n ; i++) a->bits[i] = 0; a->length = MAX(a->length, b->length); } EXPORTED void bv_oreq(bitvector_t *a, const bitvector_t *b) { unsigned int n; unsigned int i; bv_ensure(a, b->length); if (!a->length) return; n = vlen(b->length+1); for (i = 0 ; i <= n ; i++) a->bits[i] |= b->bits[i]; a->length = MAX(a->length, b->length); } /* Returns a string which describes the state of the bitvector, * useful for debugging. Returns a new string which must be free'd * by the caller */ EXPORTED char *bv_cstring(const bitvector_t *bv) { struct buf buf = BUF_INITIALIZER; unsigned int i; unsigned int first = ~0U; unsigned int last; const char *sep = ""; if (bv->length) { buf_truncate(&buf, vlen(bv->length)*2); bin_to_hex(bv->bits, vlen(bv->length), buf.s, 0); } buf_putc(&buf, '['); for (i = 0 ; i < bv->length ; i++) { if (bv->bits[vidx(i)] & vmask(i)) { if (first == ~0U) first = i; } else if (first != ~0U) { last = i-1; if (first == last) buf_printf(&buf, "%s%u", sep, first); else buf_printf(&buf, "%s%u-%u", sep, first, last); sep = ","; first = ~0U; } } if (first != ~0U) { last = bv->length-1; if (first == last) buf_printf(&buf, "%s%u", sep, first); else buf_printf(&buf, "%s%u-%u", sep, first, last); } buf_putc(&buf, ']'); return buf_release(&buf); } EXPORTED void bv_free(bitvector_t *bv) { if (bv->alloc) free(bv->bits); bv->length = 0; bv->alloc = 0; bv->bits = NULL; } cyrus-imapd-2.5.10/lib/stristr.h0000644000175000017500000000032312772415051013410 00000000000000/* stristr.h -- locate a substring case-insensitively */ #ifndef INCLUDED_STRISTR_H #define INCLUDED_STRISTR_H extern char *stristr(const char *haystack, const char *needle); #endif /* INCLUDED_STRISTR_H */ cyrus-imapd-2.5.10/lib/charset.c0000644000175000017500000010767413001236020013322 00000000000000/* charset.c -- International character set support * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include #include #include #include "charset.h" #include "xmalloc.h" #include "chartable.h" #include "util.h" #define U_REPLACEMENT 0xfffd #define unicode_isvalid(c) \ (!((c >= 0xd800 && c <= 0xdfff) || ((unsigned)c > 0x10ffff))) char QPSAFECHAR[256] = { /* control chars are unsafe */ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, /* http://en.wikipedia.org/wiki/Quoted-printable */ /* All printable ASCII characters (decimal values between 33 and 126) */ /* may be represented by themselves, except "=" (decimal 61). */ 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, /* all high bits are unsafe */ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }; struct qp_state { int isheader; int bytesleft; int codepoint; }; struct b64_state { int bytesleft; int codepoint; }; struct table_state { const struct charmap (*curtable)[256]; const struct charmap (*initialtable)[256]; int bytesleft; int codepoint; int mode; int num_bits; }; struct canon_state { int flags; int seenspace; }; struct comp_pat_s { int max_start; size_t patlen; }; struct search_state { ssize_t *starts; int max_start; int havematch; unsigned char *substr; size_t patlen; size_t offset; }; struct convert_rock; typedef void convertproc_t(struct convert_rock *rock, int c); typedef void freeconvert_t(struct convert_rock *rock); struct convert_rock { convertproc_t *f; freeconvert_t *cleanup; struct convert_rock *next; void *state; }; #define GROWSIZE 100 #define XX 127 /* * Table for decoding hexadecimal in quoted-printable */ static const char index_hex[256] = { XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, 0, 1, 2, 3, 4, 5, 6, 7, 8, 9,XX,XX, XX,XX,XX,XX, XX,10,11,12, 13,14,15,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,10,11,12, 13,14,15,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, }; #define HEXCHAR(c) (index_hex[(unsigned char)(c)]) /* * Table for decoding base64 */ static const char index_64[256] = { XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,62, XX,XX,XX,63, 52,53,54,55, 56,57,58,59, 60,61,XX,XX, XX,XX,XX,XX, XX, 0, 1, 2, 3, 4, 5, 6, 7, 8, 9,10, 11,12,13,14, 15,16,17,18, 19,20,21,22, 23,24,25,XX, XX,XX,XX,XX, XX,26,27,28, 29,30,31,32, 33,34,35,36, 37,38,39,40, 41,42,43,44, 45,46,47,48, 49,50,51,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, }; #define CHAR64(c) (index_64[(unsigned char)(c)]) EXPORTED const char *encoding_name(int encoding) { switch (encoding) { case ENCODING_NONE: return "none"; case ENCODING_QP: return "quoted-printable"; case ENCODING_BASE64: return "base64"; case ENCODING_UNKNOWN: return "unknown"; default: return "wtf"; } } static inline void convert_putc(struct convert_rock *rock, int c) { rock->f(rock, c); } static void convert_cat(struct convert_rock *rock, const char *s) { while (*s) { convert_putc(rock, (unsigned char)*s); s++; } } static void convert_catn(struct convert_rock *rock, const char *s, size_t len) { while (len-- > 0) { convert_putc(rock, (unsigned char)*s); s++; } } /* convertproc_t conversion functions */ static void qp2byte(struct convert_rock *rock, int c) { struct qp_state *s = (struct qp_state *)rock->state; int val; if (s->bytesleft) { s->bytesleft--; val = HEXCHAR(c); if (val == XX) { /* mark invalid regardless */ s->codepoint = -1; return; } if (s->codepoint != -1) { /* don't blat the invalid marker, but still absorb * the second char */ s->codepoint = (s->codepoint << 4) + val; } if (!s->bytesleft) { if (s->codepoint == -1) convert_putc(rock->next, 0xfffd); else convert_putc(rock->next, s->codepoint & 0xff); } return; } /* start an encoded byte */ if (c == '=') { s->bytesleft = 2; s->codepoint = 0; return; } /* underscores are space in headers */ if (s->isheader && c == '_') c = ' '; convert_putc(rock->next, c); } static void b64_2byte(struct convert_rock *rock, int c) { struct b64_state *s = (struct b64_state *)rock->state; char b = CHAR64(c); /* could just be whitespace, ignore it */ if (b == XX) return; switch (s->bytesleft) { case 0: s->codepoint = b; s->bytesleft = 3; break; case 3: convert_putc(rock->next, ((s->codepoint << 2) | (b >> 4)) & 0xff); s->codepoint = b; s->bytesleft = 2; break; case 2: convert_putc(rock->next, ((s->codepoint << 4) | (b >> 2)) & 0xff); s->codepoint = b; s->bytesleft = 1; break; case 1: convert_putc(rock->next, ((s->codepoint << 6) | b) & 0xff); s->codepoint = 0; s->bytesleft = 0; } } static void stripnl2uni(struct convert_rock *rock, int c) { if (c != '\r' && c != '\n') convert_putc(rock->next, c); } static void table2uni(struct convert_rock *rock, int c) { struct table_state *s = (struct table_state *)rock->state; struct charmap *map = (struct charmap *)&s->curtable[0][c & 0xff]; /* propagate errors */ if (c == 0xfffd) { convert_putc(rock->next, c); return; } if (map->c) convert_putc(rock->next, map->c); s->curtable = s->initialtable + map->next; } static void utf8_2uni(struct convert_rock *rock, int c) { struct table_state *s = (struct table_state *)rock->state; /* propagate errors */ if (c == 0xfffd) { convert_putc(rock->next, c); return; } if ((c & 0xf8) == 0xf0) { /* 11110xxx */ /* first of a 4 char sequence */ s->bytesleft = 3; s->codepoint = c & 0x07; /* 00000111 */ } else if ((c & 0xf0) == 0xe0) { /* 1110xxxx */ /* first of a 3 char sequence */ s->bytesleft = 2; s->codepoint = c & 0x0f; /* 00001111 */ } else if ((c & 0xe0) == 0xc0) { /* 110xxxxx */ /* first of a 2 char sequence */ s->bytesleft = 1; s->codepoint = c & 0x1f; /* 00011111 */ } else if ((c & 0xc0) == 0x80) { /* 10xxxxxx */ /* continuation char, handle only if expected */ if (s->bytesleft > 0) { s->codepoint = (s->codepoint << 6) + (c & 0x3f); /* 00111111 */ s->bytesleft--; if (!s->bytesleft) { convert_putc(rock->next, s->codepoint); s->codepoint = 0; } } } else { /* plain ASCII char */ convert_putc(rock->next, c); s->bytesleft = 0; s->codepoint = 0; } } static void utf7_2uni (struct convert_rock *rock, int c) { struct table_state *s = (struct table_state *)rock->state; /* propagate errors */ if (c == 0xfffd) { convert_putc(rock->next, c); return; } if (c & 0x80) { /* skip 8-bit chars */ convert_putc(rock->next, 0xfffd); return; } /* Inside a base64 encoded unicode fragment */ if (s->mode) { /* '-' marks the end of a fragment */ if (c == '-') { /* special case: sequence +- creates output '+' */ if (s->mode == 1) convert_putc(rock->next, '+'); /* otherwise no output for the '-' */ s->mode = 0; s->num_bits = 0; s->codepoint = 0; } /* a normal char drops us out of base64 mode */ else if (CHAR64(c) == XX) { /* pass on the char */ convert_putc(rock->next, c); /* and switch back to ASCII mode */ s->mode = 0; /* XXX: warn if num_bits > 4 or codepoint != 0 */ s->num_bits = 0; s->codepoint = 0; } /* base64 char - process it into the state machine */ else { s->mode = 2; /* we have some content, so don't process special +- */ /* add the 6 bits of value from this character */ s->codepoint = (s->codepoint << 6) + CHAR64(c); s->num_bits += 6; /* if we've got a full character's worth of bits, send it down * the line and keep the remainder for the next character */ if (s->num_bits >= 16) { s->num_bits -= 16; convert_putc(rock->next, (s->codepoint >> s->num_bits) & 0x7fff); s->codepoint &= ((1 << s->num_bits) - 1); /* avoid overflow by trimming */ } } } /* regular ASCII mode */ else { /* '+' switches to base64 unicode mode */ if (c == '+') { s->mode = 1; /* switch mode, but no content processed yet */ s->codepoint = 0; s->num_bits = 0; } /* regular ASCII char */ else { convert_putc(rock->next, c); } } } static void uni2searchform(struct convert_rock *rock, int c) { struct canon_state *s = (struct canon_state *)rock->state; int i; int code; unsigned char table16, table8; /* invalid character becomes an Oxff - that's illegal utf-8, * so it won't match */ if (c == 0xfffd) { convert_putc(rock->next, 0xff); return; } table16 = chartables_translation_block16[(c>>16) & 0xff]; /* no translations */ if (table16 == 255) { convert_putc(rock->next, c); return; } table8 = chartables_translation_block8[table16][(c>>8) & 0xff]; /* no translations */ if (table8 == 255) { convert_putc(rock->next, c); return; } /* use the xlate table */ code = chartables_translation[table8][c & 0xff]; /* case - zero length output */ if (code == 0) { return; } /* special case: whitespace or control characters */ if (code == ' ' || code == '\r' || code == '\n') { if (s->flags & CHARSET_SKIPSPACE) { return; } if (s->flags & CHARSET_MERGESPACE) { if (s->seenspace) return; s->seenspace = 1; code = ' '; /* one SPACE char */ } } else s->seenspace = 0; /* case - one character output */ if (code > 0) { convert_putc(rock->next, code); return; } /* case - multiple characters */ for (i = -code; chartables_translation_multichar[i]; i++) { int c = chartables_translation_multichar[i]; /* diacritical character range. This duplicates the * behaviour of Cyrus versions before 2.5 */ if (s->flags & CHARSET_SKIPDIACRIT) { if ((c & ~0xff) == 0x300) continue; } /* note: whitespace already stripped from multichar sequences... */ convert_putc(rock->next, c); } } static void uni2utf8(struct convert_rock *rock, int c) { if (c > 0xffff) { convert_putc(rock->next, 0xF0 + ((c >> 18) & 0x07)); convert_putc(rock->next, 0x80 + ((c >> 12) & 0x3f)); convert_putc(rock->next, 0x80 + ((c >> 6) & 0x3f)); convert_putc(rock->next, 0x80 + ( c & 0x3f)); } else if (c > 0x7ff) { convert_putc(rock->next, 0xE0 + ((c >> 12) & 0x0f)); convert_putc(rock->next, 0x80 + ((c >> 6) & 0x3f)); convert_putc(rock->next, 0x80 + ( c & 0x3f)); } else if (c > 0x7f) { convert_putc(rock->next, 0xC0 + ((c >> 6) & 0x1f)); convert_putc(rock->next, 0x80 + ( c & 0x3f)); } else { convert_putc(rock->next, c); } } static void byte2search(struct convert_rock *rock, int c) { struct search_state *s = (struct search_state *)rock->state; int i, cur; unsigned char b = (unsigned char)c; if (c == 0xfffd) { c = 0xff; /* searchable by invalid character! */ } /* check our "in_progress" matches to see if they're still valid */ for (i = 0, cur = 0; i < s->max_start; i++) { /* no more active offsets */ if (s->starts[i] == -1) break; /* if we've passed one that's not ongoing, copy back */ if (cur < i) s->starts[cur] = s->starts[i]; /* check that the substring is still maching */ if (b == s->substr[s->offset - s->starts[i]]) { if (s->offset - s->starts[i] == s->patlen - 1) { /* we're there! */ s->havematch = 1; } else { /* keep this one, it's ongoing */ cur++; } } } /* starting a new one! */ if (b == s->substr[0]) { /* have to treat this one specially! */ if (s->patlen == 1) s->havematch = 1; else s->starts[cur++] = s->offset; } /* empty out any others that aren't being kept */ while (cur < i) s->starts[cur++] = -1; /* increment the offset counter */ s->offset++; } static void byte2buffer(struct convert_rock *rock, int c) { struct buf *buf = (struct buf *)rock->state; buf_putc(buf, c & 0xff); } /* convert_rock manipulation routines */ static void table_switch(struct convert_rock *rock, int charset_num) { struct table_state *state = (struct table_state *)rock->state; /* wipe any current state */ memset(state, 0, sizeof(struct table_state)); /* it's a table based lookup */ if (chartables_charset_table[charset_num].table) { /* set up the initial table */ state->curtable = state->initialtable = chartables_charset_table[charset_num].table; rock->f = table2uni; } /* special case UTF-8 */ else if (strstr(chartables_charset_table[charset_num].name, "utf-8")) { rock->f = utf8_2uni; } /* special case UTF-7 */ else if (strstr(chartables_charset_table[charset_num].name, "utf-7")) { rock->f = utf7_2uni; } /* should never happen */ else { exit(1); /* do something fatal here! */ } } /* Extract a cstring from a buffer. NOTE: caller must free the memory * themselves once this is called. Resets the state. If you don't * call this function then buffer_free will clean up */ static char *buffer_cstring(struct convert_rock *rock) { struct buf *buf = (struct buf *)rock->state; return buf_release(buf); } static inline int search_havematch(struct convert_rock *rock) { struct search_state *s = (struct search_state *)rock->state; return s->havematch; } /* conversion cleanup routines */ static void basic_free(struct convert_rock *rock) { if (rock) { if (rock->state) free(rock->state); free(rock); } } static void search_free(struct convert_rock *rock) { if (rock && rock->state) { struct search_state *s = (struct search_state *)rock->state; if (s->starts) free(s->starts); } basic_free(rock); } static void buffer_free(struct convert_rock *rock) { if (rock && rock->state) { struct buf *buf = (struct buf *)rock->state; buf_free(buf); } basic_free(rock); } static void convert_free(struct convert_rock *rock) { struct convert_rock *next; while (rock) { next = rock->next; if (rock->cleanup) rock->cleanup(rock); else basic_free(rock); rock = next; } } /* converter initialisation routines */ static struct convert_rock *qp_init(int isheader, struct convert_rock *next) { struct convert_rock *rock = xzmalloc(sizeof(struct convert_rock)); struct qp_state *s = xzmalloc(sizeof(struct qp_state)); s->isheader = isheader; rock->state = (void *)s; rock->f = qp2byte; rock->next = next; return rock; } static struct convert_rock *b64_init(struct convert_rock *next) { struct convert_rock *rock = xzmalloc(sizeof(struct convert_rock)); rock->state = xzmalloc(sizeof(struct b64_state)); rock->f = b64_2byte; rock->next = next; return rock; } static struct convert_rock *stripnl_init(struct convert_rock *next) { struct convert_rock *rock = xzmalloc(sizeof(struct convert_rock)); rock->f = stripnl2uni; rock->next = next; return rock; } static struct convert_rock *canon_init(int flags, struct convert_rock *next) { struct convert_rock *rock = xzmalloc(sizeof(struct convert_rock)); struct canon_state *s = xzmalloc(sizeof(struct canon_state)); s->flags = flags; rock->f = uni2searchform; rock->state = s; rock->next = next; return rock; } static struct convert_rock *uni_init(struct convert_rock *next) { struct convert_rock *rock = xzmalloc(sizeof(struct convert_rock)); rock->f = uni2utf8; rock->next = next; return rock; } static struct convert_rock *table_init(int charset_num, struct convert_rock *next) { struct convert_rock *rock = xzmalloc(sizeof(struct convert_rock)); rock->state = xzmalloc(sizeof(struct table_state)); rock->next = next; table_switch(rock, charset_num); return rock; } static struct convert_rock *search_init(const char *substr, comp_pat *pat) { struct convert_rock *rock = xzmalloc(sizeof(struct convert_rock)); struct search_state *s = xzmalloc(sizeof(struct search_state)); struct comp_pat_s *p = (struct comp_pat_s *)pat; int i; /* copy in tracking vars */ s->max_start = p->max_start; s->patlen = p->patlen; s->substr = (unsigned char *)substr; /* allocate tracking space and initialise to "no match" */ s->starts = xmalloc(s->max_start * sizeof(size_t)); for (i = 0; i < s->max_start; i++) { s->starts[i] = -1; } /* set up the rock */ rock->f = byte2search; rock->cleanup = search_free; rock->state = (void *)s; return rock; } static struct convert_rock *buffer_init(void) { struct convert_rock *rock = xzmalloc(sizeof(struct convert_rock)); struct buf *buf = xzmalloc(sizeof(struct buf)); rock->f = byte2buffer; rock->cleanup = buffer_free; rock->state = (void *)buf; return rock; } /* API */ /* * Return the name of the given character set number, or NULL if * not known. */ EXPORTED const char *charset_name(charset_index i) { return (i >= 0 && i < chartables_num_charsets ? chartables_charset_table[i].name : "unknown"); } /* * Lookup the character set 'name'. Returns the character set number * or -1 if there is no matching character set. */ EXPORTED int charset_lookupname(const char *name) { int i; /* translate to canonical name */ for (i = 0; charset_aliases[i].name; i++) { if (!strcasecmp(name, charset_aliases[i].name)) { name = charset_aliases[i].canon_name; break; } } /* look up canonical name */ for (i = 0; i < chartables_num_charsets; i++) { if (!strcasecmp(name, chartables_charset_table[i].name)) return i; } return -1; } static int lookup_buf(const char *buf, int len) { char *name = xstrndup(buf, len); int res = charset_lookupname(name); free(name); return res; } /* * Convert the string 's' in the character set numbered 'charset' * into canonical searching form. Returns a newly allocated string * which must be free()d by the caller. */ EXPORTED char *charset_convert(const char *s, int charset, int flags) { struct convert_rock *input, *tobuffer; char *res; if (!s) return 0; if (charset < 0 || charset >= chartables_num_charsets) return xstrdup("X"); /* set up the conversion path */ tobuffer = buffer_init(); input = uni_init(tobuffer); input = canon_init(flags, input); input = table_init(charset, input); /* do the conversion */ convert_cat(input, s); /* extract the result */ res = buffer_cstring(tobuffer); /* clean up */ convert_free(input); return res; } EXPORTED char *charset_utf8_to_searchform(const char *s, int flags) { int charset = charset_lookupname("utf-8"); return charset_convert(s, charset, flags); } /* Convert from a given charset and encoding into utf8 */ EXPORTED char *charset_to_utf8(const char *msg_base, size_t len, int charset, int encoding) { struct convert_rock *input, *tobuffer; char *res; /* Initialize character set mapping */ if (charset < 0 || charset >= chartables_num_charsets) return 0; /* check for trivial search */ if (len == 0) return xstrdup(""); /* set up the conversion path */ tobuffer = buffer_init(); input = uni_init(tobuffer); input = table_init(charset, input); /* choose encoding extraction if needed */ switch (encoding) { case ENCODING_NONE: break; case ENCODING_QP: input = qp_init(0, input); break; case ENCODING_BASE64: input = b64_init(input); /* XXX have to have nl-mapping base64 in order to * properly count \n as 2 raw characters */ break; default: /* Don't know encoding--nothing can match */ convert_free(input); return 0; } convert_catn(input, msg_base, len); res = buffer_cstring(tobuffer); convert_free(input); return res; } static void mimeheader_cat(struct convert_rock *target, const char *s) { struct convert_rock *input, *stripnl; int eatspace = 0; const char *start, *endcharset, *encoding, *end; int len; int charset; const char *p; if (!s) return; /* set up the conversion path */ input = table_init(0, target); /* note: we assume the caller of this function has already * determined that all newlines are followed by whitespace */ stripnl = stripnl_init(input); start = s; while ((start = (const char*) strchr(start, '=')) != 0) { start++; if (*start != '?') continue; encoding = (const char*) strchr(start+1, '?'); if (!encoding) continue; endcharset = (const char*) strchr(start+1, '*'); /* Language code delimiter */ if (!endcharset || endcharset > encoding) endcharset = encoding; if (encoding[1] != 'b' && encoding[1] != 'B' && encoding[1] != 'q' && encoding[1] != 'Q') continue; if (encoding[2] != '?') continue; end = (const char*) strchr(encoding+3, '?'); if (!end || end[1] != '=') continue; /* * We have recognized a valid 1522-word. * Copy over leading text, unless it consists entirely of * whitespace and is between two 1522-words. */ if (eatspace) { for (p = s; p < (start-1) && Uisspace(*p); p++); if (p < (start-1)) eatspace = 0; } if (!eatspace) { len = start - s - 1; table_switch(input, 0); /* US_ASCII */ convert_catn(stripnl, s, len); } /* * Get the 1522-word's character set */ start++; charset = lookup_buf(start, endcharset-start); if (charset < 0) { /* Unrecognized charset, nothing will match here */ convert_putc(input, 0xfffd); /* unknown character */ } else { struct convert_rock *extract; table_switch(input, charset); /* choose decoder */ if (encoding[1] == 'q' || encoding[1] == 'Q') { extract = qp_init(1, input); } else { extract = b64_init(input); } /* convert */ p = encoding+3; convert_catn(extract, p, end - p); /* clean up */ basic_free(extract); } /* Prepare for the next iteration */ s = start = end+2; eatspace = 1; } /* Copy over the tail part of the input string */ if (*s) { table_switch(input, 0); /* US_ASCII */ convert_cat(stripnl, s); } /* just free these ones, the rest can be cleaned up by the sender */ basic_free(stripnl); basic_free(input); } /* * Decode MIME strings (per RFC 2047) in 's'. Returns a newly allocated * string, contining 's' in canonical searching form, which must be * free()d by the caller. */ EXPORTED char *charset_decode_mimeheader(const char *s, int flags) { struct convert_rock *tobuffer, *input; char *res; if (!s) return NULL; tobuffer = buffer_init(); input = uni_init(tobuffer); input = canon_init(flags, input); mimeheader_cat(input, s); res = buffer_cstring(tobuffer); convert_free(input); return res; } /* * Decode MIME strings (per RFC 2047) in 's'. Returns a newly allocated * string, containing the decoded string, which must be free()d by the * caller. */ EXPORTED char *charset_parse_mimeheader(const char *s) { struct convert_rock *tobuffer, *input; char *res; if (!s) return NULL; tobuffer = buffer_init(); input = uni_init(tobuffer); mimeheader_cat(input, s); res = buffer_cstring(tobuffer); convert_free(input); return res; } EXPORTED int charset_search_mimeheader(const char *substr, comp_pat *pat, const char *s, int flags) { struct convert_rock *input, *tosearch; int res; tosearch = search_init(substr, pat); input = uni_init(tosearch); input = canon_init(flags, input); mimeheader_cat(input, s); res = search_havematch(tosearch); convert_free(input); return res; } /* Compile a search pattern for later comparison. We just count * how long the string is, and how many times the first character * occurs. Later optimisation could reduce the max_start by * deeper analysis of the possible paths through the string, but * this is a good absolute maximum, and it just means a few more * bytes get allocated... */ EXPORTED comp_pat *charset_compilepat(const char *s) { struct comp_pat_s *pat = xzmalloc(sizeof(struct comp_pat_s)); const char *p = s; /* count occurances */ while (*p) { if (*p == *s) pat->max_start++; pat->patlen++; p++; } return (comp_pat *)pat; } /* * Free the compiled pattern 'pat' */ EXPORTED void charset_freepat(comp_pat *pat) { free((struct comp_pat_s *)pat); } /* * Search for the string 'substr', with compiled pattern 'pat' * in the string 's', with length 'len'. Return nonzero if match * * Uses the to_search target directly. Assumes 's' is already * in search normal form (i.e. from a cache file) */ EXPORTED int charset_searchstring(const char *substr, comp_pat *pat, const char *s, size_t len, int flags) { struct convert_rock *tosearch; struct convert_rock *input; int charset = charset_lookupname("utf-8"); int res; if (!substr[0]) return 1; /* zero length string always matches */ /* set up the search handler */ tosearch = search_init(substr, pat); /* and the input stream */ input = uni_init(tosearch); input = canon_init(flags, input); input = table_init(charset, input); /* feed the handler */ while (len-- > 0) { convert_putc(input, (unsigned char)*s++); if (search_havematch(tosearch)) break; /* shortcut if there's a match */ } /* copy the value */ res = search_havematch(tosearch); /* clean up */ convert_free(input); return res; } /* * Search for the string 'substr' in the next 'len' bytes of * 'msg_base'. * 'charset' and 'encoding' specify the character set and * content transfer encoding of the data, respectively. * Returns nonzero iff the string was found. */ EXPORTED int charset_searchfile(const char *substr, comp_pat *pat, const char *msg_base, size_t len, int charset, int encoding, int flags) { struct convert_rock *input, *tosearch; size_t i; int res; /* Initialize character set mapping */ if (charset < 0 || charset >= chartables_num_charsets) return 0; /* check for trivial search */ if (strlen(substr) == 0) return 1; /* set up the conversion path */ tosearch = search_init(substr, pat); input = uni_init(tosearch); input = canon_init(flags, input); input = table_init(charset, input); /* choose encoding extraction if needed */ switch (encoding) { case ENCODING_NONE: break; case ENCODING_QP: input = qp_init(0, input); break; case ENCODING_BASE64: input = b64_init(input); /* XXX have to have nl-mapping base64 in order to * properly count \n as 2 raw characters */ break; default: /* Don't know encoding--nothing can match */ convert_free(input); return 0; } /* implement the loop here so we can check on the search each time */ for (i = 0; i < len; i++) { convert_putc(input, msg_base[i]); if (search_havematch(tosearch)) break; } res = search_havematch(tosearch); /* copy before we free it */ convert_free(input); return res; } /* This is based on charset_searchfile above. */ EXPORTED int charset_extractitem(index_search_text_receiver_t receiver, void *rock, int uid, const char *msg_base, size_t len, int charset, int encoding, int flags, int rpart, int rcmd) { struct convert_rock *input, *tobuffer; struct buf *out; size_t i; /* Initialize character set mapping */ if (charset < 0 || charset >= chartables_num_charsets) return 0; /* set up the conversion path */ tobuffer = buffer_init(); input = uni_init(tobuffer); input = canon_init(flags, input); input = table_init(charset, input); switch (encoding) { case ENCODING_NONE: break; case ENCODING_QP: input = qp_init(0, input); break; case ENCODING_BASE64: input = b64_init(input); /* XXX have to have nl-mapping base64 in order to * properly count \n as 2 raw characters */ break; default: /* Don't know encoding--nothing can match */ convert_free(input); return 0; } /* point to the buffer for easy block sending */ out = (struct buf *)tobuffer->state; for (i = 0; i < len; i++) { convert_putc(input, msg_base[i]); /* process a block of output every so often */ if (buf_len(out) > 4096) { receiver(uid, rpart, rcmd, out->s, out->len, rock); buf_reset(out); } } if (out->len) { /* finish it */ receiver(uid, rpart, rcmd, out->s, out->len, rock); } convert_free(input); return 1; } EXPORTED int charset_extractfile(index_search_text_receiver_t receiver, void *rock, int uid, const char *msg_base, size_t len, int charset, int encoding, int flags) { return charset_extractitem(receiver, rock, uid, msg_base, len, charset, encoding, flags, SEARCHINDEX_PART_BODY, SEARCHINDEX_CMD_APPENDPART); } /* * Decode the MIME body part (per RFC 2045) of @len bytes located at * @msg_base having the content transfer @encoding. Returns a pointer * to decoded bytes. The number of decoded bytes is returned in * *@outlen. Depending on the encoding, a newly allocated buffer may be * written to *@decbuf, which should be free()d by the caller if it not * zero. Note that the return value may point to either @msg_base or * @decbuf, so @decbuf should not be free()d until the return value has * been used. */ EXPORTED const char *charset_decode_mimebody(const char *msg_base, size_t len, int encoding, char **decbuf, size_t *outlen) { struct convert_rock *input, *tobuffer; *decbuf = NULL; *outlen = 0; switch (encoding) { case ENCODING_NONE: *outlen = len; return msg_base; case ENCODING_QP: tobuffer = buffer_init(); input = qp_init(0, tobuffer); break; case ENCODING_BASE64: tobuffer = buffer_init(); input = b64_init(tobuffer); break; default: /* Don't know encoding--nothing can match */ return NULL; } convert_catn(input, msg_base, len); /* extract the string from the buffer */ { struct buf *buf = (struct buf *)tobuffer->state; *outlen = buf->len; *decbuf = buf_release(buf); } convert_free(input); if (!*decbuf) { /* didn't get a result - maybe blank input, don't return NULL */ *outlen = len; return msg_base; } return *decbuf; } /* * Base64 encode the MIME body part (per RFC 2045) of 'len' bytes located at * 'msg_base'. Encodes into 'retval' which must large enough to * accomodate the encoded data. Returns the number of encoded bytes in * 'outlen' and the number of encoded lines in 'outlines'. * * May be called with 'msg_base' as NULL to get the number of encoded * bytes for allocating 'retval' of the proper size. */ #define BASE64_MAX_LINE_LEN 72 static char base_64[] = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/"; EXPORTED char *charset_encode_mimebody(const char *msg_base, size_t len, char *retval, size_t *outlen, int *outlines) { const unsigned char *s; unsigned char s0, s1, s2; char *d; int b64_len, b64_lines, cnt; b64_len = ((len + 2) / 3) * 4; b64_lines = (b64_len + BASE64_MAX_LINE_LEN - 1) / BASE64_MAX_LINE_LEN; /* account for CRLF added to each line */ b64_len += 2 * b64_lines; if (outlen) *outlen = b64_len; if (outlines) *outlines = b64_lines; if (!msg_base) return NULL; for (s = (const unsigned char*) msg_base, d = retval, cnt = 0; len; s += 3, d += 4, cnt += 4) { /* process tuplets */ if (cnt == BASE64_MAX_LINE_LEN) { /* reset line len count, add CRLF */ cnt = 0; *d++ = '\r'; *d++ = '\n'; } s0 = s[0]; s1 = --len ? s[1] : 0; /* byte 1: high 6 bits (1) */ d[0] = base_64[s0 >> 2]; /* byte 2: low 2 bits (1), high 4 bits (2) */ d[1] = base_64[((s0 & 0x3) << 4) | ((s1 & 0xf0) >> 4)]; if (len) { s2 = --len ? s[2] : 0; /* byte 3: low 4 bits (2), high 2 bits (3) */ d[2] = base_64[((s1 & 0xf) << 2) | ((s2 & 0xc0) >> 6)]; } else { /* byte 3: pad */ d[2] = '='; } if (len) { --len; /* byte 4: low 6 bits (3) */ d[3] = base_64[s2 & 0x3f]; } else { /* byte 4: pad */ d[3] = '='; } } /* add final CRLF */ *d++ = '\r'; *d++ = '\n'; return (b64_len ? retval : NULL); } /* returns a buffer which the caller must free */ EXPORTED char *charset_encode_mimeheader(const char *header, size_t len) { struct buf buf = BUF_INITIALIZER; size_t n; int need_quote = 0; if (!header) return NULL; if (!len) len = strlen(header); for (n = 0; n < len; n++) { unsigned char this = header[n]; if (QPSAFECHAR[this] || this == ' ') continue; need_quote = 1; break; } if (need_quote) { buf_printf(&buf, "=?UTF-8?Q?"); for (n = 0; n < len; n++) { unsigned char this = header[n]; if (QPSAFECHAR[this]) { buf_putc(&buf, (char)this); } else { buf_printf(&buf, "=%02X", this); } } buf_printf(&buf, "?="); } else { buf_setmap(&buf, header, len); } return buf_release(&buf); } cyrus-imapd-2.5.10/lib/cyrusdb.c0000644000175000017500000003665213001236020013341 00000000000000/* * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include #include #include #include #include #include #include #include #include #include #include #include #include #include "cyrusdb.h" #include "util.h" #include "exitcodes.h" #include "libcyr_cfg.h" #include "xmalloc.h" #include "xstrlcpy.h" /* Note that some of these may be undefined symbols * if libcyrus was not built with support for them */ extern struct cyrusdb_backend cyrusdb_berkeley; extern struct cyrusdb_backend cyrusdb_berkeley_nosync; extern struct cyrusdb_backend cyrusdb_berkeley_hash; extern struct cyrusdb_backend cyrusdb_berkeley_hash_nosync; extern struct cyrusdb_backend cyrusdb_flat; extern struct cyrusdb_backend cyrusdb_skiplist; extern struct cyrusdb_backend cyrusdb_quotalegacy; extern struct cyrusdb_backend cyrusdb_sql; extern struct cyrusdb_backend cyrusdb_twoskip; static struct cyrusdb_backend *_backends[] = { #ifdef HAVE_BDB &cyrusdb_berkeley, &cyrusdb_berkeley_nosync, &cyrusdb_berkeley_hash, &cyrusdb_berkeley_hash_nosync, #endif &cyrusdb_flat, &cyrusdb_skiplist, &cyrusdb_quotalegacy, #if defined HAVE_MYSQL || defined HAVE_PGSQL || defined HAVE_SQLITE &cyrusdb_sql, #endif &cyrusdb_twoskip, NULL }; #define DEFAULT_BACKEND "twoskip" struct db { struct dbengine *engine; struct cyrusdb_backend *backend; }; static struct cyrusdb_backend *cyrusdb_fromname(const char *name) { int i; struct cyrusdb_backend *db = NULL; for (i = 0; _backends[i]; i++) { if (!strcmp(_backends[i]->name, name)) { db = _backends[i]; break; } } if (!db) { char errbuf[1024]; snprintf(errbuf, sizeof(errbuf), "cyrusdb backend %s not supported", name); fatal(errbuf, EC_CONFIG); } return db; } EXPORTED int cyrusdb_open(const char *backend, const char *fname, int flags, struct db **ret) { const char *realname; struct db *db = xzmalloc(sizeof(struct db)); int r; if (!backend) backend = DEFAULT_BACKEND; /* not used yet, later */ db->backend = cyrusdb_fromname(backend); /* This whole thing is a fricking critical section. We don't have the API * in place for a safe rename of a locked database, so the choices are * basically: * a) convert each DB layer to support locked database renames while still * in the transaction. Best, but lots of work. * b) rename and hope... unreliable * c) global lock around this block of code. Safest and least efficient. */ /* check if it opens normally. Horray */ r = db->backend->open(fname, flags, &db->engine); if (r == CYRUSDB_NOTFOUND) goto done; /* no open flags */ if (!r) goto done; /* magic time - we need to work out if the file was created by a different * backend and convert if possible */ realname = cyrusdb_detect(fname); if (!realname) { syslog(LOG_ERR, "DBERROR: failed to detect DB type for %s (backend %s) (r was %d)", fname, backend, r); /* r is still set */ goto done; } /* different type */ if (strcmp(realname, backend)) { if (flags & CYRUSDB_CONVERT) { r = cyrusdb_convert(fname, fname, realname, backend); if (r) { syslog(LOG_ERR, "DBERROR: failed to convert %s from %s to %s, maybe someone beat us", fname, realname, backend); } else { syslog(LOG_NOTICE, "cyrusdb: converted %s from %s to %s", fname, realname, backend); } } else { syslog(LOG_NOTICE, "cyrusdb: opening %s with backend %s (requested %s)", fname, realname, backend); db->backend = cyrusdb_fromname(realname); } } r = db->backend->open(fname, flags, &db->engine); done: if (r) free(db); else *ret = db; return r; } EXPORTED int cyrusdb_close(struct db *db) { int r = db->backend->close(db->engine); free(db); return r; } EXPORTED int cyrusdb_fetch(struct db *db, const char *key, size_t keylen, const char **data, size_t *datalen, struct txn **mytid) { return db->backend->fetch(db->engine, key, keylen, data, datalen, mytid); } EXPORTED int cyrusdb_fetchlock(struct db *db, const char *key, size_t keylen, const char **data, size_t *datalen, struct txn **mytid) { return db->backend->fetchlock(db->engine, key, keylen, data, datalen, mytid); } EXPORTED int cyrusdb_fetchnext(struct db *db, const char *key, size_t keylen, const char **found, size_t *foundlen, const char **data, size_t *datalen, struct txn **mytid) { return db->backend->fetchnext(db->engine, key, keylen, found, foundlen, data, datalen, mytid); } EXPORTED int cyrusdb_foreach(struct db *db, const char *prefix, size_t prefixlen, foreach_p *p, foreach_cb *cb, void *rock, struct txn **tid) { return db->backend->foreach(db->engine, prefix, prefixlen, p, cb, rock, tid); } EXPORTED int cyrusdb_create(struct db *db, const char *key, size_t keylen, const char *data, size_t datalen, struct txn **tid) { return db->backend->create(db->engine, key, keylen, data, datalen, tid); } EXPORTED int cyrusdb_store(struct db *db, const char *key, size_t keylen, const char *data, size_t datalen, struct txn **tid) { return db->backend->store(db->engine, key, keylen, data, datalen, tid); } EXPORTED int cyrusdb_delete(struct db *db, const char *key, size_t keylen, struct txn **tid, int force) { return db->backend->delete(db->engine, key, keylen, tid, force); } EXPORTED int cyrusdb_commit(struct db *db, struct txn *tid) { return db->backend->commit(db->engine, tid); } EXPORTED int cyrusdb_abort(struct db *db, struct txn *tid) { return db->backend->abort(db->engine, tid); } EXPORTED int cyrusdb_dump(struct db *db, int detail) { if (!db->backend->dump) return 0; return db->backend->dump(db->engine, detail); } EXPORTED int cyrusdb_consistent(struct db *db) { if (!db->backend->consistent) return 0; return db->backend->consistent(db->engine); } EXPORTED int cyrusdb_repack(struct db *db) { if (!db->backend->repack) return 0; return db->backend->repack(db->engine); } EXPORTED int cyrusdb_compar(struct db *db, const char *a, int alen, const char *b, int blen) { return db->backend->compar(db->engine, a, alen, b, blen); } /**********************************************/ EXPORTED void cyrusdb_init(void) { int i, r; char dbdir[1024]; const char *confdir = libcyrus_config_getstring(CYRUSOPT_CONFIG_DIR); int initflags = libcyrus_config_getint(CYRUSOPT_DB_INIT_FLAGS); strcpy(dbdir, confdir); strcat(dbdir, FNAME_DBDIR); for(i=0; _backends[i]; i++) { r = (_backends[i])->init(dbdir, initflags); if(r) { syslog(LOG_ERR, "DBERROR: init() on %s", _backends[i]->name); } } } EXPORTED void cyrusdb_done(void) { int i; for(i=0; _backends[i]; i++) { (_backends[i])->done(); } } HIDDEN int cyrusdb_copyfile(const char *srcname, const char *dstname) { return cyrus_copyfile(srcname, dstname, COPYFILE_NOLINK); } struct db_rock { struct db *db; struct txn **tid; }; static int delete_cb(void *rock, const char *key, size_t keylen, const char *data __attribute__((unused)), size_t datalen __attribute__((unused))) { struct db_rock *cr = (struct db_rock *)rock; return cyrusdb_delete(cr->db, key, keylen, cr->tid, 1); } static int print_cb(void *rock, const char *key, size_t keylen, const char *data, size_t datalen) { FILE *f = (FILE *)rock; /* XXX: improve binary safety */ fprintf(f, "%.*s\t%.*s\n", (int)keylen, key, (int)datalen, data); return 0; } int cyrusdb_dumpfile(struct db *db, const char *prefix, size_t prefixlen, FILE *f, struct txn **tid) { return cyrusdb_foreach(db, prefix, prefixlen, NULL, print_cb, f, tid); } int cyrusdb_truncate(struct db *db, struct txn **tid) { struct db_rock tr; tr.db = db; tr.tid = tid; return cyrusdb_foreach(db, "", 0, NULL, delete_cb, &tr, tid); } int cyrusdb_undumpfile(struct db *db, FILE *f, struct txn **tid) { struct buf line = BUF_INITIALIZER; const char *tab; const char *str; int r = 0; while (buf_getline(&line, f)) { /* skip blank lines */ if (!line.len) continue; str = buf_cstring(&line); /* skip comments */ if (str[0] == '#') continue; tab = strchr(str, '\t'); /* deletion (no value) */ if (!tab) { r = cyrusdb_delete(db, str, line.len, tid, 1); if (r) goto out; } /* store */ else { unsigned klen = (tab - str); unsigned vlen = line.len - klen - 1; /* TAB */ r = cyrusdb_store(db, str, klen, tab + 1, vlen, tid); if (r) goto out; } } out: buf_free(&line); return r; } static int converter_cb(void *rock, const char *key, size_t keylen, const char *data, size_t datalen) { struct db_rock *cr = (struct db_rock *)rock; return cyrusdb_store(cr->db, key, keylen, data, datalen, cr->tid); } /* convert (just copy every record) from one database to another in possibly a different format. It's up to the surrounding code to copy the new database over the original if it wants to */ EXPORTED int cyrusdb_convert(const char *fromfname, const char *tofname, const char *frombackend, const char *tobackend) { char *newfname = NULL; struct db *fromdb = NULL; struct db *todb = NULL; struct db_rock cr; struct txn *fromtid = NULL; struct txn *totid = NULL; int r; /* open source database */ r = cyrusdb_open(frombackend, fromfname, 0, &fromdb); if (r) goto err; /* use a bogus fetch to lock source DB before touching the destination */ r = cyrusdb_fetch(fromdb, "_", 1, NULL, NULL, &fromtid); if (r == CYRUSDB_NOTFOUND) r = 0; if (r) goto err; /* same file? Create with a new name */ if (!strcmp(tofname, fromfname)) tofname = newfname = strconcat(fromfname, ".NEW", NULL); /* remove any rubbish lying around */ unlink(tofname); r = cyrusdb_open(tobackend, tofname, CYRUSDB_CREATE, &todb); if (r) goto err; /* set up the copy rock */ cr.db = todb; cr.tid = &totid; /* copy each record to the destination DB */ cyrusdb_foreach(fromdb, "", 0, NULL, converter_cb, &cr, &fromtid); /* commit destination transaction */ if (totid) cyrusdb_commit(todb, totid); r = cyrusdb_close(todb); totid = NULL; todb = NULL; if (r) goto err; /* created a new filename - so it's a replace-in-place */ if (newfname) { r = rename(newfname, fromfname); if (r) goto err; } /* and close the source database - nothing should have * written here, so an abort is fine */ if (fromtid) cyrusdb_abort(fromdb, fromtid); cyrusdb_close(fromdb); free(newfname); return 0; err: if (totid) cyrusdb_abort(todb, totid); if (todb) cyrusdb_close(todb); if (fromtid) cyrusdb_abort(fromdb, fromtid); if (fromdb) cyrusdb_close(fromdb); unlink(tofname); free(newfname); return r; } EXPORTED const char *cyrusdb_detect(const char *fname) { FILE *f; char buf[16]; int n; uint32_t bdb_magic; f = fopen(fname, "r"); if (!f) return NULL; /* empty file? */ n = fread(buf, 16, 1, f); fclose(f); if (n != 1) return NULL; /* only compare first 16 bytes, that's OK */ if (!strncmp(buf, "\241\002\213\015skiplist file\0\0\0", 16)) return "skiplist"; if (!strncmp(buf, "\241\002\213\015twoskip file\0\0\0\0", 16)) return "twoskip"; bdb_magic = *(uint32_t *)(buf+12); if (bdb_magic == 0x053162) /* BDB BTREE MAGIC */ return "berkeley"; if (bdb_magic == 0x061561) /* BDB HASH MAGIC */ return "berkeley-hash"; /* unable to detect SQLite databases or flat files explicitly here */ return NULL; } EXPORTED int cyrusdb_sync(const char *backend) { struct cyrusdb_backend *db = cyrusdb_fromname(backend); return db->sync(); } EXPORTED cyrusdb_archiver *cyrusdb_getarchiver(const char *backend) { struct cyrusdb_backend *db = cyrusdb_fromname(backend); return db->archive; /* the function used for archiving */ } EXPORTED int cyrusdb_canfetchnext(const char *backend) { struct cyrusdb_backend *db = cyrusdb_fromname(backend); return db->fetchnext ? 1 : 0; } /* caller is responsible for calling strarray_free() */ EXPORTED strarray_t *cyrusdb_backends(void) { strarray_t *ret = strarray_new(); int i; for (i = 0; _backends[i]; i++) { strarray_add(ret, _backends[i]->name); } return ret; } /* generic backend implementations */ HIDDEN int cyrusdb_generic_init(const char *dbdir __attribute__((unused)), int myflags __attribute__((unused))) { return 0; } HIDDEN int cyrusdb_generic_done(void) { return 0; } HIDDEN int cyrusdb_generic_sync(void) { return 0; } HIDDEN int cyrusdb_generic_archive(const strarray_t *fnames, const char *dirname) { char dstname[1024], *dp; int length, rest; int i; int r; strlcpy(dstname, dirname, sizeof(dstname)); length = strlen(dstname); dp = dstname + length; rest = sizeof(dstname) - length; /* archive those files specified by the app */ for (i = 0; i < fnames->count; i++) { const char *fname = strarray_nth(fnames, i); syslog(LOG_DEBUG, "archiving database file: %s", fname); strlcpy(dp, strrchr(fname, '/'), rest); r = cyrusdb_copyfile(fname, dstname); if (r) { syslog(LOG_ERR, "DBERROR: error archiving database file: %s", fname); return CYRUSDB_IOERROR; } } return 0; } HIDDEN int cyrusdb_generic_noarchive(const strarray_t *fnames __attribute__((unused)), const char *dirname __attribute__((unused))) { return 0; } cyrus-imapd-2.5.10/lib/command.h0000644000175000017500000000411113001236020013272 00000000000000/* command.h -- utility functions to run a command * * Copyright (c) 1994-2012 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. * * Author: Chris Newman * Start Date: 4/6/93 */ #ifndef INCLUDED_COMMAND_H #define INCLUDED_COMMAND_H #include #include #include extern int run_command(const char *argv0, ...); #endif /* INCLUDED_COMMAND_H */ cyrus-imapd-2.5.10/lib/gmtoff_gmtime.c0000644000175000017500000000512013001236020014474 00000000000000/* gmtoff_tm.c - Get offset from GMT by calling gmtime and subtracting * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include /* * Returns the GMT offset of the struct tm 'tm', obtained from 'time'. */ EXPORTED int gmtoff_of(struct tm *tm, time_t time) { struct tm local, gmt; struct tm *gtm; long offset; local = *tm; gtm = gmtime(&time); gmt = *gtm; /* Assume we are never more than 24 hours away. */ offset = local.tm_yday - gmt.tm_yday; if (offset > 1) { offset = -24; } else if (offset < -1) { offset = 24; } else { offset *= 24; } /* Scale in the hours and minutes; ignore seconds. */ offset += local.tm_hour - gmt.tm_hour; offset *= 60; offset += local.tm_min - gmt.tm_min; /* Restore the data in the struct 'tm' points to */ *tm = local; return offset * 60; } cyrus-imapd-2.5.10/lib/xmalloc.h0000644000175000017500000000516413001236020013324 00000000000000/* xmalloc.h -- Allocation package that calls fatal() when out of memory * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #ifndef INCLUDED_XMALLOC_H #define INCLUDED_XMALLOC_H /* for size_t */ #include /* for free() */ #include extern void *xmalloc (unsigned size); extern void *xzmalloc (unsigned size); extern void *xcalloc (unsigned nmemb, unsigned size); extern void *xrealloc (void *ptr, unsigned size); extern char *xstrdup (const char *str); extern char *xstrdupnull (const char *str); extern char *xstrdupsafe (const char *str); extern char *xstrndup (const char *str, unsigned len); extern void *xmemdup (const void *ptr, unsigned size); /* Functions using xmalloc.h must provide a function called fatal() conforming to the following: */ extern void fatal(const char *fatal_message, int fatal_code); /* __attribute__ ((noreturn));*/ #endif /* INCLUDED_XMALLOC_H */ cyrus-imapd-2.5.10/lib/nonblock_fcntl.c0000644000175000017500000000523013001236020014645 00000000000000/* nonblock_fcntl.c -- Set nonblocking mode using fcntl() * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include #include #include #include #include "xmalloc.h" #include "exitcodes.h" #include "nonblock.h" #ifndef FNDELAY #define FNDELAY O_NDELAY #endif #ifdef O_NONBLOCK #define NON_BLOCKING_MODE O_NONBLOCK #else #define NON_BLOCKING_MODE FNDELAY #endif EXPORTED const char *nonblock_method_desc = "fcntl"; /* * Modifies the non-blocking mode on the file descriptor 'fd'. If * 'mode' is nonzero, sets non-blocking mode, if 'mode' is zero * clears non-blocking mode. */ EXPORTED void nonblock(int fd, int mode) { int flags; flags = fcntl(fd, F_GETFL, 0); if (flags < 0) fatal("Internal error: fcntl F_GETFL failed", EC_IOERR); if (mode) { flags |= NON_BLOCKING_MODE; } else { flags &= ~NON_BLOCKING_MODE; } (void)fcntl(fd, F_SETFL, flags); } cyrus-imapd-2.5.10/lib/imparse.h0000644000175000017500000000431412772415051013342 00000000000000/* imparse.h -- IMxP client-side parsing routines * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #ifndef INCLUDED_IMPARSE_H #define INCLUDED_IMPARSE_H extern int imparse_word (char **s, char **retval); extern int imparse_astring (char **s, char **retval); extern int imparse_isnatom (const char *s, int len); extern int imparse_isatom (const char *s); extern int imparse_issequence (const char *s); extern int imparse_isnumber (const char *s); #endif /* INCLUDED_IMPARSE_H */ cyrus-imapd-2.5.10/lib/acl.h0000644000175000017500000001157313001236020012425 00000000000000/* acl.h -- definitions for access control lists * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. * * Author: Chris Newman * Start Date: 6/28/93 */ #ifndef INCLUDED_ACL_H #define INCLUDED_ACL_H #include "auth.h" /* max length of an acl string */ #define ACL_MAXSTR 32 /* ACL bits */ #define ACL_LOOKUP 0x000001L #define ACL_READ 0x000002L #define ACL_SETSEEN 0x000004L #define ACL_WRITE 0x000008L #define ACL_INSERT 0x000010L #define ACL_POST 0x000020L #define ACL_CREATE 0x000040L #define ACL_DELETEMBOX 0x000080L #define ACL_DELETEMSG 0x000100L #define ACL_EXPUNGE 0x000200L #define ACL_ADMIN 0x000400L #define ACL_ANNOTATEMSG 0x000800L #define ACL_USER1 0x001000L #define ACL_USER2 0x002000L #define ACL_USER3 0x004000L #define ACL_USER4 0x008000L #define ACL_USER5 0x010000L #define ACL_USER6 0x020000L #define ACL_USER7 0x040000L #define ACL_USER8 0x080000L #define ACL_USER9 0x100000L #define ACL_USER0 0x200000L /* ALL: all non-user ACLs */ #define ACL_ALL (ACL_LOOKUP|ACL_READ|ACL_SETSEEN|ACL_WRITE\ |ACL_INSERT|ACL_POST|ACL_CREATE|ACL_DELETEMBOX\ |ACL_DELETEMSG|ACL_EXPUNGE|ACL_ADMIN\ |ACL_ANNOTATEMSG) /* FULL: ALL ACLs including user ACLs */ #define ACL_FULL (ACL_USER1|ACL_USER2|ACL_USER3|ACL_USER4|ACL_USER5\ |ACL_USER6|ACL_USER7|ACL_USER8|ACL_USER9|ACL_USER0\ |ACL_ALL) /* READ-WRITE: removed from regular ACL if you EXAMINE a mailbox, so that nothing accidentally tries to write */ #define ACL_READ_WRITE (ACL_SETSEEN|ACL_WRITE|ACL_INSERT\ |ACL_DELETEMSG|ACL_EXPUNGE|ACL_ANNOTATEMSG) #define ACL_MODE_SET 0 #define ACL_MODE_ADD 1 #define ACL_MODE_REMOVE 2 typedef int cyrus_acl_canonproc_t(void *rock, const char *identifier, int rights); /* convert a string to an acl bit vector */ extern int cyrus_acl_strtomask(const char *str); /* cyrus_acl_masktostr(acl, dst) * convert an acl bit vector to a string * dst must have room for 32 characters (only 20 used currently) * returns dst */ extern char *cyrus_acl_masktostr(int acl, char *str); /* cyrus_acl_myrights(acl) * Calculate the set of rights the user in 'auth_state' has in the ACL 'acl'. * 'acl' must be writable, but is restored to its original condition. */ extern int cyrus_acl_myrights(struct auth_state *auth_state, const char *acl); /* cyrus_acl_set(acl, identifier, mode, access, canonproc, canonrock) Modify the * ACL pointed to by 'acl' to modify the rights granted to * 'identifier' as specified by 'mode' and the set specified in the * mask 'access'. 'mode' is one of ACL_MODE_SET, ACL_MODE_ADD, or * ACL_MODE_REMOVE. The pointer pointed to by 'acl' must have been * obtained from malloc(). returns -1 on error, 0 on success */ extern int cyrus_acl_set(char **acl, const char *identifier, int mode, int access, cyrus_acl_canonproc_t *canonproc, void *canonrock); /* cyrus_acl_remove(acl, identifier, canonproc, canonrock) * Remove any entry for 'identifier' in the ACL pointed to by 'acl'. * The pointer pointed to by 'acl' must have been obtained from malloc(). * returns -1 on error, 0 on success */ extern int cyrus_acl_remove(char **acl, const char *identifier, cyrus_acl_canonproc_t *canonproc, void *canonrock); #endif /* INCLUDED_ACL_H */ cyrus-imapd-2.5.10/lib/util.h0000644000175000017500000003005413001236020012636 00000000000000/* util.h -- general utility functions * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. * * Author: Chris Newman * Start Date: 4/6/93 */ #ifndef INCLUDED_UTIL_H #define INCLUDED_UTIL_H #include #include #include #include #include #include #ifdef ENABLE_REGEX # ifdef HAVE_PCREPOSIX_H # include # include # else /* !HAVE_PCREPOSIX_H */ # ifdef HAVE_RXPOSIX_H # include # else /* !HAVE_RXPOSIX_H */ # include # endif /* HAVE_RXPOSIX_H */ # endif /* HAVE_PCREPOSIX_H */ #endif /* ENABLE_REGEX */ #ifndef __GNUC__ typedef int (*__compar_fn_t)(const void *, const void *); #endif #define BIT32_MAX 4294967295U #if UINT_MAX == BIT32_MAX typedef unsigned int bit32; #elif ULONG_MAX == BIT32_MAX typedef unsigned long bit32; #elif USHRT_MAX == BIT32_MAX typedef unsigned short bit32; #else #error dont know what to use for bit32 #endif typedef int compar_t(const void *a, const void *b); typedef unsigned long long int bit64; typedef unsigned long long int modseq_t; #define MODSEQ_FMT "%llu" #define atomodseq_t(s) strtoull(s, NULL, 10) #define Uisalnum(c) isalnum((int)((unsigned char)(c))) #define Uisalpha(c) isalpha((int)((unsigned char)(c))) #define Uisascii(c) isascii((int)((unsigned char)(c))) #define Uiscntrl(c) iscntrl((int)((unsigned char)(c))) #define Uisdigit(c) isdigit((int)((unsigned char)(c))) #define Uislower(c) islower((int)((unsigned char)(c))) #define Uisspace(c) isspace((int)((unsigned char)(c))) #define Uisupper(c) isupper((int)((unsigned char)(c))) #define Uisxdigit(c) isxdigit((int)((unsigned char)(c))) extern const unsigned char convert_to_lowercase[256]; extern const unsigned char convert_to_uppercase[256]; #ifndef TOUPPER #define TOUPPER(c) (convert_to_uppercase[(unsigned char)(c)]) #endif #ifndef TOLOWER #define TOLOWER(c) (convert_to_lowercase[(unsigned char)(c)]) #endif #ifndef MAX #define MAX(x, y) ((x) > (y) ? (x) : (y)) #endif #ifndef MIN #define MIN(x, y) ((x) < (y) ? (x) : (y)) #endif /* Some BSDs don't print "NULL" for a NULL pointer string. */ #ifndef IS_NULL #define IS_NULL(s) ((s) == NULL ? "(NULL)" : (s)) #endif /* Calculate the number of entries in a vector */ #define VECTOR_SIZE(vector) (sizeof(vector)/sizeof(vector[0])) typedef struct keyvalue { char *key, *value; } keyvalue; /* convert string to all lower case */ extern char *lcase (char *str); /* convert string to all upper case */ extern char *ucase (char *str); /* clean up control characters in a string while copying it * returns pointer to a static buffer containing the cleaned-up version */ extern char *beautify_string (const char *src); /* Same semantics as strcmp() but gracefully handles * either or both it's arguments being NULL */ int strcmpsafe(const char *a, const char *b); /* Same semantics as strcasecmp() but gracefully handles * either or both it's arguments being NULL */ int strcasecmpsafe(const char *a, const char *b); /* ditto strncmp */ int strncmpsafe(const char *a, const char *b, size_t n); /* NULL isn't "" */ int strcmpnull(const char *a, const char *b); /* do a binary search in a keyvalue array * nelem is the number of keyvalue elements in the kv array * cmpf is the comparison function (strcmp, stricmp, etc). * returns NULL if not found, or key/value pair if found. */ extern keyvalue *kv_bsearch (const char *key, keyvalue *kv, int nelem, int (*cmpf)(const char *s1, const char *s2)); /* Examine the name of a file, and return a single character * (as an int) that can be used as the name of a hash * directory. Caller is responsible for skipping any prefix * of the name. */ extern int dir_hash_c(const char *name, int full); /* * Like dir_hash_c() but builds the result as a single-byte * C string in the provided buffer, and returns the buffer, * which is sometimes more convenient. */ extern char *dir_hash_b(const char *name, int full, char buf[2]); /* * create an [unlinked] temporary file and return the file descriptor. */ extern int create_tempfile(const char *path); /* Close a network filedescriptor the "safe" way */ extern int cyrus_close_sock(int fd); /* Reset stdin/stdout/stderr */ extern void cyrus_reset_stdio(void); /* Create all parent directories for the given path, * up to but not including the basename. */ extern int cyrus_mkdir(const char *path, mode_t mode); enum { COPYFILE_NOLINK = (1<<0), COPYFILE_MKDIR = (1<<1), COPYFILE_RENAME = (1<<2) }; extern int cyrus_copyfile(const char *from, const char *to, int flags); enum { BEFORE_SETUID, AFTER_SETUID, BEFORE_BIND, AFTER_BIND, AFTER_FORK }; extern int set_caps(int stage, int is_master); extern int become_cyrus(int is_master); /* Some systems have very inefficient implementations of isdigit, * and we use it in a lot of inner loops */ #define cyrus_isdigit(x) ((x) >= '0' && (x) <= '9') int parseint32(const char *p, const char **ptr, int32_t *res); int parseuint32(const char *p, const char **ptr, uint32_t *res); int parsenum(const char *p, const char **ptr, int maxlen, bit64 *res); int parsehex(const char *p, const char **ptr, int maxlen, bit64 *res); /* Timing related funcs/vars */ extern void cmdtime_settimer(int enable); extern void cmdtime_starttimer(void); extern void cmdtime_endtimer(double * cmdtime, double * nettime); extern void cmdtime_netstart(void); extern void cmdtime_netend(void); extern double timeval_get_double(const struct timeval *tv); extern void timeval_set_double(struct timeval *tv, double d); extern void timeval_add_double(struct timeval *tv, double delta); extern double timesub(const struct timeval *start, const struct timeval *end); extern clock_t sclock(void); #define BUF_MMAP (1<<1) struct buf { char *s; size_t len; size_t alloc; unsigned flags; }; #define BUF_INITIALIZER { NULL, 0, 0, 0 } #define buf_ensure(b, n) do { if ((b)->alloc < (b)->len + (n)) _buf_ensure((b), (n)); } while (0) #define buf_putc(b, c) do { buf_ensure((b), 1); (b)->s[(b)->len++] = (c); } while (0) void _buf_ensure(struct buf *buf, size_t len); const char *buf_cstring(struct buf *buf); const char *buf_cstringnull(struct buf *buf); char *buf_release(struct buf *buf); char *buf_newcstring(struct buf *buf); char *buf_releasenull(struct buf *buf); void buf_getmap(struct buf *buf, const char **base, size_t *len); int buf_getline(struct buf *buf, FILE *fp); size_t buf_len(const struct buf *buf); const char *buf_base(const struct buf *buf); void buf_reset(struct buf *buf); void buf_truncate(struct buf *buf, ssize_t len); void buf_setcstr(struct buf *buf, const char *str); void buf_setmap(struct buf *buf, const char *base, size_t len); void buf_copy(struct buf *dst, const struct buf *src); void buf_append(struct buf *dst, const struct buf *src); void buf_appendcstr(struct buf *buf, const char *str); void buf_appendbit32(struct buf *buf, bit32 num); void buf_appendmap(struct buf *buf, const char *base, size_t len); void buf_cowappendmap(struct buf *buf, const char *base, unsigned int len); void buf_cowappendfree(struct buf *buf, char *base, unsigned int len); void buf_insert(struct buf *dst, unsigned int off, const struct buf *src); void buf_insertcstr(struct buf *buf, unsigned int off, const char *str); void buf_insertmap(struct buf *buf, unsigned int off, const char *base, int len); void buf_vprintf(struct buf *buf, const char *fmt, va_list args); void buf_printf(struct buf *buf, const char *fmt, ...) __attribute__((format(printf,2,3))); int buf_replace_all(struct buf *buf, const char *match, const char *replace); int buf_replace_char(struct buf *buf, char match, char replace); #ifdef ENABLE_REGEX int buf_replace_all_re(struct buf *buf, const regex_t *, const char *replace); int buf_replace_one_re(struct buf *buf, const regex_t *, const char *replace); #endif void buf_remove(struct buf *buf, unsigned int off, unsigned int len); int buf_cmp(const struct buf *, const struct buf *); int buf_findchar(const struct buf *, unsigned int off, int c); int buf_findline(const struct buf *buf, const char *line); void buf_init(struct buf *buf); void buf_init_ro(struct buf *buf, const char *base, size_t len); void buf_initm(struct buf *buf, char *base, int len); void buf_init_ro_cstr(struct buf *buf, const char *str); void buf_init_mmap(struct buf *buf, int onceonly, int fd, const char *fname, size_t size, const char *mboxname); void buf_free(struct buf *buf); void buf_move(struct buf *dst, struct buf *src); /* * Given a list of strings, terminated by (char *)NULL, * return a newly allocated string containing the * concatention of all the argument strings. The * caller must free the returned string using free(). * * This API idea based on glib's g_strconcat() which * is really quite amazingly convenient. */ char *strconcat(const char *s1, ...); #define BH_LOWER (0) #define BH_UPPER (1<<8) #define _BH_SEP (1<<9) #define BH_SEPARATOR(c) (_BH_SEP|((c)&0x7f)) #define _BH_GETSEP(flags) (flags & _BH_SEP ? (char)(flags & 0x7f) : '\0') int bin_to_hex(const void *bin, size_t binlen, char *hex, int flags); int hex_to_bin(const char *hex, size_t hexlen, void *bin); /* use getpassphrase on machines which support it */ #ifdef HAVE_GETPASSPHRASE #define cyrus_getpass getpassphrase #else #define cyrus_getpass getpass #endif #ifdef HAVE_ZLIB enum { DEFLATE_RAW, DEFLATE_GZIP, DEFLATE_ZLIB }; int buf_inflate(struct buf *buf, int scheme); int buf_deflate(struct buf *buf, int compLevel, int scheme); #endif /* A wrapper for close() which handles the fd=-1 case cleanly. * The argument may have side effects and must be an lvalue */ #define xclose(fd) \ do { \ int *_fdp = &(fd); \ if (*_fdp >= 0) { \ close(*_fdp); \ *_fdp = -1; \ } \ } while(0) /* A wrapper for strncpy() which ensures that the destination * string is always NUL-terminated. Yes, I know we have an * implementation of the BSD strlcpy() which has this semantic, * but that isn't a highly optimised libc or compiler provided * function like strncpy(), and we can trivially and eficiently * add the NUL termination semantic on top of strncpy(). */ #define xstrncpy(d, s, n) \ do { \ char *_d = (d); \ size_t _n = (n); \ strncpy(_d, (s), _n); \ _d[_n-1] = '\0'; \ } while(0) /* simple function to request a file gets pre-loaded by the OS */ int warmup_file(const char *filename, off_t offset, off_t length); #endif /* INCLUDED_UTIL_H */ cyrus-imapd-2.5.10/lib/cyrusdb_sql.c0000644000175000017500000005575313001236020014223 00000000000000/* cyrusdb_sql: SQL db backends * * Copyright (c) 1998-2004 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any other legal * details, please contact * Office of Technology Transfer * Carnegie Mellon University * 5000 Forbes Avenue * Pittsburgh, PA 15213-3890 * (412) 268-4387, fax: (412) 268-7395 * tech-transfer@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include #include #include #include #include #include "assert.h" #include "bsearch.h" #include "cyrusdb.h" #include "exitcodes.h" #include "libcyr_cfg.h" #include "xmalloc.h" #include "util.h" extern void fatal(const char *, int); typedef int exec_cb(void *rock, const char *key, size_t keylen, const char *data, size_t datalen); typedef struct sql_engine { const char *name; const char *binary_type; void *(*sql_open)(char *host, char *port, int usessl, const char *user, const char *password, const char *database); char *(*sql_escape)(void *conn, char **to, const char *from, size_t fromlen); int (*sql_begin_txn)(void *conn); int (*sql_commit_txn)(void *conn); int (*sql_rollback_txn)(void *conn); int (*sql_exec)(void *conn, const char *cmd, exec_cb *cb, void *rock); void (*sql_close)(void *conn); } sql_engine_t; struct dbengine { void *conn; /* connection to database */ char *table; /* table that we are operating on */ char *esc_key; /* allocated buffer for escaped key */ char *esc_data; /* allocated buffer for escaped data */ char *data; /* allocated buffer for fetched data */ }; struct txn { char *lastkey; /* allocated buffer for last SELECTed key */ size_t keylen; }; static int dbinit = 0; static const sql_engine_t *dbengine = NULL; #ifdef HAVE_MYSQL #include static void *_mysql_open(char *host, char *port, int usessl, const char *user, const char *password, const char *database) { MYSQL *mysql; if (!(mysql = mysql_init(NULL))) { syslog(LOG_ERR, "DBERROR: SQL backend could not execute mysql_init()"); return NULL; } return mysql_real_connect(mysql, host, user, password, database, port ? strtoul(port, NULL, 10) : 0, NULL, usessl ? CLIENT_SSL : 0); } static char *_mysql_escape(void *conn, char **to, const char *from, size_t fromlen) { size_t tolen; *to = xrealloc(*to, 2 * fromlen + 1); /* +1 for NUL */ tolen = mysql_real_escape_string(conn, *to, from, fromlen); (void)tolen; return *to; } static int _mysql_exec(void *conn, const char *cmd, exec_cb *cb, void *rock) { MYSQL_RES *result; MYSQL_ROW row; int len, r = 0; syslog(LOG_DEBUG, "executing SQL cmd: %s", cmd); len = strlen(cmd); /* mysql_real_query() doesn't want a terminating ';' */ if (cmd[len-1] == ';') len--; /* run the query */ if ((mysql_real_query(conn, cmd, len) < 0) || *mysql_error(conn)) { syslog(LOG_ERR, "DBERROR: SQL query failed: %s", mysql_error(conn)); return CYRUSDB_INTERNAL; } /* see if we should expect some results */ if (!mysql_field_count(conn)) { /* no results (BEGIN, COMMIT, ROLLBACK, CREATE, INSERT, UPDATE, DELETE) */ syslog(LOG_DEBUG, "no results from SQL cmd"); return 0; } /* get the results */ result = mysql_store_result(conn); /* process the results */ while (!r && (row = mysql_fetch_row(result))) { unsigned long *length = mysql_fetch_lengths(result); r = cb(rock, row[0], length[0], row[1], length[1]); } /* free result */ mysql_free_result(result); return r; } static int _mysql_begin_txn(void *conn) { return _mysql_exec(conn, #if MYSQL_VERSION_ID >= 40011 "START TRANSACTION", #else "BEGIN", #endif NULL, NULL); } static int _mysql_commit_txn(void *conn) { return _mysql_exec(conn, "COMMIT", NULL, NULL); } static int _mysql_rollback_txn(void *conn) { return _mysql_exec(conn, "ROLLBACK", NULL, NULL); } static void _mysql_close(void *conn) { mysql_close(conn); } #endif /* HAVE_MYSQL */ #ifdef HAVE_PGSQL #include #define sql_max(a, b) ((a) > (b) ? (a) : (b)) #define sql_len(input) ((input) ? strlen(input) : 0) #define sql_exists(input) ((input) && (*input)) static void *_pgsql_open(char *host, char *port, int usessl, const char *user, const char *password, const char *database) { PGconn *conn = NULL; struct buf conninfo = BUF_INITIALIZER; /* create the connection info string */ /* add each term that exists */ if (sql_exists(host)) buf_printf(&conninfo, " host='%s'", host); if (sql_exists(port)) buf_printf(&conninfo, " port='%s'", port); if (sql_exists(user)) buf_printf(&conninfo, " user='%s'", user); if (sql_exists(password)) buf_printf(&conninfo, " password='%s'", password); if (sql_exists(database)) buf_printf(&conninfo, " dbname='%s'", database); buf_printf(&conninfo, " requiressl='%d'", usessl); conn = PQconnectdb(buf_cstring(&conninfo)); buf_free(&conninfo); if ((PQstatus(conn) != CONNECTION_OK)) { syslog(LOG_ERR, "DBERROR: SQL backend: %s", PQerrorMessage(conn)); return NULL; } return conn; } static char *_pgsql_escape(void *conn __attribute__((unused)), char **to __attribute__((unused)), const char *from, size_t fromlen) { size_t tolen; /* returned buffer MUST be freed by caller */ return (char *) PQescapeBytea((unsigned char *) from, fromlen, &tolen); } static int _pgsql_exec(void *conn, const char *cmd, exec_cb *cb, void *rock) { PGresult *result; int row_count, i, r = 0; ExecStatusType status; syslog(LOG_DEBUG, "executing SQL cmd: %s", cmd); /* run the query */ result = PQexec(conn, cmd); /* check the status */ status = PQresultStatus(result); if (status == PGRES_COMMAND_OK) { /* no results (BEGIN, COMMIT, ROLLBACK, CREATE, INSERT, UPDATE, DELETE) */ PQclear(result); return 0; } else if (status != PGRES_TUPLES_OK) { /* error */ syslog(LOG_DEBUG, "SQL backend: %s ", PQresStatus(status)); PQclear(result); return CYRUSDB_INTERNAL; } row_count = PQntuples(result); for (i = 0; !r && i < row_count; i++) { char *key, *data; size_t keylen, datalen; key = (char *) PQunescapeBytea((unsigned char *) PQgetvalue(result, i, 0), &keylen); data = (char *) PQunescapeBytea((unsigned char *) PQgetvalue(result, i, 1), &datalen); r = cb(rock, key, keylen, data, datalen); free(key); free(data); } /* free result */ PQclear(result); return r; } static int _pgsql_begin_txn(void *conn) { return _pgsql_exec(conn, "BEGIN;", NULL, NULL); } static int _pgsql_commit_txn(void *conn) { return _pgsql_exec(conn, "COMMIT;", NULL, NULL); } static int _pgsql_rollback_txn(void *conn) { return _pgsql_exec(conn, "ROLLBACK;", NULL, NULL); } static void _pgsql_close(void *conn) { PQfinish(conn); } #endif /* HAVE_PGSQL */ #ifdef HAVE_SQLITE #include static void *_sqlite_open(char *host __attribute__((unused)), char *port __attribute__((unused)), int usessl __attribute__((unused)), const char *user __attribute__((unused)), const char *password __attribute__((unused)), const char *database) { int rc; sqlite3 *db; rc = sqlite3_open(database, &db); if (rc != SQLITE_OK) { syslog(LOG_ERR, "DBERROR: SQL backend: %s", sqlite3_errmsg(db)); sqlite3_close(db); } return db; } static char *_sqlite_escape(void *conn __attribute__((unused)), char **to, const char *from, size_t fromlen) { size_t tolen; #if 0 *to = xrealloc(*to, 2 + (257 * fromlen) / 254); tolen = sqlite3_encode_binary(from, fromlen, *to); #else *to = xrealloc(*to, fromlen + 1); memcpy(*to, from, fromlen); tolen = fromlen; (*to)[tolen] = '\0'; #endif return *to; } static int _sqlite_exec(void *conn, const char *cmd, exec_cb *cb, void *rock) { int rc, r = 0; sqlite3_stmt *stmt = NULL; const char *tail; syslog(LOG_DEBUG, "executing SQL cmd: %s", cmd); /* compile the SQL cmd */ rc = sqlite3_prepare(conn, cmd, strlen(cmd), &stmt, &tail); if (rc != SQLITE_OK) { syslog(LOG_DEBUG, "SQL backend: %s ", sqlite3_errmsg(conn)); return CYRUSDB_INTERNAL; } /* process the results */ while (!r && (rc = sqlite3_step(stmt)) == SQLITE_ROW) { const unsigned char *key = sqlite3_column_text(stmt, 0); int keylen = sqlite3_column_bytes(stmt, 0); const unsigned char *data = sqlite3_column_text(stmt, 1); int datalen = sqlite3_column_bytes(stmt, 1); r = cb(rock, (char *) key, keylen, (char *) data, datalen); } /* cleanup */ rc = sqlite3_finalize(stmt); if (rc != SQLITE_OK) { syslog(LOG_DEBUG, "SQL backend: %s ", sqlite3_errmsg(conn)); return CYRUSDB_INTERNAL; } return r; } static int _sqlite_begin_txn(void *conn) { return _sqlite_exec(conn, "BEGIN TRANSACTION", NULL, NULL); } static int _sqlite_commit_txn(void *conn) { return _sqlite_exec(conn, "COMMIT TRANSACTION", NULL, NULL); } static int _sqlite_rollback_txn(void *conn) { return _sqlite_exec(conn, "ROLLBACK TRANSACTION", NULL, NULL); } static void _sqlite_close(void *conn) { sqlite3_close(conn); } #endif /* HAVE_SQLITE */ static const sql_engine_t sql_engines[] = { #ifdef HAVE_MYSQL { "mysql", "BLOB", &_mysql_open, &_mysql_escape, &_mysql_begin_txn, &_mysql_commit_txn, &_mysql_rollback_txn, &_mysql_exec, &_mysql_close }, #endif /* HAVE_MYSQL */ #ifdef HAVE_PGSQL { "pgsql", "BYTEA", &_pgsql_open, &_pgsql_escape, &_pgsql_begin_txn, &_pgsql_commit_txn, &_pgsql_rollback_txn, &_pgsql_exec, &_pgsql_close }, #endif #ifdef HAVE_SQLITE { "sqlite", "BLOB", &_sqlite_open, &_sqlite_escape, &_sqlite_begin_txn, &_sqlite_commit_txn, &_sqlite_rollback_txn, &_sqlite_exec, &_sqlite_close }, #endif { NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL } }; static int init(const char *dbdir __attribute__((unused)), int flags __attribute__((unused))) { const char *engine_name; int r = 0; if (dbinit++) return 0; engine_name = libcyrus_config_getstring(CYRUSOPT_SQL_ENGINE); /* find the correct engine */ dbengine = sql_engines; while (dbengine->name) { if (!engine_name || !strcasecmp(engine_name, dbengine->name)) break; dbengine++; } if (!dbengine->name) { char errbuf[1024]; snprintf(errbuf, sizeof(errbuf), "SQL engine %s not supported", engine_name); fatal(errbuf, EC_CONFIG); } if (!engine_name) { syslog(LOG_DEBUG, "SQL backend defaulting to engine '%s'", dbengine->name); } dbinit = 1; return r; } static int done(void) { --dbinit; return 0; } static int myopen(const char *fname, int flags, struct dbengine **ret) { const char *database, *hostnames, *user, *passwd; char *host_ptr, *host, *cur_host, *cur_port; int usessl; void *conn = NULL; char *p, *table, cmd[1024]; assert(fname); assert(ret); /* make a connection to the database */ database = libcyrus_config_getstring(CYRUSOPT_SQL_DATABASE); hostnames = libcyrus_config_getstring(CYRUSOPT_SQL_HOSTNAMES); user = libcyrus_config_getstring(CYRUSOPT_SQL_USER); passwd = libcyrus_config_getstring(CYRUSOPT_SQL_PASSWD); usessl = libcyrus_config_getswitch(CYRUSOPT_SQL_USESSL); /* loop around hostnames until we get a connection */ syslog(LOG_DEBUG, "SQL backend trying to connect to a host"); /* create a working version of the hostnames */ host_ptr = hostnames ? xstrdup(hostnames) : NULL; /* make sqlite clever */ if (!database) database = fname; cur_host = host = host_ptr; while (cur_host != NULL) { host = strchr(host,','); if (host != NULL) { host[0] = '\0'; /* loop till we find some text */ while (!Uisalnum(host[0])) host++; } syslog(LOG_DEBUG, "SQL backend trying to open db '%s' on host '%s'%s", database, cur_host, usessl ? " using SSL" : ""); /* set the optional port */ if ((cur_port = strchr(cur_host, ':'))) *cur_port++ = '\0'; conn = dbengine->sql_open(cur_host, cur_port, usessl, user, passwd, database); if (conn) break; syslog(LOG_WARNING, "DBERROR: SQL backend could not connect to host %s", cur_host); cur_host = host; } if (host_ptr) free(host_ptr); if (!conn) { syslog(LOG_ERR, "DBERROR: could not open SQL database '%s'", database); return CYRUSDB_IOERROR; } /* get the name of the table and CREATE it if necessary */ /* strip any path from the fname */ p = strrchr(fname, '/'); table = xstrdup(p ? ++p : fname); /* convert '.' to '_' */ if ((p = strrchr(table, '.'))) *p = '_'; /* check if the table exists */ /* XXX is this the best way to do this? */ snprintf(cmd, sizeof(cmd), "SELECT * FROM %s LIMIT 0;", table); if (dbengine->sql_exec(conn, cmd, NULL, NULL)) { if (flags & CYRUSDB_CREATE) { /* create the table */ snprintf(cmd, sizeof(cmd), "CREATE TABLE %s (dbkey %s NOT NULL, data %s);", table, dbengine->binary_type, dbengine->binary_type); if (dbengine->sql_exec(conn, cmd, NULL, NULL)) { syslog(LOG_ERR, "DBERROR: SQL failed: %s", cmd); dbengine->sql_close(conn); return CYRUSDB_INTERNAL; } } else { return CYRUSDB_NOTFOUND; } } *ret = (struct dbengine *) xzmalloc(sizeof(struct dbengine)); (*ret)->conn = conn; (*ret)->table = table; return 0; } static int myclose(struct dbengine *db) { assert(db); dbengine->sql_close(db->conn); free(db->table); if (db->esc_key) free(db->esc_key); if (db->esc_data) free(db->esc_data); if (db->data) free(db->data); free(db); return 0; } static struct txn *start_txn(struct dbengine *db) { /* start a transaction */ if (dbengine->sql_begin_txn(db->conn)) { syslog(LOG_ERR, "DBERROR: failed to start txn on %s", db->table); return NULL; } return xzmalloc(sizeof(struct txn)); } struct select_rock { int found; struct txn *tid; foreach_cb *goodp; foreach_cb *cb; void *rock; }; static int select_cb(void *rock, const char *key, size_t keylen, const char *data, size_t datalen) { struct select_rock *srock = (struct select_rock *) rock; int r = CYRUSDB_OK; /* if we're in a transaction, save this key */ if (srock->tid) { srock->tid->lastkey = xrealloc(srock->tid->lastkey, keylen); memcpy(srock->tid->lastkey, key, keylen); srock->tid->keylen = keylen; } /* see if we want this entry */ if (!srock->goodp || srock->goodp(srock->rock, key, keylen, data, datalen)) { srock->found = 1; /* make callback */ if (srock->cb) r = srock->cb(srock->rock, key, keylen, data, datalen); } return r; } struct fetch_rock { char **data; size_t *datalen; }; static int fetch_cb(void *rock, const char *key __attribute__((unused)), size_t keylen __attribute__((unused)), const char *data, size_t datalen) { struct fetch_rock *frock = (struct fetch_rock *) rock; if (frock->data) { *(frock->data) = xrealloc(*(frock->data), datalen); memcpy(*(frock->data), data, datalen); } if (frock->datalen) *(frock->datalen) = datalen; return 0; } static int fetch(struct dbengine *db, const char *key, size_t keylen, const char **data, size_t *datalen, struct txn **tid) { char cmd[1024], *esc_key; size_t len = 0; struct fetch_rock frock = { &db->data, &len }; struct select_rock srock = { 0, NULL, NULL, &fetch_cb, &frock }; int r; assert(db); assert(key); assert(keylen); if (datalen) assert(data); if (data) *data = NULL; if (datalen) *datalen = 0; if (tid) { if (!*tid && !(*tid = start_txn(db))) return CYRUSDB_INTERNAL; srock.tid = *tid; } /* fetch the data */ esc_key = dbengine->sql_escape(db->conn, &db->esc_key, key, keylen); snprintf(cmd, sizeof(cmd), "SELECT * FROM %s WHERE dbkey = '%s';", db->table, esc_key); if (esc_key != db->esc_key) free(esc_key); r = dbengine->sql_exec(db->conn, cmd, &select_cb, &srock); if (r) { syslog(LOG_ERR, "DBERROR: SQL failed %s", cmd); if (tid) dbengine->sql_rollback_txn(db->conn); return CYRUSDB_INTERNAL; } if (!srock.found) return CYRUSDB_NOTFOUND; if (data) *data = db->data; if (datalen) *datalen = len; return 0; } static int foreach(struct dbengine *db, const char *prefix, size_t prefixlen, foreach_p *goodp, foreach_cb *cb, void *rock, struct txn **tid) { char cmd[1024], *esc_key = NULL; struct select_rock srock = { 0, NULL, goodp, cb, rock }; int r; assert(db); assert(cb); if (prefixlen) assert(prefix); if (tid) { if (!*tid && !(*tid = start_txn(db))) return CYRUSDB_INTERNAL; srock.tid = *tid; } /* fetch the data */ if (prefixlen) /* XXX hack for SQLite */ esc_key = dbengine->sql_escape(db->conn, &db->esc_key, prefix, prefixlen); snprintf(cmd, sizeof(cmd), "SELECT * FROM %s WHERE dbkey LIKE '%s%%' ORDER BY dbkey;", db->table, esc_key ? esc_key : ""); if (esc_key && (esc_key != db->esc_key)) free(esc_key); r = dbengine->sql_exec(db->conn, cmd, &select_cb, &srock); if (r) { syslog(LOG_ERR, "DBERROR: SQL failed %s", cmd); if (tid) dbengine->sql_rollback_txn(db->conn); return CYRUSDB_INTERNAL; } return 0; } static int mystore(struct dbengine *db, const char *key, int keylen, const char *data, int datalen, struct txn **tid, int overwrite, int isdelete) { char cmd[1024], *esc_key; int free_esc_key = 0; const char dummy = 0; int r = 0; assert(db); assert(key); assert(keylen); if (datalen) assert(data); if (!data) data = &dummy; if (tid && !*tid && !(*tid = start_txn(db))) return CYRUSDB_INTERNAL; esc_key = dbengine->sql_escape(db->conn, &db->esc_key, key, keylen); free_esc_key = (esc_key != db->esc_key); if (isdelete) { /* DELETE the entry */ snprintf(cmd, sizeof(cmd), "DELETE FROM %s WHERE dbkey = '%s';", db->table, esc_key); r = dbengine->sql_exec(db->conn, cmd, NULL, NULL); /* see if we just removed the previously SELECTed key */ if (!r && tid && *tid && (*tid)->keylen == strlen(esc_key) && !memcmp((*tid)->lastkey, esc_key, (*tid)->keylen)) { (*tid)->keylen = 0; } } else { /* INSERT/UPDATE the entry */ struct select_rock srock = { 0, NULL, NULL, NULL, NULL }; char *esc_data = dbengine->sql_escape(db->conn, &db->esc_data, data, datalen); int free_esc_data = (esc_data != db->esc_data); /* see if we just SELECTed this key in this transaction */ if (tid && *tid) { if ((*tid)->keylen == strlen(esc_key) && !memcmp((*tid)->lastkey, esc_key, (*tid)->keylen)) { srock.found = 1; } srock.tid = *tid; } /* check if the entry exists */ if (!srock.found) { snprintf(cmd, sizeof(cmd), "SELECT * FROM %s WHERE dbkey = '%s';", db->table, esc_key); r = dbengine->sql_exec(db->conn, cmd, &select_cb, &srock); } if (!r && srock.found) { if (overwrite) { /* already have this entry, UPDATE it */ snprintf(cmd, sizeof(cmd), "UPDATE %s SET data = '%s' WHERE dbkey = '%s';", db->table, esc_data, esc_key); r = dbengine->sql_exec(db->conn, cmd, NULL, NULL); } else { if (tid) dbengine->sql_rollback_txn(db->conn); return CYRUSDB_EXISTS; } } else if (!r && !srock.found) { /* INSERT the new entry */ snprintf(cmd, sizeof(cmd), "INSERT INTO %s VALUES ('%s', '%s');", db->table, esc_key, esc_data); r = dbengine->sql_exec(db->conn, cmd, NULL, NULL); } if (free_esc_data) free(esc_data); } if (free_esc_key) free(esc_key); if (r) { syslog(LOG_ERR, "DBERROR: SQL failed: %s", cmd); if (tid) dbengine->sql_rollback_txn(db->conn); return CYRUSDB_INTERNAL; } return 0; } static int create(struct dbengine *db, const char *key, size_t keylen, const char *data, size_t datalen, struct txn **tid) { return mystore(db, key, keylen, data, datalen, tid, 0, 0); } static int store(struct dbengine *db, const char *key, size_t keylen, const char *data, size_t datalen, struct txn **tid) { return mystore(db, key, keylen, data, datalen, tid, 1, 0); } static int delete(struct dbengine *db, const char *key, size_t keylen, struct txn **tid, int force __attribute__((unused))) { return mystore(db, key, keylen, NULL, 0, tid, 1, 1); } static int finish_txn(struct dbengine *db, struct txn *tid, int commit) { if (tid) { int rc = commit ? dbengine->sql_commit_txn(db->conn) : dbengine->sql_rollback_txn(db->conn); if (tid->lastkey) free(tid->lastkey); free(tid); if (rc) { syslog(LOG_ERR, "DBERROR: failed to %s txn on %s", commit ? "commit" : "abort", db->table); return CYRUSDB_INTERNAL; } } return 0; } static int commit_txn(struct dbengine *db, struct txn *tid) { assert(db); assert(tid); return finish_txn(db, tid, 1); } static int abort_txn(struct dbengine *db, struct txn *tid) { assert(db); assert(tid); return finish_txn(db, tid, 0); } /* SQL databases have all sorts of evil collations - we can't * make any assumptions though, so just assume raw */ static int mycompar(struct dbengine *db __attribute__((unused)), const char *a, int alen, const char *b, int blen) { (void)db; return bsearch_ncompare_raw(a, alen, b, blen); } HIDDEN struct cyrusdb_backend cyrusdb_sql = { "sql", /* name */ &init, &done, &cyrusdb_generic_sync, &cyrusdb_generic_noarchive, &myopen, &myclose, &fetch, &fetch, NULL, &foreach, &create, &store, &delete, &commit_txn, &abort_txn, NULL, NULL, NULL, &mycompar }; cyrus-imapd-2.5.10/lib/strhash.h0000644000175000017500000000361612772415051013362 00000000000000/* strhash.h string hashing * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #ifndef _STRHASH_H_ unsigned strhash(const char *string); #endif /* _STRHASH_H_ */ cyrus-imapd-2.5.10/lib/mappedfile.c0000644000175000017500000002655713001236020013777 00000000000000/* mappedfile - interface to a mmaped, lockable, writable file * * Copyright (c) 1994-2011 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ /* Interface to an mmaped file, including locking. * * Many different modules within Cyrus, including most of the * database engines, wrap an mmaped file with locking semantics, * refreshing the map on re-locking, and writing to a location * within the file. * * This module provides handy wrapper interfaces to each of those * items. NOTE - it doesn't provide a guarantee that the same file * isn't opened twice, stomping all over the locks in the process. * To get that, you need to protect in the caller. * */ #include "mappedfile.h" #include #include #include #include #include #include #include #include #ifdef HAVE_UNISTD_H #include #endif #include "assert.h" #include "cyr_lock.h" #include "libcyr_cfg.h" #include "map.h" #include "retry.h" #include "util.h" #include "xmalloc.h" #define MF_UNLOCKED 0 #define MF_READLOCKED 1 #define MF_WRITELOCKED 2 struct mappedfile { char *fname; /* obviously you will need 64 bit size_t for 64 bit files... */ struct buf map_buf; size_t map_size; /* the file itself */ int fd; /* tracking */ int lock_status; int dirty; int was_resized; int is_rw; }; static void _ensure_mapped(struct mappedfile *mf, size_t offset, int update) { /* we may be rewriting inside a file, so don't shrink, only extend */ if (update) { if (offset > mf->map_size) mf->was_resized = 1; else offset = mf->map_size; } /* always give refresh another go, we may be map_nommap */ buf_init_mmap(&mf->map_buf, /*onceonly*/0, mf->fd, mf->fname, offset, /*mboxname*/NULL); mf->map_size = offset; } /* NOTE - we don't provide any guarantees that the file isn't open multiple * times. So don't do that. It will mess with your locking no end */ EXPORTED int mappedfile_open(struct mappedfile **mfp, const char *fname, int flags) { struct mappedfile *mf; struct stat sbuf; int openmode = (flags & MAPPEDFILE_RW) ? O_RDWR : O_RDONLY; int create = (flags & MAPPEDFILE_CREATE) ? 1 : 0; int r; assert(fname); assert(!*mfp); mf = xzmalloc(sizeof(struct mappedfile)); mf->fname = xstrdup(fname); mf->is_rw = (flags & MAPPEDFILE_RW) ? 1 : 0; mf->fd = open(mf->fname, openmode, 0644); if (mf->fd < 0 && errno == ENOENT) { if (!create || !mf->is_rw) { r = -errno; goto err; } r = cyrus_mkdir(mf->fname, 0755); if (r < 0) { syslog(LOG_ERR, "IOERROR: cyrus_mkdir %s: %m", mf->fname); goto err; } mf->fd = open(mf->fname, O_RDWR | O_CREAT, 0644); } if (mf->fd == -1) { syslog(LOG_ERR, "IOERROR: open %s: %m", mf->fname); r = -errno; goto err; } /* it's zero, but set it anyway */ mf->lock_status = MF_UNLOCKED; mf->dirty = 0; r = fstat(mf->fd, &sbuf); if (r < 0) { syslog(LOG_ERR, "IOERROR: fstat %s: %m", mf->fname); goto err; } _ensure_mapped(mf, sbuf.st_size, /*update*/0); *mfp = mf; return 0; err: mappedfile_close(&mf); return r; } EXPORTED int mappedfile_close(struct mappedfile **mfp) { struct mappedfile *mf = *mfp; int r = 0; /* make this safe to call multiple times */ if (!mf) return 0; assert(mf->lock_status == MF_UNLOCKED); assert(!mf->dirty); if (mf->fd >= 0) r = close(mf->fd); buf_free(&mf->map_buf); free(mf->fname); free(mf); *mfp = NULL; return r; } EXPORTED int mappedfile_readlock(struct mappedfile *mf) { struct stat sbuf, sbuffile; int newfd = -1; assert(mf->lock_status == MF_UNLOCKED); assert(mf->fd != -1); assert(!mf->dirty); for (;;) { if (lock_shared(mf->fd, mf->fname) < 0) { syslog(LOG_ERR, "IOERROR: lock_shared %s: %m", mf->fname); return -EIO; } if (fstat(mf->fd, &sbuf) == -1) { syslog(LOG_ERR, "IOERROR: fstat %s: %m", mf->fname); lock_unlock(mf->fd, mf->fname); return -EIO; } if (stat(mf->fname, &sbuffile) == -1) { syslog(LOG_ERR, "IOERROR: stat %s: %m", mf->fname); lock_unlock(mf->fd, mf->fname); return -EIO; } if (sbuf.st_ino == sbuffile.st_ino) break; buf_free(&mf->map_buf); newfd = open(mf->fname, O_RDWR, 0644); if (newfd == -1) { syslog(LOG_ERR, "IOERROR: open %s: %m", mf->fname); lock_unlock(mf->fd, mf->fname); return -EIO; } dup2(newfd, mf->fd); close(newfd); } mf->lock_status = MF_READLOCKED; _ensure_mapped(mf, sbuf.st_size, /*update*/0); return 0; } EXPORTED int mappedfile_writelock(struct mappedfile *mf) { int r; struct stat sbuf; const char *lockfailaction; int changed = 0; assert(mf->lock_status == MF_UNLOCKED); assert(mf->fd != -1); assert(mf->is_rw); assert(!mf->dirty); r = lock_reopen_ex(mf->fd, mf->fname, &sbuf, &lockfailaction, &changed); if (r < 0) { syslog(LOG_ERR, "IOERROR: %s %s: %m", lockfailaction, mf->fname); return r; } mf->lock_status = MF_WRITELOCKED; if (changed) buf_free(&mf->map_buf); _ensure_mapped(mf, sbuf.st_size, /*update*/0); return 0; } EXPORTED int mappedfile_unlock(struct mappedfile *mf) { int r; /* make this safe to call multiple times */ if (!mf) return 0; if (mf->lock_status == MF_UNLOCKED) return 0; assert(mf->fd != -1); assert(!mf->dirty); r = lock_unlock(mf->fd, mf->fname); if (r < 0) { syslog(LOG_ERR, "IOERROR: lock_unlock %s: %m", mf->fname); return r; } mf->lock_status = MF_UNLOCKED; return 0; } EXPORTED int mappedfile_commit(struct mappedfile *mf) { assert(mf->fd != -1); if (!mf->dirty) return 0; /* nice, nothing to do */ assert(mf->is_rw); if (mf->was_resized) { if (fsync(mf->fd) < 0) { syslog(LOG_ERR, "IOERROR: %s fsync: %m", mf->fname); return -EIO; } } else { if (fdatasync(mf->fd) < 0) { syslog(LOG_ERR, "IOERROR: %s fdatasync: %m", mf->fname); return -EIO; } } mf->dirty = 0; mf->was_resized = 0; return 0; } EXPORTED ssize_t mappedfile_pwrite(struct mappedfile *mf, const char *base, size_t len, off_t offset) { ssize_t written; off_t pos; assert(mf->is_rw); assert(mf->fd != -1); assert(base); if (!len) return 0; /* nothing to write! */ /* XXX - memcmp and don't both writing if it matches? */ mf->dirty++; /* locate the file handle */ pos = lseek(mf->fd, offset, SEEK_SET); if (pos < 0) { syslog(LOG_ERR, "IOERROR: %s seek to %llX: %m", mf->fname, (long long unsigned int)offset); return -1; } /* write the buffer */ written = retry_write(mf->fd, base, len); if (written < 0) { syslog(LOG_ERR, "IOERROR: %s write %llu bytes at %llX: %m", mf->fname, (long long unsigned int)len, (long long unsigned int)offset); return -1; } _ensure_mapped(mf, pos+written, /*update*/1); return written; } EXPORTED ssize_t mappedfile_pwritebuf(struct mappedfile *mf, const struct buf *buf, off_t offset) { return mappedfile_pwrite(mf, buf->s, buf->len, offset); } EXPORTED ssize_t mappedfile_pwritev(struct mappedfile *mf, const struct iovec *iov, int nio, off_t offset) { ssize_t written; off_t pos; assert(mf->is_rw); assert(mf->fd != -1); assert(iov); if (!nio) return 0; /* nothing to write! */ /* XXX - memcmp and don't both writing if it matches? */ mf->dirty++; /* locate the file handle */ pos = lseek(mf->fd, offset, SEEK_SET); if (pos < 0) { syslog(LOG_ERR, "IOERROR: %s seek to %llX: %m", mf->fname, (long long unsigned int)offset); return -1; } /* write the buffer */ written = retry_writev(mf->fd, iov, nio); if (written < 0) { size_t len = 0; int i; for (i = 0; i < nio; i++) { len += iov[i].iov_len; } syslog(LOG_ERR, "IOERROR: %s write %llu bytes at %llX: %m", mf->fname, (long long unsigned int)len, (long long unsigned int)offset); return -1; } _ensure_mapped(mf, pos+written, /*update*/1); return written; } EXPORTED int mappedfile_truncate(struct mappedfile *mf, off_t offset) { int r; assert(mf->is_rw); assert(mf->fd != -1); mf->dirty++; r = ftruncate(mf->fd, offset); if (r < 0) { syslog(LOG_ERR, "IOERROR: ftruncate %s: %m", mf->fname); return r; } _ensure_mapped(mf, offset, /*update*/0); mf->was_resized = 1; /* force the fsync */ return 0; } EXPORTED int mappedfile_rename(struct mappedfile *mf, const char *newname) { int r; r = rename(mf->fname, newname); if (r < 0) { syslog(LOG_ERR, "IOERROR: rename (%s, %s): %m", mf->fname, newname); return r; } free(mf->fname); mf->fname = xstrdup(newname); return 0; } EXPORTED int mappedfile_islocked(const struct mappedfile *mf) { return (mf->lock_status != MF_UNLOCKED); } //FIXME this function is nowhere used EXPORTED int mappedfile_isreadlocked(const struct mappedfile *mf) { return (mf->lock_status == MF_READLOCKED); } EXPORTED int mappedfile_iswritelocked(const struct mappedfile *mf) { return (mf->lock_status == MF_WRITELOCKED); } EXPORTED int mappedfile_iswritable(const struct mappedfile *mf) { return !!mf->is_rw; } EXPORTED const char *mappedfile_base(const struct mappedfile *mf) { /* XXX - require locked? */ return mf->map_buf.s; } EXPORTED size_t mappedfile_size(const struct mappedfile *mf) { return mf->map_size; } EXPORTED const struct buf *mappedfile_buf(const struct mappedfile *mf) { return &mf->map_buf; } EXPORTED const char *mappedfile_fname(const struct mappedfile *mf) { return mf->fname; } cyrus-imapd-2.5.10/lib/bsearch.h0000644000175000017500000000461013001236020013267 00000000000000/* bsearch.h -- binary search * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #ifndef INCLUDED_BSEARCH_H #define INCLUDED_BSEARCH_H extern int bsearch_mem_mbox(const char *word, const char *base, unsigned long len, unsigned long hint, unsigned long *linelenp); extern int bsearch_compare_mbox(const char *s1, const char *s2); extern int bsearch_ncompare_mbox(const char *s1, int l1, const char *s2, int l2); extern int bsearch_ncompare_raw(const char *s1, int l1, const char *s2, int l2); extern int cmpstringp_raw(const void *p1, const void *p2); extern int cmpstringp_mbox(const void *p1, const void *p2); #endif /* INCLUDED_BSEARCH_H */ cyrus-imapd-2.5.10/lib/parseaddr.c0000644000175000017500000002540013001236020013620 00000000000000/* parseaddr.c -- RFC 822 address parser * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include #include #include #include #include "parseaddr.h" #include "xmalloc.h" #include "util.h" static const char unknown_user[] = "unknown-user"; static const char unspecified_domain[] = "unspecified-domain"; static void parseaddr_append(struct address ***addrpp, const char *name, const char *route, const char *mailbox, const char *domain, char **freemep); static int parseaddr_phrase (char **inp, char **phrasep, const char *specials); static int parseaddr_domain (char **inp, char **domainp, char **commmentp); static int parseaddr_route (char **inp, char **routep); /* * Parse an address list in 's', appending address structures to * the list pointed to by 'addrp'. */ EXPORTED void parseaddr_list(const char *str, struct address **addrp) { char *s; int ingroup = 0; char *freeme; int tok = ' '; char *phrase, *route, *mailbox, *domain, *comment; /* Skip down to the tail */ while (*addrp) { addrp = &(*addrp)->next; } s = freeme = xstrdup(str); while (tok) { tok = parseaddr_phrase(&s, &phrase, ingroup ? ",@<;" : ",@<:"); switch (tok) { case ',': case '\0': case ';': if (*phrase) { parseaddr_append(&addrp, 0, 0, phrase, "", &freeme); } if (tok == ';') { parseaddr_append(&addrp, 0, 0, 0, 0, &freeme); ingroup = 0; } continue; case ':': parseaddr_append(&addrp, 0, 0, phrase, 0, &freeme); ingroup++; continue; case '@': tok = parseaddr_domain(&s, &domain, &comment); parseaddr_append(&addrp, comment, 0, phrase, domain, &freeme); if (tok == ';') { parseaddr_append(&addrp, 0, 0, 0, 0, &freeme); ingroup = 0; } continue; case '<': tok = parseaddr_phrase(&s, &mailbox, "@>"); if (tok == '@') { route = 0; if (!*mailbox) { *--s = '@'; tok = parseaddr_route(&s, &route); if (tok != ':') { parseaddr_append(&addrp, phrase, route, "", "", &freeme); while (tok && tok != '>') tok = *s++; continue; } tok = parseaddr_phrase(&s, &mailbox, "@>"); if (tok != '@') { parseaddr_append(&addrp, phrase, route, mailbox, "", &freeme); continue; } } tok = parseaddr_domain(&s, &domain, 0); parseaddr_append(&addrp, phrase, route, mailbox, domain, &freeme); while (tok && tok != '>') tok = *s++; continue; /* effectively auto-inserts a comma */ } else { parseaddr_append(&addrp, phrase, 0, mailbox, "", &freeme); } } } if (ingroup) parseaddr_append(&addrp, 0, 0, 0, 0, &freeme); if (freeme) free(freeme); } /* * Free the address list 'addr' */ EXPORTED void parseaddr_free(struct address *addr) { struct address *next; while (addr) { if (addr->freeme) free(addr->freeme); next = addr->next; free((char *)addr); addr = next; } } /* * Helper function to append a new address structure to and address list. */ static void parseaddr_append(struct address ***addrpp, const char *name, const char *route, const char *mailbox, const char *domain, char **freemep) { struct address *newaddr; newaddr = (struct address *)xmalloc(sizeof(struct address)); if (name && *name) { newaddr->name = name; } else { newaddr->name = 0; } if (route && *route) { newaddr->route = route; } else { newaddr->route = 0; } newaddr->mailbox = mailbox; if (domain && !*domain) { domain = unspecified_domain; } newaddr->domain = domain; newaddr->next = 0; newaddr->freeme = *freemep; *freemep = 0; **addrpp = newaddr; *addrpp = &newaddr->next; } /* Macro to skip white space and rfc822 comments */ #define SKIPWHITESPACE(s) \ { \ int _c, _comment = 0; \ \ while ((_c = *(s))) { \ if (_c == '(') { \ _comment = 1; \ (s)++; \ while ((_comment && (_c = *(s)))) { \ (s)++; \ if (_c == '\\' && *(s)) (s)++; \ else if (_c == '(') _comment++; \ else if (_c == ')') _comment--; \ } \ (s)--; \ } \ else if (!Uisspace(_c)) break; \ (s)++; \ } \ } /* * Parse an RFC 822 "phrase", stopping at 'specials' */ static int parseaddr_phrase(char **inp, char **phrasep, const char *specials) { int c; char *src = *inp; char *dst; SKIPWHITESPACE(src); *phrasep = dst = src; for (;;) { c = *src++; if (c == '"') { while ((c = *src)) { src++; if (c == '\r' && *src == '\n') { /* CR+LF combination */ src++; if (*src == ' ' || *src == '\t') { /* CR+LF+WSP - folded header field, * unfold it by skipping ONLY the CR+LF */ continue; } /* otherwise we have CR+LF at the end of a header * field, which means we have an unbalanced " */ goto fail; } if (c == '\r' || c == '\n') goto fail; /* invalid chars */ if (c == '"') break; /* end of quoted string */ if (c == '\\') { if (!(c = *src)) goto fail; src++; } *dst++ = c; } if (c != '"') goto fail; /* unbalanced " */ } else if (Uisspace(c) || c == '(') { src--; SKIPWHITESPACE(src); *dst++ = ' '; } else if (!c || strchr(specials, c)) { if (dst > *phrasep && dst[-1] == ' ') dst--; *dst = '\0'; *inp = src; return c; } else { *dst++ = c; } } fail: /* simulate end-of-string */ *phrasep = ""; return 0; } /* * Parse a domain. If 'commentp' is non-nil, parses any trailing comment */ static int parseaddr_domain(char **inp, char **domainp, char **commentp) { int c; char *src = *inp; char *dst; char *cdst; int comment; if (commentp) *commentp = 0; SKIPWHITESPACE(src); *domainp = dst = src; for (;;) { c = *src++; if (Uisalnum(c) || c == '-' || c == '[' || c == ']' || c == ':') { *dst++ = c; if (commentp) *commentp = 0; } else if (c == '.') { if (dst > *domainp && dst[-1] != '.') *dst++ = c; if (commentp) *commentp = 0; } else if (c == '(') { if (commentp) { *commentp = cdst = src; comment = 1; while (comment && (c = *src)) { src++; if (c == '(') comment++; else if (c == ')') comment--; else if (c == '\\' && (c = *src)) src++; if (comment) *cdst++ = c; } *cdst = '\0'; } else { src--; SKIPWHITESPACE(src); } } else if (!Uisspace(c)) { if (dst > *domainp && dst[-1] == '.') dst--; *dst = '\0'; *inp = src; return c; } } } /* * Parse a source route (at-domain-list) */ static int parseaddr_route(char **inp, char **routep) { int c; char *src = *inp; char *dst; SKIPWHITESPACE(src); *routep = dst = src; for (;;) { c = *src++; if (Uisalnum(c) || c == '-' || c == '[' || c == ']' || c == ',' || c == '@') { *dst++ = c; } else if (c == '.') { if (dst > *routep && dst[-1] != '.') *dst++ = c; } else if (Uisspace(c) || c == '(') { src--; SKIPWHITESPACE(src); } else { while (dst > *routep && (dst[-1] == '.' || dst[-1] == ',' || dst[-1] == '@')) dst--; *dst = '\0'; *inp = src; return c; } } } EXPORTED char *address_get_all(const struct address *a, int canon_domain) { char *s = NULL; if (a->mailbox || a->domain) { const char *m = a->mailbox ? a->mailbox : unknown_user; const char *d = a->domain ? a->domain : unspecified_domain; s = strconcat(m, "@", d, (char *)NULL); if (canon_domain) lcase(s + strlen(m) + 1); } return s; } EXPORTED char *address_get_localpart(const struct address *a) { return xstrdupnull(a->mailbox); } EXPORTED char *address_get_domain(const struct address *a, int canon_domain) { char *s = NULL; if (a->domain) { s = xstrdup(a->domain); if (canon_domain) lcase(s); } return s; } EXPORTED char *address_get_user(const struct address *a) { char *s = NULL; if (a->mailbox) { char *p = strchr(a->mailbox, '+'); int len = p ? p - a->mailbox : (int)strlen(a->mailbox); s = xstrndup(a->mailbox, len); } return s; } EXPORTED char *address_get_detail(const struct address *a) { char *s = NULL; if (a->mailbox) { char *p = strchr(a->mailbox, '+'); s = p ? xstrdup(p + 1) : NULL; } return s; } /* * Address iterator interface */ EXPORTED void address_itr_init(struct address_itr *ai, const char *str) { memset(ai, 0, sizeof(*ai)); parseaddr_list(str, &ai->addrlist); ai->anext = ai->addrlist; } EXPORTED const struct address *address_itr_next(struct address_itr *ai) { struct address *a; if (ai->anext == NULL) return NULL; a = ai->anext; ai->anext = ai->anext->next; return a; } EXPORTED void address_itr_fini(struct address_itr *ai) { parseaddr_free(ai->addrlist); memset(ai, 0, sizeof(*ai)); } /* * Convenience function to return a single canonicalised address. */ EXPORTED char *address_canonicalise(const char *str) { struct address *addrlist = NULL; char *s = NULL; parseaddr_list(str, &addrlist); if (addrlist) s = address_get_all(addrlist, 1); parseaddr_free(addrlist); return s; } cyrus-imapd-2.5.10/lib/gmtoff_tm.c0000644000175000017500000000405712772415051013663 00000000000000/* gmtoff_tm.c - Get offset from GMT from the tm_gmtoff struct member * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include /* * Returns the GMT offset of the struct tm 'tm', obtained from 'time'. */ EXPORTED int gmtoff_of(struct tm *tm, time_t time __attribute__((unused))) { return tm->tm_gmtoff; } cyrus-imapd-2.5.10/lib/times.c0000644000175000017500000005072413001236020013003 00000000000000/* times.c -- Time/date utilities * * Copyright (c) 1994-2010 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include #include #include #include #include #include "assert.h" #include "times.h" #include "util.h" #include "gmtoff.h" #include "mkgmtime.h" static const char * const monthname[12] = { "Jan", "Feb", "Mar", "Apr", "May", "Jun", "Jul", "Aug", "Sep", "Oct", "Nov", "Dec" }; static const char * const wday[7] = { "Sun", "Mon", "Tue", "Wed", "Thu", "Fri", "Sat" }; static int monthdays(int year/*since 1900*/, int month/*0-based*/) { int leapday; static const int mdays[12] = { 31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31 }; #define isleap(year) (!((year) % 4) && (((year) % 100) || !((year) % 400))) leapday = (month == 1 && isleap(year+1900)); return mdays[month] + leapday; #undef isleap } /* 'buf' must be at least 80 characters */ EXPORTED int time_to_rfc822(time_t t, char *buf, size_t len) { struct tm *tm; long gmtoff; int gmtnegative = 0; assert(buf != NULL); tm = localtime(&t); gmtoff = gmtoff_of(tm, t); if (gmtoff < 0) { gmtoff = -gmtoff; gmtnegative = 1; } gmtoff /= 60; return snprintf(buf, len, "%s, %02d %s %4d %02d:%02d:%02d %c%.2lu%.2lu", wday[tm->tm_wday], tm->tm_mday, monthname[tm->tm_mon], tm->tm_year + 1900, tm->tm_hour, tm->tm_min, tm->tm_sec, gmtnegative ? '-' : '+', gmtoff / 60, gmtoff % 60); } /* * Skip RFC822 FWS = Folding White Space. This is the white * space that can be inserted harmlessly into structured * RFC822 headers, including splitting them over multiple lines. * * Note that RFC822 isn't entirely clear about whether such * space may be present in date-times, but it's successor * RFC2822 is quite clear and explicit. Note also that * neither RFC allows for (comments) inside a date-time, * so we don't attempt to handle that here. */ static const char *skip_fws(const char *p) { if (!p) return NULL; while (*p && Uisspace(*p)) { /* check for end of an RFC822 header line */ if (*p == '\n') { p++; if (*p != ' ' && *p != '\t') return NULL; } else p++; } return (*p ? p : NULL); } static int parse_rfc822(const char *s, time_t *tp, int dayonly) { const char *origs = s; struct tm tm; time_t t; char month[4]; int zone_off = 0; if (!s) goto baddate; memset(&tm, 0, sizeof(tm)); s = skip_fws(s); if (!s) goto baddate; if (Uisalpha(*s)) { /* Day name -- skip over it */ s++; if (!Uisalpha(*s)) goto baddate; s++; if (!Uisalpha(*s)) goto baddate; s++; s = skip_fws(s); if (!s || *s++ != ',') goto baddate; s = skip_fws(s); if (!s) goto baddate; } if (!Uisdigit(*s)) goto baddate; tm.tm_mday = *s++ - '0'; if (Uisdigit(*s)) { tm.tm_mday = tm.tm_mday*10 + *s++ - '0'; } /* Parse month name */ s = skip_fws(s); if (!s) goto baddate; month[0] = *s++; if (!Uisalpha(month[0])) goto baddate; month[1] = *s++; if (!Uisalpha(month[1])) goto baddate; month[2] = *s++; if (!Uisalpha(month[2])) goto baddate; month[3] = '\0'; for (tm.tm_mon = 0; tm.tm_mon < 12; tm.tm_mon++) { if (!strcasecmp(month, monthname[tm.tm_mon])) break; } if (tm.tm_mon == 12) goto baddate; /* Parse year */ s = skip_fws(s); if (!s || !Uisdigit(*s)) goto baddate; tm.tm_year = *s++ - '0'; if (!Uisdigit(*s)) goto baddate; tm.tm_year = tm.tm_year * 10 + *s++ - '0'; if (Uisdigit(*s)) { if (tm.tm_year < 19) goto baddate; tm.tm_year -= 19; tm.tm_year = tm.tm_year * 10 + *s++ - '0'; if (!Uisdigit(*s)) goto baddate; tm.tm_year = tm.tm_year * 10 + *s++ - '0'; } else { if (tm.tm_year < 70) { /* two-digit year, probably after 2000. * This patent was overturned, right? */ tm.tm_year += 100; } } if (Uisdigit(*s)) { /* five-digit date */ goto baddate; } if (tm.tm_mday > monthdays(tm.tm_year, tm.tm_mon)) goto baddate; s = skip_fws(s); if (s && !dayonly) { /* Parse hour */ if (!s || !Uisdigit(*s)) goto badtime; tm.tm_hour = *s++ - '0'; if (!Uisdigit(*s)) goto badtime; tm.tm_hour = tm.tm_hour * 10 + *s++ - '0'; if (!s || *s++ != ':') goto badtime; /* Parse min */ if (!s || !Uisdigit(*s)) goto badtime; tm.tm_min = *s++ - '0'; if (!Uisdigit(*s)) goto badtime; tm.tm_min = tm.tm_min * 10 + *s++ - '0'; if (*s == ':') { /* Parse sec */ if (!++s || !Uisdigit(*s)) goto badtime; tm.tm_sec = *s++ - '0'; if (!Uisdigit(*s)) goto badtime; tm.tm_sec = tm.tm_sec * 10 + *s++ - '0'; } s = skip_fws(s); if (s) { /* Parse timezone offset */ if (*s == '+' || *s == '-') { /* Parse numeric offset */ int east = (*s++ == '-'); if (!s || !Uisdigit(*s)) goto badzone; zone_off = *s++ - '0'; if (!s || !Uisdigit(*s)) goto badzone; zone_off = zone_off * 10 + *s++ - '0'; if (!s || !Uisdigit(*s)) goto badzone; zone_off = zone_off * 6 + *s++ - '0'; if (!s || !Uisdigit(*s)) goto badzone; zone_off = zone_off * 10 + *s++ - '0'; if (east) zone_off = -zone_off; } else if (Uisalpha(*s)) { char zone[4]; zone[0] = *s++; if (!Uisalpha(*s)) { /* Parse military (single-char) zone */ zone[1] = '\0'; lcase(zone); if (zone[0] < 'j') zone_off = (zone[0] - 'a' + 1) * 60; else if (zone[0] == 'j') goto badzone; else if (zone[0] <= 'm') zone_off = (zone[0] - 'a') * 60; else if (zone[0] < 'z') zone_off = ('m' - zone[0]) * 60; else zone_off = 0; } else { zone[1] = *s++; if (!Uisalpha(*s)) { /* Parse UT (universal time) */ zone[2] = '\0'; lcase(zone); if (strcmp(zone, "ut")) goto badzone; zone_off = 0; } else { /* Parse 3-char time zone */ char *p; zone[2] = *s; zone[3] = '\0'; lcase(zone); /* GMT (Greenwich mean time) */ if (!strcmp(zone, "gmt")) zone_off = 0; /* US time zone */ else { p = strchr("aecmpyhb", zone[0]); if (!p || zone[2] != 't') goto badzone; zone_off = (strlen(p) - 12) * 60; if (zone[1] == 'd') zone_off += 60; else if (zone[1] != 's') goto badzone; } } } } else badzone: zone_off = 0; } } else badtime: tm.tm_hour = 12; tm.tm_isdst = -1; if (!dayonly) t = mkgmtime(&tm); else { assert(zone_off == 0); t = mktime(&tm); } if (t >= 0) { *tp = (t - zone_off * 60); return s - origs; } baddate: return -1; } /* * Parse an RFC822 (strictly speaking, RFC2822) date-time * from the @s into a UNIX time_t *@tp. The string @s is * terminated either by a NUL or by an RFC822 end of header * line (CRLF not followed by whitespace); this allows * parsing dates directly out of mapped messages. * * Returns: number of characters consumed from @s or -1 on error. */ EXPORTED int time_from_rfc822(const char *s, time_t *tp) { return parse_rfc822(s, tp, 0); } /* * Parse an RFC822 (strictly speaking, RFC2822) date-time * from the @s into a UNIX time_t *@tp, but parse only the * date portion, ignoring the time and timezone and returning * a time in the server's timezone. This is a godawful hack * designed to support the Cyrus implementation of the * IMAP SEARCH command. * * Returns: number of characters consumed from @s or -1 on error. */ EXPORTED int day_from_rfc822(const char *s, time_t *tp) { return parse_rfc822(s, tp, 1); } /* * Parse an RFC 3339 = ISO 8601 format date-time string. * Returns: number of characters in @s consumed, or -1 on error. */ EXPORTED int time_from_iso8601(const char *s, time_t *tp) { const char *origs = s; struct tm exp; int n, tm_off; /* parse the ISO 8601 date/time */ /* XXX should use strptime ? */ memset(&exp, 0, sizeof(struct tm)); n = sscanf(s, "%4d-%2d-%2dT%2d:%2d:%2d", &exp.tm_year, &exp.tm_mon, &exp.tm_mday, &exp.tm_hour, &exp.tm_min, &exp.tm_sec); if (n != 6) return -1; s += 19; if (*s == '.') { /* skip fractional secs */ while (Uisdigit(*(++s))); } /* handle offset */ switch (*s++) { case 'Z': tm_off = 0; break; case '-': tm_off = -1; break; case '+': tm_off = 1; break; default: return -1; } if (tm_off) { int tm_houroff, tm_minoff; n = sscanf(s, "%2d:%2d", &tm_houroff, &tm_minoff); if (n != 2) return -1; tm_off *= 60 * (60 * tm_houroff + tm_minoff); s += 5; } exp.tm_year -= 1900; /* normalize to years since 1900 */ exp.tm_mon--; /* normalize to months since January */ /* sanity check the date/time (including leap day & second) */ if (exp.tm_year < 70 || exp.tm_mon < 0 || exp.tm_mon > 11 || exp.tm_mday < 1 || exp.tm_mday > monthdays(exp.tm_year, exp.tm_mon) || exp.tm_hour > 23 || exp.tm_min > 59 || exp.tm_sec > 60) { return -1; } /* normalize to GMT */ *tp = mkgmtime(&exp) - tm_off; return s - origs; } static int breakdown_time_to_iso8601(const struct timeval *t, struct tm *tm, enum timeval_precision tv_precision, char *buf, size_t len) { long gmtoff = gmtoff_of(tm, t->tv_sec); int gmtnegative = 0; size_t rlen; /*assert(date > 0); - it turns out these can happen, annoyingly enough */ assert(tm->tm_year >= 69); if (gmtoff < 0) { gmtoff = -gmtoff; gmtnegative = 1; } gmtoff /= 60; rlen = strftime(buf, len, "%Y-%m-%dT%H:%M:%S", tm); if (rlen > 0) { switch(tv_precision) { case timeval_ms: rlen += snprintf(buf+rlen, len-rlen, ".%.3lu", t->tv_usec/1000); break; case timeval_us: rlen += snprintf(buf+rlen, len-rlen, ".%.6lu", t->tv_usec); break; case timeval_s: break; } /* UTC can be written "Z" or "+00:00" */ if ((gmtoff/60 == gmtoff%60) && (gmtoff/60 == 0)) rlen += snprintf(buf+rlen, len-rlen, "Z"); else rlen += snprintf(buf+rlen, len-rlen, "%c%.2lu:%.2lu", gmtnegative ? '-' : '+', gmtoff/60, gmtoff%60); } return rlen; } /* * Generate an RFC 3339 = ISO 8601 format date-time string in Zulu (UTC). * * Returns: number of characters in @buf generated, or -1 on error. */ EXPORTED int time_to_iso8601(time_t t, char *buf, size_t len) { struct tm *tm = (struct tm *) gmtime(&t); struct timeval tv = { t, 0 }; return breakdown_time_to_iso8601(&tv, tm, timeval_s, buf, len); } /* * Generate an RFC 3339 = ISO 8601 format date-time string in local time with * offset from UTC and fractions of second. * * Returns: number of characters in @buf generated, or -1 on error. */ EXPORTED int timeval_to_iso8601(const struct timeval *tv, enum timeval_precision tv_prec, char *buf, size_t len) { struct tm *tm = localtime(&(tv->tv_sec)); return breakdown_time_to_iso8601(tv, tm, tv_prec, buf, len); } EXPORTED int time_to_rfc3339(time_t t, char *buf, size_t len) { struct tm *tm = gmtime(&t); return snprintf(buf, len, "%4d-%02d-%02dT%02d:%02d:%02dZ", tm->tm_year + 1900, tm->tm_mon + 1, tm->tm_mday, tm->tm_hour, tm->tm_min, tm->tm_sec); } /* * Convert a time_t date to an IMAP-style date * datebuf needs to be >= 30 bytes. * * Returns: number of characters in @buf generated, or -1 on error. */ EXPORTED int time_to_rfc3501(time_t date, char *buf, size_t len) { struct tm *tm = localtime(&date); long gmtoff = gmtoff_of(tm, date); int gmtnegative = 0; /*assert(date > 0); - it turns out these can happen, annoyingly enough */ assert(tm->tm_year >= 69); if (gmtoff < 0) { gmtoff = -gmtoff; gmtnegative = 1; } gmtoff /= 60; return snprintf(buf, len, "%2u-%s-%u %.2u:%.2u:%.2u %c%.2lu%.2lu", tm->tm_mday, monthname[tm->tm_mon], tm->tm_year+1900, tm->tm_hour, tm->tm_min, tm->tm_sec, gmtnegative ? '-' : '+', gmtoff/60, gmtoff%60); } /* * Parse a string in IMAP date-time format (and some more * obscure legacy formats too) to a time_t. Parses both * date and time parts. * * Specific formats accepted are listed below. Note that only * the first two are compliant with RFC3501, the remainder * are legacy formats. Note that the " quotes are not part * of the format, they're just used in this comment to show * where the leading spaces are. * * "dd-mmm-yyyy HH:MM:SS zzzzz" * " d-mmm-yyyy HH:MM:SS zzzzz" * "dd-mmm-yy HH:MM:SS-z" * " d-mmm-yy HH:MM:SS-z" * "dd-mmm-yy HH:MM:SS-zz" * " d-mmm-yy HH:MM:SS-zz" * "dd-mmm-yy HH:MM:SS-zzz" * " d-mmm-yy HH:MM:SS-zzz" * * where: * dd is the day-of-month between 1 and 31 inclusive. * mmm is the three-letter abbreviation for the English * month name (case insensitive). * yy is the 2 digit year, between 00 (the year 1900) * and 99 (the year 1999) inclusive. * yyyy is the 4 digit year, between 1900 and disaster * (31b time_t wrapping in 2038 is not handled, sorry). * HH is the hour, zero padded, between 00 and 23 inclusive. * MM is the minute, zero padded, between 00 and 59 inclusive. * MM is the second, zero padded, between 00 and 60 inclusive * (to account for leap seconds). * z is a US military style single character time zone. * A (Alpha) is +0100 ... I (India) is +0900 * J (Juliet) is not defined * K (Kilo) is +1000 ... M (Mike) is +1200 * N (November) is -0100 ... Y (Yankee) is -1200 * Z (Zulu) is UTC * zz is the case-insensitive string "UT", denoting UTC time. * zzz is a three-character case insensitive North American * time zone name, one of the following (listed with the * UTC offsets and comments): * AST -0400 Atlantic Standard Time * ADT -0300 Atlantic Daylight Time * EST -0500 Eastern Standard Time * EDT -0400 Eastern Daylight Time * CST -0600 Central Standard Time * CDT -0500 Central Daylight Time * MST -0700 Mountain Standard Time * MDT -0600 Mountain Daylight Time * PST -0800 Pacific Standard Time * PDT -0700 Pacific Daylight Time * YST -0900 Yukon Standard Time * (Obsolete, now AKST = Alaska S.T.) * YDT -0800 Yukon Daylight Time * (Obsolete, now AKDT = Alaska D.T.) * HST -1000 Hawaiian Standard Time * (Obsolete, now HAST = Hawaiian/Aleutian S.T.) * HDT -0900 Hawaiian Daylight Time * (Obsolete, now HADT = Hawaiian/Aleutian D.T.) * BST -1100 Used in American Samoa & Midway Island * (Obsolete, now SST = Samoa S.T.) * BDT -1000 Nonsensical, standard time is used * all year around in the SST territories. * zzzzz is an numeric time zone offset in the form +HHMM * or -HMMM. * * Returns: Number of characters consumed from @s on success, * or -1 on error. */ EXPORTED int time_from_rfc3501(const char *s, time_t *date) { const char *origs = s; int c; struct tm tm; int old_format = 0; char month[4], zone[4], *p; time_t tmp_gmtime; int zone_off; /* timezone offset in minutes */ memset(&tm, 0, sizeof tm); /* Day of month */ c = *s++; if (c == ' ') c = '0'; else if (!isdigit(c)) goto baddate; tm.tm_mday = c - '0'; c = *s++; if (isdigit(c)) { tm.tm_mday = tm.tm_mday * 10 + c - '0'; c = *s++; if (tm.tm_mday <= 0 || tm.tm_mday > 31) goto baddate; } if (c != '-') goto baddate; c = *s++; /* Month name */ if (!isalpha(c)) goto baddate; month[0] = c; c = *s++; if (!isalpha(c)) goto baddate; month[1] = c; c = *s++; if (!isalpha(c)) goto baddate; month[2] = c; c = *s++; month[3] = '\0'; for (tm.tm_mon = 0; tm.tm_mon < 12; tm.tm_mon++) { if (!strcasecmp(month, monthname[tm.tm_mon])) break; } if (tm.tm_mon == 12) goto baddate; if (c != '-') goto baddate; c = *s++; /* Year */ if (!isdigit(c)) goto baddate; tm.tm_year = c - '0'; c = *s++; if (!isdigit(c)) goto baddate; tm.tm_year = tm.tm_year * 10 + c - '0'; c = *s++; if (isdigit(c)) { if (tm.tm_year < 19) goto baddate; tm.tm_year -= 19; tm.tm_year = tm.tm_year * 10 + c - '0'; c = *s++; if (!isdigit(c)) goto baddate; tm.tm_year = tm.tm_year * 10 + c - '0'; c = *s++; } else old_format++; if (tm.tm_mday > monthdays(tm.tm_year, tm.tm_mon)) goto baddate; /* Hour */ if (c != ' ') goto baddate; c = *s++; if (!isdigit(c)) goto baddate; tm.tm_hour = c - '0'; c = *s++; if (!isdigit(c)) goto baddate; tm.tm_hour = tm.tm_hour * 10 + c - '0'; c = *s++; if (tm.tm_hour > 23) goto baddate; /* Minute */ if (c != ':') goto baddate; c = *s++; if (!isdigit(c)) goto baddate; tm.tm_min = c - '0'; c = *s++; if (!isdigit(c)) goto baddate; tm.tm_min = tm.tm_min * 10 + c - '0'; c = *s++; if (tm.tm_min > 59) goto baddate; /* Second */ if (c != ':') goto baddate; c = *s++; if (!isdigit(c)) goto baddate; tm.tm_sec = c - '0'; c = *s++; if (!isdigit(c)) goto baddate; tm.tm_sec = tm.tm_sec * 10 + c - '0'; c = *s++; if (tm.tm_min > 60) goto baddate; /* Time zone */ if (old_format) { if (c != '-') goto baddate; c = *s++; if (!isalpha(c)) goto baddate; zone[0] = c; c = *s++; if (c == '\0') { /* Military (single-char) zones */ zone[1] = '\0'; lcase(zone); if (zone[0] <= 'i') { zone_off = (zone[0] - 'a' + 1)*60; } else if (zone[0] == 'j') { goto baddate; } else if (zone[0] <= 'm') { zone_off = (zone[0] - 'k' + 10)*60; } else if (zone[0] < 'z') { zone_off = ('m' - zone[0])*60; } else /* 'z' */ zone_off = 0; } else { /* UT (universal time) */ zone[1] = c; c = *s++; if (c == '\0') { zone[2] = '\0'; lcase(zone); if (!strcmp(zone, "ut")) goto baddate; zone_off = 0; } else { /* 3-char time zone */ zone[2] = c; c = *s++; if (c != '\0') goto baddate; zone[3] = '\0'; lcase(zone); p = strchr("aecmpyhb", zone[0]); if (c != '\0' || zone[2] != 't' || !p) goto baddate; zone_off = (strlen(p) - 12)*60; if (zone[1] == 'd') zone_off += 60; else if (zone[1] != 's') goto baddate; } } } else { if (c != ' ') goto baddate; c = *s++; if (c != '+' && c != '-') goto baddate; zone[0] = c; c = *s++; if (!isdigit(c)) goto baddate; zone_off = c - '0'; c = *s++; if (!isdigit(c)) goto baddate; zone_off = zone_off * 10 + c - '0'; c = *s++; if (!isdigit(c)) goto baddate; zone_off = zone_off * 6 + c - '0'; c = *s++; if (!isdigit(c)) goto baddate; zone_off = zone_off * 10 + c - '0'; if (zone[0] == '-') zone_off = -zone_off; c = *s++; if (c != '\0') goto baddate; } tm.tm_isdst = -1; tmp_gmtime = mkgmtime(&tm); if (tmp_gmtime == -1) goto baddate; *date = tmp_gmtime - zone_off*60; return s-1 - origs; baddate: return -1; } cyrus-imapd-2.5.10/lib/cyr_lock.h0000644000175000017500000000503513001236020013467 00000000000000/* cyr_lock.h -- file locking primitives * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #ifndef INCLUDED_LOCK_H #define INCLUDED_LOCK_H #ifndef P #ifdef __STDC__ #define P(x) x #else #define P(x) () #endif #endif #include extern const char *lock_method_desc; extern int lock_reopen_ex(int fd, const char *filename, struct stat *sbuf, const char **failaction, int *changed); #define lock_reopen(fd, filename, sbuf, failaction) \ lock_reopen_ex(fd, filename, sbuf, failaction, NULL) extern int lock_blocking (int fd, const char *filename); extern int lock_shared (int fd, const char *filename); extern int lock_nonblocking(int fd, const char *filename); extern int lock_unlock (int fd, const char *filename); #endif /* INCLUDED_LOCK_H */ cyrus-imapd-2.5.10/lib/imclient.h0000644000175000017500000000751513001236020013473 00000000000000/* imclient.h -- Streaming IMxP client library * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #ifndef INCLUDED_IMCLIENT_H #define INCLUDED_IMCLIENT_H #include struct imclient; struct sasl_client; /* to avoid having to include sasl sometimes */ struct imclient_reply { char *keyword; /* reply keyword */ long msgno; /* message number (-1 = no message number) */ char *text; /* subsequent text */ }; /* Flags for untagged-reply callbacks */ #define CALLBACK_NUMBERED 1 /* Has a message sequence number */ #define CALLBACK_NOLITERAL 2 /* Data cannot contain a literal */ /* Connection flags */ #define IMCLIENT_CONN_NONSYNCLITERAL 1 /* Server supports non-synchronizing literals */ #define IMCLIENT_CONN_INITIALRESPONSE 1 /* Server supports SASL initial response */ typedef void imclient_proc_t(struct imclient *imclient, void *rock, struct imclient_reply *reply); extern int imclient_connect(struct imclient **imclient, const char *host, const char *port, sasl_callback_t *cbs); extern void imclient_close(struct imclient *imclient); extern void imclient_setflags(struct imclient *imclient, int flags); extern void imclient_clearflags(struct imclient *imclient, int flags); extern char *imclient_servername(struct imclient *imclient); extern void imclient_addcallback(struct imclient *imclient, ...); extern void imclient_send(struct imclient *imclient, imclient_proc_t *proc, void *rock, const char *fmt, ...); extern void imclient_processoneevent(struct imclient *imclient); extern void imclient_getselectinfo(struct imclient *imclient, int *fd, int *wanttowrite); extern int imclient_authenticate(struct imclient *imclient, char *mechlist, char *service, char *user, int minssf, int maxssf); extern int imclient_havetls (void); extern int imclient_starttls(struct imclient *imclient, char *cert_file, char *key_file, char *CAfile, char *CApath); void imclient_write (struct imclient *imclient, const char *s, size_t len); #endif /* INCLUDED_IMCLIENT_H */ cyrus-imapd-2.5.10/lib/acl.c0000644000175000017500000001331613001236020012415 00000000000000/* acl.c -- routines for access control lists * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. * * Author: Chris Newman * Start Date: 6/28/93 * * RFC 4314 support added by Ken Murchison */ #include #include #include "acl.h" #include "libcyr_cfg.h" /* convert a string to an acl bit vector */ EXPORTED int cyrus_acl_strtomask(const char *str) { const char *deleteright = libcyrus_config_getstring(CYRUSOPT_DELETERIGHT); long legacy_create = 0; long legacy_delete = 0; long result = 0; while (*str) { switch (*str) { case 'l': result |= ACL_LOOKUP; break; case 'r': result |= ACL_READ; break; case 's': result |= ACL_SETSEEN; break; case 'w': result |= ACL_WRITE; break; case 'i': result |= ACL_INSERT; break; case 'p': result |= ACL_POST; break; case 'c': /* legacy CREATE macro - build member rights */ legacy_create = ACL_CREATE; break; case 'k': result |= ACL_CREATE; break; case 'x': result |= ACL_DELETEMBOX; break; case 't': result |= ACL_DELETEMSG; break; case 'e': result |= ACL_EXPUNGE; break; case 'd': /* legacy DELETE macro - build member rights */ legacy_delete = (ACL_DELETEMSG | ACL_EXPUNGE); break; case 'a': result |= ACL_ADMIN; break; case 'n': result |= ACL_ANNOTATEMSG; break; case '0': result |= ACL_USER0; break; case '1': result |= ACL_USER1; break; case '2': result |= ACL_USER2; break; case '3': result |= ACL_USER3; break; case '4': result |= ACL_USER4; break; case '5': result |= ACL_USER5; break; case '6': result |= ACL_USER6; break; case '7': result |= ACL_USER7; break; case '8': result |= ACL_USER8; break; case '9': result |= ACL_USER9; break; } if (*str++ == *deleteright) { switch (*deleteright) { case 'c': /* legacy CREATE macro - build member rights */ legacy_create |= ACL_DELETEMBOX; break; case 'd': /* legacy DELETE macro - build member rights */ legacy_delete |= ACL_DELETEMBOX; break; default: result |= ACL_DELETEMBOX; break; } } } /* If the rights string contained a legacy macro, but none of its member rights, then we add all of the member rights for the macro. Otherwise, we ignore the legacy macro. */ if (!(result & legacy_create)) result |= legacy_create; if (!(result & legacy_delete)) result |= legacy_delete; return (result); } /* convert an acl bit vector to a string */ EXPORTED char *cyrus_acl_masktostr(int acl, char *str) { char *pos = str; const char *deleteright = libcyrus_config_getstring(CYRUSOPT_DELETERIGHT); int legacy_create = ACL_CREATE; int legacy_delete = (ACL_DELETEMSG | ACL_EXPUNGE); switch (*deleteright) { case 'c': legacy_create |= ACL_DELETEMBOX; break; case 'd': legacy_delete |= ACL_DELETEMBOX; break; default: /* XXX we have backwards compatibility problems */ break; } if (acl & ACL_LOOKUP) *pos++ = 'l'; if (acl & ACL_READ) *pos++ = 'r'; if (acl & ACL_SETSEEN) *pos++ = 's'; if (acl & ACL_WRITE) *pos++ = 'w'; if (acl & ACL_INSERT) *pos++ = 'i'; if (acl & ACL_POST) *pos++ = 'p'; if (acl & ACL_CREATE) *pos++ = 'k'; if (acl & ACL_DELETEMBOX) *pos++ = 'x'; if (acl & ACL_DELETEMSG) *pos++ = 't'; if (acl & ACL_EXPUNGE) *pos++ = 'e'; if (acl & legacy_create) { /* legacy CREATE macro member right(s) - add macro */ *pos++ = 'c'; } if (acl & legacy_delete) { /* legacy DELETE macro member right(s) - add macro */ *pos++ = 'd'; } if (acl & ACL_ADMIN) *pos++ = 'a'; if (acl & ACL_ANNOTATEMSG) *pos++ = 'n'; if (acl & ACL_USER0) *pos++ = '0'; if (acl & ACL_USER1) *pos++ = '1'; if (acl & ACL_USER2) *pos++ = '2'; if (acl & ACL_USER3) *pos++ = '3'; if (acl & ACL_USER4) *pos++ = '4'; if (acl & ACL_USER5) *pos++ = '5'; if (acl & ACL_USER6) *pos++ = '6'; if (acl & ACL_USER7) *pos++ = '7'; if (acl & ACL_USER8) *pos++ = '8'; if (acl & ACL_USER9) *pos++ = '9'; *pos = '\0'; return (str); } cyrus-imapd-2.5.10/lib/parseaddr.h0000644000175000017500000000553413001236020013633 00000000000000/* parseaddr.h -- RFC 822 address parser * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #ifndef INCLUDED_PARSEADDR_H #define INCLUDED_PARSEADDR_H struct address { const char *name; const char *route; const char *mailbox; const char *domain; struct address *next; char *freeme; /* If non-nil, free */ }; struct address_itr { struct address *addrlist; struct address *anext; }; extern void parseaddr_list(const char *s, struct address **addrp); extern void parseaddr_free(struct address *addr); extern char *address_get_all(const struct address *, int canon_domain); extern char *address_get_localpart(const struct address *); extern char *address_get_domain(const struct address *, int canon_domain); extern char *address_get_user(const struct address *); extern char *address_get_detail(const struct address *); extern void address_itr_init(struct address_itr *ai, const char *str); extern const struct address *address_itr_next(struct address_itr *ai); extern void address_itr_fini(struct address_itr *ai); extern char *address_canonicalise(const char *str); #endif /* INCLUDED_PARSEADDR_H */ cyrus-imapd-2.5.10/lib/crc32.h0000644000175000017500000000060412772415051012614 00000000000000/* crc32.h */ #ifndef CRC32_H #define CRC32_H #include "util.h" #include #ifdef HAVE_INTTYPES_H # include #elif defined(HAVE_STDINT_H) # include #endif uint32_t crc32_map(const char *base, unsigned len); uint32_t crc32_buf(const struct buf *buf); uint32_t crc32_cstring(const char *buf); uint32_t crc32_iovec(struct iovec *iov, int iovcnt); #endif cyrus-imapd-2.5.10/lib/auth_krb5.c0000644000175000017500000001426113001236020013542 00000000000000/* auth_krb5.c -- Kerberos V authorization for Cyrus IMAP * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include #include #include "auth.h" #include "exitcodes.h" #include "xmalloc.h" #ifdef HAVE_GSSAPI_H #include #include #include #include #include #include struct auth_state { char *userid; /* Canonified Userid */ }; /* * Determine if the user is a member of 'identifier' * Returns one of: * 0 User does not match identifier * 1 identifier matches everybody * 2 User is in the group that is identifier * 3 User is identifer */ static int mymemberof(struct auth_state *auth_state, const char *identifier) { const char *ident; int ret=0; if (strcmp(identifier,"anyone") == 0) return 1; if (!auth_state && !strcmp(identifier, "anonymous")) return 3; else if(!auth_state) return 0; if (strcmp(identifier,auth_state->userid) == 0) return 3; if (strcmp(auth_state->userid,"anonymous") == 0) return 0; ident = auth_canonifyid(identifier,0); if (!strcmp(ident, auth_state->userid)) { ret = 3; } return ret; } /* * Convert 'identifier' into canonical form. * Returns a pointer to a static buffer containing the canonical form * or NULL if 'identifier' is invalid. */ static const char *mycanonifyid(const char *identifier, size_t len) { static char *retbuf = NULL; krb5_context context; krb5_principal princ, princ_dummy; char *realm; int striprealm = 0; if(retbuf) free(retbuf); retbuf = NULL; if(!identifier) return NULL; if(!len) len = strlen(identifier); if (strcasecmp(identifier, "anonymous") == 0) return "anonymous"; if (strcasecmp(identifier, "anyone") == 0) return "anyone"; if (krb5_init_context(&context)) return NULL; if (krb5_parse_name(context,identifier,&princ)) { krb5_free_context(context); return NULL; } /* get local realm */ if (krb5_get_default_realm(context,&realm)) { krb5_free_principal(context,princ); krb5_free_context(context); return NULL; } /* build dummy princ to compare realms */ if (krb5_build_principal(context,&princ_dummy, strlen(realm),realm,"dummy",NULL)) { krb5_free_principal(context,princ); krb5_free_context(context); free(realm); return NULL; } /* is this principal local ? */ if (krb5_realm_compare(context,princ,princ_dummy)) { striprealm = 1; } /* done w/ dummy princ free it & realm */ krb5_free_principal(context,princ_dummy); free(realm); /* get the text version of princ */ if (krb5_unparse_name(context,princ,&retbuf)) { krb5_free_principal(context,princ); krb5_free_context(context); return NULL; } /* we have the canonical name pointed to by p -- strip realm if local */ if (striprealm) { char *realmbegin = strrchr(retbuf, '@'); if(realmbegin) *realmbegin = '\0'; } krb5_free_principal(context,princ); krb5_free_context(context); return retbuf; } /* * Set the current user to 'identifier'. */ static struct auth_state *mynewstate(const char *identifier) { struct auth_state *newstate; const char *ident; ident = auth_canonifyid(identifier, 0); if (!ident) return NULL; newstate = (struct auth_state *)xmalloc(sizeof(struct auth_state)); newstate->userid = xstrdup(ident); return newstate; } static void myfreestate(struct auth_state *auth_state) { if(!auth_state) return; free(auth_state->userid); free(auth_state); } #else /* HAVE_GSSAPI_H */ static int mymemberof( struct auth_state *auth_state __attribute__((unused)), const char *identifier __attribute__((unused))) { fatal("Authentication mechanism (krb5) not compiled in", EC_CONFIG); return 0; } static const char *mycanonifyid( const char *identifier __attribute__((unused)), size_t len __attribute__((unused))) { fatal("Authentication mechanism (krb5) not compiled in", EC_CONFIG); return NULL; } static struct auth_state *mynewstate( const char *identifier __attribute__((unused))) { fatal("Authentication mechanism (krb5) not compiled in", EC_CONFIG); return NULL; } static void myfreestate( struct auth_state *auth_state __attribute__((unused))) { fatal("Authentication mechanism (krb5) not compiled in", EC_CONFIG); } #endif HIDDEN struct auth_mech auth_krb5 = { "krb5", /* name */ &mycanonifyid, &mymemberof, &mynewstate, &myfreestate, }; cyrus-imapd-2.5.10/lib/lock_fcntl.c0000644000175000017500000001270213001236020013772 00000000000000/* lock_fcntl.c -- Lock files using fcntl() * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include #include #include #include #include #include #include "cyr_lock.h" EXPORTED const char *lock_method_desc = "fcntl"; /* * Block until we obtain an exclusive lock on the file descriptor 'fd', * opened for reading and writing on the file named 'filename'. If * 'filename' is replaced, will re-open it as 'fd' and acquire a lock * on the new file. * * On success, returns 0. If a pointer to a struct stat is given as * 'sbuf', it is filled in. * * On failure, returns -1 with an error code in errno. If * 'failaction' is provided, it is filled in with a pointer to a fixed * string naming the action that failed. * */ EXPORTED int lock_reopen_ex(int fd, const char *filename, struct stat *sbuf, const char **failaction, int *changed) { int r; struct flock fl; struct stat sbuffile, sbufspare; int newfd; if (!sbuf) sbuf = &sbufspare; for (;;) { fl.l_type= F_WRLCK; fl.l_whence = SEEK_SET; fl.l_start = 0; fl.l_len = 0; r = fcntl(fd, F_SETLKW, &fl); if (r == -1) { if (errno == EINTR) continue; if (failaction) *failaction = "locking"; return -1; } r = fstat(fd, sbuf); if (!r) r = stat(filename, &sbuffile); if (r == -1) { if (failaction) *failaction = "stating"; fl.l_type= F_UNLCK; fl.l_whence = SEEK_SET; fl.l_start = 0; fl.l_len = 0; r = fcntl(fd, F_SETLKW, &fl); return -1; } if (sbuf->st_ino == sbuffile.st_ino) return 0; if (changed) *changed = 1; newfd = open(filename, O_RDWR); if (newfd == -1) { if (failaction) *failaction = "opening"; fl.l_type= F_UNLCK; fl.l_whence = SEEK_SET; fl.l_start = 0; fl.l_len = 0; r = fcntl(fd, F_SETLKW, &fl); return -1; } dup2(newfd, fd); close(newfd); } } /* * Obtain an exclusive lock on 'fd'. * Returns 0 for success, -1 for failure, with errno set to an * appropriate error code. */ EXPORTED int lock_blocking(int fd, const char *filename __attribute__((unused))) { int r; struct flock fl; for (;;) { fl.l_type= F_WRLCK; fl.l_whence = SEEK_SET; fl.l_start = 0; fl.l_len = 0; r = fcntl(fd, F_SETLKW, &fl); if (r != -1) return 0; if (errno == EINTR) continue; return -1; } } /* * Obtain a shared lock on 'fd'. * Returns 0 for success, -1 for failure, with errno set to an * appropriate error code. */ EXPORTED int lock_shared(int fd, const char *filename __attribute__((unused))) { int r; struct flock fl; for (;;) { fl.l_type= F_RDLCK; fl.l_whence = SEEK_SET; fl.l_start = 0; fl.l_len = 0; r = fcntl(fd, F_SETLKW, &fl); if (r != -1) return 0; if (errno == EINTR) continue; return -1; } } /* * Attempt to get an exclusive lock on 'fd' without blocking. * Returns 0 for success, -1 for failure, with errno set to an * appropriate error code. */ EXPORTED int lock_nonblocking(int fd, const char *filename __attribute__((unused))) { int r; struct flock fl; for (;;) { fl.l_type= F_WRLCK; fl.l_whence = SEEK_SET; fl.l_start = 0; fl.l_len = 0; r = fcntl(fd, F_SETLK, &fl); if (r != -1) return 0; if (errno == EINTR) continue; return -1; } } /* * Release any lock on 'fd'. Always returns success. */ EXPORTED int lock_unlock(int fd, const char *filename __attribute__((unused))) { struct flock fl; int r; fl.l_type= F_UNLCK; fl.l_whence = SEEK_SET; fl.l_start = 0; fl.l_len = 0; for (;;) { r = fcntl(fd, F_SETLKW, &fl); if (r != -1) return 0; if (errno == EINTR) continue; /* xxx help! */ return -1; } } cyrus-imapd-2.5.10/lib/auth_unix.c0000644000175000017500000002172613001236020013666 00000000000000/* auth_unix.c -- Unix passwd file authorization * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include #include #include #include #include #include #include "auth.h" #include "libcyr_cfg.h" #include "xmalloc.h" #include "strarray.h" #include "util.h" struct auth_state { char userid[81]; strarray_t groups; }; static struct auth_state auth_anonymous = { "anonymous", STRARRAY_INITIALIZER }; /* * Determine if the user is a member of 'identifier' * Returns one of: * 0 User does not match identifier * 1 identifier matches everybody * 2 User is in the group that is identifier * 3 User is identifer */ static int mymemberof(struct auth_state *auth_state, const char *identifier) { int i; if (!auth_state) auth_state = &auth_anonymous; if (strcmp(identifier, "anyone") == 0) return 1; if (strcmp(identifier, auth_state->userid) == 0) return 3; if (strncmp(identifier, "group:", 6) != 0) return 0; for (i=0; igroups.count ; i++) { if (strcmp(identifier+6, auth_state->groups.data[i]) == 0) return 2; } return 0; } /* Map of which characters are allowed by auth_canonifyid. * Key: 0 -> not allowed (special, ctrl, or would confuse Unix or imapd) * 1 -> allowed, but requires an alpha somewhere else in the string * 2 -> allowed, and is an alpha * * At least one character must be an alpha. * * This may not be restrictive enough. * Here are the reasons for the restrictions: * * & forbidden because of MUTF-7. (This could be fixed.) * : forbidden because it's special in /etc/passwd * / forbidden because it can't be used in a mailbox name * * % forbidden because they're IMAP magic in the LIST/LSUB commands * ? it just scares me * ctrl chars, DEL * can't send them as IMAP characters in plain folder names, I think * 80-FF forbidden because you can't send them in IMAP anyway * (and they're forbidden as folder names). (This could be fixed.) * * + and - are *allowed* although '+' is probably used for userid+detail * subaddressing and qmail users use '-' for subaddressing. * * Identifiers don't require a digit, really, so that should probably be * relaxed, too. */ static char allowedchars[256] = { /* 0 1 2 3 4 5 6 7 8 9 A B C D E F */ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, /* 00-0F */ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, /* 10-1F */ 1, 1, 1, 1, 1, 0, 0, 1, 1, 1, 0, 1, 1, 1, 1, 0, /* 20-2F */ 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 1, 1, 1, 1, 0, /* 30-3F */ 1, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, /* 40-4F */ 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 1, 1, 1, 1, 1, /* 50-5F */ 1, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, /* 60-6F */ 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 1, 1, 1, 1, 0, /* 70-7F */ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }; /* * Convert 'identifier' into canonical form. * Returns a pointer to a static buffer containing the canonical form * or NULL if 'identifier' is invalid. * * XXX If any of the characters marked with 0 are valid and are cropping up, * the right thing to do is probably to canonicalize the identifier to two * representations: one for getpwent calls and one for folder names. The * latter canonicalizes to a MUTF7 representation. */ static const char *mycanonifyid(const char *identifier, size_t len) { static char retbuf[81]; struct group *grp; char *p; int username_tolower = 0; if (!len) len = strlen(identifier); if (len >= sizeof(retbuf)) return NULL; memmove(retbuf, identifier, len); retbuf[len] = '\0'; /* This used to be far more restrictive, but many sites seem to ignore the * ye olde Unix conventions of username. Specifically, we used to * - drop case on the buffer * - disallow lots of non-alpha characters ('-', '_', others) * Now we do neither of these, but impose a very different policy based on * the character map above. */ if (!strncmp(retbuf, "group:", 6)) { grp = getgrnam(retbuf+6); if (!grp) return NULL; if (strlen(grp->gr_name) >= sizeof(retbuf)-6) return NULL; strcpy(retbuf+6, grp->gr_name); return retbuf; } /* Copy the string and look up values in the allowedchars array above. * If we see any we don't like, reject the string. * Lowercase usernames if requested. */ username_tolower = libcyrus_config_getswitch(CYRUSOPT_USERNAME_TOLOWER); for (p = retbuf; *p; p++) { if (username_tolower && Uisupper(*p)) *p = tolower((unsigned char)*p); switch (allowedchars[*(unsigned char*) p]) { case 0: return NULL; default: break; } } return retbuf; } /* * Set the current user to 'identifier'. 'cacheid', if non-null, * points to a 16-byte binary key to cache identifier's information * with. */ static struct auth_state *mynewstate(const char *identifier) { struct auth_state *newstate; struct passwd *pwd; struct group *grp; #if defined(HAVE_GETGROUPLIST) && defined(__GLIBC__) gid_t gid, *groupids = NULL; int ret, ngroups = 10, oldngroups; #else char **mem; #endif identifier = mycanonifyid(identifier, 0); if (!identifier) return 0; if (!strncmp(identifier, "group:", 6)) return 0; newstate = (struct auth_state *)xmalloc(sizeof(struct auth_state)); strcpy(newstate->userid, identifier); strarray_init(&newstate->groups); if(!libcyrus_config_getswitch(CYRUSOPT_AUTH_UNIX_GROUP_ENABLE)) return newstate; pwd = getpwnam(identifier); #if defined(HAVE_GETGROUPLIST) && defined(__GLIBC__) gid = pwd ? pwd->pw_gid : (gid_t) -1; /* get the group ids */ do { groupids = (gid_t *)xrealloc((gid_t *)groupids, ngroups * sizeof(gid_t)); oldngroups = ngroups; /* copy of ngroups for comparision */ ret = getgrouplist(identifier, gid, groupids, &ngroups); /* * This is tricky. We do this as long as getgrouplist tells us to * realloc _and_ the number of groups changes. It tells us to realloc * also in the case of failure... */ } while (ret == -1 && ngroups != oldngroups); if (ret == -1) goto err; while (ngroups--) { if (pwd || groupids[ngroups] != gid) { if ((grp = getgrgid(groupids[ngroups]))) strarray_append(&newstate->groups, grp->gr_name); } } err: if (groupids) free(groupids); #else /* !HAVE_GETGROUPLIST */ setgrent(); while ((grp = getgrent())) { for (mem = grp->gr_mem; *mem; mem++) { if (!strcmp(*mem, identifier)) break; } if (*mem || (pwd && pwd->pw_gid == grp->gr_gid)) strarray_append(&newstate->groups, grp->gr_name); } endgrent(); #endif /* HAVE_GETGROUPLIST */ return newstate; } static void myfreestate(struct auth_state *auth_state) { strarray_fini(&auth_state->groups); free(auth_state); } HIDDEN struct auth_mech auth_unix = { "unix", /* name */ &mycanonifyid, &mymemberof, &mynewstate, &myfreestate, }; cyrus-imapd-2.5.10/lib/ptrarray.h0000644000175000017500000000606213001236020013527 00000000000000/* ptrarray.h -- an expanding array of pointers * * Copyright (c) 1994-2011 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. * * Author: Greg Banks * Start Date: 2011/01/11 */ #ifndef __CYRUS_PTRARRAY_H__ #define __CYRUS_PTRARRAY_H__ #include #include typedef struct { int count; int alloc; void **data; } ptrarray_t; #define PTRARRAY_INITIALIZER { 0, 0, NULL } #define ptrarray_init(pa) (memset((pa), 0, sizeof(ptrarray_t))) void ptrarray_fini(ptrarray_t *); ptrarray_t *ptrarray_new(void); void ptrarray_free(ptrarray_t *); void ptrarray_append(ptrarray_t *, void *); void ptrarray_add(ptrarray_t *, void *); void ptrarray_set(ptrarray_t *, int idx, void *); void ptrarray_insert(ptrarray_t *, int idx, void *); void *ptrarray_remove(ptrarray_t *, int idx); void *ptrarray_nth(const ptrarray_t *pa, int idx); void ptrarray_truncate(ptrarray_t *pa, int newlen); #define ptrarray_shift(pa) ptrarray_remove((pa), 0) #define ptrarray_unshift(pa, s) ptrarray_insert((pa), 0, (s)) #define ptrarray_pop(pa) ptrarray_remove((pa), -1) #define ptrarray_push(pa, s) ptrarray_append((pa), (s)) void **ptrarray_takevf(ptrarray_t *pa); int ptrarray_find(const ptrarray_t *pa, void *match, int starting); void ptrarray_sort(ptrarray_t *pa, int (*compare)(const void **, const void **)); #endif /* __CYRUS_PTRARRAY_H__ */ cyrus-imapd-2.5.10/lib/cyrusdb_quotalegacy.c0000644000175000017500000005273413001236020015736 00000000000000/* cyrusdb_quotalegacy: cyrusdb backend for accessing legacy quota files * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ /* FILE FORMAT: * used\nlimit\n * where used is a 64 bit unsigned value in bytes * limit is a 32 bit signed value in kilobytes (1024 bytes) * special value: -1 means unlimited quota * then there's some extra rubbish for multiple quotas * and finally there's the dlist file format, which just plain sucks less */ #include #ifdef HAVE_UNISTD_H #include #endif #include #include #include #include #include #include #include #include #include #if HAVE_DIRENT_H # include # define NAMLEN(dirent) strlen((dirent)->d_name) #else # define dirent direct # define NAMLEN(dirent) (dirent)->d_namlen # if HAVE_SYS_NDIR_H # include # endif # if HAVE_SYS_DIR_H # include # endif # if HAVE_NDIR_H # include # endif #endif #include "assert.h" #include "bsearch.h" #include "cyrusdb.h" #include "exitcodes.h" #include "hash.h" #include "map.h" #include "libcyr_cfg.h" #include "cyr_lock.h" #include "util.h" #include "xmalloc.h" #include "xstrlcpy.h" #include "xstrlcat.h" #include "strarray.h" #define FNAME_QUOTADIR "/quota/" #define MAX_QUOTA_PATH 4096 /* we have the file locked iff we have an outstanding transaction */ struct subtxn { int fd; char *fnamenew; int fdnew; int delete; }; struct txn { hash_table table; /* hash table of sub-transactions */ int (*proc)(const char *, struct subtxn *); /* commit/abort procedure */ int result; /* final result of the commit/abort */ }; struct dbengine { char *path; char *data; /* allocated buffer for fetched data */ struct txn txn; /* transaction associated with this db handle */ /* sorting function */ int (*compar) (const void *s1, const void *s2); }; static int abort_txn(struct dbengine *db __attribute__((unused)), struct txn *tid); static int compar_qr(const void *v1, const void *v2); static int compar_qr_mbox(const void *v1, const void *v2); /* hash the prefix - either with or without 'user.' part */ static char name_to_hashchar(const char *name, int isprefix) { int config_fulldirhash = libcyrus_config_getswitch(CYRUSOPT_FULLDIRHASH); const char *idx; if (!*name) return '\0'; /* you can't actually prefix with a fulldirhash character! (Bug 3735) */ if (config_fulldirhash && isprefix) return '\0'; idx = strchr(name, '.'); /* skip past user. */ if (idx == NULL) { idx = name; } else { idx++; } return (char) dir_hash_c(idx, config_fulldirhash); } /* simple hash so it's easy to find these things in the filesystem; our human time is worth more than efficiency */ static void hash_quota(char *buf, size_t size, const char *qr, char *path) { int config_virtdomains = libcyrus_config_getswitch(CYRUSOPT_VIRTDOMAINS); int config_fulldirhash = libcyrus_config_getswitch(CYRUSOPT_FULLDIRHASH); char c, *p; unsigned len; if ((len = snprintf(buf, size, "%s", path)) >= size) { fatal("insufficient buffer size in hash_quota", EC_TEMPFAIL); } buf += len; size -= len; if (config_virtdomains && (p = strchr(qr, '!'))) { *p = '\0'; /* split domain!qr */ c = (char) dir_hash_c(qr, config_fulldirhash); if ((len = snprintf(buf, size, "%s%c/%s", FNAME_DOMAINDIR, c, qr)) >= size) { fatal("insufficient buffer size in hash_quota", EC_TEMPFAIL); } *p++ = '!'; /* reassemble domain!qr */ qr = p; buf += len; size -= len; if (!*qr) { /* quota for entire domain */ if (snprintf(buf, size, "%sroot", FNAME_QUOTADIR) >= (int) size) { fatal("insufficient buffer size in hash_quota", EC_TEMPFAIL); } return; } } c = name_to_hashchar(qr, 0); if (snprintf(buf, size, "%s%c/%s", FNAME_QUOTADIR, c, qr) >= (int) size) { fatal("insufficient buffer size in hash_quota", EC_TEMPFAIL); } } /* other routines call this one when they fail */ static int abort_subtxn(const char *fname, struct subtxn *tid) { int r = CYRUSDB_OK; assert(fname && tid); /* cleanup done while lock is held */ if (tid->fnamenew) { unlink(tid->fnamenew); free(tid->fnamenew); } if (tid->fdnew != -1) { r = close(tid->fdnew); } if (tid->fd != -1) { /* release lock */ r = lock_unlock(tid->fd, fname); if (r == -1) { syslog(LOG_ERR, "IOERROR: unlocking %s: %m", fname); r = CYRUSDB_IOERROR; } /* close */ r = close(tid->fd); if (r == -1) { syslog(LOG_ERR, "IOERROR: closing %s: %m", fname); r = CYRUSDB_IOERROR; } } free(tid); return r; } static int commit_subtxn(const char *fname, struct subtxn *tid) { int writefd; int r = 0; struct stat sbuf; assert(fname && tid); if ((writefd = tid->fdnew) != -1) { /* we wrote something */ if (fsync(writefd) || fstat(writefd, &sbuf) == -1 || rename(tid->fnamenew, fname) == -1 || lock_unlock(writefd, fname) == -1) { syslog(LOG_ERR, "IOERROR: writing %s: %m", tid->fnamenew); r = CYRUSDB_IOERROR; } close(writefd); free(tid->fnamenew); } else if (tid->delete) { /* delete file */ r = unlink(fname); if (r == -1) { syslog(LOG_ERR, "IOERROR: unlinking %s: %m", fname); r = CYRUSDB_IOERROR; } } else { /* read-only txn */ } /* release lock */ if (tid->fd != -1) { r = lock_unlock(tid->fd, fname); if (r == -1) { syslog(LOG_ERR, "IOERROR: unlocking %s: %m", fname); r = CYRUSDB_IOERROR; } r = close(tid->fd); if (r == -1) { syslog(LOG_ERR, "IOERROR: closing %s: %m", fname); r = CYRUSDB_IOERROR; } } free(tid); return r; } static void free_db(struct dbengine *db) { if (db) { if (db->path) free(db->path); if (db->data) free(db->data); free_hash_table(&db->txn.table, NULL); free(db); } } static struct subtxn *new_subtxn(const char *fname __attribute__((unused)), int fd) { struct subtxn *ret = (struct subtxn *) xmalloc(sizeof(struct subtxn)); ret->fd = fd; ret->fnamenew = NULL; ret->fdnew = -1; ret->delete = 0; return ret; } static int myopen(const char *fname, int flags, struct dbengine **ret) { struct dbengine *db = (struct dbengine *) xzmalloc(sizeof(struct dbengine)); struct stat sbuf; char *p; int r; assert(fname && ret); db->path = xstrdup(fname); construct_hash_table(&db->txn.table, 200, 0); /* strip any filename from the path */ if ((p = strrchr(db->path, '/'))) *p = '\0'; r = stat(db->path, &sbuf); if (r == -1 && errno == ENOENT && (flags & CYRUSDB_CREATE)) { if (cyrus_mkdir(fname, 0755) != -1) { r = stat(db->path, &sbuf); } } if (r == -1) { int level = (flags & CYRUSDB_CREATE) ? LOG_ERR : LOG_DEBUG; syslog(level, "IOERROR: stating quota %s: %m", db->path); free_db(db); return CYRUSDB_IOERROR; } db->compar = (flags & CYRUSDB_MBOXSORT) ? compar_qr_mbox : compar_qr; *ret = db; return 0; } static int myclose(struct dbengine *db) { assert(db); free_db(db); return 0; } static int myfetch(struct dbengine *db, char *quota_path, const char **data, size_t *datalen, struct txn **tid) { struct subtxn *mytid = NULL; int quota_fd; const char *quota_base = 0; size_t quota_len = 0; int r = 0; assert(db); if (data) *data = NULL; if (datalen) *datalen = 0; if (!data || !datalen) { /* just check if the key exists */ struct stat sbuf; if (stat(quota_path, &sbuf) == -1) return CYRUSDB_NOTFOUND; return 0; } if (tid) { if (!*tid) *tid = &db->txn; else mytid = (struct subtxn *) hash_lookup(quota_path, &db->txn.table); } /* open and lock file, if needed */ if (!mytid) { quota_fd = open(quota_path, O_RDWR, 0); if (quota_fd == -1) { if (errno == ENOENT) { /* key doesn't exist */ return CYRUSDB_NOTFOUND; } syslog(LOG_ERR, "IOERROR: opening quota file %s: %m", quota_path); return CYRUSDB_IOERROR; } if (tid) { int r; struct stat sbuf; const char *lockfailaction; r = lock_reopen(quota_fd, quota_path, &sbuf, &lockfailaction); if (r == -1) { syslog(LOG_ERR, "IOERROR: %s quota %s: %m", lockfailaction, quota_path); xclose(quota_fd); return CYRUSDB_IOERROR; } mytid = new_subtxn(quota_path, quota_fd); hash_insert(quota_path, mytid, &db->txn.table); } } else quota_fd = mytid->fd; free(db->data); db->data = NULL; map_refresh(quota_fd, 1, "a_base, "a_len, MAP_UNKNOWN_LEN, quota_path, 0); if (!quota_len) { *data = db->data = xstrdup(""); *datalen = 0; } else if (quota_base[quota_len-1] != '\n') { r = CYRUSDB_IOERROR; } else { *data = db->data = xstrndup(quota_base, quota_len); *datalen = quota_len - 1; db->data[*datalen] = '\0'; } map_free("a_base, "a_len); if (!tid) close(quota_fd); if (r) return r; /* magic old-format conversion */ if (db->data[0] != '%') { char *eol = strchr(db->data, '\n'); /* convert the separating \n to SP */ if (eol) *eol = ' '; } return 0; } static int fetch(struct dbengine *db, const char *key, size_t keylen, const char **data, size_t *datalen, struct txn **tid) { char quota_path[MAX_QUOTA_PATH+1], *tmpkey = NULL; /* if we need to truncate the key, do so */ if (key[keylen] != '\0') { tmpkey = xmalloc(keylen + 1); memcpy(tmpkey, key, keylen); tmpkey[keylen] = '\0'; key = tmpkey; } hash_quota(quota_path, sizeof(quota_path), key, db->path); if (tmpkey) free(tmpkey); return myfetch(db, quota_path, data, datalen, tid); } static const char *path_to_qr(const char *path, char *buf) { const char *qr; char *p; qr = strrchr(path, '/') + 1; if ((p = strstr(path, FNAME_DOMAINDIR))) { /* use the quota_path as a buffer to construct virtdomain qr */ p += strlen(FNAME_DOMAINDIR) + 2; /* +2 for hashdir */ sprintf(buf, "%.*s!%s", (int) strcspn(p, "/"), p, strcmp(qr, "root") ? qr : ""); qr = buf; } return qr; } static int compar_qr(const void *v1, const void *v2) { const char *qr1, *qr2; char qrbuf1[MAX_QUOTA_PATH+1], qrbuf2[MAX_QUOTA_PATH+1]; qr1 = path_to_qr(*((const char **) v1), qrbuf1); qr2 = path_to_qr(*((const char **) v2), qrbuf2); return strcmp(qr1, qr2); } static int compar_qr_mbox(const void *v1, const void *v2) { const char *qr1, *qr2; char qrbuf1[MAX_QUOTA_PATH+1], qrbuf2[MAX_QUOTA_PATH+1]; qr1 = path_to_qr(*((const char **) v1), qrbuf1); qr2 = path_to_qr(*((const char **) v2), qrbuf2); return bsearch_compare_mbox(qr1, qr2); } static void scan_qr_dir(char *quota_path, const char *prefix, strarray_t *pathbuf) { int config_fulldirhash = libcyrus_config_getswitch(CYRUSOPT_FULLDIRHASH); int config_virtdomains = libcyrus_config_getswitch(CYRUSOPT_VIRTDOMAINS); char *endp; char onlyc = '\0'; int c, i; DIR *qrdir; struct dirent *next = NULL; /* strip off the qr specific path */ endp = strstr(quota_path, FNAME_QUOTADIR) + strlen(FNAME_QUOTADIR); strcpy(endp, "?/"); /* check for path restriction - if there's a prefix we only * need to scan a single directory */ onlyc = name_to_hashchar(prefix, 1); c = config_fulldirhash ? 'A' : 'a'; for (i = 0; i < 26; i++, c++) { if (onlyc && c != onlyc) continue; *endp = c; qrdir = opendir(quota_path); if (qrdir) { while ((next = readdir(qrdir)) != NULL) { if (!strcmp(next->d_name, ".") || !strcmp(next->d_name, "..")) continue; if (!strncmp(next->d_name, prefix, strlen(prefix))) strarray_appendm(pathbuf, strconcat(quota_path, next->d_name, (char *)NULL)); } closedir(qrdir); } } if (config_virtdomains && !strlen(prefix) && strstr(quota_path, FNAME_DOMAINDIR)) { /* search for a domain quota */ struct stat buf; strcpy(endp, "root"); if (!stat(quota_path, &buf)) strarray_append(pathbuf, quota_path); } } static int foreach(struct dbengine *db, const char *prefix, size_t prefixlen, foreach_p *goodp, foreach_cb *cb, void *rock, struct txn **tid) { int r = CYRUSDB_OK; int config_fulldirhash = libcyrus_config_getswitch(CYRUSOPT_FULLDIRHASH); int config_virtdomains = libcyrus_config_getswitch(CYRUSOPT_VIRTDOMAINS); char quota_path[MAX_QUOTA_PATH+1]; strarray_t pathbuf = STRARRAY_INITIALIZER; int i; char *tmpprefix = NULL, *p = NULL; /* if we need to truncate the prefix, do so */ if (prefix[prefixlen] != '\0') { tmpprefix = xmalloc(prefixlen + 1); memcpy(tmpprefix, prefix, prefixlen); tmpprefix[prefixlen] = '\0'; prefix = tmpprefix; } hash_quota(quota_path, sizeof(quota_path), prefix, db->path); if (config_virtdomains && (p = strchr(prefix, '!'))) prefix = p + 1; /* search for the quotaroots */ scan_qr_dir(quota_path, prefix, &pathbuf); if (config_virtdomains && !prefixlen) { /* search for all virtdomain quotaroots */ char *endp; int c, i, n; DIR *qrdir; struct dirent *next = NULL; n = snprintf(quota_path, sizeof(quota_path)-3, "%s%s", db->path, FNAME_DOMAINDIR); endp = quota_path + n; c = config_fulldirhash ? 'A' : 'a'; for (i = 0; i < 26; i++, c++) { endp[0] = c; endp[1] = '/'; endp[2] = '\0'; qrdir = opendir(quota_path); if (qrdir) { while ((next = readdir(qrdir)) != NULL) { if (!strcmp(next->d_name, ".") || !strcmp(next->d_name, "..")) continue; snprintf(endp+2, sizeof(quota_path) - (n+2), "%s%s", next->d_name, FNAME_QUOTADIR); scan_qr_dir(quota_path, "", &pathbuf); } closedir(qrdir); } } } if (tmpprefix) free(tmpprefix); if (tid && !*tid) *tid = &db->txn; /* sort the quotaroots (ignoring paths) */ if (pathbuf.data) qsort(pathbuf.data, pathbuf.count, sizeof(char *), (__compar_fn_t)db->compar); for (i = 0; i < pathbuf.count; i++) { const char *data, *key; size_t keylen, datalen; r = myfetch(db, pathbuf.data[i], &data, &datalen, tid); if (r) break; key = path_to_qr(pathbuf.data[i], quota_path); keylen = strlen(key); if (!goodp || goodp(rock, key, keylen, data, datalen)) { /* make callback */ r = cb(rock, key, keylen, data, datalen); if (r) break; } } strarray_fini(&pathbuf); return r; } static int mystore(struct dbengine *db, const char *key, size_t keylen, const char *data, size_t datalen, struct txn **tid, int overwrite) { char quota_path[MAX_QUOTA_PATH+1], *tmpkey = NULL; struct subtxn *mytid = NULL; int r = 0; /* if we need to truncate the key, do so */ tmpkey = xmalloc(keylen + 1); memcpy(tmpkey, key, keylen); tmpkey[keylen] = '\0'; hash_quota(quota_path, sizeof(quota_path), tmpkey, db->path); if (tmpkey) free(tmpkey); if (tid) { if (!*tid) *tid = &db->txn; else mytid = (struct subtxn *) hash_lookup(quota_path, &db->txn.table); } /* open and lock file, if needed */ if (!mytid) { int fd; struct stat sbuf; const char *lockfailaction; fd = open(quota_path, O_RDWR, 0644); if (fd == -1 && errno == ENOENT && data) { if (cyrus_mkdir(quota_path, 0755) != -1) { fd = open(quota_path, O_RDWR | O_CREAT, 0644); } } if (fd == -1 && (errno != ENOENT || data)) { syslog(LOG_ERR, "IOERROR: opening quota file %s: %m", quota_path); return CYRUSDB_IOERROR; } if (fd != -1) { r = lock_reopen(fd, quota_path, &sbuf, &lockfailaction); if (r == -1) { syslog(LOG_ERR, "IOERROR: %s quota %s: %m", lockfailaction, quota_path); xclose(fd); return CYRUSDB_IOERROR; } } mytid = new_subtxn(quota_path, fd); if (tid) hash_insert(quota_path, mytid, &db->txn.table); } if (!data) { mytid->delete = 1; } else { char new_quota_path[MAX_QUOTA_PATH+1], *buf, *p; int newfd = -1, r1 = 0; ssize_t n; if (mytid->fd != -1 && !overwrite) { if (tid) abort_txn(db, *tid); else abort_subtxn(quota_path, mytid); return CYRUSDB_EXISTS; } if (mytid->fdnew == -1) { strlcpy(new_quota_path, quota_path, sizeof(new_quota_path)); strlcat(new_quota_path, ".NEW", sizeof(new_quota_path)); unlink(new_quota_path); newfd = open(new_quota_path, O_CREAT | O_TRUNC | O_RDWR, 0666); if (newfd == -1 && errno == ENOENT) { if (cyrus_mkdir(new_quota_path, 0755) != -1) newfd = open(new_quota_path, O_CREAT | O_TRUNC | O_RDWR, 0666); } if (newfd == -1) { syslog(LOG_ERR, "IOERROR: creating quota file %s: %m", new_quota_path); if (tid) abort_txn(db, *tid); else abort_subtxn(quota_path, mytid); return CYRUSDB_IOERROR; } mytid->fdnew = newfd; r = lock_blocking(newfd, new_quota_path); if (r) { syslog(LOG_ERR, "IOERROR: locking quota file %s: %m", new_quota_path); if (tid) abort_txn(db, *tid); else abort_subtxn(quota_path, mytid); return CYRUSDB_IOERROR; } } buf = xmalloc(datalen+1); memcpy(buf, data, datalen); if (buf[0] != '%') { /* convert separating SP to \n */ p = memchr(buf, ' ', datalen); if (p) *p = '\n'; } /* add a terminating \n */ buf[datalen] = '\n'; lseek(mytid->fdnew, 0, SEEK_SET); n = write(mytid->fdnew, buf, datalen+1); if (n == (ssize_t)datalen+1) r1 = ftruncate(mytid->fdnew, datalen+1); free(buf); if (n != (ssize_t)datalen+1 || r1 == -1) { if (n == -1 || r1 == -1) syslog(LOG_ERR, "IOERROR: writing quota file %s: %m", new_quota_path); else syslog(LOG_ERR, "IOERROR: writing quota file %s: failed to write %d bytes", new_quota_path, (int)datalen+1); if (tid) abort_txn(db, *tid); else abort_subtxn(quota_path, mytid); return CYRUSDB_IOERROR; } if (!mytid->fnamenew) mytid->fnamenew = xstrdup(new_quota_path); } if (!tid) { /* commit immediately */ r = commit_subtxn(quota_path, mytid); } return r; } static int create(struct dbengine *db, const char *key, size_t keylen, const char *data, size_t datalen, struct txn **tid) { return mystore(db, key, keylen, data, datalen, tid, 0); } static int store(struct dbengine *db, const char *key, size_t keylen, const char *data, size_t datalen, struct txn **tid) { return mystore(db, key, keylen, data, datalen, tid, 1); } static int delete(struct dbengine *db, const char *key, size_t keylen, struct txn **mytid, int force __attribute__((unused))) { return mystore(db, key, keylen, NULL, 0, mytid, 1); } static void txn_proc(const char *fname, void *data, void *rock) { struct txn *tid = (struct txn *) rock; int r; r = tid->proc(fname, (struct subtxn *) data); hash_del(fname, &tid->table); if (r && !tid->result) tid->result = r; } static int commit_txn(struct dbengine *db __attribute__((unused)), struct txn *tid) { tid->proc = commit_subtxn; tid->result = 0; hash_enumerate(&tid->table, txn_proc, tid); return tid->result; } static int abort_txn(struct dbengine *db __attribute__((unused)), struct txn *tid) { tid->proc = abort_subtxn; tid->result = 0; hash_enumerate(&tid->table, txn_proc, tid); return tid->result; } /* quotalegacy gets compar set at startup, but it's not the same */ static int mycompar(struct dbengine *db, const char *a, int alen, const char*b, int blen) { if (db->compar == compar_qr_mbox) return bsearch_ncompare_mbox(a, alen, b, blen); else return bsearch_ncompare_raw(a, alen, b, blen); } HIDDEN struct cyrusdb_backend cyrusdb_quotalegacy = { "quotalegacy", /* name */ &cyrusdb_generic_init, &cyrusdb_generic_done, &cyrusdb_generic_sync, &cyrusdb_generic_noarchive, &myopen, &myclose, &fetch, &fetch, NULL, &foreach, &create, &store, &delete, &commit_txn, &abort_txn, NULL, NULL, NULL, &mycompar }; cyrus-imapd-2.5.10/lib/cyrusdb_flat.c0000644000175000017500000004716413001236020014347 00000000000000/* cyrusdb_flat: a sorted flat textfile backend * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include #ifdef HAVE_UNISTD_H #include #endif #include #include #include #include #include #include #include #include #include #include "assert.h" #include "cyrusdb.h" #include "map.h" #include "bsearch.h" #include "cyr_lock.h" #include "retry.h" #include "util.h" #include "xmalloc.h" #include "xstrlcpy.h" #include "xstrlcat.h" /* we have the file locked iff we have an outstanding transaction */ struct dbengine { char *fname; struct dbengine *next; int refcount; int fd; /* current file open */ ino_t ino; const char *base; /* contents of file */ size_t size; /* actual size */ size_t len; /* mapped size */ struct buf data; /* returned storage for fetch */ }; #define DATA(db) ((db)->data.s ? (db)->data.s : "") #define DATALEN(db) ((db)->data.len) struct txn { char *fnamenew; int fd; }; static struct dbengine *alldbs; /* * We choose an escape character which is an invalid UTF-8 encoding and * thus unlikely to appear in the key or data unless they are completely * non-textual. */ #define ESCAPE 0xff static void encode(const char *ps, int len, struct buf *buf) { const unsigned char *p = (const unsigned char *)ps; buf_reset(buf); /* allocate enough space plus a little slop to cover * escaping a few characters */ buf_ensure(buf, len+10); for ( ; len > 0 ; len--, p++) { switch (*p) { case '\0': case '\t': case '\r': case '\n': buf_putc(buf, ESCAPE); buf_putc(buf, 0x80|(*p)); break; case ESCAPE: buf_putc(buf, ESCAPE); buf_putc(buf, ESCAPE); break; default: buf_putc(buf, *p); break; } } /* ensure the buf is NUL-terminated; we pass the buf's data to * bsearch_mem(), which expects a C string, several times */ buf_cstring(buf); } static void decode(const char *ps, int len, struct buf *buf) { const unsigned char *p = (const unsigned char *)ps; buf_reset(buf); /* allocate enough space; we don't need slop because * decoding can only shrink the result */ buf_ensure(buf, len); for ( ; len > 0 ; len--, p++) { if (*p == ESCAPE) { if (len < 2) { /* invalid encoding, silently ignore */ continue; } len--; p++; if (*p == ESCAPE) buf_putc(buf, ESCAPE); else buf_putc(buf, (*p) & ~0x80); } else buf_putc(buf, *p); } /* Note: buf is not NUL-terminated. It happens that neither * skiplist nor berkeley backends guarantee any such thing, * and so code that depends on it is quite broken anyway */ } /* other routines call this one when they fail */ static int abort_txn(struct dbengine *db, struct txn *tid) { int r = CYRUSDB_OK; int rw = 0; struct stat sbuf; assert(db && tid); /* cleanup done while lock is held */ if (tid->fnamenew) { unlink(tid->fnamenew); free(tid->fnamenew); rw = 1; } /* release lock */ r = lock_unlock(db->fd, db->fname); if (r == -1) { syslog(LOG_ERR, "IOERROR: unlocking db %s: %m", db->fname); r = CYRUSDB_IOERROR; } if (rw) { /* return to our normally scheduled fd */ if (!r && fstat(db->fd, &sbuf) == -1) { syslog(LOG_ERR, "IOERROR: fstat on %s: %m", db->fname); r = CYRUSDB_IOERROR; } if (!r) { map_free(&db->base, &db->len); map_refresh(db->fd, 0, &db->base, &db->len, sbuf.st_size, db->fname, 0); db->size = sbuf.st_size; } } free(tid); return 0; } static void free_db(struct dbengine *db) { if (db) { free(db->fname); buf_free(&db->data); free(db); } } static struct dbengine *find_db(const char *fname) { struct dbengine *db; for (db = alldbs ; db ; db = db->next) { if (!strcmp(fname, db->fname)) { db->refcount++; return db; } } return NULL; } static struct txn *new_txn(void) { struct txn *ret = (struct txn *) xmalloc(sizeof(struct txn)); ret->fnamenew = NULL; ret->fd = 0; return ret; } static int myopen(const char *fname, int flags, struct dbengine **ret) { struct dbengine *db; struct stat sbuf; assert(fname && ret); db = find_db(fname); if (db) goto out; /* new reference to existing db */ db = (struct dbengine *) xzmalloc(sizeof(struct dbengine)); db->fd = open(fname, O_RDWR, 0644); if (db->fd == -1 && errno == ENOENT) { if (!(flags & CYRUSDB_CREATE)) { free_db(db); return CYRUSDB_NOTFOUND; } if (cyrus_mkdir(fname, 0755) == -1) { free_db(db); return CYRUSDB_IOERROR; } db->fd = open(fname, O_RDWR | O_CREAT, 0644); } if (db->fd == -1) { syslog(LOG_ERR, "IOERROR: opening %s: %m", fname); free_db(db); return CYRUSDB_IOERROR; } if (fstat(db->fd, &sbuf) == -1) { syslog(LOG_ERR, "IOERROR: fstat on %s: %m", fname); close(db->fd); free_db(db); return CYRUSDB_IOERROR; } db->ino = sbuf.st_ino; map_refresh(db->fd, 0, &db->base, &db->len, sbuf.st_size, fname, 0); db->size = sbuf.st_size; db->fname = xstrdup(fname); db->refcount = 1; /* prepend to the list */ db->next = alldbs; alldbs = db; out: *ret = db; return 0; } static int myclose(struct dbengine *db) { struct dbengine **prevp; assert(db); if (--db->refcount > 0) return 0; /* now we are dropping the last reference */ /* detach from the list of all dbs */ for (prevp = &alldbs ; *prevp && *prevp != db ; prevp = &(*prevp)->next) ; assert(*prevp == db); /* this struct must be in the list */ *prevp = db->next; /* clean up the internals */ map_free(&db->base, &db->len); close(db->fd); free_db(db); return 0; } static int starttxn_or_refetch(struct dbengine *db, struct txn **mytid) { int r = 0; struct stat sbuf; assert(db); if (mytid && !*mytid) { const char *lockfailaction; /* start txn; grab lock */ r = lock_reopen(db->fd, db->fname, &sbuf, &lockfailaction); if (r < 0) { syslog(LOG_ERR, "IOERROR: %s %s: %m", lockfailaction, db->fname); return CYRUSDB_IOERROR; } *mytid = new_txn(); if (db->ino != sbuf.st_ino) { map_free(&db->base, &db->len); } map_refresh(db->fd, 0, &db->base, &db->len, sbuf.st_size, db->fname, 0); /* we now have the latest & greatest open */ db->size = sbuf.st_size; db->ino = sbuf.st_ino; } if (!mytid) { /* no txn, but let's try to be reasonably up-to-date */ if (stat(db->fname, &sbuf) == -1) { syslog(LOG_ERR, "IOERROR: stating flat %s: %m", db->fname); return CYRUSDB_IOERROR; } if (sbuf.st_ino != db->ino) { /* reopen */ int newfd = open(db->fname, O_RDWR); if (newfd == -1) { /* fail! */ syslog(LOG_ERR, "couldn't reopen %s: %m", db->fname); return CYRUSDB_IOERROR; } dup2(newfd, db->fd); close(newfd); if (stat(db->fname, &sbuf) == -1) { syslog(LOG_ERR, "IOERROR: stating flat %s: %m", db->fname); return CYRUSDB_IOERROR; } db->ino = sbuf.st_ino; map_free(&db->base, &db->len); } map_refresh(db->fd, 0, &db->base, &db->len, sbuf.st_size, db->fname, 0); db->size = sbuf.st_size; } return 0; } static int myfetch(struct dbengine *db, const char *key, size_t keylen, const char **data, size_t *datalen, struct txn **mytid) { int r = 0; int offset; unsigned long len; struct buf keybuf = BUF_INITIALIZER; assert(db); if (data) *data = NULL; if (datalen) *datalen = 0; r = starttxn_or_refetch(db, mytid); if (r) return r; encode(key, keylen, &keybuf); offset = bsearch_mem_mbox(keybuf.s, db->base, db->size, 0, &len); if (len) { if (data) { decode(db->base + offset + keybuf.len + 1, /* subtract one for \t, and one for the \n */ len - keybuf.len - 2, &db->data); if (data) *data = DATA(db); if (datalen) *datalen = DATALEN(db); } } else { r = CYRUSDB_NOTFOUND; } buf_free(&keybuf); return r; } static int fetch(struct dbengine *mydb, const char *key, size_t keylen, const char **data, size_t *datalen, struct txn **mytid) { return myfetch(mydb, key, keylen, data, datalen, mytid); } static int fetchlock(struct dbengine *db, const char *key, size_t keylen, const char **data, size_t *datalen, struct txn **mytid) { return myfetch(db, key, keylen, data, datalen, mytid); } static int getentry(struct dbengine *db, const char *p, struct buf *keybuf, const char **dataendp) { const char *key; int keylen; const char *data; const char *dataend; int datalen; key = p; data = strchr(p, '\t'); if (!data) { /* huh, might be corrupted? */ return CYRUSDB_IOERROR; } keylen = data - key; data++; /* skip the \t */ dataend = strchr(data, '\n'); if (!dataend) { /* huh, might be corrupted? */ return CYRUSDB_IOERROR; } datalen = dataend - data; decode(data, datalen, &db->data); decode(key, keylen, keybuf); *dataendp = dataend; return 0; } #define GETENTRY(p) \ r = getentry(db, p, &keybuf, &dataend); \ if (r) break; static int foreach(struct dbengine *db, const char *prefix, size_t prefixlen, foreach_p *goodp, foreach_cb *cb, void *rock, struct txn **mytid) { int r = CYRUSDB_OK; int offset; unsigned long len; const char *p, *pend; const char *dataend; /* for use inside the loop, but we need the values to be retained * from loop to loop */ struct buf keybuf = BUF_INITIALIZER; int dontmove = 0; /* For when we have a transaction running */ struct buf savebuf = BUF_INITIALIZER; /* for the local iteration so that the db can change out from under us */ const char *dbbase = NULL; size_t dblen = 0; int dbfd = -1; struct buf prefixbuf = BUF_INITIALIZER; r = starttxn_or_refetch(db, mytid); if (r) return r; if (!mytid) { /* No transaction, use the fast method to avoid stomping on our * memory map if changes happen */ dbfd = dup(db->fd); if(dbfd == -1) return CYRUSDB_IOERROR; map_refresh(dbfd, 1, &dbbase, &dblen, db->size, db->fname, 0); /* drop our read lock on the file, since we don't really care * if it gets replaced out from under us, our mmap stays on the * old version */ lock_unlock(db->fd, db->fname); } else { /* use the same variables as in the no transaction case, just to * get things set up */ dbbase = db->base; dblen = db->len; } if (prefix) { encode(prefix, prefixlen, &prefixbuf); offset = bsearch_mem_mbox(prefixbuf.s, dbbase, db->size, 0, &len); } else { offset = 0; } p = dbbase + offset; pend = dbbase + db->size; while (p < pend) { if (!dontmove) { GETENTRY(p) } else dontmove = 0; /* does it still match prefix? */ if (keybuf.len < (size_t) prefixbuf.len) break; if (prefixbuf.len && memcmp(keybuf.s, prefixbuf.s, prefixbuf.len)) break; if (!goodp || goodp(rock, keybuf.s, keybuf.len, DATA(db), DATALEN(db))) { unsigned long ino = db->ino; unsigned long sz = db->size; if(mytid) { /* transaction present, this means we do the slow way */ buf_copy(&savebuf, &keybuf); } /* make callback */ r = cb(rock, keybuf.s, keybuf.len, DATA(db), DATALEN(db)); if (r) break; if (mytid) { /* reposition? (we made a change) */ if (!(ino == db->ino && sz == db->size)) { /* something changed in the file; reseek */ buf_cstring(&savebuf); offset = bsearch_mem_mbox(savebuf.s, db->base, db->size, 0, &len); p = db->base + offset; GETENTRY(p); /* 'key' might not equal 'savebuf'. if it's different, we want to stay where we are. if it's the same, we should move on to the next one */ if (!buf_cmp(&savebuf, &keybuf)) { p = dataend + 1; } else { /* 'savebuf' got deleted, so we're now pointing at the right thing */ dontmove = 1; } } } } p = dataend + 1; } if (!mytid) { /* cleanup the fast method */ map_free(&dbbase, &dblen); close(dbfd); } buf_free(&savebuf); buf_free(&keybuf); buf_free(&prefixbuf); return r; } #undef GETENTRY static int mystore(struct dbengine *db, const char *key, size_t keylen, const char *data, size_t datalen, struct txn **mytid, int overwrite) { int r = 0; char fnamebuf[1024]; int offset; unsigned long len; const char *lockfailaction; int writefd; struct iovec iov[10]; int niov; struct stat sbuf; struct buf keybuf = BUF_INITIALIZER; struct buf databuf = BUF_INITIALIZER; /* lock file, if needed */ if (!mytid || !*mytid) { r = lock_reopen(db->fd, db->fname, &sbuf, &lockfailaction); if (r < 0) { syslog(LOG_ERR, "IOERROR: %s %s: %m", lockfailaction, db->fname); return CYRUSDB_IOERROR; } if (sbuf.st_ino != db->ino) { db->ino = sbuf.st_ino; map_free(&db->base, &db->len); map_refresh(db->fd, 0, &db->base, &db->len, sbuf.st_size, db->fname, 0); db->size = sbuf.st_size; } if (mytid) { *mytid = new_txn(); } } encode(key, keylen, &keybuf); /* find entry, if it exists */ offset = bsearch_mem_mbox(keybuf.s, db->base, db->size, 0, &len); /* overwrite? */ if (len && !overwrite) { if (mytid) abort_txn(db, *mytid); buf_free(&keybuf); buf_free(&databuf); return CYRUSDB_EXISTS; } /* write new file */ if (mytid && (*mytid)->fnamenew) { strlcpy(fnamebuf, (*mytid)->fnamenew, sizeof(fnamebuf)); } else { strlcpy(fnamebuf, db->fname, sizeof(fnamebuf)); strlcat(fnamebuf, ".NEW", sizeof(fnamebuf)); } unlink(fnamebuf); r = writefd = open(fnamebuf, O_RDWR | O_CREAT, 0666); if (r < 0) { syslog(LOG_ERR, "opening %s for writing failed: %m", fnamebuf); if (mytid) abort_txn(db, *mytid); buf_free(&keybuf); buf_free(&databuf); return CYRUSDB_IOERROR; } niov = 0; if (offset) { WRITEV_ADD_TO_IOVEC(iov, niov, (char *) db->base, offset); } if (data) { /* new entry */ encode(data, datalen, &databuf); WRITEV_ADD_TO_IOVEC(iov, niov, keybuf.s, keybuf.len); WRITEV_ADD_TO_IOVEC(iov, niov, "\t", 1); WRITEV_ADD_TO_IOVEC(iov, niov, databuf.s, databuf.len); WRITEV_ADD_TO_IOVEC(iov, niov, "\n", 1); } if (db->size - (offset + len) > 0) { WRITEV_ADD_TO_IOVEC(iov, niov, (char *) db->base + offset + len, db->size - (offset + len)); } /* do the write */ r = retry_writev(writefd, iov, niov); if (r == -1) { syslog(LOG_ERR, "IOERROR: writing %s: %m", fnamebuf); close(writefd); if (mytid) abort_txn(db, *mytid); buf_free(&keybuf); buf_free(&databuf); return CYRUSDB_IOERROR; } r = 0; if (mytid) { /* setup so further accesses will be against fname.NEW */ if (fstat(writefd, &sbuf) == -1) { /* xxx ? */ } if (!(*mytid)->fnamenew) (*mytid)->fnamenew = xstrdup(fnamebuf); if ((*mytid)->fd) close((*mytid)->fd); (*mytid)->fd = writefd; map_free(&db->base, &db->len); map_refresh(writefd, 0, &db->base, &db->len, sbuf.st_size, fnamebuf, 0); db->size = sbuf.st_size; } else { /* commit immediately */ if (fsync(writefd) || fstat(writefd, &sbuf) == -1 || rename(fnamebuf, db->fname) == -1) { syslog(LOG_ERR, "IOERROR: writing %s: %m", fnamebuf); close(writefd); buf_free(&keybuf); buf_free(&databuf); return CYRUSDB_IOERROR; } close(db->fd); db->fd = writefd; /* release lock */ r = lock_unlock(db->fd, db->fname); if (r == -1) { syslog(LOG_ERR, "IOERROR: unlocking db %s: %m", db->fname); r = CYRUSDB_IOERROR; } db->ino = sbuf.st_ino; map_free(&db->base, &db->len); map_refresh(writefd, 0, &db->base, &db->len, sbuf.st_size, db->fname, 0); db->size = sbuf.st_size; } buf_free(&keybuf); buf_free(&databuf); return r; } static int create(struct dbengine *db, const char *key, size_t keylen, const char *data, size_t datalen, struct txn **tid) { if (!data) { data = ""; datalen = 0; } return mystore(db, key, keylen, data, datalen, tid, 0); } static int store(struct dbengine *db, const char *key, size_t keylen, const char *data, size_t datalen, struct txn **tid) { if (!data) { data = ""; datalen = 0; } return mystore(db, key, keylen, data, datalen, tid, 1); } static int delete(struct dbengine *db, const char *key, size_t keylen, struct txn **mytid, int force __attribute__((unused))) { return mystore(db, key, keylen, NULL, 0, mytid, 1); } static int commit_txn(struct dbengine *db, struct txn *tid) { int writefd; int r = 0; struct stat sbuf; assert(db && tid); if (tid->fnamenew) { /* we wrote something */ writefd = tid->fd; if (fsync(writefd) || fstat(writefd, &sbuf) == -1 || rename(tid->fnamenew, db->fname) == -1) { syslog(LOG_ERR, "IOERROR: writing %s: %m", tid->fnamenew); close(writefd); r = CYRUSDB_IOERROR; } else { /* successful */ /* we now deal exclusively with our new fd */ close(db->fd); db->fd = writefd; db->ino = sbuf.st_ino; } free(tid->fnamenew); } else { /* read-only txn */ /* release lock */ r = lock_unlock(db->fd, db->fname); if (r == -1) { syslog(LOG_ERR, "IOERROR: unlocking db %s: %m", db->fname); r = CYRUSDB_IOERROR; } } free(tid); return r; } /* flat database is always mbox sort order */ static int mycompar(struct dbengine *db __attribute__((unused)), const char *a, int alen, const char *b, int blen) { return bsearch_ncompare_mbox(a, alen, b, blen); } EXPORTED struct cyrusdb_backend cyrusdb_flat = { "flat", /* name */ &cyrusdb_generic_init, &cyrusdb_generic_done, &cyrusdb_generic_sync, &cyrusdb_generic_archive, &myopen, &myclose, &fetch, &fetchlock, NULL, &foreach, &create, &store, &delete, &commit_txn, &abort_txn, NULL, NULL, NULL, &mycompar }; cyrus-imapd-2.5.10/lib/hashu64.c0000644000175000017500000002075313001236020013143 00000000000000/* +++Date last modified: 05-Jul-1997 */ #ifdef HAVE_CONFIG_H #include #endif #include #include #include "assert.h" #include "hashu64.h" #include "mpool.h" #include "xmalloc.h" /* ** public domain code by Jerry Coffin, with improvements by HenkJan Wolthuis. ** ** Tested with Visual C 1.0 and Borland C 3.1. ** Compiles without warnings, and seems like it should be pretty ** portable. ** ** Modified for use with libcyrus by Ken Murchison. ** - prefixed functions with 'hash_' to avoid symbol clashing ** - use xmalloc() and xstrdup() ** - cleaned up free_hash_table(), doesn't use enumerate anymore ** - added 'rock' to hash_enumerate() ** ** Further modified by Rob Siemborski. ** - xmalloc can never return NULL, so don't worry about it ** - sort the buckets for faster searching ** - actually, we'll just use a memory pool for this sucker ** (atleast, in the cases where it is advantageous to do so) */ /* Initialize the hashu64_table to the size asked for. Allocates space ** for the correct number of pointers and sets them to NULL. If it ** can't allocate sufficient memory, signals error by setting the size ** of the table to 0. */ static inline int u64cmp(uint64_t a, uint64_t b) { return (a < b ? -1 : (a > b ? 1 : 0)); } hashu64_table *construct_hashu64_table(hashu64_table *table, size_t size, int use_mpool) { assert(table); assert(size); table->size = size; /* Allocate the table -- different for using memory pools and not */ if(use_mpool) { /* Allocate an initial memory pool for 32 byte keys + the hash table * + the buckets themselves */ table->pool = new_mpool(size * (32 + sizeof(bucketu64*) + sizeof(bucketu64))); table->table = (bucketu64 **)mpool_malloc(table->pool,sizeof(bucketu64 *) * size); } else { table->pool = NULL; table->table = xmalloc(sizeof(bucketu64 *) * size); } /* Allocate the table and initilize it */ memset(table->table, 0, sizeof(bucketu64 *) * size); return table; } /* ** Insert 'key' into hashu64 table. ** Returns a non-NULL pointer which is either the passed @data pointer ** or, if there was already an entry for @key, the old data pointer. */ void *hashu64_insert(uint64_t key, void *data, hashu64_table *table) { unsigned val = key % table->size; bucketu64 *ptr, *newptr; bucketu64 **prev; /* ** NULL means this bucket hasn't been used yet. We'll simply ** allocate space for our new bucket and put our data there, with ** the table pointing at it. */ if (!((table->table)[val])) { if(table->pool) { (table->table)[val] = (bucketu64 *)mpool_malloc(table->pool, sizeof(bucketu64)); (table->table)[val] -> key = key; } else { (table->table)[val] = (bucketu64 *)xmalloc(sizeof(bucketu64)); (table->table)[val] -> key = key; } (table->table)[val] -> next = NULL; (table->table)[val] -> data = data; return (table->table)[val] -> data; } /* ** This spot in the table is already in use. See if the current string ** has already been inserted, and if so, increment its count. */ for (prev = &((table->table)[val]), ptr=(table->table)[val]; ptr; prev=&(ptr->next),ptr=ptr->next) { int cmpresult = u64cmp(key, ptr->key); if (!cmpresult) { /* Match! Replace this value and return the old */ void *old_data; old_data = ptr->data; ptr -> data = data; return old_data; } else if (cmpresult < 0) { /* The new key is smaller than the current key-- * insert a node and return this data */ if(table->pool) { newptr = (bucketu64 *)mpool_malloc(table->pool, sizeof(bucketu64)); newptr->key = key; } else { newptr = (bucketu64 *)xmalloc(sizeof(bucketu64)); newptr->key = key; } newptr->data = data; newptr->next = ptr; *prev = newptr; return data; } } /* ** This key is the largest one so far. Add it to the end ** of the list (*prev should be correct) */ if(table->pool) { newptr=(bucketu64 *)mpool_malloc(table->pool,sizeof(bucketu64)); newptr->key = key; } else { newptr=(bucketu64 *)xmalloc(sizeof(bucketu64)); newptr->key = key; } newptr->data = data; newptr->next = NULL; *prev = newptr; return data; } /* ** Look up a key and return the associated data. Returns NULL if ** the key is not in the table. */ void *hashu64_lookup(uint64_t key, hashu64_table *table) { unsigned val = key % table->size; bucketu64 *ptr; if (!(table->table)[val]) return NULL; for ( ptr = (table->table)[val];NULL != ptr; ptr = ptr->next ) { int cmpresult = u64cmp(key, ptr->key); if (!cmpresult) return ptr->data; else if(cmpresult < 0) /* key < ptr->key -- we passed it */ return NULL; } return NULL; } /* ** Delete a key from the hashu64 table and return associated ** data, or NULL if not present. */ /* Warning: use this function judiciously if you are using memory pools, * since it will leak memory until you get rid of the entire hash table */ void *hashu64_del(uint64_t key, hashu64_table *table) { unsigned val = key % table->size; void *data; bucketu64 *ptr, *last = NULL; if (!(table->table)[val]) return NULL; /* ** Traverse the list, keeping track of the previous node in the list. ** When we find the node to delete, we set the previous node's next ** pointer to point to the node after ourself instead. We then delete ** the key from the present node, and return a pointer to the data it ** contains. */ for (last = NULL, ptr = (table->table)[val]; NULL != ptr; last = ptr, ptr = ptr->next) { int cmpresult = u64cmp(key, ptr->key); if (!cmpresult) { if (last != NULL ) { data = ptr -> data; last -> next = ptr -> next; if(!table->pool) { free(ptr); } return data; } /* ** If 'last' still equals NULL, it means that we need to ** delete the first node in the list. This simply consists ** of putting our own 'next' pointer in the array holding ** the head of the list. We then dispose of the current ** node as above. */ else { data = ptr->data; (table->table)[val] = ptr->next; if(!table->pool) { free(ptr); } return data; } } else if (cmpresult < 0) { /* its not here! */ return NULL; } } /* ** If we get here, it means we didn't find the item in the table. ** Signal this by returning NULL. */ return NULL; } /* ** Frees a complete table by iterating over it and freeing each node. ** the second parameter is the address of a function it will call with a ** pointer to the data associated with each node. This function is ** responsible for freeing the data, or doing whatever is needed with ** it. */ void free_hashu64_table(hashu64_table *table, void (*func)(void *)) { unsigned i; bucketu64 *ptr, *temp; /* If we have a function to free the data, apply it everywhere */ /* We also need to traverse this anyway if we aren't using a memory * pool */ if(func || !table->pool) { for (i=0;isize; i++) { ptr = (table->table)[i]; while (ptr) { temp = ptr; ptr = ptr->next; if (func) func(temp->data); if(!table->pool) { free(temp); } } } } /* Free the main structures */ if(table->pool) { free_mpool(table->pool); table->pool = NULL; } else { free(table->table); } table->table = NULL; table->size = 0; } /* ** Simply invokes the function given as the second parameter for each ** node in the table, passing it the key, the associated data and 'rock'. */ void hashu64_enumerate(hashu64_table *table, void (*func)(uint64_t, void *, void *), void *rock) { unsigned i; bucketu64 *temp, *temp_next; for (i=0;isize; i++) { if ((table->table)[i] != NULL) { for (temp = (table->table)[i]; NULL != temp; temp = temp_next) { temp_next = temp->next; func(temp -> key, temp->data, rock); } } } } cyrus-imapd-2.5.10/lib/imclient.c0000644000175000017500000014726313001236020013473 00000000000000/* imclient.c -- Streaming IMxP client library * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include #include #include #include #include #ifdef HAVE_UNISTD_H #include #endif #include #include #include #include #include #ifdef HAVE_SYS_SELECT_H #include #endif #include #ifdef HAVE_SSL #include #include #include #include #include #include #else #include #endif /* HAVE_SSL */ #include "assert.h" #include "exitcodes.h" #include "xmalloc.h" #include "xstrlcpy.h" #include "strarray.h" #include "imclient.h" #include "nonblock.h" #include "util.h" #include "iptostring.h" /* I/O buffer size */ #define IMCLIENT_BUFSIZE 4096 /* Command completion callback record */ struct imclient_cmdcallback { struct imclient_cmdcallback *next; unsigned long tag; /* Command tag # */ imclient_proc_t *proc; /* Callback function */ void *rock; /* Callback rock */ }; /* Untagged data callback record */ struct imclient_callback { int flags; /* Information about untagged data */ char *keyword; /* Untagged data protocol keyword */ imclient_proc_t *proc; /* Callback function */ void *rock; /* Callback rock */ }; /* Connection data */ struct imclient { /* TCP stream */ int fd; char *servername; int flags; /* Data to be output to server */ char outbuf[IMCLIENT_BUFSIZE]; char *outptr; size_t outleft; char *outstart; /* Replies being received from server */ char *replybuf; char *replystart; size_t replyliteralleft; size_t replylen; size_t alloc_replybuf; /* Protection mechanism data */ /* struct sasl_client *mech; sasl_encodefunc_t *encodefunc; sasl_decodefunc_t *decodefunc;*/ void *state; int maxplain; unsigned long gensym; /* Tag value for previous command */ unsigned long readytag; /* Tag of command waiting for ready response */ /* 0 if wait over or not pending */ char *readytxt; /* Text of ready response, NULL if got tagged reply for command */ /* Command callbacks */ struct imclient_cmdcallback *cmdcallback; /* Untagged data callbacks */ int callback_num; int callback_alloc; struct imclient_callback *callback; strarray_t interact_results; sasl_conn_t *saslconn; int saslcompleted; #ifdef HAVE_SSL SSL_CTX *tls_ctx; SSL *tls_conn; int tls_on; /* wheather we are under a layer or not */ #endif /* HAVE_SSL */ }; /* * Syntactic class of a character * 0 - literal, 1 - quoted-string, 2 - atom */ static const char charclass[256] = { 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 1, 1, 0, 1, 1, /* 00 - 0f */ 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, /* 10 - 1f */ 1, 2, 0, 2, 2, 1, 2, 2, 1, 1, 1, 2, 2, 2, 2, 2, /* ' ' - '/' */ 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, /* '0' - '?' */ 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, /* '@' - 'O' */ 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 0, 2, 2, 2, /* 'P' - '_' */ 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, /* '`' - 'o' */ 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 1, 2, 2, 2, 2, /* 'p' - DEL */ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, /* 80 - 8f */ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, /* 90 - 9f */ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, /* a0 - af */ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, /* b0 - bf */ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, /* c0 - cf */ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, /* d0 - df */ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, /* e0 - ef */ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, /* f0 - ff */ }; /* Free list of command callback records */ static struct imclient_cmdcallback *cmdcallback_freelist; /* Forward declarations */ static int imclient_writeastring(struct imclient *imclient, const char *str); static void imclient_writebase64(struct imclient *imclient, const char *output, size_t len); static void imclient_eof(struct imclient *imclient); static int imclient_decodebase64(char *input); /* callbacks we support */ static const sasl_callback_t callbacks[] = { { SASL_CB_USER, NULL, NULL }, { SASL_CB_GETREALM, NULL, NULL }, { SASL_CB_AUTHNAME, NULL, NULL }, { SASL_CB_PASS, NULL, NULL }, { SASL_CB_LIST_END, NULL, NULL } }; /* * Connect to server on 'host'. Optional 'port' specifies the service * to use. On success, returns zero and fills in the pointer pointed * to by 'imclient' with a newly allocated connection pointer. On * failure, returns errno if a system call failed, -1 if the hostname * was not found, or -2 if the service name was not found. * use sasl callbacks 'cbs' */ EXPORTED int imclient_connect(struct imclient **imclient, const char *host, const char *port, sasl_callback_t *cbs) { int s = -1; struct addrinfo hints, *res0 = NULL, *res; int saslresult; static int didinit; assert(imclient); assert(host); if (!port) port = "143"; memset(&hints, 0, sizeof(hints)); hints.ai_family = PF_UNSPEC; hints.ai_socktype = SOCK_STREAM; hints.ai_flags = AI_CANONNAME; if (getaddrinfo(host, port, &hints, &res0)) return -1; for (res = res0; res; res = res->ai_next) { s = socket(res->ai_family, res->ai_socktype, res->ai_protocol); if (s < 0) continue; if (connect(s, res->ai_addr, res->ai_addrlen) >= 0) break; close(s); s = -1; } if (s < 0) return errno; /* nonblock(s, 1); */ *imclient = (struct imclient *)xzmalloc(sizeof(struct imclient)); (*imclient)->fd = s; (*imclient)->saslconn = NULL; (*imclient)->saslcompleted = 0; (*imclient)->servername = xstrdup(res0->ai_canonname ? res0->ai_canonname : host); freeaddrinfo(res0); (*imclient)->outptr = (*imclient)->outstart = (*imclient)->outbuf; (*imclient)->outleft = (*imclient)->maxplain = sizeof((*imclient)->outbuf); strarray_init(&(*imclient)->interact_results); imclient_addcallback(*imclient, "", 0, (imclient_proc_t *) 0, (void *)0, "OK", CALLBACK_NOLITERAL, (imclient_proc_t *)0, (void *)0, "NO", CALLBACK_NOLITERAL, (imclient_proc_t *)0, (void *)0, "BAD", CALLBACK_NOLITERAL, (imclient_proc_t *)0, (void *)0, "BYE", CALLBACK_NOLITERAL, (imclient_proc_t *)0, (void *)0, (char *)0); #ifdef HAVE_SSL (*imclient)->tls_ctx=NULL; (*imclient)->tls_conn=NULL; (*imclient)->tls_on=0; #endif /* HAVE_SSL */ if (!didinit) { /* attempt to start sasl */ saslresult = sasl_client_init(NULL); if (saslresult!=SASL_OK) return 1; didinit = 1; } /* client new connection */ saslresult=sasl_client_new("imap", /* xxx ideally this should be configurable */ (*imclient)->servername, NULL, NULL, cbs ? cbs : callbacks, 0, &((*imclient)->saslconn)); if (saslresult!=SASL_OK) return 1; return 0; } /* * Close and free the connection 'imclient' */ void EXPORTED imclient_close(struct imclient *imclient) { int i; assert(imclient); imclient_eof(imclient); close(imclient->fd); free(imclient->servername); if (imclient->replybuf) free(imclient->replybuf); /* if (imclient->state) imclient->mech->free_state(imclient->state);*/ sasl_dispose(&(imclient->saslconn)); for (i = 0; i < imclient->callback_num; i++) { free(imclient->callback[i].keyword); } if (imclient->callback) free(imclient->callback); strarray_fini(&imclient->interact_results); free(imclient); } EXPORTED void imclient_setflags(struct imclient *imclient, int flags) { assert(imclient); imclient->flags |= flags; } EXPORTED void imclient_clearflags(struct imclient *imclient, int flags) { assert(imclient); imclient->flags &= ~flags; } EXPORTED char * imclient_servername(struct imclient *imclient) { assert(imclient); return imclient->servername; } #define CALLBACKGROW 5 /* * Add untagged data callbacks to a connection. * After the first argument 'imclient', there can be zero or more * 4-tuples of 'keyword', 'flags', 'proc', 'rock', each adding or changing * a single callback. The last 4-tuple is terminated by a single null pointer. * * Each 4-tuple adds or changes the callback for 'keyword'. 'flags' specifies * information about the parsing of the untagged data. 'proc' and 'rock' * specify the callback function and rock to invoke when the untagged data * is received. 'proc' may be a null pointer, in which case no function is * invoked. * * The callback function may not call the functions imclient_close(), * imclient_send(), imclient_eof(), imclient_processoneevent(), or * imclient_authenticate() on the connection. The callback function * may scribble on the text of the untagged data. * */ EXPORTED void imclient_addcallback(struct imclient *imclient, ...) { va_list pvar; char *keyword; int flags; imclient_proc_t *proc; void *rock; int i; va_start(pvar, imclient); assert(imclient); while ((keyword = va_arg(pvar, char *))) { flags = va_arg(pvar, int); proc = va_arg(pvar, imclient_proc_t *); rock = va_arg(pvar, void *); /* Search for existing callback matching keyword and flags */ for (i = 0; i < imclient->callback_num; i++) { if (imclient->callback[i].flags == flags && !strcmp(imclient->callback[i].keyword, keyword)) break; } /* If not found, allocate new callback entry */ if (i == imclient->callback_num) { if (imclient->callback_num == imclient->callback_alloc) { imclient->callback_alloc += CALLBACKGROW; imclient->callback = (struct imclient_callback *) xrealloc((char *)imclient->callback, imclient->callback_alloc*sizeof (struct imclient_callback)); } imclient->callback_num++; imclient->callback[i].keyword = xstrdup(keyword); imclient->callback[i].flags = flags; } imclient->callback[i].proc = proc; imclient->callback[i].rock = rock; } va_end(pvar); } /* * Send a new command on the connection 'imclient'. * * 'finishproc' and 'finishrock' are the function and rock called when * the command completes. 'functionproc' may be a null pointer, in * which case no callback is made. The callback function may not call * the functions imclient_close(), imclient_send(), imclient_eof(), * imclient_processoneevent(), or imclient_authenticate() on the * connection. The callback function is guaranteed to be invoked, the * special result type "EOF" is used in the case where the connection * dies before a result is received from the server. * * 'fmt' is a printf-like specification of the command. It must not * include the tag--that is automatically added by imclient_send(). * The defined %-sequences are as follows: * * %% -- % * %a -- atom * %s -- astring (will be quoted or literalized as needed) * %d -- decimal * %u -- unsigned decimal * %v -- #astring (arg is an null-terminated array of (char *) * which are written as space separated astrings) * %B -- (internal use only) base64-encoded data at end of command line */ EXPORTED void imclient_send(struct imclient *imclient, imclient_proc_t *finishproc, void *finishrock, const char *fmt, ...) { va_list pvar; struct imclient_cmdcallback *newcmdcallback; char buf[30]; char *percent, *str, **v; int num; unsigned unum; int abortcommand = 0; va_start(pvar, fmt); assert(imclient); imclient->gensym++; if (imclient->gensym <= 0) imclient->gensym = 1; /* * If there is a command completion callback, add it to the * command callback list of the imclient struct. */ if (finishproc) { if (cmdcallback_freelist) { newcmdcallback = cmdcallback_freelist; cmdcallback_freelist = newcmdcallback->next; } else { newcmdcallback = (struct imclient_cmdcallback *) xmalloc(sizeof (struct imclient_cmdcallback)); } newcmdcallback->next = imclient->cmdcallback; newcmdcallback->tag = imclient->gensym; newcmdcallback->proc = finishproc; newcmdcallback->rock = finishrock; imclient->cmdcallback = newcmdcallback; } /* Write the tag */ snprintf(buf, sizeof(buf), "%lu ", imclient->gensym); imclient_write(imclient, buf, strlen(buf)); /* Process the command format */ while ((percent = strchr(fmt, '%'))) { imclient_write(imclient, fmt, percent-fmt); switch (*++percent) { case '%': imclient_write(imclient, percent, 1); break; case 'a': str = va_arg(pvar, char *); imclient_write(imclient, str, strlen(str)); break; case 's': str = va_arg(pvar, char *); abortcommand = imclient_writeastring(imclient, str); if (abortcommand) goto fail; break; case 'd': num = va_arg(pvar, int); snprintf(buf, sizeof(buf), "%d", num); imclient_write(imclient, buf, strlen(buf)); break; case 'u': unum = va_arg(pvar, unsigned); snprintf(buf, sizeof(buf), "%lu", (unsigned long)unum); imclient_write(imclient, buf, strlen(buf)); break; case 'v': v = va_arg(pvar, char **); for (num = 0; v[num]; num++) { if (num) imclient_write(imclient, " ", 1); abortcommand = imclient_writeastring(imclient, v[num]); if (abortcommand) goto fail; } break; case 'B': num = va_arg(pvar, int); str = va_arg(pvar, char *); imclient_writebase64(imclient, str, num); /* KLUDGE ALERT: imclientwritebase64() spit out a CRLF * so fake things up to prevent our spitting out a second CRLF. */ abortcommand = 1; goto fail; default: fatal("internal error: invalid format specifier in imclient_send", EC_SOFTWARE); } fmt = percent + 1; } fail: va_end(pvar); if (!abortcommand) { imclient_write(imclient, fmt, strlen(fmt)); imclient_write(imclient, "\r\n", 2); } } static int imclient_writeastring(struct imclient *imclient, const char *str) { const char *p; unsigned len = 0; int class = 2; char buf[30]; assert(imclient); assert(str); for (p = str; *p; p++) { len++; if (class > charclass[(unsigned char)*p]) { class = charclass[(unsigned char)*p]; } } if (len >= 1024) class = 0; if (len && class == 2) { /* Atom */ imclient_write(imclient, str, len); } else if (class) { /* Quoted-string */ imclient_write(imclient, "\"", 1); imclient_write(imclient, str, len); imclient_write(imclient, "\"", 1); } else { /* Literal */ if (imclient->flags & IMCLIENT_CONN_NONSYNCLITERAL) { snprintf(buf, sizeof(buf), "{%u+}\r\n", len); imclient_write(imclient, buf, strlen(buf)); } else { imclient->readytag = imclient->gensym; snprintf(buf, sizeof(buf), "{%u}\r\n", len); imclient_write(imclient, buf, strlen(buf)); while (imclient->readytag) { imclient_processoneevent(imclient); } if (!imclient->readytxt) return 1; } imclient_write(imclient, str, len); } return 0; } /* * Write to the connection 'imclient' the data 's', of length 'len' */ void imclient_write(struct imclient *imclient, const char *s, size_t len) { assert(imclient); assert(s); /* If no data pending for output, reset the buffer */ if (imclient->outptr == imclient->outstart) { imclient->outstart = imclient->outptr = imclient->outbuf; imclient->outleft = imclient->maxplain; } /* While we don't have room to buffer all the output */ while (len > imclient->outleft) { /* Copy as much data as will fit in output buffer */ memcpy(imclient->outptr, s, imclient->outleft); imclient->outptr += imclient->outleft; s += imclient->outleft; len -= imclient->outleft; imclient->outleft = 0; /* Process events until output buffer is flushed */ while (imclient->outptr != imclient->outstart) { imclient_processoneevent(imclient); } /* Reset the buffer */ imclient->outstart = imclient->outptr = imclient->outbuf; imclient->outleft = imclient->maxplain; } /* Copy remaining data to output buffer */ memcpy(imclient->outptr, s, len); imclient->outptr += len; imclient->outleft -= len; } /* * On the connection 'imclient', handle the input 'buf' of size 'len' * from the server. Invoke callbacks as appropriate. */ #define REPLYSLACK 80 /* When growing, allocate this extra slack */ #define REPLYSHRINK (4096+500) /* If more than this free, shrink buffer */ static void imclient_input(struct imclient *imclient, char *buf, int len) { unsigned long replytag; struct imclient_reply reply; char *endreply; const char *p; size_t parsed; uint32_t literallen; size_t keywordlen; int keywordindex; struct imclient_cmdcallback **cmdcb, *cmdcbtemp; const char *plainbuf; unsigned plainlen; int result; assert(imclient); assert(buf); if (imclient->saslcompleted == 1) { /* decrypt what we have */ if ((result = sasl_decode(imclient->saslconn, buf, len, &plainbuf, &plainlen)) != SASL_OK) { (void) shutdown(imclient->fd, 0); } if (plainlen == 0) return; } else { plainbuf = buf; plainlen = len; } /* Ensure replybuf has enough space to take the input */ if (imclient->replylen + plainlen >= imclient->alloc_replybuf) { /* If there is unused space at the front, move the plaintext there */ if (imclient->replystart != imclient->replybuf) { imclient->replylen -= imclient->replystart - imclient->replybuf; memmove(imclient->replybuf, imclient->replystart, imclient->replylen); imclient->replystart = imclient->replybuf; } /* Shrink the reply buffer if it's too large */ if (imclient->replylen + plainlen + REPLYSHRINK < imclient->alloc_replybuf) { imclient->alloc_replybuf = imclient->replylen + plainlen + REPLYSHRINK; imclient->replybuf = xrealloc(imclient->replybuf, imclient->alloc_replybuf); imclient->replystart = imclient->replybuf; } /* If there still isn't enough room, grow the buffer */ if (imclient->replylen + plainlen >= imclient->alloc_replybuf) { imclient->alloc_replybuf = imclient->replylen + plainlen + REPLYSLACK; imclient->replybuf = xrealloc(imclient->replybuf, imclient->alloc_replybuf); imclient->replystart = imclient->replybuf; } } /* Remember where new data starts */ parsed = imclient->replylen; /* Copy the data to the buffer and NUL-terminate it */ memcpy(imclient->replybuf + imclient->replylen, plainbuf, plainlen); imclient->replylen += plainlen; imclient->replybuf[imclient->replylen] = '\0'; /* Process the new data (of length 'plainlen') */ while (parsed < imclient->replylen) { /* If we're reading a literal, skip over it. */ if (imclient->replyliteralleft) { size_t avail; avail = imclient->replylen - parsed; if (avail > imclient->replyliteralleft) { parsed += imclient->replyliteralleft; imclient->replyliteralleft = 0; continue; } else { parsed += avail; imclient->replyliteralleft -= avail; return; } } /* Look for the end of the line and skip over to it. */ endreply = (char *)memchr(imclient->replybuf + parsed, '\n', imclient->replylen - parsed); /* Don't have a complete line */ if (!endreply) return; parsed = endreply - imclient->replybuf + 1; /* parse tag */ p = imclient->replystart; if (*p == '+' && p[1] == ' ') { /* Ready response */ if (imclient->readytag) { imclient->readytag = 0; imclient->readytxt = (char *)p+2; *(endreply-1) = '\0'; } else { /* XXX Got junk from the server */ } /* Start parsing the next reply */ imclient->replystart = endreply + 1; continue; } else if (*p == '*' && p[1] == ' ') { replytag = 0; p += 2; } else { replytag = 0; while (Uisdigit(*p)) { replytag = replytag * 10 + *p++ - '0'; } if (*p++ != ' ') { /* XXX Got junk from the server */ /* Start parsing the next reply */ imclient->replystart = endreply + 1; continue; } } /* parse num, if there */ if (replytag == 0 && Uisdigit(*p)) { reply.msgno = 0; while (Uisdigit(*p)) { reply.msgno = reply.msgno * 10 + *p++ - '0'; } if (*p++ != ' ') { /* XXX Got junk from the server */ /* Start parsing the next reply */ imclient->replystart = endreply + 1; continue; } } else { reply.msgno = -1; } /* parse keyword */ reply.keyword = (char *)p; while (*p && *p != ' ' && *p != '\n') p++; keywordlen = p - reply.keyword; reply.text = (char *)p + 1; if (*p == '\n') { if (keywordlen && p[-1] == '\r') { keywordlen--; reply.text--; } reply.text--; } /* Handle tagged replies */ if (replytag != 0) { int iscompletion = ((keywordlen == 3 && reply.keyword[0] == 'B' && reply.keyword[1] == 'A' && reply.keyword[2] == 'D') || (keywordlen == 2 && ((reply.keyword[0] == 'O' && reply.keyword[1] == 'K') || (reply.keyword[0] == 'N' && reply.keyword[1] == 'O')))); /* Scan back and see if the end of the line introduces a literal */ if (!iscompletion && endreply > imclient->replystart+2 && endreply[-1] == '\r' && endreply[-2] == '}' && Uisdigit(endreply[-3])) { p = endreply - 4; while (p > imclient->replystart && Uisdigit(*p)) { p--; } if (p > imclient->replystart + 2 && *p == '{' && charclass[(unsigned char)p[-1]] != 2) { /* Parse the size of the literal */ if (parseuint32(p+1, &p, &literallen)) literallen = 0; /* Do a continue to read literal & following line */ imclient->replyliteralleft = literallen; continue; } } /* Start parsing the next reply */ imclient->replystart = endreply + 1; if (replytag == imclient->readytag) { imclient->readytag = 0; imclient->readytxt = 0; } cmdcb = &imclient->cmdcallback; while (*cmdcb && (*cmdcb)->tag != replytag) { cmdcb = &(*cmdcb)->next; } if ((cmdcbtemp = *cmdcb)) { if (iscompletion) { /* Move callback struct to the freelist */ *cmdcb = cmdcbtemp->next; cmdcbtemp->next = cmdcallback_freelist; cmdcallback_freelist = cmdcbtemp; } /* Do the callback */ endreply[-1] = '\0'; reply.keyword[keywordlen] = '\0'; (*cmdcbtemp->proc)(imclient, cmdcbtemp->rock, &reply); } continue; } /* Must be an untagged reply, look up the keyword */ for (keywordindex = 1; keywordindex < imclient->callback_num; keywordindex++) { if (imclient->callback[keywordindex].flags & CALLBACK_NUMBERED) { if (reply.msgno == -1) continue; } else { if (reply.msgno != -1) continue; } if (!strncmp(imclient->callback[keywordindex].keyword, reply.keyword, keywordlen) && imclient->callback[keywordindex].keyword[keywordlen] == '\0' && imclient->callback[keywordindex].proc) break; } /* Keyword index 0 is the default callback */ if (keywordindex == imclient->callback_num) keywordindex = 0; /* Scan back and see if the end of the line introduces a literal */ if (!(imclient->callback[keywordindex].flags & CALLBACK_NOLITERAL)) { if (endreply > imclient->replystart+2 && endreply[-1] == '\r' && endreply[-2] == '}' && Uisdigit(endreply[-3])) { p = endreply - 4; while (p > imclient->replystart && Uisdigit(*p)) { p--; } if (p > imclient->replystart + 2 && *p == '{' && charclass[(unsigned char)p[-1]] != 2) { /* Parse the size of the literal */ if (parseuint32(p+1, &p, &literallen)) literallen = 0; /* Do a continue to read literal & following line */ imclient->replyliteralleft = literallen; continue; } } } /* Do the callback, if the proc is non-null */ if (imclient->callback[keywordindex].proc) { endreply[-1] = '\0'; reply.keyword[keywordlen] = '\0'; (imclient->callback[keywordindex].proc) (imclient, imclient->callback[keywordindex].rock, &reply); } /* Start parsing the next reply */ imclient->replystart = endreply + 1; } } /* * Received an EOF on the connection 'imclient' * Issue appropriate callbacks. */ static void imclient_eof(struct imclient *imclient) { struct imclient_cmdcallback *cmdcb; struct imclient_reply reply; assert(imclient); imclient->readytag = 0; imclient->readytxt = 0; for (cmdcb = imclient->cmdcallback; cmdcb; cmdcb = cmdcb->next) { reply.keyword = "EOF"; reply.msgno = -1; reply.text = ""; (*cmdcb->proc)(imclient, cmdcb->rock, &reply); if (!cmdcb->next) { cmdcb->next = cmdcallback_freelist; cmdcallback_freelist = imclient->cmdcallback; break; } } imclient->cmdcallback = 0; /* XXX make an untagged "EOF" callback? */ } /* * Get information for calling select * 'fd' is filled in with file descriptor to select() for read * 'wanttowrite' is filled in with nonzero value iff should * select() for write as well. */ EXPORTED void imclient_getselectinfo(struct imclient *imclient, int *fd, int *wanttowrite) { assert(imclient); assert(fd); assert(wanttowrite); *fd = imclient->fd; *wanttowrite = imclient->outptr - imclient->outstart; } /* * Process one input or output event on the connection 'imclient'. */ EXPORTED void imclient_processoneevent(struct imclient *imclient) { char buf[IMCLIENT_BUFSIZE]; int n; int writelen; fd_set rfds, wfds; FD_ZERO(&rfds); FD_ZERO(&wfds); assert(imclient); for (;;) { writelen = imclient->outptr - imclient->outstart; if ((imclient->saslcompleted==1) && (writelen>0)) { unsigned int cryptlen=0; const char *cryptptr=NULL; if (sasl_encode(imclient->saslconn, imclient->outstart, writelen, &cryptptr,&cryptlen)!=SASL_OK) { /* XXX encoding error */ n=0; } #ifdef HAVE_SSL if (imclient->tls_on==1) { n = SSL_write(imclient->tls_conn, cryptptr, cryptlen); } else { n = write(imclient->fd, cryptptr, cryptlen); } #else /* HAVE_SSL */ n = write(imclient->fd, cryptptr, cryptlen); #endif /* HAVE_SSL */ if (n > 0) { imclient->outstart += writelen; return; } /* XXX Also EPIPE & the like? */ /* Make sure we select() for writing */ } else if (writelen) { /* No protection mechanism, just write the plaintext */ #ifdef HAVE_SSL if (imclient->tls_on==1) { n = SSL_write(imclient->tls_conn, imclient->outstart, writelen); } else { n = write(imclient->fd, imclient->outstart, writelen); } #else /* HAVE_SSL */ n = write(imclient->fd, imclient->outstart, writelen); #endif /* HAVE_SSL */ if (n > 0) { imclient->outstart += n; return; } /* XXX Also EPIPE & the like? */ } if (FD_ISSET(imclient->fd, &rfds)) { #ifdef HAVE_SSL /* just do a SSL read instead if we're under a tls layer */ if (imclient->tls_on==1) { n = SSL_read(imclient->tls_conn, buf, sizeof(buf)); } else { n = read(imclient->fd, buf, sizeof(buf)); } #else /* HAVE_SSL */ n = read(imclient->fd, buf, sizeof(buf)); #endif /* HAVE_SSL */ if (n >= 0) { if (n == 0) { imclient_eof(imclient); } else { imclient_input(imclient, buf, n); } return; } } FD_ZERO(&rfds); FD_ZERO(&wfds); FD_SET(imclient->fd, &rfds); if (writelen) FD_SET(imclient->fd, &wfds); (void) select(imclient->fd + 1, &rfds, &wfds, (fd_set *)0, 0); } } enum replytype {replytype_inprogress, replytype_ok, replytype_no, replytype_bad, replytype_prematureok}; struct authresult { enum replytype replytype; int r; }; /* Command completion callback for imclient_authenticate */ static void authresult(struct imclient *imclient __attribute__((unused)), void *rock, struct imclient_reply *reply) { struct authresult *result = (struct authresult *)rock; assert(result); assert(reply); if (!strcmp(reply->keyword, "OK")) { result->replytype = replytype_ok; } else if (!strcmp(reply->keyword, "NO")) { result->replytype = replytype_no; } else result->replytype = replytype_bad; } /* Command completion for starttls */ static void tlsresult(struct imclient *imclient __attribute__((unused)), void *rock, struct imclient_reply *reply) { struct authresult *result = (struct authresult *)rock; assert(result); assert(reply); if (!strcmp(reply->keyword, "OK")) { result->replytype = replytype_ok; } else if (!strcmp(reply->keyword, "NO")) { result->replytype = replytype_no; } else result->replytype = replytype_bad; } static sasl_security_properties_t *make_secprops(int min,int max) { sasl_security_properties_t *ret= (sasl_security_properties_t *)xzmalloc(sizeof(sasl_security_properties_t)); ret->maxbufsize = IMCLIENT_BUFSIZE; ret->min_ssf = min; ret->max_ssf = max; return ret; } static void interaction(struct imclient *context, sasl_interact_t *t, char *user) { char result[1024]; char *str = NULL; assert(context); assert(t); if ((t->id == SASL_CB_USER || t->id == SASL_CB_AUTHNAME) && user && user[0]) { str = xstrdup(user); } else { printf("%s: ", t->prompt); if (t->id == SASL_CB_PASS) { char *ptr = cyrus_getpass(""); strlcpy(result, ptr, sizeof(result)); } else { if (!fgets(result, sizeof(result)-1, stdin)) return; } str = xstrdup(result); } assert(str); t->result = str; t->len = strlen(str); strarray_appendm(&context->interact_results, str); } EXPORTED void fillin_interactions(struct imclient *context, sasl_interact_t *tlist, char *user) { assert(context); assert(tlist); while (tlist->id!=SASL_CB_LIST_END) { interaction(context, tlist, user); tlist++; } } /* * Params: * mechlist: list of mechanisms seperated by spaces * * Returns: * 0 - sucess * 1 - failure * 2 - severe failure? */ static int imclient_authenticate_sub(struct imclient *imclient, char *mechlist, char *user, int minssf, int maxssf, const char **mechusing) { int saslresult; sasl_security_properties_t *secprops=NULL; socklen_t addrsize; struct sockaddr_storage saddr_l; struct sockaddr_storage saddr_r; char localip[60], remoteip[60]; sasl_interact_t *client_interact=NULL; const char *out; unsigned int outlen; int inlen; struct authresult result; assert(imclient); assert(mechlist); /******* * Now set the SASL properties *******/ secprops=make_secprops(minssf,maxssf); if (secprops==NULL) return 1; saslresult=sasl_setprop(imclient->saslconn, SASL_SEC_PROPS, secprops); if (saslresult!=SASL_OK) return 1; free(secprops); addrsize=sizeof(struct sockaddr_storage); if (getpeername(imclient->fd,(struct sockaddr *)&saddr_r,&addrsize)!=0) return 1; addrsize=sizeof(struct sockaddr_storage); if (getsockname(imclient->fd,(struct sockaddr *)&saddr_l,&addrsize)!=0) return 1; if(iptostring((const struct sockaddr *)&saddr_l, addrsize, localip, sizeof(localip)) != 0) return 1; if(iptostring((const struct sockaddr *)&saddr_r, addrsize, remoteip, sizeof(remoteip)) != 0) return 1; saslresult=sasl_setprop(imclient->saslconn, SASL_IPREMOTEPORT, remoteip); if (saslresult!=SASL_OK) return 1; saslresult=sasl_setprop(imclient->saslconn, SASL_IPLOCALPORT, localip); if (saslresult!=SASL_OK) return 1; /******** * SASL is setup. Now try the actual authentication ********/ saslresult=SASL_INTERACT; /* call sasl client start */ while (saslresult==SASL_INTERACT) { saslresult=sasl_client_start(imclient->saslconn, mechlist, &client_interact, &out, &outlen, mechusing); if (saslresult==SASL_INTERACT) { fillin_interactions(imclient, client_interact, user); /* fill in prompts */ } } if ((saslresult!=SASL_OK) && (saslresult!=SASL_CONTINUE)) return saslresult; imclient_send(imclient, authresult, (void *)&result, "AUTHENTICATE %a", *mechusing); while (1) { /* Wait for ready response or command completion */ imclient->readytag = imclient->gensym; while (imclient->readytag) { imclient_processoneevent(imclient); } /* stop looping on command completion */ if (!imclient->readytxt) break; if (Uisspace(*imclient->readytxt)) { inlen = 0; } else { inlen = imclient_decodebase64(imclient->readytxt); } if (inlen == -1) { /* bad base64 string */ return replytype_bad; } if (inlen == 0 && outlen > 0) { /* we have something from the initial thing to send */ } else { /* perform a step */ saslresult = SASL_INTERACT; while (saslresult == SASL_INTERACT) { saslresult=sasl_client_step(imclient->saslconn, imclient->readytxt, inlen, &client_interact, &out, &outlen); if (saslresult == SASL_INTERACT) { /* fill in prompts */ fillin_interactions(imclient, client_interact, user); } } } /* send our reply to the server */ if ((saslresult==SASL_OK) || (saslresult==SASL_CONTINUE)) { if (out == NULL || outlen == 0) { imclient_write(imclient, "\r\n", 2); } else { imclient_writebase64(imclient, out, outlen); } } else { imclient_write(imclient,"*\r\n", 3); return saslresult; } outlen = 0; } if(result.replytype == replytype_ok) imclient->saslcompleted = 1; return (result.replytype != replytype_ok); } /* xxx service is not needed here */ EXPORTED int imclient_authenticate(struct imclient *imclient, char *mechlist, char *service __attribute__((unused)), char *user, int minssf, int maxssf) { int r; char *mlist; const char *mtried; assert(imclient); assert(mechlist); mlist = xstrdup(mechlist); ucase(mlist); do { mtried = NULL; r = imclient_authenticate_sub(imclient, mlist, user, minssf, maxssf, &mtried); /* eliminate mtried (mechanism tried) from mlist */ if (r != 0 && mtried) { char *newlist = xmalloc(strlen(mlist)+1); char *mtr = xstrdup(mtried); char *tmp; ucase(mtr); tmp = strstr(mlist,mtr); if(!tmp) { free(mtr); free(newlist); break; } *tmp = '\0'; strcpy(newlist,mlist); /* Use tmp+1 here to skip the \0 we just put in. * this is safe because even if the mechs are one character * long there would still be another trailing \0 */ tmp = strchr(tmp+1,' '); if (tmp) { tmp++; /* skip the space */ strcat(newlist,tmp); } free(mtr); free(mlist); mlist = newlist; } } while ((r != 0) && (mtried)); if (r == 0) { const void *maxp; unsigned int max; sasl_getprop(imclient->saslconn, SASL_MAXOUTBUF, &maxp); max = *((const unsigned int *) maxp); imclient->maxplain = max < IMCLIENT_BUFSIZE ? max : IMCLIENT_BUFSIZE; } free(mlist); return r; } #define XX 127 /* * Tables for encoding/decoding base64 */ static const char basis_64[] = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/"; static const char index_64[256] = { XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,62, XX,XX,XX,63, 52,53,54,55, 56,57,58,59, 60,61,XX,XX, XX,XX,XX,XX, XX, 0, 1, 2, 3, 4, 5, 6, 7, 8, 9,10, 11,12,13,14, 15,16,17,18, 19,20,21,22, 23,24,25,XX, XX,XX,XX,XX, XX,26,27,28, 29,30,31,32, 33,34,35,36, 37,38,39,40, 41,42,43,44, 45,46,47,48, 49,50,51,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, XX,XX,XX,XX, }; #define CHAR64(c) (index_64[(unsigned char)(c)]) /* * Decode in-place the base64 data in 'input'. Returns the length * of the decoded data, or -1 if there was an error. */ static int imclient_decodebase64(char *input) { int len = 0; unsigned char *output = (unsigned char *)input; int c1, c2, c3, c4; assert(input); while (*input) { c1 = *input++; if (CHAR64(c1) == XX) return -1; c2 = *input++; if (CHAR64(c2) == XX) return -1; c3 = *input++; if (c3 != '=' && CHAR64(c3) == XX) return -1; c4 = *input++; if (c4 != '=' && CHAR64(c4) == XX) return -1; *output++ = (CHAR64(c1) << 2) | (CHAR64(c2) >> 4); ++len; if (c3 == '=') break; *output++ = ((CHAR64(c2) << 4) & 0xf0) | (CHAR64(c3) >> 2); ++len; if (c4 == '=') break; *output++ = ((CHAR64(c3) << 6) & 0xc0) | CHAR64(c4); ++len; } return len; } /* * Write to the connection 'imclient' the base-64 encoded data * 'output', of (unencoded) length 'len'. */ static void imclient_writebase64(struct imclient *imclient, const char *output, size_t len) { char buf[1024]; size_t buflen = 0; int c1, c2, c3; assert(imclient); assert(output); while (len) { if (buflen >= (size_t)(sizeof(buf)-4)) { imclient_write(imclient, buf, buflen); buflen = 0; } c1 = (unsigned char)*output++; buf[buflen++] = basis_64[c1>>2]; if (--len == 0) c2 = 0; else c2 = (unsigned char)*output++; buf[buflen++] = basis_64[((c1 & 0x3)<< 4) | ((c2 & 0xF0) >> 4)]; if (len == 0) { buf[buflen++] = '='; buf[buflen++] = '='; break; } if (--len == 0) c3 = 0; else c3 = (unsigned char)*output++; buf[buflen++] = basis_64[((c2 & 0xF) << 2) | ((c3 & 0xC0) >>6)]; if (len == 0) { buf[buflen++] = '='; break; } --len; buf[buflen++] = basis_64[c3 & 0x3F]; } if (buflen >= sizeof(buf)-2) { imclient_write(imclient, buf, buflen); buflen = 0; } buf[buflen++] = '\r'; buf[buflen++] = '\n'; imclient_write(imclient, buf, buflen); } /*************** All these functions help do the starttls; these are copied from imtest.c ********/ #ifdef HAVE_SSL static int verify_depth; static int verify_error = X509_V_OK; #define CCERT_BUFSIZ 256 static char peer_CN[CCERT_BUFSIZ]; /* * Set up the cert things on the server side. We do need both the * private key (in key_file) and the cert (in cert_file). * Both files may be identical. * * This function is taken from OpenSSL apps/s_cb.c */ static int set_cert_stuff(SSL_CTX * ctx, char *cert_file, char *key_file) { if (cert_file != NULL) { if (SSL_CTX_use_certificate_chain_file(ctx, cert_file) <= 0) { printf("[ unable to get certificate from '%s' ]\n", cert_file); return (0); } if (key_file == NULL) key_file = cert_file; if (SSL_CTX_use_PrivateKey_file(ctx, key_file, SSL_FILETYPE_PEM) <= 0) { printf("[ unable to get private key from '%s' ]\n", key_file); return (0); } /* Now we know that a key and cert have been set against * the SSL context */ if (!SSL_CTX_check_private_key(ctx)) { printf("[ Private key does not match the certificate public key ]\n"); return (0); } } return (1); } /* taken from OpenSSL apps/s_cb.c */ static int verify_callback(int ok, X509_STORE_CTX * ctx) { char buf[256]; X509 *err_cert; int err; int depth; err_cert = X509_STORE_CTX_get_current_cert(ctx); err = X509_STORE_CTX_get_error(ctx); depth = X509_STORE_CTX_get_error_depth(ctx); X509_NAME_oneline(X509_get_subject_name(err_cert), buf, sizeof(buf)); /* if (verbose==1) printf("Peer cert verify depth=%d %s\n", depth, buf);*/ if (!ok) { printf("verify error:num=%d:%s\n", err, X509_verify_cert_error_string(err)); if (verify_depth >= depth) { ok = 1; verify_error = X509_V_OK; } else { ok = 0; verify_error = X509_V_ERR_CERT_CHAIN_TOO_LONG; } } switch (err) { case X509_V_ERR_UNABLE_TO_GET_ISSUER_CERT: X509_NAME_oneline(X509_get_issuer_name(err_cert), buf, sizeof(buf)); printf("issuer= %s\n", buf); break; case X509_V_ERR_CERT_NOT_YET_VALID: case X509_V_ERR_ERROR_IN_CERT_NOT_BEFORE_FIELD: printf("cert not yet valid\n"); break; case X509_V_ERR_CERT_HAS_EXPIRED: case X509_V_ERR_ERROR_IN_CERT_NOT_AFTER_FIELD: printf("cert has expired\n"); break; } /* if (verbose==1) printf("verify return:%d\n", ok);*/ return (ok); } #if OPENSSL_VERSION_NUMBER < 0x10100000L /* taken from OpenSSL apps/s_cb.c */ static RSA *tmp_rsa_cb(SSL *s __attribute__((unused)), int export __attribute__((unused)), int keylength) { static RSA *rsa_tmp = NULL; if (rsa_tmp == NULL) { rsa_tmp = RSA_generate_key(keylength, RSA_F4, NULL, NULL); } return (rsa_tmp); } #endif /* * Seed the random number generator. */ static int tls_rand_init(void) { #ifdef EGD_SOCKET return (RAND_egd(EGD_SOCKET)); #else /* otherwise let OpenSSL do it internally */ return 0; #endif } /* * This is the setup routine for the SSL client. * * The skeleton of this function is taken from OpenSSL apps/s_client.c. */ static int tls_init_clientengine(struct imclient *imclient, int verifydepth, char *var_tls_cert_file, char *var_tls_key_file, char *var_tls_CAfile, char *var_tls_CApath) { int off = 0; int verify_flags = SSL_VERIFY_NONE; char *CApath; char *CAfile; char *c_cert_file; char *c_key_file; assert(imclient); SSL_load_error_strings(); SSLeay_add_ssl_algorithms(); if (tls_rand_init() == -1) { printf("[ TLS engine: cannot seed PRNG ]\n"); return -1; } #if (OPENSSL_VERSION_NUMBER >= 0x10100000L) imclient->tls_ctx = SSL_CTX_new(TLS_client_method()); #else imclient->tls_ctx = SSL_CTX_new(SSLv23_client_method()); #endif if (imclient->tls_ctx == NULL) { return -1; }; off |= SSL_OP_ALL; /* Work around all known bugs */ off |= SSL_OP_NO_SSLv2; /* Disable insecure SSLv2 */ off |= SSL_OP_NO_SSLv3; /* Disable insecure SSLv3 */ off |= SSL_OP_NO_COMPRESSION; /* Disable TLS compression */ SSL_CTX_set_options(imclient->tls_ctx, off); /* debugging SSL_CTX_set_info_callback(imclient->tls_ctx, apps_ssl_info_callback); */ if (var_tls_CAfile == NULL || strlen(var_tls_CAfile) == 0) CAfile = NULL; else CAfile = var_tls_CAfile; if (var_tls_CApath == NULL || strlen(var_tls_CApath) == 0) CApath = NULL; else CApath = var_tls_CApath; if (CAfile || CApath) if ((!SSL_CTX_load_verify_locations(imclient->tls_ctx, CAfile, CApath)) || (!SSL_CTX_set_default_verify_paths(imclient->tls_ctx))) { printf("[ TLS engine: cannot load CA data ]\n"); return -1; } if (var_tls_cert_file == NULL || strlen(var_tls_cert_file) == 0) c_cert_file = NULL; else c_cert_file = var_tls_cert_file; if (var_tls_key_file == NULL || strlen(var_tls_key_file) == 0) c_key_file = NULL; else c_key_file = var_tls_key_file; if (c_cert_file || c_key_file) if (!set_cert_stuff(imclient->tls_ctx, c_cert_file, c_key_file)) { printf("[ TLS engine: cannot load cert/key data, may be a cert/key mismatch]\n"); return -1; } #if OPENSSL_VERSION_NUMBER < 0x10100000L SSL_CTX_set_tmp_rsa_callback(imclient->tls_ctx, tmp_rsa_cb); #endif verify_depth = verifydepth; SSL_CTX_set_verify(imclient->tls_ctx, verify_flags, verify_callback); return 0; } #if 0 /* Dead code only for debugging */ static int do_dump = 1; /* * taken from OpenSSL crypto/bio/b_dump.c, modified to save a lot of strcpy * and strcat by Matti Aarnio. */ #define TRUNCATE #define DUMP_WIDTH 16 static int tls_dump(const char *s, int len) { int ret = 0; char buf[160 + 1]; char *ss; int i; int j; int rows; int trunc; unsigned char ch; trunc = 0; #ifdef TRUNCATE for (; (len > 0) && ((s[len - 1] == ' ') || (s[len - 1] == '\0')); len--) trunc++; #endif rows = (len / DUMP_WIDTH); if ((rows * DUMP_WIDTH) < len) rows++; for (i = 0; i < rows; i++) { buf[0] = '\0'; /* start with empty string */ ss = buf; sprintf(ss, "%04x ", i * DUMP_WIDTH); ss += strlen(ss); for (j = 0; j < DUMP_WIDTH; j++) { if (((i * DUMP_WIDTH) + j) >= len) { strcpy(ss, " "); } else { ch = ((unsigned char) *((char *) (s) + i * DUMP_WIDTH + j)) & 0xff; sprintf(ss, "%02x[%c]%c", ch, ch, j == 7 ? '|' : ' '); ss += 6; } } ss += strlen(ss); *ss+= ' '; for (j = 0; j < DUMP_WIDTH; j++) { if (((i * DUMP_WIDTH) + j) >= len) break; ch = ((unsigned char) *((char *) (s) + i * DUMP_WIDTH + j)) & 0xff; *ss+= (((ch >= ' ') && (ch <= '~')) ? ch : '.'); if (j == 7) *ss+= ' '; } *ss = 0; /* * if this is the last call then update the ddt_dump thing so that * we will move the selection point in the debug window */ printf("%s\n", buf); ret += strlen(buf); } #ifdef TRUNCATE if (trunc > 0) { sprintf(buf, "%04x - \n", len+ trunc); printf("%s\n", buf); ret += strlen(buf); } #endif return (ret); } /* these next two taken from OpenSSL apps/s_cb.c */ static long bio_dump_cb(BIO * bio, int cmd, const char *argp, int argi, long argl __attribute__((unused)), long ret) { if (!do_dump) return (ret); if (cmd == (BIO_CB_READ | BIO_CB_RETURN)) { printf("read from %08X [%08lX] (%d bytes => %ld (0x%X))\n", (unsigned int) bio, (unsigned long) argp, argi, ret, (unsigned int) ret); tls_dump(argp, (int) ret); return (ret); } else if (cmd == (BIO_CB_WRITE | BIO_CB_RETURN)) { printf("write to %08X [%08lX] (%d bytes => %ld (0x%X))\n", (unsigned int) bio, (unsigned long) argp, argi, ret, (unsigned int) ret); tls_dump(argp, (int) ret); } return (ret); } static void apps_ssl_info_callback(SSL * s, int where, int ret) { char *str; int w; w = where & ~SSL_ST_MASK; if (w & SSL_ST_CONNECT) str = "SSL_connect"; else if (w & SSL_ST_ACCEPT) str = "SSL_accept"; else str = "undefined"; if (where & SSL_CB_LOOP) { printf("%s:%s\n", str, SSL_state_string_long(s)); } else if (where & SSL_CB_ALERT) { str = (where & SSL_CB_READ) ? "read" : "write"; if ((ret & 0xff) != SSL3_AD_CLOSE_NOTIFY) printf("SSL3 alert %s:%s:%s\n", str, SSL_alert_type_string_long(ret), SSL_alert_desc_string_long(ret)); } else if (where & SSL_CB_EXIT) { if (ret == 0) printf("%s:failed in %s\n", str, SSL_state_string_long(s)); else if (ret < 0) { printf("%s:error in %s %i\n", str, SSL_state_string_long(s),ret); } } } #endif EXPORTED int tls_start_clienttls(struct imclient *imclient, unsigned *layer, char **authid, int fd) { int sts; SSL_SESSION *session; const SSL_CIPHER *cipher; X509 *peer; int tls_cipher_usebits = 0; int tls_cipher_algbits = 0; char *tls_peer_CN = ""; if (!imclient->tls_conn) imclient->tls_conn = (SSL *) SSL_new(imclient->tls_ctx); if (!imclient->tls_conn) { printf("Could not allocate 'con' with SSL_new()\n"); return -1; } SSL_clear(imclient->tls_conn); if (!SSL_set_fd(imclient->tls_conn, fd)) { printf("SSL_set_fd failed\n"); return -1; } /* * This is the actual handshake routine. It will do all the negotiations * and will check the client cert etc. */ SSL_set_connect_state(imclient->tls_conn); /* * We do have an SSL_set_fd() and now suddenly a BIO_ routine is called? * Well there is a BIO below the SSL routines that is automatically * created for us, so we can use it for debugging purposes. */ /* Dump the negotiation for loglevels 3 and 4 */ sts = SSL_connect(imclient->tls_conn); if (sts <= 0) { printf("[ SSL_connect error %d ]\n", sts); /* xxx get string error? */ session = SSL_get_session(imclient->tls_conn); if (session) { SSL_CTX_remove_session(imclient->tls_ctx, session); printf("[ SSL session removed ]\n"); } if (imclient->tls_conn) SSL_free(imclient->tls_conn); imclient->tls_conn = NULL; return -1; } /* * Lets see, whether a peer certificate is availabe and what is * the actual information. We want to save it for later use. */ peer = SSL_get_peer_certificate(imclient->tls_conn); if (peer) { X509_NAME_get_text_by_NID(X509_get_subject_name(peer), NID_commonName, peer_CN, CCERT_BUFSIZ); tls_peer_CN = peer_CN; } cipher = SSL_get_current_cipher(imclient->tls_conn); tls_cipher_usebits = SSL_CIPHER_get_bits(cipher, &tls_cipher_algbits); if (layer) *layer = tls_cipher_usebits; if (authid) *authid = tls_peer_CN; return 0; } #endif /* HAVE_SSL */ EXPORTED int imclient_havetls(void) { #ifdef HAVE_SSL return 1; #else return 0; #endif } EXPORTED int imclient_starttls(struct imclient *imclient, char *cert_file, char *key_file, char *CAfile, char *CApath) { #ifdef HAVE_SSL int result; struct authresult theresult; sasl_ssf_t ssf; char *auth_id; imclient_send(imclient, tlsresult, (void *)&theresult, "STARTTLS"); /* Wait for ready response or command completion */ imclient->readytag = imclient->gensym; while (imclient->readytag) { imclient_processoneevent(imclient); } result=tls_init_clientengine(imclient, 10, cert_file, key_file, CAfile, CApath); if (result!=0) { printf("[ TLS engine failed ]\n"); return 1; } else { result=tls_start_clienttls(imclient, &ssf, &auth_id, imclient->fd); if (result!=0) { printf("[ TLS negotiation did not succeed ]\n"); return 1; } } /* turn non-blocking i/o back on */ /* TLS negotiation succeeded */ imclient->tls_on = 1; auth_id=""; /* xxx this really should be peer_CN or issuer_CN but I can't figure out which is which at the moment */ /* tell SASL about the negotiated layer */ result=sasl_setprop(imclient->saslconn, SASL_SSF_EXTERNAL, &ssf); if (result!=SASL_OK) return 1; result=sasl_setprop(imclient->saslconn, SASL_AUTH_EXTERNAL, auth_id); if (result!=SASL_OK) return 1; return 0; #else printf("[ TLS support not present (imclient_starttls) ]\n"); return 1; #endif /* HAVE_SSL */ } cyrus-imapd-2.5.10/lib/cyrusdb_twoskip.c0000644000175000017500000017054513001236020015121 00000000000000/* cyrusdb_twoskip.c - brand new twoskip implementation, not backwards anything * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include #include #include #include #include #include #include #ifdef HAVE_UNISTD_H #include #endif #include "assert.h" #include "bsearch.h" #include "byteorder64.h" #include "cyrusdb.h" #include "crc32.h" #include "libcyr_cfg.h" #include "mappedfile.h" #include "util.h" #include "xmalloc.h" /* * twoskip disk format. * * GOALS: * a) 64 bit through * b) Fast recovery after crashes * c) integrity checks throughout * d) simple format * * ACHIEVED BY: * a) * - 64 bit offsets for all values * - smaller initial keylen and vallen, but they can * can be extended up to 64 bits as well. * - no timestamps stored in the file. * - XXX - may behave strangely with large files on * 32 bit architectures, particularly if size_t is * not 64 bit. * * b) * - "dirty flag" is always set in the header and * fsynced BEFORE writing anything else. * - a header field for "current size", after which * all changes are considered suspect until commit. * - two "lowest level" offsets, used in alternating * order, so the highest value less than "current_size" * is always the correct pointer - this means we * never lose linkage, so never need to rewrite more * than the affected records during a recovery. * - all data is fsynced BEFORE rewriting the header to * remove the dirty flag. * - As long as the first 64 bytes of the file are * guaranteed to write all together or not at all, * we're crash-safe. * * c) * - every byte in the file is covered by one of the * crc32 values stored throughout. * - header CRC is checked on every header read (open/lock) * - record head CRCs are checked on every record read, * including skiplist traverse. * - record tail CRCs (key/value) are check on every exact * key match result, during traverse for read or write. * * d) * - there are no special commit, inorder, etc records. * just add records and ghost "delete" records to give * somewhere to point to on deletes. These are only * at the lowest level, so don't have a significant * seek impact. * - modular code makes the logic much clearer. */ /* * FORMAT: * * HEADER: 64 bytes * magic: 20 bytes: "4 bytes same as skiplist" "twoskip file\0\0\0\0" * version: 4 bytes * generation: 8 bytes * num_records: 8 bytes * repack_size: 8 bytes * current_size: 8 bytes * flags: 4 bytes * crc32: 4 bytes * * RECORDS: * type 1 byte * level: 1 byte * keylen: 2 bytes * vallen: 4 bytes * * * ptrs: 8 bytes * (level+1) * crc32_head: 4 bytes * crc32_tail: 4 bytes * key: (keylen bytes) * val: (vallen bytes) * padding: enough zeros to round up to an 8 byte multiple * * defined types, in skiplist language are: * '=' -> DUMMY * '+' -> ADD/INORDER * '-' -> DELETE (kind of) * '$' -> COMMIT * but note that delete records behave differently - they're * part of the pointer hierarchy, so that back offsets will * always point somewhere past the 'end' until commit. * * The DUMMY is always MAXLEVEL level, with zero keylen and vallen * The DELETE is always zero level, with zero keylen and vallen * crc32_head is calculated on all bytes before it in the record * crc32_tail is calculated on all bytes after, INCLUDING padding * * The COMMIT is inserted at the end of each transaction, and its * single pointer points back to the start of the transaction. */ /* OPERATION: * * Finding a record works very much like skiplist, but we have * a datastructure, 'struct skiploc', to help find it. There * is one of these embedded directly in the 'struct db', and * it's the only one we ever use. * * skiploc contains two complete sets of offsets - at every * level the offset of the previous record, and the offset of * the next record, in relation to the requested key. If the * key is an exact match, it also contains a copy of the * struct skiprecord. If not, it contains the struct * skiprecord for the previous record at level zero. * * It also contains a 'struct buf' with a copy of the requested * key, which allows for efficient relocation of the position in * the file when nothing is changed. * * So nothing is really changed with finding, except the special * "level zero" alternative pointer. We'll see that in action * later. * * TRANSACTIONS: * 1) before writing anything else, the header is updated with the * DIRTY flag set, and then fdatasync is run. * 2) after all changes, fdatasync is run again. * 3) finally, the header is updated with a new current_size and * the DIRTY flag clear, then fdatasync is run for a third time. * * ADDING A NEW RECORD: * a new record is created with forward locations pointing to the * next pointers in the skiploc. This is appended to the file. * This works for either a create OR replace, since in both cases * the nextlocs are correct. Level zero is set to zero on a new * record. * * If it's not a replace, a "random" level will be chosen for the * record. All update operations below apply only up to this level, * pointers above are unaffected - and continue over the location * of this change. * * For each backloc, the record at that offset is read, and the * forward pointers at each level are replaced with the offset * of the new record. NOTE: see special level zero logic below. * * Again, if this was a replace, the backlocs don't point to the * current record, so it just silently disappears from the lists. * * DELETING A RECORD: * The logic is almost identical to adding, but a delete record * always has a level of zero, with only a single pointer forward * to the next record. * * Because of this, the updates are done up to the level of the * old record instead. * * THE SPECIAL "level zero": * To allow a "fast fsck" after an aborted transaction, rather * than having only a single level 1 pointer, we have two. The * following algorithm is used to select which one to change. * * The definition of "current_size" is the size of the database * at last commit, it does not get updated during a transaction. * * So: when updating level 1 - if either level 1 or level 0 has * a value >= current_size, then that value gets updated again. * otherwise, the lowest value gets replaced with the new value. * * when reading, the highest value is used - except during * recovery when it's the highest value less than current_size, * since any "future" offsets are bogus. * * This means that there is always at least one offset which * points to the "next" record as if the current transaction * had never occured - allowing recovery to find all alive * records without scanning and updating the rest of the file. * This guarantee exists regardless of any ordering of writes * within the transaction, any page could be inconsistent and * the result is still a clean recovery. * * CHECKPOINT: * Over time, a twoskip database accumulates cruft - replaced * records and delete records. Records out of order, slowing * down sequential access. When the size at last repack * is sufficiently smaller than the current size (see the * TUNING constants below) then the file is checkpointed. * A checkpoint is achieved by creating a new file, and * copying all the current records, in order, into it, then * renaming the new file over the old. The "generation" * counter in the header is incremented to tell other users * that offsets into the file are no longer valid. This is * more reliable than just using the inode, because inodes * can be reused. * * LOCATION OPTIMISATION: * If the generation is unchanged AND the size of the file * is unchanged, then all offsets stored in the skiploc are * still valid. This is used to optimise finding the current * key, advancing to the "next" key, and also to optimise * regular fetches that happen to hit either the current key, * the gap immediately after, or the next key. All other * locations cause a full relocate. */ /********** TUNING *************/ /* don't bother rewriting if the database has less than this much "new" data */ #define MINREWRITE 16834 /* don't bother rewriting if less than this ratio is dirty (50%) */ #define REWRITE_RATIO 0.5 /* number of skiplist levels - 31 gives us binary search to 2^32 records. * limited to 255 by file format, but skiplist had 20, and that was enough * for most real uses. 31 is heaps. */ #define MAXLEVEL 31 /* should be 0.5 for binary search semantics */ #define PROB 0.5 /* format specifics */ #undef VERSION /* defined in config.h */ #define VERSION 1 /* type aliases */ #define LLU long long unsigned int #define LU long unsigned int /* record types */ #define DUMMY '=' #define RECORD '+' #define DELETE '-' #define COMMIT '$' /********** DATA STRUCTURES *************/ /* A single "record" in the twoskip file. This could be a * DUMMY, a KEYRECORD, a VALRECORD or even a DELETE - they * all read and write with the same functions */ struct skiprecord { /* location on disk (not part of the on-disk format as such) */ size_t offset; size_t len; /* what are our header fields */ uint8_t type; uint8_t level; size_t keylen; size_t vallen; /* where to do we go from here? */ size_t nextloc[MAXLEVEL+1]; /* what do our integrity checks say? */ uint32_t crc32_head; uint32_t crc32_tail; /* our key and value */ size_t keyoffset; size_t valoffset; }; /* a location in the twoskip file. We always have: * record: if "is_exactmatch" this points to the record * with the matching key, otherwise it points to * the 'compar' order previous record. * backloc: the records that point TO this location * at each level. If is_exactmatch, they * point to the record, otherwise they are * the record. * forwardloc: the records pointed to by the record * at 'backloc' at the same level. Kept * here for efficiency * keybuf: a copy of the requested key - we always keep * this so we can re-seek after the file has been * checkpointed under us (say a read-only foreach) * * generation and end can be used to see if anything in * the file may have changed and needs re-reading. */ struct skiploc { /* requested, may not match actual record */ struct buf keybuf; int is_exactmatch; /* current or next record */ struct skiprecord record; /* we need both sets of offsets to cheaply insert */ size_t backloc[MAXLEVEL+1]; size_t forwardloc[MAXLEVEL+1]; /* need a generation so we know if the location is still valid */ uint64_t generation; size_t end; }; enum { UNLOCKED = 0, READLOCKED = 1, WRITELOCKED = 2, }; #define DIRTY (1<<0) struct txn { /* logstart is where we start changes from on commit, where we truncate to on abort */ int num; }; struct db_header { /* header info */ uint32_t version; uint32_t flags; uint64_t generation; uint64_t num_records; size_t repack_size; size_t current_size; }; struct dbengine { /* file data */ struct mappedfile *mf; struct db_header header; struct skiploc loc; /* tracking info */ int is_open; size_t end; int txn_num; struct txn *current_txn; /* comparator function to use for sorting */ int open_flags; int (*compar) (const char *s1, int l1, const char *s2, int l2); }; struct db_list { struct dbengine *db; struct db_list *next; int refcount; }; #define HEADER_MAGIC ("\241\002\213\015twoskip file\0\0\0\0") #define HEADER_MAGIC_SIZE (20) /* offsets of header files */ enum { OFFSET_HEADER = 0, OFFSET_VERSION = 20, OFFSET_GENERATION = 24, OFFSET_NUM_RECORDS = 32, OFFSET_REPACK_SIZE = 40, OFFSET_CURRENT_SIZE = 48, OFFSET_FLAGS = 56, OFFSET_CRC32 = 60, }; #define HEADER_SIZE 64 #define DUMMY_OFFSET HEADER_SIZE #define MAXRECORDHEAD ((MAXLEVEL + 5)*8) /* mount a scratch monkey */ static union skipwritebuf { uint64_t align; char s[MAXRECORDHEAD]; } scratchspace; static struct db_list *open_twoskip = NULL; static int mycommit(struct dbengine *db, struct txn *tid); static int myabort(struct dbengine *db, struct txn *tid); static int mycheckpoint(struct dbengine *db); static int myconsistent(struct dbengine *db, struct txn *tid); static int recovery(struct dbengine *db); static int recovery1(struct dbengine *db, int *count); static int recovery2(struct dbengine *db, int *count); /************** HELPER FUNCTIONS ****************/ #define BASE(db) mappedfile_base((db)->mf) #define KEY(db, rec) (BASE(db) + (rec)->keyoffset) #define VAL(db, rec) (BASE(db) + (rec)->valoffset) #define SIZE(db) mappedfile_size((db)->mf) #define FNAME(db) mappedfile_fname((db)->mf) /* calculate padding size */ static size_t roundup(size_t record_size, int howfar) { if (record_size % howfar) record_size += howfar - (record_size % howfar); return record_size; } /* choose a level appropriately randomly */ static uint8_t randlvl(uint8_t lvl, uint8_t maxlvl) { while (((float) rand() / (float) (RAND_MAX)) < PROB) { lvl++; if (lvl == maxlvl) break; } return lvl; } /************** HEADER ****************/ /* given an open, mapped db, read in the header information */ static int read_header(struct dbengine *db) { uint32_t crc; assert(db && db->mf && db->is_open); if (SIZE(db) < HEADER_SIZE) { syslog(LOG_ERR, "twoskip: file not large enough for header: %s", FNAME(db)); return CYRUSDB_IOERROR; } if (memcmp(BASE(db), HEADER_MAGIC, HEADER_MAGIC_SIZE)) { syslog(LOG_ERR, "twoskip: invalid magic header: %s", FNAME(db)); return CYRUSDB_IOERROR; } db->header.version = ntohl(*((uint32_t *)(BASE(db) + OFFSET_VERSION))); if (db->header.version > VERSION) { syslog(LOG_ERR, "twoskip: version mismatch: %s has version %d", FNAME(db), db->header.version); return CYRUSDB_IOERROR; } db->header.generation = ntohll(*((uint64_t *)(BASE(db) + OFFSET_GENERATION))); db->header.num_records = ntohll(*((uint64_t *)(BASE(db) + OFFSET_NUM_RECORDS))); db->header.repack_size = ntohll(*((uint64_t *)(BASE(db) + OFFSET_REPACK_SIZE))); db->header.current_size = ntohll(*((uint64_t *)(BASE(db) + OFFSET_CURRENT_SIZE))); db->header.flags = ntohl(*((uint32_t *)(BASE(db) + OFFSET_FLAGS))); crc = ntohl(*((uint32_t *)(BASE(db) + OFFSET_CRC32))); if (crc32_map(BASE(db), OFFSET_CRC32) != crc) { syslog(LOG_ERR, "DBERROR: %s: twoskip header CRC failure", FNAME(db)); return CYRUSDB_IOERROR; } db->end = db->header.current_size; return 0; } /* given an open, mapped, locked db, write the header information */ static int write_header(struct dbengine *db) { char *buf = scratchspace.s; int n; /* format one buffer */ memcpy(buf, HEADER_MAGIC, HEADER_MAGIC_SIZE); *((uint32_t *)(buf + OFFSET_VERSION)) = htonl(db->header.version); *((uint64_t *)(buf + OFFSET_GENERATION)) = htonll(db->header.generation); *((uint64_t *)(buf + OFFSET_NUM_RECORDS)) = htonll(db->header.num_records); *((uint64_t *)(buf + OFFSET_REPACK_SIZE)) = htonll(db->header.repack_size); *((uint64_t *)(buf + OFFSET_CURRENT_SIZE)) = htonll(db->header.current_size); *((uint32_t *)(buf + OFFSET_FLAGS)) = htonl(db->header.flags); *((uint32_t *)(buf + OFFSET_CRC32)) = htonl(crc32_map(buf, OFFSET_CRC32)); /* write it out */ n = mappedfile_pwrite(db->mf, buf, HEADER_SIZE, 0); if (n < 0) return CYRUSDB_IOERROR; return 0; } /* simple wrapper to write with an fsync */ static int commit_header(struct dbengine *db) { int r = write_header(db); if (!r) r = mappedfile_commit(db->mf); return r; } /******************** RECORD *********************/ static int check_tailcrc(struct dbengine *db, struct skiprecord *record) { uint32_t crc; crc = crc32_map(BASE(db) + record->keyoffset, roundup(record->keylen + record->vallen, 8)); if (crc != record->crc32_tail) { syslog(LOG_ERR, "DBERROR: invalid tail crc %s at %llX", FNAME(db), (LLU)record->offset); return CYRUSDB_IOERROR; } return 0; } /* read a single skiprecord at the given offset */ static int read_onerecord(struct dbengine *db, size_t offset, struct skiprecord *record) { const char *base; int i; memset(record, 0, sizeof(struct skiprecord)); if (!offset) return 0; record->offset = offset; record->len = 24; /* absolute minimum */ /* need space for at least the header plus some details */ if (record->offset + record->len > SIZE(db)) goto badsize; base = BASE(db) + offset; /* read in the record header */ record->type = base[0]; record->level = base[1]; record->keylen = ntohs(*((uint16_t *)(base + 2))); record->vallen = ntohl(*((uint32_t *)(base + 4))); offset += 8; /* make sure we fit */ if (record->level > MAXLEVEL) { syslog(LOG_ERR, "DBERROR: twoskip invalid level %d for %s at %08llX", record->level, FNAME(db), (LLU)offset); return CYRUSDB_IOERROR; } /* long key */ if (record->keylen == UINT16_MAX) { base = BASE(db) + offset; record->keylen = ntohll(*((uint64_t *)base)); offset += 8; } /* long value */ if (record->vallen == UINT32_MAX) { base = BASE(db) + offset; record->vallen = ntohll(*((uint64_t *)base)); offset += 8; } /* we know the length now */ record->len = (offset - record->offset) /* header including lengths */ + 8 * (1 + record->level) /* ptrs */ + 8 /* crc32s */ + roundup(record->keylen + record->vallen, 8); /* keyval */ if (record->offset + record->len > SIZE(db)) goto badsize; for (i = 0; i <= record->level; i++) { base = BASE(db) + offset; record->nextloc[i] = ntohll(*((uint64_t *)base)); offset += 8; } base = BASE(db) + offset; record->crc32_head = ntohl(*((uint32_t *)base)); if (crc32_map(BASE(db) + record->offset, (offset - record->offset)) != record->crc32_head) { syslog(LOG_ERR, "DBERROR: twoskip checksum head error for %s at %08llX", FNAME(db), (LLU)offset); return CYRUSDB_IOERROR; } record->crc32_tail = ntohl(*((uint32_t *)(base+4))); record->keyoffset = offset + 8; record->valoffset = record->keyoffset + record->keylen; return 0; badsize: syslog(LOG_ERR, "twoskip: attempt to read past end of file %s: %08llX > %08llX", FNAME(db), (LLU)record->offset + record->len, (LLU)SIZE(db)); return CYRUSDB_IOERROR; } static int read_skipdelete(struct dbengine *db, size_t offset, struct skiprecord *record) { int r; r = read_onerecord(db, offset, record); if (r) return r; if (record->type == DELETE) r = read_onerecord(db, record->nextloc[0], record); return r; } /* prepare the header part of the record (everything except the key, value * and padding). Used for both writes and rewrites. */ static void prepare_record(struct skiprecord *record, char *buf, size_t *sizep) { int len = 8; int i; assert(record->level <= MAXLEVEL); buf[0] = record->type; buf[1] = record->level; if (record->keylen < UINT16_MAX) { *((uint16_t *)(buf+2)) = htons(record->keylen); } else { *((uint16_t *)(buf+2)) = htons(UINT16_MAX); *((uint64_t *)(buf+len)) = htonll(record->keylen); len += 8; } if (record->vallen < UINT32_MAX) { *((uint32_t *)(buf+4)) = htonl(record->vallen); } else { *((uint32_t *)(buf+4)) = htonl(UINT32_MAX); *((uint64_t *)(buf+len)) = htonll(record->vallen); len += 8; } /* got pointers? */ for (i = 0; i <= record->level; i++) { *((uint64_t *)(buf+len)) = htonll(record->nextloc[i]); len += 8; } /* NOTE: crc32_tail does not change */ record->crc32_head = crc32_map(buf, len); *((uint32_t *)(buf+len)) = htonl(record->crc32_head); *((uint32_t *)(buf+len+4)) = htonl(record->crc32_tail); len += 8; *sizep = len; } /* only changing the record head, so only rewrite that much */ static int rewrite_record(struct dbengine *db, struct skiprecord *record) { char *buf = scratchspace.s; size_t len; int n; /* we must already be in a transaction before updating records */ assert(db->header.flags & DIRTY); assert(record->offset); prepare_record(record, buf, &len); n = mappedfile_pwrite(db->mf, buf, len, record->offset); if (n < 0) return CYRUSDB_IOERROR; return 0; } /* you can only write records at the end */ static int write_record(struct dbengine *db, struct skiprecord *record, const char *key, const char *val) { char zeros[8] = {0, 0, 0, 0, 0, 0, 0, 0}; uint64_t len; size_t iolen = 0; struct iovec io[4]; int n; assert(!record->offset); /* we'll put the HEAD on later */ io[0].iov_base = scratchspace.s; io[0].iov_len = 0; io[1].iov_base = (char *)key; io[1].iov_len = record->keylen; io[2].iov_base = (char *)val; io[2].iov_len = record->vallen; /* pad to 8 bytes */ len = record->vallen + record->keylen; io[3].iov_base = zeros; io[3].iov_len = roundup(len, 8) - len; /* calculate the CRC32 of the tail first */ record->crc32_tail = crc32_iovec(io+1, 3); /* prepare the record once we know the crc32 of the tail */ prepare_record(record, scratchspace.s, &iolen); io[0].iov_base = scratchspace.s; io[0].iov_len = iolen; /* write to the mapped file, getting the offset updated */ n = mappedfile_pwritev(db->mf, io, 4, db->end); if (n < 0) return CYRUSDB_IOERROR; /* locate the record */ record->offset = db->end; record->keyoffset = db->end + io[0].iov_len; record->valoffset = record->keyoffset + record->keylen; record->len = n; /* and advance the known file size */ db->end += n; return 0; } /* helper to append a record, starting the transaction by dirtying the * header first if required */ static int append_record(struct dbengine *db, struct skiprecord *record, const char *key, const char *val) { int r; assert(db->current_txn); /* dirty the header if not already dirty */ if (!(db->header.flags & DIRTY)) { db->header.flags |= DIRTY; r = commit_header(db); if (r) return r; } return write_record(db, record, key, val); } /************************** LOCATION MANAGEMENT ***************************/ /* find the next record at a given level, encapsulating the * level 0 magic */ static size_t _getloc(struct dbengine *db, struct skiprecord *record, uint8_t level) { if (level) return record->nextloc[level + 1]; /* if one is past, must be the other */ if (record->nextloc[0] >= db->end) return record->nextloc[1]; else if (record->nextloc[1] >= db->end) return record->nextloc[0]; /* highest remaining */ else if (record->nextloc[0] > record->nextloc[1]) return record->nextloc[0]; else return record->nextloc[1]; } /* set the next record at a given level, encapsulating the * level 0 magic */ static void _setloc(struct dbengine *db, struct skiprecord *record, uint8_t level, size_t offset) { if (level) { record->nextloc[level+1] = offset; return; } /* level zero is special */ /* already this transaction, update this one */ if (record->nextloc[0] >= db->header.current_size) record->nextloc[0] = offset; else if (record->nextloc[1] >= db->header.current_size) record->nextloc[1] = offset; /* otherwise, update older one */ else if (record->nextloc[1] > record->nextloc[0]) record->nextloc[0] = offset; else record->nextloc[1] = offset; } /* finds a record, either an exact match or the record * immediately before */ static int relocate(struct dbengine *db) { struct skiploc *loc = &db->loc; struct skiprecord newrecord; size_t offset; size_t oldoffset = 0; uint8_t level; uint8_t i; int cmp = -1; /* never found a thing! */ int r; /* pointer validity */ loc->generation = db->header.generation; loc->end = db->end; /* start with the dummy */ r = read_onerecord(db, DUMMY_OFFSET, &loc->record); loc->is_exactmatch = 0; /* initialise pointers */ level = loc->record.level; newrecord.offset = 0; loc->backloc[level] = loc->record.offset; loc->forwardloc[level] = 0; /* special case start pointer for efficiency */ if (!loc->keybuf.len) { for (i = 0; i < loc->record.level; i++) { loc->backloc[i] = loc->record.offset; loc->forwardloc[i] = _getloc(db, &loc->record, i); } return 0; } while (level) { offset = _getloc(db, &loc->record, level-1); loc->backloc[level-1] = loc->record.offset; loc->forwardloc[level-1] = offset; if (offset != oldoffset) { oldoffset = offset; r = read_skipdelete(db, offset, &newrecord); if (r) return r; if (newrecord.offset) { assert(newrecord.level >= level); cmp = db->compar(KEY(db, &newrecord), newrecord.keylen, loc->keybuf.s, loc->keybuf.len); /* not there? stay at this level */ if (cmp < 0) { /* move the offset range along */ loc->record = newrecord; continue; } } } level--; } if (cmp == 0) { /* we found it exactly */ loc->is_exactmatch = 1; loc->record = newrecord; for (i = 0; i < loc->record.level; i++) loc->forwardloc[i] = _getloc(db, &loc->record, i); /* make sure this record is complete */ r = check_tailcrc(db, &loc->record); if (r) return r; } return 0; } /* helper function to find a location, either by using the existing * location if it's close enough, or using the full relocate above */ static int find_loc(struct dbengine *db, const char *key, size_t keylen) { struct skiprecord newrecord; struct skiploc *loc = &db->loc; int cmp, i, r; if (key != loc->keybuf.s) buf_setmap(&loc->keybuf, key, keylen); else if (keylen != loc->keybuf.len) buf_truncate(&loc->keybuf, keylen); /* can we special case advance? */ if (keylen && loc->end == db->end && loc->generation == db->header.generation) { cmp = db->compar(KEY(db, &loc->record), loc->record.keylen, loc->keybuf.s, loc->keybuf.len); /* same place, and was exact. Otherwise we're going back, * and the reverse pointers are no longer valid... */ if (db->loc.is_exactmatch && cmp == 0) { return 0; } /* we're looking after this record */ if (cmp < 0) { for (i = 0; i < db->loc.record.level; i++) loc->backloc[i] = db->loc.record.offset; /* read the next record */ r = read_skipdelete(db, loc->forwardloc[0], &newrecord); if (r) return r; /* nothing afterwards? */ if (!newrecord.offset) { db->loc.is_exactmatch = 0; return 0; } /* now where is THIS record? */ cmp = db->compar(KEY(db, &newrecord), newrecord.keylen, loc->keybuf.s, loc->keybuf.len); /* exact match? */ if (cmp == 0) { db->loc.is_exactmatch = 1; db->loc.record = newrecord; for (i = 0; i < newrecord.level; i++) loc->forwardloc[i] = _getloc(db, &newrecord, i); /* make sure this record is complete */ r = check_tailcrc(db, &loc->record); if (r) return r; return 0; } /* or in the gap */ if (cmp > 0) { db->loc.is_exactmatch = 0; return 0; } } /* if we fell out here, it's not a "local" record, just search */ } return relocate(db); } /* helper function to advance to the "next" record. Used by foreach, * fetchnext, and internal functions */ static int advance_loc(struct dbengine *db) { struct skiploc *loc = &db->loc; uint8_t i; int r; /* has another session made changes? Need to re-find the location */ if (loc->end != db->end || loc->generation != db->header.generation) { r = relocate(db); if (r) return r; } /* update back pointers */ for (i = 0; i < loc->record.level; i++) loc->backloc[i] = loc->record.offset; /* ADVANCE */ r = read_skipdelete(db, loc->forwardloc[0], &loc->record); if (r) return r; /* reached the end? */ if (!loc->record.offset) { buf_reset(&loc->keybuf); return relocate(db); } /* update forward pointers */ for (i = 0; i < loc->record.level; i++) loc->forwardloc[i] = _getloc(db, &loc->record, i); /* keep our location */ buf_setmap(&loc->keybuf, KEY(db, &loc->record), loc->record.keylen); loc->is_exactmatch = 1; /* make sure this record is complete */ r = check_tailcrc(db, &loc->record); if (r) return r; return 0; } /* helper function to update all the back records efficiently * after appending a new record, either create or delete. The * caller must set forwardloc[] correctly for each level it has * changed */ static int stitch(struct dbengine *db, uint8_t maxlevel, size_t newoffset) { struct skiploc *loc = &db->loc; struct skiprecord oldrecord; uint8_t i; int r; oldrecord.level = 0; while (oldrecord.level < maxlevel) { uint8_t level = oldrecord.level; r = read_onerecord(db, loc->backloc[level], &oldrecord); if (r) return r; /* always getting higher */ assert(oldrecord.level > level); for (i = level; i < maxlevel; i++) _setloc(db, &oldrecord, i, loc->forwardloc[i]); r = rewrite_record(db, &oldrecord); if (r) return r; } /* re-read the "current record" */ r = read_onerecord(db, newoffset, &loc->record); if (r) return r; /* and update the forward locations */ for (i = 0; i < loc->record.level; i++) loc->forwardloc[i] = _getloc(db, &loc->record, i); return 0; } /* overall "store" function - update the value in the current loc. All new values funnel through here. Check delete_here for deletion. Force is implied here, it gets checked higher. */ static int store_here(struct dbengine *db, const char *val, size_t vallen) { struct skiploc *loc = &db->loc; struct skiprecord newrecord; uint8_t level = 0; uint8_t i; int r; if (loc->is_exactmatch) { level = loc->record.level; db->header.num_records--; } /* build a new record */ memset(&newrecord, 0, sizeof(struct skiprecord)); newrecord.type = RECORD; newrecord.level = randlvl(1, MAXLEVEL); newrecord.keylen = loc->keybuf.len; newrecord.vallen = vallen; for (i = 0; i < newrecord.level; i++) newrecord.nextloc[i+1] = loc->forwardloc[i]; if (newrecord.level > level) level = newrecord.level; /* append to the file */ r = append_record(db, &newrecord, loc->keybuf.s, val); if (r) return r; /* get the nextlevel to point here for all this record's levels */ for (i = 0; i < newrecord.level; i++) loc->forwardloc[i] = newrecord.offset; /* update all backpointers */ r = stitch(db, level, newrecord.offset); if (r) return r; /* update header to know details of new record */ db->header.num_records++; loc->is_exactmatch = 1; loc->end = db->end; return 0; } /* delete a record */ static int delete_here(struct dbengine *db) { struct skiploc *loc = &db->loc; struct skiprecord newrecord; struct skiprecord nextrecord; int r; if (!loc->is_exactmatch) return CYRUSDB_NOTFOUND; db->header.num_records--; /* by the magic of zeroing, this even works for zero */ r = read_skipdelete(db, loc->forwardloc[0], &nextrecord); if (r) return r; /* build a delete record */ memset(&newrecord, 0, sizeof(struct skiprecord)); newrecord.type = DELETE; newrecord.nextloc[0] = nextrecord.offset; /* append to the file */ r = append_record(db, &newrecord, NULL, NULL); if (r) return r; /* get the nextlevel to point here */ loc->forwardloc[0] = newrecord.offset; /* update all backpointers right up to the old record's * level, so that they all point past */ r = stitch(db, loc->record.level, loc->backloc[0]); if (r) return r; /* update location */ loc->is_exactmatch = 0; loc->end = db->end; return 0; } /************ DATABASE STRUCT AND TRANSACTION MANAGEMENT **************/ static int db_is_clean(struct dbengine *db) { if (db->header.current_size != SIZE(db)) return 0; if (db->header.flags & DIRTY) return 0; return 1; } static int unlock(struct dbengine *db) { return mappedfile_unlock(db->mf); } static int write_lock(struct dbengine *db) { int r = mappedfile_writelock(db->mf); if (r) return r; /* reread header */ if (db->is_open) { r = read_header(db); if (r) return r; /* recovery checks for consistency */ r = recovery(db); if (r) return r; } return 0; } static int read_lock(struct dbengine *db) { int r = mappedfile_readlock(db->mf); if (r) return r; /* reread header */ if (db->is_open) { r = read_header(db); if (r) return r; /* we just take and keep a write lock if inconsistent, * the write lock will fix it up */ if (!db_is_clean(db)) { unlock(db); r = write_lock(db); if (r) return r; /* downgrade to a read lock again, since that what * was requested */ unlock(db); return read_lock(db); } } return 0; } static int newtxn(struct dbengine *db, struct txn **tidptr) { int r; assert(!db->current_txn); assert(!*tidptr); /* grab a r/w lock */ r = write_lock(db); if (r) return r; /* create the transaction */ db->txn_num++; db->current_txn = xmalloc(sizeof(struct txn)); db->current_txn->num = db->txn_num; /* pass it back out */ *tidptr = db->current_txn; return 0; } static void dispose_db(struct dbengine *db) { if (!db) return; if (db->mf) { if (mappedfile_islocked(db->mf)) unlock(db); mappedfile_close(&db->mf); } buf_free(&db->loc.keybuf); free(db); } /************************************************************/ static int opendb(const char *fname, int flags, struct dbengine **ret) { struct dbengine *db; int r; int mappedfile_flags = MAPPEDFILE_RW; assert(fname); assert(ret); db = (struct dbengine *) xzmalloc(sizeof(struct dbengine)); if (flags & CYRUSDB_CREATE) mappedfile_flags |= MAPPEDFILE_CREATE; db->open_flags = flags & ~CYRUSDB_CREATE; db->compar = (flags & CYRUSDB_MBOXSORT) ? bsearch_ncompare_mbox : bsearch_ncompare_raw; r = mappedfile_open(&db->mf, fname, mappedfile_flags); if (r) { /* convert to CYRUSDB errors*/ if (r == -ENOENT) r = CYRUSDB_NOTFOUND; else r = CYRUSDB_IOERROR; goto done; } db->is_open = 0; /* grab a read lock, only reading the header */ r = read_lock(db); if (r) goto done; /* if there's any issue which requires fixing, get a write lock */ if (0) { retry_write: unlock(db); db->is_open = 0; r = write_lock(db); if (r) goto done; } /* if the map size is zero, it's a new file - we need to create an * initial header */ if (mappedfile_size(db->mf) == 0) { struct skiprecord dummy; if (!mappedfile_iswritelocked(db->mf)) goto retry_write; /* create the dummy! */ memset(&dummy, 0, sizeof(struct skiprecord)); dummy.type = DUMMY; dummy.level = MAXLEVEL; /* append dummy after header location */ db->end = DUMMY_OFFSET; r = write_record(db, &dummy, NULL, NULL); if (r) { syslog(LOG_ERR, "DBERROR: writing dummy node for %s: %m", fname); goto done; } /* create the header */ db->header.version = VERSION; db->header.generation = 1; db->header.repack_size = db->end; db->header.current_size = db->end; r = commit_header(db); if (r) { syslog(LOG_ERR, "DBERROR: writing header for %s: %m", fname); goto done; } } db->is_open = 1; r = read_header(db); if (r) goto done; if (!db_is_clean(db)) { if (!mappedfile_iswritelocked(db->mf)) goto retry_write; /* recovery will clean the flag once it's committed the fixes */ r = recovery(db); if (r) goto done; } /* unlock the DB */ unlock(db); *ret = db; done: if (r) dispose_db(db); return r; } static int myopen(const char *fname, int flags, struct dbengine **ret) { struct db_list *ent; struct dbengine *mydb; int r; /* do we already have this DB open? */ for (ent = open_twoskip; ent; ent = ent->next) { if (strcmp(FNAME(ent->db), fname)) continue; ent->refcount++; *ret = ent->db; return 0; } r = opendb(fname, flags, &mydb); if (r) return r; /* track this database in the open list */ ent = (struct db_list *) xzmalloc(sizeof(struct db_list)); ent->db = mydb; ent->refcount = 1; ent->next = open_twoskip; open_twoskip = ent; /* return the open DB */ *ret = mydb; return 0; } static int myclose(struct dbengine *db) { struct db_list *ent = open_twoskip; struct db_list *prev = NULL; assert(db); /* remove this DB from the open list */ while (ent && ent->db != db) { prev = ent; ent = ent->next; } assert(ent); if (--ent->refcount <= 0) { if (prev) prev->next = ent->next; else open_twoskip = ent->next; free(ent); if (mappedfile_islocked(db->mf)) syslog(LOG_ERR, "twoskip: %s closed while still locked", FNAME(db)); dispose_db(db); } return 0; } /*************** EXTERNAL APIS ***********************/ static int myfetch(struct dbengine *db, const char *key, size_t keylen, const char **foundkey, size_t *foundkeylen, const char **data, size_t *datalen, struct txn **tidptr, int fetchnext) { int r = 0; assert(db); if (datalen) assert(data); if (data) *data = NULL; if (datalen) *datalen = 0; /* Hacky workaround: * * If no transaction was passed, but we're in a transaction, * then just do the read within that transaction. */ if (!tidptr && db->current_txn) tidptr = &db->current_txn; if (tidptr) { if (!*tidptr) { r = newtxn(db, tidptr); if (r) return r; } } else { /* grab a r lock */ r = read_lock(db); if (r) return r; } r = find_loc(db, key, keylen); if (r) goto done; if (fetchnext) { r = advance_loc(db); if (r) goto done; } if (foundkey) *foundkey = db->loc.keybuf.s; if (foundkeylen) *foundkeylen = db->loc.keybuf.len; if (!r && db->loc.is_exactmatch) { if (data) *data = VAL(db, &db->loc.record); if (datalen) *datalen = db->loc.record.vallen; } else { /* we didn't get an exact match */ r = CYRUSDB_NOTFOUND; } done: if (!tidptr) { /* release read lock */ int r1; if ((r1 = unlock(db)) < 0) { return r1; } } return r; } /* foreach allows for subsidary mailbox operations in 'cb'. if there is a txn, 'cb' must make use of it. */ static int myforeach(struct dbengine *db, const char *prefix, size_t prefixlen, foreach_p *goodp, foreach_cb *cb, void *rock, struct txn **tidptr) { int r = 0, cb_r = 0; int need_unlock = 0; const char *val; size_t vallen; struct buf keybuf = BUF_INITIALIZER; assert(db); assert(cb); if (prefixlen) assert(prefix); /* Hacky workaround: * * If no transaction was passed, but we're in a transaction, * then just do the read within that transaction. */ if (!tidptr && db->current_txn) tidptr = &db->current_txn; if (tidptr) { if (!*tidptr) { r = newtxn(db, tidptr); if (r) return r; } } else { /* grab a r lock */ r = read_lock(db); if (r) return r; need_unlock = 1; } r = find_loc(db, prefix, prefixlen); if (r) goto done; if (!db->loc.is_exactmatch) { /* advance to the first match */ r = advance_loc(db); if (r) goto done; } while (db->loc.is_exactmatch) { /* does it match prefix? */ if (prefixlen) { if (db->loc.record.keylen < prefixlen) break; if (db->compar(KEY(db, &db->loc.record), prefixlen, prefix, prefixlen)) break; } val = VAL(db, &db->loc.record); vallen = db->loc.record.vallen; if (!goodp || goodp(rock, db->loc.keybuf.s, db->loc.keybuf.len, val, vallen)) { if (!tidptr) { /* release read lock */ r = unlock(db); if (r) goto done; need_unlock = 0; } /* take a copy of they key - just in case cb does actions on this database * and clobbers loc */ buf_copy(&keybuf, &db->loc.keybuf); /* make callback */ cb_r = cb(rock, db->loc.keybuf.s, db->loc.keybuf.len, val, vallen); if (cb_r) break; if (!tidptr) { /* grab a r lock */ r = read_lock(db); if (r) goto done; need_unlock = 1; } /* should be cheap if we're already here */ r = find_loc(db, keybuf.s, keybuf.len); if (r) goto done; } /* move to the next one */ r = advance_loc(db); if (r) goto done; } done: buf_free(&keybuf); if (need_unlock) { /* release read lock */ int r1 = unlock(db); if (r1) return r1; } return r ? r : cb_r; } /* helper function for all writes - wraps create and delete and the FORCE * logic for each */ static int skipwrite(struct dbengine *db, const char *key, size_t keylen, const char *data, size_t datalen, int force) { int r = find_loc(db, key, keylen); if (r) return r; /* could be a delete or a replace */ if (db->loc.is_exactmatch) { if (!data) return delete_here(db); if (!force) return CYRUSDB_EXISTS; /* unchanged? Save the IO */ if (!db->compar(data, datalen, VAL(db, &db->loc.record), db->loc.record.vallen)) return 0; return store_here(db, data, datalen); } /* only create if it's not a delete, obviously */ if (data) return store_here(db, data, datalen); /* must be a delete - are we forcing? */ if (!force) return CYRUSDB_NOTFOUND; return 0; } static int mycommit(struct dbengine *db, struct txn *tid) { struct skiprecord newrecord; int r = 0; assert(db); assert(tid == db->current_txn); /* no need to abort if we're not dirty */ if (!(db->header.flags & DIRTY)) goto done; /* build a commit record */ memset(&newrecord, 0, sizeof(struct skiprecord)); newrecord.type = COMMIT; newrecord.nextloc[0] = db->header.current_size; /* append to the file */ r = append_record(db, &newrecord, NULL, NULL); if (r) goto done; /* commit ALL outstanding changes first, before * rewriting the header */ r = mappedfile_commit(db->mf); if (r) goto done; /* finally, update the header and commit again */ db->header.current_size = db->end; db->header.flags &= ~DIRTY; r = commit_header(db); done: if (r) { int r2; /* error during commit; we must abort */ r2 = myabort(db, tid); if (r2) { syslog(LOG_ERR, "DBERROR: twoskip %s: commit AND abort failed", FNAME(db)); } } else { /* consider checkpointing */ int diff = db->header.current_size - db->header.repack_size; if (diff > MINREWRITE && ((float)diff / (float)db->header.current_size) > REWRITE_RATIO) { int r2 = mycheckpoint(db); if (r2) { syslog(LOG_NOTICE, "twoskip: failed to checkpoint %s: %m", FNAME(db)); } } else unlock(db); free(tid); db->current_txn = NULL; } return r; } static int myabort(struct dbengine *db, struct txn *tid) { int r; assert(db); assert(tid == db->current_txn); /* free the tid */ free(tid); db->current_txn = NULL; db->end = db->header.current_size; /* recovery will clean up */ r = recovery1(db, NULL); buf_free(&db->loc.keybuf); memset(&db->loc, 0, sizeof(struct skiploc)); unlock(db); return r; } static int mystore(struct dbengine *db, const char *key, size_t keylen, const char *data, size_t datalen, struct txn **tidptr, int force) { struct txn *localtid = NULL; int r = 0; int r2 = 0; assert(db); assert(key && keylen); /* not keeping the transaction, just create one local to * this function */ if (!tidptr) tidptr = &localtid; /* make sure we're write locked and up to date */ if (!*tidptr) { r = newtxn(db, tidptr); if (r) return r; } r = skipwrite(db, key, keylen, data, datalen, force); if (r) { r2 = myabort(db, *tidptr); *tidptr = NULL; } else if (localtid) { /* commit the store, which releases the write lock */ r = mycommit(db, localtid); } return r2 ? r2 : r; } /* compress 'db', closing at the end. Uses foreach to copy into a new * database, then rewrites over the old one */ struct copy_rock { struct dbengine *db; struct txn *tid; }; static int copy_cb(void *rock, const char *key, size_t keylen, const char *val, size_t vallen) { struct copy_rock *cr = (struct copy_rock *)rock; return mystore(cr->db, key, keylen, val, vallen, &cr->tid, 0); } static int mycheckpoint(struct dbengine *db) { size_t old_size = db->header.current_size; char newfname[1024]; clock_t start = sclock(); struct copy_rock cr; int r = 0; r = myconsistent(db, db->current_txn); if (r) { syslog(LOG_ERR, "db %s, inconsistent pre-checkpoint, bailing out", FNAME(db)); unlock(db); return r; } /* open fname.NEW */ snprintf(newfname, sizeof(newfname), "%s.NEW", FNAME(db)); unlink(newfname); cr.db = NULL; cr.tid = NULL; r = opendb(newfname, db->open_flags | CYRUSDB_CREATE, &cr.db); if (r) return r; r = myforeach(db, NULL, 0, NULL, copy_cb, &cr, &db->current_txn); if (r) goto err; r = myconsistent(cr.db, cr.tid); if (r) { syslog(LOG_ERR, "db %s, inconsistent post-checkpoint, bailing out", FNAME(db)); goto err; } /* remember the repack size */ cr.db->header.repack_size = cr.db->end; /* increase the generation count */ cr.db->header.generation = db->header.generation + 1; r = mycommit(cr.db, cr.tid); if (r) goto err; /* move new file to original file name */ r = mappedfile_rename(cr.db->mf, FNAME(db)); if (r) goto err; /* OK, we're commmitted now - clean up */ unlock(db); /* gotta clean it all up */ mappedfile_close(&db->mf); buf_free(&db->loc.keybuf); *db = *cr.db; free(cr.db); /* leaked? */ { syslog(LOG_INFO, "twoskip: checkpointed %s (%llu record%s, %llu => %llu bytes) in %2.3f seconds", FNAME(db), (LLU)db->header.num_records, db->header.num_records == 1 ? "" : "s", (LLU)old_size, (LLU)(db->header.current_size), (sclock() - start) / (double) CLOCKS_PER_SEC); } return 0; err: if (cr.tid) myabort(cr.db, cr.tid); unlink(FNAME(cr.db)); dispose_db(cr.db); unlock(db); return CYRUSDB_IOERROR; } /* dump the database. if detail == 1, dump all records. if detail == 2, also dump pointers for active records. if detail == 3, dump all records/all pointers. */ static int dump(struct dbengine *db, int detail __attribute__((unused))) { struct skiprecord record; struct buf scratch = BUF_INITIALIZER; size_t offset = DUMMY_OFFSET; int r = 0; int i; printf("HEADER: v=%lu fl=%lu num=%llu sz=(%08llX/%08llX)\n", (LU)db->header.version, (LU)db->header.flags, (LLU)db->header.num_records, (LLU)db->header.current_size, (LLU)db->header.repack_size); while (offset < db->header.current_size) { printf("%08llX ", (LLU)offset); r = read_onerecord(db, offset, &record); if (r) { printf("ERROR\n"); break; } switch (record.type) { case DELETE: printf("DELETE ptr=%08llX\n", (LLU)record.nextloc[0]); break; case COMMIT: printf("COMMIT start=%08llX\n", (LLU)record.nextloc[0]); break; case RECORD: case DUMMY: buf_setmap(&scratch, KEY(db, &record), record.keylen); buf_replace_char(&scratch, '\0', '-'); printf("%s kl=%llu dl=%llu lvl=%d (%s)\n", (record.type == RECORD ? "RECORD" : "DUMMY"), (LLU)record.keylen, (LLU)record.vallen, record.level, buf_cstring(&scratch)); printf("\t"); for (i = 0; i <= record.level; i++) { printf("%08llX ", (LLU)record.nextloc[i]); if (!(i % 8)) printf("\n\t"); } printf("\n"); break; } offset += record.len; } buf_free(&scratch); return r; } static int consistent(struct dbengine *db) { int r; r = read_lock(db); if (r) return r; r = myconsistent(db, NULL); unlock(db); return r; } /* perform some basic consistency checks */ static int myconsistent(struct dbengine *db, struct txn *tid) { struct skiprecord prevrecord; struct skiprecord record; size_t fwd[MAXLEVEL]; size_t num_records = 0; int r = 0; int cmp; int i; assert(db->current_txn == tid); /* could both be null */ /* read in the dummy */ r = read_onerecord(db, DUMMY_OFFSET, &prevrecord); if (r) return r; /* set up the location pointers */ for (i = 0; i < MAXLEVEL; i++) fwd[i] = _getloc(db, &prevrecord, i); while (fwd[0]) { r = read_onerecord(db, fwd[0], &record); if (r) return r; if (record.type == DELETE) { fwd[0] = record.nextloc[0]; continue; } cmp = db->compar(KEY(db, &record), record.keylen, KEY(db, &prevrecord), prevrecord.keylen); if (cmp <= 0) { syslog(LOG_ERR, "DBERROR: twoskip out of order %s: %.*s (%08llX) <= %.*s (%08llX)", FNAME(db), (int)record.keylen, KEY(db, &record), (LLU)record.offset, (int)prevrecord.keylen, KEY(db, &prevrecord), (LLU)prevrecord.offset); return CYRUSDB_INTERNAL; } for (i = 0; i < record.level; i++) { /* check the old pointer was to here */ if (fwd[i] != record.offset) { syslog(LOG_ERR, "DBERROR: twoskip broken linkage %s: %08llX at %d, expected %08llX", FNAME(db), (LLU)record.offset, i, (LLU)fwd[i]); return CYRUSDB_INTERNAL; } /* and advance to the new pointer */ fwd[i] = _getloc(db, &record, i); } /* keep a copy for comparison purposes */ num_records++; prevrecord = record; } for (i = 0; i < MAXLEVEL; i++) { if (fwd[i]) { syslog(LOG_ERR, "DBERROR: twoskip broken tail %s: %08llX at %d", FNAME(db), (LLU)fwd[i], i); return CYRUSDB_INTERNAL; } } /* we walked the whole file and saw every pointer */ if (num_records != db->header.num_records) { syslog(LOG_ERR, "DBERROR: twoskip record count mismatch %s: %llu should be %llu", FNAME(db), (LLU)num_records, (LLU)db->header.num_records); return CYRUSDB_INTERNAL; } return 0; } static int _copy_commit(struct dbengine *db, struct dbengine *newdb, struct skiprecord *commit) { struct txn *tid = NULL; struct skiprecord record; const char *val; size_t offset; int r = 0; for (offset = commit->nextloc[0]; offset < commit->offset; offset += record.len) { r = read_onerecord(db, offset, &record); if (r) goto err; switch (record.type) { case DELETE: val = NULL; break; case RECORD: val = VAL(db, &record); break; default: r = CYRUSDB_IOERROR; goto err; } /* store into the new DB */ r = mystore(newdb, KEY(db, &record), record.keylen, val, record.vallen, &tid, 1); if (r) goto err; } if (tid) r = mycommit(newdb, tid); if (r) return r; return 0; err: if (tid) myabort(newdb, tid); return r; } /* recovery2 - the file is really screwed. Basically, we * failed to run recovery. Try reading out records from * the top and applying commits to a new file instead */ static int recovery2(struct dbengine *db, int *count) { uint64_t oldcount = db->header.num_records; struct skiprecord record; struct dbengine *newdb = NULL; char newfname[1024]; size_t offset; int r = 0; /* open fname.NEW */ snprintf(newfname, sizeof(newfname), "%s.NEW", FNAME(db)); unlink(newfname); r = opendb(newfname, db->open_flags | CYRUSDB_CREATE, &newdb); if (r) return r; /* increase the generation count */ newdb->header.generation = db->header.generation + 1; /* start with the dummy */ for (offset = DUMMY_OFFSET; offset < SIZE(db); offset += record.len) { r = read_onerecord(db, offset, &record); if (r) { syslog(LOG_ERR, "DBERROR: %s failed to read at %08llX in recovery2, truncating", FNAME(db), (LLU)offset); break; } if (record.type == COMMIT) { r = _copy_commit(db, newdb, &record); if (r) { syslog(LOG_ERR, "DBERROR: %s failed to apply commit at %08llX in recovery2, truncating", FNAME(db), (LLU)offset); break; } } } if (!newdb->header.num_records) { /* no records found - almost certainly bogus, and even if not, * there's no point recovering a zero record file */ syslog(LOG_ERR, "DBERROR: %s no records found in recovery2, aborting", FNAME(db)); r = CYRUSDB_NOTFOUND; goto err; } /* regardless, we had a commit during create, and in any _copy_commit, so * rename into place */ /* move new file to original file name */ r = mappedfile_rename(newdb->mf, FNAME(db)); if (r) goto err; /* OK, we're commmitted now - clean up */ unlock(db); /* gotta clean it all up */ mappedfile_close(&db->mf); buf_free(&db->loc.keybuf); *db = *newdb; free(newdb); /* leaked? */ syslog(LOG_NOTICE, "twoskip: recovery2 %s - rescued %llu of %llu records", FNAME(db), (LLU)db->header.num_records, (LLU)oldcount); if (count) *count = db->header.num_records; return 0; err: unlink(FNAME(newdb)); myclose(newdb); return r; } /* run recovery on this file. * always called with a write lock. */ static int recovery1(struct dbengine *db, int *count) { size_t prev[MAXLEVEL+1]; size_t next[MAXLEVEL+1]; struct skiprecord record; struct skiprecord prevrecord; struct skiprecord fixrecord; size_t nextoffset = 0; uint64_t num_records = 0; int changed = 0; int r = 0; int cmp; int i; assert(mappedfile_iswritelocked(db->mf)); /* no need to run recovery if we're consistent */ if (db_is_clean(db)) return 0; /* we can't recovery a file that's not created yet */ assert(db->header.current_size > HEADER_SIZE); /* dirty the header if not already dirty */ if (!(db->header.flags & DIRTY)) { db->header.flags |= DIRTY; r = commit_header(db); if (r) return r; } /* start with the dummy */ r = read_onerecord(db, DUMMY_OFFSET, &prevrecord); if (r) return r; /* and pointers forwards */ for (i = 2; i <= MAXLEVEL; i++) { prev[i] = prevrecord.offset; next[i] = prevrecord.nextloc[i]; } /* check for broken level - pointers */ for (i = 0; i < 2; i++) { if (prevrecord.nextloc[i] >= db->end) { prevrecord.nextloc[i] = 0; r = rewrite_record(db, &prevrecord); changed++; } } nextoffset = _getloc(db, &prevrecord, 0); while (nextoffset) { r = read_onerecord(db, nextoffset, &record); if (r) return r; /* just skip over delele records */ if (record.type == DELETE) { nextoffset = record.nextloc[0]; continue; } cmp = db->compar(KEY(db, &record), record.keylen, KEY(db, &prevrecord), prevrecord.keylen); if (cmp <= 0) { syslog(LOG_ERR, "DBERROR: twoskip out of order %s: %.*s (%08llX) <= %.*s (%08llX)", FNAME(db), (int)record.keylen, KEY(db, &record), (LLU)record.offset, (int)prevrecord.keylen, KEY(db, &prevrecord), (LLU)prevrecord.offset); return CYRUSDB_INTERNAL; } /* check for old offsets needing fixing */ for (i = 2; i <= record.level; i++) { if (next[i] != record.offset) { /* need to fix up the previous record to point here */ r = read_onerecord(db, prev[i], &fixrecord); if (r) return r; /* XXX - optimise adjacent same records */ fixrecord.nextloc[i] = record.offset; r = rewrite_record(db, &fixrecord); if (r) return r; changed++; } prev[i] = record.offset; next[i] = record.nextloc[i]; } /* check for broken level - pointers */ for (i = 0; i < 2; i++) { if (record.nextloc[i] >= db->end) { record.nextloc[i] = 0; r = rewrite_record(db, &record); changed++; } } num_records++; /* find the next record */ nextoffset = _getloc(db, &record, 0); prevrecord = record; } /* check for remaining offsets needing fixing */ for (i = 2; i <= MAXLEVEL; i++) { if (next[i]) { /* need to fix up the previous record to point to the end */ r = read_onerecord(db, prev[i], &fixrecord); if (r) return r; /* XXX - optimise, same as above */ fixrecord.nextloc[i] = 0; r = rewrite_record(db, &fixrecord); if (r) return r; changed++; } } r = mappedfile_truncate(db->mf, db->header.current_size); if (r) return r; r = mappedfile_commit(db->mf); if (r) return r; /* clear the dirty flag */ db->header.flags &= ~DIRTY; db->header.num_records = num_records; r = commit_header(db); if (r) return r; if (count) *count = changed; return 0; } static int recovery(struct dbengine *db) { clock_t start = sclock(); int count = 0; int r; /* no need to run recovery if we're consistent */ if (db_is_clean(db)) return 0; r = recovery1(db, &count); if (r) { syslog(LOG_ERR, "DBERROR: recovery1 failed %s, trying recovery2", FNAME(db)); count = 0; r = recovery2(db, &count); if (r) return r; } { syslog(LOG_INFO, "twoskip: recovered %s (%llu record%s, %llu bytes) in %2.3f seconds - fixed %d offset%s", FNAME(db), (LLU)db->header.num_records, db->header.num_records == 1 ? "" : "s", (LLU)(db->header.current_size), (sclock() - start) / (double) CLOCKS_PER_SEC, count, count == 1 ? "" : "s"); } return 0; } static int fetch(struct dbengine *mydb, const char *key, size_t keylen, const char **data, size_t *datalen, struct txn **tidptr) { assert(key); assert(keylen); return myfetch(mydb, key, keylen, NULL, NULL, data, datalen, tidptr, 0); } static int fetchnext(struct dbengine *mydb, const char *key, size_t keylen, const char **foundkey, size_t *fklen, const char **data, size_t *datalen, struct txn **tidptr) { return myfetch(mydb, key, keylen, foundkey, fklen, data, datalen, tidptr, 1); } static int create(struct dbengine *db, const char *key, size_t keylen, const char *data, size_t datalen, struct txn **tid) { if (datalen) assert(data); return mystore(db, key, keylen, data ? data : "", datalen, tid, 0); } static int store(struct dbengine *db, const char *key, size_t keylen, const char *data, size_t datalen, struct txn **tid) { if (datalen) assert(data); return mystore(db, key, keylen, data ? data : "", datalen, tid, 1); } static int delete(struct dbengine *db, const char *key, size_t keylen, struct txn **tid, int force) { return mystore(db, key, keylen, NULL, 0, tid, force); } /* twoskip compar function is set at open */ static int mycompar(struct dbengine *db, const char *a, int alen, const char *b, int blen) { return db->compar(a, alen, b, blen); } HIDDEN struct cyrusdb_backend cyrusdb_twoskip = { "twoskip", /* name */ &cyrusdb_generic_init, &cyrusdb_generic_done, &cyrusdb_generic_sync, &cyrusdb_generic_archive, &myopen, &myclose, &fetch, &fetch, &fetchnext, &myforeach, &create, &store, &delete, &mycommit, &myabort, &dump, &consistent, &mycheckpoint, &mycompar }; cyrus-imapd-2.5.10/lib/cyrusdb_skiplist.c0000644000175000017500000017216013001236020015256 00000000000000/* cyrusdb_skiplist.c -- cyrusdb skiplist implementation * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ /* xxx check retry_xxx for failure */ /* xxx all offsets should be uint32_ts i think */ #include #include #include #include #include #include #include #include #include #ifdef HAVE_UNISTD_H #include #endif #include #include "assert.h" #include "bsearch.h" #include "cyrusdb.h" #include "libcyr_cfg.h" #include "cyr_lock.h" #include "map.h" #include "retry.h" #include "util.h" #include "xmalloc.h" #define PROB (0.5) /* * * disk format; all numbers in network byte order * * there's the data file, consisting of the * multiple records of "key", "data", and "skip pointers", where skip * pointers are the record number of the data pointer. * * on startup, recovery is performed. the last known good data file * is taken and the intent log is replayed on it. the index file is * regenerated from scratch. * * during operation ckecpoints will compress the data. the data file * is locked. then a checkpoint rewrites the data file in order, * removing any unused records. this is written and fsync'd to * dfile.NEW and stored for use during recovery. */ /* header "skiplist file\0\0\0" version (4 bytes) version_minor (4 bytes) maxlevel (4 bytes) curlevel (4 bytes) listsize (4 bytes) in active items log start (4 bytes) offset where log records start, used mainly to tell when to compress last recovery (4 bytes) seconds since unix epoch 1 or more skipnodes, one of: record type (4 bytes) [DUMMY, INORDER, ADD] key size (4 bytes) key string (bit string, rounded to up to 4 byte multiples w/ 0s) data size (4 bytes) data string (bit string, rounded to up to 4 byte multiples w/ 0s) skip pointers (4 bytes each) least to most padding (4 bytes, must be -1) record type (4 bytes) [DELETE] record ptr (4 bytes; record to be deleted) record type (4 bytes) [COMMIT] record type is either DUMMY (first node is of this type) INORDER ADD DELETE COMMIT (commit the previous records) */ enum { INORDER = 1, ADD = 2, DELETE = 4, COMMIT = 255, DUMMY = 257 }; enum { UNLOCKED = 0, READLOCKED = 1, WRITELOCKED = 2, }; struct txn { int syncfd; /* logstart is where we start changes from on commit, where we truncate to on abort */ unsigned logstart; unsigned logend; /* where to write to continue this txn */ }; struct dbengine { /* file data */ char *fname; int fd; const char *map_base; size_t map_len; /* mapped size */ size_t map_size; /* actual size */ ino_t map_ino; /* header info */ uint32_t version; uint32_t version_minor; uint32_t maxlevel; uint32_t curlevel; uint32_t listsize; uint32_t logstart; /* where the log starts from last chkpnt */ time_t last_recovery; /* tracking info */ int lock_status; int is_open; struct txn *current_txn; struct timeval starttime; /* comparator function to use for sorting */ int (*compar) (const char *s1, int l1, const char *s2, int l2); }; struct db_list { struct dbengine *db; struct db_list *next; int refcount; }; static time_t global_recovery = 0; static struct db_list *open_db = NULL; /* Perform an FSYNC/FDATASYNC if we are *not* operating in UNSAFE mode */ #define DO_FSYNC (!libcyrus_config_getswitch(CYRUSOPT_SKIPLIST_UNSAFE)) enum { be_paranoid = 0, use_osync = 0 }; static void getsyncfd(struct dbengine *db, struct txn *t) { if (!use_osync) { t->syncfd = db->fd; } else if (t->syncfd == -1) { t->syncfd = open(db->fname, O_RDWR | O_DSYNC, 0666); assert(t->syncfd != -1); /* xxx do better error recovery */ } } static void closesyncfd(struct dbengine *db __attribute__((unused)), struct txn *t) { /* if we're using fsync, then we don't want to close the file */ if (use_osync && (t->syncfd != -1)) { close(t->syncfd); } t->syncfd = -1; } static int myinit(const char *dbdir, int myflags) { char sfile[1024]; int fd = -1, r = 0; uint32_t net32_time; snprintf(sfile, sizeof(sfile), "%s/skipstamp", dbdir); if (myflags & CYRUSDB_RECOVER) { struct stat sbuf; char cleanfile[1024]; snprintf(cleanfile, sizeof(cleanfile), "%s/skipcleanshutdown", dbdir); /* if we had a clean shutdown, we don't need to run recovery on * everything */ if (stat(cleanfile, &sbuf) == 0) { syslog(LOG_NOTICE, "skiplist: clean shutdown detected, starting normally"); unlink(cleanfile); goto normal; } syslog(LOG_NOTICE, "skiplist: clean shutdown file missing, updating recovery stamp"); /* set the recovery timestamp; all databases earlier than this time need recovery run when opened */ global_recovery = time(NULL); fd = open(sfile, O_RDWR | O_CREAT, 0644); if (fd == -1) r = -1; if (r != -1) r = ftruncate(fd, 0); net32_time = htonl(global_recovery); if (r != -1) r = write(fd, &net32_time, 4); xclose(fd); if (r == -1) { syslog(LOG_ERR, "DBERROR: writing %s: %m", sfile); xclose(fd); return CYRUSDB_IOERROR; } } else { normal: /* read the global recovery timestamp */ fd = open(sfile, O_RDONLY, 0644); if (fd == -1) r = -1; if (r != -1) r = read(fd, &net32_time, 4); xclose(fd); if (r == -1) { syslog(LOG_ERR, "DBERROR: reading %s, assuming the worst: %m", sfile); global_recovery = 0; } else { global_recovery = ntohl(net32_time); } } srand(time(NULL) * getpid()); open_db = NULL; return 0; } enum { SKIPLIST_VERSION = 1, SKIPLIST_VERSION_MINOR = 2, SKIPLIST_MAXLEVEL = 20, SKIPLIST_MINREWRITE = 16834 /* don't rewrite logs smaller than this */ }; #define HEADER_MAGIC ("\241\002\213\015skiplist file\0\0\0") #define HEADER_MAGIC_SIZE (20) /* offsets of header files */ enum { OFFSET_HEADER = 0, OFFSET_VERSION = 20, OFFSET_VERSION_MINOR = 24, OFFSET_MAXLEVEL = 28, OFFSET_CURLEVEL = 32, OFFSET_LISTSIZE = 36, OFFSET_LOGSTART = 40, OFFSET_LASTRECOVERY = 44 }; enum { HEADER_SIZE = OFFSET_LASTRECOVERY + 4 }; static int mycommit(struct dbengine *db, struct txn *tid); static int myabort(struct dbengine *db, struct txn *tid); static int mycheckpoint(struct dbengine *db); static int myconsistent(struct dbengine *db, struct txn *tid, int locked); static int recovery(struct dbengine *db, int flags); enum { /* Force recovery regardless of timestamp on database */ RECOVERY_FORCE = 1, /* Caller already has a write lock on the database. In the case * of successful recovery, the database will still be locked on return. * * If the recovery fails, then the database will be unlocked an an * error will be returned */ RECOVERY_CALLER_LOCKED = 2 }; /* file looks like: struct header { ... } struct dummy { uint32_t t = htonl(DUMMY); uint32_t ks = 0; uint32_t ds = 0; uint32_t forward[db->maxlevel]; uint32_t pad = -1; } */ #define DUMMY_OFFSET(db) (HEADER_SIZE) #define DUMMY_PTR(db) ((db)->map_base + HEADER_SIZE) #define DUMMY_SIZE(db) (4 * (3 + db->maxlevel + 1)) /* bump to the next multiple of 4 bytes */ #define ROUNDUP(num) (((num) + 3) & 0xFFFFFFFC) #define TYPE(ptr) (ntohl(*((uint32_t *)(ptr)))) #define KEY(ptr) ((ptr) + 8) #define KEYLEN(ptr) (ntohl(*((uint32_t *)((ptr) + 4)))) #define DATA(ptr) ((ptr) + 8 + ROUNDUP(KEYLEN(ptr)) + 4) #define DATALEN(ptr) (ntohl(*((uint32_t *)((ptr) + 8 + ROUNDUP(KEYLEN(ptr)))))) #define FIRSTPTR(ptr) ((ptr) + 8 + ROUNDUP(KEYLEN(ptr)) + 4 + ROUNDUP(DATALEN(ptr))) /* return a pointer to the pointer */ #define PTR(ptr, x) (FIRSTPTR(ptr) + 4 * (x)) /* FORWARD(ptr, x) * given a pointer to the start of the record, return the offset * corresponding to the xth pointer */ #define FORWARD(ptr, x) (ntohl(*((uint32_t *)(FIRSTPTR(ptr) + 4 * (x))))) static int is_safe(struct dbengine *db, const char *ptr) { if (ptr < db->map_base) return 0; if (ptr > db->map_base + db->map_size) return 0; return 1; } static unsigned LEVEL_safe(struct dbengine *db, const char *ptr) { const uint32_t *p, *q; assert(TYPE(ptr) == DUMMY || TYPE(ptr) == INORDER || TYPE(ptr) == ADD); if (!is_safe(db, ptr + 12)) return 0; if (!is_safe(db, ptr + 12 + KEYLEN(ptr))) return 0; p = q = (uint32_t *) FIRSTPTR(ptr); if (!is_safe(db, (const char *)p)) return 0; while (*p != (uint32_t)-1) { p++; if (!is_safe(db, (const char *)p)) return 0; } return (p - q); } /* how big is this record? */ static unsigned RECSIZE_safe(struct dbengine *db, const char *ptr) { int ret = 0; int level; switch (TYPE(ptr)) { case DUMMY: case INORDER: case ADD: level = LEVEL_safe(db, ptr); if (!level) { syslog(LOG_ERR, "IOERROR: skiplist RECSIZE not safe %s, offset %u", db->fname, (unsigned)(ptr - db->map_base)); return 0; } ret += 4; /* tag */ ret += 4; /* keylen */ ret += ROUNDUP(KEYLEN(ptr)); /* key */ ret += 4; /* datalen */ ret += ROUNDUP(DATALEN(ptr)); /* data */ ret += 4 * level; /* pointers */ ret += 4; /* padding */ break; case DELETE: if (!is_safe(db, ptr+8)) { syslog(LOG_ERR, "IOERROR: skiplist RECSIZE not safe %s, offset %u", db->fname, (unsigned)(ptr - db->map_base)); return 0; } ret += 8; break; case COMMIT: if (!is_safe(db, ptr+4)) { syslog(LOG_ERR, "IOERROR: skiplist RECSIZE not safe %s, offset %u", db->fname, (unsigned)(ptr - db->map_base)); return 0; } ret += 4; break; } return ret; } /* Determine if it is safe to append to this skiplist database. * e.g. does it end in 4 bytes of -1 followed by a commit record? * *or* does it end with 'DELETE' + 4 bytes + a commit record? * *or* is this the beginning of the log, in which case we only need * the padding from the last INORDER (or DUMMY) record */ static int SAFE_TO_APPEND(struct dbengine *db) { /* check it's a multiple of 4 */ if (db->map_size % 4) return 1; /* is it the beginning of the log? */ if (db->map_size == db->logstart) { if (*((uint32_t *)(db->map_base + db->map_size - 4)) != htonl(-1)) { return 1; } } /* in the middle of the log somewhere */ else { if (*((uint32_t *)(db->map_base + db->map_size - 4)) != htonl(COMMIT)) { return 1; } /* if it's not an end of a record or a delete */ if (!((*((uint32_t *)(db->map_base + db->map_size - 8)) == htonl(-1)) || (*((uint32_t *)(db->map_base + db->map_size -12)) == htonl(DELETE)))) { return 1; } } return 0; } static int newtxn(struct dbengine *db, struct txn **tidptr) { struct txn *tid; /* is this file safe to append to? * * If it isn't, we need to run recovery. */ if (SAFE_TO_APPEND(db)) { int r = recovery(db, RECOVERY_FORCE | RECOVERY_CALLER_LOCKED); if (r) return r; } /* create the transaction */ tid = xmalloc(sizeof(struct txn)); tid->syncfd = -1; tid->logstart = db->map_size; /* assert(t->logstart != -1);*/ tid->logend = tid->logstart; db->current_txn = tid; /* pass it back out */ *tidptr = tid; return 0; } static unsigned PADDING_safe(struct dbengine *db, const char *ptr) { unsigned size = RECSIZE_safe(db, ptr); if (!size) return 0; return ntohl(*((uint32_t *)((ptr) + size - 4))); } /* given an open, mapped db, read in the header information */ static int read_header(struct dbengine *db) { const char *dptr; int r; assert(db && db->map_len && db->fname && db->map_base && db->is_open && db->lock_status); if (db->map_len < HEADER_SIZE) { syslog(LOG_ERR, "skiplist: file not large enough for header: %s", db->fname); } if (memcmp(db->map_base, HEADER_MAGIC, HEADER_MAGIC_SIZE)) { syslog(LOG_ERR, "skiplist: invalid magic header: %s", db->fname); return CYRUSDB_IOERROR; } db->version = ntohl(*((uint32_t *)(db->map_base + OFFSET_VERSION))); db->version_minor = ntohl(*((uint32_t *)(db->map_base + OFFSET_VERSION_MINOR))); if (db->version != SKIPLIST_VERSION) { syslog(LOG_ERR, "skiplist: version mismatch: %s has version %d.%d", db->fname, db->version, db->version_minor); return CYRUSDB_IOERROR; } db->maxlevel = ntohl(*((uint32_t *)(db->map_base + OFFSET_MAXLEVEL))); if (db->maxlevel > SKIPLIST_MAXLEVEL) { syslog(LOG_ERR, "skiplist %s: MAXLEVEL %d in database beyond maximum %d\n", db->fname, db->maxlevel, SKIPLIST_MAXLEVEL); return CYRUSDB_IOERROR; } db->curlevel = ntohl(*((uint32_t *)(db->map_base + OFFSET_CURLEVEL))); if (db->curlevel > db->maxlevel) { syslog(LOG_ERR, "skiplist %s: CURLEVEL %d in database beyond maximum %d\n", db->fname, db->curlevel, db->maxlevel); return CYRUSDB_IOERROR; } db->listsize = ntohl(*((uint32_t *)(db->map_base + OFFSET_LISTSIZE))); db->logstart = ntohl(*((uint32_t *)(db->map_base + OFFSET_LOGSTART))); db->last_recovery = ntohl(*((uint32_t *)(db->map_base + OFFSET_LASTRECOVERY))); /* verify dummy node */ dptr = DUMMY_PTR(db); r = 0; if (!r && TYPE(dptr) != DUMMY) { syslog(LOG_ERR, "DBERROR: %s: first node not type DUMMY", db->fname); r = CYRUSDB_IOERROR; } if (!r && KEYLEN(dptr) != 0) { syslog(LOG_ERR, "DBERROR: %s: DUMMY has non-zero KEYLEN", db->fname); r = CYRUSDB_IOERROR; } if (!r && DATALEN(dptr) != 0) { syslog(LOG_ERR, "DBERROR: %s: DUMMY has non-zero DATALEN", db->fname); r = CYRUSDB_IOERROR; } if (!r && LEVEL_safe(db, dptr) != db->maxlevel) { syslog(LOG_ERR, "DBERROR: %s: DUMMY level(%d) != db->maxlevel(%d)", db->fname, LEVEL_safe(db, dptr), db->maxlevel); r = CYRUSDB_IOERROR; } return r; } /* given an open, mapped db, locked db, write the header information */ static int write_header(struct dbengine *db) { char buf[HEADER_SIZE]; int n; assert (db->lock_status == WRITELOCKED); memcpy(buf + 0, HEADER_MAGIC, HEADER_MAGIC_SIZE); *((uint32_t *)(buf + OFFSET_VERSION)) = htonl(db->version); *((uint32_t *)(buf + OFFSET_VERSION_MINOR)) = htonl(db->version_minor); *((uint32_t *)(buf + OFFSET_MAXLEVEL)) = htonl(db->maxlevel); *((uint32_t *)(buf + OFFSET_CURLEVEL)) = htonl(db->curlevel); *((uint32_t *)(buf + OFFSET_LISTSIZE)) = htonl(db->listsize); *((uint32_t *)(buf + OFFSET_LOGSTART)) = htonl(db->logstart); *((uint32_t *)(buf + OFFSET_LASTRECOVERY)) = htonl(db->last_recovery); /* write it out */ lseek(db->fd, 0, SEEK_SET); n = retry_write(db->fd, buf, HEADER_SIZE); if (n != HEADER_SIZE) { syslog(LOG_ERR, "DBERROR: writing skiplist header for %s: %m", db->fname); return CYRUSDB_IOERROR; } return 0; } /* make sure our mmap() is big enough */ static int update_lock(struct dbengine *db, struct txn *txn) { /* txn->logend is the current size of the file */ assert (db->is_open && db->lock_status == WRITELOCKED); map_refresh(db->fd, 0, &db->map_base, &db->map_len, txn->logend, db->fname, 0); db->map_size = txn->logend; return 0; } static int write_lock(struct dbengine *db, const char *altname) { struct stat sbuf; const char *lockfailaction; const char *fname = altname ? altname : db->fname; assert(db->lock_status == UNLOCKED); if (lock_reopen(db->fd, fname, &sbuf, &lockfailaction) < 0) { syslog(LOG_ERR, "IOERROR: %s %s: %m", lockfailaction, fname); return CYRUSDB_IOERROR; } if (db->map_ino != sbuf.st_ino) { map_free(&db->map_base, &db->map_len); } db->map_size = sbuf.st_size; db->map_ino = sbuf.st_ino; db->lock_status = WRITELOCKED; gettimeofday(&db->starttime, 0); map_refresh(db->fd, 0, &db->map_base, &db->map_len, sbuf.st_size, fname, 0); if (db->is_open) { /* reread header */ read_header(db); } /* printf("%d: write lock: %d\n", getpid(), db->map_ino); */ return 0; } static int read_lock(struct dbengine *db) { struct stat sbuf, sbuffile; int newfd = -1; assert(db->lock_status == UNLOCKED); for (;;) { if (lock_shared(db->fd, db->fname) < 0) { syslog(LOG_ERR, "IOERROR: lock_shared %s: %m", db->fname); return CYRUSDB_IOERROR; } if (fstat(db->fd, &sbuf) == -1) { syslog(LOG_ERR, "IOERROR: fstat %s: %m", db->fname); lock_unlock(db->fd, db->fname); return CYRUSDB_IOERROR; } if (stat(db->fname, &sbuffile) == -1) { syslog(LOG_ERR, "IOERROR: stat %s: %m", db->fname); lock_unlock(db->fd, db->fname); return CYRUSDB_IOERROR; } if (sbuf.st_ino == sbuffile.st_ino) break; newfd = open(db->fname, O_RDWR, 0644); if (newfd == -1) { syslog(LOG_ERR, "IOERROR: open %s: %m", db->fname); lock_unlock(db->fd, db->fname); return CYRUSDB_IOERROR; } dup2(newfd, db->fd); close(newfd); } if (db->map_ino != sbuf.st_ino) { map_free(&db->map_base, &db->map_len); } db->map_size = sbuf.st_size; db->map_ino = sbuf.st_ino; db->lock_status = READLOCKED; gettimeofday(&db->starttime, 0); /* printf("%d: read lock: %d\n", getpid(), db->map_ino); */ map_refresh(db->fd, 0, &db->map_base, &db->map_len, sbuf.st_size, db->fname, 0); if (db->is_open) { /* reread header */ read_header(db); } return 0; } static int unlock(struct dbengine *db) { struct timeval endtime; double timediff; if (db->lock_status == UNLOCKED) { syslog(LOG_NOTICE, "skiplist: unlock while not locked"); } if (lock_unlock(db->fd, db->fname) < 0) { syslog(LOG_ERR, "IOERROR: lock_unlock %s: %m", db->fname); return CYRUSDB_IOERROR; } db->lock_status = UNLOCKED; gettimeofday(&endtime, 0); timediff = timesub(&db->starttime, &endtime); if (timediff > 1.0) { syslog(LOG_NOTICE, "skiplist: longlock %s for %0.1f seconds", db->fname, timediff); } /* printf("%d: unlock: %d\n", getpid(), db->map_ino); */ return 0; } static int lock_or_refresh(struct dbengine *db, struct txn **tidptr) { int r; assert(db); if (!tidptr) { /* just grab a readlock */ r = read_lock(db); if (r) return r; /* start tracking the lock time */ gettimeofday(&db->starttime, 0); return 0; } else if (*tidptr) { /* check that the DB agrees that we're in this transaction */ assert(db->current_txn == *tidptr); /* just update the active transaction */ return update_lock(db, *tidptr); } /* check that the DB isn't in a transaction */ assert(db->current_txn == NULL); /* grab a r/w lock */ r = write_lock(db, NULL); if (r) return r; /* start the transaction */ r = newtxn(db, tidptr); if (r) return r; /* start tracking the lock time */ gettimeofday(&db->starttime, 0); return 0; } static int dispose_db(struct dbengine *db) { if (!db) return 0; if (db->lock_status) { syslog(LOG_ERR, "skiplist: closed while still locked"); unlock(db); } if (db->fname) { free(db->fname); } if (db->map_base) { map_free(&db->map_base, &db->map_len); } if (db->fd != -1) { close(db->fd); } free(db); return 0; } /* NOTE: this function compares with the SIGNED CHAR value of * the individual characters. This is a pretty bogus sort order, * but for backwards compatibility reasons we're stuck with it * for skiplist files at least */ static int compare_signed(const char *s1, int l1, const char *s2, int l2) { int min = l1 < l2 ? l1 : l2; int cmp = 0; while (min-- > 0 && (cmp = *s1 - *s2) == 0) { s1++; s2++; } if (min >= 0) { return cmp; } else { if (l1 > l2) return 1; else if (l2 > l1) return -1; else return 0; } } static int myopen(const char *fname, int flags, struct dbengine **ret) { struct dbengine *db; struct db_list *list_ent = open_db; int r; while (list_ent && strcmp(list_ent->db->fname, fname)) { list_ent = list_ent->next; } if (list_ent) { /* we already have this DB open! */ syslog(LOG_NOTICE, "skiplist: %s is already open %d time%s, returning object", fname, list_ent->refcount, list_ent->refcount == 1 ? "" : "s"); *ret = list_ent->db; ++list_ent->refcount; return 0; } db = (struct dbengine *) xzmalloc(sizeof(struct dbengine)); db->fd = -1; db->fname = xstrdup(fname); db->compar = (flags & CYRUSDB_MBOXSORT) ? bsearch_ncompare_mbox : compare_signed; db->fd = open(fname, O_RDWR, 0644); if (db->fd == -1 && errno == ENOENT) { if (!(flags & CYRUSDB_CREATE)) { dispose_db(db); return CYRUSDB_NOTFOUND; } if (cyrus_mkdir(fname, 0755) == -1) { dispose_db(db); return CYRUSDB_IOERROR; } db->fd = open(fname, O_RDWR | O_CREAT, 0644); } if (db->fd == -1) { syslog(LOG_ERR, "IOERROR: opening %s: %m", fname); dispose_db(db); return CYRUSDB_IOERROR; } db->curlevel = 0; db->is_open = 0; db->lock_status = UNLOCKED; /* grab a read lock, only reading the header */ r = read_lock(db); if (r < 0) { dispose_db(db); return r; } /* if the file is empty, then the header needs to be created first */ if (db->map_size == 0) { unlock(db); r = write_lock(db, NULL); if (r < 0) { dispose_db(db); return r; } } /* race condition. Another process may have already got the write * lock and created the header. Only go ahead if the map_size is * still zero (read/write_lock updates map_size). */ if (db->map_size == 0) { /* initialize in memory structure */ db->version = SKIPLIST_VERSION; db->version_minor = SKIPLIST_VERSION_MINOR; db->maxlevel = SKIPLIST_MAXLEVEL; db->curlevel = 1; db->listsize = 0; /* where do we start writing new entries? */ db->logstart = DUMMY_OFFSET(db) + DUMMY_SIZE(db); db->last_recovery = time(NULL); /* create the header */ r = write_header(db); if (!r) { int n; int dsize = DUMMY_SIZE(db); uint32_t *buf = (uint32_t *) xzmalloc(dsize); buf[0] = htonl(DUMMY); buf[(dsize / 4) - 1] = htonl(-1); lseek(db->fd, DUMMY_OFFSET(db), SEEK_SET); n = retry_write(db->fd, (char *) buf, dsize); if (n != dsize) { syslog(LOG_ERR, "DBERROR: writing dummy node for %s: %m", db->fname); r = CYRUSDB_IOERROR; } free(buf); } /* sync the db */ if (!r && DO_FSYNC && (fsync(db->fd) < 0)) { syslog(LOG_ERR, "DBERROR: fsync(%s): %m", db->fname); r = CYRUSDB_IOERROR; } /* map the new file */ db->map_size = db->logstart; map_refresh(db->fd, 0, &db->map_base, &db->map_len, db->logstart, db->fname, 0); } db->is_open = 1; r = read_header(db); if (r) { dispose_db(db); return r; } /* unlock the db */ unlock(db); if (!global_recovery || db->last_recovery < global_recovery) { /* run recovery; we rebooted since the last time recovery was run */ r = recovery(db, 0); if (r) { dispose_db(db); return r; } } *ret = db; /* track this database in the open list */ list_ent = (struct db_list *) xzmalloc(sizeof(struct db_list)); list_ent->db = db; list_ent->next = open_db; list_ent->refcount = 1; open_db = list_ent; return 0; } static int myclose(struct dbengine *db) { struct db_list *list_ent = open_db; struct db_list *prev = NULL; /* remove this DB from the open list */ while (list_ent && list_ent->db != db) { prev = list_ent; list_ent = list_ent->next; } assert(list_ent); if (--list_ent->refcount <= 0) { if (prev) prev->next = list_ent->next; else open_db = list_ent->next; free(list_ent); return dispose_db(db); } return 0; } /* returns the offset to the node asked for, or the node after it if it doesn't exist. if previous is set, finds the last node < key */ static const char *find_node(struct dbengine *db, const char *key, size_t keylen, unsigned *updateoffsets) { const char *ptr = db->map_base + DUMMY_OFFSET(db); int i; unsigned offset; if (updateoffsets) { for (i = 0; (unsigned) i < db->maxlevel; i++) { updateoffsets[i] = DUMMY_OFFSET(db); } } for (i = db->curlevel - 1; i >= 0; i--) { while ((offset = FORWARD(ptr, i)) && db->compar(KEY(db->map_base + offset), KEYLEN(db->map_base + offset), key, keylen) < 0) { /* move forward at level 'i' */ ptr = db->map_base + offset; } if (updateoffsets) updateoffsets[i] = ptr - db->map_base; } ptr = db->map_base + FORWARD(ptr, 0); return ptr; } static int myfetch(struct dbengine *db, const char *key, size_t keylen, const char **data, size_t *datalen, struct txn **tidptr) { const char *ptr; int r = 0; assert(db != NULL && key != NULL); if (data) *data = NULL; if (datalen) *datalen = 0; /* Hacky workaround: * * If no transaction was passed, but we're in a transaction, * then just do the read within that transaction. */ if (!tidptr && db->current_txn != NULL) { tidptr = &(db->current_txn); } if (tidptr) { /* make sure we're write locked and up to date */ if ((r = lock_or_refresh(db, tidptr)) < 0) { return r; } } else { /* grab a r lock */ if ((r = read_lock(db)) < 0) { return r; } } ptr = find_node(db, key, keylen, 0); if (ptr == db->map_base || db->compar(KEY(ptr), KEYLEN(ptr), key, keylen)) { /* failed to find key/keylen */ r = CYRUSDB_NOTFOUND; } else { if (datalen) *datalen = DATALEN(ptr); if (data) *data = DATA(ptr); } if (!tidptr) { /* release read lock */ int r1; if ((r1 = unlock(db)) < 0) { return r1; } } return r; } static int fetch(struct dbengine *mydb, const char *key, size_t keylen, const char **data, size_t *datalen, struct txn **tidptr) { return myfetch(mydb, key, keylen, data, datalen, tidptr); } static int fetchlock(struct dbengine *db, const char *key, size_t keylen, const char **data, size_t *datalen, struct txn **tidptr) { return myfetch(db, key, keylen, data, datalen, tidptr); } /* foreach allows for subsidary mailbox operations in 'cb'. if there is a txn, 'cb' must make use of it. */ static int myforeach(struct dbengine *db, const char *prefix, size_t prefixlen, foreach_p *goodp, foreach_cb *cb, void *rock, struct txn **tidptr) { const char *ptr; char *savebuf = NULL; size_t savebuflen = 0; size_t savebufsize; int r = 0, cb_r = 0; int need_unlock = 0; assert(db != NULL); /* Hacky workaround: * * If no transaction was passed, but we're in a transaction, * then just do the read within that transaction. */ if (!tidptr && db->current_txn != NULL) { tidptr = &(db->current_txn); } if (tidptr) { /* make sure we're write locked and up to date */ if ((r = lock_or_refresh(db, tidptr)) < 0) { return r; } } else { /* grab a r lock */ if ((r = read_lock(db)) < 0) { return r; } need_unlock = 1; } ptr = find_node(db, prefix, prefixlen, 0); while (ptr != db->map_base) { /* does it match prefix? */ if (KEYLEN(ptr) < (uint32_t) prefixlen) break; if (prefixlen && db->compar(KEY(ptr), prefixlen, prefix, prefixlen)) break; if (!goodp || goodp(rock, KEY(ptr), KEYLEN(ptr), DATA(ptr), DATALEN(ptr))) { ino_t ino = db->map_ino; unsigned long sz = db->map_size; if (!tidptr) { /* release read lock */ if ((r = unlock(db)) < 0) { return r; } need_unlock = 0; } /* save KEY, KEYLEN */ if (!savebuf || KEYLEN(ptr) > savebuflen) { savebuflen = KEYLEN(ptr) + 1024; savebuf = xrealloc(savebuf, savebuflen); } memcpy(savebuf, KEY(ptr), KEYLEN(ptr)); savebufsize = KEYLEN(ptr); /* make callback */ cb_r = cb(rock, KEY(ptr), KEYLEN(ptr), DATA(ptr), DATALEN(ptr)); if (cb_r) break; if (!tidptr) { /* grab a r lock */ if ((r = read_lock(db)) < 0) { free(savebuf); return r; } need_unlock = 1; } else { /* make sure we're up to date */ update_lock(db, *tidptr); } /* reposition */ if (!(ino == db->map_ino && sz == db->map_size)) { /* something changed in the file; reseek */ ptr = find_node(db, savebuf, savebufsize, 0); /* 'ptr' might not equal 'savebuf'. if it's different, we want to stay where we are. if it's the same, we should move on to the next one */ if (savebufsize == KEYLEN(ptr) && !memcmp(savebuf, KEY(ptr), savebufsize)) { ptr = db->map_base + FORWARD(ptr, 0); } else { /* 'savebuf' got deleted, so we're now pointing at the right thing */ } } else { /* move to the next one */ ptr = db->map_base + FORWARD(ptr, 0); } } else { /* we didn't make the callback; keep going */ ptr = db->map_base + FORWARD(ptr, 0); } } free(savebuf); if (need_unlock) { /* release read lock */ if ((r = unlock(db)) < 0) { return r; } } return r ? r : cb_r; } static unsigned int randlvl(struct dbengine *db) { unsigned int lvl = 1; while ((((float) rand() / (float) (RAND_MAX)) < PROB) && (lvl < db->maxlevel)) { lvl++; } /* syslog(LOG_DEBUG, "picked level %d", lvl); */ return lvl; } static int mystore(struct dbengine *db, const char *key, size_t keylen, const char *data, size_t datalen, struct txn **tidptr, int overwrite) { const char *ptr; uint32_t klen; uint32_t dlen; struct iovec iov[50]; unsigned lvl; unsigned i; unsigned num_iov; struct txn *tid; struct txn *localtid = NULL; uint32_t endpadding = htonl(-1); uint32_t zeropadding[4] = { 0, 0, 0, 0 }; unsigned updateoffsets[SKIPLIST_MAXLEVEL+1]; unsigned newoffsets[SKIPLIST_MAXLEVEL+1]; uint32_t addrectype = htonl(ADD); uint32_t delrectype = htonl(DELETE); uint32_t todelete; unsigned newoffset; uint32_t netnewoffset; int r; assert(db != NULL); assert(key && keylen); if (!data) datalen = 0; /* not keeping the transaction, just create one local to * this function */ if (!tidptr) { tidptr = &localtid; } /* make sure we're write locked and up to date */ if ((r = lock_or_refresh(db, tidptr)) < 0) { return r; } tid = *tidptr; /* consistent naming is nice */ if (be_paranoid) { assert(myconsistent(db, tid, 1) == 0); } num_iov = 0; newoffset = tid->logend; ptr = find_node(db, key, keylen, updateoffsets); if (ptr != db->map_base && !db->compar(KEY(ptr), KEYLEN(ptr), key, keylen)) { if (!overwrite) { myabort(db, tid); /* releases lock */ return CYRUSDB_EXISTS; } else { /* replace with an equal height node */ lvl = LEVEL_safe(db, ptr); /* log a removal */ WRITEV_ADD_TO_IOVEC(iov, num_iov, (char *) &delrectype, 4); todelete = htonl(ptr - db->map_base); WRITEV_ADD_TO_IOVEC(iov, num_iov, (char *) &todelete, 4); /* now we write at newoffset */ newoffset += 8; /* our pointers are whatever the old node pointed to */ for (i = 0; i < lvl; i++) { newoffsets[i] = htonl(FORWARD(ptr, i)); } } } else { /* pick a size for the new node */ lvl = randlvl(db); /* do we need to update the header ? */ if (lvl > db->curlevel) { for (i = db->curlevel; i < lvl; i++) { updateoffsets[i] = DUMMY_OFFSET(db); } db->curlevel = lvl; /* write out that change */ write_header(db); /* xxx errors? */ } /* we point to what we're updating used to point to */ /* newoffsets is written in the iovec later */ for (i = 0; i < lvl; i++) { /* written in the iovec */ newoffsets[i] = htonl(FORWARD(db->map_base + updateoffsets[i], i)); } } klen = htonl(keylen); dlen = htonl(datalen); netnewoffset = htonl(newoffset); WRITEV_ADD_TO_IOVEC(iov, num_iov, (char *) &addrectype, 4); WRITEV_ADD_TO_IOVEC(iov, num_iov, (char *) &klen, 4); WRITEV_ADD_TO_IOVEC(iov, num_iov, (char *) key, keylen); if (ROUNDUP(keylen) - keylen > 0) { WRITEV_ADD_TO_IOVEC(iov, num_iov, (char *) zeropadding, ROUNDUP(keylen) - keylen); } WRITEV_ADD_TO_IOVEC(iov, num_iov, (char *) &dlen, 4); if (datalen) { WRITEV_ADD_TO_IOVEC(iov, num_iov, (char *) data, datalen); } if (ROUNDUP(datalen) - datalen > 0) { WRITEV_ADD_TO_IOVEC(iov, num_iov, (char *) zeropadding, ROUNDUP(datalen) - datalen); } WRITEV_ADD_TO_IOVEC(iov, num_iov, (char *) newoffsets, 4 * lvl); WRITEV_ADD_TO_IOVEC(iov, num_iov, (char *) &endpadding, 4); getsyncfd(db, tid); lseek(tid->syncfd, tid->logend, SEEK_SET); r = retry_writev(tid->syncfd, iov, num_iov); if (r < 0) { syslog(LOG_ERR, "DBERROR: retry_writev(): %m"); myabort(db, tid); return CYRUSDB_IOERROR; } tid->logend += r; /* update where to write next */ /* update pointers after writing record so abort is guaranteed to * see which records need reverting */ for (i = 0; i < lvl; i++) { /* write pointer updates */ /* FORWARD(updates[i], i) = newoffset; */ lseek(db->fd, PTR(db->map_base + updateoffsets[i], i) - db->map_base, SEEK_SET); retry_write(db->fd, (char *) &netnewoffset, 4); } if (be_paranoid) { assert(myconsistent(db, tid, 1) == 0); } if (localtid) { /* commit the store, which releases the write lock */ r = mycommit(db, tid); if (r) return r; } return 0; } static int create(struct dbengine *db, const char *key, size_t keylen, const char *data, size_t datalen, struct txn **tid) { return mystore(db, key, keylen, data, datalen, tid, 0); } static int store(struct dbengine *db, const char *key, size_t keylen, const char *data, size_t datalen, struct txn **tid) { return mystore(db, key, keylen, data, datalen, tid, 1); } static int mydelete(struct dbengine *db, const char *key, size_t keylen, struct txn **tidptr, int force __attribute__((unused))) { const char *ptr; uint32_t delrectype = htonl(DELETE); unsigned updateoffsets[SKIPLIST_MAXLEVEL+1]; uint32_t offset; uint32_t writebuf[2]; struct txn *tid, *localtid = NULL; unsigned i; int r; /* not keeping the transaction, just create one local to * this function */ if (!tidptr) { tidptr = &localtid; } /* make sure we're write locked and up to date */ if ((r = lock_or_refresh(db, tidptr)) < 0) { return r; } tid = *tidptr; /* consistent naming is nice */ if (be_paranoid) { assert(myconsistent(db, tid, 1) == 0); } ptr = find_node(db, key, keylen, updateoffsets); if (ptr != db->map_base && !db->compar(KEY(ptr), KEYLEN(ptr), key, keylen)) { /* gotcha */ offset = ptr - db->map_base; /* log the deletion */ getsyncfd(db, tid); lseek(tid->syncfd, tid->logend, SEEK_SET); writebuf[0] = delrectype; writebuf[1] = htonl(offset); /* update end-of-log */ r = retry_write(tid->syncfd, (char *) writebuf, 8); if (r < 0) { syslog(LOG_ERR, "DBERROR: retry_write(): %m"); myabort(db, tid); return CYRUSDB_IOERROR; } tid->logend += r; /* update pointers after writing record so abort is guaranteed to * see which records need reverting */ for (i = 0; i < db->curlevel; i++) { uint32_t netnewoffset; if (FORWARD(db->map_base + updateoffsets[i], i) != offset) { break; } netnewoffset = htonl(FORWARD(ptr, i)); lseek(db->fd, PTR(db->map_base + updateoffsets[i], i) - db->map_base, SEEK_SET); retry_write(db->fd, (char *) &netnewoffset, 4); } } if (be_paranoid) { assert(myconsistent(db, tid, 1) == 0); } if (localtid) { /* commit the store, which releases the write lock */ mycommit(db, tid); } return 0; } static int mycommit(struct dbengine *db, struct txn *tid) { uint32_t commitrectype = htonl(COMMIT); int r = 0; assert(db && tid); assert(db->current_txn == tid); update_lock(db, tid); if (be_paranoid) { assert(myconsistent(db, tid, 1) == 0); } /* verify that we did something this txn */ if (tid->logstart == tid->logend) { /* empty txn, done */ r = 0; goto done; } /* fsync if we're not using O_SYNC writes */ if (!use_osync && DO_FSYNC && (fdatasync(db->fd) < 0)) { syslog(LOG_ERR, "IOERROR: writing %s: %m", db->fname); r = CYRUSDB_IOERROR; goto done; } /* xxx consider unlocking the database here: the transaction isn't yet durable but the file is in a form that is consistent for other transactions to use. releasing the lock here would give ACI properties. */ /* write a commit record */ assert(tid->syncfd != -1); lseek(tid->syncfd, tid->logend, SEEK_SET); retry_write(tid->syncfd, (char *) &commitrectype, 4); /* fsync if we're not using O_SYNC writes */ if (!use_osync && DO_FSYNC && (fdatasync(db->fd) < 0)) { syslog(LOG_ERR, "IOERROR: writing %s: %m", db->fname); r = CYRUSDB_IOERROR; goto done; } done: if (!r) db->current_txn = NULL; /* consider checkpointing */ if (!r && tid->logend > (2 * db->logstart + SKIPLIST_MINREWRITE)) { r = mycheckpoint(db); } if (be_paranoid) { assert(myconsistent(db, db->current_txn, 1) == 0); } if (r) { int r2; /* error during commit; we must abort */ r2 = myabort(db, tid); if (r2) { syslog(LOG_ERR, "DBERROR: skiplist %s: commit AND abort failed", db->fname); } } else { /* release the write lock */ if ((r = unlock(db)) < 0) { return r; } /* must close this after releasing the lock */ closesyncfd(db, tid); /* free tid */ free(tid); } return r; } static int myabort(struct dbengine *db, struct txn *tid) { const char *ptr; unsigned updateoffsets[SKIPLIST_MAXLEVEL+1]; unsigned offset; unsigned i; int r = 0; assert(db && tid); assert(db->current_txn == tid); /* look at the log entries we've written, and undo their effects */ while (tid->logstart != tid->logend) { /* update the mmap so we can see the log entries we need to remove */ update_lock(db, tid); /* find the last log entry */ for (offset = tid->logstart, ptr = db->map_base + offset; offset + RECSIZE_safe(db, ptr) != (uint32_t) tid->logend; offset += RECSIZE_safe(db, ptr), ptr = db->map_base + offset) ; offset = ptr - db->map_base; assert(TYPE(ptr) == ADD || TYPE(ptr) == DELETE); switch (TYPE(ptr)) { case DUMMY: case INORDER: case COMMIT: abort(); case ADD: /* remove this record */ (void) find_node(db, KEY(ptr), KEYLEN(ptr), updateoffsets); for (i = 0; i < db->curlevel; i++) { uint32_t netnewoffset; if (FORWARD(db->map_base + updateoffsets[i], i) != offset) { break; } netnewoffset = htonl(FORWARD(ptr, i)); lseek(db->fd, PTR(db->map_base + updateoffsets[i], i) - db->map_base, SEEK_SET); retry_write(db->fd, (char *) &netnewoffset, 4); } break; case DELETE: { unsigned lvl; uint32_t netnewoffset; const char *q; /* re-add this record. it can't exist right now. */ netnewoffset = *((uint32_t *)(ptr + 4)); q = db->map_base + ntohl(netnewoffset); lvl = LEVEL_safe(db, q); (void) find_node(db, KEY(q), KEYLEN(q), updateoffsets); for (i = 0; i < lvl; i++) { /* the current pointers FROM this node are correct, so we just have to update 'updateoffsets' */ lseek(db->fd, PTR(db->map_base + updateoffsets[i], i) - db->map_base, SEEK_SET); retry_write(db->fd, (char *) &netnewoffset, 4); } break; } } /* remove looking at this */ tid->logend -= RECSIZE_safe(db, ptr); } /* truncate the file to remove log entries */ if (ftruncate(db->fd, tid->logstart) < 0) { syslog(LOG_ERR, "DBERROR: skiplist abort %s: ftruncate: %m", db->fname); r = CYRUSDB_IOERROR; unlock(db); return r; } db->map_size = tid->logstart; /* release the write lock */ if ((r = unlock(db)) < 0) { return r; } /* must close this after releasing the lock */ closesyncfd(db, tid); /* free the tid */ free(tid); db->current_txn = NULL; return 0; } /* compress 'db'. if 'locked != 0', the database is already R/W locked and will be returned as such. */ static int mycheckpoint(struct dbengine *db) { char fname[1024]; int oldfd; struct iovec iov[50]; unsigned num_iov; unsigned updateoffsets[SKIPLIST_MAXLEVEL+1]; const char *ptr; unsigned offset; int r = 0; uint32_t iorectype = htonl(INORDER); unsigned i; clock_t start = sclock(); /* we need the latest and greatest data */ assert(db->is_open && db->lock_status == WRITELOCKED); map_refresh(db->fd, 0, &db->map_base, &db->map_len, MAP_UNKNOWN_LEN, db->fname, 0); /* can't be in a transaction */ assert(db->current_txn == NULL); if ((r = myconsistent(db, NULL, 1)) < 0) { syslog(LOG_ERR, "db %s, inconsistent pre-checkpoint, bailing out", db->fname); return r; } /* open fname.NEW */ snprintf(fname, sizeof(fname), "%s.NEW", db->fname); oldfd = db->fd; db->fd = open(fname, O_RDWR | O_CREAT, 0644); if (db->fd < 0) { syslog(LOG_ERR, "DBERROR: skiplist checkpoint: open(%s): %m", fname); db->fd = oldfd; return CYRUSDB_IOERROR; } /* truncate it just in case! */ r = ftruncate(db->fd, 0); if (r < 0) { syslog(LOG_ERR, "DBERROR: skiplist checkpoint %s: ftruncate %m", fname); db->fd = oldfd; return CYRUSDB_IOERROR; } /* write dummy record */ if (!r) { int dsize = DUMMY_SIZE(db); uint32_t *buf = (uint32_t *) xzmalloc(dsize); buf[0] = htonl(DUMMY); buf[(dsize / 4) - 1] = htonl(-1); lseek(db->fd, DUMMY_OFFSET(db), SEEK_SET); r = retry_write(db->fd, (char *) buf, dsize); if (r != dsize) { r = CYRUSDB_IOERROR; } else { r = 0; } free(buf); /* initialize the updateoffsets array so when we append records we know where to set the pointers */ for (i = 0; i < db->maxlevel; i++) { /* header_size + 4 (rectype) + 4 (ksize) + 4 (dsize) + 4 * i */ updateoffsets[i] = DUMMY_OFFSET(db) + 12 + 4 * i; } } /* write records to new file */ offset = FORWARD(db->map_base + DUMMY_OFFSET(db), 0); db->listsize = 0; while (!r && offset != 0) { unsigned int lvl; unsigned newoffset; uint32_t netnewoffset; ptr = db->map_base + offset; lvl = LEVEL_safe(db, ptr); db->listsize++; num_iov = 0; WRITEV_ADD_TO_IOVEC(iov, num_iov, (char *) &iorectype, 4); /* copy all but the rectype from the record */ WRITEV_ADD_TO_IOVEC(iov, num_iov, (char *) ptr + 4, RECSIZE_safe(db, ptr) - 4); newoffset = lseek(db->fd, 0, SEEK_END); netnewoffset = htonl(newoffset); r = retry_writev(db->fd, iov, num_iov); if (r < 0) { r = CYRUSDB_IOERROR; } else { r = 0; } for (i = 0; !r && i < lvl; i++) { /* update pointers */ r = lseek(db->fd, updateoffsets[i], SEEK_SET); if (r < 0) { r = CYRUSDB_IOERROR; break; } else { r = 0; } r = retry_write(db->fd, (char *) &netnewoffset, 4); if (r < 0) { r = CYRUSDB_IOERROR; break; } else { r = 0; } /* PTR(ptr, i) - ptr is the offset relative to me to my ith pointer */ updateoffsets[i] = newoffset + (PTR(ptr, i) - ptr); } offset = FORWARD(ptr, 0); } /* set any dangling pointers to zero */ for (i = 0; !r && i < db->maxlevel; i++) { uint32_t netnewoffset = htonl(0); r = lseek(db->fd, updateoffsets[i], SEEK_SET); if (r < 0) { r = CYRUSDB_IOERROR; break; } else { r = 0; } r = retry_write(db->fd, (char *) &netnewoffset, 4); if (r < 0) { r = CYRUSDB_IOERROR; break; } else { r = 0; } } /* create the header */ db->logstart = lseek(db->fd, 0, SEEK_END); db->last_recovery = time(NULL); r = write_header(db); /* sync new file */ if (!r && DO_FSYNC && (fdatasync(db->fd) < 0)) { syslog(LOG_ERR, "DBERROR: skiplist checkpoint: fdatasync(%s): %m", fname); r = CYRUSDB_IOERROR; } if (!r) { /* get new lock */ db->lock_status = UNLOCKED; /* well, the new file is... */ r = write_lock(db, fname); } /* move new file to original file name */ if (!r && (rename(fname, db->fname) < 0)) { syslog(LOG_ERR, "DBERROR: skiplist checkpoint: rename(%s, %s): %m", fname, db->fname); r = CYRUSDB_IOERROR; } /* force the new file name to disk */ if (!r && DO_FSYNC && (fsync(db->fd) < 0)) { syslog(LOG_ERR, "DBERROR: skiplist checkpoint: fsync(%s): %m", fname); r = CYRUSDB_IOERROR; } if (r) { /* clean up */ close(db->fd); db->fd = oldfd; unlink(fname); } else { struct stat sbuf; /* remove content of old file so it doesn't sit around using disk */ r = ftruncate(oldfd, 0); /* release old write lock */ close(oldfd); /* let's make sure we're up to date */ map_free(&db->map_base, &db->map_len); if (fstat(db->fd, &sbuf) == -1) { syslog(LOG_ERR, "IOERROR: fstat %s: %m", db->fname); return CYRUSDB_IOERROR; } db->map_size = sbuf.st_size; db->map_ino = sbuf.st_ino; map_refresh(db->fd, 0, &db->map_base, &db->map_len, sbuf.st_size, db->fname, 0); } if ((r = myconsistent(db, NULL, 1)) < 0) { syslog(LOG_ERR, "db %s, inconsistent post-checkpoint, bailing out", db->fname); return r; } syslog(LOG_INFO, "skiplist: checkpointed %s (%d record%s, %d bytes) in %2.3f sec", db->fname, db->listsize, db->listsize == 1 ? "" : "s", db->logstart, (sclock() - start) / (double) CLOCKS_PER_SEC); return r; } /* dump the database. if detail == 1, dump all records. if detail == 2, also dump pointers for active records. if detail == 3, dump all records/all pointers. */ static int dump(struct dbengine *db, int detail __attribute__((unused))) { const char *ptr, *end; unsigned i; read_lock(db); ptr = db->map_base + DUMMY_OFFSET(db); end = db->map_base + db->map_size; while (ptr < end) { printf("%04lX: ", (unsigned long) (ptr - db->map_base)); switch (TYPE(ptr)) { case DUMMY: printf("DUMMY "); break; case INORDER: printf("INORDER "); break; case ADD: printf("ADD "); break; case DELETE: printf("DELETE "); break; case COMMIT: printf("COMMIT "); break; } switch (TYPE(ptr)) { case DUMMY: case INORDER: case ADD: printf("kl=%d dl=%d lvl=%d\n", KEYLEN(ptr), DATALEN(ptr), LEVEL_safe(db, ptr)); printf("\t"); for (i = 0; i < LEVEL_safe(db, ptr); i++) { printf("%04X ", FORWARD(ptr, i)); } printf("\n"); break; case DELETE: printf("offset=%04X\n", ntohl(*((uint32_t *)(ptr + 4)))); break; case COMMIT: printf("\n"); break; } ptr += RECSIZE_safe(db, ptr); } unlock(db); return 0; } static int consistent(struct dbengine *db) { return myconsistent(db, NULL, 0); } /* perform some basic consistency checks */ static int myconsistent(struct dbengine *db, struct txn *tid, int locked) { const char *ptr; uint32_t offset; assert(db->current_txn == tid); /* could both be null */ if (!locked) read_lock(db); else if (tid) update_lock(db, tid); offset = FORWARD(db->map_base + DUMMY_OFFSET(db), 0); while (offset != 0) { unsigned i; ptr = db->map_base + offset; for (i = 0; i < LEVEL_safe(db, ptr); i++) { offset = FORWARD(ptr, i); if (offset > db->map_size) { syslog(LOG_ERR, "skiplist inconsistent: %04X: ptr %d is %04X; " "eof is %04X\n", (unsigned int) (ptr - db->map_base), i, offset, (unsigned int) db->map_size); if (!locked) unlock(db); return CYRUSDB_INTERNAL; } if (offset != 0) { /* check to see that ptr < ptr -> next */ const char *q = db->map_base + offset; int cmp; cmp = db->compar(KEY(ptr), KEYLEN(ptr), KEY(q), KEYLEN(q)); if (cmp >= 0) { syslog(LOG_ERR, "skiplist inconsistent: %04X: ptr %d is %04X; " "db->compar() = %d\n", (unsigned int) (ptr - db->map_base), i, offset, cmp); if (!locked) unlock(db); return CYRUSDB_INTERNAL; } } } offset = FORWARD(ptr, 0); } if (!locked) unlock(db); return 0; } /* run recovery on this file */ static int recovery(struct dbengine *db, int flags) { const char *ptr, *keyptr; unsigned filesize = db->map_size; unsigned updateoffsets[SKIPLIST_MAXLEVEL+1]; uint32_t offset, offsetnet, myoff = 0; int r = 0; int need_checkpoint = libcyrus_config_getswitch(CYRUSOPT_SKIPLIST_ALWAYS_CHECKPOINT); time_t start = time(NULL); unsigned i; if (!(flags & RECOVERY_CALLER_LOCKED) && (r = write_lock(db, NULL)) < 0) { return r; } assert(db->is_open && db->lock_status == WRITELOCKED); if ((r = read_header(db)) < 0) { unlock(db); return r; } if (!(flags & RECOVERY_FORCE) && global_recovery && db->last_recovery >= global_recovery) { /* someone beat us to it */ unlock(db); return 0; } /* can't run recovery inside a txn */ assert(db->current_txn == NULL); db->listsize = 0; ptr = DUMMY_PTR(db); r = 0; /* verify this is DUMMY */ if (!r && TYPE(ptr) != DUMMY) { r = CYRUSDB_IOERROR; syslog(LOG_ERR, "DBERROR: skiplist recovery %s: no dummy node?", db->fname); } /* zero key */ if (!r && KEYLEN(ptr) != 0) { r = CYRUSDB_IOERROR; syslog(LOG_ERR, "DBERROR: skiplist recovery %s: dummy node KEYLEN != 0", db->fname); } /* zero data */ if (!r && DATALEN(ptr) != 0) { r = CYRUSDB_IOERROR; syslog(LOG_ERR, "DBERROR: skiplist recovery %s: dummy node DATALEN != 0", db->fname); } /* pointers for db->maxlevel */ if (!r && LEVEL_safe(db, ptr) != db->maxlevel) { r = CYRUSDB_IOERROR; syslog(LOG_ERR, "DBERROR: skiplist recovery %s: dummy node level: %d != %d", db->fname, LEVEL_safe(db, ptr), db->maxlevel); } for (i = 0; i < db->maxlevel; i++) { /* header_size + 4 (rectype) + 4 (ksize) + 4 (dsize) + 4 * i */ updateoffsets[i] = DUMMY_OFFSET(db) + 12 + 4 * i; } /* reset the data that was written INORDER by the last checkpoint */ offset = DUMMY_OFFSET(db) + DUMMY_SIZE(db); while (!r && (offset < filesize) && TYPE(db->map_base + offset) == INORDER) { ptr = db->map_base + offset; offsetnet = htonl(offset); db->listsize++; /* xxx check \0 fill on key */ /* xxx check \0 fill on data */ /* update previous pointers, record these for updating */ for (i = 0; !r && i < LEVEL_safe(db, ptr); i++) { r = lseek(db->fd, updateoffsets[i], SEEK_SET); if (r < 0) { syslog(LOG_ERR, "DBERROR: lseek %s: %m", db->fname); r = CYRUSDB_IOERROR; break; } else { r = 0; } r = retry_write(db->fd, (char *) &offsetnet, 4); if (r < 0) { r = CYRUSDB_IOERROR; break; } else { r = 0; } /* PTR(ptr, i) - ptr is the offset relative to me to my ith pointer */ updateoffsets[i] = offset + (PTR(ptr, i) - ptr); } if (!r) { unsigned size = RECSIZE_safe(db, ptr); if (!size) { syslog(LOG_ERR, "skiplist recovery %s: damaged record at %u, truncating here", db->fname, offset); filesize = offset; break; } if (PADDING_safe(db, ptr) != (uint32_t) -1) { syslog(LOG_ERR, "DBERROR: %s: offset %04X padding not -1", db->fname, offset); filesize = offset; break; } offset += size; } } if (offset != db->logstart) { syslog(LOG_NOTICE, "skiplist recovery %s: incorrect logstart %04X changed to %04X", db->fname, db->logstart, offset); db->logstart = offset; /* header will be committed later */ } /* zero out the remaining pointers */ if (!r) { for (i = 0; !r && i < db->maxlevel; i++) { int zerooffset = 0; r = lseek(db->fd, updateoffsets[i], SEEK_SET); if (r < 0) { syslog(LOG_ERR, "DBERROR: lseek %s: %m", db->fname); r = CYRUSDB_IOERROR; break; } else { r = 0; } r = retry_write(db->fd, (char *) &zerooffset, 4); if (r < 0) { r = CYRUSDB_IOERROR; break; } else { r = 0; } } } /* replay the log */ while (!r && offset < filesize) { const char *p, *q; /* refresh map, so we see the writes we've just done */ map_refresh(db->fd, 0, &db->map_base, &db->map_len, db->map_size, db->fname, 0); ptr = db->map_base + offset; /* bugs in recovery truncates could have left some bogus zeros here */ if (TYPE(ptr) == 0) { int orig = offset; while (TYPE(ptr) == 0 && offset < filesize) { offset += 4; ptr = db->map_base + offset; } syslog(LOG_ERR, "skiplist recovery %s: skipped %d bytes of zeros at %04X", db->fname, offset - orig, orig); need_checkpoint = 1; } offsetnet = htonl(offset); /* if this is a commit, we've processed everything in this txn */ if (TYPE(ptr) == COMMIT) { unsigned size = RECSIZE_safe(db, ptr); if (!size) break; offset += size; continue; } /* make sure this is ADD or DELETE */ if (TYPE(ptr) != ADD && TYPE(ptr) != DELETE) { syslog(LOG_ERR, "DBERROR: skiplist recovery %s: %04X should be ADD or DELETE", db->fname, offset); r = CYRUSDB_IOERROR; break; } /* look ahead for a commit */ q = db->map_base + filesize; p = ptr; for (;;) { unsigned size = RECSIZE_safe(db, p); if (!size) { /* hmm, we can't trust this transaction */ syslog(LOG_ERR, "DBERROR: skiplist recovery %s: found a RECSIZE of 0, " "truncating corrupted file instead of looping forever...", db->fname); p = q; break; } p += size; if (p >= q) break; if (TYPE(p) == COMMIT) break; } if (p >= q) { syslog(LOG_NOTICE, "skiplist recovery %s: found partial txn, not replaying", db->fname); filesize = offset; break; } keyptr = NULL; /* look for the key */ if (TYPE(ptr) == ADD) { keyptr = find_node(db, KEY(ptr), KEYLEN(ptr), updateoffsets); if (keyptr == db->map_base || db->compar(KEY(ptr), KEYLEN(ptr), KEY(keyptr), KEYLEN(keyptr))) { /* didn't find exactly this node */ keyptr = NULL; } } else { /* type == DELETE */ const char *p; myoff = ntohl(*((uint32_t *)(ptr + 4))); p = db->map_base + myoff; keyptr = find_node(db, KEY(p), KEYLEN(p), updateoffsets); if (keyptr == db->map_base || db->compar(KEY(p), KEYLEN(p), KEY(keyptr), KEYLEN(keyptr))) { /* didn't find exactly this node */ keyptr = NULL; } } /* if DELETE & found key, skip over it */ if (TYPE(ptr) == DELETE && keyptr) { db->listsize--; for (i = 0; i < db->curlevel; i++) { int newoffset; if (FORWARD(db->map_base + updateoffsets[i], i) != myoff) { break; } newoffset = htonl(FORWARD(db->map_base + myoff, i)); lseek(db->fd, PTR(db->map_base + updateoffsets[i], i) - db->map_base, SEEK_SET); retry_write(db->fd, (char *) &newoffset, 4); } /* otherwise if DELETE, throw an error */ } else if (TYPE(ptr) == DELETE) { syslog(LOG_ERR, "DBERROR: skiplist recovery %s: DELETE at %04X doesn't exist, skipping", db->fname, offset); need_checkpoint = 1; /* otherwise insert it */ } else if (TYPE(ptr) == ADD) { unsigned int lvl; uint32_t newoffsets[SKIPLIST_MAXLEVEL+1]; if (keyptr) { syslog(LOG_ERR, "DBERROR: skiplist recovery %s: ADD at %04X exists, replacing", db->fname, offset); need_checkpoint = 1; } else { db->listsize++; } offsetnet = htonl(offset); lvl = LEVEL_safe(db, ptr); if (lvl > SKIPLIST_MAXLEVEL) { syslog(LOG_ERR, "DBERROR: skiplist recovery %s: node claims level %d (greater than max %d)", db->fname, lvl, SKIPLIST_MAXLEVEL); r = CYRUSDB_IOERROR; } else { /* NOTE - in the bogus case where a record with the same key already * exists, there are three possible cases: * lvl == LEVEL_safe(db, keyptr) * * trivial: all to me, all mine to keyptr's FORWARD * lvl > LEVEL_safe(db, keyptr) - * * all updateoffsets values should point to me * * up until LEVEL_safe(db, keyptr) set to keyptr's next values * (updateoffsets[i] should be keyptr in these cases) * then point all my higher pointers are updateoffsets[i]'s * FORWARD instead. * lvl < LEVEL_safe(db, keyptr) * * updateoffsets values up to lvl should point to me * * all mine should point to keyptr's next values * * from lvl up, all updateoffsets[i] should point to * FORWARD(keyptr, i) instead. * * All of this fully unstitches keyptr from the chain and stitches * the current node in, regardless of height difference. Man what * a pain! */ for (i = 0; i < lvl; i++) { /* set our next pointers */ if (keyptr && i < LEVEL_safe(db, keyptr)) { /* need to replace the matching record key */ newoffsets[i] = htonl(FORWARD(keyptr, i)); } else { newoffsets[i] = htonl(FORWARD(db->map_base + updateoffsets[i], i)); } /* replace 'updateoffsets' to point to me */ lseek(db->fd, PTR(db->map_base + updateoffsets[i], i) - db->map_base, SEEK_SET); retry_write(db->fd, (char *) &offsetnet, 4); } /* write out newoffsets */ lseek(db->fd, FIRSTPTR(ptr) - db->map_base, SEEK_SET); retry_write(db->fd, (char *) newoffsets, 4 * lvl); if (keyptr && lvl < LEVEL_safe(db, keyptr)) { uint32_t newoffsetnet; for (i = lvl; i < LEVEL_safe(db, keyptr); i++) { newoffsetnet = htonl(FORWARD(keyptr, i)); /* replace 'updateoffsets' to point onwards */ lseek(db->fd, PTR(db->map_base + updateoffsets[i], i) - db->map_base, SEEK_SET); retry_write(db->fd, (char *) &newoffsetnet, 4); } } } /* can't happen */ } else { abort(); } /* move to next record */ unsigned size = RECSIZE_safe(db, ptr); if (!size) break; offset += size; } /* didn't read the exact end? We should truncate */ if (offset < db->map_size) { if (ftruncate(db->fd, offset) < 0) { syslog(LOG_ERR, "DBERROR: skiplist recovery %s: ftruncate: %m", db->fname); r = CYRUSDB_IOERROR; } /* set the map size back as well */ db->map_size = offset; } /* fsync the recovered database */ if (!r && DO_FSYNC && (fdatasync(db->fd) < 0)) { syslog(LOG_ERR, "DBERROR: skiplist recovery %s: fdatasync: %m", db->fname); r = CYRUSDB_IOERROR; } /* set the last recovery timestamp */ if (!r) { db->last_recovery = time(NULL); write_header(db); } /* fsync the new header */ if (!r && DO_FSYNC && (fdatasync(db->fd) < 0)) { syslog(LOG_ERR, "DBERROR: skiplist recovery %s: fdatasync: %m", db->fname); r = CYRUSDB_IOERROR; } if (!r) { int diff = time(NULL) - start; syslog(LOG_NOTICE, "skiplist: recovered %s (%d record%s, %ld bytes) in %d second%s", db->fname, db->listsize, db->listsize == 1 ? "" : "s", (long unsigned)db->map_size, diff, diff == 1 ? "" : "s"); } if (!r && need_checkpoint) { /* refresh map, so we see the writes we've just done */ map_refresh(db->fd, 0, &db->map_base, &db->map_len, db->map_size, db->fname, 0); r = mycheckpoint(db); } if (r || !(flags & RECOVERY_CALLER_LOCKED)) { unlock(db); } return r; } /* skiplist compar function is set at open */ static int mycompar(struct dbengine *db, const char *a, int alen, const char *b, int blen) { return db->compar(a, alen, b, blen); } EXPORTED struct cyrusdb_backend cyrusdb_skiplist = { "skiplist", /* name */ &myinit, &cyrusdb_generic_done, &cyrusdb_generic_sync, &cyrusdb_generic_archive, &myopen, &myclose, &fetch, &fetchlock, NULL, &myforeach, &create, &store, &mydelete, &mycommit, &myabort, &dump, &consistent, &mycheckpoint, &mycompar }; cyrus-imapd-2.5.10/lib/ftruncate.c0000644000175000017500000000375412772415051013677 00000000000000/* ftruncate -- Replacement ftruncate() function * Does nothing * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include #include int ftruncate(int fd, int length) { (void)fd; (void)length; errno = EINVAL; return -1; } cyrus-imapd-2.5.10/lib/imapurl.h0000644000175000017500000000615513001236020013337 00000000000000/* * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #ifndef IMAPURL_H #define IMAPURL_H struct imapurl { char *freeme; /* copy of original URL + decoded mailbox; caller must free() */ /* RFC 2192 */ const char *user; const char *auth; const char *server; const char *mailbox; unsigned long uidvalidity; unsigned long uid; const char *section; /* RFC 2192bis */ unsigned long start_octet; unsigned long octet_count; /* URLAUTH */ struct { const char *access; const char *mech; const char *token; time_t expire; size_t rump_len; } urlauth; }; /* Convert hex coded UTF-8 URL path to modified UTF-7 IMAP mailbox * mailbox should be about twice the length of src to deal with non-hex * coded URLs; server should be as large as src. */ extern int imapurl_fromURL(struct imapurl *url, const char *src); extern int URLtoMailbox(char *dst, const char *src); #define UTF8_to_mUTF7(dst, src) URLtoMailbox(dst, src) /* Convert an IMAP mailbox to a URL path * dst needs to have roughly 4 times the storage space of mailbox * Hex encoding can triple the size of the input * UTF-7 can be slightly denser than UTF-8 * (worst case: 8 octets UTF-7 becomes 9 octets UTF-8) * * it is valid for mechname to be NULL (implies anonymous mech) */ extern void imapurl_toURL(char *dst, const struct imapurl *url); #endif /* IMAPURL_H */ cyrus-imapd-2.5.10/lib/gmtoff.h0000644000175000017500000000372612772415051013172 00000000000000/* gmtoff.h -- Get GMT offset * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #ifndef INCLUDED_GMTOFF_H #define INCLUDED_GMTOFF_H #include extern int gmtoff_of(struct tm *tm, time_t time); #endif /* INCLUDED_GMTOFF_H */ cyrus-imapd-2.5.10/lib/strarray.c0000644000175000017500000002443713001236020013533 00000000000000/* strarray.c -- an expanding array of strings * * Copyright (c) 1994-2011 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. * * Author: Greg Banks * Start Date: 2011/01/11 */ #include "strarray.h" #include #include "util.h" #include "xmalloc.h" EXPORTED strarray_t *strarray_new(void) { return xzmalloc(sizeof(strarray_t)); } EXPORTED void strarray_fini(strarray_t *sa) { int i; if (!sa) return; for (i = 0 ; i < sa->count ; i++) { free(sa->data[i]); sa->data[i] = NULL; } free(sa->data); sa->data = NULL; sa->count = 0; sa->alloc = 0; } EXPORTED void strarray_free(strarray_t *sa) { if (!sa) return; strarray_fini(sa); free(sa); } /* * Ensure the index @idx exists in the array, if necessary expanding the * array, and if necessary NULL-filling all the intervening elements. * Note that we always ensure an empty slot past the last reported * index, so that we can pass data[] to execve() or other routines that * assume a NULL terminator. */ #define QUANTUM 16 static void ensure_alloc(strarray_t *sa, int newalloc) { if (newalloc < sa->alloc) return; newalloc = ((newalloc + QUANTUM) / QUANTUM) * QUANTUM; sa->data = xrealloc(sa->data, sizeof(char *) * newalloc); memset(sa->data+sa->alloc, 0, sizeof(char *) * (newalloc-sa->alloc)); sa->alloc = newalloc; } /* * Normalise the index passed by a caller, to a value in the range * 0..count-1, or < 0 for invalid, assuming the function we're * performing does not have the side effect of expanding the array. * Note that doesn't necessarily mean the array is read-only, e.g. * strarray_remove() modifies the array but does not expand the array if * given an index outside the array's current bounds. In Perl style, * negative indexes whose absolute value is less than the length of the * array are treated as counting back from the end, e.g. idx=-1 means * the final element. */ static inline int adjust_index_ro(const strarray_t *sa, int idx) { if (idx >= sa->count) return -1; else if (idx < 0) idx += sa->count; return idx; } /* * Like adjust_index_ro(), with extra complication that the function * we're performing will expand the array if either the adjusted index * points outside the current bounds of the array, or @grow tells us * that we're about to need more space in the array. */ static inline int adjust_index_rw(strarray_t *sa, int idx, int grow) { if (idx >= sa->count) { /* expanding the array as a side effect @idx pointing * outside the current bounds, plus perhaps @grow */ ensure_alloc(sa, idx+grow); } else if (idx < 0) { /* adjust Perl-style negative indeces */ idx += sa->count; if (idx >= 0 && grow) ensure_alloc(sa, sa->count+grow); } else if (grow) { /* expanding the array due to an insert or append */ ensure_alloc(sa, sa->count+grow); } return idx; } EXPORTED strarray_t *strarray_dup(const strarray_t *sa) { strarray_t *new = strarray_new(); int i; strarray_truncate(new, sa->count); for (i = 0 ; i < sa->count ; i++) new->data[i] = xstrdup(sa->data[i]); return new; } EXPORTED int strarray_append(strarray_t *sa, const char *s) { return strarray_appendm(sa, xstrdup(s)); } EXPORTED int strarray_add(strarray_t *sa, const char *s) { int pos = strarray_find(sa, s, 0); if (pos < 0) pos = strarray_append(sa, s); return pos; } EXPORTED int strarray_add_case(strarray_t *sa, const char *s) { int pos = strarray_find_case(sa, s, 0); if (pos < 0) pos = strarray_append(sa, s); return pos; } EXPORTED int strarray_appendm(strarray_t *sa, char *s) { int pos = sa->count++; ensure_alloc(sa, sa->count); /* coverity[var_deref_op] */ sa->data[pos] = s; return pos; } static void _strarray_set(strarray_t *sa, int idx, char *s) { free(sa->data[idx]); sa->data[idx] = s; /* adjust the count if we just sparsely expanded the array */ if (s && idx >= sa->count) sa->count = idx+1; } EXPORTED void strarray_set(strarray_t *sa, int idx, const char *s) { if ((idx = adjust_index_rw(sa, idx, 0)) < 0) return; _strarray_set(sa, idx, xstrdupnull(s)); } EXPORTED void strarray_setm(strarray_t *sa, int idx, char *s) { if ((idx = adjust_index_rw(sa, idx, 0)) < 0) return; _strarray_set(sa, idx, s); } static inline void _strarray_insert(strarray_t *sa, int idx, char *s) { if (idx < sa->count) memmove(sa->data+idx+1, sa->data+idx, sizeof(char *) * (sa->count-idx)); sa->data[idx] = s; sa->count++; } EXPORTED void strarray_insert(strarray_t *sa, int idx, const char *s) { if ((idx = adjust_index_rw(sa, idx, 1)) < 0) return; _strarray_insert(sa, idx, xstrdup(s)); } EXPORTED void strarray_insertm(strarray_t *sa, int idx, char *s) { if ((idx = adjust_index_rw(sa, idx, 1)) < 0) return; _strarray_insert(sa, idx, s); } EXPORTED char *strarray_remove(strarray_t *sa, int idx) { char *s; if ((idx = adjust_index_ro(sa, idx)) < 0) return NULL; s = sa->data[idx]; sa->count--; if (idx < sa->count) memmove(sa->data+idx, sa->data+idx+1, sizeof(char *) * (sa->count-idx)); return s; } EXPORTED void strarray_remove_all(strarray_t *sa, const char *s) { int i = 0; for (;;) { i = strarray_find(sa, s, i); if (i < 0) break; free(strarray_remove(sa, i)); } } EXPORTED void strarray_remove_all_case(strarray_t *sa, const char *s) { int i = 0; for (;;) { i = strarray_find_case(sa, s, i); if (i < 0) break; free(strarray_remove(sa, i)); } } EXPORTED void strarray_truncate(strarray_t *sa, int newlen) { int i; if (newlen == sa->count) return; if (newlen > sa->count) { ensure_alloc(sa, newlen); } else { for (i = newlen ; i < sa->count ; i++) { free(sa->data[i]); sa->data[i] = NULL; } } sa->count = newlen; } EXPORTED const char *strarray_nth(const strarray_t *sa, int idx) { if ((idx = adjust_index_ro(sa, idx)) < 0) return NULL; return sa->data[idx]; } EXPORTED char *strarray_join(const strarray_t *sa, const char *sep) { int seplen = (sep ? strlen(sep) : 0); int len = 0; int i; /* array index */ int j; /* index into non-sparse logical subset of the array * i.e. doesn't count NULLs */ char *buf, *p; for (i = 0, j = 0 ; i < sa->count ; i++) { if (sa->data[i]) len += strlen(sa->data[i]) + (j++ ? seplen : 0); } if (!len) return NULL; len++; /* room for NUL terminator */ p = buf = xmalloc(len); for (i = 0, j = 0 ; i < sa->count ; i++) { if (sa->data[i]) { if (j++ && sep) { strcpy(p, sep); p += strlen(p); } strcpy(p, sa->data[i]); p += strlen(p); } } return buf; } EXPORTED strarray_t *strarray_splitm(char *buf, const char *sep, int flags) { strarray_t *sa = strarray_new(); char *p, *q; if (!buf) return sa; if (!sep) sep = " \t\r\n"; for (p = strtok(buf, sep) ; p ; p = strtok(NULL, sep)) { if (flags & STRARRAY_TRIM) { while (Uisspace(*p)) p++; q = p + strlen(p); while (q > p && Uisspace(q[-1])) q--; *q = '\0'; } if (*p) strarray_append(sa, p); } free(buf); return sa; } EXPORTED strarray_t *strarray_split(const char *line, const char *sep, int flags) { if (!line) return strarray_new(); return strarray_splitm(xstrdup(line), sep, flags); } EXPORTED strarray_t *strarray_nsplit(const char *buf, size_t len, const char *sep, int flags) { if (!len) return strarray_new(); return strarray_splitm(xstrndup(buf, len), sep, flags); } EXPORTED char **strarray_takevf(strarray_t *sa) { char **d = sa->data; sa->data = NULL; sa->count = sa->alloc = 0; strarray_free(sa); return d; } EXPORTED void strarray_sort(strarray_t *sa, compar_t *cmp) { qsort(sa->data, sa->count, sizeof(char *), (__compar_fn_t)cmp); } EXPORTED void strarray_uniq(strarray_t *sa) { int i; for (i = 1; i < sa->count; i++) { if (!strcmpsafe(sa->data[i-1], sa->data[i])) free(strarray_remove(sa, i--)); } } /* common generic routine for the _find family */ static int strarray_findg(const strarray_t *sa, const char *match, int starting, int (*compare)(const char *, const char *)) { int i; for (i = starting ; i < sa->count ; i++) if (!compare(match, sa->data[i])) return i; return -1; } EXPORTED int strarray_find(const strarray_t *sa, const char *match, int starting) { return strarray_findg(sa, match, starting, strcmpsafe); } EXPORTED int strarray_find_case(const strarray_t *sa, const char *match, int starting) { return strarray_findg(sa, match, starting, strcasecmpsafe); } EXPORTED int strarray_size(const strarray_t *sa) { return sa->count; } cyrus-imapd-2.5.10/lib/gai.h0000644000175000017500000000657513001236020012434 00000000000000/* * Mar 8, 2000 by Hajimu UMEMOTO * * This module is besed on ssh-1.2.27-IPv6-1.5 written by * KIKUCHI Takahiro */ /* * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ /* * fake library for ssh * * This file is included in getaddrinfo.c and getnameinfo.c. * See getaddrinfo.c and getnameinfo.c. */ #ifndef _GAI_H_ #define _GAI_H_ #ifndef NI_MAXHOST #define NI_MAXHOST 1025 #endif #ifndef NI_MAXSERV #define NI_MAXSERV 32 #endif /* for old netdb.h */ #ifndef EAI_SERVICE #define EAI_MEMORY 2 #define EAI_FAMILY 5 /* ai_family not supported */ #define EAI_NONAME 8 /* hostname nor servname provided, or not known */ #define EAI_SERVICE 9 /* servname not supported for ai_socktype */ #endif /* dummy value for old netdb.h */ #ifndef AI_PASSIVE #define AI_PASSIVE 1 #define AI_CANONNAME 2 #define AI_NUMERICHOST 4 #define NI_NUMERICHOST 2 #define NI_NAMEREQD 4 #define NI_NUMERICSERV 8 struct addrinfo { int ai_flags; /* AI_PASSIVE, AI_CANONNAME */ int ai_family; /* PF_xxx */ int ai_socktype; /* SOCK_xxx */ int ai_protocol; /* 0 or IPPROTO_xxx for IPv4 and IPv6 */ size_t ai_addrlen; /* length of ai_addr */ char *ai_canonname; /* canonical name for hostname */ struct sockaddr *ai_addr; /* binary address */ struct addrinfo *ai_next; /* next structure in linked list */ }; #endif #ifndef HAVE_GETNAMEINFO int getnameinfo(const struct sockaddr *, socklen_t, char *, size_t, char *, size_t, int); #endif #ifndef HAVE_GETADDRINFO int getaddrinfo(const char *, const char *, const struct addrinfo *, struct addrinfo **); void freeaddrinfo(struct addrinfo *); char *gai_strerror(int); #endif #endif cyrus-imapd-2.5.10/lib/byteorder64.c0000644000175000017500000000666313001236020014036 00000000000000/* byteorder64.c -- convert 64-bit values between host and network byte order * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include #include "byteorder64.h" #ifdef CYRUS_BYTESWAP #include /* Structure used to swap the bytes in a 64-bit unsigned long long. */ union byteswap_64_u { unsigned long long a; uint32_t b[2]; }; /* Function to byteswap 64bit unsigned integers on * little endian machines to big endian network order. * On big endian machines this will be a null macro. * The macro htonll() is defined in byteorder64.h, * and if needed refers to _htonll() here. */ EXPORTED unsigned long long _htonll(unsigned long long x) { union byteswap_64_u u1; union byteswap_64_u u2; u1.a = x; u2.b[0] = htonl(u1.b[1]); u2.b[1] = htonl(u1.b[0]); return u2.a; } /* Function to byteswap big endian 64bit unsigned integers * back to little endian host order on little endian machines. * As above, on big endian machines this will be a null macro. * The macro ntohll() is defined in byteorder64.h, and if needed, * refers to _ntohll() here. */ EXPORTED unsigned long long _ntohll(unsigned long long x) { union byteswap_64_u u1; union byteswap_64_u u2; u1.a = x; u2.b[1] = ntohl(u1.b[0]); u2.b[0] = ntohl(u1.b[1]); return u2.a; } #endif /* CYRUS_BYTESWAP */ #include EXPORTED void *align_htonll(void *dst, unsigned long long src) { unsigned long long tmp = htonll(src); return memcpy(dst, (void *) &tmp, sizeof(unsigned long long)); } EXPORTED unsigned long long align_ntohll(const void *src) { unsigned long long dst; memcpy((void *) &dst, src, sizeof(unsigned long long)); return ntohll(dst); } cyrus-imapd-2.5.10/lib/mpool.h0000644000175000017500000000473712772415051013041 00000000000000/* mpool.h memory pool management * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #ifndef _MPOOL_H_ #ifdef HAVE_UNISTD_H #include #endif #include #include #include #include /* Opaque mpool handle */ struct mpool; #define DEFAULT_MPOOL_SIZE 32768 /* Create a new pool -- pass zero for default */ /* 'size' is the size of the first blob of memory that will be allocated */ struct mpool *new_mpool(size_t size); /* Free a pool */ void free_mpool(struct mpool *pool); /* Allocate from a pool */ void *mpool_malloc(struct mpool *pool, size_t size); char *mpool_strdup(struct mpool *pool, const char *str); char *mpool_strndup(struct mpool *pool, const char *str, size_t n); #endif /* _MPOOL_H_ */ cyrus-imapd-2.5.10/lib/map_stupidshared.c0000644000175000017500000000670613001236020015217 00000000000000/* map_stupidshared.c -- memory-mapping routines working around DEC stupidity. * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include #include #include #include #include #include #include "map.h" #include "exitcodes.h" #include "xmalloc.h" EXPORTED const char *map_method_desc = "stupidshared"; #ifndef MAP_FAILED #define MAP_FAILED ((void *)-1) #endif /* * Create/refresh mapping of file */ void EXPORTED map_refresh(int fd, int onceonly, const char **base, size_t *len, size_t newlen, const char *name, const char *mboxname) { (void)onceonly; struct stat sbuf; int flags; char buf[256]; if (newlen == MAP_UNKNOWN_LEN) { if (fstat(fd, &sbuf) == -1) { syslog(LOG_ERR, "IOERROR: fstating %s file%s%s: %m", name, mboxname ? " for " : "", mboxname ? mboxname : ""); snprintf(buf, sizeof(buf), "failed to fstat %s file", name); fatal(buf, EC_IOERR); } newlen = sbuf.st_size; } /* Already mapped in */ if (*len >= newlen) return; if (*len) munmap((char *)*base, *len); flags = MAP_SHARED; #ifdef MAP_FILE flags |= MAP_FILE; #endif #ifdef MAP_VARIABLE flags |= MAP_VARIABLE; #endif *base = (char *)mmap((caddr_t)0, newlen, PROT_READ, flags, fd, 0L); if (*base == (char *)MAP_FAILED) { syslog(LOG_ERR, "IOERROR: mapping %s file%s%s: %m", name, mboxname ? " for " : "", mboxname ? mboxname : ""); snprintf(buf, sizeof(buf), "failed to mmap %s file", name); fatal(buf, EC_IOERR); } *len = newlen; } /* * Destroy mapping of file */ void EXPORTED map_free(const char **base, size_t *len) { if (*len) munmap((char *)*base, *len); *base = 0; *len = 0; } cyrus-imapd-2.5.10/lib/imparse.c0000644000175000017500000001335513001236020013321 00000000000000/* imparse.c -- IMxP client-side parsing routines * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include #include #include "imparse.h" #include "util.h" /* * Parse a word from the string starting at the pointer pointed to by 's'. * Places a pointer to the parsed word in the pointer at 'retval', * returns the character following the word, and modifies the pointer at * 's' to point after the returned character. Modifies the input buffer. */ EXPORTED int imparse_word(char **s, char **retval) { int c; *retval = *s; for (;;) { c = *(*s)++; if (!c || Uisspace(c) || c == '(' || c == ')' || c == '\"') { (*s)[-1] = '\0'; return c; } } } /* * Parse an astring from the string starting at the pointer pointed to * by 's'. On success, places a pointer to the parsed word in the * pointer at 'retval', returns the character following the word, and * modifies the pointer at 's' to point after the returned character. * On failure, returns EOF, modifies the pointer at 'retval' to point * at the empty string, and modifies 's' to point around the syntax error. * Modifies the input buffer. */ EXPORTED int imparse_astring(char **s, char **retval) { int c; char *d; int len = 0; int sawdigit = 0; switch (**s) { case '\0': case ' ': case '(': case ')': case '\r': case '\n': /* Invalid starting character */ *retval = ""; return EOF; default: /* * Atom -- parser is liberal in accepting specials other * than whitespace, parens, or double quotes */ return imparse_word(s, retval); case '\"': /* * Quoted-string. Parser is liberal in accepting qspecials * other than double-quote, CR, and LF. */ *retval = d = ++(*s); for (;;) { c = *(*s)++; if (c == '\\') { c = *(*s)++; } else if (c == '\"') { *d = '\0'; return *(*s)++; } else if (c == '\0' || c == '\r' || c == '\n') { *retval = ""; return EOF; } *d++ = c; } case '{': /* Literal */ (*s)++; while (Uisdigit(c = *(*s)++)) { sawdigit = 1; len = len*10 + c - '0'; } if (!sawdigit || c != '}' || *(*s)++ != '\r' || *(*s)++ != '\n') { *retval = ""; return EOF; } *retval = *s; *s += len; c = **s; *(*s)++ = '\0'; /* Note that 0 and '\0' mean the same thing */ return c; } } /* * Return nonzero if 's' matches the grammar for an atom. If 'len' is * zero then treat as a c string, \0 delimited. Otherwise check the * entire map, and consider not an natom if there's a NULL byte in the * mapped space. */ EXPORTED int imparse_isnatom(const char *s, int len) { int count = 0; if (!*s) return 0; for (; len || *s; s++) { count++; if (len && count > len) break; if (*s & 0x80 || *s < 0x1f || *s == 0x7f || *s == ' ' || *s == '{' || *s == '(' || *s == ')' || *s == '\"' || *s == '%' || *s == '*' || *s == '\\') return 0; } if (count >= 1024) return 0; return count; } EXPORTED int imparse_isatom(const char *s) { return imparse_isnatom(s, 0); } /* * Return nonzero if 's' matches the grammar for a sequence */ EXPORTED int imparse_issequence(const char* s) { int c; int len = 0; int sawcolon = 0; while ((c = *s)) { if (c == ',') { if (!len) return 0; if (!Uisdigit(s[-1]) && s[-1] != '*') return 0; sawcolon = 0; } else if (c == ':') { if (sawcolon || !len) return 0; if (!Uisdigit(s[-1]) && s[-1] != '*') return 0; sawcolon = 1; } else if (c == '*') { if (len && s[-1] != ',' && s[-1] != ':') return 0; if (Uisdigit(s[1])) return 0; } else if (!Uisdigit(c)) { return 0; } s++; len++; } if (len == 0) return 0; if (!Uisdigit(s[-1]) && s[-1] != '*') return 0; return 1; } /* * Return nonzero if 's' matches the grammar for a number */ EXPORTED int imparse_isnumber(const char *s) { if (!*s) return 0; for (; *s; s++) { if (!Uisdigit(*s)) return 0; } return 1; } cyrus-imapd-2.5.10/lib/chartable.h0000644000175000017500000000473513001236020013615 00000000000000/* Definitions internal to charset.c and chartable.c * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ struct charmap { unsigned int c; unsigned char next; }; struct charset { char *name; const struct charmap (*table)[256]; }; struct charset_alias { char *name; char *canon_name; }; /* unicode canon translations */ extern const int chartables_translation_multichar[]; extern const unsigned char chartables_translation_block16[256]; extern const unsigned char chartables_translation_block8[][256]; extern const int chartables_translation[][256]; /* named character sets */ extern const struct charset chartables_charset_table[]; extern const int chartables_num_charsets; extern const struct charset_alias charset_aliases[]; cyrus-imapd-2.5.10/lib/rfc822tok.c0000644000175000017500000001154213001236020013401 00000000000000/* rfc822tok.c -- RFC822/RFC2822 tokenizer * * Copyright (c) 2012 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include #include #include #include #include "rfc822tok.h" EXPORTED void rfc822tok_init(rfc822tok_t *t, const char *base, unsigned int len, unsigned int flags) { buf_init_ro(&t->buf, base, len); t->ptr = base; t->flags = flags; } EXPORTED void rfc822tok_init_buf(rfc822tok_t *t, const struct buf *b, unsigned int flags) { rfc822tok_init(t, (b ? b->s : NULL), (b ? b->len : 0), flags); } EXPORTED void rfc822tok_fini(rfc822tok_t *t) { buf_free(&t->buf); } static inline int is_special(rfc822tok_t *t, int c) { /* These specials are defined by RFC2822 */ if (strchr("()<>[]:;@\\,", c)) return 1; /* ...except '.' sometimes is and sometimes isn't special */ if (c == '.' && (t->flags & RFC822_SPECIAL_DOT)) return 1; /* ...and '=' sometimes is and sometimes isn't */ if (c == '=' && (t->flags & RFC822_SPECIAL_EQUAL)) return 1; return 0; } EXPORTED int rfc822tok_next(rfc822tok_t *t, char **textp) { const char *p; const char *end; int comment_depth = 0; static struct buf text = BUF_INITIALIZER; int r; buf_reset(&text); if (textp) *textp = NULL; if (!t->buf.len) return EOF; end = t->buf.s + t->buf.len; p = t->ptr; if (p >= end) return EOF; /* skip any leading whitespace and comments */ for ( ; p < end ; p++) { if (comment_depth) { if (*p == '\\') p++; else if (*p == ')') comment_depth--; else if (*p == '(') comment_depth++; } else if (*p == '(') { comment_depth++; } else if (!isspace(*p)) { break; } } if (comment_depth) { r = -EINVAL; goto out; } if (p >= end) { r = EOF; goto out; } /* RFC2822 specials are single-char tokens */ if (is_special(t, *p)) { r = *p++; goto out; } if (*p == '"') { /* parse quoted-string per RFC2822 section 3.2.5 */ int in_quoted_pair = 0; int in_quoted_string = 1; for (p++ ; p < end ; p++) { if (*p == '\r' && p+1 < end && p[1] == '\n') { /* elide CRLF inside a quoted string */ p++; /* a close reading of RFC2822 shows that \ is only * semantically invisible when part of a quoted-pair, * and CRLF is not part of a quoted-pair; so if we see a * dangling \ just before CRLF we need to include it in * the string */ if (in_quoted_pair) { buf_putc(&text, '\\'); in_quoted_pair = 0; } continue; } else if (in_quoted_pair) { in_quoted_pair = 0; buf_putc(&text, *p); } else if (*p == '\\') { in_quoted_pair = 1; continue; } else if (*p == '"') { in_quoted_string = 0; p++; break; } else { buf_putc(&text, *p); } } r = RFC822_QSTRING; if (in_quoted_string || in_quoted_pair) r = -EINVAL; goto out; } /* anything else is an atom */ for ( ; p < end ; p++) { if (isspace(*p) || *p == '(' || *p == '"' || is_special(t, *p)) break; buf_putc(&text, *p); } r = RFC822_ATOM; out: t->ptr = p; if (textp) *textp = text.len ? (char *)buf_cstring(&text) : NULL; return r; } cyrus-imapd-2.5.10/lib/util.c0000644000175000017500000011622013001236020012631 00000000000000/* util.c -- general utility functions * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include #include #include #include #include #include #include #include #include #include #include #include #include #if defined(__linux__) && defined(HAVE_LIBCAP) #include #include #endif #ifdef HAVE_UNISTD_H #include #endif #ifdef HAVE_STDINT_H #include #endif #include #include "exitcodes.h" #include "map.h" #include "retry.h" #include "util.h" #include "assert.h" #include "xmalloc.h" #ifdef HAVE_ZLIB #include "zlib.h" #endif #define BEAUTYBUFSIZE 4096 static const unsigned char unxdigit[128] = { 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff }; EXPORTED const unsigned char convert_to_lowercase[256] = { 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f, 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17, 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f, 0x20, 0x21, 0x22, 0x23, 0x24, 0x25, 0x26, 0x27, 0x28, 0x29, 0x2a, 0x2b, 0x2c, 0x2d, 0x2e, 0x2f, 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37, 0x38, 0x39, 0x3a, 0x3b, 0x3c, 0x3d, 0x3e, 0x3f, 0x40, 'a', 'b', 'c', 'd', 'e', 'f', 'g', 'h', 'i', 'j', 'k', 'l', 'm', 'n', 'o', 'p', 'q', 'r', 's', 't', 'u', 'v', 'w', 'x', 'y', 'z', 0x5b, 0x5c, 0x5d, 0x5e, 0x5f, 0x60, 'a', 'b', 'c', 'd', 'e', 'f', 'g', 'h', 'i', 'j', 'k', 'l', 'm', 'n', 'o', 'p', 'q', 'r', 's', 't', 'u', 'v', 'w', 'x', 'y', 'z', 0x7b, 0x7c, 0x7d, 0x7e, 0x7f, 0x80, 0x81, 0x82, 0x83, 0x84, 0x85, 0x86, 0x87, 0x88, 0x89, 0x8a, 0x8b, 0x8c, 0x8d, 0x8e, 0x8f, 0x90, 0x91, 0x92, 0x93, 0x94, 0x95, 0x96, 0x97, 0x98, 0x99, 0x9a, 0x9b, 0x9c, 0x9d, 0x9e, 0x9f, 0xa0, 0xa1, 0xa2, 0xa3, 0xa4, 0xa5, 0xa6, 0xa7, 0xa8, 0xa9, 0xaa, 0xab, 0xac, 0xad, 0xae, 0xaf, 0xb0, 0xb1, 0xb2, 0xb3, 0xb4, 0xb5, 0xb6, 0xb7, 0xb8, 0xb9, 0xba, 0xbb, 0xbc, 0xbd, 0xbe, 0xbf, 0xc0, 0xc1, 0xc2, 0xc3, 0xc4, 0xc5, 0xc6, 0xc7, 0xc8, 0xc9, 0xca, 0xcb, 0xcc, 0xcd, 0xce, 0xcf, 0xd0, 0xd1, 0xd2, 0xd3, 0xd4, 0xd5, 0xd6, 0xd7, 0xd8, 0xd9, 0xda, 0xdb, 0xdc, 0xdd, 0xde, 0xdf, 0xe0, 0xe1, 0xe2, 0xe3, 0xe4, 0xe5, 0xe6, 0xe7, 0xe8, 0xe9, 0xea, 0xeb, 0xec, 0xed, 0xee, 0xef, 0xf0, 0xf1, 0xf2, 0xf3, 0xf4, 0xf5, 0xf6, 0xf7, 0xf8, 0xf9, 0xfa, 0xfb, 0xfc, 0xfd, 0xfe, 0xff }; const unsigned char convert_to_uppercase[256] = { 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f, 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17, 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f, 0x20, 0x21, 0x22, 0x23, 0x24, 0x25, 0x26, 0x27, 0x28, 0x29, 0x2a, 0x2b, 0x2c, 0x2d, 0x2e, 0x2f, 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37, 0x38, 0x39, 0x3a, 0x3b, 0x3c, 0x3d, 0x3e, 0x3f, 0x40, 'A', 'B', 'C', 'D', 'E', 'F', 'G', 'H', 'I', 'J', 'K', 'L', 'M', 'N', 'O', 'P', 'Q', 'R', 'S', 'T', 'U', 'V', 'W', 'X', 'Y', 'Z', 0x5b, 0x5c, 0x5d, 0x5e, 0x5f, 0x60, 'A', 'B', 'C', 'D', 'E', 'F', 'G', 'H', 'I', 'J', 'K', 'L', 'M', 'N', 'O', 'P', 'Q', 'R', 'S', 'T', 'U', 'V', 'W', 'X', 'Y', 'Z', 0x7b, 0x7c, 0x7d, 0x7e, 0x7f, 0x80, 0x81, 0x82, 0x83, 0x84, 0x85, 0x86, 0x87, 0x88, 0x89, 0x8a, 0x8b, 0x8c, 0x8d, 0x8e, 0x8f, 0x90, 0x91, 0x92, 0x93, 0x94, 0x95, 0x96, 0x97, 0x98, 0x99, 0x9a, 0x9b, 0x9c, 0x9d, 0x9e, 0x9f, 0xa0, 0xa1, 0xa2, 0xa3, 0xa4, 0xa5, 0xa6, 0xa7, 0xa8, 0xa9, 0xaa, 0xab, 0xac, 0xad, 0xae, 0xaf, 0xb0, 0xb1, 0xb2, 0xb3, 0xb4, 0xb5, 0xb6, 0xb7, 0xb8, 0xb9, 0xba, 0xbb, 0xbc, 0xbd, 0xbe, 0xbf, 0xc0, 0xc1, 0xc2, 0xc3, 0xc4, 0xc5, 0xc6, 0xc7, 0xc8, 0xc9, 0xca, 0xcb, 0xcc, 0xcd, 0xce, 0xcf, 0xd0, 0xd1, 0xd2, 0xd3, 0xd4, 0xd5, 0xd6, 0xd7, 0xd8, 0xd9, 0xda, 0xdb, 0xdc, 0xdd, 0xde, 0xdf, 0xe0, 0xe1, 0xe2, 0xe3, 0xe4, 0xe5, 0xe6, 0xe7, 0xe8, 0xe9, 0xea, 0xeb, 0xec, 0xed, 0xee, 0xef, 0xf0, 0xf1, 0xf2, 0xf3, 0xf4, 0xf5, 0xf6, 0xf7, 0xf8, 0xf9, 0xfa, 0xfb, 0xfc, 0xfd, 0xfe, 0xff }; /* convert string to all lower case */ EXPORTED char *lcase(char* str) { char *scan = str; while (*scan) { *scan = TOLOWER(*scan); scan++; } return (str); } /* convert string to all upper case */ EXPORTED char *ucase(char* str) { char *scan = str; while (*scan) { *scan = convert_to_uppercase[(unsigned char)(*scan)]; scan++; } return (str); } /* clean up control characters in a string while copying it * returns pointer to end of dst string. * dst must have twice the length of source */ static char *beautify_copy(char* dst, const char* src) { unsigned char c; while (*src) { c = *src++ & 0x7F; if (!isprint(c)) { *dst++ = '^'; if (c > ' ') { c = '?'; } else { c += '@'; } } *dst++ = c; } *dst = '\0'; return (dst); } /* clean up control characters in a string while copying it * returns pointer to a static buffer containing the cleaned-up version */ EXPORTED char *beautify_string(const char* src) { static char *beautybuf = NULL; static int beautysize = 0; int len; len = strlen(src) * 2 + 1; if (beautysize < len) { if (!beautysize) { beautysize = len > BEAUTYBUFSIZE ? len : BEAUTYBUFSIZE; beautybuf = xmalloc(beautysize); } else { beautysize *= 2; if (len > beautysize) beautysize = len; beautybuf = xrealloc(beautybuf, beautysize); } } (void) beautify_copy(beautybuf, src); return beautybuf; } EXPORTED int strcmpsafe(const char *a, const char *b) { return strcmp((a == NULL ? "" : a), (b == NULL ? "" : b)); } EXPORTED int strncmpsafe(const char *a, const char *b, size_t n) { return strncmp((a == NULL ? "" : a), (b == NULL ? "" : b), n); } EXPORTED int strcasecmpsafe(const char *a, const char *b) { return strcasecmp((a == NULL ? "" : a), (b == NULL ? "" : b)); } /* in which NULL is NOT equal to "" */ EXPORTED int strcmpnull(const char *a, const char *b) { if (a) { if (b) return strcmp(a, b); return 1; } if (b) return -1; return 0; } /* do a binary search in a keyvalue array * nelem is the number of keyvalue elements in the kv array * cmpf is the comparison function (strcmp, strcasecmp, etc). * returns NULL if not found, or key/value pair if found. */ keyvalue *kv_bsearch(const char* key, keyvalue* kv, int nelem, int (*cmpf) (const char *s1, const char *s2)) { int top, mid = 0, bot, cmp = 0; cmp = 1; bot = 0; top = nelem - 1; while (top >= bot && (cmp = (*cmpf)(key, kv[mid = (bot + top) >> 1].key))) if (cmp < 0) { top = mid - 1; } else { bot = mid + 1; } return (cmp ? NULL : kv + mid); } /* Examine the name of a file, and return a single character * (as an int) that can be used as the name of a hash * directory. Stop before the first dot. Caller is responsible * for skipping any prefix of the name. */ EXPORTED int dir_hash_c(const char *name, int full) { int c; if (full) { unsigned char *pt; uint32_t n; enum { DIR_X = 3, DIR_Y = 5, DIR_P = 23, DIR_A = 'A' }; n = 0; pt = (unsigned char *)name; while (*pt && *pt != '.') { n = ((n << DIR_X) ^ (n >> DIR_Y)) ^ *pt; n &= UINT32_MAX; ++pt; } c = DIR_A + (n % DIR_P); } else { c = tolower(*name); if (!Uisascii(c) || !Uislower(c)) c = 'q'; } return c; } EXPORTED char *dir_hash_b(const char *name, int full, char buf[2]) { buf[0] = (char)dir_hash_c(name, full); buf[1] = '\0'; return buf; } EXPORTED int cyrus_close_sock(int fd) { shutdown(fd, SHUT_RD); return close(fd); } EXPORTED void cyrus_reset_stdio(void) { int devnull = open("/dev/null", O_RDWR, 0); if (devnull == -1) { fatal("open() on /dev/null failed", EC_TEMPFAIL); } /* stdin */ shutdown(0, SHUT_RD); dup2(devnull, 0); /* stdout */ shutdown(1, SHUT_RD); dup2(devnull, 1); /* stderr */ shutdown(2, SHUT_RD); dup2(devnull, 2); if (devnull > 2) close(devnull); } /* Given a directory, create a unique temporary file open for * reading and writing and return the file descriptor. * * This routine also unlinks the file so it won't appear in the * directory listing (but you won't have to worry about cleaning up * after it) */ EXPORTED int create_tempfile(const char *path) { int fd; char *pattern; pattern = strconcat(path, "/cyrus_tmpfile_XXXXXX", (char *)NULL); fd = mkstemp(pattern); if (fd >= 0 && unlink(pattern) == -1) { close(fd); fd = -1; } free(pattern); return fd; } /* Create all parent directories for the given path, * up to but not including the basename. */ EXPORTED int cyrus_mkdir(const char *pathname, mode_t mode __attribute__((unused))) { char *path = xstrdup(pathname); /* make a copy to write into */ char *p = path; int save_errno; struct stat sbuf; while ((p = strchr(p+1, '/'))) { *p = '\0'; if (mkdir(path, 0755) == -1 && errno != EEXIST) { save_errno = errno; if (stat(path, &sbuf) == -1) { errno = save_errno; syslog(LOG_ERR, "IOERROR: creating directory %s: %m", path); free(path); return -1; } } *p = '/'; } free(path); return 0; } static int _copyfile_helper(const char *from, const char *to, int flags) { int srcfd = -1; int destfd = -1; const char *src_base = 0; size_t src_size = 0; struct stat sbuf; int n; int r = 0; int nolink = flags & COPYFILE_NOLINK; /* try to hard link, but don't fail - fall back to regular copy */ if (!nolink) { if (link(from, to) == 0) return 0; if (errno == EEXIST) { if (unlink(to) == -1) { syslog(LOG_ERR, "IOERROR: unlinking to recreate %s: %m", to); return -1; } if (link(from, to) == 0) return 0; } } srcfd = open(from, O_RDONLY, 0666); if (srcfd == -1) { syslog(LOG_ERR, "IOERROR: opening %s: %m", from); r = -1; goto done; } if (fstat(srcfd, &sbuf) == -1) { syslog(LOG_ERR, "IOERROR: fstat on %s: %m", from); r = -1; goto done; } if (!sbuf.st_size) { syslog(LOG_ERR, "IOERROR: zero byte file %s: %m", from); r = -1; goto done; } destfd = open(to, O_RDWR|O_TRUNC|O_CREAT, 0666); if (destfd == -1) { if (!(flags & COPYFILE_MKDIR)) syslog(LOG_ERR, "IOERROR: creating %s: %m", to); r = -1; goto done; } map_refresh(srcfd, 1, &src_base, &src_size, sbuf.st_size, from, 0); n = retry_write(destfd, src_base, src_size); if (n == -1 || fsync(destfd)) { syslog(LOG_ERR, "IOERROR: writing %s: %m", to); r = -1; unlink(to); /* remove any rubbish we created */ goto done; } done: map_free(&src_base, &src_size); if (srcfd != -1) close(srcfd); if (destfd != -1) close(destfd); return r; } EXPORTED int cyrus_copyfile(const char *from, const char *to, int flags) { int r; /* copy over self is an error */ if (!strcmp(from, to)) return -1; r = _copyfile_helper(from, to, flags); /* try creating the target directory if requested */ if (r && (flags & COPYFILE_MKDIR)) { r = cyrus_mkdir(to, 0755); if (!r) r = _copyfile_helper(from, to, flags & ~COPYFILE_MKDIR); } if (!r && (flags & COPYFILE_RENAME)) { /* remove the original file if the copy succeeded */ unlink(from); } return r; } #if defined(__linux__) && defined(HAVE_LIBCAP) EXPORTED int set_caps(int stage, int is_master) { cap_t cap = NULL; int r = 0; int e = errno; static const char * const capsets[2][5] = { { /* !master */ "cap_setuid=ep", /* BEFORE_SETUID */ "=", /* AFTER_SETUID */ "=", /* doesn't happen */ "=", /* doesn't happen */ "=" /* doesn't happen */ }, { /* master */ "cap_net_bind_service=p cap_setuid=ep", /* BEFORE_SETUID */ "cap_net_bind_service=p", /* AFTER_SETUID */ "cap_net_bind_service=ep", /* BEFORE_BIND */ "cap_net_bind_service=p", /* AFTER_BIND */ "=" /* AFTER_FORK */ } }; cap = cap_from_text(capsets[!!is_master][stage]); assert(cap != NULL); r = cap_set_proc(cap); if (r < 0) { syslog(LOG_ERR, "cannot set caps: %m"); goto out; } if ((stage == BEFORE_SETUID) || (stage == AFTER_SETUID)) { r = prctl(PR_SET_KEEPCAPS, (stage == BEFORE_SETUID)); if (r < 0) { syslog(LOG_ERR, "cannot set keepcaps flag: %m"); goto out; } } out: if (cap) cap_free(cap); errno = e; /* preserve errno so the caller's error reporting is easy */ return r; } #else EXPORTED int set_caps(int stage __attribute__((unused)), int is_master __attribute__((unused))) { return 0; } #endif static int cap_setuid(int uid, int is_master) { int r; set_caps(BEFORE_SETUID, is_master); r = setuid(uid); set_caps(AFTER_SETUID, is_master); return r; } EXPORTED int become_cyrus(int is_master) { struct passwd *p; uid_t newuid; gid_t newgid; int result; static uid_t uid = 0; if (uid) return cap_setuid(uid, is_master); p = getpwnam(CYRUS_USER); if (p == NULL) { syslog(LOG_ERR, "no entry in /etc/passwd for user %s", CYRUS_USER); return -1; } /* Save these in case initgroups does a getpw*() */ newuid = p->pw_uid; newgid = p->pw_gid; if (newuid == geteuid() && newuid == getuid() && newgid == getegid() && newgid == getgid()) { /* already the Cyrus user, stop trying */ uid = newuid; set_caps(AFTER_SETUID, is_master); return 0; } if (initgroups(CYRUS_USER, newgid)) { syslog(LOG_ERR, "unable to initialize groups for user %s: %s", CYRUS_USER, strerror(errno)); return -1; } if (setgid(newgid)) { syslog(LOG_ERR, "unable to set group id to %d for user %s: %s", newgid, CYRUS_USER, strerror(errno)); return -1; } result = cap_setuid(newuid, is_master); /* Only set static uid if successful, else future calls won't reset gid */ if (result == 0) uid = newuid; return result; } static int cmdtime_enabled = 0; static struct timeval cmdtime_start, cmdtime_end, nettime_start, nettime_end; static double totaltime, cmdtime, nettime; double timeval_get_double(const struct timeval *tv) { return (double)tv->tv_sec + (double)tv->tv_usec/1000000.0; } EXPORTED void timeval_set_double(struct timeval *tv, double d) { double sec; double subsec = modf(d, &sec); tv->tv_sec = sec; tv->tv_usec = 1000000.0*subsec; } EXPORTED void timeval_add_double(struct timeval *tv, double delta) { timeval_set_double(tv, timeval_get_double(tv) + delta); } EXPORTED double timesub(const struct timeval *start, const struct timeval *end) { return (double)(end->tv_sec - start->tv_sec) + (double)(end->tv_usec - start->tv_usec)/1000000.0; } EXPORTED void cmdtime_settimer(int enable) { cmdtime_enabled = enable; } EXPORTED void cmdtime_starttimer(void) { if (!cmdtime_enabled) return; gettimeofday(&cmdtime_start, 0); totaltime = cmdtime = nettime = 0.0; } EXPORTED void cmdtime_endtimer(double *pcmdtime, double *pnettime) { if (!cmdtime_enabled) return; gettimeofday(&cmdtime_end, 0); totaltime = timesub(&cmdtime_start, &cmdtime_end); cmdtime = totaltime - nettime; *pcmdtime = cmdtime; *pnettime = nettime; } EXPORTED void cmdtime_netstart(void) { if (!cmdtime_enabled) return; gettimeofday(&nettime_start, 0); } EXPORTED void cmdtime_netend(void) { if (!cmdtime_enabled) return; gettimeofday(&nettime_end, 0); nettime += timesub(&nettime_start, &nettime_end); } /* * Like the system clock() but works in system time * rather than process virtual time. Would be more * useful and sensible if it worked in system monotonic * time using clock_gettime(CLOCK_MONOTONIC) but that * would require linking with -lrt. */ EXPORTED clock_t sclock(void) { struct timeval now; gettimeofday(&now, NULL); return now.tv_sec * CLOCKS_PER_SEC + (now.tv_usec * CLOCKS_PER_SEC) / 1000000; } EXPORTED int parseint32(const char *p, const char **ptr, int32_t *res) { int32_t result = 0; int gotchar = 0; if (!p) return -1; /* INT_MAX == 2147483647 */ while (cyrus_isdigit(*p)) { if (result > 214748364 || (result == 214748364 && (*p > '7'))) fatal("num too big", EC_IOERR); result = result * 10 + *p++ - '0'; gotchar = 1; } if (!gotchar) return -1; if (ptr) *ptr = p; if (res) *res = result; return 0; } EXPORTED int parseuint32(const char *p, const char **ptr, uint32_t *res) { uint32_t result = 0; int gotchar = 0; if (!p) return -1; /* UINT_MAX == 4294967295U */ while (cyrus_isdigit(*p)) { if (result > 429496729 || (result == 429496729 && (*p > '5'))) fatal("num too big", EC_IOERR); result = result * 10 + *p++ - '0'; gotchar = 1; } if (!gotchar) return -1; if (ptr) *ptr = p; if (res) *res = result; return 0; } EXPORTED int parsenum(const char *p, const char **ptr, int maxlen, bit64 *res) { bit64 result = 0; int n; int cval; /* ULLONG_MAX == 18446744073709551615ULL * - and I don't care about those last 5 */ for (n = 0; !maxlen || n < maxlen; n++) { if (!cyrus_isdigit(p[n])) break; if (result > 1844674407370955161ULL) fatal("num too big", EC_IOERR); cval = p[n] - '0'; result = result * 10 + cval; } /* no characters found... */ if (!n) return -1; if (ptr) *ptr = p + n; if (res) *res = result; return 0; } EXPORTED int parsehex(const char *p, const char **ptr, int maxlen, bit64 *res) { bit64 result = 0; int n; int cval; /* ULLONG_MAX == 18446744073709551615ULL * - and I don't care about those last 5 */ for (n = 0; !maxlen || n < maxlen; n++) { if (result > 1844674407370955161ULL) fatal("num too big", EC_IOERR); cval = unxdigit[(int)p[n]]; if (cval == 0xff) break; result = result * 16 + cval; } /* no characters found... */ if (!n) return -1; if (ptr) *ptr = p + n; if (res) *res = result; return 0; } /* buffer handling functions */ static size_t roundup(size_t size) { if (size < 32) return 32; if (size < 64) return 64; if (size < 128) return 128; if (size < 256) return 256; if (size < 512) return 512; return ((size + 1024) & ~1023); } /* this function has a side-effect of always leaving the buffer writable */ EXPORTED void _buf_ensure(struct buf *buf, size_t n) { size_t newlen = buf->len + n; char *s; assert(newlen); /* we never alloc zero bytes */ if (buf->alloc >= newlen) return; if (buf->alloc) { buf->alloc = roundup(newlen); buf->s = xrealloc(buf->s, buf->alloc); } else { buf->alloc = roundup(newlen); s = xmalloc(buf->alloc); /* if no allocation, but data exists, it means copy on write. * grab a copy of what's there now */ if (buf->len) { assert(buf->s); memcpy(s, buf->s, buf->len); } /* can release MMAP now, we've copied the data out */ if (buf->flags & BUF_MMAP) { size_t len = buf->len; /* don't wipe the length, we still need it */ map_free((const char **)&buf->s, &len); buf->flags &= ~BUF_MMAP; } buf->s = s; } } EXPORTED const char *buf_cstring(struct buf *buf) { buf_ensure(buf, 1); buf->s[buf->len] = '\0'; return buf->s; } EXPORTED char *buf_newcstring(struct buf *buf) { char *ret = xstrdup(buf_cstring(buf)); buf_reset(buf); return ret; } EXPORTED char *buf_release(struct buf *buf) { char *ret = (char *)buf_cstring(buf); buf_init(buf); return ret; } EXPORTED const char *buf_cstringnull(struct buf *buf) { if (!buf->s) return NULL; return buf_cstring(buf); } EXPORTED char *buf_releasenull(struct buf *buf) { char *ret = (char *)buf_cstringnull(buf); buf_init(buf); return ret; } EXPORTED void buf_getmap(struct buf *buf, const char **base, size_t *len) { *base = buf->s; *len = buf->len; } /* fetch a single line a file - terminated with \n ONLY. * buf does not contain the \n. * NOTE: if the final line does not contain a \n we still * return true so that the caller will process the line, * so a file A\nB will return two true responses with bufs * containing "A" and "B" respectively before returning a * false to the third call */ EXPORTED int buf_getline(struct buf *buf, FILE *fp) { int c; buf_reset(buf); while ((c = fgetc(fp)) != EOF) { if (c == '\n') break; buf_putc(buf, c); } /* ensure trailing NULL */ buf_cstring(buf); /* EOF and no content, we're done */ return (!(buf->len == 0 && c == EOF)); } EXPORTED size_t buf_len(const struct buf *buf) { return buf->len; } EXPORTED const char *buf_base(const struct buf *buf) { return buf->s; } EXPORTED void buf_reset(struct buf *buf) { if (buf->flags & BUF_MMAP) map_free((const char **)&buf->s, &buf->len); buf->len = 0; buf->flags = 0; } EXPORTED void buf_truncate(struct buf *buf, ssize_t len) { if (len < 0) { len = buf->len + len; if (len < 0) len = 0; } if ((size_t)len > buf->alloc) { /* grow the buffer and zero-fill the new bytes */ size_t more = len - buf->len; buf_ensure(buf, more); memset(buf->s + buf->len, 0, more); } buf->len = len; } EXPORTED void buf_setcstr(struct buf *buf, const char *str) { buf_setmap(buf, str, strlen(str)); } EXPORTED void buf_setmap(struct buf *buf, const char *base, size_t len) { buf_reset(buf); if (len) { buf_ensure(buf, len); memcpy(buf->s, base, len); buf->len = len; } } EXPORTED void buf_copy(struct buf *dst, const struct buf *src) { buf_setmap(dst, src->s, src->len); } EXPORTED void buf_append(struct buf *dst, const struct buf *src) { buf_appendmap(dst, src->s, src->len); } EXPORTED void buf_appendcstr(struct buf *buf, const char *str) { buf_appendmap(buf, str, strlen(str)); } EXPORTED void buf_appendbit32(struct buf *buf, bit32 num) { bit32 item = htonl(num); buf_appendmap(buf, (char *)&item, 4); } EXPORTED void buf_appendmap(struct buf *buf, const char *base, size_t len) { if (len) { buf_ensure(buf, len); memcpy(buf->s + buf->len, base, len); buf->len += len; } } /* This is like buf_appendmap() but attempts an optimisation where the * first append to an empty buf results in a read-only pointer to the * data at 'base' instead of a writable copy. */ EXPORTED void buf_cowappendmap(struct buf *buf, const char *base, unsigned int len) { if (!buf->s) buf_init_ro(buf, base, len); else buf_appendmap(buf, base, len); } /* This is like buf_cowappendmap() but takes over the given map 'base', * which is a malloc()ed C string buffer of at least 'len' bytes. */ EXPORTED void buf_cowappendfree(struct buf *buf, char *base, unsigned int len) { if (!buf->s) buf_initm(buf, base, len); else { buf_appendmap(buf, base, len); free(base); } } EXPORTED void buf_vprintf(struct buf *buf, const char *fmt, va_list args) { va_list ap; int room; int n; /* Add some more room to the buffer. We just guess a * size and rely on vsnprintf() to tell us if it * needs to overrun the size. */ buf_ensure(buf, 1024); /* Copy args in case we guess wrong on the size */ va_copy(ap, args); room = buf->alloc - buf->len; n = vsnprintf(buf->s + buf->len, room, fmt, args); if (n >= room) { /* woops, we guessed wrong...retry with enough space */ buf_ensure(buf, n+1); n = vsnprintf(buf->s + buf->len, n+1, fmt, ap); } va_end(ap); buf->len += n; } EXPORTED void buf_printf(struct buf *buf, const char *fmt, ...) { va_list args; va_start(args, fmt); buf_vprintf(buf, fmt, args); va_end(args); } static void buf_replace_buf(struct buf *buf, size_t offset, size_t length, const struct buf *replace) { if (offset > buf->len) return; if (offset + length > buf->len) length = buf->len - offset; /* we need buf to be a writable C string now please */ buf_cstring(buf); if (replace->len > length) { /* string will need to expand */ buf_ensure(buf, replace->len - length + 1); } if (length != replace->len) { /* +1 to copy the NULL to keep cstring semantics */ memmove(buf->s + offset + replace->len, buf->s + offset + length, buf->len - offset - length + 1); buf->len += (replace->len - length); } if (replace->len) memcpy(buf->s + offset, replace->s, replace->len); } /** * Replace all instances of the string literal @match in @buf * with the string @replace, which may be NULL to just remove * instances of @match. * Returns: the number of substitutions made. */ EXPORTED int buf_replace_all(struct buf *buf, const char *match, const char *replace) { int n = 0; int matchlen = strlen(match); struct buf replace_buf = BUF_INITIALIZER; size_t off; char *p; buf_init_ro_cstr(&replace_buf, replace); /* we need buf to be a nul terminated string now please */ buf_cstring(buf); off = 0; while ((p = strstr(buf->s + off, match))) { off = (p - buf->s); buf_replace_buf(buf, off, matchlen, &replace_buf); n++; off += replace_buf.len; } return n; } EXPORTED int buf_replace_char(struct buf *buf, char match, char replace) { int n = 0; size_t i; /* we need writable, so may as well cstring it */ buf_cstring(buf); for (i = 0; i < buf->len; i++) { if (buf->s[i] == match) { buf->s[i] = replace; n++; } } return n; } #ifdef ENABLE_REGEX /** * Replace the first instance of the compiled regexp @preg * in @buf with the string @replace, which may be NULL to just * remove an instance of @preg. Does not support capture references * in the replace text. * Returns: the number of substitutions made (0 or 1) */ EXPORTED int buf_replace_one_re(struct buf *buf, const regex_t *preg, const char *replace) { struct buf replace_buf = BUF_INITIALIZER; regmatch_t rm; buf_init_ro_cstr(&replace_buf, replace); /* we need buf to be a nul terminated string now please */ buf_cstring(buf); if (!regexec(preg, buf->s, 1, &rm, 0)) { buf_replace_buf(buf, rm.rm_so, rm.rm_eo - rm.rm_so, &replace_buf); return 1; } return 0; } /** * Replace all instances of the compiled regexp @preg in @buf * with the string @replace, which may be NULL to just remove * instances of @preg. Does not support capture references * in the replace text. * Returns: the number of substitutions made. */ EXPORTED int buf_replace_all_re(struct buf *buf, const regex_t *preg, const char *replace) { int n = 0; struct buf replace_buf = BUF_INITIALIZER; regmatch_t rm; size_t off; buf_init_ro_cstr(&replace_buf, replace); /* we need buf to be a nul terminated string now please */ buf_cstring(buf); off = 0; while (!regexec(preg, buf->s + off, 1, &rm, (off ? REG_NOTBOL : 0))) { buf_replace_buf(buf, off + rm.rm_so, rm.rm_eo - rm.rm_so, &replace_buf); off += rm.rm_so + replace_buf.len; n++; } return n; } #endif EXPORTED void buf_insert(struct buf *dst, unsigned int off, const struct buf *src) { buf_replace_buf(dst, off, 0, src); } EXPORTED void buf_insertcstr(struct buf *dst, unsigned int off, const char *str) { struct buf str_buf = BUF_INITIALIZER; buf_init_ro_cstr(&str_buf, str); buf_replace_buf(dst, off, 0, &str_buf); } EXPORTED void buf_insertmap(struct buf *dst, unsigned int off, const char *base, int len) { struct buf map_buf = BUF_INITIALIZER; buf_init_ro(&map_buf, base, len); buf_replace_buf(dst, off, 0, &map_buf); } EXPORTED void buf_remove(struct buf *dst, unsigned int off, unsigned int len) { struct buf empty_buf = BUF_INITIALIZER; buf_replace_buf(dst, off, len, &empty_buf); } /* * Compare two struct bufs bytewise. Returns a number * like strcmp(), suitable for sorting e.g. with qsort(), */ EXPORTED int buf_cmp(const struct buf *a, const struct buf *b) { size_t len = MIN(a->len, b->len); int r = 0; if (len) r = memcmp(a->s, b->s, len); if (!r) { if (a->len < b->len) r = -1; else if (a->len > b->len) r = 1; } return r; } EXPORTED void buf_init(struct buf *buf) { buf->alloc = 0; buf->len = 0; buf->flags = 0; buf->s = NULL; } /* * Initialise a struct buf to point to read-only data. The key here is * setting buf->alloc=0 which indicates CoW is in effect, i.e. the data * pointed to needs to be copied should it ever be modified. */ EXPORTED void buf_init_ro(struct buf *buf, const char *base, size_t len) { buf->alloc = 0; buf->len = len; buf->flags = 0; buf->s = (char *)base; } /* * Initialise a struct buf to point to writable data at 'base', which * must be a malloc()ed allocation at least 'len' bytes long and is * taken over by the struct buf. */ EXPORTED void buf_initm(struct buf *buf, char *base, int len) { buf->alloc = buf->len = len; buf->flags = 0; buf->s = base; } /* * Initialise a struct buf to point to a read-only C string. */ EXPORTED void buf_init_ro_cstr(struct buf *buf, const char *str) { buf->alloc = 0; buf->len = (str ? strlen(str) : 0); buf->flags = 0; buf->s = (char *)str; } /* * Initialise a struct buf to point to a read-only mmap()ing. * This buf is CoW, and if written to the data will be freed * using map_free(). */ EXPORTED void buf_init_mmap(struct buf *buf, int onceonly, int fd, const char *fname, size_t size, const char *mboxname) { buf->flags = BUF_MMAP; map_refresh(fd, onceonly, (const char **)&buf->s, &buf->len, size, fname, mboxname); } static void _buf_free_data(struct buf *buf) { if (buf->alloc) free(buf->s); else if (buf->flags & BUF_MMAP) map_free((const char **)&buf->s, &buf->len); } EXPORTED void buf_free(struct buf *buf) { _buf_free_data(buf); buf->alloc = 0; buf->s = NULL; buf->len = 0; buf->flags = 0; } EXPORTED void buf_move(struct buf *dst, struct buf *src) { _buf_free_data(dst); *dst = *src; buf_init(src); } EXPORTED int buf_findchar(const struct buf *buf, unsigned int off, int c) { const char *p; if (off < buf->len && (p = memchr(buf->s + off, c, buf->len - off))) return (p - buf->s); return -1; } /* * Find (the first line in) 'line' in the buffer 'buf'. The found text * will be a complete line, i.e. bounded by either \n newlines or by the * edges of 'buf'. Returns the byte index into 'buf' of the found text, * or -1 if not found. */ EXPORTED int buf_findline(const struct buf *buf, const char *line) { int linelen; const char *p; const char *end = buf->s + buf->len; if (!line) return -1; /* find the length of the first line in the text at 'line' */ p = strchr(line, '\n'); linelen = (p ? (size_t)(p - line) : strlen(line)); if (linelen == 0) return -1; for (p = buf->s ; (p = (const char *)memmem(p, end-p, line, linelen)) != NULL ; p++) { /* check the found string is at line boundaries */ if (p > buf->s && p[-1] != '\n') continue; if ((p+linelen) < end && p[linelen] != '\n') continue; return (p - buf->s); } return -1; } EXPORTED char *strconcat(const char *s1, ...) { int sz = 1; /* 1 byte for the trailing NUL */ const char *s; char *buf; char *p; va_list args; if (s1 == NULL) return NULL; /* first pass: calculate length */ sz += strlen(s1); va_start(args, s1); while ((s = va_arg(args, const char *)) != NULL) sz += strlen(s); va_end(args); /* allocate exactly the right amount of space */ p = buf = xmalloc(sz); /* second pass: copy strings in */ strcpy(p, s1); p += strlen(p); va_start(args, s1); while ((s = va_arg(args, const char *)) != NULL) { strcpy(p, s); p += strlen(p); } va_end(args); return buf; } EXPORTED int bin_to_hex(const void *bin, size_t binlen, char *hex, int flags) { const unsigned char *v = bin; char *p = hex; size_t i; const char *xd = (flags & BH_UPPER ? "0123456789ABCDEF" : "0123456789abcdef"); char sep = _BH_GETSEP(flags); for (i = 0; i < binlen; i++, v++) { if (i && sep) *p++ = sep; *p++ = xd[(*v >> 4) & 0xf]; *p++ = xd[*v & 0xf]; } *p = '\0'; return p-hex; } EXPORTED int hex_to_bin(const char *hex, size_t hexlen, void *bin) { unsigned char *v = bin, msn, lsn; const char *p = hex; size_t i; if (hex == NULL) return -1; if (hexlen == 0) hexlen = strlen(hex); if (hexlen % 2) return -1; hexlen /= 2; for (i = 0 ; i < hexlen ; i++) { msn = unxdigit[(*p++) & 0x7f]; if (msn == 0xff) return -1; lsn = unxdigit[(*p++) & 0x7f]; if (lsn == 0xff) return -1; *v++ = (msn << 4) | lsn; } return (unsigned char *)v - (unsigned char *)bin; } #ifdef HAVE_ZLIB /* Wrappers for our memory management functions */ static voidpf zalloc(voidpf opaque __attribute__((unused)), uInt items, uInt size) { return (voidpf) xmalloc(items * size); } static void zfree(voidpf opaque __attribute__((unused)), voidpf address) { free(address); } EXPORTED int buf_inflate(struct buf *src, int scheme) { struct buf localbuf = BUF_INITIALIZER; int zr = Z_OK; z_stream *zstrm = (z_stream *) xmalloc(sizeof(z_stream)); int windowBits; switch (scheme) { case DEFLATE_RAW: windowBits = -MAX_WBITS; /* raw deflate */ break; case DEFLATE_GZIP: windowBits = 16+MAX_WBITS; /* gzip header */ break; case DEFLATE_ZLIB: default: windowBits = MAX_WBITS; /* zlib header */ break; } zstrm->zalloc = zalloc; zstrm->zfree = zfree; zstrm->opaque = Z_NULL; zstrm->next_in = Z_NULL; zstrm->avail_in = 0; zr = inflateInit2(zstrm, windowBits); if (zr != Z_OK) goto err; /* set up the source */ zstrm->next_in = (unsigned char *)src->s; zstrm->avail_in = src->len; /* prepare the destination */ do { buf_ensure(&localbuf, 4096); /* find the buffer */ zstrm->next_out = (unsigned char *)localbuf.s + localbuf.len; zstrm->avail_out = localbuf.alloc - localbuf.len; zr = inflate(zstrm, Z_SYNC_FLUSH); if (!(zr == Z_OK || zr == Z_STREAM_END || zr == Z_BUF_ERROR)) goto err; localbuf.len = localbuf.alloc - zstrm->avail_out; } while (zstrm->avail_out == 0); inflateEnd(zstrm); free(zstrm); buf_free(src); /* dispose of current buffer */ *src = localbuf; /* in place replace */ return 0; err: free(zstrm); buf_free(&localbuf); return -1; } EXPORTED int buf_deflate(struct buf *src, int compLevel, int scheme) { struct buf localbuf = BUF_INITIALIZER; int zr = Z_OK; z_stream *zstrm = (z_stream *) xmalloc(sizeof(z_stream)); int windowBits; switch (scheme) { case DEFLATE_RAW: windowBits = -MAX_WBITS; /* raw deflate */ break; case DEFLATE_GZIP: windowBits = 16+MAX_WBITS; /* gzip header */ break; case DEFLATE_ZLIB: default: windowBits = MAX_WBITS; /* zlib header */ break; } zstrm->zalloc = zalloc; zstrm->zfree = zfree; zstrm->opaque = Z_NULL; zr = deflateInit2(zstrm, compLevel, Z_DEFLATED, windowBits, MAX_MEM_LEVEL, Z_DEFAULT_STRATEGY); if (zr != Z_OK) goto err; /* set up the source */ zstrm->next_in = (unsigned char *)src->s; zstrm->avail_in = src->len; /* prepare the destination */ do { buf_ensure(&localbuf, 4096); /* find the buffer */ zstrm->next_out = (unsigned char *)localbuf.s + localbuf.len; zstrm->avail_out = localbuf.alloc - localbuf.len; zr = deflate(zstrm, Z_SYNC_FLUSH); if (!(zr == Z_OK || zr == Z_STREAM_END || zr == Z_BUF_ERROR)) goto err; localbuf.len = localbuf.alloc - zstrm->avail_out; } while (zstrm->avail_out == 0); deflateEnd(zstrm); free(zstrm); buf_free(src); /* dispose of current buffer */ *src = localbuf; /* in place replace */ return 0; err: free(zstrm); buf_free(&localbuf); return -1; } #endif /* * Warm up a file, by beginning background readahead. @offset and * @length define a subset of the file to be warmed; @length = 0 means * to the end of the file. Returns a UNIX errno or 0 on success. No * error is reported if the file is missing or the kernel doesn't have * the magic system call. * * Returns zero on success or an error code (system error code). */ EXPORTED int warmup_file(const char *filename, off_t offset, off_t length) { int fd; int r; fd = open(filename, O_RDONLY, 0); if (fd < 0) return errno; /* Note, posix_fadvise() returns its error code rather than * setting errno. Unlike every other system call including * others defined in the same standard by the same committee. */ r = posix_fadvise(fd, offset, length, POSIX_FADV_WILLNEED); /* posix_fadvise(WILLNEED) on Linux will return an EINVAL error * if the file is on tmpfs, even though this effectively means * the file's bytes are all already available in RAM. Duh. */ if (r == EINVAL) r = 0; close(fd); return r; } cyrus-imapd-2.5.10/lib/strhash.c0000644000175000017500000000412112772415051013345 00000000000000/* strhash.c string hashing * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include "config.h" EXPORTED unsigned strhash(const char *string) { unsigned ret_val = 0; int i; while (*string) { i = (int) *string; ret_val ^= i; ret_val <<= 1; string ++; } return ret_val; } cyrus-imapd-2.5.10/lib/assert.h0000644000175000017500000000423613001236020013165 00000000000000/* assert.h -- assert() macro that can exit cleanly * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #ifndef INCLUDED_ASSERT_H #define INCLUDED_ASSERT_H #ifdef __STDC__ #define assert(ex) {if (!(ex))assertionfailed(__FILE__, __LINE__, #ex);} void assertionfailed(const char *file, int line, const char *expr); #else #define assert(ex) {if (!(ex))assertionfailed(__FILE__, __LINE__, (char*)0);} #endif #endif /* INCLUDED_ASSERT_H */ cyrus-imapd-2.5.10/lib/lock_flock.c0000644000175000017500000001131413001236020013760 00000000000000/* lock_flock.c -- Lock files using flock() * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include #include #include #include #include #ifdef HAVE_UNISTD_H #include #endif #include "cyr_lock.h" EXPORTED const char *lock_method_desc = "flock"; /* * Block until we obtain an exclusive lock on the file descriptor 'fd', * opened for reading and writing on the file named 'filename'. If * 'filename' is replaced, will re-open it as 'fd' and acquire a lock * on the new file. * * On success, returns 0. If a pointer to a struct stat is given as * 'sbuf', it is filled in. * * On failure, returns -1 with an error code in errno. If * 'failaction' is provided, it is filled in with a pointer to a fixed * string naming the action that failed. * */ EXPORTED int lock_reopen_ex(int fd, const char *filename, struct stat *sbuf, const char **failaction, int *changed) { int r; struct stat sbuffile, sbufspare; int newfd; if (!sbuf) sbuf = &sbufspare; for (;;) { r = flock(fd, LOCK_EX); if (r == -1) { if (errno == EINTR) continue; if (failaction) *failaction = "locking"; return -1; } fstat(fd, sbuf); r = stat(filename, &sbuffile); if (r == -1) { if (failaction) *failaction = "stating"; flock(fd, LOCK_UN); return -1; } if (sbuf->st_ino == sbuffile.st_ino) return 0; if (changed) *changed = 1; newfd = open(filename, O_RDWR); if (newfd == -1) { if (failaction) *failaction = "opening"; flock(fd, LOCK_UN); return -1; } dup2(newfd, fd); close(newfd); } } /* * Obtain an exclusive lock on 'fd'. * Returns 0 for success, -1 for failure, with errno set to an * appropriate error code. */ EXPORTED int lock_blocking(int fd, const char *filename __attribute__((unused))) { int r; for (;;) { r = flock(fd, LOCK_EX); if (r != -1) return 0; if (errno == EINTR) continue; return -1; } } /* * Obtain a shared lock on 'fd'. * Returns 0 for success, -1 for failure, with errno set to an * appropriate error code. */ EXPORTED int lock_shared(int fd, const char *filename __attribute__((unused))) { int r; for (;;) { r = flock(fd, LOCK_SH); if (r != -1) return 0; if (errno == EINTR) continue; return -1; } } /* * Attempt to get an exclusive lock on 'fd' without blocking. * Returns 0 for success, -1 for failure, with errno set to an * appropriate error code. */ EXPORTED int lock_nonblocking(int fd, const char *filename __attribute__((unused))) { int r; for (;;) { r = flock(fd, LOCK_EX|LOCK_NB); if (r != -1) return 0; if (errno == EINTR) continue; return -1; } } /* * Release any lock on 'fd'. Always returns success. */ EXPORTED int lock_unlock(int fd, const char *filename __attribute__((unused))) { int r; for (;;) { r = flock(fd, LOCK_UN); if (r != -1) return 0; if (errno == EINTR) continue; /* xxx help! */ return -1; } } cyrus-imapd-2.5.10/lib/wildmat.c0000644000175000017500000001724713001236020013326 00000000000000/* wildmat.h - NNTP wildmat processing functions * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ /* ** ** Do shell-style pattern matching for ?, \, [], and * characters. ** Might not be robust in face of malformed patterns; e.g., "foo[a-" ** could cause a segmentation violation. It is 8bit clean. ** ** Written by Rich $alz, mirror!rs, Wed Nov 26 19:03:17 EST 1986. ** Rich $alz is now . ** April, 1991: Replaced mutually-recursive calls with in-line code ** for the star character. ** ** Special thanks to Lars Mathiesen for the ABORT code. ** This can greatly speed up failing wildcard patterns. For example: ** pattern: -*-*-*-*-*-*-12-*-*-*-m-*-*-* ** text 1: -adobe-courier-bold-o-normal--12-120-75-75-m-70-iso8859-1 ** text 2: -adobe-courier-bold-o-normal--12-120-75-75-X-70-iso8859-1 ** Text 1 matches with 51 calls, while text 2 fails with 54 calls. Without ** the ABORT code, it takes 22310 calls to fail. Ugh. The following ** explanation is from Lars: ** The precondition that must be fulfilled is that DoMatch will consume ** at least one character in text. This is true if *p is neither '*' nor ** '\0'.) The last return has ABORT instead of FALSE to avoid quadratic ** behaviour in cases like pattern "*a*b*c*d" with text "abcxxxxx". With ** FALSE, each star-loop has to run to the end of the text; with ABORT ** only the last one does. ** ** Once the control of one instance of DoMatch enters the star-loop, that ** instance will return either TRUE or ABORT, and any calling instance ** will therefore return immediately after (without calling recursively ** again). In effect, only one star-loop is ever active. It would be ** possible to modify the code to maintain this context explicitly, ** eliminating all recursive calls at the cost of some complication and ** loss of clarity (and the ABORT stuff seems to be unclear enough by ** itself). I think it would be unwise to try to get this into a ** released version unless you have a good test data base to try it out ** on. */ #include #include #include #include "config.h" #include "wildmat.h" #include "xmalloc.h" #define TRUE 1 #define FALSE 0 #define ABORT -1 /* What character marks an inverted character class? */ #define NEGATE_CLASS '^' /* Is "*" a common pattern? */ #define OPTIMIZE_JUST_STAR /* Do tar(1) matching rules, which ignore a trailing slash? */ #undef MATCH_TAR_PATTERN /* ** Match text and p, return TRUE, FALSE, or ABORT. */ static int DoMatch(const char *text, const char *p) { int last; int matched; int reverse; for ( ; *p; text++, p++) { if (*text == '\0' && *p != '*') return ABORT; switch (*p) { case '\\': /* Literal match with following character. */ p++; /* FALLTHROUGH */ default: if (*text != *p) return FALSE; continue; case '?': /* Match anything. */ continue; case '*': while (*++p == '*') /* Consecutive stars act just like one. */ continue; if (*p == '\0') /* Trailing star matches everything. */ return TRUE; while (*text) if ((matched = DoMatch(text++, p)) != FALSE) return matched; return ABORT; case '[': reverse = p[1] == NEGATE_CLASS ? TRUE : FALSE; if (reverse) /* Inverted character class. */ p++; matched = FALSE; if (p[1] == ']' || p[1] == '-') if (*++p == *text) matched = TRUE; for (last = *p; *++p && *p != ']'; last = *p) /* This next line requires a good C compiler. */ if (*p == '-' && p[1] != ']' ? *text <= *++p && *text >= last : *text == *p) matched = TRUE; if (matched == reverse) return FALSE; continue; } } #ifdef MATCH_TAR_PATTERN if (*text == '/') return TRUE; #endif /* MATCH_TAR_ATTERN */ return *text == '\0'; } /* ** User-level routine. Returns TRUE or FALSE. */ EXPORTED int wildmat(const char *text, const char *p) { #ifdef OPTIMIZE_JUST_STAR if (p[0] == '*' && p[1] == '\0') return TRUE; #endif /* OPTIMIZE_JUST_STAR */ return DoMatch(text, p) == TRUE; } #if defined(TEST) /* Yes, we use gets not fgets. Sue me. */ extern char *gets(); int main() { char p[80]; char text[80]; printf("Wildmat tester. Enter pattern, then strings to test.\n"); printf("A blank line gets prompts for a new pattern; a blank pattern\n"); printf("exits the program.\n"); for ( ; ; ) { printf("\nEnter pattern: "); (void)fflush(stdout); if (gets(p) == NULL || p[0] == '\0') break; for ( ; ; ) { printf("Enter text: "); (void)fflush(stdout); if (gets(text) == NULL) exit(0); if (text[0] == '\0') /* Blank line; go back and get a new pattern. */ break; printf(" %s\n", wildmat(text, p) ? "YES" : "NO"); } } exit(0); /* NOTREACHED */ } #endif /* defined(TEST) */ EXPORTED struct wildmat *split_wildmats(char *str, const char *prefix) { char pattern[1024] = "", *p, *c; struct wildmat *wild = NULL; int n = 0; if (prefix) snprintf(pattern, sizeof(pattern), "%s.", prefix); p = pattern + strlen(pattern); /* * split the list of wildmats * * we split them right to left because this is the order in which * we want to test them (per RFC3977 section 4.2) */ do { if ((c = strrchr(str, ','))) *c++ = '\0'; else c = str; if (!(n % 10)) /* alloc some more */ wild = xrealloc(wild, (n + 11) * sizeof(struct wildmat)); if (*c == '!') wild[n].not = 1; /* not */ else if (*c == '@') wild[n].not = -1; /* absolute not (feeding) */ else wild[n].not = 0; strncpy(p, wild[n].not ? c + 1 : c, pattern+sizeof(pattern) - p); pattern[sizeof(pattern)-1] = '\0'; wild[n++].pat = xstrdup(pattern); } while (c != str); wild[n].pat = NULL; return wild; } EXPORTED void free_wildmats(struct wildmat *wild) { struct wildmat *w = wild; while (w->pat) { free(w->pat); w++; } free(wild); } cyrus-imapd-2.5.10/lib/mappedfile.h0000644000175000017500000000663713001236020014001 00000000000000/* mappedfile - interface to a mmaped, lockable, writable file * * Copyright (c) 1994-2011 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #ifndef _MAPPEDFILE_H #define _MAPPEDFILE_H // includes #include "util.h" #include #include struct mappedfile; #define MAPPEDFILE_CREATE (1<<0) #define MAPPEDFILE_RW (1<<1) extern int mappedfile_open(struct mappedfile **mfp, const char *fname, int flags); extern int mappedfile_close(struct mappedfile **mfp); extern int mappedfile_readlock(struct mappedfile *mf); extern int mappedfile_writelock(struct mappedfile *mf); extern int mappedfile_unlock(struct mappedfile *mf); extern int mappedfile_commit(struct mappedfile *mf); extern ssize_t mappedfile_pwrite(struct mappedfile *mf, const char *base, size_t len, off_t offset); extern ssize_t mappedfile_pwritebuf(struct mappedfile *mf, const struct buf *buf, off_t offset); extern ssize_t mappedfile_pwritev(struct mappedfile *mf, const struct iovec *iov, int nio, off_t offset); extern int mappedfile_truncate(struct mappedfile *mf, off_t offset); extern int mappedfile_rename(struct mappedfile *mf, const char *newname); extern int mappedfile_islocked(const struct mappedfile *mf); extern int mappedfile_isreadlocked(const struct mappedfile *mf); extern int mappedfile_iswritelocked(const struct mappedfile *mf); extern int mappedfile_iswritable(const struct mappedfile *mf); extern const char *mappedfile_base(const struct mappedfile *mf); extern size_t mappedfile_size(const struct mappedfile *mf); extern const struct buf *mappedfile_buf(const struct mappedfile *mf); extern const char *mappedfile_fname(const struct mappedfile *mf); #endif /* _MAPPEDFILE_H */ cyrus-imapd-2.5.10/lib/mpool.c0000644000175000017500000001143113001236020013000 00000000000000/* mpool.c memory pool management * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include #ifdef HAVE_UNISTD_H #include #endif #include #include #include #include #include "mpool.h" #include "xmalloc.h" #include "exitcodes.h" struct mpool { struct mpool_blob *blob; }; struct mpool_blob { size_t size; unsigned char *base; /* Base of allocated section */ unsigned char *ptr; /* End of allocated section */ struct mpool_blob *next; /* Next Pool */ }; static struct mpool_blob *new_mpool_blob(size_t size) { struct mpool_blob *blob = xmalloc(sizeof(struct mpool_blob)); if(!size) size = DEFAULT_MPOOL_SIZE; blob->base = blob->ptr = xmalloc(size); blob->size = size; blob->next = NULL; return blob; } /* Create a new pool */ EXPORTED struct mpool *new_mpool(size_t size) { struct mpool *ret = xmalloc(sizeof(struct mpool)); ret->blob = new_mpool_blob(size); return ret; } /* Free a pool */ EXPORTED void free_mpool(struct mpool *pool) { struct mpool_blob *p, *p_next; if (!pool) return; if (!pool->blob) { fatal("memory pool without a blob", EC_TEMPFAIL); return; } p = pool->blob; while(p) { p_next = p->next; free(p->base); free(p); p = p_next; } free(pool); } #ifdef ROUNDUP #undef ROUNDUP #endif /* round up to the next multiple of 16 bytes if necessary */ /* 0xFF...FFF0 = ~0 ^ 0xF */ #define ROUNDUP(num) (((num) + 15) & (~((unsigned long) 0x0) ^ 0xF)) /* Allocate from a pool */ EXPORTED void *mpool_malloc(struct mpool *pool, size_t size) { void *ret = NULL; struct mpool_blob *p; size_t remain; if(!pool || !pool->blob) { fatal("mpool_malloc called without a valid pool", EC_TEMPFAIL); } if(!size) { /* This is legal under ANSI C, so we should allow it too */ size = 1; } p = pool->blob; /* This is a bit tricky, not only do we have to make sure that the current * pool has enough room, we need to be sure that we haven't rounded p->ptr * outside of the current pool anyway */ remain = p->size - ((char *)p->ptr - (char *)p->base); if (remain < size || (char *) p->ptr > (p->size + (char *) p->base)) { /* Need a new pool */ struct mpool_blob *new_pool; size_t new_pool_size = 2 * ((size > p->size) ? size : p->size); new_pool = new_mpool_blob(new_pool_size); new_pool->next = p; p = pool->blob = new_pool; } ret = p->ptr; /* make sure that the next thing we allocate is align on a ROUNDUP boundary */ p->ptr = p->base + ROUNDUP(p->ptr - p->base + size); return ret; } EXPORTED char *mpool_strndup(struct mpool *pool, const char *str, size_t n) { char *ret; if(!str) return NULL; ret = mpool_malloc(pool, n+1); strncpy(ret, str, n); ret[n] = '\0'; return ret; } EXPORTED char *mpool_strdup(struct mpool *pool, const char *str) { size_t len; if(!str) return NULL; len = strlen(str); return mpool_strndup(pool, str, len); } cyrus-imapd-2.5.10/lib/tok.h0000644000175000017500000000570413001236020012462 00000000000000/* tok.h -- utility for string tokenisation * * Copyright (c) 2011 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. * * Author: Greg Banks * Based on his tok_t class from ggcov.sf.net */ #ifndef __CYRUS_TOK_H__ #define __CYRUS_TOK_H__ #include #include #include "xmalloc.h" typedef struct { char *buf; char *state; const char *sep; char *curr; #define _TOK_FIRST (1<<0) #define TOK_TRIMLEFT (1<<1) /* trim whitespace from start of tokens */ #define TOK_TRIMRIGHT (1<<2) /* trim whitespace from end of tokens */ #define TOK_EMPTY (1<<3) /* return empty "" tokens if adjacent * delimiter characters are present */ #define TOK_FREEBUFFER (1<<4) /* tok_t should free() the buffer when done */ unsigned int flags; } tok_t; #define TOK_INITIALIZER(str, sep, flags) \ { xstrdup((str)), NULL, (sep), NULL, (flags)|_TOK_FIRST|TOK_FREEBUFFER } void tok_init(tok_t *, const char *buf, const char *sep, int flags); void tok_initm(tok_t *, char *buf, const char *sep, int flags); void tok_fini(tok_t *); /* advance to the next token and return it */ char *tok_next(tok_t *); /* return offset into the buffer of the current token, for error messages */ unsigned int tok_offset(const tok_t *); #endif /* __CYRUS_TOK_H__ */ cyrus-imapd-2.5.10/lib/getnameinfo.c0000644000175000017500000000716013001236020014152 00000000000000/* * Mar 8, 2000 by Hajimu UMEMOTO * * This module is besed on ssh-1.2.27-IPv6-1.5 written by * KIKUCHI Takahiro */ /* * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ /* * fake library for ssh * * This file includes getnameinfo(). * These funtions are defined in rfc2133. * * But these functions are not implemented correctly. The minimum subset * is implemented for ssh use only. For exapmle, this routine assumes * that ai_family is AF_INET. Don't use it for another purpose. * * In the case not using 'configure --enable-ipv6', this getnameinfo.c * will be used if you have broken getnameinfo or no getnameinfo. */ #include "config.h" #include #include #include int getnameinfo(const struct sockaddr *sa, socklen_t salen __attribute__((unused)), char *host, size_t hostlen, char *serv, size_t servlen, int flags) { struct sockaddr_in *sin = (struct sockaddr_in *)sa; struct hostent *hp; char tmpserv[16]; if (serv) { snprintf(tmpserv, sizeof(tmpserv), "%d", ntohs(sin->sin_port)); if (strlen(tmpserv) > servlen) return EAI_MEMORY; else strcpy(serv, tmpserv); } if (host) { if (flags & NI_NUMERICHOST) { if (flags & NI_NAMEREQD) return EAI_NONAME; if (strlen(inet_ntoa(sin->sin_addr)) >= hostlen) return EAI_MEMORY; else { strcpy(host, inet_ntoa(sin->sin_addr)); return 0; } } else { hp = gethostbyaddr((char *)&sin->sin_addr, sizeof(struct in_addr), AF_INET); if (hp) if (strlen(hp->h_name) >= hostlen) return EAI_MEMORY; else { strcpy(host, hp->h_name); return 0; } else if (flags & NI_NAMEREQD) return EAI_NONAME; else if (strlen(inet_ntoa(sin->sin_addr)) >= hostlen) return EAI_MEMORY; else { strcpy(host, inet_ntoa(sin->sin_addr)); return 0; } } } return 0; } cyrus-imapd-2.5.10/lib/exitcodes.h0000644000175000017500000000760513001236020013656 00000000000000/* exitcodes.h -- wrapper around sysextis.h * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ /* Sendmail has some weird ideas on what constitutes permenant failure. On more than one occasion, we have gotten burned by this moving users around through various inadvisable means, screwing up the mailboxes file, whatever. We don't want to fail out permenantly on things like EX_USAGE, EX_SOFTWARE, etc., because that generally means someone was just screwing with the mail store and we don't want to lose mail. Instead, we map these EC_* codes to EX_* codes, thereby lying to Sendmail, since we don't derive any benefit from Sendmail knowing what the error was. We just want it to retry all the time anyway. This way, should sendmail's behavior be different and we start deriving benefit from Sendmail knowing stuff, we can easily change it back. So other code uses the EC_* error, then we maybe change it to TEMPFAIL if we don't agree on whether the error should be permenant or not. Comments below stolen from sysexits.h. */ #ifndef INCLUDED_EXITCODES_H #define INCLUDED_EXITCODES_H #include #define EC_OK 0 /* successful termination */ #define EC_USAGE EX_TEMPFAIL /* command line usage error */ #define EC_DATAERR EX_DATAERR /* data format error */ #define EC_NOINPUT EX_TEMPFAIL /* cannot open input */ #define EC_NOUSER EX_NOUSER /* addressee unknown */ #define EC_NOHOST EX_TEMPFAIL /* host name unknown */ #define EC_UNAVAILABLE EX_TEMPFAIL /* service unavailable */ #define EC_SOFTWARE EX_TEMPFAIL /* internal software error */ #define EC_OSERR EX_TEMPFAIL /* system error (e.g., can't fork) */ #define EC_OSFILE EX_TEMPFAIL /* critical OS file missing */ #define EC_CANTCREAT EX_TEMPFAIL /* can't create (user) output file */ #define EC_IOERR EX_TEMPFAIL /* input/output error */ #define EC_TEMPFAIL EX_TEMPFAIL /* user is invited to retry */ #define EC_PROTOCOL EX_TEMPFAIL /* remote error in protocol */ #define EC_NOPERM EX_NOPERM /* permission denied */ #define EC_CONFIG EX_TEMPFAIL /* configuration error */ #endif /* INCLUDED_EXITCODES_H */ cyrus-imapd-2.5.10/lib/charset/0000755000175000017500000000000013001246664013236 500000000000000cyrus-imapd-2.5.10/lib/charset/iso-8859-8.t0000644000175000017500000002012213001236020014673 00000000000000# # Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. # # Redistribution and use in source and binary forms, with or without # modification, are permitted provided that the following conditions # are met: # # 1. Redistributions of source code must retain the above copyright # notice, this list of conditions and the following disclaimer. # # 2. Redistributions in binary form must reproduce the above copyright # notice, this list of conditions and the following disclaimer in # the documentation and/or other materials provided with the # distribution. # # 3. The name "Carnegie Mellon University" must not be used to # endorse or promote products derived from this software without # prior written permission. For permission or any legal # details, please contact # Carnegie Mellon University # Center for Technology Transfer and Enterprise Creation # 4615 Forbes Avenue # Suite 302 # Pittsburgh, PA 15213 # (412) 268-7393, fax: (412) 268-7395 # innovation@andrew.cmu.edu # # 4. Redistributions of any form whatsoever must retain the following # acknowledgment: # "This product includes software developed by Computing Services # at Carnegie Mellon University (http://www.cmu.edu/computing/)." # # CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO # THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY # AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE # FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES # WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN # AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING # OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. 0 0000 NULL (NUL) 1 0001 START OF HEADING (SOH) 2 0002 START OF TEXT (STX) 3 0003 END OF TEXT (ETX) 4 0004 END OF TRANSMISSION (EOT) 5 0005 ENQUIRY (ENQ) 6 0006 ACKNOWLEDGE (ACK) 7 0007 BELL (BEL) 8 0008 BACKSPACE (BS) 9 0009 CHARACTER TABULATION (HT) A 000a LINE FEED (LF) B 000b LINE TABULATION (VT) C 000c FORM FEED (FF) D 000d CARRIAGE RETURN (CR) E 000e SHIFT OUT (SO) F 000f SHIFT IN (SI) 10 0010 DATALINK ESCAPE (DLE) 11 0011 DEVICE CONTROL ONE (DC1) 12 0012 DEVICE CONTROL TWO (DC2) 13 0013 DEVICE CONTROL THREE (DC3) 14 0014 DEVICE CONTROL FOUR (DC4) 15 0015 NEGATIVE ACKNOWLEDGE (NAK) 16 0016 SYNCRONOUS IDLE (SYN) 17 0017 END OF TRANSMISSION BLOCK (ETB) 18 0018 CANCEL (CAN) 19 0019 END OF MEDIUM (EM) 1A 001a SUBSTITUTE (SUB) 1B 001b ESCAPE (ESC) 1C 001c FILE SEPARATOR (IS4) 1D 001d GROUP SEPARATOR (IS3) 1E 001e RECORD SEPARATOR (IS2) 1F 001f UNIT SEPARATOR (IS1) 20 0020 SPACE 21 0021 EXCLAMATION MARK 22 0022 QUOTATION MARK 23 0023 NUMBER SIGN 24 0024 DOLLAR SIGN 25 0025 PERCENT SIGN 26 0026 AMPERSAND 27 0027 APOSTROPHE 28 0028 LEFT PARENTHESIS 29 0029 RIGHT PARENTHESIS 2A 002a ASTERISK 2B 002b PLUS SIGN 2C 002c COMMA 2D 002d HYPHEN-MINUS 2E 002e FULL STOP 2F 002f SOLIDUS 30 0030 DIGIT ZERO 31 0031 DIGIT ONE 32 0032 DIGIT TWO 33 0033 DIGIT THREE 34 0034 DIGIT FOUR 35 0035 DIGIT FIVE 36 0036 DIGIT SIX 37 0037 DIGIT SEVEN 38 0038 DIGIT EIGHT 39 0039 DIGIT NINE 3A 003a COLON 3B 003b SEMICOLON 3C 003c LESS-THAN SIGN 3D 003d EQUALS SIGN 3E 003e GREATER-THAN SIGN 3F 003f QUESTION MARK 40 0040 COMMERCIAL AT 41 0041 LATIN CAPITAL LETTER A 42 0042 LATIN CAPITAL LETTER B 43 0043 LATIN CAPITAL LETTER C 44 0044 LATIN CAPITAL LETTER D 45 0045 LATIN CAPITAL LETTER E 46 0046 LATIN CAPITAL LETTER F 47 0047 LATIN CAPITAL LETTER G 48 0048 LATIN CAPITAL LETTER H 49 0049 LATIN CAPITAL LETTER I 4A 004a LATIN CAPITAL LETTER J 4B 004b LATIN CAPITAL LETTER K 4C 004c LATIN CAPITAL LETTER L 4D 004d LATIN CAPITAL LETTER M 4E 004e LATIN CAPITAL LETTER N 4F 004f LATIN CAPITAL LETTER O 50 0050 LATIN CAPITAL LETTER P 51 0051 LATIN CAPITAL LETTER Q 52 0052 LATIN CAPITAL LETTER R 53 0053 LATIN CAPITAL LETTER S 54 0054 LATIN CAPITAL LETTER T 55 0055 LATIN CAPITAL LETTER U 56 0056 LATIN CAPITAL LETTER V 57 0057 LATIN CAPITAL LETTER W 58 0058 LATIN CAPITAL LETTER X 59 0059 LATIN CAPITAL LETTER Y 5A 005a LATIN CAPITAL LETTER Z 5B 005b LEFT SQUARE BRACKET 5C 005c REVERSE SOLIDUS 5D 005d RIGHT SQUARE BRACKET 5E 005e CIRCUMFLEX ACCENT 5F 005f LOW LINE 60 0060 GRAVE ACCENT 61 0061 LATIN SMALL LETTER A 62 0062 LATIN SMALL LETTER B 63 0063 LATIN SMALL LETTER C 64 0064 LATIN SMALL LETTER D 65 0065 LATIN SMALL LETTER E 66 0066 LATIN SMALL LETTER F 67 0067 LATIN SMALL LETTER G 68 0068 LATIN SMALL LETTER H 69 0069 LATIN SMALL LETTER I 6A 006a LATIN SMALL LETTER J 6B 006b LATIN SMALL LETTER K 6C 006c LATIN SMALL LETTER L 6D 006d LATIN SMALL LETTER M 6E 006e LATIN SMALL LETTER N 6F 006f LATIN SMALL LETTER O 70 0070 LATIN SMALL LETTER P 71 0071 LATIN SMALL LETTER Q 72 0072 LATIN SMALL LETTER R 73 0073 LATIN SMALL LETTER S 74 0074 LATIN SMALL LETTER T 75 0075 LATIN SMALL LETTER U 76 0076 LATIN SMALL LETTER V 77 0077 LATIN SMALL LETTER W 78 0078 LATIN SMALL LETTER X 79 0079 LATIN SMALL LETTER Y 7A 007a LATIN SMALL LETTER Z 7B 007b LEFT CURLY BRACKET 7C 007c VERTICAL LINE 7D 007d RIGHT CURLY BRACKET 7E 007e TILDE 7F 007f DELETE (DEL) 80 0080 PADDING CHARACTER (PAD) 81 0081 HIGH OCTET PRESET (HOP) 82 0082 BREAK PERMITTED HERE (BPH) 83 0083 NO BREAK HERE (NBH) 84 0084 INDEX (IND) 85 0085 NEXT LINE (NEL) 86 0086 START OF SELECTED AREA (SSA) 87 0087 END OF SELECTED AREA (ESA) 88 0088 CHARACTER TABULATION SET (HTS) 89 0089 CHARACTER TABULATION WITH JUSTIFICATION (HTJ) 8A 008a LINE TABULATION SET (VTS) 8B 008b PARTIAL LINE FORWARD (PLD) 8C 008c PARTIAL LINE BACKWARD (PLU) 8D 008d REVERSE LINE FEED (RI) 8E 008e SINGLE-SHIFT TWO (SS2) 8F 008f SINGLE-SHIFT THREE (SS3) 90 0090 DEVICE CONTROL STRING (DCS) 91 0091 PRIVATE USE ONE (PU1) 92 0092 PRIVATE USE TWO (PU2) 93 0093 SET TRANSMIT STATE (STS) 94 0094 CANCEL CHARACTER (CCH) 95 0095 MESSAGE WAITING (MW) 96 0096 START OF GUARDED AREA (SPA) 97 0097 END OF GUARDED AREA (EPA) 98 0098 START OF STRING (SOS) 99 0099 SINGLE GRAPHIC CHARACTER INTRODUCER (SGCI) 9A 009a SINGLE CHARACTER INTRODUCER (SCI) 9B 009b CONTROL SEQUENCE INTRODUCER (CSI) 9C 009c STRING TERMINATOR (ST) 9D 009d OPERATING SYSTEM COMMAND (OSC) 9E 009e PRIVACY MESSAGE (PM) 9F 009f APPLICATION PROGRAM COMMAND (APC) A0 00a0 NO-BREAK SPACE A1 ???? EMPTY A2 00a2 CENT SIGN A3 00a3 POUND SIGN A4 00a4 CURRENCY SIGN A5 00a5 YEN SIGN A6 00a6 BROKEN BAR A7 00a7 SECTION SIGN A8 00a8 DIAERESIS A9 00a9 COPYRIGHT SIGN AA 00d7 MULTIPLICATION SIGN AB 00ab LEFT-POINTING DOUBLE ANGLE QUOTATION MARK AC 00ac NOT SIGN AD 00ad SOFT HYPHEN AE 00ae REGISTERED SIGN AF 203e OVERLINE B0 00b0 DEGREE SIGN B1 00b1 PLUS-MINUS SIGN B2 00b2 SUPERSCRIPT TWO B3 00b3 SUPERSCRIPT THREE B4 00b4 ACUTE ACCENT B5 00b5 MICRO SIGN B6 00b6 PILCROW SIGN B7 00b7 MIDDLE DOT B8 00b8 CEDILLA B9 00b9 SUPERSCRIPT ONE BA 00f7 DIVISION SIGN BB 00bb RIGHT-POINTING DOUBLE ANGLE QUOTATION MARK BC 00bc VULGAR FRACTION ONE QUARTER BD 00bd VULGAR FRACTION ONE HALF BE 00be VULGAR FRACTION THREE QUARTERS BF ???? EMPTY C0 ???? EMPTY C1 ???? EMPTY C2 ???? EMPTY C3 ???? EMPTY C4 ???? EMPTY C5 ???? EMPTY C6 ???? EMPTY C7 ???? EMPTY C8 ???? EMPTY C9 ???? EMPTY CA ???? EMPTY CB ???? EMPTY CC ???? EMPTY CD ???? EMPTY CE ???? EMPTY CF ???? EMPTY D0 ???? EMPTY D1 ???? EMPTY D2 ???? EMPTY D3 ???? EMPTY D4 ???? EMPTY D5 ???? EMPTY D6 ???? EMPTY D7 ???? EMPTY D8 ???? EMPTY D9 ???? EMPTY DA ???? EMPTY DB ???? EMPTY DC ???? EMPTY DD ???? EMPTY DE ???? EMPTY DF 2017 DOUBLE LOW LINE E0 05d0 HEBREW LETTER ALEF E1 05d1 HEBREW LETTER BET E2 05d2 HEBREW LETTER GIMEL E3 05d3 HEBREW LETTER DALET E4 05d4 HEBREW LETTER HE E5 05d5 HEBREW LETTER VAV E6 05d6 HEBREW LETTER ZAYIN E7 05d7 HEBREW LETTER HET E8 05d8 HEBREW LETTER TET E9 05d9 HEBREW LETTER YOD EA 05da HEBREW LETTER FINAL KAF EB 05db HEBREW LETTER KAF EC 05dc HEBREW LETTER LAMED ED 05dd HEBREW LETTER FINAL MEM EE 05de HEBREW LETTER MEM EF 05df HEBREW LETTER FINAL NUN F0 05e0 HEBREW LETTER NUN F1 05e1 HEBREW LETTER SAMEKH F2 05e2 HEBREW LETTER AYIN F3 05e3 HEBREW LETTER FINAL PE F4 05e4 HEBREW LETTER PE F5 05e5 HEBREW LETTER FINAL TSADI F6 05e6 HEBREW LETTER TSADI F7 05e7 HEBREW LETTER QOF F8 05e8 HEBREW LETTER RESH F9 05e9 HEBREW LETTER SHIN FA 05ea HEBREW LETTER TAV FB ???? EMPTY FC ???? EMPTY FD ???? EMPTY FE ???? EMPTY FF ???? EMPTY cyrus-imapd-2.5.10/lib/charset/windows-1256.t0000644000175000017500000002117513001236020015417 00000000000000# # Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. # # Redistribution and use in source and binary forms, with or without # modification, are permitted provided that the following conditions # are met: # # 1. Redistributions of source code must retain the above copyright # notice, this list of conditions and the following disclaimer. # # 2. Redistributions in binary form must reproduce the above copyright # notice, this list of conditions and the following disclaimer in # the documentation and/or other materials provided with the # distribution. # # 3. The name "Carnegie Mellon University" must not be used to # endorse or promote products derived from this software without # prior written permission. For permission or any legal # details, please contact # Carnegie Mellon University # Center for Technology Transfer and Enterprise Creation # 4615 Forbes Avenue # Suite 302 # Pittsburgh, PA 15213 # (412) 268-7393, fax: (412) 268-7395 # innovation@andrew.cmu.edu # # 4. Redistributions of any form whatsoever must retain the following # acknowledgment: # "This product includes software developed by Computing Services # at Carnegie Mellon University (http://www.cmu.edu/computing/)." # # CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO # THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY # AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE # FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES # WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN # AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING # OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. # # Charset put together by Rayed Alrashed # Reference: # ftp://ftp.unicode.org/Public/MAPPINGS/VENDORS/MICSFT/WINDOWS/CP1256.TXT 00 0000 NULL 01 0001 START OF HEADING 02 0002 START OF TEXT 03 0003 END OF TEXT 04 0004 END OF TRANSMISSION 05 0005 ENQUIRY 06 0006 ACKNOWLEDGE 07 0007 BELL 08 0008 BACKSPACE 09 0009 HORIZONTAL TABULATION 0A 000A LINE FEED 0B 000B VERTICAL TABULATION 0C 000C FORM FEED 0D 000D CARRIAGE RETURN 0E 000E SHIFT OUT 0F 000F SHIFT IN 10 0010 DATA LINK ESCAPE 11 0011 DEVICE CONTROL ONE 12 0012 DEVICE CONTROL TWO 13 0013 DEVICE CONTROL THREE 14 0014 DEVICE CONTROL FOUR 15 0015 NEGATIVE ACKNOWLEDGE 16 0016 SYNCHRONOUS IDLE 17 0017 END OF TRANSMISSION BLOCK 18 0018 CANCEL 19 0019 END OF MEDIUM 1A 001A SUBSTITUTE 1B 001B ESCAPE 1C 001C FILE SEPARATOR 1D 001D GROUP SEPARATOR 1E 001E RECORD SEPARATOR 1F 001F UNIT SEPARATOR 20 0020 SPACE 21 0021 EXCLAMATION MARK 22 0022 QUOTATION MARK 23 0023 NUMBER SIGN 24 0024 DOLLAR SIGN 25 0025 PERCENT SIGN 26 0026 AMPERSAND 27 0027 APOSTROPHE 28 0028 LEFT PARENTHESIS 29 0029 RIGHT PARENTHESIS 2A 002A ASTERISK 2B 002B PLUS SIGN 2C 002C COMMA 2D 002D HYPHEN-MINUS 2E 002E FULL STOP 2F 002F SOLIDUS 30 0030 DIGIT ZERO 31 0031 DIGIT ONE 32 0032 DIGIT TWO 33 0033 DIGIT THREE 34 0034 DIGIT FOUR 35 0035 DIGIT FIVE 36 0036 DIGIT SIX 37 0037 DIGIT SEVEN 38 0038 DIGIT EIGHT 39 0039 DIGIT NINE 3A 003A COLON 3B 003B SEMICOLON 3C 003C LESS-THAN SIGN 3D 003D EQUALS SIGN 3E 003E GREATER-THAN SIGN 3F 003F QUESTION MARK 40 0040 COMMERCIAL AT 41 0041 LATIN CAPITAL LETTER A 42 0042 LATIN CAPITAL LETTER B 43 0043 LATIN CAPITAL LETTER C 44 0044 LATIN CAPITAL LETTER D 45 0045 LATIN CAPITAL LETTER E 46 0046 LATIN CAPITAL LETTER F 47 0047 LATIN CAPITAL LETTER G 48 0048 LATIN CAPITAL LETTER H 49 0049 LATIN CAPITAL LETTER I 4A 004A LATIN CAPITAL LETTER J 4B 004B LATIN CAPITAL LETTER K 4C 004C LATIN CAPITAL LETTER L 4D 004D LATIN CAPITAL LETTER M 4E 004E LATIN CAPITAL LETTER N 4F 004F LATIN CAPITAL LETTER O 50 0050 LATIN CAPITAL LETTER P 51 0051 LATIN CAPITAL LETTER Q 52 0052 LATIN CAPITAL LETTER R 53 0053 LATIN CAPITAL LETTER S 54 0054 LATIN CAPITAL LETTER T 55 0055 LATIN CAPITAL LETTER U 56 0056 LATIN CAPITAL LETTER V 57 0057 LATIN CAPITAL LETTER W 58 0058 LATIN CAPITAL LETTER X 59 0059 LATIN CAPITAL LETTER Y 5A 005A LATIN CAPITAL LETTER Z 5B 005B LEFT SQUARE BRACKET 5C 005C REVERSE SOLIDUS 5D 005D RIGHT SQUARE BRACKET 5E 005E CIRCUMFLEX ACCENT 5F 005F LOW LINE 60 0060 GRAVE ACCENT 61 0061 LATIN SMALL LETTER A 62 0062 LATIN SMALL LETTER B 63 0063 LATIN SMALL LETTER C 64 0064 LATIN SMALL LETTER D 65 0065 LATIN SMALL LETTER E 66 0066 LATIN SMALL LETTER F 67 0067 LATIN SMALL LETTER G 68 0068 LATIN SMALL LETTER H 69 0069 LATIN SMALL LETTER I 6A 006A LATIN SMALL LETTER J 6B 006B LATIN SMALL LETTER K 6C 006C LATIN SMALL LETTER L 6D 006D LATIN SMALL LETTER M 6E 006E LATIN SMALL LETTER N 6F 006F LATIN SMALL LETTER O 70 0070 LATIN SMALL LETTER P 71 0071 LATIN SMALL LETTER Q 72 0072 LATIN SMALL LETTER R 73 0073 LATIN SMALL LETTER S 74 0074 LATIN SMALL LETTER T 75 0075 LATIN SMALL LETTER U 76 0076 LATIN SMALL LETTER V 77 0077 LATIN SMALL LETTER W 78 0078 LATIN SMALL LETTER X 79 0079 LATIN SMALL LETTER Y 7A 007A LATIN SMALL LETTER Z 7B 007B LEFT CURLY BRACKET 7C 007C VERTICAL LINE 7D 007D RIGHT CURLY BRACKET 7E 007E TILDE 7F 007F DELETE 80 20AC EURO SIGN 81 067E ARABIC LETTER PEH 82 201A SINGLE LOW- 9QUOTATION MARK 83 0192 LATIN SMALL LETTER F WITH HOOK 84 201E DOUBLE LOW- 9QUOTATION MARK 85 2026 HORIZONTAL ELLIPSIS 86 2020 DAGGER 87 2021 DOUBLE DAGGER 88 02C6 MODIFIER LETTER CIRCUMFLEX ACCENT 89 2030 PER MILLE SIGN 8A 0679 ARABIC LETTER TTEH 8B 2039 SINGLE LEFT-POINTING ANGLE QUOTATION MARK 8C 0152 LATIN CAPITAL LIGATURE OE 8D 0686 ARABIC LETTER TCHEH 8E 0698 ARABIC LETTER JEH 8F 0688 ARABIC LETTER DDAL 90 06AF ARABIC LETTER GAF 91 2018 LEFT SINGLE QUOTATION MARK 92 2019 RIGHT SINGLE QUOTATION MARK 93 201C LEFT DOUBLE QUOTATION MARK 94 201D RIGHT DOUBLE QUOTATION MARK 95 2022 BULLET 96 2013 EN DASH 97 2014 EM DASH 98 06A9 ARABIC LETTER KEHEH 99 2122 TRADE MARK SIGN 9A 0691 ARABIC LETTER RREH 9B 203A SINGLE RIGHT-POINTING ANGLE QUOTATION MARK 9C 0153 LATIN SMALL LIGATURE OE 9D 200C ZERO WIDTH NON-JOINER 9E 200D ZERO WIDTH JOINER 9F 06BA ARABIC LETTER NOON GHUNNA A0 00A0 NO-BREAK SPACE A1 060C ARABIC COMMA A2 00A2 CENT SIGN A3 00A3 POUND SIGN A4 00A4 CURRENCY SIGN A5 00A5 YEN SIGN A6 00A6 BROKEN BAR A7 00A7 SECTION SIGN A8 00A8 DIAERESIS A9 00A9 COPYRIGHT SIGN AA 06BE ARABIC LETTER HEH DOACHASHMEE AB 00AB LEFT-POINTING DOUBLE ANGLE QUOTATION MARK AC 00AC NOT SIGN AD 00AD SOFT HYPHEN AE 00AE REGISTERED SIGN AF 00AF MACRON B0 00B0 DEGREE SIGN B1 00B1 PLUS-MINUS SIGN B2 00B2 SUPERSCRIPT TWO B3 00B3 SUPERSCRIPT THREE B4 00B4 ACUTE ACCENT B5 00B5 MICRO SIGN B6 00B6 PILCROW SIGN B7 00B7 MIDDLE DOT B8 00B8 CEDILLA B9 00B9 SUPERSCRIPT ONE BA 061B ARABIC SEMICOLON BB 00BB RIGHT-POINTING DOUBLE ANGLE QUOTATION MARK BC 00BC VULGAR FRACTION ONE QUARTER BD 00BD VULGAR FRACTION ONE HALF BE 00BE VULGAR FRACTION THREE QUARTERS BF 061F ARABIC QUESTION MARK C0 06C1 ARABIC LETTER HEH GOAL C1 0621 ARABIC LETTER HAMZA C2 0622 ARABIC LETTER ALEF WITH MADDA ABOVE C3 0623 ARABIC LETTER ALEF WITH HAMZA ABOVE C4 0624 ARABIC LETTER WAW WITH HAMZA ABOVE C5 0625 ARABIC LETTER ALEF WITH HAMZA BELOW C6 0626 ARABIC LETTER YEH WITH HAMZA ABOVE C7 0627 ARABIC LETTER ALEF C8 0628 ARABIC LETTER BEH C9 0629 ARABIC LETTER TEH MARBUTA CA 062A ARABIC LETTER TEH CB 062B ARABIC LETTER THEH CC 062C ARABIC LETTER JEEM CD 062D ARABIC LETTER HAH CE 062E ARABIC LETTER KHAH CF 062F ARABIC LETTER DAL D0 0630 ARABIC LETTER THAL D1 0631 ARABIC LETTER REH D2 0632 ARABIC LETTER ZAIN D3 0633 ARABIC LETTER SEEN D4 0634 ARABIC LETTER SHEEN D5 0635 ARABIC LETTER SAD D6 0636 ARABIC LETTER DAD D7 00D7 MULTIPLICATION SIGN D8 0637 ARABIC LETTER TAH D9 0638 ARABIC LETTER ZAH DA 0639 ARABIC LETTER AIN DB 063A ARABIC LETTER GHAIN DC 0640 ARABIC TATWEEL DD 0641 ARABIC LETTER FEH DE 0642 ARABIC LETTER QAF DF 0643 ARABIC LETTER KAF E0 00E0 LATIN SMALL LETTER A WITH GRAVE E1 0644 ARABIC LETTER LAM E2 00E2 LATIN SMALL LETTER A WITH CIRCUMFLEX E3 0645 ARABIC LETTER MEEM E4 0646 ARABIC LETTER NOON E5 0647 ARABIC LETTER HEH E6 0648 ARABIC LETTER WAW E7 00E7 LATIN SMALL LETTER C WITH CEDILLA E8 00E8 LATIN SMALL LETTER E WITH GRAVE E9 00E9 LATIN SMALL LETTER E WITH ACUTE EA 00EA LATIN SMALL LETTER E WITH CIRCUMFLEX EB 00EB LATIN SMALL LETTER E WITH DIAERESIS EC 0649 ARABIC LETTER ALEF MAKSURA ED 064A ARABIC LETTER YEH EE 00EE LATIN SMALL LETTER I WITH CIRCUMFLEX EF 00EF LATIN SMALL LETTER I WITH DIAERESIS F0 064B ARABIC FATHATAN F1 064C ARABIC DAMMATAN F2 064D ARABIC KASRATAN F3 064E ARABIC FATHA F4 00F4 LATIN SMALL LETTER O WITH CIRCUMFLEX F5 064F ARABIC DAMMA F6 0650 ARABIC KASRA F7 00F7 DIVISION SIGN F8 0651 ARABIC SHADDA F9 00F9 LATIN SMALL LETTER U WITH GRAVE FA 0652 ARABIC SUKUN FB 00FB LATIN SMALL LETTER U WITH CIRCUMFLEX FC 00FC LATIN SMALL LETTER U WITH DIAERESIS FD 200E LEFT-TO-RIGHT MARK FE 200F RIGHT-TO-LEFT MARK FF 06D2 ARABIC LETTER YEH BARREE cyrus-imapd-2.5.10/lib/charset/iso-8859-9.t0000644000175000017500000002301713001236020014702 00000000000000# # Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. # # Redistribution and use in source and binary forms, with or without # modification, are permitted provided that the following conditions # are met: # # 1. Redistributions of source code must retain the above copyright # notice, this list of conditions and the following disclaimer. # # 2. Redistributions in binary form must reproduce the above copyright # notice, this list of conditions and the following disclaimer in # the documentation and/or other materials provided with the # distribution. # # 3. The name "Carnegie Mellon University" must not be used to # endorse or promote products derived from this software without # prior written permission. For permission or any legal # details, please contact # Carnegie Mellon University # Center for Technology Transfer and Enterprise Creation # 4615 Forbes Avenue # Suite 302 # Pittsburgh, PA 15213 # (412) 268-7393, fax: (412) 268-7395 # innovation@andrew.cmu.edu # # 4. Redistributions of any form whatsoever must retain the following # acknowledgment: # "This product includes software developed by Computing Services # at Carnegie Mellon University (http://www.cmu.edu/computing/)." # # CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO # THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY # AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE # FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES # WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN # AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING # OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. 0 0000 NULL (NUL) 1 0001 START OF HEADING (SOH) 2 0002 START OF TEXT (STX) 3 0003 END OF TEXT (ETX) 4 0004 END OF TRANSMISSION (EOT) 5 0005 ENQUIRY (ENQ) 6 0006 ACKNOWLEDGE (ACK) 7 0007 BELL (BEL) 8 0008 BACKSPACE (BS) 9 0009 CHARACTER TABULATION (HT) A 000a LINE FEED (LF) B 000b LINE TABULATION (VT) C 000c FORM FEED (FF) D 000d CARRIAGE RETURN (CR) E 000e SHIFT OUT (SO) F 000f SHIFT IN (SI) 10 0010 DATALINK ESCAPE (DLE) 11 0011 DEVICE CONTROL ONE (DC1) 12 0012 DEVICE CONTROL TWO (DC2) 13 0013 DEVICE CONTROL THREE (DC3) 14 0014 DEVICE CONTROL FOUR (DC4) 15 0015 NEGATIVE ACKNOWLEDGE (NAK) 16 0016 SYNCRONOUS IDLE (SYN) 17 0017 END OF TRANSMISSION BLOCK (ETB) 18 0018 CANCEL (CAN) 19 0019 END OF MEDIUM (EM) 1A 001a SUBSTITUTE (SUB) 1B 001b ESCAPE (ESC) 1C 001c FILE SEPARATOR (IS4) 1D 001d GROUP SEPARATOR (IS3) 1E 001e RECORD SEPARATOR (IS2) 1F 001f UNIT SEPARATOR (IS1) 20 0020 SPACE 21 0021 EXCLAMATION MARK 22 0022 QUOTATION MARK 23 0023 NUMBER SIGN 24 0024 DOLLAR SIGN 25 0025 PERCENT SIGN 26 0026 AMPERSAND 27 0027 APOSTROPHE 28 0028 LEFT PARENTHESIS 29 0029 RIGHT PARENTHESIS 2A 002a ASTERISK 2B 002b PLUS SIGN 2C 002c COMMA 2D 002d HYPHEN-MINUS 2E 002e FULL STOP 2F 002f SOLIDUS 30 0030 DIGIT ZERO 31 0031 DIGIT ONE 32 0032 DIGIT TWO 33 0033 DIGIT THREE 34 0034 DIGIT FOUR 35 0035 DIGIT FIVE 36 0036 DIGIT SIX 37 0037 DIGIT SEVEN 38 0038 DIGIT EIGHT 39 0039 DIGIT NINE 3A 003a COLON 3B 003b SEMICOLON 3C 003c LESS-THAN SIGN 3D 003d EQUALS SIGN 3E 003e GREATER-THAN SIGN 3F 003f QUESTION MARK 40 0040 COMMERCIAL AT 41 0041 LATIN CAPITAL LETTER A 42 0042 LATIN CAPITAL LETTER B 43 0043 LATIN CAPITAL LETTER C 44 0044 LATIN CAPITAL LETTER D 45 0045 LATIN CAPITAL LETTER E 46 0046 LATIN CAPITAL LETTER F 47 0047 LATIN CAPITAL LETTER G 48 0048 LATIN CAPITAL LETTER H 49 0049 LATIN CAPITAL LETTER I 4A 004a LATIN CAPITAL LETTER J 4B 004b LATIN CAPITAL LETTER K 4C 004c LATIN CAPITAL LETTER L 4D 004d LATIN CAPITAL LETTER M 4E 004e LATIN CAPITAL LETTER N 4F 004f LATIN CAPITAL LETTER O 50 0050 LATIN CAPITAL LETTER P 51 0051 LATIN CAPITAL LETTER Q 52 0052 LATIN CAPITAL LETTER R 53 0053 LATIN CAPITAL LETTER S 54 0054 LATIN CAPITAL LETTER T 55 0055 LATIN CAPITAL LETTER U 56 0056 LATIN CAPITAL LETTER V 57 0057 LATIN CAPITAL LETTER W 58 0058 LATIN CAPITAL LETTER X 59 0059 LATIN CAPITAL LETTER Y 5A 005a LATIN CAPITAL LETTER Z 5B 005b LEFT SQUARE BRACKET 5C 005c REVERSE SOLIDUS 5D 005d RIGHT SQUARE BRACKET 5E 005e CIRCUMFLEX ACCENT 5F 005f LOW LINE 60 0060 GRAVE ACCENT 61 0061 LATIN SMALL LETTER A 62 0062 LATIN SMALL LETTER B 63 0063 LATIN SMALL LETTER C 64 0064 LATIN SMALL LETTER D 65 0065 LATIN SMALL LETTER E 66 0066 LATIN SMALL LETTER F 67 0067 LATIN SMALL LETTER G 68 0068 LATIN SMALL LETTER H 69 0069 LATIN SMALL LETTER I 6A 006a LATIN SMALL LETTER J 6B 006b LATIN SMALL LETTER K 6C 006c LATIN SMALL LETTER L 6D 006d LATIN SMALL LETTER M 6E 006e LATIN SMALL LETTER N 6F 006f LATIN SMALL LETTER O 70 0070 LATIN SMALL LETTER P 71 0071 LATIN SMALL LETTER Q 72 0072 LATIN SMALL LETTER R 73 0073 LATIN SMALL LETTER S 74 0074 LATIN SMALL LETTER T 75 0075 LATIN SMALL LETTER U 76 0076 LATIN SMALL LETTER V 77 0077 LATIN SMALL LETTER W 78 0078 LATIN SMALL LETTER X 79 0079 LATIN SMALL LETTER Y 7A 007a LATIN SMALL LETTER Z 7B 007b LEFT CURLY BRACKET 7C 007c VERTICAL LINE 7D 007d RIGHT CURLY BRACKET 7E 007e TILDE 7F 007f DELETE (DEL) 80 0080 PADDING CHARACTER (PAD) 81 0081 HIGH OCTET PRESET (HOP) 82 0082 BREAK PERMITTED HERE (BPH) 83 0083 NO BREAK HERE (NBH) 84 0084 INDEX (IND) 85 0085 NEXT LINE (NEL) 86 0086 START OF SELECTED AREA (SSA) 87 0087 END OF SELECTED AREA (ESA) 88 0088 CHARACTER TABULATION SET (HTS) 89 0089 CHARACTER TABULATION WITH JUSTIFICATION (HTJ) 8A 008a LINE TABULATION SET (VTS) 8B 008b PARTIAL LINE FORWARD (PLD) 8C 008c PARTIAL LINE BACKWARD (PLU) 8D 008d REVERSE LINE FEED (RI) 8E 008e SINGLE-SHIFT TWO (SS2) 8F 008f SINGLE-SHIFT THREE (SS3) 90 0090 DEVICE CONTROL STRING (DCS) 91 0091 PRIVATE USE ONE (PU1) 92 0092 PRIVATE USE TWO (PU2) 93 0093 SET TRANSMIT STATE (STS) 94 0094 CANCEL CHARACTER (CCH) 95 0095 MESSAGE WAITING (MW) 96 0096 START OF GUARDED AREA (SPA) 97 0097 END OF GUARDED AREA (EPA) 98 0098 START OF STRING (SOS) 99 0099 SINGLE GRAPHIC CHARACTER INTRODUCER (SGCI) 9A 009a SINGLE CHARACTER INTRODUCER (SCI) 9B 009b CONTROL SEQUENCE INTRODUCER (CSI) 9C 009c STRING TERMINATOR (ST) 9D 009d OPERATING SYSTEM COMMAND (OSC) 9E 009e PRIVACY MESSAGE (PM) 9F 009f APPLICATION PROGRAM COMMAND (APC) A0 00a0 NO-BREAK SPACE A1 00a1 INVERTED EXCLAMATION MARK A2 00a2 CENT SIGN A3 00a3 POUND SIGN A4 00a4 CURRENCY SIGN A5 00a5 YEN SIGN A6 00a6 BROKEN BAR A7 00a7 SECTION SIGN A8 00a8 DIAERESIS A9 00a9 COPYRIGHT SIGN AA 00aa FEMININE ORDINAL INDICATOR AB 00ab LEFT-POINTING DOUBLE ANGLE QUOTATION MARK AC 00ac NOT SIGN AD 00ad SOFT HYPHEN AE 00ae REGISTERED SIGN AF 00af MACRON B0 00b0 DEGREE SIGN B1 00b1 PLUS-MINUS SIGN B2 00b2 SUPERSCRIPT TWO B3 00b3 SUPERSCRIPT THREE B4 00b4 ACUTE ACCENT B5 00b5 MICRO SIGN B6 00b6 PILCROW SIGN B7 00b7 MIDDLE DOT B8 00b8 CEDILLA B9 00b9 SUPERSCRIPT ONE BA 00ba MASCULINE ORDINAL INDICATOR BB 00bb RIGHT-POINTING DOUBLE ANGLE QUOTATION MARK BC 00bc VULGAR FRACTION ONE QUARTER BD 00bd VULGAR FRACTION ONE HALF BE 00be VULGAR FRACTION THREE QUARTERS BF 00bf INVERTED QUESTION MARK C0 00c0 LATIN CAPITAL LETTER A WITH GRAVE C1 00c1 LATIN CAPITAL LETTER A WITH ACUTE C2 00c2 LATIN CAPITAL LETTER A WITH CIRCUMFLEX C3 00c3 LATIN CAPITAL LETTER A WITH TILDE C4 00c4 LATIN CAPITAL LETTER A WITH DIAERESIS C5 00c5 LATIN CAPITAL LETTER A WITH RING ABOVE C6 00c6 LATIN CAPITAL LETTER AE C7 00c7 LATIN CAPITAL LETTER C WITH CEDILLA C8 00c8 LATIN CAPITAL LETTER E WITH GRAVE C9 00c9 LATIN CAPITAL LETTER E WITH ACUTE CA 00ca LATIN CAPITAL LETTER E WITH CIRCUMFLEX CB 00cb LATIN CAPITAL LETTER E WITH DIAERESIS CC 00cc LATIN CAPITAL LETTER I WITH GRAVE CD 00cd LATIN CAPITAL LETTER I WITH ACUTE CE 00ce LATIN CAPITAL LETTER I WITH CIRCUMFLEX CF 00cf LATIN CAPITAL LETTER I WITH DIAERESIS D0 011e LATIN CAPITAL LETTER G WITH BREVE D1 00d1 LATIN CAPITAL LETTER N WITH TILDE D2 00d2 LATIN CAPITAL LETTER O WITH GRAVE D3 00d3 LATIN CAPITAL LETTER O WITH ACUTE D4 00d4 LATIN CAPITAL LETTER O WITH CIRCUMFLEX D5 00d5 LATIN CAPITAL LETTER O WITH TILDE D6 00d6 LATIN CAPITAL LETTER O WITH DIAERESIS D7 00d7 MULTIPLICATION SIGN D8 00d8 LATIN CAPITAL LETTER O WITH STROKE D9 00d9 LATIN CAPITAL LETTER U WITH GRAVE DA 00da LATIN CAPITAL LETTER U WITH ACUTE DB 00db LATIN CAPITAL LETTER U WITH CIRCUMFLEX DC 00dc LATIN CAPITAL LETTER U WITH DIAERESIS DD 0130 LATIN CAPITAL LETTER I WITH DOT ABOVE DE 015e LATIN CAPITAL LETTER S WITH CEDILLA DF 00df LATIN SMALL LETTER SHARP S (German) E0 00e0 LATIN SMALL LETTER A WITH GRAVE E1 00e1 LATIN SMALL LETTER A WITH ACUTE E2 00e2 LATIN SMALL LETTER A WITH CIRCUMFLEX E3 00e3 LATIN SMALL LETTER A WITH TILDE E4 00e4 LATIN SMALL LETTER A WITH DIAERESIS E5 00e5 LATIN SMALL LETTER A WITH RING ABOVE E6 00e6 LATIN SMALL LETTER AE E7 00e7 LATIN SMALL LETTER C WITH CEDILLA E8 00e8 LATIN SMALL LETTER E WITH GRAVE E9 00e9 LATIN SMALL LETTER E WITH ACUTE EA 00ea LATIN SMALL LETTER E WITH CIRCUMFLEX EB 00eb LATIN SMALL LETTER E WITH DIAERESIS EC 00ec LATIN SMALL LETTER I WITH GRAVE ED 00ed LATIN SMALL LETTER I WITH ACUTE EE 00ee LATIN SMALL LETTER I WITH CIRCUMFLEX EF 00ef LATIN SMALL LETTER I WITH DIAERESIS F0 011f LATIN SMALL LETTER G WITH BREVE F1 00f1 LATIN SMALL LETTER N WITH TILDE F2 00f2 LATIN SMALL LETTER O WITH GRAVE F3 00f3 LATIN SMALL LETTER O WITH ACUTE F4 00f4 LATIN SMALL LETTER O WITH CIRCUMFLEX F5 00f5 LATIN SMALL LETTER O WITH TILDE F6 00f6 LATIN SMALL LETTER O WITH DIAERESIS F7 00f7 DIVISION SIGN F8 00f8 LATIN SMALL LETTER O WITH STROKE F9 00f9 LATIN SMALL LETTER U WITH GRAVE FA 00fa LATIN SMALL LETTER U WITH ACUTE FB 00fb LATIN SMALL LETTER U WITH CIRCUMFLEX FC 00fc LATIN SMALL LETTER U WITH DIAERESIS FD 0131 LATIN SMALL LETTER I DOTLESS FE 015f LATIN SMALL LETTER S WITH CEDILLA FF 00ff LATIN SMALL LETTER Y WITH DIAERESIS cyrus-imapd-2.5.10/lib/charset/iso-8859-2.t0000644000175000017500000002340713001236020014676 00000000000000# # Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. # # Redistribution and use in source and binary forms, with or without # modification, are permitted provided that the following conditions # are met: # # 1. Redistributions of source code must retain the above copyright # notice, this list of conditions and the following disclaimer. # # 2. Redistributions in binary form must reproduce the above copyright # notice, this list of conditions and the following disclaimer in # the documentation and/or other materials provided with the # distribution. # # 3. The name "Carnegie Mellon University" must not be used to # endorse or promote products derived from this software without # prior written permission. For permission or any legal # details, please contact # Carnegie Mellon University # Center for Technology Transfer and Enterprise Creation # 4615 Forbes Avenue # Suite 302 # Pittsburgh, PA 15213 # (412) 268-7393, fax: (412) 268-7395 # innovation@andrew.cmu.edu # # 4. Redistributions of any form whatsoever must retain the following # acknowledgment: # "This product includes software developed by Computing Services # at Carnegie Mellon University (http://www.cmu.edu/computing/)." # # CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO # THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY # AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE # FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES # WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN # AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING # OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. 0 0000 NULL (NUL) 1 0001 START OF HEADING (SOH) 2 0002 START OF TEXT (STX) 3 0003 END OF TEXT (ETX) 4 0004 END OF TRANSMISSION (EOT) 5 0005 ENQUIRY (ENQ) 6 0006 ACKNOWLEDGE (ACK) 7 0007 BELL (BEL) 8 0008 BACKSPACE (BS) 9 0009 CHARACTER TABULATION (HT) A 000a LINE FEED (LF) B 000b LINE TABULATION (VT) C 000c FORM FEED (FF) D 000d CARRIAGE RETURN (CR) E 000e SHIFT OUT (SO) F 000f SHIFT IN (SI) 10 0010 DATALINK ESCAPE (DLE) 11 0011 DEVICE CONTROL ONE (DC1) 12 0012 DEVICE CONTROL TWO (DC2) 13 0013 DEVICE CONTROL THREE (DC3) 14 0014 DEVICE CONTROL FOUR (DC4) 15 0015 NEGATIVE ACKNOWLEDGE (NAK) 16 0016 SYNCRONOUS IDLE (SYN) 17 0017 END OF TRANSMISSION BLOCK (ETB) 18 0018 CANCEL (CAN) 19 0019 END OF MEDIUM (EM) 1A 001a SUBSTITUTE (SUB) 1B 001b ESCAPE (ESC) 1C 001c FILE SEPARATOR (IS4) 1D 001d GROUP SEPARATOR (IS3) 1E 001e RECORD SEPARATOR (IS2) 1F 001f UNIT SEPARATOR (IS1) 20 0020 SPACE 21 0021 EXCLAMATION MARK 22 0022 QUOTATION MARK 23 0023 NUMBER SIGN 24 0024 DOLLAR SIGN 25 0025 PERCENT SIGN 26 0026 AMPERSAND 27 0027 APOSTROPHE 28 0028 LEFT PARENTHESIS 29 0029 RIGHT PARENTHESIS 2A 002a ASTERISK 2B 002b PLUS SIGN 2C 002c COMMA 2D 002d HYPHEN-MINUS 2E 002e FULL STOP 2F 002f SOLIDUS 30 0030 DIGIT ZERO 31 0031 DIGIT ONE 32 0032 DIGIT TWO 33 0033 DIGIT THREE 34 0034 DIGIT FOUR 35 0035 DIGIT FIVE 36 0036 DIGIT SIX 37 0037 DIGIT SEVEN 38 0038 DIGIT EIGHT 39 0039 DIGIT NINE 3A 003a COLON 3B 003b SEMICOLON 3C 003c LESS-THAN SIGN 3D 003d EQUALS SIGN 3E 003e GREATER-THAN SIGN 3F 003f QUESTION MARK 40 0040 COMMERCIAL AT 41 0041 LATIN CAPITAL LETTER A 42 0042 LATIN CAPITAL LETTER B 43 0043 LATIN CAPITAL LETTER C 44 0044 LATIN CAPITAL LETTER D 45 0045 LATIN CAPITAL LETTER E 46 0046 LATIN CAPITAL LETTER F 47 0047 LATIN CAPITAL LETTER G 48 0048 LATIN CAPITAL LETTER H 49 0049 LATIN CAPITAL LETTER I 4A 004a LATIN CAPITAL LETTER J 4B 004b LATIN CAPITAL LETTER K 4C 004c LATIN CAPITAL LETTER L 4D 004d LATIN CAPITAL LETTER M 4E 004e LATIN CAPITAL LETTER N 4F 004f LATIN CAPITAL LETTER O 50 0050 LATIN CAPITAL LETTER P 51 0051 LATIN CAPITAL LETTER Q 52 0052 LATIN CAPITAL LETTER R 53 0053 LATIN CAPITAL LETTER S 54 0054 LATIN CAPITAL LETTER T 55 0055 LATIN CAPITAL LETTER U 56 0056 LATIN CAPITAL LETTER V 57 0057 LATIN CAPITAL LETTER W 58 0058 LATIN CAPITAL LETTER X 59 0059 LATIN CAPITAL LETTER Y 5A 005a LATIN CAPITAL LETTER Z 5B 005b LEFT SQUARE BRACKET 5C 005c REVERSE SOLIDUS 5D 005d RIGHT SQUARE BRACKET 5E 005e CIRCUMFLEX ACCENT 5F 005f LOW LINE 60 0060 GRAVE ACCENT 61 0061 LATIN SMALL LETTER A 62 0062 LATIN SMALL LETTER B 63 0063 LATIN SMALL LETTER C 64 0064 LATIN SMALL LETTER D 65 0065 LATIN SMALL LETTER E 66 0066 LATIN SMALL LETTER F 67 0067 LATIN SMALL LETTER G 68 0068 LATIN SMALL LETTER H 69 0069 LATIN SMALL LETTER I 6A 006a LATIN SMALL LETTER J 6B 006b LATIN SMALL LETTER K 6C 006c LATIN SMALL LETTER L 6D 006d LATIN SMALL LETTER M 6E 006e LATIN SMALL LETTER N 6F 006f LATIN SMALL LETTER O 70 0070 LATIN SMALL LETTER P 71 0071 LATIN SMALL LETTER Q 72 0072 LATIN SMALL LETTER R 73 0073 LATIN SMALL LETTER S 74 0074 LATIN SMALL LETTER T 75 0075 LATIN SMALL LETTER U 76 0076 LATIN SMALL LETTER V 77 0077 LATIN SMALL LETTER W 78 0078 LATIN SMALL LETTER X 79 0079 LATIN SMALL LETTER Y 7A 007a LATIN SMALL LETTER Z 7B 007b LEFT CURLY BRACKET 7C 007c VERTICAL LINE 7D 007d RIGHT CURLY BRACKET 7E 007e TILDE 7F 007f DELETE (DEL) 80 0080 PADDING CHARACTER (PAD) 81 0081 HIGH OCTET PRESET (HOP) 82 0082 BREAK PERMITTED HERE (BPH) 83 0083 NO BREAK HERE (NBH) 84 0084 INDEX (IND) 85 0085 NEXT LINE (NEL) 86 0086 START OF SELECTED AREA (SSA) 87 0087 END OF SELECTED AREA (ESA) 88 0088 CHARACTER TABULATION SET (HTS) 89 0089 CHARACTER TABULATION WITH JUSTIFICATION (HTJ) 8A 008a LINE TABULATION SET (VTS) 8B 008b PARTIAL LINE FORWARD (PLD) 8C 008c PARTIAL LINE BACKWARD (PLU) 8D 008d REVERSE LINE FEED (RI) 8E 008e SINGLE-SHIFT TWO (SS2) 8F 008f SINGLE-SHIFT THREE (SS3) 90 0090 DEVICE CONTROL STRING (DCS) 91 0091 PRIVATE USE ONE (PU1) 92 0092 PRIVATE USE TWO (PU2) 93 0093 SET TRANSMIT STATE (STS) 94 0094 CANCEL CHARACTER (CCH) 95 0095 MESSAGE WAITING (MW) 96 0096 START OF GUARDED AREA (SPA) 97 0097 END OF GUARDED AREA (EPA) 98 0098 START OF STRING (SOS) 99 0099 SINGLE GRAPHIC CHARACTER INTRODUCER (SGCI) 9A 009a SINGLE CHARACTER INTRODUCER (SCI) 9B 009b CONTROL SEQUENCE INTRODUCER (CSI) 9C 009c STRING TERMINATOR (ST) 9D 009d OPERATING SYSTEM COMMAND (OSC) 9E 009e PRIVACY MESSAGE (PM) 9F 009f APPLICATION PROGRAM COMMAND (APC) A0 00a0 NO-BREAK SPACE A1 0104 LATIN CAPITAL LETTER A WITH OGONEK A2 02d8 BREVE A3 0141 LATIN CAPITAL LETTER L WITH STROKE A4 00a4 CURRENCY SIGN A5 013d LATIN CAPITAL LETTER L WITH CARON A6 015a LATIN CAPITAL LETTER S WITH ACUTE A7 00a7 SECTION SIGN A8 00a8 DIAERESIS A9 0160 LATIN CAPITAL LETTER S WITH CARON AA 015e LATIN CAPITAL LETTER S WITH CEDILLA AB 0164 LATIN CAPITAL LETTER T WITH CARON AC 0179 LATIN CAPITAL LETTER Z WITH ACUTE AD 00ad SOFT HYPHEN AE 017d LATIN CAPITAL LETTER Z WITH CARON AF 017b LATIN CAPITAL LETTER Z WITH DOT ABOVE B0 00b0 DEGREE SIGN B1 0105 LATIN SMALL LETTER A WITH OGONEK B2 02db OGONEK B3 0142 LATIN SMALL LETTER L WITH STROKE B4 00b4 ACUTE ACCENT B5 013e LATIN SMALL LETTER L WITH CARON B6 015b LATIN SMALL LETTER S WITH ACUTE B7 02c7 CARON B8 00b8 CEDILLA B9 0161 LATIN SMALL LETTER S WITH CARON BA 015f LATIN SMALL LETTER S WITH CEDILLA BB 0165 LATIN SMALL LETTER T WITH CARON BC 017a LATIN SMALL LETTER Z WITH ACUTE BD 02dd DOUBLE ACUTE ACCENT BE 017e LATIN SMALL LETTER Z WITH CARON BF 017c LATIN SMALL LETTER Z WITH DOT ABOVE C0 0154 LATIN CAPITAL LETTER R WITH ACUTE C1 00c1 LATIN CAPITAL LETTER A WITH ACUTE C2 00c2 LATIN CAPITAL LETTER A WITH CIRCUMFLEX C3 0102 LATIN CAPITAL LETTER A WITH BREVE C4 00c4 LATIN CAPITAL LETTER A WITH DIAERESIS C5 0139 LATIN CAPITAL LETTER L WITH ACUTE C6 0106 LATIN CAPITAL LETTER C WITH ACUTE C7 00c7 LATIN CAPITAL LETTER C WITH CEDILLA C8 010c LATIN CAPITAL LETTER C WITH CARON C9 00c9 LATIN CAPITAL LETTER E WITH ACUTE CA 0118 LATIN CAPITAL LETTER E WITH OGONEK CB 00cb LATIN CAPITAL LETTER E WITH DIAERESIS CC 011a LATIN CAPITAL LETTER E WITH CARON CD 00cd LATIN CAPITAL LETTER I WITH ACUTE CE 00ce LATIN CAPITAL LETTER I WITH CIRCUMFLEX CF 010e LATIN CAPITAL LETTER D WITH CARON D0 0110 LATIN CAPITAL LETTER D WITH STROKE D1 0143 LATIN CAPITAL LETTER N WITH ACUTE D2 0147 LATIN CAPITAL LETTER N WITH CARON D3 00d3 LATIN CAPITAL LETTER O WITH ACUTE D4 00d4 LATIN CAPITAL LETTER O WITH CIRCUMFLEX D5 0150 LATIN CAPITAL LETTER O WITH DOUBLE ACUTE D6 00d6 LATIN CAPITAL LETTER O WITH DIAERESIS D7 00d7 MULTIPLICATION SIGN D8 0158 LATIN CAPITAL LETTER R WITH CARON D9 016e LATIN CAPITAL LETTER U WITH RING ABOVE DA 00da LATIN CAPITAL LETTER U WITH ACUTE DB 0170 LATIN CAPITAL LETTER U WITH DOUBLE ACUTE DC 00dc LATIN CAPITAL LETTER U WITH DIAERESIS DD 00dd LATIN CAPITAL LETTER Y WITH ACUTE DE 0162 LATIN CAPITAL LETTER T WITH CEDILLA DF 00df LATIN SMALL LETTER SHARP S (German) E0 0155 LATIN SMALL LETTER R WITH ACUTE E1 00e1 LATIN SMALL LETTER A WITH ACUTE E2 00e2 LATIN SMALL LETTER A WITH CIRCUMFLEX E3 0103 LATIN SMALL LETTER A WITH BREVE E4 00e4 LATIN SMALL LETTER A WITH DIAERESIS E5 013a LATIN SMALL LETTER L WITH ACUTE E6 0107 LATIN SMALL LETTER C WITH ACUTE E7 00e7 LATIN SMALL LETTER C WITH CEDILLA E8 010d LATIN SMALL LETTER C WITH CARON E9 00e9 LATIN SMALL LETTER E WITH ACUTE EA 0119 LATIN SMALL LETTER E WITH OGONEK EB 00eb LATIN SMALL LETTER E WITH DIAERESIS EC 011b LATIN SMALL LETTER E WITH CARON ED 00ed LATIN SMALL LETTER I WITH ACUTE EE 00ee LATIN SMALL LETTER I WITH CIRCUMFLEX EF 010f LATIN SMALL LETTER D WITH CARON F0 0111 LATIN SMALL LETTER D WITH STROKE F1 0144 LATIN SMALL LETTER N WITH ACUTE F2 0148 LATIN SMALL LETTER N WITH CARON F3 00f3 LATIN SMALL LETTER O WITH ACUTE F4 00f4 LATIN SMALL LETTER O WITH CIRCUMFLEX F5 0151 LATIN SMALL LETTER O WITH DOUBLE ACUTE F6 00f6 LATIN SMALL LETTER O WITH DIAERESIS F7 00f7 DIVISION SIGN F8 0159 LATIN SMALL LETTER R WITH CARON F9 016f LATIN SMALL LETTER U WITH RING ABOVE FA 00fa LATIN SMALL LETTER U WITH ACUTE FB 0171 LATIN SMALL LETTER U WITH DOUBLE ACUTE FC 00fc LATIN SMALL LETTER U WITH DIAERESIS FD 00fd LATIN SMALL LETTER Y WITH ACUTE FE 0163 LATIN SMALL LETTER T WITH CEDILLA FF 02d9 DOT ABOVE cyrus-imapd-2.5.10/lib/charset/windows-1255.t0000644000175000017500000002005513001236020015412 00000000000000# # Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. # # Redistribution and use in source and binary forms, with or without # modification, are permitted provided that the following conditions # are met: # # 1. Redistributions of source code must retain the above copyright # notice, this list of conditions and the following disclaimer. # # 2. Redistributions in binary form must reproduce the above copyright # notice, this list of conditions and the following disclaimer in # the documentation and/or other materials provided with the # distribution. # # 3. The name "Carnegie Mellon University" must not be used to # endorse or promote products derived from this software without # prior written permission. For permission or any legal # details, please contact # Carnegie Mellon University # Center for Technology Transfer and Enterprise Creation # 4615 Forbes Avenue # Suite 302 # Pittsburgh, PA 15213 # (412) 268-7393, fax: (412) 268-7395 # innovation@andrew.cmu.edu # # 4. Redistributions of any form whatsoever must retain the following # acknowledgment: # "This product includes software developed by Computing Services # at Carnegie Mellon University (http://www.cmu.edu/computing/)." # # CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO # THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY # AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE # FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES # WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN # AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING # OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. # # Charset put together by Ewald Dieterich # Reference: http://www.microsoft.com/globaldev/reference/sbcs/1252.htm 0 0000 NULL (NUL) 1 0001 START OF HEADING (SOH) 2 0002 START OF TEXT (STX) 3 0003 END OF TEXT (ETX) 4 0004 END OF TRANSMISSION (EOT) 5 0005 ENQUIRY (ENQ) 6 0006 ACKNOWLEDGE (ACK) 7 0007 BELL (BEL) 8 0008 BACKSPACE (BS) 9 0009 CHARACTER TABULATION (HT) A 000a LINE FEED (LF) B 000b LINE TABULATION (VT) C 000c FORM FEED (FF) D 000d CARRIAGE RETURN (CR) E 000e SHIFT OUT (SO) F 000f SHIFT IN (SI) 10 0010 DATALINK ESCAPE (DLE) 11 0011 DEVICE CONTROL ONE (DC1) 12 0012 DEVICE CONTROL TWO (DC2) 13 0013 DEVICE CONTROL THREE (DC3) 14 0014 DEVICE CONTROL FOUR (DC4) 15 0015 NEGATIVE ACKNOWLEDGE (NAK) 16 0016 SYNCRONOUS IDLE (SYN) 17 0017 END OF TRANSMISSION BLOCK (ETB) 18 0018 CANCEL (CAN) 19 0019 END OF MEDIUM (EM) 1A 001a SUBSTITUTE (SUB) 1B 001b ESCAPE (ESC) 1C 001c FILE SEPARATOR (IS4) 1D 001d GROUP SEPARATOR (IS3) 1E 001e RECORD SEPARATOR (IS2) 1F 001f UNIT SEPARATOR (IS1) 20 0020 SPACE 21 0021 EXCLAMATION MARK 22 0022 QUOTATION MARK 23 0023 NUMBER SIGN 24 0024 DOLLAR SIGN 25 0025 PERCENT SIGN 26 0026 AMPERSAND 27 0027 APOSTROPHE 28 0028 LEFT PARENTHESIS 29 0029 RIGHT PARENTHESIS 2A 002a ASTERISK 2B 002b PLUS SIGN 2C 002c COMMA 2D 002d HYPHEN-MINUS 2E 002e FULL STOP 2F 002f SOLIDUS 30 0030 DIGIT ZERO 31 0031 DIGIT ONE 32 0032 DIGIT TWO 33 0033 DIGIT THREE 34 0034 DIGIT FOUR 35 0035 DIGIT FIVE 36 0036 DIGIT SIX 37 0037 DIGIT SEVEN 38 0038 DIGIT EIGHT 39 0039 DIGIT NINE 3A 003a COLON 3B 003b SEMICOLON 3C 003c LESS-THAN SIGN 3D 003d EQUALS SIGN 3E 003e GREATER-THAN SIGN 3F 003f QUESTION MARK 40 0040 COMMERCIAL AT 41 0041 LATIN CAPITAL LETTER A 42 0042 LATIN CAPITAL LETTER B 43 0043 LATIN CAPITAL LETTER C 44 0044 LATIN CAPITAL LETTER D 45 0045 LATIN CAPITAL LETTER E 46 0046 LATIN CAPITAL LETTER F 47 0047 LATIN CAPITAL LETTER G 48 0048 LATIN CAPITAL LETTER H 49 0049 LATIN CAPITAL LETTER I 4A 004a LATIN CAPITAL LETTER J 4B 004b LATIN CAPITAL LETTER K 4C 004c LATIN CAPITAL LETTER L 4D 004d LATIN CAPITAL LETTER M 4E 004e LATIN CAPITAL LETTER N 4F 004f LATIN CAPITAL LETTER O 50 0050 LATIN CAPITAL LETTER P 51 0051 LATIN CAPITAL LETTER Q 52 0052 LATIN CAPITAL LETTER R 53 0053 LATIN CAPITAL LETTER S 54 0054 LATIN CAPITAL LETTER T 55 0055 LATIN CAPITAL LETTER U 56 0056 LATIN CAPITAL LETTER V 57 0057 LATIN CAPITAL LETTER W 58 0058 LATIN CAPITAL LETTER X 59 0059 LATIN CAPITAL LETTER Y 5A 005a LATIN CAPITAL LETTER Z 5B 005b LEFT SQUARE BRACKET 5C 005c REVERSE SOLIDUS 5D 005d RIGHT SQUARE BRACKET 5E 005e CIRCUMFLEX ACCENT 5F 005f LOW LINE 60 0060 GRAVE ACCENT 61 0061 LATIN SMALL LETTER A 62 0062 LATIN SMALL LETTER B 63 0063 LATIN SMALL LETTER C 64 0064 LATIN SMALL LETTER D 65 0065 LATIN SMALL LETTER E 66 0066 LATIN SMALL LETTER F 67 0067 LATIN SMALL LETTER G 68 0068 LATIN SMALL LETTER H 69 0069 LATIN SMALL LETTER I 6A 006a LATIN SMALL LETTER J 6B 006b LATIN SMALL LETTER K 6C 006c LATIN SMALL LETTER L 6D 006d LATIN SMALL LETTER M 6E 006e LATIN SMALL LETTER N 6F 006f LATIN SMALL LETTER O 70 0070 LATIN SMALL LETTER P 71 0071 LATIN SMALL LETTER Q 72 0072 LATIN SMALL LETTER R 73 0073 LATIN SMALL LETTER S 74 0074 LATIN SMALL LETTER T 75 0075 LATIN SMALL LETTER U 76 0076 LATIN SMALL LETTER V 77 0077 LATIN SMALL LETTER W 78 0078 LATIN SMALL LETTER X 79 0079 LATIN SMALL LETTER Y 7A 007a LATIN SMALL LETTER Z 7B 007b LEFT CURLY BRACKET 7C 007c VERTICAL LINE 7D 007d RIGHT CURLY BRACKET 7E 007e TILDE 7F 007f DELETE (DEL) 80 20AC EURO SIGN 82 201A SINGLE LOW-9 QUOTATION MARK 83 0192 LATIN SMALL LETTER F WITH HOOK 84 201E DOUBLE LOW-9 QUOTATION MARK 85 2026 HORIZONTAL ELLIPSIS 86 2020 DAGGER 87 2021 DOUBLE DAGGER 88 02C6 MODIFIER LETTER CIRCUMFLEX ACCENT 89 2030 PER MILLE SIGN 8B 2039 SINGLE LEFT-POINTING ANGLE QUOTATION MARK 91 2018 LEFT SINGLE QUOTATION MARK 92 2019 RIGHT SINGLE QUOTATION MARK 93 201C LEFT DOUBLE QUOTATION MARK 94 201D RIGHT DOUBLE QUOTATION MARK 95 2022 BULLET 96 2013 EN DASH 97 2014 EM DASH 98 02DC SMALL TILDE 99 2122 TRADE MARK SIGN 9B 203A SINGLE RIGHT-POINTING ANGLE QUOTATION MARK A0 00A0 NO-BREAK SPACE A1 00A1 INVERTED EXCLAMATION MARK A2 00A2 CENT SIGN A3 00A3 POUND SIGN A4 20AA NEW SHEQEL SIGN A5 00A5 YEN SIGN A6 00A6 BROKEN BAR A7 00A7 SECTION SIGN A8 00A8 DIAERESIS A9 00A9 COPYRIGHT SIGN AA 00D7 MULTIPLICATION SIGN AB 00AB LEFT-POINTING DOUBLE ANGLE QUOTATION MARK AC 00AC NOT SIGN AD 00AD SOFT HYPHEN AE 00AE REGISTERED SIGN AF 00AF MACRON B0 00B0 DEGREE SIGN B1 00B1 PLUS-MINUS SIGN B2 00B2 SUPERSCRIPT TWO B3 00B3 SUPERSCRIPT THREE B4 00B4 ACUTE ACCENT B5 00B5 MICRO SIGN B6 00B6 PILCROW SIGN B7 00B7 MIDDLE DOT B8 00B8 CEDILLA B9 00B9 SUPERSCRIPT ONE BA 00F7 DIVISION SIGN BB 00BB RIGHT-POINTING DOUBLE ANGLE QUOTATION MARK BC 00BC VULGAR FRACTION ONE QUARTER BD 00BD VULGAR FRACTION ONE HALF BE 00BE VULGAR FRACTION THREE QUARTERS BF 00BF INVERTED QUESTION MARK C0 05B0 HEBREW POINT SHEVA C1 05B1 HEBREW POINT HATAF SEGOL C2 05B2 HEBREW POINT HATAF PATAH C3 05B3 HEBREW POINT HATAF QAMATS C4 05B4 HEBREW POINT HIRIQ C5 05B5 HEBREW POINT TSERE C6 05B6 HEBREW POINT SEGOL C7 05B7 HEBREW POINT PATAH C8 05B8 HEBREW POINT QAMATS C9 05B9 HEBREW POINT HOLAM CB 05BB HEBREW POINT QUBUTS CC 05BC HEBREW POINT DAGESH OR MAPIQ CD 05BD HEBREW POINT METEG CE 05BE HEBREW PUNCTUATION MAQAF CF 05BF HEBREW POINT RAFE D0 05C0 HEBREW PUNCTUATION PASEQ D1 05C1 HEBREW POINT SHIN DOT D2 05C2 HEBREW POINT SIN DOT D3 05C3 HEBREW PUNCTUATION SOF PASUQ D4 05F0 HEBREW LIGATURE YIDDISH DOUBLE VAV D5 05F1 HEBREW LIGATURE YIDDISH VAV YOD D6 05F2 HEBREW LIGATURE YIDDISH DOUBLE YOD D7 05F3 HEBREW PUNCTUATION GERESH D8 05F4 HEBREW PUNCTUATION GERSHAYIM E0 05D0 HEBREW LETTER ALEF E1 05D1 HEBREW LETTER BET E2 05D2 HEBREW LETTER GIMEL E3 05D3 HEBREW LETTER DALET E4 05D4 HEBREW LETTER HE E5 05D5 HEBREW LETTER VAV E6 05D6 HEBREW LETTER ZAYIN E7 05D7 HEBREW LETTER HET E8 05D8 HEBREW LETTER TET E9 05D9 HEBREW LETTER YOD EA 05DA HEBREW LETTER FINAL KAF EB 05DB HEBREW LETTER KAF EC 05DC HEBREW LETTER LAMED ED 05DD HEBREW LETTER FINAL MEM EE 05DE HEBREW LETTER MEM EF 05DF HEBREW LETTER FINAL NUN F0 05E0 HEBREW LETTER NUN F1 05E1 HEBREW LETTER SAMEKH F2 05E2 HEBREW LETTER AYIN F3 05E3 HEBREW LETTER FINAL PE F4 05E4 HEBREW LETTER PE F5 05E5 HEBREW LETTER FINAL TSADI F6 05E6 HEBREW LETTER TSADI F7 05E7 HEBREW LETTER QOF F8 05E8 HEBREW LETTER RESH F9 05E9 HEBREW LETTER SHIN FA 05EA HEBREW LETTER TAV FD 200E LEFT-TO-RIGHT MARK FE 200F RIGHT-TO-LEFT MARK cyrus-imapd-2.5.10/lib/charset/iso-8859-13.t0000644000175000017500000002166313001236020014762 00000000000000# # Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. # # Redistribution and use in source and binary forms, with or without # modification, are permitted provided that the following conditions # are met: # # 1. Redistributions of source code must retain the above copyright # notice, this list of conditions and the following disclaimer. # # 2. Redistributions in binary form must reproduce the above copyright # notice, this list of conditions and the following disclaimer in # the documentation and/or other materials provided with the # distribution. # # 3. The name "Carnegie Mellon University" must not be used to # endorse or promote products derived from this software without # prior written permission. For permission or any legal # details, please contact # Carnegie Mellon University # Center for Technology Transfer and Enterprise Creation # 4615 Forbes Avenue # Suite 302 # Pittsburgh, PA 15213 # (412) 268-7393, fax: (412) 268-7395 # innovation@andrew.cmu.edu # # 4. Redistributions of any form whatsoever must retain the following # acknowledgment: # "This product includes software developed by Computing Services # at Carnegie Mellon University (http://www.cmu.edu/computing/)." # # CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO # THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY # AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE # FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES # WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN # AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING # OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. 00 0000 NULL 01 0001 START OF HEADING 02 0002 START OF TEXT 03 0003 END OF TEXT 04 0004 END OF TRANSMISSION 05 0005 ENQUIRY 06 0006 ACKNOWLEDGE 07 0007 BELL 08 0008 BACKSPACE 09 0009 HORIZONTAL TABULATION 0A 000A LINE FEED 0B 000B VERTICAL TABULATION 0C 000C FORM FEED 0D 000D CARRIAGE RETURN 0E 000E SHIFT OUT 0F 000F SHIFT IN 10 0010 DATA LINK ESCAPE 11 0011 DEVICE CONTROL ONE 12 0012 DEVICE CONTROL TWO 13 0013 DEVICE CONTROL THREE 14 0014 DEVICE CONTROL FOUR 15 0015 NEGATIVE ACKNOWLEDGE 16 0016 SYNCHRONOUS IDLE 17 0017 END OF TRANSMISSION BLOCK 18 0018 CANCEL 19 0019 END OF MEDIUM 1A 001A SUBSTITUTE 1B 001B ESCAPE 1C 001C FILE SEPARATOR 1D 001D GROUP SEPARATOR 1E 001E RECORD SEPARATOR 1F 001F UNIT SEPARATOR 20 0020 SPACE 21 0021 EXCLAMATION MARK 22 0022 QUOTATION MARK 23 0023 NUMBER SIGN 24 0024 DOLLAR SIGN 25 0025 PERCENT SIGN 26 0026 AMPERSAND 27 0027 APOSTROPHE 28 0028 LEFT PARENTHESIS 29 0029 RIGHT PARENTHESIS 2A 002A ASTERISK 2B 002B PLUS SIGN 2C 002C COMMA 2D 002D HYPHEN-MINUS 2E 002E FULL STOP 2F 002F SOLIDUS 30 0030 DIGIT ZERO 31 0031 DIGIT ONE 32 0032 DIGIT TWO 33 0033 DIGIT THREE 34 0034 DIGIT FOUR 35 0035 DIGIT FIVE 36 0036 DIGIT SIX 37 0037 DIGIT SEVEN 38 0038 DIGIT EIGHT 39 0039 DIGIT NINE 3A 003A COLON 3B 003B SEMICOLON 3C 003C LESS-THAN SIGN 3D 003D EQUALS SIGN 3E 003E GREATER-THAN SIGN 3F 003F QUESTION MARK 40 0040 COMMERCIAL AT 41 0041 LATIN CAPITAL LETTER A 42 0042 LATIN CAPITAL LETTER B 43 0043 LATIN CAPITAL LETTER C 44 0044 LATIN CAPITAL LETTER D 45 0045 LATIN CAPITAL LETTER E 46 0046 LATIN CAPITAL LETTER F 47 0047 LATIN CAPITAL LETTER G 48 0048 LATIN CAPITAL LETTER H 49 0049 LATIN CAPITAL LETTER I 4A 004A LATIN CAPITAL LETTER J 4B 004B LATIN CAPITAL LETTER K 4C 004C LATIN CAPITAL LETTER L 4D 004D LATIN CAPITAL LETTER M 4E 004E LATIN CAPITAL LETTER N 4F 004F LATIN CAPITAL LETTER O 50 0050 LATIN CAPITAL LETTER P 51 0051 LATIN CAPITAL LETTER Q 52 0052 LATIN CAPITAL LETTER R 53 0053 LATIN CAPITAL LETTER S 54 0054 LATIN CAPITAL LETTER T 55 0055 LATIN CAPITAL LETTER U 56 0056 LATIN CAPITAL LETTER V 57 0057 LATIN CAPITAL LETTER W 58 0058 LATIN CAPITAL LETTER X 59 0059 LATIN CAPITAL LETTER Y 5A 005A LATIN CAPITAL LETTER Z 5B 005B LEFT SQUARE BRACKET 5C 005C REVERSE SOLIDUS 5D 005D RIGHT SQUARE BRACKET 5E 005E CIRCUMFLEX ACCENT 5F 005F LOW LINE 60 0060 GRAVE ACCENT 61 0061 LATIN SMALL LETTER A 62 0062 LATIN SMALL LETTER B 63 0063 LATIN SMALL LETTER C 64 0064 LATIN SMALL LETTER D 65 0065 LATIN SMALL LETTER E 66 0066 LATIN SMALL LETTER F 67 0067 LATIN SMALL LETTER G 68 0068 LATIN SMALL LETTER H 69 0069 LATIN SMALL LETTER I 6A 006A LATIN SMALL LETTER J 6B 006B LATIN SMALL LETTER K 6C 006C LATIN SMALL LETTER L 6D 006D LATIN SMALL LETTER M 6E 006E LATIN SMALL LETTER N 6F 006F LATIN SMALL LETTER O 70 0070 LATIN SMALL LETTER P 71 0071 LATIN SMALL LETTER Q 72 0072 LATIN SMALL LETTER R 73 0073 LATIN SMALL LETTER S 74 0074 LATIN SMALL LETTER T 75 0075 LATIN SMALL LETTER U 76 0076 LATIN SMALL LETTER V 77 0077 LATIN SMALL LETTER W 78 0078 LATIN SMALL LETTER X 79 0079 LATIN SMALL LETTER Y 7A 007A LATIN SMALL LETTER Z 7B 007B LEFT CURLY BRACKET 7C 007C VERTICAL LINE 7D 007D RIGHT CURLY BRACKET 7E 007E TILDE 7F 007F DELETE 80 0080 81 0081 82 0082 83 0083 84 0084 85 0085 86 0086 87 0087 88 0088 89 0089 8A 008A 8B 008B 8C 008C 8D 008D 8E 008E 8F 008F 90 0090 91 0091 92 0092 93 0093 94 0094 95 0095 96 0096 97 0097 98 0098 99 0099 9A 009A 9B 009B 9C 009C 9D 009D 9E 009E 9F 009F A0 00A0 NO-BREAK SPACE A1 201D RIGHT DOUBLE QUOTATION MARK A2 00A2 CENT SIGN A3 00A3 POUND SIGN A4 00A4 CURRENCY SIGN A5 201E DOUBLE LOW-9 QUOTATION MARK A6 00A6 BROKEN BAR A7 00A7 SECTION SIGN A8 00D8 LATIN CAPITAL LETTER O WITH STROKE A9 00A9 COPYRIGHT SIGN AA 0156 LATIN CAPITAL LETTER R WITH CEDILLA AB 00AB LEFT-POINTING DOUBLE ANGLE QUOTATION MARK AC 00AC NOT SIGN AD 00AD SOFT HYPHEN AE 00AE REGISTERED SIGN AF 00C6 LATIN CAPITAL LETTER AE B0 00B0 DEGREE SIGN B1 00B1 PLUS-MINUS SIGN B2 00B2 SUPERSCRIPT TWO B3 00B3 SUPERSCRIPT THREE B4 201C LEFT DOUBLE QUOTATION MARK B5 00B5 MICRO SIGN B6 00B6 PILCROW SIGN B7 00B7 MIDDLE DOT B8 00F8 LATIN SMALL LETTER O WITH STROKE B9 00B9 SUPERSCRIPT ONE BA 0157 LATIN SMALL LETTER R WITH CEDILLA BB 00BB RIGHT-POINTING DOUBLE ANGLE QUOTATION MARK BC 00BC VULGAR FRACTION ONE QUARTER BD 00BD VULGAR FRACTION ONE HALF BE 00BE VULGAR FRACTION THREE QUARTERS BF 00E6 LATIN SMALL LETTER AE C0 0104 LATIN CAPITAL LETTER A WITH OGONEK C1 012E LATIN CAPITAL LETTER I WITH OGONEK C2 0100 LATIN CAPITAL LETTER A WITH MACRON C3 0106 LATIN CAPITAL LETTER C WITH ACUTE C4 00C4 LATIN CAPITAL LETTER A WITH DIAERESIS C5 00C5 LATIN CAPITAL LETTER A WITH RING ABOVE C6 0118 LATIN CAPITAL LETTER E WITH OGONEK C7 0112 LATIN CAPITAL LETTER E WITH MACRON C8 010C LATIN CAPITAL LETTER C WITH CARON C9 00C9 LATIN CAPITAL LETTER E WITH ACUTE CA 0179 LATIN CAPITAL LETTER Z WITH ACUTE CB 0116 LATIN CAPITAL LETTER E WITH DOT ABOVE CC 0122 LATIN CAPITAL LETTER G WITH CEDILLA CD 0136 LATIN CAPITAL LETTER K WITH CEDILLA CE 012A LATIN CAPITAL LETTER I WITH MACRON CF 013B LATIN CAPITAL LETTER L WITH CEDILLA D0 0160 LATIN CAPITAL LETTER S WITH CARON D1 0143 LATIN CAPITAL LETTER N WITH ACUTE D2 0145 LATIN CAPITAL LETTER N WITH CEDILLA D3 00D3 LATIN CAPITAL LETTER O WITH ACUTE D4 014C LATIN CAPITAL LETTER O WITH MACRON D5 00D5 LATIN CAPITAL LETTER O WITH TILDE D6 00D6 LATIN CAPITAL LETTER O WITH DIAERESIS D7 00D7 MULTIPLICATION SIGN D8 0172 LATIN CAPITAL LETTER U WITH OGONEK D9 0141 LATIN CAPITAL LETTER L WITH STROKE DA 015A LATIN CAPITAL LETTER S WITH ACUTE DB 016A LATIN CAPITAL LETTER U WITH MACRON DC 00DC LATIN CAPITAL LETTER U WITH DIAERESIS DD 017B LATIN CAPITAL LETTER Z WITH DOT ABOVE DE 017D LATIN CAPITAL LETTER Z WITH CARON DF 00DF LATIN SMALL LETTER SHARP S (German) E0 0105 LATIN SMALL LETTER A WITH OGONEK E1 012F LATIN SMALL LETTER I WITH OGONEK E2 0101 LATIN SMALL LETTER A WITH MACRON E3 0107 LATIN SMALL LETTER C WITH ACUTE E4 00E4 LATIN SMALL LETTER A WITH DIAERESIS E5 00E5 LATIN SMALL LETTER A WITH RING ABOVE E6 0119 LATIN SMALL LETTER E WITH OGONEK E7 0113 LATIN SMALL LETTER E WITH MACRON E8 010D LATIN SMALL LETTER C WITH CARON E9 00E9 LATIN SMALL LETTER E WITH ACUTE EA 017A LATIN SMALL LETTER Z WITH ACUTE EB 0117 LATIN SMALL LETTER E WITH DOT ABOVE EC 0123 LATIN SMALL LETTER G WITH CEDILLA ED 0137 LATIN SMALL LETTER K WITH CEDILLA EE 012B LATIN SMALL LETTER I WITH MACRON EF 013C LATIN SMALL LETTER L WITH CEDILLA F0 0161 LATIN SMALL LETTER S WITH CARON F1 0144 LATIN SMALL LETTER N WITH ACUTE F2 0146 LATIN SMALL LETTER N WITH CEDILLA F3 00F3 LATIN SMALL LETTER O WITH ACUTE F4 014D LATIN SMALL LETTER O WITH MACRON F5 00F5 LATIN SMALL LETTER O WITH TILDE F6 00F6 LATIN SMALL LETTER O WITH DIAERESIS F7 00F7 DIVISION SIGN F8 0173 LATIN SMALL LETTER U WITH OGONEK F9 0142 LATIN SMALL LETTER L WITH STROKE FA 015B LATIN SMALL LETTER S WITH ACUTE FB 016B LATIN SMALL LETTER U WITH MACRON FC 00FC LATIN SMALL LETTER U WITH DIAERESIS FD 017C LATIN SMALL LETTER Z WITH DOT ABOVE FE 017E LATIN SMALL LETTER Z WITH CARON FF 2019 RIGHT SINGLE QUOTATION MARK cyrus-imapd-2.5.10/lib/charset/iso-8859-6.t0000644000175000017500000002031413001236020014674 00000000000000# # Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. # # Redistribution and use in source and binary forms, with or without # modification, are permitted provided that the following conditions # are met: # # 1. Redistributions of source code must retain the above copyright # notice, this list of conditions and the following disclaimer. # # 2. Redistributions in binary form must reproduce the above copyright # notice, this list of conditions and the following disclaimer in # the documentation and/or other materials provided with the # distribution. # # 3. The name "Carnegie Mellon University" must not be used to # endorse or promote products derived from this software without # prior written permission. For permission or any legal # details, please contact # Carnegie Mellon University # Center for Technology Transfer and Enterprise Creation # 4615 Forbes Avenue # Suite 302 # Pittsburgh, PA 15213 # (412) 268-7393, fax: (412) 268-7395 # innovation@andrew.cmu.edu # # 4. Redistributions of any form whatsoever must retain the following # acknowledgment: # "This product includes software developed by Computing Services # at Carnegie Mellon University (http://www.cmu.edu/computing/)." # # CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO # THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY # AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE # FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES # WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN # AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING # OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. 0 0000 NULL (NUL) 1 0001 START OF HEADING (SOH) 2 0002 START OF TEXT (STX) 3 0003 END OF TEXT (ETX) 4 0004 END OF TRANSMISSION (EOT) 5 0005 ENQUIRY (ENQ) 6 0006 ACKNOWLEDGE (ACK) 7 0007 BELL (BEL) 8 0008 BACKSPACE (BS) 9 0009 CHARACTER TABULATION (HT) A 000a LINE FEED (LF) B 000b LINE TABULATION (VT) C 000c FORM FEED (FF) D 000d CARRIAGE RETURN (CR) E 000e SHIFT OUT (SO) F 000f SHIFT IN (SI) 10 0010 DATALINK ESCAPE (DLE) 11 0011 DEVICE CONTROL ONE (DC1) 12 0012 DEVICE CONTROL TWO (DC2) 13 0013 DEVICE CONTROL THREE (DC3) 14 0014 DEVICE CONTROL FOUR (DC4) 15 0015 NEGATIVE ACKNOWLEDGE (NAK) 16 0016 SYNCRONOUS IDLE (SYN) 17 0017 END OF TRANSMISSION BLOCK (ETB) 18 0018 CANCEL (CAN) 19 0019 END OF MEDIUM (EM) 1A 001a SUBSTITUTE (SUB) 1B 001b ESCAPE (ESC) 1C 001c FILE SEPARATOR (IS4) 1D 001d GROUP SEPARATOR (IS3) 1E 001e RECORD SEPARATOR (IS2) 1F 001f UNIT SEPARATOR (IS1) 20 0020 SPACE 21 0021 EXCLAMATION MARK 22 0022 QUOTATION MARK 23 0023 NUMBER SIGN 24 0024 DOLLAR SIGN 25 0025 PERCENT SIGN 26 0026 AMPERSAND 27 0027 APOSTROPHE 28 0028 LEFT PARENTHESIS 29 0029 RIGHT PARENTHESIS 2A 002a ASTERISK 2B 002b PLUS SIGN 2C 002c COMMA 2D 002d HYPHEN-MINUS 2E 002e FULL STOP 2F 002f SOLIDUS 30 0660 ARABIC-INDIC DIGIT ZERO 31 0661 ARABIC-INDIC DIGIT ONE 32 0662 ARABIC-INDIC DIGIT TWO 33 0663 ARABIC-INDIC DIGIT THREE 34 0664 ARABIC-INDIC DIGIT FOUR 35 0665 ARABIC-INDIC DIGIT FIVE 36 0666 ARABIC-INDIC DIGIT SIX 37 0667 ARABIC-INDIC DIGIT SEVEN 38 0668 ARABIC-INDIC DIGIT EIGHT 39 0669 ARABIC-INDIC DIGIT NINE 3A 003a COLON 3B 003b SEMICOLON 3C 003c LESS-THAN SIGN 3D 003d EQUALS SIGN 3E 003e GREATER-THAN SIGN 3F 003f QUESTION MARK 40 0040 COMMERCIAL AT 41 0041 LATIN CAPITAL LETTER A 42 0042 LATIN CAPITAL LETTER B 43 0043 LATIN CAPITAL LETTER C 44 0044 LATIN CAPITAL LETTER D 45 0045 LATIN CAPITAL LETTER E 46 0046 LATIN CAPITAL LETTER F 47 0047 LATIN CAPITAL LETTER G 48 0048 LATIN CAPITAL LETTER H 49 0049 LATIN CAPITAL LETTER I 4A 004a LATIN CAPITAL LETTER J 4B 004b LATIN CAPITAL LETTER K 4C 004c LATIN CAPITAL LETTER L 4D 004d LATIN CAPITAL LETTER M 4E 004e LATIN CAPITAL LETTER N 4F 004f LATIN CAPITAL LETTER O 50 0050 LATIN CAPITAL LETTER P 51 0051 LATIN CAPITAL LETTER Q 52 0052 LATIN CAPITAL LETTER R 53 0053 LATIN CAPITAL LETTER S 54 0054 LATIN CAPITAL LETTER T 55 0055 LATIN CAPITAL LETTER U 56 0056 LATIN CAPITAL LETTER V 57 0057 LATIN CAPITAL LETTER W 58 0058 LATIN CAPITAL LETTER X 59 0059 LATIN CAPITAL LETTER Y 5A 005a LATIN CAPITAL LETTER Z 5B 005b LEFT SQUARE BRACKET 5C 005c REVERSE SOLIDUS 5D 005d RIGHT SQUARE BRACKET 5E 005e CIRCUMFLEX ACCENT 5F 005f LOW LINE 60 0060 GRAVE ACCENT 61 0061 LATIN SMALL LETTER A 62 0062 LATIN SMALL LETTER B 63 0063 LATIN SMALL LETTER C 64 0064 LATIN SMALL LETTER D 65 0065 LATIN SMALL LETTER E 66 0066 LATIN SMALL LETTER F 67 0067 LATIN SMALL LETTER G 68 0068 LATIN SMALL LETTER H 69 0069 LATIN SMALL LETTER I 6A 006a LATIN SMALL LETTER J 6B 006b LATIN SMALL LETTER K 6C 006c LATIN SMALL LETTER L 6D 006d LATIN SMALL LETTER M 6E 006e LATIN SMALL LETTER N 6F 006f LATIN SMALL LETTER O 70 0070 LATIN SMALL LETTER P 71 0071 LATIN SMALL LETTER Q 72 0072 LATIN SMALL LETTER R 73 0073 LATIN SMALL LETTER S 74 0074 LATIN SMALL LETTER T 75 0075 LATIN SMALL LETTER U 76 0076 LATIN SMALL LETTER V 77 0077 LATIN SMALL LETTER W 78 0078 LATIN SMALL LETTER X 79 0079 LATIN SMALL LETTER Y 7A 007a LATIN SMALL LETTER Z 7B 007b LEFT CURLY BRACKET 7C 007c VERTICAL LINE 7D 007d RIGHT CURLY BRACKET 7E 007e TILDE 7F 007f DELETE (DEL) 80 0080 PADDING CHARACTER (PAD) 81 0081 HIGH OCTET PRESET (HOP) 82 0082 BREAK PERMITTED HERE (BPH) 83 0083 NO BREAK HERE (NBH) 84 0084 INDEX (IND) 85 0085 NEXT LINE (NEL) 86 0086 START OF SELECTED AREA (SSA) 87 0087 END OF SELECTED AREA (ESA) 88 0088 CHARACTER TABULATION SET (HTS) 89 0089 CHARACTER TABULATION WITH JUSTIFICATION (HTJ) 8A 008a LINE TABULATION SET (VTS) 8B 008b PARTIAL LINE FORWARD (PLD) 8C 008c PARTIAL LINE BACKWARD (PLU) 8D 008d REVERSE LINE FEED (RI) 8E 008e SINGLE-SHIFT TWO (SS2) 8F 008f SINGLE-SHIFT THREE (SS3) 90 0090 DEVICE CONTROL STRING (DCS) 91 0091 PRIVATE USE ONE (PU1) 92 0092 PRIVATE USE TWO (PU2) 93 0093 SET TRANSMIT STATE (STS) 94 0094 CANCEL CHARACTER (CCH) 95 0095 MESSAGE WAITING (MW) 96 0096 START OF GUARDED AREA (SPA) 97 0097 END OF GUARDED AREA (EPA) 98 0098 START OF STRING (SOS) 99 0099 SINGLE GRAPHIC CHARACTER INTRODUCER (SGCI) 9A 009a SINGLE CHARACTER INTRODUCER (SCI) 9B 009b CONTROL SEQUENCE INTRODUCER (CSI) 9C 009c STRING TERMINATOR (ST) 9D 009d OPERATING SYSTEM COMMAND (OSC) 9E 009e PRIVACY MESSAGE (PM) 9F 009f APPLICATION PROGRAM COMMAND (APC) A0 00a0 NO-BREAK SPACE A1 ???? EMPTY A2 ???? EMPTY A3 ???? EMPTY A4 00a4 CURRENCY SIGN A5 ???? EMPTY A6 ???? EMPTY A7 ???? EMPTY A8 ???? EMPTY A9 ???? EMPTY AA ???? EMPTY AB ???? EMPTY AC 060c ARABIC COMMA AD 00ad SOFT HYPHEN AE ???? EMPTY AF ???? EMPTY B0 ???? EMPTY B1 ???? EMPTY B2 ???? EMPTY B3 ???? EMPTY B4 ???? EMPTY B5 ???? EMPTY B6 ???? EMPTY B7 ???? EMPTY B8 ???? EMPTY B9 ???? EMPTY BA ???? EMPTY BB 061b ARABIC SEMICOLON BC ???? EMPTY BD ???? EMPTY BE ???? EMPTY BF 061f ARABIC QUESTION MARK C0 ???? EMPTY C1 0621 ARABIC LETTER HAMZA C2 0622 ARABIC LETTER ALEF WITH MADDA ABOVE C3 0623 ARABIC LETTER ALEF WITH HAMZA ABOVE C4 0624 ARABIC LETTER WAW WITH HAMZA ABOVE C5 0625 ARABIC LETTER ALEF WITH HAMZA BELOW C6 0626 ARABIC LETTER YEH WITH HAMZA ABOVE C7 0627 ARABIC LETTER ALEF C8 0628 ARABIC LETTER BEH C9 0629 ARABIC LETTER TEH MARBUTA CA 062a ARABIC LETTER TEH CB 062b ARABIC LETTER THEH CC 062c ARABIC LETTER JEEM CD 062d ARABIC LETTER HAH CE 062e ARABIC LETTER KHAH CF 062f ARABIC LETTER DAL D0 0630 ARABIC LETTER THAL D1 0631 ARABIC LETTER REH D2 0632 ARABIC LETTER ZAIN D3 0633 ARABIC LETTER SEEN D4 0634 ARABIC LETTER SHEEN D5 0635 ARABIC LETTER SAD D6 0636 ARABIC LETTER DAD D7 0637 ARABIC LETTER TAH D8 0638 ARABIC LETTER ZAH D9 0639 ARABIC LETTER AIN DA 063a ARABIC LETTER GHAIN DB ???? EMPTY DC ???? EMPTY DD ???? EMPTY DE ???? EMPTY DF ???? EMPTY E0 0640 ARABIC TATWEEL E1 0641 ARABIC LETTER FEH E2 0642 ARABIC LETTER QAF E3 0643 ARABIC LETTER KAF E4 0644 ARABIC LETTER LAM E5 0645 ARABIC LETTER MEEM E6 0646 ARABIC LETTER NOON E7 0647 ARABIC LETTER HEH E8 0648 ARABIC LETTER WAW E9 0649 ARABIC LETTER ALEF MAKSURA EA 064a ARABIC LETTER YEH EB 064b ARABIC FATHATAN EC 064c ARABIC DAMMATAN ED 064d ARABIC KASRATAN EE 064e ARABIC FATHA EF 064f ARABIC DAMMA F0 0650 ARABIC KASRA F1 0651 ARABIC SHADDA F2 0652 ARABIC SUKUN F3 ???? EMPTY F4 ???? EMPTY F5 ???? EMPTY F6 ???? EMPTY F7 ???? EMPTY F8 ???? EMPTY F9 ???? EMPTY FA ???? EMPTY FB ???? EMPTY FC ???? EMPTY FD ???? EMPTY FE ???? EMPTY FF ???? EMPTY cyrus-imapd-2.5.10/lib/charset/windows-874.t0000644000175000017500000001754313001236020015350 00000000000000# # Copyright (c) 1994-2014 Carnegie Mellon University. All rights reserved. # # Redistribution and use in source and binary forms, with or without # modification, are permitted provided that the following conditions # are met: # # 1. Redistributions of source code must retain the above copyright # notice, this list of conditions and the following disclaimer. # # 2. Redistributions in binary form must reproduce the above copyright # notice, this list of conditions and the following disclaimer in # the documentation and/or other materials provided with the # distribution. # # 3. The name "Carnegie Mellon University" must not be used to # endorse or promote products derived from this software without # prior written permission. For permission or any legal # details, please contact # Carnegie Mellon University # Center for Technology Transfer and Enterprise Creation # 4615 Forbes Avenue # Suite 302 # Pittsburgh, PA 15213 # (412) 268-7393, fax: (412) 268-7395 # innovation@andrew.cmu.edu # # 4. Redistributions of any form whatsoever must retain the following # acknowledgment: # "This product includes software developed by Computing Services # at Carnegie Mellon University (http://www.cmu.edu/computing/)." # # CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO # THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY # AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE # FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES # WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN # AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING # OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. # # Charset put together by Bron Gondwana # Reference: http://msdn.microsoft.com/en-au/goglobal/cc305142.aspx 00 0000 NULL 01 0001 START OF HEADING 02 0002 START OF TEXT 03 0003 END OF TEXT 04 0004 END OF TRANSMISSION 05 0005 ENQUIRY 06 0006 ACKNOWLEDGE 07 0007 BELL 08 0008 BACKSPACE 09 0009 HORIZONTAL TABULATION 0A 000A LINE FEED 0B 000B VERTICAL TABULATION 0C 000C FORM FEED 0D 000D CARRIAGE RETURN 0E 000E SHIFT OUT 0F 000F SHIFT IN 10 0010 DATA LINK ESCAPE 11 0011 DEVICE CONTROL ONE 12 0012 DEVICE CONTROL TWO 13 0013 DEVICE CONTROL THREE 14 0014 DEVICE CONTROL FOUR 15 0015 NEGATIVE ACKNOWLEDGE 16 0016 SYNCHRONOUS IDLE 17 0017 END OF TRANSMISSION BLOCK 18 0018 CANCEL 19 0019 END OF MEDIUM 1A 001A SUBSTITUTE 1B 001B ESCAPE 1C 001C FILE SEPARATOR 1D 001D GROUP SEPARATOR 1E 001E RECORD SEPARATOR 1F 001F UNIT SEPARATOR 20 0020 SPACE 21 0021 EXCLAMATION MARK 22 0022 QUOTATION MARK 23 0023 NUMBER SIGN 24 0024 DOLLAR SIGN 25 0025 PERCENT SIGN 26 0026 AMPERSAND 27 0027 APOSTROPHE 28 0028 LEFT PARENTHESIS 29 0029 RIGHT PARENTHESIS 2A 002A ASTERISK 2B 002B PLUS SIGN 2C 002C COMMA 2D 002D HYPHEN-MINUS 2E 002E FULL STOP 2F 002F SOLIDUS 30 0030 DIGIT ZERO 31 0031 DIGIT ONE 32 0032 DIGIT TWO 33 0033 DIGIT THREE 34 0034 DIGIT FOUR 35 0035 DIGIT FIVE 36 0036 DIGIT SIX 37 0037 DIGIT SEVEN 38 0038 DIGIT EIGHT 39 0039 DIGIT NINE 3A 003A COLON 3B 003B SEMICOLON 3C 003C LESS-THAN SIGN 3D 003D EQUALS SIGN 3E 003E GREATER-THAN SIGN 3F 003F QUESTION MARK 40 0040 COMMERCIAL AT 41 0041 LATIN CAPITAL LETTER A 42 0042 LATIN CAPITAL LETTER B 43 0043 LATIN CAPITAL LETTER C 44 0044 LATIN CAPITAL LETTER D 45 0045 LATIN CAPITAL LETTER E 46 0046 LATIN CAPITAL LETTER F 47 0047 LATIN CAPITAL LETTER G 48 0048 LATIN CAPITAL LETTER H 49 0049 LATIN CAPITAL LETTER I 4A 004A LATIN CAPITAL LETTER J 4B 004B LATIN CAPITAL LETTER K 4C 004C LATIN CAPITAL LETTER L 4D 004D LATIN CAPITAL LETTER M 4E 004E LATIN CAPITAL LETTER N 4F 004F LATIN CAPITAL LETTER O 50 0050 LATIN CAPITAL LETTER P 51 0051 LATIN CAPITAL LETTER Q 52 0052 LATIN CAPITAL LETTER R 53 0053 LATIN CAPITAL LETTER S 54 0054 LATIN CAPITAL LETTER T 55 0055 LATIN CAPITAL LETTER U 56 0056 LATIN CAPITAL LETTER V 57 0057 LATIN CAPITAL LETTER W 58 0058 LATIN CAPITAL LETTER X 59 0059 LATIN CAPITAL LETTER Y 5A 005A LATIN CAPITAL LETTER Z 5B 005B LEFT SQUARE BRACKET 5C 005C REVERSE SOLIDUS 5D 005D RIGHT SQUARE BRACKET 5E 005E CIRCUMFLEX ACCENT 5F 005F LOW LINE 60 0060 GRAVE ACCENT 61 0061 LATIN SMALL LETTER A 62 0062 LATIN SMALL LETTER B 63 0063 LATIN SMALL LETTER C 64 0064 LATIN SMALL LETTER D 65 0065 LATIN SMALL LETTER E 66 0066 LATIN SMALL LETTER F 67 0067 LATIN SMALL LETTER G 68 0068 LATIN SMALL LETTER H 69 0069 LATIN SMALL LETTER I 6A 006A LATIN SMALL LETTER J 6B 006B LATIN SMALL LETTER K 6C 006C LATIN SMALL LETTER L 6D 006D LATIN SMALL LETTER M 6E 006E LATIN SMALL LETTER N 6F 006F LATIN SMALL LETTER O 70 0070 LATIN SMALL LETTER P 71 0071 LATIN SMALL LETTER Q 72 0072 LATIN SMALL LETTER R 73 0073 LATIN SMALL LETTER S 74 0074 LATIN SMALL LETTER T 75 0075 LATIN SMALL LETTER U 76 0076 LATIN SMALL LETTER V 77 0077 LATIN SMALL LETTER W 78 0078 LATIN SMALL LETTER X 79 0079 LATIN SMALL LETTER Y 7A 007A LATIN SMALL LETTER Z 7B 007B LEFT CURLY BRACKET 7C 007C VERTICAL LINE 7D 007D RIGHT CURLY BRACKET 7E 007E TILDE 7F 007F DELETE 80 20AC EURO SIGN 85 2026 HORIZONTAL ELLIPSIS 91 2018 LEFT SINGLE QUOTATION MARK 92 2019 RIGHT SINGLE QUOTATION MARK 93 201C LEFT DOUBLE QUOTATION MARK 94 201D RIGHT DOUBLE QUOTATION MARK 95 2022 BULLET 96 2013 EN DASH 97 2014 EM DASH A0 00A0 NO-BREAK SPACE A1 0E01 THAI CHARACTER KO KAI A2 0E02 THAI CHARACTER KHO KHAI A3 0E03 THAI CHARACTER KHO KHUAT A4 0E04 THAI CHARACTER KHO KHWAI A5 0E05 THAI CHARACTER KHO KHON A6 0E06 THAI CHARACTER KHO RAKHANG A7 0E07 THAI CHARACTER NGO NGU A8 0E08 THAI CHARACTER CHO CHAN A9 0E09 THAI CHARACTER CHO CHING AA 0E0A THAI CHARACTER CHO CHANG AB 0E0B THAI CHARACTER SO SO AC 0E0C THAI CHARACTER CHO CHOE AD 0E0D THAI CHARACTER YO YING AE 0E0E THAI CHARACTER DO CHADA AF 0E0F THAI CHARACTER TO PATAK B0 0E10 THAI CHARACTER THO THAN B1 0E11 THAI CHARACTER THO NANGMONTHO B2 0E12 THAI CHARACTER THO PHUTHAO B3 0E13 THAI CHARACTER NO NEN B4 0E14 THAI CHARACTER DO DEK B5 0E15 THAI CHARACTER TO TAO B6 0E16 THAI CHARACTER THO THUNG B7 0E17 THAI CHARACTER THO THAHAN B8 0E18 THAI CHARACTER THO THONG B9 0E19 THAI CHARACTER NO NU BA 0E1A THAI CHARACTER BO BAIMAI BB 0E1B THAI CHARACTER PO PLA BC 0E1C THAI CHARACTER PHO PHUNG BD 0E1D THAI CHARACTER FO FA BE 0E1E THAI CHARACTER PHO PHAN BF 0E1F THAI CHARACTER FO FAN C0 0E20 THAI CHARACTER PHO SAMPHAO C1 0E21 THAI CHARACTER MO MA C2 0E22 THAI CHARACTER YO YAK C3 0E23 THAI CHARACTER RO RUA C4 0E24 THAI CHARACTER RU C5 0E25 THAI CHARACTER LO LING C6 0E26 THAI CHARACTER LU C7 0E27 THAI CHARACTER WO WAEN C8 0E28 THAI CHARACTER SO SALA C9 0E29 THAI CHARACTER SO RUSI CA 0E2A THAI CHARACTER SO SUA CB 0E2B THAI CHARACTER HO HIP CC 0E2C THAI CHARACTER LO CHULA CD 0E2D THAI CHARACTER O ANG CE 0E2E THAI CHARACTER HO NOKHUK CF 0E2F THAI CHARACTER PAIYANNOI D0 0E30 THAI CHARACTER SARA A D1 0E31 THAI CHARACTER MAI HAN-AKAT D2 0E32 THAI CHARACTER SARA AA D3 0E33 THAI CHARACTER SARA AM D4 0E34 THAI CHARACTER SARA I D5 0E35 THAI CHARACTER SARA II D6 0E36 THAI CHARACTER SARA UE D7 0E37 THAI CHARACTER SARA UEE D8 0E38 THAI CHARACTER SARA U D9 0E39 THAI CHARACTER SARA UU DA 0E3A THAI CHARACTER PHINTHU DF 0E3F THAI CURRENCY SYMBOL BAHT E0 0E40 THAI CHARACTER SARA E E1 0E41 THAI CHARACTER SARA AE E2 0E42 THAI CHARACTER SARA O E3 0E43 THAI CHARACTER SARA AI MAIMUAN E4 0E44 THAI CHARACTER SARA AI MAIMALAI E5 0E45 THAI CHARACTER LAKKHANGYAO E6 0E46 THAI CHARACTER MAIYAMOK E7 0E47 THAI CHARACTER MAITAIKHU E8 0E48 THAI CHARACTER MAI EK E9 0E49 THAI CHARACTER MAI THO EA 0E4A THAI CHARACTER MAI TRI EB 0E4B THAI CHARACTER MAI CHATTAWA EC 0E4C THAI CHARACTER THANTHAKHAT ED 0E4D THAI CHARACTER NIKHAHIT EE 0E4E THAI CHARACTER YAMAKKAN EF 0E4F THAI CHARACTER FONGMAN F0 0E50 THAI DIGIT ZERO F1 0E51 THAI DIGIT ONE F2 0E52 THAI DIGIT TWO F3 0E53 THAI DIGIT THREE F4 0E54 THAI DIGIT FOUR F5 0E55 THAI DIGIT FIVE F6 0E56 THAI DIGIT SIX F7 0E57 THAI DIGIT SEVEN F8 0E58 THAI DIGIT EIGHT F9 0E59 THAI DIGIT NINE FA 0E5A THAI CHARACTER ANGKHANKHU FB 0E5B THAI CHARACTER KHOMUT cyrus-imapd-2.5.10/lib/charset/windows-1252.t0000644000175000017500000002300513001236020015405 00000000000000# # Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. # # Redistribution and use in source and binary forms, with or without # modification, are permitted provided that the following conditions # are met: # # 1. Redistributions of source code must retain the above copyright # notice, this list of conditions and the following disclaimer. # # 2. Redistributions in binary form must reproduce the above copyright # notice, this list of conditions and the following disclaimer in # the documentation and/or other materials provided with the # distribution. # # 3. The name "Carnegie Mellon University" must not be used to # endorse or promote products derived from this software without # prior written permission. For permission or any legal # details, please contact # Carnegie Mellon University # Center for Technology Transfer and Enterprise Creation # 4615 Forbes Avenue # Suite 302 # Pittsburgh, PA 15213 # (412) 268-7393, fax: (412) 268-7395 # innovation@andrew.cmu.edu # # 4. Redistributions of any form whatsoever must retain the following # acknowledgment: # "This product includes software developed by Computing Services # at Carnegie Mellon University (http://www.cmu.edu/computing/)." # # CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO # THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY # AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE # FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES # WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN # AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING # OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. # # Charset put together by Ewald Dieterich # Reference: http://www.microsoft.com/globaldev/reference/sbcs/1252.htm 0 0000 NULL (NUL) 1 0001 START OF HEADING (SOH) 2 0002 START OF TEXT (STX) 3 0003 END OF TEXT (ETX) 4 0004 END OF TRANSMISSION (EOT) 5 0005 ENQUIRY (ENQ) 6 0006 ACKNOWLEDGE (ACK) 7 0007 BELL (BEL) 8 0008 BACKSPACE (BS) 9 0009 CHARACTER TABULATION (HT) A 000a LINE FEED (LF) B 000b LINE TABULATION (VT) C 000c FORM FEED (FF) D 000d CARRIAGE RETURN (CR) E 000e SHIFT OUT (SO) F 000f SHIFT IN (SI) 10 0010 DATALINK ESCAPE (DLE) 11 0011 DEVICE CONTROL ONE (DC1) 12 0012 DEVICE CONTROL TWO (DC2) 13 0013 DEVICE CONTROL THREE (DC3) 14 0014 DEVICE CONTROL FOUR (DC4) 15 0015 NEGATIVE ACKNOWLEDGE (NAK) 16 0016 SYNCRONOUS IDLE (SYN) 17 0017 END OF TRANSMISSION BLOCK (ETB) 18 0018 CANCEL (CAN) 19 0019 END OF MEDIUM (EM) 1A 001a SUBSTITUTE (SUB) 1B 001b ESCAPE (ESC) 1C 001c FILE SEPARATOR (IS4) 1D 001d GROUP SEPARATOR (IS3) 1E 001e RECORD SEPARATOR (IS2) 1F 001f UNIT SEPARATOR (IS1) 20 0020 SPACE 21 0021 EXCLAMATION MARK 22 0022 QUOTATION MARK 23 0023 NUMBER SIGN 24 0024 DOLLAR SIGN 25 0025 PERCENT SIGN 26 0026 AMPERSAND 27 0027 APOSTROPHE 28 0028 LEFT PARENTHESIS 29 0029 RIGHT PARENTHESIS 2A 002a ASTERISK 2B 002b PLUS SIGN 2C 002c COMMA 2D 002d HYPHEN-MINUS 2E 002e FULL STOP 2F 002f SOLIDUS 30 0030 DIGIT ZERO 31 0031 DIGIT ONE 32 0032 DIGIT TWO 33 0033 DIGIT THREE 34 0034 DIGIT FOUR 35 0035 DIGIT FIVE 36 0036 DIGIT SIX 37 0037 DIGIT SEVEN 38 0038 DIGIT EIGHT 39 0039 DIGIT NINE 3A 003a COLON 3B 003b SEMICOLON 3C 003c LESS-THAN SIGN 3D 003d EQUALS SIGN 3E 003e GREATER-THAN SIGN 3F 003f QUESTION MARK 40 0040 COMMERCIAL AT 41 0041 LATIN CAPITAL LETTER A 42 0042 LATIN CAPITAL LETTER B 43 0043 LATIN CAPITAL LETTER C 44 0044 LATIN CAPITAL LETTER D 45 0045 LATIN CAPITAL LETTER E 46 0046 LATIN CAPITAL LETTER F 47 0047 LATIN CAPITAL LETTER G 48 0048 LATIN CAPITAL LETTER H 49 0049 LATIN CAPITAL LETTER I 4A 004a LATIN CAPITAL LETTER J 4B 004b LATIN CAPITAL LETTER K 4C 004c LATIN CAPITAL LETTER L 4D 004d LATIN CAPITAL LETTER M 4E 004e LATIN CAPITAL LETTER N 4F 004f LATIN CAPITAL LETTER O 50 0050 LATIN CAPITAL LETTER P 51 0051 LATIN CAPITAL LETTER Q 52 0052 LATIN CAPITAL LETTER R 53 0053 LATIN CAPITAL LETTER S 54 0054 LATIN CAPITAL LETTER T 55 0055 LATIN CAPITAL LETTER U 56 0056 LATIN CAPITAL LETTER V 57 0057 LATIN CAPITAL LETTER W 58 0058 LATIN CAPITAL LETTER X 59 0059 LATIN CAPITAL LETTER Y 5A 005a LATIN CAPITAL LETTER Z 5B 005b LEFT SQUARE BRACKET 5C 005c REVERSE SOLIDUS 5D 005d RIGHT SQUARE BRACKET 5E 005e CIRCUMFLEX ACCENT 5F 005f LOW LINE 60 0060 GRAVE ACCENT 61 0061 LATIN SMALL LETTER A 62 0062 LATIN SMALL LETTER B 63 0063 LATIN SMALL LETTER C 64 0064 LATIN SMALL LETTER D 65 0065 LATIN SMALL LETTER E 66 0066 LATIN SMALL LETTER F 67 0067 LATIN SMALL LETTER G 68 0068 LATIN SMALL LETTER H 69 0069 LATIN SMALL LETTER I 6A 006a LATIN SMALL LETTER J 6B 006b LATIN SMALL LETTER K 6C 006c LATIN SMALL LETTER L 6D 006d LATIN SMALL LETTER M 6E 006e LATIN SMALL LETTER N 6F 006f LATIN SMALL LETTER O 70 0070 LATIN SMALL LETTER P 71 0071 LATIN SMALL LETTER Q 72 0072 LATIN SMALL LETTER R 73 0073 LATIN SMALL LETTER S 74 0074 LATIN SMALL LETTER T 75 0075 LATIN SMALL LETTER U 76 0076 LATIN SMALL LETTER V 77 0077 LATIN SMALL LETTER W 78 0078 LATIN SMALL LETTER X 79 0079 LATIN SMALL LETTER Y 7A 007a LATIN SMALL LETTER Z 7B 007b LEFT CURLY BRACKET 7C 007c VERTICAL LINE 7D 007d RIGHT CURLY BRACKET 7E 007e TILDE 7F 007f DELETE (DEL) 80 20ac EURO SIGN 81 ???? EMPTY 82 201a SINGLE LOW-9 QUOTATION MARK 83 0192 LATIN SMALL LETTER F WITH HOOK 84 201e DOUBLE LOW-9 QUOTATION MARK 85 2026 HORIZONTAL ELLIPSIS 86 2020 DAGGER 87 2021 DOUBLE DAGGER 88 02c6 MODIFIER LETTER CIRCUMFLEX ACCENT 89 2030 PER MILLE SIGN 8A 0160 LATIN CAPITAL LETTER S WITH CARON 8B 2039 SINGLE LEFT-POINTING ANGLE QUOTATION MARK 8C 0152 LATIN CAPITAL LIGATURE OE 8D ???? EMPTY 8E 017d LATIN CAPITAL LETTER Z WITH CARON 8F ???? EMPTY 90 ???? EMPTY 91 2018 LEFT SINGLE QUOTATION MARK 92 2019 RIGHT SINGLE QUOTATION MARK 93 201c LEFT DOUBLE QUOTATION MARK 94 201d RIGHT DOUBLE QUOTATION MARK 95 2022 BULLET 96 2013 EN DASH 97 2014 EM DASH 98 02dc SMALL TILDE 99 2122 TRADE MARK SIGN 9A 0161 LATIN SMALL LETTER S WITH CARON 9B 203a SINGLE RIGHT-POINTING ANGLE QUOTATION MARK 9C 0153 LATIN SMALL LIGATURE OE 9D ???? EMPTY 9E 017e LATIN SMALL LETTER Z WITH CARON 9F 0178 LATIN CAPITAL LETTER Y WITH DIAERESIS A0 00a0 NO-BREAK SPACE A1 00a1 INVERTED EXCLAMATION MARK A2 00a2 CENT SIGN A3 00a3 POUND SIGN A4 00a4 CURRENCY SIGN A5 00a5 YEN SIGN A6 00a6 BROKEN BAR A7 00a7 SECTION SIGN A8 00a8 DIAERESIS A9 00a9 COPYRIGHT SIGN AA 00aa FEMININE ORDINAL INDICATOR AB 00ab LEFT-POINTING DOUBLE ANGLE QUOTATION MARK AC 00ac NOT SIGN AD 00ad SOFT HYPHEN AE 00ae REGISTERED SIGN AF 00af MACRON B0 00b0 DEGREE SIGN B1 00b1 PLUS-MINUS SIGN B2 00b2 SUPERSCRIPT TWO B3 00b3 SUPERSCRIPT THREE B4 00b4 ACUTE ACCENT B5 00b5 MICRO SIGN B6 00b6 PILCROW SIGN B7 00b7 MIDDLE DOT B8 00b8 CEDILLA B9 00b9 SUPERSCRIPT ONE BA 00ba MASCULINE ORDINAL INDICATOR BB 00bb RIGHT-POINTING DOUBLE ANGLE QUOTATION MARK BC 00bc VULGAR FRACTION ONE QUARTER BD 00bd VULGAR FRACTION ONE HALF BE 00be VULGAR FRACTION THREE QUARTERS BF 00bf INVERTED QUESTION MARK C0 00c0 LATIN CAPITAL LETTER A WITH GRAVE C1 00c1 LATIN CAPITAL LETTER A WITH ACUTE C2 00c2 LATIN CAPITAL LETTER A WITH CIRCUMFLEX C3 00c3 LATIN CAPITAL LETTER A WITH TILDE C4 00c4 LATIN CAPITAL LETTER A WITH DIAERESIS C5 00c5 LATIN CAPITAL LETTER A WITH RING ABOVE C6 00c6 LATIN CAPITAL LETTER AE C7 00c7 LATIN CAPITAL LETTER C WITH CEDILLA C8 00c8 LATIN CAPITAL LETTER E WITH GRAVE C9 00c9 LATIN CAPITAL LETTER E WITH ACUTE CA 00ca LATIN CAPITAL LETTER E WITH CIRCUMFLEX CB 00cb LATIN CAPITAL LETTER E WITH DIAERESIS CC 00cc LATIN CAPITAL LETTER I WITH GRAVE CD 00cd LATIN CAPITAL LETTER I WITH ACUTE CE 00ce LATIN CAPITAL LETTER I WITH CIRCUMFLEX CF 00cf LATIN CAPITAL LETTER I WITH DIAERESIS D0 00d0 LATIN CAPITAL LETTER ETH (Icelandic) D1 00d1 LATIN CAPITAL LETTER N WITH TILDE D2 00d2 LATIN CAPITAL LETTER O WITH GRAVE D3 00d3 LATIN CAPITAL LETTER O WITH ACUTE D4 00d4 LATIN CAPITAL LETTER O WITH CIRCUMFLEX D5 00d5 LATIN CAPITAL LETTER O WITH TILDE D6 00d6 LATIN CAPITAL LETTER O WITH DIAERESIS D7 00d7 MULTIPLICATION SIGN D8 00d8 LATIN CAPITAL LETTER O WITH STROKE D9 00d9 LATIN CAPITAL LETTER U WITH GRAVE DA 00da LATIN CAPITAL LETTER U WITH ACUTE DB 00db LATIN CAPITAL LETTER U WITH CIRCUMFLEX DC 00dc LATIN CAPITAL LETTER U WITH DIAERESIS DD 00dd LATIN CAPITAL LETTER Y WITH ACUTE DE 00de LATIN CAPITAL LETTER THORN (Icelandic) DF 00df LATIN SMALL LETTER SHARP S (German) E0 00e0 LATIN SMALL LETTER A WITH GRAVE E1 00e1 LATIN SMALL LETTER A WITH ACUTE E2 00e2 LATIN SMALL LETTER A WITH CIRCUMFLEX E3 00e3 LATIN SMALL LETTER A WITH TILDE E4 00e4 LATIN SMALL LETTER A WITH DIAERESIS E5 00e5 LATIN SMALL LETTER A WITH RING ABOVE E6 00e6 LATIN SMALL LETTER AE E7 00e7 LATIN SMALL LETTER C WITH CEDILLA E8 00e8 LATIN SMALL LETTER E WITH GRAVE E9 00e9 LATIN SMALL LETTER E WITH ACUTE EA 00ea LATIN SMALL LETTER E WITH CIRCUMFLEX EB 00eb LATIN SMALL LETTER E WITH DIAERESIS EC 00ec LATIN SMALL LETTER I WITH GRAVE ED 00ed LATIN SMALL LETTER I WITH ACUTE EE 00ee LATIN SMALL LETTER I WITH CIRCUMFLEX EF 00ef LATIN SMALL LETTER I WITH DIAERESIS F0 00f0 LATIN SMALL LETTER ETH (Icelandic) F1 00f1 LATIN SMALL LETTER N WITH TILDE F2 00f2 LATIN SMALL LETTER O WITH GRAVE F3 00f3 LATIN SMALL LETTER O WITH ACUTE F4 00f4 LATIN SMALL LETTER O WITH CIRCUMFLEX F5 00f5 LATIN SMALL LETTER O WITH TILDE F6 00f6 LATIN SMALL LETTER O WITH DIAERESIS F7 00f7 DIVISION SIGN F8 00f8 LATIN SMALL LETTER O WITH STROKE F9 00f9 LATIN SMALL LETTER U WITH GRAVE FA 00fa LATIN SMALL LETTER U WITH ACUTE FB 00fb LATIN SMALL LETTER U WITH CIRCUMFLEX FC 00fc LATIN SMALL LETTER U WITH DIAERESIS FD 00fd LATIN SMALL LETTER Y WITH ACUTE FE 00fe LATIN SMALL LETTER THORN (Icelandic) FF 00ff LATIN SMALL LETTER Y WITH DIAERESIS cyrus-imapd-2.5.10/lib/charset/iso-8859-7.t0000644000175000017500000002236113001236020014701 00000000000000# # Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. # # Redistribution and use in source and binary forms, with or without # modification, are permitted provided that the following conditions # are met: # # 1. Redistributions of source code must retain the above copyright # notice, this list of conditions and the following disclaimer. # # 2. Redistributions in binary form must reproduce the above copyright # notice, this list of conditions and the following disclaimer in # the documentation and/or other materials provided with the # distribution. # # 3. The name "Carnegie Mellon University" must not be used to # endorse or promote products derived from this software without # prior written permission. For permission or any legal # details, please contact # Carnegie Mellon University # Center for Technology Transfer and Enterprise Creation # 4615 Forbes Avenue # Suite 302 # Pittsburgh, PA 15213 # (412) 268-7393, fax: (412) 268-7395 # innovation@andrew.cmu.edu # # 4. Redistributions of any form whatsoever must retain the following # acknowledgment: # "This product includes software developed by Computing Services # at Carnegie Mellon University (http://www.cmu.edu/computing/)." # # CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO # THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY # AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE # FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES # WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN # AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING # OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. 0 0000 NULL (NUL) 1 0001 START OF HEADING (SOH) 2 0002 START OF TEXT (STX) 3 0003 END OF TEXT (ETX) 4 0004 END OF TRANSMISSION (EOT) 5 0005 ENQUIRY (ENQ) 6 0006 ACKNOWLEDGE (ACK) 7 0007 BELL (BEL) 8 0008 BACKSPACE (BS) 9 0009 CHARACTER TABULATION (HT) A 000a LINE FEED (LF) B 000b LINE TABULATION (VT) C 000c FORM FEED (FF) D 000d CARRIAGE RETURN (CR) E 000e SHIFT OUT (SO) F 000f SHIFT IN (SI) 10 0010 DATALINK ESCAPE (DLE) 11 0011 DEVICE CONTROL ONE (DC1) 12 0012 DEVICE CONTROL TWO (DC2) 13 0013 DEVICE CONTROL THREE (DC3) 14 0014 DEVICE CONTROL FOUR (DC4) 15 0015 NEGATIVE ACKNOWLEDGE (NAK) 16 0016 SYNCRONOUS IDLE (SYN) 17 0017 END OF TRANSMISSION BLOCK (ETB) 18 0018 CANCEL (CAN) 19 0019 END OF MEDIUM (EM) 1A 001a SUBSTITUTE (SUB) 1B 001b ESCAPE (ESC) 1C 001c FILE SEPARATOR (IS4) 1D 001d GROUP SEPARATOR (IS3) 1E 001e RECORD SEPARATOR (IS2) 1F 001f UNIT SEPARATOR (IS1) 20 0020 SPACE 21 0021 EXCLAMATION MARK 22 0022 QUOTATION MARK 23 0023 NUMBER SIGN 24 0024 DOLLAR SIGN 25 0025 PERCENT SIGN 26 0026 AMPERSAND 27 0027 APOSTROPHE 28 0028 LEFT PARENTHESIS 29 0029 RIGHT PARENTHESIS 2A 002a ASTERISK 2B 002b PLUS SIGN 2C 002c COMMA 2D 002d HYPHEN-MINUS 2E 002e FULL STOP 2F 002f SOLIDUS 30 0030 DIGIT ZERO 31 0031 DIGIT ONE 32 0032 DIGIT TWO 33 0033 DIGIT THREE 34 0034 DIGIT FOUR 35 0035 DIGIT FIVE 36 0036 DIGIT SIX 37 0037 DIGIT SEVEN 38 0038 DIGIT EIGHT 39 0039 DIGIT NINE 3A 003a COLON 3B 003b SEMICOLON 3C 003c LESS-THAN SIGN 3D 003d EQUALS SIGN 3E 003e GREATER-THAN SIGN 3F 003f QUESTION MARK 40 0040 COMMERCIAL AT 41 0041 LATIN CAPITAL LETTER A 42 0042 LATIN CAPITAL LETTER B 43 0043 LATIN CAPITAL LETTER C 44 0044 LATIN CAPITAL LETTER D 45 0045 LATIN CAPITAL LETTER E 46 0046 LATIN CAPITAL LETTER F 47 0047 LATIN CAPITAL LETTER G 48 0048 LATIN CAPITAL LETTER H 49 0049 LATIN CAPITAL LETTER I 4A 004a LATIN CAPITAL LETTER J 4B 004b LATIN CAPITAL LETTER K 4C 004c LATIN CAPITAL LETTER L 4D 004d LATIN CAPITAL LETTER M 4E 004e LATIN CAPITAL LETTER N 4F 004f LATIN CAPITAL LETTER O 50 0050 LATIN CAPITAL LETTER P 51 0051 LATIN CAPITAL LETTER Q 52 0052 LATIN CAPITAL LETTER R 53 0053 LATIN CAPITAL LETTER S 54 0054 LATIN CAPITAL LETTER T 55 0055 LATIN CAPITAL LETTER U 56 0056 LATIN CAPITAL LETTER V 57 0057 LATIN CAPITAL LETTER W 58 0058 LATIN CAPITAL LETTER X 59 0059 LATIN CAPITAL LETTER Y 5A 005a LATIN CAPITAL LETTER Z 5B 005b LEFT SQUARE BRACKET 5C 005c REVERSE SOLIDUS 5D 005d RIGHT SQUARE BRACKET 5E 005e CIRCUMFLEX ACCENT 5F 005f LOW LINE 60 0060 GRAVE ACCENT 61 0061 LATIN SMALL LETTER A 62 0062 LATIN SMALL LETTER B 63 0063 LATIN SMALL LETTER C 64 0064 LATIN SMALL LETTER D 65 0065 LATIN SMALL LETTER E 66 0066 LATIN SMALL LETTER F 67 0067 LATIN SMALL LETTER G 68 0068 LATIN SMALL LETTER H 69 0069 LATIN SMALL LETTER I 6A 006a LATIN SMALL LETTER J 6B 006b LATIN SMALL LETTER K 6C 006c LATIN SMALL LETTER L 6D 006d LATIN SMALL LETTER M 6E 006e LATIN SMALL LETTER N 6F 006f LATIN SMALL LETTER O 70 0070 LATIN SMALL LETTER P 71 0071 LATIN SMALL LETTER Q 72 0072 LATIN SMALL LETTER R 73 0073 LATIN SMALL LETTER S 74 0074 LATIN SMALL LETTER T 75 0075 LATIN SMALL LETTER U 76 0076 LATIN SMALL LETTER V 77 0077 LATIN SMALL LETTER W 78 0078 LATIN SMALL LETTER X 79 0079 LATIN SMALL LETTER Y 7A 007a LATIN SMALL LETTER Z 7B 007b LEFT CURLY BRACKET 7C 007c VERTICAL LINE 7D 007d RIGHT CURLY BRACKET 7E 007e TILDE 7F 007f DELETE (DEL) 80 0080 PADDING CHARACTER (PAD) 81 0081 HIGH OCTET PRESET (HOP) 82 0082 BREAK PERMITTED HERE (BPH) 83 0083 NO BREAK HERE (NBH) 84 0084 INDEX (IND) 85 0085 NEXT LINE (NEL) 86 0086 START OF SELECTED AREA (SSA) 87 0087 END OF SELECTED AREA (ESA) 88 0088 CHARACTER TABULATION SET (HTS) 89 0089 CHARACTER TABULATION WITH JUSTIFICATION (HTJ) 8A 008a LINE TABULATION SET (VTS) 8B 008b PARTIAL LINE FORWARD (PLD) 8C 008c PARTIAL LINE BACKWARD (PLU) 8D 008d REVERSE LINE FEED (RI) 8E 008e SINGLE-SHIFT TWO (SS2) 8F 008f SINGLE-SHIFT THREE (SS3) 90 0090 DEVICE CONTROL STRING (DCS) 91 0091 PRIVATE USE ONE (PU1) 92 0092 PRIVATE USE TWO (PU2) 93 0093 SET TRANSMIT STATE (STS) 94 0094 CANCEL CHARACTER (CCH) 95 0095 MESSAGE WAITING (MW) 96 0096 START OF GUARDED AREA (SPA) 97 0097 END OF GUARDED AREA (EPA) 98 0098 START OF STRING (SOS) 99 0099 SINGLE GRAPHIC CHARACTER INTRODUCER (SGCI) 9A 009a SINGLE CHARACTER INTRODUCER (SCI) 9B 009b CONTROL SEQUENCE INTRODUCER (CSI) 9C 009c STRING TERMINATOR (ST) 9D 009d OPERATING SYSTEM COMMAND (OSC) 9E 009e PRIVACY MESSAGE (PM) 9F 009f APPLICATION PROGRAM COMMAND (APC) A0 00a0 NO-BREAK SPACE A1 02bd MODIFIER LETTER REVERSED COMMA A2 02bc MODIFIER LETTER APOSTROPHE A3 00a3 POUND SIGN A4 ???? EMPTY A5 ???? EMPTY A6 00a6 BROKEN BAR A7 00a7 SECTION SIGN A8 00a8 DIAERESIS A9 00a9 COPYRIGHT SIGN AA ???? EMPTY AB 00ab LEFT-POINTING DOUBLE ANGLE QUOTATION MARK AC 00ac NOT SIGN AD 00ad SOFT HYPHEN AE ???? EMPTY AF 2015 HORIZONTAL BAR B0 00b0 DEGREE SIGN B1 00b1 PLUS-MINUS SIGN B2 00b2 SUPERSCRIPT TWO B3 00b3 SUPERSCRIPT THREE B4 0384 GREEK TONOS B5 0385 GREEK DIALYTIKA TONOS B6 0386 GREEK CAPITAL LETTER ALPHA WITH TONOS B7 00b7 MIDDLE DOT B8 0388 GREEK CAPITAL LETTER EPSILON WITH TONOS B9 0389 GREEK CAPITAL LETTER ETA WITH TONOS BA 038a GREEK CAPITAL LETTER IOTA WITH TONOS BB 00bb RIGHT-POINTING DOUBLE ANGLE QUOTATION MARK BC 038c GREEK CAPITAL LETTER OMICRON WITH TONOS BD 00bd VULGAR FRACTION ONE HALF BE 038e GREEK CAPITAL LETTER UPSILON WITH TONOS BF 038f GREEK CAPITAL LETTER OMEGA WITH TONOS C0 0390 GREEK SMALL LETTER IOTA WITH DIALYTIKA AND TONOS C1 0391 GREEK CAPITAL LETTER ALPHA C2 0392 GREEK CAPITAL LETTER BETA C3 0393 GREEK CAPITAL LETTER GAMMA C4 0394 GREEK CAPITAL LETTER DELTA C5 0395 GREEK CAPITAL LETTER EPSILON C6 0396 GREEK CAPITAL LETTER ZETA C7 0397 GREEK CAPITAL LETTER ETA C8 0398 GREEK CAPITAL LETTER THETA C9 0399 GREEK CAPITAL LETTER IOTA CA 039a GREEK CAPITAL LETTER KAPPA CB 039b GREEK CAPITAL LETTER LAMDA CC 039c GREEK CAPITAL LETTER MU CD 039d GREEK CAPITAL LETTER NU CE 039e GREEK CAPITAL LETTER XI CF 039f GREEK CAPITAL LETTER OMICRON D0 03a0 GREEK CAPITAL LETTER PI D1 03a1 GREEK CAPITAL LETTER RHO D2 ???? EMPTY D3 03a3 GREEK CAPITAL LETTER SIGMA D4 03a4 GREEK CAPITAL LETTER TAU D5 03a5 GREEK CAPITAL LETTER UPSILON D6 03a6 GREEK CAPITAL LETTER PHI D7 03a7 GREEK CAPITAL LETTER CHI D8 03a8 GREEK CAPITAL LETTER PSI D9 03a9 GREEK CAPITAL LETTER OMEGA DA 03aa GREEK CAPITAL LETTER IOTA WITH DIALYTIKA DB 03ab GREEK CAPITAL LETTER UPSILON WITH DIALYTIKA DC 03ac GREEK SMALL LETTER ALPHA WITH TONOS DD 03ad GREEK SMALL LETTER EPSILON WITH TONOS DE 03ae GREEK SMALL LETTER ETA WITH TONOS DF 03af GREEK SMALL LETTER IOTA WITH TONOS E0 03b0 GREEK SMALL LETTER UPSILON WITH DIALYTIKA AND TONOS E1 03b1 GREEK SMALL LETTER ALPHA E2 03b2 GREEK SMALL LETTER BETA E3 03b3 GREEK SMALL LETTER GAMMA E4 03b4 GREEK SMALL LETTER DELTA E5 03b5 GREEK SMALL LETTER EPSILON E6 03b6 GREEK SMALL LETTER ZETA E7 03b7 GREEK SMALL LETTER ETA E8 03b8 GREEK SMALL LETTER THETA E9 03b9 GREEK SMALL LETTER IOTA EA 03ba GREEK SMALL LETTER KAPPA EB 03bb GREEK SMALL LETTER LAMDA EC 03bc GREEK SMALL LETTER MU ED 03bd GREEK SMALL LETTER NU EE 03be GREEK SMALL LETTER XI EF 03bf GREEK SMALL LETTER OMICRON F0 03c0 GREEK SMALL LETTER PI F1 03c1 GREEK SMALL LETTER RHO F2 03c2 GREEK SMALL LETTER FINAL SIGMA F3 03c3 GREEK SMALL LETTER SIGMA F4 03c4 GREEK SMALL LETTER TAU F5 03c5 GREEK SMALL LETTER UPSILON F6 03c6 GREEK SMALL LETTER PHI F7 03c7 GREEK SMALL LETTER CHI F8 03c8 GREEK SMALL LETTER PSI F9 03c9 GREEK SMALL LETTER OMEGA FA 03ca GREEK SMALL LETTER IOTA WITH DIALYTIKA FB 03cb GREEK SMALL LETTER UPSILON WITH DIALYTIKA FC 03cc GREEK SMALL LETTER OMICRON WITH TONOS FD 03cd GREEK SMALL LETTER UPSILON WITH TONOS FE 03ce GREEK SMALL LETTER OMEGA WITH TONOS FF ???? EMPTY cyrus-imapd-2.5.10/lib/charset/koi8-r.t0000644000175000017500000002255513001236020014446 00000000000000# # Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. # # Redistribution and use in source and binary forms, with or without # modification, are permitted provided that the following conditions # are met: # # 1. Redistributions of source code must retain the above copyright # notice, this list of conditions and the following disclaimer. # # 2. Redistributions in binary form must reproduce the above copyright # notice, this list of conditions and the following disclaimer in # the documentation and/or other materials provided with the # distribution. # # 3. The name "Carnegie Mellon University" must not be used to # endorse or promote products derived from this software without # prior written permission. For permission or any legal # details, please contact # Carnegie Mellon University # Center for Technology Transfer and Enterprise Creation # 4615 Forbes Avenue # Suite 302 # Pittsburgh, PA 15213 # (412) 268-7393, fax: (412) 268-7395 # innovation@andrew.cmu.edu # # 4. Redistributions of any form whatsoever must retain the following # acknowledgment: # "This product includes software developed by Computing Services # at Carnegie Mellon University (http://www.cmu.edu/computing/)." # # CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO # THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY # AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE # FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES # WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN # AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING # OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. 0 0000 NULL (NUL) 1 0001 START OF HEADING (SOH) 2 0002 START OF TEXT (STX) 3 0003 END OF TEXT (ETX) 4 0004 END OF TRANSMISSION (EOT) 5 0005 ENQUIRY (ENQ) 6 0006 ACKNOWLEDGE (ACK) 7 0007 BELL (BEL) 8 0008 BACKSPACE (BS) 9 0009 CHARACTER TABULATION (HT) A 000a LINE FEED (LF) B 000b LINE TABULATION (VT) C 000c FORM FEED (FF) D 000d CARRIAGE RETURN (CR) E 000e SHIFT OUT (SO) F 000f SHIFT IN (SI) 10 0010 DATALINK ESCAPE (DLE) 11 0011 DEVICE CONTROL ONE (DC1) 12 0012 DEVICE CONTROL TWO (DC2) 13 0013 DEVICE CONTROL THREE (DC3) 14 0014 DEVICE CONTROL FOUR (DC4) 15 0015 NEGATIVE ACKNOWLEDGE (NAK) 16 0016 SYNCRONOUS IDLE (SYN) 17 0017 END OF TRANSMISSION BLOCK (ETB) 18 0018 CANCEL (CAN) 19 0019 END OF MEDIUM (EM) 1A 001a SUBSTITUTE (SUB) 1B 001b ESCAPE (ESC) 1C 001c FILE SEPARATOR (IS4) 1D 001d GROUP SEPARATOR (IS3) 1E 001e RECORD SEPARATOR (IS2) 1F 001f UNIT SEPARATOR (IS1) 20 0020 SPACE 21 0021 EXCLAMATION MARK 22 0022 QUOTATION MARK 23 0023 NUMBER SIGN 24 0024 DOLLAR SIGN 25 0025 PERCENT SIGN 26 0026 AMPERSAND 27 0027 APOSTROPHE 28 0028 LEFT PARENTHESIS 29 0029 RIGHT PARENTHESIS 2A 002a ASTERISK 2B 002b PLUS SIGN 2C 002c COMMA 2D 002d HYPHEN-MINUS 2E 002e FULL STOP 2F 002f SOLIDUS 30 0030 DIGIT ZERO 31 0031 DIGIT ONE 32 0032 DIGIT TWO 33 0033 DIGIT THREE 34 0034 DIGIT FOUR 35 0035 DIGIT FIVE 36 0036 DIGIT SIX 37 0037 DIGIT SEVEN 38 0038 DIGIT EIGHT 39 0039 DIGIT NINE 3A 003a COLON 3B 003b SEMICOLON 3C 003c LESS-THAN SIGN 3D 003d EQUALS SIGN 3E 003e GREATER-THAN SIGN 3F 003f QUESTION MARK 40 0040 COMMERCIAL AT 41 0041 LATIN CAPITAL LETTER A 42 0042 LATIN CAPITAL LETTER B 43 0043 LATIN CAPITAL LETTER C 44 0044 LATIN CAPITAL LETTER D 45 0045 LATIN CAPITAL LETTER E 46 0046 LATIN CAPITAL LETTER F 47 0047 LATIN CAPITAL LETTER G 48 0048 LATIN CAPITAL LETTER H 49 0049 LATIN CAPITAL LETTER I 4A 004a LATIN CAPITAL LETTER J 4B 004b LATIN CAPITAL LETTER K 4C 004c LATIN CAPITAL LETTER L 4D 004d LATIN CAPITAL LETTER M 4E 004e LATIN CAPITAL LETTER N 4F 004f LATIN CAPITAL LETTER O 50 0050 LATIN CAPITAL LETTER P 51 0051 LATIN CAPITAL LETTER Q 52 0052 LATIN CAPITAL LETTER R 53 0053 LATIN CAPITAL LETTER S 54 0054 LATIN CAPITAL LETTER T 55 0055 LATIN CAPITAL LETTER U 56 0056 LATIN CAPITAL LETTER V 57 0057 LATIN CAPITAL LETTER W 58 0058 LATIN CAPITAL LETTER X 59 0059 LATIN CAPITAL LETTER Y 5A 005a LATIN CAPITAL LETTER Z 5B 005b LEFT SQUARE BRACKET 5C 005c REVERSE SOLIDUS 5D 005d RIGHT SQUARE BRACKET 5E 005e CIRCUMFLEX ACCENT 5F 005f LOW LINE 60 0060 GRAVE ACCENT 61 0061 LATIN SMALL LETTER A 62 0062 LATIN SMALL LETTER B 63 0063 LATIN SMALL LETTER C 64 0064 LATIN SMALL LETTER D 65 0065 LATIN SMALL LETTER E 66 0066 LATIN SMALL LETTER F 67 0067 LATIN SMALL LETTER G 68 0068 LATIN SMALL LETTER H 69 0069 LATIN SMALL LETTER I 6A 006a LATIN SMALL LETTER J 6B 006b LATIN SMALL LETTER K 6C 006c LATIN SMALL LETTER L 6D 006d LATIN SMALL LETTER M 6E 006e LATIN SMALL LETTER N 6F 006f LATIN SMALL LETTER O 70 0070 LATIN SMALL LETTER P 71 0071 LATIN SMALL LETTER Q 72 0072 LATIN SMALL LETTER R 73 0073 LATIN SMALL LETTER S 74 0074 LATIN SMALL LETTER T 75 0075 LATIN SMALL LETTER U 76 0076 LATIN SMALL LETTER V 77 0077 LATIN SMALL LETTER W 78 0078 LATIN SMALL LETTER X 79 0079 LATIN SMALL LETTER Y 7A 007a LATIN SMALL LETTER Z 7B 007b LEFT CURLY BRACKET 7C 007c VERTICAL LINE 7D 007d RIGHT CURLY BRACKET 7E 007e TILDE 7F 007f DELETE (DEL) 80 2500 FORMS LIGHT HORIZONTAL 81 2502 FORMS LIGHT VERTICAL 82 250c FORMS LIGHT DOWN AND RIGHT 83 2510 FORMS LIGHT DOWN AND LEFT 84 2514 FORMS LIGHT UP 85 2518 FORMS LIGHT UP AND LEFT 86 251c FORMS LIGHT VERTICAL AND RIGHT 87 2524 FORMS LIGHT VERTICAL AND LEFT 88 252c FORMS LIGHT DOWN AND HORIZONTAL 89 2534 FORMS LIGHT UP AND HORIZONTAL 8A 253c FORMS LIGHT VERTICAL AND HORIZONTAL 8B 2580 UPPER HALF BLOCK 8C 2584 LOWER HALF BLOCK 8D 2588 FULL BLOCK 8E 258c LEFT HALF BLOCK 8F 2590 RIGHT HALF BLOCK 90 2591 LIGHT SHADE 91 2592 MEDIUM SHADE 92 2593 DARK SHADE 93 2320 TOP HALF INTEGRAL 94 25a0 BLACK SMALL SQUARE 95 2219 BULLET OPERATOR 96 221a SQUARE ROOT 97 2248 ALMOST EQUAL TO 98 2264 LESS THAN OR EQUAL TO 99 2265 GREATER THAN OR EQUAL TO 9A 00a0 NON-BREAKING SPACE 9B 2321 BOTTOM HALF INTEGRAL 9C 00b0 DEGREE SIGN 9D 00b2 SUPERSCRIPT DIGIT TWO 9E 00b7 MIDDLE DOT 9F 00f7 DIVISION SIGN A0 2550 FORMS DOUBLE HORIZONTAL A1 2551 FORMS DOUBLE VERTICAL A2 2552 FORMS DOWN SINGLE AND RIGHT DOUBLE A3 0451 CYRILLIC SMALL LETTER IO A4 2553 FORMS DOWN DOUBLE AND RIGHT SINGLE A5 2554 FORMS DOUBLE DOWN AND RIGHT A6 2555 FORMS DOWN SINGLE AND LEFT DOUBLE A7 2556 FORMS DOWN DOUBLE AND LEFT SINGLE A8 2557 FORMS DOUBLE DOWN AND LEFT A9 2558 FORMS UP SINGLE AND RIGHT DOUBLE AA 2559 FORMS UP DOUBLE AND RIGHT SINGLE AB 255a FORMS DOUBLE UP AND RIGHT AC 255b FORMS UP SINGLE AND LEFT DOUBLE AD 255c FORMS UP DOUBLE AND LEFT SINGLE AE 255d FORMS DOUBLE UP AND LEFT AF 255e FORMS VERTICAL SINGLE AND RIGHT DOUBLE B0 255f FORMS VERTICAL DOUBLE AND RIGHT SINGLE B1 2560 FORMS DOUBLE VERTICAL AND RIGHT B2 2561 FORMS VERTICAL SINGLE AND LEFT DOUBLE B3 0401 CYRILLIC CAPITAL LETTER IO B4 2562 FORMS VERTICAL DOUBLE AND LEFT SINGLE B5 2563 FORMS DOUBLE VERTICAL AND LEFT B6 2564 FORMS DOWN SINGLE AND HORIZONTAL DOUBLE B7 2565 FORMS DOWN DOUBLE AND HORIZONTAL SINGLE B8 2566 FORMS DOUBLE DOWN AND HORIZONTAL B9 2567 FORMS UP SINGLE AND HORIZONTAL DOUBLE BA 2568 FORMS UP DOUBLE AND HORIZONTAL SINGLE BB 2569 FORMS DOUBLE UP AND HORIZONTAL BC 256a FORMS VERTICAL SINGLE AND HORIZONTAL DOUBLE BD 256b FORMS VERTICAL DOUBLE AND HORIZONTAL SINGLE BE 256c FORMS DOUBLE VERTICAL AND HORIZONTAL BF 00a9 COPYRIGHT SIGN C0 044e CYRILLIC SMALL LETTER IU C1 0430 CYRILLIC SMALL LETTER A C2 0431 CYRILLIC SMALL LETTER BE C3 0446 CYRILLIC SMALL LETTER TSE C4 0434 CYRILLIC SMALL LETTER DE C5 0435 CYRILLIC SMALL LETTER IE C6 0444 CYRILLIC SMALL LETTER EF C7 0433 CYRILLIC SMALL LETTER GE C8 0445 CYRILLIC SMALL LETTER KHA C9 0438 CYRILLIC SMALL LETTER II CA 0439 CYRILLIC SMALL LETTER SHORT II CB 043a CYRILLIC SMALL LETTER KA CC 043b CYRILLIC SMALL LETTER EL CD 043c CYRILLIC SMALL LETTER EM CE 043d CYRILLIC SMALL LETTER EN CF 043e CYRILLIC SMALL LETTER O D0 043f CYRILLIC SMALL LETTER PE D1 044f CYRILLIC SMALL LETTER IA D2 0440 CYRILLIC SMALL LETTER ER D3 0441 CYRILLIC SMALL LETTER ES D4 0442 CYRILLIC SMALL LETTER TE D5 0443 CYRILLIC SMALL LETTER U D6 0436 CYRILLIC SMALL LETTER ZHE D7 0432 CYRILLIC SMALL LETTER VE D8 044c CYRILLIC SMALL LETTER SOFT SIGN D9 044b CYRILLIC SMALL LETTER YERI DA 0437 CYRILLIC SMALL LETTER ZE DB 0448 CYRILLIC SMALL LETTER SHA DC 044d CYRILLIC SMALL LETTER REVERSED E DD 0449 CYRILLIC SMALL LETTER SHCHA DE 0447 CYRILLIC SMALL LETTER CHE DF 044a CYRILLIC SMALL LETTER HARD SIGN E0 042e CYRILLIC CAPITAL LETTER IU E1 0410 CYRILLIC CAPITAL LETTER A E2 0411 CYRILLIC CAPITAL LETTER BE E3 0426 CYRILLIC CAPITAL LETTER TSE E4 0414 CYRILLIC CAPITAL LETTER DE E5 0415 CYRILLIC CAPITAL LETTER IE E6 0424 CYRILLIC CAPITAL LETTER EF E7 0413 CYRILLIC CAPITAL LETTER GE E8 0425 CYRILLIC CAPITAL LETTER KHA E9 0418 CYRILLIC CAPITAL LETTER II EA 0419 CYRILLIC CAPITAL LETTER SHORT II EB 041a CYRILLIC CAPITAL LETTER KA EC 041b CYRILLIC CAPITAL LETTER EL ED 041c CYRILLIC CAPITAL LETTER EM EE 041d CYRILLIC CAPITAL LETTER EN EF 041e CYRILLIC CAPITAL LETTER O F0 041f CYRILLIC CAPITAL LETTER PE F1 042f CYRILLIC CAPITAL LETTER IA F2 0420 CYRILLIC CAPITAL LETTER ER F3 0421 CYRILLIC CAPITAL LETTER ES F4 0422 CYRILLIC CAPITAL LETTER TE F5 0423 CYRILLIC CAPITAL LETTER U F6 0416 CYRILLIC CAPITAL LETTER ZHE F7 0412 CYRILLIC CAPITAL LETTER VE F8 042c CYRILLIC CAPITAL LETTER SOFT SIGN F9 042b CYRILLIC CAPITAL LETTER YERI FA 0417 CYRILLIC CAPITAL LETTER ZE FB 0428 CYRILLIC CAPITAL LETTER SHA FC 042d CYRILLIC CAPITAL LETTER REVERSED E FD 0429 CYRILLIC CAPITAL LETTER SHCHA FE 0427 CYRILLIC CAPITAL LETTER CHE FF 042a CYRILLIC CAPITAL LETTER HARD SIGN cyrus-imapd-2.5.10/lib/charset/iso-8859-5.t0000644000175000017500000002307513001236020014702 00000000000000# # Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. # # Redistribution and use in source and binary forms, with or without # modification, are permitted provided that the following conditions # are met: # # 1. Redistributions of source code must retain the above copyright # notice, this list of conditions and the following disclaimer. # # 2. Redistributions in binary form must reproduce the above copyright # notice, this list of conditions and the following disclaimer in # the documentation and/or other materials provided with the # distribution. # # 3. The name "Carnegie Mellon University" must not be used to # endorse or promote products derived from this software without # prior written permission. For permission or any legal # details, please contact # Carnegie Mellon University # Center for Technology Transfer and Enterprise Creation # 4615 Forbes Avenue # Suite 302 # Pittsburgh, PA 15213 # (412) 268-7393, fax: (412) 268-7395 # innovation@andrew.cmu.edu # # 4. Redistributions of any form whatsoever must retain the following # acknowledgment: # "This product includes software developed by Computing Services # at Carnegie Mellon University (http://www.cmu.edu/computing/)." # # CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO # THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY # AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE # FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES # WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN # AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING # OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. 0 0000 NULL (NUL) 1 0001 START OF HEADING (SOH) 2 0002 START OF TEXT (STX) 3 0003 END OF TEXT (ETX) 4 0004 END OF TRANSMISSION (EOT) 5 0005 ENQUIRY (ENQ) 6 0006 ACKNOWLEDGE (ACK) 7 0007 BELL (BEL) 8 0008 BACKSPACE (BS) 9 0009 CHARACTER TABULATION (HT) A 000a LINE FEED (LF) B 000b LINE TABULATION (VT) C 000c FORM FEED (FF) D 000d CARRIAGE RETURN (CR) E 000e SHIFT OUT (SO) F 000f SHIFT IN (SI) 10 0010 DATALINK ESCAPE (DLE) 11 0011 DEVICE CONTROL ONE (DC1) 12 0012 DEVICE CONTROL TWO (DC2) 13 0013 DEVICE CONTROL THREE (DC3) 14 0014 DEVICE CONTROL FOUR (DC4) 15 0015 NEGATIVE ACKNOWLEDGE (NAK) 16 0016 SYNCRONOUS IDLE (SYN) 17 0017 END OF TRANSMISSION BLOCK (ETB) 18 0018 CANCEL (CAN) 19 0019 END OF MEDIUM (EM) 1A 001a SUBSTITUTE (SUB) 1B 001b ESCAPE (ESC) 1C 001c FILE SEPARATOR (IS4) 1D 001d GROUP SEPARATOR (IS3) 1E 001e RECORD SEPARATOR (IS2) 1F 001f UNIT SEPARATOR (IS1) 20 0020 SPACE 21 0021 EXCLAMATION MARK 22 0022 QUOTATION MARK 23 0023 NUMBER SIGN 24 0024 DOLLAR SIGN 25 0025 PERCENT SIGN 26 0026 AMPERSAND 27 0027 APOSTROPHE 28 0028 LEFT PARENTHESIS 29 0029 RIGHT PARENTHESIS 2A 002a ASTERISK 2B 002b PLUS SIGN 2C 002c COMMA 2D 002d HYPHEN-MINUS 2E 002e FULL STOP 2F 002f SOLIDUS 30 0030 DIGIT ZERO 31 0031 DIGIT ONE 32 0032 DIGIT TWO 33 0033 DIGIT THREE 34 0034 DIGIT FOUR 35 0035 DIGIT FIVE 36 0036 DIGIT SIX 37 0037 DIGIT SEVEN 38 0038 DIGIT EIGHT 39 0039 DIGIT NINE 3A 003a COLON 3B 003b SEMICOLON 3C 003c LESS-THAN SIGN 3D 003d EQUALS SIGN 3E 003e GREATER-THAN SIGN 3F 003f QUESTION MARK 40 0040 COMMERCIAL AT 41 0041 LATIN CAPITAL LETTER A 42 0042 LATIN CAPITAL LETTER B 43 0043 LATIN CAPITAL LETTER C 44 0044 LATIN CAPITAL LETTER D 45 0045 LATIN CAPITAL LETTER E 46 0046 LATIN CAPITAL LETTER F 47 0047 LATIN CAPITAL LETTER G 48 0048 LATIN CAPITAL LETTER H 49 0049 LATIN CAPITAL LETTER I 4A 004a LATIN CAPITAL LETTER J 4B 004b LATIN CAPITAL LETTER K 4C 004c LATIN CAPITAL LETTER L 4D 004d LATIN CAPITAL LETTER M 4E 004e LATIN CAPITAL LETTER N 4F 004f LATIN CAPITAL LETTER O 50 0050 LATIN CAPITAL LETTER P 51 0051 LATIN CAPITAL LETTER Q 52 0052 LATIN CAPITAL LETTER R 53 0053 LATIN CAPITAL LETTER S 54 0054 LATIN CAPITAL LETTER T 55 0055 LATIN CAPITAL LETTER U 56 0056 LATIN CAPITAL LETTER V 57 0057 LATIN CAPITAL LETTER W 58 0058 LATIN CAPITAL LETTER X 59 0059 LATIN CAPITAL LETTER Y 5A 005a LATIN CAPITAL LETTER Z 5B 005b LEFT SQUARE BRACKET 5C 005c REVERSE SOLIDUS 5D 005d RIGHT SQUARE BRACKET 5E 005e CIRCUMFLEX ACCENT 5F 005f LOW LINE 60 0060 GRAVE ACCENT 61 0061 LATIN SMALL LETTER A 62 0062 LATIN SMALL LETTER B 63 0063 LATIN SMALL LETTER C 64 0064 LATIN SMALL LETTER D 65 0065 LATIN SMALL LETTER E 66 0066 LATIN SMALL LETTER F 67 0067 LATIN SMALL LETTER G 68 0068 LATIN SMALL LETTER H 69 0069 LATIN SMALL LETTER I 6A 006a LATIN SMALL LETTER J 6B 006b LATIN SMALL LETTER K 6C 006c LATIN SMALL LETTER L 6D 006d LATIN SMALL LETTER M 6E 006e LATIN SMALL LETTER N 6F 006f LATIN SMALL LETTER O 70 0070 LATIN SMALL LETTER P 71 0071 LATIN SMALL LETTER Q 72 0072 LATIN SMALL LETTER R 73 0073 LATIN SMALL LETTER S 74 0074 LATIN SMALL LETTER T 75 0075 LATIN SMALL LETTER U 76 0076 LATIN SMALL LETTER V 77 0077 LATIN SMALL LETTER W 78 0078 LATIN SMALL LETTER X 79 0079 LATIN SMALL LETTER Y 7A 007a LATIN SMALL LETTER Z 7B 007b LEFT CURLY BRACKET 7C 007c VERTICAL LINE 7D 007d RIGHT CURLY BRACKET 7E 007e TILDE 7F 007f DELETE (DEL) 80 0080 PADDING CHARACTER (PAD) 81 0081 HIGH OCTET PRESET (HOP) 82 0082 BREAK PERMITTED HERE (BPH) 83 0083 NO BREAK HERE (NBH) 84 0084 INDEX (IND) 85 0085 NEXT LINE (NEL) 86 0086 START OF SELECTED AREA (SSA) 87 0087 END OF SELECTED AREA (ESA) 88 0088 CHARACTER TABULATION SET (HTS) 89 0089 CHARACTER TABULATION WITH JUSTIFICATION (HTJ) 8A 008a LINE TABULATION SET (VTS) 8B 008b PARTIAL LINE FORWARD (PLD) 8C 008c PARTIAL LINE BACKWARD (PLU) 8D 008d REVERSE LINE FEED (RI) 8E 008e SINGLE-SHIFT TWO (SS2) 8F 008f SINGLE-SHIFT THREE (SS3) 90 0090 DEVICE CONTROL STRING (DCS) 91 0091 PRIVATE USE ONE (PU1) 92 0092 PRIVATE USE TWO (PU2) 93 0093 SET TRANSMIT STATE (STS) 94 0094 CANCEL CHARACTER (CCH) 95 0095 MESSAGE WAITING (MW) 96 0096 START OF GUARDED AREA (SPA) 97 0097 END OF GUARDED AREA (EPA) 98 0098 START OF STRING (SOS) 99 0099 SINGLE GRAPHIC CHARACTER INTRODUCER (SGCI) 9A 009a SINGLE CHARACTER INTRODUCER (SCI) 9B 009b CONTROL SEQUENCE INTRODUCER (CSI) 9C 009c STRING TERMINATOR (ST) 9D 009d OPERATING SYSTEM COMMAND (OSC) 9E 009e PRIVACY MESSAGE (PM) 9F 009f APPLICATION PROGRAM COMMAND (APC) A0 00a0 NO-BREAK SPACE A1 0401 CYRILLIC CAPITAL LETTER IO A2 0402 CYRILLIC CAPITAL LETTER DJE (Serbocroatian) A3 0403 CYRILLIC CAPITAL LETTER GJE (Macedonian) A4 0404 CYRILLIC CAPITAL LETTER UKRAINIAN IE A5 0405 CYRILLIC CAPITAL LETTER DZE (Macedonian) A6 0406 CYRILLIC CAPITAL LETTER BYELORUSSIAN-UKRAINIAN I A7 0407 CYRILLIC CAPITAL LETTER YI (Ukrainian) A8 0408 CYRILLIC CAPITAL LETTER JE A9 0409 CYRILLIC CAPITAL LETTER LJE AA 040a CYRILLIC CAPITAL LETTER NJE AB 040b CYRILLIC CAPITAL LETTER TSHE (Serbocroatian) AC 040c CYRILLIC CAPITAL LETTER KJE (Macedonian) AD 00ad SOFT HYPHEN AE 040e CYRILLIC CAPITAL LETTER SHORT U (Byelorussian) AF 040f CYRILLIC CAPITAL LETTER DZHE B0 0410 CYRILLIC CAPITAL LETTER A B1 0411 CYRILLIC CAPITAL LETTER BE B2 0412 CYRILLIC CAPITAL LETTER VE B3 0413 CYRILLIC CAPITAL LETTER GHE B4 0414 CYRILLIC CAPITAL LETTER DE B5 0415 CYRILLIC CAPITAL LETTER IE B6 0416 CYRILLIC CAPITAL LETTER ZHE B7 0417 CYRILLIC CAPITAL LETTER ZE B8 0418 CYRILLIC CAPITAL LETTER I B9 0419 CYRILLIC CAPITAL LETTER SHORT I BA 041a CYRILLIC CAPITAL LETTER KA BB 041b CYRILLIC CAPITAL LETTER EL BC 041c CYRILLIC CAPITAL LETTER EM BD 041d CYRILLIC CAPITAL LETTER EN BE 041e CYRILLIC CAPITAL LETTER O BF 041f CYRILLIC CAPITAL LETTER PE C0 0420 CYRILLIC CAPITAL LETTER ER C1 0421 CYRILLIC CAPITAL LETTER ES C2 0422 CYRILLIC CAPITAL LETTER TE C3 0423 CYRILLIC CAPITAL LETTER U C4 0424 CYRILLIC CAPITAL LETTER EF C5 0425 CYRILLIC CAPITAL LETTER HA C6 0426 CYRILLIC CAPITAL LETTER TSE C7 0427 CYRILLIC CAPITAL LETTER CHE C8 0428 CYRILLIC CAPITAL LETTER SHA C9 0429 CYRILLIC CAPITAL LETTER SHCHA CA 042a CYRILLIC CAPITAL LETTER HARD SIGN CB 042b CYRILLIC CAPITAL LETTER YERU CC 042c CYRILLIC CAPITAL LETTER SOFT SIGN CD 042d CYRILLIC CAPITAL LETTER E CE 042e CYRILLIC CAPITAL LETTER YU CF 042f CYRILLIC CAPITAL LETTER YA D0 0430 CYRILLIC SMALL LETTER A D1 0431 CYRILLIC SMALL LETTER BE D2 0432 CYRILLIC SMALL LETTER VE D3 0433 CYRILLIC SMALL LETTER GHE D4 0434 CYRILLIC SMALL LETTER DE D5 0435 CYRILLIC SMALL LETTER IE D6 0436 CYRILLIC SMALL LETTER ZHE D7 0437 CYRILLIC SMALL LETTER ZE D8 0438 CYRILLIC SMALL LETTER I D9 0439 CYRILLIC SMALL LETTER SHORT I DA 043a CYRILLIC SMALL LETTER KA DB 043b CYRILLIC SMALL LETTER EL DC 043c CYRILLIC SMALL LETTER EM DD 043d CYRILLIC SMALL LETTER EN DE 043e CYRILLIC SMALL LETTER O DF 043f CYRILLIC SMALL LETTER PE E0 0440 CYRILLIC SMALL LETTER ER E1 0441 CYRILLIC SMALL LETTER ES E2 0442 CYRILLIC SMALL LETTER TE E3 0443 CYRILLIC SMALL LETTER U E4 0444 CYRILLIC SMALL LETTER EF E5 0445 CYRILLIC SMALL LETTER HA E6 0446 CYRILLIC SMALL LETTER TSE E7 0447 CYRILLIC SMALL LETTER CHE E8 0448 CYRILLIC SMALL LETTER SHA E9 0449 CYRILLIC SMALL LETTER SHCHA EA 044a CYRILLIC SMALL LETTER HARD SIGN EB 044b CYRILLIC SMALL LETTER YERU EC 044c CYRILLIC SMALL LETTER SOFT SIGN ED 044d CYRILLIC SMALL LETTER E EE 044e CYRILLIC SMALL LETTER YU EF 044f CYRILLIC SMALL LETTER YA F0 2116 NUMERO SIGN F1 0451 CYRILLIC SMALL LETTER IO F2 0452 CYRILLIC SMALL LETTER DJE (Serbocroatian) F3 0453 CYRILLIC SMALL LETTER GJE (Macedonian) F4 0454 CYRILLIC SMALL LETTER UKRAINIAN IE F5 0455 CYRILLIC SMALL LETTER DZE (Macedonian) F6 0456 CYRILLIC SMALL LETTER BYELORUSSIAN-UKRAINIAN I F7 0457 CYRILLIC SMALL LETTER YI (Ukrainian) F8 0458 CYRILLIC SMALL LETTER JE F9 0459 CYRILLIC SMALL LETTER LJE FA 045a CYRILLIC SMALL LETTER NJE FB 045b CYRILLIC SMALL LETTER TSHE (Serbocroatian) FC 045c CYRILLIC SMALL LETTER KJE (Macedonian) FD 00a7 SECTION SIGN FE 045e CYRILLIC SMALL LETTER SHORT U (Byelorussian) FF 045f CYRILLIC SMALL LETTER DZHE cyrus-imapd-2.5.10/lib/charset/iso-8859-11.t0000644000175000017500000002006413001236020014752 00000000000000# # Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. # # Redistribution and use in source and binary forms, with or without # modification, are permitted provided that the following conditions # are met: # # 1. Redistributions of source code must retain the above copyright # notice, this list of conditions and the following disclaimer. # # 2. Redistributions in binary form must reproduce the above copyright # notice, this list of conditions and the following disclaimer in # the documentation and/or other materials provided with the # distribution. # # 3. The name "Carnegie Mellon University" must not be used to # endorse or promote products derived from this software without # prior written permission. For permission or any legal # details, please contact # Carnegie Mellon University # Center for Technology Transfer and Enterprise Creation # 4615 Forbes Avenue # Suite 302 # Pittsburgh, PA 15213 # (412) 268-7393, fax: (412) 268-7395 # innovation@andrew.cmu.edu # # 4. Redistributions of any form whatsoever must retain the following # acknowledgment: # "This product includes software developed by Computing Services # at Carnegie Mellon University (http://www.cmu.edu/computing/)." # # CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO # THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY # AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE # FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES # WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN # AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING # OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. 00 0000 NULL 01 0001 START OF HEADING 02 0002 START OF TEXT 03 0003 END OF TEXT 04 0004 END OF TRANSMISSION 05 0005 ENQUIRY 06 0006 ACKNOWLEDGE 07 0007 BELL 08 0008 BACKSPACE 09 0009 HORIZONTAL TABULATION 0A 000A LINE FEED 0B 000B VERTICAL TABULATION 0C 000C FORM FEED 0D 000D CARRIAGE RETURN 0E 000E SHIFT OUT 0F 000F SHIFT IN 10 0010 DATA LINK ESCAPE 11 0011 DEVICE CONTROL ONE 12 0012 DEVICE CONTROL TWO 13 0013 DEVICE CONTROL THREE 14 0014 DEVICE CONTROL FOUR 15 0015 NEGATIVE ACKNOWLEDGE 16 0016 SYNCHRONOUS IDLE 17 0017 END OF TRANSMISSION BLOCK 18 0018 CANCEL 19 0019 END OF MEDIUM 1A 001A SUBSTITUTE 1B 001B ESCAPE 1C 001C FILE SEPARATOR 1D 001D GROUP SEPARATOR 1E 001E RECORD SEPARATOR 1F 001F UNIT SEPARATOR 20 0020 SPACE 21 0021 EXCLAMATION MARK 22 0022 QUOTATION MARK 23 0023 NUMBER SIGN 24 0024 DOLLAR SIGN 25 0025 PERCENT SIGN 26 0026 AMPERSAND 27 0027 APOSTROPHE 28 0028 LEFT PARENTHESIS 29 0029 RIGHT PARENTHESIS 2A 002A ASTERISK 2B 002B PLUS SIGN 2C 002C COMMA 2D 002D HYPHEN-MINUS 2E 002E FULL STOP 2F 002F SOLIDUS 30 0030 DIGIT ZERO 31 0031 DIGIT ONE 32 0032 DIGIT TWO 33 0033 DIGIT THREE 34 0034 DIGIT FOUR 35 0035 DIGIT FIVE 36 0036 DIGIT SIX 37 0037 DIGIT SEVEN 38 0038 DIGIT EIGHT 39 0039 DIGIT NINE 3A 003A COLON 3B 003B SEMICOLON 3C 003C LESS-THAN SIGN 3D 003D EQUALS SIGN 3E 003E GREATER-THAN SIGN 3F 003F QUESTION MARK 40 0040 COMMERCIAL AT 41 0041 LATIN CAPITAL LETTER A 42 0042 LATIN CAPITAL LETTER B 43 0043 LATIN CAPITAL LETTER C 44 0044 LATIN CAPITAL LETTER D 45 0045 LATIN CAPITAL LETTER E 46 0046 LATIN CAPITAL LETTER F 47 0047 LATIN CAPITAL LETTER G 48 0048 LATIN CAPITAL LETTER H 49 0049 LATIN CAPITAL LETTER I 4A 004A LATIN CAPITAL LETTER J 4B 004B LATIN CAPITAL LETTER K 4C 004C LATIN CAPITAL LETTER L 4D 004D LATIN CAPITAL LETTER M 4E 004E LATIN CAPITAL LETTER N 4F 004F LATIN CAPITAL LETTER O 50 0050 LATIN CAPITAL LETTER P 51 0051 LATIN CAPITAL LETTER Q 52 0052 LATIN CAPITAL LETTER R 53 0053 LATIN CAPITAL LETTER S 54 0054 LATIN CAPITAL LETTER T 55 0055 LATIN CAPITAL LETTER U 56 0056 LATIN CAPITAL LETTER V 57 0057 LATIN CAPITAL LETTER W 58 0058 LATIN CAPITAL LETTER X 59 0059 LATIN CAPITAL LETTER Y 5A 005A LATIN CAPITAL LETTER Z 5B 005B LEFT SQUARE BRACKET 5C 005C REVERSE SOLIDUS 5D 005D RIGHT SQUARE BRACKET 5E 005E CIRCUMFLEX ACCENT 5F 005F LOW LINE 60 0060 GRAVE ACCENT 61 0061 LATIN SMALL LETTER A 62 0062 LATIN SMALL LETTER B 63 0063 LATIN SMALL LETTER C 64 0064 LATIN SMALL LETTER D 65 0065 LATIN SMALL LETTER E 66 0066 LATIN SMALL LETTER F 67 0067 LATIN SMALL LETTER G 68 0068 LATIN SMALL LETTER H 69 0069 LATIN SMALL LETTER I 6A 006A LATIN SMALL LETTER J 6B 006B LATIN SMALL LETTER K 6C 006C LATIN SMALL LETTER L 6D 006D LATIN SMALL LETTER M 6E 006E LATIN SMALL LETTER N 6F 006F LATIN SMALL LETTER O 70 0070 LATIN SMALL LETTER P 71 0071 LATIN SMALL LETTER Q 72 0072 LATIN SMALL LETTER R 73 0073 LATIN SMALL LETTER S 74 0074 LATIN SMALL LETTER T 75 0075 LATIN SMALL LETTER U 76 0076 LATIN SMALL LETTER V 77 0077 LATIN SMALL LETTER W 78 0078 LATIN SMALL LETTER X 79 0079 LATIN SMALL LETTER Y 7A 007A LATIN SMALL LETTER Z 7B 007B LEFT CURLY BRACKET 7C 007C VERTICAL LINE 7D 007D RIGHT CURLY BRACKET 7E 007E TILDE 7F 007F DELETE 80 0080 81 0081 82 0082 83 0083 84 0084 85 0085 86 0086 87 0087 88 0088 89 0089 8A 008A 8B 008B 8C 008C 8D 008D 8E 008E 8F 008F 90 0090 91 0091 92 0092 93 0093 94 0094 95 0095 96 0096 97 0097 98 0098 99 0099 9A 009A 9B 009B 9C 009C 9D 009D 9E 009E 9F 009F A0 00A0 NO-BREAK SPACE A1 0E01 THAI CHARACTER KO KAI A2 0E02 THAI CHARACTER KHO KHAI A3 0E03 THAI CHARACTER KHO KHUAT A4 0E04 THAI CHARACTER KHO KHWAI A5 0E05 THAI CHARACTER KHO KHON A6 0E06 THAI CHARACTER KHO RAKHANG A7 0E07 THAI CHARACTER NGO NGU A8 0E08 THAI CHARACTER CHO CHAN A9 0E09 THAI CHARACTER CHO CHING AA 0E0A THAI CHARACTER CHO CHANG AB 0E0B THAI CHARACTER SO SO AC 0E0C THAI CHARACTER CHO CHOE AD 0E0D THAI CHARACTER YO YING AE 0E0E THAI CHARACTER DO CHADA AF 0E0F THAI CHARACTER TO PATAK B0 0E10 THAI CHARACTER THO THAN B1 0E11 THAI CHARACTER THO NANGMONTHO B2 0E12 THAI CHARACTER THO PHUTHAO B3 0E13 THAI CHARACTER NO NEN B4 0E14 THAI CHARACTER DO DEK B5 0E15 THAI CHARACTER TO TAO B6 0E16 THAI CHARACTER THO THUNG B7 0E17 THAI CHARACTER THO THAHAN B8 0E18 THAI CHARACTER THO THONG B9 0E19 THAI CHARACTER NO NU BA 0E1A THAI CHARACTER BO BAIMAI BB 0E1B THAI CHARACTER PO PLA BC 0E1C THAI CHARACTER PHO PHUNG BD 0E1D THAI CHARACTER FO FA BE 0E1E THAI CHARACTER PHO PHAN BF 0E1F THAI CHARACTER FO FAN C0 0E20 THAI CHARACTER PHO SAMPHAO C1 0E21 THAI CHARACTER MO MA C2 0E22 THAI CHARACTER YO YAK C3 0E23 THAI CHARACTER RO RUA C4 0E24 THAI CHARACTER RU C5 0E25 THAI CHARACTER LO LING C6 0E26 THAI CHARACTER LU C7 0E27 THAI CHARACTER WO WAEN C8 0E28 THAI CHARACTER SO SALA C9 0E29 THAI CHARACTER SO RUSI CA 0E2A THAI CHARACTER SO SUA CB 0E2B THAI CHARACTER HO HIP CC 0E2C THAI CHARACTER LO CHULA CD 0E2D THAI CHARACTER O ANG CE 0E2E THAI CHARACTER HO NOKHUK CF 0E2F THAI CHARACTER PAIYANNOI D0 0E30 THAI CHARACTER SARA A D1 0E31 THAI CHARACTER MAI HAN-AKAT D2 0E32 THAI CHARACTER SARA AA D3 0E33 THAI CHARACTER SARA AM D4 0E34 THAI CHARACTER SARA I D5 0E35 THAI CHARACTER SARA II D6 0E36 THAI CHARACTER SARA UE D7 0E37 THAI CHARACTER SARA UEE D8 0E38 THAI CHARACTER SARA U D9 0E39 THAI CHARACTER SARA UU DA 0E3A THAI CHARACTER PHINTHU DF 0E3F THAI CURRENCY SYMBOL BAHT E0 0E40 THAI CHARACTER SARA E E1 0E41 THAI CHARACTER SARA AE E2 0E42 THAI CHARACTER SARA O E3 0E43 THAI CHARACTER SARA AI MAIMUAN E4 0E44 THAI CHARACTER SARA AI MAIMALAI E5 0E45 THAI CHARACTER LAKKHANGYAO E6 0E46 THAI CHARACTER MAIYAMOK E7 0E47 THAI CHARACTER MAITAIKHU E8 0E48 THAI CHARACTER MAI EK E9 0E49 THAI CHARACTER MAI THO EA 0E4A THAI CHARACTER MAI TRI EB 0E4B THAI CHARACTER MAI CHATTAWA EC 0E4C THAI CHARACTER THANTHAKHAT ED 0E4D THAI CHARACTER NIKHAHIT EE 0E4E THAI CHARACTER YAMAKKAN EF 0E4F THAI CHARACTER FONGMAN F0 0E50 THAI DIGIT ZERO F1 0E51 THAI DIGIT ONE F2 0E52 THAI DIGIT TWO F3 0E53 THAI DIGIT THREE F4 0E54 THAI DIGIT FOUR F5 0E55 THAI DIGIT FIVE F6 0E56 THAI DIGIT SIX F7 0E57 THAI DIGIT SEVEN F8 0E58 THAI DIGIT EIGHT F9 0E59 THAI DIGIT NINE FA 0E5A THAI CHARACTER ANGKHANKHU FB 0E5B THAI CHARACTER KHOMUT cyrus-imapd-2.5.10/lib/charset/windows-1250.t0000644000175000017500000002306513001236020015411 00000000000000# # Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. # # Redistribution and use in source and binary forms, with or without # modification, are permitted provided that the following conditions # are met: # # 1. Redistributions of source code must retain the above copyright # notice, this list of conditions and the following disclaimer. # # 2. Redistributions in binary form must reproduce the above copyright # notice, this list of conditions and the following disclaimer in # the documentation and/or other materials provided with the # distribution. # # 3. The name "Carnegie Mellon University" must not be used to # endorse or promote products derived from this software without # prior written permission. For permission or any legal # details, please contact # Carnegie Mellon University # Center for Technology Transfer and Enterprise Creation # 4615 Forbes Avenue # Suite 302 # Pittsburgh, PA 15213 # (412) 268-7393, fax: (412) 268-7395 # innovation@andrew.cmu.edu # # 4. Redistributions of any form whatsoever must retain the following # acknowledgment: # "This product includes software developed by Computing Services # at Carnegie Mellon University (http://www.cmu.edu/computing/)." # # CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO # THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY # AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE # FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES # WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN # AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING # OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. # # Charset put together by Ewald Dieterich # Reference: http://www.microsoft.com/globaldev/reference/sbcs/1252.htm 0 0000 NULL (NUL) 1 0001 START OF HEADING (SOH) 2 0002 START OF TEXT (STX) 3 0003 END OF TEXT (ETX) 4 0004 END OF TRANSMISSION (EOT) 5 0005 ENQUIRY (ENQ) 6 0006 ACKNOWLEDGE (ACK) 7 0007 BELL (BEL) 8 0008 BACKSPACE (BS) 9 0009 CHARACTER TABULATION (HT) A 000a LINE FEED (LF) B 000b LINE TABULATION (VT) C 000c FORM FEED (FF) D 000d CARRIAGE RETURN (CR) E 000e SHIFT OUT (SO) F 000f SHIFT IN (SI) 10 0010 DATALINK ESCAPE (DLE) 11 0011 DEVICE CONTROL ONE (DC1) 12 0012 DEVICE CONTROL TWO (DC2) 13 0013 DEVICE CONTROL THREE (DC3) 14 0014 DEVICE CONTROL FOUR (DC4) 15 0015 NEGATIVE ACKNOWLEDGE (NAK) 16 0016 SYNCRONOUS IDLE (SYN) 17 0017 END OF TRANSMISSION BLOCK (ETB) 18 0018 CANCEL (CAN) 19 0019 END OF MEDIUM (EM) 1A 001a SUBSTITUTE (SUB) 1B 001b ESCAPE (ESC) 1C 001c FILE SEPARATOR (IS4) 1D 001d GROUP SEPARATOR (IS3) 1E 001e RECORD SEPARATOR (IS2) 1F 001f UNIT SEPARATOR (IS1) 20 0020 SPACE 21 0021 EXCLAMATION MARK 22 0022 QUOTATION MARK 23 0023 NUMBER SIGN 24 0024 DOLLAR SIGN 25 0025 PERCENT SIGN 26 0026 AMPERSAND 27 0027 APOSTROPHE 28 0028 LEFT PARENTHESIS 29 0029 RIGHT PARENTHESIS 2A 002a ASTERISK 2B 002b PLUS SIGN 2C 002c COMMA 2D 002d HYPHEN-MINUS 2E 002e FULL STOP 2F 002f SOLIDUS 30 0030 DIGIT ZERO 31 0031 DIGIT ONE 32 0032 DIGIT TWO 33 0033 DIGIT THREE 34 0034 DIGIT FOUR 35 0035 DIGIT FIVE 36 0036 DIGIT SIX 37 0037 DIGIT SEVEN 38 0038 DIGIT EIGHT 39 0039 DIGIT NINE 3A 003a COLON 3B 003b SEMICOLON 3C 003c LESS-THAN SIGN 3D 003d EQUALS SIGN 3E 003e GREATER-THAN SIGN 3F 003f QUESTION MARK 40 0040 COMMERCIAL AT 41 0041 LATIN CAPITAL LETTER A 42 0042 LATIN CAPITAL LETTER B 43 0043 LATIN CAPITAL LETTER C 44 0044 LATIN CAPITAL LETTER D 45 0045 LATIN CAPITAL LETTER E 46 0046 LATIN CAPITAL LETTER F 47 0047 LATIN CAPITAL LETTER G 48 0048 LATIN CAPITAL LETTER H 49 0049 LATIN CAPITAL LETTER I 4A 004a LATIN CAPITAL LETTER J 4B 004b LATIN CAPITAL LETTER K 4C 004c LATIN CAPITAL LETTER L 4D 004d LATIN CAPITAL LETTER M 4E 004e LATIN CAPITAL LETTER N 4F 004f LATIN CAPITAL LETTER O 50 0050 LATIN CAPITAL LETTER P 51 0051 LATIN CAPITAL LETTER Q 52 0052 LATIN CAPITAL LETTER R 53 0053 LATIN CAPITAL LETTER S 54 0054 LATIN CAPITAL LETTER T 55 0055 LATIN CAPITAL LETTER U 56 0056 LATIN CAPITAL LETTER V 57 0057 LATIN CAPITAL LETTER W 58 0058 LATIN CAPITAL LETTER X 59 0059 LATIN CAPITAL LETTER Y 5A 005a LATIN CAPITAL LETTER Z 5B 005b LEFT SQUARE BRACKET 5C 005c REVERSE SOLIDUS 5D 005d RIGHT SQUARE BRACKET 5E 005e CIRCUMFLEX ACCENT 5F 005f LOW LINE 60 0060 GRAVE ACCENT 61 0061 LATIN SMALL LETTER A 62 0062 LATIN SMALL LETTER B 63 0063 LATIN SMALL LETTER C 64 0064 LATIN SMALL LETTER D 65 0065 LATIN SMALL LETTER E 66 0066 LATIN SMALL LETTER F 67 0067 LATIN SMALL LETTER G 68 0068 LATIN SMALL LETTER H 69 0069 LATIN SMALL LETTER I 6A 006a LATIN SMALL LETTER J 6B 006b LATIN SMALL LETTER K 6C 006c LATIN SMALL LETTER L 6D 006d LATIN SMALL LETTER M 6E 006e LATIN SMALL LETTER N 6F 006f LATIN SMALL LETTER O 70 0070 LATIN SMALL LETTER P 71 0071 LATIN SMALL LETTER Q 72 0072 LATIN SMALL LETTER R 73 0073 LATIN SMALL LETTER S 74 0074 LATIN SMALL LETTER T 75 0075 LATIN SMALL LETTER U 76 0076 LATIN SMALL LETTER V 77 0077 LATIN SMALL LETTER W 78 0078 LATIN SMALL LETTER X 79 0079 LATIN SMALL LETTER Y 7A 007a LATIN SMALL LETTER Z 7B 007b LEFT CURLY BRACKET 7C 007c VERTICAL LINE 7D 007d RIGHT CURLY BRACKET 7E 007e TILDE 7F 007f DELETE (DEL) 80 20AC EURO SIGN 82 201A SINGLE LOW-9 QUOTATION MARK 84 201E DOUBLE LOW-9 QUOTATION MARK 85 2026 HORIZONTAL ELLIPSIS 86 2020 DAGGER 87 2021 DOUBLE DAGGER 89 2030 PER MILLE SIGN 8A 0160 LATIN CAPITAL LETTER S WITH CARON 8B 2039 SINGLE LEFT-POINTING ANGLE QUOTATION MARK 8C 015A LATIN CAPITAL LETTER S WITH ACUTE 8D 0164 LATIN CAPITAL LETTER T WITH CARON 8E 017D LATIN CAPITAL LETTER Z WITH CARON 8F 0179 LATIN CAPITAL LETTER Z WITH ACUTE 91 2018 LEFT SINGLE QUOTATION MARK 92 2019 RIGHT SINGLE QUOTATION MARK 93 201C LEFT DOUBLE QUOTATION MARK 94 201D RIGHT DOUBLE QUOTATION MARK 95 2022 BULLET 96 2013 EN DASH 97 2014 EM DASH 99 2122 TRADE MARK SIGN 9A 0161 LATIN SMALL LETTER S WITH CARON 9B 203A SINGLE RIGHT-POINTING ANGLE QUOTATION MARK 9C 015B LATIN SMALL LETTER S WITH ACUTE 9D 0165 LATIN SMALL LETTER T WITH CARON 9E 017E LATIN SMALL LETTER Z WITH CARON 9F 017A LATIN SMALL LETTER Z WITH ACUTE A0 00A0 NO-BREAK SPACE A1 02C7 CARON A2 02D8 BREVE A3 0141 LATIN CAPITAL LETTER L WITH STROKE A4 00A4 CURRENCY SIGN A5 0104 LATIN CAPITAL LETTER A WITH OGONEK A6 00A6 BROKEN BAR A7 00A7 SECTION SIGN A8 00A8 DIAERESIS A9 00A9 COPYRIGHT SIGN AA 015E LATIN CAPITAL LETTER S WITH CEDILLA AB 00AB LEFT-POINTING DOUBLE ANGLE QUOTATION MARK AC 00AC NOT SIGN AD 00AD SOFT HYPHEN AE 00AE REGISTERED SIGN AF 017B LATIN CAPITAL LETTER Z WITH DOT ABOVE B0 00B0 DEGREE SIGN B1 00B1 PLUS-MINUS SIGN B2 02DB OGONEK B3 0142 LATIN SMALL LETTER L WITH STROKE B4 00B4 ACUTE ACCENT B5 00B5 MICRO SIGN B6 00B6 PILCROW SIGN B7 00B7 MIDDLE DOT B8 00B8 CEDILLA B9 0105 LATIN SMALL LETTER A WITH OGONEK BA 015F LATIN SMALL LETTER S WITH CEDILLA BB 00BB RIGHT-POINTING DOUBLE ANGLE QUOTATION MARK BC 013D LATIN CAPITAL LETTER L WITH CARON BD 02DD DOUBLE ACUTE ACCENT BE 013E LATIN SMALL LETTER L WITH CARON BF 017C LATIN SMALL LETTER Z WITH DOT ABOVE C0 0154 LATIN CAPITAL LETTER R WITH ACUTE C1 00C1 LATIN CAPITAL LETTER A WITH ACUTE C2 00C2 LATIN CAPITAL LETTER A WITH CIRCUMFLEX C3 0102 LATIN CAPITAL LETTER A WITH BREVE C4 00C4 LATIN CAPITAL LETTER A WITH DIAERESIS C5 0139 LATIN CAPITAL LETTER L WITH ACUTE C6 0106 LATIN CAPITAL LETTER C WITH ACUTE C7 00C7 LATIN CAPITAL LETTER C WITH CEDILLA C8 010C LATIN CAPITAL LETTER C WITH CARON C9 00C9 LATIN CAPITAL LETTER E WITH ACUTE CA 0118 LATIN CAPITAL LETTER E WITH OGONEK CB 00CB LATIN CAPITAL LETTER E WITH DIAERESIS CC 011A LATIN CAPITAL LETTER E WITH CARON CD 00CD LATIN CAPITAL LETTER I WITH ACUTE CE 00CE LATIN CAPITAL LETTER I WITH CIRCUMFLEX CF 010E LATIN CAPITAL LETTER D WITH CARON D0 0110 LATIN CAPITAL LETTER D WITH STROKE D1 0143 LATIN CAPITAL LETTER N WITH ACUTE D2 0147 LATIN CAPITAL LETTER N WITH CARON D3 00D3 LATIN CAPITAL LETTER O WITH ACUTE D4 00D4 LATIN CAPITAL LETTER O WITH CIRCUMFLEX D5 0150 LATIN CAPITAL LETTER O WITH DOUBLE ACUTE D6 00D6 LATIN CAPITAL LETTER O WITH DIAERESIS D7 00D7 MULTIPLICATION SIGN D8 0158 LATIN CAPITAL LETTER R WITH CARON D9 016E LATIN CAPITAL LETTER U WITH RING ABOVE DA 00DA LATIN CAPITAL LETTER U WITH ACUTE DB 0170 LATIN CAPITAL LETTER U WITH DOUBLE ACUTE DC 00DC LATIN CAPITAL LETTER U WITH DIAERESIS DD 00DD LATIN CAPITAL LETTER Y WITH ACUTE DE 0162 LATIN CAPITAL LETTER T WITH CEDILLA DF 00DF LATIN SMALL LETTER SHARP S E0 0155 LATIN SMALL LETTER R WITH ACUTE E1 00E1 LATIN SMALL LETTER A WITH ACUTE E2 00E2 LATIN SMALL LETTER A WITH CIRCUMFLEX E3 0103 LATIN SMALL LETTER A WITH BREVE E4 00E4 LATIN SMALL LETTER A WITH DIAERESIS E5 013A LATIN SMALL LETTER L WITH ACUTE E6 0107 LATIN SMALL LETTER C WITH ACUTE E7 00E7 LATIN SMALL LETTER C WITH CEDILLA E8 010D LATIN SMALL LETTER C WITH CARON E9 00E9 LATIN SMALL LETTER E WITH ACUTE EA 0119 LATIN SMALL LETTER E WITH OGONEK EB 00EB LATIN SMALL LETTER E WITH DIAERESIS EC 011B LATIN SMALL LETTER E WITH CARON ED 00ED LATIN SMALL LETTER I WITH ACUTE EE 00EE LATIN SMALL LETTER I WITH CIRCUMFLEX EF 010F LATIN SMALL LETTER D WITH CARON F0 0111 LATIN SMALL LETTER D WITH STROKE F1 0144 LATIN SMALL LETTER N WITH ACUTE F2 0148 LATIN SMALL LETTER N WITH CARON F3 00F3 LATIN SMALL LETTER O WITH ACUTE F4 00F4 LATIN SMALL LETTER O WITH CIRCUMFLEX F5 0151 LATIN SMALL LETTER O WITH DOUBLE ACUTE F6 00F6 LATIN SMALL LETTER O WITH DIAERESIS F7 00F7 DIVISION SIGN F8 0159 LATIN SMALL LETTER R WITH CARON F9 016F LATIN SMALL LETTER U WITH RING ABOVE FA 00FA LATIN SMALL LETTER U WITH ACUTE FB 0171 LATIN SMALL LETTER U WITH DOUBLE ACUTE FC 00FC LATIN SMALL LETTER U WITH DIAERESIS FD 00FD LATIN SMALL LETTER Y WITH ACUTE FE 0163 LATIN SMALL LETTER T WITH CEDILLA FF 02D9 DOT ABOVE cyrus-imapd-2.5.10/lib/charset/iso-8859-15.t0000644000175000017500000002337613001236020014767 00000000000000# # Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. # # Redistribution and use in source and binary forms, with or without # modification, are permitted provided that the following conditions # are met: # # 1. Redistributions of source code must retain the above copyright # notice, this list of conditions and the following disclaimer. # # 2. Redistributions in binary form must reproduce the above copyright # notice, this list of conditions and the following disclaimer in # the documentation and/or other materials provided with the # distribution. # # 3. The name "Carnegie Mellon University" must not be used to # endorse or promote products derived from this software without # prior written permission. For permission or any legal # details, please contact # Carnegie Mellon University # Center for Technology Transfer and Enterprise Creation # 4615 Forbes Avenue # Suite 302 # Pittsburgh, PA 15213 # (412) 268-7393, fax: (412) 268-7395 # innovation@andrew.cmu.edu # # 4. Redistributions of any form whatsoever must retain the following # acknowledgment: # "This product includes software developed by Computing Services # at Carnegie Mellon University (http://www.cmu.edu/computing/)." # # CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO # THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY # AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE # FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES # WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN # AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING # OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. # # Charset put together by Ewald Dieterich # Reference: http://www.iana.org/assignments/charset-reg/ISO-8859-15 0 0000 NULL (NUL) 1 0001 START OF HEADING (SOH) 2 0002 START OF TEXT (STX) 3 0003 END OF TEXT (ETX) 4 0004 END OF TRANSMISSION (EOT) 5 0005 ENQUIRY (ENQ) 6 0006 ACKNOWLEDGE (ACK) 7 0007 BELL (BEL) 8 0008 BACKSPACE (BS) 9 0009 CHARACTER TABULATION (HT) A 000a LINE FEED (LF) B 000b LINE TABULATION (VT) C 000c FORM FEED (FF) D 000d CARRIAGE RETURN (CR) E 000e SHIFT OUT (SO) F 000f SHIFT IN (SI) 10 0010 DATALINK ESCAPE (DLE) 11 0011 DEVICE CONTROL ONE (DC1) 12 0012 DEVICE CONTROL TWO (DC2) 13 0013 DEVICE CONTROL THREE (DC3) 14 0014 DEVICE CONTROL FOUR (DC4) 15 0015 NEGATIVE ACKNOWLEDGE (NAK) 16 0016 SYNCRONOUS IDLE (SYN) 17 0017 END OF TRANSMISSION BLOCK (ETB) 18 0018 CANCEL (CAN) 19 0019 END OF MEDIUM (EM) 1A 001a SUBSTITUTE (SUB) 1B 001b ESCAPE (ESC) 1C 001c FILE SEPARATOR (IS4) 1D 001d GROUP SEPARATOR (IS3) 1E 001e RECORD SEPARATOR (IS2) 1F 001f UNIT SEPARATOR (IS1) 20 0020 SPACE 21 0021 EXCLAMATION MARK 22 0022 QUOTATION MARK 23 0023 NUMBER SIGN 24 0024 DOLLAR SIGN 25 0025 PERCENT SIGN 26 0026 AMPERSAND 27 0027 APOSTROPHE 28 0028 LEFT PARENTHESIS 29 0029 RIGHT PARENTHESIS 2A 002a ASTERISK 2B 002b PLUS SIGN 2C 002c COMMA 2D 002d HYPHEN-MINUS 2E 002e FULL STOP 2F 002f SOLIDUS 30 0030 DIGIT ZERO 31 0031 DIGIT ONE 32 0032 DIGIT TWO 33 0033 DIGIT THREE 34 0034 DIGIT FOUR 35 0035 DIGIT FIVE 36 0036 DIGIT SIX 37 0037 DIGIT SEVEN 38 0038 DIGIT EIGHT 39 0039 DIGIT NINE 3A 003a COLON 3B 003b SEMICOLON 3C 003c LESS-THAN SIGN 3D 003d EQUALS SIGN 3E 003e GREATER-THAN SIGN 3F 003f QUESTION MARK 40 0040 COMMERCIAL AT 41 0041 LATIN CAPITAL LETTER A 42 0042 LATIN CAPITAL LETTER B 43 0043 LATIN CAPITAL LETTER C 44 0044 LATIN CAPITAL LETTER D 45 0045 LATIN CAPITAL LETTER E 46 0046 LATIN CAPITAL LETTER F 47 0047 LATIN CAPITAL LETTER G 48 0048 LATIN CAPITAL LETTER H 49 0049 LATIN CAPITAL LETTER I 4A 004a LATIN CAPITAL LETTER J 4B 004b LATIN CAPITAL LETTER K 4C 004c LATIN CAPITAL LETTER L 4D 004d LATIN CAPITAL LETTER M 4E 004e LATIN CAPITAL LETTER N 4F 004f LATIN CAPITAL LETTER O 50 0050 LATIN CAPITAL LETTER P 51 0051 LATIN CAPITAL LETTER Q 52 0052 LATIN CAPITAL LETTER R 53 0053 LATIN CAPITAL LETTER S 54 0054 LATIN CAPITAL LETTER T 55 0055 LATIN CAPITAL LETTER U 56 0056 LATIN CAPITAL LETTER V 57 0057 LATIN CAPITAL LETTER W 58 0058 LATIN CAPITAL LETTER X 59 0059 LATIN CAPITAL LETTER Y 5A 005a LATIN CAPITAL LETTER Z 5B 005b LEFT SQUARE BRACKET 5C 005c REVERSE SOLIDUS 5D 005d RIGHT SQUARE BRACKET 5E 005e CIRCUMFLEX ACCENT 5F 005f LOW LINE 60 0060 GRAVE ACCENT 61 0061 LATIN SMALL LETTER A 62 0062 LATIN SMALL LETTER B 63 0063 LATIN SMALL LETTER C 64 0064 LATIN SMALL LETTER D 65 0065 LATIN SMALL LETTER E 66 0066 LATIN SMALL LETTER F 67 0067 LATIN SMALL LETTER G 68 0068 LATIN SMALL LETTER H 69 0069 LATIN SMALL LETTER I 6A 006a LATIN SMALL LETTER J 6B 006b LATIN SMALL LETTER K 6C 006c LATIN SMALL LETTER L 6D 006d LATIN SMALL LETTER M 6E 006e LATIN SMALL LETTER N 6F 006f LATIN SMALL LETTER O 70 0070 LATIN SMALL LETTER P 71 0071 LATIN SMALL LETTER Q 72 0072 LATIN SMALL LETTER R 73 0073 LATIN SMALL LETTER S 74 0074 LATIN SMALL LETTER T 75 0075 LATIN SMALL LETTER U 76 0076 LATIN SMALL LETTER V 77 0077 LATIN SMALL LETTER W 78 0078 LATIN SMALL LETTER X 79 0079 LATIN SMALL LETTER Y 7A 007a LATIN SMALL LETTER Z 7B 007b LEFT CURLY BRACKET 7C 007c VERTICAL LINE 7D 007d RIGHT CURLY BRACKET 7E 007e TILDE 7F 007f DELETE (DEL) 80 0080 PADDING CHARACTER (PAD) 81 0081 HIGH OCTET PRESET (HOP) 82 0082 BREAK PERMITTED HERE (BPH) 83 0083 NO BREAK HERE (NBH) 84 0084 INDEX (IND) 85 0085 NEXT LINE (NEL) 86 0086 START OF SELECTED AREA (SSA) 87 0087 END OF SELECTED AREA (ESA) 88 0088 CHARACTER TABULATION SET (HTS) 89 0089 CHARACTER TABULATION WITH JUSTIFICATION (HTJ) 8A 008a LINE TABULATION SET (VTS) 8B 008b PARTIAL LINE FORWARD (PLD) 8C 008c PARTIAL LINE BACKWARD (PLU) 8D 008d REVERSE LINE FEED (RI) 8E 008e SINGLE-SHIFT TWO (SS2) 8F 008f SINGLE-SHIFT THREE (SS3) 90 0090 DEVICE CONTROL STRING (DCS) 91 0091 PRIVATE USE ONE (PU1) 92 0092 PRIVATE USE TWO (PU2) 93 0093 SET TRANSMIT STATE (STS) 94 0094 CANCEL CHARACTER (CCH) 95 0095 MESSAGE WAITING (MW) 96 0096 START OF GUARDED AREA (SPA) 97 0097 END OF GUARDED AREA (EPA) 98 0098 START OF STRING (SOS) 99 0099 SINGLE GRAPHIC CHARACTER INTRODUCER (SGCI) 9A 009a SINGLE CHARACTER INTRODUCER (SCI) 9B 009b CONTROL SEQUENCE INTRODUCER (CSI) 9C 009c STRING TERMINATOR (ST) 9D 009d OPERATING SYSTEM COMMAND (OSC) 9E 009e PRIVACY MESSAGE (PM) 9F 009f APPLICATION PROGRAM COMMAND (APC) A0 00a0 NO-BREAK SPACE A1 00a1 INVERTED EXCLAMATION MARK A2 00a2 CENT SIGN A3 00a3 POUND SIGN A4 20ac EURO SIGN A5 00a5 YEN SIGN A6 0160 LATIN CAPITAL LETTER S WITH CARON A7 00a7 SECTION SIGN A8 0161 LATIN SMALL LETTER S WITH CARON A9 00a9 COPYRIGHT SIGN AA 00aa FEMININE ORDINAL INDICATOR AB 00ab LEFT-POINTING DOUBLE ANGLE QUOTATION MARK AC 00ac NOT SIGN AD 00ad SOFT HYPHEN AE 00ae REGISTERED SIGN AF 00af MACRON B0 00b0 DEGREE SIGN B1 00b1 PLUS-MINUS SIGN B2 00b2 SUPERSCRIPT TWO B3 00b3 SUPERSCRIPT THREE B4 017d LATIN CAPITAL LETTER Z WITH CARON B5 00b5 MICRO SIGN B6 00b6 PILCROW SIGN B7 00b7 MIDDLE DOT B8 017e LATIN SMALL LETTER Z WITH CARON B9 00b9 SUPERSCRIPT ONE BA 00ba MASCULINE ORDINAL INDICATOR BB 00bb RIGHT-POINTING DOUBLE ANGLE QUOTATION MARK BC 0152 LATIN CAPITAL LIGATURE OE BD 0153 LATIN SMALL LIGATURE OE BE 0178 LATIN CAPITAL LETTER Y WITH DIAERESIS BF 00bf INVERTED QUESTION MARK C0 00c0 LATIN CAPITAL LETTER A WITH GRAVE C1 00c1 LATIN CAPITAL LETTER A WITH ACUTE C2 00c2 LATIN CAPITAL LETTER A WITH CIRCUMFLEX C3 00c3 LATIN CAPITAL LETTER A WITH TILDE C4 00c4 LATIN CAPITAL LETTER A WITH DIAERESIS C5 00c5 LATIN CAPITAL LETTER A WITH RING ABOVE C6 00c6 LATIN CAPITAL LETTER AE C7 00c7 LATIN CAPITAL LETTER C WITH CEDILLA C8 00c8 LATIN CAPITAL LETTER E WITH GRAVE C9 00c9 LATIN CAPITAL LETTER E WITH ACUTE CA 00ca LATIN CAPITAL LETTER E WITH CIRCUMFLEX CB 00cb LATIN CAPITAL LETTER E WITH DIAERESIS CC 00cc LATIN CAPITAL LETTER I WITH GRAVE CD 00cd LATIN CAPITAL LETTER I WITH ACUTE CE 00ce LATIN CAPITAL LETTER I WITH CIRCUMFLEX CF 00cf LATIN CAPITAL LETTER I WITH DIAERESIS D0 00d0 LATIN CAPITAL LETTER ETH (Icelandic) D1 00d1 LATIN CAPITAL LETTER N WITH TILDE D2 00d2 LATIN CAPITAL LETTER O WITH GRAVE D3 00d3 LATIN CAPITAL LETTER O WITH ACUTE D4 00d4 LATIN CAPITAL LETTER O WITH CIRCUMFLEX D5 00d5 LATIN CAPITAL LETTER O WITH TILDE D6 00d6 LATIN CAPITAL LETTER O WITH DIAERESIS D7 00d7 MULTIPLICATION SIGN D8 00d8 LATIN CAPITAL LETTER O WITH STROKE D9 00d9 LATIN CAPITAL LETTER U WITH GRAVE DA 00da LATIN CAPITAL LETTER U WITH ACUTE DB 00db LATIN CAPITAL LETTER U WITH CIRCUMFLEX DC 00dc LATIN CAPITAL LETTER U WITH DIAERESIS DD 00dd LATIN CAPITAL LETTER Y WITH ACUTE DE 00de LATIN CAPITAL LETTER THORN (Icelandic) DF 00df LATIN SMALL LETTER SHARP S (German) E0 00e0 LATIN SMALL LETTER A WITH GRAVE E1 00e1 LATIN SMALL LETTER A WITH ACUTE E2 00e2 LATIN SMALL LETTER A WITH CIRCUMFLEX E3 00e3 LATIN SMALL LETTER A WITH TILDE E4 00e4 LATIN SMALL LETTER A WITH DIAERESIS E5 00e5 LATIN SMALL LETTER A WITH RING ABOVE E6 00e6 LATIN SMALL LETTER AE E7 00e7 LATIN SMALL LETTER C WITH CEDILLA E8 00e8 LATIN SMALL LETTER E WITH GRAVE E9 00e9 LATIN SMALL LETTER E WITH ACUTE EA 00ea LATIN SMALL LETTER E WITH CIRCUMFLEX EB 00eb LATIN SMALL LETTER E WITH DIAERESIS EC 00ec LATIN SMALL LETTER I WITH GRAVE ED 00ed LATIN SMALL LETTER I WITH ACUTE EE 00ee LATIN SMALL LETTER I WITH CIRCUMFLEX EF 00ef LATIN SMALL LETTER I WITH DIAERESIS F0 00f0 LATIN SMALL LETTER ETH (Icelandic) F1 00f1 LATIN SMALL LETTER N WITH TILDE F2 00f2 LATIN SMALL LETTER O WITH GRAVE F3 00f3 LATIN SMALL LETTER O WITH ACUTE F4 00f4 LATIN SMALL LETTER O WITH CIRCUMFLEX F5 00f5 LATIN SMALL LETTER O WITH TILDE F6 00f6 LATIN SMALL LETTER O WITH DIAERESIS F7 00f7 DIVISION SIGN F8 00f8 LATIN SMALL LETTER O WITH STROKE F9 00f9 LATIN SMALL LETTER U WITH GRAVE FA 00fa LATIN SMALL LETTER U WITH ACUTE FB 00fb LATIN SMALL LETTER U WITH CIRCUMFLEX FC 00fc LATIN SMALL LETTER U WITH DIAERESIS FD 00fd LATIN SMALL LETTER Y WITH ACUTE FE 00fe LATIN SMALL LETTER THORN (Icelandic) FF 00ff LATIN SMALL LETTER Y WITH DIAERESIS cyrus-imapd-2.5.10/lib/charset/unifix.txt0000644000175000017500000000613712772415051015232 00000000000000# # Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. # # Redistribution and use in source and binary forms, with or without # modification, are permitted provided that the following conditions # are met: # # 1. Redistributions of source code must retain the above copyright # notice, this list of conditions and the following disclaimer. # # 2. Redistributions in binary form must reproduce the above copyright # notice, this list of conditions and the following disclaimer in # the documentation and/or other materials provided with the # distribution. # # 3. The name "Carnegie Mellon University" must not be used to # endorse or promote products derived from this software without # prior written permission. For permission or any legal # details, please contact # Carnegie Mellon University # Center for Technology Transfer and Enterprise Creation # 4615 Forbes Avenue # Suite 302 # Pittsburgh, PA 15213 # (412) 268-7393, fax: (412) 268-7395 # innovation@andrew.cmu.edu # # 4. Redistributions of any form whatsoever must retain the following # acknowledgment: # "This product includes software developed by Computing Services # at Carnegie Mellon University (http://www.cmu.edu/computing/)." # # CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO # THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY # AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE # FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES # WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN # AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING # OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. # Modifications to Unicode data for better case-insensitive searching # unicode char;char name;general category;canonical combining class; # bidirectional category; character decomp; decimal digit value; # digit value; numeric value; mirrored char; unicode 1.0 name; # comment; upper case equiv; lower case equiv # Make these whitespace, so they're ignored 0009;;Zs;0;ON;;;;;N;HORIZONTAL TABULATION;;;; 000A;;Zs;0;ON;;;;;N;LINE FEED;;;; 000B;;Zs;0;ON;;;;;N;VERTICAL TABULATION;;;; 000C;;Zs;0;ON;;;;;N;FORM FEED;;;; 000D;;Zs;0;ON;;;;;N;CARRIAGE RETURN;;;; # Map s-zet to "ss" 00DF;LATIN SMALL LETTER SHARP S;Ll;0;L;0073 0073;;;;N;;German;;; # Map ae to "ae" 00E6;LATIN SMALL LETTER AE;Ll;0;L;0061 0065;;;;N;LATIN SMALL LETTER A E;;00C6;;00C6 # Map Eth and Thorn to "th" 00F0;LATIN SMALL LETTER ETH;Ll;0;L;0074 0068;;;;N;;Icelandic;00D0;;00D0 00FE;LATIN SMALL LETTER THORN;Ll;0;L;0074 0068;;;;N;;Icelandic;00DE;;00DE # Map oe ligature to "oe" 0153;LATIN SMALL LIGATURE OE;Ll;0;L;006F 0065;;;;N;LATIN SMALL LETTER O E;;0152;;0152 # Map Cyrillic ligatures 04A5;CYRILLIC SMALL LIGATURE EN GHE;Ll;0;L;041D 0413;;;;N;CYRILLIC SMALL LETTER EN GE;;04A4;;04A4 04B5;CYRILLIC SMALL LIGATURE TE TSE;Ll;0;L;0422 0426;;;;N;CYRILLIC SMALL LETTER TE TSE;Abkhasian;04B4;;04B4 # Map fraction slash to "/" 2044;FRACTION SLASH;Sm;0;ON;002F;;;;N;;;;; cyrus-imapd-2.5.10/lib/charset/gb2312.t0000644000175000017500000045072313001236020014237 00000000000000# # Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. # # Redistribution and use in source and binary forms, with or without # modification, are permitted provided that the following conditions # are met: # # 1. Redistributions of source code must retain the above copyright # notice, this list of conditions and the following disclaimer. # # 2. Redistributions in binary form must reproduce the above copyright # notice, this list of conditions and the following disclaimer in # the documentation and/or other materials provided with the # distribution. # # 3. The name "Carnegie Mellon University" must not be used to # endorse or promote products derived from this software without # prior written permission. For permission or any legal # details, please contact # Carnegie Mellon University # Center for Technology Transfer and Enterprise Creation # 4615 Forbes Avenue # Suite 302 # Pittsburgh, PA 15213 # (412) 268-7393, fax: (412) 268-7395 # innovation@andrew.cmu.edu # # 4. Redistributions of any form whatsoever must retain the following # acknowledgment: # "This product includes software developed by Computing Services # at Carnegie Mellon University (http://www.cmu.edu/computing/)." # # CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO # THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY # AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE # FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES # WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN # AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING # OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. 0 0000 NULL (NUL) 1 0001 START OF HEADING (SOH) 2 0002 START OF TEXT (STX) 3 0003 END OF TEXT (ETX) 4 0004 END OF TRANSMISSION (EOT) 5 0005 ENQUIRY (ENQ) 6 0006 ACKNOWLEDGE (ACK) 7 0007 BELL (BEL) 8 0008 BACKSPACE (BS) 9 0009 CHARACTER TABULATION (HT) A 000a LINE FEED (LF) B 000b LINE TABULATION (VT) C 000c FORM FEED (FF) D 000d CARRIAGE RETURN (CR) E 000e SHIFT OUT (SO) F 000f SHIFT IN (SI) 10 0010 DATALINK ESCAPE (DLE) 11 0011 DEVICE CONTROL ONE (DC1) 12 0012 DEVICE CONTROL TWO (DC2) 13 0013 DEVICE CONTROL THREE (DC3) 14 0014 DEVICE CONTROL FOUR (DC4) 15 0015 NEGATIVE ACKNOWLEDGE (NAK) 16 0016 SYNCRONOUS IDLE (SYN) 17 0017 END OF TRANSMISSION BLOCK (ETB) 18 0018 CANCEL (CAN) 19 0019 END OF MEDIUM (EM) 1A 001a SUBSTITUTE (SUB) 1B 001b ESCAPE (ESC) 1C 001c FILE SEPARATOR (IS4) 1D 001d GROUP SEPARATOR (IS3) 1E 001e RECORD SEPARATOR (IS2) 1F 001f UNIT SEPARATOR (IS1) 20 0020 SPACE 21 0021 EXCLAMATION MARK 22 0022 QUOTATION MARK 23 0023 NUMBER SIGN 24 0024 DOLLAR SIGN 25 0025 PERCENT SIGN 26 0026 AMPERSAND 27 0027 APOSTROPHE 28 0028 LEFT PARENTHESIS 29 0029 RIGHT PARENTHESIS 2A 002a ASTERISK 2B 002b PLUS SIGN 2C 002c COMMA 2D 002d HYPHEN-MINUS 2E 002e FULL STOP 2F 002f SOLIDUS 30 0030 DIGIT ZERO 31 0031 DIGIT ONE 32 0032 DIGIT TWO 33 0033 DIGIT THREE 34 0034 DIGIT FOUR 35 0035 DIGIT FIVE 36 0036 DIGIT SIX 37 0037 DIGIT SEVEN 38 0038 DIGIT EIGHT 39 0039 DIGIT NINE 3A 003a COLON 3B 003b SEMICOLON 3C 003c LESS-THAN SIGN 3D 003d EQUALS SIGN 3E 003e GREATER-THAN SIGN 3F 003f QUESTION MARK 40 0040 COMMERCIAL AT 41 0041 LATIN CAPITAL LETTER A 42 0042 LATIN CAPITAL LETTER B 43 0043 LATIN CAPITAL LETTER C 44 0044 LATIN CAPITAL LETTER D 45 0045 LATIN CAPITAL LETTER E 46 0046 LATIN CAPITAL LETTER F 47 0047 LATIN CAPITAL LETTER G 48 0048 LATIN CAPITAL LETTER H 49 0049 LATIN CAPITAL LETTER I 4A 004a LATIN CAPITAL LETTER J 4B 004b LATIN CAPITAL LETTER K 4C 004c LATIN CAPITAL LETTER L 4D 004d LATIN CAPITAL LETTER M 4E 004e LATIN CAPITAL LETTER N 4F 004f LATIN CAPITAL LETTER O 50 0050 LATIN CAPITAL LETTER P 51 0051 LATIN CAPITAL LETTER Q 52 0052 LATIN CAPITAL LETTER R 53 0053 LATIN CAPITAL LETTER S 54 0054 LATIN CAPITAL LETTER T 55 0055 LATIN CAPITAL LETTER U 56 0056 LATIN CAPITAL LETTER V 57 0057 LATIN CAPITAL LETTER W 58 0058 LATIN CAPITAL LETTER X 59 0059 LATIN CAPITAL LETTER Y 5A 005a LATIN CAPITAL LETTER Z 5B 005b LEFT SQUARE BRACKET 5C 005c REVERSE SOLIDUS 5D 005d RIGHT SQUARE BRACKET 5E 005e CIRCUMFLEX ACCENT 5F 005f LOW LINE 60 0060 GRAVE ACCENT 61 0061 LATIN SMALL LETTER A 62 0062 LATIN SMALL LETTER B 63 0063 LATIN SMALL LETTER C 64 0064 LATIN SMALL LETTER D 65 0065 LATIN SMALL LETTER E 66 0066 LATIN SMALL LETTER F 67 0067 LATIN SMALL LETTER G 68 0068 LATIN SMALL LETTER H 69 0069 LATIN SMALL LETTER I 6A 006a LATIN SMALL LETTER J 6B 006b LATIN SMALL LETTER K 6C 006c LATIN SMALL LETTER L 6D 006d LATIN SMALL LETTER M 6E 006e LATIN SMALL LETTER N 6F 006f LATIN SMALL LETTER O 70 0070 LATIN SMALL LETTER P 71 0071 LATIN SMALL LETTER Q 72 0072 LATIN SMALL LETTER R 73 0073 LATIN SMALL LETTER S 74 0074 LATIN SMALL LETTER T 75 0075 LATIN SMALL LETTER U 76 0076 LATIN SMALL LETTER V 77 0077 LATIN SMALL LETTER W 78 0078 LATIN SMALL LETTER X 79 0079 LATIN SMALL LETTER Y 7A 007a LATIN SMALL LETTER Z 7B 007b LEFT CURLY BRACKET 7C 007c VERTICAL LINE 7D 007d RIGHT CURLY BRACKET 7E 007e TILDE 7F 007f DELETE (DEL) A1A1 3000 # IDEOGRAPHIC SPACE A1A2 3001 # IDEOGRAPHIC COMMA A1A3 3002 # IDEOGRAPHIC FULL STOP A1A4 30FB # KATAKANA MIDDLE DOT A1A5 02C9 # MODIFIER LETTER MACRON (Mandarin Chinese first tone) A1A6 02C7 # CARON (Mandarin Chinese third tone) A1A7 00A8 # DIAERESIS A1A8 3003 # DITTO MARK A1A9 3005 # IDEOGRAPHIC ITERATION MARK A1AA 2015 # HORIZONTAL BAR A1AB FF5E # FULLWIDTH TILDE A1AC 2225 # PARALLEL TO A1AD 2026 # HORIZONTAL ELLIPSIS A1AE 2018 # LEFT SINGLE QUOTATION MARK A1AF 2019 # RIGHT SINGLE QUOTATION MARK A1B0 201C # LEFT DOUBLE QUOTATION MARK A1B1 201D # RIGHT DOUBLE QUOTATION MARK A1B2 3014 # LEFT TORTOISE SHELL BRACKET A1B3 3015 # RIGHT TORTOISE SHELL BRACKET A1B4 3008 # LEFT ANGLE BRACKET A1B5 3009 # RIGHT ANGLE BRACKET A1B6 300A # LEFT DOUBLE ANGLE BRACKET A1B7 300B # RIGHT DOUBLE ANGLE BRACKET A1B8 300C # LEFT CORNER BRACKET A1B9 300D # RIGHT CORNER BRACKET A1BA 300E # LEFT WHITE CORNER BRACKET A1BB 300F # RIGHT WHITE CORNER BRACKET A1BC 3016 # LEFT WHITE LENTICULAR BRACKET A1BD 3017 # RIGHT WHITE LENTICULAR BRACKET A1BE 3010 # LEFT BLACK LENTICULAR BRACKET A1BF 3011 # RIGHT BLACK LENTICULAR BRACKET A1C0 00B1 # PLUS-MINUS SIGN A1C1 00D7 # MULTIPLICATION SIGN A1C2 00F7 # DIVISION SIGN A1C3 2236 # RATIO A1C4 2227 # LOGICAL AND A1C5 2228 # LOGICAL OR A1C6 2211 # N-ARY SUMMATION A1C7 220F # N-ARY PRODUCT A1C8 222A # UNION A1C9 2229 # INTERSECTION A1CA 2208 # ELEMENT OF A1CB 2237 # PROPORTION A1CC 221A # SQUARE ROOT A1CD 22A5 # UP TACK A1CE 2225 # PARALLEL TO A1CF 2220 # ANGLE A1D0 2312 # ARC A1D1 2299 # CIRCLED DOT OPERATOR A1D2 222B # INTEGRAL A1D3 222E # CONTOUR INTEGRAL A1D4 2261 # IDENTICAL TO A1D5 224C # ALL EQUAL TO A1D6 2248 # ALMOST EQUAL TO A1D7 223D # REVERSED TILDE A1D8 221D # PROPORTIONAL TO A1D9 2260 # NOT EQUAL TO A1DA 226E # NOT LESS-THAN A1DB 226F # NOT GREATER-THAN A1DC 2264 # LESS-THAN OR EQUAL TO A1DD 2265 # GREATER-THAN OR EQUAL TO A1DE 221E # INFINITY A1DF 2235 # BECAUSE A160 2234 # THEREFORE A161 2642 # MALE SIGN A162 2640 # FEMALE SIGN A163 00B0 # DEGREE SIGN A164 2032 # PRIME A165 2033 # DOUBLE PRIME A166 2103 # DEGREE CELSIUS A167 FF04 # FULLWIDTH DOLLAR SIGN A168 00A4 # CURRENCY SIGN A169 FFE0 # FULLWIDTH CENT SIGN A16A FFE1 # FULLWIDTH POUND SIGN A16B 2030 # PER MILLE SIGN A16C 00A7 # SECTION SIGN A16D 2116 # NUMERO SIGN A16E 2606 # WHITE STAR A16F 2605 # BLACK STAR A1F0 25CB # WHITE CIRCLE A1F1 25CF # BLACK CIRCLE A1F2 25CE # BULLSEYE A1F3 25C7 # WHITE DIAMOND A1F4 25C6 # BLACK DIAMOND A1F5 25A1 # WHITE SQUARE A1F6 25A0 # BLACK SQUARE A1F7 25B3 # WHITE UP-POINTING TRIANGLE A1F8 25B2 # BLACK UP-POINTING TRIANGLE A1F9 203B # REFERENCE MARK A1FA 2192 # RIGHTWARDS ARROW A1FB 2190 # LEFTWARDS ARROW A1FC 2191 # UPWARDS ARROW A1FD 2193 # DOWNWARDS ARROW A1FE 3013 # GETA MARK A2B1 2488 # DIGIT ONE FULL STOP A2B2 2489 # DIGIT TWO FULL STOP A2B3 248A # DIGIT THREE FULL STOP A2B4 248B # DIGIT FOUR FULL STOP A2B5 248C # DIGIT FIVE FULL STOP A2B6 248D # DIGIT SIX FULL STOP A2B7 248E # DIGIT SEVEN FULL STOP A2B8 248F # DIGIT EIGHT FULL STOP A2B9 2490 # DIGIT NINE FULL STOP A2BA 2491 # NUMBER TEN FULL STOP A2BB 2492 # NUMBER ELEVEN FULL STOP A2BC 2493 # NUMBER TWELVE FULL STOP A2BD 2494 # NUMBER THIRTEEN FULL STOP A2BE 2495 # NUMBER FOURTEEN FULL STOP A2BF 2496 # NUMBER FIFTEEN FULL STOP A2C0 2497 # NUMBER SIXTEEN FULL STOP A2C1 2498 # NUMBER SEVENTEEN FULL STOP A2C2 2499 # NUMBER EIGHTEEN FULL STOP A2C3 249A # NUMBER NINETEEN FULL STOP A2C4 249B # NUMBER TWENTY FULL STOP A2C5 2474 # PARENTHESIZED DIGIT ONE A2C6 2475 # PARENTHESIZED DIGIT TWO A2C7 2476 # PARENTHESIZED DIGIT THREE A2C8 2477 # PARENTHESIZED DIGIT FOUR A2C9 2478 # PARENTHESIZED DIGIT FIVE A2CA 2479 # PARENTHESIZED DIGIT SIX A2CB 247A # PARENTHESIZED DIGIT SEVEN A2CC 247B # PARENTHESIZED DIGIT EIGHT A2CD 247C # PARENTHESIZED DIGIT NINE A2CE 247D # PARENTHESIZED NUMBER TEN A2CF 247E # PARENTHESIZED NUMBER ELEVEN A2D0 247F # PARENTHESIZED NUMBER TWELVE A2D1 2480 # PARENTHESIZED NUMBER THIRTEEN A2D2 2481 # PARENTHESIZED NUMBER FOURTEEN A2D3 2482 # PARENTHESIZED NUMBER FIFTEEN A2D4 2483 # PARENTHESIZED NUMBER SIXTEEN A2D5 2484 # PARENTHESIZED NUMBER SEVENTEEN A2D6 2485 # PARENTHESIZED NUMBER EIGHTEEN A2D7 2486 # PARENTHESIZED NUMBER NINETEEN A2D8 2487 # PARENTHESIZED NUMBER TWENTY A2D9 2460 # CIRCLED DIGIT ONE A2DA 2461 # CIRCLED DIGIT TWO A2DB 2462 # CIRCLED DIGIT THREE A2DC 2463 # CIRCLED DIGIT FOUR A2DD 2464 # CIRCLED DIGIT FIVE A2DE 2465 # CIRCLED DIGIT SIX A2DF 2466 # CIRCLED DIGIT SEVEN A2E0 2467 # CIRCLED DIGIT EIGHT A2E1 2468 # CIRCLED DIGIT NINE A2E2 2469 # CIRCLED NUMBER TEN A2E5 3220 # PARENTHESIZED IDEOGRAPH ONE A2E6 3221 # PARENTHESIZED IDEOGRAPH TWO A2E7 3222 # PARENTHESIZED IDEOGRAPH THREE A2E8 3223 # PARENTHESIZED IDEOGRAPH FOUR A2E9 3224 # PARENTHESIZED IDEOGRAPH FIVE A2EA 3225 # PARENTHESIZED IDEOGRAPH SIX A2EB 3226 # PARENTHESIZED IDEOGRAPH SEVEN A2EC 3227 # PARENTHESIZED IDEOGRAPH EIGHT A2ED 3228 # PARENTHESIZED IDEOGRAPH NINE A2EE 3229 # PARENTHESIZED IDEOGRAPH TEN A2F1 2160 # ROMAN NUMERAL ONE A2F2 2161 # ROMAN NUMERAL TWO A2F3 2162 # ROMAN NUMERAL THREE A2F4 2163 # ROMAN NUMERAL FOUR A2F5 2164 # ROMAN NUMERAL FIVE A2F6 2165 # ROMAN NUMERAL SIX A2F7 2166 # ROMAN NUMERAL SEVEN A2F8 2167 # ROMAN NUMERAL EIGHT A2F9 2168 # ROMAN NUMERAL NINE A2FA 2169 # ROMAN NUMERAL TEN A2FB 216A # ROMAN NUMERAL ELEVEN A2FC 216B # ROMAN NUMERAL TWELVE A3A1 FF01 # FULLWIDTH EXCLAMATION MARK A3A2 FF02 # FULLWIDTH QUOTATION MARK A3A3 FF03 # FULLWIDTH NUMBER SIGN A3A4 FFE5 # FULLWIDTH YEN SIGN A3A5 FF05 # FULLWIDTH PERCENT SIGN A3A6 FF06 # FULLWIDTH AMPERSAND A3A7 FF07 # FULLWIDTH APOSTROPHE A3A8 FF08 # FULLWIDTH LEFT PARENTHESIS A3A9 FF09 # FULLWIDTH RIGHT PARENTHESIS A3AA FF0A # FULLWIDTH ASTERISK A3AB FF0B # FULLWIDTH PLUS SIGN A3AC FF0C # FULLWIDTH COMMA A3AD FF0D # FULLWIDTH HYPHEN-MINUS A3AE FF0E # FULLWIDTH FULL STOP A3AF FF0F # FULLWIDTH SOLIDUS A3B0 FF10 # FULLWIDTH DIGIT ZERO A3B1 FF11 # FULLWIDTH DIGIT ONE A3B2 FF12 # FULLWIDTH DIGIT TWO A3B3 FF13 # FULLWIDTH DIGIT THREE A3B4 FF14 # FULLWIDTH DIGIT FOUR A3B5 FF15 # FULLWIDTH DIGIT FIVE A3B6 FF16 # FULLWIDTH DIGIT SIX A3B7 FF17 # FULLWIDTH DIGIT SEVEN A3B8 FF18 # FULLWIDTH DIGIT EIGHT A3B9 FF19 # FULLWIDTH DIGIT NINE A3BA FF1A # FULLWIDTH COLON A3BB FF1B # FULLWIDTH SEMICOLON A3BC FF1C # FULLWIDTH LESS-THAN SIGN A3BD FF1D # FULLWIDTH EQUALS SIGN A3BE FF1E # FULLWIDTH GREATER-THAN SIGN A3BF FF1F # FULLWIDTH QUESTION MARK A3C0 FF20 # FULLWIDTH COMMERCIAL AT A3C1 FF21 # FULLWIDTH LATIN CAPITAL LETTER A A3C2 FF22 # FULLWIDTH LATIN CAPITAL LETTER B A3C3 FF23 # FULLWIDTH LATIN CAPITAL LETTER C A3C4 FF24 # FULLWIDTH LATIN CAPITAL LETTER D A3C5 FF25 # FULLWIDTH LATIN CAPITAL LETTER E A3C6 FF26 # FULLWIDTH LATIN CAPITAL LETTER F A3C7 FF27 # FULLWIDTH LATIN CAPITAL LETTER G A3C8 FF28 # FULLWIDTH LATIN CAPITAL LETTER H A3C9 FF29 # FULLWIDTH LATIN CAPITAL LETTER I A3CA FF2A # FULLWIDTH LATIN CAPITAL LETTER J A3CB FF2B # FULLWIDTH LATIN CAPITAL LETTER K A3CC FF2C # FULLWIDTH LATIN CAPITAL LETTER L A3CD FF2D # FULLWIDTH LATIN CAPITAL LETTER M A3CE FF2E # FULLWIDTH LATIN CAPITAL LETTER N A3CF FF2F # FULLWIDTH LATIN CAPITAL LETTER O A3D0 FF30 # FULLWIDTH LATIN CAPITAL LETTER P A3D1 FF31 # FULLWIDTH LATIN CAPITAL LETTER Q A3D2 FF32 # FULLWIDTH LATIN CAPITAL LETTER R A3D3 FF33 # FULLWIDTH LATIN CAPITAL LETTER S A3D4 FF34 # FULLWIDTH LATIN CAPITAL LETTER T A3D5 FF35 # FULLWIDTH LATIN CAPITAL LETTER U A3D6 FF36 # FULLWIDTH LATIN CAPITAL LETTER V A3D7 FF37 # FULLWIDTH LATIN CAPITAL LETTER W A3D8 FF38 # FULLWIDTH LATIN CAPITAL LETTER X A3D9 FF39 # FULLWIDTH LATIN CAPITAL LETTER Y A3DA FF3A # FULLWIDTH LATIN CAPITAL LETTER Z A3DB FF3B # FULLWIDTH LEFT SQUARE BRACKET A3DC FF3C # FULLWIDTH REVERSE SOLIDUS A3DD FF3D # FULLWIDTH RIGHT SQUARE BRACKET A3DE FF3E # FULLWIDTH CIRCUMFLEX ACCENT A3DF FF3F # FULLWIDTH LOW LINE A3E0 FF40 # FULLWIDTH GRAVE ACCENT A3E1 FF41 # FULLWIDTH LATIN SMALL LETTER A A3E2 FF42 # FULLWIDTH LATIN SMALL LETTER B A3E3 FF43 # FULLWIDTH LATIN SMALL LETTER C A3E4 FF44 # FULLWIDTH LATIN SMALL LETTER D A3E5 FF45 # FULLWIDTH LATIN SMALL LETTER E A3E6 FF46 # FULLWIDTH LATIN SMALL LETTER F A3E7 FF47 # FULLWIDTH LATIN SMALL LETTER G A3E8 FF48 # FULLWIDTH LATIN SMALL LETTER H A3E9 FF49 # FULLWIDTH LATIN SMALL LETTER I A3EA FF4A # FULLWIDTH LATIN SMALL LETTER J A3EB FF4B # FULLWIDTH LATIN SMALL LETTER K A3EC FF4C # FULLWIDTH LATIN SMALL LETTER L A3ED FF4D # FULLWIDTH LATIN SMALL LETTER M A3EE FF4E # FULLWIDTH LATIN SMALL LETTER N A3EF FF4F # FULLWIDTH LATIN SMALL LETTER O A3F0 FF50 # FULLWIDTH LATIN SMALL LETTER P A3F1 FF51 # FULLWIDTH LATIN SMALL LETTER Q A3F2 FF52 # FULLWIDTH LATIN SMALL LETTER R A3F3 FF53 # FULLWIDTH LATIN SMALL LETTER S A3F4 FF54 # FULLWIDTH LATIN SMALL LETTER T A3F5 FF55 # FULLWIDTH LATIN SMALL LETTER U A3F6 FF56 # FULLWIDTH LATIN SMALL LETTER V A3F7 FF57 # FULLWIDTH LATIN SMALL LETTER W A3F8 FF58 # FULLWIDTH LATIN SMALL LETTER X A3F9 FF59 # FULLWIDTH LATIN SMALL LETTER Y A3FA FF5A # FULLWIDTH LATIN SMALL LETTER Z A3FB FF5B # FULLWIDTH LEFT CURLY BRACKET A3FC FF5C # FULLWIDTH VERTICAL LINE A3FD FF5D # FULLWIDTH RIGHT CURLY BRACKET A3FE FFE3 # FULLWIDTH MACRON A4A1 3041 # HIRAGANA LETTER SMALL A A4A2 3042 # HIRAGANA LETTER A A4A3 3043 # HIRAGANA LETTER SMALL I A4A4 3044 # HIRAGANA LETTER I A4A5 3045 # HIRAGANA LETTER SMALL U A4A6 3046 # HIRAGANA LETTER U A4A7 3047 # HIRAGANA LETTER SMALL E A4A8 3048 # HIRAGANA LETTER E A4A9 3049 # HIRAGANA LETTER SMALL O A4AA 304A # HIRAGANA LETTER O A4AB 304B # HIRAGANA LETTER KA A4AC 304C # HIRAGANA LETTER GA A4AD 304D # HIRAGANA LETTER KI A4AE 304E # HIRAGANA LETTER GI A4AF 304F # HIRAGANA LETTER KU A4B0 3050 # HIRAGANA LETTER GU A4B1 3051 # HIRAGANA LETTER KE A4B2 3052 # HIRAGANA LETTER GE A4B3 3053 # HIRAGANA LETTER KO A4B4 3054 # HIRAGANA LETTER GO A4B5 3055 # HIRAGANA LETTER SA A4B6 3056 # HIRAGANA LETTER ZA A4B7 3057 # HIRAGANA LETTER SI A4B8 3058 # HIRAGANA LETTER ZI A4B9 3059 # HIRAGANA LETTER SU A4BA 305A # HIRAGANA LETTER ZU A4BB 305B # HIRAGANA LETTER SE A4BC 305C # HIRAGANA LETTER ZE A4BD 305D # HIRAGANA LETTER SO A4BE 305E # HIRAGANA LETTER ZO A4BF 305F # HIRAGANA LETTER TA A4C0 3060 # HIRAGANA LETTER DA A4C1 3061 # HIRAGANA LETTER TI A4C2 3062 # HIRAGANA LETTER DI A4C3 3063 # HIRAGANA LETTER SMALL TU A4C4 3064 # HIRAGANA LETTER TU A4C5 3065 # HIRAGANA LETTER DU A4C6 3066 # HIRAGANA LETTER TE A4C7 3067 # HIRAGANA LETTER DE A4C8 3068 # HIRAGANA LETTER TO A4C9 3069 # HIRAGANA LETTER DO A4CA 306A # HIRAGANA LETTER NA A4CB 306B # HIRAGANA LETTER NI A4CC 306C # HIRAGANA LETTER NU A4CD 306D # HIRAGANA LETTER NE A4CE 306E # HIRAGANA LETTER NO A4CF 306F # HIRAGANA LETTER HA A4D0 3070 # HIRAGANA LETTER BA A4D1 3071 # HIRAGANA LETTER PA A4D2 3072 # HIRAGANA LETTER HI A4D3 3073 # HIRAGANA LETTER BI A4D4 3074 # HIRAGANA LETTER PI A4D5 3075 # HIRAGANA LETTER HU A4D6 3076 # HIRAGANA LETTER BU A4D7 3077 # HIRAGANA LETTER PU A4D8 3078 # HIRAGANA LETTER HE A4D9 3079 # HIRAGANA LETTER BE A4DA 307A # HIRAGANA LETTER PE A4DB 307B # HIRAGANA LETTER HO A4DC 307C # HIRAGANA LETTER BO A4DD 307D # HIRAGANA LETTER PO A4DE 307E # HIRAGANA LETTER MA A4DF 307F # HIRAGANA LETTER MI A4E0 3080 # HIRAGANA LETTER MU A4E1 3081 # HIRAGANA LETTER ME A4E2 3082 # HIRAGANA LETTER MO A4E3 3083 # HIRAGANA LETTER SMALL YA A4E4 3084 # HIRAGANA LETTER YA A4E5 3085 # HIRAGANA LETTER SMALL YU A4E6 3086 # HIRAGANA LETTER YU A4E7 3087 # HIRAGANA LETTER SMALL YO A4E8 3088 # HIRAGANA LETTER YO A4E9 3089 # HIRAGANA LETTER RA A4EA 308A # HIRAGANA LETTER RI A4EB 308B # HIRAGANA LETTER RU A4EC 308C # HIRAGANA LETTER RE A4ED 308D # HIRAGANA LETTER RO A4EE 308E # HIRAGANA LETTER SMALL WA A4EF 308F # HIRAGANA LETTER WA A4F0 3090 # HIRAGANA LETTER WI A4F1 3091 # HIRAGANA LETTER WE A4F2 3092 # HIRAGANA LETTER WO A4F3 3093 # HIRAGANA LETTER N A5A1 30A1 # KATAKANA LETTER SMALL A A5A2 30A2 # KATAKANA LETTER A A5A3 30A3 # KATAKANA LETTER SMALL I A5A4 30A4 # KATAKANA LETTER I A5A5 30A5 # KATAKANA LETTER SMALL U A5A6 30A6 # KATAKANA LETTER U A5A7 30A7 # KATAKANA LETTER SMALL E A5A8 30A8 # KATAKANA LETTER E A5A9 30A9 # KATAKANA LETTER SMALL O A5AA 30AA # KATAKANA LETTER O A5AB 30AB # KATAKANA LETTER KA A5AC 30AC # KATAKANA LETTER GA A5AD 30AD # KATAKANA LETTER KI A5AE 30AE # KATAKANA LETTER GI A5AF 30AF # KATAKANA LETTER KU A5B0 30B0 # KATAKANA LETTER GU A5B1 30B1 # KATAKANA LETTER KE A5B2 30B2 # KATAKANA LETTER GE A5B3 30B3 # KATAKANA LETTER KO A5B4 30B4 # KATAKANA LETTER GO A5B5 30B5 # KATAKANA LETTER SA A5B6 30B6 # KATAKANA LETTER ZA A5B7 30B7 # KATAKANA LETTER SI A5B8 30B8 # KATAKANA LETTER ZI A5B9 30B9 # KATAKANA LETTER SU A5BA 30BA # KATAKANA LETTER ZU A5BB 30BB # KATAKANA LETTER SE A5BC 30BC # KATAKANA LETTER ZE A5BD 30BD # KATAKANA LETTER SO A5BE 30BE # KATAKANA LETTER ZO A5BF 30BF # KATAKANA LETTER TA A5C0 30C0 # KATAKANA LETTER DA A5C1 30C1 # KATAKANA LETTER TI A5C2 30C2 # KATAKANA LETTER DI A5C3 30C3 # KATAKANA LETTER SMALL TU A5C4 30C4 # KATAKANA LETTER TU A5C5 30C5 # KATAKANA LETTER DU A5C6 30C6 # KATAKANA LETTER TE A5C7 30C7 # KATAKANA LETTER DE A5C8 30C8 # KATAKANA LETTER TO A5C9 30C9 # KATAKANA LETTER DO A5CA 30CA # KATAKANA LETTER NA A5CB 30CB # KATAKANA LETTER NI A5CC 30CC # KATAKANA LETTER NU A5CD 30CD # KATAKANA LETTER NE A5CE 30CE # KATAKANA LETTER NO A5CF 30CF # KATAKANA LETTER HA A5D0 30D0 # KATAKANA LETTER BA A5D1 30D1 # KATAKANA LETTER PA A5D2 30D2 # KATAKANA LETTER HI A5D3 30D3 # KATAKANA LETTER BI A5D4 30D4 # KATAKANA LETTER PI A5D5 30D5 # KATAKANA LETTER HU A5D6 30D6 # KATAKANA LETTER BU A5D7 30D7 # KATAKANA LETTER PU A5D8 30D8 # KATAKANA LETTER HE A5D9 30D9 # KATAKANA LETTER BE A5DA 30DA # KATAKANA LETTER PE A5DB 30DB # KATAKANA LETTER HO A5DC 30DC # KATAKANA LETTER BO A5DD 30DD # KATAKANA LETTER PO A5DE 30DE # KATAKANA LETTER MA A5DF 30DF # KATAKANA LETTER MI A5E0 30E0 # KATAKANA LETTER MU A5E1 30E1 # KATAKANA LETTER ME A5E2 30E2 # KATAKANA LETTER MO A5E3 30E3 # KATAKANA LETTER SMALL YA A5E4 30E4 # KATAKANA LETTER YA A5E5 30E5 # KATAKANA LETTER SMALL YU A5E6 30E6 # KATAKANA LETTER YU A5E7 30E7 # KATAKANA LETTER SMALL YO A5E8 30E8 # KATAKANA LETTER YO A5E9 30E9 # KATAKANA LETTER RA A5EA 30EA # KATAKANA LETTER RI A5EB 30EB # KATAKANA LETTER RU A5EC 30EC # KATAKANA LETTER RE A5ED 30ED # KATAKANA LETTER RO A5EE 30EE # KATAKANA LETTER SMALL WA A5EF 30EF # KATAKANA LETTER WA A5F0 30F0 # KATAKANA LETTER WI A5F1 30F1 # KATAKANA LETTER WE A5F2 30F2 # KATAKANA LETTER WO A5F3 30F3 # KATAKANA LETTER N A5F4 30F4 # KATAKANA LETTER VU A5F5 30F5 # KATAKANA LETTER SMALL KA A5F6 30F6 # KATAKANA LETTER SMALL KE A6A1 0391 # GREEK CAPITAL LETTER ALPHA A6A2 0392 # GREEK CAPITAL LETTER BETA A6A3 0393 # GREEK CAPITAL LETTER GAMMA A6A4 0394 # GREEK CAPITAL LETTER DELTA A6A5 0395 # GREEK CAPITAL LETTER EPSILON A6A6 0396 # GREEK CAPITAL LETTER ZETA A6A7 0397 # GREEK CAPITAL LETTER ETA A6A8 0398 # GREEK CAPITAL LETTER THETA A6A9 0399 # GREEK CAPITAL LETTER IOTA A6AA 039A # GREEK CAPITAL LETTER KAPPA A6AB 039B # GREEK CAPITAL LETTER LAMDA A6AC 039C # GREEK CAPITAL LETTER MU A6AD 039D # GREEK CAPITAL LETTER NU A6AE 039E # GREEK CAPITAL LETTER XI A6AF 039F # GREEK CAPITAL LETTER OMICRON A6B0 03A0 # GREEK CAPITAL LETTER PI A6B1 03A1 # GREEK CAPITAL LETTER RHO A6B2 03A3 # GREEK CAPITAL LETTER SIGMA A6B3 03A4 # GREEK CAPITAL LETTER TAU A6B4 03A5 # GREEK CAPITAL LETTER UPSILON A6B5 03A6 # GREEK CAPITAL LETTER PHI A6B6 03A7 # GREEK CAPITAL LETTER CHI A6B7 03A8 # GREEK CAPITAL LETTER PSI A6B8 03A9 # GREEK CAPITAL LETTER OMEGA A6C1 03B1 # GREEK SMALL LETTER ALPHA A6C2 03B2 # GREEK SMALL LETTER BETA A6C3 03B3 # GREEK SMALL LETTER GAMMA A6C4 03B4 # GREEK SMALL LETTER DELTA A6C5 03B5 # GREEK SMALL LETTER EPSILON A6C6 03B6 # GREEK SMALL LETTER ZETA A6C7 03B7 # GREEK SMALL LETTER ETA A6C8 03B8 # GREEK SMALL LETTER THETA A6C9 03B9 # GREEK SMALL LETTER IOTA A6CA 03BA # GREEK SMALL LETTER KAPPA A6CB 03BB # GREEK SMALL LETTER LAMDA A6CC 03BC # GREEK SMALL LETTER MU A6CD 03BD # GREEK SMALL LETTER NU A6CE 03BE # GREEK SMALL LETTER XI A6CF 03BF # GREEK SMALL LETTER OMICRON A6D0 03C0 # GREEK SMALL LETTER PI A6D1 03C1 # GREEK SMALL LETTER RHO A6D2 03C3 # GREEK SMALL LETTER SIGMA A6D3 03C4 # GREEK SMALL LETTER TAU A6D4 03C5 # GREEK SMALL LETTER UPSILON A6D5 03C6 # GREEK SMALL LETTER PHI A6D6 03C7 # GREEK SMALL LETTER CHI A6D7 03C8 # GREEK SMALL LETTER PSI A6D8 03C9 # GREEK SMALL LETTER OMEGA A7A1 0410 # CYRILLIC CAPITAL LETTER A A7A2 0411 # CYRILLIC CAPITAL LETTER BE A7A3 0412 # CYRILLIC CAPITAL LETTER VE A7A4 0413 # CYRILLIC CAPITAL LETTER GHE A7A5 0414 # CYRILLIC CAPITAL LETTER DE A7A6 0415 # CYRILLIC CAPITAL LETTER IE A7A7 0401 # CYRILLIC CAPITAL LETTER IO A7A8 0416 # CYRILLIC CAPITAL LETTER ZHE A7A9 0417 # CYRILLIC CAPITAL LETTER ZE A7AA 0418 # CYRILLIC CAPITAL LETTER I A7AB 0419 # CYRILLIC CAPITAL LETTER SHORT I A7AC 041A # CYRILLIC CAPITAL LETTER KA A7AD 041B # CYRILLIC CAPITAL LETTER EL A7AE 041C # CYRILLIC CAPITAL LETTER EM A7AF 041D # CYRILLIC CAPITAL LETTER EN A7B0 041E # CYRILLIC CAPITAL LETTER O A7B1 041F # CYRILLIC CAPITAL LETTER PE A7B2 0420 # CYRILLIC CAPITAL LETTER ER A7B3 0421 # CYRILLIC CAPITAL LETTER ES A7B4 0422 # CYRILLIC CAPITAL LETTER TE A7B5 0423 # CYRILLIC CAPITAL LETTER U A7B6 0424 # CYRILLIC CAPITAL LETTER EF A7B7 0425 # CYRILLIC CAPITAL LETTER HA A7B8 0426 # CYRILLIC CAPITAL LETTER TSE A7B9 0427 # CYRILLIC CAPITAL LETTER CHE A7BA 0428 # CYRILLIC CAPITAL LETTER SHA A7BB 0429 # CYRILLIC CAPITAL LETTER SHCHA A7BC 042A # CYRILLIC CAPITAL LETTER HARD SIGN A7BD 042B # CYRILLIC CAPITAL LETTER YERU A7BE 042C # CYRILLIC CAPITAL LETTER SOFT SIGN A7BF 042D # CYRILLIC CAPITAL LETTER E A7C0 042E # CYRILLIC CAPITAL LETTER YU A7C1 042F # CYRILLIC CAPITAL LETTER YA A7D1 0430 # CYRILLIC SMALL LETTER A A7D2 0431 # CYRILLIC SMALL LETTER BE A7D3 0432 # CYRILLIC SMALL LETTER VE A7D4 0433 # CYRILLIC SMALL LETTER GHE A7D5 0434 # CYRILLIC SMALL LETTER DE A7D6 0435 # CYRILLIC SMALL LETTER IE A7D7 0451 # CYRILLIC SMALL LETTER IO A7D8 0436 # CYRILLIC SMALL LETTER ZHE A7D9 0437 # CYRILLIC SMALL LETTER ZE A7DA 0438 # CYRILLIC SMALL LETTER I A7DB 0439 # CYRILLIC SMALL LETTER SHORT I A7DC 043A # CYRILLIC SMALL LETTER KA A7DD 043B # CYRILLIC SMALL LETTER EL A7DE 043C # CYRILLIC SMALL LETTER EM A7DF 043D # CYRILLIC SMALL LETTER EN A7E0 043E # CYRILLIC SMALL LETTER O A7E1 043F # CYRILLIC SMALL LETTER PE A7E2 0440 # CYRILLIC SMALL LETTER ER A7E3 0441 # CYRILLIC SMALL LETTER ES A7E4 0442 # CYRILLIC SMALL LETTER TE A7E5 0443 # CYRILLIC SMALL LETTER U A7E6 0444 # CYRILLIC SMALL LETTER EF A7E7 0445 # CYRILLIC SMALL LETTER HA A7E8 0446 # CYRILLIC SMALL LETTER TSE A7E9 0447 # CYRILLIC SMALL LETTER CHE A7EA 0448 # CYRILLIC SMALL LETTER SHA A7EB 0449 # CYRILLIC SMALL LETTER SHCHA A7EC 044A # CYRILLIC SMALL LETTER HARD SIGN A7ED 044B # CYRILLIC SMALL LETTER YERU A7EE 044C # CYRILLIC SMALL LETTER SOFT SIGN A7EF 044D # CYRILLIC SMALL LETTER E A7F0 044E # CYRILLIC SMALL LETTER YU A7F1 044F # CYRILLIC SMALL LETTER YA A8A1 0101 # LATIN SMALL LETTER A WITH MACRON A8A2 00E1 # LATIN SMALL LETTER A WITH ACUTE A8A3 01CE # LATIN SMALL LETTER A WITH CARON A8A4 00E0 # LATIN SMALL LETTER A WITH GRAVE A8A5 0113 # LATIN SMALL LETTER E WITH MACRON A8A6 00E9 # LATIN SMALL LETTER E WITH ACUTE A8A7 011B # LATIN SMALL LETTER E WITH CARON A8A8 00E8 # LATIN SMALL LETTER E WITH GRAVE A8A9 012B # LATIN SMALL LETTER I WITH MACRON A8AA 00ED # LATIN SMALL LETTER I WITH ACUTE A8AB 01D0 # LATIN SMALL LETTER I WITH CARON A8AC 00EC # LATIN SMALL LETTER I WITH GRAVE A8AD 014D # LATIN SMALL LETTER O WITH MACRON A8AE 00F3 # LATIN SMALL LETTER O WITH ACUTE A8AF 01D2 # LATIN SMALL LETTER O WITH CARON A8B0 00F2 # LATIN SMALL LETTER O WITH GRAVE A8B1 016B # LATIN SMALL LETTER U WITH MACRON A8B2 00FA # LATIN SMALL LETTER U WITH ACUTE A8B3 01D4 # LATIN SMALL LETTER U WITH CARON A8B4 00F9 # LATIN SMALL LETTER U WITH GRAVE A8B5 01D6 # LATIN SMALL LETTER U WITH DIAERESIS AND MACRON A8B6 01D8 # LATIN SMALL LETTER U WITH DIAERESIS AND ACUTE A8B7 01DA # LATIN SMALL LETTER U WITH DIAERESIS AND CARON A8B8 01DC # LATIN SMALL LETTER U WITH DIAERESIS AND GRAVE A8B9 00FC # LATIN SMALL LETTER U WITH DIAERESIS A8BA 00EA # LATIN SMALL LETTER E WITH CIRCUMFLEX A8C5 3105 # BOPOMOFO LETTER B A8C6 3106 # BOPOMOFO LETTER P A8C7 3107 # BOPOMOFO LETTER M A8C8 3108 # BOPOMOFO LETTER F A8C9 3109 # BOPOMOFO LETTER D A8CA 310A # BOPOMOFO LETTER T A8CB 310B # BOPOMOFO LETTER N A8CC 310C # BOPOMOFO LETTER L A8CD 310D # BOPOMOFO LETTER G A8CE 310E # BOPOMOFO LETTER K A8CF 310F # BOPOMOFO LETTER H A8D0 3110 # BOPOMOFO LETTER J A8D1 3111 # BOPOMOFO LETTER Q A8D2 3112 # BOPOMOFO LETTER X A8D3 3113 # BOPOMOFO LETTER ZH A8D4 3114 # BOPOMOFO LETTER CH A8D5 3115 # BOPOMOFO LETTER SH A8D6 3116 # BOPOMOFO LETTER R A8D7 3117 # BOPOMOFO LETTER Z A8D8 3118 # BOPOMOFO LETTER C A8D9 3119 # BOPOMOFO LETTER S A8DA 311A # BOPOMOFO LETTER A A8DB 311B # BOPOMOFO LETTER O A8DC 311C # BOPOMOFO LETTER E A8DD 311D # BOPOMOFO LETTER EH A8DE 311E # BOPOMOFO LETTER AI A8DF 311F # BOPOMOFO LETTER EI A8E0 3120 # BOPOMOFO LETTER AU A8E1 3121 # BOPOMOFO LETTER OU A8E2 3122 # BOPOMOFO LETTER AN A8E3 3123 # BOPOMOFO LETTER EN A8E4 3124 # BOPOMOFO LETTER ANG A8E5 3125 # BOPOMOFO LETTER ENG A8E6 3126 # BOPOMOFO LETTER ER A8E7 3127 # BOPOMOFO LETTER I A8E8 3128 # BOPOMOFO LETTER U A8E9 3129 # BOPOMOFO LETTER IU A9A4 2500 # BOX DRAWINGS LIGHT HORIZONTAL A9A5 2501 # BOX DRAWINGS HEAVY HORIZONTAL A9A6 2502 # BOX DRAWINGS LIGHT VERTICAL A9A7 2503 # BOX DRAWINGS HEAVY VERTICAL A9A8 2504 # BOX DRAWINGS LIGHT TRIPLE DASH HORIZONTAL A9A9 2505 # BOX DRAWINGS HEAVY TRIPLE DASH HORIZONTAL A9AA 2506 # BOX DRAWINGS LIGHT TRIPLE DASH VERTICAL A9AB 2507 # BOX DRAWINGS HEAVY TRIPLE DASH VERTICAL A9AC 2508 # BOX DRAWINGS LIGHT QUADRUPLE DASH HORIZONTAL A9AD 2509 # BOX DRAWINGS HEAVY QUADRUPLE DASH HORIZONTAL A9AE 250A # BOX DRAWINGS LIGHT QUADRUPLE DASH VERTICAL A9AF 250B # BOX DRAWINGS HEAVY QUADRUPLE DASH VERTICAL A9B0 250C # BOX DRAWINGS LIGHT DOWN AND RIGHT A9B1 250D # BOX DRAWINGS DOWN LIGHT AND RIGHT HEAVY A9B2 250E # BOX DRAWINGS DOWN HEAVY AND RIGHT LIGHT A9B3 250F # BOX DRAWINGS HEAVY DOWN AND RIGHT A9B4 2510 # BOX DRAWINGS LIGHT DOWN AND LEFT A9B5 2511 # BOX DRAWINGS DOWN LIGHT AND LEFT HEAVY A9B6 2512 # BOX DRAWINGS DOWN HEAVY AND LEFT LIGHT A9B7 2513 # BOX DRAWINGS HEAVY DOWN AND LEFT A9B8 2514 # BOX DRAWINGS LIGHT UP AND RIGHT A9B9 2515 # BOX DRAWINGS UP LIGHT AND RIGHT HEAVY A9BA 2516 # BOX DRAWINGS UP HEAVY AND RIGHT LIGHT A9BB 2517 # BOX DRAWINGS HEAVY UP AND RIGHT A9BC 2518 # BOX DRAWINGS LIGHT UP AND LEFT A9BD 2519 # BOX DRAWINGS UP LIGHT AND LEFT HEAVY A9BE 251A # BOX DRAWINGS UP HEAVY AND LEFT LIGHT A9BF 251B # BOX DRAWINGS HEAVY UP AND LEFT A9C0 251C # BOX DRAWINGS LIGHT VERTICAL AND RIGHT A9C1 251D # BOX DRAWINGS VERTICAL LIGHT AND RIGHT HEAVY A9C2 251E # BOX DRAWINGS UP HEAVY AND RIGHT DOWN LIGHT A9C3 251F # BOX DRAWINGS DOWN HEAVY AND RIGHT UP LIGHT A9C4 2520 # BOX DRAWINGS VERTICAL HEAVY AND RIGHT LIGHT A9C5 2521 # BOX DRAWINGS DOWN LIGHT AND RIGHT UP HEAVY A9C6 2522 # BOX DRAWINGS UP LIGHT AND RIGHT DOWN HEAVY A9C7 2523 # BOX DRAWINGS HEAVY VERTICAL AND RIGHT A9C8 2524 # BOX DRAWINGS LIGHT VERTICAL AND LEFT A9C9 2525 # BOX DRAWINGS VERTICAL LIGHT AND LEFT HEAVY A9CA 2526 # BOX DRAWINGS UP HEAVY AND LEFT DOWN LIGHT A9CB 2527 # BOX DRAWINGS DOWN HEAVY AND LEFT UP LIGHT A9CC 2528 # BOX DRAWINGS VERTICAL HEAVY AND LEFT LIGHT A9CD 2529 # BOX DRAWINGS DOWN LIGHT AND LEFT UP HEAVY A9CE 252A # BOX DRAWINGS UP LIGHT AND LEFT DOWN HEAVY A9CF 252B # BOX DRAWINGS HEAVY VERTICAL AND LEFT A9D0 252C # BOX DRAWINGS LIGHT DOWN AND HORIZONTAL A9D1 252D # BOX DRAWINGS LEFT HEAVY AND RIGHT DOWN LIGHT A9D2 252E # BOX DRAWINGS RIGHT HEAVY AND LEFT DOWN LIGHT A9D3 252F # BOX DRAWINGS DOWN LIGHT AND HORIZONTAL HEAVY A9D4 2530 # BOX DRAWINGS DOWN HEAVY AND HORIZONTAL LIGHT A9D5 2531 # BOX DRAWINGS RIGHT LIGHT AND LEFT DOWN HEAVY A9D6 2532 # BOX DRAWINGS LEFT LIGHT AND RIGHT DOWN HEAVY A9D7 2533 # BOX DRAWINGS HEAVY DOWN AND HORIZONTAL A9D8 2534 # BOX DRAWINGS LIGHT UP AND HORIZONTAL A9D9 2535 # BOX DRAWINGS LEFT HEAVY AND RIGHT UP LIGHT A9DA 2536 # BOX DRAWINGS RIGHT HEAVY AND LEFT UP LIGHT A9DB 2537 # BOX DRAWINGS UP LIGHT AND HORIZONTAL HEAVY A9DC 2538 # BOX DRAWINGS UP HEAVY AND HORIZONTAL LIGHT A9DD 2539 # BOX DRAWINGS RIGHT LIGHT AND LEFT UP HEAVY A9DE 253A # BOX DRAWINGS LEFT LIGHT AND RIGHT UP HEAVY A9DF 253B # BOX DRAWINGS HEAVY UP AND HORIZONTAL A9E0 253C # BOX DRAWINGS LIGHT VERTICAL AND HORIZONTAL A9E1 253D # BOX DRAWINGS LEFT HEAVY AND RIGHT VERTICAL LIGHT A9E2 253E # BOX DRAWINGS RIGHT HEAVY AND LEFT VERTICAL LIGHT A9E3 253F # BOX DRAWINGS VERTICAL LIGHT AND HORIZONTAL HEAVY A9E4 2540 # BOX DRAWINGS UP HEAVY AND DOWN HORIZONTAL LIGHT A9E5 2541 # BOX DRAWINGS DOWN HEAVY AND UP HORIZONTAL LIGHT A9E6 2542 # BOX DRAWINGS VERTICAL HEAVY AND HORIZONTAL LIGHT A9E7 2543 # BOX DRAWINGS LEFT UP HEAVY AND RIGHT DOWN LIGHT A9E8 2544 # BOX DRAWINGS RIGHT UP HEAVY AND LEFT DOWN LIGHT A9E9 2545 # BOX DRAWINGS LEFT DOWN HEAVY AND RIGHT UP LIGHT A9EA 2546 # BOX DRAWINGS RIGHT DOWN HEAVY AND LEFT UP LIGHT A9EB 2547 # BOX DRAWINGS DOWN LIGHT AND UP HORIZONTAL HEAVY A9EC 2548 # BOX DRAWINGS UP LIGHT AND DOWN HORIZONTAL HEAVY A9ED 2549 # BOX DRAWINGS RIGHT LIGHT AND LEFT VERTICAL HEAVY A9EE 254A # BOX DRAWINGS LEFT LIGHT AND RIGHT VERTICAL HEAVY A9EF 254B # BOX DRAWINGS HEAVY VERTICAL AND HORIZONTAL B0A1 554A # B0A2 963F # B0A3 57C3 # B0A4 6328 # B0A5 54CE # B0A6 5509 # B0A7 54C0 # B0A8 7691 # B0A9 764C # B0AA 853C # B0AB 77EE # B0AC 827E # B0AD 788D # B0AE 7231 # B0AF 9698 # B0B0 978D # B0B1 6C28 # B0B2 5B89 # B0B3 4FFA # B0B4 6309 # B0B5 6697 # B0B6 5CB8 # B0B7 80FA # B0B8 6848 # B0B9 80AE # B0BA 6602 # B0BB 76CE # B0BC 51F9 # B0BD 6556 # B0BE 71AC # B0BF 7FF1 # B0C0 8884 # B0C1 50B2 # B0C2 5965 # B0C3 61CA # B0C4 6FB3 # B0C5 82AD # B0C6 634C # B0C7 6252 # B0C8 53ED # B0C9 5427 # B0CA 7B06 # B0CB 516B # B0CC 75A4 # B0CD 5DF4 # B0CE 62D4 # B0CF 8DCB # B0D0 9776 # B0D1 628A # B0D2 8019 # B0D3 575D # B0D4 9738 # B0D5 7F62 # B0D6 7238 # B0D7 767D # B0D8 67CF # B0D9 767E # B0DA 6446 # B0DB 4F70 # B0DC 8D25 # B0DD 62DC # B0DE 7A17 # B0DF 6591 # B0E0 73ED # B0E1 642C # B0E2 6273 # B0E3 822C # B0E4 9881 # B0E5 677F # B0E6 7248 # B0E7 626E # B0E8 62CC # B0E9 4F34 # B0EA 74E3 # B0EB 534A # B0EC 529E # B0ED 7ECA # B0EE 90A6 # B0EF 5E2E # B0F0 6886 # B0F1 699C # B0F2 8180 # B0F3 7ED1 # B0F4 68D2 # B0F5 78C5 # B0F6 868C # B0F7 9551 # B0F8 508D # B0F9 8C24 # B0FA 82DE # B0FB 80DE # B0FC 5305 # B0FD 8912 # B0FE 5265 # B1A1 8584 # B1A2 96F9 # B1A3 4FDD # B1A4 5821 # B1A5 9971 # B1A6 5B9D # B1A7 62B1 # B1A8 62A5 # B1A9 66B4 # B1AA 8C79 # B1AB 9C8D # B1AC 7206 # B1AD 676F # B1AE 7891 # B1AF 60B2 # B1B0 5351 # B1B1 5317 # B1B2 8F88 # B1B3 80CC # B1B4 8D1D # B1B5 94A1 # B1B6 500D # B1B7 72C8 # B1B8 5907 # B1B9 60EB # B1BA 7119 # B1BB 88AB # B1BC 5954 # B1BD 82EF # B1BE 672C # B1BF 7B28 # B1C0 5D29 # B1C1 7EF7 # B1C2 752D # B1C3 6CF5 # B1C4 8E66 # B1C5 8FF8 # B1C6 903C # B1C7 9F3B # B1C8 6BD4 # B1C9 9119 # B1CA 7B14 # B1CB 5F7C # B1CC 78A7 # B1CD 84D6 # B1CE 853D # B1CF 6BD5 # B1D0 6BD9 # B1D1 6BD6 # B1D2 5E01 # B1D3 5E87 # B1D4 75F9 # B1D5 95ED # B1D6 655D # B1D7 5F0A # B1D8 5FC5 # B1D9 8F9F # B1DA 58C1 # B1DB 81C2 # B1DC 907F # B1DD 965B # B1DE 97AD # B1DF 8FB9 # B1E0 7F16 # B1E1 8D2C # B1E2 6241 # B1E3 4FBF # B1E4 53D8 # B1E5 535E # B1E6 8FA8 # B1E7 8FA9 # B1E8 8FAB # B1E9 904D # B1EA 6807 # B1EB 5F6A # B1EC 8198 # B1ED 8868 # B1EE 9CD6 # B1EF 618B # B1F0 522B # B1F1 762A # B1F2 5F6C # B1F3 658C # B1F4 6FD2 # B1F5 6EE8 # B1F6 5BBE # B1F7 6448 # B1F8 5175 # B1F9 51B0 # B1FA 67C4 # B1FB 4E19 # B1FC 79C9 # B1FD 997C # B1FE 70B3 # B2A1 75C5 # B2A2 5E76 # B2A3 73BB # B2A4 83E0 # B2A5 64AD # B2A6 62E8 # B2A7 94B5 # B2A8 6CE2 # B2A9 535A # B2AA 52C3 # B2AB 640F # B2AC 94C2 # B2AD 7B94 # B2AE 4F2F # B2AF 5E1B # B2B0 8236 # B2B1 8116 # B2B2 818A # B2B3 6E24 # B2B4 6CCA # B2B5 9A73 # B2B6 6355 # B2B7 535C # B2B8 54FA # B2B9 8865 # B2BA 57E0 # B2BB 4E0D # B2BC 5E03 # B2BD 6B65 # B2BE 7C3F # B2BF 90E8 # B2C0 6016 # B2C1 64E6 # B2C2 731C # B2C3 88C1 # B2C4 6750 # B2C5 624D # B2C6 8D22 # B2C7 776C # B2C8 8E29 # B2C9 91C7 # B2CA 5F69 # B2CB 83DC # B2CC 8521 # B2CD 9910 # B2CE 53C2 # B2CF 8695 # B2D0 6B8B # B2D1 60ED # B2D2 60E8 # B2D3 707F # B2D4 82CD # B2D5 8231 # B2D6 4ED3 # B2D7 6CA7 # B2D8 85CF # B2D9 64CD # B2DA 7CD9 # B2DB 69FD # B2DC 66F9 # B2DD 8349 # B2DE 5395 # B2DF 7B56 # B2E0 4FA7 # B2E1 518C # B2E2 6D4B # B2E3 5C42 # B2E4 8E6D # B2E5 63D2 # B2E6 53C9 # B2E7 832C # B2E8 8336 # B2E9 67E5 # B2EA 78B4 # B2EB 643D # B2EC 5BDF # B2ED 5C94 # B2EE 5DEE # B2EF 8BE7 # B2F0 62C6 # B2F1 67F4 # B2F2 8C7A # B2F3 6400 # B2F4 63BA # B2F5 8749 # B2F6 998B # B2F7 8C17 # B2F8 7F20 # B2F9 94F2 # B2FA 4EA7 # B2FB 9610 # B2FC 98A4 # B2FD 660C # B2FE 7316 # B3A1 573A # B3A2 5C1D # B3A3 5E38 # B3A4 957F # B3A5 507F # B3A6 80A0 # B3A7 5382 # B3A8 655E # B3A9 7545 # B3AA 5531 # B3AB 5021 # B3AC 8D85 # B3AD 6284 # B3AE 949E # B3AF 671D # B3B0 5632 # B3B1 6F6E # B3B2 5DE2 # B3B3 5435 # B3B4 7092 # B3B5 8F66 # B3B6 626F # B3B7 64A4 # B3B8 63A3 # B3B9 5F7B # B3BA 6F88 # B3BB 90F4 # B3BC 81E3 # B3BD 8FB0 # B3BE 5C18 # B3BF 6668 # B3C0 5FF1 # B3C1 6C89 # B3C2 9648 # B3C3 8D81 # B3C4 886C # B3C5 6491 # B3C6 79F0 # B3C7 57CE # B3C8 6A59 # B3C9 6210 # B3CA 5448 # B3CB 4E58 # B3CC 7A0B # B3CD 60E9 # B3CE 6F84 # B3CF 8BDA # B3D0 627F # B3D1 901E # B3D2 9A8B # B3D3 79E4 # B3D4 5403 # B3D5 75F4 # B3D6 6301 # B3D7 5319 # B3D8 6C60 # B3D9 8FDF # B3DA 5F1B # B3DB 9A70 # B3DC 803B # B3DD 9F7F # B3DE 4F88 # B3DF 5C3A # B3E0 8D64 # B3E1 7FC5 # B3E2 65A5 # B3E3 70BD # B3E4 5145 # B3E5 51B2 # B3E6 866B # B3E7 5D07 # B3E8 5BA0 # B3E9 62BD # B3EA 916C # B3EB 7574 # B3EC 8E0C # B3ED 7A20 # B3EE 6101 # B3EF 7B79 # B3F0 4EC7 # B3F1 7EF8 # B3F2 7785 # B3F3 4E11 # B3F4 81ED # B3F5 521D # B3F6 51FA # B3F7 6A71 # B3F8 53A8 # B3F9 8E87 # B3FA 9504 # B3FB 96CF # B3FC 6EC1 # B3FD 9664 # B3FE 695A # B4A1 7840 # B4A2 50A8 # B4A3 77D7 # B4A4 6410 # B4A5 89E6 # B4A6 5904 # B4A7 63E3 # B4A8 5DDD # B4A9 7A7F # B4AA 693D # B4AB 4F20 # B4AC 8239 # B4AD 5598 # B4AE 4E32 # B4AF 75AE # B4B0 7A97 # B4B1 5E62 # B4B2 5E8A # B4B3 95EF # B4B4 521B # B4B5 5439 # B4B6 708A # B4B7 6376 # B4B8 9524 # B4B9 5782 # B4BA 6625 # B4BB 693F # B4BC 9187 # B4BD 5507 # B4BE 6DF3 # B4BF 7EAF # B4C0 8822 # B4C1 6233 # B4C2 7EF0 # B4C3 75B5 # B4C4 8328 # B4C5 78C1 # B4C6 96CC # B4C7 8F9E # B4C8 6148 # B4C9 74F7 # B4CA 8BCD # B4CB 6B64 # B4CC 523A # B4CD 8D50 # B4CE 6B21 # B4CF 806A # B4D0 8471 # B4D1 56F1 # B4D2 5306 # B4D3 4ECE # B4D4 4E1B # B4D5 51D1 # B4D6 7C97 # B4D7 918B # B4D8 7C07 # B4D9 4FC3 # B4DA 8E7F # B4DB 7BE1 # B4DC 7A9C # B4DD 6467 # B4DE 5D14 # B4DF 50AC # B4E0 8106 # B4E1 7601 # B4E2 7CB9 # B4E3 6DEC # B4E4 7FE0 # B4E5 6751 # B4E6 5B58 # B4E7 5BF8 # B4E8 78CB # B4E9 64AE # B4EA 6413 # B4EB 63AA # B4EC 632B # B4ED 9519 # B4EE 642D # B4EF 8FBE # B4F0 7B54 # B4F1 7629 # B4F2 6253 # B4F3 5927 # B4F4 5446 # B4F5 6B79 # B4F6 50A3 # B4F7 6234 # B4F8 5E26 # B4F9 6B86 # B4FA 4EE3 # B4FB 8D37 # B4FC 888B # B4FD 5F85 # B4FE 902E # B5A1 6020 # B5A2 803D # B5A3 62C5 # B5A4 4E39 # B5A5 5355 # B5A6 90F8 # B5A7 63B8 # B5A8 80C6 # B5A9 65E6 # B5AA 6C2E # B5AB 4F46 # B5AC 60EE # B5AD 6DE1 # B5AE 8BDE # B5AF 5F39 # B5B0 86CB # B5B1 5F53 # B5B2 6321 # B5B3 515A # B5B4 8361 # B5B5 6863 # B5B6 5200 # B5B7 6363 # B5B8 8E48 # B5B9 5012 # B5BA 5C9B # B5BB 7977 # B5BC 5BFC # B5BD 5230 # B5BE 7A3B # B5BF 60BC # B5C0 9053 # B5C1 76D7 # B5C2 5FB7 # B5C3 5F97 # B5C4 7684 # B5C5 8E6C # B5C6 706F # B5C7 767B # B5C8 7B49 # B5C9 77AA # B5CA 51F3 # B5CB 9093 # B5CC 5824 # B5CD 4F4E # B5CE 6EF4 # B5CF 8FEA # B5D0 654C # B5D1 7B1B # B5D2 72C4 # B5D3 6DA4 # B5D4 7FDF # B5D5 5AE1 # B5D6 62B5 # B5D7 5E95 # B5D8 5730 # B5D9 8482 # B5DA 7B2C # B5DB 5E1D # B5DC 5F1F # B5DD 9012 # B5DE 7F14 # B5DF 98A0 # B5E0 6382 # B5E1 6EC7 # B5E2 7898 # B5E3 70B9 # B5E4 5178 # B5E5 975B # B5E6 57AB # B5E7 7535 # B5E8 4F43 # B5E9 7538 # B5EA 5E97 # B5EB 60E6 # B5EC 5960 # B5ED 6DC0 # B5EE 6BBF # B5EF 7889 # B5F0 53FC # B5F1 96D5 # B5F2 51CB # B5F3 5201 # B5F4 6389 # B5F5 540A # B5F6 9493 # B5F7 8C03 # B5F8 8DCC # B5F9 7239 # B5FA 789F # B5FB 8776 # B5FC 8FED # B5FD 8C0D # B5FE 53E0 # B6A1 4E01 # B6A2 76EF # B6A3 53EE # B6A4 9489 # B6A5 9876 # B6A6 9F0E # B6A7 952D # B6A8 5B9A # B6A9 8BA2 # B6AA 4E22 # B6AB 4E1C # B6AC 51AC # B6AD 8463 # B6AE 61C2 # B6AF 52A8 # B6B0 680B # B6B1 4F97 # B6B2 606B # B6B3 51BB # B6B4 6D1E # B6B5 515C # B6B6 6296 # B6B7 6597 # B6B8 9661 # B6B9 8C46 # B6BA 9017 # B6BB 75D8 # B6BC 90FD # B6BD 7763 # B6BE 6BD2 # B6BF 728A # B6C0 72EC # B6C1 8BFB # B6C2 5835 # B6C3 7779 # B6C4 8D4C # B6C5 675C # B6C6 9540 # B6C7 809A # B6C8 5EA6 # B6C9 6E21 # B6CA 5992 # B6CB 7AEF # B6CC 77ED # B6CD 953B # B6CE 6BB5 # B6CF 65AD # B6D0 7F0E # B6D1 5806 # B6D2 5151 # B6D3 961F # B6D4 5BF9 # B6D5 58A9 # B6D6 5428 # B6D7 8E72 # B6D8 6566 # B6D9 987F # B6DA 56E4 # B6DB 949D # B6DC 76FE # B6DD 9041 # B6DE 6387 # B6DF 54C6 # B6E0 591A # B6E1 593A # B6E2 579B # B6E3 8EB2 # B6E4 6735 # B6E5 8DFA # B6E6 8235 # B6E7 5241 # B6E8 60F0 # B6E9 5815 # B6EA 86FE # B6EB 5CE8 # B6EC 9E45 # B6ED 4FC4 # B6EE 989D # B6EF 8BB9 # B6F0 5A25 # B6F1 6076 # B6F2 5384 # B6F3 627C # B6F4 904F # B6F5 9102 # B6F6 997F # B6F7 6069 # B6F8 800C # B6F9 513F # B6FA 8033 # B6FB 5C14 # B6FC 9975 # B6FD 6D31 # B6FE 4E8C # B7A1 8D30 # B7A2 53D1 # B7A3 7F5A # B7A4 7B4F # B7A5 4F10 # B7A6 4E4F # B7A7 9600 # B7A8 6CD5 # B7A9 73D0 # B7AA 85E9 # B7AB 5E06 # B7AC 756A # B7AD 7FFB # B7AE 6A0A # B7AF 77FE # B7B0 9492 # B7B1 7E41 # B7B2 51E1 # B7B3 70E6 # B7B4 53CD # B7B5 8FD4 # B7B6 8303 # B7B7 8D29 # B7B8 72AF # B7B9 996D # B7BA 6CDB # B7BB 574A # B7BC 82B3 # B7BD 65B9 # B7BE 80AA # B7BF 623F # B7C0 9632 # B7C1 59A8 # B7C2 4EFF # B7C3 8BBF # B7C4 7EBA # B7C5 653E # B7C6 83F2 # B7C7 975E # B7C8 5561 # B7C9 98DE # B7CA 80A5 # B7CB 532A # B7CC 8BFD # B7CD 5420 # B7CE 80BA # B7CF 5E9F # B7D0 6CB8 # B7D1 8D39 # B7D2 82AC # B7D3 915A # B7D4 5429 # B7D5 6C1B # B7D6 5206 # B7D7 7EB7 # B7D8 575F # B7D9 711A # B7DA 6C7E # B7DB 7C89 # B7DC 594B # B7DD 4EFD # B7DE 5FFF # B7DF 6124 # B7E0 7CAA # B7E1 4E30 # B7E2 5C01 # B7E3 67AB # B7E4 8702 # B7E5 5CF0 # B7E6 950B # B7E7 98CE # B7E8 75AF # B7E9 70FD # B7EA 9022 # B7EB 51AF # B7EC 7F1D # B7ED 8BBD # B7EE 5949 # B7EF 51E4 # B7F0 4F5B # B7F1 5426 # B7F2 592B # B7F3 6577 # B7F4 80A4 # B7F5 5B75 # B7F6 6276 # B7F7 62C2 # B7F8 8F90 # B7F9 5E45 # B7FA 6C1F # B7FB 7B26 # B7FC 4F0F # B7FD 4FD8 # B7FE 670D # B8A1 6D6E # B8A2 6DAA # B8A3 798F # B8A4 88B1 # B8A5 5F17 # B8A6 752B # B8A7 629A # B8A8 8F85 # B8A9 4FEF # B8AA 91DC # B8AB 65A7 # B8AC 812F # B8AD 8151 # B8AE 5E9C # B8AF 8150 # B8B0 8D74 # B8B1 526F # B8B2 8986 # B8B3 8D4B # B8B4 590D # B8B5 5085 # B8B6 4ED8 # B8B7 961C # B8B8 7236 # B8B9 8179 # B8BA 8D1F # B8BB 5BCC # B8BC 8BA3 # B8BD 9644 # B8BE 5987 # B8BF 7F1A # B8C0 5490 # B8C1 5676 # B8C2 560E # B8C3 8BE5 # B8C4 6539 # B8C5 6982 # B8C6 9499 # B8C7 76D6 # B8C8 6E89 # B8C9 5E72 # B8CA 7518 # B8CB 6746 # B8CC 67D1 # B8CD 7AFF # B8CE 809D # B8CF 8D76 # B8D0 611F # B8D1 79C6 # B8D2 6562 # B8D3 8D63 # B8D4 5188 # B8D5 521A # B8D6 94A2 # B8D7 7F38 # B8D8 809B # B8D9 7EB2 # B8DA 5C97 # B8DB 6E2F # B8DC 6760 # B8DD 7BD9 # B8DE 768B # B8DF 9AD8 # B8E0 818F # B8E1 7F94 # B8E2 7CD5 # B8E3 641E # B8E4 9550 # B8E5 7A3F # B8E6 544A # B8E7 54E5 # B8E8 6B4C # B8E9 6401 # B8EA 6208 # B8EB 9E3D # B8EC 80F3 # B8ED 7599 # B8EE 5272 # B8EF 9769 # B8F0 845B # B8F1 683C # B8F2 86E4 # B8F3 9601 # B8F4 9694 # B8F5 94EC # B8F6 4E2A # B8F7 5404 # B8F8 7ED9 # B8F9 6839 # B8FA 8DDF # B8FB 8015 # B8FC 66F4 # B8FD 5E9A # B8FE 7FB9 # B9A1 57C2 # B9A2 803F # B9A3 6897 # B9A4 5DE5 # B9A5 653B # B9A6 529F # B9A7 606D # B9A8 9F9A # B9A9 4F9B # B9AA 8EAC # B9AB 516C # B9AC 5BAB # B9AD 5F13 # B9AE 5DE9 # B9AF 6C5E # B9B0 62F1 # B9B1 8D21 # B9B2 5171 # B9B3 94A9 # B9B4 52FE # B9B5 6C9F # B9B6 82DF # B9B7 72D7 # B9B8 57A2 # B9B9 6784 # B9BA 8D2D # B9BB 591F # B9BC 8F9C # B9BD 83C7 # B9BE 5495 # B9BF 7B8D # B9C0 4F30 # B9C1 6CBD # B9C2 5B64 # B9C3 59D1 # B9C4 9F13 # B9C5 53E4 # B9C6 86CA # B9C7 9AA8 # B9C8 8C37 # B9C9 80A1 # B9CA 6545 # B9CB 987E # B9CC 56FA # B9CD 96C7 # B9CE 522E # B9CF 74DC # B9D0 5250 # B9D1 5BE1 # B9D2 6302 # B9D3 8902 # B9D4 4E56 # B9D5 62D0 # B9D6 602A # B9D7 68FA # B9D8 5173 # B9D9 5B98 # B9DA 51A0 # B9DB 89C2 # B9DC 7BA1 # B9DD 9986 # B9DE 7F50 # B9DF 60EF # B9E0 704C # B9E1 8D2F # B9E2 5149 # B9E3 5E7F # B9E4 901B # B9E5 7470 # B9E6 89C4 # B9E7 572D # B9E8 7845 # B9E9 5F52 # B9EA 9F9F # B9EB 95FA # B9EC 8F68 # B9ED 9B3C # B9EE 8BE1 # B9EF 7678 # B9F0 6842 # B9F1 67DC # B9F2 8DEA # B9F3 8D35 # B9F4 523D # B9F5 8F8A # B9F6 6EDA # B9F7 68CD # B9F8 9505 # B9F9 90ED # B9FA 56FD # B9FB 679C # B9FC 88F9 # B9FD 8FC7 # B9FE 54C8 # BAA1 9AB8 # BAA2 5B69 # BAA3 6D77 # BAA4 6C26 # BAA5 4EA5 # BAA6 5BB3 # BAA7 9A87 # BAA8 9163 # BAA9 61A8 # BAAA 90AF # BAAB 97E9 # BAAC 542B # BAAD 6DB5 # BAAE 5BD2 # BAAF 51FD # BAB0 558A # BAB1 7F55 # BAB2 7FF0 # BAB3 64BC # BAB4 634D # BAB5 65F1 # BAB6 61BE # BAB7 608D # BAB8 710A # BAB9 6C57 # BABA 6C49 # BABB 592F # BABC 676D # BABD 822A # BABE 58D5 # BABF 568E # BAC0 8C6A # BAC1 6BEB # BAC2 90DD # BAC3 597D # BAC4 8017 # BAC5 53F7 # BAC6 6D69 # BAC7 5475 # BAC8 559D # BAC9 8377 # BACA 83CF # BACB 6838 # BACC 79BE # BACD 548C # BACE 4F55 # BACF 5408 # BAD0 76D2 # BAD1 8C89 # BAD2 9602 # BAD3 6CB3 # BAD4 6DB8 # BAD5 8D6B # BAD6 8910 # BAD7 9E64 # BAD8 8D3A # BAD9 563F # BADA 9ED1 # BADB 75D5 # BADC 5F88 # BADD 72E0 # BADE 6068 # BADF 54FC # BAE0 4EA8 # BAE1 6A2A # BAE2 8861 # BAE3 6052 # BAE4 8F70 # BAE5 54C4 # BAE6 70D8 # BAE7 8679 # BAE8 9E3F # BAE9 6D2A # BAEA 5B8F # BAEB 5F18 # BAEC 7EA2 # BAED 5589 # BAEE 4FAF # BAEF 7334 # BAF0 543C # BAF1 539A # BAF2 5019 # BAF3 540E # BAF4 547C # BAF5 4E4E # BAF6 5FFD # BAF7 745A # BAF8 58F6 # BAF9 846B # BAFA 80E1 # BAFB 8774 # BAFC 72D0 # BAFD 7CCA # BAFE 6E56 # BBA1 5F27 # BBA2 864E # BBA3 552C # BBA4 62A4 # BBA5 4E92 # BBA6 6CAA # BBA7 6237 # BBA8 82B1 # BBA9 54D7 # BBAA 534E # BBAB 733E # BBAC 6ED1 # BBAD 753B # BBAE 5212 # BBAF 5316 # BBB0 8BDD # BBB1 69D0 # BBB2 5F8A # BBB3 6000 # BBB4 6DEE # BBB5 574F # BBB6 6B22 # BBB7 73AF # BBB8 6853 # BBB9 8FD8 # BBBA 7F13 # BBBB 6362 # BBBC 60A3 # BBBD 5524 # BBBE 75EA # BBBF 8C62 # BBC0 7115 # BBC1 6DA3 # BBC2 5BA6 # BBC3 5E7B # BBC4 8352 # BBC5 614C # BBC6 9EC4 # BBC7 78FA # BBC8 8757 # BBC9 7C27 # BBCA 7687 # BBCB 51F0 # BBCC 60F6 # BBCD 714C # BBCE 6643 # BBCF 5E4C # BBD0 604D # BBD1 8C0E # BBD2 7070 # BBD3 6325 # BBD4 8F89 # BBD5 5FBD # BBD6 6062 # BBD7 86D4 # BBD8 56DE # BBD9 6BC1 # BBDA 6094 # BBDB 6167 # BBDC 5349 # BBDD 60E0 # BBDE 6666 # BBDF 8D3F # BBE0 79FD # BBE1 4F1A # BBE2 70E9 # BBE3 6C47 # BBE4 8BB3 # BBE5 8BF2 # BBE6 7ED8 # BBE7 8364 # BBE8 660F # BBE9 5A5A # BBEA 9B42 # BBEB 6D51 # BBEC 6DF7 # BBED 8C41 # BBEE 6D3B # BBEF 4F19 # BBF0 706B # BBF1 83B7 # BBF2 6216 # BBF3 60D1 # BBF4 970D # BBF5 8D27 # BBF6 7978 # BBF7 51FB # BBF8 573E # BBF9 57FA # BBFA 673A # BBFB 7578 # BBFC 7A3D # BBFD 79EF # BBFE 7B95 # BCA1 808C # BCA2 9965 # BCA3 8FF9 # BCA4 6FC0 # BCA5 8BA5 # BCA6 9E21 # BCA7 59EC # BCA8 7EE9 # BCA9 7F09 # BCAA 5409 # BCAB 6781 # BCAC 68D8 # BCAD 8F91 # BCAE 7C4D # BCAF 96C6 # BCB0 53CA # BCB1 6025 # BCB2 75BE # BCB3 6C72 # BCB4 5373 # BCB5 5AC9 # BCB6 7EA7 # BCB7 6324 # BCB8 51E0 # BCB9 810A # BCBA 5DF1 # BCBB 84DF # BCBC 6280 # BCBD 5180 # BCBE 5B63 # BCBF 4F0E # BCC0 796D # BCC1 5242 # BCC2 60B8 # BCC3 6D4E # BCC4 5BC4 # BCC5 5BC2 # BCC6 8BA1 # BCC7 8BB0 # BCC8 65E2 # BCC9 5FCC # BCCA 9645 # BCCB 5993 # BCCC 7EE7 # BCCD 7EAA # BCCE 5609 # BCCF 67B7 # BCD0 5939 # BCD1 4F73 # BCD2 5BB6 # BCD3 52A0 # BCD4 835A # BCD5 988A # BCD6 8D3E # BCD7 7532 # BCD8 94BE # BCD9 5047 # BCDA 7A3C # BCDB 4EF7 # BCDC 67B6 # BCDD 9A7E # BCDE 5AC1 # BCDF 6B7C # BCE0 76D1 # BCE1 575A # BCE2 5C16 # BCE3 7B3A # BCE4 95F4 # BCE5 714E # BCE6 517C # BCE7 80A9 # BCE8 8270 # BCE9 5978 # BCEA 7F04 # BCEB 8327 # BCEC 68C0 # BCED 67EC # BCEE 78B1 # BCEF 7877 # BCF0 62E3 # BCF1 6361 # BCF2 7B80 # BCF3 4FED # BCF4 526A # BCF5 51CF # BCF6 8350 # BCF7 69DB # BCF8 9274 # BCF9 8DF5 # BCFA 8D31 # BCFB 89C1 # BCFC 952E # BCFD 7BAD # BCFE 4EF6 # BDA1 5065 # BDA2 8230 # BDA3 5251 # BDA4 996F # BDA5 6E10 # BDA6 6E85 # BDA7 6DA7 # BDA8 5EFA # BDA9 50F5 # BDAA 59DC # BDAB 5C06 # BDAC 6D46 # BDAD 6C5F # BDAE 7586 # BDAF 848B # BDB0 6868 # BDB1 5956 # BDB2 8BB2 # BDB3 5320 # BDB4 9171 # BDB5 964D # BDB6 8549 # BDB7 6912 # BDB8 7901 # BDB9 7126 # BDBA 80F6 # BDBB 4EA4 # BDBC 90CA # BDBD 6D47 # BDBE 9A84 # BDBF 5A07 # BDC0 56BC # BDC1 6405 # BDC2 94F0 # BDC3 77EB # BDC4 4FA5 # BDC5 811A # BDC6 72E1 # BDC7 89D2 # BDC8 997A # BDC9 7F34 # BDCA 7EDE # BDCB 527F # BDCC 6559 # BDCD 9175 # BDCE 8F7F # BDCF 8F83 # BDD0 53EB # BDD1 7A96 # BDD2 63ED # BDD3 63A5 # BDD4 7686 # BDD5 79F8 # BDD6 8857 # BDD7 9636 # BDD8 622A # BDD9 52AB # BDDA 8282 # BDDB 6854 # BDDC 6770 # BDDD 6377 # BDDE 776B # BDDF 7AED # BDE0 6D01 # BDE1 7ED3 # BDE2 89E3 # BDE3 59D0 # BDE4 6212 # BDE5 85C9 # BDE6 82A5 # BDE7 754C # BDE8 501F # BDE9 4ECB # BDEA 75A5 # BDEB 8BEB # BDEC 5C4A # BDED 5DFE # BDEE 7B4B # BDEF 65A4 # BDF0 91D1 # BDF1 4ECA # BDF2 6D25 # BDF3 895F # BDF4 7D27 # BDF5 9526 # BDF6 4EC5 # BDF7 8C28 # BDF8 8FDB # BDF9 9773 # BDFA 664B # BDFB 7981 # BDFC 8FD1 # BDFD 70EC # BDFE 6D78 # BEA1 5C3D # BEA2 52B2 # BEA3 8346 # BEA4 5162 # BEA5 830E # BEA6 775B # BEA7 6676 # BEA8 9CB8 # BEA9 4EAC # BEAA 60CA # BEAB 7CBE # BEAC 7CB3 # BEAD 7ECF # BEAE 4E95 # BEAF 8B66 # BEB0 666F # BEB1 9888 # BEB2 9759 # BEB3 5883 # BEB4 656C # BEB5 955C # BEB6 5F84 # BEB7 75C9 # BEB8 9756 # BEB9 7ADF # BEBA 7ADE # BEBB 51C0 # BEBC 70AF # BEBD 7A98 # BEBE 63EA # BEBF 7A76 # BEC0 7EA0 # BEC1 7396 # BEC2 97ED # BEC3 4E45 # BEC4 7078 # BEC5 4E5D # BEC6 9152 # BEC7 53A9 # BEC8 6551 # BEC9 65E7 # BECA 81FC # BECB 8205 # BECC 548E # BECD 5C31 # BECE 759A # BECF 97A0 # BED0 62D8 # BED1 72D9 # BED2 75BD # BED3 5C45 # BED4 9A79 # BED5 83CA # BED6 5C40 # BED7 5480 # BED8 77E9 # BED9 4E3E # BEDA 6CAE # BEDB 805A # BEDC 62D2 # BEDD 636E # BEDE 5DE8 # BEDF 5177 # BEE0 8DDD # BEE1 8E1E # BEE2 952F # BEE3 4FF1 # BEE4 53E5 # BEE5 60E7 # BEE6 70AC # BEE7 5267 # BEE8 6350 # BEE9 9E43 # BEEA 5A1F # BEEB 5026 # BEEC 7737 # BEED 5377 # BEEE 7EE2 # BEEF 6485 # BEF0 652B # BEF1 6289 # BEF2 6398 # BEF3 5014 # BEF4 7235 # BEF5 89C9 # BEF6 51B3 # BEF7 8BC0 # BEF8 7EDD # BEF9 5747 # BEFA 83CC # BEFB 94A7 # BEFC 519B # BEFD 541B # BEFE 5CFB # BFA1 4FCA # BFA2 7AE3 # BFA3 6D5A # BFA4 90E1 # BFA5 9A8F # BFA6 5580 # BFA7 5496 # BFA8 5361 # BFA9 54AF # BFAA 5F00 # BFAB 63E9 # BFAC 6977 # BFAD 51EF # BFAE 6168 # BFAF 520A # BFB0 582A # BFB1 52D8 # BFB2 574E # BFB3 780D # BFB4 770B # BFB5 5EB7 # BFB6 6177 # BFB7 7CE0 # BFB8 625B # BFB9 6297 # BFBA 4EA2 # BFBB 7095 # BFBC 8003 # BFBD 62F7 # BFBE 70E4 # BFBF 9760 # BFC0 5777 # BFC1 82DB # BFC2 67EF # BFC3 68F5 # BFC4 78D5 # BFC5 9897 # BFC6 79D1 # BFC7 58F3 # BFC8 54B3 # BFC9 53EF # BFCA 6E34 # BFCB 514B # BFCC 523B # BFCD 5BA2 # BFCE 8BFE # BFCF 80AF # BFD0 5543 # BFD1 57A6 # BFD2 6073 # BFD3 5751 # BFD4 542D # BFD5 7A7A # BFD6 6050 # BFD7 5B54 # BFD8 63A7 # BFD9 62A0 # BFDA 53E3 # BFDB 6263 # BFDC 5BC7 # BFDD 67AF # BFDE 54ED # BFDF 7A9F # BFE0 82E6 # BFE1 9177 # BFE2 5E93 # BFE3 88E4 # BFE4 5938 # BFE5 57AE # BFE6 630E # BFE7 8DE8 # BFE8 80EF # BFE9 5757 # BFEA 7B77 # BFEB 4FA9 # BFEC 5FEB # BFED 5BBD # BFEE 6B3E # BFEF 5321 # BFF0 7B50 # BFF1 72C2 # BFF2 6846 # BFF3 77FF # BFF4 7736 # BFF5 65F7 # BFF6 51B5 # BFF7 4E8F # BFF8 76D4 # BFF9 5CBF # BFFA 7AA5 # BFFB 8475 # BFFC 594E # BFFD 9B41 # BFFE 5080 # C0A1 9988 # C0A2 6127 # C0A3 6E83 # C0A4 5764 # C0A5 6606 # C0A6 6346 # C0A7 56F0 # C0A8 62EC # C0A9 6269 # C0AA 5ED3 # C0AB 9614 # C0AC 5783 # C0AD 62C9 # C0AE 5587 # C0AF 8721 # C0B0 814A # C0B1 8FA3 # C0B2 5566 # C0B3 83B1 # C0B4 6765 # C0B5 8D56 # C0B6 84DD # C0B7 5A6A # C0B8 680F # C0B9 62E6 # C0BA 7BEE # C0BB 9611 # C0BC 5170 # C0BD 6F9C # C0BE 8C30 # C0BF 63FD # C0C0 89C8 # C0C1 61D2 # C0C2 7F06 # C0C3 70C2 # C0C4 6EE5 # C0C5 7405 # C0C6 6994 # C0C7 72FC # C0C8 5ECA # C0C9 90CE # C0CA 6717 # C0CB 6D6A # C0CC 635E # C0CD 52B3 # C0CE 7262 # C0CF 8001 # C0D0 4F6C # C0D1 59E5 # C0D2 916A # C0D3 70D9 # C0D4 6D9D # C0D5 52D2 # C0D6 4E50 # C0D7 96F7 # C0D8 956D # C0D9 857E # C0DA 78CA # C0DB 7D2F # C0DC 5121 # C0DD 5792 # C0DE 64C2 # C0DF 808B # C0E0 7C7B # C0E1 6CEA # C0E2 68F1 # C0E3 695E # C0E4 51B7 # C0E5 5398 # C0E6 68A8 # C0E7 7281 # C0E8 9ECE # C0E9 7BF1 # C0EA 72F8 # C0EB 79BB # C0EC 6F13 # C0ED 7406 # C0EE 674E # C0EF 91CC # C0F0 9CA4 # C0F1 793C # C0F2 8389 # C0F3 8354 # C0F4 540F # C0F5 6817 # C0F6 4E3D # C0F7 5389 # C0F8 52B1 # C0F9 783E # C0FA 5386 # C0FB 5229 # C0FC 5088 # C0FD 4F8B # C0FE 4FD0 # C1A1 75E2 # C1A2 7ACB # C1A3 7C92 # C1A4 6CA5 # C1A5 96B6 # C1A6 529B # C1A7 7483 # C1A8 54E9 # C1A9 4FE9 # C1AA 8054 # C1AB 83B2 # C1AC 8FDE # C1AD 9570 # C1AE 5EC9 # C1AF 601C # C1B0 6D9F # C1B1 5E18 # C1B2 655B # C1B3 8138 # C1B4 94FE # C1B5 604B # C1B6 70BC # C1B7 7EC3 # C1B8 7CAE # C1B9 51C9 # C1BA 6881 # C1BB 7CB1 # C1BC 826F # C1BD 4E24 # C1BE 8F86 # C1BF 91CF # C1C0 667E # C1C1 4EAE # C1C2 8C05 # C1C3 64A9 # C1C4 804A # C1C5 50DA # C1C6 7597 # C1C7 71CE # C1C8 5BE5 # C1C9 8FBD # C1CA 6F66 # C1CB 4E86 # C1CC 6482 # C1CD 9563 # C1CE 5ED6 # C1CF 6599 # C1D0 5217 # C1D1 88C2 # C1D2 70C8 # C1D3 52A3 # C1D4 730E # C1D5 7433 # C1D6 6797 # C1D7 78F7 # C1D8 9716 # C1D9 4E34 # C1DA 90BB # C1DB 9CDE # C1DC 6DCB # C1DD 51DB # C1DE 8D41 # C1DF 541D # C1E0 62CE # C1E1 73B2 # C1E2 83F1 # C1E3 96F6 # C1E4 9F84 # C1E5 94C3 # C1E6 4F36 # C1E7 7F9A # C1E8 51CC # C1E9 7075 # C1EA 9675 # C1EB 5CAD # C1EC 9886 # C1ED 53E6 # C1EE 4EE4 # C1EF 6E9C # C1F0 7409 # C1F1 69B4 # C1F2 786B # C1F3 998F # C1F4 7559 # C1F5 5218 # C1F6 7624 # C1F7 6D41 # C1F8 67F3 # C1F9 516D # C1FA 9F99 # C1FB 804B # C1FC 5499 # C1FD 7B3C # C1FE 7ABF # C2A1 9686 # C2A2 5784 # C2A3 62E2 # C2A4 9647 # C2A5 697C # C2A6 5A04 # C2A7 6402 # C2A8 7BD3 # C2A9 6F0F # C2AA 964B # C2AB 82A6 # C2AC 5362 # C2AD 9885 # C2AE 5E90 # C2AF 7089 # C2B0 63B3 # C2B1 5364 # C2B2 864F # C2B3 9C81 # C2B4 9E93 # C2B5 788C # C2B6 9732 # C2B7 8DEF # C2B8 8D42 # C2B9 9E7F # C2BA 6F5E # C2BB 7984 # C2BC 5F55 # C2BD 9646 # C2BE 622E # C2BF 9A74 # C2C0 5415 # C2C1 94DD # C2C2 4FA3 # C2C3 65C5 # C2C4 5C65 # C2C5 5C61 # C2C6 7F15 # C2C7 8651 # C2C8 6C2F # C2C9 5F8B # C2CA 7387 # C2CB 6EE4 # C2CC 7EFF # C2CD 5CE6 # C2CE 631B # C2CF 5B6A # C2D0 6EE6 # C2D1 5375 # C2D2 4E71 # C2D3 63A0 # C2D4 7565 # C2D5 62A1 # C2D6 8F6E # C2D7 4F26 # C2D8 4ED1 # C2D9 6CA6 # C2DA 7EB6 # C2DB 8BBA # C2DC 841D # C2DD 87BA # C2DE 7F57 # C2DF 903B # C2E0 9523 # C2E1 7BA9 # C2E2 9AA1 # C2E3 88F8 # C2E4 843D # C2E5 6D1B # C2E6 9A86 # C2E7 7EDC # C2E8 5988 # C2E9 9EBB # C2EA 739B # C2EB 7801 # C2EC 8682 # C2ED 9A6C # C2EE 9A82 # C2EF 561B # C2F0 5417 # C2F1 57CB # C2F2 4E70 # C2F3 9EA6 # C2F4 5356 # C2F5 8FC8 # C2F6 8109 # C2F7 7792 # C2F8 9992 # C2F9 86EE # C2FA 6EE1 # C2FB 8513 # C2FC 66FC # C2FD 6162 # C2FE 6F2B # C3A1 8C29 # C3A2 8292 # C3A3 832B # C3A4 76F2 # C3A5 6C13 # C3A6 5FD9 # C3A7 83BD # C3A8 732B # C3A9 8305 # C3AA 951A # C3AB 6BDB # C3AC 77DB # C3AD 94C6 # C3AE 536F # C3AF 8302 # C3B0 5192 # C3B1 5E3D # C3B2 8C8C # C3B3 8D38 # C3B4 4E48 # C3B5 73AB # C3B6 679A # C3B7 6885 # C3B8 9176 # C3B9 9709 # C3BA 7164 # C3BB 6CA1 # C3BC 7709 # C3BD 5A92 # C3BE 9541 # C3BF 6BCF # C3C0 7F8E # C3C1 6627 # C3C2 5BD0 # C3C3 59B9 # C3C4 5A9A # C3C5 95E8 # C3C6 95F7 # C3C7 4EEC # C3C8 840C # C3C9 8499 # C3CA 6AAC # C3CB 76DF # C3CC 9530 # C3CD 731B # C3CE 68A6 # C3CF 5B5F # C3D0 772F # C3D1 919A # C3D2 9761 # C3D3 7CDC # C3D4 8FF7 # C3D5 8C1C # C3D6 5F25 # C3D7 7C73 # C3D8 79D8 # C3D9 89C5 # C3DA 6CCC # C3DB 871C # C3DC 5BC6 # C3DD 5E42 # C3DE 68C9 # C3DF 7720 # C3E0 7EF5 # C3E1 5195 # C3E2 514D # C3E3 52C9 # C3E4 5A29 # C3E5 7F05 # C3E6 9762 # C3E7 82D7 # C3E8 63CF # C3E9 7784 # C3EA 85D0 # C3EB 79D2 # C3EC 6E3A # C3ED 5E99 # C3EE 5999 # C3EF 8511 # C3F0 706D # C3F1 6C11 # C3F2 62BF # C3F3 76BF # C3F4 654F # C3F5 60AF # C3F6 95FD # C3F7 660E # C3F8 879F # C3F9 9E23 # C3FA 94ED # C3FB 540D # C3FC 547D # C3FD 8C2C # C3FE 6478 # C4A1 6479 # C4A2 8611 # C4A3 6A21 # C4A4 819C # C4A5 78E8 # C4A6 6469 # C4A7 9B54 # C4A8 62B9 # C4A9 672B # C4AA 83AB # C4AB 58A8 # C4AC 9ED8 # C4AD 6CAB # C4AE 6F20 # C4AF 5BDE # C4B0 964C # C4B1 8C0B # C4B2 725F # C4B3 67D0 # C4B4 62C7 # C4B5 7261 # C4B6 4EA9 # C4B7 59C6 # C4B8 6BCD # C4B9 5893 # C4BA 66AE # C4BB 5E55 # C4BC 52DF # C4BD 6155 # C4BE 6728 # C4BF 76EE # C4C0 7766 # C4C1 7267 # C4C2 7A46 # C4C3 62FF # C4C4 54EA # C4C5 5450 # C4C6 94A0 # C4C7 90A3 # C4C8 5A1C # C4C9 7EB3 # C4CA 6C16 # C4CB 4E43 # C4CC 5976 # C4CD 8010 # C4CE 5948 # C4CF 5357 # C4D0 7537 # C4D1 96BE # C4D2 56CA # C4D3 6320 # C4D4 8111 # C4D5 607C # C4D6 95F9 # C4D7 6DD6 # C4D8 5462 # C4D9 9981 # C4DA 5185 # C4DB 5AE9 # C4DC 80FD # C4DD 59AE # C4DE 9713 # C4DF 502A # C4E0 6CE5 # C4E1 5C3C # C4E2 62DF # C4E3 4F60 # C4E4 533F # C4E5 817B # C4E6 9006 # C4E7 6EBA # C4E8 852B # C4E9 62C8 # C4EA 5E74 # C4EB 78BE # C4EC 64B5 # C4ED 637B # C4EE 5FF5 # C4EF 5A18 # C4F0 917F # C4F1 9E1F # C4F2 5C3F # C4F3 634F # C4F4 8042 # C4F5 5B7D # C4F6 556E # C4F7 954A # C4F8 954D # C4F9 6D85 # C4FA 60A8 # C4FB 67E0 # C4FC 72DE # C4FD 51DD # C4FE 5B81 # C5A1 62E7 # C5A2 6CDE # C5A3 725B # C5A4 626D # C5A5 94AE # C5A6 7EBD # C5A7 8113 # C5A8 6D53 # C5A9 519C # C5AA 5F04 # C5AB 5974 # C5AC 52AA # C5AD 6012 # C5AE 5973 # C5AF 6696 # C5B0 8650 # C5B1 759F # C5B2 632A # C5B3 61E6 # C5B4 7CEF # C5B5 8BFA # C5B6 54E6 # C5B7 6B27 # C5B8 9E25 # C5B9 6BB4 # C5BA 85D5 # C5BB 5455 # C5BC 5076 # C5BD 6CA4 # C5BE 556A # C5BF 8DB4 # C5C0 722C # C5C1 5E15 # C5C2 6015 # C5C3 7436 # C5C4 62CD # C5C5 6392 # C5C6 724C # C5C7 5F98 # C5C8 6E43 # C5C9 6D3E # C5CA 6500 # C5CB 6F58 # C5CC 76D8 # C5CD 78D0 # C5CE 76FC # C5CF 7554 # C5D0 5224 # C5D1 53DB # C5D2 4E53 # C5D3 5E9E # C5D4 65C1 # C5D5 802A # C5D6 80D6 # C5D7 629B # C5D8 5486 # C5D9 5228 # C5DA 70AE # C5DB 888D # C5DC 8DD1 # C5DD 6CE1 # C5DE 5478 # C5DF 80DA # C5E0 57F9 # C5E1 88F4 # C5E2 8D54 # C5E3 966A # C5E4 914D # C5E5 4F69 # C5E6 6C9B # C5E7 55B7 # C5E8 76C6 # C5E9 7830 # C5EA 62A8 # C5EB 70F9 # C5EC 6F8E # C5ED 5F6D # C5EE 84EC # C5EF 68DA # C5F0 787C # C5F1 7BF7 # C5F2 81A8 # C5F3 670B # C5F4 9E4F # C5F5 6367 # C5F6 78B0 # C5F7 576F # C5F8 7812 # C5F9 9739 # C5FA 6279 # C5FB 62AB # C5FC 5288 # C5FD 7435 # C5FE 6BD7 # C6A1 5564 # C6A2 813E # C6A3 75B2 # C6A4 76AE # C6A5 5339 # C6A6 75DE # C6A7 50FB # C6A8 5C41 # C6A9 8B6C # C6AA 7BC7 # C6AB 504F # C6AC 7247 # C6AD 9A97 # C6AE 98D8 # C6AF 6F02 # C6B0 74E2 # C6B1 7968 # C6B2 6487 # C6B3 77A5 # C6B4 62FC # C6B5 9891 # C6B6 8D2B # C6B7 54C1 # C6B8 8058 # C6B9 4E52 # C6BA 576A # C6BB 82F9 # C6BC 840D # C6BD 5E73 # C6BE 51ED # C6BF 74F6 # C6C0 8BC4 # C6C1 5C4F # C6C2 5761 # C6C3 6CFC # C6C4 9887 # C6C5 5A46 # C6C6 7834 # C6C7 9B44 # C6C8 8FEB # C6C9 7C95 # C6CA 5256 # C6CB 6251 # C6CC 94FA # C6CD 4EC6 # C6CE 8386 # C6CF 8461 # C6D0 83E9 # C6D1 84B2 # C6D2 57D4 # C6D3 6734 # C6D4 5703 # C6D5 666E # C6D6 6D66 # C6D7 8C31 # C6D8 66DD # C6D9 7011 # C6DA 671F # C6DB 6B3A # C6DC 6816 # C6DD 621A # C6DE 59BB # C6DF 4E03 # C6E0 51C4 # C6E1 6F06 # C6E2 67D2 # C6E3 6C8F # C6E4 5176 # C6E5 68CB # C6E6 5947 # C6E7 6B67 # C6E8 7566 # C6E9 5D0E # C6EA 8110 # C6EB 9F50 # C6EC 65D7 # C6ED 7948 # C6EE 7941 # C6EF 9A91 # C6F0 8D77 # C6F1 5C82 # C6F2 4E5E # C6F3 4F01 # C6F4 542F # C6F5 5951 # C6F6 780C # C6F7 5668 # C6F8 6C14 # C6F9 8FC4 # C6FA 5F03 # C6FB 6C7D # C6FC 6CE3 # C6FD 8BAB # C6FE 6390 # C7A1 6070 # C7A2 6D3D # C7A3 7275 # C7A4 6266 # C7A5 948E # C7A6 94C5 # C7A7 5343 # C7A8 8FC1 # C7A9 7B7E # C7AA 4EDF # C7AB 8C26 # C7AC 4E7E # C7AD 9ED4 # C7AE 94B1 # C7AF 94B3 # C7B0 524D # C7B1 6F5C # C7B2 9063 # C7B3 6D45 # C7B4 8C34 # C7B5 5811 # C7B6 5D4C # C7B7 6B20 # C7B8 6B49 # C7B9 67AA # C7BA 545B # C7BB 8154 # C7BC 7F8C # C7BD 5899 # C7BE 8537 # C7BF 5F3A # C7C0 62A2 # C7C1 6A47 # C7C2 9539 # C7C3 6572 # C7C4 6084 # C7C5 6865 # C7C6 77A7 # C7C7 4E54 # C7C8 4FA8 # C7C9 5DE7 # C7CA 9798 # C7CB 64AC # C7CC 7FD8 # C7CD 5CED # C7CE 4FCF # C7CF 7A8D # C7D0 5207 # C7D1 8304 # C7D2 4E14 # C7D3 602F # C7D4 7A83 # C7D5 94A6 # C7D6 4FB5 # C7D7 4EB2 # C7D8 79E6 # C7D9 7434 # C7DA 52E4 # C7DB 82B9 # C7DC 64D2 # C7DD 79BD # C7DE 5BDD # C7DF 6C81 # C7E0 9752 # C7E1 8F7B # C7E2 6C22 # C7E3 503E # C7E4 537F # C7E5 6E05 # C7E6 64CE # C7E7 6674 # C7E8 6C30 # C7E9 60C5 # C7EA 9877 # C7EB 8BF7 # C7EC 5E86 # C7ED 743C # C7EE 7A77 # C7EF 79CB # C7F0 4E18 # C7F1 90B1 # C7F2 7403 # C7F3 6C42 # C7F4 56DA # C7F5 914B # C7F6 6CC5 # C7F7 8D8B # C7F8 533A # C7F9 86C6 # C7FA 66F2 # C7FB 8EAF # C7FC 5C48 # C7FD 9A71 # C7FE 6E20 # C8A1 53D6 # C8A2 5A36 # C8A3 9F8B # C8A4 8DA3 # C8A5 53BB # C8A6 5708 # C8A7 98A7 # C8A8 6743 # C8A9 919B # C8AA 6CC9 # C8AB 5168 # C8AC 75CA # C8AD 62F3 # C8AE 72AC # C8AF 5238 # C8B0 529D # C8B1 7F3A # C8B2 7094 # C8B3 7638 # C8B4 5374 # C8B5 9E4A # C8B6 69B7 # C8B7 786E # C8B8 96C0 # C8B9 88D9 # C8BA 7FA4 # C8BB 7136 # C8BC 71C3 # C8BD 5189 # C8BE 67D3 # C8BF 74E4 # C8C0 58E4 # C8C1 6518 # C8C2 56B7 # C8C3 8BA9 # C8C4 9976 # C8C5 6270 # C8C6 7ED5 # C8C7 60F9 # C8C8 70ED # C8C9 58EC # C8CA 4EC1 # C8CB 4EBA # C8CC 5FCD # C8CD 97E7 # C8CE 4EFB # C8CF 8BA4 # C8D0 5203 # C8D1 598A # C8D2 7EAB # C8D3 6254 # C8D4 4ECD # C8D5 65E5 # C8D6 620E # C8D7 8338 # C8D8 84C9 # C8D9 8363 # C8DA 878D # C8DB 7194 # C8DC 6EB6 # C8DD 5BB9 # C8DE 7ED2 # C8DF 5197 # C8E0 63C9 # C8E1 67D4 # C8E2 8089 # C8E3 8339 # C8E4 8815 # C8E5 5112 # C8E6 5B7A # C8E7 5982 # C8E8 8FB1 # C8E9 4E73 # C8EA 6C5D # C8EB 5165 # C8EC 8925 # C8ED 8F6F # C8EE 962E # C8EF 854A # C8F0 745E # C8F1 9510 # C8F2 95F0 # C8F3 6DA6 # C8F4 82E5 # C8F5 5F31 # C8F6 6492 # C8F7 6D12 # C8F8 8428 # C8F9 816E # C8FA 9CC3 # C8FB 585E # C8FC 8D5B # C8FD 4E09 # C8FE 53C1 # C9A1 4F1E # C9A2 6563 # C9A3 6851 # C9A4 55D3 # C9A5 4E27 # C9A6 6414 # C9A7 9A9A # C9A8 626B # C9A9 5AC2 # C9AA 745F # C9AB 8272 # C9AC 6DA9 # C9AD 68EE # C9AE 50E7 # C9AF 838E # C9B0 7802 # C9B1 6740 # C9B2 5239 # C9B3 6C99 # C9B4 7EB1 # C9B5 50BB # C9B6 5565 # C9B7 715E # C9B8 7B5B # C9B9 6652 # C9BA 73CA # C9BB 82EB # C9BC 6749 # C9BD 5C71 # C9BE 5220 # C9BF 717D # C9C0 886B # C9C1 95EA # C9C2 9655 # C9C3 64C5 # C9C4 8D61 # C9C5 81B3 # C9C6 5584 # C9C7 6C55 # C9C8 6247 # C9C9 7F2E # C9CA 5892 # C9CB 4F24 # C9CC 5546 # C9CD 8D4F # C9CE 664C # C9CF 4E0A # C9D0 5C1A # C9D1 88F3 # C9D2 68A2 # C9D3 634E # C9D4 7A0D # C9D5 70E7 # C9D6 828D # C9D7 52FA # C9D8 97F6 # C9D9 5C11 # C9DA 54E8 # C9DB 90B5 # C9DC 7ECD # C9DD 5962 # C9DE 8D4A # C9DF 86C7 # C9E0 820C # C9E1 820D # C9E2 8D66 # C9E3 6444 # C9E4 5C04 # C9E5 6151 # C9E6 6D89 # C9E7 793E # C9E8 8BBE # C9E9 7837 # C9EA 7533 # C9EB 547B # C9EC 4F38 # C9ED 8EAB # C9EE 6DF1 # C9EF 5A20 # C9F0 7EC5 # C9F1 795E # C9F2 6C88 # C9F3 5BA1 # C9F4 5A76 # C9F5 751A # C9F6 80BE # C9F7 614E # C9F8 6E17 # C9F9 58F0 # C9FA 751F # C9FB 7525 # C9FC 7272 # C9FD 5347 # C9FE 7EF3 # CAA1 7701 # CAA2 76DB # CAA3 5269 # CAA4 80DC # CAA5 5723 # CAA6 5E08 # CAA7 5931 # CAA8 72EE # CAA9 65BD # CAAA 6E7F # CAAB 8BD7 # CAAC 5C38 # CAAD 8671 # CAAE 5341 # CAAF 77F3 # CAB0 62FE # CAB1 65F6 # CAB2 4EC0 # CAB3 98DF # CAB4 8680 # CAB5 5B9E # CAB6 8BC6 # CAB7 53F2 # CAB8 77E2 # CAB9 4F7F # CABA 5C4E # CABB 9A76 # CABC 59CB # CABD 5F0F # CABE 793A # CABF 58EB # CAC0 4E16 # CAC1 67FF # CAC2 4E8B # CAC3 62ED # CAC4 8A93 # CAC5 901D # CAC6 52BF # CAC7 662F # CAC8 55DC # CAC9 566C # CACA 9002 # CACB 4ED5 # CACC 4F8D # CACD 91CA # CACE 9970 # CACF 6C0F # CAD0 5E02 # CAD1 6043 # CAD2 5BA4 # CAD3 89C6 # CAD4 8BD5 # CAD5 6536 # CAD6 624B # CAD7 9996 # CAD8 5B88 # CAD9 5BFF # CADA 6388 # CADB 552E # CADC 53D7 # CADD 7626 # CADE 517D # CADF 852C # CAE0 67A2 # CAE1 68B3 # CAE2 6B8A # CAE3 6292 # CAE4 8F93 # CAE5 53D4 # CAE6 8212 # CAE7 6DD1 # CAE8 758F # CAE9 4E66 # CAEA 8D4E # CAEB 5B70 # CAEC 719F # CAED 85AF # CAEE 6691 # CAEF 66D9 # CAF0 7F72 # CAF1 8700 # CAF2 9ECD # CAF3 9F20 # CAF4 5C5E # CAF5 672F # CAF6 8FF0 # CAF7 6811 # CAF8 675F # CAF9 620D # CAFA 7AD6 # CAFB 5885 # CAFC 5EB6 # CAFD 6570 # CAFE 6F31 # CBA1 6055 # CBA2 5237 # CBA3 800D # CBA4 6454 # CBA5 8870 # CBA6 7529 # CBA7 5E05 # CBA8 6813 # CBA9 62F4 # CBAA 971C # CBAB 53CC # CBAC 723D # CBAD 8C01 # CBAE 6C34 # CBAF 7761 # CBB0 7A0E # CBB1 542E # CBB2 77AC # CBB3 987A # CBB4 821C # CBB5 8BF4 # CBB6 7855 # CBB7 6714 # CBB8 70C1 # CBB9 65AF # CBBA 6495 # CBBB 5636 # CBBC 601D # CBBD 79C1 # CBBE 53F8 # CBBF 4E1D # CBC0 6B7B # CBC1 8086 # CBC2 5BFA # CBC3 55E3 # CBC4 56DB # CBC5 4F3A # CBC6 4F3C # CBC7 9972 # CBC8 5DF3 # CBC9 677E # CBCA 8038 # CBCB 6002 # CBCC 9882 # CBCD 9001 # CBCE 5B8B # CBCF 8BBC # CBD0 8BF5 # CBD1 641C # CBD2 8258 # CBD3 64DE # CBD4 55FD # CBD5 82CF # CBD6 9165 # CBD7 4FD7 # CBD8 7D20 # CBD9 901F # CBDA 7C9F # CBDB 50F3 # CBDC 5851 # CBDD 6EAF # CBDE 5BBF # CBDF 8BC9 # CBE0 8083 # CBE1 9178 # CBE2 849C # CBE3 7B97 # CBE4 867D # CBE5 968B # CBE6 968F # CBE7 7EE5 # CBE8 9AD3 # CBE9 788E # CBEA 5C81 # CBEB 7A57 # CBEC 9042 # CBED 96A7 # CBEE 795F # CBEF 5B59 # CBF0 635F # CBF1 7B0B # CBF2 84D1 # CBF3 68AD # CBF4 5506 # CBF5 7F29 # CBF6 7410 # CBF7 7D22 # CBF8 9501 # CBF9 6240 # CBFA 584C # CBFB 4ED6 # CBFC 5B83 # CBFD 5979 # CBFE 5854 # CCA1 736D # CCA2 631E # CCA3 8E4B # CCA4 8E0F # CCA5 80CE # CCA6 82D4 # CCA7 62AC # CCA8 53F0 # CCA9 6CF0 # CCAA 915E # CCAB 592A # CCAC 6001 # CCAD 6C70 # CCAE 574D # CCAF 644A # CCB0 8D2A # CCB1 762B # CCB2 6EE9 # CCB3 575B # CCB4 6A80 # CCB5 75F0 # CCB6 6F6D # CCB7 8C2D # CCB8 8C08 # CCB9 5766 # CCBA 6BEF # CCBB 8892 # CCBC 78B3 # CCBD 63A2 # CCBE 53F9 # CCBF 70AD # CCC0 6C64 # CCC1 5858 # CCC2 642A # CCC3 5802 # CCC4 68E0 # CCC5 819B # CCC6 5510 # CCC7 7CD6 # CCC8 5018 # CCC9 8EBA # CCCA 6DCC # CCCB 8D9F # CCCC 70EB # CCCD 638F # CCCE 6D9B # CCCF 6ED4 # CCD0 7EE6 # CCD1 8404 # CCD2 6843 # CCD3 9003 # CCD4 6DD8 # CCD5 9676 # CCD6 8BA8 # CCD7 5957 # CCD8 7279 # CCD9 85E4 # CCDA 817E # CCDB 75BC # CCDC 8A8A # CCDD 68AF # CCDE 5254 # CCDF 8E22 # CCE0 9511 # CCE1 63D0 # CCE2 9898 # CCE3 8E44 # CCE4 557C # CCE5 4F53 # CCE6 66FF # CCE7 568F # CCE8 60D5 # CCE9 6D95 # CCEA 5243 # CCEB 5C49 # CCEC 5929 # CCED 6DFB # CCEE 586B # CCEF 7530 # CCF0 751C # CCF1 606C # CCF2 8214 # CCF3 8146 # CCF4 6311 # CCF5 6761 # CCF6 8FE2 # CCF7 773A # CCF8 8DF3 # CCF9 8D34 # CCFA 94C1 # CCFB 5E16 # CCFC 5385 # CCFD 542C # CCFE 70C3 # CDA1 6C40 # CDA2 5EF7 # CDA3 505C # CDA4 4EAD # CDA5 5EAD # CDA6 633A # CDA7 8247 # CDA8 901A # CDA9 6850 # CDAA 916E # CDAB 77B3 # CDAC 540C # CDAD 94DC # CDAE 5F64 # CDAF 7AE5 # CDB0 6876 # CDB1 6345 # CDB2 7B52 # CDB3 7EDF # CDB4 75DB # CDB5 5077 # CDB6 6295 # CDB7 5934 # CDB8 900F # CDB9 51F8 # CDBA 79C3 # CDBB 7A81 # CDBC 56FE # CDBD 5F92 # CDBE 9014 # CDBF 6D82 # CDC0 5C60 # CDC1 571F # CDC2 5410 # CDC3 5154 # CDC4 6E4D # CDC5 56E2 # CDC6 63A8 # CDC7 9893 # CDC8 817F # CDC9 8715 # CDCA 892A # CDCB 9000 # CDCC 541E # CDCD 5C6F # CDCE 81C0 # CDCF 62D6 # CDD0 6258 # CDD1 8131 # CDD2 9E35 # CDD3 9640 # CDD4 9A6E # CDD5 9A7C # CDD6 692D # CDD7 59A5 # CDD8 62D3 # CDD9 553E # CDDA 6316 # CDDB 54C7 # CDDC 86D9 # CDDD 6D3C # CDDE 5A03 # CDDF 74E6 # CDE0 889C # CDE1 6B6A # CDE2 5916 # CDE3 8C4C # CDE4 5F2F # CDE5 6E7E # CDE6 73A9 # CDE7 987D # CDE8 4E38 # CDE9 70F7 # CDEA 5B8C # CDEB 7897 # CDEC 633D # CDED 665A # CDEE 7696 # CDEF 60CB # CDF0 5B9B # CDF1 5A49 # CDF2 4E07 # CDF3 8155 # CDF4 6C6A # CDF5 738B # CDF6 4EA1 # CDF7 6789 # CDF8 7F51 # CDF9 5F80 # CDFA 65FA # CDFB 671B # CDFC 5FD8 # CDFD 5984 # CDFE 5A01 # CEA1 5DCD # CEA2 5FAE # CEA3 5371 # CEA4 97E6 # CEA5 8FDD # CEA6 6845 # CEA7 56F4 # CEA8 552F # CEA9 60DF # CEAA 4E3A # CEAB 6F4D # CEAC 7EF4 # CEAD 82C7 # CEAE 840E # CEAF 59D4 # CEB0 4F1F # CEB1 4F2A # CEB2 5C3E # CEB3 7EAC # CEB4 672A # CEB5 851A # CEB6 5473 # CEB7 754F # CEB8 80C3 # CEB9 5582 # CEBA 9B4F # CEBB 4F4D # CEBC 6E2D # CEBD 8C13 # CEBE 5C09 # CEBF 6170 # CEC0 536B # CEC1 761F # CEC2 6E29 # CEC3 868A # CEC4 6587 # CEC5 95FB # CEC6 7EB9 # CEC7 543B # CEC8 7A33 # CEC9 7D0A # CECA 95EE # CECB 55E1 # CECC 7FC1 # CECD 74EE # CECE 631D # CECF 8717 # CED0 6DA1 # CED1 7A9D # CED2 6211 # CED3 65A1 # CED4 5367 # CED5 63E1 # CED6 6C83 # CED7 5DEB # CED8 545C # CED9 94A8 # CEDA 4E4C # CEDB 6C61 # CEDC 8BEC # CEDD 5C4B # CEDE 65E0 # CEDF 829C # CEE0 68A7 # CEE1 543E # CEE2 5434 # CEE3 6BCB # CEE4 6B66 # CEE5 4E94 # CEE6 6342 # CEE7 5348 # CEE8 821E # CEE9 4F0D # CEEA 4FAE # CEEB 575E # CEEC 620A # CEED 96FE # CEEE 6664 # CEEF 7269 # CEF0 52FF # CEF1 52A1 # CEF2 609F # CEF3 8BEF # CEF4 6614 # CEF5 7199 # CEF6 6790 # CEF7 897F # CEF8 7852 # CEF9 77FD # CEFA 6670 # CEFB 563B # CEFC 5438 # CEFD 9521 # CEFE 727A # CFA1 7A00 # CFA2 606F # CFA3 5E0C # CFA4 6089 # CFA5 819D # CFA6 5915 # CFA7 60DC # CFA8 7184 # CFA9 70EF # CFAA 6EAA # CFAB 6C50 # CFAC 7280 # CFAD 6A84 # CFAE 88AD # CFAF 5E2D # CFB0 4E60 # CFB1 5AB3 # CFB2 559C # CFB3 94E3 # CFB4 6D17 # CFB5 7CFB # CFB6 9699 # CFB7 620F # CFB8 7EC6 # CFB9 778E # CFBA 867E # CFBB 5323 # CFBC 971E # CFBD 8F96 # CFBE 6687 # CFBF 5CE1 # CFC0 4FA0 # CFC1 72ED # CFC2 4E0B # CFC3 53A6 # CFC4 590F # CFC5 5413 # CFC6 6380 # CFC7 9528 # CFC8 5148 # CFC9 4ED9 # CFCA 9C9C # CFCB 7EA4 # CFCC 54B8 # CFCD 8D24 # CFCE 8854 # CFCF 8237 # CFD0 95F2 # CFD1 6D8E # CFD2 5F26 # CFD3 5ACC # CFD4 663E # CFD5 9669 # CFD6 73B0 # CFD7 732E # CFD8 53BF # CFD9 817A # CFDA 9985 # CFDB 7FA1 # CFDC 5BAA # CFDD 9677 # CFDE 9650 # CFDF 7EBF # CFE0 76F8 # CFE1 53A2 # CFE2 9576 # CFE3 9999 # CFE4 7BB1 # CFE5 8944 # CFE6 6E58 # CFE7 4E61 # CFE8 7FD4 # CFE9 7965 # CFEA 8BE6 # CFEB 60F3 # CFEC 54CD # CFED 4EAB # CFEE 9879 # CFEF 5DF7 # CFF0 6A61 # CFF1 50CF # CFF2 5411 # CFF3 8C61 # CFF4 8427 # CFF5 785D # CFF6 9704 # CFF7 524A # CFF8 54EE # CFF9 56A3 # CFFA 9500 # CFFB 6D88 # CFFC 5BB5 # CFFD 6DC6 # CFFE 6653 # D0A1 5C0F # D0A2 5B5D # D0A3 6821 # D0A4 8096 # D0A5 5578 # D0A6 7B11 # D0A7 6548 # D0A8 6954 # D0A9 4E9B # D0AA 6B47 # D0AB 874E # D0AC 978B # D0AD 534F # D0AE 631F # D0AF 643A # D0B0 90AA # D0B1 659C # D0B2 80C1 # D0B3 8C10 # D0B4 5199 # D0B5 68B0 # D0B6 5378 # D0B7 87F9 # D0B8 61C8 # D0B9 6CC4 # D0BA 6CFB # D0BB 8C22 # D0BC 5C51 # D0BD 85AA # D0BE 82AF # D0BF 950C # D0C0 6B23 # D0C1 8F9B # D0C2 65B0 # D0C3 5FFB # D0C4 5FC3 # D0C5 4FE1 # D0C6 8845 # D0C7 661F # D0C8 8165 # D0C9 7329 # D0CA 60FA # D0CB 5174 # D0CC 5211 # D0CD 578B # D0CE 5F62 # D0CF 90A2 # D0D0 884C # D0D1 9192 # D0D2 5E78 # D0D3 674F # D0D4 6027 # D0D5 59D3 # D0D6 5144 # D0D7 51F6 # D0D8 80F8 # D0D9 5308 # D0DA 6C79 # D0DB 96C4 # D0DC 718A # D0DD 4F11 # D0DE 4FEE # D0DF 7F9E # D0E0 673D # D0E1 55C5 # D0E2 9508 # D0E3 79C0 # D0E4 8896 # D0E5 7EE3 # D0E6 589F # D0E7 620C # D0E8 9700 # D0E9 865A # D0EA 5618 # D0EB 987B # D0EC 5F90 # D0ED 8BB8 # D0EE 84C4 # D0EF 9157 # D0F0 53D9 # D0F1 65ED # D0F2 5E8F # D0F3 755C # D0F4 6064 # D0F5 7D6E # D0F6 5A7F # D0F7 7EEA # D0F8 7EED # D0F9 8F69 # D0FA 55A7 # D0FB 5BA3 # D0FC 60AC # D0FD 65CB # D0FE 7384 # D1A1 9009 # D1A2 7663 # D1A3 7729 # D1A4 7EDA # D1A5 9774 # D1A6 859B # D1A7 5B66 # D1A8 7A74 # D1A9 96EA # D1AA 8840 # D1AB 52CB # D1AC 718F # D1AD 5FAA # D1AE 65EC # D1AF 8BE2 # D1B0 5BFB # D1B1 9A6F # D1B2 5DE1 # D1B3 6B89 # D1B4 6C5B # D1B5 8BAD # D1B6 8BAF # D1B7 900A # D1B8 8FC5 # D1B9 538B # D1BA 62BC # D1BB 9E26 # D1BC 9E2D # D1BD 5440 # D1BE 4E2B # D1BF 82BD # D1C0 7259 # D1C1 869C # D1C2 5D16 # D1C3 8859 # D1C4 6DAF # D1C5 96C5 # D1C6 54D1 # D1C7 4E9A # D1C8 8BB6 # D1C9 7109 # D1CA 54BD # D1CB 9609 # D1CC 70DF # D1CD 6DF9 # D1CE 76D0 # D1CF 4E25 # D1D0 7814 # D1D1 8712 # D1D2 5CA9 # D1D3 5EF6 # D1D4 8A00 # D1D5 989C # D1D6 960E # D1D7 708E # D1D8 6CBF # D1D9 5944 # D1DA 63A9 # D1DB 773C # D1DC 884D # D1DD 6F14 # D1DE 8273 # D1DF 5830 # D1E0 71D5 # D1E1 538C # D1E2 781A # D1E3 96C1 # D1E4 5501 # D1E5 5F66 # D1E6 7130 # D1E7 5BB4 # D1E8 8C1A # D1E9 9A8C # D1EA 6B83 # D1EB 592E # D1EC 9E2F # D1ED 79E7 # D1EE 6768 # D1EF 626C # D1F0 4F6F # D1F1 75A1 # D1F2 7F8A # D1F3 6D0B # D1F4 9633 # D1F5 6C27 # D1F6 4EF0 # D1F7 75D2 # D1F8 517B # D1F9 6837 # D1FA 6F3E # D1FB 9080 # D1FC 8170 # D1FD 5996 # D1FE 7476 # D2A1 6447 # D2A2 5C27 # D2A3 9065 # D2A4 7A91 # D2A5 8C23 # D2A6 59DA # D2A7 54AC # D2A8 8200 # D2A9 836F # D2AA 8981 # D2AB 8000 # D2AC 6930 # D2AD 564E # D2AE 8036 # D2AF 7237 # D2B0 91CE # D2B1 51B6 # D2B2 4E5F # D2B3 9875 # D2B4 6396 # D2B5 4E1A # D2B6 53F6 # D2B7 66F3 # D2B8 814B # D2B9 591C # D2BA 6DB2 # D2BB 4E00 # D2BC 58F9 # D2BD 533B # D2BE 63D6 # D2BF 94F1 # D2C0 4F9D # D2C1 4F0A # D2C2 8863 # D2C3 9890 # D2C4 5937 # D2C5 9057 # D2C6 79FB # D2C7 4EEA # D2C8 80F0 # D2C9 7591 # D2CA 6C82 # D2CB 5B9C # D2CC 59E8 # D2CD 5F5D # D2CE 6905 # D2CF 8681 # D2D0 501A # D2D1 5DF2 # D2D2 4E59 # D2D3 77E3 # D2D4 4EE5 # D2D5 827A # D2D6 6291 # D2D7 6613 # D2D8 9091 # D2D9 5C79 # D2DA 4EBF # D2DB 5F79 # D2DC 81C6 # D2DD 9038 # D2DE 8084 # D2DF 75AB # D2E0 4EA6 # D2E1 88D4 # D2E2 610F # D2E3 6BC5 # D2E4 5FC6 # D2E5 4E49 # D2E6 76CA # D2E7 6EA2 # D2E8 8BE3 # D2E9 8BAE # D2EA 8C0A # D2EB 8BD1 # D2EC 5F02 # D2ED 7FFC # D2EE 7FCC # D2EF 7ECE # D2F0 8335 # D2F1 836B # D2F2 56E0 # D2F3 6BB7 # D2F4 97F3 # D2F5 9634 # D2F6 59FB # D2F7 541F # D2F8 94F6 # D2F9 6DEB # D2FA 5BC5 # D2FB 996E # D2FC 5C39 # D2FD 5F15 # D2FE 9690 # D3A1 5370 # D3A2 82F1 # D3A3 6A31 # D3A4 5A74 # D3A5 9E70 # D3A6 5E94 # D3A7 7F28 # D3A8 83B9 # D3A9 8424 # D3AA 8425 # D3AB 8367 # D3AC 8747 # D3AD 8FCE # D3AE 8D62 # D3AF 76C8 # D3B0 5F71 # D3B1 9896 # D3B2 786C # D3B3 6620 # D3B4 54DF # D3B5 62E5 # D3B6 4F63 # D3B7 81C3 # D3B8 75C8 # D3B9 5EB8 # D3BA 96CD # D3BB 8E0A # D3BC 86F9 # D3BD 548F # D3BE 6CF3 # D3BF 6D8C # D3C0 6C38 # D3C1 607F # D3C2 52C7 # D3C3 7528 # D3C4 5E7D # D3C5 4F18 # D3C6 60A0 # D3C7 5FE7 # D3C8 5C24 # D3C9 7531 # D3CA 90AE # D3CB 94C0 # D3CC 72B9 # D3CD 6CB9 # D3CE 6E38 # D3CF 9149 # D3D0 6709 # D3D1 53CB # D3D2 53F3 # D3D3 4F51 # D3D4 91C9 # D3D5 8BF1 # D3D6 53C8 # D3D7 5E7C # D3D8 8FC2 # D3D9 6DE4 # D3DA 4E8E # D3DB 76C2 # D3DC 6986 # D3DD 865E # D3DE 611A # D3DF 8206 # D3E0 4F59 # D3E1 4FDE # D3E2 903E # D3E3 9C7C # D3E4 6109 # D3E5 6E1D # D3E6 6E14 # D3E7 9685 # D3E8 4E88 # D3E9 5A31 # D3EA 96E8 # D3EB 4E0E # D3EC 5C7F # D3ED 79B9 # D3EE 5B87 # D3EF 8BED # D3F0 7FBD # D3F1 7389 # D3F2 57DF # D3F3 828B # D3F4 90C1 # D3F5 5401 # D3F6 9047 # D3F7 55BB # D3F8 5CEA # D3F9 5FA1 # D3FA 6108 # D3FB 6B32 # D3FC 72F1 # D3FD 80B2 # D3FE 8A89 # D4A1 6D74 # D4A2 5BD3 # D4A3 88D5 # D4A4 9884 # D4A5 8C6B # D4A6 9A6D # D4A7 9E33 # D4A8 6E0A # D4A9 51A4 # D4AA 5143 # D4AB 57A3 # D4AC 8881 # D4AD 539F # D4AE 63F4 # D4AF 8F95 # D4B0 56ED # D4B1 5458 # D4B2 5706 # D4B3 733F # D4B4 6E90 # D4B5 7F18 # D4B6 8FDC # D4B7 82D1 # D4B8 613F # D4B9 6028 # D4BA 9662 # D4BB 66F0 # D4BC 7EA6 # D4BD 8D8A # D4BE 8DC3 # D4BF 94A5 # D4C0 5CB3 # D4C1 7CA4 # D4C2 6708 # D4C3 60A6 # D4C4 9605 # D4C5 8018 # D4C6 4E91 # D4C7 90E7 # D4C8 5300 # D4C9 9668 # D4CA 5141 # D4CB 8FD0 # D4CC 8574 # D4CD 915D # D4CE 6655 # D4CF 97F5 # D4D0 5B55 # D4D1 531D # D4D2 7838 # D4D3 6742 # D4D4 683D # D4D5 54C9 # D4D6 707E # D4D7 5BB0 # D4D8 8F7D # D4D9 518D # D4DA 5728 # D4DB 54B1 # D4DC 6512 # D4DD 6682 # D4DE 8D5E # D4DF 8D43 # D4E0 810F # D4E1 846C # D4E2 906D # D4E3 7CDF # D4E4 51FF # D4E5 85FB # D4E6 67A3 # D4E7 65E9 # D4E8 6FA1 # D4E9 86A4 # D4EA 8E81 # D4EB 566A # D4EC 9020 # D4ED 7682 # D4EE 7076 # D4EF 71E5 # D4F0 8D23 # D4F1 62E9 # D4F2 5219 # D4F3 6CFD # D4F4 8D3C # D4F5 600E # D4F6 589E # D4F7 618E # D4F8 66FE # D4F9 8D60 # D4FA 624E # D4FB 55B3 # D4FC 6E23 # D4FD 672D # D4FE 8F67 # D5A1 94E1 # D5A2 95F8 # D5A3 7728 # D5A4 6805 # D5A5 69A8 # D5A6 548B # D5A7 4E4D # D5A8 70B8 # D5A9 8BC8 # D5AA 6458 # D5AB 658B # D5AC 5B85 # D5AD 7A84 # D5AE 503A # D5AF 5BE8 # D5B0 77BB # D5B1 6BE1 # D5B2 8A79 # D5B3 7C98 # D5B4 6CBE # D5B5 76CF # D5B6 65A9 # D5B7 8F97 # D5B8 5D2D # D5B9 5C55 # D5BA 8638 # D5BB 6808 # D5BC 5360 # D5BD 6218 # D5BE 7AD9 # D5BF 6E5B # D5C0 7EFD # D5C1 6A1F # D5C2 7AE0 # D5C3 5F70 # D5C4 6F33 # D5C5 5F20 # D5C6 638C # D5C7 6DA8 # D5C8 6756 # D5C9 4E08 # D5CA 5E10 # D5CB 8D26 # D5CC 4ED7 # D5CD 80C0 # D5CE 7634 # D5CF 969C # D5D0 62DB # D5D1 662D # D5D2 627E # D5D3 6CBC # D5D4 8D75 # D5D5 7167 # D5D6 7F69 # D5D7 5146 # D5D8 8087 # D5D9 53EC # D5DA 906E # D5DB 6298 # D5DC 54F2 # D5DD 86F0 # D5DE 8F99 # D5DF 8005 # D5E0 9517 # D5E1 8517 # D5E2 8FD9 # D5E3 6D59 # D5E4 73CD # D5E5 659F # D5E6 771F # D5E7 7504 # D5E8 7827 # D5E9 81FB # D5EA 8D1E # D5EB 9488 # D5EC 4FA6 # D5ED 6795 # D5EE 75B9 # D5EF 8BCA # D5F0 9707 # D5F1 632F # D5F2 9547 # D5F3 9635 # D5F4 84B8 # D5F5 6323 # D5F6 7741 # D5F7 5F81 # D5F8 72F0 # D5F9 4E89 # D5FA 6014 # D5FB 6574 # D5FC 62EF # D5FD 6B63 # D5FE 653F # D6A1 5E27 # D6A2 75C7 # D6A3 90D1 # D6A4 8BC1 # D6A5 829D # D6A6 679D # D6A7 652F # D6A8 5431 # D6A9 8718 # D6AA 77E5 # D6AB 80A2 # D6AC 8102 # D6AD 6C41 # D6AE 4E4B # D6AF 7EC7 # D6B0 804C # D6B1 76F4 # D6B2 690D # D6B3 6B96 # D6B4 6267 # D6B5 503C # D6B6 4F84 # D6B7 5740 # D6B8 6307 # D6B9 6B62 # D6BA 8DBE # D6BB 53EA # D6BC 65E8 # D6BD 7EB8 # D6BE 5FD7 # D6BF 631A # D6C0 63B7 # D6C1 81F3 # D6C2 81F4 # D6C3 7F6E # D6C4 5E1C # D6C5 5CD9 # D6C6 5236 # D6C7 667A # D6C8 79E9 # D6C9 7A1A # D6CA 8D28 # D6CB 7099 # D6CC 75D4 # D6CD 6EDE # D6CE 6CBB # D6CF 7A92 # D6D0 4E2D # D6D1 76C5 # D6D2 5FE0 # D6D3 949F # D6D4 8877 # D6D5 7EC8 # D6D6 79CD # D6D7 80BF # D6D8 91CD # D6D9 4EF2 # D6DA 4F17 # D6DB 821F # D6DC 5468 # D6DD 5DDE # D6DE 6D32 # D6DF 8BCC # D6E0 7CA5 # D6E1 8F74 # D6E2 8098 # D6E3 5E1A # D6E4 5492 # D6E5 76B1 # D6E6 5B99 # D6E7 663C # D6E8 9AA4 # D6E9 73E0 # D6EA 682A # D6EB 86DB # D6EC 6731 # D6ED 732A # D6EE 8BF8 # D6EF 8BDB # D6F0 9010 # D6F1 7AF9 # D6F2 70DB # D6F3 716E # D6F4 62C4 # D6F5 77A9 # D6F6 5631 # D6F7 4E3B # D6F8 8457 # D6F9 67F1 # D6FA 52A9 # D6FB 86C0 # D6FC 8D2E # D6FD 94F8 # D6FE 7B51 # D7A1 4F4F # D7A2 6CE8 # D7A3 795D # D7A4 9A7B # D7A5 6293 # D7A6 722A # D7A7 62FD # D7A8 4E13 # D7A9 7816 # D7AA 8F6C # D7AB 64B0 # D7AC 8D5A # D7AD 7BC6 # D7AE 6869 # D7AF 5E84 # D7B0 88C5 # D7B1 5986 # D7B2 649E # D7B3 58EE # D7B4 72B6 # D7B5 690E # D7B6 9525 # D7B7 8FFD # D7B8 8D58 # D7B9 5760 # D7BA 7F00 # D7BB 8C06 # D7BC 51C6 # D7BD 6349 # D7BE 62D9 # D7BF 5353 # D7C0 684C # D7C1 7422 # D7C2 8301 # D7C3 914C # D7C4 5544 # D7C5 7740 # D7C6 707C # D7C7 6D4A # D7C8 5179 # D7C9 54A8 # D7CA 8D44 # D7CB 59FF # D7CC 6ECB # D7CD 6DC4 # D7CE 5B5C # D7CF 7D2B # D7D0 4ED4 # D7D1 7C7D # D7D2 6ED3 # D7D3 5B50 # D7D4 81EA # D7D5 6E0D # D7D6 5B57 # D7D7 9B03 # D7D8 68D5 # D7D9 8E2A # D7DA 5B97 # D7DB 7EFC # D7DC 603B # D7DD 7EB5 # D7DE 90B9 # D7DF 8D70 # D7E0 594F # D7E1 63CD # D7E2 79DF # D7E3 8DB3 # D7E4 5352 # D7E5 65CF # D7E6 7956 # D7E7 8BC5 # D7E8 963B # D7E9 7EC4 # D7EA 94BB # D7EB 7E82 # D7EC 5634 # D7ED 9189 # D7EE 6700 # D7EF 7F6A # D7F0 5C0A # D7F1 9075 # D7F2 6628 # D7F3 5DE6 # D7F4 4F50 # D7F5 67DE # D7F6 505A # D7F7 4F5C # D7F8 5750 # D7F9 5EA7 # D8A1 4E8D # D8A2 4E0C # D8A3 5140 # D8A4 4E10 # D8A5 5EFF # D8A6 5345 # D8A7 4E15 # D8A8 4E98 # D8A9 4E1E # D8AA 9B32 # D8AB 5B6C # D8AC 5669 # D8AD 4E28 # D8AE 79BA # D8AF 4E3F # D8B0 5315 # D8B1 4E47 # D8B2 592D # D8B3 723B # D8B4 536E # D8B5 6C10 # D8B6 56DF # D8B7 80E4 # D8B8 9997 # D8B9 6BD3 # D8BA 777E # D8BB 9F17 # D8BC 4E36 # D8BD 4E9F # D8BE 9F10 # D8BF 4E5C # D8C0 4E69 # D8C1 4E93 # D8C2 8288 # D8C3 5B5B # D8C4 556C # D8C5 560F # D8C6 4EC4 # D8C7 538D # D8C8 539D # D8C9 53A3 # D8CA 53A5 # D8CB 53AE # D8CC 9765 # D8CD 8D5D # D8CE 531A # D8CF 53F5 # D8D0 5326 # D8D1 532E # D8D2 533E # D8D3 8D5C # D8D4 5366 # D8D5 5363 # D8D6 5202 # D8D7 5208 # D8D8 520E # D8D9 522D # D8DA 5233 # D8DB 523F # D8DC 5240 # D8DD 524C # D8DE 525E # D8DF 5261 # D8E0 525C # D8E1 84AF # D8E2 527D # D8E3 5282 # D8E4 5281 # D8E5 5290 # D8E6 5293 # D8E7 5182 # D8E8 7F54 # D8E9 4EBB # D8EA 4EC3 # D8EB 4EC9 # D8EC 4EC2 # D8ED 4EE8 # D8EE 4EE1 # D8EF 4EEB # D8F0 4EDE # D8F1 4F1B # D8F2 4EF3 # D8F3 4F22 # D8F4 4F64 # D8F5 4EF5 # D8F6 4F25 # D8F7 4F27 # D8F8 4F09 # D8F9 4F2B # D8FA 4F5E # D8FB 4F67 # D8FC 6538 # D8FD 4F5A # D8FE 4F5D # D9A1 4F5F # D9A2 4F57 # D9A3 4F32 # D9A4 4F3D # D9A5 4F76 # D9A6 4F74 # D9A7 4F91 # D9A8 4F89 # D9A9 4F83 # D9AA 4F8F # D9AB 4F7E # D9AC 4F7B # D9AD 4FAA # D9AE 4F7C # D9AF 4FAC # D9B0 4F94 # D9B1 4FE6 # D9B2 4FE8 # D9B3 4FEA # D9B4 4FC5 # D9B5 4FDA # D9B6 4FE3 # D9B7 4FDC # D9B8 4FD1 # D9B9 4FDF # D9BA 4FF8 # D9BB 5029 # D9BC 504C # D9BD 4FF3 # D9BE 502C # D9BF 500F # D9C0 502E # D9C1 502D # D9C2 4FFE # D9C3 501C # D9C4 500C # D9C5 5025 # D9C6 5028 # D9C7 507E # D9C8 5043 # D9C9 5055 # D9CA 5048 # D9CB 504E # D9CC 506C # D9CD 507B # D9CE 50A5 # D9CF 50A7 # D9D0 50A9 # D9D1 50BA # D9D2 50D6 # D9D3 5106 # D9D4 50ED # D9D5 50EC # D9D6 50E6 # D9D7 50EE # D9D8 5107 # D9D9 510B # D9DA 4EDD # D9DB 6C3D # D9DC 4F58 # D9DD 4F65 # D9DE 4FCE # D9DF 9FA0 # D9E0 6C46 # D9E1 7C74 # D9E2 516E # D9E3 5DFD # D9E4 9EC9 # D9E5 9998 # D9E6 5181 # D9E7 5914 # D9E8 52F9 # D9E9 530D # D9EA 8A07 # D9EB 5310 # D9EC 51EB # D9ED 5919 # D9EE 5155 # D9EF 4EA0 # D9F0 5156 # D9F1 4EB3 # D9F2 886E # D9F3 88A4 # D9F4 4EB5 # D9F5 8114 # D9F6 88D2 # D9F7 7980 # D9F8 5B34 # D9F9 8803 # D9FA 7FB8 # D9FB 51AB # D9FC 51B1 # D9FD 51BD # D9FE 51BC # DAA1 51C7 # DAA2 5196 # DAA3 51A2 # DAA4 51A5 # DAA5 8BA0 # DAA6 8BA6 # DAA7 8BA7 # DAA8 8BAA # DAA9 8BB4 # DAAA 8BB5 # DAAB 8BB7 # DAAC 8BC2 # DAAD 8BC3 # DAAE 8BCB # DAAF 8BCF # DAB0 8BCE # DAB1 8BD2 # DAB2 8BD3 # DAB3 8BD4 # DAB4 8BD6 # DAB5 8BD8 # DAB6 8BD9 # DAB7 8BDC # DAB8 8BDF # DAB9 8BE0 # DABA 8BE4 # DABB 8BE8 # DABC 8BE9 # DABD 8BEE # DABE 8BF0 # DABF 8BF3 # DAC0 8BF6 # DAC1 8BF9 # DAC2 8BFC # DAC3 8BFF # DAC4 8C00 # DAC5 8C02 # DAC6 8C04 # DAC7 8C07 # DAC8 8C0C # DAC9 8C0F # DACA 8C11 # DACB 8C12 # DACC 8C14 # DACD 8C15 # DACE 8C16 # DACF 8C19 # DAD0 8C1B # DAD1 8C18 # DAD2 8C1D # DAD3 8C1F # DAD4 8C20 # DAD5 8C21 # DAD6 8C25 # DAD7 8C27 # DAD8 8C2A # DAD9 8C2B # DADA 8C2E # DADB 8C2F # DADC 8C32 # DADD 8C33 # DADE 8C35 # DADF 8C36 # DAE0 5369 # DAE1 537A # DAE2 961D # DAE3 9622 # DAE4 9621 # DAE5 9631 # DAE6 962A # DAE7 963D # DAE8 963C # DAE9 9642 # DAEA 9649 # DAEB 9654 # DAEC 965F # DAED 9667 # DAEE 966C # DAEF 9672 # DAF0 9674 # DAF1 9688 # DAF2 968D # DAF3 9697 # DAF4 96B0 # DAF5 9097 # DAF6 909B # DAF7 909D # DAF8 9099 # DAF9 90AC # DAFA 90A1 # DAFB 90B4 # DAFC 90B3 # DAFD 90B6 # DAFE 90BA # DBA1 90B8 # DBA2 90B0 # DBA3 90CF # DBA4 90C5 # DBA5 90BE # DBA6 90D0 # DBA7 90C4 # DBA8 90C7 # DBA9 90D3 # DBAA 90E6 # DBAB 90E2 # DBAC 90DC # DBAD 90D7 # DBAE 90DB # DBAF 90EB # DBB0 90EF # DBB1 90FE # DBB2 9104 # DBB3 9122 # DBB4 911E # DBB5 9123 # DBB6 9131 # DBB7 912F # DBB8 9139 # DBB9 9143 # DBBA 9146 # DBBB 520D # DBBC 5942 # DBBD 52A2 # DBBE 52AC # DBBF 52AD # DBC0 52BE # DBC1 54FF # DBC2 52D0 # DBC3 52D6 # DBC4 52F0 # DBC5 53DF # DBC6 71EE # DBC7 77CD # DBC8 5EF4 # DBC9 51F5 # DBCA 51FC # DBCB 9B2F # DBCC 53B6 # DBCD 5F01 # DBCE 755A # DBCF 5DEF # DBD0 574C # DBD1 57A9 # DBD2 57A1 # DBD3 587E # DBD4 58BC # DBD5 58C5 # DBD6 58D1 # DBD7 5729 # DBD8 572C # DBD9 572A # DBDA 5733 # DBDB 5739 # DBDC 572E # DBDD 572F # DBDE 575C # DBDF 573B # DBE0 5742 # DBE1 5769 # DBE2 5785 # DBE3 576B # DBE4 5786 # DBE5 577C # DBE6 577B # DBE7 5768 # DBE8 576D # DBE9 5776 # DBEA 5773 # DBEB 57AD # DBEC 57A4 # DBED 578C # DBEE 57B2 # DBEF 57CF # DBF0 57A7 # DBF1 57B4 # DBF2 5793 # DBF3 57A0 # DBF4 57D5 # DBF5 57D8 # DBF6 57DA # DBF7 57D9 # DBF8 57D2 # DBF9 57B8 # DBFA 57F4 # DBFB 57EF # DBFC 57F8 # DBFD 57E4 # DBFE 57DD # DCA1 580B # DCA2 580D # DCA3 57FD # DCA4 57ED # DCA5 5800 # DCA6 581E # DCA7 5819 # DCA8 5844 # DCA9 5820 # DCAA 5865 # DCAB 586C # DCAC 5881 # DCAD 5889 # DCAE 589A # DCAF 5880 # DCB0 99A8 # DCB1 9F19 # DCB2 61FF # DCB3 8279 # DCB4 827D # DCB5 827F # DCB6 828F # DCB7 828A # DCB8 82A8 # DCB9 8284 # DCBA 828E # DCBB 8291 # DCBC 8297 # DCBD 8299 # DCBE 82AB # DCBF 82B8 # DCC0 82BE # DCC1 82B0 # DCC2 82C8 # DCC3 82CA # DCC4 82E3 # DCC5 8298 # DCC6 82B7 # DCC7 82AE # DCC8 82CB # DCC9 82CC # DCCA 82C1 # DCCB 82A9 # DCCC 82B4 # DCCD 82A1 # DCCE 82AA # DCCF 829F # DCD0 82C4 # DCD1 82CE # DCD2 82A4 # DCD3 82E1 # DCD4 8309 # DCD5 82F7 # DCD6 82E4 # DCD7 830F # DCD8 8307 # DCD9 82DC # DCDA 82F4 # DCDB 82D2 # DCDC 82D8 # DCDD 830C # DCDE 82FB # DCDF 82D3 # DCE0 8311 # DCE1 831A # DCE2 8306 # DCE3 8314 # DCE4 8315 # DCE5 82E0 # DCE6 82D5 # DCE7 831C # DCE8 8351 # DCE9 835B # DCEA 835C # DCEB 8308 # DCEC 8392 # DCED 833C # DCEE 8334 # DCEF 8331 # DCF0 839B # DCF1 835E # DCF2 832F # DCF3 834F # DCF4 8347 # DCF5 8343 # DCF6 835F # DCF7 8340 # DCF8 8317 # DCF9 8360 # DCFA 832D # DCFB 833A # DCFC 8333 # DCFD 8366 # DCFE 8365 # DDA1 8368 # DDA2 831B # DDA3 8369 # DDA4 836C # DDA5 836A # DDA6 836D # DDA7 836E # DDA8 83B0 # DDA9 8378 # DDAA 83B3 # DDAB 83B4 # DDAC 83A0 # DDAD 83AA # DDAE 8393 # DDAF 839C # DDB0 8385 # DDB1 837C # DDB2 83B6 # DDB3 83A9 # DDB4 837D # DDB5 83B8 # DDB6 837B # DDB7 8398 # DDB8 839E # DDB9 83A8 # DDBA 83BA # DDBB 83BC # DDBC 83C1 # DDBD 8401 # DDBE 83E5 # DDBF 83D8 # DDC0 5807 # DDC1 8418 # DDC2 840B # DDC3 83DD # DDC4 83FD # DDC5 83D6 # DDC6 841C # DDC7 8438 # DDC8 8411 # DDC9 8406 # DDCA 83D4 # DDCB 83DF # DDCC 840F # DDCD 8403 # DDCE 83F8 # DDCF 83F9 # DDD0 83EA # DDD1 83C5 # DDD2 83C0 # DDD3 8426 # DDD4 83F0 # DDD5 83E1 # DDD6 845C # DDD7 8451 # DDD8 845A # DDD9 8459 # DDDA 8473 # DDDB 8487 # DDDC 8488 # DDDD 847A # DDDE 8489 # DDDF 8478 # DDE0 843C # DDE1 8446 # DDE2 8469 # DDE3 8476 # DDE4 848C # DDE5 848E # DDE6 8431 # DDE7 846D # DDE8 84C1 # DDE9 84CD # DDEA 84D0 # DDEB 84E6 # DDEC 84BD # DDED 84D3 # DDEE 84CA # DDEF 84BF # DDF0 84BA # DDF1 84E0 # DDF2 84A1 # DDF3 84B9 # DDF4 84B4 # DDF5 8497 # DDF6 84E5 # DDF7 84E3 # DDF8 850C # DDF9 750D # DDFA 8538 # DDFB 84F0 # DDFC 8539 # DDFD 851F # DDFE 853A # DEA1 8556 # DEA2 853B # DEA3 84FF # DEA4 84FC # DEA5 8559 # DEA6 8548 # DEA7 8568 # DEA8 8564 # DEA9 855E # DEAA 857A # DEAB 77A2 # DEAC 8543 # DEAD 8572 # DEAE 857B # DEAF 85A4 # DEB0 85A8 # DEB1 8587 # DEB2 858F # DEB3 8579 # DEB4 85AE # DEB5 859C # DEB6 8585 # DEB7 85B9 # DEB8 85B7 # DEB9 85B0 # DEBA 85D3 # DEBB 85C1 # DEBC 85DC # DEBD 85FF # DEBE 8627 # DEBF 8605 # DEC0 8629 # DEC1 8616 # DEC2 863C # DEC3 5EFE # DEC4 5F08 # DEC5 593C # DEC6 5941 # DEC7 8037 # DEC8 5955 # DEC9 595A # DECA 5958 # DECB 530F # DECC 5C22 # DECD 5C25 # DECE 5C2C # DECF 5C34 # DED0 624C # DED1 626A # DED2 629F # DED3 62BB # DED4 62CA # DED5 62DA # DED6 62D7 # DED7 62EE # DED8 6322 # DED9 62F6 # DEDA 6339 # DEDB 634B # DEDC 6343 # DEDD 63AD # DEDE 63F6 # DEDF 6371 # DEE0 637A # DEE1 638E # DEE2 63B4 # DEE3 636D # DEE4 63AC # DEE5 638A # DEE6 6369 # DEE7 63AE # DEE8 63BC # DEE9 63F2 # DEEA 63F8 # DEEB 63E0 # DEEC 63FF # DEED 63C4 # DEEE 63DE # DEEF 63CE # DEF0 6452 # DEF1 63C6 # DEF2 63BE # DEF3 6445 # DEF4 6441 # DEF5 640B # DEF6 641B # DEF7 6420 # DEF8 640C # DEF9 6426 # DEFA 6421 # DEFB 645E # DEFC 6484 # DEFD 646D # DEFE 6496 # DFA1 647A # DFA2 64B7 # DFA3 64B8 # DFA4 6499 # DFA5 64BA # DFA6 64C0 # DFA7 64D0 # DFA8 64D7 # DFA9 64E4 # DFAA 64E2 # DFAB 6509 # DFAC 6525 # DFAD 652E # DFAE 5F0B # DFAF 5FD2 # DFB0 7519 # DFB1 5F11 # DFB2 535F # DFB3 53F1 # DFB4 53FD # DFB5 53E9 # DFB6 53E8 # DFB7 53FB # DFB8 5412 # DFB9 5416 # DFBA 5406 # DFBB 544B # DFBC 5452 # DFBD 5453 # DFBE 5454 # DFBF 5456 # DFC0 5443 # DFC1 5421 # DFC2 5457 # DFC3 5459 # DFC4 5423 # DFC5 5432 # DFC6 5482 # DFC7 5494 # DFC8 5477 # DFC9 5471 # DFCA 5464 # DFCB 549A # DFCC 549B # DFCD 5484 # DFCE 5476 # DFCF 5466 # DFD0 549D # DFD1 54D0 # DFD2 54AD # DFD3 54C2 # DFD4 54B4 # DFD5 54D2 # DFD6 54A7 # DFD7 54A6 # DFD8 54D3 # DFD9 54D4 # DFDA 5472 # DFDB 54A3 # DFDC 54D5 # DFDD 54BB # DFDE 54BF # DFDF 54CC # DFE0 54D9 # DFE1 54DA # DFE2 54DC # DFE3 54A9 # DFE4 54AA # DFE5 54A4 # DFE6 54DD # DFE7 54CF # DFE8 54DE # DFE9 551B # DFEA 54E7 # DFEB 5520 # DFEC 54FD # DFED 5514 # DFEE 54F3 # DFEF 5522 # DFF0 5523 # DFF1 550F # DFF2 5511 # DFF3 5527 # DFF4 552A # DFF5 5567 # DFF6 558F # DFF7 55B5 # DFF8 5549 # DFF9 556D # DFFA 5541 # DFFB 5555 # DFFC 553F # DFFD 5550 # DFFE 553C # E0A1 5537 # E0A2 5556 # E0A3 5575 # E0A4 5576 # E0A5 5577 # E0A6 5533 # E0A7 5530 # E0A8 555C # E0A9 558B # E0AA 55D2 # E0AB 5583 # E0AC 55B1 # E0AD 55B9 # E0AE 5588 # E0AF 5581 # E0B0 559F # E0B1 557E # E0B2 55D6 # E0B3 5591 # E0B4 557B # E0B5 55DF # E0B6 55BD # E0B7 55BE # E0B8 5594 # E0B9 5599 # E0BA 55EA # E0BB 55F7 # E0BC 55C9 # E0BD 561F # E0BE 55D1 # E0BF 55EB # E0C0 55EC # E0C1 55D4 # E0C2 55E6 # E0C3 55DD # E0C4 55C4 # E0C5 55EF # E0C6 55E5 # E0C7 55F2 # E0C8 55F3 # E0C9 55CC # E0CA 55CD # E0CB 55E8 # E0CC 55F5 # E0CD 55E4 # E0CE 8F94 # E0CF 561E # E0D0 5608 # E0D1 560C # E0D2 5601 # E0D3 5624 # E0D4 5623 # E0D5 55FE # E0D6 5600 # E0D7 5627 # E0D8 562D # E0D9 5658 # E0DA 5639 # E0DB 5657 # E0DC 562C # E0DD 564D # E0DE 5662 # E0DF 5659 # E0E0 565C # E0E1 564C # E0E2 5654 # E0E3 5686 # E0E4 5664 # E0E5 5671 # E0E6 566B # E0E7 567B # E0E8 567C # E0E9 5685 # E0EA 5693 # E0EB 56AF # E0EC 56D4 # E0ED 56D7 # E0EE 56DD # E0EF 56E1 # E0F0 56F5 # E0F1 56EB # E0F2 56F9 # E0F3 56FF # E0F4 5704 # E0F5 570A # E0F6 5709 # E0F7 571C # E0F8 5E0F # E0F9 5E19 # E0FA 5E14 # E0FB 5E11 # E0FC 5E31 # E0FD 5E3B # E0FE 5E3C # E1A1 5E37 # E1A2 5E44 # E1A3 5E54 # E1A4 5E5B # E1A5 5E5E # E1A6 5E61 # E1A7 5C8C # E1A8 5C7A # E1A9 5C8D # E1AA 5C90 # E1AB 5C96 # E1AC 5C88 # E1AD 5C98 # E1AE 5C99 # E1AF 5C91 # E1B0 5C9A # E1B1 5C9C # E1B2 5CB5 # E1B3 5CA2 # E1B4 5CBD # E1B5 5CAC # E1B6 5CAB # E1B7 5CB1 # E1B8 5CA3 # E1B9 5CC1 # E1BA 5CB7 # E1BB 5CC4 # E1BC 5CD2 # E1BD 5CE4 # E1BE 5CCB # E1BF 5CE5 # E1C0 5D02 # E1C1 5D03 # E1C2 5D27 # E1C3 5D26 # E1C4 5D2E # E1C5 5D24 # E1C6 5D1E # E1C7 5D06 # E1C8 5D1B # E1C9 5D58 # E1CA 5D3E # E1CB 5D34 # E1CC 5D3D # E1CD 5D6C # E1CE 5D5B # E1CF 5D6F # E1D0 5D5D # E1D1 5D6B # E1D2 5D4B # E1D3 5D4A # E1D4 5D69 # E1D5 5D74 # E1D6 5D82 # E1D7 5D99 # E1D8 5D9D # E1D9 8C73 # E1DA 5DB7 # E1DB 5DC5 # E1DC 5F73 # E1DD 5F77 # E1DE 5F82 # E1DF 5F87 # E1E0 5F89 # E1E1 5F8C # E1E2 5F95 # E1E3 5F99 # E1E4 5F9C # E1E5 5FA8 # E1E6 5FAD # E1E7 5FB5 # E1E8 5FBC # E1E9 8862 # E1EA 5F61 # E1EB 72AD # E1EC 72B0 # E1ED 72B4 # E1EE 72B7 # E1EF 72B8 # E1F0 72C3 # E1F1 72C1 # E1F2 72CE # E1F3 72CD # E1F4 72D2 # E1F5 72E8 # E1F6 72EF # E1F7 72E9 # E1F8 72F2 # E1F9 72F4 # E1FA 72F7 # E1FB 7301 # E1FC 72F3 # E1FD 7303 # E1FE 72FA # E2A1 72FB # E2A2 7317 # E2A3 7313 # E2A4 7321 # E2A5 730A # E2A6 731E # E2A7 731D # E2A8 7315 # E2A9 7322 # E2AA 7339 # E2AB 7325 # E2AC 732C # E2AD 7338 # E2AE 7331 # E2AF 7350 # E2B0 734D # E2B1 7357 # E2B2 7360 # E2B3 736C # E2B4 736F # E2B5 737E # E2B6 821B # E2B7 5925 # E2B8 98E7 # E2B9 5924 # E2BA 5902 # E2BB 9963 # E2BC 9967 # E2BD 9968 # E2BE 9969 # E2BF 996A # E2C0 996B # E2C1 996C # E2C2 9974 # E2C3 9977 # E2C4 997D # E2C5 9980 # E2C6 9984 # E2C7 9987 # E2C8 998A # E2C9 998D # E2CA 9990 # E2CB 9991 # E2CC 9993 # E2CD 9994 # E2CE 9995 # E2CF 5E80 # E2D0 5E91 # E2D1 5E8B # E2D2 5E96 # E2D3 5EA5 # E2D4 5EA0 # E2D5 5EB9 # E2D6 5EB5 # E2D7 5EBE # E2D8 5EB3 # E2D9 8D53 # E2DA 5ED2 # E2DB 5ED1 # E2DC 5EDB # E2DD 5EE8 # E2DE 5EEA # E2DF 81BA # E2E0 5FC4 # E2E1 5FC9 # E2E2 5FD6 # E2E3 5FCF # E2E4 6003 # E2E5 5FEE # E2E6 6004 # E2E7 5FE1 # E2E8 5FE4 # E2E9 5FFE # E2EA 6005 # E2EB 6006 # E2EC 5FEA # E2ED 5FED # E2EE 5FF8 # E2EF 6019 # E2F0 6035 # E2F1 6026 # E2F2 601B # E2F3 600F # E2F4 600D # E2F5 6029 # E2F6 602B # E2F7 600A # E2F8 603F # E2F9 6021 # E2FA 6078 # E2FB 6079 # E2FC 607B # E2FD 607A # E2FE 6042 # E3A1 606A # E3A2 607D # E3A3 6096 # E3A4 609A # E3A5 60AD # E3A6 609D # E3A7 6083 # E3A8 6092 # E3A9 608C # E3AA 609B # E3AB 60EC # E3AC 60BB # E3AD 60B1 # E3AE 60DD # E3AF 60D8 # E3B0 60C6 # E3B1 60DA # E3B2 60B4 # E3B3 6120 # E3B4 6126 # E3B5 6115 # E3B6 6123 # E3B7 60F4 # E3B8 6100 # E3B9 610E # E3BA 612B # E3BB 614A # E3BC 6175 # E3BD 61AC # E3BE 6194 # E3BF 61A7 # E3C0 61B7 # E3C1 61D4 # E3C2 61F5 # E3C3 5FDD # E3C4 96B3 # E3C5 95E9 # E3C6 95EB # E3C7 95F1 # E3C8 95F3 # E3C9 95F5 # E3CA 95F6 # E3CB 95FC # E3CC 95FE # E3CD 9603 # E3CE 9604 # E3CF 9606 # E3D0 9608 # E3D1 960A # E3D2 960B # E3D3 960C # E3D4 960D # E3D5 960F # E3D6 9612 # E3D7 9615 # E3D8 9616 # E3D9 9617 # E3DA 9619 # E3DB 961A # E3DC 4E2C # E3DD 723F # E3DE 6215 # E3DF 6C35 # E3E0 6C54 # E3E1 6C5C # E3E2 6C4A # E3E3 6CA3 # E3E4 6C85 # E3E5 6C90 # E3E6 6C94 # E3E7 6C8C # E3E8 6C68 # E3E9 6C69 # E3EA 6C74 # E3EB 6C76 # E3EC 6C86 # E3ED 6CA9 # E3EE 6CD0 # E3EF 6CD4 # E3F0 6CAD # E3F1 6CF7 # E3F2 6CF8 # E3F3 6CF1 # E3F4 6CD7 # E3F5 6CB2 # E3F6 6CE0 # E3F7 6CD6 # E3F8 6CFA # E3F9 6CEB # E3FA 6CEE # E3FB 6CB1 # E3FC 6CD3 # E3FD 6CEF # E3FE 6CFE # E4A1 6D39 # E4A2 6D27 # E4A3 6D0C # E4A4 6D43 # E4A5 6D48 # E4A6 6D07 # E4A7 6D04 # E4A8 6D19 # E4A9 6D0E # E4AA 6D2B # E4AB 6D4D # E4AC 6D2E # E4AD 6D35 # E4AE 6D1A # E4AF 6D4F # E4B0 6D52 # E4B1 6D54 # E4B2 6D33 # E4B3 6D91 # E4B4 6D6F # E4B5 6D9E # E4B6 6DA0 # E4B7 6D5E # E4B8 6D93 # E4B9 6D94 # E4BA 6D5C # E4BB 6D60 # E4BC 6D7C # E4BD 6D63 # E4BE 6E1A # E4BF 6DC7 # E4C0 6DC5 # E4C1 6DDE # E4C2 6E0E # E4C3 6DBF # E4C4 6DE0 # E4C5 6E11 # E4C6 6DE6 # E4C7 6DDD # E4C8 6DD9 # E4C9 6E16 # E4CA 6DAB # E4CB 6E0C # E4CC 6DAE # E4CD 6E2B # E4CE 6E6E # E4CF 6E4E # E4D0 6E6B # E4D1 6EB2 # E4D2 6E5F # E4D3 6E86 # E4D4 6E53 # E4D5 6E54 # E4D6 6E32 # E4D7 6E25 # E4D8 6E44 # E4D9 6EDF # E4DA 6EB1 # E4DB 6E98 # E4DC 6EE0 # E4DD 6F2D # E4DE 6EE2 # E4DF 6EA5 # E4E0 6EA7 # E4E1 6EBD # E4E2 6EBB # E4E3 6EB7 # E4E4 6ED7 # E4E5 6EB4 # E4E6 6ECF # E4E7 6E8F # E4E8 6EC2 # E4E9 6E9F # E4EA 6F62 # E4EB 6F46 # E4EC 6F47 # E4ED 6F24 # E4EE 6F15 # E4EF 6EF9 # E4F0 6F2F # E4F1 6F36 # E4F2 6F4B # E4F3 6F74 # E4F4 6F2A # E4F5 6F09 # E4F6 6F29 # E4F7 6F89 # E4F8 6F8D # E4F9 6F8C # E4FA 6F78 # E4FB 6F72 # E4FC 6F7C # E4FD 6F7A # E4FE 6FD1 # E5A1 6FC9 # E5A2 6FA7 # E5A3 6FB9 # E5A4 6FB6 # E5A5 6FC2 # E5A6 6FE1 # E5A7 6FEE # E5A8 6FDE # E5A9 6FE0 # E5AA 6FEF # E5AB 701A # E5AC 7023 # E5AD 701B # E5AE 7039 # E5AF 7035 # E5B0 704F # E5B1 705E # E5B2 5B80 # E5B3 5B84 # E5B4 5B95 # E5B5 5B93 # E5B6 5BA5 # E5B7 5BB8 # E5B8 752F # E5B9 9A9E # E5BA 6434 # E5BB 5BE4 # E5BC 5BEE # E5BD 8930 # E5BE 5BF0 # E5BF 8E47 # E5C0 8B07 # E5C1 8FB6 # E5C2 8FD3 # E5C3 8FD5 # E5C4 8FE5 # E5C5 8FEE # E5C6 8FE4 # E5C7 8FE9 # E5C8 8FE6 # E5C9 8FF3 # E5CA 8FE8 # E5CB 9005 # E5CC 9004 # E5CD 900B # E5CE 9026 # E5CF 9011 # E5D0 900D # E5D1 9016 # E5D2 9021 # E5D3 9035 # E5D4 9036 # E5D5 902D # E5D6 902F # E5D7 9044 # E5D8 9051 # E5D9 9052 # E5DA 9050 # E5DB 9068 # E5DC 9058 # E5DD 9062 # E5DE 905B # E5DF 66B9 # E5E0 9074 # E5E1 907D # E5E2 9082 # E5E3 9088 # E5E4 9083 # E5E5 908B # E5E6 5F50 # E5E7 5F57 # E5E8 5F56 # E5E9 5F58 # E5EA 5C3B # E5EB 54AB # E5EC 5C50 # E5ED 5C59 # E5EE 5B71 # E5EF 5C63 # E5F0 5C66 # E5F1 7FBC # E5F2 5F2A # E5F3 5F29 # E5F4 5F2D # E5F5 8274 # E5F6 5F3C # E5F7 9B3B # E5F8 5C6E # E5F9 5981 # E5FA 5983 # E5FB 598D # E5FC 59A9 # E5FD 59AA # E5FE 59A3 # E6A1 5997 # E6A2 59CA # E6A3 59AB # E6A4 599E # E6A5 59A4 # E6A6 59D2 # E6A7 59B2 # E6A8 59AF # E6A9 59D7 # E6AA 59BE # E6AB 5A05 # E6AC 5A06 # E6AD 59DD # E6AE 5A08 # E6AF 59E3 # E6B0 59D8 # E6B1 59F9 # E6B2 5A0C # E6B3 5A09 # E6B4 5A32 # E6B5 5A34 # E6B6 5A11 # E6B7 5A23 # E6B8 5A13 # E6B9 5A40 # E6BA 5A67 # E6BB 5A4A # E6BC 5A55 # E6BD 5A3C # E6BE 5A62 # E6BF 5A75 # E6C0 80EC # E6C1 5AAA # E6C2 5A9B # E6C3 5A77 # E6C4 5A7A # E6C5 5ABE # E6C6 5AEB # E6C7 5AB2 # E6C8 5AD2 # E6C9 5AD4 # E6CA 5AB8 # E6CB 5AE0 # E6CC 5AE3 # E6CD 5AF1 # E6CE 5AD6 # E6CF 5AE6 # E6D0 5AD8 # E6D1 5ADC # E6D2 5B09 # E6D3 5B17 # E6D4 5B16 # E6D5 5B32 # E6D6 5B37 # E6D7 5B40 # E6D8 5C15 # E6D9 5C1C # E6DA 5B5A # E6DB 5B65 # E6DC 5B73 # E6DD 5B51 # E6DE 5B53 # E6DF 5B62 # E6E0 9A75 # E6E1 9A77 # E6E2 9A78 # E6E3 9A7A # E6E4 9A7F # E6E5 9A7D # E6E6 9A80 # E6E7 9A81 # E6E8 9A85 # E6E9 9A88 # E6EA 9A8A # E6EB 9A90 # E6EC 9A92 # E6ED 9A93 # E6EE 9A96 # E6EF 9A98 # E6F0 9A9B # E6F1 9A9C # E6F2 9A9D # E6F3 9A9F # E6F4 9AA0 # E6F5 9AA2 # E6F6 9AA3 # E6F7 9AA5 # E6F8 9AA7 # E6F9 7E9F # E6FA 7EA1 # E6FB 7EA3 # E6FC 7EA5 # E6FD 7EA8 # E6FE 7EA9 # E7A1 7EAD # E7A2 7EB0 # E7A3 7EBE # E7A4 7EC0 # E7A5 7EC1 # E7A6 7EC2 # E7A7 7EC9 # E7A8 7ECB # E7A9 7ECC # E7AA 7ED0 # E7AB 7ED4 # E7AC 7ED7 # E7AD 7EDB # E7AE 7EE0 # E7AF 7EE1 # E7B0 7EE8 # E7B1 7EEB # E7B2 7EEE # E7B3 7EEF # E7B4 7EF1 # E7B5 7EF2 # E7B6 7F0D # E7B7 7EF6 # E7B8 7EFA # E7B9 7EFB # E7BA 7EFE # E7BB 7F01 # E7BC 7F02 # E7BD 7F03 # E7BE 7F07 # E7BF 7F08 # E7C0 7F0B # E7C1 7F0C # E7C2 7F0F # E7C3 7F11 # E7C4 7F12 # E7C5 7F17 # E7C6 7F19 # E7C7 7F1C # E7C8 7F1B # E7C9 7F1F # E7CA 7F21 # E7CB 7F22 # E7CC 7F23 # E7CD 7F24 # E7CE 7F25 # E7CF 7F26 # E7D0 7F27 # E7D1 7F2A # E7D2 7F2B # E7D3 7F2C # E7D4 7F2D # E7D5 7F2F # E7D6 7F30 # E7D7 7F31 # E7D8 7F32 # E7D9 7F33 # E7DA 7F35 # E7DB 5E7A # E7DC 757F # E7DD 5DDB # E7DE 753E # E7DF 9095 # E7E0 738E # E7E1 7391 # E7E2 73AE # E7E3 73A2 # E7E4 739F # E7E5 73CF # E7E6 73C2 # E7E7 73D1 # E7E8 73B7 # E7E9 73B3 # E7EA 73C0 # E7EB 73C9 # E7EC 73C8 # E7ED 73E5 # E7EE 73D9 # E7EF 987C # E7F0 740A # E7F1 73E9 # E7F2 73E7 # E7F3 73DE # E7F4 73BA # E7F5 73F2 # E7F6 740F # E7F7 742A # E7F8 745B # E7F9 7426 # E7FA 7425 # E7FB 7428 # E7FC 7430 # E7FD 742E # E7FE 742C # E8A1 741B # E8A2 741A # E8A3 7441 # E8A4 745C # E8A5 7457 # E8A6 7455 # E8A7 7459 # E8A8 7477 # E8A9 746D # E8AA 747E # E8AB 749C # E8AC 748E # E8AD 7480 # E8AE 7481 # E8AF 7487 # E8B0 748B # E8B1 749E # E8B2 74A8 # E8B3 74A9 # E8B4 7490 # E8B5 74A7 # E8B6 74D2 # E8B7 74BA # E8B8 97EA # E8B9 97EB # E8BA 97EC # E8BB 674C # E8BC 6753 # E8BD 675E # E8BE 6748 # E8BF 6769 # E8C0 67A5 # E8C1 6787 # E8C2 676A # E8C3 6773 # E8C4 6798 # E8C5 67A7 # E8C6 6775 # E8C7 67A8 # E8C8 679E # E8C9 67AD # E8CA 678B # E8CB 6777 # E8CC 677C # E8CD 67F0 # E8CE 6809 # E8CF 67D8 # E8D0 680A # E8D1 67E9 # E8D2 67B0 # E8D3 680C # E8D4 67D9 # E8D5 67B5 # E8D6 67DA # E8D7 67B3 # E8D8 67DD # E8D9 6800 # E8DA 67C3 # E8DB 67B8 # E8DC 67E2 # E8DD 680E # E8DE 67C1 # E8DF 67FD # E8E0 6832 # E8E1 6833 # E8E2 6860 # E8E3 6861 # E8E4 684E # E8E5 6862 # E8E6 6844 # E8E7 6864 # E8E8 6883 # E8E9 681D # E8EA 6855 # E8EB 6866 # E8EC 6841 # E8ED 6867 # E8EE 6840 # E8EF 683E # E8F0 684A # E8F1 6849 # E8F2 6829 # E8F3 68B5 # E8F4 688F # E8F5 6874 # E8F6 6877 # E8F7 6893 # E8F8 686B # E8F9 68C2 # E8FA 696E # E8FB 68FC # E8FC 691F # E8FD 6920 # E8FE 68F9 # E9A1 6924 # E9A2 68F0 # E9A3 690B # E9A4 6901 # E9A5 6957 # E9A6 68E3 # E9A7 6910 # E9A8 6971 # E9A9 6939 # E9AA 6960 # E9AB 6942 # E9AC 695D # E9AD 6984 # E9AE 696B # E9AF 6980 # E9B0 6998 # E9B1 6978 # E9B2 6934 # E9B3 69CC # E9B4 6987 # E9B5 6988 # E9B6 69CE # E9B7 6989 # E9B8 6966 # E9B9 6963 # E9BA 6979 # E9BB 699B # E9BC 69A7 # E9BD 69BB # E9BE 69AB # E9BF 69AD # E9C0 69D4 # E9C1 69B1 # E9C2 69C1 # E9C3 69CA # E9C4 69DF # E9C5 6995 # E9C6 69E0 # E9C7 698D # E9C8 69FF # E9C9 6A2F # E9CA 69ED # E9CB 6A17 # E9CC 6A18 # E9CD 6A65 # E9CE 69F2 # E9CF 6A44 # E9D0 6A3E # E9D1 6AA0 # E9D2 6A50 # E9D3 6A5B # E9D4 6A35 # E9D5 6A8E # E9D6 6A79 # E9D7 6A3D # E9D8 6A28 # E9D9 6A58 # E9DA 6A7C # E9DB 6A91 # E9DC 6A90 # E9DD 6AA9 # E9DE 6A97 # E9DF 6AAB # E9E0 7337 # E9E1 7352 # E9E2 6B81 # E9E3 6B82 # E9E4 6B87 # E9E5 6B84 # E9E6 6B92 # E9E7 6B93 # E9E8 6B8D # E9E9 6B9A # E9EA 6B9B # E9EB 6BA1 # E9EC 6BAA # E9ED 8F6B # E9EE 8F6D # E9EF 8F71 # E9F0 8F72 # E9F1 8F73 # E9F2 8F75 # E9F3 8F76 # E9F4 8F78 # E9F5 8F77 # E9F6 8F79 # E9F7 8F7A # E9F8 8F7C # E9F9 8F7E # E9FA 8F81 # E9FB 8F82 # E9FC 8F84 # E9FD 8F87 # E9FE 8F8B # EAA1 8F8D # EAA2 8F8E # EAA3 8F8F # EAA4 8F98 # EAA5 8F9A # EAA6 8ECE # EAA7 620B # EAA8 6217 # EAA9 621B # EAAA 621F # EAAB 6222 # EAAC 6221 # EAAD 6225 # EAAE 6224 # EAAF 622C # EAB0 81E7 # EAB1 74EF # EAB2 74F4 # EAB3 74FF # EAB4 750F # EAB5 7511 # EAB6 7513 # EAB7 6534 # EAB8 65EE # EAB9 65EF # EABA 65F0 # EABB 660A # EABC 6619 # EABD 6772 # EABE 6603 # EABF 6615 # EAC0 6600 # EAC1 7085 # EAC2 66F7 # EAC3 661D # EAC4 6634 # EAC5 6631 # EAC6 6636 # EAC7 6635 # EAC8 8006 # EAC9 665F # EACA 6654 # EACB 6641 # EACC 664F # EACD 6656 # EACE 6661 # EACF 6657 # EAD0 6677 # EAD1 6684 # EAD2 668C # EAD3 66A7 # EAD4 669D # EAD5 66BE # EAD6 66DB # EAD7 66DC # EAD8 66E6 # EAD9 66E9 # EADA 8D32 # EADB 8D33 # EADC 8D36 # EADD 8D3B # EADE 8D3D # EADF 8D40 # EAE0 8D45 # EAE1 8D46 # EAE2 8D48 # EAE3 8D49 # EAE4 8D47 # EAE5 8D4D # EAE6 8D55 # EAE7 8D59 # EAE8 89C7 # EAE9 89CA # EAEA 89CB # EAEB 89CC # EAEC 89CE # EAED 89CF # EAEE 89D0 # EAEF 89D1 # EAF0 726E # EAF1 729F # EAF2 725D # EAF3 7266 # EAF4 726F # EAF5 727E # EAF6 727F # EAF7 7284 # EAF8 728B # EAF9 728D # EAFA 728F # EAFB 7292 # EAFC 6308 # EAFD 6332 # EAFE 63B0 # EBA1 643F # EBA2 64D8 # EBA3 8004 # EBA4 6BEA # EBA5 6BF3 # EBA6 6BFD # EBA7 6BF5 # EBA8 6BF9 # EBA9 6C05 # EBAA 6C07 # EBAB 6C06 # EBAC 6C0D # EBAD 6C15 # EBAE 6C18 # EBAF 6C19 # EBB0 6C1A # EBB1 6C21 # EBB2 6C29 # EBB3 6C24 # EBB4 6C2A # EBB5 6C32 # EBB6 6535 # EBB7 6555 # EBB8 656B # EBB9 724D # EBBA 7252 # EBBB 7256 # EBBC 7230 # EBBD 8662 # EBBE 5216 # EBBF 809F # EBC0 809C # EBC1 8093 # EBC2 80BC # EBC3 670A # EBC4 80BD # EBC5 80B1 # EBC6 80AB # EBC7 80AD # EBC8 80B4 # EBC9 80B7 # EBCA 80E7 # EBCB 80E8 # EBCC 80E9 # EBCD 80EA # EBCE 80DB # EBCF 80C2 # EBD0 80C4 # EBD1 80D9 # EBD2 80CD # EBD3 80D7 # EBD4 6710 # EBD5 80DD # EBD6 80EB # EBD7 80F1 # EBD8 80F4 # EBD9 80ED # EBDA 810D # EBDB 810E # EBDC 80F2 # EBDD 80FC # EBDE 6715 # EBDF 8112 # EBE0 8C5A # EBE1 8136 # EBE2 811E # EBE3 812C # EBE4 8118 # EBE5 8132 # EBE6 8148 # EBE7 814C # EBE8 8153 # EBE9 8174 # EBEA 8159 # EBEB 815A # EBEC 8171 # EBED 8160 # EBEE 8169 # EBEF 817C # EBF0 817D # EBF1 816D # EBF2 8167 # EBF3 584D # EBF4 5AB5 # EBF5 8188 # EBF6 8182 # EBF7 8191 # EBF8 6ED5 # EBF9 81A3 # EBFA 81AA # EBFB 81CC # EBFC 6726 # EBFD 81CA # EBFE 81BB # ECA1 81C1 # ECA2 81A6 # ECA3 6B24 # ECA4 6B37 # ECA5 6B39 # ECA6 6B43 # ECA7 6B46 # ECA8 6B59 # ECA9 98D1 # ECAA 98D2 # ECAB 98D3 # ECAC 98D5 # ECAD 98D9 # ECAE 98DA # ECAF 6BB3 # ECB0 5F40 # ECB1 6BC2 # ECB2 89F3 # ECB3 6590 # ECB4 9F51 # ECB5 6593 # ECB6 65BC # ECB7 65C6 # ECB8 65C4 # ECB9 65C3 # ECBA 65CC # ECBB 65CE # ECBC 65D2 # ECBD 65D6 # ECBE 7080 # ECBF 709C # ECC0 7096 # ECC1 709D # ECC2 70BB # ECC3 70C0 # ECC4 70B7 # ECC5 70AB # ECC6 70B1 # ECC7 70E8 # ECC8 70CA # ECC9 7110 # ECCA 7113 # ECCB 7116 # ECCC 712F # ECCD 7131 # ECCE 7173 # ECCF 715C # ECD0 7168 # ECD1 7145 # ECD2 7172 # ECD3 714A # ECD4 7178 # ECD5 717A # ECD6 7198 # ECD7 71B3 # ECD8 71B5 # ECD9 71A8 # ECDA 71A0 # ECDB 71E0 # ECDC 71D4 # ECDD 71E7 # ECDE 71F9 # ECDF 721D # ECE0 7228 # ECE1 706C # ECE2 7118 # ECE3 7166 # ECE4 71B9 # ECE5 623E # ECE6 623D # ECE7 6243 # ECE8 6248 # ECE9 6249 # ECEA 793B # ECEB 7940 # ECEC 7946 # ECED 7949 # ECEE 795B # ECEF 795C # ECF0 7953 # ECF1 795A # ECF2 7962 # ECF3 7957 # ECF4 7960 # ECF5 796F # ECF6 7967 # ECF7 797A # ECF8 7985 # ECF9 798A # ECFA 799A # ECFB 79A7 # ECFC 79B3 # ECFD 5FD1 # ECFE 5FD0 # EDA1 603C # EDA2 605D # EDA3 605A # EDA4 6067 # EDA5 6041 # EDA6 6059 # EDA7 6063 # EDA8 60AB # EDA9 6106 # EDAA 610D # EDAB 615D # EDAC 61A9 # EDAD 619D # EDAE 61CB # EDAF 61D1 # EDB0 6206 # EDB1 8080 # EDB2 807F # EDB3 6C93 # EDB4 6CF6 # EDB5 6DFC # EDB6 77F6 # EDB7 77F8 # EDB8 7800 # EDB9 7809 # EDBA 7817 # EDBB 7818 # EDBC 7811 # EDBD 65AB # EDBE 782D # EDBF 781C # EDC0 781D # EDC1 7839 # EDC2 783A # EDC3 783B # EDC4 781F # EDC5 783C # EDC6 7825 # EDC7 782C # EDC8 7823 # EDC9 7829 # EDCA 784E # EDCB 786D # EDCC 7856 # EDCD 7857 # EDCE 7826 # EDCF 7850 # EDD0 7847 # EDD1 784C # EDD2 786A # EDD3 789B # EDD4 7893 # EDD5 789A # EDD6 7887 # EDD7 789C # EDD8 78A1 # EDD9 78A3 # EDDA 78B2 # EDDB 78B9 # EDDC 78A5 # EDDD 78D4 # EDDE 78D9 # EDDF 78C9 # EDE0 78EC # EDE1 78F2 # EDE2 7905 # EDE3 78F4 # EDE4 7913 # EDE5 7924 # EDE6 791E # EDE7 7934 # EDE8 9F9B # EDE9 9EF9 # EDEA 9EFB # EDEB 9EFC # EDEC 76F1 # EDED 7704 # EDEE 770D # EDEF 76F9 # EDF0 7707 # EDF1 7708 # EDF2 771A # EDF3 7722 # EDF4 7719 # EDF5 772D # EDF6 7726 # EDF7 7735 # EDF8 7738 # EDF9 7750 # EDFA 7751 # EDFB 7747 # EDFC 7743 # EDFD 775A # EDFE 7768 # EEA1 7762 # EEA2 7765 # EEA3 777F # EEA4 778D # EEA5 777D # EEA6 7780 # EEA7 778C # EEA8 7791 # EEA9 779F # EEAA 77A0 # EEAB 77B0 # EEAC 77B5 # EEAD 77BD # EEAE 753A # EEAF 7540 # EEB0 754E # EEB1 754B # EEB2 7548 # EEB3 755B # EEB4 7572 # EEB5 7579 # EEB6 7583 # EEB7 7F58 # EEB8 7F61 # EEB9 7F5F # EEBA 8A48 # EEBB 7F68 # EEBC 7F74 # EEBD 7F71 # EEBE 7F79 # EEBF 7F81 # EEC0 7F7E # EEC1 76CD # EEC2 76E5 # EEC3 8832 # EEC4 9485 # EEC5 9486 # EEC6 9487 # EEC7 948B # EEC8 948A # EEC9 948C # EECA 948D # EECB 948F # EECC 9490 # EECD 9494 # EECE 9497 # EECF 9495 # EED0 949A # EED1 949B # EED2 949C # EED3 94A3 # EED4 94A4 # EED5 94AB # EED6 94AA # EED7 94AD # EED8 94AC # EED9 94AF # EEDA 94B0 # EEDB 94B2 # EEDC 94B4 # EEDD 94B6 # EEDE 94B7 # EEDF 94B8 # EEE0 94B9 # EEE1 94BA # EEE2 94BC # EEE3 94BD # EEE4 94BF # EEE5 94C4 # EEE6 94C8 # EEE7 94C9 # EEE8 94CA # EEE9 94CB # EEEA 94CC # EEEB 94CD # EEEC 94CE # EEED 94D0 # EEEE 94D1 # EEEF 94D2 # EEF0 94D5 # EEF1 94D6 # EEF2 94D7 # EEF3 94D9 # EEF4 94D8 # EEF5 94DB # EEF6 94DE # EEF7 94DF # EEF8 94E0 # EEF9 94E2 # EEFA 94E4 # EEFB 94E5 # EEFC 94E7 # EEFD 94E8 # EEFE 94EA # EFA1 94E9 # EFA2 94EB # EFA3 94EE # EFA4 94EF # EFA5 94F3 # EFA6 94F4 # EFA7 94F5 # EFA8 94F7 # EFA9 94F9 # EFAA 94FC # EFAB 94FD # EFAC 94FF # EFAD 9503 # EFAE 9502 # EFAF 9506 # EFB0 9507 # EFB1 9509 # EFB2 950A # EFB3 950D # EFB4 950E # EFB5 950F # EFB6 9512 # EFB7 9513 # EFB8 9514 # EFB9 9515 # EFBA 9516 # EFBB 9518 # EFBC 951B # EFBD 951D # EFBE 951E # EFBF 951F # EFC0 9522 # EFC1 952A # EFC2 952B # EFC3 9529 # EFC4 952C # EFC5 9531 # EFC6 9532 # EFC7 9534 # EFC8 9536 # EFC9 9537 # EFCA 9538 # EFCB 953C # EFCC 953E # EFCD 953F # EFCE 9542 # EFCF 9535 # EFD0 9544 # EFD1 9545 # EFD2 9546 # EFD3 9549 # EFD4 954C # EFD5 954E # EFD6 954F # EFD7 9552 # EFD8 9553 # EFD9 9554 # EFDA 9556 # EFDB 9557 # EFDC 9558 # EFDD 9559 # EFDE 955B # EFDF 955E # EFE0 955F # EFE1 955D # EFE2 9561 # EFE3 9562 # EFE4 9564 # EFE5 9565 # EFE6 9566 # EFE7 9567 # EFE8 9568 # EFE9 9569 # EFEA 956A # EFEB 956B # EFEC 956C # EFED 956F # EFEE 9571 # EFEF 9572 # EFF0 9573 # EFF1 953A # EFF2 77E7 # EFF3 77EC # EFF4 96C9 # EFF5 79D5 # EFF6 79ED # EFF7 79E3 # EFF8 79EB # EFF9 7A06 # EFFA 5D47 # EFFB 7A03 # EFFC 7A02 # EFFD 7A1E # EFFE 7A14 # F0A1 7A39 # F0A2 7A37 # F0A3 7A51 # F0A4 9ECF # F0A5 99A5 # F0A6 7A70 # F0A7 7688 # F0A8 768E # F0A9 7693 # F0AA 7699 # F0AB 76A4 # F0AC 74DE # F0AD 74E0 # F0AE 752C # F0AF 9E20 # F0B0 9E22 # F0B1 9E28 # F0B2 9E29 # F0B3 9E2A # F0B4 9E2B # F0B5 9E2C # F0B6 9E32 # F0B7 9E31 # F0B8 9E36 # F0B9 9E38 # F0BA 9E37 # F0BB 9E39 # F0BC 9E3A # F0BD 9E3E # F0BE 9E41 # F0BF 9E42 # F0C0 9E44 # F0C1 9E46 # F0C2 9E47 # F0C3 9E48 # F0C4 9E49 # F0C5 9E4B # F0C6 9E4C # F0C7 9E4E # F0C8 9E51 # F0C9 9E55 # F0CA 9E57 # F0CB 9E5A # F0CC 9E5B # F0CD 9E5C # F0CE 9E5E # F0CF 9E63 # F0D0 9E66 # F0D1 9E67 # F0D2 9E68 # F0D3 9E69 # F0D4 9E6A # F0D5 9E6B # F0D6 9E6C # F0D7 9E71 # F0D8 9E6D # F0D9 9E73 # F0DA 7592 # F0DB 7594 # F0DC 7596 # F0DD 75A0 # F0DE 759D # F0DF 75AC # F0E0 75A3 # F0E1 75B3 # F0E2 75B4 # F0E3 75B8 # F0E4 75C4 # F0E5 75B1 # F0E6 75B0 # F0E7 75C3 # F0E8 75C2 # F0E9 75D6 # F0EA 75CD # F0EB 75E3 # F0EC 75E8 # F0ED 75E6 # F0EE 75E4 # F0EF 75EB # F0F0 75E7 # F0F1 7603 # F0F2 75F1 # F0F3 75FC # F0F4 75FF # F0F5 7610 # F0F6 7600 # F0F7 7605 # F0F8 760C # F0F9 7617 # F0FA 760A # F0FB 7625 # F0FC 7618 # F0FD 7615 # F0FE 7619 # F1A1 761B # F1A2 763C # F1A3 7622 # F1A4 7620 # F1A5 7640 # F1A6 762D # F1A7 7630 # F1A8 763F # F1A9 7635 # F1AA 7643 # F1AB 763E # F1AC 7633 # F1AD 764D # F1AE 765E # F1AF 7654 # F1B0 765C # F1B1 7656 # F1B2 766B # F1B3 766F # F1B4 7FCA # F1B5 7AE6 # F1B6 7A78 # F1B7 7A79 # F1B8 7A80 # F1B9 7A86 # F1BA 7A88 # F1BB 7A95 # F1BC 7AA6 # F1BD 7AA0 # F1BE 7AAC # F1BF 7AA8 # F1C0 7AAD # F1C1 7AB3 # F1C2 8864 # F1C3 8869 # F1C4 8872 # F1C5 887D # F1C6 887F # F1C7 8882 # F1C8 88A2 # F1C9 88C6 # F1CA 88B7 # F1CB 88BC # F1CC 88C9 # F1CD 88E2 # F1CE 88CE # F1CF 88E3 # F1D0 88E5 # F1D1 88F1 # F1D2 891A # F1D3 88FC # F1D4 88E8 # F1D5 88FE # F1D6 88F0 # F1D7 8921 # F1D8 8919 # F1D9 8913 # F1DA 891B # F1DB 890A # F1DC 8934 # F1DD 892B # F1DE 8936 # F1DF 8941 # F1E0 8966 # F1E1 897B # F1E2 758B # F1E3 80E5 # F1E4 76B2 # F1E5 76B4 # F1E6 77DC # F1E7 8012 # F1E8 8014 # F1E9 8016 # F1EA 801C # F1EB 8020 # F1EC 8022 # F1ED 8025 # F1EE 8026 # F1EF 8027 # F1F0 8029 # F1F1 8028 # F1F2 8031 # F1F3 800B # F1F4 8035 # F1F5 8043 # F1F6 8046 # F1F7 804D # F1F8 8052 # F1F9 8069 # F1FA 8071 # F1FB 8983 # F1FC 9878 # F1FD 9880 # F1FE 9883 # F2A1 9889 # F2A2 988C # F2A3 988D # F2A4 988F # F2A5 9894 # F2A6 989A # F2A7 989B # F2A8 989E # F2A9 989F # F2AA 98A1 # F2AB 98A2 # F2AC 98A5 # F2AD 98A6 # F2AE 864D # F2AF 8654 # F2B0 866C # F2B1 866E # F2B2 867F # F2B3 867A # F2B4 867C # F2B5 867B # F2B6 86A8 # F2B7 868D # F2B8 868B # F2B9 86AC # F2BA 869D # F2BB 86A7 # F2BC 86A3 # F2BD 86AA # F2BE 8693 # F2BF 86A9 # F2C0 86B6 # F2C1 86C4 # F2C2 86B5 # F2C3 86CE # F2C4 86B0 # F2C5 86BA # F2C6 86B1 # F2C7 86AF # F2C8 86C9 # F2C9 86CF # F2CA 86B4 # F2CB 86E9 # F2CC 86F1 # F2CD 86F2 # F2CE 86ED # F2CF 86F3 # F2D0 86D0 # F2D1 8713 # F2D2 86DE # F2D3 86F4 # F2D4 86DF # F2D5 86D8 # F2D6 86D1 # F2D7 8703 # F2D8 8707 # F2D9 86F8 # F2DA 8708 # F2DB 870A # F2DC 870D # F2DD 8709 # F2DE 8723 # F2DF 873B # F2E0 871E # F2E1 8725 # F2E2 872E # F2E3 871A # F2E4 873E # F2E5 8748 # F2E6 8734 # F2E7 8731 # F2E8 8729 # F2E9 8737 # F2EA 873F # F2EB 8782 # F2EC 8722 # F2ED 877D # F2EE 877E # F2EF 877B # F2F0 8760 # F2F1 8770 # F2F2 874C # F2F3 876E # F2F4 878B # F2F5 8753 # F2F6 8763 # F2F7 877C # F2F8 8764 # F2F9 8759 # F2FA 8765 # F2FB 8793 # F2FC 87AF # F2FD 87A8 # F2FE 87D2 # F3A1 87C6 # F3A2 8788 # F3A3 8785 # F3A4 87AD # F3A5 8797 # F3A6 8783 # F3A7 87AB # F3A8 87E5 # F3A9 87AC # F3AA 87B5 # F3AB 87B3 # F3AC 87CB # F3AD 87D3 # F3AE 87BD # F3AF 87D1 # F3B0 87C0 # F3B1 87CA # F3B2 87DB # F3B3 87EA # F3B4 87E0 # F3B5 87EE # F3B6 8816 # F3B7 8813 # F3B8 87FE # F3B9 880A # F3BA 881B # F3BB 8821 # F3BC 8839 # F3BD 883C # F3BE 7F36 # F3BF 7F42 # F3C0 7F44 # F3C1 7F45 # F3C2 8210 # F3C3 7AFA # F3C4 7AFD # F3C5 7B08 # F3C6 7B03 # F3C7 7B04 # F3C8 7B15 # F3C9 7B0A # F3CA 7B2B # F3CB 7B0F # F3CC 7B47 # F3CD 7B38 # F3CE 7B2A # F3CF 7B19 # F3D0 7B2E # F3D1 7B31 # F3D2 7B20 # F3D3 7B25 # F3D4 7B24 # F3D5 7B33 # F3D6 7B3E # F3D7 7B1E # F3D8 7B58 # F3D9 7B5A # F3DA 7B45 # F3DB 7B75 # F3DC 7B4C # F3DD 7B5D # F3DE 7B60 # F3DF 7B6E # F3E0 7B7B # F3E1 7B62 # F3E2 7B72 # F3E3 7B71 # F3E4 7B90 # F3E5 7BA6 # F3E6 7BA7 # F3E7 7BB8 # F3E8 7BAC # F3E9 7B9D # F3EA 7BA8 # F3EB 7B85 # F3EC 7BAA # F3ED 7B9C # F3EE 7BA2 # F3EF 7BAB # F3F0 7BB4 # F3F1 7BD1 # F3F2 7BC1 # F3F3 7BCC # F3F4 7BDD # F3F5 7BDA # F3F6 7BE5 # F3F7 7BE6 # F3F8 7BEA # F3F9 7C0C # F3FA 7BFE # F3FB 7BFC # F3FC 7C0F # F3FD 7C16 # F3FE 7C0B # F4A1 7C1F # F4A2 7C2A # F4A3 7C26 # F4A4 7C38 # F4A5 7C41 # F4A6 7C40 # F4A7 81FE # F4A8 8201 # F4A9 8202 # F4AA 8204 # F4AB 81EC # F4AC 8844 # F4AD 8221 # F4AE 8222 # F4AF 8223 # F4B0 822D # F4B1 822F # F4B2 8228 # F4B3 822B # F4B4 8238 # F4B5 823B # F4B6 8233 # F4B7 8234 # F4B8 823E # F4B9 8244 # F4BA 8249 # F4BB 824B # F4BC 824F # F4BD 825A # F4BE 825F # F4BF 8268 # F4C0 887E # F4C1 8885 # F4C2 8888 # F4C3 88D8 # F4C4 88DF # F4C5 895E # F4C6 7F9D # F4C7 7F9F # F4C8 7FA7 # F4C9 7FAF # F4CA 7FB0 # F4CB 7FB2 # F4CC 7C7C # F4CD 6549 # F4CE 7C91 # F4CF 7C9D # F4D0 7C9C # F4D1 7C9E # F4D2 7CA2 # F4D3 7CB2 # F4D4 7CBC # F4D5 7CBD # F4D6 7CC1 # F4D7 7CC7 # F4D8 7CCC # F4D9 7CCD # F4DA 7CC8 # F4DB 7CC5 # F4DC 7CD7 # F4DD 7CE8 # F4DE 826E # F4DF 66A8 # F4E0 7FBF # F4E1 7FCE # F4E2 7FD5 # F4E3 7FE5 # F4E4 7FE1 # F4E5 7FE6 # F4E6 7FE9 # F4E7 7FEE # F4E8 7FF3 # F4E9 7CF8 # F4EA 7D77 # F4EB 7DA6 # F4EC 7DAE # F4ED 7E47 # F4EE 7E9B # F4EF 9EB8 # F4F0 9EB4 # F4F1 8D73 # F4F2 8D84 # F4F3 8D94 # F4F4 8D91 # F4F5 8DB1 # F4F6 8D67 # F4F7 8D6D # F4F8 8C47 # F4F9 8C49 # F4FA 914A # F4FB 9150 # F4FC 914E # F4FD 914F # F4FE 9164 # F5A1 9162 # F5A2 9161 # F5A3 9170 # F5A4 9169 # F5A5 916F # F5A6 917D # F5A7 917E # F5A8 9172 # F5A9 9174 # F5AA 9179 # F5AB 918C # F5AC 9185 # F5AD 9190 # F5AE 918D # F5AF 9191 # F5B0 91A2 # F5B1 91A3 # F5B2 91AA # F5B3 91AD # F5B4 91AE # F5B5 91AF # F5B6 91B5 # F5B7 91B4 # F5B8 91BA # F5B9 8C55 # F5BA 9E7E # F5BB 8DB8 # F5BC 8DEB # F5BD 8E05 # F5BE 8E59 # F5BF 8E69 # F5C0 8DB5 # F5C1 8DBF # F5C2 8DBC # F5C3 8DBA # F5C4 8DC4 # F5C5 8DD6 # F5C6 8DD7 # F5C7 8DDA # F5C8 8DDE # F5C9 8DCE # F5CA 8DCF # F5CB 8DDB # F5CC 8DC6 # F5CD 8DEC # F5CE 8DF7 # F5CF 8DF8 # F5D0 8DE3 # F5D1 8DF9 # F5D2 8DFB # F5D3 8DE4 # F5D4 8E09 # F5D5 8DFD # F5D6 8E14 # F5D7 8E1D # F5D8 8E1F # F5D9 8E2C # F5DA 8E2E # F5DB 8E23 # F5DC 8E2F # F5DD 8E3A # F5DE 8E40 # F5DF 8E39 # F5E0 8E35 # F5E1 8E3D # F5E2 8E31 # F5E3 8E49 # F5E4 8E41 # F5E5 8E42 # F5E6 8E51 # F5E7 8E52 # F5E8 8E4A # F5E9 8E70 # F5EA 8E76 # F5EB 8E7C # F5EC 8E6F # F5ED 8E74 # F5EE 8E85 # F5EF 8E8F # F5F0 8E94 # F5F1 8E90 # F5F2 8E9C # F5F3 8E9E # F5F4 8C78 # F5F5 8C82 # F5F6 8C8A # F5F7 8C85 # F5F8 8C98 # F5F9 8C94 # F5FA 659B # F5FB 89D6 # F5FC 89DE # F5FD 89DA # F5FE 89DC # F6A1 89E5 # F6A2 89EB # F6A3 89EF # F6A4 8A3E # F6A5 8B26 # F6A6 9753 # F6A7 96E9 # F6A8 96F3 # F6A9 96EF # F6AA 9706 # F6AB 9701 # F6AC 9708 # F6AD 970F # F6AE 970E # F6AF 972A # F6B0 972D # F6B1 9730 # F6B2 973E # F6B3 9F80 # F6B4 9F83 # F6B5 9F85 # F6B6 9F86 # F6B7 9F87 # F6B8 9F88 # F6B9 9F89 # F6BA 9F8A # F6BB 9F8C # F6BC 9EFE # F6BD 9F0B # F6BE 9F0D # F6BF 96B9 # F6C0 96BC # F6C1 96BD # F6C2 96CE # F6C3 96D2 # F6C4 77BF # F6C5 96E0 # F6C6 928E # F6C7 92AE # F6C8 92C8 # F6C9 933E # F6CA 936A # F6CB 93CA # F6CC 938F # F6CD 943E # F6CE 946B # F6CF 9C7F # F6D0 9C82 # F6D1 9C85 # F6D2 9C86 # F6D3 9C87 # F6D4 9C88 # F6D5 7A23 # F6D6 9C8B # F6D7 9C8E # F6D8 9C90 # F6D9 9C91 # F6DA 9C92 # F6DB 9C94 # F6DC 9C95 # F6DD 9C9A # F6DE 9C9B # F6DF 9C9E # F6E0 9C9F # F6E1 9CA0 # F6E2 9CA1 # F6E3 9CA2 # F6E4 9CA3 # F6E5 9CA5 # F6E6 9CA6 # F6E7 9CA7 # F6E8 9CA8 # F6E9 9CA9 # F6EA 9CAB # F6EB 9CAD # F6EC 9CAE # F6ED 9CB0 # F6EE 9CB1 # F6EF 9CB2 # F6F0 9CB3 # F6F1 9CB4 # F6F2 9CB5 # F6F3 9CB6 # F6F4 9CB7 # F6F5 9CBA # F6F6 9CBB # F6F7 9CBC # F6F8 9CBD # F6F9 9CC4 # F6FA 9CC5 # F6FB 9CC6 # F6FC 9CC7 # F6FD 9CCA # F6FE 9CCB # F7A1 9CCC # F7A2 9CCD # F7A3 9CCE # F7A4 9CCF # F7A5 9CD0 # F7A6 9CD3 # F7A7 9CD4 # F7A8 9CD5 # F7A9 9CD7 # F7AA 9CD8 # F7AB 9CD9 # F7AC 9CDC # F7AD 9CDD # F7AE 9CDF # F7AF 9CE2 # F7B0 977C # F7B1 9785 # F7B2 9791 # F7B3 9792 # F7B4 9794 # F7B5 97AF # F7B6 97AB # F7B7 97A3 # F7B8 97B2 # F7B9 97B4 # F7BA 9AB1 # F7BB 9AB0 # F7BC 9AB7 # F7BD 9E58 # F7BE 9AB6 # F7BF 9ABA # F7C0 9ABC # F7C1 9AC1 # F7C2 9AC0 # F7C3 9AC5 # F7C4 9AC2 # F7C5 9ACB # F7C6 9ACC # F7C7 9AD1 # F7C8 9B45 # F7C9 9B43 # F7CA 9B47 # F7CB 9B49 # F7CC 9B48 # F7CD 9B4D # F7CE 9B51 # F7CF 98E8 # F7D0 990D # F7D1 992E # F7D2 9955 # F7D3 9954 # F7D4 9ADF # F7D5 9AE1 # F7D6 9AE6 # F7D7 9AEF # F7D8 9AEB # F7D9 9AFB # F7DA 9AED # F7DB 9AF9 # F7DC 9B08 # F7DD 9B0F # F7DE 9B13 # F7DF 9B1F # F7E0 9B23 # F7E1 9EBD # F7E2 9EBE # F7E3 7E3B # F7E4 9E82 # F7E5 9E87 # F7E6 9E88 # F7E7 9E8B # F7E8 9E92 # F7E9 93D6 # F7EA 9E9D # F7EB 9E9F # F7EC 9EDB # F7ED 9EDC # F7EE 9EDD # F7EF 9EE0 # F7F0 9EDF # F7F1 9EE2 # F7F2 9EE9 # F7F3 9EE7 # F7F4 9EE5 # F7F5 9EEA # F7F6 9EEF # F7F7 9F22 # F7F8 9F2C # F7F9 9F2F # F7FA 9F39 # F7FB 9F37 # F7FC 9F3D # F7FD 9F3E # F7FE 9F44 # cyrus-imapd-2.5.10/lib/charset/iso-8859-1.t0000644000175000017500000002303213001236020014667 00000000000000# # Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. # # Redistribution and use in source and binary forms, with or without # modification, are permitted provided that the following conditions # are met: # # 1. Redistributions of source code must retain the above copyright # notice, this list of conditions and the following disclaimer. # # 2. Redistributions in binary form must reproduce the above copyright # notice, this list of conditions and the following disclaimer in # the documentation and/or other materials provided with the # distribution. # # 3. The name "Carnegie Mellon University" must not be used to # endorse or promote products derived from this software without # prior written permission. For permission or any legal # details, please contact # Carnegie Mellon University # Center for Technology Transfer and Enterprise Creation # 4615 Forbes Avenue # Suite 302 # Pittsburgh, PA 15213 # (412) 268-7393, fax: (412) 268-7395 # innovation@andrew.cmu.edu # # 4. Redistributions of any form whatsoever must retain the following # acknowledgment: # "This product includes software developed by Computing Services # at Carnegie Mellon University (http://www.cmu.edu/computing/)." # # CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO # THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY # AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE # FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES # WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN # AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING # OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. 0 0000 NULL (NUL) 1 0001 START OF HEADING (SOH) 2 0002 START OF TEXT (STX) 3 0003 END OF TEXT (ETX) 4 0004 END OF TRANSMISSION (EOT) 5 0005 ENQUIRY (ENQ) 6 0006 ACKNOWLEDGE (ACK) 7 0007 BELL (BEL) 8 0008 BACKSPACE (BS) 9 0009 CHARACTER TABULATION (HT) A 000a LINE FEED (LF) B 000b LINE TABULATION (VT) C 000c FORM FEED (FF) D 000d CARRIAGE RETURN (CR) E 000e SHIFT OUT (SO) F 000f SHIFT IN (SI) 10 0010 DATALINK ESCAPE (DLE) 11 0011 DEVICE CONTROL ONE (DC1) 12 0012 DEVICE CONTROL TWO (DC2) 13 0013 DEVICE CONTROL THREE (DC3) 14 0014 DEVICE CONTROL FOUR (DC4) 15 0015 NEGATIVE ACKNOWLEDGE (NAK) 16 0016 SYNCRONOUS IDLE (SYN) 17 0017 END OF TRANSMISSION BLOCK (ETB) 18 0018 CANCEL (CAN) 19 0019 END OF MEDIUM (EM) 1A 001a SUBSTITUTE (SUB) 1B 001b ESCAPE (ESC) 1C 001c FILE SEPARATOR (IS4) 1D 001d GROUP SEPARATOR (IS3) 1E 001e RECORD SEPARATOR (IS2) 1F 001f UNIT SEPARATOR (IS1) 20 0020 SPACE 21 0021 EXCLAMATION MARK 22 0022 QUOTATION MARK 23 0023 NUMBER SIGN 24 0024 DOLLAR SIGN 25 0025 PERCENT SIGN 26 0026 AMPERSAND 27 0027 APOSTROPHE 28 0028 LEFT PARENTHESIS 29 0029 RIGHT PARENTHESIS 2A 002a ASTERISK 2B 002b PLUS SIGN 2C 002c COMMA 2D 002d HYPHEN-MINUS 2E 002e FULL STOP 2F 002f SOLIDUS 30 0030 DIGIT ZERO 31 0031 DIGIT ONE 32 0032 DIGIT TWO 33 0033 DIGIT THREE 34 0034 DIGIT FOUR 35 0035 DIGIT FIVE 36 0036 DIGIT SIX 37 0037 DIGIT SEVEN 38 0038 DIGIT EIGHT 39 0039 DIGIT NINE 3A 003a COLON 3B 003b SEMICOLON 3C 003c LESS-THAN SIGN 3D 003d EQUALS SIGN 3E 003e GREATER-THAN SIGN 3F 003f QUESTION MARK 40 0040 COMMERCIAL AT 41 0041 LATIN CAPITAL LETTER A 42 0042 LATIN CAPITAL LETTER B 43 0043 LATIN CAPITAL LETTER C 44 0044 LATIN CAPITAL LETTER D 45 0045 LATIN CAPITAL LETTER E 46 0046 LATIN CAPITAL LETTER F 47 0047 LATIN CAPITAL LETTER G 48 0048 LATIN CAPITAL LETTER H 49 0049 LATIN CAPITAL LETTER I 4A 004a LATIN CAPITAL LETTER J 4B 004b LATIN CAPITAL LETTER K 4C 004c LATIN CAPITAL LETTER L 4D 004d LATIN CAPITAL LETTER M 4E 004e LATIN CAPITAL LETTER N 4F 004f LATIN CAPITAL LETTER O 50 0050 LATIN CAPITAL LETTER P 51 0051 LATIN CAPITAL LETTER Q 52 0052 LATIN CAPITAL LETTER R 53 0053 LATIN CAPITAL LETTER S 54 0054 LATIN CAPITAL LETTER T 55 0055 LATIN CAPITAL LETTER U 56 0056 LATIN CAPITAL LETTER V 57 0057 LATIN CAPITAL LETTER W 58 0058 LATIN CAPITAL LETTER X 59 0059 LATIN CAPITAL LETTER Y 5A 005a LATIN CAPITAL LETTER Z 5B 005b LEFT SQUARE BRACKET 5C 005c REVERSE SOLIDUS 5D 005d RIGHT SQUARE BRACKET 5E 005e CIRCUMFLEX ACCENT 5F 005f LOW LINE 60 0060 GRAVE ACCENT 61 0061 LATIN SMALL LETTER A 62 0062 LATIN SMALL LETTER B 63 0063 LATIN SMALL LETTER C 64 0064 LATIN SMALL LETTER D 65 0065 LATIN SMALL LETTER E 66 0066 LATIN SMALL LETTER F 67 0067 LATIN SMALL LETTER G 68 0068 LATIN SMALL LETTER H 69 0069 LATIN SMALL LETTER I 6A 006a LATIN SMALL LETTER J 6B 006b LATIN SMALL LETTER K 6C 006c LATIN SMALL LETTER L 6D 006d LATIN SMALL LETTER M 6E 006e LATIN SMALL LETTER N 6F 006f LATIN SMALL LETTER O 70 0070 LATIN SMALL LETTER P 71 0071 LATIN SMALL LETTER Q 72 0072 LATIN SMALL LETTER R 73 0073 LATIN SMALL LETTER S 74 0074 LATIN SMALL LETTER T 75 0075 LATIN SMALL LETTER U 76 0076 LATIN SMALL LETTER V 77 0077 LATIN SMALL LETTER W 78 0078 LATIN SMALL LETTER X 79 0079 LATIN SMALL LETTER Y 7A 007a LATIN SMALL LETTER Z 7B 007b LEFT CURLY BRACKET 7C 007c VERTICAL LINE 7D 007d RIGHT CURLY BRACKET 7E 007e TILDE 7F 007f DELETE (DEL) 80 0080 PADDING CHARACTER (PAD) 81 0081 HIGH OCTET PRESET (HOP) 82 0082 BREAK PERMITTED HERE (BPH) 83 0083 NO BREAK HERE (NBH) 84 0084 INDEX (IND) 85 0085 NEXT LINE (NEL) 86 0086 START OF SELECTED AREA (SSA) 87 0087 END OF SELECTED AREA (ESA) 88 0088 CHARACTER TABULATION SET (HTS) 89 0089 CHARACTER TABULATION WITH JUSTIFICATION (HTJ) 8A 008a LINE TABULATION SET (VTS) 8B 008b PARTIAL LINE FORWARD (PLD) 8C 008c PARTIAL LINE BACKWARD (PLU) 8D 008d REVERSE LINE FEED (RI) 8E 008e SINGLE-SHIFT TWO (SS2) 8F 008f SINGLE-SHIFT THREE (SS3) 90 0090 DEVICE CONTROL STRING (DCS) 91 0091 PRIVATE USE ONE (PU1) 92 0092 PRIVATE USE TWO (PU2) 93 0093 SET TRANSMIT STATE (STS) 94 0094 CANCEL CHARACTER (CCH) 95 0095 MESSAGE WAITING (MW) 96 0096 START OF GUARDED AREA (SPA) 97 0097 END OF GUARDED AREA (EPA) 98 0098 START OF STRING (SOS) 99 0099 SINGLE GRAPHIC CHARACTER INTRODUCER (SGCI) 9A 009a SINGLE CHARACTER INTRODUCER (SCI) 9B 009b CONTROL SEQUENCE INTRODUCER (CSI) 9C 009c STRING TERMINATOR (ST) 9D 009d OPERATING SYSTEM COMMAND (OSC) 9E 009e PRIVACY MESSAGE (PM) 9F 009f APPLICATION PROGRAM COMMAND (APC) A0 00a0 NO-BREAK SPACE A1 00a1 INVERTED EXCLAMATION MARK A2 00a2 CENT SIGN A3 00a3 POUND SIGN A4 00a4 CURRENCY SIGN A5 00a5 YEN SIGN A6 00a6 BROKEN BAR A7 00a7 SECTION SIGN A8 00a8 DIAERESIS A9 00a9 COPYRIGHT SIGN AA 00aa FEMININE ORDINAL INDICATOR AB 00ab LEFT-POINTING DOUBLE ANGLE QUOTATION MARK AC 00ac NOT SIGN AD 00ad SOFT HYPHEN AE 00ae REGISTERED SIGN AF 00af MACRON B0 00b0 DEGREE SIGN B1 00b1 PLUS-MINUS SIGN B2 00b2 SUPERSCRIPT TWO B3 00b3 SUPERSCRIPT THREE B4 00b4 ACUTE ACCENT B5 00b5 MICRO SIGN B6 00b6 PILCROW SIGN B7 00b7 MIDDLE DOT B8 00b8 CEDILLA B9 00b9 SUPERSCRIPT ONE BA 00ba MASCULINE ORDINAL INDICATOR BB 00bb RIGHT-POINTING DOUBLE ANGLE QUOTATION MARK BC 00bc VULGAR FRACTION ONE QUARTER BD 00bd VULGAR FRACTION ONE HALF BE 00be VULGAR FRACTION THREE QUARTERS BF 00bf INVERTED QUESTION MARK C0 00c0 LATIN CAPITAL LETTER A WITH GRAVE C1 00c1 LATIN CAPITAL LETTER A WITH ACUTE C2 00c2 LATIN CAPITAL LETTER A WITH CIRCUMFLEX C3 00c3 LATIN CAPITAL LETTER A WITH TILDE C4 00c4 LATIN CAPITAL LETTER A WITH DIAERESIS C5 00c5 LATIN CAPITAL LETTER A WITH RING ABOVE C6 00c6 LATIN CAPITAL LETTER AE C7 00c7 LATIN CAPITAL LETTER C WITH CEDILLA C8 00c8 LATIN CAPITAL LETTER E WITH GRAVE C9 00c9 LATIN CAPITAL LETTER E WITH ACUTE CA 00ca LATIN CAPITAL LETTER E WITH CIRCUMFLEX CB 00cb LATIN CAPITAL LETTER E WITH DIAERESIS CC 00cc LATIN CAPITAL LETTER I WITH GRAVE CD 00cd LATIN CAPITAL LETTER I WITH ACUTE CE 00ce LATIN CAPITAL LETTER I WITH CIRCUMFLEX CF 00cf LATIN CAPITAL LETTER I WITH DIAERESIS D0 00d0 LATIN CAPITAL LETTER ETH (Icelandic) D1 00d1 LATIN CAPITAL LETTER N WITH TILDE D2 00d2 LATIN CAPITAL LETTER O WITH GRAVE D3 00d3 LATIN CAPITAL LETTER O WITH ACUTE D4 00d4 LATIN CAPITAL LETTER O WITH CIRCUMFLEX D5 00d5 LATIN CAPITAL LETTER O WITH TILDE D6 00d6 LATIN CAPITAL LETTER O WITH DIAERESIS D7 00d7 MULTIPLICATION SIGN D8 00d8 LATIN CAPITAL LETTER O WITH STROKE D9 00d9 LATIN CAPITAL LETTER U WITH GRAVE DA 00da LATIN CAPITAL LETTER U WITH ACUTE DB 00db LATIN CAPITAL LETTER U WITH CIRCUMFLEX DC 00dc LATIN CAPITAL LETTER U WITH DIAERESIS DD 00dd LATIN CAPITAL LETTER Y WITH ACUTE DE 00de LATIN CAPITAL LETTER THORN (Icelandic) DF 00df LATIN SMALL LETTER SHARP S (German) E0 00e0 LATIN SMALL LETTER A WITH GRAVE E1 00e1 LATIN SMALL LETTER A WITH ACUTE E2 00e2 LATIN SMALL LETTER A WITH CIRCUMFLEX E3 00e3 LATIN SMALL LETTER A WITH TILDE E4 00e4 LATIN SMALL LETTER A WITH DIAERESIS E5 00e5 LATIN SMALL LETTER A WITH RING ABOVE E6 00e6 LATIN SMALL LETTER AE E7 00e7 LATIN SMALL LETTER C WITH CEDILLA E8 00e8 LATIN SMALL LETTER E WITH GRAVE E9 00e9 LATIN SMALL LETTER E WITH ACUTE EA 00ea LATIN SMALL LETTER E WITH CIRCUMFLEX EB 00eb LATIN SMALL LETTER E WITH DIAERESIS EC 00ec LATIN SMALL LETTER I WITH GRAVE ED 00ed LATIN SMALL LETTER I WITH ACUTE EE 00ee LATIN SMALL LETTER I WITH CIRCUMFLEX EF 00ef LATIN SMALL LETTER I WITH DIAERESIS F0 00f0 LATIN SMALL LETTER ETH (Icelandic) F1 00f1 LATIN SMALL LETTER N WITH TILDE F2 00f2 LATIN SMALL LETTER O WITH GRAVE F3 00f3 LATIN SMALL LETTER O WITH ACUTE F4 00f4 LATIN SMALL LETTER O WITH CIRCUMFLEX F5 00f5 LATIN SMALL LETTER O WITH TILDE F6 00f6 LATIN SMALL LETTER O WITH DIAERESIS F7 00f7 DIVISION SIGN F8 00f8 LATIN SMALL LETTER O WITH STROKE F9 00f9 LATIN SMALL LETTER U WITH GRAVE FA 00fa LATIN SMALL LETTER U WITH ACUTE FB 00fb LATIN SMALL LETTER U WITH CIRCUMFLEX FC 00fc LATIN SMALL LETTER U WITH DIAERESIS FD 00fd LATIN SMALL LETTER Y WITH ACUTE FE 00fe LATIN SMALL LETTER THORN (Icelandic) FF 00ff LATIN SMALL LETTER Y WITH DIAERESIS cyrus-imapd-2.5.10/lib/charset/iso-8859-10.t0000644000175000017500000002236113001236020014753 00000000000000# # Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. # # Redistribution and use in source and binary forms, with or without # modification, are permitted provided that the following conditions # are met: # # 1. Redistributions of source code must retain the above copyright # notice, this list of conditions and the following disclaimer. # # 2. Redistributions in binary form must reproduce the above copyright # notice, this list of conditions and the following disclaimer in # the documentation and/or other materials provided with the # distribution. # # 3. The name "Carnegie Mellon University" must not be used to # endorse or promote products derived from this software without # prior written permission. For permission or any legal # details, please contact # Carnegie Mellon University # Center for Technology Transfer and Enterprise Creation # 4615 Forbes Avenue # Suite 302 # Pittsburgh, PA 15213 # (412) 268-7393, fax: (412) 268-7395 # innovation@andrew.cmu.edu # # 4. Redistributions of any form whatsoever must retain the following # acknowledgment: # "This product includes software developed by Computing Services # at Carnegie Mellon University (http://www.cmu.edu/computing/)." # # CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO # THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY # AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE # FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES # WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN # AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING # OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. 00 0000 NULL 01 0001 START OF HEADING 02 0002 START OF TEXT 03 0003 END OF TEXT 04 0004 END OF TRANSMISSION 05 0005 ENQUIRY 06 0006 ACKNOWLEDGE 07 0007 BELL 08 0008 BACKSPACE 09 0009 HORIZONTAL TABULATION 0A 000A LINE FEED 0B 000B VERTICAL TABULATION 0C 000C FORM FEED 0D 000D CARRIAGE RETURN 0E 000E SHIFT OUT 0F 000F SHIFT IN 10 0010 DATA LINK ESCAPE 11 0011 DEVICE CONTROL ONE 12 0012 DEVICE CONTROL TWO 13 0013 DEVICE CONTROL THREE 14 0014 DEVICE CONTROL FOUR 15 0015 NEGATIVE ACKNOWLEDGE 16 0016 SYNCHRONOUS IDLE 17 0017 END OF TRANSMISSION BLOCK 18 0018 CANCEL 19 0019 END OF MEDIUM 1A 001A SUBSTITUTE 1B 001B ESCAPE 1C 001C FILE SEPARATOR 1D 001D GROUP SEPARATOR 1E 001E RECORD SEPARATOR 1F 001F UNIT SEPARATOR 20 0020 SPACE 21 0021 EXCLAMATION MARK 22 0022 QUOTATION MARK 23 0023 NUMBER SIGN 24 0024 DOLLAR SIGN 25 0025 PERCENT SIGN 26 0026 AMPERSAND 27 0027 APOSTROPHE 28 0028 LEFT PARENTHESIS 29 0029 RIGHT PARENTHESIS 2A 002A ASTERISK 2B 002B PLUS SIGN 2C 002C COMMA 2D 002D HYPHEN-MINUS 2E 002E FULL STOP 2F 002F SOLIDUS 30 0030 DIGIT ZERO 31 0031 DIGIT ONE 32 0032 DIGIT TWO 33 0033 DIGIT THREE 34 0034 DIGIT FOUR 35 0035 DIGIT FIVE 36 0036 DIGIT SIX 37 0037 DIGIT SEVEN 38 0038 DIGIT EIGHT 39 0039 DIGIT NINE 3A 003A COLON 3B 003B SEMICOLON 3C 003C LESS-THAN SIGN 3D 003D EQUALS SIGN 3E 003E GREATER-THAN SIGN 3F 003F QUESTION MARK 40 0040 COMMERCIAL AT 41 0041 LATIN CAPITAL LETTER A 42 0042 LATIN CAPITAL LETTER B 43 0043 LATIN CAPITAL LETTER C 44 0044 LATIN CAPITAL LETTER D 45 0045 LATIN CAPITAL LETTER E 46 0046 LATIN CAPITAL LETTER F 47 0047 LATIN CAPITAL LETTER G 48 0048 LATIN CAPITAL LETTER H 49 0049 LATIN CAPITAL LETTER I 4A 004A LATIN CAPITAL LETTER J 4B 004B LATIN CAPITAL LETTER K 4C 004C LATIN CAPITAL LETTER L 4D 004D LATIN CAPITAL LETTER M 4E 004E LATIN CAPITAL LETTER N 4F 004F LATIN CAPITAL LETTER O 50 0050 LATIN CAPITAL LETTER P 51 0051 LATIN CAPITAL LETTER Q 52 0052 LATIN CAPITAL LETTER R 53 0053 LATIN CAPITAL LETTER S 54 0054 LATIN CAPITAL LETTER T 55 0055 LATIN CAPITAL LETTER U 56 0056 LATIN CAPITAL LETTER V 57 0057 LATIN CAPITAL LETTER W 58 0058 LATIN CAPITAL LETTER X 59 0059 LATIN CAPITAL LETTER Y 5A 005A LATIN CAPITAL LETTER Z 5B 005B LEFT SQUARE BRACKET 5C 005C REVERSE SOLIDUS 5D 005D RIGHT SQUARE BRACKET 5E 005E CIRCUMFLEX ACCENT 5F 005F LOW LINE 60 0060 GRAVE ACCENT 61 0061 LATIN SMALL LETTER A 62 0062 LATIN SMALL LETTER B 63 0063 LATIN SMALL LETTER C 64 0064 LATIN SMALL LETTER D 65 0065 LATIN SMALL LETTER E 66 0066 LATIN SMALL LETTER F 67 0067 LATIN SMALL LETTER G 68 0068 LATIN SMALL LETTER H 69 0069 LATIN SMALL LETTER I 6A 006A LATIN SMALL LETTER J 6B 006B LATIN SMALL LETTER K 6C 006C LATIN SMALL LETTER L 6D 006D LATIN SMALL LETTER M 6E 006E LATIN SMALL LETTER N 6F 006F LATIN SMALL LETTER O 70 0070 LATIN SMALL LETTER P 71 0071 LATIN SMALL LETTER Q 72 0072 LATIN SMALL LETTER R 73 0073 LATIN SMALL LETTER S 74 0074 LATIN SMALL LETTER T 75 0075 LATIN SMALL LETTER U 76 0076 LATIN SMALL LETTER V 77 0077 LATIN SMALL LETTER W 78 0078 LATIN SMALL LETTER X 79 0079 LATIN SMALL LETTER Y 7A 007A LATIN SMALL LETTER Z 7B 007B LEFT CURLY BRACKET 7C 007C VERTICAL LINE 7D 007D RIGHT CURLY BRACKET 7E 007E TILDE 7F 007F DELETE 80 0080 81 0081 82 0082 83 0083 84 0084 85 0085 86 0086 87 0087 88 0088 89 0089 8A 008A 8B 008B 8C 008C 8D 008D 8E 008E 8F 008F 90 0090 91 0091 92 0092 93 0093 94 0094 95 0095 96 0096 97 0097 98 0098 99 0099 9A 009A 9B 009B 9C 009C 9D 009D 9E 009E 9F 009F A0 00A0 NO-BREAK SPACE A1 0104 LATIN CAPITAL LETTER A WITH OGONEK A2 0112 LATIN CAPITAL LETTER E WITH MACRON A3 0122 LATIN CAPITAL LETTER G WITH CEDILLA A4 012A LATIN CAPITAL LETTER I WITH MACRON A5 0128 LATIN CAPITAL LETTER I WITH TILDE A6 0136 LATIN CAPITAL LETTER K WITH CEDILLA A7 00A7 SECTION SIGN A8 013B LATIN CAPITAL LETTER L WITH CEDILLA A9 0110 LATIN CAPITAL LETTER D WITH STROKE AA 0160 LATIN CAPITAL LETTER S WITH CARON AB 0166 LATIN CAPITAL LETTER T WITH STROKE AC 017D LATIN CAPITAL LETTER Z WITH CARON AD 00AD SOFT HYPHEN AE 016A LATIN CAPITAL LETTER U WITH MACRON AF 014A LATIN CAPITAL LETTER ENG B0 00B0 DEGREE SIGN B1 0105 LATIN SMALL LETTER A WITH OGONEK B2 0113 LATIN SMALL LETTER E WITH MACRON B3 0123 LATIN SMALL LETTER G WITH CEDILLA B4 012B LATIN SMALL LETTER I WITH MACRON B5 0129 LATIN SMALL LETTER I WITH TILDE B6 0137 LATIN SMALL LETTER K WITH CEDILLA B7 00B7 MIDDLE DOT B8 013C LATIN SMALL LETTER L WITH CEDILLA B9 0111 LATIN SMALL LETTER D WITH STROKE BA 0161 LATIN SMALL LETTER S WITH CARON BB 0167 LATIN SMALL LETTER T WITH STROKE BC 017E LATIN SMALL LETTER Z WITH CARON BD 2015 HORIZONTAL BAR BE 016B LATIN SMALL LETTER U WITH MACRON BF 014B LATIN SMALL LETTER ENG C0 0100 LATIN CAPITAL LETTER A WITH MACRON C1 00C1 LATIN CAPITAL LETTER A WITH ACUTE C2 00C2 LATIN CAPITAL LETTER A WITH CIRCUMFLEX C3 00C3 LATIN CAPITAL LETTER A WITH TILDE C4 00C4 LATIN CAPITAL LETTER A WITH DIAERESIS C5 00C5 LATIN CAPITAL LETTER A WITH RING ABOVE C6 00C6 LATIN CAPITAL LETTER AE C7 012E LATIN CAPITAL LETTER I WITH OGONEK C8 010C LATIN CAPITAL LETTER C WITH CARON C9 00C9 LATIN CAPITAL LETTER E WITH ACUTE CA 0118 LATIN CAPITAL LETTER E WITH OGONEK CB 00CB LATIN CAPITAL LETTER E WITH DIAERESIS CC 0116 LATIN CAPITAL LETTER E WITH DOT ABOVE CD 00CD LATIN CAPITAL LETTER I WITH ACUTE CE 00CE LATIN CAPITAL LETTER I WITH CIRCUMFLEX CF 00CF LATIN CAPITAL LETTER I WITH DIAERESIS D0 00D0 LATIN CAPITAL LETTER ETH (Icelandic) D1 0145 LATIN CAPITAL LETTER N WITH CEDILLA D2 014C LATIN CAPITAL LETTER O WITH MACRON D3 00D3 LATIN CAPITAL LETTER O WITH ACUTE D4 00D4 LATIN CAPITAL LETTER O WITH CIRCUMFLEX D5 00D5 LATIN CAPITAL LETTER O WITH TILDE D6 00D6 LATIN CAPITAL LETTER O WITH DIAERESIS D7 0168 LATIN CAPITAL LETTER U WITH TILDE D8 00D8 LATIN CAPITAL LETTER O WITH STROKE D9 0172 LATIN CAPITAL LETTER U WITH OGONEK DA 00DA LATIN CAPITAL LETTER U WITH ACUTE DB 00DB LATIN CAPITAL LETTER U WITH CIRCUMFLEX DC 00DC LATIN CAPITAL LETTER U WITH DIAERESIS DD 00DD LATIN CAPITAL LETTER Y WITH ACUTE DE 00DE LATIN CAPITAL LETTER THORN (Icelandic) DF 00DF LATIN SMALL LETTER SHARP S (German) E0 0101 LATIN SMALL LETTER A WITH MACRON E1 00E1 LATIN SMALL LETTER A WITH ACUTE E2 00E2 LATIN SMALL LETTER A WITH CIRCUMFLEX E3 00E3 LATIN SMALL LETTER A WITH TILDE E4 00E4 LATIN SMALL LETTER A WITH DIAERESIS E5 00E5 LATIN SMALL LETTER A WITH RING ABOVE E6 00E6 LATIN SMALL LETTER AE E7 012F LATIN SMALL LETTER I WITH OGONEK E8 010D LATIN SMALL LETTER C WITH CARON E9 00E9 LATIN SMALL LETTER E WITH ACUTE EA 0119 LATIN SMALL LETTER E WITH OGONEK EB 00EB LATIN SMALL LETTER E WITH DIAERESIS EC 0117 LATIN SMALL LETTER E WITH DOT ABOVE ED 00ED LATIN SMALL LETTER I WITH ACUTE EE 00EE LATIN SMALL LETTER I WITH CIRCUMFLEX EF 00EF LATIN SMALL LETTER I WITH DIAERESIS F0 00F0 LATIN SMALL LETTER ETH (Icelandic) F1 0146 LATIN SMALL LETTER N WITH CEDILLA F2 014D LATIN SMALL LETTER O WITH MACRON F3 00F3 LATIN SMALL LETTER O WITH ACUTE F4 00F4 LATIN SMALL LETTER O WITH CIRCUMFLEX F5 00F5 LATIN SMALL LETTER O WITH TILDE F6 00F6 LATIN SMALL LETTER O WITH DIAERESIS F7 0169 LATIN SMALL LETTER U WITH TILDE F8 00F8 LATIN SMALL LETTER O WITH STROKE F9 0173 LATIN SMALL LETTER U WITH OGONEK FA 00FA LATIN SMALL LETTER U WITH ACUTE FB 00FB LATIN SMALL LETTER U WITH CIRCUMFLEX FC 00FC LATIN SMALL LETTER U WITH DIAERESIS FD 00FD LATIN SMALL LETTER Y WITH ACUTE FE 00FE LATIN SMALL LETTER THORN (Icelandic) FF 0138 LATIN SMALL LETTER KRA cyrus-imapd-2.5.10/lib/charset/iso-8859-4.t0000644000175000017500000002341513001236020014677 00000000000000# # Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. # # Redistribution and use in source and binary forms, with or without # modification, are permitted provided that the following conditions # are met: # # 1. Redistributions of source code must retain the above copyright # notice, this list of conditions and the following disclaimer. # # 2. Redistributions in binary form must reproduce the above copyright # notice, this list of conditions and the following disclaimer in # the documentation and/or other materials provided with the # distribution. # # 3. The name "Carnegie Mellon University" must not be used to # endorse or promote products derived from this software without # prior written permission. For permission or any legal # details, please contact # Carnegie Mellon University # Center for Technology Transfer and Enterprise Creation # 4615 Forbes Avenue # Suite 302 # Pittsburgh, PA 15213 # (412) 268-7393, fax: (412) 268-7395 # innovation@andrew.cmu.edu # # 4. Redistributions of any form whatsoever must retain the following # acknowledgment: # "This product includes software developed by Computing Services # at Carnegie Mellon University (http://www.cmu.edu/computing/)." # # CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO # THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY # AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE # FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES # WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN # AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING # OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. 0 0000 NULL (NUL) 1 0001 START OF HEADING (SOH) 2 0002 START OF TEXT (STX) 3 0003 END OF TEXT (ETX) 4 0004 END OF TRANSMISSION (EOT) 5 0005 ENQUIRY (ENQ) 6 0006 ACKNOWLEDGE (ACK) 7 0007 BELL (BEL) 8 0008 BACKSPACE (BS) 9 0009 CHARACTER TABULATION (HT) A 000a LINE FEED (LF) B 000b LINE TABULATION (VT) C 000c FORM FEED (FF) D 000d CARRIAGE RETURN (CR) E 000e SHIFT OUT (SO) F 000f SHIFT IN (SI) 10 0010 DATALINK ESCAPE (DLE) 11 0011 DEVICE CONTROL ONE (DC1) 12 0012 DEVICE CONTROL TWO (DC2) 13 0013 DEVICE CONTROL THREE (DC3) 14 0014 DEVICE CONTROL FOUR (DC4) 15 0015 NEGATIVE ACKNOWLEDGE (NAK) 16 0016 SYNCRONOUS IDLE (SYN) 17 0017 END OF TRANSMISSION BLOCK (ETB) 18 0018 CANCEL (CAN) 19 0019 END OF MEDIUM (EM) 1A 001a SUBSTITUTE (SUB) 1B 001b ESCAPE (ESC) 1C 001c FILE SEPARATOR (IS4) 1D 001d GROUP SEPARATOR (IS3) 1E 001e RECORD SEPARATOR (IS2) 1F 001f UNIT SEPARATOR (IS1) 20 0020 SPACE 21 0021 EXCLAMATION MARK 22 0022 QUOTATION MARK 23 0023 NUMBER SIGN 24 0024 DOLLAR SIGN 25 0025 PERCENT SIGN 26 0026 AMPERSAND 27 0027 APOSTROPHE 28 0028 LEFT PARENTHESIS 29 0029 RIGHT PARENTHESIS 2A 002a ASTERISK 2B 002b PLUS SIGN 2C 002c COMMA 2D 002d HYPHEN-MINUS 2E 002e FULL STOP 2F 002f SOLIDUS 30 0030 DIGIT ZERO 31 0031 DIGIT ONE 32 0032 DIGIT TWO 33 0033 DIGIT THREE 34 0034 DIGIT FOUR 35 0035 DIGIT FIVE 36 0036 DIGIT SIX 37 0037 DIGIT SEVEN 38 0038 DIGIT EIGHT 39 0039 DIGIT NINE 3A 003a COLON 3B 003b SEMICOLON 3C 003c LESS-THAN SIGN 3D 003d EQUALS SIGN 3E 003e GREATER-THAN SIGN 3F 003f QUESTION MARK 40 0040 COMMERCIAL AT 41 0041 LATIN CAPITAL LETTER A 42 0042 LATIN CAPITAL LETTER B 43 0043 LATIN CAPITAL LETTER C 44 0044 LATIN CAPITAL LETTER D 45 0045 LATIN CAPITAL LETTER E 46 0046 LATIN CAPITAL LETTER F 47 0047 LATIN CAPITAL LETTER G 48 0048 LATIN CAPITAL LETTER H 49 0049 LATIN CAPITAL LETTER I 4A 004a LATIN CAPITAL LETTER J 4B 004b LATIN CAPITAL LETTER K 4C 004c LATIN CAPITAL LETTER L 4D 004d LATIN CAPITAL LETTER M 4E 004e LATIN CAPITAL LETTER N 4F 004f LATIN CAPITAL LETTER O 50 0050 LATIN CAPITAL LETTER P 51 0051 LATIN CAPITAL LETTER Q 52 0052 LATIN CAPITAL LETTER R 53 0053 LATIN CAPITAL LETTER S 54 0054 LATIN CAPITAL LETTER T 55 0055 LATIN CAPITAL LETTER U 56 0056 LATIN CAPITAL LETTER V 57 0057 LATIN CAPITAL LETTER W 58 0058 LATIN CAPITAL LETTER X 59 0059 LATIN CAPITAL LETTER Y 5A 005a LATIN CAPITAL LETTER Z 5B 005b LEFT SQUARE BRACKET 5C 005c REVERSE SOLIDUS 5D 005d RIGHT SQUARE BRACKET 5E 005e CIRCUMFLEX ACCENT 5F 005f LOW LINE 60 0060 GRAVE ACCENT 61 0061 LATIN SMALL LETTER A 62 0062 LATIN SMALL LETTER B 63 0063 LATIN SMALL LETTER C 64 0064 LATIN SMALL LETTER D 65 0065 LATIN SMALL LETTER E 66 0066 LATIN SMALL LETTER F 67 0067 LATIN SMALL LETTER G 68 0068 LATIN SMALL LETTER H 69 0069 LATIN SMALL LETTER I 6A 006a LATIN SMALL LETTER J 6B 006b LATIN SMALL LETTER K 6C 006c LATIN SMALL LETTER L 6D 006d LATIN SMALL LETTER M 6E 006e LATIN SMALL LETTER N 6F 006f LATIN SMALL LETTER O 70 0070 LATIN SMALL LETTER P 71 0071 LATIN SMALL LETTER Q 72 0072 LATIN SMALL LETTER R 73 0073 LATIN SMALL LETTER S 74 0074 LATIN SMALL LETTER T 75 0075 LATIN SMALL LETTER U 76 0076 LATIN SMALL LETTER V 77 0077 LATIN SMALL LETTER W 78 0078 LATIN SMALL LETTER X 79 0079 LATIN SMALL LETTER Y 7A 007a LATIN SMALL LETTER Z 7B 007b LEFT CURLY BRACKET 7C 007c VERTICAL LINE 7D 007d RIGHT CURLY BRACKET 7E 007e TILDE 7F 007f DELETE (DEL) 80 0080 PADDING CHARACTER (PAD) 81 0081 HIGH OCTET PRESET (HOP) 82 0082 BREAK PERMITTED HERE (BPH) 83 0083 NO BREAK HERE (NBH) 84 0084 INDEX (IND) 85 0085 NEXT LINE (NEL) 86 0086 START OF SELECTED AREA (SSA) 87 0087 END OF SELECTED AREA (ESA) 88 0088 CHARACTER TABULATION SET (HTS) 89 0089 CHARACTER TABULATION WITH JUSTIFICATION (HTJ) 8A 008a LINE TABULATION SET (VTS) 8B 008b PARTIAL LINE FORWARD (PLD) 8C 008c PARTIAL LINE BACKWARD (PLU) 8D 008d REVERSE LINE FEED (RI) 8E 008e SINGLE-SHIFT TWO (SS2) 8F 008f SINGLE-SHIFT THREE (SS3) 90 0090 DEVICE CONTROL STRING (DCS) 91 0091 PRIVATE USE ONE (PU1) 92 0092 PRIVATE USE TWO (PU2) 93 0093 SET TRANSMIT STATE (STS) 94 0094 CANCEL CHARACTER (CCH) 95 0095 MESSAGE WAITING (MW) 96 0096 START OF GUARDED AREA (SPA) 97 0097 END OF GUARDED AREA (EPA) 98 0098 START OF STRING (SOS) 99 0099 SINGLE GRAPHIC CHARACTER INTRODUCER (SGCI) 9A 009a SINGLE CHARACTER INTRODUCER (SCI) 9B 009b CONTROL SEQUENCE INTRODUCER (CSI) 9C 009c STRING TERMINATOR (ST) 9D 009d OPERATING SYSTEM COMMAND (OSC) 9E 009e PRIVACY MESSAGE (PM) 9F 009f APPLICATION PROGRAM COMMAND (APC) A0 00a0 NO-BREAK SPACE A1 0104 LATIN CAPITAL LETTER A WITH OGONEK A2 0138 LATIN SMALL LETTER KRA (Greenlandic) A3 0156 LATIN CAPITAL LETTER R WITH CEDILLA A4 00a4 CURRENCY SIGN A5 0128 LATIN CAPITAL LETTER I WITH TILDE A6 013b LATIN CAPITAL LETTER L WITH CEDILLA A7 00a7 SECTION SIGN A8 00a8 DIAERESIS A9 0160 LATIN CAPITAL LETTER S WITH CARON AA 0112 LATIN CAPITAL LETTER E WITH MACRON AB 0122 LATIN CAPITAL LETTER G WITH CEDILLA AC 0166 LATIN CAPITAL LETTER T WITH STROKE AD 00ad SOFT HYPHEN AE 017d LATIN CAPITAL LETTER Z WITH CARON AF 00af MACRON B0 00b0 DEGREE SIGN B1 0105 LATIN SMALL LETTER A WITH OGONEK B2 02db OGONEK B3 0157 LATIN SMALL LETTER R WITH CEDILLA B4 00b4 ACUTE ACCENT B5 0129 LATIN SMALL LETTER I WITH TILDE B6 013c LATIN SMALL LETTER L WITH CEDILLA B7 02c7 CARON B8 00b8 CEDILLA B9 0161 LATIN SMALL LETTER S WITH CARON BA 0113 LATIN SMALL LETTER E WITH MACRON BB 0123 LATIN SMALL LETTER G WITH CEDILLA BC 0167 LATIN SMALL LETTER T WITH STROKE BD 014a LATIN CAPITAL LETTER ENG (Lappish) BE 017e LATIN SMALL LETTER Z WITH CARON BF 014b LATIN SMALL LETTER ENG (Lappish) C0 0100 LATIN CAPITAL LETTER A WITH MACRON C1 00c1 LATIN CAPITAL LETTER A WITH ACUTE C2 00c2 LATIN CAPITAL LETTER A WITH CIRCUMFLEX C3 00c3 LATIN CAPITAL LETTER A WITH TILDE C4 00c4 LATIN CAPITAL LETTER A WITH DIAERESIS C5 00c5 LATIN CAPITAL LETTER A WITH RING ABOVE C6 00c6 LATIN CAPITAL LETTER AE C7 012e LATIN CAPITAL LETTER I WITH OGONEK C8 010c LATIN CAPITAL LETTER C WITH CARON C9 00c9 LATIN CAPITAL LETTER E WITH ACUTE CA 0118 LATIN CAPITAL LETTER E WITH OGONEK CB 00cb LATIN CAPITAL LETTER E WITH DIAERESIS CC 0116 LATIN CAPITAL LETTER E WITH DOT ABOVE CD 00cd LATIN CAPITAL LETTER I WITH ACUTE CE 00ce LATIN CAPITAL LETTER I WITH CIRCUMFLEX CF 012a LATIN CAPITAL LETTER I WITH MACRON D0 0110 LATIN CAPITAL LETTER D WITH STROKE D1 0145 LATIN CAPITAL LETTER N WITH CEDILLA D2 014c LATIN CAPITAL LETTER O WITH MACRON D3 0136 LATIN CAPITAL LETTER K WITH CEDILLA D4 00d4 LATIN CAPITAL LETTER O WITH CIRCUMFLEX D5 00d5 LATIN CAPITAL LETTER O WITH TILDE D6 00d6 LATIN CAPITAL LETTER O WITH DIAERESIS D7 00d7 MULTIPLICATION SIGN D8 00d8 LATIN CAPITAL LETTER O WITH STROKE D9 0172 LATIN CAPITAL LETTER U WITH OGONEK DA 00da LATIN CAPITAL LETTER U WITH ACUTE DB 00db LATIN CAPITAL LETTER U WITH CIRCUMFLEX DC 00dc LATIN CAPITAL LETTER U WITH DIAERESIS DD 0168 LATIN CAPITAL LETTER U WITH TILDE DE 016a LATIN CAPITAL LETTER U WITH MACRON DF 00df LATIN SMALL LETTER SHARP S (German) E0 0101 LATIN SMALL LETTER A WITH MACRON E1 00e1 LATIN SMALL LETTER A WITH ACUTE E2 00e2 LATIN SMALL LETTER A WITH CIRCUMFLEX E3 00e3 LATIN SMALL LETTER A WITH TILDE E4 00e4 LATIN SMALL LETTER A WITH DIAERESIS E5 00e5 LATIN SMALL LETTER A WITH RING ABOVE E6 00e6 LATIN SMALL LETTER AE E7 012f LATIN SMALL LETTER I WITH OGONEK E8 010d LATIN SMALL LETTER C WITH CARON E9 00e9 LATIN SMALL LETTER E WITH ACUTE EA 0119 LATIN SMALL LETTER E WITH OGONEK EB 00eb LATIN SMALL LETTER E WITH DIAERESIS EC 0117 LATIN SMALL LETTER E WITH DOT ABOVE ED 00ed LATIN SMALL LETTER I WITH ACUTE EE 00ee LATIN SMALL LETTER I WITH CIRCUMFLEX EF 012b LATIN SMALL LETTER I WITH MACRON F0 0111 LATIN SMALL LETTER D WITH STROKE F1 0146 LATIN SMALL LETTER N WITH CEDILLA F2 014d LATIN SMALL LETTER O WITH MACRON F3 0137 LATIN SMALL LETTER K WITH CEDILLA F4 00f4 LATIN SMALL LETTER O WITH CIRCUMFLEX F5 00f5 LATIN SMALL LETTER O WITH TILDE F6 00f6 LATIN SMALL LETTER O WITH DIAERESIS F7 00f7 DIVISION SIGN F8 00f8 LATIN SMALL LETTER O WITH STROKE F9 0173 LATIN SMALL LETTER U WITH OGONEK FA 00fa LATIN SMALL LETTER U WITH ACUTE FB 00fb LATIN SMALL LETTER U WITH CIRCUMFLEX FC 00fc LATIN SMALL LETTER U WITH DIAERESIS FD 0169 LATIN SMALL LETTER U WITH TILDE FE 016b LATIN SMALL LETTER U WITH MACRON FF 02d9 DOT ABOVE cyrus-imapd-2.5.10/lib/charset/windows-1254.t0000644000175000017500000002222213001236020015407 00000000000000# # Copyright (c) 1994-2014 Carnegie Mellon University. All rights reserved. # # Redistribution and use in source and binary forms, with or without # modification, are permitted provided that the following conditions # are met: # # 1. Redistributions of source code must retain the above copyright # notice, this list of conditions and the following disclaimer. # # 2. Redistributions in binary form must reproduce the above copyright # notice, this list of conditions and the following disclaimer in # the documentation and/or other materials provided with the # distribution. # # 3. The name "Carnegie Mellon University" must not be used to # endorse or promote products derived from this software without # prior written permission. For permission or any legal # details, please contact # Carnegie Mellon University # Center for Technology Transfer and Enterprise Creation # 4615 Forbes Avenue # Suite 302 # Pittsburgh, PA 15213 # (412) 268-7393, fax(412) 268-7395 # innovation@andrew.cmu.edu # # 4. Redistributions of any form whatsoever must retain the following # acknowledgment: # "This product includes software developed by Computing Services # at Carnegie Mellon University (http://www.cmu.edu/computing/)." # # CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO # THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY # AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE # FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES # WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN # AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING # OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. # # Charset put together by Bron Gondwana # Reference: http://msdn.microsoft.com/en-us/goglobal/cc305147 00 0000 NULL 01 0001 START OF HEADING 02 0002 START OF TEXT 03 0003 END OF TEXT 04 0004 END OF TRANSMISSION 05 0005 ENQUIRY 06 0006 ACKNOWLEDGE 07 0007 BELL 08 0008 BACKSPACE 09 0009 HORIZONTAL TABULATION 0A 000A LINE FEED 0B 000B VERTICAL TABULATION 0C 000C FORM FEED 0D 000D CARRIAGE RETURN 0E 000E SHIFT OUT 0F 000F SHIFT IN 10 0010 DATA LINK ESCAPE 11 0011 DEVICE CONTROL ONE 12 0012 DEVICE CONTROL TWO 13 0013 DEVICE CONTROL THREE 14 0014 DEVICE CONTROL FOUR 15 0015 NEGATIVE ACKNOWLEDGE 16 0016 SYNCHRONOUS IDLE 17 0017 END OF TRANSMISSION BLOCK 18 0018 CANCEL 19 0019 END OF MEDIUM 1A 001A SUBSTITUTE 1B 001B ESCAPE 1C 001C FILE SEPARATOR 1D 001D GROUP SEPARATOR 1E 001E RECORD SEPARATOR 1F 001F UNIT SEPARATOR 20 0020 SPACE 21 0021 EXCLAMATION MARK 22 0022 QUOTATION MARK 23 0023 NUMBER SIGN 24 0024 DOLLAR SIGN 25 0025 PERCENT SIGN 26 0026 AMPERSAND 27 0027 APOSTROPHE 28 0028 LEFT PARENTHESIS 29 0029 RIGHT PARENTHESIS 2A 002A ASTERISK 2B 002B PLUS SIGN 2C 002C COMMA 2D 002D HYPHEN-MINUS 2E 002E FULL STOP 2F 002F SOLIDUS 30 0030 DIGIT ZERO 31 0031 DIGIT ONE 32 0032 DIGIT TWO 33 0033 DIGIT THREE 34 0034 DIGIT FOUR 35 0035 DIGIT FIVE 36 0036 DIGIT SIX 37 0037 DIGIT SEVEN 38 0038 DIGIT EIGHT 39 0039 DIGIT NINE 3A 003A COLON 3B 003B SEMICOLON 3C 003C LESS-THAN SIGN 3D 003D EQUALS SIGN 3E 003E GREATER-THAN SIGN 3F 003F QUESTION MARK 40 0040 COMMERCIAL AT 41 0041 LATIN CAPITAL LETTER A 42 0042 LATIN CAPITAL LETTER B 43 0043 LATIN CAPITAL LETTER C 44 0044 LATIN CAPITAL LETTER D 45 0045 LATIN CAPITAL LETTER E 46 0046 LATIN CAPITAL LETTER F 47 0047 LATIN CAPITAL LETTER G 48 0048 LATIN CAPITAL LETTER H 49 0049 LATIN CAPITAL LETTER I 4A 004A LATIN CAPITAL LETTER J 4B 004B LATIN CAPITAL LETTER K 4C 004C LATIN CAPITAL LETTER L 4D 004D LATIN CAPITAL LETTER M 4E 004E LATIN CAPITAL LETTER N 4F 004F LATIN CAPITAL LETTER O 50 0050 LATIN CAPITAL LETTER P 51 0051 LATIN CAPITAL LETTER Q 52 0052 LATIN CAPITAL LETTER R 53 0053 LATIN CAPITAL LETTER S 54 0054 LATIN CAPITAL LETTER T 55 0055 LATIN CAPITAL LETTER U 56 0056 LATIN CAPITAL LETTER V 57 0057 LATIN CAPITAL LETTER W 58 0058 LATIN CAPITAL LETTER X 59 0059 LATIN CAPITAL LETTER Y 5A 005A LATIN CAPITAL LETTER Z 5B 005B LEFT SQUARE BRACKET 5C 005C REVERSE SOLIDUS 5D 005D RIGHT SQUARE BRACKET 5E 005E CIRCUMFLEX ACCENT 5F 005F LOW LINE 60 0060 GRAVE ACCENT 61 0061 LATIN SMALL LETTER A 62 0062 LATIN SMALL LETTER B 63 0063 LATIN SMALL LETTER C 64 0064 LATIN SMALL LETTER D 65 0065 LATIN SMALL LETTER E 66 0066 LATIN SMALL LETTER F 67 0067 LATIN SMALL LETTER G 68 0068 LATIN SMALL LETTER H 69 0069 LATIN SMALL LETTER I 6A 006A LATIN SMALL LETTER J 6B 006B LATIN SMALL LETTER K 6C 006C LATIN SMALL LETTER L 6D 006D LATIN SMALL LETTER M 6E 006E LATIN SMALL LETTER N 6F 006F LATIN SMALL LETTER O 70 0070 LATIN SMALL LETTER P 71 0071 LATIN SMALL LETTER Q 72 0072 LATIN SMALL LETTER R 73 0073 LATIN SMALL LETTER S 74 0074 LATIN SMALL LETTER T 75 0075 LATIN SMALL LETTER U 76 0076 LATIN SMALL LETTER V 77 0077 LATIN SMALL LETTER W 78 0078 LATIN SMALL LETTER X 79 0079 LATIN SMALL LETTER Y 7A 007A LATIN SMALL LETTER Z 7B 007B LEFT CURLY BRACKET 7C 007C VERTICAL LINE 7D 007D RIGHT CURLY BRACKET 7E 007E TILDE 7F 007F DELETE 80 20AC EURO SIGN 82 201A SINGLE LOW-9 QUOTATION MARK 83 0192 LATIN SMALL LETTER F WITH HOOK 84 201E DOUBLE LOW-9 QUOTATION MARK 85 2026 HORIZONTAL ELLIPSIS 86 2020 DAGGER 87 2021 DOUBLE DAGGER 88 02C6 MODIFIER LETTER CIRCUMFLEX ACCENT 89 2030 PER MILLE SIGN 8A 0160 LATIN CAPITAL LETTER S WITH CARON 8B 2039 SINGLE LEFT-POINTING ANGLE QUOTATION MARK 8C 0152 LATIN CAPITAL LIGATURE OE 91 2018 LEFT SINGLE QUOTATION MARK 92 2019 RIGHT SINGLE QUOTATION MARK 93 201C LEFT DOUBLE QUOTATION MARK 94 201D RIGHT DOUBLE QUOTATION MARK 95 2022 BULLET 96 2013 EN DASH 97 2014 EM DASH 98 02DC SMALL TILDE 99 2122 TRADE MARK SIGN 9A 0161 LATIN SMALL LETTER S WITH CARON 9B 203A SINGLE RIGHT-POINTING ANGLE QUOTATION MARK 9C 0153 LATIN SMALL LIGATURE OE 9F 0178 LATIN CAPITAL LETTER Y WITH DIAERESIS A0 00A0 NO-BREAK SPACE A1 00A1 INVERTED EXCLAMATION MARK A2 00A2 CENT SIGN A3 00A3 POUND SIGN A4 00A4 CURRENCY SIGN A5 00A5 YEN SIGN A6 00A6 BROKEN BAR A7 00A7 SECTION SIGN A8 00A8 DIAERESIS A9 00A9 COPYRIGHT SIGN AA 00AA FEMININE ORDINAL INDICATOR AB 00AB LEFT-POINTING DOUBLE ANGLE QUOTATION MARK AC 00AC NOT SIGN AD 00AD SOFT HYPHEN AE 00AE REGISTERED SIGN AF 00AF MACRON B0 00B0 DEGREE SIGN B1 00B1 PLUS-MINUS SIGN B2 00B2 SUPERSCRIPT TWO B3 00B3 SUPERSCRIPT THREE B4 00B4 ACUTE ACCENT B5 00B5 MICRO SIGN B6 00B6 PILCROW SIGN B7 00B7 MIDDLE DOT B8 00B8 CEDILLA B9 00B9 SUPERSCRIPT ONE BA 00BA MASCULINE ORDINAL INDICATOR BB 00BB RIGHT-POINTING DOUBLE ANGLE QUOTATION MARK BC 00BC VULGAR FRACTION ONE QUARTER BD 00BD VULGAR FRACTION ONE HALF BE 00BE VULGAR FRACTION THREE QUARTERS BF 00BF INVERTED QUESTION MARK C0 00C0 LATIN CAPITAL LETTER A WITH GRAVE C1 00C1 LATIN CAPITAL LETTER A WITH ACUTE C2 00C2 LATIN CAPITAL LETTER A WITH CIRCUMFLEX C3 00C3 LATIN CAPITAL LETTER A WITH TILDE C4 00C4 LATIN CAPITAL LETTER A WITH DIAERESIS C5 00C5 LATIN CAPITAL LETTER A WITH RING ABOVE C6 00C6 LATIN CAPITAL LETTER AE C7 00C7 LATIN CAPITAL LETTER C WITH CEDILLA C8 00C8 LATIN CAPITAL LETTER E WITH GRAVE C9 00C9 LATIN CAPITAL LETTER E WITH ACUTE CA 00CA LATIN CAPITAL LETTER E WITH CIRCUMFLEX CB 00CB LATIN CAPITAL LETTER E WITH DIAERESIS CC 00CC LATIN CAPITAL LETTER I WITH GRAVE CD 00CD LATIN CAPITAL LETTER I WITH ACUTE CE 00CE LATIN CAPITAL LETTER I WITH CIRCUMFLEX CF 00CF LATIN CAPITAL LETTER I WITH DIAERESIS D0 011E LATIN CAPITAL LETTER G WITH BREVE D1 00D1 LATIN CAPITAL LETTER N WITH TILDE D2 00D2 LATIN CAPITAL LETTER O WITH GRAVE D3 00D3 LATIN CAPITAL LETTER O WITH ACUTE D4 00D4 LATIN CAPITAL LETTER O WITH CIRCUMFLEX D5 00D5 LATIN CAPITAL LETTER O WITH TILDE D6 00D6 LATIN CAPITAL LETTER O WITH DIAERESIS D7 00D7 MULTIPLICATION SIGN D8 00D8 LATIN CAPITAL LETTER O WITH STROKE D9 00D9 LATIN CAPITAL LETTER U WITH GRAVE DA 00DA LATIN CAPITAL LETTER U WITH ACUTE DB 00DB LATIN CAPITAL LETTER U WITH CIRCUMFLEX DC 00DC LATIN CAPITAL LETTER U WITH DIAERESIS DD 0130 LATIN CAPITAL LETTER I WITH DOT ABOVE DE 015E LATIN CAPITAL LETTER S WITH CEDILLA DF 00DF LATIN SMALL LETTER SHARP S E0 00E0 LATIN SMALL LETTER A WITH GRAVE E1 00E1 LATIN SMALL LETTER A WITH ACUTE E2 00E2 LATIN SMALL LETTER A WITH CIRCUMFLEX E3 00E3 LATIN SMALL LETTER A WITH TILDE E4 00E4 LATIN SMALL LETTER A WITH DIAERESIS E5 00E5 LATIN SMALL LETTER A WITH RING ABOVE E6 00E6 LATIN SMALL LETTER AE E7 00E7 LATIN SMALL LETTER C WITH CEDILLA E8 00E8 LATIN SMALL LETTER E WITH GRAVE E9 00E9 LATIN SMALL LETTER E WITH ACUTE EA 00EA LATIN SMALL LETTER E WITH CIRCUMFLEX EB 00EB LATIN SMALL LETTER E WITH DIAERESIS EC 00EC LATIN SMALL LETTER I WITH GRAVE ED 00ED LATIN SMALL LETTER I WITH ACUTE EE 00EE LATIN SMALL LETTER I WITH CIRCUMFLEX EF 00EF LATIN SMALL LETTER I WITH DIAERESIS F0 011F LATIN SMALL LETTER G WITH BREVE F1 00F1 LATIN SMALL LETTER N WITH TILDE F2 00F2 LATIN SMALL LETTER O WITH GRAVE F3 00F3 LATIN SMALL LETTER O WITH ACUTE F4 00F4 LATIN SMALL LETTER O WITH CIRCUMFLEX F5 00F5 LATIN SMALL LETTER O WITH TILDE F6 00F6 LATIN SMALL LETTER O WITH DIAERESIS F7 00F7 DIVISION SIGN F8 00F8 LATIN SMALL LETTER O WITH STROKE F9 00F9 LATIN SMALL LETTER U WITH GRAVE FA 00FA LATIN SMALL LETTER U WITH ACUTE FB 00FB LATIN SMALL LETTER U WITH CIRCUMFLEX FC 00FC LATIN SMALL LETTER U WITH DIAERESIS FD 0131 LATIN SMALL LETTER DOTLESS I FE 015F LATIN SMALL LETTER S WITH CEDILLA FF 00FF LATIN SMALL LETTER Y WITH DIAERESIS cyrus-imapd-2.5.10/lib/charset/iso-8859-16.t0000644000175000017500000002210613001236020014756 00000000000000# # Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. # # Redistribution and use in source and binary forms, with or without # modification, are permitted provided that the following conditions # are met: # # 1. Redistributions of source code must retain the above copyright # notice, this list of conditions and the following disclaimer. # # 2. Redistributions in binary form must reproduce the above copyright # notice, this list of conditions and the following disclaimer in # the documentation and/or other materials provided with the # distribution. # # 3. The name "Carnegie Mellon University" must not be used to # endorse or promote products derived from this software without # prior written permission. For permission or any legal # details, please contact # Carnegie Mellon University # Center for Technology Transfer and Enterprise Creation # 4615 Forbes Avenue # Suite 302 # Pittsburgh, PA 15213 # (412) 268-7393, fax: (412) 268-7395 # innovation@andrew.cmu.edu # # 4. Redistributions of any form whatsoever must retain the following # acknowledgment: # "This product includes software developed by Computing Services # at Carnegie Mellon University (http://www.cmu.edu/computing/)." # # CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO # THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY # AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE # FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES # WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN # AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING # OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. 00 0000 01 0001 02 0002 03 0003 04 0004 05 0005 06 0006 07 0007 08 0008 09 0009 0A 000A 0B 000B 0C 000C 0D 000D 0E 000E 0F 000F 10 0010 11 0011 12 0012 13 0013 14 0014 15 0015 16 0016 17 0017 18 0018 19 0019 1A 001A 1B 001B 1C 001C 1D 001D 1E 001E 1F 001F 20 0020 SPACE 21 0021 EXCLAMATION MARK 22 0022 QUOTATION MARK 23 0023 NUMBER SIGN 24 0024 DOLLAR SIGN 25 0025 PERCENT SIGN 26 0026 AMPERSAND 27 0027 APOSTROPHE 28 0028 LEFT PARENTHESIS 29 0029 RIGHT PARENTHESIS 2A 002A ASTERISK 2B 002B PLUS SIGN 2C 002C COMMA 2D 002D HYPHEN-MINUS 2E 002E FULL STOP 2F 002F SOLIDUS 30 0030 DIGIT ZERO 31 0031 DIGIT ONE 32 0032 DIGIT TWO 33 0033 DIGIT THREE 34 0034 DIGIT FOUR 35 0035 DIGIT FIVE 36 0036 DIGIT SIX 37 0037 DIGIT SEVEN 38 0038 DIGIT EIGHT 39 0039 DIGIT NINE 3A 003A COLON 3B 003B SEMICOLON 3C 003C LESS-THAN SIGN 3D 003D EQUALS SIGN 3E 003E GREATER-THAN SIGN 3F 003F QUESTION MARK 40 0040 COMMERCIAL AT 41 0041 LATIN CAPITAL LETTER A 42 0042 LATIN CAPITAL LETTER B 43 0043 LATIN CAPITAL LETTER C 44 0044 LATIN CAPITAL LETTER D 45 0045 LATIN CAPITAL LETTER E 46 0046 LATIN CAPITAL LETTER F 47 0047 LATIN CAPITAL LETTER G 48 0048 LATIN CAPITAL LETTER H 49 0049 LATIN CAPITAL LETTER I 4A 004A LATIN CAPITAL LETTER J 4B 004B LATIN CAPITAL LETTER K 4C 004C LATIN CAPITAL LETTER L 4D 004D LATIN CAPITAL LETTER M 4E 004E LATIN CAPITAL LETTER N 4F 004F LATIN CAPITAL LETTER O 50 0050 LATIN CAPITAL LETTER P 51 0051 LATIN CAPITAL LETTER Q 52 0052 LATIN CAPITAL LETTER R 53 0053 LATIN CAPITAL LETTER S 54 0054 LATIN CAPITAL LETTER T 55 0055 LATIN CAPITAL LETTER U 56 0056 LATIN CAPITAL LETTER V 57 0057 LATIN CAPITAL LETTER W 58 0058 LATIN CAPITAL LETTER X 59 0059 LATIN CAPITAL LETTER Y 5A 005A LATIN CAPITAL LETTER Z 5B 005B LEFT SQUARE BRACKET 5C 005C REVERSE SOLIDUS 5D 005D RIGHT SQUARE BRACKET 5E 005E CIRCUMFLEX ACCENT 5F 005F LOW LINE 60 0060 GRAVE ACCENT 61 0061 LATIN SMALL LETTER A 62 0062 LATIN SMALL LETTER B 63 0063 LATIN SMALL LETTER C 64 0064 LATIN SMALL LETTER D 65 0065 LATIN SMALL LETTER E 66 0066 LATIN SMALL LETTER F 67 0067 LATIN SMALL LETTER G 68 0068 LATIN SMALL LETTER H 69 0069 LATIN SMALL LETTER I 6A 006A LATIN SMALL LETTER J 6B 006B LATIN SMALL LETTER K 6C 006C LATIN SMALL LETTER L 6D 006D LATIN SMALL LETTER M 6E 006E LATIN SMALL LETTER N 6F 006F LATIN SMALL LETTER O 70 0070 LATIN SMALL LETTER P 71 0071 LATIN SMALL LETTER Q 72 0072 LATIN SMALL LETTER R 73 0073 LATIN SMALL LETTER S 74 0074 LATIN SMALL LETTER T 75 0075 LATIN SMALL LETTER U 76 0076 LATIN SMALL LETTER V 77 0077 LATIN SMALL LETTER W 78 0078 LATIN SMALL LETTER X 79 0079 LATIN SMALL LETTER Y 7A 007A LATIN SMALL LETTER Z 7B 007B LEFT CURLY BRACKET 7C 007C VERTICAL LINE 7D 007D RIGHT CURLY BRACKET 7E 007E TILDE 7F 007F 80 0080 81 0081 82 0082 83 0083 84 0084 85 0085 86 0086 87 0087 88 0088 89 0089 8A 008A 8B 008B 8C 008C 8D 008D 8E 008E 8F 008F 90 0090 91 0091 92 0092 93 0093 94 0094 95 0095 96 0096 97 0097 98 0098 99 0099 9A 009A 9B 009B 9C 009C 9D 009D 9E 009E 9F 009F A0 00A0 NO-BREAK SPACE A1 0104 LATIN CAPITAL LETTER A WITH OGONEK A2 0105 LATIN SMALL LETTER A WITH OGONEK A3 0141 LATIN CAPITAL LETTER L WITH STROKE A4 20AC EURO SIGN A5 201E DOUBLE LOW-9 QUOTATION MARK A6 0160 LATIN CAPITAL LETTER S WITH CARON A7 00A7 SECTION SIGN A8 0161 LATIN SMALL LETTER S WITH CARON A9 00A9 COPYRIGHT SIGN AA 0218 LATIN CAPITAL LETTER S WITH COMMA BELOW AB 00AB LEFT-POINTING DOUBLE ANGLE QUOTATION MARK AC 0179 LATIN CAPITAL LETTER Z WITH ACUTE AD 00AD SOFT HYPHEN AE 017A LATIN SMALL LETTER Z WITH ACUTE AF 017B LATIN CAPITAL LETTER Z WITH DOT ABOVE B0 00B0 DEGREE SIGN B1 00B1 PLUS-MINUS SIGN B2 010C LATIN CAPITAL LETTER C WITH CARON B3 0142 LATIN SMALL LETTER L WITH STROKE B4 017D LATIN CAPITAL LETTER Z WITH CARON B5 201D RIGHT DOUBLE QUOTATION MARK B6 00B6 PILCROW SIGN B7 00B7 MIDDLE DOT B8 017E LATIN SMALL LETTER Z WITH CARON B9 010D LATIN SMALL LETTER C WITH CARON BA 0219 LATIN SMALL LETTER S WITH COMMA BELOW BB 00BB RIGHT-POINTING DOUBLE ANGLE QUOTATION MARK BC 0152 LATIN CAPITAL LIGATURE OE BD 0153 LATIN SMALL LIGATURE OE BE 0178 LATIN CAPITAL LETTER Y WITH DIAERESIS BF 017C LATIN SMALL LETTER Z WITH DOT ABOVE C0 00C0 LATIN CAPITAL LETTER A WITH GRAVE C1 00C1 LATIN CAPITAL LETTER A WITH ACUTE C2 00C2 LATIN CAPITAL LETTER A WITH CIRCUMFLEX C3 0102 LATIN CAPITAL LETTER A WITH BREVE C4 00C4 LATIN CAPITAL LETTER A WITH DIAERESIS C5 0106 LATIN CAPITAL LETTER C WITH ACUTE C6 00C6 LATIN CAPITAL LETTER AE C7 00C7 LATIN CAPITAL LETTER C WITH CEDILLA C8 00C8 LATIN CAPITAL LETTER E WITH GRAVE C9 00C9 LATIN CAPITAL LETTER E WITH ACUTE CA 00CA LATIN CAPITAL LETTER E WITH CIRCUMFLEX CB 00CB LATIN CAPITAL LETTER E WITH DIAERESIS CC 00CC LATIN CAPITAL LETTER I WITH GRAVE CD 00CD LATIN CAPITAL LETTER I WITH ACUTE CE 00CE LATIN CAPITAL LETTER I WITH CIRCUMFLEX CF 00CF LATIN CAPITAL LETTER I WITH DIAERESIS D0 0110 LATIN CAPITAL LETTER D WITH STROKE D1 0143 LATIN CAPITAL LETTER N WITH ACUTE D2 00D2 LATIN CAPITAL LETTER O WITH GRAVE D3 00D3 LATIN CAPITAL LETTER O WITH ACUTE D4 00D4 LATIN CAPITAL LETTER O WITH CIRCUMFLEX D5 0150 LATIN CAPITAL LETTER O WITH DOUBLE ACUTE D6 00D6 LATIN CAPITAL LETTER O WITH DIAERESIS D7 015A LATIN CAPITAL LETTER S WITH ACUTE D8 0170 LATIN CAPITAL LETTER U WITH DOUBLE ACUTE D9 00D9 LATIN CAPITAL LETTER U WITH GRAVE DA 00DA LATIN CAPITAL LETTER U WITH ACUTE DB 00DB LATIN CAPITAL LETTER U WITH CIRCUMFLEX DC 00DC LATIN CAPITAL LETTER U WITH DIAERESIS DD 0118 LATIN CAPITAL LETTER E WITH OGONEK DE 021A LATIN CAPITAL LETTER T WITH COMMA BELOW DF 00DF LATIN SMALL LETTER SHARP S E0 00E0 LATIN SMALL LETTER A WITH GRAVE E1 00E1 LATIN SMALL LETTER A WITH ACUTE E2 00E2 LATIN SMALL LETTER A WITH CIRCUMFLEX E3 0103 LATIN SMALL LETTER A WITH BREVE E4 00E4 LATIN SMALL LETTER A WITH DIAERESIS E5 0107 LATIN SMALL LETTER C WITH ACUTE E6 00E6 LATIN SMALL LETTER AE E7 00E7 LATIN SMALL LETTER C WITH CEDILLA E8 00E8 LATIN SMALL LETTER E WITH GRAVE E9 00E9 LATIN SMALL LETTER E WITH ACUTE EA 00EA LATIN SMALL LETTER E WITH CIRCUMFLEX EB 00EB LATIN SMALL LETTER E WITH DIAERESIS EC 00EC LATIN SMALL LETTER I WITH GRAVE ED 00ED LATIN SMALL LETTER I WITH ACUTE EE 00EE LATIN SMALL LETTER I WITH CIRCUMFLEX EF 00EF LATIN SMALL LETTER I WITH DIAERESIS F0 0111 LATIN SMALL LETTER D WITH STROKE F1 0144 LATIN SMALL LETTER N WITH ACUTE F2 00F2 LATIN SMALL LETTER O WITH GRAVE F3 00F3 LATIN SMALL LETTER O WITH ACUTE F4 00F4 LATIN SMALL LETTER O WITH CIRCUMFLEX F5 0151 LATIN SMALL LETTER O WITH DOUBLE ACUTE F6 00F6 LATIN SMALL LETTER O WITH DIAERESIS F7 015B LATIN SMALL LETTER S WITH ACUTE F8 0171 LATIN SMALL LETTER U WITH DOUBLE ACUTE F9 00F9 LATIN SMALL LETTER U WITH GRAVE FA 00FA LATIN SMALL LETTER U WITH ACUTE FB 00FB LATIN SMALL LETTER U WITH CIRCUMFLEX FC 00FC LATIN SMALL LETTER U WITH DIAERESIS FD 0119 LATIN SMALL LETTER E WITH OGONEK FE 021B LATIN SMALL LETTER T WITH COMMA BELOW FF 00FF LATIN SMALL LETTER Y WITH DIAERESIS cyrus-imapd-2.5.10/lib/charset/iso-8859-14.t0000644000175000017500000002246013001236020014757 00000000000000# # Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. # # Redistribution and use in source and binary forms, with or without # modification, are permitted provided that the following conditions # are met: # # 1. Redistributions of source code must retain the above copyright # notice, this list of conditions and the following disclaimer. # # 2. Redistributions in binary form must reproduce the above copyright # notice, this list of conditions and the following disclaimer in # the documentation and/or other materials provided with the # distribution. # # 3. The name "Carnegie Mellon University" must not be used to # endorse or promote products derived from this software without # prior written permission. For permission or any legal # details, please contact # Carnegie Mellon University # Center for Technology Transfer and Enterprise Creation # 4615 Forbes Avenue # Suite 302 # Pittsburgh, PA 15213 # (412) 268-7393, fax: (412) 268-7395 # innovation@andrew.cmu.edu # # 4. Redistributions of any form whatsoever must retain the following # acknowledgment: # "This product includes software developed by Computing Services # at Carnegie Mellon University (http://www.cmu.edu/computing/)." # # CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO # THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY # AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE # FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES # WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN # AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING # OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. 00 0000 NULL 01 0001 START OF HEADING 02 0002 START OF TEXT 03 0003 END OF TEXT 04 0004 END OF TRANSMISSION 05 0005 ENQUIRY 06 0006 ACKNOWLEDGE 07 0007 BELL 08 0008 BACKSPACE 09 0009 HORIZONTAL TABULATION 0A 000A LINE FEED 0B 000B VERTICAL TABULATION 0C 000C FORM FEED 0D 000D CARRIAGE RETURN 0E 000E SHIFT OUT 0F 000F SHIFT IN 10 0010 DATA LINK ESCAPE 11 0011 DEVICE CONTROL ONE 12 0012 DEVICE CONTROL TWO 13 0013 DEVICE CONTROL THREE 14 0014 DEVICE CONTROL FOUR 15 0015 NEGATIVE ACKNOWLEDGE 16 0016 SYNCHRONOUS IDLE 17 0017 END OF TRANSMISSION BLOCK 18 0018 CANCEL 19 0019 END OF MEDIUM 1A 001A SUBSTITUTE 1B 001B ESCAPE 1C 001C FILE SEPARATOR 1D 001D GROUP SEPARATOR 1E 001E RECORD SEPARATOR 1F 001F UNIT SEPARATOR 20 0020 SPACE 21 0021 EXCLAMATION MARK 22 0022 QUOTATION MARK 23 0023 NUMBER SIGN 24 0024 DOLLAR SIGN 25 0025 PERCENT SIGN 26 0026 AMPERSAND 27 0027 APOSTROPHE 28 0028 LEFT PARENTHESIS 29 0029 RIGHT PARENTHESIS 2A 002A ASTERISK 2B 002B PLUS SIGN 2C 002C COMMA 2D 002D HYPHEN-MINUS 2E 002E FULL STOP 2F 002F SOLIDUS 30 0030 DIGIT ZERO 31 0031 DIGIT ONE 32 0032 DIGIT TWO 33 0033 DIGIT THREE 34 0034 DIGIT FOUR 35 0035 DIGIT FIVE 36 0036 DIGIT SIX 37 0037 DIGIT SEVEN 38 0038 DIGIT EIGHT 39 0039 DIGIT NINE 3A 003A COLON 3B 003B SEMICOLON 3C 003C LESS-THAN SIGN 3D 003D EQUALS SIGN 3E 003E GREATER-THAN SIGN 3F 003F QUESTION MARK 40 0040 COMMERCIAL AT 41 0041 LATIN CAPITAL LETTER A 42 0042 LATIN CAPITAL LETTER B 43 0043 LATIN CAPITAL LETTER C 44 0044 LATIN CAPITAL LETTER D 45 0045 LATIN CAPITAL LETTER E 46 0046 LATIN CAPITAL LETTER F 47 0047 LATIN CAPITAL LETTER G 48 0048 LATIN CAPITAL LETTER H 49 0049 LATIN CAPITAL LETTER I 4A 004A LATIN CAPITAL LETTER J 4B 004B LATIN CAPITAL LETTER K 4C 004C LATIN CAPITAL LETTER L 4D 004D LATIN CAPITAL LETTER M 4E 004E LATIN CAPITAL LETTER N 4F 004F LATIN CAPITAL LETTER O 50 0050 LATIN CAPITAL LETTER P 51 0051 LATIN CAPITAL LETTER Q 52 0052 LATIN CAPITAL LETTER R 53 0053 LATIN CAPITAL LETTER S 54 0054 LATIN CAPITAL LETTER T 55 0055 LATIN CAPITAL LETTER U 56 0056 LATIN CAPITAL LETTER V 57 0057 LATIN CAPITAL LETTER W 58 0058 LATIN CAPITAL LETTER X 59 0059 LATIN CAPITAL LETTER Y 5A 005A LATIN CAPITAL LETTER Z 5B 005B LEFT SQUARE BRACKET 5C 005C REVERSE SOLIDUS 5D 005D RIGHT SQUARE BRACKET 5E 005E CIRCUMFLEX ACCENT 5F 005F LOW LINE 60 0060 GRAVE ACCENT 61 0061 LATIN SMALL LETTER A 62 0062 LATIN SMALL LETTER B 63 0063 LATIN SMALL LETTER C 64 0064 LATIN SMALL LETTER D 65 0065 LATIN SMALL LETTER E 66 0066 LATIN SMALL LETTER F 67 0067 LATIN SMALL LETTER G 68 0068 LATIN SMALL LETTER H 69 0069 LATIN SMALL LETTER I 6A 006A LATIN SMALL LETTER J 6B 006B LATIN SMALL LETTER K 6C 006C LATIN SMALL LETTER L 6D 006D LATIN SMALL LETTER M 6E 006E LATIN SMALL LETTER N 6F 006F LATIN SMALL LETTER O 70 0070 LATIN SMALL LETTER P 71 0071 LATIN SMALL LETTER Q 72 0072 LATIN SMALL LETTER R 73 0073 LATIN SMALL LETTER S 74 0074 LATIN SMALL LETTER T 75 0075 LATIN SMALL LETTER U 76 0076 LATIN SMALL LETTER V 77 0077 LATIN SMALL LETTER W 78 0078 LATIN SMALL LETTER X 79 0079 LATIN SMALL LETTER Y 7A 007A LATIN SMALL LETTER Z 7B 007B LEFT CURLY BRACKET 7C 007C VERTICAL LINE 7D 007D RIGHT CURLY BRACKET 7E 007E TILDE 7F 007F DELETE 80 0080 81 0081 82 0082 83 0083 84 0084 85 0085 86 0086 87 0087 88 0088 89 0089 8A 008A 8B 008B 8C 008C 8D 008D 8E 008E 8F 008F 90 0090 91 0091 92 0092 93 0093 94 0094 95 0095 96 0096 97 0097 98 0098 99 0099 9A 009A 9B 009B 9C 009C 9D 009D 9E 009E 9F 009F A0 00A0 NO-BREAK SPACE A1 1E02 LATIN CAPITAL LETTER B WITH DOT ABOVE A2 1E03 LATIN SMALL LETTER B WITH DOT ABOVE A3 00A3 POUND SIGN A4 010A LATIN CAPITAL LETTER C WITH DOT ABOVE A5 010B LATIN SMALL LETTER C WITH DOT ABOVE A6 1E0A LATIN CAPITAL LETTER D WITH DOT ABOVE A7 00A7 SECTION SIGN A8 1E80 LATIN CAPITAL LETTER W WITH GRAVE A9 00A9 COPYRIGHT SIGN AA 1E82 LATIN CAPITAL LETTER W WITH ACUTE AB 1E0B LATIN SMALL LETTER D WITH DOT ABOVE AC 1EF2 LATIN CAPITAL LETTER Y WITH GRAVE AD 00AD SOFT HYPHEN AE 00AE REGISTERED SIGN AF 0178 LATIN CAPITAL LETTER Y WITH DIAERESIS B0 1E1E LATIN CAPITAL LETTER F WITH DOT ABOVE B1 1E1F LATIN SMALL LETTER F WITH DOT ABOVE B2 0120 LATIN CAPITAL LETTER G WITH DOT ABOVE B3 0121 LATIN SMALL LETTER G WITH DOT ABOVE B4 1E40 LATIN CAPITAL LETTER M WITH DOT ABOVE B5 1E41 LATIN SMALL LETTER M WITH DOT ABOVE B6 00B6 PILCROW SIGN B7 1E56 LATIN CAPITAL LETTER P WITH DOT ABOVE B8 1E81 LATIN SMALL LETTER W WITH GRAVE B9 1E57 LATIN SMALL LETTER P WITH DOT ABOVE BA 1E83 LATIN SMALL LETTER W WITH ACUTE BB 1E60 LATIN CAPITAL LETTER S WITH DOT ABOVE BC 1EF3 LATIN SMALL LETTER Y WITH GRAVE BD 1E84 LATIN CAPITAL LETTER W WITH DIAERESIS BE 1E85 LATIN SMALL LETTER W WITH DIAERESIS BF 1E61 LATIN SMALL LETTER S WITH DOT ABOVE C0 00C0 LATIN CAPITAL LETTER A WITH GRAVE C1 00C1 LATIN CAPITAL LETTER A WITH ACUTE C2 00C2 LATIN CAPITAL LETTER A WITH CIRCUMFLEX C3 00C3 LATIN CAPITAL LETTER A WITH TILDE C4 00C4 LATIN CAPITAL LETTER A WITH DIAERESIS C5 00C5 LATIN CAPITAL LETTER A WITH RING ABOVE C6 00C6 LATIN CAPITAL LETTER AE C7 00C7 LATIN CAPITAL LETTER C WITH CEDILLA C8 00C8 LATIN CAPITAL LETTER E WITH GRAVE C9 00C9 LATIN CAPITAL LETTER E WITH ACUTE CA 00CA LATIN CAPITAL LETTER E WITH CIRCUMFLEX CB 00CB LATIN CAPITAL LETTER E WITH DIAERESIS CC 00CC LATIN CAPITAL LETTER I WITH GRAVE CD 00CD LATIN CAPITAL LETTER I WITH ACUTE CE 00CE LATIN CAPITAL LETTER I WITH CIRCUMFLEX CF 00CF LATIN CAPITAL LETTER I WITH DIAERESIS D0 0174 LATIN CAPITAL LETTER W WITH CIRCUMFLEX D1 00D1 LATIN CAPITAL LETTER N WITH TILDE D2 00D2 LATIN CAPITAL LETTER O WITH GRAVE D3 00D3 LATIN CAPITAL LETTER O WITH ACUTE D4 00D4 LATIN CAPITAL LETTER O WITH CIRCUMFLEX D5 00D5 LATIN CAPITAL LETTER O WITH TILDE D6 00D6 LATIN CAPITAL LETTER O WITH DIAERESIS D7 1E6A LATIN CAPITAL LETTER T WITH DOT ABOVE D8 00D8 LATIN CAPITAL LETTER O WITH STROKE D9 00D9 LATIN CAPITAL LETTER U WITH GRAVE DA 00DA LATIN CAPITAL LETTER U WITH ACUTE DB 00DB LATIN CAPITAL LETTER U WITH CIRCUMFLEX DC 00DC LATIN CAPITAL LETTER U WITH DIAERESIS DD 00DD LATIN CAPITAL LETTER Y WITH ACUTE DE 0176 LATIN CAPITAL LETTER Y WITH CIRCUMFLEX DF 00DF LATIN SMALL LETTER SHARP S E0 00E0 LATIN SMALL LETTER A WITH GRAVE E1 00E1 LATIN SMALL LETTER A WITH ACUTE E2 00E2 LATIN SMALL LETTER A WITH CIRCUMFLEX E3 00E3 LATIN SMALL LETTER A WITH TILDE E4 00E4 LATIN SMALL LETTER A WITH DIAERESIS E5 00E5 LATIN SMALL LETTER A WITH RING ABOVE E6 00E6 LATIN SMALL LETTER AE E7 00E7 LATIN SMALL LETTER C WITH CEDILLA E8 00E8 LATIN SMALL LETTER E WITH GRAVE E9 00E9 LATIN SMALL LETTER E WITH ACUTE EA 00EA LATIN SMALL LETTER E WITH CIRCUMFLEX EB 00EB LATIN SMALL LETTER E WITH DIAERESIS EC 00EC LATIN SMALL LETTER I WITH GRAVE ED 00ED LATIN SMALL LETTER I WITH ACUTE EE 00EE LATIN SMALL LETTER I WITH CIRCUMFLEX EF 00EF LATIN SMALL LETTER I WITH DIAERESIS F0 0175 LATIN SMALL LETTER W WITH CIRCUMFLEX F1 00F1 LATIN SMALL LETTER N WITH TILDE F2 00F2 LATIN SMALL LETTER O WITH GRAVE F3 00F3 LATIN SMALL LETTER O WITH ACUTE F4 00F4 LATIN SMALL LETTER O WITH CIRCUMFLEX F5 00F5 LATIN SMALL LETTER O WITH TILDE F6 00F6 LATIN SMALL LETTER O WITH DIAERESIS F7 1E6B LATIN SMALL LETTER T WITH DOT ABOVE F8 00F8 LATIN SMALL LETTER O WITH STROKE F9 00F9 LATIN SMALL LETTER U WITH GRAVE FA 00FA LATIN SMALL LETTER U WITH ACUTE FB 00FB LATIN SMALL LETTER U WITH CIRCUMFLEX FC 00FC LATIN SMALL LETTER U WITH DIAERESIS FD 00FD LATIN SMALL LETTER Y WITH ACUTE FE 0177 LATIN SMALL LETTER Y WITH CIRCUMFLEX FF 00FF LATIN SMALL LETTER Y WITH DIAERESIS cyrus-imapd-2.5.10/lib/charset/windows-1251.t0000644000175000017500000002247013001236020015411 00000000000000# # Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. # # Redistribution and use in source and binary forms, with or without # modification, are permitted provided that the following conditions # are met: # # 1. Redistributions of source code must retain the above copyright # notice, this list of conditions and the following disclaimer. # # 2. Redistributions in binary form must reproduce the above copyright # notice, this list of conditions and the following disclaimer in # the documentation and/or other materials provided with the # distribution. # # 3. The name "Carnegie Mellon University" must not be used to # endorse or promote products derived from this software without # prior written permission. For permission or any legal # details, please contact # Carnegie Mellon University # Center for Technology Transfer and Enterprise Creation # 4615 Forbes Avenue # Suite 302 # Pittsburgh, PA 15213 # (412) 268-7393, fax: (412) 268-7395 # innovation@andrew.cmu.edu # # 4. Redistributions of any form whatsoever must retain the following # acknowledgment: # "This product includes software developed by Computing Services # at Carnegie Mellon University (http://www.cmu.edu/computing/)." # # CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO # THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY # AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE # FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES # WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN # AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING # OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. # # Charset put together by Ewald Dieterich # Reference: http://www.microsoft.com/globaldev/reference/sbcs/1252.htm 0 0000 NULL (NUL) 1 0001 START OF HEADING (SOH) 2 0002 START OF TEXT (STX) 3 0003 END OF TEXT (ETX) 4 0004 END OF TRANSMISSION (EOT) 5 0005 ENQUIRY (ENQ) 6 0006 ACKNOWLEDGE (ACK) 7 0007 BELL (BEL) 8 0008 BACKSPACE (BS) 9 0009 CHARACTER TABULATION (HT) A 000a LINE FEED (LF) B 000b LINE TABULATION (VT) C 000c FORM FEED (FF) D 000d CARRIAGE RETURN (CR) E 000e SHIFT OUT (SO) F 000f SHIFT IN (SI) 10 0010 DATALINK ESCAPE (DLE) 11 0011 DEVICE CONTROL ONE (DC1) 12 0012 DEVICE CONTROL TWO (DC2) 13 0013 DEVICE CONTROL THREE (DC3) 14 0014 DEVICE CONTROL FOUR (DC4) 15 0015 NEGATIVE ACKNOWLEDGE (NAK) 16 0016 SYNCRONOUS IDLE (SYN) 17 0017 END OF TRANSMISSION BLOCK (ETB) 18 0018 CANCEL (CAN) 19 0019 END OF MEDIUM (EM) 1A 001a SUBSTITUTE (SUB) 1B 001b ESCAPE (ESC) 1C 001c FILE SEPARATOR (IS4) 1D 001d GROUP SEPARATOR (IS3) 1E 001e RECORD SEPARATOR (IS2) 1F 001f UNIT SEPARATOR (IS1) 20 0020 SPACE 21 0021 EXCLAMATION MARK 22 0022 QUOTATION MARK 23 0023 NUMBER SIGN 24 0024 DOLLAR SIGN 25 0025 PERCENT SIGN 26 0026 AMPERSAND 27 0027 APOSTROPHE 28 0028 LEFT PARENTHESIS 29 0029 RIGHT PARENTHESIS 2A 002a ASTERISK 2B 002b PLUS SIGN 2C 002c COMMA 2D 002d HYPHEN-MINUS 2E 002e FULL STOP 2F 002f SOLIDUS 30 0030 DIGIT ZERO 31 0031 DIGIT ONE 32 0032 DIGIT TWO 33 0033 DIGIT THREE 34 0034 DIGIT FOUR 35 0035 DIGIT FIVE 36 0036 DIGIT SIX 37 0037 DIGIT SEVEN 38 0038 DIGIT EIGHT 39 0039 DIGIT NINE 3A 003a COLON 3B 003b SEMICOLON 3C 003c LESS-THAN SIGN 3D 003d EQUALS SIGN 3E 003e GREATER-THAN SIGN 3F 003f QUESTION MARK 40 0040 COMMERCIAL AT 41 0041 LATIN CAPITAL LETTER A 42 0042 LATIN CAPITAL LETTER B 43 0043 LATIN CAPITAL LETTER C 44 0044 LATIN CAPITAL LETTER D 45 0045 LATIN CAPITAL LETTER E 46 0046 LATIN CAPITAL LETTER F 47 0047 LATIN CAPITAL LETTER G 48 0048 LATIN CAPITAL LETTER H 49 0049 LATIN CAPITAL LETTER I 4A 004a LATIN CAPITAL LETTER J 4B 004b LATIN CAPITAL LETTER K 4C 004c LATIN CAPITAL LETTER L 4D 004d LATIN CAPITAL LETTER M 4E 004e LATIN CAPITAL LETTER N 4F 004f LATIN CAPITAL LETTER O 50 0050 LATIN CAPITAL LETTER P 51 0051 LATIN CAPITAL LETTER Q 52 0052 LATIN CAPITAL LETTER R 53 0053 LATIN CAPITAL LETTER S 54 0054 LATIN CAPITAL LETTER T 55 0055 LATIN CAPITAL LETTER U 56 0056 LATIN CAPITAL LETTER V 57 0057 LATIN CAPITAL LETTER W 58 0058 LATIN CAPITAL LETTER X 59 0059 LATIN CAPITAL LETTER Y 5A 005a LATIN CAPITAL LETTER Z 5B 005b LEFT SQUARE BRACKET 5C 005c REVERSE SOLIDUS 5D 005d RIGHT SQUARE BRACKET 5E 005e CIRCUMFLEX ACCENT 5F 005f LOW LINE 60 0060 GRAVE ACCENT 61 0061 LATIN SMALL LETTER A 62 0062 LATIN SMALL LETTER B 63 0063 LATIN SMALL LETTER C 64 0064 LATIN SMALL LETTER D 65 0065 LATIN SMALL LETTER E 66 0066 LATIN SMALL LETTER F 67 0067 LATIN SMALL LETTER G 68 0068 LATIN SMALL LETTER H 69 0069 LATIN SMALL LETTER I 6A 006a LATIN SMALL LETTER J 6B 006b LATIN SMALL LETTER K 6C 006c LATIN SMALL LETTER L 6D 006d LATIN SMALL LETTER M 6E 006e LATIN SMALL LETTER N 6F 006f LATIN SMALL LETTER O 70 0070 LATIN SMALL LETTER P 71 0071 LATIN SMALL LETTER Q 72 0072 LATIN SMALL LETTER R 73 0073 LATIN SMALL LETTER S 74 0074 LATIN SMALL LETTER T 75 0075 LATIN SMALL LETTER U 76 0076 LATIN SMALL LETTER V 77 0077 LATIN SMALL LETTER W 78 0078 LATIN SMALL LETTER X 79 0079 LATIN SMALL LETTER Y 7A 007a LATIN SMALL LETTER Z 7B 007b LEFT CURLY BRACKET 7C 007c VERTICAL LINE 7D 007d RIGHT CURLY BRACKET 7E 007e TILDE 7F 007f DELETE (DEL) 80 0402 CYRILLIC CAPITAL LETTER DJE 81 0403 CYRILLIC CAPITAL LETTER GJE 82 201A SINGLE LOW-9 QUOTATION MARK 83 0453 CYRILLIC SMALL LETTER GJE 84 201E DOUBLE LOW-9 QUOTATION MARK 85 2026 HORIZONTAL ELLIPSIS 86 2020 DAGGER 87 2021 DOUBLE DAGGER 88 20AC EURO SIGN 89 2030 PER MILLE SIGN 8A 0409 CYRILLIC CAPITAL LETTER LJE 8B 2039 SINGLE LEFT-POINTING ANGLE QUOTATION MARK 8C 040A CYRILLIC CAPITAL LETTER NJE 8D 040C CYRILLIC CAPITAL LETTER KJE 8E 040B CYRILLIC CAPITAL LETTER TSHE 8F 040F CYRILLIC CAPITAL LETTER DZHE 90 0452 CYRILLIC SMALL LETTER DJE 91 2018 LEFT SINGLE QUOTATION MARK 92 2019 RIGHT SINGLE QUOTATION MARK 93 201C LEFT DOUBLE QUOTATION MARK 94 201D RIGHT DOUBLE QUOTATION MARK 95 2022 BULLET 96 2013 EN DASH 97 2014 EM DASH 99 2122 TRADE MARK SIGN 9A 0459 CYRILLIC SMALL LETTER LJE 9B 203A SINGLE RIGHT-POINTING ANGLE QUOTATION MARK 9C 045A CYRILLIC SMALL LETTER NJE 9D 045C CYRILLIC SMALL LETTER KJE 9E 045B CYRILLIC SMALL LETTER TSHE 9F 045F CYRILLIC SMALL LETTER DZHE A0 00A0 NO-BREAK SPACE A1 040E CYRILLIC CAPITAL LETTER SHORT U A2 045E CYRILLIC SMALL LETTER SHORT U A3 0408 CYRILLIC CAPITAL LETTER JE A4 00A4 CURRENCY SIGN A5 0490 CYRILLIC CAPITAL LETTER GHE WITH UPTURN A6 00A6 BROKEN BAR A7 00A7 SECTION SIGN A8 0401 CYRILLIC CAPITAL LETTER IO A9 00A9 COPYRIGHT SIGN AA 0404 CYRILLIC CAPITAL LETTER UKRAINIAN IE AB 00AB LEFT-POINTING DOUBLE ANGLE QUOTATION MARK AC 00AC NOT SIGN AD 00AD SOFT HYPHEN AE 00AE REGISTERED SIGN AF 0407 CYRILLIC CAPITAL LETTER YI B0 00B0 DEGREE SIGN B1 00B1 PLUS-MINUS SIGN B2 0406 CYRILLIC CAPITAL LETTER BYELORUSSIAN-UKRAINIAN I B3 0456 CYRILLIC SMALL LETTER BYELORUSSIAN-UKRAINIAN I B4 0491 CYRILLIC SMALL LETTER GHE WITH UPTURN B5 00B5 MICRO SIGN B6 00B6 PILCROW SIGN B7 00B7 MIDDLE DOT B8 0451 CYRILLIC SMALL LETTER IO B9 2116 NUMERO SIGN BA 0454 CYRILLIC SMALL LETTER UKRAINIAN IE BB 00BB RIGHT-POINTING DOUBLE ANGLE QUOTATION MARK BC 0458 CYRILLIC SMALL LETTER JE BD 0405 CYRILLIC CAPITAL LETTER DZE BE 0455 CYRILLIC SMALL LETTER DZE BF 0457 CYRILLIC SMALL LETTER YI C0 0410 CYRILLIC CAPITAL LETTER A C1 0411 CYRILLIC CAPITAL LETTER BE C2 0412 CYRILLIC CAPITAL LETTER VE C3 0413 CYRILLIC CAPITAL LETTER GHE C4 0414 CYRILLIC CAPITAL LETTER DE C5 0415 CYRILLIC CAPITAL LETTER IE C6 0416 CYRILLIC CAPITAL LETTER ZHE C7 0417 CYRILLIC CAPITAL LETTER ZE C8 0418 CYRILLIC CAPITAL LETTER I C9 0419 CYRILLIC CAPITAL LETTER SHORT I CA 041A CYRILLIC CAPITAL LETTER KA CB 041B CYRILLIC CAPITAL LETTER EL CC 041C CYRILLIC CAPITAL LETTER EM CD 041D CYRILLIC CAPITAL LETTER EN CE 041E CYRILLIC CAPITAL LETTER O CF 041F CYRILLIC CAPITAL LETTER PE D0 0420 CYRILLIC CAPITAL LETTER ER D1 0421 CYRILLIC CAPITAL LETTER ES D2 0422 CYRILLIC CAPITAL LETTER TE D3 0423 CYRILLIC CAPITAL LETTER U D4 0424 CYRILLIC CAPITAL LETTER EF D5 0425 CYRILLIC CAPITAL LETTER HA D6 0426 CYRILLIC CAPITAL LETTER TSE D7 0427 CYRILLIC CAPITAL LETTER CHE D8 0428 CYRILLIC CAPITAL LETTER SHA D9 0429 CYRILLIC CAPITAL LETTER SHCHA DA 042A CYRILLIC CAPITAL LETTER HARD SIGN DB 042B CYRILLIC CAPITAL LETTER YERU DC 042C CYRILLIC CAPITAL LETTER SOFT SIGN DD 042D CYRILLIC CAPITAL LETTER E DE 042E CYRILLIC CAPITAL LETTER YU DF 042F CYRILLIC CAPITAL LETTER YA E0 0430 CYRILLIC SMALL LETTER A E1 0431 CYRILLIC SMALL LETTER BE E2 0432 CYRILLIC SMALL LETTER VE E3 0433 CYRILLIC SMALL LETTER GHE E4 0434 CYRILLIC SMALL LETTER DE E5 0435 CYRILLIC SMALL LETTER IE E6 0436 CYRILLIC SMALL LETTER ZHE E7 0437 CYRILLIC SMALL LETTER ZE E8 0438 CYRILLIC SMALL LETTER I E9 0439 CYRILLIC SMALL LETTER SHORT I EA 043A CYRILLIC SMALL LETTER KA EB 043B CYRILLIC SMALL LETTER EL EC 043C CYRILLIC SMALL LETTER EM ED 043D CYRILLIC SMALL LETTER EN EE 043E CYRILLIC SMALL LETTER O EF 043F CYRILLIC SMALL LETTER PE F0 0440 CYRILLIC SMALL LETTER ER F1 0441 CYRILLIC SMALL LETTER ES F2 0442 CYRILLIC SMALL LETTER TE F3 0443 CYRILLIC SMALL LETTER U F4 0444 CYRILLIC SMALL LETTER EF F5 0445 CYRILLIC SMALL LETTER HA F6 0446 CYRILLIC SMALL LETTER TSE F7 0447 CYRILLIC SMALL LETTER CHE F8 0448 CYRILLIC SMALL LETTER SHA F9 0449 CYRILLIC SMALL LETTER SHCHA FA 044A CYRILLIC SMALL LETTER HARD SIGN FB 044B CYRILLIC SMALL LETTER YERU FC 044C CYRILLIC SMALL LETTER SOFT SIGN FD 044D CYRILLIC SMALL LETTER E FE 044E CYRILLIC SMALL LETTER YU FF 044F CYRILLIC SMALL LETTER YA cyrus-imapd-2.5.10/lib/charset/us-ascii.t0000644000175000017500000001542212772415051015066 00000000000000# # Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. # # Redistribution and use in source and binary forms, with or without # modification, are permitted provided that the following conditions # are met: # # 1. Redistributions of source code must retain the above copyright # notice, this list of conditions and the following disclaimer. # # 2. Redistributions in binary form must reproduce the above copyright # notice, this list of conditions and the following disclaimer in # the documentation and/or other materials provided with the # distribution. # # 3. The name "Carnegie Mellon University" must not be used to # endorse or promote products derived from this software without # prior written permission. For permission or any legal # details, please contact # Carnegie Mellon University # Center for Technology Transfer and Enterprise Creation # 4615 Forbes Avenue # Suite 302 # Pittsburgh, PA 15213 # (412) 268-7393, fax: (412) 268-7395 # innovation@andrew.cmu.edu # # 4. Redistributions of any form whatsoever must retain the following # acknowledgment: # "This product includes software developed by Computing Services # at Carnegie Mellon University (http://www.cmu.edu/computing/)." # # CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO # THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY # AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE # FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES # WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN # AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING # OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. 0 0000 NULL (NUL) 1 0001 START OF HEADING (SOH) 2 0002 START OF TEXT (STX) 3 0003 END OF TEXT (ETX) 4 0004 END OF TRANSMISSION (EOT) 5 0005 ENQUIRY (ENQ) 6 0006 ACKNOWLEDGE (ACK) 7 0007 BELL (BEL) 8 0008 BACKSPACE (BS) 9 0009 CHARACTER TABULATION (HT) A 000a LINE FEED (LF) B 000b LINE TABULATION (VT) C 000c FORM FEED (FF) D 000d CARRIAGE RETURN (CR) E 000e SHIFT OUT (SO) F 000f SHIFT IN (SI) 10 0010 DATALINK ESCAPE (DLE) 11 0011 DEVICE CONTROL ONE (DC1) 12 0012 DEVICE CONTROL TWO (DC2) 13 0013 DEVICE CONTROL THREE (DC3) 14 0014 DEVICE CONTROL FOUR (DC4) 15 0015 NEGATIVE ACKNOWLEDGE (NAK) 16 0016 SYNCRONOUS IDLE (SYN) 17 0017 END OF TRANSMISSION BLOCK (ETB) 18 0018 CANCEL (CAN) 19 0019 END OF MEDIUM (EM) 1A 001a SUBSTITUTE (SUB) 1B 001b ESCAPE (ESC) 1C 001c FILE SEPARATOR (IS4) 1D 001d GROUP SEPARATOR (IS3) 1E 001e RECORD SEPARATOR (IS2) 1F 001f UNIT SEPARATOR (IS1) 20 0020 SPACE 21 0021 EXCLAMATION MARK 22 0022 QUOTATION MARK 23 0023 NUMBER SIGN 24 0024 DOLLAR SIGN 25 0025 PERCENT SIGN 26 0026 AMPERSAND 27 0027 APOSTROPHE 28 0028 LEFT PARENTHESIS 29 0029 RIGHT PARENTHESIS 2A 002a ASTERISK 2B 002b PLUS SIGN 2C 002c COMMA 2D 002d HYPHEN-MINUS 2E 002e FULL STOP 2F 002f SOLIDUS 30 0030 DIGIT ZERO 31 0031 DIGIT ONE 32 0032 DIGIT TWO 33 0033 DIGIT THREE 34 0034 DIGIT FOUR 35 0035 DIGIT FIVE 36 0036 DIGIT SIX 37 0037 DIGIT SEVEN 38 0038 DIGIT EIGHT 39 0039 DIGIT NINE 3A 003a COLON 3B 003b SEMICOLON 3C 003c LESS-THAN SIGN 3D 003d EQUALS SIGN 3E 003e GREATER-THAN SIGN 3F 003f QUESTION MARK 40 0040 COMMERCIAL AT 41 0041 LATIN CAPITAL LETTER A 42 0042 LATIN CAPITAL LETTER B 43 0043 LATIN CAPITAL LETTER C 44 0044 LATIN CAPITAL LETTER D 45 0045 LATIN CAPITAL LETTER E 46 0046 LATIN CAPITAL LETTER F 47 0047 LATIN CAPITAL LETTER G 48 0048 LATIN CAPITAL LETTER H 49 0049 LATIN CAPITAL LETTER I 4A 004a LATIN CAPITAL LETTER J 4B 004b LATIN CAPITAL LETTER K 4C 004c LATIN CAPITAL LETTER L 4D 004d LATIN CAPITAL LETTER M 4E 004e LATIN CAPITAL LETTER N 4F 004f LATIN CAPITAL LETTER O 50 0050 LATIN CAPITAL LETTER P 51 0051 LATIN CAPITAL LETTER Q 52 0052 LATIN CAPITAL LETTER R 53 0053 LATIN CAPITAL LETTER S 54 0054 LATIN CAPITAL LETTER T 55 0055 LATIN CAPITAL LETTER U 56 0056 LATIN CAPITAL LETTER V 57 0057 LATIN CAPITAL LETTER W 58 0058 LATIN CAPITAL LETTER X 59 0059 LATIN CAPITAL LETTER Y 5A 005a LATIN CAPITAL LETTER Z 5B 005b LEFT SQUARE BRACKET 5C 005c REVERSE SOLIDUS 5D 005d RIGHT SQUARE BRACKET 5E 005e CIRCUMFLEX ACCENT 5F 005f LOW LINE 60 0060 GRAVE ACCENT 61 0061 LATIN SMALL LETTER A 62 0062 LATIN SMALL LETTER B 63 0063 LATIN SMALL LETTER C 64 0064 LATIN SMALL LETTER D 65 0065 LATIN SMALL LETTER E 66 0066 LATIN SMALL LETTER F 67 0067 LATIN SMALL LETTER G 68 0068 LATIN SMALL LETTER H 69 0069 LATIN SMALL LETTER I 6A 006a LATIN SMALL LETTER J 6B 006b LATIN SMALL LETTER K 6C 006c LATIN SMALL LETTER L 6D 006d LATIN SMALL LETTER M 6E 006e LATIN SMALL LETTER N 6F 006f LATIN SMALL LETTER O 70 0070 LATIN SMALL LETTER P 71 0071 LATIN SMALL LETTER Q 72 0072 LATIN SMALL LETTER R 73 0073 LATIN SMALL LETTER S 74 0074 LATIN SMALL LETTER T 75 0075 LATIN SMALL LETTER U 76 0076 LATIN SMALL LETTER V 77 0077 LATIN SMALL LETTER W 78 0078 LATIN SMALL LETTER X 79 0079 LATIN SMALL LETTER Y 7A 007a LATIN SMALL LETTER Z 7B 007b LEFT CURLY BRACKET 7C 007c VERTICAL LINE 7D 007d RIGHT CURLY BRACKET 7E 007e TILDE 7F 007f DELETE (DEL) 80 ???? EMPTY 81 ???? EMPTY 82 ???? EMPTY 83 ???? EMPTY 84 ???? EMPTY 85 ???? EMPTY 86 ???? EMPTY 87 ???? EMPTY 88 ???? EMPTY 89 ???? EMPTY 8A ???? EMPTY 8B ???? EMPTY 8C ???? EMPTY 8D ???? EMPTY 8E ???? EMPTY 8F ???? EMPTY 90 ???? EMPTY 91 ???? EMPTY 92 ???? EMPTY 93 ???? EMPTY 94 ???? EMPTY 95 ???? EMPTY 96 ???? EMPTY 97 ???? EMPTY 98 ???? EMPTY 99 ???? EMPTY 9A ???? EMPTY 9B ???? EMPTY 9C ???? EMPTY 9D ???? EMPTY 9E ???? EMPTY 9F ???? EMPTY A0 ???? EMPTY A1 ???? EMPTY A2 ???? EMPTY A3 ???? EMPTY A4 ???? EMPTY A5 ???? EMPTY A6 ???? EMPTY A7 ???? EMPTY A8 ???? EMPTY A9 ???? EMPTY AA ???? EMPTY AB ???? EMPTY AC ???? EMPTY AD ???? EMPTY AE ???? EMPTY AF ???? EMPTY B0 ???? EMPTY B1 ???? EMPTY B2 ???? EMPTY B3 ???? EMPTY B4 ???? EMPTY B5 ???? EMPTY B6 ???? EMPTY B7 ???? EMPTY B8 ???? EMPTY B9 ???? EMPTY BA ???? EMPTY BB ???? EMPTY BC ???? EMPTY BD ???? EMPTY BE ???? EMPTY BF ???? EMPTY C0 ???? EMPTY C1 ???? EMPTY C2 ???? EMPTY C3 ???? EMPTY C4 ???? EMPTY C5 ???? EMPTY C6 ???? EMPTY C7 ???? EMPTY C8 ???? EMPTY C9 ???? EMPTY CA ???? EMPTY CB ???? EMPTY CC ???? EMPTY CD ???? EMPTY CE ???? EMPTY CF ???? EMPTY D0 ???? EMPTY D1 ???? EMPTY D2 ???? EMPTY D3 ???? EMPTY D4 ???? EMPTY D5 ???? EMPTY D6 ???? EMPTY D7 ???? EMPTY D8 ???? EMPTY D9 ???? EMPTY DA ???? EMPTY DB ???? EMPTY DC ???? EMPTY DD ???? EMPTY DE ???? EMPTY DF ???? EMPTY E0 ???? EMPTY E1 ???? EMPTY E2 ???? EMPTY E3 ???? EMPTY E4 ???? EMPTY E5 ???? EMPTY E6 ???? EMPTY E7 ???? EMPTY E8 ???? EMPTY E9 ???? EMPTY EA ???? EMPTY EB ???? EMPTY EC ???? EMPTY ED ???? EMPTY EE ???? EMPTY EF ???? EMPTY F0 ???? EMPTY F1 ???? EMPTY F2 ???? EMPTY F3 ???? EMPTY F4 ???? EMPTY F5 ???? EMPTY F6 ???? EMPTY F7 ???? EMPTY F8 ???? EMPTY F9 ???? EMPTY FA ???? EMPTY FB ???? EMPTY FC ???? EMPTY FD ???? EMPTY FE ???? EMPTY FF ???? EMPTY cyrus-imapd-2.5.10/lib/charset/iso-2022-jp.t0000644000175000017500000037642013001236020015124 00000000000000# # Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. # # Redistribution and use in source and binary forms, with or without # modification, are permitted provided that the following conditions # are met: # # 1. Redistributions of source code must retain the above copyright # notice, this list of conditions and the following disclaimer. # # 2. Redistributions in binary form must reproduce the above copyright # notice, this list of conditions and the following disclaimer in # the documentation and/or other materials provided with the # distribution. # # 3. The name "Carnegie Mellon University" must not be used to # endorse or promote products derived from this software without # prior written permission. For permission or any legal # details, please contact # Carnegie Mellon University # Center for Technology Transfer and Enterprise Creation # 4615 Forbes Avenue # Suite 302 # Pittsburgh, PA 15213 # (412) 268-7393, fax: (412) 268-7395 # innovation@andrew.cmu.edu # # 4. Redistributions of any form whatsoever must retain the following # acknowledgment: # "This product includes software developed by Computing Services # at Carnegie Mellon University (http://www.cmu.edu/computing/)." # # CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO # THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY # AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE # FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES # WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN # AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING # OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. :US-ASCII 0 0000 NULL (NUL) 1 0001 START OF HEADING (SOH) 2 0002 START OF TEXT (STX) 3 0003 END OF TEXT (ETX) 4 0004 END OF TRANSMISSION (EOT) 5 0005 ENQUIRY (ENQ) 6 0006 ACKNOWLEDGE (ACK) 7 0007 BELL (BEL) 8 0008 BACKSPACE (BS) 9 0009 CHARACTER TABULATION (HT) A 000a LINE FEED (LF) B 000b LINE TABULATION (VT) C 000c FORM FEED (FF) D 000d CARRIAGE RETURN (CR) E 000e SHIFT OUT (SO) F 000f SHIFT IN (SI) 10 0010 DATALINK ESCAPE (DLE) 11 0011 DEVICE CONTROL ONE (DC1) 12 0012 DEVICE CONTROL TWO (DC2) 13 0013 DEVICE CONTROL THREE (DC3) 14 0014 DEVICE CONTROL FOUR (DC4) 15 0015 NEGATIVE ACKNOWLEDGE (NAK) 16 0016 SYNCRONOUS IDLE (SYN) 17 0017 END OF TRANSMISSION BLOCK (ETB) 18 0018 CANCEL (CAN) 19 0019 END OF MEDIUM (EM) 1A 001a SUBSTITUTE (SUB) # 1B >ESC 1C 001c FILE SEPARATOR (IS4) 1D 001d GROUP SEPARATOR (IS3) 1E 001e RECORD SEPARATOR (IS2) 1F 001f UNIT SEPARATOR (IS1) 20 0020 SPACE 21 0021 EXCLAMATION MARK 22 0022 QUOTATION MARK 23 0023 NUMBER SIGN 24 0024 DOLLAR SIGN 25 0025 PERCENT SIGN 26 0026 AMPERSAND 27 0027 APOSTROPHE 28 0028 LEFT PARENTHESIS 29 0029 RIGHT PARENTHESIS 2A 002a ASTERISK 2B 002b PLUS SIGN 2C 002c COMMA 2D 002d HYPHEN-MINUS 2E 002e FULL STOP 2F 002f SOLIDUS 30 0030 DIGIT ZERO 31 0031 DIGIT ONE 32 0032 DIGIT TWO 33 0033 DIGIT THREE 34 0034 DIGIT FOUR 35 0035 DIGIT FIVE 36 0036 DIGIT SIX 37 0037 DIGIT SEVEN 38 0038 DIGIT EIGHT 39 0039 DIGIT NINE 3A 003a COLON 3B 003b SEMICOLON 3C 003c LESS-THAN SIGN 3D 003d EQUALS SIGN 3E 003e GREATER-THAN SIGN 3F 003f QUESTION MARK 40 0040 COMMERCIAL AT 41 0041 LATIN CAPITAL LETTER A 42 0042 LATIN CAPITAL LETTER B 43 0043 LATIN CAPITAL LETTER C 44 0044 LATIN CAPITAL LETTER D 45 0045 LATIN CAPITAL LETTER E 46 0046 LATIN CAPITAL LETTER F 47 0047 LATIN CAPITAL LETTER G 48 0048 LATIN CAPITAL LETTER H 49 0049 LATIN CAPITAL LETTER I 4A 004a LATIN CAPITAL LETTER J 4B 004b LATIN CAPITAL LETTER K 4C 004c LATIN CAPITAL LETTER L 4D 004d LATIN CAPITAL LETTER M 4E 004e LATIN CAPITAL LETTER N 4F 004f LATIN CAPITAL LETTER O 50 0050 LATIN CAPITAL LETTER P 51 0051 LATIN CAPITAL LETTER Q 52 0052 LATIN CAPITAL LETTER R 53 0053 LATIN CAPITAL LETTER S 54 0054 LATIN CAPITAL LETTER T 55 0055 LATIN CAPITAL LETTER U 56 0056 LATIN CAPITAL LETTER V 57 0057 LATIN CAPITAL LETTER W 58 0058 LATIN CAPITAL LETTER X 59 0059 LATIN CAPITAL LETTER Y 5A 005a LATIN CAPITAL LETTER Z 5B 005b LEFT SQUARE BRACKET 5C 005c REVERSE SOLIDUS 5D 005d RIGHT SQUARE BRACKET 5E 005e CIRCUMFLEX ACCENT 5F 005f LOW LINE 60 0060 GRAVE ACCENT 61 0061 LATIN SMALL LETTER A 62 0062 LATIN SMALL LETTER B 63 0063 LATIN SMALL LETTER C 64 0064 LATIN SMALL LETTER D 65 0065 LATIN SMALL LETTER E 66 0066 LATIN SMALL LETTER F 67 0067 LATIN SMALL LETTER G 68 0068 LATIN SMALL LETTER H 69 0069 LATIN SMALL LETTER I 6A 006a LATIN SMALL LETTER J 6B 006b LATIN SMALL LETTER K 6C 006c LATIN SMALL LETTER L 6D 006d LATIN SMALL LETTER M 6E 006e LATIN SMALL LETTER N 6F 006f LATIN SMALL LETTER O 70 0070 LATIN SMALL LETTER P 71 0071 LATIN SMALL LETTER Q 72 0072 LATIN SMALL LETTER R 73 0073 LATIN SMALL LETTER S 74 0074 LATIN SMALL LETTER T 75 0075 LATIN SMALL LETTER U 76 0076 LATIN SMALL LETTER V 77 0077 LATIN SMALL LETTER W 78 0078 LATIN SMALL LETTER X 79 0079 LATIN SMALL LETTER Y 7A 007a LATIN SMALL LETTER Z 7B 007b LEFT CURLY BRACKET 7C 007c VERTICAL LINE 7D 007d RIGHT CURLY BRACKET 7E 007e TILDE 7F 007f DELETE (DEL) # ESCAPE CODES 1B2440 :JIS-0208 ESC-$-@ 1B2442 :JIS-0208 ESC-$-B 1B2842 :US-ASCII ESC-(-B 1B284A :JIS-0201 ESC-(-J :JIS-0201 0 0000 NULL (NUL) 1 0001 START OF HEADING (SOH) 2 0002 START OF TEXT (STX) 3 0003 END OF TEXT (ETX) 4 0004 END OF TRANSMISSION (EOT) 5 0005 ENQUIRY (ENQ) 6 0006 ACKNOWLEDGE (ACK) 7 0007 BELL (BEL) 8 0008 BACKSPACE (BS) 9 0009 CHARACTER TABULATION (HT) A 000a LINE FEED (LF) B 000b LINE TABULATION (VT) C 000c FORM FEED (FF) D 000d CARRIAGE RETURN (CR) E 000e SHIFT OUT (SO) F 000f SHIFT IN (SI) 10 0010 DATALINK ESCAPE (DLE) 11 0011 DEVICE CONTROL ONE (DC1) 12 0012 DEVICE CONTROL TWO (DC2) 13 0013 DEVICE CONTROL THREE (DC3) 14 0014 DEVICE CONTROL FOUR (DC4) 15 0015 NEGATIVE ACKNOWLEDGE (NAK) 16 0016 SYNCRONOUS IDLE (SYN) 17 0017 END OF TRANSMISSION BLOCK (ETB) 18 0018 CANCEL (CAN) 19 0019 END OF MEDIUM (EM) 1A 001a SUBSTITUTE (SUB) # 1B >ESC 1C 001c FILE SEPARATOR (IS4) 1D 001d GROUP SEPARATOR (IS3) 1E 001e RECORD SEPARATOR (IS2) 1F 001f UNIT SEPARATOR (IS1) 20 0020 SPACE 21 0021 EXCLAMATION MARK 22 0022 QUOTATION MARK 23 0023 NUMBER SIGN 24 0024 DOLLAR SIGN 25 0025 PERCENT SIGN 26 0026 AMPERSAND 27 0027 APOSTROPHE 28 0028 LEFT PARENTHESIS 29 0029 RIGHT PARENTHESIS 2A 002A ASTERISK 2B 002B PLUS SIGN 2C 002C COMMA 2D 002D HYPHEN-MINUS 2E 002E FULL STOP 2F 002F SOLIDUS 30 0030 DIGIT ZERO 31 0031 DIGIT ONE 32 0032 DIGIT TWO 33 0033 DIGIT THREE 34 0034 DIGIT FOUR 35 0035 DIGIT FIVE 36 0036 DIGIT SIX 37 0037 DIGIT SEVEN 38 0038 DIGIT EIGHT 39 0039 DIGIT NINE 3A 003A COLON 3B 003B SEMICOLON 3C 003C LESS-THAN SIGN 3D 003D EQUALS SIGN 3E 003E GREATER-THAN SIGN 3F 003F QUESTION MARK 40 0040 COMMERCIAL AT 41 0041 LATIN CAPITAL LETTER A 42 0042 LATIN CAPITAL LETTER B 43 0043 LATIN CAPITAL LETTER C 44 0044 LATIN CAPITAL LETTER D 45 0045 LATIN CAPITAL LETTER E 46 0046 LATIN CAPITAL LETTER F 47 0047 LATIN CAPITAL LETTER G 48 0048 LATIN CAPITAL LETTER H 49 0049 LATIN CAPITAL LETTER I 4A 004A LATIN CAPITAL LETTER J 4B 004B LATIN CAPITAL LETTER K 4C 004C LATIN CAPITAL LETTER L 4D 004D LATIN CAPITAL LETTER M 4E 004E LATIN CAPITAL LETTER N 4F 004F LATIN CAPITAL LETTER O 50 0050 LATIN CAPITAL LETTER P 51 0051 LATIN CAPITAL LETTER Q 52 0052 LATIN CAPITAL LETTER R 53 0053 LATIN CAPITAL LETTER S 54 0054 LATIN CAPITAL LETTER T 55 0055 LATIN CAPITAL LETTER U 56 0056 LATIN CAPITAL LETTER V 57 0057 LATIN CAPITAL LETTER W 58 0058 LATIN CAPITAL LETTER X 59 0059 LATIN CAPITAL LETTER Y 5A 005A LATIN CAPITAL LETTER Z 5B 005B LEFT SQUARE BRACKET 5C 00A5 YEN SIGN 5D 005D RIGHT SQUARE BRACKET 5E 005E CIRCUMFLEX ACCENT 5F 005F LOW LINE 60 0060 GRAVE ACCENT 61 0061 LATIN SMALL LETTER A 62 0062 LATIN SMALL LETTER B 63 0063 LATIN SMALL LETTER C 64 0064 LATIN SMALL LETTER D 65 0065 LATIN SMALL LETTER E 66 0066 LATIN SMALL LETTER F 67 0067 LATIN SMALL LETTER G 68 0068 LATIN SMALL LETTER H 69 0069 LATIN SMALL LETTER I 6A 006A LATIN SMALL LETTER J 6B 006B LATIN SMALL LETTER K 6C 006C LATIN SMALL LETTER L 6D 006D LATIN SMALL LETTER M 6E 006E LATIN SMALL LETTER N 6F 006F LATIN SMALL LETTER O 70 0070 LATIN SMALL LETTER P 71 0071 LATIN SMALL LETTER Q 72 0072 LATIN SMALL LETTER R 73 0073 LATIN SMALL LETTER S 74 0074 LATIN SMALL LETTER T 75 0075 LATIN SMALL LETTER U 76 0076 LATIN SMALL LETTER V 77 0077 LATIN SMALL LETTER W 78 0078 LATIN SMALL LETTER X 79 0079 LATIN SMALL LETTER Y 7A 007A LATIN SMALL LETTER Z 7B 007B LEFT CURLY BRACKET 7C 007C VERTICAL LINE 7D 007D RIGHT CURLY BRACKET 7E 203E OVERLINE 7F 007f DELETE (DEL) A0 3000 IDEOGRAPHIC SPACE A1 FF61 HALFWIDTH IDEOGRAPHIC FULL STOP A2 FF62 HALFWIDTH LEFT CORNER BRACKET A3 FF63 HALFWIDTH RIGHT CORNER BRACKET A4 FF64 HALFWIDTH IDEOGRAPHIC COMMA A5 FF65 HALFWIDTH KATAKANA MIDDLE DOT A6 FF66 HALFWIDTH KATAKANA LETTER WO A7 FF67 HALFWIDTH KATAKANA LETTER SMALL A A8 FF68 HALFWIDTH KATAKANA LETTER SMALL I A9 FF69 HALFWIDTH KATAKANA LETTER SMALL U AA FF6A HALFWIDTH KATAKANA LETTER SMALL E AB FF6B HALFWIDTH KATAKANA LETTER SMALL O AC FF6C HALFWIDTH KATAKANA LETTER SMALL YA AD FF6D HALFWIDTH KATAKANA LETTER SMALL YU AE FF6E HALFWIDTH KATAKANA LETTER SMALL YO AF FF6F HALFWIDTH KATAKANA LETTER SMALL TU B0 FF70 HALFWIDTH KATAKANA-HIRAGANA PROLONGED SOUND MARK B1 FF71 HALFWIDTH KATAKANA LETTER A B2 FF72 HALFWIDTH KATAKANA LETTER I B3 FF73 HALFWIDTH KATAKANA LETTER U B4 FF74 HALFWIDTH KATAKANA LETTER E B5 FF75 HALFWIDTH KATAKANA LETTER O B6 FF76 HALFWIDTH KATAKANA LETTER KA B7 FF77 HALFWIDTH KATAKANA LETTER KI B8 FF78 HALFWIDTH KATAKANA LETTER KU B9 FF79 HALFWIDTH KATAKANA LETTER KE BA FF7A HALFWIDTH KATAKANA LETTER KO BB FF7B HALFWIDTH KATAKANA LETTER SA BC FF7C HALFWIDTH KATAKANA LETTER SI BD FF7D HALFWIDTH KATAKANA LETTER SU BE FF7E HALFWIDTH KATAKANA LETTER SE BF FF7F HALFWIDTH KATAKANA LETTER SO C0 FF80 HALFWIDTH KATAKANA LETTER TA C1 FF81 HALFWIDTH KATAKANA LETTER TI C2 FF82 HALFWIDTH KATAKANA LETTER TU C3 FF83 HALFWIDTH KATAKANA LETTER TE C4 FF84 HALFWIDTH KATAKANA LETTER TO C5 FF85 HALFWIDTH KATAKANA LETTER NA C6 FF86 HALFWIDTH KATAKANA LETTER NI C7 FF87 HALFWIDTH KATAKANA LETTER NU C8 FF88 HALFWIDTH KATAKANA LETTER NE C9 FF89 HALFWIDTH KATAKANA LETTER NO CA FF8A HALFWIDTH KATAKANA LETTER HA CB FF8B HALFWIDTH KATAKANA LETTER HI CC FF8C HALFWIDTH KATAKANA LETTER HU CD FF8D HALFWIDTH KATAKANA LETTER HE CE FF8E HALFWIDTH KATAKANA LETTER HO CF FF8F HALFWIDTH KATAKANA LETTER MA D0 FF90 HALFWIDTH KATAKANA LETTER MI D1 FF91 HALFWIDTH KATAKANA LETTER MU D2 FF92 HALFWIDTH KATAKANA LETTER ME D3 FF93 HALFWIDTH KATAKANA LETTER MO D4 FF94 HALFWIDTH KATAKANA LETTER YA D5 FF95 HALFWIDTH KATAKANA LETTER YU D6 FF96 HALFWIDTH KATAKANA LETTER YO D7 FF97 HALFWIDTH KATAKANA LETTER RA D8 FF98 HALFWIDTH KATAKANA LETTER RI D9 FF99 HALFWIDTH KATAKANA LETTER RU DA FF9A HALFWIDTH KATAKANA LETTER RE DB FF9B HALFWIDTH KATAKANA LETTER RO DC FF9C HALFWIDTH KATAKANA LETTER WA DD FF9D HALFWIDTH KATAKANA LETTER N DE FF9E HALFWIDTH KATAKANA VOICED SOUND MARK DF FF9F HALFWIDTH KATAKANA SEMI-VOICED SOUND MARK # ESCAPE CODES 1B2440 :JIS-0208 ESC-$-@ 1B2442 :JIS-0208 ESC-$-B 1B2842 :US-ASCII ESC-(-B 1B284A :JIS-0201 ESC-(-J :JIS-0208 2121 3000 IDEOGRAPHIC SPACE 2122 3001 IDEOGRAPHIC COMMA 2123 3002 IDEOGRAPHIC FULL STOP 2124 FF0C FULLWIDTH COMMA 2125 FF0E FULLWIDTH FULL STOP 2126 30FB KATAKANA MIDDLE DOT 2127 FF1A FULLWIDTH COLON 2128 FF1B FULLWIDTH SEMICOLON 2129 FF1F FULLWIDTH QUESTION MARK 212A FF01 FULLWIDTH EXCLAMATION MARK 212B 309B KATAKANA-HIRAGANA VOICED SOUND MARK 212C 309C KATAKANA-HIRAGANA SEMI-VOICED SOUND MARK 212D 00B4 ACUTE ACCENT 212E FF40 FULLWIDTH GRAVE ACCENT 212F 00A8 DIAERESIS 2130 FF3E FULLWIDTH CIRCUMFLEX ACCENT 2131 FFE3 FULLWIDTH MACRON 2132 FF3F FULLWIDTH LOW LINE 2133 30FD KATAKANA ITERATION MARK 2134 30FE KATAKANA VOICED ITERATION MARK 2135 309D HIRAGANA ITERATION MARK 2136 309E HIRAGANA VOICED ITERATION MARK 2137 3003 DITTO MARK 2138 4EDD 2139 3005 IDEOGRAPHIC ITERATION MARK 213A 3006 IDEOGRAPHIC CLOSING MARK 213B 3007 IDEOGRAPHIC NUMBER ZERO 213C 30FC KATAKANA-HIRAGANA PROLONGED SOUND MARK 213D 2015 HORIZONTAL BAR 213E 2010 HYPHEN 213F FF0F FULLWIDTH SOLIDUS 2140 005C REVERSE SOLIDUS 2141 301C WAVE DASH 2142 2016 DOUBLE VERTICAL LINE 2143 FF5C FULLWIDTH VERTICAL LINE 2144 2026 HORIZONTAL ELLIPSIS 2145 2025 TWO DOT LEADER 2146 2018 LEFT SINGLE QUOTATION MARK 2147 2019 RIGHT SINGLE QUOTATION MARK 2148 201C LEFT DOUBLE QUOTATION MARK 2149 201D RIGHT DOUBLE QUOTATION MARK 214A FF08 FULLWIDTH LEFT PARENTHESIS 214B FF09 FULLWIDTH RIGHT PARENTHESIS 214C 3014 LEFT TORTOISE SHELL BRACKET 214D 3015 RIGHT TORTOISE SHELL BRACKET 214E FF3B FULLWIDTH LEFT SQUARE BRACKET 214F FF3D FULLWIDTH RIGHT SQUARE BRACKET 2150 FF5B FULLWIDTH LEFT CURLY BRACKET 2151 FF5D FULLWIDTH RIGHT CURLY BRACKET 2152 3008 LEFT ANGLE BRACKET 2153 3009 RIGHT ANGLE BRACKET 2154 300A LEFT DOUBLE ANGLE BRACKET 2155 300B RIGHT DOUBLE ANGLE BRACKET 2156 300C LEFT CORNER BRACKET 2157 300D RIGHT CORNER BRACKET 2158 300E LEFT WHITE CORNER BRACKET 2159 300F RIGHT WHITE CORNER BRACKET 215A 3010 LEFT BLACK LENTICULAR BRACKET 215B 3011 RIGHT BLACK LENTICULAR BRACKET 215C FF0B FULLWIDTH PLUS SIGN 215D 2212 MINUS SIGN 215E 00B1 PLUS-MINUS SIGN 215F 00D7 MULTIPLICATION SIGN 2160 00F7 DIVISION SIGN 2161 FF1D FULLWIDTH EQUALS SIGN 2162 2260 NOT EQUAL TO 2163 FF1C FULLWIDTH LESS-THAN SIGN 2164 FF1E FULLWIDTH GREATER-THAN SIGN 2165 2266 LESS-THAN OVER EQUAL TO 2166 2267 GREATER-THAN OVER EQUAL TO 2167 221E INFINITY 2168 2234 THEREFORE 2169 2642 MALE SIGN 216A 2640 FEMALE SIGN 216B 00B0 DEGREE SIGN 216C 2032 PRIME 216D 2033 DOUBLE PRIME 216E 2103 DEGREE CELSIUS 216F FFE5 FULLWIDTH YEN SIGN 2170 FF04 FULLWIDTH DOLLAR SIGN 2171 00A2 CENT SIGN 2172 00A3 POUND SIGN 2173 FF05 FULLWIDTH PERCENT SIGN 2174 FF03 FULLWIDTH NUMBER SIGN 2175 FF06 FULLWIDTH AMPERSAND 2176 FF0A FULLWIDTH ASTERISK 2177 FF20 FULLWIDTH COMMERCIAL AT 2178 00A7 SECTION SIGN 2179 2606 WHITE STAR 217A 2605 BLACK STAR 217B 25CB WHITE CIRCLE 217C 25CF BLACK CIRCLE 217D 25CE BULLSEYE 217E 25C7 WHITE DIAMOND 2221 25C6 BLACK DIAMOND 2222 25A1 WHITE SQUARE 2223 25A0 BLACK SQUARE 2224 25B3 WHITE UP-POINTING TRIANGLE 2225 25B2 BLACK UP-POINTING TRIANGLE 2226 25BD WHITE DOWN-POINTING TRIANGLE 2227 25BC BLACK DOWN-POINTING TRIANGLE 2228 203B REFERENCE MARK 2229 3012 POSTAL MARK 222A 2192 RIGHTWARDS ARROW 222B 2190 LEFTWARDS ARROW 222C 2191 UPWARDS ARROW 222D 2193 DOWNWARDS ARROW 222E 3013 GETA MARK 223A 2208 ELEMENT OF 223B 220B CONTAINS AS MEMBER 223C 2286 SUBSET OF OR EQUAL TO 223D 2287 SUPERSET OF OR EQUAL TO 223E 2282 SUBSET OF 223F 2283 SUPERSET OF 2240 222A UNION 2241 2229 INTERSECTION 224A 2227 LOGICAL AND 224B 2228 LOGICAL OR 224C 00AC NOT SIGN 224D 21D2 RIGHTWARDS DOUBLE ARROW 224E 21D4 LEFT RIGHT DOUBLE ARROW 224F 2200 FOR ALL 2250 2203 THERE EXISTS 225C 2220 ANGLE 225D 22A5 UP TACK 225E 2312 ARC 225F 2202 PARTIAL DIFFERENTIAL 2260 2207 NABLA 2261 2261 IDENTICAL TO 2262 2252 APPROXIMATELY EQUAL TO OR THE IMAGE OF 2263 226A MUCH LESS-THAN 2264 226B MUCH GREATER-THAN 2265 221A SQUARE ROOT 2266 223D REVERSED TILDE 2267 221D PROPORTIONAL TO 2268 2235 BECAUSE 2269 222B INTEGRAL 226A 222C DOUBLE INTEGRAL 2272 212B ANGSTROM SIGN 2273 2030 PER MILLE SIGN 2274 266F MUSIC SHARP SIGN 2275 266D MUSIC FLAT SIGN 2276 266A EIGHTH NOTE 2277 2020 DAGGER 2278 2021 DOUBLE DAGGER 2279 00B6 PILCROW SIGN 227E 25EF LARGE CIRCLE 2330 FF10 FULLWIDTH DIGIT ZERO 2331 FF11 FULLWIDTH DIGIT ONE 2332 FF12 FULLWIDTH DIGIT TWO 2333 FF13 FULLWIDTH DIGIT THREE 2334 FF14 FULLWIDTH DIGIT FOUR 2335 FF15 FULLWIDTH DIGIT FIVE 2336 FF16 FULLWIDTH DIGIT SIX 2337 FF17 FULLWIDTH DIGIT SEVEN 2338 FF18 FULLWIDTH DIGIT EIGHT 2339 FF19 FULLWIDTH DIGIT NINE 2341 FF21 FULLWIDTH LATIN CAPITAL LETTER A 2342 FF22 FULLWIDTH LATIN CAPITAL LETTER B 2343 FF23 FULLWIDTH LATIN CAPITAL LETTER C 2344 FF24 FULLWIDTH LATIN CAPITAL LETTER D 2345 FF25 FULLWIDTH LATIN CAPITAL LETTER E 2346 FF26 FULLWIDTH LATIN CAPITAL LETTER F 2347 FF27 FULLWIDTH LATIN CAPITAL LETTER G 2348 FF28 FULLWIDTH LATIN CAPITAL LETTER H 2349 FF29 FULLWIDTH LATIN CAPITAL LETTER I 234A FF2A FULLWIDTH LATIN CAPITAL LETTER J 234B FF2B FULLWIDTH LATIN CAPITAL LETTER K 234C FF2C FULLWIDTH LATIN CAPITAL LETTER L 234D FF2D FULLWIDTH LATIN CAPITAL LETTER M 234E FF2E FULLWIDTH LATIN CAPITAL LETTER N 234F FF2F FULLWIDTH LATIN CAPITAL LETTER O 2350 FF30 FULLWIDTH LATIN CAPITAL LETTER P 2351 FF31 FULLWIDTH LATIN CAPITAL LETTER Q 2352 FF32 FULLWIDTH LATIN CAPITAL LETTER R 2353 FF33 FULLWIDTH LATIN CAPITAL LETTER S 2354 FF34 FULLWIDTH LATIN CAPITAL LETTER T 2355 FF35 FULLWIDTH LATIN CAPITAL LETTER U 2356 FF36 FULLWIDTH LATIN CAPITAL LETTER V 2357 FF37 FULLWIDTH LATIN CAPITAL LETTER W 2358 FF38 FULLWIDTH LATIN CAPITAL LETTER X 2359 FF39 FULLWIDTH LATIN CAPITAL LETTER Y 235A FF3A FULLWIDTH LATIN CAPITAL LETTER Z 2361 FF41 FULLWIDTH LATIN SMALL LETTER A 2362 FF42 FULLWIDTH LATIN SMALL LETTER B 2363 FF43 FULLWIDTH LATIN SMALL LETTER C 2364 FF44 FULLWIDTH LATIN SMALL LETTER D 2365 FF45 FULLWIDTH LATIN SMALL LETTER E 2366 FF46 FULLWIDTH LATIN SMALL LETTER F 2367 FF47 FULLWIDTH LATIN SMALL LETTER G 2368 FF48 FULLWIDTH LATIN SMALL LETTER H 2369 FF49 FULLWIDTH LATIN SMALL LETTER I 236A FF4A FULLWIDTH LATIN SMALL LETTER J 236B FF4B FULLWIDTH LATIN SMALL LETTER K 236C FF4C FULLWIDTH LATIN SMALL LETTER L 236D FF4D FULLWIDTH LATIN SMALL LETTER M 236E FF4E FULLWIDTH LATIN SMALL LETTER N 236F FF4F FULLWIDTH LATIN SMALL LETTER O 2370 FF50 FULLWIDTH LATIN SMALL LETTER P 2371 FF51 FULLWIDTH LATIN SMALL LETTER Q 2372 FF52 FULLWIDTH LATIN SMALL LETTER R 2373 FF53 FULLWIDTH LATIN SMALL LETTER S 2374 FF54 FULLWIDTH LATIN SMALL LETTER T 2375 FF55 FULLWIDTH LATIN SMALL LETTER U 2376 FF56 FULLWIDTH LATIN SMALL LETTER V 2377 FF57 FULLWIDTH LATIN SMALL LETTER W 2378 FF58 FULLWIDTH LATIN SMALL LETTER X 2379 FF59 FULLWIDTH LATIN SMALL LETTER Y 237A FF5A FULLWIDTH LATIN SMALL LETTER Z 2421 3041 HIRAGANA LETTER SMALL A 2422 3042 HIRAGANA LETTER A 2423 3043 HIRAGANA LETTER SMALL I 2424 3044 HIRAGANA LETTER I 2425 3045 HIRAGANA LETTER SMALL U 2426 3046 HIRAGANA LETTER U 2427 3047 HIRAGANA LETTER SMALL E 2428 3048 HIRAGANA LETTER E 2429 3049 HIRAGANA LETTER SMALL O 242A 304A HIRAGANA LETTER O 242B 304B HIRAGANA LETTER KA 242C 304C HIRAGANA LETTER GA 242D 304D HIRAGANA LETTER KI 242E 304E HIRAGANA LETTER GI 242F 304F HIRAGANA LETTER KU 2430 3050 HIRAGANA LETTER GU 2431 3051 HIRAGANA LETTER KE 2432 3052 HIRAGANA LETTER GE 2433 3053 HIRAGANA LETTER KO 2434 3054 HIRAGANA LETTER GO 2435 3055 HIRAGANA LETTER SA 2436 3056 HIRAGANA LETTER ZA 2437 3057 HIRAGANA LETTER SI 2438 3058 HIRAGANA LETTER ZI 2439 3059 HIRAGANA LETTER SU 243A 305A HIRAGANA LETTER ZU 243B 305B HIRAGANA LETTER SE 243C 305C HIRAGANA LETTER ZE 243D 305D HIRAGANA LETTER SO 243E 305E HIRAGANA LETTER ZO 243F 305F HIRAGANA LETTER TA 2440 3060 HIRAGANA LETTER DA 2441 3061 HIRAGANA LETTER TI 2442 3062 HIRAGANA LETTER DI 2443 3063 HIRAGANA LETTER SMALL TU 2444 3064 HIRAGANA LETTER TU 2445 3065 HIRAGANA LETTER DU 2446 3066 HIRAGANA LETTER TE 2447 3067 HIRAGANA LETTER DE 2448 3068 HIRAGANA LETTER TO 2449 3069 HIRAGANA LETTER DO 244A 306A HIRAGANA LETTER NA 244B 306B HIRAGANA LETTER NI 244C 306C HIRAGANA LETTER NU 244D 306D HIRAGANA LETTER NE 244E 306E HIRAGANA LETTER NO 244F 306F HIRAGANA LETTER HA 2450 3070 HIRAGANA LETTER BA 2451 3071 HIRAGANA LETTER PA 2452 3072 HIRAGANA LETTER HI 2453 3073 HIRAGANA LETTER BI 2454 3074 HIRAGANA LETTER PI 2455 3075 HIRAGANA LETTER HU 2456 3076 HIRAGANA LETTER BU 2457 3077 HIRAGANA LETTER PU 2458 3078 HIRAGANA LETTER HE 2459 3079 HIRAGANA LETTER BE 245A 307A HIRAGANA LETTER PE 245B 307B HIRAGANA LETTER HO 245C 307C HIRAGANA LETTER BO 245D 307D HIRAGANA LETTER PO 245E 307E HIRAGANA LETTER MA 245F 307F HIRAGANA LETTER MI 2460 3080 HIRAGANA LETTER MU 2461 3081 HIRAGANA LETTER ME 2462 3082 HIRAGANA LETTER MO 2463 3083 HIRAGANA LETTER SMALL YA 2464 3084 HIRAGANA LETTER YA 2465 3085 HIRAGANA LETTER SMALL YU 2466 3086 HIRAGANA LETTER YU 2467 3087 HIRAGANA LETTER SMALL YO 2468 3088 HIRAGANA LETTER YO 2469 3089 HIRAGANA LETTER RA 246A 308A HIRAGANA LETTER RI 246B 308B HIRAGANA LETTER RU 246C 308C HIRAGANA LETTER RE 246D 308D HIRAGANA LETTER RO 246E 308E HIRAGANA LETTER SMALL WA 246F 308F HIRAGANA LETTER WA 2470 3090 HIRAGANA LETTER WI 2471 3091 HIRAGANA LETTER WE 2472 3092 HIRAGANA LETTER WO 2473 3093 HIRAGANA LETTER N 2521 30A1 KATAKANA LETTER SMALL A 2522 30A2 KATAKANA LETTER A 2523 30A3 KATAKANA LETTER SMALL I 2524 30A4 KATAKANA LETTER I 2525 30A5 KATAKANA LETTER SMALL U 2526 30A6 KATAKANA LETTER U 2527 30A7 KATAKANA LETTER SMALL E 2528 30A8 KATAKANA LETTER E 2529 30A9 KATAKANA LETTER SMALL O 252A 30AA KATAKANA LETTER O 252B 30AB KATAKANA LETTER KA 252C 30AC KATAKANA LETTER GA 252D 30AD KATAKANA LETTER KI 252E 30AE KATAKANA LETTER GI 252F 30AF KATAKANA LETTER KU 2530 30B0 KATAKANA LETTER GU 2531 30B1 KATAKANA LETTER KE 2532 30B2 KATAKANA LETTER GE 2533 30B3 KATAKANA LETTER KO 2534 30B4 KATAKANA LETTER GO 2535 30B5 KATAKANA LETTER SA 2536 30B6 KATAKANA LETTER ZA 2537 30B7 KATAKANA LETTER SI 2538 30B8 KATAKANA LETTER ZI 2539 30B9 KATAKANA LETTER SU 253A 30BA KATAKANA LETTER ZU 253B 30BB KATAKANA LETTER SE 253C 30BC KATAKANA LETTER ZE 253D 30BD KATAKANA LETTER SO 253E 30BE KATAKANA LETTER ZO 253F 30BF KATAKANA LETTER TA 2540 30C0 KATAKANA LETTER DA 2541 30C1 KATAKANA LETTER TI 2542 30C2 KATAKANA LETTER DI 2543 30C3 KATAKANA LETTER SMALL TU 2544 30C4 KATAKANA LETTER TU 2545 30C5 KATAKANA LETTER DU 2546 30C6 KATAKANA LETTER TE 2547 30C7 KATAKANA LETTER DE 2548 30C8 KATAKANA LETTER TO 2549 30C9 KATAKANA LETTER DO 254A 30CA KATAKANA LETTER NA 254B 30CB KATAKANA LETTER NI 254C 30CC KATAKANA LETTER NU 254D 30CD KATAKANA LETTER NE 254E 30CE KATAKANA LETTER NO 254F 30CF KATAKANA LETTER HA 2550 30D0 KATAKANA LETTER BA 2551 30D1 KATAKANA LETTER PA 2552 30D2 KATAKANA LETTER HI 2553 30D3 KATAKANA LETTER BI 2554 30D4 KATAKANA LETTER PI 2555 30D5 KATAKANA LETTER HU 2556 30D6 KATAKANA LETTER BU 2557 30D7 KATAKANA LETTER PU 2558 30D8 KATAKANA LETTER HE 2559 30D9 KATAKANA LETTER BE 255A 30DA KATAKANA LETTER PE 255B 30DB KATAKANA LETTER HO 255C 30DC KATAKANA LETTER BO 255D 30DD KATAKANA LETTER PO 255E 30DE KATAKANA LETTER MA 255F 30DF KATAKANA LETTER MI 2560 30E0 KATAKANA LETTER MU 2561 30E1 KATAKANA LETTER ME 2562 30E2 KATAKANA LETTER MO 2563 30E3 KATAKANA LETTER SMALL YA 2564 30E4 KATAKANA LETTER YA 2565 30E5 KATAKANA LETTER SMALL YU 2566 30E6 KATAKANA LETTER YU 2567 30E7 KATAKANA LETTER SMALL YO 2568 30E8 KATAKANA LETTER YO 2569 30E9 KATAKANA LETTER RA 256A 30EA KATAKANA LETTER RI 256B 30EB KATAKANA LETTER RU 256C 30EC KATAKANA LETTER RE 256D 30ED KATAKANA LETTER RO 256E 30EE KATAKANA LETTER SMALL WA 256F 30EF KATAKANA LETTER WA 2570 30F0 KATAKANA LETTER WI 2571 30F1 KATAKANA LETTER WE 2572 30F2 KATAKANA LETTER WO 2573 30F3 KATAKANA LETTER N 2574 30F4 KATAKANA LETTER VU 2575 30F5 KATAKANA LETTER SMALL KA 2576 30F6 KATAKANA LETTER SMALL KE 2621 0391 GREEK CAPITAL LETTER ALPHA 2622 0392 GREEK CAPITAL LETTER BETA 2623 0393 GREEK CAPITAL LETTER GAMMA 2624 0394 GREEK CAPITAL LETTER DELTA 2625 0395 GREEK CAPITAL LETTER EPSILON 2626 0396 GREEK CAPITAL LETTER ZETA 2627 0397 GREEK CAPITAL LETTER ETA 2628 0398 GREEK CAPITAL LETTER THETA 2629 0399 GREEK CAPITAL LETTER IOTA 262A 039A GREEK CAPITAL LETTER KAPPA 262B 039B GREEK CAPITAL LETTER LAMDA 262C 039C GREEK CAPITAL LETTER MU 262D 039D GREEK CAPITAL LETTER NU 262E 039E GREEK CAPITAL LETTER XI 262F 039F GREEK CAPITAL LETTER OMICRON 2630 03A0 GREEK CAPITAL LETTER PI 2631 03A1 GREEK CAPITAL LETTER RHO 2632 03A3 GREEK CAPITAL LETTER SIGMA 2633 03A4 GREEK CAPITAL LETTER TAU 2634 03A5 GREEK CAPITAL LETTER UPSILON 2635 03A6 GREEK CAPITAL LETTER PHI 2636 03A7 GREEK CAPITAL LETTER CHI 2637 03A8 GREEK CAPITAL LETTER PSI 2638 03A9 GREEK CAPITAL LETTER OMEGA 2641 03B1 GREEK SMALL LETTER ALPHA 2642 03B2 GREEK SMALL LETTER BETA 2643 03B3 GREEK SMALL LETTER GAMMA 2644 03B4 GREEK SMALL LETTER DELTA 2645 03B5 GREEK SMALL LETTER EPSILON 2646 03B6 GREEK SMALL LETTER ZETA 2647 03B7 GREEK SMALL LETTER ETA 2648 03B8 GREEK SMALL LETTER THETA 2649 03B9 GREEK SMALL LETTER IOTA 264A 03BA GREEK SMALL LETTER KAPPA 264B 03BB GREEK SMALL LETTER LAMDA 264C 03BC GREEK SMALL LETTER MU 264D 03BD GREEK SMALL LETTER NU 264E 03BE GREEK SMALL LETTER XI 264F 03BF GREEK SMALL LETTER OMICRON 2650 03C0 GREEK SMALL LETTER PI 2651 03C1 GREEK SMALL LETTER RHO 2652 03C3 GREEK SMALL LETTER SIGMA 2653 03C4 GREEK SMALL LETTER TAU 2654 03C5 GREEK SMALL LETTER UPSILON 2655 03C6 GREEK SMALL LETTER PHI 2656 03C7 GREEK SMALL LETTER CHI 2657 03C8 GREEK SMALL LETTER PSI 2658 03C9 GREEK SMALL LETTER OMEGA 2721 0410 CYRILLIC CAPITAL LETTER A 2722 0411 CYRILLIC CAPITAL LETTER BE 2723 0412 CYRILLIC CAPITAL LETTER VE 2724 0413 CYRILLIC CAPITAL LETTER GHE 2725 0414 CYRILLIC CAPITAL LETTER DE 2726 0415 CYRILLIC CAPITAL LETTER IE 2727 0401 CYRILLIC CAPITAL LETTER IO 2728 0416 CYRILLIC CAPITAL LETTER ZHE 2729 0417 CYRILLIC CAPITAL LETTER ZE 272A 0418 CYRILLIC CAPITAL LETTER I 272B 0419 CYRILLIC CAPITAL LETTER SHORT I 272C 041A CYRILLIC CAPITAL LETTER KA 272D 041B CYRILLIC CAPITAL LETTER EL 272E 041C CYRILLIC CAPITAL LETTER EM 272F 041D CYRILLIC CAPITAL LETTER EN 2730 041E CYRILLIC CAPITAL LETTER O 2731 041F CYRILLIC CAPITAL LETTER PE 2732 0420 CYRILLIC CAPITAL LETTER ER 2733 0421 CYRILLIC CAPITAL LETTER ES 2734 0422 CYRILLIC CAPITAL LETTER TE 2735 0423 CYRILLIC CAPITAL LETTER U 2736 0424 CYRILLIC CAPITAL LETTER EF 2737 0425 CYRILLIC CAPITAL LETTER HA 2738 0426 CYRILLIC CAPITAL LETTER TSE 2739 0427 CYRILLIC CAPITAL LETTER CHE 273A 0428 CYRILLIC CAPITAL LETTER SHA 273B 0429 CYRILLIC CAPITAL LETTER SHCHA 273C 042A CYRILLIC CAPITAL LETTER HARD SIGN 273D 042B CYRILLIC CAPITAL LETTER YERU 273E 042C CYRILLIC CAPITAL LETTER SOFT SIGN 273F 042D CYRILLIC CAPITAL LETTER E 2740 042E CYRILLIC CAPITAL LETTER YU 2741 042F CYRILLIC CAPITAL LETTER YA 2751 0430 CYRILLIC SMALL LETTER A 2752 0431 CYRILLIC SMALL LETTER BE 2753 0432 CYRILLIC SMALL LETTER VE 2754 0433 CYRILLIC SMALL LETTER GHE 2755 0434 CYRILLIC SMALL LETTER DE 2756 0435 CYRILLIC SMALL LETTER IE 2757 0451 CYRILLIC SMALL LETTER IO 2758 0436 CYRILLIC SMALL LETTER ZHE 2759 0437 CYRILLIC SMALL LETTER ZE 275A 0438 CYRILLIC SMALL LETTER I 275B 0439 CYRILLIC SMALL LETTER SHORT I 275C 043A CYRILLIC SMALL LETTER KA 275D 043B CYRILLIC SMALL LETTER EL 275E 043C CYRILLIC SMALL LETTER EM 275F 043D CYRILLIC SMALL LETTER EN 2760 043E CYRILLIC SMALL LETTER O 2761 043F CYRILLIC SMALL LETTER PE 2762 0440 CYRILLIC SMALL LETTER ER 2763 0441 CYRILLIC SMALL LETTER ES 2764 0442 CYRILLIC SMALL LETTER TE 2765 0443 CYRILLIC SMALL LETTER U 2766 0444 CYRILLIC SMALL LETTER EF 2767 0445 CYRILLIC SMALL LETTER HA 2768 0446 CYRILLIC SMALL LETTER TSE 2769 0447 CYRILLIC SMALL LETTER CHE 276A 0448 CYRILLIC SMALL LETTER SHA 276B 0449 CYRILLIC SMALL LETTER SHCHA 276C 044A CYRILLIC SMALL LETTER HARD SIGN 276D 044B CYRILLIC SMALL LETTER YERU 276E 044C CYRILLIC SMALL LETTER SOFT SIGN 276F 044D CYRILLIC SMALL LETTER E 2770 044E CYRILLIC SMALL LETTER YU 2771 044F CYRILLIC SMALL LETTER YA 2821 2500 BOX DRAWINGS LIGHT HORIZONTAL 2822 2502 BOX DRAWINGS LIGHT VERTICAL 2823 250C BOX DRAWINGS LIGHT DOWN AND RIGHT 2824 2510 BOX DRAWINGS LIGHT DOWN AND LEFT 2825 2518 BOX DRAWINGS LIGHT UP AND LEFT 2826 2514 BOX DRAWINGS LIGHT UP AND RIGHT 2827 251C BOX DRAWINGS LIGHT VERTICAL AND RIGHT 2828 252C BOX DRAWINGS LIGHT DOWN AND HORIZONTAL 2829 2524 BOX DRAWINGS LIGHT VERTICAL AND LEFT 282A 2534 BOX DRAWINGS LIGHT UP AND HORIZONTAL 282B 253C BOX DRAWINGS LIGHT VERTICAL AND HORIZONTAL 282C 2501 BOX DRAWINGS HEAVY HORIZONTAL 282D 2503 BOX DRAWINGS HEAVY VERTICAL 282E 250F BOX DRAWINGS HEAVY DOWN AND RIGHT 282F 2513 BOX DRAWINGS HEAVY DOWN AND LEFT 2830 251B BOX DRAWINGS HEAVY UP AND LEFT 2831 2517 BOX DRAWINGS HEAVY UP AND RIGHT 2832 2523 BOX DRAWINGS HEAVY VERTICAL AND RIGHT 2833 2533 BOX DRAWINGS HEAVY DOWN AND HORIZONTAL 2834 252B BOX DRAWINGS HEAVY VERTICAL AND LEFT 2835 253B BOX DRAWINGS HEAVY UP AND HORIZONTAL 2836 254B BOX DRAWINGS HEAVY VERTICAL AND HORIZONTAL 2837 2520 BOX DRAWINGS VERTICAL HEAVY AND RIGHT LIGHT 2838 252F BOX DRAWINGS DOWN LIGHT AND HORIZONTAL HEAVY 2839 2528 BOX DRAWINGS VERTICAL HEAVY AND LEFT LIGHT 283A 2537 BOX DRAWINGS UP LIGHT AND HORIZONTAL HEAVY 283B 253F BOX DRAWINGS VERTICAL LIGHT AND HORIZONTAL HEAVY 283C 251D BOX DRAWINGS VERTICAL LIGHT AND RIGHT HEAVY 283D 2530 BOX DRAWINGS DOWN HEAVY AND HORIZONTAL LIGHT 283E 2525 BOX DRAWINGS VERTICAL LIGHT AND LEFT HEAVY 283F 2538 BOX DRAWINGS UP HEAVY AND HORIZONTAL LIGHT 2840 2542 BOX DRAWINGS VERTICAL HEAVY AND HORIZONTAL LIGHT 3021 4E9C 3022 5516 3023 5A03 3024 963F 3025 54C0 3026 611B 3027 6328 3028 59F6 3029 9022 302A 8475 302B 831C 302C 7A50 302D 60AA 302E 63E1 302F 6E25 3030 65ED 3031 8466 3032 82A6 3033 9BF5 3034 6893 3035 5727 3036 65A1 3037 6271 3038 5B9B 3039 59D0 303A 867B 303B 98F4 303C 7D62 303D 7DBE 303E 9B8E 303F 6216 3040 7C9F 3041 88B7 3042 5B89 3043 5EB5 3044 6309 3045 6697 3046 6848 3047 95C7 3048 978D 3049 674F 304A 4EE5 304B 4F0A 304C 4F4D 304D 4F9D 304E 5049 304F 56F2 3050 5937 3051 59D4 3052 5A01 3053 5C09 3054 60DF 3055 610F 3056 6170 3057 6613 3058 6905 3059 70BA 305A 754F 305B 7570 305C 79FB 305D 7DAD 305E 7DEF 305F 80C3 3060 840E 3061 8863 3062 8B02 3063 9055 3064 907A 3065 533B 3066 4E95 3067 4EA5 3068 57DF 3069 80B2 306A 90C1 306B 78EF 306C 4E00 306D 58F1 306E 6EA2 306F 9038 3070 7A32 3071 8328 3072 828B 3073 9C2F 3074 5141 3075 5370 3076 54BD 3077 54E1 3078 56E0 3079 59FB 307A 5F15 307B 98F2 307C 6DEB 307D 80E4 307E 852D 3121 9662 3122 9670 3123 96A0 3124 97FB 3125 540B 3126 53F3 3127 5B87 3128 70CF 3129 7FBD 312A 8FC2 312B 96E8 312C 536F 312D 9D5C 312E 7ABA 312F 4E11 3130 7893 3131 81FC 3132 6E26 3133 5618 3134 5504 3135 6B1D 3136 851A 3137 9C3B 3138 59E5 3139 53A9 313A 6D66 313B 74DC 313C 958F 313D 5642 313E 4E91 313F 904B 3140 96F2 3141 834F 3142 990C 3143 53E1 3144 55B6 3145 5B30 3146 5F71 3147 6620 3148 66F3 3149 6804 314A 6C38 314B 6CF3 314C 6D29 314D 745B 314E 76C8 314F 7A4E 3150 9834 3151 82F1 3152 885B 3153 8A60 3154 92ED 3155 6DB2 3156 75AB 3157 76CA 3158 99C5 3159 60A6 315A 8B01 315B 8D8A 315C 95B2 315D 698E 315E 53AD 315F 5186 3160 5712 3161 5830 3162 5944 3163 5BB4 3164 5EF6 3165 6028 3166 63A9 3167 63F4 3168 6CBF 3169 6F14 316A 708E 316B 7114 316C 7159 316D 71D5 316E 733F 316F 7E01 3170 8276 3171 82D1 3172 8597 3173 9060 3174 925B 3175 9D1B 3176 5869 3177 65BC 3178 6C5A 3179 7525 317A 51F9 317B 592E 317C 5965 317D 5F80 317E 5FDC 3221 62BC 3222 65FA 3223 6A2A 3224 6B27 3225 6BB4 3226 738B 3227 7FC1 3228 8956 3229 9D2C 322A 9D0E 322B 9EC4 322C 5CA1 322D 6C96 322E 837B 322F 5104 3230 5C4B 3231 61B6 3232 81C6 3233 6876 3234 7261 3235 4E59 3236 4FFA 3237 5378 3238 6069 3239 6E29 323A 7A4F 323B 97F3 323C 4E0B 323D 5316 323E 4EEE 323F 4F55 3240 4F3D 3241 4FA1 3242 4F73 3243 52A0 3244 53EF 3245 5609 3246 590F 3247 5AC1 3248 5BB6 3249 5BE1 324A 79D1 324B 6687 324C 679C 324D 67B6 324E 6B4C 324F 6CB3 3250 706B 3251 73C2 3252 798D 3253 79BE 3254 7A3C 3255 7B87 3256 82B1 3257 82DB 3258 8304 3259 8377 325A 83EF 325B 83D3 325C 8766 325D 8AB2 325E 5629 325F 8CA8 3260 8FE6 3261 904E 3262 971E 3263 868A 3264 4FC4 3265 5CE8 3266 6211 3267 7259 3268 753B 3269 81E5 326A 82BD 326B 86FE 326C 8CC0 326D 96C5 326E 9913 326F 99D5 3270 4ECB 3271 4F1A 3272 89E3 3273 56DE 3274 584A 3275 58CA 3276 5EFB 3277 5FEB 3278 602A 3279 6094 327A 6062 327B 61D0 327C 6212 327D 62D0 327E 6539 3321 9B41 3322 6666 3323 68B0 3324 6D77 3325 7070 3326 754C 3327 7686 3328 7D75 3329 82A5 332A 87F9 332B 958B 332C 968E 332D 8C9D 332E 51F1 332F 52BE 3330 5916 3331 54B3 3332 5BB3 3333 5D16 3334 6168 3335 6982 3336 6DAF 3337 788D 3338 84CB 3339 8857 333A 8A72 333B 93A7 333C 9AB8 333D 6D6C 333E 99A8 333F 86D9 3340 57A3 3341 67FF 3342 86CE 3343 920E 3344 5283 3345 5687 3346 5404 3347 5ED3 3348 62E1 3349 64B9 334A 683C 334B 6838 334C 6BBB 334D 7372 334E 78BA 334F 7A6B 3350 899A 3351 89D2 3352 8D6B 3353 8F03 3354 90ED 3355 95A3 3356 9694 3357 9769 3358 5B66 3359 5CB3 335A 697D 335B 984D 335C 984E 335D 639B 335E 7B20 335F 6A2B 3360 6A7F 3361 68B6 3362 9C0D 3363 6F5F 3364 5272 3365 559D 3366 6070 3367 62EC 3368 6D3B 3369 6E07 336A 6ED1 336B 845B 336C 8910 336D 8F44 336E 4E14 336F 9C39 3370 53F6 3371 691B 3372 6A3A 3373 9784 3374 682A 3375 515C 3376 7AC3 3377 84B2 3378 91DC 3379 938C 337A 565B 337B 9D28 337C 6822 337D 8305 337E 8431 3421 7CA5 3422 5208 3423 82C5 3424 74E6 3425 4E7E 3426 4F83 3427 51A0 3428 5BD2 3429 520A 342A 52D8 342B 52E7 342C 5DFB 342D 559A 342E 582A 342F 59E6 3430 5B8C 3431 5B98 3432 5BDB 3433 5E72 3434 5E79 3435 60A3 3436 611F 3437 6163 3438 61BE 3439 63DB 343A 6562 343B 67D1 343C 6853 343D 68FA 343E 6B3E 343F 6B53 3440 6C57 3441 6F22 3442 6F97 3443 6F45 3444 74B0 3445 7518 3446 76E3 3447 770B 3448 7AFF 3449 7BA1 344A 7C21 344B 7DE9 344C 7F36 344D 7FF0 344E 809D 344F 8266 3450 839E 3451 89B3 3452 8ACC 3453 8CAB 3454 9084 3455 9451 3456 9593 3457 9591 3458 95A2 3459 9665 345A 97D3 345B 9928 345C 8218 345D 4E38 345E 542B 345F 5CB8 3460 5DCC 3461 73A9 3462 764C 3463 773C 3464 5CA9 3465 7FEB 3466 8D0B 3467 96C1 3468 9811 3469 9854 346A 9858 346B 4F01 346C 4F0E 346D 5371 346E 559C 346F 5668 3470 57FA 3471 5947 3472 5B09 3473 5BC4 3474 5C90 3475 5E0C 3476 5E7E 3477 5FCC 3478 63EE 3479 673A 347A 65D7 347B 65E2 347C 671F 347D 68CB 347E 68C4 3521 6A5F 3522 5E30 3523 6BC5 3524 6C17 3525 6C7D 3526 757F 3527 7948 3528 5B63 3529 7A00 352A 7D00 352B 5FBD 352C 898F 352D 8A18 352E 8CB4 352F 8D77 3530 8ECC 3531 8F1D 3532 98E2 3533 9A0E 3534 9B3C 3535 4E80 3536 507D 3537 5100 3538 5993 3539 5B9C 353A 622F 353B 6280 353C 64EC 353D 6B3A 353E 72A0 353F 7591 3540 7947 3541 7FA9 3542 87FB 3543 8ABC 3544 8B70 3545 63AC 3546 83CA 3547 97A0 3548 5409 3549 5403 354A 55AB 354B 6854 354C 6A58 354D 8A70 354E 7827 354F 6775 3550 9ECD 3551 5374 3552 5BA2 3553 811A 3554 8650 3555 9006 3556 4E18 3557 4E45 3558 4EC7 3559 4F11 355A 53CA 355B 5438 355C 5BAE 355D 5F13 355E 6025 355F 6551 3560 673D 3561 6C42 3562 6C72 3563 6CE3 3564 7078 3565 7403 3566 7A76 3567 7AAE 3568 7B08 3569 7D1A 356A 7CFE 356B 7D66 356C 65E7 356D 725B 356E 53BB 356F 5C45 3570 5DE8 3571 62D2 3572 62E0 3573 6319 3574 6E20 3575 865A 3576 8A31 3577 8DDD 3578 92F8 3579 6F01 357A 79A6 357B 9B5A 357C 4EA8 357D 4EAB 357E 4EAC 3621 4F9B 3622 4FA0 3623 50D1 3624 5147 3625 7AF6 3626 5171 3627 51F6 3628 5354 3629 5321 362A 537F 362B 53EB 362C 55AC 362D 5883 362E 5CE1 362F 5F37 3630 5F4A 3631 602F 3632 6050 3633 606D 3634 631F 3635 6559 3636 6A4B 3637 6CC1 3638 72C2 3639 72ED 363A 77EF 363B 80F8 363C 8105 363D 8208 363E 854E 363F 90F7 3640 93E1 3641 97FF 3642 9957 3643 9A5A 3644 4EF0 3645 51DD 3646 5C2D 3647 6681 3648 696D 3649 5C40 364A 66F2 364B 6975 364C 7389 364D 6850 364E 7C81 364F 50C5 3650 52E4 3651 5747 3652 5DFE 3653 9326 3654 65A4 3655 6B23 3656 6B3D 3657 7434 3658 7981 3659 79BD 365A 7B4B 365B 7DCA 365C 82B9 365D 83CC 365E 887F 365F 895F 3660 8B39 3661 8FD1 3662 91D1 3663 541F 3664 9280 3665 4E5D 3666 5036 3667 53E5 3668 533A 3669 72D7 366A 7396 366B 77E9 366C 82E6 366D 8EAF 366E 99C6 366F 99C8 3670 99D2 3671 5177 3672 611A 3673 865E 3674 55B0 3675 7A7A 3676 5076 3677 5BD3 3678 9047 3679 9685 367A 4E32 367B 6ADB 367C 91E7 367D 5C51 367E 5C48 3721 6398 3722 7A9F 3723 6C93 3724 9774 3725 8F61 3726 7AAA 3727 718A 3728 9688 3729 7C82 372A 6817 372B 7E70 372C 6851 372D 936C 372E 52F2 372F 541B 3730 85AB 3731 8A13 3732 7FA4 3733 8ECD 3734 90E1 3735 5366 3736 8888 3737 7941 3738 4FC2 3739 50BE 373A 5211 373B 5144 373C 5553 373D 572D 373E 73EA 373F 578B 3740 5951 3741 5F62 3742 5F84 3743 6075 3744 6176 3745 6167 3746 61A9 3747 63B2 3748 643A 3749 656C 374A 666F 374B 6842 374C 6E13 374D 7566 374E 7A3D 374F 7CFB 3750 7D4C 3751 7D99 3752 7E4B 3753 7F6B 3754 830E 3755 834A 3756 86CD 3757 8A08 3758 8A63 3759 8B66 375A 8EFD 375B 981A 375C 9D8F 375D 82B8 375E 8FCE 375F 9BE8 3760 5287 3761 621F 3762 6483 3763 6FC0 3764 9699 3765 6841 3766 5091 3767 6B20 3768 6C7A 3769 6F54 376A 7A74 376B 7D50 376C 8840 376D 8A23 376E 6708 376F 4EF6 3770 5039 3771 5026 3772 5065 3773 517C 3774 5238 3775 5263 3776 55A7 3777 570F 3778 5805 3779 5ACC 377A 5EFA 377B 61B2 377C 61F8 377D 62F3 377E 6372 3821 691C 3822 6A29 3823 727D 3824 72AC 3825 732E 3826 7814 3827 786F 3828 7D79 3829 770C 382A 80A9 382B 898B 382C 8B19 382D 8CE2 382E 8ED2 382F 9063 3830 9375 3831 967A 3832 9855 3833 9A13 3834 9E78 3835 5143 3836 539F 3837 53B3 3838 5E7B 3839 5F26 383A 6E1B 383B 6E90 383C 7384 383D 73FE 383E 7D43 383F 8237 3840 8A00 3841 8AFA 3842 9650 3843 4E4E 3844 500B 3845 53E4 3846 547C 3847 56FA 3848 59D1 3849 5B64 384A 5DF1 384B 5EAB 384C 5F27 384D 6238 384E 6545 384F 67AF 3850 6E56 3851 72D0 3852 7CCA 3853 88B4 3854 80A1 3855 80E1 3856 83F0 3857 864E 3858 8A87 3859 8DE8 385A 9237 385B 96C7 385C 9867 385D 9F13 385E 4E94 385F 4E92 3860 4F0D 3861 5348 3862 5449 3863 543E 3864 5A2F 3865 5F8C 3866 5FA1 3867 609F 3868 68A7 3869 6A8E 386A 745A 386B 7881 386C 8A9E 386D 8AA4 386E 8B77 386F 9190 3870 4E5E 3871 9BC9 3872 4EA4 3873 4F7C 3874 4FAF 3875 5019 3876 5016 3877 5149 3878 516C 3879 529F 387A 52B9 387B 52FE 387C 539A 387D 53E3 387E 5411 3921 540E 3922 5589 3923 5751 3924 57A2 3925 597D 3926 5B54 3927 5B5D 3928 5B8F 3929 5DE5 392A 5DE7 392B 5DF7 392C 5E78 392D 5E83 392E 5E9A 392F 5EB7 3930 5F18 3931 6052 3932 614C 3933 6297 3934 62D8 3935 63A7 3936 653B 3937 6602 3938 6643 3939 66F4 393A 676D 393B 6821 393C 6897 393D 69CB 393E 6C5F 393F 6D2A 3940 6D69 3941 6E2F 3942 6E9D 3943 7532 3944 7687 3945 786C 3946 7A3F 3947 7CE0 3948 7D05 3949 7D18 394A 7D5E 394B 7DB1 394C 8015 394D 8003 394E 80AF 394F 80B1 3950 8154 3951 818F 3952 822A 3953 8352 3954 884C 3955 8861 3956 8B1B 3957 8CA2 3958 8CFC 3959 90CA 395A 9175 395B 9271 395C 783F 395D 92FC 395E 95A4 395F 964D 3960 9805 3961 9999 3962 9AD8 3963 9D3B 3964 525B 3965 52AB 3966 53F7 3967 5408 3968 58D5 3969 62F7 396A 6FE0 396B 8C6A 396C 8F5F 396D 9EB9 396E 514B 396F 523B 3970 544A 3971 56FD 3972 7A40 3973 9177 3974 9D60 3975 9ED2 3976 7344 3977 6F09 3978 8170 3979 7511 397A 5FFD 397B 60DA 397C 9AA8 397D 72DB 397E 8FBC 3A21 6B64 3A22 9803 3A23 4ECA 3A24 56F0 3A25 5764 3A26 58BE 3A27 5A5A 3A28 6068 3A29 61C7 3A2A 660F 3A2B 6606 3A2C 6839 3A2D 68B1 3A2E 6DF7 3A2F 75D5 3A30 7D3A 3A31 826E 3A32 9B42 3A33 4E9B 3A34 4F50 3A35 53C9 3A36 5506 3A37 5D6F 3A38 5DE6 3A39 5DEE 3A3A 67FB 3A3B 6C99 3A3C 7473 3A3D 7802 3A3E 8A50 3A3F 9396 3A40 88DF 3A41 5750 3A42 5EA7 3A43 632B 3A44 50B5 3A45 50AC 3A46 518D 3A47 6700 3A48 54C9 3A49 585E 3A4A 59BB 3A4B 5BB0 3A4C 5F69 3A4D 624D 3A4E 63A1 3A4F 683D 3A50 6B73 3A51 6E08 3A52 707D 3A53 91C7 3A54 7280 3A55 7815 3A56 7826 3A57 796D 3A58 658E 3A59 7D30 3A5A 83DC 3A5B 88C1 3A5C 8F09 3A5D 969B 3A5E 5264 3A5F 5728 3A60 6750 3A61 7F6A 3A62 8CA1 3A63 51B4 3A64 5742 3A65 962A 3A66 583A 3A67 698A 3A68 80B4 3A69 54B2 3A6A 5D0E 3A6B 57FC 3A6C 7895 3A6D 9DFA 3A6E 4F5C 3A6F 524A 3A70 548B 3A71 643E 3A72 6628 3A73 6714 3A74 67F5 3A75 7A84 3A76 7B56 3A77 7D22 3A78 932F 3A79 685C 3A7A 9BAD 3A7B 7B39 3A7C 5319 3A7D 518A 3A7E 5237 3B21 5BDF 3B22 62F6 3B23 64AE 3B24 64E6 3B25 672D 3B26 6BBA 3B27 85A9 3B28 96D1 3B29 7690 3B2A 9BD6 3B2B 634C 3B2C 9306 3B2D 9BAB 3B2E 76BF 3B2F 6652 3B30 4E09 3B31 5098 3B32 53C2 3B33 5C71 3B34 60E8 3B35 6492 3B36 6563 3B37 685F 3B38 71E6 3B39 73CA 3B3A 7523 3B3B 7B97 3B3C 7E82 3B3D 8695 3B3E 8B83 3B3F 8CDB 3B40 9178 3B41 9910 3B42 65AC 3B43 66AB 3B44 6B8B 3B45 4ED5 3B46 4ED4 3B47 4F3A 3B48 4F7F 3B49 523A 3B4A 53F8 3B4B 53F2 3B4C 55E3 3B4D 56DB 3B4E 58EB 3B4F 59CB 3B50 59C9 3B51 59FF 3B52 5B50 3B53 5C4D 3B54 5E02 3B55 5E2B 3B56 5FD7 3B57 601D 3B58 6307 3B59 652F 3B5A 5B5C 3B5B 65AF 3B5C 65BD 3B5D 65E8 3B5E 679D 3B5F 6B62 3B60 6B7B 3B61 6C0F 3B62 7345 3B63 7949 3B64 79C1 3B65 7CF8 3B66 7D19 3B67 7D2B 3B68 80A2 3B69 8102 3B6A 81F3 3B6B 8996 3B6C 8A5E 3B6D 8A69 3B6E 8A66 3B6F 8A8C 3B70 8AEE 3B71 8CC7 3B72 8CDC 3B73 96CC 3B74 98FC 3B75 6B6F 3B76 4E8B 3B77 4F3C 3B78 4F8D 3B79 5150 3B7A 5B57 3B7B 5BFA 3B7C 6148 3B7D 6301 3B7E 6642 3C21 6B21 3C22 6ECB 3C23 6CBB 3C24 723E 3C25 74BD 3C26 75D4 3C27 78C1 3C28 793A 3C29 800C 3C2A 8033 3C2B 81EA 3C2C 8494 3C2D 8F9E 3C2E 6C50 3C2F 9E7F 3C30 5F0F 3C31 8B58 3C32 9D2B 3C33 7AFA 3C34 8EF8 3C35 5B8D 3C36 96EB 3C37 4E03 3C38 53F1 3C39 57F7 3C3A 5931 3C3B 5AC9 3C3C 5BA4 3C3D 6089 3C3E 6E7F 3C3F 6F06 3C40 75BE 3C41 8CEA 3C42 5B9F 3C43 8500 3C44 7BE0 3C45 5072 3C46 67F4 3C47 829D 3C48 5C61 3C49 854A 3C4A 7E1E 3C4B 820E 3C4C 5199 3C4D 5C04 3C4E 6368 3C4F 8D66 3C50 659C 3C51 716E 3C52 793E 3C53 7D17 3C54 8005 3C55 8B1D 3C56 8ECA 3C57 906E 3C58 86C7 3C59 90AA 3C5A 501F 3C5B 52FA 3C5C 5C3A 3C5D 6753 3C5E 707C 3C5F 7235 3C60 914C 3C61 91C8 3C62 932B 3C63 82E5 3C64 5BC2 3C65 5F31 3C66 60F9 3C67 4E3B 3C68 53D6 3C69 5B88 3C6A 624B 3C6B 6731 3C6C 6B8A 3C6D 72E9 3C6E 73E0 3C6F 7A2E 3C70 816B 3C71 8DA3 3C72 9152 3C73 9996 3C74 5112 3C75 53D7 3C76 546A 3C77 5BFF 3C78 6388 3C79 6A39 3C7A 7DAC 3C7B 9700 3C7C 56DA 3C7D 53CE 3C7E 5468 3D21 5B97 3D22 5C31 3D23 5DDE 3D24 4FEE 3D25 6101 3D26 62FE 3D27 6D32 3D28 79C0 3D29 79CB 3D2A 7D42 3D2B 7E4D 3D2C 7FD2 3D2D 81ED 3D2E 821F 3D2F 8490 3D30 8846 3D31 8972 3D32 8B90 3D33 8E74 3D34 8F2F 3D35 9031 3D36 914B 3D37 916C 3D38 96C6 3D39 919C 3D3A 4EC0 3D3B 4F4F 3D3C 5145 3D3D 5341 3D3E 5F93 3D3F 620E 3D40 67D4 3D41 6C41 3D42 6E0B 3D43 7363 3D44 7E26 3D45 91CD 3D46 9283 3D47 53D4 3D48 5919 3D49 5BBF 3D4A 6DD1 3D4B 795D 3D4C 7E2E 3D4D 7C9B 3D4E 587E 3D4F 719F 3D50 51FA 3D51 8853 3D52 8FF0 3D53 4FCA 3D54 5CFB 3D55 6625 3D56 77AC 3D57 7AE3 3D58 821C 3D59 99FF 3D5A 51C6 3D5B 5FAA 3D5C 65EC 3D5D 696F 3D5E 6B89 3D5F 6DF3 3D60 6E96 3D61 6F64 3D62 76FE 3D63 7D14 3D64 5DE1 3D65 9075 3D66 9187 3D67 9806 3D68 51E6 3D69 521D 3D6A 6240 3D6B 6691 3D6C 66D9 3D6D 6E1A 3D6E 5EB6 3D6F 7DD2 3D70 7F72 3D71 66F8 3D72 85AF 3D73 85F7 3D74 8AF8 3D75 52A9 3D76 53D9 3D77 5973 3D78 5E8F 3D79 5F90 3D7A 6055 3D7B 92E4 3D7C 9664 3D7D 50B7 3D7E 511F 3E21 52DD 3E22 5320 3E23 5347 3E24 53EC 3E25 54E8 3E26 5546 3E27 5531 3E28 5617 3E29 5968 3E2A 59BE 3E2B 5A3C 3E2C 5BB5 3E2D 5C06 3E2E 5C0F 3E2F 5C11 3E30 5C1A 3E31 5E84 3E32 5E8A 3E33 5EE0 3E34 5F70 3E35 627F 3E36 6284 3E37 62DB 3E38 638C 3E39 6377 3E3A 6607 3E3B 660C 3E3C 662D 3E3D 6676 3E3E 677E 3E3F 68A2 3E40 6A1F 3E41 6A35 3E42 6CBC 3E43 6D88 3E44 6E09 3E45 6E58 3E46 713C 3E47 7126 3E48 7167 3E49 75C7 3E4A 7701 3E4B 785D 3E4C 7901 3E4D 7965 3E4E 79F0 3E4F 7AE0 3E50 7B11 3E51 7CA7 3E52 7D39 3E53 8096 3E54 83D6 3E55 848B 3E56 8549 3E57 885D 3E58 88F3 3E59 8A1F 3E5A 8A3C 3E5B 8A54 3E5C 8A73 3E5D 8C61 3E5E 8CDE 3E5F 91A4 3E60 9266 3E61 937E 3E62 9418 3E63 969C 3E64 9798 3E65 4E0A 3E66 4E08 3E67 4E1E 3E68 4E57 3E69 5197 3E6A 5270 3E6B 57CE 3E6C 5834 3E6D 58CC 3E6E 5B22 3E6F 5E38 3E70 60C5 3E71 64FE 3E72 6761 3E73 6756 3E74 6D44 3E75 72B6 3E76 7573 3E77 7A63 3E78 84B8 3E79 8B72 3E7A 91B8 3E7B 9320 3E7C 5631 3E7D 57F4 3E7E 98FE 3F21 62ED 3F22 690D 3F23 6B96 3F24 71ED 3F25 7E54 3F26 8077 3F27 8272 3F28 89E6 3F29 98DF 3F2A 8755 3F2B 8FB1 3F2C 5C3B 3F2D 4F38 3F2E 4FE1 3F2F 4FB5 3F30 5507 3F31 5A20 3F32 5BDD 3F33 5BE9 3F34 5FC3 3F35 614E 3F36 632F 3F37 65B0 3F38 664B 3F39 68EE 3F3A 699B 3F3B 6D78 3F3C 6DF1 3F3D 7533 3F3E 75B9 3F3F 771F 3F40 795E 3F41 79E6 3F42 7D33 3F43 81E3 3F44 82AF 3F45 85AA 3F46 89AA 3F47 8A3A 3F48 8EAB 3F49 8F9B 3F4A 9032 3F4B 91DD 3F4C 9707 3F4D 4EBA 3F4E 4EC1 3F4F 5203 3F50 5875 3F51 58EC 3F52 5C0B 3F53 751A 3F54 5C3D 3F55 814E 3F56 8A0A 3F57 8FC5 3F58 9663 3F59 976D 3F5A 7B25 3F5B 8ACF 3F5C 9808 3F5D 9162 3F5E 56F3 3F5F 53A8 3F60 9017 3F61 5439 3F62 5782 3F63 5E25 3F64 63A8 3F65 6C34 3F66 708A 3F67 7761 3F68 7C8B 3F69 7FE0 3F6A 8870 3F6B 9042 3F6C 9154 3F6D 9310 3F6E 9318 3F6F 968F 3F70 745E 3F71 9AC4 3F72 5D07 3F73 5D69 3F74 6570 3F75 67A2 3F76 8DA8 3F77 96DB 3F78 636E 3F79 6749 3F7A 6919 3F7B 83C5 3F7C 9817 3F7D 96C0 3F7E 88FE 4021 6F84 4022 647A 4023 5BF8 4024 4E16 4025 702C 4026 755D 4027 662F 4028 51C4 4029 5236 402A 52E2 402B 59D3 402C 5F81 402D 6027 402E 6210 402F 653F 4030 6574 4031 661F 4032 6674 4033 68F2 4034 6816 4035 6B63 4036 6E05 4037 7272 4038 751F 4039 76DB 403A 7CBE 403B 8056 403C 58F0 403D 88FD 403E 897F 403F 8AA0 4040 8A93 4041 8ACB 4042 901D 4043 9192 4044 9752 4045 9759 4046 6589 4047 7A0E 4048 8106 4049 96BB 404A 5E2D 404B 60DC 404C 621A 404D 65A5 404E 6614 404F 6790 4050 77F3 4051 7A4D 4052 7C4D 4053 7E3E 4054 810A 4055 8CAC 4056 8D64 4057 8DE1 4058 8E5F 4059 78A9 405A 5207 405B 62D9 405C 63A5 405D 6442 405E 6298 405F 8A2D 4060 7A83 4061 7BC0 4062 8AAC 4063 96EA 4064 7D76 4065 820C 4066 8749 4067 4ED9 4068 5148 4069 5343 406A 5360 406B 5BA3 406C 5C02 406D 5C16 406E 5DDD 406F 6226 4070 6247 4071 64B0 4072 6813 4073 6834 4074 6CC9 4075 6D45 4076 6D17 4077 67D3 4078 6F5C 4079 714E 407A 717D 407B 65CB 407C 7A7F 407D 7BAD 407E 7DDA 4121 7E4A 4122 7FA8 4123 817A 4124 821B 4125 8239 4126 85A6 4127 8A6E 4128 8CCE 4129 8DF5 412A 9078 412B 9077 412C 92AD 412D 9291 412E 9583 412F 9BAE 4130 524D 4131 5584 4132 6F38 4133 7136 4134 5168 4135 7985 4136 7E55 4137 81B3 4138 7CCE 4139 564C 413A 5851 413B 5CA8 413C 63AA 413D 66FE 413E 66FD 413F 695A 4140 72D9 4141 758F 4142 758E 4143 790E 4144 7956 4145 79DF 4146 7C97 4147 7D20 4148 7D44 4149 8607 414A 8A34 414B 963B 414C 9061 414D 9F20 414E 50E7 414F 5275 4150 53CC 4151 53E2 4152 5009 4153 55AA 4154 58EE 4155 594F 4156 723D 4157 5B8B 4158 5C64 4159 531D 415A 60E3 415B 60F3 415C 635C 415D 6383 415E 633F 415F 63BB 4160 64CD 4161 65E9 4162 66F9 4163 5DE3 4164 69CD 4165 69FD 4166 6F15 4167 71E5 4168 4E89 4169 75E9 416A 76F8 416B 7A93 416C 7CDF 416D 7DCF 416E 7D9C 416F 8061 4170 8349 4171 8358 4172 846C 4173 84BC 4174 85FB 4175 88C5 4176 8D70 4177 9001 4178 906D 4179 9397 417A 971C 417B 9A12 417C 50CF 417D 5897 417E 618E 4221 81D3 4222 8535 4223 8D08 4224 9020 4225 4FC3 4226 5074 4227 5247 4228 5373 4229 606F 422A 6349 422B 675F 422C 6E2C 422D 8DB3 422E 901F 422F 4FD7 4230 5C5E 4231 8CCA 4232 65CF 4233 7D9A 4234 5352 4235 8896 4236 5176 4237 63C3 4238 5B58 4239 5B6B 423A 5C0A 423B 640D 423C 6751 423D 905C 423E 4ED6 423F 591A 4240 592A 4241 6C70 4242 8A51 4243 553E 4244 5815 4245 59A5 4246 60F0 4247 6253 4248 67C1 4249 8235 424A 6955 424B 9640 424C 99C4 424D 9A28 424E 4F53 424F 5806 4250 5BFE 4251 8010 4252 5CB1 4253 5E2F 4254 5F85 4255 6020 4256 614B 4257 6234 4258 66FF 4259 6CF0 425A 6EDE 425B 80CE 425C 817F 425D 82D4 425E 888B 425F 8CB8 4260 9000 4261 902E 4262 968A 4263 9EDB 4264 9BDB 4265 4EE3 4266 53F0 4267 5927 4268 7B2C 4269 918D 426A 984C 426B 9DF9 426C 6EDD 426D 7027 426E 5353 426F 5544 4270 5B85 4271 6258 4272 629E 4273 62D3 4274 6CA2 4275 6FEF 4276 7422 4277 8A17 4278 9438 4279 6FC1 427A 8AFE 427B 8338 427C 51E7 427D 86F8 427E 53EA 4321 53E9 4322 4F46 4323 9054 4324 8FB0 4325 596A 4326 8131 4327 5DFD 4328 7AEA 4329 8FBF 432A 68DA 432B 8C37 432C 72F8 432D 9C48 432E 6A3D 432F 8AB0 4330 4E39 4331 5358 4332 5606 4333 5766 4334 62C5 4335 63A2 4336 65E6 4337 6B4E 4338 6DE1 4339 6E5B 433A 70AD 433B 77ED 433C 7AEF 433D 7BAA 433E 7DBB 433F 803D 4340 80C6 4341 86CB 4342 8A95 4343 935B 4344 56E3 4345 58C7 4346 5F3E 4347 65AD 4348 6696 4349 6A80 434A 6BB5 434B 7537 434C 8AC7 434D 5024 434E 77E5 434F 5730 4350 5F1B 4351 6065 4352 667A 4353 6C60 4354 75F4 4355 7A1A 4356 7F6E 4357 81F4 4358 8718 4359 9045 435A 99B3 435B 7BC9 435C 755C 435D 7AF9 435E 7B51 435F 84C4 4360 9010 4361 79E9 4362 7A92 4363 8336 4364 5AE1 4365 7740 4366 4E2D 4367 4EF2 4368 5B99 4369 5FE0 436A 62BD 436B 663C 436C 67F1 436D 6CE8 436E 866B 436F 8877 4370 8A3B 4371 914E 4372 92F3 4373 99D0 4374 6A17 4375 7026 4376 732A 4377 82E7 4378 8457 4379 8CAF 437A 4E01 437B 5146 437C 51CB 437D 558B 437E 5BF5 4421 5E16 4422 5E33 4423 5E81 4424 5F14 4425 5F35 4426 5F6B 4427 5FB4 4428 61F2 4429 6311 442A 66A2 442B 671D 442C 6F6E 442D 7252 442E 753A 442F 773A 4430 8074 4431 8139 4432 8178 4433 8776 4434 8ABF 4435 8ADC 4436 8D85 4437 8DF3 4438 929A 4439 9577 443A 9802 443B 9CE5 443C 52C5 443D 6357 443E 76F4 443F 6715 4440 6C88 4441 73CD 4442 8CC3 4443 93AE 4444 9673 4445 6D25 4446 589C 4447 690E 4448 69CC 4449 8FFD 444A 939A 444B 75DB 444C 901A 444D 585A 444E 6802 444F 63B4 4450 69FB 4451 4F43 4452 6F2C 4453 67D8 4454 8FBB 4455 8526 4456 7DB4 4457 9354 4458 693F 4459 6F70 445A 576A 445B 58F7 445C 5B2C 445D 7D2C 445E 722A 445F 540A 4460 91E3 4461 9DB4 4462 4EAD 4463 4F4E 4464 505C 4465 5075 4466 5243 4467 8C9E 4468 5448 4469 5824 446A 5B9A 446B 5E1D 446C 5E95 446D 5EAD 446E 5EF7 446F 5F1F 4470 608C 4471 62B5 4472 633A 4473 63D0 4474 68AF 4475 6C40 4476 7887 4477 798E 4478 7A0B 4479 7DE0 447A 8247 447B 8A02 447C 8AE6 447D 8E44 447E 9013 4521 90B8 4522 912D 4523 91D8 4524 9F0E 4525 6CE5 4526 6458 4527 64E2 4528 6575 4529 6EF4 452A 7684 452B 7B1B 452C 9069 452D 93D1 452E 6EBA 452F 54F2 4530 5FB9 4531 64A4 4532 8F4D 4533 8FED 4534 9244 4535 5178 4536 586B 4537 5929 4538 5C55 4539 5E97 453A 6DFB 453B 7E8F 453C 751C 453D 8CBC 453E 8EE2 453F 985B 4540 70B9 4541 4F1D 4542 6BBF 4543 6FB1 4544 7530 4545 96FB 4546 514E 4547 5410 4548 5835 4549 5857 454A 59AC 454B 5C60 454C 5F92 454D 6597 454E 675C 454F 6E21 4550 767B 4551 83DF 4552 8CED 4553 9014 4554 90FD 4555 934D 4556 7825 4557 783A 4558 52AA 4559 5EA6 455A 571F 455B 5974 455C 6012 455D 5012 455E 515A 455F 51AC 4560 51CD 4561 5200 4562 5510 4563 5854 4564 5858 4565 5957 4566 5B95 4567 5CF6 4568 5D8B 4569 60BC 456A 6295 456B 642D 456C 6771 456D 6843 456E 68BC 456F 68DF 4570 76D7 4571 6DD8 4572 6E6F 4573 6D9B 4574 706F 4575 71C8 4576 5F53 4577 75D8 4578 7977 4579 7B49 457A 7B54 457B 7B52 457C 7CD6 457D 7D71 457E 5230 4621 8463 4622 8569 4623 85E4 4624 8A0E 4625 8B04 4626 8C46 4627 8E0F 4628 9003 4629 900F 462A 9419 462B 9676 462C 982D 462D 9A30 462E 95D8 462F 50CD 4630 52D5 4631 540C 4632 5802 4633 5C0E 4634 61A7 4635 649E 4636 6D1E 4637 77B3 4638 7AE5 4639 80F4 463A 8404 463B 9053 463C 9285 463D 5CE0 463E 9D07 463F 533F 4640 5F97 4641 5FB3 4642 6D9C 4643 7279 4644 7763 4645 79BF 4646 7BE4 4647 6BD2 4648 72EC 4649 8AAD 464A 6803 464B 6A61 464C 51F8 464D 7A81 464E 6934 464F 5C4A 4650 9CF6 4651 82EB 4652 5BC5 4653 9149 4654 701E 4655 5678 4656 5C6F 4657 60C7 4658 6566 4659 6C8C 465A 8C5A 465B 9041 465C 9813 465D 5451 465E 66C7 465F 920D 4660 5948 4661 90A3 4662 5185 4663 4E4D 4664 51EA 4665 8599 4666 8B0E 4667 7058 4668 637A 4669 934B 466A 6962 466B 99B4 466C 7E04 466D 7577 466E 5357 466F 6960 4670 8EDF 4671 96E3 4672 6C5D 4673 4E8C 4674 5C3C 4675 5F10 4676 8FE9 4677 5302 4678 8CD1 4679 8089 467A 8679 467B 5EFF 467C 65E5 467D 4E73 467E 5165 4721 5982 4722 5C3F 4723 97EE 4724 4EFB 4725 598A 4726 5FCD 4727 8A8D 4728 6FE1 4729 79B0 472A 7962 472B 5BE7 472C 8471 472D 732B 472E 71B1 472F 5E74 4730 5FF5 4731 637B 4732 649A 4733 71C3 4734 7C98 4735 4E43 4736 5EFC 4737 4E4B 4738 57DC 4739 56A2 473A 60A9 473B 6FC3 473C 7D0D 473D 80FD 473E 8133 473F 81BF 4740 8FB2 4741 8997 4742 86A4 4743 5DF4 4744 628A 4745 64AD 4746 8987 4747 6777 4748 6CE2 4749 6D3E 474A 7436 474B 7834 474C 5A46 474D 7F75 474E 82AD 474F 99AC 4750 4FF3 4751 5EC3 4752 62DD 4753 6392 4754 6557 4755 676F 4756 76C3 4757 724C 4758 80CC 4759 80BA 475A 8F29 475B 914D 475C 500D 475D 57F9 475E 5A92 475F 6885 4760 6973 4761 7164 4762 72FD 4763 8CB7 4764 58F2 4765 8CE0 4766 966A 4767 9019 4768 877F 4769 79E4 476A 77E7 476B 8429 476C 4F2F 476D 5265 476E 535A 476F 62CD 4770 67CF 4771 6CCA 4772 767D 4773 7B94 4774 7C95 4775 8236 4776 8584 4777 8FEB 4778 66DD 4779 6F20 477A 7206 477B 7E1B 477C 83AB 477D 99C1 477E 9EA6 4821 51FD 4822 7BB1 4823 7872 4824 7BB8 4825 8087 4826 7B48 4827 6AE8 4828 5E61 4829 808C 482A 7551 482B 7560 482C 516B 482D 9262 482E 6E8C 482F 767A 4830 9197 4831 9AEA 4832 4F10 4833 7F70 4834 629C 4835 7B4F 4836 95A5 4837 9CE9 4838 567A 4839 5859 483A 86E4 483B 96BC 483C 4F34 483D 5224 483E 534A 483F 53CD 4840 53DB 4841 5E06 4842 642C 4843 6591 4844 677F 4845 6C3E 4846 6C4E 4847 7248 4848 72AF 4849 73ED 484A 7554 484B 7E41 484C 822C 484D 85E9 484E 8CA9 484F 7BC4 4850 91C6 4851 7169 4852 9812 4853 98EF 4854 633D 4855 6669 4856 756A 4857 76E4 4858 78D0 4859 8543 485A 86EE 485B 532A 485C 5351 485D 5426 485E 5983 485F 5E87 4860 5F7C 4861 60B2 4862 6249 4863 6279 4864 62AB 4865 6590 4866 6BD4 4867 6CCC 4868 75B2 4869 76AE 486A 7891 486B 79D8 486C 7DCB 486D 7F77 486E 80A5 486F 88AB 4870 8AB9 4871 8CBB 4872 907F 4873 975E 4874 98DB 4875 6A0B 4876 7C38 4877 5099 4878 5C3E 4879 5FAE 487A 6787 487B 6BD8 487C 7435 487D 7709 487E 7F8E 4921 9F3B 4922 67CA 4923 7A17 4924 5339 4925 758B 4926 9AED 4927 5F66 4928 819D 4929 83F1 492A 8098 492B 5F3C 492C 5FC5 492D 7562 492E 7B46 492F 903C 4930 6867 4931 59EB 4932 5A9B 4933 7D10 4934 767E 4935 8B2C 4936 4FF5 4937 5F6A 4938 6A19 4939 6C37 493A 6F02 493B 74E2 493C 7968 493D 8868 493E 8A55 493F 8C79 4940 5EDF 4941 63CF 4942 75C5 4943 79D2 4944 82D7 4945 9328 4946 92F2 4947 849C 4948 86ED 4949 9C2D 494A 54C1 494B 5F6C 494C 658C 494D 6D5C 494E 7015 494F 8CA7 4950 8CD3 4951 983B 4952 654F 4953 74F6 4954 4E0D 4955 4ED8 4956 57E0 4957 592B 4958 5A66 4959 5BCC 495A 51A8 495B 5E03 495C 5E9C 495D 6016 495E 6276 495F 6577 4960 65A7 4961 666E 4962 6D6E 4963 7236 4964 7B26 4965 8150 4966 819A 4967 8299 4968 8B5C 4969 8CA0 496A 8CE6 496B 8D74 496C 961C 496D 9644 496E 4FAE 496F 64AB 4970 6B66 4971 821E 4972 8461 4973 856A 4974 90E8 4975 5C01 4976 6953 4977 98A8 4978 847A 4979 8557 497A 4F0F 497B 526F 497C 5FA9 497D 5E45 497E 670D 4A21 798F 4A22 8179 4A23 8907 4A24 8986 4A25 6DF5 4A26 5F17 4A27 6255 4A28 6CB8 4A29 4ECF 4A2A 7269 4A2B 9B92 4A2C 5206 4A2D 543B 4A2E 5674 4A2F 58B3 4A30 61A4 4A31 626E 4A32 711A 4A33 596E 4A34 7C89 4A35 7CDE 4A36 7D1B 4A37 96F0 4A38 6587 4A39 805E 4A3A 4E19 4A3B 4F75 4A3C 5175 4A3D 5840 4A3E 5E63 4A3F 5E73 4A40 5F0A 4A41 67C4 4A42 4E26 4A43 853D 4A44 9589 4A45 965B 4A46 7C73 4A47 9801 4A48 50FB 4A49 58C1 4A4A 7656 4A4B 78A7 4A4C 5225 4A4D 77A5 4A4E 8511 4A4F 7B86 4A50 504F 4A51 5909 4A52 7247 4A53 7BC7 4A54 7DE8 4A55 8FBA 4A56 8FD4 4A57 904D 4A58 4FBF 4A59 52C9 4A5A 5A29 4A5B 5F01 4A5C 97AD 4A5D 4FDD 4A5E 8217 4A5F 92EA 4A60 5703 4A61 6355 4A62 6B69 4A63 752B 4A64 88DC 4A65 8F14 4A66 7A42 4A67 52DF 4A68 5893 4A69 6155 4A6A 620A 4A6B 66AE 4A6C 6BCD 4A6D 7C3F 4A6E 83E9 4A6F 5023 4A70 4FF8 4A71 5305 4A72 5446 4A73 5831 4A74 5949 4A75 5B9D 4A76 5CF0 4A77 5CEF 4A78 5D29 4A79 5E96 4A7A 62B1 4A7B 6367 4A7C 653E 4A7D 65B9 4A7E 670B 4B21 6CD5 4B22 6CE1 4B23 70F9 4B24 7832 4B25 7E2B 4B26 80DE 4B27 82B3 4B28 840C 4B29 84EC 4B2A 8702 4B2B 8912 4B2C 8A2A 4B2D 8C4A 4B2E 90A6 4B2F 92D2 4B30 98FD 4B31 9CF3 4B32 9D6C 4B33 4E4F 4B34 4EA1 4B35 508D 4B36 5256 4B37 574A 4B38 59A8 4B39 5E3D 4B3A 5FD8 4B3B 5FD9 4B3C 623F 4B3D 66B4 4B3E 671B 4B3F 67D0 4B40 68D2 4B41 5192 4B42 7D21 4B43 80AA 4B44 81A8 4B45 8B00 4B46 8C8C 4B47 8CBF 4B48 927E 4B49 9632 4B4A 5420 4B4B 982C 4B4C 5317 4B4D 50D5 4B4E 535C 4B4F 58A8 4B50 64B2 4B51 6734 4B52 7267 4B53 7766 4B54 7A46 4B55 91E6 4B56 52C3 4B57 6CA1 4B58 6B86 4B59 5800 4B5A 5E4C 4B5B 5954 4B5C 672C 4B5D 7FFB 4B5E 51E1 4B5F 76C6 4B60 6469 4B61 78E8 4B62 9B54 4B63 9EBB 4B64 57CB 4B65 59B9 4B66 6627 4B67 679A 4B68 6BCE 4B69 54E9 4B6A 69D9 4B6B 5E55 4B6C 819C 4B6D 6795 4B6E 9BAA 4B6F 67FE 4B70 9C52 4B71 685D 4B72 4EA6 4B73 4FE3 4B74 53C8 4B75 62B9 4B76 672B 4B77 6CAB 4B78 8FC4 4B79 4FAD 4B7A 7E6D 4B7B 9EBF 4B7C 4E07 4B7D 6162 4B7E 6E80 4C21 6F2B 4C22 8513 4C23 5473 4C24 672A 4C25 9B45 4C26 5DF3 4C27 7B95 4C28 5CAC 4C29 5BC6 4C2A 871C 4C2B 6E4A 4C2C 84D1 4C2D 7A14 4C2E 8108 4C2F 5999 4C30 7C8D 4C31 6C11 4C32 7720 4C33 52D9 4C34 5922 4C35 7121 4C36 725F 4C37 77DB 4C38 9727 4C39 9D61 4C3A 690B 4C3B 5A7F 4C3C 5A18 4C3D 51A5 4C3E 540D 4C3F 547D 4C40 660E 4C41 76DF 4C42 8FF7 4C43 9298 4C44 9CF4 4C45 59EA 4C46 725D 4C47 6EC5 4C48 514D 4C49 68C9 4C4A 7DBF 4C4B 7DEC 4C4C 9762 4C4D 9EBA 4C4E 6478 4C4F 6A21 4C50 8302 4C51 5984 4C52 5B5F 4C53 6BDB 4C54 731B 4C55 76F2 4C56 7DB2 4C57 8017 4C58 8499 4C59 5132 4C5A 6728 4C5B 9ED9 4C5C 76EE 4C5D 6762 4C5E 52FF 4C5F 9905 4C60 5C24 4C61 623B 4C62 7C7E 4C63 8CB0 4C64 554F 4C65 60B6 4C66 7D0B 4C67 9580 4C68 5301 4C69 4E5F 4C6A 51B6 4C6B 591C 4C6C 723A 4C6D 8036 4C6E 91CE 4C6F 5F25 4C70 77E2 4C71 5384 4C72 5F79 4C73 7D04 4C74 85AC 4C75 8A33 4C76 8E8D 4C77 9756 4C78 67F3 4C79 85AE 4C7A 9453 4C7B 6109 4C7C 6108 4C7D 6CB9 4C7E 7652 4D21 8AED 4D22 8F38 4D23 552F 4D24 4F51 4D25 512A 4D26 52C7 4D27 53CB 4D28 5BA5 4D29 5E7D 4D2A 60A0 4D2B 6182 4D2C 63D6 4D2D 6709 4D2E 67DA 4D2F 6E67 4D30 6D8C 4D31 7336 4D32 7337 4D33 7531 4D34 7950 4D35 88D5 4D36 8A98 4D37 904A 4D38 9091 4D39 90F5 4D3A 96C4 4D3B 878D 4D3C 5915 4D3D 4E88 4D3E 4F59 4D3F 4E0E 4D40 8A89 4D41 8F3F 4D42 9810 4D43 50AD 4D44 5E7C 4D45 5996 4D46 5BB9 4D47 5EB8 4D48 63DA 4D49 63FA 4D4A 64C1 4D4B 66DC 4D4C 694A 4D4D 69D8 4D4E 6D0B 4D4F 6EB6 4D50 7194 4D51 7528 4D52 7AAF 4D53 7F8A 4D54 8000 4D55 8449 4D56 84C9 4D57 8981 4D58 8B21 4D59 8E0A 4D5A 9065 4D5B 967D 4D5C 990A 4D5D 617E 4D5E 6291 4D5F 6B32 4D60 6C83 4D61 6D74 4D62 7FCC 4D63 7FFC 4D64 6DC0 4D65 7F85 4D66 87BA 4D67 88F8 4D68 6765 4D69 83B1 4D6A 983C 4D6B 96F7 4D6C 6D1B 4D6D 7D61 4D6E 843D 4D6F 916A 4D70 4E71 4D71 5375 4D72 5D50 4D73 6B04 4D74 6FEB 4D75 85CD 4D76 862D 4D77 89A7 4D78 5229 4D79 540F 4D7A 5C65 4D7B 674E 4D7C 68A8 4D7D 7406 4D7E 7483 4E21 75E2 4E22 88CF 4E23 88E1 4E24 91CC 4E25 96E2 4E26 9678 4E27 5F8B 4E28 7387 4E29 7ACB 4E2A 844E 4E2B 63A0 4E2C 7565 4E2D 5289 4E2E 6D41 4E2F 6E9C 4E30 7409 4E31 7559 4E32 786B 4E33 7C92 4E34 9686 4E35 7ADC 4E36 9F8D 4E37 4FB6 4E38 616E 4E39 65C5 4E3A 865C 4E3B 4E86 4E3C 4EAE 4E3D 50DA 4E3E 4E21 4E3F 51CC 4E40 5BEE 4E41 6599 4E42 6881 4E43 6DBC 4E44 731F 4E45 7642 4E46 77AD 4E47 7A1C 4E48 7CE7 4E49 826F 4E4A 8AD2 4E4B 907C 4E4C 91CF 4E4D 9675 4E4E 9818 4E4F 529B 4E50 7DD1 4E51 502B 4E52 5398 4E53 6797 4E54 6DCB 4E55 71D0 4E56 7433 4E57 81E8 4E58 8F2A 4E59 96A3 4E5A 9C57 4E5B 9E9F 4E5C 7460 4E5D 5841 4E5E 6D99 4E5F 7D2F 4E60 985E 4E61 4EE4 4E62 4F36 4E63 4F8B 4E64 51B7 4E65 52B1 4E66 5DBA 4E67 601C 4E68 73B2 4E69 793C 4E6A 82D3 4E6B 9234 4E6C 96B7 4E6D 96F6 4E6E 970A 4E6F 9E97 4E70 9F62 4E71 66A6 4E72 6B74 4E73 5217 4E74 52A3 4E75 70C8 4E76 88C2 4E77 5EC9 4E78 604B 4E79 6190 4E7A 6F23 4E7B 7149 4E7C 7C3E 4E7D 7DF4 4E7E 806F 4F21 84EE 4F22 9023 4F23 932C 4F24 5442 4F25 9B6F 4F26 6AD3 4F27 7089 4F28 8CC2 4F29 8DEF 4F2A 9732 4F2B 52B4 4F2C 5A41 4F2D 5ECA 4F2E 5F04 4F2F 6717 4F30 697C 4F31 6994 4F32 6D6A 4F33 6F0F 4F34 7262 4F35 72FC 4F36 7BED 4F37 8001 4F38 807E 4F39 874B 4F3A 90CE 4F3B 516D 4F3C 9E93 4F3D 7984 4F3E 808B 4F3F 9332 4F40 8AD6 4F41 502D 4F42 548C 4F43 8A71 4F44 6B6A 4F45 8CC4 4F46 8107 4F47 60D1 4F48 67A0 4F49 9DF2 4F4A 4E99 4F4B 4E98 4F4C 9C10 4F4D 8A6B 4F4E 85C1 4F4F 8568 4F50 6900 4F51 6E7E 4F52 7897 4F53 8155 5021 5F0C 5022 4E10 5023 4E15 5024 4E2A 5025 4E31 5026 4E36 5027 4E3C 5028 4E3F 5029 4E42 502A 4E56 502B 4E58 502C 4E82 502D 4E85 502E 8C6B 502F 4E8A 5030 8212 5031 5F0D 5032 4E8E 5033 4E9E 5034 4E9F 5035 4EA0 5036 4EA2 5037 4EB0 5038 4EB3 5039 4EB6 503A 4ECE 503B 4ECD 503C 4EC4 503D 4EC6 503E 4EC2 503F 4ED7 5040 4EDE 5041 4EED 5042 4EDF 5043 4EF7 5044 4F09 5045 4F5A 5046 4F30 5047 4F5B 5048 4F5D 5049 4F57 504A 4F47 504B 4F76 504C 4F88 504D 4F8F 504E 4F98 504F 4F7B 5050 4F69 5051 4F70 5052 4F91 5053 4F6F 5054 4F86 5055 4F96 5056 5118 5057 4FD4 5058 4FDF 5059 4FCE 505A 4FD8 505B 4FDB 505C 4FD1 505D 4FDA 505E 4FD0 505F 4FE4 5060 4FE5 5061 501A 5062 5028 5063 5014 5064 502A 5065 5025 5066 5005 5067 4F1C 5068 4FF6 5069 5021 506A 5029 506B 502C 506C 4FFE 506D 4FEF 506E 5011 506F 5006 5070 5043 5071 5047 5072 6703 5073 5055 5074 5050 5075 5048 5076 505A 5077 5056 5078 506C 5079 5078 507A 5080 507B 509A 507C 5085 507D 50B4 507E 50B2 5121 50C9 5122 50CA 5123 50B3 5124 50C2 5125 50D6 5126 50DE 5127 50E5 5128 50ED 5129 50E3 512A 50EE 512B 50F9 512C 50F5 512D 5109 512E 5101 512F 5102 5130 5116 5131 5115 5132 5114 5133 511A 5134 5121 5135 513A 5136 5137 5137 513C 5138 513B 5139 513F 513A 5140 513B 5152 513C 514C 513D 5154 513E 5162 513F 7AF8 5140 5169 5141 516A 5142 516E 5143 5180 5144 5182 5145 56D8 5146 518C 5147 5189 5148 518F 5149 5191 514A 5193 514B 5195 514C 5196 514D 51A4 514E 51A6 514F 51A2 5150 51A9 5151 51AA 5152 51AB 5153 51B3 5154 51B1 5155 51B2 5156 51B0 5157 51B5 5158 51BD 5159 51C5 515A 51C9 515B 51DB 515C 51E0 515D 8655 515E 51E9 515F 51ED 5160 51F0 5161 51F5 5162 51FE 5163 5204 5164 520B 5165 5214 5166 520E 5167 5227 5168 522A 5169 522E 516A 5233 516B 5239 516C 524F 516D 5244 516E 524B 516F 524C 5170 525E 5171 5254 5172 526A 5173 5274 5174 5269 5175 5273 5176 527F 5177 527D 5178 528D 5179 5294 517A 5292 517B 5271 517C 5288 517D 5291 517E 8FA8 5221 8FA7 5222 52AC 5223 52AD 5224 52BC 5225 52B5 5226 52C1 5227 52CD 5228 52D7 5229 52DE 522A 52E3 522B 52E6 522C 98ED 522D 52E0 522E 52F3 522F 52F5 5230 52F8 5231 52F9 5232 5306 5233 5308 5234 7538 5235 530D 5236 5310 5237 530F 5238 5315 5239 531A 523A 5323 523B 532F 523C 5331 523D 5333 523E 5338 523F 5340 5240 5346 5241 5345 5242 4E17 5243 5349 5244 534D 5245 51D6 5246 535E 5247 5369 5248 536E 5249 5918 524A 537B 524B 5377 524C 5382 524D 5396 524E 53A0 524F 53A6 5250 53A5 5251 53AE 5252 53B0 5253 53B6 5254 53C3 5255 7C12 5256 96D9 5257 53DF 5258 66FC 5259 71EE 525A 53EE 525B 53E8 525C 53ED 525D 53FA 525E 5401 525F 543D 5260 5440 5261 542C 5262 542D 5263 543C 5264 542E 5265 5436 5266 5429 5267 541D 5268 544E 5269 548F 526A 5475 526B 548E 526C 545F 526D 5471 526E 5477 526F 5470 5270 5492 5271 547B 5272 5480 5273 5476 5274 5484 5275 5490 5276 5486 5277 54C7 5278 54A2 5279 54B8 527A 54A5 527B 54AC 527C 54C4 527D 54C8 527E 54A8 5321 54AB 5322 54C2 5323 54A4 5324 54BE 5325 54BC 5326 54D8 5327 54E5 5328 54E6 5329 550F 532A 5514 532B 54FD 532C 54EE 532D 54ED 532E 54FA 532F 54E2 5330 5539 5331 5540 5332 5563 5333 554C 5334 552E 5335 555C 5336 5545 5337 5556 5338 5557 5339 5538 533A 5533 533B 555D 533C 5599 533D 5580 533E 54AF 533F 558A 5340 559F 5341 557B 5342 557E 5343 5598 5344 559E 5345 55AE 5346 557C 5347 5583 5348 55A9 5349 5587 534A 55A8 534B 55DA 534C 55C5 534D 55DF 534E 55C4 534F 55DC 5350 55E4 5351 55D4 5352 5614 5353 55F7 5354 5616 5355 55FE 5356 55FD 5357 561B 5358 55F9 5359 564E 535A 5650 535B 71DF 535C 5634 535D 5636 535E 5632 535F 5638 5360 566B 5361 5664 5362 562F 5363 566C 5364 566A 5365 5686 5366 5680 5367 568A 5368 56A0 5369 5694 536A 568F 536B 56A5 536C 56AE 536D 56B6 536E 56B4 536F 56C2 5370 56BC 5371 56C1 5372 56C3 5373 56C0 5374 56C8 5375 56CE 5376 56D1 5377 56D3 5378 56D7 5379 56EE 537A 56F9 537B 5700 537C 56FF 537D 5704 537E 5709 5421 5708 5422 570B 5423 570D 5424 5713 5425 5718 5426 5716 5427 55C7 5428 571C 5429 5726 542A 5737 542B 5738 542C 574E 542D 573B 542E 5740 542F 574F 5430 5769 5431 57C0 5432 5788 5433 5761 5434 577F 5435 5789 5436 5793 5437 57A0 5438 57B3 5439 57A4 543A 57AA 543B 57B0 543C 57C3 543D 57C6 543E 57D4 543F 57D2 5440 57D3 5441 580A 5442 57D6 5443 57E3 5444 580B 5445 5819 5446 581D 5447 5872 5448 5821 5449 5862 544A 584B 544B 5870 544C 6BC0 544D 5852 544E 583D 544F 5879 5450 5885 5451 58B9 5452 589F 5453 58AB 5454 58BA 5455 58DE 5456 58BB 5457 58B8 5458 58AE 5459 58C5 545A 58D3 545B 58D1 545C 58D7 545D 58D9 545E 58D8 545F 58E5 5460 58DC 5461 58E4 5462 58DF 5463 58EF 5464 58FA 5465 58F9 5466 58FB 5467 58FC 5468 58FD 5469 5902 546A 590A 546B 5910 546C 591B 546D 68A6 546E 5925 546F 592C 5470 592D 5471 5932 5472 5938 5473 593E 5474 7AD2 5475 5955 5476 5950 5477 594E 5478 595A 5479 5958 547A 5962 547B 5960 547C 5967 547D 596C 547E 5969 5521 5978 5522 5981 5523 599D 5524 4F5E 5525 4FAB 5526 59A3 5527 59B2 5528 59C6 5529 59E8 552A 59DC 552B 598D 552C 59D9 552D 59DA 552E 5A25 552F 5A1F 5530 5A11 5531 5A1C 5532 5A09 5533 5A1A 5534 5A40 5535 5A6C 5536 5A49 5537 5A35 5538 5A36 5539 5A62 553A 5A6A 553B 5A9A 553C 5ABC 553D 5ABE 553E 5ACB 553F 5AC2 5540 5ABD 5541 5AE3 5542 5AD7 5543 5AE6 5544 5AE9 5545 5AD6 5546 5AFA 5547 5AFB 5548 5B0C 5549 5B0B 554A 5B16 554B 5B32 554C 5AD0 554D 5B2A 554E 5B36 554F 5B3E 5550 5B43 5551 5B45 5552 5B40 5553 5B51 5554 5B55 5555 5B5A 5556 5B5B 5557 5B65 5558 5B69 5559 5B70 555A 5B73 555B 5B75 555C 5B78 555D 6588 555E 5B7A 555F 5B80 5560 5B83 5561 5BA6 5562 5BB8 5563 5BC3 5564 5BC7 5565 5BC9 5566 5BD4 5567 5BD0 5568 5BE4 5569 5BE6 556A 5BE2 556B 5BDE 556C 5BE5 556D 5BEB 556E 5BF0 556F 5BF6 5570 5BF3 5571 5C05 5572 5C07 5573 5C08 5574 5C0D 5575 5C13 5576 5C20 5577 5C22 5578 5C28 5579 5C38 557A 5C39 557B 5C41 557C 5C46 557D 5C4E 557E 5C53 5621 5C50 5622 5C4F 5623 5B71 5624 5C6C 5625 5C6E 5626 4E62 5627 5C76 5628 5C79 5629 5C8C 562A 5C91 562B 5C94 562C 599B 562D 5CAB 562E 5CBB 562F 5CB6 5630 5CBC 5631 5CB7 5632 5CC5 5633 5CBE 5634 5CC7 5635 5CD9 5636 5CE9 5637 5CFD 5638 5CFA 5639 5CED 563A 5D8C 563B 5CEA 563C 5D0B 563D 5D15 563E 5D17 563F 5D5C 5640 5D1F 5641 5D1B 5642 5D11 5643 5D14 5644 5D22 5645 5D1A 5646 5D19 5647 5D18 5648 5D4C 5649 5D52 564A 5D4E 564B 5D4B 564C 5D6C 564D 5D73 564E 5D76 564F 5D87 5650 5D84 5651 5D82 5652 5DA2 5653 5D9D 5654 5DAC 5655 5DAE 5656 5DBD 5657 5D90 5658 5DB7 5659 5DBC 565A 5DC9 565B 5DCD 565C 5DD3 565D 5DD2 565E 5DD6 565F 5DDB 5660 5DEB 5661 5DF2 5662 5DF5 5663 5E0B 5664 5E1A 5665 5E19 5666 5E11 5667 5E1B 5668 5E36 5669 5E37 566A 5E44 566B 5E43 566C 5E40 566D 5E4E 566E 5E57 566F 5E54 5670 5E5F 5671 5E62 5672 5E64 5673 5E47 5674 5E75 5675 5E76 5676 5E7A 5677 9EBC 5678 5E7F 5679 5EA0 567A 5EC1 567B 5EC2 567C 5EC8 567D 5ED0 567E 5ECF 5721 5ED6 5722 5EE3 5723 5EDD 5724 5EDA 5725 5EDB 5726 5EE2 5727 5EE1 5728 5EE8 5729 5EE9 572A 5EEC 572B 5EF1 572C 5EF3 572D 5EF0 572E 5EF4 572F 5EF8 5730 5EFE 5731 5F03 5732 5F09 5733 5F5D 5734 5F5C 5735 5F0B 5736 5F11 5737 5F16 5738 5F29 5739 5F2D 573A 5F38 573B 5F41 573C 5F48 573D 5F4C 573E 5F4E 573F 5F2F 5740 5F51 5741 5F56 5742 5F57 5743 5F59 5744 5F61 5745 5F6D 5746 5F73 5747 5F77 5748 5F83 5749 5F82 574A 5F7F 574B 5F8A 574C 5F88 574D 5F91 574E 5F87 574F 5F9E 5750 5F99 5751 5F98 5752 5FA0 5753 5FA8 5754 5FAD 5755 5FBC 5756 5FD6 5757 5FFB 5758 5FE4 5759 5FF8 575A 5FF1 575B 5FDD 575C 60B3 575D 5FFF 575E 6021 575F 6060 5760 6019 5761 6010 5762 6029 5763 600E 5764 6031 5765 601B 5766 6015 5767 602B 5768 6026 5769 600F 576A 603A 576B 605A 576C 6041 576D 606A 576E 6077 576F 605F 5770 604A 5771 6046 5772 604D 5773 6063 5774 6043 5775 6064 5776 6042 5777 606C 5778 606B 5779 6059 577A 6081 577B 608D 577C 60E7 577D 6083 577E 609A 5821 6084 5822 609B 5823 6096 5824 6097 5825 6092 5826 60A7 5827 608B 5828 60E1 5829 60B8 582A 60E0 582B 60D3 582C 60B4 582D 5FF0 582E 60BD 582F 60C6 5830 60B5 5831 60D8 5832 614D 5833 6115 5834 6106 5835 60F6 5836 60F7 5837 6100 5838 60F4 5839 60FA 583A 6103 583B 6121 583C 60FB 583D 60F1 583E 610D 583F 610E 5840 6147 5841 613E 5842 6128 5843 6127 5844 614A 5845 613F 5846 613C 5847 612C 5848 6134 5849 613D 584A 6142 584B 6144 584C 6173 584D 6177 584E 6158 584F 6159 5850 615A 5851 616B 5852 6174 5853 616F 5854 6165 5855 6171 5856 615F 5857 615D 5858 6153 5859 6175 585A 6199 585B 6196 585C 6187 585D 61AC 585E 6194 585F 619A 5860 618A 5861 6191 5862 61AB 5863 61AE 5864 61CC 5865 61CA 5866 61C9 5867 61F7 5868 61C8 5869 61C3 586A 61C6 586B 61BA 586C 61CB 586D 7F79 586E 61CD 586F 61E6 5870 61E3 5871 61F6 5872 61FA 5873 61F4 5874 61FF 5875 61FD 5876 61FC 5877 61FE 5878 6200 5879 6208 587A 6209 587B 620D 587C 620C 587D 6214 587E 621B 5921 621E 5922 6221 5923 622A 5924 622E 5925 6230 5926 6232 5927 6233 5928 6241 5929 624E 592A 625E 592B 6263 592C 625B 592D 6260 592E 6268 592F 627C 5930 6282 5931 6289 5932 627E 5933 6292 5934 6293 5935 6296 5936 62D4 5937 6283 5938 6294 5939 62D7 593A 62D1 593B 62BB 593C 62CF 593D 62FF 593E 62C6 593F 64D4 5940 62C8 5941 62DC 5942 62CC 5943 62CA 5944 62C2 5945 62C7 5946 629B 5947 62C9 5948 630C 5949 62EE 594A 62F1 594B 6327 594C 6302 594D 6308 594E 62EF 594F 62F5 5950 6350 5951 633E 5952 634D 5953 641C 5954 634F 5955 6396 5956 638E 5957 6380 5958 63AB 5959 6376 595A 63A3 595B 638F 595C 6389 595D 639F 595E 63B5 595F 636B 5960 6369 5961 63BE 5962 63E9 5963 63C0 5964 63C6 5965 63E3 5966 63C9 5967 63D2 5968 63F6 5969 63C4 596A 6416 596B 6434 596C 6406 596D 6413 596E 6426 596F 6436 5970 651D 5971 6417 5972 6428 5973 640F 5974 6467 5975 646F 5976 6476 5977 644E 5978 652A 5979 6495 597A 6493 597B 64A5 597C 64A9 597D 6488 597E 64BC 5A21 64DA 5A22 64D2 5A23 64C5 5A24 64C7 5A25 64BB 5A26 64D8 5A27 64C2 5A28 64F1 5A29 64E7 5A2A 8209 5A2B 64E0 5A2C 64E1 5A2D 62AC 5A2E 64E3 5A2F 64EF 5A30 652C 5A31 64F6 5A32 64F4 5A33 64F2 5A34 64FA 5A35 6500 5A36 64FD 5A37 6518 5A38 651C 5A39 6505 5A3A 6524 5A3B 6523 5A3C 652B 5A3D 6534 5A3E 6535 5A3F 6537 5A40 6536 5A41 6538 5A42 754B 5A43 6548 5A44 6556 5A45 6555 5A46 654D 5A47 6558 5A48 655E 5A49 655D 5A4A 6572 5A4B 6578 5A4C 6582 5A4D 6583 5A4E 8B8A 5A4F 659B 5A50 659F 5A51 65AB 5A52 65B7 5A53 65C3 5A54 65C6 5A55 65C1 5A56 65C4 5A57 65CC 5A58 65D2 5A59 65DB 5A5A 65D9 5A5B 65E0 5A5C 65E1 5A5D 65F1 5A5E 6772 5A5F 660A 5A60 6603 5A61 65FB 5A62 6773 5A63 6635 5A64 6636 5A65 6634 5A66 661C 5A67 664F 5A68 6644 5A69 6649 5A6A 6641 5A6B 665E 5A6C 665D 5A6D 6664 5A6E 6667 5A6F 6668 5A70 665F 5A71 6662 5A72 6670 5A73 6683 5A74 6688 5A75 668E 5A76 6689 5A77 6684 5A78 6698 5A79 669D 5A7A 66C1 5A7B 66B9 5A7C 66C9 5A7D 66BE 5A7E 66BC 5B21 66C4 5B22 66B8 5B23 66D6 5B24 66DA 5B25 66E0 5B26 663F 5B27 66E6 5B28 66E9 5B29 66F0 5B2A 66F5 5B2B 66F7 5B2C 670F 5B2D 6716 5B2E 671E 5B2F 6726 5B30 6727 5B31 9738 5B32 672E 5B33 673F 5B34 6736 5B35 6741 5B36 6738 5B37 6737 5B38 6746 5B39 675E 5B3A 6760 5B3B 6759 5B3C 6763 5B3D 6764 5B3E 6789 5B3F 6770 5B40 67A9 5B41 677C 5B42 676A 5B43 678C 5B44 678B 5B45 67A6 5B46 67A1 5B47 6785 5B48 67B7 5B49 67EF 5B4A 67B4 5B4B 67EC 5B4C 67B3 5B4D 67E9 5B4E 67B8 5B4F 67E4 5B50 67DE 5B51 67DD 5B52 67E2 5B53 67EE 5B54 67B9 5B55 67CE 5B56 67C6 5B57 67E7 5B58 6A9C 5B59 681E 5B5A 6846 5B5B 6829 5B5C 6840 5B5D 684D 5B5E 6832 5B5F 684E 5B60 68B3 5B61 682B 5B62 6859 5B63 6863 5B64 6877 5B65 687F 5B66 689F 5B67 688F 5B68 68AD 5B69 6894 5B6A 689D 5B6B 689B 5B6C 6883 5B6D 6AAE 5B6E 68B9 5B6F 6874 5B70 68B5 5B71 68A0 5B72 68BA 5B73 690F 5B74 688D 5B75 687E 5B76 6901 5B77 68CA 5B78 6908 5B79 68D8 5B7A 6922 5B7B 6926 5B7C 68E1 5B7D 690C 5B7E 68CD 5C21 68D4 5C22 68E7 5C23 68D5 5C24 6936 5C25 6912 5C26 6904 5C27 68D7 5C28 68E3 5C29 6925 5C2A 68F9 5C2B 68E0 5C2C 68EF 5C2D 6928 5C2E 692A 5C2F 691A 5C30 6923 5C31 6921 5C32 68C6 5C33 6979 5C34 6977 5C35 695C 5C36 6978 5C37 696B 5C38 6954 5C39 697E 5C3A 696E 5C3B 6939 5C3C 6974 5C3D 693D 5C3E 6959 5C3F 6930 5C40 6961 5C41 695E 5C42 695D 5C43 6981 5C44 696A 5C45 69B2 5C46 69AE 5C47 69D0 5C48 69BF 5C49 69C1 5C4A 69D3 5C4B 69BE 5C4C 69CE 5C4D 5BE8 5C4E 69CA 5C4F 69DD 5C50 69BB 5C51 69C3 5C52 69A7 5C53 6A2E 5C54 6991 5C55 69A0 5C56 699C 5C57 6995 5C58 69B4 5C59 69DE 5C5A 69E8 5C5B 6A02 5C5C 6A1B 5C5D 69FF 5C5E 6B0A 5C5F 69F9 5C60 69F2 5C61 69E7 5C62 6A05 5C63 69B1 5C64 6A1E 5C65 69ED 5C66 6A14 5C67 69EB 5C68 6A0A 5C69 6A12 5C6A 6AC1 5C6B 6A23 5C6C 6A13 5C6D 6A44 5C6E 6A0C 5C6F 6A72 5C70 6A36 5C71 6A78 5C72 6A47 5C73 6A62 5C74 6A59 5C75 6A66 5C76 6A48 5C77 6A38 5C78 6A22 5C79 6A90 5C7A 6A8D 5C7B 6AA0 5C7C 6A84 5C7D 6AA2 5C7E 6AA3 5D21 6A97 5D22 8617 5D23 6ABB 5D24 6AC3 5D25 6AC2 5D26 6AB8 5D27 6AB3 5D28 6AAC 5D29 6ADE 5D2A 6AD1 5D2B 6ADF 5D2C 6AAA 5D2D 6ADA 5D2E 6AEA 5D2F 6AFB 5D30 6B05 5D31 8616 5D32 6AFA 5D33 6B12 5D34 6B16 5D35 9B31 5D36 6B1F 5D37 6B38 5D38 6B37 5D39 76DC 5D3A 6B39 5D3B 98EE 5D3C 6B47 5D3D 6B43 5D3E 6B49 5D3F 6B50 5D40 6B59 5D41 6B54 5D42 6B5B 5D43 6B5F 5D44 6B61 5D45 6B78 5D46 6B79 5D47 6B7F 5D48 6B80 5D49 6B84 5D4A 6B83 5D4B 6B8D 5D4C 6B98 5D4D 6B95 5D4E 6B9E 5D4F 6BA4 5D50 6BAA 5D51 6BAB 5D52 6BAF 5D53 6BB2 5D54 6BB1 5D55 6BB3 5D56 6BB7 5D57 6BBC 5D58 6BC6 5D59 6BCB 5D5A 6BD3 5D5B 6BDF 5D5C 6BEC 5D5D 6BEB 5D5E 6BF3 5D5F 6BEF 5D60 9EBE 5D61 6C08 5D62 6C13 5D63 6C14 5D64 6C1B 5D65 6C24 5D66 6C23 5D67 6C5E 5D68 6C55 5D69 6C62 5D6A 6C6A 5D6B 6C82 5D6C 6C8D 5D6D 6C9A 5D6E 6C81 5D6F 6C9B 5D70 6C7E 5D71 6C68 5D72 6C73 5D73 6C92 5D74 6C90 5D75 6CC4 5D76 6CF1 5D77 6CD3 5D78 6CBD 5D79 6CD7 5D7A 6CC5 5D7B 6CDD 5D7C 6CAE 5D7D 6CB1 5D7E 6CBE 5E21 6CBA 5E22 6CDB 5E23 6CEF 5E24 6CD9 5E25 6CEA 5E26 6D1F 5E27 884D 5E28 6D36 5E29 6D2B 5E2A 6D3D 5E2B 6D38 5E2C 6D19 5E2D 6D35 5E2E 6D33 5E2F 6D12 5E30 6D0C 5E31 6D63 5E32 6D93 5E33 6D64 5E34 6D5A 5E35 6D79 5E36 6D59 5E37 6D8E 5E38 6D95 5E39 6FE4 5E3A 6D85 5E3B 6DF9 5E3C 6E15 5E3D 6E0A 5E3E 6DB5 5E3F 6DC7 5E40 6DE6 5E41 6DB8 5E42 6DC6 5E43 6DEC 5E44 6DDE 5E45 6DCC 5E46 6DE8 5E47 6DD2 5E48 6DC5 5E49 6DFA 5E4A 6DD9 5E4B 6DE4 5E4C 6DD5 5E4D 6DEA 5E4E 6DEE 5E4F 6E2D 5E50 6E6E 5E51 6E2E 5E52 6E19 5E53 6E72 5E54 6E5F 5E55 6E3E 5E56 6E23 5E57 6E6B 5E58 6E2B 5E59 6E76 5E5A 6E4D 5E5B 6E1F 5E5C 6E43 5E5D 6E3A 5E5E 6E4E 5E5F 6E24 5E60 6EFF 5E61 6E1D 5E62 6E38 5E63 6E82 5E64 6EAA 5E65 6E98 5E66 6EC9 5E67 6EB7 5E68 6ED3 5E69 6EBD 5E6A 6EAF 5E6B 6EC4 5E6C 6EB2 5E6D 6ED4 5E6E 6ED5 5E6F 6E8F 5E70 6EA5 5E71 6EC2 5E72 6E9F 5E73 6F41 5E74 6F11 5E75 704C 5E76 6EEC 5E77 6EF8 5E78 6EFE 5E79 6F3F 5E7A 6EF2 5E7B 6F31 5E7C 6EEF 5E7D 6F32 5E7E 6ECC 5F21 6F3E 5F22 6F13 5F23 6EF7 5F24 6F86 5F25 6F7A 5F26 6F78 5F27 6F81 5F28 6F80 5F29 6F6F 5F2A 6F5B 5F2B 6FF3 5F2C 6F6D 5F2D 6F82 5F2E 6F7C 5F2F 6F58 5F30 6F8E 5F31 6F91 5F32 6FC2 5F33 6F66 5F34 6FB3 5F35 6FA3 5F36 6FA1 5F37 6FA4 5F38 6FB9 5F39 6FC6 5F3A 6FAA 5F3B 6FDF 5F3C 6FD5 5F3D 6FEC 5F3E 6FD4 5F3F 6FD8 5F40 6FF1 5F41 6FEE 5F42 6FDB 5F43 7009 5F44 700B 5F45 6FFA 5F46 7011 5F47 7001 5F48 700F 5F49 6FFE 5F4A 701B 5F4B 701A 5F4C 6F74 5F4D 701D 5F4E 7018 5F4F 701F 5F50 7030 5F51 703E 5F52 7032 5F53 7051 5F54 7063 5F55 7099 5F56 7092 5F57 70AF 5F58 70F1 5F59 70AC 5F5A 70B8 5F5B 70B3 5F5C 70AE 5F5D 70DF 5F5E 70CB 5F5F 70DD 5F60 70D9 5F61 7109 5F62 70FD 5F63 711C 5F64 7119 5F65 7165 5F66 7155 5F67 7188 5F68 7166 5F69 7162 5F6A 714C 5F6B 7156 5F6C 716C 5F6D 718F 5F6E 71FB 5F6F 7184 5F70 7195 5F71 71A8 5F72 71AC 5F73 71D7 5F74 71B9 5F75 71BE 5F76 71D2 5F77 71C9 5F78 71D4 5F79 71CE 5F7A 71E0 5F7B 71EC 5F7C 71E7 5F7D 71F5 5F7E 71FC 6021 71F9 6022 71FF 6023 720D 6024 7210 6025 721B 6026 7228 6027 722D 6028 722C 6029 7230 602A 7232 602B 723B 602C 723C 602D 723F 602E 7240 602F 7246 6030 724B 6031 7258 6032 7274 6033 727E 6034 7282 6035 7281 6036 7287 6037 7292 6038 7296 6039 72A2 603A 72A7 603B 72B9 603C 72B2 603D 72C3 603E 72C6 603F 72C4 6040 72CE 6041 72D2 6042 72E2 6043 72E0 6044 72E1 6045 72F9 6046 72F7 6047 500F 6048 7317 6049 730A 604A 731C 604B 7316 604C 731D 604D 7334 604E 732F 604F 7329 6050 7325 6051 733E 6052 734E 6053 734F 6054 9ED8 6055 7357 6056 736A 6057 7368 6058 7370 6059 7378 605A 7375 605B 737B 605C 737A 605D 73C8 605E 73B3 605F 73CE 6060 73BB 6061 73C0 6062 73E5 6063 73EE 6064 73DE 6065 74A2 6066 7405 6067 746F 6068 7425 6069 73F8 606A 7432 606B 743A 606C 7455 606D 743F 606E 745F 606F 7459 6070 7441 6071 745C 6072 7469 6073 7470 6074 7463 6075 746A 6076 7476 6077 747E 6078 748B 6079 749E 607A 74A7 607B 74CA 607C 74CF 607D 74D4 607E 73F1 6121 74E0 6122 74E3 6123 74E7 6124 74E9 6125 74EE 6126 74F2 6127 74F0 6128 74F1 6129 74F8 612A 74F7 612B 7504 612C 7503 612D 7505 612E 750C 612F 750E 6130 750D 6131 7515 6132 7513 6133 751E 6134 7526 6135 752C 6136 753C 6137 7544 6138 754D 6139 754A 613A 7549 613B 755B 613C 7546 613D 755A 613E 7569 613F 7564 6140 7567 6141 756B 6142 756D 6143 7578 6144 7576 6145 7586 6146 7587 6147 7574 6148 758A 6149 7589 614A 7582 614B 7594 614C 759A 614D 759D 614E 75A5 614F 75A3 6150 75C2 6151 75B3 6152 75C3 6153 75B5 6154 75BD 6155 75B8 6156 75BC 6157 75B1 6158 75CD 6159 75CA 615A 75D2 615B 75D9 615C 75E3 615D 75DE 615E 75FE 615F 75FF 6160 75FC 6161 7601 6162 75F0 6163 75FA 6164 75F2 6165 75F3 6166 760B 6167 760D 6168 7609 6169 761F 616A 7627 616B 7620 616C 7621 616D 7622 616E 7624 616F 7634 6170 7630 6171 763B 6172 7647 6173 7648 6174 7646 6175 765C 6176 7658 6177 7661 6178 7662 6179 7668 617A 7669 617B 766A 617C 7667 617D 766C 617E 7670 6221 7672 6222 7676 6223 7678 6224 767C 6225 7680 6226 7683 6227 7688 6228 768B 6229 768E 622A 7696 622B 7693 622C 7699 622D 769A 622E 76B0 622F 76B4 6230 76B8 6231 76B9 6232 76BA 6233 76C2 6234 76CD 6235 76D6 6236 76D2 6237 76DE 6238 76E1 6239 76E5 623A 76E7 623B 76EA 623C 862F 623D 76FB 623E 7708 623F 7707 6240 7704 6241 7729 6242 7724 6243 771E 6244 7725 6245 7726 6246 771B 6247 7737 6248 7738 6249 7747 624A 775A 624B 7768 624C 776B 624D 775B 624E 7765 624F 777F 6250 777E 6251 7779 6252 778E 6253 778B 6254 7791 6255 77A0 6256 779E 6257 77B0 6258 77B6 6259 77B9 625A 77BF 625B 77BC 625C 77BD 625D 77BB 625E 77C7 625F 77CD 6260 77D7 6261 77DA 6262 77DC 6263 77E3 6264 77EE 6265 77FC 6266 780C 6267 7812 6268 7926 6269 7820 626A 792A 626B 7845 626C 788E 626D 7874 626E 7886 626F 787C 6270 789A 6271 788C 6272 78A3 6273 78B5 6274 78AA 6275 78AF 6276 78D1 6277 78C6 6278 78CB 6279 78D4 627A 78BE 627B 78BC 627C 78C5 627D 78CA 627E 78EC 6321 78E7 6322 78DA 6323 78FD 6324 78F4 6325 7907 6326 7912 6327 7911 6328 7919 6329 792C 632A 792B 632B 7940 632C 7960 632D 7957 632E 795F 632F 795A 6330 7955 6331 7953 6332 797A 6333 797F 6334 798A 6335 799D 6336 79A7 6337 9F4B 6338 79AA 6339 79AE 633A 79B3 633B 79B9 633C 79BA 633D 79C9 633E 79D5 633F 79E7 6340 79EC 6341 79E1 6342 79E3 6343 7A08 6344 7A0D 6345 7A18 6346 7A19 6347 7A20 6348 7A1F 6349 7980 634A 7A31 634B 7A3B 634C 7A3E 634D 7A37 634E 7A43 634F 7A57 6350 7A49 6351 7A61 6352 7A62 6353 7A69 6354 9F9D 6355 7A70 6356 7A79 6357 7A7D 6358 7A88 6359 7A97 635A 7A95 635B 7A98 635C 7A96 635D 7AA9 635E 7AC8 635F 7AB0 6360 7AB6 6361 7AC5 6362 7AC4 6363 7ABF 6364 9083 6365 7AC7 6366 7ACA 6367 7ACD 6368 7ACF 6369 7AD5 636A 7AD3 636B 7AD9 636C 7ADA 636D 7ADD 636E 7AE1 636F 7AE2 6370 7AE6 6371 7AED 6372 7AF0 6373 7B02 6374 7B0F 6375 7B0A 6376 7B06 6377 7B33 6378 7B18 6379 7B19 637A 7B1E 637B 7B35 637C 7B28 637D 7B36 637E 7B50 6421 7B7A 6422 7B04 6423 7B4D 6424 7B0B 6425 7B4C 6426 7B45 6427 7B75 6428 7B65 6429 7B74 642A 7B67 642B 7B70 642C 7B71 642D 7B6C 642E 7B6E 642F 7B9D 6430 7B98 6431 7B9F 6432 7B8D 6433 7B9C 6434 7B9A 6435 7B8B 6436 7B92 6437 7B8F 6438 7B5D 6439 7B99 643A 7BCB 643B 7BC1 643C 7BCC 643D 7BCF 643E 7BB4 643F 7BC6 6440 7BDD 6441 7BE9 6442 7C11 6443 7C14 6444 7BE6 6445 7BE5 6446 7C60 6447 7C00 6448 7C07 6449 7C13 644A 7BF3 644B 7BF7 644C 7C17 644D 7C0D 644E 7BF6 644F 7C23 6450 7C27 6451 7C2A 6452 7C1F 6453 7C37 6454 7C2B 6455 7C3D 6456 7C4C 6457 7C43 6458 7C54 6459 7C4F 645A 7C40 645B 7C50 645C 7C58 645D 7C5F 645E 7C64 645F 7C56 6460 7C65 6461 7C6C 6462 7C75 6463 7C83 6464 7C90 6465 7CA4 6466 7CAD 6467 7CA2 6468 7CAB 6469 7CA1 646A 7CA8 646B 7CB3 646C 7CB2 646D 7CB1 646E 7CAE 646F 7CB9 6470 7CBD 6471 7CC0 6472 7CC5 6473 7CC2 6474 7CD8 6475 7CD2 6476 7CDC 6477 7CE2 6478 9B3B 6479 7CEF 647A 7CF2 647B 7CF4 647C 7CF6 647D 7CFA 647E 7D06 6521 7D02 6522 7D1C 6523 7D15 6524 7D0A 6525 7D45 6526 7D4B 6527 7D2E 6528 7D32 6529 7D3F 652A 7D35 652B 7D46 652C 7D73 652D 7D56 652E 7D4E 652F 7D72 6530 7D68 6531 7D6E 6532 7D4F 6533 7D63 6534 7D93 6535 7D89 6536 7D5B 6537 7D8F 6538 7D7D 6539 7D9B 653A 7DBA 653B 7DAE 653C 7DA3 653D 7DB5 653E 7DC7 653F 7DBD 6540 7DAB 6541 7E3D 6542 7DA2 6543 7DAF 6544 7DDC 6545 7DB8 6546 7D9F 6547 7DB0 6548 7DD8 6549 7DDD 654A 7DE4 654B 7DDE 654C 7DFB 654D 7DF2 654E 7DE1 654F 7E05 6550 7E0A 6551 7E23 6552 7E21 6553 7E12 6554 7E31 6555 7E1F 6556 7E09 6557 7E0B 6558 7E22 6559 7E46 655A 7E66 655B 7E3B 655C 7E35 655D 7E39 655E 7E43 655F 7E37 6560 7E32 6561 7E3A 6562 7E67 6563 7E5D 6564 7E56 6565 7E5E 6566 7E59 6567 7E5A 6568 7E79 6569 7E6A 656A 7E69 656B 7E7C 656C 7E7B 656D 7E83 656E 7DD5 656F 7E7D 6570 8FAE 6571 7E7F 6572 7E88 6573 7E89 6574 7E8C 6575 7E92 6576 7E90 6577 7E93 6578 7E94 6579 7E96 657A 7E8E 657B 7E9B 657C 7E9C 657D 7F38 657E 7F3A 6621 7F45 6622 7F4C 6623 7F4D 6624 7F4E 6625 7F50 6626 7F51 6627 7F55 6628 7F54 6629 7F58 662A 7F5F 662B 7F60 662C 7F68 662D 7F69 662E 7F67 662F 7F78 6630 7F82 6631 7F86 6632 7F83 6633 7F88 6634 7F87 6635 7F8C 6636 7F94 6637 7F9E 6638 7F9D 6639 7F9A 663A 7FA3 663B 7FAF 663C 7FB2 663D 7FB9 663E 7FAE 663F 7FB6 6640 7FB8 6641 8B71 6642 7FC5 6643 7FC6 6644 7FCA 6645 7FD5 6646 7FD4 6647 7FE1 6648 7FE6 6649 7FE9 664A 7FF3 664B 7FF9 664C 98DC 664D 8006 664E 8004 664F 800B 6650 8012 6651 8018 6652 8019 6653 801C 6654 8021 6655 8028 6656 803F 6657 803B 6658 804A 6659 8046 665A 8052 665B 8058 665C 805A 665D 805F 665E 8062 665F 8068 6660 8073 6661 8072 6662 8070 6663 8076 6664 8079 6665 807D 6666 807F 6667 8084 6668 8086 6669 8085 666A 809B 666B 8093 666C 809A 666D 80AD 666E 5190 666F 80AC 6670 80DB 6671 80E5 6672 80D9 6673 80DD 6674 80C4 6675 80DA 6676 80D6 6677 8109 6678 80EF 6679 80F1 667A 811B 667B 8129 667C 8123 667D 812F 667E 814B 6721 968B 6722 8146 6723 813E 6724 8153 6725 8151 6726 80FC 6727 8171 6728 816E 6729 8165 672A 8166 672B 8174 672C 8183 672D 8188 672E 818A 672F 8180 6730 8182 6731 81A0 6732 8195 6733 81A4 6734 81A3 6735 815F 6736 8193 6737 81A9 6738 81B0 6739 81B5 673A 81BE 673B 81B8 673C 81BD 673D 81C0 673E 81C2 673F 81BA 6740 81C9 6741 81CD 6742 81D1 6743 81D9 6744 81D8 6745 81C8 6746 81DA 6747 81DF 6748 81E0 6749 81E7 674A 81FA 674B 81FB 674C 81FE 674D 8201 674E 8202 674F 8205 6750 8207 6751 820A 6752 820D 6753 8210 6754 8216 6755 8229 6756 822B 6757 8238 6758 8233 6759 8240 675A 8259 675B 8258 675C 825D 675D 825A 675E 825F 675F 8264 6760 8262 6761 8268 6762 826A 6763 826B 6764 822E 6765 8271 6766 8277 6767 8278 6768 827E 6769 828D 676A 8292 676B 82AB 676C 829F 676D 82BB 676E 82AC 676F 82E1 6770 82E3 6771 82DF 6772 82D2 6773 82F4 6774 82F3 6775 82FA 6776 8393 6777 8303 6778 82FB 6779 82F9 677A 82DE 677B 8306 677C 82DC 677D 8309 677E 82D9 6821 8335 6822 8334 6823 8316 6824 8332 6825 8331 6826 8340 6827 8339 6828 8350 6829 8345 682A 832F 682B 832B 682C 8317 682D 8318 682E 8385 682F 839A 6830 83AA 6831 839F 6832 83A2 6833 8396 6834 8323 6835 838E 6836 8387 6837 838A 6838 837C 6839 83B5 683A 8373 683B 8375 683C 83A0 683D 8389 683E 83A8 683F 83F4 6840 8413 6841 83EB 6842 83CE 6843 83FD 6844 8403 6845 83D8 6846 840B 6847 83C1 6848 83F7 6849 8407 684A 83E0 684B 83F2 684C 840D 684D 8422 684E 8420 684F 83BD 6850 8438 6851 8506 6852 83FB 6853 846D 6854 842A 6855 843C 6856 855A 6857 8484 6858 8477 6859 846B 685A 84AD 685B 846E 685C 8482 685D 8469 685E 8446 685F 842C 6860 846F 6861 8479 6862 8435 6863 84CA 6864 8462 6865 84B9 6866 84BF 6867 849F 6868 84D9 6869 84CD 686A 84BB 686B 84DA 686C 84D0 686D 84C1 686E 84C6 686F 84D6 6870 84A1 6871 8521 6872 84FF 6873 84F4 6874 8517 6875 8518 6876 852C 6877 851F 6878 8515 6879 8514 687A 84FC 687B 8540 687C 8563 687D 8558 687E 8548 6921 8541 6922 8602 6923 854B 6924 8555 6925 8580 6926 85A4 6927 8588 6928 8591 6929 858A 692A 85A8 692B 856D 692C 8594 692D 859B 692E 85EA 692F 8587 6930 859C 6931 8577 6932 857E 6933 8590 6934 85C9 6935 85BA 6936 85CF 6937 85B9 6938 85D0 6939 85D5 693A 85DD 693B 85E5 693C 85DC 693D 85F9 693E 860A 693F 8613 6940 860B 6941 85FE 6942 85FA 6943 8606 6944 8622 6945 861A 6946 8630 6947 863F 6948 864D 6949 4E55 694A 8654 694B 865F 694C 8667 694D 8671 694E 8693 694F 86A3 6950 86A9 6951 86AA 6952 868B 6953 868C 6954 86B6 6955 86AF 6956 86C4 6957 86C6 6958 86B0 6959 86C9 695A 8823 695B 86AB 695C 86D4 695D 86DE 695E 86E9 695F 86EC 6960 86DF 6961 86DB 6962 86EF 6963 8712 6964 8706 6965 8708 6966 8700 6967 8703 6968 86FB 6969 8711 696A 8709 696B 870D 696C 86F9 696D 870A 696E 8734 696F 873F 6970 8737 6971 873B 6972 8725 6973 8729 6974 871A 6975 8760 6976 875F 6977 8778 6978 874C 6979 874E 697A 8774 697B 8757 697C 8768 697D 876E 697E 8759 6A21 8753 6A22 8763 6A23 876A 6A24 8805 6A25 87A2 6A26 879F 6A27 8782 6A28 87AF 6A29 87CB 6A2A 87BD 6A2B 87C0 6A2C 87D0 6A2D 96D6 6A2E 87AB 6A2F 87C4 6A30 87B3 6A31 87C7 6A32 87C6 6A33 87BB 6A34 87EF 6A35 87F2 6A36 87E0 6A37 880F 6A38 880D 6A39 87FE 6A3A 87F6 6A3B 87F7 6A3C 880E 6A3D 87D2 6A3E 8811 6A3F 8816 6A40 8815 6A41 8822 6A42 8821 6A43 8831 6A44 8836 6A45 8839 6A46 8827 6A47 883B 6A48 8844 6A49 8842 6A4A 8852 6A4B 8859 6A4C 885E 6A4D 8862 6A4E 886B 6A4F 8881 6A50 887E 6A51 889E 6A52 8875 6A53 887D 6A54 88B5 6A55 8872 6A56 8882 6A57 8897 6A58 8892 6A59 88AE 6A5A 8899 6A5B 88A2 6A5C 888D 6A5D 88A4 6A5E 88B0 6A5F 88BF 6A60 88B1 6A61 88C3 6A62 88C4 6A63 88D4 6A64 88D8 6A65 88D9 6A66 88DD 6A67 88F9 6A68 8902 6A69 88FC 6A6A 88F4 6A6B 88E8 6A6C 88F2 6A6D 8904 6A6E 890C 6A6F 890A 6A70 8913 6A71 8943 6A72 891E 6A73 8925 6A74 892A 6A75 892B 6A76 8941 6A77 8944 6A78 893B 6A79 8936 6A7A 8938 6A7B 894C 6A7C 891D 6A7D 8960 6A7E 895E 6B21 8966 6B22 8964 6B23 896D 6B24 896A 6B25 896F 6B26 8974 6B27 8977 6B28 897E 6B29 8983 6B2A 8988 6B2B 898A 6B2C 8993 6B2D 8998 6B2E 89A1 6B2F 89A9 6B30 89A6 6B31 89AC 6B32 89AF 6B33 89B2 6B34 89BA 6B35 89BD 6B36 89BF 6B37 89C0 6B38 89DA 6B39 89DC 6B3A 89DD 6B3B 89E7 6B3C 89F4 6B3D 89F8 6B3E 8A03 6B3F 8A16 6B40 8A10 6B41 8A0C 6B42 8A1B 6B43 8A1D 6B44 8A25 6B45 8A36 6B46 8A41 6B47 8A5B 6B48 8A52 6B49 8A46 6B4A 8A48 6B4B 8A7C 6B4C 8A6D 6B4D 8A6C 6B4E 8A62 6B4F 8A85 6B50 8A82 6B51 8A84 6B52 8AA8 6B53 8AA1 6B54 8A91 6B55 8AA5 6B56 8AA6 6B57 8A9A 6B58 8AA3 6B59 8AC4 6B5A 8ACD 6B5B 8AC2 6B5C 8ADA 6B5D 8AEB 6B5E 8AF3 6B5F 8AE7 6B60 8AE4 6B61 8AF1 6B62 8B14 6B63 8AE0 6B64 8AE2 6B65 8AF7 6B66 8ADE 6B67 8ADB 6B68 8B0C 6B69 8B07 6B6A 8B1A 6B6B 8AE1 6B6C 8B16 6B6D 8B10 6B6E 8B17 6B6F 8B20 6B70 8B33 6B71 97AB 6B72 8B26 6B73 8B2B 6B74 8B3E 6B75 8B28 6B76 8B41 6B77 8B4C 6B78 8B4F 6B79 8B4E 6B7A 8B49 6B7B 8B56 6B7C 8B5B 6B7D 8B5A 6B7E 8B6B 6C21 8B5F 6C22 8B6C 6C23 8B6F 6C24 8B74 6C25 8B7D 6C26 8B80 6C27 8B8C 6C28 8B8E 6C29 8B92 6C2A 8B93 6C2B 8B96 6C2C 8B99 6C2D 8B9A 6C2E 8C3A 6C2F 8C41 6C30 8C3F 6C31 8C48 6C32 8C4C 6C33 8C4E 6C34 8C50 6C35 8C55 6C36 8C62 6C37 8C6C 6C38 8C78 6C39 8C7A 6C3A 8C82 6C3B 8C89 6C3C 8C85 6C3D 8C8A 6C3E 8C8D 6C3F 8C8E 6C40 8C94 6C41 8C7C 6C42 8C98 6C43 621D 6C44 8CAD 6C45 8CAA 6C46 8CBD 6C47 8CB2 6C48 8CB3 6C49 8CAE 6C4A 8CB6 6C4B 8CC8 6C4C 8CC1 6C4D 8CE4 6C4E 8CE3 6C4F 8CDA 6C50 8CFD 6C51 8CFA 6C52 8CFB 6C53 8D04 6C54 8D05 6C55 8D0A 6C56 8D07 6C57 8D0F 6C58 8D0D 6C59 8D10 6C5A 9F4E 6C5B 8D13 6C5C 8CCD 6C5D 8D14 6C5E 8D16 6C5F 8D67 6C60 8D6D 6C61 8D71 6C62 8D73 6C63 8D81 6C64 8D99 6C65 8DC2 6C66 8DBE 6C67 8DBA 6C68 8DCF 6C69 8DDA 6C6A 8DD6 6C6B 8DCC 6C6C 8DDB 6C6D 8DCB 6C6E 8DEA 6C6F 8DEB 6C70 8DDF 6C71 8DE3 6C72 8DFC 6C73 8E08 6C74 8E09 6C75 8DFF 6C76 8E1D 6C77 8E1E 6C78 8E10 6C79 8E1F 6C7A 8E42 6C7B 8E35 6C7C 8E30 6C7D 8E34 6C7E 8E4A 6D21 8E47 6D22 8E49 6D23 8E4C 6D24 8E50 6D25 8E48 6D26 8E59 6D27 8E64 6D28 8E60 6D29 8E2A 6D2A 8E63 6D2B 8E55 6D2C 8E76 6D2D 8E72 6D2E 8E7C 6D2F 8E81 6D30 8E87 6D31 8E85 6D32 8E84 6D33 8E8B 6D34 8E8A 6D35 8E93 6D36 8E91 6D37 8E94 6D38 8E99 6D39 8EAA 6D3A 8EA1 6D3B 8EAC 6D3C 8EB0 6D3D 8EC6 6D3E 8EB1 6D3F 8EBE 6D40 8EC5 6D41 8EC8 6D42 8ECB 6D43 8EDB 6D44 8EE3 6D45 8EFC 6D46 8EFB 6D47 8EEB 6D48 8EFE 6D49 8F0A 6D4A 8F05 6D4B 8F15 6D4C 8F12 6D4D 8F19 6D4E 8F13 6D4F 8F1C 6D50 8F1F 6D51 8F1B 6D52 8F0C 6D53 8F26 6D54 8F33 6D55 8F3B 6D56 8F39 6D57 8F45 6D58 8F42 6D59 8F3E 6D5A 8F4C 6D5B 8F49 6D5C 8F46 6D5D 8F4E 6D5E 8F57 6D5F 8F5C 6D60 8F62 6D61 8F63 6D62 8F64 6D63 8F9C 6D64 8F9F 6D65 8FA3 6D66 8FAD 6D67 8FAF 6D68 8FB7 6D69 8FDA 6D6A 8FE5 6D6B 8FE2 6D6C 8FEA 6D6D 8FEF 6D6E 9087 6D6F 8FF4 6D70 9005 6D71 8FF9 6D72 8FFA 6D73 9011 6D74 9015 6D75 9021 6D76 900D 6D77 901E 6D78 9016 6D79 900B 6D7A 9027 6D7B 9036 6D7C 9035 6D7D 9039 6D7E 8FF8 6E21 904F 6E22 9050 6E23 9051 6E24 9052 6E25 900E 6E26 9049 6E27 903E 6E28 9056 6E29 9058 6E2A 905E 6E2B 9068 6E2C 906F 6E2D 9076 6E2E 96A8 6E2F 9072 6E30 9082 6E31 907D 6E32 9081 6E33 9080 6E34 908A 6E35 9089 6E36 908F 6E37 90A8 6E38 90AF 6E39 90B1 6E3A 90B5 6E3B 90E2 6E3C 90E4 6E3D 6248 6E3E 90DB 6E3F 9102 6E40 9112 6E41 9119 6E42 9132 6E43 9130 6E44 914A 6E45 9156 6E46 9158 6E47 9163 6E48 9165 6E49 9169 6E4A 9173 6E4B 9172 6E4C 918B 6E4D 9189 6E4E 9182 6E4F 91A2 6E50 91AB 6E51 91AF 6E52 91AA 6E53 91B5 6E54 91B4 6E55 91BA 6E56 91C0 6E57 91C1 6E58 91C9 6E59 91CB 6E5A 91D0 6E5B 91D6 6E5C 91DF 6E5D 91E1 6E5E 91DB 6E5F 91FC 6E60 91F5 6E61 91F6 6E62 921E 6E63 91FF 6E64 9214 6E65 922C 6E66 9215 6E67 9211 6E68 925E 6E69 9257 6E6A 9245 6E6B 9249 6E6C 9264 6E6D 9248 6E6E 9295 6E6F 923F 6E70 924B 6E71 9250 6E72 929C 6E73 9296 6E74 9293 6E75 929B 6E76 925A 6E77 92CF 6E78 92B9 6E79 92B7 6E7A 92E9 6E7B 930F 6E7C 92FA 6E7D 9344 6E7E 932E 6F21 9319 6F22 9322 6F23 931A 6F24 9323 6F25 933A 6F26 9335 6F27 933B 6F28 935C 6F29 9360 6F2A 937C 6F2B 936E 6F2C 9356 6F2D 93B0 6F2E 93AC 6F2F 93AD 6F30 9394 6F31 93B9 6F32 93D6 6F33 93D7 6F34 93E8 6F35 93E5 6F36 93D8 6F37 93C3 6F38 93DD 6F39 93D0 6F3A 93C8 6F3B 93E4 6F3C 941A 6F3D 9414 6F3E 9413 6F3F 9403 6F40 9407 6F41 9410 6F42 9436 6F43 942B 6F44 9435 6F45 9421 6F46 943A 6F47 9441 6F48 9452 6F49 9444 6F4A 945B 6F4B 9460 6F4C 9462 6F4D 945E 6F4E 946A 6F4F 9229 6F50 9470 6F51 9475 6F52 9477 6F53 947D 6F54 945A 6F55 947C 6F56 947E 6F57 9481 6F58 947F 6F59 9582 6F5A 9587 6F5B 958A 6F5C 9594 6F5D 9596 6F5E 9598 6F5F 9599 6F60 95A0 6F61 95A8 6F62 95A7 6F63 95AD 6F64 95BC 6F65 95BB 6F66 95B9 6F67 95BE 6F68 95CA 6F69 6FF6 6F6A 95C3 6F6B 95CD 6F6C 95CC 6F6D 95D5 6F6E 95D4 6F6F 95D6 6F70 95DC 6F71 95E1 6F72 95E5 6F73 95E2 6F74 9621 6F75 9628 6F76 962E 6F77 962F 6F78 9642 6F79 964C 6F7A 964F 6F7B 964B 6F7C 9677 6F7D 965C 6F7E 965E 7021 965D 7022 965F 7023 9666 7024 9672 7025 966C 7026 968D 7027 9698 7028 9695 7029 9697 702A 96AA 702B 96A7 702C 96B1 702D 96B2 702E 96B0 702F 96B4 7030 96B6 7031 96B8 7032 96B9 7033 96CE 7034 96CB 7035 96C9 7036 96CD 7037 894D 7038 96DC 7039 970D 703A 96D5 703B 96F9 703C 9704 703D 9706 703E 9708 703F 9713 7040 970E 7041 9711 7042 970F 7043 9716 7044 9719 7045 9724 7046 972A 7047 9730 7048 9739 7049 973D 704A 973E 704B 9744 704C 9746 704D 9748 704E 9742 704F 9749 7050 975C 7051 9760 7052 9764 7053 9766 7054 9768 7055 52D2 7056 976B 7057 9771 7058 9779 7059 9785 705A 977C 705B 9781 705C 977A 705D 9786 705E 978B 705F 978F 7060 9790 7061 979C 7062 97A8 7063 97A6 7064 97A3 7065 97B3 7066 97B4 7067 97C3 7068 97C6 7069 97C8 706A 97CB 706B 97DC 706C 97ED 706D 9F4F 706E 97F2 706F 7ADF 7070 97F6 7071 97F5 7072 980F 7073 980C 7074 9838 7075 9824 7076 9821 7077 9837 7078 983D 7079 9846 707A 984F 707B 984B 707C 986B 707D 986F 707E 9870 7121 9871 7122 9874 7123 9873 7124 98AA 7125 98AF 7126 98B1 7127 98B6 7128 98C4 7129 98C3 712A 98C6 712B 98E9 712C 98EB 712D 9903 712E 9909 712F 9912 7130 9914 7131 9918 7132 9921 7133 991D 7134 991E 7135 9924 7136 9920 7137 992C 7138 992E 7139 993D 713A 993E 713B 9942 713C 9949 713D 9945 713E 9950 713F 994B 7140 9951 7141 9952 7142 994C 7143 9955 7144 9997 7145 9998 7146 99A5 7147 99AD 7148 99AE 7149 99BC 714A 99DF 714B 99DB 714C 99DD 714D 99D8 714E 99D1 714F 99ED 7150 99EE 7151 99F1 7152 99F2 7153 99FB 7154 99F8 7155 9A01 7156 9A0F 7157 9A05 7158 99E2 7159 9A19 715A 9A2B 715B 9A37 715C 9A45 715D 9A42 715E 9A40 715F 9A43 7160 9A3E 7161 9A55 7162 9A4D 7163 9A5B 7164 9A57 7165 9A5F 7166 9A62 7167 9A65 7168 9A64 7169 9A69 716A 9A6B 716B 9A6A 716C 9AAD 716D 9AB0 716E 9ABC 716F 9AC0 7170 9ACF 7171 9AD1 7172 9AD3 7173 9AD4 7174 9ADE 7175 9ADF 7176 9AE2 7177 9AE3 7178 9AE6 7179 9AEF 717A 9AEB 717B 9AEE 717C 9AF4 717D 9AF1 717E 9AF7 7221 9AFB 7222 9B06 7223 9B18 7224 9B1A 7225 9B1F 7226 9B22 7227 9B23 7228 9B25 7229 9B27 722A 9B28 722B 9B29 722C 9B2A 722D 9B2E 722E 9B2F 722F 9B32 7230 9B44 7231 9B43 7232 9B4F 7233 9B4D 7234 9B4E 7235 9B51 7236 9B58 7237 9B74 7238 9B93 7239 9B83 723A 9B91 723B 9B96 723C 9B97 723D 9B9F 723E 9BA0 723F 9BA8 7240 9BB4 7241 9BC0 7242 9BCA 7243 9BB9 7244 9BC6 7245 9BCF 7246 9BD1 7247 9BD2 7248 9BE3 7249 9BE2 724A 9BE4 724B 9BD4 724C 9BE1 724D 9C3A 724E 9BF2 724F 9BF1 7250 9BF0 7251 9C15 7252 9C14 7253 9C09 7254 9C13 7255 9C0C 7256 9C06 7257 9C08 7258 9C12 7259 9C0A 725A 9C04 725B 9C2E 725C 9C1B 725D 9C25 725E 9C24 725F 9C21 7260 9C30 7261 9C47 7262 9C32 7263 9C46 7264 9C3E 7265 9C5A 7266 9C60 7267 9C67 7268 9C76 7269 9C78 726A 9CE7 726B 9CEC 726C 9CF0 726D 9D09 726E 9D08 726F 9CEB 7270 9D03 7271 9D06 7272 9D2A 7273 9D26 7274 9DAF 7275 9D23 7276 9D1F 7277 9D44 7278 9D15 7279 9D12 727A 9D41 727B 9D3F 727C 9D3E 727D 9D46 727E 9D48 7321 9D5D 7322 9D5E 7323 9D64 7324 9D51 7325 9D50 7326 9D59 7327 9D72 7328 9D89 7329 9D87 732A 9DAB 732B 9D6F 732C 9D7A 732D 9D9A 732E 9DA4 732F 9DA9 7330 9DB2 7331 9DC4 7332 9DC1 7333 9DBB 7334 9DB8 7335 9DBA 7336 9DC6 7337 9DCF 7338 9DC2 7339 9DD9 733A 9DD3 733B 9DF8 733C 9DE6 733D 9DED 733E 9DEF 733F 9DFD 7340 9E1A 7341 9E1B 7342 9E1E 7343 9E75 7344 9E79 7345 9E7D 7346 9E81 7347 9E88 7348 9E8B 7349 9E8C 734A 9E92 734B 9E95 734C 9E91 734D 9E9D 734E 9EA5 734F 9EA9 7350 9EB8 7351 9EAA 7352 9EAD 7353 9761 7354 9ECC 7355 9ECE 7356 9ECF 7357 9ED0 7358 9ED4 7359 9EDC 735A 9EDE 735B 9EDD 735C 9EE0 735D 9EE5 735E 9EE8 735F 9EEF 7360 9EF4 7361 9EF6 7362 9EF7 7363 9EF9 7364 9EFB 7365 9EFC 7366 9EFD 7367 9F07 7368 9F08 7369 76B7 736A 9F15 736B 9F21 736C 9F2C 736D 9F3E 736E 9F4A 736F 9F52 7370 9F54 7371 9F63 7372 9F5F 7373 9F60 7374 9F61 7375 9F66 7376 9F67 7377 9F6C 7378 9F6A 7379 9F77 737A 9F72 737B 9F76 737C 9F95 737D 9F9C 737E 9FA0 7421 582F 7422 69C7 7423 9059 7424 7464 7425 51DC 7426 7199 # ESCAPE CODES 1B2440 :JIS-0208 ESC-$-@ 1B2442 :JIS-0208 ESC-$-B 1B2842 :US-ASCII ESC-(-B 1B284A :JIS-0201 ESC-(-J cyrus-imapd-2.5.10/lib/charset/iso-8859-3.t0000644000175000017500000002312113001236020014670 00000000000000# # Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. # # Redistribution and use in source and binary forms, with or without # modification, are permitted provided that the following conditions # are met: # # 1. Redistributions of source code must retain the above copyright # notice, this list of conditions and the following disclaimer. # # 2. Redistributions in binary form must reproduce the above copyright # notice, this list of conditions and the following disclaimer in # the documentation and/or other materials provided with the # distribution. # # 3. The name "Carnegie Mellon University" must not be used to # endorse or promote products derived from this software without # prior written permission. For permission or any legal # details, please contact # Carnegie Mellon University # Center for Technology Transfer and Enterprise Creation # 4615 Forbes Avenue # Suite 302 # Pittsburgh, PA 15213 # (412) 268-7393, fax: (412) 268-7395 # innovation@andrew.cmu.edu # # 4. Redistributions of any form whatsoever must retain the following # acknowledgment: # "This product includes software developed by Computing Services # at Carnegie Mellon University (http://www.cmu.edu/computing/)." # # CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO # THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY # AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE # FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES # WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN # AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING # OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. 0 0000 NULL (NUL) 1 0001 START OF HEADING (SOH) 2 0002 START OF TEXT (STX) 3 0003 END OF TEXT (ETX) 4 0004 END OF TRANSMISSION (EOT) 5 0005 ENQUIRY (ENQ) 6 0006 ACKNOWLEDGE (ACK) 7 0007 BELL (BEL) 8 0008 BACKSPACE (BS) 9 0009 CHARACTER TABULATION (HT) A 000a LINE FEED (LF) B 000b LINE TABULATION (VT) C 000c FORM FEED (FF) D 000d CARRIAGE RETURN (CR) E 000e SHIFT OUT (SO) F 000f SHIFT IN (SI) 10 0010 DATALINK ESCAPE (DLE) 11 0011 DEVICE CONTROL ONE (DC1) 12 0012 DEVICE CONTROL TWO (DC2) 13 0013 DEVICE CONTROL THREE (DC3) 14 0014 DEVICE CONTROL FOUR (DC4) 15 0015 NEGATIVE ACKNOWLEDGE (NAK) 16 0016 SYNCRONOUS IDLE (SYN) 17 0017 END OF TRANSMISSION BLOCK (ETB) 18 0018 CANCEL (CAN) 19 0019 END OF MEDIUM (EM) 1A 001a SUBSTITUTE (SUB) 1B 001b ESCAPE (ESC) 1C 001c FILE SEPARATOR (IS4) 1D 001d GROUP SEPARATOR (IS3) 1E 001e RECORD SEPARATOR (IS2) 1F 001f UNIT SEPARATOR (IS1) 20 0020 SPACE 21 0021 EXCLAMATION MARK 22 0022 QUOTATION MARK 23 0023 NUMBER SIGN 24 0024 DOLLAR SIGN 25 0025 PERCENT SIGN 26 0026 AMPERSAND 27 0027 APOSTROPHE 28 0028 LEFT PARENTHESIS 29 0029 RIGHT PARENTHESIS 2A 002a ASTERISK 2B 002b PLUS SIGN 2C 002c COMMA 2D 002d HYPHEN-MINUS 2E 002e FULL STOP 2F 002f SOLIDUS 30 0030 DIGIT ZERO 31 0031 DIGIT ONE 32 0032 DIGIT TWO 33 0033 DIGIT THREE 34 0034 DIGIT FOUR 35 0035 DIGIT FIVE 36 0036 DIGIT SIX 37 0037 DIGIT SEVEN 38 0038 DIGIT EIGHT 39 0039 DIGIT NINE 3A 003a COLON 3B 003b SEMICOLON 3C 003c LESS-THAN SIGN 3D 003d EQUALS SIGN 3E 003e GREATER-THAN SIGN 3F 003f QUESTION MARK 40 0040 COMMERCIAL AT 41 0041 LATIN CAPITAL LETTER A 42 0042 LATIN CAPITAL LETTER B 43 0043 LATIN CAPITAL LETTER C 44 0044 LATIN CAPITAL LETTER D 45 0045 LATIN CAPITAL LETTER E 46 0046 LATIN CAPITAL LETTER F 47 0047 LATIN CAPITAL LETTER G 48 0048 LATIN CAPITAL LETTER H 49 0049 LATIN CAPITAL LETTER I 4A 004a LATIN CAPITAL LETTER J 4B 004b LATIN CAPITAL LETTER K 4C 004c LATIN CAPITAL LETTER L 4D 004d LATIN CAPITAL LETTER M 4E 004e LATIN CAPITAL LETTER N 4F 004f LATIN CAPITAL LETTER O 50 0050 LATIN CAPITAL LETTER P 51 0051 LATIN CAPITAL LETTER Q 52 0052 LATIN CAPITAL LETTER R 53 0053 LATIN CAPITAL LETTER S 54 0054 LATIN CAPITAL LETTER T 55 0055 LATIN CAPITAL LETTER U 56 0056 LATIN CAPITAL LETTER V 57 0057 LATIN CAPITAL LETTER W 58 0058 LATIN CAPITAL LETTER X 59 0059 LATIN CAPITAL LETTER Y 5A 005a LATIN CAPITAL LETTER Z 5B 005b LEFT SQUARE BRACKET 5C 005c REVERSE SOLIDUS 5D 005d RIGHT SQUARE BRACKET 5E 005e CIRCUMFLEX ACCENT 5F 005f LOW LINE 60 0060 GRAVE ACCENT 61 0061 LATIN SMALL LETTER A 62 0062 LATIN SMALL LETTER B 63 0063 LATIN SMALL LETTER C 64 0064 LATIN SMALL LETTER D 65 0065 LATIN SMALL LETTER E 66 0066 LATIN SMALL LETTER F 67 0067 LATIN SMALL LETTER G 68 0068 LATIN SMALL LETTER H 69 0069 LATIN SMALL LETTER I 6A 006a LATIN SMALL LETTER J 6B 006b LATIN SMALL LETTER K 6C 006c LATIN SMALL LETTER L 6D 006d LATIN SMALL LETTER M 6E 006e LATIN SMALL LETTER N 6F 006f LATIN SMALL LETTER O 70 0070 LATIN SMALL LETTER P 71 0071 LATIN SMALL LETTER Q 72 0072 LATIN SMALL LETTER R 73 0073 LATIN SMALL LETTER S 74 0074 LATIN SMALL LETTER T 75 0075 LATIN SMALL LETTER U 76 0076 LATIN SMALL LETTER V 77 0077 LATIN SMALL LETTER W 78 0078 LATIN SMALL LETTER X 79 0079 LATIN SMALL LETTER Y 7A 007a LATIN SMALL LETTER Z 7B 007b LEFT CURLY BRACKET 7C 007c VERTICAL LINE 7D 007d RIGHT CURLY BRACKET 7E 007e TILDE 7F 007f DELETE (DEL) 80 0080 PADDING CHARACTER (PAD) 81 0081 HIGH OCTET PRESET (HOP) 82 0082 BREAK PERMITTED HERE (BPH) 83 0083 NO BREAK HERE (NBH) 84 0084 INDEX (IND) 85 0085 NEXT LINE (NEL) 86 0086 START OF SELECTED AREA (SSA) 87 0087 END OF SELECTED AREA (ESA) 88 0088 CHARACTER TABULATION SET (HTS) 89 0089 CHARACTER TABULATION WITH JUSTIFICATION (HTJ) 8A 008a LINE TABULATION SET (VTS) 8B 008b PARTIAL LINE FORWARD (PLD) 8C 008c PARTIAL LINE BACKWARD (PLU) 8D 008d REVERSE LINE FEED (RI) 8E 008e SINGLE-SHIFT TWO (SS2) 8F 008f SINGLE-SHIFT THREE (SS3) 90 0090 DEVICE CONTROL STRING (DCS) 91 0091 PRIVATE USE ONE (PU1) 92 0092 PRIVATE USE TWO (PU2) 93 0093 SET TRANSMIT STATE (STS) 94 0094 CANCEL CHARACTER (CCH) 95 0095 MESSAGE WAITING (MW) 96 0096 START OF GUARDED AREA (SPA) 97 0097 END OF GUARDED AREA (EPA) 98 0098 START OF STRING (SOS) 99 0099 SINGLE GRAPHIC CHARACTER INTRODUCER (SGCI) 9A 009a SINGLE CHARACTER INTRODUCER (SCI) 9B 009b CONTROL SEQUENCE INTRODUCER (CSI) 9C 009c STRING TERMINATOR (ST) 9D 009d OPERATING SYSTEM COMMAND (OSC) 9E 009e PRIVACY MESSAGE (PM) 9F 009f APPLICATION PROGRAM COMMAND (APC) A0 00a0 NO-BREAK SPACE A1 0126 LATIN CAPITAL LETTER H WITH STROKE A2 02d8 BREVE A3 00a3 POUND SIGN A4 00a4 CURRENCY SIGN A5 ???? EMPTY A6 0124 LATIN CAPITAL LETTER H WITH CIRCUMFLEX A7 00a7 SECTION SIGN A8 00a8 DIAERESIS A9 0130 LATIN CAPITAL LETTER I WITH DOT ABOVE AA 015e LATIN CAPITAL LETTER S WITH CEDILLA AB 011e LATIN CAPITAL LETTER G WITH BREVE AC 0134 LATIN CAPITAL LETTER J WITH CIRCUMFLEX AD 00ad SOFT HYPHEN AE ???? EMPTY AF 017b LATIN CAPITAL LETTER Z WITH DOT ABOVE B0 00b0 DEGREE SIGN B1 0127 LATIN SMALL LETTER H WITH STROKE B2 00b2 SUPERSCRIPT TWO B3 00b3 SUPERSCRIPT THREE B4 00b4 ACUTE ACCENT B5 00b5 MICRO SIGN B6 0125 LATIN SMALL LETTER H WITH CIRCUMFLEX B7 00b7 MIDDLE DOT B8 00b8 CEDILLA B9 0131 LATIN SMALL LETTER I DOTLESS BA 015f LATIN SMALL LETTER S WITH CEDILLA BB 011f LATIN SMALL LETTER G WITH BREVE BC 0135 LATIN SMALL LETTER J WITH CIRCUMFLEX BD 00bd VULGAR FRACTION ONE HALF BE ???? EMPTY BF 017c LATIN SMALL LETTER Z WITH DOT ABOVE C0 00c0 LATIN CAPITAL LETTER A WITH GRAVE C1 00c1 LATIN CAPITAL LETTER A WITH ACUTE C2 00c2 LATIN CAPITAL LETTER A WITH CIRCUMFLEX C3 ???? EMPTY C4 00c4 LATIN CAPITAL LETTER A WITH DIAERESIS C5 010a LATIN CAPITAL LETTER C WITH DOT ABOVE C6 0108 LATIN CAPITAL LETTER C WITH CIRCUMFLEX C7 00c7 LATIN CAPITAL LETTER C WITH CEDILLA C8 00c8 LATIN CAPITAL LETTER E WITH GRAVE C9 00c9 LATIN CAPITAL LETTER E WITH ACUTE CA 00ca LATIN CAPITAL LETTER E WITH CIRCUMFLEX CB 00cb LATIN CAPITAL LETTER E WITH DIAERESIS CC 00cc LATIN CAPITAL LETTER I WITH GRAVE CD 00cd LATIN CAPITAL LETTER I WITH ACUTE CE 00ce LATIN CAPITAL LETTER I WITH CIRCUMFLEX CF 00cf LATIN CAPITAL LETTER I WITH DIAERESIS D0 ???? EMPTY D1 00d1 LATIN CAPITAL LETTER N WITH TILDE D2 00d2 LATIN CAPITAL LETTER O WITH GRAVE D3 00d3 LATIN CAPITAL LETTER O WITH ACUTE D4 00d4 LATIN CAPITAL LETTER O WITH CIRCUMFLEX D5 0120 LATIN CAPITAL LETTER G WITH DOT ABOVE D6 00d6 LATIN CAPITAL LETTER O WITH DIAERESIS D7 00d7 MULTIPLICATION SIGN D8 011c LATIN CAPITAL LETTER G WITH CIRCUMFLEX D9 00d9 LATIN CAPITAL LETTER U WITH GRAVE DA 00da LATIN CAPITAL LETTER U WITH ACUTE DB 00db LATIN CAPITAL LETTER U WITH CIRCUMFLEX DC 00dc LATIN CAPITAL LETTER U WITH DIAERESIS DD 016c LATIN CAPITAL LETTER U WITH BREVE DE 015c LATIN CAPITAL LETTER S WITH CIRCUMFLEX DF 00df LATIN SMALL LETTER SHARP S (German) E0 00e0 LATIN SMALL LETTER A WITH GRAVE E1 00e1 LATIN SMALL LETTER A WITH ACUTE E2 00e2 LATIN SMALL LETTER A WITH CIRCUMFLEX E3 ???? EMPTY E4 00e4 LATIN SMALL LETTER A WITH DIAERESIS E5 010b LATIN SMALL LETTER C WITH DOT ABOVE E6 0109 LATIN SMALL LETTER C WITH CIRCUMFLEX E7 00e7 LATIN SMALL LETTER C WITH CEDILLA E8 00e8 LATIN SMALL LETTER E WITH GRAVE E9 00e9 LATIN SMALL LETTER E WITH ACUTE EA 00ea LATIN SMALL LETTER E WITH CIRCUMFLEX EB 00eb LATIN SMALL LETTER E WITH DIAERESIS EC 00ec LATIN SMALL LETTER I WITH GRAVE ED 00ed LATIN SMALL LETTER I WITH ACUTE EE 00ee LATIN SMALL LETTER I WITH CIRCUMFLEX EF 00ef LATIN SMALL LETTER I WITH DIAERESIS F0 ???? EMPTY F1 00f1 LATIN SMALL LETTER N WITH TILDE F2 00f2 LATIN SMALL LETTER O WITH GRAVE F3 00f3 LATIN SMALL LETTER O WITH ACUTE F4 00f4 LATIN SMALL LETTER O WITH CIRCUMFLEX F5 0121 LATIN SMALL LETTER G WITH DOT ABOVE F6 00f6 LATIN SMALL LETTER O WITH DIAERESIS F7 00f7 DIVISION SIGN F8 011d LATIN SMALL LETTER G WITH CIRCUMFLEX F9 00f9 LATIN SMALL LETTER U WITH GRAVE FA 00fa LATIN SMALL LETTER U WITH ACUTE FB 00fb LATIN SMALL LETTER U WITH CIRCUMFLEX FC 00fc LATIN SMALL LETTER U WITH DIAERESIS FD 016d LATIN SMALL LETTER U WITH BREVE FE 015d LATIN SMALL LETTER S WITH CIRCUMFLEX FF 02d9 DOT ABOVE cyrus-imapd-2.5.10/lib/charset/iso-2022-kr.t0000644000175000017500000240343113001236020015122 00000000000000# # Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. # # Redistribution and use in source and binary forms, with or without # modification, are permitted provided that the following conditions # are met: # # 1. Redistributions of source code must retain the above copyright # notice, this list of conditions and the following disclaimer. # # 2. Redistributions in binary form must reproduce the above copyright # notice, this list of conditions and the following disclaimer in # the documentation and/or other materials provided with the # distribution. # # 3. The name "Carnegie Mellon University" must not be used to # endorse or promote products derived from this software without # prior written permission. For permission or any legal # details, please contact # Carnegie Mellon University # Center for Technology Transfer and Enterprise Creation # 4615 Forbes Avenue # Suite 302 # Pittsburgh, PA 15213 # (412) 268-7393, fax: (412) 268-7395 # innovation@andrew.cmu.edu # # 4. Redistributions of any form whatsoever must retain the following # acknowledgment: # "This product includes software developed by Computing Services # at Carnegie Mellon University (http://www.cmu.edu/computing/)." # # CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO # THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY # AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE # FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES # WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN # AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING # OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. :US-ASCII 0 0000 NULL (NUL) 1 0001 START OF HEADING (SOH) 2 0002 START OF TEXT (STX) 3 0003 END OF TEXT (ETX) 4 0004 END OF TRANSMISSION (EOT) 5 0005 ENQUIRY (ENQ) 6 0006 ACKNOWLEDGE (ACK) 7 0007 BELL (BEL) 8 0008 BACKSPACE (BS) 9 0009 CHARACTER TABULATION (HT) A 000a LINE FEED (LF) B 000b LINE TABULATION (VT) C 000c FORM FEED (FF) D 000d CARRIAGE RETURN (CR) E :KSC-5601 F 000f SHIFT IN (SI) 10 0010 DATALINK ESCAPE (DLE) 11 0011 DEVICE CONTROL ONE (DC1) 12 0012 DEVICE CONTROL TWO (DC2) 13 0013 DEVICE CONTROL THREE (DC3) 14 0014 DEVICE CONTROL FOUR (DC4) 15 0015 NEGATIVE ACKNOWLEDGE (NAK) 16 0016 SYNCRONOUS IDLE (SYN) 17 0017 END OF TRANSMISSION BLOCK (ETB) 18 0018 CANCEL (CAN) 19 0019 END OF MEDIUM (EM) 1A 001a SUBSTITUTE (SUB) # 1B >ESC 1C 001c FILE SEPARATOR (IS4) 1D 001d GROUP SEPARATOR (IS3) 1E 001e RECORD SEPARATOR (IS2) 1F 001f UNIT SEPARATOR (IS1) 20 0020 SPACE 21 0021 EXCLAMATION MARK 22 0022 QUOTATION MARK 23 0023 NUMBER SIGN 24 0024 DOLLAR SIGN 25 0025 PERCENT SIGN 26 0026 AMPERSAND 27 0027 APOSTROPHE 28 0028 LEFT PARENTHESIS 29 0029 RIGHT PARENTHESIS 2A 002a ASTERISK 2B 002b PLUS SIGN 2C 002c COMMA 2D 002d HYPHEN-MINUS 2E 002e FULL STOP 2F 002f SOLIDUS 30 0030 DIGIT ZERO 31 0031 DIGIT ONE 32 0032 DIGIT TWO 33 0033 DIGIT THREE 34 0034 DIGIT FOUR 35 0035 DIGIT FIVE 36 0036 DIGIT SIX 37 0037 DIGIT SEVEN 38 0038 DIGIT EIGHT 39 0039 DIGIT NINE 3A 003a COLON 3B 003b SEMICOLON 3C 003c LESS-THAN SIGN 3D 003d EQUALS SIGN 3E 003e GREATER-THAN SIGN 3F 003f QUESTION MARK 40 0040 COMMERCIAL AT 41 0041 LATIN CAPITAL LETTER A 42 0042 LATIN CAPITAL LETTER B 43 0043 LATIN CAPITAL LETTER C 44 0044 LATIN CAPITAL LETTER D 45 0045 LATIN CAPITAL LETTER E 46 0046 LATIN CAPITAL LETTER F 47 0047 LATIN CAPITAL LETTER G 48 0048 LATIN CAPITAL LETTER H 49 0049 LATIN CAPITAL LETTER I 4A 004a LATIN CAPITAL LETTER J 4B 004b LATIN CAPITAL LETTER K 4C 004c LATIN CAPITAL LETTER L 4D 004d LATIN CAPITAL LETTER M 4E 004e LATIN CAPITAL LETTER N 4F 004f LATIN CAPITAL LETTER O 50 0050 LATIN CAPITAL LETTER P 51 0051 LATIN CAPITAL LETTER Q 52 0052 LATIN CAPITAL LETTER R 53 0053 LATIN CAPITAL LETTER S 54 0054 LATIN CAPITAL LETTER T 55 0055 LATIN CAPITAL LETTER U 56 0056 LATIN CAPITAL LETTER V 57 0057 LATIN CAPITAL LETTER W 58 0058 LATIN CAPITAL LETTER X 59 0059 LATIN CAPITAL LETTER Y 5A 005a LATIN CAPITAL LETTER Z 5B 005b LEFT SQUARE BRACKET 5C 005c REVERSE SOLIDUS 5D 005d RIGHT SQUARE BRACKET 5E 005e CIRCUMFLEX ACCENT 5F 005f LOW LINE 60 0060 GRAVE ACCENT 61 0061 LATIN SMALL LETTER A 62 0062 LATIN SMALL LETTER B 63 0063 LATIN SMALL LETTER C 64 0064 LATIN SMALL LETTER D 65 0065 LATIN SMALL LETTER E 66 0066 LATIN SMALL LETTER F 67 0067 LATIN SMALL LETTER G 68 0068 LATIN SMALL LETTER H 69 0069 LATIN SMALL LETTER I 6A 006a LATIN SMALL LETTER J 6B 006b LATIN SMALL LETTER K 6C 006c LATIN SMALL LETTER L 6D 006d LATIN SMALL LETTER M 6E 006e LATIN SMALL LETTER N 6F 006f LATIN SMALL LETTER O 70 0070 LATIN SMALL LETTER P 71 0071 LATIN SMALL LETTER Q 72 0072 LATIN SMALL LETTER R 73 0073 LATIN SMALL LETTER S 74 0074 LATIN SMALL LETTER T 75 0075 LATIN SMALL LETTER U 76 0076 LATIN SMALL LETTER V 77 0077 LATIN SMALL LETTER W 78 0078 LATIN SMALL LETTER X 79 0079 LATIN SMALL LETTER Y 7A 007a LATIN SMALL LETTER Z 7B 007b LEFT CURLY BRACKET 7C 007c VERTICAL LINE 7D 007d RIGHT CURLY BRACKET 7E 007e TILDE 7F 007f DELETE (DEL) # ESCAPE CODE (pretty pointless, but need to return nothing if we follow this path) 1B242943 :US-ASCII ESC-$-)-C :KSC-5601 0f :US-ASCII 8141 AC02 # HANGUL SYLLABLE KIYEOK-A-SSANGKIYEOK 8142 AC03 # HANGUL SYLLABLE KIYEOK-A-KIYEOKSIOS 8143 AC05 # HANGUL SYLLABLE KIYEOK-A-NIEUNCIEUC 8144 AC06 # HANGUL SYLLABLE KIYEOK-A-NIEUNHIEUH 8145 AC0B # HANGUL SYLLABLE KIYEOK-A-RIEULPIEUP 8146 AC0C # HANGUL SYLLABLE KIYEOK-A-RIEULSIOS 8147 AC0D # HANGUL SYLLABLE KIYEOK-A-RIEULTHIEUTH 8148 AC0E # HANGUL SYLLABLE KIYEOK-A-RIEULPHIEUPH 8149 AC0F # HANGUL SYLLABLE KIYEOK-A-RIEULHIEUH 814A AC18 # HANGUL SYLLABLE KIYEOK-A-KHIEUKH 814B AC1E # HANGUL SYLLABLE KIYEOK-AE-SSANGKIYEOK 814C AC1F # HANGUL SYLLABLE KIYEOK-AE-KIYEOKSIOS 814D AC21 # HANGUL SYLLABLE KIYEOK-AE-NIEUNCIEUC 814E AC22 # HANGUL SYLLABLE KIYEOK-AE-NIEUNHIEUH 814F AC23 # HANGUL SYLLABLE KIYEOK-AE-TIKEUT 8150 AC25 # HANGUL SYLLABLE KIYEOK-AE-RIEULKIYEOK 8151 AC26 # HANGUL SYLLABLE KIYEOK-AE-RIEULMIEUM 8152 AC27 # HANGUL SYLLABLE KIYEOK-AE-RIEULPIEUP 8153 AC28 # HANGUL SYLLABLE KIYEOK-AE-RIEULSIOS 8154 AC29 # HANGUL SYLLABLE KIYEOK-AE-RIEULTHIEUTH 8155 AC2A # HANGUL SYLLABLE KIYEOK-AE-RIEULPHIEUPH 8156 AC2B # HANGUL SYLLABLE KIYEOK-AE-RIEULHIEUH 8157 AC2E # HANGUL SYLLABLE KIYEOK-AE-PIEUPSIOS 8158 AC32 # HANGUL SYLLABLE KIYEOK-AE-CIEUC 8159 AC33 # HANGUL SYLLABLE KIYEOK-AE-CHIEUCH 815A AC34 # HANGUL SYLLABLE KIYEOK-AE-KHIEUKH 8161 AC35 # HANGUL SYLLABLE KIYEOK-AE-THIEUTH 8162 AC36 # HANGUL SYLLABLE KIYEOK-AE-PHIEUPH 8163 AC37 # HANGUL SYLLABLE KIYEOK-AE-HIEUH 8164 AC3A # HANGUL SYLLABLE KIYEOK-YA-SSANGKIYEOK 8165 AC3B # HANGUL SYLLABLE KIYEOK-YA-KIYEOKSIOS 8166 AC3D # HANGUL SYLLABLE KIYEOK-YA-NIEUNCIEUC 8167 AC3E # HANGUL SYLLABLE KIYEOK-YA-NIEUNHIEUH 8168 AC3F # HANGUL SYLLABLE KIYEOK-YA-TIKEUT 8169 AC41 # HANGUL SYLLABLE KIYEOK-YA-RIEULKIYEOK 816A AC42 # HANGUL SYLLABLE KIYEOK-YA-RIEULMIEUM 816B AC43 # HANGUL SYLLABLE KIYEOK-YA-RIEULPIEUP 816C AC44 # HANGUL SYLLABLE KIYEOK-YA-RIEULSIOS 816D AC45 # HANGUL SYLLABLE KIYEOK-YA-RIEULTHIEUTH 816E AC46 # HANGUL SYLLABLE KIYEOK-YA-RIEULPHIEUPH 816F AC47 # HANGUL SYLLABLE KIYEOK-YA-RIEULHIEUH 8170 AC48 # HANGUL SYLLABLE KIYEOK-YA-MIEUM 8171 AC49 # HANGUL SYLLABLE KIYEOK-YA-PIEUP 8172 AC4A # HANGUL SYLLABLE KIYEOK-YA-PIEUPSIOS 8173 AC4C # HANGUL SYLLABLE KIYEOK-YA-SSANGSIOS 8174 AC4E # HANGUL SYLLABLE KIYEOK-YA-CIEUC 8175 AC4F # HANGUL SYLLABLE KIYEOK-YA-CHIEUCH 8176 AC50 # HANGUL SYLLABLE KIYEOK-YA-KHIEUKH 8177 AC51 # HANGUL SYLLABLE KIYEOK-YA-THIEUTH 8178 AC52 # HANGUL SYLLABLE KIYEOK-YA-PHIEUPH 8179 AC53 # HANGUL SYLLABLE KIYEOK-YA-HIEUH 817A AC55 # HANGUL SYLLABLE KIYEOK-YAE-KIYEOK 8181 AC56 # HANGUL SYLLABLE KIYEOK-YAE-SSANGKIYEOK 8182 AC57 # HANGUL SYLLABLE KIYEOK-YAE-KIYEOKSIOS 8183 AC59 # HANGUL SYLLABLE KIYEOK-YAE-NIEUNCIEUC 8184 AC5A # HANGUL SYLLABLE KIYEOK-YAE-NIEUNHIEUH 8185 AC5B # HANGUL SYLLABLE KIYEOK-YAE-TIKEUT 8186 AC5D # HANGUL SYLLABLE KIYEOK-YAE-RIEULKIYEOK 8187 AC5E # HANGUL SYLLABLE KIYEOK-YAE-RIEULMIEUM 8188 AC5F # HANGUL SYLLABLE KIYEOK-YAE-RIEULPIEUP 8189 AC60 # HANGUL SYLLABLE KIYEOK-YAE-RIEULSIOS 818A AC61 # HANGUL SYLLABLE KIYEOK-YAE-RIEULTHIEUTH 818B AC62 # HANGUL SYLLABLE KIYEOK-YAE-RIEULPHIEUPH 818C AC63 # HANGUL SYLLABLE KIYEOK-YAE-RIEULHIEUH 818D AC64 # HANGUL SYLLABLE KIYEOK-YAE-MIEUM 818E AC65 # HANGUL SYLLABLE KIYEOK-YAE-PIEUP 818F AC66 # HANGUL SYLLABLE KIYEOK-YAE-PIEUPSIOS 8190 AC67 # HANGUL SYLLABLE KIYEOK-YAE-SIOS 8191 AC68 # HANGUL SYLLABLE KIYEOK-YAE-SSANGSIOS 8192 AC69 # HANGUL SYLLABLE KIYEOK-YAE-IEUNG 8193 AC6A # HANGUL SYLLABLE KIYEOK-YAE-CIEUC 8194 AC6B # HANGUL SYLLABLE KIYEOK-YAE-CHIEUCH 8195 AC6C # HANGUL SYLLABLE KIYEOK-YAE-KHIEUKH 8196 AC6D # HANGUL SYLLABLE KIYEOK-YAE-THIEUTH 8197 AC6E # HANGUL SYLLABLE KIYEOK-YAE-PHIEUPH 8198 AC6F # HANGUL SYLLABLE KIYEOK-YAE-HIEUH 8199 AC72 # HANGUL SYLLABLE KIYEOK-EO-SSANGKIYEOK 819A AC73 # HANGUL SYLLABLE KIYEOK-EO-KIYEOKSIOS 819B AC75 # HANGUL SYLLABLE KIYEOK-EO-NIEUNCIEUC 819C AC76 # HANGUL SYLLABLE KIYEOK-EO-NIEUNHIEUH 819D AC79 # HANGUL SYLLABLE KIYEOK-EO-RIEULKIYEOK 819E AC7B # HANGUL SYLLABLE KIYEOK-EO-RIEULPIEUP 819F AC7C # HANGUL SYLLABLE KIYEOK-EO-RIEULSIOS 81A0 AC7D # HANGUL SYLLABLE KIYEOK-EO-RIEULTHIEUTH 81A1 AC7E # HANGUL SYLLABLE KIYEOK-EO-RIEULPHIEUPH 81A2 AC7F # HANGUL SYLLABLE KIYEOK-EO-RIEULHIEUH 81A3 AC82 # HANGUL SYLLABLE KIYEOK-EO-PIEUPSIOS 81A4 AC87 # HANGUL SYLLABLE KIYEOK-EO-CHIEUCH 81A5 AC88 # HANGUL SYLLABLE KIYEOK-EO-KHIEUKH 81A6 AC8D # HANGUL SYLLABLE KIYEOK-E-KIYEOK 81A7 AC8E # HANGUL SYLLABLE KIYEOK-E-SSANGKIYEOK 81A8 AC8F # HANGUL SYLLABLE KIYEOK-E-KIYEOKSIOS 81A9 AC91 # HANGUL SYLLABLE KIYEOK-E-NIEUNCIEUC 81AA AC92 # HANGUL SYLLABLE KIYEOK-E-NIEUNHIEUH 81AB AC93 # HANGUL SYLLABLE KIYEOK-E-TIKEUT 81AC AC95 # HANGUL SYLLABLE KIYEOK-E-RIEULKIYEOK 81AD AC96 # HANGUL SYLLABLE KIYEOK-E-RIEULMIEUM 81AE AC97 # HANGUL SYLLABLE KIYEOK-E-RIEULPIEUP 81AF AC98 # HANGUL SYLLABLE KIYEOK-E-RIEULSIOS 81B0 AC99 # HANGUL SYLLABLE KIYEOK-E-RIEULTHIEUTH 81B1 AC9A # HANGUL SYLLABLE KIYEOK-E-RIEULPHIEUPH 81B2 AC9B # HANGUL SYLLABLE KIYEOK-E-RIEULHIEUH 81B3 AC9E # HANGUL SYLLABLE KIYEOK-E-PIEUPSIOS 81B4 ACA2 # HANGUL SYLLABLE KIYEOK-E-CIEUC 81B5 ACA3 # HANGUL SYLLABLE KIYEOK-E-CHIEUCH 81B6 ACA4 # HANGUL SYLLABLE KIYEOK-E-KHIEUKH 81B7 ACA5 # HANGUL SYLLABLE KIYEOK-E-THIEUTH 81B8 ACA6 # HANGUL SYLLABLE KIYEOK-E-PHIEUPH 81B9 ACA7 # HANGUL SYLLABLE KIYEOK-E-HIEUH 81BA ACAB # HANGUL SYLLABLE KIYEOK-YEO-KIYEOKSIOS 81BB ACAD # HANGUL SYLLABLE KIYEOK-YEO-NIEUNCIEUC 81BC ACAE # HANGUL SYLLABLE KIYEOK-YEO-NIEUNHIEUH 81BD ACB1 # HANGUL SYLLABLE KIYEOK-YEO-RIEULKIYEOK 81BE ACB2 # HANGUL SYLLABLE KIYEOK-YEO-RIEULMIEUM 81BF ACB3 # HANGUL SYLLABLE KIYEOK-YEO-RIEULPIEUP 81C0 ACB4 # HANGUL SYLLABLE KIYEOK-YEO-RIEULSIOS 81C1 ACB5 # HANGUL SYLLABLE KIYEOK-YEO-RIEULTHIEUTH 81C2 ACB6 # HANGUL SYLLABLE KIYEOK-YEO-RIEULPHIEUPH 81C3 ACB7 # HANGUL SYLLABLE KIYEOK-YEO-RIEULHIEUH 81C4 ACBA # HANGUL SYLLABLE KIYEOK-YEO-PIEUPSIOS 81C5 ACBE # HANGUL SYLLABLE KIYEOK-YEO-CIEUC 81C6 ACBF # HANGUL SYLLABLE KIYEOK-YEO-CHIEUCH 81C7 ACC0 # HANGUL SYLLABLE KIYEOK-YEO-KHIEUKH 81C8 ACC2 # HANGUL SYLLABLE KIYEOK-YEO-PHIEUPH 81C9 ACC3 # HANGUL SYLLABLE KIYEOK-YEO-HIEUH 81CA ACC5 # HANGUL SYLLABLE KIYEOK-YE-KIYEOK 81CB ACC6 # HANGUL SYLLABLE KIYEOK-YE-SSANGKIYEOK 81CC ACC7 # HANGUL SYLLABLE KIYEOK-YE-KIYEOKSIOS 81CD ACC9 # HANGUL SYLLABLE KIYEOK-YE-NIEUNCIEUC 81CE ACCA # HANGUL SYLLABLE KIYEOK-YE-NIEUNHIEUH 81CF ACCB # HANGUL SYLLABLE KIYEOK-YE-TIKEUT 81D0 ACCD # HANGUL SYLLABLE KIYEOK-YE-RIEULKIYEOK 81D1 ACCE # HANGUL SYLLABLE KIYEOK-YE-RIEULMIEUM 81D2 ACCF # HANGUL SYLLABLE KIYEOK-YE-RIEULPIEUP 81D3 ACD0 # HANGUL SYLLABLE KIYEOK-YE-RIEULSIOS 81D4 ACD1 # HANGUL SYLLABLE KIYEOK-YE-RIEULTHIEUTH 81D5 ACD2 # HANGUL SYLLABLE KIYEOK-YE-RIEULPHIEUPH 81D6 ACD3 # HANGUL SYLLABLE KIYEOK-YE-RIEULHIEUH 81D7 ACD4 # HANGUL SYLLABLE KIYEOK-YE-MIEUM 81D8 ACD6 # HANGUL SYLLABLE KIYEOK-YE-PIEUPSIOS 81D9 ACD8 # HANGUL SYLLABLE KIYEOK-YE-SSANGSIOS 81DA ACD9 # HANGUL SYLLABLE KIYEOK-YE-IEUNG 81DB ACDA # HANGUL SYLLABLE KIYEOK-YE-CIEUC 81DC ACDB # HANGUL SYLLABLE KIYEOK-YE-CHIEUCH 81DD ACDC # HANGUL SYLLABLE KIYEOK-YE-KHIEUKH 81DE ACDD # HANGUL SYLLABLE KIYEOK-YE-THIEUTH 81DF ACDE # HANGUL SYLLABLE KIYEOK-YE-PHIEUPH 81E0 ACDF # HANGUL SYLLABLE KIYEOK-YE-HIEUH 81E1 ACE2 # HANGUL SYLLABLE KIYEOK-O-SSANGKIYEOK 81E2 ACE3 # HANGUL SYLLABLE KIYEOK-O-KIYEOKSIOS 81E3 ACE5 # HANGUL SYLLABLE KIYEOK-O-NIEUNCIEUC 81E4 ACE6 # HANGUL SYLLABLE KIYEOK-O-NIEUNHIEUH 81E5 ACE9 # HANGUL SYLLABLE KIYEOK-O-RIEULKIYEOK 81E6 ACEB # HANGUL SYLLABLE KIYEOK-O-RIEULPIEUP 81E7 ACED # HANGUL SYLLABLE KIYEOK-O-RIEULTHIEUTH 81E8 ACEE # HANGUL SYLLABLE KIYEOK-O-RIEULPHIEUPH 81E9 ACF2 # HANGUL SYLLABLE KIYEOK-O-PIEUPSIOS 81EA ACF4 # HANGUL SYLLABLE KIYEOK-O-SSANGSIOS 81EB ACF7 # HANGUL SYLLABLE KIYEOK-O-CHIEUCH 81EC ACF8 # HANGUL SYLLABLE KIYEOK-O-KHIEUKH 81ED ACF9 # HANGUL SYLLABLE KIYEOK-O-THIEUTH 81EE ACFA # HANGUL SYLLABLE KIYEOK-O-PHIEUPH 81EF ACFB # HANGUL SYLLABLE KIYEOK-O-HIEUH 81F0 ACFE # HANGUL SYLLABLE KIYEOK-WA-SSANGKIYEOK 81F1 ACFF # HANGUL SYLLABLE KIYEOK-WA-KIYEOKSIOS 81F2 AD01 # HANGUL SYLLABLE KIYEOK-WA-NIEUNCIEUC 81F3 AD02 # HANGUL SYLLABLE KIYEOK-WA-NIEUNHIEUH 81F4 AD03 # HANGUL SYLLABLE KIYEOK-WA-TIKEUT 81F5 AD05 # HANGUL SYLLABLE KIYEOK-WA-RIEULKIYEOK 81F6 AD07 # HANGUL SYLLABLE KIYEOK-WA-RIEULPIEUP 81F7 AD08 # HANGUL SYLLABLE KIYEOK-WA-RIEULSIOS 81F8 AD09 # HANGUL SYLLABLE KIYEOK-WA-RIEULTHIEUTH 81F9 AD0A # HANGUL SYLLABLE KIYEOK-WA-RIEULPHIEUPH 81FA AD0B # HANGUL SYLLABLE KIYEOK-WA-RIEULHIEUH 81FB AD0E # HANGUL SYLLABLE KIYEOK-WA-PIEUPSIOS 81FC AD10 # HANGUL SYLLABLE KIYEOK-WA-SSANGSIOS 81FD AD12 # HANGUL SYLLABLE KIYEOK-WA-CIEUC 81FE AD13 # HANGUL SYLLABLE KIYEOK-WA-CHIEUCH 8241 AD14 # HANGUL SYLLABLE KIYEOK-WA-KHIEUKH 8242 AD15 # HANGUL SYLLABLE KIYEOK-WA-THIEUTH 8243 AD16 # HANGUL SYLLABLE KIYEOK-WA-PHIEUPH 8244 AD17 # HANGUL SYLLABLE KIYEOK-WA-HIEUH 8245 AD19 # HANGUL SYLLABLE KIYEOK-WAE-KIYEOK 8246 AD1A # HANGUL SYLLABLE KIYEOK-WAE-SSANGKIYEOK 8247 AD1B # HANGUL SYLLABLE KIYEOK-WAE-KIYEOKSIOS 8248 AD1D # HANGUL SYLLABLE KIYEOK-WAE-NIEUNCIEUC 8249 AD1E # HANGUL SYLLABLE KIYEOK-WAE-NIEUNHIEUH 824A AD1F # HANGUL SYLLABLE KIYEOK-WAE-TIKEUT 824B AD21 # HANGUL SYLLABLE KIYEOK-WAE-RIEULKIYEOK 824C AD22 # HANGUL SYLLABLE KIYEOK-WAE-RIEULMIEUM 824D AD23 # HANGUL SYLLABLE KIYEOK-WAE-RIEULPIEUP 824E AD24 # HANGUL SYLLABLE KIYEOK-WAE-RIEULSIOS 824F AD25 # HANGUL SYLLABLE KIYEOK-WAE-RIEULTHIEUTH 8250 AD26 # HANGUL SYLLABLE KIYEOK-WAE-RIEULPHIEUPH 8251 AD27 # HANGUL SYLLABLE KIYEOK-WAE-RIEULHIEUH 8252 AD28 # HANGUL SYLLABLE KIYEOK-WAE-MIEUM 8253 AD2A # HANGUL SYLLABLE KIYEOK-WAE-PIEUPSIOS 8254 AD2B # HANGUL SYLLABLE KIYEOK-WAE-SIOS 8255 AD2E # HANGUL SYLLABLE KIYEOK-WAE-CIEUC 8256 AD2F # HANGUL SYLLABLE KIYEOK-WAE-CHIEUCH 8257 AD30 # HANGUL SYLLABLE KIYEOK-WAE-KHIEUKH 8258 AD31 # HANGUL SYLLABLE KIYEOK-WAE-THIEUTH 8259 AD32 # HANGUL SYLLABLE KIYEOK-WAE-PHIEUPH 825A AD33 # HANGUL SYLLABLE KIYEOK-WAE-HIEUH 8261 AD36 # HANGUL SYLLABLE KIYEOK-OE-SSANGKIYEOK 8262 AD37 # HANGUL SYLLABLE KIYEOK-OE-KIYEOKSIOS 8263 AD39 # HANGUL SYLLABLE KIYEOK-OE-NIEUNCIEUC 8264 AD3A # HANGUL SYLLABLE KIYEOK-OE-NIEUNHIEUH 8265 AD3B # HANGUL SYLLABLE KIYEOK-OE-TIKEUT 8266 AD3D # HANGUL SYLLABLE KIYEOK-OE-RIEULKIYEOK 8267 AD3E # HANGUL SYLLABLE KIYEOK-OE-RIEULMIEUM 8268 AD3F # HANGUL SYLLABLE KIYEOK-OE-RIEULPIEUP 8269 AD40 # HANGUL SYLLABLE KIYEOK-OE-RIEULSIOS 826A AD41 # HANGUL SYLLABLE KIYEOK-OE-RIEULTHIEUTH 826B AD42 # HANGUL SYLLABLE KIYEOK-OE-RIEULPHIEUPH 826C AD43 # HANGUL SYLLABLE KIYEOK-OE-RIEULHIEUH 826D AD46 # HANGUL SYLLABLE KIYEOK-OE-PIEUPSIOS 826E AD48 # HANGUL SYLLABLE KIYEOK-OE-SSANGSIOS 826F AD4A # HANGUL SYLLABLE KIYEOK-OE-CIEUC 8270 AD4B # HANGUL SYLLABLE KIYEOK-OE-CHIEUCH 8271 AD4C # HANGUL SYLLABLE KIYEOK-OE-KHIEUKH 8272 AD4D # HANGUL SYLLABLE KIYEOK-OE-THIEUTH 8273 AD4E # HANGUL SYLLABLE KIYEOK-OE-PHIEUPH 8274 AD4F # HANGUL SYLLABLE KIYEOK-OE-HIEUH 8275 AD51 # HANGUL SYLLABLE KIYEOK-YO-KIYEOK 8276 AD52 # HANGUL SYLLABLE KIYEOK-YO-SSANGKIYEOK 8277 AD53 # HANGUL SYLLABLE KIYEOK-YO-KIYEOKSIOS 8278 AD55 # HANGUL SYLLABLE KIYEOK-YO-NIEUNCIEUC 8279 AD56 # HANGUL SYLLABLE KIYEOK-YO-NIEUNHIEUH 827A AD57 # HANGUL SYLLABLE KIYEOK-YO-TIKEUT 8281 AD59 # HANGUL SYLLABLE KIYEOK-YO-RIEULKIYEOK 8282 AD5A # HANGUL SYLLABLE KIYEOK-YO-RIEULMIEUM 8283 AD5B # HANGUL SYLLABLE KIYEOK-YO-RIEULPIEUP 8284 AD5C # HANGUL SYLLABLE KIYEOK-YO-RIEULSIOS 8285 AD5D # HANGUL SYLLABLE KIYEOK-YO-RIEULTHIEUTH 8286 AD5E # HANGUL SYLLABLE KIYEOK-YO-RIEULPHIEUPH 8287 AD5F # HANGUL SYLLABLE KIYEOK-YO-RIEULHIEUH 8288 AD60 # HANGUL SYLLABLE KIYEOK-YO-MIEUM 8289 AD62 # HANGUL SYLLABLE KIYEOK-YO-PIEUPSIOS 828A AD64 # HANGUL SYLLABLE KIYEOK-YO-SSANGSIOS 828B AD65 # HANGUL SYLLABLE KIYEOK-YO-IEUNG 828C AD66 # HANGUL SYLLABLE KIYEOK-YO-CIEUC 828D AD67 # HANGUL SYLLABLE KIYEOK-YO-CHIEUCH 828E AD68 # HANGUL SYLLABLE KIYEOK-YO-KHIEUKH 828F AD69 # HANGUL SYLLABLE KIYEOK-YO-THIEUTH 8290 AD6A # HANGUL SYLLABLE KIYEOK-YO-PHIEUPH 8291 AD6B # HANGUL SYLLABLE KIYEOK-YO-HIEUH 8292 AD6E # HANGUL SYLLABLE KIYEOK-U-SSANGKIYEOK 8293 AD6F # HANGUL SYLLABLE KIYEOK-U-KIYEOKSIOS 8294 AD71 # HANGUL SYLLABLE KIYEOK-U-NIEUNCIEUC 8295 AD72 # HANGUL SYLLABLE KIYEOK-U-NIEUNHIEUH 8296 AD77 # HANGUL SYLLABLE KIYEOK-U-RIEULPIEUP 8297 AD78 # HANGUL SYLLABLE KIYEOK-U-RIEULSIOS 8298 AD79 # HANGUL SYLLABLE KIYEOK-U-RIEULTHIEUTH 8299 AD7A # HANGUL SYLLABLE KIYEOK-U-RIEULPHIEUPH 829A AD7E # HANGUL SYLLABLE KIYEOK-U-PIEUPSIOS 829B AD80 # HANGUL SYLLABLE KIYEOK-U-SSANGSIOS 829C AD83 # HANGUL SYLLABLE KIYEOK-U-CHIEUCH 829D AD84 # HANGUL SYLLABLE KIYEOK-U-KHIEUKH 829E AD85 # HANGUL SYLLABLE KIYEOK-U-THIEUTH 829F AD86 # HANGUL SYLLABLE KIYEOK-U-PHIEUPH 82A0 AD87 # HANGUL SYLLABLE KIYEOK-U-HIEUH 82A1 AD8A # HANGUL SYLLABLE KIYEOK-WEO-SSANGKIYEOK 82A2 AD8B # HANGUL SYLLABLE KIYEOK-WEO-KIYEOKSIOS 82A3 AD8D # HANGUL SYLLABLE KIYEOK-WEO-NIEUNCIEUC 82A4 AD8E # HANGUL SYLLABLE KIYEOK-WEO-NIEUNHIEUH 82A5 AD8F # HANGUL SYLLABLE KIYEOK-WEO-TIKEUT 82A6 AD91 # HANGUL SYLLABLE KIYEOK-WEO-RIEULKIYEOK 82A7 AD92 # HANGUL SYLLABLE KIYEOK-WEO-RIEULMIEUM 82A8 AD93 # HANGUL SYLLABLE KIYEOK-WEO-RIEULPIEUP 82A9 AD94 # HANGUL SYLLABLE KIYEOK-WEO-RIEULSIOS 82AA AD95 # HANGUL SYLLABLE KIYEOK-WEO-RIEULTHIEUTH 82AB AD96 # HANGUL SYLLABLE KIYEOK-WEO-RIEULPHIEUPH 82AC AD97 # HANGUL SYLLABLE KIYEOK-WEO-RIEULHIEUH 82AD AD98 # HANGUL SYLLABLE KIYEOK-WEO-MIEUM 82AE AD99 # HANGUL SYLLABLE KIYEOK-WEO-PIEUP 82AF AD9A # HANGUL SYLLABLE KIYEOK-WEO-PIEUPSIOS 82B0 AD9B # HANGUL SYLLABLE KIYEOK-WEO-SIOS 82B1 AD9E # HANGUL SYLLABLE KIYEOK-WEO-CIEUC 82B2 AD9F # HANGUL SYLLABLE KIYEOK-WEO-CHIEUCH 82B3 ADA0 # HANGUL SYLLABLE KIYEOK-WEO-KHIEUKH 82B4 ADA1 # HANGUL SYLLABLE KIYEOK-WEO-THIEUTH 82B5 ADA2 # HANGUL SYLLABLE KIYEOK-WEO-PHIEUPH 82B6 ADA3 # HANGUL SYLLABLE KIYEOK-WEO-HIEUH 82B7 ADA5 # HANGUL SYLLABLE KIYEOK-WE-KIYEOK 82B8 ADA6 # HANGUL SYLLABLE KIYEOK-WE-SSANGKIYEOK 82B9 ADA7 # HANGUL SYLLABLE KIYEOK-WE-KIYEOKSIOS 82BA ADA8 # HANGUL SYLLABLE KIYEOK-WE-NIEUN 82BB ADA9 # HANGUL SYLLABLE KIYEOK-WE-NIEUNCIEUC 82BC ADAA # HANGUL SYLLABLE KIYEOK-WE-NIEUNHIEUH 82BD ADAB # HANGUL SYLLABLE KIYEOK-WE-TIKEUT 82BE ADAC # HANGUL SYLLABLE KIYEOK-WE-RIEUL 82BF ADAD # HANGUL SYLLABLE KIYEOK-WE-RIEULKIYEOK 82C0 ADAE # HANGUL SYLLABLE KIYEOK-WE-RIEULMIEUM 82C1 ADAF # HANGUL SYLLABLE KIYEOK-WE-RIEULPIEUP 82C2 ADB0 # HANGUL SYLLABLE KIYEOK-WE-RIEULSIOS 82C3 ADB1 # HANGUL SYLLABLE KIYEOK-WE-RIEULTHIEUTH 82C4 ADB2 # HANGUL SYLLABLE KIYEOK-WE-RIEULPHIEUPH 82C5 ADB3 # HANGUL SYLLABLE KIYEOK-WE-RIEULHIEUH 82C6 ADB4 # HANGUL SYLLABLE KIYEOK-WE-MIEUM 82C7 ADB5 # HANGUL SYLLABLE KIYEOK-WE-PIEUP 82C8 ADB6 # HANGUL SYLLABLE KIYEOK-WE-PIEUPSIOS 82C9 ADB8 # HANGUL SYLLABLE KIYEOK-WE-SSANGSIOS 82CA ADB9 # HANGUL SYLLABLE KIYEOK-WE-IEUNG 82CB ADBA # HANGUL SYLLABLE KIYEOK-WE-CIEUC 82CC ADBB # HANGUL SYLLABLE KIYEOK-WE-CHIEUCH 82CD ADBC # HANGUL SYLLABLE KIYEOK-WE-KHIEUKH 82CE ADBD # HANGUL SYLLABLE KIYEOK-WE-THIEUTH 82CF ADBE # HANGUL SYLLABLE KIYEOK-WE-PHIEUPH 82D0 ADBF # HANGUL SYLLABLE KIYEOK-WE-HIEUH 82D1 ADC2 # HANGUL SYLLABLE KIYEOK-WI-SSANGKIYEOK 82D2 ADC3 # HANGUL SYLLABLE KIYEOK-WI-KIYEOKSIOS 82D3 ADC5 # HANGUL SYLLABLE KIYEOK-WI-NIEUNCIEUC 82D4 ADC6 # HANGUL SYLLABLE KIYEOK-WI-NIEUNHIEUH 82D5 ADC7 # HANGUL SYLLABLE KIYEOK-WI-TIKEUT 82D6 ADC9 # HANGUL SYLLABLE KIYEOK-WI-RIEULKIYEOK 82D7 ADCA # HANGUL SYLLABLE KIYEOK-WI-RIEULMIEUM 82D8 ADCB # HANGUL SYLLABLE KIYEOK-WI-RIEULPIEUP 82D9 ADCC # HANGUL SYLLABLE KIYEOK-WI-RIEULSIOS 82DA ADCD # HANGUL SYLLABLE KIYEOK-WI-RIEULTHIEUTH 82DB ADCE # HANGUL SYLLABLE KIYEOK-WI-RIEULPHIEUPH 82DC ADCF # HANGUL SYLLABLE KIYEOK-WI-RIEULHIEUH 82DD ADD2 # HANGUL SYLLABLE KIYEOK-WI-PIEUPSIOS 82DE ADD4 # HANGUL SYLLABLE KIYEOK-WI-SSANGSIOS 82DF ADD5 # HANGUL SYLLABLE KIYEOK-WI-IEUNG 82E0 ADD6 # HANGUL SYLLABLE KIYEOK-WI-CIEUC 82E1 ADD7 # HANGUL SYLLABLE KIYEOK-WI-CHIEUCH 82E2 ADD8 # HANGUL SYLLABLE KIYEOK-WI-KHIEUKH 82E3 ADD9 # HANGUL SYLLABLE KIYEOK-WI-THIEUTH 82E4 ADDA # HANGUL SYLLABLE KIYEOK-WI-PHIEUPH 82E5 ADDB # HANGUL SYLLABLE KIYEOK-WI-HIEUH 82E6 ADDD # HANGUL SYLLABLE KIYEOK-YU-KIYEOK 82E7 ADDE # HANGUL SYLLABLE KIYEOK-YU-SSANGKIYEOK 82E8 ADDF # HANGUL SYLLABLE KIYEOK-YU-KIYEOKSIOS 82E9 ADE1 # HANGUL SYLLABLE KIYEOK-YU-NIEUNCIEUC 82EA ADE2 # HANGUL SYLLABLE KIYEOK-YU-NIEUNHIEUH 82EB ADE3 # HANGUL SYLLABLE KIYEOK-YU-TIKEUT 82EC ADE5 # HANGUL SYLLABLE KIYEOK-YU-RIEULKIYEOK 82ED ADE6 # HANGUL SYLLABLE KIYEOK-YU-RIEULMIEUM 82EE ADE7 # HANGUL SYLLABLE KIYEOK-YU-RIEULPIEUP 82EF ADE8 # HANGUL SYLLABLE KIYEOK-YU-RIEULSIOS 82F0 ADE9 # HANGUL SYLLABLE KIYEOK-YU-RIEULTHIEUTH 82F1 ADEA # HANGUL SYLLABLE KIYEOK-YU-RIEULPHIEUPH 82F2 ADEB # HANGUL SYLLABLE KIYEOK-YU-RIEULHIEUH 82F3 ADEC # HANGUL SYLLABLE KIYEOK-YU-MIEUM 82F4 ADED # HANGUL SYLLABLE KIYEOK-YU-PIEUP 82F5 ADEE # HANGUL SYLLABLE KIYEOK-YU-PIEUPSIOS 82F6 ADEF # HANGUL SYLLABLE KIYEOK-YU-SIOS 82F7 ADF0 # HANGUL SYLLABLE KIYEOK-YU-SSANGSIOS 82F8 ADF1 # HANGUL SYLLABLE KIYEOK-YU-IEUNG 82F9 ADF2 # HANGUL SYLLABLE KIYEOK-YU-CIEUC 82FA ADF3 # HANGUL SYLLABLE KIYEOK-YU-CHIEUCH 82FB ADF4 # HANGUL SYLLABLE KIYEOK-YU-KHIEUKH 82FC ADF5 # HANGUL SYLLABLE KIYEOK-YU-THIEUTH 82FD ADF6 # HANGUL SYLLABLE KIYEOK-YU-PHIEUPH 82FE ADF7 # HANGUL SYLLABLE KIYEOK-YU-HIEUH 8341 ADFA # HANGUL SYLLABLE KIYEOK-EU-SSANGKIYEOK 8342 ADFB # HANGUL SYLLABLE KIYEOK-EU-KIYEOKSIOS 8343 ADFD # HANGUL SYLLABLE KIYEOK-EU-NIEUNCIEUC 8344 ADFE # HANGUL SYLLABLE KIYEOK-EU-NIEUNHIEUH 8345 AE02 # HANGUL SYLLABLE KIYEOK-EU-RIEULMIEUM 8346 AE03 # HANGUL SYLLABLE KIYEOK-EU-RIEULPIEUP 8347 AE04 # HANGUL SYLLABLE KIYEOK-EU-RIEULSIOS 8348 AE05 # HANGUL SYLLABLE KIYEOK-EU-RIEULTHIEUTH 8349 AE06 # HANGUL SYLLABLE KIYEOK-EU-RIEULPHIEUPH 834A AE07 # HANGUL SYLLABLE KIYEOK-EU-RIEULHIEUH 834B AE0A # HANGUL SYLLABLE KIYEOK-EU-PIEUPSIOS 834C AE0C # HANGUL SYLLABLE KIYEOK-EU-SSANGSIOS 834D AE0E # HANGUL SYLLABLE KIYEOK-EU-CIEUC 834E AE0F # HANGUL SYLLABLE KIYEOK-EU-CHIEUCH 834F AE10 # HANGUL SYLLABLE KIYEOK-EU-KHIEUKH 8350 AE11 # HANGUL SYLLABLE KIYEOK-EU-THIEUTH 8351 AE12 # HANGUL SYLLABLE KIYEOK-EU-PHIEUPH 8352 AE13 # HANGUL SYLLABLE KIYEOK-EU-HIEUH 8353 AE15 # HANGUL SYLLABLE KIYEOK-YI-KIYEOK 8354 AE16 # HANGUL SYLLABLE KIYEOK-YI-SSANGKIYEOK 8355 AE17 # HANGUL SYLLABLE KIYEOK-YI-KIYEOKSIOS 8356 AE18 # HANGUL SYLLABLE KIYEOK-YI-NIEUN 8357 AE19 # HANGUL SYLLABLE KIYEOK-YI-NIEUNCIEUC 8358 AE1A # HANGUL SYLLABLE KIYEOK-YI-NIEUNHIEUH 8359 AE1B # HANGUL SYLLABLE KIYEOK-YI-TIKEUT 835A AE1C # HANGUL SYLLABLE KIYEOK-YI-RIEUL 8361 AE1D # HANGUL SYLLABLE KIYEOK-YI-RIEULKIYEOK 8362 AE1E # HANGUL SYLLABLE KIYEOK-YI-RIEULMIEUM 8363 AE1F # HANGUL SYLLABLE KIYEOK-YI-RIEULPIEUP 8364 AE20 # HANGUL SYLLABLE KIYEOK-YI-RIEULSIOS 8365 AE21 # HANGUL SYLLABLE KIYEOK-YI-RIEULTHIEUTH 8366 AE22 # HANGUL SYLLABLE KIYEOK-YI-RIEULPHIEUPH 8367 AE23 # HANGUL SYLLABLE KIYEOK-YI-RIEULHIEUH 8368 AE24 # HANGUL SYLLABLE KIYEOK-YI-MIEUM 8369 AE25 # HANGUL SYLLABLE KIYEOK-YI-PIEUP 836A AE26 # HANGUL SYLLABLE KIYEOK-YI-PIEUPSIOS 836B AE27 # HANGUL SYLLABLE KIYEOK-YI-SIOS 836C AE28 # HANGUL SYLLABLE KIYEOK-YI-SSANGSIOS 836D AE29 # HANGUL SYLLABLE KIYEOK-YI-IEUNG 836E AE2A # HANGUL SYLLABLE KIYEOK-YI-CIEUC 836F AE2B # HANGUL SYLLABLE KIYEOK-YI-CHIEUCH 8370 AE2C # HANGUL SYLLABLE KIYEOK-YI-KHIEUKH 8371 AE2D # HANGUL SYLLABLE KIYEOK-YI-THIEUTH 8372 AE2E # HANGUL SYLLABLE KIYEOK-YI-PHIEUPH 8373 AE2F # HANGUL SYLLABLE KIYEOK-YI-HIEUH 8374 AE32 # HANGUL SYLLABLE KIYEOK-I-SSANGKIYEOK 8375 AE33 # HANGUL SYLLABLE KIYEOK-I-KIYEOKSIOS 8376 AE35 # HANGUL SYLLABLE KIYEOK-I-NIEUNCIEUC 8377 AE36 # HANGUL SYLLABLE KIYEOK-I-NIEUNHIEUH 8378 AE39 # HANGUL SYLLABLE KIYEOK-I-RIEULKIYEOK 8379 AE3B # HANGUL SYLLABLE KIYEOK-I-RIEULPIEUP 837A AE3C # HANGUL SYLLABLE KIYEOK-I-RIEULSIOS 8381 AE3D # HANGUL SYLLABLE KIYEOK-I-RIEULTHIEUTH 8382 AE3E # HANGUL SYLLABLE KIYEOK-I-RIEULPHIEUPH 8383 AE3F # HANGUL SYLLABLE KIYEOK-I-RIEULHIEUH 8384 AE42 # HANGUL SYLLABLE KIYEOK-I-PIEUPSIOS 8385 AE44 # HANGUL SYLLABLE KIYEOK-I-SSANGSIOS 8386 AE47 # HANGUL SYLLABLE KIYEOK-I-CHIEUCH 8387 AE48 # HANGUL SYLLABLE KIYEOK-I-KHIEUKH 8388 AE49 # HANGUL SYLLABLE KIYEOK-I-THIEUTH 8389 AE4B # HANGUL SYLLABLE KIYEOK-I-HIEUH 838A AE4F # HANGUL SYLLABLE SSANGKIYEOK-A-KIYEOKSIOS 838B AE51 # HANGUL SYLLABLE SSANGKIYEOK-A-NIEUNCIEUC 838C AE52 # HANGUL SYLLABLE SSANGKIYEOK-A-NIEUNHIEUH 838D AE53 # HANGUL SYLLABLE SSANGKIYEOK-A-TIKEUT 838E AE55 # HANGUL SYLLABLE SSANGKIYEOK-A-RIEULKIYEOK 838F AE57 # HANGUL SYLLABLE SSANGKIYEOK-A-RIEULPIEUP 8390 AE58 # HANGUL SYLLABLE SSANGKIYEOK-A-RIEULSIOS 8391 AE59 # HANGUL SYLLABLE SSANGKIYEOK-A-RIEULTHIEUTH 8392 AE5A # HANGUL SYLLABLE SSANGKIYEOK-A-RIEULPHIEUPH 8393 AE5B # HANGUL SYLLABLE SSANGKIYEOK-A-RIEULHIEUH 8394 AE5E # HANGUL SYLLABLE SSANGKIYEOK-A-PIEUPSIOS 8395 AE62 # HANGUL SYLLABLE SSANGKIYEOK-A-CIEUC 8396 AE63 # HANGUL SYLLABLE SSANGKIYEOK-A-CHIEUCH 8397 AE64 # HANGUL SYLLABLE SSANGKIYEOK-A-KHIEUKH 8398 AE66 # HANGUL SYLLABLE SSANGKIYEOK-A-PHIEUPH 8399 AE67 # HANGUL SYLLABLE SSANGKIYEOK-A-HIEUH 839A AE6A # HANGUL SYLLABLE SSANGKIYEOK-AE-SSANGKIYEOK 839B AE6B # HANGUL SYLLABLE SSANGKIYEOK-AE-KIYEOKSIOS 839C AE6D # HANGUL SYLLABLE SSANGKIYEOK-AE-NIEUNCIEUC 839D AE6E # HANGUL SYLLABLE SSANGKIYEOK-AE-NIEUNHIEUH 839E AE6F # HANGUL SYLLABLE SSANGKIYEOK-AE-TIKEUT 839F AE71 # HANGUL SYLLABLE SSANGKIYEOK-AE-RIEULKIYEOK 83A0 AE72 # HANGUL SYLLABLE SSANGKIYEOK-AE-RIEULMIEUM 83A1 AE73 # HANGUL SYLLABLE SSANGKIYEOK-AE-RIEULPIEUP 83A2 AE74 # HANGUL SYLLABLE SSANGKIYEOK-AE-RIEULSIOS 83A3 AE75 # HANGUL SYLLABLE SSANGKIYEOK-AE-RIEULTHIEUTH 83A4 AE76 # HANGUL SYLLABLE SSANGKIYEOK-AE-RIEULPHIEUPH 83A5 AE77 # HANGUL SYLLABLE SSANGKIYEOK-AE-RIEULHIEUH 83A6 AE7A # HANGUL SYLLABLE SSANGKIYEOK-AE-PIEUPSIOS 83A7 AE7E # HANGUL SYLLABLE SSANGKIYEOK-AE-CIEUC 83A8 AE7F # HANGUL SYLLABLE SSANGKIYEOK-AE-CHIEUCH 83A9 AE80 # HANGUL SYLLABLE SSANGKIYEOK-AE-KHIEUKH 83AA AE81 # HANGUL SYLLABLE SSANGKIYEOK-AE-THIEUTH 83AB AE82 # HANGUL SYLLABLE SSANGKIYEOK-AE-PHIEUPH 83AC AE83 # HANGUL SYLLABLE SSANGKIYEOK-AE-HIEUH 83AD AE86 # HANGUL SYLLABLE SSANGKIYEOK-YA-SSANGKIYEOK 83AE AE87 # HANGUL SYLLABLE SSANGKIYEOK-YA-KIYEOKSIOS 83AF AE88 # HANGUL SYLLABLE SSANGKIYEOK-YA-NIEUN 83B0 AE89 # HANGUL SYLLABLE SSANGKIYEOK-YA-NIEUNCIEUC 83B1 AE8A # HANGUL SYLLABLE SSANGKIYEOK-YA-NIEUNHIEUH 83B2 AE8B # HANGUL SYLLABLE SSANGKIYEOK-YA-TIKEUT 83B3 AE8D # HANGUL SYLLABLE SSANGKIYEOK-YA-RIEULKIYEOK 83B4 AE8E # HANGUL SYLLABLE SSANGKIYEOK-YA-RIEULMIEUM 83B5 AE8F # HANGUL SYLLABLE SSANGKIYEOK-YA-RIEULPIEUP 83B6 AE90 # HANGUL SYLLABLE SSANGKIYEOK-YA-RIEULSIOS 83B7 AE91 # HANGUL SYLLABLE SSANGKIYEOK-YA-RIEULTHIEUTH 83B8 AE92 # HANGUL SYLLABLE SSANGKIYEOK-YA-RIEULPHIEUPH 83B9 AE93 # HANGUL SYLLABLE SSANGKIYEOK-YA-RIEULHIEUH 83BA AE94 # HANGUL SYLLABLE SSANGKIYEOK-YA-MIEUM 83BB AE95 # HANGUL SYLLABLE SSANGKIYEOK-YA-PIEUP 83BC AE96 # HANGUL SYLLABLE SSANGKIYEOK-YA-PIEUPSIOS 83BD AE97 # HANGUL SYLLABLE SSANGKIYEOK-YA-SIOS 83BE AE98 # HANGUL SYLLABLE SSANGKIYEOK-YA-SSANGSIOS 83BF AE99 # HANGUL SYLLABLE SSANGKIYEOK-YA-IEUNG 83C0 AE9A # HANGUL SYLLABLE SSANGKIYEOK-YA-CIEUC 83C1 AE9B # HANGUL SYLLABLE SSANGKIYEOK-YA-CHIEUCH 83C2 AE9C # HANGUL SYLLABLE SSANGKIYEOK-YA-KHIEUKH 83C3 AE9D # HANGUL SYLLABLE SSANGKIYEOK-YA-THIEUTH 83C4 AE9E # HANGUL SYLLABLE SSANGKIYEOK-YA-PHIEUPH 83C5 AE9F # HANGUL SYLLABLE SSANGKIYEOK-YA-HIEUH 83C6 AEA0 # HANGUL SYLLABLE SSANGKIYEOK-YAE 83C7 AEA1 # HANGUL SYLLABLE SSANGKIYEOK-YAE-KIYEOK 83C8 AEA2 # HANGUL SYLLABLE SSANGKIYEOK-YAE-SSANGKIYEOK 83C9 AEA3 # HANGUL SYLLABLE SSANGKIYEOK-YAE-KIYEOKSIOS 83CA AEA4 # HANGUL SYLLABLE SSANGKIYEOK-YAE-NIEUN 83CB AEA5 # HANGUL SYLLABLE SSANGKIYEOK-YAE-NIEUNCIEUC 83CC AEA6 # HANGUL SYLLABLE SSANGKIYEOK-YAE-NIEUNHIEUH 83CD AEA7 # HANGUL SYLLABLE SSANGKIYEOK-YAE-TIKEUT 83CE AEA8 # HANGUL SYLLABLE SSANGKIYEOK-YAE-RIEUL 83CF AEA9 # HANGUL SYLLABLE SSANGKIYEOK-YAE-RIEULKIYEOK 83D0 AEAA # HANGUL SYLLABLE SSANGKIYEOK-YAE-RIEULMIEUM 83D1 AEAB # HANGUL SYLLABLE SSANGKIYEOK-YAE-RIEULPIEUP 83D2 AEAC # HANGUL SYLLABLE SSANGKIYEOK-YAE-RIEULSIOS 83D3 AEAD # HANGUL SYLLABLE SSANGKIYEOK-YAE-RIEULTHIEUTH 83D4 AEAE # HANGUL SYLLABLE SSANGKIYEOK-YAE-RIEULPHIEUPH 83D5 AEAF # HANGUL SYLLABLE SSANGKIYEOK-YAE-RIEULHIEUH 83D6 AEB0 # HANGUL SYLLABLE SSANGKIYEOK-YAE-MIEUM 83D7 AEB1 # HANGUL SYLLABLE SSANGKIYEOK-YAE-PIEUP 83D8 AEB2 # HANGUL SYLLABLE SSANGKIYEOK-YAE-PIEUPSIOS 83D9 AEB3 # HANGUL SYLLABLE SSANGKIYEOK-YAE-SIOS 83DA AEB4 # HANGUL SYLLABLE SSANGKIYEOK-YAE-SSANGSIOS 83DB AEB5 # HANGUL SYLLABLE SSANGKIYEOK-YAE-IEUNG 83DC AEB6 # HANGUL SYLLABLE SSANGKIYEOK-YAE-CIEUC 83DD AEB7 # HANGUL SYLLABLE SSANGKIYEOK-YAE-CHIEUCH 83DE AEB8 # HANGUL SYLLABLE SSANGKIYEOK-YAE-KHIEUKH 83DF AEB9 # HANGUL SYLLABLE SSANGKIYEOK-YAE-THIEUTH 83E0 AEBA # HANGUL SYLLABLE SSANGKIYEOK-YAE-PHIEUPH 83E1 AEBB # HANGUL SYLLABLE SSANGKIYEOK-YAE-HIEUH 83E2 AEBF # HANGUL SYLLABLE SSANGKIYEOK-EO-KIYEOKSIOS 83E3 AEC1 # HANGUL SYLLABLE SSANGKIYEOK-EO-NIEUNCIEUC 83E4 AEC2 # HANGUL SYLLABLE SSANGKIYEOK-EO-NIEUNHIEUH 83E5 AEC3 # HANGUL SYLLABLE SSANGKIYEOK-EO-TIKEUT 83E6 AEC5 # HANGUL SYLLABLE SSANGKIYEOK-EO-RIEULKIYEOK 83E7 AEC6 # HANGUL SYLLABLE SSANGKIYEOK-EO-RIEULMIEUM 83E8 AEC7 # HANGUL SYLLABLE SSANGKIYEOK-EO-RIEULPIEUP 83E9 AEC8 # HANGUL SYLLABLE SSANGKIYEOK-EO-RIEULSIOS 83EA AEC9 # HANGUL SYLLABLE SSANGKIYEOK-EO-RIEULTHIEUTH 83EB AECA # HANGUL SYLLABLE SSANGKIYEOK-EO-RIEULPHIEUPH 83EC AECB # HANGUL SYLLABLE SSANGKIYEOK-EO-RIEULHIEUH 83ED AECE # HANGUL SYLLABLE SSANGKIYEOK-EO-PIEUPSIOS 83EE AED2 # HANGUL SYLLABLE SSANGKIYEOK-EO-CIEUC 83EF AED3 # HANGUL SYLLABLE SSANGKIYEOK-EO-CHIEUCH 83F0 AED4 # HANGUL SYLLABLE SSANGKIYEOK-EO-KHIEUKH 83F1 AED5 # HANGUL SYLLABLE SSANGKIYEOK-EO-THIEUTH 83F2 AED6 # HANGUL SYLLABLE SSANGKIYEOK-EO-PHIEUPH 83F3 AED7 # HANGUL SYLLABLE SSANGKIYEOK-EO-HIEUH 83F4 AEDA # HANGUL SYLLABLE SSANGKIYEOK-E-SSANGKIYEOK 83F5 AEDB # HANGUL SYLLABLE SSANGKIYEOK-E-KIYEOKSIOS 83F6 AEDD # HANGUL SYLLABLE SSANGKIYEOK-E-NIEUNCIEUC 83F7 AEDE # HANGUL SYLLABLE SSANGKIYEOK-E-NIEUNHIEUH 83F8 AEDF # HANGUL SYLLABLE SSANGKIYEOK-E-TIKEUT 83F9 AEE0 # HANGUL SYLLABLE SSANGKIYEOK-E-RIEUL 83FA AEE1 # HANGUL SYLLABLE SSANGKIYEOK-E-RIEULKIYEOK 83FB AEE2 # HANGUL SYLLABLE SSANGKIYEOK-E-RIEULMIEUM 83FC AEE3 # HANGUL SYLLABLE SSANGKIYEOK-E-RIEULPIEUP 83FD AEE4 # HANGUL SYLLABLE SSANGKIYEOK-E-RIEULSIOS 83FE AEE5 # HANGUL SYLLABLE SSANGKIYEOK-E-RIEULTHIEUTH 8441 AEE6 # HANGUL SYLLABLE SSANGKIYEOK-E-RIEULPHIEUPH 8442 AEE7 # HANGUL SYLLABLE SSANGKIYEOK-E-RIEULHIEUH 8443 AEE9 # HANGUL SYLLABLE SSANGKIYEOK-E-PIEUP 8444 AEEA # HANGUL SYLLABLE SSANGKIYEOK-E-PIEUPSIOS 8445 AEEC # HANGUL SYLLABLE SSANGKIYEOK-E-SSANGSIOS 8446 AEEE # HANGUL SYLLABLE SSANGKIYEOK-E-CIEUC 8447 AEEF # HANGUL SYLLABLE SSANGKIYEOK-E-CHIEUCH 8448 AEF0 # HANGUL SYLLABLE SSANGKIYEOK-E-KHIEUKH 8449 AEF1 # HANGUL SYLLABLE SSANGKIYEOK-E-THIEUTH 844A AEF2 # HANGUL SYLLABLE SSANGKIYEOK-E-PHIEUPH 844B AEF3 # HANGUL SYLLABLE SSANGKIYEOK-E-HIEUH 844C AEF5 # HANGUL SYLLABLE SSANGKIYEOK-YEO-KIYEOK 844D AEF6 # HANGUL SYLLABLE SSANGKIYEOK-YEO-SSANGKIYEOK 844E AEF7 # HANGUL SYLLABLE SSANGKIYEOK-YEO-KIYEOKSIOS 844F AEF9 # HANGUL SYLLABLE SSANGKIYEOK-YEO-NIEUNCIEUC 8450 AEFA # HANGUL SYLLABLE SSANGKIYEOK-YEO-NIEUNHIEUH 8451 AEFB # HANGUL SYLLABLE SSANGKIYEOK-YEO-TIKEUT 8452 AEFD # HANGUL SYLLABLE SSANGKIYEOK-YEO-RIEULKIYEOK 8453 AEFE # HANGUL SYLLABLE SSANGKIYEOK-YEO-RIEULMIEUM 8454 AEFF # HANGUL SYLLABLE SSANGKIYEOK-YEO-RIEULPIEUP 8455 AF00 # HANGUL SYLLABLE SSANGKIYEOK-YEO-RIEULSIOS 8456 AF01 # HANGUL SYLLABLE SSANGKIYEOK-YEO-RIEULTHIEUTH 8457 AF02 # HANGUL SYLLABLE SSANGKIYEOK-YEO-RIEULPHIEUPH 8458 AF03 # HANGUL SYLLABLE SSANGKIYEOK-YEO-RIEULHIEUH 8459 AF04 # HANGUL SYLLABLE SSANGKIYEOK-YEO-MIEUM 845A AF05 # HANGUL SYLLABLE SSANGKIYEOK-YEO-PIEUP 8461 AF06 # HANGUL SYLLABLE SSANGKIYEOK-YEO-PIEUPSIOS 8462 AF09 # HANGUL SYLLABLE SSANGKIYEOK-YEO-IEUNG 8463 AF0A # HANGUL SYLLABLE SSANGKIYEOK-YEO-CIEUC 8464 AF0B # HANGUL SYLLABLE SSANGKIYEOK-YEO-CHIEUCH 8465 AF0C # HANGUL SYLLABLE SSANGKIYEOK-YEO-KHIEUKH 8466 AF0E # HANGUL SYLLABLE SSANGKIYEOK-YEO-PHIEUPH 8467 AF0F # HANGUL SYLLABLE SSANGKIYEOK-YEO-HIEUH 8468 AF11 # HANGUL SYLLABLE SSANGKIYEOK-YE-KIYEOK 8469 AF12 # HANGUL SYLLABLE SSANGKIYEOK-YE-SSANGKIYEOK 846A AF13 # HANGUL SYLLABLE SSANGKIYEOK-YE-KIYEOKSIOS 846B AF14 # HANGUL SYLLABLE SSANGKIYEOK-YE-NIEUN 846C AF15 # HANGUL SYLLABLE SSANGKIYEOK-YE-NIEUNCIEUC 846D AF16 # HANGUL SYLLABLE SSANGKIYEOK-YE-NIEUNHIEUH 846E AF17 # HANGUL SYLLABLE SSANGKIYEOK-YE-TIKEUT 846F AF18 # HANGUL SYLLABLE SSANGKIYEOK-YE-RIEUL 8470 AF19 # HANGUL SYLLABLE SSANGKIYEOK-YE-RIEULKIYEOK 8471 AF1A # HANGUL SYLLABLE SSANGKIYEOK-YE-RIEULMIEUM 8472 AF1B # HANGUL SYLLABLE SSANGKIYEOK-YE-RIEULPIEUP 8473 AF1C # HANGUL SYLLABLE SSANGKIYEOK-YE-RIEULSIOS 8474 AF1D # HANGUL SYLLABLE SSANGKIYEOK-YE-RIEULTHIEUTH 8475 AF1E # HANGUL SYLLABLE SSANGKIYEOK-YE-RIEULPHIEUPH 8476 AF1F # HANGUL SYLLABLE SSANGKIYEOK-YE-RIEULHIEUH 8477 AF20 # HANGUL SYLLABLE SSANGKIYEOK-YE-MIEUM 8478 AF21 # HANGUL SYLLABLE SSANGKIYEOK-YE-PIEUP 8479 AF22 # HANGUL SYLLABLE SSANGKIYEOK-YE-PIEUPSIOS 847A AF23 # HANGUL SYLLABLE SSANGKIYEOK-YE-SIOS 8481 AF24 # HANGUL SYLLABLE SSANGKIYEOK-YE-SSANGSIOS 8482 AF25 # HANGUL SYLLABLE SSANGKIYEOK-YE-IEUNG 8483 AF26 # HANGUL SYLLABLE SSANGKIYEOK-YE-CIEUC 8484 AF27 # HANGUL SYLLABLE SSANGKIYEOK-YE-CHIEUCH 8485 AF28 # HANGUL SYLLABLE SSANGKIYEOK-YE-KHIEUKH 8486 AF29 # HANGUL SYLLABLE SSANGKIYEOK-YE-THIEUTH 8487 AF2A # HANGUL SYLLABLE SSANGKIYEOK-YE-PHIEUPH 8488 AF2B # HANGUL SYLLABLE SSANGKIYEOK-YE-HIEUH 8489 AF2E # HANGUL SYLLABLE SSANGKIYEOK-O-SSANGKIYEOK 848A AF2F # HANGUL SYLLABLE SSANGKIYEOK-O-KIYEOKSIOS 848B AF31 # HANGUL SYLLABLE SSANGKIYEOK-O-NIEUNCIEUC 848C AF33 # HANGUL SYLLABLE SSANGKIYEOK-O-TIKEUT 848D AF35 # HANGUL SYLLABLE SSANGKIYEOK-O-RIEULKIYEOK 848E AF36 # HANGUL SYLLABLE SSANGKIYEOK-O-RIEULMIEUM 848F AF37 # HANGUL SYLLABLE SSANGKIYEOK-O-RIEULPIEUP 8490 AF38 # HANGUL SYLLABLE SSANGKIYEOK-O-RIEULSIOS 8491 AF39 # HANGUL SYLLABLE SSANGKIYEOK-O-RIEULTHIEUTH 8492 AF3A # HANGUL SYLLABLE SSANGKIYEOK-O-RIEULPHIEUPH 8493 AF3B # HANGUL SYLLABLE SSANGKIYEOK-O-RIEULHIEUH 8494 AF3E # HANGUL SYLLABLE SSANGKIYEOK-O-PIEUPSIOS 8495 AF40 # HANGUL SYLLABLE SSANGKIYEOK-O-SSANGSIOS 8496 AF44 # HANGUL SYLLABLE SSANGKIYEOK-O-KHIEUKH 8497 AF45 # HANGUL SYLLABLE SSANGKIYEOK-O-THIEUTH 8498 AF46 # HANGUL SYLLABLE SSANGKIYEOK-O-PHIEUPH 8499 AF47 # HANGUL SYLLABLE SSANGKIYEOK-O-HIEUH 849A AF4A # HANGUL SYLLABLE SSANGKIYEOK-WA-SSANGKIYEOK 849B AF4B # HANGUL SYLLABLE SSANGKIYEOK-WA-KIYEOKSIOS 849C AF4C # HANGUL SYLLABLE SSANGKIYEOK-WA-NIEUN 849D AF4D # HANGUL SYLLABLE SSANGKIYEOK-WA-NIEUNCIEUC 849E AF4E # HANGUL SYLLABLE SSANGKIYEOK-WA-NIEUNHIEUH 849F AF4F # HANGUL SYLLABLE SSANGKIYEOK-WA-TIKEUT 84A0 AF51 # HANGUL SYLLABLE SSANGKIYEOK-WA-RIEULKIYEOK 84A1 AF52 # HANGUL SYLLABLE SSANGKIYEOK-WA-RIEULMIEUM 84A2 AF53 # HANGUL SYLLABLE SSANGKIYEOK-WA-RIEULPIEUP 84A3 AF54 # HANGUL SYLLABLE SSANGKIYEOK-WA-RIEULSIOS 84A4 AF55 # HANGUL SYLLABLE SSANGKIYEOK-WA-RIEULTHIEUTH 84A5 AF56 # HANGUL SYLLABLE SSANGKIYEOK-WA-RIEULPHIEUPH 84A6 AF57 # HANGUL SYLLABLE SSANGKIYEOK-WA-RIEULHIEUH 84A7 AF58 # HANGUL SYLLABLE SSANGKIYEOK-WA-MIEUM 84A8 AF59 # HANGUL SYLLABLE SSANGKIYEOK-WA-PIEUP 84A9 AF5A # HANGUL SYLLABLE SSANGKIYEOK-WA-PIEUPSIOS 84AA AF5B # HANGUL SYLLABLE SSANGKIYEOK-WA-SIOS 84AB AF5E # HANGUL SYLLABLE SSANGKIYEOK-WA-CIEUC 84AC AF5F # HANGUL SYLLABLE SSANGKIYEOK-WA-CHIEUCH 84AD AF60 # HANGUL SYLLABLE SSANGKIYEOK-WA-KHIEUKH 84AE AF61 # HANGUL SYLLABLE SSANGKIYEOK-WA-THIEUTH 84AF AF62 # HANGUL SYLLABLE SSANGKIYEOK-WA-PHIEUPH 84B0 AF63 # HANGUL SYLLABLE SSANGKIYEOK-WA-HIEUH 84B1 AF66 # HANGUL SYLLABLE SSANGKIYEOK-WAE-SSANGKIYEOK 84B2 AF67 # HANGUL SYLLABLE SSANGKIYEOK-WAE-KIYEOKSIOS 84B3 AF68 # HANGUL SYLLABLE SSANGKIYEOK-WAE-NIEUN 84B4 AF69 # HANGUL SYLLABLE SSANGKIYEOK-WAE-NIEUNCIEUC 84B5 AF6A # HANGUL SYLLABLE SSANGKIYEOK-WAE-NIEUNHIEUH 84B6 AF6B # HANGUL SYLLABLE SSANGKIYEOK-WAE-TIKEUT 84B7 AF6C # HANGUL SYLLABLE SSANGKIYEOK-WAE-RIEUL 84B8 AF6D # HANGUL SYLLABLE SSANGKIYEOK-WAE-RIEULKIYEOK 84B9 AF6E # HANGUL SYLLABLE SSANGKIYEOK-WAE-RIEULMIEUM 84BA AF6F # HANGUL SYLLABLE SSANGKIYEOK-WAE-RIEULPIEUP 84BB AF70 # HANGUL SYLLABLE SSANGKIYEOK-WAE-RIEULSIOS 84BC AF71 # HANGUL SYLLABLE SSANGKIYEOK-WAE-RIEULTHIEUTH 84BD AF72 # HANGUL SYLLABLE SSANGKIYEOK-WAE-RIEULPHIEUPH 84BE AF73 # HANGUL SYLLABLE SSANGKIYEOK-WAE-RIEULHIEUH 84BF AF74 # HANGUL SYLLABLE SSANGKIYEOK-WAE-MIEUM 84C0 AF75 # HANGUL SYLLABLE SSANGKIYEOK-WAE-PIEUP 84C1 AF76 # HANGUL SYLLABLE SSANGKIYEOK-WAE-PIEUPSIOS 84C2 AF77 # HANGUL SYLLABLE SSANGKIYEOK-WAE-SIOS 84C3 AF78 # HANGUL SYLLABLE SSANGKIYEOK-WAE-SSANGSIOS 84C4 AF7A # HANGUL SYLLABLE SSANGKIYEOK-WAE-CIEUC 84C5 AF7B # HANGUL SYLLABLE SSANGKIYEOK-WAE-CHIEUCH 84C6 AF7C # HANGUL SYLLABLE SSANGKIYEOK-WAE-KHIEUKH 84C7 AF7D # HANGUL SYLLABLE SSANGKIYEOK-WAE-THIEUTH 84C8 AF7E # HANGUL SYLLABLE SSANGKIYEOK-WAE-PHIEUPH 84C9 AF7F # HANGUL SYLLABLE SSANGKIYEOK-WAE-HIEUH 84CA AF81 # HANGUL SYLLABLE SSANGKIYEOK-OE-KIYEOK 84CB AF82 # HANGUL SYLLABLE SSANGKIYEOK-OE-SSANGKIYEOK 84CC AF83 # HANGUL SYLLABLE SSANGKIYEOK-OE-KIYEOKSIOS 84CD AF85 # HANGUL SYLLABLE SSANGKIYEOK-OE-NIEUNCIEUC 84CE AF86 # HANGUL SYLLABLE SSANGKIYEOK-OE-NIEUNHIEUH 84CF AF87 # HANGUL SYLLABLE SSANGKIYEOK-OE-TIKEUT 84D0 AF89 # HANGUL SYLLABLE SSANGKIYEOK-OE-RIEULKIYEOK 84D1 AF8A # HANGUL SYLLABLE SSANGKIYEOK-OE-RIEULMIEUM 84D2 AF8B # HANGUL SYLLABLE SSANGKIYEOK-OE-RIEULPIEUP 84D3 AF8C # HANGUL SYLLABLE SSANGKIYEOK-OE-RIEULSIOS 84D4 AF8D # HANGUL SYLLABLE SSANGKIYEOK-OE-RIEULTHIEUTH 84D5 AF8E # HANGUL SYLLABLE SSANGKIYEOK-OE-RIEULPHIEUPH 84D6 AF8F # HANGUL SYLLABLE SSANGKIYEOK-OE-RIEULHIEUH 84D7 AF92 # HANGUL SYLLABLE SSANGKIYEOK-OE-PIEUPSIOS 84D8 AF93 # HANGUL SYLLABLE SSANGKIYEOK-OE-SIOS 84D9 AF94 # HANGUL SYLLABLE SSANGKIYEOK-OE-SSANGSIOS 84DA AF96 # HANGUL SYLLABLE SSANGKIYEOK-OE-CIEUC 84DB AF97 # HANGUL SYLLABLE SSANGKIYEOK-OE-CHIEUCH 84DC AF98 # HANGUL SYLLABLE SSANGKIYEOK-OE-KHIEUKH 84DD AF99 # HANGUL SYLLABLE SSANGKIYEOK-OE-THIEUTH 84DE AF9A # HANGUL SYLLABLE SSANGKIYEOK-OE-PHIEUPH 84DF AF9B # HANGUL SYLLABLE SSANGKIYEOK-OE-HIEUH 84E0 AF9D # HANGUL SYLLABLE SSANGKIYEOK-YO-KIYEOK 84E1 AF9E # HANGUL SYLLABLE SSANGKIYEOK-YO-SSANGKIYEOK 84E2 AF9F # HANGUL SYLLABLE SSANGKIYEOK-YO-KIYEOKSIOS 84E3 AFA0 # HANGUL SYLLABLE SSANGKIYEOK-YO-NIEUN 84E4 AFA1 # HANGUL SYLLABLE SSANGKIYEOK-YO-NIEUNCIEUC 84E5 AFA2 # HANGUL SYLLABLE SSANGKIYEOK-YO-NIEUNHIEUH 84E6 AFA3 # HANGUL SYLLABLE SSANGKIYEOK-YO-TIKEUT 84E7 AFA4 # HANGUL SYLLABLE SSANGKIYEOK-YO-RIEUL 84E8 AFA5 # HANGUL SYLLABLE SSANGKIYEOK-YO-RIEULKIYEOK 84E9 AFA6 # HANGUL SYLLABLE SSANGKIYEOK-YO-RIEULMIEUM 84EA AFA7 # HANGUL SYLLABLE SSANGKIYEOK-YO-RIEULPIEUP 84EB AFA8 # HANGUL SYLLABLE SSANGKIYEOK-YO-RIEULSIOS 84EC AFA9 # HANGUL SYLLABLE SSANGKIYEOK-YO-RIEULTHIEUTH 84ED AFAA # HANGUL SYLLABLE SSANGKIYEOK-YO-RIEULPHIEUPH 84EE AFAB # HANGUL SYLLABLE SSANGKIYEOK-YO-RIEULHIEUH 84EF AFAC # HANGUL SYLLABLE SSANGKIYEOK-YO-MIEUM 84F0 AFAD # HANGUL SYLLABLE SSANGKIYEOK-YO-PIEUP 84F1 AFAE # HANGUL SYLLABLE SSANGKIYEOK-YO-PIEUPSIOS 84F2 AFAF # HANGUL SYLLABLE SSANGKIYEOK-YO-SIOS 84F3 AFB0 # HANGUL SYLLABLE SSANGKIYEOK-YO-SSANGSIOS 84F4 AFB1 # HANGUL SYLLABLE SSANGKIYEOK-YO-IEUNG 84F5 AFB2 # HANGUL SYLLABLE SSANGKIYEOK-YO-CIEUC 84F6 AFB3 # HANGUL SYLLABLE SSANGKIYEOK-YO-CHIEUCH 84F7 AFB4 # HANGUL SYLLABLE SSANGKIYEOK-YO-KHIEUKH 84F8 AFB5 # HANGUL SYLLABLE SSANGKIYEOK-YO-THIEUTH 84F9 AFB6 # HANGUL SYLLABLE SSANGKIYEOK-YO-PHIEUPH 84FA AFB7 # HANGUL SYLLABLE SSANGKIYEOK-YO-HIEUH 84FB AFBA # HANGUL SYLLABLE SSANGKIYEOK-U-SSANGKIYEOK 84FC AFBB # HANGUL SYLLABLE SSANGKIYEOK-U-KIYEOKSIOS 84FD AFBD # HANGUL SYLLABLE SSANGKIYEOK-U-NIEUNCIEUC 84FE AFBE # HANGUL SYLLABLE SSANGKIYEOK-U-NIEUNHIEUH 8541 AFBF # HANGUL SYLLABLE SSANGKIYEOK-U-TIKEUT 8542 AFC1 # HANGUL SYLLABLE SSANGKIYEOK-U-RIEULKIYEOK 8543 AFC2 # HANGUL SYLLABLE SSANGKIYEOK-U-RIEULMIEUM 8544 AFC3 # HANGUL SYLLABLE SSANGKIYEOK-U-RIEULPIEUP 8545 AFC4 # HANGUL SYLLABLE SSANGKIYEOK-U-RIEULSIOS 8546 AFC5 # HANGUL SYLLABLE SSANGKIYEOK-U-RIEULTHIEUTH 8547 AFC6 # HANGUL SYLLABLE SSANGKIYEOK-U-RIEULPHIEUPH 8548 AFCA # HANGUL SYLLABLE SSANGKIYEOK-U-PIEUPSIOS 8549 AFCC # HANGUL SYLLABLE SSANGKIYEOK-U-SSANGSIOS 854A AFCF # HANGUL SYLLABLE SSANGKIYEOK-U-CHIEUCH 854B AFD0 # HANGUL SYLLABLE SSANGKIYEOK-U-KHIEUKH 854C AFD1 # HANGUL SYLLABLE SSANGKIYEOK-U-THIEUTH 854D AFD2 # HANGUL SYLLABLE SSANGKIYEOK-U-PHIEUPH 854E AFD3 # HANGUL SYLLABLE SSANGKIYEOK-U-HIEUH 854F AFD5 # HANGUL SYLLABLE SSANGKIYEOK-WEO-KIYEOK 8550 AFD6 # HANGUL SYLLABLE SSANGKIYEOK-WEO-SSANGKIYEOK 8551 AFD7 # HANGUL SYLLABLE SSANGKIYEOK-WEO-KIYEOKSIOS 8552 AFD8 # HANGUL SYLLABLE SSANGKIYEOK-WEO-NIEUN 8553 AFD9 # HANGUL SYLLABLE SSANGKIYEOK-WEO-NIEUNCIEUC 8554 AFDA # HANGUL SYLLABLE SSANGKIYEOK-WEO-NIEUNHIEUH 8555 AFDB # HANGUL SYLLABLE SSANGKIYEOK-WEO-TIKEUT 8556 AFDD # HANGUL SYLLABLE SSANGKIYEOK-WEO-RIEULKIYEOK 8557 AFDE # HANGUL SYLLABLE SSANGKIYEOK-WEO-RIEULMIEUM 8558 AFDF # HANGUL SYLLABLE SSANGKIYEOK-WEO-RIEULPIEUP 8559 AFE0 # HANGUL SYLLABLE SSANGKIYEOK-WEO-RIEULSIOS 855A AFE1 # HANGUL SYLLABLE SSANGKIYEOK-WEO-RIEULTHIEUTH 8561 AFE2 # HANGUL SYLLABLE SSANGKIYEOK-WEO-RIEULPHIEUPH 8562 AFE3 # HANGUL SYLLABLE SSANGKIYEOK-WEO-RIEULHIEUH 8563 AFE4 # HANGUL SYLLABLE SSANGKIYEOK-WEO-MIEUM 8564 AFE5 # HANGUL SYLLABLE SSANGKIYEOK-WEO-PIEUP 8565 AFE6 # HANGUL SYLLABLE SSANGKIYEOK-WEO-PIEUPSIOS 8566 AFE7 # HANGUL SYLLABLE SSANGKIYEOK-WEO-SIOS 8567 AFEA # HANGUL SYLLABLE SSANGKIYEOK-WEO-CIEUC 8568 AFEB # HANGUL SYLLABLE SSANGKIYEOK-WEO-CHIEUCH 8569 AFEC # HANGUL SYLLABLE SSANGKIYEOK-WEO-KHIEUKH 856A AFED # HANGUL SYLLABLE SSANGKIYEOK-WEO-THIEUTH 856B AFEE # HANGUL SYLLABLE SSANGKIYEOK-WEO-PHIEUPH 856C AFEF # HANGUL SYLLABLE SSANGKIYEOK-WEO-HIEUH 856D AFF2 # HANGUL SYLLABLE SSANGKIYEOK-WE-SSANGKIYEOK 856E AFF3 # HANGUL SYLLABLE SSANGKIYEOK-WE-KIYEOKSIOS 856F AFF5 # HANGUL SYLLABLE SSANGKIYEOK-WE-NIEUNCIEUC 8570 AFF6 # HANGUL SYLLABLE SSANGKIYEOK-WE-NIEUNHIEUH 8571 AFF7 # HANGUL SYLLABLE SSANGKIYEOK-WE-TIKEUT 8572 AFF9 # HANGUL SYLLABLE SSANGKIYEOK-WE-RIEULKIYEOK 8573 AFFA # HANGUL SYLLABLE SSANGKIYEOK-WE-RIEULMIEUM 8574 AFFB # HANGUL SYLLABLE SSANGKIYEOK-WE-RIEULPIEUP 8575 AFFC # HANGUL SYLLABLE SSANGKIYEOK-WE-RIEULSIOS 8576 AFFD # HANGUL SYLLABLE SSANGKIYEOK-WE-RIEULTHIEUTH 8577 AFFE # HANGUL SYLLABLE SSANGKIYEOK-WE-RIEULPHIEUPH 8578 AFFF # HANGUL SYLLABLE SSANGKIYEOK-WE-RIEULHIEUH 8579 B002 # HANGUL SYLLABLE SSANGKIYEOK-WE-PIEUPSIOS 857A B003 # HANGUL SYLLABLE SSANGKIYEOK-WE-SIOS 8581 B005 # HANGUL SYLLABLE SSANGKIYEOK-WE-IEUNG 8582 B006 # HANGUL SYLLABLE SSANGKIYEOK-WE-CIEUC 8583 B007 # HANGUL SYLLABLE SSANGKIYEOK-WE-CHIEUCH 8584 B008 # HANGUL SYLLABLE SSANGKIYEOK-WE-KHIEUKH 8585 B009 # HANGUL SYLLABLE SSANGKIYEOK-WE-THIEUTH 8586 B00A # HANGUL SYLLABLE SSANGKIYEOK-WE-PHIEUPH 8587 B00B # HANGUL SYLLABLE SSANGKIYEOK-WE-HIEUH 8588 B00D # HANGUL SYLLABLE SSANGKIYEOK-WI-KIYEOK 8589 B00E # HANGUL SYLLABLE SSANGKIYEOK-WI-SSANGKIYEOK 858A B00F # HANGUL SYLLABLE SSANGKIYEOK-WI-KIYEOKSIOS 858B B011 # HANGUL SYLLABLE SSANGKIYEOK-WI-NIEUNCIEUC 858C B012 # HANGUL SYLLABLE SSANGKIYEOK-WI-NIEUNHIEUH 858D B013 # HANGUL SYLLABLE SSANGKIYEOK-WI-TIKEUT 858E B015 # HANGUL SYLLABLE SSANGKIYEOK-WI-RIEULKIYEOK 858F B016 # HANGUL SYLLABLE SSANGKIYEOK-WI-RIEULMIEUM 8590 B017 # HANGUL SYLLABLE SSANGKIYEOK-WI-RIEULPIEUP 8591 B018 # HANGUL SYLLABLE SSANGKIYEOK-WI-RIEULSIOS 8592 B019 # HANGUL SYLLABLE SSANGKIYEOK-WI-RIEULTHIEUTH 8593 B01A # HANGUL SYLLABLE SSANGKIYEOK-WI-RIEULPHIEUPH 8594 B01B # HANGUL SYLLABLE SSANGKIYEOK-WI-RIEULHIEUH 8595 B01E # HANGUL SYLLABLE SSANGKIYEOK-WI-PIEUPSIOS 8596 B01F # HANGUL SYLLABLE SSANGKIYEOK-WI-SIOS 8597 B020 # HANGUL SYLLABLE SSANGKIYEOK-WI-SSANGSIOS 8598 B021 # HANGUL SYLLABLE SSANGKIYEOK-WI-IEUNG 8599 B022 # HANGUL SYLLABLE SSANGKIYEOK-WI-CIEUC 859A B023 # HANGUL SYLLABLE SSANGKIYEOK-WI-CHIEUCH 859B B024 # HANGUL SYLLABLE SSANGKIYEOK-WI-KHIEUKH 859C B025 # HANGUL SYLLABLE SSANGKIYEOK-WI-THIEUTH 859D B026 # HANGUL SYLLABLE SSANGKIYEOK-WI-PHIEUPH 859E B027 # HANGUL SYLLABLE SSANGKIYEOK-WI-HIEUH 859F B029 # HANGUL SYLLABLE SSANGKIYEOK-YU-KIYEOK 85A0 B02A # HANGUL SYLLABLE SSANGKIYEOK-YU-SSANGKIYEOK 85A1 B02B # HANGUL SYLLABLE SSANGKIYEOK-YU-KIYEOKSIOS 85A2 B02C # HANGUL SYLLABLE SSANGKIYEOK-YU-NIEUN 85A3 B02D # HANGUL SYLLABLE SSANGKIYEOK-YU-NIEUNCIEUC 85A4 B02E # HANGUL SYLLABLE SSANGKIYEOK-YU-NIEUNHIEUH 85A5 B02F # HANGUL SYLLABLE SSANGKIYEOK-YU-TIKEUT 85A6 B030 # HANGUL SYLLABLE SSANGKIYEOK-YU-RIEUL 85A7 B031 # HANGUL SYLLABLE SSANGKIYEOK-YU-RIEULKIYEOK 85A8 B032 # HANGUL SYLLABLE SSANGKIYEOK-YU-RIEULMIEUM 85A9 B033 # HANGUL SYLLABLE SSANGKIYEOK-YU-RIEULPIEUP 85AA B034 # HANGUL SYLLABLE SSANGKIYEOK-YU-RIEULSIOS 85AB B035 # HANGUL SYLLABLE SSANGKIYEOK-YU-RIEULTHIEUTH 85AC B036 # HANGUL SYLLABLE SSANGKIYEOK-YU-RIEULPHIEUPH 85AD B037 # HANGUL SYLLABLE SSANGKIYEOK-YU-RIEULHIEUH 85AE B038 # HANGUL SYLLABLE SSANGKIYEOK-YU-MIEUM 85AF B039 # HANGUL SYLLABLE SSANGKIYEOK-YU-PIEUP 85B0 B03A # HANGUL SYLLABLE SSANGKIYEOK-YU-PIEUPSIOS 85B1 B03B # HANGUL SYLLABLE SSANGKIYEOK-YU-SIOS 85B2 B03C # HANGUL SYLLABLE SSANGKIYEOK-YU-SSANGSIOS 85B3 B03D # HANGUL SYLLABLE SSANGKIYEOK-YU-IEUNG 85B4 B03E # HANGUL SYLLABLE SSANGKIYEOK-YU-CIEUC 85B5 B03F # HANGUL SYLLABLE SSANGKIYEOK-YU-CHIEUCH 85B6 B040 # HANGUL SYLLABLE SSANGKIYEOK-YU-KHIEUKH 85B7 B041 # HANGUL SYLLABLE SSANGKIYEOK-YU-THIEUTH 85B8 B042 # HANGUL SYLLABLE SSANGKIYEOK-YU-PHIEUPH 85B9 B043 # HANGUL SYLLABLE SSANGKIYEOK-YU-HIEUH 85BA B046 # HANGUL SYLLABLE SSANGKIYEOK-EU-SSANGKIYEOK 85BB B047 # HANGUL SYLLABLE SSANGKIYEOK-EU-KIYEOKSIOS 85BC B049 # HANGUL SYLLABLE SSANGKIYEOK-EU-NIEUNCIEUC 85BD B04B # HANGUL SYLLABLE SSANGKIYEOK-EU-TIKEUT 85BE B04D # HANGUL SYLLABLE SSANGKIYEOK-EU-RIEULKIYEOK 85BF B04F # HANGUL SYLLABLE SSANGKIYEOK-EU-RIEULPIEUP 85C0 B050 # HANGUL SYLLABLE SSANGKIYEOK-EU-RIEULSIOS 85C1 B051 # HANGUL SYLLABLE SSANGKIYEOK-EU-RIEULTHIEUTH 85C2 B052 # HANGUL SYLLABLE SSANGKIYEOK-EU-RIEULPHIEUPH 85C3 B056 # HANGUL SYLLABLE SSANGKIYEOK-EU-PIEUPSIOS 85C4 B058 # HANGUL SYLLABLE SSANGKIYEOK-EU-SSANGSIOS 85C5 B05A # HANGUL SYLLABLE SSANGKIYEOK-EU-CIEUC 85C6 B05B # HANGUL SYLLABLE SSANGKIYEOK-EU-CHIEUCH 85C7 B05C # HANGUL SYLLABLE SSANGKIYEOK-EU-KHIEUKH 85C8 B05E # HANGUL SYLLABLE SSANGKIYEOK-EU-PHIEUPH 85C9 B05F # HANGUL SYLLABLE SSANGKIYEOK-EU-HIEUH 85CA B060 # HANGUL SYLLABLE SSANGKIYEOK-YI 85CB B061 # HANGUL SYLLABLE SSANGKIYEOK-YI-KIYEOK 85CC B062 # HANGUL SYLLABLE SSANGKIYEOK-YI-SSANGKIYEOK 85CD B063 # HANGUL SYLLABLE SSANGKIYEOK-YI-KIYEOKSIOS 85CE B064 # HANGUL SYLLABLE SSANGKIYEOK-YI-NIEUN 85CF B065 # HANGUL SYLLABLE SSANGKIYEOK-YI-NIEUNCIEUC 85D0 B066 # HANGUL SYLLABLE SSANGKIYEOK-YI-NIEUNHIEUH 85D1 B067 # HANGUL SYLLABLE SSANGKIYEOK-YI-TIKEUT 85D2 B068 # HANGUL SYLLABLE SSANGKIYEOK-YI-RIEUL 85D3 B069 # HANGUL SYLLABLE SSANGKIYEOK-YI-RIEULKIYEOK 85D4 B06A # HANGUL SYLLABLE SSANGKIYEOK-YI-RIEULMIEUM 85D5 B06B # HANGUL SYLLABLE SSANGKIYEOK-YI-RIEULPIEUP 85D6 B06C # HANGUL SYLLABLE SSANGKIYEOK-YI-RIEULSIOS 85D7 B06D # HANGUL SYLLABLE SSANGKIYEOK-YI-RIEULTHIEUTH 85D8 B06E # HANGUL SYLLABLE SSANGKIYEOK-YI-RIEULPHIEUPH 85D9 B06F # HANGUL SYLLABLE SSANGKIYEOK-YI-RIEULHIEUH 85DA B070 # HANGUL SYLLABLE SSANGKIYEOK-YI-MIEUM 85DB B071 # HANGUL SYLLABLE SSANGKIYEOK-YI-PIEUP 85DC B072 # HANGUL SYLLABLE SSANGKIYEOK-YI-PIEUPSIOS 85DD B073 # HANGUL SYLLABLE SSANGKIYEOK-YI-SIOS 85DE B074 # HANGUL SYLLABLE SSANGKIYEOK-YI-SSANGSIOS 85DF B075 # HANGUL SYLLABLE SSANGKIYEOK-YI-IEUNG 85E0 B076 # HANGUL SYLLABLE SSANGKIYEOK-YI-CIEUC 85E1 B077 # HANGUL SYLLABLE SSANGKIYEOK-YI-CHIEUCH 85E2 B078 # HANGUL SYLLABLE SSANGKIYEOK-YI-KHIEUKH 85E3 B079 # HANGUL SYLLABLE SSANGKIYEOK-YI-THIEUTH 85E4 B07A # HANGUL SYLLABLE SSANGKIYEOK-YI-PHIEUPH 85E5 B07B # HANGUL SYLLABLE SSANGKIYEOK-YI-HIEUH 85E6 B07E # HANGUL SYLLABLE SSANGKIYEOK-I-SSANGKIYEOK 85E7 B07F # HANGUL SYLLABLE SSANGKIYEOK-I-KIYEOKSIOS 85E8 B081 # HANGUL SYLLABLE SSANGKIYEOK-I-NIEUNCIEUC 85E9 B082 # HANGUL SYLLABLE SSANGKIYEOK-I-NIEUNHIEUH 85EA B083 # HANGUL SYLLABLE SSANGKIYEOK-I-TIKEUT 85EB B085 # HANGUL SYLLABLE SSANGKIYEOK-I-RIEULKIYEOK 85EC B086 # HANGUL SYLLABLE SSANGKIYEOK-I-RIEULMIEUM 85ED B087 # HANGUL SYLLABLE SSANGKIYEOK-I-RIEULPIEUP 85EE B088 # HANGUL SYLLABLE SSANGKIYEOK-I-RIEULSIOS 85EF B089 # HANGUL SYLLABLE SSANGKIYEOK-I-RIEULTHIEUTH 85F0 B08A # HANGUL SYLLABLE SSANGKIYEOK-I-RIEULPHIEUPH 85F1 B08B # HANGUL SYLLABLE SSANGKIYEOK-I-RIEULHIEUH 85F2 B08E # HANGUL SYLLABLE SSANGKIYEOK-I-PIEUPSIOS 85F3 B090 # HANGUL SYLLABLE SSANGKIYEOK-I-SSANGSIOS 85F4 B092 # HANGUL SYLLABLE SSANGKIYEOK-I-CIEUC 85F5 B093 # HANGUL SYLLABLE SSANGKIYEOK-I-CHIEUCH 85F6 B094 # HANGUL SYLLABLE SSANGKIYEOK-I-KHIEUKH 85F7 B095 # HANGUL SYLLABLE SSANGKIYEOK-I-THIEUTH 85F8 B096 # HANGUL SYLLABLE SSANGKIYEOK-I-PHIEUPH 85F9 B097 # HANGUL SYLLABLE SSANGKIYEOK-I-HIEUH 85FA B09B # HANGUL SYLLABLE NIEUN-A-KIYEOKSIOS 85FB B09D # HANGUL SYLLABLE NIEUN-A-NIEUNCIEUC 85FC B09E # HANGUL SYLLABLE NIEUN-A-NIEUNHIEUH 85FD B0A3 # HANGUL SYLLABLE NIEUN-A-RIEULPIEUP 85FE B0A4 # HANGUL SYLLABLE NIEUN-A-RIEULSIOS 8641 B0A5 # HANGUL SYLLABLE NIEUN-A-RIEULTHIEUTH 8642 B0A6 # HANGUL SYLLABLE NIEUN-A-RIEULPHIEUPH 8643 B0A7 # HANGUL SYLLABLE NIEUN-A-RIEULHIEUH 8644 B0AA # HANGUL SYLLABLE NIEUN-A-PIEUPSIOS 8645 B0B0 # HANGUL SYLLABLE NIEUN-A-KHIEUKH 8646 B0B2 # HANGUL SYLLABLE NIEUN-A-PHIEUPH 8647 B0B6 # HANGUL SYLLABLE NIEUN-AE-SSANGKIYEOK 8648 B0B7 # HANGUL SYLLABLE NIEUN-AE-KIYEOKSIOS 8649 B0B9 # HANGUL SYLLABLE NIEUN-AE-NIEUNCIEUC 864A B0BA # HANGUL SYLLABLE NIEUN-AE-NIEUNHIEUH 864B B0BB # HANGUL SYLLABLE NIEUN-AE-TIKEUT 864C B0BD # HANGUL SYLLABLE NIEUN-AE-RIEULKIYEOK 864D B0BE # HANGUL SYLLABLE NIEUN-AE-RIEULMIEUM 864E B0BF # HANGUL SYLLABLE NIEUN-AE-RIEULPIEUP 864F B0C0 # HANGUL SYLLABLE NIEUN-AE-RIEULSIOS 8650 B0C1 # HANGUL SYLLABLE NIEUN-AE-RIEULTHIEUTH 8651 B0C2 # HANGUL SYLLABLE NIEUN-AE-RIEULPHIEUPH 8652 B0C3 # HANGUL SYLLABLE NIEUN-AE-RIEULHIEUH 8653 B0C6 # HANGUL SYLLABLE NIEUN-AE-PIEUPSIOS 8654 B0CA # HANGUL SYLLABLE NIEUN-AE-CIEUC 8655 B0CB # HANGUL SYLLABLE NIEUN-AE-CHIEUCH 8656 B0CC # HANGUL SYLLABLE NIEUN-AE-KHIEUKH 8657 B0CD # HANGUL SYLLABLE NIEUN-AE-THIEUTH 8658 B0CE # HANGUL SYLLABLE NIEUN-AE-PHIEUPH 8659 B0CF # HANGUL SYLLABLE NIEUN-AE-HIEUH 865A B0D2 # HANGUL SYLLABLE NIEUN-YA-SSANGKIYEOK 8661 B0D3 # HANGUL SYLLABLE NIEUN-YA-KIYEOKSIOS 8662 B0D5 # HANGUL SYLLABLE NIEUN-YA-NIEUNCIEUC 8663 B0D6 # HANGUL SYLLABLE NIEUN-YA-NIEUNHIEUH 8664 B0D7 # HANGUL SYLLABLE NIEUN-YA-TIKEUT 8665 B0D9 # HANGUL SYLLABLE NIEUN-YA-RIEULKIYEOK 8666 B0DA # HANGUL SYLLABLE NIEUN-YA-RIEULMIEUM 8667 B0DB # HANGUL SYLLABLE NIEUN-YA-RIEULPIEUP 8668 B0DC # HANGUL SYLLABLE NIEUN-YA-RIEULSIOS 8669 B0DD # HANGUL SYLLABLE NIEUN-YA-RIEULTHIEUTH 866A B0DE # HANGUL SYLLABLE NIEUN-YA-RIEULPHIEUPH 866B B0DF # HANGUL SYLLABLE NIEUN-YA-RIEULHIEUH 866C B0E1 # HANGUL SYLLABLE NIEUN-YA-PIEUP 866D B0E2 # HANGUL SYLLABLE NIEUN-YA-PIEUPSIOS 866E B0E3 # HANGUL SYLLABLE NIEUN-YA-SIOS 866F B0E4 # HANGUL SYLLABLE NIEUN-YA-SSANGSIOS 8670 B0E6 # HANGUL SYLLABLE NIEUN-YA-CIEUC 8671 B0E7 # HANGUL SYLLABLE NIEUN-YA-CHIEUCH 8672 B0E8 # HANGUL SYLLABLE NIEUN-YA-KHIEUKH 8673 B0E9 # HANGUL SYLLABLE NIEUN-YA-THIEUTH 8674 B0EA # HANGUL SYLLABLE NIEUN-YA-PHIEUPH 8675 B0EB # HANGUL SYLLABLE NIEUN-YA-HIEUH 8676 B0EC # HANGUL SYLLABLE NIEUN-YAE 8677 B0ED # HANGUL SYLLABLE NIEUN-YAE-KIYEOK 8678 B0EE # HANGUL SYLLABLE NIEUN-YAE-SSANGKIYEOK 8679 B0EF # HANGUL SYLLABLE NIEUN-YAE-KIYEOKSIOS 867A B0F0 # HANGUL SYLLABLE NIEUN-YAE-NIEUN 8681 B0F1 # HANGUL SYLLABLE NIEUN-YAE-NIEUNCIEUC 8682 B0F2 # HANGUL SYLLABLE NIEUN-YAE-NIEUNHIEUH 8683 B0F3 # HANGUL SYLLABLE NIEUN-YAE-TIKEUT 8684 B0F4 # HANGUL SYLLABLE NIEUN-YAE-RIEUL 8685 B0F5 # HANGUL SYLLABLE NIEUN-YAE-RIEULKIYEOK 8686 B0F6 # HANGUL SYLLABLE NIEUN-YAE-RIEULMIEUM 8687 B0F7 # HANGUL SYLLABLE NIEUN-YAE-RIEULPIEUP 8688 B0F8 # HANGUL SYLLABLE NIEUN-YAE-RIEULSIOS 8689 B0F9 # HANGUL SYLLABLE NIEUN-YAE-RIEULTHIEUTH 868A B0FA # HANGUL SYLLABLE NIEUN-YAE-RIEULPHIEUPH 868B B0FB # HANGUL SYLLABLE NIEUN-YAE-RIEULHIEUH 868C B0FC # HANGUL SYLLABLE NIEUN-YAE-MIEUM 868D B0FD # HANGUL SYLLABLE NIEUN-YAE-PIEUP 868E B0FE # HANGUL SYLLABLE NIEUN-YAE-PIEUPSIOS 868F B0FF # HANGUL SYLLABLE NIEUN-YAE-SIOS 8690 B100 # HANGUL SYLLABLE NIEUN-YAE-SSANGSIOS 8691 B101 # HANGUL SYLLABLE NIEUN-YAE-IEUNG 8692 B102 # HANGUL SYLLABLE NIEUN-YAE-CIEUC 8693 B103 # HANGUL SYLLABLE NIEUN-YAE-CHIEUCH 8694 B104 # HANGUL SYLLABLE NIEUN-YAE-KHIEUKH 8695 B105 # HANGUL SYLLABLE NIEUN-YAE-THIEUTH 8696 B106 # HANGUL SYLLABLE NIEUN-YAE-PHIEUPH 8697 B107 # HANGUL SYLLABLE NIEUN-YAE-HIEUH 8698 B10A # HANGUL SYLLABLE NIEUN-EO-SSANGKIYEOK 8699 B10D # HANGUL SYLLABLE NIEUN-EO-NIEUNCIEUC 869A B10E # HANGUL SYLLABLE NIEUN-EO-NIEUNHIEUH 869B B10F # HANGUL SYLLABLE NIEUN-EO-TIKEUT 869C B111 # HANGUL SYLLABLE NIEUN-EO-RIEULKIYEOK 869D B114 # HANGUL SYLLABLE NIEUN-EO-RIEULSIOS 869E B115 # HANGUL SYLLABLE NIEUN-EO-RIEULTHIEUTH 869F B116 # HANGUL SYLLABLE NIEUN-EO-RIEULPHIEUPH 86A0 B117 # HANGUL SYLLABLE NIEUN-EO-RIEULHIEUH 86A1 B11A # HANGUL SYLLABLE NIEUN-EO-PIEUPSIOS 86A2 B11E # HANGUL SYLLABLE NIEUN-EO-CIEUC 86A3 B11F # HANGUL SYLLABLE NIEUN-EO-CHIEUCH 86A4 B120 # HANGUL SYLLABLE NIEUN-EO-KHIEUKH 86A5 B121 # HANGUL SYLLABLE NIEUN-EO-THIEUTH 86A6 B122 # HANGUL SYLLABLE NIEUN-EO-PHIEUPH 86A7 B126 # HANGUL SYLLABLE NIEUN-E-SSANGKIYEOK 86A8 B127 # HANGUL SYLLABLE NIEUN-E-KIYEOKSIOS 86A9 B129 # HANGUL SYLLABLE NIEUN-E-NIEUNCIEUC 86AA B12A # HANGUL SYLLABLE NIEUN-E-NIEUNHIEUH 86AB B12B # HANGUL SYLLABLE NIEUN-E-TIKEUT 86AC B12D # HANGUL SYLLABLE NIEUN-E-RIEULKIYEOK 86AD B12E # HANGUL SYLLABLE NIEUN-E-RIEULMIEUM 86AE B12F # HANGUL SYLLABLE NIEUN-E-RIEULPIEUP 86AF B130 # HANGUL SYLLABLE NIEUN-E-RIEULSIOS 86B0 B131 # HANGUL SYLLABLE NIEUN-E-RIEULTHIEUTH 86B1 B132 # HANGUL SYLLABLE NIEUN-E-RIEULPHIEUPH 86B2 B133 # HANGUL SYLLABLE NIEUN-E-RIEULHIEUH 86B3 B136 # HANGUL SYLLABLE NIEUN-E-PIEUPSIOS 86B4 B13A # HANGUL SYLLABLE NIEUN-E-CIEUC 86B5 B13B # HANGUL SYLLABLE NIEUN-E-CHIEUCH 86B6 B13C # HANGUL SYLLABLE NIEUN-E-KHIEUKH 86B7 B13D # HANGUL SYLLABLE NIEUN-E-THIEUTH 86B8 B13E # HANGUL SYLLABLE NIEUN-E-PHIEUPH 86B9 B13F # HANGUL SYLLABLE NIEUN-E-HIEUH 86BA B142 # HANGUL SYLLABLE NIEUN-YEO-SSANGKIYEOK 86BB B143 # HANGUL SYLLABLE NIEUN-YEO-KIYEOKSIOS 86BC B145 # HANGUL SYLLABLE NIEUN-YEO-NIEUNCIEUC 86BD B146 # HANGUL SYLLABLE NIEUN-YEO-NIEUNHIEUH 86BE B147 # HANGUL SYLLABLE NIEUN-YEO-TIKEUT 86BF B149 # HANGUL SYLLABLE NIEUN-YEO-RIEULKIYEOK 86C0 B14A # HANGUL SYLLABLE NIEUN-YEO-RIEULMIEUM 86C1 B14B # HANGUL SYLLABLE NIEUN-YEO-RIEULPIEUP 86C2 B14C # HANGUL SYLLABLE NIEUN-YEO-RIEULSIOS 86C3 B14D # HANGUL SYLLABLE NIEUN-YEO-RIEULTHIEUTH 86C4 B14E # HANGUL SYLLABLE NIEUN-YEO-RIEULPHIEUPH 86C5 B14F # HANGUL SYLLABLE NIEUN-YEO-RIEULHIEUH 86C6 B152 # HANGUL SYLLABLE NIEUN-YEO-PIEUPSIOS 86C7 B153 # HANGUL SYLLABLE NIEUN-YEO-SIOS 86C8 B156 # HANGUL SYLLABLE NIEUN-YEO-CIEUC 86C9 B157 # HANGUL SYLLABLE NIEUN-YEO-CHIEUCH 86CA B159 # HANGUL SYLLABLE NIEUN-YEO-THIEUTH 86CB B15A # HANGUL SYLLABLE NIEUN-YEO-PHIEUPH 86CC B15B # HANGUL SYLLABLE NIEUN-YEO-HIEUH 86CD B15D # HANGUL SYLLABLE NIEUN-YE-KIYEOK 86CE B15E # HANGUL SYLLABLE NIEUN-YE-SSANGKIYEOK 86CF B15F # HANGUL SYLLABLE NIEUN-YE-KIYEOKSIOS 86D0 B161 # HANGUL SYLLABLE NIEUN-YE-NIEUNCIEUC 86D1 B162 # HANGUL SYLLABLE NIEUN-YE-NIEUNHIEUH 86D2 B163 # HANGUL SYLLABLE NIEUN-YE-TIKEUT 86D3 B164 # HANGUL SYLLABLE NIEUN-YE-RIEUL 86D4 B165 # HANGUL SYLLABLE NIEUN-YE-RIEULKIYEOK 86D5 B166 # HANGUL SYLLABLE NIEUN-YE-RIEULMIEUM 86D6 B167 # HANGUL SYLLABLE NIEUN-YE-RIEULPIEUP 86D7 B168 # HANGUL SYLLABLE NIEUN-YE-RIEULSIOS 86D8 B169 # HANGUL SYLLABLE NIEUN-YE-RIEULTHIEUTH 86D9 B16A # HANGUL SYLLABLE NIEUN-YE-RIEULPHIEUPH 86DA B16B # HANGUL SYLLABLE NIEUN-YE-RIEULHIEUH 86DB B16C # HANGUL SYLLABLE NIEUN-YE-MIEUM 86DC B16D # HANGUL SYLLABLE NIEUN-YE-PIEUP 86DD B16E # HANGUL SYLLABLE NIEUN-YE-PIEUPSIOS 86DE B16F # HANGUL SYLLABLE NIEUN-YE-SIOS 86DF B170 # HANGUL SYLLABLE NIEUN-YE-SSANGSIOS 86E0 B171 # HANGUL SYLLABLE NIEUN-YE-IEUNG 86E1 B172 # HANGUL SYLLABLE NIEUN-YE-CIEUC 86E2 B173 # HANGUL SYLLABLE NIEUN-YE-CHIEUCH 86E3 B174 # HANGUL SYLLABLE NIEUN-YE-KHIEUKH 86E4 B175 # HANGUL SYLLABLE NIEUN-YE-THIEUTH 86E5 B176 # HANGUL SYLLABLE NIEUN-YE-PHIEUPH 86E6 B177 # HANGUL SYLLABLE NIEUN-YE-HIEUH 86E7 B17A # HANGUL SYLLABLE NIEUN-O-SSANGKIYEOK 86E8 B17B # HANGUL SYLLABLE NIEUN-O-KIYEOKSIOS 86E9 B17D # HANGUL SYLLABLE NIEUN-O-NIEUNCIEUC 86EA B17E # HANGUL SYLLABLE NIEUN-O-NIEUNHIEUH 86EB B17F # HANGUL SYLLABLE NIEUN-O-TIKEUT 86EC B181 # HANGUL SYLLABLE NIEUN-O-RIEULKIYEOK 86ED B183 # HANGUL SYLLABLE NIEUN-O-RIEULPIEUP 86EE B184 # HANGUL SYLLABLE NIEUN-O-RIEULSIOS 86EF B185 # HANGUL SYLLABLE NIEUN-O-RIEULTHIEUTH 86F0 B186 # HANGUL SYLLABLE NIEUN-O-RIEULPHIEUPH 86F1 B187 # HANGUL SYLLABLE NIEUN-O-RIEULHIEUH 86F2 B18A # HANGUL SYLLABLE NIEUN-O-PIEUPSIOS 86F3 B18C # HANGUL SYLLABLE NIEUN-O-SSANGSIOS 86F4 B18E # HANGUL SYLLABLE NIEUN-O-CIEUC 86F5 B18F # HANGUL SYLLABLE NIEUN-O-CHIEUCH 86F6 B190 # HANGUL SYLLABLE NIEUN-O-KHIEUKH 86F7 B191 # HANGUL SYLLABLE NIEUN-O-THIEUTH 86F8 B195 # HANGUL SYLLABLE NIEUN-WA-KIYEOK 86F9 B196 # HANGUL SYLLABLE NIEUN-WA-SSANGKIYEOK 86FA B197 # HANGUL SYLLABLE NIEUN-WA-KIYEOKSIOS 86FB B199 # HANGUL SYLLABLE NIEUN-WA-NIEUNCIEUC 86FC B19A # HANGUL SYLLABLE NIEUN-WA-NIEUNHIEUH 86FD B19B # HANGUL SYLLABLE NIEUN-WA-TIKEUT 86FE B19D # HANGUL SYLLABLE NIEUN-WA-RIEULKIYEOK 8741 B19E # HANGUL SYLLABLE NIEUN-WA-RIEULMIEUM 8742 B19F # HANGUL SYLLABLE NIEUN-WA-RIEULPIEUP 8743 B1A0 # HANGUL SYLLABLE NIEUN-WA-RIEULSIOS 8744 B1A1 # HANGUL SYLLABLE NIEUN-WA-RIEULTHIEUTH 8745 B1A2 # HANGUL SYLLABLE NIEUN-WA-RIEULPHIEUPH 8746 B1A3 # HANGUL SYLLABLE NIEUN-WA-RIEULHIEUH 8747 B1A4 # HANGUL SYLLABLE NIEUN-WA-MIEUM 8748 B1A5 # HANGUL SYLLABLE NIEUN-WA-PIEUP 8749 B1A6 # HANGUL SYLLABLE NIEUN-WA-PIEUPSIOS 874A B1A7 # HANGUL SYLLABLE NIEUN-WA-SIOS 874B B1A9 # HANGUL SYLLABLE NIEUN-WA-IEUNG 874C B1AA # HANGUL SYLLABLE NIEUN-WA-CIEUC 874D B1AB # HANGUL SYLLABLE NIEUN-WA-CHIEUCH 874E B1AC # HANGUL SYLLABLE NIEUN-WA-KHIEUKH 874F B1AD # HANGUL SYLLABLE NIEUN-WA-THIEUTH 8750 B1AE # HANGUL SYLLABLE NIEUN-WA-PHIEUPH 8751 B1AF # HANGUL SYLLABLE NIEUN-WA-HIEUH 8752 B1B0 # HANGUL SYLLABLE NIEUN-WAE 8753 B1B1 # HANGUL SYLLABLE NIEUN-WAE-KIYEOK 8754 B1B2 # HANGUL SYLLABLE NIEUN-WAE-SSANGKIYEOK 8755 B1B3 # HANGUL SYLLABLE NIEUN-WAE-KIYEOKSIOS 8756 B1B4 # HANGUL SYLLABLE NIEUN-WAE-NIEUN 8757 B1B5 # HANGUL SYLLABLE NIEUN-WAE-NIEUNCIEUC 8758 B1B6 # HANGUL SYLLABLE NIEUN-WAE-NIEUNHIEUH 8759 B1B7 # HANGUL SYLLABLE NIEUN-WAE-TIKEUT 875A B1B8 # HANGUL SYLLABLE NIEUN-WAE-RIEUL 8761 B1B9 # HANGUL SYLLABLE NIEUN-WAE-RIEULKIYEOK 8762 B1BA # HANGUL SYLLABLE NIEUN-WAE-RIEULMIEUM 8763 B1BB # HANGUL SYLLABLE NIEUN-WAE-RIEULPIEUP 8764 B1BC # HANGUL SYLLABLE NIEUN-WAE-RIEULSIOS 8765 B1BD # HANGUL SYLLABLE NIEUN-WAE-RIEULTHIEUTH 8766 B1BE # HANGUL SYLLABLE NIEUN-WAE-RIEULPHIEUPH 8767 B1BF # HANGUL SYLLABLE NIEUN-WAE-RIEULHIEUH 8768 B1C0 # HANGUL SYLLABLE NIEUN-WAE-MIEUM 8769 B1C1 # HANGUL SYLLABLE NIEUN-WAE-PIEUP 876A B1C2 # HANGUL SYLLABLE NIEUN-WAE-PIEUPSIOS 876B B1C3 # HANGUL SYLLABLE NIEUN-WAE-SIOS 876C B1C4 # HANGUL SYLLABLE NIEUN-WAE-SSANGSIOS 876D B1C5 # HANGUL SYLLABLE NIEUN-WAE-IEUNG 876E B1C6 # HANGUL SYLLABLE NIEUN-WAE-CIEUC 876F B1C7 # HANGUL SYLLABLE NIEUN-WAE-CHIEUCH 8770 B1C8 # HANGUL SYLLABLE NIEUN-WAE-KHIEUKH 8771 B1C9 # HANGUL SYLLABLE NIEUN-WAE-THIEUTH 8772 B1CA # HANGUL SYLLABLE NIEUN-WAE-PHIEUPH 8773 B1CB # HANGUL SYLLABLE NIEUN-WAE-HIEUH 8774 B1CD # HANGUL SYLLABLE NIEUN-OE-KIYEOK 8775 B1CE # HANGUL SYLLABLE NIEUN-OE-SSANGKIYEOK 8776 B1CF # HANGUL SYLLABLE NIEUN-OE-KIYEOKSIOS 8777 B1D1 # HANGUL SYLLABLE NIEUN-OE-NIEUNCIEUC 8778 B1D2 # HANGUL SYLLABLE NIEUN-OE-NIEUNHIEUH 8779 B1D3 # HANGUL SYLLABLE NIEUN-OE-TIKEUT 877A B1D5 # HANGUL SYLLABLE NIEUN-OE-RIEULKIYEOK 8781 B1D6 # HANGUL SYLLABLE NIEUN-OE-RIEULMIEUM 8782 B1D7 # HANGUL SYLLABLE NIEUN-OE-RIEULPIEUP 8783 B1D8 # HANGUL SYLLABLE NIEUN-OE-RIEULSIOS 8784 B1D9 # HANGUL SYLLABLE NIEUN-OE-RIEULTHIEUTH 8785 B1DA # HANGUL SYLLABLE NIEUN-OE-RIEULPHIEUPH 8786 B1DB # HANGUL SYLLABLE NIEUN-OE-RIEULHIEUH 8787 B1DE # HANGUL SYLLABLE NIEUN-OE-PIEUPSIOS 8788 B1E0 # HANGUL SYLLABLE NIEUN-OE-SSANGSIOS 8789 B1E1 # HANGUL SYLLABLE NIEUN-OE-IEUNG 878A B1E2 # HANGUL SYLLABLE NIEUN-OE-CIEUC 878B B1E3 # HANGUL SYLLABLE NIEUN-OE-CHIEUCH 878C B1E4 # HANGUL SYLLABLE NIEUN-OE-KHIEUKH 878D B1E5 # HANGUL SYLLABLE NIEUN-OE-THIEUTH 878E B1E6 # HANGUL SYLLABLE NIEUN-OE-PHIEUPH 878F B1E7 # HANGUL SYLLABLE NIEUN-OE-HIEUH 8790 B1EA # HANGUL SYLLABLE NIEUN-YO-SSANGKIYEOK 8791 B1EB # HANGUL SYLLABLE NIEUN-YO-KIYEOKSIOS 8792 B1ED # HANGUL SYLLABLE NIEUN-YO-NIEUNCIEUC 8793 B1EE # HANGUL SYLLABLE NIEUN-YO-NIEUNHIEUH 8794 B1EF # HANGUL SYLLABLE NIEUN-YO-TIKEUT 8795 B1F1 # HANGUL SYLLABLE NIEUN-YO-RIEULKIYEOK 8796 B1F2 # HANGUL SYLLABLE NIEUN-YO-RIEULMIEUM 8797 B1F3 # HANGUL SYLLABLE NIEUN-YO-RIEULPIEUP 8798 B1F4 # HANGUL SYLLABLE NIEUN-YO-RIEULSIOS 8799 B1F5 # HANGUL SYLLABLE NIEUN-YO-RIEULTHIEUTH 879A B1F6 # HANGUL SYLLABLE NIEUN-YO-RIEULPHIEUPH 879B B1F7 # HANGUL SYLLABLE NIEUN-YO-RIEULHIEUH 879C B1F8 # HANGUL SYLLABLE NIEUN-YO-MIEUM 879D B1FA # HANGUL SYLLABLE NIEUN-YO-PIEUPSIOS 879E B1FC # HANGUL SYLLABLE NIEUN-YO-SSANGSIOS 879F B1FE # HANGUL SYLLABLE NIEUN-YO-CIEUC 87A0 B1FF # HANGUL SYLLABLE NIEUN-YO-CHIEUCH 87A1 B200 # HANGUL SYLLABLE NIEUN-YO-KHIEUKH 87A2 B201 # HANGUL SYLLABLE NIEUN-YO-THIEUTH 87A3 B202 # HANGUL SYLLABLE NIEUN-YO-PHIEUPH 87A4 B203 # HANGUL SYLLABLE NIEUN-YO-HIEUH 87A5 B206 # HANGUL SYLLABLE NIEUN-U-SSANGKIYEOK 87A6 B207 # HANGUL SYLLABLE NIEUN-U-KIYEOKSIOS 87A7 B209 # HANGUL SYLLABLE NIEUN-U-NIEUNCIEUC 87A8 B20A # HANGUL SYLLABLE NIEUN-U-NIEUNHIEUH 87A9 B20D # HANGUL SYLLABLE NIEUN-U-RIEULKIYEOK 87AA B20E # HANGUL SYLLABLE NIEUN-U-RIEULMIEUM 87AB B20F # HANGUL SYLLABLE NIEUN-U-RIEULPIEUP 87AC B210 # HANGUL SYLLABLE NIEUN-U-RIEULSIOS 87AD B211 # HANGUL SYLLABLE NIEUN-U-RIEULTHIEUTH 87AE B212 # HANGUL SYLLABLE NIEUN-U-RIEULPHIEUPH 87AF B213 # HANGUL SYLLABLE NIEUN-U-RIEULHIEUH 87B0 B216 # HANGUL SYLLABLE NIEUN-U-PIEUPSIOS 87B1 B218 # HANGUL SYLLABLE NIEUN-U-SSANGSIOS 87B2 B21A # HANGUL SYLLABLE NIEUN-U-CIEUC 87B3 B21B # HANGUL SYLLABLE NIEUN-U-CHIEUCH 87B4 B21C # HANGUL SYLLABLE NIEUN-U-KHIEUKH 87B5 B21D # HANGUL SYLLABLE NIEUN-U-THIEUTH 87B6 B21E # HANGUL SYLLABLE NIEUN-U-PHIEUPH 87B7 B21F # HANGUL SYLLABLE NIEUN-U-HIEUH 87B8 B221 # HANGUL SYLLABLE NIEUN-WEO-KIYEOK 87B9 B222 # HANGUL SYLLABLE NIEUN-WEO-SSANGKIYEOK 87BA B223 # HANGUL SYLLABLE NIEUN-WEO-KIYEOKSIOS 87BB B224 # HANGUL SYLLABLE NIEUN-WEO-NIEUN 87BC B225 # HANGUL SYLLABLE NIEUN-WEO-NIEUNCIEUC 87BD B226 # HANGUL SYLLABLE NIEUN-WEO-NIEUNHIEUH 87BE B227 # HANGUL SYLLABLE NIEUN-WEO-TIKEUT 87BF B228 # HANGUL SYLLABLE NIEUN-WEO-RIEUL 87C0 B229 # HANGUL SYLLABLE NIEUN-WEO-RIEULKIYEOK 87C1 B22A # HANGUL SYLLABLE NIEUN-WEO-RIEULMIEUM 87C2 B22B # HANGUL SYLLABLE NIEUN-WEO-RIEULPIEUP 87C3 B22C # HANGUL SYLLABLE NIEUN-WEO-RIEULSIOS 87C4 B22D # HANGUL SYLLABLE NIEUN-WEO-RIEULTHIEUTH 87C5 B22E # HANGUL SYLLABLE NIEUN-WEO-RIEULPHIEUPH 87C6 B22F # HANGUL SYLLABLE NIEUN-WEO-RIEULHIEUH 87C7 B230 # HANGUL SYLLABLE NIEUN-WEO-MIEUM 87C8 B231 # HANGUL SYLLABLE NIEUN-WEO-PIEUP 87C9 B232 # HANGUL SYLLABLE NIEUN-WEO-PIEUPSIOS 87CA B233 # HANGUL SYLLABLE NIEUN-WEO-SIOS 87CB B235 # HANGUL SYLLABLE NIEUN-WEO-IEUNG 87CC B236 # HANGUL SYLLABLE NIEUN-WEO-CIEUC 87CD B237 # HANGUL SYLLABLE NIEUN-WEO-CHIEUCH 87CE B238 # HANGUL SYLLABLE NIEUN-WEO-KHIEUKH 87CF B239 # HANGUL SYLLABLE NIEUN-WEO-THIEUTH 87D0 B23A # HANGUL SYLLABLE NIEUN-WEO-PHIEUPH 87D1 B23B # HANGUL SYLLABLE NIEUN-WEO-HIEUH 87D2 B23D # HANGUL SYLLABLE NIEUN-WE-KIYEOK 87D3 B23E # HANGUL SYLLABLE NIEUN-WE-SSANGKIYEOK 87D4 B23F # HANGUL SYLLABLE NIEUN-WE-KIYEOKSIOS 87D5 B240 # HANGUL SYLLABLE NIEUN-WE-NIEUN 87D6 B241 # HANGUL SYLLABLE NIEUN-WE-NIEUNCIEUC 87D7 B242 # HANGUL SYLLABLE NIEUN-WE-NIEUNHIEUH 87D8 B243 # HANGUL SYLLABLE NIEUN-WE-TIKEUT 87D9 B244 # HANGUL SYLLABLE NIEUN-WE-RIEUL 87DA B245 # HANGUL SYLLABLE NIEUN-WE-RIEULKIYEOK 87DB B246 # HANGUL SYLLABLE NIEUN-WE-RIEULMIEUM 87DC B247 # HANGUL SYLLABLE NIEUN-WE-RIEULPIEUP 87DD B248 # HANGUL SYLLABLE NIEUN-WE-RIEULSIOS 87DE B249 # HANGUL SYLLABLE NIEUN-WE-RIEULTHIEUTH 87DF B24A # HANGUL SYLLABLE NIEUN-WE-RIEULPHIEUPH 87E0 B24B # HANGUL SYLLABLE NIEUN-WE-RIEULHIEUH 87E1 B24C # HANGUL SYLLABLE NIEUN-WE-MIEUM 87E2 B24D # HANGUL SYLLABLE NIEUN-WE-PIEUP 87E3 B24E # HANGUL SYLLABLE NIEUN-WE-PIEUPSIOS 87E4 B24F # HANGUL SYLLABLE NIEUN-WE-SIOS 87E5 B250 # HANGUL SYLLABLE NIEUN-WE-SSANGSIOS 87E6 B251 # HANGUL SYLLABLE NIEUN-WE-IEUNG 87E7 B252 # HANGUL SYLLABLE NIEUN-WE-CIEUC 87E8 B253 # HANGUL SYLLABLE NIEUN-WE-CHIEUCH 87E9 B254 # HANGUL SYLLABLE NIEUN-WE-KHIEUKH 87EA B255 # HANGUL SYLLABLE NIEUN-WE-THIEUTH 87EB B256 # HANGUL SYLLABLE NIEUN-WE-PHIEUPH 87EC B257 # HANGUL SYLLABLE NIEUN-WE-HIEUH 87ED B259 # HANGUL SYLLABLE NIEUN-WI-KIYEOK 87EE B25A # HANGUL SYLLABLE NIEUN-WI-SSANGKIYEOK 87EF B25B # HANGUL SYLLABLE NIEUN-WI-KIYEOKSIOS 87F0 B25D # HANGUL SYLLABLE NIEUN-WI-NIEUNCIEUC 87F1 B25E # HANGUL SYLLABLE NIEUN-WI-NIEUNHIEUH 87F2 B25F # HANGUL SYLLABLE NIEUN-WI-TIKEUT 87F3 B261 # HANGUL SYLLABLE NIEUN-WI-RIEULKIYEOK 87F4 B262 # HANGUL SYLLABLE NIEUN-WI-RIEULMIEUM 87F5 B263 # HANGUL SYLLABLE NIEUN-WI-RIEULPIEUP 87F6 B264 # HANGUL SYLLABLE NIEUN-WI-RIEULSIOS 87F7 B265 # HANGUL SYLLABLE NIEUN-WI-RIEULTHIEUTH 87F8 B266 # HANGUL SYLLABLE NIEUN-WI-RIEULPHIEUPH 87F9 B267 # HANGUL SYLLABLE NIEUN-WI-RIEULHIEUH 87FA B26A # HANGUL SYLLABLE NIEUN-WI-PIEUPSIOS 87FB B26B # HANGUL SYLLABLE NIEUN-WI-SIOS 87FC B26C # HANGUL SYLLABLE NIEUN-WI-SSANGSIOS 87FD B26D # HANGUL SYLLABLE NIEUN-WI-IEUNG 87FE B26E # HANGUL SYLLABLE NIEUN-WI-CIEUC 8841 B26F # HANGUL SYLLABLE NIEUN-WI-CHIEUCH 8842 B270 # HANGUL SYLLABLE NIEUN-WI-KHIEUKH 8843 B271 # HANGUL SYLLABLE NIEUN-WI-THIEUTH 8844 B272 # HANGUL SYLLABLE NIEUN-WI-PHIEUPH 8845 B273 # HANGUL SYLLABLE NIEUN-WI-HIEUH 8846 B276 # HANGUL SYLLABLE NIEUN-YU-SSANGKIYEOK 8847 B277 # HANGUL SYLLABLE NIEUN-YU-KIYEOKSIOS 8848 B278 # HANGUL SYLLABLE NIEUN-YU-NIEUN 8849 B279 # HANGUL SYLLABLE NIEUN-YU-NIEUNCIEUC 884A B27A # HANGUL SYLLABLE NIEUN-YU-NIEUNHIEUH 884B B27B # HANGUL SYLLABLE NIEUN-YU-TIKEUT 884C B27D # HANGUL SYLLABLE NIEUN-YU-RIEULKIYEOK 884D B27E # HANGUL SYLLABLE NIEUN-YU-RIEULMIEUM 884E B27F # HANGUL SYLLABLE NIEUN-YU-RIEULPIEUP 884F B280 # HANGUL SYLLABLE NIEUN-YU-RIEULSIOS 8850 B281 # HANGUL SYLLABLE NIEUN-YU-RIEULTHIEUTH 8851 B282 # HANGUL SYLLABLE NIEUN-YU-RIEULPHIEUPH 8852 B283 # HANGUL SYLLABLE NIEUN-YU-RIEULHIEUH 8853 B286 # HANGUL SYLLABLE NIEUN-YU-PIEUPSIOS 8854 B287 # HANGUL SYLLABLE NIEUN-YU-SIOS 8855 B288 # HANGUL SYLLABLE NIEUN-YU-SSANGSIOS 8856 B28A # HANGUL SYLLABLE NIEUN-YU-CIEUC 8857 B28B # HANGUL SYLLABLE NIEUN-YU-CHIEUCH 8858 B28C # HANGUL SYLLABLE NIEUN-YU-KHIEUKH 8859 B28D # HANGUL SYLLABLE NIEUN-YU-THIEUTH 885A B28E # HANGUL SYLLABLE NIEUN-YU-PHIEUPH 8861 B28F # HANGUL SYLLABLE NIEUN-YU-HIEUH 8862 B292 # HANGUL SYLLABLE NIEUN-EU-SSANGKIYEOK 8863 B293 # HANGUL SYLLABLE NIEUN-EU-KIYEOKSIOS 8864 B295 # HANGUL SYLLABLE NIEUN-EU-NIEUNCIEUC 8865 B296 # HANGUL SYLLABLE NIEUN-EU-NIEUNHIEUH 8866 B297 # HANGUL SYLLABLE NIEUN-EU-TIKEUT 8867 B29B # HANGUL SYLLABLE NIEUN-EU-RIEULPIEUP 8868 B29C # HANGUL SYLLABLE NIEUN-EU-RIEULSIOS 8869 B29D # HANGUL SYLLABLE NIEUN-EU-RIEULTHIEUTH 886A B29E # HANGUL SYLLABLE NIEUN-EU-RIEULPHIEUPH 886B B29F # HANGUL SYLLABLE NIEUN-EU-RIEULHIEUH 886C B2A2 # HANGUL SYLLABLE NIEUN-EU-PIEUPSIOS 886D B2A4 # HANGUL SYLLABLE NIEUN-EU-SSANGSIOS 886E B2A7 # HANGUL SYLLABLE NIEUN-EU-CHIEUCH 886F B2A8 # HANGUL SYLLABLE NIEUN-EU-KHIEUKH 8870 B2A9 # HANGUL SYLLABLE NIEUN-EU-THIEUTH 8871 B2AB # HANGUL SYLLABLE NIEUN-EU-HIEUH 8872 B2AD # HANGUL SYLLABLE NIEUN-YI-KIYEOK 8873 B2AE # HANGUL SYLLABLE NIEUN-YI-SSANGKIYEOK 8874 B2AF # HANGUL SYLLABLE NIEUN-YI-KIYEOKSIOS 8875 B2B1 # HANGUL SYLLABLE NIEUN-YI-NIEUNCIEUC 8876 B2B2 # HANGUL SYLLABLE NIEUN-YI-NIEUNHIEUH 8877 B2B3 # HANGUL SYLLABLE NIEUN-YI-TIKEUT 8878 B2B5 # HANGUL SYLLABLE NIEUN-YI-RIEULKIYEOK 8879 B2B6 # HANGUL SYLLABLE NIEUN-YI-RIEULMIEUM 887A B2B7 # HANGUL SYLLABLE NIEUN-YI-RIEULPIEUP 8881 B2B8 # HANGUL SYLLABLE NIEUN-YI-RIEULSIOS 8882 B2B9 # HANGUL SYLLABLE NIEUN-YI-RIEULTHIEUTH 8883 B2BA # HANGUL SYLLABLE NIEUN-YI-RIEULPHIEUPH 8884 B2BB # HANGUL SYLLABLE NIEUN-YI-RIEULHIEUH 8885 B2BC # HANGUL SYLLABLE NIEUN-YI-MIEUM 8886 B2BD # HANGUL SYLLABLE NIEUN-YI-PIEUP 8887 B2BE # HANGUL SYLLABLE NIEUN-YI-PIEUPSIOS 8888 B2BF # HANGUL SYLLABLE NIEUN-YI-SIOS 8889 B2C0 # HANGUL SYLLABLE NIEUN-YI-SSANGSIOS 888A B2C1 # HANGUL SYLLABLE NIEUN-YI-IEUNG 888B B2C2 # HANGUL SYLLABLE NIEUN-YI-CIEUC 888C B2C3 # HANGUL SYLLABLE NIEUN-YI-CHIEUCH 888D B2C4 # HANGUL SYLLABLE NIEUN-YI-KHIEUKH 888E B2C5 # HANGUL SYLLABLE NIEUN-YI-THIEUTH 888F B2C6 # HANGUL SYLLABLE NIEUN-YI-PHIEUPH 8890 B2C7 # HANGUL SYLLABLE NIEUN-YI-HIEUH 8891 B2CA # HANGUL SYLLABLE NIEUN-I-SSANGKIYEOK 8892 B2CB # HANGUL SYLLABLE NIEUN-I-KIYEOKSIOS 8893 B2CD # HANGUL SYLLABLE NIEUN-I-NIEUNCIEUC 8894 B2CE # HANGUL SYLLABLE NIEUN-I-NIEUNHIEUH 8895 B2CF # HANGUL SYLLABLE NIEUN-I-TIKEUT 8896 B2D1 # HANGUL SYLLABLE NIEUN-I-RIEULKIYEOK 8897 B2D3 # HANGUL SYLLABLE NIEUN-I-RIEULPIEUP--<3/22/95> 8898 B2D4 # HANGUL SYLLABLE NIEUN-I-RIEULSIOS---<3/22/95> 8899 B2D5 # HANGUL SYLLABLE NIEUN-I-RIEULTHIEUTH<3/22/95> 889A B2D6 # HANGUL SYLLABLE NIEUN-I-RIEULPHIEUPH<3/22/95> 889B B2D7 # HANGUL SYLLABLE NIEUN-I-RIEULHIEUH 889C B2DA # HANGUL SYLLABLE NIEUN-I-PIEUPSIOS 889D B2DC # HANGUL SYLLABLE NIEUN-I-SSANGSIOS 889E B2DE # HANGUL SYLLABLE NIEUN-I-CIEUC 889F B2DF # HANGUL SYLLABLE NIEUN-I-CHIEUCH 88A0 B2E0 # HANGUL SYLLABLE NIEUN-I-KHIEUKH 88A1 B2E1 # HANGUL SYLLABLE NIEUN-I-THIEUTH 88A2 B2E3 # HANGUL SYLLABLE NIEUN-I-HIEUH 88A3 B2E7 # HANGUL SYLLABLE TIKEUT-A-KIYEOKSIOS 88A4 B2E9 # HANGUL SYLLABLE TIKEUT-A-NIEUNCIEUC 88A5 B2EA # HANGUL SYLLABLE TIKEUT-A-NIEUNHIEUH 88A6 B2F0 # HANGUL SYLLABLE TIKEUT-A-RIEULSIOS 88A7 B2F1 # HANGUL SYLLABLE TIKEUT-A-RIEULTHIEUTH 88A8 B2F2 # HANGUL SYLLABLE TIKEUT-A-RIEULPHIEUPH 88A9 B2F6 # HANGUL SYLLABLE TIKEUT-A-PIEUPSIOS 88AA B2FC # HANGUL SYLLABLE TIKEUT-A-KHIEUKH 88AB B2FD # HANGUL SYLLABLE TIKEUT-A-THIEUTH 88AC B2FE # HANGUL SYLLABLE TIKEUT-A-PHIEUPH 88AD B302 # HANGUL SYLLABLE TIKEUT-AE-SSANGKIYEOK 88AE B303 # HANGUL SYLLABLE TIKEUT-AE-KIYEOKSIOS 88AF B305 # HANGUL SYLLABLE TIKEUT-AE-NIEUNCIEUC 88B0 B306 # HANGUL SYLLABLE TIKEUT-AE-NIEUNHIEUH 88B1 B307 # HANGUL SYLLABLE TIKEUT-AE-TIKEUT 88B2 B309 # HANGUL SYLLABLE TIKEUT-AE-RIEULKIYEOK 88B3 B30A # HANGUL SYLLABLE TIKEUT-AE-RIEULMIEUM 88B4 B30B # HANGUL SYLLABLE TIKEUT-AE-RIEULPIEUP 88B5 B30C # HANGUL SYLLABLE TIKEUT-AE-RIEULSIOS 88B6 B30D # HANGUL SYLLABLE TIKEUT-AE-RIEULTHIEUTH 88B7 B30E # HANGUL SYLLABLE TIKEUT-AE-RIEULPHIEUPH 88B8 B30F # HANGUL SYLLABLE TIKEUT-AE-RIEULHIEUH 88B9 B312 # HANGUL SYLLABLE TIKEUT-AE-PIEUPSIOS 88BA B316 # HANGUL SYLLABLE TIKEUT-AE-CIEUC 88BB B317 # HANGUL SYLLABLE TIKEUT-AE-CHIEUCH 88BC B318 # HANGUL SYLLABLE TIKEUT-AE-KHIEUKH 88BD B319 # HANGUL SYLLABLE TIKEUT-AE-THIEUTH 88BE B31A # HANGUL SYLLABLE TIKEUT-AE-PHIEUPH 88BF B31B # HANGUL SYLLABLE TIKEUT-AE-HIEUH 88C0 B31D # HANGUL SYLLABLE TIKEUT-YA-KIYEOK 88C1 B31E # HANGUL SYLLABLE TIKEUT-YA-SSANGKIYEOK 88C2 B31F # HANGUL SYLLABLE TIKEUT-YA-KIYEOKSIOS 88C3 B320 # HANGUL SYLLABLE TIKEUT-YA-NIEUN 88C4 B321 # HANGUL SYLLABLE TIKEUT-YA-NIEUNCIEUC 88C5 B322 # HANGUL SYLLABLE TIKEUT-YA-NIEUNHIEUH 88C6 B323 # HANGUL SYLLABLE TIKEUT-YA-TIKEUT 88C7 B324 # HANGUL SYLLABLE TIKEUT-YA-RIEUL 88C8 B325 # HANGUL SYLLABLE TIKEUT-YA-RIEULKIYEOK 88C9 B326 # HANGUL SYLLABLE TIKEUT-YA-RIEULMIEUM 88CA B327 # HANGUL SYLLABLE TIKEUT-YA-RIEULPIEUP 88CB B328 # HANGUL SYLLABLE TIKEUT-YA-RIEULSIOS 88CC B329 # HANGUL SYLLABLE TIKEUT-YA-RIEULTHIEUTH 88CD B32A # HANGUL SYLLABLE TIKEUT-YA-RIEULPHIEUPH 88CE B32B # HANGUL SYLLABLE TIKEUT-YA-RIEULHIEUH 88CF B32C # HANGUL SYLLABLE TIKEUT-YA-MIEUM 88D0 B32D # HANGUL SYLLABLE TIKEUT-YA-PIEUP 88D1 B32E # HANGUL SYLLABLE TIKEUT-YA-PIEUPSIOS 88D2 B32F # HANGUL SYLLABLE TIKEUT-YA-SIOS 88D3 B330 # HANGUL SYLLABLE TIKEUT-YA-SSANGSIOS 88D4 B331 # HANGUL SYLLABLE TIKEUT-YA-IEUNG 88D5 B332 # HANGUL SYLLABLE TIKEUT-YA-CIEUC 88D6 B333 # HANGUL SYLLABLE TIKEUT-YA-CHIEUCH 88D7 B334 # HANGUL SYLLABLE TIKEUT-YA-KHIEUKH 88D8 B335 # HANGUL SYLLABLE TIKEUT-YA-THIEUTH 88D9 B336 # HANGUL SYLLABLE TIKEUT-YA-PHIEUPH 88DA B337 # HANGUL SYLLABLE TIKEUT-YA-HIEUH 88DB B338 # HANGUL SYLLABLE TIKEUT-YAE 88DC B339 # HANGUL SYLLABLE TIKEUT-YAE-KIYEOK 88DD B33A # HANGUL SYLLABLE TIKEUT-YAE-SSANGKIYEOK 88DE B33B # HANGUL SYLLABLE TIKEUT-YAE-KIYEOKSIOS 88DF B33C # HANGUL SYLLABLE TIKEUT-YAE-NIEUN 88E0 B33D # HANGUL SYLLABLE TIKEUT-YAE-NIEUNCIEUC 88E1 B33E # HANGUL SYLLABLE TIKEUT-YAE-NIEUNHIEUH 88E2 B33F # HANGUL SYLLABLE TIKEUT-YAE-TIKEUT 88E3 B340 # HANGUL SYLLABLE TIKEUT-YAE-RIEUL 88E4 B341 # HANGUL SYLLABLE TIKEUT-YAE-RIEULKIYEOK 88E5 B342 # HANGUL SYLLABLE TIKEUT-YAE-RIEULMIEUM 88E6 B343 # HANGUL SYLLABLE TIKEUT-YAE-RIEULPIEUP 88E7 B344 # HANGUL SYLLABLE TIKEUT-YAE-RIEULSIOS 88E8 B345 # HANGUL SYLLABLE TIKEUT-YAE-RIEULTHIEUTH 88E9 B346 # HANGUL SYLLABLE TIKEUT-YAE-RIEULPHIEUPH 88EA B347 # HANGUL SYLLABLE TIKEUT-YAE-RIEULHIEUH 88EB B348 # HANGUL SYLLABLE TIKEUT-YAE-MIEUM 88EC B349 # HANGUL SYLLABLE TIKEUT-YAE-PIEUP 88ED B34A # HANGUL SYLLABLE TIKEUT-YAE-PIEUPSIOS 88EE B34B # HANGUL SYLLABLE TIKEUT-YAE-SIOS 88EF B34C # HANGUL SYLLABLE TIKEUT-YAE-SSANGSIOS 88F0 B34D # HANGUL SYLLABLE TIKEUT-YAE-IEUNG 88F1 B34E # HANGUL SYLLABLE TIKEUT-YAE-CIEUC 88F2 B34F # HANGUL SYLLABLE TIKEUT-YAE-CHIEUCH 88F3 B350 # HANGUL SYLLABLE TIKEUT-YAE-KHIEUKH 88F4 B351 # HANGUL SYLLABLE TIKEUT-YAE-THIEUTH 88F5 B352 # HANGUL SYLLABLE TIKEUT-YAE-PHIEUPH 88F6 B353 # HANGUL SYLLABLE TIKEUT-YAE-HIEUH 88F7 B357 # HANGUL SYLLABLE TIKEUT-EO-KIYEOKSIOS 88F8 B359 # HANGUL SYLLABLE TIKEUT-EO-NIEUNCIEUC 88F9 B35A # HANGUL SYLLABLE TIKEUT-EO-NIEUNHIEUH 88FA B35D # HANGUL SYLLABLE TIKEUT-EO-RIEULKIYEOK 88FB B360 # HANGUL SYLLABLE TIKEUT-EO-RIEULSIOS 88FC B361 # HANGUL SYLLABLE TIKEUT-EO-RIEULTHIEUTH 88FD B362 # HANGUL SYLLABLE TIKEUT-EO-RIEULPHIEUPH 88FE B363 # HANGUL SYLLABLE TIKEUT-EO-RIEULHIEUH 8941 B366 # HANGUL SYLLABLE TIKEUT-EO-PIEUPSIOS 8942 B368 # HANGUL SYLLABLE TIKEUT-EO-SSANGSIOS 8943 B36A # HANGUL SYLLABLE TIKEUT-EO-CIEUC 8944 B36C # HANGUL SYLLABLE TIKEUT-EO-KHIEUKH 8945 B36D # HANGUL SYLLABLE TIKEUT-EO-THIEUTH 8946 B36F # HANGUL SYLLABLE TIKEUT-EO-HIEUH 8947 B372 # HANGUL SYLLABLE TIKEUT-E-SSANGKIYEOK 8948 B373 # HANGUL SYLLABLE TIKEUT-E-KIYEOKSIOS 8949 B375 # HANGUL SYLLABLE TIKEUT-E-NIEUNCIEUC 894A B376 # HANGUL SYLLABLE TIKEUT-E-NIEUNHIEUH 894B B377 # HANGUL SYLLABLE TIKEUT-E-TIKEUT 894C B379 # HANGUL SYLLABLE TIKEUT-E-RIEULKIYEOK 894D B37A # HANGUL SYLLABLE TIKEUT-E-RIEULMIEUM 894E B37B # HANGUL SYLLABLE TIKEUT-E-RIEULPIEUP 894F B37C # HANGUL SYLLABLE TIKEUT-E-RIEULSIOS 8950 B37D # HANGUL SYLLABLE TIKEUT-E-RIEULTHIEUTH 8951 B37E # HANGUL SYLLABLE TIKEUT-E-RIEULPHIEUPH 8952 B37F # HANGUL SYLLABLE TIKEUT-E-RIEULHIEUH 8953 B382 # HANGUL SYLLABLE TIKEUT-E-PIEUPSIOS 8954 B386 # HANGUL SYLLABLE TIKEUT-E-CIEUC 8955 B387 # HANGUL SYLLABLE TIKEUT-E-CHIEUCH 8956 B388 # HANGUL SYLLABLE TIKEUT-E-KHIEUKH 8957 B389 # HANGUL SYLLABLE TIKEUT-E-THIEUTH 8958 B38A # HANGUL SYLLABLE TIKEUT-E-PHIEUPH 8959 B38B # HANGUL SYLLABLE TIKEUT-E-HIEUH 895A B38D # HANGUL SYLLABLE TIKEUT-YEO-KIYEOK 8961 B38E # HANGUL SYLLABLE TIKEUT-YEO-SSANGKIYEOK 8962 B38F # HANGUL SYLLABLE TIKEUT-YEO-KIYEOKSIOS 8963 B391 # HANGUL SYLLABLE TIKEUT-YEO-NIEUNCIEUC 8964 B392 # HANGUL SYLLABLE TIKEUT-YEO-NIEUNHIEUH 8965 B393 # HANGUL SYLLABLE TIKEUT-YEO-TIKEUT 8966 B395 # HANGUL SYLLABLE TIKEUT-YEO-RIEULKIYEOK 8967 B396 # HANGUL SYLLABLE TIKEUT-YEO-RIEULMIEUM 8968 B397 # HANGUL SYLLABLE TIKEUT-YEO-RIEULPIEUP 8969 B398 # HANGUL SYLLABLE TIKEUT-YEO-RIEULSIOS 896A B399 # HANGUL SYLLABLE TIKEUT-YEO-RIEULTHIEUTH 896B B39A # HANGUL SYLLABLE TIKEUT-YEO-RIEULPHIEUPH 896C B39B # HANGUL SYLLABLE TIKEUT-YEO-RIEULHIEUH 896D B39C # HANGUL SYLLABLE TIKEUT-YEO-MIEUM 896E B39D # HANGUL SYLLABLE TIKEUT-YEO-PIEUP 896F B39E # HANGUL SYLLABLE TIKEUT-YEO-PIEUPSIOS 8970 B39F # HANGUL SYLLABLE TIKEUT-YEO-SIOS 8971 B3A2 # HANGUL SYLLABLE TIKEUT-YEO-CIEUC 8972 B3A3 # HANGUL SYLLABLE TIKEUT-YEO-CHIEUCH 8973 B3A4 # HANGUL SYLLABLE TIKEUT-YEO-KHIEUKH 8974 B3A5 # HANGUL SYLLABLE TIKEUT-YEO-THIEUTH 8975 B3A6 # HANGUL SYLLABLE TIKEUT-YEO-PHIEUPH 8976 B3A7 # HANGUL SYLLABLE TIKEUT-YEO-HIEUH 8977 B3A9 # HANGUL SYLLABLE TIKEUT-YE-KIYEOK 8978 B3AA # HANGUL SYLLABLE TIKEUT-YE-SSANGKIYEOK 8979 B3AB # HANGUL SYLLABLE TIKEUT-YE-KIYEOKSIOS 897A B3AD # HANGUL SYLLABLE TIKEUT-YE-NIEUNCIEUC 8981 B3AE # HANGUL SYLLABLE TIKEUT-YE-NIEUNHIEUH 8982 B3AF # HANGUL SYLLABLE TIKEUT-YE-TIKEUT 8983 B3B0 # HANGUL SYLLABLE TIKEUT-YE-RIEUL 8984 B3B1 # HANGUL SYLLABLE TIKEUT-YE-RIEULKIYEOK 8985 B3B2 # HANGUL SYLLABLE TIKEUT-YE-RIEULMIEUM 8986 B3B3 # HANGUL SYLLABLE TIKEUT-YE-RIEULPIEUP 8987 B3B4 # HANGUL SYLLABLE TIKEUT-YE-RIEULSIOS 8988 B3B5 # HANGUL SYLLABLE TIKEUT-YE-RIEULTHIEUTH 8989 B3B6 # HANGUL SYLLABLE TIKEUT-YE-RIEULPHIEUPH 898A B3B7 # HANGUL SYLLABLE TIKEUT-YE-RIEULHIEUH 898B B3B8 # HANGUL SYLLABLE TIKEUT-YE-MIEUM 898C B3B9 # HANGUL SYLLABLE TIKEUT-YE-PIEUP 898D B3BA # HANGUL SYLLABLE TIKEUT-YE-PIEUPSIOS 898E B3BB # HANGUL SYLLABLE TIKEUT-YE-SIOS 898F B3BC # HANGUL SYLLABLE TIKEUT-YE-SSANGSIOS 8990 B3BD # HANGUL SYLLABLE TIKEUT-YE-IEUNG 8991 B3BE # HANGUL SYLLABLE TIKEUT-YE-CIEUC 8992 B3BF # HANGUL SYLLABLE TIKEUT-YE-CHIEUCH 8993 B3C0 # HANGUL SYLLABLE TIKEUT-YE-KHIEUKH 8994 B3C1 # HANGUL SYLLABLE TIKEUT-YE-THIEUTH 8995 B3C2 # HANGUL SYLLABLE TIKEUT-YE-PHIEUPH 8996 B3C3 # HANGUL SYLLABLE TIKEUT-YE-HIEUH 8997 B3C6 # HANGUL SYLLABLE TIKEUT-O-SSANGKIYEOK 8998 B3C7 # HANGUL SYLLABLE TIKEUT-O-KIYEOKSIOS 8999 B3C9 # HANGUL SYLLABLE TIKEUT-O-NIEUNCIEUC 899A B3CA # HANGUL SYLLABLE TIKEUT-O-NIEUNHIEUH 899B B3CD # HANGUL SYLLABLE TIKEUT-O-RIEULKIYEOK 899C B3CF # HANGUL SYLLABLE TIKEUT-O-RIEULPIEUP 899D B3D1 # HANGUL SYLLABLE TIKEUT-O-RIEULTHIEUTH 899E B3D2 # HANGUL SYLLABLE TIKEUT-O-RIEULPHIEUPH 899F B3D3 # HANGUL SYLLABLE TIKEUT-O-RIEULHIEUH 89A0 B3D6 # HANGUL SYLLABLE TIKEUT-O-PIEUPSIOS 89A1 B3D8 # HANGUL SYLLABLE TIKEUT-O-SSANGSIOS 89A2 B3DA # HANGUL SYLLABLE TIKEUT-O-CIEUC 89A3 B3DC # HANGUL SYLLABLE TIKEUT-O-KHIEUKH 89A4 B3DE # HANGUL SYLLABLE TIKEUT-O-PHIEUPH 89A5 B3DF # HANGUL SYLLABLE TIKEUT-O-HIEUH 89A6 B3E1 # HANGUL SYLLABLE TIKEUT-WA-KIYEOK 89A7 B3E2 # HANGUL SYLLABLE TIKEUT-WA-SSANGKIYEOK 89A8 B3E3 # HANGUL SYLLABLE TIKEUT-WA-KIYEOKSIOS 89A9 B3E5 # HANGUL SYLLABLE TIKEUT-WA-NIEUNCIEUC 89AA B3E6 # HANGUL SYLLABLE TIKEUT-WA-NIEUNHIEUH 89AB B3E7 # HANGUL SYLLABLE TIKEUT-WA-TIKEUT 89AC B3E9 # HANGUL SYLLABLE TIKEUT-WA-RIEULKIYEOK 89AD B3EA # HANGUL SYLLABLE TIKEUT-WA-RIEULMIEUM 89AE B3EB # HANGUL SYLLABLE TIKEUT-WA-RIEULPIEUP 89AF B3EC # HANGUL SYLLABLE TIKEUT-WA-RIEULSIOS 89B0 B3ED # HANGUL SYLLABLE TIKEUT-WA-RIEULTHIEUTH 89B1 B3EE # HANGUL SYLLABLE TIKEUT-WA-RIEULPHIEUPH 89B2 B3EF # HANGUL SYLLABLE TIKEUT-WA-RIEULHIEUH 89B3 B3F0 # HANGUL SYLLABLE TIKEUT-WA-MIEUM 89B4 B3F1 # HANGUL SYLLABLE TIKEUT-WA-PIEUP 89B5 B3F2 # HANGUL SYLLABLE TIKEUT-WA-PIEUPSIOS 89B6 B3F3 # HANGUL SYLLABLE TIKEUT-WA-SIOS 89B7 B3F4 # HANGUL SYLLABLE TIKEUT-WA-SSANGSIOS 89B8 B3F5 # HANGUL SYLLABLE TIKEUT-WA-IEUNG 89B9 B3F6 # HANGUL SYLLABLE TIKEUT-WA-CIEUC 89BA B3F7 # HANGUL SYLLABLE TIKEUT-WA-CHIEUCH 89BB B3F8 # HANGUL SYLLABLE TIKEUT-WA-KHIEUKH 89BC B3F9 # HANGUL SYLLABLE TIKEUT-WA-THIEUTH 89BD B3FA # HANGUL SYLLABLE TIKEUT-WA-PHIEUPH 89BE B3FB # HANGUL SYLLABLE TIKEUT-WA-HIEUH 89BF B3FD # HANGUL SYLLABLE TIKEUT-WAE-KIYEOK 89C0 B3FE # HANGUL SYLLABLE TIKEUT-WAE-SSANGKIYEOK 89C1 B3FF # HANGUL SYLLABLE TIKEUT-WAE-KIYEOKSIOS 89C2 B400 # HANGUL SYLLABLE TIKEUT-WAE-NIEUN 89C3 B401 # HANGUL SYLLABLE TIKEUT-WAE-NIEUNCIEUC 89C4 B402 # HANGUL SYLLABLE TIKEUT-WAE-NIEUNHIEUH 89C5 B403 # HANGUL SYLLABLE TIKEUT-WAE-TIKEUT 89C6 B404 # HANGUL SYLLABLE TIKEUT-WAE-RIEUL 89C7 B405 # HANGUL SYLLABLE TIKEUT-WAE-RIEULKIYEOK 89C8 B406 # HANGUL SYLLABLE TIKEUT-WAE-RIEULMIEUM 89C9 B407 # HANGUL SYLLABLE TIKEUT-WAE-RIEULPIEUP 89CA B408 # HANGUL SYLLABLE TIKEUT-WAE-RIEULSIOS 89CB B409 # HANGUL SYLLABLE TIKEUT-WAE-RIEULTHIEUTH 89CC B40A # HANGUL SYLLABLE TIKEUT-WAE-RIEULPHIEUPH 89CD B40B # HANGUL SYLLABLE TIKEUT-WAE-RIEULHIEUH 89CE B40C # HANGUL SYLLABLE TIKEUT-WAE-MIEUM 89CF B40D # HANGUL SYLLABLE TIKEUT-WAE-PIEUP 89D0 B40E # HANGUL SYLLABLE TIKEUT-WAE-PIEUPSIOS 89D1 B40F # HANGUL SYLLABLE TIKEUT-WAE-SIOS 89D2 B411 # HANGUL SYLLABLE TIKEUT-WAE-IEUNG 89D3 B412 # HANGUL SYLLABLE TIKEUT-WAE-CIEUC 89D4 B413 # HANGUL SYLLABLE TIKEUT-WAE-CHIEUCH 89D5 B414 # HANGUL SYLLABLE TIKEUT-WAE-KHIEUKH 89D6 B415 # HANGUL SYLLABLE TIKEUT-WAE-THIEUTH 89D7 B416 # HANGUL SYLLABLE TIKEUT-WAE-PHIEUPH 89D8 B417 # HANGUL SYLLABLE TIKEUT-WAE-HIEUH 89D9 B419 # HANGUL SYLLABLE TIKEUT-OE-KIYEOK 89DA B41A # HANGUL SYLLABLE TIKEUT-OE-SSANGKIYEOK 89DB B41B # HANGUL SYLLABLE TIKEUT-OE-KIYEOKSIOS 89DC B41D # HANGUL SYLLABLE TIKEUT-OE-NIEUNCIEUC 89DD B41E # HANGUL SYLLABLE TIKEUT-OE-NIEUNHIEUH 89DE B41F # HANGUL SYLLABLE TIKEUT-OE-TIKEUT 89DF B421 # HANGUL SYLLABLE TIKEUT-OE-RIEULKIYEOK 89E0 B422 # HANGUL SYLLABLE TIKEUT-OE-RIEULMIEUM 89E1 B423 # HANGUL SYLLABLE TIKEUT-OE-RIEULPIEUP 89E2 B424 # HANGUL SYLLABLE TIKEUT-OE-RIEULSIOS 89E3 B425 # HANGUL SYLLABLE TIKEUT-OE-RIEULTHIEUTH 89E4 B426 # HANGUL SYLLABLE TIKEUT-OE-RIEULPHIEUPH 89E5 B427 # HANGUL SYLLABLE TIKEUT-OE-RIEULHIEUH 89E6 B42A # HANGUL SYLLABLE TIKEUT-OE-PIEUPSIOS 89E7 B42C # HANGUL SYLLABLE TIKEUT-OE-SSANGSIOS 89E8 B42D # HANGUL SYLLABLE TIKEUT-OE-IEUNG 89E9 B42E # HANGUL SYLLABLE TIKEUT-OE-CIEUC 89EA B42F # HANGUL SYLLABLE TIKEUT-OE-CHIEUCH 89EB B430 # HANGUL SYLLABLE TIKEUT-OE-KHIEUKH 89EC B431 # HANGUL SYLLABLE TIKEUT-OE-THIEUTH 89ED B432 # HANGUL SYLLABLE TIKEUT-OE-PHIEUPH 89EE B433 # HANGUL SYLLABLE TIKEUT-OE-HIEUH 89EF B435 # HANGUL SYLLABLE TIKEUT-YO-KIYEOK 89F0 B436 # HANGUL SYLLABLE TIKEUT-YO-SSANGKIYEOK 89F1 B437 # HANGUL SYLLABLE TIKEUT-YO-KIYEOKSIOS 89F2 B438 # HANGUL SYLLABLE TIKEUT-YO-NIEUN 89F3 B439 # HANGUL SYLLABLE TIKEUT-YO-NIEUNCIEUC 89F4 B43A # HANGUL SYLLABLE TIKEUT-YO-NIEUNHIEUH 89F5 B43B # HANGUL SYLLABLE TIKEUT-YO-TIKEUT 89F6 B43C # HANGUL SYLLABLE TIKEUT-YO-RIEUL 89F7 B43D # HANGUL SYLLABLE TIKEUT-YO-RIEULKIYEOK 89F8 B43E # HANGUL SYLLABLE TIKEUT-YO-RIEULMIEUM 89F9 B43F # HANGUL SYLLABLE TIKEUT-YO-RIEULPIEUP 89FA B440 # HANGUL SYLLABLE TIKEUT-YO-RIEULSIOS 89FB B441 # HANGUL SYLLABLE TIKEUT-YO-RIEULTHIEUTH 89FC B442 # HANGUL SYLLABLE TIKEUT-YO-RIEULPHIEUPH 89FD B443 # HANGUL SYLLABLE TIKEUT-YO-RIEULHIEUH 89FE B444 # HANGUL SYLLABLE TIKEUT-YO-MIEUM 8A41 B445 # HANGUL SYLLABLE TIKEUT-YO-PIEUP 8A42 B446 # HANGUL SYLLABLE TIKEUT-YO-PIEUPSIOS 8A43 B447 # HANGUL SYLLABLE TIKEUT-YO-SIOS 8A44 B448 # HANGUL SYLLABLE TIKEUT-YO-SSANGSIOS 8A45 B449 # HANGUL SYLLABLE TIKEUT-YO-IEUNG 8A46 B44A # HANGUL SYLLABLE TIKEUT-YO-CIEUC 8A47 B44B # HANGUL SYLLABLE TIKEUT-YO-CHIEUCH 8A48 B44C # HANGUL SYLLABLE TIKEUT-YO-KHIEUKH 8A49 B44D # HANGUL SYLLABLE TIKEUT-YO-THIEUTH 8A4A B44E # HANGUL SYLLABLE TIKEUT-YO-PHIEUPH 8A4B B44F # HANGUL SYLLABLE TIKEUT-YO-HIEUH 8A4C B452 # HANGUL SYLLABLE TIKEUT-U-SSANGKIYEOK 8A4D B453 # HANGUL SYLLABLE TIKEUT-U-KIYEOKSIOS 8A4E B455 # HANGUL SYLLABLE TIKEUT-U-NIEUNCIEUC 8A4F B456 # HANGUL SYLLABLE TIKEUT-U-NIEUNHIEUH 8A50 B457 # HANGUL SYLLABLE TIKEUT-U-TIKEUT 8A51 B459 # HANGUL SYLLABLE TIKEUT-U-RIEULKIYEOK 8A52 B45A # HANGUL SYLLABLE TIKEUT-U-RIEULMIEUM 8A53 B45B # HANGUL SYLLABLE TIKEUT-U-RIEULPIEUP 8A54 B45C # HANGUL SYLLABLE TIKEUT-U-RIEULSIOS 8A55 B45D # HANGUL SYLLABLE TIKEUT-U-RIEULTHIEUTH 8A56 B45E # HANGUL SYLLABLE TIKEUT-U-RIEULPHIEUPH 8A57 B45F # HANGUL SYLLABLE TIKEUT-U-RIEULHIEUH 8A58 B462 # HANGUL SYLLABLE TIKEUT-U-PIEUPSIOS 8A59 B464 # HANGUL SYLLABLE TIKEUT-U-SSANGSIOS 8A5A B466 # HANGUL SYLLABLE TIKEUT-U-CIEUC 8A61 B467 # HANGUL SYLLABLE TIKEUT-U-CHIEUCH 8A62 B468 # HANGUL SYLLABLE TIKEUT-U-KHIEUKH 8A63 B469 # HANGUL SYLLABLE TIKEUT-U-THIEUTH 8A64 B46A # HANGUL SYLLABLE TIKEUT-U-PHIEUPH 8A65 B46B # HANGUL SYLLABLE TIKEUT-U-HIEUH 8A66 B46D # HANGUL SYLLABLE TIKEUT-WEO-KIYEOK 8A67 B46E # HANGUL SYLLABLE TIKEUT-WEO-SSANGKIYEOK 8A68 B46F # HANGUL SYLLABLE TIKEUT-WEO-KIYEOKSIOS 8A69 B470 # HANGUL SYLLABLE TIKEUT-WEO-NIEUN 8A6A B471 # HANGUL SYLLABLE TIKEUT-WEO-NIEUNCIEUC 8A6B B472 # HANGUL SYLLABLE TIKEUT-WEO-NIEUNHIEUH 8A6C B473 # HANGUL SYLLABLE TIKEUT-WEO-TIKEUT 8A6D B474 # HANGUL SYLLABLE TIKEUT-WEO-RIEUL 8A6E B475 # HANGUL SYLLABLE TIKEUT-WEO-RIEULKIYEOK 8A6F B476 # HANGUL SYLLABLE TIKEUT-WEO-RIEULMIEUM 8A70 B477 # HANGUL SYLLABLE TIKEUT-WEO-RIEULPIEUP 8A71 B478 # HANGUL SYLLABLE TIKEUT-WEO-RIEULSIOS 8A72 B479 # HANGUL SYLLABLE TIKEUT-WEO-RIEULTHIEUTH 8A73 B47A # HANGUL SYLLABLE TIKEUT-WEO-RIEULPHIEUPH 8A74 B47B # HANGUL SYLLABLE TIKEUT-WEO-RIEULHIEUH 8A75 B47C # HANGUL SYLLABLE TIKEUT-WEO-MIEUM 8A76 B47D # HANGUL SYLLABLE TIKEUT-WEO-PIEUP 8A77 B47E # HANGUL SYLLABLE TIKEUT-WEO-PIEUPSIOS 8A78 B47F # HANGUL SYLLABLE TIKEUT-WEO-SIOS 8A79 B481 # HANGUL SYLLABLE TIKEUT-WEO-IEUNG 8A7A B482 # HANGUL SYLLABLE TIKEUT-WEO-CIEUC 8A81 B483 # HANGUL SYLLABLE TIKEUT-WEO-CHIEUCH 8A82 B484 # HANGUL SYLLABLE TIKEUT-WEO-KHIEUKH 8A83 B485 # HANGUL SYLLABLE TIKEUT-WEO-THIEUTH 8A84 B486 # HANGUL SYLLABLE TIKEUT-WEO-PHIEUPH 8A85 B487 # HANGUL SYLLABLE TIKEUT-WEO-HIEUH 8A86 B489 # HANGUL SYLLABLE TIKEUT-WE-KIYEOK 8A87 B48A # HANGUL SYLLABLE TIKEUT-WE-SSANGKIYEOK 8A88 B48B # HANGUL SYLLABLE TIKEUT-WE-KIYEOKSIOS 8A89 B48C # HANGUL SYLLABLE TIKEUT-WE-NIEUN 8A8A B48D # HANGUL SYLLABLE TIKEUT-WE-NIEUNCIEUC 8A8B B48E # HANGUL SYLLABLE TIKEUT-WE-NIEUNHIEUH 8A8C B48F # HANGUL SYLLABLE TIKEUT-WE-TIKEUT 8A8D B490 # HANGUL SYLLABLE TIKEUT-WE-RIEUL 8A8E B491 # HANGUL SYLLABLE TIKEUT-WE-RIEULKIYEOK 8A8F B492 # HANGUL SYLLABLE TIKEUT-WE-RIEULMIEUM 8A90 B493 # HANGUL SYLLABLE TIKEUT-WE-RIEULPIEUP 8A91 B494 # HANGUL SYLLABLE TIKEUT-WE-RIEULSIOS 8A92 B495 # HANGUL SYLLABLE TIKEUT-WE-RIEULTHIEUTH 8A93 B496 # HANGUL SYLLABLE TIKEUT-WE-RIEULPHIEUPH 8A94 B497 # HANGUL SYLLABLE TIKEUT-WE-RIEULHIEUH 8A95 B498 # HANGUL SYLLABLE TIKEUT-WE-MIEUM 8A96 B499 # HANGUL SYLLABLE TIKEUT-WE-PIEUP 8A97 B49A # HANGUL SYLLABLE TIKEUT-WE-PIEUPSIOS 8A98 B49B # HANGUL SYLLABLE TIKEUT-WE-SIOS 8A99 B49C # HANGUL SYLLABLE TIKEUT-WE-SSANGSIOS 8A9A B49E # HANGUL SYLLABLE TIKEUT-WE-CIEUC 8A9B B49F # HANGUL SYLLABLE TIKEUT-WE-CHIEUCH 8A9C B4A0 # HANGUL SYLLABLE TIKEUT-WE-KHIEUKH 8A9D B4A1 # HANGUL SYLLABLE TIKEUT-WE-THIEUTH 8A9E B4A2 # HANGUL SYLLABLE TIKEUT-WE-PHIEUPH 8A9F B4A3 # HANGUL SYLLABLE TIKEUT-WE-HIEUH 8AA0 B4A5 # HANGUL SYLLABLE TIKEUT-WI-KIYEOK 8AA1 B4A6 # HANGUL SYLLABLE TIKEUT-WI-SSANGKIYEOK 8AA2 B4A7 # HANGUL SYLLABLE TIKEUT-WI-KIYEOKSIOS 8AA3 B4A9 # HANGUL SYLLABLE TIKEUT-WI-NIEUNCIEUC 8AA4 B4AA # HANGUL SYLLABLE TIKEUT-WI-NIEUNHIEUH 8AA5 B4AB # HANGUL SYLLABLE TIKEUT-WI-TIKEUT 8AA6 B4AD # HANGUL SYLLABLE TIKEUT-WI-RIEULKIYEOK 8AA7 B4AE # HANGUL SYLLABLE TIKEUT-WI-RIEULMIEUM 8AA8 B4AF # HANGUL SYLLABLE TIKEUT-WI-RIEULPIEUP 8AA9 B4B0 # HANGUL SYLLABLE TIKEUT-WI-RIEULSIOS 8AAA B4B1 # HANGUL SYLLABLE TIKEUT-WI-RIEULTHIEUTH 8AAB B4B2 # HANGUL SYLLABLE TIKEUT-WI-RIEULPHIEUPH 8AAC B4B3 # HANGUL SYLLABLE TIKEUT-WI-RIEULHIEUH 8AAD B4B4 # HANGUL SYLLABLE TIKEUT-WI-MIEUM 8AAE B4B6 # HANGUL SYLLABLE TIKEUT-WI-PIEUPSIOS 8AAF B4B8 # HANGUL SYLLABLE TIKEUT-WI-SSANGSIOS 8AB0 B4BA # HANGUL SYLLABLE TIKEUT-WI-CIEUC 8AB1 B4BB # HANGUL SYLLABLE TIKEUT-WI-CHIEUCH 8AB2 B4BC # HANGUL SYLLABLE TIKEUT-WI-KHIEUKH 8AB3 B4BD # HANGUL SYLLABLE TIKEUT-WI-THIEUTH 8AB4 B4BE # HANGUL SYLLABLE TIKEUT-WI-PHIEUPH 8AB5 B4BF # HANGUL SYLLABLE TIKEUT-WI-HIEUH 8AB6 B4C1 # HANGUL SYLLABLE TIKEUT-YU-KIYEOK 8AB7 B4C2 # HANGUL SYLLABLE TIKEUT-YU-SSANGKIYEOK 8AB8 B4C3 # HANGUL SYLLABLE TIKEUT-YU-KIYEOKSIOS 8AB9 B4C5 # HANGUL SYLLABLE TIKEUT-YU-NIEUNCIEUC 8ABA B4C6 # HANGUL SYLLABLE TIKEUT-YU-NIEUNHIEUH 8ABB B4C7 # HANGUL SYLLABLE TIKEUT-YU-TIKEUT 8ABC B4C9 # HANGUL SYLLABLE TIKEUT-YU-RIEULKIYEOK 8ABD B4CA # HANGUL SYLLABLE TIKEUT-YU-RIEULMIEUM 8ABE B4CB # HANGUL SYLLABLE TIKEUT-YU-RIEULPIEUP 8ABF B4CC # HANGUL SYLLABLE TIKEUT-YU-RIEULSIOS 8AC0 B4CD # HANGUL SYLLABLE TIKEUT-YU-RIEULTHIEUTH 8AC1 B4CE # HANGUL SYLLABLE TIKEUT-YU-RIEULPHIEUPH 8AC2 B4CF # HANGUL SYLLABLE TIKEUT-YU-RIEULHIEUH 8AC3 B4D1 # HANGUL SYLLABLE TIKEUT-YU-PIEUP 8AC4 B4D2 # HANGUL SYLLABLE TIKEUT-YU-PIEUPSIOS 8AC5 B4D3 # HANGUL SYLLABLE TIKEUT-YU-SIOS 8AC6 B4D4 # HANGUL SYLLABLE TIKEUT-YU-SSANGSIOS 8AC7 B4D6 # HANGUL SYLLABLE TIKEUT-YU-CIEUC 8AC8 B4D7 # HANGUL SYLLABLE TIKEUT-YU-CHIEUCH 8AC9 B4D8 # HANGUL SYLLABLE TIKEUT-YU-KHIEUKH 8ACA B4D9 # HANGUL SYLLABLE TIKEUT-YU-THIEUTH 8ACB B4DA # HANGUL SYLLABLE TIKEUT-YU-PHIEUPH 8ACC B4DB # HANGUL SYLLABLE TIKEUT-YU-HIEUH 8ACD B4DE # HANGUL SYLLABLE TIKEUT-EU-SSANGKIYEOK 8ACE B4DF # HANGUL SYLLABLE TIKEUT-EU-KIYEOKSIOS 8ACF B4E1 # HANGUL SYLLABLE TIKEUT-EU-NIEUNCIEUC 8AD0 B4E2 # HANGUL SYLLABLE TIKEUT-EU-NIEUNHIEUH 8AD1 B4E5 # HANGUL SYLLABLE TIKEUT-EU-RIEULKIYEOK 8AD2 B4E7 # HANGUL SYLLABLE TIKEUT-EU-RIEULPIEUP 8AD3 B4E8 # HANGUL SYLLABLE TIKEUT-EU-RIEULSIOS 8AD4 B4E9 # HANGUL SYLLABLE TIKEUT-EU-RIEULTHIEUTH 8AD5 B4EA # HANGUL SYLLABLE TIKEUT-EU-RIEULPHIEUPH 8AD6 B4EB # HANGUL SYLLABLE TIKEUT-EU-RIEULHIEUH 8AD7 B4EE # HANGUL SYLLABLE TIKEUT-EU-PIEUPSIOS 8AD8 B4F0 # HANGUL SYLLABLE TIKEUT-EU-SSANGSIOS 8AD9 B4F2 # HANGUL SYLLABLE TIKEUT-EU-CIEUC 8ADA B4F3 # HANGUL SYLLABLE TIKEUT-EU-CHIEUCH 8ADB B4F4 # HANGUL SYLLABLE TIKEUT-EU-KHIEUKH 8ADC B4F5 # HANGUL SYLLABLE TIKEUT-EU-THIEUTH 8ADD B4F6 # HANGUL SYLLABLE TIKEUT-EU-PHIEUPH 8ADE B4F7 # HANGUL SYLLABLE TIKEUT-EU-HIEUH 8ADF B4F9 # HANGUL SYLLABLE TIKEUT-YI-KIYEOK 8AE0 B4FA # HANGUL SYLLABLE TIKEUT-YI-SSANGKIYEOK 8AE1 B4FB # HANGUL SYLLABLE TIKEUT-YI-KIYEOKSIOS 8AE2 B4FC # HANGUL SYLLABLE TIKEUT-YI-NIEUN 8AE3 B4FD # HANGUL SYLLABLE TIKEUT-YI-NIEUNCIEUC 8AE4 B4FE # HANGUL SYLLABLE TIKEUT-YI-NIEUNHIEUH 8AE5 B4FF # HANGUL SYLLABLE TIKEUT-YI-TIKEUT 8AE6 B500 # HANGUL SYLLABLE TIKEUT-YI-RIEUL 8AE7 B501 # HANGUL SYLLABLE TIKEUT-YI-RIEULKIYEOK 8AE8 B502 # HANGUL SYLLABLE TIKEUT-YI-RIEULMIEUM 8AE9 B503 # HANGUL SYLLABLE TIKEUT-YI-RIEULPIEUP 8AEA B504 # HANGUL SYLLABLE TIKEUT-YI-RIEULSIOS 8AEB B505 # HANGUL SYLLABLE TIKEUT-YI-RIEULTHIEUTH 8AEC B506 # HANGUL SYLLABLE TIKEUT-YI-RIEULPHIEUPH 8AED B507 # HANGUL SYLLABLE TIKEUT-YI-RIEULHIEUH 8AEE B508 # HANGUL SYLLABLE TIKEUT-YI-MIEUM 8AEF B509 # HANGUL SYLLABLE TIKEUT-YI-PIEUP 8AF0 B50A # HANGUL SYLLABLE TIKEUT-YI-PIEUPSIOS 8AF1 B50B # HANGUL SYLLABLE TIKEUT-YI-SIOS 8AF2 B50C # HANGUL SYLLABLE TIKEUT-YI-SSANGSIOS 8AF3 B50D # HANGUL SYLLABLE TIKEUT-YI-IEUNG 8AF4 B50E # HANGUL SYLLABLE TIKEUT-YI-CIEUC 8AF5 B50F # HANGUL SYLLABLE TIKEUT-YI-CHIEUCH 8AF6 B510 # HANGUL SYLLABLE TIKEUT-YI-KHIEUKH 8AF7 B511 # HANGUL SYLLABLE TIKEUT-YI-THIEUTH 8AF8 B512 # HANGUL SYLLABLE TIKEUT-YI-PHIEUPH 8AF9 B513 # HANGUL SYLLABLE TIKEUT-YI-HIEUH 8AFA B516 # HANGUL SYLLABLE TIKEUT-I-SSANGKIYEOK 8AFB B517 # HANGUL SYLLABLE TIKEUT-I-KIYEOKSIOS 8AFC B519 # HANGUL SYLLABLE TIKEUT-I-NIEUNCIEUC 8AFD B51A # HANGUL SYLLABLE TIKEUT-I-NIEUNHIEUH 8AFE B51D # HANGUL SYLLABLE TIKEUT-I-RIEULKIYEOK 8B41 B51E # HANGUL SYLLABLE TIKEUT-I-RIEULMIEUM 8B42 B51F # HANGUL SYLLABLE TIKEUT-I-RIEULPIEUP 8B43 B520 # HANGUL SYLLABLE TIKEUT-I-RIEULSIOS 8B44 B521 # HANGUL SYLLABLE TIKEUT-I-RIEULTHIEUTH 8B45 B522 # HANGUL SYLLABLE TIKEUT-I-RIEULPHIEUPH 8B46 B523 # HANGUL SYLLABLE TIKEUT-I-RIEULHIEUH 8B47 B526 # HANGUL SYLLABLE TIKEUT-I-PIEUPSIOS 8B48 B52B # HANGUL SYLLABLE TIKEUT-I-CHIEUCH 8B49 B52C # HANGUL SYLLABLE TIKEUT-I-KHIEUKH 8B4A B52D # HANGUL SYLLABLE TIKEUT-I-THIEUTH 8B4B B52E # HANGUL SYLLABLE TIKEUT-I-PHIEUPH 8B4C B52F # HANGUL SYLLABLE TIKEUT-I-HIEUH 8B4D B532 # HANGUL SYLLABLE SSANGTIKEUT-A-SSANGKIYEOK 8B4E B533 # HANGUL SYLLABLE SSANGTIKEUT-A-KIYEOKSIOS 8B4F B535 # HANGUL SYLLABLE SSANGTIKEUT-A-NIEUNCIEUC 8B50 B536 # HANGUL SYLLABLE SSANGTIKEUT-A-NIEUNHIEUH 8B51 B537 # HANGUL SYLLABLE SSANGTIKEUT-A-TIKEUT 8B52 B539 # HANGUL SYLLABLE SSANGTIKEUT-A-RIEULKIYEOK 8B53 B53A # HANGUL SYLLABLE SSANGTIKEUT-A-RIEULMIEUM 8B54 B53B # HANGUL SYLLABLE SSANGTIKEUT-A-RIEULPIEUP 8B55 B53C # HANGUL SYLLABLE SSANGTIKEUT-A-RIEULSIOS 8B56 B53D # HANGUL SYLLABLE SSANGTIKEUT-A-RIEULTHIEUTH 8B57 B53E # HANGUL SYLLABLE SSANGTIKEUT-A-RIEULPHIEUPH 8B58 B53F # HANGUL SYLLABLE SSANGTIKEUT-A-RIEULHIEUH 8B59 B542 # HANGUL SYLLABLE SSANGTIKEUT-A-PIEUPSIOS 8B5A B546 # HANGUL SYLLABLE SSANGTIKEUT-A-CIEUC 8B61 B547 # HANGUL SYLLABLE SSANGTIKEUT-A-CHIEUCH 8B62 B548 # HANGUL SYLLABLE SSANGTIKEUT-A-KHIEUKH 8B63 B549 # HANGUL SYLLABLE SSANGTIKEUT-A-THIEUTH 8B64 B54A # HANGUL SYLLABLE SSANGTIKEUT-A-PHIEUPH 8B65 B54E # HANGUL SYLLABLE SSANGTIKEUT-AE-SSANGKIYEOK 8B66 B54F # HANGUL SYLLABLE SSANGTIKEUT-AE-KIYEOKSIOS 8B67 B551 # HANGUL SYLLABLE SSANGTIKEUT-AE-NIEUNCIEUC 8B68 B552 # HANGUL SYLLABLE SSANGTIKEUT-AE-NIEUNHIEUH 8B69 B553 # HANGUL SYLLABLE SSANGTIKEUT-AE-TIKEUT 8B6A B555 # HANGUL SYLLABLE SSANGTIKEUT-AE-RIEULKIYEOK 8B6B B556 # HANGUL SYLLABLE SSANGTIKEUT-AE-RIEULMIEUM 8B6C B557 # HANGUL SYLLABLE SSANGTIKEUT-AE-RIEULPIEUP 8B6D B558 # HANGUL SYLLABLE SSANGTIKEUT-AE-RIEULSIOS 8B6E B559 # HANGUL SYLLABLE SSANGTIKEUT-AE-RIEULTHIEUTH 8B6F B55A # HANGUL SYLLABLE SSANGTIKEUT-AE-RIEULPHIEUPH 8B70 B55B # HANGUL SYLLABLE SSANGTIKEUT-AE-RIEULHIEUH 8B71 B55E # HANGUL SYLLABLE SSANGTIKEUT-AE-PIEUPSIOS 8B72 B562 # HANGUL SYLLABLE SSANGTIKEUT-AE-CIEUC 8B73 B563 # HANGUL SYLLABLE SSANGTIKEUT-AE-CHIEUCH 8B74 B564 # HANGUL SYLLABLE SSANGTIKEUT-AE-KHIEUKH 8B75 B565 # HANGUL SYLLABLE SSANGTIKEUT-AE-THIEUTH 8B76 B566 # HANGUL SYLLABLE SSANGTIKEUT-AE-PHIEUPH 8B77 B567 # HANGUL SYLLABLE SSANGTIKEUT-AE-HIEUH 8B78 B568 # HANGUL SYLLABLE SSANGTIKEUT-YA 8B79 B569 # HANGUL SYLLABLE SSANGTIKEUT-YA-KIYEOK 8B7A B56A # HANGUL SYLLABLE SSANGTIKEUT-YA-SSANGKIYEOK 8B81 B56B # HANGUL SYLLABLE SSANGTIKEUT-YA-KIYEOKSIOS 8B82 B56C # HANGUL SYLLABLE SSANGTIKEUT-YA-NIEUN 8B83 B56D # HANGUL SYLLABLE SSANGTIKEUT-YA-NIEUNCIEUC 8B84 B56E # HANGUL SYLLABLE SSANGTIKEUT-YA-NIEUNHIEUH 8B85 B56F # HANGUL SYLLABLE SSANGTIKEUT-YA-TIKEUT 8B86 B570 # HANGUL SYLLABLE SSANGTIKEUT-YA-RIEUL 8B87 B571 # HANGUL SYLLABLE SSANGTIKEUT-YA-RIEULKIYEOK 8B88 B572 # HANGUL SYLLABLE SSANGTIKEUT-YA-RIEULMIEUM 8B89 B573 # HANGUL SYLLABLE SSANGTIKEUT-YA-RIEULPIEUP 8B8A B574 # HANGUL SYLLABLE SSANGTIKEUT-YA-RIEULSIOS 8B8B B575 # HANGUL SYLLABLE SSANGTIKEUT-YA-RIEULTHIEUTH 8B8C B576 # HANGUL SYLLABLE SSANGTIKEUT-YA-RIEULPHIEUPH 8B8D B577 # HANGUL SYLLABLE SSANGTIKEUT-YA-RIEULHIEUH 8B8E B578 # HANGUL SYLLABLE SSANGTIKEUT-YA-MIEUM 8B8F B579 # HANGUL SYLLABLE SSANGTIKEUT-YA-PIEUP 8B90 B57A # HANGUL SYLLABLE SSANGTIKEUT-YA-PIEUPSIOS 8B91 B57B # HANGUL SYLLABLE SSANGTIKEUT-YA-SIOS 8B92 B57C # HANGUL SYLLABLE SSANGTIKEUT-YA-SSANGSIOS 8B93 B57D # HANGUL SYLLABLE SSANGTIKEUT-YA-IEUNG 8B94 B57E # HANGUL SYLLABLE SSANGTIKEUT-YA-CIEUC 8B95 B57F # HANGUL SYLLABLE SSANGTIKEUT-YA-CHIEUCH 8B96 B580 # HANGUL SYLLABLE SSANGTIKEUT-YA-KHIEUKH 8B97 B581 # HANGUL SYLLABLE SSANGTIKEUT-YA-THIEUTH 8B98 B582 # HANGUL SYLLABLE SSANGTIKEUT-YA-PHIEUPH 8B99 B583 # HANGUL SYLLABLE SSANGTIKEUT-YA-HIEUH 8B9A B584 # HANGUL SYLLABLE SSANGTIKEUT-YAE 8B9B B585 # HANGUL SYLLABLE SSANGTIKEUT-YAE-KIYEOK 8B9C B586 # HANGUL SYLLABLE SSANGTIKEUT-YAE-SSANGKIYEOK 8B9D B587 # HANGUL SYLLABLE SSANGTIKEUT-YAE-KIYEOKSIOS 8B9E B588 # HANGUL SYLLABLE SSANGTIKEUT-YAE-NIEUN 8B9F B589 # HANGUL SYLLABLE SSANGTIKEUT-YAE-NIEUNCIEUC 8BA0 B58A # HANGUL SYLLABLE SSANGTIKEUT-YAE-NIEUNHIEUH 8BA1 B58B # HANGUL SYLLABLE SSANGTIKEUT-YAE-TIKEUT 8BA2 B58C # HANGUL SYLLABLE SSANGTIKEUT-YAE-RIEUL 8BA3 B58D # HANGUL SYLLABLE SSANGTIKEUT-YAE-RIEULKIYEOK 8BA4 B58E # HANGUL SYLLABLE SSANGTIKEUT-YAE-RIEULMIEUM 8BA5 B58F # HANGUL SYLLABLE SSANGTIKEUT-YAE-RIEULPIEUP 8BA6 B590 # HANGUL SYLLABLE SSANGTIKEUT-YAE-RIEULSIOS 8BA7 B591 # HANGUL SYLLABLE SSANGTIKEUT-YAE-RIEULTHIEUTH 8BA8 B592 # HANGUL SYLLABLE SSANGTIKEUT-YAE-RIEULPHIEUPH 8BA9 B593 # HANGUL SYLLABLE SSANGTIKEUT-YAE-RIEULHIEUH 8BAA B594 # HANGUL SYLLABLE SSANGTIKEUT-YAE-MIEUM 8BAB B595 # HANGUL SYLLABLE SSANGTIKEUT-YAE-PIEUP 8BAC B596 # HANGUL SYLLABLE SSANGTIKEUT-YAE-PIEUPSIOS 8BAD B597 # HANGUL SYLLABLE SSANGTIKEUT-YAE-SIOS 8BAE B598 # HANGUL SYLLABLE SSANGTIKEUT-YAE-SSANGSIOS 8BAF B599 # HANGUL SYLLABLE SSANGTIKEUT-YAE-IEUNG 8BB0 B59A # HANGUL SYLLABLE SSANGTIKEUT-YAE-CIEUC 8BB1 B59B # HANGUL SYLLABLE SSANGTIKEUT-YAE-CHIEUCH 8BB2 B59C # HANGUL SYLLABLE SSANGTIKEUT-YAE-KHIEUKH 8BB3 B59D # HANGUL SYLLABLE SSANGTIKEUT-YAE-THIEUTH 8BB4 B59E # HANGUL SYLLABLE SSANGTIKEUT-YAE-PHIEUPH 8BB5 B59F # HANGUL SYLLABLE SSANGTIKEUT-YAE-HIEUH 8BB6 B5A2 # HANGUL SYLLABLE SSANGTIKEUT-EO-SSANGKIYEOK 8BB7 B5A3 # HANGUL SYLLABLE SSANGTIKEUT-EO-KIYEOKSIOS 8BB8 B5A5 # HANGUL SYLLABLE SSANGTIKEUT-EO-NIEUNCIEUC 8BB9 B5A6 # HANGUL SYLLABLE SSANGTIKEUT-EO-NIEUNHIEUH 8BBA B5A7 # HANGUL SYLLABLE SSANGTIKEUT-EO-TIKEUT 8BBB B5A9 # HANGUL SYLLABLE SSANGTIKEUT-EO-RIEULKIYEOK 8BBC B5AC # HANGUL SYLLABLE SSANGTIKEUT-EO-RIEULSIOS 8BBD B5AD # HANGUL SYLLABLE SSANGTIKEUT-EO-RIEULTHIEUTH 8BBE B5AE # HANGUL SYLLABLE SSANGTIKEUT-EO-RIEULPHIEUPH 8BBF B5AF # HANGUL SYLLABLE SSANGTIKEUT-EO-RIEULHIEUH 8BC0 B5B2 # HANGUL SYLLABLE SSANGTIKEUT-EO-PIEUPSIOS 8BC1 B5B6 # HANGUL SYLLABLE SSANGTIKEUT-EO-CIEUC 8BC2 B5B7 # HANGUL SYLLABLE SSANGTIKEUT-EO-CHIEUCH 8BC3 B5B8 # HANGUL SYLLABLE SSANGTIKEUT-EO-KHIEUKH 8BC4 B5B9 # HANGUL SYLLABLE SSANGTIKEUT-EO-THIEUTH 8BC5 B5BA # HANGUL SYLLABLE SSANGTIKEUT-EO-PHIEUPH 8BC6 B5BE # HANGUL SYLLABLE SSANGTIKEUT-E-SSANGKIYEOK 8BC7 B5BF # HANGUL SYLLABLE SSANGTIKEUT-E-KIYEOKSIOS 8BC8 B5C1 # HANGUL SYLLABLE SSANGTIKEUT-E-NIEUNCIEUC 8BC9 B5C2 # HANGUL SYLLABLE SSANGTIKEUT-E-NIEUNHIEUH 8BCA B5C3 # HANGUL SYLLABLE SSANGTIKEUT-E-TIKEUT 8BCB B5C5 # HANGUL SYLLABLE SSANGTIKEUT-E-RIEULKIYEOK 8BCC B5C6 # HANGUL SYLLABLE SSANGTIKEUT-E-RIEULMIEUM 8BCD B5C7 # HANGUL SYLLABLE SSANGTIKEUT-E-RIEULPIEUP 8BCE B5C8 # HANGUL SYLLABLE SSANGTIKEUT-E-RIEULSIOS 8BCF B5C9 # HANGUL SYLLABLE SSANGTIKEUT-E-RIEULTHIEUTH 8BD0 B5CA # HANGUL SYLLABLE SSANGTIKEUT-E-RIEULPHIEUPH 8BD1 B5CB # HANGUL SYLLABLE SSANGTIKEUT-E-RIEULHIEUH 8BD2 B5CE # HANGUL SYLLABLE SSANGTIKEUT-E-PIEUPSIOS 8BD3 B5D2 # HANGUL SYLLABLE SSANGTIKEUT-E-CIEUC 8BD4 B5D3 # HANGUL SYLLABLE SSANGTIKEUT-E-CHIEUCH 8BD5 B5D4 # HANGUL SYLLABLE SSANGTIKEUT-E-KHIEUKH 8BD6 B5D5 # HANGUL SYLLABLE SSANGTIKEUT-E-THIEUTH 8BD7 B5D6 # HANGUL SYLLABLE SSANGTIKEUT-E-PHIEUPH 8BD8 B5D7 # HANGUL SYLLABLE SSANGTIKEUT-E-HIEUH 8BD9 B5D9 # HANGUL SYLLABLE SSANGTIKEUT-YEO-KIYEOK 8BDA B5DA # HANGUL SYLLABLE SSANGTIKEUT-YEO-SSANGKIYEOK 8BDB B5DB # HANGUL SYLLABLE SSANGTIKEUT-YEO-KIYEOKSIOS 8BDC B5DC # HANGUL SYLLABLE SSANGTIKEUT-YEO-NIEUN 8BDD B5DD # HANGUL SYLLABLE SSANGTIKEUT-YEO-NIEUNCIEUC 8BDE B5DE # HANGUL SYLLABLE SSANGTIKEUT-YEO-NIEUNHIEUH 8BDF B5DF # HANGUL SYLLABLE SSANGTIKEUT-YEO-TIKEUT 8BE0 B5E0 # HANGUL SYLLABLE SSANGTIKEUT-YEO-RIEUL 8BE1 B5E1 # HANGUL SYLLABLE SSANGTIKEUT-YEO-RIEULKIYEOK 8BE2 B5E2 # HANGUL SYLLABLE SSANGTIKEUT-YEO-RIEULMIEUM 8BE3 B5E3 # HANGUL SYLLABLE SSANGTIKEUT-YEO-RIEULPIEUP 8BE4 B5E4 # HANGUL SYLLABLE SSANGTIKEUT-YEO-RIEULSIOS 8BE5 B5E5 # HANGUL SYLLABLE SSANGTIKEUT-YEO-RIEULTHIEUTH 8BE6 B5E6 # HANGUL SYLLABLE SSANGTIKEUT-YEO-RIEULPHIEUPH 8BE7 B5E7 # HANGUL SYLLABLE SSANGTIKEUT-YEO-RIEULHIEUH 8BE8 B5E8 # HANGUL SYLLABLE SSANGTIKEUT-YEO-MIEUM 8BE9 B5E9 # HANGUL SYLLABLE SSANGTIKEUT-YEO-PIEUP 8BEA B5EA # HANGUL SYLLABLE SSANGTIKEUT-YEO-PIEUPSIOS 8BEB B5EB # HANGUL SYLLABLE SSANGTIKEUT-YEO-SIOS 8BEC B5ED # HANGUL SYLLABLE SSANGTIKEUT-YEO-IEUNG 8BED B5EE # HANGUL SYLLABLE SSANGTIKEUT-YEO-CIEUC 8BEE B5EF # HANGUL SYLLABLE SSANGTIKEUT-YEO-CHIEUCH 8BEF B5F0 # HANGUL SYLLABLE SSANGTIKEUT-YEO-KHIEUKH 8BF0 B5F1 # HANGUL SYLLABLE SSANGTIKEUT-YEO-THIEUTH 8BF1 B5F2 # HANGUL SYLLABLE SSANGTIKEUT-YEO-PHIEUPH 8BF2 B5F3 # HANGUL SYLLABLE SSANGTIKEUT-YEO-HIEUH 8BF3 B5F4 # HANGUL SYLLABLE SSANGTIKEUT-YE 8BF4 B5F5 # HANGUL SYLLABLE SSANGTIKEUT-YE-KIYEOK 8BF5 B5F6 # HANGUL SYLLABLE SSANGTIKEUT-YE-SSANGKIYEOK 8BF6 B5F7 # HANGUL SYLLABLE SSANGTIKEUT-YE-KIYEOKSIOS 8BF7 B5F8 # HANGUL SYLLABLE SSANGTIKEUT-YE-NIEUN 8BF8 B5F9 # HANGUL SYLLABLE SSANGTIKEUT-YE-NIEUNCIEUC 8BF9 B5FA # HANGUL SYLLABLE SSANGTIKEUT-YE-NIEUNHIEUH 8BFA B5FB # HANGUL SYLLABLE SSANGTIKEUT-YE-TIKEUT 8BFB B5FC # HANGUL SYLLABLE SSANGTIKEUT-YE-RIEUL 8BFC B5FD # HANGUL SYLLABLE SSANGTIKEUT-YE-RIEULKIYEOK 8BFD B5FE # HANGUL SYLLABLE SSANGTIKEUT-YE-RIEULMIEUM 8BFE B5FF # HANGUL SYLLABLE SSANGTIKEUT-YE-RIEULPIEUP 8C41 B600 # HANGUL SYLLABLE SSANGTIKEUT-YE-RIEULSIOS 8C42 B601 # HANGUL SYLLABLE SSANGTIKEUT-YE-RIEULTHIEUTH 8C43 B602 # HANGUL SYLLABLE SSANGTIKEUT-YE-RIEULPHIEUPH 8C44 B603 # HANGUL SYLLABLE SSANGTIKEUT-YE-RIEULHIEUH 8C45 B604 # HANGUL SYLLABLE SSANGTIKEUT-YE-MIEUM 8C46 B605 # HANGUL SYLLABLE SSANGTIKEUT-YE-PIEUP 8C47 B606 # HANGUL SYLLABLE SSANGTIKEUT-YE-PIEUPSIOS 8C48 B607 # HANGUL SYLLABLE SSANGTIKEUT-YE-SIOS 8C49 B608 # HANGUL SYLLABLE SSANGTIKEUT-YE-SSANGSIOS 8C4A B609 # HANGUL SYLLABLE SSANGTIKEUT-YE-IEUNG 8C4B B60A # HANGUL SYLLABLE SSANGTIKEUT-YE-CIEUC 8C4C B60B # HANGUL SYLLABLE SSANGTIKEUT-YE-CHIEUCH 8C4D B60C # HANGUL SYLLABLE SSANGTIKEUT-YE-KHIEUKH 8C4E B60D # HANGUL SYLLABLE SSANGTIKEUT-YE-THIEUTH 8C4F B60E # HANGUL SYLLABLE SSANGTIKEUT-YE-PHIEUPH 8C50 B60F # HANGUL SYLLABLE SSANGTIKEUT-YE-HIEUH 8C51 B612 # HANGUL SYLLABLE SSANGTIKEUT-O-SSANGKIYEOK 8C52 B613 # HANGUL SYLLABLE SSANGTIKEUT-O-KIYEOKSIOS 8C53 B615 # HANGUL SYLLABLE SSANGTIKEUT-O-NIEUNCIEUC 8C54 B616 # HANGUL SYLLABLE SSANGTIKEUT-O-NIEUNHIEUH 8C55 B617 # HANGUL SYLLABLE SSANGTIKEUT-O-TIKEUT 8C56 B619 # HANGUL SYLLABLE SSANGTIKEUT-O-RIEULKIYEOK 8C57 B61A # HANGUL SYLLABLE SSANGTIKEUT-O-RIEULMIEUM 8C58 B61B # HANGUL SYLLABLE SSANGTIKEUT-O-RIEULPIEUP 8C59 B61C # HANGUL SYLLABLE SSANGTIKEUT-O-RIEULSIOS 8C5A B61D # HANGUL SYLLABLE SSANGTIKEUT-O-RIEULTHIEUTH 8C61 B61E # HANGUL SYLLABLE SSANGTIKEUT-O-RIEULPHIEUPH 8C62 B61F # HANGUL SYLLABLE SSANGTIKEUT-O-RIEULHIEUH 8C63 B620 # HANGUL SYLLABLE SSANGTIKEUT-O-MIEUM 8C64 B621 # HANGUL SYLLABLE SSANGTIKEUT-O-PIEUP 8C65 B622 # HANGUL SYLLABLE SSANGTIKEUT-O-PIEUPSIOS 8C66 B623 # HANGUL SYLLABLE SSANGTIKEUT-O-SIOS 8C67 B624 # HANGUL SYLLABLE SSANGTIKEUT-O-SSANGSIOS 8C68 B626 # HANGUL SYLLABLE SSANGTIKEUT-O-CIEUC 8C69 B627 # HANGUL SYLLABLE SSANGTIKEUT-O-CHIEUCH 8C6A B628 # HANGUL SYLLABLE SSANGTIKEUT-O-KHIEUKH 8C6B B629 # HANGUL SYLLABLE SSANGTIKEUT-O-THIEUTH 8C6C B62A # HANGUL SYLLABLE SSANGTIKEUT-O-PHIEUPH 8C6D B62B # HANGUL SYLLABLE SSANGTIKEUT-O-HIEUH 8C6E B62D # HANGUL SYLLABLE SSANGTIKEUT-WA-KIYEOK 8C6F B62E # HANGUL SYLLABLE SSANGTIKEUT-WA-SSANGKIYEOK 8C70 B62F # HANGUL SYLLABLE SSANGTIKEUT-WA-KIYEOKSIOS 8C71 B630 # HANGUL SYLLABLE SSANGTIKEUT-WA-NIEUN 8C72 B631 # HANGUL SYLLABLE SSANGTIKEUT-WA-NIEUNCIEUC 8C73 B632 # HANGUL SYLLABLE SSANGTIKEUT-WA-NIEUNHIEUH 8C74 B633 # HANGUL SYLLABLE SSANGTIKEUT-WA-TIKEUT 8C75 B635 # HANGUL SYLLABLE SSANGTIKEUT-WA-RIEULKIYEOK 8C76 B636 # HANGUL SYLLABLE SSANGTIKEUT-WA-RIEULMIEUM 8C77 B637 # HANGUL SYLLABLE SSANGTIKEUT-WA-RIEULPIEUP 8C78 B638 # HANGUL SYLLABLE SSANGTIKEUT-WA-RIEULSIOS 8C79 B639 # HANGUL SYLLABLE SSANGTIKEUT-WA-RIEULTHIEUTH 8C7A B63A # HANGUL SYLLABLE SSANGTIKEUT-WA-RIEULPHIEUPH 8C81 B63B # HANGUL SYLLABLE SSANGTIKEUT-WA-RIEULHIEUH 8C82 B63C # HANGUL SYLLABLE SSANGTIKEUT-WA-MIEUM 8C83 B63D # HANGUL SYLLABLE SSANGTIKEUT-WA-PIEUP 8C84 B63E # HANGUL SYLLABLE SSANGTIKEUT-WA-PIEUPSIOS 8C85 B63F # HANGUL SYLLABLE SSANGTIKEUT-WA-SIOS 8C86 B640 # HANGUL SYLLABLE SSANGTIKEUT-WA-SSANGSIOS 8C87 B641 # HANGUL SYLLABLE SSANGTIKEUT-WA-IEUNG 8C88 B642 # HANGUL SYLLABLE SSANGTIKEUT-WA-CIEUC 8C89 B643 # HANGUL SYLLABLE SSANGTIKEUT-WA-CHIEUCH 8C8A B644 # HANGUL SYLLABLE SSANGTIKEUT-WA-KHIEUKH 8C8B B645 # HANGUL SYLLABLE SSANGTIKEUT-WA-THIEUTH 8C8C B646 # HANGUL SYLLABLE SSANGTIKEUT-WA-PHIEUPH 8C8D B647 # HANGUL SYLLABLE SSANGTIKEUT-WA-HIEUH 8C8E B649 # HANGUL SYLLABLE SSANGTIKEUT-WAE-KIYEOK 8C8F B64A # HANGUL SYLLABLE SSANGTIKEUT-WAE-SSANGKIYEOK 8C90 B64B # HANGUL SYLLABLE SSANGTIKEUT-WAE-KIYEOKSIOS 8C91 B64C # HANGUL SYLLABLE SSANGTIKEUT-WAE-NIEUN 8C92 B64D # HANGUL SYLLABLE SSANGTIKEUT-WAE-NIEUNCIEUC 8C93 B64E # HANGUL SYLLABLE SSANGTIKEUT-WAE-NIEUNHIEUH 8C94 B64F # HANGUL SYLLABLE SSANGTIKEUT-WAE-TIKEUT 8C95 B650 # HANGUL SYLLABLE SSANGTIKEUT-WAE-RIEUL 8C96 B651 # HANGUL SYLLABLE SSANGTIKEUT-WAE-RIEULKIYEOK 8C97 B652 # HANGUL SYLLABLE SSANGTIKEUT-WAE-RIEULMIEUM 8C98 B653 # HANGUL SYLLABLE SSANGTIKEUT-WAE-RIEULPIEUP 8C99 B654 # HANGUL SYLLABLE SSANGTIKEUT-WAE-RIEULSIOS 8C9A B655 # HANGUL SYLLABLE SSANGTIKEUT-WAE-RIEULTHIEUTH 8C9B B656 # HANGUL SYLLABLE SSANGTIKEUT-WAE-RIEULPHIEUPH 8C9C B657 # HANGUL SYLLABLE SSANGTIKEUT-WAE-RIEULHIEUH 8C9D B658 # HANGUL SYLLABLE SSANGTIKEUT-WAE-MIEUM 8C9E B659 # HANGUL SYLLABLE SSANGTIKEUT-WAE-PIEUP 8C9F B65A # HANGUL SYLLABLE SSANGTIKEUT-WAE-PIEUPSIOS 8CA0 B65B # HANGUL SYLLABLE SSANGTIKEUT-WAE-SIOS 8CA1 B65C # HANGUL SYLLABLE SSANGTIKEUT-WAE-SSANGSIOS 8CA2 B65D # HANGUL SYLLABLE SSANGTIKEUT-WAE-IEUNG 8CA3 B65E # HANGUL SYLLABLE SSANGTIKEUT-WAE-CIEUC 8CA4 B65F # HANGUL SYLLABLE SSANGTIKEUT-WAE-CHIEUCH 8CA5 B660 # HANGUL SYLLABLE SSANGTIKEUT-WAE-KHIEUKH 8CA6 B661 # HANGUL SYLLABLE SSANGTIKEUT-WAE-THIEUTH 8CA7 B662 # HANGUL SYLLABLE SSANGTIKEUT-WAE-PHIEUPH 8CA8 B663 # HANGUL SYLLABLE SSANGTIKEUT-WAE-HIEUH 8CA9 B665 # HANGUL SYLLABLE SSANGTIKEUT-OE-KIYEOK 8CAA B666 # HANGUL SYLLABLE SSANGTIKEUT-OE-SSANGKIYEOK 8CAB B667 # HANGUL SYLLABLE SSANGTIKEUT-OE-KIYEOKSIOS 8CAC B669 # HANGUL SYLLABLE SSANGTIKEUT-OE-NIEUNCIEUC 8CAD B66A # HANGUL SYLLABLE SSANGTIKEUT-OE-NIEUNHIEUH 8CAE B66B # HANGUL SYLLABLE SSANGTIKEUT-OE-TIKEUT 8CAF B66C # HANGUL SYLLABLE SSANGTIKEUT-OE-RIEUL 8CB0 B66D # HANGUL SYLLABLE SSANGTIKEUT-OE-RIEULKIYEOK 8CB1 B66E # HANGUL SYLLABLE SSANGTIKEUT-OE-RIEULMIEUM 8CB2 B66F # HANGUL SYLLABLE SSANGTIKEUT-OE-RIEULPIEUP 8CB3 B670 # HANGUL SYLLABLE SSANGTIKEUT-OE-RIEULSIOS 8CB4 B671 # HANGUL SYLLABLE SSANGTIKEUT-OE-RIEULTHIEUTH 8CB5 B672 # HANGUL SYLLABLE SSANGTIKEUT-OE-RIEULPHIEUPH 8CB6 B673 # HANGUL SYLLABLE SSANGTIKEUT-OE-RIEULHIEUH 8CB7 B674 # HANGUL SYLLABLE SSANGTIKEUT-OE-MIEUM 8CB8 B675 # HANGUL SYLLABLE SSANGTIKEUT-OE-PIEUP 8CB9 B676 # HANGUL SYLLABLE SSANGTIKEUT-OE-PIEUPSIOS 8CBA B677 # HANGUL SYLLABLE SSANGTIKEUT-OE-SIOS 8CBB B678 # HANGUL SYLLABLE SSANGTIKEUT-OE-SSANGSIOS 8CBC B679 # HANGUL SYLLABLE SSANGTIKEUT-OE-IEUNG 8CBD B67A # HANGUL SYLLABLE SSANGTIKEUT-OE-CIEUC 8CBE B67B # HANGUL SYLLABLE SSANGTIKEUT-OE-CHIEUCH 8CBF B67C # HANGUL SYLLABLE SSANGTIKEUT-OE-KHIEUKH 8CC0 B67D # HANGUL SYLLABLE SSANGTIKEUT-OE-THIEUTH 8CC1 B67E # HANGUL SYLLABLE SSANGTIKEUT-OE-PHIEUPH 8CC2 B67F # HANGUL SYLLABLE SSANGTIKEUT-OE-HIEUH 8CC3 B680 # HANGUL SYLLABLE SSANGTIKEUT-YO 8CC4 B681 # HANGUL SYLLABLE SSANGTIKEUT-YO-KIYEOK 8CC5 B682 # HANGUL SYLLABLE SSANGTIKEUT-YO-SSANGKIYEOK 8CC6 B683 # HANGUL SYLLABLE SSANGTIKEUT-YO-KIYEOKSIOS 8CC7 B684 # HANGUL SYLLABLE SSANGTIKEUT-YO-NIEUN 8CC8 B685 # HANGUL SYLLABLE SSANGTIKEUT-YO-NIEUNCIEUC 8CC9 B686 # HANGUL SYLLABLE SSANGTIKEUT-YO-NIEUNHIEUH 8CCA B687 # HANGUL SYLLABLE SSANGTIKEUT-YO-TIKEUT 8CCB B688 # HANGUL SYLLABLE SSANGTIKEUT-YO-RIEUL 8CCC B689 # HANGUL SYLLABLE SSANGTIKEUT-YO-RIEULKIYEOK 8CCD B68A # HANGUL SYLLABLE SSANGTIKEUT-YO-RIEULMIEUM 8CCE B68B # HANGUL SYLLABLE SSANGTIKEUT-YO-RIEULPIEUP 8CCF B68C # HANGUL SYLLABLE SSANGTIKEUT-YO-RIEULSIOS 8CD0 B68D # HANGUL SYLLABLE SSANGTIKEUT-YO-RIEULTHIEUTH 8CD1 B68E # HANGUL SYLLABLE SSANGTIKEUT-YO-RIEULPHIEUPH 8CD2 B68F # HANGUL SYLLABLE SSANGTIKEUT-YO-RIEULHIEUH 8CD3 B690 # HANGUL SYLLABLE SSANGTIKEUT-YO-MIEUM 8CD4 B691 # HANGUL SYLLABLE SSANGTIKEUT-YO-PIEUP 8CD5 B692 # HANGUL SYLLABLE SSANGTIKEUT-YO-PIEUPSIOS 8CD6 B693 # HANGUL SYLLABLE SSANGTIKEUT-YO-SIOS 8CD7 B694 # HANGUL SYLLABLE SSANGTIKEUT-YO-SSANGSIOS 8CD8 B695 # HANGUL SYLLABLE SSANGTIKEUT-YO-IEUNG 8CD9 B696 # HANGUL SYLLABLE SSANGTIKEUT-YO-CIEUC 8CDA B697 # HANGUL SYLLABLE SSANGTIKEUT-YO-CHIEUCH 8CDB B698 # HANGUL SYLLABLE SSANGTIKEUT-YO-KHIEUKH 8CDC B699 # HANGUL SYLLABLE SSANGTIKEUT-YO-THIEUTH 8CDD B69A # HANGUL SYLLABLE SSANGTIKEUT-YO-PHIEUPH 8CDE B69B # HANGUL SYLLABLE SSANGTIKEUT-YO-HIEUH 8CDF B69E # HANGUL SYLLABLE SSANGTIKEUT-U-SSANGKIYEOK 8CE0 B69F # HANGUL SYLLABLE SSANGTIKEUT-U-KIYEOKSIOS 8CE1 B6A1 # HANGUL SYLLABLE SSANGTIKEUT-U-NIEUNCIEUC 8CE2 B6A2 # HANGUL SYLLABLE SSANGTIKEUT-U-NIEUNHIEUH 8CE3 B6A3 # HANGUL SYLLABLE SSANGTIKEUT-U-TIKEUT 8CE4 B6A5 # HANGUL SYLLABLE SSANGTIKEUT-U-RIEULKIYEOK 8CE5 B6A6 # HANGUL SYLLABLE SSANGTIKEUT-U-RIEULMIEUM 8CE6 B6A7 # HANGUL SYLLABLE SSANGTIKEUT-U-RIEULPIEUP 8CE7 B6A8 # HANGUL SYLLABLE SSANGTIKEUT-U-RIEULSIOS 8CE8 B6A9 # HANGUL SYLLABLE SSANGTIKEUT-U-RIEULTHIEUTH 8CE9 B6AA # HANGUL SYLLABLE SSANGTIKEUT-U-RIEULPHIEUPH 8CEA B6AD # HANGUL SYLLABLE SSANGTIKEUT-U-PIEUP 8CEB B6AE # HANGUL SYLLABLE SSANGTIKEUT-U-PIEUPSIOS 8CEC B6AF # HANGUL SYLLABLE SSANGTIKEUT-U-SIOS 8CED B6B0 # HANGUL SYLLABLE SSANGTIKEUT-U-SSANGSIOS 8CEE B6B2 # HANGUL SYLLABLE SSANGTIKEUT-U-CIEUC 8CEF B6B3 # HANGUL SYLLABLE SSANGTIKEUT-U-CHIEUCH 8CF0 B6B4 # HANGUL SYLLABLE SSANGTIKEUT-U-KHIEUKH 8CF1 B6B5 # HANGUL SYLLABLE SSANGTIKEUT-U-THIEUTH 8CF2 B6B6 # HANGUL SYLLABLE SSANGTIKEUT-U-PHIEUPH 8CF3 B6B7 # HANGUL SYLLABLE SSANGTIKEUT-U-HIEUH 8CF4 B6B8 # HANGUL SYLLABLE SSANGTIKEUT-WEO 8CF5 B6B9 # HANGUL SYLLABLE SSANGTIKEUT-WEO-KIYEOK 8CF6 B6BA # HANGUL SYLLABLE SSANGTIKEUT-WEO-SSANGKIYEOK 8CF7 B6BB # HANGUL SYLLABLE SSANGTIKEUT-WEO-KIYEOKSIOS 8CF8 B6BC # HANGUL SYLLABLE SSANGTIKEUT-WEO-NIEUN 8CF9 B6BD # HANGUL SYLLABLE SSANGTIKEUT-WEO-NIEUNCIEUC 8CFA B6BE # HANGUL SYLLABLE SSANGTIKEUT-WEO-NIEUNHIEUH 8CFB B6BF # HANGUL SYLLABLE SSANGTIKEUT-WEO-TIKEUT 8CFC B6C0 # HANGUL SYLLABLE SSANGTIKEUT-WEO-RIEUL 8CFD B6C1 # HANGUL SYLLABLE SSANGTIKEUT-WEO-RIEULKIYEOK 8CFE B6C2 # HANGUL SYLLABLE SSANGTIKEUT-WEO-RIEULMIEUM 8D41 B6C3 # HANGUL SYLLABLE SSANGTIKEUT-WEO-RIEULPIEUP 8D42 B6C4 # HANGUL SYLLABLE SSANGTIKEUT-WEO-RIEULSIOS 8D43 B6C5 # HANGUL SYLLABLE SSANGTIKEUT-WEO-RIEULTHIEUTH 8D44 B6C6 # HANGUL SYLLABLE SSANGTIKEUT-WEO-RIEULPHIEUPH 8D45 B6C7 # HANGUL SYLLABLE SSANGTIKEUT-WEO-RIEULHIEUH 8D46 B6C8 # HANGUL SYLLABLE SSANGTIKEUT-WEO-MIEUM 8D47 B6C9 # HANGUL SYLLABLE SSANGTIKEUT-WEO-PIEUP 8D48 B6CA # HANGUL SYLLABLE SSANGTIKEUT-WEO-PIEUPSIOS 8D49 B6CB # HANGUL SYLLABLE SSANGTIKEUT-WEO-SIOS 8D4A B6CC # HANGUL SYLLABLE SSANGTIKEUT-WEO-SSANGSIOS 8D4B B6CD # HANGUL SYLLABLE SSANGTIKEUT-WEO-IEUNG 8D4C B6CE # HANGUL SYLLABLE SSANGTIKEUT-WEO-CIEUC 8D4D B6CF # HANGUL SYLLABLE SSANGTIKEUT-WEO-CHIEUCH 8D4E B6D0 # HANGUL SYLLABLE SSANGTIKEUT-WEO-KHIEUKH 8D4F B6D1 # HANGUL SYLLABLE SSANGTIKEUT-WEO-THIEUTH 8D50 B6D2 # HANGUL SYLLABLE SSANGTIKEUT-WEO-PHIEUPH 8D51 B6D3 # HANGUL SYLLABLE SSANGTIKEUT-WEO-HIEUH 8D52 B6D5 # HANGUL SYLLABLE SSANGTIKEUT-WE-KIYEOK 8D53 B6D6 # HANGUL SYLLABLE SSANGTIKEUT-WE-SSANGKIYEOK 8D54 B6D7 # HANGUL SYLLABLE SSANGTIKEUT-WE-KIYEOKSIOS 8D55 B6D8 # HANGUL SYLLABLE SSANGTIKEUT-WE-NIEUN 8D56 B6D9 # HANGUL SYLLABLE SSANGTIKEUT-WE-NIEUNCIEUC 8D57 B6DA # HANGUL SYLLABLE SSANGTIKEUT-WE-NIEUNHIEUH 8D58 B6DB # HANGUL SYLLABLE SSANGTIKEUT-WE-TIKEUT 8D59 B6DC # HANGUL SYLLABLE SSANGTIKEUT-WE-RIEUL 8D5A B6DD # HANGUL SYLLABLE SSANGTIKEUT-WE-RIEULKIYEOK 8D61 B6DE # HANGUL SYLLABLE SSANGTIKEUT-WE-RIEULMIEUM 8D62 B6DF # HANGUL SYLLABLE SSANGTIKEUT-WE-RIEULPIEUP 8D63 B6E0 # HANGUL SYLLABLE SSANGTIKEUT-WE-RIEULSIOS 8D64 B6E1 # HANGUL SYLLABLE SSANGTIKEUT-WE-RIEULTHIEUTH 8D65 B6E2 # HANGUL SYLLABLE SSANGTIKEUT-WE-RIEULPHIEUPH 8D66 B6E3 # HANGUL SYLLABLE SSANGTIKEUT-WE-RIEULHIEUH 8D67 B6E4 # HANGUL SYLLABLE SSANGTIKEUT-WE-MIEUM 8D68 B6E5 # HANGUL SYLLABLE SSANGTIKEUT-WE-PIEUP 8D69 B6E6 # HANGUL SYLLABLE SSANGTIKEUT-WE-PIEUPSIOS 8D6A B6E7 # HANGUL SYLLABLE SSANGTIKEUT-WE-SIOS 8D6B B6E8 # HANGUL SYLLABLE SSANGTIKEUT-WE-SSANGSIOS 8D6C B6E9 # HANGUL SYLLABLE SSANGTIKEUT-WE-IEUNG 8D6D B6EA # HANGUL SYLLABLE SSANGTIKEUT-WE-CIEUC 8D6E B6EB # HANGUL SYLLABLE SSANGTIKEUT-WE-CHIEUCH 8D6F B6EC # HANGUL SYLLABLE SSANGTIKEUT-WE-KHIEUKH 8D70 B6ED # HANGUL SYLLABLE SSANGTIKEUT-WE-THIEUTH 8D71 B6EE # HANGUL SYLLABLE SSANGTIKEUT-WE-PHIEUPH 8D72 B6EF # HANGUL SYLLABLE SSANGTIKEUT-WE-HIEUH 8D73 B6F1 # HANGUL SYLLABLE SSANGTIKEUT-WI-KIYEOK 8D74 B6F2 # HANGUL SYLLABLE SSANGTIKEUT-WI-SSANGKIYEOK 8D75 B6F3 # HANGUL SYLLABLE SSANGTIKEUT-WI-KIYEOKSIOS 8D76 B6F5 # HANGUL SYLLABLE SSANGTIKEUT-WI-NIEUNCIEUC 8D77 B6F6 # HANGUL SYLLABLE SSANGTIKEUT-WI-NIEUNHIEUH 8D78 B6F7 # HANGUL SYLLABLE SSANGTIKEUT-WI-TIKEUT 8D79 B6F9 # HANGUL SYLLABLE SSANGTIKEUT-WI-RIEULKIYEOK 8D7A B6FA # HANGUL SYLLABLE SSANGTIKEUT-WI-RIEULMIEUM 8D81 B6FB # HANGUL SYLLABLE SSANGTIKEUT-WI-RIEULPIEUP 8D82 B6FC # HANGUL SYLLABLE SSANGTIKEUT-WI-RIEULSIOS 8D83 B6FD # HANGUL SYLLABLE SSANGTIKEUT-WI-RIEULTHIEUTH 8D84 B6FE # HANGUL SYLLABLE SSANGTIKEUT-WI-RIEULPHIEUPH 8D85 B6FF # HANGUL SYLLABLE SSANGTIKEUT-WI-RIEULHIEUH 8D86 B702 # HANGUL SYLLABLE SSANGTIKEUT-WI-PIEUPSIOS 8D87 B703 # HANGUL SYLLABLE SSANGTIKEUT-WI-SIOS 8D88 B704 # HANGUL SYLLABLE SSANGTIKEUT-WI-SSANGSIOS 8D89 B706 # HANGUL SYLLABLE SSANGTIKEUT-WI-CIEUC 8D8A B707 # HANGUL SYLLABLE SSANGTIKEUT-WI-CHIEUCH 8D8B B708 # HANGUL SYLLABLE SSANGTIKEUT-WI-KHIEUKH 8D8C B709 # HANGUL SYLLABLE SSANGTIKEUT-WI-THIEUTH 8D8D B70A # HANGUL SYLLABLE SSANGTIKEUT-WI-PHIEUPH 8D8E B70B # HANGUL SYLLABLE SSANGTIKEUT-WI-HIEUH 8D8F B70C # HANGUL SYLLABLE SSANGTIKEUT-YU 8D90 B70D # HANGUL SYLLABLE SSANGTIKEUT-YU-KIYEOK 8D91 B70E # HANGUL SYLLABLE SSANGTIKEUT-YU-SSANGKIYEOK 8D92 B70F # HANGUL SYLLABLE SSANGTIKEUT-YU-KIYEOKSIOS 8D93 B710 # HANGUL SYLLABLE SSANGTIKEUT-YU-NIEUN 8D94 B711 # HANGUL SYLLABLE SSANGTIKEUT-YU-NIEUNCIEUC 8D95 B712 # HANGUL SYLLABLE SSANGTIKEUT-YU-NIEUNHIEUH 8D96 B713 # HANGUL SYLLABLE SSANGTIKEUT-YU-TIKEUT 8D97 B714 # HANGUL SYLLABLE SSANGTIKEUT-YU-RIEUL 8D98 B715 # HANGUL SYLLABLE SSANGTIKEUT-YU-RIEULKIYEOK 8D99 B716 # HANGUL SYLLABLE SSANGTIKEUT-YU-RIEULMIEUM 8D9A B717 # HANGUL SYLLABLE SSANGTIKEUT-YU-RIEULPIEUP 8D9B B718 # HANGUL SYLLABLE SSANGTIKEUT-YU-RIEULSIOS 8D9C B719 # HANGUL SYLLABLE SSANGTIKEUT-YU-RIEULTHIEUTH 8D9D B71A # HANGUL SYLLABLE SSANGTIKEUT-YU-RIEULPHIEUPH 8D9E B71B # HANGUL SYLLABLE SSANGTIKEUT-YU-RIEULHIEUH 8D9F B71C # HANGUL SYLLABLE SSANGTIKEUT-YU-MIEUM 8DA0 B71D # HANGUL SYLLABLE SSANGTIKEUT-YU-PIEUP 8DA1 B71E # HANGUL SYLLABLE SSANGTIKEUT-YU-PIEUPSIOS 8DA2 B71F # HANGUL SYLLABLE SSANGTIKEUT-YU-SIOS 8DA3 B720 # HANGUL SYLLABLE SSANGTIKEUT-YU-SSANGSIOS 8DA4 B721 # HANGUL SYLLABLE SSANGTIKEUT-YU-IEUNG 8DA5 B722 # HANGUL SYLLABLE SSANGTIKEUT-YU-CIEUC 8DA6 B723 # HANGUL SYLLABLE SSANGTIKEUT-YU-CHIEUCH 8DA7 B724 # HANGUL SYLLABLE SSANGTIKEUT-YU-KHIEUKH 8DA8 B725 # HANGUL SYLLABLE SSANGTIKEUT-YU-THIEUTH 8DA9 B726 # HANGUL SYLLABLE SSANGTIKEUT-YU-PHIEUPH 8DAA B727 # HANGUL SYLLABLE SSANGTIKEUT-YU-HIEUH 8DAB B72A # HANGUL SYLLABLE SSANGTIKEUT-EU-SSANGKIYEOK 8DAC B72B # HANGUL SYLLABLE SSANGTIKEUT-EU-KIYEOKSIOS 8DAD B72D # HANGUL SYLLABLE SSANGTIKEUT-EU-NIEUNCIEUC 8DAE B72E # HANGUL SYLLABLE SSANGTIKEUT-EU-NIEUNHIEUH 8DAF B731 # HANGUL SYLLABLE SSANGTIKEUT-EU-RIEULKIYEOK 8DB0 B732 # HANGUL SYLLABLE SSANGTIKEUT-EU-RIEULMIEUM 8DB1 B733 # HANGUL SYLLABLE SSANGTIKEUT-EU-RIEULPIEUP 8DB2 B734 # HANGUL SYLLABLE SSANGTIKEUT-EU-RIEULSIOS 8DB3 B735 # HANGUL SYLLABLE SSANGTIKEUT-EU-RIEULTHIEUTH 8DB4 B736 # HANGUL SYLLABLE SSANGTIKEUT-EU-RIEULPHIEUPH 8DB5 B737 # HANGUL SYLLABLE SSANGTIKEUT-EU-RIEULHIEUH 8DB6 B73A # HANGUL SYLLABLE SSANGTIKEUT-EU-PIEUPSIOS 8DB7 B73C # HANGUL SYLLABLE SSANGTIKEUT-EU-SSANGSIOS 8DB8 B73D # HANGUL SYLLABLE SSANGTIKEUT-EU-IEUNG 8DB9 B73E # HANGUL SYLLABLE SSANGTIKEUT-EU-CIEUC 8DBA B73F # HANGUL SYLLABLE SSANGTIKEUT-EU-CHIEUCH 8DBB B740 # HANGUL SYLLABLE SSANGTIKEUT-EU-KHIEUKH 8DBC B741 # HANGUL SYLLABLE SSANGTIKEUT-EU-THIEUTH 8DBD B742 # HANGUL SYLLABLE SSANGTIKEUT-EU-PHIEUPH 8DBE B743 # HANGUL SYLLABLE SSANGTIKEUT-EU-HIEUH 8DBF B745 # HANGUL SYLLABLE SSANGTIKEUT-YI-KIYEOK 8DC0 B746 # HANGUL SYLLABLE SSANGTIKEUT-YI-SSANGKIYEOK 8DC1 B747 # HANGUL SYLLABLE SSANGTIKEUT-YI-KIYEOKSIOS 8DC2 B749 # HANGUL SYLLABLE SSANGTIKEUT-YI-NIEUNCIEUC 8DC3 B74A # HANGUL SYLLABLE SSANGTIKEUT-YI-NIEUNHIEUH 8DC4 B74B # HANGUL SYLLABLE SSANGTIKEUT-YI-TIKEUT 8DC5 B74D # HANGUL SYLLABLE SSANGTIKEUT-YI-RIEULKIYEOK 8DC6 B74E # HANGUL SYLLABLE SSANGTIKEUT-YI-RIEULMIEUM 8DC7 B74F # HANGUL SYLLABLE SSANGTIKEUT-YI-RIEULPIEUP 8DC8 B750 # HANGUL SYLLABLE SSANGTIKEUT-YI-RIEULSIOS 8DC9 B751 # HANGUL SYLLABLE SSANGTIKEUT-YI-RIEULTHIEUTH 8DCA B752 # HANGUL SYLLABLE SSANGTIKEUT-YI-RIEULPHIEUPH 8DCB B753 # HANGUL SYLLABLE SSANGTIKEUT-YI-RIEULHIEUH 8DCC B756 # HANGUL SYLLABLE SSANGTIKEUT-YI-PIEUPSIOS 8DCD B757 # HANGUL SYLLABLE SSANGTIKEUT-YI-SIOS 8DCE B758 # HANGUL SYLLABLE SSANGTIKEUT-YI-SSANGSIOS 8DCF B759 # HANGUL SYLLABLE SSANGTIKEUT-YI-IEUNG 8DD0 B75A # HANGUL SYLLABLE SSANGTIKEUT-YI-CIEUC 8DD1 B75B # HANGUL SYLLABLE SSANGTIKEUT-YI-CHIEUCH 8DD2 B75C # HANGUL SYLLABLE SSANGTIKEUT-YI-KHIEUKH 8DD3 B75D # HANGUL SYLLABLE SSANGTIKEUT-YI-THIEUTH 8DD4 B75E # HANGUL SYLLABLE SSANGTIKEUT-YI-PHIEUPH 8DD5 B75F # HANGUL SYLLABLE SSANGTIKEUT-YI-HIEUH 8DD6 B761 # HANGUL SYLLABLE SSANGTIKEUT-I-KIYEOK 8DD7 B762 # HANGUL SYLLABLE SSANGTIKEUT-I-SSANGKIYEOK 8DD8 B763 # HANGUL SYLLABLE SSANGTIKEUT-I-KIYEOKSIOS 8DD9 B765 # HANGUL SYLLABLE SSANGTIKEUT-I-NIEUNCIEUC 8DDA B766 # HANGUL SYLLABLE SSANGTIKEUT-I-NIEUNHIEUH 8DDB B767 # HANGUL SYLLABLE SSANGTIKEUT-I-TIKEUT 8DDC B769 # HANGUL SYLLABLE SSANGTIKEUT-I-RIEULKIYEOK 8DDD B76A # HANGUL SYLLABLE SSANGTIKEUT-I-RIEULMIEUM 8DDE B76B # HANGUL SYLLABLE SSANGTIKEUT-I-RIEULPIEUP 8DDF B76C # HANGUL SYLLABLE SSANGTIKEUT-I-RIEULSIOS 8DE0 B76D # HANGUL SYLLABLE SSANGTIKEUT-I-RIEULTHIEUTH 8DE1 B76E # HANGUL SYLLABLE SSANGTIKEUT-I-RIEULPHIEUPH 8DE2 B76F # HANGUL SYLLABLE SSANGTIKEUT-I-RIEULHIEUH 8DE3 B772 # HANGUL SYLLABLE SSANGTIKEUT-I-PIEUPSIOS 8DE4 B774 # HANGUL SYLLABLE SSANGTIKEUT-I-SSANGSIOS 8DE5 B776 # HANGUL SYLLABLE SSANGTIKEUT-I-CIEUC 8DE6 B777 # HANGUL SYLLABLE SSANGTIKEUT-I-CHIEUCH 8DE7 B778 # HANGUL SYLLABLE SSANGTIKEUT-I-KHIEUKH 8DE8 B779 # HANGUL SYLLABLE SSANGTIKEUT-I-THIEUTH 8DE9 B77A # HANGUL SYLLABLE SSANGTIKEUT-I-PHIEUPH 8DEA B77B # HANGUL SYLLABLE SSANGTIKEUT-I-HIEUH 8DEB B77E # HANGUL SYLLABLE RIEUL-A-SSANGKIYEOK 8DEC B77F # HANGUL SYLLABLE RIEUL-A-KIYEOKSIOS 8DED B781 # HANGUL SYLLABLE RIEUL-A-NIEUNCIEUC 8DEE B782 # HANGUL SYLLABLE RIEUL-A-NIEUNHIEUH 8DEF B783 # HANGUL SYLLABLE RIEUL-A-TIKEUT 8DF0 B785 # HANGUL SYLLABLE RIEUL-A-RIEULKIYEOK 8DF1 B786 # HANGUL SYLLABLE RIEUL-A-RIEULMIEUM 8DF2 B787 # HANGUL SYLLABLE RIEUL-A-RIEULPIEUP 8DF3 B788 # HANGUL SYLLABLE RIEUL-A-RIEULSIOS 8DF4 B789 # HANGUL SYLLABLE RIEUL-A-RIEULTHIEUTH 8DF5 B78A # HANGUL SYLLABLE RIEUL-A-RIEULPHIEUPH 8DF6 B78B # HANGUL SYLLABLE RIEUL-A-RIEULHIEUH 8DF7 B78E # HANGUL SYLLABLE RIEUL-A-PIEUPSIOS 8DF8 B793 # HANGUL SYLLABLE RIEUL-A-CHIEUCH 8DF9 B794 # HANGUL SYLLABLE RIEUL-A-KHIEUKH 8DFA B795 # HANGUL SYLLABLE RIEUL-A-THIEUTH 8DFB B79A # HANGUL SYLLABLE RIEUL-AE-SSANGKIYEOK 8DFC B79B # HANGUL SYLLABLE RIEUL-AE-KIYEOKSIOS 8DFD B79D # HANGUL SYLLABLE RIEUL-AE-NIEUNCIEUC 8DFE B79E # HANGUL SYLLABLE RIEUL-AE-NIEUNHIEUH 8E41 B79F # HANGUL SYLLABLE RIEUL-AE-TIKEUT 8E42 B7A1 # HANGUL SYLLABLE RIEUL-AE-RIEULKIYEOK 8E43 B7A2 # HANGUL SYLLABLE RIEUL-AE-RIEULMIEUM 8E44 B7A3 # HANGUL SYLLABLE RIEUL-AE-RIEULPIEUP 8E45 B7A4 # HANGUL SYLLABLE RIEUL-AE-RIEULSIOS 8E46 B7A5 # HANGUL SYLLABLE RIEUL-AE-RIEULTHIEUTH 8E47 B7A6 # HANGUL SYLLABLE RIEUL-AE-RIEULPHIEUPH 8E48 B7A7 # HANGUL SYLLABLE RIEUL-AE-RIEULHIEUH 8E49 B7AA # HANGUL SYLLABLE RIEUL-AE-PIEUPSIOS 8E4A B7AE # HANGUL SYLLABLE RIEUL-AE-CIEUC 8E4B B7AF # HANGUL SYLLABLE RIEUL-AE-CHIEUCH 8E4C B7B0 # HANGUL SYLLABLE RIEUL-AE-KHIEUKH 8E4D B7B1 # HANGUL SYLLABLE RIEUL-AE-THIEUTH 8E4E B7B2 # HANGUL SYLLABLE RIEUL-AE-PHIEUPH 8E4F B7B3 # HANGUL SYLLABLE RIEUL-AE-HIEUH 8E50 B7B6 # HANGUL SYLLABLE RIEUL-YA-SSANGKIYEOK 8E51 B7B7 # HANGUL SYLLABLE RIEUL-YA-KIYEOKSIOS 8E52 B7B9 # HANGUL SYLLABLE RIEUL-YA-NIEUNCIEUC 8E53 B7BA # HANGUL SYLLABLE RIEUL-YA-NIEUNHIEUH 8E54 B7BB # HANGUL SYLLABLE RIEUL-YA-TIKEUT 8E55 B7BC # HANGUL SYLLABLE RIEUL-YA-RIEUL 8E56 B7BD # HANGUL SYLLABLE RIEUL-YA-RIEULKIYEOK 8E57 B7BE # HANGUL SYLLABLE RIEUL-YA-RIEULMIEUM 8E58 B7BF # HANGUL SYLLABLE RIEUL-YA-RIEULPIEUP 8E59 B7C0 # HANGUL SYLLABLE RIEUL-YA-RIEULSIOS 8E5A B7C1 # HANGUL SYLLABLE RIEUL-YA-RIEULTHIEUTH 8E61 B7C2 # HANGUL SYLLABLE RIEUL-YA-RIEULPHIEUPH 8E62 B7C3 # HANGUL SYLLABLE RIEUL-YA-RIEULHIEUH 8E63 B7C4 # HANGUL SYLLABLE RIEUL-YA-MIEUM 8E64 B7C5 # HANGUL SYLLABLE RIEUL-YA-PIEUP 8E65 B7C6 # HANGUL SYLLABLE RIEUL-YA-PIEUPSIOS 8E66 B7C8 # HANGUL SYLLABLE RIEUL-YA-SSANGSIOS 8E67 B7CA # HANGUL SYLLABLE RIEUL-YA-CIEUC 8E68 B7CB # HANGUL SYLLABLE RIEUL-YA-CHIEUCH 8E69 B7CC # HANGUL SYLLABLE RIEUL-YA-KHIEUKH 8E6A B7CD # HANGUL SYLLABLE RIEUL-YA-THIEUTH 8E6B B7CE # HANGUL SYLLABLE RIEUL-YA-PHIEUPH 8E6C B7CF # HANGUL SYLLABLE RIEUL-YA-HIEUH 8E6D B7D0 # HANGUL SYLLABLE RIEUL-YAE 8E6E B7D1 # HANGUL SYLLABLE RIEUL-YAE-KIYEOK 8E6F B7D2 # HANGUL SYLLABLE RIEUL-YAE-SSANGKIYEOK 8E70 B7D3 # HANGUL SYLLABLE RIEUL-YAE-KIYEOKSIOS 8E71 B7D4 # HANGUL SYLLABLE RIEUL-YAE-NIEUN 8E72 B7D5 # HANGUL SYLLABLE RIEUL-YAE-NIEUNCIEUC 8E73 B7D6 # HANGUL SYLLABLE RIEUL-YAE-NIEUNHIEUH 8E74 B7D7 # HANGUL SYLLABLE RIEUL-YAE-TIKEUT 8E75 B7D8 # HANGUL SYLLABLE RIEUL-YAE-RIEUL 8E76 B7D9 # HANGUL SYLLABLE RIEUL-YAE-RIEULKIYEOK 8E77 B7DA # HANGUL SYLLABLE RIEUL-YAE-RIEULMIEUM 8E78 B7DB # HANGUL SYLLABLE RIEUL-YAE-RIEULPIEUP 8E79 B7DC # HANGUL SYLLABLE RIEUL-YAE-RIEULSIOS 8E7A B7DD # HANGUL SYLLABLE RIEUL-YAE-RIEULTHIEUTH 8E81 B7DE # HANGUL SYLLABLE RIEUL-YAE-RIEULPHIEUPH 8E82 B7DF # HANGUL SYLLABLE RIEUL-YAE-RIEULHIEUH 8E83 B7E0 # HANGUL SYLLABLE RIEUL-YAE-MIEUM 8E84 B7E1 # HANGUL SYLLABLE RIEUL-YAE-PIEUP 8E85 B7E2 # HANGUL SYLLABLE RIEUL-YAE-PIEUPSIOS 8E86 B7E3 # HANGUL SYLLABLE RIEUL-YAE-SIOS 8E87 B7E4 # HANGUL SYLLABLE RIEUL-YAE-SSANGSIOS 8E88 B7E5 # HANGUL SYLLABLE RIEUL-YAE-IEUNG 8E89 B7E6 # HANGUL SYLLABLE RIEUL-YAE-CIEUC 8E8A B7E7 # HANGUL SYLLABLE RIEUL-YAE-CHIEUCH 8E8B B7E8 # HANGUL SYLLABLE RIEUL-YAE-KHIEUKH 8E8C B7E9 # HANGUL SYLLABLE RIEUL-YAE-THIEUTH 8E8D B7EA # HANGUL SYLLABLE RIEUL-YAE-PHIEUPH 8E8E B7EB # HANGUL SYLLABLE RIEUL-YAE-HIEUH 8E8F B7EE # HANGUL SYLLABLE RIEUL-EO-SSANGKIYEOK 8E90 B7EF # HANGUL SYLLABLE RIEUL-EO-KIYEOKSIOS 8E91 B7F1 # HANGUL SYLLABLE RIEUL-EO-NIEUNCIEUC 8E92 B7F2 # HANGUL SYLLABLE RIEUL-EO-NIEUNHIEUH 8E93 B7F3 # HANGUL SYLLABLE RIEUL-EO-TIKEUT 8E94 B7F5 # HANGUL SYLLABLE RIEUL-EO-RIEULKIYEOK 8E95 B7F6 # HANGUL SYLLABLE RIEUL-EO-RIEULMIEUM 8E96 B7F7 # HANGUL SYLLABLE RIEUL-EO-RIEULPIEUP 8E97 B7F8 # HANGUL SYLLABLE RIEUL-EO-RIEULSIOS 8E98 B7F9 # HANGUL SYLLABLE RIEUL-EO-RIEULTHIEUTH 8E99 B7FA # HANGUL SYLLABLE RIEUL-EO-RIEULPHIEUPH 8E9A B7FB # HANGUL SYLLABLE RIEUL-EO-RIEULHIEUH 8E9B B7FE # HANGUL SYLLABLE RIEUL-EO-PIEUPSIOS 8E9C B802 # HANGUL SYLLABLE RIEUL-EO-CIEUC 8E9D B803 # HANGUL SYLLABLE RIEUL-EO-CHIEUCH 8E9E B804 # HANGUL SYLLABLE RIEUL-EO-KHIEUKH 8E9F B805 # HANGUL SYLLABLE RIEUL-EO-THIEUTH 8EA0 B806 # HANGUL SYLLABLE RIEUL-EO-PHIEUPH 8EA1 B80A # HANGUL SYLLABLE RIEUL-E-SSANGKIYEOK 8EA2 B80B # HANGUL SYLLABLE RIEUL-E-KIYEOKSIOS 8EA3 B80D # HANGUL SYLLABLE RIEUL-E-NIEUNCIEUC 8EA4 B80E # HANGUL SYLLABLE RIEUL-E-NIEUNHIEUH 8EA5 B80F # HANGUL SYLLABLE RIEUL-E-TIKEUT 8EA6 B811 # HANGUL SYLLABLE RIEUL-E-RIEULKIYEOK 8EA7 B812 # HANGUL SYLLABLE RIEUL-E-RIEULMIEUM 8EA8 B813 # HANGUL SYLLABLE RIEUL-E-RIEULPIEUP 8EA9 B814 # HANGUL SYLLABLE RIEUL-E-RIEULSIOS 8EAA B815 # HANGUL SYLLABLE RIEUL-E-RIEULTHIEUTH 8EAB B816 # HANGUL SYLLABLE RIEUL-E-RIEULPHIEUPH 8EAC B817 # HANGUL SYLLABLE RIEUL-E-RIEULHIEUH 8EAD B81A # HANGUL SYLLABLE RIEUL-E-PIEUPSIOS 8EAE B81C # HANGUL SYLLABLE RIEUL-E-SSANGSIOS 8EAF B81E # HANGUL SYLLABLE RIEUL-E-CIEUC 8EB0 B81F # HANGUL SYLLABLE RIEUL-E-CHIEUCH 8EB1 B820 # HANGUL SYLLABLE RIEUL-E-KHIEUKH 8EB2 B821 # HANGUL SYLLABLE RIEUL-E-THIEUTH 8EB3 B822 # HANGUL SYLLABLE RIEUL-E-PHIEUPH 8EB4 B823 # HANGUL SYLLABLE RIEUL-E-HIEUH 8EB5 B826 # HANGUL SYLLABLE RIEUL-YEO-SSANGKIYEOK 8EB6 B827 # HANGUL SYLLABLE RIEUL-YEO-KIYEOKSIOS 8EB7 B829 # HANGUL SYLLABLE RIEUL-YEO-NIEUNCIEUC 8EB8 B82A # HANGUL SYLLABLE RIEUL-YEO-NIEUNHIEUH 8EB9 B82B # HANGUL SYLLABLE RIEUL-YEO-TIKEUT 8EBA B82D # HANGUL SYLLABLE RIEUL-YEO-RIEULKIYEOK 8EBB B82E # HANGUL SYLLABLE RIEUL-YEO-RIEULMIEUM 8EBC B82F # HANGUL SYLLABLE RIEUL-YEO-RIEULPIEUP 8EBD B830 # HANGUL SYLLABLE RIEUL-YEO-RIEULSIOS 8EBE B831 # HANGUL SYLLABLE RIEUL-YEO-RIEULTHIEUTH 8EBF B832 # HANGUL SYLLABLE RIEUL-YEO-RIEULPHIEUPH 8EC0 B833 # HANGUL SYLLABLE RIEUL-YEO-RIEULHIEUH 8EC1 B836 # HANGUL SYLLABLE RIEUL-YEO-PIEUPSIOS 8EC2 B83A # HANGUL SYLLABLE RIEUL-YEO-CIEUC 8EC3 B83B # HANGUL SYLLABLE RIEUL-YEO-CHIEUCH 8EC4 B83C # HANGUL SYLLABLE RIEUL-YEO-KHIEUKH 8EC5 B83D # HANGUL SYLLABLE RIEUL-YEO-THIEUTH 8EC6 B83E # HANGUL SYLLABLE RIEUL-YEO-PHIEUPH 8EC7 B83F # HANGUL SYLLABLE RIEUL-YEO-HIEUH 8EC8 B841 # HANGUL SYLLABLE RIEUL-YE-KIYEOK 8EC9 B842 # HANGUL SYLLABLE RIEUL-YE-SSANGKIYEOK 8ECA B843 # HANGUL SYLLABLE RIEUL-YE-KIYEOKSIOS 8ECB B845 # HANGUL SYLLABLE RIEUL-YE-NIEUNCIEUC 8ECC B846 # HANGUL SYLLABLE RIEUL-YE-NIEUNHIEUH 8ECD B847 # HANGUL SYLLABLE RIEUL-YE-TIKEUT 8ECE B848 # HANGUL SYLLABLE RIEUL-YE-RIEUL 8ECF B849 # HANGUL SYLLABLE RIEUL-YE-RIEULKIYEOK 8ED0 B84A # HANGUL SYLLABLE RIEUL-YE-RIEULMIEUM 8ED1 B84B # HANGUL SYLLABLE RIEUL-YE-RIEULPIEUP 8ED2 B84C # HANGUL SYLLABLE RIEUL-YE-RIEULSIOS 8ED3 B84D # HANGUL SYLLABLE RIEUL-YE-RIEULTHIEUTH 8ED4 B84E # HANGUL SYLLABLE RIEUL-YE-RIEULPHIEUPH 8ED5 B84F # HANGUL SYLLABLE RIEUL-YE-RIEULHIEUH 8ED6 B850 # HANGUL SYLLABLE RIEUL-YE-MIEUM 8ED7 B852 # HANGUL SYLLABLE RIEUL-YE-PIEUPSIOS 8ED8 B854 # HANGUL SYLLABLE RIEUL-YE-SSANGSIOS 8ED9 B855 # HANGUL SYLLABLE RIEUL-YE-IEUNG 8EDA B856 # HANGUL SYLLABLE RIEUL-YE-CIEUC 8EDB B857 # HANGUL SYLLABLE RIEUL-YE-CHIEUCH 8EDC B858 # HANGUL SYLLABLE RIEUL-YE-KHIEUKH 8EDD B859 # HANGUL SYLLABLE RIEUL-YE-THIEUTH 8EDE B85A # HANGUL SYLLABLE RIEUL-YE-PHIEUPH 8EDF B85B # HANGUL SYLLABLE RIEUL-YE-HIEUH 8EE0 B85E # HANGUL SYLLABLE RIEUL-O-SSANGKIYEOK 8EE1 B85F # HANGUL SYLLABLE RIEUL-O-KIYEOKSIOS 8EE2 B861 # HANGUL SYLLABLE RIEUL-O-NIEUNCIEUC 8EE3 B862 # HANGUL SYLLABLE RIEUL-O-NIEUNHIEUH 8EE4 B863 # HANGUL SYLLABLE RIEUL-O-TIKEUT 8EE5 B865 # HANGUL SYLLABLE RIEUL-O-RIEULKIYEOK 8EE6 B866 # HANGUL SYLLABLE RIEUL-O-RIEULMIEUM 8EE7 B867 # HANGUL SYLLABLE RIEUL-O-RIEULPIEUP 8EE8 B868 # HANGUL SYLLABLE RIEUL-O-RIEULSIOS 8EE9 B869 # HANGUL SYLLABLE RIEUL-O-RIEULTHIEUTH 8EEA B86A # HANGUL SYLLABLE RIEUL-O-RIEULPHIEUPH 8EEB B86B # HANGUL SYLLABLE RIEUL-O-RIEULHIEUH 8EEC B86E # HANGUL SYLLABLE RIEUL-O-PIEUPSIOS 8EED B870 # HANGUL SYLLABLE RIEUL-O-SSANGSIOS 8EEE B872 # HANGUL SYLLABLE RIEUL-O-CIEUC 8EEF B873 # HANGUL SYLLABLE RIEUL-O-CHIEUCH 8EF0 B874 # HANGUL SYLLABLE RIEUL-O-KHIEUKH 8EF1 B875 # HANGUL SYLLABLE RIEUL-O-THIEUTH 8EF2 B876 # HANGUL SYLLABLE RIEUL-O-PHIEUPH 8EF3 B877 # HANGUL SYLLABLE RIEUL-O-HIEUH 8EF4 B879 # HANGUL SYLLABLE RIEUL-WA-KIYEOK 8EF5 B87A # HANGUL SYLLABLE RIEUL-WA-SSANGKIYEOK 8EF6 B87B # HANGUL SYLLABLE RIEUL-WA-KIYEOKSIOS 8EF7 B87D # HANGUL SYLLABLE RIEUL-WA-NIEUNCIEUC 8EF8 B87E # HANGUL SYLLABLE RIEUL-WA-NIEUNHIEUH 8EF9 B87F # HANGUL SYLLABLE RIEUL-WA-TIKEUT 8EFA B880 # HANGUL SYLLABLE RIEUL-WA-RIEUL 8EFB B881 # HANGUL SYLLABLE RIEUL-WA-RIEULKIYEOK 8EFC B882 # HANGUL SYLLABLE RIEUL-WA-RIEULMIEUM 8EFD B883 # HANGUL SYLLABLE RIEUL-WA-RIEULPIEUP 8EFE B884 # HANGUL SYLLABLE RIEUL-WA-RIEULSIOS 8F41 B885 # HANGUL SYLLABLE RIEUL-WA-RIEULTHIEUTH 8F42 B886 # HANGUL SYLLABLE RIEUL-WA-RIEULPHIEUPH 8F43 B887 # HANGUL SYLLABLE RIEUL-WA-RIEULHIEUH 8F44 B888 # HANGUL SYLLABLE RIEUL-WA-MIEUM 8F45 B889 # HANGUL SYLLABLE RIEUL-WA-PIEUP 8F46 B88A # HANGUL SYLLABLE RIEUL-WA-PIEUPSIOS 8F47 B88B # HANGUL SYLLABLE RIEUL-WA-SIOS 8F48 B88C # HANGUL SYLLABLE RIEUL-WA-SSANGSIOS 8F49 B88E # HANGUL SYLLABLE RIEUL-WA-CIEUC 8F4A B88F # HANGUL SYLLABLE RIEUL-WA-CHIEUCH 8F4B B890 # HANGUL SYLLABLE RIEUL-WA-KHIEUKH 8F4C B891 # HANGUL SYLLABLE RIEUL-WA-THIEUTH 8F4D B892 # HANGUL SYLLABLE RIEUL-WA-PHIEUPH 8F4E B893 # HANGUL SYLLABLE RIEUL-WA-HIEUH 8F4F B894 # HANGUL SYLLABLE RIEUL-WAE 8F50 B895 # HANGUL SYLLABLE RIEUL-WAE-KIYEOK 8F51 B896 # HANGUL SYLLABLE RIEUL-WAE-SSANGKIYEOK 8F52 B897 # HANGUL SYLLABLE RIEUL-WAE-KIYEOKSIOS 8F53 B898 # HANGUL SYLLABLE RIEUL-WAE-NIEUN 8F54 B899 # HANGUL SYLLABLE RIEUL-WAE-NIEUNCIEUC 8F55 B89A # HANGUL SYLLABLE RIEUL-WAE-NIEUNHIEUH 8F56 B89B # HANGUL SYLLABLE RIEUL-WAE-TIKEUT 8F57 B89C # HANGUL SYLLABLE RIEUL-WAE-RIEUL 8F58 B89D # HANGUL SYLLABLE RIEUL-WAE-RIEULKIYEOK 8F59 B89E # HANGUL SYLLABLE RIEUL-WAE-RIEULMIEUM 8F5A B89F # HANGUL SYLLABLE RIEUL-WAE-RIEULPIEUP 8F61 B8A0 # HANGUL SYLLABLE RIEUL-WAE-RIEULSIOS 8F62 B8A1 # HANGUL SYLLABLE RIEUL-WAE-RIEULTHIEUTH 8F63 B8A2 # HANGUL SYLLABLE RIEUL-WAE-RIEULPHIEUPH 8F64 B8A3 # HANGUL SYLLABLE RIEUL-WAE-RIEULHIEUH 8F65 B8A4 # HANGUL SYLLABLE RIEUL-WAE-MIEUM 8F66 B8A5 # HANGUL SYLLABLE RIEUL-WAE-PIEUP 8F67 B8A6 # HANGUL SYLLABLE RIEUL-WAE-PIEUPSIOS 8F68 B8A7 # HANGUL SYLLABLE RIEUL-WAE-SIOS 8F69 B8A9 # HANGUL SYLLABLE RIEUL-WAE-IEUNG 8F6A B8AA # HANGUL SYLLABLE RIEUL-WAE-CIEUC 8F6B B8AB # HANGUL SYLLABLE RIEUL-WAE-CHIEUCH 8F6C B8AC # HANGUL SYLLABLE RIEUL-WAE-KHIEUKH 8F6D B8AD # HANGUL SYLLABLE RIEUL-WAE-THIEUTH 8F6E B8AE # HANGUL SYLLABLE RIEUL-WAE-PHIEUPH 8F6F B8AF # HANGUL SYLLABLE RIEUL-WAE-HIEUH 8F70 B8B1 # HANGUL SYLLABLE RIEUL-OE-KIYEOK 8F71 B8B2 # HANGUL SYLLABLE RIEUL-OE-SSANGKIYEOK 8F72 B8B3 # HANGUL SYLLABLE RIEUL-OE-KIYEOKSIOS 8F73 B8B5 # HANGUL SYLLABLE RIEUL-OE-NIEUNCIEUC 8F74 B8B6 # HANGUL SYLLABLE RIEUL-OE-NIEUNHIEUH 8F75 B8B7 # HANGUL SYLLABLE RIEUL-OE-TIKEUT 8F76 B8B9 # HANGUL SYLLABLE RIEUL-OE-RIEULKIYEOK 8F77 B8BA # HANGUL SYLLABLE RIEUL-OE-RIEULMIEUM 8F78 B8BB # HANGUL SYLLABLE RIEUL-OE-RIEULPIEUP 8F79 B8BC # HANGUL SYLLABLE RIEUL-OE-RIEULSIOS 8F7A B8BD # HANGUL SYLLABLE RIEUL-OE-RIEULTHIEUTH 8F81 B8BE # HANGUL SYLLABLE RIEUL-OE-RIEULPHIEUPH 8F82 B8BF # HANGUL SYLLABLE RIEUL-OE-RIEULHIEUH 8F83 B8C2 # HANGUL SYLLABLE RIEUL-OE-PIEUPSIOS 8F84 B8C4 # HANGUL SYLLABLE RIEUL-OE-SSANGSIOS 8F85 B8C6 # HANGUL SYLLABLE RIEUL-OE-CIEUC 8F86 B8C7 # HANGUL SYLLABLE RIEUL-OE-CHIEUCH 8F87 B8C8 # HANGUL SYLLABLE RIEUL-OE-KHIEUKH 8F88 B8C9 # HANGUL SYLLABLE RIEUL-OE-THIEUTH 8F89 B8CA # HANGUL SYLLABLE RIEUL-OE-PHIEUPH 8F8A B8CB # HANGUL SYLLABLE RIEUL-OE-HIEUH 8F8B B8CD # HANGUL SYLLABLE RIEUL-YO-KIYEOK 8F8C B8CE # HANGUL SYLLABLE RIEUL-YO-SSANGKIYEOK 8F8D B8CF # HANGUL SYLLABLE RIEUL-YO-KIYEOKSIOS 8F8E B8D1 # HANGUL SYLLABLE RIEUL-YO-NIEUNCIEUC 8F8F B8D2 # HANGUL SYLLABLE RIEUL-YO-NIEUNHIEUH 8F90 B8D3 # HANGUL SYLLABLE RIEUL-YO-TIKEUT 8F91 B8D5 # HANGUL SYLLABLE RIEUL-YO-RIEULKIYEOK 8F92 B8D6 # HANGUL SYLLABLE RIEUL-YO-RIEULMIEUM 8F93 B8D7 # HANGUL SYLLABLE RIEUL-YO-RIEULPIEUP 8F94 B8D8 # HANGUL SYLLABLE RIEUL-YO-RIEULSIOS 8F95 B8D9 # HANGUL SYLLABLE RIEUL-YO-RIEULTHIEUTH 8F96 B8DA # HANGUL SYLLABLE RIEUL-YO-RIEULPHIEUPH 8F97 B8DB # HANGUL SYLLABLE RIEUL-YO-RIEULHIEUH 8F98 B8DC # HANGUL SYLLABLE RIEUL-YO-MIEUM 8F99 B8DE # HANGUL SYLLABLE RIEUL-YO-PIEUPSIOS 8F9A B8E0 # HANGUL SYLLABLE RIEUL-YO-SSANGSIOS 8F9B B8E2 # HANGUL SYLLABLE RIEUL-YO-CIEUC 8F9C B8E3 # HANGUL SYLLABLE RIEUL-YO-CHIEUCH 8F9D B8E4 # HANGUL SYLLABLE RIEUL-YO-KHIEUKH 8F9E B8E5 # HANGUL SYLLABLE RIEUL-YO-THIEUTH 8F9F B8E6 # HANGUL SYLLABLE RIEUL-YO-PHIEUPH 8FA0 B8E7 # HANGUL SYLLABLE RIEUL-YO-HIEUH 8FA1 B8EA # HANGUL SYLLABLE RIEUL-U-SSANGKIYEOK 8FA2 B8EB # HANGUL SYLLABLE RIEUL-U-KIYEOKSIOS 8FA3 B8ED # HANGUL SYLLABLE RIEUL-U-NIEUNCIEUC 8FA4 B8EE # HANGUL SYLLABLE RIEUL-U-NIEUNHIEUH 8FA5 B8EF # HANGUL SYLLABLE RIEUL-U-TIKEUT 8FA6 B8F1 # HANGUL SYLLABLE RIEUL-U-RIEULKIYEOK 8FA7 B8F2 # HANGUL SYLLABLE RIEUL-U-RIEULMIEUM 8FA8 B8F3 # HANGUL SYLLABLE RIEUL-U-RIEULPIEUP 8FA9 B8F4 # HANGUL SYLLABLE RIEUL-U-RIEULSIOS 8FAA B8F5 # HANGUL SYLLABLE RIEUL-U-RIEULTHIEUTH 8FAB B8F6 # HANGUL SYLLABLE RIEUL-U-RIEULPHIEUPH 8FAC B8F7 # HANGUL SYLLABLE RIEUL-U-RIEULHIEUH 8FAD B8FA # HANGUL SYLLABLE RIEUL-U-PIEUPSIOS 8FAE B8FC # HANGUL SYLLABLE RIEUL-U-SSANGSIOS 8FAF B8FE # HANGUL SYLLABLE RIEUL-U-CIEUC 8FB0 B8FF # HANGUL SYLLABLE RIEUL-U-CHIEUCH 8FB1 B900 # HANGUL SYLLABLE RIEUL-U-KHIEUKH 8FB2 B901 # HANGUL SYLLABLE RIEUL-U-THIEUTH 8FB3 B902 # HANGUL SYLLABLE RIEUL-U-PHIEUPH 8FB4 B903 # HANGUL SYLLABLE RIEUL-U-HIEUH 8FB5 B905 # HANGUL SYLLABLE RIEUL-WEO-KIYEOK 8FB6 B906 # HANGUL SYLLABLE RIEUL-WEO-SSANGKIYEOK 8FB7 B907 # HANGUL SYLLABLE RIEUL-WEO-KIYEOKSIOS 8FB8 B908 # HANGUL SYLLABLE RIEUL-WEO-NIEUN 8FB9 B909 # HANGUL SYLLABLE RIEUL-WEO-NIEUNCIEUC 8FBA B90A # HANGUL SYLLABLE RIEUL-WEO-NIEUNHIEUH 8FBB B90B # HANGUL SYLLABLE RIEUL-WEO-TIKEUT 8FBC B90C # HANGUL SYLLABLE RIEUL-WEO-RIEUL 8FBD B90D # HANGUL SYLLABLE RIEUL-WEO-RIEULKIYEOK 8FBE B90E # HANGUL SYLLABLE RIEUL-WEO-RIEULMIEUM 8FBF B90F # HANGUL SYLLABLE RIEUL-WEO-RIEULPIEUP 8FC0 B910 # HANGUL SYLLABLE RIEUL-WEO-RIEULSIOS 8FC1 B911 # HANGUL SYLLABLE RIEUL-WEO-RIEULTHIEUTH 8FC2 B912 # HANGUL SYLLABLE RIEUL-WEO-RIEULPHIEUPH 8FC3 B913 # HANGUL SYLLABLE RIEUL-WEO-RIEULHIEUH 8FC4 B914 # HANGUL SYLLABLE RIEUL-WEO-MIEUM 8FC5 B915 # HANGUL SYLLABLE RIEUL-WEO-PIEUP 8FC6 B916 # HANGUL SYLLABLE RIEUL-WEO-PIEUPSIOS 8FC7 B917 # HANGUL SYLLABLE RIEUL-WEO-SIOS 8FC8 B919 # HANGUL SYLLABLE RIEUL-WEO-IEUNG 8FC9 B91A # HANGUL SYLLABLE RIEUL-WEO-CIEUC 8FCA B91B # HANGUL SYLLABLE RIEUL-WEO-CHIEUCH 8FCB B91C # HANGUL SYLLABLE RIEUL-WEO-KHIEUKH 8FCC B91D # HANGUL SYLLABLE RIEUL-WEO-THIEUTH 8FCD B91E # HANGUL SYLLABLE RIEUL-WEO-PHIEUPH 8FCE B91F # HANGUL SYLLABLE RIEUL-WEO-HIEUH 8FCF B921 # HANGUL SYLLABLE RIEUL-WE-KIYEOK 8FD0 B922 # HANGUL SYLLABLE RIEUL-WE-SSANGKIYEOK 8FD1 B923 # HANGUL SYLLABLE RIEUL-WE-KIYEOKSIOS 8FD2 B924 # HANGUL SYLLABLE RIEUL-WE-NIEUN 8FD3 B925 # HANGUL SYLLABLE RIEUL-WE-NIEUNCIEUC 8FD4 B926 # HANGUL SYLLABLE RIEUL-WE-NIEUNHIEUH 8FD5 B927 # HANGUL SYLLABLE RIEUL-WE-TIKEUT 8FD6 B928 # HANGUL SYLLABLE RIEUL-WE-RIEUL 8FD7 B929 # HANGUL SYLLABLE RIEUL-WE-RIEULKIYEOK 8FD8 B92A # HANGUL SYLLABLE RIEUL-WE-RIEULMIEUM 8FD9 B92B # HANGUL SYLLABLE RIEUL-WE-RIEULPIEUP 8FDA B92C # HANGUL SYLLABLE RIEUL-WE-RIEULSIOS 8FDB B92D # HANGUL SYLLABLE RIEUL-WE-RIEULTHIEUTH 8FDC B92E # HANGUL SYLLABLE RIEUL-WE-RIEULPHIEUPH 8FDD B92F # HANGUL SYLLABLE RIEUL-WE-RIEULHIEUH 8FDE B930 # HANGUL SYLLABLE RIEUL-WE-MIEUM 8FDF B931 # HANGUL SYLLABLE RIEUL-WE-PIEUP 8FE0 B932 # HANGUL SYLLABLE RIEUL-WE-PIEUPSIOS 8FE1 B933 # HANGUL SYLLABLE RIEUL-WE-SIOS 8FE2 B934 # HANGUL SYLLABLE RIEUL-WE-SSANGSIOS 8FE3 B935 # HANGUL SYLLABLE RIEUL-WE-IEUNG 8FE4 B936 # HANGUL SYLLABLE RIEUL-WE-CIEUC 8FE5 B937 # HANGUL SYLLABLE RIEUL-WE-CHIEUCH 8FE6 B938 # HANGUL SYLLABLE RIEUL-WE-KHIEUKH 8FE7 B939 # HANGUL SYLLABLE RIEUL-WE-THIEUTH 8FE8 B93A # HANGUL SYLLABLE RIEUL-WE-PHIEUPH 8FE9 B93B # HANGUL SYLLABLE RIEUL-WE-HIEUH 8FEA B93E # HANGUL SYLLABLE RIEUL-WI-SSANGKIYEOK 8FEB B93F # HANGUL SYLLABLE RIEUL-WI-KIYEOKSIOS 8FEC B941 # HANGUL SYLLABLE RIEUL-WI-NIEUNCIEUC 8FED B942 # HANGUL SYLLABLE RIEUL-WI-NIEUNHIEUH 8FEE B943 # HANGUL SYLLABLE RIEUL-WI-TIKEUT 8FEF B945 # HANGUL SYLLABLE RIEUL-WI-RIEULKIYEOK 8FF0 B946 # HANGUL SYLLABLE RIEUL-WI-RIEULMIEUM 8FF1 B947 # HANGUL SYLLABLE RIEUL-WI-RIEULPIEUP 8FF2 B948 # HANGUL SYLLABLE RIEUL-WI-RIEULSIOS 8FF3 B949 # HANGUL SYLLABLE RIEUL-WI-RIEULTHIEUTH 8FF4 B94A # HANGUL SYLLABLE RIEUL-WI-RIEULPHIEUPH 8FF5 B94B # HANGUL SYLLABLE RIEUL-WI-RIEULHIEUH 8FF6 B94D # HANGUL SYLLABLE RIEUL-WI-PIEUP 8FF7 B94E # HANGUL SYLLABLE RIEUL-WI-PIEUPSIOS 8FF8 B950 # HANGUL SYLLABLE RIEUL-WI-SSANGSIOS 8FF9 B952 # HANGUL SYLLABLE RIEUL-WI-CIEUC 8FFA B953 # HANGUL SYLLABLE RIEUL-WI-CHIEUCH 8FFB B954 # HANGUL SYLLABLE RIEUL-WI-KHIEUKH 8FFC B955 # HANGUL SYLLABLE RIEUL-WI-THIEUTH 8FFD B956 # HANGUL SYLLABLE RIEUL-WI-PHIEUPH 8FFE B957 # HANGUL SYLLABLE RIEUL-WI-HIEUH 9041 B95A # HANGUL SYLLABLE RIEUL-YU-SSANGKIYEOK 9042 B95B # HANGUL SYLLABLE RIEUL-YU-KIYEOKSIOS 9043 B95D # HANGUL SYLLABLE RIEUL-YU-NIEUNCIEUC 9044 B95E # HANGUL SYLLABLE RIEUL-YU-NIEUNHIEUH 9045 B95F # HANGUL SYLLABLE RIEUL-YU-TIKEUT 9046 B961 # HANGUL SYLLABLE RIEUL-YU-RIEULKIYEOK 9047 B962 # HANGUL SYLLABLE RIEUL-YU-RIEULMIEUM 9048 B963 # HANGUL SYLLABLE RIEUL-YU-RIEULPIEUP 9049 B964 # HANGUL SYLLABLE RIEUL-YU-RIEULSIOS 904A B965 # HANGUL SYLLABLE RIEUL-YU-RIEULTHIEUTH 904B B966 # HANGUL SYLLABLE RIEUL-YU-RIEULPHIEUPH 904C B967 # HANGUL SYLLABLE RIEUL-YU-RIEULHIEUH 904D B96A # HANGUL SYLLABLE RIEUL-YU-PIEUPSIOS 904E B96C # HANGUL SYLLABLE RIEUL-YU-SSANGSIOS 904F B96E # HANGUL SYLLABLE RIEUL-YU-CIEUC 9050 B96F # HANGUL SYLLABLE RIEUL-YU-CHIEUCH 9051 B970 # HANGUL SYLLABLE RIEUL-YU-KHIEUKH 9052 B971 # HANGUL SYLLABLE RIEUL-YU-THIEUTH 9053 B972 # HANGUL SYLLABLE RIEUL-YU-PHIEUPH 9054 B973 # HANGUL SYLLABLE RIEUL-YU-HIEUH 9055 B976 # HANGUL SYLLABLE RIEUL-EU-SSANGKIYEOK 9056 B977 # HANGUL SYLLABLE RIEUL-EU-KIYEOKSIOS 9057 B979 # HANGUL SYLLABLE RIEUL-EU-NIEUNCIEUC 9058 B97A # HANGUL SYLLABLE RIEUL-EU-NIEUNHIEUH 9059 B97B # HANGUL SYLLABLE RIEUL-EU-TIKEUT 905A B97D # HANGUL SYLLABLE RIEUL-EU-RIEULKIYEOK 9061 B97E # HANGUL SYLLABLE RIEUL-EU-RIEULMIEUM 9062 B97F # HANGUL SYLLABLE RIEUL-EU-RIEULPIEUP 9063 B980 # HANGUL SYLLABLE RIEUL-EU-RIEULSIOS 9064 B981 # HANGUL SYLLABLE RIEUL-EU-RIEULTHIEUTH 9065 B982 # HANGUL SYLLABLE RIEUL-EU-RIEULPHIEUPH 9066 B983 # HANGUL SYLLABLE RIEUL-EU-RIEULHIEUH 9067 B986 # HANGUL SYLLABLE RIEUL-EU-PIEUPSIOS 9068 B988 # HANGUL SYLLABLE RIEUL-EU-SSANGSIOS 9069 B98B # HANGUL SYLLABLE RIEUL-EU-CHIEUCH 906A B98C # HANGUL SYLLABLE RIEUL-EU-KHIEUKH 906B B98F # HANGUL SYLLABLE RIEUL-EU-HIEUH 906C B990 # HANGUL SYLLABLE RIEUL-YI 906D B991 # HANGUL SYLLABLE RIEUL-YI-KIYEOK 906E B992 # HANGUL SYLLABLE RIEUL-YI-SSANGKIYEOK 906F B993 # HANGUL SYLLABLE RIEUL-YI-KIYEOKSIOS 9070 B994 # HANGUL SYLLABLE RIEUL-YI-NIEUN 9071 B995 # HANGUL SYLLABLE RIEUL-YI-NIEUNCIEUC 9072 B996 # HANGUL SYLLABLE RIEUL-YI-NIEUNHIEUH 9073 B997 # HANGUL SYLLABLE RIEUL-YI-TIKEUT 9074 B998 # HANGUL SYLLABLE RIEUL-YI-RIEUL 9075 B999 # HANGUL SYLLABLE RIEUL-YI-RIEULKIYEOK 9076 B99A # HANGUL SYLLABLE RIEUL-YI-RIEULMIEUM 9077 B99B # HANGUL SYLLABLE RIEUL-YI-RIEULPIEUP 9078 B99C # HANGUL SYLLABLE RIEUL-YI-RIEULSIOS 9079 B99D # HANGUL SYLLABLE RIEUL-YI-RIEULTHIEUTH 907A B99E # HANGUL SYLLABLE RIEUL-YI-RIEULPHIEUPH 9081 B99F # HANGUL SYLLABLE RIEUL-YI-RIEULHIEUH 9082 B9A0 # HANGUL SYLLABLE RIEUL-YI-MIEUM 9083 B9A1 # HANGUL SYLLABLE RIEUL-YI-PIEUP 9084 B9A2 # HANGUL SYLLABLE RIEUL-YI-PIEUPSIOS 9085 B9A3 # HANGUL SYLLABLE RIEUL-YI-SIOS 9086 B9A4 # HANGUL SYLLABLE RIEUL-YI-SSANGSIOS 9087 B9A5 # HANGUL SYLLABLE RIEUL-YI-IEUNG 9088 B9A6 # HANGUL SYLLABLE RIEUL-YI-CIEUC 9089 B9A7 # HANGUL SYLLABLE RIEUL-YI-CHIEUCH 908A B9A8 # HANGUL SYLLABLE RIEUL-YI-KHIEUKH 908B B9A9 # HANGUL SYLLABLE RIEUL-YI-THIEUTH 908C B9AA # HANGUL SYLLABLE RIEUL-YI-PHIEUPH 908D B9AB # HANGUL SYLLABLE RIEUL-YI-HIEUH 908E B9AE # HANGUL SYLLABLE RIEUL-I-SSANGKIYEOK 908F B9AF # HANGUL SYLLABLE RIEUL-I-KIYEOKSIOS 9090 B9B1 # HANGUL SYLLABLE RIEUL-I-NIEUNCIEUC 9091 B9B2 # HANGUL SYLLABLE RIEUL-I-NIEUNHIEUH 9092 B9B3 # HANGUL SYLLABLE RIEUL-I-TIKEUT 9093 B9B5 # HANGUL SYLLABLE RIEUL-I-RIEULKIYEOK 9094 B9B6 # HANGUL SYLLABLE RIEUL-I-RIEULMIEUM 9095 B9B7 # HANGUL SYLLABLE RIEUL-I-RIEULPIEUP 9096 B9B8 # HANGUL SYLLABLE RIEUL-I-RIEULSIOS 9097 B9B9 # HANGUL SYLLABLE RIEUL-I-RIEULTHIEUTH 9098 B9BA # HANGUL SYLLABLE RIEUL-I-RIEULPHIEUPH 9099 B9BB # HANGUL SYLLABLE RIEUL-I-RIEULHIEUH 909A B9BE # HANGUL SYLLABLE RIEUL-I-PIEUPSIOS 909B B9C0 # HANGUL SYLLABLE RIEUL-I-SSANGSIOS 909C B9C2 # HANGUL SYLLABLE RIEUL-I-CIEUC 909D B9C3 # HANGUL SYLLABLE RIEUL-I-CHIEUCH 909E B9C4 # HANGUL SYLLABLE RIEUL-I-KHIEUKH 909F B9C5 # HANGUL SYLLABLE RIEUL-I-THIEUTH 90A0 B9C6 # HANGUL SYLLABLE RIEUL-I-PHIEUPH 90A1 B9C7 # HANGUL SYLLABLE RIEUL-I-HIEUH 90A2 B9CA # HANGUL SYLLABLE MIEUM-A-SSANGKIYEOK 90A3 B9CB # HANGUL SYLLABLE MIEUM-A-KIYEOKSIOS 90A4 B9CD # HANGUL SYLLABLE MIEUM-A-NIEUNCIEUC 90A5 B9D3 # HANGUL SYLLABLE MIEUM-A-RIEULPIEUP 90A6 B9D4 # HANGUL SYLLABLE MIEUM-A-RIEULSIOS 90A7 B9D5 # HANGUL SYLLABLE MIEUM-A-RIEULTHIEUTH 90A8 B9D6 # HANGUL SYLLABLE MIEUM-A-RIEULPHIEUPH 90A9 B9D7 # HANGUL SYLLABLE MIEUM-A-RIEULHIEUH 90AA B9DA # HANGUL SYLLABLE MIEUM-A-PIEUPSIOS 90AB B9DC # HANGUL SYLLABLE MIEUM-A-SSANGSIOS 90AC B9DF # HANGUL SYLLABLE MIEUM-A-CHIEUCH 90AD B9E0 # HANGUL SYLLABLE MIEUM-A-KHIEUKH 90AE B9E2 # HANGUL SYLLABLE MIEUM-A-PHIEUPH 90AF B9E6 # HANGUL SYLLABLE MIEUM-AE-SSANGKIYEOK 90B0 B9E7 # HANGUL SYLLABLE MIEUM-AE-KIYEOKSIOS 90B1 B9E9 # HANGUL SYLLABLE MIEUM-AE-NIEUNCIEUC 90B2 B9EA # HANGUL SYLLABLE MIEUM-AE-NIEUNHIEUH 90B3 B9EB # HANGUL SYLLABLE MIEUM-AE-TIKEUT 90B4 B9ED # HANGUL SYLLABLE MIEUM-AE-RIEULKIYEOK 90B5 B9EE # HANGUL SYLLABLE MIEUM-AE-RIEULMIEUM 90B6 B9EF # HANGUL SYLLABLE MIEUM-AE-RIEULPIEUP 90B7 B9F0 # HANGUL SYLLABLE MIEUM-AE-RIEULSIOS 90B8 B9F1 # HANGUL SYLLABLE MIEUM-AE-RIEULTHIEUTH 90B9 B9F2 # HANGUL SYLLABLE MIEUM-AE-RIEULPHIEUPH 90BA B9F3 # HANGUL SYLLABLE MIEUM-AE-RIEULHIEUH 90BB B9F6 # HANGUL SYLLABLE MIEUM-AE-PIEUPSIOS 90BC B9FB # HANGUL SYLLABLE MIEUM-AE-CHIEUCH 90BD B9FC # HANGUL SYLLABLE MIEUM-AE-KHIEUKH 90BE B9FD # HANGUL SYLLABLE MIEUM-AE-THIEUTH 90BF B9FE # HANGUL SYLLABLE MIEUM-AE-PHIEUPH 90C0 B9FF # HANGUL SYLLABLE MIEUM-AE-HIEUH 90C1 BA02 # HANGUL SYLLABLE MIEUM-YA-SSANGKIYEOK 90C2 BA03 # HANGUL SYLLABLE MIEUM-YA-KIYEOKSIOS 90C3 BA04 # HANGUL SYLLABLE MIEUM-YA-NIEUN 90C4 BA05 # HANGUL SYLLABLE MIEUM-YA-NIEUNCIEUC 90C5 BA06 # HANGUL SYLLABLE MIEUM-YA-NIEUNHIEUH 90C6 BA07 # HANGUL SYLLABLE MIEUM-YA-TIKEUT 90C7 BA09 # HANGUL SYLLABLE MIEUM-YA-RIEULKIYEOK 90C8 BA0A # HANGUL SYLLABLE MIEUM-YA-RIEULMIEUM 90C9 BA0B # HANGUL SYLLABLE MIEUM-YA-RIEULPIEUP 90CA BA0C # HANGUL SYLLABLE MIEUM-YA-RIEULSIOS 90CB BA0D # HANGUL SYLLABLE MIEUM-YA-RIEULTHIEUTH 90CC BA0E # HANGUL SYLLABLE MIEUM-YA-RIEULPHIEUPH 90CD BA0F # HANGUL SYLLABLE MIEUM-YA-RIEULHIEUH 90CE BA10 # HANGUL SYLLABLE MIEUM-YA-MIEUM 90CF BA11 # HANGUL SYLLABLE MIEUM-YA-PIEUP 90D0 BA12 # HANGUL SYLLABLE MIEUM-YA-PIEUPSIOS 90D1 BA13 # HANGUL SYLLABLE MIEUM-YA-SIOS 90D2 BA14 # HANGUL SYLLABLE MIEUM-YA-SSANGSIOS 90D3 BA16 # HANGUL SYLLABLE MIEUM-YA-CIEUC 90D4 BA17 # HANGUL SYLLABLE MIEUM-YA-CHIEUCH 90D5 BA18 # HANGUL SYLLABLE MIEUM-YA-KHIEUKH 90D6 BA19 # HANGUL SYLLABLE MIEUM-YA-THIEUTH 90D7 BA1A # HANGUL SYLLABLE MIEUM-YA-PHIEUPH 90D8 BA1B # HANGUL SYLLABLE MIEUM-YA-HIEUH 90D9 BA1C # HANGUL SYLLABLE MIEUM-YAE 90DA BA1D # HANGUL SYLLABLE MIEUM-YAE-KIYEOK 90DB BA1E # HANGUL SYLLABLE MIEUM-YAE-SSANGKIYEOK 90DC BA1F # HANGUL SYLLABLE MIEUM-YAE-KIYEOKSIOS 90DD BA20 # HANGUL SYLLABLE MIEUM-YAE-NIEUN 90DE BA21 # HANGUL SYLLABLE MIEUM-YAE-NIEUNCIEUC 90DF BA22 # HANGUL SYLLABLE MIEUM-YAE-NIEUNHIEUH 90E0 BA23 # HANGUL SYLLABLE MIEUM-YAE-TIKEUT 90E1 BA24 # HANGUL SYLLABLE MIEUM-YAE-RIEUL 90E2 BA25 # HANGUL SYLLABLE MIEUM-YAE-RIEULKIYEOK 90E3 BA26 # HANGUL SYLLABLE MIEUM-YAE-RIEULMIEUM 90E4 BA27 # HANGUL SYLLABLE MIEUM-YAE-RIEULPIEUP 90E5 BA28 # HANGUL SYLLABLE MIEUM-YAE-RIEULSIOS 90E6 BA29 # HANGUL SYLLABLE MIEUM-YAE-RIEULTHIEUTH 90E7 BA2A # HANGUL SYLLABLE MIEUM-YAE-RIEULPHIEUPH 90E8 BA2B # HANGUL SYLLABLE MIEUM-YAE-RIEULHIEUH 90E9 BA2C # HANGUL SYLLABLE MIEUM-YAE-MIEUM 90EA BA2D # HANGUL SYLLABLE MIEUM-YAE-PIEUP 90EB BA2E # HANGUL SYLLABLE MIEUM-YAE-PIEUPSIOS 90EC BA2F # HANGUL SYLLABLE MIEUM-YAE-SIOS 90ED BA30 # HANGUL SYLLABLE MIEUM-YAE-SSANGSIOS 90EE BA31 # HANGUL SYLLABLE MIEUM-YAE-IEUNG 90EF BA32 # HANGUL SYLLABLE MIEUM-YAE-CIEUC 90F0 BA33 # HANGUL SYLLABLE MIEUM-YAE-CHIEUCH 90F1 BA34 # HANGUL SYLLABLE MIEUM-YAE-KHIEUKH 90F2 BA35 # HANGUL SYLLABLE MIEUM-YAE-THIEUTH 90F3 BA36 # HANGUL SYLLABLE MIEUM-YAE-PHIEUPH 90F4 BA37 # HANGUL SYLLABLE MIEUM-YAE-HIEUH 90F5 BA3A # HANGUL SYLLABLE MIEUM-EO-SSANGKIYEOK 90F6 BA3B # HANGUL SYLLABLE MIEUM-EO-KIYEOKSIOS 90F7 BA3D # HANGUL SYLLABLE MIEUM-EO-NIEUNCIEUC 90F8 BA3E # HANGUL SYLLABLE MIEUM-EO-NIEUNHIEUH 90F9 BA3F # HANGUL SYLLABLE MIEUM-EO-TIKEUT 90FA BA41 # HANGUL SYLLABLE MIEUM-EO-RIEULKIYEOK 90FB BA43 # HANGUL SYLLABLE MIEUM-EO-RIEULPIEUP 90FC BA44 # HANGUL SYLLABLE MIEUM-EO-RIEULSIOS 90FD BA45 # HANGUL SYLLABLE MIEUM-EO-RIEULTHIEUTH 90FE BA46 # HANGUL SYLLABLE MIEUM-EO-RIEULPHIEUPH 9141 BA47 # HANGUL SYLLABLE MIEUM-EO-RIEULHIEUH 9142 BA4A # HANGUL SYLLABLE MIEUM-EO-PIEUPSIOS 9143 BA4C # HANGUL SYLLABLE MIEUM-EO-SSANGSIOS 9144 BA4F # HANGUL SYLLABLE MIEUM-EO-CHIEUCH 9145 BA50 # HANGUL SYLLABLE MIEUM-EO-KHIEUKH 9146 BA51 # HANGUL SYLLABLE MIEUM-EO-THIEUTH 9147 BA52 # HANGUL SYLLABLE MIEUM-EO-PHIEUPH 9148 BA56 # HANGUL SYLLABLE MIEUM-E-SSANGKIYEOK 9149 BA57 # HANGUL SYLLABLE MIEUM-E-KIYEOKSIOS 914A BA59 # HANGUL SYLLABLE MIEUM-E-NIEUNCIEUC 914B BA5A # HANGUL SYLLABLE MIEUM-E-NIEUNHIEUH 914C BA5B # HANGUL SYLLABLE MIEUM-E-TIKEUT 914D BA5D # HANGUL SYLLABLE MIEUM-E-RIEULKIYEOK 914E BA5E # HANGUL SYLLABLE MIEUM-E-RIEULMIEUM 914F BA5F # HANGUL SYLLABLE MIEUM-E-RIEULPIEUP 9150 BA60 # HANGUL SYLLABLE MIEUM-E-RIEULSIOS 9151 BA61 # HANGUL SYLLABLE MIEUM-E-RIEULTHIEUTH 9152 BA62 # HANGUL SYLLABLE MIEUM-E-RIEULPHIEUPH 9153 BA63 # HANGUL SYLLABLE MIEUM-E-RIEULHIEUH 9154 BA66 # HANGUL SYLLABLE MIEUM-E-PIEUPSIOS 9155 BA6A # HANGUL SYLLABLE MIEUM-E-CIEUC 9156 BA6B # HANGUL SYLLABLE MIEUM-E-CHIEUCH 9157 BA6C # HANGUL SYLLABLE MIEUM-E-KHIEUKH 9158 BA6D # HANGUL SYLLABLE MIEUM-E-THIEUTH 9159 BA6E # HANGUL SYLLABLE MIEUM-E-PHIEUPH 915A BA6F # HANGUL SYLLABLE MIEUM-E-HIEUH 9161 BA72 # HANGUL SYLLABLE MIEUM-YEO-SSANGKIYEOK 9162 BA73 # HANGUL SYLLABLE MIEUM-YEO-KIYEOKSIOS 9163 BA75 # HANGUL SYLLABLE MIEUM-YEO-NIEUNCIEUC 9164 BA76 # HANGUL SYLLABLE MIEUM-YEO-NIEUNHIEUH 9165 BA77 # HANGUL SYLLABLE MIEUM-YEO-TIKEUT 9166 BA79 # HANGUL SYLLABLE MIEUM-YEO-RIEULKIYEOK 9167 BA7A # HANGUL SYLLABLE MIEUM-YEO-RIEULMIEUM 9168 BA7B # HANGUL SYLLABLE MIEUM-YEO-RIEULPIEUP 9169 BA7C # HANGUL SYLLABLE MIEUM-YEO-RIEULSIOS 916A BA7D # HANGUL SYLLABLE MIEUM-YEO-RIEULTHIEUTH 916B BA7E # HANGUL SYLLABLE MIEUM-YEO-RIEULPHIEUPH 916C BA7F # HANGUL SYLLABLE MIEUM-YEO-RIEULHIEUH 916D BA80 # HANGUL SYLLABLE MIEUM-YEO-MIEUM 916E BA81 # HANGUL SYLLABLE MIEUM-YEO-PIEUP 916F BA82 # HANGUL SYLLABLE MIEUM-YEO-PIEUPSIOS 9170 BA86 # HANGUL SYLLABLE MIEUM-YEO-CIEUC 9171 BA88 # HANGUL SYLLABLE MIEUM-YEO-KHIEUKH 9172 BA89 # HANGUL SYLLABLE MIEUM-YEO-THIEUTH 9173 BA8A # HANGUL SYLLABLE MIEUM-YEO-PHIEUPH 9174 BA8B # HANGUL SYLLABLE MIEUM-YEO-HIEUH 9175 BA8D # HANGUL SYLLABLE MIEUM-YE-KIYEOK 9176 BA8E # HANGUL SYLLABLE MIEUM-YE-SSANGKIYEOK 9177 BA8F # HANGUL SYLLABLE MIEUM-YE-KIYEOKSIOS 9178 BA90 # HANGUL SYLLABLE MIEUM-YE-NIEUN 9179 BA91 # HANGUL SYLLABLE MIEUM-YE-NIEUNCIEUC 917A BA92 # HANGUL SYLLABLE MIEUM-YE-NIEUNHIEUH 9181 BA93 # HANGUL SYLLABLE MIEUM-YE-TIKEUT 9182 BA94 # HANGUL SYLLABLE MIEUM-YE-RIEUL 9183 BA95 # HANGUL SYLLABLE MIEUM-YE-RIEULKIYEOK 9184 BA96 # HANGUL SYLLABLE MIEUM-YE-RIEULMIEUM 9185 BA97 # HANGUL SYLLABLE MIEUM-YE-RIEULPIEUP 9186 BA98 # HANGUL SYLLABLE MIEUM-YE-RIEULSIOS 9187 BA99 # HANGUL SYLLABLE MIEUM-YE-RIEULTHIEUTH 9188 BA9A # HANGUL SYLLABLE MIEUM-YE-RIEULPHIEUPH 9189 BA9B # HANGUL SYLLABLE MIEUM-YE-RIEULHIEUH 918A BA9C # HANGUL SYLLABLE MIEUM-YE-MIEUM 918B BA9D # HANGUL SYLLABLE MIEUM-YE-PIEUP 918C BA9E # HANGUL SYLLABLE MIEUM-YE-PIEUPSIOS 918D BA9F # HANGUL SYLLABLE MIEUM-YE-SIOS 918E BAA0 # HANGUL SYLLABLE MIEUM-YE-SSANGSIOS 918F BAA1 # HANGUL SYLLABLE MIEUM-YE-IEUNG 9190 BAA2 # HANGUL SYLLABLE MIEUM-YE-CIEUC 9191 BAA3 # HANGUL SYLLABLE MIEUM-YE-CHIEUCH 9192 BAA4 # HANGUL SYLLABLE MIEUM-YE-KHIEUKH 9193 BAA5 # HANGUL SYLLABLE MIEUM-YE-THIEUTH 9194 BAA6 # HANGUL SYLLABLE MIEUM-YE-PHIEUPH 9195 BAA7 # HANGUL SYLLABLE MIEUM-YE-HIEUH 9196 BAAA # HANGUL SYLLABLE MIEUM-O-SSANGKIYEOK 9197 BAAD # HANGUL SYLLABLE MIEUM-O-NIEUNCIEUC 9198 BAAE # HANGUL SYLLABLE MIEUM-O-NIEUNHIEUH 9199 BAAF # HANGUL SYLLABLE MIEUM-O-TIKEUT 919A BAB1 # HANGUL SYLLABLE MIEUM-O-RIEULKIYEOK 919B BAB3 # HANGUL SYLLABLE MIEUM-O-RIEULPIEUP 919C BAB4 # HANGUL SYLLABLE MIEUM-O-RIEULSIOS 919D BAB5 # HANGUL SYLLABLE MIEUM-O-RIEULTHIEUTH 919E BAB6 # HANGUL SYLLABLE MIEUM-O-RIEULPHIEUPH 919F BAB7 # HANGUL SYLLABLE MIEUM-O-RIEULHIEUH 91A0 BABA # HANGUL SYLLABLE MIEUM-O-PIEUPSIOS 91A1 BABC # HANGUL SYLLABLE MIEUM-O-SSANGSIOS 91A2 BABE # HANGUL SYLLABLE MIEUM-O-CIEUC 91A3 BABF # HANGUL SYLLABLE MIEUM-O-CHIEUCH 91A4 BAC0 # HANGUL SYLLABLE MIEUM-O-KHIEUKH 91A5 BAC1 # HANGUL SYLLABLE MIEUM-O-THIEUTH 91A6 BAC2 # HANGUL SYLLABLE MIEUM-O-PHIEUPH 91A7 BAC3 # HANGUL SYLLABLE MIEUM-O-HIEUH 91A8 BAC5 # HANGUL SYLLABLE MIEUM-WA-KIYEOK 91A9 BAC6 # HANGUL SYLLABLE MIEUM-WA-SSANGKIYEOK 91AA BAC7 # HANGUL SYLLABLE MIEUM-WA-KIYEOKSIOS 91AB BAC9 # HANGUL SYLLABLE MIEUM-WA-NIEUNCIEUC 91AC BACA # HANGUL SYLLABLE MIEUM-WA-NIEUNHIEUH 91AD BACB # HANGUL SYLLABLE MIEUM-WA-TIKEUT 91AE BACC # HANGUL SYLLABLE MIEUM-WA-RIEUL 91AF BACD # HANGUL SYLLABLE MIEUM-WA-RIEULKIYEOK 91B0 BACE # HANGUL SYLLABLE MIEUM-WA-RIEULMIEUM 91B1 BACF # HANGUL SYLLABLE MIEUM-WA-RIEULPIEUP 91B2 BAD0 # HANGUL SYLLABLE MIEUM-WA-RIEULSIOS 91B3 BAD1 # HANGUL SYLLABLE MIEUM-WA-RIEULTHIEUTH 91B4 BAD2 # HANGUL SYLLABLE MIEUM-WA-RIEULPHIEUPH 91B5 BAD3 # HANGUL SYLLABLE MIEUM-WA-RIEULHIEUH 91B6 BAD4 # HANGUL SYLLABLE MIEUM-WA-MIEUM 91B7 BAD5 # HANGUL SYLLABLE MIEUM-WA-PIEUP 91B8 BAD6 # HANGUL SYLLABLE MIEUM-WA-PIEUPSIOS 91B9 BAD7 # HANGUL SYLLABLE MIEUM-WA-SIOS 91BA BADA # HANGUL SYLLABLE MIEUM-WA-CIEUC 91BB BADB # HANGUL SYLLABLE MIEUM-WA-CHIEUCH 91BC BADC # HANGUL SYLLABLE MIEUM-WA-KHIEUKH 91BD BADD # HANGUL SYLLABLE MIEUM-WA-THIEUTH 91BE BADE # HANGUL SYLLABLE MIEUM-WA-PHIEUPH 91BF BADF # HANGUL SYLLABLE MIEUM-WA-HIEUH 91C0 BAE0 # HANGUL SYLLABLE MIEUM-WAE 91C1 BAE1 # HANGUL SYLLABLE MIEUM-WAE-KIYEOK 91C2 BAE2 # HANGUL SYLLABLE MIEUM-WAE-SSANGKIYEOK 91C3 BAE3 # HANGUL SYLLABLE MIEUM-WAE-KIYEOKSIOS 91C4 BAE4 # HANGUL SYLLABLE MIEUM-WAE-NIEUN 91C5 BAE5 # HANGUL SYLLABLE MIEUM-WAE-NIEUNCIEUC 91C6 BAE6 # HANGUL SYLLABLE MIEUM-WAE-NIEUNHIEUH 91C7 BAE7 # HANGUL SYLLABLE MIEUM-WAE-TIKEUT 91C8 BAE8 # HANGUL SYLLABLE MIEUM-WAE-RIEUL 91C9 BAE9 # HANGUL SYLLABLE MIEUM-WAE-RIEULKIYEOK 91CA BAEA # HANGUL SYLLABLE MIEUM-WAE-RIEULMIEUM 91CB BAEB # HANGUL SYLLABLE MIEUM-WAE-RIEULPIEUP 91CC BAEC # HANGUL SYLLABLE MIEUM-WAE-RIEULSIOS 91CD BAED # HANGUL SYLLABLE MIEUM-WAE-RIEULTHIEUTH 91CE BAEE # HANGUL SYLLABLE MIEUM-WAE-RIEULPHIEUPH 91CF BAEF # HANGUL SYLLABLE MIEUM-WAE-RIEULHIEUH 91D0 BAF0 # HANGUL SYLLABLE MIEUM-WAE-MIEUM 91D1 BAF1 # HANGUL SYLLABLE MIEUM-WAE-PIEUP 91D2 BAF2 # HANGUL SYLLABLE MIEUM-WAE-PIEUPSIOS 91D3 BAF3 # HANGUL SYLLABLE MIEUM-WAE-SIOS 91D4 BAF4 # HANGUL SYLLABLE MIEUM-WAE-SSANGSIOS 91D5 BAF5 # HANGUL SYLLABLE MIEUM-WAE-IEUNG 91D6 BAF6 # HANGUL SYLLABLE MIEUM-WAE-CIEUC 91D7 BAF7 # HANGUL SYLLABLE MIEUM-WAE-CHIEUCH 91D8 BAF8 # HANGUL SYLLABLE MIEUM-WAE-KHIEUKH 91D9 BAF9 # HANGUL SYLLABLE MIEUM-WAE-THIEUTH 91DA BAFA # HANGUL SYLLABLE MIEUM-WAE-PHIEUPH 91DB BAFB # HANGUL SYLLABLE MIEUM-WAE-HIEUH 91DC BAFD # HANGUL SYLLABLE MIEUM-OE-KIYEOK 91DD BAFE # HANGUL SYLLABLE MIEUM-OE-SSANGKIYEOK 91DE BAFF # HANGUL SYLLABLE MIEUM-OE-KIYEOKSIOS 91DF BB01 # HANGUL SYLLABLE MIEUM-OE-NIEUNCIEUC 91E0 BB02 # HANGUL SYLLABLE MIEUM-OE-NIEUNHIEUH 91E1 BB03 # HANGUL SYLLABLE MIEUM-OE-TIKEUT 91E2 BB05 # HANGUL SYLLABLE MIEUM-OE-RIEULKIYEOK 91E3 BB06 # HANGUL SYLLABLE MIEUM-OE-RIEULMIEUM 91E4 BB07 # HANGUL SYLLABLE MIEUM-OE-RIEULPIEUP 91E5 BB08 # HANGUL SYLLABLE MIEUM-OE-RIEULSIOS 91E6 BB09 # HANGUL SYLLABLE MIEUM-OE-RIEULTHIEUTH 91E7 BB0A # HANGUL SYLLABLE MIEUM-OE-RIEULPHIEUPH 91E8 BB0B # HANGUL SYLLABLE MIEUM-OE-RIEULHIEUH 91E9 BB0C # HANGUL SYLLABLE MIEUM-OE-MIEUM 91EA BB0E # HANGUL SYLLABLE MIEUM-OE-PIEUPSIOS 91EB BB10 # HANGUL SYLLABLE MIEUM-OE-SSANGSIOS 91EC BB12 # HANGUL SYLLABLE MIEUM-OE-CIEUC 91ED BB13 # HANGUL SYLLABLE MIEUM-OE-CHIEUCH 91EE BB14 # HANGUL SYLLABLE MIEUM-OE-KHIEUKH 91EF BB15 # HANGUL SYLLABLE MIEUM-OE-THIEUTH 91F0 BB16 # HANGUL SYLLABLE MIEUM-OE-PHIEUPH 91F1 BB17 # HANGUL SYLLABLE MIEUM-OE-HIEUH 91F2 BB19 # HANGUL SYLLABLE MIEUM-YO-KIYEOK 91F3 BB1A # HANGUL SYLLABLE MIEUM-YO-SSANGKIYEOK 91F4 BB1B # HANGUL SYLLABLE MIEUM-YO-KIYEOKSIOS 91F5 BB1D # HANGUL SYLLABLE MIEUM-YO-NIEUNCIEUC 91F6 BB1E # HANGUL SYLLABLE MIEUM-YO-NIEUNHIEUH 91F7 BB1F # HANGUL SYLLABLE MIEUM-YO-TIKEUT 91F8 BB21 # HANGUL SYLLABLE MIEUM-YO-RIEULKIYEOK 91F9 BB22 # HANGUL SYLLABLE MIEUM-YO-RIEULMIEUM 91FA BB23 # HANGUL SYLLABLE MIEUM-YO-RIEULPIEUP 91FB BB24 # HANGUL SYLLABLE MIEUM-YO-RIEULSIOS 91FC BB25 # HANGUL SYLLABLE MIEUM-YO-RIEULTHIEUTH 91FD BB26 # HANGUL SYLLABLE MIEUM-YO-RIEULPHIEUPH 91FE BB27 # HANGUL SYLLABLE MIEUM-YO-RIEULHIEUH 9241 BB28 # HANGUL SYLLABLE MIEUM-YO-MIEUM 9242 BB2A # HANGUL SYLLABLE MIEUM-YO-PIEUPSIOS 9243 BB2C # HANGUL SYLLABLE MIEUM-YO-SSANGSIOS 9244 BB2D # HANGUL SYLLABLE MIEUM-YO-IEUNG 9245 BB2E # HANGUL SYLLABLE MIEUM-YO-CIEUC 9246 BB2F # HANGUL SYLLABLE MIEUM-YO-CHIEUCH 9247 BB30 # HANGUL SYLLABLE MIEUM-YO-KHIEUKH 9248 BB31 # HANGUL SYLLABLE MIEUM-YO-THIEUTH 9249 BB32 # HANGUL SYLLABLE MIEUM-YO-PHIEUPH 924A BB33 # HANGUL SYLLABLE MIEUM-YO-HIEUH 924B BB37 # HANGUL SYLLABLE MIEUM-U-KIYEOKSIOS 924C BB39 # HANGUL SYLLABLE MIEUM-U-NIEUNCIEUC 924D BB3A # HANGUL SYLLABLE MIEUM-U-NIEUNHIEUH 924E BB3F # HANGUL SYLLABLE MIEUM-U-RIEULPIEUP 924F BB40 # HANGUL SYLLABLE MIEUM-U-RIEULSIOS 9250 BB41 # HANGUL SYLLABLE MIEUM-U-RIEULTHIEUTH 9251 BB42 # HANGUL SYLLABLE MIEUM-U-RIEULPHIEUPH 9252 BB43 # HANGUL SYLLABLE MIEUM-U-RIEULHIEUH 9253 BB46 # HANGUL SYLLABLE MIEUM-U-PIEUPSIOS 9254 BB48 # HANGUL SYLLABLE MIEUM-U-SSANGSIOS 9255 BB4A # HANGUL SYLLABLE MIEUM-U-CIEUC 9256 BB4B # HANGUL SYLLABLE MIEUM-U-CHIEUCH 9257 BB4C # HANGUL SYLLABLE MIEUM-U-KHIEUKH 9258 BB4E # HANGUL SYLLABLE MIEUM-U-PHIEUPH 9259 BB51 # HANGUL SYLLABLE MIEUM-WEO-KIYEOK 925A BB52 # HANGUL SYLLABLE MIEUM-WEO-SSANGKIYEOK 9261 BB53 # HANGUL SYLLABLE MIEUM-WEO-KIYEOKSIOS 9262 BB55 # HANGUL SYLLABLE MIEUM-WEO-NIEUNCIEUC 9263 BB56 # HANGUL SYLLABLE MIEUM-WEO-NIEUNHIEUH 9264 BB57 # HANGUL SYLLABLE MIEUM-WEO-TIKEUT 9265 BB59 # HANGUL SYLLABLE MIEUM-WEO-RIEULKIYEOK 9266 BB5A # HANGUL SYLLABLE MIEUM-WEO-RIEULMIEUM 9267 BB5B # HANGUL SYLLABLE MIEUM-WEO-RIEULPIEUP 9268 BB5C # HANGUL SYLLABLE MIEUM-WEO-RIEULSIOS 9269 BB5D # HANGUL SYLLABLE MIEUM-WEO-RIEULTHIEUTH 926A BB5E # HANGUL SYLLABLE MIEUM-WEO-RIEULPHIEUPH 926B BB5F # HANGUL SYLLABLE MIEUM-WEO-RIEULHIEUH 926C BB60 # HANGUL SYLLABLE MIEUM-WEO-MIEUM 926D BB62 # HANGUL SYLLABLE MIEUM-WEO-PIEUPSIOS 926E BB64 # HANGUL SYLLABLE MIEUM-WEO-SSANGSIOS 926F BB65 # HANGUL SYLLABLE MIEUM-WEO-IEUNG 9270 BB66 # HANGUL SYLLABLE MIEUM-WEO-CIEUC 9271 BB67 # HANGUL SYLLABLE MIEUM-WEO-CHIEUCH 9272 BB68 # HANGUL SYLLABLE MIEUM-WEO-KHIEUKH 9273 BB69 # HANGUL SYLLABLE MIEUM-WEO-THIEUTH 9274 BB6A # HANGUL SYLLABLE MIEUM-WEO-PHIEUPH 9275 BB6B # HANGUL SYLLABLE MIEUM-WEO-HIEUH 9276 BB6D # HANGUL SYLLABLE MIEUM-WE-KIYEOK 9277 BB6E # HANGUL SYLLABLE MIEUM-WE-SSANGKIYEOK 9278 BB6F # HANGUL SYLLABLE MIEUM-WE-KIYEOKSIOS 9279 BB70 # HANGUL SYLLABLE MIEUM-WE-NIEUN 927A BB71 # HANGUL SYLLABLE MIEUM-WE-NIEUNCIEUC 9281 BB72 # HANGUL SYLLABLE MIEUM-WE-NIEUNHIEUH 9282 BB73 # HANGUL SYLLABLE MIEUM-WE-TIKEUT 9283 BB74 # HANGUL SYLLABLE MIEUM-WE-RIEUL 9284 BB75 # HANGUL SYLLABLE MIEUM-WE-RIEULKIYEOK 9285 BB76 # HANGUL SYLLABLE MIEUM-WE-RIEULMIEUM 9286 BB77 # HANGUL SYLLABLE MIEUM-WE-RIEULPIEUP 9287 BB78 # HANGUL SYLLABLE MIEUM-WE-RIEULSIOS 9288 BB79 # HANGUL SYLLABLE MIEUM-WE-RIEULTHIEUTH 9289 BB7A # HANGUL SYLLABLE MIEUM-WE-RIEULPHIEUPH 928A BB7B # HANGUL SYLLABLE MIEUM-WE-RIEULHIEUH 928B BB7C # HANGUL SYLLABLE MIEUM-WE-MIEUM 928C BB7D # HANGUL SYLLABLE MIEUM-WE-PIEUP 928D BB7E # HANGUL SYLLABLE MIEUM-WE-PIEUPSIOS 928E BB7F # HANGUL SYLLABLE MIEUM-WE-SIOS 928F BB80 # HANGUL SYLLABLE MIEUM-WE-SSANGSIOS 9290 BB81 # HANGUL SYLLABLE MIEUM-WE-IEUNG 9291 BB82 # HANGUL SYLLABLE MIEUM-WE-CIEUC 9292 BB83 # HANGUL SYLLABLE MIEUM-WE-CHIEUCH 9293 BB84 # HANGUL SYLLABLE MIEUM-WE-KHIEUKH 9294 BB85 # HANGUL SYLLABLE MIEUM-WE-THIEUTH 9295 BB86 # HANGUL SYLLABLE MIEUM-WE-PHIEUPH 9296 BB87 # HANGUL SYLLABLE MIEUM-WE-HIEUH 9297 BB89 # HANGUL SYLLABLE MIEUM-WI-KIYEOK 9298 BB8A # HANGUL SYLLABLE MIEUM-WI-SSANGKIYEOK 9299 BB8B # HANGUL SYLLABLE MIEUM-WI-KIYEOKSIOS 929A BB8D # HANGUL SYLLABLE MIEUM-WI-NIEUNCIEUC 929B BB8E # HANGUL SYLLABLE MIEUM-WI-NIEUNHIEUH 929C BB8F # HANGUL SYLLABLE MIEUM-WI-TIKEUT 929D BB91 # HANGUL SYLLABLE MIEUM-WI-RIEULKIYEOK 929E BB92 # HANGUL SYLLABLE MIEUM-WI-RIEULMIEUM 929F BB93 # HANGUL SYLLABLE MIEUM-WI-RIEULPIEUP 92A0 BB94 # HANGUL SYLLABLE MIEUM-WI-RIEULSIOS 92A1 BB95 # HANGUL SYLLABLE MIEUM-WI-RIEULTHIEUTH 92A2 BB96 # HANGUL SYLLABLE MIEUM-WI-RIEULPHIEUPH 92A3 BB97 # HANGUL SYLLABLE MIEUM-WI-RIEULHIEUH 92A4 BB98 # HANGUL SYLLABLE MIEUM-WI-MIEUM 92A5 BB99 # HANGUL SYLLABLE MIEUM-WI-PIEUP 92A6 BB9A # HANGUL SYLLABLE MIEUM-WI-PIEUPSIOS 92A7 BB9B # HANGUL SYLLABLE MIEUM-WI-SIOS 92A8 BB9C # HANGUL SYLLABLE MIEUM-WI-SSANGSIOS 92A9 BB9D # HANGUL SYLLABLE MIEUM-WI-IEUNG 92AA BB9E # HANGUL SYLLABLE MIEUM-WI-CIEUC 92AB BB9F # HANGUL SYLLABLE MIEUM-WI-CHIEUCH 92AC BBA0 # HANGUL SYLLABLE MIEUM-WI-KHIEUKH 92AD BBA1 # HANGUL SYLLABLE MIEUM-WI-THIEUTH 92AE BBA2 # HANGUL SYLLABLE MIEUM-WI-PHIEUPH 92AF BBA3 # HANGUL SYLLABLE MIEUM-WI-HIEUH 92B0 BBA5 # HANGUL SYLLABLE MIEUM-YU-KIYEOK 92B1 BBA6 # HANGUL SYLLABLE MIEUM-YU-SSANGKIYEOK 92B2 BBA7 # HANGUL SYLLABLE MIEUM-YU-KIYEOKSIOS 92B3 BBA9 # HANGUL SYLLABLE MIEUM-YU-NIEUNCIEUC 92B4 BBAA # HANGUL SYLLABLE MIEUM-YU-NIEUNHIEUH 92B5 BBAB # HANGUL SYLLABLE MIEUM-YU-TIKEUT 92B6 BBAD # HANGUL SYLLABLE MIEUM-YU-RIEULKIYEOK 92B7 BBAE # HANGUL SYLLABLE MIEUM-YU-RIEULMIEUM 92B8 BBAF # HANGUL SYLLABLE MIEUM-YU-RIEULPIEUP 92B9 BBB0 # HANGUL SYLLABLE MIEUM-YU-RIEULSIOS 92BA BBB1 # HANGUL SYLLABLE MIEUM-YU-RIEULTHIEUTH 92BB BBB2 # HANGUL SYLLABLE MIEUM-YU-RIEULPHIEUPH 92BC BBB3 # HANGUL SYLLABLE MIEUM-YU-RIEULHIEUH 92BD BBB5 # HANGUL SYLLABLE MIEUM-YU-PIEUP 92BE BBB6 # HANGUL SYLLABLE MIEUM-YU-PIEUPSIOS 92BF BBB8 # HANGUL SYLLABLE MIEUM-YU-SSANGSIOS 92C0 BBB9 # HANGUL SYLLABLE MIEUM-YU-IEUNG 92C1 BBBA # HANGUL SYLLABLE MIEUM-YU-CIEUC 92C2 BBBB # HANGUL SYLLABLE MIEUM-YU-CHIEUCH 92C3 BBBC # HANGUL SYLLABLE MIEUM-YU-KHIEUKH 92C4 BBBD # HANGUL SYLLABLE MIEUM-YU-THIEUTH 92C5 BBBE # HANGUL SYLLABLE MIEUM-YU-PHIEUPH 92C6 BBBF # HANGUL SYLLABLE MIEUM-YU-HIEUH 92C7 BBC1 # HANGUL SYLLABLE MIEUM-EU-KIYEOK 92C8 BBC2 # HANGUL SYLLABLE MIEUM-EU-SSANGKIYEOK 92C9 BBC3 # HANGUL SYLLABLE MIEUM-EU-KIYEOKSIOS 92CA BBC5 # HANGUL SYLLABLE MIEUM-EU-NIEUNCIEUC 92CB BBC6 # HANGUL SYLLABLE MIEUM-EU-NIEUNHIEUH 92CC BBC7 # HANGUL SYLLABLE MIEUM-EU-TIKEUT 92CD BBC9 # HANGUL SYLLABLE MIEUM-EU-RIEULKIYEOK 92CE BBCA # HANGUL SYLLABLE MIEUM-EU-RIEULMIEUM 92CF BBCB # HANGUL SYLLABLE MIEUM-EU-RIEULPIEUP 92D0 BBCC # HANGUL SYLLABLE MIEUM-EU-RIEULSIOS 92D1 BBCD # HANGUL SYLLABLE MIEUM-EU-RIEULTHIEUTH 92D2 BBCE # HANGUL SYLLABLE MIEUM-EU-RIEULPHIEUPH 92D3 BBCF # HANGUL SYLLABLE MIEUM-EU-RIEULHIEUH 92D4 BBD1 # HANGUL SYLLABLE MIEUM-EU-PIEUP 92D5 BBD2 # HANGUL SYLLABLE MIEUM-EU-PIEUPSIOS 92D6 BBD4 # HANGUL SYLLABLE MIEUM-EU-SSANGSIOS 92D7 BBD5 # HANGUL SYLLABLE MIEUM-EU-IEUNG 92D8 BBD6 # HANGUL SYLLABLE MIEUM-EU-CIEUC 92D9 BBD7 # HANGUL SYLLABLE MIEUM-EU-CHIEUCH 92DA BBD8 # HANGUL SYLLABLE MIEUM-EU-KHIEUKH 92DB BBD9 # HANGUL SYLLABLE MIEUM-EU-THIEUTH 92DC BBDA # HANGUL SYLLABLE MIEUM-EU-PHIEUPH 92DD BBDB # HANGUL SYLLABLE MIEUM-EU-HIEUH 92DE BBDC # HANGUL SYLLABLE MIEUM-YI 92DF BBDD # HANGUL SYLLABLE MIEUM-YI-KIYEOK 92E0 BBDE # HANGUL SYLLABLE MIEUM-YI-SSANGKIYEOK 92E1 BBDF # HANGUL SYLLABLE MIEUM-YI-KIYEOKSIOS 92E2 BBE0 # HANGUL SYLLABLE MIEUM-YI-NIEUN 92E3 BBE1 # HANGUL SYLLABLE MIEUM-YI-NIEUNCIEUC 92E4 BBE2 # HANGUL SYLLABLE MIEUM-YI-NIEUNHIEUH 92E5 BBE3 # HANGUL SYLLABLE MIEUM-YI-TIKEUT 92E6 BBE4 # HANGUL SYLLABLE MIEUM-YI-RIEUL 92E7 BBE5 # HANGUL SYLLABLE MIEUM-YI-RIEULKIYEOK 92E8 BBE6 # HANGUL SYLLABLE MIEUM-YI-RIEULMIEUM 92E9 BBE7 # HANGUL SYLLABLE MIEUM-YI-RIEULPIEUP 92EA BBE8 # HANGUL SYLLABLE MIEUM-YI-RIEULSIOS 92EB BBE9 # HANGUL SYLLABLE MIEUM-YI-RIEULTHIEUTH 92EC BBEA # HANGUL SYLLABLE MIEUM-YI-RIEULPHIEUPH 92ED BBEB # HANGUL SYLLABLE MIEUM-YI-RIEULHIEUH 92EE BBEC # HANGUL SYLLABLE MIEUM-YI-MIEUM 92EF BBED # HANGUL SYLLABLE MIEUM-YI-PIEUP 92F0 BBEE # HANGUL SYLLABLE MIEUM-YI-PIEUPSIOS 92F1 BBEF # HANGUL SYLLABLE MIEUM-YI-SIOS 92F2 BBF0 # HANGUL SYLLABLE MIEUM-YI-SSANGSIOS 92F3 BBF1 # HANGUL SYLLABLE MIEUM-YI-IEUNG 92F4 BBF2 # HANGUL SYLLABLE MIEUM-YI-CIEUC 92F5 BBF3 # HANGUL SYLLABLE MIEUM-YI-CHIEUCH 92F6 BBF4 # HANGUL SYLLABLE MIEUM-YI-KHIEUKH 92F7 BBF5 # HANGUL SYLLABLE MIEUM-YI-THIEUTH 92F8 BBF6 # HANGUL SYLLABLE MIEUM-YI-PHIEUPH 92F9 BBF7 # HANGUL SYLLABLE MIEUM-YI-HIEUH 92FA BBFA # HANGUL SYLLABLE MIEUM-I-SSANGKIYEOK 92FB BBFB # HANGUL SYLLABLE MIEUM-I-KIYEOKSIOS 92FC BBFD # HANGUL SYLLABLE MIEUM-I-NIEUNCIEUC 92FD BBFE # HANGUL SYLLABLE MIEUM-I-NIEUNHIEUH 92FE BC01 # HANGUL SYLLABLE MIEUM-I-RIEULKIYEOK 9341 BC03 # HANGUL SYLLABLE MIEUM-I-RIEULPIEUP 9342 BC04 # HANGUL SYLLABLE MIEUM-I-RIEULSIOS 9343 BC05 # HANGUL SYLLABLE MIEUM-I-RIEULTHIEUTH 9344 BC06 # HANGUL SYLLABLE MIEUM-I-RIEULPHIEUPH 9345 BC07 # HANGUL SYLLABLE MIEUM-I-RIEULHIEUH 9346 BC0A # HANGUL SYLLABLE MIEUM-I-PIEUPSIOS 9347 BC0E # HANGUL SYLLABLE MIEUM-I-CIEUC 9348 BC10 # HANGUL SYLLABLE MIEUM-I-KHIEUKH 9349 BC12 # HANGUL SYLLABLE MIEUM-I-PHIEUPH 934A BC13 # HANGUL SYLLABLE MIEUM-I-HIEUH 934B BC19 # HANGUL SYLLABLE PIEUP-A-NIEUNCIEUC 934C BC1A # HANGUL SYLLABLE PIEUP-A-NIEUNHIEUH 934D BC20 # HANGUL SYLLABLE PIEUP-A-RIEULSIOS 934E BC21 # HANGUL SYLLABLE PIEUP-A-RIEULTHIEUTH 934F BC22 # HANGUL SYLLABLE PIEUP-A-RIEULPHIEUPH 9350 BC23 # HANGUL SYLLABLE PIEUP-A-RIEULHIEUH 9351 BC26 # HANGUL SYLLABLE PIEUP-A-PIEUPSIOS 9352 BC28 # HANGUL SYLLABLE PIEUP-A-SSANGSIOS 9353 BC2A # HANGUL SYLLABLE PIEUP-A-CIEUC 9354 BC2B # HANGUL SYLLABLE PIEUP-A-CHIEUCH 9355 BC2C # HANGUL SYLLABLE PIEUP-A-KHIEUKH 9356 BC2E # HANGUL SYLLABLE PIEUP-A-PHIEUPH 9357 BC2F # HANGUL SYLLABLE PIEUP-A-HIEUH 9358 BC32 # HANGUL SYLLABLE PIEUP-AE-SSANGKIYEOK 9359 BC33 # HANGUL SYLLABLE PIEUP-AE-KIYEOKSIOS 935A BC35 # HANGUL SYLLABLE PIEUP-AE-NIEUNCIEUC 9361 BC36 # HANGUL SYLLABLE PIEUP-AE-NIEUNHIEUH 9362 BC37 # HANGUL SYLLABLE PIEUP-AE-TIKEUT 9363 BC39 # HANGUL SYLLABLE PIEUP-AE-RIEULKIYEOK 9364 BC3A # HANGUL SYLLABLE PIEUP-AE-RIEULMIEUM 9365 BC3B # HANGUL SYLLABLE PIEUP-AE-RIEULPIEUP 9366 BC3C # HANGUL SYLLABLE PIEUP-AE-RIEULSIOS 9367 BC3D # HANGUL SYLLABLE PIEUP-AE-RIEULTHIEUTH 9368 BC3E # HANGUL SYLLABLE PIEUP-AE-RIEULPHIEUPH 9369 BC3F # HANGUL SYLLABLE PIEUP-AE-RIEULHIEUH 936A BC42 # HANGUL SYLLABLE PIEUP-AE-PIEUPSIOS 936B BC46 # HANGUL SYLLABLE PIEUP-AE-CIEUC 936C BC47 # HANGUL SYLLABLE PIEUP-AE-CHIEUCH 936D BC48 # HANGUL SYLLABLE PIEUP-AE-KHIEUKH 936E BC4A # HANGUL SYLLABLE PIEUP-AE-PHIEUPH 936F BC4B # HANGUL SYLLABLE PIEUP-AE-HIEUH 9370 BC4E # HANGUL SYLLABLE PIEUP-YA-SSANGKIYEOK 9371 BC4F # HANGUL SYLLABLE PIEUP-YA-KIYEOKSIOS 9372 BC51 # HANGUL SYLLABLE PIEUP-YA-NIEUNCIEUC 9373 BC52 # HANGUL SYLLABLE PIEUP-YA-NIEUNHIEUH 9374 BC53 # HANGUL SYLLABLE PIEUP-YA-TIKEUT 9375 BC54 # HANGUL SYLLABLE PIEUP-YA-RIEUL 9376 BC55 # HANGUL SYLLABLE PIEUP-YA-RIEULKIYEOK 9377 BC56 # HANGUL SYLLABLE PIEUP-YA-RIEULMIEUM 9378 BC57 # HANGUL SYLLABLE PIEUP-YA-RIEULPIEUP 9379 BC58 # HANGUL SYLLABLE PIEUP-YA-RIEULSIOS 937A BC59 # HANGUL SYLLABLE PIEUP-YA-RIEULTHIEUTH 9381 BC5A # HANGUL SYLLABLE PIEUP-YA-RIEULPHIEUPH 9382 BC5B # HANGUL SYLLABLE PIEUP-YA-RIEULHIEUH 9383 BC5C # HANGUL SYLLABLE PIEUP-YA-MIEUM 9384 BC5E # HANGUL SYLLABLE PIEUP-YA-PIEUPSIOS 9385 BC5F # HANGUL SYLLABLE PIEUP-YA-SIOS 9386 BC60 # HANGUL SYLLABLE PIEUP-YA-SSANGSIOS 9387 BC61 # HANGUL SYLLABLE PIEUP-YA-IEUNG 9388 BC62 # HANGUL SYLLABLE PIEUP-YA-CIEUC 9389 BC63 # HANGUL SYLLABLE PIEUP-YA-CHIEUCH 938A BC64 # HANGUL SYLLABLE PIEUP-YA-KHIEUKH 938B BC65 # HANGUL SYLLABLE PIEUP-YA-THIEUTH 938C BC66 # HANGUL SYLLABLE PIEUP-YA-PHIEUPH 938D BC67 # HANGUL SYLLABLE PIEUP-YA-HIEUH 938E BC68 # HANGUL SYLLABLE PIEUP-YAE 938F BC69 # HANGUL SYLLABLE PIEUP-YAE-KIYEOK 9390 BC6A # HANGUL SYLLABLE PIEUP-YAE-SSANGKIYEOK 9391 BC6B # HANGUL SYLLABLE PIEUP-YAE-KIYEOKSIOS 9392 BC6C # HANGUL SYLLABLE PIEUP-YAE-NIEUN 9393 BC6D # HANGUL SYLLABLE PIEUP-YAE-NIEUNCIEUC 9394 BC6E # HANGUL SYLLABLE PIEUP-YAE-NIEUNHIEUH 9395 BC6F # HANGUL SYLLABLE PIEUP-YAE-TIKEUT 9396 BC70 # HANGUL SYLLABLE PIEUP-YAE-RIEUL 9397 BC71 # HANGUL SYLLABLE PIEUP-YAE-RIEULKIYEOK 9398 BC72 # HANGUL SYLLABLE PIEUP-YAE-RIEULMIEUM 9399 BC73 # HANGUL SYLLABLE PIEUP-YAE-RIEULPIEUP 939A BC74 # HANGUL SYLLABLE PIEUP-YAE-RIEULSIOS 939B BC75 # HANGUL SYLLABLE PIEUP-YAE-RIEULTHIEUTH 939C BC76 # HANGUL SYLLABLE PIEUP-YAE-RIEULPHIEUPH 939D BC77 # HANGUL SYLLABLE PIEUP-YAE-RIEULHIEUH 939E BC78 # HANGUL SYLLABLE PIEUP-YAE-MIEUM 939F BC79 # HANGUL SYLLABLE PIEUP-YAE-PIEUP 93A0 BC7A # HANGUL SYLLABLE PIEUP-YAE-PIEUPSIOS 93A1 BC7B # HANGUL SYLLABLE PIEUP-YAE-SIOS 93A2 BC7C # HANGUL SYLLABLE PIEUP-YAE-SSANGSIOS 93A3 BC7D # HANGUL SYLLABLE PIEUP-YAE-IEUNG 93A4 BC7E # HANGUL SYLLABLE PIEUP-YAE-CIEUC 93A5 BC7F # HANGUL SYLLABLE PIEUP-YAE-CHIEUCH 93A6 BC80 # HANGUL SYLLABLE PIEUP-YAE-KHIEUKH 93A7 BC81 # HANGUL SYLLABLE PIEUP-YAE-THIEUTH 93A8 BC82 # HANGUL SYLLABLE PIEUP-YAE-PHIEUPH 93A9 BC83 # HANGUL SYLLABLE PIEUP-YAE-HIEUH 93AA BC86 # HANGUL SYLLABLE PIEUP-EO-SSANGKIYEOK 93AB BC87 # HANGUL SYLLABLE PIEUP-EO-KIYEOKSIOS 93AC BC89 # HANGUL SYLLABLE PIEUP-EO-NIEUNCIEUC 93AD BC8A # HANGUL SYLLABLE PIEUP-EO-NIEUNHIEUH 93AE BC8D # HANGUL SYLLABLE PIEUP-EO-RIEULKIYEOK 93AF BC8F # HANGUL SYLLABLE PIEUP-EO-RIEULPIEUP 93B0 BC90 # HANGUL SYLLABLE PIEUP-EO-RIEULSIOS 93B1 BC91 # HANGUL SYLLABLE PIEUP-EO-RIEULTHIEUTH 93B2 BC92 # HANGUL SYLLABLE PIEUP-EO-RIEULPHIEUPH 93B3 BC93 # HANGUL SYLLABLE PIEUP-EO-RIEULHIEUH 93B4 BC96 # HANGUL SYLLABLE PIEUP-EO-PIEUPSIOS 93B5 BC98 # HANGUL SYLLABLE PIEUP-EO-SSANGSIOS 93B6 BC9B # HANGUL SYLLABLE PIEUP-EO-CHIEUCH 93B7 BC9C # HANGUL SYLLABLE PIEUP-EO-KHIEUKH 93B8 BC9D # HANGUL SYLLABLE PIEUP-EO-THIEUTH 93B9 BC9E # HANGUL SYLLABLE PIEUP-EO-PHIEUPH 93BA BC9F # HANGUL SYLLABLE PIEUP-EO-HIEUH 93BB BCA2 # HANGUL SYLLABLE PIEUP-E-SSANGKIYEOK 93BC BCA3 # HANGUL SYLLABLE PIEUP-E-KIYEOKSIOS 93BD BCA5 # HANGUL SYLLABLE PIEUP-E-NIEUNCIEUC 93BE BCA6 # HANGUL SYLLABLE PIEUP-E-NIEUNHIEUH 93BF BCA9 # HANGUL SYLLABLE PIEUP-E-RIEULKIYEOK 93C0 BCAA # HANGUL SYLLABLE PIEUP-E-RIEULMIEUM 93C1 BCAB # HANGUL SYLLABLE PIEUP-E-RIEULPIEUP 93C2 BCAC # HANGUL SYLLABLE PIEUP-E-RIEULSIOS 93C3 BCAD # HANGUL SYLLABLE PIEUP-E-RIEULTHIEUTH 93C4 BCAE # HANGUL SYLLABLE PIEUP-E-RIEULPHIEUPH 93C5 BCAF # HANGUL SYLLABLE PIEUP-E-RIEULHIEUH 93C6 BCB2 # HANGUL SYLLABLE PIEUP-E-PIEUPSIOS 93C7 BCB6 # HANGUL SYLLABLE PIEUP-E-CIEUC 93C8 BCB7 # HANGUL SYLLABLE PIEUP-E-CHIEUCH 93C9 BCB8 # HANGUL SYLLABLE PIEUP-E-KHIEUKH 93CA BCB9 # HANGUL SYLLABLE PIEUP-E-THIEUTH 93CB BCBA # HANGUL SYLLABLE PIEUP-E-PHIEUPH 93CC BCBB # HANGUL SYLLABLE PIEUP-E-HIEUH 93CD BCBE # HANGUL SYLLABLE PIEUP-YEO-SSANGKIYEOK 93CE BCBF # HANGUL SYLLABLE PIEUP-YEO-KIYEOKSIOS 93CF BCC1 # HANGUL SYLLABLE PIEUP-YEO-NIEUNCIEUC 93D0 BCC2 # HANGUL SYLLABLE PIEUP-YEO-NIEUNHIEUH 93D1 BCC3 # HANGUL SYLLABLE PIEUP-YEO-TIKEUT 93D2 BCC5 # HANGUL SYLLABLE PIEUP-YEO-RIEULKIYEOK 93D3 BCC6 # HANGUL SYLLABLE PIEUP-YEO-RIEULMIEUM 93D4 BCC7 # HANGUL SYLLABLE PIEUP-YEO-RIEULPIEUP 93D5 BCC8 # HANGUL SYLLABLE PIEUP-YEO-RIEULSIOS 93D6 BCC9 # HANGUL SYLLABLE PIEUP-YEO-RIEULTHIEUTH 93D7 BCCA # HANGUL SYLLABLE PIEUP-YEO-RIEULPHIEUPH 93D8 BCCB # HANGUL SYLLABLE PIEUP-YEO-RIEULHIEUH 93D9 BCCC # HANGUL SYLLABLE PIEUP-YEO-MIEUM 93DA BCCE # HANGUL SYLLABLE PIEUP-YEO-PIEUPSIOS 93DB BCD2 # HANGUL SYLLABLE PIEUP-YEO-CIEUC 93DC BCD3 # HANGUL SYLLABLE PIEUP-YEO-CHIEUCH 93DD BCD4 # HANGUL SYLLABLE PIEUP-YEO-KHIEUKH 93DE BCD6 # HANGUL SYLLABLE PIEUP-YEO-PHIEUPH 93DF BCD7 # HANGUL SYLLABLE PIEUP-YEO-HIEUH 93E0 BCD9 # HANGUL SYLLABLE PIEUP-YE-KIYEOK 93E1 BCDA # HANGUL SYLLABLE PIEUP-YE-SSANGKIYEOK 93E2 BCDB # HANGUL SYLLABLE PIEUP-YE-KIYEOKSIOS 93E3 BCDD # HANGUL SYLLABLE PIEUP-YE-NIEUNCIEUC 93E4 BCDE # HANGUL SYLLABLE PIEUP-YE-NIEUNHIEUH 93E5 BCDF # HANGUL SYLLABLE PIEUP-YE-TIKEUT 93E6 BCE0 # HANGUL SYLLABLE PIEUP-YE-RIEUL 93E7 BCE1 # HANGUL SYLLABLE PIEUP-YE-RIEULKIYEOK 93E8 BCE2 # HANGUL SYLLABLE PIEUP-YE-RIEULMIEUM 93E9 BCE3 # HANGUL SYLLABLE PIEUP-YE-RIEULPIEUP 93EA BCE4 # HANGUL SYLLABLE PIEUP-YE-RIEULSIOS 93EB BCE5 # HANGUL SYLLABLE PIEUP-YE-RIEULTHIEUTH 93EC BCE6 # HANGUL SYLLABLE PIEUP-YE-RIEULPHIEUPH 93ED BCE7 # HANGUL SYLLABLE PIEUP-YE-RIEULHIEUH 93EE BCE8 # HANGUL SYLLABLE PIEUP-YE-MIEUM 93EF BCE9 # HANGUL SYLLABLE PIEUP-YE-PIEUP 93F0 BCEA # HANGUL SYLLABLE PIEUP-YE-PIEUPSIOS 93F1 BCEB # HANGUL SYLLABLE PIEUP-YE-SIOS 93F2 BCEC # HANGUL SYLLABLE PIEUP-YE-SSANGSIOS 93F3 BCED # HANGUL SYLLABLE PIEUP-YE-IEUNG 93F4 BCEE # HANGUL SYLLABLE PIEUP-YE-CIEUC 93F5 BCEF # HANGUL SYLLABLE PIEUP-YE-CHIEUCH 93F6 BCF0 # HANGUL SYLLABLE PIEUP-YE-KHIEUKH 93F7 BCF1 # HANGUL SYLLABLE PIEUP-YE-THIEUTH 93F8 BCF2 # HANGUL SYLLABLE PIEUP-YE-PHIEUPH 93F9 BCF3 # HANGUL SYLLABLE PIEUP-YE-HIEUH 93FA BCF7 # HANGUL SYLLABLE PIEUP-O-KIYEOKSIOS 93FB BCF9 # HANGUL SYLLABLE PIEUP-O-NIEUNCIEUC 93FC BCFA # HANGUL SYLLABLE PIEUP-O-NIEUNHIEUH 93FD BCFB # HANGUL SYLLABLE PIEUP-O-TIKEUT 93FE BCFD # HANGUL SYLLABLE PIEUP-O-RIEULKIYEOK 9441 BCFE # HANGUL SYLLABLE PIEUP-O-RIEULMIEUM 9442 BCFF # HANGUL SYLLABLE PIEUP-O-RIEULPIEUP 9443 BD00 # HANGUL SYLLABLE PIEUP-O-RIEULSIOS 9444 BD01 # HANGUL SYLLABLE PIEUP-O-RIEULTHIEUTH 9445 BD02 # HANGUL SYLLABLE PIEUP-O-RIEULPHIEUPH 9446 BD03 # HANGUL SYLLABLE PIEUP-O-RIEULHIEUH 9447 BD06 # HANGUL SYLLABLE PIEUP-O-PIEUPSIOS 9448 BD08 # HANGUL SYLLABLE PIEUP-O-SSANGSIOS 9449 BD0A # HANGUL SYLLABLE PIEUP-O-CIEUC 944A BD0B # HANGUL SYLLABLE PIEUP-O-CHIEUCH 944B BD0C # HANGUL SYLLABLE PIEUP-O-KHIEUKH 944C BD0D # HANGUL SYLLABLE PIEUP-O-THIEUTH 944D BD0E # HANGUL SYLLABLE PIEUP-O-PHIEUPH 944E BD0F # HANGUL SYLLABLE PIEUP-O-HIEUH 944F BD11 # HANGUL SYLLABLE PIEUP-WA-KIYEOK 9450 BD12 # HANGUL SYLLABLE PIEUP-WA-SSANGKIYEOK 9451 BD13 # HANGUL SYLLABLE PIEUP-WA-KIYEOKSIOS 9452 BD15 # HANGUL SYLLABLE PIEUP-WA-NIEUNCIEUC 9453 BD16 # HANGUL SYLLABLE PIEUP-WA-NIEUNHIEUH 9454 BD17 # HANGUL SYLLABLE PIEUP-WA-TIKEUT 9455 BD18 # HANGUL SYLLABLE PIEUP-WA-RIEUL 9456 BD19 # HANGUL SYLLABLE PIEUP-WA-RIEULKIYEOK 9457 BD1A # HANGUL SYLLABLE PIEUP-WA-RIEULMIEUM 9458 BD1B # HANGUL SYLLABLE PIEUP-WA-RIEULPIEUP 9459 BD1C # HANGUL SYLLABLE PIEUP-WA-RIEULSIOS 945A BD1D # HANGUL SYLLABLE PIEUP-WA-RIEULTHIEUTH 9461 BD1E # HANGUL SYLLABLE PIEUP-WA-RIEULPHIEUPH 9462 BD1F # HANGUL SYLLABLE PIEUP-WA-RIEULHIEUH 9463 BD20 # HANGUL SYLLABLE PIEUP-WA-MIEUM 9464 BD21 # HANGUL SYLLABLE PIEUP-WA-PIEUP 9465 BD22 # HANGUL SYLLABLE PIEUP-WA-PIEUPSIOS 9466 BD23 # HANGUL SYLLABLE PIEUP-WA-SIOS 9467 BD25 # HANGUL SYLLABLE PIEUP-WA-IEUNG 9468 BD26 # HANGUL SYLLABLE PIEUP-WA-CIEUC 9469 BD27 # HANGUL SYLLABLE PIEUP-WA-CHIEUCH 946A BD28 # HANGUL SYLLABLE PIEUP-WA-KHIEUKH 946B BD29 # HANGUL SYLLABLE PIEUP-WA-THIEUTH 946C BD2A # HANGUL SYLLABLE PIEUP-WA-PHIEUPH 946D BD2B # HANGUL SYLLABLE PIEUP-WA-HIEUH 946E BD2D # HANGUL SYLLABLE PIEUP-WAE-KIYEOK 946F BD2E # HANGUL SYLLABLE PIEUP-WAE-SSANGKIYEOK 9470 BD2F # HANGUL SYLLABLE PIEUP-WAE-KIYEOKSIOS 9471 BD30 # HANGUL SYLLABLE PIEUP-WAE-NIEUN 9472 BD31 # HANGUL SYLLABLE PIEUP-WAE-NIEUNCIEUC 9473 BD32 # HANGUL SYLLABLE PIEUP-WAE-NIEUNHIEUH 9474 BD33 # HANGUL SYLLABLE PIEUP-WAE-TIKEUT 9475 BD34 # HANGUL SYLLABLE PIEUP-WAE-RIEUL 9476 BD35 # HANGUL SYLLABLE PIEUP-WAE-RIEULKIYEOK 9477 BD36 # HANGUL SYLLABLE PIEUP-WAE-RIEULMIEUM 9478 BD37 # HANGUL SYLLABLE PIEUP-WAE-RIEULPIEUP 9479 BD38 # HANGUL SYLLABLE PIEUP-WAE-RIEULSIOS 947A BD39 # HANGUL SYLLABLE PIEUP-WAE-RIEULTHIEUTH 9481 BD3A # HANGUL SYLLABLE PIEUP-WAE-RIEULPHIEUPH 9482 BD3B # HANGUL SYLLABLE PIEUP-WAE-RIEULHIEUH 9483 BD3C # HANGUL SYLLABLE PIEUP-WAE-MIEUM 9484 BD3D # HANGUL SYLLABLE PIEUP-WAE-PIEUP 9485 BD3E # HANGUL SYLLABLE PIEUP-WAE-PIEUPSIOS 9486 BD3F # HANGUL SYLLABLE PIEUP-WAE-SIOS 9487 BD41 # HANGUL SYLLABLE PIEUP-WAE-IEUNG 9488 BD42 # HANGUL SYLLABLE PIEUP-WAE-CIEUC 9489 BD43 # HANGUL SYLLABLE PIEUP-WAE-CHIEUCH 948A BD44 # HANGUL SYLLABLE PIEUP-WAE-KHIEUKH 948B BD45 # HANGUL SYLLABLE PIEUP-WAE-THIEUTH 948C BD46 # HANGUL SYLLABLE PIEUP-WAE-PHIEUPH 948D BD47 # HANGUL SYLLABLE PIEUP-WAE-HIEUH 948E BD4A # HANGUL SYLLABLE PIEUP-OE-SSANGKIYEOK 948F BD4B # HANGUL SYLLABLE PIEUP-OE-KIYEOKSIOS 9490 BD4D # HANGUL SYLLABLE PIEUP-OE-NIEUNCIEUC 9491 BD4E # HANGUL SYLLABLE PIEUP-OE-NIEUNHIEUH 9492 BD4F # HANGUL SYLLABLE PIEUP-OE-TIKEUT 9493 BD51 # HANGUL SYLLABLE PIEUP-OE-RIEULKIYEOK 9494 BD52 # HANGUL SYLLABLE PIEUP-OE-RIEULMIEUM 9495 BD53 # HANGUL SYLLABLE PIEUP-OE-RIEULPIEUP 9496 BD54 # HANGUL SYLLABLE PIEUP-OE-RIEULSIOS 9497 BD55 # HANGUL SYLLABLE PIEUP-OE-RIEULTHIEUTH 9498 BD56 # HANGUL SYLLABLE PIEUP-OE-RIEULPHIEUPH 9499 BD57 # HANGUL SYLLABLE PIEUP-OE-RIEULHIEUH 949A BD5A # HANGUL SYLLABLE PIEUP-OE-PIEUPSIOS 949B BD5B # HANGUL SYLLABLE PIEUP-OE-SIOS 949C BD5C # HANGUL SYLLABLE PIEUP-OE-SSANGSIOS 949D BD5D # HANGUL SYLLABLE PIEUP-OE-IEUNG 949E BD5E # HANGUL SYLLABLE PIEUP-OE-CIEUC 949F BD5F # HANGUL SYLLABLE PIEUP-OE-CHIEUCH 94A0 BD60 # HANGUL SYLLABLE PIEUP-OE-KHIEUKH 94A1 BD61 # HANGUL SYLLABLE PIEUP-OE-THIEUTH 94A2 BD62 # HANGUL SYLLABLE PIEUP-OE-PHIEUPH 94A3 BD63 # HANGUL SYLLABLE PIEUP-OE-HIEUH 94A4 BD65 # HANGUL SYLLABLE PIEUP-YO-KIYEOK 94A5 BD66 # HANGUL SYLLABLE PIEUP-YO-SSANGKIYEOK 94A6 BD67 # HANGUL SYLLABLE PIEUP-YO-KIYEOKSIOS 94A7 BD69 # HANGUL SYLLABLE PIEUP-YO-NIEUNCIEUC 94A8 BD6A # HANGUL SYLLABLE PIEUP-YO-NIEUNHIEUH 94A9 BD6B # HANGUL SYLLABLE PIEUP-YO-TIKEUT 94AA BD6C # HANGUL SYLLABLE PIEUP-YO-RIEUL 94AB BD6D # HANGUL SYLLABLE PIEUP-YO-RIEULKIYEOK 94AC BD6E # HANGUL SYLLABLE PIEUP-YO-RIEULMIEUM 94AD BD6F # HANGUL SYLLABLE PIEUP-YO-RIEULPIEUP 94AE BD70 # HANGUL SYLLABLE PIEUP-YO-RIEULSIOS 94AF BD71 # HANGUL SYLLABLE PIEUP-YO-RIEULTHIEUTH 94B0 BD72 # HANGUL SYLLABLE PIEUP-YO-RIEULPHIEUPH 94B1 BD73 # HANGUL SYLLABLE PIEUP-YO-RIEULHIEUH 94B2 BD74 # HANGUL SYLLABLE PIEUP-YO-MIEUM 94B3 BD75 # HANGUL SYLLABLE PIEUP-YO-PIEUP 94B4 BD76 # HANGUL SYLLABLE PIEUP-YO-PIEUPSIOS 94B5 BD77 # HANGUL SYLLABLE PIEUP-YO-SIOS 94B6 BD78 # HANGUL SYLLABLE PIEUP-YO-SSANGSIOS 94B7 BD79 # HANGUL SYLLABLE PIEUP-YO-IEUNG 94B8 BD7A # HANGUL SYLLABLE PIEUP-YO-CIEUC 94B9 BD7B # HANGUL SYLLABLE PIEUP-YO-CHIEUCH 94BA BD7C # HANGUL SYLLABLE PIEUP-YO-KHIEUKH 94BB BD7D # HANGUL SYLLABLE PIEUP-YO-THIEUTH 94BC BD7E # HANGUL SYLLABLE PIEUP-YO-PHIEUPH 94BD BD7F # HANGUL SYLLABLE PIEUP-YO-HIEUH 94BE BD82 # HANGUL SYLLABLE PIEUP-U-SSANGKIYEOK 94BF BD83 # HANGUL SYLLABLE PIEUP-U-KIYEOKSIOS 94C0 BD85 # HANGUL SYLLABLE PIEUP-U-NIEUNCIEUC 94C1 BD86 # HANGUL SYLLABLE PIEUP-U-NIEUNHIEUH 94C2 BD8B # HANGUL SYLLABLE PIEUP-U-RIEULPIEUP 94C3 BD8C # HANGUL SYLLABLE PIEUP-U-RIEULSIOS 94C4 BD8D # HANGUL SYLLABLE PIEUP-U-RIEULTHIEUTH 94C5 BD8E # HANGUL SYLLABLE PIEUP-U-RIEULPHIEUPH 94C6 BD8F # HANGUL SYLLABLE PIEUP-U-RIEULHIEUH 94C7 BD92 # HANGUL SYLLABLE PIEUP-U-PIEUPSIOS 94C8 BD94 # HANGUL SYLLABLE PIEUP-U-SSANGSIOS 94C9 BD96 # HANGUL SYLLABLE PIEUP-U-CIEUC 94CA BD97 # HANGUL SYLLABLE PIEUP-U-CHIEUCH 94CB BD98 # HANGUL SYLLABLE PIEUP-U-KHIEUKH 94CC BD9B # HANGUL SYLLABLE PIEUP-U-HIEUH 94CD BD9D # HANGUL SYLLABLE PIEUP-WEO-KIYEOK 94CE BD9E # HANGUL SYLLABLE PIEUP-WEO-SSANGKIYEOK 94CF BD9F # HANGUL SYLLABLE PIEUP-WEO-KIYEOKSIOS 94D0 BDA0 # HANGUL SYLLABLE PIEUP-WEO-NIEUN 94D1 BDA1 # HANGUL SYLLABLE PIEUP-WEO-NIEUNCIEUC 94D2 BDA2 # HANGUL SYLLABLE PIEUP-WEO-NIEUNHIEUH 94D3 BDA3 # HANGUL SYLLABLE PIEUP-WEO-TIKEUT 94D4 BDA5 # HANGUL SYLLABLE PIEUP-WEO-RIEULKIYEOK 94D5 BDA6 # HANGUL SYLLABLE PIEUP-WEO-RIEULMIEUM 94D6 BDA7 # HANGUL SYLLABLE PIEUP-WEO-RIEULPIEUP 94D7 BDA8 # HANGUL SYLLABLE PIEUP-WEO-RIEULSIOS 94D8 BDA9 # HANGUL SYLLABLE PIEUP-WEO-RIEULTHIEUTH 94D9 BDAA # HANGUL SYLLABLE PIEUP-WEO-RIEULPHIEUPH 94DA BDAB # HANGUL SYLLABLE PIEUP-WEO-RIEULHIEUH 94DB BDAC # HANGUL SYLLABLE PIEUP-WEO-MIEUM 94DC BDAD # HANGUL SYLLABLE PIEUP-WEO-PIEUP 94DD BDAE # HANGUL SYLLABLE PIEUP-WEO-PIEUPSIOS 94DE BDAF # HANGUL SYLLABLE PIEUP-WEO-SIOS 94DF BDB1 # HANGUL SYLLABLE PIEUP-WEO-IEUNG 94E0 BDB2 # HANGUL SYLLABLE PIEUP-WEO-CIEUC 94E1 BDB3 # HANGUL SYLLABLE PIEUP-WEO-CHIEUCH 94E2 BDB4 # HANGUL SYLLABLE PIEUP-WEO-KHIEUKH 94E3 BDB5 # HANGUL SYLLABLE PIEUP-WEO-THIEUTH 94E4 BDB6 # HANGUL SYLLABLE PIEUP-WEO-PHIEUPH 94E5 BDB7 # HANGUL SYLLABLE PIEUP-WEO-HIEUH 94E6 BDB9 # HANGUL SYLLABLE PIEUP-WE-KIYEOK 94E7 BDBA # HANGUL SYLLABLE PIEUP-WE-SSANGKIYEOK 94E8 BDBB # HANGUL SYLLABLE PIEUP-WE-KIYEOKSIOS 94E9 BDBC # HANGUL SYLLABLE PIEUP-WE-NIEUN 94EA BDBD # HANGUL SYLLABLE PIEUP-WE-NIEUNCIEUC 94EB BDBE # HANGUL SYLLABLE PIEUP-WE-NIEUNHIEUH 94EC BDBF # HANGUL SYLLABLE PIEUP-WE-TIKEUT 94ED BDC0 # HANGUL SYLLABLE PIEUP-WE-RIEUL 94EE BDC1 # HANGUL SYLLABLE PIEUP-WE-RIEULKIYEOK 94EF BDC2 # HANGUL SYLLABLE PIEUP-WE-RIEULMIEUM 94F0 BDC3 # HANGUL SYLLABLE PIEUP-WE-RIEULPIEUP 94F1 BDC4 # HANGUL SYLLABLE PIEUP-WE-RIEULSIOS 94F2 BDC5 # HANGUL SYLLABLE PIEUP-WE-RIEULTHIEUTH 94F3 BDC6 # HANGUL SYLLABLE PIEUP-WE-RIEULPHIEUPH 94F4 BDC7 # HANGUL SYLLABLE PIEUP-WE-RIEULHIEUH 94F5 BDC8 # HANGUL SYLLABLE PIEUP-WE-MIEUM 94F6 BDC9 # HANGUL SYLLABLE PIEUP-WE-PIEUP 94F7 BDCA # HANGUL SYLLABLE PIEUP-WE-PIEUPSIOS 94F8 BDCB # HANGUL SYLLABLE PIEUP-WE-SIOS 94F9 BDCC # HANGUL SYLLABLE PIEUP-WE-SSANGSIOS 94FA BDCD # HANGUL SYLLABLE PIEUP-WE-IEUNG 94FB BDCE # HANGUL SYLLABLE PIEUP-WE-CIEUC 94FC BDCF # HANGUL SYLLABLE PIEUP-WE-CHIEUCH 94FD BDD0 # HANGUL SYLLABLE PIEUP-WE-KHIEUKH 94FE BDD1 # HANGUL SYLLABLE PIEUP-WE-THIEUTH 9541 BDD2 # HANGUL SYLLABLE PIEUP-WE-PHIEUPH 9542 BDD3 # HANGUL SYLLABLE PIEUP-WE-HIEUH 9543 BDD6 # HANGUL SYLLABLE PIEUP-WI-SSANGKIYEOK 9544 BDD7 # HANGUL SYLLABLE PIEUP-WI-KIYEOKSIOS 9545 BDD9 # HANGUL SYLLABLE PIEUP-WI-NIEUNCIEUC 9546 BDDA # HANGUL SYLLABLE PIEUP-WI-NIEUNHIEUH 9547 BDDB # HANGUL SYLLABLE PIEUP-WI-TIKEUT 9548 BDDD # HANGUL SYLLABLE PIEUP-WI-RIEULKIYEOK 9549 BDDE # HANGUL SYLLABLE PIEUP-WI-RIEULMIEUM 954A BDDF # HANGUL SYLLABLE PIEUP-WI-RIEULPIEUP 954B BDE0 # HANGUL SYLLABLE PIEUP-WI-RIEULSIOS 954C BDE1 # HANGUL SYLLABLE PIEUP-WI-RIEULTHIEUTH 954D BDE2 # HANGUL SYLLABLE PIEUP-WI-RIEULPHIEUPH 954E BDE3 # HANGUL SYLLABLE PIEUP-WI-RIEULHIEUH 954F BDE4 # HANGUL SYLLABLE PIEUP-WI-MIEUM 9550 BDE5 # HANGUL SYLLABLE PIEUP-WI-PIEUP 9551 BDE6 # HANGUL SYLLABLE PIEUP-WI-PIEUPSIOS 9552 BDE7 # HANGUL SYLLABLE PIEUP-WI-SIOS 9553 BDE8 # HANGUL SYLLABLE PIEUP-WI-SSANGSIOS 9554 BDEA # HANGUL SYLLABLE PIEUP-WI-CIEUC 9555 BDEB # HANGUL SYLLABLE PIEUP-WI-CHIEUCH 9556 BDEC # HANGUL SYLLABLE PIEUP-WI-KHIEUKH 9557 BDED # HANGUL SYLLABLE PIEUP-WI-THIEUTH 9558 BDEE # HANGUL SYLLABLE PIEUP-WI-PHIEUPH 9559 BDEF # HANGUL SYLLABLE PIEUP-WI-HIEUH 955A BDF1 # HANGUL SYLLABLE PIEUP-YU-KIYEOK 9561 BDF2 # HANGUL SYLLABLE PIEUP-YU-SSANGKIYEOK 9562 BDF3 # HANGUL SYLLABLE PIEUP-YU-KIYEOKSIOS 9563 BDF5 # HANGUL SYLLABLE PIEUP-YU-NIEUNCIEUC 9564 BDF6 # HANGUL SYLLABLE PIEUP-YU-NIEUNHIEUH 9565 BDF7 # HANGUL SYLLABLE PIEUP-YU-TIKEUT 9566 BDF9 # HANGUL SYLLABLE PIEUP-YU-RIEULKIYEOK 9567 BDFA # HANGUL SYLLABLE PIEUP-YU-RIEULMIEUM 9568 BDFB # HANGUL SYLLABLE PIEUP-YU-RIEULPIEUP 9569 BDFC # HANGUL SYLLABLE PIEUP-YU-RIEULSIOS 956A BDFD # HANGUL SYLLABLE PIEUP-YU-RIEULTHIEUTH 956B BDFE # HANGUL SYLLABLE PIEUP-YU-RIEULPHIEUPH 956C BDFF # HANGUL SYLLABLE PIEUP-YU-RIEULHIEUH 956D BE01 # HANGUL SYLLABLE PIEUP-YU-PIEUP 956E BE02 # HANGUL SYLLABLE PIEUP-YU-PIEUPSIOS 956F BE04 # HANGUL SYLLABLE PIEUP-YU-SSANGSIOS 9570 BE06 # HANGUL SYLLABLE PIEUP-YU-CIEUC 9571 BE07 # HANGUL SYLLABLE PIEUP-YU-CHIEUCH 9572 BE08 # HANGUL SYLLABLE PIEUP-YU-KHIEUKH 9573 BE09 # HANGUL SYLLABLE PIEUP-YU-THIEUTH 9574 BE0A # HANGUL SYLLABLE PIEUP-YU-PHIEUPH 9575 BE0B # HANGUL SYLLABLE PIEUP-YU-HIEUH 9576 BE0E # HANGUL SYLLABLE PIEUP-EU-SSANGKIYEOK 9577 BE0F # HANGUL SYLLABLE PIEUP-EU-KIYEOKSIOS 9578 BE11 # HANGUL SYLLABLE PIEUP-EU-NIEUNCIEUC 9579 BE12 # HANGUL SYLLABLE PIEUP-EU-NIEUNHIEUH 957A BE13 # HANGUL SYLLABLE PIEUP-EU-TIKEUT 9581 BE15 # HANGUL SYLLABLE PIEUP-EU-RIEULKIYEOK 9582 BE16 # HANGUL SYLLABLE PIEUP-EU-RIEULMIEUM 9583 BE17 # HANGUL SYLLABLE PIEUP-EU-RIEULPIEUP 9584 BE18 # HANGUL SYLLABLE PIEUP-EU-RIEULSIOS 9585 BE19 # HANGUL SYLLABLE PIEUP-EU-RIEULTHIEUTH 9586 BE1A # HANGUL SYLLABLE PIEUP-EU-RIEULPHIEUPH 9587 BE1B # HANGUL SYLLABLE PIEUP-EU-RIEULHIEUH 9588 BE1E # HANGUL SYLLABLE PIEUP-EU-PIEUPSIOS 9589 BE20 # HANGUL SYLLABLE PIEUP-EU-SSANGSIOS 958A BE21 # HANGUL SYLLABLE PIEUP-EU-IEUNG 958B BE22 # HANGUL SYLLABLE PIEUP-EU-CIEUC 958C BE23 # HANGUL SYLLABLE PIEUP-EU-CHIEUCH 958D BE24 # HANGUL SYLLABLE PIEUP-EU-KHIEUKH 958E BE25 # HANGUL SYLLABLE PIEUP-EU-THIEUTH 958F BE26 # HANGUL SYLLABLE PIEUP-EU-PHIEUPH 9590 BE27 # HANGUL SYLLABLE PIEUP-EU-HIEUH 9591 BE28 # HANGUL SYLLABLE PIEUP-YI 9592 BE29 # HANGUL SYLLABLE PIEUP-YI-KIYEOK 9593 BE2A # HANGUL SYLLABLE PIEUP-YI-SSANGKIYEOK 9594 BE2B # HANGUL SYLLABLE PIEUP-YI-KIYEOKSIOS 9595 BE2C # HANGUL SYLLABLE PIEUP-YI-NIEUN 9596 BE2D # HANGUL SYLLABLE PIEUP-YI-NIEUNCIEUC 9597 BE2E # HANGUL SYLLABLE PIEUP-YI-NIEUNHIEUH 9598 BE2F # HANGUL SYLLABLE PIEUP-YI-TIKEUT 9599 BE30 # HANGUL SYLLABLE PIEUP-YI-RIEUL 959A BE31 # HANGUL SYLLABLE PIEUP-YI-RIEULKIYEOK 959B BE32 # HANGUL SYLLABLE PIEUP-YI-RIEULMIEUM 959C BE33 # HANGUL SYLLABLE PIEUP-YI-RIEULPIEUP 959D BE34 # HANGUL SYLLABLE PIEUP-YI-RIEULSIOS 959E BE35 # HANGUL SYLLABLE PIEUP-YI-RIEULTHIEUTH 959F BE36 # HANGUL SYLLABLE PIEUP-YI-RIEULPHIEUPH 95A0 BE37 # HANGUL SYLLABLE PIEUP-YI-RIEULHIEUH 95A1 BE38 # HANGUL SYLLABLE PIEUP-YI-MIEUM 95A2 BE39 # HANGUL SYLLABLE PIEUP-YI-PIEUP 95A3 BE3A # HANGUL SYLLABLE PIEUP-YI-PIEUPSIOS 95A4 BE3B # HANGUL SYLLABLE PIEUP-YI-SIOS 95A5 BE3C # HANGUL SYLLABLE PIEUP-YI-SSANGSIOS 95A6 BE3D # HANGUL SYLLABLE PIEUP-YI-IEUNG 95A7 BE3E # HANGUL SYLLABLE PIEUP-YI-CIEUC 95A8 BE3F # HANGUL SYLLABLE PIEUP-YI-CHIEUCH 95A9 BE40 # HANGUL SYLLABLE PIEUP-YI-KHIEUKH 95AA BE41 # HANGUL SYLLABLE PIEUP-YI-THIEUTH 95AB BE42 # HANGUL SYLLABLE PIEUP-YI-PHIEUPH 95AC BE43 # HANGUL SYLLABLE PIEUP-YI-HIEUH 95AD BE46 # HANGUL SYLLABLE PIEUP-I-SSANGKIYEOK 95AE BE47 # HANGUL SYLLABLE PIEUP-I-KIYEOKSIOS 95AF BE49 # HANGUL SYLLABLE PIEUP-I-NIEUNCIEUC 95B0 BE4A # HANGUL SYLLABLE PIEUP-I-NIEUNHIEUH 95B1 BE4B # HANGUL SYLLABLE PIEUP-I-TIKEUT 95B2 BE4D # HANGUL SYLLABLE PIEUP-I-RIEULKIYEOK 95B3 BE4F # HANGUL SYLLABLE PIEUP-I-RIEULPIEUP 95B4 BE50 # HANGUL SYLLABLE PIEUP-I-RIEULSIOS 95B5 BE51 # HANGUL SYLLABLE PIEUP-I-RIEULTHIEUTH 95B6 BE52 # HANGUL SYLLABLE PIEUP-I-RIEULPHIEUPH 95B7 BE53 # HANGUL SYLLABLE PIEUP-I-RIEULHIEUH 95B8 BE56 # HANGUL SYLLABLE PIEUP-I-PIEUPSIOS 95B9 BE58 # HANGUL SYLLABLE PIEUP-I-SSANGSIOS 95BA BE5C # HANGUL SYLLABLE PIEUP-I-KHIEUKH 95BB BE5D # HANGUL SYLLABLE PIEUP-I-THIEUTH 95BC BE5E # HANGUL SYLLABLE PIEUP-I-PHIEUPH 95BD BE5F # HANGUL SYLLABLE PIEUP-I-HIEUH 95BE BE62 # HANGUL SYLLABLE SSANGPIEUP-A-SSANGKIYEOK 95BF BE63 # HANGUL SYLLABLE SSANGPIEUP-A-KIYEOKSIOS 95C0 BE65 # HANGUL SYLLABLE SSANGPIEUP-A-NIEUNCIEUC 95C1 BE66 # HANGUL SYLLABLE SSANGPIEUP-A-NIEUNHIEUH 95C2 BE67 # HANGUL SYLLABLE SSANGPIEUP-A-TIKEUT 95C3 BE69 # HANGUL SYLLABLE SSANGPIEUP-A-RIEULKIYEOK 95C4 BE6B # HANGUL SYLLABLE SSANGPIEUP-A-RIEULPIEUP 95C5 BE6C # HANGUL SYLLABLE SSANGPIEUP-A-RIEULSIOS 95C6 BE6D # HANGUL SYLLABLE SSANGPIEUP-A-RIEULTHIEUTH 95C7 BE6E # HANGUL SYLLABLE SSANGPIEUP-A-RIEULPHIEUPH 95C8 BE6F # HANGUL SYLLABLE SSANGPIEUP-A-RIEULHIEUH 95C9 BE72 # HANGUL SYLLABLE SSANGPIEUP-A-PIEUPSIOS 95CA BE76 # HANGUL SYLLABLE SSANGPIEUP-A-CIEUC 95CB BE77 # HANGUL SYLLABLE SSANGPIEUP-A-CHIEUCH 95CC BE78 # HANGUL SYLLABLE SSANGPIEUP-A-KHIEUKH 95CD BE79 # HANGUL SYLLABLE SSANGPIEUP-A-THIEUTH 95CE BE7A # HANGUL SYLLABLE SSANGPIEUP-A-PHIEUPH 95CF BE7E # HANGUL SYLLABLE SSANGPIEUP-AE-SSANGKIYEOK 95D0 BE7F # HANGUL SYLLABLE SSANGPIEUP-AE-KIYEOKSIOS 95D1 BE81 # HANGUL SYLLABLE SSANGPIEUP-AE-NIEUNCIEUC 95D2 BE82 # HANGUL SYLLABLE SSANGPIEUP-AE-NIEUNHIEUH 95D3 BE83 # HANGUL SYLLABLE SSANGPIEUP-AE-TIKEUT 95D4 BE85 # HANGUL SYLLABLE SSANGPIEUP-AE-RIEULKIYEOK 95D5 BE86 # HANGUL SYLLABLE SSANGPIEUP-AE-RIEULMIEUM 95D6 BE87 # HANGUL SYLLABLE SSANGPIEUP-AE-RIEULPIEUP 95D7 BE88 # HANGUL SYLLABLE SSANGPIEUP-AE-RIEULSIOS 95D8 BE89 # HANGUL SYLLABLE SSANGPIEUP-AE-RIEULTHIEUTH 95D9 BE8A # HANGUL SYLLABLE SSANGPIEUP-AE-RIEULPHIEUPH 95DA BE8B # HANGUL SYLLABLE SSANGPIEUP-AE-RIEULHIEUH 95DB BE8E # HANGUL SYLLABLE SSANGPIEUP-AE-PIEUPSIOS 95DC BE92 # HANGUL SYLLABLE SSANGPIEUP-AE-CIEUC 95DD BE93 # HANGUL SYLLABLE SSANGPIEUP-AE-CHIEUCH 95DE BE94 # HANGUL SYLLABLE SSANGPIEUP-AE-KHIEUKH 95DF BE95 # HANGUL SYLLABLE SSANGPIEUP-AE-THIEUTH 95E0 BE96 # HANGUL SYLLABLE SSANGPIEUP-AE-PHIEUPH 95E1 BE97 # HANGUL SYLLABLE SSANGPIEUP-AE-HIEUH 95E2 BE9A # HANGUL SYLLABLE SSANGPIEUP-YA-SSANGKIYEOK 95E3 BE9B # HANGUL SYLLABLE SSANGPIEUP-YA-KIYEOKSIOS 95E4 BE9C # HANGUL SYLLABLE SSANGPIEUP-YA-NIEUN 95E5 BE9D # HANGUL SYLLABLE SSANGPIEUP-YA-NIEUNCIEUC 95E6 BE9E # HANGUL SYLLABLE SSANGPIEUP-YA-NIEUNHIEUH 95E7 BE9F # HANGUL SYLLABLE SSANGPIEUP-YA-TIKEUT 95E8 BEA0 # HANGUL SYLLABLE SSANGPIEUP-YA-RIEUL 95E9 BEA1 # HANGUL SYLLABLE SSANGPIEUP-YA-RIEULKIYEOK 95EA BEA2 # HANGUL SYLLABLE SSANGPIEUP-YA-RIEULMIEUM 95EB BEA3 # HANGUL SYLLABLE SSANGPIEUP-YA-RIEULPIEUP 95EC BEA4 # HANGUL SYLLABLE SSANGPIEUP-YA-RIEULSIOS 95ED BEA5 # HANGUL SYLLABLE SSANGPIEUP-YA-RIEULTHIEUTH 95EE BEA6 # HANGUL SYLLABLE SSANGPIEUP-YA-RIEULPHIEUPH 95EF BEA7 # HANGUL SYLLABLE SSANGPIEUP-YA-RIEULHIEUH 95F0 BEA9 # HANGUL SYLLABLE SSANGPIEUP-YA-PIEUP 95F1 BEAA # HANGUL SYLLABLE SSANGPIEUP-YA-PIEUPSIOS 95F2 BEAB # HANGUL SYLLABLE SSANGPIEUP-YA-SIOS 95F3 BEAC # HANGUL SYLLABLE SSANGPIEUP-YA-SSANGSIOS 95F4 BEAD # HANGUL SYLLABLE SSANGPIEUP-YA-IEUNG 95F5 BEAE # HANGUL SYLLABLE SSANGPIEUP-YA-CIEUC 95F6 BEAF # HANGUL SYLLABLE SSANGPIEUP-YA-CHIEUCH 95F7 BEB0 # HANGUL SYLLABLE SSANGPIEUP-YA-KHIEUKH 95F8 BEB1 # HANGUL SYLLABLE SSANGPIEUP-YA-THIEUTH 95F9 BEB2 # HANGUL SYLLABLE SSANGPIEUP-YA-PHIEUPH 95FA BEB3 # HANGUL SYLLABLE SSANGPIEUP-YA-HIEUH 95FB BEB4 # HANGUL SYLLABLE SSANGPIEUP-YAE 95FC BEB5 # HANGUL SYLLABLE SSANGPIEUP-YAE-KIYEOK 95FD BEB6 # HANGUL SYLLABLE SSANGPIEUP-YAE-SSANGKIYEOK 95FE BEB7 # HANGUL SYLLABLE SSANGPIEUP-YAE-KIYEOKSIOS 9641 BEB8 # HANGUL SYLLABLE SSANGPIEUP-YAE-NIEUN 9642 BEB9 # HANGUL SYLLABLE SSANGPIEUP-YAE-NIEUNCIEUC 9643 BEBA # HANGUL SYLLABLE SSANGPIEUP-YAE-NIEUNHIEUH 9644 BEBB # HANGUL SYLLABLE SSANGPIEUP-YAE-TIKEUT 9645 BEBC # HANGUL SYLLABLE SSANGPIEUP-YAE-RIEUL 9646 BEBD # HANGUL SYLLABLE SSANGPIEUP-YAE-RIEULKIYEOK 9647 BEBE # HANGUL SYLLABLE SSANGPIEUP-YAE-RIEULMIEUM 9648 BEBF # HANGUL SYLLABLE SSANGPIEUP-YAE-RIEULPIEUP 9649 BEC0 # HANGUL SYLLABLE SSANGPIEUP-YAE-RIEULSIOS 964A BEC1 # HANGUL SYLLABLE SSANGPIEUP-YAE-RIEULTHIEUTH 964B BEC2 # HANGUL SYLLABLE SSANGPIEUP-YAE-RIEULPHIEUPH 964C BEC3 # HANGUL SYLLABLE SSANGPIEUP-YAE-RIEULHIEUH 964D BEC4 # HANGUL SYLLABLE SSANGPIEUP-YAE-MIEUM 964E BEC5 # HANGUL SYLLABLE SSANGPIEUP-YAE-PIEUP 964F BEC6 # HANGUL SYLLABLE SSANGPIEUP-YAE-PIEUPSIOS 9650 BEC7 # HANGUL SYLLABLE SSANGPIEUP-YAE-SIOS 9651 BEC8 # HANGUL SYLLABLE SSANGPIEUP-YAE-SSANGSIOS 9652 BEC9 # HANGUL SYLLABLE SSANGPIEUP-YAE-IEUNG 9653 BECA # HANGUL SYLLABLE SSANGPIEUP-YAE-CIEUC 9654 BECB # HANGUL SYLLABLE SSANGPIEUP-YAE-CHIEUCH 9655 BECC # HANGUL SYLLABLE SSANGPIEUP-YAE-KHIEUKH 9656 BECD # HANGUL SYLLABLE SSANGPIEUP-YAE-THIEUTH 9657 BECE # HANGUL SYLLABLE SSANGPIEUP-YAE-PHIEUPH 9658 BECF # HANGUL SYLLABLE SSANGPIEUP-YAE-HIEUH 9659 BED2 # HANGUL SYLLABLE SSANGPIEUP-EO-SSANGKIYEOK 965A BED3 # HANGUL SYLLABLE SSANGPIEUP-EO-KIYEOKSIOS 9661 BED5 # HANGUL SYLLABLE SSANGPIEUP-EO-NIEUNCIEUC 9662 BED6 # HANGUL SYLLABLE SSANGPIEUP-EO-NIEUNHIEUH 9663 BED9 # HANGUL SYLLABLE SSANGPIEUP-EO-RIEULKIYEOK 9664 BEDA # HANGUL SYLLABLE SSANGPIEUP-EO-RIEULMIEUM 9665 BEDB # HANGUL SYLLABLE SSANGPIEUP-EO-RIEULPIEUP 9666 BEDC # HANGUL SYLLABLE SSANGPIEUP-EO-RIEULSIOS 9667 BEDD # HANGUL SYLLABLE SSANGPIEUP-EO-RIEULTHIEUTH 9668 BEDE # HANGUL SYLLABLE SSANGPIEUP-EO-RIEULPHIEUPH 9669 BEDF # HANGUL SYLLABLE SSANGPIEUP-EO-RIEULHIEUH 966A BEE1 # HANGUL SYLLABLE SSANGPIEUP-EO-PIEUP 966B BEE2 # HANGUL SYLLABLE SSANGPIEUP-EO-PIEUPSIOS 966C BEE6 # HANGUL SYLLABLE SSANGPIEUP-EO-CIEUC 966D BEE7 # HANGUL SYLLABLE SSANGPIEUP-EO-CHIEUCH 966E BEE8 # HANGUL SYLLABLE SSANGPIEUP-EO-KHIEUKH 966F BEE9 # HANGUL SYLLABLE SSANGPIEUP-EO-THIEUTH 9670 BEEA # HANGUL SYLLABLE SSANGPIEUP-EO-PHIEUPH 9671 BEEB # HANGUL SYLLABLE SSANGPIEUP-EO-HIEUH 9672 BEED # HANGUL SYLLABLE SSANGPIEUP-E-KIYEOK 9673 BEEE # HANGUL SYLLABLE SSANGPIEUP-E-SSANGKIYEOK 9674 BEEF # HANGUL SYLLABLE SSANGPIEUP-E-KIYEOKSIOS 9675 BEF0 # HANGUL SYLLABLE SSANGPIEUP-E-NIEUN 9676 BEF1 # HANGUL SYLLABLE SSANGPIEUP-E-NIEUNCIEUC 9677 BEF2 # HANGUL SYLLABLE SSANGPIEUP-E-NIEUNHIEUH 9678 BEF3 # HANGUL SYLLABLE SSANGPIEUP-E-TIKEUT 9679 BEF4 # HANGUL SYLLABLE SSANGPIEUP-E-RIEUL 967A BEF5 # HANGUL SYLLABLE SSANGPIEUP-E-RIEULKIYEOK 9681 BEF6 # HANGUL SYLLABLE SSANGPIEUP-E-RIEULMIEUM 9682 BEF7 # HANGUL SYLLABLE SSANGPIEUP-E-RIEULPIEUP 9683 BEF8 # HANGUL SYLLABLE SSANGPIEUP-E-RIEULSIOS 9684 BEF9 # HANGUL SYLLABLE SSANGPIEUP-E-RIEULTHIEUTH 9685 BEFA # HANGUL SYLLABLE SSANGPIEUP-E-RIEULPHIEUPH 9686 BEFB # HANGUL SYLLABLE SSANGPIEUP-E-RIEULHIEUH 9687 BEFC # HANGUL SYLLABLE SSANGPIEUP-E-MIEUM 9688 BEFD # HANGUL SYLLABLE SSANGPIEUP-E-PIEUP 9689 BEFE # HANGUL SYLLABLE SSANGPIEUP-E-PIEUPSIOS 968A BEFF # HANGUL SYLLABLE SSANGPIEUP-E-SIOS 968B BF00 # HANGUL SYLLABLE SSANGPIEUP-E-SSANGSIOS 968C BF02 # HANGUL SYLLABLE SSANGPIEUP-E-CIEUC 968D BF03 # HANGUL SYLLABLE SSANGPIEUP-E-CHIEUCH 968E BF04 # HANGUL SYLLABLE SSANGPIEUP-E-KHIEUKH 968F BF05 # HANGUL SYLLABLE SSANGPIEUP-E-THIEUTH 9690 BF06 # HANGUL SYLLABLE SSANGPIEUP-E-PHIEUPH 9691 BF07 # HANGUL SYLLABLE SSANGPIEUP-E-HIEUH 9692 BF0A # HANGUL SYLLABLE SSANGPIEUP-YEO-SSANGKIYEOK 9693 BF0B # HANGUL SYLLABLE SSANGPIEUP-YEO-KIYEOKSIOS 9694 BF0C # HANGUL SYLLABLE SSANGPIEUP-YEO-NIEUN 9695 BF0D # HANGUL SYLLABLE SSANGPIEUP-YEO-NIEUNCIEUC 9696 BF0E # HANGUL SYLLABLE SSANGPIEUP-YEO-NIEUNHIEUH 9697 BF0F # HANGUL SYLLABLE SSANGPIEUP-YEO-TIKEUT 9698 BF10 # HANGUL SYLLABLE SSANGPIEUP-YEO-RIEUL 9699 BF11 # HANGUL SYLLABLE SSANGPIEUP-YEO-RIEULKIYEOK 969A BF12 # HANGUL SYLLABLE SSANGPIEUP-YEO-RIEULMIEUM 969B BF13 # HANGUL SYLLABLE SSANGPIEUP-YEO-RIEULPIEUP 969C BF14 # HANGUL SYLLABLE SSANGPIEUP-YEO-RIEULSIOS 969D BF15 # HANGUL SYLLABLE SSANGPIEUP-YEO-RIEULTHIEUTH 969E BF16 # HANGUL SYLLABLE SSANGPIEUP-YEO-RIEULPHIEUPH 969F BF17 # HANGUL SYLLABLE SSANGPIEUP-YEO-RIEULHIEUH 96A0 BF1A # HANGUL SYLLABLE SSANGPIEUP-YEO-PIEUPSIOS 96A1 BF1E # HANGUL SYLLABLE SSANGPIEUP-YEO-CIEUC 96A2 BF1F # HANGUL SYLLABLE SSANGPIEUP-YEO-CHIEUCH 96A3 BF20 # HANGUL SYLLABLE SSANGPIEUP-YEO-KHIEUKH 96A4 BF21 # HANGUL SYLLABLE SSANGPIEUP-YEO-THIEUTH 96A5 BF22 # HANGUL SYLLABLE SSANGPIEUP-YEO-PHIEUPH 96A6 BF23 # HANGUL SYLLABLE SSANGPIEUP-YEO-HIEUH 96A7 BF24 # HANGUL SYLLABLE SSANGPIEUP-YE 96A8 BF25 # HANGUL SYLLABLE SSANGPIEUP-YE-KIYEOK 96A9 BF26 # HANGUL SYLLABLE SSANGPIEUP-YE-SSANGKIYEOK 96AA BF27 # HANGUL SYLLABLE SSANGPIEUP-YE-KIYEOKSIOS 96AB BF28 # HANGUL SYLLABLE SSANGPIEUP-YE-NIEUN 96AC BF29 # HANGUL SYLLABLE SSANGPIEUP-YE-NIEUNCIEUC 96AD BF2A # HANGUL SYLLABLE SSANGPIEUP-YE-NIEUNHIEUH 96AE BF2B # HANGUL SYLLABLE SSANGPIEUP-YE-TIKEUT 96AF BF2C # HANGUL SYLLABLE SSANGPIEUP-YE-RIEUL 96B0 BF2D # HANGUL SYLLABLE SSANGPIEUP-YE-RIEULKIYEOK 96B1 BF2E # HANGUL SYLLABLE SSANGPIEUP-YE-RIEULMIEUM 96B2 BF2F # HANGUL SYLLABLE SSANGPIEUP-YE-RIEULPIEUP 96B3 BF30 # HANGUL SYLLABLE SSANGPIEUP-YE-RIEULSIOS 96B4 BF31 # HANGUL SYLLABLE SSANGPIEUP-YE-RIEULTHIEUTH 96B5 BF32 # HANGUL SYLLABLE SSANGPIEUP-YE-RIEULPHIEUPH 96B6 BF33 # HANGUL SYLLABLE SSANGPIEUP-YE-RIEULHIEUH 96B7 BF34 # HANGUL SYLLABLE SSANGPIEUP-YE-MIEUM 96B8 BF35 # HANGUL SYLLABLE SSANGPIEUP-YE-PIEUP 96B9 BF36 # HANGUL SYLLABLE SSANGPIEUP-YE-PIEUPSIOS 96BA BF37 # HANGUL SYLLABLE SSANGPIEUP-YE-SIOS 96BB BF38 # HANGUL SYLLABLE SSANGPIEUP-YE-SSANGSIOS 96BC BF39 # HANGUL SYLLABLE SSANGPIEUP-YE-IEUNG 96BD BF3A # HANGUL SYLLABLE SSANGPIEUP-YE-CIEUC 96BE BF3B # HANGUL SYLLABLE SSANGPIEUP-YE-CHIEUCH 96BF BF3C # HANGUL SYLLABLE SSANGPIEUP-YE-KHIEUKH 96C0 BF3D # HANGUL SYLLABLE SSANGPIEUP-YE-THIEUTH 96C1 BF3E # HANGUL SYLLABLE SSANGPIEUP-YE-PHIEUPH 96C2 BF3F # HANGUL SYLLABLE SSANGPIEUP-YE-HIEUH 96C3 BF42 # HANGUL SYLLABLE SSANGPIEUP-O-SSANGKIYEOK 96C4 BF43 # HANGUL SYLLABLE SSANGPIEUP-O-KIYEOKSIOS 96C5 BF45 # HANGUL SYLLABLE SSANGPIEUP-O-NIEUNCIEUC 96C6 BF46 # HANGUL SYLLABLE SSANGPIEUP-O-NIEUNHIEUH 96C7 BF47 # HANGUL SYLLABLE SSANGPIEUP-O-TIKEUT 96C8 BF49 # HANGUL SYLLABLE SSANGPIEUP-O-RIEULKIYEOK 96C9 BF4A # HANGUL SYLLABLE SSANGPIEUP-O-RIEULMIEUM 96CA BF4B # HANGUL SYLLABLE SSANGPIEUP-O-RIEULPIEUP 96CB BF4C # HANGUL SYLLABLE SSANGPIEUP-O-RIEULSIOS 96CC BF4D # HANGUL SYLLABLE SSANGPIEUP-O-RIEULTHIEUTH 96CD BF4E # HANGUL SYLLABLE SSANGPIEUP-O-RIEULPHIEUPH 96CE BF4F # HANGUL SYLLABLE SSANGPIEUP-O-RIEULHIEUH 96CF BF52 # HANGUL SYLLABLE SSANGPIEUP-O-PIEUPSIOS 96D0 BF53 # HANGUL SYLLABLE SSANGPIEUP-O-SIOS 96D1 BF54 # HANGUL SYLLABLE SSANGPIEUP-O-SSANGSIOS 96D2 BF56 # HANGUL SYLLABLE SSANGPIEUP-O-CIEUC 96D3 BF57 # HANGUL SYLLABLE SSANGPIEUP-O-CHIEUCH 96D4 BF58 # HANGUL SYLLABLE SSANGPIEUP-O-KHIEUKH 96D5 BF59 # HANGUL SYLLABLE SSANGPIEUP-O-THIEUTH 96D6 BF5A # HANGUL SYLLABLE SSANGPIEUP-O-PHIEUPH 96D7 BF5B # HANGUL SYLLABLE SSANGPIEUP-O-HIEUH 96D8 BF5C # HANGUL SYLLABLE SSANGPIEUP-WA 96D9 BF5D # HANGUL SYLLABLE SSANGPIEUP-WA-KIYEOK 96DA BF5E # HANGUL SYLLABLE SSANGPIEUP-WA-SSANGKIYEOK 96DB BF5F # HANGUL SYLLABLE SSANGPIEUP-WA-KIYEOKSIOS 96DC BF60 # HANGUL SYLLABLE SSANGPIEUP-WA-NIEUN 96DD BF61 # HANGUL SYLLABLE SSANGPIEUP-WA-NIEUNCIEUC 96DE BF62 # HANGUL SYLLABLE SSANGPIEUP-WA-NIEUNHIEUH 96DF BF63 # HANGUL SYLLABLE SSANGPIEUP-WA-TIKEUT 96E0 BF64 # HANGUL SYLLABLE SSANGPIEUP-WA-RIEUL 96E1 BF65 # HANGUL SYLLABLE SSANGPIEUP-WA-RIEULKIYEOK 96E2 BF66 # HANGUL SYLLABLE SSANGPIEUP-WA-RIEULMIEUM 96E3 BF67 # HANGUL SYLLABLE SSANGPIEUP-WA-RIEULPIEUP 96E4 BF68 # HANGUL SYLLABLE SSANGPIEUP-WA-RIEULSIOS 96E5 BF69 # HANGUL SYLLABLE SSANGPIEUP-WA-RIEULTHIEUTH 96E6 BF6A # HANGUL SYLLABLE SSANGPIEUP-WA-RIEULPHIEUPH 96E7 BF6B # HANGUL SYLLABLE SSANGPIEUP-WA-RIEULHIEUH 96E8 BF6C # HANGUL SYLLABLE SSANGPIEUP-WA-MIEUM 96E9 BF6D # HANGUL SYLLABLE SSANGPIEUP-WA-PIEUP 96EA BF6E # HANGUL SYLLABLE SSANGPIEUP-WA-PIEUPSIOS 96EB BF6F # HANGUL SYLLABLE SSANGPIEUP-WA-SIOS 96EC BF70 # HANGUL SYLLABLE SSANGPIEUP-WA-SSANGSIOS 96ED BF71 # HANGUL SYLLABLE SSANGPIEUP-WA-IEUNG 96EE BF72 # HANGUL SYLLABLE SSANGPIEUP-WA-CIEUC 96EF BF73 # HANGUL SYLLABLE SSANGPIEUP-WA-CHIEUCH 96F0 BF74 # HANGUL SYLLABLE SSANGPIEUP-WA-KHIEUKH 96F1 BF75 # HANGUL SYLLABLE SSANGPIEUP-WA-THIEUTH 96F2 BF76 # HANGUL SYLLABLE SSANGPIEUP-WA-PHIEUPH 96F3 BF77 # HANGUL SYLLABLE SSANGPIEUP-WA-HIEUH 96F4 BF78 # HANGUL SYLLABLE SSANGPIEUP-WAE 96F5 BF79 # HANGUL SYLLABLE SSANGPIEUP-WAE-KIYEOK 96F6 BF7A # HANGUL SYLLABLE SSANGPIEUP-WAE-SSANGKIYEOK 96F7 BF7B # HANGUL SYLLABLE SSANGPIEUP-WAE-KIYEOKSIOS 96F8 BF7C # HANGUL SYLLABLE SSANGPIEUP-WAE-NIEUN 96F9 BF7D # HANGUL SYLLABLE SSANGPIEUP-WAE-NIEUNCIEUC 96FA BF7E # HANGUL SYLLABLE SSANGPIEUP-WAE-NIEUNHIEUH 96FB BF7F # HANGUL SYLLABLE SSANGPIEUP-WAE-TIKEUT 96FC BF80 # HANGUL SYLLABLE SSANGPIEUP-WAE-RIEUL 96FD BF81 # HANGUL SYLLABLE SSANGPIEUP-WAE-RIEULKIYEOK 96FE BF82 # HANGUL SYLLABLE SSANGPIEUP-WAE-RIEULMIEUM 9741 BF83 # HANGUL SYLLABLE SSANGPIEUP-WAE-RIEULPIEUP 9742 BF84 # HANGUL SYLLABLE SSANGPIEUP-WAE-RIEULSIOS 9743 BF85 # HANGUL SYLLABLE SSANGPIEUP-WAE-RIEULTHIEUTH 9744 BF86 # HANGUL SYLLABLE SSANGPIEUP-WAE-RIEULPHIEUPH 9745 BF87 # HANGUL SYLLABLE SSANGPIEUP-WAE-RIEULHIEUH 9746 BF88 # HANGUL SYLLABLE SSANGPIEUP-WAE-MIEUM 9747 BF89 # HANGUL SYLLABLE SSANGPIEUP-WAE-PIEUP 9748 BF8A # HANGUL SYLLABLE SSANGPIEUP-WAE-PIEUPSIOS 9749 BF8B # HANGUL SYLLABLE SSANGPIEUP-WAE-SIOS 974A BF8C # HANGUL SYLLABLE SSANGPIEUP-WAE-SSANGSIOS 974B BF8D # HANGUL SYLLABLE SSANGPIEUP-WAE-IEUNG 974C BF8E # HANGUL SYLLABLE SSANGPIEUP-WAE-CIEUC 974D BF8F # HANGUL SYLLABLE SSANGPIEUP-WAE-CHIEUCH 974E BF90 # HANGUL SYLLABLE SSANGPIEUP-WAE-KHIEUKH 974F BF91 # HANGUL SYLLABLE SSANGPIEUP-WAE-THIEUTH 9750 BF92 # HANGUL SYLLABLE SSANGPIEUP-WAE-PHIEUPH 9751 BF93 # HANGUL SYLLABLE SSANGPIEUP-WAE-HIEUH 9752 BF95 # HANGUL SYLLABLE SSANGPIEUP-OE-KIYEOK 9753 BF96 # HANGUL SYLLABLE SSANGPIEUP-OE-SSANGKIYEOK 9754 BF97 # HANGUL SYLLABLE SSANGPIEUP-OE-KIYEOKSIOS 9755 BF98 # HANGUL SYLLABLE SSANGPIEUP-OE-NIEUN 9756 BF99 # HANGUL SYLLABLE SSANGPIEUP-OE-NIEUNCIEUC 9757 BF9A # HANGUL SYLLABLE SSANGPIEUP-OE-NIEUNHIEUH 9758 BF9B # HANGUL SYLLABLE SSANGPIEUP-OE-TIKEUT 9759 BF9C # HANGUL SYLLABLE SSANGPIEUP-OE-RIEUL 975A BF9D # HANGUL SYLLABLE SSANGPIEUP-OE-RIEULKIYEOK 9761 BF9E # HANGUL SYLLABLE SSANGPIEUP-OE-RIEULMIEUM 9762 BF9F # HANGUL SYLLABLE SSANGPIEUP-OE-RIEULPIEUP 9763 BFA0 # HANGUL SYLLABLE SSANGPIEUP-OE-RIEULSIOS 9764 BFA1 # HANGUL SYLLABLE SSANGPIEUP-OE-RIEULTHIEUTH 9765 BFA2 # HANGUL SYLLABLE SSANGPIEUP-OE-RIEULPHIEUPH 9766 BFA3 # HANGUL SYLLABLE SSANGPIEUP-OE-RIEULHIEUH 9767 BFA4 # HANGUL SYLLABLE SSANGPIEUP-OE-MIEUM 9768 BFA5 # HANGUL SYLLABLE SSANGPIEUP-OE-PIEUP 9769 BFA6 # HANGUL SYLLABLE SSANGPIEUP-OE-PIEUPSIOS 976A BFA7 # HANGUL SYLLABLE SSANGPIEUP-OE-SIOS 976B BFA8 # HANGUL SYLLABLE SSANGPIEUP-OE-SSANGSIOS 976C BFA9 # HANGUL SYLLABLE SSANGPIEUP-OE-IEUNG 976D BFAA # HANGUL SYLLABLE SSANGPIEUP-OE-CIEUC 976E BFAB # HANGUL SYLLABLE SSANGPIEUP-OE-CHIEUCH 976F BFAC # HANGUL SYLLABLE SSANGPIEUP-OE-KHIEUKH 9770 BFAD # HANGUL SYLLABLE SSANGPIEUP-OE-THIEUTH 9771 BFAE # HANGUL SYLLABLE SSANGPIEUP-OE-PHIEUPH 9772 BFAF # HANGUL SYLLABLE SSANGPIEUP-OE-HIEUH 9773 BFB1 # HANGUL SYLLABLE SSANGPIEUP-YO-KIYEOK 9774 BFB2 # HANGUL SYLLABLE SSANGPIEUP-YO-SSANGKIYEOK 9775 BFB3 # HANGUL SYLLABLE SSANGPIEUP-YO-KIYEOKSIOS 9776 BFB4 # HANGUL SYLLABLE SSANGPIEUP-YO-NIEUN 9777 BFB5 # HANGUL SYLLABLE SSANGPIEUP-YO-NIEUNCIEUC 9778 BFB6 # HANGUL SYLLABLE SSANGPIEUP-YO-NIEUNHIEUH 9779 BFB7 # HANGUL SYLLABLE SSANGPIEUP-YO-TIKEUT 977A BFB8 # HANGUL SYLLABLE SSANGPIEUP-YO-RIEUL 9781 BFB9 # HANGUL SYLLABLE SSANGPIEUP-YO-RIEULKIYEOK 9782 BFBA # HANGUL SYLLABLE SSANGPIEUP-YO-RIEULMIEUM 9783 BFBB # HANGUL SYLLABLE SSANGPIEUP-YO-RIEULPIEUP 9784 BFBC # HANGUL SYLLABLE SSANGPIEUP-YO-RIEULSIOS 9785 BFBD # HANGUL SYLLABLE SSANGPIEUP-YO-RIEULTHIEUTH 9786 BFBE # HANGUL SYLLABLE SSANGPIEUP-YO-RIEULPHIEUPH 9787 BFBF # HANGUL SYLLABLE SSANGPIEUP-YO-RIEULHIEUH 9788 BFC0 # HANGUL SYLLABLE SSANGPIEUP-YO-MIEUM 9789 BFC1 # HANGUL SYLLABLE SSANGPIEUP-YO-PIEUP 978A BFC2 # HANGUL SYLLABLE SSANGPIEUP-YO-PIEUPSIOS 978B BFC3 # HANGUL SYLLABLE SSANGPIEUP-YO-SIOS 978C BFC4 # HANGUL SYLLABLE SSANGPIEUP-YO-SSANGSIOS 978D BFC6 # HANGUL SYLLABLE SSANGPIEUP-YO-CIEUC 978E BFC7 # HANGUL SYLLABLE SSANGPIEUP-YO-CHIEUCH 978F BFC8 # HANGUL SYLLABLE SSANGPIEUP-YO-KHIEUKH 9790 BFC9 # HANGUL SYLLABLE SSANGPIEUP-YO-THIEUTH 9791 BFCA # HANGUL SYLLABLE SSANGPIEUP-YO-PHIEUPH 9792 BFCB # HANGUL SYLLABLE SSANGPIEUP-YO-HIEUH 9793 BFCE # HANGUL SYLLABLE SSANGPIEUP-U-SSANGKIYEOK 9794 BFCF # HANGUL SYLLABLE SSANGPIEUP-U-KIYEOKSIOS 9795 BFD1 # HANGUL SYLLABLE SSANGPIEUP-U-NIEUNCIEUC 9796 BFD2 # HANGUL SYLLABLE SSANGPIEUP-U-NIEUNHIEUH 9797 BFD3 # HANGUL SYLLABLE SSANGPIEUP-U-TIKEUT 9798 BFD5 # HANGUL SYLLABLE SSANGPIEUP-U-RIEULKIYEOK 9799 BFD6 # HANGUL SYLLABLE SSANGPIEUP-U-RIEULMIEUM 979A BFD7 # HANGUL SYLLABLE SSANGPIEUP-U-RIEULPIEUP 979B BFD8 # HANGUL SYLLABLE SSANGPIEUP-U-RIEULSIOS 979C BFD9 # HANGUL SYLLABLE SSANGPIEUP-U-RIEULTHIEUTH 979D BFDA # HANGUL SYLLABLE SSANGPIEUP-U-RIEULPHIEUPH 979E BFDB # HANGUL SYLLABLE SSANGPIEUP-U-RIEULHIEUH 979F BFDD # HANGUL SYLLABLE SSANGPIEUP-U-PIEUP 97A0 BFDE # HANGUL SYLLABLE SSANGPIEUP-U-PIEUPSIOS 97A1 BFE0 # HANGUL SYLLABLE SSANGPIEUP-U-SSANGSIOS 97A2 BFE2 # HANGUL SYLLABLE SSANGPIEUP-U-CIEUC 97A3 BFE3 # HANGUL SYLLABLE SSANGPIEUP-U-CHIEUCH 97A4 BFE4 # HANGUL SYLLABLE SSANGPIEUP-U-KHIEUKH 97A5 BFE5 # HANGUL SYLLABLE SSANGPIEUP-U-THIEUTH 97A6 BFE6 # HANGUL SYLLABLE SSANGPIEUP-U-PHIEUPH 97A7 BFE7 # HANGUL SYLLABLE SSANGPIEUP-U-HIEUH 97A8 BFE8 # HANGUL SYLLABLE SSANGPIEUP-WEO 97A9 BFE9 # HANGUL SYLLABLE SSANGPIEUP-WEO-KIYEOK 97AA BFEA # HANGUL SYLLABLE SSANGPIEUP-WEO-SSANGKIYEOK 97AB BFEB # HANGUL SYLLABLE SSANGPIEUP-WEO-KIYEOKSIOS 97AC BFEC # HANGUL SYLLABLE SSANGPIEUP-WEO-NIEUN 97AD BFED # HANGUL SYLLABLE SSANGPIEUP-WEO-NIEUNCIEUC 97AE BFEE # HANGUL SYLLABLE SSANGPIEUP-WEO-NIEUNHIEUH 97AF BFEF # HANGUL SYLLABLE SSANGPIEUP-WEO-TIKEUT 97B0 BFF0 # HANGUL SYLLABLE SSANGPIEUP-WEO-RIEUL 97B1 BFF1 # HANGUL SYLLABLE SSANGPIEUP-WEO-RIEULKIYEOK 97B2 BFF2 # HANGUL SYLLABLE SSANGPIEUP-WEO-RIEULMIEUM 97B3 BFF3 # HANGUL SYLLABLE SSANGPIEUP-WEO-RIEULPIEUP 97B4 BFF4 # HANGUL SYLLABLE SSANGPIEUP-WEO-RIEULSIOS 97B5 BFF5 # HANGUL SYLLABLE SSANGPIEUP-WEO-RIEULTHIEUTH 97B6 BFF6 # HANGUL SYLLABLE SSANGPIEUP-WEO-RIEULPHIEUPH 97B7 BFF7 # HANGUL SYLLABLE SSANGPIEUP-WEO-RIEULHIEUH 97B8 BFF8 # HANGUL SYLLABLE SSANGPIEUP-WEO-MIEUM 97B9 BFF9 # HANGUL SYLLABLE SSANGPIEUP-WEO-PIEUP 97BA BFFA # HANGUL SYLLABLE SSANGPIEUP-WEO-PIEUPSIOS 97BB BFFB # HANGUL SYLLABLE SSANGPIEUP-WEO-SIOS 97BC BFFC # HANGUL SYLLABLE SSANGPIEUP-WEO-SSANGSIOS 97BD BFFD # HANGUL SYLLABLE SSANGPIEUP-WEO-IEUNG 97BE BFFE # HANGUL SYLLABLE SSANGPIEUP-WEO-CIEUC 97BF BFFF # HANGUL SYLLABLE SSANGPIEUP-WEO-CHIEUCH 97C0 C000 # HANGUL SYLLABLE SSANGPIEUP-WEO-KHIEUKH 97C1 C001 # HANGUL SYLLABLE SSANGPIEUP-WEO-THIEUTH 97C2 C002 # HANGUL SYLLABLE SSANGPIEUP-WEO-PHIEUPH 97C3 C003 # HANGUL SYLLABLE SSANGPIEUP-WEO-HIEUH 97C4 C004 # HANGUL SYLLABLE SSANGPIEUP-WE 97C5 C005 # HANGUL SYLLABLE SSANGPIEUP-WE-KIYEOK 97C6 C006 # HANGUL SYLLABLE SSANGPIEUP-WE-SSANGKIYEOK 97C7 C007 # HANGUL SYLLABLE SSANGPIEUP-WE-KIYEOKSIOS 97C8 C008 # HANGUL SYLLABLE SSANGPIEUP-WE-NIEUN 97C9 C009 # HANGUL SYLLABLE SSANGPIEUP-WE-NIEUNCIEUC 97CA C00A # HANGUL SYLLABLE SSANGPIEUP-WE-NIEUNHIEUH 97CB C00B # HANGUL SYLLABLE SSANGPIEUP-WE-TIKEUT 97CC C00C # HANGUL SYLLABLE SSANGPIEUP-WE-RIEUL 97CD C00D # HANGUL SYLLABLE SSANGPIEUP-WE-RIEULKIYEOK 97CE C00E # HANGUL SYLLABLE SSANGPIEUP-WE-RIEULMIEUM 97CF C00F # HANGUL SYLLABLE SSANGPIEUP-WE-RIEULPIEUP 97D0 C010 # HANGUL SYLLABLE SSANGPIEUP-WE-RIEULSIOS 97D1 C011 # HANGUL SYLLABLE SSANGPIEUP-WE-RIEULTHIEUTH 97D2 C012 # HANGUL SYLLABLE SSANGPIEUP-WE-RIEULPHIEUPH 97D3 C013 # HANGUL SYLLABLE SSANGPIEUP-WE-RIEULHIEUH 97D4 C014 # HANGUL SYLLABLE SSANGPIEUP-WE-MIEUM 97D5 C015 # HANGUL SYLLABLE SSANGPIEUP-WE-PIEUP 97D6 C016 # HANGUL SYLLABLE SSANGPIEUP-WE-PIEUPSIOS 97D7 C017 # HANGUL SYLLABLE SSANGPIEUP-WE-SIOS 97D8 C018 # HANGUL SYLLABLE SSANGPIEUP-WE-SSANGSIOS 97D9 C019 # HANGUL SYLLABLE SSANGPIEUP-WE-IEUNG 97DA C01A # HANGUL SYLLABLE SSANGPIEUP-WE-CIEUC 97DB C01B # HANGUL SYLLABLE SSANGPIEUP-WE-CHIEUCH 97DC C01C # HANGUL SYLLABLE SSANGPIEUP-WE-KHIEUKH 97DD C01D # HANGUL SYLLABLE SSANGPIEUP-WE-THIEUTH 97DE C01E # HANGUL SYLLABLE SSANGPIEUP-WE-PHIEUPH 97DF C01F # HANGUL SYLLABLE SSANGPIEUP-WE-HIEUH 97E0 C020 # HANGUL SYLLABLE SSANGPIEUP-WI 97E1 C021 # HANGUL SYLLABLE SSANGPIEUP-WI-KIYEOK 97E2 C022 # HANGUL SYLLABLE SSANGPIEUP-WI-SSANGKIYEOK 97E3 C023 # HANGUL SYLLABLE SSANGPIEUP-WI-KIYEOKSIOS 97E4 C024 # HANGUL SYLLABLE SSANGPIEUP-WI-NIEUN 97E5 C025 # HANGUL SYLLABLE SSANGPIEUP-WI-NIEUNCIEUC 97E6 C026 # HANGUL SYLLABLE SSANGPIEUP-WI-NIEUNHIEUH 97E7 C027 # HANGUL SYLLABLE SSANGPIEUP-WI-TIKEUT 97E8 C028 # HANGUL SYLLABLE SSANGPIEUP-WI-RIEUL 97E9 C029 # HANGUL SYLLABLE SSANGPIEUP-WI-RIEULKIYEOK 97EA C02A # HANGUL SYLLABLE SSANGPIEUP-WI-RIEULMIEUM 97EB C02B # HANGUL SYLLABLE SSANGPIEUP-WI-RIEULPIEUP 97EC C02C # HANGUL SYLLABLE SSANGPIEUP-WI-RIEULSIOS 97ED C02D # HANGUL SYLLABLE SSANGPIEUP-WI-RIEULTHIEUTH 97EE C02E # HANGUL SYLLABLE SSANGPIEUP-WI-RIEULPHIEUPH 97EF C02F # HANGUL SYLLABLE SSANGPIEUP-WI-RIEULHIEUH 97F0 C030 # HANGUL SYLLABLE SSANGPIEUP-WI-MIEUM 97F1 C031 # HANGUL SYLLABLE SSANGPIEUP-WI-PIEUP 97F2 C032 # HANGUL SYLLABLE SSANGPIEUP-WI-PIEUPSIOS 97F3 C033 # HANGUL SYLLABLE SSANGPIEUP-WI-SIOS 97F4 C034 # HANGUL SYLLABLE SSANGPIEUP-WI-SSANGSIOS 97F5 C035 # HANGUL SYLLABLE SSANGPIEUP-WI-IEUNG 97F6 C036 # HANGUL SYLLABLE SSANGPIEUP-WI-CIEUC 97F7 C037 # HANGUL SYLLABLE SSANGPIEUP-WI-CHIEUCH 97F8 C038 # HANGUL SYLLABLE SSANGPIEUP-WI-KHIEUKH 97F9 C039 # HANGUL SYLLABLE SSANGPIEUP-WI-THIEUTH 97FA C03A # HANGUL SYLLABLE SSANGPIEUP-WI-PHIEUPH 97FB C03B # HANGUL SYLLABLE SSANGPIEUP-WI-HIEUH 97FC C03D # HANGUL SYLLABLE SSANGPIEUP-YU-KIYEOK 97FD C03E # HANGUL SYLLABLE SSANGPIEUP-YU-SSANGKIYEOK 97FE C03F # HANGUL SYLLABLE SSANGPIEUP-YU-KIYEOKSIOS 9841 C040 # HANGUL SYLLABLE SSANGPIEUP-YU-NIEUN 9842 C041 # HANGUL SYLLABLE SSANGPIEUP-YU-NIEUNCIEUC 9843 C042 # HANGUL SYLLABLE SSANGPIEUP-YU-NIEUNHIEUH 9844 C043 # HANGUL SYLLABLE SSANGPIEUP-YU-TIKEUT 9845 C044 # HANGUL SYLLABLE SSANGPIEUP-YU-RIEUL 9846 C045 # HANGUL SYLLABLE SSANGPIEUP-YU-RIEULKIYEOK 9847 C046 # HANGUL SYLLABLE SSANGPIEUP-YU-RIEULMIEUM 9848 C047 # HANGUL SYLLABLE SSANGPIEUP-YU-RIEULPIEUP 9849 C048 # HANGUL SYLLABLE SSANGPIEUP-YU-RIEULSIOS 984A C049 # HANGUL SYLLABLE SSANGPIEUP-YU-RIEULTHIEUTH 984B C04A # HANGUL SYLLABLE SSANGPIEUP-YU-RIEULPHIEUPH 984C C04B # HANGUL SYLLABLE SSANGPIEUP-YU-RIEULHIEUH 984D C04C # HANGUL SYLLABLE SSANGPIEUP-YU-MIEUM 984E C04D # HANGUL SYLLABLE SSANGPIEUP-YU-PIEUP 984F C04E # HANGUL SYLLABLE SSANGPIEUP-YU-PIEUPSIOS 9850 C04F # HANGUL SYLLABLE SSANGPIEUP-YU-SIOS 9851 C050 # HANGUL SYLLABLE SSANGPIEUP-YU-SSANGSIOS 9852 C052 # HANGUL SYLLABLE SSANGPIEUP-YU-CIEUC 9853 C053 # HANGUL SYLLABLE SSANGPIEUP-YU-CHIEUCH 9854 C054 # HANGUL SYLLABLE SSANGPIEUP-YU-KHIEUKH 9855 C055 # HANGUL SYLLABLE SSANGPIEUP-YU-THIEUTH 9856 C056 # HANGUL SYLLABLE SSANGPIEUP-YU-PHIEUPH 9857 C057 # HANGUL SYLLABLE SSANGPIEUP-YU-HIEUH 9858 C059 # HANGUL SYLLABLE SSANGPIEUP-EU-KIYEOK 9859 C05A # HANGUL SYLLABLE SSANGPIEUP-EU-SSANGKIYEOK 985A C05B # HANGUL SYLLABLE SSANGPIEUP-EU-KIYEOKSIOS 9861 C05D # HANGUL SYLLABLE SSANGPIEUP-EU-NIEUNCIEUC 9862 C05E # HANGUL SYLLABLE SSANGPIEUP-EU-NIEUNHIEUH 9863 C05F # HANGUL SYLLABLE SSANGPIEUP-EU-TIKEUT 9864 C061 # HANGUL SYLLABLE SSANGPIEUP-EU-RIEULKIYEOK 9865 C062 # HANGUL SYLLABLE SSANGPIEUP-EU-RIEULMIEUM 9866 C063 # HANGUL SYLLABLE SSANGPIEUP-EU-RIEULPIEUP 9867 C064 # HANGUL SYLLABLE SSANGPIEUP-EU-RIEULSIOS 9868 C065 # HANGUL SYLLABLE SSANGPIEUP-EU-RIEULTHIEUTH 9869 C066 # HANGUL SYLLABLE SSANGPIEUP-EU-RIEULPHIEUPH 986A C067 # HANGUL SYLLABLE SSANGPIEUP-EU-RIEULHIEUH 986B C06A # HANGUL SYLLABLE SSANGPIEUP-EU-PIEUPSIOS 986C C06B # HANGUL SYLLABLE SSANGPIEUP-EU-SIOS 986D C06C # HANGUL SYLLABLE SSANGPIEUP-EU-SSANGSIOS 986E C06D # HANGUL SYLLABLE SSANGPIEUP-EU-IEUNG 986F C06E # HANGUL SYLLABLE SSANGPIEUP-EU-CIEUC 9870 C06F # HANGUL SYLLABLE SSANGPIEUP-EU-CHIEUCH 9871 C070 # HANGUL SYLLABLE SSANGPIEUP-EU-KHIEUKH 9872 C071 # HANGUL SYLLABLE SSANGPIEUP-EU-THIEUTH 9873 C072 # HANGUL SYLLABLE SSANGPIEUP-EU-PHIEUPH 9874 C073 # HANGUL SYLLABLE SSANGPIEUP-EU-HIEUH 9875 C074 # HANGUL SYLLABLE SSANGPIEUP-YI 9876 C075 # HANGUL SYLLABLE SSANGPIEUP-YI-KIYEOK 9877 C076 # HANGUL SYLLABLE SSANGPIEUP-YI-SSANGKIYEOK 9878 C077 # HANGUL SYLLABLE SSANGPIEUP-YI-KIYEOKSIOS 9879 C078 # HANGUL SYLLABLE SSANGPIEUP-YI-NIEUN 987A C079 # HANGUL SYLLABLE SSANGPIEUP-YI-NIEUNCIEUC 9881 C07A # HANGUL SYLLABLE SSANGPIEUP-YI-NIEUNHIEUH 9882 C07B # HANGUL SYLLABLE SSANGPIEUP-YI-TIKEUT 9883 C07C # HANGUL SYLLABLE SSANGPIEUP-YI-RIEUL 9884 C07D # HANGUL SYLLABLE SSANGPIEUP-YI-RIEULKIYEOK 9885 C07E # HANGUL SYLLABLE SSANGPIEUP-YI-RIEULMIEUM 9886 C07F # HANGUL SYLLABLE SSANGPIEUP-YI-RIEULPIEUP 9887 C080 # HANGUL SYLLABLE SSANGPIEUP-YI-RIEULSIOS 9888 C081 # HANGUL SYLLABLE SSANGPIEUP-YI-RIEULTHIEUTH 9889 C082 # HANGUL SYLLABLE SSANGPIEUP-YI-RIEULPHIEUPH 988A C083 # HANGUL SYLLABLE SSANGPIEUP-YI-RIEULHIEUH 988B C084 # HANGUL SYLLABLE SSANGPIEUP-YI-MIEUM 988C C085 # HANGUL SYLLABLE SSANGPIEUP-YI-PIEUP 988D C086 # HANGUL SYLLABLE SSANGPIEUP-YI-PIEUPSIOS 988E C087 # HANGUL SYLLABLE SSANGPIEUP-YI-SIOS 988F C088 # HANGUL SYLLABLE SSANGPIEUP-YI-SSANGSIOS 9890 C089 # HANGUL SYLLABLE SSANGPIEUP-YI-IEUNG 9891 C08A # HANGUL SYLLABLE SSANGPIEUP-YI-CIEUC 9892 C08B # HANGUL SYLLABLE SSANGPIEUP-YI-CHIEUCH 9893 C08C # HANGUL SYLLABLE SSANGPIEUP-YI-KHIEUKH 9894 C08D # HANGUL SYLLABLE SSANGPIEUP-YI-THIEUTH 9895 C08E # HANGUL SYLLABLE SSANGPIEUP-YI-PHIEUPH 9896 C08F # HANGUL SYLLABLE SSANGPIEUP-YI-HIEUH 9897 C092 # HANGUL SYLLABLE SSANGPIEUP-I-SSANGKIYEOK 9898 C093 # HANGUL SYLLABLE SSANGPIEUP-I-KIYEOKSIOS 9899 C095 # HANGUL SYLLABLE SSANGPIEUP-I-NIEUNCIEUC 989A C096 # HANGUL SYLLABLE SSANGPIEUP-I-NIEUNHIEUH 989B C097 # HANGUL SYLLABLE SSANGPIEUP-I-TIKEUT 989C C099 # HANGUL SYLLABLE SSANGPIEUP-I-RIEULKIYEOK 989D C09A # HANGUL SYLLABLE SSANGPIEUP-I-RIEULMIEUM 989E C09B # HANGUL SYLLABLE SSANGPIEUP-I-RIEULPIEUP 989F C09C # HANGUL SYLLABLE SSANGPIEUP-I-RIEULSIOS 98A0 C09D # HANGUL SYLLABLE SSANGPIEUP-I-RIEULTHIEUTH 98A1 C09E # HANGUL SYLLABLE SSANGPIEUP-I-RIEULPHIEUPH 98A2 C09F # HANGUL SYLLABLE SSANGPIEUP-I-RIEULHIEUH 98A3 C0A2 # HANGUL SYLLABLE SSANGPIEUP-I-PIEUPSIOS 98A4 C0A4 # HANGUL SYLLABLE SSANGPIEUP-I-SSANGSIOS 98A5 C0A6 # HANGUL SYLLABLE SSANGPIEUP-I-CIEUC 98A6 C0A7 # HANGUL SYLLABLE SSANGPIEUP-I-CHIEUCH 98A7 C0A8 # HANGUL SYLLABLE SSANGPIEUP-I-KHIEUKH 98A8 C0A9 # HANGUL SYLLABLE SSANGPIEUP-I-THIEUTH 98A9 C0AA # HANGUL SYLLABLE SSANGPIEUP-I-PHIEUPH 98AA C0AB # HANGUL SYLLABLE SSANGPIEUP-I-HIEUH 98AB C0AE # HANGUL SYLLABLE SIOS-A-SSANGKIYEOK 98AC C0B1 # HANGUL SYLLABLE SIOS-A-NIEUNCIEUC 98AD C0B2 # HANGUL SYLLABLE SIOS-A-NIEUNHIEUH 98AE C0B7 # HANGUL SYLLABLE SIOS-A-RIEULPIEUP 98AF C0B8 # HANGUL SYLLABLE SIOS-A-RIEULSIOS 98B0 C0B9 # HANGUL SYLLABLE SIOS-A-RIEULTHIEUTH 98B1 C0BA # HANGUL SYLLABLE SIOS-A-RIEULPHIEUPH 98B2 C0BB # HANGUL SYLLABLE SIOS-A-RIEULHIEUH 98B3 C0BE # HANGUL SYLLABLE SIOS-A-PIEUPSIOS 98B4 C0C2 # HANGUL SYLLABLE SIOS-A-CIEUC 98B5 C0C3 # HANGUL SYLLABLE SIOS-A-CHIEUCH 98B6 C0C4 # HANGUL SYLLABLE SIOS-A-KHIEUKH 98B7 C0C6 # HANGUL SYLLABLE SIOS-A-PHIEUPH 98B8 C0C7 # HANGUL SYLLABLE SIOS-A-HIEUH 98B9 C0CA # HANGUL SYLLABLE SIOS-AE-SSANGKIYEOK 98BA C0CB # HANGUL SYLLABLE SIOS-AE-KIYEOKSIOS 98BB C0CD # HANGUL SYLLABLE SIOS-AE-NIEUNCIEUC 98BC C0CE # HANGUL SYLLABLE SIOS-AE-NIEUNHIEUH 98BD C0CF # HANGUL SYLLABLE SIOS-AE-TIKEUT 98BE C0D1 # HANGUL SYLLABLE SIOS-AE-RIEULKIYEOK 98BF C0D2 # HANGUL SYLLABLE SIOS-AE-RIEULMIEUM 98C0 C0D3 # HANGUL SYLLABLE SIOS-AE-RIEULPIEUP 98C1 C0D4 # HANGUL SYLLABLE SIOS-AE-RIEULSIOS 98C2 C0D5 # HANGUL SYLLABLE SIOS-AE-RIEULTHIEUTH 98C3 C0D6 # HANGUL SYLLABLE SIOS-AE-RIEULPHIEUPH 98C4 C0D7 # HANGUL SYLLABLE SIOS-AE-RIEULHIEUH 98C5 C0DA # HANGUL SYLLABLE SIOS-AE-PIEUPSIOS 98C6 C0DE # HANGUL SYLLABLE SIOS-AE-CIEUC 98C7 C0DF # HANGUL SYLLABLE SIOS-AE-CHIEUCH 98C8 C0E0 # HANGUL SYLLABLE SIOS-AE-KHIEUKH 98C9 C0E1 # HANGUL SYLLABLE SIOS-AE-THIEUTH 98CA C0E2 # HANGUL SYLLABLE SIOS-AE-PHIEUPH 98CB C0E3 # HANGUL SYLLABLE SIOS-AE-HIEUH 98CC C0E6 # HANGUL SYLLABLE SIOS-YA-SSANGKIYEOK 98CD C0E7 # HANGUL SYLLABLE SIOS-YA-KIYEOKSIOS 98CE C0E9 # HANGUL SYLLABLE SIOS-YA-NIEUNCIEUC 98CF C0EA # HANGUL SYLLABLE SIOS-YA-NIEUNHIEUH 98D0 C0EB # HANGUL SYLLABLE SIOS-YA-TIKEUT 98D1 C0ED # HANGUL SYLLABLE SIOS-YA-RIEULKIYEOK 98D2 C0EE # HANGUL SYLLABLE SIOS-YA-RIEULMIEUM 98D3 C0EF # HANGUL SYLLABLE SIOS-YA-RIEULPIEUP 98D4 C0F0 # HANGUL SYLLABLE SIOS-YA-RIEULSIOS 98D5 C0F1 # HANGUL SYLLABLE SIOS-YA-RIEULTHIEUTH 98D6 C0F2 # HANGUL SYLLABLE SIOS-YA-RIEULPHIEUPH 98D7 C0F3 # HANGUL SYLLABLE SIOS-YA-RIEULHIEUH 98D8 C0F6 # HANGUL SYLLABLE SIOS-YA-PIEUPSIOS 98D9 C0F8 # HANGUL SYLLABLE SIOS-YA-SSANGSIOS 98DA C0FA # HANGUL SYLLABLE SIOS-YA-CIEUC 98DB C0FB # HANGUL SYLLABLE SIOS-YA-CHIEUCH 98DC C0FC # HANGUL SYLLABLE SIOS-YA-KHIEUKH 98DD C0FD # HANGUL SYLLABLE SIOS-YA-THIEUTH 98DE C0FE # HANGUL SYLLABLE SIOS-YA-PHIEUPH 98DF C0FF # HANGUL SYLLABLE SIOS-YA-HIEUH 98E0 C101 # HANGUL SYLLABLE SIOS-YAE-KIYEOK 98E1 C102 # HANGUL SYLLABLE SIOS-YAE-SSANGKIYEOK 98E2 C103 # HANGUL SYLLABLE SIOS-YAE-KIYEOKSIOS 98E3 C105 # HANGUL SYLLABLE SIOS-YAE-NIEUNCIEUC 98E4 C106 # HANGUL SYLLABLE SIOS-YAE-NIEUNHIEUH 98E5 C107 # HANGUL SYLLABLE SIOS-YAE-TIKEUT 98E6 C109 # HANGUL SYLLABLE SIOS-YAE-RIEULKIYEOK 98E7 C10A # HANGUL SYLLABLE SIOS-YAE-RIEULMIEUM 98E8 C10B # HANGUL SYLLABLE SIOS-YAE-RIEULPIEUP 98E9 C10C # HANGUL SYLLABLE SIOS-YAE-RIEULSIOS 98EA C10D # HANGUL SYLLABLE SIOS-YAE-RIEULTHIEUTH 98EB C10E # HANGUL SYLLABLE SIOS-YAE-RIEULPHIEUPH 98EC C10F # HANGUL SYLLABLE SIOS-YAE-RIEULHIEUH 98ED C111 # HANGUL SYLLABLE SIOS-YAE-PIEUP 98EE C112 # HANGUL SYLLABLE SIOS-YAE-PIEUPSIOS 98EF C113 # HANGUL SYLLABLE SIOS-YAE-SIOS 98F0 C114 # HANGUL SYLLABLE SIOS-YAE-SSANGSIOS 98F1 C116 # HANGUL SYLLABLE SIOS-YAE-CIEUC 98F2 C117 # HANGUL SYLLABLE SIOS-YAE-CHIEUCH 98F3 C118 # HANGUL SYLLABLE SIOS-YAE-KHIEUKH 98F4 C119 # HANGUL SYLLABLE SIOS-YAE-THIEUTH 98F5 C11A # HANGUL SYLLABLE SIOS-YAE-PHIEUPH 98F6 C11B # HANGUL SYLLABLE SIOS-YAE-HIEUH 98F7 C121 # HANGUL SYLLABLE SIOS-EO-NIEUNCIEUC 98F8 C122 # HANGUL SYLLABLE SIOS-EO-NIEUNHIEUH 98F9 C125 # HANGUL SYLLABLE SIOS-EO-RIEULKIYEOK 98FA C128 # HANGUL SYLLABLE SIOS-EO-RIEULSIOS 98FB C129 # HANGUL SYLLABLE SIOS-EO-RIEULTHIEUTH 98FC C12A # HANGUL SYLLABLE SIOS-EO-RIEULPHIEUPH 98FD C12B # HANGUL SYLLABLE SIOS-EO-RIEULHIEUH 98FE C12E # HANGUL SYLLABLE SIOS-EO-PIEUPSIOS 9941 C132 # HANGUL SYLLABLE SIOS-EO-CIEUC 9942 C133 # HANGUL SYLLABLE SIOS-EO-CHIEUCH 9943 C134 # HANGUL SYLLABLE SIOS-EO-KHIEUKH 9944 C135 # HANGUL SYLLABLE SIOS-EO-THIEUTH 9945 C137 # HANGUL SYLLABLE SIOS-EO-HIEUH 9946 C13A # HANGUL SYLLABLE SIOS-E-SSANGKIYEOK 9947 C13B # HANGUL SYLLABLE SIOS-E-KIYEOKSIOS 9948 C13D # HANGUL SYLLABLE SIOS-E-NIEUNCIEUC 9949 C13E # HANGUL SYLLABLE SIOS-E-NIEUNHIEUH 994A C13F # HANGUL SYLLABLE SIOS-E-TIKEUT 994B C141 # HANGUL SYLLABLE SIOS-E-RIEULKIYEOK 994C C142 # HANGUL SYLLABLE SIOS-E-RIEULMIEUM 994D C143 # HANGUL SYLLABLE SIOS-E-RIEULPIEUP 994E C144 # HANGUL SYLLABLE SIOS-E-RIEULSIOS 994F C145 # HANGUL SYLLABLE SIOS-E-RIEULTHIEUTH 9950 C146 # HANGUL SYLLABLE SIOS-E-RIEULPHIEUPH 9951 C147 # HANGUL SYLLABLE SIOS-E-RIEULHIEUH 9952 C14A # HANGUL SYLLABLE SIOS-E-PIEUPSIOS 9953 C14E # HANGUL SYLLABLE SIOS-E-CIEUC 9954 C14F # HANGUL SYLLABLE SIOS-E-CHIEUCH 9955 C150 # HANGUL SYLLABLE SIOS-E-KHIEUKH 9956 C151 # HANGUL SYLLABLE SIOS-E-THIEUTH 9957 C152 # HANGUL SYLLABLE SIOS-E-PHIEUPH 9958 C153 # HANGUL SYLLABLE SIOS-E-HIEUH 9959 C156 # HANGUL SYLLABLE SIOS-YEO-SSANGKIYEOK 995A C157 # HANGUL SYLLABLE SIOS-YEO-KIYEOKSIOS 9961 C159 # HANGUL SYLLABLE SIOS-YEO-NIEUNCIEUC 9962 C15A # HANGUL SYLLABLE SIOS-YEO-NIEUNHIEUH 9963 C15B # HANGUL SYLLABLE SIOS-YEO-TIKEUT 9964 C15D # HANGUL SYLLABLE SIOS-YEO-RIEULKIYEOK 9965 C15E # HANGUL SYLLABLE SIOS-YEO-RIEULMIEUM 9966 C15F # HANGUL SYLLABLE SIOS-YEO-RIEULPIEUP 9967 C160 # HANGUL SYLLABLE SIOS-YEO-RIEULSIOS 9968 C161 # HANGUL SYLLABLE SIOS-YEO-RIEULTHIEUTH 9969 C162 # HANGUL SYLLABLE SIOS-YEO-RIEULPHIEUPH 996A C163 # HANGUL SYLLABLE SIOS-YEO-RIEULHIEUH 996B C166 # HANGUL SYLLABLE SIOS-YEO-PIEUPSIOS 996C C16A # HANGUL SYLLABLE SIOS-YEO-CIEUC 996D C16B # HANGUL SYLLABLE SIOS-YEO-CHIEUCH 996E C16C # HANGUL SYLLABLE SIOS-YEO-KHIEUKH 996F C16D # HANGUL SYLLABLE SIOS-YEO-THIEUTH 9970 C16E # HANGUL SYLLABLE SIOS-YEO-PHIEUPH 9971 C16F # HANGUL SYLLABLE SIOS-YEO-HIEUH 9972 C171 # HANGUL SYLLABLE SIOS-YE-KIYEOK 9973 C172 # HANGUL SYLLABLE SIOS-YE-SSANGKIYEOK 9974 C173 # HANGUL SYLLABLE SIOS-YE-KIYEOKSIOS 9975 C175 # HANGUL SYLLABLE SIOS-YE-NIEUNCIEUC 9976 C176 # HANGUL SYLLABLE SIOS-YE-NIEUNHIEUH 9977 C177 # HANGUL SYLLABLE SIOS-YE-TIKEUT 9978 C179 # HANGUL SYLLABLE SIOS-YE-RIEULKIYEOK 9979 C17A # HANGUL SYLLABLE SIOS-YE-RIEULMIEUM 997A C17B # HANGUL SYLLABLE SIOS-YE-RIEULPIEUP 9981 C17C # HANGUL SYLLABLE SIOS-YE-RIEULSIOS 9982 C17D # HANGUL SYLLABLE SIOS-YE-RIEULTHIEUTH 9983 C17E # HANGUL SYLLABLE SIOS-YE-RIEULPHIEUPH 9984 C17F # HANGUL SYLLABLE SIOS-YE-RIEULHIEUH 9985 C180 # HANGUL SYLLABLE SIOS-YE-MIEUM 9986 C181 # HANGUL SYLLABLE SIOS-YE-PIEUP 9987 C182 # HANGUL SYLLABLE SIOS-YE-PIEUPSIOS 9988 C183 # HANGUL SYLLABLE SIOS-YE-SIOS 9989 C184 # HANGUL SYLLABLE SIOS-YE-SSANGSIOS 998A C186 # HANGUL SYLLABLE SIOS-YE-CIEUC 998B C187 # HANGUL SYLLABLE SIOS-YE-CHIEUCH 998C C188 # HANGUL SYLLABLE SIOS-YE-KHIEUKH 998D C189 # HANGUL SYLLABLE SIOS-YE-THIEUTH 998E C18A # HANGUL SYLLABLE SIOS-YE-PHIEUPH 998F C18B # HANGUL SYLLABLE SIOS-YE-HIEUH 9990 C18F # HANGUL SYLLABLE SIOS-O-KIYEOKSIOS 9991 C191 # HANGUL SYLLABLE SIOS-O-NIEUNCIEUC 9992 C192 # HANGUL SYLLABLE SIOS-O-NIEUNHIEUH 9993 C193 # HANGUL SYLLABLE SIOS-O-TIKEUT 9994 C195 # HANGUL SYLLABLE SIOS-O-RIEULKIYEOK 9995 C197 # HANGUL SYLLABLE SIOS-O-RIEULPIEUP 9996 C198 # HANGUL SYLLABLE SIOS-O-RIEULSIOS 9997 C199 # HANGUL SYLLABLE SIOS-O-RIEULTHIEUTH 9998 C19A # HANGUL SYLLABLE SIOS-O-RIEULPHIEUPH 9999 C19B # HANGUL SYLLABLE SIOS-O-RIEULHIEUH 999A C19E # HANGUL SYLLABLE SIOS-O-PIEUPSIOS 999B C1A0 # HANGUL SYLLABLE SIOS-O-SSANGSIOS 999C C1A2 # HANGUL SYLLABLE SIOS-O-CIEUC 999D C1A3 # HANGUL SYLLABLE SIOS-O-CHIEUCH 999E C1A4 # HANGUL SYLLABLE SIOS-O-KHIEUKH 999F C1A6 # HANGUL SYLLABLE SIOS-O-PHIEUPH 99A0 C1A7 # HANGUL SYLLABLE SIOS-O-HIEUH 99A1 C1AA # HANGUL SYLLABLE SIOS-WA-SSANGKIYEOK 99A2 C1AB # HANGUL SYLLABLE SIOS-WA-KIYEOKSIOS 99A3 C1AD # HANGUL SYLLABLE SIOS-WA-NIEUNCIEUC 99A4 C1AE # HANGUL SYLLABLE SIOS-WA-NIEUNHIEUH 99A5 C1AF # HANGUL SYLLABLE SIOS-WA-TIKEUT 99A6 C1B1 # HANGUL SYLLABLE SIOS-WA-RIEULKIYEOK 99A7 C1B2 # HANGUL SYLLABLE SIOS-WA-RIEULMIEUM 99A8 C1B3 # HANGUL SYLLABLE SIOS-WA-RIEULPIEUP 99A9 C1B4 # HANGUL SYLLABLE SIOS-WA-RIEULSIOS 99AA C1B5 # HANGUL SYLLABLE SIOS-WA-RIEULTHIEUTH 99AB C1B6 # HANGUL SYLLABLE SIOS-WA-RIEULPHIEUPH 99AC C1B7 # HANGUL SYLLABLE SIOS-WA-RIEULHIEUH 99AD C1B8 # HANGUL SYLLABLE SIOS-WA-MIEUM 99AE C1B9 # HANGUL SYLLABLE SIOS-WA-PIEUP 99AF C1BA # HANGUL SYLLABLE SIOS-WA-PIEUPSIOS 99B0 C1BB # HANGUL SYLLABLE SIOS-WA-SIOS 99B1 C1BC # HANGUL SYLLABLE SIOS-WA-SSANGSIOS 99B2 C1BE # HANGUL SYLLABLE SIOS-WA-CIEUC 99B3 C1BF # HANGUL SYLLABLE SIOS-WA-CHIEUCH 99B4 C1C0 # HANGUL SYLLABLE SIOS-WA-KHIEUKH 99B5 C1C1 # HANGUL SYLLABLE SIOS-WA-THIEUTH 99B6 C1C2 # HANGUL SYLLABLE SIOS-WA-PHIEUPH 99B7 C1C3 # HANGUL SYLLABLE SIOS-WA-HIEUH 99B8 C1C5 # HANGUL SYLLABLE SIOS-WAE-KIYEOK 99B9 C1C6 # HANGUL SYLLABLE SIOS-WAE-SSANGKIYEOK 99BA C1C7 # HANGUL SYLLABLE SIOS-WAE-KIYEOKSIOS 99BB C1C9 # HANGUL SYLLABLE SIOS-WAE-NIEUNCIEUC 99BC C1CA # HANGUL SYLLABLE SIOS-WAE-NIEUNHIEUH 99BD C1CB # HANGUL SYLLABLE SIOS-WAE-TIKEUT 99BE C1CD # HANGUL SYLLABLE SIOS-WAE-RIEULKIYEOK 99BF C1CE # HANGUL SYLLABLE SIOS-WAE-RIEULMIEUM 99C0 C1CF # HANGUL SYLLABLE SIOS-WAE-RIEULPIEUP 99C1 C1D0 # HANGUL SYLLABLE SIOS-WAE-RIEULSIOS 99C2 C1D1 # HANGUL SYLLABLE SIOS-WAE-RIEULTHIEUTH 99C3 C1D2 # HANGUL SYLLABLE SIOS-WAE-RIEULPHIEUPH 99C4 C1D3 # HANGUL SYLLABLE SIOS-WAE-RIEULHIEUH 99C5 C1D5 # HANGUL SYLLABLE SIOS-WAE-PIEUP 99C6 C1D6 # HANGUL SYLLABLE SIOS-WAE-PIEUPSIOS 99C7 C1D9 # HANGUL SYLLABLE SIOS-WAE-IEUNG 99C8 C1DA # HANGUL SYLLABLE SIOS-WAE-CIEUC 99C9 C1DB # HANGUL SYLLABLE SIOS-WAE-CHIEUCH 99CA C1DC # HANGUL SYLLABLE SIOS-WAE-KHIEUKH 99CB C1DD # HANGUL SYLLABLE SIOS-WAE-THIEUTH 99CC C1DE # HANGUL SYLLABLE SIOS-WAE-PHIEUPH 99CD C1DF # HANGUL SYLLABLE SIOS-WAE-HIEUH 99CE C1E1 # HANGUL SYLLABLE SIOS-OE-KIYEOK 99CF C1E2 # HANGUL SYLLABLE SIOS-OE-SSANGKIYEOK 99D0 C1E3 # HANGUL SYLLABLE SIOS-OE-KIYEOKSIOS 99D1 C1E5 # HANGUL SYLLABLE SIOS-OE-NIEUNCIEUC 99D2 C1E6 # HANGUL SYLLABLE SIOS-OE-NIEUNHIEUH 99D3 C1E7 # HANGUL SYLLABLE SIOS-OE-TIKEUT 99D4 C1E9 # HANGUL SYLLABLE SIOS-OE-RIEULKIYEOK 99D5 C1EA # HANGUL SYLLABLE SIOS-OE-RIEULMIEUM 99D6 C1EB # HANGUL SYLLABLE SIOS-OE-RIEULPIEUP 99D7 C1EC # HANGUL SYLLABLE SIOS-OE-RIEULSIOS 99D8 C1ED # HANGUL SYLLABLE SIOS-OE-RIEULTHIEUTH 99D9 C1EE # HANGUL SYLLABLE SIOS-OE-RIEULPHIEUPH 99DA C1EF # HANGUL SYLLABLE SIOS-OE-RIEULHIEUH 99DB C1F2 # HANGUL SYLLABLE SIOS-OE-PIEUPSIOS 99DC C1F4 # HANGUL SYLLABLE SIOS-OE-SSANGSIOS 99DD C1F5 # HANGUL SYLLABLE SIOS-OE-IEUNG 99DE C1F6 # HANGUL SYLLABLE SIOS-OE-CIEUC 99DF C1F7 # HANGUL SYLLABLE SIOS-OE-CHIEUCH 99E0 C1F8 # HANGUL SYLLABLE SIOS-OE-KHIEUKH 99E1 C1F9 # HANGUL SYLLABLE SIOS-OE-THIEUTH 99E2 C1FA # HANGUL SYLLABLE SIOS-OE-PHIEUPH 99E3 C1FB # HANGUL SYLLABLE SIOS-OE-HIEUH 99E4 C1FE # HANGUL SYLLABLE SIOS-YO-SSANGKIYEOK 99E5 C1FF # HANGUL SYLLABLE SIOS-YO-KIYEOKSIOS 99E6 C201 # HANGUL SYLLABLE SIOS-YO-NIEUNCIEUC 99E7 C202 # HANGUL SYLLABLE SIOS-YO-NIEUNHIEUH 99E8 C203 # HANGUL SYLLABLE SIOS-YO-TIKEUT 99E9 C205 # HANGUL SYLLABLE SIOS-YO-RIEULKIYEOK 99EA C206 # HANGUL SYLLABLE SIOS-YO-RIEULMIEUM 99EB C207 # HANGUL SYLLABLE SIOS-YO-RIEULPIEUP 99EC C208 # HANGUL SYLLABLE SIOS-YO-RIEULSIOS 99ED C209 # HANGUL SYLLABLE SIOS-YO-RIEULTHIEUTH 99EE C20A # HANGUL SYLLABLE SIOS-YO-RIEULPHIEUPH 99EF C20B # HANGUL SYLLABLE SIOS-YO-RIEULHIEUH 99F0 C20E # HANGUL SYLLABLE SIOS-YO-PIEUPSIOS 99F1 C210 # HANGUL SYLLABLE SIOS-YO-SSANGSIOS 99F2 C212 # HANGUL SYLLABLE SIOS-YO-CIEUC 99F3 C213 # HANGUL SYLLABLE SIOS-YO-CHIEUCH 99F4 C214 # HANGUL SYLLABLE SIOS-YO-KHIEUKH 99F5 C215 # HANGUL SYLLABLE SIOS-YO-THIEUTH 99F6 C216 # HANGUL SYLLABLE SIOS-YO-PHIEUPH 99F7 C217 # HANGUL SYLLABLE SIOS-YO-HIEUH 99F8 C21A # HANGUL SYLLABLE SIOS-U-SSANGKIYEOK 99F9 C21B # HANGUL SYLLABLE SIOS-U-KIYEOKSIOS 99FA C21D # HANGUL SYLLABLE SIOS-U-NIEUNCIEUC 99FB C21E # HANGUL SYLLABLE SIOS-U-NIEUNHIEUH 99FC C221 # HANGUL SYLLABLE SIOS-U-RIEULKIYEOK 99FD C222 # HANGUL SYLLABLE SIOS-U-RIEULMIEUM 99FE C223 # HANGUL SYLLABLE SIOS-U-RIEULPIEUP 9A41 C224 # HANGUL SYLLABLE SIOS-U-RIEULSIOS 9A42 C225 # HANGUL SYLLABLE SIOS-U-RIEULTHIEUTH 9A43 C226 # HANGUL SYLLABLE SIOS-U-RIEULPHIEUPH 9A44 C227 # HANGUL SYLLABLE SIOS-U-RIEULHIEUH 9A45 C22A # HANGUL SYLLABLE SIOS-U-PIEUPSIOS 9A46 C22C # HANGUL SYLLABLE SIOS-U-SSANGSIOS 9A47 C22E # HANGUL SYLLABLE SIOS-U-CIEUC 9A48 C230 # HANGUL SYLLABLE SIOS-U-KHIEUKH 9A49 C233 # HANGUL SYLLABLE SIOS-U-HIEUH 9A4A C235 # HANGUL SYLLABLE SIOS-WEO-KIYEOK 9A4B C236 # HANGUL SYLLABLE SIOS-WEO-SSANGKIYEOK 9A4C C237 # HANGUL SYLLABLE SIOS-WEO-KIYEOKSIOS 9A4D C238 # HANGUL SYLLABLE SIOS-WEO-NIEUN 9A4E C239 # HANGUL SYLLABLE SIOS-WEO-NIEUNCIEUC 9A4F C23A # HANGUL SYLLABLE SIOS-WEO-NIEUNHIEUH 9A50 C23B # HANGUL SYLLABLE SIOS-WEO-TIKEUT 9A51 C23C # HANGUL SYLLABLE SIOS-WEO-RIEUL 9A52 C23D # HANGUL SYLLABLE SIOS-WEO-RIEULKIYEOK 9A53 C23E # HANGUL SYLLABLE SIOS-WEO-RIEULMIEUM 9A54 C23F # HANGUL SYLLABLE SIOS-WEO-RIEULPIEUP 9A55 C240 # HANGUL SYLLABLE SIOS-WEO-RIEULSIOS 9A56 C241 # HANGUL SYLLABLE SIOS-WEO-RIEULTHIEUTH 9A57 C242 # HANGUL SYLLABLE SIOS-WEO-RIEULPHIEUPH 9A58 C243 # HANGUL SYLLABLE SIOS-WEO-RIEULHIEUH 9A59 C244 # HANGUL SYLLABLE SIOS-WEO-MIEUM 9A5A C245 # HANGUL SYLLABLE SIOS-WEO-PIEUP 9A61 C246 # HANGUL SYLLABLE SIOS-WEO-PIEUPSIOS 9A62 C247 # HANGUL SYLLABLE SIOS-WEO-SIOS 9A63 C249 # HANGUL SYLLABLE SIOS-WEO-IEUNG 9A64 C24A # HANGUL SYLLABLE SIOS-WEO-CIEUC 9A65 C24B # HANGUL SYLLABLE SIOS-WEO-CHIEUCH 9A66 C24C # HANGUL SYLLABLE SIOS-WEO-KHIEUKH 9A67 C24D # HANGUL SYLLABLE SIOS-WEO-THIEUTH 9A68 C24E # HANGUL SYLLABLE SIOS-WEO-PHIEUPH 9A69 C24F # HANGUL SYLLABLE SIOS-WEO-HIEUH 9A6A C252 # HANGUL SYLLABLE SIOS-WE-SSANGKIYEOK 9A6B C253 # HANGUL SYLLABLE SIOS-WE-KIYEOKSIOS 9A6C C255 # HANGUL SYLLABLE SIOS-WE-NIEUNCIEUC 9A6D C256 # HANGUL SYLLABLE SIOS-WE-NIEUNHIEUH 9A6E C257 # HANGUL SYLLABLE SIOS-WE-TIKEUT 9A6F C259 # HANGUL SYLLABLE SIOS-WE-RIEULKIYEOK 9A70 C25A # HANGUL SYLLABLE SIOS-WE-RIEULMIEUM 9A71 C25B # HANGUL SYLLABLE SIOS-WE-RIEULPIEUP 9A72 C25C # HANGUL SYLLABLE SIOS-WE-RIEULSIOS 9A73 C25D # HANGUL SYLLABLE SIOS-WE-RIEULTHIEUTH 9A74 C25E # HANGUL SYLLABLE SIOS-WE-RIEULPHIEUPH 9A75 C25F # HANGUL SYLLABLE SIOS-WE-RIEULHIEUH 9A76 C261 # HANGUL SYLLABLE SIOS-WE-PIEUP 9A77 C262 # HANGUL SYLLABLE SIOS-WE-PIEUPSIOS 9A78 C263 # HANGUL SYLLABLE SIOS-WE-SIOS 9A79 C264 # HANGUL SYLLABLE SIOS-WE-SSANGSIOS 9A7A C266 # HANGUL SYLLABLE SIOS-WE-CIEUC 9A81 C267 # HANGUL SYLLABLE SIOS-WE-CHIEUCH 9A82 C268 # HANGUL SYLLABLE SIOS-WE-KHIEUKH 9A83 C269 # HANGUL SYLLABLE SIOS-WE-THIEUTH 9A84 C26A # HANGUL SYLLABLE SIOS-WE-PHIEUPH 9A85 C26B # HANGUL SYLLABLE SIOS-WE-HIEUH 9A86 C26E # HANGUL SYLLABLE SIOS-WI-SSANGKIYEOK 9A87 C26F # HANGUL SYLLABLE SIOS-WI-KIYEOKSIOS 9A88 C271 # HANGUL SYLLABLE SIOS-WI-NIEUNCIEUC 9A89 C272 # HANGUL SYLLABLE SIOS-WI-NIEUNHIEUH 9A8A C273 # HANGUL SYLLABLE SIOS-WI-TIKEUT 9A8B C275 # HANGUL SYLLABLE SIOS-WI-RIEULKIYEOK 9A8C C276 # HANGUL SYLLABLE SIOS-WI-RIEULMIEUM 9A8D C277 # HANGUL SYLLABLE SIOS-WI-RIEULPIEUP 9A8E C278 # HANGUL SYLLABLE SIOS-WI-RIEULSIOS 9A8F C279 # HANGUL SYLLABLE SIOS-WI-RIEULTHIEUTH 9A90 C27A # HANGUL SYLLABLE SIOS-WI-RIEULPHIEUPH 9A91 C27B # HANGUL SYLLABLE SIOS-WI-RIEULHIEUH 9A92 C27E # HANGUL SYLLABLE SIOS-WI-PIEUPSIOS 9A93 C280 # HANGUL SYLLABLE SIOS-WI-SSANGSIOS 9A94 C282 # HANGUL SYLLABLE SIOS-WI-CIEUC 9A95 C283 # HANGUL SYLLABLE SIOS-WI-CHIEUCH 9A96 C284 # HANGUL SYLLABLE SIOS-WI-KHIEUKH 9A97 C285 # HANGUL SYLLABLE SIOS-WI-THIEUTH 9A98 C286 # HANGUL SYLLABLE SIOS-WI-PHIEUPH 9A99 C287 # HANGUL SYLLABLE SIOS-WI-HIEUH 9A9A C28A # HANGUL SYLLABLE SIOS-YU-SSANGKIYEOK 9A9B C28B # HANGUL SYLLABLE SIOS-YU-KIYEOKSIOS 9A9C C28C # HANGUL SYLLABLE SIOS-YU-NIEUN 9A9D C28D # HANGUL SYLLABLE SIOS-YU-NIEUNCIEUC 9A9E C28E # HANGUL SYLLABLE SIOS-YU-NIEUNHIEUH 9A9F C28F # HANGUL SYLLABLE SIOS-YU-TIKEUT 9AA0 C291 # HANGUL SYLLABLE SIOS-YU-RIEULKIYEOK 9AA1 C292 # HANGUL SYLLABLE SIOS-YU-RIEULMIEUM 9AA2 C293 # HANGUL SYLLABLE SIOS-YU-RIEULPIEUP 9AA3 C294 # HANGUL SYLLABLE SIOS-YU-RIEULSIOS 9AA4 C295 # HANGUL SYLLABLE SIOS-YU-RIEULTHIEUTH 9AA5 C296 # HANGUL SYLLABLE SIOS-YU-RIEULPHIEUPH 9AA6 C297 # HANGUL SYLLABLE SIOS-YU-RIEULHIEUH 9AA7 C299 # HANGUL SYLLABLE SIOS-YU-PIEUP 9AA8 C29A # HANGUL SYLLABLE SIOS-YU-PIEUPSIOS 9AA9 C29C # HANGUL SYLLABLE SIOS-YU-SSANGSIOS 9AAA C29E # HANGUL SYLLABLE SIOS-YU-CIEUC 9AAB C29F # HANGUL SYLLABLE SIOS-YU-CHIEUCH 9AAC C2A0 # HANGUL SYLLABLE SIOS-YU-KHIEUKH 9AAD C2A1 # HANGUL SYLLABLE SIOS-YU-THIEUTH 9AAE C2A2 # HANGUL SYLLABLE SIOS-YU-PHIEUPH 9AAF C2A3 # HANGUL SYLLABLE SIOS-YU-HIEUH 9AB0 C2A6 # HANGUL SYLLABLE SIOS-EU-SSANGKIYEOK 9AB1 C2A7 # HANGUL SYLLABLE SIOS-EU-KIYEOKSIOS 9AB2 C2A9 # HANGUL SYLLABLE SIOS-EU-NIEUNCIEUC 9AB3 C2AA # HANGUL SYLLABLE SIOS-EU-NIEUNHIEUH 9AB4 C2AB # HANGUL SYLLABLE SIOS-EU-TIKEUT 9AB5 C2AE # HANGUL SYLLABLE SIOS-EU-RIEULMIEUM 9AB6 C2AF # HANGUL SYLLABLE SIOS-EU-RIEULPIEUP 9AB7 C2B0 # HANGUL SYLLABLE SIOS-EU-RIEULSIOS 9AB8 C2B1 # HANGUL SYLLABLE SIOS-EU-RIEULTHIEUTH 9AB9 C2B2 # HANGUL SYLLABLE SIOS-EU-RIEULPHIEUPH 9ABA C2B3 # HANGUL SYLLABLE SIOS-EU-RIEULHIEUH 9ABB C2B6 # HANGUL SYLLABLE SIOS-EU-PIEUPSIOS 9ABC C2B8 # HANGUL SYLLABLE SIOS-EU-SSANGSIOS 9ABD C2BA # HANGUL SYLLABLE SIOS-EU-CIEUC 9ABE C2BB # HANGUL SYLLABLE SIOS-EU-CHIEUCH 9ABF C2BC # HANGUL SYLLABLE SIOS-EU-KHIEUKH 9AC0 C2BD # HANGUL SYLLABLE SIOS-EU-THIEUTH 9AC1 C2BE # HANGUL SYLLABLE SIOS-EU-PHIEUPH 9AC2 C2BF # HANGUL SYLLABLE SIOS-EU-HIEUH 9AC3 C2C0 # HANGUL SYLLABLE SIOS-YI 9AC4 C2C1 # HANGUL SYLLABLE SIOS-YI-KIYEOK 9AC5 C2C2 # HANGUL SYLLABLE SIOS-YI-SSANGKIYEOK 9AC6 C2C3 # HANGUL SYLLABLE SIOS-YI-KIYEOKSIOS 9AC7 C2C4 # HANGUL SYLLABLE SIOS-YI-NIEUN 9AC8 C2C5 # HANGUL SYLLABLE SIOS-YI-NIEUNCIEUC 9AC9 C2C6 # HANGUL SYLLABLE SIOS-YI-NIEUNHIEUH 9ACA C2C7 # HANGUL SYLLABLE SIOS-YI-TIKEUT 9ACB C2C8 # HANGUL SYLLABLE SIOS-YI-RIEUL 9ACC C2C9 # HANGUL SYLLABLE SIOS-YI-RIEULKIYEOK 9ACD C2CA # HANGUL SYLLABLE SIOS-YI-RIEULMIEUM 9ACE C2CB # HANGUL SYLLABLE SIOS-YI-RIEULPIEUP 9ACF C2CC # HANGUL SYLLABLE SIOS-YI-RIEULSIOS 9AD0 C2CD # HANGUL SYLLABLE SIOS-YI-RIEULTHIEUTH 9AD1 C2CE # HANGUL SYLLABLE SIOS-YI-RIEULPHIEUPH 9AD2 C2CF # HANGUL SYLLABLE SIOS-YI-RIEULHIEUH 9AD3 C2D0 # HANGUL SYLLABLE SIOS-YI-MIEUM 9AD4 C2D1 # HANGUL SYLLABLE SIOS-YI-PIEUP 9AD5 C2D2 # HANGUL SYLLABLE SIOS-YI-PIEUPSIOS 9AD6 C2D3 # HANGUL SYLLABLE SIOS-YI-SIOS 9AD7 C2D4 # HANGUL SYLLABLE SIOS-YI-SSANGSIOS 9AD8 C2D5 # HANGUL SYLLABLE SIOS-YI-IEUNG 9AD9 C2D6 # HANGUL SYLLABLE SIOS-YI-CIEUC 9ADA C2D7 # HANGUL SYLLABLE SIOS-YI-CHIEUCH 9ADB C2D8 # HANGUL SYLLABLE SIOS-YI-KHIEUKH 9ADC C2D9 # HANGUL SYLLABLE SIOS-YI-THIEUTH 9ADD C2DA # HANGUL SYLLABLE SIOS-YI-PHIEUPH 9ADE C2DB # HANGUL SYLLABLE SIOS-YI-HIEUH 9ADF C2DE # HANGUL SYLLABLE SIOS-I-SSANGKIYEOK 9AE0 C2DF # HANGUL SYLLABLE SIOS-I-KIYEOKSIOS 9AE1 C2E1 # HANGUL SYLLABLE SIOS-I-NIEUNCIEUC 9AE2 C2E2 # HANGUL SYLLABLE SIOS-I-NIEUNHIEUH 9AE3 C2E5 # HANGUL SYLLABLE SIOS-I-RIEULKIYEOK 9AE4 C2E6 # HANGUL SYLLABLE SIOS-I-RIEULMIEUM 9AE5 C2E7 # HANGUL SYLLABLE SIOS-I-RIEULPIEUP 9AE6 C2E8 # HANGUL SYLLABLE SIOS-I-RIEULSIOS 9AE7 C2E9 # HANGUL SYLLABLE SIOS-I-RIEULTHIEUTH 9AE8 C2EA # HANGUL SYLLABLE SIOS-I-RIEULPHIEUPH 9AE9 C2EE # HANGUL SYLLABLE SIOS-I-PIEUPSIOS 9AEA C2F0 # HANGUL SYLLABLE SIOS-I-SSANGSIOS 9AEB C2F2 # HANGUL SYLLABLE SIOS-I-CIEUC 9AEC C2F3 # HANGUL SYLLABLE SIOS-I-CHIEUCH 9AED C2F4 # HANGUL SYLLABLE SIOS-I-KHIEUKH 9AEE C2F5 # HANGUL SYLLABLE SIOS-I-THIEUTH 9AEF C2F7 # HANGUL SYLLABLE SIOS-I-HIEUH 9AF0 C2FA # HANGUL SYLLABLE SSANGSIOS-A-SSANGKIYEOK 9AF1 C2FD # HANGUL SYLLABLE SSANGSIOS-A-NIEUNCIEUC 9AF2 C2FE # HANGUL SYLLABLE SSANGSIOS-A-NIEUNHIEUH 9AF3 C2FF # HANGUL SYLLABLE SSANGSIOS-A-TIKEUT 9AF4 C301 # HANGUL SYLLABLE SSANGSIOS-A-RIEULKIYEOK 9AF5 C302 # HANGUL SYLLABLE SSANGSIOS-A-RIEULMIEUM 9AF6 C303 # HANGUL SYLLABLE SSANGSIOS-A-RIEULPIEUP 9AF7 C304 # HANGUL SYLLABLE SSANGSIOS-A-RIEULSIOS 9AF8 C305 # HANGUL SYLLABLE SSANGSIOS-A-RIEULTHIEUTH 9AF9 C306 # HANGUL SYLLABLE SSANGSIOS-A-RIEULPHIEUPH 9AFA C307 # HANGUL SYLLABLE SSANGSIOS-A-RIEULHIEUH 9AFB C30A # HANGUL SYLLABLE SSANGSIOS-A-PIEUPSIOS 9AFC C30B # HANGUL SYLLABLE SSANGSIOS-A-SIOS 9AFD C30E # HANGUL SYLLABLE SSANGSIOS-A-CIEUC 9AFE C30F # HANGUL SYLLABLE SSANGSIOS-A-CHIEUCH 9B41 C310 # HANGUL SYLLABLE SSANGSIOS-A-KHIEUKH 9B42 C311 # HANGUL SYLLABLE SSANGSIOS-A-THIEUTH 9B43 C312 # HANGUL SYLLABLE SSANGSIOS-A-PHIEUPH 9B44 C316 # HANGUL SYLLABLE SSANGSIOS-AE-SSANGKIYEOK 9B45 C317 # HANGUL SYLLABLE SSANGSIOS-AE-KIYEOKSIOS 9B46 C319 # HANGUL SYLLABLE SSANGSIOS-AE-NIEUNCIEUC 9B47 C31A # HANGUL SYLLABLE SSANGSIOS-AE-NIEUNHIEUH 9B48 C31B # HANGUL SYLLABLE SSANGSIOS-AE-TIKEUT 9B49 C31D # HANGUL SYLLABLE SSANGSIOS-AE-RIEULKIYEOK 9B4A C31E # HANGUL SYLLABLE SSANGSIOS-AE-RIEULMIEUM 9B4B C31F # HANGUL SYLLABLE SSANGSIOS-AE-RIEULPIEUP 9B4C C320 # HANGUL SYLLABLE SSANGSIOS-AE-RIEULSIOS 9B4D C321 # HANGUL SYLLABLE SSANGSIOS-AE-RIEULTHIEUTH 9B4E C322 # HANGUL SYLLABLE SSANGSIOS-AE-RIEULPHIEUPH 9B4F C323 # HANGUL SYLLABLE SSANGSIOS-AE-RIEULHIEUH 9B50 C326 # HANGUL SYLLABLE SSANGSIOS-AE-PIEUPSIOS 9B51 C327 # HANGUL SYLLABLE SSANGSIOS-AE-SIOS 9B52 C32A # HANGUL SYLLABLE SSANGSIOS-AE-CIEUC 9B53 C32B # HANGUL SYLLABLE SSANGSIOS-AE-CHIEUCH 9B54 C32C # HANGUL SYLLABLE SSANGSIOS-AE-KHIEUKH 9B55 C32D # HANGUL SYLLABLE SSANGSIOS-AE-THIEUTH 9B56 C32E # HANGUL SYLLABLE SSANGSIOS-AE-PHIEUPH 9B57 C32F # HANGUL SYLLABLE SSANGSIOS-AE-HIEUH 9B58 C330 # HANGUL SYLLABLE SSANGSIOS-YA 9B59 C331 # HANGUL SYLLABLE SSANGSIOS-YA-KIYEOK 9B5A C332 # HANGUL SYLLABLE SSANGSIOS-YA-SSANGKIYEOK 9B61 C333 # HANGUL SYLLABLE SSANGSIOS-YA-KIYEOKSIOS 9B62 C334 # HANGUL SYLLABLE SSANGSIOS-YA-NIEUN 9B63 C335 # HANGUL SYLLABLE SSANGSIOS-YA-NIEUNCIEUC 9B64 C336 # HANGUL SYLLABLE SSANGSIOS-YA-NIEUNHIEUH 9B65 C337 # HANGUL SYLLABLE SSANGSIOS-YA-TIKEUT 9B66 C338 # HANGUL SYLLABLE SSANGSIOS-YA-RIEUL 9B67 C339 # HANGUL SYLLABLE SSANGSIOS-YA-RIEULKIYEOK 9B68 C33A # HANGUL SYLLABLE SSANGSIOS-YA-RIEULMIEUM 9B69 C33B # HANGUL SYLLABLE SSANGSIOS-YA-RIEULPIEUP 9B6A C33C # HANGUL SYLLABLE SSANGSIOS-YA-RIEULSIOS 9B6B C33D # HANGUL SYLLABLE SSANGSIOS-YA-RIEULTHIEUTH 9B6C C33E # HANGUL SYLLABLE SSANGSIOS-YA-RIEULPHIEUPH 9B6D C33F # HANGUL SYLLABLE SSANGSIOS-YA-RIEULHIEUH 9B6E C340 # HANGUL SYLLABLE SSANGSIOS-YA-MIEUM 9B6F C341 # HANGUL SYLLABLE SSANGSIOS-YA-PIEUP 9B70 C342 # HANGUL SYLLABLE SSANGSIOS-YA-PIEUPSIOS 9B71 C343 # HANGUL SYLLABLE SSANGSIOS-YA-SIOS 9B72 C344 # HANGUL SYLLABLE SSANGSIOS-YA-SSANGSIOS 9B73 C346 # HANGUL SYLLABLE SSANGSIOS-YA-CIEUC 9B74 C347 # HANGUL SYLLABLE SSANGSIOS-YA-CHIEUCH 9B75 C348 # HANGUL SYLLABLE SSANGSIOS-YA-KHIEUKH 9B76 C349 # HANGUL SYLLABLE SSANGSIOS-YA-THIEUTH 9B77 C34A # HANGUL SYLLABLE SSANGSIOS-YA-PHIEUPH 9B78 C34B # HANGUL SYLLABLE SSANGSIOS-YA-HIEUH 9B79 C34C # HANGUL SYLLABLE SSANGSIOS-YAE 9B7A C34D # HANGUL SYLLABLE SSANGSIOS-YAE-KIYEOK 9B81 C34E # HANGUL SYLLABLE SSANGSIOS-YAE-SSANGKIYEOK 9B82 C34F # HANGUL SYLLABLE SSANGSIOS-YAE-KIYEOKSIOS 9B83 C350 # HANGUL SYLLABLE SSANGSIOS-YAE-NIEUN 9B84 C351 # HANGUL SYLLABLE SSANGSIOS-YAE-NIEUNCIEUC 9B85 C352 # HANGUL SYLLABLE SSANGSIOS-YAE-NIEUNHIEUH 9B86 C353 # HANGUL SYLLABLE SSANGSIOS-YAE-TIKEUT 9B87 C354 # HANGUL SYLLABLE SSANGSIOS-YAE-RIEUL 9B88 C355 # HANGUL SYLLABLE SSANGSIOS-YAE-RIEULKIYEOK 9B89 C356 # HANGUL SYLLABLE SSANGSIOS-YAE-RIEULMIEUM 9B8A C357 # HANGUL SYLLABLE SSANGSIOS-YAE-RIEULPIEUP 9B8B C358 # HANGUL SYLLABLE SSANGSIOS-YAE-RIEULSIOS 9B8C C359 # HANGUL SYLLABLE SSANGSIOS-YAE-RIEULTHIEUTH 9B8D C35A # HANGUL SYLLABLE SSANGSIOS-YAE-RIEULPHIEUPH 9B8E C35B # HANGUL SYLLABLE SSANGSIOS-YAE-RIEULHIEUH 9B8F C35C # HANGUL SYLLABLE SSANGSIOS-YAE-MIEUM 9B90 C35D # HANGUL SYLLABLE SSANGSIOS-YAE-PIEUP 9B91 C35E # HANGUL SYLLABLE SSANGSIOS-YAE-PIEUPSIOS 9B92 C35F # HANGUL SYLLABLE SSANGSIOS-YAE-SIOS 9B93 C360 # HANGUL SYLLABLE SSANGSIOS-YAE-SSANGSIOS 9B94 C361 # HANGUL SYLLABLE SSANGSIOS-YAE-IEUNG 9B95 C362 # HANGUL SYLLABLE SSANGSIOS-YAE-CIEUC 9B96 C363 # HANGUL SYLLABLE SSANGSIOS-YAE-CHIEUCH 9B97 C364 # HANGUL SYLLABLE SSANGSIOS-YAE-KHIEUKH 9B98 C365 # HANGUL SYLLABLE SSANGSIOS-YAE-THIEUTH 9B99 C366 # HANGUL SYLLABLE SSANGSIOS-YAE-PHIEUPH 9B9A C367 # HANGUL SYLLABLE SSANGSIOS-YAE-HIEUH 9B9B C36A # HANGUL SYLLABLE SSANGSIOS-EO-SSANGKIYEOK 9B9C C36B # HANGUL SYLLABLE SSANGSIOS-EO-KIYEOKSIOS 9B9D C36D # HANGUL SYLLABLE SSANGSIOS-EO-NIEUNCIEUC 9B9E C36E # HANGUL SYLLABLE SSANGSIOS-EO-NIEUNHIEUH 9B9F C36F # HANGUL SYLLABLE SSANGSIOS-EO-TIKEUT 9BA0 C371 # HANGUL SYLLABLE SSANGSIOS-EO-RIEULKIYEOK 9BA1 C373 # HANGUL SYLLABLE SSANGSIOS-EO-RIEULPIEUP 9BA2 C374 # HANGUL SYLLABLE SSANGSIOS-EO-RIEULSIOS 9BA3 C375 # HANGUL SYLLABLE SSANGSIOS-EO-RIEULTHIEUTH 9BA4 C376 # HANGUL SYLLABLE SSANGSIOS-EO-RIEULPHIEUPH 9BA5 C377 # HANGUL SYLLABLE SSANGSIOS-EO-RIEULHIEUH 9BA6 C37A # HANGUL SYLLABLE SSANGSIOS-EO-PIEUPSIOS 9BA7 C37B # HANGUL SYLLABLE SSANGSIOS-EO-SIOS 9BA8 C37E # HANGUL SYLLABLE SSANGSIOS-EO-CIEUC 9BA9 C37F # HANGUL SYLLABLE SSANGSIOS-EO-CHIEUCH 9BAA C380 # HANGUL SYLLABLE SSANGSIOS-EO-KHIEUKH 9BAB C381 # HANGUL SYLLABLE SSANGSIOS-EO-THIEUTH 9BAC C382 # HANGUL SYLLABLE SSANGSIOS-EO-PHIEUPH 9BAD C383 # HANGUL SYLLABLE SSANGSIOS-EO-HIEUH 9BAE C385 # HANGUL SYLLABLE SSANGSIOS-E-KIYEOK 9BAF C386 # HANGUL SYLLABLE SSANGSIOS-E-SSANGKIYEOK 9BB0 C387 # HANGUL SYLLABLE SSANGSIOS-E-KIYEOKSIOS 9BB1 C389 # HANGUL SYLLABLE SSANGSIOS-E-NIEUNCIEUC 9BB2 C38A # HANGUL SYLLABLE SSANGSIOS-E-NIEUNHIEUH 9BB3 C38B # HANGUL SYLLABLE SSANGSIOS-E-TIKEUT 9BB4 C38D # HANGUL SYLLABLE SSANGSIOS-E-RIEULKIYEOK 9BB5 C38E # HANGUL SYLLABLE SSANGSIOS-E-RIEULMIEUM 9BB6 C38F # HANGUL SYLLABLE SSANGSIOS-E-RIEULPIEUP 9BB7 C390 # HANGUL SYLLABLE SSANGSIOS-E-RIEULSIOS 9BB8 C391 # HANGUL SYLLABLE SSANGSIOS-E-RIEULTHIEUTH 9BB9 C392 # HANGUL SYLLABLE SSANGSIOS-E-RIEULPHIEUPH 9BBA C393 # HANGUL SYLLABLE SSANGSIOS-E-RIEULHIEUH 9BBB C394 # HANGUL SYLLABLE SSANGSIOS-E-MIEUM 9BBC C395 # HANGUL SYLLABLE SSANGSIOS-E-PIEUP 9BBD C396 # HANGUL SYLLABLE SSANGSIOS-E-PIEUPSIOS 9BBE C397 # HANGUL SYLLABLE SSANGSIOS-E-SIOS 9BBF C398 # HANGUL SYLLABLE SSANGSIOS-E-SSANGSIOS 9BC0 C399 # HANGUL SYLLABLE SSANGSIOS-E-IEUNG 9BC1 C39A # HANGUL SYLLABLE SSANGSIOS-E-CIEUC 9BC2 C39B # HANGUL SYLLABLE SSANGSIOS-E-CHIEUCH 9BC3 C39C # HANGUL SYLLABLE SSANGSIOS-E-KHIEUKH 9BC4 C39D # HANGUL SYLLABLE SSANGSIOS-E-THIEUTH 9BC5 C39E # HANGUL SYLLABLE SSANGSIOS-E-PHIEUPH 9BC6 C39F # HANGUL SYLLABLE SSANGSIOS-E-HIEUH 9BC7 C3A0 # HANGUL SYLLABLE SSANGSIOS-YEO 9BC8 C3A1 # HANGUL SYLLABLE SSANGSIOS-YEO-KIYEOK 9BC9 C3A2 # HANGUL SYLLABLE SSANGSIOS-YEO-SSANGKIYEOK 9BCA C3A3 # HANGUL SYLLABLE SSANGSIOS-YEO-KIYEOKSIOS 9BCB C3A4 # HANGUL SYLLABLE SSANGSIOS-YEO-NIEUN 9BCC C3A5 # HANGUL SYLLABLE SSANGSIOS-YEO-NIEUNCIEUC 9BCD C3A6 # HANGUL SYLLABLE SSANGSIOS-YEO-NIEUNHIEUH 9BCE C3A7 # HANGUL SYLLABLE SSANGSIOS-YEO-TIKEUT 9BCF C3A8 # HANGUL SYLLABLE SSANGSIOS-YEO-RIEUL 9BD0 C3A9 # HANGUL SYLLABLE SSANGSIOS-YEO-RIEULKIYEOK 9BD1 C3AA # HANGUL SYLLABLE SSANGSIOS-YEO-RIEULMIEUM 9BD2 C3AB # HANGUL SYLLABLE SSANGSIOS-YEO-RIEULPIEUP 9BD3 C3AC # HANGUL SYLLABLE SSANGSIOS-YEO-RIEULSIOS 9BD4 C3AD # HANGUL SYLLABLE SSANGSIOS-YEO-RIEULTHIEUTH 9BD5 C3AE # HANGUL SYLLABLE SSANGSIOS-YEO-RIEULPHIEUPH 9BD6 C3AF # HANGUL SYLLABLE SSANGSIOS-YEO-RIEULHIEUH 9BD7 C3B0 # HANGUL SYLLABLE SSANGSIOS-YEO-MIEUM 9BD8 C3B1 # HANGUL SYLLABLE SSANGSIOS-YEO-PIEUP 9BD9 C3B2 # HANGUL SYLLABLE SSANGSIOS-YEO-PIEUPSIOS 9BDA C3B3 # HANGUL SYLLABLE SSANGSIOS-YEO-SIOS 9BDB C3B4 # HANGUL SYLLABLE SSANGSIOS-YEO-SSANGSIOS 9BDC C3B5 # HANGUL SYLLABLE SSANGSIOS-YEO-IEUNG 9BDD C3B6 # HANGUL SYLLABLE SSANGSIOS-YEO-CIEUC 9BDE C3B7 # HANGUL SYLLABLE SSANGSIOS-YEO-CHIEUCH 9BDF C3B8 # HANGUL SYLLABLE SSANGSIOS-YEO-KHIEUKH 9BE0 C3B9 # HANGUL SYLLABLE SSANGSIOS-YEO-THIEUTH 9BE1 C3BA # HANGUL SYLLABLE SSANGSIOS-YEO-PHIEUPH 9BE2 C3BB # HANGUL SYLLABLE SSANGSIOS-YEO-HIEUH 9BE3 C3BC # HANGUL SYLLABLE SSANGSIOS-YE 9BE4 C3BD # HANGUL SYLLABLE SSANGSIOS-YE-KIYEOK 9BE5 C3BE # HANGUL SYLLABLE SSANGSIOS-YE-SSANGKIYEOK 9BE6 C3BF # HANGUL SYLLABLE SSANGSIOS-YE-KIYEOKSIOS 9BE7 C3C1 # HANGUL SYLLABLE SSANGSIOS-YE-NIEUNCIEUC 9BE8 C3C2 # HANGUL SYLLABLE SSANGSIOS-YE-NIEUNHIEUH 9BE9 C3C3 # HANGUL SYLLABLE SSANGSIOS-YE-TIKEUT 9BEA C3C4 # HANGUL SYLLABLE SSANGSIOS-YE-RIEUL 9BEB C3C5 # HANGUL SYLLABLE SSANGSIOS-YE-RIEULKIYEOK 9BEC C3C6 # HANGUL SYLLABLE SSANGSIOS-YE-RIEULMIEUM 9BED C3C7 # HANGUL SYLLABLE SSANGSIOS-YE-RIEULPIEUP 9BEE C3C8 # HANGUL SYLLABLE SSANGSIOS-YE-RIEULSIOS 9BEF C3C9 # HANGUL SYLLABLE SSANGSIOS-YE-RIEULTHIEUTH 9BF0 C3CA # HANGUL SYLLABLE SSANGSIOS-YE-RIEULPHIEUPH 9BF1 C3CB # HANGUL SYLLABLE SSANGSIOS-YE-RIEULHIEUH 9BF2 C3CC # HANGUL SYLLABLE SSANGSIOS-YE-MIEUM 9BF3 C3CD # HANGUL SYLLABLE SSANGSIOS-YE-PIEUP 9BF4 C3CE # HANGUL SYLLABLE SSANGSIOS-YE-PIEUPSIOS 9BF5 C3CF # HANGUL SYLLABLE SSANGSIOS-YE-SIOS 9BF6 C3D0 # HANGUL SYLLABLE SSANGSIOS-YE-SSANGSIOS 9BF7 C3D1 # HANGUL SYLLABLE SSANGSIOS-YE-IEUNG 9BF8 C3D2 # HANGUL SYLLABLE SSANGSIOS-YE-CIEUC 9BF9 C3D3 # HANGUL SYLLABLE SSANGSIOS-YE-CHIEUCH 9BFA C3D4 # HANGUL SYLLABLE SSANGSIOS-YE-KHIEUKH 9BFB C3D5 # HANGUL SYLLABLE SSANGSIOS-YE-THIEUTH 9BFC C3D6 # HANGUL SYLLABLE SSANGSIOS-YE-PHIEUPH 9BFD C3D7 # HANGUL SYLLABLE SSANGSIOS-YE-HIEUH 9BFE C3DA # HANGUL SYLLABLE SSANGSIOS-O-SSANGKIYEOK 9C41 C3DB # HANGUL SYLLABLE SSANGSIOS-O-KIYEOKSIOS 9C42 C3DD # HANGUL SYLLABLE SSANGSIOS-O-NIEUNCIEUC 9C43 C3DE # HANGUL SYLLABLE SSANGSIOS-O-NIEUNHIEUH 9C44 C3E1 # HANGUL SYLLABLE SSANGSIOS-O-RIEULKIYEOK 9C45 C3E3 # HANGUL SYLLABLE SSANGSIOS-O-RIEULPIEUP 9C46 C3E4 # HANGUL SYLLABLE SSANGSIOS-O-RIEULSIOS 9C47 C3E5 # HANGUL SYLLABLE SSANGSIOS-O-RIEULTHIEUTH 9C48 C3E6 # HANGUL SYLLABLE SSANGSIOS-O-RIEULPHIEUPH 9C49 C3E7 # HANGUL SYLLABLE SSANGSIOS-O-RIEULHIEUH 9C4A C3EA # HANGUL SYLLABLE SSANGSIOS-O-PIEUPSIOS 9C4B C3EB # HANGUL SYLLABLE SSANGSIOS-O-SIOS 9C4C C3EC # HANGUL SYLLABLE SSANGSIOS-O-SSANGSIOS 9C4D C3EE # HANGUL SYLLABLE SSANGSIOS-O-CIEUC 9C4E C3EF # HANGUL SYLLABLE SSANGSIOS-O-CHIEUCH 9C4F C3F0 # HANGUL SYLLABLE SSANGSIOS-O-KHIEUKH 9C50 C3F1 # HANGUL SYLLABLE SSANGSIOS-O-THIEUTH 9C51 C3F2 # HANGUL SYLLABLE SSANGSIOS-O-PHIEUPH 9C52 C3F3 # HANGUL SYLLABLE SSANGSIOS-O-HIEUH 9C53 C3F6 # HANGUL SYLLABLE SSANGSIOS-WA-SSANGKIYEOK 9C54 C3F7 # HANGUL SYLLABLE SSANGSIOS-WA-KIYEOKSIOS 9C55 C3F9 # HANGUL SYLLABLE SSANGSIOS-WA-NIEUNCIEUC 9C56 C3FA # HANGUL SYLLABLE SSANGSIOS-WA-NIEUNHIEUH 9C57 C3FB # HANGUL SYLLABLE SSANGSIOS-WA-TIKEUT 9C58 C3FC # HANGUL SYLLABLE SSANGSIOS-WA-RIEUL 9C59 C3FD # HANGUL SYLLABLE SSANGSIOS-WA-RIEULKIYEOK 9C5A C3FE # HANGUL SYLLABLE SSANGSIOS-WA-RIEULMIEUM 9C61 C3FF # HANGUL SYLLABLE SSANGSIOS-WA-RIEULPIEUP 9C62 C400 # HANGUL SYLLABLE SSANGSIOS-WA-RIEULSIOS 9C63 C401 # HANGUL SYLLABLE SSANGSIOS-WA-RIEULTHIEUTH 9C64 C402 # HANGUL SYLLABLE SSANGSIOS-WA-RIEULPHIEUPH 9C65 C403 # HANGUL SYLLABLE SSANGSIOS-WA-RIEULHIEUH 9C66 C404 # HANGUL SYLLABLE SSANGSIOS-WA-MIEUM 9C67 C405 # HANGUL SYLLABLE SSANGSIOS-WA-PIEUP 9C68 C406 # HANGUL SYLLABLE SSANGSIOS-WA-PIEUPSIOS 9C69 C407 # HANGUL SYLLABLE SSANGSIOS-WA-SIOS 9C6A C409 # HANGUL SYLLABLE SSANGSIOS-WA-IEUNG 9C6B C40A # HANGUL SYLLABLE SSANGSIOS-WA-CIEUC 9C6C C40B # HANGUL SYLLABLE SSANGSIOS-WA-CHIEUCH 9C6D C40C # HANGUL SYLLABLE SSANGSIOS-WA-KHIEUKH 9C6E C40D # HANGUL SYLLABLE SSANGSIOS-WA-THIEUTH 9C6F C40E # HANGUL SYLLABLE SSANGSIOS-WA-PHIEUPH 9C70 C40F # HANGUL SYLLABLE SSANGSIOS-WA-HIEUH 9C71 C411 # HANGUL SYLLABLE SSANGSIOS-WAE-KIYEOK 9C72 C412 # HANGUL SYLLABLE SSANGSIOS-WAE-SSANGKIYEOK 9C73 C413 # HANGUL SYLLABLE SSANGSIOS-WAE-KIYEOKSIOS 9C74 C414 # HANGUL SYLLABLE SSANGSIOS-WAE-NIEUN 9C75 C415 # HANGUL SYLLABLE SSANGSIOS-WAE-NIEUNCIEUC 9C76 C416 # HANGUL SYLLABLE SSANGSIOS-WAE-NIEUNHIEUH 9C77 C417 # HANGUL SYLLABLE SSANGSIOS-WAE-TIKEUT 9C78 C418 # HANGUL SYLLABLE SSANGSIOS-WAE-RIEUL 9C79 C419 # HANGUL SYLLABLE SSANGSIOS-WAE-RIEULKIYEOK 9C7A C41A # HANGUL SYLLABLE SSANGSIOS-WAE-RIEULMIEUM 9C81 C41B # HANGUL SYLLABLE SSANGSIOS-WAE-RIEULPIEUP 9C82 C41C # HANGUL SYLLABLE SSANGSIOS-WAE-RIEULSIOS 9C83 C41D # HANGUL SYLLABLE SSANGSIOS-WAE-RIEULTHIEUTH 9C84 C41E # HANGUL SYLLABLE SSANGSIOS-WAE-RIEULPHIEUPH 9C85 C41F # HANGUL SYLLABLE SSANGSIOS-WAE-RIEULHIEUH 9C86 C420 # HANGUL SYLLABLE SSANGSIOS-WAE-MIEUM 9C87 C421 # HANGUL SYLLABLE SSANGSIOS-WAE-PIEUP 9C88 C422 # HANGUL SYLLABLE SSANGSIOS-WAE-PIEUPSIOS 9C89 C423 # HANGUL SYLLABLE SSANGSIOS-WAE-SIOS 9C8A C425 # HANGUL SYLLABLE SSANGSIOS-WAE-IEUNG 9C8B C426 # HANGUL SYLLABLE SSANGSIOS-WAE-CIEUC 9C8C C427 # HANGUL SYLLABLE SSANGSIOS-WAE-CHIEUCH 9C8D C428 # HANGUL SYLLABLE SSANGSIOS-WAE-KHIEUKH 9C8E C429 # HANGUL SYLLABLE SSANGSIOS-WAE-THIEUTH 9C8F C42A # HANGUL SYLLABLE SSANGSIOS-WAE-PHIEUPH 9C90 C42B # HANGUL SYLLABLE SSANGSIOS-WAE-HIEUH 9C91 C42D # HANGUL SYLLABLE SSANGSIOS-OE-KIYEOK 9C92 C42E # HANGUL SYLLABLE SSANGSIOS-OE-SSANGKIYEOK 9C93 C42F # HANGUL SYLLABLE SSANGSIOS-OE-KIYEOKSIOS 9C94 C431 # HANGUL SYLLABLE SSANGSIOS-OE-NIEUNCIEUC 9C95 C432 # HANGUL SYLLABLE SSANGSIOS-OE-NIEUNHIEUH 9C96 C433 # HANGUL SYLLABLE SSANGSIOS-OE-TIKEUT 9C97 C435 # HANGUL SYLLABLE SSANGSIOS-OE-RIEULKIYEOK 9C98 C436 # HANGUL SYLLABLE SSANGSIOS-OE-RIEULMIEUM 9C99 C437 # HANGUL SYLLABLE SSANGSIOS-OE-RIEULPIEUP 9C9A C438 # HANGUL SYLLABLE SSANGSIOS-OE-RIEULSIOS 9C9B C439 # HANGUL SYLLABLE SSANGSIOS-OE-RIEULTHIEUTH 9C9C C43A # HANGUL SYLLABLE SSANGSIOS-OE-RIEULPHIEUPH 9C9D C43B # HANGUL SYLLABLE SSANGSIOS-OE-RIEULHIEUH 9C9E C43E # HANGUL SYLLABLE SSANGSIOS-OE-PIEUPSIOS 9C9F C43F # HANGUL SYLLABLE SSANGSIOS-OE-SIOS 9CA0 C440 # HANGUL SYLLABLE SSANGSIOS-OE-SSANGSIOS 9CA1 C441 # HANGUL SYLLABLE SSANGSIOS-OE-IEUNG 9CA2 C442 # HANGUL SYLLABLE SSANGSIOS-OE-CIEUC 9CA3 C443 # HANGUL SYLLABLE SSANGSIOS-OE-CHIEUCH 9CA4 C444 # HANGUL SYLLABLE SSANGSIOS-OE-KHIEUKH 9CA5 C445 # HANGUL SYLLABLE SSANGSIOS-OE-THIEUTH 9CA6 C446 # HANGUL SYLLABLE SSANGSIOS-OE-PHIEUPH 9CA7 C447 # HANGUL SYLLABLE SSANGSIOS-OE-HIEUH 9CA8 C449 # HANGUL SYLLABLE SSANGSIOS-YO-KIYEOK 9CA9 C44A # HANGUL SYLLABLE SSANGSIOS-YO-SSANGKIYEOK 9CAA C44B # HANGUL SYLLABLE SSANGSIOS-YO-KIYEOKSIOS 9CAB C44C # HANGUL SYLLABLE SSANGSIOS-YO-NIEUN 9CAC C44D # HANGUL SYLLABLE SSANGSIOS-YO-NIEUNCIEUC 9CAD C44E # HANGUL SYLLABLE SSANGSIOS-YO-NIEUNHIEUH 9CAE C44F # HANGUL SYLLABLE SSANGSIOS-YO-TIKEUT 9CAF C450 # HANGUL SYLLABLE SSANGSIOS-YO-RIEUL 9CB0 C451 # HANGUL SYLLABLE SSANGSIOS-YO-RIEULKIYEOK 9CB1 C452 # HANGUL SYLLABLE SSANGSIOS-YO-RIEULMIEUM 9CB2 C453 # HANGUL SYLLABLE SSANGSIOS-YO-RIEULPIEUP 9CB3 C454 # HANGUL SYLLABLE SSANGSIOS-YO-RIEULSIOS 9CB4 C455 # HANGUL SYLLABLE SSANGSIOS-YO-RIEULTHIEUTH 9CB5 C456 # HANGUL SYLLABLE SSANGSIOS-YO-RIEULPHIEUPH 9CB6 C457 # HANGUL SYLLABLE SSANGSIOS-YO-RIEULHIEUH 9CB7 C458 # HANGUL SYLLABLE SSANGSIOS-YO-MIEUM 9CB8 C459 # HANGUL SYLLABLE SSANGSIOS-YO-PIEUP 9CB9 C45A # HANGUL SYLLABLE SSANGSIOS-YO-PIEUPSIOS 9CBA C45B # HANGUL SYLLABLE SSANGSIOS-YO-SIOS 9CBB C45C # HANGUL SYLLABLE SSANGSIOS-YO-SSANGSIOS 9CBC C45D # HANGUL SYLLABLE SSANGSIOS-YO-IEUNG 9CBD C45E # HANGUL SYLLABLE SSANGSIOS-YO-CIEUC 9CBE C45F # HANGUL SYLLABLE SSANGSIOS-YO-CHIEUCH 9CBF C460 # HANGUL SYLLABLE SSANGSIOS-YO-KHIEUKH 9CC0 C461 # HANGUL SYLLABLE SSANGSIOS-YO-THIEUTH 9CC1 C462 # HANGUL SYLLABLE SSANGSIOS-YO-PHIEUPH 9CC2 C463 # HANGUL SYLLABLE SSANGSIOS-YO-HIEUH 9CC3 C466 # HANGUL SYLLABLE SSANGSIOS-U-SSANGKIYEOK 9CC4 C467 # HANGUL SYLLABLE SSANGSIOS-U-KIYEOKSIOS 9CC5 C469 # HANGUL SYLLABLE SSANGSIOS-U-NIEUNCIEUC 9CC6 C46A # HANGUL SYLLABLE SSANGSIOS-U-NIEUNHIEUH 9CC7 C46B # HANGUL SYLLABLE SSANGSIOS-U-TIKEUT 9CC8 C46D # HANGUL SYLLABLE SSANGSIOS-U-RIEULKIYEOK 9CC9 C46E # HANGUL SYLLABLE SSANGSIOS-U-RIEULMIEUM 9CCA C46F # HANGUL SYLLABLE SSANGSIOS-U-RIEULPIEUP 9CCB C470 # HANGUL SYLLABLE SSANGSIOS-U-RIEULSIOS 9CCC C471 # HANGUL SYLLABLE SSANGSIOS-U-RIEULTHIEUTH 9CCD C472 # HANGUL SYLLABLE SSANGSIOS-U-RIEULPHIEUPH 9CCE C473 # HANGUL SYLLABLE SSANGSIOS-U-RIEULHIEUH 9CCF C476 # HANGUL SYLLABLE SSANGSIOS-U-PIEUPSIOS 9CD0 C477 # HANGUL SYLLABLE SSANGSIOS-U-SIOS 9CD1 C478 # HANGUL SYLLABLE SSANGSIOS-U-SSANGSIOS 9CD2 C47A # HANGUL SYLLABLE SSANGSIOS-U-CIEUC 9CD3 C47B # HANGUL SYLLABLE SSANGSIOS-U-CHIEUCH 9CD4 C47C # HANGUL SYLLABLE SSANGSIOS-U-KHIEUKH 9CD5 C47D # HANGUL SYLLABLE SSANGSIOS-U-THIEUTH 9CD6 C47E # HANGUL SYLLABLE SSANGSIOS-U-PHIEUPH 9CD7 C47F # HANGUL SYLLABLE SSANGSIOS-U-HIEUH 9CD8 C481 # HANGUL SYLLABLE SSANGSIOS-WEO-KIYEOK 9CD9 C482 # HANGUL SYLLABLE SSANGSIOS-WEO-SSANGKIYEOK 9CDA C483 # HANGUL SYLLABLE SSANGSIOS-WEO-KIYEOKSIOS 9CDB C484 # HANGUL SYLLABLE SSANGSIOS-WEO-NIEUN 9CDC C485 # HANGUL SYLLABLE SSANGSIOS-WEO-NIEUNCIEUC 9CDD C486 # HANGUL SYLLABLE SSANGSIOS-WEO-NIEUNHIEUH 9CDE C487 # HANGUL SYLLABLE SSANGSIOS-WEO-TIKEUT 9CDF C488 # HANGUL SYLLABLE SSANGSIOS-WEO-RIEUL 9CE0 C489 # HANGUL SYLLABLE SSANGSIOS-WEO-RIEULKIYEOK 9CE1 C48A # HANGUL SYLLABLE SSANGSIOS-WEO-RIEULMIEUM 9CE2 C48B # HANGUL SYLLABLE SSANGSIOS-WEO-RIEULPIEUP 9CE3 C48C # HANGUL SYLLABLE SSANGSIOS-WEO-RIEULSIOS 9CE4 C48D # HANGUL SYLLABLE SSANGSIOS-WEO-RIEULTHIEUTH 9CE5 C48E # HANGUL SYLLABLE SSANGSIOS-WEO-RIEULPHIEUPH 9CE6 C48F # HANGUL SYLLABLE SSANGSIOS-WEO-RIEULHIEUH 9CE7 C490 # HANGUL SYLLABLE SSANGSIOS-WEO-MIEUM 9CE8 C491 # HANGUL SYLLABLE SSANGSIOS-WEO-PIEUP 9CE9 C492 # HANGUL SYLLABLE SSANGSIOS-WEO-PIEUPSIOS 9CEA C493 # HANGUL SYLLABLE SSANGSIOS-WEO-SIOS 9CEB C495 # HANGUL SYLLABLE SSANGSIOS-WEO-IEUNG 9CEC C496 # HANGUL SYLLABLE SSANGSIOS-WEO-CIEUC 9CED C497 # HANGUL SYLLABLE SSANGSIOS-WEO-CHIEUCH 9CEE C498 # HANGUL SYLLABLE SSANGSIOS-WEO-KHIEUKH 9CEF C499 # HANGUL SYLLABLE SSANGSIOS-WEO-THIEUTH 9CF0 C49A # HANGUL SYLLABLE SSANGSIOS-WEO-PHIEUPH 9CF1 C49B # HANGUL SYLLABLE SSANGSIOS-WEO-HIEUH 9CF2 C49D # HANGUL SYLLABLE SSANGSIOS-WE-KIYEOK 9CF3 C49E # HANGUL SYLLABLE SSANGSIOS-WE-SSANGKIYEOK 9CF4 C49F # HANGUL SYLLABLE SSANGSIOS-WE-KIYEOKSIOS 9CF5 C4A0 # HANGUL SYLLABLE SSANGSIOS-WE-NIEUN 9CF6 C4A1 # HANGUL SYLLABLE SSANGSIOS-WE-NIEUNCIEUC 9CF7 C4A2 # HANGUL SYLLABLE SSANGSIOS-WE-NIEUNHIEUH 9CF8 C4A3 # HANGUL SYLLABLE SSANGSIOS-WE-TIKEUT 9CF9 C4A4 # HANGUL SYLLABLE SSANGSIOS-WE-RIEUL 9CFA C4A5 # HANGUL SYLLABLE SSANGSIOS-WE-RIEULKIYEOK 9CFB C4A6 # HANGUL SYLLABLE SSANGSIOS-WE-RIEULMIEUM 9CFC C4A7 # HANGUL SYLLABLE SSANGSIOS-WE-RIEULPIEUP 9CFD C4A8 # HANGUL SYLLABLE SSANGSIOS-WE-RIEULSIOS 9CFE C4A9 # HANGUL SYLLABLE SSANGSIOS-WE-RIEULTHIEUTH 9D41 C4AA # HANGUL SYLLABLE SSANGSIOS-WE-RIEULPHIEUPH 9D42 C4AB # HANGUL SYLLABLE SSANGSIOS-WE-RIEULHIEUH 9D43 C4AC # HANGUL SYLLABLE SSANGSIOS-WE-MIEUM 9D44 C4AD # HANGUL SYLLABLE SSANGSIOS-WE-PIEUP 9D45 C4AE # HANGUL SYLLABLE SSANGSIOS-WE-PIEUPSIOS 9D46 C4AF # HANGUL SYLLABLE SSANGSIOS-WE-SIOS 9D47 C4B0 # HANGUL SYLLABLE SSANGSIOS-WE-SSANGSIOS 9D48 C4B1 # HANGUL SYLLABLE SSANGSIOS-WE-IEUNG 9D49 C4B2 # HANGUL SYLLABLE SSANGSIOS-WE-CIEUC 9D4A C4B3 # HANGUL SYLLABLE SSANGSIOS-WE-CHIEUCH 9D4B C4B4 # HANGUL SYLLABLE SSANGSIOS-WE-KHIEUKH 9D4C C4B5 # HANGUL SYLLABLE SSANGSIOS-WE-THIEUTH 9D4D C4B6 # HANGUL SYLLABLE SSANGSIOS-WE-PHIEUPH 9D4E C4B7 # HANGUL SYLLABLE SSANGSIOS-WE-HIEUH 9D4F C4B9 # HANGUL SYLLABLE SSANGSIOS-WI-KIYEOK 9D50 C4BA # HANGUL SYLLABLE SSANGSIOS-WI-SSANGKIYEOK 9D51 C4BB # HANGUL SYLLABLE SSANGSIOS-WI-KIYEOKSIOS 9D52 C4BD # HANGUL SYLLABLE SSANGSIOS-WI-NIEUNCIEUC 9D53 C4BE # HANGUL SYLLABLE SSANGSIOS-WI-NIEUNHIEUH 9D54 C4BF # HANGUL SYLLABLE SSANGSIOS-WI-TIKEUT 9D55 C4C0 # HANGUL SYLLABLE SSANGSIOS-WI-RIEUL 9D56 C4C1 # HANGUL SYLLABLE SSANGSIOS-WI-RIEULKIYEOK 9D57 C4C2 # HANGUL SYLLABLE SSANGSIOS-WI-RIEULMIEUM 9D58 C4C3 # HANGUL SYLLABLE SSANGSIOS-WI-RIEULPIEUP 9D59 C4C4 # HANGUL SYLLABLE SSANGSIOS-WI-RIEULSIOS 9D5A C4C5 # HANGUL SYLLABLE SSANGSIOS-WI-RIEULTHIEUTH 9D61 C4C6 # HANGUL SYLLABLE SSANGSIOS-WI-RIEULPHIEUPH 9D62 C4C7 # HANGUL SYLLABLE SSANGSIOS-WI-RIEULHIEUH 9D63 C4C8 # HANGUL SYLLABLE SSANGSIOS-WI-MIEUM 9D64 C4C9 # HANGUL SYLLABLE SSANGSIOS-WI-PIEUP 9D65 C4CA # HANGUL SYLLABLE SSANGSIOS-WI-PIEUPSIOS 9D66 C4CB # HANGUL SYLLABLE SSANGSIOS-WI-SIOS 9D67 C4CC # HANGUL SYLLABLE SSANGSIOS-WI-SSANGSIOS 9D68 C4CD # HANGUL SYLLABLE SSANGSIOS-WI-IEUNG 9D69 C4CE # HANGUL SYLLABLE SSANGSIOS-WI-CIEUC 9D6A C4CF # HANGUL SYLLABLE SSANGSIOS-WI-CHIEUCH 9D6B C4D0 # HANGUL SYLLABLE SSANGSIOS-WI-KHIEUKH 9D6C C4D1 # HANGUL SYLLABLE SSANGSIOS-WI-THIEUTH 9D6D C4D2 # HANGUL SYLLABLE SSANGSIOS-WI-PHIEUPH 9D6E C4D3 # HANGUL SYLLABLE SSANGSIOS-WI-HIEUH 9D6F C4D4 # HANGUL SYLLABLE SSANGSIOS-YU 9D70 C4D5 # HANGUL SYLLABLE SSANGSIOS-YU-KIYEOK 9D71 C4D6 # HANGUL SYLLABLE SSANGSIOS-YU-SSANGKIYEOK 9D72 C4D7 # HANGUL SYLLABLE SSANGSIOS-YU-KIYEOKSIOS 9D73 C4D8 # HANGUL SYLLABLE SSANGSIOS-YU-NIEUN 9D74 C4D9 # HANGUL SYLLABLE SSANGSIOS-YU-NIEUNCIEUC 9D75 C4DA # HANGUL SYLLABLE SSANGSIOS-YU-NIEUNHIEUH 9D76 C4DB # HANGUL SYLLABLE SSANGSIOS-YU-TIKEUT 9D77 C4DC # HANGUL SYLLABLE SSANGSIOS-YU-RIEUL 9D78 C4DD # HANGUL SYLLABLE SSANGSIOS-YU-RIEULKIYEOK 9D79 C4DE # HANGUL SYLLABLE SSANGSIOS-YU-RIEULMIEUM 9D7A C4DF # HANGUL SYLLABLE SSANGSIOS-YU-RIEULPIEUP 9D81 C4E0 # HANGUL SYLLABLE SSANGSIOS-YU-RIEULSIOS 9D82 C4E1 # HANGUL SYLLABLE SSANGSIOS-YU-RIEULTHIEUTH 9D83 C4E2 # HANGUL SYLLABLE SSANGSIOS-YU-RIEULPHIEUPH 9D84 C4E3 # HANGUL SYLLABLE SSANGSIOS-YU-RIEULHIEUH 9D85 C4E4 # HANGUL SYLLABLE SSANGSIOS-YU-MIEUM 9D86 C4E5 # HANGUL SYLLABLE SSANGSIOS-YU-PIEUP 9D87 C4E6 # HANGUL SYLLABLE SSANGSIOS-YU-PIEUPSIOS 9D88 C4E7 # HANGUL SYLLABLE SSANGSIOS-YU-SIOS 9D89 C4E8 # HANGUL SYLLABLE SSANGSIOS-YU-SSANGSIOS 9D8A C4EA # HANGUL SYLLABLE SSANGSIOS-YU-CIEUC 9D8B C4EB # HANGUL SYLLABLE SSANGSIOS-YU-CHIEUCH 9D8C C4EC # HANGUL SYLLABLE SSANGSIOS-YU-KHIEUKH 9D8D C4ED # HANGUL SYLLABLE SSANGSIOS-YU-THIEUTH 9D8E C4EE # HANGUL SYLLABLE SSANGSIOS-YU-PHIEUPH 9D8F C4EF # HANGUL SYLLABLE SSANGSIOS-YU-HIEUH 9D90 C4F2 # HANGUL SYLLABLE SSANGSIOS-EU-SSANGKIYEOK 9D91 C4F3 # HANGUL SYLLABLE SSANGSIOS-EU-KIYEOKSIOS 9D92 C4F5 # HANGUL SYLLABLE SSANGSIOS-EU-NIEUNCIEUC 9D93 C4F6 # HANGUL SYLLABLE SSANGSIOS-EU-NIEUNHIEUH 9D94 C4F7 # HANGUL SYLLABLE SSANGSIOS-EU-TIKEUT 9D95 C4F9 # HANGUL SYLLABLE SSANGSIOS-EU-RIEULKIYEOK 9D96 C4FB # HANGUL SYLLABLE SSANGSIOS-EU-RIEULPIEUP 9D97 C4FC # HANGUL SYLLABLE SSANGSIOS-EU-RIEULSIOS 9D98 C4FD # HANGUL SYLLABLE SSANGSIOS-EU-RIEULTHIEUTH 9D99 C4FE # HANGUL SYLLABLE SSANGSIOS-EU-RIEULPHIEUPH 9D9A C502 # HANGUL SYLLABLE SSANGSIOS-EU-PIEUPSIOS 9D9B C503 # HANGUL SYLLABLE SSANGSIOS-EU-SIOS 9D9C C504 # HANGUL SYLLABLE SSANGSIOS-EU-SSANGSIOS 9D9D C505 # HANGUL SYLLABLE SSANGSIOS-EU-IEUNG 9D9E C506 # HANGUL SYLLABLE SSANGSIOS-EU-CIEUC 9D9F C507 # HANGUL SYLLABLE SSANGSIOS-EU-CHIEUCH 9DA0 C508 # HANGUL SYLLABLE SSANGSIOS-EU-KHIEUKH 9DA1 C509 # HANGUL SYLLABLE SSANGSIOS-EU-THIEUTH 9DA2 C50A # HANGUL SYLLABLE SSANGSIOS-EU-PHIEUPH 9DA3 C50B # HANGUL SYLLABLE SSANGSIOS-EU-HIEUH 9DA4 C50D # HANGUL SYLLABLE SSANGSIOS-YI-KIYEOK 9DA5 C50E # HANGUL SYLLABLE SSANGSIOS-YI-SSANGKIYEOK 9DA6 C50F # HANGUL SYLLABLE SSANGSIOS-YI-KIYEOKSIOS 9DA7 C511 # HANGUL SYLLABLE SSANGSIOS-YI-NIEUNCIEUC 9DA8 C512 # HANGUL SYLLABLE SSANGSIOS-YI-NIEUNHIEUH 9DA9 C513 # HANGUL SYLLABLE SSANGSIOS-YI-TIKEUT 9DAA C515 # HANGUL SYLLABLE SSANGSIOS-YI-RIEULKIYEOK 9DAB C516 # HANGUL SYLLABLE SSANGSIOS-YI-RIEULMIEUM 9DAC C517 # HANGUL SYLLABLE SSANGSIOS-YI-RIEULPIEUP 9DAD C518 # HANGUL SYLLABLE SSANGSIOS-YI-RIEULSIOS 9DAE C519 # HANGUL SYLLABLE SSANGSIOS-YI-RIEULTHIEUTH 9DAF C51A # HANGUL SYLLABLE SSANGSIOS-YI-RIEULPHIEUPH 9DB0 C51B # HANGUL SYLLABLE SSANGSIOS-YI-RIEULHIEUH 9DB1 C51D # HANGUL SYLLABLE SSANGSIOS-YI-PIEUP 9DB2 C51E # HANGUL SYLLABLE SSANGSIOS-YI-PIEUPSIOS 9DB3 C51F # HANGUL SYLLABLE SSANGSIOS-YI-SIOS 9DB4 C520 # HANGUL SYLLABLE SSANGSIOS-YI-SSANGSIOS 9DB5 C521 # HANGUL SYLLABLE SSANGSIOS-YI-IEUNG 9DB6 C522 # HANGUL SYLLABLE SSANGSIOS-YI-CIEUC 9DB7 C523 # HANGUL SYLLABLE SSANGSIOS-YI-CHIEUCH 9DB8 C524 # HANGUL SYLLABLE SSANGSIOS-YI-KHIEUKH 9DB9 C525 # HANGUL SYLLABLE SSANGSIOS-YI-THIEUTH 9DBA C526 # HANGUL SYLLABLE SSANGSIOS-YI-PHIEUPH 9DBB C527 # HANGUL SYLLABLE SSANGSIOS-YI-HIEUH 9DBC C52A # HANGUL SYLLABLE SSANGSIOS-I-SSANGKIYEOK 9DBD C52B # HANGUL SYLLABLE SSANGSIOS-I-KIYEOKSIOS 9DBE C52D # HANGUL SYLLABLE SSANGSIOS-I-NIEUNCIEUC 9DBF C52E # HANGUL SYLLABLE SSANGSIOS-I-NIEUNHIEUH 9DC0 C52F # HANGUL SYLLABLE SSANGSIOS-I-TIKEUT 9DC1 C531 # HANGUL SYLLABLE SSANGSIOS-I-RIEULKIYEOK 9DC2 C532 # HANGUL SYLLABLE SSANGSIOS-I-RIEULMIEUM 9DC3 C533 # HANGUL SYLLABLE SSANGSIOS-I-RIEULPIEUP 9DC4 C534 # HANGUL SYLLABLE SSANGSIOS-I-RIEULSIOS 9DC5 C535 # HANGUL SYLLABLE SSANGSIOS-I-RIEULTHIEUTH 9DC6 C536 # HANGUL SYLLABLE SSANGSIOS-I-RIEULPHIEUPH 9DC7 C537 # HANGUL SYLLABLE SSANGSIOS-I-RIEULHIEUH 9DC8 C53A # HANGUL SYLLABLE SSANGSIOS-I-PIEUPSIOS 9DC9 C53C # HANGUL SYLLABLE SSANGSIOS-I-SSANGSIOS 9DCA C53E # HANGUL SYLLABLE SSANGSIOS-I-CIEUC 9DCB C53F # HANGUL SYLLABLE SSANGSIOS-I-CHIEUCH 9DCC C540 # HANGUL SYLLABLE SSANGSIOS-I-KHIEUKH 9DCD C541 # HANGUL SYLLABLE SSANGSIOS-I-THIEUTH 9DCE C542 # HANGUL SYLLABLE SSANGSIOS-I-PHIEUPH 9DCF C543 # HANGUL SYLLABLE SSANGSIOS-I-HIEUH 9DD0 C546 # HANGUL SYLLABLE IEUNG-A-SSANGKIYEOK 9DD1 C547 # HANGUL SYLLABLE IEUNG-A-KIYEOKSIOS 9DD2 C54B # HANGUL SYLLABLE IEUNG-A-TIKEUT 9DD3 C54F # HANGUL SYLLABLE IEUNG-A-RIEULPIEUP 9DD4 C550 # HANGUL SYLLABLE IEUNG-A-RIEULSIOS 9DD5 C551 # HANGUL SYLLABLE IEUNG-A-RIEULTHIEUTH 9DD6 C552 # HANGUL SYLLABLE IEUNG-A-RIEULPHIEUPH 9DD7 C556 # HANGUL SYLLABLE IEUNG-A-PIEUPSIOS 9DD8 C55A # HANGUL SYLLABLE IEUNG-A-CIEUC 9DD9 C55B # HANGUL SYLLABLE IEUNG-A-CHIEUCH 9DDA C55C # HANGUL SYLLABLE IEUNG-A-KHIEUKH 9DDB C55F # HANGUL SYLLABLE IEUNG-A-HIEUH 9DDC C562 # HANGUL SYLLABLE IEUNG-AE-SSANGKIYEOK 9DDD C563 # HANGUL SYLLABLE IEUNG-AE-KIYEOKSIOS 9DDE C565 # HANGUL SYLLABLE IEUNG-AE-NIEUNCIEUC 9DDF C566 # HANGUL SYLLABLE IEUNG-AE-NIEUNHIEUH 9DE0 C567 # HANGUL SYLLABLE IEUNG-AE-TIKEUT 9DE1 C569 # HANGUL SYLLABLE IEUNG-AE-RIEULKIYEOK 9DE2 C56A # HANGUL SYLLABLE IEUNG-AE-RIEULMIEUM 9DE3 C56B # HANGUL SYLLABLE IEUNG-AE-RIEULPIEUP 9DE4 C56C # HANGUL SYLLABLE IEUNG-AE-RIEULSIOS 9DE5 C56D # HANGUL SYLLABLE IEUNG-AE-RIEULTHIEUTH 9DE6 C56E # HANGUL SYLLABLE IEUNG-AE-RIEULPHIEUPH 9DE7 C56F # HANGUL SYLLABLE IEUNG-AE-RIEULHIEUH 9DE8 C572 # HANGUL SYLLABLE IEUNG-AE-PIEUPSIOS 9DE9 C576 # HANGUL SYLLABLE IEUNG-AE-CIEUC 9DEA C577 # HANGUL SYLLABLE IEUNG-AE-CHIEUCH 9DEB C578 # HANGUL SYLLABLE IEUNG-AE-KHIEUKH 9DEC C579 # HANGUL SYLLABLE IEUNG-AE-THIEUTH 9DED C57A # HANGUL SYLLABLE IEUNG-AE-PHIEUPH 9DEE C57B # HANGUL SYLLABLE IEUNG-AE-HIEUH 9DEF C57E # HANGUL SYLLABLE IEUNG-YA-SSANGKIYEOK 9DF0 C57F # HANGUL SYLLABLE IEUNG-YA-KIYEOKSIOS 9DF1 C581 # HANGUL SYLLABLE IEUNG-YA-NIEUNCIEUC 9DF2 C582 # HANGUL SYLLABLE IEUNG-YA-NIEUNHIEUH 9DF3 C583 # HANGUL SYLLABLE IEUNG-YA-TIKEUT 9DF4 C585 # HANGUL SYLLABLE IEUNG-YA-RIEULKIYEOK 9DF5 C586 # HANGUL SYLLABLE IEUNG-YA-RIEULMIEUM 9DF6 C588 # HANGUL SYLLABLE IEUNG-YA-RIEULSIOS 9DF7 C589 # HANGUL SYLLABLE IEUNG-YA-RIEULTHIEUTH 9DF8 C58A # HANGUL SYLLABLE IEUNG-YA-RIEULPHIEUPH 9DF9 C58B # HANGUL SYLLABLE IEUNG-YA-RIEULHIEUH 9DFA C58E # HANGUL SYLLABLE IEUNG-YA-PIEUPSIOS 9DFB C590 # HANGUL SYLLABLE IEUNG-YA-SSANGSIOS 9DFC C592 # HANGUL SYLLABLE IEUNG-YA-CIEUC 9DFD C593 # HANGUL SYLLABLE IEUNG-YA-CHIEUCH 9DFE C594 # HANGUL SYLLABLE IEUNG-YA-KHIEUKH 9E41 C596 # HANGUL SYLLABLE IEUNG-YA-PHIEUPH 9E42 C599 # HANGUL SYLLABLE IEUNG-YAE-KIYEOK 9E43 C59A # HANGUL SYLLABLE IEUNG-YAE-SSANGKIYEOK 9E44 C59B # HANGUL SYLLABLE IEUNG-YAE-KIYEOKSIOS 9E45 C59D # HANGUL SYLLABLE IEUNG-YAE-NIEUNCIEUC 9E46 C59E # HANGUL SYLLABLE IEUNG-YAE-NIEUNHIEUH 9E47 C59F # HANGUL SYLLABLE IEUNG-YAE-TIKEUT 9E48 C5A1 # HANGUL SYLLABLE IEUNG-YAE-RIEULKIYEOK 9E49 C5A2 # HANGUL SYLLABLE IEUNG-YAE-RIEULMIEUM 9E4A C5A3 # HANGUL SYLLABLE IEUNG-YAE-RIEULPIEUP 9E4B C5A4 # HANGUL SYLLABLE IEUNG-YAE-RIEULSIOS 9E4C C5A5 # HANGUL SYLLABLE IEUNG-YAE-RIEULTHIEUTH 9E4D C5A6 # HANGUL SYLLABLE IEUNG-YAE-RIEULPHIEUPH 9E4E C5A7 # HANGUL SYLLABLE IEUNG-YAE-RIEULHIEUH 9E4F C5A8 # HANGUL SYLLABLE IEUNG-YAE-MIEUM 9E50 C5AA # HANGUL SYLLABLE IEUNG-YAE-PIEUPSIOS 9E51 C5AB # HANGUL SYLLABLE IEUNG-YAE-SIOS 9E52 C5AC # HANGUL SYLLABLE IEUNG-YAE-SSANGSIOS 9E53 C5AD # HANGUL SYLLABLE IEUNG-YAE-IEUNG 9E54 C5AE # HANGUL SYLLABLE IEUNG-YAE-CIEUC 9E55 C5AF # HANGUL SYLLABLE IEUNG-YAE-CHIEUCH 9E56 C5B0 # HANGUL SYLLABLE IEUNG-YAE-KHIEUKH 9E57 C5B1 # HANGUL SYLLABLE IEUNG-YAE-THIEUTH 9E58 C5B2 # HANGUL SYLLABLE IEUNG-YAE-PHIEUPH 9E59 C5B3 # HANGUL SYLLABLE IEUNG-YAE-HIEUH 9E5A C5B6 # HANGUL SYLLABLE IEUNG-EO-SSANGKIYEOK 9E61 C5B7 # HANGUL SYLLABLE IEUNG-EO-KIYEOKSIOS 9E62 C5BA # HANGUL SYLLABLE IEUNG-EO-NIEUNHIEUH 9E63 C5BF # HANGUL SYLLABLE IEUNG-EO-RIEULPIEUP 9E64 C5C0 # HANGUL SYLLABLE IEUNG-EO-RIEULSIOS 9E65 C5C1 # HANGUL SYLLABLE IEUNG-EO-RIEULTHIEUTH 9E66 C5C2 # HANGUL SYLLABLE IEUNG-EO-RIEULPHIEUPH 9E67 C5C3 # HANGUL SYLLABLE IEUNG-EO-RIEULHIEUH 9E68 C5CB # HANGUL SYLLABLE IEUNG-EO-CHIEUCH 9E69 C5CD # HANGUL SYLLABLE IEUNG-EO-THIEUTH 9E6A C5CF # HANGUL SYLLABLE IEUNG-EO-HIEUH 9E6B C5D2 # HANGUL SYLLABLE IEUNG-E-SSANGKIYEOK 9E6C C5D3 # HANGUL SYLLABLE IEUNG-E-KIYEOKSIOS 9E6D C5D5 # HANGUL SYLLABLE IEUNG-E-NIEUNCIEUC 9E6E C5D6 # HANGUL SYLLABLE IEUNG-E-NIEUNHIEUH 9E6F C5D7 # HANGUL SYLLABLE IEUNG-E-TIKEUT 9E70 C5D9 # HANGUL SYLLABLE IEUNG-E-RIEULKIYEOK 9E71 C5DA # HANGUL SYLLABLE IEUNG-E-RIEULMIEUM 9E72 C5DB # HANGUL SYLLABLE IEUNG-E-RIEULPIEUP 9E73 C5DC # HANGUL SYLLABLE IEUNG-E-RIEULSIOS 9E74 C5DD # HANGUL SYLLABLE IEUNG-E-RIEULTHIEUTH 9E75 C5DE # HANGUL SYLLABLE IEUNG-E-RIEULPHIEUPH 9E76 C5DF # HANGUL SYLLABLE IEUNG-E-RIEULHIEUH 9E77 C5E2 # HANGUL SYLLABLE IEUNG-E-PIEUPSIOS 9E78 C5E4 # HANGUL SYLLABLE IEUNG-E-SSANGSIOS 9E79 C5E6 # HANGUL SYLLABLE IEUNG-E-CIEUC 9E7A C5E7 # HANGUL SYLLABLE IEUNG-E-CHIEUCH 9E81 C5E8 # HANGUL SYLLABLE IEUNG-E-KHIEUKH 9E82 C5E9 # HANGUL SYLLABLE IEUNG-E-THIEUTH 9E83 C5EA # HANGUL SYLLABLE IEUNG-E-PHIEUPH 9E84 C5EB # HANGUL SYLLABLE IEUNG-E-HIEUH 9E85 C5EF # HANGUL SYLLABLE IEUNG-YEO-KIYEOKSIOS 9E86 C5F1 # HANGUL SYLLABLE IEUNG-YEO-NIEUNCIEUC 9E87 C5F2 # HANGUL SYLLABLE IEUNG-YEO-NIEUNHIEUH 9E88 C5F3 # HANGUL SYLLABLE IEUNG-YEO-TIKEUT 9E89 C5F5 # HANGUL SYLLABLE IEUNG-YEO-RIEULKIYEOK 9E8A C5F8 # HANGUL SYLLABLE IEUNG-YEO-RIEULSIOS 9E8B C5F9 # HANGUL SYLLABLE IEUNG-YEO-RIEULTHIEUTH 9E8C C5FA # HANGUL SYLLABLE IEUNG-YEO-RIEULPHIEUPH 9E8D C5FB # HANGUL SYLLABLE IEUNG-YEO-RIEULHIEUH 9E8E C602 # HANGUL SYLLABLE IEUNG-YEO-CIEUC 9E8F C603 # HANGUL SYLLABLE IEUNG-YEO-CHIEUCH 9E90 C604 # HANGUL SYLLABLE IEUNG-YEO-KHIEUKH 9E91 C609 # HANGUL SYLLABLE IEUNG-YE-KIYEOK 9E92 C60A # HANGUL SYLLABLE IEUNG-YE-SSANGKIYEOK 9E93 C60B # HANGUL SYLLABLE IEUNG-YE-KIYEOKSIOS 9E94 C60D # HANGUL SYLLABLE IEUNG-YE-NIEUNCIEUC 9E95 C60E # HANGUL SYLLABLE IEUNG-YE-NIEUNHIEUH 9E96 C60F # HANGUL SYLLABLE IEUNG-YE-TIKEUT 9E97 C611 # HANGUL SYLLABLE IEUNG-YE-RIEULKIYEOK 9E98 C612 # HANGUL SYLLABLE IEUNG-YE-RIEULMIEUM 9E99 C613 # HANGUL SYLLABLE IEUNG-YE-RIEULPIEUP 9E9A C614 # HANGUL SYLLABLE IEUNG-YE-RIEULSIOS 9E9B C615 # HANGUL SYLLABLE IEUNG-YE-RIEULTHIEUTH 9E9C C616 # HANGUL SYLLABLE IEUNG-YE-RIEULPHIEUPH 9E9D C617 # HANGUL SYLLABLE IEUNG-YE-RIEULHIEUH 9E9E C61A # HANGUL SYLLABLE IEUNG-YE-PIEUPSIOS 9E9F C61D # HANGUL SYLLABLE IEUNG-YE-IEUNG 9EA0 C61E # HANGUL SYLLABLE IEUNG-YE-CIEUC 9EA1 C61F # HANGUL SYLLABLE IEUNG-YE-CHIEUCH 9EA2 C620 # HANGUL SYLLABLE IEUNG-YE-KHIEUKH 9EA3 C621 # HANGUL SYLLABLE IEUNG-YE-THIEUTH 9EA4 C622 # HANGUL SYLLABLE IEUNG-YE-PHIEUPH 9EA5 C623 # HANGUL SYLLABLE IEUNG-YE-HIEUH 9EA6 C626 # HANGUL SYLLABLE IEUNG-O-SSANGKIYEOK 9EA7 C627 # HANGUL SYLLABLE IEUNG-O-KIYEOKSIOS 9EA8 C629 # HANGUL SYLLABLE IEUNG-O-NIEUNCIEUC 9EA9 C62A # HANGUL SYLLABLE IEUNG-O-NIEUNHIEUH 9EAA C62B # HANGUL SYLLABLE IEUNG-O-TIKEUT 9EAB C62F # HANGUL SYLLABLE IEUNG-O-RIEULPIEUP 9EAC C631 # HANGUL SYLLABLE IEUNG-O-RIEULTHIEUTH 9EAD C632 # HANGUL SYLLABLE IEUNG-O-RIEULPHIEUPH 9EAE C636 # HANGUL SYLLABLE IEUNG-O-PIEUPSIOS 9EAF C638 # HANGUL SYLLABLE IEUNG-O-SSANGSIOS 9EB0 C63A # HANGUL SYLLABLE IEUNG-O-CIEUC 9EB1 C63C # HANGUL SYLLABLE IEUNG-O-KHIEUKH 9EB2 C63D # HANGUL SYLLABLE IEUNG-O-THIEUTH 9EB3 C63E # HANGUL SYLLABLE IEUNG-O-PHIEUPH 9EB4 C63F # HANGUL SYLLABLE IEUNG-O-HIEUH 9EB5 C642 # HANGUL SYLLABLE IEUNG-WA-SSANGKIYEOK 9EB6 C643 # HANGUL SYLLABLE IEUNG-WA-KIYEOKSIOS 9EB7 C645 # HANGUL SYLLABLE IEUNG-WA-NIEUNCIEUC 9EB8 C646 # HANGUL SYLLABLE IEUNG-WA-NIEUNHIEUH 9EB9 C647 # HANGUL SYLLABLE IEUNG-WA-TIKEUT 9EBA C649 # HANGUL SYLLABLE IEUNG-WA-RIEULKIYEOK 9EBB C64A # HANGUL SYLLABLE IEUNG-WA-RIEULMIEUM 9EBC C64B # HANGUL SYLLABLE IEUNG-WA-RIEULPIEUP 9EBD C64C # HANGUL SYLLABLE IEUNG-WA-RIEULSIOS 9EBE C64D # HANGUL SYLLABLE IEUNG-WA-RIEULTHIEUTH 9EBF C64E # HANGUL SYLLABLE IEUNG-WA-RIEULPHIEUPH 9EC0 C64F # HANGUL SYLLABLE IEUNG-WA-RIEULHIEUH 9EC1 C652 # HANGUL SYLLABLE IEUNG-WA-PIEUPSIOS 9EC2 C656 # HANGUL SYLLABLE IEUNG-WA-CIEUC 9EC3 C657 # HANGUL SYLLABLE IEUNG-WA-CHIEUCH 9EC4 C658 # HANGUL SYLLABLE IEUNG-WA-KHIEUKH 9EC5 C659 # HANGUL SYLLABLE IEUNG-WA-THIEUTH 9EC6 C65A # HANGUL SYLLABLE IEUNG-WA-PHIEUPH 9EC7 C65B # HANGUL SYLLABLE IEUNG-WA-HIEUH 9EC8 C65E # HANGUL SYLLABLE IEUNG-WAE-SSANGKIYEOK 9EC9 C65F # HANGUL SYLLABLE IEUNG-WAE-KIYEOKSIOS 9ECA C661 # HANGUL SYLLABLE IEUNG-WAE-NIEUNCIEUC 9ECB C662 # HANGUL SYLLABLE IEUNG-WAE-NIEUNHIEUH 9ECC C663 # HANGUL SYLLABLE IEUNG-WAE-TIKEUT 9ECD C664 # HANGUL SYLLABLE IEUNG-WAE-RIEUL 9ECE C665 # HANGUL SYLLABLE IEUNG-WAE-RIEULKIYEOK 9ECF C666 # HANGUL SYLLABLE IEUNG-WAE-RIEULMIEUM 9ED0 C667 # HANGUL SYLLABLE IEUNG-WAE-RIEULPIEUP 9ED1 C668 # HANGUL SYLLABLE IEUNG-WAE-RIEULSIOS 9ED2 C669 # HANGUL SYLLABLE IEUNG-WAE-RIEULTHIEUTH 9ED3 C66A # HANGUL SYLLABLE IEUNG-WAE-RIEULPHIEUPH 9ED4 C66B # HANGUL SYLLABLE IEUNG-WAE-RIEULHIEUH 9ED5 C66D # HANGUL SYLLABLE IEUNG-WAE-PIEUP 9ED6 C66E # HANGUL SYLLABLE IEUNG-WAE-PIEUPSIOS 9ED7 C670 # HANGUL SYLLABLE IEUNG-WAE-SSANGSIOS 9ED8 C672 # HANGUL SYLLABLE IEUNG-WAE-CIEUC 9ED9 C673 # HANGUL SYLLABLE IEUNG-WAE-CHIEUCH 9EDA C674 # HANGUL SYLLABLE IEUNG-WAE-KHIEUKH 9EDB C675 # HANGUL SYLLABLE IEUNG-WAE-THIEUTH 9EDC C676 # HANGUL SYLLABLE IEUNG-WAE-PHIEUPH 9EDD C677 # HANGUL SYLLABLE IEUNG-WAE-HIEUH 9EDE C67A # HANGUL SYLLABLE IEUNG-OE-SSANGKIYEOK 9EDF C67B # HANGUL SYLLABLE IEUNG-OE-KIYEOKSIOS 9EE0 C67D # HANGUL SYLLABLE IEUNG-OE-NIEUNCIEUC 9EE1 C67E # HANGUL SYLLABLE IEUNG-OE-NIEUNHIEUH 9EE2 C67F # HANGUL SYLLABLE IEUNG-OE-TIKEUT 9EE3 C681 # HANGUL SYLLABLE IEUNG-OE-RIEULKIYEOK 9EE4 C682 # HANGUL SYLLABLE IEUNG-OE-RIEULMIEUM 9EE5 C683 # HANGUL SYLLABLE IEUNG-OE-RIEULPIEUP 9EE6 C684 # HANGUL SYLLABLE IEUNG-OE-RIEULSIOS 9EE7 C685 # HANGUL SYLLABLE IEUNG-OE-RIEULTHIEUTH 9EE8 C686 # HANGUL SYLLABLE IEUNG-OE-RIEULPHIEUPH 9EE9 C687 # HANGUL SYLLABLE IEUNG-OE-RIEULHIEUH 9EEA C68A # HANGUL SYLLABLE IEUNG-OE-PIEUPSIOS 9EEB C68C # HANGUL SYLLABLE IEUNG-OE-SSANGSIOS 9EEC C68E # HANGUL SYLLABLE IEUNG-OE-CIEUC 9EED C68F # HANGUL SYLLABLE IEUNG-OE-CHIEUCH 9EEE C690 # HANGUL SYLLABLE IEUNG-OE-KHIEUKH 9EEF C691 # HANGUL SYLLABLE IEUNG-OE-THIEUTH 9EF0 C692 # HANGUL SYLLABLE IEUNG-OE-PHIEUPH 9EF1 C693 # HANGUL SYLLABLE IEUNG-OE-HIEUH 9EF2 C696 # HANGUL SYLLABLE IEUNG-YO-SSANGKIYEOK 9EF3 C697 # HANGUL SYLLABLE IEUNG-YO-KIYEOKSIOS 9EF4 C699 # HANGUL SYLLABLE IEUNG-YO-NIEUNCIEUC 9EF5 C69A # HANGUL SYLLABLE IEUNG-YO-NIEUNHIEUH 9EF6 C69B # HANGUL SYLLABLE IEUNG-YO-TIKEUT 9EF7 C69D # HANGUL SYLLABLE IEUNG-YO-RIEULKIYEOK 9EF8 C69E # HANGUL SYLLABLE IEUNG-YO-RIEULMIEUM 9EF9 C69F # HANGUL SYLLABLE IEUNG-YO-RIEULPIEUP 9EFA C6A0 # HANGUL SYLLABLE IEUNG-YO-RIEULSIOS 9EFB C6A1 # HANGUL SYLLABLE IEUNG-YO-RIEULTHIEUTH 9EFC C6A2 # HANGUL SYLLABLE IEUNG-YO-RIEULPHIEUPH 9EFD C6A3 # HANGUL SYLLABLE IEUNG-YO-RIEULHIEUH 9EFE C6A6 # HANGUL SYLLABLE IEUNG-YO-PIEUPSIOS 9F41 C6A8 # HANGUL SYLLABLE IEUNG-YO-SSANGSIOS 9F42 C6AA # HANGUL SYLLABLE IEUNG-YO-CIEUC 9F43 C6AB # HANGUL SYLLABLE IEUNG-YO-CHIEUCH 9F44 C6AC # HANGUL SYLLABLE IEUNG-YO-KHIEUKH 9F45 C6AD # HANGUL SYLLABLE IEUNG-YO-THIEUTH 9F46 C6AE # HANGUL SYLLABLE IEUNG-YO-PHIEUPH 9F47 C6AF # HANGUL SYLLABLE IEUNG-YO-HIEUH 9F48 C6B2 # HANGUL SYLLABLE IEUNG-U-SSANGKIYEOK 9F49 C6B3 # HANGUL SYLLABLE IEUNG-U-KIYEOKSIOS 9F4A C6B5 # HANGUL SYLLABLE IEUNG-U-NIEUNCIEUC 9F4B C6B6 # HANGUL SYLLABLE IEUNG-U-NIEUNHIEUH 9F4C C6B7 # HANGUL SYLLABLE IEUNG-U-TIKEUT 9F4D C6BB # HANGUL SYLLABLE IEUNG-U-RIEULPIEUP 9F4E C6BC # HANGUL SYLLABLE IEUNG-U-RIEULSIOS 9F4F C6BD # HANGUL SYLLABLE IEUNG-U-RIEULTHIEUTH 9F50 C6BE # HANGUL SYLLABLE IEUNG-U-RIEULPHIEUPH 9F51 C6BF # HANGUL SYLLABLE IEUNG-U-RIEULHIEUH 9F52 C6C2 # HANGUL SYLLABLE IEUNG-U-PIEUPSIOS 9F53 C6C4 # HANGUL SYLLABLE IEUNG-U-SSANGSIOS 9F54 C6C6 # HANGUL SYLLABLE IEUNG-U-CIEUC 9F55 C6C7 # HANGUL SYLLABLE IEUNG-U-CHIEUCH 9F56 C6C8 # HANGUL SYLLABLE IEUNG-U-KHIEUKH 9F57 C6C9 # HANGUL SYLLABLE IEUNG-U-THIEUTH 9F58 C6CA # HANGUL SYLLABLE IEUNG-U-PHIEUPH 9F59 C6CB # HANGUL SYLLABLE IEUNG-U-HIEUH 9F5A C6CE # HANGUL SYLLABLE IEUNG-WEO-SSANGKIYEOK 9F61 C6CF # HANGUL SYLLABLE IEUNG-WEO-KIYEOKSIOS 9F62 C6D1 # HANGUL SYLLABLE IEUNG-WEO-NIEUNCIEUC 9F63 C6D2 # HANGUL SYLLABLE IEUNG-WEO-NIEUNHIEUH 9F64 C6D3 # HANGUL SYLLABLE IEUNG-WEO-TIKEUT 9F65 C6D5 # HANGUL SYLLABLE IEUNG-WEO-RIEULKIYEOK 9F66 C6D6 # HANGUL SYLLABLE IEUNG-WEO-RIEULMIEUM 9F67 C6D7 # HANGUL SYLLABLE IEUNG-WEO-RIEULPIEUP 9F68 C6D8 # HANGUL SYLLABLE IEUNG-WEO-RIEULSIOS 9F69 C6D9 # HANGUL SYLLABLE IEUNG-WEO-RIEULTHIEUTH 9F6A C6DA # HANGUL SYLLABLE IEUNG-WEO-RIEULPHIEUPH 9F6B C6DB # HANGUL SYLLABLE IEUNG-WEO-RIEULHIEUH 9F6C C6DE # HANGUL SYLLABLE IEUNG-WEO-PIEUPSIOS 9F6D C6DF # HANGUL SYLLABLE IEUNG-WEO-SIOS 9F6E C6E2 # HANGUL SYLLABLE IEUNG-WEO-CIEUC 9F6F C6E3 # HANGUL SYLLABLE IEUNG-WEO-CHIEUCH 9F70 C6E4 # HANGUL SYLLABLE IEUNG-WEO-KHIEUKH 9F71 C6E5 # HANGUL SYLLABLE IEUNG-WEO-THIEUTH 9F72 C6E6 # HANGUL SYLLABLE IEUNG-WEO-PHIEUPH 9F73 C6E7 # HANGUL SYLLABLE IEUNG-WEO-HIEUH 9F74 C6EA # HANGUL SYLLABLE IEUNG-WE-SSANGKIYEOK 9F75 C6EB # HANGUL SYLLABLE IEUNG-WE-KIYEOKSIOS 9F76 C6ED # HANGUL SYLLABLE IEUNG-WE-NIEUNCIEUC 9F77 C6EE # HANGUL SYLLABLE IEUNG-WE-NIEUNHIEUH 9F78 C6EF # HANGUL SYLLABLE IEUNG-WE-TIKEUT 9F79 C6F1 # HANGUL SYLLABLE IEUNG-WE-RIEULKIYEOK 9F7A C6F2 # HANGUL SYLLABLE IEUNG-WE-RIEULMIEUM 9F81 C6F3 # HANGUL SYLLABLE IEUNG-WE-RIEULPIEUP 9F82 C6F4 # HANGUL SYLLABLE IEUNG-WE-RIEULSIOS 9F83 C6F5 # HANGUL SYLLABLE IEUNG-WE-RIEULTHIEUTH 9F84 C6F6 # HANGUL SYLLABLE IEUNG-WE-RIEULPHIEUPH 9F85 C6F7 # HANGUL SYLLABLE IEUNG-WE-RIEULHIEUH 9F86 C6FA # HANGUL SYLLABLE IEUNG-WE-PIEUPSIOS 9F87 C6FB # HANGUL SYLLABLE IEUNG-WE-SIOS 9F88 C6FC # HANGUL SYLLABLE IEUNG-WE-SSANGSIOS 9F89 C6FE # HANGUL SYLLABLE IEUNG-WE-CIEUC 9F8A C6FF # HANGUL SYLLABLE IEUNG-WE-CHIEUCH 9F8B C700 # HANGUL SYLLABLE IEUNG-WE-KHIEUKH 9F8C C701 # HANGUL SYLLABLE IEUNG-WE-THIEUTH 9F8D C702 # HANGUL SYLLABLE IEUNG-WE-PHIEUPH 9F8E C703 # HANGUL SYLLABLE IEUNG-WE-HIEUH 9F8F C706 # HANGUL SYLLABLE IEUNG-WI-SSANGKIYEOK 9F90 C707 # HANGUL SYLLABLE IEUNG-WI-KIYEOKSIOS 9F91 C709 # HANGUL SYLLABLE IEUNG-WI-NIEUNCIEUC 9F92 C70A # HANGUL SYLLABLE IEUNG-WI-NIEUNHIEUH 9F93 C70B # HANGUL SYLLABLE IEUNG-WI-TIKEUT 9F94 C70D # HANGUL SYLLABLE IEUNG-WI-RIEULKIYEOK 9F95 C70E # HANGUL SYLLABLE IEUNG-WI-RIEULMIEUM 9F96 C70F # HANGUL SYLLABLE IEUNG-WI-RIEULPIEUP 9F97 C710 # HANGUL SYLLABLE IEUNG-WI-RIEULSIOS 9F98 C711 # HANGUL SYLLABLE IEUNG-WI-RIEULTHIEUTH 9F99 C712 # HANGUL SYLLABLE IEUNG-WI-RIEULPHIEUPH 9F9A C713 # HANGUL SYLLABLE IEUNG-WI-RIEULHIEUH 9F9B C716 # HANGUL SYLLABLE IEUNG-WI-PIEUPSIOS 9F9C C718 # HANGUL SYLLABLE IEUNG-WI-SSANGSIOS 9F9D C71A # HANGUL SYLLABLE IEUNG-WI-CIEUC 9F9E C71B # HANGUL SYLLABLE IEUNG-WI-CHIEUCH 9F9F C71C # HANGUL SYLLABLE IEUNG-WI-KHIEUKH 9FA0 C71D # HANGUL SYLLABLE IEUNG-WI-THIEUTH 9FA1 C71E # HANGUL SYLLABLE IEUNG-WI-PHIEUPH 9FA2 C71F # HANGUL SYLLABLE IEUNG-WI-HIEUH 9FA3 C722 # HANGUL SYLLABLE IEUNG-YU-SSANGKIYEOK 9FA4 C723 # HANGUL SYLLABLE IEUNG-YU-KIYEOKSIOS 9FA5 C725 # HANGUL SYLLABLE IEUNG-YU-NIEUNCIEUC 9FA6 C726 # HANGUL SYLLABLE IEUNG-YU-NIEUNHIEUH 9FA7 C727 # HANGUL SYLLABLE IEUNG-YU-TIKEUT 9FA8 C729 # HANGUL SYLLABLE IEUNG-YU-RIEULKIYEOK 9FA9 C72A # HANGUL SYLLABLE IEUNG-YU-RIEULMIEUM 9FAA C72B # HANGUL SYLLABLE IEUNG-YU-RIEULPIEUP 9FAB C72C # HANGUL SYLLABLE IEUNG-YU-RIEULSIOS 9FAC C72D # HANGUL SYLLABLE IEUNG-YU-RIEULTHIEUTH 9FAD C72E # HANGUL SYLLABLE IEUNG-YU-RIEULPHIEUPH 9FAE C72F # HANGUL SYLLABLE IEUNG-YU-RIEULHIEUH 9FAF C732 # HANGUL SYLLABLE IEUNG-YU-PIEUPSIOS 9FB0 C734 # HANGUL SYLLABLE IEUNG-YU-SSANGSIOS 9FB1 C736 # HANGUL SYLLABLE IEUNG-YU-CIEUC 9FB2 C738 # HANGUL SYLLABLE IEUNG-YU-KHIEUKH 9FB3 C739 # HANGUL SYLLABLE IEUNG-YU-THIEUTH 9FB4 C73A # HANGUL SYLLABLE IEUNG-YU-PHIEUPH 9FB5 C73B # HANGUL SYLLABLE IEUNG-YU-HIEUH 9FB6 C73E # HANGUL SYLLABLE IEUNG-EU-SSANGKIYEOK 9FB7 C73F # HANGUL SYLLABLE IEUNG-EU-KIYEOKSIOS 9FB8 C741 # HANGUL SYLLABLE IEUNG-EU-NIEUNCIEUC 9FB9 C742 # HANGUL SYLLABLE IEUNG-EU-NIEUNHIEUH 9FBA C743 # HANGUL SYLLABLE IEUNG-EU-TIKEUT 9FBB C745 # HANGUL SYLLABLE IEUNG-EU-RIEULKIYEOK 9FBC C746 # HANGUL SYLLABLE IEUNG-EU-RIEULMIEUM 9FBD C747 # HANGUL SYLLABLE IEUNG-EU-RIEULPIEUP 9FBE C748 # HANGUL SYLLABLE IEUNG-EU-RIEULSIOS 9FBF C749 # HANGUL SYLLABLE IEUNG-EU-RIEULTHIEUTH 9FC0 C74B # HANGUL SYLLABLE IEUNG-EU-RIEULHIEUH 9FC1 C74E # HANGUL SYLLABLE IEUNG-EU-PIEUPSIOS 9FC2 C750 # HANGUL SYLLABLE IEUNG-EU-SSANGSIOS 9FC3 C759 # HANGUL SYLLABLE IEUNG-YI-KIYEOK 9FC4 C75A # HANGUL SYLLABLE IEUNG-YI-SSANGKIYEOK 9FC5 C75B # HANGUL SYLLABLE IEUNG-YI-KIYEOKSIOS 9FC6 C75D # HANGUL SYLLABLE IEUNG-YI-NIEUNCIEUC 9FC7 C75E # HANGUL SYLLABLE IEUNG-YI-NIEUNHIEUH 9FC8 C75F # HANGUL SYLLABLE IEUNG-YI-TIKEUT 9FC9 C761 # HANGUL SYLLABLE IEUNG-YI-RIEULKIYEOK 9FCA C762 # HANGUL SYLLABLE IEUNG-YI-RIEULMIEUM 9FCB C763 # HANGUL SYLLABLE IEUNG-YI-RIEULPIEUP 9FCC C764 # HANGUL SYLLABLE IEUNG-YI-RIEULSIOS 9FCD C765 # HANGUL SYLLABLE IEUNG-YI-RIEULTHIEUTH 9FCE C766 # HANGUL SYLLABLE IEUNG-YI-RIEULPHIEUPH 9FCF C767 # HANGUL SYLLABLE IEUNG-YI-RIEULHIEUH 9FD0 C769 # HANGUL SYLLABLE IEUNG-YI-PIEUP 9FD1 C76A # HANGUL SYLLABLE IEUNG-YI-PIEUPSIOS 9FD2 C76C # HANGUL SYLLABLE IEUNG-YI-SSANGSIOS 9FD3 C76D # HANGUL SYLLABLE IEUNG-YI-IEUNG 9FD4 C76E # HANGUL SYLLABLE IEUNG-YI-CIEUC 9FD5 C76F # HANGUL SYLLABLE IEUNG-YI-CHIEUCH 9FD6 C770 # HANGUL SYLLABLE IEUNG-YI-KHIEUKH 9FD7 C771 # HANGUL SYLLABLE IEUNG-YI-THIEUTH 9FD8 C772 # HANGUL SYLLABLE IEUNG-YI-PHIEUPH 9FD9 C773 # HANGUL SYLLABLE IEUNG-YI-HIEUH 9FDA C776 # HANGUL SYLLABLE IEUNG-I-SSANGKIYEOK 9FDB C777 # HANGUL SYLLABLE IEUNG-I-KIYEOKSIOS 9FDC C779 # HANGUL SYLLABLE IEUNG-I-NIEUNCIEUC 9FDD C77A # HANGUL SYLLABLE IEUNG-I-NIEUNHIEUH 9FDE C77B # HANGUL SYLLABLE IEUNG-I-TIKEUT 9FDF C77F # HANGUL SYLLABLE IEUNG-I-RIEULPIEUP 9FE0 C780 # HANGUL SYLLABLE IEUNG-I-RIEULSIOS 9FE1 C781 # HANGUL SYLLABLE IEUNG-I-RIEULTHIEUTH 9FE2 C782 # HANGUL SYLLABLE IEUNG-I-RIEULPHIEUPH 9FE3 C786 # HANGUL SYLLABLE IEUNG-I-PIEUPSIOS 9FE4 C78B # HANGUL SYLLABLE IEUNG-I-CHIEUCH 9FE5 C78C # HANGUL SYLLABLE IEUNG-I-KHIEUKH 9FE6 C78D # HANGUL SYLLABLE IEUNG-I-THIEUTH 9FE7 C78F # HANGUL SYLLABLE IEUNG-I-HIEUH 9FE8 C792 # HANGUL SYLLABLE CIEUC-A-SSANGKIYEOK 9FE9 C793 # HANGUL SYLLABLE CIEUC-A-KIYEOKSIOS 9FEA C795 # HANGUL SYLLABLE CIEUC-A-NIEUNCIEUC 9FEB C799 # HANGUL SYLLABLE CIEUC-A-RIEULKIYEOK 9FEC C79B # HANGUL SYLLABLE CIEUC-A-RIEULPIEUP 9FED C79C # HANGUL SYLLABLE CIEUC-A-RIEULSIOS 9FEE C79D # HANGUL SYLLABLE CIEUC-A-RIEULTHIEUTH 9FEF C79E # HANGUL SYLLABLE CIEUC-A-RIEULPHIEUPH 9FF0 C79F # HANGUL SYLLABLE CIEUC-A-RIEULHIEUH 9FF1 C7A2 # HANGUL SYLLABLE CIEUC-A-PIEUPSIOS 9FF2 C7A7 # HANGUL SYLLABLE CIEUC-A-CHIEUCH 9FF3 C7A8 # HANGUL SYLLABLE CIEUC-A-KHIEUKH 9FF4 C7A9 # HANGUL SYLLABLE CIEUC-A-THIEUTH 9FF5 C7AA # HANGUL SYLLABLE CIEUC-A-PHIEUPH 9FF6 C7AB # HANGUL SYLLABLE CIEUC-A-HIEUH 9FF7 C7AE # HANGUL SYLLABLE CIEUC-AE-SSANGKIYEOK 9FF8 C7AF # HANGUL SYLLABLE CIEUC-AE-KIYEOKSIOS 9FF9 C7B1 # HANGUL SYLLABLE CIEUC-AE-NIEUNCIEUC 9FFA C7B2 # HANGUL SYLLABLE CIEUC-AE-NIEUNHIEUH 9FFB C7B3 # HANGUL SYLLABLE CIEUC-AE-TIKEUT 9FFC C7B5 # HANGUL SYLLABLE CIEUC-AE-RIEULKIYEOK 9FFD C7B6 # HANGUL SYLLABLE CIEUC-AE-RIEULMIEUM 9FFE C7B7 # HANGUL SYLLABLE CIEUC-AE-RIEULPIEUP A041 C7B8 # HANGUL SYLLABLE CIEUC-AE-RIEULSIOS A042 C7B9 # HANGUL SYLLABLE CIEUC-AE-RIEULTHIEUTH A043 C7BA # HANGUL SYLLABLE CIEUC-AE-RIEULPHIEUPH A044 C7BB # HANGUL SYLLABLE CIEUC-AE-RIEULHIEUH A045 C7BE # HANGUL SYLLABLE CIEUC-AE-PIEUPSIOS A046 C7C2 # HANGUL SYLLABLE CIEUC-AE-CIEUC A047 C7C3 # HANGUL SYLLABLE CIEUC-AE-CHIEUCH A048 C7C4 # HANGUL SYLLABLE CIEUC-AE-KHIEUKH A049 C7C5 # HANGUL SYLLABLE CIEUC-AE-THIEUTH A04A C7C6 # HANGUL SYLLABLE CIEUC-AE-PHIEUPH A04B C7C7 # HANGUL SYLLABLE CIEUC-AE-HIEUH A04C C7CA # HANGUL SYLLABLE CIEUC-YA-SSANGKIYEOK A04D C7CB # HANGUL SYLLABLE CIEUC-YA-KIYEOKSIOS A04E C7CD # HANGUL SYLLABLE CIEUC-YA-NIEUNCIEUC A04F C7CF # HANGUL SYLLABLE CIEUC-YA-TIKEUT A050 C7D1 # HANGUL SYLLABLE CIEUC-YA-RIEULKIYEOK A051 C7D2 # HANGUL SYLLABLE CIEUC-YA-RIEULMIEUM A052 C7D3 # HANGUL SYLLABLE CIEUC-YA-RIEULPIEUP A053 C7D4 # HANGUL SYLLABLE CIEUC-YA-RIEULSIOS A054 C7D5 # HANGUL SYLLABLE CIEUC-YA-RIEULTHIEUTH A055 C7D6 # HANGUL SYLLABLE CIEUC-YA-RIEULPHIEUPH A056 C7D7 # HANGUL SYLLABLE CIEUC-YA-RIEULHIEUH A057 C7D9 # HANGUL SYLLABLE CIEUC-YA-PIEUP A058 C7DA # HANGUL SYLLABLE CIEUC-YA-PIEUPSIOS A059 C7DB # HANGUL SYLLABLE CIEUC-YA-SIOS A05A C7DC # HANGUL SYLLABLE CIEUC-YA-SSANGSIOS A061 C7DE # HANGUL SYLLABLE CIEUC-YA-CIEUC A062 C7DF # HANGUL SYLLABLE CIEUC-YA-CHIEUCH A063 C7E0 # HANGUL SYLLABLE CIEUC-YA-KHIEUKH A064 C7E1 # HANGUL SYLLABLE CIEUC-YA-THIEUTH A065 C7E2 # HANGUL SYLLABLE CIEUC-YA-PHIEUPH A066 C7E3 # HANGUL SYLLABLE CIEUC-YA-HIEUH A067 C7E5 # HANGUL SYLLABLE CIEUC-YAE-KIYEOK A068 C7E6 # HANGUL SYLLABLE CIEUC-YAE-SSANGKIYEOK A069 C7E7 # HANGUL SYLLABLE CIEUC-YAE-KIYEOKSIOS A06A C7E9 # HANGUL SYLLABLE CIEUC-YAE-NIEUNCIEUC A06B C7EA # HANGUL SYLLABLE CIEUC-YAE-NIEUNHIEUH A06C C7EB # HANGUL SYLLABLE CIEUC-YAE-TIKEUT A06D C7ED # HANGUL SYLLABLE CIEUC-YAE-RIEULKIYEOK A06E C7EE # HANGUL SYLLABLE CIEUC-YAE-RIEULMIEUM A06F C7EF # HANGUL SYLLABLE CIEUC-YAE-RIEULPIEUP A070 C7F0 # HANGUL SYLLABLE CIEUC-YAE-RIEULSIOS A071 C7F1 # HANGUL SYLLABLE CIEUC-YAE-RIEULTHIEUTH A072 C7F2 # HANGUL SYLLABLE CIEUC-YAE-RIEULPHIEUPH A073 C7F3 # HANGUL SYLLABLE CIEUC-YAE-RIEULHIEUH A074 C7F4 # HANGUL SYLLABLE CIEUC-YAE-MIEUM A075 C7F5 # HANGUL SYLLABLE CIEUC-YAE-PIEUP A076 C7F6 # HANGUL SYLLABLE CIEUC-YAE-PIEUPSIOS A077 C7F7 # HANGUL SYLLABLE CIEUC-YAE-SIOS A078 C7F8 # HANGUL SYLLABLE CIEUC-YAE-SSANGSIOS A079 C7F9 # HANGUL SYLLABLE CIEUC-YAE-IEUNG A07A C7FA # HANGUL SYLLABLE CIEUC-YAE-CIEUC A081 C7FB # HANGUL SYLLABLE CIEUC-YAE-CHIEUCH A082 C7FC # HANGUL SYLLABLE CIEUC-YAE-KHIEUKH A083 C7FD # HANGUL SYLLABLE CIEUC-YAE-THIEUTH A084 C7FE # HANGUL SYLLABLE CIEUC-YAE-PHIEUPH A085 C7FF # HANGUL SYLLABLE CIEUC-YAE-HIEUH A086 C802 # HANGUL SYLLABLE CIEUC-EO-SSANGKIYEOK A087 C803 # HANGUL SYLLABLE CIEUC-EO-KIYEOKSIOS A088 C805 # HANGUL SYLLABLE CIEUC-EO-NIEUNCIEUC A089 C806 # HANGUL SYLLABLE CIEUC-EO-NIEUNHIEUH A08A C807 # HANGUL SYLLABLE CIEUC-EO-TIKEUT A08B C809 # HANGUL SYLLABLE CIEUC-EO-RIEULKIYEOK A08C C80B # HANGUL SYLLABLE CIEUC-EO-RIEULPIEUP A08D C80C # HANGUL SYLLABLE CIEUC-EO-RIEULSIOS A08E C80D # HANGUL SYLLABLE CIEUC-EO-RIEULTHIEUTH A08F C80E # HANGUL SYLLABLE CIEUC-EO-RIEULPHIEUPH A090 C80F # HANGUL SYLLABLE CIEUC-EO-RIEULHIEUH A091 C812 # HANGUL SYLLABLE CIEUC-EO-PIEUPSIOS A092 C814 # HANGUL SYLLABLE CIEUC-EO-SSANGSIOS A093 C817 # HANGUL SYLLABLE CIEUC-EO-CHIEUCH A094 C818 # HANGUL SYLLABLE CIEUC-EO-KHIEUKH A095 C819 # HANGUL SYLLABLE CIEUC-EO-THIEUTH A096 C81A # HANGUL SYLLABLE CIEUC-EO-PHIEUPH A097 C81B # HANGUL SYLLABLE CIEUC-EO-HIEUH A098 C81E # HANGUL SYLLABLE CIEUC-E-SSANGKIYEOK A099 C81F # HANGUL SYLLABLE CIEUC-E-KIYEOKSIOS A09A C821 # HANGUL SYLLABLE CIEUC-E-NIEUNCIEUC A09B C822 # HANGUL SYLLABLE CIEUC-E-NIEUNHIEUH A09C C823 # HANGUL SYLLABLE CIEUC-E-TIKEUT A09D C825 # HANGUL SYLLABLE CIEUC-E-RIEULKIYEOK A09E C826 # HANGUL SYLLABLE CIEUC-E-RIEULMIEUM A09F C827 # HANGUL SYLLABLE CIEUC-E-RIEULPIEUP A0A0 C828 # HANGUL SYLLABLE CIEUC-E-RIEULSIOS A0A1 C829 # HANGUL SYLLABLE CIEUC-E-RIEULTHIEUTH A0A2 C82A # HANGUL SYLLABLE CIEUC-E-RIEULPHIEUPH A0A3 C82B # HANGUL SYLLABLE CIEUC-E-RIEULHIEUH A0A4 C82E # HANGUL SYLLABLE CIEUC-E-PIEUPSIOS A0A5 C830 # HANGUL SYLLABLE CIEUC-E-SSANGSIOS A0A6 C832 # HANGUL SYLLABLE CIEUC-E-CIEUC A0A7 C833 # HANGUL SYLLABLE CIEUC-E-CHIEUCH A0A8 C834 # HANGUL SYLLABLE CIEUC-E-KHIEUKH A0A9 C835 # HANGUL SYLLABLE CIEUC-E-THIEUTH A0AA C836 # HANGUL SYLLABLE CIEUC-E-PHIEUPH A0AB C837 # HANGUL SYLLABLE CIEUC-E-HIEUH A0AC C839 # HANGUL SYLLABLE CIEUC-YEO-KIYEOK A0AD C83A # HANGUL SYLLABLE CIEUC-YEO-SSANGKIYEOK A0AE C83B # HANGUL SYLLABLE CIEUC-YEO-KIYEOKSIOS A0AF C83D # HANGUL SYLLABLE CIEUC-YEO-NIEUNCIEUC A0B0 C83E # HANGUL SYLLABLE CIEUC-YEO-NIEUNHIEUH A0B1 C83F # HANGUL SYLLABLE CIEUC-YEO-TIKEUT A0B2 C841 # HANGUL SYLLABLE CIEUC-YEO-RIEULKIYEOK A0B3 C842 # HANGUL SYLLABLE CIEUC-YEO-RIEULMIEUM A0B4 C843 # HANGUL SYLLABLE CIEUC-YEO-RIEULPIEUP A0B5 C844 # HANGUL SYLLABLE CIEUC-YEO-RIEULSIOS A0B6 C845 # HANGUL SYLLABLE CIEUC-YEO-RIEULTHIEUTH A0B7 C846 # HANGUL SYLLABLE CIEUC-YEO-RIEULPHIEUPH A0B8 C847 # HANGUL SYLLABLE CIEUC-YEO-RIEULHIEUH A0B9 C84A # HANGUL SYLLABLE CIEUC-YEO-PIEUPSIOS A0BA C84B # HANGUL SYLLABLE CIEUC-YEO-SIOS A0BB C84E # HANGUL SYLLABLE CIEUC-YEO-CIEUC A0BC C84F # HANGUL SYLLABLE CIEUC-YEO-CHIEUCH A0BD C850 # HANGUL SYLLABLE CIEUC-YEO-KHIEUKH A0BE C851 # HANGUL SYLLABLE CIEUC-YEO-THIEUTH A0BF C852 # HANGUL SYLLABLE CIEUC-YEO-PHIEUPH A0C0 C853 # HANGUL SYLLABLE CIEUC-YEO-HIEUH A0C1 C855 # HANGUL SYLLABLE CIEUC-YE-KIYEOK A0C2 C856 # HANGUL SYLLABLE CIEUC-YE-SSANGKIYEOK A0C3 C857 # HANGUL SYLLABLE CIEUC-YE-KIYEOKSIOS A0C4 C858 # HANGUL SYLLABLE CIEUC-YE-NIEUN A0C5 C859 # HANGUL SYLLABLE CIEUC-YE-NIEUNCIEUC A0C6 C85A # HANGUL SYLLABLE CIEUC-YE-NIEUNHIEUH A0C7 C85B # HANGUL SYLLABLE CIEUC-YE-TIKEUT A0C8 C85C # HANGUL SYLLABLE CIEUC-YE-RIEUL A0C9 C85D # HANGUL SYLLABLE CIEUC-YE-RIEULKIYEOK A0CA C85E # HANGUL SYLLABLE CIEUC-YE-RIEULMIEUM A0CB C85F # HANGUL SYLLABLE CIEUC-YE-RIEULPIEUP A0CC C860 # HANGUL SYLLABLE CIEUC-YE-RIEULSIOS A0CD C861 # HANGUL SYLLABLE CIEUC-YE-RIEULTHIEUTH A0CE C862 # HANGUL SYLLABLE CIEUC-YE-RIEULPHIEUPH A0CF C863 # HANGUL SYLLABLE CIEUC-YE-RIEULHIEUH A0D0 C864 # HANGUL SYLLABLE CIEUC-YE-MIEUM A0D1 C865 # HANGUL SYLLABLE CIEUC-YE-PIEUP A0D2 C866 # HANGUL SYLLABLE CIEUC-YE-PIEUPSIOS A0D3 C867 # HANGUL SYLLABLE CIEUC-YE-SIOS A0D4 C868 # HANGUL SYLLABLE CIEUC-YE-SSANGSIOS A0D5 C869 # HANGUL SYLLABLE CIEUC-YE-IEUNG A0D6 C86A # HANGUL SYLLABLE CIEUC-YE-CIEUC A0D7 C86B # HANGUL SYLLABLE CIEUC-YE-CHIEUCH A0D8 C86C # HANGUL SYLLABLE CIEUC-YE-KHIEUKH A0D9 C86D # HANGUL SYLLABLE CIEUC-YE-THIEUTH A0DA C86E # HANGUL SYLLABLE CIEUC-YE-PHIEUPH A0DB C86F # HANGUL SYLLABLE CIEUC-YE-HIEUH A0DC C872 # HANGUL SYLLABLE CIEUC-O-SSANGKIYEOK A0DD C873 # HANGUL SYLLABLE CIEUC-O-KIYEOKSIOS A0DE C875 # HANGUL SYLLABLE CIEUC-O-NIEUNCIEUC A0DF C876 # HANGUL SYLLABLE CIEUC-O-NIEUNHIEUH A0E0 C877 # HANGUL SYLLABLE CIEUC-O-TIKEUT A0E1 C879 # HANGUL SYLLABLE CIEUC-O-RIEULKIYEOK A0E2 C87B # HANGUL SYLLABLE CIEUC-O-RIEULPIEUP A0E3 C87C # HANGUL SYLLABLE CIEUC-O-RIEULSIOS A0E4 C87D # HANGUL SYLLABLE CIEUC-O-RIEULTHIEUTH A0E5 C87E # HANGUL SYLLABLE CIEUC-O-RIEULPHIEUPH A0E6 C87F # HANGUL SYLLABLE CIEUC-O-RIEULHIEUH A0E7 C882 # HANGUL SYLLABLE CIEUC-O-PIEUPSIOS A0E8 C884 # HANGUL SYLLABLE CIEUC-O-SSANGSIOS A0E9 C888 # HANGUL SYLLABLE CIEUC-O-KHIEUKH A0EA C889 # HANGUL SYLLABLE CIEUC-O-THIEUTH A0EB C88A # HANGUL SYLLABLE CIEUC-O-PHIEUPH A0EC C88E # HANGUL SYLLABLE CIEUC-WA-SSANGKIYEOK A0ED C88F # HANGUL SYLLABLE CIEUC-WA-KIYEOKSIOS A0EE C890 # HANGUL SYLLABLE CIEUC-WA-NIEUN A0EF C891 # HANGUL SYLLABLE CIEUC-WA-NIEUNCIEUC A0F0 C892 # HANGUL SYLLABLE CIEUC-WA-NIEUNHIEUH A0F1 C893 # HANGUL SYLLABLE CIEUC-WA-TIKEUT A0F2 C895 # HANGUL SYLLABLE CIEUC-WA-RIEULKIYEOK A0F3 C896 # HANGUL SYLLABLE CIEUC-WA-RIEULMIEUM A0F4 C897 # HANGUL SYLLABLE CIEUC-WA-RIEULPIEUP A0F5 C898 # HANGUL SYLLABLE CIEUC-WA-RIEULSIOS A0F6 C899 # HANGUL SYLLABLE CIEUC-WA-RIEULTHIEUTH A0F7 C89A # HANGUL SYLLABLE CIEUC-WA-RIEULPHIEUPH A0F8 C89B # HANGUL SYLLABLE CIEUC-WA-RIEULHIEUH A0F9 C89C # HANGUL SYLLABLE CIEUC-WA-MIEUM A0FA C89E # HANGUL SYLLABLE CIEUC-WA-PIEUPSIOS A0FB C8A0 # HANGUL SYLLABLE CIEUC-WA-SSANGSIOS A0FC C8A2 # HANGUL SYLLABLE CIEUC-WA-CIEUC A0FD C8A3 # HANGUL SYLLABLE CIEUC-WA-CHIEUCH A0FE C8A4 # HANGUL SYLLABLE CIEUC-WA-KHIEUKH A141 C8A5 # HANGUL SYLLABLE CIEUC-WA-THIEUTH A142 C8A6 # HANGUL SYLLABLE CIEUC-WA-PHIEUPH A143 C8A7 # HANGUL SYLLABLE CIEUC-WA-HIEUH A144 C8A9 # HANGUL SYLLABLE CIEUC-WAE-KIYEOK A145 C8AA # HANGUL SYLLABLE CIEUC-WAE-SSANGKIYEOK A146 C8AB # HANGUL SYLLABLE CIEUC-WAE-KIYEOKSIOS A147 C8AC # HANGUL SYLLABLE CIEUC-WAE-NIEUN A148 C8AD # HANGUL SYLLABLE CIEUC-WAE-NIEUNCIEUC A149 C8AE # HANGUL SYLLABLE CIEUC-WAE-NIEUNHIEUH A14A C8AF # HANGUL SYLLABLE CIEUC-WAE-TIKEUT A14B C8B0 # HANGUL SYLLABLE CIEUC-WAE-RIEUL A14C C8B1 # HANGUL SYLLABLE CIEUC-WAE-RIEULKIYEOK A14D C8B2 # HANGUL SYLLABLE CIEUC-WAE-RIEULMIEUM A14E C8B3 # HANGUL SYLLABLE CIEUC-WAE-RIEULPIEUP A14F C8B4 # HANGUL SYLLABLE CIEUC-WAE-RIEULSIOS A150 C8B5 # HANGUL SYLLABLE CIEUC-WAE-RIEULTHIEUTH A151 C8B6 # HANGUL SYLLABLE CIEUC-WAE-RIEULPHIEUPH A152 C8B7 # HANGUL SYLLABLE CIEUC-WAE-RIEULHIEUH A153 C8B8 # HANGUL SYLLABLE CIEUC-WAE-MIEUM A154 C8B9 # HANGUL SYLLABLE CIEUC-WAE-PIEUP A155 C8BA # HANGUL SYLLABLE CIEUC-WAE-PIEUPSIOS A156 C8BB # HANGUL SYLLABLE CIEUC-WAE-SIOS A157 C8BE # HANGUL SYLLABLE CIEUC-WAE-CIEUC A158 C8BF # HANGUL SYLLABLE CIEUC-WAE-CHIEUCH A159 C8C0 # HANGUL SYLLABLE CIEUC-WAE-KHIEUKH A15A C8C1 # HANGUL SYLLABLE CIEUC-WAE-THIEUTH A161 C8C2 # HANGUL SYLLABLE CIEUC-WAE-PHIEUPH A162 C8C3 # HANGUL SYLLABLE CIEUC-WAE-HIEUH A163 C8C5 # HANGUL SYLLABLE CIEUC-OE-KIYEOK A164 C8C6 # HANGUL SYLLABLE CIEUC-OE-SSANGKIYEOK A165 C8C7 # HANGUL SYLLABLE CIEUC-OE-KIYEOKSIOS A166 C8C9 # HANGUL SYLLABLE CIEUC-OE-NIEUNCIEUC A167 C8CA # HANGUL SYLLABLE CIEUC-OE-NIEUNHIEUH A168 C8CB # HANGUL SYLLABLE CIEUC-OE-TIKEUT A169 C8CD # HANGUL SYLLABLE CIEUC-OE-RIEULKIYEOK A16A C8CE # HANGUL SYLLABLE CIEUC-OE-RIEULMIEUM A16B C8CF # HANGUL SYLLABLE CIEUC-OE-RIEULPIEUP A16C C8D0 # HANGUL SYLLABLE CIEUC-OE-RIEULSIOS A16D C8D1 # HANGUL SYLLABLE CIEUC-OE-RIEULTHIEUTH A16E C8D2 # HANGUL SYLLABLE CIEUC-OE-RIEULPHIEUPH A16F C8D3 # HANGUL SYLLABLE CIEUC-OE-RIEULHIEUH A170 C8D6 # HANGUL SYLLABLE CIEUC-OE-PIEUPSIOS A171 C8D8 # HANGUL SYLLABLE CIEUC-OE-SSANGSIOS A172 C8DA # HANGUL SYLLABLE CIEUC-OE-CIEUC A173 C8DB # HANGUL SYLLABLE CIEUC-OE-CHIEUCH A174 C8DC # HANGUL SYLLABLE CIEUC-OE-KHIEUKH A175 C8DD # HANGUL SYLLABLE CIEUC-OE-THIEUTH A176 C8DE # HANGUL SYLLABLE CIEUC-OE-PHIEUPH A177 C8DF # HANGUL SYLLABLE CIEUC-OE-HIEUH A178 C8E2 # HANGUL SYLLABLE CIEUC-YO-SSANGKIYEOK A179 C8E3 # HANGUL SYLLABLE CIEUC-YO-KIYEOKSIOS A17A C8E5 # HANGUL SYLLABLE CIEUC-YO-NIEUNCIEUC A181 C8E6 # HANGUL SYLLABLE CIEUC-YO-NIEUNHIEUH A182 C8E7 # HANGUL SYLLABLE CIEUC-YO-TIKEUT A183 C8E8 # HANGUL SYLLABLE CIEUC-YO-RIEUL A184 C8E9 # HANGUL SYLLABLE CIEUC-YO-RIEULKIYEOK A185 C8EA # HANGUL SYLLABLE CIEUC-YO-RIEULMIEUM A186 C8EB # HANGUL SYLLABLE CIEUC-YO-RIEULPIEUP A187 C8EC # HANGUL SYLLABLE CIEUC-YO-RIEULSIOS A188 C8ED # HANGUL SYLLABLE CIEUC-YO-RIEULTHIEUTH A189 C8EE # HANGUL SYLLABLE CIEUC-YO-RIEULPHIEUPH A18A C8EF # HANGUL SYLLABLE CIEUC-YO-RIEULHIEUH A18B C8F0 # HANGUL SYLLABLE CIEUC-YO-MIEUM A18C C8F1 # HANGUL SYLLABLE CIEUC-YO-PIEUP A18D C8F2 # HANGUL SYLLABLE CIEUC-YO-PIEUPSIOS A18E C8F3 # HANGUL SYLLABLE CIEUC-YO-SIOS A18F C8F4 # HANGUL SYLLABLE CIEUC-YO-SSANGSIOS A190 C8F6 # HANGUL SYLLABLE CIEUC-YO-CIEUC A191 C8F7 # HANGUL SYLLABLE CIEUC-YO-CHIEUCH A192 C8F8 # HANGUL SYLLABLE CIEUC-YO-KHIEUKH A193 C8F9 # HANGUL SYLLABLE CIEUC-YO-THIEUTH A194 C8FA # HANGUL SYLLABLE CIEUC-YO-PHIEUPH A195 C8FB # HANGUL SYLLABLE CIEUC-YO-HIEUH A196 C8FE # HANGUL SYLLABLE CIEUC-U-SSANGKIYEOK A197 C8FF # HANGUL SYLLABLE CIEUC-U-KIYEOKSIOS A198 C901 # HANGUL SYLLABLE CIEUC-U-NIEUNCIEUC A199 C902 # HANGUL SYLLABLE CIEUC-U-NIEUNHIEUH A19A C903 # HANGUL SYLLABLE CIEUC-U-TIKEUT A19B C907 # HANGUL SYLLABLE CIEUC-U-RIEULPIEUP A19C C908 # HANGUL SYLLABLE CIEUC-U-RIEULSIOS A19D C909 # HANGUL SYLLABLE CIEUC-U-RIEULTHIEUTH A19E C90A # HANGUL SYLLABLE CIEUC-U-RIEULPHIEUPH A19F C90B # HANGUL SYLLABLE CIEUC-U-RIEULHIEUH A1A0 C90E # HANGUL SYLLABLE CIEUC-U-PIEUPSIOS A1A1 3000 # IDEOGRAPHIC SPACE A1A2 3001 # IDEOGRAPHIC COMMA A1A3 3002 # IDEOGRAPHIC FULL STOP A1A4 00B7 # MIDDLE DOT A1A5 2025 # TWO DOT LEADER A1A6 2026 # HORIZONTAL ELLIPSIS A1A7 00A8 # DIAERESIS A1A8 3003 # DITTO MARK A1A9 00AD # SOFT HYPHEN A1AA 2015 # HORIZONTAL BAR A1AB 2225 # PARALLEL TO A1AC FF3C # FULLWIDTH REVERSE SOLIDUS A1AD 223C # TILDE OPERATOR A1AE 2018 # LEFT SINGLE QUOTATION MARK A1AF 2019 # RIGHT SINGLE QUOTATION MARK A1B0 201C # LEFT DOUBLE QUOTATION MARK A1B1 201D # RIGHT DOUBLE QUOTATION MARK A1B2 3014 # LEFT TORTOISE SHELL BRACKET A1B3 3015 # RIGHT TORTOISE SHELL BRACKET A1B4 3008 # LEFT ANGLE BRACKET A1B5 3009 # RIGHT ANGLE BRACKET A1B6 300A # LEFT DOUBLE ANGLE BRACKET A1B7 300B # RIGHT DOUBLE ANGLE BRACKET A1B8 300C # LEFT CORNER BRACKET A1B9 300D # RIGHT CORNER BRACKET A1BA 300E # LEFT WHITE CORNER BRACKET A1BB 300F # RIGHT WHITE CORNER BRACKET A1BC 3010 # LEFT BLACK LENTICULAR BRACKET A1BD 3011 # RIGHT BLACK LENTICULAR BRACKET A1BE 00B1 # PLUS-MINUS SIGN A1BF 00D7 # MULTIPLICATION SIGN A1C0 00F7 # DIVISION SIGN A1C1 2260 # NOT EQUAL TO A1C2 2264 # LESS-THAN OR EQUAL TO A1C3 2265 # GREATER-THAN OR EQUAL TO A1C4 221E # INFINITY A1C5 2234 # THEREFORE A1C6 00B0 # DEGREE SIGN A1C7 2032 # PRIME A1C8 2033 # DOUBLE PRIME A1C9 2103 # DEGREE CELSIUS A1CA 212B # ANGSTROM SIGN A1CB FFE0 # FULLWIDTH CENT SIGN A1CC FFE1 # FULLWIDTH POUND SIGN A1CD FFE5 # FULLWIDTH YEN SIGN A1CE 2642 # MALE SIGN A1CF 2640 # FEMALE SIGN A1D0 2220 # ANGLE A1D1 22A5 # UP TACK A1D2 2312 # ARC A1D3 2202 # PARTIAL DIFFERENTIAL A1D4 2207 # NABLA A1D5 2261 # IDENTICAL TO A1D6 2252 # APPROXIMATELY EQUAL TO OR THE IMAGE OF A1D7 00A7 # SECTION SIGN A1D8 203B # REFERENCE MARK A1D9 2606 # WHITE STAR A1DA 2605 # BLACK STAR A1DB 25CB # WHITE CIRCLE A1DC 25CF # BLACK CIRCLE A1DD 25CE # BULLSEYE A1DE 25C7 # WHITE DIAMOND A1DF 25C6 # BLACK DIAMOND A1E0 25A1 # WHITE SQUARE A1E1 25A0 # BLACK SQUARE A1E2 25B3 # WHITE UP-POINTING TRIANGLE A1E3 25B2 # BLACK UP-POINTING TRIANGLE A1E4 25BD # WHITE DOWN-POINTING TRIANGLE A1E5 25BC # BLACK DOWN-POINTING TRIANGLE A1E6 2192 # RIGHTWARDS ARROW A1E7 2190 # LEFTWARDS ARROW A1E8 2191 # UPWARDS ARROW A1E9 2193 # DOWNWARDS ARROW A1EA 2194 # LEFT RIGHT ARROW A1EB 3013 # GETA MARK A1EC 226A # MUCH LESS-THAN A1ED 226B # MUCH GREATER-THAN A1EE 221A # SQUARE ROOT A1EF 223D # REVERSED TILDE A1F0 221D # PROPORTIONAL TO A1F1 2235 # BECAUSE A1F2 222B # INTEGRAL A1F3 222C # DOUBLE INTEGRAL A1F4 2208 # ELEMENT OF A1F5 220B # CONTAINS AS MEMBER A1F6 2286 # SUBSET OF OR EQUAL TO A1F7 2287 # SUPERSET OF OR EQUAL TO A1F8 2282 # SUBSET OF A1F9 2283 # SUPERSET OF A1FA 222A # UNION A1FB 2229 # INTERSECTION A1FC 2227 # LOGICAL AND A1FD 2228 # LOGICAL OR A1FE FFE2 # FULLWIDTH NOT SIGN A241 C910 # HANGUL SYLLABLE CIEUC-U-SSANGSIOS A242 C912 # HANGUL SYLLABLE CIEUC-U-CIEUC A243 C913 # HANGUL SYLLABLE CIEUC-U-CHIEUCH A244 C914 # HANGUL SYLLABLE CIEUC-U-KHIEUKH A245 C915 # HANGUL SYLLABLE CIEUC-U-THIEUTH A246 C916 # HANGUL SYLLABLE CIEUC-U-PHIEUPH A247 C917 # HANGUL SYLLABLE CIEUC-U-HIEUH A248 C919 # HANGUL SYLLABLE CIEUC-WEO-KIYEOK A249 C91A # HANGUL SYLLABLE CIEUC-WEO-SSANGKIYEOK A24A C91B # HANGUL SYLLABLE CIEUC-WEO-KIYEOKSIOS A24B C91C # HANGUL SYLLABLE CIEUC-WEO-NIEUN A24C C91D # HANGUL SYLLABLE CIEUC-WEO-NIEUNCIEUC A24D C91E # HANGUL SYLLABLE CIEUC-WEO-NIEUNHIEUH A24E C91F # HANGUL SYLLABLE CIEUC-WEO-TIKEUT A24F C920 # HANGUL SYLLABLE CIEUC-WEO-RIEUL A250 C921 # HANGUL SYLLABLE CIEUC-WEO-RIEULKIYEOK A251 C922 # HANGUL SYLLABLE CIEUC-WEO-RIEULMIEUM A252 C923 # HANGUL SYLLABLE CIEUC-WEO-RIEULPIEUP A253 C924 # HANGUL SYLLABLE CIEUC-WEO-RIEULSIOS A254 C925 # HANGUL SYLLABLE CIEUC-WEO-RIEULTHIEUTH A255 C926 # HANGUL SYLLABLE CIEUC-WEO-RIEULPHIEUPH A256 C927 # HANGUL SYLLABLE CIEUC-WEO-RIEULHIEUH A257 C928 # HANGUL SYLLABLE CIEUC-WEO-MIEUM A258 C929 # HANGUL SYLLABLE CIEUC-WEO-PIEUP A259 C92A # HANGUL SYLLABLE CIEUC-WEO-PIEUPSIOS A25A C92B # HANGUL SYLLABLE CIEUC-WEO-SIOS A261 C92D # HANGUL SYLLABLE CIEUC-WEO-IEUNG A262 C92E # HANGUL SYLLABLE CIEUC-WEO-CIEUC A263 C92F # HANGUL SYLLABLE CIEUC-WEO-CHIEUCH A264 C930 # HANGUL SYLLABLE CIEUC-WEO-KHIEUKH A265 C931 # HANGUL SYLLABLE CIEUC-WEO-THIEUTH A266 C932 # HANGUL SYLLABLE CIEUC-WEO-PHIEUPH A267 C933 # HANGUL SYLLABLE CIEUC-WEO-HIEUH A268 C935 # HANGUL SYLLABLE CIEUC-WE-KIYEOK A269 C936 # HANGUL SYLLABLE CIEUC-WE-SSANGKIYEOK A26A C937 # HANGUL SYLLABLE CIEUC-WE-KIYEOKSIOS A26B C938 # HANGUL SYLLABLE CIEUC-WE-NIEUN A26C C939 # HANGUL SYLLABLE CIEUC-WE-NIEUNCIEUC A26D C93A # HANGUL SYLLABLE CIEUC-WE-NIEUNHIEUH A26E C93B # HANGUL SYLLABLE CIEUC-WE-TIKEUT A26F C93C # HANGUL SYLLABLE CIEUC-WE-RIEUL A270 C93D # HANGUL SYLLABLE CIEUC-WE-RIEULKIYEOK A271 C93E # HANGUL SYLLABLE CIEUC-WE-RIEULMIEUM A272 C93F # HANGUL SYLLABLE CIEUC-WE-RIEULPIEUP A273 C940 # HANGUL SYLLABLE CIEUC-WE-RIEULSIOS A274 C941 # HANGUL SYLLABLE CIEUC-WE-RIEULTHIEUTH A275 C942 # HANGUL SYLLABLE CIEUC-WE-RIEULPHIEUPH A276 C943 # HANGUL SYLLABLE CIEUC-WE-RIEULHIEUH A277 C944 # HANGUL SYLLABLE CIEUC-WE-MIEUM A278 C945 # HANGUL SYLLABLE CIEUC-WE-PIEUP A279 C946 # HANGUL SYLLABLE CIEUC-WE-PIEUPSIOS A27A C947 # HANGUL SYLLABLE CIEUC-WE-SIOS A281 C948 # HANGUL SYLLABLE CIEUC-WE-SSANGSIOS A282 C949 # HANGUL SYLLABLE CIEUC-WE-IEUNG A283 C94A # HANGUL SYLLABLE CIEUC-WE-CIEUC A284 C94B # HANGUL SYLLABLE CIEUC-WE-CHIEUCH A285 C94C # HANGUL SYLLABLE CIEUC-WE-KHIEUKH A286 C94D # HANGUL SYLLABLE CIEUC-WE-THIEUTH A287 C94E # HANGUL SYLLABLE CIEUC-WE-PHIEUPH A288 C94F # HANGUL SYLLABLE CIEUC-WE-HIEUH A289 C952 # HANGUL SYLLABLE CIEUC-WI-SSANGKIYEOK A28A C953 # HANGUL SYLLABLE CIEUC-WI-KIYEOKSIOS A28B C955 # HANGUL SYLLABLE CIEUC-WI-NIEUNCIEUC A28C C956 # HANGUL SYLLABLE CIEUC-WI-NIEUNHIEUH A28D C957 # HANGUL SYLLABLE CIEUC-WI-TIKEUT A28E C959 # HANGUL SYLLABLE CIEUC-WI-RIEULKIYEOK A28F C95A # HANGUL SYLLABLE CIEUC-WI-RIEULMIEUM A290 C95B # HANGUL SYLLABLE CIEUC-WI-RIEULPIEUP A291 C95C # HANGUL SYLLABLE CIEUC-WI-RIEULSIOS A292 C95D # HANGUL SYLLABLE CIEUC-WI-RIEULTHIEUTH A293 C95E # HANGUL SYLLABLE CIEUC-WI-RIEULPHIEUPH A294 C95F # HANGUL SYLLABLE CIEUC-WI-RIEULHIEUH A295 C962 # HANGUL SYLLABLE CIEUC-WI-PIEUPSIOS A296 C964 # HANGUL SYLLABLE CIEUC-WI-SSANGSIOS A297 C965 # HANGUL SYLLABLE CIEUC-WI-IEUNG A298 C966 # HANGUL SYLLABLE CIEUC-WI-CIEUC A299 C967 # HANGUL SYLLABLE CIEUC-WI-CHIEUCH A29A C968 # HANGUL SYLLABLE CIEUC-WI-KHIEUKH A29B C969 # HANGUL SYLLABLE CIEUC-WI-THIEUTH A29C C96A # HANGUL SYLLABLE CIEUC-WI-PHIEUPH A29D C96B # HANGUL SYLLABLE CIEUC-WI-HIEUH A29E C96D # HANGUL SYLLABLE CIEUC-YU-KIYEOK A29F C96E # HANGUL SYLLABLE CIEUC-YU-SSANGKIYEOK A2A0 C96F # HANGUL SYLLABLE CIEUC-YU-KIYEOKSIOS A2A1 21D2 # RIGHTWARDS DOUBLE ARROW A2A2 21D4 # LEFT RIGHT DOUBLE ARROW A2A3 2200 # FOR ALL A2A4 2203 # THERE EXISTS A2A5 00B4 # ACUTE ACCENT A2A6 FF5E # FULLWIDTH TILDE A2A7 02C7 # CARON A2A8 02D8 # BREVE A2A9 02DD # DOUBLE ACUTE ACCENT A2AA 02DA # RING ABOVE A2AB 02D9 # DOT ABOVE A2AC 00B8 # CEDILLA A2AD 02DB # OGONEK A2AE 00A1 # INVERTED EXCLAMATION MARK A2AF 00BF # INVERTED QUESTION MARK A2B0 02D0 # MODIFIER LETTER TRIANGULAR COLON A2B1 222E # CONTOUR INTEGRAL A2B2 2211 # N-ARY SUMMATION A2B3 220F # N-ARY PRODUCT A2B4 00A4 # CURRENCY SIGN A2B5 2109 # DEGREE FAHRENHEIT A2B6 2030 # PER MILLE SIGN A2B7 25C1 # WHITE LEFT-POINTING TRIANGLE A2B8 25C0 # BLACK LEFT-POINTING TRIANGLE A2B9 25B7 # WHITE RIGHT-POINTING TRIANGLE A2BA 25B6 # BLACK RIGHT-POINTING TRIANGLE A2BB 2664 # WHITE SPADE SUIT A2BC 2660 # BLACK SPADE SUIT A2BD 2661 # WHITE HEART SUIT A2BE 2665 # BLACK HEART SUIT A2BF 2667 # WHITE CLUB SUIT A2C0 2663 # BLACK CLUB SUIT A2C1 2299 # CIRCLED DOT OPERATOR A2C2 25C8 # WHITE DIAMOND CONTAINING BLACK SMALL DIAMOND A2C3 25A3 # WHITE SQUARE CONTAINING BLACK SMALL SQUARE A2C4 25D0 # CIRCLE WITH LEFT HALF BLACK A2C5 25D1 # CIRCLE WITH RIGHT HALF BLACK A2C6 2592 # MEDIUM SHADE A2C7 25A4 # SQUARE WITH HORIZONTAL FILL A2C8 25A5 # SQUARE WITH VERTICAL FILL A2C9 25A8 # SQUARE WITH UPPER RIGHT TO LOWER LEFT FILL A2CA 25A7 # SQUARE WITH UPPER LEFT TO LOWER RIGHT FILL A2CB 25A6 # SQUARE WITH ORTHOGONAL CROSSHATCH FILL A2CC 25A9 # SQUARE WITH DIAGONAL CROSSHATCH FILL A2CD 2668 # HOT SPRINGS A2CE 260F # WHITE TELEPHONE A2CF 260E # BLACK TELEPHONE A2D0 261C # WHITE LEFT POINTING INDEX A2D1 261E # WHITE RIGHT POINTING INDEX A2D2 00B6 # PILCROW SIGN A2D3 2020 # DAGGER A2D4 2021 # DOUBLE DAGGER A2D5 2195 # UP DOWN ARROW A2D6 2197 # NORTH EAST ARROW A2D7 2199 # SOUTH WEST ARROW A2D8 2196 # NORTH WEST ARROW A2D9 2198 # SOUTH EAST ARROW A2DA 266D # MUSIC FLAT SIGN A2DB 2669 # QUARTER NOTE A2DC 266A # EIGHTH NOTE A2DD 266C # BEAMED SIXTEENTH NOTES A2DE 327F # KOREAN STANDARD SYMBOL A2DF 321C # PARENTHESIZED HANGUL CIEUC U A2E0 2116 # NUMERO SIGN A2E1 33C7 # SQUARE CO A2E2 2122 # TRADE MARK SIGN A2E3 33C2 # SQUARE AM A2E4 33D8 # SQUARE PM A2E5 2121 # TELEPHONE SIGN A341 C971 # HANGUL SYLLABLE CIEUC-YU-NIEUNCIEUC A342 C972 # HANGUL SYLLABLE CIEUC-YU-NIEUNHIEUH A343 C973 # HANGUL SYLLABLE CIEUC-YU-TIKEUT A344 C975 # HANGUL SYLLABLE CIEUC-YU-RIEULKIYEOK A345 C976 # HANGUL SYLLABLE CIEUC-YU-RIEULMIEUM A346 C977 # HANGUL SYLLABLE CIEUC-YU-RIEULPIEUP A347 C978 # HANGUL SYLLABLE CIEUC-YU-RIEULSIOS A348 C979 # HANGUL SYLLABLE CIEUC-YU-RIEULTHIEUTH A349 C97A # HANGUL SYLLABLE CIEUC-YU-RIEULPHIEUPH A34A C97B # HANGUL SYLLABLE CIEUC-YU-RIEULHIEUH A34B C97D # HANGUL SYLLABLE CIEUC-YU-PIEUP A34C C97E # HANGUL SYLLABLE CIEUC-YU-PIEUPSIOS A34D C97F # HANGUL SYLLABLE CIEUC-YU-SIOS A34E C980 # HANGUL SYLLABLE CIEUC-YU-SSANGSIOS A34F C981 # HANGUL SYLLABLE CIEUC-YU-IEUNG A350 C982 # HANGUL SYLLABLE CIEUC-YU-CIEUC A351 C983 # HANGUL SYLLABLE CIEUC-YU-CHIEUCH A352 C984 # HANGUL SYLLABLE CIEUC-YU-KHIEUKH A353 C985 # HANGUL SYLLABLE CIEUC-YU-THIEUTH A354 C986 # HANGUL SYLLABLE CIEUC-YU-PHIEUPH A355 C987 # HANGUL SYLLABLE CIEUC-YU-HIEUH A356 C98A # HANGUL SYLLABLE CIEUC-EU-SSANGKIYEOK A357 C98B # HANGUL SYLLABLE CIEUC-EU-KIYEOKSIOS A358 C98D # HANGUL SYLLABLE CIEUC-EU-NIEUNCIEUC A359 C98E # HANGUL SYLLABLE CIEUC-EU-NIEUNHIEUH A35A C98F # HANGUL SYLLABLE CIEUC-EU-TIKEUT A361 C991 # HANGUL SYLLABLE CIEUC-EU-RIEULKIYEOK A362 C992 # HANGUL SYLLABLE CIEUC-EU-RIEULMIEUM A363 C993 # HANGUL SYLLABLE CIEUC-EU-RIEULPIEUP A364 C994 # HANGUL SYLLABLE CIEUC-EU-RIEULSIOS A365 C995 # HANGUL SYLLABLE CIEUC-EU-RIEULTHIEUTH A366 C996 # HANGUL SYLLABLE CIEUC-EU-RIEULPHIEUPH A367 C997 # HANGUL SYLLABLE CIEUC-EU-RIEULHIEUH A368 C99A # HANGUL SYLLABLE CIEUC-EU-PIEUPSIOS A369 C99C # HANGUL SYLLABLE CIEUC-EU-SSANGSIOS A36A C99E # HANGUL SYLLABLE CIEUC-EU-CIEUC A36B C99F # HANGUL SYLLABLE CIEUC-EU-CHIEUCH A36C C9A0 # HANGUL SYLLABLE CIEUC-EU-KHIEUKH A36D C9A1 # HANGUL SYLLABLE CIEUC-EU-THIEUTH A36E C9A2 # HANGUL SYLLABLE CIEUC-EU-PHIEUPH A36F C9A3 # HANGUL SYLLABLE CIEUC-EU-HIEUH A370 C9A4 # HANGUL SYLLABLE CIEUC-YI A371 C9A5 # HANGUL SYLLABLE CIEUC-YI-KIYEOK A372 C9A6 # HANGUL SYLLABLE CIEUC-YI-SSANGKIYEOK A373 C9A7 # HANGUL SYLLABLE CIEUC-YI-KIYEOKSIOS A374 C9A8 # HANGUL SYLLABLE CIEUC-YI-NIEUN A375 C9A9 # HANGUL SYLLABLE CIEUC-YI-NIEUNCIEUC A376 C9AA # HANGUL SYLLABLE CIEUC-YI-NIEUNHIEUH A377 C9AB # HANGUL SYLLABLE CIEUC-YI-TIKEUT A378 C9AC # HANGUL SYLLABLE CIEUC-YI-RIEUL A379 C9AD # HANGUL SYLLABLE CIEUC-YI-RIEULKIYEOK A37A C9AE # HANGUL SYLLABLE CIEUC-YI-RIEULMIEUM A381 C9AF # HANGUL SYLLABLE CIEUC-YI-RIEULPIEUP A382 C9B0 # HANGUL SYLLABLE CIEUC-YI-RIEULSIOS A383 C9B1 # HANGUL SYLLABLE CIEUC-YI-RIEULTHIEUTH A384 C9B2 # HANGUL SYLLABLE CIEUC-YI-RIEULPHIEUPH A385 C9B3 # HANGUL SYLLABLE CIEUC-YI-RIEULHIEUH A386 C9B4 # HANGUL SYLLABLE CIEUC-YI-MIEUM A387 C9B5 # HANGUL SYLLABLE CIEUC-YI-PIEUP A388 C9B6 # HANGUL SYLLABLE CIEUC-YI-PIEUPSIOS A389 C9B7 # HANGUL SYLLABLE CIEUC-YI-SIOS A38A C9B8 # HANGUL SYLLABLE CIEUC-YI-SSANGSIOS A38B C9B9 # HANGUL SYLLABLE CIEUC-YI-IEUNG A38C C9BA # HANGUL SYLLABLE CIEUC-YI-CIEUC A38D C9BB # HANGUL SYLLABLE CIEUC-YI-CHIEUCH A38E C9BC # HANGUL SYLLABLE CIEUC-YI-KHIEUKH A38F C9BD # HANGUL SYLLABLE CIEUC-YI-THIEUTH A390 C9BE # HANGUL SYLLABLE CIEUC-YI-PHIEUPH A391 C9BF # HANGUL SYLLABLE CIEUC-YI-HIEUH A392 C9C2 # HANGUL SYLLABLE CIEUC-I-SSANGKIYEOK A393 C9C3 # HANGUL SYLLABLE CIEUC-I-KIYEOKSIOS A394 C9C5 # HANGUL SYLLABLE CIEUC-I-NIEUNCIEUC A395 C9C6 # HANGUL SYLLABLE CIEUC-I-NIEUNHIEUH A396 C9C9 # HANGUL SYLLABLE CIEUC-I-RIEULKIYEOK A397 C9CB # HANGUL SYLLABLE CIEUC-I-RIEULPIEUP A398 C9CC # HANGUL SYLLABLE CIEUC-I-RIEULSIOS A399 C9CD # HANGUL SYLLABLE CIEUC-I-RIEULTHIEUTH A39A C9CE # HANGUL SYLLABLE CIEUC-I-RIEULPHIEUPH A39B C9CF # HANGUL SYLLABLE CIEUC-I-RIEULHIEUH A39C C9D2 # HANGUL SYLLABLE CIEUC-I-PIEUPSIOS A39D C9D4 # HANGUL SYLLABLE CIEUC-I-SSANGSIOS A39E C9D7 # HANGUL SYLLABLE CIEUC-I-CHIEUCH A39F C9D8 # HANGUL SYLLABLE CIEUC-I-KHIEUKH A3A0 C9DB # HANGUL SYLLABLE CIEUC-I-HIEUH A3A1 FF01 # FULLWIDTH EXCLAMATION MARK A3A2 FF02 # FULLWIDTH QUOTATION MARK A3A3 FF03 # FULLWIDTH NUMBER SIGN A3A4 FF04 # FULLWIDTH DOLLAR SIGN A3A5 FF05 # FULLWIDTH PERCENT SIGN A3A6 FF06 # FULLWIDTH AMPERSAND A3A7 FF07 # FULLWIDTH APOSTROPHE A3A8 FF08 # FULLWIDTH LEFT PARENTHESIS A3A9 FF09 # FULLWIDTH RIGHT PARENTHESIS A3AA FF0A # FULLWIDTH ASTERISK A3AB FF0B # FULLWIDTH PLUS SIGN A3AC FF0C # FULLWIDTH COMMA A3AD FF0D # FULLWIDTH HYPHEN-MINUS A3AE FF0E # FULLWIDTH FULL STOP A3AF FF0F # FULLWIDTH SOLIDUS A3B0 FF10 # FULLWIDTH DIGIT ZERO A3B1 FF11 # FULLWIDTH DIGIT ONE A3B2 FF12 # FULLWIDTH DIGIT TWO A3B3 FF13 # FULLWIDTH DIGIT THREE A3B4 FF14 # FULLWIDTH DIGIT FOUR A3B5 FF15 # FULLWIDTH DIGIT FIVE A3B6 FF16 # FULLWIDTH DIGIT SIX A3B7 FF17 # FULLWIDTH DIGIT SEVEN A3B8 FF18 # FULLWIDTH DIGIT EIGHT A3B9 FF19 # FULLWIDTH DIGIT NINE A3BA FF1A # FULLWIDTH COLON A3BB FF1B # FULLWIDTH SEMICOLON A3BC FF1C # FULLWIDTH LESS-THAN SIGN A3BD FF1D # FULLWIDTH EQUALS SIGN A3BE FF1E # FULLWIDTH GREATER-THAN SIGN A3BF FF1F # FULLWIDTH QUESTION MARK A3C0 FF20 # FULLWIDTH COMMERCIAL AT A3C1 FF21 # FULLWIDTH LATIN CAPITAL LETTER A A3C2 FF22 # FULLWIDTH LATIN CAPITAL LETTER B A3C3 FF23 # FULLWIDTH LATIN CAPITAL LETTER C A3C4 FF24 # FULLWIDTH LATIN CAPITAL LETTER D A3C5 FF25 # FULLWIDTH LATIN CAPITAL LETTER E A3C6 FF26 # FULLWIDTH LATIN CAPITAL LETTER F A3C7 FF27 # FULLWIDTH LATIN CAPITAL LETTER G A3C8 FF28 # FULLWIDTH LATIN CAPITAL LETTER H A3C9 FF29 # FULLWIDTH LATIN CAPITAL LETTER I A3CA FF2A # FULLWIDTH LATIN CAPITAL LETTER J A3CB FF2B # FULLWIDTH LATIN CAPITAL LETTER K A3CC FF2C # FULLWIDTH LATIN CAPITAL LETTER L A3CD FF2D # FULLWIDTH LATIN CAPITAL LETTER M A3CE FF2E # FULLWIDTH LATIN CAPITAL LETTER N A3CF FF2F # FULLWIDTH LATIN CAPITAL LETTER O A3D0 FF30 # FULLWIDTH LATIN CAPITAL LETTER P A3D1 FF31 # FULLWIDTH LATIN CAPITAL LETTER Q A3D2 FF32 # FULLWIDTH LATIN CAPITAL LETTER R A3D3 FF33 # FULLWIDTH LATIN CAPITAL LETTER S A3D4 FF34 # FULLWIDTH LATIN CAPITAL LETTER T A3D5 FF35 # FULLWIDTH LATIN CAPITAL LETTER U A3D6 FF36 # FULLWIDTH LATIN CAPITAL LETTER V A3D7 FF37 # FULLWIDTH LATIN CAPITAL LETTER W A3D8 FF38 # FULLWIDTH LATIN CAPITAL LETTER X A3D9 FF39 # FULLWIDTH LATIN CAPITAL LETTER Y A3DA FF3A # FULLWIDTH LATIN CAPITAL LETTER Z A3DB FF3B # FULLWIDTH LEFT SQUARE BRACKET A3DC FFE6 # FULLWIDTH WON SIGN A3DD FF3D # FULLWIDTH RIGHT SQUARE BRACKET A3DE FF3E # FULLWIDTH CIRCUMFLEX ACCENT A3DF FF3F # FULLWIDTH LOW LINE A3E0 FF40 # FULLWIDTH GRAVE ACCENT A3E1 FF41 # FULLWIDTH LATIN SMALL LETTER A A3E2 FF42 # FULLWIDTH LATIN SMALL LETTER B A3E3 FF43 # FULLWIDTH LATIN SMALL LETTER C A3E4 FF44 # FULLWIDTH LATIN SMALL LETTER D A3E5 FF45 # FULLWIDTH LATIN SMALL LETTER E A3E6 FF46 # FULLWIDTH LATIN SMALL LETTER F A3E7 FF47 # FULLWIDTH LATIN SMALL LETTER G A3E8 FF48 # FULLWIDTH LATIN SMALL LETTER H A3E9 FF49 # FULLWIDTH LATIN SMALL LETTER I A3EA FF4A # FULLWIDTH LATIN SMALL LETTER J A3EB FF4B # FULLWIDTH LATIN SMALL LETTER K A3EC FF4C # FULLWIDTH LATIN SMALL LETTER L A3ED FF4D # FULLWIDTH LATIN SMALL LETTER M A3EE FF4E # FULLWIDTH LATIN SMALL LETTER N A3EF FF4F # FULLWIDTH LATIN SMALL LETTER O A3F0 FF50 # FULLWIDTH LATIN SMALL LETTER P A3F1 FF51 # FULLWIDTH LATIN SMALL LETTER Q A3F2 FF52 # FULLWIDTH LATIN SMALL LETTER R A3F3 FF53 # FULLWIDTH LATIN SMALL LETTER S A3F4 FF54 # FULLWIDTH LATIN SMALL LETTER T A3F5 FF55 # FULLWIDTH LATIN SMALL LETTER U A3F6 FF56 # FULLWIDTH LATIN SMALL LETTER V A3F7 FF57 # FULLWIDTH LATIN SMALL LETTER W A3F8 FF58 # FULLWIDTH LATIN SMALL LETTER X A3F9 FF59 # FULLWIDTH LATIN SMALL LETTER Y A3FA FF5A # FULLWIDTH LATIN SMALL LETTER Z A3FB FF5B # FULLWIDTH LEFT CURLY BRACKET A3FC FF5C # FULLWIDTH VERTICAL LINE A3FD FF5D # FULLWIDTH RIGHT CURLY BRACKET A3FE FFE3 # FULLWIDTH MACRON A441 C9DE # HANGUL SYLLABLE SSANGCIEUC-A-SSANGKIYEOK A442 C9DF # HANGUL SYLLABLE SSANGCIEUC-A-KIYEOKSIOS A443 C9E1 # HANGUL SYLLABLE SSANGCIEUC-A-NIEUNCIEUC A444 C9E3 # HANGUL SYLLABLE SSANGCIEUC-A-TIKEUT A445 C9E5 # HANGUL SYLLABLE SSANGCIEUC-A-RIEULKIYEOK A446 C9E6 # HANGUL SYLLABLE SSANGCIEUC-A-RIEULMIEUM A447 C9E8 # HANGUL SYLLABLE SSANGCIEUC-A-RIEULSIOS A448 C9E9 # HANGUL SYLLABLE SSANGCIEUC-A-RIEULTHIEUTH A449 C9EA # HANGUL SYLLABLE SSANGCIEUC-A-RIEULPHIEUPH A44A C9EB # HANGUL SYLLABLE SSANGCIEUC-A-RIEULHIEUH A44B C9EE # HANGUL SYLLABLE SSANGCIEUC-A-PIEUPSIOS A44C C9F2 # HANGUL SYLLABLE SSANGCIEUC-A-CIEUC A44D C9F3 # HANGUL SYLLABLE SSANGCIEUC-A-CHIEUCH A44E C9F4 # HANGUL SYLLABLE SSANGCIEUC-A-KHIEUKH A44F C9F5 # HANGUL SYLLABLE SSANGCIEUC-A-THIEUTH A450 C9F6 # HANGUL SYLLABLE SSANGCIEUC-A-PHIEUPH A451 C9F7 # HANGUL SYLLABLE SSANGCIEUC-A-HIEUH A452 C9FA # HANGUL SYLLABLE SSANGCIEUC-AE-SSANGKIYEOK A453 C9FB # HANGUL SYLLABLE SSANGCIEUC-AE-KIYEOKSIOS A454 C9FD # HANGUL SYLLABLE SSANGCIEUC-AE-NIEUNCIEUC A455 C9FE # HANGUL SYLLABLE SSANGCIEUC-AE-NIEUNHIEUH A456 C9FF # HANGUL SYLLABLE SSANGCIEUC-AE-TIKEUT A457 CA01 # HANGUL SYLLABLE SSANGCIEUC-AE-RIEULKIYEOK A458 CA02 # HANGUL SYLLABLE SSANGCIEUC-AE-RIEULMIEUM A459 CA03 # HANGUL SYLLABLE SSANGCIEUC-AE-RIEULPIEUP A45A CA04 # HANGUL SYLLABLE SSANGCIEUC-AE-RIEULSIOS A461 CA05 # HANGUL SYLLABLE SSANGCIEUC-AE-RIEULTHIEUTH A462 CA06 # HANGUL SYLLABLE SSANGCIEUC-AE-RIEULPHIEUPH A463 CA07 # HANGUL SYLLABLE SSANGCIEUC-AE-RIEULHIEUH A464 CA0A # HANGUL SYLLABLE SSANGCIEUC-AE-PIEUPSIOS A465 CA0E # HANGUL SYLLABLE SSANGCIEUC-AE-CIEUC A466 CA0F # HANGUL SYLLABLE SSANGCIEUC-AE-CHIEUCH A467 CA10 # HANGUL SYLLABLE SSANGCIEUC-AE-KHIEUKH A468 CA11 # HANGUL SYLLABLE SSANGCIEUC-AE-THIEUTH A469 CA12 # HANGUL SYLLABLE SSANGCIEUC-AE-PHIEUPH A46A CA13 # HANGUL SYLLABLE SSANGCIEUC-AE-HIEUH A46B CA15 # HANGUL SYLLABLE SSANGCIEUC-YA-KIYEOK A46C CA16 # HANGUL SYLLABLE SSANGCIEUC-YA-SSANGKIYEOK A46D CA17 # HANGUL SYLLABLE SSANGCIEUC-YA-KIYEOKSIOS A46E CA19 # HANGUL SYLLABLE SSANGCIEUC-YA-NIEUNCIEUC A46F CA1A # HANGUL SYLLABLE SSANGCIEUC-YA-NIEUNHIEUH A470 CA1B # HANGUL SYLLABLE SSANGCIEUC-YA-TIKEUT A471 CA1C # HANGUL SYLLABLE SSANGCIEUC-YA-RIEUL A472 CA1D # HANGUL SYLLABLE SSANGCIEUC-YA-RIEULKIYEOK A473 CA1E # HANGUL SYLLABLE SSANGCIEUC-YA-RIEULMIEUM A474 CA1F # HANGUL SYLLABLE SSANGCIEUC-YA-RIEULPIEUP A475 CA20 # HANGUL SYLLABLE SSANGCIEUC-YA-RIEULSIOS A476 CA21 # HANGUL SYLLABLE SSANGCIEUC-YA-RIEULTHIEUTH A477 CA22 # HANGUL SYLLABLE SSANGCIEUC-YA-RIEULPHIEUPH A478 CA23 # HANGUL SYLLABLE SSANGCIEUC-YA-RIEULHIEUH A479 CA24 # HANGUL SYLLABLE SSANGCIEUC-YA-MIEUM A47A CA25 # HANGUL SYLLABLE SSANGCIEUC-YA-PIEUP A481 CA26 # HANGUL SYLLABLE SSANGCIEUC-YA-PIEUPSIOS A482 CA27 # HANGUL SYLLABLE SSANGCIEUC-YA-SIOS A483 CA28 # HANGUL SYLLABLE SSANGCIEUC-YA-SSANGSIOS A484 CA2A # HANGUL SYLLABLE SSANGCIEUC-YA-CIEUC A485 CA2B # HANGUL SYLLABLE SSANGCIEUC-YA-CHIEUCH A486 CA2C # HANGUL SYLLABLE SSANGCIEUC-YA-KHIEUKH A487 CA2D # HANGUL SYLLABLE SSANGCIEUC-YA-THIEUTH A488 CA2E # HANGUL SYLLABLE SSANGCIEUC-YA-PHIEUPH A489 CA2F # HANGUL SYLLABLE SSANGCIEUC-YA-HIEUH A48A CA30 # HANGUL SYLLABLE SSANGCIEUC-YAE A48B CA31 # HANGUL SYLLABLE SSANGCIEUC-YAE-KIYEOK A48C CA32 # HANGUL SYLLABLE SSANGCIEUC-YAE-SSANGKIYEOK A48D CA33 # HANGUL SYLLABLE SSANGCIEUC-YAE-KIYEOKSIOS A48E CA34 # HANGUL SYLLABLE SSANGCIEUC-YAE-NIEUN A48F CA35 # HANGUL SYLLABLE SSANGCIEUC-YAE-NIEUNCIEUC A490 CA36 # HANGUL SYLLABLE SSANGCIEUC-YAE-NIEUNHIEUH A491 CA37 # HANGUL SYLLABLE SSANGCIEUC-YAE-TIKEUT A492 CA38 # HANGUL SYLLABLE SSANGCIEUC-YAE-RIEUL A493 CA39 # HANGUL SYLLABLE SSANGCIEUC-YAE-RIEULKIYEOK A494 CA3A # HANGUL SYLLABLE SSANGCIEUC-YAE-RIEULMIEUM A495 CA3B # HANGUL SYLLABLE SSANGCIEUC-YAE-RIEULPIEUP A496 CA3C # HANGUL SYLLABLE SSANGCIEUC-YAE-RIEULSIOS A497 CA3D # HANGUL SYLLABLE SSANGCIEUC-YAE-RIEULTHIEUTH A498 CA3E # HANGUL SYLLABLE SSANGCIEUC-YAE-RIEULPHIEUPH A499 CA3F # HANGUL SYLLABLE SSANGCIEUC-YAE-RIEULHIEUH A49A CA40 # HANGUL SYLLABLE SSANGCIEUC-YAE-MIEUM A49B CA41 # HANGUL SYLLABLE SSANGCIEUC-YAE-PIEUP A49C CA42 # HANGUL SYLLABLE SSANGCIEUC-YAE-PIEUPSIOS A49D CA43 # HANGUL SYLLABLE SSANGCIEUC-YAE-SIOS A49E CA44 # HANGUL SYLLABLE SSANGCIEUC-YAE-SSANGSIOS A49F CA45 # HANGUL SYLLABLE SSANGCIEUC-YAE-IEUNG A4A0 CA46 # HANGUL SYLLABLE SSANGCIEUC-YAE-CIEUC A4A1 3131 # HANGUL LETTER KIYEOK A4A2 3132 # HANGUL LETTER SSANGKIYEOK A4A3 3133 # HANGUL LETTER KIYEOK-SIOS A4A4 3134 # HANGUL LETTER NIEUN A4A5 3135 # HANGUL LETTER NIEUN-CIEUC A4A6 3136 # HANGUL LETTER NIEUN-HIEUH A4A7 3137 # HANGUL LETTER TIKEUT A4A8 3138 # HANGUL LETTER SSANGTIKEUT A4A9 3139 # HANGUL LETTER RIEUL A4AA 313A # HANGUL LETTER RIEUL-KIYEOK A4AB 313B # HANGUL LETTER RIEUL-MIEUM A4AC 313C # HANGUL LETTER RIEUL-PIEUP A4AD 313D # HANGUL LETTER RIEUL-SIOS A4AE 313E # HANGUL LETTER RIEUL-THIEUTH A4AF 313F # HANGUL LETTER RIEUL-PHIEUPH A4B0 3140 # HANGUL LETTER RIEUL-HIEUH A4B1 3141 # HANGUL LETTER MIEUM A4B2 3142 # HANGUL LETTER PIEUP A4B3 3143 # HANGUL LETTER SSANGPIEUP A4B4 3144 # HANGUL LETTER PIEUP-SIOS A4B5 3145 # HANGUL LETTER SIOS A4B6 3146 # HANGUL LETTER SSANGSIOS A4B7 3147 # HANGUL LETTER IEUNG A4B8 3148 # HANGUL LETTER CIEUC A4B9 3149 # HANGUL LETTER SSANGCIEUC A4BA 314A # HANGUL LETTER CHIEUCH A4BB 314B # HANGUL LETTER KHIEUKH A4BC 314C # HANGUL LETTER THIEUTH A4BD 314D # HANGUL LETTER PHIEUPH A4BE 314E # HANGUL LETTER HIEUH A4BF 314F # HANGUL LETTER A A4C0 3150 # HANGUL LETTER AE A4C1 3151 # HANGUL LETTER YA A4C2 3152 # HANGUL LETTER YAE A4C3 3153 # HANGUL LETTER EO A4C4 3154 # HANGUL LETTER E A4C5 3155 # HANGUL LETTER YEO A4C6 3156 # HANGUL LETTER YE A4C7 3157 # HANGUL LETTER O A4C8 3158 # HANGUL LETTER WA A4C9 3159 # HANGUL LETTER WAE A4CA 315A # HANGUL LETTER OE A4CB 315B # HANGUL LETTER YO A4CC 315C # HANGUL LETTER U A4CD 315D # HANGUL LETTER WEO A4CE 315E # HANGUL LETTER WE A4CF 315F # HANGUL LETTER WI A4D0 3160 # HANGUL LETTER YU A4D1 3161 # HANGUL LETTER EU A4D2 3162 # HANGUL LETTER YI A4D3 3163 # HANGUL LETTER I A4D4 3164 # HANGUL FILLER A4D5 3165 # HANGUL LETTER SSANGNIEUN A4D6 3166 # HANGUL LETTER NIEUN-TIKEUT A4D7 3167 # HANGUL LETTER NIEUN-SIOS A4D8 3168 # HANGUL LETTER NIEUN-PANSIOS A4D9 3169 # HANGUL LETTER RIEUL-KIYEOK-SIOS A4DA 316A # HANGUL LETTER RIEUL-TIKEUT A4DB 316B # HANGUL LETTER RIEUL-PIEUP-SIOS A4DC 316C # HANGUL LETTER RIEUL-PANSIOS A4DD 316D # HANGUL LETTER RIEUL-YEORINHIEUH A4DE 316E # HANGUL LETTER MIEUM-PIEUP A4DF 316F # HANGUL LETTER MIEUM-SIOS A4E0 3170 # HANGUL LETTER MIEUM-PANSIOS A4E1 3171 # HANGUL LETTER KAPYEOUNMIEUM A4E2 3172 # HANGUL LETTER PIEUP-KIYEOK A4E3 3173 # HANGUL LETTER PIEUP-TIKEUT A4E4 3174 # HANGUL LETTER PIEUP-SIOS-KIYEOK A4E5 3175 # HANGUL LETTER PIEUP-SIOS-TIKEUT A4E6 3176 # HANGUL LETTER PIEUP-CIEUC A4E7 3177 # HANGUL LETTER PIEUP-THIEUTH A4E8 3178 # HANGUL LETTER KAPYEOUNPIEUP A4E9 3179 # HANGUL LETTER KAPYEOUNSSANGPIEUP A4EA 317A # HANGUL LETTER SIOS-KIYEOK A4EB 317B # HANGUL LETTER SIOS-NIEUN A4EC 317C # HANGUL LETTER SIOS-TIKEUT A4ED 317D # HANGUL LETTER SIOS-PIEUP A4EE 317E # HANGUL LETTER SIOS-CIEUC A4EF 317F # HANGUL LETTER PANSIOS A4F0 3180 # HANGUL LETTER SSANGIEUNG A4F1 3181 # HANGUL LETTER YESIEUNG A4F2 3182 # HANGUL LETTER YESIEUNG-SIOS A4F3 3183 # HANGUL LETTER YESIEUNG-PANSIOS A4F4 3184 # HANGUL LETTER KAPYEOUNPHIEUPH A4F5 3185 # HANGUL LETTER SSANGHIEUH A4F6 3186 # HANGUL LETTER YEORINHIEUH A4F7 3187 # HANGUL LETTER YO-YA A4F8 3188 # HANGUL LETTER YO-YAE A4F9 3189 # HANGUL LETTER YO-I A4FA 318A # HANGUL LETTER YU-YEO A4FB 318B # HANGUL LETTER YU-YE A4FC 318C # HANGUL LETTER YU-I A4FD 318D # HANGUL LETTER ARAEA A4FE 318E # HANGUL LETTER ARAEAE A541 CA47 # HANGUL SYLLABLE SSANGCIEUC-YAE-CHIEUCH A542 CA48 # HANGUL SYLLABLE SSANGCIEUC-YAE-KHIEUKH A543 CA49 # HANGUL SYLLABLE SSANGCIEUC-YAE-THIEUTH A544 CA4A # HANGUL SYLLABLE SSANGCIEUC-YAE-PHIEUPH A545 CA4B # HANGUL SYLLABLE SSANGCIEUC-YAE-HIEUH A546 CA4E # HANGUL SYLLABLE SSANGCIEUC-EO-SSANGKIYEOK A547 CA4F # HANGUL SYLLABLE SSANGCIEUC-EO-KIYEOKSIOS A548 CA51 # HANGUL SYLLABLE SSANGCIEUC-EO-NIEUNCIEUC A549 CA52 # HANGUL SYLLABLE SSANGCIEUC-EO-NIEUNHIEUH A54A CA53 # HANGUL SYLLABLE SSANGCIEUC-EO-TIKEUT A54B CA55 # HANGUL SYLLABLE SSANGCIEUC-EO-RIEULKIYEOK A54C CA56 # HANGUL SYLLABLE SSANGCIEUC-EO-RIEULMIEUM A54D CA57 # HANGUL SYLLABLE SSANGCIEUC-EO-RIEULPIEUP A54E CA58 # HANGUL SYLLABLE SSANGCIEUC-EO-RIEULSIOS A54F CA59 # HANGUL SYLLABLE SSANGCIEUC-EO-RIEULTHIEUTH A550 CA5A # HANGUL SYLLABLE SSANGCIEUC-EO-RIEULPHIEUPH A551 CA5B # HANGUL SYLLABLE SSANGCIEUC-EO-RIEULHIEUH A552 CA5E # HANGUL SYLLABLE SSANGCIEUC-EO-PIEUPSIOS A553 CA62 # HANGUL SYLLABLE SSANGCIEUC-EO-CIEUC A554 CA63 # HANGUL SYLLABLE SSANGCIEUC-EO-CHIEUCH A555 CA64 # HANGUL SYLLABLE SSANGCIEUC-EO-KHIEUKH A556 CA65 # HANGUL SYLLABLE SSANGCIEUC-EO-THIEUTH A557 CA66 # HANGUL SYLLABLE SSANGCIEUC-EO-PHIEUPH A558 CA67 # HANGUL SYLLABLE SSANGCIEUC-EO-HIEUH A559 CA69 # HANGUL SYLLABLE SSANGCIEUC-E-KIYEOK A55A CA6A # HANGUL SYLLABLE SSANGCIEUC-E-SSANGKIYEOK A561 CA6B # HANGUL SYLLABLE SSANGCIEUC-E-KIYEOKSIOS A562 CA6C # HANGUL SYLLABLE SSANGCIEUC-E-NIEUN A563 CA6D # HANGUL SYLLABLE SSANGCIEUC-E-NIEUNCIEUC A564 CA6E # HANGUL SYLLABLE SSANGCIEUC-E-NIEUNHIEUH A565 CA6F # HANGUL SYLLABLE SSANGCIEUC-E-TIKEUT A566 CA70 # HANGUL SYLLABLE SSANGCIEUC-E-RIEUL A567 CA71 # HANGUL SYLLABLE SSANGCIEUC-E-RIEULKIYEOK A568 CA72 # HANGUL SYLLABLE SSANGCIEUC-E-RIEULMIEUM A569 CA73 # HANGUL SYLLABLE SSANGCIEUC-E-RIEULPIEUP A56A CA74 # HANGUL SYLLABLE SSANGCIEUC-E-RIEULSIOS A56B CA75 # HANGUL SYLLABLE SSANGCIEUC-E-RIEULTHIEUTH A56C CA76 # HANGUL SYLLABLE SSANGCIEUC-E-RIEULPHIEUPH A56D CA77 # HANGUL SYLLABLE SSANGCIEUC-E-RIEULHIEUH A56E CA78 # HANGUL SYLLABLE SSANGCIEUC-E-MIEUM A56F CA79 # HANGUL SYLLABLE SSANGCIEUC-E-PIEUP A570 CA7A # HANGUL SYLLABLE SSANGCIEUC-E-PIEUPSIOS A571 CA7B # HANGUL SYLLABLE SSANGCIEUC-E-SIOS A572 CA7C # HANGUL SYLLABLE SSANGCIEUC-E-SSANGSIOS A573 CA7E # HANGUL SYLLABLE SSANGCIEUC-E-CIEUC A574 CA7F # HANGUL SYLLABLE SSANGCIEUC-E-CHIEUCH A575 CA80 # HANGUL SYLLABLE SSANGCIEUC-E-KHIEUKH A576 CA81 # HANGUL SYLLABLE SSANGCIEUC-E-THIEUTH A577 CA82 # HANGUL SYLLABLE SSANGCIEUC-E-PHIEUPH A578 CA83 # HANGUL SYLLABLE SSANGCIEUC-E-HIEUH A579 CA85 # HANGUL SYLLABLE SSANGCIEUC-YEO-KIYEOK A57A CA86 # HANGUL SYLLABLE SSANGCIEUC-YEO-SSANGKIYEOK A581 CA87 # HANGUL SYLLABLE SSANGCIEUC-YEO-KIYEOKSIOS A582 CA88 # HANGUL SYLLABLE SSANGCIEUC-YEO-NIEUN A583 CA89 # HANGUL SYLLABLE SSANGCIEUC-YEO-NIEUNCIEUC A584 CA8A # HANGUL SYLLABLE SSANGCIEUC-YEO-NIEUNHIEUH A585 CA8B # HANGUL SYLLABLE SSANGCIEUC-YEO-TIKEUT A586 CA8C # HANGUL SYLLABLE SSANGCIEUC-YEO-RIEUL A587 CA8D # HANGUL SYLLABLE SSANGCIEUC-YEO-RIEULKIYEOK A588 CA8E # HANGUL SYLLABLE SSANGCIEUC-YEO-RIEULMIEUM A589 CA8F # HANGUL SYLLABLE SSANGCIEUC-YEO-RIEULPIEUP A58A CA90 # HANGUL SYLLABLE SSANGCIEUC-YEO-RIEULSIOS A58B CA91 # HANGUL SYLLABLE SSANGCIEUC-YEO-RIEULTHIEUTH A58C CA92 # HANGUL SYLLABLE SSANGCIEUC-YEO-RIEULPHIEUPH A58D CA93 # HANGUL SYLLABLE SSANGCIEUC-YEO-RIEULHIEUH A58E CA94 # HANGUL SYLLABLE SSANGCIEUC-YEO-MIEUM A58F CA95 # HANGUL SYLLABLE SSANGCIEUC-YEO-PIEUP A590 CA96 # HANGUL SYLLABLE SSANGCIEUC-YEO-PIEUPSIOS A591 CA97 # HANGUL SYLLABLE SSANGCIEUC-YEO-SIOS A592 CA99 # HANGUL SYLLABLE SSANGCIEUC-YEO-IEUNG A593 CA9A # HANGUL SYLLABLE SSANGCIEUC-YEO-CIEUC A594 CA9B # HANGUL SYLLABLE SSANGCIEUC-YEO-CHIEUCH A595 CA9C # HANGUL SYLLABLE SSANGCIEUC-YEO-KHIEUKH A596 CA9D # HANGUL SYLLABLE SSANGCIEUC-YEO-THIEUTH A597 CA9E # HANGUL SYLLABLE SSANGCIEUC-YEO-PHIEUPH A598 CA9F # HANGUL SYLLABLE SSANGCIEUC-YEO-HIEUH A599 CAA0 # HANGUL SYLLABLE SSANGCIEUC-YE A59A CAA1 # HANGUL SYLLABLE SSANGCIEUC-YE-KIYEOK A59B CAA2 # HANGUL SYLLABLE SSANGCIEUC-YE-SSANGKIYEOK A59C CAA3 # HANGUL SYLLABLE SSANGCIEUC-YE-KIYEOKSIOS A59D CAA4 # HANGUL SYLLABLE SSANGCIEUC-YE-NIEUN A59E CAA5 # HANGUL SYLLABLE SSANGCIEUC-YE-NIEUNCIEUC A59F CAA6 # HANGUL SYLLABLE SSANGCIEUC-YE-NIEUNHIEUH A5A0 CAA7 # HANGUL SYLLABLE SSANGCIEUC-YE-TIKEUT A5A1 2170 # SMALL ROMAN NUMERAL ONE A5A2 2171 # SMALL ROMAN NUMERAL TWO A5A3 2172 # SMALL ROMAN NUMERAL THREE A5A4 2173 # SMALL ROMAN NUMERAL FOUR A5A5 2174 # SMALL ROMAN NUMERAL FIVE A5A6 2175 # SMALL ROMAN NUMERAL SIX A5A7 2176 # SMALL ROMAN NUMERAL SEVEN A5A8 2177 # SMALL ROMAN NUMERAL EIGHT A5A9 2178 # SMALL ROMAN NUMERAL NINE A5AA 2179 # SMALL ROMAN NUMERAL TEN A5B0 2160 # ROMAN NUMERAL ONE A5B1 2161 # ROMAN NUMERAL TWO A5B2 2162 # ROMAN NUMERAL THREE A5B3 2163 # ROMAN NUMERAL FOUR A5B4 2164 # ROMAN NUMERAL FIVE A5B5 2165 # ROMAN NUMERAL SIX A5B6 2166 # ROMAN NUMERAL SEVEN A5B7 2167 # ROMAN NUMERAL EIGHT A5B8 2168 # ROMAN NUMERAL NINE A5B9 2169 # ROMAN NUMERAL TEN A5C1 0391 # GREEK CAPITAL LETTER ALPHA A5C2 0392 # GREEK CAPITAL LETTER BETA A5C3 0393 # GREEK CAPITAL LETTER GAMMA A5C4 0394 # GREEK CAPITAL LETTER DELTA A5C5 0395 # GREEK CAPITAL LETTER EPSILON A5C6 0396 # GREEK CAPITAL LETTER ZETA A5C7 0397 # GREEK CAPITAL LETTER ETA A5C8 0398 # GREEK CAPITAL LETTER THETA A5C9 0399 # GREEK CAPITAL LETTER IOTA A5CA 039A # GREEK CAPITAL LETTER KAPPA A5CB 039B # GREEK CAPITAL LETTER LAMDA A5CC 039C # GREEK CAPITAL LETTER MU A5CD 039D # GREEK CAPITAL LETTER NU A5CE 039E # GREEK CAPITAL LETTER XI A5CF 039F # GREEK CAPITAL LETTER OMICRON A5D0 03A0 # GREEK CAPITAL LETTER PI A5D1 03A1 # GREEK CAPITAL LETTER RHO A5D2 03A3 # GREEK CAPITAL LETTER SIGMA A5D3 03A4 # GREEK CAPITAL LETTER TAU A5D4 03A5 # GREEK CAPITAL LETTER UPSILON A5D5 03A6 # GREEK CAPITAL LETTER PHI A5D6 03A7 # GREEK CAPITAL LETTER CHI A5D7 03A8 # GREEK CAPITAL LETTER PSI A5D8 03A9 # GREEK CAPITAL LETTER OMEGA A5E1 03B1 # GREEK SMALL LETTER ALPHA A5E2 03B2 # GREEK SMALL LETTER BETA A5E3 03B3 # GREEK SMALL LETTER GAMMA A5E4 03B4 # GREEK SMALL LETTER DELTA A5E5 03B5 # GREEK SMALL LETTER EPSILON A5E6 03B6 # GREEK SMALL LETTER ZETA A5E7 03B7 # GREEK SMALL LETTER ETA A5E8 03B8 # GREEK SMALL LETTER THETA A5E9 03B9 # GREEK SMALL LETTER IOTA A5EA 03BA # GREEK SMALL LETTER KAPPA A5EB 03BB # GREEK SMALL LETTER LAMDA A5EC 03BC # GREEK SMALL LETTER MU A5ED 03BD # GREEK SMALL LETTER NU A5EE 03BE # GREEK SMALL LETTER XI A5EF 03BF # GREEK SMALL LETTER OMICRON A5F0 03C0 # GREEK SMALL LETTER PI A5F1 03C1 # GREEK SMALL LETTER RHO A5F2 03C3 # GREEK SMALL LETTER SIGMA A5F3 03C4 # GREEK SMALL LETTER TAU A5F4 03C5 # GREEK SMALL LETTER UPSILON A5F5 03C6 # GREEK SMALL LETTER PHI A5F6 03C7 # GREEK SMALL LETTER CHI A5F7 03C8 # GREEK SMALL LETTER PSI A5F8 03C9 # GREEK SMALL LETTER OMEGA A641 CAA8 # HANGUL SYLLABLE SSANGCIEUC-YE-RIEUL A642 CAA9 # HANGUL SYLLABLE SSANGCIEUC-YE-RIEULKIYEOK A643 CAAA # HANGUL SYLLABLE SSANGCIEUC-YE-RIEULMIEUM A644 CAAB # HANGUL SYLLABLE SSANGCIEUC-YE-RIEULPIEUP A645 CAAC # HANGUL SYLLABLE SSANGCIEUC-YE-RIEULSIOS A646 CAAD # HANGUL SYLLABLE SSANGCIEUC-YE-RIEULTHIEUTH A647 CAAE # HANGUL SYLLABLE SSANGCIEUC-YE-RIEULPHIEUPH A648 CAAF # HANGUL SYLLABLE SSANGCIEUC-YE-RIEULHIEUH A649 CAB0 # HANGUL SYLLABLE SSANGCIEUC-YE-MIEUM A64A CAB1 # HANGUL SYLLABLE SSANGCIEUC-YE-PIEUP A64B CAB2 # HANGUL SYLLABLE SSANGCIEUC-YE-PIEUPSIOS A64C CAB3 # HANGUL SYLLABLE SSANGCIEUC-YE-SIOS A64D CAB4 # HANGUL SYLLABLE SSANGCIEUC-YE-SSANGSIOS A64E CAB5 # HANGUL SYLLABLE SSANGCIEUC-YE-IEUNG A64F CAB6 # HANGUL SYLLABLE SSANGCIEUC-YE-CIEUC A650 CAB7 # HANGUL SYLLABLE SSANGCIEUC-YE-CHIEUCH A651 CAB8 # HANGUL SYLLABLE SSANGCIEUC-YE-KHIEUKH A652 CAB9 # HANGUL SYLLABLE SSANGCIEUC-YE-THIEUTH A653 CABA # HANGUL SYLLABLE SSANGCIEUC-YE-PHIEUPH A654 CABB # HANGUL SYLLABLE SSANGCIEUC-YE-HIEUH A655 CABE # HANGUL SYLLABLE SSANGCIEUC-O-SSANGKIYEOK A656 CABF # HANGUL SYLLABLE SSANGCIEUC-O-KIYEOKSIOS A657 CAC1 # HANGUL SYLLABLE SSANGCIEUC-O-NIEUNCIEUC A658 CAC2 # HANGUL SYLLABLE SSANGCIEUC-O-NIEUNHIEUH A659 CAC3 # HANGUL SYLLABLE SSANGCIEUC-O-TIKEUT A65A CAC5 # HANGUL SYLLABLE SSANGCIEUC-O-RIEULKIYEOK A661 CAC6 # HANGUL SYLLABLE SSANGCIEUC-O-RIEULMIEUM A662 CAC7 # HANGUL SYLLABLE SSANGCIEUC-O-RIEULPIEUP A663 CAC8 # HANGUL SYLLABLE SSANGCIEUC-O-RIEULSIOS A664 CAC9 # HANGUL SYLLABLE SSANGCIEUC-O-RIEULTHIEUTH A665 CACA # HANGUL SYLLABLE SSANGCIEUC-O-RIEULPHIEUPH A666 CACB # HANGUL SYLLABLE SSANGCIEUC-O-RIEULHIEUH A667 CACE # HANGUL SYLLABLE SSANGCIEUC-O-PIEUPSIOS A668 CAD0 # HANGUL SYLLABLE SSANGCIEUC-O-SSANGSIOS A669 CAD2 # HANGUL SYLLABLE SSANGCIEUC-O-CIEUC A66A CAD4 # HANGUL SYLLABLE SSANGCIEUC-O-KHIEUKH A66B CAD5 # HANGUL SYLLABLE SSANGCIEUC-O-THIEUTH A66C CAD6 # HANGUL SYLLABLE SSANGCIEUC-O-PHIEUPH A66D CAD7 # HANGUL SYLLABLE SSANGCIEUC-O-HIEUH A66E CADA # HANGUL SYLLABLE SSANGCIEUC-WA-SSANGKIYEOK A66F CADB # HANGUL SYLLABLE SSANGCIEUC-WA-KIYEOKSIOS A670 CADC # HANGUL SYLLABLE SSANGCIEUC-WA-NIEUN A671 CADD # HANGUL SYLLABLE SSANGCIEUC-WA-NIEUNCIEUC A672 CADE # HANGUL SYLLABLE SSANGCIEUC-WA-NIEUNHIEUH A673 CADF # HANGUL SYLLABLE SSANGCIEUC-WA-TIKEUT A674 CAE1 # HANGUL SYLLABLE SSANGCIEUC-WA-RIEULKIYEOK A675 CAE2 # HANGUL SYLLABLE SSANGCIEUC-WA-RIEULMIEUM A676 CAE3 # HANGUL SYLLABLE SSANGCIEUC-WA-RIEULPIEUP A677 CAE4 # HANGUL SYLLABLE SSANGCIEUC-WA-RIEULSIOS A678 CAE5 # HANGUL SYLLABLE SSANGCIEUC-WA-RIEULTHIEUTH A679 CAE6 # HANGUL SYLLABLE SSANGCIEUC-WA-RIEULPHIEUPH A67A CAE7 # HANGUL SYLLABLE SSANGCIEUC-WA-RIEULHIEUH A681 CAE8 # HANGUL SYLLABLE SSANGCIEUC-WA-MIEUM A682 CAE9 # HANGUL SYLLABLE SSANGCIEUC-WA-PIEUP A683 CAEA # HANGUL SYLLABLE SSANGCIEUC-WA-PIEUPSIOS A684 CAEB # HANGUL SYLLABLE SSANGCIEUC-WA-SIOS A685 CAED # HANGUL SYLLABLE SSANGCIEUC-WA-IEUNG A686 CAEE # HANGUL SYLLABLE SSANGCIEUC-WA-CIEUC A687 CAEF # HANGUL SYLLABLE SSANGCIEUC-WA-CHIEUCH A688 CAF0 # HANGUL SYLLABLE SSANGCIEUC-WA-KHIEUKH A689 CAF1 # HANGUL SYLLABLE SSANGCIEUC-WA-THIEUTH A68A CAF2 # HANGUL SYLLABLE SSANGCIEUC-WA-PHIEUPH A68B CAF3 # HANGUL SYLLABLE SSANGCIEUC-WA-HIEUH A68C CAF5 # HANGUL SYLLABLE SSANGCIEUC-WAE-KIYEOK A68D CAF6 # HANGUL SYLLABLE SSANGCIEUC-WAE-SSANGKIYEOK A68E CAF7 # HANGUL SYLLABLE SSANGCIEUC-WAE-KIYEOKSIOS A68F CAF8 # HANGUL SYLLABLE SSANGCIEUC-WAE-NIEUN A690 CAF9 # HANGUL SYLLABLE SSANGCIEUC-WAE-NIEUNCIEUC A691 CAFA # HANGUL SYLLABLE SSANGCIEUC-WAE-NIEUNHIEUH A692 CAFB # HANGUL SYLLABLE SSANGCIEUC-WAE-TIKEUT A693 CAFC # HANGUL SYLLABLE SSANGCIEUC-WAE-RIEUL A694 CAFD # HANGUL SYLLABLE SSANGCIEUC-WAE-RIEULKIYEOK A695 CAFE # HANGUL SYLLABLE SSANGCIEUC-WAE-RIEULMIEUM A696 CAFF # HANGUL SYLLABLE SSANGCIEUC-WAE-RIEULPIEUP A697 CB00 # HANGUL SYLLABLE SSANGCIEUC-WAE-RIEULSIOS A698 CB01 # HANGUL SYLLABLE SSANGCIEUC-WAE-RIEULTHIEUTH A699 CB02 # HANGUL SYLLABLE SSANGCIEUC-WAE-RIEULPHIEUPH A69A CB03 # HANGUL SYLLABLE SSANGCIEUC-WAE-RIEULHIEUH A69B CB04 # HANGUL SYLLABLE SSANGCIEUC-WAE-MIEUM A69C CB05 # HANGUL SYLLABLE SSANGCIEUC-WAE-PIEUP A69D CB06 # HANGUL SYLLABLE SSANGCIEUC-WAE-PIEUPSIOS A69E CB07 # HANGUL SYLLABLE SSANGCIEUC-WAE-SIOS A69F CB09 # HANGUL SYLLABLE SSANGCIEUC-WAE-IEUNG A6A0 CB0A # HANGUL SYLLABLE SSANGCIEUC-WAE-CIEUC A6A1 2500 # BOX DRAWINGS LIGHT HORIZONTAL A6A2 2502 # BOX DRAWINGS LIGHT VERTICAL A6A3 250C # BOX DRAWINGS LIGHT DOWN AND RIGHT A6A4 2510 # BOX DRAWINGS LIGHT DOWN AND LEFT A6A5 2518 # BOX DRAWINGS LIGHT UP AND LEFT A6A6 2514 # BOX DRAWINGS LIGHT UP AND RIGHT A6A7 251C # BOX DRAWINGS LIGHT VERTICAL AND RIGHT A6A8 252C # BOX DRAWINGS LIGHT DOWN AND HORIZONTAL A6A9 2524 # BOX DRAWINGS LIGHT VERTICAL AND LEFT A6AA 2534 # BOX DRAWINGS LIGHT UP AND HORIZONTAL A6AB 253C # BOX DRAWINGS LIGHT VERTICAL AND HORIZONTAL A6AC 2501 # BOX DRAWINGS HEAVY HORIZONTAL A6AD 2503 # BOX DRAWINGS HEAVY VERTICAL A6AE 250F # BOX DRAWINGS HEAVY DOWN AND RIGHT A6AF 2513 # BOX DRAWINGS HEAVY DOWN AND LEFT A6B0 251B # BOX DRAWINGS HEAVY UP AND LEFT A6B1 2517 # BOX DRAWINGS HEAVY UP AND RIGHT A6B2 2523 # BOX DRAWINGS HEAVY VERTICAL AND RIGHT A6B3 2533 # BOX DRAWINGS HEAVY DOWN AND HORIZONTAL A6B4 252B # BOX DRAWINGS HEAVY VERTICAL AND LEFT A6B5 253B # BOX DRAWINGS HEAVY UP AND HORIZONTAL A6B6 254B # BOX DRAWINGS HEAVY VERTICAL AND HORIZONTAL A6B7 2520 # BOX DRAWINGS VERTICAL HEAVY AND RIGHT LIGHT A6B8 252F # BOX DRAWINGS DOWN LIGHT AND HORIZONTAL HEAVY A6B9 2528 # BOX DRAWINGS VERTICAL HEAVY AND LEFT LIGHT A6BA 2537 # BOX DRAWINGS UP LIGHT AND HORIZONTAL HEAVY A6BB 253F # BOX DRAWINGS VERTICAL LIGHT AND HORIZONTAL HEAVY A6BC 251D # BOX DRAWINGS VERTICAL LIGHT AND RIGHT HEAVY A6BD 2530 # BOX DRAWINGS DOWN HEAVY AND HORIZONTAL LIGHT A6BE 2525 # BOX DRAWINGS VERTICAL LIGHT AND LEFT HEAVY A6BF 2538 # BOX DRAWINGS UP HEAVY AND HORIZONTAL LIGHT A6C0 2542 # BOX DRAWINGS VERTICAL HEAVY AND HORIZONTAL LIGHT A6C1 2512 # BOX DRAWINGS DOWN HEAVY AND LEFT LIGHT A6C2 2511 # BOX DRAWINGS DOWN LIGHT AND LEFT HEAVY A6C3 251A # BOX DRAWINGS UP HEAVY AND LEFT LIGHT A6C4 2519 # BOX DRAWINGS UP LIGHT AND LEFT HEAVY A6C5 2516 # BOX DRAWINGS UP HEAVY AND RIGHT LIGHT A6C6 2515 # BOX DRAWINGS UP LIGHT AND RIGHT HEAVY A6C7 250E # BOX DRAWINGS DOWN HEAVY AND RIGHT LIGHT A6C8 250D # BOX DRAWINGS DOWN LIGHT AND RIGHT HEAVY A6C9 251E # BOX DRAWINGS UP HEAVY AND RIGHT DOWN LIGHT A6CA 251F # BOX DRAWINGS DOWN HEAVY AND RIGHT UP LIGHT A6CB 2521 # BOX DRAWINGS DOWN LIGHT AND RIGHT UP HEAVY A6CC 2522 # BOX DRAWINGS UP LIGHT AND RIGHT DOWN HEAVY A6CD 2526 # BOX DRAWINGS UP HEAVY AND LEFT DOWN LIGHT A6CE 2527 # BOX DRAWINGS DOWN HEAVY AND LEFT UP LIGHT A6CF 2529 # BOX DRAWINGS DOWN LIGHT AND LEFT UP HEAVY A6D0 252A # BOX DRAWINGS UP LIGHT AND LEFT DOWN HEAVY A6D1 252D # BOX DRAWINGS LEFT HEAVY AND RIGHT DOWN LIGHT A6D2 252E # BOX DRAWINGS RIGHT HEAVY AND LEFT DOWN LIGHT A6D3 2531 # BOX DRAWINGS RIGHT LIGHT AND LEFT DOWN HEAVY A6D4 2532 # BOX DRAWINGS LEFT LIGHT AND RIGHT DOWN HEAVY A6D5 2535 # BOX DRAWINGS LEFT HEAVY AND RIGHT UP LIGHT A6D6 2536 # BOX DRAWINGS RIGHT HEAVY AND LEFT UP LIGHT A6D7 2539 # BOX DRAWINGS RIGHT LIGHT AND LEFT UP HEAVY A6D8 253A # BOX DRAWINGS LEFT LIGHT AND RIGHT UP HEAVY A6D9 253D # BOX DRAWINGS LEFT HEAVY AND RIGHT VERTICAL LIGHT A6DA 253E # BOX DRAWINGS RIGHT HEAVY AND LEFT VERTICAL LIGHT A6DB 2540 # BOX DRAWINGS UP HEAVY AND DOWN HORIZONTAL LIGHT A6DC 2541 # BOX DRAWINGS DOWN HEAVY AND UP HORIZONTAL LIGHT A6DD 2543 # BOX DRAWINGS LEFT UP HEAVY AND RIGHT DOWN LIGHT A6DE 2544 # BOX DRAWINGS RIGHT UP HEAVY AND LEFT DOWN LIGHT A6DF 2545 # BOX DRAWINGS LEFT DOWN HEAVY AND RIGHT UP LIGHT A6E0 2546 # BOX DRAWINGS RIGHT DOWN HEAVY AND LEFT UP LIGHT A6E1 2547 # BOX DRAWINGS DOWN LIGHT AND UP HORIZONTAL HEAVY A6E2 2548 # BOX DRAWINGS UP LIGHT AND DOWN HORIZONTAL HEAVY A6E3 2549 # BOX DRAWINGS RIGHT LIGHT AND LEFT VERTICAL HEAVY A6E4 254A # BOX DRAWINGS LEFT LIGHT AND RIGHT VERTICAL HEAVY A741 CB0B # HANGUL SYLLABLE SSANGCIEUC-WAE-CHIEUCH A742 CB0C # HANGUL SYLLABLE SSANGCIEUC-WAE-KHIEUKH A743 CB0D # HANGUL SYLLABLE SSANGCIEUC-WAE-THIEUTH A744 CB0E # HANGUL SYLLABLE SSANGCIEUC-WAE-PHIEUPH A745 CB0F # HANGUL SYLLABLE SSANGCIEUC-WAE-HIEUH A746 CB11 # HANGUL SYLLABLE SSANGCIEUC-OE-KIYEOK A747 CB12 # HANGUL SYLLABLE SSANGCIEUC-OE-SSANGKIYEOK A748 CB13 # HANGUL SYLLABLE SSANGCIEUC-OE-KIYEOKSIOS A749 CB15 # HANGUL SYLLABLE SSANGCIEUC-OE-NIEUNCIEUC A74A CB16 # HANGUL SYLLABLE SSANGCIEUC-OE-NIEUNHIEUH A74B CB17 # HANGUL SYLLABLE SSANGCIEUC-OE-TIKEUT A74C CB19 # HANGUL SYLLABLE SSANGCIEUC-OE-RIEULKIYEOK A74D CB1A # HANGUL SYLLABLE SSANGCIEUC-OE-RIEULMIEUM A74E CB1B # HANGUL SYLLABLE SSANGCIEUC-OE-RIEULPIEUP A74F CB1C # HANGUL SYLLABLE SSANGCIEUC-OE-RIEULSIOS A750 CB1D # HANGUL SYLLABLE SSANGCIEUC-OE-RIEULTHIEUTH A751 CB1E # HANGUL SYLLABLE SSANGCIEUC-OE-RIEULPHIEUPH A752 CB1F # HANGUL SYLLABLE SSANGCIEUC-OE-RIEULHIEUH A753 CB22 # HANGUL SYLLABLE SSANGCIEUC-OE-PIEUPSIOS A754 CB23 # HANGUL SYLLABLE SSANGCIEUC-OE-SIOS A755 CB24 # HANGUL SYLLABLE SSANGCIEUC-OE-SSANGSIOS A756 CB25 # HANGUL SYLLABLE SSANGCIEUC-OE-IEUNG A757 CB26 # HANGUL SYLLABLE SSANGCIEUC-OE-CIEUC A758 CB27 # HANGUL SYLLABLE SSANGCIEUC-OE-CHIEUCH A759 CB28 # HANGUL SYLLABLE SSANGCIEUC-OE-KHIEUKH A75A CB29 # HANGUL SYLLABLE SSANGCIEUC-OE-THIEUTH A761 CB2A # HANGUL SYLLABLE SSANGCIEUC-OE-PHIEUPH A762 CB2B # HANGUL SYLLABLE SSANGCIEUC-OE-HIEUH A763 CB2C # HANGUL SYLLABLE SSANGCIEUC-YO A764 CB2D # HANGUL SYLLABLE SSANGCIEUC-YO-KIYEOK A765 CB2E # HANGUL SYLLABLE SSANGCIEUC-YO-SSANGKIYEOK A766 CB2F # HANGUL SYLLABLE SSANGCIEUC-YO-KIYEOKSIOS A767 CB30 # HANGUL SYLLABLE SSANGCIEUC-YO-NIEUN A768 CB31 # HANGUL SYLLABLE SSANGCIEUC-YO-NIEUNCIEUC A769 CB32 # HANGUL SYLLABLE SSANGCIEUC-YO-NIEUNHIEUH A76A CB33 # HANGUL SYLLABLE SSANGCIEUC-YO-TIKEUT A76B CB34 # HANGUL SYLLABLE SSANGCIEUC-YO-RIEUL A76C CB35 # HANGUL SYLLABLE SSANGCIEUC-YO-RIEULKIYEOK A76D CB36 # HANGUL SYLLABLE SSANGCIEUC-YO-RIEULMIEUM A76E CB37 # HANGUL SYLLABLE SSANGCIEUC-YO-RIEULPIEUP A76F CB38 # HANGUL SYLLABLE SSANGCIEUC-YO-RIEULSIOS A770 CB39 # HANGUL SYLLABLE SSANGCIEUC-YO-RIEULTHIEUTH A771 CB3A # HANGUL SYLLABLE SSANGCIEUC-YO-RIEULPHIEUPH A772 CB3B # HANGUL SYLLABLE SSANGCIEUC-YO-RIEULHIEUH A773 CB3C # HANGUL SYLLABLE SSANGCIEUC-YO-MIEUM A774 CB3D # HANGUL SYLLABLE SSANGCIEUC-YO-PIEUP A775 CB3E # HANGUL SYLLABLE SSANGCIEUC-YO-PIEUPSIOS A776 CB3F # HANGUL SYLLABLE SSANGCIEUC-YO-SIOS A777 CB40 # HANGUL SYLLABLE SSANGCIEUC-YO-SSANGSIOS A778 CB42 # HANGUL SYLLABLE SSANGCIEUC-YO-CIEUC A779 CB43 # HANGUL SYLLABLE SSANGCIEUC-YO-CHIEUCH A77A CB44 # HANGUL SYLLABLE SSANGCIEUC-YO-KHIEUKH A781 CB45 # HANGUL SYLLABLE SSANGCIEUC-YO-THIEUTH A782 CB46 # HANGUL SYLLABLE SSANGCIEUC-YO-PHIEUPH A783 CB47 # HANGUL SYLLABLE SSANGCIEUC-YO-HIEUH A784 CB4A # HANGUL SYLLABLE SSANGCIEUC-U-SSANGKIYEOK A785 CB4B # HANGUL SYLLABLE SSANGCIEUC-U-KIYEOKSIOS A786 CB4D # HANGUL SYLLABLE SSANGCIEUC-U-NIEUNCIEUC A787 CB4E # HANGUL SYLLABLE SSANGCIEUC-U-NIEUNHIEUH A788 CB4F # HANGUL SYLLABLE SSANGCIEUC-U-TIKEUT A789 CB51 # HANGUL SYLLABLE SSANGCIEUC-U-RIEULKIYEOK A78A CB52 # HANGUL SYLLABLE SSANGCIEUC-U-RIEULMIEUM A78B CB53 # HANGUL SYLLABLE SSANGCIEUC-U-RIEULPIEUP A78C CB54 # HANGUL SYLLABLE SSANGCIEUC-U-RIEULSIOS A78D CB55 # HANGUL SYLLABLE SSANGCIEUC-U-RIEULTHIEUTH A78E CB56 # HANGUL SYLLABLE SSANGCIEUC-U-RIEULPHIEUPH A78F CB57 # HANGUL SYLLABLE SSANGCIEUC-U-RIEULHIEUH A790 CB5A # HANGUL SYLLABLE SSANGCIEUC-U-PIEUPSIOS A791 CB5B # HANGUL SYLLABLE SSANGCIEUC-U-SIOS A792 CB5C # HANGUL SYLLABLE SSANGCIEUC-U-SSANGSIOS A793 CB5E # HANGUL SYLLABLE SSANGCIEUC-U-CIEUC A794 CB5F # HANGUL SYLLABLE SSANGCIEUC-U-CHIEUCH A795 CB60 # HANGUL SYLLABLE SSANGCIEUC-U-KHIEUKH A796 CB61 # HANGUL SYLLABLE SSANGCIEUC-U-THIEUTH A797 CB62 # HANGUL SYLLABLE SSANGCIEUC-U-PHIEUPH A798 CB63 # HANGUL SYLLABLE SSANGCIEUC-U-HIEUH A799 CB65 # HANGUL SYLLABLE SSANGCIEUC-WEO-KIYEOK A79A CB66 # HANGUL SYLLABLE SSANGCIEUC-WEO-SSANGKIYEOK A79B CB67 # HANGUL SYLLABLE SSANGCIEUC-WEO-KIYEOKSIOS A79C CB68 # HANGUL SYLLABLE SSANGCIEUC-WEO-NIEUN A79D CB69 # HANGUL SYLLABLE SSANGCIEUC-WEO-NIEUNCIEUC A79E CB6A # HANGUL SYLLABLE SSANGCIEUC-WEO-NIEUNHIEUH A79F CB6B # HANGUL SYLLABLE SSANGCIEUC-WEO-TIKEUT A7A0 CB6C # HANGUL SYLLABLE SSANGCIEUC-WEO-RIEUL A7A1 3395 # SQUARE MU L A7A2 3396 # SQUARE ML A7A3 3397 # SQUARE DL A7A4 2113 # SCRIPT SMALL L A7A5 3398 # SQUARE KL A7A6 33C4 # SQUARE CC A7A7 33A3 # SQUARE MM CUBED A7A8 33A4 # SQUARE CM CUBED A7A9 33A5 # SQUARE M CUBED A7AA 33A6 # SQUARE KM CUBED A7AB 3399 # SQUARE FM A7AC 339A # SQUARE NM A7AD 339B # SQUARE MU M A7AE 339C # SQUARE MM A7AF 339D # SQUARE CM A7B0 339E # SQUARE KM A7B1 339F # SQUARE MM SQUARED A7B2 33A0 # SQUARE CM SQUARED A7B3 33A1 # SQUARE M SQUARED A7B4 33A2 # SQUARE KM SQUARED A7B5 33CA # SQUARE HA A7B6 338D # SQUARE MU G A7B7 338E # SQUARE MG A7B8 338F # SQUARE KG A7B9 33CF # SQUARE KT A7BA 3388 # SQUARE CAL A7BB 3389 # SQUARE KCAL A7BC 33C8 # SQUARE DB A7BD 33A7 # SQUARE M OVER S A7BE 33A8 # SQUARE M OVER S SQUARED A7BF 33B0 # SQUARE PS A7C0 33B1 # SQUARE NS A7C1 33B2 # SQUARE MU S A7C2 33B3 # SQUARE MS A7C3 33B4 # SQUARE PV A7C4 33B5 # SQUARE NV A7C5 33B6 # SQUARE MU V A7C6 33B7 # SQUARE MV A7C7 33B8 # SQUARE KV A7C8 33B9 # SQUARE MV MEGA A7C9 3380 # SQUARE PA AMPS A7CA 3381 # SQUARE NA A7CB 3382 # SQUARE MU A A7CC 3383 # SQUARE MA A7CD 3384 # SQUARE KA A7CE 33BA # SQUARE PW A7CF 33BB # SQUARE NW A7D0 33BC # SQUARE MU W A7D1 33BD # SQUARE MW A7D2 33BE # SQUARE KW A7D3 33BF # SQUARE MW MEGA A7D4 3390 # SQUARE HZ A7D5 3391 # SQUARE KHZ A7D6 3392 # SQUARE MHZ A7D7 3393 # SQUARE GHZ A7D8 3394 # SQUARE THZ A7D9 2126 # OHM SIGN A7DA 33C0 # SQUARE K OHM A7DB 33C1 # SQUARE M OHM A7DC 338A # SQUARE PF A7DD 338B # SQUARE NF A7DE 338C # SQUARE MU F A7DF 33D6 # SQUARE MOL A7E0 33C5 # SQUARE CD A7E1 33AD # SQUARE RAD A7E2 33AE # SQUARE RAD OVER S A7E3 33AF # SQUARE RAD OVER S SQUARED A7E4 33DB # SQUARE SR A7E5 33A9 # SQUARE PA A7E6 33AA # SQUARE KPA A7E7 33AB # SQUARE MPA A7E8 33AC # SQUARE GPA A7E9 33DD # SQUARE WB A7EA 33D0 # SQUARE LM A7EB 33D3 # SQUARE LX A7EC 33C3 # SQUARE BQ A7ED 33C9 # SQUARE GY A7EE 33DC # SQUARE SV A7EF 33C6 # SQUARE C OVER KG A841 CB6D # HANGUL SYLLABLE SSANGCIEUC-WEO-RIEULKIYEOK A842 CB6E # HANGUL SYLLABLE SSANGCIEUC-WEO-RIEULMIEUM A843 CB6F # HANGUL SYLLABLE SSANGCIEUC-WEO-RIEULPIEUP A844 CB70 # HANGUL SYLLABLE SSANGCIEUC-WEO-RIEULSIOS A845 CB71 # HANGUL SYLLABLE SSANGCIEUC-WEO-RIEULTHIEUTH A846 CB72 # HANGUL SYLLABLE SSANGCIEUC-WEO-RIEULPHIEUPH A847 CB73 # HANGUL SYLLABLE SSANGCIEUC-WEO-RIEULHIEUH A848 CB74 # HANGUL SYLLABLE SSANGCIEUC-WEO-MIEUM A849 CB75 # HANGUL SYLLABLE SSANGCIEUC-WEO-PIEUP A84A CB76 # HANGUL SYLLABLE SSANGCIEUC-WEO-PIEUPSIOS A84B CB77 # HANGUL SYLLABLE SSANGCIEUC-WEO-SIOS A84C CB7A # HANGUL SYLLABLE SSANGCIEUC-WEO-CIEUC A84D CB7B # HANGUL SYLLABLE SSANGCIEUC-WEO-CHIEUCH A84E CB7C # HANGUL SYLLABLE SSANGCIEUC-WEO-KHIEUKH A84F CB7D # HANGUL SYLLABLE SSANGCIEUC-WEO-THIEUTH A850 CB7E # HANGUL SYLLABLE SSANGCIEUC-WEO-PHIEUPH A851 CB7F # HANGUL SYLLABLE SSANGCIEUC-WEO-HIEUH A852 CB80 # HANGUL SYLLABLE SSANGCIEUC-WE A853 CB81 # HANGUL SYLLABLE SSANGCIEUC-WE-KIYEOK A854 CB82 # HANGUL SYLLABLE SSANGCIEUC-WE-SSANGKIYEOK A855 CB83 # HANGUL SYLLABLE SSANGCIEUC-WE-KIYEOKSIOS A856 CB84 # HANGUL SYLLABLE SSANGCIEUC-WE-NIEUN A857 CB85 # HANGUL SYLLABLE SSANGCIEUC-WE-NIEUNCIEUC A858 CB86 # HANGUL SYLLABLE SSANGCIEUC-WE-NIEUNHIEUH A859 CB87 # HANGUL SYLLABLE SSANGCIEUC-WE-TIKEUT A85A CB88 # HANGUL SYLLABLE SSANGCIEUC-WE-RIEUL A861 CB89 # HANGUL SYLLABLE SSANGCIEUC-WE-RIEULKIYEOK A862 CB8A # HANGUL SYLLABLE SSANGCIEUC-WE-RIEULMIEUM A863 CB8B # HANGUL SYLLABLE SSANGCIEUC-WE-RIEULPIEUP A864 CB8C # HANGUL SYLLABLE SSANGCIEUC-WE-RIEULSIOS A865 CB8D # HANGUL SYLLABLE SSANGCIEUC-WE-RIEULTHIEUTH A866 CB8E # HANGUL SYLLABLE SSANGCIEUC-WE-RIEULPHIEUPH A867 CB8F # HANGUL SYLLABLE SSANGCIEUC-WE-RIEULHIEUH A868 CB90 # HANGUL SYLLABLE SSANGCIEUC-WE-MIEUM A869 CB91 # HANGUL SYLLABLE SSANGCIEUC-WE-PIEUP A86A CB92 # HANGUL SYLLABLE SSANGCIEUC-WE-PIEUPSIOS A86B CB93 # HANGUL SYLLABLE SSANGCIEUC-WE-SIOS A86C CB94 # HANGUL SYLLABLE SSANGCIEUC-WE-SSANGSIOS A86D CB95 # HANGUL SYLLABLE SSANGCIEUC-WE-IEUNG A86E CB96 # HANGUL SYLLABLE SSANGCIEUC-WE-CIEUC A86F CB97 # HANGUL SYLLABLE SSANGCIEUC-WE-CHIEUCH A870 CB98 # HANGUL SYLLABLE SSANGCIEUC-WE-KHIEUKH A871 CB99 # HANGUL SYLLABLE SSANGCIEUC-WE-THIEUTH A872 CB9A # HANGUL SYLLABLE SSANGCIEUC-WE-PHIEUPH A873 CB9B # HANGUL SYLLABLE SSANGCIEUC-WE-HIEUH A874 CB9D # HANGUL SYLLABLE SSANGCIEUC-WI-KIYEOK A875 CB9E # HANGUL SYLLABLE SSANGCIEUC-WI-SSANGKIYEOK A876 CB9F # HANGUL SYLLABLE SSANGCIEUC-WI-KIYEOKSIOS A877 CBA0 # HANGUL SYLLABLE SSANGCIEUC-WI-NIEUN A878 CBA1 # HANGUL SYLLABLE SSANGCIEUC-WI-NIEUNCIEUC A879 CBA2 # HANGUL SYLLABLE SSANGCIEUC-WI-NIEUNHIEUH A87A CBA3 # HANGUL SYLLABLE SSANGCIEUC-WI-TIKEUT A881 CBA4 # HANGUL SYLLABLE SSANGCIEUC-WI-RIEUL A882 CBA5 # HANGUL SYLLABLE SSANGCIEUC-WI-RIEULKIYEOK A883 CBA6 # HANGUL SYLLABLE SSANGCIEUC-WI-RIEULMIEUM A884 CBA7 # HANGUL SYLLABLE SSANGCIEUC-WI-RIEULPIEUP A885 CBA8 # HANGUL SYLLABLE SSANGCIEUC-WI-RIEULSIOS A886 CBA9 # HANGUL SYLLABLE SSANGCIEUC-WI-RIEULTHIEUTH A887 CBAA # HANGUL SYLLABLE SSANGCIEUC-WI-RIEULPHIEUPH A888 CBAB # HANGUL SYLLABLE SSANGCIEUC-WI-RIEULHIEUH A889 CBAC # HANGUL SYLLABLE SSANGCIEUC-WI-MIEUM A88A CBAD # HANGUL SYLLABLE SSANGCIEUC-WI-PIEUP A88B CBAE # HANGUL SYLLABLE SSANGCIEUC-WI-PIEUPSIOS A88C CBAF # HANGUL SYLLABLE SSANGCIEUC-WI-SIOS A88D CBB0 # HANGUL SYLLABLE SSANGCIEUC-WI-SSANGSIOS A88E CBB1 # HANGUL SYLLABLE SSANGCIEUC-WI-IEUNG A88F CBB2 # HANGUL SYLLABLE SSANGCIEUC-WI-CIEUC A890 CBB3 # HANGUL SYLLABLE SSANGCIEUC-WI-CHIEUCH A891 CBB4 # HANGUL SYLLABLE SSANGCIEUC-WI-KHIEUKH A892 CBB5 # HANGUL SYLLABLE SSANGCIEUC-WI-THIEUTH A893 CBB6 # HANGUL SYLLABLE SSANGCIEUC-WI-PHIEUPH A894 CBB7 # HANGUL SYLLABLE SSANGCIEUC-WI-HIEUH A895 CBB9 # HANGUL SYLLABLE SSANGCIEUC-YU-KIYEOK A896 CBBA # HANGUL SYLLABLE SSANGCIEUC-YU-SSANGKIYEOK A897 CBBB # HANGUL SYLLABLE SSANGCIEUC-YU-KIYEOKSIOS A898 CBBC # HANGUL SYLLABLE SSANGCIEUC-YU-NIEUN A899 CBBD # HANGUL SYLLABLE SSANGCIEUC-YU-NIEUNCIEUC A89A CBBE # HANGUL SYLLABLE SSANGCIEUC-YU-NIEUNHIEUH A89B CBBF # HANGUL SYLLABLE SSANGCIEUC-YU-TIKEUT A89C CBC0 # HANGUL SYLLABLE SSANGCIEUC-YU-RIEUL A89D CBC1 # HANGUL SYLLABLE SSANGCIEUC-YU-RIEULKIYEOK A89E CBC2 # HANGUL SYLLABLE SSANGCIEUC-YU-RIEULMIEUM A89F CBC3 # HANGUL SYLLABLE SSANGCIEUC-YU-RIEULPIEUP A8A0 CBC4 # HANGUL SYLLABLE SSANGCIEUC-YU-RIEULSIOS A8A1 00C6 # LATIN CAPITAL LIGATURE AE A8A2 00D0 # LATIN CAPITAL LETTER ETH A8A3 00AA # FEMININE ORDINAL INDICATOR A8A4 0126 # LATIN CAPITAL LETTER H WITH STROKE A8A6 0132 # LATIN CAPITAL LIGATURE IJ A8A8 013F # LATIN CAPITAL LETTER L WITH MIDDLE DOT A8A9 0141 # LATIN CAPITAL LETTER L WITH STROKE A8AA 00D8 # LATIN CAPITAL LETTER O WITH STROKE A8AB 0152 # LATIN CAPITAL LIGATURE OE A8AC 00BA # MASCULINE ORDINAL INDICATOR A8AD 00DE # LATIN CAPITAL LETTER THORN A8AE 0166 # LATIN CAPITAL LETTER T WITH STROKE A8AF 014A # LATIN CAPITAL LETTER ENG A8B1 3260 # CIRCLED HANGUL KIYEOK A8B2 3261 # CIRCLED HANGUL NIEUN A8B3 3262 # CIRCLED HANGUL TIKEUT A8B4 3263 # CIRCLED HANGUL RIEUL A8B5 3264 # CIRCLED HANGUL MIEUM A8B6 3265 # CIRCLED HANGUL PIEUP A8B7 3266 # CIRCLED HANGUL SIOS A8B8 3267 # CIRCLED HANGUL IEUNG A8B9 3268 # CIRCLED HANGUL CIEUC A8BA 3269 # CIRCLED HANGUL CHIEUCH A8BB 326A # CIRCLED HANGUL KHIEUKH A8BC 326B # CIRCLED HANGUL THIEUTH A8BD 326C # CIRCLED HANGUL PHIEUPH A8BE 326D # CIRCLED HANGUL HIEUH A8BF 326E # CIRCLED HANGUL KIYEOK A A8C0 326F # CIRCLED HANGUL NIEUN A A8C1 3270 # CIRCLED HANGUL TIKEUT A A8C2 3271 # CIRCLED HANGUL RIEUL A A8C3 3272 # CIRCLED HANGUL MIEUM A A8C4 3273 # CIRCLED HANGUL PIEUP A A8C5 3274 # CIRCLED HANGUL SIOS A A8C6 3275 # CIRCLED HANGUL IEUNG A A8C7 3276 # CIRCLED HANGUL CIEUC A A8C8 3277 # CIRCLED HANGUL CHIEUCH A A8C9 3278 # CIRCLED HANGUL KHIEUKH A A8CA 3279 # CIRCLED HANGUL THIEUTH A A8CB 327A # CIRCLED HANGUL PHIEUPH A A8CC 327B # CIRCLED HANGUL HIEUH A A8CD 24D0 # CIRCLED LATIN SMALL LETTER A A8CE 24D1 # CIRCLED LATIN SMALL LETTER B A8CF 24D2 # CIRCLED LATIN SMALL LETTER C A8D0 24D3 # CIRCLED LATIN SMALL LETTER D A8D1 24D4 # CIRCLED LATIN SMALL LETTER E A8D2 24D5 # CIRCLED LATIN SMALL LETTER F A8D3 24D6 # CIRCLED LATIN SMALL LETTER G A8D4 24D7 # CIRCLED LATIN SMALL LETTER H A8D5 24D8 # CIRCLED LATIN SMALL LETTER I A8D6 24D9 # CIRCLED LATIN SMALL LETTER J A8D7 24DA # CIRCLED LATIN SMALL LETTER K A8D8 24DB # CIRCLED LATIN SMALL LETTER L A8D9 24DC # CIRCLED LATIN SMALL LETTER M A8DA 24DD # CIRCLED LATIN SMALL LETTER N A8DB 24DE # CIRCLED LATIN SMALL LETTER O A8DC 24DF # CIRCLED LATIN SMALL LETTER P A8DD 24E0 # CIRCLED LATIN SMALL LETTER Q A8DE 24E1 # CIRCLED LATIN SMALL LETTER R A8DF 24E2 # CIRCLED LATIN SMALL LETTER S A8E0 24E3 # CIRCLED LATIN SMALL LETTER T A8E1 24E4 # CIRCLED LATIN SMALL LETTER U A8E2 24E5 # CIRCLED LATIN SMALL LETTER V A8E3 24E6 # CIRCLED LATIN SMALL LETTER W A8E4 24E7 # CIRCLED LATIN SMALL LETTER X A8E5 24E8 # CIRCLED LATIN SMALL LETTER Y A8E6 24E9 # CIRCLED LATIN SMALL LETTER Z A8E7 2460 # CIRCLED DIGIT ONE A8E8 2461 # CIRCLED DIGIT TWO A8E9 2462 # CIRCLED DIGIT THREE A8EA 2463 # CIRCLED DIGIT FOUR A8EB 2464 # CIRCLED DIGIT FIVE A8EC 2465 # CIRCLED DIGIT SIX A8ED 2466 # CIRCLED DIGIT SEVEN A8EE 2467 # CIRCLED DIGIT EIGHT A8EF 2468 # CIRCLED DIGIT NINE A8F0 2469 # CIRCLED NUMBER TEN A8F1 246A # CIRCLED NUMBER ELEVEN A8F2 246B # CIRCLED NUMBER TWELVE A8F3 246C # CIRCLED NUMBER THIRTEEN A8F4 246D # CIRCLED NUMBER FOURTEEN A8F5 246E # CIRCLED NUMBER FIFTEEN A8F6 00BD # VULGAR FRACTION ONE HALF A8F7 2153 # VULGAR FRACTION ONE THIRD A8F8 2154 # VULGAR FRACTION TWO THIRDS A8F9 00BC # VULGAR FRACTION ONE QUARTER A8FA 00BE # VULGAR FRACTION THREE QUARTERS A8FB 215B # VULGAR FRACTION ONE EIGHTH A8FC 215C # VULGAR FRACTION THREE EIGHTHS A8FD 215D # VULGAR FRACTION FIVE EIGHTHS A8FE 215E # VULGAR FRACTION SEVEN EIGHTHS A941 CBC5 # HANGUL SYLLABLE SSANGCIEUC-YU-RIEULTHIEUTH A942 CBC6 # HANGUL SYLLABLE SSANGCIEUC-YU-RIEULPHIEUPH A943 CBC7 # HANGUL SYLLABLE SSANGCIEUC-YU-RIEULHIEUH A944 CBC8 # HANGUL SYLLABLE SSANGCIEUC-YU-MIEUM A945 CBC9 # HANGUL SYLLABLE SSANGCIEUC-YU-PIEUP A946 CBCA # HANGUL SYLLABLE SSANGCIEUC-YU-PIEUPSIOS A947 CBCB # HANGUL SYLLABLE SSANGCIEUC-YU-SIOS A948 CBCC # HANGUL SYLLABLE SSANGCIEUC-YU-SSANGSIOS A949 CBCD # HANGUL SYLLABLE SSANGCIEUC-YU-IEUNG A94A CBCE # HANGUL SYLLABLE SSANGCIEUC-YU-CIEUC A94B CBCF # HANGUL SYLLABLE SSANGCIEUC-YU-CHIEUCH A94C CBD0 # HANGUL SYLLABLE SSANGCIEUC-YU-KHIEUKH A94D CBD1 # HANGUL SYLLABLE SSANGCIEUC-YU-THIEUTH A94E CBD2 # HANGUL SYLLABLE SSANGCIEUC-YU-PHIEUPH A94F CBD3 # HANGUL SYLLABLE SSANGCIEUC-YU-HIEUH A950 CBD5 # HANGUL SYLLABLE SSANGCIEUC-EU-KIYEOK A951 CBD6 # HANGUL SYLLABLE SSANGCIEUC-EU-SSANGKIYEOK A952 CBD7 # HANGUL SYLLABLE SSANGCIEUC-EU-KIYEOKSIOS A953 CBD8 # HANGUL SYLLABLE SSANGCIEUC-EU-NIEUN A954 CBD9 # HANGUL SYLLABLE SSANGCIEUC-EU-NIEUNCIEUC A955 CBDA # HANGUL SYLLABLE SSANGCIEUC-EU-NIEUNHIEUH A956 CBDB # HANGUL SYLLABLE SSANGCIEUC-EU-TIKEUT A957 CBDC # HANGUL SYLLABLE SSANGCIEUC-EU-RIEUL A958 CBDD # HANGUL SYLLABLE SSANGCIEUC-EU-RIEULKIYEOK A959 CBDE # HANGUL SYLLABLE SSANGCIEUC-EU-RIEULMIEUM A95A CBDF # HANGUL SYLLABLE SSANGCIEUC-EU-RIEULPIEUP A961 CBE0 # HANGUL SYLLABLE SSANGCIEUC-EU-RIEULSIOS A962 CBE1 # HANGUL SYLLABLE SSANGCIEUC-EU-RIEULTHIEUTH A963 CBE2 # HANGUL SYLLABLE SSANGCIEUC-EU-RIEULPHIEUPH A964 CBE3 # HANGUL SYLLABLE SSANGCIEUC-EU-RIEULHIEUH A965 CBE5 # HANGUL SYLLABLE SSANGCIEUC-EU-PIEUP A966 CBE6 # HANGUL SYLLABLE SSANGCIEUC-EU-PIEUPSIOS A967 CBE8 # HANGUL SYLLABLE SSANGCIEUC-EU-SSANGSIOS A968 CBEA # HANGUL SYLLABLE SSANGCIEUC-EU-CIEUC A969 CBEB # HANGUL SYLLABLE SSANGCIEUC-EU-CHIEUCH A96A CBEC # HANGUL SYLLABLE SSANGCIEUC-EU-KHIEUKH A96B CBED # HANGUL SYLLABLE SSANGCIEUC-EU-THIEUTH A96C CBEE # HANGUL SYLLABLE SSANGCIEUC-EU-PHIEUPH A96D CBEF # HANGUL SYLLABLE SSANGCIEUC-EU-HIEUH A96E CBF0 # HANGUL SYLLABLE SSANGCIEUC-YI A96F CBF1 # HANGUL SYLLABLE SSANGCIEUC-YI-KIYEOK A970 CBF2 # HANGUL SYLLABLE SSANGCIEUC-YI-SSANGKIYEOK A971 CBF3 # HANGUL SYLLABLE SSANGCIEUC-YI-KIYEOKSIOS A972 CBF4 # HANGUL SYLLABLE SSANGCIEUC-YI-NIEUN A973 CBF5 # HANGUL SYLLABLE SSANGCIEUC-YI-NIEUNCIEUC A974 CBF6 # HANGUL SYLLABLE SSANGCIEUC-YI-NIEUNHIEUH A975 CBF7 # HANGUL SYLLABLE SSANGCIEUC-YI-TIKEUT A976 CBF8 # HANGUL SYLLABLE SSANGCIEUC-YI-RIEUL A977 CBF9 # HANGUL SYLLABLE SSANGCIEUC-YI-RIEULKIYEOK A978 CBFA # HANGUL SYLLABLE SSANGCIEUC-YI-RIEULMIEUM A979 CBFB # HANGUL SYLLABLE SSANGCIEUC-YI-RIEULPIEUP A97A CBFC # HANGUL SYLLABLE SSANGCIEUC-YI-RIEULSIOS A981 CBFD # HANGUL SYLLABLE SSANGCIEUC-YI-RIEULTHIEUTH A982 CBFE # HANGUL SYLLABLE SSANGCIEUC-YI-RIEULPHIEUPH A983 CBFF # HANGUL SYLLABLE SSANGCIEUC-YI-RIEULHIEUH A984 CC00 # HANGUL SYLLABLE SSANGCIEUC-YI-MIEUM A985 CC01 # HANGUL SYLLABLE SSANGCIEUC-YI-PIEUP A986 CC02 # HANGUL SYLLABLE SSANGCIEUC-YI-PIEUPSIOS A987 CC03 # HANGUL SYLLABLE SSANGCIEUC-YI-SIOS A988 CC04 # HANGUL SYLLABLE SSANGCIEUC-YI-SSANGSIOS A989 CC05 # HANGUL SYLLABLE SSANGCIEUC-YI-IEUNG A98A CC06 # HANGUL SYLLABLE SSANGCIEUC-YI-CIEUC A98B CC07 # HANGUL SYLLABLE SSANGCIEUC-YI-CHIEUCH A98C CC08 # HANGUL SYLLABLE SSANGCIEUC-YI-KHIEUKH A98D CC09 # HANGUL SYLLABLE SSANGCIEUC-YI-THIEUTH A98E CC0A # HANGUL SYLLABLE SSANGCIEUC-YI-PHIEUPH A98F CC0B # HANGUL SYLLABLE SSANGCIEUC-YI-HIEUH A990 CC0E # HANGUL SYLLABLE SSANGCIEUC-I-SSANGKIYEOK A991 CC0F # HANGUL SYLLABLE SSANGCIEUC-I-KIYEOKSIOS A992 CC11 # HANGUL SYLLABLE SSANGCIEUC-I-NIEUNCIEUC A993 CC12 # HANGUL SYLLABLE SSANGCIEUC-I-NIEUNHIEUH A994 CC13 # HANGUL SYLLABLE SSANGCIEUC-I-TIKEUT A995 CC15 # HANGUL SYLLABLE SSANGCIEUC-I-RIEULKIYEOK A996 CC16 # HANGUL SYLLABLE SSANGCIEUC-I-RIEULMIEUM A997 CC17 # HANGUL SYLLABLE SSANGCIEUC-I-RIEULPIEUP A998 CC18 # HANGUL SYLLABLE SSANGCIEUC-I-RIEULSIOS A999 CC19 # HANGUL SYLLABLE SSANGCIEUC-I-RIEULTHIEUTH A99A CC1A # HANGUL SYLLABLE SSANGCIEUC-I-RIEULPHIEUPH A99B CC1B # HANGUL SYLLABLE SSANGCIEUC-I-RIEULHIEUH A99C CC1E # HANGUL SYLLABLE SSANGCIEUC-I-PIEUPSIOS A99D CC1F # HANGUL SYLLABLE SSANGCIEUC-I-SIOS A99E CC20 # HANGUL SYLLABLE SSANGCIEUC-I-SSANGSIOS A99F CC23 # HANGUL SYLLABLE SSANGCIEUC-I-CHIEUCH A9A0 CC24 # HANGUL SYLLABLE SSANGCIEUC-I-KHIEUKH A9A1 00E6 # LATIN SMALL LIGATURE AE A9A2 0111 # LATIN SMALL LETTER D WITH STROKE A9A3 00F0 # LATIN SMALL LETTER ETH A9A4 0127 # LATIN SMALL LETTER H WITH STROKE A9A5 0131 # LATIN SMALL LETTER DOTLESS I A9A6 0133 # LATIN SMALL LIGATURE IJ A9A7 0138 # LATIN SMALL LETTER KRA A9A8 0140 # LATIN SMALL LETTER L WITH MIDDLE DOT A9A9 0142 # LATIN SMALL LETTER L WITH STROKE A9AA 00F8 # LATIN SMALL LETTER O WITH STROKE A9AB 0153 # LATIN SMALL LIGATURE OE A9AC 00DF # LATIN SMALL LETTER SHARP S A9AD 00FE # LATIN SMALL LETTER THORN A9AE 0167 # LATIN SMALL LETTER T WITH STROKE A9AF 014B # LATIN SMALL LETTER ENG A9B0 0149 # LATIN SMALL LETTER N PRECEDED BY APOSTROPHE A9B1 3200 # PARENTHESIZED HANGUL KIYEOK A9B2 3201 # PARENTHESIZED HANGUL NIEUN A9B3 3202 # PARENTHESIZED HANGUL TIKEUT A9B4 3203 # PARENTHESIZED HANGUL RIEUL A9B5 3204 # PARENTHESIZED HANGUL MIEUM A9B6 3205 # PARENTHESIZED HANGUL PIEUP A9B7 3206 # PARENTHESIZED HANGUL SIOS A9B8 3207 # PARENTHESIZED HANGUL IEUNG A9B9 3208 # PARENTHESIZED HANGUL CIEUC A9BA 3209 # PARENTHESIZED HANGUL CHIEUCH A9BB 320A # PARENTHESIZED HANGUL KHIEUKH A9BC 320B # PARENTHESIZED HANGUL THIEUTH A9BD 320C # PARENTHESIZED HANGUL PHIEUPH A9BE 320D # PARENTHESIZED HANGUL HIEUH A9BF 320E # PARENTHESIZED HANGUL KIYEOK A A9C0 320F # PARENTHESIZED HANGUL NIEUN A A9C1 3210 # PARENTHESIZED HANGUL TIKEUT A A9C2 3211 # PARENTHESIZED HANGUL RIEUL A A9C3 3212 # PARENTHESIZED HANGUL MIEUM A A9C4 3213 # PARENTHESIZED HANGUL PIEUP A A9C5 3214 # PARENTHESIZED HANGUL SIOS A A9C6 3215 # PARENTHESIZED HANGUL IEUNG A A9C7 3216 # PARENTHESIZED HANGUL CIEUC A A9C8 3217 # PARENTHESIZED HANGUL CHIEUCH A A9C9 3218 # PARENTHESIZED HANGUL KHIEUKH A A9CA 3219 # PARENTHESIZED HANGUL THIEUTH A A9CB 321A # PARENTHESIZED HANGUL PHIEUPH A A9CC 321B # PARENTHESIZED HANGUL HIEUH A A9CD 249C # PARENTHESIZED LATIN SMALL LETTER A A9CE 249D # PARENTHESIZED LATIN SMALL LETTER B A9CF 249E # PARENTHESIZED LATIN SMALL LETTER C A9D0 249F # PARENTHESIZED LATIN SMALL LETTER D A9D1 24A0 # PARENTHESIZED LATIN SMALL LETTER E A9D2 24A1 # PARENTHESIZED LATIN SMALL LETTER F A9D3 24A2 # PARENTHESIZED LATIN SMALL LETTER G A9D4 24A3 # PARENTHESIZED LATIN SMALL LETTER H A9D5 24A4 # PARENTHESIZED LATIN SMALL LETTER I A9D6 24A5 # PARENTHESIZED LATIN SMALL LETTER J A9D7 24A6 # PARENTHESIZED LATIN SMALL LETTER K A9D8 24A7 # PARENTHESIZED LATIN SMALL LETTER L A9D9 24A8 # PARENTHESIZED LATIN SMALL LETTER M A9DA 24A9 # PARENTHESIZED LATIN SMALL LETTER N A9DB 24AA # PARENTHESIZED LATIN SMALL LETTER O A9DC 24AB # PARENTHESIZED LATIN SMALL LETTER P A9DD 24AC # PARENTHESIZED LATIN SMALL LETTER Q A9DE 24AD # PARENTHESIZED LATIN SMALL LETTER R A9DF 24AE # PARENTHESIZED LATIN SMALL LETTER S A9E0 24AF # PARENTHESIZED LATIN SMALL LETTER T A9E1 24B0 # PARENTHESIZED LATIN SMALL LETTER U A9E2 24B1 # PARENTHESIZED LATIN SMALL LETTER V A9E3 24B2 # PARENTHESIZED LATIN SMALL LETTER W A9E4 24B3 # PARENTHESIZED LATIN SMALL LETTER X A9E5 24B4 # PARENTHESIZED LATIN SMALL LETTER Y A9E6 24B5 # PARENTHESIZED LATIN SMALL LETTER Z A9E7 2474 # PARENTHESIZED DIGIT ONE A9E8 2475 # PARENTHESIZED DIGIT TWO A9E9 2476 # PARENTHESIZED DIGIT THREE A9EA 2477 # PARENTHESIZED DIGIT FOUR A9EB 2478 # PARENTHESIZED DIGIT FIVE A9EC 2479 # PARENTHESIZED DIGIT SIX A9ED 247A # PARENTHESIZED DIGIT SEVEN A9EE 247B # PARENTHESIZED DIGIT EIGHT A9EF 247C # PARENTHESIZED DIGIT NINE A9F0 247D # PARENTHESIZED NUMBER TEN A9F1 247E # PARENTHESIZED NUMBER ELEVEN A9F2 247F # PARENTHESIZED NUMBER TWELVE A9F3 2480 # PARENTHESIZED NUMBER THIRTEEN A9F4 2481 # PARENTHESIZED NUMBER FOURTEEN A9F5 2482 # PARENTHESIZED NUMBER FIFTEEN A9F6 00B9 # SUPERSCRIPT ONE A9F7 00B2 # SUPERSCRIPT TWO A9F8 00B3 # SUPERSCRIPT THREE A9F9 2074 # SUPERSCRIPT FOUR A9FA 207F # SUPERSCRIPT LATIN SMALL LETTER N A9FB 2081 # SUBSCRIPT ONE A9FC 2082 # SUBSCRIPT TWO A9FD 2083 # SUBSCRIPT THREE A9FE 2084 # SUBSCRIPT FOUR AA41 CC25 # HANGUL SYLLABLE SSANGCIEUC-I-THIEUTH AA42 CC26 # HANGUL SYLLABLE SSANGCIEUC-I-PHIEUPH AA43 CC2A # HANGUL SYLLABLE CHIEUCH-A-SSANGKIYEOK AA44 CC2B # HANGUL SYLLABLE CHIEUCH-A-KIYEOKSIOS AA45 CC2D # HANGUL SYLLABLE CHIEUCH-A-NIEUNCIEUC AA46 CC2F # HANGUL SYLLABLE CHIEUCH-A-TIKEUT AA47 CC31 # HANGUL SYLLABLE CHIEUCH-A-RIEULKIYEOK AA48 CC32 # HANGUL SYLLABLE CHIEUCH-A-RIEULMIEUM AA49 CC33 # HANGUL SYLLABLE CHIEUCH-A-RIEULPIEUP AA4A CC34 # HANGUL SYLLABLE CHIEUCH-A-RIEULSIOS AA4B CC35 # HANGUL SYLLABLE CHIEUCH-A-RIEULTHIEUTH AA4C CC36 # HANGUL SYLLABLE CHIEUCH-A-RIEULPHIEUPH AA4D CC37 # HANGUL SYLLABLE CHIEUCH-A-RIEULHIEUH AA4E CC3A # HANGUL SYLLABLE CHIEUCH-A-PIEUPSIOS AA4F CC3F # HANGUL SYLLABLE CHIEUCH-A-CHIEUCH AA50 CC40 # HANGUL SYLLABLE CHIEUCH-A-KHIEUKH AA51 CC41 # HANGUL SYLLABLE CHIEUCH-A-THIEUTH AA52 CC42 # HANGUL SYLLABLE CHIEUCH-A-PHIEUPH AA53 CC43 # HANGUL SYLLABLE CHIEUCH-A-HIEUH AA54 CC46 # HANGUL SYLLABLE CHIEUCH-AE-SSANGKIYEOK AA55 CC47 # HANGUL SYLLABLE CHIEUCH-AE-KIYEOKSIOS AA56 CC49 # HANGUL SYLLABLE CHIEUCH-AE-NIEUNCIEUC AA57 CC4A # HANGUL SYLLABLE CHIEUCH-AE-NIEUNHIEUH AA58 CC4B # HANGUL SYLLABLE CHIEUCH-AE-TIKEUT AA59 CC4D # HANGUL SYLLABLE CHIEUCH-AE-RIEULKIYEOK AA5A CC4E # HANGUL SYLLABLE CHIEUCH-AE-RIEULMIEUM AA61 CC4F # HANGUL SYLLABLE CHIEUCH-AE-RIEULPIEUP AA62 CC50 # HANGUL SYLLABLE CHIEUCH-AE-RIEULSIOS AA63 CC51 # HANGUL SYLLABLE CHIEUCH-AE-RIEULTHIEUTH AA64 CC52 # HANGUL SYLLABLE CHIEUCH-AE-RIEULPHIEUPH AA65 CC53 # HANGUL SYLLABLE CHIEUCH-AE-RIEULHIEUH AA66 CC56 # HANGUL SYLLABLE CHIEUCH-AE-PIEUPSIOS AA67 CC5A # HANGUL SYLLABLE CHIEUCH-AE-CIEUC AA68 CC5B # HANGUL SYLLABLE CHIEUCH-AE-CHIEUCH AA69 CC5C # HANGUL SYLLABLE CHIEUCH-AE-KHIEUKH AA6A CC5D # HANGUL SYLLABLE CHIEUCH-AE-THIEUTH AA6B CC5E # HANGUL SYLLABLE CHIEUCH-AE-PHIEUPH AA6C CC5F # HANGUL SYLLABLE CHIEUCH-AE-HIEUH AA6D CC61 # HANGUL SYLLABLE CHIEUCH-YA-KIYEOK AA6E CC62 # HANGUL SYLLABLE CHIEUCH-YA-SSANGKIYEOK AA6F CC63 # HANGUL SYLLABLE CHIEUCH-YA-KIYEOKSIOS AA70 CC65 # HANGUL SYLLABLE CHIEUCH-YA-NIEUNCIEUC AA71 CC67 # HANGUL SYLLABLE CHIEUCH-YA-TIKEUT AA72 CC69 # HANGUL SYLLABLE CHIEUCH-YA-RIEULKIYEOK AA73 CC6A # HANGUL SYLLABLE CHIEUCH-YA-RIEULMIEUM AA74 CC6B # HANGUL SYLLABLE CHIEUCH-YA-RIEULPIEUP AA75 CC6C # HANGUL SYLLABLE CHIEUCH-YA-RIEULSIOS AA76 CC6D # HANGUL SYLLABLE CHIEUCH-YA-RIEULTHIEUTH AA77 CC6E # HANGUL SYLLABLE CHIEUCH-YA-RIEULPHIEUPH AA78 CC6F # HANGUL SYLLABLE CHIEUCH-YA-RIEULHIEUH AA79 CC71 # HANGUL SYLLABLE CHIEUCH-YA-PIEUP AA7A CC72 # HANGUL SYLLABLE CHIEUCH-YA-PIEUPSIOS AA81 CC73 # HANGUL SYLLABLE CHIEUCH-YA-SIOS AA82 CC74 # HANGUL SYLLABLE CHIEUCH-YA-SSANGSIOS AA83 CC76 # HANGUL SYLLABLE CHIEUCH-YA-CIEUC AA84 CC77 # HANGUL SYLLABLE CHIEUCH-YA-CHIEUCH AA85 CC78 # HANGUL SYLLABLE CHIEUCH-YA-KHIEUKH AA86 CC79 # HANGUL SYLLABLE CHIEUCH-YA-THIEUTH AA87 CC7A # HANGUL SYLLABLE CHIEUCH-YA-PHIEUPH AA88 CC7B # HANGUL SYLLABLE CHIEUCH-YA-HIEUH AA89 CC7C # HANGUL SYLLABLE CHIEUCH-YAE AA8A CC7D # HANGUL SYLLABLE CHIEUCH-YAE-KIYEOK AA8B CC7E # HANGUL SYLLABLE CHIEUCH-YAE-SSANGKIYEOK AA8C CC7F # HANGUL SYLLABLE CHIEUCH-YAE-KIYEOKSIOS AA8D CC80 # HANGUL SYLLABLE CHIEUCH-YAE-NIEUN AA8E CC81 # HANGUL SYLLABLE CHIEUCH-YAE-NIEUNCIEUC AA8F CC82 # HANGUL SYLLABLE CHIEUCH-YAE-NIEUNHIEUH AA90 CC83 # HANGUL SYLLABLE CHIEUCH-YAE-TIKEUT AA91 CC84 # HANGUL SYLLABLE CHIEUCH-YAE-RIEUL AA92 CC85 # HANGUL SYLLABLE CHIEUCH-YAE-RIEULKIYEOK AA93 CC86 # HANGUL SYLLABLE CHIEUCH-YAE-RIEULMIEUM AA94 CC87 # HANGUL SYLLABLE CHIEUCH-YAE-RIEULPIEUP AA95 CC88 # HANGUL SYLLABLE CHIEUCH-YAE-RIEULSIOS AA96 CC89 # HANGUL SYLLABLE CHIEUCH-YAE-RIEULTHIEUTH AA97 CC8A # HANGUL SYLLABLE CHIEUCH-YAE-RIEULPHIEUPH AA98 CC8B # HANGUL SYLLABLE CHIEUCH-YAE-RIEULHIEUH AA99 CC8C # HANGUL SYLLABLE CHIEUCH-YAE-MIEUM AA9A CC8D # HANGUL SYLLABLE CHIEUCH-YAE-PIEUP AA9B CC8E # HANGUL SYLLABLE CHIEUCH-YAE-PIEUPSIOS AA9C CC8F # HANGUL SYLLABLE CHIEUCH-YAE-SIOS AA9D CC90 # HANGUL SYLLABLE CHIEUCH-YAE-SSANGSIOS AA9E CC91 # HANGUL SYLLABLE CHIEUCH-YAE-IEUNG AA9F CC92 # HANGUL SYLLABLE CHIEUCH-YAE-CIEUC AAA0 CC93 # HANGUL SYLLABLE CHIEUCH-YAE-CHIEUCH AAA1 3041 # HIRAGANA LETTER SMALL A AAA2 3042 # HIRAGANA LETTER A AAA3 3043 # HIRAGANA LETTER SMALL I AAA4 3044 # HIRAGANA LETTER I AAA5 3045 # HIRAGANA LETTER SMALL U AAA6 3046 # HIRAGANA LETTER U AAA7 3047 # HIRAGANA LETTER SMALL E AAA8 3048 # HIRAGANA LETTER E AAA9 3049 # HIRAGANA LETTER SMALL O AAAA 304A # HIRAGANA LETTER O AAAB 304B # HIRAGANA LETTER KA AAAC 304C # HIRAGANA LETTER GA AAAD 304D # HIRAGANA LETTER KI AAAE 304E # HIRAGANA LETTER GI AAAF 304F # HIRAGANA LETTER KU AAB0 3050 # HIRAGANA LETTER GU AAB1 3051 # HIRAGANA LETTER KE AAB2 3052 # HIRAGANA LETTER GE AAB3 3053 # HIRAGANA LETTER KO AAB4 3054 # HIRAGANA LETTER GO AAB5 3055 # HIRAGANA LETTER SA AAB6 3056 # HIRAGANA LETTER ZA AAB7 3057 # HIRAGANA LETTER SI AAB8 3058 # HIRAGANA LETTER ZI AAB9 3059 # HIRAGANA LETTER SU AABA 305A # HIRAGANA LETTER ZU AABB 305B # HIRAGANA LETTER SE AABC 305C # HIRAGANA LETTER ZE AABD 305D # HIRAGANA LETTER SO AABE 305E # HIRAGANA LETTER ZO AABF 305F # HIRAGANA LETTER TA AAC0 3060 # HIRAGANA LETTER DA AAC1 3061 # HIRAGANA LETTER TI AAC2 3062 # HIRAGANA LETTER DI AAC3 3063 # HIRAGANA LETTER SMALL TU AAC4 3064 # HIRAGANA LETTER TU AAC5 3065 # HIRAGANA LETTER DU AAC6 3066 # HIRAGANA LETTER TE AAC7 3067 # HIRAGANA LETTER DE AAC8 3068 # HIRAGANA LETTER TO AAC9 3069 # HIRAGANA LETTER DO AACA 306A # HIRAGANA LETTER NA AACB 306B # HIRAGANA LETTER NI AACC 306C # HIRAGANA LETTER NU AACD 306D # HIRAGANA LETTER NE AACE 306E # HIRAGANA LETTER NO AACF 306F # HIRAGANA LETTER HA AAD0 3070 # HIRAGANA LETTER BA AAD1 3071 # HIRAGANA LETTER PA AAD2 3072 # HIRAGANA LETTER HI AAD3 3073 # HIRAGANA LETTER BI AAD4 3074 # HIRAGANA LETTER PI AAD5 3075 # HIRAGANA LETTER HU AAD6 3076 # HIRAGANA LETTER BU AAD7 3077 # HIRAGANA LETTER PU AAD8 3078 # HIRAGANA LETTER HE AAD9 3079 # HIRAGANA LETTER BE AADA 307A # HIRAGANA LETTER PE AADB 307B # HIRAGANA LETTER HO AADC 307C # HIRAGANA LETTER BO AADD 307D # HIRAGANA LETTER PO AADE 307E # HIRAGANA LETTER MA AADF 307F # HIRAGANA LETTER MI AAE0 3080 # HIRAGANA LETTER MU AAE1 3081 # HIRAGANA LETTER ME AAE2 3082 # HIRAGANA LETTER MO AAE3 3083 # HIRAGANA LETTER SMALL YA AAE4 3084 # HIRAGANA LETTER YA AAE5 3085 # HIRAGANA LETTER SMALL YU AAE6 3086 # HIRAGANA LETTER YU AAE7 3087 # HIRAGANA LETTER SMALL YO AAE8 3088 # HIRAGANA LETTER YO AAE9 3089 # HIRAGANA LETTER RA AAEA 308A # HIRAGANA LETTER RI AAEB 308B # HIRAGANA LETTER RU AAEC 308C # HIRAGANA LETTER RE AAED 308D # HIRAGANA LETTER RO AAEE 308E # HIRAGANA LETTER SMALL WA AAEF 308F # HIRAGANA LETTER WA AAF0 3090 # HIRAGANA LETTER WI AAF1 3091 # HIRAGANA LETTER WE AAF2 3092 # HIRAGANA LETTER WO AAF3 3093 # HIRAGANA LETTER N AB41 CC94 # HANGUL SYLLABLE CHIEUCH-YAE-KHIEUKH AB42 CC95 # HANGUL SYLLABLE CHIEUCH-YAE-THIEUTH AB43 CC96 # HANGUL SYLLABLE CHIEUCH-YAE-PHIEUPH AB44 CC97 # HANGUL SYLLABLE CHIEUCH-YAE-HIEUH AB45 CC9A # HANGUL SYLLABLE CHIEUCH-EO-SSANGKIYEOK AB46 CC9B # HANGUL SYLLABLE CHIEUCH-EO-KIYEOKSIOS AB47 CC9D # HANGUL SYLLABLE CHIEUCH-EO-NIEUNCIEUC AB48 CC9E # HANGUL SYLLABLE CHIEUCH-EO-NIEUNHIEUH AB49 CC9F # HANGUL SYLLABLE CHIEUCH-EO-TIKEUT AB4A CCA1 # HANGUL SYLLABLE CHIEUCH-EO-RIEULKIYEOK AB4B CCA2 # HANGUL SYLLABLE CHIEUCH-EO-RIEULMIEUM AB4C CCA3 # HANGUL SYLLABLE CHIEUCH-EO-RIEULPIEUP AB4D CCA4 # HANGUL SYLLABLE CHIEUCH-EO-RIEULSIOS AB4E CCA5 # HANGUL SYLLABLE CHIEUCH-EO-RIEULTHIEUTH AB4F CCA6 # HANGUL SYLLABLE CHIEUCH-EO-RIEULPHIEUPH AB50 CCA7 # HANGUL SYLLABLE CHIEUCH-EO-RIEULHIEUH AB51 CCAA # HANGUL SYLLABLE CHIEUCH-EO-PIEUPSIOS AB52 CCAE # HANGUL SYLLABLE CHIEUCH-EO-CIEUC AB53 CCAF # HANGUL SYLLABLE CHIEUCH-EO-CHIEUCH AB54 CCB0 # HANGUL SYLLABLE CHIEUCH-EO-KHIEUKH AB55 CCB1 # HANGUL SYLLABLE CHIEUCH-EO-THIEUTH AB56 CCB2 # HANGUL SYLLABLE CHIEUCH-EO-PHIEUPH AB57 CCB3 # HANGUL SYLLABLE CHIEUCH-EO-HIEUH AB58 CCB6 # HANGUL SYLLABLE CHIEUCH-E-SSANGKIYEOK AB59 CCB7 # HANGUL SYLLABLE CHIEUCH-E-KIYEOKSIOS AB5A CCB9 # HANGUL SYLLABLE CHIEUCH-E-NIEUNCIEUC AB61 CCBA # HANGUL SYLLABLE CHIEUCH-E-NIEUNHIEUH AB62 CCBB # HANGUL SYLLABLE CHIEUCH-E-TIKEUT AB63 CCBD # HANGUL SYLLABLE CHIEUCH-E-RIEULKIYEOK AB64 CCBE # HANGUL SYLLABLE CHIEUCH-E-RIEULMIEUM AB65 CCBF # HANGUL SYLLABLE CHIEUCH-E-RIEULPIEUP AB66 CCC0 # HANGUL SYLLABLE CHIEUCH-E-RIEULSIOS AB67 CCC1 # HANGUL SYLLABLE CHIEUCH-E-RIEULTHIEUTH AB68 CCC2 # HANGUL SYLLABLE CHIEUCH-E-RIEULPHIEUPH AB69 CCC3 # HANGUL SYLLABLE CHIEUCH-E-RIEULHIEUH AB6A CCC6 # HANGUL SYLLABLE CHIEUCH-E-PIEUPSIOS AB6B CCC8 # HANGUL SYLLABLE CHIEUCH-E-SSANGSIOS AB6C CCCA # HANGUL SYLLABLE CHIEUCH-E-CIEUC AB6D CCCB # HANGUL SYLLABLE CHIEUCH-E-CHIEUCH AB6E CCCC # HANGUL SYLLABLE CHIEUCH-E-KHIEUKH AB6F CCCD # HANGUL SYLLABLE CHIEUCH-E-THIEUTH AB70 CCCE # HANGUL SYLLABLE CHIEUCH-E-PHIEUPH AB71 CCCF # HANGUL SYLLABLE CHIEUCH-E-HIEUH AB72 CCD1 # HANGUL SYLLABLE CHIEUCH-YEO-KIYEOK AB73 CCD2 # HANGUL SYLLABLE CHIEUCH-YEO-SSANGKIYEOK AB74 CCD3 # HANGUL SYLLABLE CHIEUCH-YEO-KIYEOKSIOS AB75 CCD5 # HANGUL SYLLABLE CHIEUCH-YEO-NIEUNCIEUC AB76 CCD6 # HANGUL SYLLABLE CHIEUCH-YEO-NIEUNHIEUH AB77 CCD7 # HANGUL SYLLABLE CHIEUCH-YEO-TIKEUT AB78 CCD8 # HANGUL SYLLABLE CHIEUCH-YEO-RIEUL AB79 CCD9 # HANGUL SYLLABLE CHIEUCH-YEO-RIEULKIYEOK AB7A CCDA # HANGUL SYLLABLE CHIEUCH-YEO-RIEULMIEUM AB81 CCDB # HANGUL SYLLABLE CHIEUCH-YEO-RIEULPIEUP AB82 CCDC # HANGUL SYLLABLE CHIEUCH-YEO-RIEULSIOS AB83 CCDD # HANGUL SYLLABLE CHIEUCH-YEO-RIEULTHIEUTH AB84 CCDE # HANGUL SYLLABLE CHIEUCH-YEO-RIEULPHIEUPH AB85 CCDF # HANGUL SYLLABLE CHIEUCH-YEO-RIEULHIEUH AB86 CCE0 # HANGUL SYLLABLE CHIEUCH-YEO-MIEUM AB87 CCE1 # HANGUL SYLLABLE CHIEUCH-YEO-PIEUP AB88 CCE2 # HANGUL SYLLABLE CHIEUCH-YEO-PIEUPSIOS AB89 CCE3 # HANGUL SYLLABLE CHIEUCH-YEO-SIOS AB8A CCE5 # HANGUL SYLLABLE CHIEUCH-YEO-IEUNG AB8B CCE6 # HANGUL SYLLABLE CHIEUCH-YEO-CIEUC AB8C CCE7 # HANGUL SYLLABLE CHIEUCH-YEO-CHIEUCH AB8D CCE8 # HANGUL SYLLABLE CHIEUCH-YEO-KHIEUKH AB8E CCE9 # HANGUL SYLLABLE CHIEUCH-YEO-THIEUTH AB8F CCEA # HANGUL SYLLABLE CHIEUCH-YEO-PHIEUPH AB90 CCEB # HANGUL SYLLABLE CHIEUCH-YEO-HIEUH AB91 CCED # HANGUL SYLLABLE CHIEUCH-YE-KIYEOK AB92 CCEE # HANGUL SYLLABLE CHIEUCH-YE-SSANGKIYEOK AB93 CCEF # HANGUL SYLLABLE CHIEUCH-YE-KIYEOKSIOS AB94 CCF1 # HANGUL SYLLABLE CHIEUCH-YE-NIEUNCIEUC AB95 CCF2 # HANGUL SYLLABLE CHIEUCH-YE-NIEUNHIEUH AB96 CCF3 # HANGUL SYLLABLE CHIEUCH-YE-TIKEUT AB97 CCF4 # HANGUL SYLLABLE CHIEUCH-YE-RIEUL AB98 CCF5 # HANGUL SYLLABLE CHIEUCH-YE-RIEULKIYEOK AB99 CCF6 # HANGUL SYLLABLE CHIEUCH-YE-RIEULMIEUM AB9A CCF7 # HANGUL SYLLABLE CHIEUCH-YE-RIEULPIEUP AB9B CCF8 # HANGUL SYLLABLE CHIEUCH-YE-RIEULSIOS AB9C CCF9 # HANGUL SYLLABLE CHIEUCH-YE-RIEULTHIEUTH AB9D CCFA # HANGUL SYLLABLE CHIEUCH-YE-RIEULPHIEUPH AB9E CCFB # HANGUL SYLLABLE CHIEUCH-YE-RIEULHIEUH AB9F CCFC # HANGUL SYLLABLE CHIEUCH-YE-MIEUM ABA0 CCFD # HANGUL SYLLABLE CHIEUCH-YE-PIEUP ABA1 30A1 # KATAKANA LETTER SMALL A ABA2 30A2 # KATAKANA LETTER A ABA3 30A3 # KATAKANA LETTER SMALL I ABA4 30A4 # KATAKANA LETTER I ABA5 30A5 # KATAKANA LETTER SMALL U ABA6 30A6 # KATAKANA LETTER U ABA7 30A7 # KATAKANA LETTER SMALL E ABA8 30A8 # KATAKANA LETTER E ABA9 30A9 # KATAKANA LETTER SMALL O ABAA 30AA # KATAKANA LETTER O ABAB 30AB # KATAKANA LETTER KA ABAC 30AC # KATAKANA LETTER GA ABAD 30AD # KATAKANA LETTER KI ABAE 30AE # KATAKANA LETTER GI ABAF 30AF # KATAKANA LETTER KU ABB0 30B0 # KATAKANA LETTER GU ABB1 30B1 # KATAKANA LETTER KE ABB2 30B2 # KATAKANA LETTER GE ABB3 30B3 # KATAKANA LETTER KO ABB4 30B4 # KATAKANA LETTER GO ABB5 30B5 # KATAKANA LETTER SA ABB6 30B6 # KATAKANA LETTER ZA ABB7 30B7 # KATAKANA LETTER SI ABB8 30B8 # KATAKANA LETTER ZI ABB9 30B9 # KATAKANA LETTER SU ABBA 30BA # KATAKANA LETTER ZU ABBB 30BB # KATAKANA LETTER SE ABBC 30BC # KATAKANA LETTER ZE ABBD 30BD # KATAKANA LETTER SO ABBE 30BE # KATAKANA LETTER ZO ABBF 30BF # KATAKANA LETTER TA ABC0 30C0 # KATAKANA LETTER DA ABC1 30C1 # KATAKANA LETTER TI ABC2 30C2 # KATAKANA LETTER DI ABC3 30C3 # KATAKANA LETTER SMALL TU ABC4 30C4 # KATAKANA LETTER TU ABC5 30C5 # KATAKANA LETTER DU ABC6 30C6 # KATAKANA LETTER TE ABC7 30C7 # KATAKANA LETTER DE ABC8 30C8 # KATAKANA LETTER TO ABC9 30C9 # KATAKANA LETTER DO ABCA 30CA # KATAKANA LETTER NA ABCB 30CB # KATAKANA LETTER NI ABCC 30CC # KATAKANA LETTER NU ABCD 30CD # KATAKANA LETTER NE ABCE 30CE # KATAKANA LETTER NO ABCF 30CF # KATAKANA LETTER HA ABD0 30D0 # KATAKANA LETTER BA ABD1 30D1 # KATAKANA LETTER PA ABD2 30D2 # KATAKANA LETTER HI ABD3 30D3 # KATAKANA LETTER BI ABD4 30D4 # KATAKANA LETTER PI ABD5 30D5 # KATAKANA LETTER HU ABD6 30D6 # KATAKANA LETTER BU ABD7 30D7 # KATAKANA LETTER PU ABD8 30D8 # KATAKANA LETTER HE ABD9 30D9 # KATAKANA LETTER BE ABDA 30DA # KATAKANA LETTER PE ABDB 30DB # KATAKANA LETTER HO ABDC 30DC # KATAKANA LETTER BO ABDD 30DD # KATAKANA LETTER PO ABDE 30DE # KATAKANA LETTER MA ABDF 30DF # KATAKANA LETTER MI ABE0 30E0 # KATAKANA LETTER MU ABE1 30E1 # KATAKANA LETTER ME ABE2 30E2 # KATAKANA LETTER MO ABE3 30E3 # KATAKANA LETTER SMALL YA ABE4 30E4 # KATAKANA LETTER YA ABE5 30E5 # KATAKANA LETTER SMALL YU ABE6 30E6 # KATAKANA LETTER YU ABE7 30E7 # KATAKANA LETTER SMALL YO ABE8 30E8 # KATAKANA LETTER YO ABE9 30E9 # KATAKANA LETTER RA ABEA 30EA # KATAKANA LETTER RI ABEB 30EB # KATAKANA LETTER RU ABEC 30EC # KATAKANA LETTER RE ABED 30ED # KATAKANA LETTER RO ABEE 30EE # KATAKANA LETTER SMALL WA ABEF 30EF # KATAKANA LETTER WA ABF0 30F0 # KATAKANA LETTER WI ABF1 30F1 # KATAKANA LETTER WE ABF2 30F2 # KATAKANA LETTER WO ABF3 30F3 # KATAKANA LETTER N ABF4 30F4 # KATAKANA LETTER VU ABF5 30F5 # KATAKANA LETTER SMALL KA ABF6 30F6 # KATAKANA LETTER SMALL KE AC41 CCFE # HANGUL SYLLABLE CHIEUCH-YE-PIEUPSIOS AC42 CCFF # HANGUL SYLLABLE CHIEUCH-YE-SIOS AC43 CD00 # HANGUL SYLLABLE CHIEUCH-YE-SSANGSIOS AC44 CD02 # HANGUL SYLLABLE CHIEUCH-YE-CIEUC AC45 CD03 # HANGUL SYLLABLE CHIEUCH-YE-CHIEUCH AC46 CD04 # HANGUL SYLLABLE CHIEUCH-YE-KHIEUKH AC47 CD05 # HANGUL SYLLABLE CHIEUCH-YE-THIEUTH AC48 CD06 # HANGUL SYLLABLE CHIEUCH-YE-PHIEUPH AC49 CD07 # HANGUL SYLLABLE CHIEUCH-YE-HIEUH AC4A CD0A # HANGUL SYLLABLE CHIEUCH-O-SSANGKIYEOK AC4B CD0B # HANGUL SYLLABLE CHIEUCH-O-KIYEOKSIOS AC4C CD0D # HANGUL SYLLABLE CHIEUCH-O-NIEUNCIEUC AC4D CD0E # HANGUL SYLLABLE CHIEUCH-O-NIEUNHIEUH AC4E CD0F # HANGUL SYLLABLE CHIEUCH-O-TIKEUT AC4F CD11 # HANGUL SYLLABLE CHIEUCH-O-RIEULKIYEOK AC50 CD12 # HANGUL SYLLABLE CHIEUCH-O-RIEULMIEUM AC51 CD13 # HANGUL SYLLABLE CHIEUCH-O-RIEULPIEUP AC52 CD14 # HANGUL SYLLABLE CHIEUCH-O-RIEULSIOS AC53 CD15 # HANGUL SYLLABLE CHIEUCH-O-RIEULTHIEUTH AC54 CD16 # HANGUL SYLLABLE CHIEUCH-O-RIEULPHIEUPH AC55 CD17 # HANGUL SYLLABLE CHIEUCH-O-RIEULHIEUH AC56 CD1A # HANGUL SYLLABLE CHIEUCH-O-PIEUPSIOS AC57 CD1C # HANGUL SYLLABLE CHIEUCH-O-SSANGSIOS AC58 CD1E # HANGUL SYLLABLE CHIEUCH-O-CIEUC AC59 CD1F # HANGUL SYLLABLE CHIEUCH-O-CHIEUCH AC5A CD20 # HANGUL SYLLABLE CHIEUCH-O-KHIEUKH AC61 CD21 # HANGUL SYLLABLE CHIEUCH-O-THIEUTH AC62 CD22 # HANGUL SYLLABLE CHIEUCH-O-PHIEUPH AC63 CD23 # HANGUL SYLLABLE CHIEUCH-O-HIEUH AC64 CD25 # HANGUL SYLLABLE CHIEUCH-WA-KIYEOK AC65 CD26 # HANGUL SYLLABLE CHIEUCH-WA-SSANGKIYEOK AC66 CD27 # HANGUL SYLLABLE CHIEUCH-WA-KIYEOKSIOS AC67 CD29 # HANGUL SYLLABLE CHIEUCH-WA-NIEUNCIEUC AC68 CD2A # HANGUL SYLLABLE CHIEUCH-WA-NIEUNHIEUH AC69 CD2B # HANGUL SYLLABLE CHIEUCH-WA-TIKEUT AC6A CD2D # HANGUL SYLLABLE CHIEUCH-WA-RIEULKIYEOK AC6B CD2E # HANGUL SYLLABLE CHIEUCH-WA-RIEULMIEUM AC6C CD2F # HANGUL SYLLABLE CHIEUCH-WA-RIEULPIEUP AC6D CD30 # HANGUL SYLLABLE CHIEUCH-WA-RIEULSIOS AC6E CD31 # HANGUL SYLLABLE CHIEUCH-WA-RIEULTHIEUTH AC6F CD32 # HANGUL SYLLABLE CHIEUCH-WA-RIEULPHIEUPH AC70 CD33 # HANGUL SYLLABLE CHIEUCH-WA-RIEULHIEUH AC71 CD34 # HANGUL SYLLABLE CHIEUCH-WA-MIEUM AC72 CD35 # HANGUL SYLLABLE CHIEUCH-WA-PIEUP AC73 CD36 # HANGUL SYLLABLE CHIEUCH-WA-PIEUPSIOS AC74 CD37 # HANGUL SYLLABLE CHIEUCH-WA-SIOS AC75 CD38 # HANGUL SYLLABLE CHIEUCH-WA-SSANGSIOS AC76 CD3A # HANGUL SYLLABLE CHIEUCH-WA-CIEUC AC77 CD3B # HANGUL SYLLABLE CHIEUCH-WA-CHIEUCH AC78 CD3C # HANGUL SYLLABLE CHIEUCH-WA-KHIEUKH AC79 CD3D # HANGUL SYLLABLE CHIEUCH-WA-THIEUTH AC7A CD3E # HANGUL SYLLABLE CHIEUCH-WA-PHIEUPH AC81 CD3F # HANGUL SYLLABLE CHIEUCH-WA-HIEUH AC82 CD40 # HANGUL SYLLABLE CHIEUCH-WAE AC83 CD41 # HANGUL SYLLABLE CHIEUCH-WAE-KIYEOK AC84 CD42 # HANGUL SYLLABLE CHIEUCH-WAE-SSANGKIYEOK AC85 CD43 # HANGUL SYLLABLE CHIEUCH-WAE-KIYEOKSIOS AC86 CD44 # HANGUL SYLLABLE CHIEUCH-WAE-NIEUN AC87 CD45 # HANGUL SYLLABLE CHIEUCH-WAE-NIEUNCIEUC AC88 CD46 # HANGUL SYLLABLE CHIEUCH-WAE-NIEUNHIEUH AC89 CD47 # HANGUL SYLLABLE CHIEUCH-WAE-TIKEUT AC8A CD48 # HANGUL SYLLABLE CHIEUCH-WAE-RIEUL AC8B CD49 # HANGUL SYLLABLE CHIEUCH-WAE-RIEULKIYEOK AC8C CD4A # HANGUL SYLLABLE CHIEUCH-WAE-RIEULMIEUM AC8D CD4B # HANGUL SYLLABLE CHIEUCH-WAE-RIEULPIEUP AC8E CD4C # HANGUL SYLLABLE CHIEUCH-WAE-RIEULSIOS AC8F CD4D # HANGUL SYLLABLE CHIEUCH-WAE-RIEULTHIEUTH AC90 CD4E # HANGUL SYLLABLE CHIEUCH-WAE-RIEULPHIEUPH AC91 CD4F # HANGUL SYLLABLE CHIEUCH-WAE-RIEULHIEUH AC92 CD50 # HANGUL SYLLABLE CHIEUCH-WAE-MIEUM AC93 CD51 # HANGUL SYLLABLE CHIEUCH-WAE-PIEUP AC94 CD52 # HANGUL SYLLABLE CHIEUCH-WAE-PIEUPSIOS AC95 CD53 # HANGUL SYLLABLE CHIEUCH-WAE-SIOS AC96 CD54 # HANGUL SYLLABLE CHIEUCH-WAE-SSANGSIOS AC97 CD55 # HANGUL SYLLABLE CHIEUCH-WAE-IEUNG AC98 CD56 # HANGUL SYLLABLE CHIEUCH-WAE-CIEUC AC99 CD57 # HANGUL SYLLABLE CHIEUCH-WAE-CHIEUCH AC9A CD58 # HANGUL SYLLABLE CHIEUCH-WAE-KHIEUKH AC9B CD59 # HANGUL SYLLABLE CHIEUCH-WAE-THIEUTH AC9C CD5A # HANGUL SYLLABLE CHIEUCH-WAE-PHIEUPH AC9D CD5B # HANGUL SYLLABLE CHIEUCH-WAE-HIEUH AC9E CD5D # HANGUL SYLLABLE CHIEUCH-OE-KIYEOK AC9F CD5E # HANGUL SYLLABLE CHIEUCH-OE-SSANGKIYEOK ACA0 CD5F # HANGUL SYLLABLE CHIEUCH-OE-KIYEOKSIOS ACA1 0410 # CYRILLIC CAPITAL LETTER A ACA2 0411 # CYRILLIC CAPITAL LETTER BE ACA3 0412 # CYRILLIC CAPITAL LETTER VE ACA4 0413 # CYRILLIC CAPITAL LETTER GHE ACA5 0414 # CYRILLIC CAPITAL LETTER DE ACA6 0415 # CYRILLIC CAPITAL LETTER IE ACA7 0401 # CYRILLIC CAPITAL LETTER IO ACA8 0416 # CYRILLIC CAPITAL LETTER ZHE ACA9 0417 # CYRILLIC CAPITAL LETTER ZE ACAA 0418 # CYRILLIC CAPITAL LETTER I ACAB 0419 # CYRILLIC CAPITAL LETTER SHORT I ACAC 041A # CYRILLIC CAPITAL LETTER KA ACAD 041B # CYRILLIC CAPITAL LETTER EL ACAE 041C # CYRILLIC CAPITAL LETTER EM ACAF 041D # CYRILLIC CAPITAL LETTER EN ACB0 041E # CYRILLIC CAPITAL LETTER O ACB1 041F # CYRILLIC CAPITAL LETTER PE ACB2 0420 # CYRILLIC CAPITAL LETTER ER ACB3 0421 # CYRILLIC CAPITAL LETTER ES ACB4 0422 # CYRILLIC CAPITAL LETTER TE ACB5 0423 # CYRILLIC CAPITAL LETTER U ACB6 0424 # CYRILLIC CAPITAL LETTER EF ACB7 0425 # CYRILLIC CAPITAL LETTER HA ACB8 0426 # CYRILLIC CAPITAL LETTER TSE ACB9 0427 # CYRILLIC CAPITAL LETTER CHE ACBA 0428 # CYRILLIC CAPITAL LETTER SHA ACBB 0429 # CYRILLIC CAPITAL LETTER SHCHA ACBC 042A # CYRILLIC CAPITAL LETTER HARD SIGN ACBD 042B # CYRILLIC CAPITAL LETTER YERU ACBE 042C # CYRILLIC CAPITAL LETTER SOFT SIGN ACBF 042D # CYRILLIC CAPITAL LETTER E ACC0 042E # CYRILLIC CAPITAL LETTER YU ACC1 042F # CYRILLIC CAPITAL LETTER YA ACD1 0430 # CYRILLIC SMALL LETTER A ACD2 0431 # CYRILLIC SMALL LETTER BE ACD3 0432 # CYRILLIC SMALL LETTER VE ACD4 0433 # CYRILLIC SMALL LETTER GHE ACD5 0434 # CYRILLIC SMALL LETTER DE ACD6 0435 # CYRILLIC SMALL LETTER IE ACD7 0451 # CYRILLIC SMALL LETTER IO ACD8 0436 # CYRILLIC SMALL LETTER ZHE ACD9 0437 # CYRILLIC SMALL LETTER ZE ACDA 0438 # CYRILLIC SMALL LETTER I ACDB 0439 # CYRILLIC SMALL LETTER SHORT I ACDC 043A # CYRILLIC SMALL LETTER KA ACDD 043B # CYRILLIC SMALL LETTER EL ACDE 043C # CYRILLIC SMALL LETTER EM ACDF 043D # CYRILLIC SMALL LETTER EN ACE0 043E # CYRILLIC SMALL LETTER O ACE1 043F # CYRILLIC SMALL LETTER PE ACE2 0440 # CYRILLIC SMALL LETTER ER ACE3 0441 # CYRILLIC SMALL LETTER ES ACE4 0442 # CYRILLIC SMALL LETTER TE ACE5 0443 # CYRILLIC SMALL LETTER U ACE6 0444 # CYRILLIC SMALL LETTER EF ACE7 0445 # CYRILLIC SMALL LETTER HA ACE8 0446 # CYRILLIC SMALL LETTER TSE ACE9 0447 # CYRILLIC SMALL LETTER CHE ACEA 0448 # CYRILLIC SMALL LETTER SHA ACEB 0449 # CYRILLIC SMALL LETTER SHCHA ACEC 044A # CYRILLIC SMALL LETTER HARD SIGN ACED 044B # CYRILLIC SMALL LETTER YERU ACEE 044C # CYRILLIC SMALL LETTER SOFT SIGN ACEF 044D # CYRILLIC SMALL LETTER E ACF0 044E # CYRILLIC SMALL LETTER YU ACF1 044F # CYRILLIC SMALL LETTER YA AD41 CD61 # HANGUL SYLLABLE CHIEUCH-OE-NIEUNCIEUC AD42 CD62 # HANGUL SYLLABLE CHIEUCH-OE-NIEUNHIEUH AD43 CD63 # HANGUL SYLLABLE CHIEUCH-OE-TIKEUT AD44 CD65 # HANGUL SYLLABLE CHIEUCH-OE-RIEULKIYEOK AD45 CD66 # HANGUL SYLLABLE CHIEUCH-OE-RIEULMIEUM AD46 CD67 # HANGUL SYLLABLE CHIEUCH-OE-RIEULPIEUP AD47 CD68 # HANGUL SYLLABLE CHIEUCH-OE-RIEULSIOS AD48 CD69 # HANGUL SYLLABLE CHIEUCH-OE-RIEULTHIEUTH AD49 CD6A # HANGUL SYLLABLE CHIEUCH-OE-RIEULPHIEUPH AD4A CD6B # HANGUL SYLLABLE CHIEUCH-OE-RIEULHIEUH AD4B CD6E # HANGUL SYLLABLE CHIEUCH-OE-PIEUPSIOS AD4C CD70 # HANGUL SYLLABLE CHIEUCH-OE-SSANGSIOS AD4D CD72 # HANGUL SYLLABLE CHIEUCH-OE-CIEUC AD4E CD73 # HANGUL SYLLABLE CHIEUCH-OE-CHIEUCH AD4F CD74 # HANGUL SYLLABLE CHIEUCH-OE-KHIEUKH AD50 CD75 # HANGUL SYLLABLE CHIEUCH-OE-THIEUTH AD51 CD76 # HANGUL SYLLABLE CHIEUCH-OE-PHIEUPH AD52 CD77 # HANGUL SYLLABLE CHIEUCH-OE-HIEUH AD53 CD79 # HANGUL SYLLABLE CHIEUCH-YO-KIYEOK AD54 CD7A # HANGUL SYLLABLE CHIEUCH-YO-SSANGKIYEOK AD55 CD7B # HANGUL SYLLABLE CHIEUCH-YO-KIYEOKSIOS AD56 CD7C # HANGUL SYLLABLE CHIEUCH-YO-NIEUN AD57 CD7D # HANGUL SYLLABLE CHIEUCH-YO-NIEUNCIEUC AD58 CD7E # HANGUL SYLLABLE CHIEUCH-YO-NIEUNHIEUH AD59 CD7F # HANGUL SYLLABLE CHIEUCH-YO-TIKEUT AD5A CD80 # HANGUL SYLLABLE CHIEUCH-YO-RIEUL AD61 CD81 # HANGUL SYLLABLE CHIEUCH-YO-RIEULKIYEOK AD62 CD82 # HANGUL SYLLABLE CHIEUCH-YO-RIEULMIEUM AD63 CD83 # HANGUL SYLLABLE CHIEUCH-YO-RIEULPIEUP AD64 CD84 # HANGUL SYLLABLE CHIEUCH-YO-RIEULSIOS AD65 CD85 # HANGUL SYLLABLE CHIEUCH-YO-RIEULTHIEUTH AD66 CD86 # HANGUL SYLLABLE CHIEUCH-YO-RIEULPHIEUPH AD67 CD87 # HANGUL SYLLABLE CHIEUCH-YO-RIEULHIEUH AD68 CD89 # HANGUL SYLLABLE CHIEUCH-YO-PIEUP AD69 CD8A # HANGUL SYLLABLE CHIEUCH-YO-PIEUPSIOS AD6A CD8B # HANGUL SYLLABLE CHIEUCH-YO-SIOS AD6B CD8C # HANGUL SYLLABLE CHIEUCH-YO-SSANGSIOS AD6C CD8D # HANGUL SYLLABLE CHIEUCH-YO-IEUNG AD6D CD8E # HANGUL SYLLABLE CHIEUCH-YO-CIEUC AD6E CD8F # HANGUL SYLLABLE CHIEUCH-YO-CHIEUCH AD6F CD90 # HANGUL SYLLABLE CHIEUCH-YO-KHIEUKH AD70 CD91 # HANGUL SYLLABLE CHIEUCH-YO-THIEUTH AD71 CD92 # HANGUL SYLLABLE CHIEUCH-YO-PHIEUPH AD72 CD93 # HANGUL SYLLABLE CHIEUCH-YO-HIEUH AD73 CD96 # HANGUL SYLLABLE CHIEUCH-U-SSANGKIYEOK AD74 CD97 # HANGUL SYLLABLE CHIEUCH-U-KIYEOKSIOS AD75 CD99 # HANGUL SYLLABLE CHIEUCH-U-NIEUNCIEUC AD76 CD9A # HANGUL SYLLABLE CHIEUCH-U-NIEUNHIEUH AD77 CD9B # HANGUL SYLLABLE CHIEUCH-U-TIKEUT AD78 CD9D # HANGUL SYLLABLE CHIEUCH-U-RIEULKIYEOK AD79 CD9E # HANGUL SYLLABLE CHIEUCH-U-RIEULMIEUM AD7A CD9F # HANGUL SYLLABLE CHIEUCH-U-RIEULPIEUP AD81 CDA0 # HANGUL SYLLABLE CHIEUCH-U-RIEULSIOS AD82 CDA1 # HANGUL SYLLABLE CHIEUCH-U-RIEULTHIEUTH AD83 CDA2 # HANGUL SYLLABLE CHIEUCH-U-RIEULPHIEUPH AD84 CDA3 # HANGUL SYLLABLE CHIEUCH-U-RIEULHIEUH AD85 CDA6 # HANGUL SYLLABLE CHIEUCH-U-PIEUPSIOS AD86 CDA8 # HANGUL SYLLABLE CHIEUCH-U-SSANGSIOS AD87 CDAA # HANGUL SYLLABLE CHIEUCH-U-CIEUC AD88 CDAB # HANGUL SYLLABLE CHIEUCH-U-CHIEUCH AD89 CDAC # HANGUL SYLLABLE CHIEUCH-U-KHIEUKH AD8A CDAD # HANGUL SYLLABLE CHIEUCH-U-THIEUTH AD8B CDAE # HANGUL SYLLABLE CHIEUCH-U-PHIEUPH AD8C CDAF # HANGUL SYLLABLE CHIEUCH-U-HIEUH AD8D CDB1 # HANGUL SYLLABLE CHIEUCH-WEO-KIYEOK AD8E CDB2 # HANGUL SYLLABLE CHIEUCH-WEO-SSANGKIYEOK AD8F CDB3 # HANGUL SYLLABLE CHIEUCH-WEO-KIYEOKSIOS AD90 CDB4 # HANGUL SYLLABLE CHIEUCH-WEO-NIEUN AD91 CDB5 # HANGUL SYLLABLE CHIEUCH-WEO-NIEUNCIEUC AD92 CDB6 # HANGUL SYLLABLE CHIEUCH-WEO-NIEUNHIEUH AD93 CDB7 # HANGUL SYLLABLE CHIEUCH-WEO-TIKEUT AD94 CDB8 # HANGUL SYLLABLE CHIEUCH-WEO-RIEUL AD95 CDB9 # HANGUL SYLLABLE CHIEUCH-WEO-RIEULKIYEOK AD96 CDBA # HANGUL SYLLABLE CHIEUCH-WEO-RIEULMIEUM AD97 CDBB # HANGUL SYLLABLE CHIEUCH-WEO-RIEULPIEUP AD98 CDBC # HANGUL SYLLABLE CHIEUCH-WEO-RIEULSIOS AD99 CDBD # HANGUL SYLLABLE CHIEUCH-WEO-RIEULTHIEUTH AD9A CDBE # HANGUL SYLLABLE CHIEUCH-WEO-RIEULPHIEUPH AD9B CDBF # HANGUL SYLLABLE CHIEUCH-WEO-RIEULHIEUH AD9C CDC0 # HANGUL SYLLABLE CHIEUCH-WEO-MIEUM AD9D CDC1 # HANGUL SYLLABLE CHIEUCH-WEO-PIEUP AD9E CDC2 # HANGUL SYLLABLE CHIEUCH-WEO-PIEUPSIOS AD9F CDC3 # HANGUL SYLLABLE CHIEUCH-WEO-SIOS ADA0 CDC5 # HANGUL SYLLABLE CHIEUCH-WEO-IEUNG AE41 CDC6 # HANGUL SYLLABLE CHIEUCH-WEO-CIEUC AE42 CDC7 # HANGUL SYLLABLE CHIEUCH-WEO-CHIEUCH AE43 CDC8 # HANGUL SYLLABLE CHIEUCH-WEO-KHIEUKH AE44 CDC9 # HANGUL SYLLABLE CHIEUCH-WEO-THIEUTH AE45 CDCA # HANGUL SYLLABLE CHIEUCH-WEO-PHIEUPH AE46 CDCB # HANGUL SYLLABLE CHIEUCH-WEO-HIEUH AE47 CDCD # HANGUL SYLLABLE CHIEUCH-WE-KIYEOK AE48 CDCE # HANGUL SYLLABLE CHIEUCH-WE-SSANGKIYEOK AE49 CDCF # HANGUL SYLLABLE CHIEUCH-WE-KIYEOKSIOS AE4A CDD1 # HANGUL SYLLABLE CHIEUCH-WE-NIEUNCIEUC AE4B CDD2 # HANGUL SYLLABLE CHIEUCH-WE-NIEUNHIEUH AE4C CDD3 # HANGUL SYLLABLE CHIEUCH-WE-TIKEUT AE4D CDD4 # HANGUL SYLLABLE CHIEUCH-WE-RIEUL AE4E CDD5 # HANGUL SYLLABLE CHIEUCH-WE-RIEULKIYEOK AE4F CDD6 # HANGUL SYLLABLE CHIEUCH-WE-RIEULMIEUM AE50 CDD7 # HANGUL SYLLABLE CHIEUCH-WE-RIEULPIEUP AE51 CDD8 # HANGUL SYLLABLE CHIEUCH-WE-RIEULSIOS AE52 CDD9 # HANGUL SYLLABLE CHIEUCH-WE-RIEULTHIEUTH AE53 CDDA # HANGUL SYLLABLE CHIEUCH-WE-RIEULPHIEUPH AE54 CDDB # HANGUL SYLLABLE CHIEUCH-WE-RIEULHIEUH AE55 CDDC # HANGUL SYLLABLE CHIEUCH-WE-MIEUM AE56 CDDD # HANGUL SYLLABLE CHIEUCH-WE-PIEUP AE57 CDDE # HANGUL SYLLABLE CHIEUCH-WE-PIEUPSIOS AE58 CDDF # HANGUL SYLLABLE CHIEUCH-WE-SIOS AE59 CDE0 # HANGUL SYLLABLE CHIEUCH-WE-SSANGSIOS AE5A CDE1 # HANGUL SYLLABLE CHIEUCH-WE-IEUNG AE61 CDE2 # HANGUL SYLLABLE CHIEUCH-WE-CIEUC AE62 CDE3 # HANGUL SYLLABLE CHIEUCH-WE-CHIEUCH AE63 CDE4 # HANGUL SYLLABLE CHIEUCH-WE-KHIEUKH AE64 CDE5 # HANGUL SYLLABLE CHIEUCH-WE-THIEUTH AE65 CDE6 # HANGUL SYLLABLE CHIEUCH-WE-PHIEUPH AE66 CDE7 # HANGUL SYLLABLE CHIEUCH-WE-HIEUH AE67 CDE9 # HANGUL SYLLABLE CHIEUCH-WI-KIYEOK AE68 CDEA # HANGUL SYLLABLE CHIEUCH-WI-SSANGKIYEOK AE69 CDEB # HANGUL SYLLABLE CHIEUCH-WI-KIYEOKSIOS AE6A CDED # HANGUL SYLLABLE CHIEUCH-WI-NIEUNCIEUC AE6B CDEE # HANGUL SYLLABLE CHIEUCH-WI-NIEUNHIEUH AE6C CDEF # HANGUL SYLLABLE CHIEUCH-WI-TIKEUT AE6D CDF1 # HANGUL SYLLABLE CHIEUCH-WI-RIEULKIYEOK AE6E CDF2 # HANGUL SYLLABLE CHIEUCH-WI-RIEULMIEUM AE6F CDF3 # HANGUL SYLLABLE CHIEUCH-WI-RIEULPIEUP AE70 CDF4 # HANGUL SYLLABLE CHIEUCH-WI-RIEULSIOS AE71 CDF5 # HANGUL SYLLABLE CHIEUCH-WI-RIEULTHIEUTH AE72 CDF6 # HANGUL SYLLABLE CHIEUCH-WI-RIEULPHIEUPH AE73 CDF7 # HANGUL SYLLABLE CHIEUCH-WI-RIEULHIEUH AE74 CDFA # HANGUL SYLLABLE CHIEUCH-WI-PIEUPSIOS AE75 CDFC # HANGUL SYLLABLE CHIEUCH-WI-SSANGSIOS AE76 CDFE # HANGUL SYLLABLE CHIEUCH-WI-CIEUC AE77 CDFF # HANGUL SYLLABLE CHIEUCH-WI-CHIEUCH AE78 CE00 # HANGUL SYLLABLE CHIEUCH-WI-KHIEUKH AE79 CE01 # HANGUL SYLLABLE CHIEUCH-WI-THIEUTH AE7A CE02 # HANGUL SYLLABLE CHIEUCH-WI-PHIEUPH AE81 CE03 # HANGUL SYLLABLE CHIEUCH-WI-HIEUH AE82 CE05 # HANGUL SYLLABLE CHIEUCH-YU-KIYEOK AE83 CE06 # HANGUL SYLLABLE CHIEUCH-YU-SSANGKIYEOK AE84 CE07 # HANGUL SYLLABLE CHIEUCH-YU-KIYEOKSIOS AE85 CE09 # HANGUL SYLLABLE CHIEUCH-YU-NIEUNCIEUC AE86 CE0A # HANGUL SYLLABLE CHIEUCH-YU-NIEUNHIEUH AE87 CE0B # HANGUL SYLLABLE CHIEUCH-YU-TIKEUT AE88 CE0D # HANGUL SYLLABLE CHIEUCH-YU-RIEULKIYEOK AE89 CE0E # HANGUL SYLLABLE CHIEUCH-YU-RIEULMIEUM AE8A CE0F # HANGUL SYLLABLE CHIEUCH-YU-RIEULPIEUP AE8B CE10 # HANGUL SYLLABLE CHIEUCH-YU-RIEULSIOS AE8C CE11 # HANGUL SYLLABLE CHIEUCH-YU-RIEULTHIEUTH AE8D CE12 # HANGUL SYLLABLE CHIEUCH-YU-RIEULPHIEUPH AE8E CE13 # HANGUL SYLLABLE CHIEUCH-YU-RIEULHIEUH AE8F CE15 # HANGUL SYLLABLE CHIEUCH-YU-PIEUP AE90 CE16 # HANGUL SYLLABLE CHIEUCH-YU-PIEUPSIOS AE91 CE17 # HANGUL SYLLABLE CHIEUCH-YU-SIOS AE92 CE18 # HANGUL SYLLABLE CHIEUCH-YU-SSANGSIOS AE93 CE1A # HANGUL SYLLABLE CHIEUCH-YU-CIEUC AE94 CE1B # HANGUL SYLLABLE CHIEUCH-YU-CHIEUCH AE95 CE1C # HANGUL SYLLABLE CHIEUCH-YU-KHIEUKH AE96 CE1D # HANGUL SYLLABLE CHIEUCH-YU-THIEUTH AE97 CE1E # HANGUL SYLLABLE CHIEUCH-YU-PHIEUPH AE98 CE1F # HANGUL SYLLABLE CHIEUCH-YU-HIEUH AE99 CE22 # HANGUL SYLLABLE CHIEUCH-EU-SSANGKIYEOK AE9A CE23 # HANGUL SYLLABLE CHIEUCH-EU-KIYEOKSIOS AE9B CE25 # HANGUL SYLLABLE CHIEUCH-EU-NIEUNCIEUC AE9C CE26 # HANGUL SYLLABLE CHIEUCH-EU-NIEUNHIEUH AE9D CE27 # HANGUL SYLLABLE CHIEUCH-EU-TIKEUT AE9E CE29 # HANGUL SYLLABLE CHIEUCH-EU-RIEULKIYEOK AE9F CE2A # HANGUL SYLLABLE CHIEUCH-EU-RIEULMIEUM AEA0 CE2B # HANGUL SYLLABLE CHIEUCH-EU-RIEULPIEUP AF41 CE2C # HANGUL SYLLABLE CHIEUCH-EU-RIEULSIOS AF42 CE2D # HANGUL SYLLABLE CHIEUCH-EU-RIEULTHIEUTH AF43 CE2E # HANGUL SYLLABLE CHIEUCH-EU-RIEULPHIEUPH AF44 CE2F # HANGUL SYLLABLE CHIEUCH-EU-RIEULHIEUH AF45 CE32 # HANGUL SYLLABLE CHIEUCH-EU-PIEUPSIOS AF46 CE34 # HANGUL SYLLABLE CHIEUCH-EU-SSANGSIOS AF47 CE36 # HANGUL SYLLABLE CHIEUCH-EU-CIEUC AF48 CE37 # HANGUL SYLLABLE CHIEUCH-EU-CHIEUCH AF49 CE38 # HANGUL SYLLABLE CHIEUCH-EU-KHIEUKH AF4A CE39 # HANGUL SYLLABLE CHIEUCH-EU-THIEUTH AF4B CE3A # HANGUL SYLLABLE CHIEUCH-EU-PHIEUPH AF4C CE3B # HANGUL SYLLABLE CHIEUCH-EU-HIEUH AF4D CE3C # HANGUL SYLLABLE CHIEUCH-YI AF4E CE3D # HANGUL SYLLABLE CHIEUCH-YI-KIYEOK AF4F CE3E # HANGUL SYLLABLE CHIEUCH-YI-SSANGKIYEOK AF50 CE3F # HANGUL SYLLABLE CHIEUCH-YI-KIYEOKSIOS AF51 CE40 # HANGUL SYLLABLE CHIEUCH-YI-NIEUN AF52 CE41 # HANGUL SYLLABLE CHIEUCH-YI-NIEUNCIEUC AF53 CE42 # HANGUL SYLLABLE CHIEUCH-YI-NIEUNHIEUH AF54 CE43 # HANGUL SYLLABLE CHIEUCH-YI-TIKEUT AF55 CE44 # HANGUL SYLLABLE CHIEUCH-YI-RIEUL AF56 CE45 # HANGUL SYLLABLE CHIEUCH-YI-RIEULKIYEOK AF57 CE46 # HANGUL SYLLABLE CHIEUCH-YI-RIEULMIEUM AF58 CE47 # HANGUL SYLLABLE CHIEUCH-YI-RIEULPIEUP AF59 CE48 # HANGUL SYLLABLE CHIEUCH-YI-RIEULSIOS AF5A CE49 # HANGUL SYLLABLE CHIEUCH-YI-RIEULTHIEUTH AF61 CE4A # HANGUL SYLLABLE CHIEUCH-YI-RIEULPHIEUPH AF62 CE4B # HANGUL SYLLABLE CHIEUCH-YI-RIEULHIEUH AF63 CE4C # HANGUL SYLLABLE CHIEUCH-YI-MIEUM AF64 CE4D # HANGUL SYLLABLE CHIEUCH-YI-PIEUP AF65 CE4E # HANGUL SYLLABLE CHIEUCH-YI-PIEUPSIOS AF66 CE4F # HANGUL SYLLABLE CHIEUCH-YI-SIOS AF67 CE50 # HANGUL SYLLABLE CHIEUCH-YI-SSANGSIOS AF68 CE51 # HANGUL SYLLABLE CHIEUCH-YI-IEUNG AF69 CE52 # HANGUL SYLLABLE CHIEUCH-YI-CIEUC AF6A CE53 # HANGUL SYLLABLE CHIEUCH-YI-CHIEUCH AF6B CE54 # HANGUL SYLLABLE CHIEUCH-YI-KHIEUKH AF6C CE55 # HANGUL SYLLABLE CHIEUCH-YI-THIEUTH AF6D CE56 # HANGUL SYLLABLE CHIEUCH-YI-PHIEUPH AF6E CE57 # HANGUL SYLLABLE CHIEUCH-YI-HIEUH AF6F CE5A # HANGUL SYLLABLE CHIEUCH-I-SSANGKIYEOK AF70 CE5B # HANGUL SYLLABLE CHIEUCH-I-KIYEOKSIOS AF71 CE5D # HANGUL SYLLABLE CHIEUCH-I-NIEUNCIEUC AF72 CE5E # HANGUL SYLLABLE CHIEUCH-I-NIEUNHIEUH AF73 CE62 # HANGUL SYLLABLE CHIEUCH-I-RIEULMIEUM AF74 CE63 # HANGUL SYLLABLE CHIEUCH-I-RIEULPIEUP AF75 CE64 # HANGUL SYLLABLE CHIEUCH-I-RIEULSIOS AF76 CE65 # HANGUL SYLLABLE CHIEUCH-I-RIEULTHIEUTH AF77 CE66 # HANGUL SYLLABLE CHIEUCH-I-RIEULPHIEUPH AF78 CE67 # HANGUL SYLLABLE CHIEUCH-I-RIEULHIEUH AF79 CE6A # HANGUL SYLLABLE CHIEUCH-I-PIEUPSIOS AF7A CE6C # HANGUL SYLLABLE CHIEUCH-I-SSANGSIOS AF81 CE6E # HANGUL SYLLABLE CHIEUCH-I-CIEUC AF82 CE6F # HANGUL SYLLABLE CHIEUCH-I-CHIEUCH AF83 CE70 # HANGUL SYLLABLE CHIEUCH-I-KHIEUKH AF84 CE71 # HANGUL SYLLABLE CHIEUCH-I-THIEUTH AF85 CE72 # HANGUL SYLLABLE CHIEUCH-I-PHIEUPH AF86 CE73 # HANGUL SYLLABLE CHIEUCH-I-HIEUH AF87 CE76 # HANGUL SYLLABLE KHIEUKH-A-SSANGKIYEOK AF88 CE77 # HANGUL SYLLABLE KHIEUKH-A-KIYEOKSIOS AF89 CE79 # HANGUL SYLLABLE KHIEUKH-A-NIEUNCIEUC AF8A CE7A # HANGUL SYLLABLE KHIEUKH-A-NIEUNHIEUH AF8B CE7B # HANGUL SYLLABLE KHIEUKH-A-TIKEUT AF8C CE7D # HANGUL SYLLABLE KHIEUKH-A-RIEULKIYEOK AF8D CE7E # HANGUL SYLLABLE KHIEUKH-A-RIEULMIEUM AF8E CE7F # HANGUL SYLLABLE KHIEUKH-A-RIEULPIEUP AF8F CE80 # HANGUL SYLLABLE KHIEUKH-A-RIEULSIOS AF90 CE81 # HANGUL SYLLABLE KHIEUKH-A-RIEULTHIEUTH AF91 CE82 # HANGUL SYLLABLE KHIEUKH-A-RIEULPHIEUPH AF92 CE83 # HANGUL SYLLABLE KHIEUKH-A-RIEULHIEUH AF93 CE86 # HANGUL SYLLABLE KHIEUKH-A-PIEUPSIOS AF94 CE88 # HANGUL SYLLABLE KHIEUKH-A-SSANGSIOS AF95 CE8A # HANGUL SYLLABLE KHIEUKH-A-CIEUC AF96 CE8B # HANGUL SYLLABLE KHIEUKH-A-CHIEUCH AF97 CE8C # HANGUL SYLLABLE KHIEUKH-A-KHIEUKH AF98 CE8D # HANGUL SYLLABLE KHIEUKH-A-THIEUTH AF99 CE8E # HANGUL SYLLABLE KHIEUKH-A-PHIEUPH AF9A CE8F # HANGUL SYLLABLE KHIEUKH-A-HIEUH AF9B CE92 # HANGUL SYLLABLE KHIEUKH-AE-SSANGKIYEOK AF9C CE93 # HANGUL SYLLABLE KHIEUKH-AE-KIYEOKSIOS AF9D CE95 # HANGUL SYLLABLE KHIEUKH-AE-NIEUNCIEUC AF9E CE96 # HANGUL SYLLABLE KHIEUKH-AE-NIEUNHIEUH AF9F CE97 # HANGUL SYLLABLE KHIEUKH-AE-TIKEUT AFA0 CE99 # HANGUL SYLLABLE KHIEUKH-AE-RIEULKIYEOK B041 CE9A # HANGUL SYLLABLE KHIEUKH-AE-RIEULMIEUM B042 CE9B # HANGUL SYLLABLE KHIEUKH-AE-RIEULPIEUP B043 CE9C # HANGUL SYLLABLE KHIEUKH-AE-RIEULSIOS B044 CE9D # HANGUL SYLLABLE KHIEUKH-AE-RIEULTHIEUTH B045 CE9E # HANGUL SYLLABLE KHIEUKH-AE-RIEULPHIEUPH B046 CE9F # HANGUL SYLLABLE KHIEUKH-AE-RIEULHIEUH B047 CEA2 # HANGUL SYLLABLE KHIEUKH-AE-PIEUPSIOS B048 CEA6 # HANGUL SYLLABLE KHIEUKH-AE-CIEUC B049 CEA7 # HANGUL SYLLABLE KHIEUKH-AE-CHIEUCH B04A CEA8 # HANGUL SYLLABLE KHIEUKH-AE-KHIEUKH B04B CEA9 # HANGUL SYLLABLE KHIEUKH-AE-THIEUTH B04C CEAA # HANGUL SYLLABLE KHIEUKH-AE-PHIEUPH B04D CEAB # HANGUL SYLLABLE KHIEUKH-AE-HIEUH B04E CEAE # HANGUL SYLLABLE KHIEUKH-YA-SSANGKIYEOK B04F CEAF # HANGUL SYLLABLE KHIEUKH-YA-KIYEOKSIOS B050 CEB0 # HANGUL SYLLABLE KHIEUKH-YA-NIEUN B051 CEB1 # HANGUL SYLLABLE KHIEUKH-YA-NIEUNCIEUC B052 CEB2 # HANGUL SYLLABLE KHIEUKH-YA-NIEUNHIEUH B053 CEB3 # HANGUL SYLLABLE KHIEUKH-YA-TIKEUT B054 CEB4 # HANGUL SYLLABLE KHIEUKH-YA-RIEUL B055 CEB5 # HANGUL SYLLABLE KHIEUKH-YA-RIEULKIYEOK B056 CEB6 # HANGUL SYLLABLE KHIEUKH-YA-RIEULMIEUM B057 CEB7 # HANGUL SYLLABLE KHIEUKH-YA-RIEULPIEUP B058 CEB8 # HANGUL SYLLABLE KHIEUKH-YA-RIEULSIOS B059 CEB9 # HANGUL SYLLABLE KHIEUKH-YA-RIEULTHIEUTH B05A CEBA # HANGUL SYLLABLE KHIEUKH-YA-RIEULPHIEUPH B061 CEBB # HANGUL SYLLABLE KHIEUKH-YA-RIEULHIEUH B062 CEBC # HANGUL SYLLABLE KHIEUKH-YA-MIEUM B063 CEBD # HANGUL SYLLABLE KHIEUKH-YA-PIEUP B064 CEBE # HANGUL SYLLABLE KHIEUKH-YA-PIEUPSIOS B065 CEBF # HANGUL SYLLABLE KHIEUKH-YA-SIOS B066 CEC0 # HANGUL SYLLABLE KHIEUKH-YA-SSANGSIOS B067 CEC2 # HANGUL SYLLABLE KHIEUKH-YA-CIEUC B068 CEC3 # HANGUL SYLLABLE KHIEUKH-YA-CHIEUCH B069 CEC4 # HANGUL SYLLABLE KHIEUKH-YA-KHIEUKH B06A CEC5 # HANGUL SYLLABLE KHIEUKH-YA-THIEUTH B06B CEC6 # HANGUL SYLLABLE KHIEUKH-YA-PHIEUPH B06C CEC7 # HANGUL SYLLABLE KHIEUKH-YA-HIEUH B06D CEC8 # HANGUL SYLLABLE KHIEUKH-YAE B06E CEC9 # HANGUL SYLLABLE KHIEUKH-YAE-KIYEOK B06F CECA # HANGUL SYLLABLE KHIEUKH-YAE-SSANGKIYEOK B070 CECB # HANGUL SYLLABLE KHIEUKH-YAE-KIYEOKSIOS B071 CECC # HANGUL SYLLABLE KHIEUKH-YAE-NIEUN B072 CECD # HANGUL SYLLABLE KHIEUKH-YAE-NIEUNCIEUC B073 CECE # HANGUL SYLLABLE KHIEUKH-YAE-NIEUNHIEUH B074 CECF # HANGUL SYLLABLE KHIEUKH-YAE-TIKEUT B075 CED0 # HANGUL SYLLABLE KHIEUKH-YAE-RIEUL B076 CED1 # HANGUL SYLLABLE KHIEUKH-YAE-RIEULKIYEOK B077 CED2 # HANGUL SYLLABLE KHIEUKH-YAE-RIEULMIEUM B078 CED3 # HANGUL SYLLABLE KHIEUKH-YAE-RIEULPIEUP B079 CED4 # HANGUL SYLLABLE KHIEUKH-YAE-RIEULSIOS B07A CED5 # HANGUL SYLLABLE KHIEUKH-YAE-RIEULTHIEUTH B081 CED6 # HANGUL SYLLABLE KHIEUKH-YAE-RIEULPHIEUPH B082 CED7 # HANGUL SYLLABLE KHIEUKH-YAE-RIEULHIEUH B083 CED8 # HANGUL SYLLABLE KHIEUKH-YAE-MIEUM B084 CED9 # HANGUL SYLLABLE KHIEUKH-YAE-PIEUP B085 CEDA # HANGUL SYLLABLE KHIEUKH-YAE-PIEUPSIOS B086 CEDB # HANGUL SYLLABLE KHIEUKH-YAE-SIOS B087 CEDC # HANGUL SYLLABLE KHIEUKH-YAE-SSANGSIOS B088 CEDD # HANGUL SYLLABLE KHIEUKH-YAE-IEUNG B089 CEDE # HANGUL SYLLABLE KHIEUKH-YAE-CIEUC B08A CEDF # HANGUL SYLLABLE KHIEUKH-YAE-CHIEUCH B08B CEE0 # HANGUL SYLLABLE KHIEUKH-YAE-KHIEUKH B08C CEE1 # HANGUL SYLLABLE KHIEUKH-YAE-THIEUTH B08D CEE2 # HANGUL SYLLABLE KHIEUKH-YAE-PHIEUPH B08E CEE3 # HANGUL SYLLABLE KHIEUKH-YAE-HIEUH B08F CEE6 # HANGUL SYLLABLE KHIEUKH-EO-SSANGKIYEOK B090 CEE7 # HANGUL SYLLABLE KHIEUKH-EO-KIYEOKSIOS B091 CEE9 # HANGUL SYLLABLE KHIEUKH-EO-NIEUNCIEUC B092 CEEA # HANGUL SYLLABLE KHIEUKH-EO-NIEUNHIEUH B093 CEED # HANGUL SYLLABLE KHIEUKH-EO-RIEULKIYEOK B094 CEEE # HANGUL SYLLABLE KHIEUKH-EO-RIEULMIEUM B095 CEEF # HANGUL SYLLABLE KHIEUKH-EO-RIEULPIEUP B096 CEF0 # HANGUL SYLLABLE KHIEUKH-EO-RIEULSIOS B097 CEF1 # HANGUL SYLLABLE KHIEUKH-EO-RIEULTHIEUTH B098 CEF2 # HANGUL SYLLABLE KHIEUKH-EO-RIEULPHIEUPH B099 CEF3 # HANGUL SYLLABLE KHIEUKH-EO-RIEULHIEUH B09A CEF6 # HANGUL SYLLABLE KHIEUKH-EO-PIEUPSIOS B09B CEFA # HANGUL SYLLABLE KHIEUKH-EO-CIEUC B09C CEFB # HANGUL SYLLABLE KHIEUKH-EO-CHIEUCH B09D CEFC # HANGUL SYLLABLE KHIEUKH-EO-KHIEUKH B09E CEFD # HANGUL SYLLABLE KHIEUKH-EO-THIEUTH B09F CEFE # HANGUL SYLLABLE KHIEUKH-EO-PHIEUPH B0A0 CEFF # HANGUL SYLLABLE KHIEUKH-EO-HIEUH B0A1 AC00 # HANGUL SYLLABLE KIYEOK-A B0A2 AC01 # HANGUL SYLLABLE KIYEOK-A-KIYEOK B0A3 AC04 # HANGUL SYLLABLE KIYEOK-A-NIEUN B0A4 AC07 # HANGUL SYLLABLE KIYEOK-A-TIKEUT B0A5 AC08 # HANGUL SYLLABLE KIYEOK-A-RIEUL B0A6 AC09 # HANGUL SYLLABLE KIYEOK-A-RIEULKIYEOK B0A7 AC0A # HANGUL SYLLABLE KIYEOK-A-RIEULMIEUM B0A8 AC10 # HANGUL SYLLABLE KIYEOK-A-MIEUM B0A9 AC11 # HANGUL SYLLABLE KIYEOK-A-PIEUP B0AA AC12 # HANGUL SYLLABLE KIYEOK-A-PIEUPSIOS B0AB AC13 # HANGUL SYLLABLE KIYEOK-A-SIOS B0AC AC14 # HANGUL SYLLABLE KIYEOK-A-SSANGSIOS B0AD AC15 # HANGUL SYLLABLE KIYEOK-A-IEUNG B0AE AC16 # HANGUL SYLLABLE KIYEOK-A-CIEUC B0AF AC17 # HANGUL SYLLABLE KIYEOK-A-CHIEUCH B0B0 AC19 # HANGUL SYLLABLE KIYEOK-A-THIEUTH B0B1 AC1A # HANGUL SYLLABLE KIYEOK-A-PHIEUPH B0B2 AC1B # HANGUL SYLLABLE KIYEOK-A-HIEUH B0B3 AC1C # HANGUL SYLLABLE KIYEOK-AE B0B4 AC1D # HANGUL SYLLABLE KIYEOK-AE-KIYEOK B0B5 AC20 # HANGUL SYLLABLE KIYEOK-AE-NIEUN B0B6 AC24 # HANGUL SYLLABLE KIYEOK-AE-RIEUL B0B7 AC2C # HANGUL SYLLABLE KIYEOK-AE-MIEUM B0B8 AC2D # HANGUL SYLLABLE KIYEOK-AE-PIEUP B0B9 AC2F # HANGUL SYLLABLE KIYEOK-AE-SIOS B0BA AC30 # HANGUL SYLLABLE KIYEOK-AE-SSANGSIOS B0BB AC31 # HANGUL SYLLABLE KIYEOK-AE-IEUNG B0BC AC38 # HANGUL SYLLABLE KIYEOK-YA B0BD AC39 # HANGUL SYLLABLE KIYEOK-YA-KIYEOK B0BE AC3C # HANGUL SYLLABLE KIYEOK-YA-NIEUN B0BF AC40 # HANGUL SYLLABLE KIYEOK-YA-RIEUL B0C0 AC4B # HANGUL SYLLABLE KIYEOK-YA-SIOS B0C1 AC4D # HANGUL SYLLABLE KIYEOK-YA-IEUNG B0C2 AC54 # HANGUL SYLLABLE KIYEOK-YAE B0C3 AC58 # HANGUL SYLLABLE KIYEOK-YAE-NIEUN B0C4 AC5C # HANGUL SYLLABLE KIYEOK-YAE-RIEUL B0C5 AC70 # HANGUL SYLLABLE KIYEOK-EO B0C6 AC71 # HANGUL SYLLABLE KIYEOK-EO-KIYEOK B0C7 AC74 # HANGUL SYLLABLE KIYEOK-EO-NIEUN B0C8 AC77 # HANGUL SYLLABLE KIYEOK-EO-TIKEUT B0C9 AC78 # HANGUL SYLLABLE KIYEOK-EO-RIEUL B0CA AC7A # HANGUL SYLLABLE KIYEOK-EO-RIEULMIEUM B0CB AC80 # HANGUL SYLLABLE KIYEOK-EO-MIEUM B0CC AC81 # HANGUL SYLLABLE KIYEOK-EO-PIEUP B0CD AC83 # HANGUL SYLLABLE KIYEOK-EO-SIOS B0CE AC84 # HANGUL SYLLABLE KIYEOK-EO-SSANGSIOS B0CF AC85 # HANGUL SYLLABLE KIYEOK-EO-IEUNG B0D0 AC86 # HANGUL SYLLABLE KIYEOK-EO-CIEUC B0D1 AC89 # HANGUL SYLLABLE KIYEOK-EO-THIEUTH B0D2 AC8A # HANGUL SYLLABLE KIYEOK-EO-PHIEUPH B0D3 AC8B # HANGUL SYLLABLE KIYEOK-EO-HIEUH B0D4 AC8C # HANGUL SYLLABLE KIYEOK-E B0D5 AC90 # HANGUL SYLLABLE KIYEOK-E-NIEUN B0D6 AC94 # HANGUL SYLLABLE KIYEOK-E-RIEUL B0D7 AC9C # HANGUL SYLLABLE KIYEOK-E-MIEUM B0D8 AC9D # HANGUL SYLLABLE KIYEOK-E-PIEUP B0D9 AC9F # HANGUL SYLLABLE KIYEOK-E-SIOS B0DA ACA0 # HANGUL SYLLABLE KIYEOK-E-SSANGSIOS B0DB ACA1 # HANGUL SYLLABLE KIYEOK-E-IEUNG B0DC ACA8 # HANGUL SYLLABLE KIYEOK-YEO B0DD ACA9 # HANGUL SYLLABLE KIYEOK-YEO-KIYEOK B0DE ACAA # HANGUL SYLLABLE KIYEOK-YEO-SSANGKIYEOK B0DF ACAC # HANGUL SYLLABLE KIYEOK-YEO-NIEUN B0E0 ACAF # HANGUL SYLLABLE KIYEOK-YEO-TIKEUT B0E1 ACB0 # HANGUL SYLLABLE KIYEOK-YEO-RIEUL B0E2 ACB8 # HANGUL SYLLABLE KIYEOK-YEO-MIEUM B0E3 ACB9 # HANGUL SYLLABLE KIYEOK-YEO-PIEUP B0E4 ACBB # HANGUL SYLLABLE KIYEOK-YEO-SIOS B0E5 ACBC # HANGUL SYLLABLE KIYEOK-YEO-SSANGSIOS B0E6 ACBD # HANGUL SYLLABLE KIYEOK-YEO-IEUNG B0E7 ACC1 # HANGUL SYLLABLE KIYEOK-YEO-THIEUTH B0E8 ACC4 # HANGUL SYLLABLE KIYEOK-YE B0E9 ACC8 # HANGUL SYLLABLE KIYEOK-YE-NIEUN B0EA ACCC # HANGUL SYLLABLE KIYEOK-YE-RIEUL B0EB ACD5 # HANGUL SYLLABLE KIYEOK-YE-PIEUP B0EC ACD7 # HANGUL SYLLABLE KIYEOK-YE-SIOS B0ED ACE0 # HANGUL SYLLABLE KIYEOK-O B0EE ACE1 # HANGUL SYLLABLE KIYEOK-O-KIYEOK B0EF ACE4 # HANGUL SYLLABLE KIYEOK-O-NIEUN B0F0 ACE7 # HANGUL SYLLABLE KIYEOK-O-TIKEUT B0F1 ACE8 # HANGUL SYLLABLE KIYEOK-O-RIEUL B0F2 ACEA # HANGUL SYLLABLE KIYEOK-O-RIEULMIEUM B0F3 ACEC # HANGUL SYLLABLE KIYEOK-O-RIEULSIOS B0F4 ACEF # HANGUL SYLLABLE KIYEOK-O-RIEULHIEUH B0F5 ACF0 # HANGUL SYLLABLE KIYEOK-O-MIEUM B0F6 ACF1 # HANGUL SYLLABLE KIYEOK-O-PIEUP B0F7 ACF3 # HANGUL SYLLABLE KIYEOK-O-SIOS B0F8 ACF5 # HANGUL SYLLABLE KIYEOK-O-IEUNG B0F9 ACF6 # HANGUL SYLLABLE KIYEOK-O-CIEUC B0FA ACFC # HANGUL SYLLABLE KIYEOK-WA B0FB ACFD # HANGUL SYLLABLE KIYEOK-WA-KIYEOK B0FC AD00 # HANGUL SYLLABLE KIYEOK-WA-NIEUN B0FD AD04 # HANGUL SYLLABLE KIYEOK-WA-RIEUL B0FE AD06 # HANGUL SYLLABLE KIYEOK-WA-RIEULMIEUM B141 CF02 # HANGUL SYLLABLE KHIEUKH-E-SSANGKIYEOK B142 CF03 # HANGUL SYLLABLE KHIEUKH-E-KIYEOKSIOS B143 CF05 # HANGUL SYLLABLE KHIEUKH-E-NIEUNCIEUC B144 CF06 # HANGUL SYLLABLE KHIEUKH-E-NIEUNHIEUH B145 CF07 # HANGUL SYLLABLE KHIEUKH-E-TIKEUT B146 CF09 # HANGUL SYLLABLE KHIEUKH-E-RIEULKIYEOK B147 CF0A # HANGUL SYLLABLE KHIEUKH-E-RIEULMIEUM B148 CF0B # HANGUL SYLLABLE KHIEUKH-E-RIEULPIEUP B149 CF0C # HANGUL SYLLABLE KHIEUKH-E-RIEULSIOS B14A CF0D # HANGUL SYLLABLE KHIEUKH-E-RIEULTHIEUTH B14B CF0E # HANGUL SYLLABLE KHIEUKH-E-RIEULPHIEUPH B14C CF0F # HANGUL SYLLABLE KHIEUKH-E-RIEULHIEUH B14D CF12 # HANGUL SYLLABLE KHIEUKH-E-PIEUPSIOS B14E CF14 # HANGUL SYLLABLE KHIEUKH-E-SSANGSIOS B14F CF16 # HANGUL SYLLABLE KHIEUKH-E-CIEUC B150 CF17 # HANGUL SYLLABLE KHIEUKH-E-CHIEUCH B151 CF18 # HANGUL SYLLABLE KHIEUKH-E-KHIEUKH B152 CF19 # HANGUL SYLLABLE KHIEUKH-E-THIEUTH B153 CF1A # HANGUL SYLLABLE KHIEUKH-E-PHIEUPH B154 CF1B # HANGUL SYLLABLE KHIEUKH-E-HIEUH B155 CF1D # HANGUL SYLLABLE KHIEUKH-YEO-KIYEOK B156 CF1E # HANGUL SYLLABLE KHIEUKH-YEO-SSANGKIYEOK B157 CF1F # HANGUL SYLLABLE KHIEUKH-YEO-KIYEOKSIOS B158 CF21 # HANGUL SYLLABLE KHIEUKH-YEO-NIEUNCIEUC B159 CF22 # HANGUL SYLLABLE KHIEUKH-YEO-NIEUNHIEUH B15A CF23 # HANGUL SYLLABLE KHIEUKH-YEO-TIKEUT B161 CF25 # HANGUL SYLLABLE KHIEUKH-YEO-RIEULKIYEOK B162 CF26 # HANGUL SYLLABLE KHIEUKH-YEO-RIEULMIEUM B163 CF27 # HANGUL SYLLABLE KHIEUKH-YEO-RIEULPIEUP B164 CF28 # HANGUL SYLLABLE KHIEUKH-YEO-RIEULSIOS B165 CF29 # HANGUL SYLLABLE KHIEUKH-YEO-RIEULTHIEUTH B166 CF2A # HANGUL SYLLABLE KHIEUKH-YEO-RIEULPHIEUPH B167 CF2B # HANGUL SYLLABLE KHIEUKH-YEO-RIEULHIEUH B168 CF2E # HANGUL SYLLABLE KHIEUKH-YEO-PIEUPSIOS B169 CF32 # HANGUL SYLLABLE KHIEUKH-YEO-CIEUC B16A CF33 # HANGUL SYLLABLE KHIEUKH-YEO-CHIEUCH B16B CF34 # HANGUL SYLLABLE KHIEUKH-YEO-KHIEUKH B16C CF35 # HANGUL SYLLABLE KHIEUKH-YEO-THIEUTH B16D CF36 # HANGUL SYLLABLE KHIEUKH-YEO-PHIEUPH B16E CF37 # HANGUL SYLLABLE KHIEUKH-YEO-HIEUH B16F CF39 # HANGUL SYLLABLE KHIEUKH-YE-KIYEOK B170 CF3A # HANGUL SYLLABLE KHIEUKH-YE-SSANGKIYEOK B171 CF3B # HANGUL SYLLABLE KHIEUKH-YE-KIYEOKSIOS B172 CF3C # HANGUL SYLLABLE KHIEUKH-YE-NIEUN B173 CF3D # HANGUL SYLLABLE KHIEUKH-YE-NIEUNCIEUC B174 CF3E # HANGUL SYLLABLE KHIEUKH-YE-NIEUNHIEUH B175 CF3F # HANGUL SYLLABLE KHIEUKH-YE-TIKEUT B176 CF40 # HANGUL SYLLABLE KHIEUKH-YE-RIEUL B177 CF41 # HANGUL SYLLABLE KHIEUKH-YE-RIEULKIYEOK B178 CF42 # HANGUL SYLLABLE KHIEUKH-YE-RIEULMIEUM B179 CF43 # HANGUL SYLLABLE KHIEUKH-YE-RIEULPIEUP B17A CF44 # HANGUL SYLLABLE KHIEUKH-YE-RIEULSIOS B181 CF45 # HANGUL SYLLABLE KHIEUKH-YE-RIEULTHIEUTH B182 CF46 # HANGUL SYLLABLE KHIEUKH-YE-RIEULPHIEUPH B183 CF47 # HANGUL SYLLABLE KHIEUKH-YE-RIEULHIEUH B184 CF48 # HANGUL SYLLABLE KHIEUKH-YE-MIEUM B185 CF49 # HANGUL SYLLABLE KHIEUKH-YE-PIEUP B186 CF4A # HANGUL SYLLABLE KHIEUKH-YE-PIEUPSIOS B187 CF4B # HANGUL SYLLABLE KHIEUKH-YE-SIOS B188 CF4C # HANGUL SYLLABLE KHIEUKH-YE-SSANGSIOS B189 CF4D # HANGUL SYLLABLE KHIEUKH-YE-IEUNG B18A CF4E # HANGUL SYLLABLE KHIEUKH-YE-CIEUC B18B CF4F # HANGUL SYLLABLE KHIEUKH-YE-CHIEUCH B18C CF50 # HANGUL SYLLABLE KHIEUKH-YE-KHIEUKH B18D CF51 # HANGUL SYLLABLE KHIEUKH-YE-THIEUTH B18E CF52 # HANGUL SYLLABLE KHIEUKH-YE-PHIEUPH B18F CF53 # HANGUL SYLLABLE KHIEUKH-YE-HIEUH B190 CF56 # HANGUL SYLLABLE KHIEUKH-O-SSANGKIYEOK B191 CF57 # HANGUL SYLLABLE KHIEUKH-O-KIYEOKSIOS B192 CF59 # HANGUL SYLLABLE KHIEUKH-O-NIEUNCIEUC B193 CF5A # HANGUL SYLLABLE KHIEUKH-O-NIEUNHIEUH B194 CF5B # HANGUL SYLLABLE KHIEUKH-O-TIKEUT B195 CF5D # HANGUL SYLLABLE KHIEUKH-O-RIEULKIYEOK B196 CF5E # HANGUL SYLLABLE KHIEUKH-O-RIEULMIEUM B197 CF5F # HANGUL SYLLABLE KHIEUKH-O-RIEULPIEUP B198 CF60 # HANGUL SYLLABLE KHIEUKH-O-RIEULSIOS B199 CF61 # HANGUL SYLLABLE KHIEUKH-O-RIEULTHIEUTH B19A CF62 # HANGUL SYLLABLE KHIEUKH-O-RIEULPHIEUPH B19B CF63 # HANGUL SYLLABLE KHIEUKH-O-RIEULHIEUH B19C CF66 # HANGUL SYLLABLE KHIEUKH-O-PIEUPSIOS B19D CF68 # HANGUL SYLLABLE KHIEUKH-O-SSANGSIOS B19E CF6A # HANGUL SYLLABLE KHIEUKH-O-CIEUC B19F CF6B # HANGUL SYLLABLE KHIEUKH-O-CHIEUCH B1A0 CF6C # HANGUL SYLLABLE KHIEUKH-O-KHIEUKH B1A1 AD0C # HANGUL SYLLABLE KIYEOK-WA-MIEUM B1A2 AD0D # HANGUL SYLLABLE KIYEOK-WA-PIEUP B1A3 AD0F # HANGUL SYLLABLE KIYEOK-WA-SIOS B1A4 AD11 # HANGUL SYLLABLE KIYEOK-WA-IEUNG B1A5 AD18 # HANGUL SYLLABLE KIYEOK-WAE B1A6 AD1C # HANGUL SYLLABLE KIYEOK-WAE-NIEUN B1A7 AD20 # HANGUL SYLLABLE KIYEOK-WAE-RIEUL B1A8 AD29 # HANGUL SYLLABLE KIYEOK-WAE-PIEUP B1A9 AD2C # HANGUL SYLLABLE KIYEOK-WAE-SSANGSIOS B1AA AD2D # HANGUL SYLLABLE KIYEOK-WAE-IEUNG B1AB AD34 # HANGUL SYLLABLE KIYEOK-OE B1AC AD35 # HANGUL SYLLABLE KIYEOK-OE-KIYEOK B1AD AD38 # HANGUL SYLLABLE KIYEOK-OE-NIEUN B1AE AD3C # HANGUL SYLLABLE KIYEOK-OE-RIEUL B1AF AD44 # HANGUL SYLLABLE KIYEOK-OE-MIEUM B1B0 AD45 # HANGUL SYLLABLE KIYEOK-OE-PIEUP B1B1 AD47 # HANGUL SYLLABLE KIYEOK-OE-SIOS B1B2 AD49 # HANGUL SYLLABLE KIYEOK-OE-IEUNG B1B3 AD50 # HANGUL SYLLABLE KIYEOK-YO B1B4 AD54 # HANGUL SYLLABLE KIYEOK-YO-NIEUN B1B5 AD58 # HANGUL SYLLABLE KIYEOK-YO-RIEUL B1B6 AD61 # HANGUL SYLLABLE KIYEOK-YO-PIEUP B1B7 AD63 # HANGUL SYLLABLE KIYEOK-YO-SIOS B1B8 AD6C # HANGUL SYLLABLE KIYEOK-U B1B9 AD6D # HANGUL SYLLABLE KIYEOK-U-KIYEOK B1BA AD70 # HANGUL SYLLABLE KIYEOK-U-NIEUN B1BB AD73 # HANGUL SYLLABLE KIYEOK-U-TIKEUT B1BC AD74 # HANGUL SYLLABLE KIYEOK-U-RIEUL B1BD AD75 # HANGUL SYLLABLE KIYEOK-U-RIEULKIYEOK B1BE AD76 # HANGUL SYLLABLE KIYEOK-U-RIEULMIEUM B1BF AD7B # HANGUL SYLLABLE KIYEOK-U-RIEULHIEUH B1C0 AD7C # HANGUL SYLLABLE KIYEOK-U-MIEUM B1C1 AD7D # HANGUL SYLLABLE KIYEOK-U-PIEUP B1C2 AD7F # HANGUL SYLLABLE KIYEOK-U-SIOS B1C3 AD81 # HANGUL SYLLABLE KIYEOK-U-IEUNG B1C4 AD82 # HANGUL SYLLABLE KIYEOK-U-CIEUC B1C5 AD88 # HANGUL SYLLABLE KIYEOK-WEO B1C6 AD89 # HANGUL SYLLABLE KIYEOK-WEO-KIYEOK B1C7 AD8C # HANGUL SYLLABLE KIYEOK-WEO-NIEUN B1C8 AD90 # HANGUL SYLLABLE KIYEOK-WEO-RIEUL B1C9 AD9C # HANGUL SYLLABLE KIYEOK-WEO-SSANGSIOS B1CA AD9D # HANGUL SYLLABLE KIYEOK-WEO-IEUNG B1CB ADA4 # HANGUL SYLLABLE KIYEOK-WE B1CC ADB7 # HANGUL SYLLABLE KIYEOK-WE-SIOS B1CD ADC0 # HANGUL SYLLABLE KIYEOK-WI B1CE ADC1 # HANGUL SYLLABLE KIYEOK-WI-KIYEOK B1CF ADC4 # HANGUL SYLLABLE KIYEOK-WI-NIEUN B1D0 ADC8 # HANGUL SYLLABLE KIYEOK-WI-RIEUL B1D1 ADD0 # HANGUL SYLLABLE KIYEOK-WI-MIEUM B1D2 ADD1 # HANGUL SYLLABLE KIYEOK-WI-PIEUP B1D3 ADD3 # HANGUL SYLLABLE KIYEOK-WI-SIOS B1D4 ADDC # HANGUL SYLLABLE KIYEOK-YU B1D5 ADE0 # HANGUL SYLLABLE KIYEOK-YU-NIEUN B1D6 ADE4 # HANGUL SYLLABLE KIYEOK-YU-RIEUL B1D7 ADF8 # HANGUL SYLLABLE KIYEOK-EU B1D8 ADF9 # HANGUL SYLLABLE KIYEOK-EU-KIYEOK B1D9 ADFC # HANGUL SYLLABLE KIYEOK-EU-NIEUN B1DA ADFF # HANGUL SYLLABLE KIYEOK-EU-TIKEUT B1DB AE00 # HANGUL SYLLABLE KIYEOK-EU-RIEUL B1DC AE01 # HANGUL SYLLABLE KIYEOK-EU-RIEULKIYEOK B1DD AE08 # HANGUL SYLLABLE KIYEOK-EU-MIEUM B1DE AE09 # HANGUL SYLLABLE KIYEOK-EU-PIEUP B1DF AE0B # HANGUL SYLLABLE KIYEOK-EU-SIOS B1E0 AE0D # HANGUL SYLLABLE KIYEOK-EU-IEUNG B1E1 AE14 # HANGUL SYLLABLE KIYEOK-YI B1E2 AE30 # HANGUL SYLLABLE KIYEOK-I B1E3 AE31 # HANGUL SYLLABLE KIYEOK-I-KIYEOK B1E4 AE34 # HANGUL SYLLABLE KIYEOK-I-NIEUN B1E5 AE37 # HANGUL SYLLABLE KIYEOK-I-TIKEUT B1E6 AE38 # HANGUL SYLLABLE KIYEOK-I-RIEUL B1E7 AE3A # HANGUL SYLLABLE KIYEOK-I-RIEULMIEUM B1E8 AE40 # HANGUL SYLLABLE KIYEOK-I-MIEUM B1E9 AE41 # HANGUL SYLLABLE KIYEOK-I-PIEUP B1EA AE43 # HANGUL SYLLABLE KIYEOK-I-SIOS B1EB AE45 # HANGUL SYLLABLE KIYEOK-I-IEUNG B1EC AE46 # HANGUL SYLLABLE KIYEOK-I-CIEUC B1ED AE4A # HANGUL SYLLABLE KIYEOK-I-PHIEUPH B1EE AE4C # HANGUL SYLLABLE SSANGKIYEOK-A B1EF AE4D # HANGUL SYLLABLE SSANGKIYEOK-A-KIYEOK B1F0 AE4E # HANGUL SYLLABLE SSANGKIYEOK-A-SSANGKIYEOK B1F1 AE50 # HANGUL SYLLABLE SSANGKIYEOK-A-NIEUN B1F2 AE54 # HANGUL SYLLABLE SSANGKIYEOK-A-RIEUL B1F3 AE56 # HANGUL SYLLABLE SSANGKIYEOK-A-RIEULMIEUM B1F4 AE5C # HANGUL SYLLABLE SSANGKIYEOK-A-MIEUM B1F5 AE5D # HANGUL SYLLABLE SSANGKIYEOK-A-PIEUP B1F6 AE5F # HANGUL SYLLABLE SSANGKIYEOK-A-SIOS B1F7 AE60 # HANGUL SYLLABLE SSANGKIYEOK-A-SSANGSIOS B1F8 AE61 # HANGUL SYLLABLE SSANGKIYEOK-A-IEUNG B1F9 AE65 # HANGUL SYLLABLE SSANGKIYEOK-A-THIEUTH B1FA AE68 # HANGUL SYLLABLE SSANGKIYEOK-AE B1FB AE69 # HANGUL SYLLABLE SSANGKIYEOK-AE-KIYEOK B1FC AE6C # HANGUL SYLLABLE SSANGKIYEOK-AE-NIEUN B1FD AE70 # HANGUL SYLLABLE SSANGKIYEOK-AE-RIEUL B1FE AE78 # HANGUL SYLLABLE SSANGKIYEOK-AE-MIEUM B241 CF6D # HANGUL SYLLABLE KHIEUKH-O-THIEUTH B242 CF6E # HANGUL SYLLABLE KHIEUKH-O-PHIEUPH B243 CF6F # HANGUL SYLLABLE KHIEUKH-O-HIEUH B244 CF72 # HANGUL SYLLABLE KHIEUKH-WA-SSANGKIYEOK B245 CF73 # HANGUL SYLLABLE KHIEUKH-WA-KIYEOKSIOS B246 CF75 # HANGUL SYLLABLE KHIEUKH-WA-NIEUNCIEUC B247 CF76 # HANGUL SYLLABLE KHIEUKH-WA-NIEUNHIEUH B248 CF77 # HANGUL SYLLABLE KHIEUKH-WA-TIKEUT B249 CF79 # HANGUL SYLLABLE KHIEUKH-WA-RIEULKIYEOK B24A CF7A # HANGUL SYLLABLE KHIEUKH-WA-RIEULMIEUM B24B CF7B # HANGUL SYLLABLE KHIEUKH-WA-RIEULPIEUP B24C CF7C # HANGUL SYLLABLE KHIEUKH-WA-RIEULSIOS B24D CF7D # HANGUL SYLLABLE KHIEUKH-WA-RIEULTHIEUTH B24E CF7E # HANGUL SYLLABLE KHIEUKH-WA-RIEULPHIEUPH B24F CF7F # HANGUL SYLLABLE KHIEUKH-WA-RIEULHIEUH B250 CF81 # HANGUL SYLLABLE KHIEUKH-WA-PIEUP B251 CF82 # HANGUL SYLLABLE KHIEUKH-WA-PIEUPSIOS B252 CF83 # HANGUL SYLLABLE KHIEUKH-WA-SIOS B253 CF84 # HANGUL SYLLABLE KHIEUKH-WA-SSANGSIOS B254 CF86 # HANGUL SYLLABLE KHIEUKH-WA-CIEUC B255 CF87 # HANGUL SYLLABLE KHIEUKH-WA-CHIEUCH B256 CF88 # HANGUL SYLLABLE KHIEUKH-WA-KHIEUKH B257 CF89 # HANGUL SYLLABLE KHIEUKH-WA-THIEUTH B258 CF8A # HANGUL SYLLABLE KHIEUKH-WA-PHIEUPH B259 CF8B # HANGUL SYLLABLE KHIEUKH-WA-HIEUH B25A CF8D # HANGUL SYLLABLE KHIEUKH-WAE-KIYEOK B261 CF8E # HANGUL SYLLABLE KHIEUKH-WAE-SSANGKIYEOK B262 CF8F # HANGUL SYLLABLE KHIEUKH-WAE-KIYEOKSIOS B263 CF90 # HANGUL SYLLABLE KHIEUKH-WAE-NIEUN B264 CF91 # HANGUL SYLLABLE KHIEUKH-WAE-NIEUNCIEUC B265 CF92 # HANGUL SYLLABLE KHIEUKH-WAE-NIEUNHIEUH B266 CF93 # HANGUL SYLLABLE KHIEUKH-WAE-TIKEUT B267 CF94 # HANGUL SYLLABLE KHIEUKH-WAE-RIEUL B268 CF95 # HANGUL SYLLABLE KHIEUKH-WAE-RIEULKIYEOK B269 CF96 # HANGUL SYLLABLE KHIEUKH-WAE-RIEULMIEUM B26A CF97 # HANGUL SYLLABLE KHIEUKH-WAE-RIEULPIEUP B26B CF98 # HANGUL SYLLABLE KHIEUKH-WAE-RIEULSIOS B26C CF99 # HANGUL SYLLABLE KHIEUKH-WAE-RIEULTHIEUTH B26D CF9A # HANGUL SYLLABLE KHIEUKH-WAE-RIEULPHIEUPH B26E CF9B # HANGUL SYLLABLE KHIEUKH-WAE-RIEULHIEUH B26F CF9C # HANGUL SYLLABLE KHIEUKH-WAE-MIEUM B270 CF9D # HANGUL SYLLABLE KHIEUKH-WAE-PIEUP B271 CF9E # HANGUL SYLLABLE KHIEUKH-WAE-PIEUPSIOS B272 CF9F # HANGUL SYLLABLE KHIEUKH-WAE-SIOS B273 CFA0 # HANGUL SYLLABLE KHIEUKH-WAE-SSANGSIOS B274 CFA2 # HANGUL SYLLABLE KHIEUKH-WAE-CIEUC B275 CFA3 # HANGUL SYLLABLE KHIEUKH-WAE-CHIEUCH B276 CFA4 # HANGUL SYLLABLE KHIEUKH-WAE-KHIEUKH B277 CFA5 # HANGUL SYLLABLE KHIEUKH-WAE-THIEUTH B278 CFA6 # HANGUL SYLLABLE KHIEUKH-WAE-PHIEUPH B279 CFA7 # HANGUL SYLLABLE KHIEUKH-WAE-HIEUH B27A CFA9 # HANGUL SYLLABLE KHIEUKH-OE-KIYEOK B281 CFAA # HANGUL SYLLABLE KHIEUKH-OE-SSANGKIYEOK B282 CFAB # HANGUL SYLLABLE KHIEUKH-OE-KIYEOKSIOS B283 CFAC # HANGUL SYLLABLE KHIEUKH-OE-NIEUN B284 CFAD # HANGUL SYLLABLE KHIEUKH-OE-NIEUNCIEUC B285 CFAE # HANGUL SYLLABLE KHIEUKH-OE-NIEUNHIEUH B286 CFAF # HANGUL SYLLABLE KHIEUKH-OE-TIKEUT B287 CFB1 # HANGUL SYLLABLE KHIEUKH-OE-RIEULKIYEOK B288 CFB2 # HANGUL SYLLABLE KHIEUKH-OE-RIEULMIEUM B289 CFB3 # HANGUL SYLLABLE KHIEUKH-OE-RIEULPIEUP B28A CFB4 # HANGUL SYLLABLE KHIEUKH-OE-RIEULSIOS B28B CFB5 # HANGUL SYLLABLE KHIEUKH-OE-RIEULTHIEUTH B28C CFB6 # HANGUL SYLLABLE KHIEUKH-OE-RIEULPHIEUPH B28D CFB7 # HANGUL SYLLABLE KHIEUKH-OE-RIEULHIEUH B28E CFB8 # HANGUL SYLLABLE KHIEUKH-OE-MIEUM B28F CFB9 # HANGUL SYLLABLE KHIEUKH-OE-PIEUP B290 CFBA # HANGUL SYLLABLE KHIEUKH-OE-PIEUPSIOS B291 CFBB # HANGUL SYLLABLE KHIEUKH-OE-SIOS B292 CFBC # HANGUL SYLLABLE KHIEUKH-OE-SSANGSIOS B293 CFBD # HANGUL SYLLABLE KHIEUKH-OE-IEUNG B294 CFBE # HANGUL SYLLABLE KHIEUKH-OE-CIEUC B295 CFBF # HANGUL SYLLABLE KHIEUKH-OE-CHIEUCH B296 CFC0 # HANGUL SYLLABLE KHIEUKH-OE-KHIEUKH B297 CFC1 # HANGUL SYLLABLE KHIEUKH-OE-THIEUTH B298 CFC2 # HANGUL SYLLABLE KHIEUKH-OE-PHIEUPH B299 CFC3 # HANGUL SYLLABLE KHIEUKH-OE-HIEUH B29A CFC5 # HANGUL SYLLABLE KHIEUKH-YO-KIYEOK B29B CFC6 # HANGUL SYLLABLE KHIEUKH-YO-SSANGKIYEOK B29C CFC7 # HANGUL SYLLABLE KHIEUKH-YO-KIYEOKSIOS B29D CFC8 # HANGUL SYLLABLE KHIEUKH-YO-NIEUN B29E CFC9 # HANGUL SYLLABLE KHIEUKH-YO-NIEUNCIEUC B29F CFCA # HANGUL SYLLABLE KHIEUKH-YO-NIEUNHIEUH B2A0 CFCB # HANGUL SYLLABLE KHIEUKH-YO-TIKEUT B2A1 AE79 # HANGUL SYLLABLE SSANGKIYEOK-AE-PIEUP B2A2 AE7B # HANGUL SYLLABLE SSANGKIYEOK-AE-SIOS B2A3 AE7C # HANGUL SYLLABLE SSANGKIYEOK-AE-SSANGSIOS B2A4 AE7D # HANGUL SYLLABLE SSANGKIYEOK-AE-IEUNG B2A5 AE84 # HANGUL SYLLABLE SSANGKIYEOK-YA B2A6 AE85 # HANGUL SYLLABLE SSANGKIYEOK-YA-KIYEOK B2A7 AE8C # HANGUL SYLLABLE SSANGKIYEOK-YA-RIEUL B2A8 AEBC # HANGUL SYLLABLE SSANGKIYEOK-EO B2A9 AEBD # HANGUL SYLLABLE SSANGKIYEOK-EO-KIYEOK B2AA AEBE # HANGUL SYLLABLE SSANGKIYEOK-EO-SSANGKIYEOK B2AB AEC0 # HANGUL SYLLABLE SSANGKIYEOK-EO-NIEUN B2AC AEC4 # HANGUL SYLLABLE SSANGKIYEOK-EO-RIEUL B2AD AECC # HANGUL SYLLABLE SSANGKIYEOK-EO-MIEUM B2AE AECD # HANGUL SYLLABLE SSANGKIYEOK-EO-PIEUP B2AF AECF # HANGUL SYLLABLE SSANGKIYEOK-EO-SIOS B2B0 AED0 # HANGUL SYLLABLE SSANGKIYEOK-EO-SSANGSIOS B2B1 AED1 # HANGUL SYLLABLE SSANGKIYEOK-EO-IEUNG B2B2 AED8 # HANGUL SYLLABLE SSANGKIYEOK-E B2B3 AED9 # HANGUL SYLLABLE SSANGKIYEOK-E-KIYEOK B2B4 AEDC # HANGUL SYLLABLE SSANGKIYEOK-E-NIEUN B2B5 AEE8 # HANGUL SYLLABLE SSANGKIYEOK-E-MIEUM B2B6 AEEB # HANGUL SYLLABLE SSANGKIYEOK-E-SIOS B2B7 AEED # HANGUL SYLLABLE SSANGKIYEOK-E-IEUNG B2B8 AEF4 # HANGUL SYLLABLE SSANGKIYEOK-YEO B2B9 AEF8 # HANGUL SYLLABLE SSANGKIYEOK-YEO-NIEUN B2BA AEFC # HANGUL SYLLABLE SSANGKIYEOK-YEO-RIEUL B2BB AF07 # HANGUL SYLLABLE SSANGKIYEOK-YEO-SIOS B2BC AF08 # HANGUL SYLLABLE SSANGKIYEOK-YEO-SSANGSIOS B2BD AF0D # HANGUL SYLLABLE SSANGKIYEOK-YEO-THIEUTH B2BE AF10 # HANGUL SYLLABLE SSANGKIYEOK-YE B2BF AF2C # HANGUL SYLLABLE SSANGKIYEOK-O B2C0 AF2D # HANGUL SYLLABLE SSANGKIYEOK-O-KIYEOK B2C1 AF30 # HANGUL SYLLABLE SSANGKIYEOK-O-NIEUN B2C2 AF32 # HANGUL SYLLABLE SSANGKIYEOK-O-NIEUNHIEUH B2C3 AF34 # HANGUL SYLLABLE SSANGKIYEOK-O-RIEUL B2C4 AF3C # HANGUL SYLLABLE SSANGKIYEOK-O-MIEUM B2C5 AF3D # HANGUL SYLLABLE SSANGKIYEOK-O-PIEUP B2C6 AF3F # HANGUL SYLLABLE SSANGKIYEOK-O-SIOS B2C7 AF41 # HANGUL SYLLABLE SSANGKIYEOK-O-IEUNG B2C8 AF42 # HANGUL SYLLABLE SSANGKIYEOK-O-CIEUC B2C9 AF43 # HANGUL SYLLABLE SSANGKIYEOK-O-CHIEUCH B2CA AF48 # HANGUL SYLLABLE SSANGKIYEOK-WA B2CB AF49 # HANGUL SYLLABLE SSANGKIYEOK-WA-KIYEOK B2CC AF50 # HANGUL SYLLABLE SSANGKIYEOK-WA-RIEUL B2CD AF5C # HANGUL SYLLABLE SSANGKIYEOK-WA-SSANGSIOS B2CE AF5D # HANGUL SYLLABLE SSANGKIYEOK-WA-IEUNG B2CF AF64 # HANGUL SYLLABLE SSANGKIYEOK-WAE B2D0 AF65 # HANGUL SYLLABLE SSANGKIYEOK-WAE-KIYEOK B2D1 AF79 # HANGUL SYLLABLE SSANGKIYEOK-WAE-IEUNG B2D2 AF80 # HANGUL SYLLABLE SSANGKIYEOK-OE B2D3 AF84 # HANGUL SYLLABLE SSANGKIYEOK-OE-NIEUN B2D4 AF88 # HANGUL SYLLABLE SSANGKIYEOK-OE-RIEUL B2D5 AF90 # HANGUL SYLLABLE SSANGKIYEOK-OE-MIEUM B2D6 AF91 # HANGUL SYLLABLE SSANGKIYEOK-OE-PIEUP B2D7 AF95 # HANGUL SYLLABLE SSANGKIYEOK-OE-IEUNG B2D8 AF9C # HANGUL SYLLABLE SSANGKIYEOK-YO B2D9 AFB8 # HANGUL SYLLABLE SSANGKIYEOK-U B2DA AFB9 # HANGUL SYLLABLE SSANGKIYEOK-U-KIYEOK B2DB AFBC # HANGUL SYLLABLE SSANGKIYEOK-U-NIEUN B2DC AFC0 # HANGUL SYLLABLE SSANGKIYEOK-U-RIEUL B2DD AFC7 # HANGUL SYLLABLE SSANGKIYEOK-U-RIEULHIEUH B2DE AFC8 # HANGUL SYLLABLE SSANGKIYEOK-U-MIEUM B2DF AFC9 # HANGUL SYLLABLE SSANGKIYEOK-U-PIEUP B2E0 AFCB # HANGUL SYLLABLE SSANGKIYEOK-U-SIOS B2E1 AFCD # HANGUL SYLLABLE SSANGKIYEOK-U-IEUNG B2E2 AFCE # HANGUL SYLLABLE SSANGKIYEOK-U-CIEUC B2E3 AFD4 # HANGUL SYLLABLE SSANGKIYEOK-WEO B2E4 AFDC # HANGUL SYLLABLE SSANGKIYEOK-WEO-RIEUL B2E5 AFE8 # HANGUL SYLLABLE SSANGKIYEOK-WEO-SSANGSIOS B2E6 AFE9 # HANGUL SYLLABLE SSANGKIYEOK-WEO-IEUNG B2E7 AFF0 # HANGUL SYLLABLE SSANGKIYEOK-WE B2E8 AFF1 # HANGUL SYLLABLE SSANGKIYEOK-WE-KIYEOK B2E9 AFF4 # HANGUL SYLLABLE SSANGKIYEOK-WE-NIEUN B2EA AFF8 # HANGUL SYLLABLE SSANGKIYEOK-WE-RIEUL B2EB B000 # HANGUL SYLLABLE SSANGKIYEOK-WE-MIEUM B2EC B001 # HANGUL SYLLABLE SSANGKIYEOK-WE-PIEUP B2ED B004 # HANGUL SYLLABLE SSANGKIYEOK-WE-SSANGSIOS B2EE B00C # HANGUL SYLLABLE SSANGKIYEOK-WI B2EF B010 # HANGUL SYLLABLE SSANGKIYEOK-WI-NIEUN B2F0 B014 # HANGUL SYLLABLE SSANGKIYEOK-WI-RIEUL B2F1 B01C # HANGUL SYLLABLE SSANGKIYEOK-WI-MIEUM B2F2 B01D # HANGUL SYLLABLE SSANGKIYEOK-WI-PIEUP B2F3 B028 # HANGUL SYLLABLE SSANGKIYEOK-YU B2F4 B044 # HANGUL SYLLABLE SSANGKIYEOK-EU B2F5 B045 # HANGUL SYLLABLE SSANGKIYEOK-EU-KIYEOK B2F6 B048 # HANGUL SYLLABLE SSANGKIYEOK-EU-NIEUN B2F7 B04A # HANGUL SYLLABLE SSANGKIYEOK-EU-NIEUNHIEUH B2F8 B04C # HANGUL SYLLABLE SSANGKIYEOK-EU-RIEUL B2F9 B04E # HANGUL SYLLABLE SSANGKIYEOK-EU-RIEULMIEUM B2FA B053 # HANGUL SYLLABLE SSANGKIYEOK-EU-RIEULHIEUH B2FB B054 # HANGUL SYLLABLE SSANGKIYEOK-EU-MIEUM B2FC B055 # HANGUL SYLLABLE SSANGKIYEOK-EU-PIEUP B2FD B057 # HANGUL SYLLABLE SSANGKIYEOK-EU-SIOS B2FE B059 # HANGUL SYLLABLE SSANGKIYEOK-EU-IEUNG B341 CFCC # HANGUL SYLLABLE KHIEUKH-YO-RIEUL B342 CFCD # HANGUL SYLLABLE KHIEUKH-YO-RIEULKIYEOK B343 CFCE # HANGUL SYLLABLE KHIEUKH-YO-RIEULMIEUM B344 CFCF # HANGUL SYLLABLE KHIEUKH-YO-RIEULPIEUP B345 CFD0 # HANGUL SYLLABLE KHIEUKH-YO-RIEULSIOS B346 CFD1 # HANGUL SYLLABLE KHIEUKH-YO-RIEULTHIEUTH B347 CFD2 # HANGUL SYLLABLE KHIEUKH-YO-RIEULPHIEUPH B348 CFD3 # HANGUL SYLLABLE KHIEUKH-YO-RIEULHIEUH B349 CFD4 # HANGUL SYLLABLE KHIEUKH-YO-MIEUM B34A CFD5 # HANGUL SYLLABLE KHIEUKH-YO-PIEUP B34B CFD6 # HANGUL SYLLABLE KHIEUKH-YO-PIEUPSIOS B34C CFD7 # HANGUL SYLLABLE KHIEUKH-YO-SIOS B34D CFD8 # HANGUL SYLLABLE KHIEUKH-YO-SSANGSIOS B34E CFD9 # HANGUL SYLLABLE KHIEUKH-YO-IEUNG B34F CFDA # HANGUL SYLLABLE KHIEUKH-YO-CIEUC B350 CFDB # HANGUL SYLLABLE KHIEUKH-YO-CHIEUCH B351 CFDC # HANGUL SYLLABLE KHIEUKH-YO-KHIEUKH B352 CFDD # HANGUL SYLLABLE KHIEUKH-YO-THIEUTH B353 CFDE # HANGUL SYLLABLE KHIEUKH-YO-PHIEUPH B354 CFDF # HANGUL SYLLABLE KHIEUKH-YO-HIEUH B355 CFE2 # HANGUL SYLLABLE KHIEUKH-U-SSANGKIYEOK B356 CFE3 # HANGUL SYLLABLE KHIEUKH-U-KIYEOKSIOS B357 CFE5 # HANGUL SYLLABLE KHIEUKH-U-NIEUNCIEUC B358 CFE6 # HANGUL SYLLABLE KHIEUKH-U-NIEUNHIEUH B359 CFE7 # HANGUL SYLLABLE KHIEUKH-U-TIKEUT B35A CFE9 # HANGUL SYLLABLE KHIEUKH-U-RIEULKIYEOK B361 CFEA # HANGUL SYLLABLE KHIEUKH-U-RIEULMIEUM B362 CFEB # HANGUL SYLLABLE KHIEUKH-U-RIEULPIEUP B363 CFEC # HANGUL SYLLABLE KHIEUKH-U-RIEULSIOS B364 CFED # HANGUL SYLLABLE KHIEUKH-U-RIEULTHIEUTH B365 CFEE # HANGUL SYLLABLE KHIEUKH-U-RIEULPHIEUPH B366 CFEF # HANGUL SYLLABLE KHIEUKH-U-RIEULHIEUH B367 CFF2 # HANGUL SYLLABLE KHIEUKH-U-PIEUPSIOS B368 CFF4 # HANGUL SYLLABLE KHIEUKH-U-SSANGSIOS B369 CFF6 # HANGUL SYLLABLE KHIEUKH-U-CIEUC B36A CFF7 # HANGUL SYLLABLE KHIEUKH-U-CHIEUCH B36B CFF8 # HANGUL SYLLABLE KHIEUKH-U-KHIEUKH B36C CFF9 # HANGUL SYLLABLE KHIEUKH-U-THIEUTH B36D CFFA # HANGUL SYLLABLE KHIEUKH-U-PHIEUPH B36E CFFB # HANGUL SYLLABLE KHIEUKH-U-HIEUH B36F CFFD # HANGUL SYLLABLE KHIEUKH-WEO-KIYEOK B370 CFFE # HANGUL SYLLABLE KHIEUKH-WEO-SSANGKIYEOK B371 CFFF # HANGUL SYLLABLE KHIEUKH-WEO-KIYEOKSIOS B372 D001 # HANGUL SYLLABLE KHIEUKH-WEO-NIEUNCIEUC B373 D002 # HANGUL SYLLABLE KHIEUKH-WEO-NIEUNHIEUH B374 D003 # HANGUL SYLLABLE KHIEUKH-WEO-TIKEUT B375 D005 # HANGUL SYLLABLE KHIEUKH-WEO-RIEULKIYEOK B376 D006 # HANGUL SYLLABLE KHIEUKH-WEO-RIEULMIEUM B377 D007 # HANGUL SYLLABLE KHIEUKH-WEO-RIEULPIEUP B378 D008 # HANGUL SYLLABLE KHIEUKH-WEO-RIEULSIOS B379 D009 # HANGUL SYLLABLE KHIEUKH-WEO-RIEULTHIEUTH B37A D00A # HANGUL SYLLABLE KHIEUKH-WEO-RIEULPHIEUPH B381 D00B # HANGUL SYLLABLE KHIEUKH-WEO-RIEULHIEUH B382 D00C # HANGUL SYLLABLE KHIEUKH-WEO-MIEUM B383 D00D # HANGUL SYLLABLE KHIEUKH-WEO-PIEUP B384 D00E # HANGUL SYLLABLE KHIEUKH-WEO-PIEUPSIOS B385 D00F # HANGUL SYLLABLE KHIEUKH-WEO-SIOS B386 D010 # HANGUL SYLLABLE KHIEUKH-WEO-SSANGSIOS B387 D012 # HANGUL SYLLABLE KHIEUKH-WEO-CIEUC B388 D013 # HANGUL SYLLABLE KHIEUKH-WEO-CHIEUCH B389 D014 # HANGUL SYLLABLE KHIEUKH-WEO-KHIEUKH B38A D015 # HANGUL SYLLABLE KHIEUKH-WEO-THIEUTH B38B D016 # HANGUL SYLLABLE KHIEUKH-WEO-PHIEUPH B38C D017 # HANGUL SYLLABLE KHIEUKH-WEO-HIEUH B38D D019 # HANGUL SYLLABLE KHIEUKH-WE-KIYEOK B38E D01A # HANGUL SYLLABLE KHIEUKH-WE-SSANGKIYEOK B38F D01B # HANGUL SYLLABLE KHIEUKH-WE-KIYEOKSIOS B390 D01C # HANGUL SYLLABLE KHIEUKH-WE-NIEUN B391 D01D # HANGUL SYLLABLE KHIEUKH-WE-NIEUNCIEUC B392 D01E # HANGUL SYLLABLE KHIEUKH-WE-NIEUNHIEUH B393 D01F # HANGUL SYLLABLE KHIEUKH-WE-TIKEUT B394 D020 # HANGUL SYLLABLE KHIEUKH-WE-RIEUL B395 D021 # HANGUL SYLLABLE KHIEUKH-WE-RIEULKIYEOK B396 D022 # HANGUL SYLLABLE KHIEUKH-WE-RIEULMIEUM B397 D023 # HANGUL SYLLABLE KHIEUKH-WE-RIEULPIEUP B398 D024 # HANGUL SYLLABLE KHIEUKH-WE-RIEULSIOS B399 D025 # HANGUL SYLLABLE KHIEUKH-WE-RIEULTHIEUTH B39A D026 # HANGUL SYLLABLE KHIEUKH-WE-RIEULPHIEUPH B39B D027 # HANGUL SYLLABLE KHIEUKH-WE-RIEULHIEUH B39C D028 # HANGUL SYLLABLE KHIEUKH-WE-MIEUM B39D D029 # HANGUL SYLLABLE KHIEUKH-WE-PIEUP B39E D02A # HANGUL SYLLABLE KHIEUKH-WE-PIEUPSIOS B39F D02B # HANGUL SYLLABLE KHIEUKH-WE-SIOS B3A0 D02C # HANGUL SYLLABLE KHIEUKH-WE-SSANGSIOS B3A1 B05D # HANGUL SYLLABLE SSANGKIYEOK-EU-THIEUTH B3A2 B07C # HANGUL SYLLABLE SSANGKIYEOK-I B3A3 B07D # HANGUL SYLLABLE SSANGKIYEOK-I-KIYEOK B3A4 B080 # HANGUL SYLLABLE SSANGKIYEOK-I-NIEUN B3A5 B084 # HANGUL SYLLABLE SSANGKIYEOK-I-RIEUL B3A6 B08C # HANGUL SYLLABLE SSANGKIYEOK-I-MIEUM B3A7 B08D # HANGUL SYLLABLE SSANGKIYEOK-I-PIEUP B3A8 B08F # HANGUL SYLLABLE SSANGKIYEOK-I-SIOS B3A9 B091 # HANGUL SYLLABLE SSANGKIYEOK-I-IEUNG B3AA B098 # HANGUL SYLLABLE NIEUN-A B3AB B099 # HANGUL SYLLABLE NIEUN-A-KIYEOK B3AC B09A # HANGUL SYLLABLE NIEUN-A-SSANGKIYEOK B3AD B09C # HANGUL SYLLABLE NIEUN-A-NIEUN B3AE B09F # HANGUL SYLLABLE NIEUN-A-TIKEUT B3AF B0A0 # HANGUL SYLLABLE NIEUN-A-RIEUL B3B0 B0A1 # HANGUL SYLLABLE NIEUN-A-RIEULKIYEOK B3B1 B0A2 # HANGUL SYLLABLE NIEUN-A-RIEULMIEUM B3B2 B0A8 # HANGUL SYLLABLE NIEUN-A-MIEUM B3B3 B0A9 # HANGUL SYLLABLE NIEUN-A-PIEUP B3B4 B0AB # HANGUL SYLLABLE NIEUN-A-SIOS B3B5 B0AC # HANGUL SYLLABLE NIEUN-A-SSANGSIOS B3B6 B0AD # HANGUL SYLLABLE NIEUN-A-IEUNG B3B7 B0AE # HANGUL SYLLABLE NIEUN-A-CIEUC B3B8 B0AF # HANGUL SYLLABLE NIEUN-A-CHIEUCH B3B9 B0B1 # HANGUL SYLLABLE NIEUN-A-THIEUTH B3BA B0B3 # HANGUL SYLLABLE NIEUN-A-HIEUH B3BB B0B4 # HANGUL SYLLABLE NIEUN-AE B3BC B0B5 # HANGUL SYLLABLE NIEUN-AE-KIYEOK B3BD B0B8 # HANGUL SYLLABLE NIEUN-AE-NIEUN B3BE B0BC # HANGUL SYLLABLE NIEUN-AE-RIEUL B3BF B0C4 # HANGUL SYLLABLE NIEUN-AE-MIEUM B3C0 B0C5 # HANGUL SYLLABLE NIEUN-AE-PIEUP B3C1 B0C7 # HANGUL SYLLABLE NIEUN-AE-SIOS B3C2 B0C8 # HANGUL SYLLABLE NIEUN-AE-SSANGSIOS B3C3 B0C9 # HANGUL SYLLABLE NIEUN-AE-IEUNG B3C4 B0D0 # HANGUL SYLLABLE NIEUN-YA B3C5 B0D1 # HANGUL SYLLABLE NIEUN-YA-KIYEOK B3C6 B0D4 # HANGUL SYLLABLE NIEUN-YA-NIEUN B3C7 B0D8 # HANGUL SYLLABLE NIEUN-YA-RIEUL B3C8 B0E0 # HANGUL SYLLABLE NIEUN-YA-MIEUM B3C9 B0E5 # HANGUL SYLLABLE NIEUN-YA-IEUNG B3CA B108 # HANGUL SYLLABLE NIEUN-EO B3CB B109 # HANGUL SYLLABLE NIEUN-EO-KIYEOK B3CC B10B # HANGUL SYLLABLE NIEUN-EO-KIYEOKSIOS B3CD B10C # HANGUL SYLLABLE NIEUN-EO-NIEUN B3CE B110 # HANGUL SYLLABLE NIEUN-EO-RIEUL B3CF B112 # HANGUL SYLLABLE NIEUN-EO-RIEULMIEUM B3D0 B113 # HANGUL SYLLABLE NIEUN-EO-RIEULPIEUP B3D1 B118 # HANGUL SYLLABLE NIEUN-EO-MIEUM B3D2 B119 # HANGUL SYLLABLE NIEUN-EO-PIEUP B3D3 B11B # HANGUL SYLLABLE NIEUN-EO-SIOS B3D4 B11C # HANGUL SYLLABLE NIEUN-EO-SSANGSIOS B3D5 B11D # HANGUL SYLLABLE NIEUN-EO-IEUNG B3D6 B123 # HANGUL SYLLABLE NIEUN-EO-HIEUH B3D7 B124 # HANGUL SYLLABLE NIEUN-E B3D8 B125 # HANGUL SYLLABLE NIEUN-E-KIYEOK B3D9 B128 # HANGUL SYLLABLE NIEUN-E-NIEUN B3DA B12C # HANGUL SYLLABLE NIEUN-E-RIEUL B3DB B134 # HANGUL SYLLABLE NIEUN-E-MIEUM B3DC B135 # HANGUL SYLLABLE NIEUN-E-PIEUP B3DD B137 # HANGUL SYLLABLE NIEUN-E-SIOS B3DE B138 # HANGUL SYLLABLE NIEUN-E-SSANGSIOS B3DF B139 # HANGUL SYLLABLE NIEUN-E-IEUNG B3E0 B140 # HANGUL SYLLABLE NIEUN-YEO B3E1 B141 # HANGUL SYLLABLE NIEUN-YEO-KIYEOK B3E2 B144 # HANGUL SYLLABLE NIEUN-YEO-NIEUN B3E3 B148 # HANGUL SYLLABLE NIEUN-YEO-RIEUL B3E4 B150 # HANGUL SYLLABLE NIEUN-YEO-MIEUM B3E5 B151 # HANGUL SYLLABLE NIEUN-YEO-PIEUP B3E6 B154 # HANGUL SYLLABLE NIEUN-YEO-SSANGSIOS B3E7 B155 # HANGUL SYLLABLE NIEUN-YEO-IEUNG B3E8 B158 # HANGUL SYLLABLE NIEUN-YEO-KHIEUKH B3E9 B15C # HANGUL SYLLABLE NIEUN-YE B3EA B160 # HANGUL SYLLABLE NIEUN-YE-NIEUN B3EB B178 # HANGUL SYLLABLE NIEUN-O B3EC B179 # HANGUL SYLLABLE NIEUN-O-KIYEOK B3ED B17C # HANGUL SYLLABLE NIEUN-O-NIEUN B3EE B180 # HANGUL SYLLABLE NIEUN-O-RIEUL B3EF B182 # HANGUL SYLLABLE NIEUN-O-RIEULMIEUM B3F0 B188 # HANGUL SYLLABLE NIEUN-O-MIEUM B3F1 B189 # HANGUL SYLLABLE NIEUN-O-PIEUP B3F2 B18B # HANGUL SYLLABLE NIEUN-O-SIOS B3F3 B18D # HANGUL SYLLABLE NIEUN-O-IEUNG B3F4 B192 # HANGUL SYLLABLE NIEUN-O-PHIEUPH B3F5 B193 # HANGUL SYLLABLE NIEUN-O-HIEUH B3F6 B194 # HANGUL SYLLABLE NIEUN-WA B3F7 B198 # HANGUL SYLLABLE NIEUN-WA-NIEUN B3F8 B19C # HANGUL SYLLABLE NIEUN-WA-RIEUL B3F9 B1A8 # HANGUL SYLLABLE NIEUN-WA-SSANGSIOS B3FA B1CC # HANGUL SYLLABLE NIEUN-OE B3FB B1D0 # HANGUL SYLLABLE NIEUN-OE-NIEUN B3FC B1D4 # HANGUL SYLLABLE NIEUN-OE-RIEUL B3FD B1DC # HANGUL SYLLABLE NIEUN-OE-MIEUM B3FE B1DD # HANGUL SYLLABLE NIEUN-OE-PIEUP B441 D02E # HANGUL SYLLABLE KHIEUKH-WE-CIEUC B442 D02F # HANGUL SYLLABLE KHIEUKH-WE-CHIEUCH B443 D030 # HANGUL SYLLABLE KHIEUKH-WE-KHIEUKH B444 D031 # HANGUL SYLLABLE KHIEUKH-WE-THIEUTH B445 D032 # HANGUL SYLLABLE KHIEUKH-WE-PHIEUPH B446 D033 # HANGUL SYLLABLE KHIEUKH-WE-HIEUH B447 D036 # HANGUL SYLLABLE KHIEUKH-WI-SSANGKIYEOK B448 D037 # HANGUL SYLLABLE KHIEUKH-WI-KIYEOKSIOS B449 D039 # HANGUL SYLLABLE KHIEUKH-WI-NIEUNCIEUC B44A D03A # HANGUL SYLLABLE KHIEUKH-WI-NIEUNHIEUH B44B D03B # HANGUL SYLLABLE KHIEUKH-WI-TIKEUT B44C D03D # HANGUL SYLLABLE KHIEUKH-WI-RIEULKIYEOK B44D D03E # HANGUL SYLLABLE KHIEUKH-WI-RIEULMIEUM B44E D03F # HANGUL SYLLABLE KHIEUKH-WI-RIEULPIEUP B44F D040 # HANGUL SYLLABLE KHIEUKH-WI-RIEULSIOS B450 D041 # HANGUL SYLLABLE KHIEUKH-WI-RIEULTHIEUTH B451 D042 # HANGUL SYLLABLE KHIEUKH-WI-RIEULPHIEUPH B452 D043 # HANGUL SYLLABLE KHIEUKH-WI-RIEULHIEUH B453 D046 # HANGUL SYLLABLE KHIEUKH-WI-PIEUPSIOS B454 D048 # HANGUL SYLLABLE KHIEUKH-WI-SSANGSIOS B455 D04A # HANGUL SYLLABLE KHIEUKH-WI-CIEUC B456 D04B # HANGUL SYLLABLE KHIEUKH-WI-CHIEUCH B457 D04C # HANGUL SYLLABLE KHIEUKH-WI-KHIEUKH B458 D04D # HANGUL SYLLABLE KHIEUKH-WI-THIEUTH B459 D04E # HANGUL SYLLABLE KHIEUKH-WI-PHIEUPH B45A D04F # HANGUL SYLLABLE KHIEUKH-WI-HIEUH B461 D051 # HANGUL SYLLABLE KHIEUKH-YU-KIYEOK B462 D052 # HANGUL SYLLABLE KHIEUKH-YU-SSANGKIYEOK B463 D053 # HANGUL SYLLABLE KHIEUKH-YU-KIYEOKSIOS B464 D055 # HANGUL SYLLABLE KHIEUKH-YU-NIEUNCIEUC B465 D056 # HANGUL SYLLABLE KHIEUKH-YU-NIEUNHIEUH B466 D057 # HANGUL SYLLABLE KHIEUKH-YU-TIKEUT B467 D059 # HANGUL SYLLABLE KHIEUKH-YU-RIEULKIYEOK B468 D05A # HANGUL SYLLABLE KHIEUKH-YU-RIEULMIEUM B469 D05B # HANGUL SYLLABLE KHIEUKH-YU-RIEULPIEUP B46A D05C # HANGUL SYLLABLE KHIEUKH-YU-RIEULSIOS B46B D05D # HANGUL SYLLABLE KHIEUKH-YU-RIEULTHIEUTH B46C D05E # HANGUL SYLLABLE KHIEUKH-YU-RIEULPHIEUPH B46D D05F # HANGUL SYLLABLE KHIEUKH-YU-RIEULHIEUH B46E D061 # HANGUL SYLLABLE KHIEUKH-YU-PIEUP B46F D062 # HANGUL SYLLABLE KHIEUKH-YU-PIEUPSIOS B470 D063 # HANGUL SYLLABLE KHIEUKH-YU-SIOS B471 D064 # HANGUL SYLLABLE KHIEUKH-YU-SSANGSIOS B472 D065 # HANGUL SYLLABLE KHIEUKH-YU-IEUNG B473 D066 # HANGUL SYLLABLE KHIEUKH-YU-CIEUC B474 D067 # HANGUL SYLLABLE KHIEUKH-YU-CHIEUCH B475 D068 # HANGUL SYLLABLE KHIEUKH-YU-KHIEUKH B476 D069 # HANGUL SYLLABLE KHIEUKH-YU-THIEUTH B477 D06A # HANGUL SYLLABLE KHIEUKH-YU-PHIEUPH B478 D06B # HANGUL SYLLABLE KHIEUKH-YU-HIEUH B479 D06E # HANGUL SYLLABLE KHIEUKH-EU-SSANGKIYEOK B47A D06F # HANGUL SYLLABLE KHIEUKH-EU-KIYEOKSIOS B481 D071 # HANGUL SYLLABLE KHIEUKH-EU-NIEUNCIEUC B482 D072 # HANGUL SYLLABLE KHIEUKH-EU-NIEUNHIEUH B483 D073 # HANGUL SYLLABLE KHIEUKH-EU-TIKEUT B484 D075 # HANGUL SYLLABLE KHIEUKH-EU-RIEULKIYEOK B485 D076 # HANGUL SYLLABLE KHIEUKH-EU-RIEULMIEUM B486 D077 # HANGUL SYLLABLE KHIEUKH-EU-RIEULPIEUP B487 D078 # HANGUL SYLLABLE KHIEUKH-EU-RIEULSIOS B488 D079 # HANGUL SYLLABLE KHIEUKH-EU-RIEULTHIEUTH B489 D07A # HANGUL SYLLABLE KHIEUKH-EU-RIEULPHIEUPH B48A D07B # HANGUL SYLLABLE KHIEUKH-EU-RIEULHIEUH B48B D07E # HANGUL SYLLABLE KHIEUKH-EU-PIEUPSIOS B48C D07F # HANGUL SYLLABLE KHIEUKH-EU-SIOS B48D D080 # HANGUL SYLLABLE KHIEUKH-EU-SSANGSIOS B48E D082 # HANGUL SYLLABLE KHIEUKH-EU-CIEUC B48F D083 # HANGUL SYLLABLE KHIEUKH-EU-CHIEUCH B490 D084 # HANGUL SYLLABLE KHIEUKH-EU-KHIEUKH B491 D085 # HANGUL SYLLABLE KHIEUKH-EU-THIEUTH B492 D086 # HANGUL SYLLABLE KHIEUKH-EU-PHIEUPH B493 D087 # HANGUL SYLLABLE KHIEUKH-EU-HIEUH B494 D088 # HANGUL SYLLABLE KHIEUKH-YI B495 D089 # HANGUL SYLLABLE KHIEUKH-YI-KIYEOK B496 D08A # HANGUL SYLLABLE KHIEUKH-YI-SSANGKIYEOK B497 D08B # HANGUL SYLLABLE KHIEUKH-YI-KIYEOKSIOS B498 D08C # HANGUL SYLLABLE KHIEUKH-YI-NIEUN B499 D08D # HANGUL SYLLABLE KHIEUKH-YI-NIEUNCIEUC B49A D08E # HANGUL SYLLABLE KHIEUKH-YI-NIEUNHIEUH B49B D08F # HANGUL SYLLABLE KHIEUKH-YI-TIKEUT B49C D090 # HANGUL SYLLABLE KHIEUKH-YI-RIEUL B49D D091 # HANGUL SYLLABLE KHIEUKH-YI-RIEULKIYEOK B49E D092 # HANGUL SYLLABLE KHIEUKH-YI-RIEULMIEUM B49F D093 # HANGUL SYLLABLE KHIEUKH-YI-RIEULPIEUP B4A0 D094 # HANGUL SYLLABLE KHIEUKH-YI-RIEULSIOS B4A1 B1DF # HANGUL SYLLABLE NIEUN-OE-SIOS B4A2 B1E8 # HANGUL SYLLABLE NIEUN-YO B4A3 B1E9 # HANGUL SYLLABLE NIEUN-YO-KIYEOK B4A4 B1EC # HANGUL SYLLABLE NIEUN-YO-NIEUN B4A5 B1F0 # HANGUL SYLLABLE NIEUN-YO-RIEUL B4A6 B1F9 # HANGUL SYLLABLE NIEUN-YO-PIEUP B4A7 B1FB # HANGUL SYLLABLE NIEUN-YO-SIOS B4A8 B1FD # HANGUL SYLLABLE NIEUN-YO-IEUNG B4A9 B204 # HANGUL SYLLABLE NIEUN-U B4AA B205 # HANGUL SYLLABLE NIEUN-U-KIYEOK B4AB B208 # HANGUL SYLLABLE NIEUN-U-NIEUN B4AC B20B # HANGUL SYLLABLE NIEUN-U-TIKEUT B4AD B20C # HANGUL SYLLABLE NIEUN-U-RIEUL B4AE B214 # HANGUL SYLLABLE NIEUN-U-MIEUM B4AF B215 # HANGUL SYLLABLE NIEUN-U-PIEUP B4B0 B217 # HANGUL SYLLABLE NIEUN-U-SIOS B4B1 B219 # HANGUL SYLLABLE NIEUN-U-IEUNG B4B2 B220 # HANGUL SYLLABLE NIEUN-WEO B4B3 B234 # HANGUL SYLLABLE NIEUN-WEO-SSANGSIOS B4B4 B23C # HANGUL SYLLABLE NIEUN-WE B4B5 B258 # HANGUL SYLLABLE NIEUN-WI B4B6 B25C # HANGUL SYLLABLE NIEUN-WI-NIEUN B4B7 B260 # HANGUL SYLLABLE NIEUN-WI-RIEUL B4B8 B268 # HANGUL SYLLABLE NIEUN-WI-MIEUM B4B9 B269 # HANGUL SYLLABLE NIEUN-WI-PIEUP B4BA B274 # HANGUL SYLLABLE NIEUN-YU B4BB B275 # HANGUL SYLLABLE NIEUN-YU-KIYEOK B4BC B27C # HANGUL SYLLABLE NIEUN-YU-RIEUL B4BD B284 # HANGUL SYLLABLE NIEUN-YU-MIEUM B4BE B285 # HANGUL SYLLABLE NIEUN-YU-PIEUP B4BF B289 # HANGUL SYLLABLE NIEUN-YU-IEUNG B4C0 B290 # HANGUL SYLLABLE NIEUN-EU B4C1 B291 # HANGUL SYLLABLE NIEUN-EU-KIYEOK B4C2 B294 # HANGUL SYLLABLE NIEUN-EU-NIEUN B4C3 B298 # HANGUL SYLLABLE NIEUN-EU-RIEUL B4C4 B299 # HANGUL SYLLABLE NIEUN-EU-RIEULKIYEOK B4C5 B29A # HANGUL SYLLABLE NIEUN-EU-RIEULMIEUM B4C6 B2A0 # HANGUL SYLLABLE NIEUN-EU-MIEUM B4C7 B2A1 # HANGUL SYLLABLE NIEUN-EU-PIEUP B4C8 B2A3 # HANGUL SYLLABLE NIEUN-EU-SIOS B4C9 B2A5 # HANGUL SYLLABLE NIEUN-EU-IEUNG B4CA B2A6 # HANGUL SYLLABLE NIEUN-EU-CIEUC B4CB B2AA # HANGUL SYLLABLE NIEUN-EU-PHIEUPH B4CC B2AC # HANGUL SYLLABLE NIEUN-YI B4CD B2B0 # HANGUL SYLLABLE NIEUN-YI-NIEUN B4CE B2B4 # HANGUL SYLLABLE NIEUN-YI-RIEUL B4CF B2C8 # HANGUL SYLLABLE NIEUN-I B4D0 B2C9 # HANGUL SYLLABLE NIEUN-I-KIYEOK B4D1 B2CC # HANGUL SYLLABLE NIEUN-I-NIEUN B4D2 B2D0 # HANGUL SYLLABLE NIEUN-I-RIEUL B4D3 B2D2 # HANGUL SYLLABLE NIEUN-I-RIEULMIEUM-<3/22/95> B4D4 B2D8 # HANGUL SYLLABLE NIEUN-I-MIEUM B4D5 B2D9 # HANGUL SYLLABLE NIEUN-I-PIEUP B4D6 B2DB # HANGUL SYLLABLE NIEUN-I-SIOS B4D7 B2DD # HANGUL SYLLABLE NIEUN-I-IEUNG B4D8 B2E2 # HANGUL SYLLABLE NIEUN-I-PHIEUPH B4D9 B2E4 # HANGUL SYLLABLE TIKEUT-A B4DA B2E5 # HANGUL SYLLABLE TIKEUT-A-KIYEOK B4DB B2E6 # HANGUL SYLLABLE TIKEUT-A-SSANGKIYEOK B4DC B2E8 # HANGUL SYLLABLE TIKEUT-A-NIEUN B4DD B2EB # HANGUL SYLLABLE TIKEUT-A-TIKEUT B4DE B2EC # HANGUL SYLLABLE TIKEUT-A-RIEUL B4DF B2ED # HANGUL SYLLABLE TIKEUT-A-RIEULKIYEOK B4E0 B2EE # HANGUL SYLLABLE TIKEUT-A-RIEULMIEUM B4E1 B2EF # HANGUL SYLLABLE TIKEUT-A-RIEULPIEUP B4E2 B2F3 # HANGUL SYLLABLE TIKEUT-A-RIEULHIEUH B4E3 B2F4 # HANGUL SYLLABLE TIKEUT-A-MIEUM B4E4 B2F5 # HANGUL SYLLABLE TIKEUT-A-PIEUP B4E5 B2F7 # HANGUL SYLLABLE TIKEUT-A-SIOS B4E6 B2F8 # HANGUL SYLLABLE TIKEUT-A-SSANGSIOS B4E7 B2F9 # HANGUL SYLLABLE TIKEUT-A-IEUNG B4E8 B2FA # HANGUL SYLLABLE TIKEUT-A-CIEUC B4E9 B2FB # HANGUL SYLLABLE TIKEUT-A-CHIEUCH B4EA B2FF # HANGUL SYLLABLE TIKEUT-A-HIEUH B4EB B300 # HANGUL SYLLABLE TIKEUT-AE B4EC B301 # HANGUL SYLLABLE TIKEUT-AE-KIYEOK B4ED B304 # HANGUL SYLLABLE TIKEUT-AE-NIEUN B4EE B308 # HANGUL SYLLABLE TIKEUT-AE-RIEUL B4EF B310 # HANGUL SYLLABLE TIKEUT-AE-MIEUM B4F0 B311 # HANGUL SYLLABLE TIKEUT-AE-PIEUP B4F1 B313 # HANGUL SYLLABLE TIKEUT-AE-SIOS B4F2 B314 # HANGUL SYLLABLE TIKEUT-AE-SSANGSIOS B4F3 B315 # HANGUL SYLLABLE TIKEUT-AE-IEUNG B4F4 B31C # HANGUL SYLLABLE TIKEUT-YA B4F5 B354 # HANGUL SYLLABLE TIKEUT-EO B4F6 B355 # HANGUL SYLLABLE TIKEUT-EO-KIYEOK B4F7 B356 # HANGUL SYLLABLE TIKEUT-EO-SSANGKIYEOK B4F8 B358 # HANGUL SYLLABLE TIKEUT-EO-NIEUN B4F9 B35B # HANGUL SYLLABLE TIKEUT-EO-TIKEUT B4FA B35C # HANGUL SYLLABLE TIKEUT-EO-RIEUL B4FB B35E # HANGUL SYLLABLE TIKEUT-EO-RIEULMIEUM B4FC B35F # HANGUL SYLLABLE TIKEUT-EO-RIEULPIEUP B4FD B364 # HANGUL SYLLABLE TIKEUT-EO-MIEUM B4FE B365 # HANGUL SYLLABLE TIKEUT-EO-PIEUP B541 D095 # HANGUL SYLLABLE KHIEUKH-YI-RIEULTHIEUTH B542 D096 # HANGUL SYLLABLE KHIEUKH-YI-RIEULPHIEUPH B543 D097 # HANGUL SYLLABLE KHIEUKH-YI-RIEULHIEUH B544 D098 # HANGUL SYLLABLE KHIEUKH-YI-MIEUM B545 D099 # HANGUL SYLLABLE KHIEUKH-YI-PIEUP B546 D09A # HANGUL SYLLABLE KHIEUKH-YI-PIEUPSIOS B547 D09B # HANGUL SYLLABLE KHIEUKH-YI-SIOS B548 D09C # HANGUL SYLLABLE KHIEUKH-YI-SSANGSIOS B549 D09D # HANGUL SYLLABLE KHIEUKH-YI-IEUNG B54A D09E # HANGUL SYLLABLE KHIEUKH-YI-CIEUC B54B D09F # HANGUL SYLLABLE KHIEUKH-YI-CHIEUCH B54C D0A0 # HANGUL SYLLABLE KHIEUKH-YI-KHIEUKH B54D D0A1 # HANGUL SYLLABLE KHIEUKH-YI-THIEUTH B54E D0A2 # HANGUL SYLLABLE KHIEUKH-YI-PHIEUPH B54F D0A3 # HANGUL SYLLABLE KHIEUKH-YI-HIEUH B550 D0A6 # HANGUL SYLLABLE KHIEUKH-I-SSANGKIYEOK B551 D0A7 # HANGUL SYLLABLE KHIEUKH-I-KIYEOKSIOS B552 D0A9 # HANGUL SYLLABLE KHIEUKH-I-NIEUNCIEUC B553 D0AA # HANGUL SYLLABLE KHIEUKH-I-NIEUNHIEUH B554 D0AB # HANGUL SYLLABLE KHIEUKH-I-TIKEUT B555 D0AD # HANGUL SYLLABLE KHIEUKH-I-RIEULKIYEOK B556 D0AE # HANGUL SYLLABLE KHIEUKH-I-RIEULMIEUM B557 D0AF # HANGUL SYLLABLE KHIEUKH-I-RIEULPIEUP B558 D0B0 # HANGUL SYLLABLE KHIEUKH-I-RIEULSIOS B559 D0B1 # HANGUL SYLLABLE KHIEUKH-I-RIEULTHIEUTH B55A D0B2 # HANGUL SYLLABLE KHIEUKH-I-RIEULPHIEUPH B561 D0B3 # HANGUL SYLLABLE KHIEUKH-I-RIEULHIEUH B562 D0B6 # HANGUL SYLLABLE KHIEUKH-I-PIEUPSIOS B563 D0B8 # HANGUL SYLLABLE KHIEUKH-I-SSANGSIOS B564 D0BA # HANGUL SYLLABLE KHIEUKH-I-CIEUC B565 D0BB # HANGUL SYLLABLE KHIEUKH-I-CHIEUCH B566 D0BC # HANGUL SYLLABLE KHIEUKH-I-KHIEUKH B567 D0BD # HANGUL SYLLABLE KHIEUKH-I-THIEUTH B568 D0BE # HANGUL SYLLABLE KHIEUKH-I-PHIEUPH B569 D0BF # HANGUL SYLLABLE KHIEUKH-I-HIEUH B56A D0C2 # HANGUL SYLLABLE THIEUTH-A-SSANGKIYEOK B56B D0C3 # HANGUL SYLLABLE THIEUTH-A-KIYEOKSIOS B56C D0C5 # HANGUL SYLLABLE THIEUTH-A-NIEUNCIEUC B56D D0C6 # HANGUL SYLLABLE THIEUTH-A-NIEUNHIEUH B56E D0C7 # HANGUL SYLLABLE THIEUTH-A-TIKEUT B56F D0CA # HANGUL SYLLABLE THIEUTH-A-RIEULMIEUM B570 D0CB # HANGUL SYLLABLE THIEUTH-A-RIEULPIEUP B571 D0CC # HANGUL SYLLABLE THIEUTH-A-RIEULSIOS B572 D0CD # HANGUL SYLLABLE THIEUTH-A-RIEULTHIEUTH B573 D0CE # HANGUL SYLLABLE THIEUTH-A-RIEULPHIEUPH B574 D0CF # HANGUL SYLLABLE THIEUTH-A-RIEULHIEUH B575 D0D2 # HANGUL SYLLABLE THIEUTH-A-PIEUPSIOS B576 D0D6 # HANGUL SYLLABLE THIEUTH-A-CIEUC B577 D0D7 # HANGUL SYLLABLE THIEUTH-A-CHIEUCH B578 D0D8 # HANGUL SYLLABLE THIEUTH-A-KHIEUKH B579 D0D9 # HANGUL SYLLABLE THIEUTH-A-THIEUTH B57A D0DA # HANGUL SYLLABLE THIEUTH-A-PHIEUPH B581 D0DB # HANGUL SYLLABLE THIEUTH-A-HIEUH B582 D0DE # HANGUL SYLLABLE THIEUTH-AE-SSANGKIYEOK B583 D0DF # HANGUL SYLLABLE THIEUTH-AE-KIYEOKSIOS B584 D0E1 # HANGUL SYLLABLE THIEUTH-AE-NIEUNCIEUC B585 D0E2 # HANGUL SYLLABLE THIEUTH-AE-NIEUNHIEUH B586 D0E3 # HANGUL SYLLABLE THIEUTH-AE-TIKEUT B587 D0E5 # HANGUL SYLLABLE THIEUTH-AE-RIEULKIYEOK B588 D0E6 # HANGUL SYLLABLE THIEUTH-AE-RIEULMIEUM B589 D0E7 # HANGUL SYLLABLE THIEUTH-AE-RIEULPIEUP B58A D0E8 # HANGUL SYLLABLE THIEUTH-AE-RIEULSIOS B58B D0E9 # HANGUL SYLLABLE THIEUTH-AE-RIEULTHIEUTH B58C D0EA # HANGUL SYLLABLE THIEUTH-AE-RIEULPHIEUPH B58D D0EB # HANGUL SYLLABLE THIEUTH-AE-RIEULHIEUH B58E D0EE # HANGUL SYLLABLE THIEUTH-AE-PIEUPSIOS B58F D0F2 # HANGUL SYLLABLE THIEUTH-AE-CIEUC B590 D0F3 # HANGUL SYLLABLE THIEUTH-AE-CHIEUCH B591 D0F4 # HANGUL SYLLABLE THIEUTH-AE-KHIEUKH B592 D0F5 # HANGUL SYLLABLE THIEUTH-AE-THIEUTH B593 D0F6 # HANGUL SYLLABLE THIEUTH-AE-PHIEUPH B594 D0F7 # HANGUL SYLLABLE THIEUTH-AE-HIEUH B595 D0F9 # HANGUL SYLLABLE THIEUTH-YA-KIYEOK B596 D0FA # HANGUL SYLLABLE THIEUTH-YA-SSANGKIYEOK B597 D0FB # HANGUL SYLLABLE THIEUTH-YA-KIYEOKSIOS B598 D0FC # HANGUL SYLLABLE THIEUTH-YA-NIEUN B599 D0FD # HANGUL SYLLABLE THIEUTH-YA-NIEUNCIEUC B59A D0FE # HANGUL SYLLABLE THIEUTH-YA-NIEUNHIEUH B59B D0FF # HANGUL SYLLABLE THIEUTH-YA-TIKEUT B59C D100 # HANGUL SYLLABLE THIEUTH-YA-RIEUL B59D D101 # HANGUL SYLLABLE THIEUTH-YA-RIEULKIYEOK B59E D102 # HANGUL SYLLABLE THIEUTH-YA-RIEULMIEUM B59F D103 # HANGUL SYLLABLE THIEUTH-YA-RIEULPIEUP B5A0 D104 # HANGUL SYLLABLE THIEUTH-YA-RIEULSIOS B5A1 B367 # HANGUL SYLLABLE TIKEUT-EO-SIOS B5A2 B369 # HANGUL SYLLABLE TIKEUT-EO-IEUNG B5A3 B36B # HANGUL SYLLABLE TIKEUT-EO-CHIEUCH B5A4 B36E # HANGUL SYLLABLE TIKEUT-EO-PHIEUPH B5A5 B370 # HANGUL SYLLABLE TIKEUT-E B5A6 B371 # HANGUL SYLLABLE TIKEUT-E-KIYEOK B5A7 B374 # HANGUL SYLLABLE TIKEUT-E-NIEUN B5A8 B378 # HANGUL SYLLABLE TIKEUT-E-RIEUL B5A9 B380 # HANGUL SYLLABLE TIKEUT-E-MIEUM B5AA B381 # HANGUL SYLLABLE TIKEUT-E-PIEUP B5AB B383 # HANGUL SYLLABLE TIKEUT-E-SIOS B5AC B384 # HANGUL SYLLABLE TIKEUT-E-SSANGSIOS B5AD B385 # HANGUL SYLLABLE TIKEUT-E-IEUNG B5AE B38C # HANGUL SYLLABLE TIKEUT-YEO B5AF B390 # HANGUL SYLLABLE TIKEUT-YEO-NIEUN B5B0 B394 # HANGUL SYLLABLE TIKEUT-YEO-RIEUL B5B1 B3A0 # HANGUL SYLLABLE TIKEUT-YEO-SSANGSIOS B5B2 B3A1 # HANGUL SYLLABLE TIKEUT-YEO-IEUNG B5B3 B3A8 # HANGUL SYLLABLE TIKEUT-YE B5B4 B3AC # HANGUL SYLLABLE TIKEUT-YE-NIEUN B5B5 B3C4 # HANGUL SYLLABLE TIKEUT-O B5B6 B3C5 # HANGUL SYLLABLE TIKEUT-O-KIYEOK B5B7 B3C8 # HANGUL SYLLABLE TIKEUT-O-NIEUN B5B8 B3CB # HANGUL SYLLABLE TIKEUT-O-TIKEUT B5B9 B3CC # HANGUL SYLLABLE TIKEUT-O-RIEUL B5BA B3CE # HANGUL SYLLABLE TIKEUT-O-RIEULMIEUM B5BB B3D0 # HANGUL SYLLABLE TIKEUT-O-RIEULSIOS B5BC B3D4 # HANGUL SYLLABLE TIKEUT-O-MIEUM B5BD B3D5 # HANGUL SYLLABLE TIKEUT-O-PIEUP B5BE B3D7 # HANGUL SYLLABLE TIKEUT-O-SIOS B5BF B3D9 # HANGUL SYLLABLE TIKEUT-O-IEUNG B5C0 B3DB # HANGUL SYLLABLE TIKEUT-O-CHIEUCH B5C1 B3DD # HANGUL SYLLABLE TIKEUT-O-THIEUTH B5C2 B3E0 # HANGUL SYLLABLE TIKEUT-WA B5C3 B3E4 # HANGUL SYLLABLE TIKEUT-WA-NIEUN B5C4 B3E8 # HANGUL SYLLABLE TIKEUT-WA-RIEUL B5C5 B3FC # HANGUL SYLLABLE TIKEUT-WAE B5C6 B410 # HANGUL SYLLABLE TIKEUT-WAE-SSANGSIOS B5C7 B418 # HANGUL SYLLABLE TIKEUT-OE B5C8 B41C # HANGUL SYLLABLE TIKEUT-OE-NIEUN B5C9 B420 # HANGUL SYLLABLE TIKEUT-OE-RIEUL B5CA B428 # HANGUL SYLLABLE TIKEUT-OE-MIEUM B5CB B429 # HANGUL SYLLABLE TIKEUT-OE-PIEUP B5CC B42B # HANGUL SYLLABLE TIKEUT-OE-SIOS B5CD B434 # HANGUL SYLLABLE TIKEUT-YO B5CE B450 # HANGUL SYLLABLE TIKEUT-U B5CF B451 # HANGUL SYLLABLE TIKEUT-U-KIYEOK B5D0 B454 # HANGUL SYLLABLE TIKEUT-U-NIEUN B5D1 B458 # HANGUL SYLLABLE TIKEUT-U-RIEUL B5D2 B460 # HANGUL SYLLABLE TIKEUT-U-MIEUM B5D3 B461 # HANGUL SYLLABLE TIKEUT-U-PIEUP B5D4 B463 # HANGUL SYLLABLE TIKEUT-U-SIOS B5D5 B465 # HANGUL SYLLABLE TIKEUT-U-IEUNG B5D6 B46C # HANGUL SYLLABLE TIKEUT-WEO B5D7 B480 # HANGUL SYLLABLE TIKEUT-WEO-SSANGSIOS B5D8 B488 # HANGUL SYLLABLE TIKEUT-WE B5D9 B49D # HANGUL SYLLABLE TIKEUT-WE-IEUNG B5DA B4A4 # HANGUL SYLLABLE TIKEUT-WI B5DB B4A8 # HANGUL SYLLABLE TIKEUT-WI-NIEUN B5DC B4AC # HANGUL SYLLABLE TIKEUT-WI-RIEUL B5DD B4B5 # HANGUL SYLLABLE TIKEUT-WI-PIEUP B5DE B4B7 # HANGUL SYLLABLE TIKEUT-WI-SIOS B5DF B4B9 # HANGUL SYLLABLE TIKEUT-WI-IEUNG B5E0 B4C0 # HANGUL SYLLABLE TIKEUT-YU B5E1 B4C4 # HANGUL SYLLABLE TIKEUT-YU-NIEUN B5E2 B4C8 # HANGUL SYLLABLE TIKEUT-YU-RIEUL B5E3 B4D0 # HANGUL SYLLABLE TIKEUT-YU-MIEUM B5E4 B4D5 # HANGUL SYLLABLE TIKEUT-YU-IEUNG B5E5 B4DC # HANGUL SYLLABLE TIKEUT-EU B5E6 B4DD # HANGUL SYLLABLE TIKEUT-EU-KIYEOK B5E7 B4E0 # HANGUL SYLLABLE TIKEUT-EU-NIEUN B5E8 B4E3 # HANGUL SYLLABLE TIKEUT-EU-TIKEUT B5E9 B4E4 # HANGUL SYLLABLE TIKEUT-EU-RIEUL B5EA B4E6 # HANGUL SYLLABLE TIKEUT-EU-RIEULMIEUM B5EB B4EC # HANGUL SYLLABLE TIKEUT-EU-MIEUM B5EC B4ED # HANGUL SYLLABLE TIKEUT-EU-PIEUP B5ED B4EF # HANGUL SYLLABLE TIKEUT-EU-SIOS B5EE B4F1 # HANGUL SYLLABLE TIKEUT-EU-IEUNG B5EF B4F8 # HANGUL SYLLABLE TIKEUT-YI B5F0 B514 # HANGUL SYLLABLE TIKEUT-I B5F1 B515 # HANGUL SYLLABLE TIKEUT-I-KIYEOK B5F2 B518 # HANGUL SYLLABLE TIKEUT-I-NIEUN B5F3 B51B # HANGUL SYLLABLE TIKEUT-I-TIKEUT B5F4 B51C # HANGUL SYLLABLE TIKEUT-I-RIEUL B5F5 B524 # HANGUL SYLLABLE TIKEUT-I-MIEUM B5F6 B525 # HANGUL SYLLABLE TIKEUT-I-PIEUP B5F7 B527 # HANGUL SYLLABLE TIKEUT-I-SIOS B5F8 B528 # HANGUL SYLLABLE TIKEUT-I-SSANGSIOS B5F9 B529 # HANGUL SYLLABLE TIKEUT-I-IEUNG B5FA B52A # HANGUL SYLLABLE TIKEUT-I-CIEUC B5FB B530 # HANGUL SYLLABLE SSANGTIKEUT-A B5FC B531 # HANGUL SYLLABLE SSANGTIKEUT-A-KIYEOK B5FD B534 # HANGUL SYLLABLE SSANGTIKEUT-A-NIEUN B5FE B538 # HANGUL SYLLABLE SSANGTIKEUT-A-RIEUL B641 D105 # HANGUL SYLLABLE THIEUTH-YA-RIEULTHIEUTH B642 D106 # HANGUL SYLLABLE THIEUTH-YA-RIEULPHIEUPH B643 D107 # HANGUL SYLLABLE THIEUTH-YA-RIEULHIEUH B644 D108 # HANGUL SYLLABLE THIEUTH-YA-MIEUM B645 D109 # HANGUL SYLLABLE THIEUTH-YA-PIEUP B646 D10A # HANGUL SYLLABLE THIEUTH-YA-PIEUPSIOS B647 D10B # HANGUL SYLLABLE THIEUTH-YA-SIOS B648 D10C # HANGUL SYLLABLE THIEUTH-YA-SSANGSIOS B649 D10E # HANGUL SYLLABLE THIEUTH-YA-CIEUC B64A D10F # HANGUL SYLLABLE THIEUTH-YA-CHIEUCH B64B D110 # HANGUL SYLLABLE THIEUTH-YA-KHIEUKH B64C D111 # HANGUL SYLLABLE THIEUTH-YA-THIEUTH B64D D112 # HANGUL SYLLABLE THIEUTH-YA-PHIEUPH B64E D113 # HANGUL SYLLABLE THIEUTH-YA-HIEUH B64F D114 # HANGUL SYLLABLE THIEUTH-YAE B650 D115 # HANGUL SYLLABLE THIEUTH-YAE-KIYEOK B651 D116 # HANGUL SYLLABLE THIEUTH-YAE-SSANGKIYEOK B652 D117 # HANGUL SYLLABLE THIEUTH-YAE-KIYEOKSIOS B653 D118 # HANGUL SYLLABLE THIEUTH-YAE-NIEUN B654 D119 # HANGUL SYLLABLE THIEUTH-YAE-NIEUNCIEUC B655 D11A # HANGUL SYLLABLE THIEUTH-YAE-NIEUNHIEUH B656 D11B # HANGUL SYLLABLE THIEUTH-YAE-TIKEUT B657 D11C # HANGUL SYLLABLE THIEUTH-YAE-RIEUL B658 D11D # HANGUL SYLLABLE THIEUTH-YAE-RIEULKIYEOK B659 D11E # HANGUL SYLLABLE THIEUTH-YAE-RIEULMIEUM B65A D11F # HANGUL SYLLABLE THIEUTH-YAE-RIEULPIEUP B661 D120 # HANGUL SYLLABLE THIEUTH-YAE-RIEULSIOS B662 D121 # HANGUL SYLLABLE THIEUTH-YAE-RIEULTHIEUTH B663 D122 # HANGUL SYLLABLE THIEUTH-YAE-RIEULPHIEUPH B664 D123 # HANGUL SYLLABLE THIEUTH-YAE-RIEULHIEUH B665 D124 # HANGUL SYLLABLE THIEUTH-YAE-MIEUM B666 D125 # HANGUL SYLLABLE THIEUTH-YAE-PIEUP B667 D126 # HANGUL SYLLABLE THIEUTH-YAE-PIEUPSIOS B668 D127 # HANGUL SYLLABLE THIEUTH-YAE-SIOS B669 D128 # HANGUL SYLLABLE THIEUTH-YAE-SSANGSIOS B66A D129 # HANGUL SYLLABLE THIEUTH-YAE-IEUNG B66B D12A # HANGUL SYLLABLE THIEUTH-YAE-CIEUC B66C D12B # HANGUL SYLLABLE THIEUTH-YAE-CHIEUCH B66D D12C # HANGUL SYLLABLE THIEUTH-YAE-KHIEUKH B66E D12D # HANGUL SYLLABLE THIEUTH-YAE-THIEUTH B66F D12E # HANGUL SYLLABLE THIEUTH-YAE-PHIEUPH B670 D12F # HANGUL SYLLABLE THIEUTH-YAE-HIEUH B671 D132 # HANGUL SYLLABLE THIEUTH-EO-SSANGKIYEOK B672 D133 # HANGUL SYLLABLE THIEUTH-EO-KIYEOKSIOS B673 D135 # HANGUL SYLLABLE THIEUTH-EO-NIEUNCIEUC B674 D136 # HANGUL SYLLABLE THIEUTH-EO-NIEUNHIEUH B675 D137 # HANGUL SYLLABLE THIEUTH-EO-TIKEUT B676 D139 # HANGUL SYLLABLE THIEUTH-EO-RIEULKIYEOK B677 D13B # HANGUL SYLLABLE THIEUTH-EO-RIEULPIEUP B678 D13C # HANGUL SYLLABLE THIEUTH-EO-RIEULSIOS B679 D13D # HANGUL SYLLABLE THIEUTH-EO-RIEULTHIEUTH B67A D13E # HANGUL SYLLABLE THIEUTH-EO-RIEULPHIEUPH B681 D13F # HANGUL SYLLABLE THIEUTH-EO-RIEULHIEUH B682 D142 # HANGUL SYLLABLE THIEUTH-EO-PIEUPSIOS B683 D146 # HANGUL SYLLABLE THIEUTH-EO-CIEUC B684 D147 # HANGUL SYLLABLE THIEUTH-EO-CHIEUCH B685 D148 # HANGUL SYLLABLE THIEUTH-EO-KHIEUKH B686 D149 # HANGUL SYLLABLE THIEUTH-EO-THIEUTH B687 D14A # HANGUL SYLLABLE THIEUTH-EO-PHIEUPH B688 D14B # HANGUL SYLLABLE THIEUTH-EO-HIEUH B689 D14E # HANGUL SYLLABLE THIEUTH-E-SSANGKIYEOK B68A D14F # HANGUL SYLLABLE THIEUTH-E-KIYEOKSIOS B68B D151 # HANGUL SYLLABLE THIEUTH-E-NIEUNCIEUC B68C D152 # HANGUL SYLLABLE THIEUTH-E-NIEUNHIEUH B68D D153 # HANGUL SYLLABLE THIEUTH-E-TIKEUT B68E D155 # HANGUL SYLLABLE THIEUTH-E-RIEULKIYEOK B68F D156 # HANGUL SYLLABLE THIEUTH-E-RIEULMIEUM B690 D157 # HANGUL SYLLABLE THIEUTH-E-RIEULPIEUP B691 D158 # HANGUL SYLLABLE THIEUTH-E-RIEULSIOS B692 D159 # HANGUL SYLLABLE THIEUTH-E-RIEULTHIEUTH B693 D15A # HANGUL SYLLABLE THIEUTH-E-RIEULPHIEUPH B694 D15B # HANGUL SYLLABLE THIEUTH-E-RIEULHIEUH B695 D15E # HANGUL SYLLABLE THIEUTH-E-PIEUPSIOS B696 D160 # HANGUL SYLLABLE THIEUTH-E-SSANGSIOS B697 D162 # HANGUL SYLLABLE THIEUTH-E-CIEUC B698 D163 # HANGUL SYLLABLE THIEUTH-E-CHIEUCH B699 D164 # HANGUL SYLLABLE THIEUTH-E-KHIEUKH B69A D165 # HANGUL SYLLABLE THIEUTH-E-THIEUTH B69B D166 # HANGUL SYLLABLE THIEUTH-E-PHIEUPH B69C D167 # HANGUL SYLLABLE THIEUTH-E-HIEUH B69D D169 # HANGUL SYLLABLE THIEUTH-YEO-KIYEOK B69E D16A # HANGUL SYLLABLE THIEUTH-YEO-SSANGKIYEOK B69F D16B # HANGUL SYLLABLE THIEUTH-YEO-KIYEOKSIOS B6A0 D16D # HANGUL SYLLABLE THIEUTH-YEO-NIEUNCIEUC B6A1 B540 # HANGUL SYLLABLE SSANGTIKEUT-A-MIEUM B6A2 B541 # HANGUL SYLLABLE SSANGTIKEUT-A-PIEUP B6A3 B543 # HANGUL SYLLABLE SSANGTIKEUT-A-SIOS B6A4 B544 # HANGUL SYLLABLE SSANGTIKEUT-A-SSANGSIOS B6A5 B545 # HANGUL SYLLABLE SSANGTIKEUT-A-IEUNG B6A6 B54B # HANGUL SYLLABLE SSANGTIKEUT-A-HIEUH B6A7 B54C # HANGUL SYLLABLE SSANGTIKEUT-AE B6A8 B54D # HANGUL SYLLABLE SSANGTIKEUT-AE-KIYEOK B6A9 B550 # HANGUL SYLLABLE SSANGTIKEUT-AE-NIEUN B6AA B554 # HANGUL SYLLABLE SSANGTIKEUT-AE-RIEUL B6AB B55C # HANGUL SYLLABLE SSANGTIKEUT-AE-MIEUM B6AC B55D # HANGUL SYLLABLE SSANGTIKEUT-AE-PIEUP B6AD B55F # HANGUL SYLLABLE SSANGTIKEUT-AE-SIOS B6AE B560 # HANGUL SYLLABLE SSANGTIKEUT-AE-SSANGSIOS B6AF B561 # HANGUL SYLLABLE SSANGTIKEUT-AE-IEUNG B6B0 B5A0 # HANGUL SYLLABLE SSANGTIKEUT-EO B6B1 B5A1 # HANGUL SYLLABLE SSANGTIKEUT-EO-KIYEOK B6B2 B5A4 # HANGUL SYLLABLE SSANGTIKEUT-EO-NIEUN B6B3 B5A8 # HANGUL SYLLABLE SSANGTIKEUT-EO-RIEUL B6B4 B5AA # HANGUL SYLLABLE SSANGTIKEUT-EO-RIEULMIEUM B6B5 B5AB # HANGUL SYLLABLE SSANGTIKEUT-EO-RIEULPIEUP B6B6 B5B0 # HANGUL SYLLABLE SSANGTIKEUT-EO-MIEUM B6B7 B5B1 # HANGUL SYLLABLE SSANGTIKEUT-EO-PIEUP B6B8 B5B3 # HANGUL SYLLABLE SSANGTIKEUT-EO-SIOS B6B9 B5B4 # HANGUL SYLLABLE SSANGTIKEUT-EO-SSANGSIOS B6BA B5B5 # HANGUL SYLLABLE SSANGTIKEUT-EO-IEUNG B6BB B5BB # HANGUL SYLLABLE SSANGTIKEUT-EO-HIEUH B6BC B5BC # HANGUL SYLLABLE SSANGTIKEUT-E B6BD B5BD # HANGUL SYLLABLE SSANGTIKEUT-E-KIYEOK B6BE B5C0 # HANGUL SYLLABLE SSANGTIKEUT-E-NIEUN B6BF B5C4 # HANGUL SYLLABLE SSANGTIKEUT-E-RIEUL B6C0 B5CC # HANGUL SYLLABLE SSANGTIKEUT-E-MIEUM B6C1 B5CD # HANGUL SYLLABLE SSANGTIKEUT-E-PIEUP B6C2 B5CF # HANGUL SYLLABLE SSANGTIKEUT-E-SIOS B6C3 B5D0 # HANGUL SYLLABLE SSANGTIKEUT-E-SSANGSIOS B6C4 B5D1 # HANGUL SYLLABLE SSANGTIKEUT-E-IEUNG B6C5 B5D8 # HANGUL SYLLABLE SSANGTIKEUT-YEO B6C6 B5EC # HANGUL SYLLABLE SSANGTIKEUT-YEO-SSANGSIOS B6C7 B610 # HANGUL SYLLABLE SSANGTIKEUT-O B6C8 B611 # HANGUL SYLLABLE SSANGTIKEUT-O-KIYEOK B6C9 B614 # HANGUL SYLLABLE SSANGTIKEUT-O-NIEUN B6CA B618 # HANGUL SYLLABLE SSANGTIKEUT-O-RIEUL B6CB B625 # HANGUL SYLLABLE SSANGTIKEUT-O-IEUNG B6CC B62C # HANGUL SYLLABLE SSANGTIKEUT-WA B6CD B634 # HANGUL SYLLABLE SSANGTIKEUT-WA-RIEUL B6CE B648 # HANGUL SYLLABLE SSANGTIKEUT-WAE B6CF B664 # HANGUL SYLLABLE SSANGTIKEUT-OE B6D0 B668 # HANGUL SYLLABLE SSANGTIKEUT-OE-NIEUN B6D1 B69C # HANGUL SYLLABLE SSANGTIKEUT-U B6D2 B69D # HANGUL SYLLABLE SSANGTIKEUT-U-KIYEOK B6D3 B6A0 # HANGUL SYLLABLE SSANGTIKEUT-U-NIEUN B6D4 B6A4 # HANGUL SYLLABLE SSANGTIKEUT-U-RIEUL B6D5 B6AB # HANGUL SYLLABLE SSANGTIKEUT-U-RIEULHIEUH B6D6 B6AC # HANGUL SYLLABLE SSANGTIKEUT-U-MIEUM B6D7 B6B1 # HANGUL SYLLABLE SSANGTIKEUT-U-IEUNG B6D8 B6D4 # HANGUL SYLLABLE SSANGTIKEUT-WE B6D9 B6F0 # HANGUL SYLLABLE SSANGTIKEUT-WI B6DA B6F4 # HANGUL SYLLABLE SSANGTIKEUT-WI-NIEUN B6DB B6F8 # HANGUL SYLLABLE SSANGTIKEUT-WI-RIEUL B6DC B700 # HANGUL SYLLABLE SSANGTIKEUT-WI-MIEUM B6DD B701 # HANGUL SYLLABLE SSANGTIKEUT-WI-PIEUP B6DE B705 # HANGUL SYLLABLE SSANGTIKEUT-WI-IEUNG B6DF B728 # HANGUL SYLLABLE SSANGTIKEUT-EU B6E0 B729 # HANGUL SYLLABLE SSANGTIKEUT-EU-KIYEOK B6E1 B72C # HANGUL SYLLABLE SSANGTIKEUT-EU-NIEUN B6E2 B72F # HANGUL SYLLABLE SSANGTIKEUT-EU-TIKEUT B6E3 B730 # HANGUL SYLLABLE SSANGTIKEUT-EU-RIEUL B6E4 B738 # HANGUL SYLLABLE SSANGTIKEUT-EU-MIEUM B6E5 B739 # HANGUL SYLLABLE SSANGTIKEUT-EU-PIEUP B6E6 B73B # HANGUL SYLLABLE SSANGTIKEUT-EU-SIOS B6E7 B744 # HANGUL SYLLABLE SSANGTIKEUT-YI B6E8 B748 # HANGUL SYLLABLE SSANGTIKEUT-YI-NIEUN B6E9 B74C # HANGUL SYLLABLE SSANGTIKEUT-YI-RIEUL B6EA B754 # HANGUL SYLLABLE SSANGTIKEUT-YI-MIEUM B6EB B755 # HANGUL SYLLABLE SSANGTIKEUT-YI-PIEUP B6EC B760 # HANGUL SYLLABLE SSANGTIKEUT-I B6ED B764 # HANGUL SYLLABLE SSANGTIKEUT-I-NIEUN B6EE B768 # HANGUL SYLLABLE SSANGTIKEUT-I-RIEUL B6EF B770 # HANGUL SYLLABLE SSANGTIKEUT-I-MIEUM B6F0 B771 # HANGUL SYLLABLE SSANGTIKEUT-I-PIEUP B6F1 B773 # HANGUL SYLLABLE SSANGTIKEUT-I-SIOS B6F2 B775 # HANGUL SYLLABLE SSANGTIKEUT-I-IEUNG B6F3 B77C # HANGUL SYLLABLE RIEUL-A B6F4 B77D # HANGUL SYLLABLE RIEUL-A-KIYEOK B6F5 B780 # HANGUL SYLLABLE RIEUL-A-NIEUN B6F6 B784 # HANGUL SYLLABLE RIEUL-A-RIEUL B6F7 B78C # HANGUL SYLLABLE RIEUL-A-MIEUM B6F8 B78D # HANGUL SYLLABLE RIEUL-A-PIEUP B6F9 B78F # HANGUL SYLLABLE RIEUL-A-SIOS B6FA B790 # HANGUL SYLLABLE RIEUL-A-SSANGSIOS B6FB B791 # HANGUL SYLLABLE RIEUL-A-IEUNG B6FC B792 # HANGUL SYLLABLE RIEUL-A-CIEUC B6FD B796 # HANGUL SYLLABLE RIEUL-A-PHIEUPH B6FE B797 # HANGUL SYLLABLE RIEUL-A-HIEUH B741 D16E # HANGUL SYLLABLE THIEUTH-YEO-NIEUNHIEUH B742 D16F # HANGUL SYLLABLE THIEUTH-YEO-TIKEUT B743 D170 # HANGUL SYLLABLE THIEUTH-YEO-RIEUL B744 D171 # HANGUL SYLLABLE THIEUTH-YEO-RIEULKIYEOK B745 D172 # HANGUL SYLLABLE THIEUTH-YEO-RIEULMIEUM B746 D173 # HANGUL SYLLABLE THIEUTH-YEO-RIEULPIEUP B747 D174 # HANGUL SYLLABLE THIEUTH-YEO-RIEULSIOS B748 D175 # HANGUL SYLLABLE THIEUTH-YEO-RIEULTHIEUTH B749 D176 # HANGUL SYLLABLE THIEUTH-YEO-RIEULPHIEUPH B74A D177 # HANGUL SYLLABLE THIEUTH-YEO-RIEULHIEUH B74B D178 # HANGUL SYLLABLE THIEUTH-YEO-MIEUM B74C D179 # HANGUL SYLLABLE THIEUTH-YEO-PIEUP B74D D17A # HANGUL SYLLABLE THIEUTH-YEO-PIEUPSIOS B74E D17B # HANGUL SYLLABLE THIEUTH-YEO-SIOS B74F D17D # HANGUL SYLLABLE THIEUTH-YEO-IEUNG B750 D17E # HANGUL SYLLABLE THIEUTH-YEO-CIEUC B751 D17F # HANGUL SYLLABLE THIEUTH-YEO-CHIEUCH B752 D180 # HANGUL SYLLABLE THIEUTH-YEO-KHIEUKH B753 D181 # HANGUL SYLLABLE THIEUTH-YEO-THIEUTH B754 D182 # HANGUL SYLLABLE THIEUTH-YEO-PHIEUPH B755 D183 # HANGUL SYLLABLE THIEUTH-YEO-HIEUH B756 D185 # HANGUL SYLLABLE THIEUTH-YE-KIYEOK B757 D186 # HANGUL SYLLABLE THIEUTH-YE-SSANGKIYEOK B758 D187 # HANGUL SYLLABLE THIEUTH-YE-KIYEOKSIOS B759 D189 # HANGUL SYLLABLE THIEUTH-YE-NIEUNCIEUC B75A D18A # HANGUL SYLLABLE THIEUTH-YE-NIEUNHIEUH B761 D18B # HANGUL SYLLABLE THIEUTH-YE-TIKEUT B762 D18C # HANGUL SYLLABLE THIEUTH-YE-RIEUL B763 D18D # HANGUL SYLLABLE THIEUTH-YE-RIEULKIYEOK B764 D18E # HANGUL SYLLABLE THIEUTH-YE-RIEULMIEUM B765 D18F # HANGUL SYLLABLE THIEUTH-YE-RIEULPIEUP B766 D190 # HANGUL SYLLABLE THIEUTH-YE-RIEULSIOS B767 D191 # HANGUL SYLLABLE THIEUTH-YE-RIEULTHIEUTH B768 D192 # HANGUL SYLLABLE THIEUTH-YE-RIEULPHIEUPH B769 D193 # HANGUL SYLLABLE THIEUTH-YE-RIEULHIEUH B76A D194 # HANGUL SYLLABLE THIEUTH-YE-MIEUM B76B D195 # HANGUL SYLLABLE THIEUTH-YE-PIEUP B76C D196 # HANGUL SYLLABLE THIEUTH-YE-PIEUPSIOS B76D D197 # HANGUL SYLLABLE THIEUTH-YE-SIOS B76E D198 # HANGUL SYLLABLE THIEUTH-YE-SSANGSIOS B76F D199 # HANGUL SYLLABLE THIEUTH-YE-IEUNG B770 D19A # HANGUL SYLLABLE THIEUTH-YE-CIEUC B771 D19B # HANGUL SYLLABLE THIEUTH-YE-CHIEUCH B772 D19C # HANGUL SYLLABLE THIEUTH-YE-KHIEUKH B773 D19D # HANGUL SYLLABLE THIEUTH-YE-THIEUTH B774 D19E # HANGUL SYLLABLE THIEUTH-YE-PHIEUPH B775 D19F # HANGUL SYLLABLE THIEUTH-YE-HIEUH B776 D1A2 # HANGUL SYLLABLE THIEUTH-O-SSANGKIYEOK B777 D1A3 # HANGUL SYLLABLE THIEUTH-O-KIYEOKSIOS B778 D1A5 # HANGUL SYLLABLE THIEUTH-O-NIEUNCIEUC B779 D1A6 # HANGUL SYLLABLE THIEUTH-O-NIEUNHIEUH B77A D1A7 # HANGUL SYLLABLE THIEUTH-O-TIKEUT B781 D1A9 # HANGUL SYLLABLE THIEUTH-O-RIEULKIYEOK B782 D1AA # HANGUL SYLLABLE THIEUTH-O-RIEULMIEUM B783 D1AB # HANGUL SYLLABLE THIEUTH-O-RIEULPIEUP B784 D1AC # HANGUL SYLLABLE THIEUTH-O-RIEULSIOS B785 D1AD # HANGUL SYLLABLE THIEUTH-O-RIEULTHIEUTH B786 D1AE # HANGUL SYLLABLE THIEUTH-O-RIEULPHIEUPH B787 D1AF # HANGUL SYLLABLE THIEUTH-O-RIEULHIEUH B788 D1B2 # HANGUL SYLLABLE THIEUTH-O-PIEUPSIOS B789 D1B4 # HANGUL SYLLABLE THIEUTH-O-SSANGSIOS B78A D1B6 # HANGUL SYLLABLE THIEUTH-O-CIEUC B78B D1B7 # HANGUL SYLLABLE THIEUTH-O-CHIEUCH B78C D1B8 # HANGUL SYLLABLE THIEUTH-O-KHIEUKH B78D D1B9 # HANGUL SYLLABLE THIEUTH-O-THIEUTH B78E D1BB # HANGUL SYLLABLE THIEUTH-O-HIEUH B78F D1BD # HANGUL SYLLABLE THIEUTH-WA-KIYEOK B790 D1BE # HANGUL SYLLABLE THIEUTH-WA-SSANGKIYEOK B791 D1BF # HANGUL SYLLABLE THIEUTH-WA-KIYEOKSIOS B792 D1C1 # HANGUL SYLLABLE THIEUTH-WA-NIEUNCIEUC B793 D1C2 # HANGUL SYLLABLE THIEUTH-WA-NIEUNHIEUH B794 D1C3 # HANGUL SYLLABLE THIEUTH-WA-TIKEUT B795 D1C4 # HANGUL SYLLABLE THIEUTH-WA-RIEUL B796 D1C5 # HANGUL SYLLABLE THIEUTH-WA-RIEULKIYEOK B797 D1C6 # HANGUL SYLLABLE THIEUTH-WA-RIEULMIEUM B798 D1C7 # HANGUL SYLLABLE THIEUTH-WA-RIEULPIEUP B799 D1C8 # HANGUL SYLLABLE THIEUTH-WA-RIEULSIOS B79A D1C9 # HANGUL SYLLABLE THIEUTH-WA-RIEULTHIEUTH B79B D1CA # HANGUL SYLLABLE THIEUTH-WA-RIEULPHIEUPH B79C D1CB # HANGUL SYLLABLE THIEUTH-WA-RIEULHIEUH B79D D1CC # HANGUL SYLLABLE THIEUTH-WA-MIEUM B79E D1CD # HANGUL SYLLABLE THIEUTH-WA-PIEUP B79F D1CE # HANGUL SYLLABLE THIEUTH-WA-PIEUPSIOS B7A0 D1CF # HANGUL SYLLABLE THIEUTH-WA-SIOS B7A1 B798 # HANGUL SYLLABLE RIEUL-AE B7A2 B799 # HANGUL SYLLABLE RIEUL-AE-KIYEOK B7A3 B79C # HANGUL SYLLABLE RIEUL-AE-NIEUN B7A4 B7A0 # HANGUL SYLLABLE RIEUL-AE-RIEUL B7A5 B7A8 # HANGUL SYLLABLE RIEUL-AE-MIEUM B7A6 B7A9 # HANGUL SYLLABLE RIEUL-AE-PIEUP B7A7 B7AB # HANGUL SYLLABLE RIEUL-AE-SIOS B7A8 B7AC # HANGUL SYLLABLE RIEUL-AE-SSANGSIOS B7A9 B7AD # HANGUL SYLLABLE RIEUL-AE-IEUNG B7AA B7B4 # HANGUL SYLLABLE RIEUL-YA B7AB B7B5 # HANGUL SYLLABLE RIEUL-YA-KIYEOK B7AC B7B8 # HANGUL SYLLABLE RIEUL-YA-NIEUN B7AD B7C7 # HANGUL SYLLABLE RIEUL-YA-SIOS B7AE B7C9 # HANGUL SYLLABLE RIEUL-YA-IEUNG B7AF B7EC # HANGUL SYLLABLE RIEUL-EO B7B0 B7ED # HANGUL SYLLABLE RIEUL-EO-KIYEOK B7B1 B7F0 # HANGUL SYLLABLE RIEUL-EO-NIEUN B7B2 B7F4 # HANGUL SYLLABLE RIEUL-EO-RIEUL B7B3 B7FC # HANGUL SYLLABLE RIEUL-EO-MIEUM B7B4 B7FD # HANGUL SYLLABLE RIEUL-EO-PIEUP B7B5 B7FF # HANGUL SYLLABLE RIEUL-EO-SIOS B7B6 B800 # HANGUL SYLLABLE RIEUL-EO-SSANGSIOS B7B7 B801 # HANGUL SYLLABLE RIEUL-EO-IEUNG B7B8 B807 # HANGUL SYLLABLE RIEUL-EO-HIEUH B7B9 B808 # HANGUL SYLLABLE RIEUL-E B7BA B809 # HANGUL SYLLABLE RIEUL-E-KIYEOK B7BB B80C # HANGUL SYLLABLE RIEUL-E-NIEUN B7BC B810 # HANGUL SYLLABLE RIEUL-E-RIEUL B7BD B818 # HANGUL SYLLABLE RIEUL-E-MIEUM B7BE B819 # HANGUL SYLLABLE RIEUL-E-PIEUP B7BF B81B # HANGUL SYLLABLE RIEUL-E-SIOS B7C0 B81D # HANGUL SYLLABLE RIEUL-E-IEUNG B7C1 B824 # HANGUL SYLLABLE RIEUL-YEO B7C2 B825 # HANGUL SYLLABLE RIEUL-YEO-KIYEOK B7C3 B828 # HANGUL SYLLABLE RIEUL-YEO-NIEUN B7C4 B82C # HANGUL SYLLABLE RIEUL-YEO-RIEUL B7C5 B834 # HANGUL SYLLABLE RIEUL-YEO-MIEUM B7C6 B835 # HANGUL SYLLABLE RIEUL-YEO-PIEUP B7C7 B837 # HANGUL SYLLABLE RIEUL-YEO-SIOS B7C8 B838 # HANGUL SYLLABLE RIEUL-YEO-SSANGSIOS B7C9 B839 # HANGUL SYLLABLE RIEUL-YEO-IEUNG B7CA B840 # HANGUL SYLLABLE RIEUL-YE B7CB B844 # HANGUL SYLLABLE RIEUL-YE-NIEUN B7CC B851 # HANGUL SYLLABLE RIEUL-YE-PIEUP B7CD B853 # HANGUL SYLLABLE RIEUL-YE-SIOS B7CE B85C # HANGUL SYLLABLE RIEUL-O B7CF B85D # HANGUL SYLLABLE RIEUL-O-KIYEOK B7D0 B860 # HANGUL SYLLABLE RIEUL-O-NIEUN B7D1 B864 # HANGUL SYLLABLE RIEUL-O-RIEUL B7D2 B86C # HANGUL SYLLABLE RIEUL-O-MIEUM B7D3 B86D # HANGUL SYLLABLE RIEUL-O-PIEUP B7D4 B86F # HANGUL SYLLABLE RIEUL-O-SIOS B7D5 B871 # HANGUL SYLLABLE RIEUL-O-IEUNG B7D6 B878 # HANGUL SYLLABLE RIEUL-WA B7D7 B87C # HANGUL SYLLABLE RIEUL-WA-NIEUN B7D8 B88D # HANGUL SYLLABLE RIEUL-WA-IEUNG B7D9 B8A8 # HANGUL SYLLABLE RIEUL-WAE-SSANGSIOS B7DA B8B0 # HANGUL SYLLABLE RIEUL-OE B7DB B8B4 # HANGUL SYLLABLE RIEUL-OE-NIEUN B7DC B8B8 # HANGUL SYLLABLE RIEUL-OE-RIEUL B7DD B8C0 # HANGUL SYLLABLE RIEUL-OE-MIEUM B7DE B8C1 # HANGUL SYLLABLE RIEUL-OE-PIEUP B7DF B8C3 # HANGUL SYLLABLE RIEUL-OE-SIOS B7E0 B8C5 # HANGUL SYLLABLE RIEUL-OE-IEUNG B7E1 B8CC # HANGUL SYLLABLE RIEUL-YO B7E2 B8D0 # HANGUL SYLLABLE RIEUL-YO-NIEUN B7E3 B8D4 # HANGUL SYLLABLE RIEUL-YO-RIEUL B7E4 B8DD # HANGUL SYLLABLE RIEUL-YO-PIEUP B7E5 B8DF # HANGUL SYLLABLE RIEUL-YO-SIOS B7E6 B8E1 # HANGUL SYLLABLE RIEUL-YO-IEUNG B7E7 B8E8 # HANGUL SYLLABLE RIEUL-U B7E8 B8E9 # HANGUL SYLLABLE RIEUL-U-KIYEOK B7E9 B8EC # HANGUL SYLLABLE RIEUL-U-NIEUN B7EA B8F0 # HANGUL SYLLABLE RIEUL-U-RIEUL B7EB B8F8 # HANGUL SYLLABLE RIEUL-U-MIEUM B7EC B8F9 # HANGUL SYLLABLE RIEUL-U-PIEUP B7ED B8FB # HANGUL SYLLABLE RIEUL-U-SIOS B7EE B8FD # HANGUL SYLLABLE RIEUL-U-IEUNG B7EF B904 # HANGUL SYLLABLE RIEUL-WEO B7F0 B918 # HANGUL SYLLABLE RIEUL-WEO-SSANGSIOS B7F1 B920 # HANGUL SYLLABLE RIEUL-WE B7F2 B93C # HANGUL SYLLABLE RIEUL-WI B7F3 B93D # HANGUL SYLLABLE RIEUL-WI-KIYEOK B7F4 B940 # HANGUL SYLLABLE RIEUL-WI-NIEUN B7F5 B944 # HANGUL SYLLABLE RIEUL-WI-RIEUL B7F6 B94C # HANGUL SYLLABLE RIEUL-WI-MIEUM B7F7 B94F # HANGUL SYLLABLE RIEUL-WI-SIOS B7F8 B951 # HANGUL SYLLABLE RIEUL-WI-IEUNG B7F9 B958 # HANGUL SYLLABLE RIEUL-YU B7FA B959 # HANGUL SYLLABLE RIEUL-YU-KIYEOK B7FB B95C # HANGUL SYLLABLE RIEUL-YU-NIEUN B7FC B960 # HANGUL SYLLABLE RIEUL-YU-RIEUL B7FD B968 # HANGUL SYLLABLE RIEUL-YU-MIEUM B7FE B969 # HANGUL SYLLABLE RIEUL-YU-PIEUP B841 D1D0 # HANGUL SYLLABLE THIEUTH-WA-SSANGSIOS B842 D1D1 # HANGUL SYLLABLE THIEUTH-WA-IEUNG B843 D1D2 # HANGUL SYLLABLE THIEUTH-WA-CIEUC B844 D1D3 # HANGUL SYLLABLE THIEUTH-WA-CHIEUCH B845 D1D4 # HANGUL SYLLABLE THIEUTH-WA-KHIEUKH B846 D1D5 # HANGUL SYLLABLE THIEUTH-WA-THIEUTH B847 D1D6 # HANGUL SYLLABLE THIEUTH-WA-PHIEUPH B848 D1D7 # HANGUL SYLLABLE THIEUTH-WA-HIEUH B849 D1D9 # HANGUL SYLLABLE THIEUTH-WAE-KIYEOK B84A D1DA # HANGUL SYLLABLE THIEUTH-WAE-SSANGKIYEOK B84B D1DB # HANGUL SYLLABLE THIEUTH-WAE-KIYEOKSIOS B84C D1DC # HANGUL SYLLABLE THIEUTH-WAE-NIEUN B84D D1DD # HANGUL SYLLABLE THIEUTH-WAE-NIEUNCIEUC B84E D1DE # HANGUL SYLLABLE THIEUTH-WAE-NIEUNHIEUH B84F D1DF # HANGUL SYLLABLE THIEUTH-WAE-TIKEUT B850 D1E0 # HANGUL SYLLABLE THIEUTH-WAE-RIEUL B851 D1E1 # HANGUL SYLLABLE THIEUTH-WAE-RIEULKIYEOK B852 D1E2 # HANGUL SYLLABLE THIEUTH-WAE-RIEULMIEUM B853 D1E3 # HANGUL SYLLABLE THIEUTH-WAE-RIEULPIEUP B854 D1E4 # HANGUL SYLLABLE THIEUTH-WAE-RIEULSIOS B855 D1E5 # HANGUL SYLLABLE THIEUTH-WAE-RIEULTHIEUTH B856 D1E6 # HANGUL SYLLABLE THIEUTH-WAE-RIEULPHIEUPH B857 D1E7 # HANGUL SYLLABLE THIEUTH-WAE-RIEULHIEUH B858 D1E8 # HANGUL SYLLABLE THIEUTH-WAE-MIEUM B859 D1E9 # HANGUL SYLLABLE THIEUTH-WAE-PIEUP B85A D1EA # HANGUL SYLLABLE THIEUTH-WAE-PIEUPSIOS B861 D1EB # HANGUL SYLLABLE THIEUTH-WAE-SIOS B862 D1EC # HANGUL SYLLABLE THIEUTH-WAE-SSANGSIOS B863 D1ED # HANGUL SYLLABLE THIEUTH-WAE-IEUNG B864 D1EE # HANGUL SYLLABLE THIEUTH-WAE-CIEUC B865 D1EF # HANGUL SYLLABLE THIEUTH-WAE-CHIEUCH B866 D1F0 # HANGUL SYLLABLE THIEUTH-WAE-KHIEUKH B867 D1F1 # HANGUL SYLLABLE THIEUTH-WAE-THIEUTH B868 D1F2 # HANGUL SYLLABLE THIEUTH-WAE-PHIEUPH B869 D1F3 # HANGUL SYLLABLE THIEUTH-WAE-HIEUH B86A D1F5 # HANGUL SYLLABLE THIEUTH-OE-KIYEOK B86B D1F6 # HANGUL SYLLABLE THIEUTH-OE-SSANGKIYEOK B86C D1F7 # HANGUL SYLLABLE THIEUTH-OE-KIYEOKSIOS B86D D1F9 # HANGUL SYLLABLE THIEUTH-OE-NIEUNCIEUC B86E D1FA # HANGUL SYLLABLE THIEUTH-OE-NIEUNHIEUH B86F D1FB # HANGUL SYLLABLE THIEUTH-OE-TIKEUT B870 D1FC # HANGUL SYLLABLE THIEUTH-OE-RIEUL B871 D1FD # HANGUL SYLLABLE THIEUTH-OE-RIEULKIYEOK B872 D1FE # HANGUL SYLLABLE THIEUTH-OE-RIEULMIEUM B873 D1FF # HANGUL SYLLABLE THIEUTH-OE-RIEULPIEUP B874 D200 # HANGUL SYLLABLE THIEUTH-OE-RIEULSIOS B875 D201 # HANGUL SYLLABLE THIEUTH-OE-RIEULTHIEUTH B876 D202 # HANGUL SYLLABLE THIEUTH-OE-RIEULPHIEUPH B877 D203 # HANGUL SYLLABLE THIEUTH-OE-RIEULHIEUH B878 D204 # HANGUL SYLLABLE THIEUTH-OE-MIEUM B879 D205 # HANGUL SYLLABLE THIEUTH-OE-PIEUP B87A D206 # HANGUL SYLLABLE THIEUTH-OE-PIEUPSIOS B881 D208 # HANGUL SYLLABLE THIEUTH-OE-SSANGSIOS B882 D20A # HANGUL SYLLABLE THIEUTH-OE-CIEUC B883 D20B # HANGUL SYLLABLE THIEUTH-OE-CHIEUCH B884 D20C # HANGUL SYLLABLE THIEUTH-OE-KHIEUKH B885 D20D # HANGUL SYLLABLE THIEUTH-OE-THIEUTH B886 D20E # HANGUL SYLLABLE THIEUTH-OE-PHIEUPH B887 D20F # HANGUL SYLLABLE THIEUTH-OE-HIEUH B888 D211 # HANGUL SYLLABLE THIEUTH-YO-KIYEOK B889 D212 # HANGUL SYLLABLE THIEUTH-YO-SSANGKIYEOK B88A D213 # HANGUL SYLLABLE THIEUTH-YO-KIYEOKSIOS B88B D214 # HANGUL SYLLABLE THIEUTH-YO-NIEUN B88C D215 # HANGUL SYLLABLE THIEUTH-YO-NIEUNCIEUC B88D D216 # HANGUL SYLLABLE THIEUTH-YO-NIEUNHIEUH B88E D217 # HANGUL SYLLABLE THIEUTH-YO-TIKEUT B88F D218 # HANGUL SYLLABLE THIEUTH-YO-RIEUL B890 D219 # HANGUL SYLLABLE THIEUTH-YO-RIEULKIYEOK B891 D21A # HANGUL SYLLABLE THIEUTH-YO-RIEULMIEUM B892 D21B # HANGUL SYLLABLE THIEUTH-YO-RIEULPIEUP B893 D21C # HANGUL SYLLABLE THIEUTH-YO-RIEULSIOS B894 D21D # HANGUL SYLLABLE THIEUTH-YO-RIEULTHIEUTH B895 D21E # HANGUL SYLLABLE THIEUTH-YO-RIEULPHIEUPH B896 D21F # HANGUL SYLLABLE THIEUTH-YO-RIEULHIEUH B897 D220 # HANGUL SYLLABLE THIEUTH-YO-MIEUM B898 D221 # HANGUL SYLLABLE THIEUTH-YO-PIEUP B899 D222 # HANGUL SYLLABLE THIEUTH-YO-PIEUPSIOS B89A D223 # HANGUL SYLLABLE THIEUTH-YO-SIOS B89B D224 # HANGUL SYLLABLE THIEUTH-YO-SSANGSIOS B89C D225 # HANGUL SYLLABLE THIEUTH-YO-IEUNG B89D D226 # HANGUL SYLLABLE THIEUTH-YO-CIEUC B89E D227 # HANGUL SYLLABLE THIEUTH-YO-CHIEUCH B89F D228 # HANGUL SYLLABLE THIEUTH-YO-KHIEUKH B8A0 D229 # HANGUL SYLLABLE THIEUTH-YO-THIEUTH B8A1 B96B # HANGUL SYLLABLE RIEUL-YU-SIOS B8A2 B96D # HANGUL SYLLABLE RIEUL-YU-IEUNG B8A3 B974 # HANGUL SYLLABLE RIEUL-EU B8A4 B975 # HANGUL SYLLABLE RIEUL-EU-KIYEOK B8A5 B978 # HANGUL SYLLABLE RIEUL-EU-NIEUN B8A6 B97C # HANGUL SYLLABLE RIEUL-EU-RIEUL B8A7 B984 # HANGUL SYLLABLE RIEUL-EU-MIEUM B8A8 B985 # HANGUL SYLLABLE RIEUL-EU-PIEUP B8A9 B987 # HANGUL SYLLABLE RIEUL-EU-SIOS B8AA B989 # HANGUL SYLLABLE RIEUL-EU-IEUNG B8AB B98A # HANGUL SYLLABLE RIEUL-EU-CIEUC B8AC B98D # HANGUL SYLLABLE RIEUL-EU-THIEUTH B8AD B98E # HANGUL SYLLABLE RIEUL-EU-PHIEUPH B8AE B9AC # HANGUL SYLLABLE RIEUL-I B8AF B9AD # HANGUL SYLLABLE RIEUL-I-KIYEOK B8B0 B9B0 # HANGUL SYLLABLE RIEUL-I-NIEUN B8B1 B9B4 # HANGUL SYLLABLE RIEUL-I-RIEUL B8B2 B9BC # HANGUL SYLLABLE RIEUL-I-MIEUM B8B3 B9BD # HANGUL SYLLABLE RIEUL-I-PIEUP B8B4 B9BF # HANGUL SYLLABLE RIEUL-I-SIOS B8B5 B9C1 # HANGUL SYLLABLE RIEUL-I-IEUNG B8B6 B9C8 # HANGUL SYLLABLE MIEUM-A B8B7 B9C9 # HANGUL SYLLABLE MIEUM-A-KIYEOK B8B8 B9CC # HANGUL SYLLABLE MIEUM-A-NIEUN B8B9 B9CE # HANGUL SYLLABLE MIEUM-A-NIEUNHIEUH B8BA B9CF # HANGUL SYLLABLE MIEUM-A-TIKEUT B8BB B9D0 # HANGUL SYLLABLE MIEUM-A-RIEUL B8BC B9D1 # HANGUL SYLLABLE MIEUM-A-RIEULKIYEOK B8BD B9D2 # HANGUL SYLLABLE MIEUM-A-RIEULMIEUM B8BE B9D8 # HANGUL SYLLABLE MIEUM-A-MIEUM B8BF B9D9 # HANGUL SYLLABLE MIEUM-A-PIEUP B8C0 B9DB # HANGUL SYLLABLE MIEUM-A-SIOS B8C1 B9DD # HANGUL SYLLABLE MIEUM-A-IEUNG B8C2 B9DE # HANGUL SYLLABLE MIEUM-A-CIEUC B8C3 B9E1 # HANGUL SYLLABLE MIEUM-A-THIEUTH B8C4 B9E3 # HANGUL SYLLABLE MIEUM-A-HIEUH B8C5 B9E4 # HANGUL SYLLABLE MIEUM-AE B8C6 B9E5 # HANGUL SYLLABLE MIEUM-AE-KIYEOK B8C7 B9E8 # HANGUL SYLLABLE MIEUM-AE-NIEUN B8C8 B9EC # HANGUL SYLLABLE MIEUM-AE-RIEUL B8C9 B9F4 # HANGUL SYLLABLE MIEUM-AE-MIEUM B8CA B9F5 # HANGUL SYLLABLE MIEUM-AE-PIEUP B8CB B9F7 # HANGUL SYLLABLE MIEUM-AE-SIOS B8CC B9F8 # HANGUL SYLLABLE MIEUM-AE-SSANGSIOS B8CD B9F9 # HANGUL SYLLABLE MIEUM-AE-IEUNG B8CE B9FA # HANGUL SYLLABLE MIEUM-AE-CIEUC B8CF BA00 # HANGUL SYLLABLE MIEUM-YA B8D0 BA01 # HANGUL SYLLABLE MIEUM-YA-KIYEOK B8D1 BA08 # HANGUL SYLLABLE MIEUM-YA-RIEUL B8D2 BA15 # HANGUL SYLLABLE MIEUM-YA-IEUNG B8D3 BA38 # HANGUL SYLLABLE MIEUM-EO B8D4 BA39 # HANGUL SYLLABLE MIEUM-EO-KIYEOK B8D5 BA3C # HANGUL SYLLABLE MIEUM-EO-NIEUN B8D6 BA40 # HANGUL SYLLABLE MIEUM-EO-RIEUL B8D7 BA42 # HANGUL SYLLABLE MIEUM-EO-RIEULMIEUM B8D8 BA48 # HANGUL SYLLABLE MIEUM-EO-MIEUM B8D9 BA49 # HANGUL SYLLABLE MIEUM-EO-PIEUP B8DA BA4B # HANGUL SYLLABLE MIEUM-EO-SIOS B8DB BA4D # HANGUL SYLLABLE MIEUM-EO-IEUNG B8DC BA4E # HANGUL SYLLABLE MIEUM-EO-CIEUC B8DD BA53 # HANGUL SYLLABLE MIEUM-EO-HIEUH B8DE BA54 # HANGUL SYLLABLE MIEUM-E B8DF BA55 # HANGUL SYLLABLE MIEUM-E-KIYEOK B8E0 BA58 # HANGUL SYLLABLE MIEUM-E-NIEUN B8E1 BA5C # HANGUL SYLLABLE MIEUM-E-RIEUL B8E2 BA64 # HANGUL SYLLABLE MIEUM-E-MIEUM B8E3 BA65 # HANGUL SYLLABLE MIEUM-E-PIEUP B8E4 BA67 # HANGUL SYLLABLE MIEUM-E-SIOS B8E5 BA68 # HANGUL SYLLABLE MIEUM-E-SSANGSIOS B8E6 BA69 # HANGUL SYLLABLE MIEUM-E-IEUNG B8E7 BA70 # HANGUL SYLLABLE MIEUM-YEO B8E8 BA71 # HANGUL SYLLABLE MIEUM-YEO-KIYEOK B8E9 BA74 # HANGUL SYLLABLE MIEUM-YEO-NIEUN B8EA BA78 # HANGUL SYLLABLE MIEUM-YEO-RIEUL B8EB BA83 # HANGUL SYLLABLE MIEUM-YEO-SIOS B8EC BA84 # HANGUL SYLLABLE MIEUM-YEO-SSANGSIOS B8ED BA85 # HANGUL SYLLABLE MIEUM-YEO-IEUNG B8EE BA87 # HANGUL SYLLABLE MIEUM-YEO-CHIEUCH B8EF BA8C # HANGUL SYLLABLE MIEUM-YE B8F0 BAA8 # HANGUL SYLLABLE MIEUM-O B8F1 BAA9 # HANGUL SYLLABLE MIEUM-O-KIYEOK B8F2 BAAB # HANGUL SYLLABLE MIEUM-O-KIYEOKSIOS B8F3 BAAC # HANGUL SYLLABLE MIEUM-O-NIEUN B8F4 BAB0 # HANGUL SYLLABLE MIEUM-O-RIEUL B8F5 BAB2 # HANGUL SYLLABLE MIEUM-O-RIEULMIEUM B8F6 BAB8 # HANGUL SYLLABLE MIEUM-O-MIEUM B8F7 BAB9 # HANGUL SYLLABLE MIEUM-O-PIEUP B8F8 BABB # HANGUL SYLLABLE MIEUM-O-SIOS B8F9 BABD # HANGUL SYLLABLE MIEUM-O-IEUNG B8FA BAC4 # HANGUL SYLLABLE MIEUM-WA B8FB BAC8 # HANGUL SYLLABLE MIEUM-WA-NIEUN B8FC BAD8 # HANGUL SYLLABLE MIEUM-WA-SSANGSIOS B8FD BAD9 # HANGUL SYLLABLE MIEUM-WA-IEUNG B8FE BAFC # HANGUL SYLLABLE MIEUM-OE B941 D22A # HANGUL SYLLABLE THIEUTH-YO-PHIEUPH B942 D22B # HANGUL SYLLABLE THIEUTH-YO-HIEUH B943 D22E # HANGUL SYLLABLE THIEUTH-U-SSANGKIYEOK B944 D22F # HANGUL SYLLABLE THIEUTH-U-KIYEOKSIOS B945 D231 # HANGUL SYLLABLE THIEUTH-U-NIEUNCIEUC B946 D232 # HANGUL SYLLABLE THIEUTH-U-NIEUNHIEUH B947 D233 # HANGUL SYLLABLE THIEUTH-U-TIKEUT B948 D235 # HANGUL SYLLABLE THIEUTH-U-RIEULKIYEOK B949 D236 # HANGUL SYLLABLE THIEUTH-U-RIEULMIEUM B94A D237 # HANGUL SYLLABLE THIEUTH-U-RIEULPIEUP B94B D238 # HANGUL SYLLABLE THIEUTH-U-RIEULSIOS B94C D239 # HANGUL SYLLABLE THIEUTH-U-RIEULTHIEUTH B94D D23A # HANGUL SYLLABLE THIEUTH-U-RIEULPHIEUPH B94E D23B # HANGUL SYLLABLE THIEUTH-U-RIEULHIEUH B94F D23E # HANGUL SYLLABLE THIEUTH-U-PIEUPSIOS B950 D240 # HANGUL SYLLABLE THIEUTH-U-SSANGSIOS B951 D242 # HANGUL SYLLABLE THIEUTH-U-CIEUC B952 D243 # HANGUL SYLLABLE THIEUTH-U-CHIEUCH B953 D244 # HANGUL SYLLABLE THIEUTH-U-KHIEUKH B954 D245 # HANGUL SYLLABLE THIEUTH-U-THIEUTH B955 D246 # HANGUL SYLLABLE THIEUTH-U-PHIEUPH B956 D247 # HANGUL SYLLABLE THIEUTH-U-HIEUH B957 D249 # HANGUL SYLLABLE THIEUTH-WEO-KIYEOK B958 D24A # HANGUL SYLLABLE THIEUTH-WEO-SSANGKIYEOK B959 D24B # HANGUL SYLLABLE THIEUTH-WEO-KIYEOKSIOS B95A D24C # HANGUL SYLLABLE THIEUTH-WEO-NIEUN B961 D24D # HANGUL SYLLABLE THIEUTH-WEO-NIEUNCIEUC B962 D24E # HANGUL SYLLABLE THIEUTH-WEO-NIEUNHIEUH B963 D24F # HANGUL SYLLABLE THIEUTH-WEO-TIKEUT B964 D250 # HANGUL SYLLABLE THIEUTH-WEO-RIEUL B965 D251 # HANGUL SYLLABLE THIEUTH-WEO-RIEULKIYEOK B966 D252 # HANGUL SYLLABLE THIEUTH-WEO-RIEULMIEUM B967 D253 # HANGUL SYLLABLE THIEUTH-WEO-RIEULPIEUP B968 D254 # HANGUL SYLLABLE THIEUTH-WEO-RIEULSIOS B969 D255 # HANGUL SYLLABLE THIEUTH-WEO-RIEULTHIEUTH B96A D256 # HANGUL SYLLABLE THIEUTH-WEO-RIEULPHIEUPH B96B D257 # HANGUL SYLLABLE THIEUTH-WEO-RIEULHIEUH B96C D258 # HANGUL SYLLABLE THIEUTH-WEO-MIEUM B96D D259 # HANGUL SYLLABLE THIEUTH-WEO-PIEUP B96E D25A # HANGUL SYLLABLE THIEUTH-WEO-PIEUPSIOS B96F D25B # HANGUL SYLLABLE THIEUTH-WEO-SIOS B970 D25D # HANGUL SYLLABLE THIEUTH-WEO-IEUNG B971 D25E # HANGUL SYLLABLE THIEUTH-WEO-CIEUC B972 D25F # HANGUL SYLLABLE THIEUTH-WEO-CHIEUCH B973 D260 # HANGUL SYLLABLE THIEUTH-WEO-KHIEUKH B974 D261 # HANGUL SYLLABLE THIEUTH-WEO-THIEUTH B975 D262 # HANGUL SYLLABLE THIEUTH-WEO-PHIEUPH B976 D263 # HANGUL SYLLABLE THIEUTH-WEO-HIEUH B977 D265 # HANGUL SYLLABLE THIEUTH-WE-KIYEOK B978 D266 # HANGUL SYLLABLE THIEUTH-WE-SSANGKIYEOK B979 D267 # HANGUL SYLLABLE THIEUTH-WE-KIYEOKSIOS B97A D268 # HANGUL SYLLABLE THIEUTH-WE-NIEUN B981 D269 # HANGUL SYLLABLE THIEUTH-WE-NIEUNCIEUC B982 D26A # HANGUL SYLLABLE THIEUTH-WE-NIEUNHIEUH B983 D26B # HANGUL SYLLABLE THIEUTH-WE-TIKEUT B984 D26C # HANGUL SYLLABLE THIEUTH-WE-RIEUL B985 D26D # HANGUL SYLLABLE THIEUTH-WE-RIEULKIYEOK B986 D26E # HANGUL SYLLABLE THIEUTH-WE-RIEULMIEUM B987 D26F # HANGUL SYLLABLE THIEUTH-WE-RIEULPIEUP B988 D270 # HANGUL SYLLABLE THIEUTH-WE-RIEULSIOS B989 D271 # HANGUL SYLLABLE THIEUTH-WE-RIEULTHIEUTH B98A D272 # HANGUL SYLLABLE THIEUTH-WE-RIEULPHIEUPH B98B D273 # HANGUL SYLLABLE THIEUTH-WE-RIEULHIEUH B98C D274 # HANGUL SYLLABLE THIEUTH-WE-MIEUM B98D D275 # HANGUL SYLLABLE THIEUTH-WE-PIEUP B98E D276 # HANGUL SYLLABLE THIEUTH-WE-PIEUPSIOS B98F D277 # HANGUL SYLLABLE THIEUTH-WE-SIOS B990 D278 # HANGUL SYLLABLE THIEUTH-WE-SSANGSIOS B991 D279 # HANGUL SYLLABLE THIEUTH-WE-IEUNG B992 D27A # HANGUL SYLLABLE THIEUTH-WE-CIEUC B993 D27B # HANGUL SYLLABLE THIEUTH-WE-CHIEUCH B994 D27C # HANGUL SYLLABLE THIEUTH-WE-KHIEUKH B995 D27D # HANGUL SYLLABLE THIEUTH-WE-THIEUTH B996 D27E # HANGUL SYLLABLE THIEUTH-WE-PHIEUPH B997 D27F # HANGUL SYLLABLE THIEUTH-WE-HIEUH B998 D282 # HANGUL SYLLABLE THIEUTH-WI-SSANGKIYEOK B999 D283 # HANGUL SYLLABLE THIEUTH-WI-KIYEOKSIOS B99A D285 # HANGUL SYLLABLE THIEUTH-WI-NIEUNCIEUC B99B D286 # HANGUL SYLLABLE THIEUTH-WI-NIEUNHIEUH B99C D287 # HANGUL SYLLABLE THIEUTH-WI-TIKEUT B99D D289 # HANGUL SYLLABLE THIEUTH-WI-RIEULKIYEOK B99E D28A # HANGUL SYLLABLE THIEUTH-WI-RIEULMIEUM B99F D28B # HANGUL SYLLABLE THIEUTH-WI-RIEULPIEUP B9A0 D28C # HANGUL SYLLABLE THIEUTH-WI-RIEULSIOS B9A1 BB00 # HANGUL SYLLABLE MIEUM-OE-NIEUN B9A2 BB04 # HANGUL SYLLABLE MIEUM-OE-RIEUL B9A3 BB0D # HANGUL SYLLABLE MIEUM-OE-PIEUP B9A4 BB0F # HANGUL SYLLABLE MIEUM-OE-SIOS B9A5 BB11 # HANGUL SYLLABLE MIEUM-OE-IEUNG B9A6 BB18 # HANGUL SYLLABLE MIEUM-YO B9A7 BB1C # HANGUL SYLLABLE MIEUM-YO-NIEUN B9A8 BB20 # HANGUL SYLLABLE MIEUM-YO-RIEUL B9A9 BB29 # HANGUL SYLLABLE MIEUM-YO-PIEUP B9AA BB2B # HANGUL SYLLABLE MIEUM-YO-SIOS B9AB BB34 # HANGUL SYLLABLE MIEUM-U B9AC BB35 # HANGUL SYLLABLE MIEUM-U-KIYEOK B9AD BB36 # HANGUL SYLLABLE MIEUM-U-SSANGKIYEOK B9AE BB38 # HANGUL SYLLABLE MIEUM-U-NIEUN B9AF BB3B # HANGUL SYLLABLE MIEUM-U-TIKEUT B9B0 BB3C # HANGUL SYLLABLE MIEUM-U-RIEUL B9B1 BB3D # HANGUL SYLLABLE MIEUM-U-RIEULKIYEOK B9B2 BB3E # HANGUL SYLLABLE MIEUM-U-RIEULMIEUM B9B3 BB44 # HANGUL SYLLABLE MIEUM-U-MIEUM B9B4 BB45 # HANGUL SYLLABLE MIEUM-U-PIEUP B9B5 BB47 # HANGUL SYLLABLE MIEUM-U-SIOS B9B6 BB49 # HANGUL SYLLABLE MIEUM-U-IEUNG B9B7 BB4D # HANGUL SYLLABLE MIEUM-U-THIEUTH B9B8 BB4F # HANGUL SYLLABLE MIEUM-U-HIEUH B9B9 BB50 # HANGUL SYLLABLE MIEUM-WEO B9BA BB54 # HANGUL SYLLABLE MIEUM-WEO-NIEUN B9BB BB58 # HANGUL SYLLABLE MIEUM-WEO-RIEUL B9BC BB61 # HANGUL SYLLABLE MIEUM-WEO-PIEUP B9BD BB63 # HANGUL SYLLABLE MIEUM-WEO-SIOS B9BE BB6C # HANGUL SYLLABLE MIEUM-WE B9BF BB88 # HANGUL SYLLABLE MIEUM-WI B9C0 BB8C # HANGUL SYLLABLE MIEUM-WI-NIEUN B9C1 BB90 # HANGUL SYLLABLE MIEUM-WI-RIEUL B9C2 BBA4 # HANGUL SYLLABLE MIEUM-YU B9C3 BBA8 # HANGUL SYLLABLE MIEUM-YU-NIEUN B9C4 BBAC # HANGUL SYLLABLE MIEUM-YU-RIEUL B9C5 BBB4 # HANGUL SYLLABLE MIEUM-YU-MIEUM B9C6 BBB7 # HANGUL SYLLABLE MIEUM-YU-SIOS B9C7 BBC0 # HANGUL SYLLABLE MIEUM-EU B9C8 BBC4 # HANGUL SYLLABLE MIEUM-EU-NIEUN B9C9 BBC8 # HANGUL SYLLABLE MIEUM-EU-RIEUL B9CA BBD0 # HANGUL SYLLABLE MIEUM-EU-MIEUM B9CB BBD3 # HANGUL SYLLABLE MIEUM-EU-SIOS B9CC BBF8 # HANGUL SYLLABLE MIEUM-I B9CD BBF9 # HANGUL SYLLABLE MIEUM-I-KIYEOK B9CE BBFC # HANGUL SYLLABLE MIEUM-I-NIEUN B9CF BBFF # HANGUL SYLLABLE MIEUM-I-TIKEUT B9D0 BC00 # HANGUL SYLLABLE MIEUM-I-RIEUL B9D1 BC02 # HANGUL SYLLABLE MIEUM-I-RIEULMIEUM B9D2 BC08 # HANGUL SYLLABLE MIEUM-I-MIEUM B9D3 BC09 # HANGUL SYLLABLE MIEUM-I-PIEUP B9D4 BC0B # HANGUL SYLLABLE MIEUM-I-SIOS B9D5 BC0C # HANGUL SYLLABLE MIEUM-I-SSANGSIOS B9D6 BC0D # HANGUL SYLLABLE MIEUM-I-IEUNG B9D7 BC0F # HANGUL SYLLABLE MIEUM-I-CHIEUCH B9D8 BC11 # HANGUL SYLLABLE MIEUM-I-THIEUTH B9D9 BC14 # HANGUL SYLLABLE PIEUP-A B9DA BC15 # HANGUL SYLLABLE PIEUP-A-KIYEOK B9DB BC16 # HANGUL SYLLABLE PIEUP-A-SSANGKIYEOK B9DC BC17 # HANGUL SYLLABLE PIEUP-A-KIYEOKSIOS B9DD BC18 # HANGUL SYLLABLE PIEUP-A-NIEUN B9DE BC1B # HANGUL SYLLABLE PIEUP-A-TIKEUT B9DF BC1C # HANGUL SYLLABLE PIEUP-A-RIEUL B9E0 BC1D # HANGUL SYLLABLE PIEUP-A-RIEULKIYEOK B9E1 BC1E # HANGUL SYLLABLE PIEUP-A-RIEULMIEUM B9E2 BC1F # HANGUL SYLLABLE PIEUP-A-RIEULPIEUP B9E3 BC24 # HANGUL SYLLABLE PIEUP-A-MIEUM B9E4 BC25 # HANGUL SYLLABLE PIEUP-A-PIEUP B9E5 BC27 # HANGUL SYLLABLE PIEUP-A-SIOS B9E6 BC29 # HANGUL SYLLABLE PIEUP-A-IEUNG B9E7 BC2D # HANGUL SYLLABLE PIEUP-A-THIEUTH B9E8 BC30 # HANGUL SYLLABLE PIEUP-AE B9E9 BC31 # HANGUL SYLLABLE PIEUP-AE-KIYEOK B9EA BC34 # HANGUL SYLLABLE PIEUP-AE-NIEUN B9EB BC38 # HANGUL SYLLABLE PIEUP-AE-RIEUL B9EC BC40 # HANGUL SYLLABLE PIEUP-AE-MIEUM B9ED BC41 # HANGUL SYLLABLE PIEUP-AE-PIEUP B9EE BC43 # HANGUL SYLLABLE PIEUP-AE-SIOS B9EF BC44 # HANGUL SYLLABLE PIEUP-AE-SSANGSIOS B9F0 BC45 # HANGUL SYLLABLE PIEUP-AE-IEUNG B9F1 BC49 # HANGUL SYLLABLE PIEUP-AE-THIEUTH B9F2 BC4C # HANGUL SYLLABLE PIEUP-YA B9F3 BC4D # HANGUL SYLLABLE PIEUP-YA-KIYEOK B9F4 BC50 # HANGUL SYLLABLE PIEUP-YA-NIEUN B9F5 BC5D # HANGUL SYLLABLE PIEUP-YA-PIEUP B9F6 BC84 # HANGUL SYLLABLE PIEUP-EO B9F7 BC85 # HANGUL SYLLABLE PIEUP-EO-KIYEOK B9F8 BC88 # HANGUL SYLLABLE PIEUP-EO-NIEUN B9F9 BC8B # HANGUL SYLLABLE PIEUP-EO-TIKEUT B9FA BC8C # HANGUL SYLLABLE PIEUP-EO-RIEUL B9FB BC8E # HANGUL SYLLABLE PIEUP-EO-RIEULMIEUM B9FC BC94 # HANGUL SYLLABLE PIEUP-EO-MIEUM B9FD BC95 # HANGUL SYLLABLE PIEUP-EO-PIEUP B9FE BC97 # HANGUL SYLLABLE PIEUP-EO-SIOS BA41 D28D # HANGUL SYLLABLE THIEUTH-WI-RIEULTHIEUTH BA42 D28E # HANGUL SYLLABLE THIEUTH-WI-RIEULPHIEUPH BA43 D28F # HANGUL SYLLABLE THIEUTH-WI-RIEULHIEUH BA44 D292 # HANGUL SYLLABLE THIEUTH-WI-PIEUPSIOS BA45 D293 # HANGUL SYLLABLE THIEUTH-WI-SIOS BA46 D294 # HANGUL SYLLABLE THIEUTH-WI-SSANGSIOS BA47 D296 # HANGUL SYLLABLE THIEUTH-WI-CIEUC BA48 D297 # HANGUL SYLLABLE THIEUTH-WI-CHIEUCH BA49 D298 # HANGUL SYLLABLE THIEUTH-WI-KHIEUKH BA4A D299 # HANGUL SYLLABLE THIEUTH-WI-THIEUTH BA4B D29A # HANGUL SYLLABLE THIEUTH-WI-PHIEUPH BA4C D29B # HANGUL SYLLABLE THIEUTH-WI-HIEUH BA4D D29D # HANGUL SYLLABLE THIEUTH-YU-KIYEOK BA4E D29E # HANGUL SYLLABLE THIEUTH-YU-SSANGKIYEOK BA4F D29F # HANGUL SYLLABLE THIEUTH-YU-KIYEOKSIOS BA50 D2A1 # HANGUL SYLLABLE THIEUTH-YU-NIEUNCIEUC BA51 D2A2 # HANGUL SYLLABLE THIEUTH-YU-NIEUNHIEUH BA52 D2A3 # HANGUL SYLLABLE THIEUTH-YU-TIKEUT BA53 D2A5 # HANGUL SYLLABLE THIEUTH-YU-RIEULKIYEOK BA54 D2A6 # HANGUL SYLLABLE THIEUTH-YU-RIEULMIEUM BA55 D2A7 # HANGUL SYLLABLE THIEUTH-YU-RIEULPIEUP BA56 D2A8 # HANGUL SYLLABLE THIEUTH-YU-RIEULSIOS BA57 D2A9 # HANGUL SYLLABLE THIEUTH-YU-RIEULTHIEUTH BA58 D2AA # HANGUL SYLLABLE THIEUTH-YU-RIEULPHIEUPH BA59 D2AB # HANGUL SYLLABLE THIEUTH-YU-RIEULHIEUH BA5A D2AD # HANGUL SYLLABLE THIEUTH-YU-PIEUP BA61 D2AE # HANGUL SYLLABLE THIEUTH-YU-PIEUPSIOS BA62 D2AF # HANGUL SYLLABLE THIEUTH-YU-SIOS BA63 D2B0 # HANGUL SYLLABLE THIEUTH-YU-SSANGSIOS BA64 D2B2 # HANGUL SYLLABLE THIEUTH-YU-CIEUC BA65 D2B3 # HANGUL SYLLABLE THIEUTH-YU-CHIEUCH BA66 D2B4 # HANGUL SYLLABLE THIEUTH-YU-KHIEUKH BA67 D2B5 # HANGUL SYLLABLE THIEUTH-YU-THIEUTH BA68 D2B6 # HANGUL SYLLABLE THIEUTH-YU-PHIEUPH BA69 D2B7 # HANGUL SYLLABLE THIEUTH-YU-HIEUH BA6A D2BA # HANGUL SYLLABLE THIEUTH-EU-SSANGKIYEOK BA6B D2BB # HANGUL SYLLABLE THIEUTH-EU-KIYEOKSIOS BA6C D2BD # HANGUL SYLLABLE THIEUTH-EU-NIEUNCIEUC BA6D D2BE # HANGUL SYLLABLE THIEUTH-EU-NIEUNHIEUH BA6E D2C1 # HANGUL SYLLABLE THIEUTH-EU-RIEULKIYEOK BA6F D2C3 # HANGUL SYLLABLE THIEUTH-EU-RIEULPIEUP BA70 D2C4 # HANGUL SYLLABLE THIEUTH-EU-RIEULSIOS BA71 D2C5 # HANGUL SYLLABLE THIEUTH-EU-RIEULTHIEUTH BA72 D2C6 # HANGUL SYLLABLE THIEUTH-EU-RIEULPHIEUPH BA73 D2C7 # HANGUL SYLLABLE THIEUTH-EU-RIEULHIEUH BA74 D2CA # HANGUL SYLLABLE THIEUTH-EU-PIEUPSIOS BA75 D2CC # HANGUL SYLLABLE THIEUTH-EU-SSANGSIOS BA76 D2CD # HANGUL SYLLABLE THIEUTH-EU-IEUNG BA77 D2CE # HANGUL SYLLABLE THIEUTH-EU-CIEUC BA78 D2CF # HANGUL SYLLABLE THIEUTH-EU-CHIEUCH BA79 D2D0 # HANGUL SYLLABLE THIEUTH-EU-KHIEUKH BA7A D2D1 # HANGUL SYLLABLE THIEUTH-EU-THIEUTH BA81 D2D2 # HANGUL SYLLABLE THIEUTH-EU-PHIEUPH BA82 D2D3 # HANGUL SYLLABLE THIEUTH-EU-HIEUH BA83 D2D5 # HANGUL SYLLABLE THIEUTH-YI-KIYEOK BA84 D2D6 # HANGUL SYLLABLE THIEUTH-YI-SSANGKIYEOK BA85 D2D7 # HANGUL SYLLABLE THIEUTH-YI-KIYEOKSIOS BA86 D2D9 # HANGUL SYLLABLE THIEUTH-YI-NIEUNCIEUC BA87 D2DA # HANGUL SYLLABLE THIEUTH-YI-NIEUNHIEUH BA88 D2DB # HANGUL SYLLABLE THIEUTH-YI-TIKEUT BA89 D2DD # HANGUL SYLLABLE THIEUTH-YI-RIEULKIYEOK BA8A D2DE # HANGUL SYLLABLE THIEUTH-YI-RIEULMIEUM BA8B D2DF # HANGUL SYLLABLE THIEUTH-YI-RIEULPIEUP BA8C D2E0 # HANGUL SYLLABLE THIEUTH-YI-RIEULSIOS BA8D D2E1 # HANGUL SYLLABLE THIEUTH-YI-RIEULTHIEUTH BA8E D2E2 # HANGUL SYLLABLE THIEUTH-YI-RIEULPHIEUPH BA8F D2E3 # HANGUL SYLLABLE THIEUTH-YI-RIEULHIEUH BA90 D2E6 # HANGUL SYLLABLE THIEUTH-YI-PIEUPSIOS BA91 D2E7 # HANGUL SYLLABLE THIEUTH-YI-SIOS BA92 D2E8 # HANGUL SYLLABLE THIEUTH-YI-SSANGSIOS BA93 D2E9 # HANGUL SYLLABLE THIEUTH-YI-IEUNG BA94 D2EA # HANGUL SYLLABLE THIEUTH-YI-CIEUC BA95 D2EB # HANGUL SYLLABLE THIEUTH-YI-CHIEUCH BA96 D2EC # HANGUL SYLLABLE THIEUTH-YI-KHIEUKH BA97 D2ED # HANGUL SYLLABLE THIEUTH-YI-THIEUTH BA98 D2EE # HANGUL SYLLABLE THIEUTH-YI-PHIEUPH BA99 D2EF # HANGUL SYLLABLE THIEUTH-YI-HIEUH BA9A D2F2 # HANGUL SYLLABLE THIEUTH-I-SSANGKIYEOK BA9B D2F3 # HANGUL SYLLABLE THIEUTH-I-KIYEOKSIOS BA9C D2F5 # HANGUL SYLLABLE THIEUTH-I-NIEUNCIEUC BA9D D2F6 # HANGUL SYLLABLE THIEUTH-I-NIEUNHIEUH BA9E D2F7 # HANGUL SYLLABLE THIEUTH-I-TIKEUT BA9F D2F9 # HANGUL SYLLABLE THIEUTH-I-RIEULKIYEOK BAA0 D2FA # HANGUL SYLLABLE THIEUTH-I-RIEULMIEUM BAA1 BC99 # HANGUL SYLLABLE PIEUP-EO-IEUNG BAA2 BC9A # HANGUL SYLLABLE PIEUP-EO-CIEUC BAA3 BCA0 # HANGUL SYLLABLE PIEUP-E BAA4 BCA1 # HANGUL SYLLABLE PIEUP-E-KIYEOK BAA5 BCA4 # HANGUL SYLLABLE PIEUP-E-NIEUN BAA6 BCA7 # HANGUL SYLLABLE PIEUP-E-TIKEUT BAA7 BCA8 # HANGUL SYLLABLE PIEUP-E-RIEUL BAA8 BCB0 # HANGUL SYLLABLE PIEUP-E-MIEUM BAA9 BCB1 # HANGUL SYLLABLE PIEUP-E-PIEUP BAAA BCB3 # HANGUL SYLLABLE PIEUP-E-SIOS BAAB BCB4 # HANGUL SYLLABLE PIEUP-E-SSANGSIOS BAAC BCB5 # HANGUL SYLLABLE PIEUP-E-IEUNG BAAD BCBC # HANGUL SYLLABLE PIEUP-YEO BAAE BCBD # HANGUL SYLLABLE PIEUP-YEO-KIYEOK BAAF BCC0 # HANGUL SYLLABLE PIEUP-YEO-NIEUN BAB0 BCC4 # HANGUL SYLLABLE PIEUP-YEO-RIEUL BAB1 BCCD # HANGUL SYLLABLE PIEUP-YEO-PIEUP BAB2 BCCF # HANGUL SYLLABLE PIEUP-YEO-SIOS BAB3 BCD0 # HANGUL SYLLABLE PIEUP-YEO-SSANGSIOS BAB4 BCD1 # HANGUL SYLLABLE PIEUP-YEO-IEUNG BAB5 BCD5 # HANGUL SYLLABLE PIEUP-YEO-THIEUTH BAB6 BCD8 # HANGUL SYLLABLE PIEUP-YE BAB7 BCDC # HANGUL SYLLABLE PIEUP-YE-NIEUN BAB8 BCF4 # HANGUL SYLLABLE PIEUP-O BAB9 BCF5 # HANGUL SYLLABLE PIEUP-O-KIYEOK BABA BCF6 # HANGUL SYLLABLE PIEUP-O-SSANGKIYEOK BABB BCF8 # HANGUL SYLLABLE PIEUP-O-NIEUN BABC BCFC # HANGUL SYLLABLE PIEUP-O-RIEUL BABD BD04 # HANGUL SYLLABLE PIEUP-O-MIEUM BABE BD05 # HANGUL SYLLABLE PIEUP-O-PIEUP BABF BD07 # HANGUL SYLLABLE PIEUP-O-SIOS BAC0 BD09 # HANGUL SYLLABLE PIEUP-O-IEUNG BAC1 BD10 # HANGUL SYLLABLE PIEUP-WA BAC2 BD14 # HANGUL SYLLABLE PIEUP-WA-NIEUN BAC3 BD24 # HANGUL SYLLABLE PIEUP-WA-SSANGSIOS BAC4 BD2C # HANGUL SYLLABLE PIEUP-WAE BAC5 BD40 # HANGUL SYLLABLE PIEUP-WAE-SSANGSIOS BAC6 BD48 # HANGUL SYLLABLE PIEUP-OE BAC7 BD49 # HANGUL SYLLABLE PIEUP-OE-KIYEOK BAC8 BD4C # HANGUL SYLLABLE PIEUP-OE-NIEUN BAC9 BD50 # HANGUL SYLLABLE PIEUP-OE-RIEUL BACA BD58 # HANGUL SYLLABLE PIEUP-OE-MIEUM BACB BD59 # HANGUL SYLLABLE PIEUP-OE-PIEUP BACC BD64 # HANGUL SYLLABLE PIEUP-YO BACD BD68 # HANGUL SYLLABLE PIEUP-YO-NIEUN BACE BD80 # HANGUL SYLLABLE PIEUP-U BACF BD81 # HANGUL SYLLABLE PIEUP-U-KIYEOK BAD0 BD84 # HANGUL SYLLABLE PIEUP-U-NIEUN BAD1 BD87 # HANGUL SYLLABLE PIEUP-U-TIKEUT BAD2 BD88 # HANGUL SYLLABLE PIEUP-U-RIEUL BAD3 BD89 # HANGUL SYLLABLE PIEUP-U-RIEULKIYEOK BAD4 BD8A # HANGUL SYLLABLE PIEUP-U-RIEULMIEUM BAD5 BD90 # HANGUL SYLLABLE PIEUP-U-MIEUM BAD6 BD91 # HANGUL SYLLABLE PIEUP-U-PIEUP BAD7 BD93 # HANGUL SYLLABLE PIEUP-U-SIOS BAD8 BD95 # HANGUL SYLLABLE PIEUP-U-IEUNG BAD9 BD99 # HANGUL SYLLABLE PIEUP-U-THIEUTH BADA BD9A # HANGUL SYLLABLE PIEUP-U-PHIEUPH BADB BD9C # HANGUL SYLLABLE PIEUP-WEO BADC BDA4 # HANGUL SYLLABLE PIEUP-WEO-RIEUL BADD BDB0 # HANGUL SYLLABLE PIEUP-WEO-SSANGSIOS BADE BDB8 # HANGUL SYLLABLE PIEUP-WE BADF BDD4 # HANGUL SYLLABLE PIEUP-WI BAE0 BDD5 # HANGUL SYLLABLE PIEUP-WI-KIYEOK BAE1 BDD8 # HANGUL SYLLABLE PIEUP-WI-NIEUN BAE2 BDDC # HANGUL SYLLABLE PIEUP-WI-RIEUL BAE3 BDE9 # HANGUL SYLLABLE PIEUP-WI-IEUNG BAE4 BDF0 # HANGUL SYLLABLE PIEUP-YU BAE5 BDF4 # HANGUL SYLLABLE PIEUP-YU-NIEUN BAE6 BDF8 # HANGUL SYLLABLE PIEUP-YU-RIEUL BAE7 BE00 # HANGUL SYLLABLE PIEUP-YU-MIEUM BAE8 BE03 # HANGUL SYLLABLE PIEUP-YU-SIOS BAE9 BE05 # HANGUL SYLLABLE PIEUP-YU-IEUNG BAEA BE0C # HANGUL SYLLABLE PIEUP-EU BAEB BE0D # HANGUL SYLLABLE PIEUP-EU-KIYEOK BAEC BE10 # HANGUL SYLLABLE PIEUP-EU-NIEUN BAED BE14 # HANGUL SYLLABLE PIEUP-EU-RIEUL BAEE BE1C # HANGUL SYLLABLE PIEUP-EU-MIEUM BAEF BE1D # HANGUL SYLLABLE PIEUP-EU-PIEUP BAF0 BE1F # HANGUL SYLLABLE PIEUP-EU-SIOS BAF1 BE44 # HANGUL SYLLABLE PIEUP-I BAF2 BE45 # HANGUL SYLLABLE PIEUP-I-KIYEOK BAF3 BE48 # HANGUL SYLLABLE PIEUP-I-NIEUN BAF4 BE4C # HANGUL SYLLABLE PIEUP-I-RIEUL BAF5 BE4E # HANGUL SYLLABLE PIEUP-I-RIEULMIEUM BAF6 BE54 # HANGUL SYLLABLE PIEUP-I-MIEUM BAF7 BE55 # HANGUL SYLLABLE PIEUP-I-PIEUP BAF8 BE57 # HANGUL SYLLABLE PIEUP-I-SIOS BAF9 BE59 # HANGUL SYLLABLE PIEUP-I-IEUNG BAFA BE5A # HANGUL SYLLABLE PIEUP-I-CIEUC BAFB BE5B # HANGUL SYLLABLE PIEUP-I-CHIEUCH BAFC BE60 # HANGUL SYLLABLE SSANGPIEUP-A BAFD BE61 # HANGUL SYLLABLE SSANGPIEUP-A-KIYEOK BAFE BE64 # HANGUL SYLLABLE SSANGPIEUP-A-NIEUN BB41 D2FB # HANGUL SYLLABLE THIEUTH-I-RIEULPIEUP BB42 D2FC # HANGUL SYLLABLE THIEUTH-I-RIEULSIOS BB43 D2FD # HANGUL SYLLABLE THIEUTH-I-RIEULTHIEUTH BB44 D2FE # HANGUL SYLLABLE THIEUTH-I-RIEULPHIEUPH BB45 D2FF # HANGUL SYLLABLE THIEUTH-I-RIEULHIEUH BB46 D302 # HANGUL SYLLABLE THIEUTH-I-PIEUPSIOS BB47 D304 # HANGUL SYLLABLE THIEUTH-I-SSANGSIOS BB48 D306 # HANGUL SYLLABLE THIEUTH-I-CIEUC BB49 D307 # HANGUL SYLLABLE THIEUTH-I-CHIEUCH BB4A D308 # HANGUL SYLLABLE THIEUTH-I-KHIEUKH BB4B D309 # HANGUL SYLLABLE THIEUTH-I-THIEUTH BB4C D30A # HANGUL SYLLABLE THIEUTH-I-PHIEUPH BB4D D30B # HANGUL SYLLABLE THIEUTH-I-HIEUH BB4E D30F # HANGUL SYLLABLE PHIEUPH-A-KIYEOKSIOS BB4F D311 # HANGUL SYLLABLE PHIEUPH-A-NIEUNCIEUC BB50 D312 # HANGUL SYLLABLE PHIEUPH-A-NIEUNHIEUH BB51 D313 # HANGUL SYLLABLE PHIEUPH-A-TIKEUT BB52 D315 # HANGUL SYLLABLE PHIEUPH-A-RIEULKIYEOK BB53 D317 # HANGUL SYLLABLE PHIEUPH-A-RIEULPIEUP BB54 D318 # HANGUL SYLLABLE PHIEUPH-A-RIEULSIOS BB55 D319 # HANGUL SYLLABLE PHIEUPH-A-RIEULTHIEUTH BB56 D31A # HANGUL SYLLABLE PHIEUPH-A-RIEULPHIEUPH BB57 D31B # HANGUL SYLLABLE PHIEUPH-A-RIEULHIEUH BB58 D31E # HANGUL SYLLABLE PHIEUPH-A-PIEUPSIOS BB59 D322 # HANGUL SYLLABLE PHIEUPH-A-CIEUC BB5A D323 # HANGUL SYLLABLE PHIEUPH-A-CHIEUCH BB61 D324 # HANGUL SYLLABLE PHIEUPH-A-KHIEUKH BB62 D326 # HANGUL SYLLABLE PHIEUPH-A-PHIEUPH BB63 D327 # HANGUL SYLLABLE PHIEUPH-A-HIEUH BB64 D32A # HANGUL SYLLABLE PHIEUPH-AE-SSANGKIYEOK BB65 D32B # HANGUL SYLLABLE PHIEUPH-AE-KIYEOKSIOS BB66 D32D # HANGUL SYLLABLE PHIEUPH-AE-NIEUNCIEUC BB67 D32E # HANGUL SYLLABLE PHIEUPH-AE-NIEUNHIEUH BB68 D32F # HANGUL SYLLABLE PHIEUPH-AE-TIKEUT BB69 D331 # HANGUL SYLLABLE PHIEUPH-AE-RIEULKIYEOK BB6A D332 # HANGUL SYLLABLE PHIEUPH-AE-RIEULMIEUM BB6B D333 # HANGUL SYLLABLE PHIEUPH-AE-RIEULPIEUP BB6C D334 # HANGUL SYLLABLE PHIEUPH-AE-RIEULSIOS BB6D D335 # HANGUL SYLLABLE PHIEUPH-AE-RIEULTHIEUTH BB6E D336 # HANGUL SYLLABLE PHIEUPH-AE-RIEULPHIEUPH BB6F D337 # HANGUL SYLLABLE PHIEUPH-AE-RIEULHIEUH BB70 D33A # HANGUL SYLLABLE PHIEUPH-AE-PIEUPSIOS BB71 D33E # HANGUL SYLLABLE PHIEUPH-AE-CIEUC BB72 D33F # HANGUL SYLLABLE PHIEUPH-AE-CHIEUCH BB73 D340 # HANGUL SYLLABLE PHIEUPH-AE-KHIEUKH BB74 D341 # HANGUL SYLLABLE PHIEUPH-AE-THIEUTH BB75 D342 # HANGUL SYLLABLE PHIEUPH-AE-PHIEUPH BB76 D343 # HANGUL SYLLABLE PHIEUPH-AE-HIEUH BB77 D346 # HANGUL SYLLABLE PHIEUPH-YA-SSANGKIYEOK BB78 D347 # HANGUL SYLLABLE PHIEUPH-YA-KIYEOKSIOS BB79 D348 # HANGUL SYLLABLE PHIEUPH-YA-NIEUN BB7A D349 # HANGUL SYLLABLE PHIEUPH-YA-NIEUNCIEUC BB81 D34A # HANGUL SYLLABLE PHIEUPH-YA-NIEUNHIEUH BB82 D34B # HANGUL SYLLABLE PHIEUPH-YA-TIKEUT BB83 D34C # HANGUL SYLLABLE PHIEUPH-YA-RIEUL BB84 D34D # HANGUL SYLLABLE PHIEUPH-YA-RIEULKIYEOK BB85 D34E # HANGUL SYLLABLE PHIEUPH-YA-RIEULMIEUM BB86 D34F # HANGUL SYLLABLE PHIEUPH-YA-RIEULPIEUP BB87 D350 # HANGUL SYLLABLE PHIEUPH-YA-RIEULSIOS BB88 D351 # HANGUL SYLLABLE PHIEUPH-YA-RIEULTHIEUTH BB89 D352 # HANGUL SYLLABLE PHIEUPH-YA-RIEULPHIEUPH BB8A D353 # HANGUL SYLLABLE PHIEUPH-YA-RIEULHIEUH BB8B D354 # HANGUL SYLLABLE PHIEUPH-YA-MIEUM BB8C D355 # HANGUL SYLLABLE PHIEUPH-YA-PIEUP BB8D D356 # HANGUL SYLLABLE PHIEUPH-YA-PIEUPSIOS BB8E D357 # HANGUL SYLLABLE PHIEUPH-YA-SIOS BB8F D358 # HANGUL SYLLABLE PHIEUPH-YA-SSANGSIOS BB90 D359 # HANGUL SYLLABLE PHIEUPH-YA-IEUNG BB91 D35A # HANGUL SYLLABLE PHIEUPH-YA-CIEUC BB92 D35B # HANGUL SYLLABLE PHIEUPH-YA-CHIEUCH BB93 D35C # HANGUL SYLLABLE PHIEUPH-YA-KHIEUKH BB94 D35D # HANGUL SYLLABLE PHIEUPH-YA-THIEUTH BB95 D35E # HANGUL SYLLABLE PHIEUPH-YA-PHIEUPH BB96 D35F # HANGUL SYLLABLE PHIEUPH-YA-HIEUH BB97 D360 # HANGUL SYLLABLE PHIEUPH-YAE BB98 D361 # HANGUL SYLLABLE PHIEUPH-YAE-KIYEOK BB99 D362 # HANGUL SYLLABLE PHIEUPH-YAE-SSANGKIYEOK BB9A D363 # HANGUL SYLLABLE PHIEUPH-YAE-KIYEOKSIOS BB9B D364 # HANGUL SYLLABLE PHIEUPH-YAE-NIEUN BB9C D365 # HANGUL SYLLABLE PHIEUPH-YAE-NIEUNCIEUC BB9D D366 # HANGUL SYLLABLE PHIEUPH-YAE-NIEUNHIEUH BB9E D367 # HANGUL SYLLABLE PHIEUPH-YAE-TIKEUT BB9F D368 # HANGUL SYLLABLE PHIEUPH-YAE-RIEUL BBA0 D369 # HANGUL SYLLABLE PHIEUPH-YAE-RIEULKIYEOK BBA1 BE68 # HANGUL SYLLABLE SSANGPIEUP-A-RIEUL BBA2 BE6A # HANGUL SYLLABLE SSANGPIEUP-A-RIEULMIEUM BBA3 BE70 # HANGUL SYLLABLE SSANGPIEUP-A-MIEUM BBA4 BE71 # HANGUL SYLLABLE SSANGPIEUP-A-PIEUP BBA5 BE73 # HANGUL SYLLABLE SSANGPIEUP-A-SIOS BBA6 BE74 # HANGUL SYLLABLE SSANGPIEUP-A-SSANGSIOS BBA7 BE75 # HANGUL SYLLABLE SSANGPIEUP-A-IEUNG BBA8 BE7B # HANGUL SYLLABLE SSANGPIEUP-A-HIEUH BBA9 BE7C # HANGUL SYLLABLE SSANGPIEUP-AE BBAA BE7D # HANGUL SYLLABLE SSANGPIEUP-AE-KIYEOK BBAB BE80 # HANGUL SYLLABLE SSANGPIEUP-AE-NIEUN BBAC BE84 # HANGUL SYLLABLE SSANGPIEUP-AE-RIEUL BBAD BE8C # HANGUL SYLLABLE SSANGPIEUP-AE-MIEUM BBAE BE8D # HANGUL SYLLABLE SSANGPIEUP-AE-PIEUP BBAF BE8F # HANGUL SYLLABLE SSANGPIEUP-AE-SIOS BBB0 BE90 # HANGUL SYLLABLE SSANGPIEUP-AE-SSANGSIOS BBB1 BE91 # HANGUL SYLLABLE SSANGPIEUP-AE-IEUNG BBB2 BE98 # HANGUL SYLLABLE SSANGPIEUP-YA BBB3 BE99 # HANGUL SYLLABLE SSANGPIEUP-YA-KIYEOK BBB4 BEA8 # HANGUL SYLLABLE SSANGPIEUP-YA-MIEUM BBB5 BED0 # HANGUL SYLLABLE SSANGPIEUP-EO BBB6 BED1 # HANGUL SYLLABLE SSANGPIEUP-EO-KIYEOK BBB7 BED4 # HANGUL SYLLABLE SSANGPIEUP-EO-NIEUN BBB8 BED7 # HANGUL SYLLABLE SSANGPIEUP-EO-TIKEUT BBB9 BED8 # HANGUL SYLLABLE SSANGPIEUP-EO-RIEUL BBBA BEE0 # HANGUL SYLLABLE SSANGPIEUP-EO-MIEUM BBBB BEE3 # HANGUL SYLLABLE SSANGPIEUP-EO-SIOS BBBC BEE4 # HANGUL SYLLABLE SSANGPIEUP-EO-SSANGSIOS BBBD BEE5 # HANGUL SYLLABLE SSANGPIEUP-EO-IEUNG BBBE BEEC # HANGUL SYLLABLE SSANGPIEUP-E BBBF BF01 # HANGUL SYLLABLE SSANGPIEUP-E-IEUNG BBC0 BF08 # HANGUL SYLLABLE SSANGPIEUP-YEO BBC1 BF09 # HANGUL SYLLABLE SSANGPIEUP-YEO-KIYEOK BBC2 BF18 # HANGUL SYLLABLE SSANGPIEUP-YEO-MIEUM BBC3 BF19 # HANGUL SYLLABLE SSANGPIEUP-YEO-PIEUP BBC4 BF1B # HANGUL SYLLABLE SSANGPIEUP-YEO-SIOS BBC5 BF1C # HANGUL SYLLABLE SSANGPIEUP-YEO-SSANGSIOS BBC6 BF1D # HANGUL SYLLABLE SSANGPIEUP-YEO-IEUNG BBC7 BF40 # HANGUL SYLLABLE SSANGPIEUP-O BBC8 BF41 # HANGUL SYLLABLE SSANGPIEUP-O-KIYEOK BBC9 BF44 # HANGUL SYLLABLE SSANGPIEUP-O-NIEUN BBCA BF48 # HANGUL SYLLABLE SSANGPIEUP-O-RIEUL BBCB BF50 # HANGUL SYLLABLE SSANGPIEUP-O-MIEUM BBCC BF51 # HANGUL SYLLABLE SSANGPIEUP-O-PIEUP BBCD BF55 # HANGUL SYLLABLE SSANGPIEUP-O-IEUNG BBCE BF94 # HANGUL SYLLABLE SSANGPIEUP-OE BBCF BFB0 # HANGUL SYLLABLE SSANGPIEUP-YO BBD0 BFC5 # HANGUL SYLLABLE SSANGPIEUP-YO-IEUNG BBD1 BFCC # HANGUL SYLLABLE SSANGPIEUP-U BBD2 BFCD # HANGUL SYLLABLE SSANGPIEUP-U-KIYEOK BBD3 BFD0 # HANGUL SYLLABLE SSANGPIEUP-U-NIEUN BBD4 BFD4 # HANGUL SYLLABLE SSANGPIEUP-U-RIEUL BBD5 BFDC # HANGUL SYLLABLE SSANGPIEUP-U-MIEUM BBD6 BFDF # HANGUL SYLLABLE SSANGPIEUP-U-SIOS BBD7 BFE1 # HANGUL SYLLABLE SSANGPIEUP-U-IEUNG BBD8 C03C # HANGUL SYLLABLE SSANGPIEUP-YU BBD9 C051 # HANGUL SYLLABLE SSANGPIEUP-YU-IEUNG BBDA C058 # HANGUL SYLLABLE SSANGPIEUP-EU BBDB C05C # HANGUL SYLLABLE SSANGPIEUP-EU-NIEUN BBDC C060 # HANGUL SYLLABLE SSANGPIEUP-EU-RIEUL BBDD C068 # HANGUL SYLLABLE SSANGPIEUP-EU-MIEUM BBDE C069 # HANGUL SYLLABLE SSANGPIEUP-EU-PIEUP BBDF C090 # HANGUL SYLLABLE SSANGPIEUP-I BBE0 C091 # HANGUL SYLLABLE SSANGPIEUP-I-KIYEOK BBE1 C094 # HANGUL SYLLABLE SSANGPIEUP-I-NIEUN BBE2 C098 # HANGUL SYLLABLE SSANGPIEUP-I-RIEUL BBE3 C0A0 # HANGUL SYLLABLE SSANGPIEUP-I-MIEUM BBE4 C0A1 # HANGUL SYLLABLE SSANGPIEUP-I-PIEUP BBE5 C0A3 # HANGUL SYLLABLE SSANGPIEUP-I-SIOS BBE6 C0A5 # HANGUL SYLLABLE SSANGPIEUP-I-IEUNG BBE7 C0AC # HANGUL SYLLABLE SIOS-A BBE8 C0AD # HANGUL SYLLABLE SIOS-A-KIYEOK BBE9 C0AF # HANGUL SYLLABLE SIOS-A-KIYEOKSIOS BBEA C0B0 # HANGUL SYLLABLE SIOS-A-NIEUN BBEB C0B3 # HANGUL SYLLABLE SIOS-A-TIKEUT BBEC C0B4 # HANGUL SYLLABLE SIOS-A-RIEUL BBED C0B5 # HANGUL SYLLABLE SIOS-A-RIEULKIYEOK BBEE C0B6 # HANGUL SYLLABLE SIOS-A-RIEULMIEUM BBEF C0BC # HANGUL SYLLABLE SIOS-A-MIEUM BBF0 C0BD # HANGUL SYLLABLE SIOS-A-PIEUP BBF1 C0BF # HANGUL SYLLABLE SIOS-A-SIOS BBF2 C0C0 # HANGUL SYLLABLE SIOS-A-SSANGSIOS BBF3 C0C1 # HANGUL SYLLABLE SIOS-A-IEUNG BBF4 C0C5 # HANGUL SYLLABLE SIOS-A-THIEUTH BBF5 C0C8 # HANGUL SYLLABLE SIOS-AE BBF6 C0C9 # HANGUL SYLLABLE SIOS-AE-KIYEOK BBF7 C0CC # HANGUL SYLLABLE SIOS-AE-NIEUN BBF8 C0D0 # HANGUL SYLLABLE SIOS-AE-RIEUL BBF9 C0D8 # HANGUL SYLLABLE SIOS-AE-MIEUM BBFA C0D9 # HANGUL SYLLABLE SIOS-AE-PIEUP BBFB C0DB # HANGUL SYLLABLE SIOS-AE-SIOS BBFC C0DC # HANGUL SYLLABLE SIOS-AE-SSANGSIOS BBFD C0DD # HANGUL SYLLABLE SIOS-AE-IEUNG BBFE C0E4 # HANGUL SYLLABLE SIOS-YA BC41 D36A # HANGUL SYLLABLE PHIEUPH-YAE-RIEULMIEUM BC42 D36B # HANGUL SYLLABLE PHIEUPH-YAE-RIEULPIEUP BC43 D36C # HANGUL SYLLABLE PHIEUPH-YAE-RIEULSIOS BC44 D36D # HANGUL SYLLABLE PHIEUPH-YAE-RIEULTHIEUTH BC45 D36E # HANGUL SYLLABLE PHIEUPH-YAE-RIEULPHIEUPH BC46 D36F # HANGUL SYLLABLE PHIEUPH-YAE-RIEULHIEUH BC47 D370 # HANGUL SYLLABLE PHIEUPH-YAE-MIEUM BC48 D371 # HANGUL SYLLABLE PHIEUPH-YAE-PIEUP BC49 D372 # HANGUL SYLLABLE PHIEUPH-YAE-PIEUPSIOS BC4A D373 # HANGUL SYLLABLE PHIEUPH-YAE-SIOS BC4B D374 # HANGUL SYLLABLE PHIEUPH-YAE-SSANGSIOS BC4C D375 # HANGUL SYLLABLE PHIEUPH-YAE-IEUNG BC4D D376 # HANGUL SYLLABLE PHIEUPH-YAE-CIEUC BC4E D377 # HANGUL SYLLABLE PHIEUPH-YAE-CHIEUCH BC4F D378 # HANGUL SYLLABLE PHIEUPH-YAE-KHIEUKH BC50 D379 # HANGUL SYLLABLE PHIEUPH-YAE-THIEUTH BC51 D37A # HANGUL SYLLABLE PHIEUPH-YAE-PHIEUPH BC52 D37B # HANGUL SYLLABLE PHIEUPH-YAE-HIEUH BC53 D37E # HANGUL SYLLABLE PHIEUPH-EO-SSANGKIYEOK BC54 D37F # HANGUL SYLLABLE PHIEUPH-EO-KIYEOKSIOS BC55 D381 # HANGUL SYLLABLE PHIEUPH-EO-NIEUNCIEUC BC56 D382 # HANGUL SYLLABLE PHIEUPH-EO-NIEUNHIEUH BC57 D383 # HANGUL SYLLABLE PHIEUPH-EO-TIKEUT BC58 D385 # HANGUL SYLLABLE PHIEUPH-EO-RIEULKIYEOK BC59 D386 # HANGUL SYLLABLE PHIEUPH-EO-RIEULMIEUM BC5A D387 # HANGUL SYLLABLE PHIEUPH-EO-RIEULPIEUP BC61 D388 # HANGUL SYLLABLE PHIEUPH-EO-RIEULSIOS BC62 D389 # HANGUL SYLLABLE PHIEUPH-EO-RIEULTHIEUTH BC63 D38A # HANGUL SYLLABLE PHIEUPH-EO-RIEULPHIEUPH BC64 D38B # HANGUL SYLLABLE PHIEUPH-EO-RIEULHIEUH BC65 D38E # HANGUL SYLLABLE PHIEUPH-EO-PIEUPSIOS BC66 D392 # HANGUL SYLLABLE PHIEUPH-EO-CIEUC BC67 D393 # HANGUL SYLLABLE PHIEUPH-EO-CHIEUCH BC68 D394 # HANGUL SYLLABLE PHIEUPH-EO-KHIEUKH BC69 D395 # HANGUL SYLLABLE PHIEUPH-EO-THIEUTH BC6A D396 # HANGUL SYLLABLE PHIEUPH-EO-PHIEUPH BC6B D397 # HANGUL SYLLABLE PHIEUPH-EO-HIEUH BC6C D39A # HANGUL SYLLABLE PHIEUPH-E-SSANGKIYEOK BC6D D39B # HANGUL SYLLABLE PHIEUPH-E-KIYEOKSIOS BC6E D39D # HANGUL SYLLABLE PHIEUPH-E-NIEUNCIEUC BC6F D39E # HANGUL SYLLABLE PHIEUPH-E-NIEUNHIEUH BC70 D39F # HANGUL SYLLABLE PHIEUPH-E-TIKEUT BC71 D3A1 # HANGUL SYLLABLE PHIEUPH-E-RIEULKIYEOK BC72 D3A2 # HANGUL SYLLABLE PHIEUPH-E-RIEULMIEUM BC73 D3A3 # HANGUL SYLLABLE PHIEUPH-E-RIEULPIEUP BC74 D3A4 # HANGUL SYLLABLE PHIEUPH-E-RIEULSIOS BC75 D3A5 # HANGUL SYLLABLE PHIEUPH-E-RIEULTHIEUTH BC76 D3A6 # HANGUL SYLLABLE PHIEUPH-E-RIEULPHIEUPH BC77 D3A7 # HANGUL SYLLABLE PHIEUPH-E-RIEULHIEUH BC78 D3AA # HANGUL SYLLABLE PHIEUPH-E-PIEUPSIOS BC79 D3AC # HANGUL SYLLABLE PHIEUPH-E-SSANGSIOS BC7A D3AE # HANGUL SYLLABLE PHIEUPH-E-CIEUC BC81 D3AF # HANGUL SYLLABLE PHIEUPH-E-CHIEUCH BC82 D3B0 # HANGUL SYLLABLE PHIEUPH-E-KHIEUKH BC83 D3B1 # HANGUL SYLLABLE PHIEUPH-E-THIEUTH BC84 D3B2 # HANGUL SYLLABLE PHIEUPH-E-PHIEUPH BC85 D3B3 # HANGUL SYLLABLE PHIEUPH-E-HIEUH BC86 D3B5 # HANGUL SYLLABLE PHIEUPH-YEO-KIYEOK BC87 D3B6 # HANGUL SYLLABLE PHIEUPH-YEO-SSANGKIYEOK BC88 D3B7 # HANGUL SYLLABLE PHIEUPH-YEO-KIYEOKSIOS BC89 D3B9 # HANGUL SYLLABLE PHIEUPH-YEO-NIEUNCIEUC BC8A D3BA # HANGUL SYLLABLE PHIEUPH-YEO-NIEUNHIEUH BC8B D3BB # HANGUL SYLLABLE PHIEUPH-YEO-TIKEUT BC8C D3BD # HANGUL SYLLABLE PHIEUPH-YEO-RIEULKIYEOK BC8D D3BE # HANGUL SYLLABLE PHIEUPH-YEO-RIEULMIEUM BC8E D3BF # HANGUL SYLLABLE PHIEUPH-YEO-RIEULPIEUP BC8F D3C0 # HANGUL SYLLABLE PHIEUPH-YEO-RIEULSIOS BC90 D3C1 # HANGUL SYLLABLE PHIEUPH-YEO-RIEULTHIEUTH BC91 D3C2 # HANGUL SYLLABLE PHIEUPH-YEO-RIEULPHIEUPH BC92 D3C3 # HANGUL SYLLABLE PHIEUPH-YEO-RIEULHIEUH BC93 D3C6 # HANGUL SYLLABLE PHIEUPH-YEO-PIEUPSIOS BC94 D3C7 # HANGUL SYLLABLE PHIEUPH-YEO-SIOS BC95 D3CA # HANGUL SYLLABLE PHIEUPH-YEO-CIEUC BC96 D3CB # HANGUL SYLLABLE PHIEUPH-YEO-CHIEUCH BC97 D3CC # HANGUL SYLLABLE PHIEUPH-YEO-KHIEUKH BC98 D3CD # HANGUL SYLLABLE PHIEUPH-YEO-THIEUTH BC99 D3CE # HANGUL SYLLABLE PHIEUPH-YEO-PHIEUPH BC9A D3CF # HANGUL SYLLABLE PHIEUPH-YEO-HIEUH BC9B D3D1 # HANGUL SYLLABLE PHIEUPH-YE-KIYEOK BC9C D3D2 # HANGUL SYLLABLE PHIEUPH-YE-SSANGKIYEOK BC9D D3D3 # HANGUL SYLLABLE PHIEUPH-YE-KIYEOKSIOS BC9E D3D4 # HANGUL SYLLABLE PHIEUPH-YE-NIEUN BC9F D3D5 # HANGUL SYLLABLE PHIEUPH-YE-NIEUNCIEUC BCA0 D3D6 # HANGUL SYLLABLE PHIEUPH-YE-NIEUNHIEUH BCA1 C0E5 # HANGUL SYLLABLE SIOS-YA-KIYEOK BCA2 C0E8 # HANGUL SYLLABLE SIOS-YA-NIEUN BCA3 C0EC # HANGUL SYLLABLE SIOS-YA-RIEUL BCA4 C0F4 # HANGUL SYLLABLE SIOS-YA-MIEUM BCA5 C0F5 # HANGUL SYLLABLE SIOS-YA-PIEUP BCA6 C0F7 # HANGUL SYLLABLE SIOS-YA-SIOS BCA7 C0F9 # HANGUL SYLLABLE SIOS-YA-IEUNG BCA8 C100 # HANGUL SYLLABLE SIOS-YAE BCA9 C104 # HANGUL SYLLABLE SIOS-YAE-NIEUN BCAA C108 # HANGUL SYLLABLE SIOS-YAE-RIEUL BCAB C110 # HANGUL SYLLABLE SIOS-YAE-MIEUM BCAC C115 # HANGUL SYLLABLE SIOS-YAE-IEUNG BCAD C11C # HANGUL SYLLABLE SIOS-EO BCAE C11D # HANGUL SYLLABLE SIOS-EO-KIYEOK BCAF C11E # HANGUL SYLLABLE SIOS-EO-SSANGKIYEOK BCB0 C11F # HANGUL SYLLABLE SIOS-EO-KIYEOKSIOS BCB1 C120 # HANGUL SYLLABLE SIOS-EO-NIEUN BCB2 C123 # HANGUL SYLLABLE SIOS-EO-TIKEUT BCB3 C124 # HANGUL SYLLABLE SIOS-EO-RIEUL BCB4 C126 # HANGUL SYLLABLE SIOS-EO-RIEULMIEUM BCB5 C127 # HANGUL SYLLABLE SIOS-EO-RIEULPIEUP BCB6 C12C # HANGUL SYLLABLE SIOS-EO-MIEUM BCB7 C12D # HANGUL SYLLABLE SIOS-EO-PIEUP BCB8 C12F # HANGUL SYLLABLE SIOS-EO-SIOS BCB9 C130 # HANGUL SYLLABLE SIOS-EO-SSANGSIOS BCBA C131 # HANGUL SYLLABLE SIOS-EO-IEUNG BCBB C136 # HANGUL SYLLABLE SIOS-EO-PHIEUPH BCBC C138 # HANGUL SYLLABLE SIOS-E BCBD C139 # HANGUL SYLLABLE SIOS-E-KIYEOK BCBE C13C # HANGUL SYLLABLE SIOS-E-NIEUN BCBF C140 # HANGUL SYLLABLE SIOS-E-RIEUL BCC0 C148 # HANGUL SYLLABLE SIOS-E-MIEUM BCC1 C149 # HANGUL SYLLABLE SIOS-E-PIEUP BCC2 C14B # HANGUL SYLLABLE SIOS-E-SIOS BCC3 C14C # HANGUL SYLLABLE SIOS-E-SSANGSIOS BCC4 C14D # HANGUL SYLLABLE SIOS-E-IEUNG BCC5 C154 # HANGUL SYLLABLE SIOS-YEO BCC6 C155 # HANGUL SYLLABLE SIOS-YEO-KIYEOK BCC7 C158 # HANGUL SYLLABLE SIOS-YEO-NIEUN BCC8 C15C # HANGUL SYLLABLE SIOS-YEO-RIEUL BCC9 C164 # HANGUL SYLLABLE SIOS-YEO-MIEUM BCCA C165 # HANGUL SYLLABLE SIOS-YEO-PIEUP BCCB C167 # HANGUL SYLLABLE SIOS-YEO-SIOS BCCC C168 # HANGUL SYLLABLE SIOS-YEO-SSANGSIOS BCCD C169 # HANGUL SYLLABLE SIOS-YEO-IEUNG BCCE C170 # HANGUL SYLLABLE SIOS-YE BCCF C174 # HANGUL SYLLABLE SIOS-YE-NIEUN BCD0 C178 # HANGUL SYLLABLE SIOS-YE-RIEUL BCD1 C185 # HANGUL SYLLABLE SIOS-YE-IEUNG BCD2 C18C # HANGUL SYLLABLE SIOS-O BCD3 C18D # HANGUL SYLLABLE SIOS-O-KIYEOK BCD4 C18E # HANGUL SYLLABLE SIOS-O-SSANGKIYEOK BCD5 C190 # HANGUL SYLLABLE SIOS-O-NIEUN BCD6 C194 # HANGUL SYLLABLE SIOS-O-RIEUL BCD7 C196 # HANGUL SYLLABLE SIOS-O-RIEULMIEUM BCD8 C19C # HANGUL SYLLABLE SIOS-O-MIEUM BCD9 C19D # HANGUL SYLLABLE SIOS-O-PIEUP BCDA C19F # HANGUL SYLLABLE SIOS-O-SIOS BCDB C1A1 # HANGUL SYLLABLE SIOS-O-IEUNG BCDC C1A5 # HANGUL SYLLABLE SIOS-O-THIEUTH BCDD C1A8 # HANGUL SYLLABLE SIOS-WA BCDE C1A9 # HANGUL SYLLABLE SIOS-WA-KIYEOK BCDF C1AC # HANGUL SYLLABLE SIOS-WA-NIEUN BCE0 C1B0 # HANGUL SYLLABLE SIOS-WA-RIEUL BCE1 C1BD # HANGUL SYLLABLE SIOS-WA-IEUNG BCE2 C1C4 # HANGUL SYLLABLE SIOS-WAE BCE3 C1C8 # HANGUL SYLLABLE SIOS-WAE-NIEUN BCE4 C1CC # HANGUL SYLLABLE SIOS-WAE-RIEUL BCE5 C1D4 # HANGUL SYLLABLE SIOS-WAE-MIEUM BCE6 C1D7 # HANGUL SYLLABLE SIOS-WAE-SIOS BCE7 C1D8 # HANGUL SYLLABLE SIOS-WAE-SSANGSIOS BCE8 C1E0 # HANGUL SYLLABLE SIOS-OE BCE9 C1E4 # HANGUL SYLLABLE SIOS-OE-NIEUN BCEA C1E8 # HANGUL SYLLABLE SIOS-OE-RIEUL BCEB C1F0 # HANGUL SYLLABLE SIOS-OE-MIEUM BCEC C1F1 # HANGUL SYLLABLE SIOS-OE-PIEUP BCED C1F3 # HANGUL SYLLABLE SIOS-OE-SIOS BCEE C1FC # HANGUL SYLLABLE SIOS-YO BCEF C1FD # HANGUL SYLLABLE SIOS-YO-KIYEOK BCF0 C200 # HANGUL SYLLABLE SIOS-YO-NIEUN BCF1 C204 # HANGUL SYLLABLE SIOS-YO-RIEUL BCF2 C20C # HANGUL SYLLABLE SIOS-YO-MIEUM BCF3 C20D # HANGUL SYLLABLE SIOS-YO-PIEUP BCF4 C20F # HANGUL SYLLABLE SIOS-YO-SIOS BCF5 C211 # HANGUL SYLLABLE SIOS-YO-IEUNG BCF6 C218 # HANGUL SYLLABLE SIOS-U BCF7 C219 # HANGUL SYLLABLE SIOS-U-KIYEOK BCF8 C21C # HANGUL SYLLABLE SIOS-U-NIEUN BCF9 C21F # HANGUL SYLLABLE SIOS-U-TIKEUT BCFA C220 # HANGUL SYLLABLE SIOS-U-RIEUL BCFB C228 # HANGUL SYLLABLE SIOS-U-MIEUM BCFC C229 # HANGUL SYLLABLE SIOS-U-PIEUP BCFD C22B # HANGUL SYLLABLE SIOS-U-SIOS BCFE C22D # HANGUL SYLLABLE SIOS-U-IEUNG BD41 D3D7 # HANGUL SYLLABLE PHIEUPH-YE-TIKEUT BD42 D3D9 # HANGUL SYLLABLE PHIEUPH-YE-RIEULKIYEOK BD43 D3DA # HANGUL SYLLABLE PHIEUPH-YE-RIEULMIEUM BD44 D3DB # HANGUL SYLLABLE PHIEUPH-YE-RIEULPIEUP BD45 D3DC # HANGUL SYLLABLE PHIEUPH-YE-RIEULSIOS BD46 D3DD # HANGUL SYLLABLE PHIEUPH-YE-RIEULTHIEUTH BD47 D3DE # HANGUL SYLLABLE PHIEUPH-YE-RIEULPHIEUPH BD48 D3DF # HANGUL SYLLABLE PHIEUPH-YE-RIEULHIEUH BD49 D3E0 # HANGUL SYLLABLE PHIEUPH-YE-MIEUM BD4A D3E2 # HANGUL SYLLABLE PHIEUPH-YE-PIEUPSIOS BD4B D3E4 # HANGUL SYLLABLE PHIEUPH-YE-SSANGSIOS BD4C D3E5 # HANGUL SYLLABLE PHIEUPH-YE-IEUNG BD4D D3E6 # HANGUL SYLLABLE PHIEUPH-YE-CIEUC BD4E D3E7 # HANGUL SYLLABLE PHIEUPH-YE-CHIEUCH BD4F D3E8 # HANGUL SYLLABLE PHIEUPH-YE-KHIEUKH BD50 D3E9 # HANGUL SYLLABLE PHIEUPH-YE-THIEUTH BD51 D3EA # HANGUL SYLLABLE PHIEUPH-YE-PHIEUPH BD52 D3EB # HANGUL SYLLABLE PHIEUPH-YE-HIEUH BD53 D3EE # HANGUL SYLLABLE PHIEUPH-O-SSANGKIYEOK BD54 D3EF # HANGUL SYLLABLE PHIEUPH-O-KIYEOKSIOS BD55 D3F1 # HANGUL SYLLABLE PHIEUPH-O-NIEUNCIEUC BD56 D3F2 # HANGUL SYLLABLE PHIEUPH-O-NIEUNHIEUH BD57 D3F3 # HANGUL SYLLABLE PHIEUPH-O-TIKEUT BD58 D3F5 # HANGUL SYLLABLE PHIEUPH-O-RIEULKIYEOK BD59 D3F6 # HANGUL SYLLABLE PHIEUPH-O-RIEULMIEUM BD5A D3F7 # HANGUL SYLLABLE PHIEUPH-O-RIEULPIEUP BD61 D3F8 # HANGUL SYLLABLE PHIEUPH-O-RIEULSIOS BD62 D3F9 # HANGUL SYLLABLE PHIEUPH-O-RIEULTHIEUTH BD63 D3FA # HANGUL SYLLABLE PHIEUPH-O-RIEULPHIEUPH BD64 D3FB # HANGUL SYLLABLE PHIEUPH-O-RIEULHIEUH BD65 D3FE # HANGUL SYLLABLE PHIEUPH-O-PIEUPSIOS BD66 D400 # HANGUL SYLLABLE PHIEUPH-O-SSANGSIOS BD67 D402 # HANGUL SYLLABLE PHIEUPH-O-CIEUC BD68 D403 # HANGUL SYLLABLE PHIEUPH-O-CHIEUCH BD69 D404 # HANGUL SYLLABLE PHIEUPH-O-KHIEUKH BD6A D405 # HANGUL SYLLABLE PHIEUPH-O-THIEUTH BD6B D406 # HANGUL SYLLABLE PHIEUPH-O-PHIEUPH BD6C D407 # HANGUL SYLLABLE PHIEUPH-O-HIEUH BD6D D409 # HANGUL SYLLABLE PHIEUPH-WA-KIYEOK BD6E D40A # HANGUL SYLLABLE PHIEUPH-WA-SSANGKIYEOK BD6F D40B # HANGUL SYLLABLE PHIEUPH-WA-KIYEOKSIOS BD70 D40C # HANGUL SYLLABLE PHIEUPH-WA-NIEUN BD71 D40D # HANGUL SYLLABLE PHIEUPH-WA-NIEUNCIEUC BD72 D40E # HANGUL SYLLABLE PHIEUPH-WA-NIEUNHIEUH BD73 D40F # HANGUL SYLLABLE PHIEUPH-WA-TIKEUT BD74 D410 # HANGUL SYLLABLE PHIEUPH-WA-RIEUL BD75 D411 # HANGUL SYLLABLE PHIEUPH-WA-RIEULKIYEOK BD76 D412 # HANGUL SYLLABLE PHIEUPH-WA-RIEULMIEUM BD77 D413 # HANGUL SYLLABLE PHIEUPH-WA-RIEULPIEUP BD78 D414 # HANGUL SYLLABLE PHIEUPH-WA-RIEULSIOS BD79 D415 # HANGUL SYLLABLE PHIEUPH-WA-RIEULTHIEUTH BD7A D416 # HANGUL SYLLABLE PHIEUPH-WA-RIEULPHIEUPH BD81 D417 # HANGUL SYLLABLE PHIEUPH-WA-RIEULHIEUH BD82 D418 # HANGUL SYLLABLE PHIEUPH-WA-MIEUM BD83 D419 # HANGUL SYLLABLE PHIEUPH-WA-PIEUP BD84 D41A # HANGUL SYLLABLE PHIEUPH-WA-PIEUPSIOS BD85 D41B # HANGUL SYLLABLE PHIEUPH-WA-SIOS BD86 D41C # HANGUL SYLLABLE PHIEUPH-WA-SSANGSIOS BD87 D41E # HANGUL SYLLABLE PHIEUPH-WA-CIEUC BD88 D41F # HANGUL SYLLABLE PHIEUPH-WA-CHIEUCH BD89 D420 # HANGUL SYLLABLE PHIEUPH-WA-KHIEUKH BD8A D421 # HANGUL SYLLABLE PHIEUPH-WA-THIEUTH BD8B D422 # HANGUL SYLLABLE PHIEUPH-WA-PHIEUPH BD8C D423 # HANGUL SYLLABLE PHIEUPH-WA-HIEUH BD8D D424 # HANGUL SYLLABLE PHIEUPH-WAE BD8E D425 # HANGUL SYLLABLE PHIEUPH-WAE-KIYEOK BD8F D426 # HANGUL SYLLABLE PHIEUPH-WAE-SSANGKIYEOK BD90 D427 # HANGUL SYLLABLE PHIEUPH-WAE-KIYEOKSIOS BD91 D428 # HANGUL SYLLABLE PHIEUPH-WAE-NIEUN BD92 D429 # HANGUL SYLLABLE PHIEUPH-WAE-NIEUNCIEUC BD93 D42A # HANGUL SYLLABLE PHIEUPH-WAE-NIEUNHIEUH BD94 D42B # HANGUL SYLLABLE PHIEUPH-WAE-TIKEUT BD95 D42C # HANGUL SYLLABLE PHIEUPH-WAE-RIEUL BD96 D42D # HANGUL SYLLABLE PHIEUPH-WAE-RIEULKIYEOK BD97 D42E # HANGUL SYLLABLE PHIEUPH-WAE-RIEULMIEUM BD98 D42F # HANGUL SYLLABLE PHIEUPH-WAE-RIEULPIEUP BD99 D430 # HANGUL SYLLABLE PHIEUPH-WAE-RIEULSIOS BD9A D431 # HANGUL SYLLABLE PHIEUPH-WAE-RIEULTHIEUTH BD9B D432 # HANGUL SYLLABLE PHIEUPH-WAE-RIEULPHIEUPH BD9C D433 # HANGUL SYLLABLE PHIEUPH-WAE-RIEULHIEUH BD9D D434 # HANGUL SYLLABLE PHIEUPH-WAE-MIEUM BD9E D435 # HANGUL SYLLABLE PHIEUPH-WAE-PIEUP BD9F D436 # HANGUL SYLLABLE PHIEUPH-WAE-PIEUPSIOS BDA0 D437 # HANGUL SYLLABLE PHIEUPH-WAE-SIOS BDA1 C22F # HANGUL SYLLABLE SIOS-U-CHIEUCH BDA2 C231 # HANGUL SYLLABLE SIOS-U-THIEUTH BDA3 C232 # HANGUL SYLLABLE SIOS-U-PHIEUPH BDA4 C234 # HANGUL SYLLABLE SIOS-WEO BDA5 C248 # HANGUL SYLLABLE SIOS-WEO-SSANGSIOS BDA6 C250 # HANGUL SYLLABLE SIOS-WE BDA7 C251 # HANGUL SYLLABLE SIOS-WE-KIYEOK BDA8 C254 # HANGUL SYLLABLE SIOS-WE-NIEUN BDA9 C258 # HANGUL SYLLABLE SIOS-WE-RIEUL BDAA C260 # HANGUL SYLLABLE SIOS-WE-MIEUM BDAB C265 # HANGUL SYLLABLE SIOS-WE-IEUNG BDAC C26C # HANGUL SYLLABLE SIOS-WI BDAD C26D # HANGUL SYLLABLE SIOS-WI-KIYEOK BDAE C270 # HANGUL SYLLABLE SIOS-WI-NIEUN BDAF C274 # HANGUL SYLLABLE SIOS-WI-RIEUL BDB0 C27C # HANGUL SYLLABLE SIOS-WI-MIEUM BDB1 C27D # HANGUL SYLLABLE SIOS-WI-PIEUP BDB2 C27F # HANGUL SYLLABLE SIOS-WI-SIOS BDB3 C281 # HANGUL SYLLABLE SIOS-WI-IEUNG BDB4 C288 # HANGUL SYLLABLE SIOS-YU BDB5 C289 # HANGUL SYLLABLE SIOS-YU-KIYEOK BDB6 C290 # HANGUL SYLLABLE SIOS-YU-RIEUL BDB7 C298 # HANGUL SYLLABLE SIOS-YU-MIEUM BDB8 C29B # HANGUL SYLLABLE SIOS-YU-SIOS BDB9 C29D # HANGUL SYLLABLE SIOS-YU-IEUNG BDBA C2A4 # HANGUL SYLLABLE SIOS-EU BDBB C2A5 # HANGUL SYLLABLE SIOS-EU-KIYEOK BDBC C2A8 # HANGUL SYLLABLE SIOS-EU-NIEUN BDBD C2AC # HANGUL SYLLABLE SIOS-EU-RIEUL BDBE C2AD # HANGUL SYLLABLE SIOS-EU-RIEULKIYEOK BDBF C2B4 # HANGUL SYLLABLE SIOS-EU-MIEUM BDC0 C2B5 # HANGUL SYLLABLE SIOS-EU-PIEUP BDC1 C2B7 # HANGUL SYLLABLE SIOS-EU-SIOS BDC2 C2B9 # HANGUL SYLLABLE SIOS-EU-IEUNG BDC3 C2DC # HANGUL SYLLABLE SIOS-I BDC4 C2DD # HANGUL SYLLABLE SIOS-I-KIYEOK BDC5 C2E0 # HANGUL SYLLABLE SIOS-I-NIEUN BDC6 C2E3 # HANGUL SYLLABLE SIOS-I-TIKEUT BDC7 C2E4 # HANGUL SYLLABLE SIOS-I-RIEUL BDC8 C2EB # HANGUL SYLLABLE SIOS-I-RIEULHIEUH BDC9 C2EC # HANGUL SYLLABLE SIOS-I-MIEUM BDCA C2ED # HANGUL SYLLABLE SIOS-I-PIEUP BDCB C2EF # HANGUL SYLLABLE SIOS-I-SIOS BDCC C2F1 # HANGUL SYLLABLE SIOS-I-IEUNG BDCD C2F6 # HANGUL SYLLABLE SIOS-I-PHIEUPH BDCE C2F8 # HANGUL SYLLABLE SSANGSIOS-A BDCF C2F9 # HANGUL SYLLABLE SSANGSIOS-A-KIYEOK BDD0 C2FB # HANGUL SYLLABLE SSANGSIOS-A-KIYEOKSIOS BDD1 C2FC # HANGUL SYLLABLE SSANGSIOS-A-NIEUN BDD2 C300 # HANGUL SYLLABLE SSANGSIOS-A-RIEUL BDD3 C308 # HANGUL SYLLABLE SSANGSIOS-A-MIEUM BDD4 C309 # HANGUL SYLLABLE SSANGSIOS-A-PIEUP BDD5 C30C # HANGUL SYLLABLE SSANGSIOS-A-SSANGSIOS BDD6 C30D # HANGUL SYLLABLE SSANGSIOS-A-IEUNG BDD7 C313 # HANGUL SYLLABLE SSANGSIOS-A-HIEUH BDD8 C314 # HANGUL SYLLABLE SSANGSIOS-AE BDD9 C315 # HANGUL SYLLABLE SSANGSIOS-AE-KIYEOK BDDA C318 # HANGUL SYLLABLE SSANGSIOS-AE-NIEUN BDDB C31C # HANGUL SYLLABLE SSANGSIOS-AE-RIEUL BDDC C324 # HANGUL SYLLABLE SSANGSIOS-AE-MIEUM BDDD C325 # HANGUL SYLLABLE SSANGSIOS-AE-PIEUP BDDE C328 # HANGUL SYLLABLE SSANGSIOS-AE-SSANGSIOS BDDF C329 # HANGUL SYLLABLE SSANGSIOS-AE-IEUNG BDE0 C345 # HANGUL SYLLABLE SSANGSIOS-YA-IEUNG BDE1 C368 # HANGUL SYLLABLE SSANGSIOS-EO BDE2 C369 # HANGUL SYLLABLE SSANGSIOS-EO-KIYEOK BDE3 C36C # HANGUL SYLLABLE SSANGSIOS-EO-NIEUN BDE4 C370 # HANGUL SYLLABLE SSANGSIOS-EO-RIEUL BDE5 C372 # HANGUL SYLLABLE SSANGSIOS-EO-RIEULMIEUM BDE6 C378 # HANGUL SYLLABLE SSANGSIOS-EO-MIEUM BDE7 C379 # HANGUL SYLLABLE SSANGSIOS-EO-PIEUP BDE8 C37C # HANGUL SYLLABLE SSANGSIOS-EO-SSANGSIOS BDE9 C37D # HANGUL SYLLABLE SSANGSIOS-EO-IEUNG BDEA C384 # HANGUL SYLLABLE SSANGSIOS-E BDEB C388 # HANGUL SYLLABLE SSANGSIOS-E-NIEUN BDEC C38C # HANGUL SYLLABLE SSANGSIOS-E-RIEUL BDED C3C0 # HANGUL SYLLABLE SSANGSIOS-YE-NIEUN BDEE C3D8 # HANGUL SYLLABLE SSANGSIOS-O BDEF C3D9 # HANGUL SYLLABLE SSANGSIOS-O-KIYEOK BDF0 C3DC # HANGUL SYLLABLE SSANGSIOS-O-NIEUN BDF1 C3DF # HANGUL SYLLABLE SSANGSIOS-O-TIKEUT BDF2 C3E0 # HANGUL SYLLABLE SSANGSIOS-O-RIEUL BDF3 C3E2 # HANGUL SYLLABLE SSANGSIOS-O-RIEULMIEUM BDF4 C3E8 # HANGUL SYLLABLE SSANGSIOS-O-MIEUM BDF5 C3E9 # HANGUL SYLLABLE SSANGSIOS-O-PIEUP BDF6 C3ED # HANGUL SYLLABLE SSANGSIOS-O-IEUNG BDF7 C3F4 # HANGUL SYLLABLE SSANGSIOS-WA BDF8 C3F5 # HANGUL SYLLABLE SSANGSIOS-WA-KIYEOK BDF9 C3F8 # HANGUL SYLLABLE SSANGSIOS-WA-NIEUN BDFA C408 # HANGUL SYLLABLE SSANGSIOS-WA-SSANGSIOS BDFB C410 # HANGUL SYLLABLE SSANGSIOS-WAE BDFC C424 # HANGUL SYLLABLE SSANGSIOS-WAE-SSANGSIOS BDFD C42C # HANGUL SYLLABLE SSANGSIOS-OE BDFE C430 # HANGUL SYLLABLE SSANGSIOS-OE-NIEUN BE41 D438 # HANGUL SYLLABLE PHIEUPH-WAE-SSANGSIOS BE42 D439 # HANGUL SYLLABLE PHIEUPH-WAE-IEUNG BE43 D43A # HANGUL SYLLABLE PHIEUPH-WAE-CIEUC BE44 D43B # HANGUL SYLLABLE PHIEUPH-WAE-CHIEUCH BE45 D43C # HANGUL SYLLABLE PHIEUPH-WAE-KHIEUKH BE46 D43D # HANGUL SYLLABLE PHIEUPH-WAE-THIEUTH BE47 D43E # HANGUL SYLLABLE PHIEUPH-WAE-PHIEUPH BE48 D43F # HANGUL SYLLABLE PHIEUPH-WAE-HIEUH BE49 D441 # HANGUL SYLLABLE PHIEUPH-OE-KIYEOK BE4A D442 # HANGUL SYLLABLE PHIEUPH-OE-SSANGKIYEOK BE4B D443 # HANGUL SYLLABLE PHIEUPH-OE-KIYEOKSIOS BE4C D445 # HANGUL SYLLABLE PHIEUPH-OE-NIEUNCIEUC BE4D D446 # HANGUL SYLLABLE PHIEUPH-OE-NIEUNHIEUH BE4E D447 # HANGUL SYLLABLE PHIEUPH-OE-TIKEUT BE4F D448 # HANGUL SYLLABLE PHIEUPH-OE-RIEUL BE50 D449 # HANGUL SYLLABLE PHIEUPH-OE-RIEULKIYEOK BE51 D44A # HANGUL SYLLABLE PHIEUPH-OE-RIEULMIEUM BE52 D44B # HANGUL SYLLABLE PHIEUPH-OE-RIEULPIEUP BE53 D44C # HANGUL SYLLABLE PHIEUPH-OE-RIEULSIOS BE54 D44D # HANGUL SYLLABLE PHIEUPH-OE-RIEULTHIEUTH BE55 D44E # HANGUL SYLLABLE PHIEUPH-OE-RIEULPHIEUPH BE56 D44F # HANGUL SYLLABLE PHIEUPH-OE-RIEULHIEUH BE57 D450 # HANGUL SYLLABLE PHIEUPH-OE-MIEUM BE58 D451 # HANGUL SYLLABLE PHIEUPH-OE-PIEUP BE59 D452 # HANGUL SYLLABLE PHIEUPH-OE-PIEUPSIOS BE5A D453 # HANGUL SYLLABLE PHIEUPH-OE-SIOS BE61 D454 # HANGUL SYLLABLE PHIEUPH-OE-SSANGSIOS BE62 D455 # HANGUL SYLLABLE PHIEUPH-OE-IEUNG BE63 D456 # HANGUL SYLLABLE PHIEUPH-OE-CIEUC BE64 D457 # HANGUL SYLLABLE PHIEUPH-OE-CHIEUCH BE65 D458 # HANGUL SYLLABLE PHIEUPH-OE-KHIEUKH BE66 D459 # HANGUL SYLLABLE PHIEUPH-OE-THIEUTH BE67 D45A # HANGUL SYLLABLE PHIEUPH-OE-PHIEUPH BE68 D45B # HANGUL SYLLABLE PHIEUPH-OE-HIEUH BE69 D45D # HANGUL SYLLABLE PHIEUPH-YO-KIYEOK BE6A D45E # HANGUL SYLLABLE PHIEUPH-YO-SSANGKIYEOK BE6B D45F # HANGUL SYLLABLE PHIEUPH-YO-KIYEOKSIOS BE6C D461 # HANGUL SYLLABLE PHIEUPH-YO-NIEUNCIEUC BE6D D462 # HANGUL SYLLABLE PHIEUPH-YO-NIEUNHIEUH BE6E D463 # HANGUL SYLLABLE PHIEUPH-YO-TIKEUT BE6F D465 # HANGUL SYLLABLE PHIEUPH-YO-RIEULKIYEOK BE70 D466 # HANGUL SYLLABLE PHIEUPH-YO-RIEULMIEUM BE71 D467 # HANGUL SYLLABLE PHIEUPH-YO-RIEULPIEUP BE72 D468 # HANGUL SYLLABLE PHIEUPH-YO-RIEULSIOS BE73 D469 # HANGUL SYLLABLE PHIEUPH-YO-RIEULTHIEUTH BE74 D46A # HANGUL SYLLABLE PHIEUPH-YO-RIEULPHIEUPH BE75 D46B # HANGUL SYLLABLE PHIEUPH-YO-RIEULHIEUH BE76 D46C # HANGUL SYLLABLE PHIEUPH-YO-MIEUM BE77 D46E # HANGUL SYLLABLE PHIEUPH-YO-PIEUPSIOS BE78 D470 # HANGUL SYLLABLE PHIEUPH-YO-SSANGSIOS BE79 D471 # HANGUL SYLLABLE PHIEUPH-YO-IEUNG BE7A D472 # HANGUL SYLLABLE PHIEUPH-YO-CIEUC BE81 D473 # HANGUL SYLLABLE PHIEUPH-YO-CHIEUCH BE82 D474 # HANGUL SYLLABLE PHIEUPH-YO-KHIEUKH BE83 D475 # HANGUL SYLLABLE PHIEUPH-YO-THIEUTH BE84 D476 # HANGUL SYLLABLE PHIEUPH-YO-PHIEUPH BE85 D477 # HANGUL SYLLABLE PHIEUPH-YO-HIEUH BE86 D47A # HANGUL SYLLABLE PHIEUPH-U-SSANGKIYEOK BE87 D47B # HANGUL SYLLABLE PHIEUPH-U-KIYEOKSIOS BE88 D47D # HANGUL SYLLABLE PHIEUPH-U-NIEUNCIEUC BE89 D47E # HANGUL SYLLABLE PHIEUPH-U-NIEUNHIEUH BE8A D481 # HANGUL SYLLABLE PHIEUPH-U-RIEULKIYEOK BE8B D483 # HANGUL SYLLABLE PHIEUPH-U-RIEULPIEUP BE8C D484 # HANGUL SYLLABLE PHIEUPH-U-RIEULSIOS BE8D D485 # HANGUL SYLLABLE PHIEUPH-U-RIEULTHIEUTH BE8E D486 # HANGUL SYLLABLE PHIEUPH-U-RIEULPHIEUPH BE8F D487 # HANGUL SYLLABLE PHIEUPH-U-RIEULHIEUH BE90 D48A # HANGUL SYLLABLE PHIEUPH-U-PIEUPSIOS BE91 D48C # HANGUL SYLLABLE PHIEUPH-U-SSANGSIOS BE92 D48E # HANGUL SYLLABLE PHIEUPH-U-CIEUC BE93 D48F # HANGUL SYLLABLE PHIEUPH-U-CHIEUCH BE94 D490 # HANGUL SYLLABLE PHIEUPH-U-KHIEUKH BE95 D491 # HANGUL SYLLABLE PHIEUPH-U-THIEUTH BE96 D492 # HANGUL SYLLABLE PHIEUPH-U-PHIEUPH BE97 D493 # HANGUL SYLLABLE PHIEUPH-U-HIEUH BE98 D495 # HANGUL SYLLABLE PHIEUPH-WEO-KIYEOK BE99 D496 # HANGUL SYLLABLE PHIEUPH-WEO-SSANGKIYEOK BE9A D497 # HANGUL SYLLABLE PHIEUPH-WEO-KIYEOKSIOS BE9B D498 # HANGUL SYLLABLE PHIEUPH-WEO-NIEUN BE9C D499 # HANGUL SYLLABLE PHIEUPH-WEO-NIEUNCIEUC BE9D D49A # HANGUL SYLLABLE PHIEUPH-WEO-NIEUNHIEUH BE9E D49B # HANGUL SYLLABLE PHIEUPH-WEO-TIKEUT BE9F D49C # HANGUL SYLLABLE PHIEUPH-WEO-RIEUL BEA0 D49D # HANGUL SYLLABLE PHIEUPH-WEO-RIEULKIYEOK BEA1 C434 # HANGUL SYLLABLE SSANGSIOS-OE-RIEUL BEA2 C43C # HANGUL SYLLABLE SSANGSIOS-OE-MIEUM BEA3 C43D # HANGUL SYLLABLE SSANGSIOS-OE-PIEUP BEA4 C448 # HANGUL SYLLABLE SSANGSIOS-YO BEA5 C464 # HANGUL SYLLABLE SSANGSIOS-U BEA6 C465 # HANGUL SYLLABLE SSANGSIOS-U-KIYEOK BEA7 C468 # HANGUL SYLLABLE SSANGSIOS-U-NIEUN BEA8 C46C # HANGUL SYLLABLE SSANGSIOS-U-RIEUL BEA9 C474 # HANGUL SYLLABLE SSANGSIOS-U-MIEUM BEAA C475 # HANGUL SYLLABLE SSANGSIOS-U-PIEUP BEAB C479 # HANGUL SYLLABLE SSANGSIOS-U-IEUNG BEAC C480 # HANGUL SYLLABLE SSANGSIOS-WEO BEAD C494 # HANGUL SYLLABLE SSANGSIOS-WEO-SSANGSIOS BEAE C49C # HANGUL SYLLABLE SSANGSIOS-WE BEAF C4B8 # HANGUL SYLLABLE SSANGSIOS-WI BEB0 C4BC # HANGUL SYLLABLE SSANGSIOS-WI-NIEUN BEB1 C4E9 # HANGUL SYLLABLE SSANGSIOS-YU-IEUNG BEB2 C4F0 # HANGUL SYLLABLE SSANGSIOS-EU BEB3 C4F1 # HANGUL SYLLABLE SSANGSIOS-EU-KIYEOK BEB4 C4F4 # HANGUL SYLLABLE SSANGSIOS-EU-NIEUN BEB5 C4F8 # HANGUL SYLLABLE SSANGSIOS-EU-RIEUL BEB6 C4FA # HANGUL SYLLABLE SSANGSIOS-EU-RIEULMIEUM BEB7 C4FF # HANGUL SYLLABLE SSANGSIOS-EU-RIEULHIEUH BEB8 C500 # HANGUL SYLLABLE SSANGSIOS-EU-MIEUM BEB9 C501 # HANGUL SYLLABLE SSANGSIOS-EU-PIEUP BEBA C50C # HANGUL SYLLABLE SSANGSIOS-YI BEBB C510 # HANGUL SYLLABLE SSANGSIOS-YI-NIEUN BEBC C514 # HANGUL SYLLABLE SSANGSIOS-YI-RIEUL BEBD C51C # HANGUL SYLLABLE SSANGSIOS-YI-MIEUM BEBE C528 # HANGUL SYLLABLE SSANGSIOS-I BEBF C529 # HANGUL SYLLABLE SSANGSIOS-I-KIYEOK BEC0 C52C # HANGUL SYLLABLE SSANGSIOS-I-NIEUN BEC1 C530 # HANGUL SYLLABLE SSANGSIOS-I-RIEUL BEC2 C538 # HANGUL SYLLABLE SSANGSIOS-I-MIEUM BEC3 C539 # HANGUL SYLLABLE SSANGSIOS-I-PIEUP BEC4 C53B # HANGUL SYLLABLE SSANGSIOS-I-SIOS BEC5 C53D # HANGUL SYLLABLE SSANGSIOS-I-IEUNG BEC6 C544 # HANGUL SYLLABLE IEUNG-A BEC7 C545 # HANGUL SYLLABLE IEUNG-A-KIYEOK BEC8 C548 # HANGUL SYLLABLE IEUNG-A-NIEUN BEC9 C549 # HANGUL SYLLABLE IEUNG-A-NIEUNCIEUC BECA C54A # HANGUL SYLLABLE IEUNG-A-NIEUNHIEUH BECB C54C # HANGUL SYLLABLE IEUNG-A-RIEUL BECC C54D # HANGUL SYLLABLE IEUNG-A-RIEULKIYEOK BECD C54E # HANGUL SYLLABLE IEUNG-A-RIEULMIEUM BECE C553 # HANGUL SYLLABLE IEUNG-A-RIEULHIEUH BECF C554 # HANGUL SYLLABLE IEUNG-A-MIEUM BED0 C555 # HANGUL SYLLABLE IEUNG-A-PIEUP BED1 C557 # HANGUL SYLLABLE IEUNG-A-SIOS BED2 C558 # HANGUL SYLLABLE IEUNG-A-SSANGSIOS BED3 C559 # HANGUL SYLLABLE IEUNG-A-IEUNG BED4 C55D # HANGUL SYLLABLE IEUNG-A-THIEUTH BED5 C55E # HANGUL SYLLABLE IEUNG-A-PHIEUPH BED6 C560 # HANGUL SYLLABLE IEUNG-AE BED7 C561 # HANGUL SYLLABLE IEUNG-AE-KIYEOK BED8 C564 # HANGUL SYLLABLE IEUNG-AE-NIEUN BED9 C568 # HANGUL SYLLABLE IEUNG-AE-RIEUL BEDA C570 # HANGUL SYLLABLE IEUNG-AE-MIEUM BEDB C571 # HANGUL SYLLABLE IEUNG-AE-PIEUP BEDC C573 # HANGUL SYLLABLE IEUNG-AE-SIOS BEDD C574 # HANGUL SYLLABLE IEUNG-AE-SSANGSIOS BEDE C575 # HANGUL SYLLABLE IEUNG-AE-IEUNG BEDF C57C # HANGUL SYLLABLE IEUNG-YA BEE0 C57D # HANGUL SYLLABLE IEUNG-YA-KIYEOK BEE1 C580 # HANGUL SYLLABLE IEUNG-YA-NIEUN BEE2 C584 # HANGUL SYLLABLE IEUNG-YA-RIEUL BEE3 C587 # HANGUL SYLLABLE IEUNG-YA-RIEULPIEUP BEE4 C58C # HANGUL SYLLABLE IEUNG-YA-MIEUM BEE5 C58D # HANGUL SYLLABLE IEUNG-YA-PIEUP BEE6 C58F # HANGUL SYLLABLE IEUNG-YA-SIOS BEE7 C591 # HANGUL SYLLABLE IEUNG-YA-IEUNG BEE8 C595 # HANGUL SYLLABLE IEUNG-YA-THIEUTH BEE9 C597 # HANGUL SYLLABLE IEUNG-YA-HIEUH BEEA C598 # HANGUL SYLLABLE IEUNG-YAE BEEB C59C # HANGUL SYLLABLE IEUNG-YAE-NIEUN BEEC C5A0 # HANGUL SYLLABLE IEUNG-YAE-RIEUL BEED C5A9 # HANGUL SYLLABLE IEUNG-YAE-PIEUP BEEE C5B4 # HANGUL SYLLABLE IEUNG-EO BEEF C5B5 # HANGUL SYLLABLE IEUNG-EO-KIYEOK BEF0 C5B8 # HANGUL SYLLABLE IEUNG-EO-NIEUN BEF1 C5B9 # HANGUL SYLLABLE IEUNG-EO-NIEUNCIEUC BEF2 C5BB # HANGUL SYLLABLE IEUNG-EO-TIKEUT BEF3 C5BC # HANGUL SYLLABLE IEUNG-EO-RIEUL BEF4 C5BD # HANGUL SYLLABLE IEUNG-EO-RIEULKIYEOK BEF5 C5BE # HANGUL SYLLABLE IEUNG-EO-RIEULMIEUM BEF6 C5C4 # HANGUL SYLLABLE IEUNG-EO-MIEUM BEF7 C5C5 # HANGUL SYLLABLE IEUNG-EO-PIEUP BEF8 C5C6 # HANGUL SYLLABLE IEUNG-EO-PIEUPSIOS BEF9 C5C7 # HANGUL SYLLABLE IEUNG-EO-SIOS BEFA C5C8 # HANGUL SYLLABLE IEUNG-EO-SSANGSIOS BEFB C5C9 # HANGUL SYLLABLE IEUNG-EO-IEUNG BEFC C5CA # HANGUL SYLLABLE IEUNG-EO-CIEUC BEFD C5CC # HANGUL SYLLABLE IEUNG-EO-KHIEUKH BEFE C5CE # HANGUL SYLLABLE IEUNG-EO-PHIEUPH BF41 D49E # HANGUL SYLLABLE PHIEUPH-WEO-RIEULMIEUM BF42 D49F # HANGUL SYLLABLE PHIEUPH-WEO-RIEULPIEUP BF43 D4A0 # HANGUL SYLLABLE PHIEUPH-WEO-RIEULSIOS BF44 D4A1 # HANGUL SYLLABLE PHIEUPH-WEO-RIEULTHIEUTH BF45 D4A2 # HANGUL SYLLABLE PHIEUPH-WEO-RIEULPHIEUPH BF46 D4A3 # HANGUL SYLLABLE PHIEUPH-WEO-RIEULHIEUH BF47 D4A4 # HANGUL SYLLABLE PHIEUPH-WEO-MIEUM BF48 D4A5 # HANGUL SYLLABLE PHIEUPH-WEO-PIEUP BF49 D4A6 # HANGUL SYLLABLE PHIEUPH-WEO-PIEUPSIOS BF4A D4A7 # HANGUL SYLLABLE PHIEUPH-WEO-SIOS BF4B D4A8 # HANGUL SYLLABLE PHIEUPH-WEO-SSANGSIOS BF4C D4AA # HANGUL SYLLABLE PHIEUPH-WEO-CIEUC BF4D D4AB # HANGUL SYLLABLE PHIEUPH-WEO-CHIEUCH BF4E D4AC # HANGUL SYLLABLE PHIEUPH-WEO-KHIEUKH BF4F D4AD # HANGUL SYLLABLE PHIEUPH-WEO-THIEUTH BF50 D4AE # HANGUL SYLLABLE PHIEUPH-WEO-PHIEUPH BF51 D4AF # HANGUL SYLLABLE PHIEUPH-WEO-HIEUH BF52 D4B0 # HANGUL SYLLABLE PHIEUPH-WE BF53 D4B1 # HANGUL SYLLABLE PHIEUPH-WE-KIYEOK BF54 D4B2 # HANGUL SYLLABLE PHIEUPH-WE-SSANGKIYEOK BF55 D4B3 # HANGUL SYLLABLE PHIEUPH-WE-KIYEOKSIOS BF56 D4B4 # HANGUL SYLLABLE PHIEUPH-WE-NIEUN BF57 D4B5 # HANGUL SYLLABLE PHIEUPH-WE-NIEUNCIEUC BF58 D4B6 # HANGUL SYLLABLE PHIEUPH-WE-NIEUNHIEUH BF59 D4B7 # HANGUL SYLLABLE PHIEUPH-WE-TIKEUT BF5A D4B8 # HANGUL SYLLABLE PHIEUPH-WE-RIEUL BF61 D4B9 # HANGUL SYLLABLE PHIEUPH-WE-RIEULKIYEOK BF62 D4BA # HANGUL SYLLABLE PHIEUPH-WE-RIEULMIEUM BF63 D4BB # HANGUL SYLLABLE PHIEUPH-WE-RIEULPIEUP BF64 D4BC # HANGUL SYLLABLE PHIEUPH-WE-RIEULSIOS BF65 D4BD # HANGUL SYLLABLE PHIEUPH-WE-RIEULTHIEUTH BF66 D4BE # HANGUL SYLLABLE PHIEUPH-WE-RIEULPHIEUPH BF67 D4BF # HANGUL SYLLABLE PHIEUPH-WE-RIEULHIEUH BF68 D4C0 # HANGUL SYLLABLE PHIEUPH-WE-MIEUM BF69 D4C1 # HANGUL SYLLABLE PHIEUPH-WE-PIEUP BF6A D4C2 # HANGUL SYLLABLE PHIEUPH-WE-PIEUPSIOS BF6B D4C3 # HANGUL SYLLABLE PHIEUPH-WE-SIOS BF6C D4C4 # HANGUL SYLLABLE PHIEUPH-WE-SSANGSIOS BF6D D4C5 # HANGUL SYLLABLE PHIEUPH-WE-IEUNG BF6E D4C6 # HANGUL SYLLABLE PHIEUPH-WE-CIEUC BF6F D4C7 # HANGUL SYLLABLE PHIEUPH-WE-CHIEUCH BF70 D4C8 # HANGUL SYLLABLE PHIEUPH-WE-KHIEUKH BF71 D4C9 # HANGUL SYLLABLE PHIEUPH-WE-THIEUTH BF72 D4CA # HANGUL SYLLABLE PHIEUPH-WE-PHIEUPH BF73 D4CB # HANGUL SYLLABLE PHIEUPH-WE-HIEUH BF74 D4CD # HANGUL SYLLABLE PHIEUPH-WI-KIYEOK BF75 D4CE # HANGUL SYLLABLE PHIEUPH-WI-SSANGKIYEOK BF76 D4CF # HANGUL SYLLABLE PHIEUPH-WI-KIYEOKSIOS BF77 D4D1 # HANGUL SYLLABLE PHIEUPH-WI-NIEUNCIEUC BF78 D4D2 # HANGUL SYLLABLE PHIEUPH-WI-NIEUNHIEUH BF79 D4D3 # HANGUL SYLLABLE PHIEUPH-WI-TIKEUT BF7A D4D5 # HANGUL SYLLABLE PHIEUPH-WI-RIEULKIYEOK BF81 D4D6 # HANGUL SYLLABLE PHIEUPH-WI-RIEULMIEUM BF82 D4D7 # HANGUL SYLLABLE PHIEUPH-WI-RIEULPIEUP BF83 D4D8 # HANGUL SYLLABLE PHIEUPH-WI-RIEULSIOS BF84 D4D9 # HANGUL SYLLABLE PHIEUPH-WI-RIEULTHIEUTH BF85 D4DA # HANGUL SYLLABLE PHIEUPH-WI-RIEULPHIEUPH BF86 D4DB # HANGUL SYLLABLE PHIEUPH-WI-RIEULHIEUH BF87 D4DD # HANGUL SYLLABLE PHIEUPH-WI-PIEUP BF88 D4DE # HANGUL SYLLABLE PHIEUPH-WI-PIEUPSIOS BF89 D4E0 # HANGUL SYLLABLE PHIEUPH-WI-SSANGSIOS BF8A D4E1 # HANGUL SYLLABLE PHIEUPH-WI-IEUNG BF8B D4E2 # HANGUL SYLLABLE PHIEUPH-WI-CIEUC BF8C D4E3 # HANGUL SYLLABLE PHIEUPH-WI-CHIEUCH BF8D D4E4 # HANGUL SYLLABLE PHIEUPH-WI-KHIEUKH BF8E D4E5 # HANGUL SYLLABLE PHIEUPH-WI-THIEUTH BF8F D4E6 # HANGUL SYLLABLE PHIEUPH-WI-PHIEUPH BF90 D4E7 # HANGUL SYLLABLE PHIEUPH-WI-HIEUH BF91 D4E9 # HANGUL SYLLABLE PHIEUPH-YU-KIYEOK BF92 D4EA # HANGUL SYLLABLE PHIEUPH-YU-SSANGKIYEOK BF93 D4EB # HANGUL SYLLABLE PHIEUPH-YU-KIYEOKSIOS BF94 D4ED # HANGUL SYLLABLE PHIEUPH-YU-NIEUNCIEUC BF95 D4EE # HANGUL SYLLABLE PHIEUPH-YU-NIEUNHIEUH BF96 D4EF # HANGUL SYLLABLE PHIEUPH-YU-TIKEUT BF97 D4F1 # HANGUL SYLLABLE PHIEUPH-YU-RIEULKIYEOK BF98 D4F2 # HANGUL SYLLABLE PHIEUPH-YU-RIEULMIEUM BF99 D4F3 # HANGUL SYLLABLE PHIEUPH-YU-RIEULPIEUP BF9A D4F4 # HANGUL SYLLABLE PHIEUPH-YU-RIEULSIOS BF9B D4F5 # HANGUL SYLLABLE PHIEUPH-YU-RIEULTHIEUTH BF9C D4F6 # HANGUL SYLLABLE PHIEUPH-YU-RIEULPHIEUPH BF9D D4F7 # HANGUL SYLLABLE PHIEUPH-YU-RIEULHIEUH BF9E D4F9 # HANGUL SYLLABLE PHIEUPH-YU-PIEUP BF9F D4FA # HANGUL SYLLABLE PHIEUPH-YU-PIEUPSIOS BFA0 D4FC # HANGUL SYLLABLE PHIEUPH-YU-SSANGSIOS BFA1 C5D0 # HANGUL SYLLABLE IEUNG-E BFA2 C5D1 # HANGUL SYLLABLE IEUNG-E-KIYEOK BFA3 C5D4 # HANGUL SYLLABLE IEUNG-E-NIEUN BFA4 C5D8 # HANGUL SYLLABLE IEUNG-E-RIEUL BFA5 C5E0 # HANGUL SYLLABLE IEUNG-E-MIEUM BFA6 C5E1 # HANGUL SYLLABLE IEUNG-E-PIEUP BFA7 C5E3 # HANGUL SYLLABLE IEUNG-E-SIOS BFA8 C5E5 # HANGUL SYLLABLE IEUNG-E-IEUNG BFA9 C5EC # HANGUL SYLLABLE IEUNG-YEO BFAA C5ED # HANGUL SYLLABLE IEUNG-YEO-KIYEOK BFAB C5EE # HANGUL SYLLABLE IEUNG-YEO-SSANGKIYEOK BFAC C5F0 # HANGUL SYLLABLE IEUNG-YEO-NIEUN BFAD C5F4 # HANGUL SYLLABLE IEUNG-YEO-RIEUL BFAE C5F6 # HANGUL SYLLABLE IEUNG-YEO-RIEULMIEUM BFAF C5F7 # HANGUL SYLLABLE IEUNG-YEO-RIEULPIEUP BFB0 C5FC # HANGUL SYLLABLE IEUNG-YEO-MIEUM BFB1 C5FD # HANGUL SYLLABLE IEUNG-YEO-PIEUP BFB2 C5FE # HANGUL SYLLABLE IEUNG-YEO-PIEUPSIOS BFB3 C5FF # HANGUL SYLLABLE IEUNG-YEO-SIOS BFB4 C600 # HANGUL SYLLABLE IEUNG-YEO-SSANGSIOS BFB5 C601 # HANGUL SYLLABLE IEUNG-YEO-IEUNG BFB6 C605 # HANGUL SYLLABLE IEUNG-YEO-THIEUTH BFB7 C606 # HANGUL SYLLABLE IEUNG-YEO-PHIEUPH BFB8 C607 # HANGUL SYLLABLE IEUNG-YEO-HIEUH BFB9 C608 # HANGUL SYLLABLE IEUNG-YE BFBA C60C # HANGUL SYLLABLE IEUNG-YE-NIEUN BFBB C610 # HANGUL SYLLABLE IEUNG-YE-RIEUL BFBC C618 # HANGUL SYLLABLE IEUNG-YE-MIEUM BFBD C619 # HANGUL SYLLABLE IEUNG-YE-PIEUP BFBE C61B # HANGUL SYLLABLE IEUNG-YE-SIOS BFBF C61C # HANGUL SYLLABLE IEUNG-YE-SSANGSIOS BFC0 C624 # HANGUL SYLLABLE IEUNG-O BFC1 C625 # HANGUL SYLLABLE IEUNG-O-KIYEOK BFC2 C628 # HANGUL SYLLABLE IEUNG-O-NIEUN BFC3 C62C # HANGUL SYLLABLE IEUNG-O-RIEUL BFC4 C62D # HANGUL SYLLABLE IEUNG-O-RIEULKIYEOK BFC5 C62E # HANGUL SYLLABLE IEUNG-O-RIEULMIEUM BFC6 C630 # HANGUL SYLLABLE IEUNG-O-RIEULSIOS BFC7 C633 # HANGUL SYLLABLE IEUNG-O-RIEULHIEUH BFC8 C634 # HANGUL SYLLABLE IEUNG-O-MIEUM BFC9 C635 # HANGUL SYLLABLE IEUNG-O-PIEUP BFCA C637 # HANGUL SYLLABLE IEUNG-O-SIOS BFCB C639 # HANGUL SYLLABLE IEUNG-O-IEUNG BFCC C63B # HANGUL SYLLABLE IEUNG-O-CHIEUCH BFCD C640 # HANGUL SYLLABLE IEUNG-WA BFCE C641 # HANGUL SYLLABLE IEUNG-WA-KIYEOK BFCF C644 # HANGUL SYLLABLE IEUNG-WA-NIEUN BFD0 C648 # HANGUL SYLLABLE IEUNG-WA-RIEUL BFD1 C650 # HANGUL SYLLABLE IEUNG-WA-MIEUM BFD2 C651 # HANGUL SYLLABLE IEUNG-WA-PIEUP BFD3 C653 # HANGUL SYLLABLE IEUNG-WA-SIOS BFD4 C654 # HANGUL SYLLABLE IEUNG-WA-SSANGSIOS BFD5 C655 # HANGUL SYLLABLE IEUNG-WA-IEUNG BFD6 C65C # HANGUL SYLLABLE IEUNG-WAE BFD7 C65D # HANGUL SYLLABLE IEUNG-WAE-KIYEOK BFD8 C660 # HANGUL SYLLABLE IEUNG-WAE-NIEUN BFD9 C66C # HANGUL SYLLABLE IEUNG-WAE-MIEUM BFDA C66F # HANGUL SYLLABLE IEUNG-WAE-SIOS BFDB C671 # HANGUL SYLLABLE IEUNG-WAE-IEUNG BFDC C678 # HANGUL SYLLABLE IEUNG-OE BFDD C679 # HANGUL SYLLABLE IEUNG-OE-KIYEOK BFDE C67C # HANGUL SYLLABLE IEUNG-OE-NIEUN BFDF C680 # HANGUL SYLLABLE IEUNG-OE-RIEUL BFE0 C688 # HANGUL SYLLABLE IEUNG-OE-MIEUM BFE1 C689 # HANGUL SYLLABLE IEUNG-OE-PIEUP BFE2 C68B # HANGUL SYLLABLE IEUNG-OE-SIOS BFE3 C68D # HANGUL SYLLABLE IEUNG-OE-IEUNG BFE4 C694 # HANGUL SYLLABLE IEUNG-YO BFE5 C695 # HANGUL SYLLABLE IEUNG-YO-KIYEOK BFE6 C698 # HANGUL SYLLABLE IEUNG-YO-NIEUN BFE7 C69C # HANGUL SYLLABLE IEUNG-YO-RIEUL BFE8 C6A4 # HANGUL SYLLABLE IEUNG-YO-MIEUM BFE9 C6A5 # HANGUL SYLLABLE IEUNG-YO-PIEUP BFEA C6A7 # HANGUL SYLLABLE IEUNG-YO-SIOS BFEB C6A9 # HANGUL SYLLABLE IEUNG-YO-IEUNG BFEC C6B0 # HANGUL SYLLABLE IEUNG-U BFED C6B1 # HANGUL SYLLABLE IEUNG-U-KIYEOK BFEE C6B4 # HANGUL SYLLABLE IEUNG-U-NIEUN BFEF C6B8 # HANGUL SYLLABLE IEUNG-U-RIEUL BFF0 C6B9 # HANGUL SYLLABLE IEUNG-U-RIEULKIYEOK BFF1 C6BA # HANGUL SYLLABLE IEUNG-U-RIEULMIEUM BFF2 C6C0 # HANGUL SYLLABLE IEUNG-U-MIEUM BFF3 C6C1 # HANGUL SYLLABLE IEUNG-U-PIEUP BFF4 C6C3 # HANGUL SYLLABLE IEUNG-U-SIOS BFF5 C6C5 # HANGUL SYLLABLE IEUNG-U-IEUNG BFF6 C6CC # HANGUL SYLLABLE IEUNG-WEO BFF7 C6CD # HANGUL SYLLABLE IEUNG-WEO-KIYEOK BFF8 C6D0 # HANGUL SYLLABLE IEUNG-WEO-NIEUN BFF9 C6D4 # HANGUL SYLLABLE IEUNG-WEO-RIEUL BFFA C6DC # HANGUL SYLLABLE IEUNG-WEO-MIEUM BFFB C6DD # HANGUL SYLLABLE IEUNG-WEO-PIEUP BFFC C6E0 # HANGUL SYLLABLE IEUNG-WEO-SSANGSIOS BFFD C6E1 # HANGUL SYLLABLE IEUNG-WEO-IEUNG BFFE C6E8 # HANGUL SYLLABLE IEUNG-WE C041 D4FE # HANGUL SYLLABLE PHIEUPH-YU-CIEUC C042 D4FF # HANGUL SYLLABLE PHIEUPH-YU-CHIEUCH C043 D500 # HANGUL SYLLABLE PHIEUPH-YU-KHIEUKH C044 D501 # HANGUL SYLLABLE PHIEUPH-YU-THIEUTH C045 D502 # HANGUL SYLLABLE PHIEUPH-YU-PHIEUPH C046 D503 # HANGUL SYLLABLE PHIEUPH-YU-HIEUH C047 D505 # HANGUL SYLLABLE PHIEUPH-EU-KIYEOK C048 D506 # HANGUL SYLLABLE PHIEUPH-EU-SSANGKIYEOK C049 D507 # HANGUL SYLLABLE PHIEUPH-EU-KIYEOKSIOS C04A D509 # HANGUL SYLLABLE PHIEUPH-EU-NIEUNCIEUC C04B D50A # HANGUL SYLLABLE PHIEUPH-EU-NIEUNHIEUH C04C D50B # HANGUL SYLLABLE PHIEUPH-EU-TIKEUT C04D D50D # HANGUL SYLLABLE PHIEUPH-EU-RIEULKIYEOK C04E D50E # HANGUL SYLLABLE PHIEUPH-EU-RIEULMIEUM C04F D50F # HANGUL SYLLABLE PHIEUPH-EU-RIEULPIEUP C050 D510 # HANGUL SYLLABLE PHIEUPH-EU-RIEULSIOS C051 D511 # HANGUL SYLLABLE PHIEUPH-EU-RIEULTHIEUTH C052 D512 # HANGUL SYLLABLE PHIEUPH-EU-RIEULPHIEUPH C053 D513 # HANGUL SYLLABLE PHIEUPH-EU-RIEULHIEUH C054 D516 # HANGUL SYLLABLE PHIEUPH-EU-PIEUPSIOS C055 D518 # HANGUL SYLLABLE PHIEUPH-EU-SSANGSIOS C056 D519 # HANGUL SYLLABLE PHIEUPH-EU-IEUNG C057 D51A # HANGUL SYLLABLE PHIEUPH-EU-CIEUC C058 D51B # HANGUL SYLLABLE PHIEUPH-EU-CHIEUCH C059 D51C # HANGUL SYLLABLE PHIEUPH-EU-KHIEUKH C05A D51D # HANGUL SYLLABLE PHIEUPH-EU-THIEUTH C061 D51E # HANGUL SYLLABLE PHIEUPH-EU-PHIEUPH C062 D51F # HANGUL SYLLABLE PHIEUPH-EU-HIEUH C063 D520 # HANGUL SYLLABLE PHIEUPH-YI C064 D521 # HANGUL SYLLABLE PHIEUPH-YI-KIYEOK C065 D522 # HANGUL SYLLABLE PHIEUPH-YI-SSANGKIYEOK C066 D523 # HANGUL SYLLABLE PHIEUPH-YI-KIYEOKSIOS C067 D524 # HANGUL SYLLABLE PHIEUPH-YI-NIEUN C068 D525 # HANGUL SYLLABLE PHIEUPH-YI-NIEUNCIEUC C069 D526 # HANGUL SYLLABLE PHIEUPH-YI-NIEUNHIEUH C06A D527 # HANGUL SYLLABLE PHIEUPH-YI-TIKEUT C06B D528 # HANGUL SYLLABLE PHIEUPH-YI-RIEUL C06C D529 # HANGUL SYLLABLE PHIEUPH-YI-RIEULKIYEOK C06D D52A # HANGUL SYLLABLE PHIEUPH-YI-RIEULMIEUM C06E D52B # HANGUL SYLLABLE PHIEUPH-YI-RIEULPIEUP C06F D52C # HANGUL SYLLABLE PHIEUPH-YI-RIEULSIOS C070 D52D # HANGUL SYLLABLE PHIEUPH-YI-RIEULTHIEUTH C071 D52E # HANGUL SYLLABLE PHIEUPH-YI-RIEULPHIEUPH C072 D52F # HANGUL SYLLABLE PHIEUPH-YI-RIEULHIEUH C073 D530 # HANGUL SYLLABLE PHIEUPH-YI-MIEUM C074 D531 # HANGUL SYLLABLE PHIEUPH-YI-PIEUP C075 D532 # HANGUL SYLLABLE PHIEUPH-YI-PIEUPSIOS C076 D533 # HANGUL SYLLABLE PHIEUPH-YI-SIOS C077 D534 # HANGUL SYLLABLE PHIEUPH-YI-SSANGSIOS C078 D535 # HANGUL SYLLABLE PHIEUPH-YI-IEUNG C079 D536 # HANGUL SYLLABLE PHIEUPH-YI-CIEUC C07A D537 # HANGUL SYLLABLE PHIEUPH-YI-CHIEUCH C081 D538 # HANGUL SYLLABLE PHIEUPH-YI-KHIEUKH C082 D539 # HANGUL SYLLABLE PHIEUPH-YI-THIEUTH C083 D53A # HANGUL SYLLABLE PHIEUPH-YI-PHIEUPH C084 D53B # HANGUL SYLLABLE PHIEUPH-YI-HIEUH C085 D53E # HANGUL SYLLABLE PHIEUPH-I-SSANGKIYEOK C086 D53F # HANGUL SYLLABLE PHIEUPH-I-KIYEOKSIOS C087 D541 # HANGUL SYLLABLE PHIEUPH-I-NIEUNCIEUC C088 D542 # HANGUL SYLLABLE PHIEUPH-I-NIEUNHIEUH C089 D543 # HANGUL SYLLABLE PHIEUPH-I-TIKEUT C08A D545 # HANGUL SYLLABLE PHIEUPH-I-RIEULKIYEOK C08B D546 # HANGUL SYLLABLE PHIEUPH-I-RIEULMIEUM C08C D547 # HANGUL SYLLABLE PHIEUPH-I-RIEULPIEUP C08D D548 # HANGUL SYLLABLE PHIEUPH-I-RIEULSIOS C08E D549 # HANGUL SYLLABLE PHIEUPH-I-RIEULTHIEUTH C08F D54A # HANGUL SYLLABLE PHIEUPH-I-RIEULPHIEUPH C090 D54B # HANGUL SYLLABLE PHIEUPH-I-RIEULHIEUH C091 D54E # HANGUL SYLLABLE PHIEUPH-I-PIEUPSIOS C092 D550 # HANGUL SYLLABLE PHIEUPH-I-SSANGSIOS C093 D552 # HANGUL SYLLABLE PHIEUPH-I-CIEUC C094 D553 # HANGUL SYLLABLE PHIEUPH-I-CHIEUCH C095 D554 # HANGUL SYLLABLE PHIEUPH-I-KHIEUKH C096 D555 # HANGUL SYLLABLE PHIEUPH-I-THIEUTH C097 D556 # HANGUL SYLLABLE PHIEUPH-I-PHIEUPH C098 D557 # HANGUL SYLLABLE PHIEUPH-I-HIEUH C099 D55A # HANGUL SYLLABLE HIEUH-A-SSANGKIYEOK C09A D55B # HANGUL SYLLABLE HIEUH-A-KIYEOKSIOS C09B D55D # HANGUL SYLLABLE HIEUH-A-NIEUNCIEUC C09C D55E # HANGUL SYLLABLE HIEUH-A-NIEUNHIEUH C09D D55F # HANGUL SYLLABLE HIEUH-A-TIKEUT C09E D561 # HANGUL SYLLABLE HIEUH-A-RIEULKIYEOK C09F D562 # HANGUL SYLLABLE HIEUH-A-RIEULMIEUM C0A0 D563 # HANGUL SYLLABLE HIEUH-A-RIEULPIEUP C0A1 C6E9 # HANGUL SYLLABLE IEUNG-WE-KIYEOK C0A2 C6EC # HANGUL SYLLABLE IEUNG-WE-NIEUN C0A3 C6F0 # HANGUL SYLLABLE IEUNG-WE-RIEUL C0A4 C6F8 # HANGUL SYLLABLE IEUNG-WE-MIEUM C0A5 C6F9 # HANGUL SYLLABLE IEUNG-WE-PIEUP C0A6 C6FD # HANGUL SYLLABLE IEUNG-WE-IEUNG C0A7 C704 # HANGUL SYLLABLE IEUNG-WI C0A8 C705 # HANGUL SYLLABLE IEUNG-WI-KIYEOK C0A9 C708 # HANGUL SYLLABLE IEUNG-WI-NIEUN C0AA C70C # HANGUL SYLLABLE IEUNG-WI-RIEUL C0AB C714 # HANGUL SYLLABLE IEUNG-WI-MIEUM C0AC C715 # HANGUL SYLLABLE IEUNG-WI-PIEUP C0AD C717 # HANGUL SYLLABLE IEUNG-WI-SIOS C0AE C719 # HANGUL SYLLABLE IEUNG-WI-IEUNG C0AF C720 # HANGUL SYLLABLE IEUNG-YU C0B0 C721 # HANGUL SYLLABLE IEUNG-YU-KIYEOK C0B1 C724 # HANGUL SYLLABLE IEUNG-YU-NIEUN C0B2 C728 # HANGUL SYLLABLE IEUNG-YU-RIEUL C0B3 C730 # HANGUL SYLLABLE IEUNG-YU-MIEUM C0B4 C731 # HANGUL SYLLABLE IEUNG-YU-PIEUP C0B5 C733 # HANGUL SYLLABLE IEUNG-YU-SIOS C0B6 C735 # HANGUL SYLLABLE IEUNG-YU-IEUNG C0B7 C737 # HANGUL SYLLABLE IEUNG-YU-CHIEUCH C0B8 C73C # HANGUL SYLLABLE IEUNG-EU C0B9 C73D # HANGUL SYLLABLE IEUNG-EU-KIYEOK C0BA C740 # HANGUL SYLLABLE IEUNG-EU-NIEUN C0BB C744 # HANGUL SYLLABLE IEUNG-EU-RIEUL C0BC C74A # HANGUL SYLLABLE IEUNG-EU-RIEULPHIEUPH C0BD C74C # HANGUL SYLLABLE IEUNG-EU-MIEUM C0BE C74D # HANGUL SYLLABLE IEUNG-EU-PIEUP C0BF C74F # HANGUL SYLLABLE IEUNG-EU-SIOS C0C0 C751 # HANGUL SYLLABLE IEUNG-EU-IEUNG C0C1 C752 # HANGUL SYLLABLE IEUNG-EU-CIEUC C0C2 C753 # HANGUL SYLLABLE IEUNG-EU-CHIEUCH C0C3 C754 # HANGUL SYLLABLE IEUNG-EU-KHIEUKH C0C4 C755 # HANGUL SYLLABLE IEUNG-EU-THIEUTH C0C5 C756 # HANGUL SYLLABLE IEUNG-EU-PHIEUPH C0C6 C757 # HANGUL SYLLABLE IEUNG-EU-HIEUH C0C7 C758 # HANGUL SYLLABLE IEUNG-YI C0C8 C75C # HANGUL SYLLABLE IEUNG-YI-NIEUN C0C9 C760 # HANGUL SYLLABLE IEUNG-YI-RIEUL C0CA C768 # HANGUL SYLLABLE IEUNG-YI-MIEUM C0CB C76B # HANGUL SYLLABLE IEUNG-YI-SIOS C0CC C774 # HANGUL SYLLABLE IEUNG-I C0CD C775 # HANGUL SYLLABLE IEUNG-I-KIYEOK C0CE C778 # HANGUL SYLLABLE IEUNG-I-NIEUN C0CF C77C # HANGUL SYLLABLE IEUNG-I-RIEUL C0D0 C77D # HANGUL SYLLABLE IEUNG-I-RIEULKIYEOK C0D1 C77E # HANGUL SYLLABLE IEUNG-I-RIEULMIEUM C0D2 C783 # HANGUL SYLLABLE IEUNG-I-RIEULHIEUH C0D3 C784 # HANGUL SYLLABLE IEUNG-I-MIEUM C0D4 C785 # HANGUL SYLLABLE IEUNG-I-PIEUP C0D5 C787 # HANGUL SYLLABLE IEUNG-I-SIOS C0D6 C788 # HANGUL SYLLABLE IEUNG-I-SSANGSIOS C0D7 C789 # HANGUL SYLLABLE IEUNG-I-IEUNG C0D8 C78A # HANGUL SYLLABLE IEUNG-I-CIEUC C0D9 C78E # HANGUL SYLLABLE IEUNG-I-PHIEUPH C0DA C790 # HANGUL SYLLABLE CIEUC-A C0DB C791 # HANGUL SYLLABLE CIEUC-A-KIYEOK C0DC C794 # HANGUL SYLLABLE CIEUC-A-NIEUN C0DD C796 # HANGUL SYLLABLE CIEUC-A-NIEUNHIEUH C0DE C797 # HANGUL SYLLABLE CIEUC-A-TIKEUT C0DF C798 # HANGUL SYLLABLE CIEUC-A-RIEUL C0E0 C79A # HANGUL SYLLABLE CIEUC-A-RIEULMIEUM C0E1 C7A0 # HANGUL SYLLABLE CIEUC-A-MIEUM C0E2 C7A1 # HANGUL SYLLABLE CIEUC-A-PIEUP C0E3 C7A3 # HANGUL SYLLABLE CIEUC-A-SIOS C0E4 C7A4 # HANGUL SYLLABLE CIEUC-A-SSANGSIOS C0E5 C7A5 # HANGUL SYLLABLE CIEUC-A-IEUNG C0E6 C7A6 # HANGUL SYLLABLE CIEUC-A-CIEUC C0E7 C7AC # HANGUL SYLLABLE CIEUC-AE C0E8 C7AD # HANGUL SYLLABLE CIEUC-AE-KIYEOK C0E9 C7B0 # HANGUL SYLLABLE CIEUC-AE-NIEUN C0EA C7B4 # HANGUL SYLLABLE CIEUC-AE-RIEUL C0EB C7BC # HANGUL SYLLABLE CIEUC-AE-MIEUM C0EC C7BD # HANGUL SYLLABLE CIEUC-AE-PIEUP C0ED C7BF # HANGUL SYLLABLE CIEUC-AE-SIOS C0EE C7C0 # HANGUL SYLLABLE CIEUC-AE-SSANGSIOS C0EF C7C1 # HANGUL SYLLABLE CIEUC-AE-IEUNG C0F0 C7C8 # HANGUL SYLLABLE CIEUC-YA C0F1 C7C9 # HANGUL SYLLABLE CIEUC-YA-KIYEOK C0F2 C7CC # HANGUL SYLLABLE CIEUC-YA-NIEUN C0F3 C7CE # HANGUL SYLLABLE CIEUC-YA-NIEUNHIEUH C0F4 C7D0 # HANGUL SYLLABLE CIEUC-YA-RIEUL C0F5 C7D8 # HANGUL SYLLABLE CIEUC-YA-MIEUM C0F6 C7DD # HANGUL SYLLABLE CIEUC-YA-IEUNG C0F7 C7E4 # HANGUL SYLLABLE CIEUC-YAE C0F8 C7E8 # HANGUL SYLLABLE CIEUC-YAE-NIEUN C0F9 C7EC # HANGUL SYLLABLE CIEUC-YAE-RIEUL C0FA C800 # HANGUL SYLLABLE CIEUC-EO C0FB C801 # HANGUL SYLLABLE CIEUC-EO-KIYEOK C0FC C804 # HANGUL SYLLABLE CIEUC-EO-NIEUN C0FD C808 # HANGUL SYLLABLE CIEUC-EO-RIEUL C0FE C80A # HANGUL SYLLABLE CIEUC-EO-RIEULMIEUM C141 D564 # HANGUL SYLLABLE HIEUH-A-RIEULSIOS C142 D566 # HANGUL SYLLABLE HIEUH-A-RIEULPHIEUPH C143 D567 # HANGUL SYLLABLE HIEUH-A-RIEULHIEUH C144 D56A # HANGUL SYLLABLE HIEUH-A-PIEUPSIOS C145 D56C # HANGUL SYLLABLE HIEUH-A-SSANGSIOS C146 D56E # HANGUL SYLLABLE HIEUH-A-CIEUC C147 D56F # HANGUL SYLLABLE HIEUH-A-CHIEUCH C148 D570 # HANGUL SYLLABLE HIEUH-A-KHIEUKH C149 D571 # HANGUL SYLLABLE HIEUH-A-THIEUTH C14A D572 # HANGUL SYLLABLE HIEUH-A-PHIEUPH C14B D573 # HANGUL SYLLABLE HIEUH-A-HIEUH C14C D576 # HANGUL SYLLABLE HIEUH-AE-SSANGKIYEOK C14D D577 # HANGUL SYLLABLE HIEUH-AE-KIYEOKSIOS C14E D579 # HANGUL SYLLABLE HIEUH-AE-NIEUNCIEUC C14F D57A # HANGUL SYLLABLE HIEUH-AE-NIEUNHIEUH C150 D57B # HANGUL SYLLABLE HIEUH-AE-TIKEUT C151 D57D # HANGUL SYLLABLE HIEUH-AE-RIEULKIYEOK C152 D57E # HANGUL SYLLABLE HIEUH-AE-RIEULMIEUM C153 D57F # HANGUL SYLLABLE HIEUH-AE-RIEULPIEUP C154 D580 # HANGUL SYLLABLE HIEUH-AE-RIEULSIOS C155 D581 # HANGUL SYLLABLE HIEUH-AE-RIEULTHIEUTH C156 D582 # HANGUL SYLLABLE HIEUH-AE-RIEULPHIEUPH C157 D583 # HANGUL SYLLABLE HIEUH-AE-RIEULHIEUH C158 D586 # HANGUL SYLLABLE HIEUH-AE-PIEUPSIOS C159 D58A # HANGUL SYLLABLE HIEUH-AE-CIEUC C15A D58B # HANGUL SYLLABLE HIEUH-AE-CHIEUCH C161 D58C # HANGUL SYLLABLE HIEUH-AE-KHIEUKH C162 D58D # HANGUL SYLLABLE HIEUH-AE-THIEUTH C163 D58E # HANGUL SYLLABLE HIEUH-AE-PHIEUPH C164 D58F # HANGUL SYLLABLE HIEUH-AE-HIEUH C165 D591 # HANGUL SYLLABLE HIEUH-YA-KIYEOK C166 D592 # HANGUL SYLLABLE HIEUH-YA-SSANGKIYEOK C167 D593 # HANGUL SYLLABLE HIEUH-YA-KIYEOKSIOS C168 D594 # HANGUL SYLLABLE HIEUH-YA-NIEUN C169 D595 # HANGUL SYLLABLE HIEUH-YA-NIEUNCIEUC C16A D596 # HANGUL SYLLABLE HIEUH-YA-NIEUNHIEUH C16B D597 # HANGUL SYLLABLE HIEUH-YA-TIKEUT C16C D598 # HANGUL SYLLABLE HIEUH-YA-RIEUL C16D D599 # HANGUL SYLLABLE HIEUH-YA-RIEULKIYEOK C16E D59A # HANGUL SYLLABLE HIEUH-YA-RIEULMIEUM C16F D59B # HANGUL SYLLABLE HIEUH-YA-RIEULPIEUP C170 D59C # HANGUL SYLLABLE HIEUH-YA-RIEULSIOS C171 D59D # HANGUL SYLLABLE HIEUH-YA-RIEULTHIEUTH C172 D59E # HANGUL SYLLABLE HIEUH-YA-RIEULPHIEUPH C173 D59F # HANGUL SYLLABLE HIEUH-YA-RIEULHIEUH C174 D5A0 # HANGUL SYLLABLE HIEUH-YA-MIEUM C175 D5A1 # HANGUL SYLLABLE HIEUH-YA-PIEUP C176 D5A2 # HANGUL SYLLABLE HIEUH-YA-PIEUPSIOS C177 D5A3 # HANGUL SYLLABLE HIEUH-YA-SIOS C178 D5A4 # HANGUL SYLLABLE HIEUH-YA-SSANGSIOS C179 D5A6 # HANGUL SYLLABLE HIEUH-YA-CIEUC C17A D5A7 # HANGUL SYLLABLE HIEUH-YA-CHIEUCH C181 D5A8 # HANGUL SYLLABLE HIEUH-YA-KHIEUKH C182 D5A9 # HANGUL SYLLABLE HIEUH-YA-THIEUTH C183 D5AA # HANGUL SYLLABLE HIEUH-YA-PHIEUPH C184 D5AB # HANGUL SYLLABLE HIEUH-YA-HIEUH C185 D5AC # HANGUL SYLLABLE HIEUH-YAE C186 D5AD # HANGUL SYLLABLE HIEUH-YAE-KIYEOK C187 D5AE # HANGUL SYLLABLE HIEUH-YAE-SSANGKIYEOK C188 D5AF # HANGUL SYLLABLE HIEUH-YAE-KIYEOKSIOS C189 D5B0 # HANGUL SYLLABLE HIEUH-YAE-NIEUN C18A D5B1 # HANGUL SYLLABLE HIEUH-YAE-NIEUNCIEUC C18B D5B2 # HANGUL SYLLABLE HIEUH-YAE-NIEUNHIEUH C18C D5B3 # HANGUL SYLLABLE HIEUH-YAE-TIKEUT C18D D5B4 # HANGUL SYLLABLE HIEUH-YAE-RIEUL C18E D5B5 # HANGUL SYLLABLE HIEUH-YAE-RIEULKIYEOK C18F D5B6 # HANGUL SYLLABLE HIEUH-YAE-RIEULMIEUM C190 D5B7 # HANGUL SYLLABLE HIEUH-YAE-RIEULPIEUP C191 D5B8 # HANGUL SYLLABLE HIEUH-YAE-RIEULSIOS C192 D5B9 # HANGUL SYLLABLE HIEUH-YAE-RIEULTHIEUTH C193 D5BA # HANGUL SYLLABLE HIEUH-YAE-RIEULPHIEUPH C194 D5BB # HANGUL SYLLABLE HIEUH-YAE-RIEULHIEUH C195 D5BC # HANGUL SYLLABLE HIEUH-YAE-MIEUM C196 D5BD # HANGUL SYLLABLE HIEUH-YAE-PIEUP C197 D5BE # HANGUL SYLLABLE HIEUH-YAE-PIEUPSIOS C198 D5BF # HANGUL SYLLABLE HIEUH-YAE-SIOS C199 D5C0 # HANGUL SYLLABLE HIEUH-YAE-SSANGSIOS C19A D5C1 # HANGUL SYLLABLE HIEUH-YAE-IEUNG C19B D5C2 # HANGUL SYLLABLE HIEUH-YAE-CIEUC C19C D5C3 # HANGUL SYLLABLE HIEUH-YAE-CHIEUCH C19D D5C4 # HANGUL SYLLABLE HIEUH-YAE-KHIEUKH C19E D5C5 # HANGUL SYLLABLE HIEUH-YAE-THIEUTH C19F D5C6 # HANGUL SYLLABLE HIEUH-YAE-PHIEUPH C1A0 D5C7 # HANGUL SYLLABLE HIEUH-YAE-HIEUH C1A1 C810 # HANGUL SYLLABLE CIEUC-EO-MIEUM C1A2 C811 # HANGUL SYLLABLE CIEUC-EO-PIEUP C1A3 C813 # HANGUL SYLLABLE CIEUC-EO-SIOS C1A4 C815 # HANGUL SYLLABLE CIEUC-EO-IEUNG C1A5 C816 # HANGUL SYLLABLE CIEUC-EO-CIEUC C1A6 C81C # HANGUL SYLLABLE CIEUC-E C1A7 C81D # HANGUL SYLLABLE CIEUC-E-KIYEOK C1A8 C820 # HANGUL SYLLABLE CIEUC-E-NIEUN C1A9 C824 # HANGUL SYLLABLE CIEUC-E-RIEUL C1AA C82C # HANGUL SYLLABLE CIEUC-E-MIEUM C1AB C82D # HANGUL SYLLABLE CIEUC-E-PIEUP C1AC C82F # HANGUL SYLLABLE CIEUC-E-SIOS C1AD C831 # HANGUL SYLLABLE CIEUC-E-IEUNG C1AE C838 # HANGUL SYLLABLE CIEUC-YEO C1AF C83C # HANGUL SYLLABLE CIEUC-YEO-NIEUN C1B0 C840 # HANGUL SYLLABLE CIEUC-YEO-RIEUL C1B1 C848 # HANGUL SYLLABLE CIEUC-YEO-MIEUM C1B2 C849 # HANGUL SYLLABLE CIEUC-YEO-PIEUP C1B3 C84C # HANGUL SYLLABLE CIEUC-YEO-SSANGSIOS C1B4 C84D # HANGUL SYLLABLE CIEUC-YEO-IEUNG C1B5 C854 # HANGUL SYLLABLE CIEUC-YE C1B6 C870 # HANGUL SYLLABLE CIEUC-O C1B7 C871 # HANGUL SYLLABLE CIEUC-O-KIYEOK C1B8 C874 # HANGUL SYLLABLE CIEUC-O-NIEUN C1B9 C878 # HANGUL SYLLABLE CIEUC-O-RIEUL C1BA C87A # HANGUL SYLLABLE CIEUC-O-RIEULMIEUM C1BB C880 # HANGUL SYLLABLE CIEUC-O-MIEUM C1BC C881 # HANGUL SYLLABLE CIEUC-O-PIEUP C1BD C883 # HANGUL SYLLABLE CIEUC-O-SIOS C1BE C885 # HANGUL SYLLABLE CIEUC-O-IEUNG C1BF C886 # HANGUL SYLLABLE CIEUC-O-CIEUC C1C0 C887 # HANGUL SYLLABLE CIEUC-O-CHIEUCH C1C1 C88B # HANGUL SYLLABLE CIEUC-O-HIEUH C1C2 C88C # HANGUL SYLLABLE CIEUC-WA C1C3 C88D # HANGUL SYLLABLE CIEUC-WA-KIYEOK C1C4 C894 # HANGUL SYLLABLE CIEUC-WA-RIEUL C1C5 C89D # HANGUL SYLLABLE CIEUC-WA-PIEUP C1C6 C89F # HANGUL SYLLABLE CIEUC-WA-SIOS C1C7 C8A1 # HANGUL SYLLABLE CIEUC-WA-IEUNG C1C8 C8A8 # HANGUL SYLLABLE CIEUC-WAE C1C9 C8BC # HANGUL SYLLABLE CIEUC-WAE-SSANGSIOS C1CA C8BD # HANGUL SYLLABLE CIEUC-WAE-IEUNG C1CB C8C4 # HANGUL SYLLABLE CIEUC-OE C1CC C8C8 # HANGUL SYLLABLE CIEUC-OE-NIEUN C1CD C8CC # HANGUL SYLLABLE CIEUC-OE-RIEUL C1CE C8D4 # HANGUL SYLLABLE CIEUC-OE-MIEUM C1CF C8D5 # HANGUL SYLLABLE CIEUC-OE-PIEUP C1D0 C8D7 # HANGUL SYLLABLE CIEUC-OE-SIOS C1D1 C8D9 # HANGUL SYLLABLE CIEUC-OE-IEUNG C1D2 C8E0 # HANGUL SYLLABLE CIEUC-YO C1D3 C8E1 # HANGUL SYLLABLE CIEUC-YO-KIYEOK C1D4 C8E4 # HANGUL SYLLABLE CIEUC-YO-NIEUN C1D5 C8F5 # HANGUL SYLLABLE CIEUC-YO-IEUNG C1D6 C8FC # HANGUL SYLLABLE CIEUC-U C1D7 C8FD # HANGUL SYLLABLE CIEUC-U-KIYEOK C1D8 C900 # HANGUL SYLLABLE CIEUC-U-NIEUN C1D9 C904 # HANGUL SYLLABLE CIEUC-U-RIEUL C1DA C905 # HANGUL SYLLABLE CIEUC-U-RIEULKIYEOK C1DB C906 # HANGUL SYLLABLE CIEUC-U-RIEULMIEUM C1DC C90C # HANGUL SYLLABLE CIEUC-U-MIEUM C1DD C90D # HANGUL SYLLABLE CIEUC-U-PIEUP C1DE C90F # HANGUL SYLLABLE CIEUC-U-SIOS C1DF C911 # HANGUL SYLLABLE CIEUC-U-IEUNG C1E0 C918 # HANGUL SYLLABLE CIEUC-WEO C1E1 C92C # HANGUL SYLLABLE CIEUC-WEO-SSANGSIOS C1E2 C934 # HANGUL SYLLABLE CIEUC-WE C1E3 C950 # HANGUL SYLLABLE CIEUC-WI C1E4 C951 # HANGUL SYLLABLE CIEUC-WI-KIYEOK C1E5 C954 # HANGUL SYLLABLE CIEUC-WI-NIEUN C1E6 C958 # HANGUL SYLLABLE CIEUC-WI-RIEUL C1E7 C960 # HANGUL SYLLABLE CIEUC-WI-MIEUM C1E8 C961 # HANGUL SYLLABLE CIEUC-WI-PIEUP C1E9 C963 # HANGUL SYLLABLE CIEUC-WI-SIOS C1EA C96C # HANGUL SYLLABLE CIEUC-YU C1EB C970 # HANGUL SYLLABLE CIEUC-YU-NIEUN C1EC C974 # HANGUL SYLLABLE CIEUC-YU-RIEUL C1ED C97C # HANGUL SYLLABLE CIEUC-YU-MIEUM C1EE C988 # HANGUL SYLLABLE CIEUC-EU C1EF C989 # HANGUL SYLLABLE CIEUC-EU-KIYEOK C1F0 C98C # HANGUL SYLLABLE CIEUC-EU-NIEUN C1F1 C990 # HANGUL SYLLABLE CIEUC-EU-RIEUL C1F2 C998 # HANGUL SYLLABLE CIEUC-EU-MIEUM C1F3 C999 # HANGUL SYLLABLE CIEUC-EU-PIEUP C1F4 C99B # HANGUL SYLLABLE CIEUC-EU-SIOS C1F5 C99D # HANGUL SYLLABLE CIEUC-EU-IEUNG C1F6 C9C0 # HANGUL SYLLABLE CIEUC-I C1F7 C9C1 # HANGUL SYLLABLE CIEUC-I-KIYEOK C1F8 C9C4 # HANGUL SYLLABLE CIEUC-I-NIEUN C1F9 C9C7 # HANGUL SYLLABLE CIEUC-I-TIKEUT C1FA C9C8 # HANGUL SYLLABLE CIEUC-I-RIEUL C1FB C9CA # HANGUL SYLLABLE CIEUC-I-RIEULMIEUM C1FC C9D0 # HANGUL SYLLABLE CIEUC-I-MIEUM C1FD C9D1 # HANGUL SYLLABLE CIEUC-I-PIEUP C1FE C9D3 # HANGUL SYLLABLE CIEUC-I-SIOS C241 D5CA # HANGUL SYLLABLE HIEUH-EO-SSANGKIYEOK C242 D5CB # HANGUL SYLLABLE HIEUH-EO-KIYEOKSIOS C243 D5CD # HANGUL SYLLABLE HIEUH-EO-NIEUNCIEUC C244 D5CE # HANGUL SYLLABLE HIEUH-EO-NIEUNHIEUH C245 D5CF # HANGUL SYLLABLE HIEUH-EO-TIKEUT C246 D5D1 # HANGUL SYLLABLE HIEUH-EO-RIEULKIYEOK C247 D5D3 # HANGUL SYLLABLE HIEUH-EO-RIEULPIEUP C248 D5D4 # HANGUL SYLLABLE HIEUH-EO-RIEULSIOS C249 D5D5 # HANGUL SYLLABLE HIEUH-EO-RIEULTHIEUTH C24A D5D6 # HANGUL SYLLABLE HIEUH-EO-RIEULPHIEUPH C24B D5D7 # HANGUL SYLLABLE HIEUH-EO-RIEULHIEUH C24C D5DA # HANGUL SYLLABLE HIEUH-EO-PIEUPSIOS C24D D5DC # HANGUL SYLLABLE HIEUH-EO-SSANGSIOS C24E D5DE # HANGUL SYLLABLE HIEUH-EO-CIEUC C24F D5DF # HANGUL SYLLABLE HIEUH-EO-CHIEUCH C250 D5E0 # HANGUL SYLLABLE HIEUH-EO-KHIEUKH C251 D5E1 # HANGUL SYLLABLE HIEUH-EO-THIEUTH C252 D5E2 # HANGUL SYLLABLE HIEUH-EO-PHIEUPH C253 D5E3 # HANGUL SYLLABLE HIEUH-EO-HIEUH C254 D5E6 # HANGUL SYLLABLE HIEUH-E-SSANGKIYEOK C255 D5E7 # HANGUL SYLLABLE HIEUH-E-KIYEOKSIOS C256 D5E9 # HANGUL SYLLABLE HIEUH-E-NIEUNCIEUC C257 D5EA # HANGUL SYLLABLE HIEUH-E-NIEUNHIEUH C258 D5EB # HANGUL SYLLABLE HIEUH-E-TIKEUT C259 D5ED # HANGUL SYLLABLE HIEUH-E-RIEULKIYEOK C25A D5EE # HANGUL SYLLABLE HIEUH-E-RIEULMIEUM C261 D5EF # HANGUL SYLLABLE HIEUH-E-RIEULPIEUP C262 D5F0 # HANGUL SYLLABLE HIEUH-E-RIEULSIOS C263 D5F1 # HANGUL SYLLABLE HIEUH-E-RIEULTHIEUTH C264 D5F2 # HANGUL SYLLABLE HIEUH-E-RIEULPHIEUPH C265 D5F3 # HANGUL SYLLABLE HIEUH-E-RIEULHIEUH C266 D5F6 # HANGUL SYLLABLE HIEUH-E-PIEUPSIOS C267 D5F8 # HANGUL SYLLABLE HIEUH-E-SSANGSIOS C268 D5FA # HANGUL SYLLABLE HIEUH-E-CIEUC C269 D5FB # HANGUL SYLLABLE HIEUH-E-CHIEUCH C26A D5FC # HANGUL SYLLABLE HIEUH-E-KHIEUKH C26B D5FD # HANGUL SYLLABLE HIEUH-E-THIEUTH C26C D5FE # HANGUL SYLLABLE HIEUH-E-PHIEUPH C26D D5FF # HANGUL SYLLABLE HIEUH-E-HIEUH C26E D602 # HANGUL SYLLABLE HIEUH-YEO-SSANGKIYEOK C26F D603 # HANGUL SYLLABLE HIEUH-YEO-KIYEOKSIOS C270 D605 # HANGUL SYLLABLE HIEUH-YEO-NIEUNCIEUC C271 D606 # HANGUL SYLLABLE HIEUH-YEO-NIEUNHIEUH C272 D607 # HANGUL SYLLABLE HIEUH-YEO-TIKEUT C273 D609 # HANGUL SYLLABLE HIEUH-YEO-RIEULKIYEOK C274 D60A # HANGUL SYLLABLE HIEUH-YEO-RIEULMIEUM C275 D60B # HANGUL SYLLABLE HIEUH-YEO-RIEULPIEUP C276 D60C # HANGUL SYLLABLE HIEUH-YEO-RIEULSIOS C277 D60D # HANGUL SYLLABLE HIEUH-YEO-RIEULTHIEUTH C278 D60E # HANGUL SYLLABLE HIEUH-YEO-RIEULPHIEUPH C279 D60F # HANGUL SYLLABLE HIEUH-YEO-RIEULHIEUH C27A D612 # HANGUL SYLLABLE HIEUH-YEO-PIEUPSIOS C281 D616 # HANGUL SYLLABLE HIEUH-YEO-CIEUC C282 D617 # HANGUL SYLLABLE HIEUH-YEO-CHIEUCH C283 D618 # HANGUL SYLLABLE HIEUH-YEO-KHIEUKH C284 D619 # HANGUL SYLLABLE HIEUH-YEO-THIEUTH C285 D61A # HANGUL SYLLABLE HIEUH-YEO-PHIEUPH C286 D61B # HANGUL SYLLABLE HIEUH-YEO-HIEUH C287 D61D # HANGUL SYLLABLE HIEUH-YE-KIYEOK C288 D61E # HANGUL SYLLABLE HIEUH-YE-SSANGKIYEOK C289 D61F # HANGUL SYLLABLE HIEUH-YE-KIYEOKSIOS C28A D621 # HANGUL SYLLABLE HIEUH-YE-NIEUNCIEUC C28B D622 # HANGUL SYLLABLE HIEUH-YE-NIEUNHIEUH C28C D623 # HANGUL SYLLABLE HIEUH-YE-TIKEUT C28D D625 # HANGUL SYLLABLE HIEUH-YE-RIEULKIYEOK C28E D626 # HANGUL SYLLABLE HIEUH-YE-RIEULMIEUM C28F D627 # HANGUL SYLLABLE HIEUH-YE-RIEULPIEUP C290 D628 # HANGUL SYLLABLE HIEUH-YE-RIEULSIOS C291 D629 # HANGUL SYLLABLE HIEUH-YE-RIEULTHIEUTH C292 D62A # HANGUL SYLLABLE HIEUH-YE-RIEULPHIEUPH C293 D62B # HANGUL SYLLABLE HIEUH-YE-RIEULHIEUH C294 D62C # HANGUL SYLLABLE HIEUH-YE-MIEUM C295 D62E # HANGUL SYLLABLE HIEUH-YE-PIEUPSIOS C296 D62F # HANGUL SYLLABLE HIEUH-YE-SIOS C297 D630 # HANGUL SYLLABLE HIEUH-YE-SSANGSIOS C298 D631 # HANGUL SYLLABLE HIEUH-YE-IEUNG C299 D632 # HANGUL SYLLABLE HIEUH-YE-CIEUC C29A D633 # HANGUL SYLLABLE HIEUH-YE-CHIEUCH C29B D634 # HANGUL SYLLABLE HIEUH-YE-KHIEUKH C29C D635 # HANGUL SYLLABLE HIEUH-YE-THIEUTH C29D D636 # HANGUL SYLLABLE HIEUH-YE-PHIEUPH C29E D637 # HANGUL SYLLABLE HIEUH-YE-HIEUH C29F D63A # HANGUL SYLLABLE HIEUH-O-SSANGKIYEOK C2A0 D63B # HANGUL SYLLABLE HIEUH-O-KIYEOKSIOS C2A1 C9D5 # HANGUL SYLLABLE CIEUC-I-IEUNG C2A2 C9D6 # HANGUL SYLLABLE CIEUC-I-CIEUC C2A3 C9D9 # HANGUL SYLLABLE CIEUC-I-THIEUTH C2A4 C9DA # HANGUL SYLLABLE CIEUC-I-PHIEUPH C2A5 C9DC # HANGUL SYLLABLE SSANGCIEUC-A C2A6 C9DD # HANGUL SYLLABLE SSANGCIEUC-A-KIYEOK C2A7 C9E0 # HANGUL SYLLABLE SSANGCIEUC-A-NIEUN C2A8 C9E2 # HANGUL SYLLABLE SSANGCIEUC-A-NIEUNHIEUH C2A9 C9E4 # HANGUL SYLLABLE SSANGCIEUC-A-RIEUL C2AA C9E7 # HANGUL SYLLABLE SSANGCIEUC-A-RIEULPIEUP C2AB C9EC # HANGUL SYLLABLE SSANGCIEUC-A-MIEUM C2AC C9ED # HANGUL SYLLABLE SSANGCIEUC-A-PIEUP C2AD C9EF # HANGUL SYLLABLE SSANGCIEUC-A-SIOS C2AE C9F0 # HANGUL SYLLABLE SSANGCIEUC-A-SSANGSIOS C2AF C9F1 # HANGUL SYLLABLE SSANGCIEUC-A-IEUNG C2B0 C9F8 # HANGUL SYLLABLE SSANGCIEUC-AE C2B1 C9F9 # HANGUL SYLLABLE SSANGCIEUC-AE-KIYEOK C2B2 C9FC # HANGUL SYLLABLE SSANGCIEUC-AE-NIEUN C2B3 CA00 # HANGUL SYLLABLE SSANGCIEUC-AE-RIEUL C2B4 CA08 # HANGUL SYLLABLE SSANGCIEUC-AE-MIEUM C2B5 CA09 # HANGUL SYLLABLE SSANGCIEUC-AE-PIEUP C2B6 CA0B # HANGUL SYLLABLE SSANGCIEUC-AE-SIOS C2B7 CA0C # HANGUL SYLLABLE SSANGCIEUC-AE-SSANGSIOS C2B8 CA0D # HANGUL SYLLABLE SSANGCIEUC-AE-IEUNG C2B9 CA14 # HANGUL SYLLABLE SSANGCIEUC-YA C2BA CA18 # HANGUL SYLLABLE SSANGCIEUC-YA-NIEUN C2BB CA29 # HANGUL SYLLABLE SSANGCIEUC-YA-IEUNG C2BC CA4C # HANGUL SYLLABLE SSANGCIEUC-EO C2BD CA4D # HANGUL SYLLABLE SSANGCIEUC-EO-KIYEOK C2BE CA50 # HANGUL SYLLABLE SSANGCIEUC-EO-NIEUN C2BF CA54 # HANGUL SYLLABLE SSANGCIEUC-EO-RIEUL C2C0 CA5C # HANGUL SYLLABLE SSANGCIEUC-EO-MIEUM C2C1 CA5D # HANGUL SYLLABLE SSANGCIEUC-EO-PIEUP C2C2 CA5F # HANGUL SYLLABLE SSANGCIEUC-EO-SIOS C2C3 CA60 # HANGUL SYLLABLE SSANGCIEUC-EO-SSANGSIOS C2C4 CA61 # HANGUL SYLLABLE SSANGCIEUC-EO-IEUNG C2C5 CA68 # HANGUL SYLLABLE SSANGCIEUC-E C2C6 CA7D # HANGUL SYLLABLE SSANGCIEUC-E-IEUNG C2C7 CA84 # HANGUL SYLLABLE SSANGCIEUC-YEO C2C8 CA98 # HANGUL SYLLABLE SSANGCIEUC-YEO-SSANGSIOS C2C9 CABC # HANGUL SYLLABLE SSANGCIEUC-O C2CA CABD # HANGUL SYLLABLE SSANGCIEUC-O-KIYEOK C2CB CAC0 # HANGUL SYLLABLE SSANGCIEUC-O-NIEUN C2CC CAC4 # HANGUL SYLLABLE SSANGCIEUC-O-RIEUL C2CD CACC # HANGUL SYLLABLE SSANGCIEUC-O-MIEUM C2CE CACD # HANGUL SYLLABLE SSANGCIEUC-O-PIEUP C2CF CACF # HANGUL SYLLABLE SSANGCIEUC-O-SIOS C2D0 CAD1 # HANGUL SYLLABLE SSANGCIEUC-O-IEUNG C2D1 CAD3 # HANGUL SYLLABLE SSANGCIEUC-O-CHIEUCH C2D2 CAD8 # HANGUL SYLLABLE SSANGCIEUC-WA C2D3 CAD9 # HANGUL SYLLABLE SSANGCIEUC-WA-KIYEOK C2D4 CAE0 # HANGUL SYLLABLE SSANGCIEUC-WA-RIEUL C2D5 CAEC # HANGUL SYLLABLE SSANGCIEUC-WA-SSANGSIOS C2D6 CAF4 # HANGUL SYLLABLE SSANGCIEUC-WAE C2D7 CB08 # HANGUL SYLLABLE SSANGCIEUC-WAE-SSANGSIOS C2D8 CB10 # HANGUL SYLLABLE SSANGCIEUC-OE C2D9 CB14 # HANGUL SYLLABLE SSANGCIEUC-OE-NIEUN C2DA CB18 # HANGUL SYLLABLE SSANGCIEUC-OE-RIEUL C2DB CB20 # HANGUL SYLLABLE SSANGCIEUC-OE-MIEUM C2DC CB21 # HANGUL SYLLABLE SSANGCIEUC-OE-PIEUP C2DD CB41 # HANGUL SYLLABLE SSANGCIEUC-YO-IEUNG C2DE CB48 # HANGUL SYLLABLE SSANGCIEUC-U C2DF CB49 # HANGUL SYLLABLE SSANGCIEUC-U-KIYEOK C2E0 CB4C # HANGUL SYLLABLE SSANGCIEUC-U-NIEUN C2E1 CB50 # HANGUL SYLLABLE SSANGCIEUC-U-RIEUL C2E2 CB58 # HANGUL SYLLABLE SSANGCIEUC-U-MIEUM C2E3 CB59 # HANGUL SYLLABLE SSANGCIEUC-U-PIEUP C2E4 CB5D # HANGUL SYLLABLE SSANGCIEUC-U-IEUNG C2E5 CB64 # HANGUL SYLLABLE SSANGCIEUC-WEO C2E6 CB78 # HANGUL SYLLABLE SSANGCIEUC-WEO-SSANGSIOS C2E7 CB79 # HANGUL SYLLABLE SSANGCIEUC-WEO-IEUNG C2E8 CB9C # HANGUL SYLLABLE SSANGCIEUC-WI C2E9 CBB8 # HANGUL SYLLABLE SSANGCIEUC-YU C2EA CBD4 # HANGUL SYLLABLE SSANGCIEUC-EU C2EB CBE4 # HANGUL SYLLABLE SSANGCIEUC-EU-MIEUM C2EC CBE7 # HANGUL SYLLABLE SSANGCIEUC-EU-SIOS C2ED CBE9 # HANGUL SYLLABLE SSANGCIEUC-EU-IEUNG C2EE CC0C # HANGUL SYLLABLE SSANGCIEUC-I C2EF CC0D # HANGUL SYLLABLE SSANGCIEUC-I-KIYEOK C2F0 CC10 # HANGUL SYLLABLE SSANGCIEUC-I-NIEUN C2F1 CC14 # HANGUL SYLLABLE SSANGCIEUC-I-RIEUL C2F2 CC1C # HANGUL SYLLABLE SSANGCIEUC-I-MIEUM C2F3 CC1D # HANGUL SYLLABLE SSANGCIEUC-I-PIEUP C2F4 CC21 # HANGUL SYLLABLE SSANGCIEUC-I-IEUNG C2F5 CC22 # HANGUL SYLLABLE SSANGCIEUC-I-CIEUC C2F6 CC27 # HANGUL SYLLABLE SSANGCIEUC-I-HIEUH C2F7 CC28 # HANGUL SYLLABLE CHIEUCH-A C2F8 CC29 # HANGUL SYLLABLE CHIEUCH-A-KIYEOK C2F9 CC2C # HANGUL SYLLABLE CHIEUCH-A-NIEUN C2FA CC2E # HANGUL SYLLABLE CHIEUCH-A-NIEUNHIEUH C2FB CC30 # HANGUL SYLLABLE CHIEUCH-A-RIEUL C2FC CC38 # HANGUL SYLLABLE CHIEUCH-A-MIEUM C2FD CC39 # HANGUL SYLLABLE CHIEUCH-A-PIEUP C2FE CC3B # HANGUL SYLLABLE CHIEUCH-A-SIOS C341 D63D # HANGUL SYLLABLE HIEUH-O-NIEUNCIEUC C342 D63E # HANGUL SYLLABLE HIEUH-O-NIEUNHIEUH C343 D63F # HANGUL SYLLABLE HIEUH-O-TIKEUT C344 D641 # HANGUL SYLLABLE HIEUH-O-RIEULKIYEOK C345 D642 # HANGUL SYLLABLE HIEUH-O-RIEULMIEUM C346 D643 # HANGUL SYLLABLE HIEUH-O-RIEULPIEUP C347 D644 # HANGUL SYLLABLE HIEUH-O-RIEULSIOS C348 D646 # HANGUL SYLLABLE HIEUH-O-RIEULPHIEUPH C349 D647 # HANGUL SYLLABLE HIEUH-O-RIEULHIEUH C34A D64A # HANGUL SYLLABLE HIEUH-O-PIEUPSIOS C34B D64C # HANGUL SYLLABLE HIEUH-O-SSANGSIOS C34C D64E # HANGUL SYLLABLE HIEUH-O-CIEUC C34D D64F # HANGUL SYLLABLE HIEUH-O-CHIEUCH C34E D650 # HANGUL SYLLABLE HIEUH-O-KHIEUKH C34F D652 # HANGUL SYLLABLE HIEUH-O-PHIEUPH C350 D653 # HANGUL SYLLABLE HIEUH-O-HIEUH C351 D656 # HANGUL SYLLABLE HIEUH-WA-SSANGKIYEOK C352 D657 # HANGUL SYLLABLE HIEUH-WA-KIYEOKSIOS C353 D659 # HANGUL SYLLABLE HIEUH-WA-NIEUNCIEUC C354 D65A # HANGUL SYLLABLE HIEUH-WA-NIEUNHIEUH C355 D65B # HANGUL SYLLABLE HIEUH-WA-TIKEUT C356 D65D # HANGUL SYLLABLE HIEUH-WA-RIEULKIYEOK C357 D65E # HANGUL SYLLABLE HIEUH-WA-RIEULMIEUM C358 D65F # HANGUL SYLLABLE HIEUH-WA-RIEULPIEUP C359 D660 # HANGUL SYLLABLE HIEUH-WA-RIEULSIOS C35A D661 # HANGUL SYLLABLE HIEUH-WA-RIEULTHIEUTH C361 D662 # HANGUL SYLLABLE HIEUH-WA-RIEULPHIEUPH C362 D663 # HANGUL SYLLABLE HIEUH-WA-RIEULHIEUH C363 D664 # HANGUL SYLLABLE HIEUH-WA-MIEUM C364 D665 # HANGUL SYLLABLE HIEUH-WA-PIEUP C365 D666 # HANGUL SYLLABLE HIEUH-WA-PIEUPSIOS C366 D668 # HANGUL SYLLABLE HIEUH-WA-SSANGSIOS C367 D66A # HANGUL SYLLABLE HIEUH-WA-CIEUC C368 D66B # HANGUL SYLLABLE HIEUH-WA-CHIEUCH C369 D66C # HANGUL SYLLABLE HIEUH-WA-KHIEUKH C36A D66D # HANGUL SYLLABLE HIEUH-WA-THIEUTH C36B D66E # HANGUL SYLLABLE HIEUH-WA-PHIEUPH C36C D66F # HANGUL SYLLABLE HIEUH-WA-HIEUH C36D D672 # HANGUL SYLLABLE HIEUH-WAE-SSANGKIYEOK C36E D673 # HANGUL SYLLABLE HIEUH-WAE-KIYEOKSIOS C36F D675 # HANGUL SYLLABLE HIEUH-WAE-NIEUNCIEUC C370 D676 # HANGUL SYLLABLE HIEUH-WAE-NIEUNHIEUH C371 D677 # HANGUL SYLLABLE HIEUH-WAE-TIKEUT C372 D678 # HANGUL SYLLABLE HIEUH-WAE-RIEUL C373 D679 # HANGUL SYLLABLE HIEUH-WAE-RIEULKIYEOK C374 D67A # HANGUL SYLLABLE HIEUH-WAE-RIEULMIEUM C375 D67B # HANGUL SYLLABLE HIEUH-WAE-RIEULPIEUP C376 D67C # HANGUL SYLLABLE HIEUH-WAE-RIEULSIOS C377 D67D # HANGUL SYLLABLE HIEUH-WAE-RIEULTHIEUTH C378 D67E # HANGUL SYLLABLE HIEUH-WAE-RIEULPHIEUPH C379 D67F # HANGUL SYLLABLE HIEUH-WAE-RIEULHIEUH C37A D680 # HANGUL SYLLABLE HIEUH-WAE-MIEUM C381 D681 # HANGUL SYLLABLE HIEUH-WAE-PIEUP C382 D682 # HANGUL SYLLABLE HIEUH-WAE-PIEUPSIOS C383 D684 # HANGUL SYLLABLE HIEUH-WAE-SSANGSIOS C384 D686 # HANGUL SYLLABLE HIEUH-WAE-CIEUC C385 D687 # HANGUL SYLLABLE HIEUH-WAE-CHIEUCH C386 D688 # HANGUL SYLLABLE HIEUH-WAE-KHIEUKH C387 D689 # HANGUL SYLLABLE HIEUH-WAE-THIEUTH C388 D68A # HANGUL SYLLABLE HIEUH-WAE-PHIEUPH C389 D68B # HANGUL SYLLABLE HIEUH-WAE-HIEUH C38A D68E # HANGUL SYLLABLE HIEUH-OE-SSANGKIYEOK C38B D68F # HANGUL SYLLABLE HIEUH-OE-KIYEOKSIOS C38C D691 # HANGUL SYLLABLE HIEUH-OE-NIEUNCIEUC C38D D692 # HANGUL SYLLABLE HIEUH-OE-NIEUNHIEUH C38E D693 # HANGUL SYLLABLE HIEUH-OE-TIKEUT C38F D695 # HANGUL SYLLABLE HIEUH-OE-RIEULKIYEOK C390 D696 # HANGUL SYLLABLE HIEUH-OE-RIEULMIEUM C391 D697 # HANGUL SYLLABLE HIEUH-OE-RIEULPIEUP C392 D698 # HANGUL SYLLABLE HIEUH-OE-RIEULSIOS C393 D699 # HANGUL SYLLABLE HIEUH-OE-RIEULTHIEUTH C394 D69A # HANGUL SYLLABLE HIEUH-OE-RIEULPHIEUPH C395 D69B # HANGUL SYLLABLE HIEUH-OE-RIEULHIEUH C396 D69C # HANGUL SYLLABLE HIEUH-OE-MIEUM C397 D69E # HANGUL SYLLABLE HIEUH-OE-PIEUPSIOS C398 D6A0 # HANGUL SYLLABLE HIEUH-OE-SSANGSIOS C399 D6A2 # HANGUL SYLLABLE HIEUH-OE-CIEUC C39A D6A3 # HANGUL SYLLABLE HIEUH-OE-CHIEUCH C39B D6A4 # HANGUL SYLLABLE HIEUH-OE-KHIEUKH C39C D6A5 # HANGUL SYLLABLE HIEUH-OE-THIEUTH C39D D6A6 # HANGUL SYLLABLE HIEUH-OE-PHIEUPH C39E D6A7 # HANGUL SYLLABLE HIEUH-OE-HIEUH C39F D6A9 # HANGUL SYLLABLE HIEUH-YO-KIYEOK C3A0 D6AA # HANGUL SYLLABLE HIEUH-YO-SSANGKIYEOK C3A1 CC3C # HANGUL SYLLABLE CHIEUCH-A-SSANGSIOS C3A2 CC3D # HANGUL SYLLABLE CHIEUCH-A-IEUNG C3A3 CC3E # HANGUL SYLLABLE CHIEUCH-A-CIEUC C3A4 CC44 # HANGUL SYLLABLE CHIEUCH-AE C3A5 CC45 # HANGUL SYLLABLE CHIEUCH-AE-KIYEOK C3A6 CC48 # HANGUL SYLLABLE CHIEUCH-AE-NIEUN C3A7 CC4C # HANGUL SYLLABLE CHIEUCH-AE-RIEUL C3A8 CC54 # HANGUL SYLLABLE CHIEUCH-AE-MIEUM C3A9 CC55 # HANGUL SYLLABLE CHIEUCH-AE-PIEUP C3AA CC57 # HANGUL SYLLABLE CHIEUCH-AE-SIOS C3AB CC58 # HANGUL SYLLABLE CHIEUCH-AE-SSANGSIOS C3AC CC59 # HANGUL SYLLABLE CHIEUCH-AE-IEUNG C3AD CC60 # HANGUL SYLLABLE CHIEUCH-YA C3AE CC64 # HANGUL SYLLABLE CHIEUCH-YA-NIEUN C3AF CC66 # HANGUL SYLLABLE CHIEUCH-YA-NIEUNHIEUH C3B0 CC68 # HANGUL SYLLABLE CHIEUCH-YA-RIEUL C3B1 CC70 # HANGUL SYLLABLE CHIEUCH-YA-MIEUM C3B2 CC75 # HANGUL SYLLABLE CHIEUCH-YA-IEUNG C3B3 CC98 # HANGUL SYLLABLE CHIEUCH-EO C3B4 CC99 # HANGUL SYLLABLE CHIEUCH-EO-KIYEOK C3B5 CC9C # HANGUL SYLLABLE CHIEUCH-EO-NIEUN C3B6 CCA0 # HANGUL SYLLABLE CHIEUCH-EO-RIEUL C3B7 CCA8 # HANGUL SYLLABLE CHIEUCH-EO-MIEUM C3B8 CCA9 # HANGUL SYLLABLE CHIEUCH-EO-PIEUP C3B9 CCAB # HANGUL SYLLABLE CHIEUCH-EO-SIOS C3BA CCAC # HANGUL SYLLABLE CHIEUCH-EO-SSANGSIOS C3BB CCAD # HANGUL SYLLABLE CHIEUCH-EO-IEUNG C3BC CCB4 # HANGUL SYLLABLE CHIEUCH-E C3BD CCB5 # HANGUL SYLLABLE CHIEUCH-E-KIYEOK C3BE CCB8 # HANGUL SYLLABLE CHIEUCH-E-NIEUN C3BF CCBC # HANGUL SYLLABLE CHIEUCH-E-RIEUL C3C0 CCC4 # HANGUL SYLLABLE CHIEUCH-E-MIEUM C3C1 CCC5 # HANGUL SYLLABLE CHIEUCH-E-PIEUP C3C2 CCC7 # HANGUL SYLLABLE CHIEUCH-E-SIOS C3C3 CCC9 # HANGUL SYLLABLE CHIEUCH-E-IEUNG C3C4 CCD0 # HANGUL SYLLABLE CHIEUCH-YEO C3C5 CCD4 # HANGUL SYLLABLE CHIEUCH-YEO-NIEUN C3C6 CCE4 # HANGUL SYLLABLE CHIEUCH-YEO-SSANGSIOS C3C7 CCEC # HANGUL SYLLABLE CHIEUCH-YE C3C8 CCF0 # HANGUL SYLLABLE CHIEUCH-YE-NIEUN C3C9 CD01 # HANGUL SYLLABLE CHIEUCH-YE-IEUNG C3CA CD08 # HANGUL SYLLABLE CHIEUCH-O C3CB CD09 # HANGUL SYLLABLE CHIEUCH-O-KIYEOK C3CC CD0C # HANGUL SYLLABLE CHIEUCH-O-NIEUN C3CD CD10 # HANGUL SYLLABLE CHIEUCH-O-RIEUL C3CE CD18 # HANGUL SYLLABLE CHIEUCH-O-MIEUM C3CF CD19 # HANGUL SYLLABLE CHIEUCH-O-PIEUP C3D0 CD1B # HANGUL SYLLABLE CHIEUCH-O-SIOS C3D1 CD1D # HANGUL SYLLABLE CHIEUCH-O-IEUNG C3D2 CD24 # HANGUL SYLLABLE CHIEUCH-WA C3D3 CD28 # HANGUL SYLLABLE CHIEUCH-WA-NIEUN C3D4 CD2C # HANGUL SYLLABLE CHIEUCH-WA-RIEUL C3D5 CD39 # HANGUL SYLLABLE CHIEUCH-WA-IEUNG C3D6 CD5C # HANGUL SYLLABLE CHIEUCH-OE C3D7 CD60 # HANGUL SYLLABLE CHIEUCH-OE-NIEUN C3D8 CD64 # HANGUL SYLLABLE CHIEUCH-OE-RIEUL C3D9 CD6C # HANGUL SYLLABLE CHIEUCH-OE-MIEUM C3DA CD6D # HANGUL SYLLABLE CHIEUCH-OE-PIEUP C3DB CD6F # HANGUL SYLLABLE CHIEUCH-OE-SIOS C3DC CD71 # HANGUL SYLLABLE CHIEUCH-OE-IEUNG C3DD CD78 # HANGUL SYLLABLE CHIEUCH-YO C3DE CD88 # HANGUL SYLLABLE CHIEUCH-YO-MIEUM C3DF CD94 # HANGUL SYLLABLE CHIEUCH-U C3E0 CD95 # HANGUL SYLLABLE CHIEUCH-U-KIYEOK C3E1 CD98 # HANGUL SYLLABLE CHIEUCH-U-NIEUN C3E2 CD9C # HANGUL SYLLABLE CHIEUCH-U-RIEUL C3E3 CDA4 # HANGUL SYLLABLE CHIEUCH-U-MIEUM C3E4 CDA5 # HANGUL SYLLABLE CHIEUCH-U-PIEUP C3E5 CDA7 # HANGUL SYLLABLE CHIEUCH-U-SIOS C3E6 CDA9 # HANGUL SYLLABLE CHIEUCH-U-IEUNG C3E7 CDB0 # HANGUL SYLLABLE CHIEUCH-WEO C3E8 CDC4 # HANGUL SYLLABLE CHIEUCH-WEO-SSANGSIOS C3E9 CDCC # HANGUL SYLLABLE CHIEUCH-WE C3EA CDD0 # HANGUL SYLLABLE CHIEUCH-WE-NIEUN C3EB CDE8 # HANGUL SYLLABLE CHIEUCH-WI C3EC CDEC # HANGUL SYLLABLE CHIEUCH-WI-NIEUN C3ED CDF0 # HANGUL SYLLABLE CHIEUCH-WI-RIEUL C3EE CDF8 # HANGUL SYLLABLE CHIEUCH-WI-MIEUM C3EF CDF9 # HANGUL SYLLABLE CHIEUCH-WI-PIEUP C3F0 CDFB # HANGUL SYLLABLE CHIEUCH-WI-SIOS C3F1 CDFD # HANGUL SYLLABLE CHIEUCH-WI-IEUNG C3F2 CE04 # HANGUL SYLLABLE CHIEUCH-YU C3F3 CE08 # HANGUL SYLLABLE CHIEUCH-YU-NIEUN C3F4 CE0C # HANGUL SYLLABLE CHIEUCH-YU-RIEUL C3F5 CE14 # HANGUL SYLLABLE CHIEUCH-YU-MIEUM C3F6 CE19 # HANGUL SYLLABLE CHIEUCH-YU-IEUNG C3F7 CE20 # HANGUL SYLLABLE CHIEUCH-EU C3F8 CE21 # HANGUL SYLLABLE CHIEUCH-EU-KIYEOK C3F9 CE24 # HANGUL SYLLABLE CHIEUCH-EU-NIEUN C3FA CE28 # HANGUL SYLLABLE CHIEUCH-EU-RIEUL C3FB CE30 # HANGUL SYLLABLE CHIEUCH-EU-MIEUM C3FC CE31 # HANGUL SYLLABLE CHIEUCH-EU-PIEUP C3FD CE33 # HANGUL SYLLABLE CHIEUCH-EU-SIOS C3FE CE35 # HANGUL SYLLABLE CHIEUCH-EU-IEUNG C441 D6AB # HANGUL SYLLABLE HIEUH-YO-KIYEOKSIOS C442 D6AD # HANGUL SYLLABLE HIEUH-YO-NIEUNCIEUC C443 D6AE # HANGUL SYLLABLE HIEUH-YO-NIEUNHIEUH C444 D6AF # HANGUL SYLLABLE HIEUH-YO-TIKEUT C445 D6B1 # HANGUL SYLLABLE HIEUH-YO-RIEULKIYEOK C446 D6B2 # HANGUL SYLLABLE HIEUH-YO-RIEULMIEUM C447 D6B3 # HANGUL SYLLABLE HIEUH-YO-RIEULPIEUP C448 D6B4 # HANGUL SYLLABLE HIEUH-YO-RIEULSIOS C449 D6B5 # HANGUL SYLLABLE HIEUH-YO-RIEULTHIEUTH C44A D6B6 # HANGUL SYLLABLE HIEUH-YO-RIEULPHIEUPH C44B D6B7 # HANGUL SYLLABLE HIEUH-YO-RIEULHIEUH C44C D6B8 # HANGUL SYLLABLE HIEUH-YO-MIEUM C44D D6BA # HANGUL SYLLABLE HIEUH-YO-PIEUPSIOS C44E D6BC # HANGUL SYLLABLE HIEUH-YO-SSANGSIOS C44F D6BD # HANGUL SYLLABLE HIEUH-YO-IEUNG C450 D6BE # HANGUL SYLLABLE HIEUH-YO-CIEUC C451 D6BF # HANGUL SYLLABLE HIEUH-YO-CHIEUCH C452 D6C0 # HANGUL SYLLABLE HIEUH-YO-KHIEUKH C453 D6C1 # HANGUL SYLLABLE HIEUH-YO-THIEUTH C454 D6C2 # HANGUL SYLLABLE HIEUH-YO-PHIEUPH C455 D6C3 # HANGUL SYLLABLE HIEUH-YO-HIEUH C456 D6C6 # HANGUL SYLLABLE HIEUH-U-SSANGKIYEOK C457 D6C7 # HANGUL SYLLABLE HIEUH-U-KIYEOKSIOS C458 D6C9 # HANGUL SYLLABLE HIEUH-U-NIEUNCIEUC C459 D6CA # HANGUL SYLLABLE HIEUH-U-NIEUNHIEUH C45A D6CB # HANGUL SYLLABLE HIEUH-U-TIKEUT C461 D6CD # HANGUL SYLLABLE HIEUH-U-RIEULKIYEOK C462 D6CE # HANGUL SYLLABLE HIEUH-U-RIEULMIEUM C463 D6CF # HANGUL SYLLABLE HIEUH-U-RIEULPIEUP C464 D6D0 # HANGUL SYLLABLE HIEUH-U-RIEULSIOS C465 D6D2 # HANGUL SYLLABLE HIEUH-U-RIEULPHIEUPH C466 D6D3 # HANGUL SYLLABLE HIEUH-U-RIEULHIEUH C467 D6D5 # HANGUL SYLLABLE HIEUH-U-PIEUP C468 D6D6 # HANGUL SYLLABLE HIEUH-U-PIEUPSIOS C469 D6D8 # HANGUL SYLLABLE HIEUH-U-SSANGSIOS C46A D6DA # HANGUL SYLLABLE HIEUH-U-CIEUC C46B D6DB # HANGUL SYLLABLE HIEUH-U-CHIEUCH C46C D6DC # HANGUL SYLLABLE HIEUH-U-KHIEUKH C46D D6DD # HANGUL SYLLABLE HIEUH-U-THIEUTH C46E D6DE # HANGUL SYLLABLE HIEUH-U-PHIEUPH C46F D6DF # HANGUL SYLLABLE HIEUH-U-HIEUH C470 D6E1 # HANGUL SYLLABLE HIEUH-WEO-KIYEOK C471 D6E2 # HANGUL SYLLABLE HIEUH-WEO-SSANGKIYEOK C472 D6E3 # HANGUL SYLLABLE HIEUH-WEO-KIYEOKSIOS C473 D6E5 # HANGUL SYLLABLE HIEUH-WEO-NIEUNCIEUC C474 D6E6 # HANGUL SYLLABLE HIEUH-WEO-NIEUNHIEUH C475 D6E7 # HANGUL SYLLABLE HIEUH-WEO-TIKEUT C476 D6E9 # HANGUL SYLLABLE HIEUH-WEO-RIEULKIYEOK C477 D6EA # HANGUL SYLLABLE HIEUH-WEO-RIEULMIEUM C478 D6EB # HANGUL SYLLABLE HIEUH-WEO-RIEULPIEUP C479 D6EC # HANGUL SYLLABLE HIEUH-WEO-RIEULSIOS C47A D6ED # HANGUL SYLLABLE HIEUH-WEO-RIEULTHIEUTH C481 D6EE # HANGUL SYLLABLE HIEUH-WEO-RIEULPHIEUPH C482 D6EF # HANGUL SYLLABLE HIEUH-WEO-RIEULHIEUH C483 D6F1 # HANGUL SYLLABLE HIEUH-WEO-PIEUP C484 D6F2 # HANGUL SYLLABLE HIEUH-WEO-PIEUPSIOS C485 D6F3 # HANGUL SYLLABLE HIEUH-WEO-SIOS C486 D6F4 # HANGUL SYLLABLE HIEUH-WEO-SSANGSIOS C487 D6F6 # HANGUL SYLLABLE HIEUH-WEO-CIEUC C488 D6F7 # HANGUL SYLLABLE HIEUH-WEO-CHIEUCH C489 D6F8 # HANGUL SYLLABLE HIEUH-WEO-KHIEUKH C48A D6F9 # HANGUL SYLLABLE HIEUH-WEO-THIEUTH C48B D6FA # HANGUL SYLLABLE HIEUH-WEO-PHIEUPH C48C D6FB # HANGUL SYLLABLE HIEUH-WEO-HIEUH C48D D6FE # HANGUL SYLLABLE HIEUH-WE-SSANGKIYEOK C48E D6FF # HANGUL SYLLABLE HIEUH-WE-KIYEOKSIOS C48F D701 # HANGUL SYLLABLE HIEUH-WE-NIEUNCIEUC C490 D702 # HANGUL SYLLABLE HIEUH-WE-NIEUNHIEUH C491 D703 # HANGUL SYLLABLE HIEUH-WE-TIKEUT C492 D705 # HANGUL SYLLABLE HIEUH-WE-RIEULKIYEOK C493 D706 # HANGUL SYLLABLE HIEUH-WE-RIEULMIEUM C494 D707 # HANGUL SYLLABLE HIEUH-WE-RIEULPIEUP C495 D708 # HANGUL SYLLABLE HIEUH-WE-RIEULSIOS C496 D709 # HANGUL SYLLABLE HIEUH-WE-RIEULTHIEUTH C497 D70A # HANGUL SYLLABLE HIEUH-WE-RIEULPHIEUPH C498 D70B # HANGUL SYLLABLE HIEUH-WE-RIEULHIEUH C499 D70C # HANGUL SYLLABLE HIEUH-WE-MIEUM C49A D70D # HANGUL SYLLABLE HIEUH-WE-PIEUP C49B D70E # HANGUL SYLLABLE HIEUH-WE-PIEUPSIOS C49C D70F # HANGUL SYLLABLE HIEUH-WE-SIOS C49D D710 # HANGUL SYLLABLE HIEUH-WE-SSANGSIOS C49E D712 # HANGUL SYLLABLE HIEUH-WE-CIEUC C49F D713 # HANGUL SYLLABLE HIEUH-WE-CHIEUCH C4A0 D714 # HANGUL SYLLABLE HIEUH-WE-KHIEUKH C4A1 CE58 # HANGUL SYLLABLE CHIEUCH-I C4A2 CE59 # HANGUL SYLLABLE CHIEUCH-I-KIYEOK C4A3 CE5C # HANGUL SYLLABLE CHIEUCH-I-NIEUN C4A4 CE5F # HANGUL SYLLABLE CHIEUCH-I-TIKEUT C4A5 CE60 # HANGUL SYLLABLE CHIEUCH-I-RIEUL C4A6 CE61 # HANGUL SYLLABLE CHIEUCH-I-RIEULKIYEOK C4A7 CE68 # HANGUL SYLLABLE CHIEUCH-I-MIEUM C4A8 CE69 # HANGUL SYLLABLE CHIEUCH-I-PIEUP C4A9 CE6B # HANGUL SYLLABLE CHIEUCH-I-SIOS C4AA CE6D # HANGUL SYLLABLE CHIEUCH-I-IEUNG C4AB CE74 # HANGUL SYLLABLE KHIEUKH-A C4AC CE75 # HANGUL SYLLABLE KHIEUKH-A-KIYEOK C4AD CE78 # HANGUL SYLLABLE KHIEUKH-A-NIEUN C4AE CE7C # HANGUL SYLLABLE KHIEUKH-A-RIEUL C4AF CE84 # HANGUL SYLLABLE KHIEUKH-A-MIEUM C4B0 CE85 # HANGUL SYLLABLE KHIEUKH-A-PIEUP C4B1 CE87 # HANGUL SYLLABLE KHIEUKH-A-SIOS C4B2 CE89 # HANGUL SYLLABLE KHIEUKH-A-IEUNG C4B3 CE90 # HANGUL SYLLABLE KHIEUKH-AE C4B4 CE91 # HANGUL SYLLABLE KHIEUKH-AE-KIYEOK C4B5 CE94 # HANGUL SYLLABLE KHIEUKH-AE-NIEUN C4B6 CE98 # HANGUL SYLLABLE KHIEUKH-AE-RIEUL C4B7 CEA0 # HANGUL SYLLABLE KHIEUKH-AE-MIEUM C4B8 CEA1 # HANGUL SYLLABLE KHIEUKH-AE-PIEUP C4B9 CEA3 # HANGUL SYLLABLE KHIEUKH-AE-SIOS C4BA CEA4 # HANGUL SYLLABLE KHIEUKH-AE-SSANGSIOS C4BB CEA5 # HANGUL SYLLABLE KHIEUKH-AE-IEUNG C4BC CEAC # HANGUL SYLLABLE KHIEUKH-YA C4BD CEAD # HANGUL SYLLABLE KHIEUKH-YA-KIYEOK C4BE CEC1 # HANGUL SYLLABLE KHIEUKH-YA-IEUNG C4BF CEE4 # HANGUL SYLLABLE KHIEUKH-EO C4C0 CEE5 # HANGUL SYLLABLE KHIEUKH-EO-KIYEOK C4C1 CEE8 # HANGUL SYLLABLE KHIEUKH-EO-NIEUN C4C2 CEEB # HANGUL SYLLABLE KHIEUKH-EO-TIKEUT C4C3 CEEC # HANGUL SYLLABLE KHIEUKH-EO-RIEUL C4C4 CEF4 # HANGUL SYLLABLE KHIEUKH-EO-MIEUM C4C5 CEF5 # HANGUL SYLLABLE KHIEUKH-EO-PIEUP C4C6 CEF7 # HANGUL SYLLABLE KHIEUKH-EO-SIOS C4C7 CEF8 # HANGUL SYLLABLE KHIEUKH-EO-SSANGSIOS C4C8 CEF9 # HANGUL SYLLABLE KHIEUKH-EO-IEUNG C4C9 CF00 # HANGUL SYLLABLE KHIEUKH-E C4CA CF01 # HANGUL SYLLABLE KHIEUKH-E-KIYEOK C4CB CF04 # HANGUL SYLLABLE KHIEUKH-E-NIEUN C4CC CF08 # HANGUL SYLLABLE KHIEUKH-E-RIEUL C4CD CF10 # HANGUL SYLLABLE KHIEUKH-E-MIEUM C4CE CF11 # HANGUL SYLLABLE KHIEUKH-E-PIEUP C4CF CF13 # HANGUL SYLLABLE KHIEUKH-E-SIOS C4D0 CF15 # HANGUL SYLLABLE KHIEUKH-E-IEUNG C4D1 CF1C # HANGUL SYLLABLE KHIEUKH-YEO C4D2 CF20 # HANGUL SYLLABLE KHIEUKH-YEO-NIEUN C4D3 CF24 # HANGUL SYLLABLE KHIEUKH-YEO-RIEUL C4D4 CF2C # HANGUL SYLLABLE KHIEUKH-YEO-MIEUM C4D5 CF2D # HANGUL SYLLABLE KHIEUKH-YEO-PIEUP C4D6 CF2F # HANGUL SYLLABLE KHIEUKH-YEO-SIOS C4D7 CF30 # HANGUL SYLLABLE KHIEUKH-YEO-SSANGSIOS C4D8 CF31 # HANGUL SYLLABLE KHIEUKH-YEO-IEUNG C4D9 CF38 # HANGUL SYLLABLE KHIEUKH-YE C4DA CF54 # HANGUL SYLLABLE KHIEUKH-O C4DB CF55 # HANGUL SYLLABLE KHIEUKH-O-KIYEOK C4DC CF58 # HANGUL SYLLABLE KHIEUKH-O-NIEUN C4DD CF5C # HANGUL SYLLABLE KHIEUKH-O-RIEUL C4DE CF64 # HANGUL SYLLABLE KHIEUKH-O-MIEUM C4DF CF65 # HANGUL SYLLABLE KHIEUKH-O-PIEUP C4E0 CF67 # HANGUL SYLLABLE KHIEUKH-O-SIOS C4E1 CF69 # HANGUL SYLLABLE KHIEUKH-O-IEUNG C4E2 CF70 # HANGUL SYLLABLE KHIEUKH-WA C4E3 CF71 # HANGUL SYLLABLE KHIEUKH-WA-KIYEOK C4E4 CF74 # HANGUL SYLLABLE KHIEUKH-WA-NIEUN C4E5 CF78 # HANGUL SYLLABLE KHIEUKH-WA-RIEUL C4E6 CF80 # HANGUL SYLLABLE KHIEUKH-WA-MIEUM C4E7 CF85 # HANGUL SYLLABLE KHIEUKH-WA-IEUNG C4E8 CF8C # HANGUL SYLLABLE KHIEUKH-WAE C4E9 CFA1 # HANGUL SYLLABLE KHIEUKH-WAE-IEUNG C4EA CFA8 # HANGUL SYLLABLE KHIEUKH-OE C4EB CFB0 # HANGUL SYLLABLE KHIEUKH-OE-RIEUL C4EC CFC4 # HANGUL SYLLABLE KHIEUKH-YO C4ED CFE0 # HANGUL SYLLABLE KHIEUKH-U C4EE CFE1 # HANGUL SYLLABLE KHIEUKH-U-KIYEOK C4EF CFE4 # HANGUL SYLLABLE KHIEUKH-U-NIEUN C4F0 CFE8 # HANGUL SYLLABLE KHIEUKH-U-RIEUL C4F1 CFF0 # HANGUL SYLLABLE KHIEUKH-U-MIEUM C4F2 CFF1 # HANGUL SYLLABLE KHIEUKH-U-PIEUP C4F3 CFF3 # HANGUL SYLLABLE KHIEUKH-U-SIOS C4F4 CFF5 # HANGUL SYLLABLE KHIEUKH-U-IEUNG C4F5 CFFC # HANGUL SYLLABLE KHIEUKH-WEO C4F6 D000 # HANGUL SYLLABLE KHIEUKH-WEO-NIEUN C4F7 D004 # HANGUL SYLLABLE KHIEUKH-WEO-RIEUL C4F8 D011 # HANGUL SYLLABLE KHIEUKH-WEO-IEUNG C4F9 D018 # HANGUL SYLLABLE KHIEUKH-WE C4FA D02D # HANGUL SYLLABLE KHIEUKH-WE-IEUNG C4FB D034 # HANGUL SYLLABLE KHIEUKH-WI C4FC D035 # HANGUL SYLLABLE KHIEUKH-WI-KIYEOK C4FD D038 # HANGUL SYLLABLE KHIEUKH-WI-NIEUN C4FE D03C # HANGUL SYLLABLE KHIEUKH-WI-RIEUL C541 D715 # HANGUL SYLLABLE HIEUH-WE-THIEUTH C542 D716 # HANGUL SYLLABLE HIEUH-WE-PHIEUPH C543 D717 # HANGUL SYLLABLE HIEUH-WE-HIEUH C544 D71A # HANGUL SYLLABLE HIEUH-WI-SSANGKIYEOK C545 D71B # HANGUL SYLLABLE HIEUH-WI-KIYEOKSIOS C546 D71D # HANGUL SYLLABLE HIEUH-WI-NIEUNCIEUC C547 D71E # HANGUL SYLLABLE HIEUH-WI-NIEUNHIEUH C548 D71F # HANGUL SYLLABLE HIEUH-WI-TIKEUT C549 D721 # HANGUL SYLLABLE HIEUH-WI-RIEULKIYEOK C54A D722 # HANGUL SYLLABLE HIEUH-WI-RIEULMIEUM C54B D723 # HANGUL SYLLABLE HIEUH-WI-RIEULPIEUP C54C D724 # HANGUL SYLLABLE HIEUH-WI-RIEULSIOS C54D D725 # HANGUL SYLLABLE HIEUH-WI-RIEULTHIEUTH C54E D726 # HANGUL SYLLABLE HIEUH-WI-RIEULPHIEUPH C54F D727 # HANGUL SYLLABLE HIEUH-WI-RIEULHIEUH C550 D72A # HANGUL SYLLABLE HIEUH-WI-PIEUPSIOS C551 D72C # HANGUL SYLLABLE HIEUH-WI-SSANGSIOS C552 D72E # HANGUL SYLLABLE HIEUH-WI-CIEUC C553 D72F # HANGUL SYLLABLE HIEUH-WI-CHIEUCH C554 D730 # HANGUL SYLLABLE HIEUH-WI-KHIEUKH C555 D731 # HANGUL SYLLABLE HIEUH-WI-THIEUTH C556 D732 # HANGUL SYLLABLE HIEUH-WI-PHIEUPH C557 D733 # HANGUL SYLLABLE HIEUH-WI-HIEUH C558 D736 # HANGUL SYLLABLE HIEUH-YU-SSANGKIYEOK C559 D737 # HANGUL SYLLABLE HIEUH-YU-KIYEOKSIOS C55A D739 # HANGUL SYLLABLE HIEUH-YU-NIEUNCIEUC C561 D73A # HANGUL SYLLABLE HIEUH-YU-NIEUNHIEUH C562 D73B # HANGUL SYLLABLE HIEUH-YU-TIKEUT C563 D73D # HANGUL SYLLABLE HIEUH-YU-RIEULKIYEOK C564 D73E # HANGUL SYLLABLE HIEUH-YU-RIEULMIEUM C565 D73F # HANGUL SYLLABLE HIEUH-YU-RIEULPIEUP C566 D740 # HANGUL SYLLABLE HIEUH-YU-RIEULSIOS C567 D741 # HANGUL SYLLABLE HIEUH-YU-RIEULTHIEUTH C568 D742 # HANGUL SYLLABLE HIEUH-YU-RIEULPHIEUPH C569 D743 # HANGUL SYLLABLE HIEUH-YU-RIEULHIEUH C56A D745 # HANGUL SYLLABLE HIEUH-YU-PIEUP C56B D746 # HANGUL SYLLABLE HIEUH-YU-PIEUPSIOS C56C D748 # HANGUL SYLLABLE HIEUH-YU-SSANGSIOS C56D D74A # HANGUL SYLLABLE HIEUH-YU-CIEUC C56E D74B # HANGUL SYLLABLE HIEUH-YU-CHIEUCH C56F D74C # HANGUL SYLLABLE HIEUH-YU-KHIEUKH C570 D74D # HANGUL SYLLABLE HIEUH-YU-THIEUTH C571 D74E # HANGUL SYLLABLE HIEUH-YU-PHIEUPH C572 D74F # HANGUL SYLLABLE HIEUH-YU-HIEUH C573 D752 # HANGUL SYLLABLE HIEUH-EU-SSANGKIYEOK C574 D753 # HANGUL SYLLABLE HIEUH-EU-KIYEOKSIOS C575 D755 # HANGUL SYLLABLE HIEUH-EU-NIEUNCIEUC C576 D75A # HANGUL SYLLABLE HIEUH-EU-RIEULMIEUM C577 D75B # HANGUL SYLLABLE HIEUH-EU-RIEULPIEUP C578 D75C # HANGUL SYLLABLE HIEUH-EU-RIEULSIOS C579 D75D # HANGUL SYLLABLE HIEUH-EU-RIEULTHIEUTH C57A D75E # HANGUL SYLLABLE HIEUH-EU-RIEULPHIEUPH C581 D75F # HANGUL SYLLABLE HIEUH-EU-RIEULHIEUH C582 D762 # HANGUL SYLLABLE HIEUH-EU-PIEUPSIOS C583 D764 # HANGUL SYLLABLE HIEUH-EU-SSANGSIOS C584 D766 # HANGUL SYLLABLE HIEUH-EU-CIEUC C585 D767 # HANGUL SYLLABLE HIEUH-EU-CHIEUCH C586 D768 # HANGUL SYLLABLE HIEUH-EU-KHIEUKH C587 D76A # HANGUL SYLLABLE HIEUH-EU-PHIEUPH C588 D76B # HANGUL SYLLABLE HIEUH-EU-HIEUH C589 D76D # HANGUL SYLLABLE HIEUH-YI-KIYEOK C58A D76E # HANGUL SYLLABLE HIEUH-YI-SSANGKIYEOK C58B D76F # HANGUL SYLLABLE HIEUH-YI-KIYEOKSIOS C58C D771 # HANGUL SYLLABLE HIEUH-YI-NIEUNCIEUC C58D D772 # HANGUL SYLLABLE HIEUH-YI-NIEUNHIEUH C58E D773 # HANGUL SYLLABLE HIEUH-YI-TIKEUT C58F D775 # HANGUL SYLLABLE HIEUH-YI-RIEULKIYEOK C590 D776 # HANGUL SYLLABLE HIEUH-YI-RIEULMIEUM C591 D777 # HANGUL SYLLABLE HIEUH-YI-RIEULPIEUP C592 D778 # HANGUL SYLLABLE HIEUH-YI-RIEULSIOS C593 D779 # HANGUL SYLLABLE HIEUH-YI-RIEULTHIEUTH C594 D77A # HANGUL SYLLABLE HIEUH-YI-RIEULPHIEUPH C595 D77B # HANGUL SYLLABLE HIEUH-YI-RIEULHIEUH C596 D77E # HANGUL SYLLABLE HIEUH-YI-PIEUPSIOS C597 D77F # HANGUL SYLLABLE HIEUH-YI-SIOS C598 D780 # HANGUL SYLLABLE HIEUH-YI-SSANGSIOS C599 D782 # HANGUL SYLLABLE HIEUH-YI-CIEUC C59A D783 # HANGUL SYLLABLE HIEUH-YI-CHIEUCH C59B D784 # HANGUL SYLLABLE HIEUH-YI-KHIEUKH C59C D785 # HANGUL SYLLABLE HIEUH-YI-THIEUTH C59D D786 # HANGUL SYLLABLE HIEUH-YI-PHIEUPH C59E D787 # HANGUL SYLLABLE HIEUH-YI-HIEUH C59F D78A # HANGUL SYLLABLE HIEUH-I-SSANGKIYEOK C5A0 D78B # HANGUL SYLLABLE HIEUH-I-KIYEOKSIOS C5A1 D044 # HANGUL SYLLABLE KHIEUKH-WI-MIEUM C5A2 D045 # HANGUL SYLLABLE KHIEUKH-WI-PIEUP C5A3 D047 # HANGUL SYLLABLE KHIEUKH-WI-SIOS C5A4 D049 # HANGUL SYLLABLE KHIEUKH-WI-IEUNG C5A5 D050 # HANGUL SYLLABLE KHIEUKH-YU C5A6 D054 # HANGUL SYLLABLE KHIEUKH-YU-NIEUN C5A7 D058 # HANGUL SYLLABLE KHIEUKH-YU-RIEUL C5A8 D060 # HANGUL SYLLABLE KHIEUKH-YU-MIEUM C5A9 D06C # HANGUL SYLLABLE KHIEUKH-EU C5AA D06D # HANGUL SYLLABLE KHIEUKH-EU-KIYEOK C5AB D070 # HANGUL SYLLABLE KHIEUKH-EU-NIEUN C5AC D074 # HANGUL SYLLABLE KHIEUKH-EU-RIEUL C5AD D07C # HANGUL SYLLABLE KHIEUKH-EU-MIEUM C5AE D07D # HANGUL SYLLABLE KHIEUKH-EU-PIEUP C5AF D081 # HANGUL SYLLABLE KHIEUKH-EU-IEUNG C5B0 D0A4 # HANGUL SYLLABLE KHIEUKH-I C5B1 D0A5 # HANGUL SYLLABLE KHIEUKH-I-KIYEOK C5B2 D0A8 # HANGUL SYLLABLE KHIEUKH-I-NIEUN C5B3 D0AC # HANGUL SYLLABLE KHIEUKH-I-RIEUL C5B4 D0B4 # HANGUL SYLLABLE KHIEUKH-I-MIEUM C5B5 D0B5 # HANGUL SYLLABLE KHIEUKH-I-PIEUP C5B6 D0B7 # HANGUL SYLLABLE KHIEUKH-I-SIOS C5B7 D0B9 # HANGUL SYLLABLE KHIEUKH-I-IEUNG C5B8 D0C0 # HANGUL SYLLABLE THIEUTH-A C5B9 D0C1 # HANGUL SYLLABLE THIEUTH-A-KIYEOK C5BA D0C4 # HANGUL SYLLABLE THIEUTH-A-NIEUN C5BB D0C8 # HANGUL SYLLABLE THIEUTH-A-RIEUL C5BC D0C9 # HANGUL SYLLABLE THIEUTH-A-RIEULKIYEOK C5BD D0D0 # HANGUL SYLLABLE THIEUTH-A-MIEUM C5BE D0D1 # HANGUL SYLLABLE THIEUTH-A-PIEUP C5BF D0D3 # HANGUL SYLLABLE THIEUTH-A-SIOS C5C0 D0D4 # HANGUL SYLLABLE THIEUTH-A-SSANGSIOS C5C1 D0D5 # HANGUL SYLLABLE THIEUTH-A-IEUNG C5C2 D0DC # HANGUL SYLLABLE THIEUTH-AE C5C3 D0DD # HANGUL SYLLABLE THIEUTH-AE-KIYEOK C5C4 D0E0 # HANGUL SYLLABLE THIEUTH-AE-NIEUN C5C5 D0E4 # HANGUL SYLLABLE THIEUTH-AE-RIEUL C5C6 D0EC # HANGUL SYLLABLE THIEUTH-AE-MIEUM C5C7 D0ED # HANGUL SYLLABLE THIEUTH-AE-PIEUP C5C8 D0EF # HANGUL SYLLABLE THIEUTH-AE-SIOS C5C9 D0F0 # HANGUL SYLLABLE THIEUTH-AE-SSANGSIOS C5CA D0F1 # HANGUL SYLLABLE THIEUTH-AE-IEUNG C5CB D0F8 # HANGUL SYLLABLE THIEUTH-YA C5CC D10D # HANGUL SYLLABLE THIEUTH-YA-IEUNG C5CD D130 # HANGUL SYLLABLE THIEUTH-EO C5CE D131 # HANGUL SYLLABLE THIEUTH-EO-KIYEOK C5CF D134 # HANGUL SYLLABLE THIEUTH-EO-NIEUN C5D0 D138 # HANGUL SYLLABLE THIEUTH-EO-RIEUL C5D1 D13A # HANGUL SYLLABLE THIEUTH-EO-RIEULMIEUM C5D2 D140 # HANGUL SYLLABLE THIEUTH-EO-MIEUM C5D3 D141 # HANGUL SYLLABLE THIEUTH-EO-PIEUP C5D4 D143 # HANGUL SYLLABLE THIEUTH-EO-SIOS C5D5 D144 # HANGUL SYLLABLE THIEUTH-EO-SSANGSIOS C5D6 D145 # HANGUL SYLLABLE THIEUTH-EO-IEUNG C5D7 D14C # HANGUL SYLLABLE THIEUTH-E C5D8 D14D # HANGUL SYLLABLE THIEUTH-E-KIYEOK C5D9 D150 # HANGUL SYLLABLE THIEUTH-E-NIEUN C5DA D154 # HANGUL SYLLABLE THIEUTH-E-RIEUL C5DB D15C # HANGUL SYLLABLE THIEUTH-E-MIEUM C5DC D15D # HANGUL SYLLABLE THIEUTH-E-PIEUP C5DD D15F # HANGUL SYLLABLE THIEUTH-E-SIOS C5DE D161 # HANGUL SYLLABLE THIEUTH-E-IEUNG C5DF D168 # HANGUL SYLLABLE THIEUTH-YEO C5E0 D16C # HANGUL SYLLABLE THIEUTH-YEO-NIEUN C5E1 D17C # HANGUL SYLLABLE THIEUTH-YEO-SSANGSIOS C5E2 D184 # HANGUL SYLLABLE THIEUTH-YE C5E3 D188 # HANGUL SYLLABLE THIEUTH-YE-NIEUN C5E4 D1A0 # HANGUL SYLLABLE THIEUTH-O C5E5 D1A1 # HANGUL SYLLABLE THIEUTH-O-KIYEOK C5E6 D1A4 # HANGUL SYLLABLE THIEUTH-O-NIEUN C5E7 D1A8 # HANGUL SYLLABLE THIEUTH-O-RIEUL C5E8 D1B0 # HANGUL SYLLABLE THIEUTH-O-MIEUM C5E9 D1B1 # HANGUL SYLLABLE THIEUTH-O-PIEUP C5EA D1B3 # HANGUL SYLLABLE THIEUTH-O-SIOS C5EB D1B5 # HANGUL SYLLABLE THIEUTH-O-IEUNG C5EC D1BA # HANGUL SYLLABLE THIEUTH-O-PHIEUPH C5ED D1BC # HANGUL SYLLABLE THIEUTH-WA C5EE D1C0 # HANGUL SYLLABLE THIEUTH-WA-NIEUN C5EF D1D8 # HANGUL SYLLABLE THIEUTH-WAE C5F0 D1F4 # HANGUL SYLLABLE THIEUTH-OE C5F1 D1F8 # HANGUL SYLLABLE THIEUTH-OE-NIEUN C5F2 D207 # HANGUL SYLLABLE THIEUTH-OE-SIOS C5F3 D209 # HANGUL SYLLABLE THIEUTH-OE-IEUNG C5F4 D210 # HANGUL SYLLABLE THIEUTH-YO C5F5 D22C # HANGUL SYLLABLE THIEUTH-U C5F6 D22D # HANGUL SYLLABLE THIEUTH-U-KIYEOK C5F7 D230 # HANGUL SYLLABLE THIEUTH-U-NIEUN C5F8 D234 # HANGUL SYLLABLE THIEUTH-U-RIEUL C5F9 D23C # HANGUL SYLLABLE THIEUTH-U-MIEUM C5FA D23D # HANGUL SYLLABLE THIEUTH-U-PIEUP C5FB D23F # HANGUL SYLLABLE THIEUTH-U-SIOS C5FC D241 # HANGUL SYLLABLE THIEUTH-U-IEUNG C5FD D248 # HANGUL SYLLABLE THIEUTH-WEO C5FE D25C # HANGUL SYLLABLE THIEUTH-WEO-SSANGSIOS C641 D78D # HANGUL SYLLABLE HIEUH-I-NIEUNCIEUC C642 D78E # HANGUL SYLLABLE HIEUH-I-NIEUNHIEUH C643 D78F # HANGUL SYLLABLE HIEUH-I-TIKEUT C644 D791 # HANGUL SYLLABLE HIEUH-I-RIEULKIYEOK C645 D792 # HANGUL SYLLABLE HIEUH-I-RIEULMIEUM C646 D793 # HANGUL SYLLABLE HIEUH-I-RIEULPIEUP C647 D794 # HANGUL SYLLABLE HIEUH-I-RIEULSIOS C648 D795 # HANGUL SYLLABLE HIEUH-I-RIEULTHIEUTH C649 D796 # HANGUL SYLLABLE HIEUH-I-RIEULPHIEUPH C64A D797 # HANGUL SYLLABLE HIEUH-I-RIEULHIEUH C64B D79A # HANGUL SYLLABLE HIEUH-I-PIEUPSIOS C64C D79C # HANGUL SYLLABLE HIEUH-I-SSANGSIOS C64D D79E # HANGUL SYLLABLE HIEUH-I-CIEUC C64E D79F # HANGUL SYLLABLE HIEUH-I-CHIEUCH C64F D7A0 # HANGUL SYLLABLE HIEUH-I-KHIEUKH C650 D7A1 # HANGUL SYLLABLE HIEUH-I-THIEUTH C651 D7A2 # HANGUL SYLLABLE HIEUH-I-PHIEUPH C652 D7A3 # HANGUL SYLLABLE HIEUH-I-HIEUH C6A1 D264 # HANGUL SYLLABLE THIEUTH-WE C6A2 D280 # HANGUL SYLLABLE THIEUTH-WI C6A3 D281 # HANGUL SYLLABLE THIEUTH-WI-KIYEOK C6A4 D284 # HANGUL SYLLABLE THIEUTH-WI-NIEUN C6A5 D288 # HANGUL SYLLABLE THIEUTH-WI-RIEUL C6A6 D290 # HANGUL SYLLABLE THIEUTH-WI-MIEUM C6A7 D291 # HANGUL SYLLABLE THIEUTH-WI-PIEUP C6A8 D295 # HANGUL SYLLABLE THIEUTH-WI-IEUNG C6A9 D29C # HANGUL SYLLABLE THIEUTH-YU C6AA D2A0 # HANGUL SYLLABLE THIEUTH-YU-NIEUN C6AB D2A4 # HANGUL SYLLABLE THIEUTH-YU-RIEUL C6AC D2AC # HANGUL SYLLABLE THIEUTH-YU-MIEUM C6AD D2B1 # HANGUL SYLLABLE THIEUTH-YU-IEUNG C6AE D2B8 # HANGUL SYLLABLE THIEUTH-EU C6AF D2B9 # HANGUL SYLLABLE THIEUTH-EU-KIYEOK C6B0 D2BC # HANGUL SYLLABLE THIEUTH-EU-NIEUN C6B1 D2BF # HANGUL SYLLABLE THIEUTH-EU-TIKEUT C6B2 D2C0 # HANGUL SYLLABLE THIEUTH-EU-RIEUL C6B3 D2C2 # HANGUL SYLLABLE THIEUTH-EU-RIEULMIEUM C6B4 D2C8 # HANGUL SYLLABLE THIEUTH-EU-MIEUM C6B5 D2C9 # HANGUL SYLLABLE THIEUTH-EU-PIEUP C6B6 D2CB # HANGUL SYLLABLE THIEUTH-EU-SIOS C6B7 D2D4 # HANGUL SYLLABLE THIEUTH-YI C6B8 D2D8 # HANGUL SYLLABLE THIEUTH-YI-NIEUN C6B9 D2DC # HANGUL SYLLABLE THIEUTH-YI-RIEUL C6BA D2E4 # HANGUL SYLLABLE THIEUTH-YI-MIEUM C6BB D2E5 # HANGUL SYLLABLE THIEUTH-YI-PIEUP C6BC D2F0 # HANGUL SYLLABLE THIEUTH-I C6BD D2F1 # HANGUL SYLLABLE THIEUTH-I-KIYEOK C6BE D2F4 # HANGUL SYLLABLE THIEUTH-I-NIEUN C6BF D2F8 # HANGUL SYLLABLE THIEUTH-I-RIEUL C6C0 D300 # HANGUL SYLLABLE THIEUTH-I-MIEUM C6C1 D301 # HANGUL SYLLABLE THIEUTH-I-PIEUP C6C2 D303 # HANGUL SYLLABLE THIEUTH-I-SIOS C6C3 D305 # HANGUL SYLLABLE THIEUTH-I-IEUNG C6C4 D30C # HANGUL SYLLABLE PHIEUPH-A C6C5 D30D # HANGUL SYLLABLE PHIEUPH-A-KIYEOK C6C6 D30E # HANGUL SYLLABLE PHIEUPH-A-SSANGKIYEOK C6C7 D310 # HANGUL SYLLABLE PHIEUPH-A-NIEUN C6C8 D314 # HANGUL SYLLABLE PHIEUPH-A-RIEUL C6C9 D316 # HANGUL SYLLABLE PHIEUPH-A-RIEULMIEUM C6CA D31C # HANGUL SYLLABLE PHIEUPH-A-MIEUM C6CB D31D # HANGUL SYLLABLE PHIEUPH-A-PIEUP C6CC D31F # HANGUL SYLLABLE PHIEUPH-A-SIOS C6CD D320 # HANGUL SYLLABLE PHIEUPH-A-SSANGSIOS C6CE D321 # HANGUL SYLLABLE PHIEUPH-A-IEUNG C6CF D325 # HANGUL SYLLABLE PHIEUPH-A-THIEUTH C6D0 D328 # HANGUL SYLLABLE PHIEUPH-AE C6D1 D329 # HANGUL SYLLABLE PHIEUPH-AE-KIYEOK C6D2 D32C # HANGUL SYLLABLE PHIEUPH-AE-NIEUN C6D3 D330 # HANGUL SYLLABLE PHIEUPH-AE-RIEUL C6D4 D338 # HANGUL SYLLABLE PHIEUPH-AE-MIEUM C6D5 D339 # HANGUL SYLLABLE PHIEUPH-AE-PIEUP C6D6 D33B # HANGUL SYLLABLE PHIEUPH-AE-SIOS C6D7 D33C # HANGUL SYLLABLE PHIEUPH-AE-SSANGSIOS C6D8 D33D # HANGUL SYLLABLE PHIEUPH-AE-IEUNG C6D9 D344 # HANGUL SYLLABLE PHIEUPH-YA C6DA D345 # HANGUL SYLLABLE PHIEUPH-YA-KIYEOK C6DB D37C # HANGUL SYLLABLE PHIEUPH-EO C6DC D37D # HANGUL SYLLABLE PHIEUPH-EO-KIYEOK C6DD D380 # HANGUL SYLLABLE PHIEUPH-EO-NIEUN C6DE D384 # HANGUL SYLLABLE PHIEUPH-EO-RIEUL C6DF D38C # HANGUL SYLLABLE PHIEUPH-EO-MIEUM C6E0 D38D # HANGUL SYLLABLE PHIEUPH-EO-PIEUP C6E1 D38F # HANGUL SYLLABLE PHIEUPH-EO-SIOS C6E2 D390 # HANGUL SYLLABLE PHIEUPH-EO-SSANGSIOS C6E3 D391 # HANGUL SYLLABLE PHIEUPH-EO-IEUNG C6E4 D398 # HANGUL SYLLABLE PHIEUPH-E C6E5 D399 # HANGUL SYLLABLE PHIEUPH-E-KIYEOK C6E6 D39C # HANGUL SYLLABLE PHIEUPH-E-NIEUN C6E7 D3A0 # HANGUL SYLLABLE PHIEUPH-E-RIEUL C6E8 D3A8 # HANGUL SYLLABLE PHIEUPH-E-MIEUM C6E9 D3A9 # HANGUL SYLLABLE PHIEUPH-E-PIEUP C6EA D3AB # HANGUL SYLLABLE PHIEUPH-E-SIOS C6EB D3AD # HANGUL SYLLABLE PHIEUPH-E-IEUNG C6EC D3B4 # HANGUL SYLLABLE PHIEUPH-YEO C6ED D3B8 # HANGUL SYLLABLE PHIEUPH-YEO-NIEUN C6EE D3BC # HANGUL SYLLABLE PHIEUPH-YEO-RIEUL C6EF D3C4 # HANGUL SYLLABLE PHIEUPH-YEO-MIEUM C6F0 D3C5 # HANGUL SYLLABLE PHIEUPH-YEO-PIEUP C6F1 D3C8 # HANGUL SYLLABLE PHIEUPH-YEO-SSANGSIOS C6F2 D3C9 # HANGUL SYLLABLE PHIEUPH-YEO-IEUNG C6F3 D3D0 # HANGUL SYLLABLE PHIEUPH-YE C6F4 D3D8 # HANGUL SYLLABLE PHIEUPH-YE-RIEUL C6F5 D3E1 # HANGUL SYLLABLE PHIEUPH-YE-PIEUP C6F6 D3E3 # HANGUL SYLLABLE PHIEUPH-YE-SIOS C6F7 D3EC # HANGUL SYLLABLE PHIEUPH-O C6F8 D3ED # HANGUL SYLLABLE PHIEUPH-O-KIYEOK C6F9 D3F0 # HANGUL SYLLABLE PHIEUPH-O-NIEUN C6FA D3F4 # HANGUL SYLLABLE PHIEUPH-O-RIEUL C6FB D3FC # HANGUL SYLLABLE PHIEUPH-O-MIEUM C6FC D3FD # HANGUL SYLLABLE PHIEUPH-O-PIEUP C6FD D3FF # HANGUL SYLLABLE PHIEUPH-O-SIOS C6FE D401 # HANGUL SYLLABLE PHIEUPH-O-IEUNG C7A1 D408 # HANGUL SYLLABLE PHIEUPH-WA C7A2 D41D # HANGUL SYLLABLE PHIEUPH-WA-IEUNG C7A3 D440 # HANGUL SYLLABLE PHIEUPH-OE C7A4 D444 # HANGUL SYLLABLE PHIEUPH-OE-NIEUN C7A5 D45C # HANGUL SYLLABLE PHIEUPH-YO C7A6 D460 # HANGUL SYLLABLE PHIEUPH-YO-NIEUN C7A7 D464 # HANGUL SYLLABLE PHIEUPH-YO-RIEUL C7A8 D46D # HANGUL SYLLABLE PHIEUPH-YO-PIEUP C7A9 D46F # HANGUL SYLLABLE PHIEUPH-YO-SIOS C7AA D478 # HANGUL SYLLABLE PHIEUPH-U C7AB D479 # HANGUL SYLLABLE PHIEUPH-U-KIYEOK C7AC D47C # HANGUL SYLLABLE PHIEUPH-U-NIEUN C7AD D47F # HANGUL SYLLABLE PHIEUPH-U-TIKEUT C7AE D480 # HANGUL SYLLABLE PHIEUPH-U-RIEUL C7AF D482 # HANGUL SYLLABLE PHIEUPH-U-RIEULMIEUM C7B0 D488 # HANGUL SYLLABLE PHIEUPH-U-MIEUM C7B1 D489 # HANGUL SYLLABLE PHIEUPH-U-PIEUP C7B2 D48B # HANGUL SYLLABLE PHIEUPH-U-SIOS C7B3 D48D # HANGUL SYLLABLE PHIEUPH-U-IEUNG C7B4 D494 # HANGUL SYLLABLE PHIEUPH-WEO C7B5 D4A9 # HANGUL SYLLABLE PHIEUPH-WEO-IEUNG C7B6 D4CC # HANGUL SYLLABLE PHIEUPH-WI C7B7 D4D0 # HANGUL SYLLABLE PHIEUPH-WI-NIEUN C7B8 D4D4 # HANGUL SYLLABLE PHIEUPH-WI-RIEUL C7B9 D4DC # HANGUL SYLLABLE PHIEUPH-WI-MIEUM C7BA D4DF # HANGUL SYLLABLE PHIEUPH-WI-SIOS C7BB D4E8 # HANGUL SYLLABLE PHIEUPH-YU C7BC D4EC # HANGUL SYLLABLE PHIEUPH-YU-NIEUN C7BD D4F0 # HANGUL SYLLABLE PHIEUPH-YU-RIEUL C7BE D4F8 # HANGUL SYLLABLE PHIEUPH-YU-MIEUM C7BF D4FB # HANGUL SYLLABLE PHIEUPH-YU-SIOS C7C0 D4FD # HANGUL SYLLABLE PHIEUPH-YU-IEUNG C7C1 D504 # HANGUL SYLLABLE PHIEUPH-EU C7C2 D508 # HANGUL SYLLABLE PHIEUPH-EU-NIEUN C7C3 D50C # HANGUL SYLLABLE PHIEUPH-EU-RIEUL C7C4 D514 # HANGUL SYLLABLE PHIEUPH-EU-MIEUM C7C5 D515 # HANGUL SYLLABLE PHIEUPH-EU-PIEUP C7C6 D517 # HANGUL SYLLABLE PHIEUPH-EU-SIOS C7C7 D53C # HANGUL SYLLABLE PHIEUPH-I C7C8 D53D # HANGUL SYLLABLE PHIEUPH-I-KIYEOK C7C9 D540 # HANGUL SYLLABLE PHIEUPH-I-NIEUN C7CA D544 # HANGUL SYLLABLE PHIEUPH-I-RIEUL C7CB D54C # HANGUL SYLLABLE PHIEUPH-I-MIEUM C7CC D54D # HANGUL SYLLABLE PHIEUPH-I-PIEUP C7CD D54F # HANGUL SYLLABLE PHIEUPH-I-SIOS C7CE D551 # HANGUL SYLLABLE PHIEUPH-I-IEUNG C7CF D558 # HANGUL SYLLABLE HIEUH-A C7D0 D559 # HANGUL SYLLABLE HIEUH-A-KIYEOK C7D1 D55C # HANGUL SYLLABLE HIEUH-A-NIEUN C7D2 D560 # HANGUL SYLLABLE HIEUH-A-RIEUL C7D3 D565 # HANGUL SYLLABLE HIEUH-A-RIEULTHIEUTH C7D4 D568 # HANGUL SYLLABLE HIEUH-A-MIEUM C7D5 D569 # HANGUL SYLLABLE HIEUH-A-PIEUP C7D6 D56B # HANGUL SYLLABLE HIEUH-A-SIOS C7D7 D56D # HANGUL SYLLABLE HIEUH-A-IEUNG C7D8 D574 # HANGUL SYLLABLE HIEUH-AE C7D9 D575 # HANGUL SYLLABLE HIEUH-AE-KIYEOK C7DA D578 # HANGUL SYLLABLE HIEUH-AE-NIEUN C7DB D57C # HANGUL SYLLABLE HIEUH-AE-RIEUL C7DC D584 # HANGUL SYLLABLE HIEUH-AE-MIEUM C7DD D585 # HANGUL SYLLABLE HIEUH-AE-PIEUP C7DE D587 # HANGUL SYLLABLE HIEUH-AE-SIOS C7DF D588 # HANGUL SYLLABLE HIEUH-AE-SSANGSIOS C7E0 D589 # HANGUL SYLLABLE HIEUH-AE-IEUNG C7E1 D590 # HANGUL SYLLABLE HIEUH-YA C7E2 D5A5 # HANGUL SYLLABLE HIEUH-YA-IEUNG C7E3 D5C8 # HANGUL SYLLABLE HIEUH-EO C7E4 D5C9 # HANGUL SYLLABLE HIEUH-EO-KIYEOK C7E5 D5CC # HANGUL SYLLABLE HIEUH-EO-NIEUN C7E6 D5D0 # HANGUL SYLLABLE HIEUH-EO-RIEUL C7E7 D5D2 # HANGUL SYLLABLE HIEUH-EO-RIEULMIEUM C7E8 D5D8 # HANGUL SYLLABLE HIEUH-EO-MIEUM C7E9 D5D9 # HANGUL SYLLABLE HIEUH-EO-PIEUP C7EA D5DB # HANGUL SYLLABLE HIEUH-EO-SIOS C7EB D5DD # HANGUL SYLLABLE HIEUH-EO-IEUNG C7EC D5E4 # HANGUL SYLLABLE HIEUH-E C7ED D5E5 # HANGUL SYLLABLE HIEUH-E-KIYEOK C7EE D5E8 # HANGUL SYLLABLE HIEUH-E-NIEUN C7EF D5EC # HANGUL SYLLABLE HIEUH-E-RIEUL C7F0 D5F4 # HANGUL SYLLABLE HIEUH-E-MIEUM C7F1 D5F5 # HANGUL SYLLABLE HIEUH-E-PIEUP C7F2 D5F7 # HANGUL SYLLABLE HIEUH-E-SIOS C7F3 D5F9 # HANGUL SYLLABLE HIEUH-E-IEUNG C7F4 D600 # HANGUL SYLLABLE HIEUH-YEO C7F5 D601 # HANGUL SYLLABLE HIEUH-YEO-KIYEOK C7F6 D604 # HANGUL SYLLABLE HIEUH-YEO-NIEUN C7F7 D608 # HANGUL SYLLABLE HIEUH-YEO-RIEUL C7F8 D610 # HANGUL SYLLABLE HIEUH-YEO-MIEUM C7F9 D611 # HANGUL SYLLABLE HIEUH-YEO-PIEUP C7FA D613 # HANGUL SYLLABLE HIEUH-YEO-SIOS C7FB D614 # HANGUL SYLLABLE HIEUH-YEO-SSANGSIOS C7FC D615 # HANGUL SYLLABLE HIEUH-YEO-IEUNG C7FD D61C # HANGUL SYLLABLE HIEUH-YE C7FE D620 # HANGUL SYLLABLE HIEUH-YE-NIEUN C8A1 D624 # HANGUL SYLLABLE HIEUH-YE-RIEUL C8A2 D62D # HANGUL SYLLABLE HIEUH-YE-PIEUP C8A3 D638 # HANGUL SYLLABLE HIEUH-O C8A4 D639 # HANGUL SYLLABLE HIEUH-O-KIYEOK C8A5 D63C # HANGUL SYLLABLE HIEUH-O-NIEUN C8A6 D640 # HANGUL SYLLABLE HIEUH-O-RIEUL C8A7 D645 # HANGUL SYLLABLE HIEUH-O-RIEULTHIEUTH C8A8 D648 # HANGUL SYLLABLE HIEUH-O-MIEUM C8A9 D649 # HANGUL SYLLABLE HIEUH-O-PIEUP C8AA D64B # HANGUL SYLLABLE HIEUH-O-SIOS C8AB D64D # HANGUL SYLLABLE HIEUH-O-IEUNG C8AC D651 # HANGUL SYLLABLE HIEUH-O-THIEUTH C8AD D654 # HANGUL SYLLABLE HIEUH-WA C8AE D655 # HANGUL SYLLABLE HIEUH-WA-KIYEOK C8AF D658 # HANGUL SYLLABLE HIEUH-WA-NIEUN C8B0 D65C # HANGUL SYLLABLE HIEUH-WA-RIEUL C8B1 D667 # HANGUL SYLLABLE HIEUH-WA-SIOS C8B2 D669 # HANGUL SYLLABLE HIEUH-WA-IEUNG C8B3 D670 # HANGUL SYLLABLE HIEUH-WAE C8B4 D671 # HANGUL SYLLABLE HIEUH-WAE-KIYEOK C8B5 D674 # HANGUL SYLLABLE HIEUH-WAE-NIEUN C8B6 D683 # HANGUL SYLLABLE HIEUH-WAE-SIOS C8B7 D685 # HANGUL SYLLABLE HIEUH-WAE-IEUNG C8B8 D68C # HANGUL SYLLABLE HIEUH-OE C8B9 D68D # HANGUL SYLLABLE HIEUH-OE-KIYEOK C8BA D690 # HANGUL SYLLABLE HIEUH-OE-NIEUN C8BB D694 # HANGUL SYLLABLE HIEUH-OE-RIEUL C8BC D69D # HANGUL SYLLABLE HIEUH-OE-PIEUP C8BD D69F # HANGUL SYLLABLE HIEUH-OE-SIOS C8BE D6A1 # HANGUL SYLLABLE HIEUH-OE-IEUNG C8BF D6A8 # HANGUL SYLLABLE HIEUH-YO C8C0 D6AC # HANGUL SYLLABLE HIEUH-YO-NIEUN C8C1 D6B0 # HANGUL SYLLABLE HIEUH-YO-RIEUL C8C2 D6B9 # HANGUL SYLLABLE HIEUH-YO-PIEUP C8C3 D6BB # HANGUL SYLLABLE HIEUH-YO-SIOS C8C4 D6C4 # HANGUL SYLLABLE HIEUH-U C8C5 D6C5 # HANGUL SYLLABLE HIEUH-U-KIYEOK C8C6 D6C8 # HANGUL SYLLABLE HIEUH-U-NIEUN C8C7 D6CC # HANGUL SYLLABLE HIEUH-U-RIEUL C8C8 D6D1 # HANGUL SYLLABLE HIEUH-U-RIEULTHIEUTH C8C9 D6D4 # HANGUL SYLLABLE HIEUH-U-MIEUM C8CA D6D7 # HANGUL SYLLABLE HIEUH-U-SIOS C8CB D6D9 # HANGUL SYLLABLE HIEUH-U-IEUNG C8CC D6E0 # HANGUL SYLLABLE HIEUH-WEO C8CD D6E4 # HANGUL SYLLABLE HIEUH-WEO-NIEUN C8CE D6E8 # HANGUL SYLLABLE HIEUH-WEO-RIEUL C8CF D6F0 # HANGUL SYLLABLE HIEUH-WEO-MIEUM C8D0 D6F5 # HANGUL SYLLABLE HIEUH-WEO-IEUNG C8D1 D6FC # HANGUL SYLLABLE HIEUH-WE C8D2 D6FD # HANGUL SYLLABLE HIEUH-WE-KIYEOK C8D3 D700 # HANGUL SYLLABLE HIEUH-WE-NIEUN C8D4 D704 # HANGUL SYLLABLE HIEUH-WE-RIEUL C8D5 D711 # HANGUL SYLLABLE HIEUH-WE-IEUNG C8D6 D718 # HANGUL SYLLABLE HIEUH-WI C8D7 D719 # HANGUL SYLLABLE HIEUH-WI-KIYEOK C8D8 D71C # HANGUL SYLLABLE HIEUH-WI-NIEUN C8D9 D720 # HANGUL SYLLABLE HIEUH-WI-RIEUL C8DA D728 # HANGUL SYLLABLE HIEUH-WI-MIEUM C8DB D729 # HANGUL SYLLABLE HIEUH-WI-PIEUP C8DC D72B # HANGUL SYLLABLE HIEUH-WI-SIOS C8DD D72D # HANGUL SYLLABLE HIEUH-WI-IEUNG C8DE D734 # HANGUL SYLLABLE HIEUH-YU C8DF D735 # HANGUL SYLLABLE HIEUH-YU-KIYEOK C8E0 D738 # HANGUL SYLLABLE HIEUH-YU-NIEUN C8E1 D73C # HANGUL SYLLABLE HIEUH-YU-RIEUL C8E2 D744 # HANGUL SYLLABLE HIEUH-YU-MIEUM C8E3 D747 # HANGUL SYLLABLE HIEUH-YU-SIOS C8E4 D749 # HANGUL SYLLABLE HIEUH-YU-IEUNG C8E5 D750 # HANGUL SYLLABLE HIEUH-EU C8E6 D751 # HANGUL SYLLABLE HIEUH-EU-KIYEOK C8E7 D754 # HANGUL SYLLABLE HIEUH-EU-NIEUN C8E8 D756 # HANGUL SYLLABLE HIEUH-EU-NIEUNHIEUH C8E9 D757 # HANGUL SYLLABLE HIEUH-EU-TIKEUT C8EA D758 # HANGUL SYLLABLE HIEUH-EU-RIEUL C8EB D759 # HANGUL SYLLABLE HIEUH-EU-RIEULKIYEOK C8EC D760 # HANGUL SYLLABLE HIEUH-EU-MIEUM C8ED D761 # HANGUL SYLLABLE HIEUH-EU-PIEUP C8EE D763 # HANGUL SYLLABLE HIEUH-EU-SIOS C8EF D765 # HANGUL SYLLABLE HIEUH-EU-IEUNG C8F0 D769 # HANGUL SYLLABLE HIEUH-EU-THIEUTH C8F1 D76C # HANGUL SYLLABLE HIEUH-YI C8F2 D770 # HANGUL SYLLABLE HIEUH-YI-NIEUN C8F3 D774 # HANGUL SYLLABLE HIEUH-YI-RIEUL C8F4 D77C # HANGUL SYLLABLE HIEUH-YI-MIEUM C8F5 D77D # HANGUL SYLLABLE HIEUH-YI-PIEUP C8F6 D781 # HANGUL SYLLABLE HIEUH-YI-IEUNG C8F7 D788 # HANGUL SYLLABLE HIEUH-I C8F8 D789 # HANGUL SYLLABLE HIEUH-I-KIYEOK C8F9 D78C # HANGUL SYLLABLE HIEUH-I-NIEUN C8FA D790 # HANGUL SYLLABLE HIEUH-I-RIEUL C8FB D798 # HANGUL SYLLABLE HIEUH-I-MIEUM C8FC D799 # HANGUL SYLLABLE HIEUH-I-PIEUP C8FD D79B # HANGUL SYLLABLE HIEUH-I-SIOS C8FE D79D # HANGUL SYLLABLE HIEUH-I-IEUNG CAA1 4F3D # CAA2 4F73 # CAA3 5047 # CAA4 50F9 # CAA5 52A0 # CAA6 53EF # CAA7 5475 # CAA8 54E5 # CAA9 5609 # CAAA 5AC1 # CAAB 5BB6 # CAAC 6687 # CAAD 67B6 # CAAE 67B7 # CAAF 67EF # CAB0 6B4C # CAB1 73C2 # CAB2 75C2 # CAB3 7A3C # CAB4 82DB # CAB5 8304 # CAB6 8857 # CAB7 8888 # CAB8 8A36 # CAB9 8CC8 # CABA 8DCF # CABB 8EFB # CABC 8FE6 # CABD 99D5 # CABE 523B # CABF 5374 # CAC0 5404 # CAC1 606A # CAC2 6164 # CAC3 6BBC # CAC4 73CF # CAC5 811A # CAC6 89BA # CAC7 89D2 # CAC8 95A3 # CAC9 4F83 # CACA 520A # CACB 58BE # CACC 5978 # CACD 59E6 # CACE 5E72 # CACF 5E79 # CAD0 61C7 # CAD1 63C0 # CAD2 6746 # CAD3 67EC # CAD4 687F # CAD5 6F97 # CAD6 764E # CAD7 770B # CAD8 78F5 # CAD9 7A08 # CADA 7AFF # CADB 7C21 # CADC 809D # CADD 826E # CADE 8271 # CADF 8AEB # CAE0 9593 # CAE1 4E6B # CAE2 559D # CAE3 66F7 # CAE4 6E34 # CAE5 78A3 # CAE6 7AED # CAE7 845B # CAE8 8910 # CAE9 874E # CAEA 97A8 # CAEB 52D8 # CAEC 574E # CAED 582A # CAEE 5D4C # CAEF 611F # CAF0 61BE # CAF1 6221 # CAF2 6562 # CAF3 67D1 # CAF4 6A44 # CAF5 6E1B # CAF6 7518 # CAF7 75B3 # CAF8 76E3 # CAF9 77B0 # CAFA 7D3A # CAFB 90AF # CAFC 9451 # CAFD 9452 # CAFE 9F95 # CBA1 5323 # CBA2 5CAC # CBA3 7532 # CBA4 80DB # CBA5 9240 # CBA6 9598 # CBA7 525B # CBA8 5808 # CBA9 59DC # CBAA 5CA1 # CBAB 5D17 # CBAC 5EB7 # CBAD 5F3A # CBAE 5F4A # CBAF 6177 # CBB0 6C5F # CBB1 757A # CBB2 7586 # CBB3 7CE0 # CBB4 7D73 # CBB5 7DB1 # CBB6 7F8C # CBB7 8154 # CBB8 8221 # CBB9 8591 # CBBA 8941 # CBBB 8B1B # CBBC 92FC # CBBD 964D # CBBE 9C47 # CBBF 4ECB # CBC0 4EF7 # CBC1 500B # CBC2 51F1 # CBC3 584F # CBC4 6137 # CBC5 613E # CBC6 6168 # CBC7 6539 # CBC8 69EA # CBC9 6F11 # CBCA 75A5 # CBCB 7686 # CBCC 76D6 # CBCD 7B87 # CBCE 82A5 # CBCF 84CB # CBD0 F900 # CBD1 93A7 # CBD2 958B # CBD3 5580 # CBD4 5BA2 # CBD5 5751 # CBD6 F901 # CBD7 7CB3 # CBD8 7FB9 # CBD9 91B5 # CBDA 5028 # CBDB 53BB # CBDC 5C45 # CBDD 5DE8 # CBDE 62D2 # CBDF 636E # CBE0 64DA # CBE1 64E7 # CBE2 6E20 # CBE3 70AC # CBE4 795B # CBE5 8DDD # CBE6 8E1E # CBE7 F902 # CBE8 907D # CBE9 9245 # CBEA 92F8 # CBEB 4E7E # CBEC 4EF6 # CBED 5065 # CBEE 5DFE # CBEF 5EFA # CBF0 6106 # CBF1 6957 # CBF2 8171 # CBF3 8654 # CBF4 8E47 # CBF5 9375 # CBF6 9A2B # CBF7 4E5E # CBF8 5091 # CBF9 6770 # CBFA 6840 # CBFB 5109 # CBFC 528D # CBFD 5292 # CBFE 6AA2 # CCA1 77BC # CCA2 9210 # CCA3 9ED4 # CCA4 52AB # CCA5 602F # CCA6 8FF2 # CCA7 5048 # CCA8 61A9 # CCA9 63ED # CCAA 64CA # CCAB 683C # CCAC 6A84 # CCAD 6FC0 # CCAE 8188 # CCAF 89A1 # CCB0 9694 # CCB1 5805 # CCB2 727D # CCB3 72AC # CCB4 7504 # CCB5 7D79 # CCB6 7E6D # CCB7 80A9 # CCB8 898B # CCB9 8B74 # CCBA 9063 # CCBB 9D51 # CCBC 6289 # CCBD 6C7A # CCBE 6F54 # CCBF 7D50 # CCC0 7F3A # CCC1 8A23 # CCC2 517C # CCC3 614A # CCC4 7B9D # CCC5 8B19 # CCC6 9257 # CCC7 938C # CCC8 4EAC # CCC9 4FD3 # CCCA 501E # CCCB 50BE # CCCC 5106 # CCCD 52C1 # CCCE 52CD # CCCF 537F # CCD0 5770 # CCD1 5883 # CCD2 5E9A # CCD3 5F91 # CCD4 6176 # CCD5 61AC # CCD6 64CE # CCD7 656C # CCD8 666F # CCD9 66BB # CCDA 66F4 # CCDB 6897 # CCDC 6D87 # CCDD 7085 # CCDE 70F1 # CCDF 749F # CCE0 74A5 # CCE1 74CA # CCE2 75D9 # CCE3 786C # CCE4 78EC # CCE5 7ADF # CCE6 7AF6 # CCE7 7D45 # CCE8 7D93 # CCE9 8015 # CCEA 803F # CCEB 811B # CCEC 8396 # CCED 8B66 # CCEE 8F15 # CCEF 9015 # CCF0 93E1 # CCF1 9803 # CCF2 9838 # CCF3 9A5A # CCF4 9BE8 # CCF5 4FC2 # CCF6 5553 # CCF7 583A # CCF8 5951 # CCF9 5B63 # CCFA 5C46 # CCFB 60B8 # CCFC 6212 # CCFD 6842 # CCFE 68B0 # CDA1 68E8 # CDA2 6EAA # CDA3 754C # CDA4 7678 # CDA5 78CE # CDA6 7A3D # CDA7 7CFB # CDA8 7E6B # CDA9 7E7C # CDAA 8A08 # CDAB 8AA1 # CDAC 8C3F # CDAD 968E # CDAE 9DC4 # CDAF 53E4 # CDB0 53E9 # CDB1 544A # CDB2 5471 # CDB3 56FA # CDB4 59D1 # CDB5 5B64 # CDB6 5C3B # CDB7 5EAB # CDB8 62F7 # CDB9 6537 # CDBA 6545 # CDBB 6572 # CDBC 66A0 # CDBD 67AF # CDBE 69C1 # CDBF 6CBD # CDC0 75FC # CDC1 7690 # CDC2 777E # CDC3 7A3F # CDC4 7F94 # CDC5 8003 # CDC6 80A1 # CDC7 818F # CDC8 82E6 # CDC9 82FD # CDCA 83F0 # CDCB 85C1 # CDCC 8831 # CDCD 88B4 # CDCE 8AA5 # CDCF F903 # CDD0 8F9C # CDD1 932E # CDD2 96C7 # CDD3 9867 # CDD4 9AD8 # CDD5 9F13 # CDD6 54ED # CDD7 659B # CDD8 66F2 # CDD9 688F # CDDA 7A40 # CDDB 8C37 # CDDC 9D60 # CDDD 56F0 # CDDE 5764 # CDDF 5D11 # CDE0 6606 # CDE1 68B1 # CDE2 68CD # CDE3 6EFE # CDE4 7428 # CDE5 889E # CDE6 9BE4 # CDE7 6C68 # CDE8 F904 # CDE9 9AA8 # CDEA 4F9B # CDEB 516C # CDEC 5171 # CDED 529F # CDEE 5B54 # CDEF 5DE5 # CDF0 6050 # CDF1 606D # CDF2 62F1 # CDF3 63A7 # CDF4 653B # CDF5 73D9 # CDF6 7A7A # CDF7 86A3 # CDF8 8CA2 # CDF9 978F # CDFA 4E32 # CDFB 5BE1 # CDFC 6208 # CDFD 679C # CDFE 74DC # CEA1 79D1 # CEA2 83D3 # CEA3 8A87 # CEA4 8AB2 # CEA5 8DE8 # CEA6 904E # CEA7 934B # CEA8 9846 # CEA9 5ED3 # CEAA 69E8 # CEAB 85FF # CEAC 90ED # CEAD F905 # CEAE 51A0 # CEAF 5B98 # CEB0 5BEC # CEB1 6163 # CEB2 68FA # CEB3 6B3E # CEB4 704C # CEB5 742F # CEB6 74D8 # CEB7 7BA1 # CEB8 7F50 # CEB9 83C5 # CEBA 89C0 # CEBB 8CAB # CEBC 95DC # CEBD 9928 # CEBE 522E # CEBF 605D # CEC0 62EC # CEC1 9002 # CEC2 4F8A # CEC3 5149 # CEC4 5321 # CEC5 58D9 # CEC6 5EE3 # CEC7 66E0 # CEC8 6D38 # CEC9 709A # CECA 72C2 # CECB 73D6 # CECC 7B50 # CECD 80F1 # CECE 945B # CECF 5366 # CED0 639B # CED1 7F6B # CED2 4E56 # CED3 5080 # CED4 584A # CED5 58DE # CED6 602A # CED7 6127 # CED8 62D0 # CED9 69D0 # CEDA 9B41 # CEDB 5B8F # CEDC 7D18 # CEDD 80B1 # CEDE 8F5F # CEDF 4EA4 # CEE0 50D1 # CEE1 54AC # CEE2 55AC # CEE3 5B0C # CEE4 5DA0 # CEE5 5DE7 # CEE6 652A # CEE7 654E # CEE8 6821 # CEE9 6A4B # CEEA 72E1 # CEEB 768E # CEEC 77EF # CEED 7D5E # CEEE 7FF9 # CEEF 81A0 # CEF0 854E # CEF1 86DF # CEF2 8F03 # CEF3 8F4E # CEF4 90CA # CEF5 9903 # CEF6 9A55 # CEF7 9BAB # CEF8 4E18 # CEF9 4E45 # CEFA 4E5D # CEFB 4EC7 # CEFC 4FF1 # CEFD 5177 # CEFE 52FE # CFA1 5340 # CFA2 53E3 # CFA3 53E5 # CFA4 548E # CFA5 5614 # CFA6 5775 # CFA7 57A2 # CFA8 5BC7 # CFA9 5D87 # CFAA 5ED0 # CFAB 61FC # CFAC 62D8 # CFAD 6551 # CFAE 67B8 # CFAF 67E9 # CFB0 69CB # CFB1 6B50 # CFB2 6BC6 # CFB3 6BEC # CFB4 6C42 # CFB5 6E9D # CFB6 7078 # CFB7 72D7 # CFB8 7396 # CFB9 7403 # CFBA 77BF # CFBB 77E9 # CFBC 7A76 # CFBD 7D7F # CFBE 8009 # CFBF 81FC # CFC0 8205 # CFC1 820A # CFC2 82DF # CFC3 8862 # CFC4 8B33 # CFC5 8CFC # CFC6 8EC0 # CFC7 9011 # CFC8 90B1 # CFC9 9264 # CFCA 92B6 # CFCB 99D2 # CFCC 9A45 # CFCD 9CE9 # CFCE 9DD7 # CFCF 9F9C # CFD0 570B # CFD1 5C40 # CFD2 83CA # CFD3 97A0 # CFD4 97AB # CFD5 9EB4 # CFD6 541B # CFD7 7A98 # CFD8 7FA4 # CFD9 88D9 # CFDA 8ECD # CFDB 90E1 # CFDC 5800 # CFDD 5C48 # CFDE 6398 # CFDF 7A9F # CFE0 5BAE # CFE1 5F13 # CFE2 7A79 # CFE3 7AAE # CFE4 828E # CFE5 8EAC # CFE6 5026 # CFE7 5238 # CFE8 52F8 # CFE9 5377 # CFEA 5708 # CFEB 62F3 # CFEC 6372 # CFED 6B0A # CFEE 6DC3 # CFEF 7737 # CFF0 53A5 # CFF1 7357 # CFF2 8568 # CFF3 8E76 # CFF4 95D5 # CFF5 673A # CFF6 6AC3 # CFF7 6F70 # CFF8 8A6D # CFF9 8ECC # CFFA 994B # CFFB F906 # CFFC 6677 # CFFD 6B78 # CFFE 8CB4 # D0A1 9B3C # D0A2 F907 # D0A3 53EB # D0A4 572D # D0A5 594E # D0A6 63C6 # D0A7 69FB # D0A8 73EA # D0A9 7845 # D0AA 7ABA # D0AB 7AC5 # D0AC 7CFE # D0AD 8475 # D0AE 898F # D0AF 8D73 # D0B0 9035 # D0B1 95A8 # D0B2 52FB # D0B3 5747 # D0B4 7547 # D0B5 7B60 # D0B6 83CC # D0B7 921E # D0B8 F908 # D0B9 6A58 # D0BA 514B # D0BB 524B # D0BC 5287 # D0BD 621F # D0BE 68D8 # D0BF 6975 # D0C0 9699 # D0C1 50C5 # D0C2 52A4 # D0C3 52E4 # D0C4 61C3 # D0C5 65A4 # D0C6 6839 # D0C7 69FF # D0C8 747E # D0C9 7B4B # D0CA 82B9 # D0CB 83EB # D0CC 89B2 # D0CD 8B39 # D0CE 8FD1 # D0CF 9949 # D0D0 F909 # D0D1 4ECA # D0D2 5997 # D0D3 64D2 # D0D4 6611 # D0D5 6A8E # D0D6 7434 # D0D7 7981 # D0D8 79BD # D0D9 82A9 # D0DA 887E # D0DB 887F # D0DC 895F # D0DD F90A # D0DE 9326 # D0DF 4F0B # D0E0 53CA # D0E1 6025 # D0E2 6271 # D0E3 6C72 # D0E4 7D1A # D0E5 7D66 # D0E6 4E98 # D0E7 5162 # D0E8 77DC # D0E9 80AF # D0EA 4F01 # D0EB 4F0E # D0EC 5176 # D0ED 5180 # D0EE 55DC # D0EF 5668 # D0F0 573B # D0F1 57FA # D0F2 57FC # D0F3 5914 # D0F4 5947 # D0F5 5993 # D0F6 5BC4 # D0F7 5C90 # D0F8 5D0E # D0F9 5DF1 # D0FA 5E7E # D0FB 5FCC # D0FC 6280 # D0FD 65D7 # D0FE 65E3 # D1A1 671E # D1A2 671F # D1A3 675E # D1A4 68CB # D1A5 68C4 # D1A6 6A5F # D1A7 6B3A # D1A8 6C23 # D1A9 6C7D # D1AA 6C82 # D1AB 6DC7 # D1AC 7398 # D1AD 7426 # D1AE 742A # D1AF 7482 # D1B0 74A3 # D1B1 7578 # D1B2 757F # D1B3 7881 # D1B4 78EF # D1B5 7941 # D1B6 7947 # D1B7 7948 # D1B8 797A # D1B9 7B95 # D1BA 7D00 # D1BB 7DBA # D1BC 7F88 # D1BD 8006 # D1BE 802D # D1BF 808C # D1C0 8A18 # D1C1 8B4F # D1C2 8C48 # D1C3 8D77 # D1C4 9321 # D1C5 9324 # D1C6 98E2 # D1C7 9951 # D1C8 9A0E # D1C9 9A0F # D1CA 9A65 # D1CB 9E92 # D1CC 7DCA # D1CD 4F76 # D1CE 5409 # D1CF 62EE # D1D0 6854 # D1D1 91D1 # D1D2 55AB # D1D3 513A # D1D4 F90B # D1D5 F90C # D1D6 5A1C # D1D7 61E6 # D1D8 F90D # D1D9 62CF # D1DA 62FF # D1DB F90E # D1DC F90F # D1DD F910 # D1DE F911 # D1DF F912 # D1E0 F913 # D1E1 90A3 # D1E2 F914 # D1E3 F915 # D1E4 F916 # D1E5 F917 # D1E6 F918 # D1E7 8AFE # D1E8 F919 # D1E9 F91A # D1EA F91B # D1EB F91C # D1EC 6696 # D1ED F91D # D1EE 7156 # D1EF F91E # D1F0 F91F # D1F1 96E3 # D1F2 F920 # D1F3 634F # D1F4 637A # D1F5 5357 # D1F6 F921 # D1F7 678F # D1F8 6960 # D1F9 6E73 # D1FA F922 # D1FB 7537 # D1FC F923 # D1FD F924 # D1FE F925 # D2A1 7D0D # D2A2 F926 # D2A3 F927 # D2A4 8872 # D2A5 56CA # D2A6 5A18 # D2A7 F928 # D2A8 F929 # D2A9 F92A # D2AA F92B # D2AB F92C # D2AC 4E43 # D2AD F92D # D2AE 5167 # D2AF 5948 # D2B0 67F0 # D2B1 8010 # D2B2 F92E # D2B3 5973 # D2B4 5E74 # D2B5 649A # D2B6 79CA # D2B7 5FF5 # D2B8 606C # D2B9 62C8 # D2BA 637B # D2BB 5BE7 # D2BC 5BD7 # D2BD 52AA # D2BE F92F # D2BF 5974 # D2C0 5F29 # D2C1 6012 # D2C2 F930 # D2C3 F931 # D2C4 F932 # D2C5 7459 # D2C6 F933 # D2C7 F934 # D2C8 F935 # D2C9 F936 # D2CA F937 # D2CB F938 # D2CC 99D1 # D2CD F939 # D2CE F93A # D2CF F93B # D2D0 F93C # D2D1 F93D # D2D2 F93E # D2D3 F93F # D2D4 F940 # D2D5 F941 # D2D6 F942 # D2D7 F943 # D2D8 6FC3 # D2D9 F944 # D2DA F945 # D2DB 81BF # D2DC 8FB2 # D2DD 60F1 # D2DE F946 # D2DF F947 # D2E0 8166 # D2E1 F948 # D2E2 F949 # D2E3 5C3F # D2E4 F94A # D2E5 F94B # D2E6 F94C # D2E7 F94D # D2E8 F94E # D2E9 F94F # D2EA F950 # D2EB F951 # D2EC 5AE9 # D2ED 8A25 # D2EE 677B # D2EF 7D10 # D2F0 F952 # D2F1 F953 # D2F2 F954 # D2F3 F955 # D2F4 F956 # D2F5 F957 # D2F6 80FD # D2F7 F958 # D2F8 F959 # D2F9 5C3C # D2FA 6CE5 # D2FB 533F # D2FC 6EBA # D2FD 591A # D2FE 8336 # D3A1 4E39 # D3A2 4EB6 # D3A3 4F46 # D3A4 55AE # D3A5 5718 # D3A6 58C7 # D3A7 5F56 # D3A8 65B7 # D3A9 65E6 # D3AA 6A80 # D3AB 6BB5 # D3AC 6E4D # D3AD 77ED # D3AE 7AEF # D3AF 7C1E # D3B0 7DDE # D3B1 86CB # D3B2 8892 # D3B3 9132 # D3B4 935B # D3B5 64BB # D3B6 6FBE # D3B7 737A # D3B8 75B8 # D3B9 9054 # D3BA 5556 # D3BB 574D # D3BC 61BA # D3BD 64D4 # D3BE 66C7 # D3BF 6DE1 # D3C0 6E5B # D3C1 6F6D # D3C2 6FB9 # D3C3 75F0 # D3C4 8043 # D3C5 81BD # D3C6 8541 # D3C7 8983 # D3C8 8AC7 # D3C9 8B5A # D3CA 931F # D3CB 6C93 # D3CC 7553 # D3CD 7B54 # D3CE 8E0F # D3CF 905D # D3D0 5510 # D3D1 5802 # D3D2 5858 # D3D3 5E62 # D3D4 6207 # D3D5 649E # D3D6 68E0 # D3D7 7576 # D3D8 7CD6 # D3D9 87B3 # D3DA 9EE8 # D3DB 4EE3 # D3DC 5788 # D3DD 576E # D3DE 5927 # D3DF 5C0D # D3E0 5CB1 # D3E1 5E36 # D3E2 5F85 # D3E3 6234 # D3E4 64E1 # D3E5 73B3 # D3E6 81FA # D3E7 888B # D3E8 8CB8 # D3E9 968A # D3EA 9EDB # D3EB 5B85 # D3EC 5FB7 # D3ED 60B3 # D3EE 5012 # D3EF 5200 # D3F0 5230 # D3F1 5716 # D3F2 5835 # D3F3 5857 # D3F4 5C0E # D3F5 5C60 # D3F6 5CF6 # D3F7 5D8B # D3F8 5EA6 # D3F9 5F92 # D3FA 60BC # D3FB 6311 # D3FC 6389 # D3FD 6417 # D3FE 6843 # D4A1 68F9 # D4A2 6AC2 # D4A3 6DD8 # D4A4 6E21 # D4A5 6ED4 # D4A6 6FE4 # D4A7 71FE # D4A8 76DC # D4A9 7779 # D4AA 79B1 # D4AB 7A3B # D4AC 8404 # D4AD 89A9 # D4AE 8CED # D4AF 8DF3 # D4B0 8E48 # D4B1 9003 # D4B2 9014 # D4B3 9053 # D4B4 90FD # D4B5 934D # D4B6 9676 # D4B7 97DC # D4B8 6BD2 # D4B9 7006 # D4BA 7258 # D4BB 72A2 # D4BC 7368 # D4BD 7763 # D4BE 79BF # D4BF 7BE4 # D4C0 7E9B # D4C1 8B80 # D4C2 58A9 # D4C3 60C7 # D4C4 6566 # D4C5 65FD # D4C6 66BE # D4C7 6C8C # D4C8 711E # D4C9 71C9 # D4CA 8C5A # D4CB 9813 # D4CC 4E6D # D4CD 7A81 # D4CE 4EDD # D4CF 51AC # D4D0 51CD # D4D1 52D5 # D4D2 540C # D4D3 61A7 # D4D4 6771 # D4D5 6850 # D4D6 68DF # D4D7 6D1E # D4D8 6F7C # D4D9 75BC # D4DA 77B3 # D4DB 7AE5 # D4DC 80F4 # D4DD 8463 # D4DE 9285 # D4DF 515C # D4E0 6597 # D4E1 675C # D4E2 6793 # D4E3 75D8 # D4E4 7AC7 # D4E5 8373 # D4E6 F95A # D4E7 8C46 # D4E8 9017 # D4E9 982D # D4EA 5C6F # D4EB 81C0 # D4EC 829A # D4ED 9041 # D4EE 906F # D4EF 920D # D4F0 5F97 # D4F1 5D9D # D4F2 6A59 # D4F3 71C8 # D4F4 767B # D4F5 7B49 # D4F6 85E4 # D4F7 8B04 # D4F8 9127 # D4F9 9A30 # D4FA 5587 # D4FB 61F6 # D4FC F95B # D4FD 7669 # D4FE 7F85 # D5A1 863F # D5A2 87BA # D5A3 88F8 # D5A4 908F # D5A5 F95C # D5A6 6D1B # D5A7 70D9 # D5A8 73DE # D5A9 7D61 # D5AA 843D # D5AB F95D # D5AC 916A # D5AD 99F1 # D5AE F95E # D5AF 4E82 # D5B0 5375 # D5B1 6B04 # D5B2 6B12 # D5B3 703E # D5B4 721B # D5B5 862D # D5B6 9E1E # D5B7 524C # D5B8 8FA3 # D5B9 5D50 # D5BA 64E5 # D5BB 652C # D5BC 6B16 # D5BD 6FEB # D5BE 7C43 # D5BF 7E9C # D5C0 85CD # D5C1 8964 # D5C2 89BD # D5C3 62C9 # D5C4 81D8 # D5C5 881F # D5C6 5ECA # D5C7 6717 # D5C8 6D6A # D5C9 72FC # D5CA 7405 # D5CB 746F # D5CC 8782 # D5CD 90DE # D5CE 4F86 # D5CF 5D0D # D5D0 5FA0 # D5D1 840A # D5D2 51B7 # D5D3 63A0 # D5D4 7565 # D5D5 4EAE # D5D6 5006 # D5D7 5169 # D5D8 51C9 # D5D9 6881 # D5DA 6A11 # D5DB 7CAE # D5DC 7CB1 # D5DD 7CE7 # D5DE 826F # D5DF 8AD2 # D5E0 8F1B # D5E1 91CF # D5E2 4FB6 # D5E3 5137 # D5E4 52F5 # D5E5 5442 # D5E6 5EEC # D5E7 616E # D5E8 623E # D5E9 65C5 # D5EA 6ADA # D5EB 6FFE # D5EC 792A # D5ED 85DC # D5EE 8823 # D5EF 95AD # D5F0 9A62 # D5F1 9A6A # D5F2 9E97 # D5F3 9ECE # D5F4 529B # D5F5 66C6 # D5F6 6B77 # D5F7 701D # D5F8 792B # D5F9 8F62 # D5FA 9742 # D5FB 6190 # D5FC 6200 # D5FD 6523 # D5FE 6F23 # D6A1 7149 # D6A2 7489 # D6A3 7DF4 # D6A4 806F # D6A5 84EE # D6A6 8F26 # D6A7 9023 # D6A8 934A # D6A9 51BD # D6AA 5217 # D6AB 52A3 # D6AC 6D0C # D6AD 70C8 # D6AE 88C2 # D6AF 5EC9 # D6B0 6582 # D6B1 6BAE # D6B2 6FC2 # D6B3 7C3E # D6B4 7375 # D6B5 4EE4 # D6B6 4F36 # D6B7 56F9 # D6B8 F95F # D6B9 5CBA # D6BA 5DBA # D6BB 601C # D6BC 73B2 # D6BD 7B2D # D6BE 7F9A # D6BF 7FCE # D6C0 8046 # D6C1 901E # D6C2 9234 # D6C3 96F6 # D6C4 9748 # D6C5 9818 # D6C6 9F61 # D6C7 4F8B # D6C8 6FA7 # D6C9 79AE # D6CA 91B4 # D6CB 96B7 # D6CC 52DE # D6CD F960 # D6CE 6488 # D6CF 64C4 # D6D0 6AD3 # D6D1 6F5E # D6D2 7018 # D6D3 7210 # D6D4 76E7 # D6D5 8001 # D6D6 8606 # D6D7 865C # D6D8 8DEF # D6D9 8F05 # D6DA 9732 # D6DB 9B6F # D6DC 9DFA # D6DD 9E75 # D6DE 788C # D6DF 797F # D6E0 7DA0 # D6E1 83C9 # D6E2 9304 # D6E3 9E7F # D6E4 9E93 # D6E5 8AD6 # D6E6 58DF # D6E7 5F04 # D6E8 6727 # D6E9 7027 # D6EA 74CF # D6EB 7C60 # D6EC 807E # D6ED 5121 # D6EE 7028 # D6EF 7262 # D6F0 78CA # D6F1 8CC2 # D6F2 8CDA # D6F3 8CF4 # D6F4 96F7 # D6F5 4E86 # D6F6 50DA # D6F7 5BEE # D6F8 5ED6 # D6F9 6599 # D6FA 71CE # D6FB 7642 # D6FC 77AD # D6FD 804A # D6FE 84FC # D7A1 907C # D7A2 9B27 # D7A3 9F8D # D7A4 58D8 # D7A5 5A41 # D7A6 5C62 # D7A7 6A13 # D7A8 6DDA # D7A9 6F0F # D7AA 763B # D7AB 7D2F # D7AC 7E37 # D7AD 851E # D7AE 8938 # D7AF 93E4 # D7B0 964B # D7B1 5289 # D7B2 65D2 # D7B3 67F3 # D7B4 69B4 # D7B5 6D41 # D7B6 6E9C # D7B7 700F # D7B8 7409 # D7B9 7460 # D7BA 7559 # D7BB 7624 # D7BC 786B # D7BD 8B2C # D7BE 985E # D7BF 516D # D7C0 622E # D7C1 9678 # D7C2 4F96 # D7C3 502B # D7C4 5D19 # D7C5 6DEA # D7C6 7DB8 # D7C7 8F2A # D7C8 5F8B # D7C9 6144 # D7CA 6817 # D7CB F961 # D7CC 9686 # D7CD 52D2 # D7CE 808B # D7CF 51DC # D7D0 51CC # D7D1 695E # D7D2 7A1C # D7D3 7DBE # D7D4 83F1 # D7D5 9675 # D7D6 4FDA # D7D7 5229 # D7D8 5398 # D7D9 540F # D7DA 550E # D7DB 5C65 # D7DC 60A7 # D7DD 674E # D7DE 68A8 # D7DF 6D6C # D7E0 7281 # D7E1 72F8 # D7E2 7406 # D7E3 7483 # D7E4 F962 # D7E5 75E2 # D7E6 7C6C # D7E7 7F79 # D7E8 7FB8 # D7E9 8389 # D7EA 88CF # D7EB 88E1 # D7EC 91CC # D7ED 91D0 # D7EE 96E2 # D7EF 9BC9 # D7F0 541D # D7F1 6F7E # D7F2 71D0 # D7F3 7498 # D7F4 85FA # D7F5 8EAA # D7F6 96A3 # D7F7 9C57 # D7F8 9E9F # D7F9 6797 # D7FA 6DCB # D7FB 7433 # D7FC 81E8 # D7FD 9716 # D7FE 782C # D8A1 7ACB # D8A2 7B20 # D8A3 7C92 # D8A4 6469 # D8A5 746A # D8A6 75F2 # D8A7 78BC # D8A8 78E8 # D8A9 99AC # D8AA 9B54 # D8AB 9EBB # D8AC 5BDE # D8AD 5E55 # D8AE 6F20 # D8AF 819C # D8B0 83AB # D8B1 9088 # D8B2 4E07 # D8B3 534D # D8B4 5A29 # D8B5 5DD2 # D8B6 5F4E # D8B7 6162 # D8B8 633D # D8B9 6669 # D8BA 66FC # D8BB 6EFF # D8BC 6F2B # D8BD 7063 # D8BE 779E # D8BF 842C # D8C0 8513 # D8C1 883B # D8C2 8F13 # D8C3 9945 # D8C4 9C3B # D8C5 551C # D8C6 62B9 # D8C7 672B # D8C8 6CAB # D8C9 8309 # D8CA 896A # D8CB 977A # D8CC 4EA1 # D8CD 5984 # D8CE 5FD8 # D8CF 5FD9 # D8D0 671B # D8D1 7DB2 # D8D2 7F54 # D8D3 8292 # D8D4 832B # D8D5 83BD # D8D6 8F1E # D8D7 9099 # D8D8 57CB # D8D9 59B9 # D8DA 5A92 # D8DB 5BD0 # D8DC 6627 # D8DD 679A # D8DE 6885 # D8DF 6BCF # D8E0 7164 # D8E1 7F75 # D8E2 8CB7 # D8E3 8CE3 # D8E4 9081 # D8E5 9B45 # D8E6 8108 # D8E7 8C8A # D8E8 964C # D8E9 9A40 # D8EA 9EA5 # D8EB 5B5F # D8EC 6C13 # D8ED 731B # D8EE 76F2 # D8EF 76DF # D8F0 840C # D8F1 51AA # D8F2 8993 # D8F3 514D # D8F4 5195 # D8F5 52C9 # D8F6 68C9 # D8F7 6C94 # D8F8 7704 # D8F9 7720 # D8FA 7DBF # D8FB 7DEC # D8FC 9762 # D8FD 9EB5 # D8FE 6EC5 # D9A1 8511 # D9A2 51A5 # D9A3 540D # D9A4 547D # D9A5 660E # D9A6 669D # D9A7 6927 # D9A8 6E9F # D9A9 76BF # D9AA 7791 # D9AB 8317 # D9AC 84C2 # D9AD 879F # D9AE 9169 # D9AF 9298 # D9B0 9CF4 # D9B1 8882 # D9B2 4FAE # D9B3 5192 # D9B4 52DF # D9B5 59C6 # D9B6 5E3D # D9B7 6155 # D9B8 6478 # D9B9 6479 # D9BA 66AE # D9BB 67D0 # D9BC 6A21 # D9BD 6BCD # D9BE 6BDB # D9BF 725F # D9C0 7261 # D9C1 7441 # D9C2 7738 # D9C3 77DB # D9C4 8017 # D9C5 82BC # D9C6 8305 # D9C7 8B00 # D9C8 8B28 # D9C9 8C8C # D9CA 6728 # D9CB 6C90 # D9CC 7267 # D9CD 76EE # D9CE 7766 # D9CF 7A46 # D9D0 9DA9 # D9D1 6B7F # D9D2 6C92 # D9D3 5922 # D9D4 6726 # D9D5 8499 # D9D6 536F # D9D7 5893 # D9D8 5999 # D9D9 5EDF # D9DA 63CF # D9DB 6634 # D9DC 6773 # D9DD 6E3A # D9DE 732B # D9DF 7AD7 # D9E0 82D7 # D9E1 9328 # D9E2 52D9 # D9E3 5DEB # D9E4 61AE # D9E5 61CB # D9E6 620A # D9E7 62C7 # D9E8 64AB # D9E9 65E0 # D9EA 6959 # D9EB 6B66 # D9EC 6BCB # D9ED 7121 # D9EE 73F7 # D9EF 755D # D9F0 7E46 # D9F1 821E # D9F2 8302 # D9F3 856A # D9F4 8AA3 # D9F5 8CBF # D9F6 9727 # D9F7 9D61 # D9F8 58A8 # D9F9 9ED8 # D9FA 5011 # D9FB 520E # D9FC 543B # D9FD 554F # D9FE 6587 # DAA1 6C76 # DAA2 7D0A # DAA3 7D0B # DAA4 805E # DAA5 868A # DAA6 9580 # DAA7 96EF # DAA8 52FF # DAA9 6C95 # DAAA 7269 # DAAB 5473 # DAAC 5A9A # DAAD 5C3E # DAAE 5D4B # DAAF 5F4C # DAB0 5FAE # DAB1 672A # DAB2 68B6 # DAB3 6963 # DAB4 6E3C # DAB5 6E44 # DAB6 7709 # DAB7 7C73 # DAB8 7F8E # DAB9 8587 # DABA 8B0E # DABB 8FF7 # DABC 9761 # DABD 9EF4 # DABE 5CB7 # DABF 60B6 # DAC0 610D # DAC1 61AB # DAC2 654F # DAC3 65FB # DAC4 65FC # DAC5 6C11 # DAC6 6CEF # DAC7 739F # DAC8 73C9 # DAC9 7DE1 # DACA 9594 # DACB 5BC6 # DACC 871C # DACD 8B10 # DACE 525D # DACF 535A # DAD0 62CD # DAD1 640F # DAD2 64B2 # DAD3 6734 # DAD4 6A38 # DAD5 6CCA # DAD6 73C0 # DAD7 749E # DAD8 7B94 # DAD9 7C95 # DADA 7E1B # DADB 818A # DADC 8236 # DADD 8584 # DADE 8FEB # DADF 96F9 # DAE0 99C1 # DAE1 4F34 # DAE2 534A # DAE3 53CD # DAE4 53DB # DAE5 62CC # DAE6 642C # DAE7 6500 # DAE8 6591 # DAE9 69C3 # DAEA 6CEE # DAEB 6F58 # DAEC 73ED # DAED 7554 # DAEE 7622 # DAEF 76E4 # DAF0 76FC # DAF1 78D0 # DAF2 78FB # DAF3 792C # DAF4 7D46 # DAF5 822C # DAF6 87E0 # DAF7 8FD4 # DAF8 9812 # DAF9 98EF # DAFA 52C3 # DAFB 62D4 # DAFC 64A5 # DAFD 6E24 # DAFE 6F51 # DBA1 767C # DBA2 8DCB # DBA3 91B1 # DBA4 9262 # DBA5 9AEE # DBA6 9B43 # DBA7 5023 # DBA8 508D # DBA9 574A # DBAA 59A8 # DBAB 5C28 # DBAC 5E47 # DBAD 5F77 # DBAE 623F # DBAF 653E # DBB0 65B9 # DBB1 65C1 # DBB2 6609 # DBB3 678B # DBB4 699C # DBB5 6EC2 # DBB6 78C5 # DBB7 7D21 # DBB8 80AA # DBB9 8180 # DBBA 822B # DBBB 82B3 # DBBC 84A1 # DBBD 868C # DBBE 8A2A # DBBF 8B17 # DBC0 90A6 # DBC1 9632 # DBC2 9F90 # DBC3 500D # DBC4 4FF3 # DBC5 F963 # DBC6 57F9 # DBC7 5F98 # DBC8 62DC # DBC9 6392 # DBCA 676F # DBCB 6E43 # DBCC 7119 # DBCD 76C3 # DBCE 80CC # DBCF 80DA # DBD0 88F4 # DBD1 88F5 # DBD2 8919 # DBD3 8CE0 # DBD4 8F29 # DBD5 914D # DBD6 966A # DBD7 4F2F # DBD8 4F70 # DBD9 5E1B # DBDA 67CF # DBDB 6822 # DBDC 767D # DBDD 767E # DBDE 9B44 # DBDF 5E61 # DBE0 6A0A # DBE1 7169 # DBE2 71D4 # DBE3 756A # DBE4 F964 # DBE5 7E41 # DBE6 8543 # DBE7 85E9 # DBE8 98DC # DBE9 4F10 # DBEA 7B4F # DBEB 7F70 # DBEC 95A5 # DBED 51E1 # DBEE 5E06 # DBEF 68B5 # DBF0 6C3E # DBF1 6C4E # DBF2 6CDB # DBF3 72AF # DBF4 7BC4 # DBF5 8303 # DBF6 6CD5 # DBF7 743A # DBF8 50FB # DBF9 5288 # DBFA 58C1 # DBFB 64D8 # DBFC 6A97 # DBFD 74A7 # DBFE 7656 # DCA1 78A7 # DCA2 8617 # DCA3 95E2 # DCA4 9739 # DCA5 F965 # DCA6 535E # DCA7 5F01 # DCA8 8B8A # DCA9 8FA8 # DCAA 8FAF # DCAB 908A # DCAC 5225 # DCAD 77A5 # DCAE 9C49 # DCAF 9F08 # DCB0 4E19 # DCB1 5002 # DCB2 5175 # DCB3 5C5B # DCB4 5E77 # DCB5 661E # DCB6 663A # DCB7 67C4 # DCB8 68C5 # DCB9 70B3 # DCBA 7501 # DCBB 75C5 # DCBC 79C9 # DCBD 7ADD # DCBE 8F27 # DCBF 9920 # DCC0 9A08 # DCC1 4FDD # DCC2 5821 # DCC3 5831 # DCC4 5BF6 # DCC5 666E # DCC6 6B65 # DCC7 6D11 # DCC8 6E7A # DCC9 6F7D # DCCA 73E4 # DCCB 752B # DCCC 83E9 # DCCD 88DC # DCCE 8913 # DCCF 8B5C # DCD0 8F14 # DCD1 4F0F # DCD2 50D5 # DCD3 5310 # DCD4 535C # DCD5 5B93 # DCD6 5FA9 # DCD7 670D # DCD8 798F # DCD9 8179 # DCDA 832F # DCDB 8514 # DCDC 8907 # DCDD 8986 # DCDE 8F39 # DCDF 8F3B # DCE0 99A5 # DCE1 9C12 # DCE2 672C # DCE3 4E76 # DCE4 4FF8 # DCE5 5949 # DCE6 5C01 # DCE7 5CEF # DCE8 5CF0 # DCE9 6367 # DCEA 68D2 # DCEB 70FD # DCEC 71A2 # DCED 742B # DCEE 7E2B # DCEF 84EC # DCF0 8702 # DCF1 9022 # DCF2 92D2 # DCF3 9CF3 # DCF4 4E0D # DCF5 4ED8 # DCF6 4FEF # DCF7 5085 # DCF8 5256 # DCF9 526F # DCFA 5426 # DCFB 5490 # DCFC 57E0 # DCFD 592B # DCFE 5A66 # DDA1 5B5A # DDA2 5B75 # DDA3 5BCC # DDA4 5E9C # DDA5 F966 # DDA6 6276 # DDA7 6577 # DDA8 65A7 # DDA9 6D6E # DDAA 6EA5 # DDAB 7236 # DDAC 7B26 # DDAD 7C3F # DDAE 7F36 # DDAF 8150 # DDB0 8151 # DDB1 819A # DDB2 8240 # DDB3 8299 # DDB4 83A9 # DDB5 8A03 # DDB6 8CA0 # DDB7 8CE6 # DDB8 8CFB # DDB9 8D74 # DDBA 8DBA # DDBB 90E8 # DDBC 91DC # DDBD 961C # DDBE 9644 # DDBF 99D9 # DDC0 9CE7 # DDC1 5317 # DDC2 5206 # DDC3 5429 # DDC4 5674 # DDC5 58B3 # DDC6 5954 # DDC7 596E # DDC8 5FFF # DDC9 61A4 # DDCA 626E # DDCB 6610 # DDCC 6C7E # DDCD 711A # DDCE 76C6 # DDCF 7C89 # DDD0 7CDE # DDD1 7D1B # DDD2 82AC # DDD3 8CC1 # DDD4 96F0 # DDD5 F967 # DDD6 4F5B # DDD7 5F17 # DDD8 5F7F # DDD9 62C2 # DDDA 5D29 # DDDB 670B # DDDC 68DA # DDDD 787C # DDDE 7E43 # DDDF 9D6C # DDE0 4E15 # DDE1 5099 # DDE2 5315 # DDE3 532A # DDE4 5351 # DDE5 5983 # DDE6 5A62 # DDE7 5E87 # DDE8 60B2 # DDE9 618A # DDEA 6249 # DDEB 6279 # DDEC 6590 # DDED 6787 # DDEE 69A7 # DDEF 6BD4 # DDF0 6BD6 # DDF1 6BD7 # DDF2 6BD8 # DDF3 6CB8 # DDF4 F968 # DDF5 7435 # DDF6 75FA # DDF7 7812 # DDF8 7891 # DDF9 79D5 # DDFA 79D8 # DDFB 7C83 # DDFC 7DCB # DDFD 7FE1 # DDFE 80A5 # DEA1 813E # DEA2 81C2 # DEA3 83F2 # DEA4 871A # DEA5 88E8 # DEA6 8AB9 # DEA7 8B6C # DEA8 8CBB # DEA9 9119 # DEAA 975E # DEAB 98DB # DEAC 9F3B # DEAD 56AC # DEAE 5B2A # DEAF 5F6C # DEB0 658C # DEB1 6AB3 # DEB2 6BAF # DEB3 6D5C # DEB4 6FF1 # DEB5 7015 # DEB6 725D # DEB7 73AD # DEB8 8CA7 # DEB9 8CD3 # DEBA 983B # DEBB 6191 # DEBC 6C37 # DEBD 8058 # DEBE 9A01 # DEBF 4E4D # DEC0 4E8B # DEC1 4E9B # DEC2 4ED5 # DEC3 4F3A # DEC4 4F3C # DEC5 4F7F # DEC6 4FDF # DEC7 50FF # DEC8 53F2 # DEC9 53F8 # DECA 5506 # DECB 55E3 # DECC 56DB # DECD 58EB # DECE 5962 # DECF 5A11 # DED0 5BEB # DED1 5BFA # DED2 5C04 # DED3 5DF3 # DED4 5E2B # DED5 5F99 # DED6 601D # DED7 6368 # DED8 659C # DED9 65AF # DEDA 67F6 # DEDB 67FB # DEDC 68AD # DEDD 6B7B # DEDE 6C99 # DEDF 6CD7 # DEE0 6E23 # DEE1 7009 # DEE2 7345 # DEE3 7802 # DEE4 793E # DEE5 7940 # DEE6 7960 # DEE7 79C1 # DEE8 7BE9 # DEE9 7D17 # DEEA 7D72 # DEEB 8086 # DEEC 820D # DEED 838E # DEEE 84D1 # DEEF 86C7 # DEF0 88DF # DEF1 8A50 # DEF2 8A5E # DEF3 8B1D # DEF4 8CDC # DEF5 8D66 # DEF6 8FAD # DEF7 90AA # DEF8 98FC # DEF9 99DF # DEFA 9E9D # DEFB 524A # DEFC F969 # DEFD 6714 # DEFE F96A # DFA1 5098 # DFA2 522A # DFA3 5C71 # DFA4 6563 # DFA5 6C55 # DFA6 73CA # DFA7 7523 # DFA8 759D # DFA9 7B97 # DFAA 849C # DFAB 9178 # DFAC 9730 # DFAD 4E77 # DFAE 6492 # DFAF 6BBA # DFB0 715E # DFB1 85A9 # DFB2 4E09 # DFB3 F96B # DFB4 6749 # DFB5 68EE # DFB6 6E17 # DFB7 829F # DFB8 8518 # DFB9 886B # DFBA 63F7 # DFBB 6F81 # DFBC 9212 # DFBD 98AF # DFBE 4E0A # DFBF 50B7 # DFC0 50CF # DFC1 511F # DFC2 5546 # DFC3 55AA # DFC4 5617 # DFC5 5B40 # DFC6 5C19 # DFC7 5CE0 # DFC8 5E38 # DFC9 5E8A # DFCA 5EA0 # DFCB 5EC2 # DFCC 60F3 # DFCD 6851 # DFCE 6A61 # DFCF 6E58 # DFD0 723D # DFD1 7240 # DFD2 72C0 # DFD3 76F8 # DFD4 7965 # DFD5 7BB1 # DFD6 7FD4 # DFD7 88F3 # DFD8 89F4 # DFD9 8A73 # DFDA 8C61 # DFDB 8CDE # DFDC 971C # DFDD 585E # DFDE 74BD # DFDF 8CFD # DFE0 55C7 # DFE1 F96C # DFE2 7A61 # DFE3 7D22 # DFE4 8272 # DFE5 7272 # DFE6 751F # DFE7 7525 # DFE8 F96D # DFE9 7B19 # DFEA 5885 # DFEB 58FB # DFEC 5DBC # DFED 5E8F # DFEE 5EB6 # DFEF 5F90 # DFF0 6055 # DFF1 6292 # DFF2 637F # DFF3 654D # DFF4 6691 # DFF5 66D9 # DFF6 66F8 # DFF7 6816 # DFF8 68F2 # DFF9 7280 # DFFA 745E # DFFB 7B6E # DFFC 7D6E # DFFD 7DD6 # DFFE 7F72 # E0A1 80E5 # E0A2 8212 # E0A3 85AF # E0A4 897F # E0A5 8A93 # E0A6 901D # E0A7 92E4 # E0A8 9ECD # E0A9 9F20 # E0AA 5915 # E0AB 596D # E0AC 5E2D # E0AD 60DC # E0AE 6614 # E0AF 6673 # E0B0 6790 # E0B1 6C50 # E0B2 6DC5 # E0B3 6F5F # E0B4 77F3 # E0B5 78A9 # E0B6 84C6 # E0B7 91CB # E0B8 932B # E0B9 4ED9 # E0BA 50CA # E0BB 5148 # E0BC 5584 # E0BD 5B0B # E0BE 5BA3 # E0BF 6247 # E0C0 657E # E0C1 65CB # E0C2 6E32 # E0C3 717D # E0C4 7401 # E0C5 7444 # E0C6 7487 # E0C7 74BF # E0C8 766C # E0C9 79AA # E0CA 7DDA # E0CB 7E55 # E0CC 7FA8 # E0CD 817A # E0CE 81B3 # E0CF 8239 # E0D0 861A # E0D1 87EC # E0D2 8A75 # E0D3 8DE3 # E0D4 9078 # E0D5 9291 # E0D6 9425 # E0D7 994D # E0D8 9BAE # E0D9 5368 # E0DA 5C51 # E0DB 6954 # E0DC 6CC4 # E0DD 6D29 # E0DE 6E2B # E0DF 820C # E0E0 859B # E0E1 893B # E0E2 8A2D # E0E3 8AAA # E0E4 96EA # E0E5 9F67 # E0E6 5261 # E0E7 66B9 # E0E8 6BB2 # E0E9 7E96 # E0EA 87FE # E0EB 8D0D # E0EC 9583 # E0ED 965D # E0EE 651D # E0EF 6D89 # E0F0 71EE # E0F1 F96E # E0F2 57CE # E0F3 59D3 # E0F4 5BAC # E0F5 6027 # E0F6 60FA # E0F7 6210 # E0F8 661F # E0F9 665F # E0FA 7329 # E0FB 73F9 # E0FC 76DB # E0FD 7701 # E0FE 7B6C # E1A1 8056 # E1A2 8072 # E1A3 8165 # E1A4 8AA0 # E1A5 9192 # E1A6 4E16 # E1A7 52E2 # E1A8 6B72 # E1A9 6D17 # E1AA 7A05 # E1AB 7B39 # E1AC 7D30 # E1AD F96F # E1AE 8CB0 # E1AF 53EC # E1B0 562F # E1B1 5851 # E1B2 5BB5 # E1B3 5C0F # E1B4 5C11 # E1B5 5DE2 # E1B6 6240 # E1B7 6383 # E1B8 6414 # E1B9 662D # E1BA 68B3 # E1BB 6CBC # E1BC 6D88 # E1BD 6EAF # E1BE 701F # E1BF 70A4 # E1C0 71D2 # E1C1 7526 # E1C2 758F # E1C3 758E # E1C4 7619 # E1C5 7B11 # E1C6 7BE0 # E1C7 7C2B # E1C8 7D20 # E1C9 7D39 # E1CA 852C # E1CB 856D # E1CC 8607 # E1CD 8A34 # E1CE 900D # E1CF 9061 # E1D0 90B5 # E1D1 92B7 # E1D2 97F6 # E1D3 9A37 # E1D4 4FD7 # E1D5 5C6C # E1D6 675F # E1D7 6D91 # E1D8 7C9F # E1D9 7E8C # E1DA 8B16 # E1DB 8D16 # E1DC 901F # E1DD 5B6B # E1DE 5DFD # E1DF 640D # E1E0 84C0 # E1E1 905C # E1E2 98E1 # E1E3 7387 # E1E4 5B8B # E1E5 609A # E1E6 677E # E1E7 6DDE # E1E8 8A1F # E1E9 8AA6 # E1EA 9001 # E1EB 980C # E1EC 5237 # E1ED F970 # E1EE 7051 # E1EF 788E # E1F0 9396 # E1F1 8870 # E1F2 91D7 # E1F3 4FEE # E1F4 53D7 # E1F5 55FD # E1F6 56DA # E1F7 5782 # E1F8 58FD # E1F9 5AC2 # E1FA 5B88 # E1FB 5CAB # E1FC 5CC0 # E1FD 5E25 # E1FE 6101 # E2A1 620D # E2A2 624B # E2A3 6388 # E2A4 641C # E2A5 6536 # E2A6 6578 # E2A7 6A39 # E2A8 6B8A # E2A9 6C34 # E2AA 6D19 # E2AB 6F31 # E2AC 71E7 # E2AD 72E9 # E2AE 7378 # E2AF 7407 # E2B0 74B2 # E2B1 7626 # E2B2 7761 # E2B3 79C0 # E2B4 7A57 # E2B5 7AEA # E2B6 7CB9 # E2B7 7D8F # E2B8 7DAC # E2B9 7E61 # E2BA 7F9E # E2BB 8129 # E2BC 8331 # E2BD 8490 # E2BE 84DA # E2BF 85EA # E2C0 8896 # E2C1 8AB0 # E2C2 8B90 # E2C3 8F38 # E2C4 9042 # E2C5 9083 # E2C6 916C # E2C7 9296 # E2C8 92B9 # E2C9 968B # E2CA 96A7 # E2CB 96A8 # E2CC 96D6 # E2CD 9700 # E2CE 9808 # E2CF 9996 # E2D0 9AD3 # E2D1 9B1A # E2D2 53D4 # E2D3 587E # E2D4 5919 # E2D5 5B70 # E2D6 5BBF # E2D7 6DD1 # E2D8 6F5A # E2D9 719F # E2DA 7421 # E2DB 74B9 # E2DC 8085 # E2DD 83FD # E2DE 5DE1 # E2DF 5F87 # E2E0 5FAA # E2E1 6042 # E2E2 65EC # E2E3 6812 # E2E4 696F # E2E5 6A53 # E2E6 6B89 # E2E7 6D35 # E2E8 6DF3 # E2E9 73E3 # E2EA 76FE # E2EB 77AC # E2EC 7B4D # E2ED 7D14 # E2EE 8123 # E2EF 821C # E2F0 8340 # E2F1 84F4 # E2F2 8563 # E2F3 8A62 # E2F4 8AC4 # E2F5 9187 # E2F6 931E # E2F7 9806 # E2F8 99B4 # E2F9 620C # E2FA 8853 # E2FB 8FF0 # E2FC 9265 # E2FD 5D07 # E2FE 5D27 # E3A1 5D69 # E3A2 745F # E3A3 819D # E3A4 8768 # E3A5 6FD5 # E3A6 62FE # E3A7 7FD2 # E3A8 8936 # E3A9 8972 # E3AA 4E1E # E3AB 4E58 # E3AC 50E7 # E3AD 52DD # E3AE 5347 # E3AF 627F # E3B0 6607 # E3B1 7E69 # E3B2 8805 # E3B3 965E # E3B4 4F8D # E3B5 5319 # E3B6 5636 # E3B7 59CB # E3B8 5AA4 # E3B9 5C38 # E3BA 5C4E # E3BB 5C4D # E3BC 5E02 # E3BD 5F11 # E3BE 6043 # E3BF 65BD # E3C0 662F # E3C1 6642 # E3C2 67BE # E3C3 67F4 # E3C4 731C # E3C5 77E2 # E3C6 793A # E3C7 7FC5 # E3C8 8494 # E3C9 84CD # E3CA 8996 # E3CB 8A66 # E3CC 8A69 # E3CD 8AE1 # E3CE 8C55 # E3CF 8C7A # E3D0 57F4 # E3D1 5BD4 # E3D2 5F0F # E3D3 606F # E3D4 62ED # E3D5 690D # E3D6 6B96 # E3D7 6E5C # E3D8 7184 # E3D9 7BD2 # E3DA 8755 # E3DB 8B58 # E3DC 8EFE # E3DD 98DF # E3DE 98FE # E3DF 4F38 # E3E0 4F81 # E3E1 4FE1 # E3E2 547B # E3E3 5A20 # E3E4 5BB8 # E3E5 613C # E3E6 65B0 # E3E7 6668 # E3E8 71FC # E3E9 7533 # E3EA 795E # E3EB 7D33 # E3EC 814E # E3ED 81E3 # E3EE 8398 # E3EF 85AA # E3F0 85CE # E3F1 8703 # E3F2 8A0A # E3F3 8EAB # E3F4 8F9B # E3F5 F971 # E3F6 8FC5 # E3F7 5931 # E3F8 5BA4 # E3F9 5BE6 # E3FA 6089 # E3FB 5BE9 # E3FC 5C0B # E3FD 5FC3 # E3FE 6C81 # E4A1 F972 # E4A2 6DF1 # E4A3 700B # E4A4 751A # E4A5 82AF # E4A6 8AF6 # E4A7 4EC0 # E4A8 5341 # E4A9 F973 # E4AA 96D9 # E4AB 6C0F # E4AC 4E9E # E4AD 4FC4 # E4AE 5152 # E4AF 555E # E4B0 5A25 # E4B1 5CE8 # E4B2 6211 # E4B3 7259 # E4B4 82BD # E4B5 83AA # E4B6 86FE # E4B7 8859 # E4B8 8A1D # E4B9 963F # E4BA 96C5 # E4BB 9913 # E4BC 9D09 # E4BD 9D5D # E4BE 580A # E4BF 5CB3 # E4C0 5DBD # E4C1 5E44 # E4C2 60E1 # E4C3 6115 # E4C4 63E1 # E4C5 6A02 # E4C6 6E25 # E4C7 9102 # E4C8 9354 # E4C9 984E # E4CA 9C10 # E4CB 9F77 # E4CC 5B89 # E4CD 5CB8 # E4CE 6309 # E4CF 664F # E4D0 6848 # E4D1 773C # E4D2 96C1 # E4D3 978D # E4D4 9854 # E4D5 9B9F # E4D6 65A1 # E4D7 8B01 # E4D8 8ECB # E4D9 95BC # E4DA 5535 # E4DB 5CA9 # E4DC 5DD6 # E4DD 5EB5 # E4DE 6697 # E4DF 764C # E4E0 83F4 # E4E1 95C7 # E4E2 58D3 # E4E3 62BC # E4E4 72CE # E4E5 9D28 # E4E6 4EF0 # E4E7 592E # E4E8 600F # E4E9 663B # E4EA 6B83 # E4EB 79E7 # E4EC 9D26 # E4ED 5393 # E4EE 54C0 # E4EF 57C3 # E4F0 5D16 # E4F1 611B # E4F2 66D6 # E4F3 6DAF # E4F4 788D # E4F5 827E # E4F6 9698 # E4F7 9744 # E4F8 5384 # E4F9 627C # E4FA 6396 # E4FB 6DB2 # E4FC 7E0A # E4FD 814B # E4FE 984D # E5A1 6AFB # E5A2 7F4C # E5A3 9DAF # E5A4 9E1A # E5A5 4E5F # E5A6 503B # E5A7 51B6 # E5A8 591C # E5A9 60F9 # E5AA 63F6 # E5AB 6930 # E5AC 723A # E5AD 8036 # E5AE F974 # E5AF 91CE # E5B0 5F31 # E5B1 F975 # E5B2 F976 # E5B3 7D04 # E5B4 82E5 # E5B5 846F # E5B6 84BB # E5B7 85E5 # E5B8 8E8D # E5B9 F977 # E5BA 4F6F # E5BB F978 # E5BC F979 # E5BD 58E4 # E5BE 5B43 # E5BF 6059 # E5C0 63DA # E5C1 6518 # E5C2 656D # E5C3 6698 # E5C4 F97A # E5C5 694A # E5C6 6A23 # E5C7 6D0B # E5C8 7001 # E5C9 716C # E5CA 75D2 # E5CB 760D # E5CC 79B3 # E5CD 7A70 # E5CE F97B # E5CF 7F8A # E5D0 F97C # E5D1 8944 # E5D2 F97D # E5D3 8B93 # E5D4 91C0 # E5D5 967D # E5D6 F97E # E5D7 990A # E5D8 5704 # E5D9 5FA1 # E5DA 65BC # E5DB 6F01 # E5DC 7600 # E5DD 79A6 # E5DE 8A9E # E5DF 99AD # E5E0 9B5A # E5E1 9F6C # E5E2 5104 # E5E3 61B6 # E5E4 6291 # E5E5 6A8D # E5E6 81C6 # E5E7 5043 # E5E8 5830 # E5E9 5F66 # E5EA 7109 # E5EB 8A00 # E5EC 8AFA # E5ED 5B7C # E5EE 8616 # E5EF 4FFA # E5F0 513C # E5F1 56B4 # E5F2 5944 # E5F3 63A9 # E5F4 6DF9 # E5F5 5DAA # E5F6 696D # E5F7 5186 # E5F8 4E88 # E5F9 4F59 # E5FA F97F # E5FB F980 # E5FC F981 # E5FD 5982 # E5FE F982 # E6A1 F983 # E6A2 6B5F # E6A3 6C5D # E6A4 F984 # E6A5 74B5 # E6A6 7916 # E6A7 F985 # E6A8 8207 # E6A9 8245 # E6AA 8339 # E6AB 8F3F # E6AC 8F5D # E6AD F986 # E6AE 9918 # E6AF F987 # E6B0 F988 # E6B1 F989 # E6B2 4EA6 # E6B3 F98A # E6B4 57DF # E6B5 5F79 # E6B6 6613 # E6B7 F98B # E6B8 F98C # E6B9 75AB # E6BA 7E79 # E6BB 8B6F # E6BC F98D # E6BD 9006 # E6BE 9A5B # E6BF 56A5 # E6C0 5827 # E6C1 59F8 # E6C2 5A1F # E6C3 5BB4 # E6C4 F98E # E6C5 5EF6 # E6C6 F98F # E6C7 F990 # E6C8 6350 # E6C9 633B # E6CA F991 # E6CB 693D # E6CC 6C87 # E6CD 6CBF # E6CE 6D8E # E6CF 6D93 # E6D0 6DF5 # E6D1 6F14 # E6D2 F992 # E6D3 70DF # E6D4 7136 # E6D5 7159 # E6D6 F993 # E6D7 71C3 # E6D8 71D5 # E6D9 F994 # E6DA 784F # E6DB 786F # E6DC F995 # E6DD 7B75 # E6DE 7DE3 # E6DF F996 # E6E0 7E2F # E6E1 F997 # E6E2 884D # E6E3 8EDF # E6E4 F998 # E6E5 F999 # E6E6 F99A # E6E7 925B # E6E8 F99B # E6E9 9CF6 # E6EA F99C # E6EB F99D # E6EC F99E # E6ED 6085 # E6EE 6D85 # E6EF F99F # E6F0 71B1 # E6F1 F9A0 # E6F2 F9A1 # E6F3 95B1 # E6F4 53AD # E6F5 F9A2 # E6F6 F9A3 # E6F7 F9A4 # E6F8 67D3 # E6F9 F9A5 # E6FA 708E # E6FB 7130 # E6FC 7430 # E6FD 8276 # E6FE 82D2 # E7A1 F9A6 # E7A2 95BB # E7A3 9AE5 # E7A4 9E7D # E7A5 66C4 # E7A6 F9A7 # E7A7 71C1 # E7A8 8449 # E7A9 F9A8 # E7AA F9A9 # E7AB 584B # E7AC F9AA # E7AD F9AB # E7AE 5DB8 # E7AF 5F71 # E7B0 F9AC # E7B1 6620 # E7B2 668E # E7B3 6979 # E7B4 69AE # E7B5 6C38 # E7B6 6CF3 # E7B7 6E36 # E7B8 6F41 # E7B9 6FDA # E7BA 701B # E7BB 702F # E7BC 7150 # E7BD 71DF # E7BE 7370 # E7BF F9AD # E7C0 745B # E7C1 F9AE # E7C2 74D4 # E7C3 76C8 # E7C4 7A4E # E7C5 7E93 # E7C6 F9AF # E7C7 F9B0 # E7C8 82F1 # E7C9 8A60 # E7CA 8FCE # E7CB F9B1 # E7CC 9348 # E7CD F9B2 # E7CE 9719 # E7CF F9B3 # E7D0 F9B4 # E7D1 4E42 # E7D2 502A # E7D3 F9B5 # E7D4 5208 # E7D5 53E1 # E7D6 66F3 # E7D7 6C6D # E7D8 6FCA # E7D9 730A # E7DA 777F # E7DB 7A62 # E7DC 82AE # E7DD 85DD # E7DE 8602 # E7DF F9B6 # E7E0 88D4 # E7E1 8A63 # E7E2 8B7D # E7E3 8C6B # E7E4 F9B7 # E7E5 92B3 # E7E6 F9B8 # E7E7 9713 # E7E8 9810 # E7E9 4E94 # E7EA 4F0D # E7EB 4FC9 # E7EC 50B2 # E7ED 5348 # E7EE 543E # E7EF 5433 # E7F0 55DA # E7F1 5862 # E7F2 58BA # E7F3 5967 # E7F4 5A1B # E7F5 5BE4 # E7F6 609F # E7F7 F9B9 # E7F8 61CA # E7F9 6556 # E7FA 65FF # E7FB 6664 # E7FC 68A7 # E7FD 6C5A # E7FE 6FB3 # E8A1 70CF # E8A2 71AC # E8A3 7352 # E8A4 7B7D # E8A5 8708 # E8A6 8AA4 # E8A7 9C32 # E8A8 9F07 # E8A9 5C4B # E8AA 6C83 # E8AB 7344 # E8AC 7389 # E8AD 923A # E8AE 6EAB # E8AF 7465 # E8B0 761F # E8B1 7A69 # E8B2 7E15 # E8B3 860A # E8B4 5140 # E8B5 58C5 # E8B6 64C1 # E8B7 74EE # E8B8 7515 # E8B9 7670 # E8BA 7FC1 # E8BB 9095 # E8BC 96CD # E8BD 9954 # E8BE 6E26 # E8BF 74E6 # E8C0 7AA9 # E8C1 7AAA # E8C2 81E5 # E8C3 86D9 # E8C4 8778 # E8C5 8A1B # E8C6 5A49 # E8C7 5B8C # E8C8 5B9B # E8C9 68A1 # E8CA 6900 # E8CB 6D63 # E8CC 73A9 # E8CD 7413 # E8CE 742C # E8CF 7897 # E8D0 7DE9 # E8D1 7FEB # E8D2 8118 # E8D3 8155 # E8D4 839E # E8D5 8C4C # E8D6 962E # E8D7 9811 # E8D8 66F0 # E8D9 5F80 # E8DA 65FA # E8DB 6789 # E8DC 6C6A # E8DD 738B # E8DE 502D # E8DF 5A03 # E8E0 6B6A # E8E1 77EE # E8E2 5916 # E8E3 5D6C # E8E4 5DCD # E8E5 7325 # E8E6 754F # E8E7 F9BA # E8E8 F9BB # E8E9 50E5 # E8EA 51F9 # E8EB 582F # E8EC 592D # E8ED 5996 # E8EE 59DA # E8EF 5BE5 # E8F0 F9BC # E8F1 F9BD # E8F2 5DA2 # E8F3 62D7 # E8F4 6416 # E8F5 6493 # E8F6 64FE # E8F7 F9BE # E8F8 66DC # E8F9 F9BF # E8FA 6A48 # E8FB F9C0 # E8FC 71FF # E8FD 7464 # E8FE F9C1 # E9A1 7A88 # E9A2 7AAF # E9A3 7E47 # E9A4 7E5E # E9A5 8000 # E9A6 8170 # E9A7 F9C2 # E9A8 87EF # E9A9 8981 # E9AA 8B20 # E9AB 9059 # E9AC F9C3 # E9AD 9080 # E9AE 9952 # E9AF 617E # E9B0 6B32 # E9B1 6D74 # E9B2 7E1F # E9B3 8925 # E9B4 8FB1 # E9B5 4FD1 # E9B6 50AD # E9B7 5197 # E9B8 52C7 # E9B9 57C7 # E9BA 5889 # E9BB 5BB9 # E9BC 5EB8 # E9BD 6142 # E9BE 6995 # E9BF 6D8C # E9C0 6E67 # E9C1 6EB6 # E9C2 7194 # E9C3 7462 # E9C4 7528 # E9C5 752C # E9C6 8073 # E9C7 8338 # E9C8 84C9 # E9C9 8E0A # E9CA 9394 # E9CB 93DE # E9CC F9C4 # E9CD 4E8E # E9CE 4F51 # E9CF 5076 # E9D0 512A # E9D1 53C8 # E9D2 53CB # E9D3 53F3 # E9D4 5B87 # E9D5 5BD3 # E9D6 5C24 # E9D7 611A # E9D8 6182 # E9D9 65F4 # E9DA 725B # E9DB 7397 # E9DC 7440 # E9DD 76C2 # E9DE 7950 # E9DF 7991 # E9E0 79B9 # E9E1 7D06 # E9E2 7FBD # E9E3 828B # E9E4 85D5 # E9E5 865E # E9E6 8FC2 # E9E7 9047 # E9E8 90F5 # E9E9 91EA # E9EA 9685 # E9EB 96E8 # E9EC 96E9 # E9ED 52D6 # E9EE 5F67 # E9EF 65ED # E9F0 6631 # E9F1 682F # E9F2 715C # E9F3 7A36 # E9F4 90C1 # E9F5 980A # E9F6 4E91 # E9F7 F9C5 # E9F8 6A52 # E9F9 6B9E # E9FA 6F90 # E9FB 7189 # E9FC 8018 # E9FD 82B8 # E9FE 8553 # EAA1 904B # EAA2 9695 # EAA3 96F2 # EAA4 97FB # EAA5 851A # EAA6 9B31 # EAA7 4E90 # EAA8 718A # EAA9 96C4 # EAAA 5143 # EAAB 539F # EAAC 54E1 # EAAD 5713 # EAAE 5712 # EAAF 57A3 # EAB0 5A9B # EAB1 5AC4 # EAB2 5BC3 # EAB3 6028 # EAB4 613F # EAB5 63F4 # EAB6 6C85 # EAB7 6D39 # EAB8 6E72 # EAB9 6E90 # EABA 7230 # EABB 733F # EABC 7457 # EABD 82D1 # EABE 8881 # EABF 8F45 # EAC0 9060 # EAC1 F9C6 # EAC2 9662 # EAC3 9858 # EAC4 9D1B # EAC5 6708 # EAC6 8D8A # EAC7 925E # EAC8 4F4D # EAC9 5049 # EACA 50DE # EACB 5371 # EACC 570D # EACD 59D4 # EACE 5A01 # EACF 5C09 # EAD0 6170 # EAD1 6690 # EAD2 6E2D # EAD3 7232 # EAD4 744B # EAD5 7DEF # EAD6 80C3 # EAD7 840E # EAD8 8466 # EAD9 853F # EADA 875F # EADB 885B # EADC 8918 # EADD 8B02 # EADE 9055 # EADF 97CB # EAE0 9B4F # EAE1 4E73 # EAE2 4F91 # EAE3 5112 # EAE4 516A # EAE5 F9C7 # EAE6 552F # EAE7 55A9 # EAE8 5B7A # EAE9 5BA5 # EAEA 5E7C # EAEB 5E7D # EAEC 5EBE # EAED 60A0 # EAEE 60DF # EAEF 6108 # EAF0 6109 # EAF1 63C4 # EAF2 6538 # EAF3 6709 # EAF4 F9C8 # EAF5 67D4 # EAF6 67DA # EAF7 F9C9 # EAF8 6961 # EAF9 6962 # EAFA 6CB9 # EAFB 6D27 # EAFC F9CA # EAFD 6E38 # EAFE F9CB # EBA1 6FE1 # EBA2 7336 # EBA3 7337 # EBA4 F9CC # EBA5 745C # EBA6 7531 # EBA7 F9CD # EBA8 7652 # EBA9 F9CE # EBAA F9CF # EBAB 7DAD # EBAC 81FE # EBAD 8438 # EBAE 88D5 # EBAF 8A98 # EBB0 8ADB # EBB1 8AED # EBB2 8E30 # EBB3 8E42 # EBB4 904A # EBB5 903E # EBB6 907A # EBB7 9149 # EBB8 91C9 # EBB9 936E # EBBA F9D0 # EBBB F9D1 # EBBC 5809 # EBBD F9D2 # EBBE 6BD3 # EBBF 8089 # EBC0 80B2 # EBC1 F9D3 # EBC2 F9D4 # EBC3 5141 # EBC4 596B # EBC5 5C39 # EBC6 F9D5 # EBC7 F9D6 # EBC8 6F64 # EBC9 73A7 # EBCA 80E4 # EBCB 8D07 # EBCC F9D7 # EBCD 9217 # EBCE 958F # EBCF F9D8 # EBD0 F9D9 # EBD1 F9DA # EBD2 F9DB # EBD3 807F # EBD4 620E # EBD5 701C # EBD6 7D68 # EBD7 878D # EBD8 F9DC # EBD9 57A0 # EBDA 6069 # EBDB 6147 # EBDC 6BB7 # EBDD 8ABE # EBDE 9280 # EBDF 96B1 # EBE0 4E59 # EBE1 541F # EBE2 6DEB # EBE3 852D # EBE4 9670 # EBE5 97F3 # EBE6 98EE # EBE7 63D6 # EBE8 6CE3 # EBE9 9091 # EBEA 51DD # EBEB 61C9 # EBEC 81BA # EBED 9DF9 # EBEE 4F9D # EBEF 501A # EBF0 5100 # EBF1 5B9C # EBF2 610F # EBF3 61FF # EBF4 64EC # EBF5 6905 # EBF6 6BC5 # EBF7 7591 # EBF8 77E3 # EBF9 7FA9 # EBFA 8264 # EBFB 858F # EBFC 87FB # EBFD 8863 # EBFE 8ABC # ECA1 8B70 # ECA2 91AB # ECA3 4E8C # ECA4 4EE5 # ECA5 4F0A # ECA6 F9DD # ECA7 F9DE # ECA8 5937 # ECA9 59E8 # ECAA F9DF # ECAB 5DF2 # ECAC 5F1B # ECAD 5F5B # ECAE 6021 # ECAF F9E0 # ECB0 F9E1 # ECB1 F9E2 # ECB2 F9E3 # ECB3 723E # ECB4 73E5 # ECB5 F9E4 # ECB6 7570 # ECB7 75CD # ECB8 F9E5 # ECB9 79FB # ECBA F9E6 # ECBB 800C # ECBC 8033 # ECBD 8084 # ECBE 82E1 # ECBF 8351 # ECC0 F9E7 # ECC1 F9E8 # ECC2 8CBD # ECC3 8CB3 # ECC4 9087 # ECC5 F9E9 # ECC6 F9EA # ECC7 98F4 # ECC8 990C # ECC9 F9EB # ECCA F9EC # ECCB 7037 # ECCC 76CA # ECCD 7FCA # ECCE 7FCC # ECCF 7FFC # ECD0 8B1A # ECD1 4EBA # ECD2 4EC1 # ECD3 5203 # ECD4 5370 # ECD5 F9ED # ECD6 54BD # ECD7 56E0 # ECD8 59FB # ECD9 5BC5 # ECDA 5F15 # ECDB 5FCD # ECDC 6E6E # ECDD F9EE # ECDE F9EF # ECDF 7D6A # ECE0 8335 # ECE1 F9F0 # ECE2 8693 # ECE3 8A8D # ECE4 F9F1 # ECE5 976D # ECE6 9777 # ECE7 F9F2 # ECE8 F9F3 # ECE9 4E00 # ECEA 4F5A # ECEB 4F7E # ECEC 58F9 # ECED 65E5 # ECEE 6EA2 # ECEF 9038 # ECF0 93B0 # ECF1 99B9 # ECF2 4EFB # ECF3 58EC # ECF4 598A # ECF5 59D9 # ECF6 6041 # ECF7 F9F4 # ECF8 F9F5 # ECF9 7A14 # ECFA F9F6 # ECFB 834F # ECFC 8CC3 # ECFD 5165 # ECFE 5344 # EDA1 F9F7 # EDA2 F9F8 # EDA3 F9F9 # EDA4 4ECD # EDA5 5269 # EDA6 5B55 # EDA7 82BF # EDA8 4ED4 # EDA9 523A # EDAA 54A8 # EDAB 59C9 # EDAC 59FF # EDAD 5B50 # EDAE 5B57 # EDAF 5B5C # EDB0 6063 # EDB1 6148 # EDB2 6ECB # EDB3 7099 # EDB4 716E # EDB5 7386 # EDB6 74F7 # EDB7 75B5 # EDB8 78C1 # EDB9 7D2B # EDBA 8005 # EDBB 81EA # EDBC 8328 # EDBD 8517 # EDBE 85C9 # EDBF 8AEE # EDC0 8CC7 # EDC1 96CC # EDC2 4F5C # EDC3 52FA # EDC4 56BC # EDC5 65AB # EDC6 6628 # EDC7 707C # EDC8 70B8 # EDC9 7235 # EDCA 7DBD # EDCB 828D # EDCC 914C # EDCD 96C0 # EDCE 9D72 # EDCF 5B71 # EDD0 68E7 # EDD1 6B98 # EDD2 6F7A # EDD3 76DE # EDD4 5C91 # EDD5 66AB # EDD6 6F5B # EDD7 7BB4 # EDD8 7C2A # EDD9 8836 # EDDA 96DC # EDDB 4E08 # EDDC 4ED7 # EDDD 5320 # EDDE 5834 # EDDF 58BB # EDE0 58EF # EDE1 596C # EDE2 5C07 # EDE3 5E33 # EDE4 5E84 # EDE5 5F35 # EDE6 638C # EDE7 66B2 # EDE8 6756 # EDE9 6A1F # EDEA 6AA3 # EDEB 6B0C # EDEC 6F3F # EDED 7246 # EDEE F9FA # EDEF 7350 # EDF0 748B # EDF1 7AE0 # EDF2 7CA7 # EDF3 8178 # EDF4 81DF # EDF5 81E7 # EDF6 838A # EDF7 846C # EDF8 8523 # EDF9 8594 # EDFA 85CF # EDFB 88DD # EDFC 8D13 # EDFD 91AC # EDFE 9577 # EEA1 969C # EEA2 518D # EEA3 54C9 # EEA4 5728 # EEA5 5BB0 # EEA6 624D # EEA7 6750 # EEA8 683D # EEA9 6893 # EEAA 6E3D # EEAB 6ED3 # EEAC 707D # EEAD 7E21 # EEAE 88C1 # EEAF 8CA1 # EEB0 8F09 # EEB1 9F4B # EEB2 9F4E # EEB3 722D # EEB4 7B8F # EEB5 8ACD # EEB6 931A # EEB7 4F47 # EEB8 4F4E # EEB9 5132 # EEBA 5480 # EEBB 59D0 # EEBC 5E95 # EEBD 62B5 # EEBE 6775 # EEBF 696E # EEC0 6A17 # EEC1 6CAE # EEC2 6E1A # EEC3 72D9 # EEC4 732A # EEC5 75BD # EEC6 7BB8 # EEC7 7D35 # EEC8 82E7 # EEC9 83F9 # EECA 8457 # EECB 85F7 # EECC 8A5B # EECD 8CAF # EECE 8E87 # EECF 9019 # EED0 90B8 # EED1 96CE # EED2 9F5F # EED3 52E3 # EED4 540A # EED5 5AE1 # EED6 5BC2 # EED7 6458 # EED8 6575 # EED9 6EF4 # EEDA 72C4 # EEDB F9FB # EEDC 7684 # EEDD 7A4D # EEDE 7B1B # EEDF 7C4D # EEE0 7E3E # EEE1 7FDF # EEE2 837B # EEE3 8B2B # EEE4 8CCA # EEE5 8D64 # EEE6 8DE1 # EEE7 8E5F # EEE8 8FEA # EEE9 8FF9 # EEEA 9069 # EEEB 93D1 # EEEC 4F43 # EEED 4F7A # EEEE 50B3 # EEEF 5168 # EEF0 5178 # EEF1 524D # EEF2 526A # EEF3 5861 # EEF4 587C # EEF5 5960 # EEF6 5C08 # EEF7 5C55 # EEF8 5EDB # EEF9 609B # EEFA 6230 # EEFB 6813 # EEFC 6BBF # EEFD 6C08 # EEFE 6FB1 # EFA1 714E # EFA2 7420 # EFA3 7530 # EFA4 7538 # EFA5 7551 # EFA6 7672 # EFA7 7B4C # EFA8 7B8B # EFA9 7BAD # EFAA 7BC6 # EFAB 7E8F # EFAC 8A6E # EFAD 8F3E # EFAE 8F49 # EFAF 923F # EFB0 9293 # EFB1 9322 # EFB2 942B # EFB3 96FB # EFB4 985A # EFB5 986B # EFB6 991E # EFB7 5207 # EFB8 622A # EFB9 6298 # EFBA 6D59 # EFBB 7664 # EFBC 7ACA # EFBD 7BC0 # EFBE 7D76 # EFBF 5360 # EFC0 5CBE # EFC1 5E97 # EFC2 6F38 # EFC3 70B9 # EFC4 7C98 # EFC5 9711 # EFC6 9B8E # EFC7 9EDE # EFC8 63A5 # EFC9 647A # EFCA 8776 # EFCB 4E01 # EFCC 4E95 # EFCD 4EAD # EFCE 505C # EFCF 5075 # EFD0 5448 # EFD1 59C3 # EFD2 5B9A # EFD3 5E40 # EFD4 5EAD # EFD5 5EF7 # EFD6 5F81 # EFD7 60C5 # EFD8 633A # EFD9 653F # EFDA 6574 # EFDB 65CC # EFDC 6676 # EFDD 6678 # EFDE 67FE # EFDF 6968 # EFE0 6A89 # EFE1 6B63 # EFE2 6C40 # EFE3 6DC0 # EFE4 6DE8 # EFE5 6E1F # EFE6 6E5E # EFE7 701E # EFE8 70A1 # EFE9 738E # EFEA 73FD # EFEB 753A # EFEC 775B # EFED 7887 # EFEE 798E # EFEF 7A0B # EFF0 7A7D # EFF1 7CBE # EFF2 7D8E # EFF3 8247 # EFF4 8A02 # EFF5 8AEA # EFF6 8C9E # EFF7 912D # EFF8 914A # EFF9 91D8 # EFFA 9266 # EFFB 92CC # EFFC 9320 # EFFD 9706 # EFFE 9756 # F0A1 975C # F0A2 9802 # F0A3 9F0E # F0A4 5236 # F0A5 5291 # F0A6 557C # F0A7 5824 # F0A8 5E1D # F0A9 5F1F # F0AA 608C # F0AB 63D0 # F0AC 68AF # F0AD 6FDF # F0AE 796D # F0AF 7B2C # F0B0 81CD # F0B1 85BA # F0B2 88FD # F0B3 8AF8 # F0B4 8E44 # F0B5 918D # F0B6 9664 # F0B7 969B # F0B8 973D # F0B9 984C # F0BA 9F4A # F0BB 4FCE # F0BC 5146 # F0BD 51CB # F0BE 52A9 # F0BF 5632 # F0C0 5F14 # F0C1 5F6B # F0C2 63AA # F0C3 64CD # F0C4 65E9 # F0C5 6641 # F0C6 66FA # F0C7 66F9 # F0C8 671D # F0C9 689D # F0CA 68D7 # F0CB 69FD # F0CC 6F15 # F0CD 6F6E # F0CE 7167 # F0CF 71E5 # F0D0 722A # F0D1 74AA # F0D2 773A # F0D3 7956 # F0D4 795A # F0D5 79DF # F0D6 7A20 # F0D7 7A95 # F0D8 7C97 # F0D9 7CDF # F0DA 7D44 # F0DB 7E70 # F0DC 8087 # F0DD 85FB # F0DE 86A4 # F0DF 8A54 # F0E0 8ABF # F0E1 8D99 # F0E2 8E81 # F0E3 9020 # F0E4 906D # F0E5 91E3 # F0E6 963B # F0E7 96D5 # F0E8 9CE5 # F0E9 65CF # F0EA 7C07 # F0EB 8DB3 # F0EC 93C3 # F0ED 5B58 # F0EE 5C0A # F0EF 5352 # F0F0 62D9 # F0F1 731D # F0F2 5027 # F0F3 5B97 # F0F4 5F9E # F0F5 60B0 # F0F6 616B # F0F7 68D5 # F0F8 6DD9 # F0F9 742E # F0FA 7A2E # F0FB 7D42 # F0FC 7D9C # F0FD 7E31 # F0FE 816B # F1A1 8E2A # F1A2 8E35 # F1A3 937E # F1A4 9418 # F1A5 4F50 # F1A6 5750 # F1A7 5DE6 # F1A8 5EA7 # F1A9 632B # F1AA 7F6A # F1AB 4E3B # F1AC 4F4F # F1AD 4F8F # F1AE 505A # F1AF 59DD # F1B0 80C4 # F1B1 546A # F1B2 5468 # F1B3 55FE # F1B4 594F # F1B5 5B99 # F1B6 5DDE # F1B7 5EDA # F1B8 665D # F1B9 6731 # F1BA 67F1 # F1BB 682A # F1BC 6CE8 # F1BD 6D32 # F1BE 6E4A # F1BF 6F8D # F1C0 70B7 # F1C1 73E0 # F1C2 7587 # F1C3 7C4C # F1C4 7D02 # F1C5 7D2C # F1C6 7DA2 # F1C7 821F # F1C8 86DB # F1C9 8A3B # F1CA 8A85 # F1CB 8D70 # F1CC 8E8A # F1CD 8F33 # F1CE 9031 # F1CF 914E # F1D0 9152 # F1D1 9444 # F1D2 99D0 # F1D3 7AF9 # F1D4 7CA5 # F1D5 4FCA # F1D6 5101 # F1D7 51C6 # F1D8 57C8 # F1D9 5BEF # F1DA 5CFB # F1DB 6659 # F1DC 6A3D # F1DD 6D5A # F1DE 6E96 # F1DF 6FEC # F1E0 710C # F1E1 756F # F1E2 7AE3 # F1E3 8822 # F1E4 9021 # F1E5 9075 # F1E6 96CB # F1E7 99FF # F1E8 8301 # F1E9 4E2D # F1EA 4EF2 # F1EB 8846 # F1EC 91CD # F1ED 537D # F1EE 6ADB # F1EF 696B # F1F0 6C41 # F1F1 847A # F1F2 589E # F1F3 618E # F1F4 66FE # F1F5 62EF # F1F6 70DD # F1F7 7511 # F1F8 75C7 # F1F9 7E52 # F1FA 84B8 # F1FB 8B49 # F1FC 8D08 # F1FD 4E4B # F1FE 53EA # F2A1 54AB # F2A2 5730 # F2A3 5740 # F2A4 5FD7 # F2A5 6301 # F2A6 6307 # F2A7 646F # F2A8 652F # F2A9 65E8 # F2AA 667A # F2AB 679D # F2AC 67B3 # F2AD 6B62 # F2AE 6C60 # F2AF 6C9A # F2B0 6F2C # F2B1 77E5 # F2B2 7825 # F2B3 7949 # F2B4 7957 # F2B5 7D19 # F2B6 80A2 # F2B7 8102 # F2B8 81F3 # F2B9 829D # F2BA 82B7 # F2BB 8718 # F2BC 8A8C # F2BD F9FC # F2BE 8D04 # F2BF 8DBE # F2C0 9072 # F2C1 76F4 # F2C2 7A19 # F2C3 7A37 # F2C4 7E54 # F2C5 8077 # F2C6 5507 # F2C7 55D4 # F2C8 5875 # F2C9 632F # F2CA 6422 # F2CB 6649 # F2CC 664B # F2CD 686D # F2CE 699B # F2CF 6B84 # F2D0 6D25 # F2D1 6EB1 # F2D2 73CD # F2D3 7468 # F2D4 74A1 # F2D5 755B # F2D6 75B9 # F2D7 76E1 # F2D8 771E # F2D9 778B # F2DA 79E6 # F2DB 7E09 # F2DC 7E1D # F2DD 81FB # F2DE 852F # F2DF 8897 # F2E0 8A3A # F2E1 8CD1 # F2E2 8EEB # F2E3 8FB0 # F2E4 9032 # F2E5 93AD # F2E6 9663 # F2E7 9673 # F2E8 9707 # F2E9 4F84 # F2EA 53F1 # F2EB 59EA # F2EC 5AC9 # F2ED 5E19 # F2EE 684E # F2EF 74C6 # F2F0 75BE # F2F1 79E9 # F2F2 7A92 # F2F3 81A3 # F2F4 86ED # F2F5 8CEA # F2F6 8DCC # F2F7 8FED # F2F8 659F # F2F9 6715 # F2FA F9FD # F2FB 57F7 # F2FC 6F57 # F2FD 7DDD # F2FE 8F2F # F3A1 93F6 # F3A2 96C6 # F3A3 5FB5 # F3A4 61F2 # F3A5 6F84 # F3A6 4E14 # F3A7 4F98 # F3A8 501F # F3A9 53C9 # F3AA 55DF # F3AB 5D6F # F3AC 5DEE # F3AD 6B21 # F3AE 6B64 # F3AF 78CB # F3B0 7B9A # F3B1 F9FE # F3B2 8E49 # F3B3 8ECA # F3B4 906E # F3B5 6349 # F3B6 643E # F3B7 7740 # F3B8 7A84 # F3B9 932F # F3BA 947F # F3BB 9F6A # F3BC 64B0 # F3BD 6FAF # F3BE 71E6 # F3BF 74A8 # F3C0 74DA # F3C1 7AC4 # F3C2 7C12 # F3C3 7E82 # F3C4 7CB2 # F3C5 7E98 # F3C6 8B9A # F3C7 8D0A # F3C8 947D # F3C9 9910 # F3CA 994C # F3CB 5239 # F3CC 5BDF # F3CD 64E6 # F3CE 672D # F3CF 7D2E # F3D0 50ED # F3D1 53C3 # F3D2 5879 # F3D3 6158 # F3D4 6159 # F3D5 61FA # F3D6 65AC # F3D7 7AD9 # F3D8 8B92 # F3D9 8B96 # F3DA 5009 # F3DB 5021 # F3DC 5275 # F3DD 5531 # F3DE 5A3C # F3DF 5EE0 # F3E0 5F70 # F3E1 6134 # F3E2 655E # F3E3 660C # F3E4 6636 # F3E5 66A2 # F3E6 69CD # F3E7 6EC4 # F3E8 6F32 # F3E9 7316 # F3EA 7621 # F3EB 7A93 # F3EC 8139 # F3ED 8259 # F3EE 83D6 # F3EF 84BC # F3F0 50B5 # F3F1 57F0 # F3F2 5BC0 # F3F3 5BE8 # F3F4 5F69 # F3F5 63A1 # F3F6 7826 # F3F7 7DB5 # F3F8 83DC # F3F9 8521 # F3FA 91C7 # F3FB 91F5 # F3FC 518A # F3FD 67F5 # F3FE 7B56 # F4A1 8CAC # F4A2 51C4 # F4A3 59BB # F4A4 60BD # F4A5 8655 # F4A6 501C # F4A7 F9FF # F4A8 5254 # F4A9 5C3A # F4AA 617D # F4AB 621A # F4AC 62D3 # F4AD 64F2 # F4AE 65A5 # F4AF 6ECC # F4B0 7620 # F4B1 810A # F4B2 8E60 # F4B3 965F # F4B4 96BB # F4B5 4EDF # F4B6 5343 # F4B7 5598 # F4B8 5929 # F4B9 5DDD # F4BA 64C5 # F4BB 6CC9 # F4BC 6DFA # F4BD 7394 # F4BE 7A7F # F4BF 821B # F4C0 85A6 # F4C1 8CE4 # F4C2 8E10 # F4C3 9077 # F4C4 91E7 # F4C5 95E1 # F4C6 9621 # F4C7 97C6 # F4C8 51F8 # F4C9 54F2 # F4CA 5586 # F4CB 5FB9 # F4CC 64A4 # F4CD 6F88 # F4CE 7DB4 # F4CF 8F1F # F4D0 8F4D # F4D1 9435 # F4D2 50C9 # F4D3 5C16 # F4D4 6CBE # F4D5 6DFB # F4D6 751B # F4D7 77BB # F4D8 7C3D # F4D9 7C64 # F4DA 8A79 # F4DB 8AC2 # F4DC 581E # F4DD 59BE # F4DE 5E16 # F4DF 6377 # F4E0 7252 # F4E1 758A # F4E2 776B # F4E3 8ADC # F4E4 8CBC # F4E5 8F12 # F4E6 5EF3 # F4E7 6674 # F4E8 6DF8 # F4E9 807D # F4EA 83C1 # F4EB 8ACB # F4EC 9751 # F4ED 9BD6 # F4EE FA00 # F4EF 5243 # F4F0 66FF # F4F1 6D95 # F4F2 6EEF # F4F3 7DE0 # F4F4 8AE6 # F4F5 902E # F4F6 905E # F4F7 9AD4 # F4F8 521D # F4F9 527F # F4FA 54E8 # F4FB 6194 # F4FC 6284 # F4FD 62DB # F4FE 68A2 # F5A1 6912 # F5A2 695A # F5A3 6A35 # F5A4 7092 # F5A5 7126 # F5A6 785D # F5A7 7901 # F5A8 790E # F5A9 79D2 # F5AA 7A0D # F5AB 8096 # F5AC 8278 # F5AD 82D5 # F5AE 8349 # F5AF 8549 # F5B0 8C82 # F5B1 8D85 # F5B2 9162 # F5B3 918B # F5B4 91AE # F5B5 4FC3 # F5B6 56D1 # F5B7 71ED # F5B8 77D7 # F5B9 8700 # F5BA 89F8 # F5BB 5BF8 # F5BC 5FD6 # F5BD 6751 # F5BE 90A8 # F5BF 53E2 # F5C0 585A # F5C1 5BF5 # F5C2 60A4 # F5C3 6181 # F5C4 6460 # F5C5 7E3D # F5C6 8070 # F5C7 8525 # F5C8 9283 # F5C9 64AE # F5CA 50AC # F5CB 5D14 # F5CC 6700 # F5CD 589C # F5CE 62BD # F5CF 63A8 # F5D0 690E # F5D1 6978 # F5D2 6A1E # F5D3 6E6B # F5D4 76BA # F5D5 79CB # F5D6 82BB # F5D7 8429 # F5D8 8ACF # F5D9 8DA8 # F5DA 8FFD # F5DB 9112 # F5DC 914B # F5DD 919C # F5DE 9310 # F5DF 9318 # F5E0 939A # F5E1 96DB # F5E2 9A36 # F5E3 9C0D # F5E4 4E11 # F5E5 755C # F5E6 795D # F5E7 7AFA # F5E8 7B51 # F5E9 7BC9 # F5EA 7E2E # F5EB 84C4 # F5EC 8E59 # F5ED 8E74 # F5EE 8EF8 # F5EF 9010 # F5F0 6625 # F5F1 693F # F5F2 7443 # F5F3 51FA # F5F4 672E # F5F5 9EDC # F5F6 5145 # F5F7 5FE0 # F5F8 6C96 # F5F9 87F2 # F5FA 885D # F5FB 8877 # F5FC 60B4 # F5FD 81B5 # F5FE 8403 # F6A1 8D05 # F6A2 53D6 # F6A3 5439 # F6A4 5634 # F6A5 5A36 # F6A6 5C31 # F6A7 708A # F6A8 7FE0 # F6A9 805A # F6AA 8106 # F6AB 81ED # F6AC 8DA3 # F6AD 9189 # F6AE 9A5F # F6AF 9DF2 # F6B0 5074 # F6B1 4EC4 # F6B2 53A0 # F6B3 60FB # F6B4 6E2C # F6B5 5C64 # F6B6 4F88 # F6B7 5024 # F6B8 55E4 # F6B9 5CD9 # F6BA 5E5F # F6BB 6065 # F6BC 6894 # F6BD 6CBB # F6BE 6DC4 # F6BF 71BE # F6C0 75D4 # F6C1 75F4 # F6C2 7661 # F6C3 7A1A # F6C4 7A49 # F6C5 7DC7 # F6C6 7DFB # F6C7 7F6E # F6C8 81F4 # F6C9 86A9 # F6CA 8F1C # F6CB 96C9 # F6CC 99B3 # F6CD 9F52 # F6CE 5247 # F6CF 52C5 # F6D0 98ED # F6D1 89AA # F6D2 4E03 # F6D3 67D2 # F6D4 6F06 # F6D5 4FB5 # F6D6 5BE2 # F6D7 6795 # F6D8 6C88 # F6D9 6D78 # F6DA 741B # F6DB 7827 # F6DC 91DD # F6DD 937C # F6DE 87C4 # F6DF 79E4 # F6E0 7A31 # F6E1 5FEB # F6E2 4ED6 # F6E3 54A4 # F6E4 553E # F6E5 58AE # F6E6 59A5 # F6E7 60F0 # F6E8 6253 # F6E9 62D6 # F6EA 6736 # F6EB 6955 # F6EC 8235 # F6ED 9640 # F6EE 99B1 # F6EF 99DD # F6F0 502C # F6F1 5353 # F6F2 5544 # F6F3 577C # F6F4 FA01 # F6F5 6258 # F6F6 FA02 # F6F7 64E2 # F6F8 666B # F6F9 67DD # F6FA 6FC1 # F6FB 6FEF # F6FC 7422 # F6FD 7438 # F6FE 8A17 # F7A1 9438 # F7A2 5451 # F7A3 5606 # F7A4 5766 # F7A5 5F48 # F7A6 619A # F7A7 6B4E # F7A8 7058 # F7A9 70AD # F7AA 7DBB # F7AB 8A95 # F7AC 596A # F7AD 812B # F7AE 63A2 # F7AF 7708 # F7B0 803D # F7B1 8CAA # F7B2 5854 # F7B3 642D # F7B4 69BB # F7B5 5B95 # F7B6 5E11 # F7B7 6E6F # F7B8 FA03 # F7B9 8569 # F7BA 514C # F7BB 53F0 # F7BC 592A # F7BD 6020 # F7BE 614B # F7BF 6B86 # F7C0 6C70 # F7C1 6CF0 # F7C2 7B1E # F7C3 80CE # F7C4 82D4 # F7C5 8DC6 # F7C6 90B0 # F7C7 98B1 # F7C8 FA04 # F7C9 64C7 # F7CA 6FA4 # F7CB 6491 # F7CC 6504 # F7CD 514E # F7CE 5410 # F7CF 571F # F7D0 8A0E # F7D1 615F # F7D2 6876 # F7D3 FA05 # F7D4 75DB # F7D5 7B52 # F7D6 7D71 # F7D7 901A # F7D8 5806 # F7D9 69CC # F7DA 817F # F7DB 892A # F7DC 9000 # F7DD 9839 # F7DE 5078 # F7DF 5957 # F7E0 59AC # F7E1 6295 # F7E2 900F # F7E3 9B2A # F7E4 615D # F7E5 7279 # F7E6 95D6 # F7E7 5761 # F7E8 5A46 # F7E9 5DF4 # F7EA 628A # F7EB 64AD # F7EC 64FA # F7ED 6777 # F7EE 6CE2 # F7EF 6D3E # F7F0 722C # F7F1 7436 # F7F2 7834 # F7F3 7F77 # F7F4 82AD # F7F5 8DDB # F7F6 9817 # F7F7 5224 # F7F8 5742 # F7F9 677F # F7FA 7248 # F7FB 74E3 # F7FC 8CA9 # F7FD 8FA6 # F7FE 9211 # F8A1 962A # F8A2 516B # F8A3 53ED # F8A4 634C # F8A5 4F69 # F8A6 5504 # F8A7 6096 # F8A8 6557 # F8A9 6C9B # F8AA 6D7F # F8AB 724C # F8AC 72FD # F8AD 7A17 # F8AE 8987 # F8AF 8C9D # F8B0 5F6D # F8B1 6F8E # F8B2 70F9 # F8B3 81A8 # F8B4 610E # F8B5 4FBF # F8B6 504F # F8B7 6241 # F8B8 7247 # F8B9 7BC7 # F8BA 7DE8 # F8BB 7FE9 # F8BC 904D # F8BD 97AD # F8BE 9A19 # F8BF 8CB6 # F8C0 576A # F8C1 5E73 # F8C2 67B0 # F8C3 840D # F8C4 8A55 # F8C5 5420 # F8C6 5B16 # F8C7 5E63 # F8C8 5EE2 # F8C9 5F0A # F8CA 6583 # F8CB 80BA # F8CC 853D # F8CD 9589 # F8CE 965B # F8CF 4F48 # F8D0 5305 # F8D1 530D # F8D2 530F # F8D3 5486 # F8D4 54FA # F8D5 5703 # F8D6 5E03 # F8D7 6016 # F8D8 629B # F8D9 62B1 # F8DA 6355 # F8DB FA06 # F8DC 6CE1 # F8DD 6D66 # F8DE 75B1 # F8DF 7832 # F8E0 80DE # F8E1 812F # F8E2 82DE # F8E3 8461 # F8E4 84B2 # F8E5 888D # F8E6 8912 # F8E7 900B # F8E8 92EA # F8E9 98FD # F8EA 9B91 # F8EB 5E45 # F8EC 66B4 # F8ED 66DD # F8EE 7011 # F8EF 7206 # F8F0 FA07 # F8F1 4FF5 # F8F2 527D # F8F3 5F6A # F8F4 6153 # F8F5 6753 # F8F6 6A19 # F8F7 6F02 # F8F8 74E2 # F8F9 7968 # F8FA 8868 # F8FB 8C79 # F8FC 98C7 # F8FD 98C4 # F8FE 9A43 # F9A1 54C1 # F9A2 7A1F # F9A3 6953 # F9A4 8AF7 # F9A5 8C4A # F9A6 98A8 # F9A7 99AE # F9A8 5F7C # F9A9 62AB # F9AA 75B2 # F9AB 76AE # F9AC 88AB # F9AD 907F # F9AE 9642 # F9AF 5339 # F9B0 5F3C # F9B1 5FC5 # F9B2 6CCC # F9B3 73CC # F9B4 7562 # F9B5 758B # F9B6 7B46 # F9B7 82FE # F9B8 999D # F9B9 4E4F # F9BA 903C # F9BB 4E0B # F9BC 4F55 # F9BD 53A6 # F9BE 590F # F9BF 5EC8 # F9C0 6630 # F9C1 6CB3 # F9C2 7455 # F9C3 8377 # F9C4 8766 # F9C5 8CC0 # F9C6 9050 # F9C7 971E # F9C8 9C15 # F9C9 58D1 # F9CA 5B78 # F9CB 8650 # F9CC 8B14 # F9CD 9DB4 # F9CE 5BD2 # F9CF 6068 # F9D0 608D # F9D1 65F1 # F9D2 6C57 # F9D3 6F22 # F9D4 6FA3 # F9D5 701A # F9D6 7F55 # F9D7 7FF0 # F9D8 9591 # F9D9 9592 # F9DA 9650 # F9DB 97D3 # F9DC 5272 # F9DD 8F44 # F9DE 51FD # F9DF 542B # F9E0 54B8 # F9E1 5563 # F9E2 558A # F9E3 6ABB # F9E4 6DB5 # F9E5 7DD8 # F9E6 8266 # F9E7 929C # F9E8 9677 # F9E9 9E79 # F9EA 5408 # F9EB 54C8 # F9EC 76D2 # F9ED 86E4 # F9EE 95A4 # F9EF 95D4 # F9F0 965C # F9F1 4EA2 # F9F2 4F09 # F9F3 59EE # F9F4 5AE6 # F9F5 5DF7 # F9F6 6052 # F9F7 6297 # F9F8 676D # F9F9 6841 # F9FA 6C86 # F9FB 6E2F # F9FC 7F38 # F9FD 809B # F9FE 822A # FAA1 FA08 # FAA2 FA09 # FAA3 9805 # FAA4 4EA5 # FAA5 5055 # FAA6 54B3 # FAA7 5793 # FAA8 595A # FAA9 5B69 # FAAA 5BB3 # FAAB 61C8 # FAAC 6977 # FAAD 6D77 # FAAE 7023 # FAAF 87F9 # FAB0 89E3 # FAB1 8A72 # FAB2 8AE7 # FAB3 9082 # FAB4 99ED # FAB5 9AB8 # FAB6 52BE # FAB7 6838 # FAB8 5016 # FAB9 5E78 # FABA 674F # FABB 8347 # FABC 884C # FABD 4EAB # FABE 5411 # FABF 56AE # FAC0 73E6 # FAC1 9115 # FAC2 97FF # FAC3 9909 # FAC4 9957 # FAC5 9999 # FAC6 5653 # FAC7 589F # FAC8 865B # FAC9 8A31 # FACA 61B2 # FACB 6AF6 # FACC 737B # FACD 8ED2 # FACE 6B47 # FACF 96AA # FAD0 9A57 # FAD1 5955 # FAD2 7200 # FAD3 8D6B # FAD4 9769 # FAD5 4FD4 # FAD6 5CF4 # FAD7 5F26 # FAD8 61F8 # FAD9 665B # FADA 6CEB # FADB 70AB # FADC 7384 # FADD 73B9 # FADE 73FE # FADF 7729 # FAE0 774D # FAE1 7D43 # FAE2 7D62 # FAE3 7E23 # FAE4 8237 # FAE5 8852 # FAE6 FA0A # FAE7 8CE2 # FAE8 9249 # FAE9 986F # FAEA 5B51 # FAEB 7A74 # FAEC 8840 # FAED 9801 # FAEE 5ACC # FAEF 4FE0 # FAF0 5354 # FAF1 593E # FAF2 5CFD # FAF3 633E # FAF4 6D79 # FAF5 72F9 # FAF6 8105 # FAF7 8107 # FAF8 83A2 # FAF9 92CF # FAFA 9830 # FAFB 4EA8 # FAFC 5144 # FAFD 5211 # FAFE 578B # FBA1 5F62 # FBA2 6CC2 # FBA3 6ECE # FBA4 7005 # FBA5 7050 # FBA6 70AF # FBA7 7192 # FBA8 73E9 # FBA9 7469 # FBAA 834A # FBAB 87A2 # FBAC 8861 # FBAD 9008 # FBAE 90A2 # FBAF 93A3 # FBB0 99A8 # FBB1 516E # FBB2 5F57 # FBB3 60E0 # FBB4 6167 # FBB5 66B3 # FBB6 8559 # FBB7 8E4A # FBB8 91AF # FBB9 978B # FBBA 4E4E # FBBB 4E92 # FBBC 547C # FBBD 58D5 # FBBE 58FA # FBBF 597D # FBC0 5CB5 # FBC1 5F27 # FBC2 6236 # FBC3 6248 # FBC4 660A # FBC5 6667 # FBC6 6BEB # FBC7 6D69 # FBC8 6DCF # FBC9 6E56 # FBCA 6EF8 # FBCB 6F94 # FBCC 6FE0 # FBCD 6FE9 # FBCE 705D # FBCF 72D0 # FBD0 7425 # FBD1 745A # FBD2 74E0 # FBD3 7693 # FBD4 795C # FBD5 7CCA # FBD6 7E1E # FBD7 80E1 # FBD8 82A6 # FBD9 846B # FBDA 84BF # FBDB 864E # FBDC 865F # FBDD 8774 # FBDE 8B77 # FBDF 8C6A # FBE0 93AC # FBE1 9800 # FBE2 9865 # FBE3 60D1 # FBE4 6216 # FBE5 9177 # FBE6 5A5A # FBE7 660F # FBE8 6DF7 # FBE9 6E3E # FBEA 743F # FBEB 9B42 # FBEC 5FFD # FBED 60DA # FBEE 7B0F # FBEF 54C4 # FBF0 5F18 # FBF1 6C5E # FBF2 6CD3 # FBF3 6D2A # FBF4 70D8 # FBF5 7D05 # FBF6 8679 # FBF7 8A0C # FBF8 9D3B # FBF9 5316 # FBFA 548C # FBFB 5B05 # FBFC 6A3A # FBFD 706B # FBFE 7575 # FCA1 798D # FCA2 79BE # FCA3 82B1 # FCA4 83EF # FCA5 8A71 # FCA6 8B41 # FCA7 8CA8 # FCA8 9774 # FCA9 FA0B # FCAA 64F4 # FCAB 652B # FCAC 78BA # FCAD 78BB # FCAE 7A6B # FCAF 4E38 # FCB0 559A # FCB1 5950 # FCB2 5BA6 # FCB3 5E7B # FCB4 60A3 # FCB5 63DB # FCB6 6B61 # FCB7 6665 # FCB8 6853 # FCB9 6E19 # FCBA 7165 # FCBB 74B0 # FCBC 7D08 # FCBD 9084 # FCBE 9A69 # FCBF 9C25 # FCC0 6D3B # FCC1 6ED1 # FCC2 733E # FCC3 8C41 # FCC4 95CA # FCC5 51F0 # FCC6 5E4C # FCC7 5FA8 # FCC8 604D # FCC9 60F6 # FCCA 6130 # FCCB 614C # FCCC 6643 # FCCD 6644 # FCCE 69A5 # FCCF 6CC1 # FCD0 6E5F # FCD1 6EC9 # FCD2 6F62 # FCD3 714C # FCD4 749C # FCD5 7687 # FCD6 7BC1 # FCD7 7C27 # FCD8 8352 # FCD9 8757 # FCDA 9051 # FCDB 968D # FCDC 9EC3 # FCDD 532F # FCDE 56DE # FCDF 5EFB # FCE0 5F8A # FCE1 6062 # FCE2 6094 # FCE3 61F7 # FCE4 6666 # FCE5 6703 # FCE6 6A9C # FCE7 6DEE # FCE8 6FAE # FCE9 7070 # FCEA 736A # FCEB 7E6A # FCEC 81BE # FCED 8334 # FCEE 86D4 # FCEF 8AA8 # FCF0 8CC4 # FCF1 5283 # FCF2 7372 # FCF3 5B96 # FCF4 6A6B # FCF5 9404 # FCF6 54EE # FCF7 5686 # FCF8 5B5D # FCF9 6548 # FCFA 6585 # FCFB 66C9 # FCFC 689F # FCFD 6D8D # FCFE 6DC6 # FDA1 723B # FDA2 80B4 # FDA3 9175 # FDA4 9A4D # FDA5 4FAF # FDA6 5019 # FDA7 539A # FDA8 540E # FDA9 543C # FDAA 5589 # FDAB 55C5 # FDAC 5E3F # FDAD 5F8C # FDAE 673D # FDAF 7166 # FDB0 73DD # FDB1 9005 # FDB2 52DB # FDB3 52F3 # FDB4 5864 # FDB5 58CE # FDB6 7104 # FDB7 718F # FDB8 71FB # FDB9 85B0 # FDBA 8A13 # FDBB 6688 # FDBC 85A8 # FDBD 55A7 # FDBE 6684 # FDBF 714A # FDC0 8431 # FDC1 5349 # FDC2 5599 # FDC3 6BC1 # FDC4 5F59 # FDC5 5FBD # FDC6 63EE # FDC7 6689 # FDC8 7147 # FDC9 8AF1 # FDCA 8F1D # FDCB 9EBE # FDCC 4F11 # FDCD 643A # FDCE 70CB # FDCF 7566 # FDD0 8667 # FDD1 6064 # FDD2 8B4E # FDD3 9DF8 # FDD4 5147 # FDD5 51F6 # FDD6 5308 # FDD7 6D36 # FDD8 80F8 # FDD9 9ED1 # FDDA 6615 # FDDB 6B23 # FDDC 7098 # FDDD 75D5 # FDDE 5403 # FDDF 5C79 # FDE0 7D07 # FDE1 8A16 # FDE2 6B20 # FDE3 6B3D # FDE4 6B46 # FDE5 5438 # FDE6 6070 # FDE7 6D3D # FDE8 7FD5 # FDE9 8208 # FDEA 50D6 # FDEB 51DE # FDEC 559C # FDED 566B # FDEE 56CD # FDEF 59EC # FDF0 5B09 # FDF1 5E0C # FDF2 6199 # FDF3 6198 # FDF4 6231 # FDF5 665E # FDF6 66E6 # FDF7 7199 # FDF8 71B9 # FDF9 71BA # FDFA 72A7 # FDFB 79A7 # FDFC 7A00 # FDFD 7FB2 # FDFE 8A70 # cyrus-imapd-2.5.10/lib/charset/UnicodeData.txt0000644000175000017500000560430212772415051016113 000000000000000000;;Cc;0;BN;;;;;N;NULL;;;; 0001;;Cc;0;BN;;;;;N;START OF HEADING;;;; 0002;;Cc;0;BN;;;;;N;START OF TEXT;;;; 0003;;Cc;0;BN;;;;;N;END OF TEXT;;;; 0004;;Cc;0;BN;;;;;N;END OF TRANSMISSION;;;; 0005;;Cc;0;BN;;;;;N;ENQUIRY;;;; 0006;;Cc;0;BN;;;;;N;ACKNOWLEDGE;;;; 0007;;Cc;0;BN;;;;;N;BELL;;;; 0008;;Cc;0;BN;;;;;N;BACKSPACE;;;; 0009;;Cc;0;S;;;;;N;CHARACTER TABULATION;;;; 000A;;Cc;0;B;;;;;N;LINE FEED (LF);;;; 000B;;Cc;0;S;;;;;N;LINE TABULATION;;;; 000C;;Cc;0;WS;;;;;N;FORM FEED (FF);;;; 000D;;Cc;0;B;;;;;N;CARRIAGE RETURN (CR);;;; 000E;;Cc;0;BN;;;;;N;SHIFT OUT;;;; 000F;;Cc;0;BN;;;;;N;SHIFT IN;;;; 0010;;Cc;0;BN;;;;;N;DATA LINK ESCAPE;;;; 0011;;Cc;0;BN;;;;;N;DEVICE CONTROL ONE;;;; 0012;;Cc;0;BN;;;;;N;DEVICE CONTROL TWO;;;; 0013;;Cc;0;BN;;;;;N;DEVICE CONTROL THREE;;;; 0014;;Cc;0;BN;;;;;N;DEVICE CONTROL FOUR;;;; 0015;;Cc;0;BN;;;;;N;NEGATIVE ACKNOWLEDGE;;;; 0016;;Cc;0;BN;;;;;N;SYNCHRONOUS IDLE;;;; 0017;;Cc;0;BN;;;;;N;END OF TRANSMISSION BLOCK;;;; 0018;;Cc;0;BN;;;;;N;CANCEL;;;; 0019;;Cc;0;BN;;;;;N;END OF MEDIUM;;;; 001A;;Cc;0;BN;;;;;N;SUBSTITUTE;;;; 001B;;Cc;0;BN;;;;;N;ESCAPE;;;; 001C;;Cc;0;B;;;;;N;INFORMATION SEPARATOR FOUR;;;; 001D;;Cc;0;B;;;;;N;INFORMATION SEPARATOR THREE;;;; 001E;;Cc;0;B;;;;;N;INFORMATION SEPARATOR TWO;;;; 001F;;Cc;0;S;;;;;N;INFORMATION SEPARATOR ONE;;;; 0020;SPACE;Zs;0;WS;;;;;N;;;;; 0021;EXCLAMATION MARK;Po;0;ON;;;;;N;;;;; 0022;QUOTATION MARK;Po;0;ON;;;;;N;;;;; 0023;NUMBER SIGN;Po;0;ET;;;;;N;;;;; 0024;DOLLAR SIGN;Sc;0;ET;;;;;N;;;;; 0025;PERCENT SIGN;Po;0;ET;;;;;N;;;;; 0026;AMPERSAND;Po;0;ON;;;;;N;;;;; 0027;APOSTROPHE;Po;0;ON;;;;;N;APOSTROPHE-QUOTE;;;; 0028;LEFT PARENTHESIS;Ps;0;ON;;;;;Y;OPENING PARENTHESIS;;;; 0029;RIGHT PARENTHESIS;Pe;0;ON;;;;;Y;CLOSING PARENTHESIS;;;; 002A;ASTERISK;Po;0;ON;;;;;N;;;;; 002B;PLUS SIGN;Sm;0;ES;;;;;N;;;;; 002C;COMMA;Po;0;CS;;;;;N;;;;; 002D;HYPHEN-MINUS;Pd;0;ES;;;;;N;;;;; 002E;FULL STOP;Po;0;CS;;;;;N;PERIOD;;;; 002F;SOLIDUS;Po;0;CS;;;;;N;SLASH;;;; 0030;DIGIT ZERO;Nd;0;EN;;0;0;0;N;;;;; 0031;DIGIT ONE;Nd;0;EN;;1;1;1;N;;;;; 0032;DIGIT TWO;Nd;0;EN;;2;2;2;N;;;;; 0033;DIGIT THREE;Nd;0;EN;;3;3;3;N;;;;; 0034;DIGIT FOUR;Nd;0;EN;;4;4;4;N;;;;; 0035;DIGIT FIVE;Nd;0;EN;;5;5;5;N;;;;; 0036;DIGIT SIX;Nd;0;EN;;6;6;6;N;;;;; 0037;DIGIT SEVEN;Nd;0;EN;;7;7;7;N;;;;; 0038;DIGIT EIGHT;Nd;0;EN;;8;8;8;N;;;;; 0039;DIGIT NINE;Nd;0;EN;;9;9;9;N;;;;; 003A;COLON;Po;0;CS;;;;;N;;;;; 003B;SEMICOLON;Po;0;ON;;;;;N;;;;; 003C;LESS-THAN SIGN;Sm;0;ON;;;;;Y;;;;; 003D;EQUALS SIGN;Sm;0;ON;;;;;N;;;;; 003E;GREATER-THAN SIGN;Sm;0;ON;;;;;Y;;;;; 003F;QUESTION MARK;Po;0;ON;;;;;N;;;;; 0040;COMMERCIAL AT;Po;0;ON;;;;;N;;;;; 0041;LATIN CAPITAL LETTER A;Lu;0;L;;;;;N;;;;0061; 0042;LATIN CAPITAL LETTER B;Lu;0;L;;;;;N;;;;0062; 0043;LATIN CAPITAL LETTER C;Lu;0;L;;;;;N;;;;0063; 0044;LATIN CAPITAL LETTER D;Lu;0;L;;;;;N;;;;0064; 0045;LATIN CAPITAL LETTER E;Lu;0;L;;;;;N;;;;0065; 0046;LATIN CAPITAL LETTER F;Lu;0;L;;;;;N;;;;0066; 0047;LATIN CAPITAL LETTER G;Lu;0;L;;;;;N;;;;0067; 0048;LATIN CAPITAL LETTER H;Lu;0;L;;;;;N;;;;0068; 0049;LATIN CAPITAL LETTER I;Lu;0;L;;;;;N;;;;0069; 004A;LATIN CAPITAL LETTER J;Lu;0;L;;;;;N;;;;006A; 004B;LATIN CAPITAL LETTER K;Lu;0;L;;;;;N;;;;006B; 004C;LATIN CAPITAL LETTER L;Lu;0;L;;;;;N;;;;006C; 004D;LATIN CAPITAL LETTER M;Lu;0;L;;;;;N;;;;006D; 004E;LATIN CAPITAL LETTER N;Lu;0;L;;;;;N;;;;006E; 004F;LATIN CAPITAL LETTER O;Lu;0;L;;;;;N;;;;006F; 0050;LATIN CAPITAL LETTER P;Lu;0;L;;;;;N;;;;0070; 0051;LATIN CAPITAL LETTER Q;Lu;0;L;;;;;N;;;;0071; 0052;LATIN CAPITAL LETTER R;Lu;0;L;;;;;N;;;;0072; 0053;LATIN CAPITAL LETTER S;Lu;0;L;;;;;N;;;;0073; 0054;LATIN CAPITAL LETTER T;Lu;0;L;;;;;N;;;;0074; 0055;LATIN CAPITAL LETTER U;Lu;0;L;;;;;N;;;;0075; 0056;LATIN CAPITAL LETTER V;Lu;0;L;;;;;N;;;;0076; 0057;LATIN CAPITAL LETTER W;Lu;0;L;;;;;N;;;;0077; 0058;LATIN CAPITAL LETTER X;Lu;0;L;;;;;N;;;;0078; 0059;LATIN CAPITAL LETTER Y;Lu;0;L;;;;;N;;;;0079; 005A;LATIN CAPITAL LETTER Z;Lu;0;L;;;;;N;;;;007A; 005B;LEFT SQUARE BRACKET;Ps;0;ON;;;;;Y;OPENING SQUARE BRACKET;;;; 005C;REVERSE SOLIDUS;Po;0;ON;;;;;N;BACKSLASH;;;; 005D;RIGHT SQUARE BRACKET;Pe;0;ON;;;;;Y;CLOSING SQUARE BRACKET;;;; 005E;CIRCUMFLEX ACCENT;Sk;0;ON;;;;;N;SPACING CIRCUMFLEX;;;; 005F;LOW LINE;Pc;0;ON;;;;;N;SPACING UNDERSCORE;;;; 0060;GRAVE ACCENT;Sk;0;ON;;;;;N;SPACING GRAVE;;;; 0061;LATIN SMALL LETTER A;Ll;0;L;;;;;N;;;0041;;0041 0062;LATIN SMALL LETTER B;Ll;0;L;;;;;N;;;0042;;0042 0063;LATIN SMALL LETTER C;Ll;0;L;;;;;N;;;0043;;0043 0064;LATIN SMALL LETTER D;Ll;0;L;;;;;N;;;0044;;0044 0065;LATIN SMALL LETTER E;Ll;0;L;;;;;N;;;0045;;0045 0066;LATIN SMALL LETTER F;Ll;0;L;;;;;N;;;0046;;0046 0067;LATIN SMALL LETTER G;Ll;0;L;;;;;N;;;0047;;0047 0068;LATIN SMALL LETTER H;Ll;0;L;;;;;N;;;0048;;0048 0069;LATIN SMALL LETTER I;Ll;0;L;;;;;N;;;0049;;0049 006A;LATIN SMALL LETTER J;Ll;0;L;;;;;N;;;004A;;004A 006B;LATIN SMALL LETTER K;Ll;0;L;;;;;N;;;004B;;004B 006C;LATIN SMALL LETTER L;Ll;0;L;;;;;N;;;004C;;004C 006D;LATIN SMALL LETTER M;Ll;0;L;;;;;N;;;004D;;004D 006E;LATIN SMALL LETTER N;Ll;0;L;;;;;N;;;004E;;004E 006F;LATIN SMALL LETTER O;Ll;0;L;;;;;N;;;004F;;004F 0070;LATIN SMALL LETTER P;Ll;0;L;;;;;N;;;0050;;0050 0071;LATIN SMALL LETTER Q;Ll;0;L;;;;;N;;;0051;;0051 0072;LATIN SMALL LETTER R;Ll;0;L;;;;;N;;;0052;;0052 0073;LATIN SMALL LETTER S;Ll;0;L;;;;;N;;;0053;;0053 0074;LATIN SMALL LETTER T;Ll;0;L;;;;;N;;;0054;;0054 0075;LATIN SMALL LETTER U;Ll;0;L;;;;;N;;;0055;;0055 0076;LATIN SMALL LETTER V;Ll;0;L;;;;;N;;;0056;;0056 0077;LATIN SMALL LETTER W;Ll;0;L;;;;;N;;;0057;;0057 0078;LATIN SMALL LETTER X;Ll;0;L;;;;;N;;;0058;;0058 0079;LATIN SMALL LETTER Y;Ll;0;L;;;;;N;;;0059;;0059 007A;LATIN SMALL LETTER Z;Ll;0;L;;;;;N;;;005A;;005A 007B;LEFT CURLY BRACKET;Ps;0;ON;;;;;Y;OPENING CURLY BRACKET;;;; 007C;VERTICAL LINE;Sm;0;ON;;;;;N;VERTICAL BAR;;;; 007D;RIGHT CURLY BRACKET;Pe;0;ON;;;;;Y;CLOSING CURLY BRACKET;;;; 007E;TILDE;Sm;0;ON;;;;;N;;;;; 007F;;Cc;0;BN;;;;;N;DELETE;;;; 0080;;Cc;0;BN;;;;;N;;;;; 0081;;Cc;0;BN;;;;;N;;;;; 0082;;Cc;0;BN;;;;;N;BREAK PERMITTED HERE;;;; 0083;;Cc;0;BN;;;;;N;NO BREAK HERE;;;; 0084;;Cc;0;BN;;;;;N;;;;; 0085;;Cc;0;B;;;;;N;NEXT LINE (NEL);;;; 0086;;Cc;0;BN;;;;;N;START OF SELECTED AREA;;;; 0087;;Cc;0;BN;;;;;N;END OF SELECTED AREA;;;; 0088;;Cc;0;BN;;;;;N;CHARACTER TABULATION SET;;;; 0089;;Cc;0;BN;;;;;N;CHARACTER TABULATION WITH JUSTIFICATION;;;; 008A;;Cc;0;BN;;;;;N;LINE TABULATION SET;;;; 008B;;Cc;0;BN;;;;;N;PARTIAL LINE FORWARD;;;; 008C;;Cc;0;BN;;;;;N;PARTIAL LINE BACKWARD;;;; 008D;;Cc;0;BN;;;;;N;REVERSE LINE FEED;;;; 008E;;Cc;0;BN;;;;;N;SINGLE SHIFT TWO;;;; 008F;;Cc;0;BN;;;;;N;SINGLE SHIFT THREE;;;; 0090;;Cc;0;BN;;;;;N;DEVICE CONTROL STRING;;;; 0091;;Cc;0;BN;;;;;N;PRIVATE USE ONE;;;; 0092;;Cc;0;BN;;;;;N;PRIVATE USE TWO;;;; 0093;;Cc;0;BN;;;;;N;SET TRANSMIT STATE;;;; 0094;;Cc;0;BN;;;;;N;CANCEL CHARACTER;;;; 0095;;Cc;0;BN;;;;;N;MESSAGE WAITING;;;; 0096;;Cc;0;BN;;;;;N;START OF GUARDED AREA;;;; 0097;;Cc;0;BN;;;;;N;END OF GUARDED AREA;;;; 0098;;Cc;0;BN;;;;;N;START OF STRING;;;; 0099;;Cc;0;BN;;;;;N;;;;; 009A;;Cc;0;BN;;;;;N;SINGLE CHARACTER INTRODUCER;;;; 009B;;Cc;0;BN;;;;;N;CONTROL SEQUENCE INTRODUCER;;;; 009C;;Cc;0;BN;;;;;N;STRING TERMINATOR;;;; 009D;;Cc;0;BN;;;;;N;OPERATING SYSTEM COMMAND;;;; 009E;;Cc;0;BN;;;;;N;PRIVACY MESSAGE;;;; 009F;;Cc;0;BN;;;;;N;APPLICATION PROGRAM COMMAND;;;; 00A0;NO-BREAK SPACE;Zs;0;CS; 0020;;;;N;NON-BREAKING SPACE;;;; 00A1;INVERTED EXCLAMATION MARK;Po;0;ON;;;;;N;;;;; 00A2;CENT SIGN;Sc;0;ET;;;;;N;;;;; 00A3;POUND SIGN;Sc;0;ET;;;;;N;;;;; 00A4;CURRENCY SIGN;Sc;0;ET;;;;;N;;;;; 00A5;YEN SIGN;Sc;0;ET;;;;;N;;;;; 00A6;BROKEN BAR;So;0;ON;;;;;N;BROKEN VERTICAL BAR;;;; 00A7;SECTION SIGN;Po;0;ON;;;;;N;;;;; 00A8;DIAERESIS;Sk;0;ON; 0020 0308;;;;N;SPACING DIAERESIS;;;; 00A9;COPYRIGHT SIGN;So;0;ON;;;;;N;;;;; 00AA;FEMININE ORDINAL INDICATOR;Lo;0;L; 0061;;;;N;;;;; 00AB;LEFT-POINTING DOUBLE ANGLE QUOTATION MARK;Pi;0;ON;;;;;Y;LEFT POINTING GUILLEMET;;;; 00AC;NOT SIGN;Sm;0;ON;;;;;N;;;;; 00AD;SOFT HYPHEN;Cf;0;BN;;;;;N;;;;; 00AE;REGISTERED SIGN;So;0;ON;;;;;N;REGISTERED TRADE MARK SIGN;;;; 00AF;MACRON;Sk;0;ON; 0020 0304;;;;N;SPACING MACRON;;;; 00B0;DEGREE SIGN;So;0;ET;;;;;N;;;;; 00B1;PLUS-MINUS SIGN;Sm;0;ET;;;;;N;PLUS-OR-MINUS SIGN;;;; 00B2;SUPERSCRIPT TWO;No;0;EN; 0032;;2;2;N;SUPERSCRIPT DIGIT TWO;;;; 00B3;SUPERSCRIPT THREE;No;0;EN; 0033;;3;3;N;SUPERSCRIPT DIGIT THREE;;;; 00B4;ACUTE ACCENT;Sk;0;ON; 0020 0301;;;;N;SPACING ACUTE;;;; 00B5;MICRO SIGN;Ll;0;L; 03BC;;;;N;;;039C;;039C 00B6;PILCROW SIGN;Po;0;ON;;;;;N;PARAGRAPH SIGN;;;; 00B7;MIDDLE DOT;Po;0;ON;;;;;N;;;;; 00B8;CEDILLA;Sk;0;ON; 0020 0327;;;;N;SPACING CEDILLA;;;; 00B9;SUPERSCRIPT ONE;No;0;EN; 0031;;1;1;N;SUPERSCRIPT DIGIT ONE;;;; 00BA;MASCULINE ORDINAL INDICATOR;Lo;0;L; 006F;;;;N;;;;; 00BB;RIGHT-POINTING DOUBLE ANGLE QUOTATION MARK;Pf;0;ON;;;;;Y;RIGHT POINTING GUILLEMET;;;; 00BC;VULGAR FRACTION ONE QUARTER;No;0;ON; 0031 2044 0034;;;1/4;N;FRACTION ONE QUARTER;;;; 00BD;VULGAR FRACTION ONE HALF;No;0;ON; 0031 2044 0032;;;1/2;N;FRACTION ONE HALF;;;; 00BE;VULGAR FRACTION THREE QUARTERS;No;0;ON; 0033 2044 0034;;;3/4;N;FRACTION THREE QUARTERS;;;; 00BF;INVERTED QUESTION MARK;Po;0;ON;;;;;N;;;;; 00C0;LATIN CAPITAL LETTER A WITH GRAVE;Lu;0;L;0041 0300;;;;N;LATIN CAPITAL LETTER A GRAVE;;;00E0; 00C1;LATIN CAPITAL LETTER A WITH ACUTE;Lu;0;L;0041 0301;;;;N;LATIN CAPITAL LETTER A ACUTE;;;00E1; 00C2;LATIN CAPITAL LETTER A WITH CIRCUMFLEX;Lu;0;L;0041 0302;;;;N;LATIN CAPITAL LETTER A CIRCUMFLEX;;;00E2; 00C3;LATIN CAPITAL LETTER A WITH TILDE;Lu;0;L;0041 0303;;;;N;LATIN CAPITAL LETTER A TILDE;;;00E3; 00C4;LATIN CAPITAL LETTER A WITH DIAERESIS;Lu;0;L;0041 0308;;;;N;LATIN CAPITAL LETTER A DIAERESIS;;;00E4; 00C5;LATIN CAPITAL LETTER A WITH RING ABOVE;Lu;0;L;0041 030A;;;;N;LATIN CAPITAL LETTER A RING;;;00E5; 00C6;LATIN CAPITAL LETTER AE;Lu;0;L;;;;;N;LATIN CAPITAL LETTER A E;;;00E6; 00C7;LATIN CAPITAL LETTER C WITH CEDILLA;Lu;0;L;0043 0327;;;;N;LATIN CAPITAL LETTER C CEDILLA;;;00E7; 00C8;LATIN CAPITAL LETTER E WITH GRAVE;Lu;0;L;0045 0300;;;;N;LATIN CAPITAL LETTER E GRAVE;;;00E8; 00C9;LATIN CAPITAL LETTER E WITH ACUTE;Lu;0;L;0045 0301;;;;N;LATIN CAPITAL LETTER E ACUTE;;;00E9; 00CA;LATIN CAPITAL LETTER E WITH CIRCUMFLEX;Lu;0;L;0045 0302;;;;N;LATIN CAPITAL LETTER E CIRCUMFLEX;;;00EA; 00CB;LATIN CAPITAL LETTER E WITH DIAERESIS;Lu;0;L;0045 0308;;;;N;LATIN CAPITAL LETTER E DIAERESIS;;;00EB; 00CC;LATIN CAPITAL LETTER I WITH GRAVE;Lu;0;L;0049 0300;;;;N;LATIN CAPITAL LETTER I GRAVE;;;00EC; 00CD;LATIN CAPITAL LETTER I WITH ACUTE;Lu;0;L;0049 0301;;;;N;LATIN CAPITAL LETTER I ACUTE;;;00ED; 00CE;LATIN CAPITAL LETTER I WITH CIRCUMFLEX;Lu;0;L;0049 0302;;;;N;LATIN CAPITAL LETTER I CIRCUMFLEX;;;00EE; 00CF;LATIN CAPITAL LETTER I WITH DIAERESIS;Lu;0;L;0049 0308;;;;N;LATIN CAPITAL LETTER I DIAERESIS;;;00EF; 00D0;LATIN CAPITAL LETTER ETH;Lu;0;L;;;;;N;;;;00F0; 00D1;LATIN CAPITAL LETTER N WITH TILDE;Lu;0;L;004E 0303;;;;N;LATIN CAPITAL LETTER N TILDE;;;00F1; 00D2;LATIN CAPITAL LETTER O WITH GRAVE;Lu;0;L;004F 0300;;;;N;LATIN CAPITAL LETTER O GRAVE;;;00F2; 00D3;LATIN CAPITAL LETTER O WITH ACUTE;Lu;0;L;004F 0301;;;;N;LATIN CAPITAL LETTER O ACUTE;;;00F3; 00D4;LATIN CAPITAL LETTER O WITH CIRCUMFLEX;Lu;0;L;004F 0302;;;;N;LATIN CAPITAL LETTER O CIRCUMFLEX;;;00F4; 00D5;LATIN CAPITAL LETTER O WITH TILDE;Lu;0;L;004F 0303;;;;N;LATIN CAPITAL LETTER O TILDE;;;00F5; 00D6;LATIN CAPITAL LETTER O WITH DIAERESIS;Lu;0;L;004F 0308;;;;N;LATIN CAPITAL LETTER O DIAERESIS;;;00F6; 00D7;MULTIPLICATION SIGN;Sm;0;ON;;;;;N;;;;; 00D8;LATIN CAPITAL LETTER O WITH STROKE;Lu;0;L;;;;;N;LATIN CAPITAL LETTER O SLASH;;;00F8; 00D9;LATIN CAPITAL LETTER U WITH GRAVE;Lu;0;L;0055 0300;;;;N;LATIN CAPITAL LETTER U GRAVE;;;00F9; 00DA;LATIN CAPITAL LETTER U WITH ACUTE;Lu;0;L;0055 0301;;;;N;LATIN CAPITAL LETTER U ACUTE;;;00FA; 00DB;LATIN CAPITAL LETTER U WITH CIRCUMFLEX;Lu;0;L;0055 0302;;;;N;LATIN CAPITAL LETTER U CIRCUMFLEX;;;00FB; 00DC;LATIN CAPITAL LETTER U WITH DIAERESIS;Lu;0;L;0055 0308;;;;N;LATIN CAPITAL LETTER U DIAERESIS;;;00FC; 00DD;LATIN CAPITAL LETTER Y WITH ACUTE;Lu;0;L;0059 0301;;;;N;LATIN CAPITAL LETTER Y ACUTE;;;00FD; 00DE;LATIN CAPITAL LETTER THORN;Lu;0;L;;;;;N;;;;00FE; 00DF;LATIN SMALL LETTER SHARP S;Ll;0;L;;;;;N;;;;; 00E0;LATIN SMALL LETTER A WITH GRAVE;Ll;0;L;0061 0300;;;;N;LATIN SMALL LETTER A GRAVE;;00C0;;00C0 00E1;LATIN SMALL LETTER A WITH ACUTE;Ll;0;L;0061 0301;;;;N;LATIN SMALL LETTER A ACUTE;;00C1;;00C1 00E2;LATIN SMALL LETTER A WITH CIRCUMFLEX;Ll;0;L;0061 0302;;;;N;LATIN SMALL LETTER A CIRCUMFLEX;;00C2;;00C2 00E3;LATIN SMALL LETTER A WITH TILDE;Ll;0;L;0061 0303;;;;N;LATIN SMALL LETTER A TILDE;;00C3;;00C3 00E4;LATIN SMALL LETTER A WITH DIAERESIS;Ll;0;L;0061 0308;;;;N;LATIN SMALL LETTER A DIAERESIS;;00C4;;00C4 00E5;LATIN SMALL LETTER A WITH RING ABOVE;Ll;0;L;0061 030A;;;;N;LATIN SMALL LETTER A RING;;00C5;;00C5 00E6;LATIN SMALL LETTER AE;Ll;0;L;;;;;N;LATIN SMALL LETTER A E;;00C6;;00C6 00E7;LATIN SMALL LETTER C WITH CEDILLA;Ll;0;L;0063 0327;;;;N;LATIN SMALL LETTER C CEDILLA;;00C7;;00C7 00E8;LATIN SMALL LETTER E WITH GRAVE;Ll;0;L;0065 0300;;;;N;LATIN SMALL LETTER E GRAVE;;00C8;;00C8 00E9;LATIN SMALL LETTER E WITH ACUTE;Ll;0;L;0065 0301;;;;N;LATIN SMALL LETTER E ACUTE;;00C9;;00C9 00EA;LATIN SMALL LETTER E WITH CIRCUMFLEX;Ll;0;L;0065 0302;;;;N;LATIN SMALL LETTER E CIRCUMFLEX;;00CA;;00CA 00EB;LATIN SMALL LETTER E WITH DIAERESIS;Ll;0;L;0065 0308;;;;N;LATIN SMALL LETTER E DIAERESIS;;00CB;;00CB 00EC;LATIN SMALL LETTER I WITH GRAVE;Ll;0;L;0069 0300;;;;N;LATIN SMALL LETTER I GRAVE;;00CC;;00CC 00ED;LATIN SMALL LETTER I WITH ACUTE;Ll;0;L;0069 0301;;;;N;LATIN SMALL LETTER I ACUTE;;00CD;;00CD 00EE;LATIN SMALL LETTER I WITH CIRCUMFLEX;Ll;0;L;0069 0302;;;;N;LATIN SMALL LETTER I CIRCUMFLEX;;00CE;;00CE 00EF;LATIN SMALL LETTER I WITH DIAERESIS;Ll;0;L;0069 0308;;;;N;LATIN SMALL LETTER I DIAERESIS;;00CF;;00CF 00F0;LATIN SMALL LETTER ETH;Ll;0;L;;;;;N;;;00D0;;00D0 00F1;LATIN SMALL LETTER N WITH TILDE;Ll;0;L;006E 0303;;;;N;LATIN SMALL LETTER N TILDE;;00D1;;00D1 00F2;LATIN SMALL LETTER O WITH GRAVE;Ll;0;L;006F 0300;;;;N;LATIN SMALL LETTER O GRAVE;;00D2;;00D2 00F3;LATIN SMALL LETTER O WITH ACUTE;Ll;0;L;006F 0301;;;;N;LATIN SMALL LETTER O ACUTE;;00D3;;00D3 00F4;LATIN SMALL LETTER O WITH CIRCUMFLEX;Ll;0;L;006F 0302;;;;N;LATIN SMALL LETTER O CIRCUMFLEX;;00D4;;00D4 00F5;LATIN SMALL LETTER O WITH TILDE;Ll;0;L;006F 0303;;;;N;LATIN SMALL LETTER O TILDE;;00D5;;00D5 00F6;LATIN SMALL LETTER O WITH DIAERESIS;Ll;0;L;006F 0308;;;;N;LATIN SMALL LETTER O DIAERESIS;;00D6;;00D6 00F7;DIVISION SIGN;Sm;0;ON;;;;;N;;;;; 00F8;LATIN SMALL LETTER O WITH STROKE;Ll;0;L;;;;;N;LATIN SMALL LETTER O SLASH;;00D8;;00D8 00F9;LATIN SMALL LETTER U WITH GRAVE;Ll;0;L;0075 0300;;;;N;LATIN SMALL LETTER U GRAVE;;00D9;;00D9 00FA;LATIN SMALL LETTER U WITH ACUTE;Ll;0;L;0075 0301;;;;N;LATIN SMALL LETTER U ACUTE;;00DA;;00DA 00FB;LATIN SMALL LETTER U WITH CIRCUMFLEX;Ll;0;L;0075 0302;;;;N;LATIN SMALL LETTER U CIRCUMFLEX;;00DB;;00DB 00FC;LATIN SMALL LETTER U WITH DIAERESIS;Ll;0;L;0075 0308;;;;N;LATIN SMALL LETTER U DIAERESIS;;00DC;;00DC 00FD;LATIN SMALL LETTER Y WITH ACUTE;Ll;0;L;0079 0301;;;;N;LATIN SMALL LETTER Y ACUTE;;00DD;;00DD 00FE;LATIN SMALL LETTER THORN;Ll;0;L;;;;;N;;;00DE;;00DE 00FF;LATIN SMALL LETTER Y WITH DIAERESIS;Ll;0;L;0079 0308;;;;N;LATIN SMALL LETTER Y DIAERESIS;;0178;;0178 0100;LATIN CAPITAL LETTER A WITH MACRON;Lu;0;L;0041 0304;;;;N;LATIN CAPITAL LETTER A MACRON;;;0101; 0101;LATIN SMALL LETTER A WITH MACRON;Ll;0;L;0061 0304;;;;N;LATIN SMALL LETTER A MACRON;;0100;;0100 0102;LATIN CAPITAL LETTER A WITH BREVE;Lu;0;L;0041 0306;;;;N;LATIN CAPITAL LETTER A BREVE;;;0103; 0103;LATIN SMALL LETTER A WITH BREVE;Ll;0;L;0061 0306;;;;N;LATIN SMALL LETTER A BREVE;;0102;;0102 0104;LATIN CAPITAL LETTER A WITH OGONEK;Lu;0;L;0041 0328;;;;N;LATIN CAPITAL LETTER A OGONEK;;;0105; 0105;LATIN SMALL LETTER A WITH OGONEK;Ll;0;L;0061 0328;;;;N;LATIN SMALL LETTER A OGONEK;;0104;;0104 0106;LATIN CAPITAL LETTER C WITH ACUTE;Lu;0;L;0043 0301;;;;N;LATIN CAPITAL LETTER C ACUTE;;;0107; 0107;LATIN SMALL LETTER C WITH ACUTE;Ll;0;L;0063 0301;;;;N;LATIN SMALL LETTER C ACUTE;;0106;;0106 0108;LATIN CAPITAL LETTER C WITH CIRCUMFLEX;Lu;0;L;0043 0302;;;;N;LATIN CAPITAL LETTER C CIRCUMFLEX;;;0109; 0109;LATIN SMALL LETTER C WITH CIRCUMFLEX;Ll;0;L;0063 0302;;;;N;LATIN SMALL LETTER C CIRCUMFLEX;;0108;;0108 010A;LATIN CAPITAL LETTER C WITH DOT ABOVE;Lu;0;L;0043 0307;;;;N;LATIN CAPITAL LETTER C DOT;;;010B; 010B;LATIN SMALL LETTER C WITH DOT ABOVE;Ll;0;L;0063 0307;;;;N;LATIN SMALL LETTER C DOT;;010A;;010A 010C;LATIN CAPITAL LETTER C WITH CARON;Lu;0;L;0043 030C;;;;N;LATIN CAPITAL LETTER C HACEK;;;010D; 010D;LATIN SMALL LETTER C WITH CARON;Ll;0;L;0063 030C;;;;N;LATIN SMALL LETTER C HACEK;;010C;;010C 010E;LATIN CAPITAL LETTER D WITH CARON;Lu;0;L;0044 030C;;;;N;LATIN CAPITAL LETTER D HACEK;;;010F; 010F;LATIN SMALL LETTER D WITH CARON;Ll;0;L;0064 030C;;;;N;LATIN SMALL LETTER D HACEK;;010E;;010E 0110;LATIN CAPITAL LETTER D WITH STROKE;Lu;0;L;;;;;N;LATIN CAPITAL LETTER D BAR;;;0111; 0111;LATIN SMALL LETTER D WITH STROKE;Ll;0;L;;;;;N;LATIN SMALL LETTER D BAR;;0110;;0110 0112;LATIN CAPITAL LETTER E WITH MACRON;Lu;0;L;0045 0304;;;;N;LATIN CAPITAL LETTER E MACRON;;;0113; 0113;LATIN SMALL LETTER E WITH MACRON;Ll;0;L;0065 0304;;;;N;LATIN SMALL LETTER E MACRON;;0112;;0112 0114;LATIN CAPITAL LETTER E WITH BREVE;Lu;0;L;0045 0306;;;;N;LATIN CAPITAL LETTER E BREVE;;;0115; 0115;LATIN SMALL LETTER E WITH BREVE;Ll;0;L;0065 0306;;;;N;LATIN SMALL LETTER E BREVE;;0114;;0114 0116;LATIN CAPITAL LETTER E WITH DOT ABOVE;Lu;0;L;0045 0307;;;;N;LATIN CAPITAL LETTER E DOT;;;0117; 0117;LATIN SMALL LETTER E WITH DOT ABOVE;Ll;0;L;0065 0307;;;;N;LATIN SMALL LETTER E DOT;;0116;;0116 0118;LATIN CAPITAL LETTER E WITH OGONEK;Lu;0;L;0045 0328;;;;N;LATIN CAPITAL LETTER E OGONEK;;;0119; 0119;LATIN SMALL LETTER E WITH OGONEK;Ll;0;L;0065 0328;;;;N;LATIN SMALL LETTER E OGONEK;;0118;;0118 011A;LATIN CAPITAL LETTER E WITH CARON;Lu;0;L;0045 030C;;;;N;LATIN CAPITAL LETTER E HACEK;;;011B; 011B;LATIN SMALL LETTER E WITH CARON;Ll;0;L;0065 030C;;;;N;LATIN SMALL LETTER E HACEK;;011A;;011A 011C;LATIN CAPITAL LETTER G WITH CIRCUMFLEX;Lu;0;L;0047 0302;;;;N;LATIN CAPITAL LETTER G CIRCUMFLEX;;;011D; 011D;LATIN SMALL LETTER G WITH CIRCUMFLEX;Ll;0;L;0067 0302;;;;N;LATIN SMALL LETTER G CIRCUMFLEX;;011C;;011C 011E;LATIN CAPITAL LETTER G WITH BREVE;Lu;0;L;0047 0306;;;;N;LATIN CAPITAL LETTER G BREVE;;;011F; 011F;LATIN SMALL LETTER G WITH BREVE;Ll;0;L;0067 0306;;;;N;LATIN SMALL LETTER G BREVE;;011E;;011E 0120;LATIN CAPITAL LETTER G WITH DOT ABOVE;Lu;0;L;0047 0307;;;;N;LATIN CAPITAL LETTER G DOT;;;0121; 0121;LATIN SMALL LETTER G WITH DOT ABOVE;Ll;0;L;0067 0307;;;;N;LATIN SMALL LETTER G DOT;;0120;;0120 0122;LATIN CAPITAL LETTER G WITH CEDILLA;Lu;0;L;0047 0327;;;;N;LATIN CAPITAL LETTER G CEDILLA;;;0123; 0123;LATIN SMALL LETTER G WITH CEDILLA;Ll;0;L;0067 0327;;;;N;LATIN SMALL LETTER G CEDILLA;;0122;;0122 0124;LATIN CAPITAL LETTER H WITH CIRCUMFLEX;Lu;0;L;0048 0302;;;;N;LATIN CAPITAL LETTER H CIRCUMFLEX;;;0125; 0125;LATIN SMALL LETTER H WITH CIRCUMFLEX;Ll;0;L;0068 0302;;;;N;LATIN SMALL LETTER H CIRCUMFLEX;;0124;;0124 0126;LATIN CAPITAL LETTER H WITH STROKE;Lu;0;L;;;;;N;LATIN CAPITAL LETTER H BAR;;;0127; 0127;LATIN SMALL LETTER H WITH STROKE;Ll;0;L;;;;;N;LATIN SMALL LETTER H BAR;;0126;;0126 0128;LATIN CAPITAL LETTER I WITH TILDE;Lu;0;L;0049 0303;;;;N;LATIN CAPITAL LETTER I TILDE;;;0129; 0129;LATIN SMALL LETTER I WITH TILDE;Ll;0;L;0069 0303;;;;N;LATIN SMALL LETTER I TILDE;;0128;;0128 012A;LATIN CAPITAL LETTER I WITH MACRON;Lu;0;L;0049 0304;;;;N;LATIN CAPITAL LETTER I MACRON;;;012B; 012B;LATIN SMALL LETTER I WITH MACRON;Ll;0;L;0069 0304;;;;N;LATIN SMALL LETTER I MACRON;;012A;;012A 012C;LATIN CAPITAL LETTER I WITH BREVE;Lu;0;L;0049 0306;;;;N;LATIN CAPITAL LETTER I BREVE;;;012D; 012D;LATIN SMALL LETTER I WITH BREVE;Ll;0;L;0069 0306;;;;N;LATIN SMALL LETTER I BREVE;;012C;;012C 012E;LATIN CAPITAL LETTER I WITH OGONEK;Lu;0;L;0049 0328;;;;N;LATIN CAPITAL LETTER I OGONEK;;;012F; 012F;LATIN SMALL LETTER I WITH OGONEK;Ll;0;L;0069 0328;;;;N;LATIN SMALL LETTER I OGONEK;;012E;;012E 0130;LATIN CAPITAL LETTER I WITH DOT ABOVE;Lu;0;L;0049 0307;;;;N;LATIN CAPITAL LETTER I DOT;;;0069; 0131;LATIN SMALL LETTER DOTLESS I;Ll;0;L;;;;;N;;;0049;;0049 0132;LATIN CAPITAL LIGATURE IJ;Lu;0;L; 0049 004A;;;;N;LATIN CAPITAL LETTER I J;;;0133; 0133;LATIN SMALL LIGATURE IJ;Ll;0;L; 0069 006A;;;;N;LATIN SMALL LETTER I J;;0132;;0132 0134;LATIN CAPITAL LETTER J WITH CIRCUMFLEX;Lu;0;L;004A 0302;;;;N;LATIN CAPITAL LETTER J CIRCUMFLEX;;;0135; 0135;LATIN SMALL LETTER J WITH CIRCUMFLEX;Ll;0;L;006A 0302;;;;N;LATIN SMALL LETTER J CIRCUMFLEX;;0134;;0134 0136;LATIN CAPITAL LETTER K WITH CEDILLA;Lu;0;L;004B 0327;;;;N;LATIN CAPITAL LETTER K CEDILLA;;;0137; 0137;LATIN SMALL LETTER K WITH CEDILLA;Ll;0;L;006B 0327;;;;N;LATIN SMALL LETTER K CEDILLA;;0136;;0136 0138;LATIN SMALL LETTER KRA;Ll;0;L;;;;;N;;;;; 0139;LATIN CAPITAL LETTER L WITH ACUTE;Lu;0;L;004C 0301;;;;N;LATIN CAPITAL LETTER L ACUTE;;;013A; 013A;LATIN SMALL LETTER L WITH ACUTE;Ll;0;L;006C 0301;;;;N;LATIN SMALL LETTER L ACUTE;;0139;;0139 013B;LATIN CAPITAL LETTER L WITH CEDILLA;Lu;0;L;004C 0327;;;;N;LATIN CAPITAL LETTER L CEDILLA;;;013C; 013C;LATIN SMALL LETTER L WITH CEDILLA;Ll;0;L;006C 0327;;;;N;LATIN SMALL LETTER L CEDILLA;;013B;;013B 013D;LATIN CAPITAL LETTER L WITH CARON;Lu;0;L;004C 030C;;;;N;LATIN CAPITAL LETTER L HACEK;;;013E; 013E;LATIN SMALL LETTER L WITH CARON;Ll;0;L;006C 030C;;;;N;LATIN SMALL LETTER L HACEK;;013D;;013D 013F;LATIN CAPITAL LETTER L WITH MIDDLE DOT;Lu;0;L; 004C 00B7;;;;N;;;;0140; 0140;LATIN SMALL LETTER L WITH MIDDLE DOT;Ll;0;L; 006C 00B7;;;;N;;;013F;;013F 0141;LATIN CAPITAL LETTER L WITH STROKE;Lu;0;L;;;;;N;LATIN CAPITAL LETTER L SLASH;;;0142; 0142;LATIN SMALL LETTER L WITH STROKE;Ll;0;L;;;;;N;LATIN SMALL LETTER L SLASH;;0141;;0141 0143;LATIN CAPITAL LETTER N WITH ACUTE;Lu;0;L;004E 0301;;;;N;LATIN CAPITAL LETTER N ACUTE;;;0144; 0144;LATIN SMALL LETTER N WITH ACUTE;Ll;0;L;006E 0301;;;;N;LATIN SMALL LETTER N ACUTE;;0143;;0143 0145;LATIN CAPITAL LETTER N WITH CEDILLA;Lu;0;L;004E 0327;;;;N;LATIN CAPITAL LETTER N CEDILLA;;;0146; 0146;LATIN SMALL LETTER N WITH CEDILLA;Ll;0;L;006E 0327;;;;N;LATIN SMALL LETTER N CEDILLA;;0145;;0145 0147;LATIN CAPITAL LETTER N WITH CARON;Lu;0;L;004E 030C;;;;N;LATIN CAPITAL LETTER N HACEK;;;0148; 0148;LATIN SMALL LETTER N WITH CARON;Ll;0;L;006E 030C;;;;N;LATIN SMALL LETTER N HACEK;;0147;;0147 0149;LATIN SMALL LETTER N PRECEDED BY APOSTROPHE;Ll;0;L; 02BC 006E;;;;N;LATIN SMALL LETTER APOSTROPHE N;;;; 014A;LATIN CAPITAL LETTER ENG;Lu;0;L;;;;;N;;;;014B; 014B;LATIN SMALL LETTER ENG;Ll;0;L;;;;;N;;;014A;;014A 014C;LATIN CAPITAL LETTER O WITH MACRON;Lu;0;L;004F 0304;;;;N;LATIN CAPITAL LETTER O MACRON;;;014D; 014D;LATIN SMALL LETTER O WITH MACRON;Ll;0;L;006F 0304;;;;N;LATIN SMALL LETTER O MACRON;;014C;;014C 014E;LATIN CAPITAL LETTER O WITH BREVE;Lu;0;L;004F 0306;;;;N;LATIN CAPITAL LETTER O BREVE;;;014F; 014F;LATIN SMALL LETTER O WITH BREVE;Ll;0;L;006F 0306;;;;N;LATIN SMALL LETTER O BREVE;;014E;;014E 0150;LATIN CAPITAL LETTER O WITH DOUBLE ACUTE;Lu;0;L;004F 030B;;;;N;LATIN CAPITAL LETTER O DOUBLE ACUTE;;;0151; 0151;LATIN SMALL LETTER O WITH DOUBLE ACUTE;Ll;0;L;006F 030B;;;;N;LATIN SMALL LETTER O DOUBLE ACUTE;;0150;;0150 0152;LATIN CAPITAL LIGATURE OE;Lu;0;L;;;;;N;LATIN CAPITAL LETTER O E;;;0153; 0153;LATIN SMALL LIGATURE OE;Ll;0;L;;;;;N;LATIN SMALL LETTER O E;;0152;;0152 0154;LATIN CAPITAL LETTER R WITH ACUTE;Lu;0;L;0052 0301;;;;N;LATIN CAPITAL LETTER R ACUTE;;;0155; 0155;LATIN SMALL LETTER R WITH ACUTE;Ll;0;L;0072 0301;;;;N;LATIN SMALL LETTER R ACUTE;;0154;;0154 0156;LATIN CAPITAL LETTER R WITH CEDILLA;Lu;0;L;0052 0327;;;;N;LATIN CAPITAL LETTER R CEDILLA;;;0157; 0157;LATIN SMALL LETTER R WITH CEDILLA;Ll;0;L;0072 0327;;;;N;LATIN SMALL LETTER R CEDILLA;;0156;;0156 0158;LATIN CAPITAL LETTER R WITH CARON;Lu;0;L;0052 030C;;;;N;LATIN CAPITAL LETTER R HACEK;;;0159; 0159;LATIN SMALL LETTER R WITH CARON;Ll;0;L;0072 030C;;;;N;LATIN SMALL LETTER R HACEK;;0158;;0158 015A;LATIN CAPITAL LETTER S WITH ACUTE;Lu;0;L;0053 0301;;;;N;LATIN CAPITAL LETTER S ACUTE;;;015B; 015B;LATIN SMALL LETTER S WITH ACUTE;Ll;0;L;0073 0301;;;;N;LATIN SMALL LETTER S ACUTE;;015A;;015A 015C;LATIN CAPITAL LETTER S WITH CIRCUMFLEX;Lu;0;L;0053 0302;;;;N;LATIN CAPITAL LETTER S CIRCUMFLEX;;;015D; 015D;LATIN SMALL LETTER S WITH CIRCUMFLEX;Ll;0;L;0073 0302;;;;N;LATIN SMALL LETTER S CIRCUMFLEX;;015C;;015C 015E;LATIN CAPITAL LETTER S WITH CEDILLA;Lu;0;L;0053 0327;;;;N;LATIN CAPITAL LETTER S CEDILLA;;;015F; 015F;LATIN SMALL LETTER S WITH CEDILLA;Ll;0;L;0073 0327;;;;N;LATIN SMALL LETTER S CEDILLA;;015E;;015E 0160;LATIN CAPITAL LETTER S WITH CARON;Lu;0;L;0053 030C;;;;N;LATIN CAPITAL LETTER S HACEK;;;0161; 0161;LATIN SMALL LETTER S WITH CARON;Ll;0;L;0073 030C;;;;N;LATIN SMALL LETTER S HACEK;;0160;;0160 0162;LATIN CAPITAL LETTER T WITH CEDILLA;Lu;0;L;0054 0327;;;;N;LATIN CAPITAL LETTER T CEDILLA;;;0163; 0163;LATIN SMALL LETTER T WITH CEDILLA;Ll;0;L;0074 0327;;;;N;LATIN SMALL LETTER T CEDILLA;;0162;;0162 0164;LATIN CAPITAL LETTER T WITH CARON;Lu;0;L;0054 030C;;;;N;LATIN CAPITAL LETTER T HACEK;;;0165; 0165;LATIN SMALL LETTER T WITH CARON;Ll;0;L;0074 030C;;;;N;LATIN SMALL LETTER T HACEK;;0164;;0164 0166;LATIN CAPITAL LETTER T WITH STROKE;Lu;0;L;;;;;N;LATIN CAPITAL LETTER T BAR;;;0167; 0167;LATIN SMALL LETTER T WITH STROKE;Ll;0;L;;;;;N;LATIN SMALL LETTER T BAR;;0166;;0166 0168;LATIN CAPITAL LETTER U WITH TILDE;Lu;0;L;0055 0303;;;;N;LATIN CAPITAL LETTER U TILDE;;;0169; 0169;LATIN SMALL LETTER U WITH TILDE;Ll;0;L;0075 0303;;;;N;LATIN SMALL LETTER U TILDE;;0168;;0168 016A;LATIN CAPITAL LETTER U WITH MACRON;Lu;0;L;0055 0304;;;;N;LATIN CAPITAL LETTER U MACRON;;;016B; 016B;LATIN SMALL LETTER U WITH MACRON;Ll;0;L;0075 0304;;;;N;LATIN SMALL LETTER U MACRON;;016A;;016A 016C;LATIN CAPITAL LETTER U WITH BREVE;Lu;0;L;0055 0306;;;;N;LATIN CAPITAL LETTER U BREVE;;;016D; 016D;LATIN SMALL LETTER U WITH BREVE;Ll;0;L;0075 0306;;;;N;LATIN SMALL LETTER U BREVE;;016C;;016C 016E;LATIN CAPITAL LETTER U WITH RING ABOVE;Lu;0;L;0055 030A;;;;N;LATIN CAPITAL LETTER U RING;;;016F; 016F;LATIN SMALL LETTER U WITH RING ABOVE;Ll;0;L;0075 030A;;;;N;LATIN SMALL LETTER U RING;;016E;;016E 0170;LATIN CAPITAL LETTER U WITH DOUBLE ACUTE;Lu;0;L;0055 030B;;;;N;LATIN CAPITAL LETTER U DOUBLE ACUTE;;;0171; 0171;LATIN SMALL LETTER U WITH DOUBLE ACUTE;Ll;0;L;0075 030B;;;;N;LATIN SMALL LETTER U DOUBLE ACUTE;;0170;;0170 0172;LATIN CAPITAL LETTER U WITH OGONEK;Lu;0;L;0055 0328;;;;N;LATIN CAPITAL LETTER U OGONEK;;;0173; 0173;LATIN SMALL LETTER U WITH OGONEK;Ll;0;L;0075 0328;;;;N;LATIN SMALL LETTER U OGONEK;;0172;;0172 0174;LATIN CAPITAL LETTER W WITH CIRCUMFLEX;Lu;0;L;0057 0302;;;;N;LATIN CAPITAL LETTER W CIRCUMFLEX;;;0175; 0175;LATIN SMALL LETTER W WITH CIRCUMFLEX;Ll;0;L;0077 0302;;;;N;LATIN SMALL LETTER W CIRCUMFLEX;;0174;;0174 0176;LATIN CAPITAL LETTER Y WITH CIRCUMFLEX;Lu;0;L;0059 0302;;;;N;LATIN CAPITAL LETTER Y CIRCUMFLEX;;;0177; 0177;LATIN SMALL LETTER Y WITH CIRCUMFLEX;Ll;0;L;0079 0302;;;;N;LATIN SMALL LETTER Y CIRCUMFLEX;;0176;;0176 0178;LATIN CAPITAL LETTER Y WITH DIAERESIS;Lu;0;L;0059 0308;;;;N;LATIN CAPITAL LETTER Y DIAERESIS;;;00FF; 0179;LATIN CAPITAL LETTER Z WITH ACUTE;Lu;0;L;005A 0301;;;;N;LATIN CAPITAL LETTER Z ACUTE;;;017A; 017A;LATIN SMALL LETTER Z WITH ACUTE;Ll;0;L;007A 0301;;;;N;LATIN SMALL LETTER Z ACUTE;;0179;;0179 017B;LATIN CAPITAL LETTER Z WITH DOT ABOVE;Lu;0;L;005A 0307;;;;N;LATIN CAPITAL LETTER Z DOT;;;017C; 017C;LATIN SMALL LETTER Z WITH DOT ABOVE;Ll;0;L;007A 0307;;;;N;LATIN SMALL LETTER Z DOT;;017B;;017B 017D;LATIN CAPITAL LETTER Z WITH CARON;Lu;0;L;005A 030C;;;;N;LATIN CAPITAL LETTER Z HACEK;;;017E; 017E;LATIN SMALL LETTER Z WITH CARON;Ll;0;L;007A 030C;;;;N;LATIN SMALL LETTER Z HACEK;;017D;;017D 017F;LATIN SMALL LETTER LONG S;Ll;0;L; 0073;;;;N;;;0053;;0053 0180;LATIN SMALL LETTER B WITH STROKE;Ll;0;L;;;;;N;LATIN SMALL LETTER B BAR;;0243;;0243 0181;LATIN CAPITAL LETTER B WITH HOOK;Lu;0;L;;;;;N;LATIN CAPITAL LETTER B HOOK;;;0253; 0182;LATIN CAPITAL LETTER B WITH TOPBAR;Lu;0;L;;;;;N;LATIN CAPITAL LETTER B TOPBAR;;;0183; 0183;LATIN SMALL LETTER B WITH TOPBAR;Ll;0;L;;;;;N;LATIN SMALL LETTER B TOPBAR;;0182;;0182 0184;LATIN CAPITAL LETTER TONE SIX;Lu;0;L;;;;;N;;;;0185; 0185;LATIN SMALL LETTER TONE SIX;Ll;0;L;;;;;N;;;0184;;0184 0186;LATIN CAPITAL LETTER OPEN O;Lu;0;L;;;;;N;;;;0254; 0187;LATIN CAPITAL LETTER C WITH HOOK;Lu;0;L;;;;;N;LATIN CAPITAL LETTER C HOOK;;;0188; 0188;LATIN SMALL LETTER C WITH HOOK;Ll;0;L;;;;;N;LATIN SMALL LETTER C HOOK;;0187;;0187 0189;LATIN CAPITAL LETTER AFRICAN D;Lu;0;L;;;;;N;;;;0256; 018A;LATIN CAPITAL LETTER D WITH HOOK;Lu;0;L;;;;;N;LATIN CAPITAL LETTER D HOOK;;;0257; 018B;LATIN CAPITAL LETTER D WITH TOPBAR;Lu;0;L;;;;;N;LATIN CAPITAL LETTER D TOPBAR;;;018C; 018C;LATIN SMALL LETTER D WITH TOPBAR;Ll;0;L;;;;;N;LATIN SMALL LETTER D TOPBAR;;018B;;018B 018D;LATIN SMALL LETTER TURNED DELTA;Ll;0;L;;;;;N;;;;; 018E;LATIN CAPITAL LETTER REVERSED E;Lu;0;L;;;;;N;LATIN CAPITAL LETTER TURNED E;;;01DD; 018F;LATIN CAPITAL LETTER SCHWA;Lu;0;L;;;;;N;;;;0259; 0190;LATIN CAPITAL LETTER OPEN E;Lu;0;L;;;;;N;LATIN CAPITAL LETTER EPSILON;;;025B; 0191;LATIN CAPITAL LETTER F WITH HOOK;Lu;0;L;;;;;N;LATIN CAPITAL LETTER F HOOK;;;0192; 0192;LATIN SMALL LETTER F WITH HOOK;Ll;0;L;;;;;N;LATIN SMALL LETTER SCRIPT F;;0191;;0191 0193;LATIN CAPITAL LETTER G WITH HOOK;Lu;0;L;;;;;N;LATIN CAPITAL LETTER G HOOK;;;0260; 0194;LATIN CAPITAL LETTER GAMMA;Lu;0;L;;;;;N;;;;0263; 0195;LATIN SMALL LETTER HV;Ll;0;L;;;;;N;LATIN SMALL LETTER H V;;01F6;;01F6 0196;LATIN CAPITAL LETTER IOTA;Lu;0;L;;;;;N;;;;0269; 0197;LATIN CAPITAL LETTER I WITH STROKE;Lu;0;L;;;;;N;LATIN CAPITAL LETTER BARRED I;;;0268; 0198;LATIN CAPITAL LETTER K WITH HOOK;Lu;0;L;;;;;N;LATIN CAPITAL LETTER K HOOK;;;0199; 0199;LATIN SMALL LETTER K WITH HOOK;Ll;0;L;;;;;N;LATIN SMALL LETTER K HOOK;;0198;;0198 019A;LATIN SMALL LETTER L WITH BAR;Ll;0;L;;;;;N;LATIN SMALL LETTER BARRED L;;023D;;023D 019B;LATIN SMALL LETTER LAMBDA WITH STROKE;Ll;0;L;;;;;N;LATIN SMALL LETTER BARRED LAMBDA;;;; 019C;LATIN CAPITAL LETTER TURNED M;Lu;0;L;;;;;N;;;;026F; 019D;LATIN CAPITAL LETTER N WITH LEFT HOOK;Lu;0;L;;;;;N;LATIN CAPITAL LETTER N HOOK;;;0272; 019E;LATIN SMALL LETTER N WITH LONG RIGHT LEG;Ll;0;L;;;;;N;;;0220;;0220 019F;LATIN CAPITAL LETTER O WITH MIDDLE TILDE;Lu;0;L;;;;;N;LATIN CAPITAL LETTER BARRED O;;;0275; 01A0;LATIN CAPITAL LETTER O WITH HORN;Lu;0;L;004F 031B;;;;N;LATIN CAPITAL LETTER O HORN;;;01A1; 01A1;LATIN SMALL LETTER O WITH HORN;Ll;0;L;006F 031B;;;;N;LATIN SMALL LETTER O HORN;;01A0;;01A0 01A2;LATIN CAPITAL LETTER OI;Lu;0;L;;;;;N;LATIN CAPITAL LETTER O I;;;01A3; 01A3;LATIN SMALL LETTER OI;Ll;0;L;;;;;N;LATIN SMALL LETTER O I;;01A2;;01A2 01A4;LATIN CAPITAL LETTER P WITH HOOK;Lu;0;L;;;;;N;LATIN CAPITAL LETTER P HOOK;;;01A5; 01A5;LATIN SMALL LETTER P WITH HOOK;Ll;0;L;;;;;N;LATIN SMALL LETTER P HOOK;;01A4;;01A4 01A6;LATIN LETTER YR;Lu;0;L;;;;;N;LATIN LETTER Y R;;;0280; 01A7;LATIN CAPITAL LETTER TONE TWO;Lu;0;L;;;;;N;;;;01A8; 01A8;LATIN SMALL LETTER TONE TWO;Ll;0;L;;;;;N;;;01A7;;01A7 01A9;LATIN CAPITAL LETTER ESH;Lu;0;L;;;;;N;;;;0283; 01AA;LATIN LETTER REVERSED ESH LOOP;Ll;0;L;;;;;N;;;;; 01AB;LATIN SMALL LETTER T WITH PALATAL HOOK;Ll;0;L;;;;;N;LATIN SMALL LETTER T PALATAL HOOK;;;; 01AC;LATIN CAPITAL LETTER T WITH HOOK;Lu;0;L;;;;;N;LATIN CAPITAL LETTER T HOOK;;;01AD; 01AD;LATIN SMALL LETTER T WITH HOOK;Ll;0;L;;;;;N;LATIN SMALL LETTER T HOOK;;01AC;;01AC 01AE;LATIN CAPITAL LETTER T WITH RETROFLEX HOOK;Lu;0;L;;;;;N;LATIN CAPITAL LETTER T RETROFLEX HOOK;;;0288; 01AF;LATIN CAPITAL LETTER U WITH HORN;Lu;0;L;0055 031B;;;;N;LATIN CAPITAL LETTER U HORN;;;01B0; 01B0;LATIN SMALL LETTER U WITH HORN;Ll;0;L;0075 031B;;;;N;LATIN SMALL LETTER U HORN;;01AF;;01AF 01B1;LATIN CAPITAL LETTER UPSILON;Lu;0;L;;;;;N;;;;028A; 01B2;LATIN CAPITAL LETTER V WITH HOOK;Lu;0;L;;;;;N;LATIN CAPITAL LETTER SCRIPT V;;;028B; 01B3;LATIN CAPITAL LETTER Y WITH HOOK;Lu;0;L;;;;;N;LATIN CAPITAL LETTER Y HOOK;;;01B4; 01B4;LATIN SMALL LETTER Y WITH HOOK;Ll;0;L;;;;;N;LATIN SMALL LETTER Y HOOK;;01B3;;01B3 01B5;LATIN CAPITAL LETTER Z WITH STROKE;Lu;0;L;;;;;N;LATIN CAPITAL LETTER Z BAR;;;01B6; 01B6;LATIN SMALL LETTER Z WITH STROKE;Ll;0;L;;;;;N;LATIN SMALL LETTER Z BAR;;01B5;;01B5 01B7;LATIN CAPITAL LETTER EZH;Lu;0;L;;;;;N;LATIN CAPITAL LETTER YOGH;;;0292; 01B8;LATIN CAPITAL LETTER EZH REVERSED;Lu;0;L;;;;;N;LATIN CAPITAL LETTER REVERSED YOGH;;;01B9; 01B9;LATIN SMALL LETTER EZH REVERSED;Ll;0;L;;;;;N;LATIN SMALL LETTER REVERSED YOGH;;01B8;;01B8 01BA;LATIN SMALL LETTER EZH WITH TAIL;Ll;0;L;;;;;N;LATIN SMALL LETTER YOGH WITH TAIL;;;; 01BB;LATIN LETTER TWO WITH STROKE;Lo;0;L;;;;;N;LATIN LETTER TWO BAR;;;; 01BC;LATIN CAPITAL LETTER TONE FIVE;Lu;0;L;;;;;N;;;;01BD; 01BD;LATIN SMALL LETTER TONE FIVE;Ll;0;L;;;;;N;;;01BC;;01BC 01BE;LATIN LETTER INVERTED GLOTTAL STOP WITH STROKE;Ll;0;L;;;;;N;LATIN LETTER INVERTED GLOTTAL STOP BAR;;;; 01BF;LATIN LETTER WYNN;Ll;0;L;;;;;N;;;01F7;;01F7 01C0;LATIN LETTER DENTAL CLICK;Lo;0;L;;;;;N;LATIN LETTER PIPE;;;; 01C1;LATIN LETTER LATERAL CLICK;Lo;0;L;;;;;N;LATIN LETTER DOUBLE PIPE;;;; 01C2;LATIN LETTER ALVEOLAR CLICK;Lo;0;L;;;;;N;LATIN LETTER PIPE DOUBLE BAR;;;; 01C3;LATIN LETTER RETROFLEX CLICK;Lo;0;L;;;;;N;LATIN LETTER EXCLAMATION MARK;;;; 01C4;LATIN CAPITAL LETTER DZ WITH CARON;Lu;0;L; 0044 017D;;;;N;LATIN CAPITAL LETTER D Z HACEK;;;01C6;01C5 01C5;LATIN CAPITAL LETTER D WITH SMALL LETTER Z WITH CARON;Lt;0;L; 0044 017E;;;;N;LATIN LETTER CAPITAL D SMALL Z HACEK;;01C4;01C6;01C5 01C6;LATIN SMALL LETTER DZ WITH CARON;Ll;0;L; 0064 017E;;;;N;LATIN SMALL LETTER D Z HACEK;;01C4;;01C5 01C7;LATIN CAPITAL LETTER LJ;Lu;0;L; 004C 004A;;;;N;LATIN CAPITAL LETTER L J;;;01C9;01C8 01C8;LATIN CAPITAL LETTER L WITH SMALL LETTER J;Lt;0;L; 004C 006A;;;;N;LATIN LETTER CAPITAL L SMALL J;;01C7;01C9;01C8 01C9;LATIN SMALL LETTER LJ;Ll;0;L; 006C 006A;;;;N;LATIN SMALL LETTER L J;;01C7;;01C8 01CA;LATIN CAPITAL LETTER NJ;Lu;0;L; 004E 004A;;;;N;LATIN CAPITAL LETTER N J;;;01CC;01CB 01CB;LATIN CAPITAL LETTER N WITH SMALL LETTER J;Lt;0;L; 004E 006A;;;;N;LATIN LETTER CAPITAL N SMALL J;;01CA;01CC;01CB 01CC;LATIN SMALL LETTER NJ;Ll;0;L; 006E 006A;;;;N;LATIN SMALL LETTER N J;;01CA;;01CB 01CD;LATIN CAPITAL LETTER A WITH CARON;Lu;0;L;0041 030C;;;;N;LATIN CAPITAL LETTER A HACEK;;;01CE; 01CE;LATIN SMALL LETTER A WITH CARON;Ll;0;L;0061 030C;;;;N;LATIN SMALL LETTER A HACEK;;01CD;;01CD 01CF;LATIN CAPITAL LETTER I WITH CARON;Lu;0;L;0049 030C;;;;N;LATIN CAPITAL LETTER I HACEK;;;01D0; 01D0;LATIN SMALL LETTER I WITH CARON;Ll;0;L;0069 030C;;;;N;LATIN SMALL LETTER I HACEK;;01CF;;01CF 01D1;LATIN CAPITAL LETTER O WITH CARON;Lu;0;L;004F 030C;;;;N;LATIN CAPITAL LETTER O HACEK;;;01D2; 01D2;LATIN SMALL LETTER O WITH CARON;Ll;0;L;006F 030C;;;;N;LATIN SMALL LETTER O HACEK;;01D1;;01D1 01D3;LATIN CAPITAL LETTER U WITH CARON;Lu;0;L;0055 030C;;;;N;LATIN CAPITAL LETTER U HACEK;;;01D4; 01D4;LATIN SMALL LETTER U WITH CARON;Ll;0;L;0075 030C;;;;N;LATIN SMALL LETTER U HACEK;;01D3;;01D3 01D5;LATIN CAPITAL LETTER U WITH DIAERESIS AND MACRON;Lu;0;L;00DC 0304;;;;N;LATIN CAPITAL LETTER U DIAERESIS MACRON;;;01D6; 01D6;LATIN SMALL LETTER U WITH DIAERESIS AND MACRON;Ll;0;L;00FC 0304;;;;N;LATIN SMALL LETTER U DIAERESIS MACRON;;01D5;;01D5 01D7;LATIN CAPITAL LETTER U WITH DIAERESIS AND ACUTE;Lu;0;L;00DC 0301;;;;N;LATIN CAPITAL LETTER U DIAERESIS ACUTE;;;01D8; 01D8;LATIN SMALL LETTER U WITH DIAERESIS AND ACUTE;Ll;0;L;00FC 0301;;;;N;LATIN SMALL LETTER U DIAERESIS ACUTE;;01D7;;01D7 01D9;LATIN CAPITAL LETTER U WITH DIAERESIS AND CARON;Lu;0;L;00DC 030C;;;;N;LATIN CAPITAL LETTER U DIAERESIS HACEK;;;01DA; 01DA;LATIN SMALL LETTER U WITH DIAERESIS AND CARON;Ll;0;L;00FC 030C;;;;N;LATIN SMALL LETTER U DIAERESIS HACEK;;01D9;;01D9 01DB;LATIN CAPITAL LETTER U WITH DIAERESIS AND GRAVE;Lu;0;L;00DC 0300;;;;N;LATIN CAPITAL LETTER U DIAERESIS GRAVE;;;01DC; 01DC;LATIN SMALL LETTER U WITH DIAERESIS AND GRAVE;Ll;0;L;00FC 0300;;;;N;LATIN SMALL LETTER U DIAERESIS GRAVE;;01DB;;01DB 01DD;LATIN SMALL LETTER TURNED E;Ll;0;L;;;;;N;;;018E;;018E 01DE;LATIN CAPITAL LETTER A WITH DIAERESIS AND MACRON;Lu;0;L;00C4 0304;;;;N;LATIN CAPITAL LETTER A DIAERESIS MACRON;;;01DF; 01DF;LATIN SMALL LETTER A WITH DIAERESIS AND MACRON;Ll;0;L;00E4 0304;;;;N;LATIN SMALL LETTER A DIAERESIS MACRON;;01DE;;01DE 01E0;LATIN CAPITAL LETTER A WITH DOT ABOVE AND MACRON;Lu;0;L;0226 0304;;;;N;LATIN CAPITAL LETTER A DOT MACRON;;;01E1; 01E1;LATIN SMALL LETTER A WITH DOT ABOVE AND MACRON;Ll;0;L;0227 0304;;;;N;LATIN SMALL LETTER A DOT MACRON;;01E0;;01E0 01E2;LATIN CAPITAL LETTER AE WITH MACRON;Lu;0;L;00C6 0304;;;;N;LATIN CAPITAL LETTER A E MACRON;;;01E3; 01E3;LATIN SMALL LETTER AE WITH MACRON;Ll;0;L;00E6 0304;;;;N;LATIN SMALL LETTER A E MACRON;;01E2;;01E2 01E4;LATIN CAPITAL LETTER G WITH STROKE;Lu;0;L;;;;;N;LATIN CAPITAL LETTER G BAR;;;01E5; 01E5;LATIN SMALL LETTER G WITH STROKE;Ll;0;L;;;;;N;LATIN SMALL LETTER G BAR;;01E4;;01E4 01E6;LATIN CAPITAL LETTER G WITH CARON;Lu;0;L;0047 030C;;;;N;LATIN CAPITAL LETTER G HACEK;;;01E7; 01E7;LATIN SMALL LETTER G WITH CARON;Ll;0;L;0067 030C;;;;N;LATIN SMALL LETTER G HACEK;;01E6;;01E6 01E8;LATIN CAPITAL LETTER K WITH CARON;Lu;0;L;004B 030C;;;;N;LATIN CAPITAL LETTER K HACEK;;;01E9; 01E9;LATIN SMALL LETTER K WITH CARON;Ll;0;L;006B 030C;;;;N;LATIN SMALL LETTER K HACEK;;01E8;;01E8 01EA;LATIN CAPITAL LETTER O WITH OGONEK;Lu;0;L;004F 0328;;;;N;LATIN CAPITAL LETTER O OGONEK;;;01EB; 01EB;LATIN SMALL LETTER O WITH OGONEK;Ll;0;L;006F 0328;;;;N;LATIN SMALL LETTER O OGONEK;;01EA;;01EA 01EC;LATIN CAPITAL LETTER O WITH OGONEK AND MACRON;Lu;0;L;01EA 0304;;;;N;LATIN CAPITAL LETTER O OGONEK MACRON;;;01ED; 01ED;LATIN SMALL LETTER O WITH OGONEK AND MACRON;Ll;0;L;01EB 0304;;;;N;LATIN SMALL LETTER O OGONEK MACRON;;01EC;;01EC 01EE;LATIN CAPITAL LETTER EZH WITH CARON;Lu;0;L;01B7 030C;;;;N;LATIN CAPITAL LETTER YOGH HACEK;;;01EF; 01EF;LATIN SMALL LETTER EZH WITH CARON;Ll;0;L;0292 030C;;;;N;LATIN SMALL LETTER YOGH HACEK;;01EE;;01EE 01F0;LATIN SMALL LETTER J WITH CARON;Ll;0;L;006A 030C;;;;N;LATIN SMALL LETTER J HACEK;;;; 01F1;LATIN CAPITAL LETTER DZ;Lu;0;L; 0044 005A;;;;N;;;;01F3;01F2 01F2;LATIN CAPITAL LETTER D WITH SMALL LETTER Z;Lt;0;L; 0044 007A;;;;N;;;01F1;01F3;01F2 01F3;LATIN SMALL LETTER DZ;Ll;0;L; 0064 007A;;;;N;;;01F1;;01F2 01F4;LATIN CAPITAL LETTER G WITH ACUTE;Lu;0;L;0047 0301;;;;N;;;;01F5; 01F5;LATIN SMALL LETTER G WITH ACUTE;Ll;0;L;0067 0301;;;;N;;;01F4;;01F4 01F6;LATIN CAPITAL LETTER HWAIR;Lu;0;L;;;;;N;;;;0195; 01F7;LATIN CAPITAL LETTER WYNN;Lu;0;L;;;;;N;;;;01BF; 01F8;LATIN CAPITAL LETTER N WITH GRAVE;Lu;0;L;004E 0300;;;;N;;;;01F9; 01F9;LATIN SMALL LETTER N WITH GRAVE;Ll;0;L;006E 0300;;;;N;;;01F8;;01F8 01FA;LATIN CAPITAL LETTER A WITH RING ABOVE AND ACUTE;Lu;0;L;00C5 0301;;;;N;;;;01FB; 01FB;LATIN SMALL LETTER A WITH RING ABOVE AND ACUTE;Ll;0;L;00E5 0301;;;;N;;;01FA;;01FA 01FC;LATIN CAPITAL LETTER AE WITH ACUTE;Lu;0;L;00C6 0301;;;;N;;;;01FD; 01FD;LATIN SMALL LETTER AE WITH ACUTE;Ll;0;L;00E6 0301;;;;N;;;01FC;;01FC 01FE;LATIN CAPITAL LETTER O WITH STROKE AND ACUTE;Lu;0;L;00D8 0301;;;;N;;;;01FF; 01FF;LATIN SMALL LETTER O WITH STROKE AND ACUTE;Ll;0;L;00F8 0301;;;;N;;;01FE;;01FE 0200;LATIN CAPITAL LETTER A WITH DOUBLE GRAVE;Lu;0;L;0041 030F;;;;N;;;;0201; 0201;LATIN SMALL LETTER A WITH DOUBLE GRAVE;Ll;0;L;0061 030F;;;;N;;;0200;;0200 0202;LATIN CAPITAL LETTER A WITH INVERTED BREVE;Lu;0;L;0041 0311;;;;N;;;;0203; 0203;LATIN SMALL LETTER A WITH INVERTED BREVE;Ll;0;L;0061 0311;;;;N;;;0202;;0202 0204;LATIN CAPITAL LETTER E WITH DOUBLE GRAVE;Lu;0;L;0045 030F;;;;N;;;;0205; 0205;LATIN SMALL LETTER E WITH DOUBLE GRAVE;Ll;0;L;0065 030F;;;;N;;;0204;;0204 0206;LATIN CAPITAL LETTER E WITH INVERTED BREVE;Lu;0;L;0045 0311;;;;N;;;;0207; 0207;LATIN SMALL LETTER E WITH INVERTED BREVE;Ll;0;L;0065 0311;;;;N;;;0206;;0206 0208;LATIN CAPITAL LETTER I WITH DOUBLE GRAVE;Lu;0;L;0049 030F;;;;N;;;;0209; 0209;LATIN SMALL LETTER I WITH DOUBLE GRAVE;Ll;0;L;0069 030F;;;;N;;;0208;;0208 020A;LATIN CAPITAL LETTER I WITH INVERTED BREVE;Lu;0;L;0049 0311;;;;N;;;;020B; 020B;LATIN SMALL LETTER I WITH INVERTED BREVE;Ll;0;L;0069 0311;;;;N;;;020A;;020A 020C;LATIN CAPITAL LETTER O WITH DOUBLE GRAVE;Lu;0;L;004F 030F;;;;N;;;;020D; 020D;LATIN SMALL LETTER O WITH DOUBLE GRAVE;Ll;0;L;006F 030F;;;;N;;;020C;;020C 020E;LATIN CAPITAL LETTER O WITH INVERTED BREVE;Lu;0;L;004F 0311;;;;N;;;;020F; 020F;LATIN SMALL LETTER O WITH INVERTED BREVE;Ll;0;L;006F 0311;;;;N;;;020E;;020E 0210;LATIN CAPITAL LETTER R WITH DOUBLE GRAVE;Lu;0;L;0052 030F;;;;N;;;;0211; 0211;LATIN SMALL LETTER R WITH DOUBLE GRAVE;Ll;0;L;0072 030F;;;;N;;;0210;;0210 0212;LATIN CAPITAL LETTER R WITH INVERTED BREVE;Lu;0;L;0052 0311;;;;N;;;;0213; 0213;LATIN SMALL LETTER R WITH INVERTED BREVE;Ll;0;L;0072 0311;;;;N;;;0212;;0212 0214;LATIN CAPITAL LETTER U WITH DOUBLE GRAVE;Lu;0;L;0055 030F;;;;N;;;;0215; 0215;LATIN SMALL LETTER U WITH DOUBLE GRAVE;Ll;0;L;0075 030F;;;;N;;;0214;;0214 0216;LATIN CAPITAL LETTER U WITH INVERTED BREVE;Lu;0;L;0055 0311;;;;N;;;;0217; 0217;LATIN SMALL LETTER U WITH INVERTED BREVE;Ll;0;L;0075 0311;;;;N;;;0216;;0216 0218;LATIN CAPITAL LETTER S WITH COMMA BELOW;Lu;0;L;0053 0326;;;;N;;;;0219; 0219;LATIN SMALL LETTER S WITH COMMA BELOW;Ll;0;L;0073 0326;;;;N;;;0218;;0218 021A;LATIN CAPITAL LETTER T WITH COMMA BELOW;Lu;0;L;0054 0326;;;;N;;;;021B; 021B;LATIN SMALL LETTER T WITH COMMA BELOW;Ll;0;L;0074 0326;;;;N;;;021A;;021A 021C;LATIN CAPITAL LETTER YOGH;Lu;0;L;;;;;N;;;;021D; 021D;LATIN SMALL LETTER YOGH;Ll;0;L;;;;;N;;;021C;;021C 021E;LATIN CAPITAL LETTER H WITH CARON;Lu;0;L;0048 030C;;;;N;;;;021F; 021F;LATIN SMALL LETTER H WITH CARON;Ll;0;L;0068 030C;;;;N;;;021E;;021E 0220;LATIN CAPITAL LETTER N WITH LONG RIGHT LEG;Lu;0;L;;;;;N;;;;019E; 0221;LATIN SMALL LETTER D WITH CURL;Ll;0;L;;;;;N;;;;; 0222;LATIN CAPITAL LETTER OU;Lu;0;L;;;;;N;;;;0223; 0223;LATIN SMALL LETTER OU;Ll;0;L;;;;;N;;;0222;;0222 0224;LATIN CAPITAL LETTER Z WITH HOOK;Lu;0;L;;;;;N;;;;0225; 0225;LATIN SMALL LETTER Z WITH HOOK;Ll;0;L;;;;;N;;;0224;;0224 0226;LATIN CAPITAL LETTER A WITH DOT ABOVE;Lu;0;L;0041 0307;;;;N;;;;0227; 0227;LATIN SMALL LETTER A WITH DOT ABOVE;Ll;0;L;0061 0307;;;;N;;;0226;;0226 0228;LATIN CAPITAL LETTER E WITH CEDILLA;Lu;0;L;0045 0327;;;;N;;;;0229; 0229;LATIN SMALL LETTER E WITH CEDILLA;Ll;0;L;0065 0327;;;;N;;;0228;;0228 022A;LATIN CAPITAL LETTER O WITH DIAERESIS AND MACRON;Lu;0;L;00D6 0304;;;;N;;;;022B; 022B;LATIN SMALL LETTER O WITH DIAERESIS AND MACRON;Ll;0;L;00F6 0304;;;;N;;;022A;;022A 022C;LATIN CAPITAL LETTER O WITH TILDE AND MACRON;Lu;0;L;00D5 0304;;;;N;;;;022D; 022D;LATIN SMALL LETTER O WITH TILDE AND MACRON;Ll;0;L;00F5 0304;;;;N;;;022C;;022C 022E;LATIN CAPITAL LETTER O WITH DOT ABOVE;Lu;0;L;004F 0307;;;;N;;;;022F; 022F;LATIN SMALL LETTER O WITH DOT ABOVE;Ll;0;L;006F 0307;;;;N;;;022E;;022E 0230;LATIN CAPITAL LETTER O WITH DOT ABOVE AND MACRON;Lu;0;L;022E 0304;;;;N;;;;0231; 0231;LATIN SMALL LETTER O WITH DOT ABOVE AND MACRON;Ll;0;L;022F 0304;;;;N;;;0230;;0230 0232;LATIN CAPITAL LETTER Y WITH MACRON;Lu;0;L;0059 0304;;;;N;;;;0233; 0233;LATIN SMALL LETTER Y WITH MACRON;Ll;0;L;0079 0304;;;;N;;;0232;;0232 0234;LATIN SMALL LETTER L WITH CURL;Ll;0;L;;;;;N;;;;; 0235;LATIN SMALL LETTER N WITH CURL;Ll;0;L;;;;;N;;;;; 0236;LATIN SMALL LETTER T WITH CURL;Ll;0;L;;;;;N;;;;; 0237;LATIN SMALL LETTER DOTLESS J;Ll;0;L;;;;;N;;;;; 0238;LATIN SMALL LETTER DB DIGRAPH;Ll;0;L;;;;;N;;;;; 0239;LATIN SMALL LETTER QP DIGRAPH;Ll;0;L;;;;;N;;;;; 023A;LATIN CAPITAL LETTER A WITH STROKE;Lu;0;L;;;;;N;;;;2C65; 023B;LATIN CAPITAL LETTER C WITH STROKE;Lu;0;L;;;;;N;;;;023C; 023C;LATIN SMALL LETTER C WITH STROKE;Ll;0;L;;;;;N;;;023B;;023B 023D;LATIN CAPITAL LETTER L WITH BAR;Lu;0;L;;;;;N;;;;019A; 023E;LATIN CAPITAL LETTER T WITH DIAGONAL STROKE;Lu;0;L;;;;;N;;;;2C66; 023F;LATIN SMALL LETTER S WITH SWASH TAIL;Ll;0;L;;;;;N;;;2C7E;;2C7E 0240;LATIN SMALL LETTER Z WITH SWASH TAIL;Ll;0;L;;;;;N;;;2C7F;;2C7F 0241;LATIN CAPITAL LETTER GLOTTAL STOP;Lu;0;L;;;;;N;;;;0242; 0242;LATIN SMALL LETTER GLOTTAL STOP;Ll;0;L;;;;;N;;;0241;;0241 0243;LATIN CAPITAL LETTER B WITH STROKE;Lu;0;L;;;;;N;;;;0180; 0244;LATIN CAPITAL LETTER U BAR;Lu;0;L;;;;;N;;;;0289; 0245;LATIN CAPITAL LETTER TURNED V;Lu;0;L;;;;;N;;;;028C; 0246;LATIN CAPITAL LETTER E WITH STROKE;Lu;0;L;;;;;N;;;;0247; 0247;LATIN SMALL LETTER E WITH STROKE;Ll;0;L;;;;;N;;;0246;;0246 0248;LATIN CAPITAL LETTER J WITH STROKE;Lu;0;L;;;;;N;;;;0249; 0249;LATIN SMALL LETTER J WITH STROKE;Ll;0;L;;;;;N;;;0248;;0248 024A;LATIN CAPITAL LETTER SMALL Q WITH HOOK TAIL;Lu;0;L;;;;;N;;;;024B; 024B;LATIN SMALL LETTER Q WITH HOOK TAIL;Ll;0;L;;;;;N;;;024A;;024A 024C;LATIN CAPITAL LETTER R WITH STROKE;Lu;0;L;;;;;N;;;;024D; 024D;LATIN SMALL LETTER R WITH STROKE;Ll;0;L;;;;;N;;;024C;;024C 024E;LATIN CAPITAL LETTER Y WITH STROKE;Lu;0;L;;;;;N;;;;024F; 024F;LATIN SMALL LETTER Y WITH STROKE;Ll;0;L;;;;;N;;;024E;;024E 0250;LATIN SMALL LETTER TURNED A;Ll;0;L;;;;;N;;;2C6F;;2C6F 0251;LATIN SMALL LETTER ALPHA;Ll;0;L;;;;;N;LATIN SMALL LETTER SCRIPT A;;2C6D;;2C6D 0252;LATIN SMALL LETTER TURNED ALPHA;Ll;0;L;;;;;N;LATIN SMALL LETTER TURNED SCRIPT A;;2C70;;2C70 0253;LATIN SMALL LETTER B WITH HOOK;Ll;0;L;;;;;N;LATIN SMALL LETTER B HOOK;;0181;;0181 0254;LATIN SMALL LETTER OPEN O;Ll;0;L;;;;;N;;;0186;;0186 0255;LATIN SMALL LETTER C WITH CURL;Ll;0;L;;;;;N;LATIN SMALL LETTER C CURL;;;; 0256;LATIN SMALL LETTER D WITH TAIL;Ll;0;L;;;;;N;LATIN SMALL LETTER D RETROFLEX HOOK;;0189;;0189 0257;LATIN SMALL LETTER D WITH HOOK;Ll;0;L;;;;;N;LATIN SMALL LETTER D HOOK;;018A;;018A 0258;LATIN SMALL LETTER REVERSED E;Ll;0;L;;;;;N;;;;; 0259;LATIN SMALL LETTER SCHWA;Ll;0;L;;;;;N;;;018F;;018F 025A;LATIN SMALL LETTER SCHWA WITH HOOK;Ll;0;L;;;;;N;LATIN SMALL LETTER SCHWA HOOK;;;; 025B;LATIN SMALL LETTER OPEN E;Ll;0;L;;;;;N;LATIN SMALL LETTER EPSILON;;0190;;0190 025C;LATIN SMALL LETTER REVERSED OPEN E;Ll;0;L;;;;;N;LATIN SMALL LETTER REVERSED EPSILON;;A7AB;;A7AB 025D;LATIN SMALL LETTER REVERSED OPEN E WITH HOOK;Ll;0;L;;;;;N;LATIN SMALL LETTER REVERSED EPSILON HOOK;;;; 025E;LATIN SMALL LETTER CLOSED REVERSED OPEN E;Ll;0;L;;;;;N;LATIN SMALL LETTER CLOSED REVERSED EPSILON;;;; 025F;LATIN SMALL LETTER DOTLESS J WITH STROKE;Ll;0;L;;;;;N;LATIN SMALL LETTER DOTLESS J BAR;;;; 0260;LATIN SMALL LETTER G WITH HOOK;Ll;0;L;;;;;N;LATIN SMALL LETTER G HOOK;;0193;;0193 0261;LATIN SMALL LETTER SCRIPT G;Ll;0;L;;;;;N;;;A7AC;;A7AC 0262;LATIN LETTER SMALL CAPITAL G;Ll;0;L;;;;;N;;;;; 0263;LATIN SMALL LETTER GAMMA;Ll;0;L;;;;;N;;;0194;;0194 0264;LATIN SMALL LETTER RAMS HORN;Ll;0;L;;;;;N;LATIN SMALL LETTER BABY GAMMA;;;; 0265;LATIN SMALL LETTER TURNED H;Ll;0;L;;;;;N;;;A78D;;A78D 0266;LATIN SMALL LETTER H WITH HOOK;Ll;0;L;;;;;N;LATIN SMALL LETTER H HOOK;;A7AA;;A7AA 0267;LATIN SMALL LETTER HENG WITH HOOK;Ll;0;L;;;;;N;LATIN SMALL LETTER HENG HOOK;;;; 0268;LATIN SMALL LETTER I WITH STROKE;Ll;0;L;;;;;N;LATIN SMALL LETTER BARRED I;;0197;;0197 0269;LATIN SMALL LETTER IOTA;Ll;0;L;;;;;N;;;0196;;0196 026A;LATIN LETTER SMALL CAPITAL I;Ll;0;L;;;;;N;;;;; 026B;LATIN SMALL LETTER L WITH MIDDLE TILDE;Ll;0;L;;;;;N;;;2C62;;2C62 026C;LATIN SMALL LETTER L WITH BELT;Ll;0;L;;;;;N;LATIN SMALL LETTER L BELT;;A7AD;;A7AD 026D;LATIN SMALL LETTER L WITH RETROFLEX HOOK;Ll;0;L;;;;;N;LATIN SMALL LETTER L RETROFLEX HOOK;;;; 026E;LATIN SMALL LETTER LEZH;Ll;0;L;;;;;N;LATIN SMALL LETTER L YOGH;;;; 026F;LATIN SMALL LETTER TURNED M;Ll;0;L;;;;;N;;;019C;;019C 0270;LATIN SMALL LETTER TURNED M WITH LONG LEG;Ll;0;L;;;;;N;;;;; 0271;LATIN SMALL LETTER M WITH HOOK;Ll;0;L;;;;;N;LATIN SMALL LETTER M HOOK;;2C6E;;2C6E 0272;LATIN SMALL LETTER N WITH LEFT HOOK;Ll;0;L;;;;;N;LATIN SMALL LETTER N HOOK;;019D;;019D 0273;LATIN SMALL LETTER N WITH RETROFLEX HOOK;Ll;0;L;;;;;N;LATIN SMALL LETTER N RETROFLEX HOOK;;;; 0274;LATIN LETTER SMALL CAPITAL N;Ll;0;L;;;;;N;;;;; 0275;LATIN SMALL LETTER BARRED O;Ll;0;L;;;;;N;;;019F;;019F 0276;LATIN LETTER SMALL CAPITAL OE;Ll;0;L;;;;;N;LATIN LETTER SMALL CAPITAL O E;;;; 0277;LATIN SMALL LETTER CLOSED OMEGA;Ll;0;L;;;;;N;;;;; 0278;LATIN SMALL LETTER PHI;Ll;0;L;;;;;N;;;;; 0279;LATIN SMALL LETTER TURNED R;Ll;0;L;;;;;N;;;;; 027A;LATIN SMALL LETTER TURNED R WITH LONG LEG;Ll;0;L;;;;;N;;;;; 027B;LATIN SMALL LETTER TURNED R WITH HOOK;Ll;0;L;;;;;N;LATIN SMALL LETTER TURNED R HOOK;;;; 027C;LATIN SMALL LETTER R WITH LONG LEG;Ll;0;L;;;;;N;;;;; 027D;LATIN SMALL LETTER R WITH TAIL;Ll;0;L;;;;;N;LATIN SMALL LETTER R HOOK;;2C64;;2C64 027E;LATIN SMALL LETTER R WITH FISHHOOK;Ll;0;L;;;;;N;LATIN SMALL LETTER FISHHOOK R;;;; 027F;LATIN SMALL LETTER REVERSED R WITH FISHHOOK;Ll;0;L;;;;;N;LATIN SMALL LETTER REVERSED FISHHOOK R;;;; 0280;LATIN LETTER SMALL CAPITAL R;Ll;0;L;;;;;N;;;01A6;;01A6 0281;LATIN LETTER SMALL CAPITAL INVERTED R;Ll;0;L;;;;;N;;;;; 0282;LATIN SMALL LETTER S WITH HOOK;Ll;0;L;;;;;N;LATIN SMALL LETTER S HOOK;;;; 0283;LATIN SMALL LETTER ESH;Ll;0;L;;;;;N;;;01A9;;01A9 0284;LATIN SMALL LETTER DOTLESS J WITH STROKE AND HOOK;Ll;0;L;;;;;N;LATIN SMALL LETTER DOTLESS J BAR HOOK;;;; 0285;LATIN SMALL LETTER SQUAT REVERSED ESH;Ll;0;L;;;;;N;;;;; 0286;LATIN SMALL LETTER ESH WITH CURL;Ll;0;L;;;;;N;LATIN SMALL LETTER ESH CURL;;;; 0287;LATIN SMALL LETTER TURNED T;Ll;0;L;;;;;N;;;A7B1;;A7B1 0288;LATIN SMALL LETTER T WITH RETROFLEX HOOK;Ll;0;L;;;;;N;LATIN SMALL LETTER T RETROFLEX HOOK;;01AE;;01AE 0289;LATIN SMALL LETTER U BAR;Ll;0;L;;;;;N;;;0244;;0244 028A;LATIN SMALL LETTER UPSILON;Ll;0;L;;;;;N;;;01B1;;01B1 028B;LATIN SMALL LETTER V WITH HOOK;Ll;0;L;;;;;N;LATIN SMALL LETTER SCRIPT V;;01B2;;01B2 028C;LATIN SMALL LETTER TURNED V;Ll;0;L;;;;;N;;;0245;;0245 028D;LATIN SMALL LETTER TURNED W;Ll;0;L;;;;;N;;;;; 028E;LATIN SMALL LETTER TURNED Y;Ll;0;L;;;;;N;;;;; 028F;LATIN LETTER SMALL CAPITAL Y;Ll;0;L;;;;;N;;;;; 0290;LATIN SMALL LETTER Z WITH RETROFLEX HOOK;Ll;0;L;;;;;N;LATIN SMALL LETTER Z RETROFLEX HOOK;;;; 0291;LATIN SMALL LETTER Z WITH CURL;Ll;0;L;;;;;N;LATIN SMALL LETTER Z CURL;;;; 0292;LATIN SMALL LETTER EZH;Ll;0;L;;;;;N;LATIN SMALL LETTER YOGH;;01B7;;01B7 0293;LATIN SMALL LETTER EZH WITH CURL;Ll;0;L;;;;;N;LATIN SMALL LETTER YOGH CURL;;;; 0294;LATIN LETTER GLOTTAL STOP;Lo;0;L;;;;;N;;;;; 0295;LATIN LETTER PHARYNGEAL VOICED FRICATIVE;Ll;0;L;;;;;N;LATIN LETTER REVERSED GLOTTAL STOP;;;; 0296;LATIN LETTER INVERTED GLOTTAL STOP;Ll;0;L;;;;;N;;;;; 0297;LATIN LETTER STRETCHED C;Ll;0;L;;;;;N;;;;; 0298;LATIN LETTER BILABIAL CLICK;Ll;0;L;;;;;N;LATIN LETTER BULLSEYE;;;; 0299;LATIN LETTER SMALL CAPITAL B;Ll;0;L;;;;;N;;;;; 029A;LATIN SMALL LETTER CLOSED OPEN E;Ll;0;L;;;;;N;LATIN SMALL LETTER CLOSED EPSILON;;;; 029B;LATIN LETTER SMALL CAPITAL G WITH HOOK;Ll;0;L;;;;;N;LATIN LETTER SMALL CAPITAL G HOOK;;;; 029C;LATIN LETTER SMALL CAPITAL H;Ll;0;L;;;;;N;;;;; 029D;LATIN SMALL LETTER J WITH CROSSED-TAIL;Ll;0;L;;;;;N;LATIN SMALL LETTER CROSSED-TAIL J;;;; 029E;LATIN SMALL LETTER TURNED K;Ll;0;L;;;;;N;;;A7B0;;A7B0 029F;LATIN LETTER SMALL CAPITAL L;Ll;0;L;;;;;N;;;;; 02A0;LATIN SMALL LETTER Q WITH HOOK;Ll;0;L;;;;;N;LATIN SMALL LETTER Q HOOK;;;; 02A1;LATIN LETTER GLOTTAL STOP WITH STROKE;Ll;0;L;;;;;N;LATIN LETTER GLOTTAL STOP BAR;;;; 02A2;LATIN LETTER REVERSED GLOTTAL STOP WITH STROKE;Ll;0;L;;;;;N;LATIN LETTER REVERSED GLOTTAL STOP BAR;;;; 02A3;LATIN SMALL LETTER DZ DIGRAPH;Ll;0;L;;;;;N;LATIN SMALL LETTER D Z;;;; 02A4;LATIN SMALL LETTER DEZH DIGRAPH;Ll;0;L;;;;;N;LATIN SMALL LETTER D YOGH;;;; 02A5;LATIN SMALL LETTER DZ DIGRAPH WITH CURL;Ll;0;L;;;;;N;LATIN SMALL LETTER D Z CURL;;;; 02A6;LATIN SMALL LETTER TS DIGRAPH;Ll;0;L;;;;;N;LATIN SMALL LETTER T S;;;; 02A7;LATIN SMALL LETTER TESH DIGRAPH;Ll;0;L;;;;;N;LATIN SMALL LETTER T ESH;;;; 02A8;LATIN SMALL LETTER TC DIGRAPH WITH CURL;Ll;0;L;;;;;N;LATIN SMALL LETTER T C CURL;;;; 02A9;LATIN SMALL LETTER FENG DIGRAPH;Ll;0;L;;;;;N;;;;; 02AA;LATIN SMALL LETTER LS DIGRAPH;Ll;0;L;;;;;N;;;;; 02AB;LATIN SMALL LETTER LZ DIGRAPH;Ll;0;L;;;;;N;;;;; 02AC;LATIN LETTER BILABIAL PERCUSSIVE;Ll;0;L;;;;;N;;;;; 02AD;LATIN LETTER BIDENTAL PERCUSSIVE;Ll;0;L;;;;;N;;;;; 02AE;LATIN SMALL LETTER TURNED H WITH FISHHOOK;Ll;0;L;;;;;N;;;;; 02AF;LATIN SMALL LETTER TURNED H WITH FISHHOOK AND TAIL;Ll;0;L;;;;;N;;;;; 02B0;MODIFIER LETTER SMALL H;Lm;0;L; 0068;;;;N;;;;; 02B1;MODIFIER LETTER SMALL H WITH HOOK;Lm;0;L; 0266;;;;N;MODIFIER LETTER SMALL H HOOK;;;; 02B2;MODIFIER LETTER SMALL J;Lm;0;L; 006A;;;;N;;;;; 02B3;MODIFIER LETTER SMALL R;Lm;0;L; 0072;;;;N;;;;; 02B4;MODIFIER LETTER SMALL TURNED R;Lm;0;L; 0279;;;;N;;;;; 02B5;MODIFIER LETTER SMALL TURNED R WITH HOOK;Lm;0;L; 027B;;;;N;MODIFIER LETTER SMALL TURNED R HOOK;;;; 02B6;MODIFIER LETTER SMALL CAPITAL INVERTED R;Lm;0;L; 0281;;;;N;;;;; 02B7;MODIFIER LETTER SMALL W;Lm;0;L; 0077;;;;N;;;;; 02B8;MODIFIER LETTER SMALL Y;Lm;0;L; 0079;;;;N;;;;; 02B9;MODIFIER LETTER PRIME;Lm;0;ON;;;;;N;;;;; 02BA;MODIFIER LETTER DOUBLE PRIME;Lm;0;ON;;;;;N;;;;; 02BB;MODIFIER LETTER TURNED COMMA;Lm;0;L;;;;;N;;;;; 02BC;MODIFIER LETTER APOSTROPHE;Lm;0;L;;;;;N;;;;; 02BD;MODIFIER LETTER REVERSED COMMA;Lm;0;L;;;;;N;;;;; 02BE;MODIFIER LETTER RIGHT HALF RING;Lm;0;L;;;;;N;;;;; 02BF;MODIFIER LETTER LEFT HALF RING;Lm;0;L;;;;;N;;;;; 02C0;MODIFIER LETTER GLOTTAL STOP;Lm;0;L;;;;;N;;;;; 02C1;MODIFIER LETTER REVERSED GLOTTAL STOP;Lm;0;L;;;;;N;;;;; 02C2;MODIFIER LETTER LEFT ARROWHEAD;Sk;0;ON;;;;;N;;;;; 02C3;MODIFIER LETTER RIGHT ARROWHEAD;Sk;0;ON;;;;;N;;;;; 02C4;MODIFIER LETTER UP ARROWHEAD;Sk;0;ON;;;;;N;;;;; 02C5;MODIFIER LETTER DOWN ARROWHEAD;Sk;0;ON;;;;;N;;;;; 02C6;MODIFIER LETTER CIRCUMFLEX ACCENT;Lm;0;ON;;;;;N;MODIFIER LETTER CIRCUMFLEX;;;; 02C7;CARON;Lm;0;ON;;;;;N;MODIFIER LETTER HACEK;;;; 02C8;MODIFIER LETTER VERTICAL LINE;Lm;0;ON;;;;;N;;;;; 02C9;MODIFIER LETTER MACRON;Lm;0;ON;;;;;N;;;;; 02CA;MODIFIER LETTER ACUTE ACCENT;Lm;0;ON;;;;;N;MODIFIER LETTER ACUTE;;;; 02CB;MODIFIER LETTER GRAVE ACCENT;Lm;0;ON;;;;;N;MODIFIER LETTER GRAVE;;;; 02CC;MODIFIER LETTER LOW VERTICAL LINE;Lm;0;ON;;;;;N;;;;; 02CD;MODIFIER LETTER LOW MACRON;Lm;0;ON;;;;;N;;;;; 02CE;MODIFIER LETTER LOW GRAVE ACCENT;Lm;0;ON;;;;;N;MODIFIER LETTER LOW GRAVE;;;; 02CF;MODIFIER LETTER LOW ACUTE ACCENT;Lm;0;ON;;;;;N;MODIFIER LETTER LOW ACUTE;;;; 02D0;MODIFIER LETTER TRIANGULAR COLON;Lm;0;L;;;;;N;;;;; 02D1;MODIFIER LETTER HALF TRIANGULAR COLON;Lm;0;L;;;;;N;;;;; 02D2;MODIFIER LETTER CENTRED RIGHT HALF RING;Sk;0;ON;;;;;N;MODIFIER LETTER CENTERED RIGHT HALF RING;;;; 02D3;MODIFIER LETTER CENTRED LEFT HALF RING;Sk;0;ON;;;;;N;MODIFIER LETTER CENTERED LEFT HALF RING;;;; 02D4;MODIFIER LETTER UP TACK;Sk;0;ON;;;;;N;;;;; 02D5;MODIFIER LETTER DOWN TACK;Sk;0;ON;;;;;N;;;;; 02D6;MODIFIER LETTER PLUS SIGN;Sk;0;ON;;;;;N;;;;; 02D7;MODIFIER LETTER MINUS SIGN;Sk;0;ON;;;;;N;;;;; 02D8;BREVE;Sk;0;ON; 0020 0306;;;;N;SPACING BREVE;;;; 02D9;DOT ABOVE;Sk;0;ON; 0020 0307;;;;N;SPACING DOT ABOVE;;;; 02DA;RING ABOVE;Sk;0;ON; 0020 030A;;;;N;SPACING RING ABOVE;;;; 02DB;OGONEK;Sk;0;ON; 0020 0328;;;;N;SPACING OGONEK;;;; 02DC;SMALL TILDE;Sk;0;ON; 0020 0303;;;;N;SPACING TILDE;;;; 02DD;DOUBLE ACUTE ACCENT;Sk;0;ON; 0020 030B;;;;N;SPACING DOUBLE ACUTE;;;; 02DE;MODIFIER LETTER RHOTIC HOOK;Sk;0;ON;;;;;N;;;;; 02DF;MODIFIER LETTER CROSS ACCENT;Sk;0;ON;;;;;N;;;;; 02E0;MODIFIER LETTER SMALL GAMMA;Lm;0;L; 0263;;;;N;;;;; 02E1;MODIFIER LETTER SMALL L;Lm;0;L; 006C;;;;N;;;;; 02E2;MODIFIER LETTER SMALL S;Lm;0;L; 0073;;;;N;;;;; 02E3;MODIFIER LETTER SMALL X;Lm;0;L; 0078;;;;N;;;;; 02E4;MODIFIER LETTER SMALL REVERSED GLOTTAL STOP;Lm;0;L; 0295;;;;N;;;;; 02E5;MODIFIER LETTER EXTRA-HIGH TONE BAR;Sk;0;ON;;;;;N;;;;; 02E6;MODIFIER LETTER HIGH TONE BAR;Sk;0;ON;;;;;N;;;;; 02E7;MODIFIER LETTER MID TONE BAR;Sk;0;ON;;;;;N;;;;; 02E8;MODIFIER LETTER LOW TONE BAR;Sk;0;ON;;;;;N;;;;; 02E9;MODIFIER LETTER EXTRA-LOW TONE BAR;Sk;0;ON;;;;;N;;;;; 02EA;MODIFIER LETTER YIN DEPARTING TONE MARK;Sk;0;ON;;;;;N;;;;; 02EB;MODIFIER LETTER YANG DEPARTING TONE MARK;Sk;0;ON;;;;;N;;;;; 02EC;MODIFIER LETTER VOICING;Lm;0;ON;;;;;N;;;;; 02ED;MODIFIER LETTER UNASPIRATED;Sk;0;ON;;;;;N;;;;; 02EE;MODIFIER LETTER DOUBLE APOSTROPHE;Lm;0;L;;;;;N;;;;; 02EF;MODIFIER LETTER LOW DOWN ARROWHEAD;Sk;0;ON;;;;;N;;;;; 02F0;MODIFIER LETTER LOW UP ARROWHEAD;Sk;0;ON;;;;;N;;;;; 02F1;MODIFIER LETTER LOW LEFT ARROWHEAD;Sk;0;ON;;;;;N;;;;; 02F2;MODIFIER LETTER LOW RIGHT ARROWHEAD;Sk;0;ON;;;;;N;;;;; 02F3;MODIFIER LETTER LOW RING;Sk;0;ON;;;;;N;;;;; 02F4;MODIFIER LETTER MIDDLE GRAVE ACCENT;Sk;0;ON;;;;;N;;;;; 02F5;MODIFIER LETTER MIDDLE DOUBLE GRAVE ACCENT;Sk;0;ON;;;;;N;;;;; 02F6;MODIFIER LETTER MIDDLE DOUBLE ACUTE ACCENT;Sk;0;ON;;;;;N;;;;; 02F7;MODIFIER LETTER LOW TILDE;Sk;0;ON;;;;;N;;;;; 02F8;MODIFIER LETTER RAISED COLON;Sk;0;ON;;;;;N;;;;; 02F9;MODIFIER LETTER BEGIN HIGH TONE;Sk;0;ON;;;;;N;;;;; 02FA;MODIFIER LETTER END HIGH TONE;Sk;0;ON;;;;;N;;;;; 02FB;MODIFIER LETTER BEGIN LOW TONE;Sk;0;ON;;;;;N;;;;; 02FC;MODIFIER LETTER END LOW TONE;Sk;0;ON;;;;;N;;;;; 02FD;MODIFIER LETTER SHELF;Sk;0;ON;;;;;N;;;;; 02FE;MODIFIER LETTER OPEN SHELF;Sk;0;ON;;;;;N;;;;; 02FF;MODIFIER LETTER LOW LEFT ARROW;Sk;0;ON;;;;;N;;;;; 0300;COMBINING GRAVE ACCENT;Mn;230;NSM;;;;;N;NON-SPACING GRAVE;;;; 0301;COMBINING ACUTE ACCENT;Mn;230;NSM;;;;;N;NON-SPACING ACUTE;;;; 0302;COMBINING CIRCUMFLEX ACCENT;Mn;230;NSM;;;;;N;NON-SPACING CIRCUMFLEX;;;; 0303;COMBINING TILDE;Mn;230;NSM;;;;;N;NON-SPACING TILDE;;;; 0304;COMBINING MACRON;Mn;230;NSM;;;;;N;NON-SPACING MACRON;;;; 0305;COMBINING OVERLINE;Mn;230;NSM;;;;;N;NON-SPACING OVERSCORE;;;; 0306;COMBINING BREVE;Mn;230;NSM;;;;;N;NON-SPACING BREVE;;;; 0307;COMBINING DOT ABOVE;Mn;230;NSM;;;;;N;NON-SPACING DOT ABOVE;;;; 0308;COMBINING DIAERESIS;Mn;230;NSM;;;;;N;NON-SPACING DIAERESIS;;;; 0309;COMBINING HOOK ABOVE;Mn;230;NSM;;;;;N;NON-SPACING HOOK ABOVE;;;; 030A;COMBINING RING ABOVE;Mn;230;NSM;;;;;N;NON-SPACING RING ABOVE;;;; 030B;COMBINING DOUBLE ACUTE ACCENT;Mn;230;NSM;;;;;N;NON-SPACING DOUBLE ACUTE;;;; 030C;COMBINING CARON;Mn;230;NSM;;;;;N;NON-SPACING HACEK;;;; 030D;COMBINING VERTICAL LINE ABOVE;Mn;230;NSM;;;;;N;NON-SPACING VERTICAL LINE ABOVE;;;; 030E;COMBINING DOUBLE VERTICAL LINE ABOVE;Mn;230;NSM;;;;;N;NON-SPACING DOUBLE VERTICAL LINE ABOVE;;;; 030F;COMBINING DOUBLE GRAVE ACCENT;Mn;230;NSM;;;;;N;NON-SPACING DOUBLE GRAVE;;;; 0310;COMBINING CANDRABINDU;Mn;230;NSM;;;;;N;NON-SPACING CANDRABINDU;;;; 0311;COMBINING INVERTED BREVE;Mn;230;NSM;;;;;N;NON-SPACING INVERTED BREVE;;;; 0312;COMBINING TURNED COMMA ABOVE;Mn;230;NSM;;;;;N;NON-SPACING TURNED COMMA ABOVE;;;; 0313;COMBINING COMMA ABOVE;Mn;230;NSM;;;;;N;NON-SPACING COMMA ABOVE;;;; 0314;COMBINING REVERSED COMMA ABOVE;Mn;230;NSM;;;;;N;NON-SPACING REVERSED COMMA ABOVE;;;; 0315;COMBINING COMMA ABOVE RIGHT;Mn;232;NSM;;;;;N;NON-SPACING COMMA ABOVE RIGHT;;;; 0316;COMBINING GRAVE ACCENT BELOW;Mn;220;NSM;;;;;N;NON-SPACING GRAVE BELOW;;;; 0317;COMBINING ACUTE ACCENT BELOW;Mn;220;NSM;;;;;N;NON-SPACING ACUTE BELOW;;;; 0318;COMBINING LEFT TACK BELOW;Mn;220;NSM;;;;;N;NON-SPACING LEFT TACK BELOW;;;; 0319;COMBINING RIGHT TACK BELOW;Mn;220;NSM;;;;;N;NON-SPACING RIGHT TACK BELOW;;;; 031A;COMBINING LEFT ANGLE ABOVE;Mn;232;NSM;;;;;N;NON-SPACING LEFT ANGLE ABOVE;;;; 031B;COMBINING HORN;Mn;216;NSM;;;;;N;NON-SPACING HORN;;;; 031C;COMBINING LEFT HALF RING BELOW;Mn;220;NSM;;;;;N;NON-SPACING LEFT HALF RING BELOW;;;; 031D;COMBINING UP TACK BELOW;Mn;220;NSM;;;;;N;NON-SPACING UP TACK BELOW;;;; 031E;COMBINING DOWN TACK BELOW;Mn;220;NSM;;;;;N;NON-SPACING DOWN TACK BELOW;;;; 031F;COMBINING PLUS SIGN BELOW;Mn;220;NSM;;;;;N;NON-SPACING PLUS SIGN BELOW;;;; 0320;COMBINING MINUS SIGN BELOW;Mn;220;NSM;;;;;N;NON-SPACING MINUS SIGN BELOW;;;; 0321;COMBINING PALATALIZED HOOK BELOW;Mn;202;NSM;;;;;N;NON-SPACING PALATALIZED HOOK BELOW;;;; 0322;COMBINING RETROFLEX HOOK BELOW;Mn;202;NSM;;;;;N;NON-SPACING RETROFLEX HOOK BELOW;;;; 0323;COMBINING DOT BELOW;Mn;220;NSM;;;;;N;NON-SPACING DOT BELOW;;;; 0324;COMBINING DIAERESIS BELOW;Mn;220;NSM;;;;;N;NON-SPACING DOUBLE DOT BELOW;;;; 0325;COMBINING RING BELOW;Mn;220;NSM;;;;;N;NON-SPACING RING BELOW;;;; 0326;COMBINING COMMA BELOW;Mn;220;NSM;;;;;N;NON-SPACING COMMA BELOW;;;; 0327;COMBINING CEDILLA;Mn;202;NSM;;;;;N;NON-SPACING CEDILLA;;;; 0328;COMBINING OGONEK;Mn;202;NSM;;;;;N;NON-SPACING OGONEK;;;; 0329;COMBINING VERTICAL LINE BELOW;Mn;220;NSM;;;;;N;NON-SPACING VERTICAL LINE BELOW;;;; 032A;COMBINING BRIDGE BELOW;Mn;220;NSM;;;;;N;NON-SPACING BRIDGE BELOW;;;; 032B;COMBINING INVERTED DOUBLE ARCH BELOW;Mn;220;NSM;;;;;N;NON-SPACING INVERTED DOUBLE ARCH BELOW;;;; 032C;COMBINING CARON BELOW;Mn;220;NSM;;;;;N;NON-SPACING HACEK BELOW;;;; 032D;COMBINING CIRCUMFLEX ACCENT BELOW;Mn;220;NSM;;;;;N;NON-SPACING CIRCUMFLEX BELOW;;;; 032E;COMBINING BREVE BELOW;Mn;220;NSM;;;;;N;NON-SPACING BREVE BELOW;;;; 032F;COMBINING INVERTED BREVE BELOW;Mn;220;NSM;;;;;N;NON-SPACING INVERTED BREVE BELOW;;;; 0330;COMBINING TILDE BELOW;Mn;220;NSM;;;;;N;NON-SPACING TILDE BELOW;;;; 0331;COMBINING MACRON BELOW;Mn;220;NSM;;;;;N;NON-SPACING MACRON BELOW;;;; 0332;COMBINING LOW LINE;Mn;220;NSM;;;;;N;NON-SPACING UNDERSCORE;;;; 0333;COMBINING DOUBLE LOW LINE;Mn;220;NSM;;;;;N;NON-SPACING DOUBLE UNDERSCORE;;;; 0334;COMBINING TILDE OVERLAY;Mn;1;NSM;;;;;N;NON-SPACING TILDE OVERLAY;;;; 0335;COMBINING SHORT STROKE OVERLAY;Mn;1;NSM;;;;;N;NON-SPACING SHORT BAR OVERLAY;;;; 0336;COMBINING LONG STROKE OVERLAY;Mn;1;NSM;;;;;N;NON-SPACING LONG BAR OVERLAY;;;; 0337;COMBINING SHORT SOLIDUS OVERLAY;Mn;1;NSM;;;;;N;NON-SPACING SHORT SLASH OVERLAY;;;; 0338;COMBINING LONG SOLIDUS OVERLAY;Mn;1;NSM;;;;;N;NON-SPACING LONG SLASH OVERLAY;;;; 0339;COMBINING RIGHT HALF RING BELOW;Mn;220;NSM;;;;;N;NON-SPACING RIGHT HALF RING BELOW;;;; 033A;COMBINING INVERTED BRIDGE BELOW;Mn;220;NSM;;;;;N;NON-SPACING INVERTED BRIDGE BELOW;;;; 033B;COMBINING SQUARE BELOW;Mn;220;NSM;;;;;N;NON-SPACING SQUARE BELOW;;;; 033C;COMBINING SEAGULL BELOW;Mn;220;NSM;;;;;N;NON-SPACING SEAGULL BELOW;;;; 033D;COMBINING X ABOVE;Mn;230;NSM;;;;;N;NON-SPACING X ABOVE;;;; 033E;COMBINING VERTICAL TILDE;Mn;230;NSM;;;;;N;NON-SPACING VERTICAL TILDE;;;; 033F;COMBINING DOUBLE OVERLINE;Mn;230;NSM;;;;;N;NON-SPACING DOUBLE OVERSCORE;;;; 0340;COMBINING GRAVE TONE MARK;Mn;230;NSM;0300;;;;N;NON-SPACING GRAVE TONE MARK;;;; 0341;COMBINING ACUTE TONE MARK;Mn;230;NSM;0301;;;;N;NON-SPACING ACUTE TONE MARK;;;; 0342;COMBINING GREEK PERISPOMENI;Mn;230;NSM;;;;;N;;;;; 0343;COMBINING GREEK KORONIS;Mn;230;NSM;0313;;;;N;;;;; 0344;COMBINING GREEK DIALYTIKA TONOS;Mn;230;NSM;0308 0301;;;;N;GREEK NON-SPACING DIAERESIS TONOS;;;; 0345;COMBINING GREEK YPOGEGRAMMENI;Mn;240;NSM;;;;;N;GREEK NON-SPACING IOTA BELOW;;0399;;0399 0346;COMBINING BRIDGE ABOVE;Mn;230;NSM;;;;;N;;;;; 0347;COMBINING EQUALS SIGN BELOW;Mn;220;NSM;;;;;N;;;;; 0348;COMBINING DOUBLE VERTICAL LINE BELOW;Mn;220;NSM;;;;;N;;;;; 0349;COMBINING LEFT ANGLE BELOW;Mn;220;NSM;;;;;N;;;;; 034A;COMBINING NOT TILDE ABOVE;Mn;230;NSM;;;;;N;;;;; 034B;COMBINING HOMOTHETIC ABOVE;Mn;230;NSM;;;;;N;;;;; 034C;COMBINING ALMOST EQUAL TO ABOVE;Mn;230;NSM;;;;;N;;;;; 034D;COMBINING LEFT RIGHT ARROW BELOW;Mn;220;NSM;;;;;N;;;;; 034E;COMBINING UPWARDS ARROW BELOW;Mn;220;NSM;;;;;N;;;;; 034F;COMBINING GRAPHEME JOINER;Mn;0;NSM;;;;;N;;;;; 0350;COMBINING RIGHT ARROWHEAD ABOVE;Mn;230;NSM;;;;;N;;;;; 0351;COMBINING LEFT HALF RING ABOVE;Mn;230;NSM;;;;;N;;;;; 0352;COMBINING FERMATA;Mn;230;NSM;;;;;N;;;;; 0353;COMBINING X BELOW;Mn;220;NSM;;;;;N;;;;; 0354;COMBINING LEFT ARROWHEAD BELOW;Mn;220;NSM;;;;;N;;;;; 0355;COMBINING RIGHT ARROWHEAD BELOW;Mn;220;NSM;;;;;N;;;;; 0356;COMBINING RIGHT ARROWHEAD AND UP ARROWHEAD BELOW;Mn;220;NSM;;;;;N;;;;; 0357;COMBINING RIGHT HALF RING ABOVE;Mn;230;NSM;;;;;N;;;;; 0358;COMBINING DOT ABOVE RIGHT;Mn;232;NSM;;;;;N;;;;; 0359;COMBINING ASTERISK BELOW;Mn;220;NSM;;;;;N;;;;; 035A;COMBINING DOUBLE RING BELOW;Mn;220;NSM;;;;;N;;;;; 035B;COMBINING ZIGZAG ABOVE;Mn;230;NSM;;;;;N;;;;; 035C;COMBINING DOUBLE BREVE BELOW;Mn;233;NSM;;;;;N;;;;; 035D;COMBINING DOUBLE BREVE;Mn;234;NSM;;;;;N;;;;; 035E;COMBINING DOUBLE MACRON;Mn;234;NSM;;;;;N;;;;; 035F;COMBINING DOUBLE MACRON BELOW;Mn;233;NSM;;;;;N;;;;; 0360;COMBINING DOUBLE TILDE;Mn;234;NSM;;;;;N;;;;; 0361;COMBINING DOUBLE INVERTED BREVE;Mn;234;NSM;;;;;N;;;;; 0362;COMBINING DOUBLE RIGHTWARDS ARROW BELOW;Mn;233;NSM;;;;;N;;;;; 0363;COMBINING LATIN SMALL LETTER A;Mn;230;NSM;;;;;N;;;;; 0364;COMBINING LATIN SMALL LETTER E;Mn;230;NSM;;;;;N;;;;; 0365;COMBINING LATIN SMALL LETTER I;Mn;230;NSM;;;;;N;;;;; 0366;COMBINING LATIN SMALL LETTER O;Mn;230;NSM;;;;;N;;;;; 0367;COMBINING LATIN SMALL LETTER U;Mn;230;NSM;;;;;N;;;;; 0368;COMBINING LATIN SMALL LETTER C;Mn;230;NSM;;;;;N;;;;; 0369;COMBINING LATIN SMALL LETTER D;Mn;230;NSM;;;;;N;;;;; 036A;COMBINING LATIN SMALL LETTER H;Mn;230;NSM;;;;;N;;;;; 036B;COMBINING LATIN SMALL LETTER M;Mn;230;NSM;;;;;N;;;;; 036C;COMBINING LATIN SMALL LETTER R;Mn;230;NSM;;;;;N;;;;; 036D;COMBINING LATIN SMALL LETTER T;Mn;230;NSM;;;;;N;;;;; 036E;COMBINING LATIN SMALL LETTER V;Mn;230;NSM;;;;;N;;;;; 036F;COMBINING LATIN SMALL LETTER X;Mn;230;NSM;;;;;N;;;;; 0370;GREEK CAPITAL LETTER HETA;Lu;0;L;;;;;N;;;;0371; 0371;GREEK SMALL LETTER HETA;Ll;0;L;;;;;N;;;0370;;0370 0372;GREEK CAPITAL LETTER ARCHAIC SAMPI;Lu;0;L;;;;;N;;;;0373; 0373;GREEK SMALL LETTER ARCHAIC SAMPI;Ll;0;L;;;;;N;;;0372;;0372 0374;GREEK NUMERAL SIGN;Lm;0;ON;02B9;;;;N;GREEK UPPER NUMERAL SIGN;;;; 0375;GREEK LOWER NUMERAL SIGN;Sk;0;ON;;;;;N;;;;; 0376;GREEK CAPITAL LETTER PAMPHYLIAN DIGAMMA;Lu;0;L;;;;;N;;;;0377; 0377;GREEK SMALL LETTER PAMPHYLIAN DIGAMMA;Ll;0;L;;;;;N;;;0376;;0376 037A;GREEK YPOGEGRAMMENI;Lm;0;L; 0020 0345;;;;N;GREEK SPACING IOTA BELOW;;;; 037B;GREEK SMALL REVERSED LUNATE SIGMA SYMBOL;Ll;0;L;;;;;N;;;03FD;;03FD 037C;GREEK SMALL DOTTED LUNATE SIGMA SYMBOL;Ll;0;L;;;;;N;;;03FE;;03FE 037D;GREEK SMALL REVERSED DOTTED LUNATE SIGMA SYMBOL;Ll;0;L;;;;;N;;;03FF;;03FF 037E;GREEK QUESTION MARK;Po;0;ON;003B;;;;N;;;;; 037F;GREEK CAPITAL LETTER YOT;Lu;0;L;;;;;N;;;;03F3; 0384;GREEK TONOS;Sk;0;ON; 0020 0301;;;;N;GREEK SPACING TONOS;;;; 0385;GREEK DIALYTIKA TONOS;Sk;0;ON;00A8 0301;;;;N;GREEK SPACING DIAERESIS TONOS;;;; 0386;GREEK CAPITAL LETTER ALPHA WITH TONOS;Lu;0;L;0391 0301;;;;N;GREEK CAPITAL LETTER ALPHA TONOS;;;03AC; 0387;GREEK ANO TELEIA;Po;0;ON;00B7;;;;N;;;;; 0388;GREEK CAPITAL LETTER EPSILON WITH TONOS;Lu;0;L;0395 0301;;;;N;GREEK CAPITAL LETTER EPSILON TONOS;;;03AD; 0389;GREEK CAPITAL LETTER ETA WITH TONOS;Lu;0;L;0397 0301;;;;N;GREEK CAPITAL LETTER ETA TONOS;;;03AE; 038A;GREEK CAPITAL LETTER IOTA WITH TONOS;Lu;0;L;0399 0301;;;;N;GREEK CAPITAL LETTER IOTA TONOS;;;03AF; 038C;GREEK CAPITAL LETTER OMICRON WITH TONOS;Lu;0;L;039F 0301;;;;N;GREEK CAPITAL LETTER OMICRON TONOS;;;03CC; 038E;GREEK CAPITAL LETTER UPSILON WITH TONOS;Lu;0;L;03A5 0301;;;;N;GREEK CAPITAL LETTER UPSILON TONOS;;;03CD; 038F;GREEK CAPITAL LETTER OMEGA WITH TONOS;Lu;0;L;03A9 0301;;;;N;GREEK CAPITAL LETTER OMEGA TONOS;;;03CE; 0390;GREEK SMALL LETTER IOTA WITH DIALYTIKA AND TONOS;Ll;0;L;03CA 0301;;;;N;GREEK SMALL LETTER IOTA DIAERESIS TONOS;;;; 0391;GREEK CAPITAL LETTER ALPHA;Lu;0;L;;;;;N;;;;03B1; 0392;GREEK CAPITAL LETTER BETA;Lu;0;L;;;;;N;;;;03B2; 0393;GREEK CAPITAL LETTER GAMMA;Lu;0;L;;;;;N;;;;03B3; 0394;GREEK CAPITAL LETTER DELTA;Lu;0;L;;;;;N;;;;03B4; 0395;GREEK CAPITAL LETTER EPSILON;Lu;0;L;;;;;N;;;;03B5; 0396;GREEK CAPITAL LETTER ZETA;Lu;0;L;;;;;N;;;;03B6; 0397;GREEK CAPITAL LETTER ETA;Lu;0;L;;;;;N;;;;03B7; 0398;GREEK CAPITAL LETTER THETA;Lu;0;L;;;;;N;;;;03B8; 0399;GREEK CAPITAL LETTER IOTA;Lu;0;L;;;;;N;;;;03B9; 039A;GREEK CAPITAL LETTER KAPPA;Lu;0;L;;;;;N;;;;03BA; 039B;GREEK CAPITAL LETTER LAMDA;Lu;0;L;;;;;N;GREEK CAPITAL LETTER LAMBDA;;;03BB; 039C;GREEK CAPITAL LETTER MU;Lu;0;L;;;;;N;;;;03BC; 039D;GREEK CAPITAL LETTER NU;Lu;0;L;;;;;N;;;;03BD; 039E;GREEK CAPITAL LETTER XI;Lu;0;L;;;;;N;;;;03BE; 039F;GREEK CAPITAL LETTER OMICRON;Lu;0;L;;;;;N;;;;03BF; 03A0;GREEK CAPITAL LETTER PI;Lu;0;L;;;;;N;;;;03C0; 03A1;GREEK CAPITAL LETTER RHO;Lu;0;L;;;;;N;;;;03C1; 03A3;GREEK CAPITAL LETTER SIGMA;Lu;0;L;;;;;N;;;;03C3; 03A4;GREEK CAPITAL LETTER TAU;Lu;0;L;;;;;N;;;;03C4; 03A5;GREEK CAPITAL LETTER UPSILON;Lu;0;L;;;;;N;;;;03C5; 03A6;GREEK CAPITAL LETTER PHI;Lu;0;L;;;;;N;;;;03C6; 03A7;GREEK CAPITAL LETTER CHI;Lu;0;L;;;;;N;;;;03C7; 03A8;GREEK CAPITAL LETTER PSI;Lu;0;L;;;;;N;;;;03C8; 03A9;GREEK CAPITAL LETTER OMEGA;Lu;0;L;;;;;N;;;;03C9; 03AA;GREEK CAPITAL LETTER IOTA WITH DIALYTIKA;Lu;0;L;0399 0308;;;;N;GREEK CAPITAL LETTER IOTA DIAERESIS;;;03CA; 03AB;GREEK CAPITAL LETTER UPSILON WITH DIALYTIKA;Lu;0;L;03A5 0308;;;;N;GREEK CAPITAL LETTER UPSILON DIAERESIS;;;03CB; 03AC;GREEK SMALL LETTER ALPHA WITH TONOS;Ll;0;L;03B1 0301;;;;N;GREEK SMALL LETTER ALPHA TONOS;;0386;;0386 03AD;GREEK SMALL LETTER EPSILON WITH TONOS;Ll;0;L;03B5 0301;;;;N;GREEK SMALL LETTER EPSILON TONOS;;0388;;0388 03AE;GREEK SMALL LETTER ETA WITH TONOS;Ll;0;L;03B7 0301;;;;N;GREEK SMALL LETTER ETA TONOS;;0389;;0389 03AF;GREEK SMALL LETTER IOTA WITH TONOS;Ll;0;L;03B9 0301;;;;N;GREEK SMALL LETTER IOTA TONOS;;038A;;038A 03B0;GREEK SMALL LETTER UPSILON WITH DIALYTIKA AND TONOS;Ll;0;L;03CB 0301;;;;N;GREEK SMALL LETTER UPSILON DIAERESIS TONOS;;;; 03B1;GREEK SMALL LETTER ALPHA;Ll;0;L;;;;;N;;;0391;;0391 03B2;GREEK SMALL LETTER BETA;Ll;0;L;;;;;N;;;0392;;0392 03B3;GREEK SMALL LETTER GAMMA;Ll;0;L;;;;;N;;;0393;;0393 03B4;GREEK SMALL LETTER DELTA;Ll;0;L;;;;;N;;;0394;;0394 03B5;GREEK SMALL LETTER EPSILON;Ll;0;L;;;;;N;;;0395;;0395 03B6;GREEK SMALL LETTER ZETA;Ll;0;L;;;;;N;;;0396;;0396 03B7;GREEK SMALL LETTER ETA;Ll;0;L;;;;;N;;;0397;;0397 03B8;GREEK SMALL LETTER THETA;Ll;0;L;;;;;N;;;0398;;0398 03B9;GREEK SMALL LETTER IOTA;Ll;0;L;;;;;N;;;0399;;0399 03BA;GREEK SMALL LETTER KAPPA;Ll;0;L;;;;;N;;;039A;;039A 03BB;GREEK SMALL LETTER LAMDA;Ll;0;L;;;;;N;GREEK SMALL LETTER LAMBDA;;039B;;039B 03BC;GREEK SMALL LETTER MU;Ll;0;L;;;;;N;;;039C;;039C 03BD;GREEK SMALL LETTER NU;Ll;0;L;;;;;N;;;039D;;039D 03BE;GREEK SMALL LETTER XI;Ll;0;L;;;;;N;;;039E;;039E 03BF;GREEK SMALL LETTER OMICRON;Ll;0;L;;;;;N;;;039F;;039F 03C0;GREEK SMALL LETTER PI;Ll;0;L;;;;;N;;;03A0;;03A0 03C1;GREEK SMALL LETTER RHO;Ll;0;L;;;;;N;;;03A1;;03A1 03C2;GREEK SMALL LETTER FINAL SIGMA;Ll;0;L;;;;;N;;;03A3;;03A3 03C3;GREEK SMALL LETTER SIGMA;Ll;0;L;;;;;N;;;03A3;;03A3 03C4;GREEK SMALL LETTER TAU;Ll;0;L;;;;;N;;;03A4;;03A4 03C5;GREEK SMALL LETTER UPSILON;Ll;0;L;;;;;N;;;03A5;;03A5 03C6;GREEK SMALL LETTER PHI;Ll;0;L;;;;;N;;;03A6;;03A6 03C7;GREEK SMALL LETTER CHI;Ll;0;L;;;;;N;;;03A7;;03A7 03C8;GREEK SMALL LETTER PSI;Ll;0;L;;;;;N;;;03A8;;03A8 03C9;GREEK SMALL LETTER OMEGA;Ll;0;L;;;;;N;;;03A9;;03A9 03CA;GREEK SMALL LETTER IOTA WITH DIALYTIKA;Ll;0;L;03B9 0308;;;;N;GREEK SMALL LETTER IOTA DIAERESIS;;03AA;;03AA 03CB;GREEK SMALL LETTER UPSILON WITH DIALYTIKA;Ll;0;L;03C5 0308;;;;N;GREEK SMALL LETTER UPSILON DIAERESIS;;03AB;;03AB 03CC;GREEK SMALL LETTER OMICRON WITH TONOS;Ll;0;L;03BF 0301;;;;N;GREEK SMALL LETTER OMICRON TONOS;;038C;;038C 03CD;GREEK SMALL LETTER UPSILON WITH TONOS;Ll;0;L;03C5 0301;;;;N;GREEK SMALL LETTER UPSILON TONOS;;038E;;038E 03CE;GREEK SMALL LETTER OMEGA WITH TONOS;Ll;0;L;03C9 0301;;;;N;GREEK SMALL LETTER OMEGA TONOS;;038F;;038F 03CF;GREEK CAPITAL KAI SYMBOL;Lu;0;L;;;;;N;;;;03D7; 03D0;GREEK BETA SYMBOL;Ll;0;L; 03B2;;;;N;GREEK SMALL LETTER CURLED BETA;;0392;;0392 03D1;GREEK THETA SYMBOL;Ll;0;L; 03B8;;;;N;GREEK SMALL LETTER SCRIPT THETA;;0398;;0398 03D2;GREEK UPSILON WITH HOOK SYMBOL;Lu;0;L; 03A5;;;;N;GREEK CAPITAL LETTER UPSILON HOOK;;;; 03D3;GREEK UPSILON WITH ACUTE AND HOOK SYMBOL;Lu;0;L;03D2 0301;;;;N;GREEK CAPITAL LETTER UPSILON HOOK TONOS;;;; 03D4;GREEK UPSILON WITH DIAERESIS AND HOOK SYMBOL;Lu;0;L;03D2 0308;;;;N;GREEK CAPITAL LETTER UPSILON HOOK DIAERESIS;;;; 03D5;GREEK PHI SYMBOL;Ll;0;L; 03C6;;;;N;GREEK SMALL LETTER SCRIPT PHI;;03A6;;03A6 03D6;GREEK PI SYMBOL;Ll;0;L; 03C0;;;;N;GREEK SMALL LETTER OMEGA PI;;03A0;;03A0 03D7;GREEK KAI SYMBOL;Ll;0;L;;;;;N;;;03CF;;03CF 03D8;GREEK LETTER ARCHAIC KOPPA;Lu;0;L;;;;;N;;;;03D9; 03D9;GREEK SMALL LETTER ARCHAIC KOPPA;Ll;0;L;;;;;N;;;03D8;;03D8 03DA;GREEK LETTER STIGMA;Lu;0;L;;;;;N;GREEK CAPITAL LETTER STIGMA;;;03DB; 03DB;GREEK SMALL LETTER STIGMA;Ll;0;L;;;;;N;;;03DA;;03DA 03DC;GREEK LETTER DIGAMMA;Lu;0;L;;;;;N;GREEK CAPITAL LETTER DIGAMMA;;;03DD; 03DD;GREEK SMALL LETTER DIGAMMA;Ll;0;L;;;;;N;;;03DC;;03DC 03DE;GREEK LETTER KOPPA;Lu;0;L;;;;;N;GREEK CAPITAL LETTER KOPPA;;;03DF; 03DF;GREEK SMALL LETTER KOPPA;Ll;0;L;;;;;N;;;03DE;;03DE 03E0;GREEK LETTER SAMPI;Lu;0;L;;;;;N;GREEK CAPITAL LETTER SAMPI;;;03E1; 03E1;GREEK SMALL LETTER SAMPI;Ll;0;L;;;;;N;;;03E0;;03E0 03E2;COPTIC CAPITAL LETTER SHEI;Lu;0;L;;;;;N;GREEK CAPITAL LETTER SHEI;;;03E3; 03E3;COPTIC SMALL LETTER SHEI;Ll;0;L;;;;;N;GREEK SMALL LETTER SHEI;;03E2;;03E2 03E4;COPTIC CAPITAL LETTER FEI;Lu;0;L;;;;;N;GREEK CAPITAL LETTER FEI;;;03E5; 03E5;COPTIC SMALL LETTER FEI;Ll;0;L;;;;;N;GREEK SMALL LETTER FEI;;03E4;;03E4 03E6;COPTIC CAPITAL LETTER KHEI;Lu;0;L;;;;;N;GREEK CAPITAL LETTER KHEI;;;03E7; 03E7;COPTIC SMALL LETTER KHEI;Ll;0;L;;;;;N;GREEK SMALL LETTER KHEI;;03E6;;03E6 03E8;COPTIC CAPITAL LETTER HORI;Lu;0;L;;;;;N;GREEK CAPITAL LETTER HORI;;;03E9; 03E9;COPTIC SMALL LETTER HORI;Ll;0;L;;;;;N;GREEK SMALL LETTER HORI;;03E8;;03E8 03EA;COPTIC CAPITAL LETTER GANGIA;Lu;0;L;;;;;N;GREEK CAPITAL LETTER GANGIA;;;03EB; 03EB;COPTIC SMALL LETTER GANGIA;Ll;0;L;;;;;N;GREEK SMALL LETTER GANGIA;;03EA;;03EA 03EC;COPTIC CAPITAL LETTER SHIMA;Lu;0;L;;;;;N;GREEK CAPITAL LETTER SHIMA;;;03ED; 03ED;COPTIC SMALL LETTER SHIMA;Ll;0;L;;;;;N;GREEK SMALL LETTER SHIMA;;03EC;;03EC 03EE;COPTIC CAPITAL LETTER DEI;Lu;0;L;;;;;N;GREEK CAPITAL LETTER DEI;;;03EF; 03EF;COPTIC SMALL LETTER DEI;Ll;0;L;;;;;N;GREEK SMALL LETTER DEI;;03EE;;03EE 03F0;GREEK KAPPA SYMBOL;Ll;0;L; 03BA;;;;N;GREEK SMALL LETTER SCRIPT KAPPA;;039A;;039A 03F1;GREEK RHO SYMBOL;Ll;0;L; 03C1;;;;N;GREEK SMALL LETTER TAILED RHO;;03A1;;03A1 03F2;GREEK LUNATE SIGMA SYMBOL;Ll;0;L; 03C2;;;;N;GREEK SMALL LETTER LUNATE SIGMA;;03F9;;03F9 03F3;GREEK LETTER YOT;Ll;0;L;;;;;N;;;037F;;037F 03F4;GREEK CAPITAL THETA SYMBOL;Lu;0;L; 0398;;;;N;;;;03B8; 03F5;GREEK LUNATE EPSILON SYMBOL;Ll;0;L; 03B5;;;;N;;;0395;;0395 03F6;GREEK REVERSED LUNATE EPSILON SYMBOL;Sm;0;ON;;;;;N;;;;; 03F7;GREEK CAPITAL LETTER SHO;Lu;0;L;;;;;N;;;;03F8; 03F8;GREEK SMALL LETTER SHO;Ll;0;L;;;;;N;;;03F7;;03F7 03F9;GREEK CAPITAL LUNATE SIGMA SYMBOL;Lu;0;L; 03A3;;;;N;;;;03F2; 03FA;GREEK CAPITAL LETTER SAN;Lu;0;L;;;;;N;;;;03FB; 03FB;GREEK SMALL LETTER SAN;Ll;0;L;;;;;N;;;03FA;;03FA 03FC;GREEK RHO WITH STROKE SYMBOL;Ll;0;L;;;;;N;;;;; 03FD;GREEK CAPITAL REVERSED LUNATE SIGMA SYMBOL;Lu;0;L;;;;;N;;;;037B; 03FE;GREEK CAPITAL DOTTED LUNATE SIGMA SYMBOL;Lu;0;L;;;;;N;;;;037C; 03FF;GREEK CAPITAL REVERSED DOTTED LUNATE SIGMA SYMBOL;Lu;0;L;;;;;N;;;;037D; 0400;CYRILLIC CAPITAL LETTER IE WITH GRAVE;Lu;0;L;0415 0300;;;;N;;;;0450; 0401;CYRILLIC CAPITAL LETTER IO;Lu;0;L;0415 0308;;;;N;;;;0451; 0402;CYRILLIC CAPITAL LETTER DJE;Lu;0;L;;;;;N;;;;0452; 0403;CYRILLIC CAPITAL LETTER GJE;Lu;0;L;0413 0301;;;;N;;;;0453; 0404;CYRILLIC CAPITAL LETTER UKRAINIAN IE;Lu;0;L;;;;;N;CYRILLIC CAPITAL LETTER E;;;0454; 0405;CYRILLIC CAPITAL LETTER DZE;Lu;0;L;;;;;N;;;;0455; 0406;CYRILLIC CAPITAL LETTER BYELORUSSIAN-UKRAINIAN I;Lu;0;L;;;;;N;CYRILLIC CAPITAL LETTER I;;;0456; 0407;CYRILLIC CAPITAL LETTER YI;Lu;0;L;0406 0308;;;;N;;;;0457; 0408;CYRILLIC CAPITAL LETTER JE;Lu;0;L;;;;;N;;;;0458; 0409;CYRILLIC CAPITAL LETTER LJE;Lu;0;L;;;;;N;;;;0459; 040A;CYRILLIC CAPITAL LETTER NJE;Lu;0;L;;;;;N;;;;045A; 040B;CYRILLIC CAPITAL LETTER TSHE;Lu;0;L;;;;;N;;;;045B; 040C;CYRILLIC CAPITAL LETTER KJE;Lu;0;L;041A 0301;;;;N;;;;045C; 040D;CYRILLIC CAPITAL LETTER I WITH GRAVE;Lu;0;L;0418 0300;;;;N;;;;045D; 040E;CYRILLIC CAPITAL LETTER SHORT U;Lu;0;L;0423 0306;;;;N;;;;045E; 040F;CYRILLIC CAPITAL LETTER DZHE;Lu;0;L;;;;;N;;;;045F; 0410;CYRILLIC CAPITAL LETTER A;Lu;0;L;;;;;N;;;;0430; 0411;CYRILLIC CAPITAL LETTER BE;Lu;0;L;;;;;N;;;;0431; 0412;CYRILLIC CAPITAL LETTER VE;Lu;0;L;;;;;N;;;;0432; 0413;CYRILLIC CAPITAL LETTER GHE;Lu;0;L;;;;;N;CYRILLIC CAPITAL LETTER GE;;;0433; 0414;CYRILLIC CAPITAL LETTER DE;Lu;0;L;;;;;N;;;;0434; 0415;CYRILLIC CAPITAL LETTER IE;Lu;0;L;;;;;N;;;;0435; 0416;CYRILLIC CAPITAL LETTER ZHE;Lu;0;L;;;;;N;;;;0436; 0417;CYRILLIC CAPITAL LETTER ZE;Lu;0;L;;;;;N;;;;0437; 0418;CYRILLIC CAPITAL LETTER I;Lu;0;L;;;;;N;CYRILLIC CAPITAL LETTER II;;;0438; 0419;CYRILLIC CAPITAL LETTER SHORT I;Lu;0;L;0418 0306;;;;N;CYRILLIC CAPITAL LETTER SHORT II;;;0439; 041A;CYRILLIC CAPITAL LETTER KA;Lu;0;L;;;;;N;;;;043A; 041B;CYRILLIC CAPITAL LETTER EL;Lu;0;L;;;;;N;;;;043B; 041C;CYRILLIC CAPITAL LETTER EM;Lu;0;L;;;;;N;;;;043C; 041D;CYRILLIC CAPITAL LETTER EN;Lu;0;L;;;;;N;;;;043D; 041E;CYRILLIC CAPITAL LETTER O;Lu;0;L;;;;;N;;;;043E; 041F;CYRILLIC CAPITAL LETTER PE;Lu;0;L;;;;;N;;;;043F; 0420;CYRILLIC CAPITAL LETTER ER;Lu;0;L;;;;;N;;;;0440; 0421;CYRILLIC CAPITAL LETTER ES;Lu;0;L;;;;;N;;;;0441; 0422;CYRILLIC CAPITAL LETTER TE;Lu;0;L;;;;;N;;;;0442; 0423;CYRILLIC CAPITAL LETTER U;Lu;0;L;;;;;N;;;;0443; 0424;CYRILLIC CAPITAL LETTER EF;Lu;0;L;;;;;N;;;;0444; 0425;CYRILLIC CAPITAL LETTER HA;Lu;0;L;;;;;N;CYRILLIC CAPITAL LETTER KHA;;;0445; 0426;CYRILLIC CAPITAL LETTER TSE;Lu;0;L;;;;;N;;;;0446; 0427;CYRILLIC CAPITAL LETTER CHE;Lu;0;L;;;;;N;;;;0447; 0428;CYRILLIC CAPITAL LETTER SHA;Lu;0;L;;;;;N;;;;0448; 0429;CYRILLIC CAPITAL LETTER SHCHA;Lu;0;L;;;;;N;;;;0449; 042A;CYRILLIC CAPITAL LETTER HARD SIGN;Lu;0;L;;;;;N;;;;044A; 042B;CYRILLIC CAPITAL LETTER YERU;Lu;0;L;;;;;N;CYRILLIC CAPITAL LETTER YERI;;;044B; 042C;CYRILLIC CAPITAL LETTER SOFT SIGN;Lu;0;L;;;;;N;;;;044C; 042D;CYRILLIC CAPITAL LETTER E;Lu;0;L;;;;;N;CYRILLIC CAPITAL LETTER REVERSED E;;;044D; 042E;CYRILLIC CAPITAL LETTER YU;Lu;0;L;;;;;N;CYRILLIC CAPITAL LETTER IU;;;044E; 042F;CYRILLIC CAPITAL LETTER YA;Lu;0;L;;;;;N;CYRILLIC CAPITAL LETTER IA;;;044F; 0430;CYRILLIC SMALL LETTER A;Ll;0;L;;;;;N;;;0410;;0410 0431;CYRILLIC SMALL LETTER BE;Ll;0;L;;;;;N;;;0411;;0411 0432;CYRILLIC SMALL LETTER VE;Ll;0;L;;;;;N;;;0412;;0412 0433;CYRILLIC SMALL LETTER GHE;Ll;0;L;;;;;N;CYRILLIC SMALL LETTER GE;;0413;;0413 0434;CYRILLIC SMALL LETTER DE;Ll;0;L;;;;;N;;;0414;;0414 0435;CYRILLIC SMALL LETTER IE;Ll;0;L;;;;;N;;;0415;;0415 0436;CYRILLIC SMALL LETTER ZHE;Ll;0;L;;;;;N;;;0416;;0416 0437;CYRILLIC SMALL LETTER ZE;Ll;0;L;;;;;N;;;0417;;0417 0438;CYRILLIC SMALL LETTER I;Ll;0;L;;;;;N;CYRILLIC SMALL LETTER II;;0418;;0418 0439;CYRILLIC SMALL LETTER SHORT I;Ll;0;L;0438 0306;;;;N;CYRILLIC SMALL LETTER SHORT II;;0419;;0419 043A;CYRILLIC SMALL LETTER KA;Ll;0;L;;;;;N;;;041A;;041A 043B;CYRILLIC SMALL LETTER EL;Ll;0;L;;;;;N;;;041B;;041B 043C;CYRILLIC SMALL LETTER EM;Ll;0;L;;;;;N;;;041C;;041C 043D;CYRILLIC SMALL LETTER EN;Ll;0;L;;;;;N;;;041D;;041D 043E;CYRILLIC SMALL LETTER O;Ll;0;L;;;;;N;;;041E;;041E 043F;CYRILLIC SMALL LETTER PE;Ll;0;L;;;;;N;;;041F;;041F 0440;CYRILLIC SMALL LETTER ER;Ll;0;L;;;;;N;;;0420;;0420 0441;CYRILLIC SMALL LETTER ES;Ll;0;L;;;;;N;;;0421;;0421 0442;CYRILLIC SMALL LETTER TE;Ll;0;L;;;;;N;;;0422;;0422 0443;CYRILLIC SMALL LETTER U;Ll;0;L;;;;;N;;;0423;;0423 0444;CYRILLIC SMALL LETTER EF;Ll;0;L;;;;;N;;;0424;;0424 0445;CYRILLIC SMALL LETTER HA;Ll;0;L;;;;;N;CYRILLIC SMALL LETTER KHA;;0425;;0425 0446;CYRILLIC SMALL LETTER TSE;Ll;0;L;;;;;N;;;0426;;0426 0447;CYRILLIC SMALL LETTER CHE;Ll;0;L;;;;;N;;;0427;;0427 0448;CYRILLIC SMALL LETTER SHA;Ll;0;L;;;;;N;;;0428;;0428 0449;CYRILLIC SMALL LETTER SHCHA;Ll;0;L;;;;;N;;;0429;;0429 044A;CYRILLIC SMALL LETTER HARD SIGN;Ll;0;L;;;;;N;;;042A;;042A 044B;CYRILLIC SMALL LETTER YERU;Ll;0;L;;;;;N;CYRILLIC SMALL LETTER YERI;;042B;;042B 044C;CYRILLIC SMALL LETTER SOFT SIGN;Ll;0;L;;;;;N;;;042C;;042C 044D;CYRILLIC SMALL LETTER E;Ll;0;L;;;;;N;CYRILLIC SMALL LETTER REVERSED E;;042D;;042D 044E;CYRILLIC SMALL LETTER YU;Ll;0;L;;;;;N;CYRILLIC SMALL LETTER IU;;042E;;042E 044F;CYRILLIC SMALL LETTER YA;Ll;0;L;;;;;N;CYRILLIC SMALL LETTER IA;;042F;;042F 0450;CYRILLIC SMALL LETTER IE WITH GRAVE;Ll;0;L;0435 0300;;;;N;;;0400;;0400 0451;CYRILLIC SMALL LETTER IO;Ll;0;L;0435 0308;;;;N;;;0401;;0401 0452;CYRILLIC SMALL LETTER DJE;Ll;0;L;;;;;N;;;0402;;0402 0453;CYRILLIC SMALL LETTER GJE;Ll;0;L;0433 0301;;;;N;;;0403;;0403 0454;CYRILLIC SMALL LETTER UKRAINIAN IE;Ll;0;L;;;;;N;CYRILLIC SMALL LETTER E;;0404;;0404 0455;CYRILLIC SMALL LETTER DZE;Ll;0;L;;;;;N;;;0405;;0405 0456;CYRILLIC SMALL LETTER BYELORUSSIAN-UKRAINIAN I;Ll;0;L;;;;;N;CYRILLIC SMALL LETTER I;;0406;;0406 0457;CYRILLIC SMALL LETTER YI;Ll;0;L;0456 0308;;;;N;;;0407;;0407 0458;CYRILLIC SMALL LETTER JE;Ll;0;L;;;;;N;;;0408;;0408 0459;CYRILLIC SMALL LETTER LJE;Ll;0;L;;;;;N;;;0409;;0409 045A;CYRILLIC SMALL LETTER NJE;Ll;0;L;;;;;N;;;040A;;040A 045B;CYRILLIC SMALL LETTER TSHE;Ll;0;L;;;;;N;;;040B;;040B 045C;CYRILLIC SMALL LETTER KJE;Ll;0;L;043A 0301;;;;N;;;040C;;040C 045D;CYRILLIC SMALL LETTER I WITH GRAVE;Ll;0;L;0438 0300;;;;N;;;040D;;040D 045E;CYRILLIC SMALL LETTER SHORT U;Ll;0;L;0443 0306;;;;N;;;040E;;040E 045F;CYRILLIC SMALL LETTER DZHE;Ll;0;L;;;;;N;;;040F;;040F 0460;CYRILLIC CAPITAL LETTER OMEGA;Lu;0;L;;;;;N;;;;0461; 0461;CYRILLIC SMALL LETTER OMEGA;Ll;0;L;;;;;N;;;0460;;0460 0462;CYRILLIC CAPITAL LETTER YAT;Lu;0;L;;;;;N;;;;0463; 0463;CYRILLIC SMALL LETTER YAT;Ll;0;L;;;;;N;;;0462;;0462 0464;CYRILLIC CAPITAL LETTER IOTIFIED E;Lu;0;L;;;;;N;;;;0465; 0465;CYRILLIC SMALL LETTER IOTIFIED E;Ll;0;L;;;;;N;;;0464;;0464 0466;CYRILLIC CAPITAL LETTER LITTLE YUS;Lu;0;L;;;;;N;;;;0467; 0467;CYRILLIC SMALL LETTER LITTLE YUS;Ll;0;L;;;;;N;;;0466;;0466 0468;CYRILLIC CAPITAL LETTER IOTIFIED LITTLE YUS;Lu;0;L;;;;;N;;;;0469; 0469;CYRILLIC SMALL LETTER IOTIFIED LITTLE YUS;Ll;0;L;;;;;N;;;0468;;0468 046A;CYRILLIC CAPITAL LETTER BIG YUS;Lu;0;L;;;;;N;;;;046B; 046B;CYRILLIC SMALL LETTER BIG YUS;Ll;0;L;;;;;N;;;046A;;046A 046C;CYRILLIC CAPITAL LETTER IOTIFIED BIG YUS;Lu;0;L;;;;;N;;;;046D; 046D;CYRILLIC SMALL LETTER IOTIFIED BIG YUS;Ll;0;L;;;;;N;;;046C;;046C 046E;CYRILLIC CAPITAL LETTER KSI;Lu;0;L;;;;;N;;;;046F; 046F;CYRILLIC SMALL LETTER KSI;Ll;0;L;;;;;N;;;046E;;046E 0470;CYRILLIC CAPITAL LETTER PSI;Lu;0;L;;;;;N;;;;0471; 0471;CYRILLIC SMALL LETTER PSI;Ll;0;L;;;;;N;;;0470;;0470 0472;CYRILLIC CAPITAL LETTER FITA;Lu;0;L;;;;;N;;;;0473; 0473;CYRILLIC SMALL LETTER FITA;Ll;0;L;;;;;N;;;0472;;0472 0474;CYRILLIC CAPITAL LETTER IZHITSA;Lu;0;L;;;;;N;;;;0475; 0475;CYRILLIC SMALL LETTER IZHITSA;Ll;0;L;;;;;N;;;0474;;0474 0476;CYRILLIC CAPITAL LETTER IZHITSA WITH DOUBLE GRAVE ACCENT;Lu;0;L;0474 030F;;;;N;CYRILLIC CAPITAL LETTER IZHITSA DOUBLE GRAVE;;;0477; 0477;CYRILLIC SMALL LETTER IZHITSA WITH DOUBLE GRAVE ACCENT;Ll;0;L;0475 030F;;;;N;CYRILLIC SMALL LETTER IZHITSA DOUBLE GRAVE;;0476;;0476 0478;CYRILLIC CAPITAL LETTER UK;Lu;0;L;;;;;N;CYRILLIC CAPITAL LETTER UK DIGRAPH;;;0479; 0479;CYRILLIC SMALL LETTER UK;Ll;0;L;;;;;N;CYRILLIC SMALL LETTER UK DIGRAPH;;0478;;0478 047A;CYRILLIC CAPITAL LETTER ROUND OMEGA;Lu;0;L;;;;;N;;;;047B; 047B;CYRILLIC SMALL LETTER ROUND OMEGA;Ll;0;L;;;;;N;;;047A;;047A 047C;CYRILLIC CAPITAL LETTER OMEGA WITH TITLO;Lu;0;L;;;;;N;CYRILLIC CAPITAL LETTER OMEGA TITLO;;;047D; 047D;CYRILLIC SMALL LETTER OMEGA WITH TITLO;Ll;0;L;;;;;N;CYRILLIC SMALL LETTER OMEGA TITLO;;047C;;047C 047E;CYRILLIC CAPITAL LETTER OT;Lu;0;L;;;;;N;;;;047F; 047F;CYRILLIC SMALL LETTER OT;Ll;0;L;;;;;N;;;047E;;047E 0480;CYRILLIC CAPITAL LETTER KOPPA;Lu;0;L;;;;;N;;;;0481; 0481;CYRILLIC SMALL LETTER KOPPA;Ll;0;L;;;;;N;;;0480;;0480 0482;CYRILLIC THOUSANDS SIGN;So;0;L;;;;;N;;;;; 0483;COMBINING CYRILLIC TITLO;Mn;230;NSM;;;;;N;CYRILLIC NON-SPACING TITLO;;;; 0484;COMBINING CYRILLIC PALATALIZATION;Mn;230;NSM;;;;;N;CYRILLIC NON-SPACING PALATALIZATION;;;; 0485;COMBINING CYRILLIC DASIA PNEUMATA;Mn;230;NSM;;;;;N;CYRILLIC NON-SPACING DASIA PNEUMATA;;;; 0486;COMBINING CYRILLIC PSILI PNEUMATA;Mn;230;NSM;;;;;N;CYRILLIC NON-SPACING PSILI PNEUMATA;;;; 0487;COMBINING CYRILLIC POKRYTIE;Mn;230;NSM;;;;;N;;;;; 0488;COMBINING CYRILLIC HUNDRED THOUSANDS SIGN;Me;0;NSM;;;;;N;;;;; 0489;COMBINING CYRILLIC MILLIONS SIGN;Me;0;NSM;;;;;N;;;;; 048A;CYRILLIC CAPITAL LETTER SHORT I WITH TAIL;Lu;0;L;;;;;N;;;;048B; 048B;CYRILLIC SMALL LETTER SHORT I WITH TAIL;Ll;0;L;;;;;N;;;048A;;048A 048C;CYRILLIC CAPITAL LETTER SEMISOFT SIGN;Lu;0;L;;;;;N;;;;048D; 048D;CYRILLIC SMALL LETTER SEMISOFT SIGN;Ll;0;L;;;;;N;;;048C;;048C 048E;CYRILLIC CAPITAL LETTER ER WITH TICK;Lu;0;L;;;;;N;;;;048F; 048F;CYRILLIC SMALL LETTER ER WITH TICK;Ll;0;L;;;;;N;;;048E;;048E 0490;CYRILLIC CAPITAL LETTER GHE WITH UPTURN;Lu;0;L;;;;;N;CYRILLIC CAPITAL LETTER GE WITH UPTURN;;;0491; 0491;CYRILLIC SMALL LETTER GHE WITH UPTURN;Ll;0;L;;;;;N;CYRILLIC SMALL LETTER GE WITH UPTURN;;0490;;0490 0492;CYRILLIC CAPITAL LETTER GHE WITH STROKE;Lu;0;L;;;;;N;CYRILLIC CAPITAL LETTER GE BAR;;;0493; 0493;CYRILLIC SMALL LETTER GHE WITH STROKE;Ll;0;L;;;;;N;CYRILLIC SMALL LETTER GE BAR;;0492;;0492 0494;CYRILLIC CAPITAL LETTER GHE WITH MIDDLE HOOK;Lu;0;L;;;;;N;CYRILLIC CAPITAL LETTER GE HOOK;;;0495; 0495;CYRILLIC SMALL LETTER GHE WITH MIDDLE HOOK;Ll;0;L;;;;;N;CYRILLIC SMALL LETTER GE HOOK;;0494;;0494 0496;CYRILLIC CAPITAL LETTER ZHE WITH DESCENDER;Lu;0;L;;;;;N;CYRILLIC CAPITAL LETTER ZHE WITH RIGHT DESCENDER;;;0497; 0497;CYRILLIC SMALL LETTER ZHE WITH DESCENDER;Ll;0;L;;;;;N;CYRILLIC SMALL LETTER ZHE WITH RIGHT DESCENDER;;0496;;0496 0498;CYRILLIC CAPITAL LETTER ZE WITH DESCENDER;Lu;0;L;;;;;N;CYRILLIC CAPITAL LETTER ZE CEDILLA;;;0499; 0499;CYRILLIC SMALL LETTER ZE WITH DESCENDER;Ll;0;L;;;;;N;CYRILLIC SMALL LETTER ZE CEDILLA;;0498;;0498 049A;CYRILLIC CAPITAL LETTER KA WITH DESCENDER;Lu;0;L;;;;;N;CYRILLIC CAPITAL LETTER KA WITH RIGHT DESCENDER;;;049B; 049B;CYRILLIC SMALL LETTER KA WITH DESCENDER;Ll;0;L;;;;;N;CYRILLIC SMALL LETTER KA WITH RIGHT DESCENDER;;049A;;049A 049C;CYRILLIC CAPITAL LETTER KA WITH VERTICAL STROKE;Lu;0;L;;;;;N;CYRILLIC CAPITAL LETTER KA VERTICAL BAR;;;049D; 049D;CYRILLIC SMALL LETTER KA WITH VERTICAL STROKE;Ll;0;L;;;;;N;CYRILLIC SMALL LETTER KA VERTICAL BAR;;049C;;049C 049E;CYRILLIC CAPITAL LETTER KA WITH STROKE;Lu;0;L;;;;;N;CYRILLIC CAPITAL LETTER KA BAR;;;049F; 049F;CYRILLIC SMALL LETTER KA WITH STROKE;Ll;0;L;;;;;N;CYRILLIC SMALL LETTER KA BAR;;049E;;049E 04A0;CYRILLIC CAPITAL LETTER BASHKIR KA;Lu;0;L;;;;;N;CYRILLIC CAPITAL LETTER REVERSED GE KA;;;04A1; 04A1;CYRILLIC SMALL LETTER BASHKIR KA;Ll;0;L;;;;;N;CYRILLIC SMALL LETTER REVERSED GE KA;;04A0;;04A0 04A2;CYRILLIC CAPITAL LETTER EN WITH DESCENDER;Lu;0;L;;;;;N;CYRILLIC CAPITAL LETTER EN WITH RIGHT DESCENDER;;;04A3; 04A3;CYRILLIC SMALL LETTER EN WITH DESCENDER;Ll;0;L;;;;;N;CYRILLIC SMALL LETTER EN WITH RIGHT DESCENDER;;04A2;;04A2 04A4;CYRILLIC CAPITAL LIGATURE EN GHE;Lu;0;L;;;;;N;CYRILLIC CAPITAL LETTER EN GE;;;04A5; 04A5;CYRILLIC SMALL LIGATURE EN GHE;Ll;0;L;;;;;N;CYRILLIC SMALL LETTER EN GE;;04A4;;04A4 04A6;CYRILLIC CAPITAL LETTER PE WITH MIDDLE HOOK;Lu;0;L;;;;;N;CYRILLIC CAPITAL LETTER PE HOOK;;;04A7; 04A7;CYRILLIC SMALL LETTER PE WITH MIDDLE HOOK;Ll;0;L;;;;;N;CYRILLIC SMALL LETTER PE HOOK;;04A6;;04A6 04A8;CYRILLIC CAPITAL LETTER ABKHASIAN HA;Lu;0;L;;;;;N;CYRILLIC CAPITAL LETTER O HOOK;;;04A9; 04A9;CYRILLIC SMALL LETTER ABKHASIAN HA;Ll;0;L;;;;;N;CYRILLIC SMALL LETTER O HOOK;;04A8;;04A8 04AA;CYRILLIC CAPITAL LETTER ES WITH DESCENDER;Lu;0;L;;;;;N;CYRILLIC CAPITAL LETTER ES CEDILLA;;;04AB; 04AB;CYRILLIC SMALL LETTER ES WITH DESCENDER;Ll;0;L;;;;;N;CYRILLIC SMALL LETTER ES CEDILLA;;04AA;;04AA 04AC;CYRILLIC CAPITAL LETTER TE WITH DESCENDER;Lu;0;L;;;;;N;CYRILLIC CAPITAL LETTER TE WITH RIGHT DESCENDER;;;04AD; 04AD;CYRILLIC SMALL LETTER TE WITH DESCENDER;Ll;0;L;;;;;N;CYRILLIC SMALL LETTER TE WITH RIGHT DESCENDER;;04AC;;04AC 04AE;CYRILLIC CAPITAL LETTER STRAIGHT U;Lu;0;L;;;;;N;;;;04AF; 04AF;CYRILLIC SMALL LETTER STRAIGHT U;Ll;0;L;;;;;N;;;04AE;;04AE 04B0;CYRILLIC CAPITAL LETTER STRAIGHT U WITH STROKE;Lu;0;L;;;;;N;CYRILLIC CAPITAL LETTER STRAIGHT U BAR;;;04B1; 04B1;CYRILLIC SMALL LETTER STRAIGHT U WITH STROKE;Ll;0;L;;;;;N;CYRILLIC SMALL LETTER STRAIGHT U BAR;;04B0;;04B0 04B2;CYRILLIC CAPITAL LETTER HA WITH DESCENDER;Lu;0;L;;;;;N;CYRILLIC CAPITAL LETTER KHA WITH RIGHT DESCENDER;;;04B3; 04B3;CYRILLIC SMALL LETTER HA WITH DESCENDER;Ll;0;L;;;;;N;CYRILLIC SMALL LETTER KHA WITH RIGHT DESCENDER;;04B2;;04B2 04B4;CYRILLIC CAPITAL LIGATURE TE TSE;Lu;0;L;;;;;N;CYRILLIC CAPITAL LETTER TE TSE;;;04B5; 04B5;CYRILLIC SMALL LIGATURE TE TSE;Ll;0;L;;;;;N;CYRILLIC SMALL LETTER TE TSE;;04B4;;04B4 04B6;CYRILLIC CAPITAL LETTER CHE WITH DESCENDER;Lu;0;L;;;;;N;CYRILLIC CAPITAL LETTER CHE WITH RIGHT DESCENDER;;;04B7; 04B7;CYRILLIC SMALL LETTER CHE WITH DESCENDER;Ll;0;L;;;;;N;CYRILLIC SMALL LETTER CHE WITH RIGHT DESCENDER;;04B6;;04B6 04B8;CYRILLIC CAPITAL LETTER CHE WITH VERTICAL STROKE;Lu;0;L;;;;;N;CYRILLIC CAPITAL LETTER CHE VERTICAL BAR;;;04B9; 04B9;CYRILLIC SMALL LETTER CHE WITH VERTICAL STROKE;Ll;0;L;;;;;N;CYRILLIC SMALL LETTER CHE VERTICAL BAR;;04B8;;04B8 04BA;CYRILLIC CAPITAL LETTER SHHA;Lu;0;L;;;;;N;CYRILLIC CAPITAL LETTER H;;;04BB; 04BB;CYRILLIC SMALL LETTER SHHA;Ll;0;L;;;;;N;CYRILLIC SMALL LETTER H;;04BA;;04BA 04BC;CYRILLIC CAPITAL LETTER ABKHASIAN CHE;Lu;0;L;;;;;N;CYRILLIC CAPITAL LETTER IE HOOK;;;04BD; 04BD;CYRILLIC SMALL LETTER ABKHASIAN CHE;Ll;0;L;;;;;N;CYRILLIC SMALL LETTER IE HOOK;;04BC;;04BC 04BE;CYRILLIC CAPITAL LETTER ABKHASIAN CHE WITH DESCENDER;Lu;0;L;;;;;N;CYRILLIC CAPITAL LETTER IE HOOK OGONEK;;;04BF; 04BF;CYRILLIC SMALL LETTER ABKHASIAN CHE WITH DESCENDER;Ll;0;L;;;;;N;CYRILLIC SMALL LETTER IE HOOK OGONEK;;04BE;;04BE 04C0;CYRILLIC LETTER PALOCHKA;Lu;0;L;;;;;N;CYRILLIC LETTER I;;;04CF; 04C1;CYRILLIC CAPITAL LETTER ZHE WITH BREVE;Lu;0;L;0416 0306;;;;N;CYRILLIC CAPITAL LETTER SHORT ZHE;;;04C2; 04C2;CYRILLIC SMALL LETTER ZHE WITH BREVE;Ll;0;L;0436 0306;;;;N;CYRILLIC SMALL LETTER SHORT ZHE;;04C1;;04C1 04C3;CYRILLIC CAPITAL LETTER KA WITH HOOK;Lu;0;L;;;;;N;CYRILLIC CAPITAL LETTER KA HOOK;;;04C4; 04C4;CYRILLIC SMALL LETTER KA WITH HOOK;Ll;0;L;;;;;N;CYRILLIC SMALL LETTER KA HOOK;;04C3;;04C3 04C5;CYRILLIC CAPITAL LETTER EL WITH TAIL;Lu;0;L;;;;;N;;;;04C6; 04C6;CYRILLIC SMALL LETTER EL WITH TAIL;Ll;0;L;;;;;N;;;04C5;;04C5 04C7;CYRILLIC CAPITAL LETTER EN WITH HOOK;Lu;0;L;;;;;N;CYRILLIC CAPITAL LETTER EN HOOK;;;04C8; 04C8;CYRILLIC SMALL LETTER EN WITH HOOK;Ll;0;L;;;;;N;CYRILLIC SMALL LETTER EN HOOK;;04C7;;04C7 04C9;CYRILLIC CAPITAL LETTER EN WITH TAIL;Lu;0;L;;;;;N;;;;04CA; 04CA;CYRILLIC SMALL LETTER EN WITH TAIL;Ll;0;L;;;;;N;;;04C9;;04C9 04CB;CYRILLIC CAPITAL LETTER KHAKASSIAN CHE;Lu;0;L;;;;;N;CYRILLIC CAPITAL LETTER CHE WITH LEFT DESCENDER;;;04CC; 04CC;CYRILLIC SMALL LETTER KHAKASSIAN CHE;Ll;0;L;;;;;N;CYRILLIC SMALL LETTER CHE WITH LEFT DESCENDER;;04CB;;04CB 04CD;CYRILLIC CAPITAL LETTER EM WITH TAIL;Lu;0;L;;;;;N;;;;04CE; 04CE;CYRILLIC SMALL LETTER EM WITH TAIL;Ll;0;L;;;;;N;;;04CD;;04CD 04CF;CYRILLIC SMALL LETTER PALOCHKA;Ll;0;L;;;;;N;;;04C0;;04C0 04D0;CYRILLIC CAPITAL LETTER A WITH BREVE;Lu;0;L;0410 0306;;;;N;;;;04D1; 04D1;CYRILLIC SMALL LETTER A WITH BREVE;Ll;0;L;0430 0306;;;;N;;;04D0;;04D0 04D2;CYRILLIC CAPITAL LETTER A WITH DIAERESIS;Lu;0;L;0410 0308;;;;N;;;;04D3; 04D3;CYRILLIC SMALL LETTER A WITH DIAERESIS;Ll;0;L;0430 0308;;;;N;;;04D2;;04D2 04D4;CYRILLIC CAPITAL LIGATURE A IE;Lu;0;L;;;;;N;;;;04D5; 04D5;CYRILLIC SMALL LIGATURE A IE;Ll;0;L;;;;;N;;;04D4;;04D4 04D6;CYRILLIC CAPITAL LETTER IE WITH BREVE;Lu;0;L;0415 0306;;;;N;;;;04D7; 04D7;CYRILLIC SMALL LETTER IE WITH BREVE;Ll;0;L;0435 0306;;;;N;;;04D6;;04D6 04D8;CYRILLIC CAPITAL LETTER SCHWA;Lu;0;L;;;;;N;;;;04D9; 04D9;CYRILLIC SMALL LETTER SCHWA;Ll;0;L;;;;;N;;;04D8;;04D8 04DA;CYRILLIC CAPITAL LETTER SCHWA WITH DIAERESIS;Lu;0;L;04D8 0308;;;;N;;;;04DB; 04DB;CYRILLIC SMALL LETTER SCHWA WITH DIAERESIS;Ll;0;L;04D9 0308;;;;N;;;04DA;;04DA 04DC;CYRILLIC CAPITAL LETTER ZHE WITH DIAERESIS;Lu;0;L;0416 0308;;;;N;;;;04DD; 04DD;CYRILLIC SMALL LETTER ZHE WITH DIAERESIS;Ll;0;L;0436 0308;;;;N;;;04DC;;04DC 04DE;CYRILLIC CAPITAL LETTER ZE WITH DIAERESIS;Lu;0;L;0417 0308;;;;N;;;;04DF; 04DF;CYRILLIC SMALL LETTER ZE WITH DIAERESIS;Ll;0;L;0437 0308;;;;N;;;04DE;;04DE 04E0;CYRILLIC CAPITAL LETTER ABKHASIAN DZE;Lu;0;L;;;;;N;;;;04E1; 04E1;CYRILLIC SMALL LETTER ABKHASIAN DZE;Ll;0;L;;;;;N;;;04E0;;04E0 04E2;CYRILLIC CAPITAL LETTER I WITH MACRON;Lu;0;L;0418 0304;;;;N;;;;04E3; 04E3;CYRILLIC SMALL LETTER I WITH MACRON;Ll;0;L;0438 0304;;;;N;;;04E2;;04E2 04E4;CYRILLIC CAPITAL LETTER I WITH DIAERESIS;Lu;0;L;0418 0308;;;;N;;;;04E5; 04E5;CYRILLIC SMALL LETTER I WITH DIAERESIS;Ll;0;L;0438 0308;;;;N;;;04E4;;04E4 04E6;CYRILLIC CAPITAL LETTER O WITH DIAERESIS;Lu;0;L;041E 0308;;;;N;;;;04E7; 04E7;CYRILLIC SMALL LETTER O WITH DIAERESIS;Ll;0;L;043E 0308;;;;N;;;04E6;;04E6 04E8;CYRILLIC CAPITAL LETTER BARRED O;Lu;0;L;;;;;N;;;;04E9; 04E9;CYRILLIC SMALL LETTER BARRED O;Ll;0;L;;;;;N;;;04E8;;04E8 04EA;CYRILLIC CAPITAL LETTER BARRED O WITH DIAERESIS;Lu;0;L;04E8 0308;;;;N;;;;04EB; 04EB;CYRILLIC SMALL LETTER BARRED O WITH DIAERESIS;Ll;0;L;04E9 0308;;;;N;;;04EA;;04EA 04EC;CYRILLIC CAPITAL LETTER E WITH DIAERESIS;Lu;0;L;042D 0308;;;;N;;;;04ED; 04ED;CYRILLIC SMALL LETTER E WITH DIAERESIS;Ll;0;L;044D 0308;;;;N;;;04EC;;04EC 04EE;CYRILLIC CAPITAL LETTER U WITH MACRON;Lu;0;L;0423 0304;;;;N;;;;04EF; 04EF;CYRILLIC SMALL LETTER U WITH MACRON;Ll;0;L;0443 0304;;;;N;;;04EE;;04EE 04F0;CYRILLIC CAPITAL LETTER U WITH DIAERESIS;Lu;0;L;0423 0308;;;;N;;;;04F1; 04F1;CYRILLIC SMALL LETTER U WITH DIAERESIS;Ll;0;L;0443 0308;;;;N;;;04F0;;04F0 04F2;CYRILLIC CAPITAL LETTER U WITH DOUBLE ACUTE;Lu;0;L;0423 030B;;;;N;;;;04F3; 04F3;CYRILLIC SMALL LETTER U WITH DOUBLE ACUTE;Ll;0;L;0443 030B;;;;N;;;04F2;;04F2 04F4;CYRILLIC CAPITAL LETTER CHE WITH DIAERESIS;Lu;0;L;0427 0308;;;;N;;;;04F5; 04F5;CYRILLIC SMALL LETTER CHE WITH DIAERESIS;Ll;0;L;0447 0308;;;;N;;;04F4;;04F4 04F6;CYRILLIC CAPITAL LETTER GHE WITH DESCENDER;Lu;0;L;;;;;N;;;;04F7; 04F7;CYRILLIC SMALL LETTER GHE WITH DESCENDER;Ll;0;L;;;;;N;;;04F6;;04F6 04F8;CYRILLIC CAPITAL LETTER YERU WITH DIAERESIS;Lu;0;L;042B 0308;;;;N;;;;04F9; 04F9;CYRILLIC SMALL LETTER YERU WITH DIAERESIS;Ll;0;L;044B 0308;;;;N;;;04F8;;04F8 04FA;CYRILLIC CAPITAL LETTER GHE WITH STROKE AND HOOK;Lu;0;L;;;;;N;;;;04FB; 04FB;CYRILLIC SMALL LETTER GHE WITH STROKE AND HOOK;Ll;0;L;;;;;N;;;04FA;;04FA 04FC;CYRILLIC CAPITAL LETTER HA WITH HOOK;Lu;0;L;;;;;N;;;;04FD; 04FD;CYRILLIC SMALL LETTER HA WITH HOOK;Ll;0;L;;;;;N;;;04FC;;04FC 04FE;CYRILLIC CAPITAL LETTER HA WITH STROKE;Lu;0;L;;;;;N;;;;04FF; 04FF;CYRILLIC SMALL LETTER HA WITH STROKE;Ll;0;L;;;;;N;;;04FE;;04FE 0500;CYRILLIC CAPITAL LETTER KOMI DE;Lu;0;L;;;;;N;;;;0501; 0501;CYRILLIC SMALL LETTER KOMI DE;Ll;0;L;;;;;N;;;0500;;0500 0502;CYRILLIC CAPITAL LETTER KOMI DJE;Lu;0;L;;;;;N;;;;0503; 0503;CYRILLIC SMALL LETTER KOMI DJE;Ll;0;L;;;;;N;;;0502;;0502 0504;CYRILLIC CAPITAL LETTER KOMI ZJE;Lu;0;L;;;;;N;;;;0505; 0505;CYRILLIC SMALL LETTER KOMI ZJE;Ll;0;L;;;;;N;;;0504;;0504 0506;CYRILLIC CAPITAL LETTER KOMI DZJE;Lu;0;L;;;;;N;;;;0507; 0507;CYRILLIC SMALL LETTER KOMI DZJE;Ll;0;L;;;;;N;;;0506;;0506 0508;CYRILLIC CAPITAL LETTER KOMI LJE;Lu;0;L;;;;;N;;;;0509; 0509;CYRILLIC SMALL LETTER KOMI LJE;Ll;0;L;;;;;N;;;0508;;0508 050A;CYRILLIC CAPITAL LETTER KOMI NJE;Lu;0;L;;;;;N;;;;050B; 050B;CYRILLIC SMALL LETTER KOMI NJE;Ll;0;L;;;;;N;;;050A;;050A 050C;CYRILLIC CAPITAL LETTER KOMI SJE;Lu;0;L;;;;;N;;;;050D; 050D;CYRILLIC SMALL LETTER KOMI SJE;Ll;0;L;;;;;N;;;050C;;050C 050E;CYRILLIC CAPITAL LETTER KOMI TJE;Lu;0;L;;;;;N;;;;050F; 050F;CYRILLIC SMALL LETTER KOMI TJE;Ll;0;L;;;;;N;;;050E;;050E 0510;CYRILLIC CAPITAL LETTER REVERSED ZE;Lu;0;L;;;;;N;;;;0511; 0511;CYRILLIC SMALL LETTER REVERSED ZE;Ll;0;L;;;;;N;;;0510;;0510 0512;CYRILLIC CAPITAL LETTER EL WITH HOOK;Lu;0;L;;;;;N;;;;0513; 0513;CYRILLIC SMALL LETTER EL WITH HOOK;Ll;0;L;;;;;N;;;0512;;0512 0514;CYRILLIC CAPITAL LETTER LHA;Lu;0;L;;;;;N;;;;0515; 0515;CYRILLIC SMALL LETTER LHA;Ll;0;L;;;;;N;;;0514;;0514 0516;CYRILLIC CAPITAL LETTER RHA;Lu;0;L;;;;;N;;;;0517; 0517;CYRILLIC SMALL LETTER RHA;Ll;0;L;;;;;N;;;0516;;0516 0518;CYRILLIC CAPITAL LETTER YAE;Lu;0;L;;;;;N;;;;0519; 0519;CYRILLIC SMALL LETTER YAE;Ll;0;L;;;;;N;;;0518;;0518 051A;CYRILLIC CAPITAL LETTER QA;Lu;0;L;;;;;N;;;;051B; 051B;CYRILLIC SMALL LETTER QA;Ll;0;L;;;;;N;;;051A;;051A 051C;CYRILLIC CAPITAL LETTER WE;Lu;0;L;;;;;N;;;;051D; 051D;CYRILLIC SMALL LETTER WE;Ll;0;L;;;;;N;;;051C;;051C 051E;CYRILLIC CAPITAL LETTER ALEUT KA;Lu;0;L;;;;;N;;;;051F; 051F;CYRILLIC SMALL LETTER ALEUT KA;Ll;0;L;;;;;N;;;051E;;051E 0520;CYRILLIC CAPITAL LETTER EL WITH MIDDLE HOOK;Lu;0;L;;;;;N;;;;0521; 0521;CYRILLIC SMALL LETTER EL WITH MIDDLE HOOK;Ll;0;L;;;;;N;;;0520;;0520 0522;CYRILLIC CAPITAL LETTER EN WITH MIDDLE HOOK;Lu;0;L;;;;;N;;;;0523; 0523;CYRILLIC SMALL LETTER EN WITH MIDDLE HOOK;Ll;0;L;;;;;N;;;0522;;0522 0524;CYRILLIC CAPITAL LETTER PE WITH DESCENDER;Lu;0;L;;;;;N;;;;0525; 0525;CYRILLIC SMALL LETTER PE WITH DESCENDER;Ll;0;L;;;;;N;;;0524;;0524 0526;CYRILLIC CAPITAL LETTER SHHA WITH DESCENDER;Lu;0;L;;;;;N;;;;0527; 0527;CYRILLIC SMALL LETTER SHHA WITH DESCENDER;Ll;0;L;;;;;N;;;0526;;0526 0528;CYRILLIC CAPITAL LETTER EN WITH LEFT HOOK;Lu;0;L;;;;;N;;;;0529; 0529;CYRILLIC SMALL LETTER EN WITH LEFT HOOK;Ll;0;L;;;;;N;;;0528;;0528 052A;CYRILLIC CAPITAL LETTER DZZHE;Lu;0;L;;;;;N;;;;052B; 052B;CYRILLIC SMALL LETTER DZZHE;Ll;0;L;;;;;N;;;052A;;052A 052C;CYRILLIC CAPITAL LETTER DCHE;Lu;0;L;;;;;N;;;;052D; 052D;CYRILLIC SMALL LETTER DCHE;Ll;0;L;;;;;N;;;052C;;052C 052E;CYRILLIC CAPITAL LETTER EL WITH DESCENDER;Lu;0;L;;;;;N;;;;052F; 052F;CYRILLIC SMALL LETTER EL WITH DESCENDER;Ll;0;L;;;;;N;;;052E;;052E 0531;ARMENIAN CAPITAL LETTER AYB;Lu;0;L;;;;;N;;;;0561; 0532;ARMENIAN CAPITAL LETTER BEN;Lu;0;L;;;;;N;;;;0562; 0533;ARMENIAN CAPITAL LETTER GIM;Lu;0;L;;;;;N;;;;0563; 0534;ARMENIAN CAPITAL LETTER DA;Lu;0;L;;;;;N;;;;0564; 0535;ARMENIAN CAPITAL LETTER ECH;Lu;0;L;;;;;N;;;;0565; 0536;ARMENIAN CAPITAL LETTER ZA;Lu;0;L;;;;;N;;;;0566; 0537;ARMENIAN CAPITAL LETTER EH;Lu;0;L;;;;;N;;;;0567; 0538;ARMENIAN CAPITAL LETTER ET;Lu;0;L;;;;;N;;;;0568; 0539;ARMENIAN CAPITAL LETTER TO;Lu;0;L;;;;;N;;;;0569; 053A;ARMENIAN CAPITAL LETTER ZHE;Lu;0;L;;;;;N;;;;056A; 053B;ARMENIAN CAPITAL LETTER INI;Lu;0;L;;;;;N;;;;056B; 053C;ARMENIAN CAPITAL LETTER LIWN;Lu;0;L;;;;;N;;;;056C; 053D;ARMENIAN CAPITAL LETTER XEH;Lu;0;L;;;;;N;;;;056D; 053E;ARMENIAN CAPITAL LETTER CA;Lu;0;L;;;;;N;;;;056E; 053F;ARMENIAN CAPITAL LETTER KEN;Lu;0;L;;;;;N;;;;056F; 0540;ARMENIAN CAPITAL LETTER HO;Lu;0;L;;;;;N;;;;0570; 0541;ARMENIAN CAPITAL LETTER JA;Lu;0;L;;;;;N;;;;0571; 0542;ARMENIAN CAPITAL LETTER GHAD;Lu;0;L;;;;;N;ARMENIAN CAPITAL LETTER LAD;;;0572; 0543;ARMENIAN CAPITAL LETTER CHEH;Lu;0;L;;;;;N;;;;0573; 0544;ARMENIAN CAPITAL LETTER MEN;Lu;0;L;;;;;N;;;;0574; 0545;ARMENIAN CAPITAL LETTER YI;Lu;0;L;;;;;N;;;;0575; 0546;ARMENIAN CAPITAL LETTER NOW;Lu;0;L;;;;;N;;;;0576; 0547;ARMENIAN CAPITAL LETTER SHA;Lu;0;L;;;;;N;;;;0577; 0548;ARMENIAN CAPITAL LETTER VO;Lu;0;L;;;;;N;;;;0578; 0549;ARMENIAN CAPITAL LETTER CHA;Lu;0;L;;;;;N;;;;0579; 054A;ARMENIAN CAPITAL LETTER PEH;Lu;0;L;;;;;N;;;;057A; 054B;ARMENIAN CAPITAL LETTER JHEH;Lu;0;L;;;;;N;;;;057B; 054C;ARMENIAN CAPITAL LETTER RA;Lu;0;L;;;;;N;;;;057C; 054D;ARMENIAN CAPITAL LETTER SEH;Lu;0;L;;;;;N;;;;057D; 054E;ARMENIAN CAPITAL LETTER VEW;Lu;0;L;;;;;N;;;;057E; 054F;ARMENIAN CAPITAL LETTER TIWN;Lu;0;L;;;;;N;;;;057F; 0550;ARMENIAN CAPITAL LETTER REH;Lu;0;L;;;;;N;;;;0580; 0551;ARMENIAN CAPITAL LETTER CO;Lu;0;L;;;;;N;;;;0581; 0552;ARMENIAN CAPITAL LETTER YIWN;Lu;0;L;;;;;N;;;;0582; 0553;ARMENIAN CAPITAL LETTER PIWR;Lu;0;L;;;;;N;;;;0583; 0554;ARMENIAN CAPITAL LETTER KEH;Lu;0;L;;;;;N;;;;0584; 0555;ARMENIAN CAPITAL LETTER OH;Lu;0;L;;;;;N;;;;0585; 0556;ARMENIAN CAPITAL LETTER FEH;Lu;0;L;;;;;N;;;;0586; 0559;ARMENIAN MODIFIER LETTER LEFT HALF RING;Lm;0;L;;;;;N;;;;; 055A;ARMENIAN APOSTROPHE;Po;0;L;;;;;N;ARMENIAN MODIFIER LETTER RIGHT HALF RING;;;; 055B;ARMENIAN EMPHASIS MARK;Po;0;L;;;;;N;;;;; 055C;ARMENIAN EXCLAMATION MARK;Po;0;L;;;;;N;;;;; 055D;ARMENIAN COMMA;Po;0;L;;;;;N;;;;; 055E;ARMENIAN QUESTION MARK;Po;0;L;;;;;N;;;;; 055F;ARMENIAN ABBREVIATION MARK;Po;0;L;;;;;N;;;;; 0561;ARMENIAN SMALL LETTER AYB;Ll;0;L;;;;;N;;;0531;;0531 0562;ARMENIAN SMALL LETTER BEN;Ll;0;L;;;;;N;;;0532;;0532 0563;ARMENIAN SMALL LETTER GIM;Ll;0;L;;;;;N;;;0533;;0533 0564;ARMENIAN SMALL LETTER DA;Ll;0;L;;;;;N;;;0534;;0534 0565;ARMENIAN SMALL LETTER ECH;Ll;0;L;;;;;N;;;0535;;0535 0566;ARMENIAN SMALL LETTER ZA;Ll;0;L;;;;;N;;;0536;;0536 0567;ARMENIAN SMALL LETTER EH;Ll;0;L;;;;;N;;;0537;;0537 0568;ARMENIAN SMALL LETTER ET;Ll;0;L;;;;;N;;;0538;;0538 0569;ARMENIAN SMALL LETTER TO;Ll;0;L;;;;;N;;;0539;;0539 056A;ARMENIAN SMALL LETTER ZHE;Ll;0;L;;;;;N;;;053A;;053A 056B;ARMENIAN SMALL LETTER INI;Ll;0;L;;;;;N;;;053B;;053B 056C;ARMENIAN SMALL LETTER LIWN;Ll;0;L;;;;;N;;;053C;;053C 056D;ARMENIAN SMALL LETTER XEH;Ll;0;L;;;;;N;;;053D;;053D 056E;ARMENIAN SMALL LETTER CA;Ll;0;L;;;;;N;;;053E;;053E 056F;ARMENIAN SMALL LETTER KEN;Ll;0;L;;;;;N;;;053F;;053F 0570;ARMENIAN SMALL LETTER HO;Ll;0;L;;;;;N;;;0540;;0540 0571;ARMENIAN SMALL LETTER JA;Ll;0;L;;;;;N;;;0541;;0541 0572;ARMENIAN SMALL LETTER GHAD;Ll;0;L;;;;;N;ARMENIAN SMALL LETTER LAD;;0542;;0542 0573;ARMENIAN SMALL LETTER CHEH;Ll;0;L;;;;;N;;;0543;;0543 0574;ARMENIAN SMALL LETTER MEN;Ll;0;L;;;;;N;;;0544;;0544 0575;ARMENIAN SMALL LETTER YI;Ll;0;L;;;;;N;;;0545;;0545 0576;ARMENIAN SMALL LETTER NOW;Ll;0;L;;;;;N;;;0546;;0546 0577;ARMENIAN SMALL LETTER SHA;Ll;0;L;;;;;N;;;0547;;0547 0578;ARMENIAN SMALL LETTER VO;Ll;0;L;;;;;N;;;0548;;0548 0579;ARMENIAN SMALL LETTER CHA;Ll;0;L;;;;;N;;;0549;;0549 057A;ARMENIAN SMALL LETTER PEH;Ll;0;L;;;;;N;;;054A;;054A 057B;ARMENIAN SMALL LETTER JHEH;Ll;0;L;;;;;N;;;054B;;054B 057C;ARMENIAN SMALL LETTER RA;Ll;0;L;;;;;N;;;054C;;054C 057D;ARMENIAN SMALL LETTER SEH;Ll;0;L;;;;;N;;;054D;;054D 057E;ARMENIAN SMALL LETTER VEW;Ll;0;L;;;;;N;;;054E;;054E 057F;ARMENIAN SMALL LETTER TIWN;Ll;0;L;;;;;N;;;054F;;054F 0580;ARMENIAN SMALL LETTER REH;Ll;0;L;;;;;N;;;0550;;0550 0581;ARMENIAN SMALL LETTER CO;Ll;0;L;;;;;N;;;0551;;0551 0582;ARMENIAN SMALL LETTER YIWN;Ll;0;L;;;;;N;;;0552;;0552 0583;ARMENIAN SMALL LETTER PIWR;Ll;0;L;;;;;N;;;0553;;0553 0584;ARMENIAN SMALL LETTER KEH;Ll;0;L;;;;;N;;;0554;;0554 0585;ARMENIAN SMALL LETTER OH;Ll;0;L;;;;;N;;;0555;;0555 0586;ARMENIAN SMALL LETTER FEH;Ll;0;L;;;;;N;;;0556;;0556 0587;ARMENIAN SMALL LIGATURE ECH YIWN;Ll;0;L; 0565 0582;;;;N;;;;; 0589;ARMENIAN FULL STOP;Po;0;L;;;;;N;ARMENIAN PERIOD;;;; 058A;ARMENIAN HYPHEN;Pd;0;ON;;;;;N;;;;; 058D;RIGHT-FACING ARMENIAN ETERNITY SIGN;So;0;ON;;;;;N;;;;; 058E;LEFT-FACING ARMENIAN ETERNITY SIGN;So;0;ON;;;;;N;;;;; 058F;ARMENIAN DRAM SIGN;Sc;0;ET;;;;;N;;;;; 0591;HEBREW ACCENT ETNAHTA;Mn;220;NSM;;;;;N;;;;; 0592;HEBREW ACCENT SEGOL;Mn;230;NSM;;;;;N;;;;; 0593;HEBREW ACCENT SHALSHELET;Mn;230;NSM;;;;;N;;;;; 0594;HEBREW ACCENT ZAQEF QATAN;Mn;230;NSM;;;;;N;;;;; 0595;HEBREW ACCENT ZAQEF GADOL;Mn;230;NSM;;;;;N;;;;; 0596;HEBREW ACCENT TIPEHA;Mn;220;NSM;;;;;N;;;;; 0597;HEBREW ACCENT REVIA;Mn;230;NSM;;;;;N;;;;; 0598;HEBREW ACCENT ZARQA;Mn;230;NSM;;;;;N;;;;; 0599;HEBREW ACCENT PASHTA;Mn;230;NSM;;;;;N;;;;; 059A;HEBREW ACCENT YETIV;Mn;222;NSM;;;;;N;;;;; 059B;HEBREW ACCENT TEVIR;Mn;220;NSM;;;;;N;;;;; 059C;HEBREW ACCENT GERESH;Mn;230;NSM;;;;;N;;;;; 059D;HEBREW ACCENT GERESH MUQDAM;Mn;230;NSM;;;;;N;;;;; 059E;HEBREW ACCENT GERSHAYIM;Mn;230;NSM;;;;;N;;;;; 059F;HEBREW ACCENT QARNEY PARA;Mn;230;NSM;;;;;N;;;;; 05A0;HEBREW ACCENT TELISHA GEDOLA;Mn;230;NSM;;;;;N;;;;; 05A1;HEBREW ACCENT PAZER;Mn;230;NSM;;;;;N;;;;; 05A2;HEBREW ACCENT ATNAH HAFUKH;Mn;220;NSM;;;;;N;;;;; 05A3;HEBREW ACCENT MUNAH;Mn;220;NSM;;;;;N;;;;; 05A4;HEBREW ACCENT MAHAPAKH;Mn;220;NSM;;;;;N;;;;; 05A5;HEBREW ACCENT MERKHA;Mn;220;NSM;;;;;N;;;;; 05A6;HEBREW ACCENT MERKHA KEFULA;Mn;220;NSM;;;;;N;;;;; 05A7;HEBREW ACCENT DARGA;Mn;220;NSM;;;;;N;;;;; 05A8;HEBREW ACCENT QADMA;Mn;230;NSM;;;;;N;;;;; 05A9;HEBREW ACCENT TELISHA QETANA;Mn;230;NSM;;;;;N;;;;; 05AA;HEBREW ACCENT YERAH BEN YOMO;Mn;220;NSM;;;;;N;;;;; 05AB;HEBREW ACCENT OLE;Mn;230;NSM;;;;;N;;;;; 05AC;HEBREW ACCENT ILUY;Mn;230;NSM;;;;;N;;;;; 05AD;HEBREW ACCENT DEHI;Mn;222;NSM;;;;;N;;;;; 05AE;HEBREW ACCENT ZINOR;Mn;228;NSM;;;;;N;;;;; 05AF;HEBREW MARK MASORA CIRCLE;Mn;230;NSM;;;;;N;;;;; 05B0;HEBREW POINT SHEVA;Mn;10;NSM;;;;;N;;;;; 05B1;HEBREW POINT HATAF SEGOL;Mn;11;NSM;;;;;N;;;;; 05B2;HEBREW POINT HATAF PATAH;Mn;12;NSM;;;;;N;;;;; 05B3;HEBREW POINT HATAF QAMATS;Mn;13;NSM;;;;;N;;;;; 05B4;HEBREW POINT HIRIQ;Mn;14;NSM;;;;;N;;;;; 05B5;HEBREW POINT TSERE;Mn;15;NSM;;;;;N;;;;; 05B6;HEBREW POINT SEGOL;Mn;16;NSM;;;;;N;;;;; 05B7;HEBREW POINT PATAH;Mn;17;NSM;;;;;N;;;;; 05B8;HEBREW POINT QAMATS;Mn;18;NSM;;;;;N;;;;; 05B9;HEBREW POINT HOLAM;Mn;19;NSM;;;;;N;;;;; 05BA;HEBREW POINT HOLAM HASER FOR VAV;Mn;19;NSM;;;;;N;;;;; 05BB;HEBREW POINT QUBUTS;Mn;20;NSM;;;;;N;;;;; 05BC;HEBREW POINT DAGESH OR MAPIQ;Mn;21;NSM;;;;;N;HEBREW POINT DAGESH;;;; 05BD;HEBREW POINT METEG;Mn;22;NSM;;;;;N;;;;; 05BE;HEBREW PUNCTUATION MAQAF;Pd;0;R;;;;;N;;;;; 05BF;HEBREW POINT RAFE;Mn;23;NSM;;;;;N;;;;; 05C0;HEBREW PUNCTUATION PASEQ;Po;0;R;;;;;N;HEBREW POINT PASEQ;;;; 05C1;HEBREW POINT SHIN DOT;Mn;24;NSM;;;;;N;;;;; 05C2;HEBREW POINT SIN DOT;Mn;25;NSM;;;;;N;;;;; 05C3;HEBREW PUNCTUATION SOF PASUQ;Po;0;R;;;;;N;;;;; 05C4;HEBREW MARK UPPER DOT;Mn;230;NSM;;;;;N;;;;; 05C5;HEBREW MARK LOWER DOT;Mn;220;NSM;;;;;N;;;;; 05C6;HEBREW PUNCTUATION NUN HAFUKHA;Po;0;R;;;;;N;;;;; 05C7;HEBREW POINT QAMATS QATAN;Mn;18;NSM;;;;;N;;;;; 05D0;HEBREW LETTER ALEF;Lo;0;R;;;;;N;;;;; 05D1;HEBREW LETTER BET;Lo;0;R;;;;;N;;;;; 05D2;HEBREW LETTER GIMEL;Lo;0;R;;;;;N;;;;; 05D3;HEBREW LETTER DALET;Lo;0;R;;;;;N;;;;; 05D4;HEBREW LETTER HE;Lo;0;R;;;;;N;;;;; 05D5;HEBREW LETTER VAV;Lo;0;R;;;;;N;;;;; 05D6;HEBREW LETTER ZAYIN;Lo;0;R;;;;;N;;;;; 05D7;HEBREW LETTER HET;Lo;0;R;;;;;N;;;;; 05D8;HEBREW LETTER TET;Lo;0;R;;;;;N;;;;; 05D9;HEBREW LETTER YOD;Lo;0;R;;;;;N;;;;; 05DA;HEBREW LETTER FINAL KAF;Lo;0;R;;;;;N;;;;; 05DB;HEBREW LETTER KAF;Lo;0;R;;;;;N;;;;; 05DC;HEBREW LETTER LAMED;Lo;0;R;;;;;N;;;;; 05DD;HEBREW LETTER FINAL MEM;Lo;0;R;;;;;N;;;;; 05DE;HEBREW LETTER MEM;Lo;0;R;;;;;N;;;;; 05DF;HEBREW LETTER FINAL NUN;Lo;0;R;;;;;N;;;;; 05E0;HEBREW LETTER NUN;Lo;0;R;;;;;N;;;;; 05E1;HEBREW LETTER SAMEKH;Lo;0;R;;;;;N;;;;; 05E2;HEBREW LETTER AYIN;Lo;0;R;;;;;N;;;;; 05E3;HEBREW LETTER FINAL PE;Lo;0;R;;;;;N;;;;; 05E4;HEBREW LETTER PE;Lo;0;R;;;;;N;;;;; 05E5;HEBREW LETTER FINAL TSADI;Lo;0;R;;;;;N;;;;; 05E6;HEBREW LETTER TSADI;Lo;0;R;;;;;N;;;;; 05E7;HEBREW LETTER QOF;Lo;0;R;;;;;N;;;;; 05E8;HEBREW LETTER RESH;Lo;0;R;;;;;N;;;;; 05E9;HEBREW LETTER SHIN;Lo;0;R;;;;;N;;;;; 05EA;HEBREW LETTER TAV;Lo;0;R;;;;;N;;;;; 05F0;HEBREW LIGATURE YIDDISH DOUBLE VAV;Lo;0;R;;;;;N;HEBREW LETTER DOUBLE VAV;;;; 05F1;HEBREW LIGATURE YIDDISH VAV YOD;Lo;0;R;;;;;N;HEBREW LETTER VAV YOD;;;; 05F2;HEBREW LIGATURE YIDDISH DOUBLE YOD;Lo;0;R;;;;;N;HEBREW LETTER DOUBLE YOD;;;; 05F3;HEBREW PUNCTUATION GERESH;Po;0;R;;;;;N;;;;; 05F4;HEBREW PUNCTUATION GERSHAYIM;Po;0;R;;;;;N;;;;; 0600;ARABIC NUMBER SIGN;Cf;0;AN;;;;;N;;;;; 0601;ARABIC SIGN SANAH;Cf;0;AN;;;;;N;;;;; 0602;ARABIC FOOTNOTE MARKER;Cf;0;AN;;;;;N;;;;; 0603;ARABIC SIGN SAFHA;Cf;0;AN;;;;;N;;;;; 0604;ARABIC SIGN SAMVAT;Cf;0;AN;;;;;N;;;;; 0605;ARABIC NUMBER MARK ABOVE;Cf;0;AN;;;;;N;;;;; 0606;ARABIC-INDIC CUBE ROOT;Sm;0;ON;;;;;N;;;;; 0607;ARABIC-INDIC FOURTH ROOT;Sm;0;ON;;;;;N;;;;; 0608;ARABIC RAY;Sm;0;AL;;;;;N;;;;; 0609;ARABIC-INDIC PER MILLE SIGN;Po;0;ET;;;;;N;;;;; 060A;ARABIC-INDIC PER TEN THOUSAND SIGN;Po;0;ET;;;;;N;;;;; 060B;AFGHANI SIGN;Sc;0;AL;;;;;N;;;;; 060C;ARABIC COMMA;Po;0;CS;;;;;N;;;;; 060D;ARABIC DATE SEPARATOR;Po;0;AL;;;;;N;;;;; 060E;ARABIC POETIC VERSE SIGN;So;0;ON;;;;;N;;;;; 060F;ARABIC SIGN MISRA;So;0;ON;;;;;N;;;;; 0610;ARABIC SIGN SALLALLAHOU ALAYHE WASSALLAM;Mn;230;NSM;;;;;N;;;;; 0611;ARABIC SIGN ALAYHE ASSALLAM;Mn;230;NSM;;;;;N;;;;; 0612;ARABIC SIGN RAHMATULLAH ALAYHE;Mn;230;NSM;;;;;N;;;;; 0613;ARABIC SIGN RADI ALLAHOU ANHU;Mn;230;NSM;;;;;N;;;;; 0614;ARABIC SIGN TAKHALLUS;Mn;230;NSM;;;;;N;;;;; 0615;ARABIC SMALL HIGH TAH;Mn;230;NSM;;;;;N;;;;; 0616;ARABIC SMALL HIGH LIGATURE ALEF WITH LAM WITH YEH;Mn;230;NSM;;;;;N;;;;; 0617;ARABIC SMALL HIGH ZAIN;Mn;230;NSM;;;;;N;;;;; 0618;ARABIC SMALL FATHA;Mn;30;NSM;;;;;N;;;;; 0619;ARABIC SMALL DAMMA;Mn;31;NSM;;;;;N;;;;; 061A;ARABIC SMALL KASRA;Mn;32;NSM;;;;;N;;;;; 061B;ARABIC SEMICOLON;Po;0;AL;;;;;N;;;;; 061C;ARABIC LETTER MARK;Cf;0;AL;;;;;N;;;;; 061E;ARABIC TRIPLE DOT PUNCTUATION MARK;Po;0;AL;;;;;N;;;;; 061F;ARABIC QUESTION MARK;Po;0;AL;;;;;N;;;;; 0620;ARABIC LETTER KASHMIRI YEH;Lo;0;AL;;;;;N;;;;; 0621;ARABIC LETTER HAMZA;Lo;0;AL;;;;;N;ARABIC LETTER HAMZAH;;;; 0622;ARABIC LETTER ALEF WITH MADDA ABOVE;Lo;0;AL;0627 0653;;;;N;ARABIC LETTER MADDAH ON ALEF;;;; 0623;ARABIC LETTER ALEF WITH HAMZA ABOVE;Lo;0;AL;0627 0654;;;;N;ARABIC LETTER HAMZAH ON ALEF;;;; 0624;ARABIC LETTER WAW WITH HAMZA ABOVE;Lo;0;AL;0648 0654;;;;N;ARABIC LETTER HAMZAH ON WAW;;;; 0625;ARABIC LETTER ALEF WITH HAMZA BELOW;Lo;0;AL;0627 0655;;;;N;ARABIC LETTER HAMZAH UNDER ALEF;;;; 0626;ARABIC LETTER YEH WITH HAMZA ABOVE;Lo;0;AL;064A 0654;;;;N;ARABIC LETTER HAMZAH ON YA;;;; 0627;ARABIC LETTER ALEF;Lo;0;AL;;;;;N;;;;; 0628;ARABIC LETTER BEH;Lo;0;AL;;;;;N;ARABIC LETTER BAA;;;; 0629;ARABIC LETTER TEH MARBUTA;Lo;0;AL;;;;;N;ARABIC LETTER TAA MARBUTAH;;;; 062A;ARABIC LETTER TEH;Lo;0;AL;;;;;N;ARABIC LETTER TAA;;;; 062B;ARABIC LETTER THEH;Lo;0;AL;;;;;N;ARABIC LETTER THAA;;;; 062C;ARABIC LETTER JEEM;Lo;0;AL;;;;;N;;;;; 062D;ARABIC LETTER HAH;Lo;0;AL;;;;;N;ARABIC LETTER HAA;;;; 062E;ARABIC LETTER KHAH;Lo;0;AL;;;;;N;ARABIC LETTER KHAA;;;; 062F;ARABIC LETTER DAL;Lo;0;AL;;;;;N;;;;; 0630;ARABIC LETTER THAL;Lo;0;AL;;;;;N;;;;; 0631;ARABIC LETTER REH;Lo;0;AL;;;;;N;ARABIC LETTER RA;;;; 0632;ARABIC LETTER ZAIN;Lo;0;AL;;;;;N;;;;; 0633;ARABIC LETTER SEEN;Lo;0;AL;;;;;N;;;;; 0634;ARABIC LETTER SHEEN;Lo;0;AL;;;;;N;;;;; 0635;ARABIC LETTER SAD;Lo;0;AL;;;;;N;;;;; 0636;ARABIC LETTER DAD;Lo;0;AL;;;;;N;;;;; 0637;ARABIC LETTER TAH;Lo;0;AL;;;;;N;;;;; 0638;ARABIC LETTER ZAH;Lo;0;AL;;;;;N;ARABIC LETTER DHAH;;;; 0639;ARABIC LETTER AIN;Lo;0;AL;;;;;N;;;;; 063A;ARABIC LETTER GHAIN;Lo;0;AL;;;;;N;;;;; 063B;ARABIC LETTER KEHEH WITH TWO DOTS ABOVE;Lo;0;AL;;;;;N;;;;; 063C;ARABIC LETTER KEHEH WITH THREE DOTS BELOW;Lo;0;AL;;;;;N;;;;; 063D;ARABIC LETTER FARSI YEH WITH INVERTED V;Lo;0;AL;;;;;N;;;;; 063E;ARABIC LETTER FARSI YEH WITH TWO DOTS ABOVE;Lo;0;AL;;;;;N;;;;; 063F;ARABIC LETTER FARSI YEH WITH THREE DOTS ABOVE;Lo;0;AL;;;;;N;;;;; 0640;ARABIC TATWEEL;Lm;0;AL;;;;;N;;;;; 0641;ARABIC LETTER FEH;Lo;0;AL;;;;;N;ARABIC LETTER FA;;;; 0642;ARABIC LETTER QAF;Lo;0;AL;;;;;N;;;;; 0643;ARABIC LETTER KAF;Lo;0;AL;;;;;N;ARABIC LETTER CAF;;;; 0644;ARABIC LETTER LAM;Lo;0;AL;;;;;N;;;;; 0645;ARABIC LETTER MEEM;Lo;0;AL;;;;;N;;;;; 0646;ARABIC LETTER NOON;Lo;0;AL;;;;;N;;;;; 0647;ARABIC LETTER HEH;Lo;0;AL;;;;;N;ARABIC LETTER HA;;;; 0648;ARABIC LETTER WAW;Lo;0;AL;;;;;N;;;;; 0649;ARABIC LETTER ALEF MAKSURA;Lo;0;AL;;;;;N;ARABIC LETTER ALEF MAQSURAH;;;; 064A;ARABIC LETTER YEH;Lo;0;AL;;;;;N;ARABIC LETTER YA;;;; 064B;ARABIC FATHATAN;Mn;27;NSM;;;;;N;;;;; 064C;ARABIC DAMMATAN;Mn;28;NSM;;;;;N;;;;; 064D;ARABIC KASRATAN;Mn;29;NSM;;;;;N;;;;; 064E;ARABIC FATHA;Mn;30;NSM;;;;;N;ARABIC FATHAH;;;; 064F;ARABIC DAMMA;Mn;31;NSM;;;;;N;ARABIC DAMMAH;;;; 0650;ARABIC KASRA;Mn;32;NSM;;;;;N;ARABIC KASRAH;;;; 0651;ARABIC SHADDA;Mn;33;NSM;;;;;N;ARABIC SHADDAH;;;; 0652;ARABIC SUKUN;Mn;34;NSM;;;;;N;;;;; 0653;ARABIC MADDAH ABOVE;Mn;230;NSM;;;;;N;;;;; 0654;ARABIC HAMZA ABOVE;Mn;230;NSM;;;;;N;;;;; 0655;ARABIC HAMZA BELOW;Mn;220;NSM;;;;;N;;;;; 0656;ARABIC SUBSCRIPT ALEF;Mn;220;NSM;;;;;N;;;;; 0657;ARABIC INVERTED DAMMA;Mn;230;NSM;;;;;N;;;;; 0658;ARABIC MARK NOON GHUNNA;Mn;230;NSM;;;;;N;;;;; 0659;ARABIC ZWARAKAY;Mn;230;NSM;;;;;N;;;;; 065A;ARABIC VOWEL SIGN SMALL V ABOVE;Mn;230;NSM;;;;;N;;;;; 065B;ARABIC VOWEL SIGN INVERTED SMALL V ABOVE;Mn;230;NSM;;;;;N;;;;; 065C;ARABIC VOWEL SIGN DOT BELOW;Mn;220;NSM;;;;;N;;;;; 065D;ARABIC REVERSED DAMMA;Mn;230;NSM;;;;;N;;;;; 065E;ARABIC FATHA WITH TWO DOTS;Mn;230;NSM;;;;;N;;;;; 065F;ARABIC WAVY HAMZA BELOW;Mn;220;NSM;;;;;N;;;;; 0660;ARABIC-INDIC DIGIT ZERO;Nd;0;AN;;0;0;0;N;;;;; 0661;ARABIC-INDIC DIGIT ONE;Nd;0;AN;;1;1;1;N;;;;; 0662;ARABIC-INDIC DIGIT TWO;Nd;0;AN;;2;2;2;N;;;;; 0663;ARABIC-INDIC DIGIT THREE;Nd;0;AN;;3;3;3;N;;;;; 0664;ARABIC-INDIC DIGIT FOUR;Nd;0;AN;;4;4;4;N;;;;; 0665;ARABIC-INDIC DIGIT FIVE;Nd;0;AN;;5;5;5;N;;;;; 0666;ARABIC-INDIC DIGIT SIX;Nd;0;AN;;6;6;6;N;;;;; 0667;ARABIC-INDIC DIGIT SEVEN;Nd;0;AN;;7;7;7;N;;;;; 0668;ARABIC-INDIC DIGIT EIGHT;Nd;0;AN;;8;8;8;N;;;;; 0669;ARABIC-INDIC DIGIT NINE;Nd;0;AN;;9;9;9;N;;;;; 066A;ARABIC PERCENT SIGN;Po;0;ET;;;;;N;;;;; 066B;ARABIC DECIMAL SEPARATOR;Po;0;AN;;;;;N;;;;; 066C;ARABIC THOUSANDS SEPARATOR;Po;0;AN;;;;;N;;;;; 066D;ARABIC FIVE POINTED STAR;Po;0;AL;;;;;N;;;;; 066E;ARABIC LETTER DOTLESS BEH;Lo;0;AL;;;;;N;;;;; 066F;ARABIC LETTER DOTLESS QAF;Lo;0;AL;;;;;N;;;;; 0670;ARABIC LETTER SUPERSCRIPT ALEF;Mn;35;NSM;;;;;N;ARABIC ALEF ABOVE;;;; 0671;ARABIC LETTER ALEF WASLA;Lo;0;AL;;;;;N;ARABIC LETTER HAMZAT WASL ON ALEF;;;; 0672;ARABIC LETTER ALEF WITH WAVY HAMZA ABOVE;Lo;0;AL;;;;;N;ARABIC LETTER WAVY HAMZAH ON ALEF;;;; 0673;ARABIC LETTER ALEF WITH WAVY HAMZA BELOW;Lo;0;AL;;;;;N;ARABIC LETTER WAVY HAMZAH UNDER ALEF;;;; 0674;ARABIC LETTER HIGH HAMZA;Lo;0;AL;;;;;N;ARABIC LETTER HIGH HAMZAH;;;; 0675;ARABIC LETTER HIGH HAMZA ALEF;Lo;0;AL; 0627 0674;;;;N;ARABIC LETTER HIGH HAMZAH ALEF;;;; 0676;ARABIC LETTER HIGH HAMZA WAW;Lo;0;AL; 0648 0674;;;;N;ARABIC LETTER HIGH HAMZAH WAW;;;; 0677;ARABIC LETTER U WITH HAMZA ABOVE;Lo;0;AL; 06C7 0674;;;;N;ARABIC LETTER HIGH HAMZAH WAW WITH DAMMAH;;;; 0678;ARABIC LETTER HIGH HAMZA YEH;Lo;0;AL; 064A 0674;;;;N;ARABIC LETTER HIGH HAMZAH YA;;;; 0679;ARABIC LETTER TTEH;Lo;0;AL;;;;;N;ARABIC LETTER TAA WITH SMALL TAH;;;; 067A;ARABIC LETTER TTEHEH;Lo;0;AL;;;;;N;ARABIC LETTER TAA WITH TWO DOTS VERTICAL ABOVE;;;; 067B;ARABIC LETTER BEEH;Lo;0;AL;;;;;N;ARABIC LETTER BAA WITH TWO DOTS VERTICAL BELOW;;;; 067C;ARABIC LETTER TEH WITH RING;Lo;0;AL;;;;;N;ARABIC LETTER TAA WITH RING;;;; 067D;ARABIC LETTER TEH WITH THREE DOTS ABOVE DOWNWARDS;Lo;0;AL;;;;;N;ARABIC LETTER TAA WITH THREE DOTS ABOVE DOWNWARD;;;; 067E;ARABIC LETTER PEH;Lo;0;AL;;;;;N;ARABIC LETTER TAA WITH THREE DOTS BELOW;;;; 067F;ARABIC LETTER TEHEH;Lo;0;AL;;;;;N;ARABIC LETTER TAA WITH FOUR DOTS ABOVE;;;; 0680;ARABIC LETTER BEHEH;Lo;0;AL;;;;;N;ARABIC LETTER BAA WITH FOUR DOTS BELOW;;;; 0681;ARABIC LETTER HAH WITH HAMZA ABOVE;Lo;0;AL;;;;;N;ARABIC LETTER HAMZAH ON HAA;;;; 0682;ARABIC LETTER HAH WITH TWO DOTS VERTICAL ABOVE;Lo;0;AL;;;;;N;ARABIC LETTER HAA WITH TWO DOTS VERTICAL ABOVE;;;; 0683;ARABIC LETTER NYEH;Lo;0;AL;;;;;N;ARABIC LETTER HAA WITH MIDDLE TWO DOTS;;;; 0684;ARABIC LETTER DYEH;Lo;0;AL;;;;;N;ARABIC LETTER HAA WITH MIDDLE TWO DOTS VERTICAL;;;; 0685;ARABIC LETTER HAH WITH THREE DOTS ABOVE;Lo;0;AL;;;;;N;ARABIC LETTER HAA WITH THREE DOTS ABOVE;;;; 0686;ARABIC LETTER TCHEH;Lo;0;AL;;;;;N;ARABIC LETTER HAA WITH MIDDLE THREE DOTS DOWNWARD;;;; 0687;ARABIC LETTER TCHEHEH;Lo;0;AL;;;;;N;ARABIC LETTER HAA WITH MIDDLE FOUR DOTS;;;; 0688;ARABIC LETTER DDAL;Lo;0;AL;;;;;N;ARABIC LETTER DAL WITH SMALL TAH;;;; 0689;ARABIC LETTER DAL WITH RING;Lo;0;AL;;;;;N;;;;; 068A;ARABIC LETTER DAL WITH DOT BELOW;Lo;0;AL;;;;;N;;;;; 068B;ARABIC LETTER DAL WITH DOT BELOW AND SMALL TAH;Lo;0;AL;;;;;N;;;;; 068C;ARABIC LETTER DAHAL;Lo;0;AL;;;;;N;ARABIC LETTER DAL WITH TWO DOTS ABOVE;;;; 068D;ARABIC LETTER DDAHAL;Lo;0;AL;;;;;N;ARABIC LETTER DAL WITH TWO DOTS BELOW;;;; 068E;ARABIC LETTER DUL;Lo;0;AL;;;;;N;ARABIC LETTER DAL WITH THREE DOTS ABOVE;;;; 068F;ARABIC LETTER DAL WITH THREE DOTS ABOVE DOWNWARDS;Lo;0;AL;;;;;N;ARABIC LETTER DAL WITH THREE DOTS ABOVE DOWNWARD;;;; 0690;ARABIC LETTER DAL WITH FOUR DOTS ABOVE;Lo;0;AL;;;;;N;;;;; 0691;ARABIC LETTER RREH;Lo;0;AL;;;;;N;ARABIC LETTER RA WITH SMALL TAH;;;; 0692;ARABIC LETTER REH WITH SMALL V;Lo;0;AL;;;;;N;ARABIC LETTER RA WITH SMALL V;;;; 0693;ARABIC LETTER REH WITH RING;Lo;0;AL;;;;;N;ARABIC LETTER RA WITH RING;;;; 0694;ARABIC LETTER REH WITH DOT BELOW;Lo;0;AL;;;;;N;ARABIC LETTER RA WITH DOT BELOW;;;; 0695;ARABIC LETTER REH WITH SMALL V BELOW;Lo;0;AL;;;;;N;ARABIC LETTER RA WITH SMALL V BELOW;;;; 0696;ARABIC LETTER REH WITH DOT BELOW AND DOT ABOVE;Lo;0;AL;;;;;N;ARABIC LETTER RA WITH DOT BELOW AND DOT ABOVE;;;; 0697;ARABIC LETTER REH WITH TWO DOTS ABOVE;Lo;0;AL;;;;;N;ARABIC LETTER RA WITH TWO DOTS ABOVE;;;; 0698;ARABIC LETTER JEH;Lo;0;AL;;;;;N;ARABIC LETTER RA WITH THREE DOTS ABOVE;;;; 0699;ARABIC LETTER REH WITH FOUR DOTS ABOVE;Lo;0;AL;;;;;N;ARABIC LETTER RA WITH FOUR DOTS ABOVE;;;; 069A;ARABIC LETTER SEEN WITH DOT BELOW AND DOT ABOVE;Lo;0;AL;;;;;N;;;;; 069B;ARABIC LETTER SEEN WITH THREE DOTS BELOW;Lo;0;AL;;;;;N;;;;; 069C;ARABIC LETTER SEEN WITH THREE DOTS BELOW AND THREE DOTS ABOVE;Lo;0;AL;;;;;N;;;;; 069D;ARABIC LETTER SAD WITH TWO DOTS BELOW;Lo;0;AL;;;;;N;;;;; 069E;ARABIC LETTER SAD WITH THREE DOTS ABOVE;Lo;0;AL;;;;;N;;;;; 069F;ARABIC LETTER TAH WITH THREE DOTS ABOVE;Lo;0;AL;;;;;N;;;;; 06A0;ARABIC LETTER AIN WITH THREE DOTS ABOVE;Lo;0;AL;;;;;N;;;;; 06A1;ARABIC LETTER DOTLESS FEH;Lo;0;AL;;;;;N;ARABIC LETTER DOTLESS FA;;;; 06A2;ARABIC LETTER FEH WITH DOT MOVED BELOW;Lo;0;AL;;;;;N;ARABIC LETTER FA WITH DOT MOVED BELOW;;;; 06A3;ARABIC LETTER FEH WITH DOT BELOW;Lo;0;AL;;;;;N;ARABIC LETTER FA WITH DOT BELOW;;;; 06A4;ARABIC LETTER VEH;Lo;0;AL;;;;;N;ARABIC LETTER FA WITH THREE DOTS ABOVE;;;; 06A5;ARABIC LETTER FEH WITH THREE DOTS BELOW;Lo;0;AL;;;;;N;ARABIC LETTER FA WITH THREE DOTS BELOW;;;; 06A6;ARABIC LETTER PEHEH;Lo;0;AL;;;;;N;ARABIC LETTER FA WITH FOUR DOTS ABOVE;;;; 06A7;ARABIC LETTER QAF WITH DOT ABOVE;Lo;0;AL;;;;;N;;;;; 06A8;ARABIC LETTER QAF WITH THREE DOTS ABOVE;Lo;0;AL;;;;;N;;;;; 06A9;ARABIC LETTER KEHEH;Lo;0;AL;;;;;N;ARABIC LETTER OPEN CAF;;;; 06AA;ARABIC LETTER SWASH KAF;Lo;0;AL;;;;;N;ARABIC LETTER SWASH CAF;;;; 06AB;ARABIC LETTER KAF WITH RING;Lo;0;AL;;;;;N;ARABIC LETTER CAF WITH RING;;;; 06AC;ARABIC LETTER KAF WITH DOT ABOVE;Lo;0;AL;;;;;N;ARABIC LETTER CAF WITH DOT ABOVE;;;; 06AD;ARABIC LETTER NG;Lo;0;AL;;;;;N;ARABIC LETTER CAF WITH THREE DOTS ABOVE;;;; 06AE;ARABIC LETTER KAF WITH THREE DOTS BELOW;Lo;0;AL;;;;;N;ARABIC LETTER CAF WITH THREE DOTS BELOW;;;; 06AF;ARABIC LETTER GAF;Lo;0;AL;;;;;N;;;;; 06B0;ARABIC LETTER GAF WITH RING;Lo;0;AL;;;;;N;;;;; 06B1;ARABIC LETTER NGOEH;Lo;0;AL;;;;;N;ARABIC LETTER GAF WITH TWO DOTS ABOVE;;;; 06B2;ARABIC LETTER GAF WITH TWO DOTS BELOW;Lo;0;AL;;;;;N;;;;; 06B3;ARABIC LETTER GUEH;Lo;0;AL;;;;;N;ARABIC LETTER GAF WITH TWO DOTS VERTICAL BELOW;;;; 06B4;ARABIC LETTER GAF WITH THREE DOTS ABOVE;Lo;0;AL;;;;;N;;;;; 06B5;ARABIC LETTER LAM WITH SMALL V;Lo;0;AL;;;;;N;;;;; 06B6;ARABIC LETTER LAM WITH DOT ABOVE;Lo;0;AL;;;;;N;;;;; 06B7;ARABIC LETTER LAM WITH THREE DOTS ABOVE;Lo;0;AL;;;;;N;;;;; 06B8;ARABIC LETTER LAM WITH THREE DOTS BELOW;Lo;0;AL;;;;;N;;;;; 06B9;ARABIC LETTER NOON WITH DOT BELOW;Lo;0;AL;;;;;N;;;;; 06BA;ARABIC LETTER NOON GHUNNA;Lo;0;AL;;;;;N;ARABIC LETTER DOTLESS NOON;;;; 06BB;ARABIC LETTER RNOON;Lo;0;AL;;;;;N;ARABIC LETTER DOTLESS NOON WITH SMALL TAH;;;; 06BC;ARABIC LETTER NOON WITH RING;Lo;0;AL;;;;;N;;;;; 06BD;ARABIC LETTER NOON WITH THREE DOTS ABOVE;Lo;0;AL;;;;;N;;;;; 06BE;ARABIC LETTER HEH DOACHASHMEE;Lo;0;AL;;;;;N;ARABIC LETTER KNOTTED HA;;;; 06BF;ARABIC LETTER TCHEH WITH DOT ABOVE;Lo;0;AL;;;;;N;;;;; 06C0;ARABIC LETTER HEH WITH YEH ABOVE;Lo;0;AL;06D5 0654;;;;N;ARABIC LETTER HAMZAH ON HA;;;; 06C1;ARABIC LETTER HEH GOAL;Lo;0;AL;;;;;N;ARABIC LETTER HA GOAL;;;; 06C2;ARABIC LETTER HEH GOAL WITH HAMZA ABOVE;Lo;0;AL;06C1 0654;;;;N;ARABIC LETTER HAMZAH ON HA GOAL;;;; 06C3;ARABIC LETTER TEH MARBUTA GOAL;Lo;0;AL;;;;;N;ARABIC LETTER TAA MARBUTAH GOAL;;;; 06C4;ARABIC LETTER WAW WITH RING;Lo;0;AL;;;;;N;;;;; 06C5;ARABIC LETTER KIRGHIZ OE;Lo;0;AL;;;;;N;ARABIC LETTER WAW WITH BAR;;;; 06C6;ARABIC LETTER OE;Lo;0;AL;;;;;N;ARABIC LETTER WAW WITH SMALL V;;;; 06C7;ARABIC LETTER U;Lo;0;AL;;;;;N;ARABIC LETTER WAW WITH DAMMAH;;;; 06C8;ARABIC LETTER YU;Lo;0;AL;;;;;N;ARABIC LETTER WAW WITH ALEF ABOVE;;;; 06C9;ARABIC LETTER KIRGHIZ YU;Lo;0;AL;;;;;N;ARABIC LETTER WAW WITH INVERTED SMALL V;;;; 06CA;ARABIC LETTER WAW WITH TWO DOTS ABOVE;Lo;0;AL;;;;;N;;;;; 06CB;ARABIC LETTER VE;Lo;0;AL;;;;;N;ARABIC LETTER WAW WITH THREE DOTS ABOVE;;;; 06CC;ARABIC LETTER FARSI YEH;Lo;0;AL;;;;;N;ARABIC LETTER DOTLESS YA;;;; 06CD;ARABIC LETTER YEH WITH TAIL;Lo;0;AL;;;;;N;ARABIC LETTER YA WITH TAIL;;;; 06CE;ARABIC LETTER YEH WITH SMALL V;Lo;0;AL;;;;;N;ARABIC LETTER YA WITH SMALL V;;;; 06CF;ARABIC LETTER WAW WITH DOT ABOVE;Lo;0;AL;;;;;N;;;;; 06D0;ARABIC LETTER E;Lo;0;AL;;;;;N;ARABIC LETTER YA WITH TWO DOTS VERTICAL BELOW;;;; 06D1;ARABIC LETTER YEH WITH THREE DOTS BELOW;Lo;0;AL;;;;;N;ARABIC LETTER YA WITH THREE DOTS BELOW;;;; 06D2;ARABIC LETTER YEH BARREE;Lo;0;AL;;;;;N;ARABIC LETTER YA BARREE;;;; 06D3;ARABIC LETTER YEH BARREE WITH HAMZA ABOVE;Lo;0;AL;06D2 0654;;;;N;ARABIC LETTER HAMZAH ON YA BARREE;;;; 06D4;ARABIC FULL STOP;Po;0;AL;;;;;N;ARABIC PERIOD;;;; 06D5;ARABIC LETTER AE;Lo;0;AL;;;;;N;;;;; 06D6;ARABIC SMALL HIGH LIGATURE SAD WITH LAM WITH ALEF MAKSURA;Mn;230;NSM;;;;;N;;;;; 06D7;ARABIC SMALL HIGH LIGATURE QAF WITH LAM WITH ALEF MAKSURA;Mn;230;NSM;;;;;N;;;;; 06D8;ARABIC SMALL HIGH MEEM INITIAL FORM;Mn;230;NSM;;;;;N;;;;; 06D9;ARABIC SMALL HIGH LAM ALEF;Mn;230;NSM;;;;;N;;;;; 06DA;ARABIC SMALL HIGH JEEM;Mn;230;NSM;;;;;N;;;;; 06DB;ARABIC SMALL HIGH THREE DOTS;Mn;230;NSM;;;;;N;;;;; 06DC;ARABIC SMALL HIGH SEEN;Mn;230;NSM;;;;;N;;;;; 06DD;ARABIC END OF AYAH;Cf;0;AN;;;;;N;;;;; 06DE;ARABIC START OF RUB EL HIZB;So;0;ON;;;;;N;;;;; 06DF;ARABIC SMALL HIGH ROUNDED ZERO;Mn;230;NSM;;;;;N;;;;; 06E0;ARABIC SMALL HIGH UPRIGHT RECTANGULAR ZERO;Mn;230;NSM;;;;;N;;;;; 06E1;ARABIC SMALL HIGH DOTLESS HEAD OF KHAH;Mn;230;NSM;;;;;N;;;;; 06E2;ARABIC SMALL HIGH MEEM ISOLATED FORM;Mn;230;NSM;;;;;N;;;;; 06E3;ARABIC SMALL LOW SEEN;Mn;220;NSM;;;;;N;;;;; 06E4;ARABIC SMALL HIGH MADDA;Mn;230;NSM;;;;;N;;;;; 06E5;ARABIC SMALL WAW;Lm;0;AL;;;;;N;;;;; 06E6;ARABIC SMALL YEH;Lm;0;AL;;;;;N;;;;; 06E7;ARABIC SMALL HIGH YEH;Mn;230;NSM;;;;;N;;;;; 06E8;ARABIC SMALL HIGH NOON;Mn;230;NSM;;;;;N;;;;; 06E9;ARABIC PLACE OF SAJDAH;So;0;ON;;;;;N;;;;; 06EA;ARABIC EMPTY CENTRE LOW STOP;Mn;220;NSM;;;;;N;;;;; 06EB;ARABIC EMPTY CENTRE HIGH STOP;Mn;230;NSM;;;;;N;;;;; 06EC;ARABIC ROUNDED HIGH STOP WITH FILLED CENTRE;Mn;230;NSM;;;;;N;;;;; 06ED;ARABIC SMALL LOW MEEM;Mn;220;NSM;;;;;N;;;;; 06EE;ARABIC LETTER DAL WITH INVERTED V;Lo;0;AL;;;;;N;;;;; 06EF;ARABIC LETTER REH WITH INVERTED V;Lo;0;AL;;;;;N;;;;; 06F0;EXTENDED ARABIC-INDIC DIGIT ZERO;Nd;0;EN;;0;0;0;N;EASTERN ARABIC-INDIC DIGIT ZERO;;;; 06F1;EXTENDED ARABIC-INDIC DIGIT ONE;Nd;0;EN;;1;1;1;N;EASTERN ARABIC-INDIC DIGIT ONE;;;; 06F2;EXTENDED ARABIC-INDIC DIGIT TWO;Nd;0;EN;;2;2;2;N;EASTERN ARABIC-INDIC DIGIT TWO;;;; 06F3;EXTENDED ARABIC-INDIC DIGIT THREE;Nd;0;EN;;3;3;3;N;EASTERN ARABIC-INDIC DIGIT THREE;;;; 06F4;EXTENDED ARABIC-INDIC DIGIT FOUR;Nd;0;EN;;4;4;4;N;EASTERN ARABIC-INDIC DIGIT FOUR;;;; 06F5;EXTENDED ARABIC-INDIC DIGIT FIVE;Nd;0;EN;;5;5;5;N;EASTERN ARABIC-INDIC DIGIT FIVE;;;; 06F6;EXTENDED ARABIC-INDIC DIGIT SIX;Nd;0;EN;;6;6;6;N;EASTERN ARABIC-INDIC DIGIT SIX;;;; 06F7;EXTENDED ARABIC-INDIC DIGIT SEVEN;Nd;0;EN;;7;7;7;N;EASTERN ARABIC-INDIC DIGIT SEVEN;;;; 06F8;EXTENDED ARABIC-INDIC DIGIT EIGHT;Nd;0;EN;;8;8;8;N;EASTERN ARABIC-INDIC DIGIT EIGHT;;;; 06F9;EXTENDED ARABIC-INDIC DIGIT NINE;Nd;0;EN;;9;9;9;N;EASTERN ARABIC-INDIC DIGIT NINE;;;; 06FA;ARABIC LETTER SHEEN WITH DOT BELOW;Lo;0;AL;;;;;N;;;;; 06FB;ARABIC LETTER DAD WITH DOT BELOW;Lo;0;AL;;;;;N;;;;; 06FC;ARABIC LETTER GHAIN WITH DOT BELOW;Lo;0;AL;;;;;N;;;;; 06FD;ARABIC SIGN SINDHI AMPERSAND;So;0;AL;;;;;N;;;;; 06FE;ARABIC SIGN SINDHI POSTPOSITION MEN;So;0;AL;;;;;N;;;;; 06FF;ARABIC LETTER HEH WITH INVERTED V;Lo;0;AL;;;;;N;;;;; 0700;SYRIAC END OF PARAGRAPH;Po;0;AL;;;;;N;;;;; 0701;SYRIAC SUPRALINEAR FULL STOP;Po;0;AL;;;;;N;;;;; 0702;SYRIAC SUBLINEAR FULL STOP;Po;0;AL;;;;;N;;;;; 0703;SYRIAC SUPRALINEAR COLON;Po;0;AL;;;;;N;;;;; 0704;SYRIAC SUBLINEAR COLON;Po;0;AL;;;;;N;;;;; 0705;SYRIAC HORIZONTAL COLON;Po;0;AL;;;;;N;;;;; 0706;SYRIAC COLON SKEWED LEFT;Po;0;AL;;;;;N;;;;; 0707;SYRIAC COLON SKEWED RIGHT;Po;0;AL;;;;;N;;;;; 0708;SYRIAC SUPRALINEAR COLON SKEWED LEFT;Po;0;AL;;;;;N;;;;; 0709;SYRIAC SUBLINEAR COLON SKEWED RIGHT;Po;0;AL;;;;;N;;;;; 070A;SYRIAC CONTRACTION;Po;0;AL;;;;;N;;;;; 070B;SYRIAC HARKLEAN OBELUS;Po;0;AL;;;;;N;;;;; 070C;SYRIAC HARKLEAN METOBELUS;Po;0;AL;;;;;N;;;;; 070D;SYRIAC HARKLEAN ASTERISCUS;Po;0;AL;;;;;N;;;;; 070F;SYRIAC ABBREVIATION MARK;Cf;0;AL;;;;;N;;;;; 0710;SYRIAC LETTER ALAPH;Lo;0;AL;;;;;N;;;;; 0711;SYRIAC LETTER SUPERSCRIPT ALAPH;Mn;36;NSM;;;;;N;;;;; 0712;SYRIAC LETTER BETH;Lo;0;AL;;;;;N;;;;; 0713;SYRIAC LETTER GAMAL;Lo;0;AL;;;;;N;;;;; 0714;SYRIAC LETTER GAMAL GARSHUNI;Lo;0;AL;;;;;N;;;;; 0715;SYRIAC LETTER DALATH;Lo;0;AL;;;;;N;;;;; 0716;SYRIAC LETTER DOTLESS DALATH RISH;Lo;0;AL;;;;;N;;;;; 0717;SYRIAC LETTER HE;Lo;0;AL;;;;;N;;;;; 0718;SYRIAC LETTER WAW;Lo;0;AL;;;;;N;;;;; 0719;SYRIAC LETTER ZAIN;Lo;0;AL;;;;;N;;;;; 071A;SYRIAC LETTER HETH;Lo;0;AL;;;;;N;;;;; 071B;SYRIAC LETTER TETH;Lo;0;AL;;;;;N;;;;; 071C;SYRIAC LETTER TETH GARSHUNI;Lo;0;AL;;;;;N;;;;; 071D;SYRIAC LETTER YUDH;Lo;0;AL;;;;;N;;;;; 071E;SYRIAC LETTER YUDH HE;Lo;0;AL;;;;;N;;;;; 071F;SYRIAC LETTER KAPH;Lo;0;AL;;;;;N;;;;; 0720;SYRIAC LETTER LAMADH;Lo;0;AL;;;;;N;;;;; 0721;SYRIAC LETTER MIM;Lo;0;AL;;;;;N;;;;; 0722;SYRIAC LETTER NUN;Lo;0;AL;;;;;N;;;;; 0723;SYRIAC LETTER SEMKATH;Lo;0;AL;;;;;N;;;;; 0724;SYRIAC LETTER FINAL SEMKATH;Lo;0;AL;;;;;N;;;;; 0725;SYRIAC LETTER E;Lo;0;AL;;;;;N;;;;; 0726;SYRIAC LETTER PE;Lo;0;AL;;;;;N;;;;; 0727;SYRIAC LETTER REVERSED PE;Lo;0;AL;;;;;N;;;;; 0728;SYRIAC LETTER SADHE;Lo;0;AL;;;;;N;;;;; 0729;SYRIAC LETTER QAPH;Lo;0;AL;;;;;N;;;;; 072A;SYRIAC LETTER RISH;Lo;0;AL;;;;;N;;;;; 072B;SYRIAC LETTER SHIN;Lo;0;AL;;;;;N;;;;; 072C;SYRIAC LETTER TAW;Lo;0;AL;;;;;N;;;;; 072D;SYRIAC LETTER PERSIAN BHETH;Lo;0;AL;;;;;N;;;;; 072E;SYRIAC LETTER PERSIAN GHAMAL;Lo;0;AL;;;;;N;;;;; 072F;SYRIAC LETTER PERSIAN DHALATH;Lo;0;AL;;;;;N;;;;; 0730;SYRIAC PTHAHA ABOVE;Mn;230;NSM;;;;;N;;;;; 0731;SYRIAC PTHAHA BELOW;Mn;220;NSM;;;;;N;;;;; 0732;SYRIAC PTHAHA DOTTED;Mn;230;NSM;;;;;N;;;;; 0733;SYRIAC ZQAPHA ABOVE;Mn;230;NSM;;;;;N;;;;; 0734;SYRIAC ZQAPHA BELOW;Mn;220;NSM;;;;;N;;;;; 0735;SYRIAC ZQAPHA DOTTED;Mn;230;NSM;;;;;N;;;;; 0736;SYRIAC RBASA ABOVE;Mn;230;NSM;;;;;N;;;;; 0737;SYRIAC RBASA BELOW;Mn;220;NSM;;;;;N;;;;; 0738;SYRIAC DOTTED ZLAMA HORIZONTAL;Mn;220;NSM;;;;;N;;;;; 0739;SYRIAC DOTTED ZLAMA ANGULAR;Mn;220;NSM;;;;;N;;;;; 073A;SYRIAC HBASA ABOVE;Mn;230;NSM;;;;;N;;;;; 073B;SYRIAC HBASA BELOW;Mn;220;NSM;;;;;N;;;;; 073C;SYRIAC HBASA-ESASA DOTTED;Mn;220;NSM;;;;;N;;;;; 073D;SYRIAC ESASA ABOVE;Mn;230;NSM;;;;;N;;;;; 073E;SYRIAC ESASA BELOW;Mn;220;NSM;;;;;N;;;;; 073F;SYRIAC RWAHA;Mn;230;NSM;;;;;N;;;;; 0740;SYRIAC FEMININE DOT;Mn;230;NSM;;;;;N;;;;; 0741;SYRIAC QUSHSHAYA;Mn;230;NSM;;;;;N;;;;; 0742;SYRIAC RUKKAKHA;Mn;220;NSM;;;;;N;;;;; 0743;SYRIAC TWO VERTICAL DOTS ABOVE;Mn;230;NSM;;;;;N;;;;; 0744;SYRIAC TWO VERTICAL DOTS BELOW;Mn;220;NSM;;;;;N;;;;; 0745;SYRIAC THREE DOTS ABOVE;Mn;230;NSM;;;;;N;;;;; 0746;SYRIAC THREE DOTS BELOW;Mn;220;NSM;;;;;N;;;;; 0747;SYRIAC OBLIQUE LINE ABOVE;Mn;230;NSM;;;;;N;;;;; 0748;SYRIAC OBLIQUE LINE BELOW;Mn;220;NSM;;;;;N;;;;; 0749;SYRIAC MUSIC;Mn;230;NSM;;;;;N;;;;; 074A;SYRIAC BARREKH;Mn;230;NSM;;;;;N;;;;; 074D;SYRIAC LETTER SOGDIAN ZHAIN;Lo;0;AL;;;;;N;;;;; 074E;SYRIAC LETTER SOGDIAN KHAPH;Lo;0;AL;;;;;N;;;;; 074F;SYRIAC LETTER SOGDIAN FE;Lo;0;AL;;;;;N;;;;; 0750;ARABIC LETTER BEH WITH THREE DOTS HORIZONTALLY BELOW;Lo;0;AL;;;;;N;;;;; 0751;ARABIC LETTER BEH WITH DOT BELOW AND THREE DOTS ABOVE;Lo;0;AL;;;;;N;;;;; 0752;ARABIC LETTER BEH WITH THREE DOTS POINTING UPWARDS BELOW;Lo;0;AL;;;;;N;;;;; 0753;ARABIC LETTER BEH WITH THREE DOTS POINTING UPWARDS BELOW AND TWO DOTS ABOVE;Lo;0;AL;;;;;N;;;;; 0754;ARABIC LETTER BEH WITH TWO DOTS BELOW AND DOT ABOVE;Lo;0;AL;;;;;N;;;;; 0755;ARABIC LETTER BEH WITH INVERTED SMALL V BELOW;Lo;0;AL;;;;;N;;;;; 0756;ARABIC LETTER BEH WITH SMALL V;Lo;0;AL;;;;;N;;;;; 0757;ARABIC LETTER HAH WITH TWO DOTS ABOVE;Lo;0;AL;;;;;N;;;;; 0758;ARABIC LETTER HAH WITH THREE DOTS POINTING UPWARDS BELOW;Lo;0;AL;;;;;N;;;;; 0759;ARABIC LETTER DAL WITH TWO DOTS VERTICALLY BELOW AND SMALL TAH;Lo;0;AL;;;;;N;;;;; 075A;ARABIC LETTER DAL WITH INVERTED SMALL V BELOW;Lo;0;AL;;;;;N;;;;; 075B;ARABIC LETTER REH WITH STROKE;Lo;0;AL;;;;;N;;;;; 075C;ARABIC LETTER SEEN WITH FOUR DOTS ABOVE;Lo;0;AL;;;;;N;;;;; 075D;ARABIC LETTER AIN WITH TWO DOTS ABOVE;Lo;0;AL;;;;;N;;;;; 075E;ARABIC LETTER AIN WITH THREE DOTS POINTING DOWNWARDS ABOVE;Lo;0;AL;;;;;N;;;;; 075F;ARABIC LETTER AIN WITH TWO DOTS VERTICALLY ABOVE;Lo;0;AL;;;;;N;;;;; 0760;ARABIC LETTER FEH WITH TWO DOTS BELOW;Lo;0;AL;;;;;N;;;;; 0761;ARABIC LETTER FEH WITH THREE DOTS POINTING UPWARDS BELOW;Lo;0;AL;;;;;N;;;;; 0762;ARABIC LETTER KEHEH WITH DOT ABOVE;Lo;0;AL;;;;;N;;;;; 0763;ARABIC LETTER KEHEH WITH THREE DOTS ABOVE;Lo;0;AL;;;;;N;;;;; 0764;ARABIC LETTER KEHEH WITH THREE DOTS POINTING UPWARDS BELOW;Lo;0;AL;;;;;N;;;;; 0765;ARABIC LETTER MEEM WITH DOT ABOVE;Lo;0;AL;;;;;N;;;;; 0766;ARABIC LETTER MEEM WITH DOT BELOW;Lo;0;AL;;;;;N;;;;; 0767;ARABIC LETTER NOON WITH TWO DOTS BELOW;Lo;0;AL;;;;;N;;;;; 0768;ARABIC LETTER NOON WITH SMALL TAH;Lo;0;AL;;;;;N;;;;; 0769;ARABIC LETTER NOON WITH SMALL V;Lo;0;AL;;;;;N;;;;; 076A;ARABIC LETTER LAM WITH BAR;Lo;0;AL;;;;;N;;;;; 076B;ARABIC LETTER REH WITH TWO DOTS VERTICALLY ABOVE;Lo;0;AL;;;;;N;;;;; 076C;ARABIC LETTER REH WITH HAMZA ABOVE;Lo;0;AL;;;;;N;;;;; 076D;ARABIC LETTER SEEN WITH TWO DOTS VERTICALLY ABOVE;Lo;0;AL;;;;;N;;;;; 076E;ARABIC LETTER HAH WITH SMALL ARABIC LETTER TAH BELOW;Lo;0;AL;;;;;N;;;;; 076F;ARABIC LETTER HAH WITH SMALL ARABIC LETTER TAH AND TWO DOTS;Lo;0;AL;;;;;N;;;;; 0770;ARABIC LETTER SEEN WITH SMALL ARABIC LETTER TAH AND TWO DOTS;Lo;0;AL;;;;;N;;;;; 0771;ARABIC LETTER REH WITH SMALL ARABIC LETTER TAH AND TWO DOTS;Lo;0;AL;;;;;N;;;;; 0772;ARABIC LETTER HAH WITH SMALL ARABIC LETTER TAH ABOVE;Lo;0;AL;;;;;N;;;;; 0773;ARABIC LETTER ALEF WITH EXTENDED ARABIC-INDIC DIGIT TWO ABOVE;Lo;0;AL;;;;;N;;;;; 0774;ARABIC LETTER ALEF WITH EXTENDED ARABIC-INDIC DIGIT THREE ABOVE;Lo;0;AL;;;;;N;;;;; 0775;ARABIC LETTER FARSI YEH WITH EXTENDED ARABIC-INDIC DIGIT TWO ABOVE;Lo;0;AL;;;;;N;;;;; 0776;ARABIC LETTER FARSI YEH WITH EXTENDED ARABIC-INDIC DIGIT THREE ABOVE;Lo;0;AL;;;;;N;;;;; 0777;ARABIC LETTER FARSI YEH WITH EXTENDED ARABIC-INDIC DIGIT FOUR BELOW;Lo;0;AL;;;;;N;;;;; 0778;ARABIC LETTER WAW WITH EXTENDED ARABIC-INDIC DIGIT TWO ABOVE;Lo;0;AL;;;;;N;;;;; 0779;ARABIC LETTER WAW WITH EXTENDED ARABIC-INDIC DIGIT THREE ABOVE;Lo;0;AL;;;;;N;;;;; 077A;ARABIC LETTER YEH BARREE WITH EXTENDED ARABIC-INDIC DIGIT TWO ABOVE;Lo;0;AL;;;;;N;;;;; 077B;ARABIC LETTER YEH BARREE WITH EXTENDED ARABIC-INDIC DIGIT THREE ABOVE;Lo;0;AL;;;;;N;;;;; 077C;ARABIC LETTER HAH WITH EXTENDED ARABIC-INDIC DIGIT FOUR BELOW;Lo;0;AL;;;;;N;;;;; 077D;ARABIC LETTER SEEN WITH EXTENDED ARABIC-INDIC DIGIT FOUR ABOVE;Lo;0;AL;;;;;N;;;;; 077E;ARABIC LETTER SEEN WITH INVERTED V;Lo;0;AL;;;;;N;;;;; 077F;ARABIC LETTER KAF WITH TWO DOTS ABOVE;Lo;0;AL;;;;;N;;;;; 0780;THAANA LETTER HAA;Lo;0;AL;;;;;N;;;;; 0781;THAANA LETTER SHAVIYANI;Lo;0;AL;;;;;N;;;;; 0782;THAANA LETTER NOONU;Lo;0;AL;;;;;N;;;;; 0783;THAANA LETTER RAA;Lo;0;AL;;;;;N;;;;; 0784;THAANA LETTER BAA;Lo;0;AL;;;;;N;;;;; 0785;THAANA LETTER LHAVIYANI;Lo;0;AL;;;;;N;;;;; 0786;THAANA LETTER KAAFU;Lo;0;AL;;;;;N;;;;; 0787;THAANA LETTER ALIFU;Lo;0;AL;;;;;N;;;;; 0788;THAANA LETTER VAAVU;Lo;0;AL;;;;;N;;;;; 0789;THAANA LETTER MEEMU;Lo;0;AL;;;;;N;;;;; 078A;THAANA LETTER FAAFU;Lo;0;AL;;;;;N;;;;; 078B;THAANA LETTER DHAALU;Lo;0;AL;;;;;N;;;;; 078C;THAANA LETTER THAA;Lo;0;AL;;;;;N;;;;; 078D;THAANA LETTER LAAMU;Lo;0;AL;;;;;N;;;;; 078E;THAANA LETTER GAAFU;Lo;0;AL;;;;;N;;;;; 078F;THAANA LETTER GNAVIYANI;Lo;0;AL;;;;;N;;;;; 0790;THAANA LETTER SEENU;Lo;0;AL;;;;;N;;;;; 0791;THAANA LETTER DAVIYANI;Lo;0;AL;;;;;N;;;;; 0792;THAANA LETTER ZAVIYANI;Lo;0;AL;;;;;N;;;;; 0793;THAANA LETTER TAVIYANI;Lo;0;AL;;;;;N;;;;; 0794;THAANA LETTER YAA;Lo;0;AL;;;;;N;;;;; 0795;THAANA LETTER PAVIYANI;Lo;0;AL;;;;;N;;;;; 0796;THAANA LETTER JAVIYANI;Lo;0;AL;;;;;N;;;;; 0797;THAANA LETTER CHAVIYANI;Lo;0;AL;;;;;N;;;;; 0798;THAANA LETTER TTAA;Lo;0;AL;;;;;N;;;;; 0799;THAANA LETTER HHAA;Lo;0;AL;;;;;N;;;;; 079A;THAANA LETTER KHAA;Lo;0;AL;;;;;N;;;;; 079B;THAANA LETTER THAALU;Lo;0;AL;;;;;N;;;;; 079C;THAANA LETTER ZAA;Lo;0;AL;;;;;N;;;;; 079D;THAANA LETTER SHEENU;Lo;0;AL;;;;;N;;;;; 079E;THAANA LETTER SAADHU;Lo;0;AL;;;;;N;;;;; 079F;THAANA LETTER DAADHU;Lo;0;AL;;;;;N;;;;; 07A0;THAANA LETTER TO;Lo;0;AL;;;;;N;;;;; 07A1;THAANA LETTER ZO;Lo;0;AL;;;;;N;;;;; 07A2;THAANA LETTER AINU;Lo;0;AL;;;;;N;;;;; 07A3;THAANA LETTER GHAINU;Lo;0;AL;;;;;N;;;;; 07A4;THAANA LETTER QAAFU;Lo;0;AL;;;;;N;;;;; 07A5;THAANA LETTER WAAVU;Lo;0;AL;;;;;N;;;;; 07A6;THAANA ABAFILI;Mn;0;NSM;;;;;N;;;;; 07A7;THAANA AABAAFILI;Mn;0;NSM;;;;;N;;;;; 07A8;THAANA IBIFILI;Mn;0;NSM;;;;;N;;;;; 07A9;THAANA EEBEEFILI;Mn;0;NSM;;;;;N;;;;; 07AA;THAANA UBUFILI;Mn;0;NSM;;;;;N;;;;; 07AB;THAANA OOBOOFILI;Mn;0;NSM;;;;;N;;;;; 07AC;THAANA EBEFILI;Mn;0;NSM;;;;;N;;;;; 07AD;THAANA EYBEYFILI;Mn;0;NSM;;;;;N;;;;; 07AE;THAANA OBOFILI;Mn;0;NSM;;;;;N;;;;; 07AF;THAANA OABOAFILI;Mn;0;NSM;;;;;N;;;;; 07B0;THAANA SUKUN;Mn;0;NSM;;;;;N;;;;; 07B1;THAANA LETTER NAA;Lo;0;AL;;;;;N;;;;; 07C0;NKO DIGIT ZERO;Nd;0;R;;0;0;0;N;;;;; 07C1;NKO DIGIT ONE;Nd;0;R;;1;1;1;N;;;;; 07C2;NKO DIGIT TWO;Nd;0;R;;2;2;2;N;;;;; 07C3;NKO DIGIT THREE;Nd;0;R;;3;3;3;N;;;;; 07C4;NKO DIGIT FOUR;Nd;0;R;;4;4;4;N;;;;; 07C5;NKO DIGIT FIVE;Nd;0;R;;5;5;5;N;;;;; 07C6;NKO DIGIT SIX;Nd;0;R;;6;6;6;N;;;;; 07C7;NKO DIGIT SEVEN;Nd;0;R;;7;7;7;N;;;;; 07C8;NKO DIGIT EIGHT;Nd;0;R;;8;8;8;N;;;;; 07C9;NKO DIGIT NINE;Nd;0;R;;9;9;9;N;;;;; 07CA;NKO LETTER A;Lo;0;R;;;;;N;;;;; 07CB;NKO LETTER EE;Lo;0;R;;;;;N;;;;; 07CC;NKO LETTER I;Lo;0;R;;;;;N;;;;; 07CD;NKO LETTER E;Lo;0;R;;;;;N;;;;; 07CE;NKO LETTER U;Lo;0;R;;;;;N;;;;; 07CF;NKO LETTER OO;Lo;0;R;;;;;N;;;;; 07D0;NKO LETTER O;Lo;0;R;;;;;N;;;;; 07D1;NKO LETTER DAGBASINNA;Lo;0;R;;;;;N;;;;; 07D2;NKO LETTER N;Lo;0;R;;;;;N;;;;; 07D3;NKO LETTER BA;Lo;0;R;;;;;N;;;;; 07D4;NKO LETTER PA;Lo;0;R;;;;;N;;;;; 07D5;NKO LETTER TA;Lo;0;R;;;;;N;;;;; 07D6;NKO LETTER JA;Lo;0;R;;;;;N;;;;; 07D7;NKO LETTER CHA;Lo;0;R;;;;;N;;;;; 07D8;NKO LETTER DA;Lo;0;R;;;;;N;;;;; 07D9;NKO LETTER RA;Lo;0;R;;;;;N;;;;; 07DA;NKO LETTER RRA;Lo;0;R;;;;;N;;;;; 07DB;NKO LETTER SA;Lo;0;R;;;;;N;;;;; 07DC;NKO LETTER GBA;Lo;0;R;;;;;N;;;;; 07DD;NKO LETTER FA;Lo;0;R;;;;;N;;;;; 07DE;NKO LETTER KA;Lo;0;R;;;;;N;;;;; 07DF;NKO LETTER LA;Lo;0;R;;;;;N;;;;; 07E0;NKO LETTER NA WOLOSO;Lo;0;R;;;;;N;;;;; 07E1;NKO LETTER MA;Lo;0;R;;;;;N;;;;; 07E2;NKO LETTER NYA;Lo;0;R;;;;;N;;;;; 07E3;NKO LETTER NA;Lo;0;R;;;;;N;;;;; 07E4;NKO LETTER HA;Lo;0;R;;;;;N;;;;; 07E5;NKO LETTER WA;Lo;0;R;;;;;N;;;;; 07E6;NKO LETTER YA;Lo;0;R;;;;;N;;;;; 07E7;NKO LETTER NYA WOLOSO;Lo;0;R;;;;;N;;;;; 07E8;NKO LETTER JONA JA;Lo;0;R;;;;;N;;;;; 07E9;NKO LETTER JONA CHA;Lo;0;R;;;;;N;;;;; 07EA;NKO LETTER JONA RA;Lo;0;R;;;;;N;;;;; 07EB;NKO COMBINING SHORT HIGH TONE;Mn;230;NSM;;;;;N;;;;; 07EC;NKO COMBINING SHORT LOW TONE;Mn;230;NSM;;;;;N;;;;; 07ED;NKO COMBINING SHORT RISING TONE;Mn;230;NSM;;;;;N;;;;; 07EE;NKO COMBINING LONG DESCENDING TONE;Mn;230;NSM;;;;;N;;;;; 07EF;NKO COMBINING LONG HIGH TONE;Mn;230;NSM;;;;;N;;;;; 07F0;NKO COMBINING LONG LOW TONE;Mn;230;NSM;;;;;N;;;;; 07F1;NKO COMBINING LONG RISING TONE;Mn;230;NSM;;;;;N;;;;; 07F2;NKO COMBINING NASALIZATION MARK;Mn;220;NSM;;;;;N;;;;; 07F3;NKO COMBINING DOUBLE DOT ABOVE;Mn;230;NSM;;;;;N;;;;; 07F4;NKO HIGH TONE APOSTROPHE;Lm;0;R;;;;;N;;;;; 07F5;NKO LOW TONE APOSTROPHE;Lm;0;R;;;;;N;;;;; 07F6;NKO SYMBOL OO DENNEN;So;0;ON;;;;;N;;;;; 07F7;NKO SYMBOL GBAKURUNEN;Po;0;ON;;;;;N;;;;; 07F8;NKO COMMA;Po;0;ON;;;;;N;;;;; 07F9;NKO EXCLAMATION MARK;Po;0;ON;;;;;N;;;;; 07FA;NKO LAJANYALAN;Lm;0;R;;;;;N;;;;; 0800;SAMARITAN LETTER ALAF;Lo;0;R;;;;;N;;;;; 0801;SAMARITAN LETTER BIT;Lo;0;R;;;;;N;;;;; 0802;SAMARITAN LETTER GAMAN;Lo;0;R;;;;;N;;;;; 0803;SAMARITAN LETTER DALAT;Lo;0;R;;;;;N;;;;; 0804;SAMARITAN LETTER IY;Lo;0;R;;;;;N;;;;; 0805;SAMARITAN LETTER BAA;Lo;0;R;;;;;N;;;;; 0806;SAMARITAN LETTER ZEN;Lo;0;R;;;;;N;;;;; 0807;SAMARITAN LETTER IT;Lo;0;R;;;;;N;;;;; 0808;SAMARITAN LETTER TIT;Lo;0;R;;;;;N;;;;; 0809;SAMARITAN LETTER YUT;Lo;0;R;;;;;N;;;;; 080A;SAMARITAN LETTER KAAF;Lo;0;R;;;;;N;;;;; 080B;SAMARITAN LETTER LABAT;Lo;0;R;;;;;N;;;;; 080C;SAMARITAN LETTER MIM;Lo;0;R;;;;;N;;;;; 080D;SAMARITAN LETTER NUN;Lo;0;R;;;;;N;;;;; 080E;SAMARITAN LETTER SINGAAT;Lo;0;R;;;;;N;;;;; 080F;SAMARITAN LETTER IN;Lo;0;R;;;;;N;;;;; 0810;SAMARITAN LETTER FI;Lo;0;R;;;;;N;;;;; 0811;SAMARITAN LETTER TSAADIY;Lo;0;R;;;;;N;;;;; 0812;SAMARITAN LETTER QUF;Lo;0;R;;;;;N;;;;; 0813;SAMARITAN LETTER RISH;Lo;0;R;;;;;N;;;;; 0814;SAMARITAN LETTER SHAN;Lo;0;R;;;;;N;;;;; 0815;SAMARITAN LETTER TAAF;Lo;0;R;;;;;N;;;;; 0816;SAMARITAN MARK IN;Mn;230;NSM;;;;;N;;;;; 0817;SAMARITAN MARK IN-ALAF;Mn;230;NSM;;;;;N;;;;; 0818;SAMARITAN MARK OCCLUSION;Mn;230;NSM;;;;;N;;;;; 0819;SAMARITAN MARK DAGESH;Mn;230;NSM;;;;;N;;;;; 081A;SAMARITAN MODIFIER LETTER EPENTHETIC YUT;Lm;0;R;;;;;N;;;;; 081B;SAMARITAN MARK EPENTHETIC YUT;Mn;230;NSM;;;;;N;;;;; 081C;SAMARITAN VOWEL SIGN LONG E;Mn;230;NSM;;;;;N;;;;; 081D;SAMARITAN VOWEL SIGN E;Mn;230;NSM;;;;;N;;;;; 081E;SAMARITAN VOWEL SIGN OVERLONG AA;Mn;230;NSM;;;;;N;;;;; 081F;SAMARITAN VOWEL SIGN LONG AA;Mn;230;NSM;;;;;N;;;;; 0820;SAMARITAN VOWEL SIGN AA;Mn;230;NSM;;;;;N;;;;; 0821;SAMARITAN VOWEL SIGN OVERLONG A;Mn;230;NSM;;;;;N;;;;; 0822;SAMARITAN VOWEL SIGN LONG A;Mn;230;NSM;;;;;N;;;;; 0823;SAMARITAN VOWEL SIGN A;Mn;230;NSM;;;;;N;;;;; 0824;SAMARITAN MODIFIER LETTER SHORT A;Lm;0;R;;;;;N;;;;; 0825;SAMARITAN VOWEL SIGN SHORT A;Mn;230;NSM;;;;;N;;;;; 0826;SAMARITAN VOWEL SIGN LONG U;Mn;230;NSM;;;;;N;;;;; 0827;SAMARITAN VOWEL SIGN U;Mn;230;NSM;;;;;N;;;;; 0828;SAMARITAN MODIFIER LETTER I;Lm;0;R;;;;;N;;;;; 0829;SAMARITAN VOWEL SIGN LONG I;Mn;230;NSM;;;;;N;;;;; 082A;SAMARITAN VOWEL SIGN I;Mn;230;NSM;;;;;N;;;;; 082B;SAMARITAN VOWEL SIGN O;Mn;230;NSM;;;;;N;;;;; 082C;SAMARITAN VOWEL SIGN SUKUN;Mn;230;NSM;;;;;N;;;;; 082D;SAMARITAN MARK NEQUDAA;Mn;230;NSM;;;;;N;;;;; 0830;SAMARITAN PUNCTUATION NEQUDAA;Po;0;R;;;;;N;;;;; 0831;SAMARITAN PUNCTUATION AFSAAQ;Po;0;R;;;;;N;;;;; 0832;SAMARITAN PUNCTUATION ANGED;Po;0;R;;;;;N;;;;; 0833;SAMARITAN PUNCTUATION BAU;Po;0;R;;;;;N;;;;; 0834;SAMARITAN PUNCTUATION ATMAAU;Po;0;R;;;;;N;;;;; 0835;SAMARITAN PUNCTUATION SHIYYAALAA;Po;0;R;;;;;N;;;;; 0836;SAMARITAN ABBREVIATION MARK;Po;0;R;;;;;N;;;;; 0837;SAMARITAN PUNCTUATION MELODIC QITSA;Po;0;R;;;;;N;;;;; 0838;SAMARITAN PUNCTUATION ZIQAA;Po;0;R;;;;;N;;;;; 0839;SAMARITAN PUNCTUATION QITSA;Po;0;R;;;;;N;;;;; 083A;SAMARITAN PUNCTUATION ZAEF;Po;0;R;;;;;N;;;;; 083B;SAMARITAN PUNCTUATION TURU;Po;0;R;;;;;N;;;;; 083C;SAMARITAN PUNCTUATION ARKAANU;Po;0;R;;;;;N;;;;; 083D;SAMARITAN PUNCTUATION SOF MASHFAAT;Po;0;R;;;;;N;;;;; 083E;SAMARITAN PUNCTUATION ANNAAU;Po;0;R;;;;;N;;;;; 0840;MANDAIC LETTER HALQA;Lo;0;R;;;;;N;;;;; 0841;MANDAIC LETTER AB;Lo;0;R;;;;;N;;;;; 0842;MANDAIC LETTER AG;Lo;0;R;;;;;N;;;;; 0843;MANDAIC LETTER AD;Lo;0;R;;;;;N;;;;; 0844;MANDAIC LETTER AH;Lo;0;R;;;;;N;;;;; 0845;MANDAIC LETTER USHENNA;Lo;0;R;;;;;N;;;;; 0846;MANDAIC LETTER AZ;Lo;0;R;;;;;N;;;;; 0847;MANDAIC LETTER IT;Lo;0;R;;;;;N;;;;; 0848;MANDAIC LETTER ATT;Lo;0;R;;;;;N;;;;; 0849;MANDAIC LETTER AKSA;Lo;0;R;;;;;N;;;;; 084A;MANDAIC LETTER AK;Lo;0;R;;;;;N;;;;; 084B;MANDAIC LETTER AL;Lo;0;R;;;;;N;;;;; 084C;MANDAIC LETTER AM;Lo;0;R;;;;;N;;;;; 084D;MANDAIC LETTER AN;Lo;0;R;;;;;N;;;;; 084E;MANDAIC LETTER AS;Lo;0;R;;;;;N;;;;; 084F;MANDAIC LETTER IN;Lo;0;R;;;;;N;;;;; 0850;MANDAIC LETTER AP;Lo;0;R;;;;;N;;;;; 0851;MANDAIC LETTER ASZ;Lo;0;R;;;;;N;;;;; 0852;MANDAIC LETTER AQ;Lo;0;R;;;;;N;;;;; 0853;MANDAIC LETTER AR;Lo;0;R;;;;;N;;;;; 0854;MANDAIC LETTER ASH;Lo;0;R;;;;;N;;;;; 0855;MANDAIC LETTER AT;Lo;0;R;;;;;N;;;;; 0856;MANDAIC LETTER DUSHENNA;Lo;0;R;;;;;N;;;;; 0857;MANDAIC LETTER KAD;Lo;0;R;;;;;N;;;;; 0858;MANDAIC LETTER AIN;Lo;0;R;;;;;N;;;;; 0859;MANDAIC AFFRICATION MARK;Mn;220;NSM;;;;;N;;;;; 085A;MANDAIC VOCALIZATION MARK;Mn;220;NSM;;;;;N;;;;; 085B;MANDAIC GEMINATION MARK;Mn;220;NSM;;;;;N;;;;; 085E;MANDAIC PUNCTUATION;Po;0;R;;;;;N;;;;; 08A0;ARABIC LETTER BEH WITH SMALL V BELOW;Lo;0;AL;;;;;N;;;;; 08A1;ARABIC LETTER BEH WITH HAMZA ABOVE;Lo;0;AL;;;;;N;;;;; 08A2;ARABIC LETTER JEEM WITH TWO DOTS ABOVE;Lo;0;AL;;;;;N;;;;; 08A3;ARABIC LETTER TAH WITH TWO DOTS ABOVE;Lo;0;AL;;;;;N;;;;; 08A4;ARABIC LETTER FEH WITH DOT BELOW AND THREE DOTS ABOVE;Lo;0;AL;;;;;N;;;;; 08A5;ARABIC LETTER QAF WITH DOT BELOW;Lo;0;AL;;;;;N;;;;; 08A6;ARABIC LETTER LAM WITH DOUBLE BAR;Lo;0;AL;;;;;N;;;;; 08A7;ARABIC LETTER MEEM WITH THREE DOTS ABOVE;Lo;0;AL;;;;;N;;;;; 08A8;ARABIC LETTER YEH WITH TWO DOTS BELOW AND HAMZA ABOVE;Lo;0;AL;;;;;N;;;;; 08A9;ARABIC LETTER YEH WITH TWO DOTS BELOW AND DOT ABOVE;Lo;0;AL;;;;;N;;;;; 08AA;ARABIC LETTER REH WITH LOOP;Lo;0;AL;;;;;N;;;;; 08AB;ARABIC LETTER WAW WITH DOT WITHIN;Lo;0;AL;;;;;N;;;;; 08AC;ARABIC LETTER ROHINGYA YEH;Lo;0;AL;;;;;N;;;;; 08AD;ARABIC LETTER LOW ALEF;Lo;0;AL;;;;;N;;;;; 08AE;ARABIC LETTER DAL WITH THREE DOTS BELOW;Lo;0;AL;;;;;N;;;;; 08AF;ARABIC LETTER SAD WITH THREE DOTS BELOW;Lo;0;AL;;;;;N;;;;; 08B0;ARABIC LETTER GAF WITH INVERTED STROKE;Lo;0;AL;;;;;N;;;;; 08B1;ARABIC LETTER STRAIGHT WAW;Lo;0;AL;;;;;N;;;;; 08B2;ARABIC LETTER ZAIN WITH INVERTED V ABOVE;Lo;0;AL;;;;;N;;;;; 08E4;ARABIC CURLY FATHA;Mn;230;NSM;;;;;N;;;;; 08E5;ARABIC CURLY DAMMA;Mn;230;NSM;;;;;N;;;;; 08E6;ARABIC CURLY KASRA;Mn;220;NSM;;;;;N;;;;; 08E7;ARABIC CURLY FATHATAN;Mn;230;NSM;;;;;N;;;;; 08E8;ARABIC CURLY DAMMATAN;Mn;230;NSM;;;;;N;;;;; 08E9;ARABIC CURLY KASRATAN;Mn;220;NSM;;;;;N;;;;; 08EA;ARABIC TONE ONE DOT ABOVE;Mn;230;NSM;;;;;N;;;;; 08EB;ARABIC TONE TWO DOTS ABOVE;Mn;230;NSM;;;;;N;;;;; 08EC;ARABIC TONE LOOP ABOVE;Mn;230;NSM;;;;;N;;;;; 08ED;ARABIC TONE ONE DOT BELOW;Mn;220;NSM;;;;;N;;;;; 08EE;ARABIC TONE TWO DOTS BELOW;Mn;220;NSM;;;;;N;;;;; 08EF;ARABIC TONE LOOP BELOW;Mn;220;NSM;;;;;N;;;;; 08F0;ARABIC OPEN FATHATAN;Mn;27;NSM;;;;;N;;;;; 08F1;ARABIC OPEN DAMMATAN;Mn;28;NSM;;;;;N;;;;; 08F2;ARABIC OPEN KASRATAN;Mn;29;NSM;;;;;N;;;;; 08F3;ARABIC SMALL HIGH WAW;Mn;230;NSM;;;;;N;;;;; 08F4;ARABIC FATHA WITH RING;Mn;230;NSM;;;;;N;;;;; 08F5;ARABIC FATHA WITH DOT ABOVE;Mn;230;NSM;;;;;N;;;;; 08F6;ARABIC KASRA WITH DOT BELOW;Mn;220;NSM;;;;;N;;;;; 08F7;ARABIC LEFT ARROWHEAD ABOVE;Mn;230;NSM;;;;;N;;;;; 08F8;ARABIC RIGHT ARROWHEAD ABOVE;Mn;230;NSM;;;;;N;;;;; 08F9;ARABIC LEFT ARROWHEAD BELOW;Mn;220;NSM;;;;;N;;;;; 08FA;ARABIC RIGHT ARROWHEAD BELOW;Mn;220;NSM;;;;;N;;;;; 08FB;ARABIC DOUBLE RIGHT ARROWHEAD ABOVE;Mn;230;NSM;;;;;N;;;;; 08FC;ARABIC DOUBLE RIGHT ARROWHEAD ABOVE WITH DOT;Mn;230;NSM;;;;;N;;;;; 08FD;ARABIC RIGHT ARROWHEAD ABOVE WITH DOT;Mn;230;NSM;;;;;N;;;;; 08FE;ARABIC DAMMA WITH DOT;Mn;230;NSM;;;;;N;;;;; 08FF;ARABIC MARK SIDEWAYS NOON GHUNNA;Mn;230;NSM;;;;;N;;;;; 0900;DEVANAGARI SIGN INVERTED CANDRABINDU;Mn;0;NSM;;;;;N;;;;; 0901;DEVANAGARI SIGN CANDRABINDU;Mn;0;NSM;;;;;N;;;;; 0902;DEVANAGARI SIGN ANUSVARA;Mn;0;NSM;;;;;N;;;;; 0903;DEVANAGARI SIGN VISARGA;Mc;0;L;;;;;N;;;;; 0904;DEVANAGARI LETTER SHORT A;Lo;0;L;;;;;N;;;;; 0905;DEVANAGARI LETTER A;Lo;0;L;;;;;N;;;;; 0906;DEVANAGARI LETTER AA;Lo;0;L;;;;;N;;;;; 0907;DEVANAGARI LETTER I;Lo;0;L;;;;;N;;;;; 0908;DEVANAGARI LETTER II;Lo;0;L;;;;;N;;;;; 0909;DEVANAGARI LETTER U;Lo;0;L;;;;;N;;;;; 090A;DEVANAGARI LETTER UU;Lo;0;L;;;;;N;;;;; 090B;DEVANAGARI LETTER VOCALIC R;Lo;0;L;;;;;N;;;;; 090C;DEVANAGARI LETTER VOCALIC L;Lo;0;L;;;;;N;;;;; 090D;DEVANAGARI LETTER CANDRA E;Lo;0;L;;;;;N;;;;; 090E;DEVANAGARI LETTER SHORT E;Lo;0;L;;;;;N;;;;; 090F;DEVANAGARI LETTER E;Lo;0;L;;;;;N;;;;; 0910;DEVANAGARI LETTER AI;Lo;0;L;;;;;N;;;;; 0911;DEVANAGARI LETTER CANDRA O;Lo;0;L;;;;;N;;;;; 0912;DEVANAGARI LETTER SHORT O;Lo;0;L;;;;;N;;;;; 0913;DEVANAGARI LETTER O;Lo;0;L;;;;;N;;;;; 0914;DEVANAGARI LETTER AU;Lo;0;L;;;;;N;;;;; 0915;DEVANAGARI LETTER KA;Lo;0;L;;;;;N;;;;; 0916;DEVANAGARI LETTER KHA;Lo;0;L;;;;;N;;;;; 0917;DEVANAGARI LETTER GA;Lo;0;L;;;;;N;;;;; 0918;DEVANAGARI LETTER GHA;Lo;0;L;;;;;N;;;;; 0919;DEVANAGARI LETTER NGA;Lo;0;L;;;;;N;;;;; 091A;DEVANAGARI LETTER CA;Lo;0;L;;;;;N;;;;; 091B;DEVANAGARI LETTER CHA;Lo;0;L;;;;;N;;;;; 091C;DEVANAGARI LETTER JA;Lo;0;L;;;;;N;;;;; 091D;DEVANAGARI LETTER JHA;Lo;0;L;;;;;N;;;;; 091E;DEVANAGARI LETTER NYA;Lo;0;L;;;;;N;;;;; 091F;DEVANAGARI LETTER TTA;Lo;0;L;;;;;N;;;;; 0920;DEVANAGARI LETTER TTHA;Lo;0;L;;;;;N;;;;; 0921;DEVANAGARI LETTER DDA;Lo;0;L;;;;;N;;;;; 0922;DEVANAGARI LETTER DDHA;Lo;0;L;;;;;N;;;;; 0923;DEVANAGARI LETTER NNA;Lo;0;L;;;;;N;;;;; 0924;DEVANAGARI LETTER TA;Lo;0;L;;;;;N;;;;; 0925;DEVANAGARI LETTER THA;Lo;0;L;;;;;N;;;;; 0926;DEVANAGARI LETTER DA;Lo;0;L;;;;;N;;;;; 0927;DEVANAGARI LETTER DHA;Lo;0;L;;;;;N;;;;; 0928;DEVANAGARI LETTER NA;Lo;0;L;;;;;N;;;;; 0929;DEVANAGARI LETTER NNNA;Lo;0;L;0928 093C;;;;N;;;;; 092A;DEVANAGARI LETTER PA;Lo;0;L;;;;;N;;;;; 092B;DEVANAGARI LETTER PHA;Lo;0;L;;;;;N;;;;; 092C;DEVANAGARI LETTER BA;Lo;0;L;;;;;N;;;;; 092D;DEVANAGARI LETTER BHA;Lo;0;L;;;;;N;;;;; 092E;DEVANAGARI LETTER MA;Lo;0;L;;;;;N;;;;; 092F;DEVANAGARI LETTER YA;Lo;0;L;;;;;N;;;;; 0930;DEVANAGARI LETTER RA;Lo;0;L;;;;;N;;;;; 0931;DEVANAGARI LETTER RRA;Lo;0;L;0930 093C;;;;N;;;;; 0932;DEVANAGARI LETTER LA;Lo;0;L;;;;;N;;;;; 0933;DEVANAGARI LETTER LLA;Lo;0;L;;;;;N;;;;; 0934;DEVANAGARI LETTER LLLA;Lo;0;L;0933 093C;;;;N;;;;; 0935;DEVANAGARI LETTER VA;Lo;0;L;;;;;N;;;;; 0936;DEVANAGARI LETTER SHA;Lo;0;L;;;;;N;;;;; 0937;DEVANAGARI LETTER SSA;Lo;0;L;;;;;N;;;;; 0938;DEVANAGARI LETTER SA;Lo;0;L;;;;;N;;;;; 0939;DEVANAGARI LETTER HA;Lo;0;L;;;;;N;;;;; 093A;DEVANAGARI VOWEL SIGN OE;Mn;0;NSM;;;;;N;;;;; 093B;DEVANAGARI VOWEL SIGN OOE;Mc;0;L;;;;;N;;;;; 093C;DEVANAGARI SIGN NUKTA;Mn;7;NSM;;;;;N;;;;; 093D;DEVANAGARI SIGN AVAGRAHA;Lo;0;L;;;;;N;;;;; 093E;DEVANAGARI VOWEL SIGN AA;Mc;0;L;;;;;N;;;;; 093F;DEVANAGARI VOWEL SIGN I;Mc;0;L;;;;;N;;;;; 0940;DEVANAGARI VOWEL SIGN II;Mc;0;L;;;;;N;;;;; 0941;DEVANAGARI VOWEL SIGN U;Mn;0;NSM;;;;;N;;;;; 0942;DEVANAGARI VOWEL SIGN UU;Mn;0;NSM;;;;;N;;;;; 0943;DEVANAGARI VOWEL SIGN VOCALIC R;Mn;0;NSM;;;;;N;;;;; 0944;DEVANAGARI VOWEL SIGN VOCALIC RR;Mn;0;NSM;;;;;N;;;;; 0945;DEVANAGARI VOWEL SIGN CANDRA E;Mn;0;NSM;;;;;N;;;;; 0946;DEVANAGARI VOWEL SIGN SHORT E;Mn;0;NSM;;;;;N;;;;; 0947;DEVANAGARI VOWEL SIGN E;Mn;0;NSM;;;;;N;;;;; 0948;DEVANAGARI VOWEL SIGN AI;Mn;0;NSM;;;;;N;;;;; 0949;DEVANAGARI VOWEL SIGN CANDRA O;Mc;0;L;;;;;N;;;;; 094A;DEVANAGARI VOWEL SIGN SHORT O;Mc;0;L;;;;;N;;;;; 094B;DEVANAGARI VOWEL SIGN O;Mc;0;L;;;;;N;;;;; 094C;DEVANAGARI VOWEL SIGN AU;Mc;0;L;;;;;N;;;;; 094D;DEVANAGARI SIGN VIRAMA;Mn;9;NSM;;;;;N;;;;; 094E;DEVANAGARI VOWEL SIGN PRISHTHAMATRA E;Mc;0;L;;;;;N;;;;; 094F;DEVANAGARI VOWEL SIGN AW;Mc;0;L;;;;;N;;;;; 0950;DEVANAGARI OM;Lo;0;L;;;;;N;;;;; 0951;DEVANAGARI STRESS SIGN UDATTA;Mn;230;NSM;;;;;N;;;;; 0952;DEVANAGARI STRESS SIGN ANUDATTA;Mn;220;NSM;;;;;N;;;;; 0953;DEVANAGARI GRAVE ACCENT;Mn;230;NSM;;;;;N;;;;; 0954;DEVANAGARI ACUTE ACCENT;Mn;230;NSM;;;;;N;;;;; 0955;DEVANAGARI VOWEL SIGN CANDRA LONG E;Mn;0;NSM;;;;;N;;;;; 0956;DEVANAGARI VOWEL SIGN UE;Mn;0;NSM;;;;;N;;;;; 0957;DEVANAGARI VOWEL SIGN UUE;Mn;0;NSM;;;;;N;;;;; 0958;DEVANAGARI LETTER QA;Lo;0;L;0915 093C;;;;N;;;;; 0959;DEVANAGARI LETTER KHHA;Lo;0;L;0916 093C;;;;N;;;;; 095A;DEVANAGARI LETTER GHHA;Lo;0;L;0917 093C;;;;N;;;;; 095B;DEVANAGARI LETTER ZA;Lo;0;L;091C 093C;;;;N;;;;; 095C;DEVANAGARI LETTER DDDHA;Lo;0;L;0921 093C;;;;N;;;;; 095D;DEVANAGARI LETTER RHA;Lo;0;L;0922 093C;;;;N;;;;; 095E;DEVANAGARI LETTER FA;Lo;0;L;092B 093C;;;;N;;;;; 095F;DEVANAGARI LETTER YYA;Lo;0;L;092F 093C;;;;N;;;;; 0960;DEVANAGARI LETTER VOCALIC RR;Lo;0;L;;;;;N;;;;; 0961;DEVANAGARI LETTER VOCALIC LL;Lo;0;L;;;;;N;;;;; 0962;DEVANAGARI VOWEL SIGN VOCALIC L;Mn;0;NSM;;;;;N;;;;; 0963;DEVANAGARI VOWEL SIGN VOCALIC LL;Mn;0;NSM;;;;;N;;;;; 0964;DEVANAGARI DANDA;Po;0;L;;;;;N;;;;; 0965;DEVANAGARI DOUBLE DANDA;Po;0;L;;;;;N;;;;; 0966;DEVANAGARI DIGIT ZERO;Nd;0;L;;0;0;0;N;;;;; 0967;DEVANAGARI DIGIT ONE;Nd;0;L;;1;1;1;N;;;;; 0968;DEVANAGARI DIGIT TWO;Nd;0;L;;2;2;2;N;;;;; 0969;DEVANAGARI DIGIT THREE;Nd;0;L;;3;3;3;N;;;;; 096A;DEVANAGARI DIGIT FOUR;Nd;0;L;;4;4;4;N;;;;; 096B;DEVANAGARI DIGIT FIVE;Nd;0;L;;5;5;5;N;;;;; 096C;DEVANAGARI DIGIT SIX;Nd;0;L;;6;6;6;N;;;;; 096D;DEVANAGARI DIGIT SEVEN;Nd;0;L;;7;7;7;N;;;;; 096E;DEVANAGARI DIGIT EIGHT;Nd;0;L;;8;8;8;N;;;;; 096F;DEVANAGARI DIGIT NINE;Nd;0;L;;9;9;9;N;;;;; 0970;DEVANAGARI ABBREVIATION SIGN;Po;0;L;;;;;N;;;;; 0971;DEVANAGARI SIGN HIGH SPACING DOT;Lm;0;L;;;;;N;;;;; 0972;DEVANAGARI LETTER CANDRA A;Lo;0;L;;;;;N;;;;; 0973;DEVANAGARI LETTER OE;Lo;0;L;;;;;N;;;;; 0974;DEVANAGARI LETTER OOE;Lo;0;L;;;;;N;;;;; 0975;DEVANAGARI LETTER AW;Lo;0;L;;;;;N;;;;; 0976;DEVANAGARI LETTER UE;Lo;0;L;;;;;N;;;;; 0977;DEVANAGARI LETTER UUE;Lo;0;L;;;;;N;;;;; 0978;DEVANAGARI LETTER MARWARI DDA;Lo;0;L;;;;;N;;;;; 0979;DEVANAGARI LETTER ZHA;Lo;0;L;;;;;N;;;;; 097A;DEVANAGARI LETTER HEAVY YA;Lo;0;L;;;;;N;;;;; 097B;DEVANAGARI LETTER GGA;Lo;0;L;;;;;N;;;;; 097C;DEVANAGARI LETTER JJA;Lo;0;L;;;;;N;;;;; 097D;DEVANAGARI LETTER GLOTTAL STOP;Lo;0;L;;;;;N;;;;; 097E;DEVANAGARI LETTER DDDA;Lo;0;L;;;;;N;;;;; 097F;DEVANAGARI LETTER BBA;Lo;0;L;;;;;N;;;;; 0980;BENGALI ANJI;Lo;0;L;;;;;N;;;;; 0981;BENGALI SIGN CANDRABINDU;Mn;0;NSM;;;;;N;;;;; 0982;BENGALI SIGN ANUSVARA;Mc;0;L;;;;;N;;;;; 0983;BENGALI SIGN VISARGA;Mc;0;L;;;;;N;;;;; 0985;BENGALI LETTER A;Lo;0;L;;;;;N;;;;; 0986;BENGALI LETTER AA;Lo;0;L;;;;;N;;;;; 0987;BENGALI LETTER I;Lo;0;L;;;;;N;;;;; 0988;BENGALI LETTER II;Lo;0;L;;;;;N;;;;; 0989;BENGALI LETTER U;Lo;0;L;;;;;N;;;;; 098A;BENGALI LETTER UU;Lo;0;L;;;;;N;;;;; 098B;BENGALI LETTER VOCALIC R;Lo;0;L;;;;;N;;;;; 098C;BENGALI LETTER VOCALIC L;Lo;0;L;;;;;N;;;;; 098F;BENGALI LETTER E;Lo;0;L;;;;;N;;;;; 0990;BENGALI LETTER AI;Lo;0;L;;;;;N;;;;; 0993;BENGALI LETTER O;Lo;0;L;;;;;N;;;;; 0994;BENGALI LETTER AU;Lo;0;L;;;;;N;;;;; 0995;BENGALI LETTER KA;Lo;0;L;;;;;N;;;;; 0996;BENGALI LETTER KHA;Lo;0;L;;;;;N;;;;; 0997;BENGALI LETTER GA;Lo;0;L;;;;;N;;;;; 0998;BENGALI LETTER GHA;Lo;0;L;;;;;N;;;;; 0999;BENGALI LETTER NGA;Lo;0;L;;;;;N;;;;; 099A;BENGALI LETTER CA;Lo;0;L;;;;;N;;;;; 099B;BENGALI LETTER CHA;Lo;0;L;;;;;N;;;;; 099C;BENGALI LETTER JA;Lo;0;L;;;;;N;;;;; 099D;BENGALI LETTER JHA;Lo;0;L;;;;;N;;;;; 099E;BENGALI LETTER NYA;Lo;0;L;;;;;N;;;;; 099F;BENGALI LETTER TTA;Lo;0;L;;;;;N;;;;; 09A0;BENGALI LETTER TTHA;Lo;0;L;;;;;N;;;;; 09A1;BENGALI LETTER DDA;Lo;0;L;;;;;N;;;;; 09A2;BENGALI LETTER DDHA;Lo;0;L;;;;;N;;;;; 09A3;BENGALI LETTER NNA;Lo;0;L;;;;;N;;;;; 09A4;BENGALI LETTER TA;Lo;0;L;;;;;N;;;;; 09A5;BENGALI LETTER THA;Lo;0;L;;;;;N;;;;; 09A6;BENGALI LETTER DA;Lo;0;L;;;;;N;;;;; 09A7;BENGALI LETTER DHA;Lo;0;L;;;;;N;;;;; 09A8;BENGALI LETTER NA;Lo;0;L;;;;;N;;;;; 09AA;BENGALI LETTER PA;Lo;0;L;;;;;N;;;;; 09AB;BENGALI LETTER PHA;Lo;0;L;;;;;N;;;;; 09AC;BENGALI LETTER BA;Lo;0;L;;;;;N;;;;; 09AD;BENGALI LETTER BHA;Lo;0;L;;;;;N;;;;; 09AE;BENGALI LETTER MA;Lo;0;L;;;;;N;;;;; 09AF;BENGALI LETTER YA;Lo;0;L;;;;;N;;;;; 09B0;BENGALI LETTER RA;Lo;0;L;;;;;N;;;;; 09B2;BENGALI LETTER LA;Lo;0;L;;;;;N;;;;; 09B6;BENGALI LETTER SHA;Lo;0;L;;;;;N;;;;; 09B7;BENGALI LETTER SSA;Lo;0;L;;;;;N;;;;; 09B8;BENGALI LETTER SA;Lo;0;L;;;;;N;;;;; 09B9;BENGALI LETTER HA;Lo;0;L;;;;;N;;;;; 09BC;BENGALI SIGN NUKTA;Mn;7;NSM;;;;;N;;;;; 09BD;BENGALI SIGN AVAGRAHA;Lo;0;L;;;;;N;;;;; 09BE;BENGALI VOWEL SIGN AA;Mc;0;L;;;;;N;;;;; 09BF;BENGALI VOWEL SIGN I;Mc;0;L;;;;;N;;;;; 09C0;BENGALI VOWEL SIGN II;Mc;0;L;;;;;N;;;;; 09C1;BENGALI VOWEL SIGN U;Mn;0;NSM;;;;;N;;;;; 09C2;BENGALI VOWEL SIGN UU;Mn;0;NSM;;;;;N;;;;; 09C3;BENGALI VOWEL SIGN VOCALIC R;Mn;0;NSM;;;;;N;;;;; 09C4;BENGALI VOWEL SIGN VOCALIC RR;Mn;0;NSM;;;;;N;;;;; 09C7;BENGALI VOWEL SIGN E;Mc;0;L;;;;;N;;;;; 09C8;BENGALI VOWEL SIGN AI;Mc;0;L;;;;;N;;;;; 09CB;BENGALI VOWEL SIGN O;Mc;0;L;09C7 09BE;;;;N;;;;; 09CC;BENGALI VOWEL SIGN AU;Mc;0;L;09C7 09D7;;;;N;;;;; 09CD;BENGALI SIGN VIRAMA;Mn;9;NSM;;;;;N;;;;; 09CE;BENGALI LETTER KHANDA TA;Lo;0;L;;;;;N;;;;; 09D7;BENGALI AU LENGTH MARK;Mc;0;L;;;;;N;;;;; 09DC;BENGALI LETTER RRA;Lo;0;L;09A1 09BC;;;;N;;;;; 09DD;BENGALI LETTER RHA;Lo;0;L;09A2 09BC;;;;N;;;;; 09DF;BENGALI LETTER YYA;Lo;0;L;09AF 09BC;;;;N;;;;; 09E0;BENGALI LETTER VOCALIC RR;Lo;0;L;;;;;N;;;;; 09E1;BENGALI LETTER VOCALIC LL;Lo;0;L;;;;;N;;;;; 09E2;BENGALI VOWEL SIGN VOCALIC L;Mn;0;NSM;;;;;N;;;;; 09E3;BENGALI VOWEL SIGN VOCALIC LL;Mn;0;NSM;;;;;N;;;;; 09E6;BENGALI DIGIT ZERO;Nd;0;L;;0;0;0;N;;;;; 09E7;BENGALI DIGIT ONE;Nd;0;L;;1;1;1;N;;;;; 09E8;BENGALI DIGIT TWO;Nd;0;L;;2;2;2;N;;;;; 09E9;BENGALI DIGIT THREE;Nd;0;L;;3;3;3;N;;;;; 09EA;BENGALI DIGIT FOUR;Nd;0;L;;4;4;4;N;;;;; 09EB;BENGALI DIGIT FIVE;Nd;0;L;;5;5;5;N;;;;; 09EC;BENGALI DIGIT SIX;Nd;0;L;;6;6;6;N;;;;; 09ED;BENGALI DIGIT SEVEN;Nd;0;L;;7;7;7;N;;;;; 09EE;BENGALI DIGIT EIGHT;Nd;0;L;;8;8;8;N;;;;; 09EF;BENGALI DIGIT NINE;Nd;0;L;;9;9;9;N;;;;; 09F0;BENGALI LETTER RA WITH MIDDLE DIAGONAL;Lo;0;L;;;;;N;;;;; 09F1;BENGALI LETTER RA WITH LOWER DIAGONAL;Lo;0;L;;;;;N;BENGALI LETTER VA WITH LOWER DIAGONAL;;;; 09F2;BENGALI RUPEE MARK;Sc;0;ET;;;;;N;;;;; 09F3;BENGALI RUPEE SIGN;Sc;0;ET;;;;;N;;;;; 09F4;BENGALI CURRENCY NUMERATOR ONE;No;0;L;;;;1/16;N;;;;; 09F5;BENGALI CURRENCY NUMERATOR TWO;No;0;L;;;;1/8;N;;;;; 09F6;BENGALI CURRENCY NUMERATOR THREE;No;0;L;;;;3/16;N;;;;; 09F7;BENGALI CURRENCY NUMERATOR FOUR;No;0;L;;;;1/4;N;;;;; 09F8;BENGALI CURRENCY NUMERATOR ONE LESS THAN THE DENOMINATOR;No;0;L;;;;3/4;N;;;;; 09F9;BENGALI CURRENCY DENOMINATOR SIXTEEN;No;0;L;;;;16;N;;;;; 09FA;BENGALI ISSHAR;So;0;L;;;;;N;;;;; 09FB;BENGALI GANDA MARK;Sc;0;ET;;;;;N;;;;; 0A01;GURMUKHI SIGN ADAK BINDI;Mn;0;NSM;;;;;N;;;;; 0A02;GURMUKHI SIGN BINDI;Mn;0;NSM;;;;;N;;;;; 0A03;GURMUKHI SIGN VISARGA;Mc;0;L;;;;;N;;;;; 0A05;GURMUKHI LETTER A;Lo;0;L;;;;;N;;;;; 0A06;GURMUKHI LETTER AA;Lo;0;L;;;;;N;;;;; 0A07;GURMUKHI LETTER I;Lo;0;L;;;;;N;;;;; 0A08;GURMUKHI LETTER II;Lo;0;L;;;;;N;;;;; 0A09;GURMUKHI LETTER U;Lo;0;L;;;;;N;;;;; 0A0A;GURMUKHI LETTER UU;Lo;0;L;;;;;N;;;;; 0A0F;GURMUKHI LETTER EE;Lo;0;L;;;;;N;;;;; 0A10;GURMUKHI LETTER AI;Lo;0;L;;;;;N;;;;; 0A13;GURMUKHI LETTER OO;Lo;0;L;;;;;N;;;;; 0A14;GURMUKHI LETTER AU;Lo;0;L;;;;;N;;;;; 0A15;GURMUKHI LETTER KA;Lo;0;L;;;;;N;;;;; 0A16;GURMUKHI LETTER KHA;Lo;0;L;;;;;N;;;;; 0A17;GURMUKHI LETTER GA;Lo;0;L;;;;;N;;;;; 0A18;GURMUKHI LETTER GHA;Lo;0;L;;;;;N;;;;; 0A19;GURMUKHI LETTER NGA;Lo;0;L;;;;;N;;;;; 0A1A;GURMUKHI LETTER CA;Lo;0;L;;;;;N;;;;; 0A1B;GURMUKHI LETTER CHA;Lo;0;L;;;;;N;;;;; 0A1C;GURMUKHI LETTER JA;Lo;0;L;;;;;N;;;;; 0A1D;GURMUKHI LETTER JHA;Lo;0;L;;;;;N;;;;; 0A1E;GURMUKHI LETTER NYA;Lo;0;L;;;;;N;;;;; 0A1F;GURMUKHI LETTER TTA;Lo;0;L;;;;;N;;;;; 0A20;GURMUKHI LETTER TTHA;Lo;0;L;;;;;N;;;;; 0A21;GURMUKHI LETTER DDA;Lo;0;L;;;;;N;;;;; 0A22;GURMUKHI LETTER DDHA;Lo;0;L;;;;;N;;;;; 0A23;GURMUKHI LETTER NNA;Lo;0;L;;;;;N;;;;; 0A24;GURMUKHI LETTER TA;Lo;0;L;;;;;N;;;;; 0A25;GURMUKHI LETTER THA;Lo;0;L;;;;;N;;;;; 0A26;GURMUKHI LETTER DA;Lo;0;L;;;;;N;;;;; 0A27;GURMUKHI LETTER DHA;Lo;0;L;;;;;N;;;;; 0A28;GURMUKHI LETTER NA;Lo;0;L;;;;;N;;;;; 0A2A;GURMUKHI LETTER PA;Lo;0;L;;;;;N;;;;; 0A2B;GURMUKHI LETTER PHA;Lo;0;L;;;;;N;;;;; 0A2C;GURMUKHI LETTER BA;Lo;0;L;;;;;N;;;;; 0A2D;GURMUKHI LETTER BHA;Lo;0;L;;;;;N;;;;; 0A2E;GURMUKHI LETTER MA;Lo;0;L;;;;;N;;;;; 0A2F;GURMUKHI LETTER YA;Lo;0;L;;;;;N;;;;; 0A30;GURMUKHI LETTER RA;Lo;0;L;;;;;N;;;;; 0A32;GURMUKHI LETTER LA;Lo;0;L;;;;;N;;;;; 0A33;GURMUKHI LETTER LLA;Lo;0;L;0A32 0A3C;;;;N;;;;; 0A35;GURMUKHI LETTER VA;Lo;0;L;;;;;N;;;;; 0A36;GURMUKHI LETTER SHA;Lo;0;L;0A38 0A3C;;;;N;;;;; 0A38;GURMUKHI LETTER SA;Lo;0;L;;;;;N;;;;; 0A39;GURMUKHI LETTER HA;Lo;0;L;;;;;N;;;;; 0A3C;GURMUKHI SIGN NUKTA;Mn;7;NSM;;;;;N;;;;; 0A3E;GURMUKHI VOWEL SIGN AA;Mc;0;L;;;;;N;;;;; 0A3F;GURMUKHI VOWEL SIGN I;Mc;0;L;;;;;N;;;;; 0A40;GURMUKHI VOWEL SIGN II;Mc;0;L;;;;;N;;;;; 0A41;GURMUKHI VOWEL SIGN U;Mn;0;NSM;;;;;N;;;;; 0A42;GURMUKHI VOWEL SIGN UU;Mn;0;NSM;;;;;N;;;;; 0A47;GURMUKHI VOWEL SIGN EE;Mn;0;NSM;;;;;N;;;;; 0A48;GURMUKHI VOWEL SIGN AI;Mn;0;NSM;;;;;N;;;;; 0A4B;GURMUKHI VOWEL SIGN OO;Mn;0;NSM;;;;;N;;;;; 0A4C;GURMUKHI VOWEL SIGN AU;Mn;0;NSM;;;;;N;;;;; 0A4D;GURMUKHI SIGN VIRAMA;Mn;9;NSM;;;;;N;;;;; 0A51;GURMUKHI SIGN UDAAT;Mn;0;NSM;;;;;N;;;;; 0A59;GURMUKHI LETTER KHHA;Lo;0;L;0A16 0A3C;;;;N;;;;; 0A5A;GURMUKHI LETTER GHHA;Lo;0;L;0A17 0A3C;;;;N;;;;; 0A5B;GURMUKHI LETTER ZA;Lo;0;L;0A1C 0A3C;;;;N;;;;; 0A5C;GURMUKHI LETTER RRA;Lo;0;L;;;;;N;;;;; 0A5E;GURMUKHI LETTER FA;Lo;0;L;0A2B 0A3C;;;;N;;;;; 0A66;GURMUKHI DIGIT ZERO;Nd;0;L;;0;0;0;N;;;;; 0A67;GURMUKHI DIGIT ONE;Nd;0;L;;1;1;1;N;;;;; 0A68;GURMUKHI DIGIT TWO;Nd;0;L;;2;2;2;N;;;;; 0A69;GURMUKHI DIGIT THREE;Nd;0;L;;3;3;3;N;;;;; 0A6A;GURMUKHI DIGIT FOUR;Nd;0;L;;4;4;4;N;;;;; 0A6B;GURMUKHI DIGIT FIVE;Nd;0;L;;5;5;5;N;;;;; 0A6C;GURMUKHI DIGIT SIX;Nd;0;L;;6;6;6;N;;;;; 0A6D;GURMUKHI DIGIT SEVEN;Nd;0;L;;7;7;7;N;;;;; 0A6E;GURMUKHI DIGIT EIGHT;Nd;0;L;;8;8;8;N;;;;; 0A6F;GURMUKHI DIGIT NINE;Nd;0;L;;9;9;9;N;;;;; 0A70;GURMUKHI TIPPI;Mn;0;NSM;;;;;N;;;;; 0A71;GURMUKHI ADDAK;Mn;0;NSM;;;;;N;;;;; 0A72;GURMUKHI IRI;Lo;0;L;;;;;N;;;;; 0A73;GURMUKHI URA;Lo;0;L;;;;;N;;;;; 0A74;GURMUKHI EK ONKAR;Lo;0;L;;;;;N;;;;; 0A75;GURMUKHI SIGN YAKASH;Mn;0;NSM;;;;;N;;;;; 0A81;GUJARATI SIGN CANDRABINDU;Mn;0;NSM;;;;;N;;;;; 0A82;GUJARATI SIGN ANUSVARA;Mn;0;NSM;;;;;N;;;;; 0A83;GUJARATI SIGN VISARGA;Mc;0;L;;;;;N;;;;; 0A85;GUJARATI LETTER A;Lo;0;L;;;;;N;;;;; 0A86;GUJARATI LETTER AA;Lo;0;L;;;;;N;;;;; 0A87;GUJARATI LETTER I;Lo;0;L;;;;;N;;;;; 0A88;GUJARATI LETTER II;Lo;0;L;;;;;N;;;;; 0A89;GUJARATI LETTER U;Lo;0;L;;;;;N;;;;; 0A8A;GUJARATI LETTER UU;Lo;0;L;;;;;N;;;;; 0A8B;GUJARATI LETTER VOCALIC R;Lo;0;L;;;;;N;;;;; 0A8C;GUJARATI LETTER VOCALIC L;Lo;0;L;;;;;N;;;;; 0A8D;GUJARATI VOWEL CANDRA E;Lo;0;L;;;;;N;;;;; 0A8F;GUJARATI LETTER E;Lo;0;L;;;;;N;;;;; 0A90;GUJARATI LETTER AI;Lo;0;L;;;;;N;;;;; 0A91;GUJARATI VOWEL CANDRA O;Lo;0;L;;;;;N;;;;; 0A93;GUJARATI LETTER O;Lo;0;L;;;;;N;;;;; 0A94;GUJARATI LETTER AU;Lo;0;L;;;;;N;;;;; 0A95;GUJARATI LETTER KA;Lo;0;L;;;;;N;;;;; 0A96;GUJARATI LETTER KHA;Lo;0;L;;;;;N;;;;; 0A97;GUJARATI LETTER GA;Lo;0;L;;;;;N;;;;; 0A98;GUJARATI LETTER GHA;Lo;0;L;;;;;N;;;;; 0A99;GUJARATI LETTER NGA;Lo;0;L;;;;;N;;;;; 0A9A;GUJARATI LETTER CA;Lo;0;L;;;;;N;;;;; 0A9B;GUJARATI LETTER CHA;Lo;0;L;;;;;N;;;;; 0A9C;GUJARATI LETTER JA;Lo;0;L;;;;;N;;;;; 0A9D;GUJARATI LETTER JHA;Lo;0;L;;;;;N;;;;; 0A9E;GUJARATI LETTER NYA;Lo;0;L;;;;;N;;;;; 0A9F;GUJARATI LETTER TTA;Lo;0;L;;;;;N;;;;; 0AA0;GUJARATI LETTER TTHA;Lo;0;L;;;;;N;;;;; 0AA1;GUJARATI LETTER DDA;Lo;0;L;;;;;N;;;;; 0AA2;GUJARATI LETTER DDHA;Lo;0;L;;;;;N;;;;; 0AA3;GUJARATI LETTER NNA;Lo;0;L;;;;;N;;;;; 0AA4;GUJARATI LETTER TA;Lo;0;L;;;;;N;;;;; 0AA5;GUJARATI LETTER THA;Lo;0;L;;;;;N;;;;; 0AA6;GUJARATI LETTER DA;Lo;0;L;;;;;N;;;;; 0AA7;GUJARATI LETTER DHA;Lo;0;L;;;;;N;;;;; 0AA8;GUJARATI LETTER NA;Lo;0;L;;;;;N;;;;; 0AAA;GUJARATI LETTER PA;Lo;0;L;;;;;N;;;;; 0AAB;GUJARATI LETTER PHA;Lo;0;L;;;;;N;;;;; 0AAC;GUJARATI LETTER BA;Lo;0;L;;;;;N;;;;; 0AAD;GUJARATI LETTER BHA;Lo;0;L;;;;;N;;;;; 0AAE;GUJARATI LETTER MA;Lo;0;L;;;;;N;;;;; 0AAF;GUJARATI LETTER YA;Lo;0;L;;;;;N;;;;; 0AB0;GUJARATI LETTER RA;Lo;0;L;;;;;N;;;;; 0AB2;GUJARATI LETTER LA;Lo;0;L;;;;;N;;;;; 0AB3;GUJARATI LETTER LLA;Lo;0;L;;;;;N;;;;; 0AB5;GUJARATI LETTER VA;Lo;0;L;;;;;N;;;;; 0AB6;GUJARATI LETTER SHA;Lo;0;L;;;;;N;;;;; 0AB7;GUJARATI LETTER SSA;Lo;0;L;;;;;N;;;;; 0AB8;GUJARATI LETTER SA;Lo;0;L;;;;;N;;;;; 0AB9;GUJARATI LETTER HA;Lo;0;L;;;;;N;;;;; 0ABC;GUJARATI SIGN NUKTA;Mn;7;NSM;;;;;N;;;;; 0ABD;GUJARATI SIGN AVAGRAHA;Lo;0;L;;;;;N;;;;; 0ABE;GUJARATI VOWEL SIGN AA;Mc;0;L;;;;;N;;;;; 0ABF;GUJARATI VOWEL SIGN I;Mc;0;L;;;;;N;;;;; 0AC0;GUJARATI VOWEL SIGN II;Mc;0;L;;;;;N;;;;; 0AC1;GUJARATI VOWEL SIGN U;Mn;0;NSM;;;;;N;;;;; 0AC2;GUJARATI VOWEL SIGN UU;Mn;0;NSM;;;;;N;;;;; 0AC3;GUJARATI VOWEL SIGN VOCALIC R;Mn;0;NSM;;;;;N;;;;; 0AC4;GUJARATI VOWEL SIGN VOCALIC RR;Mn;0;NSM;;;;;N;;;;; 0AC5;GUJARATI VOWEL SIGN CANDRA E;Mn;0;NSM;;;;;N;;;;; 0AC7;GUJARATI VOWEL SIGN E;Mn;0;NSM;;;;;N;;;;; 0AC8;GUJARATI VOWEL SIGN AI;Mn;0;NSM;;;;;N;;;;; 0AC9;GUJARATI VOWEL SIGN CANDRA O;Mc;0;L;;;;;N;;;;; 0ACB;GUJARATI VOWEL SIGN O;Mc;0;L;;;;;N;;;;; 0ACC;GUJARATI VOWEL SIGN AU;Mc;0;L;;;;;N;;;;; 0ACD;GUJARATI SIGN VIRAMA;Mn;9;NSM;;;;;N;;;;; 0AD0;GUJARATI OM;Lo;0;L;;;;;N;;;;; 0AE0;GUJARATI LETTER VOCALIC RR;Lo;0;L;;;;;N;;;;; 0AE1;GUJARATI LETTER VOCALIC LL;Lo;0;L;;;;;N;;;;; 0AE2;GUJARATI VOWEL SIGN VOCALIC L;Mn;0;NSM;;;;;N;;;;; 0AE3;GUJARATI VOWEL SIGN VOCALIC LL;Mn;0;NSM;;;;;N;;;;; 0AE6;GUJARATI DIGIT ZERO;Nd;0;L;;0;0;0;N;;;;; 0AE7;GUJARATI DIGIT ONE;Nd;0;L;;1;1;1;N;;;;; 0AE8;GUJARATI DIGIT TWO;Nd;0;L;;2;2;2;N;;;;; 0AE9;GUJARATI DIGIT THREE;Nd;0;L;;3;3;3;N;;;;; 0AEA;GUJARATI DIGIT FOUR;Nd;0;L;;4;4;4;N;;;;; 0AEB;GUJARATI DIGIT FIVE;Nd;0;L;;5;5;5;N;;;;; 0AEC;GUJARATI DIGIT SIX;Nd;0;L;;6;6;6;N;;;;; 0AED;GUJARATI DIGIT SEVEN;Nd;0;L;;7;7;7;N;;;;; 0AEE;GUJARATI DIGIT EIGHT;Nd;0;L;;8;8;8;N;;;;; 0AEF;GUJARATI DIGIT NINE;Nd;0;L;;9;9;9;N;;;;; 0AF0;GUJARATI ABBREVIATION SIGN;Po;0;L;;;;;N;;;;; 0AF1;GUJARATI RUPEE SIGN;Sc;0;ET;;;;;N;;;;; 0B01;ORIYA SIGN CANDRABINDU;Mn;0;NSM;;;;;N;;;;; 0B02;ORIYA SIGN ANUSVARA;Mc;0;L;;;;;N;;;;; 0B03;ORIYA SIGN VISARGA;Mc;0;L;;;;;N;;;;; 0B05;ORIYA LETTER A;Lo;0;L;;;;;N;;;;; 0B06;ORIYA LETTER AA;Lo;0;L;;;;;N;;;;; 0B07;ORIYA LETTER I;Lo;0;L;;;;;N;;;;; 0B08;ORIYA LETTER II;Lo;0;L;;;;;N;;;;; 0B09;ORIYA LETTER U;Lo;0;L;;;;;N;;;;; 0B0A;ORIYA LETTER UU;Lo;0;L;;;;;N;;;;; 0B0B;ORIYA LETTER VOCALIC R;Lo;0;L;;;;;N;;;;; 0B0C;ORIYA LETTER VOCALIC L;Lo;0;L;;;;;N;;;;; 0B0F;ORIYA LETTER E;Lo;0;L;;;;;N;;;;; 0B10;ORIYA LETTER AI;Lo;0;L;;;;;N;;;;; 0B13;ORIYA LETTER O;Lo;0;L;;;;;N;;;;; 0B14;ORIYA LETTER AU;Lo;0;L;;;;;N;;;;; 0B15;ORIYA LETTER KA;Lo;0;L;;;;;N;;;;; 0B16;ORIYA LETTER KHA;Lo;0;L;;;;;N;;;;; 0B17;ORIYA LETTER GA;Lo;0;L;;;;;N;;;;; 0B18;ORIYA LETTER GHA;Lo;0;L;;;;;N;;;;; 0B19;ORIYA LETTER NGA;Lo;0;L;;;;;N;;;;; 0B1A;ORIYA LETTER CA;Lo;0;L;;;;;N;;;;; 0B1B;ORIYA LETTER CHA;Lo;0;L;;;;;N;;;;; 0B1C;ORIYA LETTER JA;Lo;0;L;;;;;N;;;;; 0B1D;ORIYA LETTER JHA;Lo;0;L;;;;;N;;;;; 0B1E;ORIYA LETTER NYA;Lo;0;L;;;;;N;;;;; 0B1F;ORIYA LETTER TTA;Lo;0;L;;;;;N;;;;; 0B20;ORIYA LETTER TTHA;Lo;0;L;;;;;N;;;;; 0B21;ORIYA LETTER DDA;Lo;0;L;;;;;N;;;;; 0B22;ORIYA LETTER DDHA;Lo;0;L;;;;;N;;;;; 0B23;ORIYA LETTER NNA;Lo;0;L;;;;;N;;;;; 0B24;ORIYA LETTER TA;Lo;0;L;;;;;N;;;;; 0B25;ORIYA LETTER THA;Lo;0;L;;;;;N;;;;; 0B26;ORIYA LETTER DA;Lo;0;L;;;;;N;;;;; 0B27;ORIYA LETTER DHA;Lo;0;L;;;;;N;;;;; 0B28;ORIYA LETTER NA;Lo;0;L;;;;;N;;;;; 0B2A;ORIYA LETTER PA;Lo;0;L;;;;;N;;;;; 0B2B;ORIYA LETTER PHA;Lo;0;L;;;;;N;;;;; 0B2C;ORIYA LETTER BA;Lo;0;L;;;;;N;;;;; 0B2D;ORIYA LETTER BHA;Lo;0;L;;;;;N;;;;; 0B2E;ORIYA LETTER MA;Lo;0;L;;;;;N;;;;; 0B2F;ORIYA LETTER YA;Lo;0;L;;;;;N;;;;; 0B30;ORIYA LETTER RA;Lo;0;L;;;;;N;;;;; 0B32;ORIYA LETTER LA;Lo;0;L;;;;;N;;;;; 0B33;ORIYA LETTER LLA;Lo;0;L;;;;;N;;;;; 0B35;ORIYA LETTER VA;Lo;0;L;;;;;N;;;;; 0B36;ORIYA LETTER SHA;Lo;0;L;;;;;N;;;;; 0B37;ORIYA LETTER SSA;Lo;0;L;;;;;N;;;;; 0B38;ORIYA LETTER SA;Lo;0;L;;;;;N;;;;; 0B39;ORIYA LETTER HA;Lo;0;L;;;;;N;;;;; 0B3C;ORIYA SIGN NUKTA;Mn;7;NSM;;;;;N;;;;; 0B3D;ORIYA SIGN AVAGRAHA;Lo;0;L;;;;;N;;;;; 0B3E;ORIYA VOWEL SIGN AA;Mc;0;L;;;;;N;;;;; 0B3F;ORIYA VOWEL SIGN I;Mn;0;NSM;;;;;N;;;;; 0B40;ORIYA VOWEL SIGN II;Mc;0;L;;;;;N;;;;; 0B41;ORIYA VOWEL SIGN U;Mn;0;NSM;;;;;N;;;;; 0B42;ORIYA VOWEL SIGN UU;Mn;0;NSM;;;;;N;;;;; 0B43;ORIYA VOWEL SIGN VOCALIC R;Mn;0;NSM;;;;;N;;;;; 0B44;ORIYA VOWEL SIGN VOCALIC RR;Mn;0;NSM;;;;;N;;;;; 0B47;ORIYA VOWEL SIGN E;Mc;0;L;;;;;N;;;;; 0B48;ORIYA VOWEL SIGN AI;Mc;0;L;0B47 0B56;;;;N;;;;; 0B4B;ORIYA VOWEL SIGN O;Mc;0;L;0B47 0B3E;;;;N;;;;; 0B4C;ORIYA VOWEL SIGN AU;Mc;0;L;0B47 0B57;;;;N;;;;; 0B4D;ORIYA SIGN VIRAMA;Mn;9;NSM;;;;;N;;;;; 0B56;ORIYA AI LENGTH MARK;Mn;0;NSM;;;;;N;;;;; 0B57;ORIYA AU LENGTH MARK;Mc;0;L;;;;;N;;;;; 0B5C;ORIYA LETTER RRA;Lo;0;L;0B21 0B3C;;;;N;;;;; 0B5D;ORIYA LETTER RHA;Lo;0;L;0B22 0B3C;;;;N;;;;; 0B5F;ORIYA LETTER YYA;Lo;0;L;;;;;N;;;;; 0B60;ORIYA LETTER VOCALIC RR;Lo;0;L;;;;;N;;;;; 0B61;ORIYA LETTER VOCALIC LL;Lo;0;L;;;;;N;;;;; 0B62;ORIYA VOWEL SIGN VOCALIC L;Mn;0;NSM;;;;;N;;;;; 0B63;ORIYA VOWEL SIGN VOCALIC LL;Mn;0;NSM;;;;;N;;;;; 0B66;ORIYA DIGIT ZERO;Nd;0;L;;0;0;0;N;;;;; 0B67;ORIYA DIGIT ONE;Nd;0;L;;1;1;1;N;;;;; 0B68;ORIYA DIGIT TWO;Nd;0;L;;2;2;2;N;;;;; 0B69;ORIYA DIGIT THREE;Nd;0;L;;3;3;3;N;;;;; 0B6A;ORIYA DIGIT FOUR;Nd;0;L;;4;4;4;N;;;;; 0B6B;ORIYA DIGIT FIVE;Nd;0;L;;5;5;5;N;;;;; 0B6C;ORIYA DIGIT SIX;Nd;0;L;;6;6;6;N;;;;; 0B6D;ORIYA DIGIT SEVEN;Nd;0;L;;7;7;7;N;;;;; 0B6E;ORIYA DIGIT EIGHT;Nd;0;L;;8;8;8;N;;;;; 0B6F;ORIYA DIGIT NINE;Nd;0;L;;9;9;9;N;;;;; 0B70;ORIYA ISSHAR;So;0;L;;;;;N;;;;; 0B71;ORIYA LETTER WA;Lo;0;L;;;;;N;;;;; 0B72;ORIYA FRACTION ONE QUARTER;No;0;L;;;;1/4;N;;;;; 0B73;ORIYA FRACTION ONE HALF;No;0;L;;;;1/2;N;;;;; 0B74;ORIYA FRACTION THREE QUARTERS;No;0;L;;;;3/4;N;;;;; 0B75;ORIYA FRACTION ONE SIXTEENTH;No;0;L;;;;1/16;N;;;;; 0B76;ORIYA FRACTION ONE EIGHTH;No;0;L;;;;1/8;N;;;;; 0B77;ORIYA FRACTION THREE SIXTEENTHS;No;0;L;;;;3/16;N;;;;; 0B82;TAMIL SIGN ANUSVARA;Mn;0;NSM;;;;;N;;;;; 0B83;TAMIL SIGN VISARGA;Lo;0;L;;;;;N;;;;; 0B85;TAMIL LETTER A;Lo;0;L;;;;;N;;;;; 0B86;TAMIL LETTER AA;Lo;0;L;;;;;N;;;;; 0B87;TAMIL LETTER I;Lo;0;L;;;;;N;;;;; 0B88;TAMIL LETTER II;Lo;0;L;;;;;N;;;;; 0B89;TAMIL LETTER U;Lo;0;L;;;;;N;;;;; 0B8A;TAMIL LETTER UU;Lo;0;L;;;;;N;;;;; 0B8E;TAMIL LETTER E;Lo;0;L;;;;;N;;;;; 0B8F;TAMIL LETTER EE;Lo;0;L;;;;;N;;;;; 0B90;TAMIL LETTER AI;Lo;0;L;;;;;N;;;;; 0B92;TAMIL LETTER O;Lo;0;L;;;;;N;;;;; 0B93;TAMIL LETTER OO;Lo;0;L;;;;;N;;;;; 0B94;TAMIL LETTER AU;Lo;0;L;0B92 0BD7;;;;N;;;;; 0B95;TAMIL LETTER KA;Lo;0;L;;;;;N;;;;; 0B99;TAMIL LETTER NGA;Lo;0;L;;;;;N;;;;; 0B9A;TAMIL LETTER CA;Lo;0;L;;;;;N;;;;; 0B9C;TAMIL LETTER JA;Lo;0;L;;;;;N;;;;; 0B9E;TAMIL LETTER NYA;Lo;0;L;;;;;N;;;;; 0B9F;TAMIL LETTER TTA;Lo;0;L;;;;;N;;;;; 0BA3;TAMIL LETTER NNA;Lo;0;L;;;;;N;;;;; 0BA4;TAMIL LETTER TA;Lo;0;L;;;;;N;;;;; 0BA8;TAMIL LETTER NA;Lo;0;L;;;;;N;;;;; 0BA9;TAMIL LETTER NNNA;Lo;0;L;;;;;N;;;;; 0BAA;TAMIL LETTER PA;Lo;0;L;;;;;N;;;;; 0BAE;TAMIL LETTER MA;Lo;0;L;;;;;N;;;;; 0BAF;TAMIL LETTER YA;Lo;0;L;;;;;N;;;;; 0BB0;TAMIL LETTER RA;Lo;0;L;;;;;N;;;;; 0BB1;TAMIL LETTER RRA;Lo;0;L;;;;;N;;;;; 0BB2;TAMIL LETTER LA;Lo;0;L;;;;;N;;;;; 0BB3;TAMIL LETTER LLA;Lo;0;L;;;;;N;;;;; 0BB4;TAMIL LETTER LLLA;Lo;0;L;;;;;N;;;;; 0BB5;TAMIL LETTER VA;Lo;0;L;;;;;N;;;;; 0BB6;TAMIL LETTER SHA;Lo;0;L;;;;;N;;;;; 0BB7;TAMIL LETTER SSA;Lo;0;L;;;;;N;;;;; 0BB8;TAMIL LETTER SA;Lo;0;L;;;;;N;;;;; 0BB9;TAMIL LETTER HA;Lo;0;L;;;;;N;;;;; 0BBE;TAMIL VOWEL SIGN AA;Mc;0;L;;;;;N;;;;; 0BBF;TAMIL VOWEL SIGN I;Mc;0;L;;;;;N;;;;; 0BC0;TAMIL VOWEL SIGN II;Mn;0;NSM;;;;;N;;;;; 0BC1;TAMIL VOWEL SIGN U;Mc;0;L;;;;;N;;;;; 0BC2;TAMIL VOWEL SIGN UU;Mc;0;L;;;;;N;;;;; 0BC6;TAMIL VOWEL SIGN E;Mc;0;L;;;;;N;;;;; 0BC7;TAMIL VOWEL SIGN EE;Mc;0;L;;;;;N;;;;; 0BC8;TAMIL VOWEL SIGN AI;Mc;0;L;;;;;N;;;;; 0BCA;TAMIL VOWEL SIGN O;Mc;0;L;0BC6 0BBE;;;;N;;;;; 0BCB;TAMIL VOWEL SIGN OO;Mc;0;L;0BC7 0BBE;;;;N;;;;; 0BCC;TAMIL VOWEL SIGN AU;Mc;0;L;0BC6 0BD7;;;;N;;;;; 0BCD;TAMIL SIGN VIRAMA;Mn;9;NSM;;;;;N;;;;; 0BD0;TAMIL OM;Lo;0;L;;;;;N;;;;; 0BD7;TAMIL AU LENGTH MARK;Mc;0;L;;;;;N;;;;; 0BE6;TAMIL DIGIT ZERO;Nd;0;L;;0;0;0;N;;;;; 0BE7;TAMIL DIGIT ONE;Nd;0;L;;1;1;1;N;;;;; 0BE8;TAMIL DIGIT TWO;Nd;0;L;;2;2;2;N;;;;; 0BE9;TAMIL DIGIT THREE;Nd;0;L;;3;3;3;N;;;;; 0BEA;TAMIL DIGIT FOUR;Nd;0;L;;4;4;4;N;;;;; 0BEB;TAMIL DIGIT FIVE;Nd;0;L;;5;5;5;N;;;;; 0BEC;TAMIL DIGIT SIX;Nd;0;L;;6;6;6;N;;;;; 0BED;TAMIL DIGIT SEVEN;Nd;0;L;;7;7;7;N;;;;; 0BEE;TAMIL DIGIT EIGHT;Nd;0;L;;8;8;8;N;;;;; 0BEF;TAMIL DIGIT NINE;Nd;0;L;;9;9;9;N;;;;; 0BF0;TAMIL NUMBER TEN;No;0;L;;;;10;N;;;;; 0BF1;TAMIL NUMBER ONE HUNDRED;No;0;L;;;;100;N;;;;; 0BF2;TAMIL NUMBER ONE THOUSAND;No;0;L;;;;1000;N;;;;; 0BF3;TAMIL DAY SIGN;So;0;ON;;;;;N;;;;; 0BF4;TAMIL MONTH SIGN;So;0;ON;;;;;N;;;;; 0BF5;TAMIL YEAR SIGN;So;0;ON;;;;;N;;;;; 0BF6;TAMIL DEBIT SIGN;So;0;ON;;;;;N;;;;; 0BF7;TAMIL CREDIT SIGN;So;0;ON;;;;;N;;;;; 0BF8;TAMIL AS ABOVE SIGN;So;0;ON;;;;;N;;;;; 0BF9;TAMIL RUPEE SIGN;Sc;0;ET;;;;;N;;;;; 0BFA;TAMIL NUMBER SIGN;So;0;ON;;;;;N;;;;; 0C00;TELUGU SIGN COMBINING CANDRABINDU ABOVE;Mn;0;NSM;;;;;N;;;;; 0C01;TELUGU SIGN CANDRABINDU;Mc;0;L;;;;;N;;;;; 0C02;TELUGU SIGN ANUSVARA;Mc;0;L;;;;;N;;;;; 0C03;TELUGU SIGN VISARGA;Mc;0;L;;;;;N;;;;; 0C05;TELUGU LETTER A;Lo;0;L;;;;;N;;;;; 0C06;TELUGU LETTER AA;Lo;0;L;;;;;N;;;;; 0C07;TELUGU LETTER I;Lo;0;L;;;;;N;;;;; 0C08;TELUGU LETTER II;Lo;0;L;;;;;N;;;;; 0C09;TELUGU LETTER U;Lo;0;L;;;;;N;;;;; 0C0A;TELUGU LETTER UU;Lo;0;L;;;;;N;;;;; 0C0B;TELUGU LETTER VOCALIC R;Lo;0;L;;;;;N;;;;; 0C0C;TELUGU LETTER VOCALIC L;Lo;0;L;;;;;N;;;;; 0C0E;TELUGU LETTER E;Lo;0;L;;;;;N;;;;; 0C0F;TELUGU LETTER EE;Lo;0;L;;;;;N;;;;; 0C10;TELUGU LETTER AI;Lo;0;L;;;;;N;;;;; 0C12;TELUGU LETTER O;Lo;0;L;;;;;N;;;;; 0C13;TELUGU LETTER OO;Lo;0;L;;;;;N;;;;; 0C14;TELUGU LETTER AU;Lo;0;L;;;;;N;;;;; 0C15;TELUGU LETTER KA;Lo;0;L;;;;;N;;;;; 0C16;TELUGU LETTER KHA;Lo;0;L;;;;;N;;;;; 0C17;TELUGU LETTER GA;Lo;0;L;;;;;N;;;;; 0C18;TELUGU LETTER GHA;Lo;0;L;;;;;N;;;;; 0C19;TELUGU LETTER NGA;Lo;0;L;;;;;N;;;;; 0C1A;TELUGU LETTER CA;Lo;0;L;;;;;N;;;;; 0C1B;TELUGU LETTER CHA;Lo;0;L;;;;;N;;;;; 0C1C;TELUGU LETTER JA;Lo;0;L;;;;;N;;;;; 0C1D;TELUGU LETTER JHA;Lo;0;L;;;;;N;;;;; 0C1E;TELUGU LETTER NYA;Lo;0;L;;;;;N;;;;; 0C1F;TELUGU LETTER TTA;Lo;0;L;;;;;N;;;;; 0C20;TELUGU LETTER TTHA;Lo;0;L;;;;;N;;;;; 0C21;TELUGU LETTER DDA;Lo;0;L;;;;;N;;;;; 0C22;TELUGU LETTER DDHA;Lo;0;L;;;;;N;;;;; 0C23;TELUGU LETTER NNA;Lo;0;L;;;;;N;;;;; 0C24;TELUGU LETTER TA;Lo;0;L;;;;;N;;;;; 0C25;TELUGU LETTER THA;Lo;0;L;;;;;N;;;;; 0C26;TELUGU LETTER DA;Lo;0;L;;;;;N;;;;; 0C27;TELUGU LETTER DHA;Lo;0;L;;;;;N;;;;; 0C28;TELUGU LETTER NA;Lo;0;L;;;;;N;;;;; 0C2A;TELUGU LETTER PA;Lo;0;L;;;;;N;;;;; 0C2B;TELUGU LETTER PHA;Lo;0;L;;;;;N;;;;; 0C2C;TELUGU LETTER BA;Lo;0;L;;;;;N;;;;; 0C2D;TELUGU LETTER BHA;Lo;0;L;;;;;N;;;;; 0C2E;TELUGU LETTER MA;Lo;0;L;;;;;N;;;;; 0C2F;TELUGU LETTER YA;Lo;0;L;;;;;N;;;;; 0C30;TELUGU LETTER RA;Lo;0;L;;;;;N;;;;; 0C31;TELUGU LETTER RRA;Lo;0;L;;;;;N;;;;; 0C32;TELUGU LETTER LA;Lo;0;L;;;;;N;;;;; 0C33;TELUGU LETTER LLA;Lo;0;L;;;;;N;;;;; 0C34;TELUGU LETTER LLLA;Lo;0;L;;;;;N;;;;; 0C35;TELUGU LETTER VA;Lo;0;L;;;;;N;;;;; 0C36;TELUGU LETTER SHA;Lo;0;L;;;;;N;;;;; 0C37;TELUGU LETTER SSA;Lo;0;L;;;;;N;;;;; 0C38;TELUGU LETTER SA;Lo;0;L;;;;;N;;;;; 0C39;TELUGU LETTER HA;Lo;0;L;;;;;N;;;;; 0C3D;TELUGU SIGN AVAGRAHA;Lo;0;L;;;;;N;;;;; 0C3E;TELUGU VOWEL SIGN AA;Mn;0;NSM;;;;;N;;;;; 0C3F;TELUGU VOWEL SIGN I;Mn;0;NSM;;;;;N;;;;; 0C40;TELUGU VOWEL SIGN II;Mn;0;NSM;;;;;N;;;;; 0C41;TELUGU VOWEL SIGN U;Mc;0;L;;;;;N;;;;; 0C42;TELUGU VOWEL SIGN UU;Mc;0;L;;;;;N;;;;; 0C43;TELUGU VOWEL SIGN VOCALIC R;Mc;0;L;;;;;N;;;;; 0C44;TELUGU VOWEL SIGN VOCALIC RR;Mc;0;L;;;;;N;;;;; 0C46;TELUGU VOWEL SIGN E;Mn;0;NSM;;;;;N;;;;; 0C47;TELUGU VOWEL SIGN EE;Mn;0;NSM;;;;;N;;;;; 0C48;TELUGU VOWEL SIGN AI;Mn;0;NSM;0C46 0C56;;;;N;;;;; 0C4A;TELUGU VOWEL SIGN O;Mn;0;NSM;;;;;N;;;;; 0C4B;TELUGU VOWEL SIGN OO;Mn;0;NSM;;;;;N;;;;; 0C4C;TELUGU VOWEL SIGN AU;Mn;0;NSM;;;;;N;;;;; 0C4D;TELUGU SIGN VIRAMA;Mn;9;NSM;;;;;N;;;;; 0C55;TELUGU LENGTH MARK;Mn;84;NSM;;;;;N;;;;; 0C56;TELUGU AI LENGTH MARK;Mn;91;NSM;;;;;N;;;;; 0C58;TELUGU LETTER TSA;Lo;0;L;;;;;N;;;;; 0C59;TELUGU LETTER DZA;Lo;0;L;;;;;N;;;;; 0C60;TELUGU LETTER VOCALIC RR;Lo;0;L;;;;;N;;;;; 0C61;TELUGU LETTER VOCALIC LL;Lo;0;L;;;;;N;;;;; 0C62;TELUGU VOWEL SIGN VOCALIC L;Mn;0;NSM;;;;;N;;;;; 0C63;TELUGU VOWEL SIGN VOCALIC LL;Mn;0;NSM;;;;;N;;;;; 0C66;TELUGU DIGIT ZERO;Nd;0;L;;0;0;0;N;;;;; 0C67;TELUGU DIGIT ONE;Nd;0;L;;1;1;1;N;;;;; 0C68;TELUGU DIGIT TWO;Nd;0;L;;2;2;2;N;;;;; 0C69;TELUGU DIGIT THREE;Nd;0;L;;3;3;3;N;;;;; 0C6A;TELUGU DIGIT FOUR;Nd;0;L;;4;4;4;N;;;;; 0C6B;TELUGU DIGIT FIVE;Nd;0;L;;5;5;5;N;;;;; 0C6C;TELUGU DIGIT SIX;Nd;0;L;;6;6;6;N;;;;; 0C6D;TELUGU DIGIT SEVEN;Nd;0;L;;7;7;7;N;;;;; 0C6E;TELUGU DIGIT EIGHT;Nd;0;L;;8;8;8;N;;;;; 0C6F;TELUGU DIGIT NINE;Nd;0;L;;9;9;9;N;;;;; 0C78;TELUGU FRACTION DIGIT ZERO FOR ODD POWERS OF FOUR;No;0;ON;;;;0;N;;;;; 0C79;TELUGU FRACTION DIGIT ONE FOR ODD POWERS OF FOUR;No;0;ON;;;;1;N;;;;; 0C7A;TELUGU FRACTION DIGIT TWO FOR ODD POWERS OF FOUR;No;0;ON;;;;2;N;;;;; 0C7B;TELUGU FRACTION DIGIT THREE FOR ODD POWERS OF FOUR;No;0;ON;;;;3;N;;;;; 0C7C;TELUGU FRACTION DIGIT ONE FOR EVEN POWERS OF FOUR;No;0;ON;;;;1;N;;;;; 0C7D;TELUGU FRACTION DIGIT TWO FOR EVEN POWERS OF FOUR;No;0;ON;;;;2;N;;;;; 0C7E;TELUGU FRACTION DIGIT THREE FOR EVEN POWERS OF FOUR;No;0;ON;;;;3;N;;;;; 0C7F;TELUGU SIGN TUUMU;So;0;L;;;;;N;;;;; 0C81;KANNADA SIGN CANDRABINDU;Mn;0;NSM;;;;;N;;;;; 0C82;KANNADA SIGN ANUSVARA;Mc;0;L;;;;;N;;;;; 0C83;KANNADA SIGN VISARGA;Mc;0;L;;;;;N;;;;; 0C85;KANNADA LETTER A;Lo;0;L;;;;;N;;;;; 0C86;KANNADA LETTER AA;Lo;0;L;;;;;N;;;;; 0C87;KANNADA LETTER I;Lo;0;L;;;;;N;;;;; 0C88;KANNADA LETTER II;Lo;0;L;;;;;N;;;;; 0C89;KANNADA LETTER U;Lo;0;L;;;;;N;;;;; 0C8A;KANNADA LETTER UU;Lo;0;L;;;;;N;;;;; 0C8B;KANNADA LETTER VOCALIC R;Lo;0;L;;;;;N;;;;; 0C8C;KANNADA LETTER VOCALIC L;Lo;0;L;;;;;N;;;;; 0C8E;KANNADA LETTER E;Lo;0;L;;;;;N;;;;; 0C8F;KANNADA LETTER EE;Lo;0;L;;;;;N;;;;; 0C90;KANNADA LETTER AI;Lo;0;L;;;;;N;;;;; 0C92;KANNADA LETTER O;Lo;0;L;;;;;N;;;;; 0C93;KANNADA LETTER OO;Lo;0;L;;;;;N;;;;; 0C94;KANNADA LETTER AU;Lo;0;L;;;;;N;;;;; 0C95;KANNADA LETTER KA;Lo;0;L;;;;;N;;;;; 0C96;KANNADA LETTER KHA;Lo;0;L;;;;;N;;;;; 0C97;KANNADA LETTER GA;Lo;0;L;;;;;N;;;;; 0C98;KANNADA LETTER GHA;Lo;0;L;;;;;N;;;;; 0C99;KANNADA LETTER NGA;Lo;0;L;;;;;N;;;;; 0C9A;KANNADA LETTER CA;Lo;0;L;;;;;N;;;;; 0C9B;KANNADA LETTER CHA;Lo;0;L;;;;;N;;;;; 0C9C;KANNADA LETTER JA;Lo;0;L;;;;;N;;;;; 0C9D;KANNADA LETTER JHA;Lo;0;L;;;;;N;;;;; 0C9E;KANNADA LETTER NYA;Lo;0;L;;;;;N;;;;; 0C9F;KANNADA LETTER TTA;Lo;0;L;;;;;N;;;;; 0CA0;KANNADA LETTER TTHA;Lo;0;L;;;;;N;;;;; 0CA1;KANNADA LETTER DDA;Lo;0;L;;;;;N;;;;; 0CA2;KANNADA LETTER DDHA;Lo;0;L;;;;;N;;;;; 0CA3;KANNADA LETTER NNA;Lo;0;L;;;;;N;;;;; 0CA4;KANNADA LETTER TA;Lo;0;L;;;;;N;;;;; 0CA5;KANNADA LETTER THA;Lo;0;L;;;;;N;;;;; 0CA6;KANNADA LETTER DA;Lo;0;L;;;;;N;;;;; 0CA7;KANNADA LETTER DHA;Lo;0;L;;;;;N;;;;; 0CA8;KANNADA LETTER NA;Lo;0;L;;;;;N;;;;; 0CAA;KANNADA LETTER PA;Lo;0;L;;;;;N;;;;; 0CAB;KANNADA LETTER PHA;Lo;0;L;;;;;N;;;;; 0CAC;KANNADA LETTER BA;Lo;0;L;;;;;N;;;;; 0CAD;KANNADA LETTER BHA;Lo;0;L;;;;;N;;;;; 0CAE;KANNADA LETTER MA;Lo;0;L;;;;;N;;;;; 0CAF;KANNADA LETTER YA;Lo;0;L;;;;;N;;;;; 0CB0;KANNADA LETTER RA;Lo;0;L;;;;;N;;;;; 0CB1;KANNADA LETTER RRA;Lo;0;L;;;;;N;;;;; 0CB2;KANNADA LETTER LA;Lo;0;L;;;;;N;;;;; 0CB3;KANNADA LETTER LLA;Lo;0;L;;;;;N;;;;; 0CB5;KANNADA LETTER VA;Lo;0;L;;;;;N;;;;; 0CB6;KANNADA LETTER SHA;Lo;0;L;;;;;N;;;;; 0CB7;KANNADA LETTER SSA;Lo;0;L;;;;;N;;;;; 0CB8;KANNADA LETTER SA;Lo;0;L;;;;;N;;;;; 0CB9;KANNADA LETTER HA;Lo;0;L;;;;;N;;;;; 0CBC;KANNADA SIGN NUKTA;Mn;7;NSM;;;;;N;;;;; 0CBD;KANNADA SIGN AVAGRAHA;Lo;0;L;;;;;N;;;;; 0CBE;KANNADA VOWEL SIGN AA;Mc;0;L;;;;;N;;;;; 0CBF;KANNADA VOWEL SIGN I;Mn;0;L;;;;;N;;;;; 0CC0;KANNADA VOWEL SIGN II;Mc;0;L;0CBF 0CD5;;;;N;;;;; 0CC1;KANNADA VOWEL SIGN U;Mc;0;L;;;;;N;;;;; 0CC2;KANNADA VOWEL SIGN UU;Mc;0;L;;;;;N;;;;; 0CC3;KANNADA VOWEL SIGN VOCALIC R;Mc;0;L;;;;;N;;;;; 0CC4;KANNADA VOWEL SIGN VOCALIC RR;Mc;0;L;;;;;N;;;;; 0CC6;KANNADA VOWEL SIGN E;Mn;0;L;;;;;N;;;;; 0CC7;KANNADA VOWEL SIGN EE;Mc;0;L;0CC6 0CD5;;;;N;;;;; 0CC8;KANNADA VOWEL SIGN AI;Mc;0;L;0CC6 0CD6;;;;N;;;;; 0CCA;KANNADA VOWEL SIGN O;Mc;0;L;0CC6 0CC2;;;;N;;;;; 0CCB;KANNADA VOWEL SIGN OO;Mc;0;L;0CCA 0CD5;;;;N;;;;; 0CCC;KANNADA VOWEL SIGN AU;Mn;0;NSM;;;;;N;;;;; 0CCD;KANNADA SIGN VIRAMA;Mn;9;NSM;;;;;N;;;;; 0CD5;KANNADA LENGTH MARK;Mc;0;L;;;;;N;;;;; 0CD6;KANNADA AI LENGTH MARK;Mc;0;L;;;;;N;;;;; 0CDE;KANNADA LETTER FA;Lo;0;L;;;;;N;;;;; 0CE0;KANNADA LETTER VOCALIC RR;Lo;0;L;;;;;N;;;;; 0CE1;KANNADA LETTER VOCALIC LL;Lo;0;L;;;;;N;;;;; 0CE2;KANNADA VOWEL SIGN VOCALIC L;Mn;0;NSM;;;;;N;;;;; 0CE3;KANNADA VOWEL SIGN VOCALIC LL;Mn;0;NSM;;;;;N;;;;; 0CE6;KANNADA DIGIT ZERO;Nd;0;L;;0;0;0;N;;;;; 0CE7;KANNADA DIGIT ONE;Nd;0;L;;1;1;1;N;;;;; 0CE8;KANNADA DIGIT TWO;Nd;0;L;;2;2;2;N;;;;; 0CE9;KANNADA DIGIT THREE;Nd;0;L;;3;3;3;N;;;;; 0CEA;KANNADA DIGIT FOUR;Nd;0;L;;4;4;4;N;;;;; 0CEB;KANNADA DIGIT FIVE;Nd;0;L;;5;5;5;N;;;;; 0CEC;KANNADA DIGIT SIX;Nd;0;L;;6;6;6;N;;;;; 0CED;KANNADA DIGIT SEVEN;Nd;0;L;;7;7;7;N;;;;; 0CEE;KANNADA DIGIT EIGHT;Nd;0;L;;8;8;8;N;;;;; 0CEF;KANNADA DIGIT NINE;Nd;0;L;;9;9;9;N;;;;; 0CF1;KANNADA SIGN JIHVAMULIYA;Lo;0;L;;;;;N;;;;; 0CF2;KANNADA SIGN UPADHMANIYA;Lo;0;L;;;;;N;;;;; 0D01;MALAYALAM SIGN CANDRABINDU;Mn;0;NSM;;;;;N;;;;; 0D02;MALAYALAM SIGN ANUSVARA;Mc;0;L;;;;;N;;;;; 0D03;MALAYALAM SIGN VISARGA;Mc;0;L;;;;;N;;;;; 0D05;MALAYALAM LETTER A;Lo;0;L;;;;;N;;;;; 0D06;MALAYALAM LETTER AA;Lo;0;L;;;;;N;;;;; 0D07;MALAYALAM LETTER I;Lo;0;L;;;;;N;;;;; 0D08;MALAYALAM LETTER II;Lo;0;L;;;;;N;;;;; 0D09;MALAYALAM LETTER U;Lo;0;L;;;;;N;;;;; 0D0A;MALAYALAM LETTER UU;Lo;0;L;;;;;N;;;;; 0D0B;MALAYALAM LETTER VOCALIC R;Lo;0;L;;;;;N;;;;; 0D0C;MALAYALAM LETTER VOCALIC L;Lo;0;L;;;;;N;;;;; 0D0E;MALAYALAM LETTER E;Lo;0;L;;;;;N;;;;; 0D0F;MALAYALAM LETTER EE;Lo;0;L;;;;;N;;;;; 0D10;MALAYALAM LETTER AI;Lo;0;L;;;;;N;;;;; 0D12;MALAYALAM LETTER O;Lo;0;L;;;;;N;;;;; 0D13;MALAYALAM LETTER OO;Lo;0;L;;;;;N;;;;; 0D14;MALAYALAM LETTER AU;Lo;0;L;;;;;N;;;;; 0D15;MALAYALAM LETTER KA;Lo;0;L;;;;;N;;;;; 0D16;MALAYALAM LETTER KHA;Lo;0;L;;;;;N;;;;; 0D17;MALAYALAM LETTER GA;Lo;0;L;;;;;N;;;;; 0D18;MALAYALAM LETTER GHA;Lo;0;L;;;;;N;;;;; 0D19;MALAYALAM LETTER NGA;Lo;0;L;;;;;N;;;;; 0D1A;MALAYALAM LETTER CA;Lo;0;L;;;;;N;;;;; 0D1B;MALAYALAM LETTER CHA;Lo;0;L;;;;;N;;;;; 0D1C;MALAYALAM LETTER JA;Lo;0;L;;;;;N;;;;; 0D1D;MALAYALAM LETTER JHA;Lo;0;L;;;;;N;;;;; 0D1E;MALAYALAM LETTER NYA;Lo;0;L;;;;;N;;;;; 0D1F;MALAYALAM LETTER TTA;Lo;0;L;;;;;N;;;;; 0D20;MALAYALAM LETTER TTHA;Lo;0;L;;;;;N;;;;; 0D21;MALAYALAM LETTER DDA;Lo;0;L;;;;;N;;;;; 0D22;MALAYALAM LETTER DDHA;Lo;0;L;;;;;N;;;;; 0D23;MALAYALAM LETTER NNA;Lo;0;L;;;;;N;;;;; 0D24;MALAYALAM LETTER TA;Lo;0;L;;;;;N;;;;; 0D25;MALAYALAM LETTER THA;Lo;0;L;;;;;N;;;;; 0D26;MALAYALAM LETTER DA;Lo;0;L;;;;;N;;;;; 0D27;MALAYALAM LETTER DHA;Lo;0;L;;;;;N;;;;; 0D28;MALAYALAM LETTER NA;Lo;0;L;;;;;N;;;;; 0D29;MALAYALAM LETTER NNNA;Lo;0;L;;;;;N;;;;; 0D2A;MALAYALAM LETTER PA;Lo;0;L;;;;;N;;;;; 0D2B;MALAYALAM LETTER PHA;Lo;0;L;;;;;N;;;;; 0D2C;MALAYALAM LETTER BA;Lo;0;L;;;;;N;;;;; 0D2D;MALAYALAM LETTER BHA;Lo;0;L;;;;;N;;;;; 0D2E;MALAYALAM LETTER MA;Lo;0;L;;;;;N;;;;; 0D2F;MALAYALAM LETTER YA;Lo;0;L;;;;;N;;;;; 0D30;MALAYALAM LETTER RA;Lo;0;L;;;;;N;;;;; 0D31;MALAYALAM LETTER RRA;Lo;0;L;;;;;N;;;;; 0D32;MALAYALAM LETTER LA;Lo;0;L;;;;;N;;;;; 0D33;MALAYALAM LETTER LLA;Lo;0;L;;;;;N;;;;; 0D34;MALAYALAM LETTER LLLA;Lo;0;L;;;;;N;;;;; 0D35;MALAYALAM LETTER VA;Lo;0;L;;;;;N;;;;; 0D36;MALAYALAM LETTER SHA;Lo;0;L;;;;;N;;;;; 0D37;MALAYALAM LETTER SSA;Lo;0;L;;;;;N;;;;; 0D38;MALAYALAM LETTER SA;Lo;0;L;;;;;N;;;;; 0D39;MALAYALAM LETTER HA;Lo;0;L;;;;;N;;;;; 0D3A;MALAYALAM LETTER TTTA;Lo;0;L;;;;;N;;;;; 0D3D;MALAYALAM SIGN AVAGRAHA;Lo;0;L;;;;;N;;;;; 0D3E;MALAYALAM VOWEL SIGN AA;Mc;0;L;;;;;N;;;;; 0D3F;MALAYALAM VOWEL SIGN I;Mc;0;L;;;;;N;;;;; 0D40;MALAYALAM VOWEL SIGN II;Mc;0;L;;;;;N;;;;; 0D41;MALAYALAM VOWEL SIGN U;Mn;0;NSM;;;;;N;;;;; 0D42;MALAYALAM VOWEL SIGN UU;Mn;0;NSM;;;;;N;;;;; 0D43;MALAYALAM VOWEL SIGN VOCALIC R;Mn;0;NSM;;;;;N;;;;; 0D44;MALAYALAM VOWEL SIGN VOCALIC RR;Mn;0;NSM;;;;;N;;;;; 0D46;MALAYALAM VOWEL SIGN E;Mc;0;L;;;;;N;;;;; 0D47;MALAYALAM VOWEL SIGN EE;Mc;0;L;;;;;N;;;;; 0D48;MALAYALAM VOWEL SIGN AI;Mc;0;L;;;;;N;;;;; 0D4A;MALAYALAM VOWEL SIGN O;Mc;0;L;0D46 0D3E;;;;N;;;;; 0D4B;MALAYALAM VOWEL SIGN OO;Mc;0;L;0D47 0D3E;;;;N;;;;; 0D4C;MALAYALAM VOWEL SIGN AU;Mc;0;L;0D46 0D57;;;;N;;;;; 0D4D;MALAYALAM SIGN VIRAMA;Mn;9;NSM;;;;;N;;;;; 0D4E;MALAYALAM LETTER DOT REPH;Lo;0;L;;;;;N;;;;; 0D57;MALAYALAM AU LENGTH MARK;Mc;0;L;;;;;N;;;;; 0D60;MALAYALAM LETTER VOCALIC RR;Lo;0;L;;;;;N;;;;; 0D61;MALAYALAM LETTER VOCALIC LL;Lo;0;L;;;;;N;;;;; 0D62;MALAYALAM VOWEL SIGN VOCALIC L;Mn;0;NSM;;;;;N;;;;; 0D63;MALAYALAM VOWEL SIGN VOCALIC LL;Mn;0;NSM;;;;;N;;;;; 0D66;MALAYALAM DIGIT ZERO;Nd;0;L;;0;0;0;N;;;;; 0D67;MALAYALAM DIGIT ONE;Nd;0;L;;1;1;1;N;;;;; 0D68;MALAYALAM DIGIT TWO;Nd;0;L;;2;2;2;N;;;;; 0D69;MALAYALAM DIGIT THREE;Nd;0;L;;3;3;3;N;;;;; 0D6A;MALAYALAM DIGIT FOUR;Nd;0;L;;4;4;4;N;;;;; 0D6B;MALAYALAM DIGIT FIVE;Nd;0;L;;5;5;5;N;;;;; 0D6C;MALAYALAM DIGIT SIX;Nd;0;L;;6;6;6;N;;;;; 0D6D;MALAYALAM DIGIT SEVEN;Nd;0;L;;7;7;7;N;;;;; 0D6E;MALAYALAM DIGIT EIGHT;Nd;0;L;;8;8;8;N;;;;; 0D6F;MALAYALAM DIGIT NINE;Nd;0;L;;9;9;9;N;;;;; 0D70;MALAYALAM NUMBER TEN;No;0;L;;;;10;N;;;;; 0D71;MALAYALAM NUMBER ONE HUNDRED;No;0;L;;;;100;N;;;;; 0D72;MALAYALAM NUMBER ONE THOUSAND;No;0;L;;;;1000;N;;;;; 0D73;MALAYALAM FRACTION ONE QUARTER;No;0;L;;;;1/4;N;;;;; 0D74;MALAYALAM FRACTION ONE HALF;No;0;L;;;;1/2;N;;;;; 0D75;MALAYALAM FRACTION THREE QUARTERS;No;0;L;;;;3/4;N;;;;; 0D79;MALAYALAM DATE MARK;So;0;L;;;;;N;;;;; 0D7A;MALAYALAM LETTER CHILLU NN;Lo;0;L;;;;;N;;;;; 0D7B;MALAYALAM LETTER CHILLU N;Lo;0;L;;;;;N;;;;; 0D7C;MALAYALAM LETTER CHILLU RR;Lo;0;L;;;;;N;;;;; 0D7D;MALAYALAM LETTER CHILLU L;Lo;0;L;;;;;N;;;;; 0D7E;MALAYALAM LETTER CHILLU LL;Lo;0;L;;;;;N;;;;; 0D7F;MALAYALAM LETTER CHILLU K;Lo;0;L;;;;;N;;;;; 0D82;SINHALA SIGN ANUSVARAYA;Mc;0;L;;;;;N;;;;; 0D83;SINHALA SIGN VISARGAYA;Mc;0;L;;;;;N;;;;; 0D85;SINHALA LETTER AYANNA;Lo;0;L;;;;;N;;;;; 0D86;SINHALA LETTER AAYANNA;Lo;0;L;;;;;N;;;;; 0D87;SINHALA LETTER AEYANNA;Lo;0;L;;;;;N;;;;; 0D88;SINHALA LETTER AEEYANNA;Lo;0;L;;;;;N;;;;; 0D89;SINHALA LETTER IYANNA;Lo;0;L;;;;;N;;;;; 0D8A;SINHALA LETTER IIYANNA;Lo;0;L;;;;;N;;;;; 0D8B;SINHALA LETTER UYANNA;Lo;0;L;;;;;N;;;;; 0D8C;SINHALA LETTER UUYANNA;Lo;0;L;;;;;N;;;;; 0D8D;SINHALA LETTER IRUYANNA;Lo;0;L;;;;;N;;;;; 0D8E;SINHALA LETTER IRUUYANNA;Lo;0;L;;;;;N;;;;; 0D8F;SINHALA LETTER ILUYANNA;Lo;0;L;;;;;N;;;;; 0D90;SINHALA LETTER ILUUYANNA;Lo;0;L;;;;;N;;;;; 0D91;SINHALA LETTER EYANNA;Lo;0;L;;;;;N;;;;; 0D92;SINHALA LETTER EEYANNA;Lo;0;L;;;;;N;;;;; 0D93;SINHALA LETTER AIYANNA;Lo;0;L;;;;;N;;;;; 0D94;SINHALA LETTER OYANNA;Lo;0;L;;;;;N;;;;; 0D95;SINHALA LETTER OOYANNA;Lo;0;L;;;;;N;;;;; 0D96;SINHALA LETTER AUYANNA;Lo;0;L;;;;;N;;;;; 0D9A;SINHALA LETTER ALPAPRAANA KAYANNA;Lo;0;L;;;;;N;;;;; 0D9B;SINHALA LETTER MAHAAPRAANA KAYANNA;Lo;0;L;;;;;N;;;;; 0D9C;SINHALA LETTER ALPAPRAANA GAYANNA;Lo;0;L;;;;;N;;;;; 0D9D;SINHALA LETTER MAHAAPRAANA GAYANNA;Lo;0;L;;;;;N;;;;; 0D9E;SINHALA LETTER KANTAJA NAASIKYAYA;Lo;0;L;;;;;N;;;;; 0D9F;SINHALA LETTER SANYAKA GAYANNA;Lo;0;L;;;;;N;;;;; 0DA0;SINHALA LETTER ALPAPRAANA CAYANNA;Lo;0;L;;;;;N;;;;; 0DA1;SINHALA LETTER MAHAAPRAANA CAYANNA;Lo;0;L;;;;;N;;;;; 0DA2;SINHALA LETTER ALPAPRAANA JAYANNA;Lo;0;L;;;;;N;;;;; 0DA3;SINHALA LETTER MAHAAPRAANA JAYANNA;Lo;0;L;;;;;N;;;;; 0DA4;SINHALA LETTER TAALUJA NAASIKYAYA;Lo;0;L;;;;;N;;;;; 0DA5;SINHALA LETTER TAALUJA SANYOOGA NAAKSIKYAYA;Lo;0;L;;;;;N;;;;; 0DA6;SINHALA LETTER SANYAKA JAYANNA;Lo;0;L;;;;;N;;;;; 0DA7;SINHALA LETTER ALPAPRAANA TTAYANNA;Lo;0;L;;;;;N;;;;; 0DA8;SINHALA LETTER MAHAAPRAANA TTAYANNA;Lo;0;L;;;;;N;;;;; 0DA9;SINHALA LETTER ALPAPRAANA DDAYANNA;Lo;0;L;;;;;N;;;;; 0DAA;SINHALA LETTER MAHAAPRAANA DDAYANNA;Lo;0;L;;;;;N;;;;; 0DAB;SINHALA LETTER MUURDHAJA NAYANNA;Lo;0;L;;;;;N;;;;; 0DAC;SINHALA LETTER SANYAKA DDAYANNA;Lo;0;L;;;;;N;;;;; 0DAD;SINHALA LETTER ALPAPRAANA TAYANNA;Lo;0;L;;;;;N;;;;; 0DAE;SINHALA LETTER MAHAAPRAANA TAYANNA;Lo;0;L;;;;;N;;;;; 0DAF;SINHALA LETTER ALPAPRAANA DAYANNA;Lo;0;L;;;;;N;;;;; 0DB0;SINHALA LETTER MAHAAPRAANA DAYANNA;Lo;0;L;;;;;N;;;;; 0DB1;SINHALA LETTER DANTAJA NAYANNA;Lo;0;L;;;;;N;;;;; 0DB3;SINHALA LETTER SANYAKA DAYANNA;Lo;0;L;;;;;N;;;;; 0DB4;SINHALA LETTER ALPAPRAANA PAYANNA;Lo;0;L;;;;;N;;;;; 0DB5;SINHALA LETTER MAHAAPRAANA PAYANNA;Lo;0;L;;;;;N;;;;; 0DB6;SINHALA LETTER ALPAPRAANA BAYANNA;Lo;0;L;;;;;N;;;;; 0DB7;SINHALA LETTER MAHAAPRAANA BAYANNA;Lo;0;L;;;;;N;;;;; 0DB8;SINHALA LETTER MAYANNA;Lo;0;L;;;;;N;;;;; 0DB9;SINHALA LETTER AMBA BAYANNA;Lo;0;L;;;;;N;;;;; 0DBA;SINHALA LETTER YAYANNA;Lo;0;L;;;;;N;;;;; 0DBB;SINHALA LETTER RAYANNA;Lo;0;L;;;;;N;;;;; 0DBD;SINHALA LETTER DANTAJA LAYANNA;Lo;0;L;;;;;N;;;;; 0DC0;SINHALA LETTER VAYANNA;Lo;0;L;;;;;N;;;;; 0DC1;SINHALA LETTER TAALUJA SAYANNA;Lo;0;L;;;;;N;;;;; 0DC2;SINHALA LETTER MUURDHAJA SAYANNA;Lo;0;L;;;;;N;;;;; 0DC3;SINHALA LETTER DANTAJA SAYANNA;Lo;0;L;;;;;N;;;;; 0DC4;SINHALA LETTER HAYANNA;Lo;0;L;;;;;N;;;;; 0DC5;SINHALA LETTER MUURDHAJA LAYANNA;Lo;0;L;;;;;N;;;;; 0DC6;SINHALA LETTER FAYANNA;Lo;0;L;;;;;N;;;;; 0DCA;SINHALA SIGN AL-LAKUNA;Mn;9;NSM;;;;;N;;;;; 0DCF;SINHALA VOWEL SIGN AELA-PILLA;Mc;0;L;;;;;N;;;;; 0DD0;SINHALA VOWEL SIGN KETTI AEDA-PILLA;Mc;0;L;;;;;N;;;;; 0DD1;SINHALA VOWEL SIGN DIGA AEDA-PILLA;Mc;0;L;;;;;N;;;;; 0DD2;SINHALA VOWEL SIGN KETTI IS-PILLA;Mn;0;NSM;;;;;N;;;;; 0DD3;SINHALA VOWEL SIGN DIGA IS-PILLA;Mn;0;NSM;;;;;N;;;;; 0DD4;SINHALA VOWEL SIGN KETTI PAA-PILLA;Mn;0;NSM;;;;;N;;;;; 0DD6;SINHALA VOWEL SIGN DIGA PAA-PILLA;Mn;0;NSM;;;;;N;;;;; 0DD8;SINHALA VOWEL SIGN GAETTA-PILLA;Mc;0;L;;;;;N;;;;; 0DD9;SINHALA VOWEL SIGN KOMBUVA;Mc;0;L;;;;;N;;;;; 0DDA;SINHALA VOWEL SIGN DIGA KOMBUVA;Mc;0;L;0DD9 0DCA;;;;N;;;;; 0DDB;SINHALA VOWEL SIGN KOMBU DEKA;Mc;0;L;;;;;N;;;;; 0DDC;SINHALA VOWEL SIGN KOMBUVA HAA AELA-PILLA;Mc;0;L;0DD9 0DCF;;;;N;;;;; 0DDD;SINHALA VOWEL SIGN KOMBUVA HAA DIGA AELA-PILLA;Mc;0;L;0DDC 0DCA;;;;N;;;;; 0DDE;SINHALA VOWEL SIGN KOMBUVA HAA GAYANUKITTA;Mc;0;L;0DD9 0DDF;;;;N;;;;; 0DDF;SINHALA VOWEL SIGN GAYANUKITTA;Mc;0;L;;;;;N;;;;; 0DE6;SINHALA LITH DIGIT ZERO;Nd;0;L;;0;0;0;N;;;;; 0DE7;SINHALA LITH DIGIT ONE;Nd;0;L;;1;1;1;N;;;;; 0DE8;SINHALA LITH DIGIT TWO;Nd;0;L;;2;2;2;N;;;;; 0DE9;SINHALA LITH DIGIT THREE;Nd;0;L;;3;3;3;N;;;;; 0DEA;SINHALA LITH DIGIT FOUR;Nd;0;L;;4;4;4;N;;;;; 0DEB;SINHALA LITH DIGIT FIVE;Nd;0;L;;5;5;5;N;;;;; 0DEC;SINHALA LITH DIGIT SIX;Nd;0;L;;6;6;6;N;;;;; 0DED;SINHALA LITH DIGIT SEVEN;Nd;0;L;;7;7;7;N;;;;; 0DEE;SINHALA LITH DIGIT EIGHT;Nd;0;L;;8;8;8;N;;;;; 0DEF;SINHALA LITH DIGIT NINE;Nd;0;L;;9;9;9;N;;;;; 0DF2;SINHALA VOWEL SIGN DIGA GAETTA-PILLA;Mc;0;L;;;;;N;;;;; 0DF3;SINHALA VOWEL SIGN DIGA GAYANUKITTA;Mc;0;L;;;;;N;;;;; 0DF4;SINHALA PUNCTUATION KUNDDALIYA;Po;0;L;;;;;N;;;;; 0E01;THAI CHARACTER KO KAI;Lo;0;L;;;;;N;THAI LETTER KO KAI;;;; 0E02;THAI CHARACTER KHO KHAI;Lo;0;L;;;;;N;THAI LETTER KHO KHAI;;;; 0E03;THAI CHARACTER KHO KHUAT;Lo;0;L;;;;;N;THAI LETTER KHO KHUAT;;;; 0E04;THAI CHARACTER KHO KHWAI;Lo;0;L;;;;;N;THAI LETTER KHO KHWAI;;;; 0E05;THAI CHARACTER KHO KHON;Lo;0;L;;;;;N;THAI LETTER KHO KHON;;;; 0E06;THAI CHARACTER KHO RAKHANG;Lo;0;L;;;;;N;THAI LETTER KHO RAKHANG;;;; 0E07;THAI CHARACTER NGO NGU;Lo;0;L;;;;;N;THAI LETTER NGO NGU;;;; 0E08;THAI CHARACTER CHO CHAN;Lo;0;L;;;;;N;THAI LETTER CHO CHAN;;;; 0E09;THAI CHARACTER CHO CHING;Lo;0;L;;;;;N;THAI LETTER CHO CHING;;;; 0E0A;THAI CHARACTER CHO CHANG;Lo;0;L;;;;;N;THAI LETTER CHO CHANG;;;; 0E0B;THAI CHARACTER SO SO;Lo;0;L;;;;;N;THAI LETTER SO SO;;;; 0E0C;THAI CHARACTER CHO CHOE;Lo;0;L;;;;;N;THAI LETTER CHO CHOE;;;; 0E0D;THAI CHARACTER YO YING;Lo;0;L;;;;;N;THAI LETTER YO YING;;;; 0E0E;THAI CHARACTER DO CHADA;Lo;0;L;;;;;N;THAI LETTER DO CHADA;;;; 0E0F;THAI CHARACTER TO PATAK;Lo;0;L;;;;;N;THAI LETTER TO PATAK;;;; 0E10;THAI CHARACTER THO THAN;Lo;0;L;;;;;N;THAI LETTER THO THAN;;;; 0E11;THAI CHARACTER THO NANGMONTHO;Lo;0;L;;;;;N;THAI LETTER THO NANGMONTHO;;;; 0E12;THAI CHARACTER THO PHUTHAO;Lo;0;L;;;;;N;THAI LETTER THO PHUTHAO;;;; 0E13;THAI CHARACTER NO NEN;Lo;0;L;;;;;N;THAI LETTER NO NEN;;;; 0E14;THAI CHARACTER DO DEK;Lo;0;L;;;;;N;THAI LETTER DO DEK;;;; 0E15;THAI CHARACTER TO TAO;Lo;0;L;;;;;N;THAI LETTER TO TAO;;;; 0E16;THAI CHARACTER THO THUNG;Lo;0;L;;;;;N;THAI LETTER THO THUNG;;;; 0E17;THAI CHARACTER THO THAHAN;Lo;0;L;;;;;N;THAI LETTER THO THAHAN;;;; 0E18;THAI CHARACTER THO THONG;Lo;0;L;;;;;N;THAI LETTER THO THONG;;;; 0E19;THAI CHARACTER NO NU;Lo;0;L;;;;;N;THAI LETTER NO NU;;;; 0E1A;THAI CHARACTER BO BAIMAI;Lo;0;L;;;;;N;THAI LETTER BO BAIMAI;;;; 0E1B;THAI CHARACTER PO PLA;Lo;0;L;;;;;N;THAI LETTER PO PLA;;;; 0E1C;THAI CHARACTER PHO PHUNG;Lo;0;L;;;;;N;THAI LETTER PHO PHUNG;;;; 0E1D;THAI CHARACTER FO FA;Lo;0;L;;;;;N;THAI LETTER FO FA;;;; 0E1E;THAI CHARACTER PHO PHAN;Lo;0;L;;;;;N;THAI LETTER PHO PHAN;;;; 0E1F;THAI CHARACTER FO FAN;Lo;0;L;;;;;N;THAI LETTER FO FAN;;;; 0E20;THAI CHARACTER PHO SAMPHAO;Lo;0;L;;;;;N;THAI LETTER PHO SAMPHAO;;;; 0E21;THAI CHARACTER MO MA;Lo;0;L;;;;;N;THAI LETTER MO MA;;;; 0E22;THAI CHARACTER YO YAK;Lo;0;L;;;;;N;THAI LETTER YO YAK;;;; 0E23;THAI CHARACTER RO RUA;Lo;0;L;;;;;N;THAI LETTER RO RUA;;;; 0E24;THAI CHARACTER RU;Lo;0;L;;;;;N;THAI LETTER RU;;;; 0E25;THAI CHARACTER LO LING;Lo;0;L;;;;;N;THAI LETTER LO LING;;;; 0E26;THAI CHARACTER LU;Lo;0;L;;;;;N;THAI LETTER LU;;;; 0E27;THAI CHARACTER WO WAEN;Lo;0;L;;;;;N;THAI LETTER WO WAEN;;;; 0E28;THAI CHARACTER SO SALA;Lo;0;L;;;;;N;THAI LETTER SO SALA;;;; 0E29;THAI CHARACTER SO RUSI;Lo;0;L;;;;;N;THAI LETTER SO RUSI;;;; 0E2A;THAI CHARACTER SO SUA;Lo;0;L;;;;;N;THAI LETTER SO SUA;;;; 0E2B;THAI CHARACTER HO HIP;Lo;0;L;;;;;N;THAI LETTER HO HIP;;;; 0E2C;THAI CHARACTER LO CHULA;Lo;0;L;;;;;N;THAI LETTER LO CHULA;;;; 0E2D;THAI CHARACTER O ANG;Lo;0;L;;;;;N;THAI LETTER O ANG;;;; 0E2E;THAI CHARACTER HO NOKHUK;Lo;0;L;;;;;N;THAI LETTER HO NOK HUK;;;; 0E2F;THAI CHARACTER PAIYANNOI;Lo;0;L;;;;;N;THAI PAI YAN NOI;;;; 0E30;THAI CHARACTER SARA A;Lo;0;L;;;;;N;THAI VOWEL SIGN SARA A;;;; 0E31;THAI CHARACTER MAI HAN-AKAT;Mn;0;NSM;;;;;N;THAI VOWEL SIGN MAI HAN-AKAT;;;; 0E32;THAI CHARACTER SARA AA;Lo;0;L;;;;;N;THAI VOWEL SIGN SARA AA;;;; 0E33;THAI CHARACTER SARA AM;Lo;0;L; 0E4D 0E32;;;;N;THAI VOWEL SIGN SARA AM;;;; 0E34;THAI CHARACTER SARA I;Mn;0;NSM;;;;;N;THAI VOWEL SIGN SARA I;;;; 0E35;THAI CHARACTER SARA II;Mn;0;NSM;;;;;N;THAI VOWEL SIGN SARA II;;;; 0E36;THAI CHARACTER SARA UE;Mn;0;NSM;;;;;N;THAI VOWEL SIGN SARA UE;;;; 0E37;THAI CHARACTER SARA UEE;Mn;0;NSM;;;;;N;THAI VOWEL SIGN SARA UEE;;;; 0E38;THAI CHARACTER SARA U;Mn;103;NSM;;;;;N;THAI VOWEL SIGN SARA U;;;; 0E39;THAI CHARACTER SARA UU;Mn;103;NSM;;;;;N;THAI VOWEL SIGN SARA UU;;;; 0E3A;THAI CHARACTER PHINTHU;Mn;9;NSM;;;;;N;THAI VOWEL SIGN PHINTHU;;;; 0E3F;THAI CURRENCY SYMBOL BAHT;Sc;0;ET;;;;;N;THAI BAHT SIGN;;;; 0E40;THAI CHARACTER SARA E;Lo;0;L;;;;;N;THAI VOWEL SIGN SARA E;;;; 0E41;THAI CHARACTER SARA AE;Lo;0;L;;;;;N;THAI VOWEL SIGN SARA AE;;;; 0E42;THAI CHARACTER SARA O;Lo;0;L;;;;;N;THAI VOWEL SIGN SARA O;;;; 0E43;THAI CHARACTER SARA AI MAIMUAN;Lo;0;L;;;;;N;THAI VOWEL SIGN SARA MAI MUAN;;;; 0E44;THAI CHARACTER SARA AI MAIMALAI;Lo;0;L;;;;;N;THAI VOWEL SIGN SARA MAI MALAI;;;; 0E45;THAI CHARACTER LAKKHANGYAO;Lo;0;L;;;;;N;THAI LAK KHANG YAO;;;; 0E46;THAI CHARACTER MAIYAMOK;Lm;0;L;;;;;N;THAI MAI YAMOK;;;; 0E47;THAI CHARACTER MAITAIKHU;Mn;0;NSM;;;;;N;THAI VOWEL SIGN MAI TAI KHU;;;; 0E48;THAI CHARACTER MAI EK;Mn;107;NSM;;;;;N;THAI TONE MAI EK;;;; 0E49;THAI CHARACTER MAI THO;Mn;107;NSM;;;;;N;THAI TONE MAI THO;;;; 0E4A;THAI CHARACTER MAI TRI;Mn;107;NSM;;;;;N;THAI TONE MAI TRI;;;; 0E4B;THAI CHARACTER MAI CHATTAWA;Mn;107;NSM;;;;;N;THAI TONE MAI CHATTAWA;;;; 0E4C;THAI CHARACTER THANTHAKHAT;Mn;0;NSM;;;;;N;THAI THANTHAKHAT;;;; 0E4D;THAI CHARACTER NIKHAHIT;Mn;0;NSM;;;;;N;THAI NIKKHAHIT;;;; 0E4E;THAI CHARACTER YAMAKKAN;Mn;0;NSM;;;;;N;THAI YAMAKKAN;;;; 0E4F;THAI CHARACTER FONGMAN;Po;0;L;;;;;N;THAI FONGMAN;;;; 0E50;THAI DIGIT ZERO;Nd;0;L;;0;0;0;N;;;;; 0E51;THAI DIGIT ONE;Nd;0;L;;1;1;1;N;;;;; 0E52;THAI DIGIT TWO;Nd;0;L;;2;2;2;N;;;;; 0E53;THAI DIGIT THREE;Nd;0;L;;3;3;3;N;;;;; 0E54;THAI DIGIT FOUR;Nd;0;L;;4;4;4;N;;;;; 0E55;THAI DIGIT FIVE;Nd;0;L;;5;5;5;N;;;;; 0E56;THAI DIGIT SIX;Nd;0;L;;6;6;6;N;;;;; 0E57;THAI DIGIT SEVEN;Nd;0;L;;7;7;7;N;;;;; 0E58;THAI DIGIT EIGHT;Nd;0;L;;8;8;8;N;;;;; 0E59;THAI DIGIT NINE;Nd;0;L;;9;9;9;N;;;;; 0E5A;THAI CHARACTER ANGKHANKHU;Po;0;L;;;;;N;THAI ANGKHANKHU;;;; 0E5B;THAI CHARACTER KHOMUT;Po;0;L;;;;;N;THAI KHOMUT;;;; 0E81;LAO LETTER KO;Lo;0;L;;;;;N;;;;; 0E82;LAO LETTER KHO SUNG;Lo;0;L;;;;;N;;;;; 0E84;LAO LETTER KHO TAM;Lo;0;L;;;;;N;;;;; 0E87;LAO LETTER NGO;Lo;0;L;;;;;N;;;;; 0E88;LAO LETTER CO;Lo;0;L;;;;;N;;;;; 0E8A;LAO LETTER SO TAM;Lo;0;L;;;;;N;;;;; 0E8D;LAO LETTER NYO;Lo;0;L;;;;;N;;;;; 0E94;LAO LETTER DO;Lo;0;L;;;;;N;;;;; 0E95;LAO LETTER TO;Lo;0;L;;;;;N;;;;; 0E96;LAO LETTER THO SUNG;Lo;0;L;;;;;N;;;;; 0E97;LAO LETTER THO TAM;Lo;0;L;;;;;N;;;;; 0E99;LAO LETTER NO;Lo;0;L;;;;;N;;;;; 0E9A;LAO LETTER BO;Lo;0;L;;;;;N;;;;; 0E9B;LAO LETTER PO;Lo;0;L;;;;;N;;;;; 0E9C;LAO LETTER PHO SUNG;Lo;0;L;;;;;N;;;;; 0E9D;LAO LETTER FO TAM;Lo;0;L;;;;;N;;;;; 0E9E;LAO LETTER PHO TAM;Lo;0;L;;;;;N;;;;; 0E9F;LAO LETTER FO SUNG;Lo;0;L;;;;;N;;;;; 0EA1;LAO LETTER MO;Lo;0;L;;;;;N;;;;; 0EA2;LAO LETTER YO;Lo;0;L;;;;;N;;;;; 0EA3;LAO LETTER LO LING;Lo;0;L;;;;;N;;;;; 0EA5;LAO LETTER LO LOOT;Lo;0;L;;;;;N;;;;; 0EA7;LAO LETTER WO;Lo;0;L;;;;;N;;;;; 0EAA;LAO LETTER SO SUNG;Lo;0;L;;;;;N;;;;; 0EAB;LAO LETTER HO SUNG;Lo;0;L;;;;;N;;;;; 0EAD;LAO LETTER O;Lo;0;L;;;;;N;;;;; 0EAE;LAO LETTER HO TAM;Lo;0;L;;;;;N;;;;; 0EAF;LAO ELLIPSIS;Lo;0;L;;;;;N;;;;; 0EB0;LAO VOWEL SIGN A;Lo;0;L;;;;;N;;;;; 0EB1;LAO VOWEL SIGN MAI KAN;Mn;0;NSM;;;;;N;;;;; 0EB2;LAO VOWEL SIGN AA;Lo;0;L;;;;;N;;;;; 0EB3;LAO VOWEL SIGN AM;Lo;0;L; 0ECD 0EB2;;;;N;;;;; 0EB4;LAO VOWEL SIGN I;Mn;0;NSM;;;;;N;;;;; 0EB5;LAO VOWEL SIGN II;Mn;0;NSM;;;;;N;;;;; 0EB6;LAO VOWEL SIGN Y;Mn;0;NSM;;;;;N;;;;; 0EB7;LAO VOWEL SIGN YY;Mn;0;NSM;;;;;N;;;;; 0EB8;LAO VOWEL SIGN U;Mn;118;NSM;;;;;N;;;;; 0EB9;LAO VOWEL SIGN UU;Mn;118;NSM;;;;;N;;;;; 0EBB;LAO VOWEL SIGN MAI KON;Mn;0;NSM;;;;;N;;;;; 0EBC;LAO SEMIVOWEL SIGN LO;Mn;0;NSM;;;;;N;;;;; 0EBD;LAO SEMIVOWEL SIGN NYO;Lo;0;L;;;;;N;;;;; 0EC0;LAO VOWEL SIGN E;Lo;0;L;;;;;N;;;;; 0EC1;LAO VOWEL SIGN EI;Lo;0;L;;;;;N;;;;; 0EC2;LAO VOWEL SIGN O;Lo;0;L;;;;;N;;;;; 0EC3;LAO VOWEL SIGN AY;Lo;0;L;;;;;N;;;;; 0EC4;LAO VOWEL SIGN AI;Lo;0;L;;;;;N;;;;; 0EC6;LAO KO LA;Lm;0;L;;;;;N;;;;; 0EC8;LAO TONE MAI EK;Mn;122;NSM;;;;;N;;;;; 0EC9;LAO TONE MAI THO;Mn;122;NSM;;;;;N;;;;; 0ECA;LAO TONE MAI TI;Mn;122;NSM;;;;;N;;;;; 0ECB;LAO TONE MAI CATAWA;Mn;122;NSM;;;;;N;;;;; 0ECC;LAO CANCELLATION MARK;Mn;0;NSM;;;;;N;;;;; 0ECD;LAO NIGGAHITA;Mn;0;NSM;;;;;N;;;;; 0ED0;LAO DIGIT ZERO;Nd;0;L;;0;0;0;N;;;;; 0ED1;LAO DIGIT ONE;Nd;0;L;;1;1;1;N;;;;; 0ED2;LAO DIGIT TWO;Nd;0;L;;2;2;2;N;;;;; 0ED3;LAO DIGIT THREE;Nd;0;L;;3;3;3;N;;;;; 0ED4;LAO DIGIT FOUR;Nd;0;L;;4;4;4;N;;;;; 0ED5;LAO DIGIT FIVE;Nd;0;L;;5;5;5;N;;;;; 0ED6;LAO DIGIT SIX;Nd;0;L;;6;6;6;N;;;;; 0ED7;LAO DIGIT SEVEN;Nd;0;L;;7;7;7;N;;;;; 0ED8;LAO DIGIT EIGHT;Nd;0;L;;8;8;8;N;;;;; 0ED9;LAO DIGIT NINE;Nd;0;L;;9;9;9;N;;;;; 0EDC;LAO HO NO;Lo;0;L; 0EAB 0E99;;;;N;;;;; 0EDD;LAO HO MO;Lo;0;L; 0EAB 0EA1;;;;N;;;;; 0EDE;LAO LETTER KHMU GO;Lo;0;L;;;;;N;;;;; 0EDF;LAO LETTER KHMU NYO;Lo;0;L;;;;;N;;;;; 0F00;TIBETAN SYLLABLE OM;Lo;0;L;;;;;N;;;;; 0F01;TIBETAN MARK GTER YIG MGO TRUNCATED A;So;0;L;;;;;N;;;;; 0F02;TIBETAN MARK GTER YIG MGO -UM RNAM BCAD MA;So;0;L;;;;;N;;;;; 0F03;TIBETAN MARK GTER YIG MGO -UM GTER TSHEG MA;So;0;L;;;;;N;;;;; 0F04;TIBETAN MARK INITIAL YIG MGO MDUN MA;Po;0;L;;;;;N;TIBETAN SINGLE ORNAMENT;;;; 0F05;TIBETAN MARK CLOSING YIG MGO SGAB MA;Po;0;L;;;;;N;;;;; 0F06;TIBETAN MARK CARET YIG MGO PHUR SHAD MA;Po;0;L;;;;;N;;;;; 0F07;TIBETAN MARK YIG MGO TSHEG SHAD MA;Po;0;L;;;;;N;;;;; 0F08;TIBETAN MARK SBRUL SHAD;Po;0;L;;;;;N;TIBETAN RGYANSHAD;;;; 0F09;TIBETAN MARK BSKUR YIG MGO;Po;0;L;;;;;N;;;;; 0F0A;TIBETAN MARK BKA- SHOG YIG MGO;Po;0;L;;;;;N;;;;; 0F0B;TIBETAN MARK INTERSYLLABIC TSHEG;Po;0;L;;;;;N;TIBETAN TSEG;;;; 0F0C;TIBETAN MARK DELIMITER TSHEG BSTAR;Po;0;L; 0F0B;;;;N;;;;; 0F0D;TIBETAN MARK SHAD;Po;0;L;;;;;N;TIBETAN SHAD;;;; 0F0E;TIBETAN MARK NYIS SHAD;Po;0;L;;;;;N;TIBETAN DOUBLE SHAD;;;; 0F0F;TIBETAN MARK TSHEG SHAD;Po;0;L;;;;;N;;;;; 0F10;TIBETAN MARK NYIS TSHEG SHAD;Po;0;L;;;;;N;;;;; 0F11;TIBETAN MARK RIN CHEN SPUNGS SHAD;Po;0;L;;;;;N;TIBETAN RINCHANPHUNGSHAD;;;; 0F12;TIBETAN MARK RGYA GRAM SHAD;Po;0;L;;;;;N;;;;; 0F13;TIBETAN MARK CARET -DZUD RTAGS ME LONG CAN;So;0;L;;;;;N;;;;; 0F14;TIBETAN MARK GTER TSHEG;Po;0;L;;;;;N;TIBETAN COMMA;;;; 0F15;TIBETAN LOGOTYPE SIGN CHAD RTAGS;So;0;L;;;;;N;;;;; 0F16;TIBETAN LOGOTYPE SIGN LHAG RTAGS;So;0;L;;;;;N;;;;; 0F17;TIBETAN ASTROLOGICAL SIGN SGRA GCAN -CHAR RTAGS;So;0;L;;;;;N;;;;; 0F18;TIBETAN ASTROLOGICAL SIGN -KHYUD PA;Mn;220;NSM;;;;;N;;;;; 0F19;TIBETAN ASTROLOGICAL SIGN SDONG TSHUGS;Mn;220;NSM;;;;;N;;;;; 0F1A;TIBETAN SIGN RDEL DKAR GCIG;So;0;L;;;;;N;;;;; 0F1B;TIBETAN SIGN RDEL DKAR GNYIS;So;0;L;;;;;N;;;;; 0F1C;TIBETAN SIGN RDEL DKAR GSUM;So;0;L;;;;;N;;;;; 0F1D;TIBETAN SIGN RDEL NAG GCIG;So;0;L;;;;;N;;;;; 0F1E;TIBETAN SIGN RDEL NAG GNYIS;So;0;L;;;;;N;;;;; 0F1F;TIBETAN SIGN RDEL DKAR RDEL NAG;So;0;L;;;;;N;;;;; 0F20;TIBETAN DIGIT ZERO;Nd;0;L;;0;0;0;N;;;;; 0F21;TIBETAN DIGIT ONE;Nd;0;L;;1;1;1;N;;;;; 0F22;TIBETAN DIGIT TWO;Nd;0;L;;2;2;2;N;;;;; 0F23;TIBETAN DIGIT THREE;Nd;0;L;;3;3;3;N;;;;; 0F24;TIBETAN DIGIT FOUR;Nd;0;L;;4;4;4;N;;;;; 0F25;TIBETAN DIGIT FIVE;Nd;0;L;;5;5;5;N;;;;; 0F26;TIBETAN DIGIT SIX;Nd;0;L;;6;6;6;N;;;;; 0F27;TIBETAN DIGIT SEVEN;Nd;0;L;;7;7;7;N;;;;; 0F28;TIBETAN DIGIT EIGHT;Nd;0;L;;8;8;8;N;;;;; 0F29;TIBETAN DIGIT NINE;Nd;0;L;;9;9;9;N;;;;; 0F2A;TIBETAN DIGIT HALF ONE;No;0;L;;;;1/2;N;;;;; 0F2B;TIBETAN DIGIT HALF TWO;No;0;L;;;;3/2;N;;;;; 0F2C;TIBETAN DIGIT HALF THREE;No;0;L;;;;5/2;N;;;;; 0F2D;TIBETAN DIGIT HALF FOUR;No;0;L;;;;7/2;N;;;;; 0F2E;TIBETAN DIGIT HALF FIVE;No;0;L;;;;9/2;N;;;;; 0F2F;TIBETAN DIGIT HALF SIX;No;0;L;;;;11/2;N;;;;; 0F30;TIBETAN DIGIT HALF SEVEN;No;0;L;;;;13/2;N;;;;; 0F31;TIBETAN DIGIT HALF EIGHT;No;0;L;;;;15/2;N;;;;; 0F32;TIBETAN DIGIT HALF NINE;No;0;L;;;;17/2;N;;;;; 0F33;TIBETAN DIGIT HALF ZERO;No;0;L;;;;-1/2;N;;;;; 0F34;TIBETAN MARK BSDUS RTAGS;So;0;L;;;;;N;;;;; 0F35;TIBETAN MARK NGAS BZUNG NYI ZLA;Mn;220;NSM;;;;;N;TIBETAN HONORIFIC UNDER RING;;;; 0F36;TIBETAN MARK CARET -DZUD RTAGS BZHI MIG CAN;So;0;L;;;;;N;;;;; 0F37;TIBETAN MARK NGAS BZUNG SGOR RTAGS;Mn;220;NSM;;;;;N;TIBETAN UNDER RING;;;; 0F38;TIBETAN MARK CHE MGO;So;0;L;;;;;N;;;;; 0F39;TIBETAN MARK TSA -PHRU;Mn;216;NSM;;;;;N;TIBETAN LENITION MARK;;;; 0F3A;TIBETAN MARK GUG RTAGS GYON;Ps;0;ON;;;;;Y;;;;; 0F3B;TIBETAN MARK GUG RTAGS GYAS;Pe;0;ON;;;;;Y;;;;; 0F3C;TIBETAN MARK ANG KHANG GYON;Ps;0;ON;;;;;Y;TIBETAN LEFT BRACE;;;; 0F3D;TIBETAN MARK ANG KHANG GYAS;Pe;0;ON;;;;;Y;TIBETAN RIGHT BRACE;;;; 0F3E;TIBETAN SIGN YAR TSHES;Mc;0;L;;;;;N;;;;; 0F3F;TIBETAN SIGN MAR TSHES;Mc;0;L;;;;;N;;;;; 0F40;TIBETAN LETTER KA;Lo;0;L;;;;;N;;;;; 0F41;TIBETAN LETTER KHA;Lo;0;L;;;;;N;;;;; 0F42;TIBETAN LETTER GA;Lo;0;L;;;;;N;;;;; 0F43;TIBETAN LETTER GHA;Lo;0;L;0F42 0FB7;;;;N;;;;; 0F44;TIBETAN LETTER NGA;Lo;0;L;;;;;N;;;;; 0F45;TIBETAN LETTER CA;Lo;0;L;;;;;N;;;;; 0F46;TIBETAN LETTER CHA;Lo;0;L;;;;;N;;;;; 0F47;TIBETAN LETTER JA;Lo;0;L;;;;;N;;;;; 0F49;TIBETAN LETTER NYA;Lo;0;L;;;;;N;;;;; 0F4A;TIBETAN LETTER TTA;Lo;0;L;;;;;N;TIBETAN LETTER REVERSED TA;;;; 0F4B;TIBETAN LETTER TTHA;Lo;0;L;;;;;N;TIBETAN LETTER REVERSED THA;;;; 0F4C;TIBETAN LETTER DDA;Lo;0;L;;;;;N;TIBETAN LETTER REVERSED DA;;;; 0F4D;TIBETAN LETTER DDHA;Lo;0;L;0F4C 0FB7;;;;N;;;;; 0F4E;TIBETAN LETTER NNA;Lo;0;L;;;;;N;TIBETAN LETTER REVERSED NA;;;; 0F4F;TIBETAN LETTER TA;Lo;0;L;;;;;N;;;;; 0F50;TIBETAN LETTER THA;Lo;0;L;;;;;N;;;;; 0F51;TIBETAN LETTER DA;Lo;0;L;;;;;N;;;;; 0F52;TIBETAN LETTER DHA;Lo;0;L;0F51 0FB7;;;;N;;;;; 0F53;TIBETAN LETTER NA;Lo;0;L;;;;;N;;;;; 0F54;TIBETAN LETTER PA;Lo;0;L;;;;;N;;;;; 0F55;TIBETAN LETTER PHA;Lo;0;L;;;;;N;;;;; 0F56;TIBETAN LETTER BA;Lo;0;L;;;;;N;;;;; 0F57;TIBETAN LETTER BHA;Lo;0;L;0F56 0FB7;;;;N;;;;; 0F58;TIBETAN LETTER MA;Lo;0;L;;;;;N;;;;; 0F59;TIBETAN LETTER TSA;Lo;0;L;;;;;N;;;;; 0F5A;TIBETAN LETTER TSHA;Lo;0;L;;;;;N;;;;; 0F5B;TIBETAN LETTER DZA;Lo;0;L;;;;;N;;;;; 0F5C;TIBETAN LETTER DZHA;Lo;0;L;0F5B 0FB7;;;;N;;;;; 0F5D;TIBETAN LETTER WA;Lo;0;L;;;;;N;;;;; 0F5E;TIBETAN LETTER ZHA;Lo;0;L;;;;;N;;;;; 0F5F;TIBETAN LETTER ZA;Lo;0;L;;;;;N;;;;; 0F60;TIBETAN LETTER -A;Lo;0;L;;;;;N;TIBETAN LETTER AA;;;; 0F61;TIBETAN LETTER YA;Lo;0;L;;;;;N;;;;; 0F62;TIBETAN LETTER RA;Lo;0;L;;;;;N;;;;; 0F63;TIBETAN LETTER LA;Lo;0;L;;;;;N;;;;; 0F64;TIBETAN LETTER SHA;Lo;0;L;;;;;N;;;;; 0F65;TIBETAN LETTER SSA;Lo;0;L;;;;;N;TIBETAN LETTER REVERSED SHA;;;; 0F66;TIBETAN LETTER SA;Lo;0;L;;;;;N;;;;; 0F67;TIBETAN LETTER HA;Lo;0;L;;;;;N;;;;; 0F68;TIBETAN LETTER A;Lo;0;L;;;;;N;;;;; 0F69;TIBETAN LETTER KSSA;Lo;0;L;0F40 0FB5;;;;N;;;;; 0F6A;TIBETAN LETTER FIXED-FORM RA;Lo;0;L;;;;;N;;;;; 0F6B;TIBETAN LETTER KKA;Lo;0;L;;;;;N;;;;; 0F6C;TIBETAN LETTER RRA;Lo;0;L;;;;;N;;;;; 0F71;TIBETAN VOWEL SIGN AA;Mn;129;NSM;;;;;N;;;;; 0F72;TIBETAN VOWEL SIGN I;Mn;130;NSM;;;;;N;;;;; 0F73;TIBETAN VOWEL SIGN II;Mn;0;NSM;0F71 0F72;;;;N;;;;; 0F74;TIBETAN VOWEL SIGN U;Mn;132;NSM;;;;;N;;;;; 0F75;TIBETAN VOWEL SIGN UU;Mn;0;NSM;0F71 0F74;;;;N;;;;; 0F76;TIBETAN VOWEL SIGN VOCALIC R;Mn;0;NSM;0FB2 0F80;;;;N;;;;; 0F77;TIBETAN VOWEL SIGN VOCALIC RR;Mn;0;NSM; 0FB2 0F81;;;;N;;;;; 0F78;TIBETAN VOWEL SIGN VOCALIC L;Mn;0;NSM;0FB3 0F80;;;;N;;;;; 0F79;TIBETAN VOWEL SIGN VOCALIC LL;Mn;0;NSM; 0FB3 0F81;;;;N;;;;; 0F7A;TIBETAN VOWEL SIGN E;Mn;130;NSM;;;;;N;;;;; 0F7B;TIBETAN VOWEL SIGN EE;Mn;130;NSM;;;;;N;TIBETAN VOWEL SIGN AI;;;; 0F7C;TIBETAN VOWEL SIGN O;Mn;130;NSM;;;;;N;;;;; 0F7D;TIBETAN VOWEL SIGN OO;Mn;130;NSM;;;;;N;TIBETAN VOWEL SIGN AU;;;; 0F7E;TIBETAN SIGN RJES SU NGA RO;Mn;0;NSM;;;;;N;TIBETAN ANUSVARA;;;; 0F7F;TIBETAN SIGN RNAM BCAD;Mc;0;L;;;;;N;TIBETAN VISARGA;;;; 0F80;TIBETAN VOWEL SIGN REVERSED I;Mn;130;NSM;;;;;N;TIBETAN VOWEL SIGN SHORT I;;;; 0F81;TIBETAN VOWEL SIGN REVERSED II;Mn;0;NSM;0F71 0F80;;;;N;;;;; 0F82;TIBETAN SIGN NYI ZLA NAA DA;Mn;230;NSM;;;;;N;TIBETAN CANDRABINDU WITH ORNAMENT;;;; 0F83;TIBETAN SIGN SNA LDAN;Mn;230;NSM;;;;;N;TIBETAN CANDRABINDU;;;; 0F84;TIBETAN MARK HALANTA;Mn;9;NSM;;;;;N;TIBETAN VIRAMA;;;; 0F85;TIBETAN MARK PALUTA;Po;0;L;;;;;N;TIBETAN CHUCHENYIGE;;;; 0F86;TIBETAN SIGN LCI RTAGS;Mn;230;NSM;;;;;N;;;;; 0F87;TIBETAN SIGN YANG RTAGS;Mn;230;NSM;;;;;N;;;;; 0F88;TIBETAN SIGN LCE TSA CAN;Lo;0;L;;;;;N;;;;; 0F89;TIBETAN SIGN MCHU CAN;Lo;0;L;;;;;N;;;;; 0F8A;TIBETAN SIGN GRU CAN RGYINGS;Lo;0;L;;;;;N;;;;; 0F8B;TIBETAN SIGN GRU MED RGYINGS;Lo;0;L;;;;;N;;;;; 0F8C;TIBETAN SIGN INVERTED MCHU CAN;Lo;0;L;;;;;N;;;;; 0F8D;TIBETAN SUBJOINED SIGN LCE TSA CAN;Mn;0;NSM;;;;;N;;;;; 0F8E;TIBETAN SUBJOINED SIGN MCHU CAN;Mn;0;NSM;;;;;N;;;;; 0F8F;TIBETAN SUBJOINED SIGN INVERTED MCHU CAN;Mn;0;NSM;;;;;N;;;;; 0F90;TIBETAN SUBJOINED LETTER KA;Mn;0;NSM;;;;;N;;;;; 0F91;TIBETAN SUBJOINED LETTER KHA;Mn;0;NSM;;;;;N;;;;; 0F92;TIBETAN SUBJOINED LETTER GA;Mn;0;NSM;;;;;N;;;;; 0F93;TIBETAN SUBJOINED LETTER GHA;Mn;0;NSM;0F92 0FB7;;;;N;;;;; 0F94;TIBETAN SUBJOINED LETTER NGA;Mn;0;NSM;;;;;N;;;;; 0F95;TIBETAN SUBJOINED LETTER CA;Mn;0;NSM;;;;;N;;;;; 0F96;TIBETAN SUBJOINED LETTER CHA;Mn;0;NSM;;;;;N;;;;; 0F97;TIBETAN SUBJOINED LETTER JA;Mn;0;NSM;;;;;N;;;;; 0F99;TIBETAN SUBJOINED LETTER NYA;Mn;0;NSM;;;;;N;;;;; 0F9A;TIBETAN SUBJOINED LETTER TTA;Mn;0;NSM;;;;;N;;;;; 0F9B;TIBETAN SUBJOINED LETTER TTHA;Mn;0;NSM;;;;;N;;;;; 0F9C;TIBETAN SUBJOINED LETTER DDA;Mn;0;NSM;;;;;N;;;;; 0F9D;TIBETAN SUBJOINED LETTER DDHA;Mn;0;NSM;0F9C 0FB7;;;;N;;;;; 0F9E;TIBETAN SUBJOINED LETTER NNA;Mn;0;NSM;;;;;N;;;;; 0F9F;TIBETAN SUBJOINED LETTER TA;Mn;0;NSM;;;;;N;;;;; 0FA0;TIBETAN SUBJOINED LETTER THA;Mn;0;NSM;;;;;N;;;;; 0FA1;TIBETAN SUBJOINED LETTER DA;Mn;0;NSM;;;;;N;;;;; 0FA2;TIBETAN SUBJOINED LETTER DHA;Mn;0;NSM;0FA1 0FB7;;;;N;;;;; 0FA3;TIBETAN SUBJOINED LETTER NA;Mn;0;NSM;;;;;N;;;;; 0FA4;TIBETAN SUBJOINED LETTER PA;Mn;0;NSM;;;;;N;;;;; 0FA5;TIBETAN SUBJOINED LETTER PHA;Mn;0;NSM;;;;;N;;;;; 0FA6;TIBETAN SUBJOINED LETTER BA;Mn;0;NSM;;;;;N;;;;; 0FA7;TIBETAN SUBJOINED LETTER BHA;Mn;0;NSM;0FA6 0FB7;;;;N;;;;; 0FA8;TIBETAN SUBJOINED LETTER MA;Mn;0;NSM;;;;;N;;;;; 0FA9;TIBETAN SUBJOINED LETTER TSA;Mn;0;NSM;;;;;N;;;;; 0FAA;TIBETAN SUBJOINED LETTER TSHA;Mn;0;NSM;;;;;N;;;;; 0FAB;TIBETAN SUBJOINED LETTER DZA;Mn;0;NSM;;;;;N;;;;; 0FAC;TIBETAN SUBJOINED LETTER DZHA;Mn;0;NSM;0FAB 0FB7;;;;N;;;;; 0FAD;TIBETAN SUBJOINED LETTER WA;Mn;0;NSM;;;;;N;;;;; 0FAE;TIBETAN SUBJOINED LETTER ZHA;Mn;0;NSM;;;;;N;;;;; 0FAF;TIBETAN SUBJOINED LETTER ZA;Mn;0;NSM;;;;;N;;;;; 0FB0;TIBETAN SUBJOINED LETTER -A;Mn;0;NSM;;;;;N;;;;; 0FB1;TIBETAN SUBJOINED LETTER YA;Mn;0;NSM;;;;;N;;;;; 0FB2;TIBETAN SUBJOINED LETTER RA;Mn;0;NSM;;;;;N;;;;; 0FB3;TIBETAN SUBJOINED LETTER LA;Mn;0;NSM;;;;;N;;;;; 0FB4;TIBETAN SUBJOINED LETTER SHA;Mn;0;NSM;;;;;N;;;;; 0FB5;TIBETAN SUBJOINED LETTER SSA;Mn;0;NSM;;;;;N;;;;; 0FB6;TIBETAN SUBJOINED LETTER SA;Mn;0;NSM;;;;;N;;;;; 0FB7;TIBETAN SUBJOINED LETTER HA;Mn;0;NSM;;;;;N;;;;; 0FB8;TIBETAN SUBJOINED LETTER A;Mn;0;NSM;;;;;N;;;;; 0FB9;TIBETAN SUBJOINED LETTER KSSA;Mn;0;NSM;0F90 0FB5;;;;N;;;;; 0FBA;TIBETAN SUBJOINED LETTER FIXED-FORM WA;Mn;0;NSM;;;;;N;;;;; 0FBB;TIBETAN SUBJOINED LETTER FIXED-FORM YA;Mn;0;NSM;;;;;N;;;;; 0FBC;TIBETAN SUBJOINED LETTER FIXED-FORM RA;Mn;0;NSM;;;;;N;;;;; 0FBE;TIBETAN KU RU KHA;So;0;L;;;;;N;;;;; 0FBF;TIBETAN KU RU KHA BZHI MIG CAN;So;0;L;;;;;N;;;;; 0FC0;TIBETAN CANTILLATION SIGN HEAVY BEAT;So;0;L;;;;;N;;;;; 0FC1;TIBETAN CANTILLATION SIGN LIGHT BEAT;So;0;L;;;;;N;;;;; 0FC2;TIBETAN CANTILLATION SIGN CANG TE-U;So;0;L;;;;;N;;;;; 0FC3;TIBETAN CANTILLATION SIGN SBUB -CHAL;So;0;L;;;;;N;;;;; 0FC4;TIBETAN SYMBOL DRIL BU;So;0;L;;;;;N;;;;; 0FC5;TIBETAN SYMBOL RDO RJE;So;0;L;;;;;N;;;;; 0FC6;TIBETAN SYMBOL PADMA GDAN;Mn;220;NSM;;;;;N;;;;; 0FC7;TIBETAN SYMBOL RDO RJE RGYA GRAM;So;0;L;;;;;N;;;;; 0FC8;TIBETAN SYMBOL PHUR PA;So;0;L;;;;;N;;;;; 0FC9;TIBETAN SYMBOL NOR BU;So;0;L;;;;;N;;;;; 0FCA;TIBETAN SYMBOL NOR BU NYIS -KHYIL;So;0;L;;;;;N;;;;; 0FCB;TIBETAN SYMBOL NOR BU GSUM -KHYIL;So;0;L;;;;;N;;;;; 0FCC;TIBETAN SYMBOL NOR BU BZHI -KHYIL;So;0;L;;;;;N;;;;; 0FCE;TIBETAN SIGN RDEL NAG RDEL DKAR;So;0;L;;;;;N;;;;; 0FCF;TIBETAN SIGN RDEL NAG GSUM;So;0;L;;;;;N;;;;; 0FD0;TIBETAN MARK BSKA- SHOG GI MGO RGYAN;Po;0;L;;;;;N;;;;; 0FD1;TIBETAN MARK MNYAM YIG GI MGO RGYAN;Po;0;L;;;;;N;;;;; 0FD2;TIBETAN MARK NYIS TSHEG;Po;0;L;;;;;N;;;;; 0FD3;TIBETAN MARK INITIAL BRDA RNYING YIG MGO MDUN MA;Po;0;L;;;;;N;;;;; 0FD4;TIBETAN MARK CLOSING BRDA RNYING YIG MGO SGAB MA;Po;0;L;;;;;N;;;;; 0FD5;RIGHT-FACING SVASTI SIGN;So;0;L;;;;;N;;;;; 0FD6;LEFT-FACING SVASTI SIGN;So;0;L;;;;;N;;;;; 0FD7;RIGHT-FACING SVASTI SIGN WITH DOTS;So;0;L;;;;;N;;;;; 0FD8;LEFT-FACING SVASTI SIGN WITH DOTS;So;0;L;;;;;N;;;;; 0FD9;TIBETAN MARK LEADING MCHAN RTAGS;Po;0;L;;;;;N;;;;; 0FDA;TIBETAN MARK TRAILING MCHAN RTAGS;Po;0;L;;;;;N;;;;; 1000;MYANMAR LETTER KA;Lo;0;L;;;;;N;;;;; 1001;MYANMAR LETTER KHA;Lo;0;L;;;;;N;;;;; 1002;MYANMAR LETTER GA;Lo;0;L;;;;;N;;;;; 1003;MYANMAR LETTER GHA;Lo;0;L;;;;;N;;;;; 1004;MYANMAR LETTER NGA;Lo;0;L;;;;;N;;;;; 1005;MYANMAR LETTER CA;Lo;0;L;;;;;N;;;;; 1006;MYANMAR LETTER CHA;Lo;0;L;;;;;N;;;;; 1007;MYANMAR LETTER JA;Lo;0;L;;;;;N;;;;; 1008;MYANMAR LETTER JHA;Lo;0;L;;;;;N;;;;; 1009;MYANMAR LETTER NYA;Lo;0;L;;;;;N;;;;; 100A;MYANMAR LETTER NNYA;Lo;0;L;;;;;N;;;;; 100B;MYANMAR LETTER TTA;Lo;0;L;;;;;N;;;;; 100C;MYANMAR LETTER TTHA;Lo;0;L;;;;;N;;;;; 100D;MYANMAR LETTER DDA;Lo;0;L;;;;;N;;;;; 100E;MYANMAR LETTER DDHA;Lo;0;L;;;;;N;;;;; 100F;MYANMAR LETTER NNA;Lo;0;L;;;;;N;;;;; 1010;MYANMAR LETTER TA;Lo;0;L;;;;;N;;;;; 1011;MYANMAR LETTER THA;Lo;0;L;;;;;N;;;;; 1012;MYANMAR LETTER DA;Lo;0;L;;;;;N;;;;; 1013;MYANMAR LETTER DHA;Lo;0;L;;;;;N;;;;; 1014;MYANMAR LETTER NA;Lo;0;L;;;;;N;;;;; 1015;MYANMAR LETTER PA;Lo;0;L;;;;;N;;;;; 1016;MYANMAR LETTER PHA;Lo;0;L;;;;;N;;;;; 1017;MYANMAR LETTER BA;Lo;0;L;;;;;N;;;;; 1018;MYANMAR LETTER BHA;Lo;0;L;;;;;N;;;;; 1019;MYANMAR LETTER MA;Lo;0;L;;;;;N;;;;; 101A;MYANMAR LETTER YA;Lo;0;L;;;;;N;;;;; 101B;MYANMAR LETTER RA;Lo;0;L;;;;;N;;;;; 101C;MYANMAR LETTER LA;Lo;0;L;;;;;N;;;;; 101D;MYANMAR LETTER WA;Lo;0;L;;;;;N;;;;; 101E;MYANMAR LETTER SA;Lo;0;L;;;;;N;;;;; 101F;MYANMAR LETTER HA;Lo;0;L;;;;;N;;;;; 1020;MYANMAR LETTER LLA;Lo;0;L;;;;;N;;;;; 1021;MYANMAR LETTER A;Lo;0;L;;;;;N;;;;; 1022;MYANMAR LETTER SHAN A;Lo;0;L;;;;;N;;;;; 1023;MYANMAR LETTER I;Lo;0;L;;;;;N;;;;; 1024;MYANMAR LETTER II;Lo;0;L;;;;;N;;;;; 1025;MYANMAR LETTER U;Lo;0;L;;;;;N;;;;; 1026;MYANMAR LETTER UU;Lo;0;L;1025 102E;;;;N;;;;; 1027;MYANMAR LETTER E;Lo;0;L;;;;;N;;;;; 1028;MYANMAR LETTER MON E;Lo;0;L;;;;;N;;;;; 1029;MYANMAR LETTER O;Lo;0;L;;;;;N;;;;; 102A;MYANMAR LETTER AU;Lo;0;L;;;;;N;;;;; 102B;MYANMAR VOWEL SIGN TALL AA;Mc;0;L;;;;;N;;;;; 102C;MYANMAR VOWEL SIGN AA;Mc;0;L;;;;;N;;;;; 102D;MYANMAR VOWEL SIGN I;Mn;0;NSM;;;;;N;;;;; 102E;MYANMAR VOWEL SIGN II;Mn;0;NSM;;;;;N;;;;; 102F;MYANMAR VOWEL SIGN U;Mn;0;NSM;;;;;N;;;;; 1030;MYANMAR VOWEL SIGN UU;Mn;0;NSM;;;;;N;;;;; 1031;MYANMAR VOWEL SIGN E;Mc;0;L;;;;;N;;;;; 1032;MYANMAR VOWEL SIGN AI;Mn;0;NSM;;;;;N;;;;; 1033;MYANMAR VOWEL SIGN MON II;Mn;0;NSM;;;;;N;;;;; 1034;MYANMAR VOWEL SIGN MON O;Mn;0;NSM;;;;;N;;;;; 1035;MYANMAR VOWEL SIGN E ABOVE;Mn;0;NSM;;;;;N;;;;; 1036;MYANMAR SIGN ANUSVARA;Mn;0;NSM;;;;;N;;;;; 1037;MYANMAR SIGN DOT BELOW;Mn;7;NSM;;;;;N;;;;; 1038;MYANMAR SIGN VISARGA;Mc;0;L;;;;;N;;;;; 1039;MYANMAR SIGN VIRAMA;Mn;9;NSM;;;;;N;;;;; 103A;MYANMAR SIGN ASAT;Mn;9;NSM;;;;;N;;;;; 103B;MYANMAR CONSONANT SIGN MEDIAL YA;Mc;0;L;;;;;N;;;;; 103C;MYANMAR CONSONANT SIGN MEDIAL RA;Mc;0;L;;;;;N;;;;; 103D;MYANMAR CONSONANT SIGN MEDIAL WA;Mn;0;NSM;;;;;N;;;;; 103E;MYANMAR CONSONANT SIGN MEDIAL HA;Mn;0;NSM;;;;;N;;;;; 103F;MYANMAR LETTER GREAT SA;Lo;0;L;;;;;N;;;;; 1040;MYANMAR DIGIT ZERO;Nd;0;L;;0;0;0;N;;;;; 1041;MYANMAR DIGIT ONE;Nd;0;L;;1;1;1;N;;;;; 1042;MYANMAR DIGIT TWO;Nd;0;L;;2;2;2;N;;;;; 1043;MYANMAR DIGIT THREE;Nd;0;L;;3;3;3;N;;;;; 1044;MYANMAR DIGIT FOUR;Nd;0;L;;4;4;4;N;;;;; 1045;MYANMAR DIGIT FIVE;Nd;0;L;;5;5;5;N;;;;; 1046;MYANMAR DIGIT SIX;Nd;0;L;;6;6;6;N;;;;; 1047;MYANMAR DIGIT SEVEN;Nd;0;L;;7;7;7;N;;;;; 1048;MYANMAR DIGIT EIGHT;Nd;0;L;;8;8;8;N;;;;; 1049;MYANMAR DIGIT NINE;Nd;0;L;;9;9;9;N;;;;; 104A;MYANMAR SIGN LITTLE SECTION;Po;0;L;;;;;N;;;;; 104B;MYANMAR SIGN SECTION;Po;0;L;;;;;N;;;;; 104C;MYANMAR SYMBOL LOCATIVE;Po;0;L;;;;;N;;;;; 104D;MYANMAR SYMBOL COMPLETED;Po;0;L;;;;;N;;;;; 104E;MYANMAR SYMBOL AFOREMENTIONED;Po;0;L;;;;;N;;;;; 104F;MYANMAR SYMBOL GENITIVE;Po;0;L;;;;;N;;;;; 1050;MYANMAR LETTER SHA;Lo;0;L;;;;;N;;;;; 1051;MYANMAR LETTER SSA;Lo;0;L;;;;;N;;;;; 1052;MYANMAR LETTER VOCALIC R;Lo;0;L;;;;;N;;;;; 1053;MYANMAR LETTER VOCALIC RR;Lo;0;L;;;;;N;;;;; 1054;MYANMAR LETTER VOCALIC L;Lo;0;L;;;;;N;;;;; 1055;MYANMAR LETTER VOCALIC LL;Lo;0;L;;;;;N;;;;; 1056;MYANMAR VOWEL SIGN VOCALIC R;Mc;0;L;;;;;N;;;;; 1057;MYANMAR VOWEL SIGN VOCALIC RR;Mc;0;L;;;;;N;;;;; 1058;MYANMAR VOWEL SIGN VOCALIC L;Mn;0;NSM;;;;;N;;;;; 1059;MYANMAR VOWEL SIGN VOCALIC LL;Mn;0;NSM;;;;;N;;;;; 105A;MYANMAR LETTER MON NGA;Lo;0;L;;;;;N;;;;; 105B;MYANMAR LETTER MON JHA;Lo;0;L;;;;;N;;;;; 105C;MYANMAR LETTER MON BBA;Lo;0;L;;;;;N;;;;; 105D;MYANMAR LETTER MON BBE;Lo;0;L;;;;;N;;;;; 105E;MYANMAR CONSONANT SIGN MON MEDIAL NA;Mn;0;NSM;;;;;N;;;;; 105F;MYANMAR CONSONANT SIGN MON MEDIAL MA;Mn;0;NSM;;;;;N;;;;; 1060;MYANMAR CONSONANT SIGN MON MEDIAL LA;Mn;0;NSM;;;;;N;;;;; 1061;MYANMAR LETTER SGAW KAREN SHA;Lo;0;L;;;;;N;;;;; 1062;MYANMAR VOWEL SIGN SGAW KAREN EU;Mc;0;L;;;;;N;;;;; 1063;MYANMAR TONE MARK SGAW KAREN HATHI;Mc;0;L;;;;;N;;;;; 1064;MYANMAR TONE MARK SGAW KAREN KE PHO;Mc;0;L;;;;;N;;;;; 1065;MYANMAR LETTER WESTERN PWO KAREN THA;Lo;0;L;;;;;N;;;;; 1066;MYANMAR LETTER WESTERN PWO KAREN PWA;Lo;0;L;;;;;N;;;;; 1067;MYANMAR VOWEL SIGN WESTERN PWO KAREN EU;Mc;0;L;;;;;N;;;;; 1068;MYANMAR VOWEL SIGN WESTERN PWO KAREN UE;Mc;0;L;;;;;N;;;;; 1069;MYANMAR SIGN WESTERN PWO KAREN TONE-1;Mc;0;L;;;;;N;;;;; 106A;MYANMAR SIGN WESTERN PWO KAREN TONE-2;Mc;0;L;;;;;N;;;;; 106B;MYANMAR SIGN WESTERN PWO KAREN TONE-3;Mc;0;L;;;;;N;;;;; 106C;MYANMAR SIGN WESTERN PWO KAREN TONE-4;Mc;0;L;;;;;N;;;;; 106D;MYANMAR SIGN WESTERN PWO KAREN TONE-5;Mc;0;L;;;;;N;;;;; 106E;MYANMAR LETTER EASTERN PWO KAREN NNA;Lo;0;L;;;;;N;;;;; 106F;MYANMAR LETTER EASTERN PWO KAREN YWA;Lo;0;L;;;;;N;;;;; 1070;MYANMAR LETTER EASTERN PWO KAREN GHWA;Lo;0;L;;;;;N;;;;; 1071;MYANMAR VOWEL SIGN GEBA KAREN I;Mn;0;NSM;;;;;N;;;;; 1072;MYANMAR VOWEL SIGN KAYAH OE;Mn;0;NSM;;;;;N;;;;; 1073;MYANMAR VOWEL SIGN KAYAH U;Mn;0;NSM;;;;;N;;;;; 1074;MYANMAR VOWEL SIGN KAYAH EE;Mn;0;NSM;;;;;N;;;;; 1075;MYANMAR LETTER SHAN KA;Lo;0;L;;;;;N;;;;; 1076;MYANMAR LETTER SHAN KHA;Lo;0;L;;;;;N;;;;; 1077;MYANMAR LETTER SHAN GA;Lo;0;L;;;;;N;;;;; 1078;MYANMAR LETTER SHAN CA;Lo;0;L;;;;;N;;;;; 1079;MYANMAR LETTER SHAN ZA;Lo;0;L;;;;;N;;;;; 107A;MYANMAR LETTER SHAN NYA;Lo;0;L;;;;;N;;;;; 107B;MYANMAR LETTER SHAN DA;Lo;0;L;;;;;N;;;;; 107C;MYANMAR LETTER SHAN NA;Lo;0;L;;;;;N;;;;; 107D;MYANMAR LETTER SHAN PHA;Lo;0;L;;;;;N;;;;; 107E;MYANMAR LETTER SHAN FA;Lo;0;L;;;;;N;;;;; 107F;MYANMAR LETTER SHAN BA;Lo;0;L;;;;;N;;;;; 1080;MYANMAR LETTER SHAN THA;Lo;0;L;;;;;N;;;;; 1081;MYANMAR LETTER SHAN HA;Lo;0;L;;;;;N;;;;; 1082;MYANMAR CONSONANT SIGN SHAN MEDIAL WA;Mn;0;NSM;;;;;N;;;;; 1083;MYANMAR VOWEL SIGN SHAN AA;Mc;0;L;;;;;N;;;;; 1084;MYANMAR VOWEL SIGN SHAN E;Mc;0;L;;;;;N;;;;; 1085;MYANMAR VOWEL SIGN SHAN E ABOVE;Mn;0;NSM;;;;;N;;;;; 1086;MYANMAR VOWEL SIGN SHAN FINAL Y;Mn;0;NSM;;;;;N;;;;; 1087;MYANMAR SIGN SHAN TONE-2;Mc;0;L;;;;;N;;;;; 1088;MYANMAR SIGN SHAN TONE-3;Mc;0;L;;;;;N;;;;; 1089;MYANMAR SIGN SHAN TONE-5;Mc;0;L;;;;;N;;;;; 108A;MYANMAR SIGN SHAN TONE-6;Mc;0;L;;;;;N;;;;; 108B;MYANMAR SIGN SHAN COUNCIL TONE-2;Mc;0;L;;;;;N;;;;; 108C;MYANMAR SIGN SHAN COUNCIL TONE-3;Mc;0;L;;;;;N;;;;; 108D;MYANMAR SIGN SHAN COUNCIL EMPHATIC TONE;Mn;220;NSM;;;;;N;;;;; 108E;MYANMAR LETTER RUMAI PALAUNG FA;Lo;0;L;;;;;N;;;;; 108F;MYANMAR SIGN RUMAI PALAUNG TONE-5;Mc;0;L;;;;;N;;;;; 1090;MYANMAR SHAN DIGIT ZERO;Nd;0;L;;0;0;0;N;;;;; 1091;MYANMAR SHAN DIGIT ONE;Nd;0;L;;1;1;1;N;;;;; 1092;MYANMAR SHAN DIGIT TWO;Nd;0;L;;2;2;2;N;;;;; 1093;MYANMAR SHAN DIGIT THREE;Nd;0;L;;3;3;3;N;;;;; 1094;MYANMAR SHAN DIGIT FOUR;Nd;0;L;;4;4;4;N;;;;; 1095;MYANMAR SHAN DIGIT FIVE;Nd;0;L;;5;5;5;N;;;;; 1096;MYANMAR SHAN DIGIT SIX;Nd;0;L;;6;6;6;N;;;;; 1097;MYANMAR SHAN DIGIT SEVEN;Nd;0;L;;7;7;7;N;;;;; 1098;MYANMAR SHAN DIGIT EIGHT;Nd;0;L;;8;8;8;N;;;;; 1099;MYANMAR SHAN DIGIT NINE;Nd;0;L;;9;9;9;N;;;;; 109A;MYANMAR SIGN KHAMTI TONE-1;Mc;0;L;;;;;N;;;;; 109B;MYANMAR SIGN KHAMTI TONE-3;Mc;0;L;;;;;N;;;;; 109C;MYANMAR VOWEL SIGN AITON A;Mc;0;L;;;;;N;;;;; 109D;MYANMAR VOWEL SIGN AITON AI;Mn;0;NSM;;;;;N;;;;; 109E;MYANMAR SYMBOL SHAN ONE;So;0;L;;;;;N;;;;; 109F;MYANMAR SYMBOL SHAN EXCLAMATION;So;0;L;;;;;N;;;;; 10A0;GEORGIAN CAPITAL LETTER AN;Lu;0;L;;;;;N;;;;2D00; 10A1;GEORGIAN CAPITAL LETTER BAN;Lu;0;L;;;;;N;;;;2D01; 10A2;GEORGIAN CAPITAL LETTER GAN;Lu;0;L;;;;;N;;;;2D02; 10A3;GEORGIAN CAPITAL LETTER DON;Lu;0;L;;;;;N;;;;2D03; 10A4;GEORGIAN CAPITAL LETTER EN;Lu;0;L;;;;;N;;;;2D04; 10A5;GEORGIAN CAPITAL LETTER VIN;Lu;0;L;;;;;N;;;;2D05; 10A6;GEORGIAN CAPITAL LETTER ZEN;Lu;0;L;;;;;N;;;;2D06; 10A7;GEORGIAN CAPITAL LETTER TAN;Lu;0;L;;;;;N;;;;2D07; 10A8;GEORGIAN CAPITAL LETTER IN;Lu;0;L;;;;;N;;;;2D08; 10A9;GEORGIAN CAPITAL LETTER KAN;Lu;0;L;;;;;N;;;;2D09; 10AA;GEORGIAN CAPITAL LETTER LAS;Lu;0;L;;;;;N;;;;2D0A; 10AB;GEORGIAN CAPITAL LETTER MAN;Lu;0;L;;;;;N;;;;2D0B; 10AC;GEORGIAN CAPITAL LETTER NAR;Lu;0;L;;;;;N;;;;2D0C; 10AD;GEORGIAN CAPITAL LETTER ON;Lu;0;L;;;;;N;;;;2D0D; 10AE;GEORGIAN CAPITAL LETTER PAR;Lu;0;L;;;;;N;;;;2D0E; 10AF;GEORGIAN CAPITAL LETTER ZHAR;Lu;0;L;;;;;N;;;;2D0F; 10B0;GEORGIAN CAPITAL LETTER RAE;Lu;0;L;;;;;N;;;;2D10; 10B1;GEORGIAN CAPITAL LETTER SAN;Lu;0;L;;;;;N;;;;2D11; 10B2;GEORGIAN CAPITAL LETTER TAR;Lu;0;L;;;;;N;;;;2D12; 10B3;GEORGIAN CAPITAL LETTER UN;Lu;0;L;;;;;N;;;;2D13; 10B4;GEORGIAN CAPITAL LETTER PHAR;Lu;0;L;;;;;N;;;;2D14; 10B5;GEORGIAN CAPITAL LETTER KHAR;Lu;0;L;;;;;N;;;;2D15; 10B6;GEORGIAN CAPITAL LETTER GHAN;Lu;0;L;;;;;N;;;;2D16; 10B7;GEORGIAN CAPITAL LETTER QAR;Lu;0;L;;;;;N;;;;2D17; 10B8;GEORGIAN CAPITAL LETTER SHIN;Lu;0;L;;;;;N;;;;2D18; 10B9;GEORGIAN CAPITAL LETTER CHIN;Lu;0;L;;;;;N;;;;2D19; 10BA;GEORGIAN CAPITAL LETTER CAN;Lu;0;L;;;;;N;;;;2D1A; 10BB;GEORGIAN CAPITAL LETTER JIL;Lu;0;L;;;;;N;;;;2D1B; 10BC;GEORGIAN CAPITAL LETTER CIL;Lu;0;L;;;;;N;;;;2D1C; 10BD;GEORGIAN CAPITAL LETTER CHAR;Lu;0;L;;;;;N;;;;2D1D; 10BE;GEORGIAN CAPITAL LETTER XAN;Lu;0;L;;;;;N;;;;2D1E; 10BF;GEORGIAN CAPITAL LETTER JHAN;Lu;0;L;;;;;N;;;;2D1F; 10C0;GEORGIAN CAPITAL LETTER HAE;Lu;0;L;;;;;N;;;;2D20; 10C1;GEORGIAN CAPITAL LETTER HE;Lu;0;L;;;;;N;;;;2D21; 10C2;GEORGIAN CAPITAL LETTER HIE;Lu;0;L;;;;;N;;;;2D22; 10C3;GEORGIAN CAPITAL LETTER WE;Lu;0;L;;;;;N;;;;2D23; 10C4;GEORGIAN CAPITAL LETTER HAR;Lu;0;L;;;;;N;;;;2D24; 10C5;GEORGIAN CAPITAL LETTER HOE;Lu;0;L;;;;;N;;;;2D25; 10C7;GEORGIAN CAPITAL LETTER YN;Lu;0;L;;;;;N;;;;2D27; 10CD;GEORGIAN CAPITAL LETTER AEN;Lu;0;L;;;;;N;;;;2D2D; 10D0;GEORGIAN LETTER AN;Lo;0;L;;;;;N;GEORGIAN SMALL LETTER AN;;;; 10D1;GEORGIAN LETTER BAN;Lo;0;L;;;;;N;GEORGIAN SMALL LETTER BAN;;;; 10D2;GEORGIAN LETTER GAN;Lo;0;L;;;;;N;GEORGIAN SMALL LETTER GAN;;;; 10D3;GEORGIAN LETTER DON;Lo;0;L;;;;;N;GEORGIAN SMALL LETTER DON;;;; 10D4;GEORGIAN LETTER EN;Lo;0;L;;;;;N;GEORGIAN SMALL LETTER EN;;;; 10D5;GEORGIAN LETTER VIN;Lo;0;L;;;;;N;GEORGIAN SMALL LETTER VIN;;;; 10D6;GEORGIAN LETTER ZEN;Lo;0;L;;;;;N;GEORGIAN SMALL LETTER ZEN;;;; 10D7;GEORGIAN LETTER TAN;Lo;0;L;;;;;N;GEORGIAN SMALL LETTER TAN;;;; 10D8;GEORGIAN LETTER IN;Lo;0;L;;;;;N;GEORGIAN SMALL LETTER IN;;;; 10D9;GEORGIAN LETTER KAN;Lo;0;L;;;;;N;GEORGIAN SMALL LETTER KAN;;;; 10DA;GEORGIAN LETTER LAS;Lo;0;L;;;;;N;GEORGIAN SMALL LETTER LAS;;;; 10DB;GEORGIAN LETTER MAN;Lo;0;L;;;;;N;GEORGIAN SMALL LETTER MAN;;;; 10DC;GEORGIAN LETTER NAR;Lo;0;L;;;;;N;GEORGIAN SMALL LETTER NAR;;;; 10DD;GEORGIAN LETTER ON;Lo;0;L;;;;;N;GEORGIAN SMALL LETTER ON;;;; 10DE;GEORGIAN LETTER PAR;Lo;0;L;;;;;N;GEORGIAN SMALL LETTER PAR;;;; 10DF;GEORGIAN LETTER ZHAR;Lo;0;L;;;;;N;GEORGIAN SMALL LETTER ZHAR;;;; 10E0;GEORGIAN LETTER RAE;Lo;0;L;;;;;N;GEORGIAN SMALL LETTER RAE;;;; 10E1;GEORGIAN LETTER SAN;Lo;0;L;;;;;N;GEORGIAN SMALL LETTER SAN;;;; 10E2;GEORGIAN LETTER TAR;Lo;0;L;;;;;N;GEORGIAN SMALL LETTER TAR;;;; 10E3;GEORGIAN LETTER UN;Lo;0;L;;;;;N;GEORGIAN SMALL LETTER UN;;;; 10E4;GEORGIAN LETTER PHAR;Lo;0;L;;;;;N;GEORGIAN SMALL LETTER PHAR;;;; 10E5;GEORGIAN LETTER KHAR;Lo;0;L;;;;;N;GEORGIAN SMALL LETTER KHAR;;;; 10E6;GEORGIAN LETTER GHAN;Lo;0;L;;;;;N;GEORGIAN SMALL LETTER GHAN;;;; 10E7;GEORGIAN LETTER QAR;Lo;0;L;;;;;N;GEORGIAN SMALL LETTER QAR;;;; 10E8;GEORGIAN LETTER SHIN;Lo;0;L;;;;;N;GEORGIAN SMALL LETTER SHIN;;;; 10E9;GEORGIAN LETTER CHIN;Lo;0;L;;;;;N;GEORGIAN SMALL LETTER CHIN;;;; 10EA;GEORGIAN LETTER CAN;Lo;0;L;;;;;N;GEORGIAN SMALL LETTER CAN;;;; 10EB;GEORGIAN LETTER JIL;Lo;0;L;;;;;N;GEORGIAN SMALL LETTER JIL;;;; 10EC;GEORGIAN LETTER CIL;Lo;0;L;;;;;N;GEORGIAN SMALL LETTER CIL;;;; 10ED;GEORGIAN LETTER CHAR;Lo;0;L;;;;;N;GEORGIAN SMALL LETTER CHAR;;;; 10EE;GEORGIAN LETTER XAN;Lo;0;L;;;;;N;GEORGIAN SMALL LETTER XAN;;;; 10EF;GEORGIAN LETTER JHAN;Lo;0;L;;;;;N;GEORGIAN SMALL LETTER JHAN;;;; 10F0;GEORGIAN LETTER HAE;Lo;0;L;;;;;N;GEORGIAN SMALL LETTER HAE;;;; 10F1;GEORGIAN LETTER HE;Lo;0;L;;;;;N;GEORGIAN SMALL LETTER HE;;;; 10F2;GEORGIAN LETTER HIE;Lo;0;L;;;;;N;GEORGIAN SMALL LETTER HIE;;;; 10F3;GEORGIAN LETTER WE;Lo;0;L;;;;;N;GEORGIAN SMALL LETTER WE;;;; 10F4;GEORGIAN LETTER HAR;Lo;0;L;;;;;N;GEORGIAN SMALL LETTER HAR;;;; 10F5;GEORGIAN LETTER HOE;Lo;0;L;;;;;N;GEORGIAN SMALL LETTER HOE;;;; 10F6;GEORGIAN LETTER FI;Lo;0;L;;;;;N;GEORGIAN SMALL LETTER FI;;;; 10F7;GEORGIAN LETTER YN;Lo;0;L;;;;;N;;;;; 10F8;GEORGIAN LETTER ELIFI;Lo;0;L;;;;;N;;;;; 10F9;GEORGIAN LETTER TURNED GAN;Lo;0;L;;;;;N;;;;; 10FA;GEORGIAN LETTER AIN;Lo;0;L;;;;;N;;;;; 10FB;GEORGIAN PARAGRAPH SEPARATOR;Po;0;L;;;;;N;;;;; 10FC;MODIFIER LETTER GEORGIAN NAR;Lm;0;L; 10DC;;;;N;;;;; 10FD;GEORGIAN LETTER AEN;Lo;0;L;;;;;N;;;;; 10FE;GEORGIAN LETTER HARD SIGN;Lo;0;L;;;;;N;;;;; 10FF;GEORGIAN LETTER LABIAL SIGN;Lo;0;L;;;;;N;;;;; 1100;HANGUL CHOSEONG KIYEOK;Lo;0;L;;;;;N;;;;; 1101;HANGUL CHOSEONG SSANGKIYEOK;Lo;0;L;;;;;N;;;;; 1102;HANGUL CHOSEONG NIEUN;Lo;0;L;;;;;N;;;;; 1103;HANGUL CHOSEONG TIKEUT;Lo;0;L;;;;;N;;;;; 1104;HANGUL CHOSEONG SSANGTIKEUT;Lo;0;L;;;;;N;;;;; 1105;HANGUL CHOSEONG RIEUL;Lo;0;L;;;;;N;;;;; 1106;HANGUL CHOSEONG MIEUM;Lo;0;L;;;;;N;;;;; 1107;HANGUL CHOSEONG PIEUP;Lo;0;L;;;;;N;;;;; 1108;HANGUL CHOSEONG SSANGPIEUP;Lo;0;L;;;;;N;;;;; 1109;HANGUL CHOSEONG SIOS;Lo;0;L;;;;;N;;;;; 110A;HANGUL CHOSEONG SSANGSIOS;Lo;0;L;;;;;N;;;;; 110B;HANGUL CHOSEONG IEUNG;Lo;0;L;;;;;N;;;;; 110C;HANGUL CHOSEONG CIEUC;Lo;0;L;;;;;N;;;;; 110D;HANGUL CHOSEONG SSANGCIEUC;Lo;0;L;;;;;N;;;;; 110E;HANGUL CHOSEONG CHIEUCH;Lo;0;L;;;;;N;;;;; 110F;HANGUL CHOSEONG KHIEUKH;Lo;0;L;;;;;N;;;;; 1110;HANGUL CHOSEONG THIEUTH;Lo;0;L;;;;;N;;;;; 1111;HANGUL CHOSEONG PHIEUPH;Lo;0;L;;;;;N;;;;; 1112;HANGUL CHOSEONG HIEUH;Lo;0;L;;;;;N;;;;; 1113;HANGUL CHOSEONG NIEUN-KIYEOK;Lo;0;L;;;;;N;;;;; 1114;HANGUL CHOSEONG SSANGNIEUN;Lo;0;L;;;;;N;;;;; 1115;HANGUL CHOSEONG NIEUN-TIKEUT;Lo;0;L;;;;;N;;;;; 1116;HANGUL CHOSEONG NIEUN-PIEUP;Lo;0;L;;;;;N;;;;; 1117;HANGUL CHOSEONG TIKEUT-KIYEOK;Lo;0;L;;;;;N;;;;; 1118;HANGUL CHOSEONG RIEUL-NIEUN;Lo;0;L;;;;;N;;;;; 1119;HANGUL CHOSEONG SSANGRIEUL;Lo;0;L;;;;;N;;;;; 111A;HANGUL CHOSEONG RIEUL-HIEUH;Lo;0;L;;;;;N;;;;; 111B;HANGUL CHOSEONG KAPYEOUNRIEUL;Lo;0;L;;;;;N;;;;; 111C;HANGUL CHOSEONG MIEUM-PIEUP;Lo;0;L;;;;;N;;;;; 111D;HANGUL CHOSEONG KAPYEOUNMIEUM;Lo;0;L;;;;;N;;;;; 111E;HANGUL CHOSEONG PIEUP-KIYEOK;Lo;0;L;;;;;N;;;;; 111F;HANGUL CHOSEONG PIEUP-NIEUN;Lo;0;L;;;;;N;;;;; 1120;HANGUL CHOSEONG PIEUP-TIKEUT;Lo;0;L;;;;;N;;;;; 1121;HANGUL CHOSEONG PIEUP-SIOS;Lo;0;L;;;;;N;;;;; 1122;HANGUL CHOSEONG PIEUP-SIOS-KIYEOK;Lo;0;L;;;;;N;;;;; 1123;HANGUL CHOSEONG PIEUP-SIOS-TIKEUT;Lo;0;L;;;;;N;;;;; 1124;HANGUL CHOSEONG PIEUP-SIOS-PIEUP;Lo;0;L;;;;;N;;;;; 1125;HANGUL CHOSEONG PIEUP-SSANGSIOS;Lo;0;L;;;;;N;;;;; 1126;HANGUL CHOSEONG PIEUP-SIOS-CIEUC;Lo;0;L;;;;;N;;;;; 1127;HANGUL CHOSEONG PIEUP-CIEUC;Lo;0;L;;;;;N;;;;; 1128;HANGUL CHOSEONG PIEUP-CHIEUCH;Lo;0;L;;;;;N;;;;; 1129;HANGUL CHOSEONG PIEUP-THIEUTH;Lo;0;L;;;;;N;;;;; 112A;HANGUL CHOSEONG PIEUP-PHIEUPH;Lo;0;L;;;;;N;;;;; 112B;HANGUL CHOSEONG KAPYEOUNPIEUP;Lo;0;L;;;;;N;;;;; 112C;HANGUL CHOSEONG KAPYEOUNSSANGPIEUP;Lo;0;L;;;;;N;;;;; 112D;HANGUL CHOSEONG SIOS-KIYEOK;Lo;0;L;;;;;N;;;;; 112E;HANGUL CHOSEONG SIOS-NIEUN;Lo;0;L;;;;;N;;;;; 112F;HANGUL CHOSEONG SIOS-TIKEUT;Lo;0;L;;;;;N;;;;; 1130;HANGUL CHOSEONG SIOS-RIEUL;Lo;0;L;;;;;N;;;;; 1131;HANGUL CHOSEONG SIOS-MIEUM;Lo;0;L;;;;;N;;;;; 1132;HANGUL CHOSEONG SIOS-PIEUP;Lo;0;L;;;;;N;;;;; 1133;HANGUL CHOSEONG SIOS-PIEUP-KIYEOK;Lo;0;L;;;;;N;;;;; 1134;HANGUL CHOSEONG SIOS-SSANGSIOS;Lo;0;L;;;;;N;;;;; 1135;HANGUL CHOSEONG SIOS-IEUNG;Lo;0;L;;;;;N;;;;; 1136;HANGUL CHOSEONG SIOS-CIEUC;Lo;0;L;;;;;N;;;;; 1137;HANGUL CHOSEONG SIOS-CHIEUCH;Lo;0;L;;;;;N;;;;; 1138;HANGUL CHOSEONG SIOS-KHIEUKH;Lo;0;L;;;;;N;;;;; 1139;HANGUL CHOSEONG SIOS-THIEUTH;Lo;0;L;;;;;N;;;;; 113A;HANGUL CHOSEONG SIOS-PHIEUPH;Lo;0;L;;;;;N;;;;; 113B;HANGUL CHOSEONG SIOS-HIEUH;Lo;0;L;;;;;N;;;;; 113C;HANGUL CHOSEONG CHITUEUMSIOS;Lo;0;L;;;;;N;;;;; 113D;HANGUL CHOSEONG CHITUEUMSSANGSIOS;Lo;0;L;;;;;N;;;;; 113E;HANGUL CHOSEONG CEONGCHIEUMSIOS;Lo;0;L;;;;;N;;;;; 113F;HANGUL CHOSEONG CEONGCHIEUMSSANGSIOS;Lo;0;L;;;;;N;;;;; 1140;HANGUL CHOSEONG PANSIOS;Lo;0;L;;;;;N;;;;; 1141;HANGUL CHOSEONG IEUNG-KIYEOK;Lo;0;L;;;;;N;;;;; 1142;HANGUL CHOSEONG IEUNG-TIKEUT;Lo;0;L;;;;;N;;;;; 1143;HANGUL CHOSEONG IEUNG-MIEUM;Lo;0;L;;;;;N;;;;; 1144;HANGUL CHOSEONG IEUNG-PIEUP;Lo;0;L;;;;;N;;;;; 1145;HANGUL CHOSEONG IEUNG-SIOS;Lo;0;L;;;;;N;;;;; 1146;HANGUL CHOSEONG IEUNG-PANSIOS;Lo;0;L;;;;;N;;;;; 1147;HANGUL CHOSEONG SSANGIEUNG;Lo;0;L;;;;;N;;;;; 1148;HANGUL CHOSEONG IEUNG-CIEUC;Lo;0;L;;;;;N;;;;; 1149;HANGUL CHOSEONG IEUNG-CHIEUCH;Lo;0;L;;;;;N;;;;; 114A;HANGUL CHOSEONG IEUNG-THIEUTH;Lo;0;L;;;;;N;;;;; 114B;HANGUL CHOSEONG IEUNG-PHIEUPH;Lo;0;L;;;;;N;;;;; 114C;HANGUL CHOSEONG YESIEUNG;Lo;0;L;;;;;N;;;;; 114D;HANGUL CHOSEONG CIEUC-IEUNG;Lo;0;L;;;;;N;;;;; 114E;HANGUL CHOSEONG CHITUEUMCIEUC;Lo;0;L;;;;;N;;;;; 114F;HANGUL CHOSEONG CHITUEUMSSANGCIEUC;Lo;0;L;;;;;N;;;;; 1150;HANGUL CHOSEONG CEONGCHIEUMCIEUC;Lo;0;L;;;;;N;;;;; 1151;HANGUL CHOSEONG CEONGCHIEUMSSANGCIEUC;Lo;0;L;;;;;N;;;;; 1152;HANGUL CHOSEONG CHIEUCH-KHIEUKH;Lo;0;L;;;;;N;;;;; 1153;HANGUL CHOSEONG CHIEUCH-HIEUH;Lo;0;L;;;;;N;;;;; 1154;HANGUL CHOSEONG CHITUEUMCHIEUCH;Lo;0;L;;;;;N;;;;; 1155;HANGUL CHOSEONG CEONGCHIEUMCHIEUCH;Lo;0;L;;;;;N;;;;; 1156;HANGUL CHOSEONG PHIEUPH-PIEUP;Lo;0;L;;;;;N;;;;; 1157;HANGUL CHOSEONG KAPYEOUNPHIEUPH;Lo;0;L;;;;;N;;;;; 1158;HANGUL CHOSEONG SSANGHIEUH;Lo;0;L;;;;;N;;;;; 1159;HANGUL CHOSEONG YEORINHIEUH;Lo;0;L;;;;;N;;;;; 115A;HANGUL CHOSEONG KIYEOK-TIKEUT;Lo;0;L;;;;;N;;;;; 115B;HANGUL CHOSEONG NIEUN-SIOS;Lo;0;L;;;;;N;;;;; 115C;HANGUL CHOSEONG NIEUN-CIEUC;Lo;0;L;;;;;N;;;;; 115D;HANGUL CHOSEONG NIEUN-HIEUH;Lo;0;L;;;;;N;;;;; 115E;HANGUL CHOSEONG TIKEUT-RIEUL;Lo;0;L;;;;;N;;;;; 115F;HANGUL CHOSEONG FILLER;Lo;0;L;;;;;N;;;;; 1160;HANGUL JUNGSEONG FILLER;Lo;0;L;;;;;N;;;;; 1161;HANGUL JUNGSEONG A;Lo;0;L;;;;;N;;;;; 1162;HANGUL JUNGSEONG AE;Lo;0;L;;;;;N;;;;; 1163;HANGUL JUNGSEONG YA;Lo;0;L;;;;;N;;;;; 1164;HANGUL JUNGSEONG YAE;Lo;0;L;;;;;N;;;;; 1165;HANGUL JUNGSEONG EO;Lo;0;L;;;;;N;;;;; 1166;HANGUL JUNGSEONG E;Lo;0;L;;;;;N;;;;; 1167;HANGUL JUNGSEONG YEO;Lo;0;L;;;;;N;;;;; 1168;HANGUL JUNGSEONG YE;Lo;0;L;;;;;N;;;;; 1169;HANGUL JUNGSEONG O;Lo;0;L;;;;;N;;;;; 116A;HANGUL JUNGSEONG WA;Lo;0;L;;;;;N;;;;; 116B;HANGUL JUNGSEONG WAE;Lo;0;L;;;;;N;;;;; 116C;HANGUL JUNGSEONG OE;Lo;0;L;;;;;N;;;;; 116D;HANGUL JUNGSEONG YO;Lo;0;L;;;;;N;;;;; 116E;HANGUL JUNGSEONG U;Lo;0;L;;;;;N;;;;; 116F;HANGUL JUNGSEONG WEO;Lo;0;L;;;;;N;;;;; 1170;HANGUL JUNGSEONG WE;Lo;0;L;;;;;N;;;;; 1171;HANGUL JUNGSEONG WI;Lo;0;L;;;;;N;;;;; 1172;HANGUL JUNGSEONG YU;Lo;0;L;;;;;N;;;;; 1173;HANGUL JUNGSEONG EU;Lo;0;L;;;;;N;;;;; 1174;HANGUL JUNGSEONG YI;Lo;0;L;;;;;N;;;;; 1175;HANGUL JUNGSEONG I;Lo;0;L;;;;;N;;;;; 1176;HANGUL JUNGSEONG A-O;Lo;0;L;;;;;N;;;;; 1177;HANGUL JUNGSEONG A-U;Lo;0;L;;;;;N;;;;; 1178;HANGUL JUNGSEONG YA-O;Lo;0;L;;;;;N;;;;; 1179;HANGUL JUNGSEONG YA-YO;Lo;0;L;;;;;N;;;;; 117A;HANGUL JUNGSEONG EO-O;Lo;0;L;;;;;N;;;;; 117B;HANGUL JUNGSEONG EO-U;Lo;0;L;;;;;N;;;;; 117C;HANGUL JUNGSEONG EO-EU;Lo;0;L;;;;;N;;;;; 117D;HANGUL JUNGSEONG YEO-O;Lo;0;L;;;;;N;;;;; 117E;HANGUL JUNGSEONG YEO-U;Lo;0;L;;;;;N;;;;; 117F;HANGUL JUNGSEONG O-EO;Lo;0;L;;;;;N;;;;; 1180;HANGUL JUNGSEONG O-E;Lo;0;L;;;;;N;;;;; 1181;HANGUL JUNGSEONG O-YE;Lo;0;L;;;;;N;;;;; 1182;HANGUL JUNGSEONG O-O;Lo;0;L;;;;;N;;;;; 1183;HANGUL JUNGSEONG O-U;Lo;0;L;;;;;N;;;;; 1184;HANGUL JUNGSEONG YO-YA;Lo;0;L;;;;;N;;;;; 1185;HANGUL JUNGSEONG YO-YAE;Lo;0;L;;;;;N;;;;; 1186;HANGUL JUNGSEONG YO-YEO;Lo;0;L;;;;;N;;;;; 1187;HANGUL JUNGSEONG YO-O;Lo;0;L;;;;;N;;;;; 1188;HANGUL JUNGSEONG YO-I;Lo;0;L;;;;;N;;;;; 1189;HANGUL JUNGSEONG U-A;Lo;0;L;;;;;N;;;;; 118A;HANGUL JUNGSEONG U-AE;Lo;0;L;;;;;N;;;;; 118B;HANGUL JUNGSEONG U-EO-EU;Lo;0;L;;;;;N;;;;; 118C;HANGUL JUNGSEONG U-YE;Lo;0;L;;;;;N;;;;; 118D;HANGUL JUNGSEONG U-U;Lo;0;L;;;;;N;;;;; 118E;HANGUL JUNGSEONG YU-A;Lo;0;L;;;;;N;;;;; 118F;HANGUL JUNGSEONG YU-EO;Lo;0;L;;;;;N;;;;; 1190;HANGUL JUNGSEONG YU-E;Lo;0;L;;;;;N;;;;; 1191;HANGUL JUNGSEONG YU-YEO;Lo;0;L;;;;;N;;;;; 1192;HANGUL JUNGSEONG YU-YE;Lo;0;L;;;;;N;;;;; 1193;HANGUL JUNGSEONG YU-U;Lo;0;L;;;;;N;;;;; 1194;HANGUL JUNGSEONG YU-I;Lo;0;L;;;;;N;;;;; 1195;HANGUL JUNGSEONG EU-U;Lo;0;L;;;;;N;;;;; 1196;HANGUL JUNGSEONG EU-EU;Lo;0;L;;;;;N;;;;; 1197;HANGUL JUNGSEONG YI-U;Lo;0;L;;;;;N;;;;; 1198;HANGUL JUNGSEONG I-A;Lo;0;L;;;;;N;;;;; 1199;HANGUL JUNGSEONG I-YA;Lo;0;L;;;;;N;;;;; 119A;HANGUL JUNGSEONG I-O;Lo;0;L;;;;;N;;;;; 119B;HANGUL JUNGSEONG I-U;Lo;0;L;;;;;N;;;;; 119C;HANGUL JUNGSEONG I-EU;Lo;0;L;;;;;N;;;;; 119D;HANGUL JUNGSEONG I-ARAEA;Lo;0;L;;;;;N;;;;; 119E;HANGUL JUNGSEONG ARAEA;Lo;0;L;;;;;N;;;;; 119F;HANGUL JUNGSEONG ARAEA-EO;Lo;0;L;;;;;N;;;;; 11A0;HANGUL JUNGSEONG ARAEA-U;Lo;0;L;;;;;N;;;;; 11A1;HANGUL JUNGSEONG ARAEA-I;Lo;0;L;;;;;N;;;;; 11A2;HANGUL JUNGSEONG SSANGARAEA;Lo;0;L;;;;;N;;;;; 11A3;HANGUL JUNGSEONG A-EU;Lo;0;L;;;;;N;;;;; 11A4;HANGUL JUNGSEONG YA-U;Lo;0;L;;;;;N;;;;; 11A5;HANGUL JUNGSEONG YEO-YA;Lo;0;L;;;;;N;;;;; 11A6;HANGUL JUNGSEONG O-YA;Lo;0;L;;;;;N;;;;; 11A7;HANGUL JUNGSEONG O-YAE;Lo;0;L;;;;;N;;;;; 11A8;HANGUL JONGSEONG KIYEOK;Lo;0;L;;;;;N;;;;; 11A9;HANGUL JONGSEONG SSANGKIYEOK;Lo;0;L;;;;;N;;;;; 11AA;HANGUL JONGSEONG KIYEOK-SIOS;Lo;0;L;;;;;N;;;;; 11AB;HANGUL JONGSEONG NIEUN;Lo;0;L;;;;;N;;;;; 11AC;HANGUL JONGSEONG NIEUN-CIEUC;Lo;0;L;;;;;N;;;;; 11AD;HANGUL JONGSEONG NIEUN-HIEUH;Lo;0;L;;;;;N;;;;; 11AE;HANGUL JONGSEONG TIKEUT;Lo;0;L;;;;;N;;;;; 11AF;HANGUL JONGSEONG RIEUL;Lo;0;L;;;;;N;;;;; 11B0;HANGUL JONGSEONG RIEUL-KIYEOK;Lo;0;L;;;;;N;;;;; 11B1;HANGUL JONGSEONG RIEUL-MIEUM;Lo;0;L;;;;;N;;;;; 11B2;HANGUL JONGSEONG RIEUL-PIEUP;Lo;0;L;;;;;N;;;;; 11B3;HANGUL JONGSEONG RIEUL-SIOS;Lo;0;L;;;;;N;;;;; 11B4;HANGUL JONGSEONG RIEUL-THIEUTH;Lo;0;L;;;;;N;;;;; 11B5;HANGUL JONGSEONG RIEUL-PHIEUPH;Lo;0;L;;;;;N;;;;; 11B6;HANGUL JONGSEONG RIEUL-HIEUH;Lo;0;L;;;;;N;;;;; 11B7;HANGUL JONGSEONG MIEUM;Lo;0;L;;;;;N;;;;; 11B8;HANGUL JONGSEONG PIEUP;Lo;0;L;;;;;N;;;;; 11B9;HANGUL JONGSEONG PIEUP-SIOS;Lo;0;L;;;;;N;;;;; 11BA;HANGUL JONGSEONG SIOS;Lo;0;L;;;;;N;;;;; 11BB;HANGUL JONGSEONG SSANGSIOS;Lo;0;L;;;;;N;;;;; 11BC;HANGUL JONGSEONG IEUNG;Lo;0;L;;;;;N;;;;; 11BD;HANGUL JONGSEONG CIEUC;Lo;0;L;;;;;N;;;;; 11BE;HANGUL JONGSEONG CHIEUCH;Lo;0;L;;;;;N;;;;; 11BF;HANGUL JONGSEONG KHIEUKH;Lo;0;L;;;;;N;;;;; 11C0;HANGUL JONGSEONG THIEUTH;Lo;0;L;;;;;N;;;;; 11C1;HANGUL JONGSEONG PHIEUPH;Lo;0;L;;;;;N;;;;; 11C2;HANGUL JONGSEONG HIEUH;Lo;0;L;;;;;N;;;;; 11C3;HANGUL JONGSEONG KIYEOK-RIEUL;Lo;0;L;;;;;N;;;;; 11C4;HANGUL JONGSEONG KIYEOK-SIOS-KIYEOK;Lo;0;L;;;;;N;;;;; 11C5;HANGUL JONGSEONG NIEUN-KIYEOK;Lo;0;L;;;;;N;;;;; 11C6;HANGUL JONGSEONG NIEUN-TIKEUT;Lo;0;L;;;;;N;;;;; 11C7;HANGUL JONGSEONG NIEUN-SIOS;Lo;0;L;;;;;N;;;;; 11C8;HANGUL JONGSEONG NIEUN-PANSIOS;Lo;0;L;;;;;N;;;;; 11C9;HANGUL JONGSEONG NIEUN-THIEUTH;Lo;0;L;;;;;N;;;;; 11CA;HANGUL JONGSEONG TIKEUT-KIYEOK;Lo;0;L;;;;;N;;;;; 11CB;HANGUL JONGSEONG TIKEUT-RIEUL;Lo;0;L;;;;;N;;;;; 11CC;HANGUL JONGSEONG RIEUL-KIYEOK-SIOS;Lo;0;L;;;;;N;;;;; 11CD;HANGUL JONGSEONG RIEUL-NIEUN;Lo;0;L;;;;;N;;;;; 11CE;HANGUL JONGSEONG RIEUL-TIKEUT;Lo;0;L;;;;;N;;;;; 11CF;HANGUL JONGSEONG RIEUL-TIKEUT-HIEUH;Lo;0;L;;;;;N;;;;; 11D0;HANGUL JONGSEONG SSANGRIEUL;Lo;0;L;;;;;N;;;;; 11D1;HANGUL JONGSEONG RIEUL-MIEUM-KIYEOK;Lo;0;L;;;;;N;;;;; 11D2;HANGUL JONGSEONG RIEUL-MIEUM-SIOS;Lo;0;L;;;;;N;;;;; 11D3;HANGUL JONGSEONG RIEUL-PIEUP-SIOS;Lo;0;L;;;;;N;;;;; 11D4;HANGUL JONGSEONG RIEUL-PIEUP-HIEUH;Lo;0;L;;;;;N;;;;; 11D5;HANGUL JONGSEONG RIEUL-KAPYEOUNPIEUP;Lo;0;L;;;;;N;;;;; 11D6;HANGUL JONGSEONG RIEUL-SSANGSIOS;Lo;0;L;;;;;N;;;;; 11D7;HANGUL JONGSEONG RIEUL-PANSIOS;Lo;0;L;;;;;N;;;;; 11D8;HANGUL JONGSEONG RIEUL-KHIEUKH;Lo;0;L;;;;;N;;;;; 11D9;HANGUL JONGSEONG RIEUL-YEORINHIEUH;Lo;0;L;;;;;N;;;;; 11DA;HANGUL JONGSEONG MIEUM-KIYEOK;Lo;0;L;;;;;N;;;;; 11DB;HANGUL JONGSEONG MIEUM-RIEUL;Lo;0;L;;;;;N;;;;; 11DC;HANGUL JONGSEONG MIEUM-PIEUP;Lo;0;L;;;;;N;;;;; 11DD;HANGUL JONGSEONG MIEUM-SIOS;Lo;0;L;;;;;N;;;;; 11DE;HANGUL JONGSEONG MIEUM-SSANGSIOS;Lo;0;L;;;;;N;;;;; 11DF;HANGUL JONGSEONG MIEUM-PANSIOS;Lo;0;L;;;;;N;;;;; 11E0;HANGUL JONGSEONG MIEUM-CHIEUCH;Lo;0;L;;;;;N;;;;; 11E1;HANGUL JONGSEONG MIEUM-HIEUH;Lo;0;L;;;;;N;;;;; 11E2;HANGUL JONGSEONG KAPYEOUNMIEUM;Lo;0;L;;;;;N;;;;; 11E3;HANGUL JONGSEONG PIEUP-RIEUL;Lo;0;L;;;;;N;;;;; 11E4;HANGUL JONGSEONG PIEUP-PHIEUPH;Lo;0;L;;;;;N;;;;; 11E5;HANGUL JONGSEONG PIEUP-HIEUH;Lo;0;L;;;;;N;;;;; 11E6;HANGUL JONGSEONG KAPYEOUNPIEUP;Lo;0;L;;;;;N;;;;; 11E7;HANGUL JONGSEONG SIOS-KIYEOK;Lo;0;L;;;;;N;;;;; 11E8;HANGUL JONGSEONG SIOS-TIKEUT;Lo;0;L;;;;;N;;;;; 11E9;HANGUL JONGSEONG SIOS-RIEUL;Lo;0;L;;;;;N;;;;; 11EA;HANGUL JONGSEONG SIOS-PIEUP;Lo;0;L;;;;;N;;;;; 11EB;HANGUL JONGSEONG PANSIOS;Lo;0;L;;;;;N;;;;; 11EC;HANGUL JONGSEONG IEUNG-KIYEOK;Lo;0;L;;;;;N;;;;; 11ED;HANGUL JONGSEONG IEUNG-SSANGKIYEOK;Lo;0;L;;;;;N;;;;; 11EE;HANGUL JONGSEONG SSANGIEUNG;Lo;0;L;;;;;N;;;;; 11EF;HANGUL JONGSEONG IEUNG-KHIEUKH;Lo;0;L;;;;;N;;;;; 11F0;HANGUL JONGSEONG YESIEUNG;Lo;0;L;;;;;N;;;;; 11F1;HANGUL JONGSEONG YESIEUNG-SIOS;Lo;0;L;;;;;N;;;;; 11F2;HANGUL JONGSEONG YESIEUNG-PANSIOS;Lo;0;L;;;;;N;;;;; 11F3;HANGUL JONGSEONG PHIEUPH-PIEUP;Lo;0;L;;;;;N;;;;; 11F4;HANGUL JONGSEONG KAPYEOUNPHIEUPH;Lo;0;L;;;;;N;;;;; 11F5;HANGUL JONGSEONG HIEUH-NIEUN;Lo;0;L;;;;;N;;;;; 11F6;HANGUL JONGSEONG HIEUH-RIEUL;Lo;0;L;;;;;N;;;;; 11F7;HANGUL JONGSEONG HIEUH-MIEUM;Lo;0;L;;;;;N;;;;; 11F8;HANGUL JONGSEONG HIEUH-PIEUP;Lo;0;L;;;;;N;;;;; 11F9;HANGUL JONGSEONG YEORINHIEUH;Lo;0;L;;;;;N;;;;; 11FA;HANGUL JONGSEONG KIYEOK-NIEUN;Lo;0;L;;;;;N;;;;; 11FB;HANGUL JONGSEONG KIYEOK-PIEUP;Lo;0;L;;;;;N;;;;; 11FC;HANGUL JONGSEONG KIYEOK-CHIEUCH;Lo;0;L;;;;;N;;;;; 11FD;HANGUL JONGSEONG KIYEOK-KHIEUKH;Lo;0;L;;;;;N;;;;; 11FE;HANGUL JONGSEONG KIYEOK-HIEUH;Lo;0;L;;;;;N;;;;; 11FF;HANGUL JONGSEONG SSANGNIEUN;Lo;0;L;;;;;N;;;;; 1200;ETHIOPIC SYLLABLE HA;Lo;0;L;;;;;N;;;;; 1201;ETHIOPIC SYLLABLE HU;Lo;0;L;;;;;N;;;;; 1202;ETHIOPIC SYLLABLE HI;Lo;0;L;;;;;N;;;;; 1203;ETHIOPIC SYLLABLE HAA;Lo;0;L;;;;;N;;;;; 1204;ETHIOPIC SYLLABLE HEE;Lo;0;L;;;;;N;;;;; 1205;ETHIOPIC SYLLABLE HE;Lo;0;L;;;;;N;;;;; 1206;ETHIOPIC SYLLABLE HO;Lo;0;L;;;;;N;;;;; 1207;ETHIOPIC SYLLABLE HOA;Lo;0;L;;;;;N;;;;; 1208;ETHIOPIC SYLLABLE LA;Lo;0;L;;;;;N;;;;; 1209;ETHIOPIC SYLLABLE LU;Lo;0;L;;;;;N;;;;; 120A;ETHIOPIC SYLLABLE LI;Lo;0;L;;;;;N;;;;; 120B;ETHIOPIC SYLLABLE LAA;Lo;0;L;;;;;N;;;;; 120C;ETHIOPIC SYLLABLE LEE;Lo;0;L;;;;;N;;;;; 120D;ETHIOPIC SYLLABLE LE;Lo;0;L;;;;;N;;;;; 120E;ETHIOPIC SYLLABLE LO;Lo;0;L;;;;;N;;;;; 120F;ETHIOPIC SYLLABLE LWA;Lo;0;L;;;;;N;;;;; 1210;ETHIOPIC SYLLABLE HHA;Lo;0;L;;;;;N;;;;; 1211;ETHIOPIC SYLLABLE HHU;Lo;0;L;;;;;N;;;;; 1212;ETHIOPIC SYLLABLE HHI;Lo;0;L;;;;;N;;;;; 1213;ETHIOPIC SYLLABLE HHAA;Lo;0;L;;;;;N;;;;; 1214;ETHIOPIC SYLLABLE HHEE;Lo;0;L;;;;;N;;;;; 1215;ETHIOPIC SYLLABLE HHE;Lo;0;L;;;;;N;;;;; 1216;ETHIOPIC SYLLABLE HHO;Lo;0;L;;;;;N;;;;; 1217;ETHIOPIC SYLLABLE HHWA;Lo;0;L;;;;;N;;;;; 1218;ETHIOPIC SYLLABLE MA;Lo;0;L;;;;;N;;;;; 1219;ETHIOPIC SYLLABLE MU;Lo;0;L;;;;;N;;;;; 121A;ETHIOPIC SYLLABLE MI;Lo;0;L;;;;;N;;;;; 121B;ETHIOPIC SYLLABLE MAA;Lo;0;L;;;;;N;;;;; 121C;ETHIOPIC SYLLABLE MEE;Lo;0;L;;;;;N;;;;; 121D;ETHIOPIC SYLLABLE ME;Lo;0;L;;;;;N;;;;; 121E;ETHIOPIC SYLLABLE MO;Lo;0;L;;;;;N;;;;; 121F;ETHIOPIC SYLLABLE MWA;Lo;0;L;;;;;N;;;;; 1220;ETHIOPIC SYLLABLE SZA;Lo;0;L;;;;;N;;;;; 1221;ETHIOPIC SYLLABLE SZU;Lo;0;L;;;;;N;;;;; 1222;ETHIOPIC SYLLABLE SZI;Lo;0;L;;;;;N;;;;; 1223;ETHIOPIC SYLLABLE SZAA;Lo;0;L;;;;;N;;;;; 1224;ETHIOPIC SYLLABLE SZEE;Lo;0;L;;;;;N;;;;; 1225;ETHIOPIC SYLLABLE SZE;Lo;0;L;;;;;N;;;;; 1226;ETHIOPIC SYLLABLE SZO;Lo;0;L;;;;;N;;;;; 1227;ETHIOPIC SYLLABLE SZWA;Lo;0;L;;;;;N;;;;; 1228;ETHIOPIC SYLLABLE RA;Lo;0;L;;;;;N;;;;; 1229;ETHIOPIC SYLLABLE RU;Lo;0;L;;;;;N;;;;; 122A;ETHIOPIC SYLLABLE RI;Lo;0;L;;;;;N;;;;; 122B;ETHIOPIC SYLLABLE RAA;Lo;0;L;;;;;N;;;;; 122C;ETHIOPIC SYLLABLE REE;Lo;0;L;;;;;N;;;;; 122D;ETHIOPIC SYLLABLE RE;Lo;0;L;;;;;N;;;;; 122E;ETHIOPIC SYLLABLE RO;Lo;0;L;;;;;N;;;;; 122F;ETHIOPIC SYLLABLE RWA;Lo;0;L;;;;;N;;;;; 1230;ETHIOPIC SYLLABLE SA;Lo;0;L;;;;;N;;;;; 1231;ETHIOPIC SYLLABLE SU;Lo;0;L;;;;;N;;;;; 1232;ETHIOPIC SYLLABLE SI;Lo;0;L;;;;;N;;;;; 1233;ETHIOPIC SYLLABLE SAA;Lo;0;L;;;;;N;;;;; 1234;ETHIOPIC SYLLABLE SEE;Lo;0;L;;;;;N;;;;; 1235;ETHIOPIC SYLLABLE SE;Lo;0;L;;;;;N;;;;; 1236;ETHIOPIC SYLLABLE SO;Lo;0;L;;;;;N;;;;; 1237;ETHIOPIC SYLLABLE SWA;Lo;0;L;;;;;N;;;;; 1238;ETHIOPIC SYLLABLE SHA;Lo;0;L;;;;;N;;;;; 1239;ETHIOPIC SYLLABLE SHU;Lo;0;L;;;;;N;;;;; 123A;ETHIOPIC SYLLABLE SHI;Lo;0;L;;;;;N;;;;; 123B;ETHIOPIC SYLLABLE SHAA;Lo;0;L;;;;;N;;;;; 123C;ETHIOPIC SYLLABLE SHEE;Lo;0;L;;;;;N;;;;; 123D;ETHIOPIC SYLLABLE SHE;Lo;0;L;;;;;N;;;;; 123E;ETHIOPIC SYLLABLE SHO;Lo;0;L;;;;;N;;;;; 123F;ETHIOPIC SYLLABLE SHWA;Lo;0;L;;;;;N;;;;; 1240;ETHIOPIC SYLLABLE QA;Lo;0;L;;;;;N;;;;; 1241;ETHIOPIC SYLLABLE QU;Lo;0;L;;;;;N;;;;; 1242;ETHIOPIC SYLLABLE QI;Lo;0;L;;;;;N;;;;; 1243;ETHIOPIC SYLLABLE QAA;Lo;0;L;;;;;N;;;;; 1244;ETHIOPIC SYLLABLE QEE;Lo;0;L;;;;;N;;;;; 1245;ETHIOPIC SYLLABLE QE;Lo;0;L;;;;;N;;;;; 1246;ETHIOPIC SYLLABLE QO;Lo;0;L;;;;;N;;;;; 1247;ETHIOPIC SYLLABLE QOA;Lo;0;L;;;;;N;;;;; 1248;ETHIOPIC SYLLABLE QWA;Lo;0;L;;;;;N;;;;; 124A;ETHIOPIC SYLLABLE QWI;Lo;0;L;;;;;N;;;;; 124B;ETHIOPIC SYLLABLE QWAA;Lo;0;L;;;;;N;;;;; 124C;ETHIOPIC SYLLABLE QWEE;Lo;0;L;;;;;N;;;;; 124D;ETHIOPIC SYLLABLE QWE;Lo;0;L;;;;;N;;;;; 1250;ETHIOPIC SYLLABLE QHA;Lo;0;L;;;;;N;;;;; 1251;ETHIOPIC SYLLABLE QHU;Lo;0;L;;;;;N;;;;; 1252;ETHIOPIC SYLLABLE QHI;Lo;0;L;;;;;N;;;;; 1253;ETHIOPIC SYLLABLE QHAA;Lo;0;L;;;;;N;;;;; 1254;ETHIOPIC SYLLABLE QHEE;Lo;0;L;;;;;N;;;;; 1255;ETHIOPIC SYLLABLE QHE;Lo;0;L;;;;;N;;;;; 1256;ETHIOPIC SYLLABLE QHO;Lo;0;L;;;;;N;;;;; 1258;ETHIOPIC SYLLABLE QHWA;Lo;0;L;;;;;N;;;;; 125A;ETHIOPIC SYLLABLE QHWI;Lo;0;L;;;;;N;;;;; 125B;ETHIOPIC SYLLABLE QHWAA;Lo;0;L;;;;;N;;;;; 125C;ETHIOPIC SYLLABLE QHWEE;Lo;0;L;;;;;N;;;;; 125D;ETHIOPIC SYLLABLE QHWE;Lo;0;L;;;;;N;;;;; 1260;ETHIOPIC SYLLABLE BA;Lo;0;L;;;;;N;;;;; 1261;ETHIOPIC SYLLABLE BU;Lo;0;L;;;;;N;;;;; 1262;ETHIOPIC SYLLABLE BI;Lo;0;L;;;;;N;;;;; 1263;ETHIOPIC SYLLABLE BAA;Lo;0;L;;;;;N;;;;; 1264;ETHIOPIC SYLLABLE BEE;Lo;0;L;;;;;N;;;;; 1265;ETHIOPIC SYLLABLE BE;Lo;0;L;;;;;N;;;;; 1266;ETHIOPIC SYLLABLE BO;Lo;0;L;;;;;N;;;;; 1267;ETHIOPIC SYLLABLE BWA;Lo;0;L;;;;;N;;;;; 1268;ETHIOPIC SYLLABLE VA;Lo;0;L;;;;;N;;;;; 1269;ETHIOPIC SYLLABLE VU;Lo;0;L;;;;;N;;;;; 126A;ETHIOPIC SYLLABLE VI;Lo;0;L;;;;;N;;;;; 126B;ETHIOPIC SYLLABLE VAA;Lo;0;L;;;;;N;;;;; 126C;ETHIOPIC SYLLABLE VEE;Lo;0;L;;;;;N;;;;; 126D;ETHIOPIC SYLLABLE VE;Lo;0;L;;;;;N;;;;; 126E;ETHIOPIC SYLLABLE VO;Lo;0;L;;;;;N;;;;; 126F;ETHIOPIC SYLLABLE VWA;Lo;0;L;;;;;N;;;;; 1270;ETHIOPIC SYLLABLE TA;Lo;0;L;;;;;N;;;;; 1271;ETHIOPIC SYLLABLE TU;Lo;0;L;;;;;N;;;;; 1272;ETHIOPIC SYLLABLE TI;Lo;0;L;;;;;N;;;;; 1273;ETHIOPIC SYLLABLE TAA;Lo;0;L;;;;;N;;;;; 1274;ETHIOPIC SYLLABLE TEE;Lo;0;L;;;;;N;;;;; 1275;ETHIOPIC SYLLABLE TE;Lo;0;L;;;;;N;;;;; 1276;ETHIOPIC SYLLABLE TO;Lo;0;L;;;;;N;;;;; 1277;ETHIOPIC SYLLABLE TWA;Lo;0;L;;;;;N;;;;; 1278;ETHIOPIC SYLLABLE CA;Lo;0;L;;;;;N;;;;; 1279;ETHIOPIC SYLLABLE CU;Lo;0;L;;;;;N;;;;; 127A;ETHIOPIC SYLLABLE CI;Lo;0;L;;;;;N;;;;; 127B;ETHIOPIC SYLLABLE CAA;Lo;0;L;;;;;N;;;;; 127C;ETHIOPIC SYLLABLE CEE;Lo;0;L;;;;;N;;;;; 127D;ETHIOPIC SYLLABLE CE;Lo;0;L;;;;;N;;;;; 127E;ETHIOPIC SYLLABLE CO;Lo;0;L;;;;;N;;;;; 127F;ETHIOPIC SYLLABLE CWA;Lo;0;L;;;;;N;;;;; 1280;ETHIOPIC SYLLABLE XA;Lo;0;L;;;;;N;;;;; 1281;ETHIOPIC SYLLABLE XU;Lo;0;L;;;;;N;;;;; 1282;ETHIOPIC SYLLABLE XI;Lo;0;L;;;;;N;;;;; 1283;ETHIOPIC SYLLABLE XAA;Lo;0;L;;;;;N;;;;; 1284;ETHIOPIC SYLLABLE XEE;Lo;0;L;;;;;N;;;;; 1285;ETHIOPIC SYLLABLE XE;Lo;0;L;;;;;N;;;;; 1286;ETHIOPIC SYLLABLE XO;Lo;0;L;;;;;N;;;;; 1287;ETHIOPIC SYLLABLE XOA;Lo;0;L;;;;;N;;;;; 1288;ETHIOPIC SYLLABLE XWA;Lo;0;L;;;;;N;;;;; 128A;ETHIOPIC SYLLABLE XWI;Lo;0;L;;;;;N;;;;; 128B;ETHIOPIC SYLLABLE XWAA;Lo;0;L;;;;;N;;;;; 128C;ETHIOPIC SYLLABLE XWEE;Lo;0;L;;;;;N;;;;; 128D;ETHIOPIC SYLLABLE XWE;Lo;0;L;;;;;N;;;;; 1290;ETHIOPIC SYLLABLE NA;Lo;0;L;;;;;N;;;;; 1291;ETHIOPIC SYLLABLE NU;Lo;0;L;;;;;N;;;;; 1292;ETHIOPIC SYLLABLE NI;Lo;0;L;;;;;N;;;;; 1293;ETHIOPIC SYLLABLE NAA;Lo;0;L;;;;;N;;;;; 1294;ETHIOPIC SYLLABLE NEE;Lo;0;L;;;;;N;;;;; 1295;ETHIOPIC SYLLABLE NE;Lo;0;L;;;;;N;;;;; 1296;ETHIOPIC SYLLABLE NO;Lo;0;L;;;;;N;;;;; 1297;ETHIOPIC SYLLABLE NWA;Lo;0;L;;;;;N;;;;; 1298;ETHIOPIC SYLLABLE NYA;Lo;0;L;;;;;N;;;;; 1299;ETHIOPIC SYLLABLE NYU;Lo;0;L;;;;;N;;;;; 129A;ETHIOPIC SYLLABLE NYI;Lo;0;L;;;;;N;;;;; 129B;ETHIOPIC SYLLABLE NYAA;Lo;0;L;;;;;N;;;;; 129C;ETHIOPIC SYLLABLE NYEE;Lo;0;L;;;;;N;;;;; 129D;ETHIOPIC SYLLABLE NYE;Lo;0;L;;;;;N;;;;; 129E;ETHIOPIC SYLLABLE NYO;Lo;0;L;;;;;N;;;;; 129F;ETHIOPIC SYLLABLE NYWA;Lo;0;L;;;;;N;;;;; 12A0;ETHIOPIC SYLLABLE GLOTTAL A;Lo;0;L;;;;;N;;;;; 12A1;ETHIOPIC SYLLABLE GLOTTAL U;Lo;0;L;;;;;N;;;;; 12A2;ETHIOPIC SYLLABLE GLOTTAL I;Lo;0;L;;;;;N;;;;; 12A3;ETHIOPIC SYLLABLE GLOTTAL AA;Lo;0;L;;;;;N;;;;; 12A4;ETHIOPIC SYLLABLE GLOTTAL EE;Lo;0;L;;;;;N;;;;; 12A5;ETHIOPIC SYLLABLE GLOTTAL E;Lo;0;L;;;;;N;;;;; 12A6;ETHIOPIC SYLLABLE GLOTTAL O;Lo;0;L;;;;;N;;;;; 12A7;ETHIOPIC SYLLABLE GLOTTAL WA;Lo;0;L;;;;;N;;;;; 12A8;ETHIOPIC SYLLABLE KA;Lo;0;L;;;;;N;;;;; 12A9;ETHIOPIC SYLLABLE KU;Lo;0;L;;;;;N;;;;; 12AA;ETHIOPIC SYLLABLE KI;Lo;0;L;;;;;N;;;;; 12AB;ETHIOPIC SYLLABLE KAA;Lo;0;L;;;;;N;;;;; 12AC;ETHIOPIC SYLLABLE KEE;Lo;0;L;;;;;N;;;;; 12AD;ETHIOPIC SYLLABLE KE;Lo;0;L;;;;;N;;;;; 12AE;ETHIOPIC SYLLABLE KO;Lo;0;L;;;;;N;;;;; 12AF;ETHIOPIC SYLLABLE KOA;Lo;0;L;;;;;N;;;;; 12B0;ETHIOPIC SYLLABLE KWA;Lo;0;L;;;;;N;;;;; 12B2;ETHIOPIC SYLLABLE KWI;Lo;0;L;;;;;N;;;;; 12B3;ETHIOPIC SYLLABLE KWAA;Lo;0;L;;;;;N;;;;; 12B4;ETHIOPIC SYLLABLE KWEE;Lo;0;L;;;;;N;;;;; 12B5;ETHIOPIC SYLLABLE KWE;Lo;0;L;;;;;N;;;;; 12B8;ETHIOPIC SYLLABLE KXA;Lo;0;L;;;;;N;;;;; 12B9;ETHIOPIC SYLLABLE KXU;Lo;0;L;;;;;N;;;;; 12BA;ETHIOPIC SYLLABLE KXI;Lo;0;L;;;;;N;;;;; 12BB;ETHIOPIC SYLLABLE KXAA;Lo;0;L;;;;;N;;;;; 12BC;ETHIOPIC SYLLABLE KXEE;Lo;0;L;;;;;N;;;;; 12BD;ETHIOPIC SYLLABLE KXE;Lo;0;L;;;;;N;;;;; 12BE;ETHIOPIC SYLLABLE KXO;Lo;0;L;;;;;N;;;;; 12C0;ETHIOPIC SYLLABLE KXWA;Lo;0;L;;;;;N;;;;; 12C2;ETHIOPIC SYLLABLE KXWI;Lo;0;L;;;;;N;;;;; 12C3;ETHIOPIC SYLLABLE KXWAA;Lo;0;L;;;;;N;;;;; 12C4;ETHIOPIC SYLLABLE KXWEE;Lo;0;L;;;;;N;;;;; 12C5;ETHIOPIC SYLLABLE KXWE;Lo;0;L;;;;;N;;;;; 12C8;ETHIOPIC SYLLABLE WA;Lo;0;L;;;;;N;;;;; 12C9;ETHIOPIC SYLLABLE WU;Lo;0;L;;;;;N;;;;; 12CA;ETHIOPIC SYLLABLE WI;Lo;0;L;;;;;N;;;;; 12CB;ETHIOPIC SYLLABLE WAA;Lo;0;L;;;;;N;;;;; 12CC;ETHIOPIC SYLLABLE WEE;Lo;0;L;;;;;N;;;;; 12CD;ETHIOPIC SYLLABLE WE;Lo;0;L;;;;;N;;;;; 12CE;ETHIOPIC SYLLABLE WO;Lo;0;L;;;;;N;;;;; 12CF;ETHIOPIC SYLLABLE WOA;Lo;0;L;;;;;N;;;;; 12D0;ETHIOPIC SYLLABLE PHARYNGEAL A;Lo;0;L;;;;;N;;;;; 12D1;ETHIOPIC SYLLABLE PHARYNGEAL U;Lo;0;L;;;;;N;;;;; 12D2;ETHIOPIC SYLLABLE PHARYNGEAL I;Lo;0;L;;;;;N;;;;; 12D3;ETHIOPIC SYLLABLE PHARYNGEAL AA;Lo;0;L;;;;;N;;;;; 12D4;ETHIOPIC SYLLABLE PHARYNGEAL EE;Lo;0;L;;;;;N;;;;; 12D5;ETHIOPIC SYLLABLE PHARYNGEAL E;Lo;0;L;;;;;N;;;;; 12D6;ETHIOPIC SYLLABLE PHARYNGEAL O;Lo;0;L;;;;;N;;;;; 12D8;ETHIOPIC SYLLABLE ZA;Lo;0;L;;;;;N;;;;; 12D9;ETHIOPIC SYLLABLE ZU;Lo;0;L;;;;;N;;;;; 12DA;ETHIOPIC SYLLABLE ZI;Lo;0;L;;;;;N;;;;; 12DB;ETHIOPIC SYLLABLE ZAA;Lo;0;L;;;;;N;;;;; 12DC;ETHIOPIC SYLLABLE ZEE;Lo;0;L;;;;;N;;;;; 12DD;ETHIOPIC SYLLABLE ZE;Lo;0;L;;;;;N;;;;; 12DE;ETHIOPIC SYLLABLE ZO;Lo;0;L;;;;;N;;;;; 12DF;ETHIOPIC SYLLABLE ZWA;Lo;0;L;;;;;N;;;;; 12E0;ETHIOPIC SYLLABLE ZHA;Lo;0;L;;;;;N;;;;; 12E1;ETHIOPIC SYLLABLE ZHU;Lo;0;L;;;;;N;;;;; 12E2;ETHIOPIC SYLLABLE ZHI;Lo;0;L;;;;;N;;;;; 12E3;ETHIOPIC SYLLABLE ZHAA;Lo;0;L;;;;;N;;;;; 12E4;ETHIOPIC SYLLABLE ZHEE;Lo;0;L;;;;;N;;;;; 12E5;ETHIOPIC SYLLABLE ZHE;Lo;0;L;;;;;N;;;;; 12E6;ETHIOPIC SYLLABLE ZHO;Lo;0;L;;;;;N;;;;; 12E7;ETHIOPIC SYLLABLE ZHWA;Lo;0;L;;;;;N;;;;; 12E8;ETHIOPIC SYLLABLE YA;Lo;0;L;;;;;N;;;;; 12E9;ETHIOPIC SYLLABLE YU;Lo;0;L;;;;;N;;;;; 12EA;ETHIOPIC SYLLABLE YI;Lo;0;L;;;;;N;;;;; 12EB;ETHIOPIC SYLLABLE YAA;Lo;0;L;;;;;N;;;;; 12EC;ETHIOPIC SYLLABLE YEE;Lo;0;L;;;;;N;;;;; 12ED;ETHIOPIC SYLLABLE YE;Lo;0;L;;;;;N;;;;; 12EE;ETHIOPIC SYLLABLE YO;Lo;0;L;;;;;N;;;;; 12EF;ETHIOPIC SYLLABLE YOA;Lo;0;L;;;;;N;;;;; 12F0;ETHIOPIC SYLLABLE DA;Lo;0;L;;;;;N;;;;; 12F1;ETHIOPIC SYLLABLE DU;Lo;0;L;;;;;N;;;;; 12F2;ETHIOPIC SYLLABLE DI;Lo;0;L;;;;;N;;;;; 12F3;ETHIOPIC SYLLABLE DAA;Lo;0;L;;;;;N;;;;; 12F4;ETHIOPIC SYLLABLE DEE;Lo;0;L;;;;;N;;;;; 12F5;ETHIOPIC SYLLABLE DE;Lo;0;L;;;;;N;;;;; 12F6;ETHIOPIC SYLLABLE DO;Lo;0;L;;;;;N;;;;; 12F7;ETHIOPIC SYLLABLE DWA;Lo;0;L;;;;;N;;;;; 12F8;ETHIOPIC SYLLABLE DDA;Lo;0;L;;;;;N;;;;; 12F9;ETHIOPIC SYLLABLE DDU;Lo;0;L;;;;;N;;;;; 12FA;ETHIOPIC SYLLABLE DDI;Lo;0;L;;;;;N;;;;; 12FB;ETHIOPIC SYLLABLE DDAA;Lo;0;L;;;;;N;;;;; 12FC;ETHIOPIC SYLLABLE DDEE;Lo;0;L;;;;;N;;;;; 12FD;ETHIOPIC SYLLABLE DDE;Lo;0;L;;;;;N;;;;; 12FE;ETHIOPIC SYLLABLE DDO;Lo;0;L;;;;;N;;;;; 12FF;ETHIOPIC SYLLABLE DDWA;Lo;0;L;;;;;N;;;;; 1300;ETHIOPIC SYLLABLE JA;Lo;0;L;;;;;N;;;;; 1301;ETHIOPIC SYLLABLE JU;Lo;0;L;;;;;N;;;;; 1302;ETHIOPIC SYLLABLE JI;Lo;0;L;;;;;N;;;;; 1303;ETHIOPIC SYLLABLE JAA;Lo;0;L;;;;;N;;;;; 1304;ETHIOPIC SYLLABLE JEE;Lo;0;L;;;;;N;;;;; 1305;ETHIOPIC SYLLABLE JE;Lo;0;L;;;;;N;;;;; 1306;ETHIOPIC SYLLABLE JO;Lo;0;L;;;;;N;;;;; 1307;ETHIOPIC SYLLABLE JWA;Lo;0;L;;;;;N;;;;; 1308;ETHIOPIC SYLLABLE GA;Lo;0;L;;;;;N;;;;; 1309;ETHIOPIC SYLLABLE GU;Lo;0;L;;;;;N;;;;; 130A;ETHIOPIC SYLLABLE GI;Lo;0;L;;;;;N;;;;; 130B;ETHIOPIC SYLLABLE GAA;Lo;0;L;;;;;N;;;;; 130C;ETHIOPIC SYLLABLE GEE;Lo;0;L;;;;;N;;;;; 130D;ETHIOPIC SYLLABLE GE;Lo;0;L;;;;;N;;;;; 130E;ETHIOPIC SYLLABLE GO;Lo;0;L;;;;;N;;;;; 130F;ETHIOPIC SYLLABLE GOA;Lo;0;L;;;;;N;;;;; 1310;ETHIOPIC SYLLABLE GWA;Lo;0;L;;;;;N;;;;; 1312;ETHIOPIC SYLLABLE GWI;Lo;0;L;;;;;N;;;;; 1313;ETHIOPIC SYLLABLE GWAA;Lo;0;L;;;;;N;;;;; 1314;ETHIOPIC SYLLABLE GWEE;Lo;0;L;;;;;N;;;;; 1315;ETHIOPIC SYLLABLE GWE;Lo;0;L;;;;;N;;;;; 1318;ETHIOPIC SYLLABLE GGA;Lo;0;L;;;;;N;;;;; 1319;ETHIOPIC SYLLABLE GGU;Lo;0;L;;;;;N;;;;; 131A;ETHIOPIC SYLLABLE GGI;Lo;0;L;;;;;N;;;;; 131B;ETHIOPIC SYLLABLE GGAA;Lo;0;L;;;;;N;;;;; 131C;ETHIOPIC SYLLABLE GGEE;Lo;0;L;;;;;N;;;;; 131D;ETHIOPIC SYLLABLE GGE;Lo;0;L;;;;;N;;;;; 131E;ETHIOPIC SYLLABLE GGO;Lo;0;L;;;;;N;;;;; 131F;ETHIOPIC SYLLABLE GGWAA;Lo;0;L;;;;;N;;;;; 1320;ETHIOPIC SYLLABLE THA;Lo;0;L;;;;;N;;;;; 1321;ETHIOPIC SYLLABLE THU;Lo;0;L;;;;;N;;;;; 1322;ETHIOPIC SYLLABLE THI;Lo;0;L;;;;;N;;;;; 1323;ETHIOPIC SYLLABLE THAA;Lo;0;L;;;;;N;;;;; 1324;ETHIOPIC SYLLABLE THEE;Lo;0;L;;;;;N;;;;; 1325;ETHIOPIC SYLLABLE THE;Lo;0;L;;;;;N;;;;; 1326;ETHIOPIC SYLLABLE THO;Lo;0;L;;;;;N;;;;; 1327;ETHIOPIC SYLLABLE THWA;Lo;0;L;;;;;N;;;;; 1328;ETHIOPIC SYLLABLE CHA;Lo;0;L;;;;;N;;;;; 1329;ETHIOPIC SYLLABLE CHU;Lo;0;L;;;;;N;;;;; 132A;ETHIOPIC SYLLABLE CHI;Lo;0;L;;;;;N;;;;; 132B;ETHIOPIC SYLLABLE CHAA;Lo;0;L;;;;;N;;;;; 132C;ETHIOPIC SYLLABLE CHEE;Lo;0;L;;;;;N;;;;; 132D;ETHIOPIC SYLLABLE CHE;Lo;0;L;;;;;N;;;;; 132E;ETHIOPIC SYLLABLE CHO;Lo;0;L;;;;;N;;;;; 132F;ETHIOPIC SYLLABLE CHWA;Lo;0;L;;;;;N;;;;; 1330;ETHIOPIC SYLLABLE PHA;Lo;0;L;;;;;N;;;;; 1331;ETHIOPIC SYLLABLE PHU;Lo;0;L;;;;;N;;;;; 1332;ETHIOPIC SYLLABLE PHI;Lo;0;L;;;;;N;;;;; 1333;ETHIOPIC SYLLABLE PHAA;Lo;0;L;;;;;N;;;;; 1334;ETHIOPIC SYLLABLE PHEE;Lo;0;L;;;;;N;;;;; 1335;ETHIOPIC SYLLABLE PHE;Lo;0;L;;;;;N;;;;; 1336;ETHIOPIC SYLLABLE PHO;Lo;0;L;;;;;N;;;;; 1337;ETHIOPIC SYLLABLE PHWA;Lo;0;L;;;;;N;;;;; 1338;ETHIOPIC SYLLABLE TSA;Lo;0;L;;;;;N;;;;; 1339;ETHIOPIC SYLLABLE TSU;Lo;0;L;;;;;N;;;;; 133A;ETHIOPIC SYLLABLE TSI;Lo;0;L;;;;;N;;;;; 133B;ETHIOPIC SYLLABLE TSAA;Lo;0;L;;;;;N;;;;; 133C;ETHIOPIC SYLLABLE TSEE;Lo;0;L;;;;;N;;;;; 133D;ETHIOPIC SYLLABLE TSE;Lo;0;L;;;;;N;;;;; 133E;ETHIOPIC SYLLABLE TSO;Lo;0;L;;;;;N;;;;; 133F;ETHIOPIC SYLLABLE TSWA;Lo;0;L;;;;;N;;;;; 1340;ETHIOPIC SYLLABLE TZA;Lo;0;L;;;;;N;;;;; 1341;ETHIOPIC SYLLABLE TZU;Lo;0;L;;;;;N;;;;; 1342;ETHIOPIC SYLLABLE TZI;Lo;0;L;;;;;N;;;;; 1343;ETHIOPIC SYLLABLE TZAA;Lo;0;L;;;;;N;;;;; 1344;ETHIOPIC SYLLABLE TZEE;Lo;0;L;;;;;N;;;;; 1345;ETHIOPIC SYLLABLE TZE;Lo;0;L;;;;;N;;;;; 1346;ETHIOPIC SYLLABLE TZO;Lo;0;L;;;;;N;;;;; 1347;ETHIOPIC SYLLABLE TZOA;Lo;0;L;;;;;N;;;;; 1348;ETHIOPIC SYLLABLE FA;Lo;0;L;;;;;N;;;;; 1349;ETHIOPIC SYLLABLE FU;Lo;0;L;;;;;N;;;;; 134A;ETHIOPIC SYLLABLE FI;Lo;0;L;;;;;N;;;;; 134B;ETHIOPIC SYLLABLE FAA;Lo;0;L;;;;;N;;;;; 134C;ETHIOPIC SYLLABLE FEE;Lo;0;L;;;;;N;;;;; 134D;ETHIOPIC SYLLABLE FE;Lo;0;L;;;;;N;;;;; 134E;ETHIOPIC SYLLABLE FO;Lo;0;L;;;;;N;;;;; 134F;ETHIOPIC SYLLABLE FWA;Lo;0;L;;;;;N;;;;; 1350;ETHIOPIC SYLLABLE PA;Lo;0;L;;;;;N;;;;; 1351;ETHIOPIC SYLLABLE PU;Lo;0;L;;;;;N;;;;; 1352;ETHIOPIC SYLLABLE PI;Lo;0;L;;;;;N;;;;; 1353;ETHIOPIC SYLLABLE PAA;Lo;0;L;;;;;N;;;;; 1354;ETHIOPIC SYLLABLE PEE;Lo;0;L;;;;;N;;;;; 1355;ETHIOPIC SYLLABLE PE;Lo;0;L;;;;;N;;;;; 1356;ETHIOPIC SYLLABLE PO;Lo;0;L;;;;;N;;;;; 1357;ETHIOPIC SYLLABLE PWA;Lo;0;L;;;;;N;;;;; 1358;ETHIOPIC SYLLABLE RYA;Lo;0;L;;;;;N;;;;; 1359;ETHIOPIC SYLLABLE MYA;Lo;0;L;;;;;N;;;;; 135A;ETHIOPIC SYLLABLE FYA;Lo;0;L;;;;;N;;;;; 135D;ETHIOPIC COMBINING GEMINATION AND VOWEL LENGTH MARK;Mn;230;NSM;;;;;N;;;;; 135E;ETHIOPIC COMBINING VOWEL LENGTH MARK;Mn;230;NSM;;;;;N;;;;; 135F;ETHIOPIC COMBINING GEMINATION MARK;Mn;230;NSM;;;;;N;;;;; 1360;ETHIOPIC SECTION MARK;Po;0;L;;;;;N;;;;; 1361;ETHIOPIC WORDSPACE;Po;0;L;;;;;N;;;;; 1362;ETHIOPIC FULL STOP;Po;0;L;;;;;N;;;;; 1363;ETHIOPIC COMMA;Po;0;L;;;;;N;;;;; 1364;ETHIOPIC SEMICOLON;Po;0;L;;;;;N;;;;; 1365;ETHIOPIC COLON;Po;0;L;;;;;N;;;;; 1366;ETHIOPIC PREFACE COLON;Po;0;L;;;;;N;;;;; 1367;ETHIOPIC QUESTION MARK;Po;0;L;;;;;N;;;;; 1368;ETHIOPIC PARAGRAPH SEPARATOR;Po;0;L;;;;;N;;;;; 1369;ETHIOPIC DIGIT ONE;No;0;L;;;1;1;N;;;;; 136A;ETHIOPIC DIGIT TWO;No;0;L;;;2;2;N;;;;; 136B;ETHIOPIC DIGIT THREE;No;0;L;;;3;3;N;;;;; 136C;ETHIOPIC DIGIT FOUR;No;0;L;;;4;4;N;;;;; 136D;ETHIOPIC DIGIT FIVE;No;0;L;;;5;5;N;;;;; 136E;ETHIOPIC DIGIT SIX;No;0;L;;;6;6;N;;;;; 136F;ETHIOPIC DIGIT SEVEN;No;0;L;;;7;7;N;;;;; 1370;ETHIOPIC DIGIT EIGHT;No;0;L;;;8;8;N;;;;; 1371;ETHIOPIC DIGIT NINE;No;0;L;;;9;9;N;;;;; 1372;ETHIOPIC NUMBER TEN;No;0;L;;;;10;N;;;;; 1373;ETHIOPIC NUMBER TWENTY;No;0;L;;;;20;N;;;;; 1374;ETHIOPIC NUMBER THIRTY;No;0;L;;;;30;N;;;;; 1375;ETHIOPIC NUMBER FORTY;No;0;L;;;;40;N;;;;; 1376;ETHIOPIC NUMBER FIFTY;No;0;L;;;;50;N;;;;; 1377;ETHIOPIC NUMBER SIXTY;No;0;L;;;;60;N;;;;; 1378;ETHIOPIC NUMBER SEVENTY;No;0;L;;;;70;N;;;;; 1379;ETHIOPIC NUMBER EIGHTY;No;0;L;;;;80;N;;;;; 137A;ETHIOPIC NUMBER NINETY;No;0;L;;;;90;N;;;;; 137B;ETHIOPIC NUMBER HUNDRED;No;0;L;;;;100;N;;;;; 137C;ETHIOPIC NUMBER TEN THOUSAND;No;0;L;;;;10000;N;;;;; 1380;ETHIOPIC SYLLABLE SEBATBEIT MWA;Lo;0;L;;;;;N;;;;; 1381;ETHIOPIC SYLLABLE MWI;Lo;0;L;;;;;N;;;;; 1382;ETHIOPIC SYLLABLE MWEE;Lo;0;L;;;;;N;;;;; 1383;ETHIOPIC SYLLABLE MWE;Lo;0;L;;;;;N;;;;; 1384;ETHIOPIC SYLLABLE SEBATBEIT BWA;Lo;0;L;;;;;N;;;;; 1385;ETHIOPIC SYLLABLE BWI;Lo;0;L;;;;;N;;;;; 1386;ETHIOPIC SYLLABLE BWEE;Lo;0;L;;;;;N;;;;; 1387;ETHIOPIC SYLLABLE BWE;Lo;0;L;;;;;N;;;;; 1388;ETHIOPIC SYLLABLE SEBATBEIT FWA;Lo;0;L;;;;;N;;;;; 1389;ETHIOPIC SYLLABLE FWI;Lo;0;L;;;;;N;;;;; 138A;ETHIOPIC SYLLABLE FWEE;Lo;0;L;;;;;N;;;;; 138B;ETHIOPIC SYLLABLE FWE;Lo;0;L;;;;;N;;;;; 138C;ETHIOPIC SYLLABLE SEBATBEIT PWA;Lo;0;L;;;;;N;;;;; 138D;ETHIOPIC SYLLABLE PWI;Lo;0;L;;;;;N;;;;; 138E;ETHIOPIC SYLLABLE PWEE;Lo;0;L;;;;;N;;;;; 138F;ETHIOPIC SYLLABLE PWE;Lo;0;L;;;;;N;;;;; 1390;ETHIOPIC TONAL MARK YIZET;So;0;ON;;;;;N;;;;; 1391;ETHIOPIC TONAL MARK DERET;So;0;ON;;;;;N;;;;; 1392;ETHIOPIC TONAL MARK RIKRIK;So;0;ON;;;;;N;;;;; 1393;ETHIOPIC TONAL MARK SHORT RIKRIK;So;0;ON;;;;;N;;;;; 1394;ETHIOPIC TONAL MARK DIFAT;So;0;ON;;;;;N;;;;; 1395;ETHIOPIC TONAL MARK KENAT;So;0;ON;;;;;N;;;;; 1396;ETHIOPIC TONAL MARK CHIRET;So;0;ON;;;;;N;;;;; 1397;ETHIOPIC TONAL MARK HIDET;So;0;ON;;;;;N;;;;; 1398;ETHIOPIC TONAL MARK DERET-HIDET;So;0;ON;;;;;N;;;;; 1399;ETHIOPIC TONAL MARK KURT;So;0;ON;;;;;N;;;;; 13A0;CHEROKEE LETTER A;Lo;0;L;;;;;N;;;;; 13A1;CHEROKEE LETTER E;Lo;0;L;;;;;N;;;;; 13A2;CHEROKEE LETTER I;Lo;0;L;;;;;N;;;;; 13A3;CHEROKEE LETTER O;Lo;0;L;;;;;N;;;;; 13A4;CHEROKEE LETTER U;Lo;0;L;;;;;N;;;;; 13A5;CHEROKEE LETTER V;Lo;0;L;;;;;N;;;;; 13A6;CHEROKEE LETTER GA;Lo;0;L;;;;;N;;;;; 13A7;CHEROKEE LETTER KA;Lo;0;L;;;;;N;;;;; 13A8;CHEROKEE LETTER GE;Lo;0;L;;;;;N;;;;; 13A9;CHEROKEE LETTER GI;Lo;0;L;;;;;N;;;;; 13AA;CHEROKEE LETTER GO;Lo;0;L;;;;;N;;;;; 13AB;CHEROKEE LETTER GU;Lo;0;L;;;;;N;;;;; 13AC;CHEROKEE LETTER GV;Lo;0;L;;;;;N;;;;; 13AD;CHEROKEE LETTER HA;Lo;0;L;;;;;N;;;;; 13AE;CHEROKEE LETTER HE;Lo;0;L;;;;;N;;;;; 13AF;CHEROKEE LETTER HI;Lo;0;L;;;;;N;;;;; 13B0;CHEROKEE LETTER HO;Lo;0;L;;;;;N;;;;; 13B1;CHEROKEE LETTER HU;Lo;0;L;;;;;N;;;;; 13B2;CHEROKEE LETTER HV;Lo;0;L;;;;;N;;;;; 13B3;CHEROKEE LETTER LA;Lo;0;L;;;;;N;;;;; 13B4;CHEROKEE LETTER LE;Lo;0;L;;;;;N;;;;; 13B5;CHEROKEE LETTER LI;Lo;0;L;;;;;N;;;;; 13B6;CHEROKEE LETTER LO;Lo;0;L;;;;;N;;;;; 13B7;CHEROKEE LETTER LU;Lo;0;L;;;;;N;;;;; 13B8;CHEROKEE LETTER LV;Lo;0;L;;;;;N;;;;; 13B9;CHEROKEE LETTER MA;Lo;0;L;;;;;N;;;;; 13BA;CHEROKEE LETTER ME;Lo;0;L;;;;;N;;;;; 13BB;CHEROKEE LETTER MI;Lo;0;L;;;;;N;;;;; 13BC;CHEROKEE LETTER MO;Lo;0;L;;;;;N;;;;; 13BD;CHEROKEE LETTER MU;Lo;0;L;;;;;N;;;;; 13BE;CHEROKEE LETTER NA;Lo;0;L;;;;;N;;;;; 13BF;CHEROKEE LETTER HNA;Lo;0;L;;;;;N;;;;; 13C0;CHEROKEE LETTER NAH;Lo;0;L;;;;;N;;;;; 13C1;CHEROKEE LETTER NE;Lo;0;L;;;;;N;;;;; 13C2;CHEROKEE LETTER NI;Lo;0;L;;;;;N;;;;; 13C3;CHEROKEE LETTER NO;Lo;0;L;;;;;N;;;;; 13C4;CHEROKEE LETTER NU;Lo;0;L;;;;;N;;;;; 13C5;CHEROKEE LETTER NV;Lo;0;L;;;;;N;;;;; 13C6;CHEROKEE LETTER QUA;Lo;0;L;;;;;N;;;;; 13C7;CHEROKEE LETTER QUE;Lo;0;L;;;;;N;;;;; 13C8;CHEROKEE LETTER QUI;Lo;0;L;;;;;N;;;;; 13C9;CHEROKEE LETTER QUO;Lo;0;L;;;;;N;;;;; 13CA;CHEROKEE LETTER QUU;Lo;0;L;;;;;N;;;;; 13CB;CHEROKEE LETTER QUV;Lo;0;L;;;;;N;;;;; 13CC;CHEROKEE LETTER SA;Lo;0;L;;;;;N;;;;; 13CD;CHEROKEE LETTER S;Lo;0;L;;;;;N;;;;; 13CE;CHEROKEE LETTER SE;Lo;0;L;;;;;N;;;;; 13CF;CHEROKEE LETTER SI;Lo;0;L;;;;;N;;;;; 13D0;CHEROKEE LETTER SO;Lo;0;L;;;;;N;;;;; 13D1;CHEROKEE LETTER SU;Lo;0;L;;;;;N;;;;; 13D2;CHEROKEE LETTER SV;Lo;0;L;;;;;N;;;;; 13D3;CHEROKEE LETTER DA;Lo;0;L;;;;;N;;;;; 13D4;CHEROKEE LETTER TA;Lo;0;L;;;;;N;;;;; 13D5;CHEROKEE LETTER DE;Lo;0;L;;;;;N;;;;; 13D6;CHEROKEE LETTER TE;Lo;0;L;;;;;N;;;;; 13D7;CHEROKEE LETTER DI;Lo;0;L;;;;;N;;;;; 13D8;CHEROKEE LETTER TI;Lo;0;L;;;;;N;;;;; 13D9;CHEROKEE LETTER DO;Lo;0;L;;;;;N;;;;; 13DA;CHEROKEE LETTER DU;Lo;0;L;;;;;N;;;;; 13DB;CHEROKEE LETTER DV;Lo;0;L;;;;;N;;;;; 13DC;CHEROKEE LETTER DLA;Lo;0;L;;;;;N;;;;; 13DD;CHEROKEE LETTER TLA;Lo;0;L;;;;;N;;;;; 13DE;CHEROKEE LETTER TLE;Lo;0;L;;;;;N;;;;; 13DF;CHEROKEE LETTER TLI;Lo;0;L;;;;;N;;;;; 13E0;CHEROKEE LETTER TLO;Lo;0;L;;;;;N;;;;; 13E1;CHEROKEE LETTER TLU;Lo;0;L;;;;;N;;;;; 13E2;CHEROKEE LETTER TLV;Lo;0;L;;;;;N;;;;; 13E3;CHEROKEE LETTER TSA;Lo;0;L;;;;;N;;;;; 13E4;CHEROKEE LETTER TSE;Lo;0;L;;;;;N;;;;; 13E5;CHEROKEE LETTER TSI;Lo;0;L;;;;;N;;;;; 13E6;CHEROKEE LETTER TSO;Lo;0;L;;;;;N;;;;; 13E7;CHEROKEE LETTER TSU;Lo;0;L;;;;;N;;;;; 13E8;CHEROKEE LETTER TSV;Lo;0;L;;;;;N;;;;; 13E9;CHEROKEE LETTER WA;Lo;0;L;;;;;N;;;;; 13EA;CHEROKEE LETTER WE;Lo;0;L;;;;;N;;;;; 13EB;CHEROKEE LETTER WI;Lo;0;L;;;;;N;;;;; 13EC;CHEROKEE LETTER WO;Lo;0;L;;;;;N;;;;; 13ED;CHEROKEE LETTER WU;Lo;0;L;;;;;N;;;;; 13EE;CHEROKEE LETTER WV;Lo;0;L;;;;;N;;;;; 13EF;CHEROKEE LETTER YA;Lo;0;L;;;;;N;;;;; 13F0;CHEROKEE LETTER YE;Lo;0;L;;;;;N;;;;; 13F1;CHEROKEE LETTER YI;Lo;0;L;;;;;N;;;;; 13F2;CHEROKEE LETTER YO;Lo;0;L;;;;;N;;;;; 13F3;CHEROKEE LETTER YU;Lo;0;L;;;;;N;;;;; 13F4;CHEROKEE LETTER YV;Lo;0;L;;;;;N;;;;; 1400;CANADIAN SYLLABICS HYPHEN;Pd;0;ON;;;;;N;;;;; 1401;CANADIAN SYLLABICS E;Lo;0;L;;;;;N;;;;; 1402;CANADIAN SYLLABICS AAI;Lo;0;L;;;;;N;;;;; 1403;CANADIAN SYLLABICS I;Lo;0;L;;;;;N;;;;; 1404;CANADIAN SYLLABICS II;Lo;0;L;;;;;N;;;;; 1405;CANADIAN SYLLABICS O;Lo;0;L;;;;;N;;;;; 1406;CANADIAN SYLLABICS OO;Lo;0;L;;;;;N;;;;; 1407;CANADIAN SYLLABICS Y-CREE OO;Lo;0;L;;;;;N;;;;; 1408;CANADIAN SYLLABICS CARRIER EE;Lo;0;L;;;;;N;;;;; 1409;CANADIAN SYLLABICS CARRIER I;Lo;0;L;;;;;N;;;;; 140A;CANADIAN SYLLABICS A;Lo;0;L;;;;;N;;;;; 140B;CANADIAN SYLLABICS AA;Lo;0;L;;;;;N;;;;; 140C;CANADIAN SYLLABICS WE;Lo;0;L;;;;;N;;;;; 140D;CANADIAN SYLLABICS WEST-CREE WE;Lo;0;L;;;;;N;;;;; 140E;CANADIAN SYLLABICS WI;Lo;0;L;;;;;N;;;;; 140F;CANADIAN SYLLABICS WEST-CREE WI;Lo;0;L;;;;;N;;;;; 1410;CANADIAN SYLLABICS WII;Lo;0;L;;;;;N;;;;; 1411;CANADIAN SYLLABICS WEST-CREE WII;Lo;0;L;;;;;N;;;;; 1412;CANADIAN SYLLABICS WO;Lo;0;L;;;;;N;;;;; 1413;CANADIAN SYLLABICS WEST-CREE WO;Lo;0;L;;;;;N;;;;; 1414;CANADIAN SYLLABICS WOO;Lo;0;L;;;;;N;;;;; 1415;CANADIAN SYLLABICS WEST-CREE WOO;Lo;0;L;;;;;N;;;;; 1416;CANADIAN SYLLABICS NASKAPI WOO;Lo;0;L;;;;;N;;;;; 1417;CANADIAN SYLLABICS WA;Lo;0;L;;;;;N;;;;; 1418;CANADIAN SYLLABICS WEST-CREE WA;Lo;0;L;;;;;N;;;;; 1419;CANADIAN SYLLABICS WAA;Lo;0;L;;;;;N;;;;; 141A;CANADIAN SYLLABICS WEST-CREE WAA;Lo;0;L;;;;;N;;;;; 141B;CANADIAN SYLLABICS NASKAPI WAA;Lo;0;L;;;;;N;;;;; 141C;CANADIAN SYLLABICS AI;Lo;0;L;;;;;N;;;;; 141D;CANADIAN SYLLABICS Y-CREE W;Lo;0;L;;;;;N;;;;; 141E;CANADIAN SYLLABICS GLOTTAL STOP;Lo;0;L;;;;;N;;;;; 141F;CANADIAN SYLLABICS FINAL ACUTE;Lo;0;L;;;;;N;;;;; 1420;CANADIAN SYLLABICS FINAL GRAVE;Lo;0;L;;;;;N;;;;; 1421;CANADIAN SYLLABICS FINAL BOTTOM HALF RING;Lo;0;L;;;;;N;;;;; 1422;CANADIAN SYLLABICS FINAL TOP HALF RING;Lo;0;L;;;;;N;;;;; 1423;CANADIAN SYLLABICS FINAL RIGHT HALF RING;Lo;0;L;;;;;N;;;;; 1424;CANADIAN SYLLABICS FINAL RING;Lo;0;L;;;;;N;;;;; 1425;CANADIAN SYLLABICS FINAL DOUBLE ACUTE;Lo;0;L;;;;;N;;;;; 1426;CANADIAN SYLLABICS FINAL DOUBLE SHORT VERTICAL STROKES;Lo;0;L;;;;;N;;;;; 1427;CANADIAN SYLLABICS FINAL MIDDLE DOT;Lo;0;L;;;;;N;;;;; 1428;CANADIAN SYLLABICS FINAL SHORT HORIZONTAL STROKE;Lo;0;L;;;;;N;;;;; 1429;CANADIAN SYLLABICS FINAL PLUS;Lo;0;L;;;;;N;;;;; 142A;CANADIAN SYLLABICS FINAL DOWN TACK;Lo;0;L;;;;;N;;;;; 142B;CANADIAN SYLLABICS EN;Lo;0;L;;;;;N;;;;; 142C;CANADIAN SYLLABICS IN;Lo;0;L;;;;;N;;;;; 142D;CANADIAN SYLLABICS ON;Lo;0;L;;;;;N;;;;; 142E;CANADIAN SYLLABICS AN;Lo;0;L;;;;;N;;;;; 142F;CANADIAN SYLLABICS PE;Lo;0;L;;;;;N;;;;; 1430;CANADIAN SYLLABICS PAAI;Lo;0;L;;;;;N;;;;; 1431;CANADIAN SYLLABICS PI;Lo;0;L;;;;;N;;;;; 1432;CANADIAN SYLLABICS PII;Lo;0;L;;;;;N;;;;; 1433;CANADIAN SYLLABICS PO;Lo;0;L;;;;;N;;;;; 1434;CANADIAN SYLLABICS POO;Lo;0;L;;;;;N;;;;; 1435;CANADIAN SYLLABICS Y-CREE POO;Lo;0;L;;;;;N;;;;; 1436;CANADIAN SYLLABICS CARRIER HEE;Lo;0;L;;;;;N;;;;; 1437;CANADIAN SYLLABICS CARRIER HI;Lo;0;L;;;;;N;;;;; 1438;CANADIAN SYLLABICS PA;Lo;0;L;;;;;N;;;;; 1439;CANADIAN SYLLABICS PAA;Lo;0;L;;;;;N;;;;; 143A;CANADIAN SYLLABICS PWE;Lo;0;L;;;;;N;;;;; 143B;CANADIAN SYLLABICS WEST-CREE PWE;Lo;0;L;;;;;N;;;;; 143C;CANADIAN SYLLABICS PWI;Lo;0;L;;;;;N;;;;; 143D;CANADIAN SYLLABICS WEST-CREE PWI;Lo;0;L;;;;;N;;;;; 143E;CANADIAN SYLLABICS PWII;Lo;0;L;;;;;N;;;;; 143F;CANADIAN SYLLABICS WEST-CREE PWII;Lo;0;L;;;;;N;;;;; 1440;CANADIAN SYLLABICS PWO;Lo;0;L;;;;;N;;;;; 1441;CANADIAN SYLLABICS WEST-CREE PWO;Lo;0;L;;;;;N;;;;; 1442;CANADIAN SYLLABICS PWOO;Lo;0;L;;;;;N;;;;; 1443;CANADIAN SYLLABICS WEST-CREE PWOO;Lo;0;L;;;;;N;;;;; 1444;CANADIAN SYLLABICS PWA;Lo;0;L;;;;;N;;;;; 1445;CANADIAN SYLLABICS WEST-CREE PWA;Lo;0;L;;;;;N;;;;; 1446;CANADIAN SYLLABICS PWAA;Lo;0;L;;;;;N;;;;; 1447;CANADIAN SYLLABICS WEST-CREE PWAA;Lo;0;L;;;;;N;;;;; 1448;CANADIAN SYLLABICS Y-CREE PWAA;Lo;0;L;;;;;N;;;;; 1449;CANADIAN SYLLABICS P;Lo;0;L;;;;;N;;;;; 144A;CANADIAN SYLLABICS WEST-CREE P;Lo;0;L;;;;;N;;;;; 144B;CANADIAN SYLLABICS CARRIER H;Lo;0;L;;;;;N;;;;; 144C;CANADIAN SYLLABICS TE;Lo;0;L;;;;;N;;;;; 144D;CANADIAN SYLLABICS TAAI;Lo;0;L;;;;;N;;;;; 144E;CANADIAN SYLLABICS TI;Lo;0;L;;;;;N;;;;; 144F;CANADIAN SYLLABICS TII;Lo;0;L;;;;;N;;;;; 1450;CANADIAN SYLLABICS TO;Lo;0;L;;;;;N;;;;; 1451;CANADIAN SYLLABICS TOO;Lo;0;L;;;;;N;;;;; 1452;CANADIAN SYLLABICS Y-CREE TOO;Lo;0;L;;;;;N;;;;; 1453;CANADIAN SYLLABICS CARRIER DEE;Lo;0;L;;;;;N;;;;; 1454;CANADIAN SYLLABICS CARRIER DI;Lo;0;L;;;;;N;;;;; 1455;CANADIAN SYLLABICS TA;Lo;0;L;;;;;N;;;;; 1456;CANADIAN SYLLABICS TAA;Lo;0;L;;;;;N;;;;; 1457;CANADIAN SYLLABICS TWE;Lo;0;L;;;;;N;;;;; 1458;CANADIAN SYLLABICS WEST-CREE TWE;Lo;0;L;;;;;N;;;;; 1459;CANADIAN SYLLABICS TWI;Lo;0;L;;;;;N;;;;; 145A;CANADIAN SYLLABICS WEST-CREE TWI;Lo;0;L;;;;;N;;;;; 145B;CANADIAN SYLLABICS TWII;Lo;0;L;;;;;N;;;;; 145C;CANADIAN SYLLABICS WEST-CREE TWII;Lo;0;L;;;;;N;;;;; 145D;CANADIAN SYLLABICS TWO;Lo;0;L;;;;;N;;;;; 145E;CANADIAN SYLLABICS WEST-CREE TWO;Lo;0;L;;;;;N;;;;; 145F;CANADIAN SYLLABICS TWOO;Lo;0;L;;;;;N;;;;; 1460;CANADIAN SYLLABICS WEST-CREE TWOO;Lo;0;L;;;;;N;;;;; 1461;CANADIAN SYLLABICS TWA;Lo;0;L;;;;;N;;;;; 1462;CANADIAN SYLLABICS WEST-CREE TWA;Lo;0;L;;;;;N;;;;; 1463;CANADIAN SYLLABICS TWAA;Lo;0;L;;;;;N;;;;; 1464;CANADIAN SYLLABICS WEST-CREE TWAA;Lo;0;L;;;;;N;;;;; 1465;CANADIAN SYLLABICS NASKAPI TWAA;Lo;0;L;;;;;N;;;;; 1466;CANADIAN SYLLABICS T;Lo;0;L;;;;;N;;;;; 1467;CANADIAN SYLLABICS TTE;Lo;0;L;;;;;N;;;;; 1468;CANADIAN SYLLABICS TTI;Lo;0;L;;;;;N;;;;; 1469;CANADIAN SYLLABICS TTO;Lo;0;L;;;;;N;;;;; 146A;CANADIAN SYLLABICS TTA;Lo;0;L;;;;;N;;;;; 146B;CANADIAN SYLLABICS KE;Lo;0;L;;;;;N;;;;; 146C;CANADIAN SYLLABICS KAAI;Lo;0;L;;;;;N;;;;; 146D;CANADIAN SYLLABICS KI;Lo;0;L;;;;;N;;;;; 146E;CANADIAN SYLLABICS KII;Lo;0;L;;;;;N;;;;; 146F;CANADIAN SYLLABICS KO;Lo;0;L;;;;;N;;;;; 1470;CANADIAN SYLLABICS KOO;Lo;0;L;;;;;N;;;;; 1471;CANADIAN SYLLABICS Y-CREE KOO;Lo;0;L;;;;;N;;;;; 1472;CANADIAN SYLLABICS KA;Lo;0;L;;;;;N;;;;; 1473;CANADIAN SYLLABICS KAA;Lo;0;L;;;;;N;;;;; 1474;CANADIAN SYLLABICS KWE;Lo;0;L;;;;;N;;;;; 1475;CANADIAN SYLLABICS WEST-CREE KWE;Lo;0;L;;;;;N;;;;; 1476;CANADIAN SYLLABICS KWI;Lo;0;L;;;;;N;;;;; 1477;CANADIAN SYLLABICS WEST-CREE KWI;Lo;0;L;;;;;N;;;;; 1478;CANADIAN SYLLABICS KWII;Lo;0;L;;;;;N;;;;; 1479;CANADIAN SYLLABICS WEST-CREE KWII;Lo;0;L;;;;;N;;;;; 147A;CANADIAN SYLLABICS KWO;Lo;0;L;;;;;N;;;;; 147B;CANADIAN SYLLABICS WEST-CREE KWO;Lo;0;L;;;;;N;;;;; 147C;CANADIAN SYLLABICS KWOO;Lo;0;L;;;;;N;;;;; 147D;CANADIAN SYLLABICS WEST-CREE KWOO;Lo;0;L;;;;;N;;;;; 147E;CANADIAN SYLLABICS KWA;Lo;0;L;;;;;N;;;;; 147F;CANADIAN SYLLABICS WEST-CREE KWA;Lo;0;L;;;;;N;;;;; 1480;CANADIAN SYLLABICS KWAA;Lo;0;L;;;;;N;;;;; 1481;CANADIAN SYLLABICS WEST-CREE KWAA;Lo;0;L;;;;;N;;;;; 1482;CANADIAN SYLLABICS NASKAPI KWAA;Lo;0;L;;;;;N;;;;; 1483;CANADIAN SYLLABICS K;Lo;0;L;;;;;N;;;;; 1484;CANADIAN SYLLABICS KW;Lo;0;L;;;;;N;;;;; 1485;CANADIAN SYLLABICS SOUTH-SLAVEY KEH;Lo;0;L;;;;;N;;;;; 1486;CANADIAN SYLLABICS SOUTH-SLAVEY KIH;Lo;0;L;;;;;N;;;;; 1487;CANADIAN SYLLABICS SOUTH-SLAVEY KOH;Lo;0;L;;;;;N;;;;; 1488;CANADIAN SYLLABICS SOUTH-SLAVEY KAH;Lo;0;L;;;;;N;;;;; 1489;CANADIAN SYLLABICS CE;Lo;0;L;;;;;N;;;;; 148A;CANADIAN SYLLABICS CAAI;Lo;0;L;;;;;N;;;;; 148B;CANADIAN SYLLABICS CI;Lo;0;L;;;;;N;;;;; 148C;CANADIAN SYLLABICS CII;Lo;0;L;;;;;N;;;;; 148D;CANADIAN SYLLABICS CO;Lo;0;L;;;;;N;;;;; 148E;CANADIAN SYLLABICS COO;Lo;0;L;;;;;N;;;;; 148F;CANADIAN SYLLABICS Y-CREE COO;Lo;0;L;;;;;N;;;;; 1490;CANADIAN SYLLABICS CA;Lo;0;L;;;;;N;;;;; 1491;CANADIAN SYLLABICS CAA;Lo;0;L;;;;;N;;;;; 1492;CANADIAN SYLLABICS CWE;Lo;0;L;;;;;N;;;;; 1493;CANADIAN SYLLABICS WEST-CREE CWE;Lo;0;L;;;;;N;;;;; 1494;CANADIAN SYLLABICS CWI;Lo;0;L;;;;;N;;;;; 1495;CANADIAN SYLLABICS WEST-CREE CWI;Lo;0;L;;;;;N;;;;; 1496;CANADIAN SYLLABICS CWII;Lo;0;L;;;;;N;;;;; 1497;CANADIAN SYLLABICS WEST-CREE CWII;Lo;0;L;;;;;N;;;;; 1498;CANADIAN SYLLABICS CWO;Lo;0;L;;;;;N;;;;; 1499;CANADIAN SYLLABICS WEST-CREE CWO;Lo;0;L;;;;;N;;;;; 149A;CANADIAN SYLLABICS CWOO;Lo;0;L;;;;;N;;;;; 149B;CANADIAN SYLLABICS WEST-CREE CWOO;Lo;0;L;;;;;N;;;;; 149C;CANADIAN SYLLABICS CWA;Lo;0;L;;;;;N;;;;; 149D;CANADIAN SYLLABICS WEST-CREE CWA;Lo;0;L;;;;;N;;;;; 149E;CANADIAN SYLLABICS CWAA;Lo;0;L;;;;;N;;;;; 149F;CANADIAN SYLLABICS WEST-CREE CWAA;Lo;0;L;;;;;N;;;;; 14A0;CANADIAN SYLLABICS NASKAPI CWAA;Lo;0;L;;;;;N;;;;; 14A1;CANADIAN SYLLABICS C;Lo;0;L;;;;;N;;;;; 14A2;CANADIAN SYLLABICS SAYISI TH;Lo;0;L;;;;;N;;;;; 14A3;CANADIAN SYLLABICS ME;Lo;0;L;;;;;N;;;;; 14A4;CANADIAN SYLLABICS MAAI;Lo;0;L;;;;;N;;;;; 14A5;CANADIAN SYLLABICS MI;Lo;0;L;;;;;N;;;;; 14A6;CANADIAN SYLLABICS MII;Lo;0;L;;;;;N;;;;; 14A7;CANADIAN SYLLABICS MO;Lo;0;L;;;;;N;;;;; 14A8;CANADIAN SYLLABICS MOO;Lo;0;L;;;;;N;;;;; 14A9;CANADIAN SYLLABICS Y-CREE MOO;Lo;0;L;;;;;N;;;;; 14AA;CANADIAN SYLLABICS MA;Lo;0;L;;;;;N;;;;; 14AB;CANADIAN SYLLABICS MAA;Lo;0;L;;;;;N;;;;; 14AC;CANADIAN SYLLABICS MWE;Lo;0;L;;;;;N;;;;; 14AD;CANADIAN SYLLABICS WEST-CREE MWE;Lo;0;L;;;;;N;;;;; 14AE;CANADIAN SYLLABICS MWI;Lo;0;L;;;;;N;;;;; 14AF;CANADIAN SYLLABICS WEST-CREE MWI;Lo;0;L;;;;;N;;;;; 14B0;CANADIAN SYLLABICS MWII;Lo;0;L;;;;;N;;;;; 14B1;CANADIAN SYLLABICS WEST-CREE MWII;Lo;0;L;;;;;N;;;;; 14B2;CANADIAN SYLLABICS MWO;Lo;0;L;;;;;N;;;;; 14B3;CANADIAN SYLLABICS WEST-CREE MWO;Lo;0;L;;;;;N;;;;; 14B4;CANADIAN SYLLABICS MWOO;Lo;0;L;;;;;N;;;;; 14B5;CANADIAN SYLLABICS WEST-CREE MWOO;Lo;0;L;;;;;N;;;;; 14B6;CANADIAN SYLLABICS MWA;Lo;0;L;;;;;N;;;;; 14B7;CANADIAN SYLLABICS WEST-CREE MWA;Lo;0;L;;;;;N;;;;; 14B8;CANADIAN SYLLABICS MWAA;Lo;0;L;;;;;N;;;;; 14B9;CANADIAN SYLLABICS WEST-CREE MWAA;Lo;0;L;;;;;N;;;;; 14BA;CANADIAN SYLLABICS NASKAPI MWAA;Lo;0;L;;;;;N;;;;; 14BB;CANADIAN SYLLABICS M;Lo;0;L;;;;;N;;;;; 14BC;CANADIAN SYLLABICS WEST-CREE M;Lo;0;L;;;;;N;;;;; 14BD;CANADIAN SYLLABICS MH;Lo;0;L;;;;;N;;;;; 14BE;CANADIAN SYLLABICS ATHAPASCAN M;Lo;0;L;;;;;N;;;;; 14BF;CANADIAN SYLLABICS SAYISI M;Lo;0;L;;;;;N;;;;; 14C0;CANADIAN SYLLABICS NE;Lo;0;L;;;;;N;;;;; 14C1;CANADIAN SYLLABICS NAAI;Lo;0;L;;;;;N;;;;; 14C2;CANADIAN SYLLABICS NI;Lo;0;L;;;;;N;;;;; 14C3;CANADIAN SYLLABICS NII;Lo;0;L;;;;;N;;;;; 14C4;CANADIAN SYLLABICS NO;Lo;0;L;;;;;N;;;;; 14C5;CANADIAN SYLLABICS NOO;Lo;0;L;;;;;N;;;;; 14C6;CANADIAN SYLLABICS Y-CREE NOO;Lo;0;L;;;;;N;;;;; 14C7;CANADIAN SYLLABICS NA;Lo;0;L;;;;;N;;;;; 14C8;CANADIAN SYLLABICS NAA;Lo;0;L;;;;;N;;;;; 14C9;CANADIAN SYLLABICS NWE;Lo;0;L;;;;;N;;;;; 14CA;CANADIAN SYLLABICS WEST-CREE NWE;Lo;0;L;;;;;N;;;;; 14CB;CANADIAN SYLLABICS NWA;Lo;0;L;;;;;N;;;;; 14CC;CANADIAN SYLLABICS WEST-CREE NWA;Lo;0;L;;;;;N;;;;; 14CD;CANADIAN SYLLABICS NWAA;Lo;0;L;;;;;N;;;;; 14CE;CANADIAN SYLLABICS WEST-CREE NWAA;Lo;0;L;;;;;N;;;;; 14CF;CANADIAN SYLLABICS NASKAPI NWAA;Lo;0;L;;;;;N;;;;; 14D0;CANADIAN SYLLABICS N;Lo;0;L;;;;;N;;;;; 14D1;CANADIAN SYLLABICS CARRIER NG;Lo;0;L;;;;;N;;;;; 14D2;CANADIAN SYLLABICS NH;Lo;0;L;;;;;N;;;;; 14D3;CANADIAN SYLLABICS LE;Lo;0;L;;;;;N;;;;; 14D4;CANADIAN SYLLABICS LAAI;Lo;0;L;;;;;N;;;;; 14D5;CANADIAN SYLLABICS LI;Lo;0;L;;;;;N;;;;; 14D6;CANADIAN SYLLABICS LII;Lo;0;L;;;;;N;;;;; 14D7;CANADIAN SYLLABICS LO;Lo;0;L;;;;;N;;;;; 14D8;CANADIAN SYLLABICS LOO;Lo;0;L;;;;;N;;;;; 14D9;CANADIAN SYLLABICS Y-CREE LOO;Lo;0;L;;;;;N;;;;; 14DA;CANADIAN SYLLABICS LA;Lo;0;L;;;;;N;;;;; 14DB;CANADIAN SYLLABICS LAA;Lo;0;L;;;;;N;;;;; 14DC;CANADIAN SYLLABICS LWE;Lo;0;L;;;;;N;;;;; 14DD;CANADIAN SYLLABICS WEST-CREE LWE;Lo;0;L;;;;;N;;;;; 14DE;CANADIAN SYLLABICS LWI;Lo;0;L;;;;;N;;;;; 14DF;CANADIAN SYLLABICS WEST-CREE LWI;Lo;0;L;;;;;N;;;;; 14E0;CANADIAN SYLLABICS LWII;Lo;0;L;;;;;N;;;;; 14E1;CANADIAN SYLLABICS WEST-CREE LWII;Lo;0;L;;;;;N;;;;; 14E2;CANADIAN SYLLABICS LWO;Lo;0;L;;;;;N;;;;; 14E3;CANADIAN SYLLABICS WEST-CREE LWO;Lo;0;L;;;;;N;;;;; 14E4;CANADIAN SYLLABICS LWOO;Lo;0;L;;;;;N;;;;; 14E5;CANADIAN SYLLABICS WEST-CREE LWOO;Lo;0;L;;;;;N;;;;; 14E6;CANADIAN SYLLABICS LWA;Lo;0;L;;;;;N;;;;; 14E7;CANADIAN SYLLABICS WEST-CREE LWA;Lo;0;L;;;;;N;;;;; 14E8;CANADIAN SYLLABICS LWAA;Lo;0;L;;;;;N;;;;; 14E9;CANADIAN SYLLABICS WEST-CREE LWAA;Lo;0;L;;;;;N;;;;; 14EA;CANADIAN SYLLABICS L;Lo;0;L;;;;;N;;;;; 14EB;CANADIAN SYLLABICS WEST-CREE L;Lo;0;L;;;;;N;;;;; 14EC;CANADIAN SYLLABICS MEDIAL L;Lo;0;L;;;;;N;;;;; 14ED;CANADIAN SYLLABICS SE;Lo;0;L;;;;;N;;;;; 14EE;CANADIAN SYLLABICS SAAI;Lo;0;L;;;;;N;;;;; 14EF;CANADIAN SYLLABICS SI;Lo;0;L;;;;;N;;;;; 14F0;CANADIAN SYLLABICS SII;Lo;0;L;;;;;N;;;;; 14F1;CANADIAN SYLLABICS SO;Lo;0;L;;;;;N;;;;; 14F2;CANADIAN SYLLABICS SOO;Lo;0;L;;;;;N;;;;; 14F3;CANADIAN SYLLABICS Y-CREE SOO;Lo;0;L;;;;;N;;;;; 14F4;CANADIAN SYLLABICS SA;Lo;0;L;;;;;N;;;;; 14F5;CANADIAN SYLLABICS SAA;Lo;0;L;;;;;N;;;;; 14F6;CANADIAN SYLLABICS SWE;Lo;0;L;;;;;N;;;;; 14F7;CANADIAN SYLLABICS WEST-CREE SWE;Lo;0;L;;;;;N;;;;; 14F8;CANADIAN SYLLABICS SWI;Lo;0;L;;;;;N;;;;; 14F9;CANADIAN SYLLABICS WEST-CREE SWI;Lo;0;L;;;;;N;;;;; 14FA;CANADIAN SYLLABICS SWII;Lo;0;L;;;;;N;;;;; 14FB;CANADIAN SYLLABICS WEST-CREE SWII;Lo;0;L;;;;;N;;;;; 14FC;CANADIAN SYLLABICS SWO;Lo;0;L;;;;;N;;;;; 14FD;CANADIAN SYLLABICS WEST-CREE SWO;Lo;0;L;;;;;N;;;;; 14FE;CANADIAN SYLLABICS SWOO;Lo;0;L;;;;;N;;;;; 14FF;CANADIAN SYLLABICS WEST-CREE SWOO;Lo;0;L;;;;;N;;;;; 1500;CANADIAN SYLLABICS SWA;Lo;0;L;;;;;N;;;;; 1501;CANADIAN SYLLABICS WEST-CREE SWA;Lo;0;L;;;;;N;;;;; 1502;CANADIAN SYLLABICS SWAA;Lo;0;L;;;;;N;;;;; 1503;CANADIAN SYLLABICS WEST-CREE SWAA;Lo;0;L;;;;;N;;;;; 1504;CANADIAN SYLLABICS NASKAPI SWAA;Lo;0;L;;;;;N;;;;; 1505;CANADIAN SYLLABICS S;Lo;0;L;;;;;N;;;;; 1506;CANADIAN SYLLABICS ATHAPASCAN S;Lo;0;L;;;;;N;;;;; 1507;CANADIAN SYLLABICS SW;Lo;0;L;;;;;N;;;;; 1508;CANADIAN SYLLABICS BLACKFOOT S;Lo;0;L;;;;;N;;;;; 1509;CANADIAN SYLLABICS MOOSE-CREE SK;Lo;0;L;;;;;N;;;;; 150A;CANADIAN SYLLABICS NASKAPI SKW;Lo;0;L;;;;;N;;;;; 150B;CANADIAN SYLLABICS NASKAPI S-W;Lo;0;L;;;;;N;;;;; 150C;CANADIAN SYLLABICS NASKAPI SPWA;Lo;0;L;;;;;N;;;;; 150D;CANADIAN SYLLABICS NASKAPI STWA;Lo;0;L;;;;;N;;;;; 150E;CANADIAN SYLLABICS NASKAPI SKWA;Lo;0;L;;;;;N;;;;; 150F;CANADIAN SYLLABICS NASKAPI SCWA;Lo;0;L;;;;;N;;;;; 1510;CANADIAN SYLLABICS SHE;Lo;0;L;;;;;N;;;;; 1511;CANADIAN SYLLABICS SHI;Lo;0;L;;;;;N;;;;; 1512;CANADIAN SYLLABICS SHII;Lo;0;L;;;;;N;;;;; 1513;CANADIAN SYLLABICS SHO;Lo;0;L;;;;;N;;;;; 1514;CANADIAN SYLLABICS SHOO;Lo;0;L;;;;;N;;;;; 1515;CANADIAN SYLLABICS SHA;Lo;0;L;;;;;N;;;;; 1516;CANADIAN SYLLABICS SHAA;Lo;0;L;;;;;N;;;;; 1517;CANADIAN SYLLABICS SHWE;Lo;0;L;;;;;N;;;;; 1518;CANADIAN SYLLABICS WEST-CREE SHWE;Lo;0;L;;;;;N;;;;; 1519;CANADIAN SYLLABICS SHWI;Lo;0;L;;;;;N;;;;; 151A;CANADIAN SYLLABICS WEST-CREE SHWI;Lo;0;L;;;;;N;;;;; 151B;CANADIAN SYLLABICS SHWII;Lo;0;L;;;;;N;;;;; 151C;CANADIAN SYLLABICS WEST-CREE SHWII;Lo;0;L;;;;;N;;;;; 151D;CANADIAN SYLLABICS SHWO;Lo;0;L;;;;;N;;;;; 151E;CANADIAN SYLLABICS WEST-CREE SHWO;Lo;0;L;;;;;N;;;;; 151F;CANADIAN SYLLABICS SHWOO;Lo;0;L;;;;;N;;;;; 1520;CANADIAN SYLLABICS WEST-CREE SHWOO;Lo;0;L;;;;;N;;;;; 1521;CANADIAN SYLLABICS SHWA;Lo;0;L;;;;;N;;;;; 1522;CANADIAN SYLLABICS WEST-CREE SHWA;Lo;0;L;;;;;N;;;;; 1523;CANADIAN SYLLABICS SHWAA;Lo;0;L;;;;;N;;;;; 1524;CANADIAN SYLLABICS WEST-CREE SHWAA;Lo;0;L;;;;;N;;;;; 1525;CANADIAN SYLLABICS SH;Lo;0;L;;;;;N;;;;; 1526;CANADIAN SYLLABICS YE;Lo;0;L;;;;;N;;;;; 1527;CANADIAN SYLLABICS YAAI;Lo;0;L;;;;;N;;;;; 1528;CANADIAN SYLLABICS YI;Lo;0;L;;;;;N;;;;; 1529;CANADIAN SYLLABICS YII;Lo;0;L;;;;;N;;;;; 152A;CANADIAN SYLLABICS YO;Lo;0;L;;;;;N;;;;; 152B;CANADIAN SYLLABICS YOO;Lo;0;L;;;;;N;;;;; 152C;CANADIAN SYLLABICS Y-CREE YOO;Lo;0;L;;;;;N;;;;; 152D;CANADIAN SYLLABICS YA;Lo;0;L;;;;;N;;;;; 152E;CANADIAN SYLLABICS YAA;Lo;0;L;;;;;N;;;;; 152F;CANADIAN SYLLABICS YWE;Lo;0;L;;;;;N;;;;; 1530;CANADIAN SYLLABICS WEST-CREE YWE;Lo;0;L;;;;;N;;;;; 1531;CANADIAN SYLLABICS YWI;Lo;0;L;;;;;N;;;;; 1532;CANADIAN SYLLABICS WEST-CREE YWI;Lo;0;L;;;;;N;;;;; 1533;CANADIAN SYLLABICS YWII;Lo;0;L;;;;;N;;;;; 1534;CANADIAN SYLLABICS WEST-CREE YWII;Lo;0;L;;;;;N;;;;; 1535;CANADIAN SYLLABICS YWO;Lo;0;L;;;;;N;;;;; 1536;CANADIAN SYLLABICS WEST-CREE YWO;Lo;0;L;;;;;N;;;;; 1537;CANADIAN SYLLABICS YWOO;Lo;0;L;;;;;N;;;;; 1538;CANADIAN SYLLABICS WEST-CREE YWOO;Lo;0;L;;;;;N;;;;; 1539;CANADIAN SYLLABICS YWA;Lo;0;L;;;;;N;;;;; 153A;CANADIAN SYLLABICS WEST-CREE YWA;Lo;0;L;;;;;N;;;;; 153B;CANADIAN SYLLABICS YWAA;Lo;0;L;;;;;N;;;;; 153C;CANADIAN SYLLABICS WEST-CREE YWAA;Lo;0;L;;;;;N;;;;; 153D;CANADIAN SYLLABICS NASKAPI YWAA;Lo;0;L;;;;;N;;;;; 153E;CANADIAN SYLLABICS Y;Lo;0;L;;;;;N;;;;; 153F;CANADIAN SYLLABICS BIBLE-CREE Y;Lo;0;L;;;;;N;;;;; 1540;CANADIAN SYLLABICS WEST-CREE Y;Lo;0;L;;;;;N;;;;; 1541;CANADIAN SYLLABICS SAYISI YI;Lo;0;L;;;;;N;;;;; 1542;CANADIAN SYLLABICS RE;Lo;0;L;;;;;N;;;;; 1543;CANADIAN SYLLABICS R-CREE RE;Lo;0;L;;;;;N;;;;; 1544;CANADIAN SYLLABICS WEST-CREE LE;Lo;0;L;;;;;N;;;;; 1545;CANADIAN SYLLABICS RAAI;Lo;0;L;;;;;N;;;;; 1546;CANADIAN SYLLABICS RI;Lo;0;L;;;;;N;;;;; 1547;CANADIAN SYLLABICS RII;Lo;0;L;;;;;N;;;;; 1548;CANADIAN SYLLABICS RO;Lo;0;L;;;;;N;;;;; 1549;CANADIAN SYLLABICS ROO;Lo;0;L;;;;;N;;;;; 154A;CANADIAN SYLLABICS WEST-CREE LO;Lo;0;L;;;;;N;;;;; 154B;CANADIAN SYLLABICS RA;Lo;0;L;;;;;N;;;;; 154C;CANADIAN SYLLABICS RAA;Lo;0;L;;;;;N;;;;; 154D;CANADIAN SYLLABICS WEST-CREE LA;Lo;0;L;;;;;N;;;;; 154E;CANADIAN SYLLABICS RWAA;Lo;0;L;;;;;N;;;;; 154F;CANADIAN SYLLABICS WEST-CREE RWAA;Lo;0;L;;;;;N;;;;; 1550;CANADIAN SYLLABICS R;Lo;0;L;;;;;N;;;;; 1551;CANADIAN SYLLABICS WEST-CREE R;Lo;0;L;;;;;N;;;;; 1552;CANADIAN SYLLABICS MEDIAL R;Lo;0;L;;;;;N;;;;; 1553;CANADIAN SYLLABICS FE;Lo;0;L;;;;;N;;;;; 1554;CANADIAN SYLLABICS FAAI;Lo;0;L;;;;;N;;;;; 1555;CANADIAN SYLLABICS FI;Lo;0;L;;;;;N;;;;; 1556;CANADIAN SYLLABICS FII;Lo;0;L;;;;;N;;;;; 1557;CANADIAN SYLLABICS FO;Lo;0;L;;;;;N;;;;; 1558;CANADIAN SYLLABICS FOO;Lo;0;L;;;;;N;;;;; 1559;CANADIAN SYLLABICS FA;Lo;0;L;;;;;N;;;;; 155A;CANADIAN SYLLABICS FAA;Lo;0;L;;;;;N;;;;; 155B;CANADIAN SYLLABICS FWAA;Lo;0;L;;;;;N;;;;; 155C;CANADIAN SYLLABICS WEST-CREE FWAA;Lo;0;L;;;;;N;;;;; 155D;CANADIAN SYLLABICS F;Lo;0;L;;;;;N;;;;; 155E;CANADIAN SYLLABICS THE;Lo;0;L;;;;;N;;;;; 155F;CANADIAN SYLLABICS N-CREE THE;Lo;0;L;;;;;N;;;;; 1560;CANADIAN SYLLABICS THI;Lo;0;L;;;;;N;;;;; 1561;CANADIAN SYLLABICS N-CREE THI;Lo;0;L;;;;;N;;;;; 1562;CANADIAN SYLLABICS THII;Lo;0;L;;;;;N;;;;; 1563;CANADIAN SYLLABICS N-CREE THII;Lo;0;L;;;;;N;;;;; 1564;CANADIAN SYLLABICS THO;Lo;0;L;;;;;N;;;;; 1565;CANADIAN SYLLABICS THOO;Lo;0;L;;;;;N;;;;; 1566;CANADIAN SYLLABICS THA;Lo;0;L;;;;;N;;;;; 1567;CANADIAN SYLLABICS THAA;Lo;0;L;;;;;N;;;;; 1568;CANADIAN SYLLABICS THWAA;Lo;0;L;;;;;N;;;;; 1569;CANADIAN SYLLABICS WEST-CREE THWAA;Lo;0;L;;;;;N;;;;; 156A;CANADIAN SYLLABICS TH;Lo;0;L;;;;;N;;;;; 156B;CANADIAN SYLLABICS TTHE;Lo;0;L;;;;;N;;;;; 156C;CANADIAN SYLLABICS TTHI;Lo;0;L;;;;;N;;;;; 156D;CANADIAN SYLLABICS TTHO;Lo;0;L;;;;;N;;;;; 156E;CANADIAN SYLLABICS TTHA;Lo;0;L;;;;;N;;;;; 156F;CANADIAN SYLLABICS TTH;Lo;0;L;;;;;N;;;;; 1570;CANADIAN SYLLABICS TYE;Lo;0;L;;;;;N;;;;; 1571;CANADIAN SYLLABICS TYI;Lo;0;L;;;;;N;;;;; 1572;CANADIAN SYLLABICS TYO;Lo;0;L;;;;;N;;;;; 1573;CANADIAN SYLLABICS TYA;Lo;0;L;;;;;N;;;;; 1574;CANADIAN SYLLABICS NUNAVIK HE;Lo;0;L;;;;;N;;;;; 1575;CANADIAN SYLLABICS NUNAVIK HI;Lo;0;L;;;;;N;;;;; 1576;CANADIAN SYLLABICS NUNAVIK HII;Lo;0;L;;;;;N;;;;; 1577;CANADIAN SYLLABICS NUNAVIK HO;Lo;0;L;;;;;N;;;;; 1578;CANADIAN SYLLABICS NUNAVIK HOO;Lo;0;L;;;;;N;;;;; 1579;CANADIAN SYLLABICS NUNAVIK HA;Lo;0;L;;;;;N;;;;; 157A;CANADIAN SYLLABICS NUNAVIK HAA;Lo;0;L;;;;;N;;;;; 157B;CANADIAN SYLLABICS NUNAVIK H;Lo;0;L;;;;;N;;;;; 157C;CANADIAN SYLLABICS NUNAVUT H;Lo;0;L;;;;;N;;;;; 157D;CANADIAN SYLLABICS HK;Lo;0;L;;;;;N;;;;; 157E;CANADIAN SYLLABICS QAAI;Lo;0;L;;;;;N;;;;; 157F;CANADIAN SYLLABICS QI;Lo;0;L;;;;;N;;;;; 1580;CANADIAN SYLLABICS QII;Lo;0;L;;;;;N;;;;; 1581;CANADIAN SYLLABICS QO;Lo;0;L;;;;;N;;;;; 1582;CANADIAN SYLLABICS QOO;Lo;0;L;;;;;N;;;;; 1583;CANADIAN SYLLABICS QA;Lo;0;L;;;;;N;;;;; 1584;CANADIAN SYLLABICS QAA;Lo;0;L;;;;;N;;;;; 1585;CANADIAN SYLLABICS Q;Lo;0;L;;;;;N;;;;; 1586;CANADIAN SYLLABICS TLHE;Lo;0;L;;;;;N;;;;; 1587;CANADIAN SYLLABICS TLHI;Lo;0;L;;;;;N;;;;; 1588;CANADIAN SYLLABICS TLHO;Lo;0;L;;;;;N;;;;; 1589;CANADIAN SYLLABICS TLHA;Lo;0;L;;;;;N;;;;; 158A;CANADIAN SYLLABICS WEST-CREE RE;Lo;0;L;;;;;N;;;;; 158B;CANADIAN SYLLABICS WEST-CREE RI;Lo;0;L;;;;;N;;;;; 158C;CANADIAN SYLLABICS WEST-CREE RO;Lo;0;L;;;;;N;;;;; 158D;CANADIAN SYLLABICS WEST-CREE RA;Lo;0;L;;;;;N;;;;; 158E;CANADIAN SYLLABICS NGAAI;Lo;0;L;;;;;N;;;;; 158F;CANADIAN SYLLABICS NGI;Lo;0;L;;;;;N;;;;; 1590;CANADIAN SYLLABICS NGII;Lo;0;L;;;;;N;;;;; 1591;CANADIAN SYLLABICS NGO;Lo;0;L;;;;;N;;;;; 1592;CANADIAN SYLLABICS NGOO;Lo;0;L;;;;;N;;;;; 1593;CANADIAN SYLLABICS NGA;Lo;0;L;;;;;N;;;;; 1594;CANADIAN SYLLABICS NGAA;Lo;0;L;;;;;N;;;;; 1595;CANADIAN SYLLABICS NG;Lo;0;L;;;;;N;;;;; 1596;CANADIAN SYLLABICS NNG;Lo;0;L;;;;;N;;;;; 1597;CANADIAN SYLLABICS SAYISI SHE;Lo;0;L;;;;;N;;;;; 1598;CANADIAN SYLLABICS SAYISI SHI;Lo;0;L;;;;;N;;;;; 1599;CANADIAN SYLLABICS SAYISI SHO;Lo;0;L;;;;;N;;;;; 159A;CANADIAN SYLLABICS SAYISI SHA;Lo;0;L;;;;;N;;;;; 159B;CANADIAN SYLLABICS WOODS-CREE THE;Lo;0;L;;;;;N;;;;; 159C;CANADIAN SYLLABICS WOODS-CREE THI;Lo;0;L;;;;;N;;;;; 159D;CANADIAN SYLLABICS WOODS-CREE THO;Lo;0;L;;;;;N;;;;; 159E;CANADIAN SYLLABICS WOODS-CREE THA;Lo;0;L;;;;;N;;;;; 159F;CANADIAN SYLLABICS WOODS-CREE TH;Lo;0;L;;;;;N;;;;; 15A0;CANADIAN SYLLABICS LHI;Lo;0;L;;;;;N;;;;; 15A1;CANADIAN SYLLABICS LHII;Lo;0;L;;;;;N;;;;; 15A2;CANADIAN SYLLABICS LHO;Lo;0;L;;;;;N;;;;; 15A3;CANADIAN SYLLABICS LHOO;Lo;0;L;;;;;N;;;;; 15A4;CANADIAN SYLLABICS LHA;Lo;0;L;;;;;N;;;;; 15A5;CANADIAN SYLLABICS LHAA;Lo;0;L;;;;;N;;;;; 15A6;CANADIAN SYLLABICS LH;Lo;0;L;;;;;N;;;;; 15A7;CANADIAN SYLLABICS TH-CREE THE;Lo;0;L;;;;;N;;;;; 15A8;CANADIAN SYLLABICS TH-CREE THI;Lo;0;L;;;;;N;;;;; 15A9;CANADIAN SYLLABICS TH-CREE THII;Lo;0;L;;;;;N;;;;; 15AA;CANADIAN SYLLABICS TH-CREE THO;Lo;0;L;;;;;N;;;;; 15AB;CANADIAN SYLLABICS TH-CREE THOO;Lo;0;L;;;;;N;;;;; 15AC;CANADIAN SYLLABICS TH-CREE THA;Lo;0;L;;;;;N;;;;; 15AD;CANADIAN SYLLABICS TH-CREE THAA;Lo;0;L;;;;;N;;;;; 15AE;CANADIAN SYLLABICS TH-CREE TH;Lo;0;L;;;;;N;;;;; 15AF;CANADIAN SYLLABICS AIVILIK B;Lo;0;L;;;;;N;;;;; 15B0;CANADIAN SYLLABICS BLACKFOOT E;Lo;0;L;;;;;N;;;;; 15B1;CANADIAN SYLLABICS BLACKFOOT I;Lo;0;L;;;;;N;;;;; 15B2;CANADIAN SYLLABICS BLACKFOOT O;Lo;0;L;;;;;N;;;;; 15B3;CANADIAN SYLLABICS BLACKFOOT A;Lo;0;L;;;;;N;;;;; 15B4;CANADIAN SYLLABICS BLACKFOOT WE;Lo;0;L;;;;;N;;;;; 15B5;CANADIAN SYLLABICS BLACKFOOT WI;Lo;0;L;;;;;N;;;;; 15B6;CANADIAN SYLLABICS BLACKFOOT WO;Lo;0;L;;;;;N;;;;; 15B7;CANADIAN SYLLABICS BLACKFOOT WA;Lo;0;L;;;;;N;;;;; 15B8;CANADIAN SYLLABICS BLACKFOOT NE;Lo;0;L;;;;;N;;;;; 15B9;CANADIAN SYLLABICS BLACKFOOT NI;Lo;0;L;;;;;N;;;;; 15BA;CANADIAN SYLLABICS BLACKFOOT NO;Lo;0;L;;;;;N;;;;; 15BB;CANADIAN SYLLABICS BLACKFOOT NA;Lo;0;L;;;;;N;;;;; 15BC;CANADIAN SYLLABICS BLACKFOOT KE;Lo;0;L;;;;;N;;;;; 15BD;CANADIAN SYLLABICS BLACKFOOT KI;Lo;0;L;;;;;N;;;;; 15BE;CANADIAN SYLLABICS BLACKFOOT KO;Lo;0;L;;;;;N;;;;; 15BF;CANADIAN SYLLABICS BLACKFOOT KA;Lo;0;L;;;;;N;;;;; 15C0;CANADIAN SYLLABICS SAYISI HE;Lo;0;L;;;;;N;;;;; 15C1;CANADIAN SYLLABICS SAYISI HI;Lo;0;L;;;;;N;;;;; 15C2;CANADIAN SYLLABICS SAYISI HO;Lo;0;L;;;;;N;;;;; 15C3;CANADIAN SYLLABICS SAYISI HA;Lo;0;L;;;;;N;;;;; 15C4;CANADIAN SYLLABICS CARRIER GHU;Lo;0;L;;;;;N;;;;; 15C5;CANADIAN SYLLABICS CARRIER GHO;Lo;0;L;;;;;N;;;;; 15C6;CANADIAN SYLLABICS CARRIER GHE;Lo;0;L;;;;;N;;;;; 15C7;CANADIAN SYLLABICS CARRIER GHEE;Lo;0;L;;;;;N;;;;; 15C8;CANADIAN SYLLABICS CARRIER GHI;Lo;0;L;;;;;N;;;;; 15C9;CANADIAN SYLLABICS CARRIER GHA;Lo;0;L;;;;;N;;;;; 15CA;CANADIAN SYLLABICS CARRIER RU;Lo;0;L;;;;;N;;;;; 15CB;CANADIAN SYLLABICS CARRIER RO;Lo;0;L;;;;;N;;;;; 15CC;CANADIAN SYLLABICS CARRIER RE;Lo;0;L;;;;;N;;;;; 15CD;CANADIAN SYLLABICS CARRIER REE;Lo;0;L;;;;;N;;;;; 15CE;CANADIAN SYLLABICS CARRIER RI;Lo;0;L;;;;;N;;;;; 15CF;CANADIAN SYLLABICS CARRIER RA;Lo;0;L;;;;;N;;;;; 15D0;CANADIAN SYLLABICS CARRIER WU;Lo;0;L;;;;;N;;;;; 15D1;CANADIAN SYLLABICS CARRIER WO;Lo;0;L;;;;;N;;;;; 15D2;CANADIAN SYLLABICS CARRIER WE;Lo;0;L;;;;;N;;;;; 15D3;CANADIAN SYLLABICS CARRIER WEE;Lo;0;L;;;;;N;;;;; 15D4;CANADIAN SYLLABICS CARRIER WI;Lo;0;L;;;;;N;;;;; 15D5;CANADIAN SYLLABICS CARRIER WA;Lo;0;L;;;;;N;;;;; 15D6;CANADIAN SYLLABICS CARRIER HWU;Lo;0;L;;;;;N;;;;; 15D7;CANADIAN SYLLABICS CARRIER HWO;Lo;0;L;;;;;N;;;;; 15D8;CANADIAN SYLLABICS CARRIER HWE;Lo;0;L;;;;;N;;;;; 15D9;CANADIAN SYLLABICS CARRIER HWEE;Lo;0;L;;;;;N;;;;; 15DA;CANADIAN SYLLABICS CARRIER HWI;Lo;0;L;;;;;N;;;;; 15DB;CANADIAN SYLLABICS CARRIER HWA;Lo;0;L;;;;;N;;;;; 15DC;CANADIAN SYLLABICS CARRIER THU;Lo;0;L;;;;;N;;;;; 15DD;CANADIAN SYLLABICS CARRIER THO;Lo;0;L;;;;;N;;;;; 15DE;CANADIAN SYLLABICS CARRIER THE;Lo;0;L;;;;;N;;;;; 15DF;CANADIAN SYLLABICS CARRIER THEE;Lo;0;L;;;;;N;;;;; 15E0;CANADIAN SYLLABICS CARRIER THI;Lo;0;L;;;;;N;;;;; 15E1;CANADIAN SYLLABICS CARRIER THA;Lo;0;L;;;;;N;;;;; 15E2;CANADIAN SYLLABICS CARRIER TTU;Lo;0;L;;;;;N;;;;; 15E3;CANADIAN SYLLABICS CARRIER TTO;Lo;0;L;;;;;N;;;;; 15E4;CANADIAN SYLLABICS CARRIER TTE;Lo;0;L;;;;;N;;;;; 15E5;CANADIAN SYLLABICS CARRIER TTEE;Lo;0;L;;;;;N;;;;; 15E6;CANADIAN SYLLABICS CARRIER TTI;Lo;0;L;;;;;N;;;;; 15E7;CANADIAN SYLLABICS CARRIER TTA;Lo;0;L;;;;;N;;;;; 15E8;CANADIAN SYLLABICS CARRIER PU;Lo;0;L;;;;;N;;;;; 15E9;CANADIAN SYLLABICS CARRIER PO;Lo;0;L;;;;;N;;;;; 15EA;CANADIAN SYLLABICS CARRIER PE;Lo;0;L;;;;;N;;;;; 15EB;CANADIAN SYLLABICS CARRIER PEE;Lo;0;L;;;;;N;;;;; 15EC;CANADIAN SYLLABICS CARRIER PI;Lo;0;L;;;;;N;;;;; 15ED;CANADIAN SYLLABICS CARRIER PA;Lo;0;L;;;;;N;;;;; 15EE;CANADIAN SYLLABICS CARRIER P;Lo;0;L;;;;;N;;;;; 15EF;CANADIAN SYLLABICS CARRIER GU;Lo;0;L;;;;;N;;;;; 15F0;CANADIAN SYLLABICS CARRIER GO;Lo;0;L;;;;;N;;;;; 15F1;CANADIAN SYLLABICS CARRIER GE;Lo;0;L;;;;;N;;;;; 15F2;CANADIAN SYLLABICS CARRIER GEE;Lo;0;L;;;;;N;;;;; 15F3;CANADIAN SYLLABICS CARRIER GI;Lo;0;L;;;;;N;;;;; 15F4;CANADIAN SYLLABICS CARRIER GA;Lo;0;L;;;;;N;;;;; 15F5;CANADIAN SYLLABICS CARRIER KHU;Lo;0;L;;;;;N;;;;; 15F6;CANADIAN SYLLABICS CARRIER KHO;Lo;0;L;;;;;N;;;;; 15F7;CANADIAN SYLLABICS CARRIER KHE;Lo;0;L;;;;;N;;;;; 15F8;CANADIAN SYLLABICS CARRIER KHEE;Lo;0;L;;;;;N;;;;; 15F9;CANADIAN SYLLABICS CARRIER KHI;Lo;0;L;;;;;N;;;;; 15FA;CANADIAN SYLLABICS CARRIER KHA;Lo;0;L;;;;;N;;;;; 15FB;CANADIAN SYLLABICS CARRIER KKU;Lo;0;L;;;;;N;;;;; 15FC;CANADIAN SYLLABICS CARRIER KKO;Lo;0;L;;;;;N;;;;; 15FD;CANADIAN SYLLABICS CARRIER KKE;Lo;0;L;;;;;N;;;;; 15FE;CANADIAN SYLLABICS CARRIER KKEE;Lo;0;L;;;;;N;;;;; 15FF;CANADIAN SYLLABICS CARRIER KKI;Lo;0;L;;;;;N;;;;; 1600;CANADIAN SYLLABICS CARRIER KKA;Lo;0;L;;;;;N;;;;; 1601;CANADIAN SYLLABICS CARRIER KK;Lo;0;L;;;;;N;;;;; 1602;CANADIAN SYLLABICS CARRIER NU;Lo;0;L;;;;;N;;;;; 1603;CANADIAN SYLLABICS CARRIER NO;Lo;0;L;;;;;N;;;;; 1604;CANADIAN SYLLABICS CARRIER NE;Lo;0;L;;;;;N;;;;; 1605;CANADIAN SYLLABICS CARRIER NEE;Lo;0;L;;;;;N;;;;; 1606;CANADIAN SYLLABICS CARRIER NI;Lo;0;L;;;;;N;;;;; 1607;CANADIAN SYLLABICS CARRIER NA;Lo;0;L;;;;;N;;;;; 1608;CANADIAN SYLLABICS CARRIER MU;Lo;0;L;;;;;N;;;;; 1609;CANADIAN SYLLABICS CARRIER MO;Lo;0;L;;;;;N;;;;; 160A;CANADIAN SYLLABICS CARRIER ME;Lo;0;L;;;;;N;;;;; 160B;CANADIAN SYLLABICS CARRIER MEE;Lo;0;L;;;;;N;;;;; 160C;CANADIAN SYLLABICS CARRIER MI;Lo;0;L;;;;;N;;;;; 160D;CANADIAN SYLLABICS CARRIER MA;Lo;0;L;;;;;N;;;;; 160E;CANADIAN SYLLABICS CARRIER YU;Lo;0;L;;;;;N;;;;; 160F;CANADIAN SYLLABICS CARRIER YO;Lo;0;L;;;;;N;;;;; 1610;CANADIAN SYLLABICS CARRIER YE;Lo;0;L;;;;;N;;;;; 1611;CANADIAN SYLLABICS CARRIER YEE;Lo;0;L;;;;;N;;;;; 1612;CANADIAN SYLLABICS CARRIER YI;Lo;0;L;;;;;N;;;;; 1613;CANADIAN SYLLABICS CARRIER YA;Lo;0;L;;;;;N;;;;; 1614;CANADIAN SYLLABICS CARRIER JU;Lo;0;L;;;;;N;;;;; 1615;CANADIAN SYLLABICS SAYISI JU;Lo;0;L;;;;;N;;;;; 1616;CANADIAN SYLLABICS CARRIER JO;Lo;0;L;;;;;N;;;;; 1617;CANADIAN SYLLABICS CARRIER JE;Lo;0;L;;;;;N;;;;; 1618;CANADIAN SYLLABICS CARRIER JEE;Lo;0;L;;;;;N;;;;; 1619;CANADIAN SYLLABICS CARRIER JI;Lo;0;L;;;;;N;;;;; 161A;CANADIAN SYLLABICS SAYISI JI;Lo;0;L;;;;;N;;;;; 161B;CANADIAN SYLLABICS CARRIER JA;Lo;0;L;;;;;N;;;;; 161C;CANADIAN SYLLABICS CARRIER JJU;Lo;0;L;;;;;N;;;;; 161D;CANADIAN SYLLABICS CARRIER JJO;Lo;0;L;;;;;N;;;;; 161E;CANADIAN SYLLABICS CARRIER JJE;Lo;0;L;;;;;N;;;;; 161F;CANADIAN SYLLABICS CARRIER JJEE;Lo;0;L;;;;;N;;;;; 1620;CANADIAN SYLLABICS CARRIER JJI;Lo;0;L;;;;;N;;;;; 1621;CANADIAN SYLLABICS CARRIER JJA;Lo;0;L;;;;;N;;;;; 1622;CANADIAN SYLLABICS CARRIER LU;Lo;0;L;;;;;N;;;;; 1623;CANADIAN SYLLABICS CARRIER LO;Lo;0;L;;;;;N;;;;; 1624;CANADIAN SYLLABICS CARRIER LE;Lo;0;L;;;;;N;;;;; 1625;CANADIAN SYLLABICS CARRIER LEE;Lo;0;L;;;;;N;;;;; 1626;CANADIAN SYLLABICS CARRIER LI;Lo;0;L;;;;;N;;;;; 1627;CANADIAN SYLLABICS CARRIER LA;Lo;0;L;;;;;N;;;;; 1628;CANADIAN SYLLABICS CARRIER DLU;Lo;0;L;;;;;N;;;;; 1629;CANADIAN SYLLABICS CARRIER DLO;Lo;0;L;;;;;N;;;;; 162A;CANADIAN SYLLABICS CARRIER DLE;Lo;0;L;;;;;N;;;;; 162B;CANADIAN SYLLABICS CARRIER DLEE;Lo;0;L;;;;;N;;;;; 162C;CANADIAN SYLLABICS CARRIER DLI;Lo;0;L;;;;;N;;;;; 162D;CANADIAN SYLLABICS CARRIER DLA;Lo;0;L;;;;;N;;;;; 162E;CANADIAN SYLLABICS CARRIER LHU;Lo;0;L;;;;;N;;;;; 162F;CANADIAN SYLLABICS CARRIER LHO;Lo;0;L;;;;;N;;;;; 1630;CANADIAN SYLLABICS CARRIER LHE;Lo;0;L;;;;;N;;;;; 1631;CANADIAN SYLLABICS CARRIER LHEE;Lo;0;L;;;;;N;;;;; 1632;CANADIAN SYLLABICS CARRIER LHI;Lo;0;L;;;;;N;;;;; 1633;CANADIAN SYLLABICS CARRIER LHA;Lo;0;L;;;;;N;;;;; 1634;CANADIAN SYLLABICS CARRIER TLHU;Lo;0;L;;;;;N;;;;; 1635;CANADIAN SYLLABICS CARRIER TLHO;Lo;0;L;;;;;N;;;;; 1636;CANADIAN SYLLABICS CARRIER TLHE;Lo;0;L;;;;;N;;;;; 1637;CANADIAN SYLLABICS CARRIER TLHEE;Lo;0;L;;;;;N;;;;; 1638;CANADIAN SYLLABICS CARRIER TLHI;Lo;0;L;;;;;N;;;;; 1639;CANADIAN SYLLABICS CARRIER TLHA;Lo;0;L;;;;;N;;;;; 163A;CANADIAN SYLLABICS CARRIER TLU;Lo;0;L;;;;;N;;;;; 163B;CANADIAN SYLLABICS CARRIER TLO;Lo;0;L;;;;;N;;;;; 163C;CANADIAN SYLLABICS CARRIER TLE;Lo;0;L;;;;;N;;;;; 163D;CANADIAN SYLLABICS CARRIER TLEE;Lo;0;L;;;;;N;;;;; 163E;CANADIAN SYLLABICS CARRIER TLI;Lo;0;L;;;;;N;;;;; 163F;CANADIAN SYLLABICS CARRIER TLA;Lo;0;L;;;;;N;;;;; 1640;CANADIAN SYLLABICS CARRIER ZU;Lo;0;L;;;;;N;;;;; 1641;CANADIAN SYLLABICS CARRIER ZO;Lo;0;L;;;;;N;;;;; 1642;CANADIAN SYLLABICS CARRIER ZE;Lo;0;L;;;;;N;;;;; 1643;CANADIAN SYLLABICS CARRIER ZEE;Lo;0;L;;;;;N;;;;; 1644;CANADIAN SYLLABICS CARRIER ZI;Lo;0;L;;;;;N;;;;; 1645;CANADIAN SYLLABICS CARRIER ZA;Lo;0;L;;;;;N;;;;; 1646;CANADIAN SYLLABICS CARRIER Z;Lo;0;L;;;;;N;;;;; 1647;CANADIAN SYLLABICS CARRIER INITIAL Z;Lo;0;L;;;;;N;;;;; 1648;CANADIAN SYLLABICS CARRIER DZU;Lo;0;L;;;;;N;;;;; 1649;CANADIAN SYLLABICS CARRIER DZO;Lo;0;L;;;;;N;;;;; 164A;CANADIAN SYLLABICS CARRIER DZE;Lo;0;L;;;;;N;;;;; 164B;CANADIAN SYLLABICS CARRIER DZEE;Lo;0;L;;;;;N;;;;; 164C;CANADIAN SYLLABICS CARRIER DZI;Lo;0;L;;;;;N;;;;; 164D;CANADIAN SYLLABICS CARRIER DZA;Lo;0;L;;;;;N;;;;; 164E;CANADIAN SYLLABICS CARRIER SU;Lo;0;L;;;;;N;;;;; 164F;CANADIAN SYLLABICS CARRIER SO;Lo;0;L;;;;;N;;;;; 1650;CANADIAN SYLLABICS CARRIER SE;Lo;0;L;;;;;N;;;;; 1651;CANADIAN SYLLABICS CARRIER SEE;Lo;0;L;;;;;N;;;;; 1652;CANADIAN SYLLABICS CARRIER SI;Lo;0;L;;;;;N;;;;; 1653;CANADIAN SYLLABICS CARRIER SA;Lo;0;L;;;;;N;;;;; 1654;CANADIAN SYLLABICS CARRIER SHU;Lo;0;L;;;;;N;;;;; 1655;CANADIAN SYLLABICS CARRIER SHO;Lo;0;L;;;;;N;;;;; 1656;CANADIAN SYLLABICS CARRIER SHE;Lo;0;L;;;;;N;;;;; 1657;CANADIAN SYLLABICS CARRIER SHEE;Lo;0;L;;;;;N;;;;; 1658;CANADIAN SYLLABICS CARRIER SHI;Lo;0;L;;;;;N;;;;; 1659;CANADIAN SYLLABICS CARRIER SHA;Lo;0;L;;;;;N;;;;; 165A;CANADIAN SYLLABICS CARRIER SH;Lo;0;L;;;;;N;;;;; 165B;CANADIAN SYLLABICS CARRIER TSU;Lo;0;L;;;;;N;;;;; 165C;CANADIAN SYLLABICS CARRIER TSO;Lo;0;L;;;;;N;;;;; 165D;CANADIAN SYLLABICS CARRIER TSE;Lo;0;L;;;;;N;;;;; 165E;CANADIAN SYLLABICS CARRIER TSEE;Lo;0;L;;;;;N;;;;; 165F;CANADIAN SYLLABICS CARRIER TSI;Lo;0;L;;;;;N;;;;; 1660;CANADIAN SYLLABICS CARRIER TSA;Lo;0;L;;;;;N;;;;; 1661;CANADIAN SYLLABICS CARRIER CHU;Lo;0;L;;;;;N;;;;; 1662;CANADIAN SYLLABICS CARRIER CHO;Lo;0;L;;;;;N;;;;; 1663;CANADIAN SYLLABICS CARRIER CHE;Lo;0;L;;;;;N;;;;; 1664;CANADIAN SYLLABICS CARRIER CHEE;Lo;0;L;;;;;N;;;;; 1665;CANADIAN SYLLABICS CARRIER CHI;Lo;0;L;;;;;N;;;;; 1666;CANADIAN SYLLABICS CARRIER CHA;Lo;0;L;;;;;N;;;;; 1667;CANADIAN SYLLABICS CARRIER TTSU;Lo;0;L;;;;;N;;;;; 1668;CANADIAN SYLLABICS CARRIER TTSO;Lo;0;L;;;;;N;;;;; 1669;CANADIAN SYLLABICS CARRIER TTSE;Lo;0;L;;;;;N;;;;; 166A;CANADIAN SYLLABICS CARRIER TTSEE;Lo;0;L;;;;;N;;;;; 166B;CANADIAN SYLLABICS CARRIER TTSI;Lo;0;L;;;;;N;;;;; 166C;CANADIAN SYLLABICS CARRIER TTSA;Lo;0;L;;;;;N;;;;; 166D;CANADIAN SYLLABICS CHI SIGN;Po;0;L;;;;;N;;;;; 166E;CANADIAN SYLLABICS FULL STOP;Po;0;L;;;;;N;;;;; 166F;CANADIAN SYLLABICS QAI;Lo;0;L;;;;;N;;;;; 1670;CANADIAN SYLLABICS NGAI;Lo;0;L;;;;;N;;;;; 1671;CANADIAN SYLLABICS NNGI;Lo;0;L;;;;;N;;;;; 1672;CANADIAN SYLLABICS NNGII;Lo;0;L;;;;;N;;;;; 1673;CANADIAN SYLLABICS NNGO;Lo;0;L;;;;;N;;;;; 1674;CANADIAN SYLLABICS NNGOO;Lo;0;L;;;;;N;;;;; 1675;CANADIAN SYLLABICS NNGA;Lo;0;L;;;;;N;;;;; 1676;CANADIAN SYLLABICS NNGAA;Lo;0;L;;;;;N;;;;; 1677;CANADIAN SYLLABICS WOODS-CREE THWEE;Lo;0;L;;;;;N;;;;; 1678;CANADIAN SYLLABICS WOODS-CREE THWI;Lo;0;L;;;;;N;;;;; 1679;CANADIAN SYLLABICS WOODS-CREE THWII;Lo;0;L;;;;;N;;;;; 167A;CANADIAN SYLLABICS WOODS-CREE THWO;Lo;0;L;;;;;N;;;;; 167B;CANADIAN SYLLABICS WOODS-CREE THWOO;Lo;0;L;;;;;N;;;;; 167C;CANADIAN SYLLABICS WOODS-CREE THWA;Lo;0;L;;;;;N;;;;; 167D;CANADIAN SYLLABICS WOODS-CREE THWAA;Lo;0;L;;;;;N;;;;; 167E;CANADIAN SYLLABICS WOODS-CREE FINAL TH;Lo;0;L;;;;;N;;;;; 167F;CANADIAN SYLLABICS BLACKFOOT W;Lo;0;L;;;;;N;;;;; 1680;OGHAM SPACE MARK;Zs;0;WS;;;;;N;;;;; 1681;OGHAM LETTER BEITH;Lo;0;L;;;;;N;;;;; 1682;OGHAM LETTER LUIS;Lo;0;L;;;;;N;;;;; 1683;OGHAM LETTER FEARN;Lo;0;L;;;;;N;;;;; 1684;OGHAM LETTER SAIL;Lo;0;L;;;;;N;;;;; 1685;OGHAM LETTER NION;Lo;0;L;;;;;N;;;;; 1686;OGHAM LETTER UATH;Lo;0;L;;;;;N;;;;; 1687;OGHAM LETTER DAIR;Lo;0;L;;;;;N;;;;; 1688;OGHAM LETTER TINNE;Lo;0;L;;;;;N;;;;; 1689;OGHAM LETTER COLL;Lo;0;L;;;;;N;;;;; 168A;OGHAM LETTER CEIRT;Lo;0;L;;;;;N;;;;; 168B;OGHAM LETTER MUIN;Lo;0;L;;;;;N;;;;; 168C;OGHAM LETTER GORT;Lo;0;L;;;;;N;;;;; 168D;OGHAM LETTER NGEADAL;Lo;0;L;;;;;N;;;;; 168E;OGHAM LETTER STRAIF;Lo;0;L;;;;;N;;;;; 168F;OGHAM LETTER RUIS;Lo;0;L;;;;;N;;;;; 1690;OGHAM LETTER AILM;Lo;0;L;;;;;N;;;;; 1691;OGHAM LETTER ONN;Lo;0;L;;;;;N;;;;; 1692;OGHAM LETTER UR;Lo;0;L;;;;;N;;;;; 1693;OGHAM LETTER EADHADH;Lo;0;L;;;;;N;;;;; 1694;OGHAM LETTER IODHADH;Lo;0;L;;;;;N;;;;; 1695;OGHAM LETTER EABHADH;Lo;0;L;;;;;N;;;;; 1696;OGHAM LETTER OR;Lo;0;L;;;;;N;;;;; 1697;OGHAM LETTER UILLEANN;Lo;0;L;;;;;N;;;;; 1698;OGHAM LETTER IFIN;Lo;0;L;;;;;N;;;;; 1699;OGHAM LETTER EAMHANCHOLL;Lo;0;L;;;;;N;;;;; 169A;OGHAM LETTER PEITH;Lo;0;L;;;;;N;;;;; 169B;OGHAM FEATHER MARK;Ps;0;ON;;;;;Y;;;;; 169C;OGHAM REVERSED FEATHER MARK;Pe;0;ON;;;;;Y;;;;; 16A0;RUNIC LETTER FEHU FEOH FE F;Lo;0;L;;;;;N;;;;; 16A1;RUNIC LETTER V;Lo;0;L;;;;;N;;;;; 16A2;RUNIC LETTER URUZ UR U;Lo;0;L;;;;;N;;;;; 16A3;RUNIC LETTER YR;Lo;0;L;;;;;N;;;;; 16A4;RUNIC LETTER Y;Lo;0;L;;;;;N;;;;; 16A5;RUNIC LETTER W;Lo;0;L;;;;;N;;;;; 16A6;RUNIC LETTER THURISAZ THURS THORN;Lo;0;L;;;;;N;;;;; 16A7;RUNIC LETTER ETH;Lo;0;L;;;;;N;;;;; 16A8;RUNIC LETTER ANSUZ A;Lo;0;L;;;;;N;;;;; 16A9;RUNIC LETTER OS O;Lo;0;L;;;;;N;;;;; 16AA;RUNIC LETTER AC A;Lo;0;L;;;;;N;;;;; 16AB;RUNIC LETTER AESC;Lo;0;L;;;;;N;;;;; 16AC;RUNIC LETTER LONG-BRANCH-OSS O;Lo;0;L;;;;;N;;;;; 16AD;RUNIC LETTER SHORT-TWIG-OSS O;Lo;0;L;;;;;N;;;;; 16AE;RUNIC LETTER O;Lo;0;L;;;;;N;;;;; 16AF;RUNIC LETTER OE;Lo;0;L;;;;;N;;;;; 16B0;RUNIC LETTER ON;Lo;0;L;;;;;N;;;;; 16B1;RUNIC LETTER RAIDO RAD REID R;Lo;0;L;;;;;N;;;;; 16B2;RUNIC LETTER KAUNA;Lo;0;L;;;;;N;;;;; 16B3;RUNIC LETTER CEN;Lo;0;L;;;;;N;;;;; 16B4;RUNIC LETTER KAUN K;Lo;0;L;;;;;N;;;;; 16B5;RUNIC LETTER G;Lo;0;L;;;;;N;;;;; 16B6;RUNIC LETTER ENG;Lo;0;L;;;;;N;;;;; 16B7;RUNIC LETTER GEBO GYFU G;Lo;0;L;;;;;N;;;;; 16B8;RUNIC LETTER GAR;Lo;0;L;;;;;N;;;;; 16B9;RUNIC LETTER WUNJO WYNN W;Lo;0;L;;;;;N;;;;; 16BA;RUNIC LETTER HAGLAZ H;Lo;0;L;;;;;N;;;;; 16BB;RUNIC LETTER HAEGL H;Lo;0;L;;;;;N;;;;; 16BC;RUNIC LETTER LONG-BRANCH-HAGALL H;Lo;0;L;;;;;N;;;;; 16BD;RUNIC LETTER SHORT-TWIG-HAGALL H;Lo;0;L;;;;;N;;;;; 16BE;RUNIC LETTER NAUDIZ NYD NAUD N;Lo;0;L;;;;;N;;;;; 16BF;RUNIC LETTER SHORT-TWIG-NAUD N;Lo;0;L;;;;;N;;;;; 16C0;RUNIC LETTER DOTTED-N;Lo;0;L;;;;;N;;;;; 16C1;RUNIC LETTER ISAZ IS ISS I;Lo;0;L;;;;;N;;;;; 16C2;RUNIC LETTER E;Lo;0;L;;;;;N;;;;; 16C3;RUNIC LETTER JERAN J;Lo;0;L;;;;;N;;;;; 16C4;RUNIC LETTER GER;Lo;0;L;;;;;N;;;;; 16C5;RUNIC LETTER LONG-BRANCH-AR AE;Lo;0;L;;;;;N;;;;; 16C6;RUNIC LETTER SHORT-TWIG-AR A;Lo;0;L;;;;;N;;;;; 16C7;RUNIC LETTER IWAZ EOH;Lo;0;L;;;;;N;;;;; 16C8;RUNIC LETTER PERTHO PEORTH P;Lo;0;L;;;;;N;;;;; 16C9;RUNIC LETTER ALGIZ EOLHX;Lo;0;L;;;;;N;;;;; 16CA;RUNIC LETTER SOWILO S;Lo;0;L;;;;;N;;;;; 16CB;RUNIC LETTER SIGEL LONG-BRANCH-SOL S;Lo;0;L;;;;;N;;;;; 16CC;RUNIC LETTER SHORT-TWIG-SOL S;Lo;0;L;;;;;N;;;;; 16CD;RUNIC LETTER C;Lo;0;L;;;;;N;;;;; 16CE;RUNIC LETTER Z;Lo;0;L;;;;;N;;;;; 16CF;RUNIC LETTER TIWAZ TIR TYR T;Lo;0;L;;;;;N;;;;; 16D0;RUNIC LETTER SHORT-TWIG-TYR T;Lo;0;L;;;;;N;;;;; 16D1;RUNIC LETTER D;Lo;0;L;;;;;N;;;;; 16D2;RUNIC LETTER BERKANAN BEORC BJARKAN B;Lo;0;L;;;;;N;;;;; 16D3;RUNIC LETTER SHORT-TWIG-BJARKAN B;Lo;0;L;;;;;N;;;;; 16D4;RUNIC LETTER DOTTED-P;Lo;0;L;;;;;N;;;;; 16D5;RUNIC LETTER OPEN-P;Lo;0;L;;;;;N;;;;; 16D6;RUNIC LETTER EHWAZ EH E;Lo;0;L;;;;;N;;;;; 16D7;RUNIC LETTER MANNAZ MAN M;Lo;0;L;;;;;N;;;;; 16D8;RUNIC LETTER LONG-BRANCH-MADR M;Lo;0;L;;;;;N;;;;; 16D9;RUNIC LETTER SHORT-TWIG-MADR M;Lo;0;L;;;;;N;;;;; 16DA;RUNIC LETTER LAUKAZ LAGU LOGR L;Lo;0;L;;;;;N;;;;; 16DB;RUNIC LETTER DOTTED-L;Lo;0;L;;;;;N;;;;; 16DC;RUNIC LETTER INGWAZ;Lo;0;L;;;;;N;;;;; 16DD;RUNIC LETTER ING;Lo;0;L;;;;;N;;;;; 16DE;RUNIC LETTER DAGAZ DAEG D;Lo;0;L;;;;;N;;;;; 16DF;RUNIC LETTER OTHALAN ETHEL O;Lo;0;L;;;;;N;;;;; 16E0;RUNIC LETTER EAR;Lo;0;L;;;;;N;;;;; 16E1;RUNIC LETTER IOR;Lo;0;L;;;;;N;;;;; 16E2;RUNIC LETTER CWEORTH;Lo;0;L;;;;;N;;;;; 16E3;RUNIC LETTER CALC;Lo;0;L;;;;;N;;;;; 16E4;RUNIC LETTER CEALC;Lo;0;L;;;;;N;;;;; 16E5;RUNIC LETTER STAN;Lo;0;L;;;;;N;;;;; 16E6;RUNIC LETTER LONG-BRANCH-YR;Lo;0;L;;;;;N;;;;; 16E7;RUNIC LETTER SHORT-TWIG-YR;Lo;0;L;;;;;N;;;;; 16E8;RUNIC LETTER ICELANDIC-YR;Lo;0;L;;;;;N;;;;; 16E9;RUNIC LETTER Q;Lo;0;L;;;;;N;;;;; 16EA;RUNIC LETTER X;Lo;0;L;;;;;N;;;;; 16EB;RUNIC SINGLE PUNCTUATION;Po;0;L;;;;;N;;;;; 16EC;RUNIC MULTIPLE PUNCTUATION;Po;0;L;;;;;N;;;;; 16ED;RUNIC CROSS PUNCTUATION;Po;0;L;;;;;N;;;;; 16EE;RUNIC ARLAUG SYMBOL;Nl;0;L;;;;17;N;;;;; 16EF;RUNIC TVIMADUR SYMBOL;Nl;0;L;;;;18;N;;;;; 16F0;RUNIC BELGTHOR SYMBOL;Nl;0;L;;;;19;N;;;;; 16F1;RUNIC LETTER K;Lo;0;L;;;;;N;;;;; 16F2;RUNIC LETTER SH;Lo;0;L;;;;;N;;;;; 16F3;RUNIC LETTER OO;Lo;0;L;;;;;N;;;;; 16F4;RUNIC LETTER FRANKS CASKET OS;Lo;0;L;;;;;N;;;;; 16F5;RUNIC LETTER FRANKS CASKET IS;Lo;0;L;;;;;N;;;;; 16F6;RUNIC LETTER FRANKS CASKET EH;Lo;0;L;;;;;N;;;;; 16F7;RUNIC LETTER FRANKS CASKET AC;Lo;0;L;;;;;N;;;;; 16F8;RUNIC LETTER FRANKS CASKET AESC;Lo;0;L;;;;;N;;;;; 1700;TAGALOG LETTER A;Lo;0;L;;;;;N;;;;; 1701;TAGALOG LETTER I;Lo;0;L;;;;;N;;;;; 1702;TAGALOG LETTER U;Lo;0;L;;;;;N;;;;; 1703;TAGALOG LETTER KA;Lo;0;L;;;;;N;;;;; 1704;TAGALOG LETTER GA;Lo;0;L;;;;;N;;;;; 1705;TAGALOG LETTER NGA;Lo;0;L;;;;;N;;;;; 1706;TAGALOG LETTER TA;Lo;0;L;;;;;N;;;;; 1707;TAGALOG LETTER DA;Lo;0;L;;;;;N;;;;; 1708;TAGALOG LETTER NA;Lo;0;L;;;;;N;;;;; 1709;TAGALOG LETTER PA;Lo;0;L;;;;;N;;;;; 170A;TAGALOG LETTER BA;Lo;0;L;;;;;N;;;;; 170B;TAGALOG LETTER MA;Lo;0;L;;;;;N;;;;; 170C;TAGALOG LETTER YA;Lo;0;L;;;;;N;;;;; 170E;TAGALOG LETTER LA;Lo;0;L;;;;;N;;;;; 170F;TAGALOG LETTER WA;Lo;0;L;;;;;N;;;;; 1710;TAGALOG LETTER SA;Lo;0;L;;;;;N;;;;; 1711;TAGALOG LETTER HA;Lo;0;L;;;;;N;;;;; 1712;TAGALOG VOWEL SIGN I;Mn;0;NSM;;;;;N;;;;; 1713;TAGALOG VOWEL SIGN U;Mn;0;NSM;;;;;N;;;;; 1714;TAGALOG SIGN VIRAMA;Mn;9;NSM;;;;;N;;;;; 1720;HANUNOO LETTER A;Lo;0;L;;;;;N;;;;; 1721;HANUNOO LETTER I;Lo;0;L;;;;;N;;;;; 1722;HANUNOO LETTER U;Lo;0;L;;;;;N;;;;; 1723;HANUNOO LETTER KA;Lo;0;L;;;;;N;;;;; 1724;HANUNOO LETTER GA;Lo;0;L;;;;;N;;;;; 1725;HANUNOO LETTER NGA;Lo;0;L;;;;;N;;;;; 1726;HANUNOO LETTER TA;Lo;0;L;;;;;N;;;;; 1727;HANUNOO LETTER DA;Lo;0;L;;;;;N;;;;; 1728;HANUNOO LETTER NA;Lo;0;L;;;;;N;;;;; 1729;HANUNOO LETTER PA;Lo;0;L;;;;;N;;;;; 172A;HANUNOO LETTER BA;Lo;0;L;;;;;N;;;;; 172B;HANUNOO LETTER MA;Lo;0;L;;;;;N;;;;; 172C;HANUNOO LETTER YA;Lo;0;L;;;;;N;;;;; 172D;HANUNOO LETTER RA;Lo;0;L;;;;;N;;;;; 172E;HANUNOO LETTER LA;Lo;0;L;;;;;N;;;;; 172F;HANUNOO LETTER WA;Lo;0;L;;;;;N;;;;; 1730;HANUNOO LETTER SA;Lo;0;L;;;;;N;;;;; 1731;HANUNOO LETTER HA;Lo;0;L;;;;;N;;;;; 1732;HANUNOO VOWEL SIGN I;Mn;0;NSM;;;;;N;;;;; 1733;HANUNOO VOWEL SIGN U;Mn;0;NSM;;;;;N;;;;; 1734;HANUNOO SIGN PAMUDPOD;Mn;9;NSM;;;;;N;;;;; 1735;PHILIPPINE SINGLE PUNCTUATION;Po;0;L;;;;;N;;;;; 1736;PHILIPPINE DOUBLE PUNCTUATION;Po;0;L;;;;;N;;;;; 1740;BUHID LETTER A;Lo;0;L;;;;;N;;;;; 1741;BUHID LETTER I;Lo;0;L;;;;;N;;;;; 1742;BUHID LETTER U;Lo;0;L;;;;;N;;;;; 1743;BUHID LETTER KA;Lo;0;L;;;;;N;;;;; 1744;BUHID LETTER GA;Lo;0;L;;;;;N;;;;; 1745;BUHID LETTER NGA;Lo;0;L;;;;;N;;;;; 1746;BUHID LETTER TA;Lo;0;L;;;;;N;;;;; 1747;BUHID LETTER DA;Lo;0;L;;;;;N;;;;; 1748;BUHID LETTER NA;Lo;0;L;;;;;N;;;;; 1749;BUHID LETTER PA;Lo;0;L;;;;;N;;;;; 174A;BUHID LETTER BA;Lo;0;L;;;;;N;;;;; 174B;BUHID LETTER MA;Lo;0;L;;;;;N;;;;; 174C;BUHID LETTER YA;Lo;0;L;;;;;N;;;;; 174D;BUHID LETTER RA;Lo;0;L;;;;;N;;;;; 174E;BUHID LETTER LA;Lo;0;L;;;;;N;;;;; 174F;BUHID LETTER WA;Lo;0;L;;;;;N;;;;; 1750;BUHID LETTER SA;Lo;0;L;;;;;N;;;;; 1751;BUHID LETTER HA;Lo;0;L;;;;;N;;;;; 1752;BUHID VOWEL SIGN I;Mn;0;NSM;;;;;N;;;;; 1753;BUHID VOWEL SIGN U;Mn;0;NSM;;;;;N;;;;; 1760;TAGBANWA LETTER A;Lo;0;L;;;;;N;;;;; 1761;TAGBANWA LETTER I;Lo;0;L;;;;;N;;;;; 1762;TAGBANWA LETTER U;Lo;0;L;;;;;N;;;;; 1763;TAGBANWA LETTER KA;Lo;0;L;;;;;N;;;;; 1764;TAGBANWA LETTER GA;Lo;0;L;;;;;N;;;;; 1765;TAGBANWA LETTER NGA;Lo;0;L;;;;;N;;;;; 1766;TAGBANWA LETTER TA;Lo;0;L;;;;;N;;;;; 1767;TAGBANWA LETTER DA;Lo;0;L;;;;;N;;;;; 1768;TAGBANWA LETTER NA;Lo;0;L;;;;;N;;;;; 1769;TAGBANWA LETTER PA;Lo;0;L;;;;;N;;;;; 176A;TAGBANWA LETTER BA;Lo;0;L;;;;;N;;;;; 176B;TAGBANWA LETTER MA;Lo;0;L;;;;;N;;;;; 176C;TAGBANWA LETTER YA;Lo;0;L;;;;;N;;;;; 176E;TAGBANWA LETTER LA;Lo;0;L;;;;;N;;;;; 176F;TAGBANWA LETTER WA;Lo;0;L;;;;;N;;;;; 1770;TAGBANWA LETTER SA;Lo;0;L;;;;;N;;;;; 1772;TAGBANWA VOWEL SIGN I;Mn;0;NSM;;;;;N;;;;; 1773;TAGBANWA VOWEL SIGN U;Mn;0;NSM;;;;;N;;;;; 1780;KHMER LETTER KA;Lo;0;L;;;;;N;;;;; 1781;KHMER LETTER KHA;Lo;0;L;;;;;N;;;;; 1782;KHMER LETTER KO;Lo;0;L;;;;;N;;;;; 1783;KHMER LETTER KHO;Lo;0;L;;;;;N;;;;; 1784;KHMER LETTER NGO;Lo;0;L;;;;;N;;;;; 1785;KHMER LETTER CA;Lo;0;L;;;;;N;;;;; 1786;KHMER LETTER CHA;Lo;0;L;;;;;N;;;;; 1787;KHMER LETTER CO;Lo;0;L;;;;;N;;;;; 1788;KHMER LETTER CHO;Lo;0;L;;;;;N;;;;; 1789;KHMER LETTER NYO;Lo;0;L;;;;;N;;;;; 178A;KHMER LETTER DA;Lo;0;L;;;;;N;;;;; 178B;KHMER LETTER TTHA;Lo;0;L;;;;;N;;;;; 178C;KHMER LETTER DO;Lo;0;L;;;;;N;;;;; 178D;KHMER LETTER TTHO;Lo;0;L;;;;;N;;;;; 178E;KHMER LETTER NNO;Lo;0;L;;;;;N;;;;; 178F;KHMER LETTER TA;Lo;0;L;;;;;N;;;;; 1790;KHMER LETTER THA;Lo;0;L;;;;;N;;;;; 1791;KHMER LETTER TO;Lo;0;L;;;;;N;;;;; 1792;KHMER LETTER THO;Lo;0;L;;;;;N;;;;; 1793;KHMER LETTER NO;Lo;0;L;;;;;N;;;;; 1794;KHMER LETTER BA;Lo;0;L;;;;;N;;;;; 1795;KHMER LETTER PHA;Lo;0;L;;;;;N;;;;; 1796;KHMER LETTER PO;Lo;0;L;;;;;N;;;;; 1797;KHMER LETTER PHO;Lo;0;L;;;;;N;;;;; 1798;KHMER LETTER MO;Lo;0;L;;;;;N;;;;; 1799;KHMER LETTER YO;Lo;0;L;;;;;N;;;;; 179A;KHMER LETTER RO;Lo;0;L;;;;;N;;;;; 179B;KHMER LETTER LO;Lo;0;L;;;;;N;;;;; 179C;KHMER LETTER VO;Lo;0;L;;;;;N;;;;; 179D;KHMER LETTER SHA;Lo;0;L;;;;;N;;;;; 179E;KHMER LETTER SSO;Lo;0;L;;;;;N;;;;; 179F;KHMER LETTER SA;Lo;0;L;;;;;N;;;;; 17A0;KHMER LETTER HA;Lo;0;L;;;;;N;;;;; 17A1;KHMER LETTER LA;Lo;0;L;;;;;N;;;;; 17A2;KHMER LETTER QA;Lo;0;L;;;;;N;;;;; 17A3;KHMER INDEPENDENT VOWEL QAQ;Lo;0;L;;;;;N;;;;; 17A4;KHMER INDEPENDENT VOWEL QAA;Lo;0;L;;;;;N;;;;; 17A5;KHMER INDEPENDENT VOWEL QI;Lo;0;L;;;;;N;;;;; 17A6;KHMER INDEPENDENT VOWEL QII;Lo;0;L;;;;;N;;;;; 17A7;KHMER INDEPENDENT VOWEL QU;Lo;0;L;;;;;N;;;;; 17A8;KHMER INDEPENDENT VOWEL QUK;Lo;0;L;;;;;N;;;;; 17A9;KHMER INDEPENDENT VOWEL QUU;Lo;0;L;;;;;N;;;;; 17AA;KHMER INDEPENDENT VOWEL QUUV;Lo;0;L;;;;;N;;;;; 17AB;KHMER INDEPENDENT VOWEL RY;Lo;0;L;;;;;N;;;;; 17AC;KHMER INDEPENDENT VOWEL RYY;Lo;0;L;;;;;N;;;;; 17AD;KHMER INDEPENDENT VOWEL LY;Lo;0;L;;;;;N;;;;; 17AE;KHMER INDEPENDENT VOWEL LYY;Lo;0;L;;;;;N;;;;; 17AF;KHMER INDEPENDENT VOWEL QE;Lo;0;L;;;;;N;;;;; 17B0;KHMER INDEPENDENT VOWEL QAI;Lo;0;L;;;;;N;;;;; 17B1;KHMER INDEPENDENT VOWEL QOO TYPE ONE;Lo;0;L;;;;;N;;;;; 17B2;KHMER INDEPENDENT VOWEL QOO TYPE TWO;Lo;0;L;;;;;N;;;;; 17B3;KHMER INDEPENDENT VOWEL QAU;Lo;0;L;;;;;N;;;;; 17B4;KHMER VOWEL INHERENT AQ;Mn;0;NSM;;;;;N;;;;; 17B5;KHMER VOWEL INHERENT AA;Mn;0;NSM;;;;;N;;;;; 17B6;KHMER VOWEL SIGN AA;Mc;0;L;;;;;N;;;;; 17B7;KHMER VOWEL SIGN I;Mn;0;NSM;;;;;N;;;;; 17B8;KHMER VOWEL SIGN II;Mn;0;NSM;;;;;N;;;;; 17B9;KHMER VOWEL SIGN Y;Mn;0;NSM;;;;;N;;;;; 17BA;KHMER VOWEL SIGN YY;Mn;0;NSM;;;;;N;;;;; 17BB;KHMER VOWEL SIGN U;Mn;0;NSM;;;;;N;;;;; 17BC;KHMER VOWEL SIGN UU;Mn;0;NSM;;;;;N;;;;; 17BD;KHMER VOWEL SIGN UA;Mn;0;NSM;;;;;N;;;;; 17BE;KHMER VOWEL SIGN OE;Mc;0;L;;;;;N;;;;; 17BF;KHMER VOWEL SIGN YA;Mc;0;L;;;;;N;;;;; 17C0;KHMER VOWEL SIGN IE;Mc;0;L;;;;;N;;;;; 17C1;KHMER VOWEL SIGN E;Mc;0;L;;;;;N;;;;; 17C2;KHMER VOWEL SIGN AE;Mc;0;L;;;;;N;;;;; 17C3;KHMER VOWEL SIGN AI;Mc;0;L;;;;;N;;;;; 17C4;KHMER VOWEL SIGN OO;Mc;0;L;;;;;N;;;;; 17C5;KHMER VOWEL SIGN AU;Mc;0;L;;;;;N;;;;; 17C6;KHMER SIGN NIKAHIT;Mn;0;NSM;;;;;N;;;;; 17C7;KHMER SIGN REAHMUK;Mc;0;L;;;;;N;;;;; 17C8;KHMER SIGN YUUKALEAPINTU;Mc;0;L;;;;;N;;;;; 17C9;KHMER SIGN MUUSIKATOAN;Mn;0;NSM;;;;;N;;;;; 17CA;KHMER SIGN TRIISAP;Mn;0;NSM;;;;;N;;;;; 17CB;KHMER SIGN BANTOC;Mn;0;NSM;;;;;N;;;;; 17CC;KHMER SIGN ROBAT;Mn;0;NSM;;;;;N;;;;; 17CD;KHMER SIGN TOANDAKHIAT;Mn;0;NSM;;;;;N;;;;; 17CE;KHMER SIGN KAKABAT;Mn;0;NSM;;;;;N;;;;; 17CF;KHMER SIGN AHSDA;Mn;0;NSM;;;;;N;;;;; 17D0;KHMER SIGN SAMYOK SANNYA;Mn;0;NSM;;;;;N;;;;; 17D1;KHMER SIGN VIRIAM;Mn;0;NSM;;;;;N;;;;; 17D2;KHMER SIGN COENG;Mn;9;NSM;;;;;N;;;;; 17D3;KHMER SIGN BATHAMASAT;Mn;0;NSM;;;;;N;;;;; 17D4;KHMER SIGN KHAN;Po;0;L;;;;;N;;;;; 17D5;KHMER SIGN BARIYOOSAN;Po;0;L;;;;;N;;;;; 17D6;KHMER SIGN CAMNUC PII KUUH;Po;0;L;;;;;N;;;;; 17D7;KHMER SIGN LEK TOO;Lm;0;L;;;;;N;;;;; 17D8;KHMER SIGN BEYYAL;Po;0;L;;;;;N;;;;; 17D9;KHMER SIGN PHNAEK MUAN;Po;0;L;;;;;N;;;;; 17DA;KHMER SIGN KOOMUUT;Po;0;L;;;;;N;;;;; 17DB;KHMER CURRENCY SYMBOL RIEL;Sc;0;ET;;;;;N;;;;; 17DC;KHMER SIGN AVAKRAHASANYA;Lo;0;L;;;;;N;;;;; 17DD;KHMER SIGN ATTHACAN;Mn;230;NSM;;;;;N;;;;; 17E0;KHMER DIGIT ZERO;Nd;0;L;;0;0;0;N;;;;; 17E1;KHMER DIGIT ONE;Nd;0;L;;1;1;1;N;;;;; 17E2;KHMER DIGIT TWO;Nd;0;L;;2;2;2;N;;;;; 17E3;KHMER DIGIT THREE;Nd;0;L;;3;3;3;N;;;;; 17E4;KHMER DIGIT FOUR;Nd;0;L;;4;4;4;N;;;;; 17E5;KHMER DIGIT FIVE;Nd;0;L;;5;5;5;N;;;;; 17E6;KHMER DIGIT SIX;Nd;0;L;;6;6;6;N;;;;; 17E7;KHMER DIGIT SEVEN;Nd;0;L;;7;7;7;N;;;;; 17E8;KHMER DIGIT EIGHT;Nd;0;L;;8;8;8;N;;;;; 17E9;KHMER DIGIT NINE;Nd;0;L;;9;9;9;N;;;;; 17F0;KHMER SYMBOL LEK ATTAK SON;No;0;ON;;;;0;N;;;;; 17F1;KHMER SYMBOL LEK ATTAK MUOY;No;0;ON;;;;1;N;;;;; 17F2;KHMER SYMBOL LEK ATTAK PII;No;0;ON;;;;2;N;;;;; 17F3;KHMER SYMBOL LEK ATTAK BEI;No;0;ON;;;;3;N;;;;; 17F4;KHMER SYMBOL LEK ATTAK BUON;No;0;ON;;;;4;N;;;;; 17F5;KHMER SYMBOL LEK ATTAK PRAM;No;0;ON;;;;5;N;;;;; 17F6;KHMER SYMBOL LEK ATTAK PRAM-MUOY;No;0;ON;;;;6;N;;;;; 17F7;KHMER SYMBOL LEK ATTAK PRAM-PII;No;0;ON;;;;7;N;;;;; 17F8;KHMER SYMBOL LEK ATTAK PRAM-BEI;No;0;ON;;;;8;N;;;;; 17F9;KHMER SYMBOL LEK ATTAK PRAM-BUON;No;0;ON;;;;9;N;;;;; 1800;MONGOLIAN BIRGA;Po;0;ON;;;;;N;;;;; 1801;MONGOLIAN ELLIPSIS;Po;0;ON;;;;;N;;;;; 1802;MONGOLIAN COMMA;Po;0;ON;;;;;N;;;;; 1803;MONGOLIAN FULL STOP;Po;0;ON;;;;;N;;;;; 1804;MONGOLIAN COLON;Po;0;ON;;;;;N;;;;; 1805;MONGOLIAN FOUR DOTS;Po;0;ON;;;;;N;;;;; 1806;MONGOLIAN TODO SOFT HYPHEN;Pd;0;ON;;;;;N;;;;; 1807;MONGOLIAN SIBE SYLLABLE BOUNDARY MARKER;Po;0;ON;;;;;N;;;;; 1808;MONGOLIAN MANCHU COMMA;Po;0;ON;;;;;N;;;;; 1809;MONGOLIAN MANCHU FULL STOP;Po;0;ON;;;;;N;;;;; 180A;MONGOLIAN NIRUGU;Po;0;ON;;;;;N;;;;; 180B;MONGOLIAN FREE VARIATION SELECTOR ONE;Mn;0;NSM;;;;;N;;;;; 180C;MONGOLIAN FREE VARIATION SELECTOR TWO;Mn;0;NSM;;;;;N;;;;; 180D;MONGOLIAN FREE VARIATION SELECTOR THREE;Mn;0;NSM;;;;;N;;;;; 180E;MONGOLIAN VOWEL SEPARATOR;Cf;0;BN;;;;;N;;;;; 1810;MONGOLIAN DIGIT ZERO;Nd;0;L;;0;0;0;N;;;;; 1811;MONGOLIAN DIGIT ONE;Nd;0;L;;1;1;1;N;;;;; 1812;MONGOLIAN DIGIT TWO;Nd;0;L;;2;2;2;N;;;;; 1813;MONGOLIAN DIGIT THREE;Nd;0;L;;3;3;3;N;;;;; 1814;MONGOLIAN DIGIT FOUR;Nd;0;L;;4;4;4;N;;;;; 1815;MONGOLIAN DIGIT FIVE;Nd;0;L;;5;5;5;N;;;;; 1816;MONGOLIAN DIGIT SIX;Nd;0;L;;6;6;6;N;;;;; 1817;MONGOLIAN DIGIT SEVEN;Nd;0;L;;7;7;7;N;;;;; 1818;MONGOLIAN DIGIT EIGHT;Nd;0;L;;8;8;8;N;;;;; 1819;MONGOLIAN DIGIT NINE;Nd;0;L;;9;9;9;N;;;;; 1820;MONGOLIAN LETTER A;Lo;0;L;;;;;N;;;;; 1821;MONGOLIAN LETTER E;Lo;0;L;;;;;N;;;;; 1822;MONGOLIAN LETTER I;Lo;0;L;;;;;N;;;;; 1823;MONGOLIAN LETTER O;Lo;0;L;;;;;N;;;;; 1824;MONGOLIAN LETTER U;Lo;0;L;;;;;N;;;;; 1825;MONGOLIAN LETTER OE;Lo;0;L;;;;;N;;;;; 1826;MONGOLIAN LETTER UE;Lo;0;L;;;;;N;;;;; 1827;MONGOLIAN LETTER EE;Lo;0;L;;;;;N;;;;; 1828;MONGOLIAN LETTER NA;Lo;0;L;;;;;N;;;;; 1829;MONGOLIAN LETTER ANG;Lo;0;L;;;;;N;;;;; 182A;MONGOLIAN LETTER BA;Lo;0;L;;;;;N;;;;; 182B;MONGOLIAN LETTER PA;Lo;0;L;;;;;N;;;;; 182C;MONGOLIAN LETTER QA;Lo;0;L;;;;;N;;;;; 182D;MONGOLIAN LETTER GA;Lo;0;L;;;;;N;;;;; 182E;MONGOLIAN LETTER MA;Lo;0;L;;;;;N;;;;; 182F;MONGOLIAN LETTER LA;Lo;0;L;;;;;N;;;;; 1830;MONGOLIAN LETTER SA;Lo;0;L;;;;;N;;;;; 1831;MONGOLIAN LETTER SHA;Lo;0;L;;;;;N;;;;; 1832;MONGOLIAN LETTER TA;Lo;0;L;;;;;N;;;;; 1833;MONGOLIAN LETTER DA;Lo;0;L;;;;;N;;;;; 1834;MONGOLIAN LETTER CHA;Lo;0;L;;;;;N;;;;; 1835;MONGOLIAN LETTER JA;Lo;0;L;;;;;N;;;;; 1836;MONGOLIAN LETTER YA;Lo;0;L;;;;;N;;;;; 1837;MONGOLIAN LETTER RA;Lo;0;L;;;;;N;;;;; 1838;MONGOLIAN LETTER WA;Lo;0;L;;;;;N;;;;; 1839;MONGOLIAN LETTER FA;Lo;0;L;;;;;N;;;;; 183A;MONGOLIAN LETTER KA;Lo;0;L;;;;;N;;;;; 183B;MONGOLIAN LETTER KHA;Lo;0;L;;;;;N;;;;; 183C;MONGOLIAN LETTER TSA;Lo;0;L;;;;;N;;;;; 183D;MONGOLIAN LETTER ZA;Lo;0;L;;;;;N;;;;; 183E;MONGOLIAN LETTER HAA;Lo;0;L;;;;;N;;;;; 183F;MONGOLIAN LETTER ZRA;Lo;0;L;;;;;N;;;;; 1840;MONGOLIAN LETTER LHA;Lo;0;L;;;;;N;;;;; 1841;MONGOLIAN LETTER ZHI;Lo;0;L;;;;;N;;;;; 1842;MONGOLIAN LETTER CHI;Lo;0;L;;;;;N;;;;; 1843;MONGOLIAN LETTER TODO LONG VOWEL SIGN;Lm;0;L;;;;;N;;;;; 1844;MONGOLIAN LETTER TODO E;Lo;0;L;;;;;N;;;;; 1845;MONGOLIAN LETTER TODO I;Lo;0;L;;;;;N;;;;; 1846;MONGOLIAN LETTER TODO O;Lo;0;L;;;;;N;;;;; 1847;MONGOLIAN LETTER TODO U;Lo;0;L;;;;;N;;;;; 1848;MONGOLIAN LETTER TODO OE;Lo;0;L;;;;;N;;;;; 1849;MONGOLIAN LETTER TODO UE;Lo;0;L;;;;;N;;;;; 184A;MONGOLIAN LETTER TODO ANG;Lo;0;L;;;;;N;;;;; 184B;MONGOLIAN LETTER TODO BA;Lo;0;L;;;;;N;;;;; 184C;MONGOLIAN LETTER TODO PA;Lo;0;L;;;;;N;;;;; 184D;MONGOLIAN LETTER TODO QA;Lo;0;L;;;;;N;;;;; 184E;MONGOLIAN LETTER TODO GA;Lo;0;L;;;;;N;;;;; 184F;MONGOLIAN LETTER TODO MA;Lo;0;L;;;;;N;;;;; 1850;MONGOLIAN LETTER TODO TA;Lo;0;L;;;;;N;;;;; 1851;MONGOLIAN LETTER TODO DA;Lo;0;L;;;;;N;;;;; 1852;MONGOLIAN LETTER TODO CHA;Lo;0;L;;;;;N;;;;; 1853;MONGOLIAN LETTER TODO JA;Lo;0;L;;;;;N;;;;; 1854;MONGOLIAN LETTER TODO TSA;Lo;0;L;;;;;N;;;;; 1855;MONGOLIAN LETTER TODO YA;Lo;0;L;;;;;N;;;;; 1856;MONGOLIAN LETTER TODO WA;Lo;0;L;;;;;N;;;;; 1857;MONGOLIAN LETTER TODO KA;Lo;0;L;;;;;N;;;;; 1858;MONGOLIAN LETTER TODO GAA;Lo;0;L;;;;;N;;;;; 1859;MONGOLIAN LETTER TODO HAA;Lo;0;L;;;;;N;;;;; 185A;MONGOLIAN LETTER TODO JIA;Lo;0;L;;;;;N;;;;; 185B;MONGOLIAN LETTER TODO NIA;Lo;0;L;;;;;N;;;;; 185C;MONGOLIAN LETTER TODO DZA;Lo;0;L;;;;;N;;;;; 185D;MONGOLIAN LETTER SIBE E;Lo;0;L;;;;;N;;;;; 185E;MONGOLIAN LETTER SIBE I;Lo;0;L;;;;;N;;;;; 185F;MONGOLIAN LETTER SIBE IY;Lo;0;L;;;;;N;;;;; 1860;MONGOLIAN LETTER SIBE UE;Lo;0;L;;;;;N;;;;; 1861;MONGOLIAN LETTER SIBE U;Lo;0;L;;;;;N;;;;; 1862;MONGOLIAN LETTER SIBE ANG;Lo;0;L;;;;;N;;;;; 1863;MONGOLIAN LETTER SIBE KA;Lo;0;L;;;;;N;;;;; 1864;MONGOLIAN LETTER SIBE GA;Lo;0;L;;;;;N;;;;; 1865;MONGOLIAN LETTER SIBE HA;Lo;0;L;;;;;N;;;;; 1866;MONGOLIAN LETTER SIBE PA;Lo;0;L;;;;;N;;;;; 1867;MONGOLIAN LETTER SIBE SHA;Lo;0;L;;;;;N;;;;; 1868;MONGOLIAN LETTER SIBE TA;Lo;0;L;;;;;N;;;;; 1869;MONGOLIAN LETTER SIBE DA;Lo;0;L;;;;;N;;;;; 186A;MONGOLIAN LETTER SIBE JA;Lo;0;L;;;;;N;;;;; 186B;MONGOLIAN LETTER SIBE FA;Lo;0;L;;;;;N;;;;; 186C;MONGOLIAN LETTER SIBE GAA;Lo;0;L;;;;;N;;;;; 186D;MONGOLIAN LETTER SIBE HAA;Lo;0;L;;;;;N;;;;; 186E;MONGOLIAN LETTER SIBE TSA;Lo;0;L;;;;;N;;;;; 186F;MONGOLIAN LETTER SIBE ZA;Lo;0;L;;;;;N;;;;; 1870;MONGOLIAN LETTER SIBE RAA;Lo;0;L;;;;;N;;;;; 1871;MONGOLIAN LETTER SIBE CHA;Lo;0;L;;;;;N;;;;; 1872;MONGOLIAN LETTER SIBE ZHA;Lo;0;L;;;;;N;;;;; 1873;MONGOLIAN LETTER MANCHU I;Lo;0;L;;;;;N;;;;; 1874;MONGOLIAN LETTER MANCHU KA;Lo;0;L;;;;;N;;;;; 1875;MONGOLIAN LETTER MANCHU RA;Lo;0;L;;;;;N;;;;; 1876;MONGOLIAN LETTER MANCHU FA;Lo;0;L;;;;;N;;;;; 1877;MONGOLIAN LETTER MANCHU ZHA;Lo;0;L;;;;;N;;;;; 1880;MONGOLIAN LETTER ALI GALI ANUSVARA ONE;Lo;0;L;;;;;N;;;;; 1881;MONGOLIAN LETTER ALI GALI VISARGA ONE;Lo;0;L;;;;;N;;;;; 1882;MONGOLIAN LETTER ALI GALI DAMARU;Lo;0;L;;;;;N;;;;; 1883;MONGOLIAN LETTER ALI GALI UBADAMA;Lo;0;L;;;;;N;;;;; 1884;MONGOLIAN LETTER ALI GALI INVERTED UBADAMA;Lo;0;L;;;;;N;;;;; 1885;MONGOLIAN LETTER ALI GALI BALUDA;Lo;0;L;;;;;N;;;;; 1886;MONGOLIAN LETTER ALI GALI THREE BALUDA;Lo;0;L;;;;;N;;;;; 1887;MONGOLIAN LETTER ALI GALI A;Lo;0;L;;;;;N;;;;; 1888;MONGOLIAN LETTER ALI GALI I;Lo;0;L;;;;;N;;;;; 1889;MONGOLIAN LETTER ALI GALI KA;Lo;0;L;;;;;N;;;;; 188A;MONGOLIAN LETTER ALI GALI NGA;Lo;0;L;;;;;N;;;;; 188B;MONGOLIAN LETTER ALI GALI CA;Lo;0;L;;;;;N;;;;; 188C;MONGOLIAN LETTER ALI GALI TTA;Lo;0;L;;;;;N;;;;; 188D;MONGOLIAN LETTER ALI GALI TTHA;Lo;0;L;;;;;N;;;;; 188E;MONGOLIAN LETTER ALI GALI DDA;Lo;0;L;;;;;N;;;;; 188F;MONGOLIAN LETTER ALI GALI NNA;Lo;0;L;;;;;N;;;;; 1890;MONGOLIAN LETTER ALI GALI TA;Lo;0;L;;;;;N;;;;; 1891;MONGOLIAN LETTER ALI GALI DA;Lo;0;L;;;;;N;;;;; 1892;MONGOLIAN LETTER ALI GALI PA;Lo;0;L;;;;;N;;;;; 1893;MONGOLIAN LETTER ALI GALI PHA;Lo;0;L;;;;;N;;;;; 1894;MONGOLIAN LETTER ALI GALI SSA;Lo;0;L;;;;;N;;;;; 1895;MONGOLIAN LETTER ALI GALI ZHA;Lo;0;L;;;;;N;;;;; 1896;MONGOLIAN LETTER ALI GALI ZA;Lo;0;L;;;;;N;;;;; 1897;MONGOLIAN LETTER ALI GALI AH;Lo;0;L;;;;;N;;;;; 1898;MONGOLIAN LETTER TODO ALI GALI TA;Lo;0;L;;;;;N;;;;; 1899;MONGOLIAN LETTER TODO ALI GALI ZHA;Lo;0;L;;;;;N;;;;; 189A;MONGOLIAN LETTER MANCHU ALI GALI GHA;Lo;0;L;;;;;N;;;;; 189B;MONGOLIAN LETTER MANCHU ALI GALI NGA;Lo;0;L;;;;;N;;;;; 189C;MONGOLIAN LETTER MANCHU ALI GALI CA;Lo;0;L;;;;;N;;;;; 189D;MONGOLIAN LETTER MANCHU ALI GALI JHA;Lo;0;L;;;;;N;;;;; 189E;MONGOLIAN LETTER MANCHU ALI GALI TTA;Lo;0;L;;;;;N;;;;; 189F;MONGOLIAN LETTER MANCHU ALI GALI DDHA;Lo;0;L;;;;;N;;;;; 18A0;MONGOLIAN LETTER MANCHU ALI GALI TA;Lo;0;L;;;;;N;;;;; 18A1;MONGOLIAN LETTER MANCHU ALI GALI DHA;Lo;0;L;;;;;N;;;;; 18A2;MONGOLIAN LETTER MANCHU ALI GALI SSA;Lo;0;L;;;;;N;;;;; 18A3;MONGOLIAN LETTER MANCHU ALI GALI CYA;Lo;0;L;;;;;N;;;;; 18A4;MONGOLIAN LETTER MANCHU ALI GALI ZHA;Lo;0;L;;;;;N;;;;; 18A5;MONGOLIAN LETTER MANCHU ALI GALI ZA;Lo;0;L;;;;;N;;;;; 18A6;MONGOLIAN LETTER ALI GALI HALF U;Lo;0;L;;;;;N;;;;; 18A7;MONGOLIAN LETTER ALI GALI HALF YA;Lo;0;L;;;;;N;;;;; 18A8;MONGOLIAN LETTER MANCHU ALI GALI BHA;Lo;0;L;;;;;N;;;;; 18A9;MONGOLIAN LETTER ALI GALI DAGALGA;Mn;228;NSM;;;;;N;;;;; 18AA;MONGOLIAN LETTER MANCHU ALI GALI LHA;Lo;0;L;;;;;N;;;;; 18B0;CANADIAN SYLLABICS OY;Lo;0;L;;;;;N;;;;; 18B1;CANADIAN SYLLABICS AY;Lo;0;L;;;;;N;;;;; 18B2;CANADIAN SYLLABICS AAY;Lo;0;L;;;;;N;;;;; 18B3;CANADIAN SYLLABICS WAY;Lo;0;L;;;;;N;;;;; 18B4;CANADIAN SYLLABICS POY;Lo;0;L;;;;;N;;;;; 18B5;CANADIAN SYLLABICS PAY;Lo;0;L;;;;;N;;;;; 18B6;CANADIAN SYLLABICS PWOY;Lo;0;L;;;;;N;;;;; 18B7;CANADIAN SYLLABICS TAY;Lo;0;L;;;;;N;;;;; 18B8;CANADIAN SYLLABICS KAY;Lo;0;L;;;;;N;;;;; 18B9;CANADIAN SYLLABICS KWAY;Lo;0;L;;;;;N;;;;; 18BA;CANADIAN SYLLABICS MAY;Lo;0;L;;;;;N;;;;; 18BB;CANADIAN SYLLABICS NOY;Lo;0;L;;;;;N;;;;; 18BC;CANADIAN SYLLABICS NAY;Lo;0;L;;;;;N;;;;; 18BD;CANADIAN SYLLABICS LAY;Lo;0;L;;;;;N;;;;; 18BE;CANADIAN SYLLABICS SOY;Lo;0;L;;;;;N;;;;; 18BF;CANADIAN SYLLABICS SAY;Lo;0;L;;;;;N;;;;; 18C0;CANADIAN SYLLABICS SHOY;Lo;0;L;;;;;N;;;;; 18C1;CANADIAN SYLLABICS SHAY;Lo;0;L;;;;;N;;;;; 18C2;CANADIAN SYLLABICS SHWOY;Lo;0;L;;;;;N;;;;; 18C3;CANADIAN SYLLABICS YOY;Lo;0;L;;;;;N;;;;; 18C4;CANADIAN SYLLABICS YAY;Lo;0;L;;;;;N;;;;; 18C5;CANADIAN SYLLABICS RAY;Lo;0;L;;;;;N;;;;; 18C6;CANADIAN SYLLABICS NWI;Lo;0;L;;;;;N;;;;; 18C7;CANADIAN SYLLABICS OJIBWAY NWI;Lo;0;L;;;;;N;;;;; 18C8;CANADIAN SYLLABICS NWII;Lo;0;L;;;;;N;;;;; 18C9;CANADIAN SYLLABICS OJIBWAY NWII;Lo;0;L;;;;;N;;;;; 18CA;CANADIAN SYLLABICS NWO;Lo;0;L;;;;;N;;;;; 18CB;CANADIAN SYLLABICS OJIBWAY NWO;Lo;0;L;;;;;N;;;;; 18CC;CANADIAN SYLLABICS NWOO;Lo;0;L;;;;;N;;;;; 18CD;CANADIAN SYLLABICS OJIBWAY NWOO;Lo;0;L;;;;;N;;;;; 18CE;CANADIAN SYLLABICS RWEE;Lo;0;L;;;;;N;;;;; 18CF;CANADIAN SYLLABICS RWI;Lo;0;L;;;;;N;;;;; 18D0;CANADIAN SYLLABICS RWII;Lo;0;L;;;;;N;;;;; 18D1;CANADIAN SYLLABICS RWO;Lo;0;L;;;;;N;;;;; 18D2;CANADIAN SYLLABICS RWOO;Lo;0;L;;;;;N;;;;; 18D3;CANADIAN SYLLABICS RWA;Lo;0;L;;;;;N;;;;; 18D4;CANADIAN SYLLABICS OJIBWAY P;Lo;0;L;;;;;N;;;;; 18D5;CANADIAN SYLLABICS OJIBWAY T;Lo;0;L;;;;;N;;;;; 18D6;CANADIAN SYLLABICS OJIBWAY K;Lo;0;L;;;;;N;;;;; 18D7;CANADIAN SYLLABICS OJIBWAY C;Lo;0;L;;;;;N;;;;; 18D8;CANADIAN SYLLABICS OJIBWAY M;Lo;0;L;;;;;N;;;;; 18D9;CANADIAN SYLLABICS OJIBWAY N;Lo;0;L;;;;;N;;;;; 18DA;CANADIAN SYLLABICS OJIBWAY S;Lo;0;L;;;;;N;;;;; 18DB;CANADIAN SYLLABICS OJIBWAY SH;Lo;0;L;;;;;N;;;;; 18DC;CANADIAN SYLLABICS EASTERN W;Lo;0;L;;;;;N;;;;; 18DD;CANADIAN SYLLABICS WESTERN W;Lo;0;L;;;;;N;;;;; 18DE;CANADIAN SYLLABICS FINAL SMALL RING;Lo;0;L;;;;;N;;;;; 18DF;CANADIAN SYLLABICS FINAL RAISED DOT;Lo;0;L;;;;;N;;;;; 18E0;CANADIAN SYLLABICS R-CREE RWE;Lo;0;L;;;;;N;;;;; 18E1;CANADIAN SYLLABICS WEST-CREE LOO;Lo;0;L;;;;;N;;;;; 18E2;CANADIAN SYLLABICS WEST-CREE LAA;Lo;0;L;;;;;N;;;;; 18E3;CANADIAN SYLLABICS THWE;Lo;0;L;;;;;N;;;;; 18E4;CANADIAN SYLLABICS THWA;Lo;0;L;;;;;N;;;;; 18E5;CANADIAN SYLLABICS TTHWE;Lo;0;L;;;;;N;;;;; 18E6;CANADIAN SYLLABICS TTHOO;Lo;0;L;;;;;N;;;;; 18E7;CANADIAN SYLLABICS TTHAA;Lo;0;L;;;;;N;;;;; 18E8;CANADIAN SYLLABICS TLHWE;Lo;0;L;;;;;N;;;;; 18E9;CANADIAN SYLLABICS TLHOO;Lo;0;L;;;;;N;;;;; 18EA;CANADIAN SYLLABICS SAYISI SHWE;Lo;0;L;;;;;N;;;;; 18EB;CANADIAN SYLLABICS SAYISI SHOO;Lo;0;L;;;;;N;;;;; 18EC;CANADIAN SYLLABICS SAYISI HOO;Lo;0;L;;;;;N;;;;; 18ED;CANADIAN SYLLABICS CARRIER GWU;Lo;0;L;;;;;N;;;;; 18EE;CANADIAN SYLLABICS CARRIER DENE GEE;Lo;0;L;;;;;N;;;;; 18EF;CANADIAN SYLLABICS CARRIER GAA;Lo;0;L;;;;;N;;;;; 18F0;CANADIAN SYLLABICS CARRIER GWA;Lo;0;L;;;;;N;;;;; 18F1;CANADIAN SYLLABICS SAYISI JUU;Lo;0;L;;;;;N;;;;; 18F2;CANADIAN SYLLABICS CARRIER JWA;Lo;0;L;;;;;N;;;;; 18F3;CANADIAN SYLLABICS BEAVER DENE L;Lo;0;L;;;;;N;;;;; 18F4;CANADIAN SYLLABICS BEAVER DENE R;Lo;0;L;;;;;N;;;;; 18F5;CANADIAN SYLLABICS CARRIER DENTAL S;Lo;0;L;;;;;N;;;;; 1900;LIMBU VOWEL-CARRIER LETTER;Lo;0;L;;;;;N;;;;; 1901;LIMBU LETTER KA;Lo;0;L;;;;;N;;;;; 1902;LIMBU LETTER KHA;Lo;0;L;;;;;N;;;;; 1903;LIMBU LETTER GA;Lo;0;L;;;;;N;;;;; 1904;LIMBU LETTER GHA;Lo;0;L;;;;;N;;;;; 1905;LIMBU LETTER NGA;Lo;0;L;;;;;N;;;;; 1906;LIMBU LETTER CA;Lo;0;L;;;;;N;;;;; 1907;LIMBU LETTER CHA;Lo;0;L;;;;;N;;;;; 1908;LIMBU LETTER JA;Lo;0;L;;;;;N;;;;; 1909;LIMBU LETTER JHA;Lo;0;L;;;;;N;;;;; 190A;LIMBU LETTER YAN;Lo;0;L;;;;;N;;;;; 190B;LIMBU LETTER TA;Lo;0;L;;;;;N;;;;; 190C;LIMBU LETTER THA;Lo;0;L;;;;;N;;;;; 190D;LIMBU LETTER DA;Lo;0;L;;;;;N;;;;; 190E;LIMBU LETTER DHA;Lo;0;L;;;;;N;;;;; 190F;LIMBU LETTER NA;Lo;0;L;;;;;N;;;;; 1910;LIMBU LETTER PA;Lo;0;L;;;;;N;;;;; 1911;LIMBU LETTER PHA;Lo;0;L;;;;;N;;;;; 1912;LIMBU LETTER BA;Lo;0;L;;;;;N;;;;; 1913;LIMBU LETTER BHA;Lo;0;L;;;;;N;;;;; 1914;LIMBU LETTER MA;Lo;0;L;;;;;N;;;;; 1915;LIMBU LETTER YA;Lo;0;L;;;;;N;;;;; 1916;LIMBU LETTER RA;Lo;0;L;;;;;N;;;;; 1917;LIMBU LETTER LA;Lo;0;L;;;;;N;;;;; 1918;LIMBU LETTER WA;Lo;0;L;;;;;N;;;;; 1919;LIMBU LETTER SHA;Lo;0;L;;;;;N;;;;; 191A;LIMBU LETTER SSA;Lo;0;L;;;;;N;;;;; 191B;LIMBU LETTER SA;Lo;0;L;;;;;N;;;;; 191C;LIMBU LETTER HA;Lo;0;L;;;;;N;;;;; 191D;LIMBU LETTER GYAN;Lo;0;L;;;;;N;;;;; 191E;LIMBU LETTER TRA;Lo;0;L;;;;;N;;;;; 1920;LIMBU VOWEL SIGN A;Mn;0;NSM;;;;;N;;;;; 1921;LIMBU VOWEL SIGN I;Mn;0;NSM;;;;;N;;;;; 1922;LIMBU VOWEL SIGN U;Mn;0;NSM;;;;;N;;;;; 1923;LIMBU VOWEL SIGN EE;Mc;0;L;;;;;N;;;;; 1924;LIMBU VOWEL SIGN AI;Mc;0;L;;;;;N;;;;; 1925;LIMBU VOWEL SIGN OO;Mc;0;L;;;;;N;;;;; 1926;LIMBU VOWEL SIGN AU;Mc;0;L;;;;;N;;;;; 1927;LIMBU VOWEL SIGN E;Mn;0;NSM;;;;;N;;;;; 1928;LIMBU VOWEL SIGN O;Mn;0;NSM;;;;;N;;;;; 1929;LIMBU SUBJOINED LETTER YA;Mc;0;L;;;;;N;;;;; 192A;LIMBU SUBJOINED LETTER RA;Mc;0;L;;;;;N;;;;; 192B;LIMBU SUBJOINED LETTER WA;Mc;0;L;;;;;N;;;;; 1930;LIMBU SMALL LETTER KA;Mc;0;L;;;;;N;;;;; 1931;LIMBU SMALL LETTER NGA;Mc;0;L;;;;;N;;;;; 1932;LIMBU SMALL LETTER ANUSVARA;Mn;0;NSM;;;;;N;;;;; 1933;LIMBU SMALL LETTER TA;Mc;0;L;;;;;N;;;;; 1934;LIMBU SMALL LETTER NA;Mc;0;L;;;;;N;;;;; 1935;LIMBU SMALL LETTER PA;Mc;0;L;;;;;N;;;;; 1936;LIMBU SMALL LETTER MA;Mc;0;L;;;;;N;;;;; 1937;LIMBU SMALL LETTER RA;Mc;0;L;;;;;N;;;;; 1938;LIMBU SMALL LETTER LA;Mc;0;L;;;;;N;;;;; 1939;LIMBU SIGN MUKPHRENG;Mn;222;NSM;;;;;N;;;;; 193A;LIMBU SIGN KEMPHRENG;Mn;230;NSM;;;;;N;;;;; 193B;LIMBU SIGN SA-I;Mn;220;NSM;;;;;N;;;;; 1940;LIMBU SIGN LOO;So;0;ON;;;;;N;;;;; 1944;LIMBU EXCLAMATION MARK;Po;0;ON;;;;;N;;;;; 1945;LIMBU QUESTION MARK;Po;0;ON;;;;;N;;;;; 1946;LIMBU DIGIT ZERO;Nd;0;L;;0;0;0;N;;;;; 1947;LIMBU DIGIT ONE;Nd;0;L;;1;1;1;N;;;;; 1948;LIMBU DIGIT TWO;Nd;0;L;;2;2;2;N;;;;; 1949;LIMBU DIGIT THREE;Nd;0;L;;3;3;3;N;;;;; 194A;LIMBU DIGIT FOUR;Nd;0;L;;4;4;4;N;;;;; 194B;LIMBU DIGIT FIVE;Nd;0;L;;5;5;5;N;;;;; 194C;LIMBU DIGIT SIX;Nd;0;L;;6;6;6;N;;;;; 194D;LIMBU DIGIT SEVEN;Nd;0;L;;7;7;7;N;;;;; 194E;LIMBU DIGIT EIGHT;Nd;0;L;;8;8;8;N;;;;; 194F;LIMBU DIGIT NINE;Nd;0;L;;9;9;9;N;;;;; 1950;TAI LE LETTER KA;Lo;0;L;;;;;N;;;;; 1951;TAI LE LETTER XA;Lo;0;L;;;;;N;;;;; 1952;TAI LE LETTER NGA;Lo;0;L;;;;;N;;;;; 1953;TAI LE LETTER TSA;Lo;0;L;;;;;N;;;;; 1954;TAI LE LETTER SA;Lo;0;L;;;;;N;;;;; 1955;TAI LE LETTER YA;Lo;0;L;;;;;N;;;;; 1956;TAI LE LETTER TA;Lo;0;L;;;;;N;;;;; 1957;TAI LE LETTER THA;Lo;0;L;;;;;N;;;;; 1958;TAI LE LETTER LA;Lo;0;L;;;;;N;;;;; 1959;TAI LE LETTER PA;Lo;0;L;;;;;N;;;;; 195A;TAI LE LETTER PHA;Lo;0;L;;;;;N;;;;; 195B;TAI LE LETTER MA;Lo;0;L;;;;;N;;;;; 195C;TAI LE LETTER FA;Lo;0;L;;;;;N;;;;; 195D;TAI LE LETTER VA;Lo;0;L;;;;;N;;;;; 195E;TAI LE LETTER HA;Lo;0;L;;;;;N;;;;; 195F;TAI LE LETTER QA;Lo;0;L;;;;;N;;;;; 1960;TAI LE LETTER KHA;Lo;0;L;;;;;N;;;;; 1961;TAI LE LETTER TSHA;Lo;0;L;;;;;N;;;;; 1962;TAI LE LETTER NA;Lo;0;L;;;;;N;;;;; 1963;TAI LE LETTER A;Lo;0;L;;;;;N;;;;; 1964;TAI LE LETTER I;Lo;0;L;;;;;N;;;;; 1965;TAI LE LETTER EE;Lo;0;L;;;;;N;;;;; 1966;TAI LE LETTER EH;Lo;0;L;;;;;N;;;;; 1967;TAI LE LETTER U;Lo;0;L;;;;;N;;;;; 1968;TAI LE LETTER OO;Lo;0;L;;;;;N;;;;; 1969;TAI LE LETTER O;Lo;0;L;;;;;N;;;;; 196A;TAI LE LETTER UE;Lo;0;L;;;;;N;;;;; 196B;TAI LE LETTER E;Lo;0;L;;;;;N;;;;; 196C;TAI LE LETTER AUE;Lo;0;L;;;;;N;;;;; 196D;TAI LE LETTER AI;Lo;0;L;;;;;N;;;;; 1970;TAI LE LETTER TONE-2;Lo;0;L;;;;;N;;;;; 1971;TAI LE LETTER TONE-3;Lo;0;L;;;;;N;;;;; 1972;TAI LE LETTER TONE-4;Lo;0;L;;;;;N;;;;; 1973;TAI LE LETTER TONE-5;Lo;0;L;;;;;N;;;;; 1974;TAI LE LETTER TONE-6;Lo;0;L;;;;;N;;;;; 1980;NEW TAI LUE LETTER HIGH QA;Lo;0;L;;;;;N;;;;; 1981;NEW TAI LUE LETTER LOW QA;Lo;0;L;;;;;N;;;;; 1982;NEW TAI LUE LETTER HIGH KA;Lo;0;L;;;;;N;;;;; 1983;NEW TAI LUE LETTER HIGH XA;Lo;0;L;;;;;N;;;;; 1984;NEW TAI LUE LETTER HIGH NGA;Lo;0;L;;;;;N;;;;; 1985;NEW TAI LUE LETTER LOW KA;Lo;0;L;;;;;N;;;;; 1986;NEW TAI LUE LETTER LOW XA;Lo;0;L;;;;;N;;;;; 1987;NEW TAI LUE LETTER LOW NGA;Lo;0;L;;;;;N;;;;; 1988;NEW TAI LUE LETTER HIGH TSA;Lo;0;L;;;;;N;;;;; 1989;NEW TAI LUE LETTER HIGH SA;Lo;0;L;;;;;N;;;;; 198A;NEW TAI LUE LETTER HIGH YA;Lo;0;L;;;;;N;;;;; 198B;NEW TAI LUE LETTER LOW TSA;Lo;0;L;;;;;N;;;;; 198C;NEW TAI LUE LETTER LOW SA;Lo;0;L;;;;;N;;;;; 198D;NEW TAI LUE LETTER LOW YA;Lo;0;L;;;;;N;;;;; 198E;NEW TAI LUE LETTER HIGH TA;Lo;0;L;;;;;N;;;;; 198F;NEW TAI LUE LETTER HIGH THA;Lo;0;L;;;;;N;;;;; 1990;NEW TAI LUE LETTER HIGH NA;Lo;0;L;;;;;N;;;;; 1991;NEW TAI LUE LETTER LOW TA;Lo;0;L;;;;;N;;;;; 1992;NEW TAI LUE LETTER LOW THA;Lo;0;L;;;;;N;;;;; 1993;NEW TAI LUE LETTER LOW NA;Lo;0;L;;;;;N;;;;; 1994;NEW TAI LUE LETTER HIGH PA;Lo;0;L;;;;;N;;;;; 1995;NEW TAI LUE LETTER HIGH PHA;Lo;0;L;;;;;N;;;;; 1996;NEW TAI LUE LETTER HIGH MA;Lo;0;L;;;;;N;;;;; 1997;NEW TAI LUE LETTER LOW PA;Lo;0;L;;;;;N;;;;; 1998;NEW TAI LUE LETTER LOW PHA;Lo;0;L;;;;;N;;;;; 1999;NEW TAI LUE LETTER LOW MA;Lo;0;L;;;;;N;;;;; 199A;NEW TAI LUE LETTER HIGH FA;Lo;0;L;;;;;N;;;;; 199B;NEW TAI LUE LETTER HIGH VA;Lo;0;L;;;;;N;;;;; 199C;NEW TAI LUE LETTER HIGH LA;Lo;0;L;;;;;N;;;;; 199D;NEW TAI LUE LETTER LOW FA;Lo;0;L;;;;;N;;;;; 199E;NEW TAI LUE LETTER LOW VA;Lo;0;L;;;;;N;;;;; 199F;NEW TAI LUE LETTER LOW LA;Lo;0;L;;;;;N;;;;; 19A0;NEW TAI LUE LETTER HIGH HA;Lo;0;L;;;;;N;;;;; 19A1;NEW TAI LUE LETTER HIGH DA;Lo;0;L;;;;;N;;;;; 19A2;NEW TAI LUE LETTER HIGH BA;Lo;0;L;;;;;N;;;;; 19A3;NEW TAI LUE LETTER LOW HA;Lo;0;L;;;;;N;;;;; 19A4;NEW TAI LUE LETTER LOW DA;Lo;0;L;;;;;N;;;;; 19A5;NEW TAI LUE LETTER LOW BA;Lo;0;L;;;;;N;;;;; 19A6;NEW TAI LUE LETTER HIGH KVA;Lo;0;L;;;;;N;;;;; 19A7;NEW TAI LUE LETTER HIGH XVA;Lo;0;L;;;;;N;;;;; 19A8;NEW TAI LUE LETTER LOW KVA;Lo;0;L;;;;;N;;;;; 19A9;NEW TAI LUE LETTER LOW XVA;Lo;0;L;;;;;N;;;;; 19AA;NEW TAI LUE LETTER HIGH SUA;Lo;0;L;;;;;N;;;;; 19AB;NEW TAI LUE LETTER LOW SUA;Lo;0;L;;;;;N;;;;; 19B0;NEW TAI LUE VOWEL SIGN VOWEL SHORTENER;Mc;0;L;;;;;N;;;;; 19B1;NEW TAI LUE VOWEL SIGN AA;Mc;0;L;;;;;N;;;;; 19B2;NEW TAI LUE VOWEL SIGN II;Mc;0;L;;;;;N;;;;; 19B3;NEW TAI LUE VOWEL SIGN U;Mc;0;L;;;;;N;;;;; 19B4;NEW TAI LUE VOWEL SIGN UU;Mc;0;L;;;;;N;;;;; 19B5;NEW TAI LUE VOWEL SIGN E;Mc;0;L;;;;;N;;;;; 19B6;NEW TAI LUE VOWEL SIGN AE;Mc;0;L;;;;;N;;;;; 19B7;NEW TAI LUE VOWEL SIGN O;Mc;0;L;;;;;N;;;;; 19B8;NEW TAI LUE VOWEL SIGN OA;Mc;0;L;;;;;N;;;;; 19B9;NEW TAI LUE VOWEL SIGN UE;Mc;0;L;;;;;N;;;;; 19BA;NEW TAI LUE VOWEL SIGN AY;Mc;0;L;;;;;N;;;;; 19BB;NEW TAI LUE VOWEL SIGN AAY;Mc;0;L;;;;;N;;;;; 19BC;NEW TAI LUE VOWEL SIGN UY;Mc;0;L;;;;;N;;;;; 19BD;NEW TAI LUE VOWEL SIGN OY;Mc;0;L;;;;;N;;;;; 19BE;NEW TAI LUE VOWEL SIGN OAY;Mc;0;L;;;;;N;;;;; 19BF;NEW TAI LUE VOWEL SIGN UEY;Mc;0;L;;;;;N;;;;; 19C0;NEW TAI LUE VOWEL SIGN IY;Mc;0;L;;;;;N;;;;; 19C1;NEW TAI LUE LETTER FINAL V;Lo;0;L;;;;;N;;;;; 19C2;NEW TAI LUE LETTER FINAL NG;Lo;0;L;;;;;N;;;;; 19C3;NEW TAI LUE LETTER FINAL N;Lo;0;L;;;;;N;;;;; 19C4;NEW TAI LUE LETTER FINAL M;Lo;0;L;;;;;N;;;;; 19C5;NEW TAI LUE LETTER FINAL K;Lo;0;L;;;;;N;;;;; 19C6;NEW TAI LUE LETTER FINAL D;Lo;0;L;;;;;N;;;;; 19C7;NEW TAI LUE LETTER FINAL B;Lo;0;L;;;;;N;;;;; 19C8;NEW TAI LUE TONE MARK-1;Mc;0;L;;;;;N;;;;; 19C9;NEW TAI LUE TONE MARK-2;Mc;0;L;;;;;N;;;;; 19D0;NEW TAI LUE DIGIT ZERO;Nd;0;L;;0;0;0;N;;;;; 19D1;NEW TAI LUE DIGIT ONE;Nd;0;L;;1;1;1;N;;;;; 19D2;NEW TAI LUE DIGIT TWO;Nd;0;L;;2;2;2;N;;;;; 19D3;NEW TAI LUE DIGIT THREE;Nd;0;L;;3;3;3;N;;;;; 19D4;NEW TAI LUE DIGIT FOUR;Nd;0;L;;4;4;4;N;;;;; 19D5;NEW TAI LUE DIGIT FIVE;Nd;0;L;;5;5;5;N;;;;; 19D6;NEW TAI LUE DIGIT SIX;Nd;0;L;;6;6;6;N;;;;; 19D7;NEW TAI LUE DIGIT SEVEN;Nd;0;L;;7;7;7;N;;;;; 19D8;NEW TAI LUE DIGIT EIGHT;Nd;0;L;;8;8;8;N;;;;; 19D9;NEW TAI LUE DIGIT NINE;Nd;0;L;;9;9;9;N;;;;; 19DA;NEW TAI LUE THAM DIGIT ONE;No;0;L;;;1;1;N;;;;; 19DE;NEW TAI LUE SIGN LAE;So;0;ON;;;;;N;;;;; 19DF;NEW TAI LUE SIGN LAEV;So;0;ON;;;;;N;;;;; 19E0;KHMER SYMBOL PATHAMASAT;So;0;ON;;;;;N;;;;; 19E1;KHMER SYMBOL MUOY KOET;So;0;ON;;;;;N;;;;; 19E2;KHMER SYMBOL PII KOET;So;0;ON;;;;;N;;;;; 19E3;KHMER SYMBOL BEI KOET;So;0;ON;;;;;N;;;;; 19E4;KHMER SYMBOL BUON KOET;So;0;ON;;;;;N;;;;; 19E5;KHMER SYMBOL PRAM KOET;So;0;ON;;;;;N;;;;; 19E6;KHMER SYMBOL PRAM-MUOY KOET;So;0;ON;;;;;N;;;;; 19E7;KHMER SYMBOL PRAM-PII KOET;So;0;ON;;;;;N;;;;; 19E8;KHMER SYMBOL PRAM-BEI KOET;So;0;ON;;;;;N;;;;; 19E9;KHMER SYMBOL PRAM-BUON KOET;So;0;ON;;;;;N;;;;; 19EA;KHMER SYMBOL DAP KOET;So;0;ON;;;;;N;;;;; 19EB;KHMER SYMBOL DAP-MUOY KOET;So;0;ON;;;;;N;;;;; 19EC;KHMER SYMBOL DAP-PII KOET;So;0;ON;;;;;N;;;;; 19ED;KHMER SYMBOL DAP-BEI KOET;So;0;ON;;;;;N;;;;; 19EE;KHMER SYMBOL DAP-BUON KOET;So;0;ON;;;;;N;;;;; 19EF;KHMER SYMBOL DAP-PRAM KOET;So;0;ON;;;;;N;;;;; 19F0;KHMER SYMBOL TUTEYASAT;So;0;ON;;;;;N;;;;; 19F1;KHMER SYMBOL MUOY ROC;So;0;ON;;;;;N;;;;; 19F2;KHMER SYMBOL PII ROC;So;0;ON;;;;;N;;;;; 19F3;KHMER SYMBOL BEI ROC;So;0;ON;;;;;N;;;;; 19F4;KHMER SYMBOL BUON ROC;So;0;ON;;;;;N;;;;; 19F5;KHMER SYMBOL PRAM ROC;So;0;ON;;;;;N;;;;; 19F6;KHMER SYMBOL PRAM-MUOY ROC;So;0;ON;;;;;N;;;;; 19F7;KHMER SYMBOL PRAM-PII ROC;So;0;ON;;;;;N;;;;; 19F8;KHMER SYMBOL PRAM-BEI ROC;So;0;ON;;;;;N;;;;; 19F9;KHMER SYMBOL PRAM-BUON ROC;So;0;ON;;;;;N;;;;; 19FA;KHMER SYMBOL DAP ROC;So;0;ON;;;;;N;;;;; 19FB;KHMER SYMBOL DAP-MUOY ROC;So;0;ON;;;;;N;;;;; 19FC;KHMER SYMBOL DAP-PII ROC;So;0;ON;;;;;N;;;;; 19FD;KHMER SYMBOL DAP-BEI ROC;So;0;ON;;;;;N;;;;; 19FE;KHMER SYMBOL DAP-BUON ROC;So;0;ON;;;;;N;;;;; 19FF;KHMER SYMBOL DAP-PRAM ROC;So;0;ON;;;;;N;;;;; 1A00;BUGINESE LETTER KA;Lo;0;L;;;;;N;;;;; 1A01;BUGINESE LETTER GA;Lo;0;L;;;;;N;;;;; 1A02;BUGINESE LETTER NGA;Lo;0;L;;;;;N;;;;; 1A03;BUGINESE LETTER NGKA;Lo;0;L;;;;;N;;;;; 1A04;BUGINESE LETTER PA;Lo;0;L;;;;;N;;;;; 1A05;BUGINESE LETTER BA;Lo;0;L;;;;;N;;;;; 1A06;BUGINESE LETTER MA;Lo;0;L;;;;;N;;;;; 1A07;BUGINESE LETTER MPA;Lo;0;L;;;;;N;;;;; 1A08;BUGINESE LETTER TA;Lo;0;L;;;;;N;;;;; 1A09;BUGINESE LETTER DA;Lo;0;L;;;;;N;;;;; 1A0A;BUGINESE LETTER NA;Lo;0;L;;;;;N;;;;; 1A0B;BUGINESE LETTER NRA;Lo;0;L;;;;;N;;;;; 1A0C;BUGINESE LETTER CA;Lo;0;L;;;;;N;;;;; 1A0D;BUGINESE LETTER JA;Lo;0;L;;;;;N;;;;; 1A0E;BUGINESE LETTER NYA;Lo;0;L;;;;;N;;;;; 1A0F;BUGINESE LETTER NYCA;Lo;0;L;;;;;N;;;;; 1A10;BUGINESE LETTER YA;Lo;0;L;;;;;N;;;;; 1A11;BUGINESE LETTER RA;Lo;0;L;;;;;N;;;;; 1A12;BUGINESE LETTER LA;Lo;0;L;;;;;N;;;;; 1A13;BUGINESE LETTER VA;Lo;0;L;;;;;N;;;;; 1A14;BUGINESE LETTER SA;Lo;0;L;;;;;N;;;;; 1A15;BUGINESE LETTER A;Lo;0;L;;;;;N;;;;; 1A16;BUGINESE LETTER HA;Lo;0;L;;;;;N;;;;; 1A17;BUGINESE VOWEL SIGN I;Mn;230;NSM;;;;;N;;;;; 1A18;BUGINESE VOWEL SIGN U;Mn;220;NSM;;;;;N;;;;; 1A19;BUGINESE VOWEL SIGN E;Mc;0;L;;;;;N;;;;; 1A1A;BUGINESE VOWEL SIGN O;Mc;0;L;;;;;N;;;;; 1A1B;BUGINESE VOWEL SIGN AE;Mn;0;NSM;;;;;N;;;;; 1A1E;BUGINESE PALLAWA;Po;0;L;;;;;N;;;;; 1A1F;BUGINESE END OF SECTION;Po;0;L;;;;;N;;;;; 1A20;TAI THAM LETTER HIGH KA;Lo;0;L;;;;;N;;;;; 1A21;TAI THAM LETTER HIGH KHA;Lo;0;L;;;;;N;;;;; 1A22;TAI THAM LETTER HIGH KXA;Lo;0;L;;;;;N;;;;; 1A23;TAI THAM LETTER LOW KA;Lo;0;L;;;;;N;;;;; 1A24;TAI THAM LETTER LOW KXA;Lo;0;L;;;;;N;;;;; 1A25;TAI THAM LETTER LOW KHA;Lo;0;L;;;;;N;;;;; 1A26;TAI THAM LETTER NGA;Lo;0;L;;;;;N;;;;; 1A27;TAI THAM LETTER HIGH CA;Lo;0;L;;;;;N;;;;; 1A28;TAI THAM LETTER HIGH CHA;Lo;0;L;;;;;N;;;;; 1A29;TAI THAM LETTER LOW CA;Lo;0;L;;;;;N;;;;; 1A2A;TAI THAM LETTER LOW SA;Lo;0;L;;;;;N;;;;; 1A2B;TAI THAM LETTER LOW CHA;Lo;0;L;;;;;N;;;;; 1A2C;TAI THAM LETTER NYA;Lo;0;L;;;;;N;;;;; 1A2D;TAI THAM LETTER RATA;Lo;0;L;;;;;N;;;;; 1A2E;TAI THAM LETTER HIGH RATHA;Lo;0;L;;;;;N;;;;; 1A2F;TAI THAM LETTER DA;Lo;0;L;;;;;N;;;;; 1A30;TAI THAM LETTER LOW RATHA;Lo;0;L;;;;;N;;;;; 1A31;TAI THAM LETTER RANA;Lo;0;L;;;;;N;;;;; 1A32;TAI THAM LETTER HIGH TA;Lo;0;L;;;;;N;;;;; 1A33;TAI THAM LETTER HIGH THA;Lo;0;L;;;;;N;;;;; 1A34;TAI THAM LETTER LOW TA;Lo;0;L;;;;;N;;;;; 1A35;TAI THAM LETTER LOW THA;Lo;0;L;;;;;N;;;;; 1A36;TAI THAM LETTER NA;Lo;0;L;;;;;N;;;;; 1A37;TAI THAM LETTER BA;Lo;0;L;;;;;N;;;;; 1A38;TAI THAM LETTER HIGH PA;Lo;0;L;;;;;N;;;;; 1A39;TAI THAM LETTER HIGH PHA;Lo;0;L;;;;;N;;;;; 1A3A;TAI THAM LETTER HIGH FA;Lo;0;L;;;;;N;;;;; 1A3B;TAI THAM LETTER LOW PA;Lo;0;L;;;;;N;;;;; 1A3C;TAI THAM LETTER LOW FA;Lo;0;L;;;;;N;;;;; 1A3D;TAI THAM LETTER LOW PHA;Lo;0;L;;;;;N;;;;; 1A3E;TAI THAM LETTER MA;Lo;0;L;;;;;N;;;;; 1A3F;TAI THAM LETTER LOW YA;Lo;0;L;;;;;N;;;;; 1A40;TAI THAM LETTER HIGH YA;Lo;0;L;;;;;N;;;;; 1A41;TAI THAM LETTER RA;Lo;0;L;;;;;N;;;;; 1A42;TAI THAM LETTER RUE;Lo;0;L;;;;;N;;;;; 1A43;TAI THAM LETTER LA;Lo;0;L;;;;;N;;;;; 1A44;TAI THAM LETTER LUE;Lo;0;L;;;;;N;;;;; 1A45;TAI THAM LETTER WA;Lo;0;L;;;;;N;;;;; 1A46;TAI THAM LETTER HIGH SHA;Lo;0;L;;;;;N;;;;; 1A47;TAI THAM LETTER HIGH SSA;Lo;0;L;;;;;N;;;;; 1A48;TAI THAM LETTER HIGH SA;Lo;0;L;;;;;N;;;;; 1A49;TAI THAM LETTER HIGH HA;Lo;0;L;;;;;N;;;;; 1A4A;TAI THAM LETTER LLA;Lo;0;L;;;;;N;;;;; 1A4B;TAI THAM LETTER A;Lo;0;L;;;;;N;;;;; 1A4C;TAI THAM LETTER LOW HA;Lo;0;L;;;;;N;;;;; 1A4D;TAI THAM LETTER I;Lo;0;L;;;;;N;;;;; 1A4E;TAI THAM LETTER II;Lo;0;L;;;;;N;;;;; 1A4F;TAI THAM LETTER U;Lo;0;L;;;;;N;;;;; 1A50;TAI THAM LETTER UU;Lo;0;L;;;;;N;;;;; 1A51;TAI THAM LETTER EE;Lo;0;L;;;;;N;;;;; 1A52;TAI THAM LETTER OO;Lo;0;L;;;;;N;;;;; 1A53;TAI THAM LETTER LAE;Lo;0;L;;;;;N;;;;; 1A54;TAI THAM LETTER GREAT SA;Lo;0;L;;;;;N;;;;; 1A55;TAI THAM CONSONANT SIGN MEDIAL RA;Mc;0;L;;;;;N;;;;; 1A56;TAI THAM CONSONANT SIGN MEDIAL LA;Mn;0;NSM;;;;;N;;;;; 1A57;TAI THAM CONSONANT SIGN LA TANG LAI;Mc;0;L;;;;;N;;;;; 1A58;TAI THAM SIGN MAI KANG LAI;Mn;0;NSM;;;;;N;;;;; 1A59;TAI THAM CONSONANT SIGN FINAL NGA;Mn;0;NSM;;;;;N;;;;; 1A5A;TAI THAM CONSONANT SIGN LOW PA;Mn;0;NSM;;;;;N;;;;; 1A5B;TAI THAM CONSONANT SIGN HIGH RATHA OR LOW PA;Mn;0;NSM;;;;;N;;;;; 1A5C;TAI THAM CONSONANT SIGN MA;Mn;0;NSM;;;;;N;;;;; 1A5D;TAI THAM CONSONANT SIGN BA;Mn;0;NSM;;;;;N;;;;; 1A5E;TAI THAM CONSONANT SIGN SA;Mn;0;NSM;;;;;N;;;;; 1A60;TAI THAM SIGN SAKOT;Mn;9;NSM;;;;;N;;;;; 1A61;TAI THAM VOWEL SIGN A;Mc;0;L;;;;;N;;;;; 1A62;TAI THAM VOWEL SIGN MAI SAT;Mn;0;NSM;;;;;N;;;;; 1A63;TAI THAM VOWEL SIGN AA;Mc;0;L;;;;;N;;;;; 1A64;TAI THAM VOWEL SIGN TALL AA;Mc;0;L;;;;;N;;;;; 1A65;TAI THAM VOWEL SIGN I;Mn;0;NSM;;;;;N;;;;; 1A66;TAI THAM VOWEL SIGN II;Mn;0;NSM;;;;;N;;;;; 1A67;TAI THAM VOWEL SIGN UE;Mn;0;NSM;;;;;N;;;;; 1A68;TAI THAM VOWEL SIGN UUE;Mn;0;NSM;;;;;N;;;;; 1A69;TAI THAM VOWEL SIGN U;Mn;0;NSM;;;;;N;;;;; 1A6A;TAI THAM VOWEL SIGN UU;Mn;0;NSM;;;;;N;;;;; 1A6B;TAI THAM VOWEL SIGN O;Mn;0;NSM;;;;;N;;;;; 1A6C;TAI THAM VOWEL SIGN OA BELOW;Mn;0;NSM;;;;;N;;;;; 1A6D;TAI THAM VOWEL SIGN OY;Mc;0;L;;;;;N;;;;; 1A6E;TAI THAM VOWEL SIGN E;Mc;0;L;;;;;N;;;;; 1A6F;TAI THAM VOWEL SIGN AE;Mc;0;L;;;;;N;;;;; 1A70;TAI THAM VOWEL SIGN OO;Mc;0;L;;;;;N;;;;; 1A71;TAI THAM VOWEL SIGN AI;Mc;0;L;;;;;N;;;;; 1A72;TAI THAM VOWEL SIGN THAM AI;Mc;0;L;;;;;N;;;;; 1A73;TAI THAM VOWEL SIGN OA ABOVE;Mn;0;NSM;;;;;N;;;;; 1A74;TAI THAM SIGN MAI KANG;Mn;0;NSM;;;;;N;;;;; 1A75;TAI THAM SIGN TONE-1;Mn;230;NSM;;;;;N;;;;; 1A76;TAI THAM SIGN TONE-2;Mn;230;NSM;;;;;N;;;;; 1A77;TAI THAM SIGN KHUEN TONE-3;Mn;230;NSM;;;;;N;;;;; 1A78;TAI THAM SIGN KHUEN TONE-4;Mn;230;NSM;;;;;N;;;;; 1A79;TAI THAM SIGN KHUEN TONE-5;Mn;230;NSM;;;;;N;;;;; 1A7A;TAI THAM SIGN RA HAAM;Mn;230;NSM;;;;;N;;;;; 1A7B;TAI THAM SIGN MAI SAM;Mn;230;NSM;;;;;N;;;;; 1A7C;TAI THAM SIGN KHUEN-LUE KARAN;Mn;230;NSM;;;;;N;;;;; 1A7F;TAI THAM COMBINING CRYPTOGRAMMIC DOT;Mn;220;NSM;;;;;N;;;;; 1A80;TAI THAM HORA DIGIT ZERO;Nd;0;L;;0;0;0;N;;;;; 1A81;TAI THAM HORA DIGIT ONE;Nd;0;L;;1;1;1;N;;;;; 1A82;TAI THAM HORA DIGIT TWO;Nd;0;L;;2;2;2;N;;;;; 1A83;TAI THAM HORA DIGIT THREE;Nd;0;L;;3;3;3;N;;;;; 1A84;TAI THAM HORA DIGIT FOUR;Nd;0;L;;4;4;4;N;;;;; 1A85;TAI THAM HORA DIGIT FIVE;Nd;0;L;;5;5;5;N;;;;; 1A86;TAI THAM HORA DIGIT SIX;Nd;0;L;;6;6;6;N;;;;; 1A87;TAI THAM HORA DIGIT SEVEN;Nd;0;L;;7;7;7;N;;;;; 1A88;TAI THAM HORA DIGIT EIGHT;Nd;0;L;;8;8;8;N;;;;; 1A89;TAI THAM HORA DIGIT NINE;Nd;0;L;;9;9;9;N;;;;; 1A90;TAI THAM THAM DIGIT ZERO;Nd;0;L;;0;0;0;N;;;;; 1A91;TAI THAM THAM DIGIT ONE;Nd;0;L;;1;1;1;N;;;;; 1A92;TAI THAM THAM DIGIT TWO;Nd;0;L;;2;2;2;N;;;;; 1A93;TAI THAM THAM DIGIT THREE;Nd;0;L;;3;3;3;N;;;;; 1A94;TAI THAM THAM DIGIT FOUR;Nd;0;L;;4;4;4;N;;;;; 1A95;TAI THAM THAM DIGIT FIVE;Nd;0;L;;5;5;5;N;;;;; 1A96;TAI THAM THAM DIGIT SIX;Nd;0;L;;6;6;6;N;;;;; 1A97;TAI THAM THAM DIGIT SEVEN;Nd;0;L;;7;7;7;N;;;;; 1A98;TAI THAM THAM DIGIT EIGHT;Nd;0;L;;8;8;8;N;;;;; 1A99;TAI THAM THAM DIGIT NINE;Nd;0;L;;9;9;9;N;;;;; 1AA0;TAI THAM SIGN WIANG;Po;0;L;;;;;N;;;;; 1AA1;TAI THAM SIGN WIANGWAAK;Po;0;L;;;;;N;;;;; 1AA2;TAI THAM SIGN SAWAN;Po;0;L;;;;;N;;;;; 1AA3;TAI THAM SIGN KEOW;Po;0;L;;;;;N;;;;; 1AA4;TAI THAM SIGN HOY;Po;0;L;;;;;N;;;;; 1AA5;TAI THAM SIGN DOKMAI;Po;0;L;;;;;N;;;;; 1AA6;TAI THAM SIGN REVERSED ROTATED RANA;Po;0;L;;;;;N;;;;; 1AA7;TAI THAM SIGN MAI YAMOK;Lm;0;L;;;;;N;;;;; 1AA8;TAI THAM SIGN KAAN;Po;0;L;;;;;N;;;;; 1AA9;TAI THAM SIGN KAANKUU;Po;0;L;;;;;N;;;;; 1AAA;TAI THAM SIGN SATKAAN;Po;0;L;;;;;N;;;;; 1AAB;TAI THAM SIGN SATKAANKUU;Po;0;L;;;;;N;;;;; 1AAC;TAI THAM SIGN HANG;Po;0;L;;;;;N;;;;; 1AAD;TAI THAM SIGN CAANG;Po;0;L;;;;;N;;;;; 1AB0;COMBINING DOUBLED CIRCUMFLEX ACCENT;Mn;230;NSM;;;;;N;;;;; 1AB1;COMBINING DIAERESIS-RING;Mn;230;NSM;;;;;N;;;;; 1AB2;COMBINING INFINITY;Mn;230;NSM;;;;;N;;;;; 1AB3;COMBINING DOWNWARDS ARROW;Mn;230;NSM;;;;;N;;;;; 1AB4;COMBINING TRIPLE DOT;Mn;230;NSM;;;;;N;;;;; 1AB5;COMBINING X-X BELOW;Mn;220;NSM;;;;;N;;;;; 1AB6;COMBINING WIGGLY LINE BELOW;Mn;220;NSM;;;;;N;;;;; 1AB7;COMBINING OPEN MARK BELOW;Mn;220;NSM;;;;;N;;;;; 1AB8;COMBINING DOUBLE OPEN MARK BELOW;Mn;220;NSM;;;;;N;;;;; 1AB9;COMBINING LIGHT CENTRALIZATION STROKE BELOW;Mn;220;NSM;;;;;N;;;;; 1ABA;COMBINING STRONG CENTRALIZATION STROKE BELOW;Mn;220;NSM;;;;;N;;;;; 1ABB;COMBINING PARENTHESES ABOVE;Mn;230;NSM;;;;;N;;;;; 1ABC;COMBINING DOUBLE PARENTHESES ABOVE;Mn;230;NSM;;;;;N;;;;; 1ABD;COMBINING PARENTHESES BELOW;Mn;220;NSM;;;;;N;;;;; 1ABE;COMBINING PARENTHESES OVERLAY;Me;0;NSM;;;;;N;;;;; 1B00;BALINESE SIGN ULU RICEM;Mn;0;NSM;;;;;N;;;;; 1B01;BALINESE SIGN ULU CANDRA;Mn;0;NSM;;;;;N;;;;; 1B02;BALINESE SIGN CECEK;Mn;0;NSM;;;;;N;;;;; 1B03;BALINESE SIGN SURANG;Mn;0;NSM;;;;;N;;;;; 1B04;BALINESE SIGN BISAH;Mc;0;L;;;;;N;;;;; 1B05;BALINESE LETTER AKARA;Lo;0;L;;;;;N;;;;; 1B06;BALINESE LETTER AKARA TEDUNG;Lo;0;L;1B05 1B35;;;;N;;;;; 1B07;BALINESE LETTER IKARA;Lo;0;L;;;;;N;;;;; 1B08;BALINESE LETTER IKARA TEDUNG;Lo;0;L;1B07 1B35;;;;N;;;;; 1B09;BALINESE LETTER UKARA;Lo;0;L;;;;;N;;;;; 1B0A;BALINESE LETTER UKARA TEDUNG;Lo;0;L;1B09 1B35;;;;N;;;;; 1B0B;BALINESE LETTER RA REPA;Lo;0;L;;;;;N;;;;; 1B0C;BALINESE LETTER RA REPA TEDUNG;Lo;0;L;1B0B 1B35;;;;N;;;;; 1B0D;BALINESE LETTER LA LENGA;Lo;0;L;;;;;N;;;;; 1B0E;BALINESE LETTER LA LENGA TEDUNG;Lo;0;L;1B0D 1B35;;;;N;;;;; 1B0F;BALINESE LETTER EKARA;Lo;0;L;;;;;N;;;;; 1B10;BALINESE LETTER AIKARA;Lo;0;L;;;;;N;;;;; 1B11;BALINESE LETTER OKARA;Lo;0;L;;;;;N;;;;; 1B12;BALINESE LETTER OKARA TEDUNG;Lo;0;L;1B11 1B35;;;;N;;;;; 1B13;BALINESE LETTER KA;Lo;0;L;;;;;N;;;;; 1B14;BALINESE LETTER KA MAHAPRANA;Lo;0;L;;;;;N;;;;; 1B15;BALINESE LETTER GA;Lo;0;L;;;;;N;;;;; 1B16;BALINESE LETTER GA GORA;Lo;0;L;;;;;N;;;;; 1B17;BALINESE LETTER NGA;Lo;0;L;;;;;N;;;;; 1B18;BALINESE LETTER CA;Lo;0;L;;;;;N;;;;; 1B19;BALINESE LETTER CA LACA;Lo;0;L;;;;;N;;;;; 1B1A;BALINESE LETTER JA;Lo;0;L;;;;;N;;;;; 1B1B;BALINESE LETTER JA JERA;Lo;0;L;;;;;N;;;;; 1B1C;BALINESE LETTER NYA;Lo;0;L;;;;;N;;;;; 1B1D;BALINESE LETTER TA LATIK;Lo;0;L;;;;;N;;;;; 1B1E;BALINESE LETTER TA MURDA MAHAPRANA;Lo;0;L;;;;;N;;;;; 1B1F;BALINESE LETTER DA MURDA ALPAPRANA;Lo;0;L;;;;;N;;;;; 1B20;BALINESE LETTER DA MURDA MAHAPRANA;Lo;0;L;;;;;N;;;;; 1B21;BALINESE LETTER NA RAMBAT;Lo;0;L;;;;;N;;;;; 1B22;BALINESE LETTER TA;Lo;0;L;;;;;N;;;;; 1B23;BALINESE LETTER TA TAWA;Lo;0;L;;;;;N;;;;; 1B24;BALINESE LETTER DA;Lo;0;L;;;;;N;;;;; 1B25;BALINESE LETTER DA MADU;Lo;0;L;;;;;N;;;;; 1B26;BALINESE LETTER NA;Lo;0;L;;;;;N;;;;; 1B27;BALINESE LETTER PA;Lo;0;L;;;;;N;;;;; 1B28;BALINESE LETTER PA KAPAL;Lo;0;L;;;;;N;;;;; 1B29;BALINESE LETTER BA;Lo;0;L;;;;;N;;;;; 1B2A;BALINESE LETTER BA KEMBANG;Lo;0;L;;;;;N;;;;; 1B2B;BALINESE LETTER MA;Lo;0;L;;;;;N;;;;; 1B2C;BALINESE LETTER YA;Lo;0;L;;;;;N;;;;; 1B2D;BALINESE LETTER RA;Lo;0;L;;;;;N;;;;; 1B2E;BALINESE LETTER LA;Lo;0;L;;;;;N;;;;; 1B2F;BALINESE LETTER WA;Lo;0;L;;;;;N;;;;; 1B30;BALINESE LETTER SA SAGA;Lo;0;L;;;;;N;;;;; 1B31;BALINESE LETTER SA SAPA;Lo;0;L;;;;;N;;;;; 1B32;BALINESE LETTER SA;Lo;0;L;;;;;N;;;;; 1B33;BALINESE LETTER HA;Lo;0;L;;;;;N;;;;; 1B34;BALINESE SIGN REREKAN;Mn;7;NSM;;;;;N;;;;; 1B35;BALINESE VOWEL SIGN TEDUNG;Mc;0;L;;;;;N;;;;; 1B36;BALINESE VOWEL SIGN ULU;Mn;0;NSM;;;;;N;;;;; 1B37;BALINESE VOWEL SIGN ULU SARI;Mn;0;NSM;;;;;N;;;;; 1B38;BALINESE VOWEL SIGN SUKU;Mn;0;NSM;;;;;N;;;;; 1B39;BALINESE VOWEL SIGN SUKU ILUT;Mn;0;NSM;;;;;N;;;;; 1B3A;BALINESE VOWEL SIGN RA REPA;Mn;0;NSM;;;;;N;;;;; 1B3B;BALINESE VOWEL SIGN RA REPA TEDUNG;Mc;0;L;1B3A 1B35;;;;N;;;;; 1B3C;BALINESE VOWEL SIGN LA LENGA;Mn;0;NSM;;;;;N;;;;; 1B3D;BALINESE VOWEL SIGN LA LENGA TEDUNG;Mc;0;L;1B3C 1B35;;;;N;;;;; 1B3E;BALINESE VOWEL SIGN TALING;Mc;0;L;;;;;N;;;;; 1B3F;BALINESE VOWEL SIGN TALING REPA;Mc;0;L;;;;;N;;;;; 1B40;BALINESE VOWEL SIGN TALING TEDUNG;Mc;0;L;1B3E 1B35;;;;N;;;;; 1B41;BALINESE VOWEL SIGN TALING REPA TEDUNG;Mc;0;L;1B3F 1B35;;;;N;;;;; 1B42;BALINESE VOWEL SIGN PEPET;Mn;0;NSM;;;;;N;;;;; 1B43;BALINESE VOWEL SIGN PEPET TEDUNG;Mc;0;L;1B42 1B35;;;;N;;;;; 1B44;BALINESE ADEG ADEG;Mc;9;L;;;;;N;;;;; 1B45;BALINESE LETTER KAF SASAK;Lo;0;L;;;;;N;;;;; 1B46;BALINESE LETTER KHOT SASAK;Lo;0;L;;;;;N;;;;; 1B47;BALINESE LETTER TZIR SASAK;Lo;0;L;;;;;N;;;;; 1B48;BALINESE LETTER EF SASAK;Lo;0;L;;;;;N;;;;; 1B49;BALINESE LETTER VE SASAK;Lo;0;L;;;;;N;;;;; 1B4A;BALINESE LETTER ZAL SASAK;Lo;0;L;;;;;N;;;;; 1B4B;BALINESE LETTER ASYURA SASAK;Lo;0;L;;;;;N;;;;; 1B50;BALINESE DIGIT ZERO;Nd;0;L;;0;0;0;N;;;;; 1B51;BALINESE DIGIT ONE;Nd;0;L;;1;1;1;N;;;;; 1B52;BALINESE DIGIT TWO;Nd;0;L;;2;2;2;N;;;;; 1B53;BALINESE DIGIT THREE;Nd;0;L;;3;3;3;N;;;;; 1B54;BALINESE DIGIT FOUR;Nd;0;L;;4;4;4;N;;;;; 1B55;BALINESE DIGIT FIVE;Nd;0;L;;5;5;5;N;;;;; 1B56;BALINESE DIGIT SIX;Nd;0;L;;6;6;6;N;;;;; 1B57;BALINESE DIGIT SEVEN;Nd;0;L;;7;7;7;N;;;;; 1B58;BALINESE DIGIT EIGHT;Nd;0;L;;8;8;8;N;;;;; 1B59;BALINESE DIGIT NINE;Nd;0;L;;9;9;9;N;;;;; 1B5A;BALINESE PANTI;Po;0;L;;;;;N;;;;; 1B5B;BALINESE PAMADA;Po;0;L;;;;;N;;;;; 1B5C;BALINESE WINDU;Po;0;L;;;;;N;;;;; 1B5D;BALINESE CARIK PAMUNGKAH;Po;0;L;;;;;N;;;;; 1B5E;BALINESE CARIK SIKI;Po;0;L;;;;;N;;;;; 1B5F;BALINESE CARIK PAREREN;Po;0;L;;;;;N;;;;; 1B60;BALINESE PAMENENG;Po;0;L;;;;;N;;;;; 1B61;BALINESE MUSICAL SYMBOL DONG;So;0;L;;;;;N;;;;; 1B62;BALINESE MUSICAL SYMBOL DENG;So;0;L;;;;;N;;;;; 1B63;BALINESE MUSICAL SYMBOL DUNG;So;0;L;;;;;N;;;;; 1B64;BALINESE MUSICAL SYMBOL DANG;So;0;L;;;;;N;;;;; 1B65;BALINESE MUSICAL SYMBOL DANG SURANG;So;0;L;;;;;N;;;;; 1B66;BALINESE MUSICAL SYMBOL DING;So;0;L;;;;;N;;;;; 1B67;BALINESE MUSICAL SYMBOL DAENG;So;0;L;;;;;N;;;;; 1B68;BALINESE MUSICAL SYMBOL DEUNG;So;0;L;;;;;N;;;;; 1B69;BALINESE MUSICAL SYMBOL DAING;So;0;L;;;;;N;;;;; 1B6A;BALINESE MUSICAL SYMBOL DANG GEDE;So;0;L;;;;;N;;;;; 1B6B;BALINESE MUSICAL SYMBOL COMBINING TEGEH;Mn;230;NSM;;;;;N;;;;; 1B6C;BALINESE MUSICAL SYMBOL COMBINING ENDEP;Mn;220;NSM;;;;;N;;;;; 1B6D;BALINESE MUSICAL SYMBOL COMBINING KEMPUL;Mn;230;NSM;;;;;N;;;;; 1B6E;BALINESE MUSICAL SYMBOL COMBINING KEMPLI;Mn;230;NSM;;;;;N;;;;; 1B6F;BALINESE MUSICAL SYMBOL COMBINING JEGOGAN;Mn;230;NSM;;;;;N;;;;; 1B70;BALINESE MUSICAL SYMBOL COMBINING KEMPUL WITH JEGOGAN;Mn;230;NSM;;;;;N;;;;; 1B71;BALINESE MUSICAL SYMBOL COMBINING KEMPLI WITH JEGOGAN;Mn;230;NSM;;;;;N;;;;; 1B72;BALINESE MUSICAL SYMBOL COMBINING BENDE;Mn;230;NSM;;;;;N;;;;; 1B73;BALINESE MUSICAL SYMBOL COMBINING GONG;Mn;230;NSM;;;;;N;;;;; 1B74;BALINESE MUSICAL SYMBOL RIGHT-HAND OPEN DUG;So;0;L;;;;;N;;;;; 1B75;BALINESE MUSICAL SYMBOL RIGHT-HAND OPEN DAG;So;0;L;;;;;N;;;;; 1B76;BALINESE MUSICAL SYMBOL RIGHT-HAND CLOSED TUK;So;0;L;;;;;N;;;;; 1B77;BALINESE MUSICAL SYMBOL RIGHT-HAND CLOSED TAK;So;0;L;;;;;N;;;;; 1B78;BALINESE MUSICAL SYMBOL LEFT-HAND OPEN PANG;So;0;L;;;;;N;;;;; 1B79;BALINESE MUSICAL SYMBOL LEFT-HAND OPEN PUNG;So;0;L;;;;;N;;;;; 1B7A;BALINESE MUSICAL SYMBOL LEFT-HAND CLOSED PLAK;So;0;L;;;;;N;;;;; 1B7B;BALINESE MUSICAL SYMBOL LEFT-HAND CLOSED PLUK;So;0;L;;;;;N;;;;; 1B7C;BALINESE MUSICAL SYMBOL LEFT-HAND OPEN PING;So;0;L;;;;;N;;;;; 1B80;SUNDANESE SIGN PANYECEK;Mn;0;NSM;;;;;N;;;;; 1B81;SUNDANESE SIGN PANGLAYAR;Mn;0;NSM;;;;;N;;;;; 1B82;SUNDANESE SIGN PANGWISAD;Mc;0;L;;;;;N;;;;; 1B83;SUNDANESE LETTER A;Lo;0;L;;;;;N;;;;; 1B84;SUNDANESE LETTER I;Lo;0;L;;;;;N;;;;; 1B85;SUNDANESE LETTER U;Lo;0;L;;;;;N;;;;; 1B86;SUNDANESE LETTER AE;Lo;0;L;;;;;N;;;;; 1B87;SUNDANESE LETTER O;Lo;0;L;;;;;N;;;;; 1B88;SUNDANESE LETTER E;Lo;0;L;;;;;N;;;;; 1B89;SUNDANESE LETTER EU;Lo;0;L;;;;;N;;;;; 1B8A;SUNDANESE LETTER KA;Lo;0;L;;;;;N;;;;; 1B8B;SUNDANESE LETTER QA;Lo;0;L;;;;;N;;;;; 1B8C;SUNDANESE LETTER GA;Lo;0;L;;;;;N;;;;; 1B8D;SUNDANESE LETTER NGA;Lo;0;L;;;;;N;;;;; 1B8E;SUNDANESE LETTER CA;Lo;0;L;;;;;N;;;;; 1B8F;SUNDANESE LETTER JA;Lo;0;L;;;;;N;;;;; 1B90;SUNDANESE LETTER ZA;Lo;0;L;;;;;N;;;;; 1B91;SUNDANESE LETTER NYA;Lo;0;L;;;;;N;;;;; 1B92;SUNDANESE LETTER TA;Lo;0;L;;;;;N;;;;; 1B93;SUNDANESE LETTER DA;Lo;0;L;;;;;N;;;;; 1B94;SUNDANESE LETTER NA;Lo;0;L;;;;;N;;;;; 1B95;SUNDANESE LETTER PA;Lo;0;L;;;;;N;;;;; 1B96;SUNDANESE LETTER FA;Lo;0;L;;;;;N;;;;; 1B97;SUNDANESE LETTER VA;Lo;0;L;;;;;N;;;;; 1B98;SUNDANESE LETTER BA;Lo;0;L;;;;;N;;;;; 1B99;SUNDANESE LETTER MA;Lo;0;L;;;;;N;;;;; 1B9A;SUNDANESE LETTER YA;Lo;0;L;;;;;N;;;;; 1B9B;SUNDANESE LETTER RA;Lo;0;L;;;;;N;;;;; 1B9C;SUNDANESE LETTER LA;Lo;0;L;;;;;N;;;;; 1B9D;SUNDANESE LETTER WA;Lo;0;L;;;;;N;;;;; 1B9E;SUNDANESE LETTER SA;Lo;0;L;;;;;N;;;;; 1B9F;SUNDANESE LETTER XA;Lo;0;L;;;;;N;;;;; 1BA0;SUNDANESE LETTER HA;Lo;0;L;;;;;N;;;;; 1BA1;SUNDANESE CONSONANT SIGN PAMINGKAL;Mc;0;L;;;;;N;;;;; 1BA2;SUNDANESE CONSONANT SIGN PANYAKRA;Mn;0;NSM;;;;;N;;;;; 1BA3;SUNDANESE CONSONANT SIGN PANYIKU;Mn;0;NSM;;;;;N;;;;; 1BA4;SUNDANESE VOWEL SIGN PANGHULU;Mn;0;NSM;;;;;N;;;;; 1BA5;SUNDANESE VOWEL SIGN PANYUKU;Mn;0;NSM;;;;;N;;;;; 1BA6;SUNDANESE VOWEL SIGN PANAELAENG;Mc;0;L;;;;;N;;;;; 1BA7;SUNDANESE VOWEL SIGN PANOLONG;Mc;0;L;;;;;N;;;;; 1BA8;SUNDANESE VOWEL SIGN PAMEPET;Mn;0;NSM;;;;;N;;;;; 1BA9;SUNDANESE VOWEL SIGN PANEULEUNG;Mn;0;NSM;;;;;N;;;;; 1BAA;SUNDANESE SIGN PAMAAEH;Mc;9;L;;;;;N;;;;; 1BAB;SUNDANESE SIGN VIRAMA;Mn;9;NSM;;;;;N;;;;; 1BAC;SUNDANESE CONSONANT SIGN PASANGAN MA;Mn;0;NSM;;;;;N;;;;; 1BAD;SUNDANESE CONSONANT SIGN PASANGAN WA;Mn;0;NSM;;;;;N;;;;; 1BAE;SUNDANESE LETTER KHA;Lo;0;L;;;;;N;;;;; 1BAF;SUNDANESE LETTER SYA;Lo;0;L;;;;;N;;;;; 1BB0;SUNDANESE DIGIT ZERO;Nd;0;L;;0;0;0;N;;;;; 1BB1;SUNDANESE DIGIT ONE;Nd;0;L;;1;1;1;N;;;;; 1BB2;SUNDANESE DIGIT TWO;Nd;0;L;;2;2;2;N;;;;; 1BB3;SUNDANESE DIGIT THREE;Nd;0;L;;3;3;3;N;;;;; 1BB4;SUNDANESE DIGIT FOUR;Nd;0;L;;4;4;4;N;;;;; 1BB5;SUNDANESE DIGIT FIVE;Nd;0;L;;5;5;5;N;;;;; 1BB6;SUNDANESE DIGIT SIX;Nd;0;L;;6;6;6;N;;;;; 1BB7;SUNDANESE DIGIT SEVEN;Nd;0;L;;7;7;7;N;;;;; 1BB8;SUNDANESE DIGIT EIGHT;Nd;0;L;;8;8;8;N;;;;; 1BB9;SUNDANESE DIGIT NINE;Nd;0;L;;9;9;9;N;;;;; 1BBA;SUNDANESE AVAGRAHA;Lo;0;L;;;;;N;;;;; 1BBB;SUNDANESE LETTER REU;Lo;0;L;;;;;N;;;;; 1BBC;SUNDANESE LETTER LEU;Lo;0;L;;;;;N;;;;; 1BBD;SUNDANESE LETTER BHA;Lo;0;L;;;;;N;;;;; 1BBE;SUNDANESE LETTER FINAL K;Lo;0;L;;;;;N;;;;; 1BBF;SUNDANESE LETTER FINAL M;Lo;0;L;;;;;N;;;;; 1BC0;BATAK LETTER A;Lo;0;L;;;;;N;;;;; 1BC1;BATAK LETTER SIMALUNGUN A;Lo;0;L;;;;;N;;;;; 1BC2;BATAK LETTER HA;Lo;0;L;;;;;N;;;;; 1BC3;BATAK LETTER SIMALUNGUN HA;Lo;0;L;;;;;N;;;;; 1BC4;BATAK LETTER MANDAILING HA;Lo;0;L;;;;;N;;;;; 1BC5;BATAK LETTER BA;Lo;0;L;;;;;N;;;;; 1BC6;BATAK LETTER KARO BA;Lo;0;L;;;;;N;;;;; 1BC7;BATAK LETTER PA;Lo;0;L;;;;;N;;;;; 1BC8;BATAK LETTER SIMALUNGUN PA;Lo;0;L;;;;;N;;;;; 1BC9;BATAK LETTER NA;Lo;0;L;;;;;N;;;;; 1BCA;BATAK LETTER MANDAILING NA;Lo;0;L;;;;;N;;;;; 1BCB;BATAK LETTER WA;Lo;0;L;;;;;N;;;;; 1BCC;BATAK LETTER SIMALUNGUN WA;Lo;0;L;;;;;N;;;;; 1BCD;BATAK LETTER PAKPAK WA;Lo;0;L;;;;;N;;;;; 1BCE;BATAK LETTER GA;Lo;0;L;;;;;N;;;;; 1BCF;BATAK LETTER SIMALUNGUN GA;Lo;0;L;;;;;N;;;;; 1BD0;BATAK LETTER JA;Lo;0;L;;;;;N;;;;; 1BD1;BATAK LETTER DA;Lo;0;L;;;;;N;;;;; 1BD2;BATAK LETTER RA;Lo;0;L;;;;;N;;;;; 1BD3;BATAK LETTER SIMALUNGUN RA;Lo;0;L;;;;;N;;;;; 1BD4;BATAK LETTER MA;Lo;0;L;;;;;N;;;;; 1BD5;BATAK LETTER SIMALUNGUN MA;Lo;0;L;;;;;N;;;;; 1BD6;BATAK LETTER SOUTHERN TA;Lo;0;L;;;;;N;;;;; 1BD7;BATAK LETTER NORTHERN TA;Lo;0;L;;;;;N;;;;; 1BD8;BATAK LETTER SA;Lo;0;L;;;;;N;;;;; 1BD9;BATAK LETTER SIMALUNGUN SA;Lo;0;L;;;;;N;;;;; 1BDA;BATAK LETTER MANDAILING SA;Lo;0;L;;;;;N;;;;; 1BDB;BATAK LETTER YA;Lo;0;L;;;;;N;;;;; 1BDC;BATAK LETTER SIMALUNGUN YA;Lo;0;L;;;;;N;;;;; 1BDD;BATAK LETTER NGA;Lo;0;L;;;;;N;;;;; 1BDE;BATAK LETTER LA;Lo;0;L;;;;;N;;;;; 1BDF;BATAK LETTER SIMALUNGUN LA;Lo;0;L;;;;;N;;;;; 1BE0;BATAK LETTER NYA;Lo;0;L;;;;;N;;;;; 1BE1;BATAK LETTER CA;Lo;0;L;;;;;N;;;;; 1BE2;BATAK LETTER NDA;Lo;0;L;;;;;N;;;;; 1BE3;BATAK LETTER MBA;Lo;0;L;;;;;N;;;;; 1BE4;BATAK LETTER I;Lo;0;L;;;;;N;;;;; 1BE5;BATAK LETTER U;Lo;0;L;;;;;N;;;;; 1BE6;BATAK SIGN TOMPI;Mn;7;NSM;;;;;N;;;;; 1BE7;BATAK VOWEL SIGN E;Mc;0;L;;;;;N;;;;; 1BE8;BATAK VOWEL SIGN PAKPAK E;Mn;0;NSM;;;;;N;;;;; 1BE9;BATAK VOWEL SIGN EE;Mn;0;NSM;;;;;N;;;;; 1BEA;BATAK VOWEL SIGN I;Mc;0;L;;;;;N;;;;; 1BEB;BATAK VOWEL SIGN KARO I;Mc;0;L;;;;;N;;;;; 1BEC;BATAK VOWEL SIGN O;Mc;0;L;;;;;N;;;;; 1BED;BATAK VOWEL SIGN KARO O;Mn;0;NSM;;;;;N;;;;; 1BEE;BATAK VOWEL SIGN U;Mc;0;L;;;;;N;;;;; 1BEF;BATAK VOWEL SIGN U FOR SIMALUNGUN SA;Mn;0;NSM;;;;;N;;;;; 1BF0;BATAK CONSONANT SIGN NG;Mn;0;NSM;;;;;N;;;;; 1BF1;BATAK CONSONANT SIGN H;Mn;0;NSM;;;;;N;;;;; 1BF2;BATAK PANGOLAT;Mc;9;L;;;;;N;;;;; 1BF3;BATAK PANONGONAN;Mc;9;L;;;;;N;;;;; 1BFC;BATAK SYMBOL BINDU NA METEK;Po;0;L;;;;;N;;;;; 1BFD;BATAK SYMBOL BINDU PINARBORAS;Po;0;L;;;;;N;;;;; 1BFE;BATAK SYMBOL BINDU JUDUL;Po;0;L;;;;;N;;;;; 1BFF;BATAK SYMBOL BINDU PANGOLAT;Po;0;L;;;;;N;;;;; 1C00;LEPCHA LETTER KA;Lo;0;L;;;;;N;;;;; 1C01;LEPCHA LETTER KLA;Lo;0;L;;;;;N;;;;; 1C02;LEPCHA LETTER KHA;Lo;0;L;;;;;N;;;;; 1C03;LEPCHA LETTER GA;Lo;0;L;;;;;N;;;;; 1C04;LEPCHA LETTER GLA;Lo;0;L;;;;;N;;;;; 1C05;LEPCHA LETTER NGA;Lo;0;L;;;;;N;;;;; 1C06;LEPCHA LETTER CA;Lo;0;L;;;;;N;;;;; 1C07;LEPCHA LETTER CHA;Lo;0;L;;;;;N;;;;; 1C08;LEPCHA LETTER JA;Lo;0;L;;;;;N;;;;; 1C09;LEPCHA LETTER NYA;Lo;0;L;;;;;N;;;;; 1C0A;LEPCHA LETTER TA;Lo;0;L;;;;;N;;;;; 1C0B;LEPCHA LETTER THA;Lo;0;L;;;;;N;;;;; 1C0C;LEPCHA LETTER DA;Lo;0;L;;;;;N;;;;; 1C0D;LEPCHA LETTER NA;Lo;0;L;;;;;N;;;;; 1C0E;LEPCHA LETTER PA;Lo;0;L;;;;;N;;;;; 1C0F;LEPCHA LETTER PLA;Lo;0;L;;;;;N;;;;; 1C10;LEPCHA LETTER PHA;Lo;0;L;;;;;N;;;;; 1C11;LEPCHA LETTER FA;Lo;0;L;;;;;N;;;;; 1C12;LEPCHA LETTER FLA;Lo;0;L;;;;;N;;;;; 1C13;LEPCHA LETTER BA;Lo;0;L;;;;;N;;;;; 1C14;LEPCHA LETTER BLA;Lo;0;L;;;;;N;;;;; 1C15;LEPCHA LETTER MA;Lo;0;L;;;;;N;;;;; 1C16;LEPCHA LETTER MLA;Lo;0;L;;;;;N;;;;; 1C17;LEPCHA LETTER TSA;Lo;0;L;;;;;N;;;;; 1C18;LEPCHA LETTER TSHA;Lo;0;L;;;;;N;;;;; 1C19;LEPCHA LETTER DZA;Lo;0;L;;;;;N;;;;; 1C1A;LEPCHA LETTER YA;Lo;0;L;;;;;N;;;;; 1C1B;LEPCHA LETTER RA;Lo;0;L;;;;;N;;;;; 1C1C;LEPCHA LETTER LA;Lo;0;L;;;;;N;;;;; 1C1D;LEPCHA LETTER HA;Lo;0;L;;;;;N;;;;; 1C1E;LEPCHA LETTER HLA;Lo;0;L;;;;;N;;;;; 1C1F;LEPCHA LETTER VA;Lo;0;L;;;;;N;;;;; 1C20;LEPCHA LETTER SA;Lo;0;L;;;;;N;;;;; 1C21;LEPCHA LETTER SHA;Lo;0;L;;;;;N;;;;; 1C22;LEPCHA LETTER WA;Lo;0;L;;;;;N;;;;; 1C23;LEPCHA LETTER A;Lo;0;L;;;;;N;;;;; 1C24;LEPCHA SUBJOINED LETTER YA;Mc;0;L;;;;;N;;;;; 1C25;LEPCHA SUBJOINED LETTER RA;Mc;0;L;;;;;N;;;;; 1C26;LEPCHA VOWEL SIGN AA;Mc;0;L;;;;;N;;;;; 1C27;LEPCHA VOWEL SIGN I;Mc;0;L;;;;;N;;;;; 1C28;LEPCHA VOWEL SIGN O;Mc;0;L;;;;;N;;;;; 1C29;LEPCHA VOWEL SIGN OO;Mc;0;L;;;;;N;;;;; 1C2A;LEPCHA VOWEL SIGN U;Mc;0;L;;;;;N;;;;; 1C2B;LEPCHA VOWEL SIGN UU;Mc;0;L;;;;;N;;;;; 1C2C;LEPCHA VOWEL SIGN E;Mn;0;NSM;;;;;N;;;;; 1C2D;LEPCHA CONSONANT SIGN K;Mn;0;NSM;;;;;N;;;;; 1C2E;LEPCHA CONSONANT SIGN M;Mn;0;NSM;;;;;N;;;;; 1C2F;LEPCHA CONSONANT SIGN L;Mn;0;NSM;;;;;N;;;;; 1C30;LEPCHA CONSONANT SIGN N;Mn;0;NSM;;;;;N;;;;; 1C31;LEPCHA CONSONANT SIGN P;Mn;0;NSM;;;;;N;;;;; 1C32;LEPCHA CONSONANT SIGN R;Mn;0;NSM;;;;;N;;;;; 1C33;LEPCHA CONSONANT SIGN T;Mn;0;NSM;;;;;N;;;;; 1C34;LEPCHA CONSONANT SIGN NYIN-DO;Mc;0;L;;;;;N;;;;; 1C35;LEPCHA CONSONANT SIGN KANG;Mc;0;L;;;;;N;;;;; 1C36;LEPCHA SIGN RAN;Mn;0;NSM;;;;;N;;;;; 1C37;LEPCHA SIGN NUKTA;Mn;7;NSM;;;;;N;;;;; 1C3B;LEPCHA PUNCTUATION TA-ROL;Po;0;L;;;;;N;;;;; 1C3C;LEPCHA PUNCTUATION NYET THYOOM TA-ROL;Po;0;L;;;;;N;;;;; 1C3D;LEPCHA PUNCTUATION CER-WA;Po;0;L;;;;;N;;;;; 1C3E;LEPCHA PUNCTUATION TSHOOK CER-WA;Po;0;L;;;;;N;;;;; 1C3F;LEPCHA PUNCTUATION TSHOOK;Po;0;L;;;;;N;;;;; 1C40;LEPCHA DIGIT ZERO;Nd;0;L;;0;0;0;N;;;;; 1C41;LEPCHA DIGIT ONE;Nd;0;L;;1;1;1;N;;;;; 1C42;LEPCHA DIGIT TWO;Nd;0;L;;2;2;2;N;;;;; 1C43;LEPCHA DIGIT THREE;Nd;0;L;;3;3;3;N;;;;; 1C44;LEPCHA DIGIT FOUR;Nd;0;L;;4;4;4;N;;;;; 1C45;LEPCHA DIGIT FIVE;Nd;0;L;;5;5;5;N;;;;; 1C46;LEPCHA DIGIT SIX;Nd;0;L;;6;6;6;N;;;;; 1C47;LEPCHA DIGIT SEVEN;Nd;0;L;;7;7;7;N;;;;; 1C48;LEPCHA DIGIT EIGHT;Nd;0;L;;8;8;8;N;;;;; 1C49;LEPCHA DIGIT NINE;Nd;0;L;;9;9;9;N;;;;; 1C4D;LEPCHA LETTER TTA;Lo;0;L;;;;;N;;;;; 1C4E;LEPCHA LETTER TTHA;Lo;0;L;;;;;N;;;;; 1C4F;LEPCHA LETTER DDA;Lo;0;L;;;;;N;;;;; 1C50;OL CHIKI DIGIT ZERO;Nd;0;L;;0;0;0;N;;;;; 1C51;OL CHIKI DIGIT ONE;Nd;0;L;;1;1;1;N;;;;; 1C52;OL CHIKI DIGIT TWO;Nd;0;L;;2;2;2;N;;;;; 1C53;OL CHIKI DIGIT THREE;Nd;0;L;;3;3;3;N;;;;; 1C54;OL CHIKI DIGIT FOUR;Nd;0;L;;4;4;4;N;;;;; 1C55;OL CHIKI DIGIT FIVE;Nd;0;L;;5;5;5;N;;;;; 1C56;OL CHIKI DIGIT SIX;Nd;0;L;;6;6;6;N;;;;; 1C57;OL CHIKI DIGIT SEVEN;Nd;0;L;;7;7;7;N;;;;; 1C58;OL CHIKI DIGIT EIGHT;Nd;0;L;;8;8;8;N;;;;; 1C59;OL CHIKI DIGIT NINE;Nd;0;L;;9;9;9;N;;;;; 1C5A;OL CHIKI LETTER LA;Lo;0;L;;;;;N;;;;; 1C5B;OL CHIKI LETTER AT;Lo;0;L;;;;;N;;;;; 1C5C;OL CHIKI LETTER AG;Lo;0;L;;;;;N;;;;; 1C5D;OL CHIKI LETTER ANG;Lo;0;L;;;;;N;;;;; 1C5E;OL CHIKI LETTER AL;Lo;0;L;;;;;N;;;;; 1C5F;OL CHIKI LETTER LAA;Lo;0;L;;;;;N;;;;; 1C60;OL CHIKI LETTER AAK;Lo;0;L;;;;;N;;;;; 1C61;OL CHIKI LETTER AAJ;Lo;0;L;;;;;N;;;;; 1C62;OL CHIKI LETTER AAM;Lo;0;L;;;;;N;;;;; 1C63;OL CHIKI LETTER AAW;Lo;0;L;;;;;N;;;;; 1C64;OL CHIKI LETTER LI;Lo;0;L;;;;;N;;;;; 1C65;OL CHIKI LETTER IS;Lo;0;L;;;;;N;;;;; 1C66;OL CHIKI LETTER IH;Lo;0;L;;;;;N;;;;; 1C67;OL CHIKI LETTER INY;Lo;0;L;;;;;N;;;;; 1C68;OL CHIKI LETTER IR;Lo;0;L;;;;;N;;;;; 1C69;OL CHIKI LETTER LU;Lo;0;L;;;;;N;;;;; 1C6A;OL CHIKI LETTER UC;Lo;0;L;;;;;N;;;;; 1C6B;OL CHIKI LETTER UD;Lo;0;L;;;;;N;;;;; 1C6C;OL CHIKI LETTER UNN;Lo;0;L;;;;;N;;;;; 1C6D;OL CHIKI LETTER UY;Lo;0;L;;;;;N;;;;; 1C6E;OL CHIKI LETTER LE;Lo;0;L;;;;;N;;;;; 1C6F;OL CHIKI LETTER EP;Lo;0;L;;;;;N;;;;; 1C70;OL CHIKI LETTER EDD;Lo;0;L;;;;;N;;;;; 1C71;OL CHIKI LETTER EN;Lo;0;L;;;;;N;;;;; 1C72;OL CHIKI LETTER ERR;Lo;0;L;;;;;N;;;;; 1C73;OL CHIKI LETTER LO;Lo;0;L;;;;;N;;;;; 1C74;OL CHIKI LETTER OTT;Lo;0;L;;;;;N;;;;; 1C75;OL CHIKI LETTER OB;Lo;0;L;;;;;N;;;;; 1C76;OL CHIKI LETTER OV;Lo;0;L;;;;;N;;;;; 1C77;OL CHIKI LETTER OH;Lo;0;L;;;;;N;;;;; 1C78;OL CHIKI MU TTUDDAG;Lm;0;L;;;;;N;;;;; 1C79;OL CHIKI GAAHLAA TTUDDAAG;Lm;0;L;;;;;N;;;;; 1C7A;OL CHIKI MU-GAAHLAA TTUDDAAG;Lm;0;L;;;;;N;;;;; 1C7B;OL CHIKI RELAA;Lm;0;L;;;;;N;;;;; 1C7C;OL CHIKI PHAARKAA;Lm;0;L;;;;;N;;;;; 1C7D;OL CHIKI AHAD;Lm;0;L;;;;;N;;;;; 1C7E;OL CHIKI PUNCTUATION MUCAAD;Po;0;L;;;;;N;;;;; 1C7F;OL CHIKI PUNCTUATION DOUBLE MUCAAD;Po;0;L;;;;;N;;;;; 1CC0;SUNDANESE PUNCTUATION BINDU SURYA;Po;0;L;;;;;N;;;;; 1CC1;SUNDANESE PUNCTUATION BINDU PANGLONG;Po;0;L;;;;;N;;;;; 1CC2;SUNDANESE PUNCTUATION BINDU PURNAMA;Po;0;L;;;;;N;;;;; 1CC3;SUNDANESE PUNCTUATION BINDU CAKRA;Po;0;L;;;;;N;;;;; 1CC4;SUNDANESE PUNCTUATION BINDU LEU SATANGA;Po;0;L;;;;;N;;;;; 1CC5;SUNDANESE PUNCTUATION BINDU KA SATANGA;Po;0;L;;;;;N;;;;; 1CC6;SUNDANESE PUNCTUATION BINDU DA SATANGA;Po;0;L;;;;;N;;;;; 1CC7;SUNDANESE PUNCTUATION BINDU BA SATANGA;Po;0;L;;;;;N;;;;; 1CD0;VEDIC TONE KARSHANA;Mn;230;NSM;;;;;N;;;;; 1CD1;VEDIC TONE SHARA;Mn;230;NSM;;;;;N;;;;; 1CD2;VEDIC TONE PRENKHA;Mn;230;NSM;;;;;N;;;;; 1CD3;VEDIC SIGN NIHSHVASA;Po;0;L;;;;;N;;;;; 1CD4;VEDIC SIGN YAJURVEDIC MIDLINE SVARITA;Mn;1;NSM;;;;;N;;;;; 1CD5;VEDIC TONE YAJURVEDIC AGGRAVATED INDEPENDENT SVARITA;Mn;220;NSM;;;;;N;;;;; 1CD6;VEDIC TONE YAJURVEDIC INDEPENDENT SVARITA;Mn;220;NSM;;;;;N;;;;; 1CD7;VEDIC TONE YAJURVEDIC KATHAKA INDEPENDENT SVARITA;Mn;220;NSM;;;;;N;;;;; 1CD8;VEDIC TONE CANDRA BELOW;Mn;220;NSM;;;;;N;;;;; 1CD9;VEDIC TONE YAJURVEDIC KATHAKA INDEPENDENT SVARITA SCHROEDER;Mn;220;NSM;;;;;N;;;;; 1CDA;VEDIC TONE DOUBLE SVARITA;Mn;230;NSM;;;;;N;;;;; 1CDB;VEDIC TONE TRIPLE SVARITA;Mn;230;NSM;;;;;N;;;;; 1CDC;VEDIC TONE KATHAKA ANUDATTA;Mn;220;NSM;;;;;N;;;;; 1CDD;VEDIC TONE DOT BELOW;Mn;220;NSM;;;;;N;;;;; 1CDE;VEDIC TONE TWO DOTS BELOW;Mn;220;NSM;;;;;N;;;;; 1CDF;VEDIC TONE THREE DOTS BELOW;Mn;220;NSM;;;;;N;;;;; 1CE0;VEDIC TONE RIGVEDIC KASHMIRI INDEPENDENT SVARITA;Mn;230;NSM;;;;;N;;;;; 1CE1;VEDIC TONE ATHARVAVEDIC INDEPENDENT SVARITA;Mc;0;L;;;;;N;;;;; 1CE2;VEDIC SIGN VISARGA SVARITA;Mn;1;NSM;;;;;N;;;;; 1CE3;VEDIC SIGN VISARGA UDATTA;Mn;1;NSM;;;;;N;;;;; 1CE4;VEDIC SIGN REVERSED VISARGA UDATTA;Mn;1;NSM;;;;;N;;;;; 1CE5;VEDIC SIGN VISARGA ANUDATTA;Mn;1;NSM;;;;;N;;;;; 1CE6;VEDIC SIGN REVERSED VISARGA ANUDATTA;Mn;1;NSM;;;;;N;;;;; 1CE7;VEDIC SIGN VISARGA UDATTA WITH TAIL;Mn;1;NSM;;;;;N;;;;; 1CE8;VEDIC SIGN VISARGA ANUDATTA WITH TAIL;Mn;1;NSM;;;;;N;;;;; 1CE9;VEDIC SIGN ANUSVARA ANTARGOMUKHA;Lo;0;L;;;;;N;;;;; 1CEA;VEDIC SIGN ANUSVARA BAHIRGOMUKHA;Lo;0;L;;;;;N;;;;; 1CEB;VEDIC SIGN ANUSVARA VAMAGOMUKHA;Lo;0;L;;;;;N;;;;; 1CEC;VEDIC SIGN ANUSVARA VAMAGOMUKHA WITH TAIL;Lo;0;L;;;;;N;;;;; 1CED;VEDIC SIGN TIRYAK;Mn;220;NSM;;;;;N;;;;; 1CEE;VEDIC SIGN HEXIFORM LONG ANUSVARA;Lo;0;L;;;;;N;;;;; 1CEF;VEDIC SIGN LONG ANUSVARA;Lo;0;L;;;;;N;;;;; 1CF0;VEDIC SIGN RTHANG LONG ANUSVARA;Lo;0;L;;;;;N;;;;; 1CF1;VEDIC SIGN ANUSVARA UBHAYATO MUKHA;Lo;0;L;;;;;N;;;;; 1CF2;VEDIC SIGN ARDHAVISARGA;Mc;0;L;;;;;N;;;;; 1CF3;VEDIC SIGN ROTATED ARDHAVISARGA;Mc;0;L;;;;;N;;;;; 1CF4;VEDIC TONE CANDRA ABOVE;Mn;230;NSM;;;;;N;;;;; 1CF5;VEDIC SIGN JIHVAMULIYA;Lo;0;L;;;;;N;;;;; 1CF6;VEDIC SIGN UPADHMANIYA;Lo;0;L;;;;;N;;;;; 1CF8;VEDIC TONE RING ABOVE;Mn;230;NSM;;;;;N;;;;; 1CF9;VEDIC TONE DOUBLE RING ABOVE;Mn;230;NSM;;;;;N;;;;; 1D00;LATIN LETTER SMALL CAPITAL A;Ll;0;L;;;;;N;;;;; 1D01;LATIN LETTER SMALL CAPITAL AE;Ll;0;L;;;;;N;;;;; 1D02;LATIN SMALL LETTER TURNED AE;Ll;0;L;;;;;N;;;;; 1D03;LATIN LETTER SMALL CAPITAL BARRED B;Ll;0;L;;;;;N;;;;; 1D04;LATIN LETTER SMALL CAPITAL C;Ll;0;L;;;;;N;;;;; 1D05;LATIN LETTER SMALL CAPITAL D;Ll;0;L;;;;;N;;;;; 1D06;LATIN LETTER SMALL CAPITAL ETH;Ll;0;L;;;;;N;;;;; 1D07;LATIN LETTER SMALL CAPITAL E;Ll;0;L;;;;;N;;;;; 1D08;LATIN SMALL LETTER TURNED OPEN E;Ll;0;L;;;;;N;;;;; 1D09;LATIN SMALL LETTER TURNED I;Ll;0;L;;;;;N;;;;; 1D0A;LATIN LETTER SMALL CAPITAL J;Ll;0;L;;;;;N;;;;; 1D0B;LATIN LETTER SMALL CAPITAL K;Ll;0;L;;;;;N;;;;; 1D0C;LATIN LETTER SMALL CAPITAL L WITH STROKE;Ll;0;L;;;;;N;;;;; 1D0D;LATIN LETTER SMALL CAPITAL M;Ll;0;L;;;;;N;;;;; 1D0E;LATIN LETTER SMALL CAPITAL REVERSED N;Ll;0;L;;;;;N;;;;; 1D0F;LATIN LETTER SMALL CAPITAL O;Ll;0;L;;;;;N;;;;; 1D10;LATIN LETTER SMALL CAPITAL OPEN O;Ll;0;L;;;;;N;;;;; 1D11;LATIN SMALL LETTER SIDEWAYS O;Ll;0;L;;;;;N;;;;; 1D12;LATIN SMALL LETTER SIDEWAYS OPEN O;Ll;0;L;;;;;N;;;;; 1D13;LATIN SMALL LETTER SIDEWAYS O WITH STROKE;Ll;0;L;;;;;N;;;;; 1D14;LATIN SMALL LETTER TURNED OE;Ll;0;L;;;;;N;;;;; 1D15;LATIN LETTER SMALL CAPITAL OU;Ll;0;L;;;;;N;;;;; 1D16;LATIN SMALL LETTER TOP HALF O;Ll;0;L;;;;;N;;;;; 1D17;LATIN SMALL LETTER BOTTOM HALF O;Ll;0;L;;;;;N;;;;; 1D18;LATIN LETTER SMALL CAPITAL P;Ll;0;L;;;;;N;;;;; 1D19;LATIN LETTER SMALL CAPITAL REVERSED R;Ll;0;L;;;;;N;;;;; 1D1A;LATIN LETTER SMALL CAPITAL TURNED R;Ll;0;L;;;;;N;;;;; 1D1B;LATIN LETTER SMALL CAPITAL T;Ll;0;L;;;;;N;;;;; 1D1C;LATIN LETTER SMALL CAPITAL U;Ll;0;L;;;;;N;;;;; 1D1D;LATIN SMALL LETTER SIDEWAYS U;Ll;0;L;;;;;N;;;;; 1D1E;LATIN SMALL LETTER SIDEWAYS DIAERESIZED U;Ll;0;L;;;;;N;;;;; 1D1F;LATIN SMALL LETTER SIDEWAYS TURNED M;Ll;0;L;;;;;N;;;;; 1D20;LATIN LETTER SMALL CAPITAL V;Ll;0;L;;;;;N;;;;; 1D21;LATIN LETTER SMALL CAPITAL W;Ll;0;L;;;;;N;;;;; 1D22;LATIN LETTER SMALL CAPITAL Z;Ll;0;L;;;;;N;;;;; 1D23;LATIN LETTER SMALL CAPITAL EZH;Ll;0;L;;;;;N;;;;; 1D24;LATIN LETTER VOICED LARYNGEAL SPIRANT;Ll;0;L;;;;;N;;;;; 1D25;LATIN LETTER AIN;Ll;0;L;;;;;N;;;;; 1D26;GREEK LETTER SMALL CAPITAL GAMMA;Ll;0;L;;;;;N;;;;; 1D27;GREEK LETTER SMALL CAPITAL LAMDA;Ll;0;L;;;;;N;;;;; 1D28;GREEK LETTER SMALL CAPITAL PI;Ll;0;L;;;;;N;;;;; 1D29;GREEK LETTER SMALL CAPITAL RHO;Ll;0;L;;;;;N;;;;; 1D2A;GREEK LETTER SMALL CAPITAL PSI;Ll;0;L;;;;;N;;;;; 1D2B;CYRILLIC LETTER SMALL CAPITAL EL;Ll;0;L;;;;;N;;;;; 1D2C;MODIFIER LETTER CAPITAL A;Lm;0;L; 0041;;;;N;;;;; 1D2D;MODIFIER LETTER CAPITAL AE;Lm;0;L; 00C6;;;;N;;;;; 1D2E;MODIFIER LETTER CAPITAL B;Lm;0;L; 0042;;;;N;;;;; 1D2F;MODIFIER LETTER CAPITAL BARRED B;Lm;0;L;;;;;N;;;;; 1D30;MODIFIER LETTER CAPITAL D;Lm;0;L; 0044;;;;N;;;;; 1D31;MODIFIER LETTER CAPITAL E;Lm;0;L; 0045;;;;N;;;;; 1D32;MODIFIER LETTER CAPITAL REVERSED E;Lm;0;L; 018E;;;;N;;;;; 1D33;MODIFIER LETTER CAPITAL G;Lm;0;L; 0047;;;;N;;;;; 1D34;MODIFIER LETTER CAPITAL H;Lm;0;L; 0048;;;;N;;;;; 1D35;MODIFIER LETTER CAPITAL I;Lm;0;L; 0049;;;;N;;;;; 1D36;MODIFIER LETTER CAPITAL J;Lm;0;L; 004A;;;;N;;;;; 1D37;MODIFIER LETTER CAPITAL K;Lm;0;L; 004B;;;;N;;;;; 1D38;MODIFIER LETTER CAPITAL L;Lm;0;L; 004C;;;;N;;;;; 1D39;MODIFIER LETTER CAPITAL M;Lm;0;L; 004D;;;;N;;;;; 1D3A;MODIFIER LETTER CAPITAL N;Lm;0;L; 004E;;;;N;;;;; 1D3B;MODIFIER LETTER CAPITAL REVERSED N;Lm;0;L;;;;;N;;;;; 1D3C;MODIFIER LETTER CAPITAL O;Lm;0;L; 004F;;;;N;;;;; 1D3D;MODIFIER LETTER CAPITAL OU;Lm;0;L; 0222;;;;N;;;;; 1D3E;MODIFIER LETTER CAPITAL P;Lm;0;L; 0050;;;;N;;;;; 1D3F;MODIFIER LETTER CAPITAL R;Lm;0;L; 0052;;;;N;;;;; 1D40;MODIFIER LETTER CAPITAL T;Lm;0;L; 0054;;;;N;;;;; 1D41;MODIFIER LETTER CAPITAL U;Lm;0;L; 0055;;;;N;;;;; 1D42;MODIFIER LETTER CAPITAL W;Lm;0;L; 0057;;;;N;;;;; 1D43;MODIFIER LETTER SMALL A;Lm;0;L; 0061;;;;N;;;;; 1D44;MODIFIER LETTER SMALL TURNED A;Lm;0;L; 0250;;;;N;;;;; 1D45;MODIFIER LETTER SMALL ALPHA;Lm;0;L; 0251;;;;N;;;;; 1D46;MODIFIER LETTER SMALL TURNED AE;Lm;0;L; 1D02;;;;N;;;;; 1D47;MODIFIER LETTER SMALL B;Lm;0;L; 0062;;;;N;;;;; 1D48;MODIFIER LETTER SMALL D;Lm;0;L; 0064;;;;N;;;;; 1D49;MODIFIER LETTER SMALL E;Lm;0;L; 0065;;;;N;;;;; 1D4A;MODIFIER LETTER SMALL SCHWA;Lm;0;L; 0259;;;;N;;;;; 1D4B;MODIFIER LETTER SMALL OPEN E;Lm;0;L; 025B;;;;N;;;;; 1D4C;MODIFIER LETTER SMALL TURNED OPEN E;Lm;0;L; 025C;;;;N;;;;; 1D4D;MODIFIER LETTER SMALL G;Lm;0;L; 0067;;;;N;;;;; 1D4E;MODIFIER LETTER SMALL TURNED I;Lm;0;L;;;;;N;;;;; 1D4F;MODIFIER LETTER SMALL K;Lm;0;L; 006B;;;;N;;;;; 1D50;MODIFIER LETTER SMALL M;Lm;0;L; 006D;;;;N;;;;; 1D51;MODIFIER LETTER SMALL ENG;Lm;0;L; 014B;;;;N;;;;; 1D52;MODIFIER LETTER SMALL O;Lm;0;L; 006F;;;;N;;;;; 1D53;MODIFIER LETTER SMALL OPEN O;Lm;0;L; 0254;;;;N;;;;; 1D54;MODIFIER LETTER SMALL TOP HALF O;Lm;0;L; 1D16;;;;N;;;;; 1D55;MODIFIER LETTER SMALL BOTTOM HALF O;Lm;0;L; 1D17;;;;N;;;;; 1D56;MODIFIER LETTER SMALL P;Lm;0;L; 0070;;;;N;;;;; 1D57;MODIFIER LETTER SMALL T;Lm;0;L; 0074;;;;N;;;;; 1D58;MODIFIER LETTER SMALL U;Lm;0;L; 0075;;;;N;;;;; 1D59;MODIFIER LETTER SMALL SIDEWAYS U;Lm;0;L; 1D1D;;;;N;;;;; 1D5A;MODIFIER LETTER SMALL TURNED M;Lm;0;L; 026F;;;;N;;;;; 1D5B;MODIFIER LETTER SMALL V;Lm;0;L; 0076;;;;N;;;;; 1D5C;MODIFIER LETTER SMALL AIN;Lm;0;L; 1D25;;;;N;;;;; 1D5D;MODIFIER LETTER SMALL BETA;Lm;0;L; 03B2;;;;N;;;;; 1D5E;MODIFIER LETTER SMALL GREEK GAMMA;Lm;0;L; 03B3;;;;N;;;;; 1D5F;MODIFIER LETTER SMALL DELTA;Lm;0;L; 03B4;;;;N;;;;; 1D60;MODIFIER LETTER SMALL GREEK PHI;Lm;0;L; 03C6;;;;N;;;;; 1D61;MODIFIER LETTER SMALL CHI;Lm;0;L; 03C7;;;;N;;;;; 1D62;LATIN SUBSCRIPT SMALL LETTER I;Lm;0;L; 0069;;;;N;;;;; 1D63;LATIN SUBSCRIPT SMALL LETTER R;Lm;0;L; 0072;;;;N;;;;; 1D64;LATIN SUBSCRIPT SMALL LETTER U;Lm;0;L; 0075;;;;N;;;;; 1D65;LATIN SUBSCRIPT SMALL LETTER V;Lm;0;L; 0076;;;;N;;;;; 1D66;GREEK SUBSCRIPT SMALL LETTER BETA;Lm;0;L; 03B2;;;;N;;;;; 1D67;GREEK SUBSCRIPT SMALL LETTER GAMMA;Lm;0;L; 03B3;;;;N;;;;; 1D68;GREEK SUBSCRIPT SMALL LETTER RHO;Lm;0;L; 03C1;;;;N;;;;; 1D69;GREEK SUBSCRIPT SMALL LETTER PHI;Lm;0;L; 03C6;;;;N;;;;; 1D6A;GREEK SUBSCRIPT SMALL LETTER CHI;Lm;0;L; 03C7;;;;N;;;;; 1D6B;LATIN SMALL LETTER UE;Ll;0;L;;;;;N;;;;; 1D6C;LATIN SMALL LETTER B WITH MIDDLE TILDE;Ll;0;L;;;;;N;;;;; 1D6D;LATIN SMALL LETTER D WITH MIDDLE TILDE;Ll;0;L;;;;;N;;;;; 1D6E;LATIN SMALL LETTER F WITH MIDDLE TILDE;Ll;0;L;;;;;N;;;;; 1D6F;LATIN SMALL LETTER M WITH MIDDLE TILDE;Ll;0;L;;;;;N;;;;; 1D70;LATIN SMALL LETTER N WITH MIDDLE TILDE;Ll;0;L;;;;;N;;;;; 1D71;LATIN SMALL LETTER P WITH MIDDLE TILDE;Ll;0;L;;;;;N;;;;; 1D72;LATIN SMALL LETTER R WITH MIDDLE TILDE;Ll;0;L;;;;;N;;;;; 1D73;LATIN SMALL LETTER R WITH FISHHOOK AND MIDDLE TILDE;Ll;0;L;;;;;N;;;;; 1D74;LATIN SMALL LETTER S WITH MIDDLE TILDE;Ll;0;L;;;;;N;;;;; 1D75;LATIN SMALL LETTER T WITH MIDDLE TILDE;Ll;0;L;;;;;N;;;;; 1D76;LATIN SMALL LETTER Z WITH MIDDLE TILDE;Ll;0;L;;;;;N;;;;; 1D77;LATIN SMALL LETTER TURNED G;Ll;0;L;;;;;N;;;;; 1D78;MODIFIER LETTER CYRILLIC EN;Lm;0;L; 043D;;;;N;;;;; 1D79;LATIN SMALL LETTER INSULAR G;Ll;0;L;;;;;N;;;A77D;;A77D 1D7A;LATIN SMALL LETTER TH WITH STRIKETHROUGH;Ll;0;L;;;;;N;;;;; 1D7B;LATIN SMALL CAPITAL LETTER I WITH STROKE;Ll;0;L;;;;;N;;;;; 1D7C;LATIN SMALL LETTER IOTA WITH STROKE;Ll;0;L;;;;;N;;;;; 1D7D;LATIN SMALL LETTER P WITH STROKE;Ll;0;L;;;;;N;;;2C63;;2C63 1D7E;LATIN SMALL CAPITAL LETTER U WITH STROKE;Ll;0;L;;;;;N;;;;; 1D7F;LATIN SMALL LETTER UPSILON WITH STROKE;Ll;0;L;;;;;N;;;;; 1D80;LATIN SMALL LETTER B WITH PALATAL HOOK;Ll;0;L;;;;;N;;;;; 1D81;LATIN SMALL LETTER D WITH PALATAL HOOK;Ll;0;L;;;;;N;;;;; 1D82;LATIN SMALL LETTER F WITH PALATAL HOOK;Ll;0;L;;;;;N;;;;; 1D83;LATIN SMALL LETTER G WITH PALATAL HOOK;Ll;0;L;;;;;N;;;;; 1D84;LATIN SMALL LETTER K WITH PALATAL HOOK;Ll;0;L;;;;;N;;;;; 1D85;LATIN SMALL LETTER L WITH PALATAL HOOK;Ll;0;L;;;;;N;;;;; 1D86;LATIN SMALL LETTER M WITH PALATAL HOOK;Ll;0;L;;;;;N;;;;; 1D87;LATIN SMALL LETTER N WITH PALATAL HOOK;Ll;0;L;;;;;N;;;;; 1D88;LATIN SMALL LETTER P WITH PALATAL HOOK;Ll;0;L;;;;;N;;;;; 1D89;LATIN SMALL LETTER R WITH PALATAL HOOK;Ll;0;L;;;;;N;;;;; 1D8A;LATIN SMALL LETTER S WITH PALATAL HOOK;Ll;0;L;;;;;N;;;;; 1D8B;LATIN SMALL LETTER ESH WITH PALATAL HOOK;Ll;0;L;;;;;N;;;;; 1D8C;LATIN SMALL LETTER V WITH PALATAL HOOK;Ll;0;L;;;;;N;;;;; 1D8D;LATIN SMALL LETTER X WITH PALATAL HOOK;Ll;0;L;;;;;N;;;;; 1D8E;LATIN SMALL LETTER Z WITH PALATAL HOOK;Ll;0;L;;;;;N;;;;; 1D8F;LATIN SMALL LETTER A WITH RETROFLEX HOOK;Ll;0;L;;;;;N;;;;; 1D90;LATIN SMALL LETTER ALPHA WITH RETROFLEX HOOK;Ll;0;L;;;;;N;;;;; 1D91;LATIN SMALL LETTER D WITH HOOK AND TAIL;Ll;0;L;;;;;N;;;;; 1D92;LATIN SMALL LETTER E WITH RETROFLEX HOOK;Ll;0;L;;;;;N;;;;; 1D93;LATIN SMALL LETTER OPEN E WITH RETROFLEX HOOK;Ll;0;L;;;;;N;;;;; 1D94;LATIN SMALL LETTER REVERSED OPEN E WITH RETROFLEX HOOK;Ll;0;L;;;;;N;;;;; 1D95;LATIN SMALL LETTER SCHWA WITH RETROFLEX HOOK;Ll;0;L;;;;;N;;;;; 1D96;LATIN SMALL LETTER I WITH RETROFLEX HOOK;Ll;0;L;;;;;N;;;;; 1D97;LATIN SMALL LETTER OPEN O WITH RETROFLEX HOOK;Ll;0;L;;;;;N;;;;; 1D98;LATIN SMALL LETTER ESH WITH RETROFLEX HOOK;Ll;0;L;;;;;N;;;;; 1D99;LATIN SMALL LETTER U WITH RETROFLEX HOOK;Ll;0;L;;;;;N;;;;; 1D9A;LATIN SMALL LETTER EZH WITH RETROFLEX HOOK;Ll;0;L;;;;;N;;;;; 1D9B;MODIFIER LETTER SMALL TURNED ALPHA;Lm;0;L; 0252;;;;N;;;;; 1D9C;MODIFIER LETTER SMALL C;Lm;0;L; 0063;;;;N;;;;; 1D9D;MODIFIER LETTER SMALL C WITH CURL;Lm;0;L; 0255;;;;N;;;;; 1D9E;MODIFIER LETTER SMALL ETH;Lm;0;L; 00F0;;;;N;;;;; 1D9F;MODIFIER LETTER SMALL REVERSED OPEN E;Lm;0;L; 025C;;;;N;;;;; 1DA0;MODIFIER LETTER SMALL F;Lm;0;L; 0066;;;;N;;;;; 1DA1;MODIFIER LETTER SMALL DOTLESS J WITH STROKE;Lm;0;L; 025F;;;;N;;;;; 1DA2;MODIFIER LETTER SMALL SCRIPT G;Lm;0;L; 0261;;;;N;;;;; 1DA3;MODIFIER LETTER SMALL TURNED H;Lm;0;L; 0265;;;;N;;;;; 1DA4;MODIFIER LETTER SMALL I WITH STROKE;Lm;0;L; 0268;;;;N;;;;; 1DA5;MODIFIER LETTER SMALL IOTA;Lm;0;L; 0269;;;;N;;;;; 1DA6;MODIFIER LETTER SMALL CAPITAL I;Lm;0;L; 026A;;;;N;;;;; 1DA7;MODIFIER LETTER SMALL CAPITAL I WITH STROKE;Lm;0;L; 1D7B;;;;N;;;;; 1DA8;MODIFIER LETTER SMALL J WITH CROSSED-TAIL;Lm;0;L; 029D;;;;N;;;;; 1DA9;MODIFIER LETTER SMALL L WITH RETROFLEX HOOK;Lm;0;L; 026D;;;;N;;;;; 1DAA;MODIFIER LETTER SMALL L WITH PALATAL HOOK;Lm;0;L; 1D85;;;;N;;;;; 1DAB;MODIFIER LETTER SMALL CAPITAL L;Lm;0;L; 029F;;;;N;;;;; 1DAC;MODIFIER LETTER SMALL M WITH HOOK;Lm;0;L; 0271;;;;N;;;;; 1DAD;MODIFIER LETTER SMALL TURNED M WITH LONG LEG;Lm;0;L; 0270;;;;N;;;;; 1DAE;MODIFIER LETTER SMALL N WITH LEFT HOOK;Lm;0;L; 0272;;;;N;;;;; 1DAF;MODIFIER LETTER SMALL N WITH RETROFLEX HOOK;Lm;0;L; 0273;;;;N;;;;; 1DB0;MODIFIER LETTER SMALL CAPITAL N;Lm;0;L; 0274;;;;N;;;;; 1DB1;MODIFIER LETTER SMALL BARRED O;Lm;0;L; 0275;;;;N;;;;; 1DB2;MODIFIER LETTER SMALL PHI;Lm;0;L; 0278;;;;N;;;;; 1DB3;MODIFIER LETTER SMALL S WITH HOOK;Lm;0;L; 0282;;;;N;;;;; 1DB4;MODIFIER LETTER SMALL ESH;Lm;0;L; 0283;;;;N;;;;; 1DB5;MODIFIER LETTER SMALL T WITH PALATAL HOOK;Lm;0;L; 01AB;;;;N;;;;; 1DB6;MODIFIER LETTER SMALL U BAR;Lm;0;L; 0289;;;;N;;;;; 1DB7;MODIFIER LETTER SMALL UPSILON;Lm;0;L; 028A;;;;N;;;;; 1DB8;MODIFIER LETTER SMALL CAPITAL U;Lm;0;L; 1D1C;;;;N;;;;; 1DB9;MODIFIER LETTER SMALL V WITH HOOK;Lm;0;L; 028B;;;;N;;;;; 1DBA;MODIFIER LETTER SMALL TURNED V;Lm;0;L; 028C;;;;N;;;;; 1DBB;MODIFIER LETTER SMALL Z;Lm;0;L; 007A;;;;N;;;;; 1DBC;MODIFIER LETTER SMALL Z WITH RETROFLEX HOOK;Lm;0;L; 0290;;;;N;;;;; 1DBD;MODIFIER LETTER SMALL Z WITH CURL;Lm;0;L; 0291;;;;N;;;;; 1DBE;MODIFIER LETTER SMALL EZH;Lm;0;L; 0292;;;;N;;;;; 1DBF;MODIFIER LETTER SMALL THETA;Lm;0;L; 03B8;;;;N;;;;; 1DC0;COMBINING DOTTED GRAVE ACCENT;Mn;230;NSM;;;;;N;;;;; 1DC1;COMBINING DOTTED ACUTE ACCENT;Mn;230;NSM;;;;;N;;;;; 1DC2;COMBINING SNAKE BELOW;Mn;220;NSM;;;;;N;;;;; 1DC3;COMBINING SUSPENSION MARK;Mn;230;NSM;;;;;N;;;;; 1DC4;COMBINING MACRON-ACUTE;Mn;230;NSM;;;;;N;;;;; 1DC5;COMBINING GRAVE-MACRON;Mn;230;NSM;;;;;N;;;;; 1DC6;COMBINING MACRON-GRAVE;Mn;230;NSM;;;;;N;;;;; 1DC7;COMBINING ACUTE-MACRON;Mn;230;NSM;;;;;N;;;;; 1DC8;COMBINING GRAVE-ACUTE-GRAVE;Mn;230;NSM;;;;;N;;;;; 1DC9;COMBINING ACUTE-GRAVE-ACUTE;Mn;230;NSM;;;;;N;;;;; 1DCA;COMBINING LATIN SMALL LETTER R BELOW;Mn;220;NSM;;;;;N;;;;; 1DCB;COMBINING BREVE-MACRON;Mn;230;NSM;;;;;N;;;;; 1DCC;COMBINING MACRON-BREVE;Mn;230;NSM;;;;;N;;;;; 1DCD;COMBINING DOUBLE CIRCUMFLEX ABOVE;Mn;234;NSM;;;;;N;;;;; 1DCE;COMBINING OGONEK ABOVE;Mn;214;NSM;;;;;N;;;;; 1DCF;COMBINING ZIGZAG BELOW;Mn;220;NSM;;;;;N;;;;; 1DD0;COMBINING IS BELOW;Mn;202;NSM;;;;;N;;;;; 1DD1;COMBINING UR ABOVE;Mn;230;NSM;;;;;N;;;;; 1DD2;COMBINING US ABOVE;Mn;230;NSM;;;;;N;;;;; 1DD3;COMBINING LATIN SMALL LETTER FLATTENED OPEN A ABOVE;Mn;230;NSM;;;;;N;;;;; 1DD4;COMBINING LATIN SMALL LETTER AE;Mn;230;NSM;;;;;N;;;;; 1DD5;COMBINING LATIN SMALL LETTER AO;Mn;230;NSM;;;;;N;;;;; 1DD6;COMBINING LATIN SMALL LETTER AV;Mn;230;NSM;;;;;N;;;;; 1DD7;COMBINING LATIN SMALL LETTER C CEDILLA;Mn;230;NSM;;;;;N;;;;; 1DD8;COMBINING LATIN SMALL LETTER INSULAR D;Mn;230;NSM;;;;;N;;;;; 1DD9;COMBINING LATIN SMALL LETTER ETH;Mn;230;NSM;;;;;N;;;;; 1DDA;COMBINING LATIN SMALL LETTER G;Mn;230;NSM;;;;;N;;;;; 1DDB;COMBINING LATIN LETTER SMALL CAPITAL G;Mn;230;NSM;;;;;N;;;;; 1DDC;COMBINING LATIN SMALL LETTER K;Mn;230;NSM;;;;;N;;;;; 1DDD;COMBINING LATIN SMALL LETTER L;Mn;230;NSM;;;;;N;;;;; 1DDE;COMBINING LATIN LETTER SMALL CAPITAL L;Mn;230;NSM;;;;;N;;;;; 1DDF;COMBINING LATIN LETTER SMALL CAPITAL M;Mn;230;NSM;;;;;N;;;;; 1DE0;COMBINING LATIN SMALL LETTER N;Mn;230;NSM;;;;;N;;;;; 1DE1;COMBINING LATIN LETTER SMALL CAPITAL N;Mn;230;NSM;;;;;N;;;;; 1DE2;COMBINING LATIN LETTER SMALL CAPITAL R;Mn;230;NSM;;;;;N;;;;; 1DE3;COMBINING LATIN SMALL LETTER R ROTUNDA;Mn;230;NSM;;;;;N;;;;; 1DE4;COMBINING LATIN SMALL LETTER S;Mn;230;NSM;;;;;N;;;;; 1DE5;COMBINING LATIN SMALL LETTER LONG S;Mn;230;NSM;;;;;N;;;;; 1DE6;COMBINING LATIN SMALL LETTER Z;Mn;230;NSM;;;;;N;;;;; 1DE7;COMBINING LATIN SMALL LETTER ALPHA;Mn;230;NSM;;;;;N;;;;; 1DE8;COMBINING LATIN SMALL LETTER B;Mn;230;NSM;;;;;N;;;;; 1DE9;COMBINING LATIN SMALL LETTER BETA;Mn;230;NSM;;;;;N;;;;; 1DEA;COMBINING LATIN SMALL LETTER SCHWA;Mn;230;NSM;;;;;N;;;;; 1DEB;COMBINING LATIN SMALL LETTER F;Mn;230;NSM;;;;;N;;;;; 1DEC;COMBINING LATIN SMALL LETTER L WITH DOUBLE MIDDLE TILDE;Mn;230;NSM;;;;;N;;;;; 1DED;COMBINING LATIN SMALL LETTER O WITH LIGHT CENTRALIZATION STROKE;Mn;230;NSM;;;;;N;;;;; 1DEE;COMBINING LATIN SMALL LETTER P;Mn;230;NSM;;;;;N;;;;; 1DEF;COMBINING LATIN SMALL LETTER ESH;Mn;230;NSM;;;;;N;;;;; 1DF0;COMBINING LATIN SMALL LETTER U WITH LIGHT CENTRALIZATION STROKE;Mn;230;NSM;;;;;N;;;;; 1DF1;COMBINING LATIN SMALL LETTER W;Mn;230;NSM;;;;;N;;;;; 1DF2;COMBINING LATIN SMALL LETTER A WITH DIAERESIS;Mn;230;NSM;;;;;N;;;;; 1DF3;COMBINING LATIN SMALL LETTER O WITH DIAERESIS;Mn;230;NSM;;;;;N;;;;; 1DF4;COMBINING LATIN SMALL LETTER U WITH DIAERESIS;Mn;230;NSM;;;;;N;;;;; 1DF5;COMBINING UP TACK ABOVE;Mn;230;NSM;;;;;N;;;;; 1DFC;COMBINING DOUBLE INVERTED BREVE BELOW;Mn;233;NSM;;;;;N;;;;; 1DFD;COMBINING ALMOST EQUAL TO BELOW;Mn;220;NSM;;;;;N;;;;; 1DFE;COMBINING LEFT ARROWHEAD ABOVE;Mn;230;NSM;;;;;N;;;;; 1DFF;COMBINING RIGHT ARROWHEAD AND DOWN ARROWHEAD BELOW;Mn;220;NSM;;;;;N;;;;; 1E00;LATIN CAPITAL LETTER A WITH RING BELOW;Lu;0;L;0041 0325;;;;N;;;;1E01; 1E01;LATIN SMALL LETTER A WITH RING BELOW;Ll;0;L;0061 0325;;;;N;;;1E00;;1E00 1E02;LATIN CAPITAL LETTER B WITH DOT ABOVE;Lu;0;L;0042 0307;;;;N;;;;1E03; 1E03;LATIN SMALL LETTER B WITH DOT ABOVE;Ll;0;L;0062 0307;;;;N;;;1E02;;1E02 1E04;LATIN CAPITAL LETTER B WITH DOT BELOW;Lu;0;L;0042 0323;;;;N;;;;1E05; 1E05;LATIN SMALL LETTER B WITH DOT BELOW;Ll;0;L;0062 0323;;;;N;;;1E04;;1E04 1E06;LATIN CAPITAL LETTER B WITH LINE BELOW;Lu;0;L;0042 0331;;;;N;;;;1E07; 1E07;LATIN SMALL LETTER B WITH LINE BELOW;Ll;0;L;0062 0331;;;;N;;;1E06;;1E06 1E08;LATIN CAPITAL LETTER C WITH CEDILLA AND ACUTE;Lu;0;L;00C7 0301;;;;N;;;;1E09; 1E09;LATIN SMALL LETTER C WITH CEDILLA AND ACUTE;Ll;0;L;00E7 0301;;;;N;;;1E08;;1E08 1E0A;LATIN CAPITAL LETTER D WITH DOT ABOVE;Lu;0;L;0044 0307;;;;N;;;;1E0B; 1E0B;LATIN SMALL LETTER D WITH DOT ABOVE;Ll;0;L;0064 0307;;;;N;;;1E0A;;1E0A 1E0C;LATIN CAPITAL LETTER D WITH DOT BELOW;Lu;0;L;0044 0323;;;;N;;;;1E0D; 1E0D;LATIN SMALL LETTER D WITH DOT BELOW;Ll;0;L;0064 0323;;;;N;;;1E0C;;1E0C 1E0E;LATIN CAPITAL LETTER D WITH LINE BELOW;Lu;0;L;0044 0331;;;;N;;;;1E0F; 1E0F;LATIN SMALL LETTER D WITH LINE BELOW;Ll;0;L;0064 0331;;;;N;;;1E0E;;1E0E 1E10;LATIN CAPITAL LETTER D WITH CEDILLA;Lu;0;L;0044 0327;;;;N;;;;1E11; 1E11;LATIN SMALL LETTER D WITH CEDILLA;Ll;0;L;0064 0327;;;;N;;;1E10;;1E10 1E12;LATIN CAPITAL LETTER D WITH CIRCUMFLEX BELOW;Lu;0;L;0044 032D;;;;N;;;;1E13; 1E13;LATIN SMALL LETTER D WITH CIRCUMFLEX BELOW;Ll;0;L;0064 032D;;;;N;;;1E12;;1E12 1E14;LATIN CAPITAL LETTER E WITH MACRON AND GRAVE;Lu;0;L;0112 0300;;;;N;;;;1E15; 1E15;LATIN SMALL LETTER E WITH MACRON AND GRAVE;Ll;0;L;0113 0300;;;;N;;;1E14;;1E14 1E16;LATIN CAPITAL LETTER E WITH MACRON AND ACUTE;Lu;0;L;0112 0301;;;;N;;;;1E17; 1E17;LATIN SMALL LETTER E WITH MACRON AND ACUTE;Ll;0;L;0113 0301;;;;N;;;1E16;;1E16 1E18;LATIN CAPITAL LETTER E WITH CIRCUMFLEX BELOW;Lu;0;L;0045 032D;;;;N;;;;1E19; 1E19;LATIN SMALL LETTER E WITH CIRCUMFLEX BELOW;Ll;0;L;0065 032D;;;;N;;;1E18;;1E18 1E1A;LATIN CAPITAL LETTER E WITH TILDE BELOW;Lu;0;L;0045 0330;;;;N;;;;1E1B; 1E1B;LATIN SMALL LETTER E WITH TILDE BELOW;Ll;0;L;0065 0330;;;;N;;;1E1A;;1E1A 1E1C;LATIN CAPITAL LETTER E WITH CEDILLA AND BREVE;Lu;0;L;0228 0306;;;;N;;;;1E1D; 1E1D;LATIN SMALL LETTER E WITH CEDILLA AND BREVE;Ll;0;L;0229 0306;;;;N;;;1E1C;;1E1C 1E1E;LATIN CAPITAL LETTER F WITH DOT ABOVE;Lu;0;L;0046 0307;;;;N;;;;1E1F; 1E1F;LATIN SMALL LETTER F WITH DOT ABOVE;Ll;0;L;0066 0307;;;;N;;;1E1E;;1E1E 1E20;LATIN CAPITAL LETTER G WITH MACRON;Lu;0;L;0047 0304;;;;N;;;;1E21; 1E21;LATIN SMALL LETTER G WITH MACRON;Ll;0;L;0067 0304;;;;N;;;1E20;;1E20 1E22;LATIN CAPITAL LETTER H WITH DOT ABOVE;Lu;0;L;0048 0307;;;;N;;;;1E23; 1E23;LATIN SMALL LETTER H WITH DOT ABOVE;Ll;0;L;0068 0307;;;;N;;;1E22;;1E22 1E24;LATIN CAPITAL LETTER H WITH DOT BELOW;Lu;0;L;0048 0323;;;;N;;;;1E25; 1E25;LATIN SMALL LETTER H WITH DOT BELOW;Ll;0;L;0068 0323;;;;N;;;1E24;;1E24 1E26;LATIN CAPITAL LETTER H WITH DIAERESIS;Lu;0;L;0048 0308;;;;N;;;;1E27; 1E27;LATIN SMALL LETTER H WITH DIAERESIS;Ll;0;L;0068 0308;;;;N;;;1E26;;1E26 1E28;LATIN CAPITAL LETTER H WITH CEDILLA;Lu;0;L;0048 0327;;;;N;;;;1E29; 1E29;LATIN SMALL LETTER H WITH CEDILLA;Ll;0;L;0068 0327;;;;N;;;1E28;;1E28 1E2A;LATIN CAPITAL LETTER H WITH BREVE BELOW;Lu;0;L;0048 032E;;;;N;;;;1E2B; 1E2B;LATIN SMALL LETTER H WITH BREVE BELOW;Ll;0;L;0068 032E;;;;N;;;1E2A;;1E2A 1E2C;LATIN CAPITAL LETTER I WITH TILDE BELOW;Lu;0;L;0049 0330;;;;N;;;;1E2D; 1E2D;LATIN SMALL LETTER I WITH TILDE BELOW;Ll;0;L;0069 0330;;;;N;;;1E2C;;1E2C 1E2E;LATIN CAPITAL LETTER I WITH DIAERESIS AND ACUTE;Lu;0;L;00CF 0301;;;;N;;;;1E2F; 1E2F;LATIN SMALL LETTER I WITH DIAERESIS AND ACUTE;Ll;0;L;00EF 0301;;;;N;;;1E2E;;1E2E 1E30;LATIN CAPITAL LETTER K WITH ACUTE;Lu;0;L;004B 0301;;;;N;;;;1E31; 1E31;LATIN SMALL LETTER K WITH ACUTE;Ll;0;L;006B 0301;;;;N;;;1E30;;1E30 1E32;LATIN CAPITAL LETTER K WITH DOT BELOW;Lu;0;L;004B 0323;;;;N;;;;1E33; 1E33;LATIN SMALL LETTER K WITH DOT BELOW;Ll;0;L;006B 0323;;;;N;;;1E32;;1E32 1E34;LATIN CAPITAL LETTER K WITH LINE BELOW;Lu;0;L;004B 0331;;;;N;;;;1E35; 1E35;LATIN SMALL LETTER K WITH LINE BELOW;Ll;0;L;006B 0331;;;;N;;;1E34;;1E34 1E36;LATIN CAPITAL LETTER L WITH DOT BELOW;Lu;0;L;004C 0323;;;;N;;;;1E37; 1E37;LATIN SMALL LETTER L WITH DOT BELOW;Ll;0;L;006C 0323;;;;N;;;1E36;;1E36 1E38;LATIN CAPITAL LETTER L WITH DOT BELOW AND MACRON;Lu;0;L;1E36 0304;;;;N;;;;1E39; 1E39;LATIN SMALL LETTER L WITH DOT BELOW AND MACRON;Ll;0;L;1E37 0304;;;;N;;;1E38;;1E38 1E3A;LATIN CAPITAL LETTER L WITH LINE BELOW;Lu;0;L;004C 0331;;;;N;;;;1E3B; 1E3B;LATIN SMALL LETTER L WITH LINE BELOW;Ll;0;L;006C 0331;;;;N;;;1E3A;;1E3A 1E3C;LATIN CAPITAL LETTER L WITH CIRCUMFLEX BELOW;Lu;0;L;004C 032D;;;;N;;;;1E3D; 1E3D;LATIN SMALL LETTER L WITH CIRCUMFLEX BELOW;Ll;0;L;006C 032D;;;;N;;;1E3C;;1E3C 1E3E;LATIN CAPITAL LETTER M WITH ACUTE;Lu;0;L;004D 0301;;;;N;;;;1E3F; 1E3F;LATIN SMALL LETTER M WITH ACUTE;Ll;0;L;006D 0301;;;;N;;;1E3E;;1E3E 1E40;LATIN CAPITAL LETTER M WITH DOT ABOVE;Lu;0;L;004D 0307;;;;N;;;;1E41; 1E41;LATIN SMALL LETTER M WITH DOT ABOVE;Ll;0;L;006D 0307;;;;N;;;1E40;;1E40 1E42;LATIN CAPITAL LETTER M WITH DOT BELOW;Lu;0;L;004D 0323;;;;N;;;;1E43; 1E43;LATIN SMALL LETTER M WITH DOT BELOW;Ll;0;L;006D 0323;;;;N;;;1E42;;1E42 1E44;LATIN CAPITAL LETTER N WITH DOT ABOVE;Lu;0;L;004E 0307;;;;N;;;;1E45; 1E45;LATIN SMALL LETTER N WITH DOT ABOVE;Ll;0;L;006E 0307;;;;N;;;1E44;;1E44 1E46;LATIN CAPITAL LETTER N WITH DOT BELOW;Lu;0;L;004E 0323;;;;N;;;;1E47; 1E47;LATIN SMALL LETTER N WITH DOT BELOW;Ll;0;L;006E 0323;;;;N;;;1E46;;1E46 1E48;LATIN CAPITAL LETTER N WITH LINE BELOW;Lu;0;L;004E 0331;;;;N;;;;1E49; 1E49;LATIN SMALL LETTER N WITH LINE BELOW;Ll;0;L;006E 0331;;;;N;;;1E48;;1E48 1E4A;LATIN CAPITAL LETTER N WITH CIRCUMFLEX BELOW;Lu;0;L;004E 032D;;;;N;;;;1E4B; 1E4B;LATIN SMALL LETTER N WITH CIRCUMFLEX BELOW;Ll;0;L;006E 032D;;;;N;;;1E4A;;1E4A 1E4C;LATIN CAPITAL LETTER O WITH TILDE AND ACUTE;Lu;0;L;00D5 0301;;;;N;;;;1E4D; 1E4D;LATIN SMALL LETTER O WITH TILDE AND ACUTE;Ll;0;L;00F5 0301;;;;N;;;1E4C;;1E4C 1E4E;LATIN CAPITAL LETTER O WITH TILDE AND DIAERESIS;Lu;0;L;00D5 0308;;;;N;;;;1E4F; 1E4F;LATIN SMALL LETTER O WITH TILDE AND DIAERESIS;Ll;0;L;00F5 0308;;;;N;;;1E4E;;1E4E 1E50;LATIN CAPITAL LETTER O WITH MACRON AND GRAVE;Lu;0;L;014C 0300;;;;N;;;;1E51; 1E51;LATIN SMALL LETTER O WITH MACRON AND GRAVE;Ll;0;L;014D 0300;;;;N;;;1E50;;1E50 1E52;LATIN CAPITAL LETTER O WITH MACRON AND ACUTE;Lu;0;L;014C 0301;;;;N;;;;1E53; 1E53;LATIN SMALL LETTER O WITH MACRON AND ACUTE;Ll;0;L;014D 0301;;;;N;;;1E52;;1E52 1E54;LATIN CAPITAL LETTER P WITH ACUTE;Lu;0;L;0050 0301;;;;N;;;;1E55; 1E55;LATIN SMALL LETTER P WITH ACUTE;Ll;0;L;0070 0301;;;;N;;;1E54;;1E54 1E56;LATIN CAPITAL LETTER P WITH DOT ABOVE;Lu;0;L;0050 0307;;;;N;;;;1E57; 1E57;LATIN SMALL LETTER P WITH DOT ABOVE;Ll;0;L;0070 0307;;;;N;;;1E56;;1E56 1E58;LATIN CAPITAL LETTER R WITH DOT ABOVE;Lu;0;L;0052 0307;;;;N;;;;1E59; 1E59;LATIN SMALL LETTER R WITH DOT ABOVE;Ll;0;L;0072 0307;;;;N;;;1E58;;1E58 1E5A;LATIN CAPITAL LETTER R WITH DOT BELOW;Lu;0;L;0052 0323;;;;N;;;;1E5B; 1E5B;LATIN SMALL LETTER R WITH DOT BELOW;Ll;0;L;0072 0323;;;;N;;;1E5A;;1E5A 1E5C;LATIN CAPITAL LETTER R WITH DOT BELOW AND MACRON;Lu;0;L;1E5A 0304;;;;N;;;;1E5D; 1E5D;LATIN SMALL LETTER R WITH DOT BELOW AND MACRON;Ll;0;L;1E5B 0304;;;;N;;;1E5C;;1E5C 1E5E;LATIN CAPITAL LETTER R WITH LINE BELOW;Lu;0;L;0052 0331;;;;N;;;;1E5F; 1E5F;LATIN SMALL LETTER R WITH LINE BELOW;Ll;0;L;0072 0331;;;;N;;;1E5E;;1E5E 1E60;LATIN CAPITAL LETTER S WITH DOT ABOVE;Lu;0;L;0053 0307;;;;N;;;;1E61; 1E61;LATIN SMALL LETTER S WITH DOT ABOVE;Ll;0;L;0073 0307;;;;N;;;1E60;;1E60 1E62;LATIN CAPITAL LETTER S WITH DOT BELOW;Lu;0;L;0053 0323;;;;N;;;;1E63; 1E63;LATIN SMALL LETTER S WITH DOT BELOW;Ll;0;L;0073 0323;;;;N;;;1E62;;1E62 1E64;LATIN CAPITAL LETTER S WITH ACUTE AND DOT ABOVE;Lu;0;L;015A 0307;;;;N;;;;1E65; 1E65;LATIN SMALL LETTER S WITH ACUTE AND DOT ABOVE;Ll;0;L;015B 0307;;;;N;;;1E64;;1E64 1E66;LATIN CAPITAL LETTER S WITH CARON AND DOT ABOVE;Lu;0;L;0160 0307;;;;N;;;;1E67; 1E67;LATIN SMALL LETTER S WITH CARON AND DOT ABOVE;Ll;0;L;0161 0307;;;;N;;;1E66;;1E66 1E68;LATIN CAPITAL LETTER S WITH DOT BELOW AND DOT ABOVE;Lu;0;L;1E62 0307;;;;N;;;;1E69; 1E69;LATIN SMALL LETTER S WITH DOT BELOW AND DOT ABOVE;Ll;0;L;1E63 0307;;;;N;;;1E68;;1E68 1E6A;LATIN CAPITAL LETTER T WITH DOT ABOVE;Lu;0;L;0054 0307;;;;N;;;;1E6B; 1E6B;LATIN SMALL LETTER T WITH DOT ABOVE;Ll;0;L;0074 0307;;;;N;;;1E6A;;1E6A 1E6C;LATIN CAPITAL LETTER T WITH DOT BELOW;Lu;0;L;0054 0323;;;;N;;;;1E6D; 1E6D;LATIN SMALL LETTER T WITH DOT BELOW;Ll;0;L;0074 0323;;;;N;;;1E6C;;1E6C 1E6E;LATIN CAPITAL LETTER T WITH LINE BELOW;Lu;0;L;0054 0331;;;;N;;;;1E6F; 1E6F;LATIN SMALL LETTER T WITH LINE BELOW;Ll;0;L;0074 0331;;;;N;;;1E6E;;1E6E 1E70;LATIN CAPITAL LETTER T WITH CIRCUMFLEX BELOW;Lu;0;L;0054 032D;;;;N;;;;1E71; 1E71;LATIN SMALL LETTER T WITH CIRCUMFLEX BELOW;Ll;0;L;0074 032D;;;;N;;;1E70;;1E70 1E72;LATIN CAPITAL LETTER U WITH DIAERESIS BELOW;Lu;0;L;0055 0324;;;;N;;;;1E73; 1E73;LATIN SMALL LETTER U WITH DIAERESIS BELOW;Ll;0;L;0075 0324;;;;N;;;1E72;;1E72 1E74;LATIN CAPITAL LETTER U WITH TILDE BELOW;Lu;0;L;0055 0330;;;;N;;;;1E75; 1E75;LATIN SMALL LETTER U WITH TILDE BELOW;Ll;0;L;0075 0330;;;;N;;;1E74;;1E74 1E76;LATIN CAPITAL LETTER U WITH CIRCUMFLEX BELOW;Lu;0;L;0055 032D;;;;N;;;;1E77; 1E77;LATIN SMALL LETTER U WITH CIRCUMFLEX BELOW;Ll;0;L;0075 032D;;;;N;;;1E76;;1E76 1E78;LATIN CAPITAL LETTER U WITH TILDE AND ACUTE;Lu;0;L;0168 0301;;;;N;;;;1E79; 1E79;LATIN SMALL LETTER U WITH TILDE AND ACUTE;Ll;0;L;0169 0301;;;;N;;;1E78;;1E78 1E7A;LATIN CAPITAL LETTER U WITH MACRON AND DIAERESIS;Lu;0;L;016A 0308;;;;N;;;;1E7B; 1E7B;LATIN SMALL LETTER U WITH MACRON AND DIAERESIS;Ll;0;L;016B 0308;;;;N;;;1E7A;;1E7A 1E7C;LATIN CAPITAL LETTER V WITH TILDE;Lu;0;L;0056 0303;;;;N;;;;1E7D; 1E7D;LATIN SMALL LETTER V WITH TILDE;Ll;0;L;0076 0303;;;;N;;;1E7C;;1E7C 1E7E;LATIN CAPITAL LETTER V WITH DOT BELOW;Lu;0;L;0056 0323;;;;N;;;;1E7F; 1E7F;LATIN SMALL LETTER V WITH DOT BELOW;Ll;0;L;0076 0323;;;;N;;;1E7E;;1E7E 1E80;LATIN CAPITAL LETTER W WITH GRAVE;Lu;0;L;0057 0300;;;;N;;;;1E81; 1E81;LATIN SMALL LETTER W WITH GRAVE;Ll;0;L;0077 0300;;;;N;;;1E80;;1E80 1E82;LATIN CAPITAL LETTER W WITH ACUTE;Lu;0;L;0057 0301;;;;N;;;;1E83; 1E83;LATIN SMALL LETTER W WITH ACUTE;Ll;0;L;0077 0301;;;;N;;;1E82;;1E82 1E84;LATIN CAPITAL LETTER W WITH DIAERESIS;Lu;0;L;0057 0308;;;;N;;;;1E85; 1E85;LATIN SMALL LETTER W WITH DIAERESIS;Ll;0;L;0077 0308;;;;N;;;1E84;;1E84 1E86;LATIN CAPITAL LETTER W WITH DOT ABOVE;Lu;0;L;0057 0307;;;;N;;;;1E87; 1E87;LATIN SMALL LETTER W WITH DOT ABOVE;Ll;0;L;0077 0307;;;;N;;;1E86;;1E86 1E88;LATIN CAPITAL LETTER W WITH DOT BELOW;Lu;0;L;0057 0323;;;;N;;;;1E89; 1E89;LATIN SMALL LETTER W WITH DOT BELOW;Ll;0;L;0077 0323;;;;N;;;1E88;;1E88 1E8A;LATIN CAPITAL LETTER X WITH DOT ABOVE;Lu;0;L;0058 0307;;;;N;;;;1E8B; 1E8B;LATIN SMALL LETTER X WITH DOT ABOVE;Ll;0;L;0078 0307;;;;N;;;1E8A;;1E8A 1E8C;LATIN CAPITAL LETTER X WITH DIAERESIS;Lu;0;L;0058 0308;;;;N;;;;1E8D; 1E8D;LATIN SMALL LETTER X WITH DIAERESIS;Ll;0;L;0078 0308;;;;N;;;1E8C;;1E8C 1E8E;LATIN CAPITAL LETTER Y WITH DOT ABOVE;Lu;0;L;0059 0307;;;;N;;;;1E8F; 1E8F;LATIN SMALL LETTER Y WITH DOT ABOVE;Ll;0;L;0079 0307;;;;N;;;1E8E;;1E8E 1E90;LATIN CAPITAL LETTER Z WITH CIRCUMFLEX;Lu;0;L;005A 0302;;;;N;;;;1E91; 1E91;LATIN SMALL LETTER Z WITH CIRCUMFLEX;Ll;0;L;007A 0302;;;;N;;;1E90;;1E90 1E92;LATIN CAPITAL LETTER Z WITH DOT BELOW;Lu;0;L;005A 0323;;;;N;;;;1E93; 1E93;LATIN SMALL LETTER Z WITH DOT BELOW;Ll;0;L;007A 0323;;;;N;;;1E92;;1E92 1E94;LATIN CAPITAL LETTER Z WITH LINE BELOW;Lu;0;L;005A 0331;;;;N;;;;1E95; 1E95;LATIN SMALL LETTER Z WITH LINE BELOW;Ll;0;L;007A 0331;;;;N;;;1E94;;1E94 1E96;LATIN SMALL LETTER H WITH LINE BELOW;Ll;0;L;0068 0331;;;;N;;;;; 1E97;LATIN SMALL LETTER T WITH DIAERESIS;Ll;0;L;0074 0308;;;;N;;;;; 1E98;LATIN SMALL LETTER W WITH RING ABOVE;Ll;0;L;0077 030A;;;;N;;;;; 1E99;LATIN SMALL LETTER Y WITH RING ABOVE;Ll;0;L;0079 030A;;;;N;;;;; 1E9A;LATIN SMALL LETTER A WITH RIGHT HALF RING;Ll;0;L; 0061 02BE;;;;N;;;;; 1E9B;LATIN SMALL LETTER LONG S WITH DOT ABOVE;Ll;0;L;017F 0307;;;;N;;;1E60;;1E60 1E9C;LATIN SMALL LETTER LONG S WITH DIAGONAL STROKE;Ll;0;L;;;;;N;;;;; 1E9D;LATIN SMALL LETTER LONG S WITH HIGH STROKE;Ll;0;L;;;;;N;;;;; 1E9E;LATIN CAPITAL LETTER SHARP S;Lu;0;L;;;;;N;;;;00DF; 1E9F;LATIN SMALL LETTER DELTA;Ll;0;L;;;;;N;;;;; 1EA0;LATIN CAPITAL LETTER A WITH DOT BELOW;Lu;0;L;0041 0323;;;;N;;;;1EA1; 1EA1;LATIN SMALL LETTER A WITH DOT BELOW;Ll;0;L;0061 0323;;;;N;;;1EA0;;1EA0 1EA2;LATIN CAPITAL LETTER A WITH HOOK ABOVE;Lu;0;L;0041 0309;;;;N;;;;1EA3; 1EA3;LATIN SMALL LETTER A WITH HOOK ABOVE;Ll;0;L;0061 0309;;;;N;;;1EA2;;1EA2 1EA4;LATIN CAPITAL LETTER A WITH CIRCUMFLEX AND ACUTE;Lu;0;L;00C2 0301;;;;N;;;;1EA5; 1EA5;LATIN SMALL LETTER A WITH CIRCUMFLEX AND ACUTE;Ll;0;L;00E2 0301;;;;N;;;1EA4;;1EA4 1EA6;LATIN CAPITAL LETTER A WITH CIRCUMFLEX AND GRAVE;Lu;0;L;00C2 0300;;;;N;;;;1EA7; 1EA7;LATIN SMALL LETTER A WITH CIRCUMFLEX AND GRAVE;Ll;0;L;00E2 0300;;;;N;;;1EA6;;1EA6 1EA8;LATIN CAPITAL LETTER A WITH CIRCUMFLEX AND HOOK ABOVE;Lu;0;L;00C2 0309;;;;N;;;;1EA9; 1EA9;LATIN SMALL LETTER A WITH CIRCUMFLEX AND HOOK ABOVE;Ll;0;L;00E2 0309;;;;N;;;1EA8;;1EA8 1EAA;LATIN CAPITAL LETTER A WITH CIRCUMFLEX AND TILDE;Lu;0;L;00C2 0303;;;;N;;;;1EAB; 1EAB;LATIN SMALL LETTER A WITH CIRCUMFLEX AND TILDE;Ll;0;L;00E2 0303;;;;N;;;1EAA;;1EAA 1EAC;LATIN CAPITAL LETTER A WITH CIRCUMFLEX AND DOT BELOW;Lu;0;L;1EA0 0302;;;;N;;;;1EAD; 1EAD;LATIN SMALL LETTER A WITH CIRCUMFLEX AND DOT BELOW;Ll;0;L;1EA1 0302;;;;N;;;1EAC;;1EAC 1EAE;LATIN CAPITAL LETTER A WITH BREVE AND ACUTE;Lu;0;L;0102 0301;;;;N;;;;1EAF; 1EAF;LATIN SMALL LETTER A WITH BREVE AND ACUTE;Ll;0;L;0103 0301;;;;N;;;1EAE;;1EAE 1EB0;LATIN CAPITAL LETTER A WITH BREVE AND GRAVE;Lu;0;L;0102 0300;;;;N;;;;1EB1; 1EB1;LATIN SMALL LETTER A WITH BREVE AND GRAVE;Ll;0;L;0103 0300;;;;N;;;1EB0;;1EB0 1EB2;LATIN CAPITAL LETTER A WITH BREVE AND HOOK ABOVE;Lu;0;L;0102 0309;;;;N;;;;1EB3; 1EB3;LATIN SMALL LETTER A WITH BREVE AND HOOK ABOVE;Ll;0;L;0103 0309;;;;N;;;1EB2;;1EB2 1EB4;LATIN CAPITAL LETTER A WITH BREVE AND TILDE;Lu;0;L;0102 0303;;;;N;;;;1EB5; 1EB5;LATIN SMALL LETTER A WITH BREVE AND TILDE;Ll;0;L;0103 0303;;;;N;;;1EB4;;1EB4 1EB6;LATIN CAPITAL LETTER A WITH BREVE AND DOT BELOW;Lu;0;L;1EA0 0306;;;;N;;;;1EB7; 1EB7;LATIN SMALL LETTER A WITH BREVE AND DOT BELOW;Ll;0;L;1EA1 0306;;;;N;;;1EB6;;1EB6 1EB8;LATIN CAPITAL LETTER E WITH DOT BELOW;Lu;0;L;0045 0323;;;;N;;;;1EB9; 1EB9;LATIN SMALL LETTER E WITH DOT BELOW;Ll;0;L;0065 0323;;;;N;;;1EB8;;1EB8 1EBA;LATIN CAPITAL LETTER E WITH HOOK ABOVE;Lu;0;L;0045 0309;;;;N;;;;1EBB; 1EBB;LATIN SMALL LETTER E WITH HOOK ABOVE;Ll;0;L;0065 0309;;;;N;;;1EBA;;1EBA 1EBC;LATIN CAPITAL LETTER E WITH TILDE;Lu;0;L;0045 0303;;;;N;;;;1EBD; 1EBD;LATIN SMALL LETTER E WITH TILDE;Ll;0;L;0065 0303;;;;N;;;1EBC;;1EBC 1EBE;LATIN CAPITAL LETTER E WITH CIRCUMFLEX AND ACUTE;Lu;0;L;00CA 0301;;;;N;;;;1EBF; 1EBF;LATIN SMALL LETTER E WITH CIRCUMFLEX AND ACUTE;Ll;0;L;00EA 0301;;;;N;;;1EBE;;1EBE 1EC0;LATIN CAPITAL LETTER E WITH CIRCUMFLEX AND GRAVE;Lu;0;L;00CA 0300;;;;N;;;;1EC1; 1EC1;LATIN SMALL LETTER E WITH CIRCUMFLEX AND GRAVE;Ll;0;L;00EA 0300;;;;N;;;1EC0;;1EC0 1EC2;LATIN CAPITAL LETTER E WITH CIRCUMFLEX AND HOOK ABOVE;Lu;0;L;00CA 0309;;;;N;;;;1EC3; 1EC3;LATIN SMALL LETTER E WITH CIRCUMFLEX AND HOOK ABOVE;Ll;0;L;00EA 0309;;;;N;;;1EC2;;1EC2 1EC4;LATIN CAPITAL LETTER E WITH CIRCUMFLEX AND TILDE;Lu;0;L;00CA 0303;;;;N;;;;1EC5; 1EC5;LATIN SMALL LETTER E WITH CIRCUMFLEX AND TILDE;Ll;0;L;00EA 0303;;;;N;;;1EC4;;1EC4 1EC6;LATIN CAPITAL LETTER E WITH CIRCUMFLEX AND DOT BELOW;Lu;0;L;1EB8 0302;;;;N;;;;1EC7; 1EC7;LATIN SMALL LETTER E WITH CIRCUMFLEX AND DOT BELOW;Ll;0;L;1EB9 0302;;;;N;;;1EC6;;1EC6 1EC8;LATIN CAPITAL LETTER I WITH HOOK ABOVE;Lu;0;L;0049 0309;;;;N;;;;1EC9; 1EC9;LATIN SMALL LETTER I WITH HOOK ABOVE;Ll;0;L;0069 0309;;;;N;;;1EC8;;1EC8 1ECA;LATIN CAPITAL LETTER I WITH DOT BELOW;Lu;0;L;0049 0323;;;;N;;;;1ECB; 1ECB;LATIN SMALL LETTER I WITH DOT BELOW;Ll;0;L;0069 0323;;;;N;;;1ECA;;1ECA 1ECC;LATIN CAPITAL LETTER O WITH DOT BELOW;Lu;0;L;004F 0323;;;;N;;;;1ECD; 1ECD;LATIN SMALL LETTER O WITH DOT BELOW;Ll;0;L;006F 0323;;;;N;;;1ECC;;1ECC 1ECE;LATIN CAPITAL LETTER O WITH HOOK ABOVE;Lu;0;L;004F 0309;;;;N;;;;1ECF; 1ECF;LATIN SMALL LETTER O WITH HOOK ABOVE;Ll;0;L;006F 0309;;;;N;;;1ECE;;1ECE 1ED0;LATIN CAPITAL LETTER O WITH CIRCUMFLEX AND ACUTE;Lu;0;L;00D4 0301;;;;N;;;;1ED1; 1ED1;LATIN SMALL LETTER O WITH CIRCUMFLEX AND ACUTE;Ll;0;L;00F4 0301;;;;N;;;1ED0;;1ED0 1ED2;LATIN CAPITAL LETTER O WITH CIRCUMFLEX AND GRAVE;Lu;0;L;00D4 0300;;;;N;;;;1ED3; 1ED3;LATIN SMALL LETTER O WITH CIRCUMFLEX AND GRAVE;Ll;0;L;00F4 0300;;;;N;;;1ED2;;1ED2 1ED4;LATIN CAPITAL LETTER O WITH CIRCUMFLEX AND HOOK ABOVE;Lu;0;L;00D4 0309;;;;N;;;;1ED5; 1ED5;LATIN SMALL LETTER O WITH CIRCUMFLEX AND HOOK ABOVE;Ll;0;L;00F4 0309;;;;N;;;1ED4;;1ED4 1ED6;LATIN CAPITAL LETTER O WITH CIRCUMFLEX AND TILDE;Lu;0;L;00D4 0303;;;;N;;;;1ED7; 1ED7;LATIN SMALL LETTER O WITH CIRCUMFLEX AND TILDE;Ll;0;L;00F4 0303;;;;N;;;1ED6;;1ED6 1ED8;LATIN CAPITAL LETTER O WITH CIRCUMFLEX AND DOT BELOW;Lu;0;L;1ECC 0302;;;;N;;;;1ED9; 1ED9;LATIN SMALL LETTER O WITH CIRCUMFLEX AND DOT BELOW;Ll;0;L;1ECD 0302;;;;N;;;1ED8;;1ED8 1EDA;LATIN CAPITAL LETTER O WITH HORN AND ACUTE;Lu;0;L;01A0 0301;;;;N;;;;1EDB; 1EDB;LATIN SMALL LETTER O WITH HORN AND ACUTE;Ll;0;L;01A1 0301;;;;N;;;1EDA;;1EDA 1EDC;LATIN CAPITAL LETTER O WITH HORN AND GRAVE;Lu;0;L;01A0 0300;;;;N;;;;1EDD; 1EDD;LATIN SMALL LETTER O WITH HORN AND GRAVE;Ll;0;L;01A1 0300;;;;N;;;1EDC;;1EDC 1EDE;LATIN CAPITAL LETTER O WITH HORN AND HOOK ABOVE;Lu;0;L;01A0 0309;;;;N;;;;1EDF; 1EDF;LATIN SMALL LETTER O WITH HORN AND HOOK ABOVE;Ll;0;L;01A1 0309;;;;N;;;1EDE;;1EDE 1EE0;LATIN CAPITAL LETTER O WITH HORN AND TILDE;Lu;0;L;01A0 0303;;;;N;;;;1EE1; 1EE1;LATIN SMALL LETTER O WITH HORN AND TILDE;Ll;0;L;01A1 0303;;;;N;;;1EE0;;1EE0 1EE2;LATIN CAPITAL LETTER O WITH HORN AND DOT BELOW;Lu;0;L;01A0 0323;;;;N;;;;1EE3; 1EE3;LATIN SMALL LETTER O WITH HORN AND DOT BELOW;Ll;0;L;01A1 0323;;;;N;;;1EE2;;1EE2 1EE4;LATIN CAPITAL LETTER U WITH DOT BELOW;Lu;0;L;0055 0323;;;;N;;;;1EE5; 1EE5;LATIN SMALL LETTER U WITH DOT BELOW;Ll;0;L;0075 0323;;;;N;;;1EE4;;1EE4 1EE6;LATIN CAPITAL LETTER U WITH HOOK ABOVE;Lu;0;L;0055 0309;;;;N;;;;1EE7; 1EE7;LATIN SMALL LETTER U WITH HOOK ABOVE;Ll;0;L;0075 0309;;;;N;;;1EE6;;1EE6 1EE8;LATIN CAPITAL LETTER U WITH HORN AND ACUTE;Lu;0;L;01AF 0301;;;;N;;;;1EE9; 1EE9;LATIN SMALL LETTER U WITH HORN AND ACUTE;Ll;0;L;01B0 0301;;;;N;;;1EE8;;1EE8 1EEA;LATIN CAPITAL LETTER U WITH HORN AND GRAVE;Lu;0;L;01AF 0300;;;;N;;;;1EEB; 1EEB;LATIN SMALL LETTER U WITH HORN AND GRAVE;Ll;0;L;01B0 0300;;;;N;;;1EEA;;1EEA 1EEC;LATIN CAPITAL LETTER U WITH HORN AND HOOK ABOVE;Lu;0;L;01AF 0309;;;;N;;;;1EED; 1EED;LATIN SMALL LETTER U WITH HORN AND HOOK ABOVE;Ll;0;L;01B0 0309;;;;N;;;1EEC;;1EEC 1EEE;LATIN CAPITAL LETTER U WITH HORN AND TILDE;Lu;0;L;01AF 0303;;;;N;;;;1EEF; 1EEF;LATIN SMALL LETTER U WITH HORN AND TILDE;Ll;0;L;01B0 0303;;;;N;;;1EEE;;1EEE 1EF0;LATIN CAPITAL LETTER U WITH HORN AND DOT BELOW;Lu;0;L;01AF 0323;;;;N;;;;1EF1; 1EF1;LATIN SMALL LETTER U WITH HORN AND DOT BELOW;Ll;0;L;01B0 0323;;;;N;;;1EF0;;1EF0 1EF2;LATIN CAPITAL LETTER Y WITH GRAVE;Lu;0;L;0059 0300;;;;N;;;;1EF3; 1EF3;LATIN SMALL LETTER Y WITH GRAVE;Ll;0;L;0079 0300;;;;N;;;1EF2;;1EF2 1EF4;LATIN CAPITAL LETTER Y WITH DOT BELOW;Lu;0;L;0059 0323;;;;N;;;;1EF5; 1EF5;LATIN SMALL LETTER Y WITH DOT BELOW;Ll;0;L;0079 0323;;;;N;;;1EF4;;1EF4 1EF6;LATIN CAPITAL LETTER Y WITH HOOK ABOVE;Lu;0;L;0059 0309;;;;N;;;;1EF7; 1EF7;LATIN SMALL LETTER Y WITH HOOK ABOVE;Ll;0;L;0079 0309;;;;N;;;1EF6;;1EF6 1EF8;LATIN CAPITAL LETTER Y WITH TILDE;Lu;0;L;0059 0303;;;;N;;;;1EF9; 1EF9;LATIN SMALL LETTER Y WITH TILDE;Ll;0;L;0079 0303;;;;N;;;1EF8;;1EF8 1EFA;LATIN CAPITAL LETTER MIDDLE-WELSH LL;Lu;0;L;;;;;N;;;;1EFB; 1EFB;LATIN SMALL LETTER MIDDLE-WELSH LL;Ll;0;L;;;;;N;;;1EFA;;1EFA 1EFC;LATIN CAPITAL LETTER MIDDLE-WELSH V;Lu;0;L;;;;;N;;;;1EFD; 1EFD;LATIN SMALL LETTER MIDDLE-WELSH V;Ll;0;L;;;;;N;;;1EFC;;1EFC 1EFE;LATIN CAPITAL LETTER Y WITH LOOP;Lu;0;L;;;;;N;;;;1EFF; 1EFF;LATIN SMALL LETTER Y WITH LOOP;Ll;0;L;;;;;N;;;1EFE;;1EFE 1F00;GREEK SMALL LETTER ALPHA WITH PSILI;Ll;0;L;03B1 0313;;;;N;;;1F08;;1F08 1F01;GREEK SMALL LETTER ALPHA WITH DASIA;Ll;0;L;03B1 0314;;;;N;;;1F09;;1F09 1F02;GREEK SMALL LETTER ALPHA WITH PSILI AND VARIA;Ll;0;L;1F00 0300;;;;N;;;1F0A;;1F0A 1F03;GREEK SMALL LETTER ALPHA WITH DASIA AND VARIA;Ll;0;L;1F01 0300;;;;N;;;1F0B;;1F0B 1F04;GREEK SMALL LETTER ALPHA WITH PSILI AND OXIA;Ll;0;L;1F00 0301;;;;N;;;1F0C;;1F0C 1F05;GREEK SMALL LETTER ALPHA WITH DASIA AND OXIA;Ll;0;L;1F01 0301;;;;N;;;1F0D;;1F0D 1F06;GREEK SMALL LETTER ALPHA WITH PSILI AND PERISPOMENI;Ll;0;L;1F00 0342;;;;N;;;1F0E;;1F0E 1F07;GREEK SMALL LETTER ALPHA WITH DASIA AND PERISPOMENI;Ll;0;L;1F01 0342;;;;N;;;1F0F;;1F0F 1F08;GREEK CAPITAL LETTER ALPHA WITH PSILI;Lu;0;L;0391 0313;;;;N;;;;1F00; 1F09;GREEK CAPITAL LETTER ALPHA WITH DASIA;Lu;0;L;0391 0314;;;;N;;;;1F01; 1F0A;GREEK CAPITAL LETTER ALPHA WITH PSILI AND VARIA;Lu;0;L;1F08 0300;;;;N;;;;1F02; 1F0B;GREEK CAPITAL LETTER ALPHA WITH DASIA AND VARIA;Lu;0;L;1F09 0300;;;;N;;;;1F03; 1F0C;GREEK CAPITAL LETTER ALPHA WITH PSILI AND OXIA;Lu;0;L;1F08 0301;;;;N;;;;1F04; 1F0D;GREEK CAPITAL LETTER ALPHA WITH DASIA AND OXIA;Lu;0;L;1F09 0301;;;;N;;;;1F05; 1F0E;GREEK CAPITAL LETTER ALPHA WITH PSILI AND PERISPOMENI;Lu;0;L;1F08 0342;;;;N;;;;1F06; 1F0F;GREEK CAPITAL LETTER ALPHA WITH DASIA AND PERISPOMENI;Lu;0;L;1F09 0342;;;;N;;;;1F07; 1F10;GREEK SMALL LETTER EPSILON WITH PSILI;Ll;0;L;03B5 0313;;;;N;;;1F18;;1F18 1F11;GREEK SMALL LETTER EPSILON WITH DASIA;Ll;0;L;03B5 0314;;;;N;;;1F19;;1F19 1F12;GREEK SMALL LETTER EPSILON WITH PSILI AND VARIA;Ll;0;L;1F10 0300;;;;N;;;1F1A;;1F1A 1F13;GREEK SMALL LETTER EPSILON WITH DASIA AND VARIA;Ll;0;L;1F11 0300;;;;N;;;1F1B;;1F1B 1F14;GREEK SMALL LETTER EPSILON WITH PSILI AND OXIA;Ll;0;L;1F10 0301;;;;N;;;1F1C;;1F1C 1F15;GREEK SMALL LETTER EPSILON WITH DASIA AND OXIA;Ll;0;L;1F11 0301;;;;N;;;1F1D;;1F1D 1F18;GREEK CAPITAL LETTER EPSILON WITH PSILI;Lu;0;L;0395 0313;;;;N;;;;1F10; 1F19;GREEK CAPITAL LETTER EPSILON WITH DASIA;Lu;0;L;0395 0314;;;;N;;;;1F11; 1F1A;GREEK CAPITAL LETTER EPSILON WITH PSILI AND VARIA;Lu;0;L;1F18 0300;;;;N;;;;1F12; 1F1B;GREEK CAPITAL LETTER EPSILON WITH DASIA AND VARIA;Lu;0;L;1F19 0300;;;;N;;;;1F13; 1F1C;GREEK CAPITAL LETTER EPSILON WITH PSILI AND OXIA;Lu;0;L;1F18 0301;;;;N;;;;1F14; 1F1D;GREEK CAPITAL LETTER EPSILON WITH DASIA AND OXIA;Lu;0;L;1F19 0301;;;;N;;;;1F15; 1F20;GREEK SMALL LETTER ETA WITH PSILI;Ll;0;L;03B7 0313;;;;N;;;1F28;;1F28 1F21;GREEK SMALL LETTER ETA WITH DASIA;Ll;0;L;03B7 0314;;;;N;;;1F29;;1F29 1F22;GREEK SMALL LETTER ETA WITH PSILI AND VARIA;Ll;0;L;1F20 0300;;;;N;;;1F2A;;1F2A 1F23;GREEK SMALL LETTER ETA WITH DASIA AND VARIA;Ll;0;L;1F21 0300;;;;N;;;1F2B;;1F2B 1F24;GREEK SMALL LETTER ETA WITH PSILI AND OXIA;Ll;0;L;1F20 0301;;;;N;;;1F2C;;1F2C 1F25;GREEK SMALL LETTER ETA WITH DASIA AND OXIA;Ll;0;L;1F21 0301;;;;N;;;1F2D;;1F2D 1F26;GREEK SMALL LETTER ETA WITH PSILI AND PERISPOMENI;Ll;0;L;1F20 0342;;;;N;;;1F2E;;1F2E 1F27;GREEK SMALL LETTER ETA WITH DASIA AND PERISPOMENI;Ll;0;L;1F21 0342;;;;N;;;1F2F;;1F2F 1F28;GREEK CAPITAL LETTER ETA WITH PSILI;Lu;0;L;0397 0313;;;;N;;;;1F20; 1F29;GREEK CAPITAL LETTER ETA WITH DASIA;Lu;0;L;0397 0314;;;;N;;;;1F21; 1F2A;GREEK CAPITAL LETTER ETA WITH PSILI AND VARIA;Lu;0;L;1F28 0300;;;;N;;;;1F22; 1F2B;GREEK CAPITAL LETTER ETA WITH DASIA AND VARIA;Lu;0;L;1F29 0300;;;;N;;;;1F23; 1F2C;GREEK CAPITAL LETTER ETA WITH PSILI AND OXIA;Lu;0;L;1F28 0301;;;;N;;;;1F24; 1F2D;GREEK CAPITAL LETTER ETA WITH DASIA AND OXIA;Lu;0;L;1F29 0301;;;;N;;;;1F25; 1F2E;GREEK CAPITAL LETTER ETA WITH PSILI AND PERISPOMENI;Lu;0;L;1F28 0342;;;;N;;;;1F26; 1F2F;GREEK CAPITAL LETTER ETA WITH DASIA AND PERISPOMENI;Lu;0;L;1F29 0342;;;;N;;;;1F27; 1F30;GREEK SMALL LETTER IOTA WITH PSILI;Ll;0;L;03B9 0313;;;;N;;;1F38;;1F38 1F31;GREEK SMALL LETTER IOTA WITH DASIA;Ll;0;L;03B9 0314;;;;N;;;1F39;;1F39 1F32;GREEK SMALL LETTER IOTA WITH PSILI AND VARIA;Ll;0;L;1F30 0300;;;;N;;;1F3A;;1F3A 1F33;GREEK SMALL LETTER IOTA WITH DASIA AND VARIA;Ll;0;L;1F31 0300;;;;N;;;1F3B;;1F3B 1F34;GREEK SMALL LETTER IOTA WITH PSILI AND OXIA;Ll;0;L;1F30 0301;;;;N;;;1F3C;;1F3C 1F35;GREEK SMALL LETTER IOTA WITH DASIA AND OXIA;Ll;0;L;1F31 0301;;;;N;;;1F3D;;1F3D 1F36;GREEK SMALL LETTER IOTA WITH PSILI AND PERISPOMENI;Ll;0;L;1F30 0342;;;;N;;;1F3E;;1F3E 1F37;GREEK SMALL LETTER IOTA WITH DASIA AND PERISPOMENI;Ll;0;L;1F31 0342;;;;N;;;1F3F;;1F3F 1F38;GREEK CAPITAL LETTER IOTA WITH PSILI;Lu;0;L;0399 0313;;;;N;;;;1F30; 1F39;GREEK CAPITAL LETTER IOTA WITH DASIA;Lu;0;L;0399 0314;;;;N;;;;1F31; 1F3A;GREEK CAPITAL LETTER IOTA WITH PSILI AND VARIA;Lu;0;L;1F38 0300;;;;N;;;;1F32; 1F3B;GREEK CAPITAL LETTER IOTA WITH DASIA AND VARIA;Lu;0;L;1F39 0300;;;;N;;;;1F33; 1F3C;GREEK CAPITAL LETTER IOTA WITH PSILI AND OXIA;Lu;0;L;1F38 0301;;;;N;;;;1F34; 1F3D;GREEK CAPITAL LETTER IOTA WITH DASIA AND OXIA;Lu;0;L;1F39 0301;;;;N;;;;1F35; 1F3E;GREEK CAPITAL LETTER IOTA WITH PSILI AND PERISPOMENI;Lu;0;L;1F38 0342;;;;N;;;;1F36; 1F3F;GREEK CAPITAL LETTER IOTA WITH DASIA AND PERISPOMENI;Lu;0;L;1F39 0342;;;;N;;;;1F37; 1F40;GREEK SMALL LETTER OMICRON WITH PSILI;Ll;0;L;03BF 0313;;;;N;;;1F48;;1F48 1F41;GREEK SMALL LETTER OMICRON WITH DASIA;Ll;0;L;03BF 0314;;;;N;;;1F49;;1F49 1F42;GREEK SMALL LETTER OMICRON WITH PSILI AND VARIA;Ll;0;L;1F40 0300;;;;N;;;1F4A;;1F4A 1F43;GREEK SMALL LETTER OMICRON WITH DASIA AND VARIA;Ll;0;L;1F41 0300;;;;N;;;1F4B;;1F4B 1F44;GREEK SMALL LETTER OMICRON WITH PSILI AND OXIA;Ll;0;L;1F40 0301;;;;N;;;1F4C;;1F4C 1F45;GREEK SMALL LETTER OMICRON WITH DASIA AND OXIA;Ll;0;L;1F41 0301;;;;N;;;1F4D;;1F4D 1F48;GREEK CAPITAL LETTER OMICRON WITH PSILI;Lu;0;L;039F 0313;;;;N;;;;1F40; 1F49;GREEK CAPITAL LETTER OMICRON WITH DASIA;Lu;0;L;039F 0314;;;;N;;;;1F41; 1F4A;GREEK CAPITAL LETTER OMICRON WITH PSILI AND VARIA;Lu;0;L;1F48 0300;;;;N;;;;1F42; 1F4B;GREEK CAPITAL LETTER OMICRON WITH DASIA AND VARIA;Lu;0;L;1F49 0300;;;;N;;;;1F43; 1F4C;GREEK CAPITAL LETTER OMICRON WITH PSILI AND OXIA;Lu;0;L;1F48 0301;;;;N;;;;1F44; 1F4D;GREEK CAPITAL LETTER OMICRON WITH DASIA AND OXIA;Lu;0;L;1F49 0301;;;;N;;;;1F45; 1F50;GREEK SMALL LETTER UPSILON WITH PSILI;Ll;0;L;03C5 0313;;;;N;;;;; 1F51;GREEK SMALL LETTER UPSILON WITH DASIA;Ll;0;L;03C5 0314;;;;N;;;1F59;;1F59 1F52;GREEK SMALL LETTER UPSILON WITH PSILI AND VARIA;Ll;0;L;1F50 0300;;;;N;;;;; 1F53;GREEK SMALL LETTER UPSILON WITH DASIA AND VARIA;Ll;0;L;1F51 0300;;;;N;;;1F5B;;1F5B 1F54;GREEK SMALL LETTER UPSILON WITH PSILI AND OXIA;Ll;0;L;1F50 0301;;;;N;;;;; 1F55;GREEK SMALL LETTER UPSILON WITH DASIA AND OXIA;Ll;0;L;1F51 0301;;;;N;;;1F5D;;1F5D 1F56;GREEK SMALL LETTER UPSILON WITH PSILI AND PERISPOMENI;Ll;0;L;1F50 0342;;;;N;;;;; 1F57;GREEK SMALL LETTER UPSILON WITH DASIA AND PERISPOMENI;Ll;0;L;1F51 0342;;;;N;;;1F5F;;1F5F 1F59;GREEK CAPITAL LETTER UPSILON WITH DASIA;Lu;0;L;03A5 0314;;;;N;;;;1F51; 1F5B;GREEK CAPITAL LETTER UPSILON WITH DASIA AND VARIA;Lu;0;L;1F59 0300;;;;N;;;;1F53; 1F5D;GREEK CAPITAL LETTER UPSILON WITH DASIA AND OXIA;Lu;0;L;1F59 0301;;;;N;;;;1F55; 1F5F;GREEK CAPITAL LETTER UPSILON WITH DASIA AND PERISPOMENI;Lu;0;L;1F59 0342;;;;N;;;;1F57; 1F60;GREEK SMALL LETTER OMEGA WITH PSILI;Ll;0;L;03C9 0313;;;;N;;;1F68;;1F68 1F61;GREEK SMALL LETTER OMEGA WITH DASIA;Ll;0;L;03C9 0314;;;;N;;;1F69;;1F69 1F62;GREEK SMALL LETTER OMEGA WITH PSILI AND VARIA;Ll;0;L;1F60 0300;;;;N;;;1F6A;;1F6A 1F63;GREEK SMALL LETTER OMEGA WITH DASIA AND VARIA;Ll;0;L;1F61 0300;;;;N;;;1F6B;;1F6B 1F64;GREEK SMALL LETTER OMEGA WITH PSILI AND OXIA;Ll;0;L;1F60 0301;;;;N;;;1F6C;;1F6C 1F65;GREEK SMALL LETTER OMEGA WITH DASIA AND OXIA;Ll;0;L;1F61 0301;;;;N;;;1F6D;;1F6D 1F66;GREEK SMALL LETTER OMEGA WITH PSILI AND PERISPOMENI;Ll;0;L;1F60 0342;;;;N;;;1F6E;;1F6E 1F67;GREEK SMALL LETTER OMEGA WITH DASIA AND PERISPOMENI;Ll;0;L;1F61 0342;;;;N;;;1F6F;;1F6F 1F68;GREEK CAPITAL LETTER OMEGA WITH PSILI;Lu;0;L;03A9 0313;;;;N;;;;1F60; 1F69;GREEK CAPITAL LETTER OMEGA WITH DASIA;Lu;0;L;03A9 0314;;;;N;;;;1F61; 1F6A;GREEK CAPITAL LETTER OMEGA WITH PSILI AND VARIA;Lu;0;L;1F68 0300;;;;N;;;;1F62; 1F6B;GREEK CAPITAL LETTER OMEGA WITH DASIA AND VARIA;Lu;0;L;1F69 0300;;;;N;;;;1F63; 1F6C;GREEK CAPITAL LETTER OMEGA WITH PSILI AND OXIA;Lu;0;L;1F68 0301;;;;N;;;;1F64; 1F6D;GREEK CAPITAL LETTER OMEGA WITH DASIA AND OXIA;Lu;0;L;1F69 0301;;;;N;;;;1F65; 1F6E;GREEK CAPITAL LETTER OMEGA WITH PSILI AND PERISPOMENI;Lu;0;L;1F68 0342;;;;N;;;;1F66; 1F6F;GREEK CAPITAL LETTER OMEGA WITH DASIA AND PERISPOMENI;Lu;0;L;1F69 0342;;;;N;;;;1F67; 1F70;GREEK SMALL LETTER ALPHA WITH VARIA;Ll;0;L;03B1 0300;;;;N;;;1FBA;;1FBA 1F71;GREEK SMALL LETTER ALPHA WITH OXIA;Ll;0;L;03AC;;;;N;;;1FBB;;1FBB 1F72;GREEK SMALL LETTER EPSILON WITH VARIA;Ll;0;L;03B5 0300;;;;N;;;1FC8;;1FC8 1F73;GREEK SMALL LETTER EPSILON WITH OXIA;Ll;0;L;03AD;;;;N;;;1FC9;;1FC9 1F74;GREEK SMALL LETTER ETA WITH VARIA;Ll;0;L;03B7 0300;;;;N;;;1FCA;;1FCA 1F75;GREEK SMALL LETTER ETA WITH OXIA;Ll;0;L;03AE;;;;N;;;1FCB;;1FCB 1F76;GREEK SMALL LETTER IOTA WITH VARIA;Ll;0;L;03B9 0300;;;;N;;;1FDA;;1FDA 1F77;GREEK SMALL LETTER IOTA WITH OXIA;Ll;0;L;03AF;;;;N;;;1FDB;;1FDB 1F78;GREEK SMALL LETTER OMICRON WITH VARIA;Ll;0;L;03BF 0300;;;;N;;;1FF8;;1FF8 1F79;GREEK SMALL LETTER OMICRON WITH OXIA;Ll;0;L;03CC;;;;N;;;1FF9;;1FF9 1F7A;GREEK SMALL LETTER UPSILON WITH VARIA;Ll;0;L;03C5 0300;;;;N;;;1FEA;;1FEA 1F7B;GREEK SMALL LETTER UPSILON WITH OXIA;Ll;0;L;03CD;;;;N;;;1FEB;;1FEB 1F7C;GREEK SMALL LETTER OMEGA WITH VARIA;Ll;0;L;03C9 0300;;;;N;;;1FFA;;1FFA 1F7D;GREEK SMALL LETTER OMEGA WITH OXIA;Ll;0;L;03CE;;;;N;;;1FFB;;1FFB 1F80;GREEK SMALL LETTER ALPHA WITH PSILI AND YPOGEGRAMMENI;Ll;0;L;1F00 0345;;;;N;;;1F88;;1F88 1F81;GREEK SMALL LETTER ALPHA WITH DASIA AND YPOGEGRAMMENI;Ll;0;L;1F01 0345;;;;N;;;1F89;;1F89 1F82;GREEK SMALL LETTER ALPHA WITH PSILI AND VARIA AND YPOGEGRAMMENI;Ll;0;L;1F02 0345;;;;N;;;1F8A;;1F8A 1F83;GREEK SMALL LETTER ALPHA WITH DASIA AND VARIA AND YPOGEGRAMMENI;Ll;0;L;1F03 0345;;;;N;;;1F8B;;1F8B 1F84;GREEK SMALL LETTER ALPHA WITH PSILI AND OXIA AND YPOGEGRAMMENI;Ll;0;L;1F04 0345;;;;N;;;1F8C;;1F8C 1F85;GREEK SMALL LETTER ALPHA WITH DASIA AND OXIA AND YPOGEGRAMMENI;Ll;0;L;1F05 0345;;;;N;;;1F8D;;1F8D 1F86;GREEK SMALL LETTER ALPHA WITH PSILI AND PERISPOMENI AND YPOGEGRAMMENI;Ll;0;L;1F06 0345;;;;N;;;1F8E;;1F8E 1F87;GREEK SMALL LETTER ALPHA WITH DASIA AND PERISPOMENI AND YPOGEGRAMMENI;Ll;0;L;1F07 0345;;;;N;;;1F8F;;1F8F 1F88;GREEK CAPITAL LETTER ALPHA WITH PSILI AND PROSGEGRAMMENI;Lt;0;L;1F08 0345;;;;N;;;;1F80; 1F89;GREEK CAPITAL LETTER ALPHA WITH DASIA AND PROSGEGRAMMENI;Lt;0;L;1F09 0345;;;;N;;;;1F81; 1F8A;GREEK CAPITAL LETTER ALPHA WITH PSILI AND VARIA AND PROSGEGRAMMENI;Lt;0;L;1F0A 0345;;;;N;;;;1F82; 1F8B;GREEK CAPITAL LETTER ALPHA WITH DASIA AND VARIA AND PROSGEGRAMMENI;Lt;0;L;1F0B 0345;;;;N;;;;1F83; 1F8C;GREEK CAPITAL LETTER ALPHA WITH PSILI AND OXIA AND PROSGEGRAMMENI;Lt;0;L;1F0C 0345;;;;N;;;;1F84; 1F8D;GREEK CAPITAL LETTER ALPHA WITH DASIA AND OXIA AND PROSGEGRAMMENI;Lt;0;L;1F0D 0345;;;;N;;;;1F85; 1F8E;GREEK CAPITAL LETTER ALPHA WITH PSILI AND PERISPOMENI AND PROSGEGRAMMENI;Lt;0;L;1F0E 0345;;;;N;;;;1F86; 1F8F;GREEK CAPITAL LETTER ALPHA WITH DASIA AND PERISPOMENI AND PROSGEGRAMMENI;Lt;0;L;1F0F 0345;;;;N;;;;1F87; 1F90;GREEK SMALL LETTER ETA WITH PSILI AND YPOGEGRAMMENI;Ll;0;L;1F20 0345;;;;N;;;1F98;;1F98 1F91;GREEK SMALL LETTER ETA WITH DASIA AND YPOGEGRAMMENI;Ll;0;L;1F21 0345;;;;N;;;1F99;;1F99 1F92;GREEK SMALL LETTER ETA WITH PSILI AND VARIA AND YPOGEGRAMMENI;Ll;0;L;1F22 0345;;;;N;;;1F9A;;1F9A 1F93;GREEK SMALL LETTER ETA WITH DASIA AND VARIA AND YPOGEGRAMMENI;Ll;0;L;1F23 0345;;;;N;;;1F9B;;1F9B 1F94;GREEK SMALL LETTER ETA WITH PSILI AND OXIA AND YPOGEGRAMMENI;Ll;0;L;1F24 0345;;;;N;;;1F9C;;1F9C 1F95;GREEK SMALL LETTER ETA WITH DASIA AND OXIA AND YPOGEGRAMMENI;Ll;0;L;1F25 0345;;;;N;;;1F9D;;1F9D 1F96;GREEK SMALL LETTER ETA WITH PSILI AND PERISPOMENI AND YPOGEGRAMMENI;Ll;0;L;1F26 0345;;;;N;;;1F9E;;1F9E 1F97;GREEK SMALL LETTER ETA WITH DASIA AND PERISPOMENI AND YPOGEGRAMMENI;Ll;0;L;1F27 0345;;;;N;;;1F9F;;1F9F 1F98;GREEK CAPITAL LETTER ETA WITH PSILI AND PROSGEGRAMMENI;Lt;0;L;1F28 0345;;;;N;;;;1F90; 1F99;GREEK CAPITAL LETTER ETA WITH DASIA AND PROSGEGRAMMENI;Lt;0;L;1F29 0345;;;;N;;;;1F91; 1F9A;GREEK CAPITAL LETTER ETA WITH PSILI AND VARIA AND PROSGEGRAMMENI;Lt;0;L;1F2A 0345;;;;N;;;;1F92; 1F9B;GREEK CAPITAL LETTER ETA WITH DASIA AND VARIA AND PROSGEGRAMMENI;Lt;0;L;1F2B 0345;;;;N;;;;1F93; 1F9C;GREEK CAPITAL LETTER ETA WITH PSILI AND OXIA AND PROSGEGRAMMENI;Lt;0;L;1F2C 0345;;;;N;;;;1F94; 1F9D;GREEK CAPITAL LETTER ETA WITH DASIA AND OXIA AND PROSGEGRAMMENI;Lt;0;L;1F2D 0345;;;;N;;;;1F95; 1F9E;GREEK CAPITAL LETTER ETA WITH PSILI AND PERISPOMENI AND PROSGEGRAMMENI;Lt;0;L;1F2E 0345;;;;N;;;;1F96; 1F9F;GREEK CAPITAL LETTER ETA WITH DASIA AND PERISPOMENI AND PROSGEGRAMMENI;Lt;0;L;1F2F 0345;;;;N;;;;1F97; 1FA0;GREEK SMALL LETTER OMEGA WITH PSILI AND YPOGEGRAMMENI;Ll;0;L;1F60 0345;;;;N;;;1FA8;;1FA8 1FA1;GREEK SMALL LETTER OMEGA WITH DASIA AND YPOGEGRAMMENI;Ll;0;L;1F61 0345;;;;N;;;1FA9;;1FA9 1FA2;GREEK SMALL LETTER OMEGA WITH PSILI AND VARIA AND YPOGEGRAMMENI;Ll;0;L;1F62 0345;;;;N;;;1FAA;;1FAA 1FA3;GREEK SMALL LETTER OMEGA WITH DASIA AND VARIA AND YPOGEGRAMMENI;Ll;0;L;1F63 0345;;;;N;;;1FAB;;1FAB 1FA4;GREEK SMALL LETTER OMEGA WITH PSILI AND OXIA AND YPOGEGRAMMENI;Ll;0;L;1F64 0345;;;;N;;;1FAC;;1FAC 1FA5;GREEK SMALL LETTER OMEGA WITH DASIA AND OXIA AND YPOGEGRAMMENI;Ll;0;L;1F65 0345;;;;N;;;1FAD;;1FAD 1FA6;GREEK SMALL LETTER OMEGA WITH PSILI AND PERISPOMENI AND YPOGEGRAMMENI;Ll;0;L;1F66 0345;;;;N;;;1FAE;;1FAE 1FA7;GREEK SMALL LETTER OMEGA WITH DASIA AND PERISPOMENI AND YPOGEGRAMMENI;Ll;0;L;1F67 0345;;;;N;;;1FAF;;1FAF 1FA8;GREEK CAPITAL LETTER OMEGA WITH PSILI AND PROSGEGRAMMENI;Lt;0;L;1F68 0345;;;;N;;;;1FA0; 1FA9;GREEK CAPITAL LETTER OMEGA WITH DASIA AND PROSGEGRAMMENI;Lt;0;L;1F69 0345;;;;N;;;;1FA1; 1FAA;GREEK CAPITAL LETTER OMEGA WITH PSILI AND VARIA AND PROSGEGRAMMENI;Lt;0;L;1F6A 0345;;;;N;;;;1FA2; 1FAB;GREEK CAPITAL LETTER OMEGA WITH DASIA AND VARIA AND PROSGEGRAMMENI;Lt;0;L;1F6B 0345;;;;N;;;;1FA3; 1FAC;GREEK CAPITAL LETTER OMEGA WITH PSILI AND OXIA AND PROSGEGRAMMENI;Lt;0;L;1F6C 0345;;;;N;;;;1FA4; 1FAD;GREEK CAPITAL LETTER OMEGA WITH DASIA AND OXIA AND PROSGEGRAMMENI;Lt;0;L;1F6D 0345;;;;N;;;;1FA5; 1FAE;GREEK CAPITAL LETTER OMEGA WITH PSILI AND PERISPOMENI AND PROSGEGRAMMENI;Lt;0;L;1F6E 0345;;;;N;;;;1FA6; 1FAF;GREEK CAPITAL LETTER OMEGA WITH DASIA AND PERISPOMENI AND PROSGEGRAMMENI;Lt;0;L;1F6F 0345;;;;N;;;;1FA7; 1FB0;GREEK SMALL LETTER ALPHA WITH VRACHY;Ll;0;L;03B1 0306;;;;N;;;1FB8;;1FB8 1FB1;GREEK SMALL LETTER ALPHA WITH MACRON;Ll;0;L;03B1 0304;;;;N;;;1FB9;;1FB9 1FB2;GREEK SMALL LETTER ALPHA WITH VARIA AND YPOGEGRAMMENI;Ll;0;L;1F70 0345;;;;N;;;;; 1FB3;GREEK SMALL LETTER ALPHA WITH YPOGEGRAMMENI;Ll;0;L;03B1 0345;;;;N;;;1FBC;;1FBC 1FB4;GREEK SMALL LETTER ALPHA WITH OXIA AND YPOGEGRAMMENI;Ll;0;L;03AC 0345;;;;N;;;;; 1FB6;GREEK SMALL LETTER ALPHA WITH PERISPOMENI;Ll;0;L;03B1 0342;;;;N;;;;; 1FB7;GREEK SMALL LETTER ALPHA WITH PERISPOMENI AND YPOGEGRAMMENI;Ll;0;L;1FB6 0345;;;;N;;;;; 1FB8;GREEK CAPITAL LETTER ALPHA WITH VRACHY;Lu;0;L;0391 0306;;;;N;;;;1FB0; 1FB9;GREEK CAPITAL LETTER ALPHA WITH MACRON;Lu;0;L;0391 0304;;;;N;;;;1FB1; 1FBA;GREEK CAPITAL LETTER ALPHA WITH VARIA;Lu;0;L;0391 0300;;;;N;;;;1F70; 1FBB;GREEK CAPITAL LETTER ALPHA WITH OXIA;Lu;0;L;0386;;;;N;;;;1F71; 1FBC;GREEK CAPITAL LETTER ALPHA WITH PROSGEGRAMMENI;Lt;0;L;0391 0345;;;;N;;;;1FB3; 1FBD;GREEK KORONIS;Sk;0;ON; 0020 0313;;;;N;;;;; 1FBE;GREEK PROSGEGRAMMENI;Ll;0;L;03B9;;;;N;;;0399;;0399 1FBF;GREEK PSILI;Sk;0;ON; 0020 0313;;;;N;;;;; 1FC0;GREEK PERISPOMENI;Sk;0;ON; 0020 0342;;;;N;;;;; 1FC1;GREEK DIALYTIKA AND PERISPOMENI;Sk;0;ON;00A8 0342;;;;N;;;;; 1FC2;GREEK SMALL LETTER ETA WITH VARIA AND YPOGEGRAMMENI;Ll;0;L;1F74 0345;;;;N;;;;; 1FC3;GREEK SMALL LETTER ETA WITH YPOGEGRAMMENI;Ll;0;L;03B7 0345;;;;N;;;1FCC;;1FCC 1FC4;GREEK SMALL LETTER ETA WITH OXIA AND YPOGEGRAMMENI;Ll;0;L;03AE 0345;;;;N;;;;; 1FC6;GREEK SMALL LETTER ETA WITH PERISPOMENI;Ll;0;L;03B7 0342;;;;N;;;;; 1FC7;GREEK SMALL LETTER ETA WITH PERISPOMENI AND YPOGEGRAMMENI;Ll;0;L;1FC6 0345;;;;N;;;;; 1FC8;GREEK CAPITAL LETTER EPSILON WITH VARIA;Lu;0;L;0395 0300;;;;N;;;;1F72; 1FC9;GREEK CAPITAL LETTER EPSILON WITH OXIA;Lu;0;L;0388;;;;N;;;;1F73; 1FCA;GREEK CAPITAL LETTER ETA WITH VARIA;Lu;0;L;0397 0300;;;;N;;;;1F74; 1FCB;GREEK CAPITAL LETTER ETA WITH OXIA;Lu;0;L;0389;;;;N;;;;1F75; 1FCC;GREEK CAPITAL LETTER ETA WITH PROSGEGRAMMENI;Lt;0;L;0397 0345;;;;N;;;;1FC3; 1FCD;GREEK PSILI AND VARIA;Sk;0;ON;1FBF 0300;;;;N;;;;; 1FCE;GREEK PSILI AND OXIA;Sk;0;ON;1FBF 0301;;;;N;;;;; 1FCF;GREEK PSILI AND PERISPOMENI;Sk;0;ON;1FBF 0342;;;;N;;;;; 1FD0;GREEK SMALL LETTER IOTA WITH VRACHY;Ll;0;L;03B9 0306;;;;N;;;1FD8;;1FD8 1FD1;GREEK SMALL LETTER IOTA WITH MACRON;Ll;0;L;03B9 0304;;;;N;;;1FD9;;1FD9 1FD2;GREEK SMALL LETTER IOTA WITH DIALYTIKA AND VARIA;Ll;0;L;03CA 0300;;;;N;;;;; 1FD3;GREEK SMALL LETTER IOTA WITH DIALYTIKA AND OXIA;Ll;0;L;0390;;;;N;;;;; 1FD6;GREEK SMALL LETTER IOTA WITH PERISPOMENI;Ll;0;L;03B9 0342;;;;N;;;;; 1FD7;GREEK SMALL LETTER IOTA WITH DIALYTIKA AND PERISPOMENI;Ll;0;L;03CA 0342;;;;N;;;;; 1FD8;GREEK CAPITAL LETTER IOTA WITH VRACHY;Lu;0;L;0399 0306;;;;N;;;;1FD0; 1FD9;GREEK CAPITAL LETTER IOTA WITH MACRON;Lu;0;L;0399 0304;;;;N;;;;1FD1; 1FDA;GREEK CAPITAL LETTER IOTA WITH VARIA;Lu;0;L;0399 0300;;;;N;;;;1F76; 1FDB;GREEK CAPITAL LETTER IOTA WITH OXIA;Lu;0;L;038A;;;;N;;;;1F77; 1FDD;GREEK DASIA AND VARIA;Sk;0;ON;1FFE 0300;;;;N;;;;; 1FDE;GREEK DASIA AND OXIA;Sk;0;ON;1FFE 0301;;;;N;;;;; 1FDF;GREEK DASIA AND PERISPOMENI;Sk;0;ON;1FFE 0342;;;;N;;;;; 1FE0;GREEK SMALL LETTER UPSILON WITH VRACHY;Ll;0;L;03C5 0306;;;;N;;;1FE8;;1FE8 1FE1;GREEK SMALL LETTER UPSILON WITH MACRON;Ll;0;L;03C5 0304;;;;N;;;1FE9;;1FE9 1FE2;GREEK SMALL LETTER UPSILON WITH DIALYTIKA AND VARIA;Ll;0;L;03CB 0300;;;;N;;;;; 1FE3;GREEK SMALL LETTER UPSILON WITH DIALYTIKA AND OXIA;Ll;0;L;03B0;;;;N;;;;; 1FE4;GREEK SMALL LETTER RHO WITH PSILI;Ll;0;L;03C1 0313;;;;N;;;;; 1FE5;GREEK SMALL LETTER RHO WITH DASIA;Ll;0;L;03C1 0314;;;;N;;;1FEC;;1FEC 1FE6;GREEK SMALL LETTER UPSILON WITH PERISPOMENI;Ll;0;L;03C5 0342;;;;N;;;;; 1FE7;GREEK SMALL LETTER UPSILON WITH DIALYTIKA AND PERISPOMENI;Ll;0;L;03CB 0342;;;;N;;;;; 1FE8;GREEK CAPITAL LETTER UPSILON WITH VRACHY;Lu;0;L;03A5 0306;;;;N;;;;1FE0; 1FE9;GREEK CAPITAL LETTER UPSILON WITH MACRON;Lu;0;L;03A5 0304;;;;N;;;;1FE1; 1FEA;GREEK CAPITAL LETTER UPSILON WITH VARIA;Lu;0;L;03A5 0300;;;;N;;;;1F7A; 1FEB;GREEK CAPITAL LETTER UPSILON WITH OXIA;Lu;0;L;038E;;;;N;;;;1F7B; 1FEC;GREEK CAPITAL LETTER RHO WITH DASIA;Lu;0;L;03A1 0314;;;;N;;;;1FE5; 1FED;GREEK DIALYTIKA AND VARIA;Sk;0;ON;00A8 0300;;;;N;;;;; 1FEE;GREEK DIALYTIKA AND OXIA;Sk;0;ON;0385;;;;N;;;;; 1FEF;GREEK VARIA;Sk;0;ON;0060;;;;N;;;;; 1FF2;GREEK SMALL LETTER OMEGA WITH VARIA AND YPOGEGRAMMENI;Ll;0;L;1F7C 0345;;;;N;;;;; 1FF3;GREEK SMALL LETTER OMEGA WITH YPOGEGRAMMENI;Ll;0;L;03C9 0345;;;;N;;;1FFC;;1FFC 1FF4;GREEK SMALL LETTER OMEGA WITH OXIA AND YPOGEGRAMMENI;Ll;0;L;03CE 0345;;;;N;;;;; 1FF6;GREEK SMALL LETTER OMEGA WITH PERISPOMENI;Ll;0;L;03C9 0342;;;;N;;;;; 1FF7;GREEK SMALL LETTER OMEGA WITH PERISPOMENI AND YPOGEGRAMMENI;Ll;0;L;1FF6 0345;;;;N;;;;; 1FF8;GREEK CAPITAL LETTER OMICRON WITH VARIA;Lu;0;L;039F 0300;;;;N;;;;1F78; 1FF9;GREEK CAPITAL LETTER OMICRON WITH OXIA;Lu;0;L;038C;;;;N;;;;1F79; 1FFA;GREEK CAPITAL LETTER OMEGA WITH VARIA;Lu;0;L;03A9 0300;;;;N;;;;1F7C; 1FFB;GREEK CAPITAL LETTER OMEGA WITH OXIA;Lu;0;L;038F;;;;N;;;;1F7D; 1FFC;GREEK CAPITAL LETTER OMEGA WITH PROSGEGRAMMENI;Lt;0;L;03A9 0345;;;;N;;;;1FF3; 1FFD;GREEK OXIA;Sk;0;ON;00B4;;;;N;;;;; 1FFE;GREEK DASIA;Sk;0;ON; 0020 0314;;;;N;;;;; 2000;EN QUAD;Zs;0;WS;2002;;;;N;;;;; 2001;EM QUAD;Zs;0;WS;2003;;;;N;;;;; 2002;EN SPACE;Zs;0;WS; 0020;;;;N;;;;; 2003;EM SPACE;Zs;0;WS; 0020;;;;N;;;;; 2004;THREE-PER-EM SPACE;Zs;0;WS; 0020;;;;N;;;;; 2005;FOUR-PER-EM SPACE;Zs;0;WS; 0020;;;;N;;;;; 2006;SIX-PER-EM SPACE;Zs;0;WS; 0020;;;;N;;;;; 2007;FIGURE SPACE;Zs;0;WS; 0020;;;;N;;;;; 2008;PUNCTUATION SPACE;Zs;0;WS; 0020;;;;N;;;;; 2009;THIN SPACE;Zs;0;WS; 0020;;;;N;;;;; 200A;HAIR SPACE;Zs;0;WS; 0020;;;;N;;;;; 200B;ZERO WIDTH SPACE;Cf;0;BN;;;;;N;;;;; 200C;ZERO WIDTH NON-JOINER;Cf;0;BN;;;;;N;;;;; 200D;ZERO WIDTH JOINER;Cf;0;BN;;;;;N;;;;; 200E;LEFT-TO-RIGHT MARK;Cf;0;L;;;;;N;;;;; 200F;RIGHT-TO-LEFT MARK;Cf;0;R;;;;;N;;;;; 2010;HYPHEN;Pd;0;ON;;;;;N;;;;; 2011;NON-BREAKING HYPHEN;Pd;0;ON; 2010;;;;N;;;;; 2012;FIGURE DASH;Pd;0;ON;;;;;N;;;;; 2013;EN DASH;Pd;0;ON;;;;;N;;;;; 2014;EM DASH;Pd;0;ON;;;;;N;;;;; 2015;HORIZONTAL BAR;Pd;0;ON;;;;;N;QUOTATION DASH;;;; 2016;DOUBLE VERTICAL LINE;Po;0;ON;;;;;N;DOUBLE VERTICAL BAR;;;; 2017;DOUBLE LOW LINE;Po;0;ON; 0020 0333;;;;N;SPACING DOUBLE UNDERSCORE;;;; 2018;LEFT SINGLE QUOTATION MARK;Pi;0;ON;;;;;N;SINGLE TURNED COMMA QUOTATION MARK;;;; 2019;RIGHT SINGLE QUOTATION MARK;Pf;0;ON;;;;;N;SINGLE COMMA QUOTATION MARK;;;; 201A;SINGLE LOW-9 QUOTATION MARK;Ps;0;ON;;;;;N;LOW SINGLE COMMA QUOTATION MARK;;;; 201B;SINGLE HIGH-REVERSED-9 QUOTATION MARK;Pi;0;ON;;;;;N;SINGLE REVERSED COMMA QUOTATION MARK;;;; 201C;LEFT DOUBLE QUOTATION MARK;Pi;0;ON;;;;;N;DOUBLE TURNED COMMA QUOTATION MARK;;;; 201D;RIGHT DOUBLE QUOTATION MARK;Pf;0;ON;;;;;N;DOUBLE COMMA QUOTATION MARK;;;; 201E;DOUBLE LOW-9 QUOTATION MARK;Ps;0;ON;;;;;N;LOW DOUBLE COMMA QUOTATION MARK;;;; 201F;DOUBLE HIGH-REVERSED-9 QUOTATION MARK;Pi;0;ON;;;;;N;DOUBLE REVERSED COMMA QUOTATION MARK;;;; 2020;DAGGER;Po;0;ON;;;;;N;;;;; 2021;DOUBLE DAGGER;Po;0;ON;;;;;N;;;;; 2022;BULLET;Po;0;ON;;;;;N;;;;; 2023;TRIANGULAR BULLET;Po;0;ON;;;;;N;;;;; 2024;ONE DOT LEADER;Po;0;ON; 002E;;;;N;;;;; 2025;TWO DOT LEADER;Po;0;ON; 002E 002E;;;;N;;;;; 2026;HORIZONTAL ELLIPSIS;Po;0;ON; 002E 002E 002E;;;;N;;;;; 2027;HYPHENATION POINT;Po;0;ON;;;;;N;;;;; 2028;LINE SEPARATOR;Zl;0;WS;;;;;N;;;;; 2029;PARAGRAPH SEPARATOR;Zp;0;B;;;;;N;;;;; 202A;LEFT-TO-RIGHT EMBEDDING;Cf;0;LRE;;;;;N;;;;; 202B;RIGHT-TO-LEFT EMBEDDING;Cf;0;RLE;;;;;N;;;;; 202C;POP DIRECTIONAL FORMATTING;Cf;0;PDF;;;;;N;;;;; 202D;LEFT-TO-RIGHT OVERRIDE;Cf;0;LRO;;;;;N;;;;; 202E;RIGHT-TO-LEFT OVERRIDE;Cf;0;RLO;;;;;N;;;;; 202F;NARROW NO-BREAK SPACE;Zs;0;CS; 0020;;;;N;;;;; 2030;PER MILLE SIGN;Po;0;ET;;;;;N;;;;; 2031;PER TEN THOUSAND SIGN;Po;0;ET;;;;;N;;;;; 2032;PRIME;Po;0;ET;;;;;N;;;;; 2033;DOUBLE PRIME;Po;0;ET; 2032 2032;;;;N;;;;; 2034;TRIPLE PRIME;Po;0;ET; 2032 2032 2032;;;;N;;;;; 2035;REVERSED PRIME;Po;0;ON;;;;;N;;;;; 2036;REVERSED DOUBLE PRIME;Po;0;ON; 2035 2035;;;;N;;;;; 2037;REVERSED TRIPLE PRIME;Po;0;ON; 2035 2035 2035;;;;N;;;;; 2038;CARET;Po;0;ON;;;;;N;;;;; 2039;SINGLE LEFT-POINTING ANGLE QUOTATION MARK;Pi;0;ON;;;;;Y;LEFT POINTING SINGLE GUILLEMET;;;; 203A;SINGLE RIGHT-POINTING ANGLE QUOTATION MARK;Pf;0;ON;;;;;Y;RIGHT POINTING SINGLE GUILLEMET;;;; 203B;REFERENCE MARK;Po;0;ON;;;;;N;;;;; 203C;DOUBLE EXCLAMATION MARK;Po;0;ON; 0021 0021;;;;N;;;;; 203D;INTERROBANG;Po;0;ON;;;;;N;;;;; 203E;OVERLINE;Po;0;ON; 0020 0305;;;;N;SPACING OVERSCORE;;;; 203F;UNDERTIE;Pc;0;ON;;;;;N;;;;; 2040;CHARACTER TIE;Pc;0;ON;;;;;N;;;;; 2041;CARET INSERTION POINT;Po;0;ON;;;;;N;;;;; 2042;ASTERISM;Po;0;ON;;;;;N;;;;; 2043;HYPHEN BULLET;Po;0;ON;;;;;N;;;;; 2044;FRACTION SLASH;Sm;0;CS;;;;;N;;;;; 2045;LEFT SQUARE BRACKET WITH QUILL;Ps;0;ON;;;;;Y;;;;; 2046;RIGHT SQUARE BRACKET WITH QUILL;Pe;0;ON;;;;;Y;;;;; 2047;DOUBLE QUESTION MARK;Po;0;ON; 003F 003F;;;;N;;;;; 2048;QUESTION EXCLAMATION MARK;Po;0;ON; 003F 0021;;;;N;;;;; 2049;EXCLAMATION QUESTION MARK;Po;0;ON; 0021 003F;;;;N;;;;; 204A;TIRONIAN SIGN ET;Po;0;ON;;;;;N;;;;; 204B;REVERSED PILCROW SIGN;Po;0;ON;;;;;N;;;;; 204C;BLACK LEFTWARDS BULLET;Po;0;ON;;;;;N;;;;; 204D;BLACK RIGHTWARDS BULLET;Po;0;ON;;;;;N;;;;; 204E;LOW ASTERISK;Po;0;ON;;;;;N;;;;; 204F;REVERSED SEMICOLON;Po;0;ON;;;;;N;;;;; 2050;CLOSE UP;Po;0;ON;;;;;N;;;;; 2051;TWO ASTERISKS ALIGNED VERTICALLY;Po;0;ON;;;;;N;;;;; 2052;COMMERCIAL MINUS SIGN;Sm;0;ON;;;;;N;;;;; 2053;SWUNG DASH;Po;0;ON;;;;;N;;;;; 2054;INVERTED UNDERTIE;Pc;0;ON;;;;;N;;;;; 2055;FLOWER PUNCTUATION MARK;Po;0;ON;;;;;N;;;;; 2056;THREE DOT PUNCTUATION;Po;0;ON;;;;;N;;;;; 2057;QUADRUPLE PRIME;Po;0;ON; 2032 2032 2032 2032;;;;N;;;;; 2058;FOUR DOT PUNCTUATION;Po;0;ON;;;;;N;;;;; 2059;FIVE DOT PUNCTUATION;Po;0;ON;;;;;N;;;;; 205A;TWO DOT PUNCTUATION;Po;0;ON;;;;;N;;;;; 205B;FOUR DOT MARK;Po;0;ON;;;;;N;;;;; 205C;DOTTED CROSS;Po;0;ON;;;;;N;;;;; 205D;TRICOLON;Po;0;ON;;;;;N;;;;; 205E;VERTICAL FOUR DOTS;Po;0;ON;;;;;N;;;;; 205F;MEDIUM MATHEMATICAL SPACE;Zs;0;WS; 0020;;;;N;;;;; 2060;WORD JOINER;Cf;0;BN;;;;;N;;;;; 2061;FUNCTION APPLICATION;Cf;0;BN;;;;;N;;;;; 2062;INVISIBLE TIMES;Cf;0;BN;;;;;N;;;;; 2063;INVISIBLE SEPARATOR;Cf;0;BN;;;;;N;;;;; 2064;INVISIBLE PLUS;Cf;0;BN;;;;;N;;;;; 2066;LEFT-TO-RIGHT ISOLATE;Cf;0;LRI;;;;;N;;;;; 2067;RIGHT-TO-LEFT ISOLATE;Cf;0;RLI;;;;;N;;;;; 2068;FIRST STRONG ISOLATE;Cf;0;FSI;;;;;N;;;;; 2069;POP DIRECTIONAL ISOLATE;Cf;0;PDI;;;;;N;;;;; 206A;INHIBIT SYMMETRIC SWAPPING;Cf;0;BN;;;;;N;;;;; 206B;ACTIVATE SYMMETRIC SWAPPING;Cf;0;BN;;;;;N;;;;; 206C;INHIBIT ARABIC FORM SHAPING;Cf;0;BN;;;;;N;;;;; 206D;ACTIVATE ARABIC FORM SHAPING;Cf;0;BN;;;;;N;;;;; 206E;NATIONAL DIGIT SHAPES;Cf;0;BN;;;;;N;;;;; 206F;NOMINAL DIGIT SHAPES;Cf;0;BN;;;;;N;;;;; 2070;SUPERSCRIPT ZERO;No;0;EN; 0030;;0;0;N;SUPERSCRIPT DIGIT ZERO;;;; 2071;SUPERSCRIPT LATIN SMALL LETTER I;Lm;0;L; 0069;;;;N;;;;; 2074;SUPERSCRIPT FOUR;No;0;EN; 0034;;4;4;N;SUPERSCRIPT DIGIT FOUR;;;; 2075;SUPERSCRIPT FIVE;No;0;EN; 0035;;5;5;N;SUPERSCRIPT DIGIT FIVE;;;; 2076;SUPERSCRIPT SIX;No;0;EN; 0036;;6;6;N;SUPERSCRIPT DIGIT SIX;;;; 2077;SUPERSCRIPT SEVEN;No;0;EN; 0037;;7;7;N;SUPERSCRIPT DIGIT SEVEN;;;; 2078;SUPERSCRIPT EIGHT;No;0;EN; 0038;;8;8;N;SUPERSCRIPT DIGIT EIGHT;;;; 2079;SUPERSCRIPT NINE;No;0;EN; 0039;;9;9;N;SUPERSCRIPT DIGIT NINE;;;; 207A;SUPERSCRIPT PLUS SIGN;Sm;0;ES; 002B;;;;N;;;;; 207B;SUPERSCRIPT MINUS;Sm;0;ES; 2212;;;;N;SUPERSCRIPT HYPHEN-MINUS;;;; 207C;SUPERSCRIPT EQUALS SIGN;Sm;0;ON; 003D;;;;N;;;;; 207D;SUPERSCRIPT LEFT PARENTHESIS;Ps;0;ON; 0028;;;;Y;SUPERSCRIPT OPENING PARENTHESIS;;;; 207E;SUPERSCRIPT RIGHT PARENTHESIS;Pe;0;ON; 0029;;;;Y;SUPERSCRIPT CLOSING PARENTHESIS;;;; 207F;SUPERSCRIPT LATIN SMALL LETTER N;Lm;0;L; 006E;;;;N;;;;; 2080;SUBSCRIPT ZERO;No;0;EN; 0030;;0;0;N;SUBSCRIPT DIGIT ZERO;;;; 2081;SUBSCRIPT ONE;No;0;EN; 0031;;1;1;N;SUBSCRIPT DIGIT ONE;;;; 2082;SUBSCRIPT TWO;No;0;EN; 0032;;2;2;N;SUBSCRIPT DIGIT TWO;;;; 2083;SUBSCRIPT THREE;No;0;EN; 0033;;3;3;N;SUBSCRIPT DIGIT THREE;;;; 2084;SUBSCRIPT FOUR;No;0;EN; 0034;;4;4;N;SUBSCRIPT DIGIT FOUR;;;; 2085;SUBSCRIPT FIVE;No;0;EN; 0035;;5;5;N;SUBSCRIPT DIGIT FIVE;;;; 2086;SUBSCRIPT SIX;No;0;EN; 0036;;6;6;N;SUBSCRIPT DIGIT SIX;;;; 2087;SUBSCRIPT SEVEN;No;0;EN; 0037;;7;7;N;SUBSCRIPT DIGIT SEVEN;;;; 2088;SUBSCRIPT EIGHT;No;0;EN; 0038;;8;8;N;SUBSCRIPT DIGIT EIGHT;;;; 2089;SUBSCRIPT NINE;No;0;EN; 0039;;9;9;N;SUBSCRIPT DIGIT NINE;;;; 208A;SUBSCRIPT PLUS SIGN;Sm;0;ES; 002B;;;;N;;;;; 208B;SUBSCRIPT MINUS;Sm;0;ES; 2212;;;;N;SUBSCRIPT HYPHEN-MINUS;;;; 208C;SUBSCRIPT EQUALS SIGN;Sm;0;ON; 003D;;;;N;;;;; 208D;SUBSCRIPT LEFT PARENTHESIS;Ps;0;ON; 0028;;;;Y;SUBSCRIPT OPENING PARENTHESIS;;;; 208E;SUBSCRIPT RIGHT PARENTHESIS;Pe;0;ON; 0029;;;;Y;SUBSCRIPT CLOSING PARENTHESIS;;;; 2090;LATIN SUBSCRIPT SMALL LETTER A;Lm;0;L; 0061;;;;N;;;;; 2091;LATIN SUBSCRIPT SMALL LETTER E;Lm;0;L; 0065;;;;N;;;;; 2092;LATIN SUBSCRIPT SMALL LETTER O;Lm;0;L; 006F;;;;N;;;;; 2093;LATIN SUBSCRIPT SMALL LETTER X;Lm;0;L; 0078;;;;N;;;;; 2094;LATIN SUBSCRIPT SMALL LETTER SCHWA;Lm;0;L; 0259;;;;N;;;;; 2095;LATIN SUBSCRIPT SMALL LETTER H;Lm;0;L; 0068;;;;N;;;;; 2096;LATIN SUBSCRIPT SMALL LETTER K;Lm;0;L; 006B;;;;N;;;;; 2097;LATIN SUBSCRIPT SMALL LETTER L;Lm;0;L; 006C;;;;N;;;;; 2098;LATIN SUBSCRIPT SMALL LETTER M;Lm;0;L; 006D;;;;N;;;;; 2099;LATIN SUBSCRIPT SMALL LETTER N;Lm;0;L; 006E;;;;N;;;;; 209A;LATIN SUBSCRIPT SMALL LETTER P;Lm;0;L; 0070;;;;N;;;;; 209B;LATIN SUBSCRIPT SMALL LETTER S;Lm;0;L; 0073;;;;N;;;;; 209C;LATIN SUBSCRIPT SMALL LETTER T;Lm;0;L; 0074;;;;N;;;;; 20A0;EURO-CURRENCY SIGN;Sc;0;ET;;;;;N;;;;; 20A1;COLON SIGN;Sc;0;ET;;;;;N;;;;; 20A2;CRUZEIRO SIGN;Sc;0;ET;;;;;N;;;;; 20A3;FRENCH FRANC SIGN;Sc;0;ET;;;;;N;;;;; 20A4;LIRA SIGN;Sc;0;ET;;;;;N;;;;; 20A5;MILL SIGN;Sc;0;ET;;;;;N;;;;; 20A6;NAIRA SIGN;Sc;0;ET;;;;;N;;;;; 20A7;PESETA SIGN;Sc;0;ET;;;;;N;;;;; 20A8;RUPEE SIGN;Sc;0;ET; 0052 0073;;;;N;;;;; 20A9;WON SIGN;Sc;0;ET;;;;;N;;;;; 20AA;NEW SHEQEL SIGN;Sc;0;ET;;;;;N;;;;; 20AB;DONG SIGN;Sc;0;ET;;;;;N;;;;; 20AC;EURO SIGN;Sc;0;ET;;;;;N;;;;; 20AD;KIP SIGN;Sc;0;ET;;;;;N;;;;; 20AE;TUGRIK SIGN;Sc;0;ET;;;;;N;;;;; 20AF;DRACHMA SIGN;Sc;0;ET;;;;;N;;;;; 20B0;GERMAN PENNY SIGN;Sc;0;ET;;;;;N;;;;; 20B1;PESO SIGN;Sc;0;ET;;;;;N;;;;; 20B2;GUARANI SIGN;Sc;0;ET;;;;;N;;;;; 20B3;AUSTRAL SIGN;Sc;0;ET;;;;;N;;;;; 20B4;HRYVNIA SIGN;Sc;0;ET;;;;;N;;;;; 20B5;CEDI SIGN;Sc;0;ET;;;;;N;;;;; 20B6;LIVRE TOURNOIS SIGN;Sc;0;ET;;;;;N;;;;; 20B7;SPESMILO SIGN;Sc;0;ET;;;;;N;;;;; 20B8;TENGE SIGN;Sc;0;ET;;;;;N;;;;; 20B9;INDIAN RUPEE SIGN;Sc;0;ET;;;;;N;;;;; 20BA;TURKISH LIRA SIGN;Sc;0;ET;;;;;N;;;;; 20BB;NORDIC MARK SIGN;Sc;0;ET;;;;;N;;;;; 20BC;MANAT SIGN;Sc;0;ET;;;;;N;;;;; 20BD;RUBLE SIGN;Sc;0;ET;;;;;N;;;;; 20D0;COMBINING LEFT HARPOON ABOVE;Mn;230;NSM;;;;;N;NON-SPACING LEFT HARPOON ABOVE;;;; 20D1;COMBINING RIGHT HARPOON ABOVE;Mn;230;NSM;;;;;N;NON-SPACING RIGHT HARPOON ABOVE;;;; 20D2;COMBINING LONG VERTICAL LINE OVERLAY;Mn;1;NSM;;;;;N;NON-SPACING LONG VERTICAL BAR OVERLAY;;;; 20D3;COMBINING SHORT VERTICAL LINE OVERLAY;Mn;1;NSM;;;;;N;NON-SPACING SHORT VERTICAL BAR OVERLAY;;;; 20D4;COMBINING ANTICLOCKWISE ARROW ABOVE;Mn;230;NSM;;;;;N;NON-SPACING ANTICLOCKWISE ARROW ABOVE;;;; 20D5;COMBINING CLOCKWISE ARROW ABOVE;Mn;230;NSM;;;;;N;NON-SPACING CLOCKWISE ARROW ABOVE;;;; 20D6;COMBINING LEFT ARROW ABOVE;Mn;230;NSM;;;;;N;NON-SPACING LEFT ARROW ABOVE;;;; 20D7;COMBINING RIGHT ARROW ABOVE;Mn;230;NSM;;;;;N;NON-SPACING RIGHT ARROW ABOVE;;;; 20D8;COMBINING RING OVERLAY;Mn;1;NSM;;;;;N;NON-SPACING RING OVERLAY;;;; 20D9;COMBINING CLOCKWISE RING OVERLAY;Mn;1;NSM;;;;;N;NON-SPACING CLOCKWISE RING OVERLAY;;;; 20DA;COMBINING ANTICLOCKWISE RING OVERLAY;Mn;1;NSM;;;;;N;NON-SPACING ANTICLOCKWISE RING OVERLAY;;;; 20DB;COMBINING THREE DOTS ABOVE;Mn;230;NSM;;;;;N;NON-SPACING THREE DOTS ABOVE;;;; 20DC;COMBINING FOUR DOTS ABOVE;Mn;230;NSM;;;;;N;NON-SPACING FOUR DOTS ABOVE;;;; 20DD;COMBINING ENCLOSING CIRCLE;Me;0;NSM;;;;;N;ENCLOSING CIRCLE;;;; 20DE;COMBINING ENCLOSING SQUARE;Me;0;NSM;;;;;N;ENCLOSING SQUARE;;;; 20DF;COMBINING ENCLOSING DIAMOND;Me;0;NSM;;;;;N;ENCLOSING DIAMOND;;;; 20E0;COMBINING ENCLOSING CIRCLE BACKSLASH;Me;0;NSM;;;;;N;ENCLOSING CIRCLE SLASH;;;; 20E1;COMBINING LEFT RIGHT ARROW ABOVE;Mn;230;NSM;;;;;N;NON-SPACING LEFT RIGHT ARROW ABOVE;;;; 20E2;COMBINING ENCLOSING SCREEN;Me;0;NSM;;;;;N;;;;; 20E3;COMBINING ENCLOSING KEYCAP;Me;0;NSM;;;;;N;;;;; 20E4;COMBINING ENCLOSING UPWARD POINTING TRIANGLE;Me;0;NSM;;;;;N;;;;; 20E5;COMBINING REVERSE SOLIDUS OVERLAY;Mn;1;NSM;;;;;N;;;;; 20E6;COMBINING DOUBLE VERTICAL STROKE OVERLAY;Mn;1;NSM;;;;;N;;;;; 20E7;COMBINING ANNUITY SYMBOL;Mn;230;NSM;;;;;N;;;;; 20E8;COMBINING TRIPLE UNDERDOT;Mn;220;NSM;;;;;N;;;;; 20E9;COMBINING WIDE BRIDGE ABOVE;Mn;230;NSM;;;;;N;;;;; 20EA;COMBINING LEFTWARDS ARROW OVERLAY;Mn;1;NSM;;;;;N;;;;; 20EB;COMBINING LONG DOUBLE SOLIDUS OVERLAY;Mn;1;NSM;;;;;N;;;;; 20EC;COMBINING RIGHTWARDS HARPOON WITH BARB DOWNWARDS;Mn;220;NSM;;;;;N;;;;; 20ED;COMBINING LEFTWARDS HARPOON WITH BARB DOWNWARDS;Mn;220;NSM;;;;;N;;;;; 20EE;COMBINING LEFT ARROW BELOW;Mn;220;NSM;;;;;N;;;;; 20EF;COMBINING RIGHT ARROW BELOW;Mn;220;NSM;;;;;N;;;;; 20F0;COMBINING ASTERISK ABOVE;Mn;230;NSM;;;;;N;;;;; 2100;ACCOUNT OF;So;0;ON; 0061 002F 0063;;;;N;;;;; 2101;ADDRESSED TO THE SUBJECT;So;0;ON; 0061 002F 0073;;;;N;;;;; 2102;DOUBLE-STRUCK CAPITAL C;Lu;0;L; 0043;;;;N;DOUBLE-STRUCK C;;;; 2103;DEGREE CELSIUS;So;0;ON; 00B0 0043;;;;N;DEGREES CENTIGRADE;;;; 2104;CENTRE LINE SYMBOL;So;0;ON;;;;;N;C L SYMBOL;;;; 2105;CARE OF;So;0;ON; 0063 002F 006F;;;;N;;;;; 2106;CADA UNA;So;0;ON; 0063 002F 0075;;;;N;;;;; 2107;EULER CONSTANT;Lu;0;L; 0190;;;;N;EULERS;;;; 2108;SCRUPLE;So;0;ON;;;;;N;;;;; 2109;DEGREE FAHRENHEIT;So;0;ON; 00B0 0046;;;;N;DEGREES FAHRENHEIT;;;; 210A;SCRIPT SMALL G;Ll;0;L; 0067;;;;N;;;;; 210B;SCRIPT CAPITAL H;Lu;0;L; 0048;;;;N;SCRIPT H;;;; 210C;BLACK-LETTER CAPITAL H;Lu;0;L; 0048;;;;N;BLACK-LETTER H;;;; 210D;DOUBLE-STRUCK CAPITAL H;Lu;0;L; 0048;;;;N;DOUBLE-STRUCK H;;;; 210E;PLANCK CONSTANT;Ll;0;L; 0068;;;;N;;;;; 210F;PLANCK CONSTANT OVER TWO PI;Ll;0;L; 0127;;;;N;PLANCK CONSTANT OVER 2 PI;;;; 2110;SCRIPT CAPITAL I;Lu;0;L; 0049;;;;N;SCRIPT I;;;; 2111;BLACK-LETTER CAPITAL I;Lu;0;L; 0049;;;;N;BLACK-LETTER I;;;; 2112;SCRIPT CAPITAL L;Lu;0;L; 004C;;;;N;SCRIPT L;;;; 2113;SCRIPT SMALL L;Ll;0;L; 006C;;;;N;;;;; 2114;L B BAR SYMBOL;So;0;ON;;;;;N;;;;; 2115;DOUBLE-STRUCK CAPITAL N;Lu;0;L; 004E;;;;N;DOUBLE-STRUCK N;;;; 2116;NUMERO SIGN;So;0;ON; 004E 006F;;;;N;NUMERO;;;; 2117;SOUND RECORDING COPYRIGHT;So;0;ON;;;;;N;;;;; 2118;SCRIPT CAPITAL P;Sm;0;ON;;;;;N;SCRIPT P;;;; 2119;DOUBLE-STRUCK CAPITAL P;Lu;0;L; 0050;;;;N;DOUBLE-STRUCK P;;;; 211A;DOUBLE-STRUCK CAPITAL Q;Lu;0;L; 0051;;;;N;DOUBLE-STRUCK Q;;;; 211B;SCRIPT CAPITAL R;Lu;0;L; 0052;;;;N;SCRIPT R;;;; 211C;BLACK-LETTER CAPITAL R;Lu;0;L; 0052;;;;N;BLACK-LETTER R;;;; 211D;DOUBLE-STRUCK CAPITAL R;Lu;0;L; 0052;;;;N;DOUBLE-STRUCK R;;;; 211E;PRESCRIPTION TAKE;So;0;ON;;;;;N;;;;; 211F;RESPONSE;So;0;ON;;;;;N;;;;; 2120;SERVICE MARK;So;0;ON; 0053 004D;;;;N;;;;; 2121;TELEPHONE SIGN;So;0;ON; 0054 0045 004C;;;;N;T E L SYMBOL;;;; 2122;TRADE MARK SIGN;So;0;ON; 0054 004D;;;;N;TRADEMARK;;;; 2123;VERSICLE;So;0;ON;;;;;N;;;;; 2124;DOUBLE-STRUCK CAPITAL Z;Lu;0;L; 005A;;;;N;DOUBLE-STRUCK Z;;;; 2125;OUNCE SIGN;So;0;ON;;;;;N;OUNCE;;;; 2126;OHM SIGN;Lu;0;L;03A9;;;;N;OHM;;;03C9; 2127;INVERTED OHM SIGN;So;0;ON;;;;;N;MHO;;;; 2128;BLACK-LETTER CAPITAL Z;Lu;0;L; 005A;;;;N;BLACK-LETTER Z;;;; 2129;TURNED GREEK SMALL LETTER IOTA;So;0;ON;;;;;N;;;;; 212A;KELVIN SIGN;Lu;0;L;004B;;;;N;DEGREES KELVIN;;;006B; 212B;ANGSTROM SIGN;Lu;0;L;00C5;;;;N;ANGSTROM UNIT;;;00E5; 212C;SCRIPT CAPITAL B;Lu;0;L; 0042;;;;N;SCRIPT B;;;; 212D;BLACK-LETTER CAPITAL C;Lu;0;L; 0043;;;;N;BLACK-LETTER C;;;; 212E;ESTIMATED SYMBOL;So;0;ET;;;;;N;;;;; 212F;SCRIPT SMALL E;Ll;0;L; 0065;;;;N;;;;; 2130;SCRIPT CAPITAL E;Lu;0;L; 0045;;;;N;SCRIPT E;;;; 2131;SCRIPT CAPITAL F;Lu;0;L; 0046;;;;N;SCRIPT F;;;; 2132;TURNED CAPITAL F;Lu;0;L;;;;;N;TURNED F;;;214E; 2133;SCRIPT CAPITAL M;Lu;0;L; 004D;;;;N;SCRIPT M;;;; 2134;SCRIPT SMALL O;Ll;0;L; 006F;;;;N;;;;; 2135;ALEF SYMBOL;Lo;0;L; 05D0;;;;N;FIRST TRANSFINITE CARDINAL;;;; 2136;BET SYMBOL;Lo;0;L; 05D1;;;;N;SECOND TRANSFINITE CARDINAL;;;; 2137;GIMEL SYMBOL;Lo;0;L; 05D2;;;;N;THIRD TRANSFINITE CARDINAL;;;; 2138;DALET SYMBOL;Lo;0;L; 05D3;;;;N;FOURTH TRANSFINITE CARDINAL;;;; 2139;INFORMATION SOURCE;Ll;0;L; 0069;;;;N;;;;; 213A;ROTATED CAPITAL Q;So;0;ON;;;;;N;;;;; 213B;FACSIMILE SIGN;So;0;ON; 0046 0041 0058;;;;N;;;;; 213C;DOUBLE-STRUCK SMALL PI;Ll;0;L; 03C0;;;;N;;;;; 213D;DOUBLE-STRUCK SMALL GAMMA;Ll;0;L; 03B3;;;;N;;;;; 213E;DOUBLE-STRUCK CAPITAL GAMMA;Lu;0;L; 0393;;;;N;;;;; 213F;DOUBLE-STRUCK CAPITAL PI;Lu;0;L; 03A0;;;;N;;;;; 2140;DOUBLE-STRUCK N-ARY SUMMATION;Sm;0;ON; 2211;;;;Y;;;;; 2141;TURNED SANS-SERIF CAPITAL G;Sm;0;ON;;;;;N;;;;; 2142;TURNED SANS-SERIF CAPITAL L;Sm;0;ON;;;;;N;;;;; 2143;REVERSED SANS-SERIF CAPITAL L;Sm;0;ON;;;;;N;;;;; 2144;TURNED SANS-SERIF CAPITAL Y;Sm;0;ON;;;;;N;;;;; 2145;DOUBLE-STRUCK ITALIC CAPITAL D;Lu;0;L; 0044;;;;N;;;;; 2146;DOUBLE-STRUCK ITALIC SMALL D;Ll;0;L; 0064;;;;N;;;;; 2147;DOUBLE-STRUCK ITALIC SMALL E;Ll;0;L; 0065;;;;N;;;;; 2148;DOUBLE-STRUCK ITALIC SMALL I;Ll;0;L; 0069;;;;N;;;;; 2149;DOUBLE-STRUCK ITALIC SMALL J;Ll;0;L; 006A;;;;N;;;;; 214A;PROPERTY LINE;So;0;ON;;;;;N;;;;; 214B;TURNED AMPERSAND;Sm;0;ON;;;;;N;;;;; 214C;PER SIGN;So;0;ON;;;;;N;;;;; 214D;AKTIESELSKAB;So;0;ON;;;;;N;;;;; 214E;TURNED SMALL F;Ll;0;L;;;;;N;;;2132;;2132 214F;SYMBOL FOR SAMARITAN SOURCE;So;0;L;;;;;N;;;;; 2150;VULGAR FRACTION ONE SEVENTH;No;0;ON; 0031 2044 0037;;;1/7;N;;;;; 2151;VULGAR FRACTION ONE NINTH;No;0;ON; 0031 2044 0039;;;1/9;N;;;;; 2152;VULGAR FRACTION ONE TENTH;No;0;ON; 0031 2044 0031 0030;;;1/10;N;;;;; 2153;VULGAR FRACTION ONE THIRD;No;0;ON; 0031 2044 0033;;;1/3;N;FRACTION ONE THIRD;;;; 2154;VULGAR FRACTION TWO THIRDS;No;0;ON; 0032 2044 0033;;;2/3;N;FRACTION TWO THIRDS;;;; 2155;VULGAR FRACTION ONE FIFTH;No;0;ON; 0031 2044 0035;;;1/5;N;FRACTION ONE FIFTH;;;; 2156;VULGAR FRACTION TWO FIFTHS;No;0;ON; 0032 2044 0035;;;2/5;N;FRACTION TWO FIFTHS;;;; 2157;VULGAR FRACTION THREE FIFTHS;No;0;ON; 0033 2044 0035;;;3/5;N;FRACTION THREE FIFTHS;;;; 2158;VULGAR FRACTION FOUR FIFTHS;No;0;ON; 0034 2044 0035;;;4/5;N;FRACTION FOUR FIFTHS;;;; 2159;VULGAR FRACTION ONE SIXTH;No;0;ON; 0031 2044 0036;;;1/6;N;FRACTION ONE SIXTH;;;; 215A;VULGAR FRACTION FIVE SIXTHS;No;0;ON; 0035 2044 0036;;;5/6;N;FRACTION FIVE SIXTHS;;;; 215B;VULGAR FRACTION ONE EIGHTH;No;0;ON; 0031 2044 0038;;;1/8;N;FRACTION ONE EIGHTH;;;; 215C;VULGAR FRACTION THREE EIGHTHS;No;0;ON; 0033 2044 0038;;;3/8;N;FRACTION THREE EIGHTHS;;;; 215D;VULGAR FRACTION FIVE EIGHTHS;No;0;ON; 0035 2044 0038;;;5/8;N;FRACTION FIVE EIGHTHS;;;; 215E;VULGAR FRACTION SEVEN EIGHTHS;No;0;ON; 0037 2044 0038;;;7/8;N;FRACTION SEVEN EIGHTHS;;;; 215F;FRACTION NUMERATOR ONE;No;0;ON; 0031 2044;;;1;N;;;;; 2160;ROMAN NUMERAL ONE;Nl;0;L; 0049;;;1;N;;;;2170; 2161;ROMAN NUMERAL TWO;Nl;0;L; 0049 0049;;;2;N;;;;2171; 2162;ROMAN NUMERAL THREE;Nl;0;L; 0049 0049 0049;;;3;N;;;;2172; 2163;ROMAN NUMERAL FOUR;Nl;0;L; 0049 0056;;;4;N;;;;2173; 2164;ROMAN NUMERAL FIVE;Nl;0;L; 0056;;;5;N;;;;2174; 2165;ROMAN NUMERAL SIX;Nl;0;L; 0056 0049;;;6;N;;;;2175; 2166;ROMAN NUMERAL SEVEN;Nl;0;L; 0056 0049 0049;;;7;N;;;;2176; 2167;ROMAN NUMERAL EIGHT;Nl;0;L; 0056 0049 0049 0049;;;8;N;;;;2177; 2168;ROMAN NUMERAL NINE;Nl;0;L; 0049 0058;;;9;N;;;;2178; 2169;ROMAN NUMERAL TEN;Nl;0;L; 0058;;;10;N;;;;2179; 216A;ROMAN NUMERAL ELEVEN;Nl;0;L; 0058 0049;;;11;N;;;;217A; 216B;ROMAN NUMERAL TWELVE;Nl;0;L; 0058 0049 0049;;;12;N;;;;217B; 216C;ROMAN NUMERAL FIFTY;Nl;0;L; 004C;;;50;N;;;;217C; 216D;ROMAN NUMERAL ONE HUNDRED;Nl;0;L; 0043;;;100;N;;;;217D; 216E;ROMAN NUMERAL FIVE HUNDRED;Nl;0;L; 0044;;;500;N;;;;217E; 216F;ROMAN NUMERAL ONE THOUSAND;Nl;0;L; 004D;;;1000;N;;;;217F; 2170;SMALL ROMAN NUMERAL ONE;Nl;0;L; 0069;;;1;N;;;2160;;2160 2171;SMALL ROMAN NUMERAL TWO;Nl;0;L; 0069 0069;;;2;N;;;2161;;2161 2172;SMALL ROMAN NUMERAL THREE;Nl;0;L; 0069 0069 0069;;;3;N;;;2162;;2162 2173;SMALL ROMAN NUMERAL FOUR;Nl;0;L; 0069 0076;;;4;N;;;2163;;2163 2174;SMALL ROMAN NUMERAL FIVE;Nl;0;L; 0076;;;5;N;;;2164;;2164 2175;SMALL ROMAN NUMERAL SIX;Nl;0;L; 0076 0069;;;6;N;;;2165;;2165 2176;SMALL ROMAN NUMERAL SEVEN;Nl;0;L; 0076 0069 0069;;;7;N;;;2166;;2166 2177;SMALL ROMAN NUMERAL EIGHT;Nl;0;L; 0076 0069 0069 0069;;;8;N;;;2167;;2167 2178;SMALL ROMAN NUMERAL NINE;Nl;0;L; 0069 0078;;;9;N;;;2168;;2168 2179;SMALL ROMAN NUMERAL TEN;Nl;0;L; 0078;;;10;N;;;2169;;2169 217A;SMALL ROMAN NUMERAL ELEVEN;Nl;0;L; 0078 0069;;;11;N;;;216A;;216A 217B;SMALL ROMAN NUMERAL TWELVE;Nl;0;L; 0078 0069 0069;;;12;N;;;216B;;216B 217C;SMALL ROMAN NUMERAL FIFTY;Nl;0;L; 006C;;;50;N;;;216C;;216C 217D;SMALL ROMAN NUMERAL ONE HUNDRED;Nl;0;L; 0063;;;100;N;;;216D;;216D 217E;SMALL ROMAN NUMERAL FIVE HUNDRED;Nl;0;L; 0064;;;500;N;;;216E;;216E 217F;SMALL ROMAN NUMERAL ONE THOUSAND;Nl;0;L; 006D;;;1000;N;;;216F;;216F 2180;ROMAN NUMERAL ONE THOUSAND C D;Nl;0;L;;;;1000;N;;;;; 2181;ROMAN NUMERAL FIVE THOUSAND;Nl;0;L;;;;5000;N;;;;; 2182;ROMAN NUMERAL TEN THOUSAND;Nl;0;L;;;;10000;N;;;;; 2183;ROMAN NUMERAL REVERSED ONE HUNDRED;Lu;0;L;;;;;N;;;;2184; 2184;LATIN SMALL LETTER REVERSED C;Ll;0;L;;;;;N;;;2183;;2183 2185;ROMAN NUMERAL SIX LATE FORM;Nl;0;L;;;;6;N;;;;; 2186;ROMAN NUMERAL FIFTY EARLY FORM;Nl;0;L;;;;50;N;;;;; 2187;ROMAN NUMERAL FIFTY THOUSAND;Nl;0;L;;;;50000;N;;;;; 2188;ROMAN NUMERAL ONE HUNDRED THOUSAND;Nl;0;L;;;;100000;N;;;;; 2189;VULGAR FRACTION ZERO THIRDS;No;0;ON; 0030 2044 0033;;;0;N;;;;; 2190;LEFTWARDS ARROW;Sm;0;ON;;;;;N;LEFT ARROW;;;; 2191;UPWARDS ARROW;Sm;0;ON;;;;;N;UP ARROW;;;; 2192;RIGHTWARDS ARROW;Sm;0;ON;;;;;N;RIGHT ARROW;;;; 2193;DOWNWARDS ARROW;Sm;0;ON;;;;;N;DOWN ARROW;;;; 2194;LEFT RIGHT ARROW;Sm;0;ON;;;;;N;;;;; 2195;UP DOWN ARROW;So;0;ON;;;;;N;;;;; 2196;NORTH WEST ARROW;So;0;ON;;;;;N;UPPER LEFT ARROW;;;; 2197;NORTH EAST ARROW;So;0;ON;;;;;N;UPPER RIGHT ARROW;;;; 2198;SOUTH EAST ARROW;So;0;ON;;;;;N;LOWER RIGHT ARROW;;;; 2199;SOUTH WEST ARROW;So;0;ON;;;;;N;LOWER LEFT ARROW;;;; 219A;LEFTWARDS ARROW WITH STROKE;Sm;0;ON;2190 0338;;;;N;LEFT ARROW WITH STROKE;;;; 219B;RIGHTWARDS ARROW WITH STROKE;Sm;0;ON;2192 0338;;;;N;RIGHT ARROW WITH STROKE;;;; 219C;LEFTWARDS WAVE ARROW;So;0;ON;;;;;N;LEFT WAVE ARROW;;;; 219D;RIGHTWARDS WAVE ARROW;So;0;ON;;;;;N;RIGHT WAVE ARROW;;;; 219E;LEFTWARDS TWO HEADED ARROW;So;0;ON;;;;;N;LEFT TWO HEADED ARROW;;;; 219F;UPWARDS TWO HEADED ARROW;So;0;ON;;;;;N;UP TWO HEADED ARROW;;;; 21A0;RIGHTWARDS TWO HEADED ARROW;Sm;0;ON;;;;;N;RIGHT TWO HEADED ARROW;;;; 21A1;DOWNWARDS TWO HEADED ARROW;So;0;ON;;;;;N;DOWN TWO HEADED ARROW;;;; 21A2;LEFTWARDS ARROW WITH TAIL;So;0;ON;;;;;N;LEFT ARROW WITH TAIL;;;; 21A3;RIGHTWARDS ARROW WITH TAIL;Sm;0;ON;;;;;N;RIGHT ARROW WITH TAIL;;;; 21A4;LEFTWARDS ARROW FROM BAR;So;0;ON;;;;;N;LEFT ARROW FROM BAR;;;; 21A5;UPWARDS ARROW FROM BAR;So;0;ON;;;;;N;UP ARROW FROM BAR;;;; 21A6;RIGHTWARDS ARROW FROM BAR;Sm;0;ON;;;;;N;RIGHT ARROW FROM BAR;;;; 21A7;DOWNWARDS ARROW FROM BAR;So;0;ON;;;;;N;DOWN ARROW FROM BAR;;;; 21A8;UP DOWN ARROW WITH BASE;So;0;ON;;;;;N;;;;; 21A9;LEFTWARDS ARROW WITH HOOK;So;0;ON;;;;;N;LEFT ARROW WITH HOOK;;;; 21AA;RIGHTWARDS ARROW WITH HOOK;So;0;ON;;;;;N;RIGHT ARROW WITH HOOK;;;; 21AB;LEFTWARDS ARROW WITH LOOP;So;0;ON;;;;;N;LEFT ARROW WITH LOOP;;;; 21AC;RIGHTWARDS ARROW WITH LOOP;So;0;ON;;;;;N;RIGHT ARROW WITH LOOP;;;; 21AD;LEFT RIGHT WAVE ARROW;So;0;ON;;;;;N;;;;; 21AE;LEFT RIGHT ARROW WITH STROKE;Sm;0;ON;2194 0338;;;;N;;;;; 21AF;DOWNWARDS ZIGZAG ARROW;So;0;ON;;;;;N;DOWN ZIGZAG ARROW;;;; 21B0;UPWARDS ARROW WITH TIP LEFTWARDS;So;0;ON;;;;;N;UP ARROW WITH TIP LEFT;;;; 21B1;UPWARDS ARROW WITH TIP RIGHTWARDS;So;0;ON;;;;;N;UP ARROW WITH TIP RIGHT;;;; 21B2;DOWNWARDS ARROW WITH TIP LEFTWARDS;So;0;ON;;;;;N;DOWN ARROW WITH TIP LEFT;;;; 21B3;DOWNWARDS ARROW WITH TIP RIGHTWARDS;So;0;ON;;;;;N;DOWN ARROW WITH TIP RIGHT;;;; 21B4;RIGHTWARDS ARROW WITH CORNER DOWNWARDS;So;0;ON;;;;;N;RIGHT ARROW WITH CORNER DOWN;;;; 21B5;DOWNWARDS ARROW WITH CORNER LEFTWARDS;So;0;ON;;;;;N;DOWN ARROW WITH CORNER LEFT;;;; 21B6;ANTICLOCKWISE TOP SEMICIRCLE ARROW;So;0;ON;;;;;N;;;;; 21B7;CLOCKWISE TOP SEMICIRCLE ARROW;So;0;ON;;;;;N;;;;; 21B8;NORTH WEST ARROW TO LONG BAR;So;0;ON;;;;;N;UPPER LEFT ARROW TO LONG BAR;;;; 21B9;LEFTWARDS ARROW TO BAR OVER RIGHTWARDS ARROW TO BAR;So;0;ON;;;;;N;LEFT ARROW TO BAR OVER RIGHT ARROW TO BAR;;;; 21BA;ANTICLOCKWISE OPEN CIRCLE ARROW;So;0;ON;;;;;N;;;;; 21BB;CLOCKWISE OPEN CIRCLE ARROW;So;0;ON;;;;;N;;;;; 21BC;LEFTWARDS HARPOON WITH BARB UPWARDS;So;0;ON;;;;;N;LEFT HARPOON WITH BARB UP;;;; 21BD;LEFTWARDS HARPOON WITH BARB DOWNWARDS;So;0;ON;;;;;N;LEFT HARPOON WITH BARB DOWN;;;; 21BE;UPWARDS HARPOON WITH BARB RIGHTWARDS;So;0;ON;;;;;N;UP HARPOON WITH BARB RIGHT;;;; 21BF;UPWARDS HARPOON WITH BARB LEFTWARDS;So;0;ON;;;;;N;UP HARPOON WITH BARB LEFT;;;; 21C0;RIGHTWARDS HARPOON WITH BARB UPWARDS;So;0;ON;;;;;N;RIGHT HARPOON WITH BARB UP;;;; 21C1;RIGHTWARDS HARPOON WITH BARB DOWNWARDS;So;0;ON;;;;;N;RIGHT HARPOON WITH BARB DOWN;;;; 21C2;DOWNWARDS HARPOON WITH BARB RIGHTWARDS;So;0;ON;;;;;N;DOWN HARPOON WITH BARB RIGHT;;;; 21C3;DOWNWARDS HARPOON WITH BARB LEFTWARDS;So;0;ON;;;;;N;DOWN HARPOON WITH BARB LEFT;;;; 21C4;RIGHTWARDS ARROW OVER LEFTWARDS ARROW;So;0;ON;;;;;N;RIGHT ARROW OVER LEFT ARROW;;;; 21C5;UPWARDS ARROW LEFTWARDS OF DOWNWARDS ARROW;So;0;ON;;;;;N;UP ARROW LEFT OF DOWN ARROW;;;; 21C6;LEFTWARDS ARROW OVER RIGHTWARDS ARROW;So;0;ON;;;;;N;LEFT ARROW OVER RIGHT ARROW;;;; 21C7;LEFTWARDS PAIRED ARROWS;So;0;ON;;;;;N;LEFT PAIRED ARROWS;;;; 21C8;UPWARDS PAIRED ARROWS;So;0;ON;;;;;N;UP PAIRED ARROWS;;;; 21C9;RIGHTWARDS PAIRED ARROWS;So;0;ON;;;;;N;RIGHT PAIRED ARROWS;;;; 21CA;DOWNWARDS PAIRED ARROWS;So;0;ON;;;;;N;DOWN PAIRED ARROWS;;;; 21CB;LEFTWARDS HARPOON OVER RIGHTWARDS HARPOON;So;0;ON;;;;;N;LEFT HARPOON OVER RIGHT HARPOON;;;; 21CC;RIGHTWARDS HARPOON OVER LEFTWARDS HARPOON;So;0;ON;;;;;N;RIGHT HARPOON OVER LEFT HARPOON;;;; 21CD;LEFTWARDS DOUBLE ARROW WITH STROKE;So;0;ON;21D0 0338;;;;N;LEFT DOUBLE ARROW WITH STROKE;;;; 21CE;LEFT RIGHT DOUBLE ARROW WITH STROKE;Sm;0;ON;21D4 0338;;;;N;;;;; 21CF;RIGHTWARDS DOUBLE ARROW WITH STROKE;Sm;0;ON;21D2 0338;;;;N;RIGHT DOUBLE ARROW WITH STROKE;;;; 21D0;LEFTWARDS DOUBLE ARROW;So;0;ON;;;;;N;LEFT DOUBLE ARROW;;;; 21D1;UPWARDS DOUBLE ARROW;So;0;ON;;;;;N;UP DOUBLE ARROW;;;; 21D2;RIGHTWARDS DOUBLE ARROW;Sm;0;ON;;;;;N;RIGHT DOUBLE ARROW;;;; 21D3;DOWNWARDS DOUBLE ARROW;So;0;ON;;;;;N;DOWN DOUBLE ARROW;;;; 21D4;LEFT RIGHT DOUBLE ARROW;Sm;0;ON;;;;;N;;;;; 21D5;UP DOWN DOUBLE ARROW;So;0;ON;;;;;N;;;;; 21D6;NORTH WEST DOUBLE ARROW;So;0;ON;;;;;N;UPPER LEFT DOUBLE ARROW;;;; 21D7;NORTH EAST DOUBLE ARROW;So;0;ON;;;;;N;UPPER RIGHT DOUBLE ARROW;;;; 21D8;SOUTH EAST DOUBLE ARROW;So;0;ON;;;;;N;LOWER RIGHT DOUBLE ARROW;;;; 21D9;SOUTH WEST DOUBLE ARROW;So;0;ON;;;;;N;LOWER LEFT DOUBLE ARROW;;;; 21DA;LEFTWARDS TRIPLE ARROW;So;0;ON;;;;;N;LEFT TRIPLE ARROW;;;; 21DB;RIGHTWARDS TRIPLE ARROW;So;0;ON;;;;;N;RIGHT TRIPLE ARROW;;;; 21DC;LEFTWARDS SQUIGGLE ARROW;So;0;ON;;;;;N;LEFT SQUIGGLE ARROW;;;; 21DD;RIGHTWARDS SQUIGGLE ARROW;So;0;ON;;;;;N;RIGHT SQUIGGLE ARROW;;;; 21DE;UPWARDS ARROW WITH DOUBLE STROKE;So;0;ON;;;;;N;UP ARROW WITH DOUBLE STROKE;;;; 21DF;DOWNWARDS ARROW WITH DOUBLE STROKE;So;0;ON;;;;;N;DOWN ARROW WITH DOUBLE STROKE;;;; 21E0;LEFTWARDS DASHED ARROW;So;0;ON;;;;;N;LEFT DASHED ARROW;;;; 21E1;UPWARDS DASHED ARROW;So;0;ON;;;;;N;UP DASHED ARROW;;;; 21E2;RIGHTWARDS DASHED ARROW;So;0;ON;;;;;N;RIGHT DASHED ARROW;;;; 21E3;DOWNWARDS DASHED ARROW;So;0;ON;;;;;N;DOWN DASHED ARROW;;;; 21E4;LEFTWARDS ARROW TO BAR;So;0;ON;;;;;N;LEFT ARROW TO BAR;;;; 21E5;RIGHTWARDS ARROW TO BAR;So;0;ON;;;;;N;RIGHT ARROW TO BAR;;;; 21E6;LEFTWARDS WHITE ARROW;So;0;ON;;;;;N;WHITE LEFT ARROW;;;; 21E7;UPWARDS WHITE ARROW;So;0;ON;;;;;N;WHITE UP ARROW;;;; 21E8;RIGHTWARDS WHITE ARROW;So;0;ON;;;;;N;WHITE RIGHT ARROW;;;; 21E9;DOWNWARDS WHITE ARROW;So;0;ON;;;;;N;WHITE DOWN ARROW;;;; 21EA;UPWARDS WHITE ARROW FROM BAR;So;0;ON;;;;;N;WHITE UP ARROW FROM BAR;;;; 21EB;UPWARDS WHITE ARROW ON PEDESTAL;So;0;ON;;;;;N;;;;; 21EC;UPWARDS WHITE ARROW ON PEDESTAL WITH HORIZONTAL BAR;So;0;ON;;;;;N;;;;; 21ED;UPWARDS WHITE ARROW ON PEDESTAL WITH VERTICAL BAR;So;0;ON;;;;;N;;;;; 21EE;UPWARDS WHITE DOUBLE ARROW;So;0;ON;;;;;N;;;;; 21EF;UPWARDS WHITE DOUBLE ARROW ON PEDESTAL;So;0;ON;;;;;N;;;;; 21F0;RIGHTWARDS WHITE ARROW FROM WALL;So;0;ON;;;;;N;;;;; 21F1;NORTH WEST ARROW TO CORNER;So;0;ON;;;;;N;;;;; 21F2;SOUTH EAST ARROW TO CORNER;So;0;ON;;;;;N;;;;; 21F3;UP DOWN WHITE ARROW;So;0;ON;;;;;N;;;;; 21F4;RIGHT ARROW WITH SMALL CIRCLE;Sm;0;ON;;;;;N;;;;; 21F5;DOWNWARDS ARROW LEFTWARDS OF UPWARDS ARROW;Sm;0;ON;;;;;N;;;;; 21F6;THREE RIGHTWARDS ARROWS;Sm;0;ON;;;;;N;;;;; 21F7;LEFTWARDS ARROW WITH VERTICAL STROKE;Sm;0;ON;;;;;N;;;;; 21F8;RIGHTWARDS ARROW WITH VERTICAL STROKE;Sm;0;ON;;;;;N;;;;; 21F9;LEFT RIGHT ARROW WITH VERTICAL STROKE;Sm;0;ON;;;;;N;;;;; 21FA;LEFTWARDS ARROW WITH DOUBLE VERTICAL STROKE;Sm;0;ON;;;;;N;;;;; 21FB;RIGHTWARDS ARROW WITH DOUBLE VERTICAL STROKE;Sm;0;ON;;;;;N;;;;; 21FC;LEFT RIGHT ARROW WITH DOUBLE VERTICAL STROKE;Sm;0;ON;;;;;N;;;;; 21FD;LEFTWARDS OPEN-HEADED ARROW;Sm;0;ON;;;;;N;;;;; 21FE;RIGHTWARDS OPEN-HEADED ARROW;Sm;0;ON;;;;;N;;;;; 21FF;LEFT RIGHT OPEN-HEADED ARROW;Sm;0;ON;;;;;N;;;;; 2200;FOR ALL;Sm;0;ON;;;;;N;;;;; 2201;COMPLEMENT;Sm;0;ON;;;;;Y;;;;; 2202;PARTIAL DIFFERENTIAL;Sm;0;ON;;;;;Y;;;;; 2203;THERE EXISTS;Sm;0;ON;;;;;Y;;;;; 2204;THERE DOES NOT EXIST;Sm;0;ON;2203 0338;;;;Y;;;;; 2205;EMPTY SET;Sm;0;ON;;;;;N;;;;; 2206;INCREMENT;Sm;0;ON;;;;;N;;;;; 2207;NABLA;Sm;0;ON;;;;;N;;;;; 2208;ELEMENT OF;Sm;0;ON;;;;;Y;;;;; 2209;NOT AN ELEMENT OF;Sm;0;ON;2208 0338;;;;Y;;;;; 220A;SMALL ELEMENT OF;Sm;0;ON;;;;;Y;;;;; 220B;CONTAINS AS MEMBER;Sm;0;ON;;;;;Y;;;;; 220C;DOES NOT CONTAIN AS MEMBER;Sm;0;ON;220B 0338;;;;Y;;;;; 220D;SMALL CONTAINS AS MEMBER;Sm;0;ON;;;;;Y;;;;; 220E;END OF PROOF;Sm;0;ON;;;;;N;;;;; 220F;N-ARY PRODUCT;Sm;0;ON;;;;;N;;;;; 2210;N-ARY COPRODUCT;Sm;0;ON;;;;;N;;;;; 2211;N-ARY SUMMATION;Sm;0;ON;;;;;Y;;;;; 2212;MINUS SIGN;Sm;0;ES;;;;;N;;;;; 2213;MINUS-OR-PLUS SIGN;Sm;0;ET;;;;;N;;;;; 2214;DOT PLUS;Sm;0;ON;;;;;N;;;;; 2215;DIVISION SLASH;Sm;0;ON;;;;;Y;;;;; 2216;SET MINUS;Sm;0;ON;;;;;Y;;;;; 2217;ASTERISK OPERATOR;Sm;0;ON;;;;;N;;;;; 2218;RING OPERATOR;Sm;0;ON;;;;;N;;;;; 2219;BULLET OPERATOR;Sm;0;ON;;;;;N;;;;; 221A;SQUARE ROOT;Sm;0;ON;;;;;Y;;;;; 221B;CUBE ROOT;Sm;0;ON;;;;;Y;;;;; 221C;FOURTH ROOT;Sm;0;ON;;;;;Y;;;;; 221D;PROPORTIONAL TO;Sm;0;ON;;;;;Y;;;;; 221E;INFINITY;Sm;0;ON;;;;;N;;;;; 221F;RIGHT ANGLE;Sm;0;ON;;;;;Y;;;;; 2220;ANGLE;Sm;0;ON;;;;;Y;;;;; 2221;MEASURED ANGLE;Sm;0;ON;;;;;Y;;;;; 2222;SPHERICAL ANGLE;Sm;0;ON;;;;;Y;;;;; 2223;DIVIDES;Sm;0;ON;;;;;N;;;;; 2224;DOES NOT DIVIDE;Sm;0;ON;2223 0338;;;;Y;;;;; 2225;PARALLEL TO;Sm;0;ON;;;;;N;;;;; 2226;NOT PARALLEL TO;Sm;0;ON;2225 0338;;;;Y;;;;; 2227;LOGICAL AND;Sm;0;ON;;;;;N;;;;; 2228;LOGICAL OR;Sm;0;ON;;;;;N;;;;; 2229;INTERSECTION;Sm;0;ON;;;;;N;;;;; 222A;UNION;Sm;0;ON;;;;;N;;;;; 222B;INTEGRAL;Sm;0;ON;;;;;Y;;;;; 222C;DOUBLE INTEGRAL;Sm;0;ON; 222B 222B;;;;Y;;;;; 222D;TRIPLE INTEGRAL;Sm;0;ON; 222B 222B 222B;;;;Y;;;;; 222E;CONTOUR INTEGRAL;Sm;0;ON;;;;;Y;;;;; 222F;SURFACE INTEGRAL;Sm;0;ON; 222E 222E;;;;Y;;;;; 2230;VOLUME INTEGRAL;Sm;0;ON; 222E 222E 222E;;;;Y;;;;; 2231;CLOCKWISE INTEGRAL;Sm;0;ON;;;;;Y;;;;; 2232;CLOCKWISE CONTOUR INTEGRAL;Sm;0;ON;;;;;Y;;;;; 2233;ANTICLOCKWISE CONTOUR INTEGRAL;Sm;0;ON;;;;;Y;;;;; 2234;THEREFORE;Sm;0;ON;;;;;N;;;;; 2235;BECAUSE;Sm;0;ON;;;;;N;;;;; 2236;RATIO;Sm;0;ON;;;;;N;;;;; 2237;PROPORTION;Sm;0;ON;;;;;N;;;;; 2238;DOT MINUS;Sm;0;ON;;;;;N;;;;; 2239;EXCESS;Sm;0;ON;;;;;Y;;;;; 223A;GEOMETRIC PROPORTION;Sm;0;ON;;;;;N;;;;; 223B;HOMOTHETIC;Sm;0;ON;;;;;Y;;;;; 223C;TILDE OPERATOR;Sm;0;ON;;;;;Y;;;;; 223D;REVERSED TILDE;Sm;0;ON;;;;;Y;;;;; 223E;INVERTED LAZY S;Sm;0;ON;;;;;Y;;;;; 223F;SINE WAVE;Sm;0;ON;;;;;Y;;;;; 2240;WREATH PRODUCT;Sm;0;ON;;;;;Y;;;;; 2241;NOT TILDE;Sm;0;ON;223C 0338;;;;Y;;;;; 2242;MINUS TILDE;Sm;0;ON;;;;;Y;;;;; 2243;ASYMPTOTICALLY EQUAL TO;Sm;0;ON;;;;;Y;;;;; 2244;NOT ASYMPTOTICALLY EQUAL TO;Sm;0;ON;2243 0338;;;;Y;;;;; 2245;APPROXIMATELY EQUAL TO;Sm;0;ON;;;;;Y;;;;; 2246;APPROXIMATELY BUT NOT ACTUALLY EQUAL TO;Sm;0;ON;;;;;Y;;;;; 2247;NEITHER APPROXIMATELY NOR ACTUALLY EQUAL TO;Sm;0;ON;2245 0338;;;;Y;;;;; 2248;ALMOST EQUAL TO;Sm;0;ON;;;;;Y;;;;; 2249;NOT ALMOST EQUAL TO;Sm;0;ON;2248 0338;;;;Y;;;;; 224A;ALMOST EQUAL OR EQUAL TO;Sm;0;ON;;;;;Y;;;;; 224B;TRIPLE TILDE;Sm;0;ON;;;;;Y;;;;; 224C;ALL EQUAL TO;Sm;0;ON;;;;;Y;;;;; 224D;EQUIVALENT TO;Sm;0;ON;;;;;N;;;;; 224E;GEOMETRICALLY EQUIVALENT TO;Sm;0;ON;;;;;N;;;;; 224F;DIFFERENCE BETWEEN;Sm;0;ON;;;;;N;;;;; 2250;APPROACHES THE LIMIT;Sm;0;ON;;;;;N;;;;; 2251;GEOMETRICALLY EQUAL TO;Sm;0;ON;;;;;N;;;;; 2252;APPROXIMATELY EQUAL TO OR THE IMAGE OF;Sm;0;ON;;;;;Y;;;;; 2253;IMAGE OF OR APPROXIMATELY EQUAL TO;Sm;0;ON;;;;;Y;;;;; 2254;COLON EQUALS;Sm;0;ON;;;;;Y;COLON EQUAL;;;; 2255;EQUALS COLON;Sm;0;ON;;;;;Y;EQUAL COLON;;;; 2256;RING IN EQUAL TO;Sm;0;ON;;;;;N;;;;; 2257;RING EQUAL TO;Sm;0;ON;;;;;N;;;;; 2258;CORRESPONDS TO;Sm;0;ON;;;;;N;;;;; 2259;ESTIMATES;Sm;0;ON;;;;;N;;;;; 225A;EQUIANGULAR TO;Sm;0;ON;;;;;N;;;;; 225B;STAR EQUALS;Sm;0;ON;;;;;N;;;;; 225C;DELTA EQUAL TO;Sm;0;ON;;;;;N;;;;; 225D;EQUAL TO BY DEFINITION;Sm;0;ON;;;;;N;;;;; 225E;MEASURED BY;Sm;0;ON;;;;;N;;;;; 225F;QUESTIONED EQUAL TO;Sm;0;ON;;;;;Y;;;;; 2260;NOT EQUAL TO;Sm;0;ON;003D 0338;;;;Y;;;;; 2261;IDENTICAL TO;Sm;0;ON;;;;;N;;;;; 2262;NOT IDENTICAL TO;Sm;0;ON;2261 0338;;;;Y;;;;; 2263;STRICTLY EQUIVALENT TO;Sm;0;ON;;;;;N;;;;; 2264;LESS-THAN OR EQUAL TO;Sm;0;ON;;;;;Y;LESS THAN OR EQUAL TO;;;; 2265;GREATER-THAN OR EQUAL TO;Sm;0;ON;;;;;Y;GREATER THAN OR EQUAL TO;;;; 2266;LESS-THAN OVER EQUAL TO;Sm;0;ON;;;;;Y;LESS THAN OVER EQUAL TO;;;; 2267;GREATER-THAN OVER EQUAL TO;Sm;0;ON;;;;;Y;GREATER THAN OVER EQUAL TO;;;; 2268;LESS-THAN BUT NOT EQUAL TO;Sm;0;ON;;;;;Y;LESS THAN BUT NOT EQUAL TO;;;; 2269;GREATER-THAN BUT NOT EQUAL TO;Sm;0;ON;;;;;Y;GREATER THAN BUT NOT EQUAL TO;;;; 226A;MUCH LESS-THAN;Sm;0;ON;;;;;Y;MUCH LESS THAN;;;; 226B;MUCH GREATER-THAN;Sm;0;ON;;;;;Y;MUCH GREATER THAN;;;; 226C;BETWEEN;Sm;0;ON;;;;;N;;;;; 226D;NOT EQUIVALENT TO;Sm;0;ON;224D 0338;;;;N;;;;; 226E;NOT LESS-THAN;Sm;0;ON;003C 0338;;;;Y;NOT LESS THAN;;;; 226F;NOT GREATER-THAN;Sm;0;ON;003E 0338;;;;Y;NOT GREATER THAN;;;; 2270;NEITHER LESS-THAN NOR EQUAL TO;Sm;0;ON;2264 0338;;;;Y;NEITHER LESS THAN NOR EQUAL TO;;;; 2271;NEITHER GREATER-THAN NOR EQUAL TO;Sm;0;ON;2265 0338;;;;Y;NEITHER GREATER THAN NOR EQUAL TO;;;; 2272;LESS-THAN OR EQUIVALENT TO;Sm;0;ON;;;;;Y;LESS THAN OR EQUIVALENT TO;;;; 2273;GREATER-THAN OR EQUIVALENT TO;Sm;0;ON;;;;;Y;GREATER THAN OR EQUIVALENT TO;;;; 2274;NEITHER LESS-THAN NOR EQUIVALENT TO;Sm;0;ON;2272 0338;;;;Y;NEITHER LESS THAN NOR EQUIVALENT TO;;;; 2275;NEITHER GREATER-THAN NOR EQUIVALENT TO;Sm;0;ON;2273 0338;;;;Y;NEITHER GREATER THAN NOR EQUIVALENT TO;;;; 2276;LESS-THAN OR GREATER-THAN;Sm;0;ON;;;;;Y;LESS THAN OR GREATER THAN;;;; 2277;GREATER-THAN OR LESS-THAN;Sm;0;ON;;;;;Y;GREATER THAN OR LESS THAN;;;; 2278;NEITHER LESS-THAN NOR GREATER-THAN;Sm;0;ON;2276 0338;;;;Y;NEITHER LESS THAN NOR GREATER THAN;;;; 2279;NEITHER GREATER-THAN NOR LESS-THAN;Sm;0;ON;2277 0338;;;;Y;NEITHER GREATER THAN NOR LESS THAN;;;; 227A;PRECEDES;Sm;0;ON;;;;;Y;;;;; 227B;SUCCEEDS;Sm;0;ON;;;;;Y;;;;; 227C;PRECEDES OR EQUAL TO;Sm;0;ON;;;;;Y;;;;; 227D;SUCCEEDS OR EQUAL TO;Sm;0;ON;;;;;Y;;;;; 227E;PRECEDES OR EQUIVALENT TO;Sm;0;ON;;;;;Y;;;;; 227F;SUCCEEDS OR EQUIVALENT TO;Sm;0;ON;;;;;Y;;;;; 2280;DOES NOT PRECEDE;Sm;0;ON;227A 0338;;;;Y;;;;; 2281;DOES NOT SUCCEED;Sm;0;ON;227B 0338;;;;Y;;;;; 2282;SUBSET OF;Sm;0;ON;;;;;Y;;;;; 2283;SUPERSET OF;Sm;0;ON;;;;;Y;;;;; 2284;NOT A SUBSET OF;Sm;0;ON;2282 0338;;;;Y;;;;; 2285;NOT A SUPERSET OF;Sm;0;ON;2283 0338;;;;Y;;;;; 2286;SUBSET OF OR EQUAL TO;Sm;0;ON;;;;;Y;;;;; 2287;SUPERSET OF OR EQUAL TO;Sm;0;ON;;;;;Y;;;;; 2288;NEITHER A SUBSET OF NOR EQUAL TO;Sm;0;ON;2286 0338;;;;Y;;;;; 2289;NEITHER A SUPERSET OF NOR EQUAL TO;Sm;0;ON;2287 0338;;;;Y;;;;; 228A;SUBSET OF WITH NOT EQUAL TO;Sm;0;ON;;;;;Y;SUBSET OF OR NOT EQUAL TO;;;; 228B;SUPERSET OF WITH NOT EQUAL TO;Sm;0;ON;;;;;Y;SUPERSET OF OR NOT EQUAL TO;;;; 228C;MULTISET;Sm;0;ON;;;;;Y;;;;; 228D;MULTISET MULTIPLICATION;Sm;0;ON;;;;;N;;;;; 228E;MULTISET UNION;Sm;0;ON;;;;;N;;;;; 228F;SQUARE IMAGE OF;Sm;0;ON;;;;;Y;;;;; 2290;SQUARE ORIGINAL OF;Sm;0;ON;;;;;Y;;;;; 2291;SQUARE IMAGE OF OR EQUAL TO;Sm;0;ON;;;;;Y;;;;; 2292;SQUARE ORIGINAL OF OR EQUAL TO;Sm;0;ON;;;;;Y;;;;; 2293;SQUARE CAP;Sm;0;ON;;;;;N;;;;; 2294;SQUARE CUP;Sm;0;ON;;;;;N;;;;; 2295;CIRCLED PLUS;Sm;0;ON;;;;;N;;;;; 2296;CIRCLED MINUS;Sm;0;ON;;;;;N;;;;; 2297;CIRCLED TIMES;Sm;0;ON;;;;;N;;;;; 2298;CIRCLED DIVISION SLASH;Sm;0;ON;;;;;Y;;;;; 2299;CIRCLED DOT OPERATOR;Sm;0;ON;;;;;N;;;;; 229A;CIRCLED RING OPERATOR;Sm;0;ON;;;;;N;;;;; 229B;CIRCLED ASTERISK OPERATOR;Sm;0;ON;;;;;N;;;;; 229C;CIRCLED EQUALS;Sm;0;ON;;;;;N;;;;; 229D;CIRCLED DASH;Sm;0;ON;;;;;N;;;;; 229E;SQUARED PLUS;Sm;0;ON;;;;;N;;;;; 229F;SQUARED MINUS;Sm;0;ON;;;;;N;;;;; 22A0;SQUARED TIMES;Sm;0;ON;;;;;N;;;;; 22A1;SQUARED DOT OPERATOR;Sm;0;ON;;;;;N;;;;; 22A2;RIGHT TACK;Sm;0;ON;;;;;Y;;;;; 22A3;LEFT TACK;Sm;0;ON;;;;;Y;;;;; 22A4;DOWN TACK;Sm;0;ON;;;;;N;;;;; 22A5;UP TACK;Sm;0;ON;;;;;N;;;;; 22A6;ASSERTION;Sm;0;ON;;;;;Y;;;;; 22A7;MODELS;Sm;0;ON;;;;;Y;;;;; 22A8;TRUE;Sm;0;ON;;;;;Y;;;;; 22A9;FORCES;Sm;0;ON;;;;;Y;;;;; 22AA;TRIPLE VERTICAL BAR RIGHT TURNSTILE;Sm;0;ON;;;;;Y;;;;; 22AB;DOUBLE VERTICAL BAR DOUBLE RIGHT TURNSTILE;Sm;0;ON;;;;;Y;;;;; 22AC;DOES NOT PROVE;Sm;0;ON;22A2 0338;;;;Y;;;;; 22AD;NOT TRUE;Sm;0;ON;22A8 0338;;;;Y;;;;; 22AE;DOES NOT FORCE;Sm;0;ON;22A9 0338;;;;Y;;;;; 22AF;NEGATED DOUBLE VERTICAL BAR DOUBLE RIGHT TURNSTILE;Sm;0;ON;22AB 0338;;;;Y;;;;; 22B0;PRECEDES UNDER RELATION;Sm;0;ON;;;;;Y;;;;; 22B1;SUCCEEDS UNDER RELATION;Sm;0;ON;;;;;Y;;;;; 22B2;NORMAL SUBGROUP OF;Sm;0;ON;;;;;Y;;;;; 22B3;CONTAINS AS NORMAL SUBGROUP;Sm;0;ON;;;;;Y;;;;; 22B4;NORMAL SUBGROUP OF OR EQUAL TO;Sm;0;ON;;;;;Y;;;;; 22B5;CONTAINS AS NORMAL SUBGROUP OR EQUAL TO;Sm;0;ON;;;;;Y;;;;; 22B6;ORIGINAL OF;Sm;0;ON;;;;;Y;;;;; 22B7;IMAGE OF;Sm;0;ON;;;;;Y;;;;; 22B8;MULTIMAP;Sm;0;ON;;;;;Y;;;;; 22B9;HERMITIAN CONJUGATE MATRIX;Sm;0;ON;;;;;N;;;;; 22BA;INTERCALATE;Sm;0;ON;;;;;N;;;;; 22BB;XOR;Sm;0;ON;;;;;N;;;;; 22BC;NAND;Sm;0;ON;;;;;N;;;;; 22BD;NOR;Sm;0;ON;;;;;N;;;;; 22BE;RIGHT ANGLE WITH ARC;Sm;0;ON;;;;;Y;;;;; 22BF;RIGHT TRIANGLE;Sm;0;ON;;;;;Y;;;;; 22C0;N-ARY LOGICAL AND;Sm;0;ON;;;;;N;;;;; 22C1;N-ARY LOGICAL OR;Sm;0;ON;;;;;N;;;;; 22C2;N-ARY INTERSECTION;Sm;0;ON;;;;;N;;;;; 22C3;N-ARY UNION;Sm;0;ON;;;;;N;;;;; 22C4;DIAMOND OPERATOR;Sm;0;ON;;;;;N;;;;; 22C5;DOT OPERATOR;Sm;0;ON;;;;;N;;;;; 22C6;STAR OPERATOR;Sm;0;ON;;;;;N;;;;; 22C7;DIVISION TIMES;Sm;0;ON;;;;;N;;;;; 22C8;BOWTIE;Sm;0;ON;;;;;N;;;;; 22C9;LEFT NORMAL FACTOR SEMIDIRECT PRODUCT;Sm;0;ON;;;;;Y;;;;; 22CA;RIGHT NORMAL FACTOR SEMIDIRECT PRODUCT;Sm;0;ON;;;;;Y;;;;; 22CB;LEFT SEMIDIRECT PRODUCT;Sm;0;ON;;;;;Y;;;;; 22CC;RIGHT SEMIDIRECT PRODUCT;Sm;0;ON;;;;;Y;;;;; 22CD;REVERSED TILDE EQUALS;Sm;0;ON;;;;;Y;;;;; 22CE;CURLY LOGICAL OR;Sm;0;ON;;;;;N;;;;; 22CF;CURLY LOGICAL AND;Sm;0;ON;;;;;N;;;;; 22D0;DOUBLE SUBSET;Sm;0;ON;;;;;Y;;;;; 22D1;DOUBLE SUPERSET;Sm;0;ON;;;;;Y;;;;; 22D2;DOUBLE INTERSECTION;Sm;0;ON;;;;;N;;;;; 22D3;DOUBLE UNION;Sm;0;ON;;;;;N;;;;; 22D4;PITCHFORK;Sm;0;ON;;;;;N;;;;; 22D5;EQUAL AND PARALLEL TO;Sm;0;ON;;;;;N;;;;; 22D6;LESS-THAN WITH DOT;Sm;0;ON;;;;;Y;LESS THAN WITH DOT;;;; 22D7;GREATER-THAN WITH DOT;Sm;0;ON;;;;;Y;GREATER THAN WITH DOT;;;; 22D8;VERY MUCH LESS-THAN;Sm;0;ON;;;;;Y;VERY MUCH LESS THAN;;;; 22D9;VERY MUCH GREATER-THAN;Sm;0;ON;;;;;Y;VERY MUCH GREATER THAN;;;; 22DA;LESS-THAN EQUAL TO OR GREATER-THAN;Sm;0;ON;;;;;Y;LESS THAN EQUAL TO OR GREATER THAN;;;; 22DB;GREATER-THAN EQUAL TO OR LESS-THAN;Sm;0;ON;;;;;Y;GREATER THAN EQUAL TO OR LESS THAN;;;; 22DC;EQUAL TO OR LESS-THAN;Sm;0;ON;;;;;Y;EQUAL TO OR LESS THAN;;;; 22DD;EQUAL TO OR GREATER-THAN;Sm;0;ON;;;;;Y;EQUAL TO OR GREATER THAN;;;; 22DE;EQUAL TO OR PRECEDES;Sm;0;ON;;;;;Y;;;;; 22DF;EQUAL TO OR SUCCEEDS;Sm;0;ON;;;;;Y;;;;; 22E0;DOES NOT PRECEDE OR EQUAL;Sm;0;ON;227C 0338;;;;Y;;;;; 22E1;DOES NOT SUCCEED OR EQUAL;Sm;0;ON;227D 0338;;;;Y;;;;; 22E2;NOT SQUARE IMAGE OF OR EQUAL TO;Sm;0;ON;2291 0338;;;;Y;;;;; 22E3;NOT SQUARE ORIGINAL OF OR EQUAL TO;Sm;0;ON;2292 0338;;;;Y;;;;; 22E4;SQUARE IMAGE OF OR NOT EQUAL TO;Sm;0;ON;;;;;Y;;;;; 22E5;SQUARE ORIGINAL OF OR NOT EQUAL TO;Sm;0;ON;;;;;Y;;;;; 22E6;LESS-THAN BUT NOT EQUIVALENT TO;Sm;0;ON;;;;;Y;LESS THAN BUT NOT EQUIVALENT TO;;;; 22E7;GREATER-THAN BUT NOT EQUIVALENT TO;Sm;0;ON;;;;;Y;GREATER THAN BUT NOT EQUIVALENT TO;;;; 22E8;PRECEDES BUT NOT EQUIVALENT TO;Sm;0;ON;;;;;Y;;;;; 22E9;SUCCEEDS BUT NOT EQUIVALENT TO;Sm;0;ON;;;;;Y;;;;; 22EA;NOT NORMAL SUBGROUP OF;Sm;0;ON;22B2 0338;;;;Y;;;;; 22EB;DOES NOT CONTAIN AS NORMAL SUBGROUP;Sm;0;ON;22B3 0338;;;;Y;;;;; 22EC;NOT NORMAL SUBGROUP OF OR EQUAL TO;Sm;0;ON;22B4 0338;;;;Y;;;;; 22ED;DOES NOT CONTAIN AS NORMAL SUBGROUP OR EQUAL;Sm;0;ON;22B5 0338;;;;Y;;;;; 22EE;VERTICAL ELLIPSIS;Sm;0;ON;;;;;N;;;;; 22EF;MIDLINE HORIZONTAL ELLIPSIS;Sm;0;ON;;;;;N;;;;; 22F0;UP RIGHT DIAGONAL ELLIPSIS;Sm;0;ON;;;;;Y;;;;; 22F1;DOWN RIGHT DIAGONAL ELLIPSIS;Sm;0;ON;;;;;Y;;;;; 22F2;ELEMENT OF WITH LONG HORIZONTAL STROKE;Sm;0;ON;;;;;Y;;;;; 22F3;ELEMENT OF WITH VERTICAL BAR AT END OF HORIZONTAL STROKE;Sm;0;ON;;;;;Y;;;;; 22F4;SMALL ELEMENT OF WITH VERTICAL BAR AT END OF HORIZONTAL STROKE;Sm;0;ON;;;;;Y;;;;; 22F5;ELEMENT OF WITH DOT ABOVE;Sm;0;ON;;;;;Y;;;;; 22F6;ELEMENT OF WITH OVERBAR;Sm;0;ON;;;;;Y;;;;; 22F7;SMALL ELEMENT OF WITH OVERBAR;Sm;0;ON;;;;;Y;;;;; 22F8;ELEMENT OF WITH UNDERBAR;Sm;0;ON;;;;;Y;;;;; 22F9;ELEMENT OF WITH TWO HORIZONTAL STROKES;Sm;0;ON;;;;;Y;;;;; 22FA;CONTAINS WITH LONG HORIZONTAL STROKE;Sm;0;ON;;;;;Y;;;;; 22FB;CONTAINS WITH VERTICAL BAR AT END OF HORIZONTAL STROKE;Sm;0;ON;;;;;Y;;;;; 22FC;SMALL CONTAINS WITH VERTICAL BAR AT END OF HORIZONTAL STROKE;Sm;0;ON;;;;;Y;;;;; 22FD;CONTAINS WITH OVERBAR;Sm;0;ON;;;;;Y;;;;; 22FE;SMALL CONTAINS WITH OVERBAR;Sm;0;ON;;;;;Y;;;;; 22FF;Z NOTATION BAG MEMBERSHIP;Sm;0;ON;;;;;Y;;;;; 2300;DIAMETER SIGN;So;0;ON;;;;;N;;;;; 2301;ELECTRIC ARROW;So;0;ON;;;;;N;;;;; 2302;HOUSE;So;0;ON;;;;;N;;;;; 2303;UP ARROWHEAD;So;0;ON;;;;;N;;;;; 2304;DOWN ARROWHEAD;So;0;ON;;;;;N;;;;; 2305;PROJECTIVE;So;0;ON;;;;;N;;;;; 2306;PERSPECTIVE;So;0;ON;;;;;N;;;;; 2307;WAVY LINE;So;0;ON;;;;;N;;;;; 2308;LEFT CEILING;Ps;0;ON;;;;;Y;;;;; 2309;RIGHT CEILING;Pe;0;ON;;;;;Y;;;;; 230A;LEFT FLOOR;Ps;0;ON;;;;;Y;;;;; 230B;RIGHT FLOOR;Pe;0;ON;;;;;Y;;;;; 230C;BOTTOM RIGHT CROP;So;0;ON;;;;;N;;;;; 230D;BOTTOM LEFT CROP;So;0;ON;;;;;N;;;;; 230E;TOP RIGHT CROP;So;0;ON;;;;;N;;;;; 230F;TOP LEFT CROP;So;0;ON;;;;;N;;;;; 2310;REVERSED NOT SIGN;So;0;ON;;;;;N;;;;; 2311;SQUARE LOZENGE;So;0;ON;;;;;N;;;;; 2312;ARC;So;0;ON;;;;;N;;;;; 2313;SEGMENT;So;0;ON;;;;;N;;;;; 2314;SECTOR;So;0;ON;;;;;N;;;;; 2315;TELEPHONE RECORDER;So;0;ON;;;;;N;;;;; 2316;POSITION INDICATOR;So;0;ON;;;;;N;;;;; 2317;VIEWDATA SQUARE;So;0;ON;;;;;N;;;;; 2318;PLACE OF INTEREST SIGN;So;0;ON;;;;;N;COMMAND KEY;;;; 2319;TURNED NOT SIGN;So;0;ON;;;;;N;;;;; 231A;WATCH;So;0;ON;;;;;N;;;;; 231B;HOURGLASS;So;0;ON;;;;;N;;;;; 231C;TOP LEFT CORNER;So;0;ON;;;;;N;;;;; 231D;TOP RIGHT CORNER;So;0;ON;;;;;N;;;;; 231E;BOTTOM LEFT CORNER;So;0;ON;;;;;N;;;;; 231F;BOTTOM RIGHT CORNER;So;0;ON;;;;;N;;;;; 2320;TOP HALF INTEGRAL;Sm;0;ON;;;;;Y;;;;; 2321;BOTTOM HALF INTEGRAL;Sm;0;ON;;;;;Y;;;;; 2322;FROWN;So;0;ON;;;;;N;;;;; 2323;SMILE;So;0;ON;;;;;N;;;;; 2324;UP ARROWHEAD BETWEEN TWO HORIZONTAL BARS;So;0;ON;;;;;N;ENTER KEY;;;; 2325;OPTION KEY;So;0;ON;;;;;N;;;;; 2326;ERASE TO THE RIGHT;So;0;ON;;;;;N;DELETE TO THE RIGHT KEY;;;; 2327;X IN A RECTANGLE BOX;So;0;ON;;;;;N;CLEAR KEY;;;; 2328;KEYBOARD;So;0;ON;;;;;N;;;;; 2329;LEFT-POINTING ANGLE BRACKET;Ps;0;ON;3008;;;;Y;BRA;;;; 232A;RIGHT-POINTING ANGLE BRACKET;Pe;0;ON;3009;;;;Y;KET;;;; 232B;ERASE TO THE LEFT;So;0;ON;;;;;N;DELETE TO THE LEFT KEY;;;; 232C;BENZENE RING;So;0;ON;;;;;N;;;;; 232D;CYLINDRICITY;So;0;ON;;;;;N;;;;; 232E;ALL AROUND-PROFILE;So;0;ON;;;;;N;;;;; 232F;SYMMETRY;So;0;ON;;;;;N;;;;; 2330;TOTAL RUNOUT;So;0;ON;;;;;N;;;;; 2331;DIMENSION ORIGIN;So;0;ON;;;;;N;;;;; 2332;CONICAL TAPER;So;0;ON;;;;;N;;;;; 2333;SLOPE;So;0;ON;;;;;N;;;;; 2334;COUNTERBORE;So;0;ON;;;;;N;;;;; 2335;COUNTERSINK;So;0;ON;;;;;N;;;;; 2336;APL FUNCTIONAL SYMBOL I-BEAM;So;0;L;;;;;N;;;;; 2337;APL FUNCTIONAL SYMBOL SQUISH QUAD;So;0;L;;;;;N;;;;; 2338;APL FUNCTIONAL SYMBOL QUAD EQUAL;So;0;L;;;;;N;;;;; 2339;APL FUNCTIONAL SYMBOL QUAD DIVIDE;So;0;L;;;;;N;;;;; 233A;APL FUNCTIONAL SYMBOL QUAD DIAMOND;So;0;L;;;;;N;;;;; 233B;APL FUNCTIONAL SYMBOL QUAD JOT;So;0;L;;;;;N;;;;; 233C;APL FUNCTIONAL SYMBOL QUAD CIRCLE;So;0;L;;;;;N;;;;; 233D;APL FUNCTIONAL SYMBOL CIRCLE STILE;So;0;L;;;;;N;;;;; 233E;APL FUNCTIONAL SYMBOL CIRCLE JOT;So;0;L;;;;;N;;;;; 233F;APL FUNCTIONAL SYMBOL SLASH BAR;So;0;L;;;;;N;;;;; 2340;APL FUNCTIONAL SYMBOL BACKSLASH BAR;So;0;L;;;;;N;;;;; 2341;APL FUNCTIONAL SYMBOL QUAD SLASH;So;0;L;;;;;N;;;;; 2342;APL FUNCTIONAL SYMBOL QUAD BACKSLASH;So;0;L;;;;;N;;;;; 2343;APL FUNCTIONAL SYMBOL QUAD LESS-THAN;So;0;L;;;;;N;;;;; 2344;APL FUNCTIONAL SYMBOL QUAD GREATER-THAN;So;0;L;;;;;N;;;;; 2345;APL FUNCTIONAL SYMBOL LEFTWARDS VANE;So;0;L;;;;;N;;;;; 2346;APL FUNCTIONAL SYMBOL RIGHTWARDS VANE;So;0;L;;;;;N;;;;; 2347;APL FUNCTIONAL SYMBOL QUAD LEFTWARDS ARROW;So;0;L;;;;;N;;;;; 2348;APL FUNCTIONAL SYMBOL QUAD RIGHTWARDS ARROW;So;0;L;;;;;N;;;;; 2349;APL FUNCTIONAL SYMBOL CIRCLE BACKSLASH;So;0;L;;;;;N;;;;; 234A;APL FUNCTIONAL SYMBOL DOWN TACK UNDERBAR;So;0;L;;;;;N;;;;; 234B;APL FUNCTIONAL SYMBOL DELTA STILE;So;0;L;;;;;N;;;;; 234C;APL FUNCTIONAL SYMBOL QUAD DOWN CARET;So;0;L;;;;;N;;;;; 234D;APL FUNCTIONAL SYMBOL QUAD DELTA;So;0;L;;;;;N;;;;; 234E;APL FUNCTIONAL SYMBOL DOWN TACK JOT;So;0;L;;;;;N;;;;; 234F;APL FUNCTIONAL SYMBOL UPWARDS VANE;So;0;L;;;;;N;;;;; 2350;APL FUNCTIONAL SYMBOL QUAD UPWARDS ARROW;So;0;L;;;;;N;;;;; 2351;APL FUNCTIONAL SYMBOL UP TACK OVERBAR;So;0;L;;;;;N;;;;; 2352;APL FUNCTIONAL SYMBOL DEL STILE;So;0;L;;;;;N;;;;; 2353;APL FUNCTIONAL SYMBOL QUAD UP CARET;So;0;L;;;;;N;;;;; 2354;APL FUNCTIONAL SYMBOL QUAD DEL;So;0;L;;;;;N;;;;; 2355;APL FUNCTIONAL SYMBOL UP TACK JOT;So;0;L;;;;;N;;;;; 2356;APL FUNCTIONAL SYMBOL DOWNWARDS VANE;So;0;L;;;;;N;;;;; 2357;APL FUNCTIONAL SYMBOL QUAD DOWNWARDS ARROW;So;0;L;;;;;N;;;;; 2358;APL FUNCTIONAL SYMBOL QUOTE UNDERBAR;So;0;L;;;;;N;;;;; 2359;APL FUNCTIONAL SYMBOL DELTA UNDERBAR;So;0;L;;;;;N;;;;; 235A;APL FUNCTIONAL SYMBOL DIAMOND UNDERBAR;So;0;L;;;;;N;;;;; 235B;APL FUNCTIONAL SYMBOL JOT UNDERBAR;So;0;L;;;;;N;;;;; 235C;APL FUNCTIONAL SYMBOL CIRCLE UNDERBAR;So;0;L;;;;;N;;;;; 235D;APL FUNCTIONAL SYMBOL UP SHOE JOT;So;0;L;;;;;N;;;;; 235E;APL FUNCTIONAL SYMBOL QUOTE QUAD;So;0;L;;;;;N;;;;; 235F;APL FUNCTIONAL SYMBOL CIRCLE STAR;So;0;L;;;;;N;;;;; 2360;APL FUNCTIONAL SYMBOL QUAD COLON;So;0;L;;;;;N;;;;; 2361;APL FUNCTIONAL SYMBOL UP TACK DIAERESIS;So;0;L;;;;;N;;;;; 2362;APL FUNCTIONAL SYMBOL DEL DIAERESIS;So;0;L;;;;;N;;;;; 2363;APL FUNCTIONAL SYMBOL STAR DIAERESIS;So;0;L;;;;;N;;;;; 2364;APL FUNCTIONAL SYMBOL JOT DIAERESIS;So;0;L;;;;;N;;;;; 2365;APL FUNCTIONAL SYMBOL CIRCLE DIAERESIS;So;0;L;;;;;N;;;;; 2366;APL FUNCTIONAL SYMBOL DOWN SHOE STILE;So;0;L;;;;;N;;;;; 2367;APL FUNCTIONAL SYMBOL LEFT SHOE STILE;So;0;L;;;;;N;;;;; 2368;APL FUNCTIONAL SYMBOL TILDE DIAERESIS;So;0;L;;;;;N;;;;; 2369;APL FUNCTIONAL SYMBOL GREATER-THAN DIAERESIS;So;0;L;;;;;N;;;;; 236A;APL FUNCTIONAL SYMBOL COMMA BAR;So;0;L;;;;;N;;;;; 236B;APL FUNCTIONAL SYMBOL DEL TILDE;So;0;L;;;;;N;;;;; 236C;APL FUNCTIONAL SYMBOL ZILDE;So;0;L;;;;;N;;;;; 236D;APL FUNCTIONAL SYMBOL STILE TILDE;So;0;L;;;;;N;;;;; 236E;APL FUNCTIONAL SYMBOL SEMICOLON UNDERBAR;So;0;L;;;;;N;;;;; 236F;APL FUNCTIONAL SYMBOL QUAD NOT EQUAL;So;0;L;;;;;N;;;;; 2370;APL FUNCTIONAL SYMBOL QUAD QUESTION;So;0;L;;;;;N;;;;; 2371;APL FUNCTIONAL SYMBOL DOWN CARET TILDE;So;0;L;;;;;N;;;;; 2372;APL FUNCTIONAL SYMBOL UP CARET TILDE;So;0;L;;;;;N;;;;; 2373;APL FUNCTIONAL SYMBOL IOTA;So;0;L;;;;;N;;;;; 2374;APL FUNCTIONAL SYMBOL RHO;So;0;L;;;;;N;;;;; 2375;APL FUNCTIONAL SYMBOL OMEGA;So;0;L;;;;;N;;;;; 2376;APL FUNCTIONAL SYMBOL ALPHA UNDERBAR;So;0;L;;;;;N;;;;; 2377;APL FUNCTIONAL SYMBOL EPSILON UNDERBAR;So;0;L;;;;;N;;;;; 2378;APL FUNCTIONAL SYMBOL IOTA UNDERBAR;So;0;L;;;;;N;;;;; 2379;APL FUNCTIONAL SYMBOL OMEGA UNDERBAR;So;0;L;;;;;N;;;;; 237A;APL FUNCTIONAL SYMBOL ALPHA;So;0;L;;;;;N;;;;; 237B;NOT CHECK MARK;So;0;ON;;;;;N;;;;; 237C;RIGHT ANGLE WITH DOWNWARDS ZIGZAG ARROW;Sm;0;ON;;;;;N;;;;; 237D;SHOULDERED OPEN BOX;So;0;ON;;;;;N;;;;; 237E;BELL SYMBOL;So;0;ON;;;;;N;;;;; 237F;VERTICAL LINE WITH MIDDLE DOT;So;0;ON;;;;;N;;;;; 2380;INSERTION SYMBOL;So;0;ON;;;;;N;;;;; 2381;CONTINUOUS UNDERLINE SYMBOL;So;0;ON;;;;;N;;;;; 2382;DISCONTINUOUS UNDERLINE SYMBOL;So;0;ON;;;;;N;;;;; 2383;EMPHASIS SYMBOL;So;0;ON;;;;;N;;;;; 2384;COMPOSITION SYMBOL;So;0;ON;;;;;N;;;;; 2385;WHITE SQUARE WITH CENTRE VERTICAL LINE;So;0;ON;;;;;N;;;;; 2386;ENTER SYMBOL;So;0;ON;;;;;N;;;;; 2387;ALTERNATIVE KEY SYMBOL;So;0;ON;;;;;N;;;;; 2388;HELM SYMBOL;So;0;ON;;;;;N;;;;; 2389;CIRCLED HORIZONTAL BAR WITH NOTCH;So;0;ON;;;;;N;;;;; 238A;CIRCLED TRIANGLE DOWN;So;0;ON;;;;;N;;;;; 238B;BROKEN CIRCLE WITH NORTHWEST ARROW;So;0;ON;;;;;N;;;;; 238C;UNDO SYMBOL;So;0;ON;;;;;N;;;;; 238D;MONOSTABLE SYMBOL;So;0;ON;;;;;N;;;;; 238E;HYSTERESIS SYMBOL;So;0;ON;;;;;N;;;;; 238F;OPEN-CIRCUIT-OUTPUT H-TYPE SYMBOL;So;0;ON;;;;;N;;;;; 2390;OPEN-CIRCUIT-OUTPUT L-TYPE SYMBOL;So;0;ON;;;;;N;;;;; 2391;PASSIVE-PULL-DOWN-OUTPUT SYMBOL;So;0;ON;;;;;N;;;;; 2392;PASSIVE-PULL-UP-OUTPUT SYMBOL;So;0;ON;;;;;N;;;;; 2393;DIRECT CURRENT SYMBOL FORM TWO;So;0;ON;;;;;N;;;;; 2394;SOFTWARE-FUNCTION SYMBOL;So;0;ON;;;;;N;;;;; 2395;APL FUNCTIONAL SYMBOL QUAD;So;0;L;;;;;N;;;;; 2396;DECIMAL SEPARATOR KEY SYMBOL;So;0;ON;;;;;N;;;;; 2397;PREVIOUS PAGE;So;0;ON;;;;;N;;;;; 2398;NEXT PAGE;So;0;ON;;;;;N;;;;; 2399;PRINT SCREEN SYMBOL;So;0;ON;;;;;N;;;;; 239A;CLEAR SCREEN SYMBOL;So;0;ON;;;;;N;;;;; 239B;LEFT PARENTHESIS UPPER HOOK;Sm;0;ON;;;;;N;;;;; 239C;LEFT PARENTHESIS EXTENSION;Sm;0;ON;;;;;N;;;;; 239D;LEFT PARENTHESIS LOWER HOOK;Sm;0;ON;;;;;N;;;;; 239E;RIGHT PARENTHESIS UPPER HOOK;Sm;0;ON;;;;;N;;;;; 239F;RIGHT PARENTHESIS EXTENSION;Sm;0;ON;;;;;N;;;;; 23A0;RIGHT PARENTHESIS LOWER HOOK;Sm;0;ON;;;;;N;;;;; 23A1;LEFT SQUARE BRACKET UPPER CORNER;Sm;0;ON;;;;;N;;;;; 23A2;LEFT SQUARE BRACKET EXTENSION;Sm;0;ON;;;;;N;;;;; 23A3;LEFT SQUARE BRACKET LOWER CORNER;Sm;0;ON;;;;;N;;;;; 23A4;RIGHT SQUARE BRACKET UPPER CORNER;Sm;0;ON;;;;;N;;;;; 23A5;RIGHT SQUARE BRACKET EXTENSION;Sm;0;ON;;;;;N;;;;; 23A6;RIGHT SQUARE BRACKET LOWER CORNER;Sm;0;ON;;;;;N;;;;; 23A7;LEFT CURLY BRACKET UPPER HOOK;Sm;0;ON;;;;;N;;;;; 23A8;LEFT CURLY BRACKET MIDDLE PIECE;Sm;0;ON;;;;;N;;;;; 23A9;LEFT CURLY BRACKET LOWER HOOK;Sm;0;ON;;;;;N;;;;; 23AA;CURLY BRACKET EXTENSION;Sm;0;ON;;;;;N;;;;; 23AB;RIGHT CURLY BRACKET UPPER HOOK;Sm;0;ON;;;;;N;;;;; 23AC;RIGHT CURLY BRACKET MIDDLE PIECE;Sm;0;ON;;;;;N;;;;; 23AD;RIGHT CURLY BRACKET LOWER HOOK;Sm;0;ON;;;;;N;;;;; 23AE;INTEGRAL EXTENSION;Sm;0;ON;;;;;N;;;;; 23AF;HORIZONTAL LINE EXTENSION;Sm;0;ON;;;;;N;;;;; 23B0;UPPER LEFT OR LOWER RIGHT CURLY BRACKET SECTION;Sm;0;ON;;;;;N;;;;; 23B1;UPPER RIGHT OR LOWER LEFT CURLY BRACKET SECTION;Sm;0;ON;;;;;N;;;;; 23B2;SUMMATION TOP;Sm;0;ON;;;;;N;;;;; 23B3;SUMMATION BOTTOM;Sm;0;ON;;;;;N;;;;; 23B4;TOP SQUARE BRACKET;So;0;ON;;;;;N;;;;; 23B5;BOTTOM SQUARE BRACKET;So;0;ON;;;;;N;;;;; 23B6;BOTTOM SQUARE BRACKET OVER TOP SQUARE BRACKET;So;0;ON;;;;;N;;;;; 23B7;RADICAL SYMBOL BOTTOM;So;0;ON;;;;;N;;;;; 23B8;LEFT VERTICAL BOX LINE;So;0;ON;;;;;N;;;;; 23B9;RIGHT VERTICAL BOX LINE;So;0;ON;;;;;N;;;;; 23BA;HORIZONTAL SCAN LINE-1;So;0;ON;;;;;N;;;;; 23BB;HORIZONTAL SCAN LINE-3;So;0;ON;;;;;N;;;;; 23BC;HORIZONTAL SCAN LINE-7;So;0;ON;;;;;N;;;;; 23BD;HORIZONTAL SCAN LINE-9;So;0;ON;;;;;N;;;;; 23BE;DENTISTRY SYMBOL LIGHT VERTICAL AND TOP RIGHT;So;0;ON;;;;;N;;;;; 23BF;DENTISTRY SYMBOL LIGHT VERTICAL AND BOTTOM RIGHT;So;0;ON;;;;;N;;;;; 23C0;DENTISTRY SYMBOL LIGHT VERTICAL WITH CIRCLE;So;0;ON;;;;;N;;;;; 23C1;DENTISTRY SYMBOL LIGHT DOWN AND HORIZONTAL WITH CIRCLE;So;0;ON;;;;;N;;;;; 23C2;DENTISTRY SYMBOL LIGHT UP AND HORIZONTAL WITH CIRCLE;So;0;ON;;;;;N;;;;; 23C3;DENTISTRY SYMBOL LIGHT VERTICAL WITH TRIANGLE;So;0;ON;;;;;N;;;;; 23C4;DENTISTRY SYMBOL LIGHT DOWN AND HORIZONTAL WITH TRIANGLE;So;0;ON;;;;;N;;;;; 23C5;DENTISTRY SYMBOL LIGHT UP AND HORIZONTAL WITH TRIANGLE;So;0;ON;;;;;N;;;;; 23C6;DENTISTRY SYMBOL LIGHT VERTICAL AND WAVE;So;0;ON;;;;;N;;;;; 23C7;DENTISTRY SYMBOL LIGHT DOWN AND HORIZONTAL WITH WAVE;So;0;ON;;;;;N;;;;; 23C8;DENTISTRY SYMBOL LIGHT UP AND HORIZONTAL WITH WAVE;So;0;ON;;;;;N;;;;; 23C9;DENTISTRY SYMBOL LIGHT DOWN AND HORIZONTAL;So;0;ON;;;;;N;;;;; 23CA;DENTISTRY SYMBOL LIGHT UP AND HORIZONTAL;So;0;ON;;;;;N;;;;; 23CB;DENTISTRY SYMBOL LIGHT VERTICAL AND TOP LEFT;So;0;ON;;;;;N;;;;; 23CC;DENTISTRY SYMBOL LIGHT VERTICAL AND BOTTOM LEFT;So;0;ON;;;;;N;;;;; 23CD;SQUARE FOOT;So;0;ON;;;;;N;;;;; 23CE;RETURN SYMBOL;So;0;ON;;;;;N;;;;; 23CF;EJECT SYMBOL;So;0;ON;;;;;N;;;;; 23D0;VERTICAL LINE EXTENSION;So;0;ON;;;;;N;;;;; 23D1;METRICAL BREVE;So;0;ON;;;;;N;;;;; 23D2;METRICAL LONG OVER SHORT;So;0;ON;;;;;N;;;;; 23D3;METRICAL SHORT OVER LONG;So;0;ON;;;;;N;;;;; 23D4;METRICAL LONG OVER TWO SHORTS;So;0;ON;;;;;N;;;;; 23D5;METRICAL TWO SHORTS OVER LONG;So;0;ON;;;;;N;;;;; 23D6;METRICAL TWO SHORTS JOINED;So;0;ON;;;;;N;;;;; 23D7;METRICAL TRISEME;So;0;ON;;;;;N;;;;; 23D8;METRICAL TETRASEME;So;0;ON;;;;;N;;;;; 23D9;METRICAL PENTASEME;So;0;ON;;;;;N;;;;; 23DA;EARTH GROUND;So;0;ON;;;;;N;;;;; 23DB;FUSE;So;0;ON;;;;;N;;;;; 23DC;TOP PARENTHESIS;Sm;0;ON;;;;;N;;;;; 23DD;BOTTOM PARENTHESIS;Sm;0;ON;;;;;N;;;;; 23DE;TOP CURLY BRACKET;Sm;0;ON;;;;;N;;;;; 23DF;BOTTOM CURLY BRACKET;Sm;0;ON;;;;;N;;;;; 23E0;TOP TORTOISE SHELL BRACKET;Sm;0;ON;;;;;N;;;;; 23E1;BOTTOM TORTOISE SHELL BRACKET;Sm;0;ON;;;;;N;;;;; 23E2;WHITE TRAPEZIUM;So;0;ON;;;;;N;;;;; 23E3;BENZENE RING WITH CIRCLE;So;0;ON;;;;;N;;;;; 23E4;STRAIGHTNESS;So;0;ON;;;;;N;;;;; 23E5;FLATNESS;So;0;ON;;;;;N;;;;; 23E6;AC CURRENT;So;0;ON;;;;;N;;;;; 23E7;ELECTRICAL INTERSECTION;So;0;ON;;;;;N;;;;; 23E8;DECIMAL EXPONENT SYMBOL;So;0;ON;;;;;N;;;;; 23E9;BLACK RIGHT-POINTING DOUBLE TRIANGLE;So;0;ON;;;;;N;;;;; 23EA;BLACK LEFT-POINTING DOUBLE TRIANGLE;So;0;ON;;;;;N;;;;; 23EB;BLACK UP-POINTING DOUBLE TRIANGLE;So;0;ON;;;;;N;;;;; 23EC;BLACK DOWN-POINTING DOUBLE TRIANGLE;So;0;ON;;;;;N;;;;; 23ED;BLACK RIGHT-POINTING DOUBLE TRIANGLE WITH VERTICAL BAR;So;0;ON;;;;;N;;;;; 23EE;BLACK LEFT-POINTING DOUBLE TRIANGLE WITH VERTICAL BAR;So;0;ON;;;;;N;;;;; 23EF;BLACK RIGHT-POINTING TRIANGLE WITH DOUBLE VERTICAL BAR;So;0;ON;;;;;N;;;;; 23F0;ALARM CLOCK;So;0;ON;;;;;N;;;;; 23F1;STOPWATCH;So;0;ON;;;;;N;;;;; 23F2;TIMER CLOCK;So;0;ON;;;;;N;;;;; 23F3;HOURGLASS WITH FLOWING SAND;So;0;ON;;;;;N;;;;; 23F4;BLACK MEDIUM LEFT-POINTING TRIANGLE;So;0;ON;;;;;N;;;;; 23F5;BLACK MEDIUM RIGHT-POINTING TRIANGLE;So;0;ON;;;;;N;;;;; 23F6;BLACK MEDIUM UP-POINTING TRIANGLE;So;0;ON;;;;;N;;;;; 23F7;BLACK MEDIUM DOWN-POINTING TRIANGLE;So;0;ON;;;;;N;;;;; 23F8;DOUBLE VERTICAL BAR;So;0;ON;;;;;N;;;;; 23F9;BLACK SQUARE FOR STOP;So;0;ON;;;;;N;;;;; 23FA;BLACK CIRCLE FOR RECORD;So;0;ON;;;;;N;;;;; 2400;SYMBOL FOR NULL;So;0;ON;;;;;N;GRAPHIC FOR NULL;;;; 2401;SYMBOL FOR START OF HEADING;So;0;ON;;;;;N;GRAPHIC FOR START OF HEADING;;;; 2402;SYMBOL FOR START OF TEXT;So;0;ON;;;;;N;GRAPHIC FOR START OF TEXT;;;; 2403;SYMBOL FOR END OF TEXT;So;0;ON;;;;;N;GRAPHIC FOR END OF TEXT;;;; 2404;SYMBOL FOR END OF TRANSMISSION;So;0;ON;;;;;N;GRAPHIC FOR END OF TRANSMISSION;;;; 2405;SYMBOL FOR ENQUIRY;So;0;ON;;;;;N;GRAPHIC FOR ENQUIRY;;;; 2406;SYMBOL FOR ACKNOWLEDGE;So;0;ON;;;;;N;GRAPHIC FOR ACKNOWLEDGE;;;; 2407;SYMBOL FOR BELL;So;0;ON;;;;;N;GRAPHIC FOR BELL;;;; 2408;SYMBOL FOR BACKSPACE;So;0;ON;;;;;N;GRAPHIC FOR BACKSPACE;;;; 2409;SYMBOL FOR HORIZONTAL TABULATION;So;0;ON;;;;;N;GRAPHIC FOR HORIZONTAL TABULATION;;;; 240A;SYMBOL FOR LINE FEED;So;0;ON;;;;;N;GRAPHIC FOR LINE FEED;;;; 240B;SYMBOL FOR VERTICAL TABULATION;So;0;ON;;;;;N;GRAPHIC FOR VERTICAL TABULATION;;;; 240C;SYMBOL FOR FORM FEED;So;0;ON;;;;;N;GRAPHIC FOR FORM FEED;;;; 240D;SYMBOL FOR CARRIAGE RETURN;So;0;ON;;;;;N;GRAPHIC FOR CARRIAGE RETURN;;;; 240E;SYMBOL FOR SHIFT OUT;So;0;ON;;;;;N;GRAPHIC FOR SHIFT OUT;;;; 240F;SYMBOL FOR SHIFT IN;So;0;ON;;;;;N;GRAPHIC FOR SHIFT IN;;;; 2410;SYMBOL FOR DATA LINK ESCAPE;So;0;ON;;;;;N;GRAPHIC FOR DATA LINK ESCAPE;;;; 2411;SYMBOL FOR DEVICE CONTROL ONE;So;0;ON;;;;;N;GRAPHIC FOR DEVICE CONTROL ONE;;;; 2412;SYMBOL FOR DEVICE CONTROL TWO;So;0;ON;;;;;N;GRAPHIC FOR DEVICE CONTROL TWO;;;; 2413;SYMBOL FOR DEVICE CONTROL THREE;So;0;ON;;;;;N;GRAPHIC FOR DEVICE CONTROL THREE;;;; 2414;SYMBOL FOR DEVICE CONTROL FOUR;So;0;ON;;;;;N;GRAPHIC FOR DEVICE CONTROL FOUR;;;; 2415;SYMBOL FOR NEGATIVE ACKNOWLEDGE;So;0;ON;;;;;N;GRAPHIC FOR NEGATIVE ACKNOWLEDGE;;;; 2416;SYMBOL FOR SYNCHRONOUS IDLE;So;0;ON;;;;;N;GRAPHIC FOR SYNCHRONOUS IDLE;;;; 2417;SYMBOL FOR END OF TRANSMISSION BLOCK;So;0;ON;;;;;N;GRAPHIC FOR END OF TRANSMISSION BLOCK;;;; 2418;SYMBOL FOR CANCEL;So;0;ON;;;;;N;GRAPHIC FOR CANCEL;;;; 2419;SYMBOL FOR END OF MEDIUM;So;0;ON;;;;;N;GRAPHIC FOR END OF MEDIUM;;;; 241A;SYMBOL FOR SUBSTITUTE;So;0;ON;;;;;N;GRAPHIC FOR SUBSTITUTE;;;; 241B;SYMBOL FOR ESCAPE;So;0;ON;;;;;N;GRAPHIC FOR ESCAPE;;;; 241C;SYMBOL FOR FILE SEPARATOR;So;0;ON;;;;;N;GRAPHIC FOR FILE SEPARATOR;;;; 241D;SYMBOL FOR GROUP SEPARATOR;So;0;ON;;;;;N;GRAPHIC FOR GROUP SEPARATOR;;;; 241E;SYMBOL FOR RECORD SEPARATOR;So;0;ON;;;;;N;GRAPHIC FOR RECORD SEPARATOR;;;; 241F;SYMBOL FOR UNIT SEPARATOR;So;0;ON;;;;;N;GRAPHIC FOR UNIT SEPARATOR;;;; 2420;SYMBOL FOR SPACE;So;0;ON;;;;;N;GRAPHIC FOR SPACE;;;; 2421;SYMBOL FOR DELETE;So;0;ON;;;;;N;GRAPHIC FOR DELETE;;;; 2422;BLANK SYMBOL;So;0;ON;;;;;N;BLANK;;;; 2423;OPEN BOX;So;0;ON;;;;;N;;;;; 2424;SYMBOL FOR NEWLINE;So;0;ON;;;;;N;GRAPHIC FOR NEWLINE;;;; 2425;SYMBOL FOR DELETE FORM TWO;So;0;ON;;;;;N;;;;; 2426;SYMBOL FOR SUBSTITUTE FORM TWO;So;0;ON;;;;;N;;;;; 2440;OCR HOOK;So;0;ON;;;;;N;;;;; 2441;OCR CHAIR;So;0;ON;;;;;N;;;;; 2442;OCR FORK;So;0;ON;;;;;N;;;;; 2443;OCR INVERTED FORK;So;0;ON;;;;;N;;;;; 2444;OCR BELT BUCKLE;So;0;ON;;;;;N;;;;; 2445;OCR BOW TIE;So;0;ON;;;;;N;;;;; 2446;OCR BRANCH BANK IDENTIFICATION;So;0;ON;;;;;N;;;;; 2447;OCR AMOUNT OF CHECK;So;0;ON;;;;;N;;;;; 2448;OCR DASH;So;0;ON;;;;;N;;;;; 2449;OCR CUSTOMER ACCOUNT NUMBER;So;0;ON;;;;;N;;;;; 244A;OCR DOUBLE BACKSLASH;So;0;ON;;;;;N;;;;; 2460;CIRCLED DIGIT ONE;No;0;ON; 0031;;1;1;N;;;;; 2461;CIRCLED DIGIT TWO;No;0;ON; 0032;;2;2;N;;;;; 2462;CIRCLED DIGIT THREE;No;0;ON; 0033;;3;3;N;;;;; 2463;CIRCLED DIGIT FOUR;No;0;ON; 0034;;4;4;N;;;;; 2464;CIRCLED DIGIT FIVE;No;0;ON; 0035;;5;5;N;;;;; 2465;CIRCLED DIGIT SIX;No;0;ON; 0036;;6;6;N;;;;; 2466;CIRCLED DIGIT SEVEN;No;0;ON; 0037;;7;7;N;;;;; 2467;CIRCLED DIGIT EIGHT;No;0;ON; 0038;;8;8;N;;;;; 2468;CIRCLED DIGIT NINE;No;0;ON; 0039;;9;9;N;;;;; 2469;CIRCLED NUMBER TEN;No;0;ON; 0031 0030;;;10;N;;;;; 246A;CIRCLED NUMBER ELEVEN;No;0;ON; 0031 0031;;;11;N;;;;; 246B;CIRCLED NUMBER TWELVE;No;0;ON; 0031 0032;;;12;N;;;;; 246C;CIRCLED NUMBER THIRTEEN;No;0;ON; 0031 0033;;;13;N;;;;; 246D;CIRCLED NUMBER FOURTEEN;No;0;ON; 0031 0034;;;14;N;;;;; 246E;CIRCLED NUMBER FIFTEEN;No;0;ON; 0031 0035;;;15;N;;;;; 246F;CIRCLED NUMBER SIXTEEN;No;0;ON; 0031 0036;;;16;N;;;;; 2470;CIRCLED NUMBER SEVENTEEN;No;0;ON; 0031 0037;;;17;N;;;;; 2471;CIRCLED NUMBER EIGHTEEN;No;0;ON; 0031 0038;;;18;N;;;;; 2472;CIRCLED NUMBER NINETEEN;No;0;ON; 0031 0039;;;19;N;;;;; 2473;CIRCLED NUMBER TWENTY;No;0;ON; 0032 0030;;;20;N;;;;; 2474;PARENTHESIZED DIGIT ONE;No;0;ON; 0028 0031 0029;;1;1;N;;;;; 2475;PARENTHESIZED DIGIT TWO;No;0;ON; 0028 0032 0029;;2;2;N;;;;; 2476;PARENTHESIZED DIGIT THREE;No;0;ON; 0028 0033 0029;;3;3;N;;;;; 2477;PARENTHESIZED DIGIT FOUR;No;0;ON; 0028 0034 0029;;4;4;N;;;;; 2478;PARENTHESIZED DIGIT FIVE;No;0;ON; 0028 0035 0029;;5;5;N;;;;; 2479;PARENTHESIZED DIGIT SIX;No;0;ON; 0028 0036 0029;;6;6;N;;;;; 247A;PARENTHESIZED DIGIT SEVEN;No;0;ON; 0028 0037 0029;;7;7;N;;;;; 247B;PARENTHESIZED DIGIT EIGHT;No;0;ON; 0028 0038 0029;;8;8;N;;;;; 247C;PARENTHESIZED DIGIT NINE;No;0;ON; 0028 0039 0029;;9;9;N;;;;; 247D;PARENTHESIZED NUMBER TEN;No;0;ON; 0028 0031 0030 0029;;;10;N;;;;; 247E;PARENTHESIZED NUMBER ELEVEN;No;0;ON; 0028 0031 0031 0029;;;11;N;;;;; 247F;PARENTHESIZED NUMBER TWELVE;No;0;ON; 0028 0031 0032 0029;;;12;N;;;;; 2480;PARENTHESIZED NUMBER THIRTEEN;No;0;ON; 0028 0031 0033 0029;;;13;N;;;;; 2481;PARENTHESIZED NUMBER FOURTEEN;No;0;ON; 0028 0031 0034 0029;;;14;N;;;;; 2482;PARENTHESIZED NUMBER FIFTEEN;No;0;ON; 0028 0031 0035 0029;;;15;N;;;;; 2483;PARENTHESIZED NUMBER SIXTEEN;No;0;ON; 0028 0031 0036 0029;;;16;N;;;;; 2484;PARENTHESIZED NUMBER SEVENTEEN;No;0;ON; 0028 0031 0037 0029;;;17;N;;;;; 2485;PARENTHESIZED NUMBER EIGHTEEN;No;0;ON; 0028 0031 0038 0029;;;18;N;;;;; 2486;PARENTHESIZED NUMBER NINETEEN;No;0;ON; 0028 0031 0039 0029;;;19;N;;;;; 2487;PARENTHESIZED NUMBER TWENTY;No;0;ON; 0028 0032 0030 0029;;;20;N;;;;; 2488;DIGIT ONE FULL STOP;No;0;EN; 0031 002E;;1;1;N;DIGIT ONE PERIOD;;;; 2489;DIGIT TWO FULL STOP;No;0;EN; 0032 002E;;2;2;N;DIGIT TWO PERIOD;;;; 248A;DIGIT THREE FULL STOP;No;0;EN; 0033 002E;;3;3;N;DIGIT THREE PERIOD;;;; 248B;DIGIT FOUR FULL STOP;No;0;EN; 0034 002E;;4;4;N;DIGIT FOUR PERIOD;;;; 248C;DIGIT FIVE FULL STOP;No;0;EN; 0035 002E;;5;5;N;DIGIT FIVE PERIOD;;;; 248D;DIGIT SIX FULL STOP;No;0;EN; 0036 002E;;6;6;N;DIGIT SIX PERIOD;;;; 248E;DIGIT SEVEN FULL STOP;No;0;EN; 0037 002E;;7;7;N;DIGIT SEVEN PERIOD;;;; 248F;DIGIT EIGHT FULL STOP;No;0;EN; 0038 002E;;8;8;N;DIGIT EIGHT PERIOD;;;; 2490;DIGIT NINE FULL STOP;No;0;EN; 0039 002E;;9;9;N;DIGIT NINE PERIOD;;;; 2491;NUMBER TEN FULL STOP;No;0;EN; 0031 0030 002E;;;10;N;NUMBER TEN PERIOD;;;; 2492;NUMBER ELEVEN FULL STOP;No;0;EN; 0031 0031 002E;;;11;N;NUMBER ELEVEN PERIOD;;;; 2493;NUMBER TWELVE FULL STOP;No;0;EN; 0031 0032 002E;;;12;N;NUMBER TWELVE PERIOD;;;; 2494;NUMBER THIRTEEN FULL STOP;No;0;EN; 0031 0033 002E;;;13;N;NUMBER THIRTEEN PERIOD;;;; 2495;NUMBER FOURTEEN FULL STOP;No;0;EN; 0031 0034 002E;;;14;N;NUMBER FOURTEEN PERIOD;;;; 2496;NUMBER FIFTEEN FULL STOP;No;0;EN; 0031 0035 002E;;;15;N;NUMBER FIFTEEN PERIOD;;;; 2497;NUMBER SIXTEEN FULL STOP;No;0;EN; 0031 0036 002E;;;16;N;NUMBER SIXTEEN PERIOD;;;; 2498;NUMBER SEVENTEEN FULL STOP;No;0;EN; 0031 0037 002E;;;17;N;NUMBER SEVENTEEN PERIOD;;;; 2499;NUMBER EIGHTEEN FULL STOP;No;0;EN; 0031 0038 002E;;;18;N;NUMBER EIGHTEEN PERIOD;;;; 249A;NUMBER NINETEEN FULL STOP;No;0;EN; 0031 0039 002E;;;19;N;NUMBER NINETEEN PERIOD;;;; 249B;NUMBER TWENTY FULL STOP;No;0;EN; 0032 0030 002E;;;20;N;NUMBER TWENTY PERIOD;;;; 249C;PARENTHESIZED LATIN SMALL LETTER A;So;0;L; 0028 0061 0029;;;;N;;;;; 249D;PARENTHESIZED LATIN SMALL LETTER B;So;0;L; 0028 0062 0029;;;;N;;;;; 249E;PARENTHESIZED LATIN SMALL LETTER C;So;0;L; 0028 0063 0029;;;;N;;;;; 249F;PARENTHESIZED LATIN SMALL LETTER D;So;0;L; 0028 0064 0029;;;;N;;;;; 24A0;PARENTHESIZED LATIN SMALL LETTER E;So;0;L; 0028 0065 0029;;;;N;;;;; 24A1;PARENTHESIZED LATIN SMALL LETTER F;So;0;L; 0028 0066 0029;;;;N;;;;; 24A2;PARENTHESIZED LATIN SMALL LETTER G;So;0;L; 0028 0067 0029;;;;N;;;;; 24A3;PARENTHESIZED LATIN SMALL LETTER H;So;0;L; 0028 0068 0029;;;;N;;;;; 24A4;PARENTHESIZED LATIN SMALL LETTER I;So;0;L; 0028 0069 0029;;;;N;;;;; 24A5;PARENTHESIZED LATIN SMALL LETTER J;So;0;L; 0028 006A 0029;;;;N;;;;; 24A6;PARENTHESIZED LATIN SMALL LETTER K;So;0;L; 0028 006B 0029;;;;N;;;;; 24A7;PARENTHESIZED LATIN SMALL LETTER L;So;0;L; 0028 006C 0029;;;;N;;;;; 24A8;PARENTHESIZED LATIN SMALL LETTER M;So;0;L; 0028 006D 0029;;;;N;;;;; 24A9;PARENTHESIZED LATIN SMALL LETTER N;So;0;L; 0028 006E 0029;;;;N;;;;; 24AA;PARENTHESIZED LATIN SMALL LETTER O;So;0;L; 0028 006F 0029;;;;N;;;;; 24AB;PARENTHESIZED LATIN SMALL LETTER P;So;0;L; 0028 0070 0029;;;;N;;;;; 24AC;PARENTHESIZED LATIN SMALL LETTER Q;So;0;L; 0028 0071 0029;;;;N;;;;; 24AD;PARENTHESIZED LATIN SMALL LETTER R;So;0;L; 0028 0072 0029;;;;N;;;;; 24AE;PARENTHESIZED LATIN SMALL LETTER S;So;0;L; 0028 0073 0029;;;;N;;;;; 24AF;PARENTHESIZED LATIN SMALL LETTER T;So;0;L; 0028 0074 0029;;;;N;;;;; 24B0;PARENTHESIZED LATIN SMALL LETTER U;So;0;L; 0028 0075 0029;;;;N;;;;; 24B1;PARENTHESIZED LATIN SMALL LETTER V;So;0;L; 0028 0076 0029;;;;N;;;;; 24B2;PARENTHESIZED LATIN SMALL LETTER W;So;0;L; 0028 0077 0029;;;;N;;;;; 24B3;PARENTHESIZED LATIN SMALL LETTER X;So;0;L; 0028 0078 0029;;;;N;;;;; 24B4;PARENTHESIZED LATIN SMALL LETTER Y;So;0;L; 0028 0079 0029;;;;N;;;;; 24B5;PARENTHESIZED LATIN SMALL LETTER Z;So;0;L; 0028 007A 0029;;;;N;;;;; 24B6;CIRCLED LATIN CAPITAL LETTER A;So;0;L; 0041;;;;N;;;;24D0; 24B7;CIRCLED LATIN CAPITAL LETTER B;So;0;L; 0042;;;;N;;;;24D1; 24B8;CIRCLED LATIN CAPITAL LETTER C;So;0;L; 0043;;;;N;;;;24D2; 24B9;CIRCLED LATIN CAPITAL LETTER D;So;0;L; 0044;;;;N;;;;24D3; 24BA;CIRCLED LATIN CAPITAL LETTER E;So;0;L; 0045;;;;N;;;;24D4; 24BB;CIRCLED LATIN CAPITAL LETTER F;So;0;L; 0046;;;;N;;;;24D5; 24BC;CIRCLED LATIN CAPITAL LETTER G;So;0;L; 0047;;;;N;;;;24D6; 24BD;CIRCLED LATIN CAPITAL LETTER H;So;0;L; 0048;;;;N;;;;24D7; 24BE;CIRCLED LATIN CAPITAL LETTER I;So;0;L; 0049;;;;N;;;;24D8; 24BF;CIRCLED LATIN CAPITAL LETTER J;So;0;L; 004A;;;;N;;;;24D9; 24C0;CIRCLED LATIN CAPITAL LETTER K;So;0;L; 004B;;;;N;;;;24DA; 24C1;CIRCLED LATIN CAPITAL LETTER L;So;0;L; 004C;;;;N;;;;24DB; 24C2;CIRCLED LATIN CAPITAL LETTER M;So;0;L; 004D;;;;N;;;;24DC; 24C3;CIRCLED LATIN CAPITAL LETTER N;So;0;L; 004E;;;;N;;;;24DD; 24C4;CIRCLED LATIN CAPITAL LETTER O;So;0;L; 004F;;;;N;;;;24DE; 24C5;CIRCLED LATIN CAPITAL LETTER P;So;0;L; 0050;;;;N;;;;24DF; 24C6;CIRCLED LATIN CAPITAL LETTER Q;So;0;L; 0051;;;;N;;;;24E0; 24C7;CIRCLED LATIN CAPITAL LETTER R;So;0;L; 0052;;;;N;;;;24E1; 24C8;CIRCLED LATIN CAPITAL LETTER S;So;0;L; 0053;;;;N;;;;24E2; 24C9;CIRCLED LATIN CAPITAL LETTER T;So;0;L; 0054;;;;N;;;;24E3; 24CA;CIRCLED LATIN CAPITAL LETTER U;So;0;L; 0055;;;;N;;;;24E4; 24CB;CIRCLED LATIN CAPITAL LETTER V;So;0;L; 0056;;;;N;;;;24E5; 24CC;CIRCLED LATIN CAPITAL LETTER W;So;0;L; 0057;;;;N;;;;24E6; 24CD;CIRCLED LATIN CAPITAL LETTER X;So;0;L; 0058;;;;N;;;;24E7; 24CE;CIRCLED LATIN CAPITAL LETTER Y;So;0;L; 0059;;;;N;;;;24E8; 24CF;CIRCLED LATIN CAPITAL LETTER Z;So;0;L; 005A;;;;N;;;;24E9; 24D0;CIRCLED LATIN SMALL LETTER A;So;0;L; 0061;;;;N;;;24B6;;24B6 24D1;CIRCLED LATIN SMALL LETTER B;So;0;L; 0062;;;;N;;;24B7;;24B7 24D2;CIRCLED LATIN SMALL LETTER C;So;0;L; 0063;;;;N;;;24B8;;24B8 24D3;CIRCLED LATIN SMALL LETTER D;So;0;L; 0064;;;;N;;;24B9;;24B9 24D4;CIRCLED LATIN SMALL LETTER E;So;0;L; 0065;;;;N;;;24BA;;24BA 24D5;CIRCLED LATIN SMALL LETTER F;So;0;L; 0066;;;;N;;;24BB;;24BB 24D6;CIRCLED LATIN SMALL LETTER G;So;0;L; 0067;;;;N;;;24BC;;24BC 24D7;CIRCLED LATIN SMALL LETTER H;So;0;L; 0068;;;;N;;;24BD;;24BD 24D8;CIRCLED LATIN SMALL LETTER I;So;0;L; 0069;;;;N;;;24BE;;24BE 24D9;CIRCLED LATIN SMALL LETTER J;So;0;L; 006A;;;;N;;;24BF;;24BF 24DA;CIRCLED LATIN SMALL LETTER K;So;0;L; 006B;;;;N;;;24C0;;24C0 24DB;CIRCLED LATIN SMALL LETTER L;So;0;L; 006C;;;;N;;;24C1;;24C1 24DC;CIRCLED LATIN SMALL LETTER M;So;0;L; 006D;;;;N;;;24C2;;24C2 24DD;CIRCLED LATIN SMALL LETTER N;So;0;L; 006E;;;;N;;;24C3;;24C3 24DE;CIRCLED LATIN SMALL LETTER O;So;0;L; 006F;;;;N;;;24C4;;24C4 24DF;CIRCLED LATIN SMALL LETTER P;So;0;L; 0070;;;;N;;;24C5;;24C5 24E0;CIRCLED LATIN SMALL LETTER Q;So;0;L; 0071;;;;N;;;24C6;;24C6 24E1;CIRCLED LATIN SMALL LETTER R;So;0;L; 0072;;;;N;;;24C7;;24C7 24E2;CIRCLED LATIN SMALL LETTER S;So;0;L; 0073;;;;N;;;24C8;;24C8 24E3;CIRCLED LATIN SMALL LETTER T;So;0;L; 0074;;;;N;;;24C9;;24C9 24E4;CIRCLED LATIN SMALL LETTER U;So;0;L; 0075;;;;N;;;24CA;;24CA 24E5;CIRCLED LATIN SMALL LETTER V;So;0;L; 0076;;;;N;;;24CB;;24CB 24E6;CIRCLED LATIN SMALL LETTER W;So;0;L; 0077;;;;N;;;24CC;;24CC 24E7;CIRCLED LATIN SMALL LETTER X;So;0;L; 0078;;;;N;;;24CD;;24CD 24E8;CIRCLED LATIN SMALL LETTER Y;So;0;L; 0079;;;;N;;;24CE;;24CE 24E9;CIRCLED LATIN SMALL LETTER Z;So;0;L; 007A;;;;N;;;24CF;;24CF 24EA;CIRCLED DIGIT ZERO;No;0;ON; 0030;;0;0;N;;;;; 24EB;NEGATIVE CIRCLED NUMBER ELEVEN;No;0;ON;;;;11;N;;;;; 24EC;NEGATIVE CIRCLED NUMBER TWELVE;No;0;ON;;;;12;N;;;;; 24ED;NEGATIVE CIRCLED NUMBER THIRTEEN;No;0;ON;;;;13;N;;;;; 24EE;NEGATIVE CIRCLED NUMBER FOURTEEN;No;0;ON;;;;14;N;;;;; 24EF;NEGATIVE CIRCLED NUMBER FIFTEEN;No;0;ON;;;;15;N;;;;; 24F0;NEGATIVE CIRCLED NUMBER SIXTEEN;No;0;ON;;;;16;N;;;;; 24F1;NEGATIVE CIRCLED NUMBER SEVENTEEN;No;0;ON;;;;17;N;;;;; 24F2;NEGATIVE CIRCLED NUMBER EIGHTEEN;No;0;ON;;;;18;N;;;;; 24F3;NEGATIVE CIRCLED NUMBER NINETEEN;No;0;ON;;;;19;N;;;;; 24F4;NEGATIVE CIRCLED NUMBER TWENTY;No;0;ON;;;;20;N;;;;; 24F5;DOUBLE CIRCLED DIGIT ONE;No;0;ON;;;1;1;N;;;;; 24F6;DOUBLE CIRCLED DIGIT TWO;No;0;ON;;;2;2;N;;;;; 24F7;DOUBLE CIRCLED DIGIT THREE;No;0;ON;;;3;3;N;;;;; 24F8;DOUBLE CIRCLED DIGIT FOUR;No;0;ON;;;4;4;N;;;;; 24F9;DOUBLE CIRCLED DIGIT FIVE;No;0;ON;;;5;5;N;;;;; 24FA;DOUBLE CIRCLED DIGIT SIX;No;0;ON;;;6;6;N;;;;; 24FB;DOUBLE CIRCLED DIGIT SEVEN;No;0;ON;;;7;7;N;;;;; 24FC;DOUBLE CIRCLED DIGIT EIGHT;No;0;ON;;;8;8;N;;;;; 24FD;DOUBLE CIRCLED DIGIT NINE;No;0;ON;;;9;9;N;;;;; 24FE;DOUBLE CIRCLED NUMBER TEN;No;0;ON;;;;10;N;;;;; 24FF;NEGATIVE CIRCLED DIGIT ZERO;No;0;ON;;;0;0;N;;;;; 2500;BOX DRAWINGS LIGHT HORIZONTAL;So;0;ON;;;;;N;FORMS LIGHT HORIZONTAL;;;; 2501;BOX DRAWINGS HEAVY HORIZONTAL;So;0;ON;;;;;N;FORMS HEAVY HORIZONTAL;;;; 2502;BOX DRAWINGS LIGHT VERTICAL;So;0;ON;;;;;N;FORMS LIGHT VERTICAL;;;; 2503;BOX DRAWINGS HEAVY VERTICAL;So;0;ON;;;;;N;FORMS HEAVY VERTICAL;;;; 2504;BOX DRAWINGS LIGHT TRIPLE DASH HORIZONTAL;So;0;ON;;;;;N;FORMS LIGHT TRIPLE DASH HORIZONTAL;;;; 2505;BOX DRAWINGS HEAVY TRIPLE DASH HORIZONTAL;So;0;ON;;;;;N;FORMS HEAVY TRIPLE DASH HORIZONTAL;;;; 2506;BOX DRAWINGS LIGHT TRIPLE DASH VERTICAL;So;0;ON;;;;;N;FORMS LIGHT TRIPLE DASH VERTICAL;;;; 2507;BOX DRAWINGS HEAVY TRIPLE DASH VERTICAL;So;0;ON;;;;;N;FORMS HEAVY TRIPLE DASH VERTICAL;;;; 2508;BOX DRAWINGS LIGHT QUADRUPLE DASH HORIZONTAL;So;0;ON;;;;;N;FORMS LIGHT QUADRUPLE DASH HORIZONTAL;;;; 2509;BOX DRAWINGS HEAVY QUADRUPLE DASH HORIZONTAL;So;0;ON;;;;;N;FORMS HEAVY QUADRUPLE DASH HORIZONTAL;;;; 250A;BOX DRAWINGS LIGHT QUADRUPLE DASH VERTICAL;So;0;ON;;;;;N;FORMS LIGHT QUADRUPLE DASH VERTICAL;;;; 250B;BOX DRAWINGS HEAVY QUADRUPLE DASH VERTICAL;So;0;ON;;;;;N;FORMS HEAVY QUADRUPLE DASH VERTICAL;;;; 250C;BOX DRAWINGS LIGHT DOWN AND RIGHT;So;0;ON;;;;;N;FORMS LIGHT DOWN AND RIGHT;;;; 250D;BOX DRAWINGS DOWN LIGHT AND RIGHT HEAVY;So;0;ON;;;;;N;FORMS DOWN LIGHT AND RIGHT HEAVY;;;; 250E;BOX DRAWINGS DOWN HEAVY AND RIGHT LIGHT;So;0;ON;;;;;N;FORMS DOWN HEAVY AND RIGHT LIGHT;;;; 250F;BOX DRAWINGS HEAVY DOWN AND RIGHT;So;0;ON;;;;;N;FORMS HEAVY DOWN AND RIGHT;;;; 2510;BOX DRAWINGS LIGHT DOWN AND LEFT;So;0;ON;;;;;N;FORMS LIGHT DOWN AND LEFT;;;; 2511;BOX DRAWINGS DOWN LIGHT AND LEFT HEAVY;So;0;ON;;;;;N;FORMS DOWN LIGHT AND LEFT HEAVY;;;; 2512;BOX DRAWINGS DOWN HEAVY AND LEFT LIGHT;So;0;ON;;;;;N;FORMS DOWN HEAVY AND LEFT LIGHT;;;; 2513;BOX DRAWINGS HEAVY DOWN AND LEFT;So;0;ON;;;;;N;FORMS HEAVY DOWN AND LEFT;;;; 2514;BOX DRAWINGS LIGHT UP AND RIGHT;So;0;ON;;;;;N;FORMS LIGHT UP AND RIGHT;;;; 2515;BOX DRAWINGS UP LIGHT AND RIGHT HEAVY;So;0;ON;;;;;N;FORMS UP LIGHT AND RIGHT HEAVY;;;; 2516;BOX DRAWINGS UP HEAVY AND RIGHT LIGHT;So;0;ON;;;;;N;FORMS UP HEAVY AND RIGHT LIGHT;;;; 2517;BOX DRAWINGS HEAVY UP AND RIGHT;So;0;ON;;;;;N;FORMS HEAVY UP AND RIGHT;;;; 2518;BOX DRAWINGS LIGHT UP AND LEFT;So;0;ON;;;;;N;FORMS LIGHT UP AND LEFT;;;; 2519;BOX DRAWINGS UP LIGHT AND LEFT HEAVY;So;0;ON;;;;;N;FORMS UP LIGHT AND LEFT HEAVY;;;; 251A;BOX DRAWINGS UP HEAVY AND LEFT LIGHT;So;0;ON;;;;;N;FORMS UP HEAVY AND LEFT LIGHT;;;; 251B;BOX DRAWINGS HEAVY UP AND LEFT;So;0;ON;;;;;N;FORMS HEAVY UP AND LEFT;;;; 251C;BOX DRAWINGS LIGHT VERTICAL AND RIGHT;So;0;ON;;;;;N;FORMS LIGHT VERTICAL AND RIGHT;;;; 251D;BOX DRAWINGS VERTICAL LIGHT AND RIGHT HEAVY;So;0;ON;;;;;N;FORMS VERTICAL LIGHT AND RIGHT HEAVY;;;; 251E;BOX DRAWINGS UP HEAVY AND RIGHT DOWN LIGHT;So;0;ON;;;;;N;FORMS UP HEAVY AND RIGHT DOWN LIGHT;;;; 251F;BOX DRAWINGS DOWN HEAVY AND RIGHT UP LIGHT;So;0;ON;;;;;N;FORMS DOWN HEAVY AND RIGHT UP LIGHT;;;; 2520;BOX DRAWINGS VERTICAL HEAVY AND RIGHT LIGHT;So;0;ON;;;;;N;FORMS VERTICAL HEAVY AND RIGHT LIGHT;;;; 2521;BOX DRAWINGS DOWN LIGHT AND RIGHT UP HEAVY;So;0;ON;;;;;N;FORMS DOWN LIGHT AND RIGHT UP HEAVY;;;; 2522;BOX DRAWINGS UP LIGHT AND RIGHT DOWN HEAVY;So;0;ON;;;;;N;FORMS UP LIGHT AND RIGHT DOWN HEAVY;;;; 2523;BOX DRAWINGS HEAVY VERTICAL AND RIGHT;So;0;ON;;;;;N;FORMS HEAVY VERTICAL AND RIGHT;;;; 2524;BOX DRAWINGS LIGHT VERTICAL AND LEFT;So;0;ON;;;;;N;FORMS LIGHT VERTICAL AND LEFT;;;; 2525;BOX DRAWINGS VERTICAL LIGHT AND LEFT HEAVY;So;0;ON;;;;;N;FORMS VERTICAL LIGHT AND LEFT HEAVY;;;; 2526;BOX DRAWINGS UP HEAVY AND LEFT DOWN LIGHT;So;0;ON;;;;;N;FORMS UP HEAVY AND LEFT DOWN LIGHT;;;; 2527;BOX DRAWINGS DOWN HEAVY AND LEFT UP LIGHT;So;0;ON;;;;;N;FORMS DOWN HEAVY AND LEFT UP LIGHT;;;; 2528;BOX DRAWINGS VERTICAL HEAVY AND LEFT LIGHT;So;0;ON;;;;;N;FORMS VERTICAL HEAVY AND LEFT LIGHT;;;; 2529;BOX DRAWINGS DOWN LIGHT AND LEFT UP HEAVY;So;0;ON;;;;;N;FORMS DOWN LIGHT AND LEFT UP HEAVY;;;; 252A;BOX DRAWINGS UP LIGHT AND LEFT DOWN HEAVY;So;0;ON;;;;;N;FORMS UP LIGHT AND LEFT DOWN HEAVY;;;; 252B;BOX DRAWINGS HEAVY VERTICAL AND LEFT;So;0;ON;;;;;N;FORMS HEAVY VERTICAL AND LEFT;;;; 252C;BOX DRAWINGS LIGHT DOWN AND HORIZONTAL;So;0;ON;;;;;N;FORMS LIGHT DOWN AND HORIZONTAL;;;; 252D;BOX DRAWINGS LEFT HEAVY AND RIGHT DOWN LIGHT;So;0;ON;;;;;N;FORMS LEFT HEAVY AND RIGHT DOWN LIGHT;;;; 252E;BOX DRAWINGS RIGHT HEAVY AND LEFT DOWN LIGHT;So;0;ON;;;;;N;FORMS RIGHT HEAVY AND LEFT DOWN LIGHT;;;; 252F;BOX DRAWINGS DOWN LIGHT AND HORIZONTAL HEAVY;So;0;ON;;;;;N;FORMS DOWN LIGHT AND HORIZONTAL HEAVY;;;; 2530;BOX DRAWINGS DOWN HEAVY AND HORIZONTAL LIGHT;So;0;ON;;;;;N;FORMS DOWN HEAVY AND HORIZONTAL LIGHT;;;; 2531;BOX DRAWINGS RIGHT LIGHT AND LEFT DOWN HEAVY;So;0;ON;;;;;N;FORMS RIGHT LIGHT AND LEFT DOWN HEAVY;;;; 2532;BOX DRAWINGS LEFT LIGHT AND RIGHT DOWN HEAVY;So;0;ON;;;;;N;FORMS LEFT LIGHT AND RIGHT DOWN HEAVY;;;; 2533;BOX DRAWINGS HEAVY DOWN AND HORIZONTAL;So;0;ON;;;;;N;FORMS HEAVY DOWN AND HORIZONTAL;;;; 2534;BOX DRAWINGS LIGHT UP AND HORIZONTAL;So;0;ON;;;;;N;FORMS LIGHT UP AND HORIZONTAL;;;; 2535;BOX DRAWINGS LEFT HEAVY AND RIGHT UP LIGHT;So;0;ON;;;;;N;FORMS LEFT HEAVY AND RIGHT UP LIGHT;;;; 2536;BOX DRAWINGS RIGHT HEAVY AND LEFT UP LIGHT;So;0;ON;;;;;N;FORMS RIGHT HEAVY AND LEFT UP LIGHT;;;; 2537;BOX DRAWINGS UP LIGHT AND HORIZONTAL HEAVY;So;0;ON;;;;;N;FORMS UP LIGHT AND HORIZONTAL HEAVY;;;; 2538;BOX DRAWINGS UP HEAVY AND HORIZONTAL LIGHT;So;0;ON;;;;;N;FORMS UP HEAVY AND HORIZONTAL LIGHT;;;; 2539;BOX DRAWINGS RIGHT LIGHT AND LEFT UP HEAVY;So;0;ON;;;;;N;FORMS RIGHT LIGHT AND LEFT UP HEAVY;;;; 253A;BOX DRAWINGS LEFT LIGHT AND RIGHT UP HEAVY;So;0;ON;;;;;N;FORMS LEFT LIGHT AND RIGHT UP HEAVY;;;; 253B;BOX DRAWINGS HEAVY UP AND HORIZONTAL;So;0;ON;;;;;N;FORMS HEAVY UP AND HORIZONTAL;;;; 253C;BOX DRAWINGS LIGHT VERTICAL AND HORIZONTAL;So;0;ON;;;;;N;FORMS LIGHT VERTICAL AND HORIZONTAL;;;; 253D;BOX DRAWINGS LEFT HEAVY AND RIGHT VERTICAL LIGHT;So;0;ON;;;;;N;FORMS LEFT HEAVY AND RIGHT VERTICAL LIGHT;;;; 253E;BOX DRAWINGS RIGHT HEAVY AND LEFT VERTICAL LIGHT;So;0;ON;;;;;N;FORMS RIGHT HEAVY AND LEFT VERTICAL LIGHT;;;; 253F;BOX DRAWINGS VERTICAL LIGHT AND HORIZONTAL HEAVY;So;0;ON;;;;;N;FORMS VERTICAL LIGHT AND HORIZONTAL HEAVY;;;; 2540;BOX DRAWINGS UP HEAVY AND DOWN HORIZONTAL LIGHT;So;0;ON;;;;;N;FORMS UP HEAVY AND DOWN HORIZONTAL LIGHT;;;; 2541;BOX DRAWINGS DOWN HEAVY AND UP HORIZONTAL LIGHT;So;0;ON;;;;;N;FORMS DOWN HEAVY AND UP HORIZONTAL LIGHT;;;; 2542;BOX DRAWINGS VERTICAL HEAVY AND HORIZONTAL LIGHT;So;0;ON;;;;;N;FORMS VERTICAL HEAVY AND HORIZONTAL LIGHT;;;; 2543;BOX DRAWINGS LEFT UP HEAVY AND RIGHT DOWN LIGHT;So;0;ON;;;;;N;FORMS LEFT UP HEAVY AND RIGHT DOWN LIGHT;;;; 2544;BOX DRAWINGS RIGHT UP HEAVY AND LEFT DOWN LIGHT;So;0;ON;;;;;N;FORMS RIGHT UP HEAVY AND LEFT DOWN LIGHT;;;; 2545;BOX DRAWINGS LEFT DOWN HEAVY AND RIGHT UP LIGHT;So;0;ON;;;;;N;FORMS LEFT DOWN HEAVY AND RIGHT UP LIGHT;;;; 2546;BOX DRAWINGS RIGHT DOWN HEAVY AND LEFT UP LIGHT;So;0;ON;;;;;N;FORMS RIGHT DOWN HEAVY AND LEFT UP LIGHT;;;; 2547;BOX DRAWINGS DOWN LIGHT AND UP HORIZONTAL HEAVY;So;0;ON;;;;;N;FORMS DOWN LIGHT AND UP HORIZONTAL HEAVY;;;; 2548;BOX DRAWINGS UP LIGHT AND DOWN HORIZONTAL HEAVY;So;0;ON;;;;;N;FORMS UP LIGHT AND DOWN HORIZONTAL HEAVY;;;; 2549;BOX DRAWINGS RIGHT LIGHT AND LEFT VERTICAL HEAVY;So;0;ON;;;;;N;FORMS RIGHT LIGHT AND LEFT VERTICAL HEAVY;;;; 254A;BOX DRAWINGS LEFT LIGHT AND RIGHT VERTICAL HEAVY;So;0;ON;;;;;N;FORMS LEFT LIGHT AND RIGHT VERTICAL HEAVY;;;; 254B;BOX DRAWINGS HEAVY VERTICAL AND HORIZONTAL;So;0;ON;;;;;N;FORMS HEAVY VERTICAL AND HORIZONTAL;;;; 254C;BOX DRAWINGS LIGHT DOUBLE DASH HORIZONTAL;So;0;ON;;;;;N;FORMS LIGHT DOUBLE DASH HORIZONTAL;;;; 254D;BOX DRAWINGS HEAVY DOUBLE DASH HORIZONTAL;So;0;ON;;;;;N;FORMS HEAVY DOUBLE DASH HORIZONTAL;;;; 254E;BOX DRAWINGS LIGHT DOUBLE DASH VERTICAL;So;0;ON;;;;;N;FORMS LIGHT DOUBLE DASH VERTICAL;;;; 254F;BOX DRAWINGS HEAVY DOUBLE DASH VERTICAL;So;0;ON;;;;;N;FORMS HEAVY DOUBLE DASH VERTICAL;;;; 2550;BOX DRAWINGS DOUBLE HORIZONTAL;So;0;ON;;;;;N;FORMS DOUBLE HORIZONTAL;;;; 2551;BOX DRAWINGS DOUBLE VERTICAL;So;0;ON;;;;;N;FORMS DOUBLE VERTICAL;;;; 2552;BOX DRAWINGS DOWN SINGLE AND RIGHT DOUBLE;So;0;ON;;;;;N;FORMS DOWN SINGLE AND RIGHT DOUBLE;;;; 2553;BOX DRAWINGS DOWN DOUBLE AND RIGHT SINGLE;So;0;ON;;;;;N;FORMS DOWN DOUBLE AND RIGHT SINGLE;;;; 2554;BOX DRAWINGS DOUBLE DOWN AND RIGHT;So;0;ON;;;;;N;FORMS DOUBLE DOWN AND RIGHT;;;; 2555;BOX DRAWINGS DOWN SINGLE AND LEFT DOUBLE;So;0;ON;;;;;N;FORMS DOWN SINGLE AND LEFT DOUBLE;;;; 2556;BOX DRAWINGS DOWN DOUBLE AND LEFT SINGLE;So;0;ON;;;;;N;FORMS DOWN DOUBLE AND LEFT SINGLE;;;; 2557;BOX DRAWINGS DOUBLE DOWN AND LEFT;So;0;ON;;;;;N;FORMS DOUBLE DOWN AND LEFT;;;; 2558;BOX DRAWINGS UP SINGLE AND RIGHT DOUBLE;So;0;ON;;;;;N;FORMS UP SINGLE AND RIGHT DOUBLE;;;; 2559;BOX DRAWINGS UP DOUBLE AND RIGHT SINGLE;So;0;ON;;;;;N;FORMS UP DOUBLE AND RIGHT SINGLE;;;; 255A;BOX DRAWINGS DOUBLE UP AND RIGHT;So;0;ON;;;;;N;FORMS DOUBLE UP AND RIGHT;;;; 255B;BOX DRAWINGS UP SINGLE AND LEFT DOUBLE;So;0;ON;;;;;N;FORMS UP SINGLE AND LEFT DOUBLE;;;; 255C;BOX DRAWINGS UP DOUBLE AND LEFT SINGLE;So;0;ON;;;;;N;FORMS UP DOUBLE AND LEFT SINGLE;;;; 255D;BOX DRAWINGS DOUBLE UP AND LEFT;So;0;ON;;;;;N;FORMS DOUBLE UP AND LEFT;;;; 255E;BOX DRAWINGS VERTICAL SINGLE AND RIGHT DOUBLE;So;0;ON;;;;;N;FORMS VERTICAL SINGLE AND RIGHT DOUBLE;;;; 255F;BOX DRAWINGS VERTICAL DOUBLE AND RIGHT SINGLE;So;0;ON;;;;;N;FORMS VERTICAL DOUBLE AND RIGHT SINGLE;;;; 2560;BOX DRAWINGS DOUBLE VERTICAL AND RIGHT;So;0;ON;;;;;N;FORMS DOUBLE VERTICAL AND RIGHT;;;; 2561;BOX DRAWINGS VERTICAL SINGLE AND LEFT DOUBLE;So;0;ON;;;;;N;FORMS VERTICAL SINGLE AND LEFT DOUBLE;;;; 2562;BOX DRAWINGS VERTICAL DOUBLE AND LEFT SINGLE;So;0;ON;;;;;N;FORMS VERTICAL DOUBLE AND LEFT SINGLE;;;; 2563;BOX DRAWINGS DOUBLE VERTICAL AND LEFT;So;0;ON;;;;;N;FORMS DOUBLE VERTICAL AND LEFT;;;; 2564;BOX DRAWINGS DOWN SINGLE AND HORIZONTAL DOUBLE;So;0;ON;;;;;N;FORMS DOWN SINGLE AND HORIZONTAL DOUBLE;;;; 2565;BOX DRAWINGS DOWN DOUBLE AND HORIZONTAL SINGLE;So;0;ON;;;;;N;FORMS DOWN DOUBLE AND HORIZONTAL SINGLE;;;; 2566;BOX DRAWINGS DOUBLE DOWN AND HORIZONTAL;So;0;ON;;;;;N;FORMS DOUBLE DOWN AND HORIZONTAL;;;; 2567;BOX DRAWINGS UP SINGLE AND HORIZONTAL DOUBLE;So;0;ON;;;;;N;FORMS UP SINGLE AND HORIZONTAL DOUBLE;;;; 2568;BOX DRAWINGS UP DOUBLE AND HORIZONTAL SINGLE;So;0;ON;;;;;N;FORMS UP DOUBLE AND HORIZONTAL SINGLE;;;; 2569;BOX DRAWINGS DOUBLE UP AND HORIZONTAL;So;0;ON;;;;;N;FORMS DOUBLE UP AND HORIZONTAL;;;; 256A;BOX DRAWINGS VERTICAL SINGLE AND HORIZONTAL DOUBLE;So;0;ON;;;;;N;FORMS VERTICAL SINGLE AND HORIZONTAL DOUBLE;;;; 256B;BOX DRAWINGS VERTICAL DOUBLE AND HORIZONTAL SINGLE;So;0;ON;;;;;N;FORMS VERTICAL DOUBLE AND HORIZONTAL SINGLE;;;; 256C;BOX DRAWINGS DOUBLE VERTICAL AND HORIZONTAL;So;0;ON;;;;;N;FORMS DOUBLE VERTICAL AND HORIZONTAL;;;; 256D;BOX DRAWINGS LIGHT ARC DOWN AND RIGHT;So;0;ON;;;;;N;FORMS LIGHT ARC DOWN AND RIGHT;;;; 256E;BOX DRAWINGS LIGHT ARC DOWN AND LEFT;So;0;ON;;;;;N;FORMS LIGHT ARC DOWN AND LEFT;;;; 256F;BOX DRAWINGS LIGHT ARC UP AND LEFT;So;0;ON;;;;;N;FORMS LIGHT ARC UP AND LEFT;;;; 2570;BOX DRAWINGS LIGHT ARC UP AND RIGHT;So;0;ON;;;;;N;FORMS LIGHT ARC UP AND RIGHT;;;; 2571;BOX DRAWINGS LIGHT DIAGONAL UPPER RIGHT TO LOWER LEFT;So;0;ON;;;;;N;FORMS LIGHT DIAGONAL UPPER RIGHT TO LOWER LEFT;;;; 2572;BOX DRAWINGS LIGHT DIAGONAL UPPER LEFT TO LOWER RIGHT;So;0;ON;;;;;N;FORMS LIGHT DIAGONAL UPPER LEFT TO LOWER RIGHT;;;; 2573;BOX DRAWINGS LIGHT DIAGONAL CROSS;So;0;ON;;;;;N;FORMS LIGHT DIAGONAL CROSS;;;; 2574;BOX DRAWINGS LIGHT LEFT;So;0;ON;;;;;N;FORMS LIGHT LEFT;;;; 2575;BOX DRAWINGS LIGHT UP;So;0;ON;;;;;N;FORMS LIGHT UP;;;; 2576;BOX DRAWINGS LIGHT RIGHT;So;0;ON;;;;;N;FORMS LIGHT RIGHT;;;; 2577;BOX DRAWINGS LIGHT DOWN;So;0;ON;;;;;N;FORMS LIGHT DOWN;;;; 2578;BOX DRAWINGS HEAVY LEFT;So;0;ON;;;;;N;FORMS HEAVY LEFT;;;; 2579;BOX DRAWINGS HEAVY UP;So;0;ON;;;;;N;FORMS HEAVY UP;;;; 257A;BOX DRAWINGS HEAVY RIGHT;So;0;ON;;;;;N;FORMS HEAVY RIGHT;;;; 257B;BOX DRAWINGS HEAVY DOWN;So;0;ON;;;;;N;FORMS HEAVY DOWN;;;; 257C;BOX DRAWINGS LIGHT LEFT AND HEAVY RIGHT;So;0;ON;;;;;N;FORMS LIGHT LEFT AND HEAVY RIGHT;;;; 257D;BOX DRAWINGS LIGHT UP AND HEAVY DOWN;So;0;ON;;;;;N;FORMS LIGHT UP AND HEAVY DOWN;;;; 257E;BOX DRAWINGS HEAVY LEFT AND LIGHT RIGHT;So;0;ON;;;;;N;FORMS HEAVY LEFT AND LIGHT RIGHT;;;; 257F;BOX DRAWINGS HEAVY UP AND LIGHT DOWN;So;0;ON;;;;;N;FORMS HEAVY UP AND LIGHT DOWN;;;; 2580;UPPER HALF BLOCK;So;0;ON;;;;;N;;;;; 2581;LOWER ONE EIGHTH BLOCK;So;0;ON;;;;;N;;;;; 2582;LOWER ONE QUARTER BLOCK;So;0;ON;;;;;N;;;;; 2583;LOWER THREE EIGHTHS BLOCK;So;0;ON;;;;;N;;;;; 2584;LOWER HALF BLOCK;So;0;ON;;;;;N;;;;; 2585;LOWER FIVE EIGHTHS BLOCK;So;0;ON;;;;;N;;;;; 2586;LOWER THREE QUARTERS BLOCK;So;0;ON;;;;;N;LOWER THREE QUARTER BLOCK;;;; 2587;LOWER SEVEN EIGHTHS BLOCK;So;0;ON;;;;;N;;;;; 2588;FULL BLOCK;So;0;ON;;;;;N;;;;; 2589;LEFT SEVEN EIGHTHS BLOCK;So;0;ON;;;;;N;;;;; 258A;LEFT THREE QUARTERS BLOCK;So;0;ON;;;;;N;LEFT THREE QUARTER BLOCK;;;; 258B;LEFT FIVE EIGHTHS BLOCK;So;0;ON;;;;;N;;;;; 258C;LEFT HALF BLOCK;So;0;ON;;;;;N;;;;; 258D;LEFT THREE EIGHTHS BLOCK;So;0;ON;;;;;N;;;;; 258E;LEFT ONE QUARTER BLOCK;So;0;ON;;;;;N;;;;; 258F;LEFT ONE EIGHTH BLOCK;So;0;ON;;;;;N;;;;; 2590;RIGHT HALF BLOCK;So;0;ON;;;;;N;;;;; 2591;LIGHT SHADE;So;0;ON;;;;;N;;;;; 2592;MEDIUM SHADE;So;0;ON;;;;;N;;;;; 2593;DARK SHADE;So;0;ON;;;;;N;;;;; 2594;UPPER ONE EIGHTH BLOCK;So;0;ON;;;;;N;;;;; 2595;RIGHT ONE EIGHTH BLOCK;So;0;ON;;;;;N;;;;; 2596;QUADRANT LOWER LEFT;So;0;ON;;;;;N;;;;; 2597;QUADRANT LOWER RIGHT;So;0;ON;;;;;N;;;;; 2598;QUADRANT UPPER LEFT;So;0;ON;;;;;N;;;;; 2599;QUADRANT UPPER LEFT AND LOWER LEFT AND LOWER RIGHT;So;0;ON;;;;;N;;;;; 259A;QUADRANT UPPER LEFT AND LOWER RIGHT;So;0;ON;;;;;N;;;;; 259B;QUADRANT UPPER LEFT AND UPPER RIGHT AND LOWER LEFT;So;0;ON;;;;;N;;;;; 259C;QUADRANT UPPER LEFT AND UPPER RIGHT AND LOWER RIGHT;So;0;ON;;;;;N;;;;; 259D;QUADRANT UPPER RIGHT;So;0;ON;;;;;N;;;;; 259E;QUADRANT UPPER RIGHT AND LOWER LEFT;So;0;ON;;;;;N;;;;; 259F;QUADRANT UPPER RIGHT AND LOWER LEFT AND LOWER RIGHT;So;0;ON;;;;;N;;;;; 25A0;BLACK SQUARE;So;0;ON;;;;;N;;;;; 25A1;WHITE SQUARE;So;0;ON;;;;;N;;;;; 25A2;WHITE SQUARE WITH ROUNDED CORNERS;So;0;ON;;;;;N;;;;; 25A3;WHITE SQUARE CONTAINING BLACK SMALL SQUARE;So;0;ON;;;;;N;;;;; 25A4;SQUARE WITH HORIZONTAL FILL;So;0;ON;;;;;N;;;;; 25A5;SQUARE WITH VERTICAL FILL;So;0;ON;;;;;N;;;;; 25A6;SQUARE WITH ORTHOGONAL CROSSHATCH FILL;So;0;ON;;;;;N;;;;; 25A7;SQUARE WITH UPPER LEFT TO LOWER RIGHT FILL;So;0;ON;;;;;N;;;;; 25A8;SQUARE WITH UPPER RIGHT TO LOWER LEFT FILL;So;0;ON;;;;;N;;;;; 25A9;SQUARE WITH DIAGONAL CROSSHATCH FILL;So;0;ON;;;;;N;;;;; 25AA;BLACK SMALL SQUARE;So;0;ON;;;;;N;;;;; 25AB;WHITE SMALL SQUARE;So;0;ON;;;;;N;;;;; 25AC;BLACK RECTANGLE;So;0;ON;;;;;N;;;;; 25AD;WHITE RECTANGLE;So;0;ON;;;;;N;;;;; 25AE;BLACK VERTICAL RECTANGLE;So;0;ON;;;;;N;;;;; 25AF;WHITE VERTICAL RECTANGLE;So;0;ON;;;;;N;;;;; 25B0;BLACK PARALLELOGRAM;So;0;ON;;;;;N;;;;; 25B1;WHITE PARALLELOGRAM;So;0;ON;;;;;N;;;;; 25B2;BLACK UP-POINTING TRIANGLE;So;0;ON;;;;;N;BLACK UP POINTING TRIANGLE;;;; 25B3;WHITE UP-POINTING TRIANGLE;So;0;ON;;;;;N;WHITE UP POINTING TRIANGLE;;;; 25B4;BLACK UP-POINTING SMALL TRIANGLE;So;0;ON;;;;;N;BLACK UP POINTING SMALL TRIANGLE;;;; 25B5;WHITE UP-POINTING SMALL TRIANGLE;So;0;ON;;;;;N;WHITE UP POINTING SMALL TRIANGLE;;;; 25B6;BLACK RIGHT-POINTING TRIANGLE;So;0;ON;;;;;N;BLACK RIGHT POINTING TRIANGLE;;;; 25B7;WHITE RIGHT-POINTING TRIANGLE;Sm;0;ON;;;;;N;WHITE RIGHT POINTING TRIANGLE;;;; 25B8;BLACK RIGHT-POINTING SMALL TRIANGLE;So;0;ON;;;;;N;BLACK RIGHT POINTING SMALL TRIANGLE;;;; 25B9;WHITE RIGHT-POINTING SMALL TRIANGLE;So;0;ON;;;;;N;WHITE RIGHT POINTING SMALL TRIANGLE;;;; 25BA;BLACK RIGHT-POINTING POINTER;So;0;ON;;;;;N;BLACK RIGHT POINTING POINTER;;;; 25BB;WHITE RIGHT-POINTING POINTER;So;0;ON;;;;;N;WHITE RIGHT POINTING POINTER;;;; 25BC;BLACK DOWN-POINTING TRIANGLE;So;0;ON;;;;;N;BLACK DOWN POINTING TRIANGLE;;;; 25BD;WHITE DOWN-POINTING TRIANGLE;So;0;ON;;;;;N;WHITE DOWN POINTING TRIANGLE;;;; 25BE;BLACK DOWN-POINTING SMALL TRIANGLE;So;0;ON;;;;;N;BLACK DOWN POINTING SMALL TRIANGLE;;;; 25BF;WHITE DOWN-POINTING SMALL TRIANGLE;So;0;ON;;;;;N;WHITE DOWN POINTING SMALL TRIANGLE;;;; 25C0;BLACK LEFT-POINTING TRIANGLE;So;0;ON;;;;;N;BLACK LEFT POINTING TRIANGLE;;;; 25C1;WHITE LEFT-POINTING TRIANGLE;Sm;0;ON;;;;;N;WHITE LEFT POINTING TRIANGLE;;;; 25C2;BLACK LEFT-POINTING SMALL TRIANGLE;So;0;ON;;;;;N;BLACK LEFT POINTING SMALL TRIANGLE;;;; 25C3;WHITE LEFT-POINTING SMALL TRIANGLE;So;0;ON;;;;;N;WHITE LEFT POINTING SMALL TRIANGLE;;;; 25C4;BLACK LEFT-POINTING POINTER;So;0;ON;;;;;N;BLACK LEFT POINTING POINTER;;;; 25C5;WHITE LEFT-POINTING POINTER;So;0;ON;;;;;N;WHITE LEFT POINTING POINTER;;;; 25C6;BLACK DIAMOND;So;0;ON;;;;;N;;;;; 25C7;WHITE DIAMOND;So;0;ON;;;;;N;;;;; 25C8;WHITE DIAMOND CONTAINING BLACK SMALL DIAMOND;So;0;ON;;;;;N;;;;; 25C9;FISHEYE;So;0;ON;;;;;N;;;;; 25CA;LOZENGE;So;0;ON;;;;;N;;;;; 25CB;WHITE CIRCLE;So;0;ON;;;;;N;;;;; 25CC;DOTTED CIRCLE;So;0;ON;;;;;N;;;;; 25CD;CIRCLE WITH VERTICAL FILL;So;0;ON;;;;;N;;;;; 25CE;BULLSEYE;So;0;ON;;;;;N;;;;; 25CF;BLACK CIRCLE;So;0;ON;;;;;N;;;;; 25D0;CIRCLE WITH LEFT HALF BLACK;So;0;ON;;;;;N;;;;; 25D1;CIRCLE WITH RIGHT HALF BLACK;So;0;ON;;;;;N;;;;; 25D2;CIRCLE WITH LOWER HALF BLACK;So;0;ON;;;;;N;;;;; 25D3;CIRCLE WITH UPPER HALF BLACK;So;0;ON;;;;;N;;;;; 25D4;CIRCLE WITH UPPER RIGHT QUADRANT BLACK;So;0;ON;;;;;N;;;;; 25D5;CIRCLE WITH ALL BUT UPPER LEFT QUADRANT BLACK;So;0;ON;;;;;N;;;;; 25D6;LEFT HALF BLACK CIRCLE;So;0;ON;;;;;N;;;;; 25D7;RIGHT HALF BLACK CIRCLE;So;0;ON;;;;;N;;;;; 25D8;INVERSE BULLET;So;0;ON;;;;;N;;;;; 25D9;INVERSE WHITE CIRCLE;So;0;ON;;;;;N;;;;; 25DA;UPPER HALF INVERSE WHITE CIRCLE;So;0;ON;;;;;N;;;;; 25DB;LOWER HALF INVERSE WHITE CIRCLE;So;0;ON;;;;;N;;;;; 25DC;UPPER LEFT QUADRANT CIRCULAR ARC;So;0;ON;;;;;N;;;;; 25DD;UPPER RIGHT QUADRANT CIRCULAR ARC;So;0;ON;;;;;N;;;;; 25DE;LOWER RIGHT QUADRANT CIRCULAR ARC;So;0;ON;;;;;N;;;;; 25DF;LOWER LEFT QUADRANT CIRCULAR ARC;So;0;ON;;;;;N;;;;; 25E0;UPPER HALF CIRCLE;So;0;ON;;;;;N;;;;; 25E1;LOWER HALF CIRCLE;So;0;ON;;;;;N;;;;; 25E2;BLACK LOWER RIGHT TRIANGLE;So;0;ON;;;;;N;;;;; 25E3;BLACK LOWER LEFT TRIANGLE;So;0;ON;;;;;N;;;;; 25E4;BLACK UPPER LEFT TRIANGLE;So;0;ON;;;;;N;;;;; 25E5;BLACK UPPER RIGHT TRIANGLE;So;0;ON;;;;;N;;;;; 25E6;WHITE BULLET;So;0;ON;;;;;N;;;;; 25E7;SQUARE WITH LEFT HALF BLACK;So;0;ON;;;;;N;;;;; 25E8;SQUARE WITH RIGHT HALF BLACK;So;0;ON;;;;;N;;;;; 25E9;SQUARE WITH UPPER LEFT DIAGONAL HALF BLACK;So;0;ON;;;;;N;;;;; 25EA;SQUARE WITH LOWER RIGHT DIAGONAL HALF BLACK;So;0;ON;;;;;N;;;;; 25EB;WHITE SQUARE WITH VERTICAL BISECTING LINE;So;0;ON;;;;;N;;;;; 25EC;WHITE UP-POINTING TRIANGLE WITH DOT;So;0;ON;;;;;N;WHITE UP POINTING TRIANGLE WITH DOT;;;; 25ED;UP-POINTING TRIANGLE WITH LEFT HALF BLACK;So;0;ON;;;;;N;UP POINTING TRIANGLE WITH LEFT HALF BLACK;;;; 25EE;UP-POINTING TRIANGLE WITH RIGHT HALF BLACK;So;0;ON;;;;;N;UP POINTING TRIANGLE WITH RIGHT HALF BLACK;;;; 25EF;LARGE CIRCLE;So;0;ON;;;;;N;;;;; 25F0;WHITE SQUARE WITH UPPER LEFT QUADRANT;So;0;ON;;;;;N;;;;; 25F1;WHITE SQUARE WITH LOWER LEFT QUADRANT;So;0;ON;;;;;N;;;;; 25F2;WHITE SQUARE WITH LOWER RIGHT QUADRANT;So;0;ON;;;;;N;;;;; 25F3;WHITE SQUARE WITH UPPER RIGHT QUADRANT;So;0;ON;;;;;N;;;;; 25F4;WHITE CIRCLE WITH UPPER LEFT QUADRANT;So;0;ON;;;;;N;;;;; 25F5;WHITE CIRCLE WITH LOWER LEFT QUADRANT;So;0;ON;;;;;N;;;;; 25F6;WHITE CIRCLE WITH LOWER RIGHT QUADRANT;So;0;ON;;;;;N;;;;; 25F7;WHITE CIRCLE WITH UPPER RIGHT QUADRANT;So;0;ON;;;;;N;;;;; 25F8;UPPER LEFT TRIANGLE;Sm;0;ON;;;;;N;;;;; 25F9;UPPER RIGHT TRIANGLE;Sm;0;ON;;;;;N;;;;; 25FA;LOWER LEFT TRIANGLE;Sm;0;ON;;;;;N;;;;; 25FB;WHITE MEDIUM SQUARE;Sm;0;ON;;;;;N;;;;; 25FC;BLACK MEDIUM SQUARE;Sm;0;ON;;;;;N;;;;; 25FD;WHITE MEDIUM SMALL SQUARE;Sm;0;ON;;;;;N;;;;; 25FE;BLACK MEDIUM SMALL SQUARE;Sm;0;ON;;;;;N;;;;; 25FF;LOWER RIGHT TRIANGLE;Sm;0;ON;;;;;N;;;;; 2600;BLACK SUN WITH RAYS;So;0;ON;;;;;N;;;;; 2601;CLOUD;So;0;ON;;;;;N;;;;; 2602;UMBRELLA;So;0;ON;;;;;N;;;;; 2603;SNOWMAN;So;0;ON;;;;;N;;;;; 2604;COMET;So;0;ON;;;;;N;;;;; 2605;BLACK STAR;So;0;ON;;;;;N;;;;; 2606;WHITE STAR;So;0;ON;;;;;N;;;;; 2607;LIGHTNING;So;0;ON;;;;;N;;;;; 2608;THUNDERSTORM;So;0;ON;;;;;N;;;;; 2609;SUN;So;0;ON;;;;;N;;;;; 260A;ASCENDING NODE;So;0;ON;;;;;N;;;;; 260B;DESCENDING NODE;So;0;ON;;;;;N;;;;; 260C;CONJUNCTION;So;0;ON;;;;;N;;;;; 260D;OPPOSITION;So;0;ON;;;;;N;;;;; 260E;BLACK TELEPHONE;So;0;ON;;;;;N;;;;; 260F;WHITE TELEPHONE;So;0;ON;;;;;N;;;;; 2610;BALLOT BOX;So;0;ON;;;;;N;;;;; 2611;BALLOT BOX WITH CHECK;So;0;ON;;;;;N;;;;; 2612;BALLOT BOX WITH X;So;0;ON;;;;;N;;;;; 2613;SALTIRE;So;0;ON;;;;;N;;;;; 2614;UMBRELLA WITH RAIN DROPS;So;0;ON;;;;;N;;;;; 2615;HOT BEVERAGE;So;0;ON;;;;;N;;;;; 2616;WHITE SHOGI PIECE;So;0;ON;;;;;N;;;;; 2617;BLACK SHOGI PIECE;So;0;ON;;;;;N;;;;; 2618;SHAMROCK;So;0;ON;;;;;N;;;;; 2619;REVERSED ROTATED FLORAL HEART BULLET;So;0;ON;;;;;N;;;;; 261A;BLACK LEFT POINTING INDEX;So;0;ON;;;;;N;;;;; 261B;BLACK RIGHT POINTING INDEX;So;0;ON;;;;;N;;;;; 261C;WHITE LEFT POINTING INDEX;So;0;ON;;;;;N;;;;; 261D;WHITE UP POINTING INDEX;So;0;ON;;;;;N;;;;; 261E;WHITE RIGHT POINTING INDEX;So;0;ON;;;;;N;;;;; 261F;WHITE DOWN POINTING INDEX;So;0;ON;;;;;N;;;;; 2620;SKULL AND CROSSBONES;So;0;ON;;;;;N;;;;; 2621;CAUTION SIGN;So;0;ON;;;;;N;;;;; 2622;RADIOACTIVE SIGN;So;0;ON;;;;;N;;;;; 2623;BIOHAZARD SIGN;So;0;ON;;;;;N;;;;; 2624;CADUCEUS;So;0;ON;;;;;N;;;;; 2625;ANKH;So;0;ON;;;;;N;;;;; 2626;ORTHODOX CROSS;So;0;ON;;;;;N;;;;; 2627;CHI RHO;So;0;ON;;;;;N;;;;; 2628;CROSS OF LORRAINE;So;0;ON;;;;;N;;;;; 2629;CROSS OF JERUSALEM;So;0;ON;;;;;N;;;;; 262A;STAR AND CRESCENT;So;0;ON;;;;;N;;;;; 262B;FARSI SYMBOL;So;0;ON;;;;;N;SYMBOL OF IRAN;;;; 262C;ADI SHAKTI;So;0;ON;;;;;N;;;;; 262D;HAMMER AND SICKLE;So;0;ON;;;;;N;;;;; 262E;PEACE SYMBOL;So;0;ON;;;;;N;;;;; 262F;YIN YANG;So;0;ON;;;;;N;;;;; 2630;TRIGRAM FOR HEAVEN;So;0;ON;;;;;N;;;;; 2631;TRIGRAM FOR LAKE;So;0;ON;;;;;N;;;;; 2632;TRIGRAM FOR FIRE;So;0;ON;;;;;N;;;;; 2633;TRIGRAM FOR THUNDER;So;0;ON;;;;;N;;;;; 2634;TRIGRAM FOR WIND;So;0;ON;;;;;N;;;;; 2635;TRIGRAM FOR WATER;So;0;ON;;;;;N;;;;; 2636;TRIGRAM FOR MOUNTAIN;So;0;ON;;;;;N;;;;; 2637;TRIGRAM FOR EARTH;So;0;ON;;;;;N;;;;; 2638;WHEEL OF DHARMA;So;0;ON;;;;;N;;;;; 2639;WHITE FROWNING FACE;So;0;ON;;;;;N;;;;; 263A;WHITE SMILING FACE;So;0;ON;;;;;N;;;;; 263B;BLACK SMILING FACE;So;0;ON;;;;;N;;;;; 263C;WHITE SUN WITH RAYS;So;0;ON;;;;;N;;;;; 263D;FIRST QUARTER MOON;So;0;ON;;;;;N;;;;; 263E;LAST QUARTER MOON;So;0;ON;;;;;N;;;;; 263F;MERCURY;So;0;ON;;;;;N;;;;; 2640;FEMALE SIGN;So;0;ON;;;;;N;;;;; 2641;EARTH;So;0;ON;;;;;N;;;;; 2642;MALE SIGN;So;0;ON;;;;;N;;;;; 2643;JUPITER;So;0;ON;;;;;N;;;;; 2644;SATURN;So;0;ON;;;;;N;;;;; 2645;URANUS;So;0;ON;;;;;N;;;;; 2646;NEPTUNE;So;0;ON;;;;;N;;;;; 2647;PLUTO;So;0;ON;;;;;N;;;;; 2648;ARIES;So;0;ON;;;;;N;;;;; 2649;TAURUS;So;0;ON;;;;;N;;;;; 264A;GEMINI;So;0;ON;;;;;N;;;;; 264B;CANCER;So;0;ON;;;;;N;;;;; 264C;LEO;So;0;ON;;;;;N;;;;; 264D;VIRGO;So;0;ON;;;;;N;;;;; 264E;LIBRA;So;0;ON;;;;;N;;;;; 264F;SCORPIUS;So;0;ON;;;;;N;;;;; 2650;SAGITTARIUS;So;0;ON;;;;;N;;;;; 2651;CAPRICORN;So;0;ON;;;;;N;;;;; 2652;AQUARIUS;So;0;ON;;;;;N;;;;; 2653;PISCES;So;0;ON;;;;;N;;;;; 2654;WHITE CHESS KING;So;0;ON;;;;;N;;;;; 2655;WHITE CHESS QUEEN;So;0;ON;;;;;N;;;;; 2656;WHITE CHESS ROOK;So;0;ON;;;;;N;;;;; 2657;WHITE CHESS BISHOP;So;0;ON;;;;;N;;;;; 2658;WHITE CHESS KNIGHT;So;0;ON;;;;;N;;;;; 2659;WHITE CHESS PAWN;So;0;ON;;;;;N;;;;; 265A;BLACK CHESS KING;So;0;ON;;;;;N;;;;; 265B;BLACK CHESS QUEEN;So;0;ON;;;;;N;;;;; 265C;BLACK CHESS ROOK;So;0;ON;;;;;N;;;;; 265D;BLACK CHESS BISHOP;So;0;ON;;;;;N;;;;; 265E;BLACK CHESS KNIGHT;So;0;ON;;;;;N;;;;; 265F;BLACK CHESS PAWN;So;0;ON;;;;;N;;;;; 2660;BLACK SPADE SUIT;So;0;ON;;;;;N;;;;; 2661;WHITE HEART SUIT;So;0;ON;;;;;N;;;;; 2662;WHITE DIAMOND SUIT;So;0;ON;;;;;N;;;;; 2663;BLACK CLUB SUIT;So;0;ON;;;;;N;;;;; 2664;WHITE SPADE SUIT;So;0;ON;;;;;N;;;;; 2665;BLACK HEART SUIT;So;0;ON;;;;;N;;;;; 2666;BLACK DIAMOND SUIT;So;0;ON;;;;;N;;;;; 2667;WHITE CLUB SUIT;So;0;ON;;;;;N;;;;; 2668;HOT SPRINGS;So;0;ON;;;;;N;;;;; 2669;QUARTER NOTE;So;0;ON;;;;;N;;;;; 266A;EIGHTH NOTE;So;0;ON;;;;;N;;;;; 266B;BEAMED EIGHTH NOTES;So;0;ON;;;;;N;BARRED EIGHTH NOTES;;;; 266C;BEAMED SIXTEENTH NOTES;So;0;ON;;;;;N;BARRED SIXTEENTH NOTES;;;; 266D;MUSIC FLAT SIGN;So;0;ON;;;;;N;FLAT;;;; 266E;MUSIC NATURAL SIGN;So;0;ON;;;;;N;NATURAL;;;; 266F;MUSIC SHARP SIGN;Sm;0;ON;;;;;N;SHARP;;;; 2670;WEST SYRIAC CROSS;So;0;ON;;;;;N;;;;; 2671;EAST SYRIAC CROSS;So;0;ON;;;;;N;;;;; 2672;UNIVERSAL RECYCLING SYMBOL;So;0;ON;;;;;N;;;;; 2673;RECYCLING SYMBOL FOR TYPE-1 PLASTICS;So;0;ON;;;;;N;;;;; 2674;RECYCLING SYMBOL FOR TYPE-2 PLASTICS;So;0;ON;;;;;N;;;;; 2675;RECYCLING SYMBOL FOR TYPE-3 PLASTICS;So;0;ON;;;;;N;;;;; 2676;RECYCLING SYMBOL FOR TYPE-4 PLASTICS;So;0;ON;;;;;N;;;;; 2677;RECYCLING SYMBOL FOR TYPE-5 PLASTICS;So;0;ON;;;;;N;;;;; 2678;RECYCLING SYMBOL FOR TYPE-6 PLASTICS;So;0;ON;;;;;N;;;;; 2679;RECYCLING SYMBOL FOR TYPE-7 PLASTICS;So;0;ON;;;;;N;;;;; 267A;RECYCLING SYMBOL FOR GENERIC MATERIALS;So;0;ON;;;;;N;;;;; 267B;BLACK UNIVERSAL RECYCLING SYMBOL;So;0;ON;;;;;N;;;;; 267C;RECYCLED PAPER SYMBOL;So;0;ON;;;;;N;;;;; 267D;PARTIALLY-RECYCLED PAPER SYMBOL;So;0;ON;;;;;N;;;;; 267E;PERMANENT PAPER SIGN;So;0;ON;;;;;N;;;;; 267F;WHEELCHAIR SYMBOL;So;0;ON;;;;;N;;;;; 2680;DIE FACE-1;So;0;ON;;;;;N;;;;; 2681;DIE FACE-2;So;0;ON;;;;;N;;;;; 2682;DIE FACE-3;So;0;ON;;;;;N;;;;; 2683;DIE FACE-4;So;0;ON;;;;;N;;;;; 2684;DIE FACE-5;So;0;ON;;;;;N;;;;; 2685;DIE FACE-6;So;0;ON;;;;;N;;;;; 2686;WHITE CIRCLE WITH DOT RIGHT;So;0;ON;;;;;N;;;;; 2687;WHITE CIRCLE WITH TWO DOTS;So;0;ON;;;;;N;;;;; 2688;BLACK CIRCLE WITH WHITE DOT RIGHT;So;0;ON;;;;;N;;;;; 2689;BLACK CIRCLE WITH TWO WHITE DOTS;So;0;ON;;;;;N;;;;; 268A;MONOGRAM FOR YANG;So;0;ON;;;;;N;;;;; 268B;MONOGRAM FOR YIN;So;0;ON;;;;;N;;;;; 268C;DIGRAM FOR GREATER YANG;So;0;ON;;;;;N;;;;; 268D;DIGRAM FOR LESSER YIN;So;0;ON;;;;;N;;;;; 268E;DIGRAM FOR LESSER YANG;So;0;ON;;;;;N;;;;; 268F;DIGRAM FOR GREATER YIN;So;0;ON;;;;;N;;;;; 2690;WHITE FLAG;So;0;ON;;;;;N;;;;; 2691;BLACK FLAG;So;0;ON;;;;;N;;;;; 2692;HAMMER AND PICK;So;0;ON;;;;;N;;;;; 2693;ANCHOR;So;0;ON;;;;;N;;;;; 2694;CROSSED SWORDS;So;0;ON;;;;;N;;;;; 2695;STAFF OF AESCULAPIUS;So;0;ON;;;;;N;;;;; 2696;SCALES;So;0;ON;;;;;N;;;;; 2697;ALEMBIC;So;0;ON;;;;;N;;;;; 2698;FLOWER;So;0;ON;;;;;N;;;;; 2699;GEAR;So;0;ON;;;;;N;;;;; 269A;STAFF OF HERMES;So;0;ON;;;;;N;;;;; 269B;ATOM SYMBOL;So;0;ON;;;;;N;;;;; 269C;FLEUR-DE-LIS;So;0;ON;;;;;N;;;;; 269D;OUTLINED WHITE STAR;So;0;ON;;;;;N;;;;; 269E;THREE LINES CONVERGING RIGHT;So;0;ON;;;;;N;;;;; 269F;THREE LINES CONVERGING LEFT;So;0;ON;;;;;N;;;;; 26A0;WARNING SIGN;So;0;ON;;;;;N;;;;; 26A1;HIGH VOLTAGE SIGN;So;0;ON;;;;;N;;;;; 26A2;DOUBLED FEMALE SIGN;So;0;ON;;;;;N;;;;; 26A3;DOUBLED MALE SIGN;So;0;ON;;;;;N;;;;; 26A4;INTERLOCKED FEMALE AND MALE SIGN;So;0;ON;;;;;N;;;;; 26A5;MALE AND FEMALE SIGN;So;0;ON;;;;;N;;;;; 26A6;MALE WITH STROKE SIGN;So;0;ON;;;;;N;;;;; 26A7;MALE WITH STROKE AND MALE AND FEMALE SIGN;So;0;ON;;;;;N;;;;; 26A8;VERTICAL MALE WITH STROKE SIGN;So;0;ON;;;;;N;;;;; 26A9;HORIZONTAL MALE WITH STROKE SIGN;So;0;ON;;;;;N;;;;; 26AA;MEDIUM WHITE CIRCLE;So;0;ON;;;;;N;;;;; 26AB;MEDIUM BLACK CIRCLE;So;0;ON;;;;;N;;;;; 26AC;MEDIUM SMALL WHITE CIRCLE;So;0;L;;;;;N;;;;; 26AD;MARRIAGE SYMBOL;So;0;ON;;;;;N;;;;; 26AE;DIVORCE SYMBOL;So;0;ON;;;;;N;;;;; 26AF;UNMARRIED PARTNERSHIP SYMBOL;So;0;ON;;;;;N;;;;; 26B0;COFFIN;So;0;ON;;;;;N;;;;; 26B1;FUNERAL URN;So;0;ON;;;;;N;;;;; 26B2;NEUTER;So;0;ON;;;;;N;;;;; 26B3;CERES;So;0;ON;;;;;N;;;;; 26B4;PALLAS;So;0;ON;;;;;N;;;;; 26B5;JUNO;So;0;ON;;;;;N;;;;; 26B6;VESTA;So;0;ON;;;;;N;;;;; 26B7;CHIRON;So;0;ON;;;;;N;;;;; 26B8;BLACK MOON LILITH;So;0;ON;;;;;N;;;;; 26B9;SEXTILE;So;0;ON;;;;;N;;;;; 26BA;SEMISEXTILE;So;0;ON;;;;;N;;;;; 26BB;QUINCUNX;So;0;ON;;;;;N;;;;; 26BC;SESQUIQUADRATE;So;0;ON;;;;;N;;;;; 26BD;SOCCER BALL;So;0;ON;;;;;N;;;;; 26BE;BASEBALL;So;0;ON;;;;;N;;;;; 26BF;SQUARED KEY;So;0;ON;;;;;N;;;;; 26C0;WHITE DRAUGHTS MAN;So;0;ON;;;;;N;;;;; 26C1;WHITE DRAUGHTS KING;So;0;ON;;;;;N;;;;; 26C2;BLACK DRAUGHTS MAN;So;0;ON;;;;;N;;;;; 26C3;BLACK DRAUGHTS KING;So;0;ON;;;;;N;;;;; 26C4;SNOWMAN WITHOUT SNOW;So;0;ON;;;;;N;;;;; 26C5;SUN BEHIND CLOUD;So;0;ON;;;;;N;;;;; 26C6;RAIN;So;0;ON;;;;;N;;;;; 26C7;BLACK SNOWMAN;So;0;ON;;;;;N;;;;; 26C8;THUNDER CLOUD AND RAIN;So;0;ON;;;;;N;;;;; 26C9;TURNED WHITE SHOGI PIECE;So;0;ON;;;;;N;;;;; 26CA;TURNED BLACK SHOGI PIECE;So;0;ON;;;;;N;;;;; 26CB;WHITE DIAMOND IN SQUARE;So;0;ON;;;;;N;;;;; 26CC;CROSSING LANES;So;0;ON;;;;;N;;;;; 26CD;DISABLED CAR;So;0;ON;;;;;N;;;;; 26CE;OPHIUCHUS;So;0;ON;;;;;N;;;;; 26CF;PICK;So;0;ON;;;;;N;;;;; 26D0;CAR SLIDING;So;0;ON;;;;;N;;;;; 26D1;HELMET WITH WHITE CROSS;So;0;ON;;;;;N;;;;; 26D2;CIRCLED CROSSING LANES;So;0;ON;;;;;N;;;;; 26D3;CHAINS;So;0;ON;;;;;N;;;;; 26D4;NO ENTRY;So;0;ON;;;;;N;;;;; 26D5;ALTERNATE ONE-WAY LEFT WAY TRAFFIC;So;0;ON;;;;;N;;;;; 26D6;BLACK TWO-WAY LEFT WAY TRAFFIC;So;0;ON;;;;;N;;;;; 26D7;WHITE TWO-WAY LEFT WAY TRAFFIC;So;0;ON;;;;;N;;;;; 26D8;BLACK LEFT LANE MERGE;So;0;ON;;;;;N;;;;; 26D9;WHITE LEFT LANE MERGE;So;0;ON;;;;;N;;;;; 26DA;DRIVE SLOW SIGN;So;0;ON;;;;;N;;;;; 26DB;HEAVY WHITE DOWN-POINTING TRIANGLE;So;0;ON;;;;;N;;;;; 26DC;LEFT CLOSED ENTRY;So;0;ON;;;;;N;;;;; 26DD;SQUARED SALTIRE;So;0;ON;;;;;N;;;;; 26DE;FALLING DIAGONAL IN WHITE CIRCLE IN BLACK SQUARE;So;0;ON;;;;;N;;;;; 26DF;BLACK TRUCK;So;0;ON;;;;;N;;;;; 26E0;RESTRICTED LEFT ENTRY-1;So;0;ON;;;;;N;;;;; 26E1;RESTRICTED LEFT ENTRY-2;So;0;ON;;;;;N;;;;; 26E2;ASTRONOMICAL SYMBOL FOR URANUS;So;0;ON;;;;;N;;;;; 26E3;HEAVY CIRCLE WITH STROKE AND TWO DOTS ABOVE;So;0;ON;;;;;N;;;;; 26E4;PENTAGRAM;So;0;ON;;;;;N;;;;; 26E5;RIGHT-HANDED INTERLACED PENTAGRAM;So;0;ON;;;;;N;;;;; 26E6;LEFT-HANDED INTERLACED PENTAGRAM;So;0;ON;;;;;N;;;;; 26E7;INVERTED PENTAGRAM;So;0;ON;;;;;N;;;;; 26E8;BLACK CROSS ON SHIELD;So;0;ON;;;;;N;;;;; 26E9;SHINTO SHRINE;So;0;ON;;;;;N;;;;; 26EA;CHURCH;So;0;ON;;;;;N;;;;; 26EB;CASTLE;So;0;ON;;;;;N;;;;; 26EC;HISTORIC SITE;So;0;ON;;;;;N;;;;; 26ED;GEAR WITHOUT HUB;So;0;ON;;;;;N;;;;; 26EE;GEAR WITH HANDLES;So;0;ON;;;;;N;;;;; 26EF;MAP SYMBOL FOR LIGHTHOUSE;So;0;ON;;;;;N;;;;; 26F0;MOUNTAIN;So;0;ON;;;;;N;;;;; 26F1;UMBRELLA ON GROUND;So;0;ON;;;;;N;;;;; 26F2;FOUNTAIN;So;0;ON;;;;;N;;;;; 26F3;FLAG IN HOLE;So;0;ON;;;;;N;;;;; 26F4;FERRY;So;0;ON;;;;;N;;;;; 26F5;SAILBOAT;So;0;ON;;;;;N;;;;; 26F6;SQUARE FOUR CORNERS;So;0;ON;;;;;N;;;;; 26F7;SKIER;So;0;ON;;;;;N;;;;; 26F8;ICE SKATE;So;0;ON;;;;;N;;;;; 26F9;PERSON WITH BALL;So;0;ON;;;;;N;;;;; 26FA;TENT;So;0;ON;;;;;N;;;;; 26FB;JAPANESE BANK SYMBOL;So;0;ON;;;;;N;;;;; 26FC;HEADSTONE GRAVEYARD SYMBOL;So;0;ON;;;;;N;;;;; 26FD;FUEL PUMP;So;0;ON;;;;;N;;;;; 26FE;CUP ON BLACK SQUARE;So;0;ON;;;;;N;;;;; 26FF;WHITE FLAG WITH HORIZONTAL MIDDLE BLACK STRIPE;So;0;ON;;;;;N;;;;; 2700;BLACK SAFETY SCISSORS;So;0;ON;;;;;N;;;;; 2701;UPPER BLADE SCISSORS;So;0;ON;;;;;N;;;;; 2702;BLACK SCISSORS;So;0;ON;;;;;N;;;;; 2703;LOWER BLADE SCISSORS;So;0;ON;;;;;N;;;;; 2704;WHITE SCISSORS;So;0;ON;;;;;N;;;;; 2705;WHITE HEAVY CHECK MARK;So;0;ON;;;;;N;;;;; 2706;TELEPHONE LOCATION SIGN;So;0;ON;;;;;N;;;;; 2707;TAPE DRIVE;So;0;ON;;;;;N;;;;; 2708;AIRPLANE;So;0;ON;;;;;N;;;;; 2709;ENVELOPE;So;0;ON;;;;;N;;;;; 270A;RAISED FIST;So;0;ON;;;;;N;;;;; 270B;RAISED HAND;So;0;ON;;;;;N;;;;; 270C;VICTORY HAND;So;0;ON;;;;;N;;;;; 270D;WRITING HAND;So;0;ON;;;;;N;;;;; 270E;LOWER RIGHT PENCIL;So;0;ON;;;;;N;;;;; 270F;PENCIL;So;0;ON;;;;;N;;;;; 2710;UPPER RIGHT PENCIL;So;0;ON;;;;;N;;;;; 2711;WHITE NIB;So;0;ON;;;;;N;;;;; 2712;BLACK NIB;So;0;ON;;;;;N;;;;; 2713;CHECK MARK;So;0;ON;;;;;N;;;;; 2714;HEAVY CHECK MARK;So;0;ON;;;;;N;;;;; 2715;MULTIPLICATION X;So;0;ON;;;;;N;;;;; 2716;HEAVY MULTIPLICATION X;So;0;ON;;;;;N;;;;; 2717;BALLOT X;So;0;ON;;;;;N;;;;; 2718;HEAVY BALLOT X;So;0;ON;;;;;N;;;;; 2719;OUTLINED GREEK CROSS;So;0;ON;;;;;N;;;;; 271A;HEAVY GREEK CROSS;So;0;ON;;;;;N;;;;; 271B;OPEN CENTRE CROSS;So;0;ON;;;;;N;OPEN CENTER CROSS;;;; 271C;HEAVY OPEN CENTRE CROSS;So;0;ON;;;;;N;HEAVY OPEN CENTER CROSS;;;; 271D;LATIN CROSS;So;0;ON;;;;;N;;;;; 271E;SHADOWED WHITE LATIN CROSS;So;0;ON;;;;;N;;;;; 271F;OUTLINED LATIN CROSS;So;0;ON;;;;;N;;;;; 2720;MALTESE CROSS;So;0;ON;;;;;N;;;;; 2721;STAR OF DAVID;So;0;ON;;;;;N;;;;; 2722;FOUR TEARDROP-SPOKED ASTERISK;So;0;ON;;;;;N;;;;; 2723;FOUR BALLOON-SPOKED ASTERISK;So;0;ON;;;;;N;;;;; 2724;HEAVY FOUR BALLOON-SPOKED ASTERISK;So;0;ON;;;;;N;;;;; 2725;FOUR CLUB-SPOKED ASTERISK;So;0;ON;;;;;N;;;;; 2726;BLACK FOUR POINTED STAR;So;0;ON;;;;;N;;;;; 2727;WHITE FOUR POINTED STAR;So;0;ON;;;;;N;;;;; 2728;SPARKLES;So;0;ON;;;;;N;;;;; 2729;STRESS OUTLINED WHITE STAR;So;0;ON;;;;;N;;;;; 272A;CIRCLED WHITE STAR;So;0;ON;;;;;N;;;;; 272B;OPEN CENTRE BLACK STAR;So;0;ON;;;;;N;OPEN CENTER BLACK STAR;;;; 272C;BLACK CENTRE WHITE STAR;So;0;ON;;;;;N;BLACK CENTER WHITE STAR;;;; 272D;OUTLINED BLACK STAR;So;0;ON;;;;;N;;;;; 272E;HEAVY OUTLINED BLACK STAR;So;0;ON;;;;;N;;;;; 272F;PINWHEEL STAR;So;0;ON;;;;;N;;;;; 2730;SHADOWED WHITE STAR;So;0;ON;;;;;N;;;;; 2731;HEAVY ASTERISK;So;0;ON;;;;;N;;;;; 2732;OPEN CENTRE ASTERISK;So;0;ON;;;;;N;OPEN CENTER ASTERISK;;;; 2733;EIGHT SPOKED ASTERISK;So;0;ON;;;;;N;;;;; 2734;EIGHT POINTED BLACK STAR;So;0;ON;;;;;N;;;;; 2735;EIGHT POINTED PINWHEEL STAR;So;0;ON;;;;;N;;;;; 2736;SIX POINTED BLACK STAR;So;0;ON;;;;;N;;;;; 2737;EIGHT POINTED RECTILINEAR BLACK STAR;So;0;ON;;;;;N;;;;; 2738;HEAVY EIGHT POINTED RECTILINEAR BLACK STAR;So;0;ON;;;;;N;;;;; 2739;TWELVE POINTED BLACK STAR;So;0;ON;;;;;N;;;;; 273A;SIXTEEN POINTED ASTERISK;So;0;ON;;;;;N;;;;; 273B;TEARDROP-SPOKED ASTERISK;So;0;ON;;;;;N;;;;; 273C;OPEN CENTRE TEARDROP-SPOKED ASTERISK;So;0;ON;;;;;N;OPEN CENTER TEARDROP-SPOKED ASTERISK;;;; 273D;HEAVY TEARDROP-SPOKED ASTERISK;So;0;ON;;;;;N;;;;; 273E;SIX PETALLED BLACK AND WHITE FLORETTE;So;0;ON;;;;;N;;;;; 273F;BLACK FLORETTE;So;0;ON;;;;;N;;;;; 2740;WHITE FLORETTE;So;0;ON;;;;;N;;;;; 2741;EIGHT PETALLED OUTLINED BLACK FLORETTE;So;0;ON;;;;;N;;;;; 2742;CIRCLED OPEN CENTRE EIGHT POINTED STAR;So;0;ON;;;;;N;CIRCLED OPEN CENTER EIGHT POINTED STAR;;;; 2743;HEAVY TEARDROP-SPOKED PINWHEEL ASTERISK;So;0;ON;;;;;N;;;;; 2744;SNOWFLAKE;So;0;ON;;;;;N;;;;; 2745;TIGHT TRIFOLIATE SNOWFLAKE;So;0;ON;;;;;N;;;;; 2746;HEAVY CHEVRON SNOWFLAKE;So;0;ON;;;;;N;;;;; 2747;SPARKLE;So;0;ON;;;;;N;;;;; 2748;HEAVY SPARKLE;So;0;ON;;;;;N;;;;; 2749;BALLOON-SPOKED ASTERISK;So;0;ON;;;;;N;;;;; 274A;EIGHT TEARDROP-SPOKED PROPELLER ASTERISK;So;0;ON;;;;;N;;;;; 274B;HEAVY EIGHT TEARDROP-SPOKED PROPELLER ASTERISK;So;0;ON;;;;;N;;;;; 274C;CROSS MARK;So;0;ON;;;;;N;;;;; 274D;SHADOWED WHITE CIRCLE;So;0;ON;;;;;N;;;;; 274E;NEGATIVE SQUARED CROSS MARK;So;0;ON;;;;;N;;;;; 274F;LOWER RIGHT DROP-SHADOWED WHITE SQUARE;So;0;ON;;;;;N;;;;; 2750;UPPER RIGHT DROP-SHADOWED WHITE SQUARE;So;0;ON;;;;;N;;;;; 2751;LOWER RIGHT SHADOWED WHITE SQUARE;So;0;ON;;;;;N;;;;; 2752;UPPER RIGHT SHADOWED WHITE SQUARE;So;0;ON;;;;;N;;;;; 2753;BLACK QUESTION MARK ORNAMENT;So;0;ON;;;;;N;;;;; 2754;WHITE QUESTION MARK ORNAMENT;So;0;ON;;;;;N;;;;; 2755;WHITE EXCLAMATION MARK ORNAMENT;So;0;ON;;;;;N;;;;; 2756;BLACK DIAMOND MINUS WHITE X;So;0;ON;;;;;N;;;;; 2757;HEAVY EXCLAMATION MARK SYMBOL;So;0;ON;;;;;N;;;;; 2758;LIGHT VERTICAL BAR;So;0;ON;;;;;N;;;;; 2759;MEDIUM VERTICAL BAR;So;0;ON;;;;;N;;;;; 275A;HEAVY VERTICAL BAR;So;0;ON;;;;;N;;;;; 275B;HEAVY SINGLE TURNED COMMA QUOTATION MARK ORNAMENT;So;0;ON;;;;;N;;;;; 275C;HEAVY SINGLE COMMA QUOTATION MARK ORNAMENT;So;0;ON;;;;;N;;;;; 275D;HEAVY DOUBLE TURNED COMMA QUOTATION MARK ORNAMENT;So;0;ON;;;;;N;;;;; 275E;HEAVY DOUBLE COMMA QUOTATION MARK ORNAMENT;So;0;ON;;;;;N;;;;; 275F;HEAVY LOW SINGLE COMMA QUOTATION MARK ORNAMENT;So;0;ON;;;;;N;;;;; 2760;HEAVY LOW DOUBLE COMMA QUOTATION MARK ORNAMENT;So;0;ON;;;;;N;;;;; 2761;CURVED STEM PARAGRAPH SIGN ORNAMENT;So;0;ON;;;;;N;;;;; 2762;HEAVY EXCLAMATION MARK ORNAMENT;So;0;ON;;;;;N;;;;; 2763;HEAVY HEART EXCLAMATION MARK ORNAMENT;So;0;ON;;;;;N;;;;; 2764;HEAVY BLACK HEART;So;0;ON;;;;;N;;;;; 2765;ROTATED HEAVY BLACK HEART BULLET;So;0;ON;;;;;N;;;;; 2766;FLORAL HEART;So;0;ON;;;;;N;;;;; 2767;ROTATED FLORAL HEART BULLET;So;0;ON;;;;;N;;;;; 2768;MEDIUM LEFT PARENTHESIS ORNAMENT;Ps;0;ON;;;;;Y;;;;; 2769;MEDIUM RIGHT PARENTHESIS ORNAMENT;Pe;0;ON;;;;;Y;;;;; 276A;MEDIUM FLATTENED LEFT PARENTHESIS ORNAMENT;Ps;0;ON;;;;;Y;;;;; 276B;MEDIUM FLATTENED RIGHT PARENTHESIS ORNAMENT;Pe;0;ON;;;;;Y;;;;; 276C;MEDIUM LEFT-POINTING ANGLE BRACKET ORNAMENT;Ps;0;ON;;;;;Y;;;;; 276D;MEDIUM RIGHT-POINTING ANGLE BRACKET ORNAMENT;Pe;0;ON;;;;;Y;;;;; 276E;HEAVY LEFT-POINTING ANGLE QUOTATION MARK ORNAMENT;Ps;0;ON;;;;;Y;;;;; 276F;HEAVY RIGHT-POINTING ANGLE QUOTATION MARK ORNAMENT;Pe;0;ON;;;;;Y;;;;; 2770;HEAVY LEFT-POINTING ANGLE BRACKET ORNAMENT;Ps;0;ON;;;;;Y;;;;; 2771;HEAVY RIGHT-POINTING ANGLE BRACKET ORNAMENT;Pe;0;ON;;;;;Y;;;;; 2772;LIGHT LEFT TORTOISE SHELL BRACKET ORNAMENT;Ps;0;ON;;;;;Y;;;;; 2773;LIGHT RIGHT TORTOISE SHELL BRACKET ORNAMENT;Pe;0;ON;;;;;Y;;;;; 2774;MEDIUM LEFT CURLY BRACKET ORNAMENT;Ps;0;ON;;;;;Y;;;;; 2775;MEDIUM RIGHT CURLY BRACKET ORNAMENT;Pe;0;ON;;;;;Y;;;;; 2776;DINGBAT NEGATIVE CIRCLED DIGIT ONE;No;0;ON;;;1;1;N;INVERSE CIRCLED DIGIT ONE;;;; 2777;DINGBAT NEGATIVE CIRCLED DIGIT TWO;No;0;ON;;;2;2;N;INVERSE CIRCLED DIGIT TWO;;;; 2778;DINGBAT NEGATIVE CIRCLED DIGIT THREE;No;0;ON;;;3;3;N;INVERSE CIRCLED DIGIT THREE;;;; 2779;DINGBAT NEGATIVE CIRCLED DIGIT FOUR;No;0;ON;;;4;4;N;INVERSE CIRCLED DIGIT FOUR;;;; 277A;DINGBAT NEGATIVE CIRCLED DIGIT FIVE;No;0;ON;;;5;5;N;INVERSE CIRCLED DIGIT FIVE;;;; 277B;DINGBAT NEGATIVE CIRCLED DIGIT SIX;No;0;ON;;;6;6;N;INVERSE CIRCLED DIGIT SIX;;;; 277C;DINGBAT NEGATIVE CIRCLED DIGIT SEVEN;No;0;ON;;;7;7;N;INVERSE CIRCLED DIGIT SEVEN;;;; 277D;DINGBAT NEGATIVE CIRCLED DIGIT EIGHT;No;0;ON;;;8;8;N;INVERSE CIRCLED DIGIT EIGHT;;;; 277E;DINGBAT NEGATIVE CIRCLED DIGIT NINE;No;0;ON;;;9;9;N;INVERSE CIRCLED DIGIT NINE;;;; 277F;DINGBAT NEGATIVE CIRCLED NUMBER TEN;No;0;ON;;;;10;N;INVERSE CIRCLED NUMBER TEN;;;; 2780;DINGBAT CIRCLED SANS-SERIF DIGIT ONE;No;0;ON;;;1;1;N;CIRCLED SANS-SERIF DIGIT ONE;;;; 2781;DINGBAT CIRCLED SANS-SERIF DIGIT TWO;No;0;ON;;;2;2;N;CIRCLED SANS-SERIF DIGIT TWO;;;; 2782;DINGBAT CIRCLED SANS-SERIF DIGIT THREE;No;0;ON;;;3;3;N;CIRCLED SANS-SERIF DIGIT THREE;;;; 2783;DINGBAT CIRCLED SANS-SERIF DIGIT FOUR;No;0;ON;;;4;4;N;CIRCLED SANS-SERIF DIGIT FOUR;;;; 2784;DINGBAT CIRCLED SANS-SERIF DIGIT FIVE;No;0;ON;;;5;5;N;CIRCLED SANS-SERIF DIGIT FIVE;;;; 2785;DINGBAT CIRCLED SANS-SERIF DIGIT SIX;No;0;ON;;;6;6;N;CIRCLED SANS-SERIF DIGIT SIX;;;; 2786;DINGBAT CIRCLED SANS-SERIF DIGIT SEVEN;No;0;ON;;;7;7;N;CIRCLED SANS-SERIF DIGIT SEVEN;;;; 2787;DINGBAT CIRCLED SANS-SERIF DIGIT EIGHT;No;0;ON;;;8;8;N;CIRCLED SANS-SERIF DIGIT EIGHT;;;; 2788;DINGBAT CIRCLED SANS-SERIF DIGIT NINE;No;0;ON;;;9;9;N;CIRCLED SANS-SERIF DIGIT NINE;;;; 2789;DINGBAT CIRCLED SANS-SERIF NUMBER TEN;No;0;ON;;;;10;N;CIRCLED SANS-SERIF NUMBER TEN;;;; 278A;DINGBAT NEGATIVE CIRCLED SANS-SERIF DIGIT ONE;No;0;ON;;;1;1;N;INVERSE CIRCLED SANS-SERIF DIGIT ONE;;;; 278B;DINGBAT NEGATIVE CIRCLED SANS-SERIF DIGIT TWO;No;0;ON;;;2;2;N;INVERSE CIRCLED SANS-SERIF DIGIT TWO;;;; 278C;DINGBAT NEGATIVE CIRCLED SANS-SERIF DIGIT THREE;No;0;ON;;;3;3;N;INVERSE CIRCLED SANS-SERIF DIGIT THREE;;;; 278D;DINGBAT NEGATIVE CIRCLED SANS-SERIF DIGIT FOUR;No;0;ON;;;4;4;N;INVERSE CIRCLED SANS-SERIF DIGIT FOUR;;;; 278E;DINGBAT NEGATIVE CIRCLED SANS-SERIF DIGIT FIVE;No;0;ON;;;5;5;N;INVERSE CIRCLED SANS-SERIF DIGIT FIVE;;;; 278F;DINGBAT NEGATIVE CIRCLED SANS-SERIF DIGIT SIX;No;0;ON;;;6;6;N;INVERSE CIRCLED SANS-SERIF DIGIT SIX;;;; 2790;DINGBAT NEGATIVE CIRCLED SANS-SERIF DIGIT SEVEN;No;0;ON;;;7;7;N;INVERSE CIRCLED SANS-SERIF DIGIT SEVEN;;;; 2791;DINGBAT NEGATIVE CIRCLED SANS-SERIF DIGIT EIGHT;No;0;ON;;;8;8;N;INVERSE CIRCLED SANS-SERIF DIGIT EIGHT;;;; 2792;DINGBAT NEGATIVE CIRCLED SANS-SERIF DIGIT NINE;No;0;ON;;;9;9;N;INVERSE CIRCLED SANS-SERIF DIGIT NINE;;;; 2793;DINGBAT NEGATIVE CIRCLED SANS-SERIF NUMBER TEN;No;0;ON;;;;10;N;INVERSE CIRCLED SANS-SERIF NUMBER TEN;;;; 2794;HEAVY WIDE-HEADED RIGHTWARDS ARROW;So;0;ON;;;;;N;HEAVY WIDE-HEADED RIGHT ARROW;;;; 2795;HEAVY PLUS SIGN;So;0;ON;;;;;N;;;;; 2796;HEAVY MINUS SIGN;So;0;ON;;;;;N;;;;; 2797;HEAVY DIVISION SIGN;So;0;ON;;;;;N;;;;; 2798;HEAVY SOUTH EAST ARROW;So;0;ON;;;;;N;HEAVY LOWER RIGHT ARROW;;;; 2799;HEAVY RIGHTWARDS ARROW;So;0;ON;;;;;N;HEAVY RIGHT ARROW;;;; 279A;HEAVY NORTH EAST ARROW;So;0;ON;;;;;N;HEAVY UPPER RIGHT ARROW;;;; 279B;DRAFTING POINT RIGHTWARDS ARROW;So;0;ON;;;;;N;DRAFTING POINT RIGHT ARROW;;;; 279C;HEAVY ROUND-TIPPED RIGHTWARDS ARROW;So;0;ON;;;;;N;HEAVY ROUND-TIPPED RIGHT ARROW;;;; 279D;TRIANGLE-HEADED RIGHTWARDS ARROW;So;0;ON;;;;;N;TRIANGLE-HEADED RIGHT ARROW;;;; 279E;HEAVY TRIANGLE-HEADED RIGHTWARDS ARROW;So;0;ON;;;;;N;HEAVY TRIANGLE-HEADED RIGHT ARROW;;;; 279F;DASHED TRIANGLE-HEADED RIGHTWARDS ARROW;So;0;ON;;;;;N;DASHED TRIANGLE-HEADED RIGHT ARROW;;;; 27A0;HEAVY DASHED TRIANGLE-HEADED RIGHTWARDS ARROW;So;0;ON;;;;;N;HEAVY DASHED TRIANGLE-HEADED RIGHT ARROW;;;; 27A1;BLACK RIGHTWARDS ARROW;So;0;ON;;;;;N;BLACK RIGHT ARROW;;;; 27A2;THREE-D TOP-LIGHTED RIGHTWARDS ARROWHEAD;So;0;ON;;;;;N;THREE-D TOP-LIGHTED RIGHT ARROWHEAD;;;; 27A3;THREE-D BOTTOM-LIGHTED RIGHTWARDS ARROWHEAD;So;0;ON;;;;;N;THREE-D BOTTOM-LIGHTED RIGHT ARROWHEAD;;;; 27A4;BLACK RIGHTWARDS ARROWHEAD;So;0;ON;;;;;N;BLACK RIGHT ARROWHEAD;;;; 27A5;HEAVY BLACK CURVED DOWNWARDS AND RIGHTWARDS ARROW;So;0;ON;;;;;N;HEAVY BLACK CURVED DOWN AND RIGHT ARROW;;;; 27A6;HEAVY BLACK CURVED UPWARDS AND RIGHTWARDS ARROW;So;0;ON;;;;;N;HEAVY BLACK CURVED UP AND RIGHT ARROW;;;; 27A7;SQUAT BLACK RIGHTWARDS ARROW;So;0;ON;;;;;N;SQUAT BLACK RIGHT ARROW;;;; 27A8;HEAVY CONCAVE-POINTED BLACK RIGHTWARDS ARROW;So;0;ON;;;;;N;HEAVY CONCAVE-POINTED BLACK RIGHT ARROW;;;; 27A9;RIGHT-SHADED WHITE RIGHTWARDS ARROW;So;0;ON;;;;;N;RIGHT-SHADED WHITE RIGHT ARROW;;;; 27AA;LEFT-SHADED WHITE RIGHTWARDS ARROW;So;0;ON;;;;;N;LEFT-SHADED WHITE RIGHT ARROW;;;; 27AB;BACK-TILTED SHADOWED WHITE RIGHTWARDS ARROW;So;0;ON;;;;;N;BACK-TILTED SHADOWED WHITE RIGHT ARROW;;;; 27AC;FRONT-TILTED SHADOWED WHITE RIGHTWARDS ARROW;So;0;ON;;;;;N;FRONT-TILTED SHADOWED WHITE RIGHT ARROW;;;; 27AD;HEAVY LOWER RIGHT-SHADOWED WHITE RIGHTWARDS ARROW;So;0;ON;;;;;N;HEAVY LOWER RIGHT-SHADOWED WHITE RIGHT ARROW;;;; 27AE;HEAVY UPPER RIGHT-SHADOWED WHITE RIGHTWARDS ARROW;So;0;ON;;;;;N;HEAVY UPPER RIGHT-SHADOWED WHITE RIGHT ARROW;;;; 27AF;NOTCHED LOWER RIGHT-SHADOWED WHITE RIGHTWARDS ARROW;So;0;ON;;;;;N;NOTCHED LOWER RIGHT-SHADOWED WHITE RIGHT ARROW;;;; 27B0;CURLY LOOP;So;0;ON;;;;;N;;;;; 27B1;NOTCHED UPPER RIGHT-SHADOWED WHITE RIGHTWARDS ARROW;So;0;ON;;;;;N;NOTCHED UPPER RIGHT-SHADOWED WHITE RIGHT ARROW;;;; 27B2;CIRCLED HEAVY WHITE RIGHTWARDS ARROW;So;0;ON;;;;;N;CIRCLED HEAVY WHITE RIGHT ARROW;;;; 27B3;WHITE-FEATHERED RIGHTWARDS ARROW;So;0;ON;;;;;N;WHITE-FEATHERED RIGHT ARROW;;;; 27B4;BLACK-FEATHERED SOUTH EAST ARROW;So;0;ON;;;;;N;BLACK-FEATHERED LOWER RIGHT ARROW;;;; 27B5;BLACK-FEATHERED RIGHTWARDS ARROW;So;0;ON;;;;;N;BLACK-FEATHERED RIGHT ARROW;;;; 27B6;BLACK-FEATHERED NORTH EAST ARROW;So;0;ON;;;;;N;BLACK-FEATHERED UPPER RIGHT ARROW;;;; 27B7;HEAVY BLACK-FEATHERED SOUTH EAST ARROW;So;0;ON;;;;;N;HEAVY BLACK-FEATHERED LOWER RIGHT ARROW;;;; 27B8;HEAVY BLACK-FEATHERED RIGHTWARDS ARROW;So;0;ON;;;;;N;HEAVY BLACK-FEATHERED RIGHT ARROW;;;; 27B9;HEAVY BLACK-FEATHERED NORTH EAST ARROW;So;0;ON;;;;;N;HEAVY BLACK-FEATHERED UPPER RIGHT ARROW;;;; 27BA;TEARDROP-BARBED RIGHTWARDS ARROW;So;0;ON;;;;;N;TEARDROP-BARBED RIGHT ARROW;;;; 27BB;HEAVY TEARDROP-SHANKED RIGHTWARDS ARROW;So;0;ON;;;;;N;HEAVY TEARDROP-SHANKED RIGHT ARROW;;;; 27BC;WEDGE-TAILED RIGHTWARDS ARROW;So;0;ON;;;;;N;WEDGE-TAILED RIGHT ARROW;;;; 27BD;HEAVY WEDGE-TAILED RIGHTWARDS ARROW;So;0;ON;;;;;N;HEAVY WEDGE-TAILED RIGHT ARROW;;;; 27BE;OPEN-OUTLINED RIGHTWARDS ARROW;So;0;ON;;;;;N;OPEN-OUTLINED RIGHT ARROW;;;; 27BF;DOUBLE CURLY LOOP;So;0;ON;;;;;N;;;;; 27C0;THREE DIMENSIONAL ANGLE;Sm;0;ON;;;;;Y;;;;; 27C1;WHITE TRIANGLE CONTAINING SMALL WHITE TRIANGLE;Sm;0;ON;;;;;N;;;;; 27C2;PERPENDICULAR;Sm;0;ON;;;;;N;;;;; 27C3;OPEN SUBSET;Sm;0;ON;;;;;Y;;;;; 27C4;OPEN SUPERSET;Sm;0;ON;;;;;Y;;;;; 27C5;LEFT S-SHAPED BAG DELIMITER;Ps;0;ON;;;;;Y;;;;; 27C6;RIGHT S-SHAPED BAG DELIMITER;Pe;0;ON;;;;;Y;;;;; 27C7;OR WITH DOT INSIDE;Sm;0;ON;;;;;N;;;;; 27C8;REVERSE SOLIDUS PRECEDING SUBSET;Sm;0;ON;;;;;Y;;;;; 27C9;SUPERSET PRECEDING SOLIDUS;Sm;0;ON;;;;;Y;;;;; 27CA;VERTICAL BAR WITH HORIZONTAL STROKE;Sm;0;ON;;;;;N;;;;; 27CB;MATHEMATICAL RISING DIAGONAL;Sm;0;ON;;;;;Y;;;;; 27CC;LONG DIVISION;Sm;0;ON;;;;;Y;;;;; 27CD;MATHEMATICAL FALLING DIAGONAL;Sm;0;ON;;;;;Y;;;;; 27CE;SQUARED LOGICAL AND;Sm;0;ON;;;;;N;;;;; 27CF;SQUARED LOGICAL OR;Sm;0;ON;;;;;N;;;;; 27D0;WHITE DIAMOND WITH CENTRED DOT;Sm;0;ON;;;;;N;;;;; 27D1;AND WITH DOT;Sm;0;ON;;;;;N;;;;; 27D2;ELEMENT OF OPENING UPWARDS;Sm;0;ON;;;;;N;;;;; 27D3;LOWER RIGHT CORNER WITH DOT;Sm;0;ON;;;;;Y;;;;; 27D4;UPPER LEFT CORNER WITH DOT;Sm;0;ON;;;;;Y;;;;; 27D5;LEFT OUTER JOIN;Sm;0;ON;;;;;Y;;;;; 27D6;RIGHT OUTER JOIN;Sm;0;ON;;;;;Y;;;;; 27D7;FULL OUTER JOIN;Sm;0;ON;;;;;N;;;;; 27D8;LARGE UP TACK;Sm;0;ON;;;;;N;;;;; 27D9;LARGE DOWN TACK;Sm;0;ON;;;;;N;;;;; 27DA;LEFT AND RIGHT DOUBLE TURNSTILE;Sm;0;ON;;;;;N;;;;; 27DB;LEFT AND RIGHT TACK;Sm;0;ON;;;;;N;;;;; 27DC;LEFT MULTIMAP;Sm;0;ON;;;;;Y;;;;; 27DD;LONG RIGHT TACK;Sm;0;ON;;;;;Y;;;;; 27DE;LONG LEFT TACK;Sm;0;ON;;;;;Y;;;;; 27DF;UP TACK WITH CIRCLE ABOVE;Sm;0;ON;;;;;N;;;;; 27E0;LOZENGE DIVIDED BY HORIZONTAL RULE;Sm;0;ON;;;;;N;;;;; 27E1;WHITE CONCAVE-SIDED DIAMOND;Sm;0;ON;;;;;N;;;;; 27E2;WHITE CONCAVE-SIDED DIAMOND WITH LEFTWARDS TICK;Sm;0;ON;;;;;Y;;;;; 27E3;WHITE CONCAVE-SIDED DIAMOND WITH RIGHTWARDS TICK;Sm;0;ON;;;;;Y;;;;; 27E4;WHITE SQUARE WITH LEFTWARDS TICK;Sm;0;ON;;;;;Y;;;;; 27E5;WHITE SQUARE WITH RIGHTWARDS TICK;Sm;0;ON;;;;;Y;;;;; 27E6;MATHEMATICAL LEFT WHITE SQUARE BRACKET;Ps;0;ON;;;;;Y;;;;; 27E7;MATHEMATICAL RIGHT WHITE SQUARE BRACKET;Pe;0;ON;;;;;Y;;;;; 27E8;MATHEMATICAL LEFT ANGLE BRACKET;Ps;0;ON;;;;;Y;;;;; 27E9;MATHEMATICAL RIGHT ANGLE BRACKET;Pe;0;ON;;;;;Y;;;;; 27EA;MATHEMATICAL LEFT DOUBLE ANGLE BRACKET;Ps;0;ON;;;;;Y;;;;; 27EB;MATHEMATICAL RIGHT DOUBLE ANGLE BRACKET;Pe;0;ON;;;;;Y;;;;; 27EC;MATHEMATICAL LEFT WHITE TORTOISE SHELL BRACKET;Ps;0;ON;;;;;Y;;;;; 27ED;MATHEMATICAL RIGHT WHITE TORTOISE SHELL BRACKET;Pe;0;ON;;;;;Y;;;;; 27EE;MATHEMATICAL LEFT FLATTENED PARENTHESIS;Ps;0;ON;;;;;Y;;;;; 27EF;MATHEMATICAL RIGHT FLATTENED PARENTHESIS;Pe;0;ON;;;;;Y;;;;; 27F0;UPWARDS QUADRUPLE ARROW;Sm;0;ON;;;;;N;;;;; 27F1;DOWNWARDS QUADRUPLE ARROW;Sm;0;ON;;;;;N;;;;; 27F2;ANTICLOCKWISE GAPPED CIRCLE ARROW;Sm;0;ON;;;;;N;;;;; 27F3;CLOCKWISE GAPPED CIRCLE ARROW;Sm;0;ON;;;;;N;;;;; 27F4;RIGHT ARROW WITH CIRCLED PLUS;Sm;0;ON;;;;;N;;;;; 27F5;LONG LEFTWARDS ARROW;Sm;0;ON;;;;;N;;;;; 27F6;LONG RIGHTWARDS ARROW;Sm;0;ON;;;;;N;;;;; 27F7;LONG LEFT RIGHT ARROW;Sm;0;ON;;;;;N;;;;; 27F8;LONG LEFTWARDS DOUBLE ARROW;Sm;0;ON;;;;;N;;;;; 27F9;LONG RIGHTWARDS DOUBLE ARROW;Sm;0;ON;;;;;N;;;;; 27FA;LONG LEFT RIGHT DOUBLE ARROW;Sm;0;ON;;;;;N;;;;; 27FB;LONG LEFTWARDS ARROW FROM BAR;Sm;0;ON;;;;;N;;;;; 27FC;LONG RIGHTWARDS ARROW FROM BAR;Sm;0;ON;;;;;N;;;;; 27FD;LONG LEFTWARDS DOUBLE ARROW FROM BAR;Sm;0;ON;;;;;N;;;;; 27FE;LONG RIGHTWARDS DOUBLE ARROW FROM BAR;Sm;0;ON;;;;;N;;;;; 27FF;LONG RIGHTWARDS SQUIGGLE ARROW;Sm;0;ON;;;;;N;;;;; 2800;BRAILLE PATTERN BLANK;So;0;L;;;;;N;;;;; 2801;BRAILLE PATTERN DOTS-1;So;0;L;;;;;N;;;;; 2802;BRAILLE PATTERN DOTS-2;So;0;L;;;;;N;;;;; 2803;BRAILLE PATTERN DOTS-12;So;0;L;;;;;N;;;;; 2804;BRAILLE PATTERN DOTS-3;So;0;L;;;;;N;;;;; 2805;BRAILLE PATTERN DOTS-13;So;0;L;;;;;N;;;;; 2806;BRAILLE PATTERN DOTS-23;So;0;L;;;;;N;;;;; 2807;BRAILLE PATTERN DOTS-123;So;0;L;;;;;N;;;;; 2808;BRAILLE PATTERN DOTS-4;So;0;L;;;;;N;;;;; 2809;BRAILLE PATTERN DOTS-14;So;0;L;;;;;N;;;;; 280A;BRAILLE PATTERN DOTS-24;So;0;L;;;;;N;;;;; 280B;BRAILLE PATTERN DOTS-124;So;0;L;;;;;N;;;;; 280C;BRAILLE PATTERN DOTS-34;So;0;L;;;;;N;;;;; 280D;BRAILLE PATTERN DOTS-134;So;0;L;;;;;N;;;;; 280E;BRAILLE PATTERN DOTS-234;So;0;L;;;;;N;;;;; 280F;BRAILLE PATTERN DOTS-1234;So;0;L;;;;;N;;;;; 2810;BRAILLE PATTERN DOTS-5;So;0;L;;;;;N;;;;; 2811;BRAILLE PATTERN DOTS-15;So;0;L;;;;;N;;;;; 2812;BRAILLE PATTERN DOTS-25;So;0;L;;;;;N;;;;; 2813;BRAILLE PATTERN DOTS-125;So;0;L;;;;;N;;;;; 2814;BRAILLE PATTERN DOTS-35;So;0;L;;;;;N;;;;; 2815;BRAILLE PATTERN DOTS-135;So;0;L;;;;;N;;;;; 2816;BRAILLE PATTERN DOTS-235;So;0;L;;;;;N;;;;; 2817;BRAILLE PATTERN DOTS-1235;So;0;L;;;;;N;;;;; 2818;BRAILLE PATTERN DOTS-45;So;0;L;;;;;N;;;;; 2819;BRAILLE PATTERN DOTS-145;So;0;L;;;;;N;;;;; 281A;BRAILLE PATTERN DOTS-245;So;0;L;;;;;N;;;;; 281B;BRAILLE PATTERN DOTS-1245;So;0;L;;;;;N;;;;; 281C;BRAILLE PATTERN DOTS-345;So;0;L;;;;;N;;;;; 281D;BRAILLE PATTERN DOTS-1345;So;0;L;;;;;N;;;;; 281E;BRAILLE PATTERN DOTS-2345;So;0;L;;;;;N;;;;; 281F;BRAILLE PATTERN DOTS-12345;So;0;L;;;;;N;;;;; 2820;BRAILLE PATTERN DOTS-6;So;0;L;;;;;N;;;;; 2821;BRAILLE PATTERN DOTS-16;So;0;L;;;;;N;;;;; 2822;BRAILLE PATTERN DOTS-26;So;0;L;;;;;N;;;;; 2823;BRAILLE PATTERN DOTS-126;So;0;L;;;;;N;;;;; 2824;BRAILLE PATTERN DOTS-36;So;0;L;;;;;N;;;;; 2825;BRAILLE PATTERN DOTS-136;So;0;L;;;;;N;;;;; 2826;BRAILLE PATTERN DOTS-236;So;0;L;;;;;N;;;;; 2827;BRAILLE PATTERN DOTS-1236;So;0;L;;;;;N;;;;; 2828;BRAILLE PATTERN DOTS-46;So;0;L;;;;;N;;;;; 2829;BRAILLE PATTERN DOTS-146;So;0;L;;;;;N;;;;; 282A;BRAILLE PATTERN DOTS-246;So;0;L;;;;;N;;;;; 282B;BRAILLE PATTERN DOTS-1246;So;0;L;;;;;N;;;;; 282C;BRAILLE PATTERN DOTS-346;So;0;L;;;;;N;;;;; 282D;BRAILLE PATTERN DOTS-1346;So;0;L;;;;;N;;;;; 282E;BRAILLE PATTERN DOTS-2346;So;0;L;;;;;N;;;;; 282F;BRAILLE PATTERN DOTS-12346;So;0;L;;;;;N;;;;; 2830;BRAILLE PATTERN DOTS-56;So;0;L;;;;;N;;;;; 2831;BRAILLE PATTERN DOTS-156;So;0;L;;;;;N;;;;; 2832;BRAILLE PATTERN DOTS-256;So;0;L;;;;;N;;;;; 2833;BRAILLE PATTERN DOTS-1256;So;0;L;;;;;N;;;;; 2834;BRAILLE PATTERN DOTS-356;So;0;L;;;;;N;;;;; 2835;BRAILLE PATTERN DOTS-1356;So;0;L;;;;;N;;;;; 2836;BRAILLE PATTERN DOTS-2356;So;0;L;;;;;N;;;;; 2837;BRAILLE PATTERN DOTS-12356;So;0;L;;;;;N;;;;; 2838;BRAILLE PATTERN DOTS-456;So;0;L;;;;;N;;;;; 2839;BRAILLE PATTERN DOTS-1456;So;0;L;;;;;N;;;;; 283A;BRAILLE PATTERN DOTS-2456;So;0;L;;;;;N;;;;; 283B;BRAILLE PATTERN DOTS-12456;So;0;L;;;;;N;;;;; 283C;BRAILLE PATTERN DOTS-3456;So;0;L;;;;;N;;;;; 283D;BRAILLE PATTERN DOTS-13456;So;0;L;;;;;N;;;;; 283E;BRAILLE PATTERN DOTS-23456;So;0;L;;;;;N;;;;; 283F;BRAILLE PATTERN DOTS-123456;So;0;L;;;;;N;;;;; 2840;BRAILLE PATTERN DOTS-7;So;0;L;;;;;N;;;;; 2841;BRAILLE PATTERN DOTS-17;So;0;L;;;;;N;;;;; 2842;BRAILLE PATTERN DOTS-27;So;0;L;;;;;N;;;;; 2843;BRAILLE PATTERN DOTS-127;So;0;L;;;;;N;;;;; 2844;BRAILLE PATTERN DOTS-37;So;0;L;;;;;N;;;;; 2845;BRAILLE PATTERN DOTS-137;So;0;L;;;;;N;;;;; 2846;BRAILLE PATTERN DOTS-237;So;0;L;;;;;N;;;;; 2847;BRAILLE PATTERN DOTS-1237;So;0;L;;;;;N;;;;; 2848;BRAILLE PATTERN DOTS-47;So;0;L;;;;;N;;;;; 2849;BRAILLE PATTERN DOTS-147;So;0;L;;;;;N;;;;; 284A;BRAILLE PATTERN DOTS-247;So;0;L;;;;;N;;;;; 284B;BRAILLE PATTERN DOTS-1247;So;0;L;;;;;N;;;;; 284C;BRAILLE PATTERN DOTS-347;So;0;L;;;;;N;;;;; 284D;BRAILLE PATTERN DOTS-1347;So;0;L;;;;;N;;;;; 284E;BRAILLE PATTERN DOTS-2347;So;0;L;;;;;N;;;;; 284F;BRAILLE PATTERN DOTS-12347;So;0;L;;;;;N;;;;; 2850;BRAILLE PATTERN DOTS-57;So;0;L;;;;;N;;;;; 2851;BRAILLE PATTERN DOTS-157;So;0;L;;;;;N;;;;; 2852;BRAILLE PATTERN DOTS-257;So;0;L;;;;;N;;;;; 2853;BRAILLE PATTERN DOTS-1257;So;0;L;;;;;N;;;;; 2854;BRAILLE PATTERN DOTS-357;So;0;L;;;;;N;;;;; 2855;BRAILLE PATTERN DOTS-1357;So;0;L;;;;;N;;;;; 2856;BRAILLE PATTERN DOTS-2357;So;0;L;;;;;N;;;;; 2857;BRAILLE PATTERN DOTS-12357;So;0;L;;;;;N;;;;; 2858;BRAILLE PATTERN DOTS-457;So;0;L;;;;;N;;;;; 2859;BRAILLE PATTERN DOTS-1457;So;0;L;;;;;N;;;;; 285A;BRAILLE PATTERN DOTS-2457;So;0;L;;;;;N;;;;; 285B;BRAILLE PATTERN DOTS-12457;So;0;L;;;;;N;;;;; 285C;BRAILLE PATTERN DOTS-3457;So;0;L;;;;;N;;;;; 285D;BRAILLE PATTERN DOTS-13457;So;0;L;;;;;N;;;;; 285E;BRAILLE PATTERN DOTS-23457;So;0;L;;;;;N;;;;; 285F;BRAILLE PATTERN DOTS-123457;So;0;L;;;;;N;;;;; 2860;BRAILLE PATTERN DOTS-67;So;0;L;;;;;N;;;;; 2861;BRAILLE PATTERN DOTS-167;So;0;L;;;;;N;;;;; 2862;BRAILLE PATTERN DOTS-267;So;0;L;;;;;N;;;;; 2863;BRAILLE PATTERN DOTS-1267;So;0;L;;;;;N;;;;; 2864;BRAILLE PATTERN DOTS-367;So;0;L;;;;;N;;;;; 2865;BRAILLE PATTERN DOTS-1367;So;0;L;;;;;N;;;;; 2866;BRAILLE PATTERN DOTS-2367;So;0;L;;;;;N;;;;; 2867;BRAILLE PATTERN DOTS-12367;So;0;L;;;;;N;;;;; 2868;BRAILLE PATTERN DOTS-467;So;0;L;;;;;N;;;;; 2869;BRAILLE PATTERN DOTS-1467;So;0;L;;;;;N;;;;; 286A;BRAILLE PATTERN DOTS-2467;So;0;L;;;;;N;;;;; 286B;BRAILLE PATTERN DOTS-12467;So;0;L;;;;;N;;;;; 286C;BRAILLE PATTERN DOTS-3467;So;0;L;;;;;N;;;;; 286D;BRAILLE PATTERN DOTS-13467;So;0;L;;;;;N;;;;; 286E;BRAILLE PATTERN DOTS-23467;So;0;L;;;;;N;;;;; 286F;BRAILLE PATTERN DOTS-123467;So;0;L;;;;;N;;;;; 2870;BRAILLE PATTERN DOTS-567;So;0;L;;;;;N;;;;; 2871;BRAILLE PATTERN DOTS-1567;So;0;L;;;;;N;;;;; 2872;BRAILLE PATTERN DOTS-2567;So;0;L;;;;;N;;;;; 2873;BRAILLE PATTERN DOTS-12567;So;0;L;;;;;N;;;;; 2874;BRAILLE PATTERN DOTS-3567;So;0;L;;;;;N;;;;; 2875;BRAILLE PATTERN DOTS-13567;So;0;L;;;;;N;;;;; 2876;BRAILLE PATTERN DOTS-23567;So;0;L;;;;;N;;;;; 2877;BRAILLE PATTERN DOTS-123567;So;0;L;;;;;N;;;;; 2878;BRAILLE PATTERN DOTS-4567;So;0;L;;;;;N;;;;; 2879;BRAILLE PATTERN DOTS-14567;So;0;L;;;;;N;;;;; 287A;BRAILLE PATTERN DOTS-24567;So;0;L;;;;;N;;;;; 287B;BRAILLE PATTERN DOTS-124567;So;0;L;;;;;N;;;;; 287C;BRAILLE PATTERN DOTS-34567;So;0;L;;;;;N;;;;; 287D;BRAILLE PATTERN DOTS-134567;So;0;L;;;;;N;;;;; 287E;BRAILLE PATTERN DOTS-234567;So;0;L;;;;;N;;;;; 287F;BRAILLE PATTERN DOTS-1234567;So;0;L;;;;;N;;;;; 2880;BRAILLE PATTERN DOTS-8;So;0;L;;;;;N;;;;; 2881;BRAILLE PATTERN DOTS-18;So;0;L;;;;;N;;;;; 2882;BRAILLE PATTERN DOTS-28;So;0;L;;;;;N;;;;; 2883;BRAILLE PATTERN DOTS-128;So;0;L;;;;;N;;;;; 2884;BRAILLE PATTERN DOTS-38;So;0;L;;;;;N;;;;; 2885;BRAILLE PATTERN DOTS-138;So;0;L;;;;;N;;;;; 2886;BRAILLE PATTERN DOTS-238;So;0;L;;;;;N;;;;; 2887;BRAILLE PATTERN DOTS-1238;So;0;L;;;;;N;;;;; 2888;BRAILLE PATTERN DOTS-48;So;0;L;;;;;N;;;;; 2889;BRAILLE PATTERN DOTS-148;So;0;L;;;;;N;;;;; 288A;BRAILLE PATTERN DOTS-248;So;0;L;;;;;N;;;;; 288B;BRAILLE PATTERN DOTS-1248;So;0;L;;;;;N;;;;; 288C;BRAILLE PATTERN DOTS-348;So;0;L;;;;;N;;;;; 288D;BRAILLE PATTERN DOTS-1348;So;0;L;;;;;N;;;;; 288E;BRAILLE PATTERN DOTS-2348;So;0;L;;;;;N;;;;; 288F;BRAILLE PATTERN DOTS-12348;So;0;L;;;;;N;;;;; 2890;BRAILLE PATTERN DOTS-58;So;0;L;;;;;N;;;;; 2891;BRAILLE PATTERN DOTS-158;So;0;L;;;;;N;;;;; 2892;BRAILLE PATTERN DOTS-258;So;0;L;;;;;N;;;;; 2893;BRAILLE PATTERN DOTS-1258;So;0;L;;;;;N;;;;; 2894;BRAILLE PATTERN DOTS-358;So;0;L;;;;;N;;;;; 2895;BRAILLE PATTERN DOTS-1358;So;0;L;;;;;N;;;;; 2896;BRAILLE PATTERN DOTS-2358;So;0;L;;;;;N;;;;; 2897;BRAILLE PATTERN DOTS-12358;So;0;L;;;;;N;;;;; 2898;BRAILLE PATTERN DOTS-458;So;0;L;;;;;N;;;;; 2899;BRAILLE PATTERN DOTS-1458;So;0;L;;;;;N;;;;; 289A;BRAILLE PATTERN DOTS-2458;So;0;L;;;;;N;;;;; 289B;BRAILLE PATTERN DOTS-12458;So;0;L;;;;;N;;;;; 289C;BRAILLE PATTERN DOTS-3458;So;0;L;;;;;N;;;;; 289D;BRAILLE PATTERN DOTS-13458;So;0;L;;;;;N;;;;; 289E;BRAILLE PATTERN DOTS-23458;So;0;L;;;;;N;;;;; 289F;BRAILLE PATTERN DOTS-123458;So;0;L;;;;;N;;;;; 28A0;BRAILLE PATTERN DOTS-68;So;0;L;;;;;N;;;;; 28A1;BRAILLE PATTERN DOTS-168;So;0;L;;;;;N;;;;; 28A2;BRAILLE PATTERN DOTS-268;So;0;L;;;;;N;;;;; 28A3;BRAILLE PATTERN DOTS-1268;So;0;L;;;;;N;;;;; 28A4;BRAILLE PATTERN DOTS-368;So;0;L;;;;;N;;;;; 28A5;BRAILLE PATTERN DOTS-1368;So;0;L;;;;;N;;;;; 28A6;BRAILLE PATTERN DOTS-2368;So;0;L;;;;;N;;;;; 28A7;BRAILLE PATTERN DOTS-12368;So;0;L;;;;;N;;;;; 28A8;BRAILLE PATTERN DOTS-468;So;0;L;;;;;N;;;;; 28A9;BRAILLE PATTERN DOTS-1468;So;0;L;;;;;N;;;;; 28AA;BRAILLE PATTERN DOTS-2468;So;0;L;;;;;N;;;;; 28AB;BRAILLE PATTERN DOTS-12468;So;0;L;;;;;N;;;;; 28AC;BRAILLE PATTERN DOTS-3468;So;0;L;;;;;N;;;;; 28AD;BRAILLE PATTERN DOTS-13468;So;0;L;;;;;N;;;;; 28AE;BRAILLE PATTERN DOTS-23468;So;0;L;;;;;N;;;;; 28AF;BRAILLE PATTERN DOTS-123468;So;0;L;;;;;N;;;;; 28B0;BRAILLE PATTERN DOTS-568;So;0;L;;;;;N;;;;; 28B1;BRAILLE PATTERN DOTS-1568;So;0;L;;;;;N;;;;; 28B2;BRAILLE PATTERN DOTS-2568;So;0;L;;;;;N;;;;; 28B3;BRAILLE PATTERN DOTS-12568;So;0;L;;;;;N;;;;; 28B4;BRAILLE PATTERN DOTS-3568;So;0;L;;;;;N;;;;; 28B5;BRAILLE PATTERN DOTS-13568;So;0;L;;;;;N;;;;; 28B6;BRAILLE PATTERN DOTS-23568;So;0;L;;;;;N;;;;; 28B7;BRAILLE PATTERN DOTS-123568;So;0;L;;;;;N;;;;; 28B8;BRAILLE PATTERN DOTS-4568;So;0;L;;;;;N;;;;; 28B9;BRAILLE PATTERN DOTS-14568;So;0;L;;;;;N;;;;; 28BA;BRAILLE PATTERN DOTS-24568;So;0;L;;;;;N;;;;; 28BB;BRAILLE PATTERN DOTS-124568;So;0;L;;;;;N;;;;; 28BC;BRAILLE PATTERN DOTS-34568;So;0;L;;;;;N;;;;; 28BD;BRAILLE PATTERN DOTS-134568;So;0;L;;;;;N;;;;; 28BE;BRAILLE PATTERN DOTS-234568;So;0;L;;;;;N;;;;; 28BF;BRAILLE PATTERN DOTS-1234568;So;0;L;;;;;N;;;;; 28C0;BRAILLE PATTERN DOTS-78;So;0;L;;;;;N;;;;; 28C1;BRAILLE PATTERN DOTS-178;So;0;L;;;;;N;;;;; 28C2;BRAILLE PATTERN DOTS-278;So;0;L;;;;;N;;;;; 28C3;BRAILLE PATTERN DOTS-1278;So;0;L;;;;;N;;;;; 28C4;BRAILLE PATTERN DOTS-378;So;0;L;;;;;N;;;;; 28C5;BRAILLE PATTERN DOTS-1378;So;0;L;;;;;N;;;;; 28C6;BRAILLE PATTERN DOTS-2378;So;0;L;;;;;N;;;;; 28C7;BRAILLE PATTERN DOTS-12378;So;0;L;;;;;N;;;;; 28C8;BRAILLE PATTERN DOTS-478;So;0;L;;;;;N;;;;; 28C9;BRAILLE PATTERN DOTS-1478;So;0;L;;;;;N;;;;; 28CA;BRAILLE PATTERN DOTS-2478;So;0;L;;;;;N;;;;; 28CB;BRAILLE PATTERN DOTS-12478;So;0;L;;;;;N;;;;; 28CC;BRAILLE PATTERN DOTS-3478;So;0;L;;;;;N;;;;; 28CD;BRAILLE PATTERN DOTS-13478;So;0;L;;;;;N;;;;; 28CE;BRAILLE PATTERN DOTS-23478;So;0;L;;;;;N;;;;; 28CF;BRAILLE PATTERN DOTS-123478;So;0;L;;;;;N;;;;; 28D0;BRAILLE PATTERN DOTS-578;So;0;L;;;;;N;;;;; 28D1;BRAILLE PATTERN DOTS-1578;So;0;L;;;;;N;;;;; 28D2;BRAILLE PATTERN DOTS-2578;So;0;L;;;;;N;;;;; 28D3;BRAILLE PATTERN DOTS-12578;So;0;L;;;;;N;;;;; 28D4;BRAILLE PATTERN DOTS-3578;So;0;L;;;;;N;;;;; 28D5;BRAILLE PATTERN DOTS-13578;So;0;L;;;;;N;;;;; 28D6;BRAILLE PATTERN DOTS-23578;So;0;L;;;;;N;;;;; 28D7;BRAILLE PATTERN DOTS-123578;So;0;L;;;;;N;;;;; 28D8;BRAILLE PATTERN DOTS-4578;So;0;L;;;;;N;;;;; 28D9;BRAILLE PATTERN DOTS-14578;So;0;L;;;;;N;;;;; 28DA;BRAILLE PATTERN DOTS-24578;So;0;L;;;;;N;;;;; 28DB;BRAILLE PATTERN DOTS-124578;So;0;L;;;;;N;;;;; 28DC;BRAILLE PATTERN DOTS-34578;So;0;L;;;;;N;;;;; 28DD;BRAILLE PATTERN DOTS-134578;So;0;L;;;;;N;;;;; 28DE;BRAILLE PATTERN DOTS-234578;So;0;L;;;;;N;;;;; 28DF;BRAILLE PATTERN DOTS-1234578;So;0;L;;;;;N;;;;; 28E0;BRAILLE PATTERN DOTS-678;So;0;L;;;;;N;;;;; 28E1;BRAILLE PATTERN DOTS-1678;So;0;L;;;;;N;;;;; 28E2;BRAILLE PATTERN DOTS-2678;So;0;L;;;;;N;;;;; 28E3;BRAILLE PATTERN DOTS-12678;So;0;L;;;;;N;;;;; 28E4;BRAILLE PATTERN DOTS-3678;So;0;L;;;;;N;;;;; 28E5;BRAILLE PATTERN DOTS-13678;So;0;L;;;;;N;;;;; 28E6;BRAILLE PATTERN DOTS-23678;So;0;L;;;;;N;;;;; 28E7;BRAILLE PATTERN DOTS-123678;So;0;L;;;;;N;;;;; 28E8;BRAILLE PATTERN DOTS-4678;So;0;L;;;;;N;;;;; 28E9;BRAILLE PATTERN DOTS-14678;So;0;L;;;;;N;;;;; 28EA;BRAILLE PATTERN DOTS-24678;So;0;L;;;;;N;;;;; 28EB;BRAILLE PATTERN DOTS-124678;So;0;L;;;;;N;;;;; 28EC;BRAILLE PATTERN DOTS-34678;So;0;L;;;;;N;;;;; 28ED;BRAILLE PATTERN DOTS-134678;So;0;L;;;;;N;;;;; 28EE;BRAILLE PATTERN DOTS-234678;So;0;L;;;;;N;;;;; 28EF;BRAILLE PATTERN DOTS-1234678;So;0;L;;;;;N;;;;; 28F0;BRAILLE PATTERN DOTS-5678;So;0;L;;;;;N;;;;; 28F1;BRAILLE PATTERN DOTS-15678;So;0;L;;;;;N;;;;; 28F2;BRAILLE PATTERN DOTS-25678;So;0;L;;;;;N;;;;; 28F3;BRAILLE PATTERN DOTS-125678;So;0;L;;;;;N;;;;; 28F4;BRAILLE PATTERN DOTS-35678;So;0;L;;;;;N;;;;; 28F5;BRAILLE PATTERN DOTS-135678;So;0;L;;;;;N;;;;; 28F6;BRAILLE PATTERN DOTS-235678;So;0;L;;;;;N;;;;; 28F7;BRAILLE PATTERN DOTS-1235678;So;0;L;;;;;N;;;;; 28F8;BRAILLE PATTERN DOTS-45678;So;0;L;;;;;N;;;;; 28F9;BRAILLE PATTERN DOTS-145678;So;0;L;;;;;N;;;;; 28FA;BRAILLE PATTERN DOTS-245678;So;0;L;;;;;N;;;;; 28FB;BRAILLE PATTERN DOTS-1245678;So;0;L;;;;;N;;;;; 28FC;BRAILLE PATTERN DOTS-345678;So;0;L;;;;;N;;;;; 28FD;BRAILLE PATTERN DOTS-1345678;So;0;L;;;;;N;;;;; 28FE;BRAILLE PATTERN DOTS-2345678;So;0;L;;;;;N;;;;; 28FF;BRAILLE PATTERN DOTS-12345678;So;0;L;;;;;N;;;;; 2900;RIGHTWARDS TWO-HEADED ARROW WITH VERTICAL STROKE;Sm;0;ON;;;;;N;;;;; 2901;RIGHTWARDS TWO-HEADED ARROW WITH DOUBLE VERTICAL STROKE;Sm;0;ON;;;;;N;;;;; 2902;LEFTWARDS DOUBLE ARROW WITH VERTICAL STROKE;Sm;0;ON;;;;;N;;;;; 2903;RIGHTWARDS DOUBLE ARROW WITH VERTICAL STROKE;Sm;0;ON;;;;;N;;;;; 2904;LEFT RIGHT DOUBLE ARROW WITH VERTICAL STROKE;Sm;0;ON;;;;;N;;;;; 2905;RIGHTWARDS TWO-HEADED ARROW FROM BAR;Sm;0;ON;;;;;N;;;;; 2906;LEFTWARDS DOUBLE ARROW FROM BAR;Sm;0;ON;;;;;N;;;;; 2907;RIGHTWARDS DOUBLE ARROW FROM BAR;Sm;0;ON;;;;;N;;;;; 2908;DOWNWARDS ARROW WITH HORIZONTAL STROKE;Sm;0;ON;;;;;N;;;;; 2909;UPWARDS ARROW WITH HORIZONTAL STROKE;Sm;0;ON;;;;;N;;;;; 290A;UPWARDS TRIPLE ARROW;Sm;0;ON;;;;;N;;;;; 290B;DOWNWARDS TRIPLE ARROW;Sm;0;ON;;;;;N;;;;; 290C;LEFTWARDS DOUBLE DASH ARROW;Sm;0;ON;;;;;N;;;;; 290D;RIGHTWARDS DOUBLE DASH ARROW;Sm;0;ON;;;;;N;;;;; 290E;LEFTWARDS TRIPLE DASH ARROW;Sm;0;ON;;;;;N;;;;; 290F;RIGHTWARDS TRIPLE DASH ARROW;Sm;0;ON;;;;;N;;;;; 2910;RIGHTWARDS TWO-HEADED TRIPLE DASH ARROW;Sm;0;ON;;;;;N;;;;; 2911;RIGHTWARDS ARROW WITH DOTTED STEM;Sm;0;ON;;;;;N;;;;; 2912;UPWARDS ARROW TO BAR;Sm;0;ON;;;;;N;;;;; 2913;DOWNWARDS ARROW TO BAR;Sm;0;ON;;;;;N;;;;; 2914;RIGHTWARDS ARROW WITH TAIL WITH VERTICAL STROKE;Sm;0;ON;;;;;N;;;;; 2915;RIGHTWARDS ARROW WITH TAIL WITH DOUBLE VERTICAL STROKE;Sm;0;ON;;;;;N;;;;; 2916;RIGHTWARDS TWO-HEADED ARROW WITH TAIL;Sm;0;ON;;;;;N;;;;; 2917;RIGHTWARDS TWO-HEADED ARROW WITH TAIL WITH VERTICAL STROKE;Sm;0;ON;;;;;N;;;;; 2918;RIGHTWARDS TWO-HEADED ARROW WITH TAIL WITH DOUBLE VERTICAL STROKE;Sm;0;ON;;;;;N;;;;; 2919;LEFTWARDS ARROW-TAIL;Sm;0;ON;;;;;N;;;;; 291A;RIGHTWARDS ARROW-TAIL;Sm;0;ON;;;;;N;;;;; 291B;LEFTWARDS DOUBLE ARROW-TAIL;Sm;0;ON;;;;;N;;;;; 291C;RIGHTWARDS DOUBLE ARROW-TAIL;Sm;0;ON;;;;;N;;;;; 291D;LEFTWARDS ARROW TO BLACK DIAMOND;Sm;0;ON;;;;;N;;;;; 291E;RIGHTWARDS ARROW TO BLACK DIAMOND;Sm;0;ON;;;;;N;;;;; 291F;LEFTWARDS ARROW FROM BAR TO BLACK DIAMOND;Sm;0;ON;;;;;N;;;;; 2920;RIGHTWARDS ARROW FROM BAR TO BLACK DIAMOND;Sm;0;ON;;;;;N;;;;; 2921;NORTH WEST AND SOUTH EAST ARROW;Sm;0;ON;;;;;N;;;;; 2922;NORTH EAST AND SOUTH WEST ARROW;Sm;0;ON;;;;;N;;;;; 2923;NORTH WEST ARROW WITH HOOK;Sm;0;ON;;;;;N;;;;; 2924;NORTH EAST ARROW WITH HOOK;Sm;0;ON;;;;;N;;;;; 2925;SOUTH EAST ARROW WITH HOOK;Sm;0;ON;;;;;N;;;;; 2926;SOUTH WEST ARROW WITH HOOK;Sm;0;ON;;;;;N;;;;; 2927;NORTH WEST ARROW AND NORTH EAST ARROW;Sm;0;ON;;;;;N;;;;; 2928;NORTH EAST ARROW AND SOUTH EAST ARROW;Sm;0;ON;;;;;N;;;;; 2929;SOUTH EAST ARROW AND SOUTH WEST ARROW;Sm;0;ON;;;;;N;;;;; 292A;SOUTH WEST ARROW AND NORTH WEST ARROW;Sm;0;ON;;;;;N;;;;; 292B;RISING DIAGONAL CROSSING FALLING DIAGONAL;Sm;0;ON;;;;;N;;;;; 292C;FALLING DIAGONAL CROSSING RISING DIAGONAL;Sm;0;ON;;;;;N;;;;; 292D;SOUTH EAST ARROW CROSSING NORTH EAST ARROW;Sm;0;ON;;;;;N;;;;; 292E;NORTH EAST ARROW CROSSING SOUTH EAST ARROW;Sm;0;ON;;;;;N;;;;; 292F;FALLING DIAGONAL CROSSING NORTH EAST ARROW;Sm;0;ON;;;;;N;;;;; 2930;RISING DIAGONAL CROSSING SOUTH EAST ARROW;Sm;0;ON;;;;;N;;;;; 2931;NORTH EAST ARROW CROSSING NORTH WEST ARROW;Sm;0;ON;;;;;N;;;;; 2932;NORTH WEST ARROW CROSSING NORTH EAST ARROW;Sm;0;ON;;;;;N;;;;; 2933;WAVE ARROW POINTING DIRECTLY RIGHT;Sm;0;ON;;;;;N;;;;; 2934;ARROW POINTING RIGHTWARDS THEN CURVING UPWARDS;Sm;0;ON;;;;;N;;;;; 2935;ARROW POINTING RIGHTWARDS THEN CURVING DOWNWARDS;Sm;0;ON;;;;;N;;;;; 2936;ARROW POINTING DOWNWARDS THEN CURVING LEFTWARDS;Sm;0;ON;;;;;N;;;;; 2937;ARROW POINTING DOWNWARDS THEN CURVING RIGHTWARDS;Sm;0;ON;;;;;N;;;;; 2938;RIGHT-SIDE ARC CLOCKWISE ARROW;Sm;0;ON;;;;;N;;;;; 2939;LEFT-SIDE ARC ANTICLOCKWISE ARROW;Sm;0;ON;;;;;N;;;;; 293A;TOP ARC ANTICLOCKWISE ARROW;Sm;0;ON;;;;;N;;;;; 293B;BOTTOM ARC ANTICLOCKWISE ARROW;Sm;0;ON;;;;;N;;;;; 293C;TOP ARC CLOCKWISE ARROW WITH MINUS;Sm;0;ON;;;;;N;;;;; 293D;TOP ARC ANTICLOCKWISE ARROW WITH PLUS;Sm;0;ON;;;;;N;;;;; 293E;LOWER RIGHT SEMICIRCULAR CLOCKWISE ARROW;Sm;0;ON;;;;;N;;;;; 293F;LOWER LEFT SEMICIRCULAR ANTICLOCKWISE ARROW;Sm;0;ON;;;;;N;;;;; 2940;ANTICLOCKWISE CLOSED CIRCLE ARROW;Sm;0;ON;;;;;N;;;;; 2941;CLOCKWISE CLOSED CIRCLE ARROW;Sm;0;ON;;;;;N;;;;; 2942;RIGHTWARDS ARROW ABOVE SHORT LEFTWARDS ARROW;Sm;0;ON;;;;;N;;;;; 2943;LEFTWARDS ARROW ABOVE SHORT RIGHTWARDS ARROW;Sm;0;ON;;;;;N;;;;; 2944;SHORT RIGHTWARDS ARROW ABOVE LEFTWARDS ARROW;Sm;0;ON;;;;;N;;;;; 2945;RIGHTWARDS ARROW WITH PLUS BELOW;Sm;0;ON;;;;;N;;;;; 2946;LEFTWARDS ARROW WITH PLUS BELOW;Sm;0;ON;;;;;N;;;;; 2947;RIGHTWARDS ARROW THROUGH X;Sm;0;ON;;;;;N;;;;; 2948;LEFT RIGHT ARROW THROUGH SMALL CIRCLE;Sm;0;ON;;;;;N;;;;; 2949;UPWARDS TWO-HEADED ARROW FROM SMALL CIRCLE;Sm;0;ON;;;;;N;;;;; 294A;LEFT BARB UP RIGHT BARB DOWN HARPOON;Sm;0;ON;;;;;N;;;;; 294B;LEFT BARB DOWN RIGHT BARB UP HARPOON;Sm;0;ON;;;;;N;;;;; 294C;UP BARB RIGHT DOWN BARB LEFT HARPOON;Sm;0;ON;;;;;N;;;;; 294D;UP BARB LEFT DOWN BARB RIGHT HARPOON;Sm;0;ON;;;;;N;;;;; 294E;LEFT BARB UP RIGHT BARB UP HARPOON;Sm;0;ON;;;;;N;;;;; 294F;UP BARB RIGHT DOWN BARB RIGHT HARPOON;Sm;0;ON;;;;;N;;;;; 2950;LEFT BARB DOWN RIGHT BARB DOWN HARPOON;Sm;0;ON;;;;;N;;;;; 2951;UP BARB LEFT DOWN BARB LEFT HARPOON;Sm;0;ON;;;;;N;;;;; 2952;LEFTWARDS HARPOON WITH BARB UP TO BAR;Sm;0;ON;;;;;N;;;;; 2953;RIGHTWARDS HARPOON WITH BARB UP TO BAR;Sm;0;ON;;;;;N;;;;; 2954;UPWARDS HARPOON WITH BARB RIGHT TO BAR;Sm;0;ON;;;;;N;;;;; 2955;DOWNWARDS HARPOON WITH BARB RIGHT TO BAR;Sm;0;ON;;;;;N;;;;; 2956;LEFTWARDS HARPOON WITH BARB DOWN TO BAR;Sm;0;ON;;;;;N;;;;; 2957;RIGHTWARDS HARPOON WITH BARB DOWN TO BAR;Sm;0;ON;;;;;N;;;;; 2958;UPWARDS HARPOON WITH BARB LEFT TO BAR;Sm;0;ON;;;;;N;;;;; 2959;DOWNWARDS HARPOON WITH BARB LEFT TO BAR;Sm;0;ON;;;;;N;;;;; 295A;LEFTWARDS HARPOON WITH BARB UP FROM BAR;Sm;0;ON;;;;;N;;;;; 295B;RIGHTWARDS HARPOON WITH BARB UP FROM BAR;Sm;0;ON;;;;;N;;;;; 295C;UPWARDS HARPOON WITH BARB RIGHT FROM BAR;Sm;0;ON;;;;;N;;;;; 295D;DOWNWARDS HARPOON WITH BARB RIGHT FROM BAR;Sm;0;ON;;;;;N;;;;; 295E;LEFTWARDS HARPOON WITH BARB DOWN FROM BAR;Sm;0;ON;;;;;N;;;;; 295F;RIGHTWARDS HARPOON WITH BARB DOWN FROM BAR;Sm;0;ON;;;;;N;;;;; 2960;UPWARDS HARPOON WITH BARB LEFT FROM BAR;Sm;0;ON;;;;;N;;;;; 2961;DOWNWARDS HARPOON WITH BARB LEFT FROM BAR;Sm;0;ON;;;;;N;;;;; 2962;LEFTWARDS HARPOON WITH BARB UP ABOVE LEFTWARDS HARPOON WITH BARB DOWN;Sm;0;ON;;;;;N;;;;; 2963;UPWARDS HARPOON WITH BARB LEFT BESIDE UPWARDS HARPOON WITH BARB RIGHT;Sm;0;ON;;;;;N;;;;; 2964;RIGHTWARDS HARPOON WITH BARB UP ABOVE RIGHTWARDS HARPOON WITH BARB DOWN;Sm;0;ON;;;;;N;;;;; 2965;DOWNWARDS HARPOON WITH BARB LEFT BESIDE DOWNWARDS HARPOON WITH BARB RIGHT;Sm;0;ON;;;;;N;;;;; 2966;LEFTWARDS HARPOON WITH BARB UP ABOVE RIGHTWARDS HARPOON WITH BARB UP;Sm;0;ON;;;;;N;;;;; 2967;LEFTWARDS HARPOON WITH BARB DOWN ABOVE RIGHTWARDS HARPOON WITH BARB DOWN;Sm;0;ON;;;;;N;;;;; 2968;RIGHTWARDS HARPOON WITH BARB UP ABOVE LEFTWARDS HARPOON WITH BARB UP;Sm;0;ON;;;;;N;;;;; 2969;RIGHTWARDS HARPOON WITH BARB DOWN ABOVE LEFTWARDS HARPOON WITH BARB DOWN;Sm;0;ON;;;;;N;;;;; 296A;LEFTWARDS HARPOON WITH BARB UP ABOVE LONG DASH;Sm;0;ON;;;;;N;;;;; 296B;LEFTWARDS HARPOON WITH BARB DOWN BELOW LONG DASH;Sm;0;ON;;;;;N;;;;; 296C;RIGHTWARDS HARPOON WITH BARB UP ABOVE LONG DASH;Sm;0;ON;;;;;N;;;;; 296D;RIGHTWARDS HARPOON WITH BARB DOWN BELOW LONG DASH;Sm;0;ON;;;;;N;;;;; 296E;UPWARDS HARPOON WITH BARB LEFT BESIDE DOWNWARDS HARPOON WITH BARB RIGHT;Sm;0;ON;;;;;N;;;;; 296F;DOWNWARDS HARPOON WITH BARB LEFT BESIDE UPWARDS HARPOON WITH BARB RIGHT;Sm;0;ON;;;;;N;;;;; 2970;RIGHT DOUBLE ARROW WITH ROUNDED HEAD;Sm;0;ON;;;;;N;;;;; 2971;EQUALS SIGN ABOVE RIGHTWARDS ARROW;Sm;0;ON;;;;;N;;;;; 2972;TILDE OPERATOR ABOVE RIGHTWARDS ARROW;Sm;0;ON;;;;;N;;;;; 2973;LEFTWARDS ARROW ABOVE TILDE OPERATOR;Sm;0;ON;;;;;N;;;;; 2974;RIGHTWARDS ARROW ABOVE TILDE OPERATOR;Sm;0;ON;;;;;N;;;;; 2975;RIGHTWARDS ARROW ABOVE ALMOST EQUAL TO;Sm;0;ON;;;;;N;;;;; 2976;LESS-THAN ABOVE LEFTWARDS ARROW;Sm;0;ON;;;;;N;;;;; 2977;LEFTWARDS ARROW THROUGH LESS-THAN;Sm;0;ON;;;;;N;;;;; 2978;GREATER-THAN ABOVE RIGHTWARDS ARROW;Sm;0;ON;;;;;N;;;;; 2979;SUBSET ABOVE RIGHTWARDS ARROW;Sm;0;ON;;;;;N;;;;; 297A;LEFTWARDS ARROW THROUGH SUBSET;Sm;0;ON;;;;;N;;;;; 297B;SUPERSET ABOVE LEFTWARDS ARROW;Sm;0;ON;;;;;N;;;;; 297C;LEFT FISH TAIL;Sm;0;ON;;;;;N;;;;; 297D;RIGHT FISH TAIL;Sm;0;ON;;;;;N;;;;; 297E;UP FISH TAIL;Sm;0;ON;;;;;N;;;;; 297F;DOWN FISH TAIL;Sm;0;ON;;;;;N;;;;; 2980;TRIPLE VERTICAL BAR DELIMITER;Sm;0;ON;;;;;N;;;;; 2981;Z NOTATION SPOT;Sm;0;ON;;;;;N;;;;; 2982;Z NOTATION TYPE COLON;Sm;0;ON;;;;;N;;;;; 2983;LEFT WHITE CURLY BRACKET;Ps;0;ON;;;;;Y;;;;; 2984;RIGHT WHITE CURLY BRACKET;Pe;0;ON;;;;;Y;;;;; 2985;LEFT WHITE PARENTHESIS;Ps;0;ON;;;;;Y;;;;; 2986;RIGHT WHITE PARENTHESIS;Pe;0;ON;;;;;Y;;;;; 2987;Z NOTATION LEFT IMAGE BRACKET;Ps;0;ON;;;;;Y;;;;; 2988;Z NOTATION RIGHT IMAGE BRACKET;Pe;0;ON;;;;;Y;;;;; 2989;Z NOTATION LEFT BINDING BRACKET;Ps;0;ON;;;;;Y;;;;; 298A;Z NOTATION RIGHT BINDING BRACKET;Pe;0;ON;;;;;Y;;;;; 298B;LEFT SQUARE BRACKET WITH UNDERBAR;Ps;0;ON;;;;;Y;;;;; 298C;RIGHT SQUARE BRACKET WITH UNDERBAR;Pe;0;ON;;;;;Y;;;;; 298D;LEFT SQUARE BRACKET WITH TICK IN TOP CORNER;Ps;0;ON;;;;;Y;;;;; 298E;RIGHT SQUARE BRACKET WITH TICK IN BOTTOM CORNER;Pe;0;ON;;;;;Y;;;;; 298F;LEFT SQUARE BRACKET WITH TICK IN BOTTOM CORNER;Ps;0;ON;;;;;Y;;;;; 2990;RIGHT SQUARE BRACKET WITH TICK IN TOP CORNER;Pe;0;ON;;;;;Y;;;;; 2991;LEFT ANGLE BRACKET WITH DOT;Ps;0;ON;;;;;Y;;;;; 2992;RIGHT ANGLE BRACKET WITH DOT;Pe;0;ON;;;;;Y;;;;; 2993;LEFT ARC LESS-THAN BRACKET;Ps;0;ON;;;;;Y;;;;; 2994;RIGHT ARC GREATER-THAN BRACKET;Pe;0;ON;;;;;Y;;;;; 2995;DOUBLE LEFT ARC GREATER-THAN BRACKET;Ps;0;ON;;;;;Y;;;;; 2996;DOUBLE RIGHT ARC LESS-THAN BRACKET;Pe;0;ON;;;;;Y;;;;; 2997;LEFT BLACK TORTOISE SHELL BRACKET;Ps;0;ON;;;;;Y;;;;; 2998;RIGHT BLACK TORTOISE SHELL BRACKET;Pe;0;ON;;;;;Y;;;;; 2999;DOTTED FENCE;Sm;0;ON;;;;;N;;;;; 299A;VERTICAL ZIGZAG LINE;Sm;0;ON;;;;;N;;;;; 299B;MEASURED ANGLE OPENING LEFT;Sm;0;ON;;;;;Y;;;;; 299C;RIGHT ANGLE VARIANT WITH SQUARE;Sm;0;ON;;;;;Y;;;;; 299D;MEASURED RIGHT ANGLE WITH DOT;Sm;0;ON;;;;;Y;;;;; 299E;ANGLE WITH S INSIDE;Sm;0;ON;;;;;Y;;;;; 299F;ACUTE ANGLE;Sm;0;ON;;;;;Y;;;;; 29A0;SPHERICAL ANGLE OPENING LEFT;Sm;0;ON;;;;;Y;;;;; 29A1;SPHERICAL ANGLE OPENING UP;Sm;0;ON;;;;;Y;;;;; 29A2;TURNED ANGLE;Sm;0;ON;;;;;Y;;;;; 29A3;REVERSED ANGLE;Sm;0;ON;;;;;Y;;;;; 29A4;ANGLE WITH UNDERBAR;Sm;0;ON;;;;;Y;;;;; 29A5;REVERSED ANGLE WITH UNDERBAR;Sm;0;ON;;;;;Y;;;;; 29A6;OBLIQUE ANGLE OPENING UP;Sm;0;ON;;;;;Y;;;;; 29A7;OBLIQUE ANGLE OPENING DOWN;Sm;0;ON;;;;;Y;;;;; 29A8;MEASURED ANGLE WITH OPEN ARM ENDING IN ARROW POINTING UP AND RIGHT;Sm;0;ON;;;;;Y;;;;; 29A9;MEASURED ANGLE WITH OPEN ARM ENDING IN ARROW POINTING UP AND LEFT;Sm;0;ON;;;;;Y;;;;; 29AA;MEASURED ANGLE WITH OPEN ARM ENDING IN ARROW POINTING DOWN AND RIGHT;Sm;0;ON;;;;;Y;;;;; 29AB;MEASURED ANGLE WITH OPEN ARM ENDING IN ARROW POINTING DOWN AND LEFT;Sm;0;ON;;;;;Y;;;;; 29AC;MEASURED ANGLE WITH OPEN ARM ENDING IN ARROW POINTING RIGHT AND UP;Sm;0;ON;;;;;Y;;;;; 29AD;MEASURED ANGLE WITH OPEN ARM ENDING IN ARROW POINTING LEFT AND UP;Sm;0;ON;;;;;Y;;;;; 29AE;MEASURED ANGLE WITH OPEN ARM ENDING IN ARROW POINTING RIGHT AND DOWN;Sm;0;ON;;;;;Y;;;;; 29AF;MEASURED ANGLE WITH OPEN ARM ENDING IN ARROW POINTING LEFT AND DOWN;Sm;0;ON;;;;;Y;;;;; 29B0;REVERSED EMPTY SET;Sm;0;ON;;;;;N;;;;; 29B1;EMPTY SET WITH OVERBAR;Sm;0;ON;;;;;N;;;;; 29B2;EMPTY SET WITH SMALL CIRCLE ABOVE;Sm;0;ON;;;;;N;;;;; 29B3;EMPTY SET WITH RIGHT ARROW ABOVE;Sm;0;ON;;;;;N;;;;; 29B4;EMPTY SET WITH LEFT ARROW ABOVE;Sm;0;ON;;;;;N;;;;; 29B5;CIRCLE WITH HORIZONTAL BAR;Sm;0;ON;;;;;N;;;;; 29B6;CIRCLED VERTICAL BAR;Sm;0;ON;;;;;N;;;;; 29B7;CIRCLED PARALLEL;Sm;0;ON;;;;;N;;;;; 29B8;CIRCLED REVERSE SOLIDUS;Sm;0;ON;;;;;Y;;;;; 29B9;CIRCLED PERPENDICULAR;Sm;0;ON;;;;;N;;;;; 29BA;CIRCLE DIVIDED BY HORIZONTAL BAR AND TOP HALF DIVIDED BY VERTICAL BAR;Sm;0;ON;;;;;N;;;;; 29BB;CIRCLE WITH SUPERIMPOSED X;Sm;0;ON;;;;;N;;;;; 29BC;CIRCLED ANTICLOCKWISE-ROTATED DIVISION SIGN;Sm;0;ON;;;;;N;;;;; 29BD;UP ARROW THROUGH CIRCLE;Sm;0;ON;;;;;N;;;;; 29BE;CIRCLED WHITE BULLET;Sm;0;ON;;;;;N;;;;; 29BF;CIRCLED BULLET;Sm;0;ON;;;;;N;;;;; 29C0;CIRCLED LESS-THAN;Sm;0;ON;;;;;Y;;;;; 29C1;CIRCLED GREATER-THAN;Sm;0;ON;;;;;Y;;;;; 29C2;CIRCLE WITH SMALL CIRCLE TO THE RIGHT;Sm;0;ON;;;;;Y;;;;; 29C3;CIRCLE WITH TWO HORIZONTAL STROKES TO THE RIGHT;Sm;0;ON;;;;;Y;;;;; 29C4;SQUARED RISING DIAGONAL SLASH;Sm;0;ON;;;;;Y;;;;; 29C5;SQUARED FALLING DIAGONAL SLASH;Sm;0;ON;;;;;Y;;;;; 29C6;SQUARED ASTERISK;Sm;0;ON;;;;;N;;;;; 29C7;SQUARED SMALL CIRCLE;Sm;0;ON;;;;;N;;;;; 29C8;SQUARED SQUARE;Sm;0;ON;;;;;N;;;;; 29C9;TWO JOINED SQUARES;Sm;0;ON;;;;;Y;;;;; 29CA;TRIANGLE WITH DOT ABOVE;Sm;0;ON;;;;;N;;;;; 29CB;TRIANGLE WITH UNDERBAR;Sm;0;ON;;;;;N;;;;; 29CC;S IN TRIANGLE;Sm;0;ON;;;;;N;;;;; 29CD;TRIANGLE WITH SERIFS AT BOTTOM;Sm;0;ON;;;;;N;;;;; 29CE;RIGHT TRIANGLE ABOVE LEFT TRIANGLE;Sm;0;ON;;;;;Y;;;;; 29CF;LEFT TRIANGLE BESIDE VERTICAL BAR;Sm;0;ON;;;;;Y;;;;; 29D0;VERTICAL BAR BESIDE RIGHT TRIANGLE;Sm;0;ON;;;;;Y;;;;; 29D1;BOWTIE WITH LEFT HALF BLACK;Sm;0;ON;;;;;Y;;;;; 29D2;BOWTIE WITH RIGHT HALF BLACK;Sm;0;ON;;;;;Y;;;;; 29D3;BLACK BOWTIE;Sm;0;ON;;;;;N;;;;; 29D4;TIMES WITH LEFT HALF BLACK;Sm;0;ON;;;;;Y;;;;; 29D5;TIMES WITH RIGHT HALF BLACK;Sm;0;ON;;;;;Y;;;;; 29D6;WHITE HOURGLASS;Sm;0;ON;;;;;N;;;;; 29D7;BLACK HOURGLASS;Sm;0;ON;;;;;N;;;;; 29D8;LEFT WIGGLY FENCE;Ps;0;ON;;;;;Y;;;;; 29D9;RIGHT WIGGLY FENCE;Pe;0;ON;;;;;Y;;;;; 29DA;LEFT DOUBLE WIGGLY FENCE;Ps;0;ON;;;;;Y;;;;; 29DB;RIGHT DOUBLE WIGGLY FENCE;Pe;0;ON;;;;;Y;;;;; 29DC;INCOMPLETE INFINITY;Sm;0;ON;;;;;Y;;;;; 29DD;TIE OVER INFINITY;Sm;0;ON;;;;;N;;;;; 29DE;INFINITY NEGATED WITH VERTICAL BAR;Sm;0;ON;;;;;N;;;;; 29DF;DOUBLE-ENDED MULTIMAP;Sm;0;ON;;;;;N;;;;; 29E0;SQUARE WITH CONTOURED OUTLINE;Sm;0;ON;;;;;N;;;;; 29E1;INCREASES AS;Sm;0;ON;;;;;Y;;;;; 29E2;SHUFFLE PRODUCT;Sm;0;ON;;;;;N;;;;; 29E3;EQUALS SIGN AND SLANTED PARALLEL;Sm;0;ON;;;;;Y;;;;; 29E4;EQUALS SIGN AND SLANTED PARALLEL WITH TILDE ABOVE;Sm;0;ON;;;;;Y;;;;; 29E5;IDENTICAL TO AND SLANTED PARALLEL;Sm;0;ON;;;;;Y;;;;; 29E6;GLEICH STARK;Sm;0;ON;;;;;N;;;;; 29E7;THERMODYNAMIC;Sm;0;ON;;;;;N;;;;; 29E8;DOWN-POINTING TRIANGLE WITH LEFT HALF BLACK;Sm;0;ON;;;;;Y;;;;; 29E9;DOWN-POINTING TRIANGLE WITH RIGHT HALF BLACK;Sm;0;ON;;;;;Y;;;;; 29EA;BLACK DIAMOND WITH DOWN ARROW;Sm;0;ON;;;;;N;;;;; 29EB;BLACK LOZENGE;Sm;0;ON;;;;;N;;;;; 29EC;WHITE CIRCLE WITH DOWN ARROW;Sm;0;ON;;;;;N;;;;; 29ED;BLACK CIRCLE WITH DOWN ARROW;Sm;0;ON;;;;;N;;;;; 29EE;ERROR-BARRED WHITE SQUARE;Sm;0;ON;;;;;N;;;;; 29EF;ERROR-BARRED BLACK SQUARE;Sm;0;ON;;;;;N;;;;; 29F0;ERROR-BARRED WHITE DIAMOND;Sm;0;ON;;;;;N;;;;; 29F1;ERROR-BARRED BLACK DIAMOND;Sm;0;ON;;;;;N;;;;; 29F2;ERROR-BARRED WHITE CIRCLE;Sm;0;ON;;;;;N;;;;; 29F3;ERROR-BARRED BLACK CIRCLE;Sm;0;ON;;;;;N;;;;; 29F4;RULE-DELAYED;Sm;0;ON;;;;;Y;;;;; 29F5;REVERSE SOLIDUS OPERATOR;Sm;0;ON;;;;;Y;;;;; 29F6;SOLIDUS WITH OVERBAR;Sm;0;ON;;;;;Y;;;;; 29F7;REVERSE SOLIDUS WITH HORIZONTAL STROKE;Sm;0;ON;;;;;Y;;;;; 29F8;BIG SOLIDUS;Sm;0;ON;;;;;Y;;;;; 29F9;BIG REVERSE SOLIDUS;Sm;0;ON;;;;;Y;;;;; 29FA;DOUBLE PLUS;Sm;0;ON;;;;;N;;;;; 29FB;TRIPLE PLUS;Sm;0;ON;;;;;N;;;;; 29FC;LEFT-POINTING CURVED ANGLE BRACKET;Ps;0;ON;;;;;Y;;;;; 29FD;RIGHT-POINTING CURVED ANGLE BRACKET;Pe;0;ON;;;;;Y;;;;; 29FE;TINY;Sm;0;ON;;;;;N;;;;; 29FF;MINY;Sm;0;ON;;;;;N;;;;; 2A00;N-ARY CIRCLED DOT OPERATOR;Sm;0;ON;;;;;N;;;;; 2A01;N-ARY CIRCLED PLUS OPERATOR;Sm;0;ON;;;;;N;;;;; 2A02;N-ARY CIRCLED TIMES OPERATOR;Sm;0;ON;;;;;N;;;;; 2A03;N-ARY UNION OPERATOR WITH DOT;Sm;0;ON;;;;;N;;;;; 2A04;N-ARY UNION OPERATOR WITH PLUS;Sm;0;ON;;;;;N;;;;; 2A05;N-ARY SQUARE INTERSECTION OPERATOR;Sm;0;ON;;;;;N;;;;; 2A06;N-ARY SQUARE UNION OPERATOR;Sm;0;ON;;;;;N;;;;; 2A07;TWO LOGICAL AND OPERATOR;Sm;0;ON;;;;;N;;;;; 2A08;TWO LOGICAL OR OPERATOR;Sm;0;ON;;;;;N;;;;; 2A09;N-ARY TIMES OPERATOR;Sm;0;ON;;;;;N;;;;; 2A0A;MODULO TWO SUM;Sm;0;ON;;;;;Y;;;;; 2A0B;SUMMATION WITH INTEGRAL;Sm;0;ON;;;;;Y;;;;; 2A0C;QUADRUPLE INTEGRAL OPERATOR;Sm;0;ON; 222B 222B 222B 222B;;;;Y;;;;; 2A0D;FINITE PART INTEGRAL;Sm;0;ON;;;;;Y;;;;; 2A0E;INTEGRAL WITH DOUBLE STROKE;Sm;0;ON;;;;;Y;;;;; 2A0F;INTEGRAL AVERAGE WITH SLASH;Sm;0;ON;;;;;Y;;;;; 2A10;CIRCULATION FUNCTION;Sm;0;ON;;;;;Y;;;;; 2A11;ANTICLOCKWISE INTEGRATION;Sm;0;ON;;;;;Y;;;;; 2A12;LINE INTEGRATION WITH RECTANGULAR PATH AROUND POLE;Sm;0;ON;;;;;Y;;;;; 2A13;LINE INTEGRATION WITH SEMICIRCULAR PATH AROUND POLE;Sm;0;ON;;;;;Y;;;;; 2A14;LINE INTEGRATION NOT INCLUDING THE POLE;Sm;0;ON;;;;;Y;;;;; 2A15;INTEGRAL AROUND A POINT OPERATOR;Sm;0;ON;;;;;Y;;;;; 2A16;QUATERNION INTEGRAL OPERATOR;Sm;0;ON;;;;;Y;;;;; 2A17;INTEGRAL WITH LEFTWARDS ARROW WITH HOOK;Sm;0;ON;;;;;Y;;;;; 2A18;INTEGRAL WITH TIMES SIGN;Sm;0;ON;;;;;Y;;;;; 2A19;INTEGRAL WITH INTERSECTION;Sm;0;ON;;;;;Y;;;;; 2A1A;INTEGRAL WITH UNION;Sm;0;ON;;;;;Y;;;;; 2A1B;INTEGRAL WITH OVERBAR;Sm;0;ON;;;;;Y;;;;; 2A1C;INTEGRAL WITH UNDERBAR;Sm;0;ON;;;;;Y;;;;; 2A1D;JOIN;Sm;0;ON;;;;;N;;;;; 2A1E;LARGE LEFT TRIANGLE OPERATOR;Sm;0;ON;;;;;Y;;;;; 2A1F;Z NOTATION SCHEMA COMPOSITION;Sm;0;ON;;;;;Y;;;;; 2A20;Z NOTATION SCHEMA PIPING;Sm;0;ON;;;;;Y;;;;; 2A21;Z NOTATION SCHEMA PROJECTION;Sm;0;ON;;;;;Y;;;;; 2A22;PLUS SIGN WITH SMALL CIRCLE ABOVE;Sm;0;ON;;;;;N;;;;; 2A23;PLUS SIGN WITH CIRCUMFLEX ACCENT ABOVE;Sm;0;ON;;;;;N;;;;; 2A24;PLUS SIGN WITH TILDE ABOVE;Sm;0;ON;;;;;Y;;;;; 2A25;PLUS SIGN WITH DOT BELOW;Sm;0;ON;;;;;N;;;;; 2A26;PLUS SIGN WITH TILDE BELOW;Sm;0;ON;;;;;Y;;;;; 2A27;PLUS SIGN WITH SUBSCRIPT TWO;Sm;0;ON;;;;;N;;;;; 2A28;PLUS SIGN WITH BLACK TRIANGLE;Sm;0;ON;;;;;N;;;;; 2A29;MINUS SIGN WITH COMMA ABOVE;Sm;0;ON;;;;;Y;;;;; 2A2A;MINUS SIGN WITH DOT BELOW;Sm;0;ON;;;;;N;;;;; 2A2B;MINUS SIGN WITH FALLING DOTS;Sm;0;ON;;;;;Y;;;;; 2A2C;MINUS SIGN WITH RISING DOTS;Sm;0;ON;;;;;Y;;;;; 2A2D;PLUS SIGN IN LEFT HALF CIRCLE;Sm;0;ON;;;;;Y;;;;; 2A2E;PLUS SIGN IN RIGHT HALF CIRCLE;Sm;0;ON;;;;;Y;;;;; 2A2F;VECTOR OR CROSS PRODUCT;Sm;0;ON;;;;;N;;;;; 2A30;MULTIPLICATION SIGN WITH DOT ABOVE;Sm;0;ON;;;;;N;;;;; 2A31;MULTIPLICATION SIGN WITH UNDERBAR;Sm;0;ON;;;;;N;;;;; 2A32;SEMIDIRECT PRODUCT WITH BOTTOM CLOSED;Sm;0;ON;;;;;N;;;;; 2A33;SMASH PRODUCT;Sm;0;ON;;;;;N;;;;; 2A34;MULTIPLICATION SIGN IN LEFT HALF CIRCLE;Sm;0;ON;;;;;Y;;;;; 2A35;MULTIPLICATION SIGN IN RIGHT HALF CIRCLE;Sm;0;ON;;;;;Y;;;;; 2A36;CIRCLED MULTIPLICATION SIGN WITH CIRCUMFLEX ACCENT;Sm;0;ON;;;;;N;;;;; 2A37;MULTIPLICATION SIGN IN DOUBLE CIRCLE;Sm;0;ON;;;;;N;;;;; 2A38;CIRCLED DIVISION SIGN;Sm;0;ON;;;;;N;;;;; 2A39;PLUS SIGN IN TRIANGLE;Sm;0;ON;;;;;N;;;;; 2A3A;MINUS SIGN IN TRIANGLE;Sm;0;ON;;;;;N;;;;; 2A3B;MULTIPLICATION SIGN IN TRIANGLE;Sm;0;ON;;;;;N;;;;; 2A3C;INTERIOR PRODUCT;Sm;0;ON;;;;;Y;;;;; 2A3D;RIGHTHAND INTERIOR PRODUCT;Sm;0;ON;;;;;Y;;;;; 2A3E;Z NOTATION RELATIONAL COMPOSITION;Sm;0;ON;;;;;Y;;;;; 2A3F;AMALGAMATION OR COPRODUCT;Sm;0;ON;;;;;N;;;;; 2A40;INTERSECTION WITH DOT;Sm;0;ON;;;;;N;;;;; 2A41;UNION WITH MINUS SIGN;Sm;0;ON;;;;;N;;;;; 2A42;UNION WITH OVERBAR;Sm;0;ON;;;;;N;;;;; 2A43;INTERSECTION WITH OVERBAR;Sm;0;ON;;;;;N;;;;; 2A44;INTERSECTION WITH LOGICAL AND;Sm;0;ON;;;;;N;;;;; 2A45;UNION WITH LOGICAL OR;Sm;0;ON;;;;;N;;;;; 2A46;UNION ABOVE INTERSECTION;Sm;0;ON;;;;;N;;;;; 2A47;INTERSECTION ABOVE UNION;Sm;0;ON;;;;;N;;;;; 2A48;UNION ABOVE BAR ABOVE INTERSECTION;Sm;0;ON;;;;;N;;;;; 2A49;INTERSECTION ABOVE BAR ABOVE UNION;Sm;0;ON;;;;;N;;;;; 2A4A;UNION BESIDE AND JOINED WITH UNION;Sm;0;ON;;;;;N;;;;; 2A4B;INTERSECTION BESIDE AND JOINED WITH INTERSECTION;Sm;0;ON;;;;;N;;;;; 2A4C;CLOSED UNION WITH SERIFS;Sm;0;ON;;;;;N;;;;; 2A4D;CLOSED INTERSECTION WITH SERIFS;Sm;0;ON;;;;;N;;;;; 2A4E;DOUBLE SQUARE INTERSECTION;Sm;0;ON;;;;;N;;;;; 2A4F;DOUBLE SQUARE UNION;Sm;0;ON;;;;;N;;;;; 2A50;CLOSED UNION WITH SERIFS AND SMASH PRODUCT;Sm;0;ON;;;;;N;;;;; 2A51;LOGICAL AND WITH DOT ABOVE;Sm;0;ON;;;;;N;;;;; 2A52;LOGICAL OR WITH DOT ABOVE;Sm;0;ON;;;;;N;;;;; 2A53;DOUBLE LOGICAL AND;Sm;0;ON;;;;;N;;;;; 2A54;DOUBLE LOGICAL OR;Sm;0;ON;;;;;N;;;;; 2A55;TWO INTERSECTING LOGICAL AND;Sm;0;ON;;;;;N;;;;; 2A56;TWO INTERSECTING LOGICAL OR;Sm;0;ON;;;;;N;;;;; 2A57;SLOPING LARGE OR;Sm;0;ON;;;;;Y;;;;; 2A58;SLOPING LARGE AND;Sm;0;ON;;;;;Y;;;;; 2A59;LOGICAL OR OVERLAPPING LOGICAL AND;Sm;0;ON;;;;;N;;;;; 2A5A;LOGICAL AND WITH MIDDLE STEM;Sm;0;ON;;;;;N;;;;; 2A5B;LOGICAL OR WITH MIDDLE STEM;Sm;0;ON;;;;;N;;;;; 2A5C;LOGICAL AND WITH HORIZONTAL DASH;Sm;0;ON;;;;;N;;;;; 2A5D;LOGICAL OR WITH HORIZONTAL DASH;Sm;0;ON;;;;;N;;;;; 2A5E;LOGICAL AND WITH DOUBLE OVERBAR;Sm;0;ON;;;;;N;;;;; 2A5F;LOGICAL AND WITH UNDERBAR;Sm;0;ON;;;;;N;;;;; 2A60;LOGICAL AND WITH DOUBLE UNDERBAR;Sm;0;ON;;;;;N;;;;; 2A61;SMALL VEE WITH UNDERBAR;Sm;0;ON;;;;;N;;;;; 2A62;LOGICAL OR WITH DOUBLE OVERBAR;Sm;0;ON;;;;;N;;;;; 2A63;LOGICAL OR WITH DOUBLE UNDERBAR;Sm;0;ON;;;;;N;;;;; 2A64;Z NOTATION DOMAIN ANTIRESTRICTION;Sm;0;ON;;;;;Y;;;;; 2A65;Z NOTATION RANGE ANTIRESTRICTION;Sm;0;ON;;;;;Y;;;;; 2A66;EQUALS SIGN WITH DOT BELOW;Sm;0;ON;;;;;N;;;;; 2A67;IDENTICAL WITH DOT ABOVE;Sm;0;ON;;;;;N;;;;; 2A68;TRIPLE HORIZONTAL BAR WITH DOUBLE VERTICAL STROKE;Sm;0;ON;;;;;N;;;;; 2A69;TRIPLE HORIZONTAL BAR WITH TRIPLE VERTICAL STROKE;Sm;0;ON;;;;;N;;;;; 2A6A;TILDE OPERATOR WITH DOT ABOVE;Sm;0;ON;;;;;Y;;;;; 2A6B;TILDE OPERATOR WITH RISING DOTS;Sm;0;ON;;;;;Y;;;;; 2A6C;SIMILAR MINUS SIMILAR;Sm;0;ON;;;;;Y;;;;; 2A6D;CONGRUENT WITH DOT ABOVE;Sm;0;ON;;;;;Y;;;;; 2A6E;EQUALS WITH ASTERISK;Sm;0;ON;;;;;N;;;;; 2A6F;ALMOST EQUAL TO WITH CIRCUMFLEX ACCENT;Sm;0;ON;;;;;Y;;;;; 2A70;APPROXIMATELY EQUAL OR EQUAL TO;Sm;0;ON;;;;;Y;;;;; 2A71;EQUALS SIGN ABOVE PLUS SIGN;Sm;0;ON;;;;;N;;;;; 2A72;PLUS SIGN ABOVE EQUALS SIGN;Sm;0;ON;;;;;N;;;;; 2A73;EQUALS SIGN ABOVE TILDE OPERATOR;Sm;0;ON;;;;;Y;;;;; 2A74;DOUBLE COLON EQUAL;Sm;0;ON; 003A 003A 003D;;;;Y;;;;; 2A75;TWO CONSECUTIVE EQUALS SIGNS;Sm;0;ON; 003D 003D;;;;N;;;;; 2A76;THREE CONSECUTIVE EQUALS SIGNS;Sm;0;ON; 003D 003D 003D;;;;N;;;;; 2A77;EQUALS SIGN WITH TWO DOTS ABOVE AND TWO DOTS BELOW;Sm;0;ON;;;;;N;;;;; 2A78;EQUIVALENT WITH FOUR DOTS ABOVE;Sm;0;ON;;;;;N;;;;; 2A79;LESS-THAN WITH CIRCLE INSIDE;Sm;0;ON;;;;;Y;;;;; 2A7A;GREATER-THAN WITH CIRCLE INSIDE;Sm;0;ON;;;;;Y;;;;; 2A7B;LESS-THAN WITH QUESTION MARK ABOVE;Sm;0;ON;;;;;Y;;;;; 2A7C;GREATER-THAN WITH QUESTION MARK ABOVE;Sm;0;ON;;;;;Y;;;;; 2A7D;LESS-THAN OR SLANTED EQUAL TO;Sm;0;ON;;;;;Y;;;;; 2A7E;GREATER-THAN OR SLANTED EQUAL TO;Sm;0;ON;;;;;Y;;;;; 2A7F;LESS-THAN OR SLANTED EQUAL TO WITH DOT INSIDE;Sm;0;ON;;;;;Y;;;;; 2A80;GREATER-THAN OR SLANTED EQUAL TO WITH DOT INSIDE;Sm;0;ON;;;;;Y;;;;; 2A81;LESS-THAN OR SLANTED EQUAL TO WITH DOT ABOVE;Sm;0;ON;;;;;Y;;;;; 2A82;GREATER-THAN OR SLANTED EQUAL TO WITH DOT ABOVE;Sm;0;ON;;;;;Y;;;;; 2A83;LESS-THAN OR SLANTED EQUAL TO WITH DOT ABOVE RIGHT;Sm;0;ON;;;;;Y;;;;; 2A84;GREATER-THAN OR SLANTED EQUAL TO WITH DOT ABOVE LEFT;Sm;0;ON;;;;;Y;;;;; 2A85;LESS-THAN OR APPROXIMATE;Sm;0;ON;;;;;Y;;;;; 2A86;GREATER-THAN OR APPROXIMATE;Sm;0;ON;;;;;Y;;;;; 2A87;LESS-THAN AND SINGLE-LINE NOT EQUAL TO;Sm;0;ON;;;;;Y;;;;; 2A88;GREATER-THAN AND SINGLE-LINE NOT EQUAL TO;Sm;0;ON;;;;;Y;;;;; 2A89;LESS-THAN AND NOT APPROXIMATE;Sm;0;ON;;;;;Y;;;;; 2A8A;GREATER-THAN AND NOT APPROXIMATE;Sm;0;ON;;;;;Y;;;;; 2A8B;LESS-THAN ABOVE DOUBLE-LINE EQUAL ABOVE GREATER-THAN;Sm;0;ON;;;;;Y;;;;; 2A8C;GREATER-THAN ABOVE DOUBLE-LINE EQUAL ABOVE LESS-THAN;Sm;0;ON;;;;;Y;;;;; 2A8D;LESS-THAN ABOVE SIMILAR OR EQUAL;Sm;0;ON;;;;;Y;;;;; 2A8E;GREATER-THAN ABOVE SIMILAR OR EQUAL;Sm;0;ON;;;;;Y;;;;; 2A8F;LESS-THAN ABOVE SIMILAR ABOVE GREATER-THAN;Sm;0;ON;;;;;Y;;;;; 2A90;GREATER-THAN ABOVE SIMILAR ABOVE LESS-THAN;Sm;0;ON;;;;;Y;;;;; 2A91;LESS-THAN ABOVE GREATER-THAN ABOVE DOUBLE-LINE EQUAL;Sm;0;ON;;;;;Y;;;;; 2A92;GREATER-THAN ABOVE LESS-THAN ABOVE DOUBLE-LINE EQUAL;Sm;0;ON;;;;;Y;;;;; 2A93;LESS-THAN ABOVE SLANTED EQUAL ABOVE GREATER-THAN ABOVE SLANTED EQUAL;Sm;0;ON;;;;;Y;;;;; 2A94;GREATER-THAN ABOVE SLANTED EQUAL ABOVE LESS-THAN ABOVE SLANTED EQUAL;Sm;0;ON;;;;;Y;;;;; 2A95;SLANTED EQUAL TO OR LESS-THAN;Sm;0;ON;;;;;Y;;;;; 2A96;SLANTED EQUAL TO OR GREATER-THAN;Sm;0;ON;;;;;Y;;;;; 2A97;SLANTED EQUAL TO OR LESS-THAN WITH DOT INSIDE;Sm;0;ON;;;;;Y;;;;; 2A98;SLANTED EQUAL TO OR GREATER-THAN WITH DOT INSIDE;Sm;0;ON;;;;;Y;;;;; 2A99;DOUBLE-LINE EQUAL TO OR LESS-THAN;Sm;0;ON;;;;;Y;;;;; 2A9A;DOUBLE-LINE EQUAL TO OR GREATER-THAN;Sm;0;ON;;;;;Y;;;;; 2A9B;DOUBLE-LINE SLANTED EQUAL TO OR LESS-THAN;Sm;0;ON;;;;;Y;;;;; 2A9C;DOUBLE-LINE SLANTED EQUAL TO OR GREATER-THAN;Sm;0;ON;;;;;Y;;;;; 2A9D;SIMILAR OR LESS-THAN;Sm;0;ON;;;;;Y;;;;; 2A9E;SIMILAR OR GREATER-THAN;Sm;0;ON;;;;;Y;;;;; 2A9F;SIMILAR ABOVE LESS-THAN ABOVE EQUALS SIGN;Sm;0;ON;;;;;Y;;;;; 2AA0;SIMILAR ABOVE GREATER-THAN ABOVE EQUALS SIGN;Sm;0;ON;;;;;Y;;;;; 2AA1;DOUBLE NESTED LESS-THAN;Sm;0;ON;;;;;Y;;;;; 2AA2;DOUBLE NESTED GREATER-THAN;Sm;0;ON;;;;;Y;;;;; 2AA3;DOUBLE NESTED LESS-THAN WITH UNDERBAR;Sm;0;ON;;;;;Y;;;;; 2AA4;GREATER-THAN OVERLAPPING LESS-THAN;Sm;0;ON;;;;;N;;;;; 2AA5;GREATER-THAN BESIDE LESS-THAN;Sm;0;ON;;;;;N;;;;; 2AA6;LESS-THAN CLOSED BY CURVE;Sm;0;ON;;;;;Y;;;;; 2AA7;GREATER-THAN CLOSED BY CURVE;Sm;0;ON;;;;;Y;;;;; 2AA8;LESS-THAN CLOSED BY CURVE ABOVE SLANTED EQUAL;Sm;0;ON;;;;;Y;;;;; 2AA9;GREATER-THAN CLOSED BY CURVE ABOVE SLANTED EQUAL;Sm;0;ON;;;;;Y;;;;; 2AAA;SMALLER THAN;Sm;0;ON;;;;;Y;;;;; 2AAB;LARGER THAN;Sm;0;ON;;;;;Y;;;;; 2AAC;SMALLER THAN OR EQUAL TO;Sm;0;ON;;;;;Y;;;;; 2AAD;LARGER THAN OR EQUAL TO;Sm;0;ON;;;;;Y;;;;; 2AAE;EQUALS SIGN WITH BUMPY ABOVE;Sm;0;ON;;;;;N;;;;; 2AAF;PRECEDES ABOVE SINGLE-LINE EQUALS SIGN;Sm;0;ON;;;;;Y;;;;; 2AB0;SUCCEEDS ABOVE SINGLE-LINE EQUALS SIGN;Sm;0;ON;;;;;Y;;;;; 2AB1;PRECEDES ABOVE SINGLE-LINE NOT EQUAL TO;Sm;0;ON;;;;;Y;;;;; 2AB2;SUCCEEDS ABOVE SINGLE-LINE NOT EQUAL TO;Sm;0;ON;;;;;Y;;;;; 2AB3;PRECEDES ABOVE EQUALS SIGN;Sm;0;ON;;;;;Y;;;;; 2AB4;SUCCEEDS ABOVE EQUALS SIGN;Sm;0;ON;;;;;Y;;;;; 2AB5;PRECEDES ABOVE NOT EQUAL TO;Sm;0;ON;;;;;Y;;;;; 2AB6;SUCCEEDS ABOVE NOT EQUAL TO;Sm;0;ON;;;;;Y;;;;; 2AB7;PRECEDES ABOVE ALMOST EQUAL TO;Sm;0;ON;;;;;Y;;;;; 2AB8;SUCCEEDS ABOVE ALMOST EQUAL TO;Sm;0;ON;;;;;Y;;;;; 2AB9;PRECEDES ABOVE NOT ALMOST EQUAL TO;Sm;0;ON;;;;;Y;;;;; 2ABA;SUCCEEDS ABOVE NOT ALMOST EQUAL TO;Sm;0;ON;;;;;Y;;;;; 2ABB;DOUBLE PRECEDES;Sm;0;ON;;;;;Y;;;;; 2ABC;DOUBLE SUCCEEDS;Sm;0;ON;;;;;Y;;;;; 2ABD;SUBSET WITH DOT;Sm;0;ON;;;;;Y;;;;; 2ABE;SUPERSET WITH DOT;Sm;0;ON;;;;;Y;;;;; 2ABF;SUBSET WITH PLUS SIGN BELOW;Sm;0;ON;;;;;Y;;;;; 2AC0;SUPERSET WITH PLUS SIGN BELOW;Sm;0;ON;;;;;Y;;;;; 2AC1;SUBSET WITH MULTIPLICATION SIGN BELOW;Sm;0;ON;;;;;Y;;;;; 2AC2;SUPERSET WITH MULTIPLICATION SIGN BELOW;Sm;0;ON;;;;;Y;;;;; 2AC3;SUBSET OF OR EQUAL TO WITH DOT ABOVE;Sm;0;ON;;;;;Y;;;;; 2AC4;SUPERSET OF OR EQUAL TO WITH DOT ABOVE;Sm;0;ON;;;;;Y;;;;; 2AC5;SUBSET OF ABOVE EQUALS SIGN;Sm;0;ON;;;;;Y;;;;; 2AC6;SUPERSET OF ABOVE EQUALS SIGN;Sm;0;ON;;;;;Y;;;;; 2AC7;SUBSET OF ABOVE TILDE OPERATOR;Sm;0;ON;;;;;Y;;;;; 2AC8;SUPERSET OF ABOVE TILDE OPERATOR;Sm;0;ON;;;;;Y;;;;; 2AC9;SUBSET OF ABOVE ALMOST EQUAL TO;Sm;0;ON;;;;;Y;;;;; 2ACA;SUPERSET OF ABOVE ALMOST EQUAL TO;Sm;0;ON;;;;;Y;;;;; 2ACB;SUBSET OF ABOVE NOT EQUAL TO;Sm;0;ON;;;;;Y;;;;; 2ACC;SUPERSET OF ABOVE NOT EQUAL TO;Sm;0;ON;;;;;Y;;;;; 2ACD;SQUARE LEFT OPEN BOX OPERATOR;Sm;0;ON;;;;;Y;;;;; 2ACE;SQUARE RIGHT OPEN BOX OPERATOR;Sm;0;ON;;;;;Y;;;;; 2ACF;CLOSED SUBSET;Sm;0;ON;;;;;Y;;;;; 2AD0;CLOSED SUPERSET;Sm;0;ON;;;;;Y;;;;; 2AD1;CLOSED SUBSET OR EQUAL TO;Sm;0;ON;;;;;Y;;;;; 2AD2;CLOSED SUPERSET OR EQUAL TO;Sm;0;ON;;;;;Y;;;;; 2AD3;SUBSET ABOVE SUPERSET;Sm;0;ON;;;;;Y;;;;; 2AD4;SUPERSET ABOVE SUBSET;Sm;0;ON;;;;;Y;;;;; 2AD5;SUBSET ABOVE SUBSET;Sm;0;ON;;;;;Y;;;;; 2AD6;SUPERSET ABOVE SUPERSET;Sm;0;ON;;;;;Y;;;;; 2AD7;SUPERSET BESIDE SUBSET;Sm;0;ON;;;;;N;;;;; 2AD8;SUPERSET BESIDE AND JOINED BY DASH WITH SUBSET;Sm;0;ON;;;;;N;;;;; 2AD9;ELEMENT OF OPENING DOWNWARDS;Sm;0;ON;;;;;N;;;;; 2ADA;PITCHFORK WITH TEE TOP;Sm;0;ON;;;;;N;;;;; 2ADB;TRANSVERSAL INTERSECTION;Sm;0;ON;;;;;N;;;;; 2ADC;FORKING;Sm;0;ON;2ADD 0338;;;;Y;;;;; 2ADD;NONFORKING;Sm;0;ON;;;;;N;;;;; 2ADE;SHORT LEFT TACK;Sm;0;ON;;;;;Y;;;;; 2ADF;SHORT DOWN TACK;Sm;0;ON;;;;;N;;;;; 2AE0;SHORT UP TACK;Sm;0;ON;;;;;N;;;;; 2AE1;PERPENDICULAR WITH S;Sm;0;ON;;;;;N;;;;; 2AE2;VERTICAL BAR TRIPLE RIGHT TURNSTILE;Sm;0;ON;;;;;Y;;;;; 2AE3;DOUBLE VERTICAL BAR LEFT TURNSTILE;Sm;0;ON;;;;;Y;;;;; 2AE4;VERTICAL BAR DOUBLE LEFT TURNSTILE;Sm;0;ON;;;;;Y;;;;; 2AE5;DOUBLE VERTICAL BAR DOUBLE LEFT TURNSTILE;Sm;0;ON;;;;;Y;;;;; 2AE6;LONG DASH FROM LEFT MEMBER OF DOUBLE VERTICAL;Sm;0;ON;;;;;Y;;;;; 2AE7;SHORT DOWN TACK WITH OVERBAR;Sm;0;ON;;;;;N;;;;; 2AE8;SHORT UP TACK WITH UNDERBAR;Sm;0;ON;;;;;N;;;;; 2AE9;SHORT UP TACK ABOVE SHORT DOWN TACK;Sm;0;ON;;;;;N;;;;; 2AEA;DOUBLE DOWN TACK;Sm;0;ON;;;;;N;;;;; 2AEB;DOUBLE UP TACK;Sm;0;ON;;;;;N;;;;; 2AEC;DOUBLE STROKE NOT SIGN;Sm;0;ON;;;;;Y;;;;; 2AED;REVERSED DOUBLE STROKE NOT SIGN;Sm;0;ON;;;;;Y;;;;; 2AEE;DOES NOT DIVIDE WITH REVERSED NEGATION SLASH;Sm;0;ON;;;;;Y;;;;; 2AEF;VERTICAL LINE WITH CIRCLE ABOVE;Sm;0;ON;;;;;N;;;;; 2AF0;VERTICAL LINE WITH CIRCLE BELOW;Sm;0;ON;;;;;N;;;;; 2AF1;DOWN TACK WITH CIRCLE BELOW;Sm;0;ON;;;;;N;;;;; 2AF2;PARALLEL WITH HORIZONTAL STROKE;Sm;0;ON;;;;;N;;;;; 2AF3;PARALLEL WITH TILDE OPERATOR;Sm;0;ON;;;;;Y;;;;; 2AF4;TRIPLE VERTICAL BAR BINARY RELATION;Sm;0;ON;;;;;N;;;;; 2AF5;TRIPLE VERTICAL BAR WITH HORIZONTAL STROKE;Sm;0;ON;;;;;N;;;;; 2AF6;TRIPLE COLON OPERATOR;Sm;0;ON;;;;;N;;;;; 2AF7;TRIPLE NESTED LESS-THAN;Sm;0;ON;;;;;Y;;;;; 2AF8;TRIPLE NESTED GREATER-THAN;Sm;0;ON;;;;;Y;;;;; 2AF9;DOUBLE-LINE SLANTED LESS-THAN OR EQUAL TO;Sm;0;ON;;;;;Y;;;;; 2AFA;DOUBLE-LINE SLANTED GREATER-THAN OR EQUAL TO;Sm;0;ON;;;;;Y;;;;; 2AFB;TRIPLE SOLIDUS BINARY RELATION;Sm;0;ON;;;;;Y;;;;; 2AFC;LARGE TRIPLE VERTICAL BAR OPERATOR;Sm;0;ON;;;;;N;;;;; 2AFD;DOUBLE SOLIDUS OPERATOR;Sm;0;ON;;;;;Y;;;;; 2AFE;WHITE VERTICAL BAR;Sm;0;ON;;;;;N;;;;; 2AFF;N-ARY WHITE VERTICAL BAR;Sm;0;ON;;;;;N;;;;; 2B00;NORTH EAST WHITE ARROW;So;0;ON;;;;;N;;;;; 2B01;NORTH WEST WHITE ARROW;So;0;ON;;;;;N;;;;; 2B02;SOUTH EAST WHITE ARROW;So;0;ON;;;;;N;;;;; 2B03;SOUTH WEST WHITE ARROW;So;0;ON;;;;;N;;;;; 2B04;LEFT RIGHT WHITE ARROW;So;0;ON;;;;;N;;;;; 2B05;LEFTWARDS BLACK ARROW;So;0;ON;;;;;N;;;;; 2B06;UPWARDS BLACK ARROW;So;0;ON;;;;;N;;;;; 2B07;DOWNWARDS BLACK ARROW;So;0;ON;;;;;N;;;;; 2B08;NORTH EAST BLACK ARROW;So;0;ON;;;;;N;;;;; 2B09;NORTH WEST BLACK ARROW;So;0;ON;;;;;N;;;;; 2B0A;SOUTH EAST BLACK ARROW;So;0;ON;;;;;N;;;;; 2B0B;SOUTH WEST BLACK ARROW;So;0;ON;;;;;N;;;;; 2B0C;LEFT RIGHT BLACK ARROW;So;0;ON;;;;;N;;;;; 2B0D;UP DOWN BLACK ARROW;So;0;ON;;;;;N;;;;; 2B0E;RIGHTWARDS ARROW WITH TIP DOWNWARDS;So;0;ON;;;;;N;;;;; 2B0F;RIGHTWARDS ARROW WITH TIP UPWARDS;So;0;ON;;;;;N;;;;; 2B10;LEFTWARDS ARROW WITH TIP DOWNWARDS;So;0;ON;;;;;N;;;;; 2B11;LEFTWARDS ARROW WITH TIP UPWARDS;So;0;ON;;;;;N;;;;; 2B12;SQUARE WITH TOP HALF BLACK;So;0;ON;;;;;N;;;;; 2B13;SQUARE WITH BOTTOM HALF BLACK;So;0;ON;;;;;N;;;;; 2B14;SQUARE WITH UPPER RIGHT DIAGONAL HALF BLACK;So;0;ON;;;;;N;;;;; 2B15;SQUARE WITH LOWER LEFT DIAGONAL HALF BLACK;So;0;ON;;;;;N;;;;; 2B16;DIAMOND WITH LEFT HALF BLACK;So;0;ON;;;;;N;;;;; 2B17;DIAMOND WITH RIGHT HALF BLACK;So;0;ON;;;;;N;;;;; 2B18;DIAMOND WITH TOP HALF BLACK;So;0;ON;;;;;N;;;;; 2B19;DIAMOND WITH BOTTOM HALF BLACK;So;0;ON;;;;;N;;;;; 2B1A;DOTTED SQUARE;So;0;ON;;;;;N;;;;; 2B1B;BLACK LARGE SQUARE;So;0;ON;;;;;N;;;;; 2B1C;WHITE LARGE SQUARE;So;0;ON;;;;;N;;;;; 2B1D;BLACK VERY SMALL SQUARE;So;0;ON;;;;;N;;;;; 2B1E;WHITE VERY SMALL SQUARE;So;0;ON;;;;;N;;;;; 2B1F;BLACK PENTAGON;So;0;ON;;;;;N;;;;; 2B20;WHITE PENTAGON;So;0;ON;;;;;N;;;;; 2B21;WHITE HEXAGON;So;0;ON;;;;;N;;;;; 2B22;BLACK HEXAGON;So;0;ON;;;;;N;;;;; 2B23;HORIZONTAL BLACK HEXAGON;So;0;ON;;;;;N;;;;; 2B24;BLACK LARGE CIRCLE;So;0;ON;;;;;N;;;;; 2B25;BLACK MEDIUM DIAMOND;So;0;ON;;;;;N;;;;; 2B26;WHITE MEDIUM DIAMOND;So;0;ON;;;;;N;;;;; 2B27;BLACK MEDIUM LOZENGE;So;0;ON;;;;;N;;;;; 2B28;WHITE MEDIUM LOZENGE;So;0;ON;;;;;N;;;;; 2B29;BLACK SMALL DIAMOND;So;0;ON;;;;;N;;;;; 2B2A;BLACK SMALL LOZENGE;So;0;ON;;;;;N;;;;; 2B2B;WHITE SMALL LOZENGE;So;0;ON;;;;;N;;;;; 2B2C;BLACK HORIZONTAL ELLIPSE;So;0;ON;;;;;N;;;;; 2B2D;WHITE HORIZONTAL ELLIPSE;So;0;ON;;;;;N;;;;; 2B2E;BLACK VERTICAL ELLIPSE;So;0;ON;;;;;N;;;;; 2B2F;WHITE VERTICAL ELLIPSE;So;0;ON;;;;;N;;;;; 2B30;LEFT ARROW WITH SMALL CIRCLE;Sm;0;ON;;;;;N;;;;; 2B31;THREE LEFTWARDS ARROWS;Sm;0;ON;;;;;N;;;;; 2B32;LEFT ARROW WITH CIRCLED PLUS;Sm;0;ON;;;;;N;;;;; 2B33;LONG LEFTWARDS SQUIGGLE ARROW;Sm;0;ON;;;;;N;;;;; 2B34;LEFTWARDS TWO-HEADED ARROW WITH VERTICAL STROKE;Sm;0;ON;;;;;N;;;;; 2B35;LEFTWARDS TWO-HEADED ARROW WITH DOUBLE VERTICAL STROKE;Sm;0;ON;;;;;N;;;;; 2B36;LEFTWARDS TWO-HEADED ARROW FROM BAR;Sm;0;ON;;;;;N;;;;; 2B37;LEFTWARDS TWO-HEADED TRIPLE DASH ARROW;Sm;0;ON;;;;;N;;;;; 2B38;LEFTWARDS ARROW WITH DOTTED STEM;Sm;0;ON;;;;;N;;;;; 2B39;LEFTWARDS ARROW WITH TAIL WITH VERTICAL STROKE;Sm;0;ON;;;;;N;;;;; 2B3A;LEFTWARDS ARROW WITH TAIL WITH DOUBLE VERTICAL STROKE;Sm;0;ON;;;;;N;;;;; 2B3B;LEFTWARDS TWO-HEADED ARROW WITH TAIL;Sm;0;ON;;;;;N;;;;; 2B3C;LEFTWARDS TWO-HEADED ARROW WITH TAIL WITH VERTICAL STROKE;Sm;0;ON;;;;;N;;;;; 2B3D;LEFTWARDS TWO-HEADED ARROW WITH TAIL WITH DOUBLE VERTICAL STROKE;Sm;0;ON;;;;;N;;;;; 2B3E;LEFTWARDS ARROW THROUGH X;Sm;0;ON;;;;;N;;;;; 2B3F;WAVE ARROW POINTING DIRECTLY LEFT;Sm;0;ON;;;;;N;;;;; 2B40;EQUALS SIGN ABOVE LEFTWARDS ARROW;Sm;0;ON;;;;;N;;;;; 2B41;REVERSE TILDE OPERATOR ABOVE LEFTWARDS ARROW;Sm;0;ON;;;;;N;;;;; 2B42;LEFTWARDS ARROW ABOVE REVERSE ALMOST EQUAL TO;Sm;0;ON;;;;;N;;;;; 2B43;RIGHTWARDS ARROW THROUGH GREATER-THAN;Sm;0;ON;;;;;N;;;;; 2B44;RIGHTWARDS ARROW THROUGH SUPERSET;Sm;0;ON;;;;;N;;;;; 2B45;LEFTWARDS QUADRUPLE ARROW;So;0;ON;;;;;N;;;;; 2B46;RIGHTWARDS QUADRUPLE ARROW;So;0;ON;;;;;N;;;;; 2B47;REVERSE TILDE OPERATOR ABOVE RIGHTWARDS ARROW;Sm;0;ON;;;;;N;;;;; 2B48;RIGHTWARDS ARROW ABOVE REVERSE ALMOST EQUAL TO;Sm;0;ON;;;;;N;;;;; 2B49;TILDE OPERATOR ABOVE LEFTWARDS ARROW;Sm;0;ON;;;;;N;;;;; 2B4A;LEFTWARDS ARROW ABOVE ALMOST EQUAL TO;Sm;0;ON;;;;;N;;;;; 2B4B;LEFTWARDS ARROW ABOVE REVERSE TILDE OPERATOR;Sm;0;ON;;;;;N;;;;; 2B4C;RIGHTWARDS ARROW ABOVE REVERSE TILDE OPERATOR;Sm;0;ON;;;;;N;;;;; 2B4D;DOWNWARDS TRIANGLE-HEADED ZIGZAG ARROW;So;0;ON;;;;;N;;;;; 2B4E;SHORT SLANTED NORTH ARROW;So;0;ON;;;;;N;;;;; 2B4F;SHORT BACKSLANTED SOUTH ARROW;So;0;ON;;;;;N;;;;; 2B50;WHITE MEDIUM STAR;So;0;ON;;;;;N;;;;; 2B51;BLACK SMALL STAR;So;0;ON;;;;;N;;;;; 2B52;WHITE SMALL STAR;So;0;ON;;;;;N;;;;; 2B53;BLACK RIGHT-POINTING PENTAGON;So;0;ON;;;;;N;;;;; 2B54;WHITE RIGHT-POINTING PENTAGON;So;0;ON;;;;;N;;;;; 2B55;HEAVY LARGE CIRCLE;So;0;ON;;;;;N;;;;; 2B56;HEAVY OVAL WITH OVAL INSIDE;So;0;ON;;;;;N;;;;; 2B57;HEAVY CIRCLE WITH CIRCLE INSIDE;So;0;ON;;;;;N;;;;; 2B58;HEAVY CIRCLE;So;0;ON;;;;;N;;;;; 2B59;HEAVY CIRCLED SALTIRE;So;0;ON;;;;;N;;;;; 2B5A;SLANTED NORTH ARROW WITH HOOKED HEAD;So;0;ON;;;;;N;;;;; 2B5B;BACKSLANTED SOUTH ARROW WITH HOOKED TAIL;So;0;ON;;;;;N;;;;; 2B5C;SLANTED NORTH ARROW WITH HORIZONTAL TAIL;So;0;ON;;;;;N;;;;; 2B5D;BACKSLANTED SOUTH ARROW WITH HORIZONTAL TAIL;So;0;ON;;;;;N;;;;; 2B5E;BENT ARROW POINTING DOWNWARDS THEN NORTH EAST;So;0;ON;;;;;N;;;;; 2B5F;SHORT BENT ARROW POINTING DOWNWARDS THEN NORTH EAST;So;0;ON;;;;;N;;;;; 2B60;LEFTWARDS TRIANGLE-HEADED ARROW;So;0;ON;;;;;N;;;;; 2B61;UPWARDS TRIANGLE-HEADED ARROW;So;0;ON;;;;;N;;;;; 2B62;RIGHTWARDS TRIANGLE-HEADED ARROW;So;0;ON;;;;;N;;;;; 2B63;DOWNWARDS TRIANGLE-HEADED ARROW;So;0;ON;;;;;N;;;;; 2B64;LEFT RIGHT TRIANGLE-HEADED ARROW;So;0;ON;;;;;N;;;;; 2B65;UP DOWN TRIANGLE-HEADED ARROW;So;0;ON;;;;;N;;;;; 2B66;NORTH WEST TRIANGLE-HEADED ARROW;So;0;ON;;;;;N;;;;; 2B67;NORTH EAST TRIANGLE-HEADED ARROW;So;0;ON;;;;;N;;;;; 2B68;SOUTH EAST TRIANGLE-HEADED ARROW;So;0;ON;;;;;N;;;;; 2B69;SOUTH WEST TRIANGLE-HEADED ARROW;So;0;ON;;;;;N;;;;; 2B6A;LEFTWARDS TRIANGLE-HEADED DASHED ARROW;So;0;ON;;;;;N;;;;; 2B6B;UPWARDS TRIANGLE-HEADED DASHED ARROW;So;0;ON;;;;;N;;;;; 2B6C;RIGHTWARDS TRIANGLE-HEADED DASHED ARROW;So;0;ON;;;;;N;;;;; 2B6D;DOWNWARDS TRIANGLE-HEADED DASHED ARROW;So;0;ON;;;;;N;;;;; 2B6E;CLOCKWISE TRIANGLE-HEADED OPEN CIRCLE ARROW;So;0;ON;;;;;N;;;;; 2B6F;ANTICLOCKWISE TRIANGLE-HEADED OPEN CIRCLE ARROW;So;0;ON;;;;;N;;;;; 2B70;LEFTWARDS TRIANGLE-HEADED ARROW TO BAR;So;0;ON;;;;;N;;;;; 2B71;UPWARDS TRIANGLE-HEADED ARROW TO BAR;So;0;ON;;;;;N;;;;; 2B72;RIGHTWARDS TRIANGLE-HEADED ARROW TO BAR;So;0;ON;;;;;N;;;;; 2B73;DOWNWARDS TRIANGLE-HEADED ARROW TO BAR;So;0;ON;;;;;N;;;;; 2B76;NORTH WEST TRIANGLE-HEADED ARROW TO BAR;So;0;ON;;;;;N;;;;; 2B77;NORTH EAST TRIANGLE-HEADED ARROW TO BAR;So;0;ON;;;;;N;;;;; 2B78;SOUTH EAST TRIANGLE-HEADED ARROW TO BAR;So;0;ON;;;;;N;;;;; 2B79;SOUTH WEST TRIANGLE-HEADED ARROW TO BAR;So;0;ON;;;;;N;;;;; 2B7A;LEFTWARDS TRIANGLE-HEADED ARROW WITH DOUBLE HORIZONTAL STROKE;So;0;ON;;;;;N;;;;; 2B7B;UPWARDS TRIANGLE-HEADED ARROW WITH DOUBLE HORIZONTAL STROKE;So;0;ON;;;;;N;;;;; 2B7C;RIGHTWARDS TRIANGLE-HEADED ARROW WITH DOUBLE HORIZONTAL STROKE;So;0;ON;;;;;N;;;;; 2B7D;DOWNWARDS TRIANGLE-HEADED ARROW WITH DOUBLE HORIZONTAL STROKE;So;0;ON;;;;;N;;;;; 2B7E;HORIZONTAL TAB KEY;So;0;ON;;;;;N;;;;; 2B7F;VERTICAL TAB KEY;So;0;ON;;;;;N;;;;; 2B80;LEFTWARDS TRIANGLE-HEADED ARROW OVER RIGHTWARDS TRIANGLE-HEADED ARROW;So;0;ON;;;;;N;;;;; 2B81;UPWARDS TRIANGLE-HEADED ARROW LEFTWARDS OF DOWNWARDS TRIANGLE-HEADED ARROW;So;0;ON;;;;;N;;;;; 2B82;RIGHTWARDS TRIANGLE-HEADED ARROW OVER LEFTWARDS TRIANGLE-HEADED ARROW;So;0;ON;;;;;N;;;;; 2B83;DOWNWARDS TRIANGLE-HEADED ARROW LEFTWARDS OF UPWARDS TRIANGLE-HEADED ARROW;So;0;ON;;;;;N;;;;; 2B84;LEFTWARDS TRIANGLE-HEADED PAIRED ARROWS;So;0;ON;;;;;N;;;;; 2B85;UPWARDS TRIANGLE-HEADED PAIRED ARROWS;So;0;ON;;;;;N;;;;; 2B86;RIGHTWARDS TRIANGLE-HEADED PAIRED ARROWS;So;0;ON;;;;;N;;;;; 2B87;DOWNWARDS TRIANGLE-HEADED PAIRED ARROWS;So;0;ON;;;;;N;;;;; 2B88;LEFTWARDS BLACK CIRCLED WHITE ARROW;So;0;ON;;;;;N;;;;; 2B89;UPWARDS BLACK CIRCLED WHITE ARROW;So;0;ON;;;;;N;;;;; 2B8A;RIGHTWARDS BLACK CIRCLED WHITE ARROW;So;0;ON;;;;;N;;;;; 2B8B;DOWNWARDS BLACK CIRCLED WHITE ARROW;So;0;ON;;;;;N;;;;; 2B8C;ANTICLOCKWISE TRIANGLE-HEADED RIGHT U-SHAPED ARROW;So;0;ON;;;;;N;;;;; 2B8D;ANTICLOCKWISE TRIANGLE-HEADED BOTTOM U-SHAPED ARROW;So;0;ON;;;;;N;;;;; 2B8E;ANTICLOCKWISE TRIANGLE-HEADED LEFT U-SHAPED ARROW;So;0;ON;;;;;N;;;;; 2B8F;ANTICLOCKWISE TRIANGLE-HEADED TOP U-SHAPED ARROW;So;0;ON;;;;;N;;;;; 2B90;RETURN LEFT;So;0;ON;;;;;N;;;;; 2B91;RETURN RIGHT;So;0;ON;;;;;N;;;;; 2B92;NEWLINE LEFT;So;0;ON;;;;;N;;;;; 2B93;NEWLINE RIGHT;So;0;ON;;;;;N;;;;; 2B94;FOUR CORNER ARROWS CIRCLING ANTICLOCKWISE;So;0;ON;;;;;N;;;;; 2B95;RIGHTWARDS BLACK ARROW;So;0;ON;;;;;N;;;;; 2B98;THREE-D TOP-LIGHTED LEFTWARDS EQUILATERAL ARROWHEAD;So;0;ON;;;;;N;;;;; 2B99;THREE-D RIGHT-LIGHTED UPWARDS EQUILATERAL ARROWHEAD;So;0;ON;;;;;N;;;;; 2B9A;THREE-D TOP-LIGHTED RIGHTWARDS EQUILATERAL ARROWHEAD;So;0;ON;;;;;N;;;;; 2B9B;THREE-D LEFT-LIGHTED DOWNWARDS EQUILATERAL ARROWHEAD;So;0;ON;;;;;N;;;;; 2B9C;BLACK LEFTWARDS EQUILATERAL ARROWHEAD;So;0;ON;;;;;N;;;;; 2B9D;BLACK UPWARDS EQUILATERAL ARROWHEAD;So;0;ON;;;;;N;;;;; 2B9E;BLACK RIGHTWARDS EQUILATERAL ARROWHEAD;So;0;ON;;;;;N;;;;; 2B9F;BLACK DOWNWARDS EQUILATERAL ARROWHEAD;So;0;ON;;;;;N;;;;; 2BA0;DOWNWARDS TRIANGLE-HEADED ARROW WITH LONG TIP LEFTWARDS;So;0;ON;;;;;N;;;;; 2BA1;DOWNWARDS TRIANGLE-HEADED ARROW WITH LONG TIP RIGHTWARDS;So;0;ON;;;;;N;;;;; 2BA2;UPWARDS TRIANGLE-HEADED ARROW WITH LONG TIP LEFTWARDS;So;0;ON;;;;;N;;;;; 2BA3;UPWARDS TRIANGLE-HEADED ARROW WITH LONG TIP RIGHTWARDS;So;0;ON;;;;;N;;;;; 2BA4;LEFTWARDS TRIANGLE-HEADED ARROW WITH LONG TIP UPWARDS;So;0;ON;;;;;N;;;;; 2BA5;RIGHTWARDS TRIANGLE-HEADED ARROW WITH LONG TIP UPWARDS;So;0;ON;;;;;N;;;;; 2BA6;LEFTWARDS TRIANGLE-HEADED ARROW WITH LONG TIP DOWNWARDS;So;0;ON;;;;;N;;;;; 2BA7;RIGHTWARDS TRIANGLE-HEADED ARROW WITH LONG TIP DOWNWARDS;So;0;ON;;;;;N;;;;; 2BA8;BLACK CURVED DOWNWARDS AND LEFTWARDS ARROW;So;0;ON;;;;;N;;;;; 2BA9;BLACK CURVED DOWNWARDS AND RIGHTWARDS ARROW;So;0;ON;;;;;N;;;;; 2BAA;BLACK CURVED UPWARDS AND LEFTWARDS ARROW;So;0;ON;;;;;N;;;;; 2BAB;BLACK CURVED UPWARDS AND RIGHTWARDS ARROW;So;0;ON;;;;;N;;;;; 2BAC;BLACK CURVED LEFTWARDS AND UPWARDS ARROW;So;0;ON;;;;;N;;;;; 2BAD;BLACK CURVED RIGHTWARDS AND UPWARDS ARROW;So;0;ON;;;;;N;;;;; 2BAE;BLACK CURVED LEFTWARDS AND DOWNWARDS ARROW;So;0;ON;;;;;N;;;;; 2BAF;BLACK CURVED RIGHTWARDS AND DOWNWARDS ARROW;So;0;ON;;;;;N;;;;; 2BB0;RIBBON ARROW DOWN LEFT;So;0;ON;;;;;N;;;;; 2BB1;RIBBON ARROW DOWN RIGHT;So;0;ON;;;;;N;;;;; 2BB2;RIBBON ARROW UP LEFT;So;0;ON;;;;;N;;;;; 2BB3;RIBBON ARROW UP RIGHT;So;0;ON;;;;;N;;;;; 2BB4;RIBBON ARROW LEFT UP;So;0;ON;;;;;N;;;;; 2BB5;RIBBON ARROW RIGHT UP;So;0;ON;;;;;N;;;;; 2BB6;RIBBON ARROW LEFT DOWN;So;0;ON;;;;;N;;;;; 2BB7;RIBBON ARROW RIGHT DOWN;So;0;ON;;;;;N;;;;; 2BB8;UPWARDS WHITE ARROW FROM BAR WITH HORIZONTAL BAR;So;0;ON;;;;;N;;;;; 2BB9;UP ARROWHEAD IN A RECTANGLE BOX;So;0;ON;;;;;N;;;;; 2BBD;BALLOT BOX WITH LIGHT X;So;0;ON;;;;;N;;;;; 2BBE;CIRCLED X;So;0;ON;;;;;N;;;;; 2BBF;CIRCLED BOLD X;So;0;ON;;;;;N;;;;; 2BC0;BLACK SQUARE CENTRED;So;0;ON;;;;;N;;;;; 2BC1;BLACK DIAMOND CENTRED;So;0;ON;;;;;N;;;;; 2BC2;TURNED BLACK PENTAGON;So;0;ON;;;;;N;;;;; 2BC3;HORIZONTAL BLACK OCTAGON;So;0;ON;;;;;N;;;;; 2BC4;BLACK OCTAGON;So;0;ON;;;;;N;;;;; 2BC5;BLACK MEDIUM UP-POINTING TRIANGLE CENTRED;So;0;ON;;;;;N;;;;; 2BC6;BLACK MEDIUM DOWN-POINTING TRIANGLE CENTRED;So;0;ON;;;;;N;;;;; 2BC7;BLACK MEDIUM LEFT-POINTING TRIANGLE CENTRED;So;0;ON;;;;;N;;;;; 2BC8;BLACK MEDIUM RIGHT-POINTING TRIANGLE CENTRED;So;0;ON;;;;;N;;;;; 2BCA;TOP HALF BLACK CIRCLE;So;0;ON;;;;;N;;;;; 2BCB;BOTTOM HALF BLACK CIRCLE;So;0;ON;;;;;N;;;;; 2BCC;LIGHT FOUR POINTED BLACK CUSP;So;0;ON;;;;;N;;;;; 2BCD;ROTATED LIGHT FOUR POINTED BLACK CUSP;So;0;ON;;;;;N;;;;; 2BCE;WHITE FOUR POINTED CUSP;So;0;ON;;;;;N;;;;; 2BCF;ROTATED WHITE FOUR POINTED CUSP;So;0;ON;;;;;N;;;;; 2BD0;SQUARE POSITION INDICATOR;So;0;ON;;;;;N;;;;; 2BD1;UNCERTAINTY SIGN;So;0;ON;;;;;N;;;;; 2C00;GLAGOLITIC CAPITAL LETTER AZU;Lu;0;L;;;;;N;;;;2C30; 2C01;GLAGOLITIC CAPITAL LETTER BUKY;Lu;0;L;;;;;N;;;;2C31; 2C02;GLAGOLITIC CAPITAL LETTER VEDE;Lu;0;L;;;;;N;;;;2C32; 2C03;GLAGOLITIC CAPITAL LETTER GLAGOLI;Lu;0;L;;;;;N;;;;2C33; 2C04;GLAGOLITIC CAPITAL LETTER DOBRO;Lu;0;L;;;;;N;;;;2C34; 2C05;GLAGOLITIC CAPITAL LETTER YESTU;Lu;0;L;;;;;N;;;;2C35; 2C06;GLAGOLITIC CAPITAL LETTER ZHIVETE;Lu;0;L;;;;;N;;;;2C36; 2C07;GLAGOLITIC CAPITAL LETTER DZELO;Lu;0;L;;;;;N;;;;2C37; 2C08;GLAGOLITIC CAPITAL LETTER ZEMLJA;Lu;0;L;;;;;N;;;;2C38; 2C09;GLAGOLITIC CAPITAL LETTER IZHE;Lu;0;L;;;;;N;;;;2C39; 2C0A;GLAGOLITIC CAPITAL LETTER INITIAL IZHE;Lu;0;L;;;;;N;;;;2C3A; 2C0B;GLAGOLITIC CAPITAL LETTER I;Lu;0;L;;;;;N;;;;2C3B; 2C0C;GLAGOLITIC CAPITAL LETTER DJERVI;Lu;0;L;;;;;N;;;;2C3C; 2C0D;GLAGOLITIC CAPITAL LETTER KAKO;Lu;0;L;;;;;N;;;;2C3D; 2C0E;GLAGOLITIC CAPITAL LETTER LJUDIJE;Lu;0;L;;;;;N;;;;2C3E; 2C0F;GLAGOLITIC CAPITAL LETTER MYSLITE;Lu;0;L;;;;;N;;;;2C3F; 2C10;GLAGOLITIC CAPITAL LETTER NASHI;Lu;0;L;;;;;N;;;;2C40; 2C11;GLAGOLITIC CAPITAL LETTER ONU;Lu;0;L;;;;;N;;;;2C41; 2C12;GLAGOLITIC CAPITAL LETTER POKOJI;Lu;0;L;;;;;N;;;;2C42; 2C13;GLAGOLITIC CAPITAL LETTER RITSI;Lu;0;L;;;;;N;;;;2C43; 2C14;GLAGOLITIC CAPITAL LETTER SLOVO;Lu;0;L;;;;;N;;;;2C44; 2C15;GLAGOLITIC CAPITAL LETTER TVRIDO;Lu;0;L;;;;;N;;;;2C45; 2C16;GLAGOLITIC CAPITAL LETTER UKU;Lu;0;L;;;;;N;;;;2C46; 2C17;GLAGOLITIC CAPITAL LETTER FRITU;Lu;0;L;;;;;N;;;;2C47; 2C18;GLAGOLITIC CAPITAL LETTER HERU;Lu;0;L;;;;;N;;;;2C48; 2C19;GLAGOLITIC CAPITAL LETTER OTU;Lu;0;L;;;;;N;;;;2C49; 2C1A;GLAGOLITIC CAPITAL LETTER PE;Lu;0;L;;;;;N;;;;2C4A; 2C1B;GLAGOLITIC CAPITAL LETTER SHTA;Lu;0;L;;;;;N;;;;2C4B; 2C1C;GLAGOLITIC CAPITAL LETTER TSI;Lu;0;L;;;;;N;;;;2C4C; 2C1D;GLAGOLITIC CAPITAL LETTER CHRIVI;Lu;0;L;;;;;N;;;;2C4D; 2C1E;GLAGOLITIC CAPITAL LETTER SHA;Lu;0;L;;;;;N;;;;2C4E; 2C1F;GLAGOLITIC CAPITAL LETTER YERU;Lu;0;L;;;;;N;;;;2C4F; 2C20;GLAGOLITIC CAPITAL LETTER YERI;Lu;0;L;;;;;N;;;;2C50; 2C21;GLAGOLITIC CAPITAL LETTER YATI;Lu;0;L;;;;;N;;;;2C51; 2C22;GLAGOLITIC CAPITAL LETTER SPIDERY HA;Lu;0;L;;;;;N;;;;2C52; 2C23;GLAGOLITIC CAPITAL LETTER YU;Lu;0;L;;;;;N;;;;2C53; 2C24;GLAGOLITIC CAPITAL LETTER SMALL YUS;Lu;0;L;;;;;N;;;;2C54; 2C25;GLAGOLITIC CAPITAL LETTER SMALL YUS WITH TAIL;Lu;0;L;;;;;N;;;;2C55; 2C26;GLAGOLITIC CAPITAL LETTER YO;Lu;0;L;;;;;N;;;;2C56; 2C27;GLAGOLITIC CAPITAL LETTER IOTATED SMALL YUS;Lu;0;L;;;;;N;;;;2C57; 2C28;GLAGOLITIC CAPITAL LETTER BIG YUS;Lu;0;L;;;;;N;;;;2C58; 2C29;GLAGOLITIC CAPITAL LETTER IOTATED BIG YUS;Lu;0;L;;;;;N;;;;2C59; 2C2A;GLAGOLITIC CAPITAL LETTER FITA;Lu;0;L;;;;;N;;;;2C5A; 2C2B;GLAGOLITIC CAPITAL LETTER IZHITSA;Lu;0;L;;;;;N;;;;2C5B; 2C2C;GLAGOLITIC CAPITAL LETTER SHTAPIC;Lu;0;L;;;;;N;;;;2C5C; 2C2D;GLAGOLITIC CAPITAL LETTER TROKUTASTI A;Lu;0;L;;;;;N;;;;2C5D; 2C2E;GLAGOLITIC CAPITAL LETTER LATINATE MYSLITE;Lu;0;L;;;;;N;;;;2C5E; 2C30;GLAGOLITIC SMALL LETTER AZU;Ll;0;L;;;;;N;;;2C00;;2C00 2C31;GLAGOLITIC SMALL LETTER BUKY;Ll;0;L;;;;;N;;;2C01;;2C01 2C32;GLAGOLITIC SMALL LETTER VEDE;Ll;0;L;;;;;N;;;2C02;;2C02 2C33;GLAGOLITIC SMALL LETTER GLAGOLI;Ll;0;L;;;;;N;;;2C03;;2C03 2C34;GLAGOLITIC SMALL LETTER DOBRO;Ll;0;L;;;;;N;;;2C04;;2C04 2C35;GLAGOLITIC SMALL LETTER YESTU;Ll;0;L;;;;;N;;;2C05;;2C05 2C36;GLAGOLITIC SMALL LETTER ZHIVETE;Ll;0;L;;;;;N;;;2C06;;2C06 2C37;GLAGOLITIC SMALL LETTER DZELO;Ll;0;L;;;;;N;;;2C07;;2C07 2C38;GLAGOLITIC SMALL LETTER ZEMLJA;Ll;0;L;;;;;N;;;2C08;;2C08 2C39;GLAGOLITIC SMALL LETTER IZHE;Ll;0;L;;;;;N;;;2C09;;2C09 2C3A;GLAGOLITIC SMALL LETTER INITIAL IZHE;Ll;0;L;;;;;N;;;2C0A;;2C0A 2C3B;GLAGOLITIC SMALL LETTER I;Ll;0;L;;;;;N;;;2C0B;;2C0B 2C3C;GLAGOLITIC SMALL LETTER DJERVI;Ll;0;L;;;;;N;;;2C0C;;2C0C 2C3D;GLAGOLITIC SMALL LETTER KAKO;Ll;0;L;;;;;N;;;2C0D;;2C0D 2C3E;GLAGOLITIC SMALL LETTER LJUDIJE;Ll;0;L;;;;;N;;;2C0E;;2C0E 2C3F;GLAGOLITIC SMALL LETTER MYSLITE;Ll;0;L;;;;;N;;;2C0F;;2C0F 2C40;GLAGOLITIC SMALL LETTER NASHI;Ll;0;L;;;;;N;;;2C10;;2C10 2C41;GLAGOLITIC SMALL LETTER ONU;Ll;0;L;;;;;N;;;2C11;;2C11 2C42;GLAGOLITIC SMALL LETTER POKOJI;Ll;0;L;;;;;N;;;2C12;;2C12 2C43;GLAGOLITIC SMALL LETTER RITSI;Ll;0;L;;;;;N;;;2C13;;2C13 2C44;GLAGOLITIC SMALL LETTER SLOVO;Ll;0;L;;;;;N;;;2C14;;2C14 2C45;GLAGOLITIC SMALL LETTER TVRIDO;Ll;0;L;;;;;N;;;2C15;;2C15 2C46;GLAGOLITIC SMALL LETTER UKU;Ll;0;L;;;;;N;;;2C16;;2C16 2C47;GLAGOLITIC SMALL LETTER FRITU;Ll;0;L;;;;;N;;;2C17;;2C17 2C48;GLAGOLITIC SMALL LETTER HERU;Ll;0;L;;;;;N;;;2C18;;2C18 2C49;GLAGOLITIC SMALL LETTER OTU;Ll;0;L;;;;;N;;;2C19;;2C19 2C4A;GLAGOLITIC SMALL LETTER PE;Ll;0;L;;;;;N;;;2C1A;;2C1A 2C4B;GLAGOLITIC SMALL LETTER SHTA;Ll;0;L;;;;;N;;;2C1B;;2C1B 2C4C;GLAGOLITIC SMALL LETTER TSI;Ll;0;L;;;;;N;;;2C1C;;2C1C 2C4D;GLAGOLITIC SMALL LETTER CHRIVI;Ll;0;L;;;;;N;;;2C1D;;2C1D 2C4E;GLAGOLITIC SMALL LETTER SHA;Ll;0;L;;;;;N;;;2C1E;;2C1E 2C4F;GLAGOLITIC SMALL LETTER YERU;Ll;0;L;;;;;N;;;2C1F;;2C1F 2C50;GLAGOLITIC SMALL LETTER YERI;Ll;0;L;;;;;N;;;2C20;;2C20 2C51;GLAGOLITIC SMALL LETTER YATI;Ll;0;L;;;;;N;;;2C21;;2C21 2C52;GLAGOLITIC SMALL LETTER SPIDERY HA;Ll;0;L;;;;;N;;;2C22;;2C22 2C53;GLAGOLITIC SMALL LETTER YU;Ll;0;L;;;;;N;;;2C23;;2C23 2C54;GLAGOLITIC SMALL LETTER SMALL YUS;Ll;0;L;;;;;N;;;2C24;;2C24 2C55;GLAGOLITIC SMALL LETTER SMALL YUS WITH TAIL;Ll;0;L;;;;;N;;;2C25;;2C25 2C56;GLAGOLITIC SMALL LETTER YO;Ll;0;L;;;;;N;;;2C26;;2C26 2C57;GLAGOLITIC SMALL LETTER IOTATED SMALL YUS;Ll;0;L;;;;;N;;;2C27;;2C27 2C58;GLAGOLITIC SMALL LETTER BIG YUS;Ll;0;L;;;;;N;;;2C28;;2C28 2C59;GLAGOLITIC SMALL LETTER IOTATED BIG YUS;Ll;0;L;;;;;N;;;2C29;;2C29 2C5A;GLAGOLITIC SMALL LETTER FITA;Ll;0;L;;;;;N;;;2C2A;;2C2A 2C5B;GLAGOLITIC SMALL LETTER IZHITSA;Ll;0;L;;;;;N;;;2C2B;;2C2B 2C5C;GLAGOLITIC SMALL LETTER SHTAPIC;Ll;0;L;;;;;N;;;2C2C;;2C2C 2C5D;GLAGOLITIC SMALL LETTER TROKUTASTI A;Ll;0;L;;;;;N;;;2C2D;;2C2D 2C5E;GLAGOLITIC SMALL LETTER LATINATE MYSLITE;Ll;0;L;;;;;N;;;2C2E;;2C2E 2C60;LATIN CAPITAL LETTER L WITH DOUBLE BAR;Lu;0;L;;;;;N;;;;2C61; 2C61;LATIN SMALL LETTER L WITH DOUBLE BAR;Ll;0;L;;;;;N;;;2C60;;2C60 2C62;LATIN CAPITAL LETTER L WITH MIDDLE TILDE;Lu;0;L;;;;;N;;;;026B; 2C63;LATIN CAPITAL LETTER P WITH STROKE;Lu;0;L;;;;;N;;;;1D7D; 2C64;LATIN CAPITAL LETTER R WITH TAIL;Lu;0;L;;;;;N;;;;027D; 2C65;LATIN SMALL LETTER A WITH STROKE;Ll;0;L;;;;;N;;;023A;;023A 2C66;LATIN SMALL LETTER T WITH DIAGONAL STROKE;Ll;0;L;;;;;N;;;023E;;023E 2C67;LATIN CAPITAL LETTER H WITH DESCENDER;Lu;0;L;;;;;N;;;;2C68; 2C68;LATIN SMALL LETTER H WITH DESCENDER;Ll;0;L;;;;;N;;;2C67;;2C67 2C69;LATIN CAPITAL LETTER K WITH DESCENDER;Lu;0;L;;;;;N;;;;2C6A; 2C6A;LATIN SMALL LETTER K WITH DESCENDER;Ll;0;L;;;;;N;;;2C69;;2C69 2C6B;LATIN CAPITAL LETTER Z WITH DESCENDER;Lu;0;L;;;;;N;;;;2C6C; 2C6C;LATIN SMALL LETTER Z WITH DESCENDER;Ll;0;L;;;;;N;;;2C6B;;2C6B 2C6D;LATIN CAPITAL LETTER ALPHA;Lu;0;L;;;;;N;;;;0251; 2C6E;LATIN CAPITAL LETTER M WITH HOOK;Lu;0;L;;;;;N;;;;0271; 2C6F;LATIN CAPITAL LETTER TURNED A;Lu;0;L;;;;;N;;;;0250; 2C70;LATIN CAPITAL LETTER TURNED ALPHA;Lu;0;L;;;;;N;;;;0252; 2C71;LATIN SMALL LETTER V WITH RIGHT HOOK;Ll;0;L;;;;;N;;;;; 2C72;LATIN CAPITAL LETTER W WITH HOOK;Lu;0;L;;;;;N;;;;2C73; 2C73;LATIN SMALL LETTER W WITH HOOK;Ll;0;L;;;;;N;;;2C72;;2C72 2C74;LATIN SMALL LETTER V WITH CURL;Ll;0;L;;;;;N;;;;; 2C75;LATIN CAPITAL LETTER HALF H;Lu;0;L;;;;;N;;;;2C76; 2C76;LATIN SMALL LETTER HALF H;Ll;0;L;;;;;N;;;2C75;;2C75 2C77;LATIN SMALL LETTER TAILLESS PHI;Ll;0;L;;;;;N;;;;; 2C78;LATIN SMALL LETTER E WITH NOTCH;Ll;0;L;;;;;N;;;;; 2C79;LATIN SMALL LETTER TURNED R WITH TAIL;Ll;0;L;;;;;N;;;;; 2C7A;LATIN SMALL LETTER O WITH LOW RING INSIDE;Ll;0;L;;;;;N;;;;; 2C7B;LATIN LETTER SMALL CAPITAL TURNED E;Ll;0;L;;;;;N;;;;; 2C7C;LATIN SUBSCRIPT SMALL LETTER J;Lm;0;L; 006A;;;;N;;;;; 2C7D;MODIFIER LETTER CAPITAL V;Lm;0;L; 0056;;;;N;;;;; 2C7E;LATIN CAPITAL LETTER S WITH SWASH TAIL;Lu;0;L;;;;;N;;;;023F; 2C7F;LATIN CAPITAL LETTER Z WITH SWASH TAIL;Lu;0;L;;;;;N;;;;0240; 2C80;COPTIC CAPITAL LETTER ALFA;Lu;0;L;;;;;N;;;;2C81; 2C81;COPTIC SMALL LETTER ALFA;Ll;0;L;;;;;N;;;2C80;;2C80 2C82;COPTIC CAPITAL LETTER VIDA;Lu;0;L;;;;;N;;;;2C83; 2C83;COPTIC SMALL LETTER VIDA;Ll;0;L;;;;;N;;;2C82;;2C82 2C84;COPTIC CAPITAL LETTER GAMMA;Lu;0;L;;;;;N;;;;2C85; 2C85;COPTIC SMALL LETTER GAMMA;Ll;0;L;;;;;N;;;2C84;;2C84 2C86;COPTIC CAPITAL LETTER DALDA;Lu;0;L;;;;;N;;;;2C87; 2C87;COPTIC SMALL LETTER DALDA;Ll;0;L;;;;;N;;;2C86;;2C86 2C88;COPTIC CAPITAL LETTER EIE;Lu;0;L;;;;;N;;;;2C89; 2C89;COPTIC SMALL LETTER EIE;Ll;0;L;;;;;N;;;2C88;;2C88 2C8A;COPTIC CAPITAL LETTER SOU;Lu;0;L;;;;;N;;;;2C8B; 2C8B;COPTIC SMALL LETTER SOU;Ll;0;L;;;;;N;;;2C8A;;2C8A 2C8C;COPTIC CAPITAL LETTER ZATA;Lu;0;L;;;;;N;;;;2C8D; 2C8D;COPTIC SMALL LETTER ZATA;Ll;0;L;;;;;N;;;2C8C;;2C8C 2C8E;COPTIC CAPITAL LETTER HATE;Lu;0;L;;;;;N;;;;2C8F; 2C8F;COPTIC SMALL LETTER HATE;Ll;0;L;;;;;N;;;2C8E;;2C8E 2C90;COPTIC CAPITAL LETTER THETHE;Lu;0;L;;;;;N;;;;2C91; 2C91;COPTIC SMALL LETTER THETHE;Ll;0;L;;;;;N;;;2C90;;2C90 2C92;COPTIC CAPITAL LETTER IAUDA;Lu;0;L;;;;;N;;;;2C93; 2C93;COPTIC SMALL LETTER IAUDA;Ll;0;L;;;;;N;;;2C92;;2C92 2C94;COPTIC CAPITAL LETTER KAPA;Lu;0;L;;;;;N;;;;2C95; 2C95;COPTIC SMALL LETTER KAPA;Ll;0;L;;;;;N;;;2C94;;2C94 2C96;COPTIC CAPITAL LETTER LAULA;Lu;0;L;;;;;N;;;;2C97; 2C97;COPTIC SMALL LETTER LAULA;Ll;0;L;;;;;N;;;2C96;;2C96 2C98;COPTIC CAPITAL LETTER MI;Lu;0;L;;;;;N;;;;2C99; 2C99;COPTIC SMALL LETTER MI;Ll;0;L;;;;;N;;;2C98;;2C98 2C9A;COPTIC CAPITAL LETTER NI;Lu;0;L;;;;;N;;;;2C9B; 2C9B;COPTIC SMALL LETTER NI;Ll;0;L;;;;;N;;;2C9A;;2C9A 2C9C;COPTIC CAPITAL LETTER KSI;Lu;0;L;;;;;N;;;;2C9D; 2C9D;COPTIC SMALL LETTER KSI;Ll;0;L;;;;;N;;;2C9C;;2C9C 2C9E;COPTIC CAPITAL LETTER O;Lu;0;L;;;;;N;;;;2C9F; 2C9F;COPTIC SMALL LETTER O;Ll;0;L;;;;;N;;;2C9E;;2C9E 2CA0;COPTIC CAPITAL LETTER PI;Lu;0;L;;;;;N;;;;2CA1; 2CA1;COPTIC SMALL LETTER PI;Ll;0;L;;;;;N;;;2CA0;;2CA0 2CA2;COPTIC CAPITAL LETTER RO;Lu;0;L;;;;;N;;;;2CA3; 2CA3;COPTIC SMALL LETTER RO;Ll;0;L;;;;;N;;;2CA2;;2CA2 2CA4;COPTIC CAPITAL LETTER SIMA;Lu;0;L;;;;;N;;;;2CA5; 2CA5;COPTIC SMALL LETTER SIMA;Ll;0;L;;;;;N;;;2CA4;;2CA4 2CA6;COPTIC CAPITAL LETTER TAU;Lu;0;L;;;;;N;;;;2CA7; 2CA7;COPTIC SMALL LETTER TAU;Ll;0;L;;;;;N;;;2CA6;;2CA6 2CA8;COPTIC CAPITAL LETTER UA;Lu;0;L;;;;;N;;;;2CA9; 2CA9;COPTIC SMALL LETTER UA;Ll;0;L;;;;;N;;;2CA8;;2CA8 2CAA;COPTIC CAPITAL LETTER FI;Lu;0;L;;;;;N;;;;2CAB; 2CAB;COPTIC SMALL LETTER FI;Ll;0;L;;;;;N;;;2CAA;;2CAA 2CAC;COPTIC CAPITAL LETTER KHI;Lu;0;L;;;;;N;;;;2CAD; 2CAD;COPTIC SMALL LETTER KHI;Ll;0;L;;;;;N;;;2CAC;;2CAC 2CAE;COPTIC CAPITAL LETTER PSI;Lu;0;L;;;;;N;;;;2CAF; 2CAF;COPTIC SMALL LETTER PSI;Ll;0;L;;;;;N;;;2CAE;;2CAE 2CB0;COPTIC CAPITAL LETTER OOU;Lu;0;L;;;;;N;;;;2CB1; 2CB1;COPTIC SMALL LETTER OOU;Ll;0;L;;;;;N;;;2CB0;;2CB0 2CB2;COPTIC CAPITAL LETTER DIALECT-P ALEF;Lu;0;L;;;;;N;;;;2CB3; 2CB3;COPTIC SMALL LETTER DIALECT-P ALEF;Ll;0;L;;;;;N;;;2CB2;;2CB2 2CB4;COPTIC CAPITAL LETTER OLD COPTIC AIN;Lu;0;L;;;;;N;;;;2CB5; 2CB5;COPTIC SMALL LETTER OLD COPTIC AIN;Ll;0;L;;;;;N;;;2CB4;;2CB4 2CB6;COPTIC CAPITAL LETTER CRYPTOGRAMMIC EIE;Lu;0;L;;;;;N;;;;2CB7; 2CB7;COPTIC SMALL LETTER CRYPTOGRAMMIC EIE;Ll;0;L;;;;;N;;;2CB6;;2CB6 2CB8;COPTIC CAPITAL LETTER DIALECT-P KAPA;Lu;0;L;;;;;N;;;;2CB9; 2CB9;COPTIC SMALL LETTER DIALECT-P KAPA;Ll;0;L;;;;;N;;;2CB8;;2CB8 2CBA;COPTIC CAPITAL LETTER DIALECT-P NI;Lu;0;L;;;;;N;;;;2CBB; 2CBB;COPTIC SMALL LETTER DIALECT-P NI;Ll;0;L;;;;;N;;;2CBA;;2CBA 2CBC;COPTIC CAPITAL LETTER CRYPTOGRAMMIC NI;Lu;0;L;;;;;N;;;;2CBD; 2CBD;COPTIC SMALL LETTER CRYPTOGRAMMIC NI;Ll;0;L;;;;;N;;;2CBC;;2CBC 2CBE;COPTIC CAPITAL LETTER OLD COPTIC OOU;Lu;0;L;;;;;N;;;;2CBF; 2CBF;COPTIC SMALL LETTER OLD COPTIC OOU;Ll;0;L;;;;;N;;;2CBE;;2CBE 2CC0;COPTIC CAPITAL LETTER SAMPI;Lu;0;L;;;;;N;;;;2CC1; 2CC1;COPTIC SMALL LETTER SAMPI;Ll;0;L;;;;;N;;;2CC0;;2CC0 2CC2;COPTIC CAPITAL LETTER CROSSED SHEI;Lu;0;L;;;;;N;;;;2CC3; 2CC3;COPTIC SMALL LETTER CROSSED SHEI;Ll;0;L;;;;;N;;;2CC2;;2CC2 2CC4;COPTIC CAPITAL LETTER OLD COPTIC SHEI;Lu;0;L;;;;;N;;;;2CC5; 2CC5;COPTIC SMALL LETTER OLD COPTIC SHEI;Ll;0;L;;;;;N;;;2CC4;;2CC4 2CC6;COPTIC CAPITAL LETTER OLD COPTIC ESH;Lu;0;L;;;;;N;;;;2CC7; 2CC7;COPTIC SMALL LETTER OLD COPTIC ESH;Ll;0;L;;;;;N;;;2CC6;;2CC6 2CC8;COPTIC CAPITAL LETTER AKHMIMIC KHEI;Lu;0;L;;;;;N;;;;2CC9; 2CC9;COPTIC SMALL LETTER AKHMIMIC KHEI;Ll;0;L;;;;;N;;;2CC8;;2CC8 2CCA;COPTIC CAPITAL LETTER DIALECT-P HORI;Lu;0;L;;;;;N;;;;2CCB; 2CCB;COPTIC SMALL LETTER DIALECT-P HORI;Ll;0;L;;;;;N;;;2CCA;;2CCA 2CCC;COPTIC CAPITAL LETTER OLD COPTIC HORI;Lu;0;L;;;;;N;;;;2CCD; 2CCD;COPTIC SMALL LETTER OLD COPTIC HORI;Ll;0;L;;;;;N;;;2CCC;;2CCC 2CCE;COPTIC CAPITAL LETTER OLD COPTIC HA;Lu;0;L;;;;;N;;;;2CCF; 2CCF;COPTIC SMALL LETTER OLD COPTIC HA;Ll;0;L;;;;;N;;;2CCE;;2CCE 2CD0;COPTIC CAPITAL LETTER L-SHAPED HA;Lu;0;L;;;;;N;;;;2CD1; 2CD1;COPTIC SMALL LETTER L-SHAPED HA;Ll;0;L;;;;;N;;;2CD0;;2CD0 2CD2;COPTIC CAPITAL LETTER OLD COPTIC HEI;Lu;0;L;;;;;N;;;;2CD3; 2CD3;COPTIC SMALL LETTER OLD COPTIC HEI;Ll;0;L;;;;;N;;;2CD2;;2CD2 2CD4;COPTIC CAPITAL LETTER OLD COPTIC HAT;Lu;0;L;;;;;N;;;;2CD5; 2CD5;COPTIC SMALL LETTER OLD COPTIC HAT;Ll;0;L;;;;;N;;;2CD4;;2CD4 2CD6;COPTIC CAPITAL LETTER OLD COPTIC GANGIA;Lu;0;L;;;;;N;;;;2CD7; 2CD7;COPTIC SMALL LETTER OLD COPTIC GANGIA;Ll;0;L;;;;;N;;;2CD6;;2CD6 2CD8;COPTIC CAPITAL LETTER OLD COPTIC DJA;Lu;0;L;;;;;N;;;;2CD9; 2CD9;COPTIC SMALL LETTER OLD COPTIC DJA;Ll;0;L;;;;;N;;;2CD8;;2CD8 2CDA;COPTIC CAPITAL LETTER OLD COPTIC SHIMA;Lu;0;L;;;;;N;;;;2CDB; 2CDB;COPTIC SMALL LETTER OLD COPTIC SHIMA;Ll;0;L;;;;;N;;;2CDA;;2CDA 2CDC;COPTIC CAPITAL LETTER OLD NUBIAN SHIMA;Lu;0;L;;;;;N;;;;2CDD; 2CDD;COPTIC SMALL LETTER OLD NUBIAN SHIMA;Ll;0;L;;;;;N;;;2CDC;;2CDC 2CDE;COPTIC CAPITAL LETTER OLD NUBIAN NGI;Lu;0;L;;;;;N;;;;2CDF; 2CDF;COPTIC SMALL LETTER OLD NUBIAN NGI;Ll;0;L;;;;;N;;;2CDE;;2CDE 2CE0;COPTIC CAPITAL LETTER OLD NUBIAN NYI;Lu;0;L;;;;;N;;;;2CE1; 2CE1;COPTIC SMALL LETTER OLD NUBIAN NYI;Ll;0;L;;;;;N;;;2CE0;;2CE0 2CE2;COPTIC CAPITAL LETTER OLD NUBIAN WAU;Lu;0;L;;;;;N;;;;2CE3; 2CE3;COPTIC SMALL LETTER OLD NUBIAN WAU;Ll;0;L;;;;;N;;;2CE2;;2CE2 2CE4;COPTIC SYMBOL KAI;Ll;0;L;;;;;N;;;;; 2CE5;COPTIC SYMBOL MI RO;So;0;ON;;;;;N;;;;; 2CE6;COPTIC SYMBOL PI RO;So;0;ON;;;;;N;;;;; 2CE7;COPTIC SYMBOL STAUROS;So;0;ON;;;;;N;;;;; 2CE8;COPTIC SYMBOL TAU RO;So;0;ON;;;;;N;;;;; 2CE9;COPTIC SYMBOL KHI RO;So;0;ON;;;;;N;;;;; 2CEA;COPTIC SYMBOL SHIMA SIMA;So;0;ON;;;;;N;;;;; 2CEB;COPTIC CAPITAL LETTER CRYPTOGRAMMIC SHEI;Lu;0;L;;;;;N;;;;2CEC; 2CEC;COPTIC SMALL LETTER CRYPTOGRAMMIC SHEI;Ll;0;L;;;;;N;;;2CEB;;2CEB 2CED;COPTIC CAPITAL LETTER CRYPTOGRAMMIC GANGIA;Lu;0;L;;;;;N;;;;2CEE; 2CEE;COPTIC SMALL LETTER CRYPTOGRAMMIC GANGIA;Ll;0;L;;;;;N;;;2CED;;2CED 2CEF;COPTIC COMBINING NI ABOVE;Mn;230;NSM;;;;;N;;;;; 2CF0;COPTIC COMBINING SPIRITUS ASPER;Mn;230;NSM;;;;;N;;;;; 2CF1;COPTIC COMBINING SPIRITUS LENIS;Mn;230;NSM;;;;;N;;;;; 2CF2;COPTIC CAPITAL LETTER BOHAIRIC KHEI;Lu;0;L;;;;;N;;;;2CF3; 2CF3;COPTIC SMALL LETTER BOHAIRIC KHEI;Ll;0;L;;;;;N;;;2CF2;;2CF2 2CF9;COPTIC OLD NUBIAN FULL STOP;Po;0;ON;;;;;N;;;;; 2CFA;COPTIC OLD NUBIAN DIRECT QUESTION MARK;Po;0;ON;;;;;N;;;;; 2CFB;COPTIC OLD NUBIAN INDIRECT QUESTION MARK;Po;0;ON;;;;;N;;;;; 2CFC;COPTIC OLD NUBIAN VERSE DIVIDER;Po;0;ON;;;;;N;;;;; 2CFD;COPTIC FRACTION ONE HALF;No;0;ON;;;;1/2;N;;;;; 2CFE;COPTIC FULL STOP;Po;0;ON;;;;;N;;;;; 2CFF;COPTIC MORPHOLOGICAL DIVIDER;Po;0;ON;;;;;N;;;;; 2D00;GEORGIAN SMALL LETTER AN;Ll;0;L;;;;;N;;;10A0;;10A0 2D01;GEORGIAN SMALL LETTER BAN;Ll;0;L;;;;;N;;;10A1;;10A1 2D02;GEORGIAN SMALL LETTER GAN;Ll;0;L;;;;;N;;;10A2;;10A2 2D03;GEORGIAN SMALL LETTER DON;Ll;0;L;;;;;N;;;10A3;;10A3 2D04;GEORGIAN SMALL LETTER EN;Ll;0;L;;;;;N;;;10A4;;10A4 2D05;GEORGIAN SMALL LETTER VIN;Ll;0;L;;;;;N;;;10A5;;10A5 2D06;GEORGIAN SMALL LETTER ZEN;Ll;0;L;;;;;N;;;10A6;;10A6 2D07;GEORGIAN SMALL LETTER TAN;Ll;0;L;;;;;N;;;10A7;;10A7 2D08;GEORGIAN SMALL LETTER IN;Ll;0;L;;;;;N;;;10A8;;10A8 2D09;GEORGIAN SMALL LETTER KAN;Ll;0;L;;;;;N;;;10A9;;10A9 2D0A;GEORGIAN SMALL LETTER LAS;Ll;0;L;;;;;N;;;10AA;;10AA 2D0B;GEORGIAN SMALL LETTER MAN;Ll;0;L;;;;;N;;;10AB;;10AB 2D0C;GEORGIAN SMALL LETTER NAR;Ll;0;L;;;;;N;;;10AC;;10AC 2D0D;GEORGIAN SMALL LETTER ON;Ll;0;L;;;;;N;;;10AD;;10AD 2D0E;GEORGIAN SMALL LETTER PAR;Ll;0;L;;;;;N;;;10AE;;10AE 2D0F;GEORGIAN SMALL LETTER ZHAR;Ll;0;L;;;;;N;;;10AF;;10AF 2D10;GEORGIAN SMALL LETTER RAE;Ll;0;L;;;;;N;;;10B0;;10B0 2D11;GEORGIAN SMALL LETTER SAN;Ll;0;L;;;;;N;;;10B1;;10B1 2D12;GEORGIAN SMALL LETTER TAR;Ll;0;L;;;;;N;;;10B2;;10B2 2D13;GEORGIAN SMALL LETTER UN;Ll;0;L;;;;;N;;;10B3;;10B3 2D14;GEORGIAN SMALL LETTER PHAR;Ll;0;L;;;;;N;;;10B4;;10B4 2D15;GEORGIAN SMALL LETTER KHAR;Ll;0;L;;;;;N;;;10B5;;10B5 2D16;GEORGIAN SMALL LETTER GHAN;Ll;0;L;;;;;N;;;10B6;;10B6 2D17;GEORGIAN SMALL LETTER QAR;Ll;0;L;;;;;N;;;10B7;;10B7 2D18;GEORGIAN SMALL LETTER SHIN;Ll;0;L;;;;;N;;;10B8;;10B8 2D19;GEORGIAN SMALL LETTER CHIN;Ll;0;L;;;;;N;;;10B9;;10B9 2D1A;GEORGIAN SMALL LETTER CAN;Ll;0;L;;;;;N;;;10BA;;10BA 2D1B;GEORGIAN SMALL LETTER JIL;Ll;0;L;;;;;N;;;10BB;;10BB 2D1C;GEORGIAN SMALL LETTER CIL;Ll;0;L;;;;;N;;;10BC;;10BC 2D1D;GEORGIAN SMALL LETTER CHAR;Ll;0;L;;;;;N;;;10BD;;10BD 2D1E;GEORGIAN SMALL LETTER XAN;Ll;0;L;;;;;N;;;10BE;;10BE 2D1F;GEORGIAN SMALL LETTER JHAN;Ll;0;L;;;;;N;;;10BF;;10BF 2D20;GEORGIAN SMALL LETTER HAE;Ll;0;L;;;;;N;;;10C0;;10C0 2D21;GEORGIAN SMALL LETTER HE;Ll;0;L;;;;;N;;;10C1;;10C1 2D22;GEORGIAN SMALL LETTER HIE;Ll;0;L;;;;;N;;;10C2;;10C2 2D23;GEORGIAN SMALL LETTER WE;Ll;0;L;;;;;N;;;10C3;;10C3 2D24;GEORGIAN SMALL LETTER HAR;Ll;0;L;;;;;N;;;10C4;;10C4 2D25;GEORGIAN SMALL LETTER HOE;Ll;0;L;;;;;N;;;10C5;;10C5 2D27;GEORGIAN SMALL LETTER YN;Ll;0;L;;;;;N;;;10C7;;10C7 2D2D;GEORGIAN SMALL LETTER AEN;Ll;0;L;;;;;N;;;10CD;;10CD 2D30;TIFINAGH LETTER YA;Lo;0;L;;;;;N;;;;; 2D31;TIFINAGH LETTER YAB;Lo;0;L;;;;;N;;;;; 2D32;TIFINAGH LETTER YABH;Lo;0;L;;;;;N;;;;; 2D33;TIFINAGH LETTER YAG;Lo;0;L;;;;;N;;;;; 2D34;TIFINAGH LETTER YAGHH;Lo;0;L;;;;;N;;;;; 2D35;TIFINAGH LETTER BERBER ACADEMY YAJ;Lo;0;L;;;;;N;;;;; 2D36;TIFINAGH LETTER YAJ;Lo;0;L;;;;;N;;;;; 2D37;TIFINAGH LETTER YAD;Lo;0;L;;;;;N;;;;; 2D38;TIFINAGH LETTER YADH;Lo;0;L;;;;;N;;;;; 2D39;TIFINAGH LETTER YADD;Lo;0;L;;;;;N;;;;; 2D3A;TIFINAGH LETTER YADDH;Lo;0;L;;;;;N;;;;; 2D3B;TIFINAGH LETTER YEY;Lo;0;L;;;;;N;;;;; 2D3C;TIFINAGH LETTER YAF;Lo;0;L;;;;;N;;;;; 2D3D;TIFINAGH LETTER YAK;Lo;0;L;;;;;N;;;;; 2D3E;TIFINAGH LETTER TUAREG YAK;Lo;0;L;;;;;N;;;;; 2D3F;TIFINAGH LETTER YAKHH;Lo;0;L;;;;;N;;;;; 2D40;TIFINAGH LETTER YAH;Lo;0;L;;;;;N;;;;; 2D41;TIFINAGH LETTER BERBER ACADEMY YAH;Lo;0;L;;;;;N;;;;; 2D42;TIFINAGH LETTER TUAREG YAH;Lo;0;L;;;;;N;;;;; 2D43;TIFINAGH LETTER YAHH;Lo;0;L;;;;;N;;;;; 2D44;TIFINAGH LETTER YAA;Lo;0;L;;;;;N;;;;; 2D45;TIFINAGH LETTER YAKH;Lo;0;L;;;;;N;;;;; 2D46;TIFINAGH LETTER TUAREG YAKH;Lo;0;L;;;;;N;;;;; 2D47;TIFINAGH LETTER YAQ;Lo;0;L;;;;;N;;;;; 2D48;TIFINAGH LETTER TUAREG YAQ;Lo;0;L;;;;;N;;;;; 2D49;TIFINAGH LETTER YI;Lo;0;L;;;;;N;;;;; 2D4A;TIFINAGH LETTER YAZH;Lo;0;L;;;;;N;;;;; 2D4B;TIFINAGH LETTER AHAGGAR YAZH;Lo;0;L;;;;;N;;;;; 2D4C;TIFINAGH LETTER TUAREG YAZH;Lo;0;L;;;;;N;;;;; 2D4D;TIFINAGH LETTER YAL;Lo;0;L;;;;;N;;;;; 2D4E;TIFINAGH LETTER YAM;Lo;0;L;;;;;N;;;;; 2D4F;TIFINAGH LETTER YAN;Lo;0;L;;;;;N;;;;; 2D50;TIFINAGH LETTER TUAREG YAGN;Lo;0;L;;;;;N;;;;; 2D51;TIFINAGH LETTER TUAREG YANG;Lo;0;L;;;;;N;;;;; 2D52;TIFINAGH LETTER YAP;Lo;0;L;;;;;N;;;;; 2D53;TIFINAGH LETTER YU;Lo;0;L;;;;;N;;;;; 2D54;TIFINAGH LETTER YAR;Lo;0;L;;;;;N;;;;; 2D55;TIFINAGH LETTER YARR;Lo;0;L;;;;;N;;;;; 2D56;TIFINAGH LETTER YAGH;Lo;0;L;;;;;N;;;;; 2D57;TIFINAGH LETTER TUAREG YAGH;Lo;0;L;;;;;N;;;;; 2D58;TIFINAGH LETTER AYER YAGH;Lo;0;L;;;;;N;;;;; 2D59;TIFINAGH LETTER YAS;Lo;0;L;;;;;N;;;;; 2D5A;TIFINAGH LETTER YASS;Lo;0;L;;;;;N;;;;; 2D5B;TIFINAGH LETTER YASH;Lo;0;L;;;;;N;;;;; 2D5C;TIFINAGH LETTER YAT;Lo;0;L;;;;;N;;;;; 2D5D;TIFINAGH LETTER YATH;Lo;0;L;;;;;N;;;;; 2D5E;TIFINAGH LETTER YACH;Lo;0;L;;;;;N;;;;; 2D5F;TIFINAGH LETTER YATT;Lo;0;L;;;;;N;;;;; 2D60;TIFINAGH LETTER YAV;Lo;0;L;;;;;N;;;;; 2D61;TIFINAGH LETTER YAW;Lo;0;L;;;;;N;;;;; 2D62;TIFINAGH LETTER YAY;Lo;0;L;;;;;N;;;;; 2D63;TIFINAGH LETTER YAZ;Lo;0;L;;;;;N;;;;; 2D64;TIFINAGH LETTER TAWELLEMET YAZ;Lo;0;L;;;;;N;;;;; 2D65;TIFINAGH LETTER YAZZ;Lo;0;L;;;;;N;;;;; 2D66;TIFINAGH LETTER YE;Lo;0;L;;;;;N;;;;; 2D67;TIFINAGH LETTER YO;Lo;0;L;;;;;N;;;;; 2D6F;TIFINAGH MODIFIER LETTER LABIALIZATION MARK;Lm;0;L; 2D61;;;;N;;;;; 2D70;TIFINAGH SEPARATOR MARK;Po;0;L;;;;;N;;;;; 2D7F;TIFINAGH CONSONANT JOINER;Mn;9;NSM;;;;;N;;;;; 2D80;ETHIOPIC SYLLABLE LOA;Lo;0;L;;;;;N;;;;; 2D81;ETHIOPIC SYLLABLE MOA;Lo;0;L;;;;;N;;;;; 2D82;ETHIOPIC SYLLABLE ROA;Lo;0;L;;;;;N;;;;; 2D83;ETHIOPIC SYLLABLE SOA;Lo;0;L;;;;;N;;;;; 2D84;ETHIOPIC SYLLABLE SHOA;Lo;0;L;;;;;N;;;;; 2D85;ETHIOPIC SYLLABLE BOA;Lo;0;L;;;;;N;;;;; 2D86;ETHIOPIC SYLLABLE TOA;Lo;0;L;;;;;N;;;;; 2D87;ETHIOPIC SYLLABLE COA;Lo;0;L;;;;;N;;;;; 2D88;ETHIOPIC SYLLABLE NOA;Lo;0;L;;;;;N;;;;; 2D89;ETHIOPIC SYLLABLE NYOA;Lo;0;L;;;;;N;;;;; 2D8A;ETHIOPIC SYLLABLE GLOTTAL OA;Lo;0;L;;;;;N;;;;; 2D8B;ETHIOPIC SYLLABLE ZOA;Lo;0;L;;;;;N;;;;; 2D8C;ETHIOPIC SYLLABLE DOA;Lo;0;L;;;;;N;;;;; 2D8D;ETHIOPIC SYLLABLE DDOA;Lo;0;L;;;;;N;;;;; 2D8E;ETHIOPIC SYLLABLE JOA;Lo;0;L;;;;;N;;;;; 2D8F;ETHIOPIC SYLLABLE THOA;Lo;0;L;;;;;N;;;;; 2D90;ETHIOPIC SYLLABLE CHOA;Lo;0;L;;;;;N;;;;; 2D91;ETHIOPIC SYLLABLE PHOA;Lo;0;L;;;;;N;;;;; 2D92;ETHIOPIC SYLLABLE POA;Lo;0;L;;;;;N;;;;; 2D93;ETHIOPIC SYLLABLE GGWA;Lo;0;L;;;;;N;;;;; 2D94;ETHIOPIC SYLLABLE GGWI;Lo;0;L;;;;;N;;;;; 2D95;ETHIOPIC SYLLABLE GGWEE;Lo;0;L;;;;;N;;;;; 2D96;ETHIOPIC SYLLABLE GGWE;Lo;0;L;;;;;N;;;;; 2DA0;ETHIOPIC SYLLABLE SSA;Lo;0;L;;;;;N;;;;; 2DA1;ETHIOPIC SYLLABLE SSU;Lo;0;L;;;;;N;;;;; 2DA2;ETHIOPIC SYLLABLE SSI;Lo;0;L;;;;;N;;;;; 2DA3;ETHIOPIC SYLLABLE SSAA;Lo;0;L;;;;;N;;;;; 2DA4;ETHIOPIC SYLLABLE SSEE;Lo;0;L;;;;;N;;;;; 2DA5;ETHIOPIC SYLLABLE SSE;Lo;0;L;;;;;N;;;;; 2DA6;ETHIOPIC SYLLABLE SSO;Lo;0;L;;;;;N;;;;; 2DA8;ETHIOPIC SYLLABLE CCA;Lo;0;L;;;;;N;;;;; 2DA9;ETHIOPIC SYLLABLE CCU;Lo;0;L;;;;;N;;;;; 2DAA;ETHIOPIC SYLLABLE CCI;Lo;0;L;;;;;N;;;;; 2DAB;ETHIOPIC SYLLABLE CCAA;Lo;0;L;;;;;N;;;;; 2DAC;ETHIOPIC SYLLABLE CCEE;Lo;0;L;;;;;N;;;;; 2DAD;ETHIOPIC SYLLABLE CCE;Lo;0;L;;;;;N;;;;; 2DAE;ETHIOPIC SYLLABLE CCO;Lo;0;L;;;;;N;;;;; 2DB0;ETHIOPIC SYLLABLE ZZA;Lo;0;L;;;;;N;;;;; 2DB1;ETHIOPIC SYLLABLE ZZU;Lo;0;L;;;;;N;;;;; 2DB2;ETHIOPIC SYLLABLE ZZI;Lo;0;L;;;;;N;;;;; 2DB3;ETHIOPIC SYLLABLE ZZAA;Lo;0;L;;;;;N;;;;; 2DB4;ETHIOPIC SYLLABLE ZZEE;Lo;0;L;;;;;N;;;;; 2DB5;ETHIOPIC SYLLABLE ZZE;Lo;0;L;;;;;N;;;;; 2DB6;ETHIOPIC SYLLABLE ZZO;Lo;0;L;;;;;N;;;;; 2DB8;ETHIOPIC SYLLABLE CCHA;Lo;0;L;;;;;N;;;;; 2DB9;ETHIOPIC SYLLABLE CCHU;Lo;0;L;;;;;N;;;;; 2DBA;ETHIOPIC SYLLABLE CCHI;Lo;0;L;;;;;N;;;;; 2DBB;ETHIOPIC SYLLABLE CCHAA;Lo;0;L;;;;;N;;;;; 2DBC;ETHIOPIC SYLLABLE CCHEE;Lo;0;L;;;;;N;;;;; 2DBD;ETHIOPIC SYLLABLE CCHE;Lo;0;L;;;;;N;;;;; 2DBE;ETHIOPIC SYLLABLE CCHO;Lo;0;L;;;;;N;;;;; 2DC0;ETHIOPIC SYLLABLE QYA;Lo;0;L;;;;;N;;;;; 2DC1;ETHIOPIC SYLLABLE QYU;Lo;0;L;;;;;N;;;;; 2DC2;ETHIOPIC SYLLABLE QYI;Lo;0;L;;;;;N;;;;; 2DC3;ETHIOPIC SYLLABLE QYAA;Lo;0;L;;;;;N;;;;; 2DC4;ETHIOPIC SYLLABLE QYEE;Lo;0;L;;;;;N;;;;; 2DC5;ETHIOPIC SYLLABLE QYE;Lo;0;L;;;;;N;;;;; 2DC6;ETHIOPIC SYLLABLE QYO;Lo;0;L;;;;;N;;;;; 2DC8;ETHIOPIC SYLLABLE KYA;Lo;0;L;;;;;N;;;;; 2DC9;ETHIOPIC SYLLABLE KYU;Lo;0;L;;;;;N;;;;; 2DCA;ETHIOPIC SYLLABLE KYI;Lo;0;L;;;;;N;;;;; 2DCB;ETHIOPIC SYLLABLE KYAA;Lo;0;L;;;;;N;;;;; 2DCC;ETHIOPIC SYLLABLE KYEE;Lo;0;L;;;;;N;;;;; 2DCD;ETHIOPIC SYLLABLE KYE;Lo;0;L;;;;;N;;;;; 2DCE;ETHIOPIC SYLLABLE KYO;Lo;0;L;;;;;N;;;;; 2DD0;ETHIOPIC SYLLABLE XYA;Lo;0;L;;;;;N;;;;; 2DD1;ETHIOPIC SYLLABLE XYU;Lo;0;L;;;;;N;;;;; 2DD2;ETHIOPIC SYLLABLE XYI;Lo;0;L;;;;;N;;;;; 2DD3;ETHIOPIC SYLLABLE XYAA;Lo;0;L;;;;;N;;;;; 2DD4;ETHIOPIC SYLLABLE XYEE;Lo;0;L;;;;;N;;;;; 2DD5;ETHIOPIC SYLLABLE XYE;Lo;0;L;;;;;N;;;;; 2DD6;ETHIOPIC SYLLABLE XYO;Lo;0;L;;;;;N;;;;; 2DD8;ETHIOPIC SYLLABLE GYA;Lo;0;L;;;;;N;;;;; 2DD9;ETHIOPIC SYLLABLE GYU;Lo;0;L;;;;;N;;;;; 2DDA;ETHIOPIC SYLLABLE GYI;Lo;0;L;;;;;N;;;;; 2DDB;ETHIOPIC SYLLABLE GYAA;Lo;0;L;;;;;N;;;;; 2DDC;ETHIOPIC SYLLABLE GYEE;Lo;0;L;;;;;N;;;;; 2DDD;ETHIOPIC SYLLABLE GYE;Lo;0;L;;;;;N;;;;; 2DDE;ETHIOPIC SYLLABLE GYO;Lo;0;L;;;;;N;;;;; 2DE0;COMBINING CYRILLIC LETTER BE;Mn;230;NSM;;;;;N;;;;; 2DE1;COMBINING CYRILLIC LETTER VE;Mn;230;NSM;;;;;N;;;;; 2DE2;COMBINING CYRILLIC LETTER GHE;Mn;230;NSM;;;;;N;;;;; 2DE3;COMBINING CYRILLIC LETTER DE;Mn;230;NSM;;;;;N;;;;; 2DE4;COMBINING CYRILLIC LETTER ZHE;Mn;230;NSM;;;;;N;;;;; 2DE5;COMBINING CYRILLIC LETTER ZE;Mn;230;NSM;;;;;N;;;;; 2DE6;COMBINING CYRILLIC LETTER KA;Mn;230;NSM;;;;;N;;;;; 2DE7;COMBINING CYRILLIC LETTER EL;Mn;230;NSM;;;;;N;;;;; 2DE8;COMBINING CYRILLIC LETTER EM;Mn;230;NSM;;;;;N;;;;; 2DE9;COMBINING CYRILLIC LETTER EN;Mn;230;NSM;;;;;N;;;;; 2DEA;COMBINING CYRILLIC LETTER O;Mn;230;NSM;;;;;N;;;;; 2DEB;COMBINING CYRILLIC LETTER PE;Mn;230;NSM;;;;;N;;;;; 2DEC;COMBINING CYRILLIC LETTER ER;Mn;230;NSM;;;;;N;;;;; 2DED;COMBINING CYRILLIC LETTER ES;Mn;230;NSM;;;;;N;;;;; 2DEE;COMBINING CYRILLIC LETTER TE;Mn;230;NSM;;;;;N;;;;; 2DEF;COMBINING CYRILLIC LETTER HA;Mn;230;NSM;;;;;N;;;;; 2DF0;COMBINING CYRILLIC LETTER TSE;Mn;230;NSM;;;;;N;;;;; 2DF1;COMBINING CYRILLIC LETTER CHE;Mn;230;NSM;;;;;N;;;;; 2DF2;COMBINING CYRILLIC LETTER SHA;Mn;230;NSM;;;;;N;;;;; 2DF3;COMBINING CYRILLIC LETTER SHCHA;Mn;230;NSM;;;;;N;;;;; 2DF4;COMBINING CYRILLIC LETTER FITA;Mn;230;NSM;;;;;N;;;;; 2DF5;COMBINING CYRILLIC LETTER ES-TE;Mn;230;NSM;;;;;N;;;;; 2DF6;COMBINING CYRILLIC LETTER A;Mn;230;NSM;;;;;N;;;;; 2DF7;COMBINING CYRILLIC LETTER IE;Mn;230;NSM;;;;;N;;;;; 2DF8;COMBINING CYRILLIC LETTER DJERV;Mn;230;NSM;;;;;N;;;;; 2DF9;COMBINING CYRILLIC LETTER MONOGRAPH UK;Mn;230;NSM;;;;;N;;;;; 2DFA;COMBINING CYRILLIC LETTER YAT;Mn;230;NSM;;;;;N;;;;; 2DFB;COMBINING CYRILLIC LETTER YU;Mn;230;NSM;;;;;N;;;;; 2DFC;COMBINING CYRILLIC LETTER IOTIFIED A;Mn;230;NSM;;;;;N;;;;; 2DFD;COMBINING CYRILLIC LETTER LITTLE YUS;Mn;230;NSM;;;;;N;;;;; 2DFE;COMBINING CYRILLIC LETTER BIG YUS;Mn;230;NSM;;;;;N;;;;; 2DFF;COMBINING CYRILLIC LETTER IOTIFIED BIG YUS;Mn;230;NSM;;;;;N;;;;; 2E00;RIGHT ANGLE SUBSTITUTION MARKER;Po;0;ON;;;;;N;;;;; 2E01;RIGHT ANGLE DOTTED SUBSTITUTION MARKER;Po;0;ON;;;;;N;;;;; 2E02;LEFT SUBSTITUTION BRACKET;Pi;0;ON;;;;;Y;;;;; 2E03;RIGHT SUBSTITUTION BRACKET;Pf;0;ON;;;;;Y;;;;; 2E04;LEFT DOTTED SUBSTITUTION BRACKET;Pi;0;ON;;;;;Y;;;;; 2E05;RIGHT DOTTED SUBSTITUTION BRACKET;Pf;0;ON;;;;;Y;;;;; 2E06;RAISED INTERPOLATION MARKER;Po;0;ON;;;;;N;;;;; 2E07;RAISED DOTTED INTERPOLATION MARKER;Po;0;ON;;;;;N;;;;; 2E08;DOTTED TRANSPOSITION MARKER;Po;0;ON;;;;;N;;;;; 2E09;LEFT TRANSPOSITION BRACKET;Pi;0;ON;;;;;Y;;;;; 2E0A;RIGHT TRANSPOSITION BRACKET;Pf;0;ON;;;;;Y;;;;; 2E0B;RAISED SQUARE;Po;0;ON;;;;;N;;;;; 2E0C;LEFT RAISED OMISSION BRACKET;Pi;0;ON;;;;;Y;;;;; 2E0D;RIGHT RAISED OMISSION BRACKET;Pf;0;ON;;;;;Y;;;;; 2E0E;EDITORIAL CORONIS;Po;0;ON;;;;;N;;;;; 2E0F;PARAGRAPHOS;Po;0;ON;;;;;N;;;;; 2E10;FORKED PARAGRAPHOS;Po;0;ON;;;;;N;;;;; 2E11;REVERSED FORKED PARAGRAPHOS;Po;0;ON;;;;;N;;;;; 2E12;HYPODIASTOLE;Po;0;ON;;;;;N;;;;; 2E13;DOTTED OBELOS;Po;0;ON;;;;;N;;;;; 2E14;DOWNWARDS ANCORA;Po;0;ON;;;;;N;;;;; 2E15;UPWARDS ANCORA;Po;0;ON;;;;;N;;;;; 2E16;DOTTED RIGHT-POINTING ANGLE;Po;0;ON;;;;;N;;;;; 2E17;DOUBLE OBLIQUE HYPHEN;Pd;0;ON;;;;;N;;;;; 2E18;INVERTED INTERROBANG;Po;0;ON;;;;;N;;;;; 2E19;PALM BRANCH;Po;0;ON;;;;;N;;;;; 2E1A;HYPHEN WITH DIAERESIS;Pd;0;ON;;;;;N;;;;; 2E1B;TILDE WITH RING ABOVE;Po;0;ON;;;;;N;;;;; 2E1C;LEFT LOW PARAPHRASE BRACKET;Pi;0;ON;;;;;Y;;;;; 2E1D;RIGHT LOW PARAPHRASE BRACKET;Pf;0;ON;;;;;Y;;;;; 2E1E;TILDE WITH DOT ABOVE;Po;0;ON;;;;;N;;;;; 2E1F;TILDE WITH DOT BELOW;Po;0;ON;;;;;N;;;;; 2E20;LEFT VERTICAL BAR WITH QUILL;Pi;0;ON;;;;;Y;;;;; 2E21;RIGHT VERTICAL BAR WITH QUILL;Pf;0;ON;;;;;Y;;;;; 2E22;TOP LEFT HALF BRACKET;Ps;0;ON;;;;;Y;;;;; 2E23;TOP RIGHT HALF BRACKET;Pe;0;ON;;;;;Y;;;;; 2E24;BOTTOM LEFT HALF BRACKET;Ps;0;ON;;;;;Y;;;;; 2E25;BOTTOM RIGHT HALF BRACKET;Pe;0;ON;;;;;Y;;;;; 2E26;LEFT SIDEWAYS U BRACKET;Ps;0;ON;;;;;Y;;;;; 2E27;RIGHT SIDEWAYS U BRACKET;Pe;0;ON;;;;;Y;;;;; 2E28;LEFT DOUBLE PARENTHESIS;Ps;0;ON;;;;;Y;;;;; 2E29;RIGHT DOUBLE PARENTHESIS;Pe;0;ON;;;;;Y;;;;; 2E2A;TWO DOTS OVER ONE DOT PUNCTUATION;Po;0;ON;;;;;N;;;;; 2E2B;ONE DOT OVER TWO DOTS PUNCTUATION;Po;0;ON;;;;;N;;;;; 2E2C;SQUARED FOUR DOT PUNCTUATION;Po;0;ON;;;;;N;;;;; 2E2D;FIVE DOT MARK;Po;0;ON;;;;;N;;;;; 2E2E;REVERSED QUESTION MARK;Po;0;ON;;;;;N;;;;; 2E2F;VERTICAL TILDE;Lm;0;ON;;;;;N;;;;; 2E30;RING POINT;Po;0;ON;;;;;N;;;;; 2E31;WORD SEPARATOR MIDDLE DOT;Po;0;ON;;;;;N;;;;; 2E32;TURNED COMMA;Po;0;ON;;;;;N;;;;; 2E33;RAISED DOT;Po;0;ON;;;;;N;;;;; 2E34;RAISED COMMA;Po;0;ON;;;;;N;;;;; 2E35;TURNED SEMICOLON;Po;0;ON;;;;;N;;;;; 2E36;DAGGER WITH LEFT GUARD;Po;0;ON;;;;;N;;;;; 2E37;DAGGER WITH RIGHT GUARD;Po;0;ON;;;;;N;;;;; 2E38;TURNED DAGGER;Po;0;ON;;;;;N;;;;; 2E39;TOP HALF SECTION SIGN;Po;0;ON;;;;;N;;;;; 2E3A;TWO-EM DASH;Pd;0;ON;;;;;N;;;;; 2E3B;THREE-EM DASH;Pd;0;ON;;;;;N;;;;; 2E3C;STENOGRAPHIC FULL STOP;Po;0;ON;;;;;N;;;;; 2E3D;VERTICAL SIX DOTS;Po;0;ON;;;;;N;;;;; 2E3E;WIGGLY VERTICAL LINE;Po;0;ON;;;;;N;;;;; 2E3F;CAPITULUM;Po;0;ON;;;;;N;;;;; 2E40;DOUBLE HYPHEN;Pd;0;ON;;;;;N;;;;; 2E41;REVERSED COMMA;Po;0;ON;;;;;N;;;;; 2E42;DOUBLE LOW-REVERSED-9 QUOTATION MARK;Ps;0;ON;;;;;N;;;;; 2E80;CJK RADICAL REPEAT;So;0;ON;;;;;N;;;;; 2E81;CJK RADICAL CLIFF;So;0;ON;;;;;N;;;;; 2E82;CJK RADICAL SECOND ONE;So;0;ON;;;;;N;;;;; 2E83;CJK RADICAL SECOND TWO;So;0;ON;;;;;N;;;;; 2E84;CJK RADICAL SECOND THREE;So;0;ON;;;;;N;;;;; 2E85;CJK RADICAL PERSON;So;0;ON;;;;;N;;;;; 2E86;CJK RADICAL BOX;So;0;ON;;;;;N;;;;; 2E87;CJK RADICAL TABLE;So;0;ON;;;;;N;;;;; 2E88;CJK RADICAL KNIFE ONE;So;0;ON;;;;;N;;;;; 2E89;CJK RADICAL KNIFE TWO;So;0;ON;;;;;N;;;;; 2E8A;CJK RADICAL DIVINATION;So;0;ON;;;;;N;;;;; 2E8B;CJK RADICAL SEAL;So;0;ON;;;;;N;;;;; 2E8C;CJK RADICAL SMALL ONE;So;0;ON;;;;;N;;;;; 2E8D;CJK RADICAL SMALL TWO;So;0;ON;;;;;N;;;;; 2E8E;CJK RADICAL LAME ONE;So;0;ON;;;;;N;;;;; 2E8F;CJK RADICAL LAME TWO;So;0;ON;;;;;N;;;;; 2E90;CJK RADICAL LAME THREE;So;0;ON;;;;;N;;;;; 2E91;CJK RADICAL LAME FOUR;So;0;ON;;;;;N;;;;; 2E92;CJK RADICAL SNAKE;So;0;ON;;;;;N;;;;; 2E93;CJK RADICAL THREAD;So;0;ON;;;;;N;;;;; 2E94;CJK RADICAL SNOUT ONE;So;0;ON;;;;;N;;;;; 2E95;CJK RADICAL SNOUT TWO;So;0;ON;;;;;N;;;;; 2E96;CJK RADICAL HEART ONE;So;0;ON;;;;;N;;;;; 2E97;CJK RADICAL HEART TWO;So;0;ON;;;;;N;;;;; 2E98;CJK RADICAL HAND;So;0;ON;;;;;N;;;;; 2E99;CJK RADICAL RAP;So;0;ON;;;;;N;;;;; 2E9B;CJK RADICAL CHOKE;So;0;ON;;;;;N;;;;; 2E9C;CJK RADICAL SUN;So;0;ON;;;;;N;;;;; 2E9D;CJK RADICAL MOON;So;0;ON;;;;;N;;;;; 2E9E;CJK RADICAL DEATH;So;0;ON;;;;;N;;;;; 2E9F;CJK RADICAL MOTHER;So;0;ON; 6BCD;;;;N;;;;; 2EA0;CJK RADICAL CIVILIAN;So;0;ON;;;;;N;;;;; 2EA1;CJK RADICAL WATER ONE;So;0;ON;;;;;N;;;;; 2EA2;CJK RADICAL WATER TWO;So;0;ON;;;;;N;;;;; 2EA3;CJK RADICAL FIRE;So;0;ON;;;;;N;;;;; 2EA4;CJK RADICAL PAW ONE;So;0;ON;;;;;N;;;;; 2EA5;CJK RADICAL PAW TWO;So;0;ON;;;;;N;;;;; 2EA6;CJK RADICAL SIMPLIFIED HALF TREE TRUNK;So;0;ON;;;;;N;;;;; 2EA7;CJK RADICAL COW;So;0;ON;;;;;N;;;;; 2EA8;CJK RADICAL DOG;So;0;ON;;;;;N;;;;; 2EA9;CJK RADICAL JADE;So;0;ON;;;;;N;;;;; 2EAA;CJK RADICAL BOLT OF CLOTH;So;0;ON;;;;;N;;;;; 2EAB;CJK RADICAL EYE;So;0;ON;;;;;N;;;;; 2EAC;CJK RADICAL SPIRIT ONE;So;0;ON;;;;;N;;;;; 2EAD;CJK RADICAL SPIRIT TWO;So;0;ON;;;;;N;;;;; 2EAE;CJK RADICAL BAMBOO;So;0;ON;;;;;N;;;;; 2EAF;CJK RADICAL SILK;So;0;ON;;;;;N;;;;; 2EB0;CJK RADICAL C-SIMPLIFIED SILK;So;0;ON;;;;;N;;;;; 2EB1;CJK RADICAL NET ONE;So;0;ON;;;;;N;;;;; 2EB2;CJK RADICAL NET TWO;So;0;ON;;;;;N;;;;; 2EB3;CJK RADICAL NET THREE;So;0;ON;;;;;N;;;;; 2EB4;CJK RADICAL NET FOUR;So;0;ON;;;;;N;;;;; 2EB5;CJK RADICAL MESH;So;0;ON;;;;;N;;;;; 2EB6;CJK RADICAL SHEEP;So;0;ON;;;;;N;;;;; 2EB7;CJK RADICAL RAM;So;0;ON;;;;;N;;;;; 2EB8;CJK RADICAL EWE;So;0;ON;;;;;N;;;;; 2EB9;CJK RADICAL OLD;So;0;ON;;;;;N;;;;; 2EBA;CJK RADICAL BRUSH ONE;So;0;ON;;;;;N;;;;; 2EBB;CJK RADICAL BRUSH TWO;So;0;ON;;;;;N;;;;; 2EBC;CJK RADICAL MEAT;So;0;ON;;;;;N;;;;; 2EBD;CJK RADICAL MORTAR;So;0;ON;;;;;N;;;;; 2EBE;CJK RADICAL GRASS ONE;So;0;ON;;;;;N;;;;; 2EBF;CJK RADICAL GRASS TWO;So;0;ON;;;;;N;;;;; 2EC0;CJK RADICAL GRASS THREE;So;0;ON;;;;;N;;;;; 2EC1;CJK RADICAL TIGER;So;0;ON;;;;;N;;;;; 2EC2;CJK RADICAL CLOTHES;So;0;ON;;;;;N;;;;; 2EC3;CJK RADICAL WEST ONE;So;0;ON;;;;;N;;;;; 2EC4;CJK RADICAL WEST TWO;So;0;ON;;;;;N;;;;; 2EC5;CJK RADICAL C-SIMPLIFIED SEE;So;0;ON;;;;;N;;;;; 2EC6;CJK RADICAL SIMPLIFIED HORN;So;0;ON;;;;;N;;;;; 2EC7;CJK RADICAL HORN;So;0;ON;;;;;N;;;;; 2EC8;CJK RADICAL C-SIMPLIFIED SPEECH;So;0;ON;;;;;N;;;;; 2EC9;CJK RADICAL C-SIMPLIFIED SHELL;So;0;ON;;;;;N;;;;; 2ECA;CJK RADICAL FOOT;So;0;ON;;;;;N;;;;; 2ECB;CJK RADICAL C-SIMPLIFIED CART;So;0;ON;;;;;N;;;;; 2ECC;CJK RADICAL SIMPLIFIED WALK;So;0;ON;;;;;N;;;;; 2ECD;CJK RADICAL WALK ONE;So;0;ON;;;;;N;;;;; 2ECE;CJK RADICAL WALK TWO;So;0;ON;;;;;N;;;;; 2ECF;CJK RADICAL CITY;So;0;ON;;;;;N;;;;; 2ED0;CJK RADICAL C-SIMPLIFIED GOLD;So;0;ON;;;;;N;;;;; 2ED1;CJK RADICAL LONG ONE;So;0;ON;;;;;N;;;;; 2ED2;CJK RADICAL LONG TWO;So;0;ON;;;;;N;;;;; 2ED3;CJK RADICAL C-SIMPLIFIED LONG;So;0;ON;;;;;N;;;;; 2ED4;CJK RADICAL C-SIMPLIFIED GATE;So;0;ON;;;;;N;;;;; 2ED5;CJK RADICAL MOUND ONE;So;0;ON;;;;;N;;;;; 2ED6;CJK RADICAL MOUND TWO;So;0;ON;;;;;N;;;;; 2ED7;CJK RADICAL RAIN;So;0;ON;;;;;N;;;;; 2ED8;CJK RADICAL BLUE;So;0;ON;;;;;N;;;;; 2ED9;CJK RADICAL C-SIMPLIFIED TANNED LEATHER;So;0;ON;;;;;N;;;;; 2EDA;CJK RADICAL C-SIMPLIFIED LEAF;So;0;ON;;;;;N;;;;; 2EDB;CJK RADICAL C-SIMPLIFIED WIND;So;0;ON;;;;;N;;;;; 2EDC;CJK RADICAL C-SIMPLIFIED FLY;So;0;ON;;;;;N;;;;; 2EDD;CJK RADICAL EAT ONE;So;0;ON;;;;;N;;;;; 2EDE;CJK RADICAL EAT TWO;So;0;ON;;;;;N;;;;; 2EDF;CJK RADICAL EAT THREE;So;0;ON;;;;;N;;;;; 2EE0;CJK RADICAL C-SIMPLIFIED EAT;So;0;ON;;;;;N;;;;; 2EE1;CJK RADICAL HEAD;So;0;ON;;;;;N;;;;; 2EE2;CJK RADICAL C-SIMPLIFIED HORSE;So;0;ON;;;;;N;;;;; 2EE3;CJK RADICAL BONE;So;0;ON;;;;;N;;;;; 2EE4;CJK RADICAL GHOST;So;0;ON;;;;;N;;;;; 2EE5;CJK RADICAL C-SIMPLIFIED FISH;So;0;ON;;;;;N;;;;; 2EE6;CJK RADICAL C-SIMPLIFIED BIRD;So;0;ON;;;;;N;;;;; 2EE7;CJK RADICAL C-SIMPLIFIED SALT;So;0;ON;;;;;N;;;;; 2EE8;CJK RADICAL SIMPLIFIED WHEAT;So;0;ON;;;;;N;;;;; 2EE9;CJK RADICAL SIMPLIFIED YELLOW;So;0;ON;;;;;N;;;;; 2EEA;CJK RADICAL C-SIMPLIFIED FROG;So;0;ON;;;;;N;;;;; 2EEB;CJK RADICAL J-SIMPLIFIED EVEN;So;0;ON;;;;;N;;;;; 2EEC;CJK RADICAL C-SIMPLIFIED EVEN;So;0;ON;;;;;N;;;;; 2EED;CJK RADICAL J-SIMPLIFIED TOOTH;So;0;ON;;;;;N;;;;; 2EEE;CJK RADICAL C-SIMPLIFIED TOOTH;So;0;ON;;;;;N;;;;; 2EEF;CJK RADICAL J-SIMPLIFIED DRAGON;So;0;ON;;;;;N;;;;; 2EF0;CJK RADICAL C-SIMPLIFIED DRAGON;So;0;ON;;;;;N;;;;; 2EF1;CJK RADICAL TURTLE;So;0;ON;;;;;N;;;;; 2EF2;CJK RADICAL J-SIMPLIFIED TURTLE;So;0;ON;;;;;N;;;;; 2EF3;CJK RADICAL C-SIMPLIFIED TURTLE;So;0;ON; 9F9F;;;;N;;;;; 2F00;KANGXI RADICAL ONE;So;0;ON; 4E00;;;;N;;;;; 2F01;KANGXI RADICAL LINE;So;0;ON; 4E28;;;;N;;;;; 2F02;KANGXI RADICAL DOT;So;0;ON; 4E36;;;;N;;;;; 2F03;KANGXI RADICAL SLASH;So;0;ON; 4E3F;;;;N;;;;; 2F04;KANGXI RADICAL SECOND;So;0;ON; 4E59;;;;N;;;;; 2F05;KANGXI RADICAL HOOK;So;0;ON; 4E85;;;;N;;;;; 2F06;KANGXI RADICAL TWO;So;0;ON; 4E8C;;;;N;;;;; 2F07;KANGXI RADICAL LID;So;0;ON; 4EA0;;;;N;;;;; 2F08;KANGXI RADICAL MAN;So;0;ON; 4EBA;;;;N;;;;; 2F09;KANGXI RADICAL LEGS;So;0;ON; 513F;;;;N;;;;; 2F0A;KANGXI RADICAL ENTER;So;0;ON; 5165;;;;N;;;;; 2F0B;KANGXI RADICAL EIGHT;So;0;ON; 516B;;;;N;;;;; 2F0C;KANGXI RADICAL DOWN BOX;So;0;ON; 5182;;;;N;;;;; 2F0D;KANGXI RADICAL COVER;So;0;ON; 5196;;;;N;;;;; 2F0E;KANGXI RADICAL ICE;So;0;ON; 51AB;;;;N;;;;; 2F0F;KANGXI RADICAL TABLE;So;0;ON; 51E0;;;;N;;;;; 2F10;KANGXI RADICAL OPEN BOX;So;0;ON; 51F5;;;;N;;;;; 2F11;KANGXI RADICAL KNIFE;So;0;ON; 5200;;;;N;;;;; 2F12;KANGXI RADICAL POWER;So;0;ON; 529B;;;;N;;;;; 2F13;KANGXI RADICAL WRAP;So;0;ON; 52F9;;;;N;;;;; 2F14;KANGXI RADICAL SPOON;So;0;ON; 5315;;;;N;;;;; 2F15;KANGXI RADICAL RIGHT OPEN BOX;So;0;ON; 531A;;;;N;;;;; 2F16;KANGXI RADICAL HIDING ENCLOSURE;So;0;ON; 5338;;;;N;;;;; 2F17;KANGXI RADICAL TEN;So;0;ON; 5341;;;;N;;;;; 2F18;KANGXI RADICAL DIVINATION;So;0;ON; 535C;;;;N;;;;; 2F19;KANGXI RADICAL SEAL;So;0;ON; 5369;;;;N;;;;; 2F1A;KANGXI RADICAL CLIFF;So;0;ON; 5382;;;;N;;;;; 2F1B;KANGXI RADICAL PRIVATE;So;0;ON; 53B6;;;;N;;;;; 2F1C;KANGXI RADICAL AGAIN;So;0;ON; 53C8;;;;N;;;;; 2F1D;KANGXI RADICAL MOUTH;So;0;ON; 53E3;;;;N;;;;; 2F1E;KANGXI RADICAL ENCLOSURE;So;0;ON; 56D7;;;;N;;;;; 2F1F;KANGXI RADICAL EARTH;So;0;ON; 571F;;;;N;;;;; 2F20;KANGXI RADICAL SCHOLAR;So;0;ON; 58EB;;;;N;;;;; 2F21;KANGXI RADICAL GO;So;0;ON; 5902;;;;N;;;;; 2F22;KANGXI RADICAL GO SLOWLY;So;0;ON; 590A;;;;N;;;;; 2F23;KANGXI RADICAL EVENING;So;0;ON; 5915;;;;N;;;;; 2F24;KANGXI RADICAL BIG;So;0;ON; 5927;;;;N;;;;; 2F25;KANGXI RADICAL WOMAN;So;0;ON; 5973;;;;N;;;;; 2F26;KANGXI RADICAL CHILD;So;0;ON; 5B50;;;;N;;;;; 2F27;KANGXI RADICAL ROOF;So;0;ON; 5B80;;;;N;;;;; 2F28;KANGXI RADICAL INCH;So;0;ON; 5BF8;;;;N;;;;; 2F29;KANGXI RADICAL SMALL;So;0;ON; 5C0F;;;;N;;;;; 2F2A;KANGXI RADICAL LAME;So;0;ON; 5C22;;;;N;;;;; 2F2B;KANGXI RADICAL CORPSE;So;0;ON; 5C38;;;;N;;;;; 2F2C;KANGXI RADICAL SPROUT;So;0;ON; 5C6E;;;;N;;;;; 2F2D;KANGXI RADICAL MOUNTAIN;So;0;ON; 5C71;;;;N;;;;; 2F2E;KANGXI RADICAL RIVER;So;0;ON; 5DDB;;;;N;;;;; 2F2F;KANGXI RADICAL WORK;So;0;ON; 5DE5;;;;N;;;;; 2F30;KANGXI RADICAL ONESELF;So;0;ON; 5DF1;;;;N;;;;; 2F31;KANGXI RADICAL TURBAN;So;0;ON; 5DFE;;;;N;;;;; 2F32;KANGXI RADICAL DRY;So;0;ON; 5E72;;;;N;;;;; 2F33;KANGXI RADICAL SHORT THREAD;So;0;ON; 5E7A;;;;N;;;;; 2F34;KANGXI RADICAL DOTTED CLIFF;So;0;ON; 5E7F;;;;N;;;;; 2F35;KANGXI RADICAL LONG STRIDE;So;0;ON; 5EF4;;;;N;;;;; 2F36;KANGXI RADICAL TWO HANDS;So;0;ON; 5EFE;;;;N;;;;; 2F37;KANGXI RADICAL SHOOT;So;0;ON; 5F0B;;;;N;;;;; 2F38;KANGXI RADICAL BOW;So;0;ON; 5F13;;;;N;;;;; 2F39;KANGXI RADICAL SNOUT;So;0;ON; 5F50;;;;N;;;;; 2F3A;KANGXI RADICAL BRISTLE;So;0;ON; 5F61;;;;N;;;;; 2F3B;KANGXI RADICAL STEP;So;0;ON; 5F73;;;;N;;;;; 2F3C;KANGXI RADICAL HEART;So;0;ON; 5FC3;;;;N;;;;; 2F3D;KANGXI RADICAL HALBERD;So;0;ON; 6208;;;;N;;;;; 2F3E;KANGXI RADICAL DOOR;So;0;ON; 6236;;;;N;;;;; 2F3F;KANGXI RADICAL HAND;So;0;ON; 624B;;;;N;;;;; 2F40;KANGXI RADICAL BRANCH;So;0;ON; 652F;;;;N;;;;; 2F41;KANGXI RADICAL RAP;So;0;ON; 6534;;;;N;;;;; 2F42;KANGXI RADICAL SCRIPT;So;0;ON; 6587;;;;N;;;;; 2F43;KANGXI RADICAL DIPPER;So;0;ON; 6597;;;;N;;;;; 2F44;KANGXI RADICAL AXE;So;0;ON; 65A4;;;;N;;;;; 2F45;KANGXI RADICAL SQUARE;So;0;ON; 65B9;;;;N;;;;; 2F46;KANGXI RADICAL NOT;So;0;ON; 65E0;;;;N;;;;; 2F47;KANGXI RADICAL SUN;So;0;ON; 65E5;;;;N;;;;; 2F48;KANGXI RADICAL SAY;So;0;ON; 66F0;;;;N;;;;; 2F49;KANGXI RADICAL MOON;So;0;ON; 6708;;;;N;;;;; 2F4A;KANGXI RADICAL TREE;So;0;ON; 6728;;;;N;;;;; 2F4B;KANGXI RADICAL LACK;So;0;ON; 6B20;;;;N;;;;; 2F4C;KANGXI RADICAL STOP;So;0;ON; 6B62;;;;N;;;;; 2F4D;KANGXI RADICAL DEATH;So;0;ON; 6B79;;;;N;;;;; 2F4E;KANGXI RADICAL WEAPON;So;0;ON; 6BB3;;;;N;;;;; 2F4F;KANGXI RADICAL DO NOT;So;0;ON; 6BCB;;;;N;;;;; 2F50;KANGXI RADICAL COMPARE;So;0;ON; 6BD4;;;;N;;;;; 2F51;KANGXI RADICAL FUR;So;0;ON; 6BDB;;;;N;;;;; 2F52;KANGXI RADICAL CLAN;So;0;ON; 6C0F;;;;N;;;;; 2F53;KANGXI RADICAL STEAM;So;0;ON; 6C14;;;;N;;;;; 2F54;KANGXI RADICAL WATER;So;0;ON; 6C34;;;;N;;;;; 2F55;KANGXI RADICAL FIRE;So;0;ON; 706B;;;;N;;;;; 2F56;KANGXI RADICAL CLAW;So;0;ON; 722A;;;;N;;;;; 2F57;KANGXI RADICAL FATHER;So;0;ON; 7236;;;;N;;;;; 2F58;KANGXI RADICAL DOUBLE X;So;0;ON; 723B;;;;N;;;;; 2F59;KANGXI RADICAL HALF TREE TRUNK;So;0;ON; 723F;;;;N;;;;; 2F5A;KANGXI RADICAL SLICE;So;0;ON; 7247;;;;N;;;;; 2F5B;KANGXI RADICAL FANG;So;0;ON; 7259;;;;N;;;;; 2F5C;KANGXI RADICAL COW;So;0;ON; 725B;;;;N;;;;; 2F5D;KANGXI RADICAL DOG;So;0;ON; 72AC;;;;N;;;;; 2F5E;KANGXI RADICAL PROFOUND;So;0;ON; 7384;;;;N;;;;; 2F5F;KANGXI RADICAL JADE;So;0;ON; 7389;;;;N;;;;; 2F60;KANGXI RADICAL MELON;So;0;ON; 74DC;;;;N;;;;; 2F61;KANGXI RADICAL TILE;So;0;ON; 74E6;;;;N;;;;; 2F62;KANGXI RADICAL SWEET;So;0;ON; 7518;;;;N;;;;; 2F63;KANGXI RADICAL LIFE;So;0;ON; 751F;;;;N;;;;; 2F64;KANGXI RADICAL USE;So;0;ON; 7528;;;;N;;;;; 2F65;KANGXI RADICAL FIELD;So;0;ON; 7530;;;;N;;;;; 2F66;KANGXI RADICAL BOLT OF CLOTH;So;0;ON; 758B;;;;N;;;;; 2F67;KANGXI RADICAL SICKNESS;So;0;ON; 7592;;;;N;;;;; 2F68;KANGXI RADICAL DOTTED TENT;So;0;ON; 7676;;;;N;;;;; 2F69;KANGXI RADICAL WHITE;So;0;ON; 767D;;;;N;;;;; 2F6A;KANGXI RADICAL SKIN;So;0;ON; 76AE;;;;N;;;;; 2F6B;KANGXI RADICAL DISH;So;0;ON; 76BF;;;;N;;;;; 2F6C;KANGXI RADICAL EYE;So;0;ON; 76EE;;;;N;;;;; 2F6D;KANGXI RADICAL SPEAR;So;0;ON; 77DB;;;;N;;;;; 2F6E;KANGXI RADICAL ARROW;So;0;ON; 77E2;;;;N;;;;; 2F6F;KANGXI RADICAL STONE;So;0;ON; 77F3;;;;N;;;;; 2F70;KANGXI RADICAL SPIRIT;So;0;ON; 793A;;;;N;;;;; 2F71;KANGXI RADICAL TRACK;So;0;ON; 79B8;;;;N;;;;; 2F72;KANGXI RADICAL GRAIN;So;0;ON; 79BE;;;;N;;;;; 2F73;KANGXI RADICAL CAVE;So;0;ON; 7A74;;;;N;;;;; 2F74;KANGXI RADICAL STAND;So;0;ON; 7ACB;;;;N;;;;; 2F75;KANGXI RADICAL BAMBOO;So;0;ON; 7AF9;;;;N;;;;; 2F76;KANGXI RADICAL RICE;So;0;ON; 7C73;;;;N;;;;; 2F77;KANGXI RADICAL SILK;So;0;ON; 7CF8;;;;N;;;;; 2F78;KANGXI RADICAL JAR;So;0;ON; 7F36;;;;N;;;;; 2F79;KANGXI RADICAL NET;So;0;ON; 7F51;;;;N;;;;; 2F7A;KANGXI RADICAL SHEEP;So;0;ON; 7F8A;;;;N;;;;; 2F7B;KANGXI RADICAL FEATHER;So;0;ON; 7FBD;;;;N;;;;; 2F7C;KANGXI RADICAL OLD;So;0;ON; 8001;;;;N;;;;; 2F7D;KANGXI RADICAL AND;So;0;ON; 800C;;;;N;;;;; 2F7E;KANGXI RADICAL PLOW;So;0;ON; 8012;;;;N;;;;; 2F7F;KANGXI RADICAL EAR;So;0;ON; 8033;;;;N;;;;; 2F80;KANGXI RADICAL BRUSH;So;0;ON; 807F;;;;N;;;;; 2F81;KANGXI RADICAL MEAT;So;0;ON; 8089;;;;N;;;;; 2F82;KANGXI RADICAL MINISTER;So;0;ON; 81E3;;;;N;;;;; 2F83;KANGXI RADICAL SELF;So;0;ON; 81EA;;;;N;;;;; 2F84;KANGXI RADICAL ARRIVE;So;0;ON; 81F3;;;;N;;;;; 2F85;KANGXI RADICAL MORTAR;So;0;ON; 81FC;;;;N;;;;; 2F86;KANGXI RADICAL TONGUE;So;0;ON; 820C;;;;N;;;;; 2F87;KANGXI RADICAL OPPOSE;So;0;ON; 821B;;;;N;;;;; 2F88;KANGXI RADICAL BOAT;So;0;ON; 821F;;;;N;;;;; 2F89;KANGXI RADICAL STOPPING;So;0;ON; 826E;;;;N;;;;; 2F8A;KANGXI RADICAL COLOR;So;0;ON; 8272;;;;N;;;;; 2F8B;KANGXI RADICAL GRASS;So;0;ON; 8278;;;;N;;;;; 2F8C;KANGXI RADICAL TIGER;So;0;ON; 864D;;;;N;;;;; 2F8D;KANGXI RADICAL INSECT;So;0;ON; 866B;;;;N;;;;; 2F8E;KANGXI RADICAL BLOOD;So;0;ON; 8840;;;;N;;;;; 2F8F;KANGXI RADICAL WALK ENCLOSURE;So;0;ON; 884C;;;;N;;;;; 2F90;KANGXI RADICAL CLOTHES;So;0;ON; 8863;;;;N;;;;; 2F91;KANGXI RADICAL WEST;So;0;ON; 897E;;;;N;;;;; 2F92;KANGXI RADICAL SEE;So;0;ON; 898B;;;;N;;;;; 2F93;KANGXI RADICAL HORN;So;0;ON; 89D2;;;;N;;;;; 2F94;KANGXI RADICAL SPEECH;So;0;ON; 8A00;;;;N;;;;; 2F95;KANGXI RADICAL VALLEY;So;0;ON; 8C37;;;;N;;;;; 2F96;KANGXI RADICAL BEAN;So;0;ON; 8C46;;;;N;;;;; 2F97;KANGXI RADICAL PIG;So;0;ON; 8C55;;;;N;;;;; 2F98;KANGXI RADICAL BADGER;So;0;ON; 8C78;;;;N;;;;; 2F99;KANGXI RADICAL SHELL;So;0;ON; 8C9D;;;;N;;;;; 2F9A;KANGXI RADICAL RED;So;0;ON; 8D64;;;;N;;;;; 2F9B;KANGXI RADICAL RUN;So;0;ON; 8D70;;;;N;;;;; 2F9C;KANGXI RADICAL FOOT;So;0;ON; 8DB3;;;;N;;;;; 2F9D;KANGXI RADICAL BODY;So;0;ON; 8EAB;;;;N;;;;; 2F9E;KANGXI RADICAL CART;So;0;ON; 8ECA;;;;N;;;;; 2F9F;KANGXI RADICAL BITTER;So;0;ON; 8F9B;;;;N;;;;; 2FA0;KANGXI RADICAL MORNING;So;0;ON; 8FB0;;;;N;;;;; 2FA1;KANGXI RADICAL WALK;So;0;ON; 8FB5;;;;N;;;;; 2FA2;KANGXI RADICAL CITY;So;0;ON; 9091;;;;N;;;;; 2FA3;KANGXI RADICAL WINE;So;0;ON; 9149;;;;N;;;;; 2FA4;KANGXI RADICAL DISTINGUISH;So;0;ON; 91C6;;;;N;;;;; 2FA5;KANGXI RADICAL VILLAGE;So;0;ON; 91CC;;;;N;;;;; 2FA6;KANGXI RADICAL GOLD;So;0;ON; 91D1;;;;N;;;;; 2FA7;KANGXI RADICAL LONG;So;0;ON; 9577;;;;N;;;;; 2FA8;KANGXI RADICAL GATE;So;0;ON; 9580;;;;N;;;;; 2FA9;KANGXI RADICAL MOUND;So;0;ON; 961C;;;;N;;;;; 2FAA;KANGXI RADICAL SLAVE;So;0;ON; 96B6;;;;N;;;;; 2FAB;KANGXI RADICAL SHORT TAILED BIRD;So;0;ON; 96B9;;;;N;;;;; 2FAC;KANGXI RADICAL RAIN;So;0;ON; 96E8;;;;N;;;;; 2FAD;KANGXI RADICAL BLUE;So;0;ON; 9751;;;;N;;;;; 2FAE;KANGXI RADICAL WRONG;So;0;ON; 975E;;;;N;;;;; 2FAF;KANGXI RADICAL FACE;So;0;ON; 9762;;;;N;;;;; 2FB0;KANGXI RADICAL LEATHER;So;0;ON; 9769;;;;N;;;;; 2FB1;KANGXI RADICAL TANNED LEATHER;So;0;ON; 97CB;;;;N;;;;; 2FB2;KANGXI RADICAL LEEK;So;0;ON; 97ED;;;;N;;;;; 2FB3;KANGXI RADICAL SOUND;So;0;ON; 97F3;;;;N;;;;; 2FB4;KANGXI RADICAL LEAF;So;0;ON; 9801;;;;N;;;;; 2FB5;KANGXI RADICAL WIND;So;0;ON; 98A8;;;;N;;;;; 2FB6;KANGXI RADICAL FLY;So;0;ON; 98DB;;;;N;;;;; 2FB7;KANGXI RADICAL EAT;So;0;ON; 98DF;;;;N;;;;; 2FB8;KANGXI RADICAL HEAD;So;0;ON; 9996;;;;N;;;;; 2FB9;KANGXI RADICAL FRAGRANT;So;0;ON; 9999;;;;N;;;;; 2FBA;KANGXI RADICAL HORSE;So;0;ON; 99AC;;;;N;;;;; 2FBB;KANGXI RADICAL BONE;So;0;ON; 9AA8;;;;N;;;;; 2FBC;KANGXI RADICAL TALL;So;0;ON; 9AD8;;;;N;;;;; 2FBD;KANGXI RADICAL HAIR;So;0;ON; 9ADF;;;;N;;;;; 2FBE;KANGXI RADICAL FIGHT;So;0;ON; 9B25;;;;N;;;;; 2FBF;KANGXI RADICAL SACRIFICIAL WINE;So;0;ON; 9B2F;;;;N;;;;; 2FC0;KANGXI RADICAL CAULDRON;So;0;ON; 9B32;;;;N;;;;; 2FC1;KANGXI RADICAL GHOST;So;0;ON; 9B3C;;;;N;;;;; 2FC2;KANGXI RADICAL FISH;So;0;ON; 9B5A;;;;N;;;;; 2FC3;KANGXI RADICAL BIRD;So;0;ON; 9CE5;;;;N;;;;; 2FC4;KANGXI RADICAL SALT;So;0;ON; 9E75;;;;N;;;;; 2FC5;KANGXI RADICAL DEER;So;0;ON; 9E7F;;;;N;;;;; 2FC6;KANGXI RADICAL WHEAT;So;0;ON; 9EA5;;;;N;;;;; 2FC7;KANGXI RADICAL HEMP;So;0;ON; 9EBB;;;;N;;;;; 2FC8;KANGXI RADICAL YELLOW;So;0;ON; 9EC3;;;;N;;;;; 2FC9;KANGXI RADICAL MILLET;So;0;ON; 9ECD;;;;N;;;;; 2FCA;KANGXI RADICAL BLACK;So;0;ON; 9ED1;;;;N;;;;; 2FCB;KANGXI RADICAL EMBROIDERY;So;0;ON; 9EF9;;;;N;;;;; 2FCC;KANGXI RADICAL FROG;So;0;ON; 9EFD;;;;N;;;;; 2FCD;KANGXI RADICAL TRIPOD;So;0;ON; 9F0E;;;;N;;;;; 2FCE;KANGXI RADICAL DRUM;So;0;ON; 9F13;;;;N;;;;; 2FCF;KANGXI RADICAL RAT;So;0;ON; 9F20;;;;N;;;;; 2FD0;KANGXI RADICAL NOSE;So;0;ON; 9F3B;;;;N;;;;; 2FD1;KANGXI RADICAL EVEN;So;0;ON; 9F4A;;;;N;;;;; 2FD2;KANGXI RADICAL TOOTH;So;0;ON; 9F52;;;;N;;;;; 2FD3;KANGXI RADICAL DRAGON;So;0;ON; 9F8D;;;;N;;;;; 2FD4;KANGXI RADICAL TURTLE;So;0;ON; 9F9C;;;;N;;;;; 2FD5;KANGXI RADICAL FLUTE;So;0;ON; 9FA0;;;;N;;;;; 2FF0;IDEOGRAPHIC DESCRIPTION CHARACTER LEFT TO RIGHT;So;0;ON;;;;;N;;;;; 2FF1;IDEOGRAPHIC DESCRIPTION CHARACTER ABOVE TO BELOW;So;0;ON;;;;;N;;;;; 2FF2;IDEOGRAPHIC DESCRIPTION CHARACTER LEFT TO MIDDLE AND RIGHT;So;0;ON;;;;;N;;;;; 2FF3;IDEOGRAPHIC DESCRIPTION CHARACTER ABOVE TO MIDDLE AND BELOW;So;0;ON;;;;;N;;;;; 2FF4;IDEOGRAPHIC DESCRIPTION CHARACTER FULL SURROUND;So;0;ON;;;;;N;;;;; 2FF5;IDEOGRAPHIC DESCRIPTION CHARACTER SURROUND FROM ABOVE;So;0;ON;;;;;N;;;;; 2FF6;IDEOGRAPHIC DESCRIPTION CHARACTER SURROUND FROM BELOW;So;0;ON;;;;;N;;;;; 2FF7;IDEOGRAPHIC DESCRIPTION CHARACTER SURROUND FROM LEFT;So;0;ON;;;;;N;;;;; 2FF8;IDEOGRAPHIC DESCRIPTION CHARACTER SURROUND FROM UPPER LEFT;So;0;ON;;;;;N;;;;; 2FF9;IDEOGRAPHIC DESCRIPTION CHARACTER SURROUND FROM UPPER RIGHT;So;0;ON;;;;;N;;;;; 2FFA;IDEOGRAPHIC DESCRIPTION CHARACTER SURROUND FROM LOWER LEFT;So;0;ON;;;;;N;;;;; 2FFB;IDEOGRAPHIC DESCRIPTION CHARACTER OVERLAID;So;0;ON;;;;;N;;;;; 3000;IDEOGRAPHIC SPACE;Zs;0;WS; 0020;;;;N;;;;; 3001;IDEOGRAPHIC COMMA;Po;0;ON;;;;;N;;;;; 3002;IDEOGRAPHIC FULL STOP;Po;0;ON;;;;;N;IDEOGRAPHIC PERIOD;;;; 3003;DITTO MARK;Po;0;ON;;;;;N;;;;; 3004;JAPANESE INDUSTRIAL STANDARD SYMBOL;So;0;ON;;;;;N;;;;; 3005;IDEOGRAPHIC ITERATION MARK;Lm;0;L;;;;;N;;;;; 3006;IDEOGRAPHIC CLOSING MARK;Lo;0;L;;;;;N;;;;; 3007;IDEOGRAPHIC NUMBER ZERO;Nl;0;L;;;;0;N;;;;; 3008;LEFT ANGLE BRACKET;Ps;0;ON;;;;;Y;OPENING ANGLE BRACKET;;;; 3009;RIGHT ANGLE BRACKET;Pe;0;ON;;;;;Y;CLOSING ANGLE BRACKET;;;; 300A;LEFT DOUBLE ANGLE BRACKET;Ps;0;ON;;;;;Y;OPENING DOUBLE ANGLE BRACKET;;;; 300B;RIGHT DOUBLE ANGLE BRACKET;Pe;0;ON;;;;;Y;CLOSING DOUBLE ANGLE BRACKET;;;; 300C;LEFT CORNER BRACKET;Ps;0;ON;;;;;Y;OPENING CORNER BRACKET;;;; 300D;RIGHT CORNER BRACKET;Pe;0;ON;;;;;Y;CLOSING CORNER BRACKET;;;; 300E;LEFT WHITE CORNER BRACKET;Ps;0;ON;;;;;Y;OPENING WHITE CORNER BRACKET;;;; 300F;RIGHT WHITE CORNER BRACKET;Pe;0;ON;;;;;Y;CLOSING WHITE CORNER BRACKET;;;; 3010;LEFT BLACK LENTICULAR BRACKET;Ps;0;ON;;;;;Y;OPENING BLACK LENTICULAR BRACKET;;;; 3011;RIGHT BLACK LENTICULAR BRACKET;Pe;0;ON;;;;;Y;CLOSING BLACK LENTICULAR BRACKET;;;; 3012;POSTAL MARK;So;0;ON;;;;;N;;;;; 3013;GETA MARK;So;0;ON;;;;;N;;;;; 3014;LEFT TORTOISE SHELL BRACKET;Ps;0;ON;;;;;Y;OPENING TORTOISE SHELL BRACKET;;;; 3015;RIGHT TORTOISE SHELL BRACKET;Pe;0;ON;;;;;Y;CLOSING TORTOISE SHELL BRACKET;;;; 3016;LEFT WHITE LENTICULAR BRACKET;Ps;0;ON;;;;;Y;OPENING WHITE LENTICULAR BRACKET;;;; 3017;RIGHT WHITE LENTICULAR BRACKET;Pe;0;ON;;;;;Y;CLOSING WHITE LENTICULAR BRACKET;;;; 3018;LEFT WHITE TORTOISE SHELL BRACKET;Ps;0;ON;;;;;Y;OPENING WHITE TORTOISE SHELL BRACKET;;;; 3019;RIGHT WHITE TORTOISE SHELL BRACKET;Pe;0;ON;;;;;Y;CLOSING WHITE TORTOISE SHELL BRACKET;;;; 301A;LEFT WHITE SQUARE BRACKET;Ps;0;ON;;;;;Y;OPENING WHITE SQUARE BRACKET;;;; 301B;RIGHT WHITE SQUARE BRACKET;Pe;0;ON;;;;;Y;CLOSING WHITE SQUARE BRACKET;;;; 301C;WAVE DASH;Pd;0;ON;;;;;N;;;;; 301D;REVERSED DOUBLE PRIME QUOTATION MARK;Ps;0;ON;;;;;N;;;;; 301E;DOUBLE PRIME QUOTATION MARK;Pe;0;ON;;;;;N;;;;; 301F;LOW DOUBLE PRIME QUOTATION MARK;Pe;0;ON;;;;;N;;;;; 3020;POSTAL MARK FACE;So;0;ON;;;;;N;;;;; 3021;HANGZHOU NUMERAL ONE;Nl;0;L;;;;1;N;;;;; 3022;HANGZHOU NUMERAL TWO;Nl;0;L;;;;2;N;;;;; 3023;HANGZHOU NUMERAL THREE;Nl;0;L;;;;3;N;;;;; 3024;HANGZHOU NUMERAL FOUR;Nl;0;L;;;;4;N;;;;; 3025;HANGZHOU NUMERAL FIVE;Nl;0;L;;;;5;N;;;;; 3026;HANGZHOU NUMERAL SIX;Nl;0;L;;;;6;N;;;;; 3027;HANGZHOU NUMERAL SEVEN;Nl;0;L;;;;7;N;;;;; 3028;HANGZHOU NUMERAL EIGHT;Nl;0;L;;;;8;N;;;;; 3029;HANGZHOU NUMERAL NINE;Nl;0;L;;;;9;N;;;;; 302A;IDEOGRAPHIC LEVEL TONE MARK;Mn;218;NSM;;;;;N;;;;; 302B;IDEOGRAPHIC RISING TONE MARK;Mn;228;NSM;;;;;N;;;;; 302C;IDEOGRAPHIC DEPARTING TONE MARK;Mn;232;NSM;;;;;N;;;;; 302D;IDEOGRAPHIC ENTERING TONE MARK;Mn;222;NSM;;;;;N;;;;; 302E;HANGUL SINGLE DOT TONE MARK;Mc;224;L;;;;;N;;;;; 302F;HANGUL DOUBLE DOT TONE MARK;Mc;224;L;;;;;N;;;;; 3030;WAVY DASH;Pd;0;ON;;;;;N;;;;; 3031;VERTICAL KANA REPEAT MARK;Lm;0;L;;;;;N;;;;; 3032;VERTICAL KANA REPEAT WITH VOICED SOUND MARK;Lm;0;L;;;;;N;;;;; 3033;VERTICAL KANA REPEAT MARK UPPER HALF;Lm;0;L;;;;;N;;;;; 3034;VERTICAL KANA REPEAT WITH VOICED SOUND MARK UPPER HALF;Lm;0;L;;;;;N;;;;; 3035;VERTICAL KANA REPEAT MARK LOWER HALF;Lm;0;L;;;;;N;;;;; 3036;CIRCLED POSTAL MARK;So;0;ON; 3012;;;;N;;;;; 3037;IDEOGRAPHIC TELEGRAPH LINE FEED SEPARATOR SYMBOL;So;0;ON;;;;;N;;;;; 3038;HANGZHOU NUMERAL TEN;Nl;0;L; 5341;;;10;N;;;;; 3039;HANGZHOU NUMERAL TWENTY;Nl;0;L; 5344;;;20;N;;;;; 303A;HANGZHOU NUMERAL THIRTY;Nl;0;L; 5345;;;30;N;;;;; 303B;VERTICAL IDEOGRAPHIC ITERATION MARK;Lm;0;L;;;;;N;;;;; 303C;MASU MARK;Lo;0;L;;;;;N;;;;; 303D;PART ALTERNATION MARK;Po;0;ON;;;;;N;;;;; 303E;IDEOGRAPHIC VARIATION INDICATOR;So;0;ON;;;;;N;;;;; 303F;IDEOGRAPHIC HALF FILL SPACE;So;0;ON;;;;;N;;;;; 3041;HIRAGANA LETTER SMALL A;Lo;0;L;;;;;N;;;;; 3042;HIRAGANA LETTER A;Lo;0;L;;;;;N;;;;; 3043;HIRAGANA LETTER SMALL I;Lo;0;L;;;;;N;;;;; 3044;HIRAGANA LETTER I;Lo;0;L;;;;;N;;;;; 3045;HIRAGANA LETTER SMALL U;Lo;0;L;;;;;N;;;;; 3046;HIRAGANA LETTER U;Lo;0;L;;;;;N;;;;; 3047;HIRAGANA LETTER SMALL E;Lo;0;L;;;;;N;;;;; 3048;HIRAGANA LETTER E;Lo;0;L;;;;;N;;;;; 3049;HIRAGANA LETTER SMALL O;Lo;0;L;;;;;N;;;;; 304A;HIRAGANA LETTER O;Lo;0;L;;;;;N;;;;; 304B;HIRAGANA LETTER KA;Lo;0;L;;;;;N;;;;; 304C;HIRAGANA LETTER GA;Lo;0;L;304B 3099;;;;N;;;;; 304D;HIRAGANA LETTER KI;Lo;0;L;;;;;N;;;;; 304E;HIRAGANA LETTER GI;Lo;0;L;304D 3099;;;;N;;;;; 304F;HIRAGANA LETTER KU;Lo;0;L;;;;;N;;;;; 3050;HIRAGANA LETTER GU;Lo;0;L;304F 3099;;;;N;;;;; 3051;HIRAGANA LETTER KE;Lo;0;L;;;;;N;;;;; 3052;HIRAGANA LETTER GE;Lo;0;L;3051 3099;;;;N;;;;; 3053;HIRAGANA LETTER KO;Lo;0;L;;;;;N;;;;; 3054;HIRAGANA LETTER GO;Lo;0;L;3053 3099;;;;N;;;;; 3055;HIRAGANA LETTER SA;Lo;0;L;;;;;N;;;;; 3056;HIRAGANA LETTER ZA;Lo;0;L;3055 3099;;;;N;;;;; 3057;HIRAGANA LETTER SI;Lo;0;L;;;;;N;;;;; 3058;HIRAGANA LETTER ZI;Lo;0;L;3057 3099;;;;N;;;;; 3059;HIRAGANA LETTER SU;Lo;0;L;;;;;N;;;;; 305A;HIRAGANA LETTER ZU;Lo;0;L;3059 3099;;;;N;;;;; 305B;HIRAGANA LETTER SE;Lo;0;L;;;;;N;;;;; 305C;HIRAGANA LETTER ZE;Lo;0;L;305B 3099;;;;N;;;;; 305D;HIRAGANA LETTER SO;Lo;0;L;;;;;N;;;;; 305E;HIRAGANA LETTER ZO;Lo;0;L;305D 3099;;;;N;;;;; 305F;HIRAGANA LETTER TA;Lo;0;L;;;;;N;;;;; 3060;HIRAGANA LETTER DA;Lo;0;L;305F 3099;;;;N;;;;; 3061;HIRAGANA LETTER TI;Lo;0;L;;;;;N;;;;; 3062;HIRAGANA LETTER DI;Lo;0;L;3061 3099;;;;N;;;;; 3063;HIRAGANA LETTER SMALL TU;Lo;0;L;;;;;N;;;;; 3064;HIRAGANA LETTER TU;Lo;0;L;;;;;N;;;;; 3065;HIRAGANA LETTER DU;Lo;0;L;3064 3099;;;;N;;;;; 3066;HIRAGANA LETTER TE;Lo;0;L;;;;;N;;;;; 3067;HIRAGANA LETTER DE;Lo;0;L;3066 3099;;;;N;;;;; 3068;HIRAGANA LETTER TO;Lo;0;L;;;;;N;;;;; 3069;HIRAGANA LETTER DO;Lo;0;L;3068 3099;;;;N;;;;; 306A;HIRAGANA LETTER NA;Lo;0;L;;;;;N;;;;; 306B;HIRAGANA LETTER NI;Lo;0;L;;;;;N;;;;; 306C;HIRAGANA LETTER NU;Lo;0;L;;;;;N;;;;; 306D;HIRAGANA LETTER NE;Lo;0;L;;;;;N;;;;; 306E;HIRAGANA LETTER NO;Lo;0;L;;;;;N;;;;; 306F;HIRAGANA LETTER HA;Lo;0;L;;;;;N;;;;; 3070;HIRAGANA LETTER BA;Lo;0;L;306F 3099;;;;N;;;;; 3071;HIRAGANA LETTER PA;Lo;0;L;306F 309A;;;;N;;;;; 3072;HIRAGANA LETTER HI;Lo;0;L;;;;;N;;;;; 3073;HIRAGANA LETTER BI;Lo;0;L;3072 3099;;;;N;;;;; 3074;HIRAGANA LETTER PI;Lo;0;L;3072 309A;;;;N;;;;; 3075;HIRAGANA LETTER HU;Lo;0;L;;;;;N;;;;; 3076;HIRAGANA LETTER BU;Lo;0;L;3075 3099;;;;N;;;;; 3077;HIRAGANA LETTER PU;Lo;0;L;3075 309A;;;;N;;;;; 3078;HIRAGANA LETTER HE;Lo;0;L;;;;;N;;;;; 3079;HIRAGANA LETTER BE;Lo;0;L;3078 3099;;;;N;;;;; 307A;HIRAGANA LETTER PE;Lo;0;L;3078 309A;;;;N;;;;; 307B;HIRAGANA LETTER HO;Lo;0;L;;;;;N;;;;; 307C;HIRAGANA LETTER BO;Lo;0;L;307B 3099;;;;N;;;;; 307D;HIRAGANA LETTER PO;Lo;0;L;307B 309A;;;;N;;;;; 307E;HIRAGANA LETTER MA;Lo;0;L;;;;;N;;;;; 307F;HIRAGANA LETTER MI;Lo;0;L;;;;;N;;;;; 3080;HIRAGANA LETTER MU;Lo;0;L;;;;;N;;;;; 3081;HIRAGANA LETTER ME;Lo;0;L;;;;;N;;;;; 3082;HIRAGANA LETTER MO;Lo;0;L;;;;;N;;;;; 3083;HIRAGANA LETTER SMALL YA;Lo;0;L;;;;;N;;;;; 3084;HIRAGANA LETTER YA;Lo;0;L;;;;;N;;;;; 3085;HIRAGANA LETTER SMALL YU;Lo;0;L;;;;;N;;;;; 3086;HIRAGANA LETTER YU;Lo;0;L;;;;;N;;;;; 3087;HIRAGANA LETTER SMALL YO;Lo;0;L;;;;;N;;;;; 3088;HIRAGANA LETTER YO;Lo;0;L;;;;;N;;;;; 3089;HIRAGANA LETTER RA;Lo;0;L;;;;;N;;;;; 308A;HIRAGANA LETTER RI;Lo;0;L;;;;;N;;;;; 308B;HIRAGANA LETTER RU;Lo;0;L;;;;;N;;;;; 308C;HIRAGANA LETTER RE;Lo;0;L;;;;;N;;;;; 308D;HIRAGANA LETTER RO;Lo;0;L;;;;;N;;;;; 308E;HIRAGANA LETTER SMALL WA;Lo;0;L;;;;;N;;;;; 308F;HIRAGANA LETTER WA;Lo;0;L;;;;;N;;;;; 3090;HIRAGANA LETTER WI;Lo;0;L;;;;;N;;;;; 3091;HIRAGANA LETTER WE;Lo;0;L;;;;;N;;;;; 3092;HIRAGANA LETTER WO;Lo;0;L;;;;;N;;;;; 3093;HIRAGANA LETTER N;Lo;0;L;;;;;N;;;;; 3094;HIRAGANA LETTER VU;Lo;0;L;3046 3099;;;;N;;;;; 3095;HIRAGANA LETTER SMALL KA;Lo;0;L;;;;;N;;;;; 3096;HIRAGANA LETTER SMALL KE;Lo;0;L;;;;;N;;;;; 3099;COMBINING KATAKANA-HIRAGANA VOICED SOUND MARK;Mn;8;NSM;;;;;N;NON-SPACING KATAKANA-HIRAGANA VOICED SOUND MARK;;;; 309A;COMBINING KATAKANA-HIRAGANA SEMI-VOICED SOUND MARK;Mn;8;NSM;;;;;N;NON-SPACING KATAKANA-HIRAGANA SEMI-VOICED SOUND MARK;;;; 309B;KATAKANA-HIRAGANA VOICED SOUND MARK;Sk;0;ON; 0020 3099;;;;N;;;;; 309C;KATAKANA-HIRAGANA SEMI-VOICED SOUND MARK;Sk;0;ON; 0020 309A;;;;N;;;;; 309D;HIRAGANA ITERATION MARK;Lm;0;L;;;;;N;;;;; 309E;HIRAGANA VOICED ITERATION MARK;Lm;0;L;309D 3099;;;;N;;;;; 309F;HIRAGANA DIGRAPH YORI;Lo;0;L; 3088 308A;;;;N;;;;; 30A0;KATAKANA-HIRAGANA DOUBLE HYPHEN;Pd;0;ON;;;;;N;;;;; 30A1;KATAKANA LETTER SMALL A;Lo;0;L;;;;;N;;;;; 30A2;KATAKANA LETTER A;Lo;0;L;;;;;N;;;;; 30A3;KATAKANA LETTER SMALL I;Lo;0;L;;;;;N;;;;; 30A4;KATAKANA LETTER I;Lo;0;L;;;;;N;;;;; 30A5;KATAKANA LETTER SMALL U;Lo;0;L;;;;;N;;;;; 30A6;KATAKANA LETTER U;Lo;0;L;;;;;N;;;;; 30A7;KATAKANA LETTER SMALL E;Lo;0;L;;;;;N;;;;; 30A8;KATAKANA LETTER E;Lo;0;L;;;;;N;;;;; 30A9;KATAKANA LETTER SMALL O;Lo;0;L;;;;;N;;;;; 30AA;KATAKANA LETTER O;Lo;0;L;;;;;N;;;;; 30AB;KATAKANA LETTER KA;Lo;0;L;;;;;N;;;;; 30AC;KATAKANA LETTER GA;Lo;0;L;30AB 3099;;;;N;;;;; 30AD;KATAKANA LETTER KI;Lo;0;L;;;;;N;;;;; 30AE;KATAKANA LETTER GI;Lo;0;L;30AD 3099;;;;N;;;;; 30AF;KATAKANA LETTER KU;Lo;0;L;;;;;N;;;;; 30B0;KATAKANA LETTER GU;Lo;0;L;30AF 3099;;;;N;;;;; 30B1;KATAKANA LETTER KE;Lo;0;L;;;;;N;;;;; 30B2;KATAKANA LETTER GE;Lo;0;L;30B1 3099;;;;N;;;;; 30B3;KATAKANA LETTER KO;Lo;0;L;;;;;N;;;;; 30B4;KATAKANA LETTER GO;Lo;0;L;30B3 3099;;;;N;;;;; 30B5;KATAKANA LETTER SA;Lo;0;L;;;;;N;;;;; 30B6;KATAKANA LETTER ZA;Lo;0;L;30B5 3099;;;;N;;;;; 30B7;KATAKANA LETTER SI;Lo;0;L;;;;;N;;;;; 30B8;KATAKANA LETTER ZI;Lo;0;L;30B7 3099;;;;N;;;;; 30B9;KATAKANA LETTER SU;Lo;0;L;;;;;N;;;;; 30BA;KATAKANA LETTER ZU;Lo;0;L;30B9 3099;;;;N;;;;; 30BB;KATAKANA LETTER SE;Lo;0;L;;;;;N;;;;; 30BC;KATAKANA LETTER ZE;Lo;0;L;30BB 3099;;;;N;;;;; 30BD;KATAKANA LETTER SO;Lo;0;L;;;;;N;;;;; 30BE;KATAKANA LETTER ZO;Lo;0;L;30BD 3099;;;;N;;;;; 30BF;KATAKANA LETTER TA;Lo;0;L;;;;;N;;;;; 30C0;KATAKANA LETTER DA;Lo;0;L;30BF 3099;;;;N;;;;; 30C1;KATAKANA LETTER TI;Lo;0;L;;;;;N;;;;; 30C2;KATAKANA LETTER DI;Lo;0;L;30C1 3099;;;;N;;;;; 30C3;KATAKANA LETTER SMALL TU;Lo;0;L;;;;;N;;;;; 30C4;KATAKANA LETTER TU;Lo;0;L;;;;;N;;;;; 30C5;KATAKANA LETTER DU;Lo;0;L;30C4 3099;;;;N;;;;; 30C6;KATAKANA LETTER TE;Lo;0;L;;;;;N;;;;; 30C7;KATAKANA LETTER DE;Lo;0;L;30C6 3099;;;;N;;;;; 30C8;KATAKANA LETTER TO;Lo;0;L;;;;;N;;;;; 30C9;KATAKANA LETTER DO;Lo;0;L;30C8 3099;;;;N;;;;; 30CA;KATAKANA LETTER NA;Lo;0;L;;;;;N;;;;; 30CB;KATAKANA LETTER NI;Lo;0;L;;;;;N;;;;; 30CC;KATAKANA LETTER NU;Lo;0;L;;;;;N;;;;; 30CD;KATAKANA LETTER NE;Lo;0;L;;;;;N;;;;; 30CE;KATAKANA LETTER NO;Lo;0;L;;;;;N;;;;; 30CF;KATAKANA LETTER HA;Lo;0;L;;;;;N;;;;; 30D0;KATAKANA LETTER BA;Lo;0;L;30CF 3099;;;;N;;;;; 30D1;KATAKANA LETTER PA;Lo;0;L;30CF 309A;;;;N;;;;; 30D2;KATAKANA LETTER HI;Lo;0;L;;;;;N;;;;; 30D3;KATAKANA LETTER BI;Lo;0;L;30D2 3099;;;;N;;;;; 30D4;KATAKANA LETTER PI;Lo;0;L;30D2 309A;;;;N;;;;; 30D5;KATAKANA LETTER HU;Lo;0;L;;;;;N;;;;; 30D6;KATAKANA LETTER BU;Lo;0;L;30D5 3099;;;;N;;;;; 30D7;KATAKANA LETTER PU;Lo;0;L;30D5 309A;;;;N;;;;; 30D8;KATAKANA LETTER HE;Lo;0;L;;;;;N;;;;; 30D9;KATAKANA LETTER BE;Lo;0;L;30D8 3099;;;;N;;;;; 30DA;KATAKANA LETTER PE;Lo;0;L;30D8 309A;;;;N;;;;; 30DB;KATAKANA LETTER HO;Lo;0;L;;;;;N;;;;; 30DC;KATAKANA LETTER BO;Lo;0;L;30DB 3099;;;;N;;;;; 30DD;KATAKANA LETTER PO;Lo;0;L;30DB 309A;;;;N;;;;; 30DE;KATAKANA LETTER MA;Lo;0;L;;;;;N;;;;; 30DF;KATAKANA LETTER MI;Lo;0;L;;;;;N;;;;; 30E0;KATAKANA LETTER MU;Lo;0;L;;;;;N;;;;; 30E1;KATAKANA LETTER ME;Lo;0;L;;;;;N;;;;; 30E2;KATAKANA LETTER MO;Lo;0;L;;;;;N;;;;; 30E3;KATAKANA LETTER SMALL YA;Lo;0;L;;;;;N;;;;; 30E4;KATAKANA LETTER YA;Lo;0;L;;;;;N;;;;; 30E5;KATAKANA LETTER SMALL YU;Lo;0;L;;;;;N;;;;; 30E6;KATAKANA LETTER YU;Lo;0;L;;;;;N;;;;; 30E7;KATAKANA LETTER SMALL YO;Lo;0;L;;;;;N;;;;; 30E8;KATAKANA LETTER YO;Lo;0;L;;;;;N;;;;; 30E9;KATAKANA LETTER RA;Lo;0;L;;;;;N;;;;; 30EA;KATAKANA LETTER RI;Lo;0;L;;;;;N;;;;; 30EB;KATAKANA LETTER RU;Lo;0;L;;;;;N;;;;; 30EC;KATAKANA LETTER RE;Lo;0;L;;;;;N;;;;; 30ED;KATAKANA LETTER RO;Lo;0;L;;;;;N;;;;; 30EE;KATAKANA LETTER SMALL WA;Lo;0;L;;;;;N;;;;; 30EF;KATAKANA LETTER WA;Lo;0;L;;;;;N;;;;; 30F0;KATAKANA LETTER WI;Lo;0;L;;;;;N;;;;; 30F1;KATAKANA LETTER WE;Lo;0;L;;;;;N;;;;; 30F2;KATAKANA LETTER WO;Lo;0;L;;;;;N;;;;; 30F3;KATAKANA LETTER N;Lo;0;L;;;;;N;;;;; 30F4;KATAKANA LETTER VU;Lo;0;L;30A6 3099;;;;N;;;;; 30F5;KATAKANA LETTER SMALL KA;Lo;0;L;;;;;N;;;;; 30F6;KATAKANA LETTER SMALL KE;Lo;0;L;;;;;N;;;;; 30F7;KATAKANA LETTER VA;Lo;0;L;30EF 3099;;;;N;;;;; 30F8;KATAKANA LETTER VI;Lo;0;L;30F0 3099;;;;N;;;;; 30F9;KATAKANA LETTER VE;Lo;0;L;30F1 3099;;;;N;;;;; 30FA;KATAKANA LETTER VO;Lo;0;L;30F2 3099;;;;N;;;;; 30FB;KATAKANA MIDDLE DOT;Po;0;ON;;;;;N;;;;; 30FC;KATAKANA-HIRAGANA PROLONGED SOUND MARK;Lm;0;L;;;;;N;;;;; 30FD;KATAKANA ITERATION MARK;Lm;0;L;;;;;N;;;;; 30FE;KATAKANA VOICED ITERATION MARK;Lm;0;L;30FD 3099;;;;N;;;;; 30FF;KATAKANA DIGRAPH KOTO;Lo;0;L; 30B3 30C8;;;;N;;;;; 3105;BOPOMOFO LETTER B;Lo;0;L;;;;;N;;;;; 3106;BOPOMOFO LETTER P;Lo;0;L;;;;;N;;;;; 3107;BOPOMOFO LETTER M;Lo;0;L;;;;;N;;;;; 3108;BOPOMOFO LETTER F;Lo;0;L;;;;;N;;;;; 3109;BOPOMOFO LETTER D;Lo;0;L;;;;;N;;;;; 310A;BOPOMOFO LETTER T;Lo;0;L;;;;;N;;;;; 310B;BOPOMOFO LETTER N;Lo;0;L;;;;;N;;;;; 310C;BOPOMOFO LETTER L;Lo;0;L;;;;;N;;;;; 310D;BOPOMOFO LETTER G;Lo;0;L;;;;;N;;;;; 310E;BOPOMOFO LETTER K;Lo;0;L;;;;;N;;;;; 310F;BOPOMOFO LETTER H;Lo;0;L;;;;;N;;;;; 3110;BOPOMOFO LETTER J;Lo;0;L;;;;;N;;;;; 3111;BOPOMOFO LETTER Q;Lo;0;L;;;;;N;;;;; 3112;BOPOMOFO LETTER X;Lo;0;L;;;;;N;;;;; 3113;BOPOMOFO LETTER ZH;Lo;0;L;;;;;N;;;;; 3114;BOPOMOFO LETTER CH;Lo;0;L;;;;;N;;;;; 3115;BOPOMOFO LETTER SH;Lo;0;L;;;;;N;;;;; 3116;BOPOMOFO LETTER R;Lo;0;L;;;;;N;;;;; 3117;BOPOMOFO LETTER Z;Lo;0;L;;;;;N;;;;; 3118;BOPOMOFO LETTER C;Lo;0;L;;;;;N;;;;; 3119;BOPOMOFO LETTER S;Lo;0;L;;;;;N;;;;; 311A;BOPOMOFO LETTER A;Lo;0;L;;;;;N;;;;; 311B;BOPOMOFO LETTER O;Lo;0;L;;;;;N;;;;; 311C;BOPOMOFO LETTER E;Lo;0;L;;;;;N;;;;; 311D;BOPOMOFO LETTER EH;Lo;0;L;;;;;N;;;;; 311E;BOPOMOFO LETTER AI;Lo;0;L;;;;;N;;;;; 311F;BOPOMOFO LETTER EI;Lo;0;L;;;;;N;;;;; 3120;BOPOMOFO LETTER AU;Lo;0;L;;;;;N;;;;; 3121;BOPOMOFO LETTER OU;Lo;0;L;;;;;N;;;;; 3122;BOPOMOFO LETTER AN;Lo;0;L;;;;;N;;;;; 3123;BOPOMOFO LETTER EN;Lo;0;L;;;;;N;;;;; 3124;BOPOMOFO LETTER ANG;Lo;0;L;;;;;N;;;;; 3125;BOPOMOFO LETTER ENG;Lo;0;L;;;;;N;;;;; 3126;BOPOMOFO LETTER ER;Lo;0;L;;;;;N;;;;; 3127;BOPOMOFO LETTER I;Lo;0;L;;;;;N;;;;; 3128;BOPOMOFO LETTER U;Lo;0;L;;;;;N;;;;; 3129;BOPOMOFO LETTER IU;Lo;0;L;;;;;N;;;;; 312A;BOPOMOFO LETTER V;Lo;0;L;;;;;N;;;;; 312B;BOPOMOFO LETTER NG;Lo;0;L;;;;;N;;;;; 312C;BOPOMOFO LETTER GN;Lo;0;L;;;;;N;;;;; 312D;BOPOMOFO LETTER IH;Lo;0;L;;;;;N;;;;; 3131;HANGUL LETTER KIYEOK;Lo;0;L; 1100;;;;N;HANGUL LETTER GIYEOG;;;; 3132;HANGUL LETTER SSANGKIYEOK;Lo;0;L; 1101;;;;N;HANGUL LETTER SSANG GIYEOG;;;; 3133;HANGUL LETTER KIYEOK-SIOS;Lo;0;L; 11AA;;;;N;HANGUL LETTER GIYEOG SIOS;;;; 3134;HANGUL LETTER NIEUN;Lo;0;L; 1102;;;;N;;;;; 3135;HANGUL LETTER NIEUN-CIEUC;Lo;0;L; 11AC;;;;N;HANGUL LETTER NIEUN JIEUJ;;;; 3136;HANGUL LETTER NIEUN-HIEUH;Lo;0;L; 11AD;;;;N;HANGUL LETTER NIEUN HIEUH;;;; 3137;HANGUL LETTER TIKEUT;Lo;0;L; 1103;;;;N;HANGUL LETTER DIGEUD;;;; 3138;HANGUL LETTER SSANGTIKEUT;Lo;0;L; 1104;;;;N;HANGUL LETTER SSANG DIGEUD;;;; 3139;HANGUL LETTER RIEUL;Lo;0;L; 1105;;;;N;HANGUL LETTER LIEUL;;;; 313A;HANGUL LETTER RIEUL-KIYEOK;Lo;0;L; 11B0;;;;N;HANGUL LETTER LIEUL GIYEOG;;;; 313B;HANGUL LETTER RIEUL-MIEUM;Lo;0;L; 11B1;;;;N;HANGUL LETTER LIEUL MIEUM;;;; 313C;HANGUL LETTER RIEUL-PIEUP;Lo;0;L; 11B2;;;;N;HANGUL LETTER LIEUL BIEUB;;;; 313D;HANGUL LETTER RIEUL-SIOS;Lo;0;L; 11B3;;;;N;HANGUL LETTER LIEUL SIOS;;;; 313E;HANGUL LETTER RIEUL-THIEUTH;Lo;0;L; 11B4;;;;N;HANGUL LETTER LIEUL TIEUT;;;; 313F;HANGUL LETTER RIEUL-PHIEUPH;Lo;0;L; 11B5;;;;N;HANGUL LETTER LIEUL PIEUP;;;; 3140;HANGUL LETTER RIEUL-HIEUH;Lo;0;L; 111A;;;;N;HANGUL LETTER LIEUL HIEUH;;;; 3141;HANGUL LETTER MIEUM;Lo;0;L; 1106;;;;N;;;;; 3142;HANGUL LETTER PIEUP;Lo;0;L; 1107;;;;N;HANGUL LETTER BIEUB;;;; 3143;HANGUL LETTER SSANGPIEUP;Lo;0;L; 1108;;;;N;HANGUL LETTER SSANG BIEUB;;;; 3144;HANGUL LETTER PIEUP-SIOS;Lo;0;L; 1121;;;;N;HANGUL LETTER BIEUB SIOS;;;; 3145;HANGUL LETTER SIOS;Lo;0;L; 1109;;;;N;;;;; 3146;HANGUL LETTER SSANGSIOS;Lo;0;L; 110A;;;;N;HANGUL LETTER SSANG SIOS;;;; 3147;HANGUL LETTER IEUNG;Lo;0;L; 110B;;;;N;;;;; 3148;HANGUL LETTER CIEUC;Lo;0;L; 110C;;;;N;HANGUL LETTER JIEUJ;;;; 3149;HANGUL LETTER SSANGCIEUC;Lo;0;L; 110D;;;;N;HANGUL LETTER SSANG JIEUJ;;;; 314A;HANGUL LETTER CHIEUCH;Lo;0;L; 110E;;;;N;HANGUL LETTER CIEUC;;;; 314B;HANGUL LETTER KHIEUKH;Lo;0;L; 110F;;;;N;HANGUL LETTER KIYEOK;;;; 314C;HANGUL LETTER THIEUTH;Lo;0;L; 1110;;;;N;HANGUL LETTER TIEUT;;;; 314D;HANGUL LETTER PHIEUPH;Lo;0;L; 1111;;;;N;HANGUL LETTER PIEUP;;;; 314E;HANGUL LETTER HIEUH;Lo;0;L; 1112;;;;N;;;;; 314F;HANGUL LETTER A;Lo;0;L; 1161;;;;N;;;;; 3150;HANGUL LETTER AE;Lo;0;L; 1162;;;;N;;;;; 3151;HANGUL LETTER YA;Lo;0;L; 1163;;;;N;;;;; 3152;HANGUL LETTER YAE;Lo;0;L; 1164;;;;N;;;;; 3153;HANGUL LETTER EO;Lo;0;L; 1165;;;;N;;;;; 3154;HANGUL LETTER E;Lo;0;L; 1166;;;;N;;;;; 3155;HANGUL LETTER YEO;Lo;0;L; 1167;;;;N;;;;; 3156;HANGUL LETTER YE;Lo;0;L; 1168;;;;N;;;;; 3157;HANGUL LETTER O;Lo;0;L; 1169;;;;N;;;;; 3158;HANGUL LETTER WA;Lo;0;L; 116A;;;;N;;;;; 3159;HANGUL LETTER WAE;Lo;0;L; 116B;;;;N;;;;; 315A;HANGUL LETTER OE;Lo;0;L; 116C;;;;N;;;;; 315B;HANGUL LETTER YO;Lo;0;L; 116D;;;;N;;;;; 315C;HANGUL LETTER U;Lo;0;L; 116E;;;;N;;;;; 315D;HANGUL LETTER WEO;Lo;0;L; 116F;;;;N;;;;; 315E;HANGUL LETTER WE;Lo;0;L; 1170;;;;N;;;;; 315F;HANGUL LETTER WI;Lo;0;L; 1171;;;;N;;;;; 3160;HANGUL LETTER YU;Lo;0;L; 1172;;;;N;;;;; 3161;HANGUL LETTER EU;Lo;0;L; 1173;;;;N;;;;; 3162;HANGUL LETTER YI;Lo;0;L; 1174;;;;N;;;;; 3163;HANGUL LETTER I;Lo;0;L; 1175;;;;N;;;;; 3164;HANGUL FILLER;Lo;0;L; 1160;;;;N;HANGUL CAE OM;;;; 3165;HANGUL LETTER SSANGNIEUN;Lo;0;L; 1114;;;;N;HANGUL LETTER SSANG NIEUN;;;; 3166;HANGUL LETTER NIEUN-TIKEUT;Lo;0;L; 1115;;;;N;HANGUL LETTER NIEUN DIGEUD;;;; 3167;HANGUL LETTER NIEUN-SIOS;Lo;0;L; 11C7;;;;N;HANGUL LETTER NIEUN SIOS;;;; 3168;HANGUL LETTER NIEUN-PANSIOS;Lo;0;L; 11C8;;;;N;HANGUL LETTER NIEUN BAN CHI EUM;;;; 3169;HANGUL LETTER RIEUL-KIYEOK-SIOS;Lo;0;L; 11CC;;;;N;HANGUL LETTER LIEUL GIYEOG SIOS;;;; 316A;HANGUL LETTER RIEUL-TIKEUT;Lo;0;L; 11CE;;;;N;HANGUL LETTER LIEUL DIGEUD;;;; 316B;HANGUL LETTER RIEUL-PIEUP-SIOS;Lo;0;L; 11D3;;;;N;HANGUL LETTER LIEUL BIEUB SIOS;;;; 316C;HANGUL LETTER RIEUL-PANSIOS;Lo;0;L; 11D7;;;;N;HANGUL LETTER LIEUL BAN CHI EUM;;;; 316D;HANGUL LETTER RIEUL-YEORINHIEUH;Lo;0;L; 11D9;;;;N;HANGUL LETTER LIEUL YEOLIN HIEUH;;;; 316E;HANGUL LETTER MIEUM-PIEUP;Lo;0;L; 111C;;;;N;HANGUL LETTER MIEUM BIEUB;;;; 316F;HANGUL LETTER MIEUM-SIOS;Lo;0;L; 11DD;;;;N;HANGUL LETTER MIEUM SIOS;;;; 3170;HANGUL LETTER MIEUM-PANSIOS;Lo;0;L; 11DF;;;;N;HANGUL LETTER BIEUB BAN CHI EUM;;;; 3171;HANGUL LETTER KAPYEOUNMIEUM;Lo;0;L; 111D;;;;N;HANGUL LETTER MIEUM SUN GYEONG EUM;;;; 3172;HANGUL LETTER PIEUP-KIYEOK;Lo;0;L; 111E;;;;N;HANGUL LETTER BIEUB GIYEOG;;;; 3173;HANGUL LETTER PIEUP-TIKEUT;Lo;0;L; 1120;;;;N;HANGUL LETTER BIEUB DIGEUD;;;; 3174;HANGUL LETTER PIEUP-SIOS-KIYEOK;Lo;0;L; 1122;;;;N;HANGUL LETTER BIEUB SIOS GIYEOG;;;; 3175;HANGUL LETTER PIEUP-SIOS-TIKEUT;Lo;0;L; 1123;;;;N;HANGUL LETTER BIEUB SIOS DIGEUD;;;; 3176;HANGUL LETTER PIEUP-CIEUC;Lo;0;L; 1127;;;;N;HANGUL LETTER BIEUB JIEUJ;;;; 3177;HANGUL LETTER PIEUP-THIEUTH;Lo;0;L; 1129;;;;N;HANGUL LETTER BIEUB TIEUT;;;; 3178;HANGUL LETTER KAPYEOUNPIEUP;Lo;0;L; 112B;;;;N;HANGUL LETTER BIEUB SUN GYEONG EUM;;;; 3179;HANGUL LETTER KAPYEOUNSSANGPIEUP;Lo;0;L; 112C;;;;N;HANGUL LETTER SSANG BIEUB SUN GYEONG EUM;;;; 317A;HANGUL LETTER SIOS-KIYEOK;Lo;0;L; 112D;;;;N;HANGUL LETTER SIOS GIYEOG;;;; 317B;HANGUL LETTER SIOS-NIEUN;Lo;0;L; 112E;;;;N;HANGUL LETTER SIOS NIEUN;;;; 317C;HANGUL LETTER SIOS-TIKEUT;Lo;0;L; 112F;;;;N;HANGUL LETTER SIOS DIGEUD;;;; 317D;HANGUL LETTER SIOS-PIEUP;Lo;0;L; 1132;;;;N;HANGUL LETTER SIOS BIEUB;;;; 317E;HANGUL LETTER SIOS-CIEUC;Lo;0;L; 1136;;;;N;HANGUL LETTER SIOS JIEUJ;;;; 317F;HANGUL LETTER PANSIOS;Lo;0;L; 1140;;;;N;HANGUL LETTER BAN CHI EUM;;;; 3180;HANGUL LETTER SSANGIEUNG;Lo;0;L; 1147;;;;N;HANGUL LETTER SSANG IEUNG;;;; 3181;HANGUL LETTER YESIEUNG;Lo;0;L; 114C;;;;N;HANGUL LETTER NGIEUNG;;;; 3182;HANGUL LETTER YESIEUNG-SIOS;Lo;0;L; 11F1;;;;N;HANGUL LETTER NGIEUNG SIOS;;;; 3183;HANGUL LETTER YESIEUNG-PANSIOS;Lo;0;L; 11F2;;;;N;HANGUL LETTER NGIEUNG BAN CHI EUM;;;; 3184;HANGUL LETTER KAPYEOUNPHIEUPH;Lo;0;L; 1157;;;;N;HANGUL LETTER PIEUP SUN GYEONG EUM;;;; 3185;HANGUL LETTER SSANGHIEUH;Lo;0;L; 1158;;;;N;HANGUL LETTER SSANG HIEUH;;;; 3186;HANGUL LETTER YEORINHIEUH;Lo;0;L; 1159;;;;N;HANGUL LETTER YEOLIN HIEUH;;;; 3187;HANGUL LETTER YO-YA;Lo;0;L; 1184;;;;N;HANGUL LETTER YOYA;;;; 3188;HANGUL LETTER YO-YAE;Lo;0;L; 1185;;;;N;HANGUL LETTER YOYAE;;;; 3189;HANGUL LETTER YO-I;Lo;0;L; 1188;;;;N;HANGUL LETTER YOI;;;; 318A;HANGUL LETTER YU-YEO;Lo;0;L; 1191;;;;N;HANGUL LETTER YUYEO;;;; 318B;HANGUL LETTER YU-YE;Lo;0;L; 1192;;;;N;HANGUL LETTER YUYE;;;; 318C;HANGUL LETTER YU-I;Lo;0;L; 1194;;;;N;HANGUL LETTER YUI;;;; 318D;HANGUL LETTER ARAEA;Lo;0;L; 119E;;;;N;HANGUL LETTER ALAE A;;;; 318E;HANGUL LETTER ARAEAE;Lo;0;L; 11A1;;;;N;HANGUL LETTER ALAE AE;;;; 3190;IDEOGRAPHIC ANNOTATION LINKING MARK;So;0;L;;;;;N;KANBUN TATETEN;;;; 3191;IDEOGRAPHIC ANNOTATION REVERSE MARK;So;0;L;;;;;N;KAERITEN RE;;;; 3192;IDEOGRAPHIC ANNOTATION ONE MARK;No;0;L; 4E00;;;1;N;KAERITEN ITI;;;; 3193;IDEOGRAPHIC ANNOTATION TWO MARK;No;0;L; 4E8C;;;2;N;KAERITEN NI;;;; 3194;IDEOGRAPHIC ANNOTATION THREE MARK;No;0;L; 4E09;;;3;N;KAERITEN SAN;;;; 3195;IDEOGRAPHIC ANNOTATION FOUR MARK;No;0;L; 56DB;;;4;N;KAERITEN SI;;;; 3196;IDEOGRAPHIC ANNOTATION TOP MARK;So;0;L; 4E0A;;;;N;KAERITEN ZYOU;;;; 3197;IDEOGRAPHIC ANNOTATION MIDDLE MARK;So;0;L; 4E2D;;;;N;KAERITEN TYUU;;;; 3198;IDEOGRAPHIC ANNOTATION BOTTOM MARK;So;0;L; 4E0B;;;;N;KAERITEN GE;;;; 3199;IDEOGRAPHIC ANNOTATION FIRST MARK;So;0;L; 7532;;;;N;KAERITEN KOU;;;; 319A;IDEOGRAPHIC ANNOTATION SECOND MARK;So;0;L; 4E59;;;;N;KAERITEN OTU;;;; 319B;IDEOGRAPHIC ANNOTATION THIRD MARK;So;0;L; 4E19;;;;N;KAERITEN HEI;;;; 319C;IDEOGRAPHIC ANNOTATION FOURTH MARK;So;0;L; 4E01;;;;N;KAERITEN TEI;;;; 319D;IDEOGRAPHIC ANNOTATION HEAVEN MARK;So;0;L; 5929;;;;N;KAERITEN TEN;;;; 319E;IDEOGRAPHIC ANNOTATION EARTH MARK;So;0;L; 5730;;;;N;KAERITEN TI;;;; 319F;IDEOGRAPHIC ANNOTATION MAN MARK;So;0;L; 4EBA;;;;N;KAERITEN ZIN;;;; 31A0;BOPOMOFO LETTER BU;Lo;0;L;;;;;N;;;;; 31A1;BOPOMOFO LETTER ZI;Lo;0;L;;;;;N;;;;; 31A2;BOPOMOFO LETTER JI;Lo;0;L;;;;;N;;;;; 31A3;BOPOMOFO LETTER GU;Lo;0;L;;;;;N;;;;; 31A4;BOPOMOFO LETTER EE;Lo;0;L;;;;;N;;;;; 31A5;BOPOMOFO LETTER ENN;Lo;0;L;;;;;N;;;;; 31A6;BOPOMOFO LETTER OO;Lo;0;L;;;;;N;;;;; 31A7;BOPOMOFO LETTER ONN;Lo;0;L;;;;;N;;;;; 31A8;BOPOMOFO LETTER IR;Lo;0;L;;;;;N;;;;; 31A9;BOPOMOFO LETTER ANN;Lo;0;L;;;;;N;;;;; 31AA;BOPOMOFO LETTER INN;Lo;0;L;;;;;N;;;;; 31AB;BOPOMOFO LETTER UNN;Lo;0;L;;;;;N;;;;; 31AC;BOPOMOFO LETTER IM;Lo;0;L;;;;;N;;;;; 31AD;BOPOMOFO LETTER NGG;Lo;0;L;;;;;N;;;;; 31AE;BOPOMOFO LETTER AINN;Lo;0;L;;;;;N;;;;; 31AF;BOPOMOFO LETTER AUNN;Lo;0;L;;;;;N;;;;; 31B0;BOPOMOFO LETTER AM;Lo;0;L;;;;;N;;;;; 31B1;BOPOMOFO LETTER OM;Lo;0;L;;;;;N;;;;; 31B2;BOPOMOFO LETTER ONG;Lo;0;L;;;;;N;;;;; 31B3;BOPOMOFO LETTER INNN;Lo;0;L;;;;;N;;;;; 31B4;BOPOMOFO FINAL LETTER P;Lo;0;L;;;;;N;;;;; 31B5;BOPOMOFO FINAL LETTER T;Lo;0;L;;;;;N;;;;; 31B6;BOPOMOFO FINAL LETTER K;Lo;0;L;;;;;N;;;;; 31B7;BOPOMOFO FINAL LETTER H;Lo;0;L;;;;;N;;;;; 31B8;BOPOMOFO LETTER GH;Lo;0;L;;;;;N;;;;; 31B9;BOPOMOFO LETTER LH;Lo;0;L;;;;;N;;;;; 31BA;BOPOMOFO LETTER ZY;Lo;0;L;;;;;N;;;;; 31C0;CJK STROKE T;So;0;ON;;;;;N;;;;; 31C1;CJK STROKE WG;So;0;ON;;;;;N;;;;; 31C2;CJK STROKE XG;So;0;ON;;;;;N;;;;; 31C3;CJK STROKE BXG;So;0;ON;;;;;N;;;;; 31C4;CJK STROKE SW;So;0;ON;;;;;N;;;;; 31C5;CJK STROKE HZZ;So;0;ON;;;;;N;;;;; 31C6;CJK STROKE HZG;So;0;ON;;;;;N;;;;; 31C7;CJK STROKE HP;So;0;ON;;;;;N;;;;; 31C8;CJK STROKE HZWG;So;0;ON;;;;;N;;;;; 31C9;CJK STROKE SZWG;So;0;ON;;;;;N;;;;; 31CA;CJK STROKE HZT;So;0;ON;;;;;N;;;;; 31CB;CJK STROKE HZZP;So;0;ON;;;;;N;;;;; 31CC;CJK STROKE HPWG;So;0;ON;;;;;N;;;;; 31CD;CJK STROKE HZW;So;0;ON;;;;;N;;;;; 31CE;CJK STROKE HZZZ;So;0;ON;;;;;N;;;;; 31CF;CJK STROKE N;So;0;ON;;;;;N;;;;; 31D0;CJK STROKE H;So;0;ON;;;;;N;;;;; 31D1;CJK STROKE S;So;0;ON;;;;;N;;;;; 31D2;CJK STROKE P;So;0;ON;;;;;N;;;;; 31D3;CJK STROKE SP;So;0;ON;;;;;N;;;;; 31D4;CJK STROKE D;So;0;ON;;;;;N;;;;; 31D5;CJK STROKE HZ;So;0;ON;;;;;N;;;;; 31D6;CJK STROKE HG;So;0;ON;;;;;N;;;;; 31D7;CJK STROKE SZ;So;0;ON;;;;;N;;;;; 31D8;CJK STROKE SWZ;So;0;ON;;;;;N;;;;; 31D9;CJK STROKE ST;So;0;ON;;;;;N;;;;; 31DA;CJK STROKE SG;So;0;ON;;;;;N;;;;; 31DB;CJK STROKE PD;So;0;ON;;;;;N;;;;; 31DC;CJK STROKE PZ;So;0;ON;;;;;N;;;;; 31DD;CJK STROKE TN;So;0;ON;;;;;N;;;;; 31DE;CJK STROKE SZZ;So;0;ON;;;;;N;;;;; 31DF;CJK STROKE SWG;So;0;ON;;;;;N;;;;; 31E0;CJK STROKE HXWG;So;0;ON;;;;;N;;;;; 31E1;CJK STROKE HZZZG;So;0;ON;;;;;N;;;;; 31E2;CJK STROKE PG;So;0;ON;;;;;N;;;;; 31E3;CJK STROKE Q;So;0;ON;;;;;N;;;;; 31F0;KATAKANA LETTER SMALL KU;Lo;0;L;;;;;N;;;;; 31F1;KATAKANA LETTER SMALL SI;Lo;0;L;;;;;N;;;;; 31F2;KATAKANA LETTER SMALL SU;Lo;0;L;;;;;N;;;;; 31F3;KATAKANA LETTER SMALL TO;Lo;0;L;;;;;N;;;;; 31F4;KATAKANA LETTER SMALL NU;Lo;0;L;;;;;N;;;;; 31F5;KATAKANA LETTER SMALL HA;Lo;0;L;;;;;N;;;;; 31F6;KATAKANA LETTER SMALL HI;Lo;0;L;;;;;N;;;;; 31F7;KATAKANA LETTER SMALL HU;Lo;0;L;;;;;N;;;;; 31F8;KATAKANA LETTER SMALL HE;Lo;0;L;;;;;N;;;;; 31F9;KATAKANA LETTER SMALL HO;Lo;0;L;;;;;N;;;;; 31FA;KATAKANA LETTER SMALL MU;Lo;0;L;;;;;N;;;;; 31FB;KATAKANA LETTER SMALL RA;Lo;0;L;;;;;N;;;;; 31FC;KATAKANA LETTER SMALL RI;Lo;0;L;;;;;N;;;;; 31FD;KATAKANA LETTER SMALL RU;Lo;0;L;;;;;N;;;;; 31FE;KATAKANA LETTER SMALL RE;Lo;0;L;;;;;N;;;;; 31FF;KATAKANA LETTER SMALL RO;Lo;0;L;;;;;N;;;;; 3200;PARENTHESIZED HANGUL KIYEOK;So;0;L; 0028 1100 0029;;;;N;PARENTHESIZED HANGUL GIYEOG;;;; 3201;PARENTHESIZED HANGUL NIEUN;So;0;L; 0028 1102 0029;;;;N;;;;; 3202;PARENTHESIZED HANGUL TIKEUT;So;0;L; 0028 1103 0029;;;;N;PARENTHESIZED HANGUL DIGEUD;;;; 3203;PARENTHESIZED HANGUL RIEUL;So;0;L; 0028 1105 0029;;;;N;PARENTHESIZED HANGUL LIEUL;;;; 3204;PARENTHESIZED HANGUL MIEUM;So;0;L; 0028 1106 0029;;;;N;;;;; 3205;PARENTHESIZED HANGUL PIEUP;So;0;L; 0028 1107 0029;;;;N;PARENTHESIZED HANGUL BIEUB;;;; 3206;PARENTHESIZED HANGUL SIOS;So;0;L; 0028 1109 0029;;;;N;;;;; 3207;PARENTHESIZED HANGUL IEUNG;So;0;L; 0028 110B 0029;;;;N;;;;; 3208;PARENTHESIZED HANGUL CIEUC;So;0;L; 0028 110C 0029;;;;N;PARENTHESIZED HANGUL JIEUJ;;;; 3209;PARENTHESIZED HANGUL CHIEUCH;So;0;L; 0028 110E 0029;;;;N;PARENTHESIZED HANGUL CIEUC;;;; 320A;PARENTHESIZED HANGUL KHIEUKH;So;0;L; 0028 110F 0029;;;;N;PARENTHESIZED HANGUL KIYEOK;;;; 320B;PARENTHESIZED HANGUL THIEUTH;So;0;L; 0028 1110 0029;;;;N;PARENTHESIZED HANGUL TIEUT;;;; 320C;PARENTHESIZED HANGUL PHIEUPH;So;0;L; 0028 1111 0029;;;;N;PARENTHESIZED HANGUL PIEUP;;;; 320D;PARENTHESIZED HANGUL HIEUH;So;0;L; 0028 1112 0029;;;;N;;;;; 320E;PARENTHESIZED HANGUL KIYEOK A;So;0;L; 0028 1100 1161 0029;;;;N;PARENTHESIZED HANGUL GA;;;; 320F;PARENTHESIZED HANGUL NIEUN A;So;0;L; 0028 1102 1161 0029;;;;N;PARENTHESIZED HANGUL NA;;;; 3210;PARENTHESIZED HANGUL TIKEUT A;So;0;L; 0028 1103 1161 0029;;;;N;PARENTHESIZED HANGUL DA;;;; 3211;PARENTHESIZED HANGUL RIEUL A;So;0;L; 0028 1105 1161 0029;;;;N;PARENTHESIZED HANGUL LA;;;; 3212;PARENTHESIZED HANGUL MIEUM A;So;0;L; 0028 1106 1161 0029;;;;N;PARENTHESIZED HANGUL MA;;;; 3213;PARENTHESIZED HANGUL PIEUP A;So;0;L; 0028 1107 1161 0029;;;;N;PARENTHESIZED HANGUL BA;;;; 3214;PARENTHESIZED HANGUL SIOS A;So;0;L; 0028 1109 1161 0029;;;;N;PARENTHESIZED HANGUL SA;;;; 3215;PARENTHESIZED HANGUL IEUNG A;So;0;L; 0028 110B 1161 0029;;;;N;PARENTHESIZED HANGUL A;;;; 3216;PARENTHESIZED HANGUL CIEUC A;So;0;L; 0028 110C 1161 0029;;;;N;PARENTHESIZED HANGUL JA;;;; 3217;PARENTHESIZED HANGUL CHIEUCH A;So;0;L; 0028 110E 1161 0029;;;;N;PARENTHESIZED HANGUL CA;;;; 3218;PARENTHESIZED HANGUL KHIEUKH A;So;0;L; 0028 110F 1161 0029;;;;N;PARENTHESIZED HANGUL KA;;;; 3219;PARENTHESIZED HANGUL THIEUTH A;So;0;L; 0028 1110 1161 0029;;;;N;PARENTHESIZED HANGUL TA;;;; 321A;PARENTHESIZED HANGUL PHIEUPH A;So;0;L; 0028 1111 1161 0029;;;;N;PARENTHESIZED HANGUL PA;;;; 321B;PARENTHESIZED HANGUL HIEUH A;So;0;L; 0028 1112 1161 0029;;;;N;PARENTHESIZED HANGUL HA;;;; 321C;PARENTHESIZED HANGUL CIEUC U;So;0;L; 0028 110C 116E 0029;;;;N;PARENTHESIZED HANGUL JU;;;; 321D;PARENTHESIZED KOREAN CHARACTER OJEON;So;0;ON; 0028 110B 1169 110C 1165 11AB 0029;;;;N;;;;; 321E;PARENTHESIZED KOREAN CHARACTER O HU;So;0;ON; 0028 110B 1169 1112 116E 0029;;;;N;;;;; 3220;PARENTHESIZED IDEOGRAPH ONE;No;0;L; 0028 4E00 0029;;;1;N;;;;; 3221;PARENTHESIZED IDEOGRAPH TWO;No;0;L; 0028 4E8C 0029;;;2;N;;;;; 3222;PARENTHESIZED IDEOGRAPH THREE;No;0;L; 0028 4E09 0029;;;3;N;;;;; 3223;PARENTHESIZED IDEOGRAPH FOUR;No;0;L; 0028 56DB 0029;;;4;N;;;;; 3224;PARENTHESIZED IDEOGRAPH FIVE;No;0;L; 0028 4E94 0029;;;5;N;;;;; 3225;PARENTHESIZED IDEOGRAPH SIX;No;0;L; 0028 516D 0029;;;6;N;;;;; 3226;PARENTHESIZED IDEOGRAPH SEVEN;No;0;L; 0028 4E03 0029;;;7;N;;;;; 3227;PARENTHESIZED IDEOGRAPH EIGHT;No;0;L; 0028 516B 0029;;;8;N;;;;; 3228;PARENTHESIZED IDEOGRAPH NINE;No;0;L; 0028 4E5D 0029;;;9;N;;;;; 3229;PARENTHESIZED IDEOGRAPH TEN;No;0;L; 0028 5341 0029;;;10;N;;;;; 322A;PARENTHESIZED IDEOGRAPH MOON;So;0;L; 0028 6708 0029;;;;N;;;;; 322B;PARENTHESIZED IDEOGRAPH FIRE;So;0;L; 0028 706B 0029;;;;N;;;;; 322C;PARENTHESIZED IDEOGRAPH WATER;So;0;L; 0028 6C34 0029;;;;N;;;;; 322D;PARENTHESIZED IDEOGRAPH WOOD;So;0;L; 0028 6728 0029;;;;N;;;;; 322E;PARENTHESIZED IDEOGRAPH METAL;So;0;L; 0028 91D1 0029;;;;N;;;;; 322F;PARENTHESIZED IDEOGRAPH EARTH;So;0;L; 0028 571F 0029;;;;N;;;;; 3230;PARENTHESIZED IDEOGRAPH SUN;So;0;L; 0028 65E5 0029;;;;N;;;;; 3231;PARENTHESIZED IDEOGRAPH STOCK;So;0;L; 0028 682A 0029;;;;N;;;;; 3232;PARENTHESIZED IDEOGRAPH HAVE;So;0;L; 0028 6709 0029;;;;N;;;;; 3233;PARENTHESIZED IDEOGRAPH SOCIETY;So;0;L; 0028 793E 0029;;;;N;;;;; 3234;PARENTHESIZED IDEOGRAPH NAME;So;0;L; 0028 540D 0029;;;;N;;;;; 3235;PARENTHESIZED IDEOGRAPH SPECIAL;So;0;L; 0028 7279 0029;;;;N;;;;; 3236;PARENTHESIZED IDEOGRAPH FINANCIAL;So;0;L; 0028 8CA1 0029;;;;N;;;;; 3237;PARENTHESIZED IDEOGRAPH CONGRATULATION;So;0;L; 0028 795D 0029;;;;N;;;;; 3238;PARENTHESIZED IDEOGRAPH LABOR;So;0;L; 0028 52B4 0029;;;;N;;;;; 3239;PARENTHESIZED IDEOGRAPH REPRESENT;So;0;L; 0028 4EE3 0029;;;;N;;;;; 323A;PARENTHESIZED IDEOGRAPH CALL;So;0;L; 0028 547C 0029;;;;N;;;;; 323B;PARENTHESIZED IDEOGRAPH STUDY;So;0;L; 0028 5B66 0029;;;;N;;;;; 323C;PARENTHESIZED IDEOGRAPH SUPERVISE;So;0;L; 0028 76E3 0029;;;;N;;;;; 323D;PARENTHESIZED IDEOGRAPH ENTERPRISE;So;0;L; 0028 4F01 0029;;;;N;;;;; 323E;PARENTHESIZED IDEOGRAPH RESOURCE;So;0;L; 0028 8CC7 0029;;;;N;;;;; 323F;PARENTHESIZED IDEOGRAPH ALLIANCE;So;0;L; 0028 5354 0029;;;;N;;;;; 3240;PARENTHESIZED IDEOGRAPH FESTIVAL;So;0;L; 0028 796D 0029;;;;N;;;;; 3241;PARENTHESIZED IDEOGRAPH REST;So;0;L; 0028 4F11 0029;;;;N;;;;; 3242;PARENTHESIZED IDEOGRAPH SELF;So;0;L; 0028 81EA 0029;;;;N;;;;; 3243;PARENTHESIZED IDEOGRAPH REACH;So;0;L; 0028 81F3 0029;;;;N;;;;; 3244;CIRCLED IDEOGRAPH QUESTION;So;0;L; 554F;;;;N;;;;; 3245;CIRCLED IDEOGRAPH KINDERGARTEN;So;0;L; 5E7C;;;;N;;;;; 3246;CIRCLED IDEOGRAPH SCHOOL;So;0;L; 6587;;;;N;;;;; 3247;CIRCLED IDEOGRAPH KOTO;So;0;L; 7B8F;;;;N;;;;; 3248;CIRCLED NUMBER TEN ON BLACK SQUARE;No;0;L;;;;10;N;;;;; 3249;CIRCLED NUMBER TWENTY ON BLACK SQUARE;No;0;L;;;;20;N;;;;; 324A;CIRCLED NUMBER THIRTY ON BLACK SQUARE;No;0;L;;;;30;N;;;;; 324B;CIRCLED NUMBER FORTY ON BLACK SQUARE;No;0;L;;;;40;N;;;;; 324C;CIRCLED NUMBER FIFTY ON BLACK SQUARE;No;0;L;;;;50;N;;;;; 324D;CIRCLED NUMBER SIXTY ON BLACK SQUARE;No;0;L;;;;60;N;;;;; 324E;CIRCLED NUMBER SEVENTY ON BLACK SQUARE;No;0;L;;;;70;N;;;;; 324F;CIRCLED NUMBER EIGHTY ON BLACK SQUARE;No;0;L;;;;80;N;;;;; 3250;PARTNERSHIP SIGN;So;0;ON; 0050 0054 0045;;;;N;;;;; 3251;CIRCLED NUMBER TWENTY ONE;No;0;ON; 0032 0031;;;21;N;;;;; 3252;CIRCLED NUMBER TWENTY TWO;No;0;ON; 0032 0032;;;22;N;;;;; 3253;CIRCLED NUMBER TWENTY THREE;No;0;ON; 0032 0033;;;23;N;;;;; 3254;CIRCLED NUMBER TWENTY FOUR;No;0;ON; 0032 0034;;;24;N;;;;; 3255;CIRCLED NUMBER TWENTY FIVE;No;0;ON; 0032 0035;;;25;N;;;;; 3256;CIRCLED NUMBER TWENTY SIX;No;0;ON; 0032 0036;;;26;N;;;;; 3257;CIRCLED NUMBER TWENTY SEVEN;No;0;ON; 0032 0037;;;27;N;;;;; 3258;CIRCLED NUMBER TWENTY EIGHT;No;0;ON; 0032 0038;;;28;N;;;;; 3259;CIRCLED NUMBER TWENTY NINE;No;0;ON; 0032 0039;;;29;N;;;;; 325A;CIRCLED NUMBER THIRTY;No;0;ON; 0033 0030;;;30;N;;;;; 325B;CIRCLED NUMBER THIRTY ONE;No;0;ON; 0033 0031;;;31;N;;;;; 325C;CIRCLED NUMBER THIRTY TWO;No;0;ON; 0033 0032;;;32;N;;;;; 325D;CIRCLED NUMBER THIRTY THREE;No;0;ON; 0033 0033;;;33;N;;;;; 325E;CIRCLED NUMBER THIRTY FOUR;No;0;ON; 0033 0034;;;34;N;;;;; 325F;CIRCLED NUMBER THIRTY FIVE;No;0;ON; 0033 0035;;;35;N;;;;; 3260;CIRCLED HANGUL KIYEOK;So;0;L; 1100;;;;N;CIRCLED HANGUL GIYEOG;;;; 3261;CIRCLED HANGUL NIEUN;So;0;L; 1102;;;;N;;;;; 3262;CIRCLED HANGUL TIKEUT;So;0;L; 1103;;;;N;CIRCLED HANGUL DIGEUD;;;; 3263;CIRCLED HANGUL RIEUL;So;0;L; 1105;;;;N;CIRCLED HANGUL LIEUL;;;; 3264;CIRCLED HANGUL MIEUM;So;0;L; 1106;;;;N;;;;; 3265;CIRCLED HANGUL PIEUP;So;0;L; 1107;;;;N;CIRCLED HANGUL BIEUB;;;; 3266;CIRCLED HANGUL SIOS;So;0;L; 1109;;;;N;;;;; 3267;CIRCLED HANGUL IEUNG;So;0;L; 110B;;;;N;;;;; 3268;CIRCLED HANGUL CIEUC;So;0;L; 110C;;;;N;CIRCLED HANGUL JIEUJ;;;; 3269;CIRCLED HANGUL CHIEUCH;So;0;L; 110E;;;;N;CIRCLED HANGUL CIEUC;;;; 326A;CIRCLED HANGUL KHIEUKH;So;0;L; 110F;;;;N;CIRCLED HANGUL KIYEOK;;;; 326B;CIRCLED HANGUL THIEUTH;So;0;L; 1110;;;;N;CIRCLED HANGUL TIEUT;;;; 326C;CIRCLED HANGUL PHIEUPH;So;0;L; 1111;;;;N;CIRCLED HANGUL PIEUP;;;; 326D;CIRCLED HANGUL HIEUH;So;0;L; 1112;;;;N;;;;; 326E;CIRCLED HANGUL KIYEOK A;So;0;L; 1100 1161;;;;N;CIRCLED HANGUL GA;;;; 326F;CIRCLED HANGUL NIEUN A;So;0;L; 1102 1161;;;;N;CIRCLED HANGUL NA;;;; 3270;CIRCLED HANGUL TIKEUT A;So;0;L; 1103 1161;;;;N;CIRCLED HANGUL DA;;;; 3271;CIRCLED HANGUL RIEUL A;So;0;L; 1105 1161;;;;N;CIRCLED HANGUL LA;;;; 3272;CIRCLED HANGUL MIEUM A;So;0;L; 1106 1161;;;;N;CIRCLED HANGUL MA;;;; 3273;CIRCLED HANGUL PIEUP A;So;0;L; 1107 1161;;;;N;CIRCLED HANGUL BA;;;; 3274;CIRCLED HANGUL SIOS A;So;0;L; 1109 1161;;;;N;CIRCLED HANGUL SA;;;; 3275;CIRCLED HANGUL IEUNG A;So;0;L; 110B 1161;;;;N;CIRCLED HANGUL A;;;; 3276;CIRCLED HANGUL CIEUC A;So;0;L; 110C 1161;;;;N;CIRCLED HANGUL JA;;;; 3277;CIRCLED HANGUL CHIEUCH A;So;0;L; 110E 1161;;;;N;CIRCLED HANGUL CA;;;; 3278;CIRCLED HANGUL KHIEUKH A;So;0;L; 110F 1161;;;;N;CIRCLED HANGUL KA;;;; 3279;CIRCLED HANGUL THIEUTH A;So;0;L; 1110 1161;;;;N;CIRCLED HANGUL TA;;;; 327A;CIRCLED HANGUL PHIEUPH A;So;0;L; 1111 1161;;;;N;CIRCLED HANGUL PA;;;; 327B;CIRCLED HANGUL HIEUH A;So;0;L; 1112 1161;;;;N;CIRCLED HANGUL HA;;;; 327C;CIRCLED KOREAN CHARACTER CHAMKO;So;0;ON; 110E 1161 11B7 1100 1169;;;;N;;;;; 327D;CIRCLED KOREAN CHARACTER JUEUI;So;0;ON; 110C 116E 110B 1174;;;;N;;;;; 327E;CIRCLED HANGUL IEUNG U;So;0;ON; 110B 116E;;;;N;;;;; 327F;KOREAN STANDARD SYMBOL;So;0;L;;;;;N;;;;; 3280;CIRCLED IDEOGRAPH ONE;No;0;L; 4E00;;;1;N;;;;; 3281;CIRCLED IDEOGRAPH TWO;No;0;L; 4E8C;;;2;N;;;;; 3282;CIRCLED IDEOGRAPH THREE;No;0;L; 4E09;;;3;N;;;;; 3283;CIRCLED IDEOGRAPH FOUR;No;0;L; 56DB;;;4;N;;;;; 3284;CIRCLED IDEOGRAPH FIVE;No;0;L; 4E94;;;5;N;;;;; 3285;CIRCLED IDEOGRAPH SIX;No;0;L; 516D;;;6;N;;;;; 3286;CIRCLED IDEOGRAPH SEVEN;No;0;L; 4E03;;;7;N;;;;; 3287;CIRCLED IDEOGRAPH EIGHT;No;0;L; 516B;;;8;N;;;;; 3288;CIRCLED IDEOGRAPH NINE;No;0;L; 4E5D;;;9;N;;;;; 3289;CIRCLED IDEOGRAPH TEN;No;0;L; 5341;;;10;N;;;;; 328A;CIRCLED IDEOGRAPH MOON;So;0;L; 6708;;;;N;;;;; 328B;CIRCLED IDEOGRAPH FIRE;So;0;L; 706B;;;;N;;;;; 328C;CIRCLED IDEOGRAPH WATER;So;0;L; 6C34;;;;N;;;;; 328D;CIRCLED IDEOGRAPH WOOD;So;0;L; 6728;;;;N;;;;; 328E;CIRCLED IDEOGRAPH METAL;So;0;L; 91D1;;;;N;;;;; 328F;CIRCLED IDEOGRAPH EARTH;So;0;L; 571F;;;;N;;;;; 3290;CIRCLED IDEOGRAPH SUN;So;0;L; 65E5;;;;N;;;;; 3291;CIRCLED IDEOGRAPH STOCK;So;0;L; 682A;;;;N;;;;; 3292;CIRCLED IDEOGRAPH HAVE;So;0;L; 6709;;;;N;;;;; 3293;CIRCLED IDEOGRAPH SOCIETY;So;0;L; 793E;;;;N;;;;; 3294;CIRCLED IDEOGRAPH NAME;So;0;L; 540D;;;;N;;;;; 3295;CIRCLED IDEOGRAPH SPECIAL;So;0;L; 7279;;;;N;;;;; 3296;CIRCLED IDEOGRAPH FINANCIAL;So;0;L; 8CA1;;;;N;;;;; 3297;CIRCLED IDEOGRAPH CONGRATULATION;So;0;L; 795D;;;;N;;;;; 3298;CIRCLED IDEOGRAPH LABOR;So;0;L; 52B4;;;;N;;;;; 3299;CIRCLED IDEOGRAPH SECRET;So;0;L; 79D8;;;;N;;;;; 329A;CIRCLED IDEOGRAPH MALE;So;0;L; 7537;;;;N;;;;; 329B;CIRCLED IDEOGRAPH FEMALE;So;0;L; 5973;;;;N;;;;; 329C;CIRCLED IDEOGRAPH SUITABLE;So;0;L; 9069;;;;N;;;;; 329D;CIRCLED IDEOGRAPH EXCELLENT;So;0;L; 512A;;;;N;;;;; 329E;CIRCLED IDEOGRAPH PRINT;So;0;L; 5370;;;;N;;;;; 329F;CIRCLED IDEOGRAPH ATTENTION;So;0;L; 6CE8;;;;N;;;;; 32A0;CIRCLED IDEOGRAPH ITEM;So;0;L; 9805;;;;N;;;;; 32A1;CIRCLED IDEOGRAPH REST;So;0;L; 4F11;;;;N;;;;; 32A2;CIRCLED IDEOGRAPH COPY;So;0;L; 5199;;;;N;;;;; 32A3;CIRCLED IDEOGRAPH CORRECT;So;0;L; 6B63;;;;N;;;;; 32A4;CIRCLED IDEOGRAPH HIGH;So;0;L; 4E0A;;;;N;;;;; 32A5;CIRCLED IDEOGRAPH CENTRE;So;0;L; 4E2D;;;;N;CIRCLED IDEOGRAPH CENTER;;;; 32A6;CIRCLED IDEOGRAPH LOW;So;0;L; 4E0B;;;;N;;;;; 32A7;CIRCLED IDEOGRAPH LEFT;So;0;L; 5DE6;;;;N;;;;; 32A8;CIRCLED IDEOGRAPH RIGHT;So;0;L; 53F3;;;;N;;;;; 32A9;CIRCLED IDEOGRAPH MEDICINE;So;0;L; 533B;;;;N;;;;; 32AA;CIRCLED IDEOGRAPH RELIGION;So;0;L; 5B97;;;;N;;;;; 32AB;CIRCLED IDEOGRAPH STUDY;So;0;L; 5B66;;;;N;;;;; 32AC;CIRCLED IDEOGRAPH SUPERVISE;So;0;L; 76E3;;;;N;;;;; 32AD;CIRCLED IDEOGRAPH ENTERPRISE;So;0;L; 4F01;;;;N;;;;; 32AE;CIRCLED IDEOGRAPH RESOURCE;So;0;L; 8CC7;;;;N;;;;; 32AF;CIRCLED IDEOGRAPH ALLIANCE;So;0;L; 5354;;;;N;;;;; 32B0;CIRCLED IDEOGRAPH NIGHT;So;0;L; 591C;;;;N;;;;; 32B1;CIRCLED NUMBER THIRTY SIX;No;0;ON; 0033 0036;;;36;N;;;;; 32B2;CIRCLED NUMBER THIRTY SEVEN;No;0;ON; 0033 0037;;;37;N;;;;; 32B3;CIRCLED NUMBER THIRTY EIGHT;No;0;ON; 0033 0038;;;38;N;;;;; 32B4;CIRCLED NUMBER THIRTY NINE;No;0;ON; 0033 0039;;;39;N;;;;; 32B5;CIRCLED NUMBER FORTY;No;0;ON; 0034 0030;;;40;N;;;;; 32B6;CIRCLED NUMBER FORTY ONE;No;0;ON; 0034 0031;;;41;N;;;;; 32B7;CIRCLED NUMBER FORTY TWO;No;0;ON; 0034 0032;;;42;N;;;;; 32B8;CIRCLED NUMBER FORTY THREE;No;0;ON; 0034 0033;;;43;N;;;;; 32B9;CIRCLED NUMBER FORTY FOUR;No;0;ON; 0034 0034;;;44;N;;;;; 32BA;CIRCLED NUMBER FORTY FIVE;No;0;ON; 0034 0035;;;45;N;;;;; 32BB;CIRCLED NUMBER FORTY SIX;No;0;ON; 0034 0036;;;46;N;;;;; 32BC;CIRCLED NUMBER FORTY SEVEN;No;0;ON; 0034 0037;;;47;N;;;;; 32BD;CIRCLED NUMBER FORTY EIGHT;No;0;ON; 0034 0038;;;48;N;;;;; 32BE;CIRCLED NUMBER FORTY NINE;No;0;ON; 0034 0039;;;49;N;;;;; 32BF;CIRCLED NUMBER FIFTY;No;0;ON; 0035 0030;;;50;N;;;;; 32C0;IDEOGRAPHIC TELEGRAPH SYMBOL FOR JANUARY;So;0;L; 0031 6708;;;;N;;;;; 32C1;IDEOGRAPHIC TELEGRAPH SYMBOL FOR FEBRUARY;So;0;L; 0032 6708;;;;N;;;;; 32C2;IDEOGRAPHIC TELEGRAPH SYMBOL FOR MARCH;So;0;L; 0033 6708;;;;N;;;;; 32C3;IDEOGRAPHIC TELEGRAPH SYMBOL FOR APRIL;So;0;L; 0034 6708;;;;N;;;;; 32C4;IDEOGRAPHIC TELEGRAPH SYMBOL FOR MAY;So;0;L; 0035 6708;;;;N;;;;; 32C5;IDEOGRAPHIC TELEGRAPH SYMBOL FOR JUNE;So;0;L; 0036 6708;;;;N;;;;; 32C6;IDEOGRAPHIC TELEGRAPH SYMBOL FOR JULY;So;0;L; 0037 6708;;;;N;;;;; 32C7;IDEOGRAPHIC TELEGRAPH SYMBOL FOR AUGUST;So;0;L; 0038 6708;;;;N;;;;; 32C8;IDEOGRAPHIC TELEGRAPH SYMBOL FOR SEPTEMBER;So;0;L; 0039 6708;;;;N;;;;; 32C9;IDEOGRAPHIC TELEGRAPH SYMBOL FOR OCTOBER;So;0;L; 0031 0030 6708;;;;N;;;;; 32CA;IDEOGRAPHIC TELEGRAPH SYMBOL FOR NOVEMBER;So;0;L; 0031 0031 6708;;;;N;;;;; 32CB;IDEOGRAPHIC TELEGRAPH SYMBOL FOR DECEMBER;So;0;L; 0031 0032 6708;;;;N;;;;; 32CC;SQUARE HG;So;0;ON; 0048 0067;;;;N;;;;; 32CD;SQUARE ERG;So;0;ON; 0065 0072 0067;;;;N;;;;; 32CE;SQUARE EV;So;0;ON; 0065 0056;;;;N;;;;; 32CF;LIMITED LIABILITY SIGN;So;0;ON; 004C 0054 0044;;;;N;;;;; 32D0;CIRCLED KATAKANA A;So;0;L; 30A2;;;;N;;;;; 32D1;CIRCLED KATAKANA I;So;0;L; 30A4;;;;N;;;;; 32D2;CIRCLED KATAKANA U;So;0;L; 30A6;;;;N;;;;; 32D3;CIRCLED KATAKANA E;So;0;L; 30A8;;;;N;;;;; 32D4;CIRCLED KATAKANA O;So;0;L; 30AA;;;;N;;;;; 32D5;CIRCLED KATAKANA KA;So;0;L; 30AB;;;;N;;;;; 32D6;CIRCLED KATAKANA KI;So;0;L; 30AD;;;;N;;;;; 32D7;CIRCLED KATAKANA KU;So;0;L; 30AF;;;;N;;;;; 32D8;CIRCLED KATAKANA KE;So;0;L; 30B1;;;;N;;;;; 32D9;CIRCLED KATAKANA KO;So;0;L; 30B3;;;;N;;;;; 32DA;CIRCLED KATAKANA SA;So;0;L; 30B5;;;;N;;;;; 32DB;CIRCLED KATAKANA SI;So;0;L; 30B7;;;;N;;;;; 32DC;CIRCLED KATAKANA SU;So;0;L; 30B9;;;;N;;;;; 32DD;CIRCLED KATAKANA SE;So;0;L; 30BB;;;;N;;;;; 32DE;CIRCLED KATAKANA SO;So;0;L; 30BD;;;;N;;;;; 32DF;CIRCLED KATAKANA TA;So;0;L; 30BF;;;;N;;;;; 32E0;CIRCLED KATAKANA TI;So;0;L; 30C1;;;;N;;;;; 32E1;CIRCLED KATAKANA TU;So;0;L; 30C4;;;;N;;;;; 32E2;CIRCLED KATAKANA TE;So;0;L; 30C6;;;;N;;;;; 32E3;CIRCLED KATAKANA TO;So;0;L; 30C8;;;;N;;;;; 32E4;CIRCLED KATAKANA NA;So;0;L; 30CA;;;;N;;;;; 32E5;CIRCLED KATAKANA NI;So;0;L; 30CB;;;;N;;;;; 32E6;CIRCLED KATAKANA NU;So;0;L; 30CC;;;;N;;;;; 32E7;CIRCLED KATAKANA NE;So;0;L; 30CD;;;;N;;;;; 32E8;CIRCLED KATAKANA NO;So;0;L; 30CE;;;;N;;;;; 32E9;CIRCLED KATAKANA HA;So;0;L; 30CF;;;;N;;;;; 32EA;CIRCLED KATAKANA HI;So;0;L; 30D2;;;;N;;;;; 32EB;CIRCLED KATAKANA HU;So;0;L; 30D5;;;;N;;;;; 32EC;CIRCLED KATAKANA HE;So;0;L; 30D8;;;;N;;;;; 32ED;CIRCLED KATAKANA HO;So;0;L; 30DB;;;;N;;;;; 32EE;CIRCLED KATAKANA MA;So;0;L; 30DE;;;;N;;;;; 32EF;CIRCLED KATAKANA MI;So;0;L; 30DF;;;;N;;;;; 32F0;CIRCLED KATAKANA MU;So;0;L; 30E0;;;;N;;;;; 32F1;CIRCLED KATAKANA ME;So;0;L; 30E1;;;;N;;;;; 32F2;CIRCLED KATAKANA MO;So;0;L; 30E2;;;;N;;;;; 32F3;CIRCLED KATAKANA YA;So;0;L; 30E4;;;;N;;;;; 32F4;CIRCLED KATAKANA YU;So;0;L; 30E6;;;;N;;;;; 32F5;CIRCLED KATAKANA YO;So;0;L; 30E8;;;;N;;;;; 32F6;CIRCLED KATAKANA RA;So;0;L; 30E9;;;;N;;;;; 32F7;CIRCLED KATAKANA RI;So;0;L; 30EA;;;;N;;;;; 32F8;CIRCLED KATAKANA RU;So;0;L; 30EB;;;;N;;;;; 32F9;CIRCLED KATAKANA RE;So;0;L; 30EC;;;;N;;;;; 32FA;CIRCLED KATAKANA RO;So;0;L; 30ED;;;;N;;;;; 32FB;CIRCLED KATAKANA WA;So;0;L; 30EF;;;;N;;;;; 32FC;CIRCLED KATAKANA WI;So;0;L; 30F0;;;;N;;;;; 32FD;CIRCLED KATAKANA WE;So;0;L; 30F1;;;;N;;;;; 32FE;CIRCLED KATAKANA WO;So;0;L; 30F2;;;;N;;;;; 3300;SQUARE APAATO;So;0;L; 30A2 30D1 30FC 30C8;;;;N;SQUARED APAATO;;;; 3301;SQUARE ARUHUA;So;0;L; 30A2 30EB 30D5 30A1;;;;N;SQUARED ARUHUA;;;; 3302;SQUARE ANPEA;So;0;L; 30A2 30F3 30DA 30A2;;;;N;SQUARED ANPEA;;;; 3303;SQUARE AARU;So;0;L; 30A2 30FC 30EB;;;;N;SQUARED AARU;;;; 3304;SQUARE ININGU;So;0;L; 30A4 30CB 30F3 30B0;;;;N;SQUARED ININGU;;;; 3305;SQUARE INTI;So;0;L; 30A4 30F3 30C1;;;;N;SQUARED INTI;;;; 3306;SQUARE UON;So;0;L; 30A6 30A9 30F3;;;;N;SQUARED UON;;;; 3307;SQUARE ESUKUUDO;So;0;L; 30A8 30B9 30AF 30FC 30C9;;;;N;SQUARED ESUKUUDO;;;; 3308;SQUARE EEKAA;So;0;L; 30A8 30FC 30AB 30FC;;;;N;SQUARED EEKAA;;;; 3309;SQUARE ONSU;So;0;L; 30AA 30F3 30B9;;;;N;SQUARED ONSU;;;; 330A;SQUARE OOMU;So;0;L; 30AA 30FC 30E0;;;;N;SQUARED OOMU;;;; 330B;SQUARE KAIRI;So;0;L; 30AB 30A4 30EA;;;;N;SQUARED KAIRI;;;; 330C;SQUARE KARATTO;So;0;L; 30AB 30E9 30C3 30C8;;;;N;SQUARED KARATTO;;;; 330D;SQUARE KARORII;So;0;L; 30AB 30ED 30EA 30FC;;;;N;SQUARED KARORII;;;; 330E;SQUARE GARON;So;0;L; 30AC 30ED 30F3;;;;N;SQUARED GARON;;;; 330F;SQUARE GANMA;So;0;L; 30AC 30F3 30DE;;;;N;SQUARED GANMA;;;; 3310;SQUARE GIGA;So;0;L; 30AE 30AC;;;;N;SQUARED GIGA;;;; 3311;SQUARE GINII;So;0;L; 30AE 30CB 30FC;;;;N;SQUARED GINII;;;; 3312;SQUARE KYURII;So;0;L; 30AD 30E5 30EA 30FC;;;;N;SQUARED KYURII;;;; 3313;SQUARE GIRUDAA;So;0;L; 30AE 30EB 30C0 30FC;;;;N;SQUARED GIRUDAA;;;; 3314;SQUARE KIRO;So;0;L; 30AD 30ED;;;;N;SQUARED KIRO;;;; 3315;SQUARE KIROGURAMU;So;0;L; 30AD 30ED 30B0 30E9 30E0;;;;N;SQUARED KIROGURAMU;;;; 3316;SQUARE KIROMEETORU;So;0;L; 30AD 30ED 30E1 30FC 30C8 30EB;;;;N;SQUARED KIROMEETORU;;;; 3317;SQUARE KIROWATTO;So;0;L; 30AD 30ED 30EF 30C3 30C8;;;;N;SQUARED KIROWATTO;;;; 3318;SQUARE GURAMU;So;0;L; 30B0 30E9 30E0;;;;N;SQUARED GURAMU;;;; 3319;SQUARE GURAMUTON;So;0;L; 30B0 30E9 30E0 30C8 30F3;;;;N;SQUARED GURAMUTON;;;; 331A;SQUARE KURUZEIRO;So;0;L; 30AF 30EB 30BC 30A4 30ED;;;;N;SQUARED KURUZEIRO;;;; 331B;SQUARE KUROONE;So;0;L; 30AF 30ED 30FC 30CD;;;;N;SQUARED KUROONE;;;; 331C;SQUARE KEESU;So;0;L; 30B1 30FC 30B9;;;;N;SQUARED KEESU;;;; 331D;SQUARE KORUNA;So;0;L; 30B3 30EB 30CA;;;;N;SQUARED KORUNA;;;; 331E;SQUARE KOOPO;So;0;L; 30B3 30FC 30DD;;;;N;SQUARED KOOPO;;;; 331F;SQUARE SAIKURU;So;0;L; 30B5 30A4 30AF 30EB;;;;N;SQUARED SAIKURU;;;; 3320;SQUARE SANTIIMU;So;0;L; 30B5 30F3 30C1 30FC 30E0;;;;N;SQUARED SANTIIMU;;;; 3321;SQUARE SIRINGU;So;0;L; 30B7 30EA 30F3 30B0;;;;N;SQUARED SIRINGU;;;; 3322;SQUARE SENTI;So;0;L; 30BB 30F3 30C1;;;;N;SQUARED SENTI;;;; 3323;SQUARE SENTO;So;0;L; 30BB 30F3 30C8;;;;N;SQUARED SENTO;;;; 3324;SQUARE DAASU;So;0;L; 30C0 30FC 30B9;;;;N;SQUARED DAASU;;;; 3325;SQUARE DESI;So;0;L; 30C7 30B7;;;;N;SQUARED DESI;;;; 3326;SQUARE DORU;So;0;L; 30C9 30EB;;;;N;SQUARED DORU;;;; 3327;SQUARE TON;So;0;L; 30C8 30F3;;;;N;SQUARED TON;;;; 3328;SQUARE NANO;So;0;L; 30CA 30CE;;;;N;SQUARED NANO;;;; 3329;SQUARE NOTTO;So;0;L; 30CE 30C3 30C8;;;;N;SQUARED NOTTO;;;; 332A;SQUARE HAITU;So;0;L; 30CF 30A4 30C4;;;;N;SQUARED HAITU;;;; 332B;SQUARE PAASENTO;So;0;L; 30D1 30FC 30BB 30F3 30C8;;;;N;SQUARED PAASENTO;;;; 332C;SQUARE PAATU;So;0;L; 30D1 30FC 30C4;;;;N;SQUARED PAATU;;;; 332D;SQUARE BAARERU;So;0;L; 30D0 30FC 30EC 30EB;;;;N;SQUARED BAARERU;;;; 332E;SQUARE PIASUTORU;So;0;L; 30D4 30A2 30B9 30C8 30EB;;;;N;SQUARED PIASUTORU;;;; 332F;SQUARE PIKURU;So;0;L; 30D4 30AF 30EB;;;;N;SQUARED PIKURU;;;; 3330;SQUARE PIKO;So;0;L; 30D4 30B3;;;;N;SQUARED PIKO;;;; 3331;SQUARE BIRU;So;0;L; 30D3 30EB;;;;N;SQUARED BIRU;;;; 3332;SQUARE HUARADDO;So;0;L; 30D5 30A1 30E9 30C3 30C9;;;;N;SQUARED HUARADDO;;;; 3333;SQUARE HUIITO;So;0;L; 30D5 30A3 30FC 30C8;;;;N;SQUARED HUIITO;;;; 3334;SQUARE BUSSYERU;So;0;L; 30D6 30C3 30B7 30A7 30EB;;;;N;SQUARED BUSSYERU;;;; 3335;SQUARE HURAN;So;0;L; 30D5 30E9 30F3;;;;N;SQUARED HURAN;;;; 3336;SQUARE HEKUTAARU;So;0;L; 30D8 30AF 30BF 30FC 30EB;;;;N;SQUARED HEKUTAARU;;;; 3337;SQUARE PESO;So;0;L; 30DA 30BD;;;;N;SQUARED PESO;;;; 3338;SQUARE PENIHI;So;0;L; 30DA 30CB 30D2;;;;N;SQUARED PENIHI;;;; 3339;SQUARE HERUTU;So;0;L; 30D8 30EB 30C4;;;;N;SQUARED HERUTU;;;; 333A;SQUARE PENSU;So;0;L; 30DA 30F3 30B9;;;;N;SQUARED PENSU;;;; 333B;SQUARE PEEZI;So;0;L; 30DA 30FC 30B8;;;;N;SQUARED PEEZI;;;; 333C;SQUARE BEETA;So;0;L; 30D9 30FC 30BF;;;;N;SQUARED BEETA;;;; 333D;SQUARE POINTO;So;0;L; 30DD 30A4 30F3 30C8;;;;N;SQUARED POINTO;;;; 333E;SQUARE BORUTO;So;0;L; 30DC 30EB 30C8;;;;N;SQUARED BORUTO;;;; 333F;SQUARE HON;So;0;L; 30DB 30F3;;;;N;SQUARED HON;;;; 3340;SQUARE PONDO;So;0;L; 30DD 30F3 30C9;;;;N;SQUARED PONDO;;;; 3341;SQUARE HOORU;So;0;L; 30DB 30FC 30EB;;;;N;SQUARED HOORU;;;; 3342;SQUARE HOON;So;0;L; 30DB 30FC 30F3;;;;N;SQUARED HOON;;;; 3343;SQUARE MAIKURO;So;0;L; 30DE 30A4 30AF 30ED;;;;N;SQUARED MAIKURO;;;; 3344;SQUARE MAIRU;So;0;L; 30DE 30A4 30EB;;;;N;SQUARED MAIRU;;;; 3345;SQUARE MAHHA;So;0;L; 30DE 30C3 30CF;;;;N;SQUARED MAHHA;;;; 3346;SQUARE MARUKU;So;0;L; 30DE 30EB 30AF;;;;N;SQUARED MARUKU;;;; 3347;SQUARE MANSYON;So;0;L; 30DE 30F3 30B7 30E7 30F3;;;;N;SQUARED MANSYON;;;; 3348;SQUARE MIKURON;So;0;L; 30DF 30AF 30ED 30F3;;;;N;SQUARED MIKURON;;;; 3349;SQUARE MIRI;So;0;L; 30DF 30EA;;;;N;SQUARED MIRI;;;; 334A;SQUARE MIRIBAARU;So;0;L; 30DF 30EA 30D0 30FC 30EB;;;;N;SQUARED MIRIBAARU;;;; 334B;SQUARE MEGA;So;0;L; 30E1 30AC;;;;N;SQUARED MEGA;;;; 334C;SQUARE MEGATON;So;0;L; 30E1 30AC 30C8 30F3;;;;N;SQUARED MEGATON;;;; 334D;SQUARE MEETORU;So;0;L; 30E1 30FC 30C8 30EB;;;;N;SQUARED MEETORU;;;; 334E;SQUARE YAADO;So;0;L; 30E4 30FC 30C9;;;;N;SQUARED YAADO;;;; 334F;SQUARE YAARU;So;0;L; 30E4 30FC 30EB;;;;N;SQUARED YAARU;;;; 3350;SQUARE YUAN;So;0;L; 30E6 30A2 30F3;;;;N;SQUARED YUAN;;;; 3351;SQUARE RITTORU;So;0;L; 30EA 30C3 30C8 30EB;;;;N;SQUARED RITTORU;;;; 3352;SQUARE RIRA;So;0;L; 30EA 30E9;;;;N;SQUARED RIRA;;;; 3353;SQUARE RUPII;So;0;L; 30EB 30D4 30FC;;;;N;SQUARED RUPII;;;; 3354;SQUARE RUUBURU;So;0;L; 30EB 30FC 30D6 30EB;;;;N;SQUARED RUUBURU;;;; 3355;SQUARE REMU;So;0;L; 30EC 30E0;;;;N;SQUARED REMU;;;; 3356;SQUARE RENTOGEN;So;0;L; 30EC 30F3 30C8 30B2 30F3;;;;N;SQUARED RENTOGEN;;;; 3357;SQUARE WATTO;So;0;L; 30EF 30C3 30C8;;;;N;SQUARED WATTO;;;; 3358;IDEOGRAPHIC TELEGRAPH SYMBOL FOR HOUR ZERO;So;0;L; 0030 70B9;;;;N;;;;; 3359;IDEOGRAPHIC TELEGRAPH SYMBOL FOR HOUR ONE;So;0;L; 0031 70B9;;;;N;;;;; 335A;IDEOGRAPHIC TELEGRAPH SYMBOL FOR HOUR TWO;So;0;L; 0032 70B9;;;;N;;;;; 335B;IDEOGRAPHIC TELEGRAPH SYMBOL FOR HOUR THREE;So;0;L; 0033 70B9;;;;N;;;;; 335C;IDEOGRAPHIC TELEGRAPH SYMBOL FOR HOUR FOUR;So;0;L; 0034 70B9;;;;N;;;;; 335D;IDEOGRAPHIC TELEGRAPH SYMBOL FOR HOUR FIVE;So;0;L; 0035 70B9;;;;N;;;;; 335E;IDEOGRAPHIC TELEGRAPH SYMBOL FOR HOUR SIX;So;0;L; 0036 70B9;;;;N;;;;; 335F;IDEOGRAPHIC TELEGRAPH SYMBOL FOR HOUR SEVEN;So;0;L; 0037 70B9;;;;N;;;;; 3360;IDEOGRAPHIC TELEGRAPH SYMBOL FOR HOUR EIGHT;So;0;L; 0038 70B9;;;;N;;;;; 3361;IDEOGRAPHIC TELEGRAPH SYMBOL FOR HOUR NINE;So;0;L; 0039 70B9;;;;N;;;;; 3362;IDEOGRAPHIC TELEGRAPH SYMBOL FOR HOUR TEN;So;0;L; 0031 0030 70B9;;;;N;;;;; 3363;IDEOGRAPHIC TELEGRAPH SYMBOL FOR HOUR ELEVEN;So;0;L; 0031 0031 70B9;;;;N;;;;; 3364;IDEOGRAPHIC TELEGRAPH SYMBOL FOR HOUR TWELVE;So;0;L; 0031 0032 70B9;;;;N;;;;; 3365;IDEOGRAPHIC TELEGRAPH SYMBOL FOR HOUR THIRTEEN;So;0;L; 0031 0033 70B9;;;;N;;;;; 3366;IDEOGRAPHIC TELEGRAPH SYMBOL FOR HOUR FOURTEEN;So;0;L; 0031 0034 70B9;;;;N;;;;; 3367;IDEOGRAPHIC TELEGRAPH SYMBOL FOR HOUR FIFTEEN;So;0;L; 0031 0035 70B9;;;;N;;;;; 3368;IDEOGRAPHIC TELEGRAPH SYMBOL FOR HOUR SIXTEEN;So;0;L; 0031 0036 70B9;;;;N;;;;; 3369;IDEOGRAPHIC TELEGRAPH SYMBOL FOR HOUR SEVENTEEN;So;0;L; 0031 0037 70B9;;;;N;;;;; 336A;IDEOGRAPHIC TELEGRAPH SYMBOL FOR HOUR EIGHTEEN;So;0;L; 0031 0038 70B9;;;;N;;;;; 336B;IDEOGRAPHIC TELEGRAPH SYMBOL FOR HOUR NINETEEN;So;0;L; 0031 0039 70B9;;;;N;;;;; 336C;IDEOGRAPHIC TELEGRAPH SYMBOL FOR HOUR TWENTY;So;0;L; 0032 0030 70B9;;;;N;;;;; 336D;IDEOGRAPHIC TELEGRAPH SYMBOL FOR HOUR TWENTY-ONE;So;0;L; 0032 0031 70B9;;;;N;;;;; 336E;IDEOGRAPHIC TELEGRAPH SYMBOL FOR HOUR TWENTY-TWO;So;0;L; 0032 0032 70B9;;;;N;;;;; 336F;IDEOGRAPHIC TELEGRAPH SYMBOL FOR HOUR TWENTY-THREE;So;0;L; 0032 0033 70B9;;;;N;;;;; 3370;IDEOGRAPHIC TELEGRAPH SYMBOL FOR HOUR TWENTY-FOUR;So;0;L; 0032 0034 70B9;;;;N;;;;; 3371;SQUARE HPA;So;0;L; 0068 0050 0061;;;;N;;;;; 3372;SQUARE DA;So;0;L; 0064 0061;;;;N;;;;; 3373;SQUARE AU;So;0;L; 0041 0055;;;;N;;;;; 3374;SQUARE BAR;So;0;L; 0062 0061 0072;;;;N;;;;; 3375;SQUARE OV;So;0;L; 006F 0056;;;;N;;;;; 3376;SQUARE PC;So;0;L; 0070 0063;;;;N;;;;; 3377;SQUARE DM;So;0;ON; 0064 006D;;;;N;;;;; 3378;SQUARE DM SQUARED;So;0;ON; 0064 006D 00B2;;;;N;;;;; 3379;SQUARE DM CUBED;So;0;ON; 0064 006D 00B3;;;;N;;;;; 337A;SQUARE IU;So;0;ON; 0049 0055;;;;N;;;;; 337B;SQUARE ERA NAME HEISEI;So;0;L; 5E73 6210;;;;N;SQUARED TWO IDEOGRAPHS ERA NAME HEISEI;;;; 337C;SQUARE ERA NAME SYOUWA;So;0;L; 662D 548C;;;;N;SQUARED TWO IDEOGRAPHS ERA NAME SYOUWA;;;; 337D;SQUARE ERA NAME TAISYOU;So;0;L; 5927 6B63;;;;N;SQUARED TWO IDEOGRAPHS ERA NAME TAISYOU;;;; 337E;SQUARE ERA NAME MEIZI;So;0;L; 660E 6CBB;;;;N;SQUARED TWO IDEOGRAPHS ERA NAME MEIZI;;;; 337F;SQUARE CORPORATION;So;0;L; 682A 5F0F 4F1A 793E;;;;N;SQUARED FOUR IDEOGRAPHS CORPORATION;;;; 3380;SQUARE PA AMPS;So;0;L; 0070 0041;;;;N;SQUARED PA AMPS;;;; 3381;SQUARE NA;So;0;L; 006E 0041;;;;N;SQUARED NA;;;; 3382;SQUARE MU A;So;0;L; 03BC 0041;;;;N;SQUARED MU A;;;; 3383;SQUARE MA;So;0;L; 006D 0041;;;;N;SQUARED MA;;;; 3384;SQUARE KA;So;0;L; 006B 0041;;;;N;SQUARED KA;;;; 3385;SQUARE KB;So;0;L; 004B 0042;;;;N;SQUARED KB;;;; 3386;SQUARE MB;So;0;L; 004D 0042;;;;N;SQUARED MB;;;; 3387;SQUARE GB;So;0;L; 0047 0042;;;;N;SQUARED GB;;;; 3388;SQUARE CAL;So;0;L; 0063 0061 006C;;;;N;SQUARED CAL;;;; 3389;SQUARE KCAL;So;0;L; 006B 0063 0061 006C;;;;N;SQUARED KCAL;;;; 338A;SQUARE PF;So;0;L; 0070 0046;;;;N;SQUARED PF;;;; 338B;SQUARE NF;So;0;L; 006E 0046;;;;N;SQUARED NF;;;; 338C;SQUARE MU F;So;0;L; 03BC 0046;;;;N;SQUARED MU F;;;; 338D;SQUARE MU G;So;0;L; 03BC 0067;;;;N;SQUARED MU G;;;; 338E;SQUARE MG;So;0;L; 006D 0067;;;;N;SQUARED MG;;;; 338F;SQUARE KG;So;0;L; 006B 0067;;;;N;SQUARED KG;;;; 3390;SQUARE HZ;So;0;L; 0048 007A;;;;N;SQUARED HZ;;;; 3391;SQUARE KHZ;So;0;L; 006B 0048 007A;;;;N;SQUARED KHZ;;;; 3392;SQUARE MHZ;So;0;L; 004D 0048 007A;;;;N;SQUARED MHZ;;;; 3393;SQUARE GHZ;So;0;L; 0047 0048 007A;;;;N;SQUARED GHZ;;;; 3394;SQUARE THZ;So;0;L; 0054 0048 007A;;;;N;SQUARED THZ;;;; 3395;SQUARE MU L;So;0;L; 03BC 2113;;;;N;SQUARED MU L;;;; 3396;SQUARE ML;So;0;L; 006D 2113;;;;N;SQUARED ML;;;; 3397;SQUARE DL;So;0;L; 0064 2113;;;;N;SQUARED DL;;;; 3398;SQUARE KL;So;0;L; 006B 2113;;;;N;SQUARED KL;;;; 3399;SQUARE FM;So;0;L; 0066 006D;;;;N;SQUARED FM;;;; 339A;SQUARE NM;So;0;L; 006E 006D;;;;N;SQUARED NM;;;; 339B;SQUARE MU M;So;0;L; 03BC 006D;;;;N;SQUARED MU M;;;; 339C;SQUARE MM;So;0;L; 006D 006D;;;;N;SQUARED MM;;;; 339D;SQUARE CM;So;0;L; 0063 006D;;;;N;SQUARED CM;;;; 339E;SQUARE KM;So;0;L; 006B 006D;;;;N;SQUARED KM;;;; 339F;SQUARE MM SQUARED;So;0;L; 006D 006D 00B2;;;;N;SQUARED MM SQUARED;;;; 33A0;SQUARE CM SQUARED;So;0;L; 0063 006D 00B2;;;;N;SQUARED CM SQUARED;;;; 33A1;SQUARE M SQUARED;So;0;L; 006D 00B2;;;;N;SQUARED M SQUARED;;;; 33A2;SQUARE KM SQUARED;So;0;L; 006B 006D 00B2;;;;N;SQUARED KM SQUARED;;;; 33A3;SQUARE MM CUBED;So;0;L; 006D 006D 00B3;;;;N;SQUARED MM CUBED;;;; 33A4;SQUARE CM CUBED;So;0;L; 0063 006D 00B3;;;;N;SQUARED CM CUBED;;;; 33A5;SQUARE M CUBED;So;0;L; 006D 00B3;;;;N;SQUARED M CUBED;;;; 33A6;SQUARE KM CUBED;So;0;L; 006B 006D 00B3;;;;N;SQUARED KM CUBED;;;; 33A7;SQUARE M OVER S;So;0;L; 006D 2215 0073;;;;N;SQUARED M OVER S;;;; 33A8;SQUARE M OVER S SQUARED;So;0;L; 006D 2215 0073 00B2;;;;N;SQUARED M OVER S SQUARED;;;; 33A9;SQUARE PA;So;0;L; 0050 0061;;;;N;SQUARED PA;;;; 33AA;SQUARE KPA;So;0;L; 006B 0050 0061;;;;N;SQUARED KPA;;;; 33AB;SQUARE MPA;So;0;L; 004D 0050 0061;;;;N;SQUARED MPA;;;; 33AC;SQUARE GPA;So;0;L; 0047 0050 0061;;;;N;SQUARED GPA;;;; 33AD;SQUARE RAD;So;0;L; 0072 0061 0064;;;;N;SQUARED RAD;;;; 33AE;SQUARE RAD OVER S;So;0;L; 0072 0061 0064 2215 0073;;;;N;SQUARED RAD OVER S;;;; 33AF;SQUARE RAD OVER S SQUARED;So;0;L; 0072 0061 0064 2215 0073 00B2;;;;N;SQUARED RAD OVER S SQUARED;;;; 33B0;SQUARE PS;So;0;L; 0070 0073;;;;N;SQUARED PS;;;; 33B1;SQUARE NS;So;0;L; 006E 0073;;;;N;SQUARED NS;;;; 33B2;SQUARE MU S;So;0;L; 03BC 0073;;;;N;SQUARED MU S;;;; 33B3;SQUARE MS;So;0;L; 006D 0073;;;;N;SQUARED MS;;;; 33B4;SQUARE PV;So;0;L; 0070 0056;;;;N;SQUARED PV;;;; 33B5;SQUARE NV;So;0;L; 006E 0056;;;;N;SQUARED NV;;;; 33B6;SQUARE MU V;So;0;L; 03BC 0056;;;;N;SQUARED MU V;;;; 33B7;SQUARE MV;So;0;L; 006D 0056;;;;N;SQUARED MV;;;; 33B8;SQUARE KV;So;0;L; 006B 0056;;;;N;SQUARED KV;;;; 33B9;SQUARE MV MEGA;So;0;L; 004D 0056;;;;N;SQUARED MV MEGA;;;; 33BA;SQUARE PW;So;0;L; 0070 0057;;;;N;SQUARED PW;;;; 33BB;SQUARE NW;So;0;L; 006E 0057;;;;N;SQUARED NW;;;; 33BC;SQUARE MU W;So;0;L; 03BC 0057;;;;N;SQUARED MU W;;;; 33BD;SQUARE MW;So;0;L; 006D 0057;;;;N;SQUARED MW;;;; 33BE;SQUARE KW;So;0;L; 006B 0057;;;;N;SQUARED KW;;;; 33BF;SQUARE MW MEGA;So;0;L; 004D 0057;;;;N;SQUARED MW MEGA;;;; 33C0;SQUARE K OHM;So;0;L; 006B 03A9;;;;N;SQUARED K OHM;;;; 33C1;SQUARE M OHM;So;0;L; 004D 03A9;;;;N;SQUARED M OHM;;;; 33C2;SQUARE AM;So;0;L; 0061 002E 006D 002E;;;;N;SQUARED AM;;;; 33C3;SQUARE BQ;So;0;L; 0042 0071;;;;N;SQUARED BQ;;;; 33C4;SQUARE CC;So;0;L; 0063 0063;;;;N;SQUARED CC;;;; 33C5;SQUARE CD;So;0;L; 0063 0064;;;;N;SQUARED CD;;;; 33C6;SQUARE C OVER KG;So;0;L; 0043 2215 006B 0067;;;;N;SQUARED C OVER KG;;;; 33C7;SQUARE CO;So;0;L; 0043 006F 002E;;;;N;SQUARED CO;;;; 33C8;SQUARE DB;So;0;L; 0064 0042;;;;N;SQUARED DB;;;; 33C9;SQUARE GY;So;0;L; 0047 0079;;;;N;SQUARED GY;;;; 33CA;SQUARE HA;So;0;L; 0068 0061;;;;N;SQUARED HA;;;; 33CB;SQUARE HP;So;0;L; 0048 0050;;;;N;SQUARED HP;;;; 33CC;SQUARE IN;So;0;L; 0069 006E;;;;N;SQUARED IN;;;; 33CD;SQUARE KK;So;0;L; 004B 004B;;;;N;SQUARED KK;;;; 33CE;SQUARE KM CAPITAL;So;0;L; 004B 004D;;;;N;SQUARED KM CAPITAL;;;; 33CF;SQUARE KT;So;0;L; 006B 0074;;;;N;SQUARED KT;;;; 33D0;SQUARE LM;So;0;L; 006C 006D;;;;N;SQUARED LM;;;; 33D1;SQUARE LN;So;0;L; 006C 006E;;;;N;SQUARED LN;;;; 33D2;SQUARE LOG;So;0;L; 006C 006F 0067;;;;N;SQUARED LOG;;;; 33D3;SQUARE LX;So;0;L; 006C 0078;;;;N;SQUARED LX;;;; 33D4;SQUARE MB SMALL;So;0;L; 006D 0062;;;;N;SQUARED MB SMALL;;;; 33D5;SQUARE MIL;So;0;L; 006D 0069 006C;;;;N;SQUARED MIL;;;; 33D6;SQUARE MOL;So;0;L; 006D 006F 006C;;;;N;SQUARED MOL;;;; 33D7;SQUARE PH;So;0;L; 0050 0048;;;;N;SQUARED PH;;;; 33D8;SQUARE PM;So;0;L; 0070 002E 006D 002E;;;;N;SQUARED PM;;;; 33D9;SQUARE PPM;So;0;L; 0050 0050 004D;;;;N;SQUARED PPM;;;; 33DA;SQUARE PR;So;0;L; 0050 0052;;;;N;SQUARED PR;;;; 33DB;SQUARE SR;So;0;L; 0073 0072;;;;N;SQUARED SR;;;; 33DC;SQUARE SV;So;0;L; 0053 0076;;;;N;SQUARED SV;;;; 33DD;SQUARE WB;So;0;L; 0057 0062;;;;N;SQUARED WB;;;; 33DE;SQUARE V OVER M;So;0;ON; 0056 2215 006D;;;;N;;;;; 33DF;SQUARE A OVER M;So;0;ON; 0041 2215 006D;;;;N;;;;; 33E0;IDEOGRAPHIC TELEGRAPH SYMBOL FOR DAY ONE;So;0;L; 0031 65E5;;;;N;;;;; 33E1;IDEOGRAPHIC TELEGRAPH SYMBOL FOR DAY TWO;So;0;L; 0032 65E5;;;;N;;;;; 33E2;IDEOGRAPHIC TELEGRAPH SYMBOL FOR DAY THREE;So;0;L; 0033 65E5;;;;N;;;;; 33E3;IDEOGRAPHIC TELEGRAPH SYMBOL FOR DAY FOUR;So;0;L; 0034 65E5;;;;N;;;;; 33E4;IDEOGRAPHIC TELEGRAPH SYMBOL FOR DAY FIVE;So;0;L; 0035 65E5;;;;N;;;;; 33E5;IDEOGRAPHIC TELEGRAPH SYMBOL FOR DAY SIX;So;0;L; 0036 65E5;;;;N;;;;; 33E6;IDEOGRAPHIC TELEGRAPH SYMBOL FOR DAY SEVEN;So;0;L; 0037 65E5;;;;N;;;;; 33E7;IDEOGRAPHIC TELEGRAPH SYMBOL FOR DAY EIGHT;So;0;L; 0038 65E5;;;;N;;;;; 33E8;IDEOGRAPHIC TELEGRAPH SYMBOL FOR DAY NINE;So;0;L; 0039 65E5;;;;N;;;;; 33E9;IDEOGRAPHIC TELEGRAPH SYMBOL FOR DAY TEN;So;0;L; 0031 0030 65E5;;;;N;;;;; 33EA;IDEOGRAPHIC TELEGRAPH SYMBOL FOR DAY ELEVEN;So;0;L; 0031 0031 65E5;;;;N;;;;; 33EB;IDEOGRAPHIC TELEGRAPH SYMBOL FOR DAY TWELVE;So;0;L; 0031 0032 65E5;;;;N;;;;; 33EC;IDEOGRAPHIC TELEGRAPH SYMBOL FOR DAY THIRTEEN;So;0;L; 0031 0033 65E5;;;;N;;;;; 33ED;IDEOGRAPHIC TELEGRAPH SYMBOL FOR DAY FOURTEEN;So;0;L; 0031 0034 65E5;;;;N;;;;; 33EE;IDEOGRAPHIC TELEGRAPH SYMBOL FOR DAY FIFTEEN;So;0;L; 0031 0035 65E5;;;;N;;;;; 33EF;IDEOGRAPHIC TELEGRAPH SYMBOL FOR DAY SIXTEEN;So;0;L; 0031 0036 65E5;;;;N;;;;; 33F0;IDEOGRAPHIC TELEGRAPH SYMBOL FOR DAY SEVENTEEN;So;0;L; 0031 0037 65E5;;;;N;;;;; 33F1;IDEOGRAPHIC TELEGRAPH SYMBOL FOR DAY EIGHTEEN;So;0;L; 0031 0038 65E5;;;;N;;;;; 33F2;IDEOGRAPHIC TELEGRAPH SYMBOL FOR DAY NINETEEN;So;0;L; 0031 0039 65E5;;;;N;;;;; 33F3;IDEOGRAPHIC TELEGRAPH SYMBOL FOR DAY TWENTY;So;0;L; 0032 0030 65E5;;;;N;;;;; 33F4;IDEOGRAPHIC TELEGRAPH SYMBOL FOR DAY TWENTY-ONE;So;0;L; 0032 0031 65E5;;;;N;;;;; 33F5;IDEOGRAPHIC TELEGRAPH SYMBOL FOR DAY TWENTY-TWO;So;0;L; 0032 0032 65E5;;;;N;;;;; 33F6;IDEOGRAPHIC TELEGRAPH SYMBOL FOR DAY TWENTY-THREE;So;0;L; 0032 0033 65E5;;;;N;;;;; 33F7;IDEOGRAPHIC TELEGRAPH SYMBOL FOR DAY TWENTY-FOUR;So;0;L; 0032 0034 65E5;;;;N;;;;; 33F8;IDEOGRAPHIC TELEGRAPH SYMBOL FOR DAY TWENTY-FIVE;So;0;L; 0032 0035 65E5;;;;N;;;;; 33F9;IDEOGRAPHIC TELEGRAPH SYMBOL FOR DAY TWENTY-SIX;So;0;L; 0032 0036 65E5;;;;N;;;;; 33FA;IDEOGRAPHIC TELEGRAPH SYMBOL FOR DAY TWENTY-SEVEN;So;0;L; 0032 0037 65E5;;;;N;;;;; 33FB;IDEOGRAPHIC TELEGRAPH SYMBOL FOR DAY TWENTY-EIGHT;So;0;L; 0032 0038 65E5;;;;N;;;;; 33FC;IDEOGRAPHIC TELEGRAPH SYMBOL FOR DAY TWENTY-NINE;So;0;L; 0032 0039 65E5;;;;N;;;;; 33FD;IDEOGRAPHIC TELEGRAPH SYMBOL FOR DAY THIRTY;So;0;L; 0033 0030 65E5;;;;N;;;;; 33FE;IDEOGRAPHIC TELEGRAPH SYMBOL FOR DAY THIRTY-ONE;So;0;L; 0033 0031 65E5;;;;N;;;;; 33FF;SQUARE GAL;So;0;ON; 0067 0061 006C;;;;N;;;;; 3400;;Lo;0;L;;;;;N;;;;; 4DB5;;Lo;0;L;;;;;N;;;;; 4DC0;HEXAGRAM FOR THE CREATIVE HEAVEN;So;0;ON;;;;;N;;;;; 4DC1;HEXAGRAM FOR THE RECEPTIVE EARTH;So;0;ON;;;;;N;;;;; 4DC2;HEXAGRAM FOR DIFFICULTY AT THE BEGINNING;So;0;ON;;;;;N;;;;; 4DC3;HEXAGRAM FOR YOUTHFUL FOLLY;So;0;ON;;;;;N;;;;; 4DC4;HEXAGRAM FOR WAITING;So;0;ON;;;;;N;;;;; 4DC5;HEXAGRAM FOR CONFLICT;So;0;ON;;;;;N;;;;; 4DC6;HEXAGRAM FOR THE ARMY;So;0;ON;;;;;N;;;;; 4DC7;HEXAGRAM FOR HOLDING TOGETHER;So;0;ON;;;;;N;;;;; 4DC8;HEXAGRAM FOR SMALL TAMING;So;0;ON;;;;;N;;;;; 4DC9;HEXAGRAM FOR TREADING;So;0;ON;;;;;N;;;;; 4DCA;HEXAGRAM FOR PEACE;So;0;ON;;;;;N;;;;; 4DCB;HEXAGRAM FOR STANDSTILL;So;0;ON;;;;;N;;;;; 4DCC;HEXAGRAM FOR FELLOWSHIP;So;0;ON;;;;;N;;;;; 4DCD;HEXAGRAM FOR GREAT POSSESSION;So;0;ON;;;;;N;;;;; 4DCE;HEXAGRAM FOR MODESTY;So;0;ON;;;;;N;;;;; 4DCF;HEXAGRAM FOR ENTHUSIASM;So;0;ON;;;;;N;;;;; 4DD0;HEXAGRAM FOR FOLLOWING;So;0;ON;;;;;N;;;;; 4DD1;HEXAGRAM FOR WORK ON THE DECAYED;So;0;ON;;;;;N;;;;; 4DD2;HEXAGRAM FOR APPROACH;So;0;ON;;;;;N;;;;; 4DD3;HEXAGRAM FOR CONTEMPLATION;So;0;ON;;;;;N;;;;; 4DD4;HEXAGRAM FOR BITING THROUGH;So;0;ON;;;;;N;;;;; 4DD5;HEXAGRAM FOR GRACE;So;0;ON;;;;;N;;;;; 4DD6;HEXAGRAM FOR SPLITTING APART;So;0;ON;;;;;N;;;;; 4DD7;HEXAGRAM FOR RETURN;So;0;ON;;;;;N;;;;; 4DD8;HEXAGRAM FOR INNOCENCE;So;0;ON;;;;;N;;;;; 4DD9;HEXAGRAM FOR GREAT TAMING;So;0;ON;;;;;N;;;;; 4DDA;HEXAGRAM FOR MOUTH CORNERS;So;0;ON;;;;;N;;;;; 4DDB;HEXAGRAM FOR GREAT PREPONDERANCE;So;0;ON;;;;;N;;;;; 4DDC;HEXAGRAM FOR THE ABYSMAL WATER;So;0;ON;;;;;N;;;;; 4DDD;HEXAGRAM FOR THE CLINGING FIRE;So;0;ON;;;;;N;;;;; 4DDE;HEXAGRAM FOR INFLUENCE;So;0;ON;;;;;N;;;;; 4DDF;HEXAGRAM FOR DURATION;So;0;ON;;;;;N;;;;; 4DE0;HEXAGRAM FOR RETREAT;So;0;ON;;;;;N;;;;; 4DE1;HEXAGRAM FOR GREAT POWER;So;0;ON;;;;;N;;;;; 4DE2;HEXAGRAM FOR PROGRESS;So;0;ON;;;;;N;;;;; 4DE3;HEXAGRAM FOR DARKENING OF THE LIGHT;So;0;ON;;;;;N;;;;; 4DE4;HEXAGRAM FOR THE FAMILY;So;0;ON;;;;;N;;;;; 4DE5;HEXAGRAM FOR OPPOSITION;So;0;ON;;;;;N;;;;; 4DE6;HEXAGRAM FOR OBSTRUCTION;So;0;ON;;;;;N;;;;; 4DE7;HEXAGRAM FOR DELIVERANCE;So;0;ON;;;;;N;;;;; 4DE8;HEXAGRAM FOR DECREASE;So;0;ON;;;;;N;;;;; 4DE9;HEXAGRAM FOR INCREASE;So;0;ON;;;;;N;;;;; 4DEA;HEXAGRAM FOR BREAKTHROUGH;So;0;ON;;;;;N;;;;; 4DEB;HEXAGRAM FOR COMING TO MEET;So;0;ON;;;;;N;;;;; 4DEC;HEXAGRAM FOR GATHERING TOGETHER;So;0;ON;;;;;N;;;;; 4DED;HEXAGRAM FOR PUSHING UPWARD;So;0;ON;;;;;N;;;;; 4DEE;HEXAGRAM FOR OPPRESSION;So;0;ON;;;;;N;;;;; 4DEF;HEXAGRAM FOR THE WELL;So;0;ON;;;;;N;;;;; 4DF0;HEXAGRAM FOR REVOLUTION;So;0;ON;;;;;N;;;;; 4DF1;HEXAGRAM FOR THE CAULDRON;So;0;ON;;;;;N;;;;; 4DF2;HEXAGRAM FOR THE AROUSING THUNDER;So;0;ON;;;;;N;;;;; 4DF3;HEXAGRAM FOR THE KEEPING STILL MOUNTAIN;So;0;ON;;;;;N;;;;; 4DF4;HEXAGRAM FOR DEVELOPMENT;So;0;ON;;;;;N;;;;; 4DF5;HEXAGRAM FOR THE MARRYING MAIDEN;So;0;ON;;;;;N;;;;; 4DF6;HEXAGRAM FOR ABUNDANCE;So;0;ON;;;;;N;;;;; 4DF7;HEXAGRAM FOR THE WANDERER;So;0;ON;;;;;N;;;;; 4DF8;HEXAGRAM FOR THE GENTLE WIND;So;0;ON;;;;;N;;;;; 4DF9;HEXAGRAM FOR THE JOYOUS LAKE;So;0;ON;;;;;N;;;;; 4DFA;HEXAGRAM FOR DISPERSION;So;0;ON;;;;;N;;;;; 4DFB;HEXAGRAM FOR LIMITATION;So;0;ON;;;;;N;;;;; 4DFC;HEXAGRAM FOR INNER TRUTH;So;0;ON;;;;;N;;;;; 4DFD;HEXAGRAM FOR SMALL PREPONDERANCE;So;0;ON;;;;;N;;;;; 4DFE;HEXAGRAM FOR AFTER COMPLETION;So;0;ON;;;;;N;;;;; 4DFF;HEXAGRAM FOR BEFORE COMPLETION;So;0;ON;;;;;N;;;;; 4E00;;Lo;0;L;;;;;N;;;;; 9FCC;;Lo;0;L;;;;;N;;;;; A000;YI SYLLABLE IT;Lo;0;L;;;;;N;;;;; A001;YI SYLLABLE IX;Lo;0;L;;;;;N;;;;; A002;YI SYLLABLE I;Lo;0;L;;;;;N;;;;; A003;YI SYLLABLE IP;Lo;0;L;;;;;N;;;;; A004;YI SYLLABLE IET;Lo;0;L;;;;;N;;;;; A005;YI SYLLABLE IEX;Lo;0;L;;;;;N;;;;; A006;YI SYLLABLE IE;Lo;0;L;;;;;N;;;;; A007;YI SYLLABLE IEP;Lo;0;L;;;;;N;;;;; A008;YI SYLLABLE AT;Lo;0;L;;;;;N;;;;; A009;YI SYLLABLE AX;Lo;0;L;;;;;N;;;;; A00A;YI SYLLABLE A;Lo;0;L;;;;;N;;;;; A00B;YI SYLLABLE AP;Lo;0;L;;;;;N;;;;; A00C;YI SYLLABLE UOX;Lo;0;L;;;;;N;;;;; A00D;YI SYLLABLE UO;Lo;0;L;;;;;N;;;;; A00E;YI SYLLABLE UOP;Lo;0;L;;;;;N;;;;; A00F;YI SYLLABLE OT;Lo;0;L;;;;;N;;;;; A010;YI SYLLABLE OX;Lo;0;L;;;;;N;;;;; A011;YI SYLLABLE O;Lo;0;L;;;;;N;;;;; A012;YI SYLLABLE OP;Lo;0;L;;;;;N;;;;; A013;YI SYLLABLE EX;Lo;0;L;;;;;N;;;;; A014;YI SYLLABLE E;Lo;0;L;;;;;N;;;;; A015;YI SYLLABLE WU;Lm;0;L;;;;;N;;;;; A016;YI SYLLABLE BIT;Lo;0;L;;;;;N;;;;; A017;YI SYLLABLE BIX;Lo;0;L;;;;;N;;;;; A018;YI SYLLABLE BI;Lo;0;L;;;;;N;;;;; A019;YI SYLLABLE BIP;Lo;0;L;;;;;N;;;;; A01A;YI SYLLABLE BIET;Lo;0;L;;;;;N;;;;; A01B;YI SYLLABLE BIEX;Lo;0;L;;;;;N;;;;; A01C;YI SYLLABLE BIE;Lo;0;L;;;;;N;;;;; A01D;YI SYLLABLE BIEP;Lo;0;L;;;;;N;;;;; A01E;YI SYLLABLE BAT;Lo;0;L;;;;;N;;;;; A01F;YI SYLLABLE BAX;Lo;0;L;;;;;N;;;;; A020;YI SYLLABLE BA;Lo;0;L;;;;;N;;;;; A021;YI SYLLABLE BAP;Lo;0;L;;;;;N;;;;; A022;YI SYLLABLE BUOX;Lo;0;L;;;;;N;;;;; A023;YI SYLLABLE BUO;Lo;0;L;;;;;N;;;;; A024;YI SYLLABLE BUOP;Lo;0;L;;;;;N;;;;; A025;YI SYLLABLE BOT;Lo;0;L;;;;;N;;;;; A026;YI SYLLABLE BOX;Lo;0;L;;;;;N;;;;; A027;YI SYLLABLE BO;Lo;0;L;;;;;N;;;;; A028;YI SYLLABLE BOP;Lo;0;L;;;;;N;;;;; A029;YI SYLLABLE BEX;Lo;0;L;;;;;N;;;;; A02A;YI SYLLABLE BE;Lo;0;L;;;;;N;;;;; A02B;YI SYLLABLE BEP;Lo;0;L;;;;;N;;;;; A02C;YI SYLLABLE BUT;Lo;0;L;;;;;N;;;;; A02D;YI SYLLABLE BUX;Lo;0;L;;;;;N;;;;; A02E;YI SYLLABLE BU;Lo;0;L;;;;;N;;;;; A02F;YI SYLLABLE BUP;Lo;0;L;;;;;N;;;;; A030;YI SYLLABLE BURX;Lo;0;L;;;;;N;;;;; A031;YI SYLLABLE BUR;Lo;0;L;;;;;N;;;;; A032;YI SYLLABLE BYT;Lo;0;L;;;;;N;;;;; A033;YI SYLLABLE BYX;Lo;0;L;;;;;N;;;;; A034;YI SYLLABLE BY;Lo;0;L;;;;;N;;;;; A035;YI SYLLABLE BYP;Lo;0;L;;;;;N;;;;; A036;YI SYLLABLE BYRX;Lo;0;L;;;;;N;;;;; A037;YI SYLLABLE BYR;Lo;0;L;;;;;N;;;;; A038;YI SYLLABLE PIT;Lo;0;L;;;;;N;;;;; A039;YI SYLLABLE PIX;Lo;0;L;;;;;N;;;;; A03A;YI SYLLABLE PI;Lo;0;L;;;;;N;;;;; A03B;YI SYLLABLE PIP;Lo;0;L;;;;;N;;;;; A03C;YI SYLLABLE PIEX;Lo;0;L;;;;;N;;;;; A03D;YI SYLLABLE PIE;Lo;0;L;;;;;N;;;;; A03E;YI SYLLABLE PIEP;Lo;0;L;;;;;N;;;;; A03F;YI SYLLABLE PAT;Lo;0;L;;;;;N;;;;; A040;YI SYLLABLE PAX;Lo;0;L;;;;;N;;;;; A041;YI SYLLABLE PA;Lo;0;L;;;;;N;;;;; A042;YI SYLLABLE PAP;Lo;0;L;;;;;N;;;;; A043;YI SYLLABLE PUOX;Lo;0;L;;;;;N;;;;; A044;YI SYLLABLE PUO;Lo;0;L;;;;;N;;;;; A045;YI SYLLABLE PUOP;Lo;0;L;;;;;N;;;;; A046;YI SYLLABLE POT;Lo;0;L;;;;;N;;;;; A047;YI SYLLABLE POX;Lo;0;L;;;;;N;;;;; A048;YI SYLLABLE PO;Lo;0;L;;;;;N;;;;; A049;YI SYLLABLE POP;Lo;0;L;;;;;N;;;;; A04A;YI SYLLABLE PUT;Lo;0;L;;;;;N;;;;; A04B;YI SYLLABLE PUX;Lo;0;L;;;;;N;;;;; A04C;YI SYLLABLE PU;Lo;0;L;;;;;N;;;;; A04D;YI SYLLABLE PUP;Lo;0;L;;;;;N;;;;; A04E;YI SYLLABLE PURX;Lo;0;L;;;;;N;;;;; A04F;YI SYLLABLE PUR;Lo;0;L;;;;;N;;;;; A050;YI SYLLABLE PYT;Lo;0;L;;;;;N;;;;; A051;YI SYLLABLE PYX;Lo;0;L;;;;;N;;;;; A052;YI SYLLABLE PY;Lo;0;L;;;;;N;;;;; A053;YI SYLLABLE PYP;Lo;0;L;;;;;N;;;;; A054;YI SYLLABLE PYRX;Lo;0;L;;;;;N;;;;; A055;YI SYLLABLE PYR;Lo;0;L;;;;;N;;;;; A056;YI SYLLABLE BBIT;Lo;0;L;;;;;N;;;;; A057;YI SYLLABLE BBIX;Lo;0;L;;;;;N;;;;; A058;YI SYLLABLE BBI;Lo;0;L;;;;;N;;;;; A059;YI SYLLABLE BBIP;Lo;0;L;;;;;N;;;;; A05A;YI SYLLABLE BBIET;Lo;0;L;;;;;N;;;;; A05B;YI SYLLABLE BBIEX;Lo;0;L;;;;;N;;;;; A05C;YI SYLLABLE BBIE;Lo;0;L;;;;;N;;;;; A05D;YI SYLLABLE BBIEP;Lo;0;L;;;;;N;;;;; A05E;YI SYLLABLE BBAT;Lo;0;L;;;;;N;;;;; A05F;YI SYLLABLE BBAX;Lo;0;L;;;;;N;;;;; A060;YI SYLLABLE BBA;Lo;0;L;;;;;N;;;;; A061;YI SYLLABLE BBAP;Lo;0;L;;;;;N;;;;; A062;YI SYLLABLE BBUOX;Lo;0;L;;;;;N;;;;; A063;YI SYLLABLE BBUO;Lo;0;L;;;;;N;;;;; A064;YI SYLLABLE BBUOP;Lo;0;L;;;;;N;;;;; A065;YI SYLLABLE BBOT;Lo;0;L;;;;;N;;;;; A066;YI SYLLABLE BBOX;Lo;0;L;;;;;N;;;;; A067;YI SYLLABLE BBO;Lo;0;L;;;;;N;;;;; A068;YI SYLLABLE BBOP;Lo;0;L;;;;;N;;;;; A069;YI SYLLABLE BBEX;Lo;0;L;;;;;N;;;;; A06A;YI SYLLABLE BBE;Lo;0;L;;;;;N;;;;; A06B;YI SYLLABLE BBEP;Lo;0;L;;;;;N;;;;; A06C;YI SYLLABLE BBUT;Lo;0;L;;;;;N;;;;; A06D;YI SYLLABLE BBUX;Lo;0;L;;;;;N;;;;; A06E;YI SYLLABLE BBU;Lo;0;L;;;;;N;;;;; A06F;YI SYLLABLE BBUP;Lo;0;L;;;;;N;;;;; A070;YI SYLLABLE BBURX;Lo;0;L;;;;;N;;;;; A071;YI SYLLABLE BBUR;Lo;0;L;;;;;N;;;;; A072;YI SYLLABLE BBYT;Lo;0;L;;;;;N;;;;; A073;YI SYLLABLE BBYX;Lo;0;L;;;;;N;;;;; A074;YI SYLLABLE BBY;Lo;0;L;;;;;N;;;;; A075;YI SYLLABLE BBYP;Lo;0;L;;;;;N;;;;; A076;YI SYLLABLE NBIT;Lo;0;L;;;;;N;;;;; A077;YI SYLLABLE NBIX;Lo;0;L;;;;;N;;;;; A078;YI SYLLABLE NBI;Lo;0;L;;;;;N;;;;; A079;YI SYLLABLE NBIP;Lo;0;L;;;;;N;;;;; A07A;YI SYLLABLE NBIEX;Lo;0;L;;;;;N;;;;; A07B;YI SYLLABLE NBIE;Lo;0;L;;;;;N;;;;; A07C;YI SYLLABLE NBIEP;Lo;0;L;;;;;N;;;;; A07D;YI SYLLABLE NBAT;Lo;0;L;;;;;N;;;;; A07E;YI SYLLABLE NBAX;Lo;0;L;;;;;N;;;;; A07F;YI SYLLABLE NBA;Lo;0;L;;;;;N;;;;; A080;YI SYLLABLE NBAP;Lo;0;L;;;;;N;;;;; A081;YI SYLLABLE NBOT;Lo;0;L;;;;;N;;;;; A082;YI SYLLABLE NBOX;Lo;0;L;;;;;N;;;;; A083;YI SYLLABLE NBO;Lo;0;L;;;;;N;;;;; A084;YI SYLLABLE NBOP;Lo;0;L;;;;;N;;;;; A085;YI SYLLABLE NBUT;Lo;0;L;;;;;N;;;;; A086;YI SYLLABLE NBUX;Lo;0;L;;;;;N;;;;; A087;YI SYLLABLE NBU;Lo;0;L;;;;;N;;;;; A088;YI SYLLABLE NBUP;Lo;0;L;;;;;N;;;;; A089;YI SYLLABLE NBURX;Lo;0;L;;;;;N;;;;; A08A;YI SYLLABLE NBUR;Lo;0;L;;;;;N;;;;; A08B;YI SYLLABLE NBYT;Lo;0;L;;;;;N;;;;; A08C;YI SYLLABLE NBYX;Lo;0;L;;;;;N;;;;; A08D;YI SYLLABLE NBY;Lo;0;L;;;;;N;;;;; A08E;YI SYLLABLE NBYP;Lo;0;L;;;;;N;;;;; A08F;YI SYLLABLE NBYRX;Lo;0;L;;;;;N;;;;; A090;YI SYLLABLE NBYR;Lo;0;L;;;;;N;;;;; A091;YI SYLLABLE HMIT;Lo;0;L;;;;;N;;;;; A092;YI SYLLABLE HMIX;Lo;0;L;;;;;N;;;;; A093;YI SYLLABLE HMI;Lo;0;L;;;;;N;;;;; A094;YI SYLLABLE HMIP;Lo;0;L;;;;;N;;;;; A095;YI SYLLABLE HMIEX;Lo;0;L;;;;;N;;;;; A096;YI SYLLABLE HMIE;Lo;0;L;;;;;N;;;;; A097;YI SYLLABLE HMIEP;Lo;0;L;;;;;N;;;;; A098;YI SYLLABLE HMAT;Lo;0;L;;;;;N;;;;; A099;YI SYLLABLE HMAX;Lo;0;L;;;;;N;;;;; A09A;YI SYLLABLE HMA;Lo;0;L;;;;;N;;;;; A09B;YI SYLLABLE HMAP;Lo;0;L;;;;;N;;;;; A09C;YI SYLLABLE HMUOX;Lo;0;L;;;;;N;;;;; A09D;YI SYLLABLE HMUO;Lo;0;L;;;;;N;;;;; A09E;YI SYLLABLE HMUOP;Lo;0;L;;;;;N;;;;; A09F;YI SYLLABLE HMOT;Lo;0;L;;;;;N;;;;; A0A0;YI SYLLABLE HMOX;Lo;0;L;;;;;N;;;;; A0A1;YI SYLLABLE HMO;Lo;0;L;;;;;N;;;;; A0A2;YI SYLLABLE HMOP;Lo;0;L;;;;;N;;;;; A0A3;YI SYLLABLE HMUT;Lo;0;L;;;;;N;;;;; A0A4;YI SYLLABLE HMUX;Lo;0;L;;;;;N;;;;; A0A5;YI SYLLABLE HMU;Lo;0;L;;;;;N;;;;; A0A6;YI SYLLABLE HMUP;Lo;0;L;;;;;N;;;;; A0A7;YI SYLLABLE HMURX;Lo;0;L;;;;;N;;;;; A0A8;YI SYLLABLE HMUR;Lo;0;L;;;;;N;;;;; A0A9;YI SYLLABLE HMYX;Lo;0;L;;;;;N;;;;; A0AA;YI SYLLABLE HMY;Lo;0;L;;;;;N;;;;; A0AB;YI SYLLABLE HMYP;Lo;0;L;;;;;N;;;;; A0AC;YI SYLLABLE HMYRX;Lo;0;L;;;;;N;;;;; A0AD;YI SYLLABLE HMYR;Lo;0;L;;;;;N;;;;; A0AE;YI SYLLABLE MIT;Lo;0;L;;;;;N;;;;; A0AF;YI SYLLABLE MIX;Lo;0;L;;;;;N;;;;; A0B0;YI SYLLABLE MI;Lo;0;L;;;;;N;;;;; A0B1;YI SYLLABLE MIP;Lo;0;L;;;;;N;;;;; A0B2;YI SYLLABLE MIEX;Lo;0;L;;;;;N;;;;; A0B3;YI SYLLABLE MIE;Lo;0;L;;;;;N;;;;; A0B4;YI SYLLABLE MIEP;Lo;0;L;;;;;N;;;;; A0B5;YI SYLLABLE MAT;Lo;0;L;;;;;N;;;;; A0B6;YI SYLLABLE MAX;Lo;0;L;;;;;N;;;;; A0B7;YI SYLLABLE MA;Lo;0;L;;;;;N;;;;; A0B8;YI SYLLABLE MAP;Lo;0;L;;;;;N;;;;; A0B9;YI SYLLABLE MUOT;Lo;0;L;;;;;N;;;;; A0BA;YI SYLLABLE MUOX;Lo;0;L;;;;;N;;;;; A0BB;YI SYLLABLE MUO;Lo;0;L;;;;;N;;;;; A0BC;YI SYLLABLE MUOP;Lo;0;L;;;;;N;;;;; A0BD;YI SYLLABLE MOT;Lo;0;L;;;;;N;;;;; A0BE;YI SYLLABLE MOX;Lo;0;L;;;;;N;;;;; A0BF;YI SYLLABLE MO;Lo;0;L;;;;;N;;;;; A0C0;YI SYLLABLE MOP;Lo;0;L;;;;;N;;;;; A0C1;YI SYLLABLE MEX;Lo;0;L;;;;;N;;;;; A0C2;YI SYLLABLE ME;Lo;0;L;;;;;N;;;;; A0C3;YI SYLLABLE MUT;Lo;0;L;;;;;N;;;;; A0C4;YI SYLLABLE MUX;Lo;0;L;;;;;N;;;;; A0C5;YI SYLLABLE MU;Lo;0;L;;;;;N;;;;; A0C6;YI SYLLABLE MUP;Lo;0;L;;;;;N;;;;; A0C7;YI SYLLABLE MURX;Lo;0;L;;;;;N;;;;; A0C8;YI SYLLABLE MUR;Lo;0;L;;;;;N;;;;; A0C9;YI SYLLABLE MYT;Lo;0;L;;;;;N;;;;; A0CA;YI SYLLABLE MYX;Lo;0;L;;;;;N;;;;; A0CB;YI SYLLABLE MY;Lo;0;L;;;;;N;;;;; A0CC;YI SYLLABLE MYP;Lo;0;L;;;;;N;;;;; A0CD;YI SYLLABLE FIT;Lo;0;L;;;;;N;;;;; A0CE;YI SYLLABLE FIX;Lo;0;L;;;;;N;;;;; A0CF;YI SYLLABLE FI;Lo;0;L;;;;;N;;;;; A0D0;YI SYLLABLE FIP;Lo;0;L;;;;;N;;;;; A0D1;YI SYLLABLE FAT;Lo;0;L;;;;;N;;;;; A0D2;YI SYLLABLE FAX;Lo;0;L;;;;;N;;;;; A0D3;YI SYLLABLE FA;Lo;0;L;;;;;N;;;;; A0D4;YI SYLLABLE FAP;Lo;0;L;;;;;N;;;;; A0D5;YI SYLLABLE FOX;Lo;0;L;;;;;N;;;;; A0D6;YI SYLLABLE FO;Lo;0;L;;;;;N;;;;; A0D7;YI SYLLABLE FOP;Lo;0;L;;;;;N;;;;; A0D8;YI SYLLABLE FUT;Lo;0;L;;;;;N;;;;; A0D9;YI SYLLABLE FUX;Lo;0;L;;;;;N;;;;; A0DA;YI SYLLABLE FU;Lo;0;L;;;;;N;;;;; A0DB;YI SYLLABLE FUP;Lo;0;L;;;;;N;;;;; A0DC;YI SYLLABLE FURX;Lo;0;L;;;;;N;;;;; A0DD;YI SYLLABLE FUR;Lo;0;L;;;;;N;;;;; A0DE;YI SYLLABLE FYT;Lo;0;L;;;;;N;;;;; A0DF;YI SYLLABLE FYX;Lo;0;L;;;;;N;;;;; A0E0;YI SYLLABLE FY;Lo;0;L;;;;;N;;;;; A0E1;YI SYLLABLE FYP;Lo;0;L;;;;;N;;;;; A0E2;YI SYLLABLE VIT;Lo;0;L;;;;;N;;;;; A0E3;YI SYLLABLE VIX;Lo;0;L;;;;;N;;;;; A0E4;YI SYLLABLE VI;Lo;0;L;;;;;N;;;;; A0E5;YI SYLLABLE VIP;Lo;0;L;;;;;N;;;;; A0E6;YI SYLLABLE VIET;Lo;0;L;;;;;N;;;;; A0E7;YI SYLLABLE VIEX;Lo;0;L;;;;;N;;;;; A0E8;YI SYLLABLE VIE;Lo;0;L;;;;;N;;;;; A0E9;YI SYLLABLE VIEP;Lo;0;L;;;;;N;;;;; A0EA;YI SYLLABLE VAT;Lo;0;L;;;;;N;;;;; A0EB;YI SYLLABLE VAX;Lo;0;L;;;;;N;;;;; A0EC;YI SYLLABLE VA;Lo;0;L;;;;;N;;;;; A0ED;YI SYLLABLE VAP;Lo;0;L;;;;;N;;;;; A0EE;YI SYLLABLE VOT;Lo;0;L;;;;;N;;;;; A0EF;YI SYLLABLE VOX;Lo;0;L;;;;;N;;;;; A0F0;YI SYLLABLE VO;Lo;0;L;;;;;N;;;;; A0F1;YI SYLLABLE VOP;Lo;0;L;;;;;N;;;;; A0F2;YI SYLLABLE VEX;Lo;0;L;;;;;N;;;;; A0F3;YI SYLLABLE VEP;Lo;0;L;;;;;N;;;;; A0F4;YI SYLLABLE VUT;Lo;0;L;;;;;N;;;;; A0F5;YI SYLLABLE VUX;Lo;0;L;;;;;N;;;;; A0F6;YI SYLLABLE VU;Lo;0;L;;;;;N;;;;; A0F7;YI SYLLABLE VUP;Lo;0;L;;;;;N;;;;; A0F8;YI SYLLABLE VURX;Lo;0;L;;;;;N;;;;; A0F9;YI SYLLABLE VUR;Lo;0;L;;;;;N;;;;; A0FA;YI SYLLABLE VYT;Lo;0;L;;;;;N;;;;; A0FB;YI SYLLABLE VYX;Lo;0;L;;;;;N;;;;; A0FC;YI SYLLABLE VY;Lo;0;L;;;;;N;;;;; A0FD;YI SYLLABLE VYP;Lo;0;L;;;;;N;;;;; A0FE;YI SYLLABLE VYRX;Lo;0;L;;;;;N;;;;; A0FF;YI SYLLABLE VYR;Lo;0;L;;;;;N;;;;; A100;YI SYLLABLE DIT;Lo;0;L;;;;;N;;;;; A101;YI SYLLABLE DIX;Lo;0;L;;;;;N;;;;; A102;YI SYLLABLE DI;Lo;0;L;;;;;N;;;;; A103;YI SYLLABLE DIP;Lo;0;L;;;;;N;;;;; A104;YI SYLLABLE DIEX;Lo;0;L;;;;;N;;;;; A105;YI SYLLABLE DIE;Lo;0;L;;;;;N;;;;; A106;YI SYLLABLE DIEP;Lo;0;L;;;;;N;;;;; A107;YI SYLLABLE DAT;Lo;0;L;;;;;N;;;;; A108;YI SYLLABLE DAX;Lo;0;L;;;;;N;;;;; A109;YI SYLLABLE DA;Lo;0;L;;;;;N;;;;; A10A;YI SYLLABLE DAP;Lo;0;L;;;;;N;;;;; A10B;YI SYLLABLE DUOX;Lo;0;L;;;;;N;;;;; A10C;YI SYLLABLE DUO;Lo;0;L;;;;;N;;;;; A10D;YI SYLLABLE DOT;Lo;0;L;;;;;N;;;;; A10E;YI SYLLABLE DOX;Lo;0;L;;;;;N;;;;; A10F;YI SYLLABLE DO;Lo;0;L;;;;;N;;;;; A110;YI SYLLABLE DOP;Lo;0;L;;;;;N;;;;; A111;YI SYLLABLE DEX;Lo;0;L;;;;;N;;;;; A112;YI SYLLABLE DE;Lo;0;L;;;;;N;;;;; A113;YI SYLLABLE DEP;Lo;0;L;;;;;N;;;;; A114;YI SYLLABLE DUT;Lo;0;L;;;;;N;;;;; A115;YI SYLLABLE DUX;Lo;0;L;;;;;N;;;;; A116;YI SYLLABLE DU;Lo;0;L;;;;;N;;;;; A117;YI SYLLABLE DUP;Lo;0;L;;;;;N;;;;; A118;YI SYLLABLE DURX;Lo;0;L;;;;;N;;;;; A119;YI SYLLABLE DUR;Lo;0;L;;;;;N;;;;; A11A;YI SYLLABLE TIT;Lo;0;L;;;;;N;;;;; A11B;YI SYLLABLE TIX;Lo;0;L;;;;;N;;;;; A11C;YI SYLLABLE TI;Lo;0;L;;;;;N;;;;; A11D;YI SYLLABLE TIP;Lo;0;L;;;;;N;;;;; A11E;YI SYLLABLE TIEX;Lo;0;L;;;;;N;;;;; A11F;YI SYLLABLE TIE;Lo;0;L;;;;;N;;;;; A120;YI SYLLABLE TIEP;Lo;0;L;;;;;N;;;;; A121;YI SYLLABLE TAT;Lo;0;L;;;;;N;;;;; A122;YI SYLLABLE TAX;Lo;0;L;;;;;N;;;;; A123;YI SYLLABLE TA;Lo;0;L;;;;;N;;;;; A124;YI SYLLABLE TAP;Lo;0;L;;;;;N;;;;; A125;YI SYLLABLE TUOT;Lo;0;L;;;;;N;;;;; A126;YI SYLLABLE TUOX;Lo;0;L;;;;;N;;;;; A127;YI SYLLABLE TUO;Lo;0;L;;;;;N;;;;; A128;YI SYLLABLE TUOP;Lo;0;L;;;;;N;;;;; A129;YI SYLLABLE TOT;Lo;0;L;;;;;N;;;;; A12A;YI SYLLABLE TOX;Lo;0;L;;;;;N;;;;; A12B;YI SYLLABLE TO;Lo;0;L;;;;;N;;;;; A12C;YI SYLLABLE TOP;Lo;0;L;;;;;N;;;;; A12D;YI SYLLABLE TEX;Lo;0;L;;;;;N;;;;; A12E;YI SYLLABLE TE;Lo;0;L;;;;;N;;;;; A12F;YI SYLLABLE TEP;Lo;0;L;;;;;N;;;;; A130;YI SYLLABLE TUT;Lo;0;L;;;;;N;;;;; A131;YI SYLLABLE TUX;Lo;0;L;;;;;N;;;;; A132;YI SYLLABLE TU;Lo;0;L;;;;;N;;;;; A133;YI SYLLABLE TUP;Lo;0;L;;;;;N;;;;; A134;YI SYLLABLE TURX;Lo;0;L;;;;;N;;;;; A135;YI SYLLABLE TUR;Lo;0;L;;;;;N;;;;; A136;YI SYLLABLE DDIT;Lo;0;L;;;;;N;;;;; A137;YI SYLLABLE DDIX;Lo;0;L;;;;;N;;;;; A138;YI SYLLABLE DDI;Lo;0;L;;;;;N;;;;; A139;YI SYLLABLE DDIP;Lo;0;L;;;;;N;;;;; A13A;YI SYLLABLE DDIEX;Lo;0;L;;;;;N;;;;; A13B;YI SYLLABLE DDIE;Lo;0;L;;;;;N;;;;; A13C;YI SYLLABLE DDIEP;Lo;0;L;;;;;N;;;;; A13D;YI SYLLABLE DDAT;Lo;0;L;;;;;N;;;;; A13E;YI SYLLABLE DDAX;Lo;0;L;;;;;N;;;;; A13F;YI SYLLABLE DDA;Lo;0;L;;;;;N;;;;; A140;YI SYLLABLE DDAP;Lo;0;L;;;;;N;;;;; A141;YI SYLLABLE DDUOX;Lo;0;L;;;;;N;;;;; A142;YI SYLLABLE DDUO;Lo;0;L;;;;;N;;;;; A143;YI SYLLABLE DDUOP;Lo;0;L;;;;;N;;;;; A144;YI SYLLABLE DDOT;Lo;0;L;;;;;N;;;;; A145;YI SYLLABLE DDOX;Lo;0;L;;;;;N;;;;; A146;YI SYLLABLE DDO;Lo;0;L;;;;;N;;;;; A147;YI SYLLABLE DDOP;Lo;0;L;;;;;N;;;;; A148;YI SYLLABLE DDEX;Lo;0;L;;;;;N;;;;; A149;YI SYLLABLE DDE;Lo;0;L;;;;;N;;;;; A14A;YI SYLLABLE DDEP;Lo;0;L;;;;;N;;;;; A14B;YI SYLLABLE DDUT;Lo;0;L;;;;;N;;;;; A14C;YI SYLLABLE DDUX;Lo;0;L;;;;;N;;;;; A14D;YI SYLLABLE DDU;Lo;0;L;;;;;N;;;;; A14E;YI SYLLABLE DDUP;Lo;0;L;;;;;N;;;;; A14F;YI SYLLABLE DDURX;Lo;0;L;;;;;N;;;;; A150;YI SYLLABLE DDUR;Lo;0;L;;;;;N;;;;; A151;YI SYLLABLE NDIT;Lo;0;L;;;;;N;;;;; A152;YI SYLLABLE NDIX;Lo;0;L;;;;;N;;;;; A153;YI SYLLABLE NDI;Lo;0;L;;;;;N;;;;; A154;YI SYLLABLE NDIP;Lo;0;L;;;;;N;;;;; A155;YI SYLLABLE NDIEX;Lo;0;L;;;;;N;;;;; A156;YI SYLLABLE NDIE;Lo;0;L;;;;;N;;;;; A157;YI SYLLABLE NDAT;Lo;0;L;;;;;N;;;;; A158;YI SYLLABLE NDAX;Lo;0;L;;;;;N;;;;; A159;YI SYLLABLE NDA;Lo;0;L;;;;;N;;;;; A15A;YI SYLLABLE NDAP;Lo;0;L;;;;;N;;;;; A15B;YI SYLLABLE NDOT;Lo;0;L;;;;;N;;;;; A15C;YI SYLLABLE NDOX;Lo;0;L;;;;;N;;;;; A15D;YI SYLLABLE NDO;Lo;0;L;;;;;N;;;;; A15E;YI SYLLABLE NDOP;Lo;0;L;;;;;N;;;;; A15F;YI SYLLABLE NDEX;Lo;0;L;;;;;N;;;;; A160;YI SYLLABLE NDE;Lo;0;L;;;;;N;;;;; A161;YI SYLLABLE NDEP;Lo;0;L;;;;;N;;;;; A162;YI SYLLABLE NDUT;Lo;0;L;;;;;N;;;;; A163;YI SYLLABLE NDUX;Lo;0;L;;;;;N;;;;; A164;YI SYLLABLE NDU;Lo;0;L;;;;;N;;;;; A165;YI SYLLABLE NDUP;Lo;0;L;;;;;N;;;;; A166;YI SYLLABLE NDURX;Lo;0;L;;;;;N;;;;; A167;YI SYLLABLE NDUR;Lo;0;L;;;;;N;;;;; A168;YI SYLLABLE HNIT;Lo;0;L;;;;;N;;;;; A169;YI SYLLABLE HNIX;Lo;0;L;;;;;N;;;;; A16A;YI SYLLABLE HNI;Lo;0;L;;;;;N;;;;; A16B;YI SYLLABLE HNIP;Lo;0;L;;;;;N;;;;; A16C;YI SYLLABLE HNIET;Lo;0;L;;;;;N;;;;; A16D;YI SYLLABLE HNIEX;Lo;0;L;;;;;N;;;;; A16E;YI SYLLABLE HNIE;Lo;0;L;;;;;N;;;;; A16F;YI SYLLABLE HNIEP;Lo;0;L;;;;;N;;;;; A170;YI SYLLABLE HNAT;Lo;0;L;;;;;N;;;;; A171;YI SYLLABLE HNAX;Lo;0;L;;;;;N;;;;; A172;YI SYLLABLE HNA;Lo;0;L;;;;;N;;;;; A173;YI SYLLABLE HNAP;Lo;0;L;;;;;N;;;;; A174;YI SYLLABLE HNUOX;Lo;0;L;;;;;N;;;;; A175;YI SYLLABLE HNUO;Lo;0;L;;;;;N;;;;; A176;YI SYLLABLE HNOT;Lo;0;L;;;;;N;;;;; A177;YI SYLLABLE HNOX;Lo;0;L;;;;;N;;;;; A178;YI SYLLABLE HNOP;Lo;0;L;;;;;N;;;;; A179;YI SYLLABLE HNEX;Lo;0;L;;;;;N;;;;; A17A;YI SYLLABLE HNE;Lo;0;L;;;;;N;;;;; A17B;YI SYLLABLE HNEP;Lo;0;L;;;;;N;;;;; A17C;YI SYLLABLE HNUT;Lo;0;L;;;;;N;;;;; A17D;YI SYLLABLE NIT;Lo;0;L;;;;;N;;;;; A17E;YI SYLLABLE NIX;Lo;0;L;;;;;N;;;;; A17F;YI SYLLABLE NI;Lo;0;L;;;;;N;;;;; A180;YI SYLLABLE NIP;Lo;0;L;;;;;N;;;;; A181;YI SYLLABLE NIEX;Lo;0;L;;;;;N;;;;; A182;YI SYLLABLE NIE;Lo;0;L;;;;;N;;;;; A183;YI SYLLABLE NIEP;Lo;0;L;;;;;N;;;;; A184;YI SYLLABLE NAX;Lo;0;L;;;;;N;;;;; A185;YI SYLLABLE NA;Lo;0;L;;;;;N;;;;; A186;YI SYLLABLE NAP;Lo;0;L;;;;;N;;;;; A187;YI SYLLABLE NUOX;Lo;0;L;;;;;N;;;;; A188;YI SYLLABLE NUO;Lo;0;L;;;;;N;;;;; A189;YI SYLLABLE NUOP;Lo;0;L;;;;;N;;;;; A18A;YI SYLLABLE NOT;Lo;0;L;;;;;N;;;;; A18B;YI SYLLABLE NOX;Lo;0;L;;;;;N;;;;; A18C;YI SYLLABLE NO;Lo;0;L;;;;;N;;;;; A18D;YI SYLLABLE NOP;Lo;0;L;;;;;N;;;;; A18E;YI SYLLABLE NEX;Lo;0;L;;;;;N;;;;; A18F;YI SYLLABLE NE;Lo;0;L;;;;;N;;;;; A190;YI SYLLABLE NEP;Lo;0;L;;;;;N;;;;; A191;YI SYLLABLE NUT;Lo;0;L;;;;;N;;;;; A192;YI SYLLABLE NUX;Lo;0;L;;;;;N;;;;; A193;YI SYLLABLE NU;Lo;0;L;;;;;N;;;;; A194;YI SYLLABLE NUP;Lo;0;L;;;;;N;;;;; A195;YI SYLLABLE NURX;Lo;0;L;;;;;N;;;;; A196;YI SYLLABLE NUR;Lo;0;L;;;;;N;;;;; A197;YI SYLLABLE HLIT;Lo;0;L;;;;;N;;;;; A198;YI SYLLABLE HLIX;Lo;0;L;;;;;N;;;;; A199;YI SYLLABLE HLI;Lo;0;L;;;;;N;;;;; A19A;YI SYLLABLE HLIP;Lo;0;L;;;;;N;;;;; A19B;YI SYLLABLE HLIEX;Lo;0;L;;;;;N;;;;; A19C;YI SYLLABLE HLIE;Lo;0;L;;;;;N;;;;; A19D;YI SYLLABLE HLIEP;Lo;0;L;;;;;N;;;;; A19E;YI SYLLABLE HLAT;Lo;0;L;;;;;N;;;;; A19F;YI SYLLABLE HLAX;Lo;0;L;;;;;N;;;;; A1A0;YI SYLLABLE HLA;Lo;0;L;;;;;N;;;;; A1A1;YI SYLLABLE HLAP;Lo;0;L;;;;;N;;;;; A1A2;YI SYLLABLE HLUOX;Lo;0;L;;;;;N;;;;; A1A3;YI SYLLABLE HLUO;Lo;0;L;;;;;N;;;;; A1A4;YI SYLLABLE HLUOP;Lo;0;L;;;;;N;;;;; A1A5;YI SYLLABLE HLOX;Lo;0;L;;;;;N;;;;; A1A6;YI SYLLABLE HLO;Lo;0;L;;;;;N;;;;; A1A7;YI SYLLABLE HLOP;Lo;0;L;;;;;N;;;;; A1A8;YI SYLLABLE HLEX;Lo;0;L;;;;;N;;;;; A1A9;YI SYLLABLE HLE;Lo;0;L;;;;;N;;;;; A1AA;YI SYLLABLE HLEP;Lo;0;L;;;;;N;;;;; A1AB;YI SYLLABLE HLUT;Lo;0;L;;;;;N;;;;; A1AC;YI SYLLABLE HLUX;Lo;0;L;;;;;N;;;;; A1AD;YI SYLLABLE HLU;Lo;0;L;;;;;N;;;;; A1AE;YI SYLLABLE HLUP;Lo;0;L;;;;;N;;;;; A1AF;YI SYLLABLE HLURX;Lo;0;L;;;;;N;;;;; A1B0;YI SYLLABLE HLUR;Lo;0;L;;;;;N;;;;; A1B1;YI SYLLABLE HLYT;Lo;0;L;;;;;N;;;;; A1B2;YI SYLLABLE HLYX;Lo;0;L;;;;;N;;;;; A1B3;YI SYLLABLE HLY;Lo;0;L;;;;;N;;;;; A1B4;YI SYLLABLE HLYP;Lo;0;L;;;;;N;;;;; A1B5;YI SYLLABLE HLYRX;Lo;0;L;;;;;N;;;;; A1B6;YI SYLLABLE HLYR;Lo;0;L;;;;;N;;;;; A1B7;YI SYLLABLE LIT;Lo;0;L;;;;;N;;;;; A1B8;YI SYLLABLE LIX;Lo;0;L;;;;;N;;;;; A1B9;YI SYLLABLE LI;Lo;0;L;;;;;N;;;;; A1BA;YI SYLLABLE LIP;Lo;0;L;;;;;N;;;;; A1BB;YI SYLLABLE LIET;Lo;0;L;;;;;N;;;;; A1BC;YI SYLLABLE LIEX;Lo;0;L;;;;;N;;;;; A1BD;YI SYLLABLE LIE;Lo;0;L;;;;;N;;;;; A1BE;YI SYLLABLE LIEP;Lo;0;L;;;;;N;;;;; A1BF;YI SYLLABLE LAT;Lo;0;L;;;;;N;;;;; A1C0;YI SYLLABLE LAX;Lo;0;L;;;;;N;;;;; A1C1;YI SYLLABLE LA;Lo;0;L;;;;;N;;;;; A1C2;YI SYLLABLE LAP;Lo;0;L;;;;;N;;;;; A1C3;YI SYLLABLE LUOT;Lo;0;L;;;;;N;;;;; A1C4;YI SYLLABLE LUOX;Lo;0;L;;;;;N;;;;; A1C5;YI SYLLABLE LUO;Lo;0;L;;;;;N;;;;; A1C6;YI SYLLABLE LUOP;Lo;0;L;;;;;N;;;;; A1C7;YI SYLLABLE LOT;Lo;0;L;;;;;N;;;;; A1C8;YI SYLLABLE LOX;Lo;0;L;;;;;N;;;;; A1C9;YI SYLLABLE LO;Lo;0;L;;;;;N;;;;; A1CA;YI SYLLABLE LOP;Lo;0;L;;;;;N;;;;; A1CB;YI SYLLABLE LEX;Lo;0;L;;;;;N;;;;; A1CC;YI SYLLABLE LE;Lo;0;L;;;;;N;;;;; A1CD;YI SYLLABLE LEP;Lo;0;L;;;;;N;;;;; A1CE;YI SYLLABLE LUT;Lo;0;L;;;;;N;;;;; A1CF;YI SYLLABLE LUX;Lo;0;L;;;;;N;;;;; A1D0;YI SYLLABLE LU;Lo;0;L;;;;;N;;;;; A1D1;YI SYLLABLE LUP;Lo;0;L;;;;;N;;;;; A1D2;YI SYLLABLE LURX;Lo;0;L;;;;;N;;;;; A1D3;YI SYLLABLE LUR;Lo;0;L;;;;;N;;;;; A1D4;YI SYLLABLE LYT;Lo;0;L;;;;;N;;;;; A1D5;YI SYLLABLE LYX;Lo;0;L;;;;;N;;;;; A1D6;YI SYLLABLE LY;Lo;0;L;;;;;N;;;;; A1D7;YI SYLLABLE LYP;Lo;0;L;;;;;N;;;;; A1D8;YI SYLLABLE LYRX;Lo;0;L;;;;;N;;;;; A1D9;YI SYLLABLE LYR;Lo;0;L;;;;;N;;;;; A1DA;YI SYLLABLE GIT;Lo;0;L;;;;;N;;;;; A1DB;YI SYLLABLE GIX;Lo;0;L;;;;;N;;;;; A1DC;YI SYLLABLE GI;Lo;0;L;;;;;N;;;;; A1DD;YI SYLLABLE GIP;Lo;0;L;;;;;N;;;;; A1DE;YI SYLLABLE GIET;Lo;0;L;;;;;N;;;;; A1DF;YI SYLLABLE GIEX;Lo;0;L;;;;;N;;;;; A1E0;YI SYLLABLE GIE;Lo;0;L;;;;;N;;;;; A1E1;YI SYLLABLE GIEP;Lo;0;L;;;;;N;;;;; A1E2;YI SYLLABLE GAT;Lo;0;L;;;;;N;;;;; A1E3;YI SYLLABLE GAX;Lo;0;L;;;;;N;;;;; A1E4;YI SYLLABLE GA;Lo;0;L;;;;;N;;;;; A1E5;YI SYLLABLE GAP;Lo;0;L;;;;;N;;;;; A1E6;YI SYLLABLE GUOT;Lo;0;L;;;;;N;;;;; A1E7;YI SYLLABLE GUOX;Lo;0;L;;;;;N;;;;; A1E8;YI SYLLABLE GUO;Lo;0;L;;;;;N;;;;; A1E9;YI SYLLABLE GUOP;Lo;0;L;;;;;N;;;;; A1EA;YI SYLLABLE GOT;Lo;0;L;;;;;N;;;;; A1EB;YI SYLLABLE GOX;Lo;0;L;;;;;N;;;;; A1EC;YI SYLLABLE GO;Lo;0;L;;;;;N;;;;; A1ED;YI SYLLABLE GOP;Lo;0;L;;;;;N;;;;; A1EE;YI SYLLABLE GET;Lo;0;L;;;;;N;;;;; A1EF;YI SYLLABLE GEX;Lo;0;L;;;;;N;;;;; A1F0;YI SYLLABLE GE;Lo;0;L;;;;;N;;;;; A1F1;YI SYLLABLE GEP;Lo;0;L;;;;;N;;;;; A1F2;YI SYLLABLE GUT;Lo;0;L;;;;;N;;;;; A1F3;YI SYLLABLE GUX;Lo;0;L;;;;;N;;;;; A1F4;YI SYLLABLE GU;Lo;0;L;;;;;N;;;;; A1F5;YI SYLLABLE GUP;Lo;0;L;;;;;N;;;;; A1F6;YI SYLLABLE GURX;Lo;0;L;;;;;N;;;;; A1F7;YI SYLLABLE GUR;Lo;0;L;;;;;N;;;;; A1F8;YI SYLLABLE KIT;Lo;0;L;;;;;N;;;;; A1F9;YI SYLLABLE KIX;Lo;0;L;;;;;N;;;;; A1FA;YI SYLLABLE KI;Lo;0;L;;;;;N;;;;; A1FB;YI SYLLABLE KIP;Lo;0;L;;;;;N;;;;; A1FC;YI SYLLABLE KIEX;Lo;0;L;;;;;N;;;;; A1FD;YI SYLLABLE KIE;Lo;0;L;;;;;N;;;;; A1FE;YI SYLLABLE KIEP;Lo;0;L;;;;;N;;;;; A1FF;YI SYLLABLE KAT;Lo;0;L;;;;;N;;;;; A200;YI SYLLABLE KAX;Lo;0;L;;;;;N;;;;; A201;YI SYLLABLE KA;Lo;0;L;;;;;N;;;;; A202;YI SYLLABLE KAP;Lo;0;L;;;;;N;;;;; A203;YI SYLLABLE KUOX;Lo;0;L;;;;;N;;;;; A204;YI SYLLABLE KUO;Lo;0;L;;;;;N;;;;; A205;YI SYLLABLE KUOP;Lo;0;L;;;;;N;;;;; A206;YI SYLLABLE KOT;Lo;0;L;;;;;N;;;;; A207;YI SYLLABLE KOX;Lo;0;L;;;;;N;;;;; A208;YI SYLLABLE KO;Lo;0;L;;;;;N;;;;; A209;YI SYLLABLE KOP;Lo;0;L;;;;;N;;;;; A20A;YI SYLLABLE KET;Lo;0;L;;;;;N;;;;; A20B;YI SYLLABLE KEX;Lo;0;L;;;;;N;;;;; A20C;YI SYLLABLE KE;Lo;0;L;;;;;N;;;;; A20D;YI SYLLABLE KEP;Lo;0;L;;;;;N;;;;; A20E;YI SYLLABLE KUT;Lo;0;L;;;;;N;;;;; A20F;YI SYLLABLE KUX;Lo;0;L;;;;;N;;;;; A210;YI SYLLABLE KU;Lo;0;L;;;;;N;;;;; A211;YI SYLLABLE KUP;Lo;0;L;;;;;N;;;;; A212;YI SYLLABLE KURX;Lo;0;L;;;;;N;;;;; A213;YI SYLLABLE KUR;Lo;0;L;;;;;N;;;;; A214;YI SYLLABLE GGIT;Lo;0;L;;;;;N;;;;; A215;YI SYLLABLE GGIX;Lo;0;L;;;;;N;;;;; A216;YI SYLLABLE GGI;Lo;0;L;;;;;N;;;;; A217;YI SYLLABLE GGIEX;Lo;0;L;;;;;N;;;;; A218;YI SYLLABLE GGIE;Lo;0;L;;;;;N;;;;; A219;YI SYLLABLE GGIEP;Lo;0;L;;;;;N;;;;; A21A;YI SYLLABLE GGAT;Lo;0;L;;;;;N;;;;; A21B;YI SYLLABLE GGAX;Lo;0;L;;;;;N;;;;; A21C;YI SYLLABLE GGA;Lo;0;L;;;;;N;;;;; A21D;YI SYLLABLE GGAP;Lo;0;L;;;;;N;;;;; A21E;YI SYLLABLE GGUOT;Lo;0;L;;;;;N;;;;; A21F;YI SYLLABLE GGUOX;Lo;0;L;;;;;N;;;;; A220;YI SYLLABLE GGUO;Lo;0;L;;;;;N;;;;; A221;YI SYLLABLE GGUOP;Lo;0;L;;;;;N;;;;; A222;YI SYLLABLE GGOT;Lo;0;L;;;;;N;;;;; A223;YI SYLLABLE GGOX;Lo;0;L;;;;;N;;;;; A224;YI SYLLABLE GGO;Lo;0;L;;;;;N;;;;; A225;YI SYLLABLE GGOP;Lo;0;L;;;;;N;;;;; A226;YI SYLLABLE GGET;Lo;0;L;;;;;N;;;;; A227;YI SYLLABLE GGEX;Lo;0;L;;;;;N;;;;; A228;YI SYLLABLE GGE;Lo;0;L;;;;;N;;;;; A229;YI SYLLABLE GGEP;Lo;0;L;;;;;N;;;;; A22A;YI SYLLABLE GGUT;Lo;0;L;;;;;N;;;;; A22B;YI SYLLABLE GGUX;Lo;0;L;;;;;N;;;;; A22C;YI SYLLABLE GGU;Lo;0;L;;;;;N;;;;; A22D;YI SYLLABLE GGUP;Lo;0;L;;;;;N;;;;; A22E;YI SYLLABLE GGURX;Lo;0;L;;;;;N;;;;; A22F;YI SYLLABLE GGUR;Lo;0;L;;;;;N;;;;; A230;YI SYLLABLE MGIEX;Lo;0;L;;;;;N;;;;; A231;YI SYLLABLE MGIE;Lo;0;L;;;;;N;;;;; A232;YI SYLLABLE MGAT;Lo;0;L;;;;;N;;;;; A233;YI SYLLABLE MGAX;Lo;0;L;;;;;N;;;;; A234;YI SYLLABLE MGA;Lo;0;L;;;;;N;;;;; A235;YI SYLLABLE MGAP;Lo;0;L;;;;;N;;;;; A236;YI SYLLABLE MGUOX;Lo;0;L;;;;;N;;;;; A237;YI SYLLABLE MGUO;Lo;0;L;;;;;N;;;;; A238;YI SYLLABLE MGUOP;Lo;0;L;;;;;N;;;;; A239;YI SYLLABLE MGOT;Lo;0;L;;;;;N;;;;; A23A;YI SYLLABLE MGOX;Lo;0;L;;;;;N;;;;; A23B;YI SYLLABLE MGO;Lo;0;L;;;;;N;;;;; A23C;YI SYLLABLE MGOP;Lo;0;L;;;;;N;;;;; A23D;YI SYLLABLE MGEX;Lo;0;L;;;;;N;;;;; A23E;YI SYLLABLE MGE;Lo;0;L;;;;;N;;;;; A23F;YI SYLLABLE MGEP;Lo;0;L;;;;;N;;;;; A240;YI SYLLABLE MGUT;Lo;0;L;;;;;N;;;;; A241;YI SYLLABLE MGUX;Lo;0;L;;;;;N;;;;; A242;YI SYLLABLE MGU;Lo;0;L;;;;;N;;;;; A243;YI SYLLABLE MGUP;Lo;0;L;;;;;N;;;;; A244;YI SYLLABLE MGURX;Lo;0;L;;;;;N;;;;; A245;YI SYLLABLE MGUR;Lo;0;L;;;;;N;;;;; A246;YI SYLLABLE HXIT;Lo;0;L;;;;;N;;;;; A247;YI SYLLABLE HXIX;Lo;0;L;;;;;N;;;;; A248;YI SYLLABLE HXI;Lo;0;L;;;;;N;;;;; A249;YI SYLLABLE HXIP;Lo;0;L;;;;;N;;;;; A24A;YI SYLLABLE HXIET;Lo;0;L;;;;;N;;;;; A24B;YI SYLLABLE HXIEX;Lo;0;L;;;;;N;;;;; A24C;YI SYLLABLE HXIE;Lo;0;L;;;;;N;;;;; A24D;YI SYLLABLE HXIEP;Lo;0;L;;;;;N;;;;; A24E;YI SYLLABLE HXAT;Lo;0;L;;;;;N;;;;; A24F;YI SYLLABLE HXAX;Lo;0;L;;;;;N;;;;; A250;YI SYLLABLE HXA;Lo;0;L;;;;;N;;;;; A251;YI SYLLABLE HXAP;Lo;0;L;;;;;N;;;;; A252;YI SYLLABLE HXUOT;Lo;0;L;;;;;N;;;;; A253;YI SYLLABLE HXUOX;Lo;0;L;;;;;N;;;;; A254;YI SYLLABLE HXUO;Lo;0;L;;;;;N;;;;; A255;YI SYLLABLE HXUOP;Lo;0;L;;;;;N;;;;; A256;YI SYLLABLE HXOT;Lo;0;L;;;;;N;;;;; A257;YI SYLLABLE HXOX;Lo;0;L;;;;;N;;;;; A258;YI SYLLABLE HXO;Lo;0;L;;;;;N;;;;; A259;YI SYLLABLE HXOP;Lo;0;L;;;;;N;;;;; A25A;YI SYLLABLE HXEX;Lo;0;L;;;;;N;;;;; A25B;YI SYLLABLE HXE;Lo;0;L;;;;;N;;;;; A25C;YI SYLLABLE HXEP;Lo;0;L;;;;;N;;;;; A25D;YI SYLLABLE NGIEX;Lo;0;L;;;;;N;;;;; A25E;YI SYLLABLE NGIE;Lo;0;L;;;;;N;;;;; A25F;YI SYLLABLE NGIEP;Lo;0;L;;;;;N;;;;; A260;YI SYLLABLE NGAT;Lo;0;L;;;;;N;;;;; A261;YI SYLLABLE NGAX;Lo;0;L;;;;;N;;;;; A262;YI SYLLABLE NGA;Lo;0;L;;;;;N;;;;; A263;YI SYLLABLE NGAP;Lo;0;L;;;;;N;;;;; A264;YI SYLLABLE NGUOT;Lo;0;L;;;;;N;;;;; A265;YI SYLLABLE NGUOX;Lo;0;L;;;;;N;;;;; A266;YI SYLLABLE NGUO;Lo;0;L;;;;;N;;;;; A267;YI SYLLABLE NGOT;Lo;0;L;;;;;N;;;;; A268;YI SYLLABLE NGOX;Lo;0;L;;;;;N;;;;; A269;YI SYLLABLE NGO;Lo;0;L;;;;;N;;;;; A26A;YI SYLLABLE NGOP;Lo;0;L;;;;;N;;;;; A26B;YI SYLLABLE NGEX;Lo;0;L;;;;;N;;;;; A26C;YI SYLLABLE NGE;Lo;0;L;;;;;N;;;;; A26D;YI SYLLABLE NGEP;Lo;0;L;;;;;N;;;;; A26E;YI SYLLABLE HIT;Lo;0;L;;;;;N;;;;; A26F;YI SYLLABLE HIEX;Lo;0;L;;;;;N;;;;; A270;YI SYLLABLE HIE;Lo;0;L;;;;;N;;;;; A271;YI SYLLABLE HAT;Lo;0;L;;;;;N;;;;; A272;YI SYLLABLE HAX;Lo;0;L;;;;;N;;;;; A273;YI SYLLABLE HA;Lo;0;L;;;;;N;;;;; A274;YI SYLLABLE HAP;Lo;0;L;;;;;N;;;;; A275;YI SYLLABLE HUOT;Lo;0;L;;;;;N;;;;; A276;YI SYLLABLE HUOX;Lo;0;L;;;;;N;;;;; A277;YI SYLLABLE HUO;Lo;0;L;;;;;N;;;;; A278;YI SYLLABLE HUOP;Lo;0;L;;;;;N;;;;; A279;YI SYLLABLE HOT;Lo;0;L;;;;;N;;;;; A27A;YI SYLLABLE HOX;Lo;0;L;;;;;N;;;;; A27B;YI SYLLABLE HO;Lo;0;L;;;;;N;;;;; A27C;YI SYLLABLE HOP;Lo;0;L;;;;;N;;;;; A27D;YI SYLLABLE HEX;Lo;0;L;;;;;N;;;;; A27E;YI SYLLABLE HE;Lo;0;L;;;;;N;;;;; A27F;YI SYLLABLE HEP;Lo;0;L;;;;;N;;;;; A280;YI SYLLABLE WAT;Lo;0;L;;;;;N;;;;; A281;YI SYLLABLE WAX;Lo;0;L;;;;;N;;;;; A282;YI SYLLABLE WA;Lo;0;L;;;;;N;;;;; A283;YI SYLLABLE WAP;Lo;0;L;;;;;N;;;;; A284;YI SYLLABLE WUOX;Lo;0;L;;;;;N;;;;; A285;YI SYLLABLE WUO;Lo;0;L;;;;;N;;;;; A286;YI SYLLABLE WUOP;Lo;0;L;;;;;N;;;;; A287;YI SYLLABLE WOX;Lo;0;L;;;;;N;;;;; A288;YI SYLLABLE WO;Lo;0;L;;;;;N;;;;; A289;YI SYLLABLE WOP;Lo;0;L;;;;;N;;;;; A28A;YI SYLLABLE WEX;Lo;0;L;;;;;N;;;;; A28B;YI SYLLABLE WE;Lo;0;L;;;;;N;;;;; A28C;YI SYLLABLE WEP;Lo;0;L;;;;;N;;;;; A28D;YI SYLLABLE ZIT;Lo;0;L;;;;;N;;;;; A28E;YI SYLLABLE ZIX;Lo;0;L;;;;;N;;;;; A28F;YI SYLLABLE ZI;Lo;0;L;;;;;N;;;;; A290;YI SYLLABLE ZIP;Lo;0;L;;;;;N;;;;; A291;YI SYLLABLE ZIEX;Lo;0;L;;;;;N;;;;; A292;YI SYLLABLE ZIE;Lo;0;L;;;;;N;;;;; A293;YI SYLLABLE ZIEP;Lo;0;L;;;;;N;;;;; A294;YI SYLLABLE ZAT;Lo;0;L;;;;;N;;;;; A295;YI SYLLABLE ZAX;Lo;0;L;;;;;N;;;;; A296;YI SYLLABLE ZA;Lo;0;L;;;;;N;;;;; A297;YI SYLLABLE ZAP;Lo;0;L;;;;;N;;;;; A298;YI SYLLABLE ZUOX;Lo;0;L;;;;;N;;;;; A299;YI SYLLABLE ZUO;Lo;0;L;;;;;N;;;;; A29A;YI SYLLABLE ZUOP;Lo;0;L;;;;;N;;;;; A29B;YI SYLLABLE ZOT;Lo;0;L;;;;;N;;;;; A29C;YI SYLLABLE ZOX;Lo;0;L;;;;;N;;;;; A29D;YI SYLLABLE ZO;Lo;0;L;;;;;N;;;;; A29E;YI SYLLABLE ZOP;Lo;0;L;;;;;N;;;;; A29F;YI SYLLABLE ZEX;Lo;0;L;;;;;N;;;;; A2A0;YI SYLLABLE ZE;Lo;0;L;;;;;N;;;;; A2A1;YI SYLLABLE ZEP;Lo;0;L;;;;;N;;;;; A2A2;YI SYLLABLE ZUT;Lo;0;L;;;;;N;;;;; A2A3;YI SYLLABLE ZUX;Lo;0;L;;;;;N;;;;; A2A4;YI SYLLABLE ZU;Lo;0;L;;;;;N;;;;; A2A5;YI SYLLABLE ZUP;Lo;0;L;;;;;N;;;;; A2A6;YI SYLLABLE ZURX;Lo;0;L;;;;;N;;;;; A2A7;YI SYLLABLE ZUR;Lo;0;L;;;;;N;;;;; A2A8;YI SYLLABLE ZYT;Lo;0;L;;;;;N;;;;; A2A9;YI SYLLABLE ZYX;Lo;0;L;;;;;N;;;;; A2AA;YI SYLLABLE ZY;Lo;0;L;;;;;N;;;;; A2AB;YI SYLLABLE ZYP;Lo;0;L;;;;;N;;;;; A2AC;YI SYLLABLE ZYRX;Lo;0;L;;;;;N;;;;; A2AD;YI SYLLABLE ZYR;Lo;0;L;;;;;N;;;;; A2AE;YI SYLLABLE CIT;Lo;0;L;;;;;N;;;;; A2AF;YI SYLLABLE CIX;Lo;0;L;;;;;N;;;;; A2B0;YI SYLLABLE CI;Lo;0;L;;;;;N;;;;; A2B1;YI SYLLABLE CIP;Lo;0;L;;;;;N;;;;; A2B2;YI SYLLABLE CIET;Lo;0;L;;;;;N;;;;; A2B3;YI SYLLABLE CIEX;Lo;0;L;;;;;N;;;;; A2B4;YI SYLLABLE CIE;Lo;0;L;;;;;N;;;;; A2B5;YI SYLLABLE CIEP;Lo;0;L;;;;;N;;;;; A2B6;YI SYLLABLE CAT;Lo;0;L;;;;;N;;;;; A2B7;YI SYLLABLE CAX;Lo;0;L;;;;;N;;;;; A2B8;YI SYLLABLE CA;Lo;0;L;;;;;N;;;;; A2B9;YI SYLLABLE CAP;Lo;0;L;;;;;N;;;;; A2BA;YI SYLLABLE CUOX;Lo;0;L;;;;;N;;;;; A2BB;YI SYLLABLE CUO;Lo;0;L;;;;;N;;;;; A2BC;YI SYLLABLE CUOP;Lo;0;L;;;;;N;;;;; A2BD;YI SYLLABLE COT;Lo;0;L;;;;;N;;;;; A2BE;YI SYLLABLE COX;Lo;0;L;;;;;N;;;;; A2BF;YI SYLLABLE CO;Lo;0;L;;;;;N;;;;; A2C0;YI SYLLABLE COP;Lo;0;L;;;;;N;;;;; A2C1;YI SYLLABLE CEX;Lo;0;L;;;;;N;;;;; A2C2;YI SYLLABLE CE;Lo;0;L;;;;;N;;;;; A2C3;YI SYLLABLE CEP;Lo;0;L;;;;;N;;;;; A2C4;YI SYLLABLE CUT;Lo;0;L;;;;;N;;;;; A2C5;YI SYLLABLE CUX;Lo;0;L;;;;;N;;;;; A2C6;YI SYLLABLE CU;Lo;0;L;;;;;N;;;;; A2C7;YI SYLLABLE CUP;Lo;0;L;;;;;N;;;;; A2C8;YI SYLLABLE CURX;Lo;0;L;;;;;N;;;;; A2C9;YI SYLLABLE CUR;Lo;0;L;;;;;N;;;;; A2CA;YI SYLLABLE CYT;Lo;0;L;;;;;N;;;;; A2CB;YI SYLLABLE CYX;Lo;0;L;;;;;N;;;;; A2CC;YI SYLLABLE CY;Lo;0;L;;;;;N;;;;; A2CD;YI SYLLABLE CYP;Lo;0;L;;;;;N;;;;; A2CE;YI SYLLABLE CYRX;Lo;0;L;;;;;N;;;;; A2CF;YI SYLLABLE CYR;Lo;0;L;;;;;N;;;;; A2D0;YI SYLLABLE ZZIT;Lo;0;L;;;;;N;;;;; A2D1;YI SYLLABLE ZZIX;Lo;0;L;;;;;N;;;;; A2D2;YI SYLLABLE ZZI;Lo;0;L;;;;;N;;;;; A2D3;YI SYLLABLE ZZIP;Lo;0;L;;;;;N;;;;; A2D4;YI SYLLABLE ZZIET;Lo;0;L;;;;;N;;;;; A2D5;YI SYLLABLE ZZIEX;Lo;0;L;;;;;N;;;;; A2D6;YI SYLLABLE ZZIE;Lo;0;L;;;;;N;;;;; A2D7;YI SYLLABLE ZZIEP;Lo;0;L;;;;;N;;;;; A2D8;YI SYLLABLE ZZAT;Lo;0;L;;;;;N;;;;; A2D9;YI SYLLABLE ZZAX;Lo;0;L;;;;;N;;;;; A2DA;YI SYLLABLE ZZA;Lo;0;L;;;;;N;;;;; A2DB;YI SYLLABLE ZZAP;Lo;0;L;;;;;N;;;;; A2DC;YI SYLLABLE ZZOX;Lo;0;L;;;;;N;;;;; A2DD;YI SYLLABLE ZZO;Lo;0;L;;;;;N;;;;; A2DE;YI SYLLABLE ZZOP;Lo;0;L;;;;;N;;;;; A2DF;YI SYLLABLE ZZEX;Lo;0;L;;;;;N;;;;; A2E0;YI SYLLABLE ZZE;Lo;0;L;;;;;N;;;;; A2E1;YI SYLLABLE ZZEP;Lo;0;L;;;;;N;;;;; A2E2;YI SYLLABLE ZZUX;Lo;0;L;;;;;N;;;;; A2E3;YI SYLLABLE ZZU;Lo;0;L;;;;;N;;;;; A2E4;YI SYLLABLE ZZUP;Lo;0;L;;;;;N;;;;; A2E5;YI SYLLABLE ZZURX;Lo;0;L;;;;;N;;;;; A2E6;YI SYLLABLE ZZUR;Lo;0;L;;;;;N;;;;; A2E7;YI SYLLABLE ZZYT;Lo;0;L;;;;;N;;;;; A2E8;YI SYLLABLE ZZYX;Lo;0;L;;;;;N;;;;; A2E9;YI SYLLABLE ZZY;Lo;0;L;;;;;N;;;;; A2EA;YI SYLLABLE ZZYP;Lo;0;L;;;;;N;;;;; A2EB;YI SYLLABLE ZZYRX;Lo;0;L;;;;;N;;;;; A2EC;YI SYLLABLE ZZYR;Lo;0;L;;;;;N;;;;; A2ED;YI SYLLABLE NZIT;Lo;0;L;;;;;N;;;;; A2EE;YI SYLLABLE NZIX;Lo;0;L;;;;;N;;;;; A2EF;YI SYLLABLE NZI;Lo;0;L;;;;;N;;;;; A2F0;YI SYLLABLE NZIP;Lo;0;L;;;;;N;;;;; A2F1;YI SYLLABLE NZIEX;Lo;0;L;;;;;N;;;;; A2F2;YI SYLLABLE NZIE;Lo;0;L;;;;;N;;;;; A2F3;YI SYLLABLE NZIEP;Lo;0;L;;;;;N;;;;; A2F4;YI SYLLABLE NZAT;Lo;0;L;;;;;N;;;;; A2F5;YI SYLLABLE NZAX;Lo;0;L;;;;;N;;;;; A2F6;YI SYLLABLE NZA;Lo;0;L;;;;;N;;;;; A2F7;YI SYLLABLE NZAP;Lo;0;L;;;;;N;;;;; A2F8;YI SYLLABLE NZUOX;Lo;0;L;;;;;N;;;;; A2F9;YI SYLLABLE NZUO;Lo;0;L;;;;;N;;;;; A2FA;YI SYLLABLE NZOX;Lo;0;L;;;;;N;;;;; A2FB;YI SYLLABLE NZOP;Lo;0;L;;;;;N;;;;; A2FC;YI SYLLABLE NZEX;Lo;0;L;;;;;N;;;;; A2FD;YI SYLLABLE NZE;Lo;0;L;;;;;N;;;;; A2FE;YI SYLLABLE NZUX;Lo;0;L;;;;;N;;;;; A2FF;YI SYLLABLE NZU;Lo;0;L;;;;;N;;;;; A300;YI SYLLABLE NZUP;Lo;0;L;;;;;N;;;;; A301;YI SYLLABLE NZURX;Lo;0;L;;;;;N;;;;; A302;YI SYLLABLE NZUR;Lo;0;L;;;;;N;;;;; A303;YI SYLLABLE NZYT;Lo;0;L;;;;;N;;;;; A304;YI SYLLABLE NZYX;Lo;0;L;;;;;N;;;;; A305;YI SYLLABLE NZY;Lo;0;L;;;;;N;;;;; A306;YI SYLLABLE NZYP;Lo;0;L;;;;;N;;;;; A307;YI SYLLABLE NZYRX;Lo;0;L;;;;;N;;;;; A308;YI SYLLABLE NZYR;Lo;0;L;;;;;N;;;;; A309;YI SYLLABLE SIT;Lo;0;L;;;;;N;;;;; A30A;YI SYLLABLE SIX;Lo;0;L;;;;;N;;;;; A30B;YI SYLLABLE SI;Lo;0;L;;;;;N;;;;; A30C;YI SYLLABLE SIP;Lo;0;L;;;;;N;;;;; A30D;YI SYLLABLE SIEX;Lo;0;L;;;;;N;;;;; A30E;YI SYLLABLE SIE;Lo;0;L;;;;;N;;;;; A30F;YI SYLLABLE SIEP;Lo;0;L;;;;;N;;;;; A310;YI SYLLABLE SAT;Lo;0;L;;;;;N;;;;; A311;YI SYLLABLE SAX;Lo;0;L;;;;;N;;;;; A312;YI SYLLABLE SA;Lo;0;L;;;;;N;;;;; A313;YI SYLLABLE SAP;Lo;0;L;;;;;N;;;;; A314;YI SYLLABLE SUOX;Lo;0;L;;;;;N;;;;; A315;YI SYLLABLE SUO;Lo;0;L;;;;;N;;;;; A316;YI SYLLABLE SUOP;Lo;0;L;;;;;N;;;;; A317;YI SYLLABLE SOT;Lo;0;L;;;;;N;;;;; A318;YI SYLLABLE SOX;Lo;0;L;;;;;N;;;;; A319;YI SYLLABLE SO;Lo;0;L;;;;;N;;;;; A31A;YI SYLLABLE SOP;Lo;0;L;;;;;N;;;;; A31B;YI SYLLABLE SEX;Lo;0;L;;;;;N;;;;; A31C;YI SYLLABLE SE;Lo;0;L;;;;;N;;;;; A31D;YI SYLLABLE SEP;Lo;0;L;;;;;N;;;;; A31E;YI SYLLABLE SUT;Lo;0;L;;;;;N;;;;; A31F;YI SYLLABLE SUX;Lo;0;L;;;;;N;;;;; A320;YI SYLLABLE SU;Lo;0;L;;;;;N;;;;; A321;YI SYLLABLE SUP;Lo;0;L;;;;;N;;;;; A322;YI SYLLABLE SURX;Lo;0;L;;;;;N;;;;; A323;YI SYLLABLE SUR;Lo;0;L;;;;;N;;;;; A324;YI SYLLABLE SYT;Lo;0;L;;;;;N;;;;; A325;YI SYLLABLE SYX;Lo;0;L;;;;;N;;;;; A326;YI SYLLABLE SY;Lo;0;L;;;;;N;;;;; A327;YI SYLLABLE SYP;Lo;0;L;;;;;N;;;;; A328;YI SYLLABLE SYRX;Lo;0;L;;;;;N;;;;; A329;YI SYLLABLE SYR;Lo;0;L;;;;;N;;;;; A32A;YI SYLLABLE SSIT;Lo;0;L;;;;;N;;;;; A32B;YI SYLLABLE SSIX;Lo;0;L;;;;;N;;;;; A32C;YI SYLLABLE SSI;Lo;0;L;;;;;N;;;;; A32D;YI SYLLABLE SSIP;Lo;0;L;;;;;N;;;;; A32E;YI SYLLABLE SSIEX;Lo;0;L;;;;;N;;;;; A32F;YI SYLLABLE SSIE;Lo;0;L;;;;;N;;;;; A330;YI SYLLABLE SSIEP;Lo;0;L;;;;;N;;;;; A331;YI SYLLABLE SSAT;Lo;0;L;;;;;N;;;;; A332;YI SYLLABLE SSAX;Lo;0;L;;;;;N;;;;; A333;YI SYLLABLE SSA;Lo;0;L;;;;;N;;;;; A334;YI SYLLABLE SSAP;Lo;0;L;;;;;N;;;;; A335;YI SYLLABLE SSOT;Lo;0;L;;;;;N;;;;; A336;YI SYLLABLE SSOX;Lo;0;L;;;;;N;;;;; A337;YI SYLLABLE SSO;Lo;0;L;;;;;N;;;;; A338;YI SYLLABLE SSOP;Lo;0;L;;;;;N;;;;; A339;YI SYLLABLE SSEX;Lo;0;L;;;;;N;;;;; A33A;YI SYLLABLE SSE;Lo;0;L;;;;;N;;;;; A33B;YI SYLLABLE SSEP;Lo;0;L;;;;;N;;;;; A33C;YI SYLLABLE SSUT;Lo;0;L;;;;;N;;;;; A33D;YI SYLLABLE SSUX;Lo;0;L;;;;;N;;;;; A33E;YI SYLLABLE SSU;Lo;0;L;;;;;N;;;;; A33F;YI SYLLABLE SSUP;Lo;0;L;;;;;N;;;;; A340;YI SYLLABLE SSYT;Lo;0;L;;;;;N;;;;; A341;YI SYLLABLE SSYX;Lo;0;L;;;;;N;;;;; A342;YI SYLLABLE SSY;Lo;0;L;;;;;N;;;;; A343;YI SYLLABLE SSYP;Lo;0;L;;;;;N;;;;; A344;YI SYLLABLE SSYRX;Lo;0;L;;;;;N;;;;; A345;YI SYLLABLE SSYR;Lo;0;L;;;;;N;;;;; A346;YI SYLLABLE ZHAT;Lo;0;L;;;;;N;;;;; A347;YI SYLLABLE ZHAX;Lo;0;L;;;;;N;;;;; A348;YI SYLLABLE ZHA;Lo;0;L;;;;;N;;;;; A349;YI SYLLABLE ZHAP;Lo;0;L;;;;;N;;;;; A34A;YI SYLLABLE ZHUOX;Lo;0;L;;;;;N;;;;; A34B;YI SYLLABLE ZHUO;Lo;0;L;;;;;N;;;;; A34C;YI SYLLABLE ZHUOP;Lo;0;L;;;;;N;;;;; A34D;YI SYLLABLE ZHOT;Lo;0;L;;;;;N;;;;; A34E;YI SYLLABLE ZHOX;Lo;0;L;;;;;N;;;;; A34F;YI SYLLABLE ZHO;Lo;0;L;;;;;N;;;;; A350;YI SYLLABLE ZHOP;Lo;0;L;;;;;N;;;;; A351;YI SYLLABLE ZHET;Lo;0;L;;;;;N;;;;; A352;YI SYLLABLE ZHEX;Lo;0;L;;;;;N;;;;; A353;YI SYLLABLE ZHE;Lo;0;L;;;;;N;;;;; A354;YI SYLLABLE ZHEP;Lo;0;L;;;;;N;;;;; A355;YI SYLLABLE ZHUT;Lo;0;L;;;;;N;;;;; A356;YI SYLLABLE ZHUX;Lo;0;L;;;;;N;;;;; A357;YI SYLLABLE ZHU;Lo;0;L;;;;;N;;;;; A358;YI SYLLABLE ZHUP;Lo;0;L;;;;;N;;;;; A359;YI SYLLABLE ZHURX;Lo;0;L;;;;;N;;;;; A35A;YI SYLLABLE ZHUR;Lo;0;L;;;;;N;;;;; A35B;YI SYLLABLE ZHYT;Lo;0;L;;;;;N;;;;; A35C;YI SYLLABLE ZHYX;Lo;0;L;;;;;N;;;;; A35D;YI SYLLABLE ZHY;Lo;0;L;;;;;N;;;;; A35E;YI SYLLABLE ZHYP;Lo;0;L;;;;;N;;;;; A35F;YI SYLLABLE ZHYRX;Lo;0;L;;;;;N;;;;; A360;YI SYLLABLE ZHYR;Lo;0;L;;;;;N;;;;; A361;YI SYLLABLE CHAT;Lo;0;L;;;;;N;;;;; A362;YI SYLLABLE CHAX;Lo;0;L;;;;;N;;;;; A363;YI SYLLABLE CHA;Lo;0;L;;;;;N;;;;; A364;YI SYLLABLE CHAP;Lo;0;L;;;;;N;;;;; A365;YI SYLLABLE CHUOT;Lo;0;L;;;;;N;;;;; A366;YI SYLLABLE CHUOX;Lo;0;L;;;;;N;;;;; A367;YI SYLLABLE CHUO;Lo;0;L;;;;;N;;;;; A368;YI SYLLABLE CHUOP;Lo;0;L;;;;;N;;;;; A369;YI SYLLABLE CHOT;Lo;0;L;;;;;N;;;;; A36A;YI SYLLABLE CHOX;Lo;0;L;;;;;N;;;;; A36B;YI SYLLABLE CHO;Lo;0;L;;;;;N;;;;; A36C;YI SYLLABLE CHOP;Lo;0;L;;;;;N;;;;; A36D;YI SYLLABLE CHET;Lo;0;L;;;;;N;;;;; A36E;YI SYLLABLE CHEX;Lo;0;L;;;;;N;;;;; A36F;YI SYLLABLE CHE;Lo;0;L;;;;;N;;;;; A370;YI SYLLABLE CHEP;Lo;0;L;;;;;N;;;;; A371;YI SYLLABLE CHUX;Lo;0;L;;;;;N;;;;; A372;YI SYLLABLE CHU;Lo;0;L;;;;;N;;;;; A373;YI SYLLABLE CHUP;Lo;0;L;;;;;N;;;;; A374;YI SYLLABLE CHURX;Lo;0;L;;;;;N;;;;; A375;YI SYLLABLE CHUR;Lo;0;L;;;;;N;;;;; A376;YI SYLLABLE CHYT;Lo;0;L;;;;;N;;;;; A377;YI SYLLABLE CHYX;Lo;0;L;;;;;N;;;;; A378;YI SYLLABLE CHY;Lo;0;L;;;;;N;;;;; A379;YI SYLLABLE CHYP;Lo;0;L;;;;;N;;;;; A37A;YI SYLLABLE CHYRX;Lo;0;L;;;;;N;;;;; A37B;YI SYLLABLE CHYR;Lo;0;L;;;;;N;;;;; A37C;YI SYLLABLE RRAX;Lo;0;L;;;;;N;;;;; A37D;YI SYLLABLE RRA;Lo;0;L;;;;;N;;;;; A37E;YI SYLLABLE RRUOX;Lo;0;L;;;;;N;;;;; A37F;YI SYLLABLE RRUO;Lo;0;L;;;;;N;;;;; A380;YI SYLLABLE RROT;Lo;0;L;;;;;N;;;;; A381;YI SYLLABLE RROX;Lo;0;L;;;;;N;;;;; A382;YI SYLLABLE RRO;Lo;0;L;;;;;N;;;;; A383;YI SYLLABLE RROP;Lo;0;L;;;;;N;;;;; A384;YI SYLLABLE RRET;Lo;0;L;;;;;N;;;;; A385;YI SYLLABLE RREX;Lo;0;L;;;;;N;;;;; A386;YI SYLLABLE RRE;Lo;0;L;;;;;N;;;;; A387;YI SYLLABLE RREP;Lo;0;L;;;;;N;;;;; A388;YI SYLLABLE RRUT;Lo;0;L;;;;;N;;;;; A389;YI SYLLABLE RRUX;Lo;0;L;;;;;N;;;;; A38A;YI SYLLABLE RRU;Lo;0;L;;;;;N;;;;; A38B;YI SYLLABLE RRUP;Lo;0;L;;;;;N;;;;; A38C;YI SYLLABLE RRURX;Lo;0;L;;;;;N;;;;; A38D;YI SYLLABLE RRUR;Lo;0;L;;;;;N;;;;; A38E;YI SYLLABLE RRYT;Lo;0;L;;;;;N;;;;; A38F;YI SYLLABLE RRYX;Lo;0;L;;;;;N;;;;; A390;YI SYLLABLE RRY;Lo;0;L;;;;;N;;;;; A391;YI SYLLABLE RRYP;Lo;0;L;;;;;N;;;;; A392;YI SYLLABLE RRYRX;Lo;0;L;;;;;N;;;;; A393;YI SYLLABLE RRYR;Lo;0;L;;;;;N;;;;; A394;YI SYLLABLE NRAT;Lo;0;L;;;;;N;;;;; A395;YI SYLLABLE NRAX;Lo;0;L;;;;;N;;;;; A396;YI SYLLABLE NRA;Lo;0;L;;;;;N;;;;; A397;YI SYLLABLE NRAP;Lo;0;L;;;;;N;;;;; A398;YI SYLLABLE NROX;Lo;0;L;;;;;N;;;;; A399;YI SYLLABLE NRO;Lo;0;L;;;;;N;;;;; A39A;YI SYLLABLE NROP;Lo;0;L;;;;;N;;;;; A39B;YI SYLLABLE NRET;Lo;0;L;;;;;N;;;;; A39C;YI SYLLABLE NREX;Lo;0;L;;;;;N;;;;; A39D;YI SYLLABLE NRE;Lo;0;L;;;;;N;;;;; A39E;YI SYLLABLE NREP;Lo;0;L;;;;;N;;;;; A39F;YI SYLLABLE NRUT;Lo;0;L;;;;;N;;;;; A3A0;YI SYLLABLE NRUX;Lo;0;L;;;;;N;;;;; A3A1;YI SYLLABLE NRU;Lo;0;L;;;;;N;;;;; A3A2;YI SYLLABLE NRUP;Lo;0;L;;;;;N;;;;; A3A3;YI SYLLABLE NRURX;Lo;0;L;;;;;N;;;;; A3A4;YI SYLLABLE NRUR;Lo;0;L;;;;;N;;;;; A3A5;YI SYLLABLE NRYT;Lo;0;L;;;;;N;;;;; A3A6;YI SYLLABLE NRYX;Lo;0;L;;;;;N;;;;; A3A7;YI SYLLABLE NRY;Lo;0;L;;;;;N;;;;; A3A8;YI SYLLABLE NRYP;Lo;0;L;;;;;N;;;;; A3A9;YI SYLLABLE NRYRX;Lo;0;L;;;;;N;;;;; A3AA;YI SYLLABLE NRYR;Lo;0;L;;;;;N;;;;; A3AB;YI SYLLABLE SHAT;Lo;0;L;;;;;N;;;;; A3AC;YI SYLLABLE SHAX;Lo;0;L;;;;;N;;;;; A3AD;YI SYLLABLE SHA;Lo;0;L;;;;;N;;;;; A3AE;YI SYLLABLE SHAP;Lo;0;L;;;;;N;;;;; A3AF;YI SYLLABLE SHUOX;Lo;0;L;;;;;N;;;;; A3B0;YI SYLLABLE SHUO;Lo;0;L;;;;;N;;;;; A3B1;YI SYLLABLE SHUOP;Lo;0;L;;;;;N;;;;; A3B2;YI SYLLABLE SHOT;Lo;0;L;;;;;N;;;;; A3B3;YI SYLLABLE SHOX;Lo;0;L;;;;;N;;;;; A3B4;YI SYLLABLE SHO;Lo;0;L;;;;;N;;;;; A3B5;YI SYLLABLE SHOP;Lo;0;L;;;;;N;;;;; A3B6;YI SYLLABLE SHET;Lo;0;L;;;;;N;;;;; A3B7;YI SYLLABLE SHEX;Lo;0;L;;;;;N;;;;; A3B8;YI SYLLABLE SHE;Lo;0;L;;;;;N;;;;; A3B9;YI SYLLABLE SHEP;Lo;0;L;;;;;N;;;;; A3BA;YI SYLLABLE SHUT;Lo;0;L;;;;;N;;;;; A3BB;YI SYLLABLE SHUX;Lo;0;L;;;;;N;;;;; A3BC;YI SYLLABLE SHU;Lo;0;L;;;;;N;;;;; A3BD;YI SYLLABLE SHUP;Lo;0;L;;;;;N;;;;; A3BE;YI SYLLABLE SHURX;Lo;0;L;;;;;N;;;;; A3BF;YI SYLLABLE SHUR;Lo;0;L;;;;;N;;;;; A3C0;YI SYLLABLE SHYT;Lo;0;L;;;;;N;;;;; A3C1;YI SYLLABLE SHYX;Lo;0;L;;;;;N;;;;; A3C2;YI SYLLABLE SHY;Lo;0;L;;;;;N;;;;; A3C3;YI SYLLABLE SHYP;Lo;0;L;;;;;N;;;;; A3C4;YI SYLLABLE SHYRX;Lo;0;L;;;;;N;;;;; A3C5;YI SYLLABLE SHYR;Lo;0;L;;;;;N;;;;; A3C6;YI SYLLABLE RAT;Lo;0;L;;;;;N;;;;; A3C7;YI SYLLABLE RAX;Lo;0;L;;;;;N;;;;; A3C8;YI SYLLABLE RA;Lo;0;L;;;;;N;;;;; A3C9;YI SYLLABLE RAP;Lo;0;L;;;;;N;;;;; A3CA;YI SYLLABLE RUOX;Lo;0;L;;;;;N;;;;; A3CB;YI SYLLABLE RUO;Lo;0;L;;;;;N;;;;; A3CC;YI SYLLABLE RUOP;Lo;0;L;;;;;N;;;;; A3CD;YI SYLLABLE ROT;Lo;0;L;;;;;N;;;;; A3CE;YI SYLLABLE ROX;Lo;0;L;;;;;N;;;;; A3CF;YI SYLLABLE RO;Lo;0;L;;;;;N;;;;; A3D0;YI SYLLABLE ROP;Lo;0;L;;;;;N;;;;; A3D1;YI SYLLABLE REX;Lo;0;L;;;;;N;;;;; A3D2;YI SYLLABLE RE;Lo;0;L;;;;;N;;;;; A3D3;YI SYLLABLE REP;Lo;0;L;;;;;N;;;;; A3D4;YI SYLLABLE RUT;Lo;0;L;;;;;N;;;;; A3D5;YI SYLLABLE RUX;Lo;0;L;;;;;N;;;;; A3D6;YI SYLLABLE RU;Lo;0;L;;;;;N;;;;; A3D7;YI SYLLABLE RUP;Lo;0;L;;;;;N;;;;; A3D8;YI SYLLABLE RURX;Lo;0;L;;;;;N;;;;; A3D9;YI SYLLABLE RUR;Lo;0;L;;;;;N;;;;; A3DA;YI SYLLABLE RYT;Lo;0;L;;;;;N;;;;; A3DB;YI SYLLABLE RYX;Lo;0;L;;;;;N;;;;; A3DC;YI SYLLABLE RY;Lo;0;L;;;;;N;;;;; A3DD;YI SYLLABLE RYP;Lo;0;L;;;;;N;;;;; A3DE;YI SYLLABLE RYRX;Lo;0;L;;;;;N;;;;; A3DF;YI SYLLABLE RYR;Lo;0;L;;;;;N;;;;; A3E0;YI SYLLABLE JIT;Lo;0;L;;;;;N;;;;; A3E1;YI SYLLABLE JIX;Lo;0;L;;;;;N;;;;; A3E2;YI SYLLABLE JI;Lo;0;L;;;;;N;;;;; A3E3;YI SYLLABLE JIP;Lo;0;L;;;;;N;;;;; A3E4;YI SYLLABLE JIET;Lo;0;L;;;;;N;;;;; A3E5;YI SYLLABLE JIEX;Lo;0;L;;;;;N;;;;; A3E6;YI SYLLABLE JIE;Lo;0;L;;;;;N;;;;; A3E7;YI SYLLABLE JIEP;Lo;0;L;;;;;N;;;;; A3E8;YI SYLLABLE JUOT;Lo;0;L;;;;;N;;;;; A3E9;YI SYLLABLE JUOX;Lo;0;L;;;;;N;;;;; A3EA;YI SYLLABLE JUO;Lo;0;L;;;;;N;;;;; A3EB;YI SYLLABLE JUOP;Lo;0;L;;;;;N;;;;; A3EC;YI SYLLABLE JOT;Lo;0;L;;;;;N;;;;; A3ED;YI SYLLABLE JOX;Lo;0;L;;;;;N;;;;; A3EE;YI SYLLABLE JO;Lo;0;L;;;;;N;;;;; A3EF;YI SYLLABLE JOP;Lo;0;L;;;;;N;;;;; A3F0;YI SYLLABLE JUT;Lo;0;L;;;;;N;;;;; A3F1;YI SYLLABLE JUX;Lo;0;L;;;;;N;;;;; A3F2;YI SYLLABLE JU;Lo;0;L;;;;;N;;;;; A3F3;YI SYLLABLE JUP;Lo;0;L;;;;;N;;;;; A3F4;YI SYLLABLE JURX;Lo;0;L;;;;;N;;;;; A3F5;YI SYLLABLE JUR;Lo;0;L;;;;;N;;;;; A3F6;YI SYLLABLE JYT;Lo;0;L;;;;;N;;;;; A3F7;YI SYLLABLE JYX;Lo;0;L;;;;;N;;;;; A3F8;YI SYLLABLE JY;Lo;0;L;;;;;N;;;;; A3F9;YI SYLLABLE JYP;Lo;0;L;;;;;N;;;;; A3FA;YI SYLLABLE JYRX;Lo;0;L;;;;;N;;;;; A3FB;YI SYLLABLE JYR;Lo;0;L;;;;;N;;;;; A3FC;YI SYLLABLE QIT;Lo;0;L;;;;;N;;;;; A3FD;YI SYLLABLE QIX;Lo;0;L;;;;;N;;;;; A3FE;YI SYLLABLE QI;Lo;0;L;;;;;N;;;;; A3FF;YI SYLLABLE QIP;Lo;0;L;;;;;N;;;;; A400;YI SYLLABLE QIET;Lo;0;L;;;;;N;;;;; A401;YI SYLLABLE QIEX;Lo;0;L;;;;;N;;;;; A402;YI SYLLABLE QIE;Lo;0;L;;;;;N;;;;; A403;YI SYLLABLE QIEP;Lo;0;L;;;;;N;;;;; A404;YI SYLLABLE QUOT;Lo;0;L;;;;;N;;;;; A405;YI SYLLABLE QUOX;Lo;0;L;;;;;N;;;;; A406;YI SYLLABLE QUO;Lo;0;L;;;;;N;;;;; A407;YI SYLLABLE QUOP;Lo;0;L;;;;;N;;;;; A408;YI SYLLABLE QOT;Lo;0;L;;;;;N;;;;; A409;YI SYLLABLE QOX;Lo;0;L;;;;;N;;;;; A40A;YI SYLLABLE QO;Lo;0;L;;;;;N;;;;; A40B;YI SYLLABLE QOP;Lo;0;L;;;;;N;;;;; A40C;YI SYLLABLE QUT;Lo;0;L;;;;;N;;;;; A40D;YI SYLLABLE QUX;Lo;0;L;;;;;N;;;;; A40E;YI SYLLABLE QU;Lo;0;L;;;;;N;;;;; A40F;YI SYLLABLE QUP;Lo;0;L;;;;;N;;;;; A410;YI SYLLABLE QURX;Lo;0;L;;;;;N;;;;; A411;YI SYLLABLE QUR;Lo;0;L;;;;;N;;;;; A412;YI SYLLABLE QYT;Lo;0;L;;;;;N;;;;; A413;YI SYLLABLE QYX;Lo;0;L;;;;;N;;;;; A414;YI SYLLABLE QY;Lo;0;L;;;;;N;;;;; A415;YI SYLLABLE QYP;Lo;0;L;;;;;N;;;;; A416;YI SYLLABLE QYRX;Lo;0;L;;;;;N;;;;; A417;YI SYLLABLE QYR;Lo;0;L;;;;;N;;;;; A418;YI SYLLABLE JJIT;Lo;0;L;;;;;N;;;;; A419;YI SYLLABLE JJIX;Lo;0;L;;;;;N;;;;; A41A;YI SYLLABLE JJI;Lo;0;L;;;;;N;;;;; A41B;YI SYLLABLE JJIP;Lo;0;L;;;;;N;;;;; A41C;YI SYLLABLE JJIET;Lo;0;L;;;;;N;;;;; A41D;YI SYLLABLE JJIEX;Lo;0;L;;;;;N;;;;; A41E;YI SYLLABLE JJIE;Lo;0;L;;;;;N;;;;; A41F;YI SYLLABLE JJIEP;Lo;0;L;;;;;N;;;;; A420;YI SYLLABLE JJUOX;Lo;0;L;;;;;N;;;;; A421;YI SYLLABLE JJUO;Lo;0;L;;;;;N;;;;; A422;YI SYLLABLE JJUOP;Lo;0;L;;;;;N;;;;; A423;YI SYLLABLE JJOT;Lo;0;L;;;;;N;;;;; A424;YI SYLLABLE JJOX;Lo;0;L;;;;;N;;;;; A425;YI SYLLABLE JJO;Lo;0;L;;;;;N;;;;; A426;YI SYLLABLE JJOP;Lo;0;L;;;;;N;;;;; A427;YI SYLLABLE JJUT;Lo;0;L;;;;;N;;;;; A428;YI SYLLABLE JJUX;Lo;0;L;;;;;N;;;;; A429;YI SYLLABLE JJU;Lo;0;L;;;;;N;;;;; A42A;YI SYLLABLE JJUP;Lo;0;L;;;;;N;;;;; A42B;YI SYLLABLE JJURX;Lo;0;L;;;;;N;;;;; A42C;YI SYLLABLE JJUR;Lo;0;L;;;;;N;;;;; A42D;YI SYLLABLE JJYT;Lo;0;L;;;;;N;;;;; A42E;YI SYLLABLE JJYX;Lo;0;L;;;;;N;;;;; A42F;YI SYLLABLE JJY;Lo;0;L;;;;;N;;;;; A430;YI SYLLABLE JJYP;Lo;0;L;;;;;N;;;;; A431;YI SYLLABLE NJIT;Lo;0;L;;;;;N;;;;; A432;YI SYLLABLE NJIX;Lo;0;L;;;;;N;;;;; A433;YI SYLLABLE NJI;Lo;0;L;;;;;N;;;;; A434;YI SYLLABLE NJIP;Lo;0;L;;;;;N;;;;; A435;YI SYLLABLE NJIET;Lo;0;L;;;;;N;;;;; A436;YI SYLLABLE NJIEX;Lo;0;L;;;;;N;;;;; A437;YI SYLLABLE NJIE;Lo;0;L;;;;;N;;;;; A438;YI SYLLABLE NJIEP;Lo;0;L;;;;;N;;;;; A439;YI SYLLABLE NJUOX;Lo;0;L;;;;;N;;;;; A43A;YI SYLLABLE NJUO;Lo;0;L;;;;;N;;;;; A43B;YI SYLLABLE NJOT;Lo;0;L;;;;;N;;;;; A43C;YI SYLLABLE NJOX;Lo;0;L;;;;;N;;;;; A43D;YI SYLLABLE NJO;Lo;0;L;;;;;N;;;;; A43E;YI SYLLABLE NJOP;Lo;0;L;;;;;N;;;;; A43F;YI SYLLABLE NJUX;Lo;0;L;;;;;N;;;;; A440;YI SYLLABLE NJU;Lo;0;L;;;;;N;;;;; A441;YI SYLLABLE NJUP;Lo;0;L;;;;;N;;;;; A442;YI SYLLABLE NJURX;Lo;0;L;;;;;N;;;;; A443;YI SYLLABLE NJUR;Lo;0;L;;;;;N;;;;; A444;YI SYLLABLE NJYT;Lo;0;L;;;;;N;;;;; A445;YI SYLLABLE NJYX;Lo;0;L;;;;;N;;;;; A446;YI SYLLABLE NJY;Lo;0;L;;;;;N;;;;; A447;YI SYLLABLE NJYP;Lo;0;L;;;;;N;;;;; A448;YI SYLLABLE NJYRX;Lo;0;L;;;;;N;;;;; A449;YI SYLLABLE NJYR;Lo;0;L;;;;;N;;;;; A44A;YI SYLLABLE NYIT;Lo;0;L;;;;;N;;;;; A44B;YI SYLLABLE NYIX;Lo;0;L;;;;;N;;;;; A44C;YI SYLLABLE NYI;Lo;0;L;;;;;N;;;;; A44D;YI SYLLABLE NYIP;Lo;0;L;;;;;N;;;;; A44E;YI SYLLABLE NYIET;Lo;0;L;;;;;N;;;;; A44F;YI SYLLABLE NYIEX;Lo;0;L;;;;;N;;;;; A450;YI SYLLABLE NYIE;Lo;0;L;;;;;N;;;;; A451;YI SYLLABLE NYIEP;Lo;0;L;;;;;N;;;;; A452;YI SYLLABLE NYUOX;Lo;0;L;;;;;N;;;;; A453;YI SYLLABLE NYUO;Lo;0;L;;;;;N;;;;; A454;YI SYLLABLE NYUOP;Lo;0;L;;;;;N;;;;; A455;YI SYLLABLE NYOT;Lo;0;L;;;;;N;;;;; A456;YI SYLLABLE NYOX;Lo;0;L;;;;;N;;;;; A457;YI SYLLABLE NYO;Lo;0;L;;;;;N;;;;; A458;YI SYLLABLE NYOP;Lo;0;L;;;;;N;;;;; A459;YI SYLLABLE NYUT;Lo;0;L;;;;;N;;;;; A45A;YI SYLLABLE NYUX;Lo;0;L;;;;;N;;;;; A45B;YI SYLLABLE NYU;Lo;0;L;;;;;N;;;;; A45C;YI SYLLABLE NYUP;Lo;0;L;;;;;N;;;;; A45D;YI SYLLABLE XIT;Lo;0;L;;;;;N;;;;; A45E;YI SYLLABLE XIX;Lo;0;L;;;;;N;;;;; A45F;YI SYLLABLE XI;Lo;0;L;;;;;N;;;;; A460;YI SYLLABLE XIP;Lo;0;L;;;;;N;;;;; A461;YI SYLLABLE XIET;Lo;0;L;;;;;N;;;;; A462;YI SYLLABLE XIEX;Lo;0;L;;;;;N;;;;; A463;YI SYLLABLE XIE;Lo;0;L;;;;;N;;;;; A464;YI SYLLABLE XIEP;Lo;0;L;;;;;N;;;;; A465;YI SYLLABLE XUOX;Lo;0;L;;;;;N;;;;; A466;YI SYLLABLE XUO;Lo;0;L;;;;;N;;;;; A467;YI SYLLABLE XOT;Lo;0;L;;;;;N;;;;; A468;YI SYLLABLE XOX;Lo;0;L;;;;;N;;;;; A469;YI SYLLABLE XO;Lo;0;L;;;;;N;;;;; A46A;YI SYLLABLE XOP;Lo;0;L;;;;;N;;;;; A46B;YI SYLLABLE XYT;Lo;0;L;;;;;N;;;;; A46C;YI SYLLABLE XYX;Lo;0;L;;;;;N;;;;; A46D;YI SYLLABLE XY;Lo;0;L;;;;;N;;;;; A46E;YI SYLLABLE XYP;Lo;0;L;;;;;N;;;;; A46F;YI SYLLABLE XYRX;Lo;0;L;;;;;N;;;;; A470;YI SYLLABLE XYR;Lo;0;L;;;;;N;;;;; A471;YI SYLLABLE YIT;Lo;0;L;;;;;N;;;;; A472;YI SYLLABLE YIX;Lo;0;L;;;;;N;;;;; A473;YI SYLLABLE YI;Lo;0;L;;;;;N;;;;; A474;YI SYLLABLE YIP;Lo;0;L;;;;;N;;;;; A475;YI SYLLABLE YIET;Lo;0;L;;;;;N;;;;; A476;YI SYLLABLE YIEX;Lo;0;L;;;;;N;;;;; A477;YI SYLLABLE YIE;Lo;0;L;;;;;N;;;;; A478;YI SYLLABLE YIEP;Lo;0;L;;;;;N;;;;; A479;YI SYLLABLE YUOT;Lo;0;L;;;;;N;;;;; A47A;YI SYLLABLE YUOX;Lo;0;L;;;;;N;;;;; A47B;YI SYLLABLE YUO;Lo;0;L;;;;;N;;;;; A47C;YI SYLLABLE YUOP;Lo;0;L;;;;;N;;;;; A47D;YI SYLLABLE YOT;Lo;0;L;;;;;N;;;;; A47E;YI SYLLABLE YOX;Lo;0;L;;;;;N;;;;; A47F;YI SYLLABLE YO;Lo;0;L;;;;;N;;;;; A480;YI SYLLABLE YOP;Lo;0;L;;;;;N;;;;; A481;YI SYLLABLE YUT;Lo;0;L;;;;;N;;;;; A482;YI SYLLABLE YUX;Lo;0;L;;;;;N;;;;; A483;YI SYLLABLE YU;Lo;0;L;;;;;N;;;;; A484;YI SYLLABLE YUP;Lo;0;L;;;;;N;;;;; A485;YI SYLLABLE YURX;Lo;0;L;;;;;N;;;;; A486;YI SYLLABLE YUR;Lo;0;L;;;;;N;;;;; A487;YI SYLLABLE YYT;Lo;0;L;;;;;N;;;;; A488;YI SYLLABLE YYX;Lo;0;L;;;;;N;;;;; A489;YI SYLLABLE YY;Lo;0;L;;;;;N;;;;; A48A;YI SYLLABLE YYP;Lo;0;L;;;;;N;;;;; A48B;YI SYLLABLE YYRX;Lo;0;L;;;;;N;;;;; A48C;YI SYLLABLE YYR;Lo;0;L;;;;;N;;;;; A490;YI RADICAL QOT;So;0;ON;;;;;N;;;;; A491;YI RADICAL LI;So;0;ON;;;;;N;;;;; A492;YI RADICAL KIT;So;0;ON;;;;;N;;;;; A493;YI RADICAL NYIP;So;0;ON;;;;;N;;;;; A494;YI RADICAL CYP;So;0;ON;;;;;N;;;;; A495;YI RADICAL SSI;So;0;ON;;;;;N;;;;; A496;YI RADICAL GGOP;So;0;ON;;;;;N;;;;; A497;YI RADICAL GEP;So;0;ON;;;;;N;;;;; A498;YI RADICAL MI;So;0;ON;;;;;N;;;;; A499;YI RADICAL HXIT;So;0;ON;;;;;N;;;;; A49A;YI RADICAL LYR;So;0;ON;;;;;N;;;;; A49B;YI RADICAL BBUT;So;0;ON;;;;;N;;;;; A49C;YI RADICAL MOP;So;0;ON;;;;;N;;;;; A49D;YI RADICAL YO;So;0;ON;;;;;N;;;;; A49E;YI RADICAL PUT;So;0;ON;;;;;N;;;;; A49F;YI RADICAL HXUO;So;0;ON;;;;;N;;;;; A4A0;YI RADICAL TAT;So;0;ON;;;;;N;;;;; A4A1;YI RADICAL GA;So;0;ON;;;;;N;;;;; A4A2;YI RADICAL ZUP;So;0;ON;;;;;N;;;;; A4A3;YI RADICAL CYT;So;0;ON;;;;;N;;;;; A4A4;YI RADICAL DDUR;So;0;ON;;;;;N;;;;; A4A5;YI RADICAL BUR;So;0;ON;;;;;N;;;;; A4A6;YI RADICAL GGUO;So;0;ON;;;;;N;;;;; A4A7;YI RADICAL NYOP;So;0;ON;;;;;N;;;;; A4A8;YI RADICAL TU;So;0;ON;;;;;N;;;;; A4A9;YI RADICAL OP;So;0;ON;;;;;N;;;;; A4AA;YI RADICAL JJUT;So;0;ON;;;;;N;;;;; A4AB;YI RADICAL ZOT;So;0;ON;;;;;N;;;;; A4AC;YI RADICAL PYT;So;0;ON;;;;;N;;;;; A4AD;YI RADICAL HMO;So;0;ON;;;;;N;;;;; A4AE;YI RADICAL YIT;So;0;ON;;;;;N;;;;; A4AF;YI RADICAL VUR;So;0;ON;;;;;N;;;;; A4B0;YI RADICAL SHY;So;0;ON;;;;;N;;;;; A4B1;YI RADICAL VEP;So;0;ON;;;;;N;;;;; A4B2;YI RADICAL ZA;So;0;ON;;;;;N;;;;; A4B3;YI RADICAL JO;So;0;ON;;;;;N;;;;; A4B4;YI RADICAL NZUP;So;0;ON;;;;;N;;;;; A4B5;YI RADICAL JJY;So;0;ON;;;;;N;;;;; A4B6;YI RADICAL GOT;So;0;ON;;;;;N;;;;; A4B7;YI RADICAL JJIE;So;0;ON;;;;;N;;;;; A4B8;YI RADICAL WO;So;0;ON;;;;;N;;;;; A4B9;YI RADICAL DU;So;0;ON;;;;;N;;;;; A4BA;YI RADICAL SHUR;So;0;ON;;;;;N;;;;; A4BB;YI RADICAL LIE;So;0;ON;;;;;N;;;;; A4BC;YI RADICAL CY;So;0;ON;;;;;N;;;;; A4BD;YI RADICAL CUOP;So;0;ON;;;;;N;;;;; A4BE;YI RADICAL CIP;So;0;ON;;;;;N;;;;; A4BF;YI RADICAL HXOP;So;0;ON;;;;;N;;;;; A4C0;YI RADICAL SHAT;So;0;ON;;;;;N;;;;; A4C1;YI RADICAL ZUR;So;0;ON;;;;;N;;;;; A4C2;YI RADICAL SHOP;So;0;ON;;;;;N;;;;; A4C3;YI RADICAL CHE;So;0;ON;;;;;N;;;;; A4C4;YI RADICAL ZZIET;So;0;ON;;;;;N;;;;; A4C5;YI RADICAL NBIE;So;0;ON;;;;;N;;;;; A4C6;YI RADICAL KE;So;0;ON;;;;;N;;;;; A4D0;LISU LETTER BA;Lo;0;L;;;;;N;;;;; A4D1;LISU LETTER PA;Lo;0;L;;;;;N;;;;; A4D2;LISU LETTER PHA;Lo;0;L;;;;;N;;;;; A4D3;LISU LETTER DA;Lo;0;L;;;;;N;;;;; A4D4;LISU LETTER TA;Lo;0;L;;;;;N;;;;; A4D5;LISU LETTER THA;Lo;0;L;;;;;N;;;;; A4D6;LISU LETTER GA;Lo;0;L;;;;;N;;;;; A4D7;LISU LETTER KA;Lo;0;L;;;;;N;;;;; A4D8;LISU LETTER KHA;Lo;0;L;;;;;N;;;;; A4D9;LISU LETTER JA;Lo;0;L;;;;;N;;;;; A4DA;LISU LETTER CA;Lo;0;L;;;;;N;;;;; A4DB;LISU LETTER CHA;Lo;0;L;;;;;N;;;;; A4DC;LISU LETTER DZA;Lo;0;L;;;;;N;;;;; A4DD;LISU LETTER TSA;Lo;0;L;;;;;N;;;;; A4DE;LISU LETTER TSHA;Lo;0;L;;;;;N;;;;; A4DF;LISU LETTER MA;Lo;0;L;;;;;N;;;;; A4E0;LISU LETTER NA;Lo;0;L;;;;;N;;;;; A4E1;LISU LETTER LA;Lo;0;L;;;;;N;;;;; A4E2;LISU LETTER SA;Lo;0;L;;;;;N;;;;; A4E3;LISU LETTER ZHA;Lo;0;L;;;;;N;;;;; A4E4;LISU LETTER ZA;Lo;0;L;;;;;N;;;;; A4E5;LISU LETTER NGA;Lo;0;L;;;;;N;;;;; A4E6;LISU LETTER HA;Lo;0;L;;;;;N;;;;; A4E7;LISU LETTER XA;Lo;0;L;;;;;N;;;;; A4E8;LISU LETTER HHA;Lo;0;L;;;;;N;;;;; A4E9;LISU LETTER FA;Lo;0;L;;;;;N;;;;; A4EA;LISU LETTER WA;Lo;0;L;;;;;N;;;;; A4EB;LISU LETTER SHA;Lo;0;L;;;;;N;;;;; A4EC;LISU LETTER YA;Lo;0;L;;;;;N;;;;; A4ED;LISU LETTER GHA;Lo;0;L;;;;;N;;;;; A4EE;LISU LETTER A;Lo;0;L;;;;;N;;;;; A4EF;LISU LETTER AE;Lo;0;L;;;;;N;;;;; A4F0;LISU LETTER E;Lo;0;L;;;;;N;;;;; A4F1;LISU LETTER EU;Lo;0;L;;;;;N;;;;; A4F2;LISU LETTER I;Lo;0;L;;;;;N;;;;; A4F3;LISU LETTER O;Lo;0;L;;;;;N;;;;; A4F4;LISU LETTER U;Lo;0;L;;;;;N;;;;; A4F5;LISU LETTER UE;Lo;0;L;;;;;N;;;;; A4F6;LISU LETTER UH;Lo;0;L;;;;;N;;;;; A4F7;LISU LETTER OE;Lo;0;L;;;;;N;;;;; A4F8;LISU LETTER TONE MYA TI;Lm;0;L;;;;;N;;;;; A4F9;LISU LETTER TONE NA PO;Lm;0;L;;;;;N;;;;; A4FA;LISU LETTER TONE MYA CYA;Lm;0;L;;;;;N;;;;; A4FB;LISU LETTER TONE MYA BO;Lm;0;L;;;;;N;;;;; A4FC;LISU LETTER TONE MYA NA;Lm;0;L;;;;;N;;;;; A4FD;LISU LETTER TONE MYA JEU;Lm;0;L;;;;;N;;;;; A4FE;LISU PUNCTUATION COMMA;Po;0;L;;;;;N;;;;; A4FF;LISU PUNCTUATION FULL STOP;Po;0;L;;;;;N;;;;; A500;VAI SYLLABLE EE;Lo;0;L;;;;;N;;;;; A501;VAI SYLLABLE EEN;Lo;0;L;;;;;N;;;;; A502;VAI SYLLABLE HEE;Lo;0;L;;;;;N;;;;; A503;VAI SYLLABLE WEE;Lo;0;L;;;;;N;;;;; A504;VAI SYLLABLE WEEN;Lo;0;L;;;;;N;;;;; A505;VAI SYLLABLE PEE;Lo;0;L;;;;;N;;;;; A506;VAI SYLLABLE BHEE;Lo;0;L;;;;;N;;;;; A507;VAI SYLLABLE BEE;Lo;0;L;;;;;N;;;;; A508;VAI SYLLABLE MBEE;Lo;0;L;;;;;N;;;;; A509;VAI SYLLABLE KPEE;Lo;0;L;;;;;N;;;;; A50A;VAI SYLLABLE MGBEE;Lo;0;L;;;;;N;;;;; A50B;VAI SYLLABLE GBEE;Lo;0;L;;;;;N;;;;; A50C;VAI SYLLABLE FEE;Lo;0;L;;;;;N;;;;; A50D;VAI SYLLABLE VEE;Lo;0;L;;;;;N;;;;; A50E;VAI SYLLABLE TEE;Lo;0;L;;;;;N;;;;; A50F;VAI SYLLABLE THEE;Lo;0;L;;;;;N;;;;; A510;VAI SYLLABLE DHEE;Lo;0;L;;;;;N;;;;; A511;VAI SYLLABLE DHHEE;Lo;0;L;;;;;N;;;;; A512;VAI SYLLABLE LEE;Lo;0;L;;;;;N;;;;; A513;VAI SYLLABLE REE;Lo;0;L;;;;;N;;;;; A514;VAI SYLLABLE DEE;Lo;0;L;;;;;N;;;;; A515;VAI SYLLABLE NDEE;Lo;0;L;;;;;N;;;;; A516;VAI SYLLABLE SEE;Lo;0;L;;;;;N;;;;; A517;VAI SYLLABLE SHEE;Lo;0;L;;;;;N;;;;; A518;VAI SYLLABLE ZEE;Lo;0;L;;;;;N;;;;; A519;VAI SYLLABLE ZHEE;Lo;0;L;;;;;N;;;;; A51A;VAI SYLLABLE CEE;Lo;0;L;;;;;N;;;;; A51B;VAI SYLLABLE JEE;Lo;0;L;;;;;N;;;;; A51C;VAI SYLLABLE NJEE;Lo;0;L;;;;;N;;;;; A51D;VAI SYLLABLE YEE;Lo;0;L;;;;;N;;;;; A51E;VAI SYLLABLE KEE;Lo;0;L;;;;;N;;;;; A51F;VAI SYLLABLE NGGEE;Lo;0;L;;;;;N;;;;; A520;VAI SYLLABLE GEE;Lo;0;L;;;;;N;;;;; A521;VAI SYLLABLE MEE;Lo;0;L;;;;;N;;;;; A522;VAI SYLLABLE NEE;Lo;0;L;;;;;N;;;;; A523;VAI SYLLABLE NYEE;Lo;0;L;;;;;N;;;;; A524;VAI SYLLABLE I;Lo;0;L;;;;;N;;;;; A525;VAI SYLLABLE IN;Lo;0;L;;;;;N;;;;; A526;VAI SYLLABLE HI;Lo;0;L;;;;;N;;;;; A527;VAI SYLLABLE HIN;Lo;0;L;;;;;N;;;;; A528;VAI SYLLABLE WI;Lo;0;L;;;;;N;;;;; A529;VAI SYLLABLE WIN;Lo;0;L;;;;;N;;;;; A52A;VAI SYLLABLE PI;Lo;0;L;;;;;N;;;;; A52B;VAI SYLLABLE BHI;Lo;0;L;;;;;N;;;;; A52C;VAI SYLLABLE BI;Lo;0;L;;;;;N;;;;; A52D;VAI SYLLABLE MBI;Lo;0;L;;;;;N;;;;; A52E;VAI SYLLABLE KPI;Lo;0;L;;;;;N;;;;; A52F;VAI SYLLABLE MGBI;Lo;0;L;;;;;N;;;;; A530;VAI SYLLABLE GBI;Lo;0;L;;;;;N;;;;; A531;VAI SYLLABLE FI;Lo;0;L;;;;;N;;;;; A532;VAI SYLLABLE VI;Lo;0;L;;;;;N;;;;; A533;VAI SYLLABLE TI;Lo;0;L;;;;;N;;;;; A534;VAI SYLLABLE THI;Lo;0;L;;;;;N;;;;; A535;VAI SYLLABLE DHI;Lo;0;L;;;;;N;;;;; A536;VAI SYLLABLE DHHI;Lo;0;L;;;;;N;;;;; A537;VAI SYLLABLE LI;Lo;0;L;;;;;N;;;;; A538;VAI SYLLABLE RI;Lo;0;L;;;;;N;;;;; A539;VAI SYLLABLE DI;Lo;0;L;;;;;N;;;;; A53A;VAI SYLLABLE NDI;Lo;0;L;;;;;N;;;;; A53B;VAI SYLLABLE SI;Lo;0;L;;;;;N;;;;; A53C;VAI SYLLABLE SHI;Lo;0;L;;;;;N;;;;; A53D;VAI SYLLABLE ZI;Lo;0;L;;;;;N;;;;; A53E;VAI SYLLABLE ZHI;Lo;0;L;;;;;N;;;;; A53F;VAI SYLLABLE CI;Lo;0;L;;;;;N;;;;; A540;VAI SYLLABLE JI;Lo;0;L;;;;;N;;;;; A541;VAI SYLLABLE NJI;Lo;0;L;;;;;N;;;;; A542;VAI SYLLABLE YI;Lo;0;L;;;;;N;;;;; A543;VAI SYLLABLE KI;Lo;0;L;;;;;N;;;;; A544;VAI SYLLABLE NGGI;Lo;0;L;;;;;N;;;;; A545;VAI SYLLABLE GI;Lo;0;L;;;;;N;;;;; A546;VAI SYLLABLE MI;Lo;0;L;;;;;N;;;;; A547;VAI SYLLABLE NI;Lo;0;L;;;;;N;;;;; A548;VAI SYLLABLE NYI;Lo;0;L;;;;;N;;;;; A549;VAI SYLLABLE A;Lo;0;L;;;;;N;;;;; A54A;VAI SYLLABLE AN;Lo;0;L;;;;;N;;;;; A54B;VAI SYLLABLE NGAN;Lo;0;L;;;;;N;;;;; A54C;VAI SYLLABLE HA;Lo;0;L;;;;;N;;;;; A54D;VAI SYLLABLE HAN;Lo;0;L;;;;;N;;;;; A54E;VAI SYLLABLE WA;Lo;0;L;;;;;N;;;;; A54F;VAI SYLLABLE WAN;Lo;0;L;;;;;N;;;;; A550;VAI SYLLABLE PA;Lo;0;L;;;;;N;;;;; A551;VAI SYLLABLE BHA;Lo;0;L;;;;;N;;;;; A552;VAI SYLLABLE BA;Lo;0;L;;;;;N;;;;; A553;VAI SYLLABLE MBA;Lo;0;L;;;;;N;;;;; A554;VAI SYLLABLE KPA;Lo;0;L;;;;;N;;;;; A555;VAI SYLLABLE KPAN;Lo;0;L;;;;;N;;;;; A556;VAI SYLLABLE MGBA;Lo;0;L;;;;;N;;;;; A557;VAI SYLLABLE GBA;Lo;0;L;;;;;N;;;;; A558;VAI SYLLABLE FA;Lo;0;L;;;;;N;;;;; A559;VAI SYLLABLE VA;Lo;0;L;;;;;N;;;;; A55A;VAI SYLLABLE TA;Lo;0;L;;;;;N;;;;; A55B;VAI SYLLABLE THA;Lo;0;L;;;;;N;;;;; A55C;VAI SYLLABLE DHA;Lo;0;L;;;;;N;;;;; A55D;VAI SYLLABLE DHHA;Lo;0;L;;;;;N;;;;; A55E;VAI SYLLABLE LA;Lo;0;L;;;;;N;;;;; A55F;VAI SYLLABLE RA;Lo;0;L;;;;;N;;;;; A560;VAI SYLLABLE DA;Lo;0;L;;;;;N;;;;; A561;VAI SYLLABLE NDA;Lo;0;L;;;;;N;;;;; A562;VAI SYLLABLE SA;Lo;0;L;;;;;N;;;;; A563;VAI SYLLABLE SHA;Lo;0;L;;;;;N;;;;; A564;VAI SYLLABLE ZA;Lo;0;L;;;;;N;;;;; A565;VAI SYLLABLE ZHA;Lo;0;L;;;;;N;;;;; A566;VAI SYLLABLE CA;Lo;0;L;;;;;N;;;;; A567;VAI SYLLABLE JA;Lo;0;L;;;;;N;;;;; A568;VAI SYLLABLE NJA;Lo;0;L;;;;;N;;;;; A569;VAI SYLLABLE YA;Lo;0;L;;;;;N;;;;; A56A;VAI SYLLABLE KA;Lo;0;L;;;;;N;;;;; A56B;VAI SYLLABLE KAN;Lo;0;L;;;;;N;;;;; A56C;VAI SYLLABLE NGGA;Lo;0;L;;;;;N;;;;; A56D;VAI SYLLABLE GA;Lo;0;L;;;;;N;;;;; A56E;VAI SYLLABLE MA;Lo;0;L;;;;;N;;;;; A56F;VAI SYLLABLE NA;Lo;0;L;;;;;N;;;;; A570;VAI SYLLABLE NYA;Lo;0;L;;;;;N;;;;; A571;VAI SYLLABLE OO;Lo;0;L;;;;;N;;;;; A572;VAI SYLLABLE OON;Lo;0;L;;;;;N;;;;; A573;VAI SYLLABLE HOO;Lo;0;L;;;;;N;;;;; A574;VAI SYLLABLE WOO;Lo;0;L;;;;;N;;;;; A575;VAI SYLLABLE WOON;Lo;0;L;;;;;N;;;;; A576;VAI SYLLABLE POO;Lo;0;L;;;;;N;;;;; A577;VAI SYLLABLE BHOO;Lo;0;L;;;;;N;;;;; A578;VAI SYLLABLE BOO;Lo;0;L;;;;;N;;;;; A579;VAI SYLLABLE MBOO;Lo;0;L;;;;;N;;;;; A57A;VAI SYLLABLE KPOO;Lo;0;L;;;;;N;;;;; A57B;VAI SYLLABLE MGBOO;Lo;0;L;;;;;N;;;;; A57C;VAI SYLLABLE GBOO;Lo;0;L;;;;;N;;;;; A57D;VAI SYLLABLE FOO;Lo;0;L;;;;;N;;;;; A57E;VAI SYLLABLE VOO;Lo;0;L;;;;;N;;;;; A57F;VAI SYLLABLE TOO;Lo;0;L;;;;;N;;;;; A580;VAI SYLLABLE THOO;Lo;0;L;;;;;N;;;;; A581;VAI SYLLABLE DHOO;Lo;0;L;;;;;N;;;;; A582;VAI SYLLABLE DHHOO;Lo;0;L;;;;;N;;;;; A583;VAI SYLLABLE LOO;Lo;0;L;;;;;N;;;;; A584;VAI SYLLABLE ROO;Lo;0;L;;;;;N;;;;; A585;VAI SYLLABLE DOO;Lo;0;L;;;;;N;;;;; A586;VAI SYLLABLE NDOO;Lo;0;L;;;;;N;;;;; A587;VAI SYLLABLE SOO;Lo;0;L;;;;;N;;;;; A588;VAI SYLLABLE SHOO;Lo;0;L;;;;;N;;;;; A589;VAI SYLLABLE ZOO;Lo;0;L;;;;;N;;;;; A58A;VAI SYLLABLE ZHOO;Lo;0;L;;;;;N;;;;; A58B;VAI SYLLABLE COO;Lo;0;L;;;;;N;;;;; A58C;VAI SYLLABLE JOO;Lo;0;L;;;;;N;;;;; A58D;VAI SYLLABLE NJOO;Lo;0;L;;;;;N;;;;; A58E;VAI SYLLABLE YOO;Lo;0;L;;;;;N;;;;; A58F;VAI SYLLABLE KOO;Lo;0;L;;;;;N;;;;; A590;VAI SYLLABLE NGGOO;Lo;0;L;;;;;N;;;;; A591;VAI SYLLABLE GOO;Lo;0;L;;;;;N;;;;; A592;VAI SYLLABLE MOO;Lo;0;L;;;;;N;;;;; A593;VAI SYLLABLE NOO;Lo;0;L;;;;;N;;;;; A594;VAI SYLLABLE NYOO;Lo;0;L;;;;;N;;;;; A595;VAI SYLLABLE U;Lo;0;L;;;;;N;;;;; A596;VAI SYLLABLE UN;Lo;0;L;;;;;N;;;;; A597;VAI SYLLABLE HU;Lo;0;L;;;;;N;;;;; A598;VAI SYLLABLE HUN;Lo;0;L;;;;;N;;;;; A599;VAI SYLLABLE WU;Lo;0;L;;;;;N;;;;; A59A;VAI SYLLABLE WUN;Lo;0;L;;;;;N;;;;; A59B;VAI SYLLABLE PU;Lo;0;L;;;;;N;;;;; A59C;VAI SYLLABLE BHU;Lo;0;L;;;;;N;;;;; A59D;VAI SYLLABLE BU;Lo;0;L;;;;;N;;;;; A59E;VAI SYLLABLE MBU;Lo;0;L;;;;;N;;;;; A59F;VAI SYLLABLE KPU;Lo;0;L;;;;;N;;;;; A5A0;VAI SYLLABLE MGBU;Lo;0;L;;;;;N;;;;; A5A1;VAI SYLLABLE GBU;Lo;0;L;;;;;N;;;;; A5A2;VAI SYLLABLE FU;Lo;0;L;;;;;N;;;;; A5A3;VAI SYLLABLE VU;Lo;0;L;;;;;N;;;;; A5A4;VAI SYLLABLE TU;Lo;0;L;;;;;N;;;;; A5A5;VAI SYLLABLE THU;Lo;0;L;;;;;N;;;;; A5A6;VAI SYLLABLE DHU;Lo;0;L;;;;;N;;;;; A5A7;VAI SYLLABLE DHHU;Lo;0;L;;;;;N;;;;; A5A8;VAI SYLLABLE LU;Lo;0;L;;;;;N;;;;; A5A9;VAI SYLLABLE RU;Lo;0;L;;;;;N;;;;; A5AA;VAI SYLLABLE DU;Lo;0;L;;;;;N;;;;; A5AB;VAI SYLLABLE NDU;Lo;0;L;;;;;N;;;;; A5AC;VAI SYLLABLE SU;Lo;0;L;;;;;N;;;;; A5AD;VAI SYLLABLE SHU;Lo;0;L;;;;;N;;;;; A5AE;VAI SYLLABLE ZU;Lo;0;L;;;;;N;;;;; A5AF;VAI SYLLABLE ZHU;Lo;0;L;;;;;N;;;;; A5B0;VAI SYLLABLE CU;Lo;0;L;;;;;N;;;;; A5B1;VAI SYLLABLE JU;Lo;0;L;;;;;N;;;;; A5B2;VAI SYLLABLE NJU;Lo;0;L;;;;;N;;;;; A5B3;VAI SYLLABLE YU;Lo;0;L;;;;;N;;;;; A5B4;VAI SYLLABLE KU;Lo;0;L;;;;;N;;;;; A5B5;VAI SYLLABLE NGGU;Lo;0;L;;;;;N;;;;; A5B6;VAI SYLLABLE GU;Lo;0;L;;;;;N;;;;; A5B7;VAI SYLLABLE MU;Lo;0;L;;;;;N;;;;; A5B8;VAI SYLLABLE NU;Lo;0;L;;;;;N;;;;; A5B9;VAI SYLLABLE NYU;Lo;0;L;;;;;N;;;;; A5BA;VAI SYLLABLE O;Lo;0;L;;;;;N;;;;; A5BB;VAI SYLLABLE ON;Lo;0;L;;;;;N;;;;; A5BC;VAI SYLLABLE NGON;Lo;0;L;;;;;N;;;;; A5BD;VAI SYLLABLE HO;Lo;0;L;;;;;N;;;;; A5BE;VAI SYLLABLE HON;Lo;0;L;;;;;N;;;;; A5BF;VAI SYLLABLE WO;Lo;0;L;;;;;N;;;;; A5C0;VAI SYLLABLE WON;Lo;0;L;;;;;N;;;;; A5C1;VAI SYLLABLE PO;Lo;0;L;;;;;N;;;;; A5C2;VAI SYLLABLE BHO;Lo;0;L;;;;;N;;;;; A5C3;VAI SYLLABLE BO;Lo;0;L;;;;;N;;;;; A5C4;VAI SYLLABLE MBO;Lo;0;L;;;;;N;;;;; A5C5;VAI SYLLABLE KPO;Lo;0;L;;;;;N;;;;; A5C6;VAI SYLLABLE MGBO;Lo;0;L;;;;;N;;;;; A5C7;VAI SYLLABLE GBO;Lo;0;L;;;;;N;;;;; A5C8;VAI SYLLABLE GBON;Lo;0;L;;;;;N;;;;; A5C9;VAI SYLLABLE FO;Lo;0;L;;;;;N;;;;; A5CA;VAI SYLLABLE VO;Lo;0;L;;;;;N;;;;; A5CB;VAI SYLLABLE TO;Lo;0;L;;;;;N;;;;; A5CC;VAI SYLLABLE THO;Lo;0;L;;;;;N;;;;; A5CD;VAI SYLLABLE DHO;Lo;0;L;;;;;N;;;;; A5CE;VAI SYLLABLE DHHO;Lo;0;L;;;;;N;;;;; A5CF;VAI SYLLABLE LO;Lo;0;L;;;;;N;;;;; A5D0;VAI SYLLABLE RO;Lo;0;L;;;;;N;;;;; A5D1;VAI SYLLABLE DO;Lo;0;L;;;;;N;;;;; A5D2;VAI SYLLABLE NDO;Lo;0;L;;;;;N;;;;; A5D3;VAI SYLLABLE SO;Lo;0;L;;;;;N;;;;; A5D4;VAI SYLLABLE SHO;Lo;0;L;;;;;N;;;;; A5D5;VAI SYLLABLE ZO;Lo;0;L;;;;;N;;;;; A5D6;VAI SYLLABLE ZHO;Lo;0;L;;;;;N;;;;; A5D7;VAI SYLLABLE CO;Lo;0;L;;;;;N;;;;; A5D8;VAI SYLLABLE JO;Lo;0;L;;;;;N;;;;; A5D9;VAI SYLLABLE NJO;Lo;0;L;;;;;N;;;;; A5DA;VAI SYLLABLE YO;Lo;0;L;;;;;N;;;;; A5DB;VAI SYLLABLE KO;Lo;0;L;;;;;N;;;;; A5DC;VAI SYLLABLE NGGO;Lo;0;L;;;;;N;;;;; A5DD;VAI SYLLABLE GO;Lo;0;L;;;;;N;;;;; A5DE;VAI SYLLABLE MO;Lo;0;L;;;;;N;;;;; A5DF;VAI SYLLABLE NO;Lo;0;L;;;;;N;;;;; A5E0;VAI SYLLABLE NYO;Lo;0;L;;;;;N;;;;; A5E1;VAI SYLLABLE E;Lo;0;L;;;;;N;;;;; A5E2;VAI SYLLABLE EN;Lo;0;L;;;;;N;;;;; A5E3;VAI SYLLABLE NGEN;Lo;0;L;;;;;N;;;;; A5E4;VAI SYLLABLE HE;Lo;0;L;;;;;N;;;;; A5E5;VAI SYLLABLE HEN;Lo;0;L;;;;;N;;;;; A5E6;VAI SYLLABLE WE;Lo;0;L;;;;;N;;;;; A5E7;VAI SYLLABLE WEN;Lo;0;L;;;;;N;;;;; A5E8;VAI SYLLABLE PE;Lo;0;L;;;;;N;;;;; A5E9;VAI SYLLABLE BHE;Lo;0;L;;;;;N;;;;; A5EA;VAI SYLLABLE BE;Lo;0;L;;;;;N;;;;; A5EB;VAI SYLLABLE MBE;Lo;0;L;;;;;N;;;;; A5EC;VAI SYLLABLE KPE;Lo;0;L;;;;;N;;;;; A5ED;VAI SYLLABLE KPEN;Lo;0;L;;;;;N;;;;; A5EE;VAI SYLLABLE MGBE;Lo;0;L;;;;;N;;;;; A5EF;VAI SYLLABLE GBE;Lo;0;L;;;;;N;;;;; A5F0;VAI SYLLABLE GBEN;Lo;0;L;;;;;N;;;;; A5F1;VAI SYLLABLE FE;Lo;0;L;;;;;N;;;;; A5F2;VAI SYLLABLE VE;Lo;0;L;;;;;N;;;;; A5F3;VAI SYLLABLE TE;Lo;0;L;;;;;N;;;;; A5F4;VAI SYLLABLE THE;Lo;0;L;;;;;N;;;;; A5F5;VAI SYLLABLE DHE;Lo;0;L;;;;;N;;;;; A5F6;VAI SYLLABLE DHHE;Lo;0;L;;;;;N;;;;; A5F7;VAI SYLLABLE LE;Lo;0;L;;;;;N;;;;; A5F8;VAI SYLLABLE RE;Lo;0;L;;;;;N;;;;; A5F9;VAI SYLLABLE DE;Lo;0;L;;;;;N;;;;; A5FA;VAI SYLLABLE NDE;Lo;0;L;;;;;N;;;;; A5FB;VAI SYLLABLE SE;Lo;0;L;;;;;N;;;;; A5FC;VAI SYLLABLE SHE;Lo;0;L;;;;;N;;;;; A5FD;VAI SYLLABLE ZE;Lo;0;L;;;;;N;;;;; A5FE;VAI SYLLABLE ZHE;Lo;0;L;;;;;N;;;;; A5FF;VAI SYLLABLE CE;Lo;0;L;;;;;N;;;;; A600;VAI SYLLABLE JE;Lo;0;L;;;;;N;;;;; A601;VAI SYLLABLE NJE;Lo;0;L;;;;;N;;;;; A602;VAI SYLLABLE YE;Lo;0;L;;;;;N;;;;; A603;VAI SYLLABLE KE;Lo;0;L;;;;;N;;;;; A604;VAI SYLLABLE NGGE;Lo;0;L;;;;;N;;;;; A605;VAI SYLLABLE NGGEN;Lo;0;L;;;;;N;;;;; A606;VAI SYLLABLE GE;Lo;0;L;;;;;N;;;;; A607;VAI SYLLABLE GEN;Lo;0;L;;;;;N;;;;; A608;VAI SYLLABLE ME;Lo;0;L;;;;;N;;;;; A609;VAI SYLLABLE NE;Lo;0;L;;;;;N;;;;; A60A;VAI SYLLABLE NYE;Lo;0;L;;;;;N;;;;; A60B;VAI SYLLABLE NG;Lo;0;L;;;;;N;;;;; A60C;VAI SYLLABLE LENGTHENER;Lm;0;L;;;;;N;;;;; A60D;VAI COMMA;Po;0;ON;;;;;N;;;;; A60E;VAI FULL STOP;Po;0;ON;;;;;N;;;;; A60F;VAI QUESTION MARK;Po;0;ON;;;;;N;;;;; A610;VAI SYLLABLE NDOLE FA;Lo;0;L;;;;;N;;;;; A611;VAI SYLLABLE NDOLE KA;Lo;0;L;;;;;N;;;;; A612;VAI SYLLABLE NDOLE SOO;Lo;0;L;;;;;N;;;;; A613;VAI SYMBOL FEENG;Lo;0;L;;;;;N;;;;; A614;VAI SYMBOL KEENG;Lo;0;L;;;;;N;;;;; A615;VAI SYMBOL TING;Lo;0;L;;;;;N;;;;; A616;VAI SYMBOL NII;Lo;0;L;;;;;N;;;;; A617;VAI SYMBOL BANG;Lo;0;L;;;;;N;;;;; A618;VAI SYMBOL FAA;Lo;0;L;;;;;N;;;;; A619;VAI SYMBOL TAA;Lo;0;L;;;;;N;;;;; A61A;VAI SYMBOL DANG;Lo;0;L;;;;;N;;;;; A61B;VAI SYMBOL DOONG;Lo;0;L;;;;;N;;;;; A61C;VAI SYMBOL KUNG;Lo;0;L;;;;;N;;;;; A61D;VAI SYMBOL TONG;Lo;0;L;;;;;N;;;;; A61E;VAI SYMBOL DO-O;Lo;0;L;;;;;N;;;;; A61F;VAI SYMBOL JONG;Lo;0;L;;;;;N;;;;; A620;VAI DIGIT ZERO;Nd;0;L;;0;0;0;N;;;;; A621;VAI DIGIT ONE;Nd;0;L;;1;1;1;N;;;;; A622;VAI DIGIT TWO;Nd;0;L;;2;2;2;N;;;;; A623;VAI DIGIT THREE;Nd;0;L;;3;3;3;N;;;;; A624;VAI DIGIT FOUR;Nd;0;L;;4;4;4;N;;;;; A625;VAI DIGIT FIVE;Nd;0;L;;5;5;5;N;;;;; A626;VAI DIGIT SIX;Nd;0;L;;6;6;6;N;;;;; A627;VAI DIGIT SEVEN;Nd;0;L;;7;7;7;N;;;;; A628;VAI DIGIT EIGHT;Nd;0;L;;8;8;8;N;;;;; A629;VAI DIGIT NINE;Nd;0;L;;9;9;9;N;;;;; A62A;VAI SYLLABLE NDOLE MA;Lo;0;L;;;;;N;;;;; A62B;VAI SYLLABLE NDOLE DO;Lo;0;L;;;;;N;;;;; A640;CYRILLIC CAPITAL LETTER ZEMLYA;Lu;0;L;;;;;N;;;;A641; A641;CYRILLIC SMALL LETTER ZEMLYA;Ll;0;L;;;;;N;;;A640;;A640 A642;CYRILLIC CAPITAL LETTER DZELO;Lu;0;L;;;;;N;;;;A643; A643;CYRILLIC SMALL LETTER DZELO;Ll;0;L;;;;;N;;;A642;;A642 A644;CYRILLIC CAPITAL LETTER REVERSED DZE;Lu;0;L;;;;;N;;;;A645; A645;CYRILLIC SMALL LETTER REVERSED DZE;Ll;0;L;;;;;N;;;A644;;A644 A646;CYRILLIC CAPITAL LETTER IOTA;Lu;0;L;;;;;N;;;;A647; A647;CYRILLIC SMALL LETTER IOTA;Ll;0;L;;;;;N;;;A646;;A646 A648;CYRILLIC CAPITAL LETTER DJERV;Lu;0;L;;;;;N;;;;A649; A649;CYRILLIC SMALL LETTER DJERV;Ll;0;L;;;;;N;;;A648;;A648 A64A;CYRILLIC CAPITAL LETTER MONOGRAPH UK;Lu;0;L;;;;;N;;;;A64B; A64B;CYRILLIC SMALL LETTER MONOGRAPH UK;Ll;0;L;;;;;N;;;A64A;;A64A A64C;CYRILLIC CAPITAL LETTER BROAD OMEGA;Lu;0;L;;;;;N;;;;A64D; A64D;CYRILLIC SMALL LETTER BROAD OMEGA;Ll;0;L;;;;;N;;;A64C;;A64C A64E;CYRILLIC CAPITAL LETTER NEUTRAL YER;Lu;0;L;;;;;N;;;;A64F; A64F;CYRILLIC SMALL LETTER NEUTRAL YER;Ll;0;L;;;;;N;;;A64E;;A64E A650;CYRILLIC CAPITAL LETTER YERU WITH BACK YER;Lu;0;L;;;;;N;;;;A651; A651;CYRILLIC SMALL LETTER YERU WITH BACK YER;Ll;0;L;;;;;N;;;A650;;A650 A652;CYRILLIC CAPITAL LETTER IOTIFIED YAT;Lu;0;L;;;;;N;;;;A653; A653;CYRILLIC SMALL LETTER IOTIFIED YAT;Ll;0;L;;;;;N;;;A652;;A652 A654;CYRILLIC CAPITAL LETTER REVERSED YU;Lu;0;L;;;;;N;;;;A655; A655;CYRILLIC SMALL LETTER REVERSED YU;Ll;0;L;;;;;N;;;A654;;A654 A656;CYRILLIC CAPITAL LETTER IOTIFIED A;Lu;0;L;;;;;N;;;;A657; A657;CYRILLIC SMALL LETTER IOTIFIED A;Ll;0;L;;;;;N;;;A656;;A656 A658;CYRILLIC CAPITAL LETTER CLOSED LITTLE YUS;Lu;0;L;;;;;N;;;;A659; A659;CYRILLIC SMALL LETTER CLOSED LITTLE YUS;Ll;0;L;;;;;N;;;A658;;A658 A65A;CYRILLIC CAPITAL LETTER BLENDED YUS;Lu;0;L;;;;;N;;;;A65B; A65B;CYRILLIC SMALL LETTER BLENDED YUS;Ll;0;L;;;;;N;;;A65A;;A65A A65C;CYRILLIC CAPITAL LETTER IOTIFIED CLOSED LITTLE YUS;Lu;0;L;;;;;N;;;;A65D; A65D;CYRILLIC SMALL LETTER IOTIFIED CLOSED LITTLE YUS;Ll;0;L;;;;;N;;;A65C;;A65C A65E;CYRILLIC CAPITAL LETTER YN;Lu;0;L;;;;;N;;;;A65F; A65F;CYRILLIC SMALL LETTER YN;Ll;0;L;;;;;N;;;A65E;;A65E A660;CYRILLIC CAPITAL LETTER REVERSED TSE;Lu;0;L;;;;;N;;;;A661; A661;CYRILLIC SMALL LETTER REVERSED TSE;Ll;0;L;;;;;N;;;A660;;A660 A662;CYRILLIC CAPITAL LETTER SOFT DE;Lu;0;L;;;;;N;;;;A663; A663;CYRILLIC SMALL LETTER SOFT DE;Ll;0;L;;;;;N;;;A662;;A662 A664;CYRILLIC CAPITAL LETTER SOFT EL;Lu;0;L;;;;;N;;;;A665; A665;CYRILLIC SMALL LETTER SOFT EL;Ll;0;L;;;;;N;;;A664;;A664 A666;CYRILLIC CAPITAL LETTER SOFT EM;Lu;0;L;;;;;N;;;;A667; A667;CYRILLIC SMALL LETTER SOFT EM;Ll;0;L;;;;;N;;;A666;;A666 A668;CYRILLIC CAPITAL LETTER MONOCULAR O;Lu;0;L;;;;;N;;;;A669; A669;CYRILLIC SMALL LETTER MONOCULAR O;Ll;0;L;;;;;N;;;A668;;A668 A66A;CYRILLIC CAPITAL LETTER BINOCULAR O;Lu;0;L;;;;;N;;;;A66B; A66B;CYRILLIC SMALL LETTER BINOCULAR O;Ll;0;L;;;;;N;;;A66A;;A66A A66C;CYRILLIC CAPITAL LETTER DOUBLE MONOCULAR O;Lu;0;L;;;;;N;;;;A66D; A66D;CYRILLIC SMALL LETTER DOUBLE MONOCULAR O;Ll;0;L;;;;;N;;;A66C;;A66C A66E;CYRILLIC LETTER MULTIOCULAR O;Lo;0;L;;;;;N;;;;; A66F;COMBINING CYRILLIC VZMET;Mn;230;NSM;;;;;N;;;;; A670;COMBINING CYRILLIC TEN MILLIONS SIGN;Me;0;NSM;;;;;N;;;;; A671;COMBINING CYRILLIC HUNDRED MILLIONS SIGN;Me;0;NSM;;;;;N;;;;; A672;COMBINING CYRILLIC THOUSAND MILLIONS SIGN;Me;0;NSM;;;;;N;;;;; A673;SLAVONIC ASTERISK;Po;0;ON;;;;;N;;;;; A674;COMBINING CYRILLIC LETTER UKRAINIAN IE;Mn;230;NSM;;;;;N;;;;; A675;COMBINING CYRILLIC LETTER I;Mn;230;NSM;;;;;N;;;;; A676;COMBINING CYRILLIC LETTER YI;Mn;230;NSM;;;;;N;;;;; A677;COMBINING CYRILLIC LETTER U;Mn;230;NSM;;;;;N;;;;; A678;COMBINING CYRILLIC LETTER HARD SIGN;Mn;230;NSM;;;;;N;;;;; A679;COMBINING CYRILLIC LETTER YERU;Mn;230;NSM;;;;;N;;;;; A67A;COMBINING CYRILLIC LETTER SOFT SIGN;Mn;230;NSM;;;;;N;;;;; A67B;COMBINING CYRILLIC LETTER OMEGA;Mn;230;NSM;;;;;N;;;;; A67C;COMBINING CYRILLIC KAVYKA;Mn;230;NSM;;;;;N;;;;; A67D;COMBINING CYRILLIC PAYEROK;Mn;230;NSM;;;;;N;;;;; A67E;CYRILLIC KAVYKA;Po;0;ON;;;;;N;;;;; A67F;CYRILLIC PAYEROK;Lm;0;ON;;;;;N;;;;; A680;CYRILLIC CAPITAL LETTER DWE;Lu;0;L;;;;;N;;;;A681; A681;CYRILLIC SMALL LETTER DWE;Ll;0;L;;;;;N;;;A680;;A680 A682;CYRILLIC CAPITAL LETTER DZWE;Lu;0;L;;;;;N;;;;A683; A683;CYRILLIC SMALL LETTER DZWE;Ll;0;L;;;;;N;;;A682;;A682 A684;CYRILLIC CAPITAL LETTER ZHWE;Lu;0;L;;;;;N;;;;A685; A685;CYRILLIC SMALL LETTER ZHWE;Ll;0;L;;;;;N;;;A684;;A684 A686;CYRILLIC CAPITAL LETTER CCHE;Lu;0;L;;;;;N;;;;A687; A687;CYRILLIC SMALL LETTER CCHE;Ll;0;L;;;;;N;;;A686;;A686 A688;CYRILLIC CAPITAL LETTER DZZE;Lu;0;L;;;;;N;;;;A689; A689;CYRILLIC SMALL LETTER DZZE;Ll;0;L;;;;;N;;;A688;;A688 A68A;CYRILLIC CAPITAL LETTER TE WITH MIDDLE HOOK;Lu;0;L;;;;;N;;;;A68B; A68B;CYRILLIC SMALL LETTER TE WITH MIDDLE HOOK;Ll;0;L;;;;;N;;;A68A;;A68A A68C;CYRILLIC CAPITAL LETTER TWE;Lu;0;L;;;;;N;;;;A68D; A68D;CYRILLIC SMALL LETTER TWE;Ll;0;L;;;;;N;;;A68C;;A68C A68E;CYRILLIC CAPITAL LETTER TSWE;Lu;0;L;;;;;N;;;;A68F; A68F;CYRILLIC SMALL LETTER TSWE;Ll;0;L;;;;;N;;;A68E;;A68E A690;CYRILLIC CAPITAL LETTER TSSE;Lu;0;L;;;;;N;;;;A691; A691;CYRILLIC SMALL LETTER TSSE;Ll;0;L;;;;;N;;;A690;;A690 A692;CYRILLIC CAPITAL LETTER TCHE;Lu;0;L;;;;;N;;;;A693; A693;CYRILLIC SMALL LETTER TCHE;Ll;0;L;;;;;N;;;A692;;A692 A694;CYRILLIC CAPITAL LETTER HWE;Lu;0;L;;;;;N;;;;A695; A695;CYRILLIC SMALL LETTER HWE;Ll;0;L;;;;;N;;;A694;;A694 A696;CYRILLIC CAPITAL LETTER SHWE;Lu;0;L;;;;;N;;;;A697; A697;CYRILLIC SMALL LETTER SHWE;Ll;0;L;;;;;N;;;A696;;A696 A698;CYRILLIC CAPITAL LETTER DOUBLE O;Lu;0;L;;;;;N;;;;A699; A699;CYRILLIC SMALL LETTER DOUBLE O;Ll;0;L;;;;;N;;;A698;;A698 A69A;CYRILLIC CAPITAL LETTER CROSSED O;Lu;0;L;;;;;N;;;;A69B; A69B;CYRILLIC SMALL LETTER CROSSED O;Ll;0;L;;;;;N;;;A69A;;A69A A69C;MODIFIER LETTER CYRILLIC HARD SIGN;Lm;0;L; 044A;;;;N;;;;; A69D;MODIFIER LETTER CYRILLIC SOFT SIGN;Lm;0;L; 044C;;;;N;;;;; A69F;COMBINING CYRILLIC LETTER IOTIFIED E;Mn;230;NSM;;;;;N;;;;; A6A0;BAMUM LETTER A;Lo;0;L;;;;;N;;;;; A6A1;BAMUM LETTER KA;Lo;0;L;;;;;N;;;;; A6A2;BAMUM LETTER U;Lo;0;L;;;;;N;;;;; A6A3;BAMUM LETTER KU;Lo;0;L;;;;;N;;;;; A6A4;BAMUM LETTER EE;Lo;0;L;;;;;N;;;;; A6A5;BAMUM LETTER REE;Lo;0;L;;;;;N;;;;; A6A6;BAMUM LETTER TAE;Lo;0;L;;;;;N;;;;; A6A7;BAMUM LETTER O;Lo;0;L;;;;;N;;;;; A6A8;BAMUM LETTER NYI;Lo;0;L;;;;;N;;;;; A6A9;BAMUM LETTER I;Lo;0;L;;;;;N;;;;; A6AA;BAMUM LETTER LA;Lo;0;L;;;;;N;;;;; A6AB;BAMUM LETTER PA;Lo;0;L;;;;;N;;;;; A6AC;BAMUM LETTER RII;Lo;0;L;;;;;N;;;;; A6AD;BAMUM LETTER RIEE;Lo;0;L;;;;;N;;;;; A6AE;BAMUM LETTER LEEEE;Lo;0;L;;;;;N;;;;; A6AF;BAMUM LETTER MEEEE;Lo;0;L;;;;;N;;;;; A6B0;BAMUM LETTER TAA;Lo;0;L;;;;;N;;;;; A6B1;BAMUM LETTER NDAA;Lo;0;L;;;;;N;;;;; A6B2;BAMUM LETTER NJAEM;Lo;0;L;;;;;N;;;;; A6B3;BAMUM LETTER M;Lo;0;L;;;;;N;;;;; A6B4;BAMUM LETTER SUU;Lo;0;L;;;;;N;;;;; A6B5;BAMUM LETTER MU;Lo;0;L;;;;;N;;;;; A6B6;BAMUM LETTER SHII;Lo;0;L;;;;;N;;;;; A6B7;BAMUM LETTER SI;Lo;0;L;;;;;N;;;;; A6B8;BAMUM LETTER SHEUX;Lo;0;L;;;;;N;;;;; A6B9;BAMUM LETTER SEUX;Lo;0;L;;;;;N;;;;; A6BA;BAMUM LETTER KYEE;Lo;0;L;;;;;N;;;;; A6BB;BAMUM LETTER KET;Lo;0;L;;;;;N;;;;; A6BC;BAMUM LETTER NUAE;Lo;0;L;;;;;N;;;;; A6BD;BAMUM LETTER NU;Lo;0;L;;;;;N;;;;; A6BE;BAMUM LETTER NJUAE;Lo;0;L;;;;;N;;;;; A6BF;BAMUM LETTER YOQ;Lo;0;L;;;;;N;;;;; A6C0;BAMUM LETTER SHU;Lo;0;L;;;;;N;;;;; A6C1;BAMUM LETTER YUQ;Lo;0;L;;;;;N;;;;; A6C2;BAMUM LETTER YA;Lo;0;L;;;;;N;;;;; A6C3;BAMUM LETTER NSHA;Lo;0;L;;;;;N;;;;; A6C4;BAMUM LETTER KEUX;Lo;0;L;;;;;N;;;;; A6C5;BAMUM LETTER PEUX;Lo;0;L;;;;;N;;;;; A6C6;BAMUM LETTER NJEE;Lo;0;L;;;;;N;;;;; A6C7;BAMUM LETTER NTEE;Lo;0;L;;;;;N;;;;; A6C8;BAMUM LETTER PUE;Lo;0;L;;;;;N;;;;; A6C9;BAMUM LETTER WUE;Lo;0;L;;;;;N;;;;; A6CA;BAMUM LETTER PEE;Lo;0;L;;;;;N;;;;; A6CB;BAMUM LETTER FEE;Lo;0;L;;;;;N;;;;; A6CC;BAMUM LETTER RU;Lo;0;L;;;;;N;;;;; A6CD;BAMUM LETTER LU;Lo;0;L;;;;;N;;;;; A6CE;BAMUM LETTER MI;Lo;0;L;;;;;N;;;;; A6CF;BAMUM LETTER NI;Lo;0;L;;;;;N;;;;; A6D0;BAMUM LETTER REUX;Lo;0;L;;;;;N;;;;; A6D1;BAMUM LETTER RAE;Lo;0;L;;;;;N;;;;; A6D2;BAMUM LETTER KEN;Lo;0;L;;;;;N;;;;; A6D3;BAMUM LETTER NGKWAEN;Lo;0;L;;;;;N;;;;; A6D4;BAMUM LETTER NGGA;Lo;0;L;;;;;N;;;;; A6D5;BAMUM LETTER NGA;Lo;0;L;;;;;N;;;;; A6D6;BAMUM LETTER SHO;Lo;0;L;;;;;N;;;;; A6D7;BAMUM LETTER PUAE;Lo;0;L;;;;;N;;;;; A6D8;BAMUM LETTER FU;Lo;0;L;;;;;N;;;;; A6D9;BAMUM LETTER FOM;Lo;0;L;;;;;N;;;;; A6DA;BAMUM LETTER WA;Lo;0;L;;;;;N;;;;; A6DB;BAMUM LETTER NA;Lo;0;L;;;;;N;;;;; A6DC;BAMUM LETTER LI;Lo;0;L;;;;;N;;;;; A6DD;BAMUM LETTER PI;Lo;0;L;;;;;N;;;;; A6DE;BAMUM LETTER LOQ;Lo;0;L;;;;;N;;;;; A6DF;BAMUM LETTER KO;Lo;0;L;;;;;N;;;;; A6E0;BAMUM LETTER MBEN;Lo;0;L;;;;;N;;;;; A6E1;BAMUM LETTER REN;Lo;0;L;;;;;N;;;;; A6E2;BAMUM LETTER MEN;Lo;0;L;;;;;N;;;;; A6E3;BAMUM LETTER MA;Lo;0;L;;;;;N;;;;; A6E4;BAMUM LETTER TI;Lo;0;L;;;;;N;;;;; A6E5;BAMUM LETTER KI;Lo;0;L;;;;;N;;;;; A6E6;BAMUM LETTER MO;Nl;0;L;;;;1;N;;;;; A6E7;BAMUM LETTER MBAA;Nl;0;L;;;;2;N;;;;; A6E8;BAMUM LETTER TET;Nl;0;L;;;;3;N;;;;; A6E9;BAMUM LETTER KPA;Nl;0;L;;;;4;N;;;;; A6EA;BAMUM LETTER TEN;Nl;0;L;;;;5;N;;;;; A6EB;BAMUM LETTER NTUU;Nl;0;L;;;;6;N;;;;; A6EC;BAMUM LETTER SAMBA;Nl;0;L;;;;7;N;;;;; A6ED;BAMUM LETTER FAAMAE;Nl;0;L;;;;8;N;;;;; A6EE;BAMUM LETTER KOVUU;Nl;0;L;;;;9;N;;;;; A6EF;BAMUM LETTER KOGHOM;Nl;0;L;;;;0;N;;;;; A6F0;BAMUM COMBINING MARK KOQNDON;Mn;230;NSM;;;;;N;;;;; A6F1;BAMUM COMBINING MARK TUKWENTIS;Mn;230;NSM;;;;;N;;;;; A6F2;BAMUM NJAEMLI;Po;0;L;;;;;N;;;;; A6F3;BAMUM FULL STOP;Po;0;L;;;;;N;;;;; A6F4;BAMUM COLON;Po;0;L;;;;;N;;;;; A6F5;BAMUM COMMA;Po;0;L;;;;;N;;;;; A6F6;BAMUM SEMICOLON;Po;0;L;;;;;N;;;;; A6F7;BAMUM QUESTION MARK;Po;0;L;;;;;N;;;;; A700;MODIFIER LETTER CHINESE TONE YIN PING;Sk;0;ON;;;;;N;;;;; A701;MODIFIER LETTER CHINESE TONE YANG PING;Sk;0;ON;;;;;N;;;;; A702;MODIFIER LETTER CHINESE TONE YIN SHANG;Sk;0;ON;;;;;N;;;;; A703;MODIFIER LETTER CHINESE TONE YANG SHANG;Sk;0;ON;;;;;N;;;;; A704;MODIFIER LETTER CHINESE TONE YIN QU;Sk;0;ON;;;;;N;;;;; A705;MODIFIER LETTER CHINESE TONE YANG QU;Sk;0;ON;;;;;N;;;;; A706;MODIFIER LETTER CHINESE TONE YIN RU;Sk;0;ON;;;;;N;;;;; A707;MODIFIER LETTER CHINESE TONE YANG RU;Sk;0;ON;;;;;N;;;;; A708;MODIFIER LETTER EXTRA-HIGH DOTTED TONE BAR;Sk;0;ON;;;;;N;;;;; A709;MODIFIER LETTER HIGH DOTTED TONE BAR;Sk;0;ON;;;;;N;;;;; A70A;MODIFIER LETTER MID DOTTED TONE BAR;Sk;0;ON;;;;;N;;;;; A70B;MODIFIER LETTER LOW DOTTED TONE BAR;Sk;0;ON;;;;;N;;;;; A70C;MODIFIER LETTER EXTRA-LOW DOTTED TONE BAR;Sk;0;ON;;;;;N;;;;; A70D;MODIFIER LETTER EXTRA-HIGH DOTTED LEFT-STEM TONE BAR;Sk;0;ON;;;;;N;;;;; A70E;MODIFIER LETTER HIGH DOTTED LEFT-STEM TONE BAR;Sk;0;ON;;;;;N;;;;; A70F;MODIFIER LETTER MID DOTTED LEFT-STEM TONE BAR;Sk;0;ON;;;;;N;;;;; A710;MODIFIER LETTER LOW DOTTED LEFT-STEM TONE BAR;Sk;0;ON;;;;;N;;;;; A711;MODIFIER LETTER EXTRA-LOW DOTTED LEFT-STEM TONE BAR;Sk;0;ON;;;;;N;;;;; A712;MODIFIER LETTER EXTRA-HIGH LEFT-STEM TONE BAR;Sk;0;ON;;;;;N;;;;; A713;MODIFIER LETTER HIGH LEFT-STEM TONE BAR;Sk;0;ON;;;;;N;;;;; A714;MODIFIER LETTER MID LEFT-STEM TONE BAR;Sk;0;ON;;;;;N;;;;; A715;MODIFIER LETTER LOW LEFT-STEM TONE BAR;Sk;0;ON;;;;;N;;;;; A716;MODIFIER LETTER EXTRA-LOW LEFT-STEM TONE BAR;Sk;0;ON;;;;;N;;;;; A717;MODIFIER LETTER DOT VERTICAL BAR;Lm;0;ON;;;;;N;;;;; A718;MODIFIER LETTER DOT SLASH;Lm;0;ON;;;;;N;;;;; A719;MODIFIER LETTER DOT HORIZONTAL BAR;Lm;0;ON;;;;;N;;;;; A71A;MODIFIER LETTER LOWER RIGHT CORNER ANGLE;Lm;0;ON;;;;;N;;;;; A71B;MODIFIER LETTER RAISED UP ARROW;Lm;0;ON;;;;;N;;;;; A71C;MODIFIER LETTER RAISED DOWN ARROW;Lm;0;ON;;;;;N;;;;; A71D;MODIFIER LETTER RAISED EXCLAMATION MARK;Lm;0;ON;;;;;N;;;;; A71E;MODIFIER LETTER RAISED INVERTED EXCLAMATION MARK;Lm;0;ON;;;;;N;;;;; A71F;MODIFIER LETTER LOW INVERTED EXCLAMATION MARK;Lm;0;ON;;;;;N;;;;; A720;MODIFIER LETTER STRESS AND HIGH TONE;Sk;0;ON;;;;;N;;;;; A721;MODIFIER LETTER STRESS AND LOW TONE;Sk;0;ON;;;;;N;;;;; A722;LATIN CAPITAL LETTER EGYPTOLOGICAL ALEF;Lu;0;L;;;;;N;;;;A723; A723;LATIN SMALL LETTER EGYPTOLOGICAL ALEF;Ll;0;L;;;;;N;;;A722;;A722 A724;LATIN CAPITAL LETTER EGYPTOLOGICAL AIN;Lu;0;L;;;;;N;;;;A725; A725;LATIN SMALL LETTER EGYPTOLOGICAL AIN;Ll;0;L;;;;;N;;;A724;;A724 A726;LATIN CAPITAL LETTER HENG;Lu;0;L;;;;;N;;;;A727; A727;LATIN SMALL LETTER HENG;Ll;0;L;;;;;N;;;A726;;A726 A728;LATIN CAPITAL LETTER TZ;Lu;0;L;;;;;N;;;;A729; A729;LATIN SMALL LETTER TZ;Ll;0;L;;;;;N;;;A728;;A728 A72A;LATIN CAPITAL LETTER TRESILLO;Lu;0;L;;;;;N;;;;A72B; A72B;LATIN SMALL LETTER TRESILLO;Ll;0;L;;;;;N;;;A72A;;A72A A72C;LATIN CAPITAL LETTER CUATRILLO;Lu;0;L;;;;;N;;;;A72D; A72D;LATIN SMALL LETTER CUATRILLO;Ll;0;L;;;;;N;;;A72C;;A72C A72E;LATIN CAPITAL LETTER CUATRILLO WITH COMMA;Lu;0;L;;;;;N;;;;A72F; A72F;LATIN SMALL LETTER CUATRILLO WITH COMMA;Ll;0;L;;;;;N;;;A72E;;A72E A730;LATIN LETTER SMALL CAPITAL F;Ll;0;L;;;;;N;;;;; A731;LATIN LETTER SMALL CAPITAL S;Ll;0;L;;;;;N;;;;; A732;LATIN CAPITAL LETTER AA;Lu;0;L;;;;;N;;;;A733; A733;LATIN SMALL LETTER AA;Ll;0;L;;;;;N;;;A732;;A732 A734;LATIN CAPITAL LETTER AO;Lu;0;L;;;;;N;;;;A735; A735;LATIN SMALL LETTER AO;Ll;0;L;;;;;N;;;A734;;A734 A736;LATIN CAPITAL LETTER AU;Lu;0;L;;;;;N;;;;A737; A737;LATIN SMALL LETTER AU;Ll;0;L;;;;;N;;;A736;;A736 A738;LATIN CAPITAL LETTER AV;Lu;0;L;;;;;N;;;;A739; A739;LATIN SMALL LETTER AV;Ll;0;L;;;;;N;;;A738;;A738 A73A;LATIN CAPITAL LETTER AV WITH HORIZONTAL BAR;Lu;0;L;;;;;N;;;;A73B; A73B;LATIN SMALL LETTER AV WITH HORIZONTAL BAR;Ll;0;L;;;;;N;;;A73A;;A73A A73C;LATIN CAPITAL LETTER AY;Lu;0;L;;;;;N;;;;A73D; A73D;LATIN SMALL LETTER AY;Ll;0;L;;;;;N;;;A73C;;A73C A73E;LATIN CAPITAL LETTER REVERSED C WITH DOT;Lu;0;L;;;;;N;;;;A73F; A73F;LATIN SMALL LETTER REVERSED C WITH DOT;Ll;0;L;;;;;N;;;A73E;;A73E A740;LATIN CAPITAL LETTER K WITH STROKE;Lu;0;L;;;;;N;;;;A741; A741;LATIN SMALL LETTER K WITH STROKE;Ll;0;L;;;;;N;;;A740;;A740 A742;LATIN CAPITAL LETTER K WITH DIAGONAL STROKE;Lu;0;L;;;;;N;;;;A743; A743;LATIN SMALL LETTER K WITH DIAGONAL STROKE;Ll;0;L;;;;;N;;;A742;;A742 A744;LATIN CAPITAL LETTER K WITH STROKE AND DIAGONAL STROKE;Lu;0;L;;;;;N;;;;A745; A745;LATIN SMALL LETTER K WITH STROKE AND DIAGONAL STROKE;Ll;0;L;;;;;N;;;A744;;A744 A746;LATIN CAPITAL LETTER BROKEN L;Lu;0;L;;;;;N;;;;A747; A747;LATIN SMALL LETTER BROKEN L;Ll;0;L;;;;;N;;;A746;;A746 A748;LATIN CAPITAL LETTER L WITH HIGH STROKE;Lu;0;L;;;;;N;;;;A749; A749;LATIN SMALL LETTER L WITH HIGH STROKE;Ll;0;L;;;;;N;;;A748;;A748 A74A;LATIN CAPITAL LETTER O WITH LONG STROKE OVERLAY;Lu;0;L;;;;;N;;;;A74B; A74B;LATIN SMALL LETTER O WITH LONG STROKE OVERLAY;Ll;0;L;;;;;N;;;A74A;;A74A A74C;LATIN CAPITAL LETTER O WITH LOOP;Lu;0;L;;;;;N;;;;A74D; A74D;LATIN SMALL LETTER O WITH LOOP;Ll;0;L;;;;;N;;;A74C;;A74C A74E;LATIN CAPITAL LETTER OO;Lu;0;L;;;;;N;;;;A74F; A74F;LATIN SMALL LETTER OO;Ll;0;L;;;;;N;;;A74E;;A74E A750;LATIN CAPITAL LETTER P WITH STROKE THROUGH DESCENDER;Lu;0;L;;;;;N;;;;A751; A751;LATIN SMALL LETTER P WITH STROKE THROUGH DESCENDER;Ll;0;L;;;;;N;;;A750;;A750 A752;LATIN CAPITAL LETTER P WITH FLOURISH;Lu;0;L;;;;;N;;;;A753; A753;LATIN SMALL LETTER P WITH FLOURISH;Ll;0;L;;;;;N;;;A752;;A752 A754;LATIN CAPITAL LETTER P WITH SQUIRREL TAIL;Lu;0;L;;;;;N;;;;A755; A755;LATIN SMALL LETTER P WITH SQUIRREL TAIL;Ll;0;L;;;;;N;;;A754;;A754 A756;LATIN CAPITAL LETTER Q WITH STROKE THROUGH DESCENDER;Lu;0;L;;;;;N;;;;A757; A757;LATIN SMALL LETTER Q WITH STROKE THROUGH DESCENDER;Ll;0;L;;;;;N;;;A756;;A756 A758;LATIN CAPITAL LETTER Q WITH DIAGONAL STROKE;Lu;0;L;;;;;N;;;;A759; A759;LATIN SMALL LETTER Q WITH DIAGONAL STROKE;Ll;0;L;;;;;N;;;A758;;A758 A75A;LATIN CAPITAL LETTER R ROTUNDA;Lu;0;L;;;;;N;;;;A75B; A75B;LATIN SMALL LETTER R ROTUNDA;Ll;0;L;;;;;N;;;A75A;;A75A A75C;LATIN CAPITAL LETTER RUM ROTUNDA;Lu;0;L;;;;;N;;;;A75D; A75D;LATIN SMALL LETTER RUM ROTUNDA;Ll;0;L;;;;;N;;;A75C;;A75C A75E;LATIN CAPITAL LETTER V WITH DIAGONAL STROKE;Lu;0;L;;;;;N;;;;A75F; A75F;LATIN SMALL LETTER V WITH DIAGONAL STROKE;Ll;0;L;;;;;N;;;A75E;;A75E A760;LATIN CAPITAL LETTER VY;Lu;0;L;;;;;N;;;;A761; A761;LATIN SMALL LETTER VY;Ll;0;L;;;;;N;;;A760;;A760 A762;LATIN CAPITAL LETTER VISIGOTHIC Z;Lu;0;L;;;;;N;;;;A763; A763;LATIN SMALL LETTER VISIGOTHIC Z;Ll;0;L;;;;;N;;;A762;;A762 A764;LATIN CAPITAL LETTER THORN WITH STROKE;Lu;0;L;;;;;N;;;;A765; A765;LATIN SMALL LETTER THORN WITH STROKE;Ll;0;L;;;;;N;;;A764;;A764 A766;LATIN CAPITAL LETTER THORN WITH STROKE THROUGH DESCENDER;Lu;0;L;;;;;N;;;;A767; A767;LATIN SMALL LETTER THORN WITH STROKE THROUGH DESCENDER;Ll;0;L;;;;;N;;;A766;;A766 A768;LATIN CAPITAL LETTER VEND;Lu;0;L;;;;;N;;;;A769; A769;LATIN SMALL LETTER VEND;Ll;0;L;;;;;N;;;A768;;A768 A76A;LATIN CAPITAL LETTER ET;Lu;0;L;;;;;N;;;;A76B; A76B;LATIN SMALL LETTER ET;Ll;0;L;;;;;N;;;A76A;;A76A A76C;LATIN CAPITAL LETTER IS;Lu;0;L;;;;;N;;;;A76D; A76D;LATIN SMALL LETTER IS;Ll;0;L;;;;;N;;;A76C;;A76C A76E;LATIN CAPITAL LETTER CON;Lu;0;L;;;;;N;;;;A76F; A76F;LATIN SMALL LETTER CON;Ll;0;L;;;;;N;;;A76E;;A76E A770;MODIFIER LETTER US;Lm;0;L; A76F;;;;N;;;;; A771;LATIN SMALL LETTER DUM;Ll;0;L;;;;;N;;;;; A772;LATIN SMALL LETTER LUM;Ll;0;L;;;;;N;;;;; A773;LATIN SMALL LETTER MUM;Ll;0;L;;;;;N;;;;; A774;LATIN SMALL LETTER NUM;Ll;0;L;;;;;N;;;;; A775;LATIN SMALL LETTER RUM;Ll;0;L;;;;;N;;;;; A776;LATIN LETTER SMALL CAPITAL RUM;Ll;0;L;;;;;N;;;;; A777;LATIN SMALL LETTER TUM;Ll;0;L;;;;;N;;;;; A778;LATIN SMALL LETTER UM;Ll;0;L;;;;;N;;;;; A779;LATIN CAPITAL LETTER INSULAR D;Lu;0;L;;;;;N;;;;A77A; A77A;LATIN SMALL LETTER INSULAR D;Ll;0;L;;;;;N;;;A779;;A779 A77B;LATIN CAPITAL LETTER INSULAR F;Lu;0;L;;;;;N;;;;A77C; A77C;LATIN SMALL LETTER INSULAR F;Ll;0;L;;;;;N;;;A77B;;A77B A77D;LATIN CAPITAL LETTER INSULAR G;Lu;0;L;;;;;N;;;;1D79; A77E;LATIN CAPITAL LETTER TURNED INSULAR G;Lu;0;L;;;;;N;;;;A77F; A77F;LATIN SMALL LETTER TURNED INSULAR G;Ll;0;L;;;;;N;;;A77E;;A77E A780;LATIN CAPITAL LETTER TURNED L;Lu;0;L;;;;;N;;;;A781; A781;LATIN SMALL LETTER TURNED L;Ll;0;L;;;;;N;;;A780;;A780 A782;LATIN CAPITAL LETTER INSULAR R;Lu;0;L;;;;;N;;;;A783; A783;LATIN SMALL LETTER INSULAR R;Ll;0;L;;;;;N;;;A782;;A782 A784;LATIN CAPITAL LETTER INSULAR S;Lu;0;L;;;;;N;;;;A785; A785;LATIN SMALL LETTER INSULAR S;Ll;0;L;;;;;N;;;A784;;A784 A786;LATIN CAPITAL LETTER INSULAR T;Lu;0;L;;;;;N;;;;A787; A787;LATIN SMALL LETTER INSULAR T;Ll;0;L;;;;;N;;;A786;;A786 A788;MODIFIER LETTER LOW CIRCUMFLEX ACCENT;Lm;0;ON;;;;;N;;;;; A789;MODIFIER LETTER COLON;Sk;0;L;;;;;N;;;;; A78A;MODIFIER LETTER SHORT EQUALS SIGN;Sk;0;L;;;;;N;;;;; A78B;LATIN CAPITAL LETTER SALTILLO;Lu;0;L;;;;;N;;;;A78C; A78C;LATIN SMALL LETTER SALTILLO;Ll;0;L;;;;;N;;;A78B;;A78B A78D;LATIN CAPITAL LETTER TURNED H;Lu;0;L;;;;;N;;;;0265; A78E;LATIN SMALL LETTER L WITH RETROFLEX HOOK AND BELT;Ll;0;L;;;;;N;;;;; A790;LATIN CAPITAL LETTER N WITH DESCENDER;Lu;0;L;;;;;N;;;;A791; A791;LATIN SMALL LETTER N WITH DESCENDER;Ll;0;L;;;;;N;;;A790;;A790 A792;LATIN CAPITAL LETTER C WITH BAR;Lu;0;L;;;;;N;;;;A793; A793;LATIN SMALL LETTER C WITH BAR;Ll;0;L;;;;;N;;;A792;;A792 A794;LATIN SMALL LETTER C WITH PALATAL HOOK;Ll;0;L;;;;;N;;;;; A795;LATIN SMALL LETTER H WITH PALATAL HOOK;Ll;0;L;;;;;N;;;;; A796;LATIN CAPITAL LETTER B WITH FLOURISH;Lu;0;L;;;;;N;;;;A797; A797;LATIN SMALL LETTER B WITH FLOURISH;Ll;0;L;;;;;N;;;A796;;A796 A798;LATIN CAPITAL LETTER F WITH STROKE;Lu;0;L;;;;;N;;;;A799; A799;LATIN SMALL LETTER F WITH STROKE;Ll;0;L;;;;;N;;;A798;;A798 A79A;LATIN CAPITAL LETTER VOLAPUK AE;Lu;0;L;;;;;N;;;;A79B; A79B;LATIN SMALL LETTER VOLAPUK AE;Ll;0;L;;;;;N;;;A79A;;A79A A79C;LATIN CAPITAL LETTER VOLAPUK OE;Lu;0;L;;;;;N;;;;A79D; A79D;LATIN SMALL LETTER VOLAPUK OE;Ll;0;L;;;;;N;;;A79C;;A79C A79E;LATIN CAPITAL LETTER VOLAPUK UE;Lu;0;L;;;;;N;;;;A79F; A79F;LATIN SMALL LETTER VOLAPUK UE;Ll;0;L;;;;;N;;;A79E;;A79E A7A0;LATIN CAPITAL LETTER G WITH OBLIQUE STROKE;Lu;0;L;;;;;N;;;;A7A1; A7A1;LATIN SMALL LETTER G WITH OBLIQUE STROKE;Ll;0;L;;;;;N;;;A7A0;;A7A0 A7A2;LATIN CAPITAL LETTER K WITH OBLIQUE STROKE;Lu;0;L;;;;;N;;;;A7A3; A7A3;LATIN SMALL LETTER K WITH OBLIQUE STROKE;Ll;0;L;;;;;N;;;A7A2;;A7A2 A7A4;LATIN CAPITAL LETTER N WITH OBLIQUE STROKE;Lu;0;L;;;;;N;;;;A7A5; A7A5;LATIN SMALL LETTER N WITH OBLIQUE STROKE;Ll;0;L;;;;;N;;;A7A4;;A7A4 A7A6;LATIN CAPITAL LETTER R WITH OBLIQUE STROKE;Lu;0;L;;;;;N;;;;A7A7; A7A7;LATIN SMALL LETTER R WITH OBLIQUE STROKE;Ll;0;L;;;;;N;;;A7A6;;A7A6 A7A8;LATIN CAPITAL LETTER S WITH OBLIQUE STROKE;Lu;0;L;;;;;N;;;;A7A9; A7A9;LATIN SMALL LETTER S WITH OBLIQUE STROKE;Ll;0;L;;;;;N;;;A7A8;;A7A8 A7AA;LATIN CAPITAL LETTER H WITH HOOK;Lu;0;L;;;;;N;;;;0266; A7AB;LATIN CAPITAL LETTER REVERSED OPEN E;Lu;0;L;;;;;N;;;;025C; A7AC;LATIN CAPITAL LETTER SCRIPT G;Lu;0;L;;;;;N;;;;0261; A7AD;LATIN CAPITAL LETTER L WITH BELT;Lu;0;L;;;;;N;;;;026C; A7B0;LATIN CAPITAL LETTER TURNED K;Lu;0;L;;;;;N;;;;029E; A7B1;LATIN CAPITAL LETTER TURNED T;Lu;0;L;;;;;N;;;;0287; A7F7;LATIN EPIGRAPHIC LETTER SIDEWAYS I;Lo;0;L;;;;;N;;;;; A7F8;MODIFIER LETTER CAPITAL H WITH STROKE;Lm;0;L; 0126;;;;N;;;;; A7F9;MODIFIER LETTER SMALL LIGATURE OE;Lm;0;L; 0153;;;;N;;;;; A7FA;LATIN LETTER SMALL CAPITAL TURNED M;Ll;0;L;;;;;N;;;;; A7FB;LATIN EPIGRAPHIC LETTER REVERSED F;Lo;0;L;;;;;N;;;;; A7FC;LATIN EPIGRAPHIC LETTER REVERSED P;Lo;0;L;;;;;N;;;;; A7FD;LATIN EPIGRAPHIC LETTER INVERTED M;Lo;0;L;;;;;N;;;;; A7FE;LATIN EPIGRAPHIC LETTER I LONGA;Lo;0;L;;;;;N;;;;; A7FF;LATIN EPIGRAPHIC LETTER ARCHAIC M;Lo;0;L;;;;;N;;;;; A800;SYLOTI NAGRI LETTER A;Lo;0;L;;;;;N;;;;; A801;SYLOTI NAGRI LETTER I;Lo;0;L;;;;;N;;;;; A802;SYLOTI NAGRI SIGN DVISVARA;Mn;0;NSM;;;;;N;;;;; A803;SYLOTI NAGRI LETTER U;Lo;0;L;;;;;N;;;;; A804;SYLOTI NAGRI LETTER E;Lo;0;L;;;;;N;;;;; A805;SYLOTI NAGRI LETTER O;Lo;0;L;;;;;N;;;;; A806;SYLOTI NAGRI SIGN HASANTA;Mn;9;NSM;;;;;N;;;;; A807;SYLOTI NAGRI LETTER KO;Lo;0;L;;;;;N;;;;; A808;SYLOTI NAGRI LETTER KHO;Lo;0;L;;;;;N;;;;; A809;SYLOTI NAGRI LETTER GO;Lo;0;L;;;;;N;;;;; A80A;SYLOTI NAGRI LETTER GHO;Lo;0;L;;;;;N;;;;; A80B;SYLOTI NAGRI SIGN ANUSVARA;Mn;0;NSM;;;;;N;;;;; A80C;SYLOTI NAGRI LETTER CO;Lo;0;L;;;;;N;;;;; A80D;SYLOTI NAGRI LETTER CHO;Lo;0;L;;;;;N;;;;; A80E;SYLOTI NAGRI LETTER JO;Lo;0;L;;;;;N;;;;; A80F;SYLOTI NAGRI LETTER JHO;Lo;0;L;;;;;N;;;;; A810;SYLOTI NAGRI LETTER TTO;Lo;0;L;;;;;N;;;;; A811;SYLOTI NAGRI LETTER TTHO;Lo;0;L;;;;;N;;;;; A812;SYLOTI NAGRI LETTER DDO;Lo;0;L;;;;;N;;;;; A813;SYLOTI NAGRI LETTER DDHO;Lo;0;L;;;;;N;;;;; A814;SYLOTI NAGRI LETTER TO;Lo;0;L;;;;;N;;;;; A815;SYLOTI NAGRI LETTER THO;Lo;0;L;;;;;N;;;;; A816;SYLOTI NAGRI LETTER DO;Lo;0;L;;;;;N;;;;; A817;SYLOTI NAGRI LETTER DHO;Lo;0;L;;;;;N;;;;; A818;SYLOTI NAGRI LETTER NO;Lo;0;L;;;;;N;;;;; A819;SYLOTI NAGRI LETTER PO;Lo;0;L;;;;;N;;;;; A81A;SYLOTI NAGRI LETTER PHO;Lo;0;L;;;;;N;;;;; A81B;SYLOTI NAGRI LETTER BO;Lo;0;L;;;;;N;;;;; A81C;SYLOTI NAGRI LETTER BHO;Lo;0;L;;;;;N;;;;; A81D;SYLOTI NAGRI LETTER MO;Lo;0;L;;;;;N;;;;; A81E;SYLOTI NAGRI LETTER RO;Lo;0;L;;;;;N;;;;; A81F;SYLOTI NAGRI LETTER LO;Lo;0;L;;;;;N;;;;; A820;SYLOTI NAGRI LETTER RRO;Lo;0;L;;;;;N;;;;; A821;SYLOTI NAGRI LETTER SO;Lo;0;L;;;;;N;;;;; A822;SYLOTI NAGRI LETTER HO;Lo;0;L;;;;;N;;;;; A823;SYLOTI NAGRI VOWEL SIGN A;Mc;0;L;;;;;N;;;;; A824;SYLOTI NAGRI VOWEL SIGN I;Mc;0;L;;;;;N;;;;; A825;SYLOTI NAGRI VOWEL SIGN U;Mn;0;NSM;;;;;N;;;;; A826;SYLOTI NAGRI VOWEL SIGN E;Mn;0;NSM;;;;;N;;;;; A827;SYLOTI NAGRI VOWEL SIGN OO;Mc;0;L;;;;;N;;;;; A828;SYLOTI NAGRI POETRY MARK-1;So;0;ON;;;;;N;;;;; A829;SYLOTI NAGRI POETRY MARK-2;So;0;ON;;;;;N;;;;; A82A;SYLOTI NAGRI POETRY MARK-3;So;0;ON;;;;;N;;;;; A82B;SYLOTI NAGRI POETRY MARK-4;So;0;ON;;;;;N;;;;; A830;NORTH INDIC FRACTION ONE QUARTER;No;0;L;;;;1/4;N;;;;; A831;NORTH INDIC FRACTION ONE HALF;No;0;L;;;;1/2;N;;;;; A832;NORTH INDIC FRACTION THREE QUARTERS;No;0;L;;;;3/4;N;;;;; A833;NORTH INDIC FRACTION ONE SIXTEENTH;No;0;L;;;;1/16;N;;;;; A834;NORTH INDIC FRACTION ONE EIGHTH;No;0;L;;;;1/8;N;;;;; A835;NORTH INDIC FRACTION THREE SIXTEENTHS;No;0;L;;;;3/16;N;;;;; A836;NORTH INDIC QUARTER MARK;So;0;L;;;;;N;;;;; A837;NORTH INDIC PLACEHOLDER MARK;So;0;L;;;;;N;;;;; A838;NORTH INDIC RUPEE MARK;Sc;0;ET;;;;;N;;;;; A839;NORTH INDIC QUANTITY MARK;So;0;ET;;;;;N;;;;; A840;PHAGS-PA LETTER KA;Lo;0;L;;;;;N;;;;; A841;PHAGS-PA LETTER KHA;Lo;0;L;;;;;N;;;;; A842;PHAGS-PA LETTER GA;Lo;0;L;;;;;N;;;;; A843;PHAGS-PA LETTER NGA;Lo;0;L;;;;;N;;;;; A844;PHAGS-PA LETTER CA;Lo;0;L;;;;;N;;;;; A845;PHAGS-PA LETTER CHA;Lo;0;L;;;;;N;;;;; A846;PHAGS-PA LETTER JA;Lo;0;L;;;;;N;;;;; A847;PHAGS-PA LETTER NYA;Lo;0;L;;;;;N;;;;; A848;PHAGS-PA LETTER TA;Lo;0;L;;;;;N;;;;; A849;PHAGS-PA LETTER THA;Lo;0;L;;;;;N;;;;; A84A;PHAGS-PA LETTER DA;Lo;0;L;;;;;N;;;;; A84B;PHAGS-PA LETTER NA;Lo;0;L;;;;;N;;;;; A84C;PHAGS-PA LETTER PA;Lo;0;L;;;;;N;;;;; A84D;PHAGS-PA LETTER PHA;Lo;0;L;;;;;N;;;;; A84E;PHAGS-PA LETTER BA;Lo;0;L;;;;;N;;;;; A84F;PHAGS-PA LETTER MA;Lo;0;L;;;;;N;;;;; A850;PHAGS-PA LETTER TSA;Lo;0;L;;;;;N;;;;; A851;PHAGS-PA LETTER TSHA;Lo;0;L;;;;;N;;;;; A852;PHAGS-PA LETTER DZA;Lo;0;L;;;;;N;;;;; A853;PHAGS-PA LETTER WA;Lo;0;L;;;;;N;;;;; A854;PHAGS-PA LETTER ZHA;Lo;0;L;;;;;N;;;;; A855;PHAGS-PA LETTER ZA;Lo;0;L;;;;;N;;;;; A856;PHAGS-PA LETTER SMALL A;Lo;0;L;;;;;N;;;;; A857;PHAGS-PA LETTER YA;Lo;0;L;;;;;N;;;;; A858;PHAGS-PA LETTER RA;Lo;0;L;;;;;N;;;;; A859;PHAGS-PA LETTER LA;Lo;0;L;;;;;N;;;;; A85A;PHAGS-PA LETTER SHA;Lo;0;L;;;;;N;;;;; A85B;PHAGS-PA LETTER SA;Lo;0;L;;;;;N;;;;; A85C;PHAGS-PA LETTER HA;Lo;0;L;;;;;N;;;;; A85D;PHAGS-PA LETTER A;Lo;0;L;;;;;N;;;;; A85E;PHAGS-PA LETTER I;Lo;0;L;;;;;N;;;;; A85F;PHAGS-PA LETTER U;Lo;0;L;;;;;N;;;;; A860;PHAGS-PA LETTER E;Lo;0;L;;;;;N;;;;; A861;PHAGS-PA LETTER O;Lo;0;L;;;;;N;;;;; A862;PHAGS-PA LETTER QA;Lo;0;L;;;;;N;;;;; A863;PHAGS-PA LETTER XA;Lo;0;L;;;;;N;;;;; A864;PHAGS-PA LETTER FA;Lo;0;L;;;;;N;;;;; A865;PHAGS-PA LETTER GGA;Lo;0;L;;;;;N;;;;; A866;PHAGS-PA LETTER EE;Lo;0;L;;;;;N;;;;; A867;PHAGS-PA SUBJOINED LETTER WA;Lo;0;L;;;;;N;;;;; A868;PHAGS-PA SUBJOINED LETTER YA;Lo;0;L;;;;;N;;;;; A869;PHAGS-PA LETTER TTA;Lo;0;L;;;;;N;;;;; A86A;PHAGS-PA LETTER TTHA;Lo;0;L;;;;;N;;;;; A86B;PHAGS-PA LETTER DDA;Lo;0;L;;;;;N;;;;; A86C;PHAGS-PA LETTER NNA;Lo;0;L;;;;;N;;;;; A86D;PHAGS-PA LETTER ALTERNATE YA;Lo;0;L;;;;;N;;;;; A86E;PHAGS-PA LETTER VOICELESS SHA;Lo;0;L;;;;;N;;;;; A86F;PHAGS-PA LETTER VOICED HA;Lo;0;L;;;;;N;;;;; A870;PHAGS-PA LETTER ASPIRATED FA;Lo;0;L;;;;;N;;;;; A871;PHAGS-PA SUBJOINED LETTER RA;Lo;0;L;;;;;N;;;;; A872;PHAGS-PA SUPERFIXED LETTER RA;Lo;0;L;;;;;N;;;;; A873;PHAGS-PA LETTER CANDRABINDU;Lo;0;L;;;;;N;;;;; A874;PHAGS-PA SINGLE HEAD MARK;Po;0;ON;;;;;N;;;;; A875;PHAGS-PA DOUBLE HEAD MARK;Po;0;ON;;;;;N;;;;; A876;PHAGS-PA MARK SHAD;Po;0;ON;;;;;N;;;;; A877;PHAGS-PA MARK DOUBLE SHAD;Po;0;ON;;;;;N;;;;; A880;SAURASHTRA SIGN ANUSVARA;Mc;0;L;;;;;N;;;;; A881;SAURASHTRA SIGN VISARGA;Mc;0;L;;;;;N;;;;; A882;SAURASHTRA LETTER A;Lo;0;L;;;;;N;;;;; A883;SAURASHTRA LETTER AA;Lo;0;L;;;;;N;;;;; A884;SAURASHTRA LETTER I;Lo;0;L;;;;;N;;;;; A885;SAURASHTRA LETTER II;Lo;0;L;;;;;N;;;;; A886;SAURASHTRA LETTER U;Lo;0;L;;;;;N;;;;; A887;SAURASHTRA LETTER UU;Lo;0;L;;;;;N;;;;; A888;SAURASHTRA LETTER VOCALIC R;Lo;0;L;;;;;N;;;;; A889;SAURASHTRA LETTER VOCALIC RR;Lo;0;L;;;;;N;;;;; A88A;SAURASHTRA LETTER VOCALIC L;Lo;0;L;;;;;N;;;;; A88B;SAURASHTRA LETTER VOCALIC LL;Lo;0;L;;;;;N;;;;; A88C;SAURASHTRA LETTER E;Lo;0;L;;;;;N;;;;; A88D;SAURASHTRA LETTER EE;Lo;0;L;;;;;N;;;;; A88E;SAURASHTRA LETTER AI;Lo;0;L;;;;;N;;;;; A88F;SAURASHTRA LETTER O;Lo;0;L;;;;;N;;;;; A890;SAURASHTRA LETTER OO;Lo;0;L;;;;;N;;;;; A891;SAURASHTRA LETTER AU;Lo;0;L;;;;;N;;;;; A892;SAURASHTRA LETTER KA;Lo;0;L;;;;;N;;;;; A893;SAURASHTRA LETTER KHA;Lo;0;L;;;;;N;;;;; A894;SAURASHTRA LETTER GA;Lo;0;L;;;;;N;;;;; A895;SAURASHTRA LETTER GHA;Lo;0;L;;;;;N;;;;; A896;SAURASHTRA LETTER NGA;Lo;0;L;;;;;N;;;;; A897;SAURASHTRA LETTER CA;Lo;0;L;;;;;N;;;;; A898;SAURASHTRA LETTER CHA;Lo;0;L;;;;;N;;;;; A899;SAURASHTRA LETTER JA;Lo;0;L;;;;;N;;;;; A89A;SAURASHTRA LETTER JHA;Lo;0;L;;;;;N;;;;; A89B;SAURASHTRA LETTER NYA;Lo;0;L;;;;;N;;;;; A89C;SAURASHTRA LETTER TTA;Lo;0;L;;;;;N;;;;; A89D;SAURASHTRA LETTER TTHA;Lo;0;L;;;;;N;;;;; A89E;SAURASHTRA LETTER DDA;Lo;0;L;;;;;N;;;;; A89F;SAURASHTRA LETTER DDHA;Lo;0;L;;;;;N;;;;; A8A0;SAURASHTRA LETTER NNA;Lo;0;L;;;;;N;;;;; A8A1;SAURASHTRA LETTER TA;Lo;0;L;;;;;N;;;;; A8A2;SAURASHTRA LETTER THA;Lo;0;L;;;;;N;;;;; A8A3;SAURASHTRA LETTER DA;Lo;0;L;;;;;N;;;;; A8A4;SAURASHTRA LETTER DHA;Lo;0;L;;;;;N;;;;; A8A5;SAURASHTRA LETTER NA;Lo;0;L;;;;;N;;;;; A8A6;SAURASHTRA LETTER PA;Lo;0;L;;;;;N;;;;; A8A7;SAURASHTRA LETTER PHA;Lo;0;L;;;;;N;;;;; A8A8;SAURASHTRA LETTER BA;Lo;0;L;;;;;N;;;;; A8A9;SAURASHTRA LETTER BHA;Lo;0;L;;;;;N;;;;; A8AA;SAURASHTRA LETTER MA;Lo;0;L;;;;;N;;;;; A8AB;SAURASHTRA LETTER YA;Lo;0;L;;;;;N;;;;; A8AC;SAURASHTRA LETTER RA;Lo;0;L;;;;;N;;;;; A8AD;SAURASHTRA LETTER LA;Lo;0;L;;;;;N;;;;; A8AE;SAURASHTRA LETTER VA;Lo;0;L;;;;;N;;;;; A8AF;SAURASHTRA LETTER SHA;Lo;0;L;;;;;N;;;;; A8B0;SAURASHTRA LETTER SSA;Lo;0;L;;;;;N;;;;; A8B1;SAURASHTRA LETTER SA;Lo;0;L;;;;;N;;;;; A8B2;SAURASHTRA LETTER HA;Lo;0;L;;;;;N;;;;; A8B3;SAURASHTRA LETTER LLA;Lo;0;L;;;;;N;;;;; A8B4;SAURASHTRA CONSONANT SIGN HAARU;Mc;0;L;;;;;N;;;;; A8B5;SAURASHTRA VOWEL SIGN AA;Mc;0;L;;;;;N;;;;; A8B6;SAURASHTRA VOWEL SIGN I;Mc;0;L;;;;;N;;;;; A8B7;SAURASHTRA VOWEL SIGN II;Mc;0;L;;;;;N;;;;; A8B8;SAURASHTRA VOWEL SIGN U;Mc;0;L;;;;;N;;;;; A8B9;SAURASHTRA VOWEL SIGN UU;Mc;0;L;;;;;N;;;;; A8BA;SAURASHTRA VOWEL SIGN VOCALIC R;Mc;0;L;;;;;N;;;;; A8BB;SAURASHTRA VOWEL SIGN VOCALIC RR;Mc;0;L;;;;;N;;;;; A8BC;SAURASHTRA VOWEL SIGN VOCALIC L;Mc;0;L;;;;;N;;;;; A8BD;SAURASHTRA VOWEL SIGN VOCALIC LL;Mc;0;L;;;;;N;;;;; A8BE;SAURASHTRA VOWEL SIGN E;Mc;0;L;;;;;N;;;;; A8BF;SAURASHTRA VOWEL SIGN EE;Mc;0;L;;;;;N;;;;; A8C0;SAURASHTRA VOWEL SIGN AI;Mc;0;L;;;;;N;;;;; A8C1;SAURASHTRA VOWEL SIGN O;Mc;0;L;;;;;N;;;;; A8C2;SAURASHTRA VOWEL SIGN OO;Mc;0;L;;;;;N;;;;; A8C3;SAURASHTRA VOWEL SIGN AU;Mc;0;L;;;;;N;;;;; A8C4;SAURASHTRA SIGN VIRAMA;Mn;9;NSM;;;;;N;;;;; A8CE;SAURASHTRA DANDA;Po;0;L;;;;;N;;;;; A8CF;SAURASHTRA DOUBLE DANDA;Po;0;L;;;;;N;;;;; A8D0;SAURASHTRA DIGIT ZERO;Nd;0;L;;0;0;0;N;;;;; A8D1;SAURASHTRA DIGIT ONE;Nd;0;L;;1;1;1;N;;;;; A8D2;SAURASHTRA DIGIT TWO;Nd;0;L;;2;2;2;N;;;;; A8D3;SAURASHTRA DIGIT THREE;Nd;0;L;;3;3;3;N;;;;; A8D4;SAURASHTRA DIGIT FOUR;Nd;0;L;;4;4;4;N;;;;; A8D5;SAURASHTRA DIGIT FIVE;Nd;0;L;;5;5;5;N;;;;; A8D6;SAURASHTRA DIGIT SIX;Nd;0;L;;6;6;6;N;;;;; A8D7;SAURASHTRA DIGIT SEVEN;Nd;0;L;;7;7;7;N;;;;; A8D8;SAURASHTRA DIGIT EIGHT;Nd;0;L;;8;8;8;N;;;;; A8D9;SAURASHTRA DIGIT NINE;Nd;0;L;;9;9;9;N;;;;; A8E0;COMBINING DEVANAGARI DIGIT ZERO;Mn;230;NSM;;;;;N;;;;; A8E1;COMBINING DEVANAGARI DIGIT ONE;Mn;230;NSM;;;;;N;;;;; A8E2;COMBINING DEVANAGARI DIGIT TWO;Mn;230;NSM;;;;;N;;;;; A8E3;COMBINING DEVANAGARI DIGIT THREE;Mn;230;NSM;;;;;N;;;;; A8E4;COMBINING DEVANAGARI DIGIT FOUR;Mn;230;NSM;;;;;N;;;;; A8E5;COMBINING DEVANAGARI DIGIT FIVE;Mn;230;NSM;;;;;N;;;;; A8E6;COMBINING DEVANAGARI DIGIT SIX;Mn;230;NSM;;;;;N;;;;; A8E7;COMBINING DEVANAGARI DIGIT SEVEN;Mn;230;NSM;;;;;N;;;;; A8E8;COMBINING DEVANAGARI DIGIT EIGHT;Mn;230;NSM;;;;;N;;;;; A8E9;COMBINING DEVANAGARI DIGIT NINE;Mn;230;NSM;;;;;N;;;;; A8EA;COMBINING DEVANAGARI LETTER A;Mn;230;NSM;;;;;N;;;;; A8EB;COMBINING DEVANAGARI LETTER U;Mn;230;NSM;;;;;N;;;;; A8EC;COMBINING DEVANAGARI LETTER KA;Mn;230;NSM;;;;;N;;;;; A8ED;COMBINING DEVANAGARI LETTER NA;Mn;230;NSM;;;;;N;;;;; A8EE;COMBINING DEVANAGARI LETTER PA;Mn;230;NSM;;;;;N;;;;; A8EF;COMBINING DEVANAGARI LETTER RA;Mn;230;NSM;;;;;N;;;;; A8F0;COMBINING DEVANAGARI LETTER VI;Mn;230;NSM;;;;;N;;;;; A8F1;COMBINING DEVANAGARI SIGN AVAGRAHA;Mn;230;NSM;;;;;N;;;;; A8F2;DEVANAGARI SIGN SPACING CANDRABINDU;Lo;0;L;;;;;N;;;;; A8F3;DEVANAGARI SIGN CANDRABINDU VIRAMA;Lo;0;L;;;;;N;;;;; A8F4;DEVANAGARI SIGN DOUBLE CANDRABINDU VIRAMA;Lo;0;L;;;;;N;;;;; A8F5;DEVANAGARI SIGN CANDRABINDU TWO;Lo;0;L;;;;;N;;;;; A8F6;DEVANAGARI SIGN CANDRABINDU THREE;Lo;0;L;;;;;N;;;;; A8F7;DEVANAGARI SIGN CANDRABINDU AVAGRAHA;Lo;0;L;;;;;N;;;;; A8F8;DEVANAGARI SIGN PUSHPIKA;Po;0;L;;;;;N;;;;; A8F9;DEVANAGARI GAP FILLER;Po;0;L;;;;;N;;;;; A8FA;DEVANAGARI CARET;Po;0;L;;;;;N;;;;; A8FB;DEVANAGARI HEADSTROKE;Lo;0;L;;;;;N;;;;; A900;KAYAH LI DIGIT ZERO;Nd;0;L;;0;0;0;N;;;;; A901;KAYAH LI DIGIT ONE;Nd;0;L;;1;1;1;N;;;;; A902;KAYAH LI DIGIT TWO;Nd;0;L;;2;2;2;N;;;;; A903;KAYAH LI DIGIT THREE;Nd;0;L;;3;3;3;N;;;;; A904;KAYAH LI DIGIT FOUR;Nd;0;L;;4;4;4;N;;;;; A905;KAYAH LI DIGIT FIVE;Nd;0;L;;5;5;5;N;;;;; A906;KAYAH LI DIGIT SIX;Nd;0;L;;6;6;6;N;;;;; A907;KAYAH LI DIGIT SEVEN;Nd;0;L;;7;7;7;N;;;;; A908;KAYAH LI DIGIT EIGHT;Nd;0;L;;8;8;8;N;;;;; A909;KAYAH LI DIGIT NINE;Nd;0;L;;9;9;9;N;;;;; A90A;KAYAH LI LETTER KA;Lo;0;L;;;;;N;;;;; A90B;KAYAH LI LETTER KHA;Lo;0;L;;;;;N;;;;; A90C;KAYAH LI LETTER GA;Lo;0;L;;;;;N;;;;; A90D;KAYAH LI LETTER NGA;Lo;0;L;;;;;N;;;;; A90E;KAYAH LI LETTER SA;Lo;0;L;;;;;N;;;;; A90F;KAYAH LI LETTER SHA;Lo;0;L;;;;;N;;;;; A910;KAYAH LI LETTER ZA;Lo;0;L;;;;;N;;;;; A911;KAYAH LI LETTER NYA;Lo;0;L;;;;;N;;;;; A912;KAYAH LI LETTER TA;Lo;0;L;;;;;N;;;;; A913;KAYAH LI LETTER HTA;Lo;0;L;;;;;N;;;;; A914;KAYAH LI LETTER NA;Lo;0;L;;;;;N;;;;; A915;KAYAH LI LETTER PA;Lo;0;L;;;;;N;;;;; A916;KAYAH LI LETTER PHA;Lo;0;L;;;;;N;;;;; A917;KAYAH LI LETTER MA;Lo;0;L;;;;;N;;;;; A918;KAYAH LI LETTER DA;Lo;0;L;;;;;N;;;;; A919;KAYAH LI LETTER BA;Lo;0;L;;;;;N;;;;; A91A;KAYAH LI LETTER RA;Lo;0;L;;;;;N;;;;; A91B;KAYAH LI LETTER YA;Lo;0;L;;;;;N;;;;; A91C;KAYAH LI LETTER LA;Lo;0;L;;;;;N;;;;; A91D;KAYAH LI LETTER WA;Lo;0;L;;;;;N;;;;; A91E;KAYAH LI LETTER THA;Lo;0;L;;;;;N;;;;; A91F;KAYAH LI LETTER HA;Lo;0;L;;;;;N;;;;; A920;KAYAH LI LETTER VA;Lo;0;L;;;;;N;;;;; A921;KAYAH LI LETTER CA;Lo;0;L;;;;;N;;;;; A922;KAYAH LI LETTER A;Lo;0;L;;;;;N;;;;; A923;KAYAH LI LETTER OE;Lo;0;L;;;;;N;;;;; A924;KAYAH LI LETTER I;Lo;0;L;;;;;N;;;;; A925;KAYAH LI LETTER OO;Lo;0;L;;;;;N;;;;; A926;KAYAH LI VOWEL UE;Mn;0;NSM;;;;;N;;;;; A927;KAYAH LI VOWEL E;Mn;0;NSM;;;;;N;;;;; A928;KAYAH LI VOWEL U;Mn;0;NSM;;;;;N;;;;; A929;KAYAH LI VOWEL EE;Mn;0;NSM;;;;;N;;;;; A92A;KAYAH LI VOWEL O;Mn;0;NSM;;;;;N;;;;; A92B;KAYAH LI TONE PLOPHU;Mn;220;NSM;;;;;N;;;;; A92C;KAYAH LI TONE CALYA;Mn;220;NSM;;;;;N;;;;; A92D;KAYAH LI TONE CALYA PLOPHU;Mn;220;NSM;;;;;N;;;;; A92E;KAYAH LI SIGN CWI;Po;0;L;;;;;N;;;;; A92F;KAYAH LI SIGN SHYA;Po;0;L;;;;;N;;;;; A930;REJANG LETTER KA;Lo;0;L;;;;;N;;;;; A931;REJANG LETTER GA;Lo;0;L;;;;;N;;;;; A932;REJANG LETTER NGA;Lo;0;L;;;;;N;;;;; A933;REJANG LETTER TA;Lo;0;L;;;;;N;;;;; A934;REJANG LETTER DA;Lo;0;L;;;;;N;;;;; A935;REJANG LETTER NA;Lo;0;L;;;;;N;;;;; A936;REJANG LETTER PA;Lo;0;L;;;;;N;;;;; A937;REJANG LETTER BA;Lo;0;L;;;;;N;;;;; A938;REJANG LETTER MA;Lo;0;L;;;;;N;;;;; A939;REJANG LETTER CA;Lo;0;L;;;;;N;;;;; A93A;REJANG LETTER JA;Lo;0;L;;;;;N;;;;; A93B;REJANG LETTER NYA;Lo;0;L;;;;;N;;;;; A93C;REJANG LETTER SA;Lo;0;L;;;;;N;;;;; A93D;REJANG LETTER RA;Lo;0;L;;;;;N;;;;; A93E;REJANG LETTER LA;Lo;0;L;;;;;N;;;;; A93F;REJANG LETTER YA;Lo;0;L;;;;;N;;;;; A940;REJANG LETTER WA;Lo;0;L;;;;;N;;;;; A941;REJANG LETTER HA;Lo;0;L;;;;;N;;;;; A942;REJANG LETTER MBA;Lo;0;L;;;;;N;;;;; A943;REJANG LETTER NGGA;Lo;0;L;;;;;N;;;;; A944;REJANG LETTER NDA;Lo;0;L;;;;;N;;;;; A945;REJANG LETTER NYJA;Lo;0;L;;;;;N;;;;; A946;REJANG LETTER A;Lo;0;L;;;;;N;;;;; A947;REJANG VOWEL SIGN I;Mn;0;NSM;;;;;N;;;;; A948;REJANG VOWEL SIGN U;Mn;0;NSM;;;;;N;;;;; A949;REJANG VOWEL SIGN E;Mn;0;NSM;;;;;N;;;;; A94A;REJANG VOWEL SIGN AI;Mn;0;NSM;;;;;N;;;;; A94B;REJANG VOWEL SIGN O;Mn;0;NSM;;;;;N;;;;; A94C;REJANG VOWEL SIGN AU;Mn;0;NSM;;;;;N;;;;; A94D;REJANG VOWEL SIGN EU;Mn;0;NSM;;;;;N;;;;; A94E;REJANG VOWEL SIGN EA;Mn;0;NSM;;;;;N;;;;; A94F;REJANG CONSONANT SIGN NG;Mn;0;NSM;;;;;N;;;;; A950;REJANG CONSONANT SIGN N;Mn;0;NSM;;;;;N;;;;; A951;REJANG CONSONANT SIGN R;Mn;0;NSM;;;;;N;;;;; A952;REJANG CONSONANT SIGN H;Mc;0;L;;;;;N;;;;; A953;REJANG VIRAMA;Mc;9;L;;;;;N;;;;; A95F;REJANG SECTION MARK;Po;0;L;;;;;N;;;;; A960;HANGUL CHOSEONG TIKEUT-MIEUM;Lo;0;L;;;;;N;;;;; A961;HANGUL CHOSEONG TIKEUT-PIEUP;Lo;0;L;;;;;N;;;;; A962;HANGUL CHOSEONG TIKEUT-SIOS;Lo;0;L;;;;;N;;;;; A963;HANGUL CHOSEONG TIKEUT-CIEUC;Lo;0;L;;;;;N;;;;; A964;HANGUL CHOSEONG RIEUL-KIYEOK;Lo;0;L;;;;;N;;;;; A965;HANGUL CHOSEONG RIEUL-SSANGKIYEOK;Lo;0;L;;;;;N;;;;; A966;HANGUL CHOSEONG RIEUL-TIKEUT;Lo;0;L;;;;;N;;;;; A967;HANGUL CHOSEONG RIEUL-SSANGTIKEUT;Lo;0;L;;;;;N;;;;; A968;HANGUL CHOSEONG RIEUL-MIEUM;Lo;0;L;;;;;N;;;;; A969;HANGUL CHOSEONG RIEUL-PIEUP;Lo;0;L;;;;;N;;;;; A96A;HANGUL CHOSEONG RIEUL-SSANGPIEUP;Lo;0;L;;;;;N;;;;; A96B;HANGUL CHOSEONG RIEUL-KAPYEOUNPIEUP;Lo;0;L;;;;;N;;;;; A96C;HANGUL CHOSEONG RIEUL-SIOS;Lo;0;L;;;;;N;;;;; A96D;HANGUL CHOSEONG RIEUL-CIEUC;Lo;0;L;;;;;N;;;;; A96E;HANGUL CHOSEONG RIEUL-KHIEUKH;Lo;0;L;;;;;N;;;;; A96F;HANGUL CHOSEONG MIEUM-KIYEOK;Lo;0;L;;;;;N;;;;; A970;HANGUL CHOSEONG MIEUM-TIKEUT;Lo;0;L;;;;;N;;;;; A971;HANGUL CHOSEONG MIEUM-SIOS;Lo;0;L;;;;;N;;;;; A972;HANGUL CHOSEONG PIEUP-SIOS-THIEUTH;Lo;0;L;;;;;N;;;;; A973;HANGUL CHOSEONG PIEUP-KHIEUKH;Lo;0;L;;;;;N;;;;; A974;HANGUL CHOSEONG PIEUP-HIEUH;Lo;0;L;;;;;N;;;;; A975;HANGUL CHOSEONG SSANGSIOS-PIEUP;Lo;0;L;;;;;N;;;;; A976;HANGUL CHOSEONG IEUNG-RIEUL;Lo;0;L;;;;;N;;;;; A977;HANGUL CHOSEONG IEUNG-HIEUH;Lo;0;L;;;;;N;;;;; A978;HANGUL CHOSEONG SSANGCIEUC-HIEUH;Lo;0;L;;;;;N;;;;; A979;HANGUL CHOSEONG SSANGTHIEUTH;Lo;0;L;;;;;N;;;;; A97A;HANGUL CHOSEONG PHIEUPH-HIEUH;Lo;0;L;;;;;N;;;;; A97B;HANGUL CHOSEONG HIEUH-SIOS;Lo;0;L;;;;;N;;;;; A97C;HANGUL CHOSEONG SSANGYEORINHIEUH;Lo;0;L;;;;;N;;;;; A980;JAVANESE SIGN PANYANGGA;Mn;0;NSM;;;;;N;;;;; A981;JAVANESE SIGN CECAK;Mn;0;NSM;;;;;N;;;;; A982;JAVANESE SIGN LAYAR;Mn;0;NSM;;;;;N;;;;; A983;JAVANESE SIGN WIGNYAN;Mc;0;L;;;;;N;;;;; A984;JAVANESE LETTER A;Lo;0;L;;;;;N;;;;; A985;JAVANESE LETTER I KAWI;Lo;0;L;;;;;N;;;;; A986;JAVANESE LETTER I;Lo;0;L;;;;;N;;;;; A987;JAVANESE LETTER II;Lo;0;L;;;;;N;;;;; A988;JAVANESE LETTER U;Lo;0;L;;;;;N;;;;; A989;JAVANESE LETTER PA CEREK;Lo;0;L;;;;;N;;;;; A98A;JAVANESE LETTER NGA LELET;Lo;0;L;;;;;N;;;;; A98B;JAVANESE LETTER NGA LELET RASWADI;Lo;0;L;;;;;N;;;;; A98C;JAVANESE LETTER E;Lo;0;L;;;;;N;;;;; A98D;JAVANESE LETTER AI;Lo;0;L;;;;;N;;;;; A98E;JAVANESE LETTER O;Lo;0;L;;;;;N;;;;; A98F;JAVANESE LETTER KA;Lo;0;L;;;;;N;;;;; A990;JAVANESE LETTER KA SASAK;Lo;0;L;;;;;N;;;;; A991;JAVANESE LETTER KA MURDA;Lo;0;L;;;;;N;;;;; A992;JAVANESE LETTER GA;Lo;0;L;;;;;N;;;;; A993;JAVANESE LETTER GA MURDA;Lo;0;L;;;;;N;;;;; A994;JAVANESE LETTER NGA;Lo;0;L;;;;;N;;;;; A995;JAVANESE LETTER CA;Lo;0;L;;;;;N;;;;; A996;JAVANESE LETTER CA MURDA;Lo;0;L;;;;;N;;;;; A997;JAVANESE LETTER JA;Lo;0;L;;;;;N;;;;; A998;JAVANESE LETTER NYA MURDA;Lo;0;L;;;;;N;;;;; A999;JAVANESE LETTER JA MAHAPRANA;Lo;0;L;;;;;N;;;;; A99A;JAVANESE LETTER NYA;Lo;0;L;;;;;N;;;;; A99B;JAVANESE LETTER TTA;Lo;0;L;;;;;N;;;;; A99C;JAVANESE LETTER TTA MAHAPRANA;Lo;0;L;;;;;N;;;;; A99D;JAVANESE LETTER DDA;Lo;0;L;;;;;N;;;;; A99E;JAVANESE LETTER DDA MAHAPRANA;Lo;0;L;;;;;N;;;;; A99F;JAVANESE LETTER NA MURDA;Lo;0;L;;;;;N;;;;; A9A0;JAVANESE LETTER TA;Lo;0;L;;;;;N;;;;; A9A1;JAVANESE LETTER TA MURDA;Lo;0;L;;;;;N;;;;; A9A2;JAVANESE LETTER DA;Lo;0;L;;;;;N;;;;; A9A3;JAVANESE LETTER DA MAHAPRANA;Lo;0;L;;;;;N;;;;; A9A4;JAVANESE LETTER NA;Lo;0;L;;;;;N;;;;; A9A5;JAVANESE LETTER PA;Lo;0;L;;;;;N;;;;; A9A6;JAVANESE LETTER PA MURDA;Lo;0;L;;;;;N;;;;; A9A7;JAVANESE LETTER BA;Lo;0;L;;;;;N;;;;; A9A8;JAVANESE LETTER BA MURDA;Lo;0;L;;;;;N;;;;; A9A9;JAVANESE LETTER MA;Lo;0;L;;;;;N;;;;; A9AA;JAVANESE LETTER YA;Lo;0;L;;;;;N;;;;; A9AB;JAVANESE LETTER RA;Lo;0;L;;;;;N;;;;; A9AC;JAVANESE LETTER RA AGUNG;Lo;0;L;;;;;N;;;;; A9AD;JAVANESE LETTER LA;Lo;0;L;;;;;N;;;;; A9AE;JAVANESE LETTER WA;Lo;0;L;;;;;N;;;;; A9AF;JAVANESE LETTER SA MURDA;Lo;0;L;;;;;N;;;;; A9B0;JAVANESE LETTER SA MAHAPRANA;Lo;0;L;;;;;N;;;;; A9B1;JAVANESE LETTER SA;Lo;0;L;;;;;N;;;;; A9B2;JAVANESE LETTER HA;Lo;0;L;;;;;N;;;;; A9B3;JAVANESE SIGN CECAK TELU;Mn;7;NSM;;;;;N;;;;; A9B4;JAVANESE VOWEL SIGN TARUNG;Mc;0;L;;;;;N;;;;; A9B5;JAVANESE VOWEL SIGN TOLONG;Mc;0;L;;;;;N;;;;; A9B6;JAVANESE VOWEL SIGN WULU;Mn;0;NSM;;;;;N;;;;; A9B7;JAVANESE VOWEL SIGN WULU MELIK;Mn;0;NSM;;;;;N;;;;; A9B8;JAVANESE VOWEL SIGN SUKU;Mn;0;NSM;;;;;N;;;;; A9B9;JAVANESE VOWEL SIGN SUKU MENDUT;Mn;0;NSM;;;;;N;;;;; A9BA;JAVANESE VOWEL SIGN TALING;Mc;0;L;;;;;N;;;;; A9BB;JAVANESE VOWEL SIGN DIRGA MURE;Mc;0;L;;;;;N;;;;; A9BC;JAVANESE VOWEL SIGN PEPET;Mn;0;NSM;;;;;N;;;;; A9BD;JAVANESE CONSONANT SIGN KERET;Mc;0;L;;;;;N;;;;; A9BE;JAVANESE CONSONANT SIGN PENGKAL;Mc;0;L;;;;;N;;;;; A9BF;JAVANESE CONSONANT SIGN CAKRA;Mc;0;L;;;;;N;;;;; A9C0;JAVANESE PANGKON;Mc;9;L;;;;;N;;;;; A9C1;JAVANESE LEFT RERENGGAN;Po;0;L;;;;;N;;;;; A9C2;JAVANESE RIGHT RERENGGAN;Po;0;L;;;;;N;;;;; A9C3;JAVANESE PADA ANDAP;Po;0;L;;;;;N;;;;; A9C4;JAVANESE PADA MADYA;Po;0;L;;;;;N;;;;; A9C5;JAVANESE PADA LUHUR;Po;0;L;;;;;N;;;;; A9C6;JAVANESE PADA WINDU;Po;0;L;;;;;N;;;;; A9C7;JAVANESE PADA PANGKAT;Po;0;L;;;;;N;;;;; A9C8;JAVANESE PADA LINGSA;Po;0;L;;;;;N;;;;; A9C9;JAVANESE PADA LUNGSI;Po;0;L;;;;;N;;;;; A9CA;JAVANESE PADA ADEG;Po;0;L;;;;;N;;;;; A9CB;JAVANESE PADA ADEG ADEG;Po;0;L;;;;;N;;;;; A9CC;JAVANESE PADA PISELEH;Po;0;L;;;;;N;;;;; A9CD;JAVANESE TURNED PADA PISELEH;Po;0;L;;;;;N;;;;; A9CF;JAVANESE PANGRANGKEP;Lm;0;L;;;;;N;;;;; A9D0;JAVANESE DIGIT ZERO;Nd;0;L;;0;0;0;N;;;;; A9D1;JAVANESE DIGIT ONE;Nd;0;L;;1;1;1;N;;;;; A9D2;JAVANESE DIGIT TWO;Nd;0;L;;2;2;2;N;;;;; A9D3;JAVANESE DIGIT THREE;Nd;0;L;;3;3;3;N;;;;; A9D4;JAVANESE DIGIT FOUR;Nd;0;L;;4;4;4;N;;;;; A9D5;JAVANESE DIGIT FIVE;Nd;0;L;;5;5;5;N;;;;; A9D6;JAVANESE DIGIT SIX;Nd;0;L;;6;6;6;N;;;;; A9D7;JAVANESE DIGIT SEVEN;Nd;0;L;;7;7;7;N;;;;; A9D8;JAVANESE DIGIT EIGHT;Nd;0;L;;8;8;8;N;;;;; A9D9;JAVANESE DIGIT NINE;Nd;0;L;;9;9;9;N;;;;; A9DE;JAVANESE PADA TIRTA TUMETES;Po;0;L;;;;;N;;;;; A9DF;JAVANESE PADA ISEN-ISEN;Po;0;L;;;;;N;;;;; A9E0;MYANMAR LETTER SHAN GHA;Lo;0;L;;;;;N;;;;; A9E1;MYANMAR LETTER SHAN CHA;Lo;0;L;;;;;N;;;;; A9E2;MYANMAR LETTER SHAN JHA;Lo;0;L;;;;;N;;;;; A9E3;MYANMAR LETTER SHAN NNA;Lo;0;L;;;;;N;;;;; A9E4;MYANMAR LETTER SHAN BHA;Lo;0;L;;;;;N;;;;; A9E5;MYANMAR SIGN SHAN SAW;Mn;0;NSM;;;;;N;;;;; A9E6;MYANMAR MODIFIER LETTER SHAN REDUPLICATION;Lm;0;L;;;;;N;;;;; A9E7;MYANMAR LETTER TAI LAING NYA;Lo;0;L;;;;;N;;;;; A9E8;MYANMAR LETTER TAI LAING FA;Lo;0;L;;;;;N;;;;; A9E9;MYANMAR LETTER TAI LAING GA;Lo;0;L;;;;;N;;;;; A9EA;MYANMAR LETTER TAI LAING GHA;Lo;0;L;;;;;N;;;;; A9EB;MYANMAR LETTER TAI LAING JA;Lo;0;L;;;;;N;;;;; A9EC;MYANMAR LETTER TAI LAING JHA;Lo;0;L;;;;;N;;;;; A9ED;MYANMAR LETTER TAI LAING DDA;Lo;0;L;;;;;N;;;;; A9EE;MYANMAR LETTER TAI LAING DDHA;Lo;0;L;;;;;N;;;;; A9EF;MYANMAR LETTER TAI LAING NNA;Lo;0;L;;;;;N;;;;; A9F0;MYANMAR TAI LAING DIGIT ZERO;Nd;0;L;;0;0;0;N;;;;; A9F1;MYANMAR TAI LAING DIGIT ONE;Nd;0;L;;1;1;1;N;;;;; A9F2;MYANMAR TAI LAING DIGIT TWO;Nd;0;L;;2;2;2;N;;;;; A9F3;MYANMAR TAI LAING DIGIT THREE;Nd;0;L;;3;3;3;N;;;;; A9F4;MYANMAR TAI LAING DIGIT FOUR;Nd;0;L;;4;4;4;N;;;;; A9F5;MYANMAR TAI LAING DIGIT FIVE;Nd;0;L;;5;5;5;N;;;;; A9F6;MYANMAR TAI LAING DIGIT SIX;Nd;0;L;;6;6;6;N;;;;; A9F7;MYANMAR TAI LAING DIGIT SEVEN;Nd;0;L;;7;7;7;N;;;;; A9F8;MYANMAR TAI LAING DIGIT EIGHT;Nd;0;L;;8;8;8;N;;;;; A9F9;MYANMAR TAI LAING DIGIT NINE;Nd;0;L;;9;9;9;N;;;;; A9FA;MYANMAR LETTER TAI LAING LLA;Lo;0;L;;;;;N;;;;; A9FB;MYANMAR LETTER TAI LAING DA;Lo;0;L;;;;;N;;;;; A9FC;MYANMAR LETTER TAI LAING DHA;Lo;0;L;;;;;N;;;;; A9FD;MYANMAR LETTER TAI LAING BA;Lo;0;L;;;;;N;;;;; A9FE;MYANMAR LETTER TAI LAING BHA;Lo;0;L;;;;;N;;;;; AA00;CHAM LETTER A;Lo;0;L;;;;;N;;;;; AA01;CHAM LETTER I;Lo;0;L;;;;;N;;;;; AA02;CHAM LETTER U;Lo;0;L;;;;;N;;;;; AA03;CHAM LETTER E;Lo;0;L;;;;;N;;;;; AA04;CHAM LETTER AI;Lo;0;L;;;;;N;;;;; AA05;CHAM LETTER O;Lo;0;L;;;;;N;;;;; AA06;CHAM LETTER KA;Lo;0;L;;;;;N;;;;; AA07;CHAM LETTER KHA;Lo;0;L;;;;;N;;;;; AA08;CHAM LETTER GA;Lo;0;L;;;;;N;;;;; AA09;CHAM LETTER GHA;Lo;0;L;;;;;N;;;;; AA0A;CHAM LETTER NGUE;Lo;0;L;;;;;N;;;;; AA0B;CHAM LETTER NGA;Lo;0;L;;;;;N;;;;; AA0C;CHAM LETTER CHA;Lo;0;L;;;;;N;;;;; AA0D;CHAM LETTER CHHA;Lo;0;L;;;;;N;;;;; AA0E;CHAM LETTER JA;Lo;0;L;;;;;N;;;;; AA0F;CHAM LETTER JHA;Lo;0;L;;;;;N;;;;; AA10;CHAM LETTER NHUE;Lo;0;L;;;;;N;;;;; AA11;CHAM LETTER NHA;Lo;0;L;;;;;N;;;;; AA12;CHAM LETTER NHJA;Lo;0;L;;;;;N;;;;; AA13;CHAM LETTER TA;Lo;0;L;;;;;N;;;;; AA14;CHAM LETTER THA;Lo;0;L;;;;;N;;;;; AA15;CHAM LETTER DA;Lo;0;L;;;;;N;;;;; AA16;CHAM LETTER DHA;Lo;0;L;;;;;N;;;;; AA17;CHAM LETTER NUE;Lo;0;L;;;;;N;;;;; AA18;CHAM LETTER NA;Lo;0;L;;;;;N;;;;; AA19;CHAM LETTER DDA;Lo;0;L;;;;;N;;;;; AA1A;CHAM LETTER PA;Lo;0;L;;;;;N;;;;; AA1B;CHAM LETTER PPA;Lo;0;L;;;;;N;;;;; AA1C;CHAM LETTER PHA;Lo;0;L;;;;;N;;;;; AA1D;CHAM LETTER BA;Lo;0;L;;;;;N;;;;; AA1E;CHAM LETTER BHA;Lo;0;L;;;;;N;;;;; AA1F;CHAM LETTER MUE;Lo;0;L;;;;;N;;;;; AA20;CHAM LETTER MA;Lo;0;L;;;;;N;;;;; AA21;CHAM LETTER BBA;Lo;0;L;;;;;N;;;;; AA22;CHAM LETTER YA;Lo;0;L;;;;;N;;;;; AA23;CHAM LETTER RA;Lo;0;L;;;;;N;;;;; AA24;CHAM LETTER LA;Lo;0;L;;;;;N;;;;; AA25;CHAM LETTER VA;Lo;0;L;;;;;N;;;;; AA26;CHAM LETTER SSA;Lo;0;L;;;;;N;;;;; AA27;CHAM LETTER SA;Lo;0;L;;;;;N;;;;; AA28;CHAM LETTER HA;Lo;0;L;;;;;N;;;;; AA29;CHAM VOWEL SIGN AA;Mn;0;NSM;;;;;N;;;;; AA2A;CHAM VOWEL SIGN I;Mn;0;NSM;;;;;N;;;;; AA2B;CHAM VOWEL SIGN II;Mn;0;NSM;;;;;N;;;;; AA2C;CHAM VOWEL SIGN EI;Mn;0;NSM;;;;;N;;;;; AA2D;CHAM VOWEL SIGN U;Mn;0;NSM;;;;;N;;;;; AA2E;CHAM VOWEL SIGN OE;Mn;0;NSM;;;;;N;;;;; AA2F;CHAM VOWEL SIGN O;Mc;0;L;;;;;N;;;;; AA30;CHAM VOWEL SIGN AI;Mc;0;L;;;;;N;;;;; AA31;CHAM VOWEL SIGN AU;Mn;0;NSM;;;;;N;;;;; AA32;CHAM VOWEL SIGN UE;Mn;0;NSM;;;;;N;;;;; AA33;CHAM CONSONANT SIGN YA;Mc;0;L;;;;;N;;;;; AA34;CHAM CONSONANT SIGN RA;Mc;0;L;;;;;N;;;;; AA35;CHAM CONSONANT SIGN LA;Mn;0;NSM;;;;;N;;;;; AA36;CHAM CONSONANT SIGN WA;Mn;0;NSM;;;;;N;;;;; AA40;CHAM LETTER FINAL K;Lo;0;L;;;;;N;;;;; AA41;CHAM LETTER FINAL G;Lo;0;L;;;;;N;;;;; AA42;CHAM LETTER FINAL NG;Lo;0;L;;;;;N;;;;; AA43;CHAM CONSONANT SIGN FINAL NG;Mn;0;NSM;;;;;N;;;;; AA44;CHAM LETTER FINAL CH;Lo;0;L;;;;;N;;;;; AA45;CHAM LETTER FINAL T;Lo;0;L;;;;;N;;;;; AA46;CHAM LETTER FINAL N;Lo;0;L;;;;;N;;;;; AA47;CHAM LETTER FINAL P;Lo;0;L;;;;;N;;;;; AA48;CHAM LETTER FINAL Y;Lo;0;L;;;;;N;;;;; AA49;CHAM LETTER FINAL R;Lo;0;L;;;;;N;;;;; AA4A;CHAM LETTER FINAL L;Lo;0;L;;;;;N;;;;; AA4B;CHAM LETTER FINAL SS;Lo;0;L;;;;;N;;;;; AA4C;CHAM CONSONANT SIGN FINAL M;Mn;0;NSM;;;;;N;;;;; AA4D;CHAM CONSONANT SIGN FINAL H;Mc;0;L;;;;;N;;;;; AA50;CHAM DIGIT ZERO;Nd;0;L;;0;0;0;N;;;;; AA51;CHAM DIGIT ONE;Nd;0;L;;1;1;1;N;;;;; AA52;CHAM DIGIT TWO;Nd;0;L;;2;2;2;N;;;;; AA53;CHAM DIGIT THREE;Nd;0;L;;3;3;3;N;;;;; AA54;CHAM DIGIT FOUR;Nd;0;L;;4;4;4;N;;;;; AA55;CHAM DIGIT FIVE;Nd;0;L;;5;5;5;N;;;;; AA56;CHAM DIGIT SIX;Nd;0;L;;6;6;6;N;;;;; AA57;CHAM DIGIT SEVEN;Nd;0;L;;7;7;7;N;;;;; AA58;CHAM DIGIT EIGHT;Nd;0;L;;8;8;8;N;;;;; AA59;CHAM DIGIT NINE;Nd;0;L;;9;9;9;N;;;;; AA5C;CHAM PUNCTUATION SPIRAL;Po;0;L;;;;;N;;;;; AA5D;CHAM PUNCTUATION DANDA;Po;0;L;;;;;N;;;;; AA5E;CHAM PUNCTUATION DOUBLE DANDA;Po;0;L;;;;;N;;;;; AA5F;CHAM PUNCTUATION TRIPLE DANDA;Po;0;L;;;;;N;;;;; AA60;MYANMAR LETTER KHAMTI GA;Lo;0;L;;;;;N;;;;; AA61;MYANMAR LETTER KHAMTI CA;Lo;0;L;;;;;N;;;;; AA62;MYANMAR LETTER KHAMTI CHA;Lo;0;L;;;;;N;;;;; AA63;MYANMAR LETTER KHAMTI JA;Lo;0;L;;;;;N;;;;; AA64;MYANMAR LETTER KHAMTI JHA;Lo;0;L;;;;;N;;;;; AA65;MYANMAR LETTER KHAMTI NYA;Lo;0;L;;;;;N;;;;; AA66;MYANMAR LETTER KHAMTI TTA;Lo;0;L;;;;;N;;;;; AA67;MYANMAR LETTER KHAMTI TTHA;Lo;0;L;;;;;N;;;;; AA68;MYANMAR LETTER KHAMTI DDA;Lo;0;L;;;;;N;;;;; AA69;MYANMAR LETTER KHAMTI DDHA;Lo;0;L;;;;;N;;;;; AA6A;MYANMAR LETTER KHAMTI DHA;Lo;0;L;;;;;N;;;;; AA6B;MYANMAR LETTER KHAMTI NA;Lo;0;L;;;;;N;;;;; AA6C;MYANMAR LETTER KHAMTI SA;Lo;0;L;;;;;N;;;;; AA6D;MYANMAR LETTER KHAMTI HA;Lo;0;L;;;;;N;;;;; AA6E;MYANMAR LETTER KHAMTI HHA;Lo;0;L;;;;;N;;;;; AA6F;MYANMAR LETTER KHAMTI FA;Lo;0;L;;;;;N;;;;; AA70;MYANMAR MODIFIER LETTER KHAMTI REDUPLICATION;Lm;0;L;;;;;N;;;;; AA71;MYANMAR LETTER KHAMTI XA;Lo;0;L;;;;;N;;;;; AA72;MYANMAR LETTER KHAMTI ZA;Lo;0;L;;;;;N;;;;; AA73;MYANMAR LETTER KHAMTI RA;Lo;0;L;;;;;N;;;;; AA74;MYANMAR LOGOGRAM KHAMTI OAY;Lo;0;L;;;;;N;;;;; AA75;MYANMAR LOGOGRAM KHAMTI QN;Lo;0;L;;;;;N;;;;; AA76;MYANMAR LOGOGRAM KHAMTI HM;Lo;0;L;;;;;N;;;;; AA77;MYANMAR SYMBOL AITON EXCLAMATION;So;0;L;;;;;N;;;;; AA78;MYANMAR SYMBOL AITON ONE;So;0;L;;;;;N;;;;; AA79;MYANMAR SYMBOL AITON TWO;So;0;L;;;;;N;;;;; AA7A;MYANMAR LETTER AITON RA;Lo;0;L;;;;;N;;;;; AA7B;MYANMAR SIGN PAO KAREN TONE;Mc;0;L;;;;;N;;;;; AA7C;MYANMAR SIGN TAI LAING TONE-2;Mn;0;NSM;;;;;N;;;;; AA7D;MYANMAR SIGN TAI LAING TONE-5;Mc;0;L;;;;;N;;;;; AA7E;MYANMAR LETTER SHWE PALAUNG CHA;Lo;0;L;;;;;N;;;;; AA7F;MYANMAR LETTER SHWE PALAUNG SHA;Lo;0;L;;;;;N;;;;; AA80;TAI VIET LETTER LOW KO;Lo;0;L;;;;;N;;;;; AA81;TAI VIET LETTER HIGH KO;Lo;0;L;;;;;N;;;;; AA82;TAI VIET LETTER LOW KHO;Lo;0;L;;;;;N;;;;; AA83;TAI VIET LETTER HIGH KHO;Lo;0;L;;;;;N;;;;; AA84;TAI VIET LETTER LOW KHHO;Lo;0;L;;;;;N;;;;; AA85;TAI VIET LETTER HIGH KHHO;Lo;0;L;;;;;N;;;;; AA86;TAI VIET LETTER LOW GO;Lo;0;L;;;;;N;;;;; AA87;TAI VIET LETTER HIGH GO;Lo;0;L;;;;;N;;;;; AA88;TAI VIET LETTER LOW NGO;Lo;0;L;;;;;N;;;;; AA89;TAI VIET LETTER HIGH NGO;Lo;0;L;;;;;N;;;;; AA8A;TAI VIET LETTER LOW CO;Lo;0;L;;;;;N;;;;; AA8B;TAI VIET LETTER HIGH CO;Lo;0;L;;;;;N;;;;; AA8C;TAI VIET LETTER LOW CHO;Lo;0;L;;;;;N;;;;; AA8D;TAI VIET LETTER HIGH CHO;Lo;0;L;;;;;N;;;;; AA8E;TAI VIET LETTER LOW SO;Lo;0;L;;;;;N;;;;; AA8F;TAI VIET LETTER HIGH SO;Lo;0;L;;;;;N;;;;; AA90;TAI VIET LETTER LOW NYO;Lo;0;L;;;;;N;;;;; AA91;TAI VIET LETTER HIGH NYO;Lo;0;L;;;;;N;;;;; AA92;TAI VIET LETTER LOW DO;Lo;0;L;;;;;N;;;;; AA93;TAI VIET LETTER HIGH DO;Lo;0;L;;;;;N;;;;; AA94;TAI VIET LETTER LOW TO;Lo;0;L;;;;;N;;;;; AA95;TAI VIET LETTER HIGH TO;Lo;0;L;;;;;N;;;;; AA96;TAI VIET LETTER LOW THO;Lo;0;L;;;;;N;;;;; AA97;TAI VIET LETTER HIGH THO;Lo;0;L;;;;;N;;;;; AA98;TAI VIET LETTER LOW NO;Lo;0;L;;;;;N;;;;; AA99;TAI VIET LETTER HIGH NO;Lo;0;L;;;;;N;;;;; AA9A;TAI VIET LETTER LOW BO;Lo;0;L;;;;;N;;;;; AA9B;TAI VIET LETTER HIGH BO;Lo;0;L;;;;;N;;;;; AA9C;TAI VIET LETTER LOW PO;Lo;0;L;;;;;N;;;;; AA9D;TAI VIET LETTER HIGH PO;Lo;0;L;;;;;N;;;;; AA9E;TAI VIET LETTER LOW PHO;Lo;0;L;;;;;N;;;;; AA9F;TAI VIET LETTER HIGH PHO;Lo;0;L;;;;;N;;;;; AAA0;TAI VIET LETTER LOW FO;Lo;0;L;;;;;N;;;;; AAA1;TAI VIET LETTER HIGH FO;Lo;0;L;;;;;N;;;;; AAA2;TAI VIET LETTER LOW MO;Lo;0;L;;;;;N;;;;; AAA3;TAI VIET LETTER HIGH MO;Lo;0;L;;;;;N;;;;; AAA4;TAI VIET LETTER LOW YO;Lo;0;L;;;;;N;;;;; AAA5;TAI VIET LETTER HIGH YO;Lo;0;L;;;;;N;;;;; AAA6;TAI VIET LETTER LOW RO;Lo;0;L;;;;;N;;;;; AAA7;TAI VIET LETTER HIGH RO;Lo;0;L;;;;;N;;;;; AAA8;TAI VIET LETTER LOW LO;Lo;0;L;;;;;N;;;;; AAA9;TAI VIET LETTER HIGH LO;Lo;0;L;;;;;N;;;;; AAAA;TAI VIET LETTER LOW VO;Lo;0;L;;;;;N;;;;; AAAB;TAI VIET LETTER HIGH VO;Lo;0;L;;;;;N;;;;; AAAC;TAI VIET LETTER LOW HO;Lo;0;L;;;;;N;;;;; AAAD;TAI VIET LETTER HIGH HO;Lo;0;L;;;;;N;;;;; AAAE;TAI VIET LETTER LOW O;Lo;0;L;;;;;N;;;;; AAAF;TAI VIET LETTER HIGH O;Lo;0;L;;;;;N;;;;; AAB0;TAI VIET MAI KANG;Mn;230;NSM;;;;;N;;;;; AAB1;TAI VIET VOWEL AA;Lo;0;L;;;;;N;;;;; AAB2;TAI VIET VOWEL I;Mn;230;NSM;;;;;N;;;;; AAB3;TAI VIET VOWEL UE;Mn;230;NSM;;;;;N;;;;; AAB4;TAI VIET VOWEL U;Mn;220;NSM;;;;;N;;;;; AAB5;TAI VIET VOWEL E;Lo;0;L;;;;;N;;;;; AAB6;TAI VIET VOWEL O;Lo;0;L;;;;;N;;;;; AAB7;TAI VIET MAI KHIT;Mn;230;NSM;;;;;N;;;;; AAB8;TAI VIET VOWEL IA;Mn;230;NSM;;;;;N;;;;; AAB9;TAI VIET VOWEL UEA;Lo;0;L;;;;;N;;;;; AABA;TAI VIET VOWEL UA;Lo;0;L;;;;;N;;;;; AABB;TAI VIET VOWEL AUE;Lo;0;L;;;;;N;;;;; AABC;TAI VIET VOWEL AY;Lo;0;L;;;;;N;;;;; AABD;TAI VIET VOWEL AN;Lo;0;L;;;;;N;;;;; AABE;TAI VIET VOWEL AM;Mn;230;NSM;;;;;N;;;;; AABF;TAI VIET TONE MAI EK;Mn;230;NSM;;;;;N;;;;; AAC0;TAI VIET TONE MAI NUENG;Lo;0;L;;;;;N;;;;; AAC1;TAI VIET TONE MAI THO;Mn;230;NSM;;;;;N;;;;; AAC2;TAI VIET TONE MAI SONG;Lo;0;L;;;;;N;;;;; AADB;TAI VIET SYMBOL KON;Lo;0;L;;;;;N;;;;; AADC;TAI VIET SYMBOL NUENG;Lo;0;L;;;;;N;;;;; AADD;TAI VIET SYMBOL SAM;Lm;0;L;;;;;N;;;;; AADE;TAI VIET SYMBOL HO HOI;Po;0;L;;;;;N;;;;; AADF;TAI VIET SYMBOL KOI KOI;Po;0;L;;;;;N;;;;; AAE0;MEETEI MAYEK LETTER E;Lo;0;L;;;;;N;;;;; AAE1;MEETEI MAYEK LETTER O;Lo;0;L;;;;;N;;;;; AAE2;MEETEI MAYEK LETTER CHA;Lo;0;L;;;;;N;;;;; AAE3;MEETEI MAYEK LETTER NYA;Lo;0;L;;;;;N;;;;; AAE4;MEETEI MAYEK LETTER TTA;Lo;0;L;;;;;N;;;;; AAE5;MEETEI MAYEK LETTER TTHA;Lo;0;L;;;;;N;;;;; AAE6;MEETEI MAYEK LETTER DDA;Lo;0;L;;;;;N;;;;; AAE7;MEETEI MAYEK LETTER DDHA;Lo;0;L;;;;;N;;;;; AAE8;MEETEI MAYEK LETTER NNA;Lo;0;L;;;;;N;;;;; AAE9;MEETEI MAYEK LETTER SHA;Lo;0;L;;;;;N;;;;; AAEA;MEETEI MAYEK LETTER SSA;Lo;0;L;;;;;N;;;;; AAEB;MEETEI MAYEK VOWEL SIGN II;Mc;0;L;;;;;N;;;;; AAEC;MEETEI MAYEK VOWEL SIGN UU;Mn;0;NSM;;;;;N;;;;; AAED;MEETEI MAYEK VOWEL SIGN AAI;Mn;0;NSM;;;;;N;;;;; AAEE;MEETEI MAYEK VOWEL SIGN AU;Mc;0;L;;;;;N;;;;; AAEF;MEETEI MAYEK VOWEL SIGN AAU;Mc;0;L;;;;;N;;;;; AAF0;MEETEI MAYEK CHEIKHAN;Po;0;L;;;;;N;;;;; AAF1;MEETEI MAYEK AHANG KHUDAM;Po;0;L;;;;;N;;;;; AAF2;MEETEI MAYEK ANJI;Lo;0;L;;;;;N;;;;; AAF3;MEETEI MAYEK SYLLABLE REPETITION MARK;Lm;0;L;;;;;N;;;;; AAF4;MEETEI MAYEK WORD REPETITION MARK;Lm;0;L;;;;;N;;;;; AAF5;MEETEI MAYEK VOWEL SIGN VISARGA;Mc;0;L;;;;;N;;;;; AAF6;MEETEI MAYEK VIRAMA;Mn;9;NSM;;;;;N;;;;; AB01;ETHIOPIC SYLLABLE TTHU;Lo;0;L;;;;;N;;;;; AB02;ETHIOPIC SYLLABLE TTHI;Lo;0;L;;;;;N;;;;; AB03;ETHIOPIC SYLLABLE TTHAA;Lo;0;L;;;;;N;;;;; AB04;ETHIOPIC SYLLABLE TTHEE;Lo;0;L;;;;;N;;;;; AB05;ETHIOPIC SYLLABLE TTHE;Lo;0;L;;;;;N;;;;; AB06;ETHIOPIC SYLLABLE TTHO;Lo;0;L;;;;;N;;;;; AB09;ETHIOPIC SYLLABLE DDHU;Lo;0;L;;;;;N;;;;; AB0A;ETHIOPIC SYLLABLE DDHI;Lo;0;L;;;;;N;;;;; AB0B;ETHIOPIC SYLLABLE DDHAA;Lo;0;L;;;;;N;;;;; AB0C;ETHIOPIC SYLLABLE DDHEE;Lo;0;L;;;;;N;;;;; AB0D;ETHIOPIC SYLLABLE DDHE;Lo;0;L;;;;;N;;;;; AB0E;ETHIOPIC SYLLABLE DDHO;Lo;0;L;;;;;N;;;;; AB11;ETHIOPIC SYLLABLE DZU;Lo;0;L;;;;;N;;;;; AB12;ETHIOPIC SYLLABLE DZI;Lo;0;L;;;;;N;;;;; AB13;ETHIOPIC SYLLABLE DZAA;Lo;0;L;;;;;N;;;;; AB14;ETHIOPIC SYLLABLE DZEE;Lo;0;L;;;;;N;;;;; AB15;ETHIOPIC SYLLABLE DZE;Lo;0;L;;;;;N;;;;; AB16;ETHIOPIC SYLLABLE DZO;Lo;0;L;;;;;N;;;;; AB20;ETHIOPIC SYLLABLE CCHHA;Lo;0;L;;;;;N;;;;; AB21;ETHIOPIC SYLLABLE CCHHU;Lo;0;L;;;;;N;;;;; AB22;ETHIOPIC SYLLABLE CCHHI;Lo;0;L;;;;;N;;;;; AB23;ETHIOPIC SYLLABLE CCHHAA;Lo;0;L;;;;;N;;;;; AB24;ETHIOPIC SYLLABLE CCHHEE;Lo;0;L;;;;;N;;;;; AB25;ETHIOPIC SYLLABLE CCHHE;Lo;0;L;;;;;N;;;;; AB26;ETHIOPIC SYLLABLE CCHHO;Lo;0;L;;;;;N;;;;; AB28;ETHIOPIC SYLLABLE BBA;Lo;0;L;;;;;N;;;;; AB29;ETHIOPIC SYLLABLE BBU;Lo;0;L;;;;;N;;;;; AB2A;ETHIOPIC SYLLABLE BBI;Lo;0;L;;;;;N;;;;; AB2B;ETHIOPIC SYLLABLE BBAA;Lo;0;L;;;;;N;;;;; AB2C;ETHIOPIC SYLLABLE BBEE;Lo;0;L;;;;;N;;;;; AB2D;ETHIOPIC SYLLABLE BBE;Lo;0;L;;;;;N;;;;; AB2E;ETHIOPIC SYLLABLE BBO;Lo;0;L;;;;;N;;;;; AB30;LATIN SMALL LETTER BARRED ALPHA;Ll;0;L;;;;;N;;;;; AB31;LATIN SMALL LETTER A REVERSED-SCHWA;Ll;0;L;;;;;N;;;;; AB32;LATIN SMALL LETTER BLACKLETTER E;Ll;0;L;;;;;N;;;;; AB33;LATIN SMALL LETTER BARRED E;Ll;0;L;;;;;N;;;;; AB34;LATIN SMALL LETTER E WITH FLOURISH;Ll;0;L;;;;;N;;;;; AB35;LATIN SMALL LETTER LENIS F;Ll;0;L;;;;;N;;;;; AB36;LATIN SMALL LETTER SCRIPT G WITH CROSSED-TAIL;Ll;0;L;;;;;N;;;;; AB37;LATIN SMALL LETTER L WITH INVERTED LAZY S;Ll;0;L;;;;;N;;;;; AB38;LATIN SMALL LETTER L WITH DOUBLE MIDDLE TILDE;Ll;0;L;;;;;N;;;;; AB39;LATIN SMALL LETTER L WITH MIDDLE RING;Ll;0;L;;;;;N;;;;; AB3A;LATIN SMALL LETTER M WITH CROSSED-TAIL;Ll;0;L;;;;;N;;;;; AB3B;LATIN SMALL LETTER N WITH CROSSED-TAIL;Ll;0;L;;;;;N;;;;; AB3C;LATIN SMALL LETTER ENG WITH CROSSED-TAIL;Ll;0;L;;;;;N;;;;; AB3D;LATIN SMALL LETTER BLACKLETTER O;Ll;0;L;;;;;N;;;;; AB3E;LATIN SMALL LETTER BLACKLETTER O WITH STROKE;Ll;0;L;;;;;N;;;;; AB3F;LATIN SMALL LETTER OPEN O WITH STROKE;Ll;0;L;;;;;N;;;;; AB40;LATIN SMALL LETTER INVERTED OE;Ll;0;L;;;;;N;;;;; AB41;LATIN SMALL LETTER TURNED OE WITH STROKE;Ll;0;L;;;;;N;;;;; AB42;LATIN SMALL LETTER TURNED OE WITH HORIZONTAL STROKE;Ll;0;L;;;;;N;;;;; AB43;LATIN SMALL LETTER TURNED O OPEN-O;Ll;0;L;;;;;N;;;;; AB44;LATIN SMALL LETTER TURNED O OPEN-O WITH STROKE;Ll;0;L;;;;;N;;;;; AB45;LATIN SMALL LETTER STIRRUP R;Ll;0;L;;;;;N;;;;; AB46;LATIN LETTER SMALL CAPITAL R WITH RIGHT LEG;Ll;0;L;;;;;N;;;;; AB47;LATIN SMALL LETTER R WITHOUT HANDLE;Ll;0;L;;;;;N;;;;; AB48;LATIN SMALL LETTER DOUBLE R;Ll;0;L;;;;;N;;;;; AB49;LATIN SMALL LETTER R WITH CROSSED-TAIL;Ll;0;L;;;;;N;;;;; AB4A;LATIN SMALL LETTER DOUBLE R WITH CROSSED-TAIL;Ll;0;L;;;;;N;;;;; AB4B;LATIN SMALL LETTER SCRIPT R;Ll;0;L;;;;;N;;;;; AB4C;LATIN SMALL LETTER SCRIPT R WITH RING;Ll;0;L;;;;;N;;;;; AB4D;LATIN SMALL LETTER BASELINE ESH;Ll;0;L;;;;;N;;;;; AB4E;LATIN SMALL LETTER U WITH SHORT RIGHT LEG;Ll;0;L;;;;;N;;;;; AB4F;LATIN SMALL LETTER U BAR WITH SHORT RIGHT LEG;Ll;0;L;;;;;N;;;;; AB50;LATIN SMALL LETTER UI;Ll;0;L;;;;;N;;;;; AB51;LATIN SMALL LETTER TURNED UI;Ll;0;L;;;;;N;;;;; AB52;LATIN SMALL LETTER U WITH LEFT HOOK;Ll;0;L;;;;;N;;;;; AB53;LATIN SMALL LETTER CHI;Ll;0;L;;;;;N;;;;; AB54;LATIN SMALL LETTER CHI WITH LOW RIGHT RING;Ll;0;L;;;;;N;;;;; AB55;LATIN SMALL LETTER CHI WITH LOW LEFT SERIF;Ll;0;L;;;;;N;;;;; AB56;LATIN SMALL LETTER X WITH LOW RIGHT RING;Ll;0;L;;;;;N;;;;; AB57;LATIN SMALL LETTER X WITH LONG LEFT LEG;Ll;0;L;;;;;N;;;;; AB58;LATIN SMALL LETTER X WITH LONG LEFT LEG AND LOW RIGHT RING;Ll;0;L;;;;;N;;;;; AB59;LATIN SMALL LETTER X WITH LONG LEFT LEG WITH SERIF;Ll;0;L;;;;;N;;;;; AB5A;LATIN SMALL LETTER Y WITH SHORT RIGHT LEG;Ll;0;L;;;;;N;;;;; AB5B;MODIFIER BREVE WITH INVERTED BREVE;Sk;0;L;;;;;N;;;;; AB5C;MODIFIER LETTER SMALL HENG;Lm;0;L; A727;;;;N;;;;; AB5D;MODIFIER LETTER SMALL L WITH INVERTED LAZY S;Lm;0;L; AB37;;;;N;;;;; AB5E;MODIFIER LETTER SMALL L WITH MIDDLE TILDE;Lm;0;L; 026B;;;;N;;;;; AB5F;MODIFIER LETTER SMALL U WITH LEFT HOOK;Lm;0;L; AB52;;;;N;;;;; AB64;LATIN SMALL LETTER INVERTED ALPHA;Ll;0;L;;;;;N;;;;; AB65;GREEK LETTER SMALL CAPITAL OMEGA;Ll;0;L;;;;;N;;;;; ABC0;MEETEI MAYEK LETTER KOK;Lo;0;L;;;;;N;;;;; ABC1;MEETEI MAYEK LETTER SAM;Lo;0;L;;;;;N;;;;; ABC2;MEETEI MAYEK LETTER LAI;Lo;0;L;;;;;N;;;;; ABC3;MEETEI MAYEK LETTER MIT;Lo;0;L;;;;;N;;;;; ABC4;MEETEI MAYEK LETTER PA;Lo;0;L;;;;;N;;;;; ABC5;MEETEI MAYEK LETTER NA;Lo;0;L;;;;;N;;;;; ABC6;MEETEI MAYEK LETTER CHIL;Lo;0;L;;;;;N;;;;; ABC7;MEETEI MAYEK LETTER TIL;Lo;0;L;;;;;N;;;;; ABC8;MEETEI MAYEK LETTER KHOU;Lo;0;L;;;;;N;;;;; ABC9;MEETEI MAYEK LETTER NGOU;Lo;0;L;;;;;N;;;;; ABCA;MEETEI MAYEK LETTER THOU;Lo;0;L;;;;;N;;;;; ABCB;MEETEI MAYEK LETTER WAI;Lo;0;L;;;;;N;;;;; ABCC;MEETEI MAYEK LETTER YANG;Lo;0;L;;;;;N;;;;; ABCD;MEETEI MAYEK LETTER HUK;Lo;0;L;;;;;N;;;;; ABCE;MEETEI MAYEK LETTER UN;Lo;0;L;;;;;N;;;;; ABCF;MEETEI MAYEK LETTER I;Lo;0;L;;;;;N;;;;; ABD0;MEETEI MAYEK LETTER PHAM;Lo;0;L;;;;;N;;;;; ABD1;MEETEI MAYEK LETTER ATIYA;Lo;0;L;;;;;N;;;;; ABD2;MEETEI MAYEK LETTER GOK;Lo;0;L;;;;;N;;;;; ABD3;MEETEI MAYEK LETTER JHAM;Lo;0;L;;;;;N;;;;; ABD4;MEETEI MAYEK LETTER RAI;Lo;0;L;;;;;N;;;;; ABD5;MEETEI MAYEK LETTER BA;Lo;0;L;;;;;N;;;;; ABD6;MEETEI MAYEK LETTER JIL;Lo;0;L;;;;;N;;;;; ABD7;MEETEI MAYEK LETTER DIL;Lo;0;L;;;;;N;;;;; ABD8;MEETEI MAYEK LETTER GHOU;Lo;0;L;;;;;N;;;;; ABD9;MEETEI MAYEK LETTER DHOU;Lo;0;L;;;;;N;;;;; ABDA;MEETEI MAYEK LETTER BHAM;Lo;0;L;;;;;N;;;;; ABDB;MEETEI MAYEK LETTER KOK LONSUM;Lo;0;L;;;;;N;;;;; ABDC;MEETEI MAYEK LETTER LAI LONSUM;Lo;0;L;;;;;N;;;;; ABDD;MEETEI MAYEK LETTER MIT LONSUM;Lo;0;L;;;;;N;;;;; ABDE;MEETEI MAYEK LETTER PA LONSUM;Lo;0;L;;;;;N;;;;; ABDF;MEETEI MAYEK LETTER NA LONSUM;Lo;0;L;;;;;N;;;;; ABE0;MEETEI MAYEK LETTER TIL LONSUM;Lo;0;L;;;;;N;;;;; ABE1;MEETEI MAYEK LETTER NGOU LONSUM;Lo;0;L;;;;;N;;;;; ABE2;MEETEI MAYEK LETTER I LONSUM;Lo;0;L;;;;;N;;;;; ABE3;MEETEI MAYEK VOWEL SIGN ONAP;Mc;0;L;;;;;N;;;;; ABE4;MEETEI MAYEK VOWEL SIGN INAP;Mc;0;L;;;;;N;;;;; ABE5;MEETEI MAYEK VOWEL SIGN ANAP;Mn;0;NSM;;;;;N;;;;; ABE6;MEETEI MAYEK VOWEL SIGN YENAP;Mc;0;L;;;;;N;;;;; ABE7;MEETEI MAYEK VOWEL SIGN SOUNAP;Mc;0;L;;;;;N;;;;; ABE8;MEETEI MAYEK VOWEL SIGN UNAP;Mn;0;NSM;;;;;N;;;;; ABE9;MEETEI MAYEK VOWEL SIGN CHEINAP;Mc;0;L;;;;;N;;;;; ABEA;MEETEI MAYEK VOWEL SIGN NUNG;Mc;0;L;;;;;N;;;;; ABEB;MEETEI MAYEK CHEIKHEI;Po;0;L;;;;;N;;;;; ABEC;MEETEI MAYEK LUM IYEK;Mc;0;L;;;;;N;;;;; ABED;MEETEI MAYEK APUN IYEK;Mn;9;NSM;;;;;N;;;;; ABF0;MEETEI MAYEK DIGIT ZERO;Nd;0;L;;0;0;0;N;;;;; ABF1;MEETEI MAYEK DIGIT ONE;Nd;0;L;;1;1;1;N;;;;; ABF2;MEETEI MAYEK DIGIT TWO;Nd;0;L;;2;2;2;N;;;;; ABF3;MEETEI MAYEK DIGIT THREE;Nd;0;L;;3;3;3;N;;;;; ABF4;MEETEI MAYEK DIGIT FOUR;Nd;0;L;;4;4;4;N;;;;; ABF5;MEETEI MAYEK DIGIT FIVE;Nd;0;L;;5;5;5;N;;;;; ABF6;MEETEI MAYEK DIGIT SIX;Nd;0;L;;6;6;6;N;;;;; ABF7;MEETEI MAYEK DIGIT SEVEN;Nd;0;L;;7;7;7;N;;;;; ABF8;MEETEI MAYEK DIGIT EIGHT;Nd;0;L;;8;8;8;N;;;;; ABF9;MEETEI MAYEK DIGIT NINE;Nd;0;L;;9;9;9;N;;;;; AC00;;Lo;0;L;;;;;N;;;;; D7A3;;Lo;0;L;;;;;N;;;;; D7B0;HANGUL JUNGSEONG O-YEO;Lo;0;L;;;;;N;;;;; D7B1;HANGUL JUNGSEONG O-O-I;Lo;0;L;;;;;N;;;;; D7B2;HANGUL JUNGSEONG YO-A;Lo;0;L;;;;;N;;;;; D7B3;HANGUL JUNGSEONG YO-AE;Lo;0;L;;;;;N;;;;; D7B4;HANGUL JUNGSEONG YO-EO;Lo;0;L;;;;;N;;;;; D7B5;HANGUL JUNGSEONG U-YEO;Lo;0;L;;;;;N;;;;; D7B6;HANGUL JUNGSEONG U-I-I;Lo;0;L;;;;;N;;;;; D7B7;HANGUL JUNGSEONG YU-AE;Lo;0;L;;;;;N;;;;; D7B8;HANGUL JUNGSEONG YU-O;Lo;0;L;;;;;N;;;;; D7B9;HANGUL JUNGSEONG EU-A;Lo;0;L;;;;;N;;;;; D7BA;HANGUL JUNGSEONG EU-EO;Lo;0;L;;;;;N;;;;; D7BB;HANGUL JUNGSEONG EU-E;Lo;0;L;;;;;N;;;;; D7BC;HANGUL JUNGSEONG EU-O;Lo;0;L;;;;;N;;;;; D7BD;HANGUL JUNGSEONG I-YA-O;Lo;0;L;;;;;N;;;;; D7BE;HANGUL JUNGSEONG I-YAE;Lo;0;L;;;;;N;;;;; D7BF;HANGUL JUNGSEONG I-YEO;Lo;0;L;;;;;N;;;;; D7C0;HANGUL JUNGSEONG I-YE;Lo;0;L;;;;;N;;;;; D7C1;HANGUL JUNGSEONG I-O-I;Lo;0;L;;;;;N;;;;; D7C2;HANGUL JUNGSEONG I-YO;Lo;0;L;;;;;N;;;;; D7C3;HANGUL JUNGSEONG I-YU;Lo;0;L;;;;;N;;;;; D7C4;HANGUL JUNGSEONG I-I;Lo;0;L;;;;;N;;;;; D7C5;HANGUL JUNGSEONG ARAEA-A;Lo;0;L;;;;;N;;;;; D7C6;HANGUL JUNGSEONG ARAEA-E;Lo;0;L;;;;;N;;;;; D7CB;HANGUL JONGSEONG NIEUN-RIEUL;Lo;0;L;;;;;N;;;;; D7CC;HANGUL JONGSEONG NIEUN-CHIEUCH;Lo;0;L;;;;;N;;;;; D7CD;HANGUL JONGSEONG SSANGTIKEUT;Lo;0;L;;;;;N;;;;; D7CE;HANGUL JONGSEONG SSANGTIKEUT-PIEUP;Lo;0;L;;;;;N;;;;; D7CF;HANGUL JONGSEONG TIKEUT-PIEUP;Lo;0;L;;;;;N;;;;; D7D0;HANGUL JONGSEONG TIKEUT-SIOS;Lo;0;L;;;;;N;;;;; D7D1;HANGUL JONGSEONG TIKEUT-SIOS-KIYEOK;Lo;0;L;;;;;N;;;;; D7D2;HANGUL JONGSEONG TIKEUT-CIEUC;Lo;0;L;;;;;N;;;;; D7D3;HANGUL JONGSEONG TIKEUT-CHIEUCH;Lo;0;L;;;;;N;;;;; D7D4;HANGUL JONGSEONG TIKEUT-THIEUTH;Lo;0;L;;;;;N;;;;; D7D5;HANGUL JONGSEONG RIEUL-SSANGKIYEOK;Lo;0;L;;;;;N;;;;; D7D6;HANGUL JONGSEONG RIEUL-KIYEOK-HIEUH;Lo;0;L;;;;;N;;;;; D7D7;HANGUL JONGSEONG SSANGRIEUL-KHIEUKH;Lo;0;L;;;;;N;;;;; D7D8;HANGUL JONGSEONG RIEUL-MIEUM-HIEUH;Lo;0;L;;;;;N;;;;; D7D9;HANGUL JONGSEONG RIEUL-PIEUP-TIKEUT;Lo;0;L;;;;;N;;;;; D7DA;HANGUL JONGSEONG RIEUL-PIEUP-PHIEUPH;Lo;0;L;;;;;N;;;;; D7DB;HANGUL JONGSEONG RIEUL-YESIEUNG;Lo;0;L;;;;;N;;;;; D7DC;HANGUL JONGSEONG RIEUL-YEORINHIEUH-HIEUH;Lo;0;L;;;;;N;;;;; D7DD;HANGUL JONGSEONG KAPYEOUNRIEUL;Lo;0;L;;;;;N;;;;; D7DE;HANGUL JONGSEONG MIEUM-NIEUN;Lo;0;L;;;;;N;;;;; D7DF;HANGUL JONGSEONG MIEUM-SSANGNIEUN;Lo;0;L;;;;;N;;;;; D7E0;HANGUL JONGSEONG SSANGMIEUM;Lo;0;L;;;;;N;;;;; D7E1;HANGUL JONGSEONG MIEUM-PIEUP-SIOS;Lo;0;L;;;;;N;;;;; D7E2;HANGUL JONGSEONG MIEUM-CIEUC;Lo;0;L;;;;;N;;;;; D7E3;HANGUL JONGSEONG PIEUP-TIKEUT;Lo;0;L;;;;;N;;;;; D7E4;HANGUL JONGSEONG PIEUP-RIEUL-PHIEUPH;Lo;0;L;;;;;N;;;;; D7E5;HANGUL JONGSEONG PIEUP-MIEUM;Lo;0;L;;;;;N;;;;; D7E6;HANGUL JONGSEONG SSANGPIEUP;Lo;0;L;;;;;N;;;;; D7E7;HANGUL JONGSEONG PIEUP-SIOS-TIKEUT;Lo;0;L;;;;;N;;;;; D7E8;HANGUL JONGSEONG PIEUP-CIEUC;Lo;0;L;;;;;N;;;;; D7E9;HANGUL JONGSEONG PIEUP-CHIEUCH;Lo;0;L;;;;;N;;;;; D7EA;HANGUL JONGSEONG SIOS-MIEUM;Lo;0;L;;;;;N;;;;; D7EB;HANGUL JONGSEONG SIOS-KAPYEOUNPIEUP;Lo;0;L;;;;;N;;;;; D7EC;HANGUL JONGSEONG SSANGSIOS-KIYEOK;Lo;0;L;;;;;N;;;;; D7ED;HANGUL JONGSEONG SSANGSIOS-TIKEUT;Lo;0;L;;;;;N;;;;; D7EE;HANGUL JONGSEONG SIOS-PANSIOS;Lo;0;L;;;;;N;;;;; D7EF;HANGUL JONGSEONG SIOS-CIEUC;Lo;0;L;;;;;N;;;;; D7F0;HANGUL JONGSEONG SIOS-CHIEUCH;Lo;0;L;;;;;N;;;;; D7F1;HANGUL JONGSEONG SIOS-THIEUTH;Lo;0;L;;;;;N;;;;; D7F2;HANGUL JONGSEONG SIOS-HIEUH;Lo;0;L;;;;;N;;;;; D7F3;HANGUL JONGSEONG PANSIOS-PIEUP;Lo;0;L;;;;;N;;;;; D7F4;HANGUL JONGSEONG PANSIOS-KAPYEOUNPIEUP;Lo;0;L;;;;;N;;;;; D7F5;HANGUL JONGSEONG YESIEUNG-MIEUM;Lo;0;L;;;;;N;;;;; D7F6;HANGUL JONGSEONG YESIEUNG-HIEUH;Lo;0;L;;;;;N;;;;; D7F7;HANGUL JONGSEONG CIEUC-PIEUP;Lo;0;L;;;;;N;;;;; D7F8;HANGUL JONGSEONG CIEUC-SSANGPIEUP;Lo;0;L;;;;;N;;;;; D7F9;HANGUL JONGSEONG SSANGCIEUC;Lo;0;L;;;;;N;;;;; D7FA;HANGUL JONGSEONG PHIEUPH-SIOS;Lo;0;L;;;;;N;;;;; D7FB;HANGUL JONGSEONG PHIEUPH-THIEUTH;Lo;0;L;;;;;N;;;;; D800;;Cs;0;L;;;;;N;;;;; DB7F;;Cs;0;L;;;;;N;;;;; DB80;;Cs;0;L;;;;;N;;;;; DBFF;;Cs;0;L;;;;;N;;;;; DC00;;Cs;0;L;;;;;N;;;;; DFFF;;Cs;0;L;;;;;N;;;;; E000;;Co;0;L;;;;;N;;;;; F8FF;;Co;0;L;;;;;N;;;;; F900;CJK COMPATIBILITY IDEOGRAPH-F900;Lo;0;L;8C48;;;;N;;;;; F901;CJK COMPATIBILITY IDEOGRAPH-F901;Lo;0;L;66F4;;;;N;;;;; F902;CJK COMPATIBILITY IDEOGRAPH-F902;Lo;0;L;8ECA;;;;N;;;;; F903;CJK COMPATIBILITY IDEOGRAPH-F903;Lo;0;L;8CC8;;;;N;;;;; F904;CJK COMPATIBILITY IDEOGRAPH-F904;Lo;0;L;6ED1;;;;N;;;;; F905;CJK COMPATIBILITY IDEOGRAPH-F905;Lo;0;L;4E32;;;;N;;;;; F906;CJK COMPATIBILITY IDEOGRAPH-F906;Lo;0;L;53E5;;;;N;;;;; F907;CJK COMPATIBILITY IDEOGRAPH-F907;Lo;0;L;9F9C;;;;N;;;;; F908;CJK COMPATIBILITY IDEOGRAPH-F908;Lo;0;L;9F9C;;;;N;;;;; F909;CJK COMPATIBILITY IDEOGRAPH-F909;Lo;0;L;5951;;;;N;;;;; F90A;CJK COMPATIBILITY IDEOGRAPH-F90A;Lo;0;L;91D1;;;;N;;;;; F90B;CJK COMPATIBILITY IDEOGRAPH-F90B;Lo;0;L;5587;;;;N;;;;; F90C;CJK COMPATIBILITY IDEOGRAPH-F90C;Lo;0;L;5948;;;;N;;;;; F90D;CJK COMPATIBILITY IDEOGRAPH-F90D;Lo;0;L;61F6;;;;N;;;;; F90E;CJK COMPATIBILITY IDEOGRAPH-F90E;Lo;0;L;7669;;;;N;;;;; F90F;CJK COMPATIBILITY IDEOGRAPH-F90F;Lo;0;L;7F85;;;;N;;;;; F910;CJK COMPATIBILITY IDEOGRAPH-F910;Lo;0;L;863F;;;;N;;;;; F911;CJK COMPATIBILITY IDEOGRAPH-F911;Lo;0;L;87BA;;;;N;;;;; F912;CJK COMPATIBILITY IDEOGRAPH-F912;Lo;0;L;88F8;;;;N;;;;; F913;CJK COMPATIBILITY IDEOGRAPH-F913;Lo;0;L;908F;;;;N;;;;; F914;CJK COMPATIBILITY IDEOGRAPH-F914;Lo;0;L;6A02;;;;N;;;;; F915;CJK COMPATIBILITY IDEOGRAPH-F915;Lo;0;L;6D1B;;;;N;;;;; F916;CJK COMPATIBILITY IDEOGRAPH-F916;Lo;0;L;70D9;;;;N;;;;; F917;CJK COMPATIBILITY IDEOGRAPH-F917;Lo;0;L;73DE;;;;N;;;;; F918;CJK COMPATIBILITY IDEOGRAPH-F918;Lo;0;L;843D;;;;N;;;;; F919;CJK COMPATIBILITY IDEOGRAPH-F919;Lo;0;L;916A;;;;N;;;;; F91A;CJK COMPATIBILITY IDEOGRAPH-F91A;Lo;0;L;99F1;;;;N;;;;; F91B;CJK COMPATIBILITY IDEOGRAPH-F91B;Lo;0;L;4E82;;;;N;;;;; F91C;CJK COMPATIBILITY IDEOGRAPH-F91C;Lo;0;L;5375;;;;N;;;;; F91D;CJK COMPATIBILITY IDEOGRAPH-F91D;Lo;0;L;6B04;;;;N;;;;; F91E;CJK COMPATIBILITY IDEOGRAPH-F91E;Lo;0;L;721B;;;;N;;;;; F91F;CJK COMPATIBILITY IDEOGRAPH-F91F;Lo;0;L;862D;;;;N;;;;; F920;CJK COMPATIBILITY IDEOGRAPH-F920;Lo;0;L;9E1E;;;;N;;;;; F921;CJK COMPATIBILITY IDEOGRAPH-F921;Lo;0;L;5D50;;;;N;;;;; F922;CJK COMPATIBILITY IDEOGRAPH-F922;Lo;0;L;6FEB;;;;N;;;;; F923;CJK COMPATIBILITY IDEOGRAPH-F923;Lo;0;L;85CD;;;;N;;;;; F924;CJK COMPATIBILITY IDEOGRAPH-F924;Lo;0;L;8964;;;;N;;;;; F925;CJK COMPATIBILITY IDEOGRAPH-F925;Lo;0;L;62C9;;;;N;;;;; F926;CJK COMPATIBILITY IDEOGRAPH-F926;Lo;0;L;81D8;;;;N;;;;; F927;CJK COMPATIBILITY IDEOGRAPH-F927;Lo;0;L;881F;;;;N;;;;; F928;CJK COMPATIBILITY IDEOGRAPH-F928;Lo;0;L;5ECA;;;;N;;;;; F929;CJK COMPATIBILITY IDEOGRAPH-F929;Lo;0;L;6717;;;;N;;;;; F92A;CJK COMPATIBILITY IDEOGRAPH-F92A;Lo;0;L;6D6A;;;;N;;;;; F92B;CJK COMPATIBILITY IDEOGRAPH-F92B;Lo;0;L;72FC;;;;N;;;;; F92C;CJK COMPATIBILITY IDEOGRAPH-F92C;Lo;0;L;90CE;;;;N;;;;; F92D;CJK COMPATIBILITY IDEOGRAPH-F92D;Lo;0;L;4F86;;;;N;;;;; F92E;CJK COMPATIBILITY IDEOGRAPH-F92E;Lo;0;L;51B7;;;;N;;;;; F92F;CJK COMPATIBILITY IDEOGRAPH-F92F;Lo;0;L;52DE;;;;N;;;;; F930;CJK COMPATIBILITY IDEOGRAPH-F930;Lo;0;L;64C4;;;;N;;;;; F931;CJK COMPATIBILITY IDEOGRAPH-F931;Lo;0;L;6AD3;;;;N;;;;; F932;CJK COMPATIBILITY IDEOGRAPH-F932;Lo;0;L;7210;;;;N;;;;; F933;CJK COMPATIBILITY IDEOGRAPH-F933;Lo;0;L;76E7;;;;N;;;;; F934;CJK COMPATIBILITY IDEOGRAPH-F934;Lo;0;L;8001;;;;N;;;;; F935;CJK COMPATIBILITY IDEOGRAPH-F935;Lo;0;L;8606;;;;N;;;;; F936;CJK COMPATIBILITY IDEOGRAPH-F936;Lo;0;L;865C;;;;N;;;;; F937;CJK COMPATIBILITY IDEOGRAPH-F937;Lo;0;L;8DEF;;;;N;;;;; F938;CJK COMPATIBILITY IDEOGRAPH-F938;Lo;0;L;9732;;;;N;;;;; F939;CJK COMPATIBILITY IDEOGRAPH-F939;Lo;0;L;9B6F;;;;N;;;;; F93A;CJK COMPATIBILITY IDEOGRAPH-F93A;Lo;0;L;9DFA;;;;N;;;;; F93B;CJK COMPATIBILITY IDEOGRAPH-F93B;Lo;0;L;788C;;;;N;;;;; F93C;CJK COMPATIBILITY IDEOGRAPH-F93C;Lo;0;L;797F;;;;N;;;;; F93D;CJK COMPATIBILITY IDEOGRAPH-F93D;Lo;0;L;7DA0;;;;N;;;;; F93E;CJK COMPATIBILITY IDEOGRAPH-F93E;Lo;0;L;83C9;;;;N;;;;; F93F;CJK COMPATIBILITY IDEOGRAPH-F93F;Lo;0;L;9304;;;;N;;;;; F940;CJK COMPATIBILITY IDEOGRAPH-F940;Lo;0;L;9E7F;;;;N;;;;; F941;CJK COMPATIBILITY IDEOGRAPH-F941;Lo;0;L;8AD6;;;;N;;;;; F942;CJK COMPATIBILITY IDEOGRAPH-F942;Lo;0;L;58DF;;;;N;;;;; F943;CJK COMPATIBILITY IDEOGRAPH-F943;Lo;0;L;5F04;;;;N;;;;; F944;CJK COMPATIBILITY IDEOGRAPH-F944;Lo;0;L;7C60;;;;N;;;;; F945;CJK COMPATIBILITY IDEOGRAPH-F945;Lo;0;L;807E;;;;N;;;;; F946;CJK COMPATIBILITY IDEOGRAPH-F946;Lo;0;L;7262;;;;N;;;;; F947;CJK COMPATIBILITY IDEOGRAPH-F947;Lo;0;L;78CA;;;;N;;;;; F948;CJK COMPATIBILITY IDEOGRAPH-F948;Lo;0;L;8CC2;;;;N;;;;; F949;CJK COMPATIBILITY IDEOGRAPH-F949;Lo;0;L;96F7;;;;N;;;;; F94A;CJK COMPATIBILITY IDEOGRAPH-F94A;Lo;0;L;58D8;;;;N;;;;; F94B;CJK COMPATIBILITY IDEOGRAPH-F94B;Lo;0;L;5C62;;;;N;;;;; F94C;CJK COMPATIBILITY IDEOGRAPH-F94C;Lo;0;L;6A13;;;;N;;;;; F94D;CJK COMPATIBILITY IDEOGRAPH-F94D;Lo;0;L;6DDA;;;;N;;;;; F94E;CJK COMPATIBILITY IDEOGRAPH-F94E;Lo;0;L;6F0F;;;;N;;;;; F94F;CJK COMPATIBILITY IDEOGRAPH-F94F;Lo;0;L;7D2F;;;;N;;;;; F950;CJK COMPATIBILITY IDEOGRAPH-F950;Lo;0;L;7E37;;;;N;;;;; F951;CJK COMPATIBILITY IDEOGRAPH-F951;Lo;0;L;964B;;;;N;;;;; F952;CJK COMPATIBILITY IDEOGRAPH-F952;Lo;0;L;52D2;;;;N;;;;; F953;CJK COMPATIBILITY IDEOGRAPH-F953;Lo;0;L;808B;;;;N;;;;; F954;CJK COMPATIBILITY IDEOGRAPH-F954;Lo;0;L;51DC;;;;N;;;;; F955;CJK COMPATIBILITY IDEOGRAPH-F955;Lo;0;L;51CC;;;;N;;;;; F956;CJK COMPATIBILITY IDEOGRAPH-F956;Lo;0;L;7A1C;;;;N;;;;; F957;CJK COMPATIBILITY IDEOGRAPH-F957;Lo;0;L;7DBE;;;;N;;;;; F958;CJK COMPATIBILITY IDEOGRAPH-F958;Lo;0;L;83F1;;;;N;;;;; F959;CJK COMPATIBILITY IDEOGRAPH-F959;Lo;0;L;9675;;;;N;;;;; F95A;CJK COMPATIBILITY IDEOGRAPH-F95A;Lo;0;L;8B80;;;;N;;;;; F95B;CJK COMPATIBILITY IDEOGRAPH-F95B;Lo;0;L;62CF;;;;N;;;;; F95C;CJK COMPATIBILITY IDEOGRAPH-F95C;Lo;0;L;6A02;;;;N;;;;; F95D;CJK COMPATIBILITY IDEOGRAPH-F95D;Lo;0;L;8AFE;;;;N;;;;; F95E;CJK COMPATIBILITY IDEOGRAPH-F95E;Lo;0;L;4E39;;;;N;;;;; F95F;CJK COMPATIBILITY IDEOGRAPH-F95F;Lo;0;L;5BE7;;;;N;;;;; F960;CJK COMPATIBILITY IDEOGRAPH-F960;Lo;0;L;6012;;;;N;;;;; F961;CJK COMPATIBILITY IDEOGRAPH-F961;Lo;0;L;7387;;;;N;;;;; F962;CJK COMPATIBILITY IDEOGRAPH-F962;Lo;0;L;7570;;;;N;;;;; F963;CJK COMPATIBILITY IDEOGRAPH-F963;Lo;0;L;5317;;;;N;;;;; F964;CJK COMPATIBILITY IDEOGRAPH-F964;Lo;0;L;78FB;;;;N;;;;; F965;CJK COMPATIBILITY IDEOGRAPH-F965;Lo;0;L;4FBF;;;;N;;;;; F966;CJK COMPATIBILITY IDEOGRAPH-F966;Lo;0;L;5FA9;;;;N;;;;; F967;CJK COMPATIBILITY IDEOGRAPH-F967;Lo;0;L;4E0D;;;;N;;;;; F968;CJK COMPATIBILITY IDEOGRAPH-F968;Lo;0;L;6CCC;;;;N;;;;; F969;CJK COMPATIBILITY IDEOGRAPH-F969;Lo;0;L;6578;;;;N;;;;; F96A;CJK COMPATIBILITY IDEOGRAPH-F96A;Lo;0;L;7D22;;;;N;;;;; F96B;CJK COMPATIBILITY IDEOGRAPH-F96B;Lo;0;L;53C3;;;3;N;;;;; F96C;CJK COMPATIBILITY IDEOGRAPH-F96C;Lo;0;L;585E;;;;N;;;;; F96D;CJK COMPATIBILITY IDEOGRAPH-F96D;Lo;0;L;7701;;;;N;;;;; F96E;CJK COMPATIBILITY IDEOGRAPH-F96E;Lo;0;L;8449;;;;N;;;;; F96F;CJK COMPATIBILITY IDEOGRAPH-F96F;Lo;0;L;8AAA;;;;N;;;;; F970;CJK COMPATIBILITY IDEOGRAPH-F970;Lo;0;L;6BBA;;;;N;;;;; F971;CJK COMPATIBILITY IDEOGRAPH-F971;Lo;0;L;8FB0;;;;N;;;;; F972;CJK COMPATIBILITY IDEOGRAPH-F972;Lo;0;L;6C88;;;;N;;;;; F973;CJK COMPATIBILITY IDEOGRAPH-F973;Lo;0;L;62FE;;;10;N;;;;; F974;CJK COMPATIBILITY IDEOGRAPH-F974;Lo;0;L;82E5;;;;N;;;;; F975;CJK COMPATIBILITY IDEOGRAPH-F975;Lo;0;L;63A0;;;;N;;;;; F976;CJK COMPATIBILITY IDEOGRAPH-F976;Lo;0;L;7565;;;;N;;;;; F977;CJK COMPATIBILITY IDEOGRAPH-F977;Lo;0;L;4EAE;;;;N;;;;; F978;CJK COMPATIBILITY IDEOGRAPH-F978;Lo;0;L;5169;;;2;N;;;;; F979;CJK COMPATIBILITY IDEOGRAPH-F979;Lo;0;L;51C9;;;;N;;;;; F97A;CJK COMPATIBILITY IDEOGRAPH-F97A;Lo;0;L;6881;;;;N;;;;; F97B;CJK COMPATIBILITY IDEOGRAPH-F97B;Lo;0;L;7CE7;;;;N;;;;; F97C;CJK COMPATIBILITY IDEOGRAPH-F97C;Lo;0;L;826F;;;;N;;;;; F97D;CJK COMPATIBILITY IDEOGRAPH-F97D;Lo;0;L;8AD2;;;;N;;;;; F97E;CJK COMPATIBILITY IDEOGRAPH-F97E;Lo;0;L;91CF;;;;N;;;;; F97F;CJK COMPATIBILITY IDEOGRAPH-F97F;Lo;0;L;52F5;;;;N;;;;; F980;CJK COMPATIBILITY IDEOGRAPH-F980;Lo;0;L;5442;;;;N;;;;; F981;CJK COMPATIBILITY IDEOGRAPH-F981;Lo;0;L;5973;;;;N;;;;; F982;CJK COMPATIBILITY IDEOGRAPH-F982;Lo;0;L;5EEC;;;;N;;;;; F983;CJK COMPATIBILITY IDEOGRAPH-F983;Lo;0;L;65C5;;;;N;;;;; F984;CJK COMPATIBILITY IDEOGRAPH-F984;Lo;0;L;6FFE;;;;N;;;;; F985;CJK COMPATIBILITY IDEOGRAPH-F985;Lo;0;L;792A;;;;N;;;;; F986;CJK COMPATIBILITY IDEOGRAPH-F986;Lo;0;L;95AD;;;;N;;;;; F987;CJK COMPATIBILITY IDEOGRAPH-F987;Lo;0;L;9A6A;;;;N;;;;; F988;CJK COMPATIBILITY IDEOGRAPH-F988;Lo;0;L;9E97;;;;N;;;;; F989;CJK COMPATIBILITY IDEOGRAPH-F989;Lo;0;L;9ECE;;;;N;;;;; F98A;CJK COMPATIBILITY IDEOGRAPH-F98A;Lo;0;L;529B;;;;N;;;;; F98B;CJK COMPATIBILITY IDEOGRAPH-F98B;Lo;0;L;66C6;;;;N;;;;; F98C;CJK COMPATIBILITY IDEOGRAPH-F98C;Lo;0;L;6B77;;;;N;;;;; F98D;CJK COMPATIBILITY IDEOGRAPH-F98D;Lo;0;L;8F62;;;;N;;;;; F98E;CJK COMPATIBILITY IDEOGRAPH-F98E;Lo;0;L;5E74;;;;N;;;;; F98F;CJK COMPATIBILITY IDEOGRAPH-F98F;Lo;0;L;6190;;;;N;;;;; F990;CJK COMPATIBILITY IDEOGRAPH-F990;Lo;0;L;6200;;;;N;;;;; F991;CJK COMPATIBILITY IDEOGRAPH-F991;Lo;0;L;649A;;;;N;;;;; F992;CJK COMPATIBILITY IDEOGRAPH-F992;Lo;0;L;6F23;;;;N;;;;; F993;CJK COMPATIBILITY IDEOGRAPH-F993;Lo;0;L;7149;;;;N;;;;; F994;CJK COMPATIBILITY IDEOGRAPH-F994;Lo;0;L;7489;;;;N;;;;; F995;CJK COMPATIBILITY IDEOGRAPH-F995;Lo;0;L;79CA;;;;N;;;;; F996;CJK COMPATIBILITY IDEOGRAPH-F996;Lo;0;L;7DF4;;;;N;;;;; F997;CJK COMPATIBILITY IDEOGRAPH-F997;Lo;0;L;806F;;;;N;;;;; F998;CJK COMPATIBILITY IDEOGRAPH-F998;Lo;0;L;8F26;;;;N;;;;; F999;CJK COMPATIBILITY IDEOGRAPH-F999;Lo;0;L;84EE;;;;N;;;;; F99A;CJK COMPATIBILITY IDEOGRAPH-F99A;Lo;0;L;9023;;;;N;;;;; F99B;CJK COMPATIBILITY IDEOGRAPH-F99B;Lo;0;L;934A;;;;N;;;;; F99C;CJK COMPATIBILITY IDEOGRAPH-F99C;Lo;0;L;5217;;;;N;;;;; F99D;CJK COMPATIBILITY IDEOGRAPH-F99D;Lo;0;L;52A3;;;;N;;;;; F99E;CJK COMPATIBILITY IDEOGRAPH-F99E;Lo;0;L;54BD;;;;N;;;;; F99F;CJK COMPATIBILITY IDEOGRAPH-F99F;Lo;0;L;70C8;;;;N;;;;; F9A0;CJK COMPATIBILITY IDEOGRAPH-F9A0;Lo;0;L;88C2;;;;N;;;;; F9A1;CJK COMPATIBILITY IDEOGRAPH-F9A1;Lo;0;L;8AAA;;;;N;;;;; F9A2;CJK COMPATIBILITY IDEOGRAPH-F9A2;Lo;0;L;5EC9;;;;N;;;;; F9A3;CJK COMPATIBILITY IDEOGRAPH-F9A3;Lo;0;L;5FF5;;;;N;;;;; F9A4;CJK COMPATIBILITY IDEOGRAPH-F9A4;Lo;0;L;637B;;;;N;;;;; F9A5;CJK COMPATIBILITY IDEOGRAPH-F9A5;Lo;0;L;6BAE;;;;N;;;;; F9A6;CJK COMPATIBILITY IDEOGRAPH-F9A6;Lo;0;L;7C3E;;;;N;;;;; F9A7;CJK COMPATIBILITY IDEOGRAPH-F9A7;Lo;0;L;7375;;;;N;;;;; F9A8;CJK COMPATIBILITY IDEOGRAPH-F9A8;Lo;0;L;4EE4;;;;N;;;;; F9A9;CJK COMPATIBILITY IDEOGRAPH-F9A9;Lo;0;L;56F9;;;;N;;;;; F9AA;CJK COMPATIBILITY IDEOGRAPH-F9AA;Lo;0;L;5BE7;;;;N;;;;; F9AB;CJK COMPATIBILITY IDEOGRAPH-F9AB;Lo;0;L;5DBA;;;;N;;;;; F9AC;CJK COMPATIBILITY IDEOGRAPH-F9AC;Lo;0;L;601C;;;;N;;;;; F9AD;CJK COMPATIBILITY IDEOGRAPH-F9AD;Lo;0;L;73B2;;;;N;;;;; F9AE;CJK COMPATIBILITY IDEOGRAPH-F9AE;Lo;0;L;7469;;;;N;;;;; F9AF;CJK COMPATIBILITY IDEOGRAPH-F9AF;Lo;0;L;7F9A;;;;N;;;;; F9B0;CJK COMPATIBILITY IDEOGRAPH-F9B0;Lo;0;L;8046;;;;N;;;;; F9B1;CJK COMPATIBILITY IDEOGRAPH-F9B1;Lo;0;L;9234;;;;N;;;;; F9B2;CJK COMPATIBILITY IDEOGRAPH-F9B2;Lo;0;L;96F6;;;0;N;;;;; F9B3;CJK COMPATIBILITY IDEOGRAPH-F9B3;Lo;0;L;9748;;;;N;;;;; F9B4;CJK COMPATIBILITY IDEOGRAPH-F9B4;Lo;0;L;9818;;;;N;;;;; F9B5;CJK COMPATIBILITY IDEOGRAPH-F9B5;Lo;0;L;4F8B;;;;N;;;;; F9B6;CJK COMPATIBILITY IDEOGRAPH-F9B6;Lo;0;L;79AE;;;;N;;;;; F9B7;CJK COMPATIBILITY IDEOGRAPH-F9B7;Lo;0;L;91B4;;;;N;;;;; F9B8;CJK COMPATIBILITY IDEOGRAPH-F9B8;Lo;0;L;96B8;;;;N;;;;; F9B9;CJK COMPATIBILITY IDEOGRAPH-F9B9;Lo;0;L;60E1;;;;N;;;;; F9BA;CJK COMPATIBILITY IDEOGRAPH-F9BA;Lo;0;L;4E86;;;;N;;;;; F9BB;CJK COMPATIBILITY IDEOGRAPH-F9BB;Lo;0;L;50DA;;;;N;;;;; F9BC;CJK COMPATIBILITY IDEOGRAPH-F9BC;Lo;0;L;5BEE;;;;N;;;;; F9BD;CJK COMPATIBILITY IDEOGRAPH-F9BD;Lo;0;L;5C3F;;;;N;;;;; F9BE;CJK COMPATIBILITY IDEOGRAPH-F9BE;Lo;0;L;6599;;;;N;;;;; F9BF;CJK COMPATIBILITY IDEOGRAPH-F9BF;Lo;0;L;6A02;;;;N;;;;; F9C0;CJK COMPATIBILITY IDEOGRAPH-F9C0;Lo;0;L;71CE;;;;N;;;;; F9C1;CJK COMPATIBILITY IDEOGRAPH-F9C1;Lo;0;L;7642;;;;N;;;;; F9C2;CJK COMPATIBILITY IDEOGRAPH-F9C2;Lo;0;L;84FC;;;;N;;;;; F9C3;CJK COMPATIBILITY IDEOGRAPH-F9C3;Lo;0;L;907C;;;;N;;;;; F9C4;CJK COMPATIBILITY IDEOGRAPH-F9C4;Lo;0;L;9F8D;;;;N;;;;; F9C5;CJK COMPATIBILITY IDEOGRAPH-F9C5;Lo;0;L;6688;;;;N;;;;; F9C6;CJK COMPATIBILITY IDEOGRAPH-F9C6;Lo;0;L;962E;;;;N;;;;; F9C7;CJK COMPATIBILITY IDEOGRAPH-F9C7;Lo;0;L;5289;;;;N;;;;; F9C8;CJK COMPATIBILITY IDEOGRAPH-F9C8;Lo;0;L;677B;;;;N;;;;; F9C9;CJK COMPATIBILITY IDEOGRAPH-F9C9;Lo;0;L;67F3;;;;N;;;;; F9CA;CJK COMPATIBILITY IDEOGRAPH-F9CA;Lo;0;L;6D41;;;;N;;;;; F9CB;CJK COMPATIBILITY IDEOGRAPH-F9CB;Lo;0;L;6E9C;;;;N;;;;; F9CC;CJK COMPATIBILITY IDEOGRAPH-F9CC;Lo;0;L;7409;;;;N;;;;; F9CD;CJK COMPATIBILITY IDEOGRAPH-F9CD;Lo;0;L;7559;;;;N;;;;; F9CE;CJK COMPATIBILITY IDEOGRAPH-F9CE;Lo;0;L;786B;;;;N;;;;; F9CF;CJK COMPATIBILITY IDEOGRAPH-F9CF;Lo;0;L;7D10;;;;N;;;;; F9D0;CJK COMPATIBILITY IDEOGRAPH-F9D0;Lo;0;L;985E;;;;N;;;;; F9D1;CJK COMPATIBILITY IDEOGRAPH-F9D1;Lo;0;L;516D;;;6;N;;;;; F9D2;CJK COMPATIBILITY IDEOGRAPH-F9D2;Lo;0;L;622E;;;;N;;;;; F9D3;CJK COMPATIBILITY IDEOGRAPH-F9D3;Lo;0;L;9678;;;6;N;;;;; F9D4;CJK COMPATIBILITY IDEOGRAPH-F9D4;Lo;0;L;502B;;;;N;;;;; F9D5;CJK COMPATIBILITY IDEOGRAPH-F9D5;Lo;0;L;5D19;;;;N;;;;; F9D6;CJK COMPATIBILITY IDEOGRAPH-F9D6;Lo;0;L;6DEA;;;;N;;;;; F9D7;CJK COMPATIBILITY IDEOGRAPH-F9D7;Lo;0;L;8F2A;;;;N;;;;; F9D8;CJK COMPATIBILITY IDEOGRAPH-F9D8;Lo;0;L;5F8B;;;;N;;;;; F9D9;CJK COMPATIBILITY IDEOGRAPH-F9D9;Lo;0;L;6144;;;;N;;;;; F9DA;CJK COMPATIBILITY IDEOGRAPH-F9DA;Lo;0;L;6817;;;;N;;;;; F9DB;CJK COMPATIBILITY IDEOGRAPH-F9DB;Lo;0;L;7387;;;;N;;;;; F9DC;CJK COMPATIBILITY IDEOGRAPH-F9DC;Lo;0;L;9686;;;;N;;;;; F9DD;CJK COMPATIBILITY IDEOGRAPH-F9DD;Lo;0;L;5229;;;;N;;;;; F9DE;CJK COMPATIBILITY IDEOGRAPH-F9DE;Lo;0;L;540F;;;;N;;;;; F9DF;CJK COMPATIBILITY IDEOGRAPH-F9DF;Lo;0;L;5C65;;;;N;;;;; F9E0;CJK COMPATIBILITY IDEOGRAPH-F9E0;Lo;0;L;6613;;;;N;;;;; F9E1;CJK COMPATIBILITY IDEOGRAPH-F9E1;Lo;0;L;674E;;;;N;;;;; F9E2;CJK COMPATIBILITY IDEOGRAPH-F9E2;Lo;0;L;68A8;;;;N;;;;; F9E3;CJK COMPATIBILITY IDEOGRAPH-F9E3;Lo;0;L;6CE5;;;;N;;;;; F9E4;CJK COMPATIBILITY IDEOGRAPH-F9E4;Lo;0;L;7406;;;;N;;;;; F9E5;CJK COMPATIBILITY IDEOGRAPH-F9E5;Lo;0;L;75E2;;;;N;;;;; F9E6;CJK COMPATIBILITY IDEOGRAPH-F9E6;Lo;0;L;7F79;;;;N;;;;; F9E7;CJK COMPATIBILITY IDEOGRAPH-F9E7;Lo;0;L;88CF;;;;N;;;;; F9E8;CJK COMPATIBILITY IDEOGRAPH-F9E8;Lo;0;L;88E1;;;;N;;;;; F9E9;CJK COMPATIBILITY IDEOGRAPH-F9E9;Lo;0;L;91CC;;;;N;;;;; F9EA;CJK COMPATIBILITY IDEOGRAPH-F9EA;Lo;0;L;96E2;;;;N;;;;; F9EB;CJK COMPATIBILITY IDEOGRAPH-F9EB;Lo;0;L;533F;;;;N;;;;; F9EC;CJK COMPATIBILITY IDEOGRAPH-F9EC;Lo;0;L;6EBA;;;;N;;;;; F9ED;CJK COMPATIBILITY IDEOGRAPH-F9ED;Lo;0;L;541D;;;;N;;;;; F9EE;CJK COMPATIBILITY IDEOGRAPH-F9EE;Lo;0;L;71D0;;;;N;;;;; F9EF;CJK COMPATIBILITY IDEOGRAPH-F9EF;Lo;0;L;7498;;;;N;;;;; F9F0;CJK COMPATIBILITY IDEOGRAPH-F9F0;Lo;0;L;85FA;;;;N;;;;; F9F1;CJK COMPATIBILITY IDEOGRAPH-F9F1;Lo;0;L;96A3;;;;N;;;;; F9F2;CJK COMPATIBILITY IDEOGRAPH-F9F2;Lo;0;L;9C57;;;;N;;;;; F9F3;CJK COMPATIBILITY IDEOGRAPH-F9F3;Lo;0;L;9E9F;;;;N;;;;; F9F4;CJK COMPATIBILITY IDEOGRAPH-F9F4;Lo;0;L;6797;;;;N;;;;; F9F5;CJK COMPATIBILITY IDEOGRAPH-F9F5;Lo;0;L;6DCB;;;;N;;;;; F9F6;CJK COMPATIBILITY IDEOGRAPH-F9F6;Lo;0;L;81E8;;;;N;;;;; F9F7;CJK COMPATIBILITY IDEOGRAPH-F9F7;Lo;0;L;7ACB;;;;N;;;;; F9F8;CJK COMPATIBILITY IDEOGRAPH-F9F8;Lo;0;L;7B20;;;;N;;;;; F9F9;CJK COMPATIBILITY IDEOGRAPH-F9F9;Lo;0;L;7C92;;;;N;;;;; F9FA;CJK COMPATIBILITY IDEOGRAPH-F9FA;Lo;0;L;72C0;;;;N;;;;; F9FB;CJK COMPATIBILITY IDEOGRAPH-F9FB;Lo;0;L;7099;;;;N;;;;; F9FC;CJK COMPATIBILITY IDEOGRAPH-F9FC;Lo;0;L;8B58;;;;N;;;;; F9FD;CJK COMPATIBILITY IDEOGRAPH-F9FD;Lo;0;L;4EC0;;;10;N;;;;; F9FE;CJK COMPATIBILITY IDEOGRAPH-F9FE;Lo;0;L;8336;;;;N;;;;; F9FF;CJK COMPATIBILITY IDEOGRAPH-F9FF;Lo;0;L;523A;;;;N;;;;; FA00;CJK COMPATIBILITY IDEOGRAPH-FA00;Lo;0;L;5207;;;;N;;;;; FA01;CJK COMPATIBILITY IDEOGRAPH-FA01;Lo;0;L;5EA6;;;;N;;;;; FA02;CJK COMPATIBILITY IDEOGRAPH-FA02;Lo;0;L;62D3;;;;N;;;;; FA03;CJK COMPATIBILITY IDEOGRAPH-FA03;Lo;0;L;7CD6;;;;N;;;;; FA04;CJK COMPATIBILITY IDEOGRAPH-FA04;Lo;0;L;5B85;;;;N;;;;; FA05;CJK COMPATIBILITY IDEOGRAPH-FA05;Lo;0;L;6D1E;;;;N;;;;; FA06;CJK COMPATIBILITY IDEOGRAPH-FA06;Lo;0;L;66B4;;;;N;;;;; FA07;CJK COMPATIBILITY IDEOGRAPH-FA07;Lo;0;L;8F3B;;;;N;;;;; FA08;CJK COMPATIBILITY IDEOGRAPH-FA08;Lo;0;L;884C;;;;N;;;;; FA09;CJK COMPATIBILITY IDEOGRAPH-FA09;Lo;0;L;964D;;;;N;;;;; FA0A;CJK COMPATIBILITY IDEOGRAPH-FA0A;Lo;0;L;898B;;;;N;;;;; FA0B;CJK COMPATIBILITY IDEOGRAPH-FA0B;Lo;0;L;5ED3;;;;N;;;;; FA0C;CJK COMPATIBILITY IDEOGRAPH-FA0C;Lo;0;L;5140;;;;N;;;;; FA0D;CJK COMPATIBILITY IDEOGRAPH-FA0D;Lo;0;L;55C0;;;;N;;;;; FA0E;CJK COMPATIBILITY IDEOGRAPH-FA0E;Lo;0;L;;;;;N;;;;; FA0F;CJK COMPATIBILITY IDEOGRAPH-FA0F;Lo;0;L;;;;;N;;;;; FA10;CJK COMPATIBILITY IDEOGRAPH-FA10;Lo;0;L;585A;;;;N;;;;; FA11;CJK COMPATIBILITY IDEOGRAPH-FA11;Lo;0;L;;;;;N;;;;; FA12;CJK COMPATIBILITY IDEOGRAPH-FA12;Lo;0;L;6674;;;;N;;;;; FA13;CJK COMPATIBILITY IDEOGRAPH-FA13;Lo;0;L;;;;;N;;;;; FA14;CJK COMPATIBILITY IDEOGRAPH-FA14;Lo;0;L;;;;;N;;;;; FA15;CJK COMPATIBILITY IDEOGRAPH-FA15;Lo;0;L;51DE;;;;N;;;;; FA16;CJK COMPATIBILITY IDEOGRAPH-FA16;Lo;0;L;732A;;;;N;;;;; FA17;CJK COMPATIBILITY IDEOGRAPH-FA17;Lo;0;L;76CA;;;;N;;;;; FA18;CJK COMPATIBILITY IDEOGRAPH-FA18;Lo;0;L;793C;;;;N;;;;; FA19;CJK COMPATIBILITY IDEOGRAPH-FA19;Lo;0;L;795E;;;;N;;;;; FA1A;CJK COMPATIBILITY IDEOGRAPH-FA1A;Lo;0;L;7965;;;;N;;;;; FA1B;CJK COMPATIBILITY IDEOGRAPH-FA1B;Lo;0;L;798F;;;;N;;;;; FA1C;CJK COMPATIBILITY IDEOGRAPH-FA1C;Lo;0;L;9756;;;;N;;;;; FA1D;CJK COMPATIBILITY IDEOGRAPH-FA1D;Lo;0;L;7CBE;;;;N;;;;; FA1E;CJK COMPATIBILITY IDEOGRAPH-FA1E;Lo;0;L;7FBD;;;;N;;;;; FA1F;CJK COMPATIBILITY IDEOGRAPH-FA1F;Lo;0;L;;;;;N;;;;; FA20;CJK COMPATIBILITY IDEOGRAPH-FA20;Lo;0;L;8612;;;;N;;;;; FA21;CJK COMPATIBILITY IDEOGRAPH-FA21;Lo;0;L;;;;;N;;;;; FA22;CJK COMPATIBILITY IDEOGRAPH-FA22;Lo;0;L;8AF8;;;;N;;;;; FA23;CJK COMPATIBILITY IDEOGRAPH-FA23;Lo;0;L;;;;;N;;;;; FA24;CJK COMPATIBILITY IDEOGRAPH-FA24;Lo;0;L;;;;;N;;;;; FA25;CJK COMPATIBILITY IDEOGRAPH-FA25;Lo;0;L;9038;;;;N;;;;; FA26;CJK COMPATIBILITY IDEOGRAPH-FA26;Lo;0;L;90FD;;;;N;;;;; FA27;CJK COMPATIBILITY IDEOGRAPH-FA27;Lo;0;L;;;;;N;;;;; FA28;CJK COMPATIBILITY IDEOGRAPH-FA28;Lo;0;L;;;;;N;;;;; FA29;CJK COMPATIBILITY IDEOGRAPH-FA29;Lo;0;L;;;;;N;;;;; FA2A;CJK COMPATIBILITY IDEOGRAPH-FA2A;Lo;0;L;98EF;;;;N;;;;; FA2B;CJK COMPATIBILITY IDEOGRAPH-FA2B;Lo;0;L;98FC;;;;N;;;;; FA2C;CJK COMPATIBILITY IDEOGRAPH-FA2C;Lo;0;L;9928;;;;N;;;;; FA2D;CJK COMPATIBILITY IDEOGRAPH-FA2D;Lo;0;L;9DB4;;;;N;;;;; FA2E;CJK COMPATIBILITY IDEOGRAPH-FA2E;Lo;0;L;90DE;;;;N;;;;; FA2F;CJK COMPATIBILITY IDEOGRAPH-FA2F;Lo;0;L;96B7;;;;N;;;;; FA30;CJK COMPATIBILITY IDEOGRAPH-FA30;Lo;0;L;4FAE;;;;N;;;;; FA31;CJK COMPATIBILITY IDEOGRAPH-FA31;Lo;0;L;50E7;;;;N;;;;; FA32;CJK COMPATIBILITY IDEOGRAPH-FA32;Lo;0;L;514D;;;;N;;;;; FA33;CJK COMPATIBILITY IDEOGRAPH-FA33;Lo;0;L;52C9;;;;N;;;;; FA34;CJK COMPATIBILITY IDEOGRAPH-FA34;Lo;0;L;52E4;;;;N;;;;; FA35;CJK COMPATIBILITY IDEOGRAPH-FA35;Lo;0;L;5351;;;;N;;;;; FA36;CJK COMPATIBILITY IDEOGRAPH-FA36;Lo;0;L;559D;;;;N;;;;; FA37;CJK COMPATIBILITY IDEOGRAPH-FA37;Lo;0;L;5606;;;;N;;;;; FA38;CJK COMPATIBILITY IDEOGRAPH-FA38;Lo;0;L;5668;;;;N;;;;; FA39;CJK COMPATIBILITY IDEOGRAPH-FA39;Lo;0;L;5840;;;;N;;;;; FA3A;CJK COMPATIBILITY IDEOGRAPH-FA3A;Lo;0;L;58A8;;;;N;;;;; FA3B;CJK COMPATIBILITY IDEOGRAPH-FA3B;Lo;0;L;5C64;;;;N;;;;; FA3C;CJK COMPATIBILITY IDEOGRAPH-FA3C;Lo;0;L;5C6E;;;;N;;;;; FA3D;CJK COMPATIBILITY IDEOGRAPH-FA3D;Lo;0;L;6094;;;;N;;;;; FA3E;CJK COMPATIBILITY IDEOGRAPH-FA3E;Lo;0;L;6168;;;;N;;;;; FA3F;CJK COMPATIBILITY IDEOGRAPH-FA3F;Lo;0;L;618E;;;;N;;;;; FA40;CJK COMPATIBILITY IDEOGRAPH-FA40;Lo;0;L;61F2;;;;N;;;;; FA41;CJK COMPATIBILITY IDEOGRAPH-FA41;Lo;0;L;654F;;;;N;;;;; FA42;CJK COMPATIBILITY IDEOGRAPH-FA42;Lo;0;L;65E2;;;;N;;;;; FA43;CJK COMPATIBILITY IDEOGRAPH-FA43;Lo;0;L;6691;;;;N;;;;; FA44;CJK COMPATIBILITY IDEOGRAPH-FA44;Lo;0;L;6885;;;;N;;;;; FA45;CJK COMPATIBILITY IDEOGRAPH-FA45;Lo;0;L;6D77;;;;N;;;;; FA46;CJK COMPATIBILITY IDEOGRAPH-FA46;Lo;0;L;6E1A;;;;N;;;;; FA47;CJK COMPATIBILITY IDEOGRAPH-FA47;Lo;0;L;6F22;;;;N;;;;; FA48;CJK COMPATIBILITY IDEOGRAPH-FA48;Lo;0;L;716E;;;;N;;;;; FA49;CJK COMPATIBILITY IDEOGRAPH-FA49;Lo;0;L;722B;;;;N;;;;; FA4A;CJK COMPATIBILITY IDEOGRAPH-FA4A;Lo;0;L;7422;;;;N;;;;; FA4B;CJK COMPATIBILITY IDEOGRAPH-FA4B;Lo;0;L;7891;;;;N;;;;; FA4C;CJK COMPATIBILITY IDEOGRAPH-FA4C;Lo;0;L;793E;;;;N;;;;; FA4D;CJK COMPATIBILITY IDEOGRAPH-FA4D;Lo;0;L;7949;;;;N;;;;; FA4E;CJK COMPATIBILITY IDEOGRAPH-FA4E;Lo;0;L;7948;;;;N;;;;; FA4F;CJK COMPATIBILITY IDEOGRAPH-FA4F;Lo;0;L;7950;;;;N;;;;; FA50;CJK COMPATIBILITY IDEOGRAPH-FA50;Lo;0;L;7956;;;;N;;;;; FA51;CJK COMPATIBILITY IDEOGRAPH-FA51;Lo;0;L;795D;;;;N;;;;; FA52;CJK COMPATIBILITY IDEOGRAPH-FA52;Lo;0;L;798D;;;;N;;;;; FA53;CJK COMPATIBILITY IDEOGRAPH-FA53;Lo;0;L;798E;;;;N;;;;; FA54;CJK COMPATIBILITY IDEOGRAPH-FA54;Lo;0;L;7A40;;;;N;;;;; FA55;CJK COMPATIBILITY IDEOGRAPH-FA55;Lo;0;L;7A81;;;;N;;;;; FA56;CJK COMPATIBILITY IDEOGRAPH-FA56;Lo;0;L;7BC0;;;;N;;;;; FA57;CJK COMPATIBILITY IDEOGRAPH-FA57;Lo;0;L;7DF4;;;;N;;;;; FA58;CJK COMPATIBILITY IDEOGRAPH-FA58;Lo;0;L;7E09;;;;N;;;;; FA59;CJK COMPATIBILITY IDEOGRAPH-FA59;Lo;0;L;7E41;;;;N;;;;; FA5A;CJK COMPATIBILITY IDEOGRAPH-FA5A;Lo;0;L;7F72;;;;N;;;;; FA5B;CJK COMPATIBILITY IDEOGRAPH-FA5B;Lo;0;L;8005;;;;N;;;;; FA5C;CJK COMPATIBILITY IDEOGRAPH-FA5C;Lo;0;L;81ED;;;;N;;;;; FA5D;CJK COMPATIBILITY IDEOGRAPH-FA5D;Lo;0;L;8279;;;;N;;;;; FA5E;CJK COMPATIBILITY IDEOGRAPH-FA5E;Lo;0;L;8279;;;;N;;;;; FA5F;CJK COMPATIBILITY IDEOGRAPH-FA5F;Lo;0;L;8457;;;;N;;;;; FA60;CJK COMPATIBILITY IDEOGRAPH-FA60;Lo;0;L;8910;;;;N;;;;; FA61;CJK COMPATIBILITY IDEOGRAPH-FA61;Lo;0;L;8996;;;;N;;;;; FA62;CJK COMPATIBILITY IDEOGRAPH-FA62;Lo;0;L;8B01;;;;N;;;;; FA63;CJK COMPATIBILITY IDEOGRAPH-FA63;Lo;0;L;8B39;;;;N;;;;; FA64;CJK COMPATIBILITY IDEOGRAPH-FA64;Lo;0;L;8CD3;;;;N;;;;; FA65;CJK COMPATIBILITY IDEOGRAPH-FA65;Lo;0;L;8D08;;;;N;;;;; FA66;CJK COMPATIBILITY IDEOGRAPH-FA66;Lo;0;L;8FB6;;;;N;;;;; FA67;CJK COMPATIBILITY IDEOGRAPH-FA67;Lo;0;L;9038;;;;N;;;;; FA68;CJK COMPATIBILITY IDEOGRAPH-FA68;Lo;0;L;96E3;;;;N;;;;; FA69;CJK COMPATIBILITY IDEOGRAPH-FA69;Lo;0;L;97FF;;;;N;;;;; FA6A;CJK COMPATIBILITY IDEOGRAPH-FA6A;Lo;0;L;983B;;;;N;;;;; FA6B;CJK COMPATIBILITY IDEOGRAPH-FA6B;Lo;0;L;6075;;;;N;;;;; FA6C;CJK COMPATIBILITY IDEOGRAPH-FA6C;Lo;0;L;242EE;;;;N;;;;; FA6D;CJK COMPATIBILITY IDEOGRAPH-FA6D;Lo;0;L;8218;;;;N;;;;; FA70;CJK COMPATIBILITY IDEOGRAPH-FA70;Lo;0;L;4E26;;;;N;;;;; FA71;CJK COMPATIBILITY IDEOGRAPH-FA71;Lo;0;L;51B5;;;;N;;;;; FA72;CJK COMPATIBILITY IDEOGRAPH-FA72;Lo;0;L;5168;;;;N;;;;; FA73;CJK COMPATIBILITY IDEOGRAPH-FA73;Lo;0;L;4F80;;;;N;;;;; FA74;CJK COMPATIBILITY IDEOGRAPH-FA74;Lo;0;L;5145;;;;N;;;;; FA75;CJK COMPATIBILITY IDEOGRAPH-FA75;Lo;0;L;5180;;;;N;;;;; FA76;CJK COMPATIBILITY IDEOGRAPH-FA76;Lo;0;L;52C7;;;;N;;;;; FA77;CJK COMPATIBILITY IDEOGRAPH-FA77;Lo;0;L;52FA;;;;N;;;;; FA78;CJK COMPATIBILITY IDEOGRAPH-FA78;Lo;0;L;559D;;;;N;;;;; FA79;CJK COMPATIBILITY IDEOGRAPH-FA79;Lo;0;L;5555;;;;N;;;;; FA7A;CJK COMPATIBILITY IDEOGRAPH-FA7A;Lo;0;L;5599;;;;N;;;;; FA7B;CJK COMPATIBILITY IDEOGRAPH-FA7B;Lo;0;L;55E2;;;;N;;;;; FA7C;CJK COMPATIBILITY IDEOGRAPH-FA7C;Lo;0;L;585A;;;;N;;;;; FA7D;CJK COMPATIBILITY IDEOGRAPH-FA7D;Lo;0;L;58B3;;;;N;;;;; FA7E;CJK COMPATIBILITY IDEOGRAPH-FA7E;Lo;0;L;5944;;;;N;;;;; FA7F;CJK COMPATIBILITY IDEOGRAPH-FA7F;Lo;0;L;5954;;;;N;;;;; FA80;CJK COMPATIBILITY IDEOGRAPH-FA80;Lo;0;L;5A62;;;;N;;;;; FA81;CJK COMPATIBILITY IDEOGRAPH-FA81;Lo;0;L;5B28;;;;N;;;;; FA82;CJK COMPATIBILITY IDEOGRAPH-FA82;Lo;0;L;5ED2;;;;N;;;;; FA83;CJK COMPATIBILITY IDEOGRAPH-FA83;Lo;0;L;5ED9;;;;N;;;;; FA84;CJK COMPATIBILITY IDEOGRAPH-FA84;Lo;0;L;5F69;;;;N;;;;; FA85;CJK COMPATIBILITY IDEOGRAPH-FA85;Lo;0;L;5FAD;;;;N;;;;; FA86;CJK COMPATIBILITY IDEOGRAPH-FA86;Lo;0;L;60D8;;;;N;;;;; FA87;CJK COMPATIBILITY IDEOGRAPH-FA87;Lo;0;L;614E;;;;N;;;;; FA88;CJK COMPATIBILITY IDEOGRAPH-FA88;Lo;0;L;6108;;;;N;;;;; FA89;CJK COMPATIBILITY IDEOGRAPH-FA89;Lo;0;L;618E;;;;N;;;;; FA8A;CJK COMPATIBILITY IDEOGRAPH-FA8A;Lo;0;L;6160;;;;N;;;;; FA8B;CJK COMPATIBILITY IDEOGRAPH-FA8B;Lo;0;L;61F2;;;;N;;;;; FA8C;CJK COMPATIBILITY IDEOGRAPH-FA8C;Lo;0;L;6234;;;;N;;;;; FA8D;CJK COMPATIBILITY IDEOGRAPH-FA8D;Lo;0;L;63C4;;;;N;;;;; FA8E;CJK COMPATIBILITY IDEOGRAPH-FA8E;Lo;0;L;641C;;;;N;;;;; FA8F;CJK COMPATIBILITY IDEOGRAPH-FA8F;Lo;0;L;6452;;;;N;;;;; FA90;CJK COMPATIBILITY IDEOGRAPH-FA90;Lo;0;L;6556;;;;N;;;;; FA91;CJK COMPATIBILITY IDEOGRAPH-FA91;Lo;0;L;6674;;;;N;;;;; FA92;CJK COMPATIBILITY IDEOGRAPH-FA92;Lo;0;L;6717;;;;N;;;;; FA93;CJK COMPATIBILITY IDEOGRAPH-FA93;Lo;0;L;671B;;;;N;;;;; FA94;CJK COMPATIBILITY IDEOGRAPH-FA94;Lo;0;L;6756;;;;N;;;;; FA95;CJK COMPATIBILITY IDEOGRAPH-FA95;Lo;0;L;6B79;;;;N;;;;; FA96;CJK COMPATIBILITY IDEOGRAPH-FA96;Lo;0;L;6BBA;;;;N;;;;; FA97;CJK COMPATIBILITY IDEOGRAPH-FA97;Lo;0;L;6D41;;;;N;;;;; FA98;CJK COMPATIBILITY IDEOGRAPH-FA98;Lo;0;L;6EDB;;;;N;;;;; FA99;CJK COMPATIBILITY IDEOGRAPH-FA99;Lo;0;L;6ECB;;;;N;;;;; FA9A;CJK COMPATIBILITY IDEOGRAPH-FA9A;Lo;0;L;6F22;;;;N;;;;; FA9B;CJK COMPATIBILITY IDEOGRAPH-FA9B;Lo;0;L;701E;;;;N;;;;; FA9C;CJK COMPATIBILITY IDEOGRAPH-FA9C;Lo;0;L;716E;;;;N;;;;; FA9D;CJK COMPATIBILITY IDEOGRAPH-FA9D;Lo;0;L;77A7;;;;N;;;;; FA9E;CJK COMPATIBILITY IDEOGRAPH-FA9E;Lo;0;L;7235;;;;N;;;;; FA9F;CJK COMPATIBILITY IDEOGRAPH-FA9F;Lo;0;L;72AF;;;;N;;;;; FAA0;CJK COMPATIBILITY IDEOGRAPH-FAA0;Lo;0;L;732A;;;;N;;;;; FAA1;CJK COMPATIBILITY IDEOGRAPH-FAA1;Lo;0;L;7471;;;;N;;;;; FAA2;CJK COMPATIBILITY IDEOGRAPH-FAA2;Lo;0;L;7506;;;;N;;;;; FAA3;CJK COMPATIBILITY IDEOGRAPH-FAA3;Lo;0;L;753B;;;;N;;;;; FAA4;CJK COMPATIBILITY IDEOGRAPH-FAA4;Lo;0;L;761D;;;;N;;;;; FAA5;CJK COMPATIBILITY IDEOGRAPH-FAA5;Lo;0;L;761F;;;;N;;;;; FAA6;CJK COMPATIBILITY IDEOGRAPH-FAA6;Lo;0;L;76CA;;;;N;;;;; FAA7;CJK COMPATIBILITY IDEOGRAPH-FAA7;Lo;0;L;76DB;;;;N;;;;; FAA8;CJK COMPATIBILITY IDEOGRAPH-FAA8;Lo;0;L;76F4;;;;N;;;;; FAA9;CJK COMPATIBILITY IDEOGRAPH-FAA9;Lo;0;L;774A;;;;N;;;;; FAAA;CJK COMPATIBILITY IDEOGRAPH-FAAA;Lo;0;L;7740;;;;N;;;;; FAAB;CJK COMPATIBILITY IDEOGRAPH-FAAB;Lo;0;L;78CC;;;;N;;;;; FAAC;CJK COMPATIBILITY IDEOGRAPH-FAAC;Lo;0;L;7AB1;;;;N;;;;; FAAD;CJK COMPATIBILITY IDEOGRAPH-FAAD;Lo;0;L;7BC0;;;;N;;;;; FAAE;CJK COMPATIBILITY IDEOGRAPH-FAAE;Lo;0;L;7C7B;;;;N;;;;; FAAF;CJK COMPATIBILITY IDEOGRAPH-FAAF;Lo;0;L;7D5B;;;;N;;;;; FAB0;CJK COMPATIBILITY IDEOGRAPH-FAB0;Lo;0;L;7DF4;;;;N;;;;; FAB1;CJK COMPATIBILITY IDEOGRAPH-FAB1;Lo;0;L;7F3E;;;;N;;;;; FAB2;CJK COMPATIBILITY IDEOGRAPH-FAB2;Lo;0;L;8005;;;;N;;;;; FAB3;CJK COMPATIBILITY IDEOGRAPH-FAB3;Lo;0;L;8352;;;;N;;;;; FAB4;CJK COMPATIBILITY IDEOGRAPH-FAB4;Lo;0;L;83EF;;;;N;;;;; FAB5;CJK COMPATIBILITY IDEOGRAPH-FAB5;Lo;0;L;8779;;;;N;;;;; FAB6;CJK COMPATIBILITY IDEOGRAPH-FAB6;Lo;0;L;8941;;;;N;;;;; FAB7;CJK COMPATIBILITY IDEOGRAPH-FAB7;Lo;0;L;8986;;;;N;;;;; FAB8;CJK COMPATIBILITY IDEOGRAPH-FAB8;Lo;0;L;8996;;;;N;;;;; FAB9;CJK COMPATIBILITY IDEOGRAPH-FAB9;Lo;0;L;8ABF;;;;N;;;;; FABA;CJK COMPATIBILITY IDEOGRAPH-FABA;Lo;0;L;8AF8;;;;N;;;;; FABB;CJK COMPATIBILITY IDEOGRAPH-FABB;Lo;0;L;8ACB;;;;N;;;;; FABC;CJK COMPATIBILITY IDEOGRAPH-FABC;Lo;0;L;8B01;;;;N;;;;; FABD;CJK COMPATIBILITY IDEOGRAPH-FABD;Lo;0;L;8AFE;;;;N;;;;; FABE;CJK COMPATIBILITY IDEOGRAPH-FABE;Lo;0;L;8AED;;;;N;;;;; FABF;CJK COMPATIBILITY IDEOGRAPH-FABF;Lo;0;L;8B39;;;;N;;;;; FAC0;CJK COMPATIBILITY IDEOGRAPH-FAC0;Lo;0;L;8B8A;;;;N;;;;; FAC1;CJK COMPATIBILITY IDEOGRAPH-FAC1;Lo;0;L;8D08;;;;N;;;;; FAC2;CJK COMPATIBILITY IDEOGRAPH-FAC2;Lo;0;L;8F38;;;;N;;;;; FAC3;CJK COMPATIBILITY IDEOGRAPH-FAC3;Lo;0;L;9072;;;;N;;;;; FAC4;CJK COMPATIBILITY IDEOGRAPH-FAC4;Lo;0;L;9199;;;;N;;;;; FAC5;CJK COMPATIBILITY IDEOGRAPH-FAC5;Lo;0;L;9276;;;;N;;;;; FAC6;CJK COMPATIBILITY IDEOGRAPH-FAC6;Lo;0;L;967C;;;;N;;;;; FAC7;CJK COMPATIBILITY IDEOGRAPH-FAC7;Lo;0;L;96E3;;;;N;;;;; FAC8;CJK COMPATIBILITY IDEOGRAPH-FAC8;Lo;0;L;9756;;;;N;;;;; FAC9;CJK COMPATIBILITY IDEOGRAPH-FAC9;Lo;0;L;97DB;;;;N;;;;; FACA;CJK COMPATIBILITY IDEOGRAPH-FACA;Lo;0;L;97FF;;;;N;;;;; FACB;CJK COMPATIBILITY IDEOGRAPH-FACB;Lo;0;L;980B;;;;N;;;;; FACC;CJK COMPATIBILITY IDEOGRAPH-FACC;Lo;0;L;983B;;;;N;;;;; FACD;CJK COMPATIBILITY IDEOGRAPH-FACD;Lo;0;L;9B12;;;;N;;;;; FACE;CJK COMPATIBILITY IDEOGRAPH-FACE;Lo;0;L;9F9C;;;;N;;;;; FACF;CJK COMPATIBILITY IDEOGRAPH-FACF;Lo;0;L;2284A;;;;N;;;;; FAD0;CJK COMPATIBILITY IDEOGRAPH-FAD0;Lo;0;L;22844;;;;N;;;;; FAD1;CJK COMPATIBILITY IDEOGRAPH-FAD1;Lo;0;L;233D5;;;;N;;;;; FAD2;CJK COMPATIBILITY IDEOGRAPH-FAD2;Lo;0;L;3B9D;;;;N;;;;; FAD3;CJK COMPATIBILITY IDEOGRAPH-FAD3;Lo;0;L;4018;;;;N;;;;; FAD4;CJK COMPATIBILITY IDEOGRAPH-FAD4;Lo;0;L;4039;;;;N;;;;; FAD5;CJK COMPATIBILITY IDEOGRAPH-FAD5;Lo;0;L;25249;;;;N;;;;; FAD6;CJK COMPATIBILITY IDEOGRAPH-FAD6;Lo;0;L;25CD0;;;;N;;;;; FAD7;CJK COMPATIBILITY IDEOGRAPH-FAD7;Lo;0;L;27ED3;;;;N;;;;; FAD8;CJK COMPATIBILITY IDEOGRAPH-FAD8;Lo;0;L;9F43;;;;N;;;;; FAD9;CJK COMPATIBILITY IDEOGRAPH-FAD9;Lo;0;L;9F8E;;;;N;;;;; FB00;LATIN SMALL LIGATURE FF;Ll;0;L; 0066 0066;;;;N;;;;; FB01;LATIN SMALL LIGATURE FI;Ll;0;L; 0066 0069;;;;N;;;;; FB02;LATIN SMALL LIGATURE FL;Ll;0;L; 0066 006C;;;;N;;;;; FB03;LATIN SMALL LIGATURE FFI;Ll;0;L; 0066 0066 0069;;;;N;;;;; FB04;LATIN SMALL LIGATURE FFL;Ll;0;L; 0066 0066 006C;;;;N;;;;; FB05;LATIN SMALL LIGATURE LONG S T;Ll;0;L; 017F 0074;;;;N;;;;; FB06;LATIN SMALL LIGATURE ST;Ll;0;L; 0073 0074;;;;N;;;;; FB13;ARMENIAN SMALL LIGATURE MEN NOW;Ll;0;L; 0574 0576;;;;N;;;;; FB14;ARMENIAN SMALL LIGATURE MEN ECH;Ll;0;L; 0574 0565;;;;N;;;;; FB15;ARMENIAN SMALL LIGATURE MEN INI;Ll;0;L; 0574 056B;;;;N;;;;; FB16;ARMENIAN SMALL LIGATURE VEW NOW;Ll;0;L; 057E 0576;;;;N;;;;; FB17;ARMENIAN SMALL LIGATURE MEN XEH;Ll;0;L; 0574 056D;;;;N;;;;; FB1D;HEBREW LETTER YOD WITH HIRIQ;Lo;0;R;05D9 05B4;;;;N;;;;; FB1E;HEBREW POINT JUDEO-SPANISH VARIKA;Mn;26;NSM;;;;;N;HEBREW POINT VARIKA;;;; FB1F;HEBREW LIGATURE YIDDISH YOD YOD PATAH;Lo;0;R;05F2 05B7;;;;N;;;;; FB20;HEBREW LETTER ALTERNATIVE AYIN;Lo;0;R; 05E2;;;;N;;;;; FB21;HEBREW LETTER WIDE ALEF;Lo;0;R; 05D0;;;;N;;;;; FB22;HEBREW LETTER WIDE DALET;Lo;0;R; 05D3;;;;N;;;;; FB23;HEBREW LETTER WIDE HE;Lo;0;R; 05D4;;;;N;;;;; FB24;HEBREW LETTER WIDE KAF;Lo;0;R; 05DB;;;;N;;;;; FB25;HEBREW LETTER WIDE LAMED;Lo;0;R; 05DC;;;;N;;;;; FB26;HEBREW LETTER WIDE FINAL MEM;Lo;0;R; 05DD;;;;N;;;;; FB27;HEBREW LETTER WIDE RESH;Lo;0;R; 05E8;;;;N;;;;; FB28;HEBREW LETTER WIDE TAV;Lo;0;R; 05EA;;;;N;;;;; FB29;HEBREW LETTER ALTERNATIVE PLUS SIGN;Sm;0;ES; 002B;;;;N;;;;; FB2A;HEBREW LETTER SHIN WITH SHIN DOT;Lo;0;R;05E9 05C1;;;;N;;;;; FB2B;HEBREW LETTER SHIN WITH SIN DOT;Lo;0;R;05E9 05C2;;;;N;;;;; FB2C;HEBREW LETTER SHIN WITH DAGESH AND SHIN DOT;Lo;0;R;FB49 05C1;;;;N;;;;; FB2D;HEBREW LETTER SHIN WITH DAGESH AND SIN DOT;Lo;0;R;FB49 05C2;;;;N;;;;; FB2E;HEBREW LETTER ALEF WITH PATAH;Lo;0;R;05D0 05B7;;;;N;;;;; FB2F;HEBREW LETTER ALEF WITH QAMATS;Lo;0;R;05D0 05B8;;;;N;;;;; FB30;HEBREW LETTER ALEF WITH MAPIQ;Lo;0;R;05D0 05BC;;;;N;;;;; FB31;HEBREW LETTER BET WITH DAGESH;Lo;0;R;05D1 05BC;;;;N;;;;; FB32;HEBREW LETTER GIMEL WITH DAGESH;Lo;0;R;05D2 05BC;;;;N;;;;; FB33;HEBREW LETTER DALET WITH DAGESH;Lo;0;R;05D3 05BC;;;;N;;;;; FB34;HEBREW LETTER HE WITH MAPIQ;Lo;0;R;05D4 05BC;;;;N;;;;; FB35;HEBREW LETTER VAV WITH DAGESH;Lo;0;R;05D5 05BC;;;;N;;;;; FB36;HEBREW LETTER ZAYIN WITH DAGESH;Lo;0;R;05D6 05BC;;;;N;;;;; FB38;HEBREW LETTER TET WITH DAGESH;Lo;0;R;05D8 05BC;;;;N;;;;; FB39;HEBREW LETTER YOD WITH DAGESH;Lo;0;R;05D9 05BC;;;;N;;;;; FB3A;HEBREW LETTER FINAL KAF WITH DAGESH;Lo;0;R;05DA 05BC;;;;N;;;;; FB3B;HEBREW LETTER KAF WITH DAGESH;Lo;0;R;05DB 05BC;;;;N;;;;; FB3C;HEBREW LETTER LAMED WITH DAGESH;Lo;0;R;05DC 05BC;;;;N;;;;; FB3E;HEBREW LETTER MEM WITH DAGESH;Lo;0;R;05DE 05BC;;;;N;;;;; FB40;HEBREW LETTER NUN WITH DAGESH;Lo;0;R;05E0 05BC;;;;N;;;;; FB41;HEBREW LETTER SAMEKH WITH DAGESH;Lo;0;R;05E1 05BC;;;;N;;;;; FB43;HEBREW LETTER FINAL PE WITH DAGESH;Lo;0;R;05E3 05BC;;;;N;;;;; FB44;HEBREW LETTER PE WITH DAGESH;Lo;0;R;05E4 05BC;;;;N;;;;; FB46;HEBREW LETTER TSADI WITH DAGESH;Lo;0;R;05E6 05BC;;;;N;;;;; FB47;HEBREW LETTER QOF WITH DAGESH;Lo;0;R;05E7 05BC;;;;N;;;;; FB48;HEBREW LETTER RESH WITH DAGESH;Lo;0;R;05E8 05BC;;;;N;;;;; FB49;HEBREW LETTER SHIN WITH DAGESH;Lo;0;R;05E9 05BC;;;;N;;;;; FB4A;HEBREW LETTER TAV WITH DAGESH;Lo;0;R;05EA 05BC;;;;N;;;;; FB4B;HEBREW LETTER VAV WITH HOLAM;Lo;0;R;05D5 05B9;;;;N;;;;; FB4C;HEBREW LETTER BET WITH RAFE;Lo;0;R;05D1 05BF;;;;N;;;;; FB4D;HEBREW LETTER KAF WITH RAFE;Lo;0;R;05DB 05BF;;;;N;;;;; FB4E;HEBREW LETTER PE WITH RAFE;Lo;0;R;05E4 05BF;;;;N;;;;; FB4F;HEBREW LIGATURE ALEF LAMED;Lo;0;R; 05D0 05DC;;;;N;;;;; FB50;ARABIC LETTER ALEF WASLA ISOLATED FORM;Lo;0;AL; 0671;;;;N;;;;; FB51;ARABIC LETTER ALEF WASLA FINAL FORM;Lo;0;AL; 0671;;;;N;;;;; FB52;ARABIC LETTER BEEH ISOLATED FORM;Lo;0;AL; 067B;;;;N;;;;; FB53;ARABIC LETTER BEEH FINAL FORM;Lo;0;AL; 067B;;;;N;;;;; FB54;ARABIC LETTER BEEH INITIAL FORM;Lo;0;AL; 067B;;;;N;;;;; FB55;ARABIC LETTER BEEH MEDIAL FORM;Lo;0;AL; 067B;;;;N;;;;; FB56;ARABIC LETTER PEH ISOLATED FORM;Lo;0;AL; 067E;;;;N;;;;; FB57;ARABIC LETTER PEH FINAL FORM;Lo;0;AL; 067E;;;;N;;;;; FB58;ARABIC LETTER PEH INITIAL FORM;Lo;0;AL; 067E;;;;N;;;;; FB59;ARABIC LETTER PEH MEDIAL FORM;Lo;0;AL; 067E;;;;N;;;;; FB5A;ARABIC LETTER BEHEH ISOLATED FORM;Lo;0;AL; 0680;;;;N;;;;; FB5B;ARABIC LETTER BEHEH FINAL FORM;Lo;0;AL; 0680;;;;N;;;;; FB5C;ARABIC LETTER BEHEH INITIAL FORM;Lo;0;AL; 0680;;;;N;;;;; FB5D;ARABIC LETTER BEHEH MEDIAL FORM;Lo;0;AL; 0680;;;;N;;;;; FB5E;ARABIC LETTER TTEHEH ISOLATED FORM;Lo;0;AL; 067A;;;;N;;;;; FB5F;ARABIC LETTER TTEHEH FINAL FORM;Lo;0;AL; 067A;;;;N;;;;; FB60;ARABIC LETTER TTEHEH INITIAL FORM;Lo;0;AL; 067A;;;;N;;;;; FB61;ARABIC LETTER TTEHEH MEDIAL FORM;Lo;0;AL; 067A;;;;N;;;;; FB62;ARABIC LETTER TEHEH ISOLATED FORM;Lo;0;AL; 067F;;;;N;;;;; FB63;ARABIC LETTER TEHEH FINAL FORM;Lo;0;AL; 067F;;;;N;;;;; FB64;ARABIC LETTER TEHEH INITIAL FORM;Lo;0;AL; 067F;;;;N;;;;; FB65;ARABIC LETTER TEHEH MEDIAL FORM;Lo;0;AL; 067F;;;;N;;;;; FB66;ARABIC LETTER TTEH ISOLATED FORM;Lo;0;AL; 0679;;;;N;;;;; FB67;ARABIC LETTER TTEH FINAL FORM;Lo;0;AL; 0679;;;;N;;;;; FB68;ARABIC LETTER TTEH INITIAL FORM;Lo;0;AL; 0679;;;;N;;;;; FB69;ARABIC LETTER TTEH MEDIAL FORM;Lo;0;AL; 0679;;;;N;;;;; FB6A;ARABIC LETTER VEH ISOLATED FORM;Lo;0;AL; 06A4;;;;N;;;;; FB6B;ARABIC LETTER VEH FINAL FORM;Lo;0;AL; 06A4;;;;N;;;;; FB6C;ARABIC LETTER VEH INITIAL FORM;Lo;0;AL; 06A4;;;;N;;;;; FB6D;ARABIC LETTER VEH MEDIAL FORM;Lo;0;AL; 06A4;;;;N;;;;; FB6E;ARABIC LETTER PEHEH ISOLATED FORM;Lo;0;AL; 06A6;;;;N;;;;; FB6F;ARABIC LETTER PEHEH FINAL FORM;Lo;0;AL; 06A6;;;;N;;;;; FB70;ARABIC LETTER PEHEH INITIAL FORM;Lo;0;AL; 06A6;;;;N;;;;; FB71;ARABIC LETTER PEHEH MEDIAL FORM;Lo;0;AL; 06A6;;;;N;;;;; FB72;ARABIC LETTER DYEH ISOLATED FORM;Lo;0;AL; 0684;;;;N;;;;; FB73;ARABIC LETTER DYEH FINAL FORM;Lo;0;AL; 0684;;;;N;;;;; FB74;ARABIC LETTER DYEH INITIAL FORM;Lo;0;AL; 0684;;;;N;;;;; FB75;ARABIC LETTER DYEH MEDIAL FORM;Lo;0;AL; 0684;;;;N;;;;; FB76;ARABIC LETTER NYEH ISOLATED FORM;Lo;0;AL; 0683;;;;N;;;;; FB77;ARABIC LETTER NYEH FINAL FORM;Lo;0;AL; 0683;;;;N;;;;; FB78;ARABIC LETTER NYEH INITIAL FORM;Lo;0;AL; 0683;;;;N;;;;; FB79;ARABIC LETTER NYEH MEDIAL FORM;Lo;0;AL; 0683;;;;N;;;;; FB7A;ARABIC LETTER TCHEH ISOLATED FORM;Lo;0;AL; 0686;;;;N;;;;; FB7B;ARABIC LETTER TCHEH FINAL FORM;Lo;0;AL; 0686;;;;N;;;;; FB7C;ARABIC LETTER TCHEH INITIAL FORM;Lo;0;AL; 0686;;;;N;;;;; FB7D;ARABIC LETTER TCHEH MEDIAL FORM;Lo;0;AL; 0686;;;;N;;;;; FB7E;ARABIC LETTER TCHEHEH ISOLATED FORM;Lo;0;AL; 0687;;;;N;;;;; FB7F;ARABIC LETTER TCHEHEH FINAL FORM;Lo;0;AL; 0687;;;;N;;;;; FB80;ARABIC LETTER TCHEHEH INITIAL FORM;Lo;0;AL; 0687;;;;N;;;;; FB81;ARABIC LETTER TCHEHEH MEDIAL FORM;Lo;0;AL; 0687;;;;N;;;;; FB82;ARABIC LETTER DDAHAL ISOLATED FORM;Lo;0;AL; 068D;;;;N;;;;; FB83;ARABIC LETTER DDAHAL FINAL FORM;Lo;0;AL; 068D;;;;N;;;;; FB84;ARABIC LETTER DAHAL ISOLATED FORM;Lo;0;AL; 068C;;;;N;;;;; FB85;ARABIC LETTER DAHAL FINAL FORM;Lo;0;AL; 068C;;;;N;;;;; FB86;ARABIC LETTER DUL ISOLATED FORM;Lo;0;AL; 068E;;;;N;;;;; FB87;ARABIC LETTER DUL FINAL FORM;Lo;0;AL; 068E;;;;N;;;;; FB88;ARABIC LETTER DDAL ISOLATED FORM;Lo;0;AL; 0688;;;;N;;;;; FB89;ARABIC LETTER DDAL FINAL FORM;Lo;0;AL; 0688;;;;N;;;;; FB8A;ARABIC LETTER JEH ISOLATED FORM;Lo;0;AL; 0698;;;;N;;;;; FB8B;ARABIC LETTER JEH FINAL FORM;Lo;0;AL; 0698;;;;N;;;;; FB8C;ARABIC LETTER RREH ISOLATED FORM;Lo;0;AL; 0691;;;;N;;;;; FB8D;ARABIC LETTER RREH FINAL FORM;Lo;0;AL; 0691;;;;N;;;;; FB8E;ARABIC LETTER KEHEH ISOLATED FORM;Lo;0;AL; 06A9;;;;N;;;;; FB8F;ARABIC LETTER KEHEH FINAL FORM;Lo;0;AL; 06A9;;;;N;;;;; FB90;ARABIC LETTER KEHEH INITIAL FORM;Lo;0;AL; 06A9;;;;N;;;;; FB91;ARABIC LETTER KEHEH MEDIAL FORM;Lo;0;AL; 06A9;;;;N;;;;; FB92;ARABIC LETTER GAF ISOLATED FORM;Lo;0;AL; 06AF;;;;N;;;;; FB93;ARABIC LETTER GAF FINAL FORM;Lo;0;AL; 06AF;;;;N;;;;; FB94;ARABIC LETTER GAF INITIAL FORM;Lo;0;AL; 06AF;;;;N;;;;; FB95;ARABIC LETTER GAF MEDIAL FORM;Lo;0;AL; 06AF;;;;N;;;;; FB96;ARABIC LETTER GUEH ISOLATED FORM;Lo;0;AL; 06B3;;;;N;;;;; FB97;ARABIC LETTER GUEH FINAL FORM;Lo;0;AL; 06B3;;;;N;;;;; FB98;ARABIC LETTER GUEH INITIAL FORM;Lo;0;AL; 06B3;;;;N;;;;; FB99;ARABIC LETTER GUEH MEDIAL FORM;Lo;0;AL; 06B3;;;;N;;;;; FB9A;ARABIC LETTER NGOEH ISOLATED FORM;Lo;0;AL; 06B1;;;;N;;;;; FB9B;ARABIC LETTER NGOEH FINAL FORM;Lo;0;AL; 06B1;;;;N;;;;; FB9C;ARABIC LETTER NGOEH INITIAL FORM;Lo;0;AL; 06B1;;;;N;;;;; FB9D;ARABIC LETTER NGOEH MEDIAL FORM;Lo;0;AL; 06B1;;;;N;;;;; FB9E;ARABIC LETTER NOON GHUNNA ISOLATED FORM;Lo;0;AL; 06BA;;;;N;;;;; FB9F;ARABIC LETTER NOON GHUNNA FINAL FORM;Lo;0;AL; 06BA;;;;N;;;;; FBA0;ARABIC LETTER RNOON ISOLATED FORM;Lo;0;AL; 06BB;;;;N;;;;; FBA1;ARABIC LETTER RNOON FINAL FORM;Lo;0;AL; 06BB;;;;N;;;;; FBA2;ARABIC LETTER RNOON INITIAL FORM;Lo;0;AL; 06BB;;;;N;;;;; FBA3;ARABIC LETTER RNOON MEDIAL FORM;Lo;0;AL; 06BB;;;;N;;;;; FBA4;ARABIC LETTER HEH WITH YEH ABOVE ISOLATED FORM;Lo;0;AL; 06C0;;;;N;;;;; FBA5;ARABIC LETTER HEH WITH YEH ABOVE FINAL FORM;Lo;0;AL; 06C0;;;;N;;;;; FBA6;ARABIC LETTER HEH GOAL ISOLATED FORM;Lo;0;AL; 06C1;;;;N;;;;; FBA7;ARABIC LETTER HEH GOAL FINAL FORM;Lo;0;AL; 06C1;;;;N;;;;; FBA8;ARABIC LETTER HEH GOAL INITIAL FORM;Lo;0;AL; 06C1;;;;N;;;;; FBA9;ARABIC LETTER HEH GOAL MEDIAL FORM;Lo;0;AL; 06C1;;;;N;;;;; FBAA;ARABIC LETTER HEH DOACHASHMEE ISOLATED FORM;Lo;0;AL; 06BE;;;;N;;;;; FBAB;ARABIC LETTER HEH DOACHASHMEE FINAL FORM;Lo;0;AL; 06BE;;;;N;;;;; FBAC;ARABIC LETTER HEH DOACHASHMEE INITIAL FORM;Lo;0;AL; 06BE;;;;N;;;;; FBAD;ARABIC LETTER HEH DOACHASHMEE MEDIAL FORM;Lo;0;AL; 06BE;;;;N;;;;; FBAE;ARABIC LETTER YEH BARREE ISOLATED FORM;Lo;0;AL; 06D2;;;;N;;;;; FBAF;ARABIC LETTER YEH BARREE FINAL FORM;Lo;0;AL; 06D2;;;;N;;;;; FBB0;ARABIC LETTER YEH BARREE WITH HAMZA ABOVE ISOLATED FORM;Lo;0;AL; 06D3;;;;N;;;;; FBB1;ARABIC LETTER YEH BARREE WITH HAMZA ABOVE FINAL FORM;Lo;0;AL; 06D3;;;;N;;;;; FBB2;ARABIC SYMBOL DOT ABOVE;Sk;0;AL;;;;;N;;;;; FBB3;ARABIC SYMBOL DOT BELOW;Sk;0;AL;;;;;N;;;;; FBB4;ARABIC SYMBOL TWO DOTS ABOVE;Sk;0;AL;;;;;N;;;;; FBB5;ARABIC SYMBOL TWO DOTS BELOW;Sk;0;AL;;;;;N;;;;; FBB6;ARABIC SYMBOL THREE DOTS ABOVE;Sk;0;AL;;;;;N;;;;; FBB7;ARABIC SYMBOL THREE DOTS BELOW;Sk;0;AL;;;;;N;;;;; FBB8;ARABIC SYMBOL THREE DOTS POINTING DOWNWARDS ABOVE;Sk;0;AL;;;;;N;;;;; FBB9;ARABIC SYMBOL THREE DOTS POINTING DOWNWARDS BELOW;Sk;0;AL;;;;;N;;;;; FBBA;ARABIC SYMBOL FOUR DOTS ABOVE;Sk;0;AL;;;;;N;;;;; FBBB;ARABIC SYMBOL FOUR DOTS BELOW;Sk;0;AL;;;;;N;;;;; FBBC;ARABIC SYMBOL DOUBLE VERTICAL BAR BELOW;Sk;0;AL;;;;;N;;;;; FBBD;ARABIC SYMBOL TWO DOTS VERTICALLY ABOVE;Sk;0;AL;;;;;N;;;;; FBBE;ARABIC SYMBOL TWO DOTS VERTICALLY BELOW;Sk;0;AL;;;;;N;;;;; FBBF;ARABIC SYMBOL RING;Sk;0;AL;;;;;N;;;;; FBC0;ARABIC SYMBOL SMALL TAH ABOVE;Sk;0;AL;;;;;N;;;;; FBC1;ARABIC SYMBOL SMALL TAH BELOW;Sk;0;AL;;;;;N;;;;; FBD3;ARABIC LETTER NG ISOLATED FORM;Lo;0;AL; 06AD;;;;N;;;;; FBD4;ARABIC LETTER NG FINAL FORM;Lo;0;AL; 06AD;;;;N;;;;; FBD5;ARABIC LETTER NG INITIAL FORM;Lo;0;AL; 06AD;;;;N;;;;; FBD6;ARABIC LETTER NG MEDIAL FORM;Lo;0;AL; 06AD;;;;N;;;;; FBD7;ARABIC LETTER U ISOLATED FORM;Lo;0;AL; 06C7;;;;N;;;;; FBD8;ARABIC LETTER U FINAL FORM;Lo;0;AL; 06C7;;;;N;;;;; FBD9;ARABIC LETTER OE ISOLATED FORM;Lo;0;AL; 06C6;;;;N;;;;; FBDA;ARABIC LETTER OE FINAL FORM;Lo;0;AL; 06C6;;;;N;;;;; FBDB;ARABIC LETTER YU ISOLATED FORM;Lo;0;AL; 06C8;;;;N;;;;; FBDC;ARABIC LETTER YU FINAL FORM;Lo;0;AL; 06C8;;;;N;;;;; FBDD;ARABIC LETTER U WITH HAMZA ABOVE ISOLATED FORM;Lo;0;AL; 0677;;;;N;;;;; FBDE;ARABIC LETTER VE ISOLATED FORM;Lo;0;AL; 06CB;;;;N;;;;; FBDF;ARABIC LETTER VE FINAL FORM;Lo;0;AL; 06CB;;;;N;;;;; FBE0;ARABIC LETTER KIRGHIZ OE ISOLATED FORM;Lo;0;AL; 06C5;;;;N;;;;; FBE1;ARABIC LETTER KIRGHIZ OE FINAL FORM;Lo;0;AL; 06C5;;;;N;;;;; FBE2;ARABIC LETTER KIRGHIZ YU ISOLATED FORM;Lo;0;AL; 06C9;;;;N;;;;; FBE3;ARABIC LETTER KIRGHIZ YU FINAL FORM;Lo;0;AL; 06C9;;;;N;;;;; FBE4;ARABIC LETTER E ISOLATED FORM;Lo;0;AL; 06D0;;;;N;;;;; FBE5;ARABIC LETTER E FINAL FORM;Lo;0;AL; 06D0;;;;N;;;;; FBE6;ARABIC LETTER E INITIAL FORM;Lo;0;AL; 06D0;;;;N;;;;; FBE7;ARABIC LETTER E MEDIAL FORM;Lo;0;AL; 06D0;;;;N;;;;; FBE8;ARABIC LETTER UIGHUR KAZAKH KIRGHIZ ALEF MAKSURA INITIAL FORM;Lo;0;AL; 0649;;;;N;;;;; FBE9;ARABIC LETTER UIGHUR KAZAKH KIRGHIZ ALEF MAKSURA MEDIAL FORM;Lo;0;AL; 0649;;;;N;;;;; FBEA;ARABIC LIGATURE YEH WITH HAMZA ABOVE WITH ALEF ISOLATED FORM;Lo;0;AL; 0626 0627;;;;N;;;;; FBEB;ARABIC LIGATURE YEH WITH HAMZA ABOVE WITH ALEF FINAL FORM;Lo;0;AL; 0626 0627;;;;N;;;;; FBEC;ARABIC LIGATURE YEH WITH HAMZA ABOVE WITH AE ISOLATED FORM;Lo;0;AL; 0626 06D5;;;;N;;;;; FBED;ARABIC LIGATURE YEH WITH HAMZA ABOVE WITH AE FINAL FORM;Lo;0;AL; 0626 06D5;;;;N;;;;; FBEE;ARABIC LIGATURE YEH WITH HAMZA ABOVE WITH WAW ISOLATED FORM;Lo;0;AL; 0626 0648;;;;N;;;;; FBEF;ARABIC LIGATURE YEH WITH HAMZA ABOVE WITH WAW FINAL FORM;Lo;0;AL; 0626 0648;;;;N;;;;; FBF0;ARABIC LIGATURE YEH WITH HAMZA ABOVE WITH U ISOLATED FORM;Lo;0;AL; 0626 06C7;;;;N;;;;; FBF1;ARABIC LIGATURE YEH WITH HAMZA ABOVE WITH U FINAL FORM;Lo;0;AL; 0626 06C7;;;;N;;;;; FBF2;ARABIC LIGATURE YEH WITH HAMZA ABOVE WITH OE ISOLATED FORM;Lo;0;AL; 0626 06C6;;;;N;;;;; FBF3;ARABIC LIGATURE YEH WITH HAMZA ABOVE WITH OE FINAL FORM;Lo;0;AL; 0626 06C6;;;;N;;;;; FBF4;ARABIC LIGATURE YEH WITH HAMZA ABOVE WITH YU ISOLATED FORM;Lo;0;AL; 0626 06C8;;;;N;;;;; FBF5;ARABIC LIGATURE YEH WITH HAMZA ABOVE WITH YU FINAL FORM;Lo;0;AL; 0626 06C8;;;;N;;;;; FBF6;ARABIC LIGATURE YEH WITH HAMZA ABOVE WITH E ISOLATED FORM;Lo;0;AL; 0626 06D0;;;;N;;;;; FBF7;ARABIC LIGATURE YEH WITH HAMZA ABOVE WITH E FINAL FORM;Lo;0;AL; 0626 06D0;;;;N;;;;; FBF8;ARABIC LIGATURE YEH WITH HAMZA ABOVE WITH E INITIAL FORM;Lo;0;AL; 0626 06D0;;;;N;;;;; FBF9;ARABIC LIGATURE UIGHUR KIRGHIZ YEH WITH HAMZA ABOVE WITH ALEF MAKSURA ISOLATED FORM;Lo;0;AL; 0626 0649;;;;N;;;;; FBFA;ARABIC LIGATURE UIGHUR KIRGHIZ YEH WITH HAMZA ABOVE WITH ALEF MAKSURA FINAL FORM;Lo;0;AL; 0626 0649;;;;N;;;;; FBFB;ARABIC LIGATURE UIGHUR KIRGHIZ YEH WITH HAMZA ABOVE WITH ALEF MAKSURA INITIAL FORM;Lo;0;AL; 0626 0649;;;;N;;;;; FBFC;ARABIC LETTER FARSI YEH ISOLATED FORM;Lo;0;AL; 06CC;;;;N;;;;; FBFD;ARABIC LETTER FARSI YEH FINAL FORM;Lo;0;AL; 06CC;;;;N;;;;; FBFE;ARABIC LETTER FARSI YEH INITIAL FORM;Lo;0;AL; 06CC;;;;N;;;;; FBFF;ARABIC LETTER FARSI YEH MEDIAL FORM;Lo;0;AL; 06CC;;;;N;;;;; FC00;ARABIC LIGATURE YEH WITH HAMZA ABOVE WITH JEEM ISOLATED FORM;Lo;0;AL; 0626 062C;;;;N;;;;; FC01;ARABIC LIGATURE YEH WITH HAMZA ABOVE WITH HAH ISOLATED FORM;Lo;0;AL; 0626 062D;;;;N;;;;; FC02;ARABIC LIGATURE YEH WITH HAMZA ABOVE WITH MEEM ISOLATED FORM;Lo;0;AL; 0626 0645;;;;N;;;;; FC03;ARABIC LIGATURE YEH WITH HAMZA ABOVE WITH ALEF MAKSURA ISOLATED FORM;Lo;0;AL; 0626 0649;;;;N;;;;; FC04;ARABIC LIGATURE YEH WITH HAMZA ABOVE WITH YEH ISOLATED FORM;Lo;0;AL; 0626 064A;;;;N;;;;; FC05;ARABIC LIGATURE BEH WITH JEEM ISOLATED FORM;Lo;0;AL; 0628 062C;;;;N;;;;; FC06;ARABIC LIGATURE BEH WITH HAH ISOLATED FORM;Lo;0;AL; 0628 062D;;;;N;;;;; FC07;ARABIC LIGATURE BEH WITH KHAH ISOLATED FORM;Lo;0;AL; 0628 062E;;;;N;;;;; FC08;ARABIC LIGATURE BEH WITH MEEM ISOLATED FORM;Lo;0;AL; 0628 0645;;;;N;;;;; FC09;ARABIC LIGATURE BEH WITH ALEF MAKSURA ISOLATED FORM;Lo;0;AL; 0628 0649;;;;N;;;;; FC0A;ARABIC LIGATURE BEH WITH YEH ISOLATED FORM;Lo;0;AL; 0628 064A;;;;N;;;;; FC0B;ARABIC LIGATURE TEH WITH JEEM ISOLATED FORM;Lo;0;AL; 062A 062C;;;;N;;;;; FC0C;ARABIC LIGATURE TEH WITH HAH ISOLATED FORM;Lo;0;AL; 062A 062D;;;;N;;;;; FC0D;ARABIC LIGATURE TEH WITH KHAH ISOLATED FORM;Lo;0;AL; 062A 062E;;;;N;;;;; FC0E;ARABIC LIGATURE TEH WITH MEEM ISOLATED FORM;Lo;0;AL; 062A 0645;;;;N;;;;; FC0F;ARABIC LIGATURE TEH WITH ALEF MAKSURA ISOLATED FORM;Lo;0;AL; 062A 0649;;;;N;;;;; FC10;ARABIC LIGATURE TEH WITH YEH ISOLATED FORM;Lo;0;AL; 062A 064A;;;;N;;;;; FC11;ARABIC LIGATURE THEH WITH JEEM ISOLATED FORM;Lo;0;AL; 062B 062C;;;;N;;;;; FC12;ARABIC LIGATURE THEH WITH MEEM ISOLATED FORM;Lo;0;AL; 062B 0645;;;;N;;;;; FC13;ARABIC LIGATURE THEH WITH ALEF MAKSURA ISOLATED FORM;Lo;0;AL; 062B 0649;;;;N;;;;; FC14;ARABIC LIGATURE THEH WITH YEH ISOLATED FORM;Lo;0;AL; 062B 064A;;;;N;;;;; FC15;ARABIC LIGATURE JEEM WITH HAH ISOLATED FORM;Lo;0;AL; 062C 062D;;;;N;;;;; FC16;ARABIC LIGATURE JEEM WITH MEEM ISOLATED FORM;Lo;0;AL; 062C 0645;;;;N;;;;; FC17;ARABIC LIGATURE HAH WITH JEEM ISOLATED FORM;Lo;0;AL; 062D 062C;;;;N;;;;; FC18;ARABIC LIGATURE HAH WITH MEEM ISOLATED FORM;Lo;0;AL; 062D 0645;;;;N;;;;; FC19;ARABIC LIGATURE KHAH WITH JEEM ISOLATED FORM;Lo;0;AL; 062E 062C;;;;N;;;;; FC1A;ARABIC LIGATURE KHAH WITH HAH ISOLATED FORM;Lo;0;AL; 062E 062D;;;;N;;;;; FC1B;ARABIC LIGATURE KHAH WITH MEEM ISOLATED FORM;Lo;0;AL; 062E 0645;;;;N;;;;; FC1C;ARABIC LIGATURE SEEN WITH JEEM ISOLATED FORM;Lo;0;AL; 0633 062C;;;;N;;;;; FC1D;ARABIC LIGATURE SEEN WITH HAH ISOLATED FORM;Lo;0;AL; 0633 062D;;;;N;;;;; FC1E;ARABIC LIGATURE SEEN WITH KHAH ISOLATED FORM;Lo;0;AL; 0633 062E;;;;N;;;;; FC1F;ARABIC LIGATURE SEEN WITH MEEM ISOLATED FORM;Lo;0;AL; 0633 0645;;;;N;;;;; FC20;ARABIC LIGATURE SAD WITH HAH ISOLATED FORM;Lo;0;AL; 0635 062D;;;;N;;;;; FC21;ARABIC LIGATURE SAD WITH MEEM ISOLATED FORM;Lo;0;AL; 0635 0645;;;;N;;;;; FC22;ARABIC LIGATURE DAD WITH JEEM ISOLATED FORM;Lo;0;AL; 0636 062C;;;;N;;;;; FC23;ARABIC LIGATURE DAD WITH HAH ISOLATED FORM;Lo;0;AL; 0636 062D;;;;N;;;;; FC24;ARABIC LIGATURE DAD WITH KHAH ISOLATED FORM;Lo;0;AL; 0636 062E;;;;N;;;;; FC25;ARABIC LIGATURE DAD WITH MEEM ISOLATED FORM;Lo;0;AL; 0636 0645;;;;N;;;;; FC26;ARABIC LIGATURE TAH WITH HAH ISOLATED FORM;Lo;0;AL; 0637 062D;;;;N;;;;; FC27;ARABIC LIGATURE TAH WITH MEEM ISOLATED FORM;Lo;0;AL; 0637 0645;;;;N;;;;; FC28;ARABIC LIGATURE ZAH WITH MEEM ISOLATED FORM;Lo;0;AL; 0638 0645;;;;N;;;;; FC29;ARABIC LIGATURE AIN WITH JEEM ISOLATED FORM;Lo;0;AL; 0639 062C;;;;N;;;;; FC2A;ARABIC LIGATURE AIN WITH MEEM ISOLATED FORM;Lo;0;AL; 0639 0645;;;;N;;;;; FC2B;ARABIC LIGATURE GHAIN WITH JEEM ISOLATED FORM;Lo;0;AL; 063A 062C;;;;N;;;;; FC2C;ARABIC LIGATURE GHAIN WITH MEEM ISOLATED FORM;Lo;0;AL; 063A 0645;;;;N;;;;; FC2D;ARABIC LIGATURE FEH WITH JEEM ISOLATED FORM;Lo;0;AL; 0641 062C;;;;N;;;;; FC2E;ARABIC LIGATURE FEH WITH HAH ISOLATED FORM;Lo;0;AL; 0641 062D;;;;N;;;;; FC2F;ARABIC LIGATURE FEH WITH KHAH ISOLATED FORM;Lo;0;AL; 0641 062E;;;;N;;;;; FC30;ARABIC LIGATURE FEH WITH MEEM ISOLATED FORM;Lo;0;AL; 0641 0645;;;;N;;;;; FC31;ARABIC LIGATURE FEH WITH ALEF MAKSURA ISOLATED FORM;Lo;0;AL; 0641 0649;;;;N;;;;; FC32;ARABIC LIGATURE FEH WITH YEH ISOLATED FORM;Lo;0;AL; 0641 064A;;;;N;;;;; FC33;ARABIC LIGATURE QAF WITH HAH ISOLATED FORM;Lo;0;AL; 0642 062D;;;;N;;;;; FC34;ARABIC LIGATURE QAF WITH MEEM ISOLATED FORM;Lo;0;AL; 0642 0645;;;;N;;;;; FC35;ARABIC LIGATURE QAF WITH ALEF MAKSURA ISOLATED FORM;Lo;0;AL; 0642 0649;;;;N;;;;; FC36;ARABIC LIGATURE QAF WITH YEH ISOLATED FORM;Lo;0;AL; 0642 064A;;;;N;;;;; FC37;ARABIC LIGATURE KAF WITH ALEF ISOLATED FORM;Lo;0;AL; 0643 0627;;;;N;;;;; FC38;ARABIC LIGATURE KAF WITH JEEM ISOLATED FORM;Lo;0;AL; 0643 062C;;;;N;;;;; FC39;ARABIC LIGATURE KAF WITH HAH ISOLATED FORM;Lo;0;AL; 0643 062D;;;;N;;;;; FC3A;ARABIC LIGATURE KAF WITH KHAH ISOLATED FORM;Lo;0;AL; 0643 062E;;;;N;;;;; FC3B;ARABIC LIGATURE KAF WITH LAM ISOLATED FORM;Lo;0;AL; 0643 0644;;;;N;;;;; FC3C;ARABIC LIGATURE KAF WITH MEEM ISOLATED FORM;Lo;0;AL; 0643 0645;;;;N;;;;; FC3D;ARABIC LIGATURE KAF WITH ALEF MAKSURA ISOLATED FORM;Lo;0;AL; 0643 0649;;;;N;;;;; FC3E;ARABIC LIGATURE KAF WITH YEH ISOLATED FORM;Lo;0;AL; 0643 064A;;;;N;;;;; FC3F;ARABIC LIGATURE LAM WITH JEEM ISOLATED FORM;Lo;0;AL; 0644 062C;;;;N;;;;; FC40;ARABIC LIGATURE LAM WITH HAH ISOLATED FORM;Lo;0;AL; 0644 062D;;;;N;;;;; FC41;ARABIC LIGATURE LAM WITH KHAH ISOLATED FORM;Lo;0;AL; 0644 062E;;;;N;;;;; FC42;ARABIC LIGATURE LAM WITH MEEM ISOLATED FORM;Lo;0;AL; 0644 0645;;;;N;;;;; FC43;ARABIC LIGATURE LAM WITH ALEF MAKSURA ISOLATED FORM;Lo;0;AL; 0644 0649;;;;N;;;;; FC44;ARABIC LIGATURE LAM WITH YEH ISOLATED FORM;Lo;0;AL; 0644 064A;;;;N;;;;; FC45;ARABIC LIGATURE MEEM WITH JEEM ISOLATED FORM;Lo;0;AL; 0645 062C;;;;N;;;;; FC46;ARABIC LIGATURE MEEM WITH HAH ISOLATED FORM;Lo;0;AL; 0645 062D;;;;N;;;;; FC47;ARABIC LIGATURE MEEM WITH KHAH ISOLATED FORM;Lo;0;AL; 0645 062E;;;;N;;;;; FC48;ARABIC LIGATURE MEEM WITH MEEM ISOLATED FORM;Lo;0;AL; 0645 0645;;;;N;;;;; FC49;ARABIC LIGATURE MEEM WITH ALEF MAKSURA ISOLATED FORM;Lo;0;AL; 0645 0649;;;;N;;;;; FC4A;ARABIC LIGATURE MEEM WITH YEH ISOLATED FORM;Lo;0;AL; 0645 064A;;;;N;;;;; FC4B;ARABIC LIGATURE NOON WITH JEEM ISOLATED FORM;Lo;0;AL; 0646 062C;;;;N;;;;; FC4C;ARABIC LIGATURE NOON WITH HAH ISOLATED FORM;Lo;0;AL; 0646 062D;;;;N;;;;; FC4D;ARABIC LIGATURE NOON WITH KHAH ISOLATED FORM;Lo;0;AL; 0646 062E;;;;N;;;;; FC4E;ARABIC LIGATURE NOON WITH MEEM ISOLATED FORM;Lo;0;AL; 0646 0645;;;;N;;;;; FC4F;ARABIC LIGATURE NOON WITH ALEF MAKSURA ISOLATED FORM;Lo;0;AL; 0646 0649;;;;N;;;;; FC50;ARABIC LIGATURE NOON WITH YEH ISOLATED FORM;Lo;0;AL; 0646 064A;;;;N;;;;; FC51;ARABIC LIGATURE HEH WITH JEEM ISOLATED FORM;Lo;0;AL; 0647 062C;;;;N;;;;; FC52;ARABIC LIGATURE HEH WITH MEEM ISOLATED FORM;Lo;0;AL; 0647 0645;;;;N;;;;; FC53;ARABIC LIGATURE HEH WITH ALEF MAKSURA ISOLATED FORM;Lo;0;AL; 0647 0649;;;;N;;;;; FC54;ARABIC LIGATURE HEH WITH YEH ISOLATED FORM;Lo;0;AL; 0647 064A;;;;N;;;;; FC55;ARABIC LIGATURE YEH WITH JEEM ISOLATED FORM;Lo;0;AL; 064A 062C;;;;N;;;;; FC56;ARABIC LIGATURE YEH WITH HAH ISOLATED FORM;Lo;0;AL; 064A 062D;;;;N;;;;; FC57;ARABIC LIGATURE YEH WITH KHAH ISOLATED FORM;Lo;0;AL; 064A 062E;;;;N;;;;; FC58;ARABIC LIGATURE YEH WITH MEEM ISOLATED FORM;Lo;0;AL; 064A 0645;;;;N;;;;; FC59;ARABIC LIGATURE YEH WITH ALEF MAKSURA ISOLATED FORM;Lo;0;AL; 064A 0649;;;;N;;;;; FC5A;ARABIC LIGATURE YEH WITH YEH ISOLATED FORM;Lo;0;AL; 064A 064A;;;;N;;;;; FC5B;ARABIC LIGATURE THAL WITH SUPERSCRIPT ALEF ISOLATED FORM;Lo;0;AL; 0630 0670;;;;N;;;;; FC5C;ARABIC LIGATURE REH WITH SUPERSCRIPT ALEF ISOLATED FORM;Lo;0;AL; 0631 0670;;;;N;;;;; FC5D;ARABIC LIGATURE ALEF MAKSURA WITH SUPERSCRIPT ALEF ISOLATED FORM;Lo;0;AL; 0649 0670;;;;N;;;;; FC5E;ARABIC LIGATURE SHADDA WITH DAMMATAN ISOLATED FORM;Lo;0;AL; 0020 064C 0651;;;;N;;;;; FC5F;ARABIC LIGATURE SHADDA WITH KASRATAN ISOLATED FORM;Lo;0;AL; 0020 064D 0651;;;;N;;;;; FC60;ARABIC LIGATURE SHADDA WITH FATHA ISOLATED FORM;Lo;0;AL; 0020 064E 0651;;;;N;;;;; FC61;ARABIC LIGATURE SHADDA WITH DAMMA ISOLATED FORM;Lo;0;AL; 0020 064F 0651;;;;N;;;;; FC62;ARABIC LIGATURE SHADDA WITH KASRA ISOLATED FORM;Lo;0;AL; 0020 0650 0651;;;;N;;;;; FC63;ARABIC LIGATURE SHADDA WITH SUPERSCRIPT ALEF ISOLATED FORM;Lo;0;AL; 0020 0651 0670;;;;N;;;;; FC64;ARABIC LIGATURE YEH WITH HAMZA ABOVE WITH REH FINAL FORM;Lo;0;AL; 0626 0631;;;;N;;;;; FC65;ARABIC LIGATURE YEH WITH HAMZA ABOVE WITH ZAIN FINAL FORM;Lo;0;AL; 0626 0632;;;;N;;;;; FC66;ARABIC LIGATURE YEH WITH HAMZA ABOVE WITH MEEM FINAL FORM;Lo;0;AL; 0626 0645;;;;N;;;;; FC67;ARABIC LIGATURE YEH WITH HAMZA ABOVE WITH NOON FINAL FORM;Lo;0;AL; 0626 0646;;;;N;;;;; FC68;ARABIC LIGATURE YEH WITH HAMZA ABOVE WITH ALEF MAKSURA FINAL FORM;Lo;0;AL; 0626 0649;;;;N;;;;; FC69;ARABIC LIGATURE YEH WITH HAMZA ABOVE WITH YEH FINAL FORM;Lo;0;AL; 0626 064A;;;;N;;;;; FC6A;ARABIC LIGATURE BEH WITH REH FINAL FORM;Lo;0;AL; 0628 0631;;;;N;;;;; FC6B;ARABIC LIGATURE BEH WITH ZAIN FINAL FORM;Lo;0;AL; 0628 0632;;;;N;;;;; FC6C;ARABIC LIGATURE BEH WITH MEEM FINAL FORM;Lo;0;AL; 0628 0645;;;;N;;;;; FC6D;ARABIC LIGATURE BEH WITH NOON FINAL FORM;Lo;0;AL; 0628 0646;;;;N;;;;; FC6E;ARABIC LIGATURE BEH WITH ALEF MAKSURA FINAL FORM;Lo;0;AL; 0628 0649;;;;N;;;;; FC6F;ARABIC LIGATURE BEH WITH YEH FINAL FORM;Lo;0;AL; 0628 064A;;;;N;;;;; FC70;ARABIC LIGATURE TEH WITH REH FINAL FORM;Lo;0;AL; 062A 0631;;;;N;;;;; FC71;ARABIC LIGATURE TEH WITH ZAIN FINAL FORM;Lo;0;AL; 062A 0632;;;;N;;;;; FC72;ARABIC LIGATURE TEH WITH MEEM FINAL FORM;Lo;0;AL; 062A 0645;;;;N;;;;; FC73;ARABIC LIGATURE TEH WITH NOON FINAL FORM;Lo;0;AL; 062A 0646;;;;N;;;;; FC74;ARABIC LIGATURE TEH WITH ALEF MAKSURA FINAL FORM;Lo;0;AL; 062A 0649;;;;N;;;;; FC75;ARABIC LIGATURE TEH WITH YEH FINAL FORM;Lo;0;AL; 062A 064A;;;;N;;;;; FC76;ARABIC LIGATURE THEH WITH REH FINAL FORM;Lo;0;AL; 062B 0631;;;;N;;;;; FC77;ARABIC LIGATURE THEH WITH ZAIN FINAL FORM;Lo;0;AL; 062B 0632;;;;N;;;;; FC78;ARABIC LIGATURE THEH WITH MEEM FINAL FORM;Lo;0;AL; 062B 0645;;;;N;;;;; FC79;ARABIC LIGATURE THEH WITH NOON FINAL FORM;Lo;0;AL; 062B 0646;;;;N;;;;; FC7A;ARABIC LIGATURE THEH WITH ALEF MAKSURA FINAL FORM;Lo;0;AL; 062B 0649;;;;N;;;;; FC7B;ARABIC LIGATURE THEH WITH YEH FINAL FORM;Lo;0;AL; 062B 064A;;;;N;;;;; FC7C;ARABIC LIGATURE FEH WITH ALEF MAKSURA FINAL FORM;Lo;0;AL; 0641 0649;;;;N;;;;; FC7D;ARABIC LIGATURE FEH WITH YEH FINAL FORM;Lo;0;AL; 0641 064A;;;;N;;;;; FC7E;ARABIC LIGATURE QAF WITH ALEF MAKSURA FINAL FORM;Lo;0;AL; 0642 0649;;;;N;;;;; FC7F;ARABIC LIGATURE QAF WITH YEH FINAL FORM;Lo;0;AL; 0642 064A;;;;N;;;;; FC80;ARABIC LIGATURE KAF WITH ALEF FINAL FORM;Lo;0;AL; 0643 0627;;;;N;;;;; FC81;ARABIC LIGATURE KAF WITH LAM FINAL FORM;Lo;0;AL; 0643 0644;;;;N;;;;; FC82;ARABIC LIGATURE KAF WITH MEEM FINAL FORM;Lo;0;AL; 0643 0645;;;;N;;;;; FC83;ARABIC LIGATURE KAF WITH ALEF MAKSURA FINAL FORM;Lo;0;AL; 0643 0649;;;;N;;;;; FC84;ARABIC LIGATURE KAF WITH YEH FINAL FORM;Lo;0;AL; 0643 064A;;;;N;;;;; FC85;ARABIC LIGATURE LAM WITH MEEM FINAL FORM;Lo;0;AL; 0644 0645;;;;N;;;;; FC86;ARABIC LIGATURE LAM WITH ALEF MAKSURA FINAL FORM;Lo;0;AL; 0644 0649;;;;N;;;;; FC87;ARABIC LIGATURE LAM WITH YEH FINAL FORM;Lo;0;AL; 0644 064A;;;;N;;;;; FC88;ARABIC LIGATURE MEEM WITH ALEF FINAL FORM;Lo;0;AL; 0645 0627;;;;N;;;;; FC89;ARABIC LIGATURE MEEM WITH MEEM FINAL FORM;Lo;0;AL; 0645 0645;;;;N;;;;; FC8A;ARABIC LIGATURE NOON WITH REH FINAL FORM;Lo;0;AL; 0646 0631;;;;N;;;;; FC8B;ARABIC LIGATURE NOON WITH ZAIN FINAL FORM;Lo;0;AL; 0646 0632;;;;N;;;;; FC8C;ARABIC LIGATURE NOON WITH MEEM FINAL FORM;Lo;0;AL; 0646 0645;;;;N;;;;; FC8D;ARABIC LIGATURE NOON WITH NOON FINAL FORM;Lo;0;AL; 0646 0646;;;;N;;;;; FC8E;ARABIC LIGATURE NOON WITH ALEF MAKSURA FINAL FORM;Lo;0;AL; 0646 0649;;;;N;;;;; FC8F;ARABIC LIGATURE NOON WITH YEH FINAL FORM;Lo;0;AL; 0646 064A;;;;N;;;;; FC90;ARABIC LIGATURE ALEF MAKSURA WITH SUPERSCRIPT ALEF FINAL FORM;Lo;0;AL; 0649 0670;;;;N;;;;; FC91;ARABIC LIGATURE YEH WITH REH FINAL FORM;Lo;0;AL; 064A 0631;;;;N;;;;; FC92;ARABIC LIGATURE YEH WITH ZAIN FINAL FORM;Lo;0;AL; 064A 0632;;;;N;;;;; FC93;ARABIC LIGATURE YEH WITH MEEM FINAL FORM;Lo;0;AL; 064A 0645;;;;N;;;;; FC94;ARABIC LIGATURE YEH WITH NOON FINAL FORM;Lo;0;AL; 064A 0646;;;;N;;;;; FC95;ARABIC LIGATURE YEH WITH ALEF MAKSURA FINAL FORM;Lo;0;AL; 064A 0649;;;;N;;;;; FC96;ARABIC LIGATURE YEH WITH YEH FINAL FORM;Lo;0;AL; 064A 064A;;;;N;;;;; FC97;ARABIC LIGATURE YEH WITH HAMZA ABOVE WITH JEEM INITIAL FORM;Lo;0;AL; 0626 062C;;;;N;;;;; FC98;ARABIC LIGATURE YEH WITH HAMZA ABOVE WITH HAH INITIAL FORM;Lo;0;AL; 0626 062D;;;;N;;;;; FC99;ARABIC LIGATURE YEH WITH HAMZA ABOVE WITH KHAH INITIAL FORM;Lo;0;AL; 0626 062E;;;;N;;;;; FC9A;ARABIC LIGATURE YEH WITH HAMZA ABOVE WITH MEEM INITIAL FORM;Lo;0;AL; 0626 0645;;;;N;;;;; FC9B;ARABIC LIGATURE YEH WITH HAMZA ABOVE WITH HEH INITIAL FORM;Lo;0;AL; 0626 0647;;;;N;;;;; FC9C;ARABIC LIGATURE BEH WITH JEEM INITIAL FORM;Lo;0;AL; 0628 062C;;;;N;;;;; FC9D;ARABIC LIGATURE BEH WITH HAH INITIAL FORM;Lo;0;AL; 0628 062D;;;;N;;;;; FC9E;ARABIC LIGATURE BEH WITH KHAH INITIAL FORM;Lo;0;AL; 0628 062E;;;;N;;;;; FC9F;ARABIC LIGATURE BEH WITH MEEM INITIAL FORM;Lo;0;AL; 0628 0645;;;;N;;;;; FCA0;ARABIC LIGATURE BEH WITH HEH INITIAL FORM;Lo;0;AL; 0628 0647;;;;N;;;;; FCA1;ARABIC LIGATURE TEH WITH JEEM INITIAL FORM;Lo;0;AL; 062A 062C;;;;N;;;;; FCA2;ARABIC LIGATURE TEH WITH HAH INITIAL FORM;Lo;0;AL; 062A 062D;;;;N;;;;; FCA3;ARABIC LIGATURE TEH WITH KHAH INITIAL FORM;Lo;0;AL; 062A 062E;;;;N;;;;; FCA4;ARABIC LIGATURE TEH WITH MEEM INITIAL FORM;Lo;0;AL; 062A 0645;;;;N;;;;; FCA5;ARABIC LIGATURE TEH WITH HEH INITIAL FORM;Lo;0;AL; 062A 0647;;;;N;;;;; FCA6;ARABIC LIGATURE THEH WITH MEEM INITIAL FORM;Lo;0;AL; 062B 0645;;;;N;;;;; FCA7;ARABIC LIGATURE JEEM WITH HAH INITIAL FORM;Lo;0;AL; 062C 062D;;;;N;;;;; FCA8;ARABIC LIGATURE JEEM WITH MEEM INITIAL FORM;Lo;0;AL; 062C 0645;;;;N;;;;; FCA9;ARABIC LIGATURE HAH WITH JEEM INITIAL FORM;Lo;0;AL; 062D 062C;;;;N;;;;; FCAA;ARABIC LIGATURE HAH WITH MEEM INITIAL FORM;Lo;0;AL; 062D 0645;;;;N;;;;; FCAB;ARABIC LIGATURE KHAH WITH JEEM INITIAL FORM;Lo;0;AL; 062E 062C;;;;N;;;;; FCAC;ARABIC LIGATURE KHAH WITH MEEM INITIAL FORM;Lo;0;AL; 062E 0645;;;;N;;;;; FCAD;ARABIC LIGATURE SEEN WITH JEEM INITIAL FORM;Lo;0;AL; 0633 062C;;;;N;;;;; FCAE;ARABIC LIGATURE SEEN WITH HAH INITIAL FORM;Lo;0;AL; 0633 062D;;;;N;;;;; FCAF;ARABIC LIGATURE SEEN WITH KHAH INITIAL FORM;Lo;0;AL; 0633 062E;;;;N;;;;; FCB0;ARABIC LIGATURE SEEN WITH MEEM INITIAL FORM;Lo;0;AL; 0633 0645;;;;N;;;;; FCB1;ARABIC LIGATURE SAD WITH HAH INITIAL FORM;Lo;0;AL; 0635 062D;;;;N;;;;; FCB2;ARABIC LIGATURE SAD WITH KHAH INITIAL FORM;Lo;0;AL; 0635 062E;;;;N;;;;; FCB3;ARABIC LIGATURE SAD WITH MEEM INITIAL FORM;Lo;0;AL; 0635 0645;;;;N;;;;; FCB4;ARABIC LIGATURE DAD WITH JEEM INITIAL FORM;Lo;0;AL; 0636 062C;;;;N;;;;; FCB5;ARABIC LIGATURE DAD WITH HAH INITIAL FORM;Lo;0;AL; 0636 062D;;;;N;;;;; FCB6;ARABIC LIGATURE DAD WITH KHAH INITIAL FORM;Lo;0;AL; 0636 062E;;;;N;;;;; FCB7;ARABIC LIGATURE DAD WITH MEEM INITIAL FORM;Lo;0;AL; 0636 0645;;;;N;;;;; FCB8;ARABIC LIGATURE TAH WITH HAH INITIAL FORM;Lo;0;AL; 0637 062D;;;;N;;;;; FCB9;ARABIC LIGATURE ZAH WITH MEEM INITIAL FORM;Lo;0;AL; 0638 0645;;;;N;;;;; FCBA;ARABIC LIGATURE AIN WITH JEEM INITIAL FORM;Lo;0;AL; 0639 062C;;;;N;;;;; FCBB;ARABIC LIGATURE AIN WITH MEEM INITIAL FORM;Lo;0;AL; 0639 0645;;;;N;;;;; FCBC;ARABIC LIGATURE GHAIN WITH JEEM INITIAL FORM;Lo;0;AL; 063A 062C;;;;N;;;;; FCBD;ARABIC LIGATURE GHAIN WITH MEEM INITIAL FORM;Lo;0;AL; 063A 0645;;;;N;;;;; FCBE;ARABIC LIGATURE FEH WITH JEEM INITIAL FORM;Lo;0;AL; 0641 062C;;;;N;;;;; FCBF;ARABIC LIGATURE FEH WITH HAH INITIAL FORM;Lo;0;AL; 0641 062D;;;;N;;;;; FCC0;ARABIC LIGATURE FEH WITH KHAH INITIAL FORM;Lo;0;AL; 0641 062E;;;;N;;;;; FCC1;ARABIC LIGATURE FEH WITH MEEM INITIAL FORM;Lo;0;AL; 0641 0645;;;;N;;;;; FCC2;ARABIC LIGATURE QAF WITH HAH INITIAL FORM;Lo;0;AL; 0642 062D;;;;N;;;;; FCC3;ARABIC LIGATURE QAF WITH MEEM INITIAL FORM;Lo;0;AL; 0642 0645;;;;N;;;;; FCC4;ARABIC LIGATURE KAF WITH JEEM INITIAL FORM;Lo;0;AL; 0643 062C;;;;N;;;;; FCC5;ARABIC LIGATURE KAF WITH HAH INITIAL FORM;Lo;0;AL; 0643 062D;;;;N;;;;; FCC6;ARABIC LIGATURE KAF WITH KHAH INITIAL FORM;Lo;0;AL; 0643 062E;;;;N;;;;; FCC7;ARABIC LIGATURE KAF WITH LAM INITIAL FORM;Lo;0;AL; 0643 0644;;;;N;;;;; FCC8;ARABIC LIGATURE KAF WITH MEEM INITIAL FORM;Lo;0;AL; 0643 0645;;;;N;;;;; FCC9;ARABIC LIGATURE LAM WITH JEEM INITIAL FORM;Lo;0;AL; 0644 062C;;;;N;;;;; FCCA;ARABIC LIGATURE LAM WITH HAH INITIAL FORM;Lo;0;AL; 0644 062D;;;;N;;;;; FCCB;ARABIC LIGATURE LAM WITH KHAH INITIAL FORM;Lo;0;AL; 0644 062E;;;;N;;;;; FCCC;ARABIC LIGATURE LAM WITH MEEM INITIAL FORM;Lo;0;AL; 0644 0645;;;;N;;;;; FCCD;ARABIC LIGATURE LAM WITH HEH INITIAL FORM;Lo;0;AL; 0644 0647;;;;N;;;;; FCCE;ARABIC LIGATURE MEEM WITH JEEM INITIAL FORM;Lo;0;AL; 0645 062C;;;;N;;;;; FCCF;ARABIC LIGATURE MEEM WITH HAH INITIAL FORM;Lo;0;AL; 0645 062D;;;;N;;;;; FCD0;ARABIC LIGATURE MEEM WITH KHAH INITIAL FORM;Lo;0;AL; 0645 062E;;;;N;;;;; FCD1;ARABIC LIGATURE MEEM WITH MEEM INITIAL FORM;Lo;0;AL; 0645 0645;;;;N;;;;; FCD2;ARABIC LIGATURE NOON WITH JEEM INITIAL FORM;Lo;0;AL; 0646 062C;;;;N;;;;; FCD3;ARABIC LIGATURE NOON WITH HAH INITIAL FORM;Lo;0;AL; 0646 062D;;;;N;;;;; FCD4;ARABIC LIGATURE NOON WITH KHAH INITIAL FORM;Lo;0;AL; 0646 062E;;;;N;;;;; FCD5;ARABIC LIGATURE NOON WITH MEEM INITIAL FORM;Lo;0;AL; 0646 0645;;;;N;;;;; FCD6;ARABIC LIGATURE NOON WITH HEH INITIAL FORM;Lo;0;AL; 0646 0647;;;;N;;;;; FCD7;ARABIC LIGATURE HEH WITH JEEM INITIAL FORM;Lo;0;AL; 0647 062C;;;;N;;;;; FCD8;ARABIC LIGATURE HEH WITH MEEM INITIAL FORM;Lo;0;AL; 0647 0645;;;;N;;;;; FCD9;ARABIC LIGATURE HEH WITH SUPERSCRIPT ALEF INITIAL FORM;Lo;0;AL; 0647 0670;;;;N;;;;; FCDA;ARABIC LIGATURE YEH WITH JEEM INITIAL FORM;Lo;0;AL; 064A 062C;;;;N;;;;; FCDB;ARABIC LIGATURE YEH WITH HAH INITIAL FORM;Lo;0;AL; 064A 062D;;;;N;;;;; FCDC;ARABIC LIGATURE YEH WITH KHAH INITIAL FORM;Lo;0;AL; 064A 062E;;;;N;;;;; FCDD;ARABIC LIGATURE YEH WITH MEEM INITIAL FORM;Lo;0;AL; 064A 0645;;;;N;;;;; FCDE;ARABIC LIGATURE YEH WITH HEH INITIAL FORM;Lo;0;AL; 064A 0647;;;;N;;;;; FCDF;ARABIC LIGATURE YEH WITH HAMZA ABOVE WITH MEEM MEDIAL FORM;Lo;0;AL; 0626 0645;;;;N;;;;; FCE0;ARABIC LIGATURE YEH WITH HAMZA ABOVE WITH HEH MEDIAL FORM;Lo;0;AL; 0626 0647;;;;N;;;;; FCE1;ARABIC LIGATURE BEH WITH MEEM MEDIAL FORM;Lo;0;AL; 0628 0645;;;;N;;;;; FCE2;ARABIC LIGATURE BEH WITH HEH MEDIAL FORM;Lo;0;AL; 0628 0647;;;;N;;;;; FCE3;ARABIC LIGATURE TEH WITH MEEM MEDIAL FORM;Lo;0;AL; 062A 0645;;;;N;;;;; FCE4;ARABIC LIGATURE TEH WITH HEH MEDIAL FORM;Lo;0;AL; 062A 0647;;;;N;;;;; FCE5;ARABIC LIGATURE THEH WITH MEEM MEDIAL FORM;Lo;0;AL; 062B 0645;;;;N;;;;; FCE6;ARABIC LIGATURE THEH WITH HEH MEDIAL FORM;Lo;0;AL; 062B 0647;;;;N;;;;; FCE7;ARABIC LIGATURE SEEN WITH MEEM MEDIAL FORM;Lo;0;AL; 0633 0645;;;;N;;;;; FCE8;ARABIC LIGATURE SEEN WITH HEH MEDIAL FORM;Lo;0;AL; 0633 0647;;;;N;;;;; FCE9;ARABIC LIGATURE SHEEN WITH MEEM MEDIAL FORM;Lo;0;AL; 0634 0645;;;;N;;;;; FCEA;ARABIC LIGATURE SHEEN WITH HEH MEDIAL FORM;Lo;0;AL; 0634 0647;;;;N;;;;; FCEB;ARABIC LIGATURE KAF WITH LAM MEDIAL FORM;Lo;0;AL; 0643 0644;;;;N;;;;; FCEC;ARABIC LIGATURE KAF WITH MEEM MEDIAL FORM;Lo;0;AL; 0643 0645;;;;N;;;;; FCED;ARABIC LIGATURE LAM WITH MEEM MEDIAL FORM;Lo;0;AL; 0644 0645;;;;N;;;;; FCEE;ARABIC LIGATURE NOON WITH MEEM MEDIAL FORM;Lo;0;AL; 0646 0645;;;;N;;;;; FCEF;ARABIC LIGATURE NOON WITH HEH MEDIAL FORM;Lo;0;AL; 0646 0647;;;;N;;;;; FCF0;ARABIC LIGATURE YEH WITH MEEM MEDIAL FORM;Lo;0;AL; 064A 0645;;;;N;;;;; FCF1;ARABIC LIGATURE YEH WITH HEH MEDIAL FORM;Lo;0;AL; 064A 0647;;;;N;;;;; FCF2;ARABIC LIGATURE SHADDA WITH FATHA MEDIAL FORM;Lo;0;AL; 0640 064E 0651;;;;N;;;;; FCF3;ARABIC LIGATURE SHADDA WITH DAMMA MEDIAL FORM;Lo;0;AL; 0640 064F 0651;;;;N;;;;; FCF4;ARABIC LIGATURE SHADDA WITH KASRA MEDIAL FORM;Lo;0;AL; 0640 0650 0651;;;;N;;;;; FCF5;ARABIC LIGATURE TAH WITH ALEF MAKSURA ISOLATED FORM;Lo;0;AL; 0637 0649;;;;N;;;;; FCF6;ARABIC LIGATURE TAH WITH YEH ISOLATED FORM;Lo;0;AL; 0637 064A;;;;N;;;;; FCF7;ARABIC LIGATURE AIN WITH ALEF MAKSURA ISOLATED FORM;Lo;0;AL; 0639 0649;;;;N;;;;; FCF8;ARABIC LIGATURE AIN WITH YEH ISOLATED FORM;Lo;0;AL; 0639 064A;;;;N;;;;; FCF9;ARABIC LIGATURE GHAIN WITH ALEF MAKSURA ISOLATED FORM;Lo;0;AL; 063A 0649;;;;N;;;;; FCFA;ARABIC LIGATURE GHAIN WITH YEH ISOLATED FORM;Lo;0;AL; 063A 064A;;;;N;;;;; FCFB;ARABIC LIGATURE SEEN WITH ALEF MAKSURA ISOLATED FORM;Lo;0;AL; 0633 0649;;;;N;;;;; FCFC;ARABIC LIGATURE SEEN WITH YEH ISOLATED FORM;Lo;0;AL; 0633 064A;;;;N;;;;; FCFD;ARABIC LIGATURE SHEEN WITH ALEF MAKSURA ISOLATED FORM;Lo;0;AL; 0634 0649;;;;N;;;;; FCFE;ARABIC LIGATURE SHEEN WITH YEH ISOLATED FORM;Lo;0;AL; 0634 064A;;;;N;;;;; FCFF;ARABIC LIGATURE HAH WITH ALEF MAKSURA ISOLATED FORM;Lo;0;AL; 062D 0649;;;;N;;;;; FD00;ARABIC LIGATURE HAH WITH YEH ISOLATED FORM;Lo;0;AL; 062D 064A;;;;N;;;;; FD01;ARABIC LIGATURE JEEM WITH ALEF MAKSURA ISOLATED FORM;Lo;0;AL; 062C 0649;;;;N;;;;; FD02;ARABIC LIGATURE JEEM WITH YEH ISOLATED FORM;Lo;0;AL; 062C 064A;;;;N;;;;; FD03;ARABIC LIGATURE KHAH WITH ALEF MAKSURA ISOLATED FORM;Lo;0;AL; 062E 0649;;;;N;;;;; FD04;ARABIC LIGATURE KHAH WITH YEH ISOLATED FORM;Lo;0;AL; 062E 064A;;;;N;;;;; FD05;ARABIC LIGATURE SAD WITH ALEF MAKSURA ISOLATED FORM;Lo;0;AL; 0635 0649;;;;N;;;;; FD06;ARABIC LIGATURE SAD WITH YEH ISOLATED FORM;Lo;0;AL; 0635 064A;;;;N;;;;; FD07;ARABIC LIGATURE DAD WITH ALEF MAKSURA ISOLATED FORM;Lo;0;AL; 0636 0649;;;;N;;;;; FD08;ARABIC LIGATURE DAD WITH YEH ISOLATED FORM;Lo;0;AL; 0636 064A;;;;N;;;;; FD09;ARABIC LIGATURE SHEEN WITH JEEM ISOLATED FORM;Lo;0;AL; 0634 062C;;;;N;;;;; FD0A;ARABIC LIGATURE SHEEN WITH HAH ISOLATED FORM;Lo;0;AL; 0634 062D;;;;N;;;;; FD0B;ARABIC LIGATURE SHEEN WITH KHAH ISOLATED FORM;Lo;0;AL; 0634 062E;;;;N;;;;; FD0C;ARABIC LIGATURE SHEEN WITH MEEM ISOLATED FORM;Lo;0;AL; 0634 0645;;;;N;;;;; FD0D;ARABIC LIGATURE SHEEN WITH REH ISOLATED FORM;Lo;0;AL; 0634 0631;;;;N;;;;; FD0E;ARABIC LIGATURE SEEN WITH REH ISOLATED FORM;Lo;0;AL; 0633 0631;;;;N;;;;; FD0F;ARABIC LIGATURE SAD WITH REH ISOLATED FORM;Lo;0;AL; 0635 0631;;;;N;;;;; FD10;ARABIC LIGATURE DAD WITH REH ISOLATED FORM;Lo;0;AL; 0636 0631;;;;N;;;;; FD11;ARABIC LIGATURE TAH WITH ALEF MAKSURA FINAL FORM;Lo;0;AL; 0637 0649;;;;N;;;;; FD12;ARABIC LIGATURE TAH WITH YEH FINAL FORM;Lo;0;AL; 0637 064A;;;;N;;;;; FD13;ARABIC LIGATURE AIN WITH ALEF MAKSURA FINAL FORM;Lo;0;AL; 0639 0649;;;;N;;;;; FD14;ARABIC LIGATURE AIN WITH YEH FINAL FORM;Lo;0;AL; 0639 064A;;;;N;;;;; FD15;ARABIC LIGATURE GHAIN WITH ALEF MAKSURA FINAL FORM;Lo;0;AL; 063A 0649;;;;N;;;;; FD16;ARABIC LIGATURE GHAIN WITH YEH FINAL FORM;Lo;0;AL; 063A 064A;;;;N;;;;; FD17;ARABIC LIGATURE SEEN WITH ALEF MAKSURA FINAL FORM;Lo;0;AL; 0633 0649;;;;N;;;;; FD18;ARABIC LIGATURE SEEN WITH YEH FINAL FORM;Lo;0;AL; 0633 064A;;;;N;;;;; FD19;ARABIC LIGATURE SHEEN WITH ALEF MAKSURA FINAL FORM;Lo;0;AL; 0634 0649;;;;N;;;;; FD1A;ARABIC LIGATURE SHEEN WITH YEH FINAL FORM;Lo;0;AL; 0634 064A;;;;N;;;;; FD1B;ARABIC LIGATURE HAH WITH ALEF MAKSURA FINAL FORM;Lo;0;AL; 062D 0649;;;;N;;;;; FD1C;ARABIC LIGATURE HAH WITH YEH FINAL FORM;Lo;0;AL; 062D 064A;;;;N;;;;; FD1D;ARABIC LIGATURE JEEM WITH ALEF MAKSURA FINAL FORM;Lo;0;AL; 062C 0649;;;;N;;;;; FD1E;ARABIC LIGATURE JEEM WITH YEH FINAL FORM;Lo;0;AL; 062C 064A;;;;N;;;;; FD1F;ARABIC LIGATURE KHAH WITH ALEF MAKSURA FINAL FORM;Lo;0;AL; 062E 0649;;;;N;;;;; FD20;ARABIC LIGATURE KHAH WITH YEH FINAL FORM;Lo;0;AL; 062E 064A;;;;N;;;;; FD21;ARABIC LIGATURE SAD WITH ALEF MAKSURA FINAL FORM;Lo;0;AL; 0635 0649;;;;N;;;;; FD22;ARABIC LIGATURE SAD WITH YEH FINAL FORM;Lo;0;AL; 0635 064A;;;;N;;;;; FD23;ARABIC LIGATURE DAD WITH ALEF MAKSURA FINAL FORM;Lo;0;AL; 0636 0649;;;;N;;;;; FD24;ARABIC LIGATURE DAD WITH YEH FINAL FORM;Lo;0;AL; 0636 064A;;;;N;;;;; FD25;ARABIC LIGATURE SHEEN WITH JEEM FINAL FORM;Lo;0;AL; 0634 062C;;;;N;;;;; FD26;ARABIC LIGATURE SHEEN WITH HAH FINAL FORM;Lo;0;AL; 0634 062D;;;;N;;;;; FD27;ARABIC LIGATURE SHEEN WITH KHAH FINAL FORM;Lo;0;AL; 0634 062E;;;;N;;;;; FD28;ARABIC LIGATURE SHEEN WITH MEEM FINAL FORM;Lo;0;AL; 0634 0645;;;;N;;;;; FD29;ARABIC LIGATURE SHEEN WITH REH FINAL FORM;Lo;0;AL; 0634 0631;;;;N;;;;; FD2A;ARABIC LIGATURE SEEN WITH REH FINAL FORM;Lo;0;AL; 0633 0631;;;;N;;;;; FD2B;ARABIC LIGATURE SAD WITH REH FINAL FORM;Lo;0;AL; 0635 0631;;;;N;;;;; FD2C;ARABIC LIGATURE DAD WITH REH FINAL FORM;Lo;0;AL; 0636 0631;;;;N;;;;; FD2D;ARABIC LIGATURE SHEEN WITH JEEM INITIAL FORM;Lo;0;AL; 0634 062C;;;;N;;;;; FD2E;ARABIC LIGATURE SHEEN WITH HAH INITIAL FORM;Lo;0;AL; 0634 062D;;;;N;;;;; FD2F;ARABIC LIGATURE SHEEN WITH KHAH INITIAL FORM;Lo;0;AL; 0634 062E;;;;N;;;;; FD30;ARABIC LIGATURE SHEEN WITH MEEM INITIAL FORM;Lo;0;AL; 0634 0645;;;;N;;;;; FD31;ARABIC LIGATURE SEEN WITH HEH INITIAL FORM;Lo;0;AL; 0633 0647;;;;N;;;;; FD32;ARABIC LIGATURE SHEEN WITH HEH INITIAL FORM;Lo;0;AL; 0634 0647;;;;N;;;;; FD33;ARABIC LIGATURE TAH WITH MEEM INITIAL FORM;Lo;0;AL; 0637 0645;;;;N;;;;; FD34;ARABIC LIGATURE SEEN WITH JEEM MEDIAL FORM;Lo;0;AL; 0633 062C;;;;N;;;;; FD35;ARABIC LIGATURE SEEN WITH HAH MEDIAL FORM;Lo;0;AL; 0633 062D;;;;N;;;;; FD36;ARABIC LIGATURE SEEN WITH KHAH MEDIAL FORM;Lo;0;AL; 0633 062E;;;;N;;;;; FD37;ARABIC LIGATURE SHEEN WITH JEEM MEDIAL FORM;Lo;0;AL; 0634 062C;;;;N;;;;; FD38;ARABIC LIGATURE SHEEN WITH HAH MEDIAL FORM;Lo;0;AL; 0634 062D;;;;N;;;;; FD39;ARABIC LIGATURE SHEEN WITH KHAH MEDIAL FORM;Lo;0;AL; 0634 062E;;;;N;;;;; FD3A;ARABIC LIGATURE TAH WITH MEEM MEDIAL FORM;Lo;0;AL; 0637 0645;;;;N;;;;; FD3B;ARABIC LIGATURE ZAH WITH MEEM MEDIAL FORM;Lo;0;AL; 0638 0645;;;;N;;;;; FD3C;ARABIC LIGATURE ALEF WITH FATHATAN FINAL FORM;Lo;0;AL; 0627 064B;;;;N;;;;; FD3D;ARABIC LIGATURE ALEF WITH FATHATAN ISOLATED FORM;Lo;0;AL; 0627 064B;;;;N;;;;; FD3E;ORNATE LEFT PARENTHESIS;Pe;0;ON;;;;;N;;;;; FD3F;ORNATE RIGHT PARENTHESIS;Ps;0;ON;;;;;N;;;;; FD50;ARABIC LIGATURE TEH WITH JEEM WITH MEEM INITIAL FORM;Lo;0;AL; 062A 062C 0645;;;;N;;;;; FD51;ARABIC LIGATURE TEH WITH HAH WITH JEEM FINAL FORM;Lo;0;AL; 062A 062D 062C;;;;N;;;;; FD52;ARABIC LIGATURE TEH WITH HAH WITH JEEM INITIAL FORM;Lo;0;AL; 062A 062D 062C;;;;N;;;;; FD53;ARABIC LIGATURE TEH WITH HAH WITH MEEM INITIAL FORM;Lo;0;AL; 062A 062D 0645;;;;N;;;;; FD54;ARABIC LIGATURE TEH WITH KHAH WITH MEEM INITIAL FORM;Lo;0;AL; 062A 062E 0645;;;;N;;;;; FD55;ARABIC LIGATURE TEH WITH MEEM WITH JEEM INITIAL FORM;Lo;0;AL; 062A 0645 062C;;;;N;;;;; FD56;ARABIC LIGATURE TEH WITH MEEM WITH HAH INITIAL FORM;Lo;0;AL; 062A 0645 062D;;;;N;;;;; FD57;ARABIC LIGATURE TEH WITH MEEM WITH KHAH INITIAL FORM;Lo;0;AL; 062A 0645 062E;;;;N;;;;; FD58;ARABIC LIGATURE JEEM WITH MEEM WITH HAH FINAL FORM;Lo;0;AL; 062C 0645 062D;;;;N;;;;; FD59;ARABIC LIGATURE JEEM WITH MEEM WITH HAH INITIAL FORM;Lo;0;AL; 062C 0645 062D;;;;N;;;;; FD5A;ARABIC LIGATURE HAH WITH MEEM WITH YEH FINAL FORM;Lo;0;AL; 062D 0645 064A;;;;N;;;;; FD5B;ARABIC LIGATURE HAH WITH MEEM WITH ALEF MAKSURA FINAL FORM;Lo;0;AL; 062D 0645 0649;;;;N;;;;; FD5C;ARABIC LIGATURE SEEN WITH HAH WITH JEEM INITIAL FORM;Lo;0;AL; 0633 062D 062C;;;;N;;;;; FD5D;ARABIC LIGATURE SEEN WITH JEEM WITH HAH INITIAL FORM;Lo;0;AL; 0633 062C 062D;;;;N;;;;; FD5E;ARABIC LIGATURE SEEN WITH JEEM WITH ALEF MAKSURA FINAL FORM;Lo;0;AL; 0633 062C 0649;;;;N;;;;; FD5F;ARABIC LIGATURE SEEN WITH MEEM WITH HAH FINAL FORM;Lo;0;AL; 0633 0645 062D;;;;N;;;;; FD60;ARABIC LIGATURE SEEN WITH MEEM WITH HAH INITIAL FORM;Lo;0;AL; 0633 0645 062D;;;;N;;;;; FD61;ARABIC LIGATURE SEEN WITH MEEM WITH JEEM INITIAL FORM;Lo;0;AL; 0633 0645 062C;;;;N;;;;; FD62;ARABIC LIGATURE SEEN WITH MEEM WITH MEEM FINAL FORM;Lo;0;AL; 0633 0645 0645;;;;N;;;;; FD63;ARABIC LIGATURE SEEN WITH MEEM WITH MEEM INITIAL FORM;Lo;0;AL; 0633 0645 0645;;;;N;;;;; FD64;ARABIC LIGATURE SAD WITH HAH WITH HAH FINAL FORM;Lo;0;AL; 0635 062D 062D;;;;N;;;;; FD65;ARABIC LIGATURE SAD WITH HAH WITH HAH INITIAL FORM;Lo;0;AL; 0635 062D 062D;;;;N;;;;; FD66;ARABIC LIGATURE SAD WITH MEEM WITH MEEM FINAL FORM;Lo;0;AL; 0635 0645 0645;;;;N;;;;; FD67;ARABIC LIGATURE SHEEN WITH HAH WITH MEEM FINAL FORM;Lo;0;AL; 0634 062D 0645;;;;N;;;;; FD68;ARABIC LIGATURE SHEEN WITH HAH WITH MEEM INITIAL FORM;Lo;0;AL; 0634 062D 0645;;;;N;;;;; FD69;ARABIC LIGATURE SHEEN WITH JEEM WITH YEH FINAL FORM;Lo;0;AL; 0634 062C 064A;;;;N;;;;; FD6A;ARABIC LIGATURE SHEEN WITH MEEM WITH KHAH FINAL FORM;Lo;0;AL; 0634 0645 062E;;;;N;;;;; FD6B;ARABIC LIGATURE SHEEN WITH MEEM WITH KHAH INITIAL FORM;Lo;0;AL; 0634 0645 062E;;;;N;;;;; FD6C;ARABIC LIGATURE SHEEN WITH MEEM WITH MEEM FINAL FORM;Lo;0;AL; 0634 0645 0645;;;;N;;;;; FD6D;ARABIC LIGATURE SHEEN WITH MEEM WITH MEEM INITIAL FORM;Lo;0;AL; 0634 0645 0645;;;;N;;;;; FD6E;ARABIC LIGATURE DAD WITH HAH WITH ALEF MAKSURA FINAL FORM;Lo;0;AL; 0636 062D 0649;;;;N;;;;; FD6F;ARABIC LIGATURE DAD WITH KHAH WITH MEEM FINAL FORM;Lo;0;AL; 0636 062E 0645;;;;N;;;;; FD70;ARABIC LIGATURE DAD WITH KHAH WITH MEEM INITIAL FORM;Lo;0;AL; 0636 062E 0645;;;;N;;;;; FD71;ARABIC LIGATURE TAH WITH MEEM WITH HAH FINAL FORM;Lo;0;AL; 0637 0645 062D;;;;N;;;;; FD72;ARABIC LIGATURE TAH WITH MEEM WITH HAH INITIAL FORM;Lo;0;AL; 0637 0645 062D;;;;N;;;;; FD73;ARABIC LIGATURE TAH WITH MEEM WITH MEEM INITIAL FORM;Lo;0;AL; 0637 0645 0645;;;;N;;;;; FD74;ARABIC LIGATURE TAH WITH MEEM WITH YEH FINAL FORM;Lo;0;AL; 0637 0645 064A;;;;N;;;;; FD75;ARABIC LIGATURE AIN WITH JEEM WITH MEEM FINAL FORM;Lo;0;AL; 0639 062C 0645;;;;N;;;;; FD76;ARABIC LIGATURE AIN WITH MEEM WITH MEEM FINAL FORM;Lo;0;AL; 0639 0645 0645;;;;N;;;;; FD77;ARABIC LIGATURE AIN WITH MEEM WITH MEEM INITIAL FORM;Lo;0;AL; 0639 0645 0645;;;;N;;;;; FD78;ARABIC LIGATURE AIN WITH MEEM WITH ALEF MAKSURA FINAL FORM;Lo;0;AL; 0639 0645 0649;;;;N;;;;; FD79;ARABIC LIGATURE GHAIN WITH MEEM WITH MEEM FINAL FORM;Lo;0;AL; 063A 0645 0645;;;;N;;;;; FD7A;ARABIC LIGATURE GHAIN WITH MEEM WITH YEH FINAL FORM;Lo;0;AL; 063A 0645 064A;;;;N;;;;; FD7B;ARABIC LIGATURE GHAIN WITH MEEM WITH ALEF MAKSURA FINAL FORM;Lo;0;AL; 063A 0645 0649;;;;N;;;;; FD7C;ARABIC LIGATURE FEH WITH KHAH WITH MEEM FINAL FORM;Lo;0;AL; 0641 062E 0645;;;;N;;;;; FD7D;ARABIC LIGATURE FEH WITH KHAH WITH MEEM INITIAL FORM;Lo;0;AL; 0641 062E 0645;;;;N;;;;; FD7E;ARABIC LIGATURE QAF WITH MEEM WITH HAH FINAL FORM;Lo;0;AL; 0642 0645 062D;;;;N;;;;; FD7F;ARABIC LIGATURE QAF WITH MEEM WITH MEEM FINAL FORM;Lo;0;AL; 0642 0645 0645;;;;N;;;;; FD80;ARABIC LIGATURE LAM WITH HAH WITH MEEM FINAL FORM;Lo;0;AL; 0644 062D 0645;;;;N;;;;; FD81;ARABIC LIGATURE LAM WITH HAH WITH YEH FINAL FORM;Lo;0;AL; 0644 062D 064A;;;;N;;;;; FD82;ARABIC LIGATURE LAM WITH HAH WITH ALEF MAKSURA FINAL FORM;Lo;0;AL; 0644 062D 0649;;;;N;;;;; FD83;ARABIC LIGATURE LAM WITH JEEM WITH JEEM INITIAL FORM;Lo;0;AL; 0644 062C 062C;;;;N;;;;; FD84;ARABIC LIGATURE LAM WITH JEEM WITH JEEM FINAL FORM;Lo;0;AL; 0644 062C 062C;;;;N;;;;; FD85;ARABIC LIGATURE LAM WITH KHAH WITH MEEM FINAL FORM;Lo;0;AL; 0644 062E 0645;;;;N;;;;; FD86;ARABIC LIGATURE LAM WITH KHAH WITH MEEM INITIAL FORM;Lo;0;AL; 0644 062E 0645;;;;N;;;;; FD87;ARABIC LIGATURE LAM WITH MEEM WITH HAH FINAL FORM;Lo;0;AL; 0644 0645 062D;;;;N;;;;; FD88;ARABIC LIGATURE LAM WITH MEEM WITH HAH INITIAL FORM;Lo;0;AL; 0644 0645 062D;;;;N;;;;; FD89;ARABIC LIGATURE MEEM WITH HAH WITH JEEM INITIAL FORM;Lo;0;AL; 0645 062D 062C;;;;N;;;;; FD8A;ARABIC LIGATURE MEEM WITH HAH WITH MEEM INITIAL FORM;Lo;0;AL; 0645 062D 0645;;;;N;;;;; FD8B;ARABIC LIGATURE MEEM WITH HAH WITH YEH FINAL FORM;Lo;0;AL; 0645 062D 064A;;;;N;;;;; FD8C;ARABIC LIGATURE MEEM WITH JEEM WITH HAH INITIAL FORM;Lo;0;AL; 0645 062C 062D;;;;N;;;;; FD8D;ARABIC LIGATURE MEEM WITH JEEM WITH MEEM INITIAL FORM;Lo;0;AL; 0645 062C 0645;;;;N;;;;; FD8E;ARABIC LIGATURE MEEM WITH KHAH WITH JEEM INITIAL FORM;Lo;0;AL; 0645 062E 062C;;;;N;;;;; FD8F;ARABIC LIGATURE MEEM WITH KHAH WITH MEEM INITIAL FORM;Lo;0;AL; 0645 062E 0645;;;;N;;;;; FD92;ARABIC LIGATURE MEEM WITH JEEM WITH KHAH INITIAL FORM;Lo;0;AL; 0645 062C 062E;;;;N;;;;; FD93;ARABIC LIGATURE HEH WITH MEEM WITH JEEM INITIAL FORM;Lo;0;AL; 0647 0645 062C;;;;N;;;;; FD94;ARABIC LIGATURE HEH WITH MEEM WITH MEEM INITIAL FORM;Lo;0;AL; 0647 0645 0645;;;;N;;;;; FD95;ARABIC LIGATURE NOON WITH HAH WITH MEEM INITIAL FORM;Lo;0;AL; 0646 062D 0645;;;;N;;;;; FD96;ARABIC LIGATURE NOON WITH HAH WITH ALEF MAKSURA FINAL FORM;Lo;0;AL; 0646 062D 0649;;;;N;;;;; FD97;ARABIC LIGATURE NOON WITH JEEM WITH MEEM FINAL FORM;Lo;0;AL; 0646 062C 0645;;;;N;;;;; FD98;ARABIC LIGATURE NOON WITH JEEM WITH MEEM INITIAL FORM;Lo;0;AL; 0646 062C 0645;;;;N;;;;; FD99;ARABIC LIGATURE NOON WITH JEEM WITH ALEF MAKSURA FINAL FORM;Lo;0;AL; 0646 062C 0649;;;;N;;;;; FD9A;ARABIC LIGATURE NOON WITH MEEM WITH YEH FINAL FORM;Lo;0;AL; 0646 0645 064A;;;;N;;;;; FD9B;ARABIC LIGATURE NOON WITH MEEM WITH ALEF MAKSURA FINAL FORM;Lo;0;AL; 0646 0645 0649;;;;N;;;;; FD9C;ARABIC LIGATURE YEH WITH MEEM WITH MEEM FINAL FORM;Lo;0;AL; 064A 0645 0645;;;;N;;;;; FD9D;ARABIC LIGATURE YEH WITH MEEM WITH MEEM INITIAL FORM;Lo;0;AL; 064A 0645 0645;;;;N;;;;; FD9E;ARABIC LIGATURE BEH WITH KHAH WITH YEH FINAL FORM;Lo;0;AL; 0628 062E 064A;;;;N;;;;; FD9F;ARABIC LIGATURE TEH WITH JEEM WITH YEH FINAL FORM;Lo;0;AL; 062A 062C 064A;;;;N;;;;; FDA0;ARABIC LIGATURE TEH WITH JEEM WITH ALEF MAKSURA FINAL FORM;Lo;0;AL; 062A 062C 0649;;;;N;;;;; FDA1;ARABIC LIGATURE TEH WITH KHAH WITH YEH FINAL FORM;Lo;0;AL; 062A 062E 064A;;;;N;;;;; FDA2;ARABIC LIGATURE TEH WITH KHAH WITH ALEF MAKSURA FINAL FORM;Lo;0;AL; 062A 062E 0649;;;;N;;;;; FDA3;ARABIC LIGATURE TEH WITH MEEM WITH YEH FINAL FORM;Lo;0;AL; 062A 0645 064A;;;;N;;;;; FDA4;ARABIC LIGATURE TEH WITH MEEM WITH ALEF MAKSURA FINAL FORM;Lo;0;AL; 062A 0645 0649;;;;N;;;;; FDA5;ARABIC LIGATURE JEEM WITH MEEM WITH YEH FINAL FORM;Lo;0;AL; 062C 0645 064A;;;;N;;;;; FDA6;ARABIC LIGATURE JEEM WITH HAH WITH ALEF MAKSURA FINAL FORM;Lo;0;AL; 062C 062D 0649;;;;N;;;;; FDA7;ARABIC LIGATURE JEEM WITH MEEM WITH ALEF MAKSURA FINAL FORM;Lo;0;AL; 062C 0645 0649;;;;N;;;;; FDA8;ARABIC LIGATURE SEEN WITH KHAH WITH ALEF MAKSURA FINAL FORM;Lo;0;AL; 0633 062E 0649;;;;N;;;;; FDA9;ARABIC LIGATURE SAD WITH HAH WITH YEH FINAL FORM;Lo;0;AL; 0635 062D 064A;;;;N;;;;; FDAA;ARABIC LIGATURE SHEEN WITH HAH WITH YEH FINAL FORM;Lo;0;AL; 0634 062D 064A;;;;N;;;;; FDAB;ARABIC LIGATURE DAD WITH HAH WITH YEH FINAL FORM;Lo;0;AL; 0636 062D 064A;;;;N;;;;; FDAC;ARABIC LIGATURE LAM WITH JEEM WITH YEH FINAL FORM;Lo;0;AL; 0644 062C 064A;;;;N;;;;; FDAD;ARABIC LIGATURE LAM WITH MEEM WITH YEH FINAL FORM;Lo;0;AL; 0644 0645 064A;;;;N;;;;; FDAE;ARABIC LIGATURE YEH WITH HAH WITH YEH FINAL FORM;Lo;0;AL; 064A 062D 064A;;;;N;;;;; FDAF;ARABIC LIGATURE YEH WITH JEEM WITH YEH FINAL FORM;Lo;0;AL; 064A 062C 064A;;;;N;;;;; FDB0;ARABIC LIGATURE YEH WITH MEEM WITH YEH FINAL FORM;Lo;0;AL; 064A 0645 064A;;;;N;;;;; FDB1;ARABIC LIGATURE MEEM WITH MEEM WITH YEH FINAL FORM;Lo;0;AL; 0645 0645 064A;;;;N;;;;; FDB2;ARABIC LIGATURE QAF WITH MEEM WITH YEH FINAL FORM;Lo;0;AL; 0642 0645 064A;;;;N;;;;; FDB3;ARABIC LIGATURE NOON WITH HAH WITH YEH FINAL FORM;Lo;0;AL; 0646 062D 064A;;;;N;;;;; FDB4;ARABIC LIGATURE QAF WITH MEEM WITH HAH INITIAL FORM;Lo;0;AL; 0642 0645 062D;;;;N;;;;; FDB5;ARABIC LIGATURE LAM WITH HAH WITH MEEM INITIAL FORM;Lo;0;AL; 0644 062D 0645;;;;N;;;;; FDB6;ARABIC LIGATURE AIN WITH MEEM WITH YEH FINAL FORM;Lo;0;AL; 0639 0645 064A;;;;N;;;;; FDB7;ARABIC LIGATURE KAF WITH MEEM WITH YEH FINAL FORM;Lo;0;AL; 0643 0645 064A;;;;N;;;;; FDB8;ARABIC LIGATURE NOON WITH JEEM WITH HAH INITIAL FORM;Lo;0;AL; 0646 062C 062D;;;;N;;;;; FDB9;ARABIC LIGATURE MEEM WITH KHAH WITH YEH FINAL FORM;Lo;0;AL; 0645 062E 064A;;;;N;;;;; FDBA;ARABIC LIGATURE LAM WITH JEEM WITH MEEM INITIAL FORM;Lo;0;AL; 0644 062C 0645;;;;N;;;;; FDBB;ARABIC LIGATURE KAF WITH MEEM WITH MEEM FINAL FORM;Lo;0;AL; 0643 0645 0645;;;;N;;;;; FDBC;ARABIC LIGATURE LAM WITH JEEM WITH MEEM FINAL FORM;Lo;0;AL; 0644 062C 0645;;;;N;;;;; FDBD;ARABIC LIGATURE NOON WITH JEEM WITH HAH FINAL FORM;Lo;0;AL; 0646 062C 062D;;;;N;;;;; FDBE;ARABIC LIGATURE JEEM WITH HAH WITH YEH FINAL FORM;Lo;0;AL; 062C 062D 064A;;;;N;;;;; FDBF;ARABIC LIGATURE HAH WITH JEEM WITH YEH FINAL FORM;Lo;0;AL; 062D 062C 064A;;;;N;;;;; FDC0;ARABIC LIGATURE MEEM WITH JEEM WITH YEH FINAL FORM;Lo;0;AL; 0645 062C 064A;;;;N;;;;; FDC1;ARABIC LIGATURE FEH WITH MEEM WITH YEH FINAL FORM;Lo;0;AL; 0641 0645 064A;;;;N;;;;; FDC2;ARABIC LIGATURE BEH WITH HAH WITH YEH FINAL FORM;Lo;0;AL; 0628 062D 064A;;;;N;;;;; FDC3;ARABIC LIGATURE KAF WITH MEEM WITH MEEM INITIAL FORM;Lo;0;AL; 0643 0645 0645;;;;N;;;;; FDC4;ARABIC LIGATURE AIN WITH JEEM WITH MEEM INITIAL FORM;Lo;0;AL; 0639 062C 0645;;;;N;;;;; FDC5;ARABIC LIGATURE SAD WITH MEEM WITH MEEM INITIAL FORM;Lo;0;AL; 0635 0645 0645;;;;N;;;;; FDC6;ARABIC LIGATURE SEEN WITH KHAH WITH YEH FINAL FORM;Lo;0;AL; 0633 062E 064A;;;;N;;;;; FDC7;ARABIC LIGATURE NOON WITH JEEM WITH YEH FINAL FORM;Lo;0;AL; 0646 062C 064A;;;;N;;;;; FDF0;ARABIC LIGATURE SALLA USED AS KORANIC STOP SIGN ISOLATED FORM;Lo;0;AL; 0635 0644 06D2;;;;N;;;;; FDF1;ARABIC LIGATURE QALA USED AS KORANIC STOP SIGN ISOLATED FORM;Lo;0;AL; 0642 0644 06D2;;;;N;;;;; FDF2;ARABIC LIGATURE ALLAH ISOLATED FORM;Lo;0;AL; 0627 0644 0644 0647;;;;N;;;;; FDF3;ARABIC LIGATURE AKBAR ISOLATED FORM;Lo;0;AL; 0627 0643 0628 0631;;;;N;;;;; FDF4;ARABIC LIGATURE MOHAMMAD ISOLATED FORM;Lo;0;AL; 0645 062D 0645 062F;;;;N;;;;; FDF5;ARABIC LIGATURE SALAM ISOLATED FORM;Lo;0;AL; 0635 0644 0639 0645;;;;N;;;;; FDF6;ARABIC LIGATURE RASOUL ISOLATED FORM;Lo;0;AL; 0631 0633 0648 0644;;;;N;;;;; FDF7;ARABIC LIGATURE ALAYHE ISOLATED FORM;Lo;0;AL; 0639 0644 064A 0647;;;;N;;;;; FDF8;ARABIC LIGATURE WASALLAM ISOLATED FORM;Lo;0;AL; 0648 0633 0644 0645;;;;N;;;;; FDF9;ARABIC LIGATURE SALLA ISOLATED FORM;Lo;0;AL; 0635 0644 0649;;;;N;;;;; FDFA;ARABIC LIGATURE SALLALLAHOU ALAYHE WASALLAM;Lo;0;AL; 0635 0644 0649 0020 0627 0644 0644 0647 0020 0639 0644 064A 0647 0020 0648 0633 0644 0645;;;;N;ARABIC LETTER SALLALLAHOU ALAYHE WASALLAM;;;; FDFB;ARABIC LIGATURE JALLAJALALOUHOU;Lo;0;AL; 062C 0644 0020 062C 0644 0627 0644 0647;;;;N;ARABIC LETTER JALLAJALALOUHOU;;;; FDFC;RIAL SIGN;Sc;0;AL; 0631 06CC 0627 0644;;;;N;;;;; FDFD;ARABIC LIGATURE BISMILLAH AR-RAHMAN AR-RAHEEM;So;0;ON;;;;;N;;;;; FE00;VARIATION SELECTOR-1;Mn;0;NSM;;;;;N;;;;; FE01;VARIATION SELECTOR-2;Mn;0;NSM;;;;;N;;;;; FE02;VARIATION SELECTOR-3;Mn;0;NSM;;;;;N;;;;; FE03;VARIATION SELECTOR-4;Mn;0;NSM;;;;;N;;;;; FE04;VARIATION SELECTOR-5;Mn;0;NSM;;;;;N;;;;; FE05;VARIATION SELECTOR-6;Mn;0;NSM;;;;;N;;;;; FE06;VARIATION SELECTOR-7;Mn;0;NSM;;;;;N;;;;; FE07;VARIATION SELECTOR-8;Mn;0;NSM;;;;;N;;;;; FE08;VARIATION SELECTOR-9;Mn;0;NSM;;;;;N;;;;; FE09;VARIATION SELECTOR-10;Mn;0;NSM;;;;;N;;;;; FE0A;VARIATION SELECTOR-11;Mn;0;NSM;;;;;N;;;;; FE0B;VARIATION SELECTOR-12;Mn;0;NSM;;;;;N;;;;; FE0C;VARIATION SELECTOR-13;Mn;0;NSM;;;;;N;;;;; FE0D;VARIATION SELECTOR-14;Mn;0;NSM;;;;;N;;;;; FE0E;VARIATION SELECTOR-15;Mn;0;NSM;;;;;N;;;;; FE0F;VARIATION SELECTOR-16;Mn;0;NSM;;;;;N;;;;; FE10;PRESENTATION FORM FOR VERTICAL COMMA;Po;0;ON; 002C;;;;N;;;;; FE11;PRESENTATION FORM FOR VERTICAL IDEOGRAPHIC COMMA;Po;0;ON; 3001;;;;N;;;;; FE12;PRESENTATION FORM FOR VERTICAL IDEOGRAPHIC FULL STOP;Po;0;ON; 3002;;;;N;;;;; FE13;PRESENTATION FORM FOR VERTICAL COLON;Po;0;ON; 003A;;;;N;;;;; FE14;PRESENTATION FORM FOR VERTICAL SEMICOLON;Po;0;ON; 003B;;;;N;;;;; FE15;PRESENTATION FORM FOR VERTICAL EXCLAMATION MARK;Po;0;ON; 0021;;;;N;;;;; FE16;PRESENTATION FORM FOR VERTICAL QUESTION MARK;Po;0;ON; 003F;;;;N;;;;; FE17;PRESENTATION FORM FOR VERTICAL LEFT WHITE LENTICULAR BRACKET;Ps;0;ON; 3016;;;;N;;;;; FE18;PRESENTATION FORM FOR VERTICAL RIGHT WHITE LENTICULAR BRAKCET;Pe;0;ON; 3017;;;;N;;;;; FE19;PRESENTATION FORM FOR VERTICAL HORIZONTAL ELLIPSIS;Po;0;ON; 2026;;;;N;;;;; FE20;COMBINING LIGATURE LEFT HALF;Mn;230;NSM;;;;;N;;;;; FE21;COMBINING LIGATURE RIGHT HALF;Mn;230;NSM;;;;;N;;;;; FE22;COMBINING DOUBLE TILDE LEFT HALF;Mn;230;NSM;;;;;N;;;;; FE23;COMBINING DOUBLE TILDE RIGHT HALF;Mn;230;NSM;;;;;N;;;;; FE24;COMBINING MACRON LEFT HALF;Mn;230;NSM;;;;;N;;;;; FE25;COMBINING MACRON RIGHT HALF;Mn;230;NSM;;;;;N;;;;; FE26;COMBINING CONJOINING MACRON;Mn;230;NSM;;;;;N;;;;; FE27;COMBINING LIGATURE LEFT HALF BELOW;Mn;220;NSM;;;;;N;;;;; FE28;COMBINING LIGATURE RIGHT HALF BELOW;Mn;220;NSM;;;;;N;;;;; FE29;COMBINING TILDE LEFT HALF BELOW;Mn;220;NSM;;;;;N;;;;; FE2A;COMBINING TILDE RIGHT HALF BELOW;Mn;220;NSM;;;;;N;;;;; FE2B;COMBINING MACRON LEFT HALF BELOW;Mn;220;NSM;;;;;N;;;;; FE2C;COMBINING MACRON RIGHT HALF BELOW;Mn;220;NSM;;;;;N;;;;; FE2D;COMBINING CONJOINING MACRON BELOW;Mn;220;NSM;;;;;N;;;;; FE30;PRESENTATION FORM FOR VERTICAL TWO DOT LEADER;Po;0;ON; 2025;;;;N;GLYPH FOR VERTICAL TWO DOT LEADER;;;; FE31;PRESENTATION FORM FOR VERTICAL EM DASH;Pd;0;ON; 2014;;;;N;GLYPH FOR VERTICAL EM DASH;;;; FE32;PRESENTATION FORM FOR VERTICAL EN DASH;Pd;0;ON; 2013;;;;N;GLYPH FOR VERTICAL EN DASH;;;; FE33;PRESENTATION FORM FOR VERTICAL LOW LINE;Pc;0;ON; 005F;;;;N;GLYPH FOR VERTICAL SPACING UNDERSCORE;;;; FE34;PRESENTATION FORM FOR VERTICAL WAVY LOW LINE;Pc;0;ON; 005F;;;;N;GLYPH FOR VERTICAL SPACING WAVY UNDERSCORE;;;; FE35;PRESENTATION FORM FOR VERTICAL LEFT PARENTHESIS;Ps;0;ON; 0028;;;;N;GLYPH FOR VERTICAL OPENING PARENTHESIS;;;; FE36;PRESENTATION FORM FOR VERTICAL RIGHT PARENTHESIS;Pe;0;ON; 0029;;;;N;GLYPH FOR VERTICAL CLOSING PARENTHESIS;;;; FE37;PRESENTATION FORM FOR VERTICAL LEFT CURLY BRACKET;Ps;0;ON; 007B;;;;N;GLYPH FOR VERTICAL OPENING CURLY BRACKET;;;; FE38;PRESENTATION FORM FOR VERTICAL RIGHT CURLY BRACKET;Pe;0;ON; 007D;;;;N;GLYPH FOR VERTICAL CLOSING CURLY BRACKET;;;; FE39;PRESENTATION FORM FOR VERTICAL LEFT TORTOISE SHELL BRACKET;Ps;0;ON; 3014;;;;N;GLYPH FOR VERTICAL OPENING TORTOISE SHELL BRACKET;;;; FE3A;PRESENTATION FORM FOR VERTICAL RIGHT TORTOISE SHELL BRACKET;Pe;0;ON; 3015;;;;N;GLYPH FOR VERTICAL CLOSING TORTOISE SHELL BRACKET;;;; FE3B;PRESENTATION FORM FOR VERTICAL LEFT BLACK LENTICULAR BRACKET;Ps;0;ON; 3010;;;;N;GLYPH FOR VERTICAL OPENING BLACK LENTICULAR BRACKET;;;; FE3C;PRESENTATION FORM FOR VERTICAL RIGHT BLACK LENTICULAR BRACKET;Pe;0;ON; 3011;;;;N;GLYPH FOR VERTICAL CLOSING BLACK LENTICULAR BRACKET;;;; FE3D;PRESENTATION FORM FOR VERTICAL LEFT DOUBLE ANGLE BRACKET;Ps;0;ON; 300A;;;;N;GLYPH FOR VERTICAL OPENING DOUBLE ANGLE BRACKET;;;; FE3E;PRESENTATION FORM FOR VERTICAL RIGHT DOUBLE ANGLE BRACKET;Pe;0;ON; 300B;;;;N;GLYPH FOR VERTICAL CLOSING DOUBLE ANGLE BRACKET;;;; FE3F;PRESENTATION FORM FOR VERTICAL LEFT ANGLE BRACKET;Ps;0;ON; 3008;;;;N;GLYPH FOR VERTICAL OPENING ANGLE BRACKET;;;; FE40;PRESENTATION FORM FOR VERTICAL RIGHT ANGLE BRACKET;Pe;0;ON; 3009;;;;N;GLYPH FOR VERTICAL CLOSING ANGLE BRACKET;;;; FE41;PRESENTATION FORM FOR VERTICAL LEFT CORNER BRACKET;Ps;0;ON; 300C;;;;N;GLYPH FOR VERTICAL OPENING CORNER BRACKET;;;; FE42;PRESENTATION FORM FOR VERTICAL RIGHT CORNER BRACKET;Pe;0;ON; 300D;;;;N;GLYPH FOR VERTICAL CLOSING CORNER BRACKET;;;; FE43;PRESENTATION FORM FOR VERTICAL LEFT WHITE CORNER BRACKET;Ps;0;ON; 300E;;;;N;GLYPH FOR VERTICAL OPENING WHITE CORNER BRACKET;;;; FE44;PRESENTATION FORM FOR VERTICAL RIGHT WHITE CORNER BRACKET;Pe;0;ON; 300F;;;;N;GLYPH FOR VERTICAL CLOSING WHITE CORNER BRACKET;;;; FE45;SESAME DOT;Po;0;ON;;;;;N;;;;; FE46;WHITE SESAME DOT;Po;0;ON;;;;;N;;;;; FE47;PRESENTATION FORM FOR VERTICAL LEFT SQUARE BRACKET;Ps;0;ON; 005B;;;;N;;;;; FE48;PRESENTATION FORM FOR VERTICAL RIGHT SQUARE BRACKET;Pe;0;ON; 005D;;;;N;;;;; FE49;DASHED OVERLINE;Po;0;ON; 203E;;;;N;SPACING DASHED OVERSCORE;;;; FE4A;CENTRELINE OVERLINE;Po;0;ON; 203E;;;;N;SPACING CENTERLINE OVERSCORE;;;; FE4B;WAVY OVERLINE;Po;0;ON; 203E;;;;N;SPACING WAVY OVERSCORE;;;; FE4C;DOUBLE WAVY OVERLINE;Po;0;ON; 203E;;;;N;SPACING DOUBLE WAVY OVERSCORE;;;; FE4D;DASHED LOW LINE;Pc;0;ON; 005F;;;;N;SPACING DASHED UNDERSCORE;;;; FE4E;CENTRELINE LOW LINE;Pc;0;ON; 005F;;;;N;SPACING CENTERLINE UNDERSCORE;;;; FE4F;WAVY LOW LINE;Pc;0;ON; 005F;;;;N;SPACING WAVY UNDERSCORE;;;; FE50;SMALL COMMA;Po;0;CS; 002C;;;;N;;;;; FE51;SMALL IDEOGRAPHIC COMMA;Po;0;ON; 3001;;;;N;;;;; FE52;SMALL FULL STOP;Po;0;CS; 002E;;;;N;SMALL PERIOD;;;; FE54;SMALL SEMICOLON;Po;0;ON; 003B;;;;N;;;;; FE55;SMALL COLON;Po;0;CS; 003A;;;;N;;;;; FE56;SMALL QUESTION MARK;Po;0;ON; 003F;;;;N;;;;; FE57;SMALL EXCLAMATION MARK;Po;0;ON; 0021;;;;N;;;;; FE58;SMALL EM DASH;Pd;0;ON; 2014;;;;N;;;;; FE59;SMALL LEFT PARENTHESIS;Ps;0;ON; 0028;;;;Y;SMALL OPENING PARENTHESIS;;;; FE5A;SMALL RIGHT PARENTHESIS;Pe;0;ON; 0029;;;;Y;SMALL CLOSING PARENTHESIS;;;; FE5B;SMALL LEFT CURLY BRACKET;Ps;0;ON; 007B;;;;Y;SMALL OPENING CURLY BRACKET;;;; FE5C;SMALL RIGHT CURLY BRACKET;Pe;0;ON; 007D;;;;Y;SMALL CLOSING CURLY BRACKET;;;; FE5D;SMALL LEFT TORTOISE SHELL BRACKET;Ps;0;ON; 3014;;;;Y;SMALL OPENING TORTOISE SHELL BRACKET;;;; FE5E;SMALL RIGHT TORTOISE SHELL BRACKET;Pe;0;ON; 3015;;;;Y;SMALL CLOSING TORTOISE SHELL BRACKET;;;; FE5F;SMALL NUMBER SIGN;Po;0;ET; 0023;;;;N;;;;; FE60;SMALL AMPERSAND;Po;0;ON; 0026;;;;N;;;;; FE61;SMALL ASTERISK;Po;0;ON; 002A;;;;N;;;;; FE62;SMALL PLUS SIGN;Sm;0;ES; 002B;;;;N;;;;; FE63;SMALL HYPHEN-MINUS;Pd;0;ES; 002D;;;;N;;;;; FE64;SMALL LESS-THAN SIGN;Sm;0;ON; 003C;;;;Y;;;;; FE65;SMALL GREATER-THAN SIGN;Sm;0;ON; 003E;;;;Y;;;;; FE66;SMALL EQUALS SIGN;Sm;0;ON; 003D;;;;N;;;;; FE68;SMALL REVERSE SOLIDUS;Po;0;ON; 005C;;;;N;SMALL BACKSLASH;;;; FE69;SMALL DOLLAR SIGN;Sc;0;ET; 0024;;;;N;;;;; FE6A;SMALL PERCENT SIGN;Po;0;ET; 0025;;;;N;;;;; FE6B;SMALL COMMERCIAL AT;Po;0;ON; 0040;;;;N;;;;; FE70;ARABIC FATHATAN ISOLATED FORM;Lo;0;AL; 0020 064B;;;;N;ARABIC SPACING FATHATAN;;;; FE71;ARABIC TATWEEL WITH FATHATAN ABOVE;Lo;0;AL; 0640 064B;;;;N;ARABIC FATHATAN ON TATWEEL;;;; FE72;ARABIC DAMMATAN ISOLATED FORM;Lo;0;AL; 0020 064C;;;;N;ARABIC SPACING DAMMATAN;;;; FE73;ARABIC TAIL FRAGMENT;Lo;0;AL;;;;;N;;;;; FE74;ARABIC KASRATAN ISOLATED FORM;Lo;0;AL; 0020 064D;;;;N;ARABIC SPACING KASRATAN;;;; FE76;ARABIC FATHA ISOLATED FORM;Lo;0;AL; 0020 064E;;;;N;ARABIC SPACING FATHAH;;;; FE77;ARABIC FATHA MEDIAL FORM;Lo;0;AL; 0640 064E;;;;N;ARABIC FATHAH ON TATWEEL;;;; FE78;ARABIC DAMMA ISOLATED FORM;Lo;0;AL; 0020 064F;;;;N;ARABIC SPACING DAMMAH;;;; FE79;ARABIC DAMMA MEDIAL FORM;Lo;0;AL; 0640 064F;;;;N;ARABIC DAMMAH ON TATWEEL;;;; FE7A;ARABIC KASRA ISOLATED FORM;Lo;0;AL; 0020 0650;;;;N;ARABIC SPACING KASRAH;;;; FE7B;ARABIC KASRA MEDIAL FORM;Lo;0;AL; 0640 0650;;;;N;ARABIC KASRAH ON TATWEEL;;;; FE7C;ARABIC SHADDA ISOLATED FORM;Lo;0;AL; 0020 0651;;;;N;ARABIC SPACING SHADDAH;;;; FE7D;ARABIC SHADDA MEDIAL FORM;Lo;0;AL; 0640 0651;;;;N;ARABIC SHADDAH ON TATWEEL;;;; FE7E;ARABIC SUKUN ISOLATED FORM;Lo;0;AL; 0020 0652;;;;N;ARABIC SPACING SUKUN;;;; FE7F;ARABIC SUKUN MEDIAL FORM;Lo;0;AL; 0640 0652;;;;N;ARABIC SUKUN ON TATWEEL;;;; FE80;ARABIC LETTER HAMZA ISOLATED FORM;Lo;0;AL; 0621;;;;N;GLYPH FOR ISOLATE ARABIC HAMZAH;;;; FE81;ARABIC LETTER ALEF WITH MADDA ABOVE ISOLATED FORM;Lo;0;AL; 0622;;;;N;GLYPH FOR ISOLATE ARABIC MADDAH ON ALEF;;;; FE82;ARABIC LETTER ALEF WITH MADDA ABOVE FINAL FORM;Lo;0;AL; 0622;;;;N;GLYPH FOR FINAL ARABIC MADDAH ON ALEF;;;; FE83;ARABIC LETTER ALEF WITH HAMZA ABOVE ISOLATED FORM;Lo;0;AL; 0623;;;;N;GLYPH FOR ISOLATE ARABIC HAMZAH ON ALEF;;;; FE84;ARABIC LETTER ALEF WITH HAMZA ABOVE FINAL FORM;Lo;0;AL; 0623;;;;N;GLYPH FOR FINAL ARABIC HAMZAH ON ALEF;;;; FE85;ARABIC LETTER WAW WITH HAMZA ABOVE ISOLATED FORM;Lo;0;AL; 0624;;;;N;GLYPH FOR ISOLATE ARABIC HAMZAH ON WAW;;;; FE86;ARABIC LETTER WAW WITH HAMZA ABOVE FINAL FORM;Lo;0;AL; 0624;;;;N;GLYPH FOR FINAL ARABIC HAMZAH ON WAW;;;; FE87;ARABIC LETTER ALEF WITH HAMZA BELOW ISOLATED FORM;Lo;0;AL; 0625;;;;N;GLYPH FOR ISOLATE ARABIC HAMZAH UNDER ALEF;;;; FE88;ARABIC LETTER ALEF WITH HAMZA BELOW FINAL FORM;Lo;0;AL; 0625;;;;N;GLYPH FOR FINAL ARABIC HAMZAH UNDER ALEF;;;; FE89;ARABIC LETTER YEH WITH HAMZA ABOVE ISOLATED FORM;Lo;0;AL; 0626;;;;N;GLYPH FOR ISOLATE ARABIC HAMZAH ON YA;;;; FE8A;ARABIC LETTER YEH WITH HAMZA ABOVE FINAL FORM;Lo;0;AL; 0626;;;;N;GLYPH FOR FINAL ARABIC HAMZAH ON YA;;;; FE8B;ARABIC LETTER YEH WITH HAMZA ABOVE INITIAL FORM;Lo;0;AL; 0626;;;;N;GLYPH FOR INITIAL ARABIC HAMZAH ON YA;;;; FE8C;ARABIC LETTER YEH WITH HAMZA ABOVE MEDIAL FORM;Lo;0;AL; 0626;;;;N;GLYPH FOR MEDIAL ARABIC HAMZAH ON YA;;;; FE8D;ARABIC LETTER ALEF ISOLATED FORM;Lo;0;AL; 0627;;;;N;GLYPH FOR ISOLATE ARABIC ALEF;;;; FE8E;ARABIC LETTER ALEF FINAL FORM;Lo;0;AL; 0627;;;;N;GLYPH FOR FINAL ARABIC ALEF;;;; FE8F;ARABIC LETTER BEH ISOLATED FORM;Lo;0;AL; 0628;;;;N;GLYPH FOR ISOLATE ARABIC BAA;;;; FE90;ARABIC LETTER BEH FINAL FORM;Lo;0;AL; 0628;;;;N;GLYPH FOR FINAL ARABIC BAA;;;; FE91;ARABIC LETTER BEH INITIAL FORM;Lo;0;AL; 0628;;;;N;GLYPH FOR INITIAL ARABIC BAA;;;; FE92;ARABIC LETTER BEH MEDIAL FORM;Lo;0;AL; 0628;;;;N;GLYPH FOR MEDIAL ARABIC BAA;;;; FE93;ARABIC LETTER TEH MARBUTA ISOLATED FORM;Lo;0;AL; 0629;;;;N;GLYPH FOR ISOLATE ARABIC TAA MARBUTAH;;;; FE94;ARABIC LETTER TEH MARBUTA FINAL FORM;Lo;0;AL; 0629;;;;N;GLYPH FOR FINAL ARABIC TAA MARBUTAH;;;; FE95;ARABIC LETTER TEH ISOLATED FORM;Lo;0;AL; 062A;;;;N;GLYPH FOR ISOLATE ARABIC TAA;;;; FE96;ARABIC LETTER TEH FINAL FORM;Lo;0;AL; 062A;;;;N;GLYPH FOR FINAL ARABIC TAA;;;; FE97;ARABIC LETTER TEH INITIAL FORM;Lo;0;AL; 062A;;;;N;GLYPH FOR INITIAL ARABIC TAA;;;; FE98;ARABIC LETTER TEH MEDIAL FORM;Lo;0;AL; 062A;;;;N;GLYPH FOR MEDIAL ARABIC TAA;;;; FE99;ARABIC LETTER THEH ISOLATED FORM;Lo;0;AL; 062B;;;;N;GLYPH FOR ISOLATE ARABIC THAA;;;; FE9A;ARABIC LETTER THEH FINAL FORM;Lo;0;AL; 062B;;;;N;GLYPH FOR FINAL ARABIC THAA;;;; FE9B;ARABIC LETTER THEH INITIAL FORM;Lo;0;AL; 062B;;;;N;GLYPH FOR INITIAL ARABIC THAA;;;; FE9C;ARABIC LETTER THEH MEDIAL FORM;Lo;0;AL; 062B;;;;N;GLYPH FOR MEDIAL ARABIC THAA;;;; FE9D;ARABIC LETTER JEEM ISOLATED FORM;Lo;0;AL; 062C;;;;N;GLYPH FOR ISOLATE ARABIC JEEM;;;; FE9E;ARABIC LETTER JEEM FINAL FORM;Lo;0;AL; 062C;;;;N;GLYPH FOR FINAL ARABIC JEEM;;;; FE9F;ARABIC LETTER JEEM INITIAL FORM;Lo;0;AL; 062C;;;;N;GLYPH FOR INITIAL ARABIC JEEM;;;; FEA0;ARABIC LETTER JEEM MEDIAL FORM;Lo;0;AL; 062C;;;;N;GLYPH FOR MEDIAL ARABIC JEEM;;;; FEA1;ARABIC LETTER HAH ISOLATED FORM;Lo;0;AL; 062D;;;;N;GLYPH FOR ISOLATE ARABIC HAA;;;; FEA2;ARABIC LETTER HAH FINAL FORM;Lo;0;AL; 062D;;;;N;GLYPH FOR FINAL ARABIC HAA;;;; FEA3;ARABIC LETTER HAH INITIAL FORM;Lo;0;AL; 062D;;;;N;GLYPH FOR INITIAL ARABIC HAA;;;; FEA4;ARABIC LETTER HAH MEDIAL FORM;Lo;0;AL; 062D;;;;N;GLYPH FOR MEDIAL ARABIC HAA;;;; FEA5;ARABIC LETTER KHAH ISOLATED FORM;Lo;0;AL; 062E;;;;N;GLYPH FOR ISOLATE ARABIC KHAA;;;; FEA6;ARABIC LETTER KHAH FINAL FORM;Lo;0;AL; 062E;;;;N;GLYPH FOR FINAL ARABIC KHAA;;;; FEA7;ARABIC LETTER KHAH INITIAL FORM;Lo;0;AL; 062E;;;;N;GLYPH FOR INITIAL ARABIC KHAA;;;; FEA8;ARABIC LETTER KHAH MEDIAL FORM;Lo;0;AL; 062E;;;;N;GLYPH FOR MEDIAL ARABIC KHAA;;;; FEA9;ARABIC LETTER DAL ISOLATED FORM;Lo;0;AL; 062F;;;;N;GLYPH FOR ISOLATE ARABIC DAL;;;; FEAA;ARABIC LETTER DAL FINAL FORM;Lo;0;AL; 062F;;;;N;GLYPH FOR FINAL ARABIC DAL;;;; FEAB;ARABIC LETTER THAL ISOLATED FORM;Lo;0;AL; 0630;;;;N;GLYPH FOR ISOLATE ARABIC THAL;;;; FEAC;ARABIC LETTER THAL FINAL FORM;Lo;0;AL; 0630;;;;N;GLYPH FOR FINAL ARABIC THAL;;;; FEAD;ARABIC LETTER REH ISOLATED FORM;Lo;0;AL; 0631;;;;N;GLYPH FOR ISOLATE ARABIC RA;;;; FEAE;ARABIC LETTER REH FINAL FORM;Lo;0;AL; 0631;;;;N;GLYPH FOR FINAL ARABIC RA;;;; FEAF;ARABIC LETTER ZAIN ISOLATED FORM;Lo;0;AL; 0632;;;;N;GLYPH FOR ISOLATE ARABIC ZAIN;;;; FEB0;ARABIC LETTER ZAIN FINAL FORM;Lo;0;AL; 0632;;;;N;GLYPH FOR FINAL ARABIC ZAIN;;;; FEB1;ARABIC LETTER SEEN ISOLATED FORM;Lo;0;AL; 0633;;;;N;GLYPH FOR ISOLATE ARABIC SEEN;;;; FEB2;ARABIC LETTER SEEN FINAL FORM;Lo;0;AL; 0633;;;;N;GLYPH FOR FINAL ARABIC SEEN;;;; FEB3;ARABIC LETTER SEEN INITIAL FORM;Lo;0;AL; 0633;;;;N;GLYPH FOR INITIAL ARABIC SEEN;;;; FEB4;ARABIC LETTER SEEN MEDIAL FORM;Lo;0;AL; 0633;;;;N;GLYPH FOR MEDIAL ARABIC SEEN;;;; FEB5;ARABIC LETTER SHEEN ISOLATED FORM;Lo;0;AL; 0634;;;;N;GLYPH FOR ISOLATE ARABIC SHEEN;;;; FEB6;ARABIC LETTER SHEEN FINAL FORM;Lo;0;AL; 0634;;;;N;GLYPH FOR FINAL ARABIC SHEEN;;;; FEB7;ARABIC LETTER SHEEN INITIAL FORM;Lo;0;AL; 0634;;;;N;GLYPH FOR INITIAL ARABIC SHEEN;;;; FEB8;ARABIC LETTER SHEEN MEDIAL FORM;Lo;0;AL; 0634;;;;N;GLYPH FOR MEDIAL ARABIC SHEEN;;;; FEB9;ARABIC LETTER SAD ISOLATED FORM;Lo;0;AL; 0635;;;;N;GLYPH FOR ISOLATE ARABIC SAD;;;; FEBA;ARABIC LETTER SAD FINAL FORM;Lo;0;AL; 0635;;;;N;GLYPH FOR FINAL ARABIC SAD;;;; FEBB;ARABIC LETTER SAD INITIAL FORM;Lo;0;AL; 0635;;;;N;GLYPH FOR INITIAL ARABIC SAD;;;; FEBC;ARABIC LETTER SAD MEDIAL FORM;Lo;0;AL; 0635;;;;N;GLYPH FOR MEDIAL ARABIC SAD;;;; FEBD;ARABIC LETTER DAD ISOLATED FORM;Lo;0;AL; 0636;;;;N;GLYPH FOR ISOLATE ARABIC DAD;;;; FEBE;ARABIC LETTER DAD FINAL FORM;Lo;0;AL; 0636;;;;N;GLYPH FOR FINAL ARABIC DAD;;;; FEBF;ARABIC LETTER DAD INITIAL FORM;Lo;0;AL; 0636;;;;N;GLYPH FOR INITIAL ARABIC DAD;;;; FEC0;ARABIC LETTER DAD MEDIAL FORM;Lo;0;AL; 0636;;;;N;GLYPH FOR MEDIAL ARABIC DAD;;;; FEC1;ARABIC LETTER TAH ISOLATED FORM;Lo;0;AL; 0637;;;;N;GLYPH FOR ISOLATE ARABIC TAH;;;; FEC2;ARABIC LETTER TAH FINAL FORM;Lo;0;AL; 0637;;;;N;GLYPH FOR FINAL ARABIC TAH;;;; FEC3;ARABIC LETTER TAH INITIAL FORM;Lo;0;AL; 0637;;;;N;GLYPH FOR INITIAL ARABIC TAH;;;; FEC4;ARABIC LETTER TAH MEDIAL FORM;Lo;0;AL; 0637;;;;N;GLYPH FOR MEDIAL ARABIC TAH;;;; FEC5;ARABIC LETTER ZAH ISOLATED FORM;Lo;0;AL; 0638;;;;N;GLYPH FOR ISOLATE ARABIC DHAH;;;; FEC6;ARABIC LETTER ZAH FINAL FORM;Lo;0;AL; 0638;;;;N;GLYPH FOR FINAL ARABIC DHAH;;;; FEC7;ARABIC LETTER ZAH INITIAL FORM;Lo;0;AL; 0638;;;;N;GLYPH FOR INITIAL ARABIC DHAH;;;; FEC8;ARABIC LETTER ZAH MEDIAL FORM;Lo;0;AL; 0638;;;;N;GLYPH FOR MEDIAL ARABIC DHAH;;;; FEC9;ARABIC LETTER AIN ISOLATED FORM;Lo;0;AL; 0639;;;;N;GLYPH FOR ISOLATE ARABIC AIN;;;; FECA;ARABIC LETTER AIN FINAL FORM;Lo;0;AL; 0639;;;;N;GLYPH FOR FINAL ARABIC AIN;;;; FECB;ARABIC LETTER AIN INITIAL FORM;Lo;0;AL; 0639;;;;N;GLYPH FOR INITIAL ARABIC AIN;;;; FECC;ARABIC LETTER AIN MEDIAL FORM;Lo;0;AL; 0639;;;;N;GLYPH FOR MEDIAL ARABIC AIN;;;; FECD;ARABIC LETTER GHAIN ISOLATED FORM;Lo;0;AL; 063A;;;;N;GLYPH FOR ISOLATE ARABIC GHAIN;;;; FECE;ARABIC LETTER GHAIN FINAL FORM;Lo;0;AL; 063A;;;;N;GLYPH FOR FINAL ARABIC GHAIN;;;; FECF;ARABIC LETTER GHAIN INITIAL FORM;Lo;0;AL; 063A;;;;N;GLYPH FOR INITIAL ARABIC GHAIN;;;; FED0;ARABIC LETTER GHAIN MEDIAL FORM;Lo;0;AL; 063A;;;;N;GLYPH FOR MEDIAL ARABIC GHAIN;;;; FED1;ARABIC LETTER FEH ISOLATED FORM;Lo;0;AL; 0641;;;;N;GLYPH FOR ISOLATE ARABIC FA;;;; FED2;ARABIC LETTER FEH FINAL FORM;Lo;0;AL; 0641;;;;N;GLYPH FOR FINAL ARABIC FA;;;; FED3;ARABIC LETTER FEH INITIAL FORM;Lo;0;AL; 0641;;;;N;GLYPH FOR INITIAL ARABIC FA;;;; FED4;ARABIC LETTER FEH MEDIAL FORM;Lo;0;AL; 0641;;;;N;GLYPH FOR MEDIAL ARABIC FA;;;; FED5;ARABIC LETTER QAF ISOLATED FORM;Lo;0;AL; 0642;;;;N;GLYPH FOR ISOLATE ARABIC QAF;;;; FED6;ARABIC LETTER QAF FINAL FORM;Lo;0;AL; 0642;;;;N;GLYPH FOR FINAL ARABIC QAF;;;; FED7;ARABIC LETTER QAF INITIAL FORM;Lo;0;AL; 0642;;;;N;GLYPH FOR INITIAL ARABIC QAF;;;; FED8;ARABIC LETTER QAF MEDIAL FORM;Lo;0;AL; 0642;;;;N;GLYPH FOR MEDIAL ARABIC QAF;;;; FED9;ARABIC LETTER KAF ISOLATED FORM;Lo;0;AL; 0643;;;;N;GLYPH FOR ISOLATE ARABIC CAF;;;; FEDA;ARABIC LETTER KAF FINAL FORM;Lo;0;AL; 0643;;;;N;GLYPH FOR FINAL ARABIC CAF;;;; FEDB;ARABIC LETTER KAF INITIAL FORM;Lo;0;AL; 0643;;;;N;GLYPH FOR INITIAL ARABIC CAF;;;; FEDC;ARABIC LETTER KAF MEDIAL FORM;Lo;0;AL; 0643;;;;N;GLYPH FOR MEDIAL ARABIC CAF;;;; FEDD;ARABIC LETTER LAM ISOLATED FORM;Lo;0;AL; 0644;;;;N;GLYPH FOR ISOLATE ARABIC LAM;;;; FEDE;ARABIC LETTER LAM FINAL FORM;Lo;0;AL; 0644;;;;N;GLYPH FOR FINAL ARABIC LAM;;;; FEDF;ARABIC LETTER LAM INITIAL FORM;Lo;0;AL; 0644;;;;N;GLYPH FOR INITIAL ARABIC LAM;;;; FEE0;ARABIC LETTER LAM MEDIAL FORM;Lo;0;AL; 0644;;;;N;GLYPH FOR MEDIAL ARABIC LAM;;;; FEE1;ARABIC LETTER MEEM ISOLATED FORM;Lo;0;AL; 0645;;;;N;GLYPH FOR ISOLATE ARABIC MEEM;;;; FEE2;ARABIC LETTER MEEM FINAL FORM;Lo;0;AL; 0645;;;;N;GLYPH FOR FINAL ARABIC MEEM;;;; FEE3;ARABIC LETTER MEEM INITIAL FORM;Lo;0;AL; 0645;;;;N;GLYPH FOR INITIAL ARABIC MEEM;;;; FEE4;ARABIC LETTER MEEM MEDIAL FORM;Lo;0;AL; 0645;;;;N;GLYPH FOR MEDIAL ARABIC MEEM;;;; FEE5;ARABIC LETTER NOON ISOLATED FORM;Lo;0;AL; 0646;;;;N;GLYPH FOR ISOLATE ARABIC NOON;;;; FEE6;ARABIC LETTER NOON FINAL FORM;Lo;0;AL; 0646;;;;N;GLYPH FOR FINAL ARABIC NOON;;;; FEE7;ARABIC LETTER NOON INITIAL FORM;Lo;0;AL; 0646;;;;N;GLYPH FOR INITIAL ARABIC NOON;;;; FEE8;ARABIC LETTER NOON MEDIAL FORM;Lo;0;AL; 0646;;;;N;GLYPH FOR MEDIAL ARABIC NOON;;;; FEE9;ARABIC LETTER HEH ISOLATED FORM;Lo;0;AL; 0647;;;;N;GLYPH FOR ISOLATE ARABIC HA;;;; FEEA;ARABIC LETTER HEH FINAL FORM;Lo;0;AL; 0647;;;;N;GLYPH FOR FINAL ARABIC HA;;;; FEEB;ARABIC LETTER HEH INITIAL FORM;Lo;0;AL; 0647;;;;N;GLYPH FOR INITIAL ARABIC HA;;;; FEEC;ARABIC LETTER HEH MEDIAL FORM;Lo;0;AL; 0647;;;;N;GLYPH FOR MEDIAL ARABIC HA;;;; FEED;ARABIC LETTER WAW ISOLATED FORM;Lo;0;AL; 0648;;;;N;GLYPH FOR ISOLATE ARABIC WAW;;;; FEEE;ARABIC LETTER WAW FINAL FORM;Lo;0;AL; 0648;;;;N;GLYPH FOR FINAL ARABIC WAW;;;; FEEF;ARABIC LETTER ALEF MAKSURA ISOLATED FORM;Lo;0;AL; 0649;;;;N;GLYPH FOR ISOLATE ARABIC ALEF MAQSURAH;;;; FEF0;ARABIC LETTER ALEF MAKSURA FINAL FORM;Lo;0;AL; 0649;;;;N;GLYPH FOR FINAL ARABIC ALEF MAQSURAH;;;; FEF1;ARABIC LETTER YEH ISOLATED FORM;Lo;0;AL; 064A;;;;N;GLYPH FOR ISOLATE ARABIC YA;;;; FEF2;ARABIC LETTER YEH FINAL FORM;Lo;0;AL; 064A;;;;N;GLYPH FOR FINAL ARABIC YA;;;; FEF3;ARABIC LETTER YEH INITIAL FORM;Lo;0;AL; 064A;;;;N;GLYPH FOR INITIAL ARABIC YA;;;; FEF4;ARABIC LETTER YEH MEDIAL FORM;Lo;0;AL; 064A;;;;N;GLYPH FOR MEDIAL ARABIC YA;;;; FEF5;ARABIC LIGATURE LAM WITH ALEF WITH MADDA ABOVE ISOLATED FORM;Lo;0;AL; 0644 0622;;;;N;GLYPH FOR ISOLATE ARABIC MADDAH ON LIGATURE LAM ALEF;;;; FEF6;ARABIC LIGATURE LAM WITH ALEF WITH MADDA ABOVE FINAL FORM;Lo;0;AL; 0644 0622;;;;N;GLYPH FOR FINAL ARABIC MADDAH ON LIGATURE LAM ALEF;;;; FEF7;ARABIC LIGATURE LAM WITH ALEF WITH HAMZA ABOVE ISOLATED FORM;Lo;0;AL; 0644 0623;;;;N;GLYPH FOR ISOLATE ARABIC HAMZAH ON LIGATURE LAM ALEF;;;; FEF8;ARABIC LIGATURE LAM WITH ALEF WITH HAMZA ABOVE FINAL FORM;Lo;0;AL; 0644 0623;;;;N;GLYPH FOR FINAL ARABIC HAMZAH ON LIGATURE LAM ALEF;;;; FEF9;ARABIC LIGATURE LAM WITH ALEF WITH HAMZA BELOW ISOLATED FORM;Lo;0;AL; 0644 0625;;;;N;GLYPH FOR ISOLATE ARABIC HAMZAH UNDER LIGATURE LAM ALEF;;;; FEFA;ARABIC LIGATURE LAM WITH ALEF WITH HAMZA BELOW FINAL FORM;Lo;0;AL; 0644 0625;;;;N;GLYPH FOR FINAL ARABIC HAMZAH UNDER LIGATURE LAM ALEF;;;; FEFB;ARABIC LIGATURE LAM WITH ALEF ISOLATED FORM;Lo;0;AL; 0644 0627;;;;N;GLYPH FOR ISOLATE ARABIC LIGATURE LAM ALEF;;;; FEFC;ARABIC LIGATURE LAM WITH ALEF FINAL FORM;Lo;0;AL; 0644 0627;;;;N;GLYPH FOR FINAL ARABIC LIGATURE LAM ALEF;;;; FEFF;ZERO WIDTH NO-BREAK SPACE;Cf;0;BN;;;;;N;BYTE ORDER MARK;;;; FF01;FULLWIDTH EXCLAMATION MARK;Po;0;ON; 0021;;;;N;;;;; FF02;FULLWIDTH QUOTATION MARK;Po;0;ON; 0022;;;;N;;;;; FF03;FULLWIDTH NUMBER SIGN;Po;0;ET; 0023;;;;N;;;;; FF04;FULLWIDTH DOLLAR SIGN;Sc;0;ET; 0024;;;;N;;;;; FF05;FULLWIDTH PERCENT SIGN;Po;0;ET; 0025;;;;N;;;;; FF06;FULLWIDTH AMPERSAND;Po;0;ON; 0026;;;;N;;;;; FF07;FULLWIDTH APOSTROPHE;Po;0;ON; 0027;;;;N;;;;; FF08;FULLWIDTH LEFT PARENTHESIS;Ps;0;ON; 0028;;;;Y;FULLWIDTH OPENING PARENTHESIS;;;; FF09;FULLWIDTH RIGHT PARENTHESIS;Pe;0;ON; 0029;;;;Y;FULLWIDTH CLOSING PARENTHESIS;;;; FF0A;FULLWIDTH ASTERISK;Po;0;ON; 002A;;;;N;;;;; FF0B;FULLWIDTH PLUS SIGN;Sm;0;ES; 002B;;;;N;;;;; FF0C;FULLWIDTH COMMA;Po;0;CS; 002C;;;;N;;;;; FF0D;FULLWIDTH HYPHEN-MINUS;Pd;0;ES; 002D;;;;N;;;;; FF0E;FULLWIDTH FULL STOP;Po;0;CS; 002E;;;;N;FULLWIDTH PERIOD;;;; FF0F;FULLWIDTH SOLIDUS;Po;0;CS; 002F;;;;N;FULLWIDTH SLASH;;;; FF10;FULLWIDTH DIGIT ZERO;Nd;0;EN; 0030;0;0;0;N;;;;; FF11;FULLWIDTH DIGIT ONE;Nd;0;EN; 0031;1;1;1;N;;;;; FF12;FULLWIDTH DIGIT TWO;Nd;0;EN; 0032;2;2;2;N;;;;; FF13;FULLWIDTH DIGIT THREE;Nd;0;EN; 0033;3;3;3;N;;;;; FF14;FULLWIDTH DIGIT FOUR;Nd;0;EN; 0034;4;4;4;N;;;;; FF15;FULLWIDTH DIGIT FIVE;Nd;0;EN; 0035;5;5;5;N;;;;; FF16;FULLWIDTH DIGIT SIX;Nd;0;EN; 0036;6;6;6;N;;;;; FF17;FULLWIDTH DIGIT SEVEN;Nd;0;EN; 0037;7;7;7;N;;;;; FF18;FULLWIDTH DIGIT EIGHT;Nd;0;EN; 0038;8;8;8;N;;;;; FF19;FULLWIDTH DIGIT NINE;Nd;0;EN; 0039;9;9;9;N;;;;; FF1A;FULLWIDTH COLON;Po;0;CS; 003A;;;;N;;;;; FF1B;FULLWIDTH SEMICOLON;Po;0;ON; 003B;;;;N;;;;; FF1C;FULLWIDTH LESS-THAN SIGN;Sm;0;ON; 003C;;;;Y;;;;; FF1D;FULLWIDTH EQUALS SIGN;Sm;0;ON; 003D;;;;N;;;;; FF1E;FULLWIDTH GREATER-THAN SIGN;Sm;0;ON; 003E;;;;Y;;;;; FF1F;FULLWIDTH QUESTION MARK;Po;0;ON; 003F;;;;N;;;;; FF20;FULLWIDTH COMMERCIAL AT;Po;0;ON; 0040;;;;N;;;;; FF21;FULLWIDTH LATIN CAPITAL LETTER A;Lu;0;L; 0041;;;;N;;;;FF41; FF22;FULLWIDTH LATIN CAPITAL LETTER B;Lu;0;L; 0042;;;;N;;;;FF42; FF23;FULLWIDTH LATIN CAPITAL LETTER C;Lu;0;L; 0043;;;;N;;;;FF43; FF24;FULLWIDTH LATIN CAPITAL LETTER D;Lu;0;L; 0044;;;;N;;;;FF44; FF25;FULLWIDTH LATIN CAPITAL LETTER E;Lu;0;L; 0045;;;;N;;;;FF45; FF26;FULLWIDTH LATIN CAPITAL LETTER F;Lu;0;L; 0046;;;;N;;;;FF46; FF27;FULLWIDTH LATIN CAPITAL LETTER G;Lu;0;L; 0047;;;;N;;;;FF47; FF28;FULLWIDTH LATIN CAPITAL LETTER H;Lu;0;L; 0048;;;;N;;;;FF48; FF29;FULLWIDTH LATIN CAPITAL LETTER I;Lu;0;L; 0049;;;;N;;;;FF49; FF2A;FULLWIDTH LATIN CAPITAL LETTER J;Lu;0;L; 004A;;;;N;;;;FF4A; FF2B;FULLWIDTH LATIN CAPITAL LETTER K;Lu;0;L; 004B;;;;N;;;;FF4B; FF2C;FULLWIDTH LATIN CAPITAL LETTER L;Lu;0;L; 004C;;;;N;;;;FF4C; FF2D;FULLWIDTH LATIN CAPITAL LETTER M;Lu;0;L; 004D;;;;N;;;;FF4D; FF2E;FULLWIDTH LATIN CAPITAL LETTER N;Lu;0;L; 004E;;;;N;;;;FF4E; FF2F;FULLWIDTH LATIN CAPITAL LETTER O;Lu;0;L; 004F;;;;N;;;;FF4F; FF30;FULLWIDTH LATIN CAPITAL LETTER P;Lu;0;L; 0050;;;;N;;;;FF50; FF31;FULLWIDTH LATIN CAPITAL LETTER Q;Lu;0;L; 0051;;;;N;;;;FF51; FF32;FULLWIDTH LATIN CAPITAL LETTER R;Lu;0;L; 0052;;;;N;;;;FF52; FF33;FULLWIDTH LATIN CAPITAL LETTER S;Lu;0;L; 0053;;;;N;;;;FF53; FF34;FULLWIDTH LATIN CAPITAL LETTER T;Lu;0;L; 0054;;;;N;;;;FF54; FF35;FULLWIDTH LATIN CAPITAL LETTER U;Lu;0;L; 0055;;;;N;;;;FF55; FF36;FULLWIDTH LATIN CAPITAL LETTER V;Lu;0;L; 0056;;;;N;;;;FF56; FF37;FULLWIDTH LATIN CAPITAL LETTER W;Lu;0;L; 0057;;;;N;;;;FF57; FF38;FULLWIDTH LATIN CAPITAL LETTER X;Lu;0;L; 0058;;;;N;;;;FF58; FF39;FULLWIDTH LATIN CAPITAL LETTER Y;Lu;0;L; 0059;;;;N;;;;FF59; FF3A;FULLWIDTH LATIN CAPITAL LETTER Z;Lu;0;L; 005A;;;;N;;;;FF5A; FF3B;FULLWIDTH LEFT SQUARE BRACKET;Ps;0;ON; 005B;;;;Y;FULLWIDTH OPENING SQUARE BRACKET;;;; FF3C;FULLWIDTH REVERSE SOLIDUS;Po;0;ON; 005C;;;;N;FULLWIDTH BACKSLASH;;;; FF3D;FULLWIDTH RIGHT SQUARE BRACKET;Pe;0;ON; 005D;;;;Y;FULLWIDTH CLOSING SQUARE BRACKET;;;; FF3E;FULLWIDTH CIRCUMFLEX ACCENT;Sk;0;ON; 005E;;;;N;FULLWIDTH SPACING CIRCUMFLEX;;;; FF3F;FULLWIDTH LOW LINE;Pc;0;ON; 005F;;;;N;FULLWIDTH SPACING UNDERSCORE;;;; FF40;FULLWIDTH GRAVE ACCENT;Sk;0;ON; 0060;;;;N;FULLWIDTH SPACING GRAVE;;;; FF41;FULLWIDTH LATIN SMALL LETTER A;Ll;0;L; 0061;;;;N;;;FF21;;FF21 FF42;FULLWIDTH LATIN SMALL LETTER B;Ll;0;L; 0062;;;;N;;;FF22;;FF22 FF43;FULLWIDTH LATIN SMALL LETTER C;Ll;0;L; 0063;;;;N;;;FF23;;FF23 FF44;FULLWIDTH LATIN SMALL LETTER D;Ll;0;L; 0064;;;;N;;;FF24;;FF24 FF45;FULLWIDTH LATIN SMALL LETTER E;Ll;0;L; 0065;;;;N;;;FF25;;FF25 FF46;FULLWIDTH LATIN SMALL LETTER F;Ll;0;L; 0066;;;;N;;;FF26;;FF26 FF47;FULLWIDTH LATIN SMALL LETTER G;Ll;0;L; 0067;;;;N;;;FF27;;FF27 FF48;FULLWIDTH LATIN SMALL LETTER H;Ll;0;L; 0068;;;;N;;;FF28;;FF28 FF49;FULLWIDTH LATIN SMALL LETTER I;Ll;0;L; 0069;;;;N;;;FF29;;FF29 FF4A;FULLWIDTH LATIN SMALL LETTER J;Ll;0;L; 006A;;;;N;;;FF2A;;FF2A FF4B;FULLWIDTH LATIN SMALL LETTER K;Ll;0;L; 006B;;;;N;;;FF2B;;FF2B FF4C;FULLWIDTH LATIN SMALL LETTER L;Ll;0;L; 006C;;;;N;;;FF2C;;FF2C FF4D;FULLWIDTH LATIN SMALL LETTER M;Ll;0;L; 006D;;;;N;;;FF2D;;FF2D FF4E;FULLWIDTH LATIN SMALL LETTER N;Ll;0;L; 006E;;;;N;;;FF2E;;FF2E FF4F;FULLWIDTH LATIN SMALL LETTER O;Ll;0;L; 006F;;;;N;;;FF2F;;FF2F FF50;FULLWIDTH LATIN SMALL LETTER P;Ll;0;L; 0070;;;;N;;;FF30;;FF30 FF51;FULLWIDTH LATIN SMALL LETTER Q;Ll;0;L; 0071;;;;N;;;FF31;;FF31 FF52;FULLWIDTH LATIN SMALL LETTER R;Ll;0;L; 0072;;;;N;;;FF32;;FF32 FF53;FULLWIDTH LATIN SMALL LETTER S;Ll;0;L; 0073;;;;N;;;FF33;;FF33 FF54;FULLWIDTH LATIN SMALL LETTER T;Ll;0;L; 0074;;;;N;;;FF34;;FF34 FF55;FULLWIDTH LATIN SMALL LETTER U;Ll;0;L; 0075;;;;N;;;FF35;;FF35 FF56;FULLWIDTH LATIN SMALL LETTER V;Ll;0;L; 0076;;;;N;;;FF36;;FF36 FF57;FULLWIDTH LATIN SMALL LETTER W;Ll;0;L; 0077;;;;N;;;FF37;;FF37 FF58;FULLWIDTH LATIN SMALL LETTER X;Ll;0;L; 0078;;;;N;;;FF38;;FF38 FF59;FULLWIDTH LATIN SMALL LETTER Y;Ll;0;L; 0079;;;;N;;;FF39;;FF39 FF5A;FULLWIDTH LATIN SMALL LETTER Z;Ll;0;L; 007A;;;;N;;;FF3A;;FF3A FF5B;FULLWIDTH LEFT CURLY BRACKET;Ps;0;ON; 007B;;;;Y;FULLWIDTH OPENING CURLY BRACKET;;;; FF5C;FULLWIDTH VERTICAL LINE;Sm;0;ON; 007C;;;;N;FULLWIDTH VERTICAL BAR;;;; FF5D;FULLWIDTH RIGHT CURLY BRACKET;Pe;0;ON; 007D;;;;Y;FULLWIDTH CLOSING CURLY BRACKET;;;; FF5E;FULLWIDTH TILDE;Sm;0;ON; 007E;;;;N;FULLWIDTH SPACING TILDE;;;; FF5F;FULLWIDTH LEFT WHITE PARENTHESIS;Ps;0;ON; 2985;;;;Y;;;;; FF60;FULLWIDTH RIGHT WHITE PARENTHESIS;Pe;0;ON; 2986;;;;Y;;;;; FF61;HALFWIDTH IDEOGRAPHIC FULL STOP;Po;0;ON; 3002;;;;N;HALFWIDTH IDEOGRAPHIC PERIOD;;;; FF62;HALFWIDTH LEFT CORNER BRACKET;Ps;0;ON; 300C;;;;Y;HALFWIDTH OPENING CORNER BRACKET;;;; FF63;HALFWIDTH RIGHT CORNER BRACKET;Pe;0;ON; 300D;;;;Y;HALFWIDTH CLOSING CORNER BRACKET;;;; FF64;HALFWIDTH IDEOGRAPHIC COMMA;Po;0;ON; 3001;;;;N;;;;; FF65;HALFWIDTH KATAKANA MIDDLE DOT;Po;0;ON; 30FB;;;;N;;;;; FF66;HALFWIDTH KATAKANA LETTER WO;Lo;0;L; 30F2;;;;N;;;;; FF67;HALFWIDTH KATAKANA LETTER SMALL A;Lo;0;L; 30A1;;;;N;;;;; FF68;HALFWIDTH KATAKANA LETTER SMALL I;Lo;0;L; 30A3;;;;N;;;;; FF69;HALFWIDTH KATAKANA LETTER SMALL U;Lo;0;L; 30A5;;;;N;;;;; FF6A;HALFWIDTH KATAKANA LETTER SMALL E;Lo;0;L; 30A7;;;;N;;;;; FF6B;HALFWIDTH KATAKANA LETTER SMALL O;Lo;0;L; 30A9;;;;N;;;;; FF6C;HALFWIDTH KATAKANA LETTER SMALL YA;Lo;0;L; 30E3;;;;N;;;;; FF6D;HALFWIDTH KATAKANA LETTER SMALL YU;Lo;0;L; 30E5;;;;N;;;;; FF6E;HALFWIDTH KATAKANA LETTER SMALL YO;Lo;0;L; 30E7;;;;N;;;;; FF6F;HALFWIDTH KATAKANA LETTER SMALL TU;Lo;0;L; 30C3;;;;N;;;;; FF70;HALFWIDTH KATAKANA-HIRAGANA PROLONGED SOUND MARK;Lm;0;L; 30FC;;;;N;;;;; FF71;HALFWIDTH KATAKANA LETTER A;Lo;0;L; 30A2;;;;N;;;;; FF72;HALFWIDTH KATAKANA LETTER I;Lo;0;L; 30A4;;;;N;;;;; FF73;HALFWIDTH KATAKANA LETTER U;Lo;0;L; 30A6;;;;N;;;;; FF74;HALFWIDTH KATAKANA LETTER E;Lo;0;L; 30A8;;;;N;;;;; FF75;HALFWIDTH KATAKANA LETTER O;Lo;0;L; 30AA;;;;N;;;;; FF76;HALFWIDTH KATAKANA LETTER KA;Lo;0;L; 30AB;;;;N;;;;; FF77;HALFWIDTH KATAKANA LETTER KI;Lo;0;L; 30AD;;;;N;;;;; FF78;HALFWIDTH KATAKANA LETTER KU;Lo;0;L; 30AF;;;;N;;;;; FF79;HALFWIDTH KATAKANA LETTER KE;Lo;0;L; 30B1;;;;N;;;;; FF7A;HALFWIDTH KATAKANA LETTER KO;Lo;0;L; 30B3;;;;N;;;;; FF7B;HALFWIDTH KATAKANA LETTER SA;Lo;0;L; 30B5;;;;N;;;;; FF7C;HALFWIDTH KATAKANA LETTER SI;Lo;0;L; 30B7;;;;N;;;;; FF7D;HALFWIDTH KATAKANA LETTER SU;Lo;0;L; 30B9;;;;N;;;;; FF7E;HALFWIDTH KATAKANA LETTER SE;Lo;0;L; 30BB;;;;N;;;;; FF7F;HALFWIDTH KATAKANA LETTER SO;Lo;0;L; 30BD;;;;N;;;;; FF80;HALFWIDTH KATAKANA LETTER TA;Lo;0;L; 30BF;;;;N;;;;; FF81;HALFWIDTH KATAKANA LETTER TI;Lo;0;L; 30C1;;;;N;;;;; FF82;HALFWIDTH KATAKANA LETTER TU;Lo;0;L; 30C4;;;;N;;;;; FF83;HALFWIDTH KATAKANA LETTER TE;Lo;0;L; 30C6;;;;N;;;;; FF84;HALFWIDTH KATAKANA LETTER TO;Lo;0;L; 30C8;;;;N;;;;; FF85;HALFWIDTH KATAKANA LETTER NA;Lo;0;L; 30CA;;;;N;;;;; FF86;HALFWIDTH KATAKANA LETTER NI;Lo;0;L; 30CB;;;;N;;;;; FF87;HALFWIDTH KATAKANA LETTER NU;Lo;0;L; 30CC;;;;N;;;;; FF88;HALFWIDTH KATAKANA LETTER NE;Lo;0;L; 30CD;;;;N;;;;; FF89;HALFWIDTH KATAKANA LETTER NO;Lo;0;L; 30CE;;;;N;;;;; FF8A;HALFWIDTH KATAKANA LETTER HA;Lo;0;L; 30CF;;;;N;;;;; FF8B;HALFWIDTH KATAKANA LETTER HI;Lo;0;L; 30D2;;;;N;;;;; FF8C;HALFWIDTH KATAKANA LETTER HU;Lo;0;L; 30D5;;;;N;;;;; FF8D;HALFWIDTH KATAKANA LETTER HE;Lo;0;L; 30D8;;;;N;;;;; FF8E;HALFWIDTH KATAKANA LETTER HO;Lo;0;L; 30DB;;;;N;;;;; FF8F;HALFWIDTH KATAKANA LETTER MA;Lo;0;L; 30DE;;;;N;;;;; FF90;HALFWIDTH KATAKANA LETTER MI;Lo;0;L; 30DF;;;;N;;;;; FF91;HALFWIDTH KATAKANA LETTER MU;Lo;0;L; 30E0;;;;N;;;;; FF92;HALFWIDTH KATAKANA LETTER ME;Lo;0;L; 30E1;;;;N;;;;; FF93;HALFWIDTH KATAKANA LETTER MO;Lo;0;L; 30E2;;;;N;;;;; FF94;HALFWIDTH KATAKANA LETTER YA;Lo;0;L; 30E4;;;;N;;;;; FF95;HALFWIDTH KATAKANA LETTER YU;Lo;0;L; 30E6;;;;N;;;;; FF96;HALFWIDTH KATAKANA LETTER YO;Lo;0;L; 30E8;;;;N;;;;; FF97;HALFWIDTH KATAKANA LETTER RA;Lo;0;L; 30E9;;;;N;;;;; FF98;HALFWIDTH KATAKANA LETTER RI;Lo;0;L; 30EA;;;;N;;;;; FF99;HALFWIDTH KATAKANA LETTER RU;Lo;0;L; 30EB;;;;N;;;;; FF9A;HALFWIDTH KATAKANA LETTER RE;Lo;0;L; 30EC;;;;N;;;;; FF9B;HALFWIDTH KATAKANA LETTER RO;Lo;0;L; 30ED;;;;N;;;;; FF9C;HALFWIDTH KATAKANA LETTER WA;Lo;0;L; 30EF;;;;N;;;;; FF9D;HALFWIDTH KATAKANA LETTER N;Lo;0;L; 30F3;;;;N;;;;; FF9E;HALFWIDTH KATAKANA VOICED SOUND MARK;Lm;0;L; 3099;;;;N;;;;; FF9F;HALFWIDTH KATAKANA SEMI-VOICED SOUND MARK;Lm;0;L; 309A;;;;N;;;;; FFA0;HALFWIDTH HANGUL FILLER;Lo;0;L; 3164;;;;N;HALFWIDTH HANGUL CAE OM;;;; FFA1;HALFWIDTH HANGUL LETTER KIYEOK;Lo;0;L; 3131;;;;N;HALFWIDTH HANGUL LETTER GIYEOG;;;; FFA2;HALFWIDTH HANGUL LETTER SSANGKIYEOK;Lo;0;L; 3132;;;;N;HALFWIDTH HANGUL LETTER SSANG GIYEOG;;;; FFA3;HALFWIDTH HANGUL LETTER KIYEOK-SIOS;Lo;0;L; 3133;;;;N;HALFWIDTH HANGUL LETTER GIYEOG SIOS;;;; FFA4;HALFWIDTH HANGUL LETTER NIEUN;Lo;0;L; 3134;;;;N;;;;; FFA5;HALFWIDTH HANGUL LETTER NIEUN-CIEUC;Lo;0;L; 3135;;;;N;HALFWIDTH HANGUL LETTER NIEUN JIEUJ;;;; FFA6;HALFWIDTH HANGUL LETTER NIEUN-HIEUH;Lo;0;L; 3136;;;;N;HALFWIDTH HANGUL LETTER NIEUN HIEUH;;;; FFA7;HALFWIDTH HANGUL LETTER TIKEUT;Lo;0;L; 3137;;;;N;HALFWIDTH HANGUL LETTER DIGEUD;;;; FFA8;HALFWIDTH HANGUL LETTER SSANGTIKEUT;Lo;0;L; 3138;;;;N;HALFWIDTH HANGUL LETTER SSANG DIGEUD;;;; FFA9;HALFWIDTH HANGUL LETTER RIEUL;Lo;0;L; 3139;;;;N;HALFWIDTH HANGUL LETTER LIEUL;;;; FFAA;HALFWIDTH HANGUL LETTER RIEUL-KIYEOK;Lo;0;L; 313A;;;;N;HALFWIDTH HANGUL LETTER LIEUL GIYEOG;;;; FFAB;HALFWIDTH HANGUL LETTER RIEUL-MIEUM;Lo;0;L; 313B;;;;N;HALFWIDTH HANGUL LETTER LIEUL MIEUM;;;; FFAC;HALFWIDTH HANGUL LETTER RIEUL-PIEUP;Lo;0;L; 313C;;;;N;HALFWIDTH HANGUL LETTER LIEUL BIEUB;;;; FFAD;HALFWIDTH HANGUL LETTER RIEUL-SIOS;Lo;0;L; 313D;;;;N;HALFWIDTH HANGUL LETTER LIEUL SIOS;;;; FFAE;HALFWIDTH HANGUL LETTER RIEUL-THIEUTH;Lo;0;L; 313E;;;;N;HALFWIDTH HANGUL LETTER LIEUL TIEUT;;;; FFAF;HALFWIDTH HANGUL LETTER RIEUL-PHIEUPH;Lo;0;L; 313F;;;;N;HALFWIDTH HANGUL LETTER LIEUL PIEUP;;;; FFB0;HALFWIDTH HANGUL LETTER RIEUL-HIEUH;Lo;0;L; 3140;;;;N;HALFWIDTH HANGUL LETTER LIEUL HIEUH;;;; FFB1;HALFWIDTH HANGUL LETTER MIEUM;Lo;0;L; 3141;;;;N;;;;; FFB2;HALFWIDTH HANGUL LETTER PIEUP;Lo;0;L; 3142;;;;N;HALFWIDTH HANGUL LETTER BIEUB;;;; FFB3;HALFWIDTH HANGUL LETTER SSANGPIEUP;Lo;0;L; 3143;;;;N;HALFWIDTH HANGUL LETTER SSANG BIEUB;;;; FFB4;HALFWIDTH HANGUL LETTER PIEUP-SIOS;Lo;0;L; 3144;;;;N;HALFWIDTH HANGUL LETTER BIEUB SIOS;;;; FFB5;HALFWIDTH HANGUL LETTER SIOS;Lo;0;L; 3145;;;;N;;;;; FFB6;HALFWIDTH HANGUL LETTER SSANGSIOS;Lo;0;L; 3146;;;;N;HALFWIDTH HANGUL LETTER SSANG SIOS;;;; FFB7;HALFWIDTH HANGUL LETTER IEUNG;Lo;0;L; 3147;;;;N;;;;; FFB8;HALFWIDTH HANGUL LETTER CIEUC;Lo;0;L; 3148;;;;N;HALFWIDTH HANGUL LETTER JIEUJ;;;; FFB9;HALFWIDTH HANGUL LETTER SSANGCIEUC;Lo;0;L; 3149;;;;N;HALFWIDTH HANGUL LETTER SSANG JIEUJ;;;; FFBA;HALFWIDTH HANGUL LETTER CHIEUCH;Lo;0;L; 314A;;;;N;HALFWIDTH HANGUL LETTER CIEUC;;;; FFBB;HALFWIDTH HANGUL LETTER KHIEUKH;Lo;0;L; 314B;;;;N;HALFWIDTH HANGUL LETTER KIYEOK;;;; FFBC;HALFWIDTH HANGUL LETTER THIEUTH;Lo;0;L; 314C;;;;N;HALFWIDTH HANGUL LETTER TIEUT;;;; FFBD;HALFWIDTH HANGUL LETTER PHIEUPH;Lo;0;L; 314D;;;;N;HALFWIDTH HANGUL LETTER PIEUP;;;; FFBE;HALFWIDTH HANGUL LETTER HIEUH;Lo;0;L; 314E;;;;N;;;;; FFC2;HALFWIDTH HANGUL LETTER A;Lo;0;L; 314F;;;;N;;;;; FFC3;HALFWIDTH HANGUL LETTER AE;Lo;0;L; 3150;;;;N;;;;; FFC4;HALFWIDTH HANGUL LETTER YA;Lo;0;L; 3151;;;;N;;;;; FFC5;HALFWIDTH HANGUL LETTER YAE;Lo;0;L; 3152;;;;N;;;;; FFC6;HALFWIDTH HANGUL LETTER EO;Lo;0;L; 3153;;;;N;;;;; FFC7;HALFWIDTH HANGUL LETTER E;Lo;0;L; 3154;;;;N;;;;; FFCA;HALFWIDTH HANGUL LETTER YEO;Lo;0;L; 3155;;;;N;;;;; FFCB;HALFWIDTH HANGUL LETTER YE;Lo;0;L; 3156;;;;N;;;;; FFCC;HALFWIDTH HANGUL LETTER O;Lo;0;L; 3157;;;;N;;;;; FFCD;HALFWIDTH HANGUL LETTER WA;Lo;0;L; 3158;;;;N;;;;; FFCE;HALFWIDTH HANGUL LETTER WAE;Lo;0;L; 3159;;;;N;;;;; FFCF;HALFWIDTH HANGUL LETTER OE;Lo;0;L; 315A;;;;N;;;;; FFD2;HALFWIDTH HANGUL LETTER YO;Lo;0;L; 315B;;;;N;;;;; FFD3;HALFWIDTH HANGUL LETTER U;Lo;0;L; 315C;;;;N;;;;; FFD4;HALFWIDTH HANGUL LETTER WEO;Lo;0;L; 315D;;;;N;;;;; FFD5;HALFWIDTH HANGUL LETTER WE;Lo;0;L; 315E;;;;N;;;;; FFD6;HALFWIDTH HANGUL LETTER WI;Lo;0;L; 315F;;;;N;;;;; FFD7;HALFWIDTH HANGUL LETTER YU;Lo;0;L; 3160;;;;N;;;;; FFDA;HALFWIDTH HANGUL LETTER EU;Lo;0;L; 3161;;;;N;;;;; FFDB;HALFWIDTH HANGUL LETTER YI;Lo;0;L; 3162;;;;N;;;;; FFDC;HALFWIDTH HANGUL LETTER I;Lo;0;L; 3163;;;;N;;;;; FFE0;FULLWIDTH CENT SIGN;Sc;0;ET; 00A2;;;;N;;;;; FFE1;FULLWIDTH POUND SIGN;Sc;0;ET; 00A3;;;;N;;;;; FFE2;FULLWIDTH NOT SIGN;Sm;0;ON; 00AC;;;;N;;;;; FFE3;FULLWIDTH MACRON;Sk;0;ON; 00AF;;;;N;FULLWIDTH SPACING MACRON;;;; FFE4;FULLWIDTH BROKEN BAR;So;0;ON; 00A6;;;;N;FULLWIDTH BROKEN VERTICAL BAR;;;; FFE5;FULLWIDTH YEN SIGN;Sc;0;ET; 00A5;;;;N;;;;; FFE6;FULLWIDTH WON SIGN;Sc;0;ET; 20A9;;;;N;;;;; FFE8;HALFWIDTH FORMS LIGHT VERTICAL;So;0;ON; 2502;;;;N;;;;; FFE9;HALFWIDTH LEFTWARDS ARROW;Sm;0;ON; 2190;;;;N;;;;; FFEA;HALFWIDTH UPWARDS ARROW;Sm;0;ON; 2191;;;;N;;;;; FFEB;HALFWIDTH RIGHTWARDS ARROW;Sm;0;ON; 2192;;;;N;;;;; FFEC;HALFWIDTH DOWNWARDS ARROW;Sm;0;ON; 2193;;;;N;;;;; FFED;HALFWIDTH BLACK SQUARE;So;0;ON; 25A0;;;;N;;;;; FFEE;HALFWIDTH WHITE CIRCLE;So;0;ON; 25CB;;;;N;;;;; FFF9;INTERLINEAR ANNOTATION ANCHOR;Cf;0;ON;;;;;N;;;;; FFFA;INTERLINEAR ANNOTATION SEPARATOR;Cf;0;ON;;;;;N;;;;; FFFB;INTERLINEAR ANNOTATION TERMINATOR;Cf;0;ON;;;;;N;;;;; FFFC;OBJECT REPLACEMENT CHARACTER;So;0;ON;;;;;N;;;;; FFFD;REPLACEMENT CHARACTER;So;0;ON;;;;;N;;;;; 10000;LINEAR B SYLLABLE B008 A;Lo;0;L;;;;;N;;;;; 10001;LINEAR B SYLLABLE B038 E;Lo;0;L;;;;;N;;;;; 10002;LINEAR B SYLLABLE B028 I;Lo;0;L;;;;;N;;;;; 10003;LINEAR B SYLLABLE B061 O;Lo;0;L;;;;;N;;;;; 10004;LINEAR B SYLLABLE B010 U;Lo;0;L;;;;;N;;;;; 10005;LINEAR B SYLLABLE B001 DA;Lo;0;L;;;;;N;;;;; 10006;LINEAR B SYLLABLE B045 DE;Lo;0;L;;;;;N;;;;; 10007;LINEAR B SYLLABLE B007 DI;Lo;0;L;;;;;N;;;;; 10008;LINEAR B SYLLABLE B014 DO;Lo;0;L;;;;;N;;;;; 10009;LINEAR B SYLLABLE B051 DU;Lo;0;L;;;;;N;;;;; 1000A;LINEAR B SYLLABLE B057 JA;Lo;0;L;;;;;N;;;;; 1000B;LINEAR B SYLLABLE B046 JE;Lo;0;L;;;;;N;;;;; 1000D;LINEAR B SYLLABLE B036 JO;Lo;0;L;;;;;N;;;;; 1000E;LINEAR B SYLLABLE B065 JU;Lo;0;L;;;;;N;;;;; 1000F;LINEAR B SYLLABLE B077 KA;Lo;0;L;;;;;N;;;;; 10010;LINEAR B SYLLABLE B044 KE;Lo;0;L;;;;;N;;;;; 10011;LINEAR B SYLLABLE B067 KI;Lo;0;L;;;;;N;;;;; 10012;LINEAR B SYLLABLE B070 KO;Lo;0;L;;;;;N;;;;; 10013;LINEAR B SYLLABLE B081 KU;Lo;0;L;;;;;N;;;;; 10014;LINEAR B SYLLABLE B080 MA;Lo;0;L;;;;;N;;;;; 10015;LINEAR B SYLLABLE B013 ME;Lo;0;L;;;;;N;;;;; 10016;LINEAR B SYLLABLE B073 MI;Lo;0;L;;;;;N;;;;; 10017;LINEAR B SYLLABLE B015 MO;Lo;0;L;;;;;N;;;;; 10018;LINEAR B SYLLABLE B023 MU;Lo;0;L;;;;;N;;;;; 10019;LINEAR B SYLLABLE B006 NA;Lo;0;L;;;;;N;;;;; 1001A;LINEAR B SYLLABLE B024 NE;Lo;0;L;;;;;N;;;;; 1001B;LINEAR B SYLLABLE B030 NI;Lo;0;L;;;;;N;;;;; 1001C;LINEAR B SYLLABLE B052 NO;Lo;0;L;;;;;N;;;;; 1001D;LINEAR B SYLLABLE B055 NU;Lo;0;L;;;;;N;;;;; 1001E;LINEAR B SYLLABLE B003 PA;Lo;0;L;;;;;N;;;;; 1001F;LINEAR B SYLLABLE B072 PE;Lo;0;L;;;;;N;;;;; 10020;LINEAR B SYLLABLE B039 PI;Lo;0;L;;;;;N;;;;; 10021;LINEAR B SYLLABLE B011 PO;Lo;0;L;;;;;N;;;;; 10022;LINEAR B SYLLABLE B050 PU;Lo;0;L;;;;;N;;;;; 10023;LINEAR B SYLLABLE B016 QA;Lo;0;L;;;;;N;;;;; 10024;LINEAR B SYLLABLE B078 QE;Lo;0;L;;;;;N;;;;; 10025;LINEAR B SYLLABLE B021 QI;Lo;0;L;;;;;N;;;;; 10026;LINEAR B SYLLABLE B032 QO;Lo;0;L;;;;;N;;;;; 10028;LINEAR B SYLLABLE B060 RA;Lo;0;L;;;;;N;;;;; 10029;LINEAR B SYLLABLE B027 RE;Lo;0;L;;;;;N;;;;; 1002A;LINEAR B SYLLABLE B053 RI;Lo;0;L;;;;;N;;;;; 1002B;LINEAR B SYLLABLE B002 RO;Lo;0;L;;;;;N;;;;; 1002C;LINEAR B SYLLABLE B026 RU;Lo;0;L;;;;;N;;;;; 1002D;LINEAR B SYLLABLE B031 SA;Lo;0;L;;;;;N;;;;; 1002E;LINEAR B SYLLABLE B009 SE;Lo;0;L;;;;;N;;;;; 1002F;LINEAR B SYLLABLE B041 SI;Lo;0;L;;;;;N;;;;; 10030;LINEAR B SYLLABLE B012 SO;Lo;0;L;;;;;N;;;;; 10031;LINEAR B SYLLABLE B058 SU;Lo;0;L;;;;;N;;;;; 10032;LINEAR B SYLLABLE B059 TA;Lo;0;L;;;;;N;;;;; 10033;LINEAR B SYLLABLE B004 TE;Lo;0;L;;;;;N;;;;; 10034;LINEAR B SYLLABLE B037 TI;Lo;0;L;;;;;N;;;;; 10035;LINEAR B SYLLABLE B005 TO;Lo;0;L;;;;;N;;;;; 10036;LINEAR B SYLLABLE B069 TU;Lo;0;L;;;;;N;;;;; 10037;LINEAR B SYLLABLE B054 WA;Lo;0;L;;;;;N;;;;; 10038;LINEAR B SYLLABLE B075 WE;Lo;0;L;;;;;N;;;;; 10039;LINEAR B SYLLABLE B040 WI;Lo;0;L;;;;;N;;;;; 1003A;LINEAR B SYLLABLE B042 WO;Lo;0;L;;;;;N;;;;; 1003C;LINEAR B SYLLABLE B017 ZA;Lo;0;L;;;;;N;;;;; 1003D;LINEAR B SYLLABLE B074 ZE;Lo;0;L;;;;;N;;;;; 1003F;LINEAR B SYLLABLE B020 ZO;Lo;0;L;;;;;N;;;;; 10040;LINEAR B SYLLABLE B025 A2;Lo;0;L;;;;;N;;;;; 10041;LINEAR B SYLLABLE B043 A3;Lo;0;L;;;;;N;;;;; 10042;LINEAR B SYLLABLE B085 AU;Lo;0;L;;;;;N;;;;; 10043;LINEAR B SYLLABLE B071 DWE;Lo;0;L;;;;;N;;;;; 10044;LINEAR B SYLLABLE B090 DWO;Lo;0;L;;;;;N;;;;; 10045;LINEAR B SYLLABLE B048 NWA;Lo;0;L;;;;;N;;;;; 10046;LINEAR B SYLLABLE B029 PU2;Lo;0;L;;;;;N;;;;; 10047;LINEAR B SYLLABLE B062 PTE;Lo;0;L;;;;;N;;;;; 10048;LINEAR B SYLLABLE B076 RA2;Lo;0;L;;;;;N;;;;; 10049;LINEAR B SYLLABLE B033 RA3;Lo;0;L;;;;;N;;;;; 1004A;LINEAR B SYLLABLE B068 RO2;Lo;0;L;;;;;N;;;;; 1004B;LINEAR B SYLLABLE B066 TA2;Lo;0;L;;;;;N;;;;; 1004C;LINEAR B SYLLABLE B087 TWE;Lo;0;L;;;;;N;;;;; 1004D;LINEAR B SYLLABLE B091 TWO;Lo;0;L;;;;;N;;;;; 10050;LINEAR B SYMBOL B018;Lo;0;L;;;;;N;;;;; 10051;LINEAR B SYMBOL B019;Lo;0;L;;;;;N;;;;; 10052;LINEAR B SYMBOL B022;Lo;0;L;;;;;N;;;;; 10053;LINEAR B SYMBOL B034;Lo;0;L;;;;;N;;;;; 10054;LINEAR B SYMBOL B047;Lo;0;L;;;;;N;;;;; 10055;LINEAR B SYMBOL B049;Lo;0;L;;;;;N;;;;; 10056;LINEAR B SYMBOL B056;Lo;0;L;;;;;N;;;;; 10057;LINEAR B SYMBOL B063;Lo;0;L;;;;;N;;;;; 10058;LINEAR B SYMBOL B064;Lo;0;L;;;;;N;;;;; 10059;LINEAR B SYMBOL B079;Lo;0;L;;;;;N;;;;; 1005A;LINEAR B SYMBOL B082;Lo;0;L;;;;;N;;;;; 1005B;LINEAR B SYMBOL B083;Lo;0;L;;;;;N;;;;; 1005C;LINEAR B SYMBOL B086;Lo;0;L;;;;;N;;;;; 1005D;LINEAR B SYMBOL B089;Lo;0;L;;;;;N;;;;; 10080;LINEAR B IDEOGRAM B100 MAN;Lo;0;L;;;;;N;;;;; 10081;LINEAR B IDEOGRAM B102 WOMAN;Lo;0;L;;;;;N;;;;; 10082;LINEAR B IDEOGRAM B104 DEER;Lo;0;L;;;;;N;;;;; 10083;LINEAR B IDEOGRAM B105 EQUID;Lo;0;L;;;;;N;;;;; 10084;LINEAR B IDEOGRAM B105F MARE;Lo;0;L;;;;;N;;;;; 10085;LINEAR B IDEOGRAM B105M STALLION;Lo;0;L;;;;;N;;;;; 10086;LINEAR B IDEOGRAM B106F EWE;Lo;0;L;;;;;N;;;;; 10087;LINEAR B IDEOGRAM B106M RAM;Lo;0;L;;;;;N;;;;; 10088;LINEAR B IDEOGRAM B107F SHE-GOAT;Lo;0;L;;;;;N;;;;; 10089;LINEAR B IDEOGRAM B107M HE-GOAT;Lo;0;L;;;;;N;;;;; 1008A;LINEAR B IDEOGRAM B108F SOW;Lo;0;L;;;;;N;;;;; 1008B;LINEAR B IDEOGRAM B108M BOAR;Lo;0;L;;;;;N;;;;; 1008C;LINEAR B IDEOGRAM B109F COW;Lo;0;L;;;;;N;;;;; 1008D;LINEAR B IDEOGRAM B109M BULL;Lo;0;L;;;;;N;;;;; 1008E;LINEAR B IDEOGRAM B120 WHEAT;Lo;0;L;;;;;N;;;;; 1008F;LINEAR B IDEOGRAM B121 BARLEY;Lo;0;L;;;;;N;;;;; 10090;LINEAR B IDEOGRAM B122 OLIVE;Lo;0;L;;;;;N;;;;; 10091;LINEAR B IDEOGRAM B123 SPICE;Lo;0;L;;;;;N;;;;; 10092;LINEAR B IDEOGRAM B125 CYPERUS;Lo;0;L;;;;;N;;;;; 10093;LINEAR B MONOGRAM B127 KAPO;Lo;0;L;;;;;N;;;;; 10094;LINEAR B MONOGRAM B128 KANAKO;Lo;0;L;;;;;N;;;;; 10095;LINEAR B IDEOGRAM B130 OIL;Lo;0;L;;;;;N;;;;; 10096;LINEAR B IDEOGRAM B131 WINE;Lo;0;L;;;;;N;;;;; 10097;LINEAR B IDEOGRAM B132;Lo;0;L;;;;;N;;;;; 10098;LINEAR B MONOGRAM B133 AREPA;Lo;0;L;;;;;N;;;;; 10099;LINEAR B MONOGRAM B135 MERI;Lo;0;L;;;;;N;;;;; 1009A;LINEAR B IDEOGRAM B140 BRONZE;Lo;0;L;;;;;N;;;;; 1009B;LINEAR B IDEOGRAM B141 GOLD;Lo;0;L;;;;;N;;;;; 1009C;LINEAR B IDEOGRAM B142;Lo;0;L;;;;;N;;;;; 1009D;LINEAR B IDEOGRAM B145 WOOL;Lo;0;L;;;;;N;;;;; 1009E;LINEAR B IDEOGRAM B146;Lo;0;L;;;;;N;;;;; 1009F;LINEAR B IDEOGRAM B150;Lo;0;L;;;;;N;;;;; 100A0;LINEAR B IDEOGRAM B151 HORN;Lo;0;L;;;;;N;;;;; 100A1;LINEAR B IDEOGRAM B152;Lo;0;L;;;;;N;;;;; 100A2;LINEAR B IDEOGRAM B153;Lo;0;L;;;;;N;;;;; 100A3;LINEAR B IDEOGRAM B154;Lo;0;L;;;;;N;;;;; 100A4;LINEAR B MONOGRAM B156 TURO2;Lo;0;L;;;;;N;;;;; 100A5;LINEAR B IDEOGRAM B157;Lo;0;L;;;;;N;;;;; 100A6;LINEAR B IDEOGRAM B158;Lo;0;L;;;;;N;;;;; 100A7;LINEAR B IDEOGRAM B159 CLOTH;Lo;0;L;;;;;N;;;;; 100A8;LINEAR B IDEOGRAM B160;Lo;0;L;;;;;N;;;;; 100A9;LINEAR B IDEOGRAM B161;Lo;0;L;;;;;N;;;;; 100AA;LINEAR B IDEOGRAM B162 GARMENT;Lo;0;L;;;;;N;;;;; 100AB;LINEAR B IDEOGRAM B163 ARMOUR;Lo;0;L;;;;;N;;;;; 100AC;LINEAR B IDEOGRAM B164;Lo;0;L;;;;;N;;;;; 100AD;LINEAR B IDEOGRAM B165;Lo;0;L;;;;;N;;;;; 100AE;LINEAR B IDEOGRAM B166;Lo;0;L;;;;;N;;;;; 100AF;LINEAR B IDEOGRAM B167;Lo;0;L;;;;;N;;;;; 100B0;LINEAR B IDEOGRAM B168;Lo;0;L;;;;;N;;;;; 100B1;LINEAR B IDEOGRAM B169;Lo;0;L;;;;;N;;;;; 100B2;LINEAR B IDEOGRAM B170;Lo;0;L;;;;;N;;;;; 100B3;LINEAR B IDEOGRAM B171;Lo;0;L;;;;;N;;;;; 100B4;LINEAR B IDEOGRAM B172;Lo;0;L;;;;;N;;;;; 100B5;LINEAR B IDEOGRAM B173 MONTH;Lo;0;L;;;;;N;;;;; 100B6;LINEAR B IDEOGRAM B174;Lo;0;L;;;;;N;;;;; 100B7;LINEAR B IDEOGRAM B176 TREE;Lo;0;L;;;;;N;;;;; 100B8;LINEAR B IDEOGRAM B177;Lo;0;L;;;;;N;;;;; 100B9;LINEAR B IDEOGRAM B178;Lo;0;L;;;;;N;;;;; 100BA;LINEAR B IDEOGRAM B179;Lo;0;L;;;;;N;;;;; 100BB;LINEAR B IDEOGRAM B180;Lo;0;L;;;;;N;;;;; 100BC;LINEAR B IDEOGRAM B181;Lo;0;L;;;;;N;;;;; 100BD;LINEAR B IDEOGRAM B182;Lo;0;L;;;;;N;;;;; 100BE;LINEAR B IDEOGRAM B183;Lo;0;L;;;;;N;;;;; 100BF;LINEAR B IDEOGRAM B184;Lo;0;L;;;;;N;;;;; 100C0;LINEAR B IDEOGRAM B185;Lo;0;L;;;;;N;;;;; 100C1;LINEAR B IDEOGRAM B189;Lo;0;L;;;;;N;;;;; 100C2;LINEAR B IDEOGRAM B190;Lo;0;L;;;;;N;;;;; 100C3;LINEAR B IDEOGRAM B191 HELMET;Lo;0;L;;;;;N;;;;; 100C4;LINEAR B IDEOGRAM B220 FOOTSTOOL;Lo;0;L;;;;;N;;;;; 100C5;LINEAR B IDEOGRAM B225 BATHTUB;Lo;0;L;;;;;N;;;;; 100C6;LINEAR B IDEOGRAM B230 SPEAR;Lo;0;L;;;;;N;;;;; 100C7;LINEAR B IDEOGRAM B231 ARROW;Lo;0;L;;;;;N;;;;; 100C8;LINEAR B IDEOGRAM B232;Lo;0;L;;;;;N;;;;; 100C9;LINEAR B IDEOGRAM B233 SWORD;Lo;0;L;;;;;N;;;;; 100CA;LINEAR B IDEOGRAM B234;Lo;0;L;;;;;N;;;;; 100CB;LINEAR B IDEOGRAM B236;Lo;0;L;;;;;N;;;;; 100CC;LINEAR B IDEOGRAM B240 WHEELED CHARIOT;Lo;0;L;;;;;N;;;;; 100CD;LINEAR B IDEOGRAM B241 CHARIOT;Lo;0;L;;;;;N;;;;; 100CE;LINEAR B IDEOGRAM B242 CHARIOT FRAME;Lo;0;L;;;;;N;;;;; 100CF;LINEAR B IDEOGRAM B243 WHEEL;Lo;0;L;;;;;N;;;;; 100D0;LINEAR B IDEOGRAM B245;Lo;0;L;;;;;N;;;;; 100D1;LINEAR B IDEOGRAM B246;Lo;0;L;;;;;N;;;;; 100D2;LINEAR B MONOGRAM B247 DIPTE;Lo;0;L;;;;;N;;;;; 100D3;LINEAR B IDEOGRAM B248;Lo;0;L;;;;;N;;;;; 100D4;LINEAR B IDEOGRAM B249;Lo;0;L;;;;;N;;;;; 100D5;LINEAR B IDEOGRAM B251;Lo;0;L;;;;;N;;;;; 100D6;LINEAR B IDEOGRAM B252;Lo;0;L;;;;;N;;;;; 100D7;LINEAR B IDEOGRAM B253;Lo;0;L;;;;;N;;;;; 100D8;LINEAR B IDEOGRAM B254 DART;Lo;0;L;;;;;N;;;;; 100D9;LINEAR B IDEOGRAM B255;Lo;0;L;;;;;N;;;;; 100DA;LINEAR B IDEOGRAM B256;Lo;0;L;;;;;N;;;;; 100DB;LINEAR B IDEOGRAM B257;Lo;0;L;;;;;N;;;;; 100DC;LINEAR B IDEOGRAM B258;Lo;0;L;;;;;N;;;;; 100DD;LINEAR B IDEOGRAM B259;Lo;0;L;;;;;N;;;;; 100DE;LINEAR B IDEOGRAM VESSEL B155;Lo;0;L;;;;;N;;;;; 100DF;LINEAR B IDEOGRAM VESSEL B200;Lo;0;L;;;;;N;;;;; 100E0;LINEAR B IDEOGRAM VESSEL B201;Lo;0;L;;;;;N;;;;; 100E1;LINEAR B IDEOGRAM VESSEL B202;Lo;0;L;;;;;N;;;;; 100E2;LINEAR B IDEOGRAM VESSEL B203;Lo;0;L;;;;;N;;;;; 100E3;LINEAR B IDEOGRAM VESSEL B204;Lo;0;L;;;;;N;;;;; 100E4;LINEAR B IDEOGRAM VESSEL B205;Lo;0;L;;;;;N;;;;; 100E5;LINEAR B IDEOGRAM VESSEL B206;Lo;0;L;;;;;N;;;;; 100E6;LINEAR B IDEOGRAM VESSEL B207;Lo;0;L;;;;;N;;;;; 100E7;LINEAR B IDEOGRAM VESSEL B208;Lo;0;L;;;;;N;;;;; 100E8;LINEAR B IDEOGRAM VESSEL B209;Lo;0;L;;;;;N;;;;; 100E9;LINEAR B IDEOGRAM VESSEL B210;Lo;0;L;;;;;N;;;;; 100EA;LINEAR B IDEOGRAM VESSEL B211;Lo;0;L;;;;;N;;;;; 100EB;LINEAR B IDEOGRAM VESSEL B212;Lo;0;L;;;;;N;;;;; 100EC;LINEAR B IDEOGRAM VESSEL B213;Lo;0;L;;;;;N;;;;; 100ED;LINEAR B IDEOGRAM VESSEL B214;Lo;0;L;;;;;N;;;;; 100EE;LINEAR B IDEOGRAM VESSEL B215;Lo;0;L;;;;;N;;;;; 100EF;LINEAR B IDEOGRAM VESSEL B216;Lo;0;L;;;;;N;;;;; 100F0;LINEAR B IDEOGRAM VESSEL B217;Lo;0;L;;;;;N;;;;; 100F1;LINEAR B IDEOGRAM VESSEL B218;Lo;0;L;;;;;N;;;;; 100F2;LINEAR B IDEOGRAM VESSEL B219;Lo;0;L;;;;;N;;;;; 100F3;LINEAR B IDEOGRAM VESSEL B221;Lo;0;L;;;;;N;;;;; 100F4;LINEAR B IDEOGRAM VESSEL B222;Lo;0;L;;;;;N;;;;; 100F5;LINEAR B IDEOGRAM VESSEL B226;Lo;0;L;;;;;N;;;;; 100F6;LINEAR B IDEOGRAM VESSEL B227;Lo;0;L;;;;;N;;;;; 100F7;LINEAR B IDEOGRAM VESSEL B228;Lo;0;L;;;;;N;;;;; 100F8;LINEAR B IDEOGRAM VESSEL B229;Lo;0;L;;;;;N;;;;; 100F9;LINEAR B IDEOGRAM VESSEL B250;Lo;0;L;;;;;N;;;;; 100FA;LINEAR B IDEOGRAM VESSEL B305;Lo;0;L;;;;;N;;;;; 10100;AEGEAN WORD SEPARATOR LINE;Po;0;L;;;;;N;;;;; 10101;AEGEAN WORD SEPARATOR DOT;Po;0;ON;;;;;N;;;;; 10102;AEGEAN CHECK MARK;Po;0;L;;;;;N;;;;; 10107;AEGEAN NUMBER ONE;No;0;L;;;;1;N;;;;; 10108;AEGEAN NUMBER TWO;No;0;L;;;;2;N;;;;; 10109;AEGEAN NUMBER THREE;No;0;L;;;;3;N;;;;; 1010A;AEGEAN NUMBER FOUR;No;0;L;;;;4;N;;;;; 1010B;AEGEAN NUMBER FIVE;No;0;L;;;;5;N;;;;; 1010C;AEGEAN NUMBER SIX;No;0;L;;;;6;N;;;;; 1010D;AEGEAN NUMBER SEVEN;No;0;L;;;;7;N;;;;; 1010E;AEGEAN NUMBER EIGHT;No;0;L;;;;8;N;;;;; 1010F;AEGEAN NUMBER NINE;No;0;L;;;;9;N;;;;; 10110;AEGEAN NUMBER TEN;No;0;L;;;;10;N;;;;; 10111;AEGEAN NUMBER TWENTY;No;0;L;;;;20;N;;;;; 10112;AEGEAN NUMBER THIRTY;No;0;L;;;;30;N;;;;; 10113;AEGEAN NUMBER FORTY;No;0;L;;;;40;N;;;;; 10114;AEGEAN NUMBER FIFTY;No;0;L;;;;50;N;;;;; 10115;AEGEAN NUMBER SIXTY;No;0;L;;;;60;N;;;;; 10116;AEGEAN NUMBER SEVENTY;No;0;L;;;;70;N;;;;; 10117;AEGEAN NUMBER EIGHTY;No;0;L;;;;80;N;;;;; 10118;AEGEAN NUMBER NINETY;No;0;L;;;;90;N;;;;; 10119;AEGEAN NUMBER ONE HUNDRED;No;0;L;;;;100;N;;;;; 1011A;AEGEAN NUMBER TWO HUNDRED;No;0;L;;;;200;N;;;;; 1011B;AEGEAN NUMBER THREE HUNDRED;No;0;L;;;;300;N;;;;; 1011C;AEGEAN NUMBER FOUR HUNDRED;No;0;L;;;;400;N;;;;; 1011D;AEGEAN NUMBER FIVE HUNDRED;No;0;L;;;;500;N;;;;; 1011E;AEGEAN NUMBER SIX HUNDRED;No;0;L;;;;600;N;;;;; 1011F;AEGEAN NUMBER SEVEN HUNDRED;No;0;L;;;;700;N;;;;; 10120;AEGEAN NUMBER EIGHT HUNDRED;No;0;L;;;;800;N;;;;; 10121;AEGEAN NUMBER NINE HUNDRED;No;0;L;;;;900;N;;;;; 10122;AEGEAN NUMBER ONE THOUSAND;No;0;L;;;;1000;N;;;;; 10123;AEGEAN NUMBER TWO THOUSAND;No;0;L;;;;2000;N;;;;; 10124;AEGEAN NUMBER THREE THOUSAND;No;0;L;;;;3000;N;;;;; 10125;AEGEAN NUMBER FOUR THOUSAND;No;0;L;;;;4000;N;;;;; 10126;AEGEAN NUMBER FIVE THOUSAND;No;0;L;;;;5000;N;;;;; 10127;AEGEAN NUMBER SIX THOUSAND;No;0;L;;;;6000;N;;;;; 10128;AEGEAN NUMBER SEVEN THOUSAND;No;0;L;;;;7000;N;;;;; 10129;AEGEAN NUMBER EIGHT THOUSAND;No;0;L;;;;8000;N;;;;; 1012A;AEGEAN NUMBER NINE THOUSAND;No;0;L;;;;9000;N;;;;; 1012B;AEGEAN NUMBER TEN THOUSAND;No;0;L;;;;10000;N;;;;; 1012C;AEGEAN NUMBER TWENTY THOUSAND;No;0;L;;;;20000;N;;;;; 1012D;AEGEAN NUMBER THIRTY THOUSAND;No;0;L;;;;30000;N;;;;; 1012E;AEGEAN NUMBER FORTY THOUSAND;No;0;L;;;;40000;N;;;;; 1012F;AEGEAN NUMBER FIFTY THOUSAND;No;0;L;;;;50000;N;;;;; 10130;AEGEAN NUMBER SIXTY THOUSAND;No;0;L;;;;60000;N;;;;; 10131;AEGEAN NUMBER SEVENTY THOUSAND;No;0;L;;;;70000;N;;;;; 10132;AEGEAN NUMBER EIGHTY THOUSAND;No;0;L;;;;80000;N;;;;; 10133;AEGEAN NUMBER NINETY THOUSAND;No;0;L;;;;90000;N;;;;; 10137;AEGEAN WEIGHT BASE UNIT;So;0;L;;;;;N;;;;; 10138;AEGEAN WEIGHT FIRST SUBUNIT;So;0;L;;;;;N;;;;; 10139;AEGEAN WEIGHT SECOND SUBUNIT;So;0;L;;;;;N;;;;; 1013A;AEGEAN WEIGHT THIRD SUBUNIT;So;0;L;;;;;N;;;;; 1013B;AEGEAN WEIGHT FOURTH SUBUNIT;So;0;L;;;;;N;;;;; 1013C;AEGEAN DRY MEASURE FIRST SUBUNIT;So;0;L;;;;;N;;;;; 1013D;AEGEAN LIQUID MEASURE FIRST SUBUNIT;So;0;L;;;;;N;;;;; 1013E;AEGEAN MEASURE SECOND SUBUNIT;So;0;L;;;;;N;;;;; 1013F;AEGEAN MEASURE THIRD SUBUNIT;So;0;L;;;;;N;;;;; 10140;GREEK ACROPHONIC ATTIC ONE QUARTER;Nl;0;ON;;;;1/4;N;;;;; 10141;GREEK ACROPHONIC ATTIC ONE HALF;Nl;0;ON;;;;1/2;N;;;;; 10142;GREEK ACROPHONIC ATTIC ONE DRACHMA;Nl;0;ON;;;;1;N;;;;; 10143;GREEK ACROPHONIC ATTIC FIVE;Nl;0;ON;;;;5;N;;;;; 10144;GREEK ACROPHONIC ATTIC FIFTY;Nl;0;ON;;;;50;N;;;;; 10145;GREEK ACROPHONIC ATTIC FIVE HUNDRED;Nl;0;ON;;;;500;N;;;;; 10146;GREEK ACROPHONIC ATTIC FIVE THOUSAND;Nl;0;ON;;;;5000;N;;;;; 10147;GREEK ACROPHONIC ATTIC FIFTY THOUSAND;Nl;0;ON;;;;50000;N;;;;; 10148;GREEK ACROPHONIC ATTIC FIVE TALENTS;Nl;0;ON;;;;5;N;;;;; 10149;GREEK ACROPHONIC ATTIC TEN TALENTS;Nl;0;ON;;;;10;N;;;;; 1014A;GREEK ACROPHONIC ATTIC FIFTY TALENTS;Nl;0;ON;;;;50;N;;;;; 1014B;GREEK ACROPHONIC ATTIC ONE HUNDRED TALENTS;Nl;0;ON;;;;100;N;;;;; 1014C;GREEK ACROPHONIC ATTIC FIVE HUNDRED TALENTS;Nl;0;ON;;;;500;N;;;;; 1014D;GREEK ACROPHONIC ATTIC ONE THOUSAND TALENTS;Nl;0;ON;;;;1000;N;;;;; 1014E;GREEK ACROPHONIC ATTIC FIVE THOUSAND TALENTS;Nl;0;ON;;;;5000;N;;;;; 1014F;GREEK ACROPHONIC ATTIC FIVE STATERS;Nl;0;ON;;;;5;N;;;;; 10150;GREEK ACROPHONIC ATTIC TEN STATERS;Nl;0;ON;;;;10;N;;;;; 10151;GREEK ACROPHONIC ATTIC FIFTY STATERS;Nl;0;ON;;;;50;N;;;;; 10152;GREEK ACROPHONIC ATTIC ONE HUNDRED STATERS;Nl;0;ON;;;;100;N;;;;; 10153;GREEK ACROPHONIC ATTIC FIVE HUNDRED STATERS;Nl;0;ON;;;;500;N;;;;; 10154;GREEK ACROPHONIC ATTIC ONE THOUSAND STATERS;Nl;0;ON;;;;1000;N;;;;; 10155;GREEK ACROPHONIC ATTIC TEN THOUSAND STATERS;Nl;0;ON;;;;10000;N;;;;; 10156;GREEK ACROPHONIC ATTIC FIFTY THOUSAND STATERS;Nl;0;ON;;;;50000;N;;;;; 10157;GREEK ACROPHONIC ATTIC TEN MNAS;Nl;0;ON;;;;10;N;;;;; 10158;GREEK ACROPHONIC HERAEUM ONE PLETHRON;Nl;0;ON;;;;1;N;;;;; 10159;GREEK ACROPHONIC THESPIAN ONE;Nl;0;ON;;;;1;N;;;;; 1015A;GREEK ACROPHONIC HERMIONIAN ONE;Nl;0;ON;;;;1;N;;;;; 1015B;GREEK ACROPHONIC EPIDAUREAN TWO;Nl;0;ON;;;;2;N;;;;; 1015C;GREEK ACROPHONIC THESPIAN TWO;Nl;0;ON;;;;2;N;;;;; 1015D;GREEK ACROPHONIC CYRENAIC TWO DRACHMAS;Nl;0;ON;;;;2;N;;;;; 1015E;GREEK ACROPHONIC EPIDAUREAN TWO DRACHMAS;Nl;0;ON;;;;2;N;;;;; 1015F;GREEK ACROPHONIC TROEZENIAN FIVE;Nl;0;ON;;;;5;N;;;;; 10160;GREEK ACROPHONIC TROEZENIAN TEN;Nl;0;ON;;;;10;N;;;;; 10161;GREEK ACROPHONIC TROEZENIAN TEN ALTERNATE FORM;Nl;0;ON;;;;10;N;;;;; 10162;GREEK ACROPHONIC HERMIONIAN TEN;Nl;0;ON;;;;10;N;;;;; 10163;GREEK ACROPHONIC MESSENIAN TEN;Nl;0;ON;;;;10;N;;;;; 10164;GREEK ACROPHONIC THESPIAN TEN;Nl;0;ON;;;;10;N;;;;; 10165;GREEK ACROPHONIC THESPIAN THIRTY;Nl;0;ON;;;;30;N;;;;; 10166;GREEK ACROPHONIC TROEZENIAN FIFTY;Nl;0;ON;;;;50;N;;;;; 10167;GREEK ACROPHONIC TROEZENIAN FIFTY ALTERNATE FORM;Nl;0;ON;;;;50;N;;;;; 10168;GREEK ACROPHONIC HERMIONIAN FIFTY;Nl;0;ON;;;;50;N;;;;; 10169;GREEK ACROPHONIC THESPIAN FIFTY;Nl;0;ON;;;;50;N;;;;; 1016A;GREEK ACROPHONIC THESPIAN ONE HUNDRED;Nl;0;ON;;;;100;N;;;;; 1016B;GREEK ACROPHONIC THESPIAN THREE HUNDRED;Nl;0;ON;;;;300;N;;;;; 1016C;GREEK ACROPHONIC EPIDAUREAN FIVE HUNDRED;Nl;0;ON;;;;500;N;;;;; 1016D;GREEK ACROPHONIC TROEZENIAN FIVE HUNDRED;Nl;0;ON;;;;500;N;;;;; 1016E;GREEK ACROPHONIC THESPIAN FIVE HUNDRED;Nl;0;ON;;;;500;N;;;;; 1016F;GREEK ACROPHONIC CARYSTIAN FIVE HUNDRED;Nl;0;ON;;;;500;N;;;;; 10170;GREEK ACROPHONIC NAXIAN FIVE HUNDRED;Nl;0;ON;;;;500;N;;;;; 10171;GREEK ACROPHONIC THESPIAN ONE THOUSAND;Nl;0;ON;;;;1000;N;;;;; 10172;GREEK ACROPHONIC THESPIAN FIVE THOUSAND;Nl;0;ON;;;;5000;N;;;;; 10173;GREEK ACROPHONIC DELPHIC FIVE MNAS;Nl;0;ON;;;;5;N;;;;; 10174;GREEK ACROPHONIC STRATIAN FIFTY MNAS;Nl;0;ON;;;;50;N;;;;; 10175;GREEK ONE HALF SIGN;No;0;ON;;;;1/2;N;;;;; 10176;GREEK ONE HALF SIGN ALTERNATE FORM;No;0;ON;;;;1/2;N;;;;; 10177;GREEK TWO THIRDS SIGN;No;0;ON;;;;2/3;N;;;;; 10178;GREEK THREE QUARTERS SIGN;No;0;ON;;;;3/4;N;;;;; 10179;GREEK YEAR SIGN;So;0;ON;;;;;N;;;;; 1017A;GREEK TALENT SIGN;So;0;ON;;;;;N;;;;; 1017B;GREEK DRACHMA SIGN;So;0;ON;;;;;N;;;;; 1017C;GREEK OBOL SIGN;So;0;ON;;;;;N;;;;; 1017D;GREEK TWO OBOLS SIGN;So;0;ON;;;;;N;;;;; 1017E;GREEK THREE OBOLS SIGN;So;0;ON;;;;;N;;;;; 1017F;GREEK FOUR OBOLS SIGN;So;0;ON;;;;;N;;;;; 10180;GREEK FIVE OBOLS SIGN;So;0;ON;;;;;N;;;;; 10181;GREEK METRETES SIGN;So;0;ON;;;;;N;;;;; 10182;GREEK KYATHOS BASE SIGN;So;0;ON;;;;;N;;;;; 10183;GREEK LITRA SIGN;So;0;ON;;;;;N;;;;; 10184;GREEK OUNKIA SIGN;So;0;ON;;;;;N;;;;; 10185;GREEK XESTES SIGN;So;0;ON;;;;;N;;;;; 10186;GREEK ARTABE SIGN;So;0;ON;;;;;N;;;;; 10187;GREEK AROURA SIGN;So;0;ON;;;;;N;;;;; 10188;GREEK GRAMMA SIGN;So;0;ON;;;;;N;;;;; 10189;GREEK TRYBLION BASE SIGN;So;0;ON;;;;;N;;;;; 1018A;GREEK ZERO SIGN;No;0;ON;;;;0;N;;;;; 1018B;GREEK ONE QUARTER SIGN;No;0;ON;;;;1/4;N;;;;; 1018C;GREEK SINUSOID SIGN;So;0;ON;;;;;N;;;;; 10190;ROMAN SEXTANS SIGN;So;0;ON;;;;;N;;;;; 10191;ROMAN UNCIA SIGN;So;0;ON;;;;;N;;;;; 10192;ROMAN SEMUNCIA SIGN;So;0;ON;;;;;N;;;;; 10193;ROMAN SEXTULA SIGN;So;0;ON;;;;;N;;;;; 10194;ROMAN DIMIDIA SEXTULA SIGN;So;0;ON;;;;;N;;;;; 10195;ROMAN SILIQUA SIGN;So;0;ON;;;;;N;;;;; 10196;ROMAN DENARIUS SIGN;So;0;ON;;;;;N;;;;; 10197;ROMAN QUINARIUS SIGN;So;0;ON;;;;;N;;;;; 10198;ROMAN SESTERTIUS SIGN;So;0;ON;;;;;N;;;;; 10199;ROMAN DUPONDIUS SIGN;So;0;ON;;;;;N;;;;; 1019A;ROMAN AS SIGN;So;0;ON;;;;;N;;;;; 1019B;ROMAN CENTURIAL SIGN;So;0;ON;;;;;N;;;;; 101A0;GREEK SYMBOL TAU RHO;So;0;ON;;;;;N;;;;; 101D0;PHAISTOS DISC SIGN PEDESTRIAN;So;0;L;;;;;N;;;;; 101D1;PHAISTOS DISC SIGN PLUMED HEAD;So;0;L;;;;;N;;;;; 101D2;PHAISTOS DISC SIGN TATTOOED HEAD;So;0;L;;;;;N;;;;; 101D3;PHAISTOS DISC SIGN CAPTIVE;So;0;L;;;;;N;;;;; 101D4;PHAISTOS DISC SIGN CHILD;So;0;L;;;;;N;;;;; 101D5;PHAISTOS DISC SIGN WOMAN;So;0;L;;;;;N;;;;; 101D6;PHAISTOS DISC SIGN HELMET;So;0;L;;;;;N;;;;; 101D7;PHAISTOS DISC SIGN GAUNTLET;So;0;L;;;;;N;;;;; 101D8;PHAISTOS DISC SIGN TIARA;So;0;L;;;;;N;;;;; 101D9;PHAISTOS DISC SIGN ARROW;So;0;L;;;;;N;;;;; 101DA;PHAISTOS DISC SIGN BOW;So;0;L;;;;;N;;;;; 101DB;PHAISTOS DISC SIGN SHIELD;So;0;L;;;;;N;;;;; 101DC;PHAISTOS DISC SIGN CLUB;So;0;L;;;;;N;;;;; 101DD;PHAISTOS DISC SIGN MANACLES;So;0;L;;;;;N;;;;; 101DE;PHAISTOS DISC SIGN MATTOCK;So;0;L;;;;;N;;;;; 101DF;PHAISTOS DISC SIGN SAW;So;0;L;;;;;N;;;;; 101E0;PHAISTOS DISC SIGN LID;So;0;L;;;;;N;;;;; 101E1;PHAISTOS DISC SIGN BOOMERANG;So;0;L;;;;;N;;;;; 101E2;PHAISTOS DISC SIGN CARPENTRY PLANE;So;0;L;;;;;N;;;;; 101E3;PHAISTOS DISC SIGN DOLIUM;So;0;L;;;;;N;;;;; 101E4;PHAISTOS DISC SIGN COMB;So;0;L;;;;;N;;;;; 101E5;PHAISTOS DISC SIGN SLING;So;0;L;;;;;N;;;;; 101E6;PHAISTOS DISC SIGN COLUMN;So;0;L;;;;;N;;;;; 101E7;PHAISTOS DISC SIGN BEEHIVE;So;0;L;;;;;N;;;;; 101E8;PHAISTOS DISC SIGN SHIP;So;0;L;;;;;N;;;;; 101E9;PHAISTOS DISC SIGN HORN;So;0;L;;;;;N;;;;; 101EA;PHAISTOS DISC SIGN HIDE;So;0;L;;;;;N;;;;; 101EB;PHAISTOS DISC SIGN BULLS LEG;So;0;L;;;;;N;;;;; 101EC;PHAISTOS DISC SIGN CAT;So;0;L;;;;;N;;;;; 101ED;PHAISTOS DISC SIGN RAM;So;0;L;;;;;N;;;;; 101EE;PHAISTOS DISC SIGN EAGLE;So;0;L;;;;;N;;;;; 101EF;PHAISTOS DISC SIGN DOVE;So;0;L;;;;;N;;;;; 101F0;PHAISTOS DISC SIGN TUNNY;So;0;L;;;;;N;;;;; 101F1;PHAISTOS DISC SIGN BEE;So;0;L;;;;;N;;;;; 101F2;PHAISTOS DISC SIGN PLANE TREE;So;0;L;;;;;N;;;;; 101F3;PHAISTOS DISC SIGN VINE;So;0;L;;;;;N;;;;; 101F4;PHAISTOS DISC SIGN PAPYRUS;So;0;L;;;;;N;;;;; 101F5;PHAISTOS DISC SIGN ROSETTE;So;0;L;;;;;N;;;;; 101F6;PHAISTOS DISC SIGN LILY;So;0;L;;;;;N;;;;; 101F7;PHAISTOS DISC SIGN OX BACK;So;0;L;;;;;N;;;;; 101F8;PHAISTOS DISC SIGN FLUTE;So;0;L;;;;;N;;;;; 101F9;PHAISTOS DISC SIGN GRATER;So;0;L;;;;;N;;;;; 101FA;PHAISTOS DISC SIGN STRAINER;So;0;L;;;;;N;;;;; 101FB;PHAISTOS DISC SIGN SMALL AXE;So;0;L;;;;;N;;;;; 101FC;PHAISTOS DISC SIGN WAVY BAND;So;0;L;;;;;N;;;;; 101FD;PHAISTOS DISC SIGN COMBINING OBLIQUE STROKE;Mn;220;NSM;;;;;N;;;;; 10280;LYCIAN LETTER A;Lo;0;L;;;;;N;;;;; 10281;LYCIAN LETTER E;Lo;0;L;;;;;N;;;;; 10282;LYCIAN LETTER B;Lo;0;L;;;;;N;;;;; 10283;LYCIAN LETTER BH;Lo;0;L;;;;;N;;;;; 10284;LYCIAN LETTER G;Lo;0;L;;;;;N;;;;; 10285;LYCIAN LETTER D;Lo;0;L;;;;;N;;;;; 10286;LYCIAN LETTER I;Lo;0;L;;;;;N;;;;; 10287;LYCIAN LETTER W;Lo;0;L;;;;;N;;;;; 10288;LYCIAN LETTER Z;Lo;0;L;;;;;N;;;;; 10289;LYCIAN LETTER TH;Lo;0;L;;;;;N;;;;; 1028A;LYCIAN LETTER J;Lo;0;L;;;;;N;;;;; 1028B;LYCIAN LETTER K;Lo;0;L;;;;;N;;;;; 1028C;LYCIAN LETTER Q;Lo;0;L;;;;;N;;;;; 1028D;LYCIAN LETTER L;Lo;0;L;;;;;N;;;;; 1028E;LYCIAN LETTER M;Lo;0;L;;;;;N;;;;; 1028F;LYCIAN LETTER N;Lo;0;L;;;;;N;;;;; 10290;LYCIAN LETTER MM;Lo;0;L;;;;;N;;;;; 10291;LYCIAN LETTER NN;Lo;0;L;;;;;N;;;;; 10292;LYCIAN LETTER U;Lo;0;L;;;;;N;;;;; 10293;LYCIAN LETTER P;Lo;0;L;;;;;N;;;;; 10294;LYCIAN LETTER KK;Lo;0;L;;;;;N;;;;; 10295;LYCIAN LETTER R;Lo;0;L;;;;;N;;;;; 10296;LYCIAN LETTER S;Lo;0;L;;;;;N;;;;; 10297;LYCIAN LETTER T;Lo;0;L;;;;;N;;;;; 10298;LYCIAN LETTER TT;Lo;0;L;;;;;N;;;;; 10299;LYCIAN LETTER AN;Lo;0;L;;;;;N;;;;; 1029A;LYCIAN LETTER EN;Lo;0;L;;;;;N;;;;; 1029B;LYCIAN LETTER H;Lo;0;L;;;;;N;;;;; 1029C;LYCIAN LETTER X;Lo;0;L;;;;;N;;;;; 102A0;CARIAN LETTER A;Lo;0;L;;;;;N;;;;; 102A1;CARIAN LETTER P2;Lo;0;L;;;;;N;;;;; 102A2;CARIAN LETTER D;Lo;0;L;;;;;N;;;;; 102A3;CARIAN LETTER L;Lo;0;L;;;;;N;;;;; 102A4;CARIAN LETTER UUU;Lo;0;L;;;;;N;;;;; 102A5;CARIAN LETTER R;Lo;0;L;;;;;N;;;;; 102A6;CARIAN LETTER LD;Lo;0;L;;;;;N;;;;; 102A7;CARIAN LETTER A2;Lo;0;L;;;;;N;;;;; 102A8;CARIAN LETTER Q;Lo;0;L;;;;;N;;;;; 102A9;CARIAN LETTER B;Lo;0;L;;;;;N;;;;; 102AA;CARIAN LETTER M;Lo;0;L;;;;;N;;;;; 102AB;CARIAN LETTER O;Lo;0;L;;;;;N;;;;; 102AC;CARIAN LETTER D2;Lo;0;L;;;;;N;;;;; 102AD;CARIAN LETTER T;Lo;0;L;;;;;N;;;;; 102AE;CARIAN LETTER SH;Lo;0;L;;;;;N;;;;; 102AF;CARIAN LETTER SH2;Lo;0;L;;;;;N;;;;; 102B0;CARIAN LETTER S;Lo;0;L;;;;;N;;;;; 102B1;CARIAN LETTER C-18;Lo;0;L;;;;;N;;;;; 102B2;CARIAN LETTER U;Lo;0;L;;;;;N;;;;; 102B3;CARIAN LETTER NN;Lo;0;L;;;;;N;;;;; 102B4;CARIAN LETTER X;Lo;0;L;;;;;N;;;;; 102B5;CARIAN LETTER N;Lo;0;L;;;;;N;;;;; 102B6;CARIAN LETTER TT2;Lo;0;L;;;;;N;;;;; 102B7;CARIAN LETTER P;Lo;0;L;;;;;N;;;;; 102B8;CARIAN LETTER SS;Lo;0;L;;;;;N;;;;; 102B9;CARIAN LETTER I;Lo;0;L;;;;;N;;;;; 102BA;CARIAN LETTER E;Lo;0;L;;;;;N;;;;; 102BB;CARIAN LETTER UUUU;Lo;0;L;;;;;N;;;;; 102BC;CARIAN LETTER K;Lo;0;L;;;;;N;;;;; 102BD;CARIAN LETTER K2;Lo;0;L;;;;;N;;;;; 102BE;CARIAN LETTER ND;Lo;0;L;;;;;N;;;;; 102BF;CARIAN LETTER UU;Lo;0;L;;;;;N;;;;; 102C0;CARIAN LETTER G;Lo;0;L;;;;;N;;;;; 102C1;CARIAN LETTER G2;Lo;0;L;;;;;N;;;;; 102C2;CARIAN LETTER ST;Lo;0;L;;;;;N;;;;; 102C3;CARIAN LETTER ST2;Lo;0;L;;;;;N;;;;; 102C4;CARIAN LETTER NG;Lo;0;L;;;;;N;;;;; 102C5;CARIAN LETTER II;Lo;0;L;;;;;N;;;;; 102C6;CARIAN LETTER C-39;Lo;0;L;;;;;N;;;;; 102C7;CARIAN LETTER TT;Lo;0;L;;;;;N;;;;; 102C8;CARIAN LETTER UUU2;Lo;0;L;;;;;N;;;;; 102C9;CARIAN LETTER RR;Lo;0;L;;;;;N;;;;; 102CA;CARIAN LETTER MB;Lo;0;L;;;;;N;;;;; 102CB;CARIAN LETTER MB2;Lo;0;L;;;;;N;;;;; 102CC;CARIAN LETTER MB3;Lo;0;L;;;;;N;;;;; 102CD;CARIAN LETTER MB4;Lo;0;L;;;;;N;;;;; 102CE;CARIAN LETTER LD2;Lo;0;L;;;;;N;;;;; 102CF;CARIAN LETTER E2;Lo;0;L;;;;;N;;;;; 102D0;CARIAN LETTER UUU3;Lo;0;L;;;;;N;;;;; 102E0;COPTIC EPACT THOUSANDS MARK;Mn;220;NSM;;;;;N;;;;; 102E1;COPTIC EPACT DIGIT ONE;No;0;EN;;;;1;N;;;;; 102E2;COPTIC EPACT DIGIT TWO;No;0;EN;;;;2;N;;;;; 102E3;COPTIC EPACT DIGIT THREE;No;0;EN;;;;3;N;;;;; 102E4;COPTIC EPACT DIGIT FOUR;No;0;EN;;;;4;N;;;;; 102E5;COPTIC EPACT DIGIT FIVE;No;0;EN;;;;5;N;;;;; 102E6;COPTIC EPACT DIGIT SIX;No;0;EN;;;;6;N;;;;; 102E7;COPTIC EPACT DIGIT SEVEN;No;0;EN;;;;7;N;;;;; 102E8;COPTIC EPACT DIGIT EIGHT;No;0;EN;;;;8;N;;;;; 102E9;COPTIC EPACT DIGIT NINE;No;0;EN;;;;9;N;;;;; 102EA;COPTIC EPACT NUMBER TEN;No;0;EN;;;;10;N;;;;; 102EB;COPTIC EPACT NUMBER TWENTY;No;0;EN;;;;20;N;;;;; 102EC;COPTIC EPACT NUMBER THIRTY;No;0;EN;;;;30;N;;;;; 102ED;COPTIC EPACT NUMBER FORTY;No;0;EN;;;;40;N;;;;; 102EE;COPTIC EPACT NUMBER FIFTY;No;0;EN;;;;50;N;;;;; 102EF;COPTIC EPACT NUMBER SIXTY;No;0;EN;;;;60;N;;;;; 102F0;COPTIC EPACT NUMBER SEVENTY;No;0;EN;;;;70;N;;;;; 102F1;COPTIC EPACT NUMBER EIGHTY;No;0;EN;;;;80;N;;;;; 102F2;COPTIC EPACT NUMBER NINETY;No;0;EN;;;;90;N;;;;; 102F3;COPTIC EPACT NUMBER ONE HUNDRED;No;0;EN;;;;100;N;;;;; 102F4;COPTIC EPACT NUMBER TWO HUNDRED;No;0;EN;;;;200;N;;;;; 102F5;COPTIC EPACT NUMBER THREE HUNDRED;No;0;EN;;;;300;N;;;;; 102F6;COPTIC EPACT NUMBER FOUR HUNDRED;No;0;EN;;;;400;N;;;;; 102F7;COPTIC EPACT NUMBER FIVE HUNDRED;No;0;EN;;;;500;N;;;;; 102F8;COPTIC EPACT NUMBER SIX HUNDRED;No;0;EN;;;;600;N;;;;; 102F9;COPTIC EPACT NUMBER SEVEN HUNDRED;No;0;EN;;;;700;N;;;;; 102FA;COPTIC EPACT NUMBER EIGHT HUNDRED;No;0;EN;;;;800;N;;;;; 102FB;COPTIC EPACT NUMBER NINE HUNDRED;No;0;EN;;;;900;N;;;;; 10300;OLD ITALIC LETTER A;Lo;0;L;;;;;N;;;;; 10301;OLD ITALIC LETTER BE;Lo;0;L;;;;;N;;;;; 10302;OLD ITALIC LETTER KE;Lo;0;L;;;;;N;;;;; 10303;OLD ITALIC LETTER DE;Lo;0;L;;;;;N;;;;; 10304;OLD ITALIC LETTER E;Lo;0;L;;;;;N;;;;; 10305;OLD ITALIC LETTER VE;Lo;0;L;;;;;N;;;;; 10306;OLD ITALIC LETTER ZE;Lo;0;L;;;;;N;;;;; 10307;OLD ITALIC LETTER HE;Lo;0;L;;;;;N;;;;; 10308;OLD ITALIC LETTER THE;Lo;0;L;;;;;N;;;;; 10309;OLD ITALIC LETTER I;Lo;0;L;;;;;N;;;;; 1030A;OLD ITALIC LETTER KA;Lo;0;L;;;;;N;;;;; 1030B;OLD ITALIC LETTER EL;Lo;0;L;;;;;N;;;;; 1030C;OLD ITALIC LETTER EM;Lo;0;L;;;;;N;;;;; 1030D;OLD ITALIC LETTER EN;Lo;0;L;;;;;N;;;;; 1030E;OLD ITALIC LETTER ESH;Lo;0;L;;;;;N;;;;; 1030F;OLD ITALIC LETTER O;Lo;0;L;;;;;N;;;;; 10310;OLD ITALIC LETTER PE;Lo;0;L;;;;;N;;;;; 10311;OLD ITALIC LETTER SHE;Lo;0;L;;;;;N;;;;; 10312;OLD ITALIC LETTER KU;Lo;0;L;;;;;N;;;;; 10313;OLD ITALIC LETTER ER;Lo;0;L;;;;;N;;;;; 10314;OLD ITALIC LETTER ES;Lo;0;L;;;;;N;;;;; 10315;OLD ITALIC LETTER TE;Lo;0;L;;;;;N;;;;; 10316;OLD ITALIC LETTER U;Lo;0;L;;;;;N;;;;; 10317;OLD ITALIC LETTER EKS;Lo;0;L;;;;;N;;;;; 10318;OLD ITALIC LETTER PHE;Lo;0;L;;;;;N;;;;; 10319;OLD ITALIC LETTER KHE;Lo;0;L;;;;;N;;;;; 1031A;OLD ITALIC LETTER EF;Lo;0;L;;;;;N;;;;; 1031B;OLD ITALIC LETTER ERS;Lo;0;L;;;;;N;;;;; 1031C;OLD ITALIC LETTER CHE;Lo;0;L;;;;;N;;;;; 1031D;OLD ITALIC LETTER II;Lo;0;L;;;;;N;;;;; 1031E;OLD ITALIC LETTER UU;Lo;0;L;;;;;N;;;;; 1031F;OLD ITALIC LETTER ESS;Lo;0;L;;;;;N;;;;; 10320;OLD ITALIC NUMERAL ONE;No;0;L;;;;1;N;;;;; 10321;OLD ITALIC NUMERAL FIVE;No;0;L;;;;5;N;;;;; 10322;OLD ITALIC NUMERAL TEN;No;0;L;;;;10;N;;;;; 10323;OLD ITALIC NUMERAL FIFTY;No;0;L;;;;50;N;;;;; 10330;GOTHIC LETTER AHSA;Lo;0;L;;;;;N;;;;; 10331;GOTHIC LETTER BAIRKAN;Lo;0;L;;;;;N;;;;; 10332;GOTHIC LETTER GIBA;Lo;0;L;;;;;N;;;;; 10333;GOTHIC LETTER DAGS;Lo;0;L;;;;;N;;;;; 10334;GOTHIC LETTER AIHVUS;Lo;0;L;;;;;N;;;;; 10335;GOTHIC LETTER QAIRTHRA;Lo;0;L;;;;;N;;;;; 10336;GOTHIC LETTER IUJA;Lo;0;L;;;;;N;;;;; 10337;GOTHIC LETTER HAGL;Lo;0;L;;;;;N;;;;; 10338;GOTHIC LETTER THIUTH;Lo;0;L;;;;;N;;;;; 10339;GOTHIC LETTER EIS;Lo;0;L;;;;;N;;;;; 1033A;GOTHIC LETTER KUSMA;Lo;0;L;;;;;N;;;;; 1033B;GOTHIC LETTER LAGUS;Lo;0;L;;;;;N;;;;; 1033C;GOTHIC LETTER MANNA;Lo;0;L;;;;;N;;;;; 1033D;GOTHIC LETTER NAUTHS;Lo;0;L;;;;;N;;;;; 1033E;GOTHIC LETTER JER;Lo;0;L;;;;;N;;;;; 1033F;GOTHIC LETTER URUS;Lo;0;L;;;;;N;;;;; 10340;GOTHIC LETTER PAIRTHRA;Lo;0;L;;;;;N;;;;; 10341;GOTHIC LETTER NINETY;Nl;0;L;;;;90;N;;;;; 10342;GOTHIC LETTER RAIDA;Lo;0;L;;;;;N;;;;; 10343;GOTHIC LETTER SAUIL;Lo;0;L;;;;;N;;;;; 10344;GOTHIC LETTER TEIWS;Lo;0;L;;;;;N;;;;; 10345;GOTHIC LETTER WINJA;Lo;0;L;;;;;N;;;;; 10346;GOTHIC LETTER FAIHU;Lo;0;L;;;;;N;;;;; 10347;GOTHIC LETTER IGGWS;Lo;0;L;;;;;N;;;;; 10348;GOTHIC LETTER HWAIR;Lo;0;L;;;;;N;;;;; 10349;GOTHIC LETTER OTHAL;Lo;0;L;;;;;N;;;;; 1034A;GOTHIC LETTER NINE HUNDRED;Nl;0;L;;;;900;N;;;;; 10350;OLD PERMIC LETTER AN;Lo;0;L;;;;;N;;;;; 10351;OLD PERMIC LETTER BUR;Lo;0;L;;;;;N;;;;; 10352;OLD PERMIC LETTER GAI;Lo;0;L;;;;;N;;;;; 10353;OLD PERMIC LETTER DOI;Lo;0;L;;;;;N;;;;; 10354;OLD PERMIC LETTER E;Lo;0;L;;;;;N;;;;; 10355;OLD PERMIC LETTER ZHOI;Lo;0;L;;;;;N;;;;; 10356;OLD PERMIC LETTER DZHOI;Lo;0;L;;;;;N;;;;; 10357;OLD PERMIC LETTER ZATA;Lo;0;L;;;;;N;;;;; 10358;OLD PERMIC LETTER DZITA;Lo;0;L;;;;;N;;;;; 10359;OLD PERMIC LETTER I;Lo;0;L;;;;;N;;;;; 1035A;OLD PERMIC LETTER KOKE;Lo;0;L;;;;;N;;;;; 1035B;OLD PERMIC LETTER LEI;Lo;0;L;;;;;N;;;;; 1035C;OLD PERMIC LETTER MENOE;Lo;0;L;;;;;N;;;;; 1035D;OLD PERMIC LETTER NENOE;Lo;0;L;;;;;N;;;;; 1035E;OLD PERMIC LETTER VOOI;Lo;0;L;;;;;N;;;;; 1035F;OLD PERMIC LETTER PEEI;Lo;0;L;;;;;N;;;;; 10360;OLD PERMIC LETTER REI;Lo;0;L;;;;;N;;;;; 10361;OLD PERMIC LETTER SII;Lo;0;L;;;;;N;;;;; 10362;OLD PERMIC LETTER TAI;Lo;0;L;;;;;N;;;;; 10363;OLD PERMIC LETTER U;Lo;0;L;;;;;N;;;;; 10364;OLD PERMIC LETTER CHERY;Lo;0;L;;;;;N;;;;; 10365;OLD PERMIC LETTER SHOOI;Lo;0;L;;;;;N;;;;; 10366;OLD PERMIC LETTER SHCHOOI;Lo;0;L;;;;;N;;;;; 10367;OLD PERMIC LETTER YRY;Lo;0;L;;;;;N;;;;; 10368;OLD PERMIC LETTER YERU;Lo;0;L;;;;;N;;;;; 10369;OLD PERMIC LETTER O;Lo;0;L;;;;;N;;;;; 1036A;OLD PERMIC LETTER OO;Lo;0;L;;;;;N;;;;; 1036B;OLD PERMIC LETTER EF;Lo;0;L;;;;;N;;;;; 1036C;OLD PERMIC LETTER HA;Lo;0;L;;;;;N;;;;; 1036D;OLD PERMIC LETTER TSIU;Lo;0;L;;;;;N;;;;; 1036E;OLD PERMIC LETTER VER;Lo;0;L;;;;;N;;;;; 1036F;OLD PERMIC LETTER YER;Lo;0;L;;;;;N;;;;; 10370;OLD PERMIC LETTER YERI;Lo;0;L;;;;;N;;;;; 10371;OLD PERMIC LETTER YAT;Lo;0;L;;;;;N;;;;; 10372;OLD PERMIC LETTER IE;Lo;0;L;;;;;N;;;;; 10373;OLD PERMIC LETTER YU;Lo;0;L;;;;;N;;;;; 10374;OLD PERMIC LETTER YA;Lo;0;L;;;;;N;;;;; 10375;OLD PERMIC LETTER IA;Lo;0;L;;;;;N;;;;; 10376;COMBINING OLD PERMIC LETTER AN;Mn;230;NSM;;;;;N;;;;; 10377;COMBINING OLD PERMIC LETTER DOI;Mn;230;NSM;;;;;N;;;;; 10378;COMBINING OLD PERMIC LETTER ZATA;Mn;230;NSM;;;;;N;;;;; 10379;COMBINING OLD PERMIC LETTER NENOE;Mn;230;NSM;;;;;N;;;;; 1037A;COMBINING OLD PERMIC LETTER SII;Mn;230;NSM;;;;;N;;;;; 10380;UGARITIC LETTER ALPA;Lo;0;L;;;;;N;;;;; 10381;UGARITIC LETTER BETA;Lo;0;L;;;;;N;;;;; 10382;UGARITIC LETTER GAMLA;Lo;0;L;;;;;N;;;;; 10383;UGARITIC LETTER KHA;Lo;0;L;;;;;N;;;;; 10384;UGARITIC LETTER DELTA;Lo;0;L;;;;;N;;;;; 10385;UGARITIC LETTER HO;Lo;0;L;;;;;N;;;;; 10386;UGARITIC LETTER WO;Lo;0;L;;;;;N;;;;; 10387;UGARITIC LETTER ZETA;Lo;0;L;;;;;N;;;;; 10388;UGARITIC LETTER HOTA;Lo;0;L;;;;;N;;;;; 10389;UGARITIC LETTER TET;Lo;0;L;;;;;N;;;;; 1038A;UGARITIC LETTER YOD;Lo;0;L;;;;;N;;;;; 1038B;UGARITIC LETTER KAF;Lo;0;L;;;;;N;;;;; 1038C;UGARITIC LETTER SHIN;Lo;0;L;;;;;N;;;;; 1038D;UGARITIC LETTER LAMDA;Lo;0;L;;;;;N;;;;; 1038E;UGARITIC LETTER MEM;Lo;0;L;;;;;N;;;;; 1038F;UGARITIC LETTER DHAL;Lo;0;L;;;;;N;;;;; 10390;UGARITIC LETTER NUN;Lo;0;L;;;;;N;;;;; 10391;UGARITIC LETTER ZU;Lo;0;L;;;;;N;;;;; 10392;UGARITIC LETTER SAMKA;Lo;0;L;;;;;N;;;;; 10393;UGARITIC LETTER AIN;Lo;0;L;;;;;N;;;;; 10394;UGARITIC LETTER PU;Lo;0;L;;;;;N;;;;; 10395;UGARITIC LETTER SADE;Lo;0;L;;;;;N;;;;; 10396;UGARITIC LETTER QOPA;Lo;0;L;;;;;N;;;;; 10397;UGARITIC LETTER RASHA;Lo;0;L;;;;;N;;;;; 10398;UGARITIC LETTER THANNA;Lo;0;L;;;;;N;;;;; 10399;UGARITIC LETTER GHAIN;Lo;0;L;;;;;N;;;;; 1039A;UGARITIC LETTER TO;Lo;0;L;;;;;N;;;;; 1039B;UGARITIC LETTER I;Lo;0;L;;;;;N;;;;; 1039C;UGARITIC LETTER U;Lo;0;L;;;;;N;;;;; 1039D;UGARITIC LETTER SSU;Lo;0;L;;;;;N;;;;; 1039F;UGARITIC WORD DIVIDER;Po;0;L;;;;;N;;;;; 103A0;OLD PERSIAN SIGN A;Lo;0;L;;;;;N;;;;; 103A1;OLD PERSIAN SIGN I;Lo;0;L;;;;;N;;;;; 103A2;OLD PERSIAN SIGN U;Lo;0;L;;;;;N;;;;; 103A3;OLD PERSIAN SIGN KA;Lo;0;L;;;;;N;;;;; 103A4;OLD PERSIAN SIGN KU;Lo;0;L;;;;;N;;;;; 103A5;OLD PERSIAN SIGN GA;Lo;0;L;;;;;N;;;;; 103A6;OLD PERSIAN SIGN GU;Lo;0;L;;;;;N;;;;; 103A7;OLD PERSIAN SIGN XA;Lo;0;L;;;;;N;;;;; 103A8;OLD PERSIAN SIGN CA;Lo;0;L;;;;;N;;;;; 103A9;OLD PERSIAN SIGN JA;Lo;0;L;;;;;N;;;;; 103AA;OLD PERSIAN SIGN JI;Lo;0;L;;;;;N;;;;; 103AB;OLD PERSIAN SIGN TA;Lo;0;L;;;;;N;;;;; 103AC;OLD PERSIAN SIGN TU;Lo;0;L;;;;;N;;;;; 103AD;OLD PERSIAN SIGN DA;Lo;0;L;;;;;N;;;;; 103AE;OLD PERSIAN SIGN DI;Lo;0;L;;;;;N;;;;; 103AF;OLD PERSIAN SIGN DU;Lo;0;L;;;;;N;;;;; 103B0;OLD PERSIAN SIGN THA;Lo;0;L;;;;;N;;;;; 103B1;OLD PERSIAN SIGN PA;Lo;0;L;;;;;N;;;;; 103B2;OLD PERSIAN SIGN BA;Lo;0;L;;;;;N;;;;; 103B3;OLD PERSIAN SIGN FA;Lo;0;L;;;;;N;;;;; 103B4;OLD PERSIAN SIGN NA;Lo;0;L;;;;;N;;;;; 103B5;OLD PERSIAN SIGN NU;Lo;0;L;;;;;N;;;;; 103B6;OLD PERSIAN SIGN MA;Lo;0;L;;;;;N;;;;; 103B7;OLD PERSIAN SIGN MI;Lo;0;L;;;;;N;;;;; 103B8;OLD PERSIAN SIGN MU;Lo;0;L;;;;;N;;;;; 103B9;OLD PERSIAN SIGN YA;Lo;0;L;;;;;N;;;;; 103BA;OLD PERSIAN SIGN VA;Lo;0;L;;;;;N;;;;; 103BB;OLD PERSIAN SIGN VI;Lo;0;L;;;;;N;;;;; 103BC;OLD PERSIAN SIGN RA;Lo;0;L;;;;;N;;;;; 103BD;OLD PERSIAN SIGN RU;Lo;0;L;;;;;N;;;;; 103BE;OLD PERSIAN SIGN LA;Lo;0;L;;;;;N;;;;; 103BF;OLD PERSIAN SIGN SA;Lo;0;L;;;;;N;;;;; 103C0;OLD PERSIAN SIGN ZA;Lo;0;L;;;;;N;;;;; 103C1;OLD PERSIAN SIGN SHA;Lo;0;L;;;;;N;;;;; 103C2;OLD PERSIAN SIGN SSA;Lo;0;L;;;;;N;;;;; 103C3;OLD PERSIAN SIGN HA;Lo;0;L;;;;;N;;;;; 103C8;OLD PERSIAN SIGN AURAMAZDAA;Lo;0;L;;;;;N;;;;; 103C9;OLD PERSIAN SIGN AURAMAZDAA-2;Lo;0;L;;;;;N;;;;; 103CA;OLD PERSIAN SIGN AURAMAZDAAHA;Lo;0;L;;;;;N;;;;; 103CB;OLD PERSIAN SIGN XSHAAYATHIYA;Lo;0;L;;;;;N;;;;; 103CC;OLD PERSIAN SIGN DAHYAAUSH;Lo;0;L;;;;;N;;;;; 103CD;OLD PERSIAN SIGN DAHYAAUSH-2;Lo;0;L;;;;;N;;;;; 103CE;OLD PERSIAN SIGN BAGA;Lo;0;L;;;;;N;;;;; 103CF;OLD PERSIAN SIGN BUUMISH;Lo;0;L;;;;;N;;;;; 103D0;OLD PERSIAN WORD DIVIDER;Po;0;L;;;;;N;;;;; 103D1;OLD PERSIAN NUMBER ONE;Nl;0;L;;;;1;N;;;;; 103D2;OLD PERSIAN NUMBER TWO;Nl;0;L;;;;2;N;;;;; 103D3;OLD PERSIAN NUMBER TEN;Nl;0;L;;;;10;N;;;;; 103D4;OLD PERSIAN NUMBER TWENTY;Nl;0;L;;;;20;N;;;;; 103D5;OLD PERSIAN NUMBER HUNDRED;Nl;0;L;;;;100;N;;;;; 10400;DESERET CAPITAL LETTER LONG I;Lu;0;L;;;;;N;;;;10428; 10401;DESERET CAPITAL LETTER LONG E;Lu;0;L;;;;;N;;;;10429; 10402;DESERET CAPITAL LETTER LONG A;Lu;0;L;;;;;N;;;;1042A; 10403;DESERET CAPITAL LETTER LONG AH;Lu;0;L;;;;;N;;;;1042B; 10404;DESERET CAPITAL LETTER LONG O;Lu;0;L;;;;;N;;;;1042C; 10405;DESERET CAPITAL LETTER LONG OO;Lu;0;L;;;;;N;;;;1042D; 10406;DESERET CAPITAL LETTER SHORT I;Lu;0;L;;;;;N;;;;1042E; 10407;DESERET CAPITAL LETTER SHORT E;Lu;0;L;;;;;N;;;;1042F; 10408;DESERET CAPITAL LETTER SHORT A;Lu;0;L;;;;;N;;;;10430; 10409;DESERET CAPITAL LETTER SHORT AH;Lu;0;L;;;;;N;;;;10431; 1040A;DESERET CAPITAL LETTER SHORT O;Lu;0;L;;;;;N;;;;10432; 1040B;DESERET CAPITAL LETTER SHORT OO;Lu;0;L;;;;;N;;;;10433; 1040C;DESERET CAPITAL LETTER AY;Lu;0;L;;;;;N;;;;10434; 1040D;DESERET CAPITAL LETTER OW;Lu;0;L;;;;;N;;;;10435; 1040E;DESERET CAPITAL LETTER WU;Lu;0;L;;;;;N;;;;10436; 1040F;DESERET CAPITAL LETTER YEE;Lu;0;L;;;;;N;;;;10437; 10410;DESERET CAPITAL LETTER H;Lu;0;L;;;;;N;;;;10438; 10411;DESERET CAPITAL LETTER PEE;Lu;0;L;;;;;N;;;;10439; 10412;DESERET CAPITAL LETTER BEE;Lu;0;L;;;;;N;;;;1043A; 10413;DESERET CAPITAL LETTER TEE;Lu;0;L;;;;;N;;;;1043B; 10414;DESERET CAPITAL LETTER DEE;Lu;0;L;;;;;N;;;;1043C; 10415;DESERET CAPITAL LETTER CHEE;Lu;0;L;;;;;N;;;;1043D; 10416;DESERET CAPITAL LETTER JEE;Lu;0;L;;;;;N;;;;1043E; 10417;DESERET CAPITAL LETTER KAY;Lu;0;L;;;;;N;;;;1043F; 10418;DESERET CAPITAL LETTER GAY;Lu;0;L;;;;;N;;;;10440; 10419;DESERET CAPITAL LETTER EF;Lu;0;L;;;;;N;;;;10441; 1041A;DESERET CAPITAL LETTER VEE;Lu;0;L;;;;;N;;;;10442; 1041B;DESERET CAPITAL LETTER ETH;Lu;0;L;;;;;N;;;;10443; 1041C;DESERET CAPITAL LETTER THEE;Lu;0;L;;;;;N;;;;10444; 1041D;DESERET CAPITAL LETTER ES;Lu;0;L;;;;;N;;;;10445; 1041E;DESERET CAPITAL LETTER ZEE;Lu;0;L;;;;;N;;;;10446; 1041F;DESERET CAPITAL LETTER ESH;Lu;0;L;;;;;N;;;;10447; 10420;DESERET CAPITAL LETTER ZHEE;Lu;0;L;;;;;N;;;;10448; 10421;DESERET CAPITAL LETTER ER;Lu;0;L;;;;;N;;;;10449; 10422;DESERET CAPITAL LETTER EL;Lu;0;L;;;;;N;;;;1044A; 10423;DESERET CAPITAL LETTER EM;Lu;0;L;;;;;N;;;;1044B; 10424;DESERET CAPITAL LETTER EN;Lu;0;L;;;;;N;;;;1044C; 10425;DESERET CAPITAL LETTER ENG;Lu;0;L;;;;;N;;;;1044D; 10426;DESERET CAPITAL LETTER OI;Lu;0;L;;;;;N;;;;1044E; 10427;DESERET CAPITAL LETTER EW;Lu;0;L;;;;;N;;;;1044F; 10428;DESERET SMALL LETTER LONG I;Ll;0;L;;;;;N;;;10400;;10400 10429;DESERET SMALL LETTER LONG E;Ll;0;L;;;;;N;;;10401;;10401 1042A;DESERET SMALL LETTER LONG A;Ll;0;L;;;;;N;;;10402;;10402 1042B;DESERET SMALL LETTER LONG AH;Ll;0;L;;;;;N;;;10403;;10403 1042C;DESERET SMALL LETTER LONG O;Ll;0;L;;;;;N;;;10404;;10404 1042D;DESERET SMALL LETTER LONG OO;Ll;0;L;;;;;N;;;10405;;10405 1042E;DESERET SMALL LETTER SHORT I;Ll;0;L;;;;;N;;;10406;;10406 1042F;DESERET SMALL LETTER SHORT E;Ll;0;L;;;;;N;;;10407;;10407 10430;DESERET SMALL LETTER SHORT A;Ll;0;L;;;;;N;;;10408;;10408 10431;DESERET SMALL LETTER SHORT AH;Ll;0;L;;;;;N;;;10409;;10409 10432;DESERET SMALL LETTER SHORT O;Ll;0;L;;;;;N;;;1040A;;1040A 10433;DESERET SMALL LETTER SHORT OO;Ll;0;L;;;;;N;;;1040B;;1040B 10434;DESERET SMALL LETTER AY;Ll;0;L;;;;;N;;;1040C;;1040C 10435;DESERET SMALL LETTER OW;Ll;0;L;;;;;N;;;1040D;;1040D 10436;DESERET SMALL LETTER WU;Ll;0;L;;;;;N;;;1040E;;1040E 10437;DESERET SMALL LETTER YEE;Ll;0;L;;;;;N;;;1040F;;1040F 10438;DESERET SMALL LETTER H;Ll;0;L;;;;;N;;;10410;;10410 10439;DESERET SMALL LETTER PEE;Ll;0;L;;;;;N;;;10411;;10411 1043A;DESERET SMALL LETTER BEE;Ll;0;L;;;;;N;;;10412;;10412 1043B;DESERET SMALL LETTER TEE;Ll;0;L;;;;;N;;;10413;;10413 1043C;DESERET SMALL LETTER DEE;Ll;0;L;;;;;N;;;10414;;10414 1043D;DESERET SMALL LETTER CHEE;Ll;0;L;;;;;N;;;10415;;10415 1043E;DESERET SMALL LETTER JEE;Ll;0;L;;;;;N;;;10416;;10416 1043F;DESERET SMALL LETTER KAY;Ll;0;L;;;;;N;;;10417;;10417 10440;DESERET SMALL LETTER GAY;Ll;0;L;;;;;N;;;10418;;10418 10441;DESERET SMALL LETTER EF;Ll;0;L;;;;;N;;;10419;;10419 10442;DESERET SMALL LETTER VEE;Ll;0;L;;;;;N;;;1041A;;1041A 10443;DESERET SMALL LETTER ETH;Ll;0;L;;;;;N;;;1041B;;1041B 10444;DESERET SMALL LETTER THEE;Ll;0;L;;;;;N;;;1041C;;1041C 10445;DESERET SMALL LETTER ES;Ll;0;L;;;;;N;;;1041D;;1041D 10446;DESERET SMALL LETTER ZEE;Ll;0;L;;;;;N;;;1041E;;1041E 10447;DESERET SMALL LETTER ESH;Ll;0;L;;;;;N;;;1041F;;1041F 10448;DESERET SMALL LETTER ZHEE;Ll;0;L;;;;;N;;;10420;;10420 10449;DESERET SMALL LETTER ER;Ll;0;L;;;;;N;;;10421;;10421 1044A;DESERET SMALL LETTER EL;Ll;0;L;;;;;N;;;10422;;10422 1044B;DESERET SMALL LETTER EM;Ll;0;L;;;;;N;;;10423;;10423 1044C;DESERET SMALL LETTER EN;Ll;0;L;;;;;N;;;10424;;10424 1044D;DESERET SMALL LETTER ENG;Ll;0;L;;;;;N;;;10425;;10425 1044E;DESERET SMALL LETTER OI;Ll;0;L;;;;;N;;;10426;;10426 1044F;DESERET SMALL LETTER EW;Ll;0;L;;;;;N;;;10427;;10427 10450;SHAVIAN LETTER PEEP;Lo;0;L;;;;;N;;;;; 10451;SHAVIAN LETTER TOT;Lo;0;L;;;;;N;;;;; 10452;SHAVIAN LETTER KICK;Lo;0;L;;;;;N;;;;; 10453;SHAVIAN LETTER FEE;Lo;0;L;;;;;N;;;;; 10454;SHAVIAN LETTER THIGH;Lo;0;L;;;;;N;;;;; 10455;SHAVIAN LETTER SO;Lo;0;L;;;;;N;;;;; 10456;SHAVIAN LETTER SURE;Lo;0;L;;;;;N;;;;; 10457;SHAVIAN LETTER CHURCH;Lo;0;L;;;;;N;;;;; 10458;SHAVIAN LETTER YEA;Lo;0;L;;;;;N;;;;; 10459;SHAVIAN LETTER HUNG;Lo;0;L;;;;;N;;;;; 1045A;SHAVIAN LETTER BIB;Lo;0;L;;;;;N;;;;; 1045B;SHAVIAN LETTER DEAD;Lo;0;L;;;;;N;;;;; 1045C;SHAVIAN LETTER GAG;Lo;0;L;;;;;N;;;;; 1045D;SHAVIAN LETTER VOW;Lo;0;L;;;;;N;;;;; 1045E;SHAVIAN LETTER THEY;Lo;0;L;;;;;N;;;;; 1045F;SHAVIAN LETTER ZOO;Lo;0;L;;;;;N;;;;; 10460;SHAVIAN LETTER MEASURE;Lo;0;L;;;;;N;;;;; 10461;SHAVIAN LETTER JUDGE;Lo;0;L;;;;;N;;;;; 10462;SHAVIAN LETTER WOE;Lo;0;L;;;;;N;;;;; 10463;SHAVIAN LETTER HA-HA;Lo;0;L;;;;;N;;;;; 10464;SHAVIAN LETTER LOLL;Lo;0;L;;;;;N;;;;; 10465;SHAVIAN LETTER MIME;Lo;0;L;;;;;N;;;;; 10466;SHAVIAN LETTER IF;Lo;0;L;;;;;N;;;;; 10467;SHAVIAN LETTER EGG;Lo;0;L;;;;;N;;;;; 10468;SHAVIAN LETTER ASH;Lo;0;L;;;;;N;;;;; 10469;SHAVIAN LETTER ADO;Lo;0;L;;;;;N;;;;; 1046A;SHAVIAN LETTER ON;Lo;0;L;;;;;N;;;;; 1046B;SHAVIAN LETTER WOOL;Lo;0;L;;;;;N;;;;; 1046C;SHAVIAN LETTER OUT;Lo;0;L;;;;;N;;;;; 1046D;SHAVIAN LETTER AH;Lo;0;L;;;;;N;;;;; 1046E;SHAVIAN LETTER ROAR;Lo;0;L;;;;;N;;;;; 1046F;SHAVIAN LETTER NUN;Lo;0;L;;;;;N;;;;; 10470;SHAVIAN LETTER EAT;Lo;0;L;;;;;N;;;;; 10471;SHAVIAN LETTER AGE;Lo;0;L;;;;;N;;;;; 10472;SHAVIAN LETTER ICE;Lo;0;L;;;;;N;;;;; 10473;SHAVIAN LETTER UP;Lo;0;L;;;;;N;;;;; 10474;SHAVIAN LETTER OAK;Lo;0;L;;;;;N;;;;; 10475;SHAVIAN LETTER OOZE;Lo;0;L;;;;;N;;;;; 10476;SHAVIAN LETTER OIL;Lo;0;L;;;;;N;;;;; 10477;SHAVIAN LETTER AWE;Lo;0;L;;;;;N;;;;; 10478;SHAVIAN LETTER ARE;Lo;0;L;;;;;N;;;;; 10479;SHAVIAN LETTER OR;Lo;0;L;;;;;N;;;;; 1047A;SHAVIAN LETTER AIR;Lo;0;L;;;;;N;;;;; 1047B;SHAVIAN LETTER ERR;Lo;0;L;;;;;N;;;;; 1047C;SHAVIAN LETTER ARRAY;Lo;0;L;;;;;N;;;;; 1047D;SHAVIAN LETTER EAR;Lo;0;L;;;;;N;;;;; 1047E;SHAVIAN LETTER IAN;Lo;0;L;;;;;N;;;;; 1047F;SHAVIAN LETTER YEW;Lo;0;L;;;;;N;;;;; 10480;OSMANYA LETTER ALEF;Lo;0;L;;;;;N;;;;; 10481;OSMANYA LETTER BA;Lo;0;L;;;;;N;;;;; 10482;OSMANYA LETTER TA;Lo;0;L;;;;;N;;;;; 10483;OSMANYA LETTER JA;Lo;0;L;;;;;N;;;;; 10484;OSMANYA LETTER XA;Lo;0;L;;;;;N;;;;; 10485;OSMANYA LETTER KHA;Lo;0;L;;;;;N;;;;; 10486;OSMANYA LETTER DEEL;Lo;0;L;;;;;N;;;;; 10487;OSMANYA LETTER RA;Lo;0;L;;;;;N;;;;; 10488;OSMANYA LETTER SA;Lo;0;L;;;;;N;;;;; 10489;OSMANYA LETTER SHIIN;Lo;0;L;;;;;N;;;;; 1048A;OSMANYA LETTER DHA;Lo;0;L;;;;;N;;;;; 1048B;OSMANYA LETTER CAYN;Lo;0;L;;;;;N;;;;; 1048C;OSMANYA LETTER GA;Lo;0;L;;;;;N;;;;; 1048D;OSMANYA LETTER FA;Lo;0;L;;;;;N;;;;; 1048E;OSMANYA LETTER QAAF;Lo;0;L;;;;;N;;;;; 1048F;OSMANYA LETTER KAAF;Lo;0;L;;;;;N;;;;; 10490;OSMANYA LETTER LAAN;Lo;0;L;;;;;N;;;;; 10491;OSMANYA LETTER MIIN;Lo;0;L;;;;;N;;;;; 10492;OSMANYA LETTER NUUN;Lo;0;L;;;;;N;;;;; 10493;OSMANYA LETTER WAW;Lo;0;L;;;;;N;;;;; 10494;OSMANYA LETTER HA;Lo;0;L;;;;;N;;;;; 10495;OSMANYA LETTER YA;Lo;0;L;;;;;N;;;;; 10496;OSMANYA LETTER A;Lo;0;L;;;;;N;;;;; 10497;OSMANYA LETTER E;Lo;0;L;;;;;N;;;;; 10498;OSMANYA LETTER I;Lo;0;L;;;;;N;;;;; 10499;OSMANYA LETTER O;Lo;0;L;;;;;N;;;;; 1049A;OSMANYA LETTER U;Lo;0;L;;;;;N;;;;; 1049B;OSMANYA LETTER AA;Lo;0;L;;;;;N;;;;; 1049C;OSMANYA LETTER EE;Lo;0;L;;;;;N;;;;; 1049D;OSMANYA LETTER OO;Lo;0;L;;;;;N;;;;; 104A0;OSMANYA DIGIT ZERO;Nd;0;L;;0;0;0;N;;;;; 104A1;OSMANYA DIGIT ONE;Nd;0;L;;1;1;1;N;;;;; 104A2;OSMANYA DIGIT TWO;Nd;0;L;;2;2;2;N;;;;; 104A3;OSMANYA DIGIT THREE;Nd;0;L;;3;3;3;N;;;;; 104A4;OSMANYA DIGIT FOUR;Nd;0;L;;4;4;4;N;;;;; 104A5;OSMANYA DIGIT FIVE;Nd;0;L;;5;5;5;N;;;;; 104A6;OSMANYA DIGIT SIX;Nd;0;L;;6;6;6;N;;;;; 104A7;OSMANYA DIGIT SEVEN;Nd;0;L;;7;7;7;N;;;;; 104A8;OSMANYA DIGIT EIGHT;Nd;0;L;;8;8;8;N;;;;; 104A9;OSMANYA DIGIT NINE;Nd;0;L;;9;9;9;N;;;;; 10500;ELBASAN LETTER A;Lo;0;L;;;;;N;;;;; 10501;ELBASAN LETTER BE;Lo;0;L;;;;;N;;;;; 10502;ELBASAN LETTER CE;Lo;0;L;;;;;N;;;;; 10503;ELBASAN LETTER CHE;Lo;0;L;;;;;N;;;;; 10504;ELBASAN LETTER DE;Lo;0;L;;;;;N;;;;; 10505;ELBASAN LETTER NDE;Lo;0;L;;;;;N;;;;; 10506;ELBASAN LETTER DHE;Lo;0;L;;;;;N;;;;; 10507;ELBASAN LETTER EI;Lo;0;L;;;;;N;;;;; 10508;ELBASAN LETTER E;Lo;0;L;;;;;N;;;;; 10509;ELBASAN LETTER FE;Lo;0;L;;;;;N;;;;; 1050A;ELBASAN LETTER GE;Lo;0;L;;;;;N;;;;; 1050B;ELBASAN LETTER GJE;Lo;0;L;;;;;N;;;;; 1050C;ELBASAN LETTER HE;Lo;0;L;;;;;N;;;;; 1050D;ELBASAN LETTER I;Lo;0;L;;;;;N;;;;; 1050E;ELBASAN LETTER JE;Lo;0;L;;;;;N;;;;; 1050F;ELBASAN LETTER KE;Lo;0;L;;;;;N;;;;; 10510;ELBASAN LETTER LE;Lo;0;L;;;;;N;;;;; 10511;ELBASAN LETTER LLE;Lo;0;L;;;;;N;;;;; 10512;ELBASAN LETTER ME;Lo;0;L;;;;;N;;;;; 10513;ELBASAN LETTER NE;Lo;0;L;;;;;N;;;;; 10514;ELBASAN LETTER NA;Lo;0;L;;;;;N;;;;; 10515;ELBASAN LETTER NJE;Lo;0;L;;;;;N;;;;; 10516;ELBASAN LETTER O;Lo;0;L;;;;;N;;;;; 10517;ELBASAN LETTER PE;Lo;0;L;;;;;N;;;;; 10518;ELBASAN LETTER QE;Lo;0;L;;;;;N;;;;; 10519;ELBASAN LETTER RE;Lo;0;L;;;;;N;;;;; 1051A;ELBASAN LETTER RRE;Lo;0;L;;;;;N;;;;; 1051B;ELBASAN LETTER SE;Lo;0;L;;;;;N;;;;; 1051C;ELBASAN LETTER SHE;Lo;0;L;;;;;N;;;;; 1051D;ELBASAN LETTER TE;Lo;0;L;;;;;N;;;;; 1051E;ELBASAN LETTER THE;Lo;0;L;;;;;N;;;;; 1051F;ELBASAN LETTER U;Lo;0;L;;;;;N;;;;; 10520;ELBASAN LETTER VE;Lo;0;L;;;;;N;;;;; 10521;ELBASAN LETTER XE;Lo;0;L;;;;;N;;;;; 10522;ELBASAN LETTER Y;Lo;0;L;;;;;N;;;;; 10523;ELBASAN LETTER ZE;Lo;0;L;;;;;N;;;;; 10524;ELBASAN LETTER ZHE;Lo;0;L;;;;;N;;;;; 10525;ELBASAN LETTER GHE;Lo;0;L;;;;;N;;;;; 10526;ELBASAN LETTER GHAMMA;Lo;0;L;;;;;N;;;;; 10527;ELBASAN LETTER KHE;Lo;0;L;;;;;N;;;;; 10530;CAUCASIAN ALBANIAN LETTER ALT;Lo;0;L;;;;;N;;;;; 10531;CAUCASIAN ALBANIAN LETTER BET;Lo;0;L;;;;;N;;;;; 10532;CAUCASIAN ALBANIAN LETTER GIM;Lo;0;L;;;;;N;;;;; 10533;CAUCASIAN ALBANIAN LETTER DAT;Lo;0;L;;;;;N;;;;; 10534;CAUCASIAN ALBANIAN LETTER EB;Lo;0;L;;;;;N;;;;; 10535;CAUCASIAN ALBANIAN LETTER ZARL;Lo;0;L;;;;;N;;;;; 10536;CAUCASIAN ALBANIAN LETTER EYN;Lo;0;L;;;;;N;;;;; 10537;CAUCASIAN ALBANIAN LETTER ZHIL;Lo;0;L;;;;;N;;;;; 10538;CAUCASIAN ALBANIAN LETTER TAS;Lo;0;L;;;;;N;;;;; 10539;CAUCASIAN ALBANIAN LETTER CHA;Lo;0;L;;;;;N;;;;; 1053A;CAUCASIAN ALBANIAN LETTER YOWD;Lo;0;L;;;;;N;;;;; 1053B;CAUCASIAN ALBANIAN LETTER ZHA;Lo;0;L;;;;;N;;;;; 1053C;CAUCASIAN ALBANIAN LETTER IRB;Lo;0;L;;;;;N;;;;; 1053D;CAUCASIAN ALBANIAN LETTER SHA;Lo;0;L;;;;;N;;;;; 1053E;CAUCASIAN ALBANIAN LETTER LAN;Lo;0;L;;;;;N;;;;; 1053F;CAUCASIAN ALBANIAN LETTER INYA;Lo;0;L;;;;;N;;;;; 10540;CAUCASIAN ALBANIAN LETTER XEYN;Lo;0;L;;;;;N;;;;; 10541;CAUCASIAN ALBANIAN LETTER DYAN;Lo;0;L;;;;;N;;;;; 10542;CAUCASIAN ALBANIAN LETTER CAR;Lo;0;L;;;;;N;;;;; 10543;CAUCASIAN ALBANIAN LETTER JHOX;Lo;0;L;;;;;N;;;;; 10544;CAUCASIAN ALBANIAN LETTER KAR;Lo;0;L;;;;;N;;;;; 10545;CAUCASIAN ALBANIAN LETTER LYIT;Lo;0;L;;;;;N;;;;; 10546;CAUCASIAN ALBANIAN LETTER HEYT;Lo;0;L;;;;;N;;;;; 10547;CAUCASIAN ALBANIAN LETTER QAY;Lo;0;L;;;;;N;;;;; 10548;CAUCASIAN ALBANIAN LETTER AOR;Lo;0;L;;;;;N;;;;; 10549;CAUCASIAN ALBANIAN LETTER CHOY;Lo;0;L;;;;;N;;;;; 1054A;CAUCASIAN ALBANIAN LETTER CHI;Lo;0;L;;;;;N;;;;; 1054B;CAUCASIAN ALBANIAN LETTER CYAY;Lo;0;L;;;;;N;;;;; 1054C;CAUCASIAN ALBANIAN LETTER MAQ;Lo;0;L;;;;;N;;;;; 1054D;CAUCASIAN ALBANIAN LETTER QAR;Lo;0;L;;;;;N;;;;; 1054E;CAUCASIAN ALBANIAN LETTER NOWC;Lo;0;L;;;;;N;;;;; 1054F;CAUCASIAN ALBANIAN LETTER DZYAY;Lo;0;L;;;;;N;;;;; 10550;CAUCASIAN ALBANIAN LETTER SHAK;Lo;0;L;;;;;N;;;;; 10551;CAUCASIAN ALBANIAN LETTER JAYN;Lo;0;L;;;;;N;;;;; 10552;CAUCASIAN ALBANIAN LETTER ON;Lo;0;L;;;;;N;;;;; 10553;CAUCASIAN ALBANIAN LETTER TYAY;Lo;0;L;;;;;N;;;;; 10554;CAUCASIAN ALBANIAN LETTER FAM;Lo;0;L;;;;;N;;;;; 10555;CAUCASIAN ALBANIAN LETTER DZAY;Lo;0;L;;;;;N;;;;; 10556;CAUCASIAN ALBANIAN LETTER CHAT;Lo;0;L;;;;;N;;;;; 10557;CAUCASIAN ALBANIAN LETTER PEN;Lo;0;L;;;;;N;;;;; 10558;CAUCASIAN ALBANIAN LETTER GHEYS;Lo;0;L;;;;;N;;;;; 10559;CAUCASIAN ALBANIAN LETTER RAT;Lo;0;L;;;;;N;;;;; 1055A;CAUCASIAN ALBANIAN LETTER SEYK;Lo;0;L;;;;;N;;;;; 1055B;CAUCASIAN ALBANIAN LETTER VEYZ;Lo;0;L;;;;;N;;;;; 1055C;CAUCASIAN ALBANIAN LETTER TIWR;Lo;0;L;;;;;N;;;;; 1055D;CAUCASIAN ALBANIAN LETTER SHOY;Lo;0;L;;;;;N;;;;; 1055E;CAUCASIAN ALBANIAN LETTER IWN;Lo;0;L;;;;;N;;;;; 1055F;CAUCASIAN ALBANIAN LETTER CYAW;Lo;0;L;;;;;N;;;;; 10560;CAUCASIAN ALBANIAN LETTER CAYN;Lo;0;L;;;;;N;;;;; 10561;CAUCASIAN ALBANIAN LETTER YAYD;Lo;0;L;;;;;N;;;;; 10562;CAUCASIAN ALBANIAN LETTER PIWR;Lo;0;L;;;;;N;;;;; 10563;CAUCASIAN ALBANIAN LETTER KIW;Lo;0;L;;;;;N;;;;; 1056F;CAUCASIAN ALBANIAN CITATION MARK;Po;0;L;;;;;N;;;;; 10600;LINEAR A SIGN AB001;Lo;0;L;;;;;N;;;;; 10601;LINEAR A SIGN AB002;Lo;0;L;;;;;N;;;;; 10602;LINEAR A SIGN AB003;Lo;0;L;;;;;N;;;;; 10603;LINEAR A SIGN AB004;Lo;0;L;;;;;N;;;;; 10604;LINEAR A SIGN AB005;Lo;0;L;;;;;N;;;;; 10605;LINEAR A SIGN AB006;Lo;0;L;;;;;N;;;;; 10606;LINEAR A SIGN AB007;Lo;0;L;;;;;N;;;;; 10607;LINEAR A SIGN AB008;Lo;0;L;;;;;N;;;;; 10608;LINEAR A SIGN AB009;Lo;0;L;;;;;N;;;;; 10609;LINEAR A SIGN AB010;Lo;0;L;;;;;N;;;;; 1060A;LINEAR A SIGN AB011;Lo;0;L;;;;;N;;;;; 1060B;LINEAR A SIGN AB013;Lo;0;L;;;;;N;;;;; 1060C;LINEAR A SIGN AB016;Lo;0;L;;;;;N;;;;; 1060D;LINEAR A SIGN AB017;Lo;0;L;;;;;N;;;;; 1060E;LINEAR A SIGN AB020;Lo;0;L;;;;;N;;;;; 1060F;LINEAR A SIGN AB021;Lo;0;L;;;;;N;;;;; 10610;LINEAR A SIGN AB021F;Lo;0;L;;;;;N;;;;; 10611;LINEAR A SIGN AB021M;Lo;0;L;;;;;N;;;;; 10612;LINEAR A SIGN AB022;Lo;0;L;;;;;N;;;;; 10613;LINEAR A SIGN AB022F;Lo;0;L;;;;;N;;;;; 10614;LINEAR A SIGN AB022M;Lo;0;L;;;;;N;;;;; 10615;LINEAR A SIGN AB023;Lo;0;L;;;;;N;;;;; 10616;LINEAR A SIGN AB023M;Lo;0;L;;;;;N;;;;; 10617;LINEAR A SIGN AB024;Lo;0;L;;;;;N;;;;; 10618;LINEAR A SIGN AB026;Lo;0;L;;;;;N;;;;; 10619;LINEAR A SIGN AB027;Lo;0;L;;;;;N;;;;; 1061A;LINEAR A SIGN AB028;Lo;0;L;;;;;N;;;;; 1061B;LINEAR A SIGN A028B;Lo;0;L;;;;;N;;;;; 1061C;LINEAR A SIGN AB029;Lo;0;L;;;;;N;;;;; 1061D;LINEAR A SIGN AB030;Lo;0;L;;;;;N;;;;; 1061E;LINEAR A SIGN AB031;Lo;0;L;;;;;N;;;;; 1061F;LINEAR A SIGN AB034;Lo;0;L;;;;;N;;;;; 10620;LINEAR A SIGN AB037;Lo;0;L;;;;;N;;;;; 10621;LINEAR A SIGN AB038;Lo;0;L;;;;;N;;;;; 10622;LINEAR A SIGN AB039;Lo;0;L;;;;;N;;;;; 10623;LINEAR A SIGN AB040;Lo;0;L;;;;;N;;;;; 10624;LINEAR A SIGN AB041;Lo;0;L;;;;;N;;;;; 10625;LINEAR A SIGN AB044;Lo;0;L;;;;;N;;;;; 10626;LINEAR A SIGN AB045;Lo;0;L;;;;;N;;;;; 10627;LINEAR A SIGN AB046;Lo;0;L;;;;;N;;;;; 10628;LINEAR A SIGN AB047;Lo;0;L;;;;;N;;;;; 10629;LINEAR A SIGN AB048;Lo;0;L;;;;;N;;;;; 1062A;LINEAR A SIGN AB049;Lo;0;L;;;;;N;;;;; 1062B;LINEAR A SIGN AB050;Lo;0;L;;;;;N;;;;; 1062C;LINEAR A SIGN AB051;Lo;0;L;;;;;N;;;;; 1062D;LINEAR A SIGN AB053;Lo;0;L;;;;;N;;;;; 1062E;LINEAR A SIGN AB054;Lo;0;L;;;;;N;;;;; 1062F;LINEAR A SIGN AB055;Lo;0;L;;;;;N;;;;; 10630;LINEAR A SIGN AB056;Lo;0;L;;;;;N;;;;; 10631;LINEAR A SIGN AB057;Lo;0;L;;;;;N;;;;; 10632;LINEAR A SIGN AB058;Lo;0;L;;;;;N;;;;; 10633;LINEAR A SIGN AB059;Lo;0;L;;;;;N;;;;; 10634;LINEAR A SIGN AB060;Lo;0;L;;;;;N;;;;; 10635;LINEAR A SIGN AB061;Lo;0;L;;;;;N;;;;; 10636;LINEAR A SIGN AB065;Lo;0;L;;;;;N;;;;; 10637;LINEAR A SIGN AB066;Lo;0;L;;;;;N;;;;; 10638;LINEAR A SIGN AB067;Lo;0;L;;;;;N;;;;; 10639;LINEAR A SIGN AB069;Lo;0;L;;;;;N;;;;; 1063A;LINEAR A SIGN AB070;Lo;0;L;;;;;N;;;;; 1063B;LINEAR A SIGN AB073;Lo;0;L;;;;;N;;;;; 1063C;LINEAR A SIGN AB074;Lo;0;L;;;;;N;;;;; 1063D;LINEAR A SIGN AB076;Lo;0;L;;;;;N;;;;; 1063E;LINEAR A SIGN AB077;Lo;0;L;;;;;N;;;;; 1063F;LINEAR A SIGN AB078;Lo;0;L;;;;;N;;;;; 10640;LINEAR A SIGN AB079;Lo;0;L;;;;;N;;;;; 10641;LINEAR A SIGN AB080;Lo;0;L;;;;;N;;;;; 10642;LINEAR A SIGN AB081;Lo;0;L;;;;;N;;;;; 10643;LINEAR A SIGN AB082;Lo;0;L;;;;;N;;;;; 10644;LINEAR A SIGN AB085;Lo;0;L;;;;;N;;;;; 10645;LINEAR A SIGN AB086;Lo;0;L;;;;;N;;;;; 10646;LINEAR A SIGN AB087;Lo;0;L;;;;;N;;;;; 10647;LINEAR A SIGN A100-102;Lo;0;L;;;;;N;;;;; 10648;LINEAR A SIGN AB118;Lo;0;L;;;;;N;;;;; 10649;LINEAR A SIGN AB120;Lo;0;L;;;;;N;;;;; 1064A;LINEAR A SIGN A120B;Lo;0;L;;;;;N;;;;; 1064B;LINEAR A SIGN AB122;Lo;0;L;;;;;N;;;;; 1064C;LINEAR A SIGN AB123;Lo;0;L;;;;;N;;;;; 1064D;LINEAR A SIGN AB131A;Lo;0;L;;;;;N;;;;; 1064E;LINEAR A SIGN AB131B;Lo;0;L;;;;;N;;;;; 1064F;LINEAR A SIGN A131C;Lo;0;L;;;;;N;;;;; 10650;LINEAR A SIGN AB164;Lo;0;L;;;;;N;;;;; 10651;LINEAR A SIGN AB171;Lo;0;L;;;;;N;;;;; 10652;LINEAR A SIGN AB180;Lo;0;L;;;;;N;;;;; 10653;LINEAR A SIGN AB188;Lo;0;L;;;;;N;;;;; 10654;LINEAR A SIGN AB191;Lo;0;L;;;;;N;;;;; 10655;LINEAR A SIGN A301;Lo;0;L;;;;;N;;;;; 10656;LINEAR A SIGN A302;Lo;0;L;;;;;N;;;;; 10657;LINEAR A SIGN A303;Lo;0;L;;;;;N;;;;; 10658;LINEAR A SIGN A304;Lo;0;L;;;;;N;;;;; 10659;LINEAR A SIGN A305;Lo;0;L;;;;;N;;;;; 1065A;LINEAR A SIGN A306;Lo;0;L;;;;;N;;;;; 1065B;LINEAR A SIGN A307;Lo;0;L;;;;;N;;;;; 1065C;LINEAR A SIGN A308;Lo;0;L;;;;;N;;;;; 1065D;LINEAR A SIGN A309A;Lo;0;L;;;;;N;;;;; 1065E;LINEAR A SIGN A309B;Lo;0;L;;;;;N;;;;; 1065F;LINEAR A SIGN A309C;Lo;0;L;;;;;N;;;;; 10660;LINEAR A SIGN A310;Lo;0;L;;;;;N;;;;; 10661;LINEAR A SIGN A311;Lo;0;L;;;;;N;;;;; 10662;LINEAR A SIGN A312;Lo;0;L;;;;;N;;;;; 10663;LINEAR A SIGN A313A;Lo;0;L;;;;;N;;;;; 10664;LINEAR A SIGN A313B;Lo;0;L;;;;;N;;;;; 10665;LINEAR A SIGN A313C;Lo;0;L;;;;;N;;;;; 10666;LINEAR A SIGN A314;Lo;0;L;;;;;N;;;;; 10667;LINEAR A SIGN A315;Lo;0;L;;;;;N;;;;; 10668;LINEAR A SIGN A316;Lo;0;L;;;;;N;;;;; 10669;LINEAR A SIGN A317;Lo;0;L;;;;;N;;;;; 1066A;LINEAR A SIGN A318;Lo;0;L;;;;;N;;;;; 1066B;LINEAR A SIGN A319;Lo;0;L;;;;;N;;;;; 1066C;LINEAR A SIGN A320;Lo;0;L;;;;;N;;;;; 1066D;LINEAR A SIGN A321;Lo;0;L;;;;;N;;;;; 1066E;LINEAR A SIGN A322;Lo;0;L;;;;;N;;;;; 1066F;LINEAR A SIGN A323;Lo;0;L;;;;;N;;;;; 10670;LINEAR A SIGN A324;Lo;0;L;;;;;N;;;;; 10671;LINEAR A SIGN A325;Lo;0;L;;;;;N;;;;; 10672;LINEAR A SIGN A326;Lo;0;L;;;;;N;;;;; 10673;LINEAR A SIGN A327;Lo;0;L;;;;;N;;;;; 10674;LINEAR A SIGN A328;Lo;0;L;;;;;N;;;;; 10675;LINEAR A SIGN A329;Lo;0;L;;;;;N;;;;; 10676;LINEAR A SIGN A330;Lo;0;L;;;;;N;;;;; 10677;LINEAR A SIGN A331;Lo;0;L;;;;;N;;;;; 10678;LINEAR A SIGN A332;Lo;0;L;;;;;N;;;;; 10679;LINEAR A SIGN A333;Lo;0;L;;;;;N;;;;; 1067A;LINEAR A SIGN A334;Lo;0;L;;;;;N;;;;; 1067B;LINEAR A SIGN A335;Lo;0;L;;;;;N;;;;; 1067C;LINEAR A SIGN A336;Lo;0;L;;;;;N;;;;; 1067D;LINEAR A SIGN A337;Lo;0;L;;;;;N;;;;; 1067E;LINEAR A SIGN A338;Lo;0;L;;;;;N;;;;; 1067F;LINEAR A SIGN A339;Lo;0;L;;;;;N;;;;; 10680;LINEAR A SIGN A340;Lo;0;L;;;;;N;;;;; 10681;LINEAR A SIGN A341;Lo;0;L;;;;;N;;;;; 10682;LINEAR A SIGN A342;Lo;0;L;;;;;N;;;;; 10683;LINEAR A SIGN A343;Lo;0;L;;;;;N;;;;; 10684;LINEAR A SIGN A344;Lo;0;L;;;;;N;;;;; 10685;LINEAR A SIGN A345;Lo;0;L;;;;;N;;;;; 10686;LINEAR A SIGN A346;Lo;0;L;;;;;N;;;;; 10687;LINEAR A SIGN A347;Lo;0;L;;;;;N;;;;; 10688;LINEAR A SIGN A348;Lo;0;L;;;;;N;;;;; 10689;LINEAR A SIGN A349;Lo;0;L;;;;;N;;;;; 1068A;LINEAR A SIGN A350;Lo;0;L;;;;;N;;;;; 1068B;LINEAR A SIGN A351;Lo;0;L;;;;;N;;;;; 1068C;LINEAR A SIGN A352;Lo;0;L;;;;;N;;;;; 1068D;LINEAR A SIGN A353;Lo;0;L;;;;;N;;;;; 1068E;LINEAR A SIGN A354;Lo;0;L;;;;;N;;;;; 1068F;LINEAR A SIGN A355;Lo;0;L;;;;;N;;;;; 10690;LINEAR A SIGN A356;Lo;0;L;;;;;N;;;;; 10691;LINEAR A SIGN A357;Lo;0;L;;;;;N;;;;; 10692;LINEAR A SIGN A358;Lo;0;L;;;;;N;;;;; 10693;LINEAR A SIGN A359;Lo;0;L;;;;;N;;;;; 10694;LINEAR A SIGN A360;Lo;0;L;;;;;N;;;;; 10695;LINEAR A SIGN A361;Lo;0;L;;;;;N;;;;; 10696;LINEAR A SIGN A362;Lo;0;L;;;;;N;;;;; 10697;LINEAR A SIGN A363;Lo;0;L;;;;;N;;;;; 10698;LINEAR A SIGN A364;Lo;0;L;;;;;N;;;;; 10699;LINEAR A SIGN A365;Lo;0;L;;;;;N;;;;; 1069A;LINEAR A SIGN A366;Lo;0;L;;;;;N;;;;; 1069B;LINEAR A SIGN A367;Lo;0;L;;;;;N;;;;; 1069C;LINEAR A SIGN A368;Lo;0;L;;;;;N;;;;; 1069D;LINEAR A SIGN A369;Lo;0;L;;;;;N;;;;; 1069E;LINEAR A SIGN A370;Lo;0;L;;;;;N;;;;; 1069F;LINEAR A SIGN A371;Lo;0;L;;;;;N;;;;; 106A0;LINEAR A SIGN A400-VAS;Lo;0;L;;;;;N;;;;; 106A1;LINEAR A SIGN A401-VAS;Lo;0;L;;;;;N;;;;; 106A2;LINEAR A SIGN A402-VAS;Lo;0;L;;;;;N;;;;; 106A3;LINEAR A SIGN A403-VAS;Lo;0;L;;;;;N;;;;; 106A4;LINEAR A SIGN A404-VAS;Lo;0;L;;;;;N;;;;; 106A5;LINEAR A SIGN A405-VAS;Lo;0;L;;;;;N;;;;; 106A6;LINEAR A SIGN A406-VAS;Lo;0;L;;;;;N;;;;; 106A7;LINEAR A SIGN A407-VAS;Lo;0;L;;;;;N;;;;; 106A8;LINEAR A SIGN A408-VAS;Lo;0;L;;;;;N;;;;; 106A9;LINEAR A SIGN A409-VAS;Lo;0;L;;;;;N;;;;; 106AA;LINEAR A SIGN A410-VAS;Lo;0;L;;;;;N;;;;; 106AB;LINEAR A SIGN A411-VAS;Lo;0;L;;;;;N;;;;; 106AC;LINEAR A SIGN A412-VAS;Lo;0;L;;;;;N;;;;; 106AD;LINEAR A SIGN A413-VAS;Lo;0;L;;;;;N;;;;; 106AE;LINEAR A SIGN A414-VAS;Lo;0;L;;;;;N;;;;; 106AF;LINEAR A SIGN A415-VAS;Lo;0;L;;;;;N;;;;; 106B0;LINEAR A SIGN A416-VAS;Lo;0;L;;;;;N;;;;; 106B1;LINEAR A SIGN A417-VAS;Lo;0;L;;;;;N;;;;; 106B2;LINEAR A SIGN A418-VAS;Lo;0;L;;;;;N;;;;; 106B3;LINEAR A SIGN A501;Lo;0;L;;;;;N;;;;; 106B4;LINEAR A SIGN A502;Lo;0;L;;;;;N;;;;; 106B5;LINEAR A SIGN A503;Lo;0;L;;;;;N;;;;; 106B6;LINEAR A SIGN A504;Lo;0;L;;;;;N;;;;; 106B7;LINEAR A SIGN A505;Lo;0;L;;;;;N;;;;; 106B8;LINEAR A SIGN A506;Lo;0;L;;;;;N;;;;; 106B9;LINEAR A SIGN A508;Lo;0;L;;;;;N;;;;; 106BA;LINEAR A SIGN A509;Lo;0;L;;;;;N;;;;; 106BB;LINEAR A SIGN A510;Lo;0;L;;;;;N;;;;; 106BC;LINEAR A SIGN A511;Lo;0;L;;;;;N;;;;; 106BD;LINEAR A SIGN A512;Lo;0;L;;;;;N;;;;; 106BE;LINEAR A SIGN A513;Lo;0;L;;;;;N;;;;; 106BF;LINEAR A SIGN A515;Lo;0;L;;;;;N;;;;; 106C0;LINEAR A SIGN A516;Lo;0;L;;;;;N;;;;; 106C1;LINEAR A SIGN A520;Lo;0;L;;;;;N;;;;; 106C2;LINEAR A SIGN A521;Lo;0;L;;;;;N;;;;; 106C3;LINEAR A SIGN A523;Lo;0;L;;;;;N;;;;; 106C4;LINEAR A SIGN A524;Lo;0;L;;;;;N;;;;; 106C5;LINEAR A SIGN A525;Lo;0;L;;;;;N;;;;; 106C6;LINEAR A SIGN A526;Lo;0;L;;;;;N;;;;; 106C7;LINEAR A SIGN A527;Lo;0;L;;;;;N;;;;; 106C8;LINEAR A SIGN A528;Lo;0;L;;;;;N;;;;; 106C9;LINEAR A SIGN A529;Lo;0;L;;;;;N;;;;; 106CA;LINEAR A SIGN A530;Lo;0;L;;;;;N;;;;; 106CB;LINEAR A SIGN A531;Lo;0;L;;;;;N;;;;; 106CC;LINEAR A SIGN A532;Lo;0;L;;;;;N;;;;; 106CD;LINEAR A SIGN A534;Lo;0;L;;;;;N;;;;; 106CE;LINEAR A SIGN A535;Lo;0;L;;;;;N;;;;; 106CF;LINEAR A SIGN A536;Lo;0;L;;;;;N;;;;; 106D0;LINEAR A SIGN A537;Lo;0;L;;;;;N;;;;; 106D1;LINEAR A SIGN A538;Lo;0;L;;;;;N;;;;; 106D2;LINEAR A SIGN A539;Lo;0;L;;;;;N;;;;; 106D3;LINEAR A SIGN A540;Lo;0;L;;;;;N;;;;; 106D4;LINEAR A SIGN A541;Lo;0;L;;;;;N;;;;; 106D5;LINEAR A SIGN A542;Lo;0;L;;;;;N;;;;; 106D6;LINEAR A SIGN A545;Lo;0;L;;;;;N;;;;; 106D7;LINEAR A SIGN A547;Lo;0;L;;;;;N;;;;; 106D8;LINEAR A SIGN A548;Lo;0;L;;;;;N;;;;; 106D9;LINEAR A SIGN A549;Lo;0;L;;;;;N;;;;; 106DA;LINEAR A SIGN A550;Lo;0;L;;;;;N;;;;; 106DB;LINEAR A SIGN A551;Lo;0;L;;;;;N;;;;; 106DC;LINEAR A SIGN A552;Lo;0;L;;;;;N;;;;; 106DD;LINEAR A SIGN A553;Lo;0;L;;;;;N;;;;; 106DE;LINEAR A SIGN A554;Lo;0;L;;;;;N;;;;; 106DF;LINEAR A SIGN A555;Lo;0;L;;;;;N;;;;; 106E0;LINEAR A SIGN A556;Lo;0;L;;;;;N;;;;; 106E1;LINEAR A SIGN A557;Lo;0;L;;;;;N;;;;; 106E2;LINEAR A SIGN A559;Lo;0;L;;;;;N;;;;; 106E3;LINEAR A SIGN A563;Lo;0;L;;;;;N;;;;; 106E4;LINEAR A SIGN A564;Lo;0;L;;;;;N;;;;; 106E5;LINEAR A SIGN A565;Lo;0;L;;;;;N;;;;; 106E6;LINEAR A SIGN A566;Lo;0;L;;;;;N;;;;; 106E7;LINEAR A SIGN A568;Lo;0;L;;;;;N;;;;; 106E8;LINEAR A SIGN A569;Lo;0;L;;;;;N;;;;; 106E9;LINEAR A SIGN A570;Lo;0;L;;;;;N;;;;; 106EA;LINEAR A SIGN A571;Lo;0;L;;;;;N;;;;; 106EB;LINEAR A SIGN A572;Lo;0;L;;;;;N;;;;; 106EC;LINEAR A SIGN A573;Lo;0;L;;;;;N;;;;; 106ED;LINEAR A SIGN A574;Lo;0;L;;;;;N;;;;; 106EE;LINEAR A SIGN A575;Lo;0;L;;;;;N;;;;; 106EF;LINEAR A SIGN A576;Lo;0;L;;;;;N;;;;; 106F0;LINEAR A SIGN A577;Lo;0;L;;;;;N;;;;; 106F1;LINEAR A SIGN A578;Lo;0;L;;;;;N;;;;; 106F2;LINEAR A SIGN A579;Lo;0;L;;;;;N;;;;; 106F3;LINEAR A SIGN A580;Lo;0;L;;;;;N;;;;; 106F4;LINEAR A SIGN A581;Lo;0;L;;;;;N;;;;; 106F5;LINEAR A SIGN A582;Lo;0;L;;;;;N;;;;; 106F6;LINEAR A SIGN A583;Lo;0;L;;;;;N;;;;; 106F7;LINEAR A SIGN A584;Lo;0;L;;;;;N;;;;; 106F8;LINEAR A SIGN A585;Lo;0;L;;;;;N;;;;; 106F9;LINEAR A SIGN A586;Lo;0;L;;;;;N;;;;; 106FA;LINEAR A SIGN A587;Lo;0;L;;;;;N;;;;; 106FB;LINEAR A SIGN A588;Lo;0;L;;;;;N;;;;; 106FC;LINEAR A SIGN A589;Lo;0;L;;;;;N;;;;; 106FD;LINEAR A SIGN A591;Lo;0;L;;;;;N;;;;; 106FE;LINEAR A SIGN A592;Lo;0;L;;;;;N;;;;; 106FF;LINEAR A SIGN A594;Lo;0;L;;;;;N;;;;; 10700;LINEAR A SIGN A595;Lo;0;L;;;;;N;;;;; 10701;LINEAR A SIGN A596;Lo;0;L;;;;;N;;;;; 10702;LINEAR A SIGN A598;Lo;0;L;;;;;N;;;;; 10703;LINEAR A SIGN A600;Lo;0;L;;;;;N;;;;; 10704;LINEAR A SIGN A601;Lo;0;L;;;;;N;;;;; 10705;LINEAR A SIGN A602;Lo;0;L;;;;;N;;;;; 10706;LINEAR A SIGN A603;Lo;0;L;;;;;N;;;;; 10707;LINEAR A SIGN A604;Lo;0;L;;;;;N;;;;; 10708;LINEAR A SIGN A606;Lo;0;L;;;;;N;;;;; 10709;LINEAR A SIGN A608;Lo;0;L;;;;;N;;;;; 1070A;LINEAR A SIGN A609;Lo;0;L;;;;;N;;;;; 1070B;LINEAR A SIGN A610;Lo;0;L;;;;;N;;;;; 1070C;LINEAR A SIGN A611;Lo;0;L;;;;;N;;;;; 1070D;LINEAR A SIGN A612;Lo;0;L;;;;;N;;;;; 1070E;LINEAR A SIGN A613;Lo;0;L;;;;;N;;;;; 1070F;LINEAR A SIGN A614;Lo;0;L;;;;;N;;;;; 10710;LINEAR A SIGN A615;Lo;0;L;;;;;N;;;;; 10711;LINEAR A SIGN A616;Lo;0;L;;;;;N;;;;; 10712;LINEAR A SIGN A617;Lo;0;L;;;;;N;;;;; 10713;LINEAR A SIGN A618;Lo;0;L;;;;;N;;;;; 10714;LINEAR A SIGN A619;Lo;0;L;;;;;N;;;;; 10715;LINEAR A SIGN A620;Lo;0;L;;;;;N;;;;; 10716;LINEAR A SIGN A621;Lo;0;L;;;;;N;;;;; 10717;LINEAR A SIGN A622;Lo;0;L;;;;;N;;;;; 10718;LINEAR A SIGN A623;Lo;0;L;;;;;N;;;;; 10719;LINEAR A SIGN A624;Lo;0;L;;;;;N;;;;; 1071A;LINEAR A SIGN A626;Lo;0;L;;;;;N;;;;; 1071B;LINEAR A SIGN A627;Lo;0;L;;;;;N;;;;; 1071C;LINEAR A SIGN A628;Lo;0;L;;;;;N;;;;; 1071D;LINEAR A SIGN A629;Lo;0;L;;;;;N;;;;; 1071E;LINEAR A SIGN A634;Lo;0;L;;;;;N;;;;; 1071F;LINEAR A SIGN A637;Lo;0;L;;;;;N;;;;; 10720;LINEAR A SIGN A638;Lo;0;L;;;;;N;;;;; 10721;LINEAR A SIGN A640;Lo;0;L;;;;;N;;;;; 10722;LINEAR A SIGN A642;Lo;0;L;;;;;N;;;;; 10723;LINEAR A SIGN A643;Lo;0;L;;;;;N;;;;; 10724;LINEAR A SIGN A644;Lo;0;L;;;;;N;;;;; 10725;LINEAR A SIGN A645;Lo;0;L;;;;;N;;;;; 10726;LINEAR A SIGN A646;Lo;0;L;;;;;N;;;;; 10727;LINEAR A SIGN A648;Lo;0;L;;;;;N;;;;; 10728;LINEAR A SIGN A649;Lo;0;L;;;;;N;;;;; 10729;LINEAR A SIGN A651;Lo;0;L;;;;;N;;;;; 1072A;LINEAR A SIGN A652;Lo;0;L;;;;;N;;;;; 1072B;LINEAR A SIGN A653;Lo;0;L;;;;;N;;;;; 1072C;LINEAR A SIGN A654;Lo;0;L;;;;;N;;;;; 1072D;LINEAR A SIGN A655;Lo;0;L;;;;;N;;;;; 1072E;LINEAR A SIGN A656;Lo;0;L;;;;;N;;;;; 1072F;LINEAR A SIGN A657;Lo;0;L;;;;;N;;;;; 10730;LINEAR A SIGN A658;Lo;0;L;;;;;N;;;;; 10731;LINEAR A SIGN A659;Lo;0;L;;;;;N;;;;; 10732;LINEAR A SIGN A660;Lo;0;L;;;;;N;;;;; 10733;LINEAR A SIGN A661;Lo;0;L;;;;;N;;;;; 10734;LINEAR A SIGN A662;Lo;0;L;;;;;N;;;;; 10735;LINEAR A SIGN A663;Lo;0;L;;;;;N;;;;; 10736;LINEAR A SIGN A664;Lo;0;L;;;;;N;;;;; 10740;LINEAR A SIGN A701 A;Lo;0;L;;;;;N;;;;; 10741;LINEAR A SIGN A702 B;Lo;0;L;;;;;N;;;;; 10742;LINEAR A SIGN A703 D;Lo;0;L;;;;;N;;;;; 10743;LINEAR A SIGN A704 E;Lo;0;L;;;;;N;;;;; 10744;LINEAR A SIGN A705 F;Lo;0;L;;;;;N;;;;; 10745;LINEAR A SIGN A706 H;Lo;0;L;;;;;N;;;;; 10746;LINEAR A SIGN A707 J;Lo;0;L;;;;;N;;;;; 10747;LINEAR A SIGN A708 K;Lo;0;L;;;;;N;;;;; 10748;LINEAR A SIGN A709 L;Lo;0;L;;;;;N;;;;; 10749;LINEAR A SIGN A709-2 L2;Lo;0;L;;;;;N;;;;; 1074A;LINEAR A SIGN A709-3 L3;Lo;0;L;;;;;N;;;;; 1074B;LINEAR A SIGN A709-4 L4;Lo;0;L;;;;;N;;;;; 1074C;LINEAR A SIGN A709-6 L6;Lo;0;L;;;;;N;;;;; 1074D;LINEAR A SIGN A710 W;Lo;0;L;;;;;N;;;;; 1074E;LINEAR A SIGN A711 X;Lo;0;L;;;;;N;;;;; 1074F;LINEAR A SIGN A712 Y;Lo;0;L;;;;;N;;;;; 10750;LINEAR A SIGN A713 OMEGA;Lo;0;L;;;;;N;;;;; 10751;LINEAR A SIGN A714 ABB;Lo;0;L;;;;;N;;;;; 10752;LINEAR A SIGN A715 BB;Lo;0;L;;;;;N;;;;; 10753;LINEAR A SIGN A717 DD;Lo;0;L;;;;;N;;;;; 10754;LINEAR A SIGN A726 EYYY;Lo;0;L;;;;;N;;;;; 10755;LINEAR A SIGN A732 JE;Lo;0;L;;;;;N;;;;; 10760;LINEAR A SIGN A800;Lo;0;L;;;;;N;;;;; 10761;LINEAR A SIGN A801;Lo;0;L;;;;;N;;;;; 10762;LINEAR A SIGN A802;Lo;0;L;;;;;N;;;;; 10763;LINEAR A SIGN A803;Lo;0;L;;;;;N;;;;; 10764;LINEAR A SIGN A804;Lo;0;L;;;;;N;;;;; 10765;LINEAR A SIGN A805;Lo;0;L;;;;;N;;;;; 10766;LINEAR A SIGN A806;Lo;0;L;;;;;N;;;;; 10767;LINEAR A SIGN A807;Lo;0;L;;;;;N;;;;; 10800;CYPRIOT SYLLABLE A;Lo;0;R;;;;;N;;;;; 10801;CYPRIOT SYLLABLE E;Lo;0;R;;;;;N;;;;; 10802;CYPRIOT SYLLABLE I;Lo;0;R;;;;;N;;;;; 10803;CYPRIOT SYLLABLE O;Lo;0;R;;;;;N;;;;; 10804;CYPRIOT SYLLABLE U;Lo;0;R;;;;;N;;;;; 10805;CYPRIOT SYLLABLE JA;Lo;0;R;;;;;N;;;;; 10808;CYPRIOT SYLLABLE JO;Lo;0;R;;;;;N;;;;; 1080A;CYPRIOT SYLLABLE KA;Lo;0;R;;;;;N;;;;; 1080B;CYPRIOT SYLLABLE KE;Lo;0;R;;;;;N;;;;; 1080C;CYPRIOT SYLLABLE KI;Lo;0;R;;;;;N;;;;; 1080D;CYPRIOT SYLLABLE KO;Lo;0;R;;;;;N;;;;; 1080E;CYPRIOT SYLLABLE KU;Lo;0;R;;;;;N;;;;; 1080F;CYPRIOT SYLLABLE LA;Lo;0;R;;;;;N;;;;; 10810;CYPRIOT SYLLABLE LE;Lo;0;R;;;;;N;;;;; 10811;CYPRIOT SYLLABLE LI;Lo;0;R;;;;;N;;;;; 10812;CYPRIOT SYLLABLE LO;Lo;0;R;;;;;N;;;;; 10813;CYPRIOT SYLLABLE LU;Lo;0;R;;;;;N;;;;; 10814;CYPRIOT SYLLABLE MA;Lo;0;R;;;;;N;;;;; 10815;CYPRIOT SYLLABLE ME;Lo;0;R;;;;;N;;;;; 10816;CYPRIOT SYLLABLE MI;Lo;0;R;;;;;N;;;;; 10817;CYPRIOT SYLLABLE MO;Lo;0;R;;;;;N;;;;; 10818;CYPRIOT SYLLABLE MU;Lo;0;R;;;;;N;;;;; 10819;CYPRIOT SYLLABLE NA;Lo;0;R;;;;;N;;;;; 1081A;CYPRIOT SYLLABLE NE;Lo;0;R;;;;;N;;;;; 1081B;CYPRIOT SYLLABLE NI;Lo;0;R;;;;;N;;;;; 1081C;CYPRIOT SYLLABLE NO;Lo;0;R;;;;;N;;;;; 1081D;CYPRIOT SYLLABLE NU;Lo;0;R;;;;;N;;;;; 1081E;CYPRIOT SYLLABLE PA;Lo;0;R;;;;;N;;;;; 1081F;CYPRIOT SYLLABLE PE;Lo;0;R;;;;;N;;;;; 10820;CYPRIOT SYLLABLE PI;Lo;0;R;;;;;N;;;;; 10821;CYPRIOT SYLLABLE PO;Lo;0;R;;;;;N;;;;; 10822;CYPRIOT SYLLABLE PU;Lo;0;R;;;;;N;;;;; 10823;CYPRIOT SYLLABLE RA;Lo;0;R;;;;;N;;;;; 10824;CYPRIOT SYLLABLE RE;Lo;0;R;;;;;N;;;;; 10825;CYPRIOT SYLLABLE RI;Lo;0;R;;;;;N;;;;; 10826;CYPRIOT SYLLABLE RO;Lo;0;R;;;;;N;;;;; 10827;CYPRIOT SYLLABLE RU;Lo;0;R;;;;;N;;;;; 10828;CYPRIOT SYLLABLE SA;Lo;0;R;;;;;N;;;;; 10829;CYPRIOT SYLLABLE SE;Lo;0;R;;;;;N;;;;; 1082A;CYPRIOT SYLLABLE SI;Lo;0;R;;;;;N;;;;; 1082B;CYPRIOT SYLLABLE SO;Lo;0;R;;;;;N;;;;; 1082C;CYPRIOT SYLLABLE SU;Lo;0;R;;;;;N;;;;; 1082D;CYPRIOT SYLLABLE TA;Lo;0;R;;;;;N;;;;; 1082E;CYPRIOT SYLLABLE TE;Lo;0;R;;;;;N;;;;; 1082F;CYPRIOT SYLLABLE TI;Lo;0;R;;;;;N;;;;; 10830;CYPRIOT SYLLABLE TO;Lo;0;R;;;;;N;;;;; 10831;CYPRIOT SYLLABLE TU;Lo;0;R;;;;;N;;;;; 10832;CYPRIOT SYLLABLE WA;Lo;0;R;;;;;N;;;;; 10833;CYPRIOT SYLLABLE WE;Lo;0;R;;;;;N;;;;; 10834;CYPRIOT SYLLABLE WI;Lo;0;R;;;;;N;;;;; 10835;CYPRIOT SYLLABLE WO;Lo;0;R;;;;;N;;;;; 10837;CYPRIOT SYLLABLE XA;Lo;0;R;;;;;N;;;;; 10838;CYPRIOT SYLLABLE XE;Lo;0;R;;;;;N;;;;; 1083C;CYPRIOT SYLLABLE ZA;Lo;0;R;;;;;N;;;;; 1083F;CYPRIOT SYLLABLE ZO;Lo;0;R;;;;;N;;;;; 10840;IMPERIAL ARAMAIC LETTER ALEPH;Lo;0;R;;;;;N;;;;; 10841;IMPERIAL ARAMAIC LETTER BETH;Lo;0;R;;;;;N;;;;; 10842;IMPERIAL ARAMAIC LETTER GIMEL;Lo;0;R;;;;;N;;;;; 10843;IMPERIAL ARAMAIC LETTER DALETH;Lo;0;R;;;;;N;;;;; 10844;IMPERIAL ARAMAIC LETTER HE;Lo;0;R;;;;;N;;;;; 10845;IMPERIAL ARAMAIC LETTER WAW;Lo;0;R;;;;;N;;;;; 10846;IMPERIAL ARAMAIC LETTER ZAYIN;Lo;0;R;;;;;N;;;;; 10847;IMPERIAL ARAMAIC LETTER HETH;Lo;0;R;;;;;N;;;;; 10848;IMPERIAL ARAMAIC LETTER TETH;Lo;0;R;;;;;N;;;;; 10849;IMPERIAL ARAMAIC LETTER YODH;Lo;0;R;;;;;N;;;;; 1084A;IMPERIAL ARAMAIC LETTER KAPH;Lo;0;R;;;;;N;;;;; 1084B;IMPERIAL ARAMAIC LETTER LAMEDH;Lo;0;R;;;;;N;;;;; 1084C;IMPERIAL ARAMAIC LETTER MEM;Lo;0;R;;;;;N;;;;; 1084D;IMPERIAL ARAMAIC LETTER NUN;Lo;0;R;;;;;N;;;;; 1084E;IMPERIAL ARAMAIC LETTER SAMEKH;Lo;0;R;;;;;N;;;;; 1084F;IMPERIAL ARAMAIC LETTER AYIN;Lo;0;R;;;;;N;;;;; 10850;IMPERIAL ARAMAIC LETTER PE;Lo;0;R;;;;;N;;;;; 10851;IMPERIAL ARAMAIC LETTER SADHE;Lo;0;R;;;;;N;;;;; 10852;IMPERIAL ARAMAIC LETTER QOPH;Lo;0;R;;;;;N;;;;; 10853;IMPERIAL ARAMAIC LETTER RESH;Lo;0;R;;;;;N;;;;; 10854;IMPERIAL ARAMAIC LETTER SHIN;Lo;0;R;;;;;N;;;;; 10855;IMPERIAL ARAMAIC LETTER TAW;Lo;0;R;;;;;N;;;;; 10857;IMPERIAL ARAMAIC SECTION SIGN;Po;0;R;;;;;N;;;;; 10858;IMPERIAL ARAMAIC NUMBER ONE;No;0;R;;;;1;N;;;;; 10859;IMPERIAL ARAMAIC NUMBER TWO;No;0;R;;;;2;N;;;;; 1085A;IMPERIAL ARAMAIC NUMBER THREE;No;0;R;;;;3;N;;;;; 1085B;IMPERIAL ARAMAIC NUMBER TEN;No;0;R;;;;10;N;;;;; 1085C;IMPERIAL ARAMAIC NUMBER TWENTY;No;0;R;;;;20;N;;;;; 1085D;IMPERIAL ARAMAIC NUMBER ONE HUNDRED;No;0;R;;;;100;N;;;;; 1085E;IMPERIAL ARAMAIC NUMBER ONE THOUSAND;No;0;R;;;;1000;N;;;;; 1085F;IMPERIAL ARAMAIC NUMBER TEN THOUSAND;No;0;R;;;;10000;N;;;;; 10860;PALMYRENE LETTER ALEPH;Lo;0;R;;;;;N;;;;; 10861;PALMYRENE LETTER BETH;Lo;0;R;;;;;N;;;;; 10862;PALMYRENE LETTER GIMEL;Lo;0;R;;;;;N;;;;; 10863;PALMYRENE LETTER DALETH;Lo;0;R;;;;;N;;;;; 10864;PALMYRENE LETTER HE;Lo;0;R;;;;;N;;;;; 10865;PALMYRENE LETTER WAW;Lo;0;R;;;;;N;;;;; 10866;PALMYRENE LETTER ZAYIN;Lo;0;R;;;;;N;;;;; 10867;PALMYRENE LETTER HETH;Lo;0;R;;;;;N;;;;; 10868;PALMYRENE LETTER TETH;Lo;0;R;;;;;N;;;;; 10869;PALMYRENE LETTER YODH;Lo;0;R;;;;;N;;;;; 1086A;PALMYRENE LETTER KAPH;Lo;0;R;;;;;N;;;;; 1086B;PALMYRENE LETTER LAMEDH;Lo;0;R;;;;;N;;;;; 1086C;PALMYRENE LETTER MEM;Lo;0;R;;;;;N;;;;; 1086D;PALMYRENE LETTER FINAL NUN;Lo;0;R;;;;;N;;;;; 1086E;PALMYRENE LETTER NUN;Lo;0;R;;;;;N;;;;; 1086F;PALMYRENE LETTER SAMEKH;Lo;0;R;;;;;N;;;;; 10870;PALMYRENE LETTER AYIN;Lo;0;R;;;;;N;;;;; 10871;PALMYRENE LETTER PE;Lo;0;R;;;;;N;;;;; 10872;PALMYRENE LETTER SADHE;Lo;0;R;;;;;N;;;;; 10873;PALMYRENE LETTER QOPH;Lo;0;R;;;;;N;;;;; 10874;PALMYRENE LETTER RESH;Lo;0;R;;;;;N;;;;; 10875;PALMYRENE LETTER SHIN;Lo;0;R;;;;;N;;;;; 10876;PALMYRENE LETTER TAW;Lo;0;R;;;;;N;;;;; 10877;PALMYRENE LEFT-POINTING FLEURON;So;0;R;;;;;N;;;;; 10878;PALMYRENE RIGHT-POINTING FLEURON;So;0;R;;;;;N;;;;; 10879;PALMYRENE NUMBER ONE;No;0;R;;;;1;N;;;;; 1087A;PALMYRENE NUMBER TWO;No;0;R;;;;2;N;;;;; 1087B;PALMYRENE NUMBER THREE;No;0;R;;;;3;N;;;;; 1087C;PALMYRENE NUMBER FOUR;No;0;R;;;;4;N;;;;; 1087D;PALMYRENE NUMBER FIVE;No;0;R;;;;5;N;;;;; 1087E;PALMYRENE NUMBER TEN;No;0;R;;;;10;N;;;;; 1087F;PALMYRENE NUMBER TWENTY;No;0;R;;;;20;N;;;;; 10880;NABATAEAN LETTER FINAL ALEPH;Lo;0;R;;;;;N;;;;; 10881;NABATAEAN LETTER ALEPH;Lo;0;R;;;;;N;;;;; 10882;NABATAEAN LETTER FINAL BETH;Lo;0;R;;;;;N;;;;; 10883;NABATAEAN LETTER BETH;Lo;0;R;;;;;N;;;;; 10884;NABATAEAN LETTER GIMEL;Lo;0;R;;;;;N;;;;; 10885;NABATAEAN LETTER DALETH;Lo;0;R;;;;;N;;;;; 10886;NABATAEAN LETTER FINAL HE;Lo;0;R;;;;;N;;;;; 10887;NABATAEAN LETTER HE;Lo;0;R;;;;;N;;;;; 10888;NABATAEAN LETTER WAW;Lo;0;R;;;;;N;;;;; 10889;NABATAEAN LETTER ZAYIN;Lo;0;R;;;;;N;;;;; 1088A;NABATAEAN LETTER HETH;Lo;0;R;;;;;N;;;;; 1088B;NABATAEAN LETTER TETH;Lo;0;R;;;;;N;;;;; 1088C;NABATAEAN LETTER FINAL YODH;Lo;0;R;;;;;N;;;;; 1088D;NABATAEAN LETTER YODH;Lo;0;R;;;;;N;;;;; 1088E;NABATAEAN LETTER FINAL KAPH;Lo;0;R;;;;;N;;;;; 1088F;NABATAEAN LETTER KAPH;Lo;0;R;;;;;N;;;;; 10890;NABATAEAN LETTER FINAL LAMEDH;Lo;0;R;;;;;N;;;;; 10891;NABATAEAN LETTER LAMEDH;Lo;0;R;;;;;N;;;;; 10892;NABATAEAN LETTER FINAL MEM;Lo;0;R;;;;;N;;;;; 10893;NABATAEAN LETTER MEM;Lo;0;R;;;;;N;;;;; 10894;NABATAEAN LETTER FINAL NUN;Lo;0;R;;;;;N;;;;; 10895;NABATAEAN LETTER NUN;Lo;0;R;;;;;N;;;;; 10896;NABATAEAN LETTER SAMEKH;Lo;0;R;;;;;N;;;;; 10897;NABATAEAN LETTER AYIN;Lo;0;R;;;;;N;;;;; 10898;NABATAEAN LETTER PE;Lo;0;R;;;;;N;;;;; 10899;NABATAEAN LETTER SADHE;Lo;0;R;;;;;N;;;;; 1089A;NABATAEAN LETTER QOPH;Lo;0;R;;;;;N;;;;; 1089B;NABATAEAN LETTER RESH;Lo;0;R;;;;;N;;;;; 1089C;NABATAEAN LETTER FINAL SHIN;Lo;0;R;;;;;N;;;;; 1089D;NABATAEAN LETTER SHIN;Lo;0;R;;;;;N;;;;; 1089E;NABATAEAN LETTER TAW;Lo;0;R;;;;;N;;;;; 108A7;NABATAEAN NUMBER ONE;No;0;R;;;;1;N;;;;; 108A8;NABATAEAN NUMBER TWO;No;0;R;;;;2;N;;;;; 108A9;NABATAEAN NUMBER THREE;No;0;R;;;;3;N;;;;; 108AA;NABATAEAN NUMBER FOUR;No;0;R;;;;4;N;;;;; 108AB;NABATAEAN CRUCIFORM NUMBER FOUR;No;0;R;;;;4;N;;;;; 108AC;NABATAEAN NUMBER FIVE;No;0;R;;;;5;N;;;;; 108AD;NABATAEAN NUMBER TEN;No;0;R;;;;10;N;;;;; 108AE;NABATAEAN NUMBER TWENTY;No;0;R;;;;20;N;;;;; 108AF;NABATAEAN NUMBER ONE HUNDRED;No;0;R;;;;100;N;;;;; 10900;PHOENICIAN LETTER ALF;Lo;0;R;;;;;N;;;;; 10901;PHOENICIAN LETTER BET;Lo;0;R;;;;;N;;;;; 10902;PHOENICIAN LETTER GAML;Lo;0;R;;;;;N;;;;; 10903;PHOENICIAN LETTER DELT;Lo;0;R;;;;;N;;;;; 10904;PHOENICIAN LETTER HE;Lo;0;R;;;;;N;;;;; 10905;PHOENICIAN LETTER WAU;Lo;0;R;;;;;N;;;;; 10906;PHOENICIAN LETTER ZAI;Lo;0;R;;;;;N;;;;; 10907;PHOENICIAN LETTER HET;Lo;0;R;;;;;N;;;;; 10908;PHOENICIAN LETTER TET;Lo;0;R;;;;;N;;;;; 10909;PHOENICIAN LETTER YOD;Lo;0;R;;;;;N;;;;; 1090A;PHOENICIAN LETTER KAF;Lo;0;R;;;;;N;;;;; 1090B;PHOENICIAN LETTER LAMD;Lo;0;R;;;;;N;;;;; 1090C;PHOENICIAN LETTER MEM;Lo;0;R;;;;;N;;;;; 1090D;PHOENICIAN LETTER NUN;Lo;0;R;;;;;N;;;;; 1090E;PHOENICIAN LETTER SEMK;Lo;0;R;;;;;N;;;;; 1090F;PHOENICIAN LETTER AIN;Lo;0;R;;;;;N;;;;; 10910;PHOENICIAN LETTER PE;Lo;0;R;;;;;N;;;;; 10911;PHOENICIAN LETTER SADE;Lo;0;R;;;;;N;;;;; 10912;PHOENICIAN LETTER QOF;Lo;0;R;;;;;N;;;;; 10913;PHOENICIAN LETTER ROSH;Lo;0;R;;;;;N;;;;; 10914;PHOENICIAN LETTER SHIN;Lo;0;R;;;;;N;;;;; 10915;PHOENICIAN LETTER TAU;Lo;0;R;;;;;N;;;;; 10916;PHOENICIAN NUMBER ONE;No;0;R;;;;1;N;;;;; 10917;PHOENICIAN NUMBER TEN;No;0;R;;;;10;N;;;;; 10918;PHOENICIAN NUMBER TWENTY;No;0;R;;;;20;N;;;;; 10919;PHOENICIAN NUMBER ONE HUNDRED;No;0;R;;;;100;N;;;;; 1091A;PHOENICIAN NUMBER TWO;No;0;R;;;;2;N;;;;; 1091B;PHOENICIAN NUMBER THREE;No;0;R;;;;3;N;;;;; 1091F;PHOENICIAN WORD SEPARATOR;Po;0;ON;;;;;N;;;;; 10920;LYDIAN LETTER A;Lo;0;R;;;;;N;;;;; 10921;LYDIAN LETTER B;Lo;0;R;;;;;N;;;;; 10922;LYDIAN LETTER G;Lo;0;R;;;;;N;;;;; 10923;LYDIAN LETTER D;Lo;0;R;;;;;N;;;;; 10924;LYDIAN LETTER E;Lo;0;R;;;;;N;;;;; 10925;LYDIAN LETTER V;Lo;0;R;;;;;N;;;;; 10926;LYDIAN LETTER I;Lo;0;R;;;;;N;;;;; 10927;LYDIAN LETTER Y;Lo;0;R;;;;;N;;;;; 10928;LYDIAN LETTER K;Lo;0;R;;;;;N;;;;; 10929;LYDIAN LETTER L;Lo;0;R;;;;;N;;;;; 1092A;LYDIAN LETTER M;Lo;0;R;;;;;N;;;;; 1092B;LYDIAN LETTER N;Lo;0;R;;;;;N;;;;; 1092C;LYDIAN LETTER O;Lo;0;R;;;;;N;;;;; 1092D;LYDIAN LETTER R;Lo;0;R;;;;;N;;;;; 1092E;LYDIAN LETTER SS;Lo;0;R;;;;;N;;;;; 1092F;LYDIAN LETTER T;Lo;0;R;;;;;N;;;;; 10930;LYDIAN LETTER U;Lo;0;R;;;;;N;;;;; 10931;LYDIAN LETTER F;Lo;0;R;;;;;N;;;;; 10932;LYDIAN LETTER Q;Lo;0;R;;;;;N;;;;; 10933;LYDIAN LETTER S;Lo;0;R;;;;;N;;;;; 10934;LYDIAN LETTER TT;Lo;0;R;;;;;N;;;;; 10935;LYDIAN LETTER AN;Lo;0;R;;;;;N;;;;; 10936;LYDIAN LETTER EN;Lo;0;R;;;;;N;;;;; 10937;LYDIAN LETTER LY;Lo;0;R;;;;;N;;;;; 10938;LYDIAN LETTER NN;Lo;0;R;;;;;N;;;;; 10939;LYDIAN LETTER C;Lo;0;R;;;;;N;;;;; 1093F;LYDIAN TRIANGULAR MARK;Po;0;R;;;;;N;;;;; 10980;MEROITIC HIEROGLYPHIC LETTER A;Lo;0;R;;;;;N;;;;; 10981;MEROITIC HIEROGLYPHIC LETTER E;Lo;0;R;;;;;N;;;;; 10982;MEROITIC HIEROGLYPHIC LETTER I;Lo;0;R;;;;;N;;;;; 10983;MEROITIC HIEROGLYPHIC LETTER O;Lo;0;R;;;;;N;;;;; 10984;MEROITIC HIEROGLYPHIC LETTER YA;Lo;0;R;;;;;N;;;;; 10985;MEROITIC HIEROGLYPHIC LETTER WA;Lo;0;R;;;;;N;;;;; 10986;MEROITIC HIEROGLYPHIC LETTER BA;Lo;0;R;;;;;N;;;;; 10987;MEROITIC HIEROGLYPHIC LETTER BA-2;Lo;0;R;;;;;N;;;;; 10988;MEROITIC HIEROGLYPHIC LETTER PA;Lo;0;R;;;;;N;;;;; 10989;MEROITIC HIEROGLYPHIC LETTER MA;Lo;0;R;;;;;N;;;;; 1098A;MEROITIC HIEROGLYPHIC LETTER NA;Lo;0;R;;;;;N;;;;; 1098B;MEROITIC HIEROGLYPHIC LETTER NA-2;Lo;0;R;;;;;N;;;;; 1098C;MEROITIC HIEROGLYPHIC LETTER NE;Lo;0;R;;;;;N;;;;; 1098D;MEROITIC HIEROGLYPHIC LETTER NE-2;Lo;0;R;;;;;N;;;;; 1098E;MEROITIC HIEROGLYPHIC LETTER RA;Lo;0;R;;;;;N;;;;; 1098F;MEROITIC HIEROGLYPHIC LETTER RA-2;Lo;0;R;;;;;N;;;;; 10990;MEROITIC HIEROGLYPHIC LETTER LA;Lo;0;R;;;;;N;;;;; 10991;MEROITIC HIEROGLYPHIC LETTER KHA;Lo;0;R;;;;;N;;;;; 10992;MEROITIC HIEROGLYPHIC LETTER HHA;Lo;0;R;;;;;N;;;;; 10993;MEROITIC HIEROGLYPHIC LETTER SA;Lo;0;R;;;;;N;;;;; 10994;MEROITIC HIEROGLYPHIC LETTER SA-2;Lo;0;R;;;;;N;;;;; 10995;MEROITIC HIEROGLYPHIC LETTER SE;Lo;0;R;;;;;N;;;;; 10996;MEROITIC HIEROGLYPHIC LETTER KA;Lo;0;R;;;;;N;;;;; 10997;MEROITIC HIEROGLYPHIC LETTER QA;Lo;0;R;;;;;N;;;;; 10998;MEROITIC HIEROGLYPHIC LETTER TA;Lo;0;R;;;;;N;;;;; 10999;MEROITIC HIEROGLYPHIC LETTER TA-2;Lo;0;R;;;;;N;;;;; 1099A;MEROITIC HIEROGLYPHIC LETTER TE;Lo;0;R;;;;;N;;;;; 1099B;MEROITIC HIEROGLYPHIC LETTER TE-2;Lo;0;R;;;;;N;;;;; 1099C;MEROITIC HIEROGLYPHIC LETTER TO;Lo;0;R;;;;;N;;;;; 1099D;MEROITIC HIEROGLYPHIC LETTER DA;Lo;0;R;;;;;N;;;;; 1099E;MEROITIC HIEROGLYPHIC SYMBOL VIDJ;Lo;0;R;;;;;N;;;;; 1099F;MEROITIC HIEROGLYPHIC SYMBOL VIDJ-2;Lo;0;R;;;;;N;;;;; 109A0;MEROITIC CURSIVE LETTER A;Lo;0;R;;;;;N;;;;; 109A1;MEROITIC CURSIVE LETTER E;Lo;0;R;;;;;N;;;;; 109A2;MEROITIC CURSIVE LETTER I;Lo;0;R;;;;;N;;;;; 109A3;MEROITIC CURSIVE LETTER O;Lo;0;R;;;;;N;;;;; 109A4;MEROITIC CURSIVE LETTER YA;Lo;0;R;;;;;N;;;;; 109A5;MEROITIC CURSIVE LETTER WA;Lo;0;R;;;;;N;;;;; 109A6;MEROITIC CURSIVE LETTER BA;Lo;0;R;;;;;N;;;;; 109A7;MEROITIC CURSIVE LETTER PA;Lo;0;R;;;;;N;;;;; 109A8;MEROITIC CURSIVE LETTER MA;Lo;0;R;;;;;N;;;;; 109A9;MEROITIC CURSIVE LETTER NA;Lo;0;R;;;;;N;;;;; 109AA;MEROITIC CURSIVE LETTER NE;Lo;0;R;;;;;N;;;;; 109AB;MEROITIC CURSIVE LETTER RA;Lo;0;R;;;;;N;;;;; 109AC;MEROITIC CURSIVE LETTER LA;Lo;0;R;;;;;N;;;;; 109AD;MEROITIC CURSIVE LETTER KHA;Lo;0;R;;;;;N;;;;; 109AE;MEROITIC CURSIVE LETTER HHA;Lo;0;R;;;;;N;;;;; 109AF;MEROITIC CURSIVE LETTER SA;Lo;0;R;;;;;N;;;;; 109B0;MEROITIC CURSIVE LETTER ARCHAIC SA;Lo;0;R;;;;;N;;;;; 109B1;MEROITIC CURSIVE LETTER SE;Lo;0;R;;;;;N;;;;; 109B2;MEROITIC CURSIVE LETTER KA;Lo;0;R;;;;;N;;;;; 109B3;MEROITIC CURSIVE LETTER QA;Lo;0;R;;;;;N;;;;; 109B4;MEROITIC CURSIVE LETTER TA;Lo;0;R;;;;;N;;;;; 109B5;MEROITIC CURSIVE LETTER TE;Lo;0;R;;;;;N;;;;; 109B6;MEROITIC CURSIVE LETTER TO;Lo;0;R;;;;;N;;;;; 109B7;MEROITIC CURSIVE LETTER DA;Lo;0;R;;;;;N;;;;; 109BE;MEROITIC CURSIVE LOGOGRAM RMT;Lo;0;R;;;;;N;;;;; 109BF;MEROITIC CURSIVE LOGOGRAM IMN;Lo;0;R;;;;;N;;;;; 10A00;KHAROSHTHI LETTER A;Lo;0;R;;;;;N;;;;; 10A01;KHAROSHTHI VOWEL SIGN I;Mn;0;NSM;;;;;N;;;;; 10A02;KHAROSHTHI VOWEL SIGN U;Mn;0;NSM;;;;;N;;;;; 10A03;KHAROSHTHI VOWEL SIGN VOCALIC R;Mn;0;NSM;;;;;N;;;;; 10A05;KHAROSHTHI VOWEL SIGN E;Mn;0;NSM;;;;;N;;;;; 10A06;KHAROSHTHI VOWEL SIGN O;Mn;0;NSM;;;;;N;;;;; 10A0C;KHAROSHTHI VOWEL LENGTH MARK;Mn;0;NSM;;;;;N;;;;; 10A0D;KHAROSHTHI SIGN DOUBLE RING BELOW;Mn;220;NSM;;;;;N;;;;; 10A0E;KHAROSHTHI SIGN ANUSVARA;Mn;0;NSM;;;;;N;;;;; 10A0F;KHAROSHTHI SIGN VISARGA;Mn;230;NSM;;;;;N;;;;; 10A10;KHAROSHTHI LETTER KA;Lo;0;R;;;;;N;;;;; 10A11;KHAROSHTHI LETTER KHA;Lo;0;R;;;;;N;;;;; 10A12;KHAROSHTHI LETTER GA;Lo;0;R;;;;;N;;;;; 10A13;KHAROSHTHI LETTER GHA;Lo;0;R;;;;;N;;;;; 10A15;KHAROSHTHI LETTER CA;Lo;0;R;;;;;N;;;;; 10A16;KHAROSHTHI LETTER CHA;Lo;0;R;;;;;N;;;;; 10A17;KHAROSHTHI LETTER JA;Lo;0;R;;;;;N;;;;; 10A19;KHAROSHTHI LETTER NYA;Lo;0;R;;;;;N;;;;; 10A1A;KHAROSHTHI LETTER TTA;Lo;0;R;;;;;N;;;;; 10A1B;KHAROSHTHI LETTER TTHA;Lo;0;R;;;;;N;;;;; 10A1C;KHAROSHTHI LETTER DDA;Lo;0;R;;;;;N;;;;; 10A1D;KHAROSHTHI LETTER DDHA;Lo;0;R;;;;;N;;;;; 10A1E;KHAROSHTHI LETTER NNA;Lo;0;R;;;;;N;;;;; 10A1F;KHAROSHTHI LETTER TA;Lo;0;R;;;;;N;;;;; 10A20;KHAROSHTHI LETTER THA;Lo;0;R;;;;;N;;;;; 10A21;KHAROSHTHI LETTER DA;Lo;0;R;;;;;N;;;;; 10A22;KHAROSHTHI LETTER DHA;Lo;0;R;;;;;N;;;;; 10A23;KHAROSHTHI LETTER NA;Lo;0;R;;;;;N;;;;; 10A24;KHAROSHTHI LETTER PA;Lo;0;R;;;;;N;;;;; 10A25;KHAROSHTHI LETTER PHA;Lo;0;R;;;;;N;;;;; 10A26;KHAROSHTHI LETTER BA;Lo;0;R;;;;;N;;;;; 10A27;KHAROSHTHI LETTER BHA;Lo;0;R;;;;;N;;;;; 10A28;KHAROSHTHI LETTER MA;Lo;0;R;;;;;N;;;;; 10A29;KHAROSHTHI LETTER YA;Lo;0;R;;;;;N;;;;; 10A2A;KHAROSHTHI LETTER RA;Lo;0;R;;;;;N;;;;; 10A2B;KHAROSHTHI LETTER LA;Lo;0;R;;;;;N;;;;; 10A2C;KHAROSHTHI LETTER VA;Lo;0;R;;;;;N;;;;; 10A2D;KHAROSHTHI LETTER SHA;Lo;0;R;;;;;N;;;;; 10A2E;KHAROSHTHI LETTER SSA;Lo;0;R;;;;;N;;;;; 10A2F;KHAROSHTHI LETTER SA;Lo;0;R;;;;;N;;;;; 10A30;KHAROSHTHI LETTER ZA;Lo;0;R;;;;;N;;;;; 10A31;KHAROSHTHI LETTER HA;Lo;0;R;;;;;N;;;;; 10A32;KHAROSHTHI LETTER KKA;Lo;0;R;;;;;N;;;;; 10A33;KHAROSHTHI LETTER TTTHA;Lo;0;R;;;;;N;;;;; 10A38;KHAROSHTHI SIGN BAR ABOVE;Mn;230;NSM;;;;;N;;;;; 10A39;KHAROSHTHI SIGN CAUDA;Mn;1;NSM;;;;;N;;;;; 10A3A;KHAROSHTHI SIGN DOT BELOW;Mn;220;NSM;;;;;N;;;;; 10A3F;KHAROSHTHI VIRAMA;Mn;9;NSM;;;;;N;;;;; 10A40;KHAROSHTHI DIGIT ONE;No;0;R;;;1;1;N;;;;; 10A41;KHAROSHTHI DIGIT TWO;No;0;R;;;2;2;N;;;;; 10A42;KHAROSHTHI DIGIT THREE;No;0;R;;;3;3;N;;;;; 10A43;KHAROSHTHI DIGIT FOUR;No;0;R;;;4;4;N;;;;; 10A44;KHAROSHTHI NUMBER TEN;No;0;R;;;;10;N;;;;; 10A45;KHAROSHTHI NUMBER TWENTY;No;0;R;;;;20;N;;;;; 10A46;KHAROSHTHI NUMBER ONE HUNDRED;No;0;R;;;;100;N;;;;; 10A47;KHAROSHTHI NUMBER ONE THOUSAND;No;0;R;;;;1000;N;;;;; 10A50;KHAROSHTHI PUNCTUATION DOT;Po;0;R;;;;;N;;;;; 10A51;KHAROSHTHI PUNCTUATION SMALL CIRCLE;Po;0;R;;;;;N;;;;; 10A52;KHAROSHTHI PUNCTUATION CIRCLE;Po;0;R;;;;;N;;;;; 10A53;KHAROSHTHI PUNCTUATION CRESCENT BAR;Po;0;R;;;;;N;;;;; 10A54;KHAROSHTHI PUNCTUATION MANGALAM;Po;0;R;;;;;N;;;;; 10A55;KHAROSHTHI PUNCTUATION LOTUS;Po;0;R;;;;;N;;;;; 10A56;KHAROSHTHI PUNCTUATION DANDA;Po;0;R;;;;;N;;;;; 10A57;KHAROSHTHI PUNCTUATION DOUBLE DANDA;Po;0;R;;;;;N;;;;; 10A58;KHAROSHTHI PUNCTUATION LINES;Po;0;R;;;;;N;;;;; 10A60;OLD SOUTH ARABIAN LETTER HE;Lo;0;R;;;;;N;;;;; 10A61;OLD SOUTH ARABIAN LETTER LAMEDH;Lo;0;R;;;;;N;;;;; 10A62;OLD SOUTH ARABIAN LETTER HETH;Lo;0;R;;;;;N;;;;; 10A63;OLD SOUTH ARABIAN LETTER MEM;Lo;0;R;;;;;N;;;;; 10A64;OLD SOUTH ARABIAN LETTER QOPH;Lo;0;R;;;;;N;;;;; 10A65;OLD SOUTH ARABIAN LETTER WAW;Lo;0;R;;;;;N;;;;; 10A66;OLD SOUTH ARABIAN LETTER SHIN;Lo;0;R;;;;;N;;;;; 10A67;OLD SOUTH ARABIAN LETTER RESH;Lo;0;R;;;;;N;;;;; 10A68;OLD SOUTH ARABIAN LETTER BETH;Lo;0;R;;;;;N;;;;; 10A69;OLD SOUTH ARABIAN LETTER TAW;Lo;0;R;;;;;N;;;;; 10A6A;OLD SOUTH ARABIAN LETTER SAT;Lo;0;R;;;;;N;;;;; 10A6B;OLD SOUTH ARABIAN LETTER KAPH;Lo;0;R;;;;;N;;;;; 10A6C;OLD SOUTH ARABIAN LETTER NUN;Lo;0;R;;;;;N;;;;; 10A6D;OLD SOUTH ARABIAN LETTER KHETH;Lo;0;R;;;;;N;;;;; 10A6E;OLD SOUTH ARABIAN LETTER SADHE;Lo;0;R;;;;;N;;;;; 10A6F;OLD SOUTH ARABIAN LETTER SAMEKH;Lo;0;R;;;;;N;;;;; 10A70;OLD SOUTH ARABIAN LETTER FE;Lo;0;R;;;;;N;;;;; 10A71;OLD SOUTH ARABIAN LETTER ALEF;Lo;0;R;;;;;N;;;;; 10A72;OLD SOUTH ARABIAN LETTER AYN;Lo;0;R;;;;;N;;;;; 10A73;OLD SOUTH ARABIAN LETTER DHADHE;Lo;0;R;;;;;N;;;;; 10A74;OLD SOUTH ARABIAN LETTER GIMEL;Lo;0;R;;;;;N;;;;; 10A75;OLD SOUTH ARABIAN LETTER DALETH;Lo;0;R;;;;;N;;;;; 10A76;OLD SOUTH ARABIAN LETTER GHAYN;Lo;0;R;;;;;N;;;;; 10A77;OLD SOUTH ARABIAN LETTER TETH;Lo;0;R;;;;;N;;;;; 10A78;OLD SOUTH ARABIAN LETTER ZAYN;Lo;0;R;;;;;N;;;;; 10A79;OLD SOUTH ARABIAN LETTER DHALETH;Lo;0;R;;;;;N;;;;; 10A7A;OLD SOUTH ARABIAN LETTER YODH;Lo;0;R;;;;;N;;;;; 10A7B;OLD SOUTH ARABIAN LETTER THAW;Lo;0;R;;;;;N;;;;; 10A7C;OLD SOUTH ARABIAN LETTER THETH;Lo;0;R;;;;;N;;;;; 10A7D;OLD SOUTH ARABIAN NUMBER ONE;No;0;R;;;;1;N;;;;; 10A7E;OLD SOUTH ARABIAN NUMBER FIFTY;No;0;R;;;;50;N;;;;; 10A7F;OLD SOUTH ARABIAN NUMERIC INDICATOR;Po;0;R;;;;;N;;;;; 10A80;OLD NORTH ARABIAN LETTER HEH;Lo;0;R;;;;;N;;;;; 10A81;OLD NORTH ARABIAN LETTER LAM;Lo;0;R;;;;;N;;;;; 10A82;OLD NORTH ARABIAN LETTER HAH;Lo;0;R;;;;;N;;;;; 10A83;OLD NORTH ARABIAN LETTER MEEM;Lo;0;R;;;;;N;;;;; 10A84;OLD NORTH ARABIAN LETTER QAF;Lo;0;R;;;;;N;;;;; 10A85;OLD NORTH ARABIAN LETTER WAW;Lo;0;R;;;;;N;;;;; 10A86;OLD NORTH ARABIAN LETTER ES-2;Lo;0;R;;;;;N;;;;; 10A87;OLD NORTH ARABIAN LETTER REH;Lo;0;R;;;;;N;;;;; 10A88;OLD NORTH ARABIAN LETTER BEH;Lo;0;R;;;;;N;;;;; 10A89;OLD NORTH ARABIAN LETTER TEH;Lo;0;R;;;;;N;;;;; 10A8A;OLD NORTH ARABIAN LETTER ES-1;Lo;0;R;;;;;N;;;;; 10A8B;OLD NORTH ARABIAN LETTER KAF;Lo;0;R;;;;;N;;;;; 10A8C;OLD NORTH ARABIAN LETTER NOON;Lo;0;R;;;;;N;;;;; 10A8D;OLD NORTH ARABIAN LETTER KHAH;Lo;0;R;;;;;N;;;;; 10A8E;OLD NORTH ARABIAN LETTER SAD;Lo;0;R;;;;;N;;;;; 10A8F;OLD NORTH ARABIAN LETTER ES-3;Lo;0;R;;;;;N;;;;; 10A90;OLD NORTH ARABIAN LETTER FEH;Lo;0;R;;;;;N;;;;; 10A91;OLD NORTH ARABIAN LETTER ALEF;Lo;0;R;;;;;N;;;;; 10A92;OLD NORTH ARABIAN LETTER AIN;Lo;0;R;;;;;N;;;;; 10A93;OLD NORTH ARABIAN LETTER DAD;Lo;0;R;;;;;N;;;;; 10A94;OLD NORTH ARABIAN LETTER GEEM;Lo;0;R;;;;;N;;;;; 10A95;OLD NORTH ARABIAN LETTER DAL;Lo;0;R;;;;;N;;;;; 10A96;OLD NORTH ARABIAN LETTER GHAIN;Lo;0;R;;;;;N;;;;; 10A97;OLD NORTH ARABIAN LETTER TAH;Lo;0;R;;;;;N;;;;; 10A98;OLD NORTH ARABIAN LETTER ZAIN;Lo;0;R;;;;;N;;;;; 10A99;OLD NORTH ARABIAN LETTER THAL;Lo;0;R;;;;;N;;;;; 10A9A;OLD NORTH ARABIAN LETTER YEH;Lo;0;R;;;;;N;;;;; 10A9B;OLD NORTH ARABIAN LETTER THEH;Lo;0;R;;;;;N;;;;; 10A9C;OLD NORTH ARABIAN LETTER ZAH;Lo;0;R;;;;;N;;;;; 10A9D;OLD NORTH ARABIAN NUMBER ONE;No;0;R;;;;1;N;;;;; 10A9E;OLD NORTH ARABIAN NUMBER TEN;No;0;R;;;;10;N;;;;; 10A9F;OLD NORTH ARABIAN NUMBER TWENTY;No;0;R;;;;20;N;;;;; 10AC0;MANICHAEAN LETTER ALEPH;Lo;0;R;;;;;N;;;;; 10AC1;MANICHAEAN LETTER BETH;Lo;0;R;;;;;N;;;;; 10AC2;MANICHAEAN LETTER BHETH;Lo;0;R;;;;;N;;;;; 10AC3;MANICHAEAN LETTER GIMEL;Lo;0;R;;;;;N;;;;; 10AC4;MANICHAEAN LETTER GHIMEL;Lo;0;R;;;;;N;;;;; 10AC5;MANICHAEAN LETTER DALETH;Lo;0;R;;;;;N;;;;; 10AC6;MANICHAEAN LETTER HE;Lo;0;R;;;;;N;;;;; 10AC7;MANICHAEAN LETTER WAW;Lo;0;R;;;;;N;;;;; 10AC8;MANICHAEAN SIGN UD;So;0;R;;;;;N;;;;; 10AC9;MANICHAEAN LETTER ZAYIN;Lo;0;R;;;;;N;;;;; 10ACA;MANICHAEAN LETTER ZHAYIN;Lo;0;R;;;;;N;;;;; 10ACB;MANICHAEAN LETTER JAYIN;Lo;0;R;;;;;N;;;;; 10ACC;MANICHAEAN LETTER JHAYIN;Lo;0;R;;;;;N;;;;; 10ACD;MANICHAEAN LETTER HETH;Lo;0;R;;;;;N;;;;; 10ACE;MANICHAEAN LETTER TETH;Lo;0;R;;;;;N;;;;; 10ACF;MANICHAEAN LETTER YODH;Lo;0;R;;;;;N;;;;; 10AD0;MANICHAEAN LETTER KAPH;Lo;0;R;;;;;N;;;;; 10AD1;MANICHAEAN LETTER XAPH;Lo;0;R;;;;;N;;;;; 10AD2;MANICHAEAN LETTER KHAPH;Lo;0;R;;;;;N;;;;; 10AD3;MANICHAEAN LETTER LAMEDH;Lo;0;R;;;;;N;;;;; 10AD4;MANICHAEAN LETTER DHAMEDH;Lo;0;R;;;;;N;;;;; 10AD5;MANICHAEAN LETTER THAMEDH;Lo;0;R;;;;;N;;;;; 10AD6;MANICHAEAN LETTER MEM;Lo;0;R;;;;;N;;;;; 10AD7;MANICHAEAN LETTER NUN;Lo;0;R;;;;;N;;;;; 10AD8;MANICHAEAN LETTER SAMEKH;Lo;0;R;;;;;N;;;;; 10AD9;MANICHAEAN LETTER AYIN;Lo;0;R;;;;;N;;;;; 10ADA;MANICHAEAN LETTER AAYIN;Lo;0;R;;;;;N;;;;; 10ADB;MANICHAEAN LETTER PE;Lo;0;R;;;;;N;;;;; 10ADC;MANICHAEAN LETTER FE;Lo;0;R;;;;;N;;;;; 10ADD;MANICHAEAN LETTER SADHE;Lo;0;R;;;;;N;;;;; 10ADE;MANICHAEAN LETTER QOPH;Lo;0;R;;;;;N;;;;; 10ADF;MANICHAEAN LETTER XOPH;Lo;0;R;;;;;N;;;;; 10AE0;MANICHAEAN LETTER QHOPH;Lo;0;R;;;;;N;;;;; 10AE1;MANICHAEAN LETTER RESH;Lo;0;R;;;;;N;;;;; 10AE2;MANICHAEAN LETTER SHIN;Lo;0;R;;;;;N;;;;; 10AE3;MANICHAEAN LETTER SSHIN;Lo;0;R;;;;;N;;;;; 10AE4;MANICHAEAN LETTER TAW;Lo;0;R;;;;;N;;;;; 10AE5;MANICHAEAN ABBREVIATION MARK ABOVE;Mn;230;NSM;;;;;N;;;;; 10AE6;MANICHAEAN ABBREVIATION MARK BELOW;Mn;220;NSM;;;;;N;;;;; 10AEB;MANICHAEAN NUMBER ONE;No;0;R;;;;1;N;;;;; 10AEC;MANICHAEAN NUMBER FIVE;No;0;R;;;;5;N;;;;; 10AED;MANICHAEAN NUMBER TEN;No;0;R;;;;10;N;;;;; 10AEE;MANICHAEAN NUMBER TWENTY;No;0;R;;;;20;N;;;;; 10AEF;MANICHAEAN NUMBER ONE HUNDRED;No;0;R;;;;100;N;;;;; 10AF0;MANICHAEAN PUNCTUATION STAR;Po;0;R;;;;;N;;;;; 10AF1;MANICHAEAN PUNCTUATION FLEURON;Po;0;R;;;;;N;;;;; 10AF2;MANICHAEAN PUNCTUATION DOUBLE DOT WITHIN DOT;Po;0;R;;;;;N;;;;; 10AF3;MANICHAEAN PUNCTUATION DOT WITHIN DOT;Po;0;R;;;;;N;;;;; 10AF4;MANICHAEAN PUNCTUATION DOT;Po;0;R;;;;;N;;;;; 10AF5;MANICHAEAN PUNCTUATION TWO DOTS;Po;0;R;;;;;N;;;;; 10AF6;MANICHAEAN PUNCTUATION LINE FILLER;Po;0;R;;;;;N;;;;; 10B00;AVESTAN LETTER A;Lo;0;R;;;;;N;;;;; 10B01;AVESTAN LETTER AA;Lo;0;R;;;;;N;;;;; 10B02;AVESTAN LETTER AO;Lo;0;R;;;;;N;;;;; 10B03;AVESTAN LETTER AAO;Lo;0;R;;;;;N;;;;; 10B04;AVESTAN LETTER AN;Lo;0;R;;;;;N;;;;; 10B05;AVESTAN LETTER AAN;Lo;0;R;;;;;N;;;;; 10B06;AVESTAN LETTER AE;Lo;0;R;;;;;N;;;;; 10B07;AVESTAN LETTER AEE;Lo;0;R;;;;;N;;;;; 10B08;AVESTAN LETTER E;Lo;0;R;;;;;N;;;;; 10B09;AVESTAN LETTER EE;Lo;0;R;;;;;N;;;;; 10B0A;AVESTAN LETTER O;Lo;0;R;;;;;N;;;;; 10B0B;AVESTAN LETTER OO;Lo;0;R;;;;;N;;;;; 10B0C;AVESTAN LETTER I;Lo;0;R;;;;;N;;;;; 10B0D;AVESTAN LETTER II;Lo;0;R;;;;;N;;;;; 10B0E;AVESTAN LETTER U;Lo;0;R;;;;;N;;;;; 10B0F;AVESTAN LETTER UU;Lo;0;R;;;;;N;;;;; 10B10;AVESTAN LETTER KE;Lo;0;R;;;;;N;;;;; 10B11;AVESTAN LETTER XE;Lo;0;R;;;;;N;;;;; 10B12;AVESTAN LETTER XYE;Lo;0;R;;;;;N;;;;; 10B13;AVESTAN LETTER XVE;Lo;0;R;;;;;N;;;;; 10B14;AVESTAN LETTER GE;Lo;0;R;;;;;N;;;;; 10B15;AVESTAN LETTER GGE;Lo;0;R;;;;;N;;;;; 10B16;AVESTAN LETTER GHE;Lo;0;R;;;;;N;;;;; 10B17;AVESTAN LETTER CE;Lo;0;R;;;;;N;;;;; 10B18;AVESTAN LETTER JE;Lo;0;R;;;;;N;;;;; 10B19;AVESTAN LETTER TE;Lo;0;R;;;;;N;;;;; 10B1A;AVESTAN LETTER THE;Lo;0;R;;;;;N;;;;; 10B1B;AVESTAN LETTER DE;Lo;0;R;;;;;N;;;;; 10B1C;AVESTAN LETTER DHE;Lo;0;R;;;;;N;;;;; 10B1D;AVESTAN LETTER TTE;Lo;0;R;;;;;N;;;;; 10B1E;AVESTAN LETTER PE;Lo;0;R;;;;;N;;;;; 10B1F;AVESTAN LETTER FE;Lo;0;R;;;;;N;;;;; 10B20;AVESTAN LETTER BE;Lo;0;R;;;;;N;;;;; 10B21;AVESTAN LETTER BHE;Lo;0;R;;;;;N;;;;; 10B22;AVESTAN LETTER NGE;Lo;0;R;;;;;N;;;;; 10B23;AVESTAN LETTER NGYE;Lo;0;R;;;;;N;;;;; 10B24;AVESTAN LETTER NGVE;Lo;0;R;;;;;N;;;;; 10B25;AVESTAN LETTER NE;Lo;0;R;;;;;N;;;;; 10B26;AVESTAN LETTER NYE;Lo;0;R;;;;;N;;;;; 10B27;AVESTAN LETTER NNE;Lo;0;R;;;;;N;;;;; 10B28;AVESTAN LETTER ME;Lo;0;R;;;;;N;;;;; 10B29;AVESTAN LETTER HME;Lo;0;R;;;;;N;;;;; 10B2A;AVESTAN LETTER YYE;Lo;0;R;;;;;N;;;;; 10B2B;AVESTAN LETTER YE;Lo;0;R;;;;;N;;;;; 10B2C;AVESTAN LETTER VE;Lo;0;R;;;;;N;;;;; 10B2D;AVESTAN LETTER RE;Lo;0;R;;;;;N;;;;; 10B2E;AVESTAN LETTER LE;Lo;0;R;;;;;N;;;;; 10B2F;AVESTAN LETTER SE;Lo;0;R;;;;;N;;;;; 10B30;AVESTAN LETTER ZE;Lo;0;R;;;;;N;;;;; 10B31;AVESTAN LETTER SHE;Lo;0;R;;;;;N;;;;; 10B32;AVESTAN LETTER ZHE;Lo;0;R;;;;;N;;;;; 10B33;AVESTAN LETTER SHYE;Lo;0;R;;;;;N;;;;; 10B34;AVESTAN LETTER SSHE;Lo;0;R;;;;;N;;;;; 10B35;AVESTAN LETTER HE;Lo;0;R;;;;;N;;;;; 10B39;AVESTAN ABBREVIATION MARK;Po;0;ON;;;;;N;;;;; 10B3A;TINY TWO DOTS OVER ONE DOT PUNCTUATION;Po;0;ON;;;;;N;;;;; 10B3B;SMALL TWO DOTS OVER ONE DOT PUNCTUATION;Po;0;ON;;;;;N;;;;; 10B3C;LARGE TWO DOTS OVER ONE DOT PUNCTUATION;Po;0;ON;;;;;N;;;;; 10B3D;LARGE ONE DOT OVER TWO DOTS PUNCTUATION;Po;0;ON;;;;;N;;;;; 10B3E;LARGE TWO RINGS OVER ONE RING PUNCTUATION;Po;0;ON;;;;;N;;;;; 10B3F;LARGE ONE RING OVER TWO RINGS PUNCTUATION;Po;0;ON;;;;;N;;;;; 10B40;INSCRIPTIONAL PARTHIAN LETTER ALEPH;Lo;0;R;;;;;N;;;;; 10B41;INSCRIPTIONAL PARTHIAN LETTER BETH;Lo;0;R;;;;;N;;;;; 10B42;INSCRIPTIONAL PARTHIAN LETTER GIMEL;Lo;0;R;;;;;N;;;;; 10B43;INSCRIPTIONAL PARTHIAN LETTER DALETH;Lo;0;R;;;;;N;;;;; 10B44;INSCRIPTIONAL PARTHIAN LETTER HE;Lo;0;R;;;;;N;;;;; 10B45;INSCRIPTIONAL PARTHIAN LETTER WAW;Lo;0;R;;;;;N;;;;; 10B46;INSCRIPTIONAL PARTHIAN LETTER ZAYIN;Lo;0;R;;;;;N;;;;; 10B47;INSCRIPTIONAL PARTHIAN LETTER HETH;Lo;0;R;;;;;N;;;;; 10B48;INSCRIPTIONAL PARTHIAN LETTER TETH;Lo;0;R;;;;;N;;;;; 10B49;INSCRIPTIONAL PARTHIAN LETTER YODH;Lo;0;R;;;;;N;;;;; 10B4A;INSCRIPTIONAL PARTHIAN LETTER KAPH;Lo;0;R;;;;;N;;;;; 10B4B;INSCRIPTIONAL PARTHIAN LETTER LAMEDH;Lo;0;R;;;;;N;;;;; 10B4C;INSCRIPTIONAL PARTHIAN LETTER MEM;Lo;0;R;;;;;N;;;;; 10B4D;INSCRIPTIONAL PARTHIAN LETTER NUN;Lo;0;R;;;;;N;;;;; 10B4E;INSCRIPTIONAL PARTHIAN LETTER SAMEKH;Lo;0;R;;;;;N;;;;; 10B4F;INSCRIPTIONAL PARTHIAN LETTER AYIN;Lo;0;R;;;;;N;;;;; 10B50;INSCRIPTIONAL PARTHIAN LETTER PE;Lo;0;R;;;;;N;;;;; 10B51;INSCRIPTIONAL PARTHIAN LETTER SADHE;Lo;0;R;;;;;N;;;;; 10B52;INSCRIPTIONAL PARTHIAN LETTER QOPH;Lo;0;R;;;;;N;;;;; 10B53;INSCRIPTIONAL PARTHIAN LETTER RESH;Lo;0;R;;;;;N;;;;; 10B54;INSCRIPTIONAL PARTHIAN LETTER SHIN;Lo;0;R;;;;;N;;;;; 10B55;INSCRIPTIONAL PARTHIAN LETTER TAW;Lo;0;R;;;;;N;;;;; 10B58;INSCRIPTIONAL PARTHIAN NUMBER ONE;No;0;R;;;;1;N;;;;; 10B59;INSCRIPTIONAL PARTHIAN NUMBER TWO;No;0;R;;;;2;N;;;;; 10B5A;INSCRIPTIONAL PARTHIAN NUMBER THREE;No;0;R;;;;3;N;;;;; 10B5B;INSCRIPTIONAL PARTHIAN NUMBER FOUR;No;0;R;;;;4;N;;;;; 10B5C;INSCRIPTIONAL PARTHIAN NUMBER TEN;No;0;R;;;;10;N;;;;; 10B5D;INSCRIPTIONAL PARTHIAN NUMBER TWENTY;No;0;R;;;;20;N;;;;; 10B5E;INSCRIPTIONAL PARTHIAN NUMBER ONE HUNDRED;No;0;R;;;;100;N;;;;; 10B5F;INSCRIPTIONAL PARTHIAN NUMBER ONE THOUSAND;No;0;R;;;;1000;N;;;;; 10B60;INSCRIPTIONAL PAHLAVI LETTER ALEPH;Lo;0;R;;;;;N;;;;; 10B61;INSCRIPTIONAL PAHLAVI LETTER BETH;Lo;0;R;;;;;N;;;;; 10B62;INSCRIPTIONAL PAHLAVI LETTER GIMEL;Lo;0;R;;;;;N;;;;; 10B63;INSCRIPTIONAL PAHLAVI LETTER DALETH;Lo;0;R;;;;;N;;;;; 10B64;INSCRIPTIONAL PAHLAVI LETTER HE;Lo;0;R;;;;;N;;;;; 10B65;INSCRIPTIONAL PAHLAVI LETTER WAW-AYIN-RESH;Lo;0;R;;;;;N;;;;; 10B66;INSCRIPTIONAL PAHLAVI LETTER ZAYIN;Lo;0;R;;;;;N;;;;; 10B67;INSCRIPTIONAL PAHLAVI LETTER HETH;Lo;0;R;;;;;N;;;;; 10B68;INSCRIPTIONAL PAHLAVI LETTER TETH;Lo;0;R;;;;;N;;;;; 10B69;INSCRIPTIONAL PAHLAVI LETTER YODH;Lo;0;R;;;;;N;;;;; 10B6A;INSCRIPTIONAL PAHLAVI LETTER KAPH;Lo;0;R;;;;;N;;;;; 10B6B;INSCRIPTIONAL PAHLAVI LETTER LAMEDH;Lo;0;R;;;;;N;;;;; 10B6C;INSCRIPTIONAL PAHLAVI LETTER MEM-QOPH;Lo;0;R;;;;;N;;;;; 10B6D;INSCRIPTIONAL PAHLAVI LETTER NUN;Lo;0;R;;;;;N;;;;; 10B6E;INSCRIPTIONAL PAHLAVI LETTER SAMEKH;Lo;0;R;;;;;N;;;;; 10B6F;INSCRIPTIONAL PAHLAVI LETTER PE;Lo;0;R;;;;;N;;;;; 10B70;INSCRIPTIONAL PAHLAVI LETTER SADHE;Lo;0;R;;;;;N;;;;; 10B71;INSCRIPTIONAL PAHLAVI LETTER SHIN;Lo;0;R;;;;;N;;;;; 10B72;INSCRIPTIONAL PAHLAVI LETTER TAW;Lo;0;R;;;;;N;;;;; 10B78;INSCRIPTIONAL PAHLAVI NUMBER ONE;No;0;R;;;;1;N;;;;; 10B79;INSCRIPTIONAL PAHLAVI NUMBER TWO;No;0;R;;;;2;N;;;;; 10B7A;INSCRIPTIONAL PAHLAVI NUMBER THREE;No;0;R;;;;3;N;;;;; 10B7B;INSCRIPTIONAL PAHLAVI NUMBER FOUR;No;0;R;;;;4;N;;;;; 10B7C;INSCRIPTIONAL PAHLAVI NUMBER TEN;No;0;R;;;;10;N;;;;; 10B7D;INSCRIPTIONAL PAHLAVI NUMBER TWENTY;No;0;R;;;;20;N;;;;; 10B7E;INSCRIPTIONAL PAHLAVI NUMBER ONE HUNDRED;No;0;R;;;;100;N;;;;; 10B7F;INSCRIPTIONAL PAHLAVI NUMBER ONE THOUSAND;No;0;R;;;;1000;N;;;;; 10B80;PSALTER PAHLAVI LETTER ALEPH;Lo;0;R;;;;;N;;;;; 10B81;PSALTER PAHLAVI LETTER BETH;Lo;0;R;;;;;N;;;;; 10B82;PSALTER PAHLAVI LETTER GIMEL;Lo;0;R;;;;;N;;;;; 10B83;PSALTER PAHLAVI LETTER DALETH;Lo;0;R;;;;;N;;;;; 10B84;PSALTER PAHLAVI LETTER HE;Lo;0;R;;;;;N;;;;; 10B85;PSALTER PAHLAVI LETTER WAW-AYIN-RESH;Lo;0;R;;;;;N;;;;; 10B86;PSALTER PAHLAVI LETTER ZAYIN;Lo;0;R;;;;;N;;;;; 10B87;PSALTER PAHLAVI LETTER HETH;Lo;0;R;;;;;N;;;;; 10B88;PSALTER PAHLAVI LETTER YODH;Lo;0;R;;;;;N;;;;; 10B89;PSALTER PAHLAVI LETTER KAPH;Lo;0;R;;;;;N;;;;; 10B8A;PSALTER PAHLAVI LETTER LAMEDH;Lo;0;R;;;;;N;;;;; 10B8B;PSALTER PAHLAVI LETTER MEM-QOPH;Lo;0;R;;;;;N;;;;; 10B8C;PSALTER PAHLAVI LETTER NUN;Lo;0;R;;;;;N;;;;; 10B8D;PSALTER PAHLAVI LETTER SAMEKH;Lo;0;R;;;;;N;;;;; 10B8E;PSALTER PAHLAVI LETTER PE;Lo;0;R;;;;;N;;;;; 10B8F;PSALTER PAHLAVI LETTER SADHE;Lo;0;R;;;;;N;;;;; 10B90;PSALTER PAHLAVI LETTER SHIN;Lo;0;R;;;;;N;;;;; 10B91;PSALTER PAHLAVI LETTER TAW;Lo;0;R;;;;;N;;;;; 10B99;PSALTER PAHLAVI SECTION MARK;Po;0;R;;;;;N;;;;; 10B9A;PSALTER PAHLAVI TURNED SECTION MARK;Po;0;R;;;;;N;;;;; 10B9B;PSALTER PAHLAVI FOUR DOTS WITH CROSS;Po;0;R;;;;;N;;;;; 10B9C;PSALTER PAHLAVI FOUR DOTS WITH DOT;Po;0;R;;;;;N;;;;; 10BA9;PSALTER PAHLAVI NUMBER ONE;No;0;R;;;;1;N;;;;; 10BAA;PSALTER PAHLAVI NUMBER TWO;No;0;R;;;;2;N;;;;; 10BAB;PSALTER PAHLAVI NUMBER THREE;No;0;R;;;;3;N;;;;; 10BAC;PSALTER PAHLAVI NUMBER FOUR;No;0;R;;;;4;N;;;;; 10BAD;PSALTER PAHLAVI NUMBER TEN;No;0;R;;;;10;N;;;;; 10BAE;PSALTER PAHLAVI NUMBER TWENTY;No;0;R;;;;20;N;;;;; 10BAF;PSALTER PAHLAVI NUMBER ONE HUNDRED;No;0;R;;;;100;N;;;;; 10C00;OLD TURKIC LETTER ORKHON A;Lo;0;R;;;;;N;;;;; 10C01;OLD TURKIC LETTER YENISEI A;Lo;0;R;;;;;N;;;;; 10C02;OLD TURKIC LETTER YENISEI AE;Lo;0;R;;;;;N;;;;; 10C03;OLD TURKIC LETTER ORKHON I;Lo;0;R;;;;;N;;;;; 10C04;OLD TURKIC LETTER YENISEI I;Lo;0;R;;;;;N;;;;; 10C05;OLD TURKIC LETTER YENISEI E;Lo;0;R;;;;;N;;;;; 10C06;OLD TURKIC LETTER ORKHON O;Lo;0;R;;;;;N;;;;; 10C07;OLD TURKIC LETTER ORKHON OE;Lo;0;R;;;;;N;;;;; 10C08;OLD TURKIC LETTER YENISEI OE;Lo;0;R;;;;;N;;;;; 10C09;OLD TURKIC LETTER ORKHON AB;Lo;0;R;;;;;N;;;;; 10C0A;OLD TURKIC LETTER YENISEI AB;Lo;0;R;;;;;N;;;;; 10C0B;OLD TURKIC LETTER ORKHON AEB;Lo;0;R;;;;;N;;;;; 10C0C;OLD TURKIC LETTER YENISEI AEB;Lo;0;R;;;;;N;;;;; 10C0D;OLD TURKIC LETTER ORKHON AG;Lo;0;R;;;;;N;;;;; 10C0E;OLD TURKIC LETTER YENISEI AG;Lo;0;R;;;;;N;;;;; 10C0F;OLD TURKIC LETTER ORKHON AEG;Lo;0;R;;;;;N;;;;; 10C10;OLD TURKIC LETTER YENISEI AEG;Lo;0;R;;;;;N;;;;; 10C11;OLD TURKIC LETTER ORKHON AD;Lo;0;R;;;;;N;;;;; 10C12;OLD TURKIC LETTER YENISEI AD;Lo;0;R;;;;;N;;;;; 10C13;OLD TURKIC LETTER ORKHON AED;Lo;0;R;;;;;N;;;;; 10C14;OLD TURKIC LETTER ORKHON EZ;Lo;0;R;;;;;N;;;;; 10C15;OLD TURKIC LETTER YENISEI EZ;Lo;0;R;;;;;N;;;;; 10C16;OLD TURKIC LETTER ORKHON AY;Lo;0;R;;;;;N;;;;; 10C17;OLD TURKIC LETTER YENISEI AY;Lo;0;R;;;;;N;;;;; 10C18;OLD TURKIC LETTER ORKHON AEY;Lo;0;R;;;;;N;;;;; 10C19;OLD TURKIC LETTER YENISEI AEY;Lo;0;R;;;;;N;;;;; 10C1A;OLD TURKIC LETTER ORKHON AEK;Lo;0;R;;;;;N;;;;; 10C1B;OLD TURKIC LETTER YENISEI AEK;Lo;0;R;;;;;N;;;;; 10C1C;OLD TURKIC LETTER ORKHON OEK;Lo;0;R;;;;;N;;;;; 10C1D;OLD TURKIC LETTER YENISEI OEK;Lo;0;R;;;;;N;;;;; 10C1E;OLD TURKIC LETTER ORKHON AL;Lo;0;R;;;;;N;;;;; 10C1F;OLD TURKIC LETTER YENISEI AL;Lo;0;R;;;;;N;;;;; 10C20;OLD TURKIC LETTER ORKHON AEL;Lo;0;R;;;;;N;;;;; 10C21;OLD TURKIC LETTER ORKHON ELT;Lo;0;R;;;;;N;;;;; 10C22;OLD TURKIC LETTER ORKHON EM;Lo;0;R;;;;;N;;;;; 10C23;OLD TURKIC LETTER ORKHON AN;Lo;0;R;;;;;N;;;;; 10C24;OLD TURKIC LETTER ORKHON AEN;Lo;0;R;;;;;N;;;;; 10C25;OLD TURKIC LETTER YENISEI AEN;Lo;0;R;;;;;N;;;;; 10C26;OLD TURKIC LETTER ORKHON ENT;Lo;0;R;;;;;N;;;;; 10C27;OLD TURKIC LETTER YENISEI ENT;Lo;0;R;;;;;N;;;;; 10C28;OLD TURKIC LETTER ORKHON ENC;Lo;0;R;;;;;N;;;;; 10C29;OLD TURKIC LETTER YENISEI ENC;Lo;0;R;;;;;N;;;;; 10C2A;OLD TURKIC LETTER ORKHON ENY;Lo;0;R;;;;;N;;;;; 10C2B;OLD TURKIC LETTER YENISEI ENY;Lo;0;R;;;;;N;;;;; 10C2C;OLD TURKIC LETTER YENISEI ANG;Lo;0;R;;;;;N;;;;; 10C2D;OLD TURKIC LETTER ORKHON ENG;Lo;0;R;;;;;N;;;;; 10C2E;OLD TURKIC LETTER YENISEI AENG;Lo;0;R;;;;;N;;;;; 10C2F;OLD TURKIC LETTER ORKHON EP;Lo;0;R;;;;;N;;;;; 10C30;OLD TURKIC LETTER ORKHON OP;Lo;0;R;;;;;N;;;;; 10C31;OLD TURKIC LETTER ORKHON IC;Lo;0;R;;;;;N;;;;; 10C32;OLD TURKIC LETTER ORKHON EC;Lo;0;R;;;;;N;;;;; 10C33;OLD TURKIC LETTER YENISEI EC;Lo;0;R;;;;;N;;;;; 10C34;OLD TURKIC LETTER ORKHON AQ;Lo;0;R;;;;;N;;;;; 10C35;OLD TURKIC LETTER YENISEI AQ;Lo;0;R;;;;;N;;;;; 10C36;OLD TURKIC LETTER ORKHON IQ;Lo;0;R;;;;;N;;;;; 10C37;OLD TURKIC LETTER YENISEI IQ;Lo;0;R;;;;;N;;;;; 10C38;OLD TURKIC LETTER ORKHON OQ;Lo;0;R;;;;;N;;;;; 10C39;OLD TURKIC LETTER YENISEI OQ;Lo;0;R;;;;;N;;;;; 10C3A;OLD TURKIC LETTER ORKHON AR;Lo;0;R;;;;;N;;;;; 10C3B;OLD TURKIC LETTER YENISEI AR;Lo;0;R;;;;;N;;;;; 10C3C;OLD TURKIC LETTER ORKHON AER;Lo;0;R;;;;;N;;;;; 10C3D;OLD TURKIC LETTER ORKHON AS;Lo;0;R;;;;;N;;;;; 10C3E;OLD TURKIC LETTER ORKHON AES;Lo;0;R;;;;;N;;;;; 10C3F;OLD TURKIC LETTER ORKHON ASH;Lo;0;R;;;;;N;;;;; 10C40;OLD TURKIC LETTER YENISEI ASH;Lo;0;R;;;;;N;;;;; 10C41;OLD TURKIC LETTER ORKHON ESH;Lo;0;R;;;;;N;;;;; 10C42;OLD TURKIC LETTER YENISEI ESH;Lo;0;R;;;;;N;;;;; 10C43;OLD TURKIC LETTER ORKHON AT;Lo;0;R;;;;;N;;;;; 10C44;OLD TURKIC LETTER YENISEI AT;Lo;0;R;;;;;N;;;;; 10C45;OLD TURKIC LETTER ORKHON AET;Lo;0;R;;;;;N;;;;; 10C46;OLD TURKIC LETTER YENISEI AET;Lo;0;R;;;;;N;;;;; 10C47;OLD TURKIC LETTER ORKHON OT;Lo;0;R;;;;;N;;;;; 10C48;OLD TURKIC LETTER ORKHON BASH;Lo;0;R;;;;;N;;;;; 10E60;RUMI DIGIT ONE;No;0;AN;;;1;1;N;;;;; 10E61;RUMI DIGIT TWO;No;0;AN;;;2;2;N;;;;; 10E62;RUMI DIGIT THREE;No;0;AN;;;3;3;N;;;;; 10E63;RUMI DIGIT FOUR;No;0;AN;;;4;4;N;;;;; 10E64;RUMI DIGIT FIVE;No;0;AN;;;5;5;N;;;;; 10E65;RUMI DIGIT SIX;No;0;AN;;;6;6;N;;;;; 10E66;RUMI DIGIT SEVEN;No;0;AN;;;7;7;N;;;;; 10E67;RUMI DIGIT EIGHT;No;0;AN;;;8;8;N;;;;; 10E68;RUMI DIGIT NINE;No;0;AN;;;9;9;N;;;;; 10E69;RUMI NUMBER TEN;No;0;AN;;;;10;N;;;;; 10E6A;RUMI NUMBER TWENTY;No;0;AN;;;;20;N;;;;; 10E6B;RUMI NUMBER THIRTY;No;0;AN;;;;30;N;;;;; 10E6C;RUMI NUMBER FORTY;No;0;AN;;;;40;N;;;;; 10E6D;RUMI NUMBER FIFTY;No;0;AN;;;;50;N;;;;; 10E6E;RUMI NUMBER SIXTY;No;0;AN;;;;60;N;;;;; 10E6F;RUMI NUMBER SEVENTY;No;0;AN;;;;70;N;;;;; 10E70;RUMI NUMBER EIGHTY;No;0;AN;;;;80;N;;;;; 10E71;RUMI NUMBER NINETY;No;0;AN;;;;90;N;;;;; 10E72;RUMI NUMBER ONE HUNDRED;No;0;AN;;;;100;N;;;;; 10E73;RUMI NUMBER TWO HUNDRED;No;0;AN;;;;200;N;;;;; 10E74;RUMI NUMBER THREE HUNDRED;No;0;AN;;;;300;N;;;;; 10E75;RUMI NUMBER FOUR HUNDRED;No;0;AN;;;;400;N;;;;; 10E76;RUMI NUMBER FIVE HUNDRED;No;0;AN;;;;500;N;;;;; 10E77;RUMI NUMBER SIX HUNDRED;No;0;AN;;;;600;N;;;;; 10E78;RUMI NUMBER SEVEN HUNDRED;No;0;AN;;;;700;N;;;;; 10E79;RUMI NUMBER EIGHT HUNDRED;No;0;AN;;;;800;N;;;;; 10E7A;RUMI NUMBER NINE HUNDRED;No;0;AN;;;;900;N;;;;; 10E7B;RUMI FRACTION ONE HALF;No;0;AN;;;;1/2;N;;;;; 10E7C;RUMI FRACTION ONE QUARTER;No;0;AN;;;;1/4;N;;;;; 10E7D;RUMI FRACTION ONE THIRD;No;0;AN;;;;1/3;N;;;;; 10E7E;RUMI FRACTION TWO THIRDS;No;0;AN;;;;2/3;N;;;;; 11000;BRAHMI SIGN CANDRABINDU;Mc;0;L;;;;;N;;;;; 11001;BRAHMI SIGN ANUSVARA;Mn;0;NSM;;;;;N;;;;; 11002;BRAHMI SIGN VISARGA;Mc;0;L;;;;;N;;;;; 11003;BRAHMI SIGN JIHVAMULIYA;Lo;0;L;;;;;N;;;;; 11004;BRAHMI SIGN UPADHMANIYA;Lo;0;L;;;;;N;;;;; 11005;BRAHMI LETTER A;Lo;0;L;;;;;N;;;;; 11006;BRAHMI LETTER AA;Lo;0;L;;;;;N;;;;; 11007;BRAHMI LETTER I;Lo;0;L;;;;;N;;;;; 11008;BRAHMI LETTER II;Lo;0;L;;;;;N;;;;; 11009;BRAHMI LETTER U;Lo;0;L;;;;;N;;;;; 1100A;BRAHMI LETTER UU;Lo;0;L;;;;;N;;;;; 1100B;BRAHMI LETTER VOCALIC R;Lo;0;L;;;;;N;;;;; 1100C;BRAHMI LETTER VOCALIC RR;Lo;0;L;;;;;N;;;;; 1100D;BRAHMI LETTER VOCALIC L;Lo;0;L;;;;;N;;;;; 1100E;BRAHMI LETTER VOCALIC LL;Lo;0;L;;;;;N;;;;; 1100F;BRAHMI LETTER E;Lo;0;L;;;;;N;;;;; 11010;BRAHMI LETTER AI;Lo;0;L;;;;;N;;;;; 11011;BRAHMI LETTER O;Lo;0;L;;;;;N;;;;; 11012;BRAHMI LETTER AU;Lo;0;L;;;;;N;;;;; 11013;BRAHMI LETTER KA;Lo;0;L;;;;;N;;;;; 11014;BRAHMI LETTER KHA;Lo;0;L;;;;;N;;;;; 11015;BRAHMI LETTER GA;Lo;0;L;;;;;N;;;;; 11016;BRAHMI LETTER GHA;Lo;0;L;;;;;N;;;;; 11017;BRAHMI LETTER NGA;Lo;0;L;;;;;N;;;;; 11018;BRAHMI LETTER CA;Lo;0;L;;;;;N;;;;; 11019;BRAHMI LETTER CHA;Lo;0;L;;;;;N;;;;; 1101A;BRAHMI LETTER JA;Lo;0;L;;;;;N;;;;; 1101B;BRAHMI LETTER JHA;Lo;0;L;;;;;N;;;;; 1101C;BRAHMI LETTER NYA;Lo;0;L;;;;;N;;;;; 1101D;BRAHMI LETTER TTA;Lo;0;L;;;;;N;;;;; 1101E;BRAHMI LETTER TTHA;Lo;0;L;;;;;N;;;;; 1101F;BRAHMI LETTER DDA;Lo;0;L;;;;;N;;;;; 11020;BRAHMI LETTER DDHA;Lo;0;L;;;;;N;;;;; 11021;BRAHMI LETTER NNA;Lo;0;L;;;;;N;;;;; 11022;BRAHMI LETTER TA;Lo;0;L;;;;;N;;;;; 11023;BRAHMI LETTER THA;Lo;0;L;;;;;N;;;;; 11024;BRAHMI LETTER DA;Lo;0;L;;;;;N;;;;; 11025;BRAHMI LETTER DHA;Lo;0;L;;;;;N;;;;; 11026;BRAHMI LETTER NA;Lo;0;L;;;;;N;;;;; 11027;BRAHMI LETTER PA;Lo;0;L;;;;;N;;;;; 11028;BRAHMI LETTER PHA;Lo;0;L;;;;;N;;;;; 11029;BRAHMI LETTER BA;Lo;0;L;;;;;N;;;;; 1102A;BRAHMI LETTER BHA;Lo;0;L;;;;;N;;;;; 1102B;BRAHMI LETTER MA;Lo;0;L;;;;;N;;;;; 1102C;BRAHMI LETTER YA;Lo;0;L;;;;;N;;;;; 1102D;BRAHMI LETTER RA;Lo;0;L;;;;;N;;;;; 1102E;BRAHMI LETTER LA;Lo;0;L;;;;;N;;;;; 1102F;BRAHMI LETTER VA;Lo;0;L;;;;;N;;;;; 11030;BRAHMI LETTER SHA;Lo;0;L;;;;;N;;;;; 11031;BRAHMI LETTER SSA;Lo;0;L;;;;;N;;;;; 11032;BRAHMI LETTER SA;Lo;0;L;;;;;N;;;;; 11033;BRAHMI LETTER HA;Lo;0;L;;;;;N;;;;; 11034;BRAHMI LETTER LLA;Lo;0;L;;;;;N;;;;; 11035;BRAHMI LETTER OLD TAMIL LLLA;Lo;0;L;;;;;N;;;;; 11036;BRAHMI LETTER OLD TAMIL RRA;Lo;0;L;;;;;N;;;;; 11037;BRAHMI LETTER OLD TAMIL NNNA;Lo;0;L;;;;;N;;;;; 11038;BRAHMI VOWEL SIGN AA;Mn;0;NSM;;;;;N;;;;; 11039;BRAHMI VOWEL SIGN BHATTIPROLU AA;Mn;0;NSM;;;;;N;;;;; 1103A;BRAHMI VOWEL SIGN I;Mn;0;NSM;;;;;N;;;;; 1103B;BRAHMI VOWEL SIGN II;Mn;0;NSM;;;;;N;;;;; 1103C;BRAHMI VOWEL SIGN U;Mn;0;NSM;;;;;N;;;;; 1103D;BRAHMI VOWEL SIGN UU;Mn;0;NSM;;;;;N;;;;; 1103E;BRAHMI VOWEL SIGN VOCALIC R;Mn;0;NSM;;;;;N;;;;; 1103F;BRAHMI VOWEL SIGN VOCALIC RR;Mn;0;NSM;;;;;N;;;;; 11040;BRAHMI VOWEL SIGN VOCALIC L;Mn;0;NSM;;;;;N;;;;; 11041;BRAHMI VOWEL SIGN VOCALIC LL;Mn;0;NSM;;;;;N;;;;; 11042;BRAHMI VOWEL SIGN E;Mn;0;NSM;;;;;N;;;;; 11043;BRAHMI VOWEL SIGN AI;Mn;0;NSM;;;;;N;;;;; 11044;BRAHMI VOWEL SIGN O;Mn;0;NSM;;;;;N;;;;; 11045;BRAHMI VOWEL SIGN AU;Mn;0;NSM;;;;;N;;;;; 11046;BRAHMI VIRAMA;Mn;9;NSM;;;;;N;;;;; 11047;BRAHMI DANDA;Po;0;L;;;;;N;;;;; 11048;BRAHMI DOUBLE DANDA;Po;0;L;;;;;N;;;;; 11049;BRAHMI PUNCTUATION DOT;Po;0;L;;;;;N;;;;; 1104A;BRAHMI PUNCTUATION DOUBLE DOT;Po;0;L;;;;;N;;;;; 1104B;BRAHMI PUNCTUATION LINE;Po;0;L;;;;;N;;;;; 1104C;BRAHMI PUNCTUATION CRESCENT BAR;Po;0;L;;;;;N;;;;; 1104D;BRAHMI PUNCTUATION LOTUS;Po;0;L;;;;;N;;;;; 11052;BRAHMI NUMBER ONE;No;0;ON;;;1;1;N;;;;; 11053;BRAHMI NUMBER TWO;No;0;ON;;;2;2;N;;;;; 11054;BRAHMI NUMBER THREE;No;0;ON;;;3;3;N;;;;; 11055;BRAHMI NUMBER FOUR;No;0;ON;;;4;4;N;;;;; 11056;BRAHMI NUMBER FIVE;No;0;ON;;;5;5;N;;;;; 11057;BRAHMI NUMBER SIX;No;0;ON;;;6;6;N;;;;; 11058;BRAHMI NUMBER SEVEN;No;0;ON;;;7;7;N;;;;; 11059;BRAHMI NUMBER EIGHT;No;0;ON;;;8;8;N;;;;; 1105A;BRAHMI NUMBER NINE;No;0;ON;;;9;9;N;;;;; 1105B;BRAHMI NUMBER TEN;No;0;ON;;;;10;N;;;;; 1105C;BRAHMI NUMBER TWENTY;No;0;ON;;;;20;N;;;;; 1105D;BRAHMI NUMBER THIRTY;No;0;ON;;;;30;N;;;;; 1105E;BRAHMI NUMBER FORTY;No;0;ON;;;;40;N;;;;; 1105F;BRAHMI NUMBER FIFTY;No;0;ON;;;;50;N;;;;; 11060;BRAHMI NUMBER SIXTY;No;0;ON;;;;60;N;;;;; 11061;BRAHMI NUMBER SEVENTY;No;0;ON;;;;70;N;;;;; 11062;BRAHMI NUMBER EIGHTY;No;0;ON;;;;80;N;;;;; 11063;BRAHMI NUMBER NINETY;No;0;ON;;;;90;N;;;;; 11064;BRAHMI NUMBER ONE HUNDRED;No;0;ON;;;;100;N;;;;; 11065;BRAHMI NUMBER ONE THOUSAND;No;0;ON;;;;1000;N;;;;; 11066;BRAHMI DIGIT ZERO;Nd;0;L;;0;0;0;N;;;;; 11067;BRAHMI DIGIT ONE;Nd;0;L;;1;1;1;N;;;;; 11068;BRAHMI DIGIT TWO;Nd;0;L;;2;2;2;N;;;;; 11069;BRAHMI DIGIT THREE;Nd;0;L;;3;3;3;N;;;;; 1106A;BRAHMI DIGIT FOUR;Nd;0;L;;4;4;4;N;;;;; 1106B;BRAHMI DIGIT FIVE;Nd;0;L;;5;5;5;N;;;;; 1106C;BRAHMI DIGIT SIX;Nd;0;L;;6;6;6;N;;;;; 1106D;BRAHMI DIGIT SEVEN;Nd;0;L;;7;7;7;N;;;;; 1106E;BRAHMI DIGIT EIGHT;Nd;0;L;;8;8;8;N;;;;; 1106F;BRAHMI DIGIT NINE;Nd;0;L;;9;9;9;N;;;;; 1107F;BRAHMI NUMBER JOINER;Mn;9;NSM;;;;;N;;;;; 11080;KAITHI SIGN CANDRABINDU;Mn;0;NSM;;;;;N;;;;; 11081;KAITHI SIGN ANUSVARA;Mn;0;NSM;;;;;N;;;;; 11082;KAITHI SIGN VISARGA;Mc;0;L;;;;;N;;;;; 11083;KAITHI LETTER A;Lo;0;L;;;;;N;;;;; 11084;KAITHI LETTER AA;Lo;0;L;;;;;N;;;;; 11085;KAITHI LETTER I;Lo;0;L;;;;;N;;;;; 11086;KAITHI LETTER II;Lo;0;L;;;;;N;;;;; 11087;KAITHI LETTER U;Lo;0;L;;;;;N;;;;; 11088;KAITHI LETTER UU;Lo;0;L;;;;;N;;;;; 11089;KAITHI LETTER E;Lo;0;L;;;;;N;;;;; 1108A;KAITHI LETTER AI;Lo;0;L;;;;;N;;;;; 1108B;KAITHI LETTER O;Lo;0;L;;;;;N;;;;; 1108C;KAITHI LETTER AU;Lo;0;L;;;;;N;;;;; 1108D;KAITHI LETTER KA;Lo;0;L;;;;;N;;;;; 1108E;KAITHI LETTER KHA;Lo;0;L;;;;;N;;;;; 1108F;KAITHI LETTER GA;Lo;0;L;;;;;N;;;;; 11090;KAITHI LETTER GHA;Lo;0;L;;;;;N;;;;; 11091;KAITHI LETTER NGA;Lo;0;L;;;;;N;;;;; 11092;KAITHI LETTER CA;Lo;0;L;;;;;N;;;;; 11093;KAITHI LETTER CHA;Lo;0;L;;;;;N;;;;; 11094;KAITHI LETTER JA;Lo;0;L;;;;;N;;;;; 11095;KAITHI LETTER JHA;Lo;0;L;;;;;N;;;;; 11096;KAITHI LETTER NYA;Lo;0;L;;;;;N;;;;; 11097;KAITHI LETTER TTA;Lo;0;L;;;;;N;;;;; 11098;KAITHI LETTER TTHA;Lo;0;L;;;;;N;;;;; 11099;KAITHI LETTER DDA;Lo;0;L;;;;;N;;;;; 1109A;KAITHI LETTER DDDHA;Lo;0;L;11099 110BA;;;;N;;;;; 1109B;KAITHI LETTER DDHA;Lo;0;L;;;;;N;;;;; 1109C;KAITHI LETTER RHA;Lo;0;L;1109B 110BA;;;;N;;;;; 1109D;KAITHI LETTER NNA;Lo;0;L;;;;;N;;;;; 1109E;KAITHI LETTER TA;Lo;0;L;;;;;N;;;;; 1109F;KAITHI LETTER THA;Lo;0;L;;;;;N;;;;; 110A0;KAITHI LETTER DA;Lo;0;L;;;;;N;;;;; 110A1;KAITHI LETTER DHA;Lo;0;L;;;;;N;;;;; 110A2;KAITHI LETTER NA;Lo;0;L;;;;;N;;;;; 110A3;KAITHI LETTER PA;Lo;0;L;;;;;N;;;;; 110A4;KAITHI LETTER PHA;Lo;0;L;;;;;N;;;;; 110A5;KAITHI LETTER BA;Lo;0;L;;;;;N;;;;; 110A6;KAITHI LETTER BHA;Lo;0;L;;;;;N;;;;; 110A7;KAITHI LETTER MA;Lo;0;L;;;;;N;;;;; 110A8;KAITHI LETTER YA;Lo;0;L;;;;;N;;;;; 110A9;KAITHI LETTER RA;Lo;0;L;;;;;N;;;;; 110AA;KAITHI LETTER LA;Lo;0;L;;;;;N;;;;; 110AB;KAITHI LETTER VA;Lo;0;L;110A5 110BA;;;;N;;;;; 110AC;KAITHI LETTER SHA;Lo;0;L;;;;;N;;;;; 110AD;KAITHI LETTER SSA;Lo;0;L;;;;;N;;;;; 110AE;KAITHI LETTER SA;Lo;0;L;;;;;N;;;;; 110AF;KAITHI LETTER HA;Lo;0;L;;;;;N;;;;; 110B0;KAITHI VOWEL SIGN AA;Mc;0;L;;;;;N;;;;; 110B1;KAITHI VOWEL SIGN I;Mc;0;L;;;;;N;;;;; 110B2;KAITHI VOWEL SIGN II;Mc;0;L;;;;;N;;;;; 110B3;KAITHI VOWEL SIGN U;Mn;0;NSM;;;;;N;;;;; 110B4;KAITHI VOWEL SIGN UU;Mn;0;NSM;;;;;N;;;;; 110B5;KAITHI VOWEL SIGN E;Mn;0;NSM;;;;;N;;;;; 110B6;KAITHI VOWEL SIGN AI;Mn;0;NSM;;;;;N;;;;; 110B7;KAITHI VOWEL SIGN O;Mc;0;L;;;;;N;;;;; 110B8;KAITHI VOWEL SIGN AU;Mc;0;L;;;;;N;;;;; 110B9;KAITHI SIGN VIRAMA;Mn;9;NSM;;;;;N;;;;; 110BA;KAITHI SIGN NUKTA;Mn;7;NSM;;;;;N;;;;; 110BB;KAITHI ABBREVIATION SIGN;Po;0;L;;;;;N;;;;; 110BC;KAITHI ENUMERATION SIGN;Po;0;L;;;;;N;;;;; 110BD;KAITHI NUMBER SIGN;Cf;0;L;;;;;N;;;;; 110BE;KAITHI SECTION MARK;Po;0;L;;;;;N;;;;; 110BF;KAITHI DOUBLE SECTION MARK;Po;0;L;;;;;N;;;;; 110C0;KAITHI DANDA;Po;0;L;;;;;N;;;;; 110C1;KAITHI DOUBLE DANDA;Po;0;L;;;;;N;;;;; 110D0;SORA SOMPENG LETTER SAH;Lo;0;L;;;;;N;;;;; 110D1;SORA SOMPENG LETTER TAH;Lo;0;L;;;;;N;;;;; 110D2;SORA SOMPENG LETTER BAH;Lo;0;L;;;;;N;;;;; 110D3;SORA SOMPENG LETTER CAH;Lo;0;L;;;;;N;;;;; 110D4;SORA SOMPENG LETTER DAH;Lo;0;L;;;;;N;;;;; 110D5;SORA SOMPENG LETTER GAH;Lo;0;L;;;;;N;;;;; 110D6;SORA SOMPENG LETTER MAH;Lo;0;L;;;;;N;;;;; 110D7;SORA SOMPENG LETTER NGAH;Lo;0;L;;;;;N;;;;; 110D8;SORA SOMPENG LETTER LAH;Lo;0;L;;;;;N;;;;; 110D9;SORA SOMPENG LETTER NAH;Lo;0;L;;;;;N;;;;; 110DA;SORA SOMPENG LETTER VAH;Lo;0;L;;;;;N;;;;; 110DB;SORA SOMPENG LETTER PAH;Lo;0;L;;;;;N;;;;; 110DC;SORA SOMPENG LETTER YAH;Lo;0;L;;;;;N;;;;; 110DD;SORA SOMPENG LETTER RAH;Lo;0;L;;;;;N;;;;; 110DE;SORA SOMPENG LETTER HAH;Lo;0;L;;;;;N;;;;; 110DF;SORA SOMPENG LETTER KAH;Lo;0;L;;;;;N;;;;; 110E0;SORA SOMPENG LETTER JAH;Lo;0;L;;;;;N;;;;; 110E1;SORA SOMPENG LETTER NYAH;Lo;0;L;;;;;N;;;;; 110E2;SORA SOMPENG LETTER AH;Lo;0;L;;;;;N;;;;; 110E3;SORA SOMPENG LETTER EEH;Lo;0;L;;;;;N;;;;; 110E4;SORA SOMPENG LETTER IH;Lo;0;L;;;;;N;;;;; 110E5;SORA SOMPENG LETTER UH;Lo;0;L;;;;;N;;;;; 110E6;SORA SOMPENG LETTER OH;Lo;0;L;;;;;N;;;;; 110E7;SORA SOMPENG LETTER EH;Lo;0;L;;;;;N;;;;; 110E8;SORA SOMPENG LETTER MAE;Lo;0;L;;;;;N;;;;; 110F0;SORA SOMPENG DIGIT ZERO;Nd;0;L;;0;0;0;N;;;;; 110F1;SORA SOMPENG DIGIT ONE;Nd;0;L;;1;1;1;N;;;;; 110F2;SORA SOMPENG DIGIT TWO;Nd;0;L;;2;2;2;N;;;;; 110F3;SORA SOMPENG DIGIT THREE;Nd;0;L;;3;3;3;N;;;;; 110F4;SORA SOMPENG DIGIT FOUR;Nd;0;L;;4;4;4;N;;;;; 110F5;SORA SOMPENG DIGIT FIVE;Nd;0;L;;5;5;5;N;;;;; 110F6;SORA SOMPENG DIGIT SIX;Nd;0;L;;6;6;6;N;;;;; 110F7;SORA SOMPENG DIGIT SEVEN;Nd;0;L;;7;7;7;N;;;;; 110F8;SORA SOMPENG DIGIT EIGHT;Nd;0;L;;8;8;8;N;;;;; 110F9;SORA SOMPENG DIGIT NINE;Nd;0;L;;9;9;9;N;;;;; 11100;CHAKMA SIGN CANDRABINDU;Mn;230;NSM;;;;;N;;;;; 11101;CHAKMA SIGN ANUSVARA;Mn;230;NSM;;;;;N;;;;; 11102;CHAKMA SIGN VISARGA;Mn;230;NSM;;;;;N;;;;; 11103;CHAKMA LETTER AA;Lo;0;L;;;;;N;;;;; 11104;CHAKMA LETTER I;Lo;0;L;;;;;N;;;;; 11105;CHAKMA LETTER U;Lo;0;L;;;;;N;;;;; 11106;CHAKMA LETTER E;Lo;0;L;;;;;N;;;;; 11107;CHAKMA LETTER KAA;Lo;0;L;;;;;N;;;;; 11108;CHAKMA LETTER KHAA;Lo;0;L;;;;;N;;;;; 11109;CHAKMA LETTER GAA;Lo;0;L;;;;;N;;;;; 1110A;CHAKMA LETTER GHAA;Lo;0;L;;;;;N;;;;; 1110B;CHAKMA LETTER NGAA;Lo;0;L;;;;;N;;;;; 1110C;CHAKMA LETTER CAA;Lo;0;L;;;;;N;;;;; 1110D;CHAKMA LETTER CHAA;Lo;0;L;;;;;N;;;;; 1110E;CHAKMA LETTER JAA;Lo;0;L;;;;;N;;;;; 1110F;CHAKMA LETTER JHAA;Lo;0;L;;;;;N;;;;; 11110;CHAKMA LETTER NYAA;Lo;0;L;;;;;N;;;;; 11111;CHAKMA LETTER TTAA;Lo;0;L;;;;;N;;;;; 11112;CHAKMA LETTER TTHAA;Lo;0;L;;;;;N;;;;; 11113;CHAKMA LETTER DDAA;Lo;0;L;;;;;N;;;;; 11114;CHAKMA LETTER DDHAA;Lo;0;L;;;;;N;;;;; 11115;CHAKMA LETTER NNAA;Lo;0;L;;;;;N;;;;; 11116;CHAKMA LETTER TAA;Lo;0;L;;;;;N;;;;; 11117;CHAKMA LETTER THAA;Lo;0;L;;;;;N;;;;; 11118;CHAKMA LETTER DAA;Lo;0;L;;;;;N;;;;; 11119;CHAKMA LETTER DHAA;Lo;0;L;;;;;N;;;;; 1111A;CHAKMA LETTER NAA;Lo;0;L;;;;;N;;;;; 1111B;CHAKMA LETTER PAA;Lo;0;L;;;;;N;;;;; 1111C;CHAKMA LETTER PHAA;Lo;0;L;;;;;N;;;;; 1111D;CHAKMA LETTER BAA;Lo;0;L;;;;;N;;;;; 1111E;CHAKMA LETTER BHAA;Lo;0;L;;;;;N;;;;; 1111F;CHAKMA LETTER MAA;Lo;0;L;;;;;N;;;;; 11120;CHAKMA LETTER YYAA;Lo;0;L;;;;;N;;;;; 11121;CHAKMA LETTER YAA;Lo;0;L;;;;;N;;;;; 11122;CHAKMA LETTER RAA;Lo;0;L;;;;;N;;;;; 11123;CHAKMA LETTER LAA;Lo;0;L;;;;;N;;;;; 11124;CHAKMA LETTER WAA;Lo;0;L;;;;;N;;;;; 11125;CHAKMA LETTER SAA;Lo;0;L;;;;;N;;;;; 11126;CHAKMA LETTER HAA;Lo;0;L;;;;;N;;;;; 11127;CHAKMA VOWEL SIGN A;Mn;0;NSM;;;;;N;;;;; 11128;CHAKMA VOWEL SIGN I;Mn;0;NSM;;;;;N;;;;; 11129;CHAKMA VOWEL SIGN II;Mn;0;NSM;;;;;N;;;;; 1112A;CHAKMA VOWEL SIGN U;Mn;0;NSM;;;;;N;;;;; 1112B;CHAKMA VOWEL SIGN UU;Mn;0;NSM;;;;;N;;;;; 1112C;CHAKMA VOWEL SIGN E;Mc;0;L;;;;;N;;;;; 1112D;CHAKMA VOWEL SIGN AI;Mn;0;NSM;;;;;N;;;;; 1112E;CHAKMA VOWEL SIGN O;Mn;0;NSM;11131 11127;;;;N;;;;; 1112F;CHAKMA VOWEL SIGN AU;Mn;0;NSM;11132 11127;;;;N;;;;; 11130;CHAKMA VOWEL SIGN OI;Mn;0;NSM;;;;;N;;;;; 11131;CHAKMA O MARK;Mn;0;NSM;;;;;N;;;;; 11132;CHAKMA AU MARK;Mn;0;NSM;;;;;N;;;;; 11133;CHAKMA VIRAMA;Mn;9;NSM;;;;;N;;;;; 11134;CHAKMA MAAYYAA;Mn;9;NSM;;;;;N;;;;; 11136;CHAKMA DIGIT ZERO;Nd;0;L;;0;0;0;N;;;;; 11137;CHAKMA DIGIT ONE;Nd;0;L;;1;1;1;N;;;;; 11138;CHAKMA DIGIT TWO;Nd;0;L;;2;2;2;N;;;;; 11139;CHAKMA DIGIT THREE;Nd;0;L;;3;3;3;N;;;;; 1113A;CHAKMA DIGIT FOUR;Nd;0;L;;4;4;4;N;;;;; 1113B;CHAKMA DIGIT FIVE;Nd;0;L;;5;5;5;N;;;;; 1113C;CHAKMA DIGIT SIX;Nd;0;L;;6;6;6;N;;;;; 1113D;CHAKMA DIGIT SEVEN;Nd;0;L;;7;7;7;N;;;;; 1113E;CHAKMA DIGIT EIGHT;Nd;0;L;;8;8;8;N;;;;; 1113F;CHAKMA DIGIT NINE;Nd;0;L;;9;9;9;N;;;;; 11140;CHAKMA SECTION MARK;Po;0;L;;;;;N;;;;; 11141;CHAKMA DANDA;Po;0;L;;;;;N;;;;; 11142;CHAKMA DOUBLE DANDA;Po;0;L;;;;;N;;;;; 11143;CHAKMA QUESTION MARK;Po;0;L;;;;;N;;;;; 11150;MAHAJANI LETTER A;Lo;0;L;;;;;N;;;;; 11151;MAHAJANI LETTER I;Lo;0;L;;;;;N;;;;; 11152;MAHAJANI LETTER U;Lo;0;L;;;;;N;;;;; 11153;MAHAJANI LETTER E;Lo;0;L;;;;;N;;;;; 11154;MAHAJANI LETTER O;Lo;0;L;;;;;N;;;;; 11155;MAHAJANI LETTER KA;Lo;0;L;;;;;N;;;;; 11156;MAHAJANI LETTER KHA;Lo;0;L;;;;;N;;;;; 11157;MAHAJANI LETTER GA;Lo;0;L;;;;;N;;;;; 11158;MAHAJANI LETTER GHA;Lo;0;L;;;;;N;;;;; 11159;MAHAJANI LETTER CA;Lo;0;L;;;;;N;;;;; 1115A;MAHAJANI LETTER CHA;Lo;0;L;;;;;N;;;;; 1115B;MAHAJANI LETTER JA;Lo;0;L;;;;;N;;;;; 1115C;MAHAJANI LETTER JHA;Lo;0;L;;;;;N;;;;; 1115D;MAHAJANI LETTER NYA;Lo;0;L;;;;;N;;;;; 1115E;MAHAJANI LETTER TTA;Lo;0;L;;;;;N;;;;; 1115F;MAHAJANI LETTER TTHA;Lo;0;L;;;;;N;;;;; 11160;MAHAJANI LETTER DDA;Lo;0;L;;;;;N;;;;; 11161;MAHAJANI LETTER DDHA;Lo;0;L;;;;;N;;;;; 11162;MAHAJANI LETTER NNA;Lo;0;L;;;;;N;;;;; 11163;MAHAJANI LETTER TA;Lo;0;L;;;;;N;;;;; 11164;MAHAJANI LETTER THA;Lo;0;L;;;;;N;;;;; 11165;MAHAJANI LETTER DA;Lo;0;L;;;;;N;;;;; 11166;MAHAJANI LETTER DHA;Lo;0;L;;;;;N;;;;; 11167;MAHAJANI LETTER NA;Lo;0;L;;;;;N;;;;; 11168;MAHAJANI LETTER PA;Lo;0;L;;;;;N;;;;; 11169;MAHAJANI LETTER PHA;Lo;0;L;;;;;N;;;;; 1116A;MAHAJANI LETTER BA;Lo;0;L;;;;;N;;;;; 1116B;MAHAJANI LETTER BHA;Lo;0;L;;;;;N;;;;; 1116C;MAHAJANI LETTER MA;Lo;0;L;;;;;N;;;;; 1116D;MAHAJANI LETTER RA;Lo;0;L;;;;;N;;;;; 1116E;MAHAJANI LETTER LA;Lo;0;L;;;;;N;;;;; 1116F;MAHAJANI LETTER VA;Lo;0;L;;;;;N;;;;; 11170;MAHAJANI LETTER SA;Lo;0;L;;;;;N;;;;; 11171;MAHAJANI LETTER HA;Lo;0;L;;;;;N;;;;; 11172;MAHAJANI LETTER RRA;Lo;0;L;;;;;N;;;;; 11173;MAHAJANI SIGN NUKTA;Mn;7;NSM;;;;;N;;;;; 11174;MAHAJANI ABBREVIATION SIGN;Po;0;L;;;;;N;;;;; 11175;MAHAJANI SECTION MARK;Po;0;L;;;;;N;;;;; 11176;MAHAJANI LIGATURE SHRI;Lo;0;L;;;;;N;;;;; 11180;SHARADA SIGN CANDRABINDU;Mn;0;NSM;;;;;N;;;;; 11181;SHARADA SIGN ANUSVARA;Mn;0;NSM;;;;;N;;;;; 11182;SHARADA SIGN VISARGA;Mc;0;L;;;;;N;;;;; 11183;SHARADA LETTER A;Lo;0;L;;;;;N;;;;; 11184;SHARADA LETTER AA;Lo;0;L;;;;;N;;;;; 11185;SHARADA LETTER I;Lo;0;L;;;;;N;;;;; 11186;SHARADA LETTER II;Lo;0;L;;;;;N;;;;; 11187;SHARADA LETTER U;Lo;0;L;;;;;N;;;;; 11188;SHARADA LETTER UU;Lo;0;L;;;;;N;;;;; 11189;SHARADA LETTER VOCALIC R;Lo;0;L;;;;;N;;;;; 1118A;SHARADA LETTER VOCALIC RR;Lo;0;L;;;;;N;;;;; 1118B;SHARADA LETTER VOCALIC L;Lo;0;L;;;;;N;;;;; 1118C;SHARADA LETTER VOCALIC LL;Lo;0;L;;;;;N;;;;; 1118D;SHARADA LETTER E;Lo;0;L;;;;;N;;;;; 1118E;SHARADA LETTER AI;Lo;0;L;;;;;N;;;;; 1118F;SHARADA LETTER O;Lo;0;L;;;;;N;;;;; 11190;SHARADA LETTER AU;Lo;0;L;;;;;N;;;;; 11191;SHARADA LETTER KA;Lo;0;L;;;;;N;;;;; 11192;SHARADA LETTER KHA;Lo;0;L;;;;;N;;;;; 11193;SHARADA LETTER GA;Lo;0;L;;;;;N;;;;; 11194;SHARADA LETTER GHA;Lo;0;L;;;;;N;;;;; 11195;SHARADA LETTER NGA;Lo;0;L;;;;;N;;;;; 11196;SHARADA LETTER CA;Lo;0;L;;;;;N;;;;; 11197;SHARADA LETTER CHA;Lo;0;L;;;;;N;;;;; 11198;SHARADA LETTER JA;Lo;0;L;;;;;N;;;;; 11199;SHARADA LETTER JHA;Lo;0;L;;;;;N;;;;; 1119A;SHARADA LETTER NYA;Lo;0;L;;;;;N;;;;; 1119B;SHARADA LETTER TTA;Lo;0;L;;;;;N;;;;; 1119C;SHARADA LETTER TTHA;Lo;0;L;;;;;N;;;;; 1119D;SHARADA LETTER DDA;Lo;0;L;;;;;N;;;;; 1119E;SHARADA LETTER DDHA;Lo;0;L;;;;;N;;;;; 1119F;SHARADA LETTER NNA;Lo;0;L;;;;;N;;;;; 111A0;SHARADA LETTER TA;Lo;0;L;;;;;N;;;;; 111A1;SHARADA LETTER THA;Lo;0;L;;;;;N;;;;; 111A2;SHARADA LETTER DA;Lo;0;L;;;;;N;;;;; 111A3;SHARADA LETTER DHA;Lo;0;L;;;;;N;;;;; 111A4;SHARADA LETTER NA;Lo;0;L;;;;;N;;;;; 111A5;SHARADA LETTER PA;Lo;0;L;;;;;N;;;;; 111A6;SHARADA LETTER PHA;Lo;0;L;;;;;N;;;;; 111A7;SHARADA LETTER BA;Lo;0;L;;;;;N;;;;; 111A8;SHARADA LETTER BHA;Lo;0;L;;;;;N;;;;; 111A9;SHARADA LETTER MA;Lo;0;L;;;;;N;;;;; 111AA;SHARADA LETTER YA;Lo;0;L;;;;;N;;;;; 111AB;SHARADA LETTER RA;Lo;0;L;;;;;N;;;;; 111AC;SHARADA LETTER LA;Lo;0;L;;;;;N;;;;; 111AD;SHARADA LETTER LLA;Lo;0;L;;;;;N;;;;; 111AE;SHARADA LETTER VA;Lo;0;L;;;;;N;;;;; 111AF;SHARADA LETTER SHA;Lo;0;L;;;;;N;;;;; 111B0;SHARADA LETTER SSA;Lo;0;L;;;;;N;;;;; 111B1;SHARADA LETTER SA;Lo;0;L;;;;;N;;;;; 111B2;SHARADA LETTER HA;Lo;0;L;;;;;N;;;;; 111B3;SHARADA VOWEL SIGN AA;Mc;0;L;;;;;N;;;;; 111B4;SHARADA VOWEL SIGN I;Mc;0;L;;;;;N;;;;; 111B5;SHARADA VOWEL SIGN II;Mc;0;L;;;;;N;;;;; 111B6;SHARADA VOWEL SIGN U;Mn;0;NSM;;;;;N;;;;; 111B7;SHARADA VOWEL SIGN UU;Mn;0;NSM;;;;;N;;;;; 111B8;SHARADA VOWEL SIGN VOCALIC R;Mn;0;NSM;;;;;N;;;;; 111B9;SHARADA VOWEL SIGN VOCALIC RR;Mn;0;NSM;;;;;N;;;;; 111BA;SHARADA VOWEL SIGN VOCALIC L;Mn;0;NSM;;;;;N;;;;; 111BB;SHARADA VOWEL SIGN VOCALIC LL;Mn;0;NSM;;;;;N;;;;; 111BC;SHARADA VOWEL SIGN E;Mn;0;NSM;;;;;N;;;;; 111BD;SHARADA VOWEL SIGN AI;Mn;0;NSM;;;;;N;;;;; 111BE;SHARADA VOWEL SIGN O;Mn;0;NSM;;;;;N;;;;; 111BF;SHARADA VOWEL SIGN AU;Mc;0;L;;;;;N;;;;; 111C0;SHARADA SIGN VIRAMA;Mc;9;L;;;;;N;;;;; 111C1;SHARADA SIGN AVAGRAHA;Lo;0;L;;;;;N;;;;; 111C2;SHARADA SIGN JIHVAMULIYA;Lo;0;L;;;;;N;;;;; 111C3;SHARADA SIGN UPADHMANIYA;Lo;0;L;;;;;N;;;;; 111C4;SHARADA OM;Lo;0;L;;;;;N;;;;; 111C5;SHARADA DANDA;Po;0;L;;;;;N;;;;; 111C6;SHARADA DOUBLE DANDA;Po;0;L;;;;;N;;;;; 111C7;SHARADA ABBREVIATION SIGN;Po;0;L;;;;;N;;;;; 111C8;SHARADA SEPARATOR;Po;0;L;;;;;N;;;;; 111CD;SHARADA SUTRA MARK;Po;0;L;;;;;N;;;;; 111D0;SHARADA DIGIT ZERO;Nd;0;L;;0;0;0;N;;;;; 111D1;SHARADA DIGIT ONE;Nd;0;L;;1;1;1;N;;;;; 111D2;SHARADA DIGIT TWO;Nd;0;L;;2;2;2;N;;;;; 111D3;SHARADA DIGIT THREE;Nd;0;L;;3;3;3;N;;;;; 111D4;SHARADA DIGIT FOUR;Nd;0;L;;4;4;4;N;;;;; 111D5;SHARADA DIGIT FIVE;Nd;0;L;;5;5;5;N;;;;; 111D6;SHARADA DIGIT SIX;Nd;0;L;;6;6;6;N;;;;; 111D7;SHARADA DIGIT SEVEN;Nd;0;L;;7;7;7;N;;;;; 111D8;SHARADA DIGIT EIGHT;Nd;0;L;;8;8;8;N;;;;; 111D9;SHARADA DIGIT NINE;Nd;0;L;;9;9;9;N;;;;; 111DA;SHARADA EKAM;Lo;0;L;;;;;N;;;;; 111E1;SINHALA ARCHAIC DIGIT ONE;No;0;L;;;;1;N;;;;; 111E2;SINHALA ARCHAIC DIGIT TWO;No;0;L;;;;2;N;;;;; 111E3;SINHALA ARCHAIC DIGIT THREE;No;0;L;;;;3;N;;;;; 111E4;SINHALA ARCHAIC DIGIT FOUR;No;0;L;;;;4;N;;;;; 111E5;SINHALA ARCHAIC DIGIT FIVE;No;0;L;;;;5;N;;;;; 111E6;SINHALA ARCHAIC DIGIT SIX;No;0;L;;;;6;N;;;;; 111E7;SINHALA ARCHAIC DIGIT SEVEN;No;0;L;;;;7;N;;;;; 111E8;SINHALA ARCHAIC DIGIT EIGHT;No;0;L;;;;8;N;;;;; 111E9;SINHALA ARCHAIC DIGIT NINE;No;0;L;;;;9;N;;;;; 111EA;SINHALA ARCHAIC NUMBER TEN;No;0;L;;;;10;N;;;;; 111EB;SINHALA ARCHAIC NUMBER TWENTY;No;0;L;;;;20;N;;;;; 111EC;SINHALA ARCHAIC NUMBER THIRTY;No;0;L;;;;30;N;;;;; 111ED;SINHALA ARCHAIC NUMBER FORTY;No;0;L;;;;40;N;;;;; 111EE;SINHALA ARCHAIC NUMBER FIFTY;No;0;L;;;;50;N;;;;; 111EF;SINHALA ARCHAIC NUMBER SIXTY;No;0;L;;;;60;N;;;;; 111F0;SINHALA ARCHAIC NUMBER SEVENTY;No;0;L;;;;70;N;;;;; 111F1;SINHALA ARCHAIC NUMBER EIGHTY;No;0;L;;;;80;N;;;;; 111F2;SINHALA ARCHAIC NUMBER NINETY;No;0;L;;;;90;N;;;;; 111F3;SINHALA ARCHAIC NUMBER ONE HUNDRED;No;0;L;;;;100;N;;;;; 111F4;SINHALA ARCHAIC NUMBER ONE THOUSAND;No;0;L;;;;1000;N;;;;; 11200;KHOJKI LETTER A;Lo;0;L;;;;;N;;;;; 11201;KHOJKI LETTER AA;Lo;0;L;;;;;N;;;;; 11202;KHOJKI LETTER I;Lo;0;L;;;;;N;;;;; 11203;KHOJKI LETTER U;Lo;0;L;;;;;N;;;;; 11204;KHOJKI LETTER E;Lo;0;L;;;;;N;;;;; 11205;KHOJKI LETTER AI;Lo;0;L;;;;;N;;;;; 11206;KHOJKI LETTER O;Lo;0;L;;;;;N;;;;; 11207;KHOJKI LETTER AU;Lo;0;L;;;;;N;;;;; 11208;KHOJKI LETTER KA;Lo;0;L;;;;;N;;;;; 11209;KHOJKI LETTER KHA;Lo;0;L;;;;;N;;;;; 1120A;KHOJKI LETTER GA;Lo;0;L;;;;;N;;;;; 1120B;KHOJKI LETTER GGA;Lo;0;L;;;;;N;;;;; 1120C;KHOJKI LETTER GHA;Lo;0;L;;;;;N;;;;; 1120D;KHOJKI LETTER NGA;Lo;0;L;;;;;N;;;;; 1120E;KHOJKI LETTER CA;Lo;0;L;;;;;N;;;;; 1120F;KHOJKI LETTER CHA;Lo;0;L;;;;;N;;;;; 11210;KHOJKI LETTER JA;Lo;0;L;;;;;N;;;;; 11211;KHOJKI LETTER JJA;Lo;0;L;;;;;N;;;;; 11213;KHOJKI LETTER NYA;Lo;0;L;;;;;N;;;;; 11214;KHOJKI LETTER TTA;Lo;0;L;;;;;N;;;;; 11215;KHOJKI LETTER TTHA;Lo;0;L;;;;;N;;;;; 11216;KHOJKI LETTER DDA;Lo;0;L;;;;;N;;;;; 11217;KHOJKI LETTER DDHA;Lo;0;L;;;;;N;;;;; 11218;KHOJKI LETTER NNA;Lo;0;L;;;;;N;;;;; 11219;KHOJKI LETTER TA;Lo;0;L;;;;;N;;;;; 1121A;KHOJKI LETTER THA;Lo;0;L;;;;;N;;;;; 1121B;KHOJKI LETTER DA;Lo;0;L;;;;;N;;;;; 1121C;KHOJKI LETTER DDDA;Lo;0;L;;;;;N;;;;; 1121D;KHOJKI LETTER DHA;Lo;0;L;;;;;N;;;;; 1121E;KHOJKI LETTER NA;Lo;0;L;;;;;N;;;;; 1121F;KHOJKI LETTER PA;Lo;0;L;;;;;N;;;;; 11220;KHOJKI LETTER PHA;Lo;0;L;;;;;N;;;;; 11221;KHOJKI LETTER BA;Lo;0;L;;;;;N;;;;; 11222;KHOJKI LETTER BBA;Lo;0;L;;;;;N;;;;; 11223;KHOJKI LETTER BHA;Lo;0;L;;;;;N;;;;; 11224;KHOJKI LETTER MA;Lo;0;L;;;;;N;;;;; 11225;KHOJKI LETTER YA;Lo;0;L;;;;;N;;;;; 11226;KHOJKI LETTER RA;Lo;0;L;;;;;N;;;;; 11227;KHOJKI LETTER LA;Lo;0;L;;;;;N;;;;; 11228;KHOJKI LETTER VA;Lo;0;L;;;;;N;;;;; 11229;KHOJKI LETTER SA;Lo;0;L;;;;;N;;;;; 1122A;KHOJKI LETTER HA;Lo;0;L;;;;;N;;;;; 1122B;KHOJKI LETTER LLA;Lo;0;L;;;;;N;;;;; 1122C;KHOJKI VOWEL SIGN AA;Mc;0;L;;;;;N;;;;; 1122D;KHOJKI VOWEL SIGN I;Mc;0;L;;;;;N;;;;; 1122E;KHOJKI VOWEL SIGN II;Mc;0;L;;;;;N;;;;; 1122F;KHOJKI VOWEL SIGN U;Mn;0;NSM;;;;;N;;;;; 11230;KHOJKI VOWEL SIGN E;Mn;0;NSM;;;;;N;;;;; 11231;KHOJKI VOWEL SIGN AI;Mn;0;NSM;;;;;N;;;;; 11232;KHOJKI VOWEL SIGN O;Mc;0;L;;;;;N;;;;; 11233;KHOJKI VOWEL SIGN AU;Mc;0;L;;;;;N;;;;; 11234;KHOJKI SIGN ANUSVARA;Mn;0;NSM;;;;;N;;;;; 11235;KHOJKI SIGN VIRAMA;Mc;9;L;;;;;N;;;;; 11236;KHOJKI SIGN NUKTA;Mn;7;NSM;;;;;N;;;;; 11237;KHOJKI SIGN SHADDA;Mn;0;NSM;;;;;N;;;;; 11238;KHOJKI DANDA;Po;0;L;;;;;N;;;;; 11239;KHOJKI DOUBLE DANDA;Po;0;L;;;;;N;;;;; 1123A;KHOJKI WORD SEPARATOR;Po;0;L;;;;;N;;;;; 1123B;KHOJKI SECTION MARK;Po;0;L;;;;;N;;;;; 1123C;KHOJKI DOUBLE SECTION MARK;Po;0;L;;;;;N;;;;; 1123D;KHOJKI ABBREVIATION SIGN;Po;0;L;;;;;N;;;;; 112B0;KHUDAWADI LETTER A;Lo;0;L;;;;;N;;;;; 112B1;KHUDAWADI LETTER AA;Lo;0;L;;;;;N;;;;; 112B2;KHUDAWADI LETTER I;Lo;0;L;;;;;N;;;;; 112B3;KHUDAWADI LETTER II;Lo;0;L;;;;;N;;;;; 112B4;KHUDAWADI LETTER U;Lo;0;L;;;;;N;;;;; 112B5;KHUDAWADI LETTER UU;Lo;0;L;;;;;N;;;;; 112B6;KHUDAWADI LETTER E;Lo;0;L;;;;;N;;;;; 112B7;KHUDAWADI LETTER AI;Lo;0;L;;;;;N;;;;; 112B8;KHUDAWADI LETTER O;Lo;0;L;;;;;N;;;;; 112B9;KHUDAWADI LETTER AU;Lo;0;L;;;;;N;;;;; 112BA;KHUDAWADI LETTER KA;Lo;0;L;;;;;N;;;;; 112BB;KHUDAWADI LETTER KHA;Lo;0;L;;;;;N;;;;; 112BC;KHUDAWADI LETTER GA;Lo;0;L;;;;;N;;;;; 112BD;KHUDAWADI LETTER GGA;Lo;0;L;;;;;N;;;;; 112BE;KHUDAWADI LETTER GHA;Lo;0;L;;;;;N;;;;; 112BF;KHUDAWADI LETTER NGA;Lo;0;L;;;;;N;;;;; 112C0;KHUDAWADI LETTER CA;Lo;0;L;;;;;N;;;;; 112C1;KHUDAWADI LETTER CHA;Lo;0;L;;;;;N;;;;; 112C2;KHUDAWADI LETTER JA;Lo;0;L;;;;;N;;;;; 112C3;KHUDAWADI LETTER JJA;Lo;0;L;;;;;N;;;;; 112C4;KHUDAWADI LETTER JHA;Lo;0;L;;;;;N;;;;; 112C5;KHUDAWADI LETTER NYA;Lo;0;L;;;;;N;;;;; 112C6;KHUDAWADI LETTER TTA;Lo;0;L;;;;;N;;;;; 112C7;KHUDAWADI LETTER TTHA;Lo;0;L;;;;;N;;;;; 112C8;KHUDAWADI LETTER DDA;Lo;0;L;;;;;N;;;;; 112C9;KHUDAWADI LETTER DDDA;Lo;0;L;;;;;N;;;;; 112CA;KHUDAWADI LETTER RRA;Lo;0;L;;;;;N;;;;; 112CB;KHUDAWADI LETTER DDHA;Lo;0;L;;;;;N;;;;; 112CC;KHUDAWADI LETTER NNA;Lo;0;L;;;;;N;;;;; 112CD;KHUDAWADI LETTER TA;Lo;0;L;;;;;N;;;;; 112CE;KHUDAWADI LETTER THA;Lo;0;L;;;;;N;;;;; 112CF;KHUDAWADI LETTER DA;Lo;0;L;;;;;N;;;;; 112D0;KHUDAWADI LETTER DHA;Lo;0;L;;;;;N;;;;; 112D1;KHUDAWADI LETTER NA;Lo;0;L;;;;;N;;;;; 112D2;KHUDAWADI LETTER PA;Lo;0;L;;;;;N;;;;; 112D3;KHUDAWADI LETTER PHA;Lo;0;L;;;;;N;;;;; 112D4;KHUDAWADI LETTER BA;Lo;0;L;;;;;N;;;;; 112D5;KHUDAWADI LETTER BBA;Lo;0;L;;;;;N;;;;; 112D6;KHUDAWADI LETTER BHA;Lo;0;L;;;;;N;;;;; 112D7;KHUDAWADI LETTER MA;Lo;0;L;;;;;N;;;;; 112D8;KHUDAWADI LETTER YA;Lo;0;L;;;;;N;;;;; 112D9;KHUDAWADI LETTER RA;Lo;0;L;;;;;N;;;;; 112DA;KHUDAWADI LETTER LA;Lo;0;L;;;;;N;;;;; 112DB;KHUDAWADI LETTER VA;Lo;0;L;;;;;N;;;;; 112DC;KHUDAWADI LETTER SHA;Lo;0;L;;;;;N;;;;; 112DD;KHUDAWADI LETTER SA;Lo;0;L;;;;;N;;;;; 112DE;KHUDAWADI LETTER HA;Lo;0;L;;;;;N;;;;; 112DF;KHUDAWADI SIGN ANUSVARA;Mn;0;NSM;;;;;N;;;;; 112E0;KHUDAWADI VOWEL SIGN AA;Mc;0;L;;;;;N;;;;; 112E1;KHUDAWADI VOWEL SIGN I;Mc;0;L;;;;;N;;;;; 112E2;KHUDAWADI VOWEL SIGN II;Mc;0;L;;;;;N;;;;; 112E3;KHUDAWADI VOWEL SIGN U;Mn;0;NSM;;;;;N;;;;; 112E4;KHUDAWADI VOWEL SIGN UU;Mn;0;NSM;;;;;N;;;;; 112E5;KHUDAWADI VOWEL SIGN E;Mn;0;NSM;;;;;N;;;;; 112E6;KHUDAWADI VOWEL SIGN AI;Mn;0;NSM;;;;;N;;;;; 112E7;KHUDAWADI VOWEL SIGN O;Mn;0;NSM;;;;;N;;;;; 112E8;KHUDAWADI VOWEL SIGN AU;Mn;0;NSM;;;;;N;;;;; 112E9;KHUDAWADI SIGN NUKTA;Mn;7;NSM;;;;;N;;;;; 112EA;KHUDAWADI SIGN VIRAMA;Mn;9;NSM;;;;;N;;;;; 112F0;KHUDAWADI DIGIT ZERO;Nd;0;L;;0;0;0;N;;;;; 112F1;KHUDAWADI DIGIT ONE;Nd;0;L;;1;1;1;N;;;;; 112F2;KHUDAWADI DIGIT TWO;Nd;0;L;;2;2;2;N;;;;; 112F3;KHUDAWADI DIGIT THREE;Nd;0;L;;3;3;3;N;;;;; 112F4;KHUDAWADI DIGIT FOUR;Nd;0;L;;4;4;4;N;;;;; 112F5;KHUDAWADI DIGIT FIVE;Nd;0;L;;5;5;5;N;;;;; 112F6;KHUDAWADI DIGIT SIX;Nd;0;L;;6;6;6;N;;;;; 112F7;KHUDAWADI DIGIT SEVEN;Nd;0;L;;7;7;7;N;;;;; 112F8;KHUDAWADI DIGIT EIGHT;Nd;0;L;;8;8;8;N;;;;; 112F9;KHUDAWADI DIGIT NINE;Nd;0;L;;9;9;9;N;;;;; 11301;GRANTHA SIGN CANDRABINDU;Mn;0;NSM;;;;;N;;;;; 11302;GRANTHA SIGN ANUSVARA;Mc;0;L;;;;;N;;;;; 11303;GRANTHA SIGN VISARGA;Mc;0;L;;;;;N;;;;; 11305;GRANTHA LETTER A;Lo;0;L;;;;;N;;;;; 11306;GRANTHA LETTER AA;Lo;0;L;;;;;N;;;;; 11307;GRANTHA LETTER I;Lo;0;L;;;;;N;;;;; 11308;GRANTHA LETTER II;Lo;0;L;;;;;N;;;;; 11309;GRANTHA LETTER U;Lo;0;L;;;;;N;;;;; 1130A;GRANTHA LETTER UU;Lo;0;L;;;;;N;;;;; 1130B;GRANTHA LETTER VOCALIC R;Lo;0;L;;;;;N;;;;; 1130C;GRANTHA LETTER VOCALIC L;Lo;0;L;;;;;N;;;;; 1130F;GRANTHA LETTER EE;Lo;0;L;;;;;N;;;;; 11310;GRANTHA LETTER AI;Lo;0;L;;;;;N;;;;; 11313;GRANTHA LETTER OO;Lo;0;L;;;;;N;;;;; 11314;GRANTHA LETTER AU;Lo;0;L;;;;;N;;;;; 11315;GRANTHA LETTER KA;Lo;0;L;;;;;N;;;;; 11316;GRANTHA LETTER KHA;Lo;0;L;;;;;N;;;;; 11317;GRANTHA LETTER GA;Lo;0;L;;;;;N;;;;; 11318;GRANTHA LETTER GHA;Lo;0;L;;;;;N;;;;; 11319;GRANTHA LETTER NGA;Lo;0;L;;;;;N;;;;; 1131A;GRANTHA LETTER CA;Lo;0;L;;;;;N;;;;; 1131B;GRANTHA LETTER CHA;Lo;0;L;;;;;N;;;;; 1131C;GRANTHA LETTER JA;Lo;0;L;;;;;N;;;;; 1131D;GRANTHA LETTER JHA;Lo;0;L;;;;;N;;;;; 1131E;GRANTHA LETTER NYA;Lo;0;L;;;;;N;;;;; 1131F;GRANTHA LETTER TTA;Lo;0;L;;;;;N;;;;; 11320;GRANTHA LETTER TTHA;Lo;0;L;;;;;N;;;;; 11321;GRANTHA LETTER DDA;Lo;0;L;;;;;N;;;;; 11322;GRANTHA LETTER DDHA;Lo;0;L;;;;;N;;;;; 11323;GRANTHA LETTER NNA;Lo;0;L;;;;;N;;;;; 11324;GRANTHA LETTER TA;Lo;0;L;;;;;N;;;;; 11325;GRANTHA LETTER THA;Lo;0;L;;;;;N;;;;; 11326;GRANTHA LETTER DA;Lo;0;L;;;;;N;;;;; 11327;GRANTHA LETTER DHA;Lo;0;L;;;;;N;;;;; 11328;GRANTHA LETTER NA;Lo;0;L;;;;;N;;;;; 1132A;GRANTHA LETTER PA;Lo;0;L;;;;;N;;;;; 1132B;GRANTHA LETTER PHA;Lo;0;L;;;;;N;;;;; 1132C;GRANTHA LETTER BA;Lo;0;L;;;;;N;;;;; 1132D;GRANTHA LETTER BHA;Lo;0;L;;;;;N;;;;; 1132E;GRANTHA LETTER MA;Lo;0;L;;;;;N;;;;; 1132F;GRANTHA LETTER YA;Lo;0;L;;;;;N;;;;; 11330;GRANTHA LETTER RA;Lo;0;L;;;;;N;;;;; 11332;GRANTHA LETTER LA;Lo;0;L;;;;;N;;;;; 11333;GRANTHA LETTER LLA;Lo;0;L;;;;;N;;;;; 11335;GRANTHA LETTER VA;Lo;0;L;;;;;N;;;;; 11336;GRANTHA LETTER SHA;Lo;0;L;;;;;N;;;;; 11337;GRANTHA LETTER SSA;Lo;0;L;;;;;N;;;;; 11338;GRANTHA LETTER SA;Lo;0;L;;;;;N;;;;; 11339;GRANTHA LETTER HA;Lo;0;L;;;;;N;;;;; 1133C;GRANTHA SIGN NUKTA;Mn;7;NSM;;;;;N;;;;; 1133D;GRANTHA SIGN AVAGRAHA;Lo;0;L;;;;;N;;;;; 1133E;GRANTHA VOWEL SIGN AA;Mc;0;L;;;;;N;;;;; 1133F;GRANTHA VOWEL SIGN I;Mc;0;L;;;;;N;;;;; 11340;GRANTHA VOWEL SIGN II;Mn;0;NSM;;;;;N;;;;; 11341;GRANTHA VOWEL SIGN U;Mc;0;L;;;;;N;;;;; 11342;GRANTHA VOWEL SIGN UU;Mc;0;L;;;;;N;;;;; 11343;GRANTHA VOWEL SIGN VOCALIC R;Mc;0;L;;;;;N;;;;; 11344;GRANTHA VOWEL SIGN VOCALIC RR;Mc;0;L;;;;;N;;;;; 11347;GRANTHA VOWEL SIGN EE;Mc;0;L;;;;;N;;;;; 11348;GRANTHA VOWEL SIGN AI;Mc;0;L;;;;;N;;;;; 1134B;GRANTHA VOWEL SIGN OO;Mc;0;L;11347 1133E;;;;N;;;;; 1134C;GRANTHA VOWEL SIGN AU;Mc;0;L;11347 11357;;;;N;;;;; 1134D;GRANTHA SIGN VIRAMA;Mc;9;L;;;;;N;;;;; 11357;GRANTHA AU LENGTH MARK;Mc;0;L;;;;;N;;;;; 1135D;GRANTHA SIGN PLUTA;Lo;0;L;;;;;N;;;;; 1135E;GRANTHA LETTER VEDIC ANUSVARA;Lo;0;L;;;;;N;;;;; 1135F;GRANTHA LETTER VEDIC DOUBLE ANUSVARA;Lo;0;L;;;;;N;;;;; 11360;GRANTHA LETTER VOCALIC RR;Lo;0;L;;;;;N;;;;; 11361;GRANTHA LETTER VOCALIC LL;Lo;0;L;;;;;N;;;;; 11362;GRANTHA VOWEL SIGN VOCALIC L;Mc;0;L;;;;;N;;;;; 11363;GRANTHA VOWEL SIGN VOCALIC LL;Mc;0;L;;;;;N;;;;; 11366;COMBINING GRANTHA DIGIT ZERO;Mn;230;NSM;;;;;N;;;;; 11367;COMBINING GRANTHA DIGIT ONE;Mn;230;NSM;;;;;N;;;;; 11368;COMBINING GRANTHA DIGIT TWO;Mn;230;NSM;;;;;N;;;;; 11369;COMBINING GRANTHA DIGIT THREE;Mn;230;NSM;;;;;N;;;;; 1136A;COMBINING GRANTHA DIGIT FOUR;Mn;230;NSM;;;;;N;;;;; 1136B;COMBINING GRANTHA DIGIT FIVE;Mn;230;NSM;;;;;N;;;;; 1136C;COMBINING GRANTHA DIGIT SIX;Mn;230;NSM;;;;;N;;;;; 11370;COMBINING GRANTHA LETTER A;Mn;230;NSM;;;;;N;;;;; 11371;COMBINING GRANTHA LETTER KA;Mn;230;NSM;;;;;N;;;;; 11372;COMBINING GRANTHA LETTER NA;Mn;230;NSM;;;;;N;;;;; 11373;COMBINING GRANTHA LETTER VI;Mn;230;NSM;;;;;N;;;;; 11374;COMBINING GRANTHA LETTER PA;Mn;230;NSM;;;;;N;;;;; 11480;TIRHUTA ANJI;Lo;0;L;;;;;N;;;;; 11481;TIRHUTA LETTER A;Lo;0;L;;;;;N;;;;; 11482;TIRHUTA LETTER AA;Lo;0;L;;;;;N;;;;; 11483;TIRHUTA LETTER I;Lo;0;L;;;;;N;;;;; 11484;TIRHUTA LETTER II;Lo;0;L;;;;;N;;;;; 11485;TIRHUTA LETTER U;Lo;0;L;;;;;N;;;;; 11486;TIRHUTA LETTER UU;Lo;0;L;;;;;N;;;;; 11487;TIRHUTA LETTER VOCALIC R;Lo;0;L;;;;;N;;;;; 11488;TIRHUTA LETTER VOCALIC RR;Lo;0;L;;;;;N;;;;; 11489;TIRHUTA LETTER VOCALIC L;Lo;0;L;;;;;N;;;;; 1148A;TIRHUTA LETTER VOCALIC LL;Lo;0;L;;;;;N;;;;; 1148B;TIRHUTA LETTER E;Lo;0;L;;;;;N;;;;; 1148C;TIRHUTA LETTER AI;Lo;0;L;;;;;N;;;;; 1148D;TIRHUTA LETTER O;Lo;0;L;;;;;N;;;;; 1148E;TIRHUTA LETTER AU;Lo;0;L;;;;;N;;;;; 1148F;TIRHUTA LETTER KA;Lo;0;L;;;;;N;;;;; 11490;TIRHUTA LETTER KHA;Lo;0;L;;;;;N;;;;; 11491;TIRHUTA LETTER GA;Lo;0;L;;;;;N;;;;; 11492;TIRHUTA LETTER GHA;Lo;0;L;;;;;N;;;;; 11493;TIRHUTA LETTER NGA;Lo;0;L;;;;;N;;;;; 11494;TIRHUTA LETTER CA;Lo;0;L;;;;;N;;;;; 11495;TIRHUTA LETTER CHA;Lo;0;L;;;;;N;;;;; 11496;TIRHUTA LETTER JA;Lo;0;L;;;;;N;;;;; 11497;TIRHUTA LETTER JHA;Lo;0;L;;;;;N;;;;; 11498;TIRHUTA LETTER NYA;Lo;0;L;;;;;N;;;;; 11499;TIRHUTA LETTER TTA;Lo;0;L;;;;;N;;;;; 1149A;TIRHUTA LETTER TTHA;Lo;0;L;;;;;N;;;;; 1149B;TIRHUTA LETTER DDA;Lo;0;L;;;;;N;;;;; 1149C;TIRHUTA LETTER DDHA;Lo;0;L;;;;;N;;;;; 1149D;TIRHUTA LETTER NNA;Lo;0;L;;;;;N;;;;; 1149E;TIRHUTA LETTER TA;Lo;0;L;;;;;N;;;;; 1149F;TIRHUTA LETTER THA;Lo;0;L;;;;;N;;;;; 114A0;TIRHUTA LETTER DA;Lo;0;L;;;;;N;;;;; 114A1;TIRHUTA LETTER DHA;Lo;0;L;;;;;N;;;;; 114A2;TIRHUTA LETTER NA;Lo;0;L;;;;;N;;;;; 114A3;TIRHUTA LETTER PA;Lo;0;L;;;;;N;;;;; 114A4;TIRHUTA LETTER PHA;Lo;0;L;;;;;N;;;;; 114A5;TIRHUTA LETTER BA;Lo;0;L;;;;;N;;;;; 114A6;TIRHUTA LETTER BHA;Lo;0;L;;;;;N;;;;; 114A7;TIRHUTA LETTER MA;Lo;0;L;;;;;N;;;;; 114A8;TIRHUTA LETTER YA;Lo;0;L;;;;;N;;;;; 114A9;TIRHUTA LETTER RA;Lo;0;L;;;;;N;;;;; 114AA;TIRHUTA LETTER LA;Lo;0;L;;;;;N;;;;; 114AB;TIRHUTA LETTER VA;Lo;0;L;;;;;N;;;;; 114AC;TIRHUTA LETTER SHA;Lo;0;L;;;;;N;;;;; 114AD;TIRHUTA LETTER SSA;Lo;0;L;;;;;N;;;;; 114AE;TIRHUTA LETTER SA;Lo;0;L;;;;;N;;;;; 114AF;TIRHUTA LETTER HA;Lo;0;L;;;;;N;;;;; 114B0;TIRHUTA VOWEL SIGN AA;Mc;0;L;;;;;N;;;;; 114B1;TIRHUTA VOWEL SIGN I;Mc;0;L;;;;;N;;;;; 114B2;TIRHUTA VOWEL SIGN II;Mc;0;L;;;;;N;;;;; 114B3;TIRHUTA VOWEL SIGN U;Mn;0;NSM;;;;;N;;;;; 114B4;TIRHUTA VOWEL SIGN UU;Mn;0;NSM;;;;;N;;;;; 114B5;TIRHUTA VOWEL SIGN VOCALIC R;Mn;0;NSM;;;;;N;;;;; 114B6;TIRHUTA VOWEL SIGN VOCALIC RR;Mn;0;NSM;;;;;N;;;;; 114B7;TIRHUTA VOWEL SIGN VOCALIC L;Mn;0;NSM;;;;;N;;;;; 114B8;TIRHUTA VOWEL SIGN VOCALIC LL;Mn;0;NSM;;;;;N;;;;; 114B9;TIRHUTA VOWEL SIGN E;Mc;0;L;;;;;N;;;;; 114BA;TIRHUTA VOWEL SIGN SHORT E;Mn;0;NSM;;;;;N;;;;; 114BB;TIRHUTA VOWEL SIGN AI;Mc;0;L;114B9 114BA;;;;N;;;;; 114BC;TIRHUTA VOWEL SIGN O;Mc;0;L;114B9 114B0;;;;N;;;;; 114BD;TIRHUTA VOWEL SIGN SHORT O;Mc;0;L;;;;;N;;;;; 114BE;TIRHUTA VOWEL SIGN AU;Mc;0;L;114B9 114BD;;;;N;;;;; 114BF;TIRHUTA SIGN CANDRABINDU;Mn;0;NSM;;;;;N;;;;; 114C0;TIRHUTA SIGN ANUSVARA;Mn;0;NSM;;;;;N;;;;; 114C1;TIRHUTA SIGN VISARGA;Mc;0;L;;;;;N;;;;; 114C2;TIRHUTA SIGN VIRAMA;Mn;9;NSM;;;;;N;;;;; 114C3;TIRHUTA SIGN NUKTA;Mn;7;NSM;;;;;N;;;;; 114C4;TIRHUTA SIGN AVAGRAHA;Lo;0;L;;;;;N;;;;; 114C5;TIRHUTA GVANG;Lo;0;L;;;;;N;;;;; 114C6;TIRHUTA ABBREVIATION SIGN;Po;0;L;;;;;N;;;;; 114C7;TIRHUTA OM;Lo;0;L;;;;;N;;;;; 114D0;TIRHUTA DIGIT ZERO;Nd;0;L;;0;0;0;N;;;;; 114D1;TIRHUTA DIGIT ONE;Nd;0;L;;1;1;1;N;;;;; 114D2;TIRHUTA DIGIT TWO;Nd;0;L;;2;2;2;N;;;;; 114D3;TIRHUTA DIGIT THREE;Nd;0;L;;3;3;3;N;;;;; 114D4;TIRHUTA DIGIT FOUR;Nd;0;L;;4;4;4;N;;;;; 114D5;TIRHUTA DIGIT FIVE;Nd;0;L;;5;5;5;N;;;;; 114D6;TIRHUTA DIGIT SIX;Nd;0;L;;6;6;6;N;;;;; 114D7;TIRHUTA DIGIT SEVEN;Nd;0;L;;7;7;7;N;;;;; 114D8;TIRHUTA DIGIT EIGHT;Nd;0;L;;8;8;8;N;;;;; 114D9;TIRHUTA DIGIT NINE;Nd;0;L;;9;9;9;N;;;;; 11580;SIDDHAM LETTER A;Lo;0;L;;;;;N;;;;; 11581;SIDDHAM LETTER AA;Lo;0;L;;;;;N;;;;; 11582;SIDDHAM LETTER I;Lo;0;L;;;;;N;;;;; 11583;SIDDHAM LETTER II;Lo;0;L;;;;;N;;;;; 11584;SIDDHAM LETTER U;Lo;0;L;;;;;N;;;;; 11585;SIDDHAM LETTER UU;Lo;0;L;;;;;N;;;;; 11586;SIDDHAM LETTER VOCALIC R;Lo;0;L;;;;;N;;;;; 11587;SIDDHAM LETTER VOCALIC RR;Lo;0;L;;;;;N;;;;; 11588;SIDDHAM LETTER VOCALIC L;Lo;0;L;;;;;N;;;;; 11589;SIDDHAM LETTER VOCALIC LL;Lo;0;L;;;;;N;;;;; 1158A;SIDDHAM LETTER E;Lo;0;L;;;;;N;;;;; 1158B;SIDDHAM LETTER AI;Lo;0;L;;;;;N;;;;; 1158C;SIDDHAM LETTER O;Lo;0;L;;;;;N;;;;; 1158D;SIDDHAM LETTER AU;Lo;0;L;;;;;N;;;;; 1158E;SIDDHAM LETTER KA;Lo;0;L;;;;;N;;;;; 1158F;SIDDHAM LETTER KHA;Lo;0;L;;;;;N;;;;; 11590;SIDDHAM LETTER GA;Lo;0;L;;;;;N;;;;; 11591;SIDDHAM LETTER GHA;Lo;0;L;;;;;N;;;;; 11592;SIDDHAM LETTER NGA;Lo;0;L;;;;;N;;;;; 11593;SIDDHAM LETTER CA;Lo;0;L;;;;;N;;;;; 11594;SIDDHAM LETTER CHA;Lo;0;L;;;;;N;;;;; 11595;SIDDHAM LETTER JA;Lo;0;L;;;;;N;;;;; 11596;SIDDHAM LETTER JHA;Lo;0;L;;;;;N;;;;; 11597;SIDDHAM LETTER NYA;Lo;0;L;;;;;N;;;;; 11598;SIDDHAM LETTER TTA;Lo;0;L;;;;;N;;;;; 11599;SIDDHAM LETTER TTHA;Lo;0;L;;;;;N;;;;; 1159A;SIDDHAM LETTER DDA;Lo;0;L;;;;;N;;;;; 1159B;SIDDHAM LETTER DDHA;Lo;0;L;;;;;N;;;;; 1159C;SIDDHAM LETTER NNA;Lo;0;L;;;;;N;;;;; 1159D;SIDDHAM LETTER TA;Lo;0;L;;;;;N;;;;; 1159E;SIDDHAM LETTER THA;Lo;0;L;;;;;N;;;;; 1159F;SIDDHAM LETTER DA;Lo;0;L;;;;;N;;;;; 115A0;SIDDHAM LETTER DHA;Lo;0;L;;;;;N;;;;; 115A1;SIDDHAM LETTER NA;Lo;0;L;;;;;N;;;;; 115A2;SIDDHAM LETTER PA;Lo;0;L;;;;;N;;;;; 115A3;SIDDHAM LETTER PHA;Lo;0;L;;;;;N;;;;; 115A4;SIDDHAM LETTER BA;Lo;0;L;;;;;N;;;;; 115A5;SIDDHAM LETTER BHA;Lo;0;L;;;;;N;;;;; 115A6;SIDDHAM LETTER MA;Lo;0;L;;;;;N;;;;; 115A7;SIDDHAM LETTER YA;Lo;0;L;;;;;N;;;;; 115A8;SIDDHAM LETTER RA;Lo;0;L;;;;;N;;;;; 115A9;SIDDHAM LETTER LA;Lo;0;L;;;;;N;;;;; 115AA;SIDDHAM LETTER VA;Lo;0;L;;;;;N;;;;; 115AB;SIDDHAM LETTER SHA;Lo;0;L;;;;;N;;;;; 115AC;SIDDHAM LETTER SSA;Lo;0;L;;;;;N;;;;; 115AD;SIDDHAM LETTER SA;Lo;0;L;;;;;N;;;;; 115AE;SIDDHAM LETTER HA;Lo;0;L;;;;;N;;;;; 115AF;SIDDHAM VOWEL SIGN AA;Mc;0;L;;;;;N;;;;; 115B0;SIDDHAM VOWEL SIGN I;Mc;0;L;;;;;N;;;;; 115B1;SIDDHAM VOWEL SIGN II;Mc;0;L;;;;;N;;;;; 115B2;SIDDHAM VOWEL SIGN U;Mn;0;NSM;;;;;N;;;;; 115B3;SIDDHAM VOWEL SIGN UU;Mn;0;NSM;;;;;N;;;;; 115B4;SIDDHAM VOWEL SIGN VOCALIC R;Mn;0;NSM;;;;;N;;;;; 115B5;SIDDHAM VOWEL SIGN VOCALIC RR;Mn;0;NSM;;;;;N;;;;; 115B8;SIDDHAM VOWEL SIGN E;Mc;0;L;;;;;N;;;;; 115B9;SIDDHAM VOWEL SIGN AI;Mc;0;L;;;;;N;;;;; 115BA;SIDDHAM VOWEL SIGN O;Mc;0;L;115B8 115AF;;;;N;;;;; 115BB;SIDDHAM VOWEL SIGN AU;Mc;0;L;115B9 115AF;;;;N;;;;; 115BC;SIDDHAM SIGN CANDRABINDU;Mn;0;NSM;;;;;N;;;;; 115BD;SIDDHAM SIGN ANUSVARA;Mn;0;NSM;;;;;N;;;;; 115BE;SIDDHAM SIGN VISARGA;Mc;0;L;;;;;N;;;;; 115BF;SIDDHAM SIGN VIRAMA;Mn;9;NSM;;;;;N;;;;; 115C0;SIDDHAM SIGN NUKTA;Mn;7;NSM;;;;;N;;;;; 115C1;SIDDHAM SIGN SIDDHAM;Po;0;L;;;;;N;;;;; 115C2;SIDDHAM DANDA;Po;0;L;;;;;N;;;;; 115C3;SIDDHAM DOUBLE DANDA;Po;0;L;;;;;N;;;;; 115C4;SIDDHAM SEPARATOR DOT;Po;0;L;;;;;N;;;;; 115C5;SIDDHAM SEPARATOR BAR;Po;0;L;;;;;N;;;;; 115C6;SIDDHAM REPETITION MARK-1;Po;0;L;;;;;N;;;;; 115C7;SIDDHAM REPETITION MARK-2;Po;0;L;;;;;N;;;;; 115C8;SIDDHAM REPETITION MARK-3;Po;0;L;;;;;N;;;;; 115C9;SIDDHAM END OF TEXT MARK;Po;0;L;;;;;N;;;;; 11600;MODI LETTER A;Lo;0;L;;;;;N;;;;; 11601;MODI LETTER AA;Lo;0;L;;;;;N;;;;; 11602;MODI LETTER I;Lo;0;L;;;;;N;;;;; 11603;MODI LETTER II;Lo;0;L;;;;;N;;;;; 11604;MODI LETTER U;Lo;0;L;;;;;N;;;;; 11605;MODI LETTER UU;Lo;0;L;;;;;N;;;;; 11606;MODI LETTER VOCALIC R;Lo;0;L;;;;;N;;;;; 11607;MODI LETTER VOCALIC RR;Lo;0;L;;;;;N;;;;; 11608;MODI LETTER VOCALIC L;Lo;0;L;;;;;N;;;;; 11609;MODI LETTER VOCALIC LL;Lo;0;L;;;;;N;;;;; 1160A;MODI LETTER E;Lo;0;L;;;;;N;;;;; 1160B;MODI LETTER AI;Lo;0;L;;;;;N;;;;; 1160C;MODI LETTER O;Lo;0;L;;;;;N;;;;; 1160D;MODI LETTER AU;Lo;0;L;;;;;N;;;;; 1160E;MODI LETTER KA;Lo;0;L;;;;;N;;;;; 1160F;MODI LETTER KHA;Lo;0;L;;;;;N;;;;; 11610;MODI LETTER GA;Lo;0;L;;;;;N;;;;; 11611;MODI LETTER GHA;Lo;0;L;;;;;N;;;;; 11612;MODI LETTER NGA;Lo;0;L;;;;;N;;;;; 11613;MODI LETTER CA;Lo;0;L;;;;;N;;;;; 11614;MODI LETTER CHA;Lo;0;L;;;;;N;;;;; 11615;MODI LETTER JA;Lo;0;L;;;;;N;;;;; 11616;MODI LETTER JHA;Lo;0;L;;;;;N;;;;; 11617;MODI LETTER NYA;Lo;0;L;;;;;N;;;;; 11618;MODI LETTER TTA;Lo;0;L;;;;;N;;;;; 11619;MODI LETTER TTHA;Lo;0;L;;;;;N;;;;; 1161A;MODI LETTER DDA;Lo;0;L;;;;;N;;;;; 1161B;MODI LETTER DDHA;Lo;0;L;;;;;N;;;;; 1161C;MODI LETTER NNA;Lo;0;L;;;;;N;;;;; 1161D;MODI LETTER TA;Lo;0;L;;;;;N;;;;; 1161E;MODI LETTER THA;Lo;0;L;;;;;N;;;;; 1161F;MODI LETTER DA;Lo;0;L;;;;;N;;;;; 11620;MODI LETTER DHA;Lo;0;L;;;;;N;;;;; 11621;MODI LETTER NA;Lo;0;L;;;;;N;;;;; 11622;MODI LETTER PA;Lo;0;L;;;;;N;;;;; 11623;MODI LETTER PHA;Lo;0;L;;;;;N;;;;; 11624;MODI LETTER BA;Lo;0;L;;;;;N;;;;; 11625;MODI LETTER BHA;Lo;0;L;;;;;N;;;;; 11626;MODI LETTER MA;Lo;0;L;;;;;N;;;;; 11627;MODI LETTER YA;Lo;0;L;;;;;N;;;;; 11628;MODI LETTER RA;Lo;0;L;;;;;N;;;;; 11629;MODI LETTER LA;Lo;0;L;;;;;N;;;;; 1162A;MODI LETTER VA;Lo;0;L;;;;;N;;;;; 1162B;MODI LETTER SHA;Lo;0;L;;;;;N;;;;; 1162C;MODI LETTER SSA;Lo;0;L;;;;;N;;;;; 1162D;MODI LETTER SA;Lo;0;L;;;;;N;;;;; 1162E;MODI LETTER HA;Lo;0;L;;;;;N;;;;; 1162F;MODI LETTER LLA;Lo;0;L;;;;;N;;;;; 11630;MODI VOWEL SIGN AA;Mc;0;L;;;;;N;;;;; 11631;MODI VOWEL SIGN I;Mc;0;L;;;;;N;;;;; 11632;MODI VOWEL SIGN II;Mc;0;L;;;;;N;;;;; 11633;MODI VOWEL SIGN U;Mn;0;NSM;;;;;N;;;;; 11634;MODI VOWEL SIGN UU;Mn;0;NSM;;;;;N;;;;; 11635;MODI VOWEL SIGN VOCALIC R;Mn;0;NSM;;;;;N;;;;; 11636;MODI VOWEL SIGN VOCALIC RR;Mn;0;NSM;;;;;N;;;;; 11637;MODI VOWEL SIGN VOCALIC L;Mn;0;NSM;;;;;N;;;;; 11638;MODI VOWEL SIGN VOCALIC LL;Mn;0;NSM;;;;;N;;;;; 11639;MODI VOWEL SIGN E;Mn;0;NSM;;;;;N;;;;; 1163A;MODI VOWEL SIGN AI;Mn;0;NSM;;;;;N;;;;; 1163B;MODI VOWEL SIGN O;Mc;0;L;;;;;N;;;;; 1163C;MODI VOWEL SIGN AU;Mc;0;L;;;;;N;;;;; 1163D;MODI SIGN ANUSVARA;Mn;0;NSM;;;;;N;;;;; 1163E;MODI SIGN VISARGA;Mc;0;L;;;;;N;;;;; 1163F;MODI SIGN VIRAMA;Mn;9;NSM;;;;;N;;;;; 11640;MODI SIGN ARDHACANDRA;Mn;0;NSM;;;;;N;;;;; 11641;MODI DANDA;Po;0;L;;;;;N;;;;; 11642;MODI DOUBLE DANDA;Po;0;L;;;;;N;;;;; 11643;MODI ABBREVIATION SIGN;Po;0;L;;;;;N;;;;; 11644;MODI SIGN HUVA;Lo;0;L;;;;;N;;;;; 11650;MODI DIGIT ZERO;Nd;0;L;;0;0;0;N;;;;; 11651;MODI DIGIT ONE;Nd;0;L;;1;1;1;N;;;;; 11652;MODI DIGIT TWO;Nd;0;L;;2;2;2;N;;;;; 11653;MODI DIGIT THREE;Nd;0;L;;3;3;3;N;;;;; 11654;MODI DIGIT FOUR;Nd;0;L;;4;4;4;N;;;;; 11655;MODI DIGIT FIVE;Nd;0;L;;5;5;5;N;;;;; 11656;MODI DIGIT SIX;Nd;0;L;;6;6;6;N;;;;; 11657;MODI DIGIT SEVEN;Nd;0;L;;7;7;7;N;;;;; 11658;MODI DIGIT EIGHT;Nd;0;L;;8;8;8;N;;;;; 11659;MODI DIGIT NINE;Nd;0;L;;9;9;9;N;;;;; 11680;TAKRI LETTER A;Lo;0;L;;;;;N;;;;; 11681;TAKRI LETTER AA;Lo;0;L;;;;;N;;;;; 11682;TAKRI LETTER I;Lo;0;L;;;;;N;;;;; 11683;TAKRI LETTER II;Lo;0;L;;;;;N;;;;; 11684;TAKRI LETTER U;Lo;0;L;;;;;N;;;;; 11685;TAKRI LETTER UU;Lo;0;L;;;;;N;;;;; 11686;TAKRI LETTER E;Lo;0;L;;;;;N;;;;; 11687;TAKRI LETTER AI;Lo;0;L;;;;;N;;;;; 11688;TAKRI LETTER O;Lo;0;L;;;;;N;;;;; 11689;TAKRI LETTER AU;Lo;0;L;;;;;N;;;;; 1168A;TAKRI LETTER KA;Lo;0;L;;;;;N;;;;; 1168B;TAKRI LETTER KHA;Lo;0;L;;;;;N;;;;; 1168C;TAKRI LETTER GA;Lo;0;L;;;;;N;;;;; 1168D;TAKRI LETTER GHA;Lo;0;L;;;;;N;;;;; 1168E;TAKRI LETTER NGA;Lo;0;L;;;;;N;;;;; 1168F;TAKRI LETTER CA;Lo;0;L;;;;;N;;;;; 11690;TAKRI LETTER CHA;Lo;0;L;;;;;N;;;;; 11691;TAKRI LETTER JA;Lo;0;L;;;;;N;;;;; 11692;TAKRI LETTER JHA;Lo;0;L;;;;;N;;;;; 11693;TAKRI LETTER NYA;Lo;0;L;;;;;N;;;;; 11694;TAKRI LETTER TTA;Lo;0;L;;;;;N;;;;; 11695;TAKRI LETTER TTHA;Lo;0;L;;;;;N;;;;; 11696;TAKRI LETTER DDA;Lo;0;L;;;;;N;;;;; 11697;TAKRI LETTER DDHA;Lo;0;L;;;;;N;;;;; 11698;TAKRI LETTER NNA;Lo;0;L;;;;;N;;;;; 11699;TAKRI LETTER TA;Lo;0;L;;;;;N;;;;; 1169A;TAKRI LETTER THA;Lo;0;L;;;;;N;;;;; 1169B;TAKRI LETTER DA;Lo;0;L;;;;;N;;;;; 1169C;TAKRI LETTER DHA;Lo;0;L;;;;;N;;;;; 1169D;TAKRI LETTER NA;Lo;0;L;;;;;N;;;;; 1169E;TAKRI LETTER PA;Lo;0;L;;;;;N;;;;; 1169F;TAKRI LETTER PHA;Lo;0;L;;;;;N;;;;; 116A0;TAKRI LETTER BA;Lo;0;L;;;;;N;;;;; 116A1;TAKRI LETTER BHA;Lo;0;L;;;;;N;;;;; 116A2;TAKRI LETTER MA;Lo;0;L;;;;;N;;;;; 116A3;TAKRI LETTER YA;Lo;0;L;;;;;N;;;;; 116A4;TAKRI LETTER RA;Lo;0;L;;;;;N;;;;; 116A5;TAKRI LETTER LA;Lo;0;L;;;;;N;;;;; 116A6;TAKRI LETTER VA;Lo;0;L;;;;;N;;;;; 116A7;TAKRI LETTER SHA;Lo;0;L;;;;;N;;;;; 116A8;TAKRI LETTER SA;Lo;0;L;;;;;N;;;;; 116A9;TAKRI LETTER HA;Lo;0;L;;;;;N;;;;; 116AA;TAKRI LETTER RRA;Lo;0;L;;;;;N;;;;; 116AB;TAKRI SIGN ANUSVARA;Mn;0;NSM;;;;;N;;;;; 116AC;TAKRI SIGN VISARGA;Mc;0;L;;;;;N;;;;; 116AD;TAKRI VOWEL SIGN AA;Mn;0;NSM;;;;;N;;;;; 116AE;TAKRI VOWEL SIGN I;Mc;0;L;;;;;N;;;;; 116AF;TAKRI VOWEL SIGN II;Mc;0;L;;;;;N;;;;; 116B0;TAKRI VOWEL SIGN U;Mn;0;NSM;;;;;N;;;;; 116B1;TAKRI VOWEL SIGN UU;Mn;0;NSM;;;;;N;;;;; 116B2;TAKRI VOWEL SIGN E;Mn;0;NSM;;;;;N;;;;; 116B3;TAKRI VOWEL SIGN AI;Mn;0;NSM;;;;;N;;;;; 116B4;TAKRI VOWEL SIGN O;Mn;0;NSM;;;;;N;;;;; 116B5;TAKRI VOWEL SIGN AU;Mn;0;NSM;;;;;N;;;;; 116B6;TAKRI SIGN VIRAMA;Mc;9;L;;;;;N;;;;; 116B7;TAKRI SIGN NUKTA;Mn;7;NSM;;;;;N;;;;; 116C0;TAKRI DIGIT ZERO;Nd;0;L;;0;0;0;N;;;;; 116C1;TAKRI DIGIT ONE;Nd;0;L;;1;1;1;N;;;;; 116C2;TAKRI DIGIT TWO;Nd;0;L;;2;2;2;N;;;;; 116C3;TAKRI DIGIT THREE;Nd;0;L;;3;3;3;N;;;;; 116C4;TAKRI DIGIT FOUR;Nd;0;L;;4;4;4;N;;;;; 116C5;TAKRI DIGIT FIVE;Nd;0;L;;5;5;5;N;;;;; 116C6;TAKRI DIGIT SIX;Nd;0;L;;6;6;6;N;;;;; 116C7;TAKRI DIGIT SEVEN;Nd;0;L;;7;7;7;N;;;;; 116C8;TAKRI DIGIT EIGHT;Nd;0;L;;8;8;8;N;;;;; 116C9;TAKRI DIGIT NINE;Nd;0;L;;9;9;9;N;;;;; 118A0;WARANG CITI CAPITAL LETTER NGAA;Lu;0;L;;;;;N;;;;118C0; 118A1;WARANG CITI CAPITAL LETTER A;Lu;0;L;;;;;N;;;;118C1; 118A2;WARANG CITI CAPITAL LETTER WI;Lu;0;L;;;;;N;;;;118C2; 118A3;WARANG CITI CAPITAL LETTER YU;Lu;0;L;;;;;N;;;;118C3; 118A4;WARANG CITI CAPITAL LETTER YA;Lu;0;L;;;;;N;;;;118C4; 118A5;WARANG CITI CAPITAL LETTER YO;Lu;0;L;;;;;N;;;;118C5; 118A6;WARANG CITI CAPITAL LETTER II;Lu;0;L;;;;;N;;;;118C6; 118A7;WARANG CITI CAPITAL LETTER UU;Lu;0;L;;;;;N;;;;118C7; 118A8;WARANG CITI CAPITAL LETTER E;Lu;0;L;;;;;N;;;;118C8; 118A9;WARANG CITI CAPITAL LETTER O;Lu;0;L;;;;;N;;;;118C9; 118AA;WARANG CITI CAPITAL LETTER ANG;Lu;0;L;;;;;N;;;;118CA; 118AB;WARANG CITI CAPITAL LETTER GA;Lu;0;L;;;;;N;;;;118CB; 118AC;WARANG CITI CAPITAL LETTER KO;Lu;0;L;;;;;N;;;;118CC; 118AD;WARANG CITI CAPITAL LETTER ENY;Lu;0;L;;;;;N;;;;118CD; 118AE;WARANG CITI CAPITAL LETTER YUJ;Lu;0;L;;;;;N;;;;118CE; 118AF;WARANG CITI CAPITAL LETTER UC;Lu;0;L;;;;;N;;;;118CF; 118B0;WARANG CITI CAPITAL LETTER ENN;Lu;0;L;;;;;N;;;;118D0; 118B1;WARANG CITI CAPITAL LETTER ODD;Lu;0;L;;;;;N;;;;118D1; 118B2;WARANG CITI CAPITAL LETTER TTE;Lu;0;L;;;;;N;;;;118D2; 118B3;WARANG CITI CAPITAL LETTER NUNG;Lu;0;L;;;;;N;;;;118D3; 118B4;WARANG CITI CAPITAL LETTER DA;Lu;0;L;;;;;N;;;;118D4; 118B5;WARANG CITI CAPITAL LETTER AT;Lu;0;L;;;;;N;;;;118D5; 118B6;WARANG CITI CAPITAL LETTER AM;Lu;0;L;;;;;N;;;;118D6; 118B7;WARANG CITI CAPITAL LETTER BU;Lu;0;L;;;;;N;;;;118D7; 118B8;WARANG CITI CAPITAL LETTER PU;Lu;0;L;;;;;N;;;;118D8; 118B9;WARANG CITI CAPITAL LETTER HIYO;Lu;0;L;;;;;N;;;;118D9; 118BA;WARANG CITI CAPITAL LETTER HOLO;Lu;0;L;;;;;N;;;;118DA; 118BB;WARANG CITI CAPITAL LETTER HORR;Lu;0;L;;;;;N;;;;118DB; 118BC;WARANG CITI CAPITAL LETTER HAR;Lu;0;L;;;;;N;;;;118DC; 118BD;WARANG CITI CAPITAL LETTER SSUU;Lu;0;L;;;;;N;;;;118DD; 118BE;WARANG CITI CAPITAL LETTER SII;Lu;0;L;;;;;N;;;;118DE; 118BF;WARANG CITI CAPITAL LETTER VIYO;Lu;0;L;;;;;N;;;;118DF; 118C0;WARANG CITI SMALL LETTER NGAA;Ll;0;L;;;;;N;;;118A0;;118A0 118C1;WARANG CITI SMALL LETTER A;Ll;0;L;;;;;N;;;118A1;;118A1 118C2;WARANG CITI SMALL LETTER WI;Ll;0;L;;;;;N;;;118A2;;118A2 118C3;WARANG CITI SMALL LETTER YU;Ll;0;L;;;;;N;;;118A3;;118A3 118C4;WARANG CITI SMALL LETTER YA;Ll;0;L;;;;;N;;;118A4;;118A4 118C5;WARANG CITI SMALL LETTER YO;Ll;0;L;;;;;N;;;118A5;;118A5 118C6;WARANG CITI SMALL LETTER II;Ll;0;L;;;;;N;;;118A6;;118A6 118C7;WARANG CITI SMALL LETTER UU;Ll;0;L;;;;;N;;;118A7;;118A7 118C8;WARANG CITI SMALL LETTER E;Ll;0;L;;;;;N;;;118A8;;118A8 118C9;WARANG CITI SMALL LETTER O;Ll;0;L;;;;;N;;;118A9;;118A9 118CA;WARANG CITI SMALL LETTER ANG;Ll;0;L;;;;;N;;;118AA;;118AA 118CB;WARANG CITI SMALL LETTER GA;Ll;0;L;;;;;N;;;118AB;;118AB 118CC;WARANG CITI SMALL LETTER KO;Ll;0;L;;;;;N;;;118AC;;118AC 118CD;WARANG CITI SMALL LETTER ENY;Ll;0;L;;;;;N;;;118AD;;118AD 118CE;WARANG CITI SMALL LETTER YUJ;Ll;0;L;;;;;N;;;118AE;;118AE 118CF;WARANG CITI SMALL LETTER UC;Ll;0;L;;;;;N;;;118AF;;118AF 118D0;WARANG CITI SMALL LETTER ENN;Ll;0;L;;;;;N;;;118B0;;118B0 118D1;WARANG CITI SMALL LETTER ODD;Ll;0;L;;;;;N;;;118B1;;118B1 118D2;WARANG CITI SMALL LETTER TTE;Ll;0;L;;;;;N;;;118B2;;118B2 118D3;WARANG CITI SMALL LETTER NUNG;Ll;0;L;;;;;N;;;118B3;;118B3 118D4;WARANG CITI SMALL LETTER DA;Ll;0;L;;;;;N;;;118B4;;118B4 118D5;WARANG CITI SMALL LETTER AT;Ll;0;L;;;;;N;;;118B5;;118B5 118D6;WARANG CITI SMALL LETTER AM;Ll;0;L;;;;;N;;;118B6;;118B6 118D7;WARANG CITI SMALL LETTER BU;Ll;0;L;;;;;N;;;118B7;;118B7 118D8;WARANG CITI SMALL LETTER PU;Ll;0;L;;;;;N;;;118B8;;118B8 118D9;WARANG CITI SMALL LETTER HIYO;Ll;0;L;;;;;N;;;118B9;;118B9 118DA;WARANG CITI SMALL LETTER HOLO;Ll;0;L;;;;;N;;;118BA;;118BA 118DB;WARANG CITI SMALL LETTER HORR;Ll;0;L;;;;;N;;;118BB;;118BB 118DC;WARANG CITI SMALL LETTER HAR;Ll;0;L;;;;;N;;;118BC;;118BC 118DD;WARANG CITI SMALL LETTER SSUU;Ll;0;L;;;;;N;;;118BD;;118BD 118DE;WARANG CITI SMALL LETTER SII;Ll;0;L;;;;;N;;;118BE;;118BE 118DF;WARANG CITI SMALL LETTER VIYO;Ll;0;L;;;;;N;;;118BF;;118BF 118E0;WARANG CITI DIGIT ZERO;Nd;0;L;;0;0;0;N;;;;; 118E1;WARANG CITI DIGIT ONE;Nd;0;L;;1;1;1;N;;;;; 118E2;WARANG CITI DIGIT TWO;Nd;0;L;;2;2;2;N;;;;; 118E3;WARANG CITI DIGIT THREE;Nd;0;L;;3;3;3;N;;;;; 118E4;WARANG CITI DIGIT FOUR;Nd;0;L;;4;4;4;N;;;;; 118E5;WARANG CITI DIGIT FIVE;Nd;0;L;;5;5;5;N;;;;; 118E6;WARANG CITI DIGIT SIX;Nd;0;L;;6;6;6;N;;;;; 118E7;WARANG CITI DIGIT SEVEN;Nd;0;L;;7;7;7;N;;;;; 118E8;WARANG CITI DIGIT EIGHT;Nd;0;L;;8;8;8;N;;;;; 118E9;WARANG CITI DIGIT NINE;Nd;0;L;;9;9;9;N;;;;; 118EA;WARANG CITI NUMBER TEN;No;0;L;;;;10;N;;;;; 118EB;WARANG CITI NUMBER TWENTY;No;0;L;;;;20;N;;;;; 118EC;WARANG CITI NUMBER THIRTY;No;0;L;;;;30;N;;;;; 118ED;WARANG CITI NUMBER FORTY;No;0;L;;;;40;N;;;;; 118EE;WARANG CITI NUMBER FIFTY;No;0;L;;;;50;N;;;;; 118EF;WARANG CITI NUMBER SIXTY;No;0;L;;;;60;N;;;;; 118F0;WARANG CITI NUMBER SEVENTY;No;0;L;;;;70;N;;;;; 118F1;WARANG CITI NUMBER EIGHTY;No;0;L;;;;80;N;;;;; 118F2;WARANG CITI NUMBER NINETY;No;0;L;;;;90;N;;;;; 118FF;WARANG CITI OM;Lo;0;L;;;;;N;;;;; 11AC0;PAU CIN HAU LETTER PA;Lo;0;L;;;;;N;;;;; 11AC1;PAU CIN HAU LETTER KA;Lo;0;L;;;;;N;;;;; 11AC2;PAU CIN HAU LETTER LA;Lo;0;L;;;;;N;;;;; 11AC3;PAU CIN HAU LETTER MA;Lo;0;L;;;;;N;;;;; 11AC4;PAU CIN HAU LETTER DA;Lo;0;L;;;;;N;;;;; 11AC5;PAU CIN HAU LETTER ZA;Lo;0;L;;;;;N;;;;; 11AC6;PAU CIN HAU LETTER VA;Lo;0;L;;;;;N;;;;; 11AC7;PAU CIN HAU LETTER NGA;Lo;0;L;;;;;N;;;;; 11AC8;PAU CIN HAU LETTER HA;Lo;0;L;;;;;N;;;;; 11AC9;PAU CIN HAU LETTER GA;Lo;0;L;;;;;N;;;;; 11ACA;PAU CIN HAU LETTER KHA;Lo;0;L;;;;;N;;;;; 11ACB;PAU CIN HAU LETTER SA;Lo;0;L;;;;;N;;;;; 11ACC;PAU CIN HAU LETTER BA;Lo;0;L;;;;;N;;;;; 11ACD;PAU CIN HAU LETTER CA;Lo;0;L;;;;;N;;;;; 11ACE;PAU CIN HAU LETTER TA;Lo;0;L;;;;;N;;;;; 11ACF;PAU CIN HAU LETTER THA;Lo;0;L;;;;;N;;;;; 11AD0;PAU CIN HAU LETTER NA;Lo;0;L;;;;;N;;;;; 11AD1;PAU CIN HAU LETTER PHA;Lo;0;L;;;;;N;;;;; 11AD2;PAU CIN HAU LETTER RA;Lo;0;L;;;;;N;;;;; 11AD3;PAU CIN HAU LETTER FA;Lo;0;L;;;;;N;;;;; 11AD4;PAU CIN HAU LETTER CHA;Lo;0;L;;;;;N;;;;; 11AD5;PAU CIN HAU LETTER A;Lo;0;L;;;;;N;;;;; 11AD6;PAU CIN HAU LETTER E;Lo;0;L;;;;;N;;;;; 11AD7;PAU CIN HAU LETTER I;Lo;0;L;;;;;N;;;;; 11AD8;PAU CIN HAU LETTER O;Lo;0;L;;;;;N;;;;; 11AD9;PAU CIN HAU LETTER U;Lo;0;L;;;;;N;;;;; 11ADA;PAU CIN HAU LETTER UA;Lo;0;L;;;;;N;;;;; 11ADB;PAU CIN HAU LETTER IA;Lo;0;L;;;;;N;;;;; 11ADC;PAU CIN HAU LETTER FINAL P;Lo;0;L;;;;;N;;;;; 11ADD;PAU CIN HAU LETTER FINAL K;Lo;0;L;;;;;N;;;;; 11ADE;PAU CIN HAU LETTER FINAL T;Lo;0;L;;;;;N;;;;; 11ADF;PAU CIN HAU LETTER FINAL M;Lo;0;L;;;;;N;;;;; 11AE0;PAU CIN HAU LETTER FINAL N;Lo;0;L;;;;;N;;;;; 11AE1;PAU CIN HAU LETTER FINAL L;Lo;0;L;;;;;N;;;;; 11AE2;PAU CIN HAU LETTER FINAL W;Lo;0;L;;;;;N;;;;; 11AE3;PAU CIN HAU LETTER FINAL NG;Lo;0;L;;;;;N;;;;; 11AE4;PAU CIN HAU LETTER FINAL Y;Lo;0;L;;;;;N;;;;; 11AE5;PAU CIN HAU RISING TONE LONG;Lo;0;L;;;;;N;;;;; 11AE6;PAU CIN HAU RISING TONE;Lo;0;L;;;;;N;;;;; 11AE7;PAU CIN HAU SANDHI GLOTTAL STOP;Lo;0;L;;;;;N;;;;; 11AE8;PAU CIN HAU RISING TONE LONG FINAL;Lo;0;L;;;;;N;;;;; 11AE9;PAU CIN HAU RISING TONE FINAL;Lo;0;L;;;;;N;;;;; 11AEA;PAU CIN HAU SANDHI GLOTTAL STOP FINAL;Lo;0;L;;;;;N;;;;; 11AEB;PAU CIN HAU SANDHI TONE LONG;Lo;0;L;;;;;N;;;;; 11AEC;PAU CIN HAU SANDHI TONE;Lo;0;L;;;;;N;;;;; 11AED;PAU CIN HAU SANDHI TONE LONG FINAL;Lo;0;L;;;;;N;;;;; 11AEE;PAU CIN HAU SANDHI TONE FINAL;Lo;0;L;;;;;N;;;;; 11AEF;PAU CIN HAU MID-LEVEL TONE;Lo;0;L;;;;;N;;;;; 11AF0;PAU CIN HAU GLOTTAL STOP VARIANT;Lo;0;L;;;;;N;;;;; 11AF1;PAU CIN HAU MID-LEVEL TONE LONG FINAL;Lo;0;L;;;;;N;;;;; 11AF2;PAU CIN HAU MID-LEVEL TONE FINAL;Lo;0;L;;;;;N;;;;; 11AF3;PAU CIN HAU LOW-FALLING TONE LONG;Lo;0;L;;;;;N;;;;; 11AF4;PAU CIN HAU LOW-FALLING TONE;Lo;0;L;;;;;N;;;;; 11AF5;PAU CIN HAU GLOTTAL STOP;Lo;0;L;;;;;N;;;;; 11AF6;PAU CIN HAU LOW-FALLING TONE LONG FINAL;Lo;0;L;;;;;N;;;;; 11AF7;PAU CIN HAU LOW-FALLING TONE FINAL;Lo;0;L;;;;;N;;;;; 11AF8;PAU CIN HAU GLOTTAL STOP FINAL;Lo;0;L;;;;;N;;;;; 12000;CUNEIFORM SIGN A;Lo;0;L;;;;;N;;;;; 12001;CUNEIFORM SIGN A TIMES A;Lo;0;L;;;;;N;;;;; 12002;CUNEIFORM SIGN A TIMES BAD;Lo;0;L;;;;;N;;;;; 12003;CUNEIFORM SIGN A TIMES GAN2 TENU;Lo;0;L;;;;;N;;;;; 12004;CUNEIFORM SIGN A TIMES HA;Lo;0;L;;;;;N;;;;; 12005;CUNEIFORM SIGN A TIMES IGI;Lo;0;L;;;;;N;;;;; 12006;CUNEIFORM SIGN A TIMES LAGAR GUNU;Lo;0;L;;;;;N;;;;; 12007;CUNEIFORM SIGN A TIMES MUSH;Lo;0;L;;;;;N;;;;; 12008;CUNEIFORM SIGN A TIMES SAG;Lo;0;L;;;;;N;;;;; 12009;CUNEIFORM SIGN A2;Lo;0;L;;;;;N;;;;; 1200A;CUNEIFORM SIGN AB;Lo;0;L;;;;;N;;;;; 1200B;CUNEIFORM SIGN AB TIMES ASH2;Lo;0;L;;;;;N;;;;; 1200C;CUNEIFORM SIGN AB TIMES DUN3 GUNU;Lo;0;L;;;;;N;;;;; 1200D;CUNEIFORM SIGN AB TIMES GAL;Lo;0;L;;;;;N;;;;; 1200E;CUNEIFORM SIGN AB TIMES GAN2 TENU;Lo;0;L;;;;;N;;;;; 1200F;CUNEIFORM SIGN AB TIMES HA;Lo;0;L;;;;;N;;;;; 12010;CUNEIFORM SIGN AB TIMES IGI GUNU;Lo;0;L;;;;;N;;;;; 12011;CUNEIFORM SIGN AB TIMES IMIN;Lo;0;L;;;;;N;;;;; 12012;CUNEIFORM SIGN AB TIMES LAGAB;Lo;0;L;;;;;N;;;;; 12013;CUNEIFORM SIGN AB TIMES SHESH;Lo;0;L;;;;;N;;;;; 12014;CUNEIFORM SIGN AB TIMES U PLUS U PLUS U;Lo;0;L;;;;;N;;;;; 12015;CUNEIFORM SIGN AB GUNU;Lo;0;L;;;;;N;;;;; 12016;CUNEIFORM SIGN AB2;Lo;0;L;;;;;N;;;;; 12017;CUNEIFORM SIGN AB2 TIMES BALAG;Lo;0;L;;;;;N;;;;; 12018;CUNEIFORM SIGN AB2 TIMES GAN2 TENU;Lo;0;L;;;;;N;;;;; 12019;CUNEIFORM SIGN AB2 TIMES ME PLUS EN;Lo;0;L;;;;;N;;;;; 1201A;CUNEIFORM SIGN AB2 TIMES SHA3;Lo;0;L;;;;;N;;;;; 1201B;CUNEIFORM SIGN AB2 TIMES TAK4;Lo;0;L;;;;;N;;;;; 1201C;CUNEIFORM SIGN AD;Lo;0;L;;;;;N;;;;; 1201D;CUNEIFORM SIGN AK;Lo;0;L;;;;;N;;;;; 1201E;CUNEIFORM SIGN AK TIMES ERIN2;Lo;0;L;;;;;N;;;;; 1201F;CUNEIFORM SIGN AK TIMES SHITA PLUS GISH;Lo;0;L;;;;;N;;;;; 12020;CUNEIFORM SIGN AL;Lo;0;L;;;;;N;;;;; 12021;CUNEIFORM SIGN AL TIMES AL;Lo;0;L;;;;;N;;;;; 12022;CUNEIFORM SIGN AL TIMES DIM2;Lo;0;L;;;;;N;;;;; 12023;CUNEIFORM SIGN AL TIMES GISH;Lo;0;L;;;;;N;;;;; 12024;CUNEIFORM SIGN AL TIMES HA;Lo;0;L;;;;;N;;;;; 12025;CUNEIFORM SIGN AL TIMES KAD3;Lo;0;L;;;;;N;;;;; 12026;CUNEIFORM SIGN AL TIMES KI;Lo;0;L;;;;;N;;;;; 12027;CUNEIFORM SIGN AL TIMES SHE;Lo;0;L;;;;;N;;;;; 12028;CUNEIFORM SIGN AL TIMES USH;Lo;0;L;;;;;N;;;;; 12029;CUNEIFORM SIGN ALAN;Lo;0;L;;;;;N;;;;; 1202A;CUNEIFORM SIGN ALEPH;Lo;0;L;;;;;N;;;;; 1202B;CUNEIFORM SIGN AMAR;Lo;0;L;;;;;N;;;;; 1202C;CUNEIFORM SIGN AMAR TIMES SHE;Lo;0;L;;;;;N;;;;; 1202D;CUNEIFORM SIGN AN;Lo;0;L;;;;;N;;;;; 1202E;CUNEIFORM SIGN AN OVER AN;Lo;0;L;;;;;N;;;;; 1202F;CUNEIFORM SIGN AN THREE TIMES;Lo;0;L;;;;;N;;;;; 12030;CUNEIFORM SIGN AN PLUS NAGA OPPOSING AN PLUS NAGA;Lo;0;L;;;;;N;;;;; 12031;CUNEIFORM SIGN AN PLUS NAGA SQUARED;Lo;0;L;;;;;N;;;;; 12032;CUNEIFORM SIGN ANSHE;Lo;0;L;;;;;N;;;;; 12033;CUNEIFORM SIGN APIN;Lo;0;L;;;;;N;;;;; 12034;CUNEIFORM SIGN ARAD;Lo;0;L;;;;;N;;;;; 12035;CUNEIFORM SIGN ARAD TIMES KUR;Lo;0;L;;;;;N;;;;; 12036;CUNEIFORM SIGN ARKAB;Lo;0;L;;;;;N;;;;; 12037;CUNEIFORM SIGN ASAL2;Lo;0;L;;;;;N;;;;; 12038;CUNEIFORM SIGN ASH;Lo;0;L;;;;;N;;;;; 12039;CUNEIFORM SIGN ASH ZIDA TENU;Lo;0;L;;;;;N;;;;; 1203A;CUNEIFORM SIGN ASH KABA TENU;Lo;0;L;;;;;N;;;;; 1203B;CUNEIFORM SIGN ASH OVER ASH TUG2 OVER TUG2 TUG2 OVER TUG2 PAP;Lo;0;L;;;;;N;;;;; 1203C;CUNEIFORM SIGN ASH OVER ASH OVER ASH;Lo;0;L;;;;;N;;;;; 1203D;CUNEIFORM SIGN ASH OVER ASH OVER ASH CROSSING ASH OVER ASH OVER ASH;Lo;0;L;;;;;N;;;;; 1203E;CUNEIFORM SIGN ASH2;Lo;0;L;;;;;N;;;;; 1203F;CUNEIFORM SIGN ASHGAB;Lo;0;L;;;;;N;;;;; 12040;CUNEIFORM SIGN BA;Lo;0;L;;;;;N;;;;; 12041;CUNEIFORM SIGN BAD;Lo;0;L;;;;;N;;;;; 12042;CUNEIFORM SIGN BAG3;Lo;0;L;;;;;N;;;;; 12043;CUNEIFORM SIGN BAHAR2;Lo;0;L;;;;;N;;;;; 12044;CUNEIFORM SIGN BAL;Lo;0;L;;;;;N;;;;; 12045;CUNEIFORM SIGN BAL OVER BAL;Lo;0;L;;;;;N;;;;; 12046;CUNEIFORM SIGN BALAG;Lo;0;L;;;;;N;;;;; 12047;CUNEIFORM SIGN BAR;Lo;0;L;;;;;N;;;;; 12048;CUNEIFORM SIGN BARA2;Lo;0;L;;;;;N;;;;; 12049;CUNEIFORM SIGN BI;Lo;0;L;;;;;N;;;;; 1204A;CUNEIFORM SIGN BI TIMES A;Lo;0;L;;;;;N;;;;; 1204B;CUNEIFORM SIGN BI TIMES GAR;Lo;0;L;;;;;N;;;;; 1204C;CUNEIFORM SIGN BI TIMES IGI GUNU;Lo;0;L;;;;;N;;;;; 1204D;CUNEIFORM SIGN BU;Lo;0;L;;;;;N;;;;; 1204E;CUNEIFORM SIGN BU OVER BU AB;Lo;0;L;;;;;N;;;;; 1204F;CUNEIFORM SIGN BU OVER BU UN;Lo;0;L;;;;;N;;;;; 12050;CUNEIFORM SIGN BU CROSSING BU;Lo;0;L;;;;;N;;;;; 12051;CUNEIFORM SIGN BULUG;Lo;0;L;;;;;N;;;;; 12052;CUNEIFORM SIGN BULUG OVER BULUG;Lo;0;L;;;;;N;;;;; 12053;CUNEIFORM SIGN BUR;Lo;0;L;;;;;N;;;;; 12054;CUNEIFORM SIGN BUR2;Lo;0;L;;;;;N;;;;; 12055;CUNEIFORM SIGN DA;Lo;0;L;;;;;N;;;;; 12056;CUNEIFORM SIGN DAG;Lo;0;L;;;;;N;;;;; 12057;CUNEIFORM SIGN DAG KISIM5 TIMES A PLUS MASH;Lo;0;L;;;;;N;;;;; 12058;CUNEIFORM SIGN DAG KISIM5 TIMES AMAR;Lo;0;L;;;;;N;;;;; 12059;CUNEIFORM SIGN DAG KISIM5 TIMES BALAG;Lo;0;L;;;;;N;;;;; 1205A;CUNEIFORM SIGN DAG KISIM5 TIMES BI;Lo;0;L;;;;;N;;;;; 1205B;CUNEIFORM SIGN DAG KISIM5 TIMES GA;Lo;0;L;;;;;N;;;;; 1205C;CUNEIFORM SIGN DAG KISIM5 TIMES GA PLUS MASH;Lo;0;L;;;;;N;;;;; 1205D;CUNEIFORM SIGN DAG KISIM5 TIMES GI;Lo;0;L;;;;;N;;;;; 1205E;CUNEIFORM SIGN DAG KISIM5 TIMES GIR2;Lo;0;L;;;;;N;;;;; 1205F;CUNEIFORM SIGN DAG KISIM5 TIMES GUD;Lo;0;L;;;;;N;;;;; 12060;CUNEIFORM SIGN DAG KISIM5 TIMES HA;Lo;0;L;;;;;N;;;;; 12061;CUNEIFORM SIGN DAG KISIM5 TIMES IR;Lo;0;L;;;;;N;;;;; 12062;CUNEIFORM SIGN DAG KISIM5 TIMES IR PLUS LU;Lo;0;L;;;;;N;;;;; 12063;CUNEIFORM SIGN DAG KISIM5 TIMES KAK;Lo;0;L;;;;;N;;;;; 12064;CUNEIFORM SIGN DAG KISIM5 TIMES LA;Lo;0;L;;;;;N;;;;; 12065;CUNEIFORM SIGN DAG KISIM5 TIMES LU;Lo;0;L;;;;;N;;;;; 12066;CUNEIFORM SIGN DAG KISIM5 TIMES LU PLUS MASH2;Lo;0;L;;;;;N;;;;; 12067;CUNEIFORM SIGN DAG KISIM5 TIMES LUM;Lo;0;L;;;;;N;;;;; 12068;CUNEIFORM SIGN DAG KISIM5 TIMES NE;Lo;0;L;;;;;N;;;;; 12069;CUNEIFORM SIGN DAG KISIM5 TIMES PAP PLUS PAP;Lo;0;L;;;;;N;;;;; 1206A;CUNEIFORM SIGN DAG KISIM5 TIMES SI;Lo;0;L;;;;;N;;;;; 1206B;CUNEIFORM SIGN DAG KISIM5 TIMES TAK4;Lo;0;L;;;;;N;;;;; 1206C;CUNEIFORM SIGN DAG KISIM5 TIMES U2 PLUS GIR2;Lo;0;L;;;;;N;;;;; 1206D;CUNEIFORM SIGN DAG KISIM5 TIMES USH;Lo;0;L;;;;;N;;;;; 1206E;CUNEIFORM SIGN DAM;Lo;0;L;;;;;N;;;;; 1206F;CUNEIFORM SIGN DAR;Lo;0;L;;;;;N;;;;; 12070;CUNEIFORM SIGN DARA3;Lo;0;L;;;;;N;;;;; 12071;CUNEIFORM SIGN DARA4;Lo;0;L;;;;;N;;;;; 12072;CUNEIFORM SIGN DI;Lo;0;L;;;;;N;;;;; 12073;CUNEIFORM SIGN DIB;Lo;0;L;;;;;N;;;;; 12074;CUNEIFORM SIGN DIM;Lo;0;L;;;;;N;;;;; 12075;CUNEIFORM SIGN DIM TIMES SHE;Lo;0;L;;;;;N;;;;; 12076;CUNEIFORM SIGN DIM2;Lo;0;L;;;;;N;;;;; 12077;CUNEIFORM SIGN DIN;Lo;0;L;;;;;N;;;;; 12078;CUNEIFORM SIGN DIN KASKAL U GUNU DISH;Lo;0;L;;;;;N;;;;; 12079;CUNEIFORM SIGN DISH;Lo;0;L;;;;;N;;;;; 1207A;CUNEIFORM SIGN DU;Lo;0;L;;;;;N;;;;; 1207B;CUNEIFORM SIGN DU OVER DU;Lo;0;L;;;;;N;;;;; 1207C;CUNEIFORM SIGN DU GUNU;Lo;0;L;;;;;N;;;;; 1207D;CUNEIFORM SIGN DU SHESHIG;Lo;0;L;;;;;N;;;;; 1207E;CUNEIFORM SIGN DUB;Lo;0;L;;;;;N;;;;; 1207F;CUNEIFORM SIGN DUB TIMES ESH2;Lo;0;L;;;;;N;;;;; 12080;CUNEIFORM SIGN DUB2;Lo;0;L;;;;;N;;;;; 12081;CUNEIFORM SIGN DUG;Lo;0;L;;;;;N;;;;; 12082;CUNEIFORM SIGN DUGUD;Lo;0;L;;;;;N;;;;; 12083;CUNEIFORM SIGN DUH;Lo;0;L;;;;;N;;;;; 12084;CUNEIFORM SIGN DUN;Lo;0;L;;;;;N;;;;; 12085;CUNEIFORM SIGN DUN3;Lo;0;L;;;;;N;;;;; 12086;CUNEIFORM SIGN DUN3 GUNU;Lo;0;L;;;;;N;;;;; 12087;CUNEIFORM SIGN DUN3 GUNU GUNU;Lo;0;L;;;;;N;;;;; 12088;CUNEIFORM SIGN DUN4;Lo;0;L;;;;;N;;;;; 12089;CUNEIFORM SIGN DUR2;Lo;0;L;;;;;N;;;;; 1208A;CUNEIFORM SIGN E;Lo;0;L;;;;;N;;;;; 1208B;CUNEIFORM SIGN E TIMES PAP;Lo;0;L;;;;;N;;;;; 1208C;CUNEIFORM SIGN E OVER E NUN OVER NUN;Lo;0;L;;;;;N;;;;; 1208D;CUNEIFORM SIGN E2;Lo;0;L;;;;;N;;;;; 1208E;CUNEIFORM SIGN E2 TIMES A PLUS HA PLUS DA;Lo;0;L;;;;;N;;;;; 1208F;CUNEIFORM SIGN E2 TIMES GAR;Lo;0;L;;;;;N;;;;; 12090;CUNEIFORM SIGN E2 TIMES MI;Lo;0;L;;;;;N;;;;; 12091;CUNEIFORM SIGN E2 TIMES SAL;Lo;0;L;;;;;N;;;;; 12092;CUNEIFORM SIGN E2 TIMES SHE;Lo;0;L;;;;;N;;;;; 12093;CUNEIFORM SIGN E2 TIMES U;Lo;0;L;;;;;N;;;;; 12094;CUNEIFORM SIGN EDIN;Lo;0;L;;;;;N;;;;; 12095;CUNEIFORM SIGN EGIR;Lo;0;L;;;;;N;;;;; 12096;CUNEIFORM SIGN EL;Lo;0;L;;;;;N;;;;; 12097;CUNEIFORM SIGN EN;Lo;0;L;;;;;N;;;;; 12098;CUNEIFORM SIGN EN TIMES GAN2;Lo;0;L;;;;;N;;;;; 12099;CUNEIFORM SIGN EN TIMES GAN2 TENU;Lo;0;L;;;;;N;;;;; 1209A;CUNEIFORM SIGN EN TIMES ME;Lo;0;L;;;;;N;;;;; 1209B;CUNEIFORM SIGN EN CROSSING EN;Lo;0;L;;;;;N;;;;; 1209C;CUNEIFORM SIGN EN OPPOSING EN;Lo;0;L;;;;;N;;;;; 1209D;CUNEIFORM SIGN EN SQUARED;Lo;0;L;;;;;N;;;;; 1209E;CUNEIFORM SIGN EREN;Lo;0;L;;;;;N;;;;; 1209F;CUNEIFORM SIGN ERIN2;Lo;0;L;;;;;N;;;;; 120A0;CUNEIFORM SIGN ESH2;Lo;0;L;;;;;N;;;;; 120A1;CUNEIFORM SIGN EZEN;Lo;0;L;;;;;N;;;;; 120A2;CUNEIFORM SIGN EZEN TIMES A;Lo;0;L;;;;;N;;;;; 120A3;CUNEIFORM SIGN EZEN TIMES A PLUS LAL;Lo;0;L;;;;;N;;;;; 120A4;CUNEIFORM SIGN EZEN TIMES A PLUS LAL TIMES LAL;Lo;0;L;;;;;N;;;;; 120A5;CUNEIFORM SIGN EZEN TIMES AN;Lo;0;L;;;;;N;;;;; 120A6;CUNEIFORM SIGN EZEN TIMES BAD;Lo;0;L;;;;;N;;;;; 120A7;CUNEIFORM SIGN EZEN TIMES DUN3 GUNU;Lo;0;L;;;;;N;;;;; 120A8;CUNEIFORM SIGN EZEN TIMES DUN3 GUNU GUNU;Lo;0;L;;;;;N;;;;; 120A9;CUNEIFORM SIGN EZEN TIMES HA;Lo;0;L;;;;;N;;;;; 120AA;CUNEIFORM SIGN EZEN TIMES HA GUNU;Lo;0;L;;;;;N;;;;; 120AB;CUNEIFORM SIGN EZEN TIMES IGI GUNU;Lo;0;L;;;;;N;;;;; 120AC;CUNEIFORM SIGN EZEN TIMES KASKAL;Lo;0;L;;;;;N;;;;; 120AD;CUNEIFORM SIGN EZEN TIMES KASKAL SQUARED;Lo;0;L;;;;;N;;;;; 120AE;CUNEIFORM SIGN EZEN TIMES KU3;Lo;0;L;;;;;N;;;;; 120AF;CUNEIFORM SIGN EZEN TIMES LA;Lo;0;L;;;;;N;;;;; 120B0;CUNEIFORM SIGN EZEN TIMES LAL TIMES LAL;Lo;0;L;;;;;N;;;;; 120B1;CUNEIFORM SIGN EZEN TIMES LI;Lo;0;L;;;;;N;;;;; 120B2;CUNEIFORM SIGN EZEN TIMES LU;Lo;0;L;;;;;N;;;;; 120B3;CUNEIFORM SIGN EZEN TIMES U2;Lo;0;L;;;;;N;;;;; 120B4;CUNEIFORM SIGN EZEN TIMES UD;Lo;0;L;;;;;N;;;;; 120B5;CUNEIFORM SIGN GA;Lo;0;L;;;;;N;;;;; 120B6;CUNEIFORM SIGN GA GUNU;Lo;0;L;;;;;N;;;;; 120B7;CUNEIFORM SIGN GA2;Lo;0;L;;;;;N;;;;; 120B8;CUNEIFORM SIGN GA2 TIMES A PLUS DA PLUS HA;Lo;0;L;;;;;N;;;;; 120B9;CUNEIFORM SIGN GA2 TIMES A PLUS HA;Lo;0;L;;;;;N;;;;; 120BA;CUNEIFORM SIGN GA2 TIMES A PLUS IGI;Lo;0;L;;;;;N;;;;; 120BB;CUNEIFORM SIGN GA2 TIMES AB2 TENU PLUS TAB;Lo;0;L;;;;;N;;;;; 120BC;CUNEIFORM SIGN GA2 TIMES AN;Lo;0;L;;;;;N;;;;; 120BD;CUNEIFORM SIGN GA2 TIMES ASH;Lo;0;L;;;;;N;;;;; 120BE;CUNEIFORM SIGN GA2 TIMES ASH2 PLUS GAL;Lo;0;L;;;;;N;;;;; 120BF;CUNEIFORM SIGN GA2 TIMES BAD;Lo;0;L;;;;;N;;;;; 120C0;CUNEIFORM SIGN GA2 TIMES BAR PLUS RA;Lo;0;L;;;;;N;;;;; 120C1;CUNEIFORM SIGN GA2 TIMES BUR;Lo;0;L;;;;;N;;;;; 120C2;CUNEIFORM SIGN GA2 TIMES BUR PLUS RA;Lo;0;L;;;;;N;;;;; 120C3;CUNEIFORM SIGN GA2 TIMES DA;Lo;0;L;;;;;N;;;;; 120C4;CUNEIFORM SIGN GA2 TIMES DI;Lo;0;L;;;;;N;;;;; 120C5;CUNEIFORM SIGN GA2 TIMES DIM TIMES SHE;Lo;0;L;;;;;N;;;;; 120C6;CUNEIFORM SIGN GA2 TIMES DUB;Lo;0;L;;;;;N;;;;; 120C7;CUNEIFORM SIGN GA2 TIMES EL;Lo;0;L;;;;;N;;;;; 120C8;CUNEIFORM SIGN GA2 TIMES EL PLUS LA;Lo;0;L;;;;;N;;;;; 120C9;CUNEIFORM SIGN GA2 TIMES EN;Lo;0;L;;;;;N;;;;; 120CA;CUNEIFORM SIGN GA2 TIMES EN TIMES GAN2 TENU;Lo;0;L;;;;;N;;;;; 120CB;CUNEIFORM SIGN GA2 TIMES GAN2 TENU;Lo;0;L;;;;;N;;;;; 120CC;CUNEIFORM SIGN GA2 TIMES GAR;Lo;0;L;;;;;N;;;;; 120CD;CUNEIFORM SIGN GA2 TIMES GI;Lo;0;L;;;;;N;;;;; 120CE;CUNEIFORM SIGN GA2 TIMES GI4;Lo;0;L;;;;;N;;;;; 120CF;CUNEIFORM SIGN GA2 TIMES GI4 PLUS A;Lo;0;L;;;;;N;;;;; 120D0;CUNEIFORM SIGN GA2 TIMES GIR2 PLUS SU;Lo;0;L;;;;;N;;;;; 120D1;CUNEIFORM SIGN GA2 TIMES HA PLUS LU PLUS ESH2;Lo;0;L;;;;;N;;;;; 120D2;CUNEIFORM SIGN GA2 TIMES HAL;Lo;0;L;;;;;N;;;;; 120D3;CUNEIFORM SIGN GA2 TIMES HAL PLUS LA;Lo;0;L;;;;;N;;;;; 120D4;CUNEIFORM SIGN GA2 TIMES HI PLUS LI;Lo;0;L;;;;;N;;;;; 120D5;CUNEIFORM SIGN GA2 TIMES HUB2;Lo;0;L;;;;;N;;;;; 120D6;CUNEIFORM SIGN GA2 TIMES IGI GUNU;Lo;0;L;;;;;N;;;;; 120D7;CUNEIFORM SIGN GA2 TIMES ISH PLUS HU PLUS ASH;Lo;0;L;;;;;N;;;;; 120D8;CUNEIFORM SIGN GA2 TIMES KAK;Lo;0;L;;;;;N;;;;; 120D9;CUNEIFORM SIGN GA2 TIMES KASKAL;Lo;0;L;;;;;N;;;;; 120DA;CUNEIFORM SIGN GA2 TIMES KID;Lo;0;L;;;;;N;;;;; 120DB;CUNEIFORM SIGN GA2 TIMES KID PLUS LAL;Lo;0;L;;;;;N;;;;; 120DC;CUNEIFORM SIGN GA2 TIMES KU3 PLUS AN;Lo;0;L;;;;;N;;;;; 120DD;CUNEIFORM SIGN GA2 TIMES LA;Lo;0;L;;;;;N;;;;; 120DE;CUNEIFORM SIGN GA2 TIMES ME PLUS EN;Lo;0;L;;;;;N;;;;; 120DF;CUNEIFORM SIGN GA2 TIMES MI;Lo;0;L;;;;;N;;;;; 120E0;CUNEIFORM SIGN GA2 TIMES NUN;Lo;0;L;;;;;N;;;;; 120E1;CUNEIFORM SIGN GA2 TIMES NUN OVER NUN;Lo;0;L;;;;;N;;;;; 120E2;CUNEIFORM SIGN GA2 TIMES PA;Lo;0;L;;;;;N;;;;; 120E3;CUNEIFORM SIGN GA2 TIMES SAL;Lo;0;L;;;;;N;;;;; 120E4;CUNEIFORM SIGN GA2 TIMES SAR;Lo;0;L;;;;;N;;;;; 120E5;CUNEIFORM SIGN GA2 TIMES SHE;Lo;0;L;;;;;N;;;;; 120E6;CUNEIFORM SIGN GA2 TIMES SHE PLUS TUR;Lo;0;L;;;;;N;;;;; 120E7;CUNEIFORM SIGN GA2 TIMES SHID;Lo;0;L;;;;;N;;;;; 120E8;CUNEIFORM SIGN GA2 TIMES SUM;Lo;0;L;;;;;N;;;;; 120E9;CUNEIFORM SIGN GA2 TIMES TAK4;Lo;0;L;;;;;N;;;;; 120EA;CUNEIFORM SIGN GA2 TIMES U;Lo;0;L;;;;;N;;;;; 120EB;CUNEIFORM SIGN GA2 TIMES UD;Lo;0;L;;;;;N;;;;; 120EC;CUNEIFORM SIGN GA2 TIMES UD PLUS DU;Lo;0;L;;;;;N;;;;; 120ED;CUNEIFORM SIGN GA2 OVER GA2;Lo;0;L;;;;;N;;;;; 120EE;CUNEIFORM SIGN GABA;Lo;0;L;;;;;N;;;;; 120EF;CUNEIFORM SIGN GABA CROSSING GABA;Lo;0;L;;;;;N;;;;; 120F0;CUNEIFORM SIGN GAD;Lo;0;L;;;;;N;;;;; 120F1;CUNEIFORM SIGN GAD OVER GAD GAR OVER GAR;Lo;0;L;;;;;N;;;;; 120F2;CUNEIFORM SIGN GAL;Lo;0;L;;;;;N;;;;; 120F3;CUNEIFORM SIGN GAL GAD OVER GAD GAR OVER GAR;Lo;0;L;;;;;N;;;;; 120F4;CUNEIFORM SIGN GALAM;Lo;0;L;;;;;N;;;;; 120F5;CUNEIFORM SIGN GAM;Lo;0;L;;;;;N;;;;; 120F6;CUNEIFORM SIGN GAN;Lo;0;L;;;;;N;;;;; 120F7;CUNEIFORM SIGN GAN2;Lo;0;L;;;;;N;;;;; 120F8;CUNEIFORM SIGN GAN2 TENU;Lo;0;L;;;;;N;;;;; 120F9;CUNEIFORM SIGN GAN2 OVER GAN2;Lo;0;L;;;;;N;;;;; 120FA;CUNEIFORM SIGN GAN2 CROSSING GAN2;Lo;0;L;;;;;N;;;;; 120FB;CUNEIFORM SIGN GAR;Lo;0;L;;;;;N;;;;; 120FC;CUNEIFORM SIGN GAR3;Lo;0;L;;;;;N;;;;; 120FD;CUNEIFORM SIGN GASHAN;Lo;0;L;;;;;N;;;;; 120FE;CUNEIFORM SIGN GESHTIN;Lo;0;L;;;;;N;;;;; 120FF;CUNEIFORM SIGN GESHTIN TIMES KUR;Lo;0;L;;;;;N;;;;; 12100;CUNEIFORM SIGN GI;Lo;0;L;;;;;N;;;;; 12101;CUNEIFORM SIGN GI TIMES E;Lo;0;L;;;;;N;;;;; 12102;CUNEIFORM SIGN GI TIMES U;Lo;0;L;;;;;N;;;;; 12103;CUNEIFORM SIGN GI CROSSING GI;Lo;0;L;;;;;N;;;;; 12104;CUNEIFORM SIGN GI4;Lo;0;L;;;;;N;;;;; 12105;CUNEIFORM SIGN GI4 OVER GI4;Lo;0;L;;;;;N;;;;; 12106;CUNEIFORM SIGN GI4 CROSSING GI4;Lo;0;L;;;;;N;;;;; 12107;CUNEIFORM SIGN GIDIM;Lo;0;L;;;;;N;;;;; 12108;CUNEIFORM SIGN GIR2;Lo;0;L;;;;;N;;;;; 12109;CUNEIFORM SIGN GIR2 GUNU;Lo;0;L;;;;;N;;;;; 1210A;CUNEIFORM SIGN GIR3;Lo;0;L;;;;;N;;;;; 1210B;CUNEIFORM SIGN GIR3 TIMES A PLUS IGI;Lo;0;L;;;;;N;;;;; 1210C;CUNEIFORM SIGN GIR3 TIMES GAN2 TENU;Lo;0;L;;;;;N;;;;; 1210D;CUNEIFORM SIGN GIR3 TIMES IGI;Lo;0;L;;;;;N;;;;; 1210E;CUNEIFORM SIGN GIR3 TIMES LU PLUS IGI;Lo;0;L;;;;;N;;;;; 1210F;CUNEIFORM SIGN GIR3 TIMES PA;Lo;0;L;;;;;N;;;;; 12110;CUNEIFORM SIGN GISAL;Lo;0;L;;;;;N;;;;; 12111;CUNEIFORM SIGN GISH;Lo;0;L;;;;;N;;;;; 12112;CUNEIFORM SIGN GISH CROSSING GISH;Lo;0;L;;;;;N;;;;; 12113;CUNEIFORM SIGN GISH TIMES BAD;Lo;0;L;;;;;N;;;;; 12114;CUNEIFORM SIGN GISH TIMES TAK4;Lo;0;L;;;;;N;;;;; 12115;CUNEIFORM SIGN GISH TENU;Lo;0;L;;;;;N;;;;; 12116;CUNEIFORM SIGN GU;Lo;0;L;;;;;N;;;;; 12117;CUNEIFORM SIGN GU CROSSING GU;Lo;0;L;;;;;N;;;;; 12118;CUNEIFORM SIGN GU2;Lo;0;L;;;;;N;;;;; 12119;CUNEIFORM SIGN GU2 TIMES KAK;Lo;0;L;;;;;N;;;;; 1211A;CUNEIFORM SIGN GU2 TIMES KAK TIMES IGI GUNU;Lo;0;L;;;;;N;;;;; 1211B;CUNEIFORM SIGN GU2 TIMES NUN;Lo;0;L;;;;;N;;;;; 1211C;CUNEIFORM SIGN GU2 TIMES SAL PLUS TUG2;Lo;0;L;;;;;N;;;;; 1211D;CUNEIFORM SIGN GU2 GUNU;Lo;0;L;;;;;N;;;;; 1211E;CUNEIFORM SIGN GUD;Lo;0;L;;;;;N;;;;; 1211F;CUNEIFORM SIGN GUD TIMES A PLUS KUR;Lo;0;L;;;;;N;;;;; 12120;CUNEIFORM SIGN GUD TIMES KUR;Lo;0;L;;;;;N;;;;; 12121;CUNEIFORM SIGN GUD OVER GUD LUGAL;Lo;0;L;;;;;N;;;;; 12122;CUNEIFORM SIGN GUL;Lo;0;L;;;;;N;;;;; 12123;CUNEIFORM SIGN GUM;Lo;0;L;;;;;N;;;;; 12124;CUNEIFORM SIGN GUM TIMES SHE;Lo;0;L;;;;;N;;;;; 12125;CUNEIFORM SIGN GUR;Lo;0;L;;;;;N;;;;; 12126;CUNEIFORM SIGN GUR7;Lo;0;L;;;;;N;;;;; 12127;CUNEIFORM SIGN GURUN;Lo;0;L;;;;;N;;;;; 12128;CUNEIFORM SIGN GURUSH;Lo;0;L;;;;;N;;;;; 12129;CUNEIFORM SIGN HA;Lo;0;L;;;;;N;;;;; 1212A;CUNEIFORM SIGN HA TENU;Lo;0;L;;;;;N;;;;; 1212B;CUNEIFORM SIGN HA GUNU;Lo;0;L;;;;;N;;;;; 1212C;CUNEIFORM SIGN HAL;Lo;0;L;;;;;N;;;;; 1212D;CUNEIFORM SIGN HI;Lo;0;L;;;;;N;;;;; 1212E;CUNEIFORM SIGN HI TIMES ASH;Lo;0;L;;;;;N;;;;; 1212F;CUNEIFORM SIGN HI TIMES ASH2;Lo;0;L;;;;;N;;;;; 12130;CUNEIFORM SIGN HI TIMES BAD;Lo;0;L;;;;;N;;;;; 12131;CUNEIFORM SIGN HI TIMES DISH;Lo;0;L;;;;;N;;;;; 12132;CUNEIFORM SIGN HI TIMES GAD;Lo;0;L;;;;;N;;;;; 12133;CUNEIFORM SIGN HI TIMES KIN;Lo;0;L;;;;;N;;;;; 12134;CUNEIFORM SIGN HI TIMES NUN;Lo;0;L;;;;;N;;;;; 12135;CUNEIFORM SIGN HI TIMES SHE;Lo;0;L;;;;;N;;;;; 12136;CUNEIFORM SIGN HI TIMES U;Lo;0;L;;;;;N;;;;; 12137;CUNEIFORM SIGN HU;Lo;0;L;;;;;N;;;;; 12138;CUNEIFORM SIGN HUB2;Lo;0;L;;;;;N;;;;; 12139;CUNEIFORM SIGN HUB2 TIMES AN;Lo;0;L;;;;;N;;;;; 1213A;CUNEIFORM SIGN HUB2 TIMES HAL;Lo;0;L;;;;;N;;;;; 1213B;CUNEIFORM SIGN HUB2 TIMES KASKAL;Lo;0;L;;;;;N;;;;; 1213C;CUNEIFORM SIGN HUB2 TIMES LISH;Lo;0;L;;;;;N;;;;; 1213D;CUNEIFORM SIGN HUB2 TIMES UD;Lo;0;L;;;;;N;;;;; 1213E;CUNEIFORM SIGN HUL2;Lo;0;L;;;;;N;;;;; 1213F;CUNEIFORM SIGN I;Lo;0;L;;;;;N;;;;; 12140;CUNEIFORM SIGN I A;Lo;0;L;;;;;N;;;;; 12141;CUNEIFORM SIGN IB;Lo;0;L;;;;;N;;;;; 12142;CUNEIFORM SIGN IDIM;Lo;0;L;;;;;N;;;;; 12143;CUNEIFORM SIGN IDIM OVER IDIM BUR;Lo;0;L;;;;;N;;;;; 12144;CUNEIFORM SIGN IDIM OVER IDIM SQUARED;Lo;0;L;;;;;N;;;;; 12145;CUNEIFORM SIGN IG;Lo;0;L;;;;;N;;;;; 12146;CUNEIFORM SIGN IGI;Lo;0;L;;;;;N;;;;; 12147;CUNEIFORM SIGN IGI DIB;Lo;0;L;;;;;N;;;;; 12148;CUNEIFORM SIGN IGI RI;Lo;0;L;;;;;N;;;;; 12149;CUNEIFORM SIGN IGI OVER IGI SHIR OVER SHIR UD OVER UD;Lo;0;L;;;;;N;;;;; 1214A;CUNEIFORM SIGN IGI GUNU;Lo;0;L;;;;;N;;;;; 1214B;CUNEIFORM SIGN IL;Lo;0;L;;;;;N;;;;; 1214C;CUNEIFORM SIGN IL TIMES GAN2 TENU;Lo;0;L;;;;;N;;;;; 1214D;CUNEIFORM SIGN IL2;Lo;0;L;;;;;N;;;;; 1214E;CUNEIFORM SIGN IM;Lo;0;L;;;;;N;;;;; 1214F;CUNEIFORM SIGN IM TIMES TAK4;Lo;0;L;;;;;N;;;;; 12150;CUNEIFORM SIGN IM CROSSING IM;Lo;0;L;;;;;N;;;;; 12151;CUNEIFORM SIGN IM OPPOSING IM;Lo;0;L;;;;;N;;;;; 12152;CUNEIFORM SIGN IM SQUARED;Lo;0;L;;;;;N;;;;; 12153;CUNEIFORM SIGN IMIN;Lo;0;L;;;;;N;;;;; 12154;CUNEIFORM SIGN IN;Lo;0;L;;;;;N;;;;; 12155;CUNEIFORM SIGN IR;Lo;0;L;;;;;N;;;;; 12156;CUNEIFORM SIGN ISH;Lo;0;L;;;;;N;;;;; 12157;CUNEIFORM SIGN KA;Lo;0;L;;;;;N;;;;; 12158;CUNEIFORM SIGN KA TIMES A;Lo;0;L;;;;;N;;;;; 12159;CUNEIFORM SIGN KA TIMES AD;Lo;0;L;;;;;N;;;;; 1215A;CUNEIFORM SIGN KA TIMES AD PLUS KU3;Lo;0;L;;;;;N;;;;; 1215B;CUNEIFORM SIGN KA TIMES ASH2;Lo;0;L;;;;;N;;;;; 1215C;CUNEIFORM SIGN KA TIMES BAD;Lo;0;L;;;;;N;;;;; 1215D;CUNEIFORM SIGN KA TIMES BALAG;Lo;0;L;;;;;N;;;;; 1215E;CUNEIFORM SIGN KA TIMES BAR;Lo;0;L;;;;;N;;;;; 1215F;CUNEIFORM SIGN KA TIMES BI;Lo;0;L;;;;;N;;;;; 12160;CUNEIFORM SIGN KA TIMES ERIN2;Lo;0;L;;;;;N;;;;; 12161;CUNEIFORM SIGN KA TIMES ESH2;Lo;0;L;;;;;N;;;;; 12162;CUNEIFORM SIGN KA TIMES GA;Lo;0;L;;;;;N;;;;; 12163;CUNEIFORM SIGN KA TIMES GAL;Lo;0;L;;;;;N;;;;; 12164;CUNEIFORM SIGN KA TIMES GAN2 TENU;Lo;0;L;;;;;N;;;;; 12165;CUNEIFORM SIGN KA TIMES GAR;Lo;0;L;;;;;N;;;;; 12166;CUNEIFORM SIGN KA TIMES GAR PLUS SHA3 PLUS A;Lo;0;L;;;;;N;;;;; 12167;CUNEIFORM SIGN KA TIMES GI;Lo;0;L;;;;;N;;;;; 12168;CUNEIFORM SIGN KA TIMES GIR2;Lo;0;L;;;;;N;;;;; 12169;CUNEIFORM SIGN KA TIMES GISH PLUS SAR;Lo;0;L;;;;;N;;;;; 1216A;CUNEIFORM SIGN KA TIMES GISH CROSSING GISH;Lo;0;L;;;;;N;;;;; 1216B;CUNEIFORM SIGN KA TIMES GU;Lo;0;L;;;;;N;;;;; 1216C;CUNEIFORM SIGN KA TIMES GUR7;Lo;0;L;;;;;N;;;;; 1216D;CUNEIFORM SIGN KA TIMES IGI;Lo;0;L;;;;;N;;;;; 1216E;CUNEIFORM SIGN KA TIMES IM;Lo;0;L;;;;;N;;;;; 1216F;CUNEIFORM SIGN KA TIMES KAK;Lo;0;L;;;;;N;;;;; 12170;CUNEIFORM SIGN KA TIMES KI;Lo;0;L;;;;;N;;;;; 12171;CUNEIFORM SIGN KA TIMES KID;Lo;0;L;;;;;N;;;;; 12172;CUNEIFORM SIGN KA TIMES LI;Lo;0;L;;;;;N;;;;; 12173;CUNEIFORM SIGN KA TIMES LU;Lo;0;L;;;;;N;;;;; 12174;CUNEIFORM SIGN KA TIMES ME;Lo;0;L;;;;;N;;;;; 12175;CUNEIFORM SIGN KA TIMES ME PLUS DU;Lo;0;L;;;;;N;;;;; 12176;CUNEIFORM SIGN KA TIMES ME PLUS GI;Lo;0;L;;;;;N;;;;; 12177;CUNEIFORM SIGN KA TIMES ME PLUS TE;Lo;0;L;;;;;N;;;;; 12178;CUNEIFORM SIGN KA TIMES MI;Lo;0;L;;;;;N;;;;; 12179;CUNEIFORM SIGN KA TIMES MI PLUS NUNUZ;Lo;0;L;;;;;N;;;;; 1217A;CUNEIFORM SIGN KA TIMES NE;Lo;0;L;;;;;N;;;;; 1217B;CUNEIFORM SIGN KA TIMES NUN;Lo;0;L;;;;;N;;;;; 1217C;CUNEIFORM SIGN KA TIMES PI;Lo;0;L;;;;;N;;;;; 1217D;CUNEIFORM SIGN KA TIMES RU;Lo;0;L;;;;;N;;;;; 1217E;CUNEIFORM SIGN KA TIMES SA;Lo;0;L;;;;;N;;;;; 1217F;CUNEIFORM SIGN KA TIMES SAR;Lo;0;L;;;;;N;;;;; 12180;CUNEIFORM SIGN KA TIMES SHA;Lo;0;L;;;;;N;;;;; 12181;CUNEIFORM SIGN KA TIMES SHE;Lo;0;L;;;;;N;;;;; 12182;CUNEIFORM SIGN KA TIMES SHID;Lo;0;L;;;;;N;;;;; 12183;CUNEIFORM SIGN KA TIMES SHU;Lo;0;L;;;;;N;;;;; 12184;CUNEIFORM SIGN KA TIMES SIG;Lo;0;L;;;;;N;;;;; 12185;CUNEIFORM SIGN KA TIMES SUHUR;Lo;0;L;;;;;N;;;;; 12186;CUNEIFORM SIGN KA TIMES TAR;Lo;0;L;;;;;N;;;;; 12187;CUNEIFORM SIGN KA TIMES U;Lo;0;L;;;;;N;;;;; 12188;CUNEIFORM SIGN KA TIMES U2;Lo;0;L;;;;;N;;;;; 12189;CUNEIFORM SIGN KA TIMES UD;Lo;0;L;;;;;N;;;;; 1218A;CUNEIFORM SIGN KA TIMES UMUM TIMES PA;Lo;0;L;;;;;N;;;;; 1218B;CUNEIFORM SIGN KA TIMES USH;Lo;0;L;;;;;N;;;;; 1218C;CUNEIFORM SIGN KA TIMES ZI;Lo;0;L;;;;;N;;;;; 1218D;CUNEIFORM SIGN KA2;Lo;0;L;;;;;N;;;;; 1218E;CUNEIFORM SIGN KA2 CROSSING KA2;Lo;0;L;;;;;N;;;;; 1218F;CUNEIFORM SIGN KAB;Lo;0;L;;;;;N;;;;; 12190;CUNEIFORM SIGN KAD2;Lo;0;L;;;;;N;;;;; 12191;CUNEIFORM SIGN KAD3;Lo;0;L;;;;;N;;;;; 12192;CUNEIFORM SIGN KAD4;Lo;0;L;;;;;N;;;;; 12193;CUNEIFORM SIGN KAD5;Lo;0;L;;;;;N;;;;; 12194;CUNEIFORM SIGN KAD5 OVER KAD5;Lo;0;L;;;;;N;;;;; 12195;CUNEIFORM SIGN KAK;Lo;0;L;;;;;N;;;;; 12196;CUNEIFORM SIGN KAK TIMES IGI GUNU;Lo;0;L;;;;;N;;;;; 12197;CUNEIFORM SIGN KAL;Lo;0;L;;;;;N;;;;; 12198;CUNEIFORM SIGN KAL TIMES BAD;Lo;0;L;;;;;N;;;;; 12199;CUNEIFORM SIGN KAL CROSSING KAL;Lo;0;L;;;;;N;;;;; 1219A;CUNEIFORM SIGN KAM2;Lo;0;L;;;;;N;;;;; 1219B;CUNEIFORM SIGN KAM4;Lo;0;L;;;;;N;;;;; 1219C;CUNEIFORM SIGN KASKAL;Lo;0;L;;;;;N;;;;; 1219D;CUNEIFORM SIGN KASKAL LAGAB TIMES U OVER LAGAB TIMES U;Lo;0;L;;;;;N;;;;; 1219E;CUNEIFORM SIGN KASKAL OVER KASKAL LAGAB TIMES U OVER LAGAB TIMES U;Lo;0;L;;;;;N;;;;; 1219F;CUNEIFORM SIGN KESH2;Lo;0;L;;;;;N;;;;; 121A0;CUNEIFORM SIGN KI;Lo;0;L;;;;;N;;;;; 121A1;CUNEIFORM SIGN KI TIMES BAD;Lo;0;L;;;;;N;;;;; 121A2;CUNEIFORM SIGN KI TIMES U;Lo;0;L;;;;;N;;;;; 121A3;CUNEIFORM SIGN KI TIMES UD;Lo;0;L;;;;;N;;;;; 121A4;CUNEIFORM SIGN KID;Lo;0;L;;;;;N;;;;; 121A5;CUNEIFORM SIGN KIN;Lo;0;L;;;;;N;;;;; 121A6;CUNEIFORM SIGN KISAL;Lo;0;L;;;;;N;;;;; 121A7;CUNEIFORM SIGN KISH;Lo;0;L;;;;;N;;;;; 121A8;CUNEIFORM SIGN KISIM5;Lo;0;L;;;;;N;;;;; 121A9;CUNEIFORM SIGN KISIM5 OVER KISIM5;Lo;0;L;;;;;N;;;;; 121AA;CUNEIFORM SIGN KU;Lo;0;L;;;;;N;;;;; 121AB;CUNEIFORM SIGN KU OVER HI TIMES ASH2 KU OVER HI TIMES ASH2;Lo;0;L;;;;;N;;;;; 121AC;CUNEIFORM SIGN KU3;Lo;0;L;;;;;N;;;;; 121AD;CUNEIFORM SIGN KU4;Lo;0;L;;;;;N;;;;; 121AE;CUNEIFORM SIGN KU4 VARIANT FORM;Lo;0;L;;;;;N;;;;; 121AF;CUNEIFORM SIGN KU7;Lo;0;L;;;;;N;;;;; 121B0;CUNEIFORM SIGN KUL;Lo;0;L;;;;;N;;;;; 121B1;CUNEIFORM SIGN KUL GUNU;Lo;0;L;;;;;N;;;;; 121B2;CUNEIFORM SIGN KUN;Lo;0;L;;;;;N;;;;; 121B3;CUNEIFORM SIGN KUR;Lo;0;L;;;;;N;;;;; 121B4;CUNEIFORM SIGN KUR OPPOSING KUR;Lo;0;L;;;;;N;;;;; 121B5;CUNEIFORM SIGN KUSHU2;Lo;0;L;;;;;N;;;;; 121B6;CUNEIFORM SIGN KWU318;Lo;0;L;;;;;N;;;;; 121B7;CUNEIFORM SIGN LA;Lo;0;L;;;;;N;;;;; 121B8;CUNEIFORM SIGN LAGAB;Lo;0;L;;;;;N;;;;; 121B9;CUNEIFORM SIGN LAGAB TIMES A;Lo;0;L;;;;;N;;;;; 121BA;CUNEIFORM SIGN LAGAB TIMES A PLUS DA PLUS HA;Lo;0;L;;;;;N;;;;; 121BB;CUNEIFORM SIGN LAGAB TIMES A PLUS GAR;Lo;0;L;;;;;N;;;;; 121BC;CUNEIFORM SIGN LAGAB TIMES A PLUS LAL;Lo;0;L;;;;;N;;;;; 121BD;CUNEIFORM SIGN LAGAB TIMES AL;Lo;0;L;;;;;N;;;;; 121BE;CUNEIFORM SIGN LAGAB TIMES AN;Lo;0;L;;;;;N;;;;; 121BF;CUNEIFORM SIGN LAGAB TIMES ASH ZIDA TENU;Lo;0;L;;;;;N;;;;; 121C0;CUNEIFORM SIGN LAGAB TIMES BAD;Lo;0;L;;;;;N;;;;; 121C1;CUNEIFORM SIGN LAGAB TIMES BI;Lo;0;L;;;;;N;;;;; 121C2;CUNEIFORM SIGN LAGAB TIMES DAR;Lo;0;L;;;;;N;;;;; 121C3;CUNEIFORM SIGN LAGAB TIMES EN;Lo;0;L;;;;;N;;;;; 121C4;CUNEIFORM SIGN LAGAB TIMES GA;Lo;0;L;;;;;N;;;;; 121C5;CUNEIFORM SIGN LAGAB TIMES GAR;Lo;0;L;;;;;N;;;;; 121C6;CUNEIFORM SIGN LAGAB TIMES GUD;Lo;0;L;;;;;N;;;;; 121C7;CUNEIFORM SIGN LAGAB TIMES GUD PLUS GUD;Lo;0;L;;;;;N;;;;; 121C8;CUNEIFORM SIGN LAGAB TIMES HA;Lo;0;L;;;;;N;;;;; 121C9;CUNEIFORM SIGN LAGAB TIMES HAL;Lo;0;L;;;;;N;;;;; 121CA;CUNEIFORM SIGN LAGAB TIMES HI TIMES NUN;Lo;0;L;;;;;N;;;;; 121CB;CUNEIFORM SIGN LAGAB TIMES IGI GUNU;Lo;0;L;;;;;N;;;;; 121CC;CUNEIFORM SIGN LAGAB TIMES IM;Lo;0;L;;;;;N;;;;; 121CD;CUNEIFORM SIGN LAGAB TIMES IM PLUS HA;Lo;0;L;;;;;N;;;;; 121CE;CUNEIFORM SIGN LAGAB TIMES IM PLUS LU;Lo;0;L;;;;;N;;;;; 121CF;CUNEIFORM SIGN LAGAB TIMES KI;Lo;0;L;;;;;N;;;;; 121D0;CUNEIFORM SIGN LAGAB TIMES KIN;Lo;0;L;;;;;N;;;;; 121D1;CUNEIFORM SIGN LAGAB TIMES KU3;Lo;0;L;;;;;N;;;;; 121D2;CUNEIFORM SIGN LAGAB TIMES KUL;Lo;0;L;;;;;N;;;;; 121D3;CUNEIFORM SIGN LAGAB TIMES KUL PLUS HI PLUS A;Lo;0;L;;;;;N;;;;; 121D4;CUNEIFORM SIGN LAGAB TIMES LAGAB;Lo;0;L;;;;;N;;;;; 121D5;CUNEIFORM SIGN LAGAB TIMES LISH;Lo;0;L;;;;;N;;;;; 121D6;CUNEIFORM SIGN LAGAB TIMES LU;Lo;0;L;;;;;N;;;;; 121D7;CUNEIFORM SIGN LAGAB TIMES LUL;Lo;0;L;;;;;N;;;;; 121D8;CUNEIFORM SIGN LAGAB TIMES ME;Lo;0;L;;;;;N;;;;; 121D9;CUNEIFORM SIGN LAGAB TIMES ME PLUS EN;Lo;0;L;;;;;N;;;;; 121DA;CUNEIFORM SIGN LAGAB TIMES MUSH;Lo;0;L;;;;;N;;;;; 121DB;CUNEIFORM SIGN LAGAB TIMES NE;Lo;0;L;;;;;N;;;;; 121DC;CUNEIFORM SIGN LAGAB TIMES SHE PLUS SUM;Lo;0;L;;;;;N;;;;; 121DD;CUNEIFORM SIGN LAGAB TIMES SHITA PLUS GISH PLUS ERIN2;Lo;0;L;;;;;N;;;;; 121DE;CUNEIFORM SIGN LAGAB TIMES SHITA PLUS GISH TENU;Lo;0;L;;;;;N;;;;; 121DF;CUNEIFORM SIGN LAGAB TIMES SHU2;Lo;0;L;;;;;N;;;;; 121E0;CUNEIFORM SIGN LAGAB TIMES SHU2 PLUS SHU2;Lo;0;L;;;;;N;;;;; 121E1;CUNEIFORM SIGN LAGAB TIMES SUM;Lo;0;L;;;;;N;;;;; 121E2;CUNEIFORM SIGN LAGAB TIMES TAG;Lo;0;L;;;;;N;;;;; 121E3;CUNEIFORM SIGN LAGAB TIMES TAK4;Lo;0;L;;;;;N;;;;; 121E4;CUNEIFORM SIGN LAGAB TIMES TE PLUS A PLUS SU PLUS NA;Lo;0;L;;;;;N;;;;; 121E5;CUNEIFORM SIGN LAGAB TIMES U;Lo;0;L;;;;;N;;;;; 121E6;CUNEIFORM SIGN LAGAB TIMES U PLUS A;Lo;0;L;;;;;N;;;;; 121E7;CUNEIFORM SIGN LAGAB TIMES U PLUS U PLUS U;Lo;0;L;;;;;N;;;;; 121E8;CUNEIFORM SIGN LAGAB TIMES U2 PLUS ASH;Lo;0;L;;;;;N;;;;; 121E9;CUNEIFORM SIGN LAGAB TIMES UD;Lo;0;L;;;;;N;;;;; 121EA;CUNEIFORM SIGN LAGAB TIMES USH;Lo;0;L;;;;;N;;;;; 121EB;CUNEIFORM SIGN LAGAB SQUARED;Lo;0;L;;;;;N;;;;; 121EC;CUNEIFORM SIGN LAGAR;Lo;0;L;;;;;N;;;;; 121ED;CUNEIFORM SIGN LAGAR TIMES SHE;Lo;0;L;;;;;N;;;;; 121EE;CUNEIFORM SIGN LAGAR TIMES SHE PLUS SUM;Lo;0;L;;;;;N;;;;; 121EF;CUNEIFORM SIGN LAGAR GUNU;Lo;0;L;;;;;N;;;;; 121F0;CUNEIFORM SIGN LAGAR GUNU OVER LAGAR GUNU SHE;Lo;0;L;;;;;N;;;;; 121F1;CUNEIFORM SIGN LAHSHU;Lo;0;L;;;;;N;;;;; 121F2;CUNEIFORM SIGN LAL;Lo;0;L;;;;;N;;;;; 121F3;CUNEIFORM SIGN LAL TIMES LAL;Lo;0;L;;;;;N;;;;; 121F4;CUNEIFORM SIGN LAM;Lo;0;L;;;;;N;;;;; 121F5;CUNEIFORM SIGN LAM TIMES KUR;Lo;0;L;;;;;N;;;;; 121F6;CUNEIFORM SIGN LAM TIMES KUR PLUS RU;Lo;0;L;;;;;N;;;;; 121F7;CUNEIFORM SIGN LI;Lo;0;L;;;;;N;;;;; 121F8;CUNEIFORM SIGN LIL;Lo;0;L;;;;;N;;;;; 121F9;CUNEIFORM SIGN LIMMU2;Lo;0;L;;;;;N;;;;; 121FA;CUNEIFORM SIGN LISH;Lo;0;L;;;;;N;;;;; 121FB;CUNEIFORM SIGN LU;Lo;0;L;;;;;N;;;;; 121FC;CUNEIFORM SIGN LU TIMES BAD;Lo;0;L;;;;;N;;;;; 121FD;CUNEIFORM SIGN LU2;Lo;0;L;;;;;N;;;;; 121FE;CUNEIFORM SIGN LU2 TIMES AL;Lo;0;L;;;;;N;;;;; 121FF;CUNEIFORM SIGN LU2 TIMES BAD;Lo;0;L;;;;;N;;;;; 12200;CUNEIFORM SIGN LU2 TIMES ESH2;Lo;0;L;;;;;N;;;;; 12201;CUNEIFORM SIGN LU2 TIMES ESH2 TENU;Lo;0;L;;;;;N;;;;; 12202;CUNEIFORM SIGN LU2 TIMES GAN2 TENU;Lo;0;L;;;;;N;;;;; 12203;CUNEIFORM SIGN LU2 TIMES HI TIMES BAD;Lo;0;L;;;;;N;;;;; 12204;CUNEIFORM SIGN LU2 TIMES IM;Lo;0;L;;;;;N;;;;; 12205;CUNEIFORM SIGN LU2 TIMES KAD2;Lo;0;L;;;;;N;;;;; 12206;CUNEIFORM SIGN LU2 TIMES KAD3;Lo;0;L;;;;;N;;;;; 12207;CUNEIFORM SIGN LU2 TIMES KAD3 PLUS ASH;Lo;0;L;;;;;N;;;;; 12208;CUNEIFORM SIGN LU2 TIMES KI;Lo;0;L;;;;;N;;;;; 12209;CUNEIFORM SIGN LU2 TIMES LA PLUS ASH;Lo;0;L;;;;;N;;;;; 1220A;CUNEIFORM SIGN LU2 TIMES LAGAB;Lo;0;L;;;;;N;;;;; 1220B;CUNEIFORM SIGN LU2 TIMES ME PLUS EN;Lo;0;L;;;;;N;;;;; 1220C;CUNEIFORM SIGN LU2 TIMES NE;Lo;0;L;;;;;N;;;;; 1220D;CUNEIFORM SIGN LU2 TIMES NU;Lo;0;L;;;;;N;;;;; 1220E;CUNEIFORM SIGN LU2 TIMES SI PLUS ASH;Lo;0;L;;;;;N;;;;; 1220F;CUNEIFORM SIGN LU2 TIMES SIK2 PLUS BU;Lo;0;L;;;;;N;;;;; 12210;CUNEIFORM SIGN LU2 TIMES TUG2;Lo;0;L;;;;;N;;;;; 12211;CUNEIFORM SIGN LU2 TENU;Lo;0;L;;;;;N;;;;; 12212;CUNEIFORM SIGN LU2 CROSSING LU2;Lo;0;L;;;;;N;;;;; 12213;CUNEIFORM SIGN LU2 OPPOSING LU2;Lo;0;L;;;;;N;;;;; 12214;CUNEIFORM SIGN LU2 SQUARED;Lo;0;L;;;;;N;;;;; 12215;CUNEIFORM SIGN LU2 SHESHIG;Lo;0;L;;;;;N;;;;; 12216;CUNEIFORM SIGN LU3;Lo;0;L;;;;;N;;;;; 12217;CUNEIFORM SIGN LUGAL;Lo;0;L;;;;;N;;;;; 12218;CUNEIFORM SIGN LUGAL OVER LUGAL;Lo;0;L;;;;;N;;;;; 12219;CUNEIFORM SIGN LUGAL OPPOSING LUGAL;Lo;0;L;;;;;N;;;;; 1221A;CUNEIFORM SIGN LUGAL SHESHIG;Lo;0;L;;;;;N;;;;; 1221B;CUNEIFORM SIGN LUH;Lo;0;L;;;;;N;;;;; 1221C;CUNEIFORM SIGN LUL;Lo;0;L;;;;;N;;;;; 1221D;CUNEIFORM SIGN LUM;Lo;0;L;;;;;N;;;;; 1221E;CUNEIFORM SIGN LUM OVER LUM;Lo;0;L;;;;;N;;;;; 1221F;CUNEIFORM SIGN LUM OVER LUM GAR OVER GAR;Lo;0;L;;;;;N;;;;; 12220;CUNEIFORM SIGN MA;Lo;0;L;;;;;N;;;;; 12221;CUNEIFORM SIGN MA TIMES TAK4;Lo;0;L;;;;;N;;;;; 12222;CUNEIFORM SIGN MA GUNU;Lo;0;L;;;;;N;;;;; 12223;CUNEIFORM SIGN MA2;Lo;0;L;;;;;N;;;;; 12224;CUNEIFORM SIGN MAH;Lo;0;L;;;;;N;;;;; 12225;CUNEIFORM SIGN MAR;Lo;0;L;;;;;N;;;;; 12226;CUNEIFORM SIGN MASH;Lo;0;L;;;;;N;;;;; 12227;CUNEIFORM SIGN MASH2;Lo;0;L;;;;;N;;;;; 12228;CUNEIFORM SIGN ME;Lo;0;L;;;;;N;;;;; 12229;CUNEIFORM SIGN MES;Lo;0;L;;;;;N;;;;; 1222A;CUNEIFORM SIGN MI;Lo;0;L;;;;;N;;;;; 1222B;CUNEIFORM SIGN MIN;Lo;0;L;;;;;N;;;;; 1222C;CUNEIFORM SIGN MU;Lo;0;L;;;;;N;;;;; 1222D;CUNEIFORM SIGN MU OVER MU;Lo;0;L;;;;;N;;;;; 1222E;CUNEIFORM SIGN MUG;Lo;0;L;;;;;N;;;;; 1222F;CUNEIFORM SIGN MUG GUNU;Lo;0;L;;;;;N;;;;; 12230;CUNEIFORM SIGN MUNSUB;Lo;0;L;;;;;N;;;;; 12231;CUNEIFORM SIGN MURGU2;Lo;0;L;;;;;N;;;;; 12232;CUNEIFORM SIGN MUSH;Lo;0;L;;;;;N;;;;; 12233;CUNEIFORM SIGN MUSH TIMES A;Lo;0;L;;;;;N;;;;; 12234;CUNEIFORM SIGN MUSH TIMES KUR;Lo;0;L;;;;;N;;;;; 12235;CUNEIFORM SIGN MUSH TIMES ZA;Lo;0;L;;;;;N;;;;; 12236;CUNEIFORM SIGN MUSH OVER MUSH;Lo;0;L;;;;;N;;;;; 12237;CUNEIFORM SIGN MUSH OVER MUSH TIMES A PLUS NA;Lo;0;L;;;;;N;;;;; 12238;CUNEIFORM SIGN MUSH CROSSING MUSH;Lo;0;L;;;;;N;;;;; 12239;CUNEIFORM SIGN MUSH3;Lo;0;L;;;;;N;;;;; 1223A;CUNEIFORM SIGN MUSH3 TIMES A;Lo;0;L;;;;;N;;;;; 1223B;CUNEIFORM SIGN MUSH3 TIMES A PLUS DI;Lo;0;L;;;;;N;;;;; 1223C;CUNEIFORM SIGN MUSH3 TIMES DI;Lo;0;L;;;;;N;;;;; 1223D;CUNEIFORM SIGN MUSH3 GUNU;Lo;0;L;;;;;N;;;;; 1223E;CUNEIFORM SIGN NA;Lo;0;L;;;;;N;;;;; 1223F;CUNEIFORM SIGN NA2;Lo;0;L;;;;;N;;;;; 12240;CUNEIFORM SIGN NAGA;Lo;0;L;;;;;N;;;;; 12241;CUNEIFORM SIGN NAGA INVERTED;Lo;0;L;;;;;N;;;;; 12242;CUNEIFORM SIGN NAGA TIMES SHU TENU;Lo;0;L;;;;;N;;;;; 12243;CUNEIFORM SIGN NAGA OPPOSING NAGA;Lo;0;L;;;;;N;;;;; 12244;CUNEIFORM SIGN NAGAR;Lo;0;L;;;;;N;;;;; 12245;CUNEIFORM SIGN NAM NUTILLU;Lo;0;L;;;;;N;;;;; 12246;CUNEIFORM SIGN NAM;Lo;0;L;;;;;N;;;;; 12247;CUNEIFORM SIGN NAM2;Lo;0;L;;;;;N;;;;; 12248;CUNEIFORM SIGN NE;Lo;0;L;;;;;N;;;;; 12249;CUNEIFORM SIGN NE TIMES A;Lo;0;L;;;;;N;;;;; 1224A;CUNEIFORM SIGN NE TIMES UD;Lo;0;L;;;;;N;;;;; 1224B;CUNEIFORM SIGN NE SHESHIG;Lo;0;L;;;;;N;;;;; 1224C;CUNEIFORM SIGN NI;Lo;0;L;;;;;N;;;;; 1224D;CUNEIFORM SIGN NI TIMES E;Lo;0;L;;;;;N;;;;; 1224E;CUNEIFORM SIGN NI2;Lo;0;L;;;;;N;;;;; 1224F;CUNEIFORM SIGN NIM;Lo;0;L;;;;;N;;;;; 12250;CUNEIFORM SIGN NIM TIMES GAN2 TENU;Lo;0;L;;;;;N;;;;; 12251;CUNEIFORM SIGN NIM TIMES GAR PLUS GAN2 TENU;Lo;0;L;;;;;N;;;;; 12252;CUNEIFORM SIGN NINDA2;Lo;0;L;;;;;N;;;;; 12253;CUNEIFORM SIGN NINDA2 TIMES AN;Lo;0;L;;;;;N;;;;; 12254;CUNEIFORM SIGN NINDA2 TIMES ASH;Lo;0;L;;;;;N;;;;; 12255;CUNEIFORM SIGN NINDA2 TIMES ASH PLUS ASH;Lo;0;L;;;;;N;;;;; 12256;CUNEIFORM SIGN NINDA2 TIMES GUD;Lo;0;L;;;;;N;;;;; 12257;CUNEIFORM SIGN NINDA2 TIMES ME PLUS GAN2 TENU;Lo;0;L;;;;;N;;;;; 12258;CUNEIFORM SIGN NINDA2 TIMES NE;Lo;0;L;;;;;N;;;;; 12259;CUNEIFORM SIGN NINDA2 TIMES NUN;Lo;0;L;;;;;N;;;;; 1225A;CUNEIFORM SIGN NINDA2 TIMES SHE;Lo;0;L;;;;;N;;;;; 1225B;CUNEIFORM SIGN NINDA2 TIMES SHE PLUS A AN;Lo;0;L;;;;;N;;;;; 1225C;CUNEIFORM SIGN NINDA2 TIMES SHE PLUS ASH;Lo;0;L;;;;;N;;;;; 1225D;CUNEIFORM SIGN NINDA2 TIMES SHE PLUS ASH PLUS ASH;Lo;0;L;;;;;N;;;;; 1225E;CUNEIFORM SIGN NINDA2 TIMES U2 PLUS ASH;Lo;0;L;;;;;N;;;;; 1225F;CUNEIFORM SIGN NINDA2 TIMES USH;Lo;0;L;;;;;N;;;;; 12260;CUNEIFORM SIGN NISAG;Lo;0;L;;;;;N;;;;; 12261;CUNEIFORM SIGN NU;Lo;0;L;;;;;N;;;;; 12262;CUNEIFORM SIGN NU11;Lo;0;L;;;;;N;;;;; 12263;CUNEIFORM SIGN NUN;Lo;0;L;;;;;N;;;;; 12264;CUNEIFORM SIGN NUN LAGAR TIMES GAR;Lo;0;L;;;;;N;;;;; 12265;CUNEIFORM SIGN NUN LAGAR TIMES MASH;Lo;0;L;;;;;N;;;;; 12266;CUNEIFORM SIGN NUN LAGAR TIMES SAL;Lo;0;L;;;;;N;;;;; 12267;CUNEIFORM SIGN NUN LAGAR TIMES SAL OVER NUN LAGAR TIMES SAL;Lo;0;L;;;;;N;;;;; 12268;CUNEIFORM SIGN NUN LAGAR TIMES USH;Lo;0;L;;;;;N;;;;; 12269;CUNEIFORM SIGN NUN TENU;Lo;0;L;;;;;N;;;;; 1226A;CUNEIFORM SIGN NUN OVER NUN;Lo;0;L;;;;;N;;;;; 1226B;CUNEIFORM SIGN NUN CROSSING NUN;Lo;0;L;;;;;N;;;;; 1226C;CUNEIFORM SIGN NUN CROSSING NUN LAGAR OVER LAGAR;Lo;0;L;;;;;N;;;;; 1226D;CUNEIFORM SIGN NUNUZ;Lo;0;L;;;;;N;;;;; 1226E;CUNEIFORM SIGN NUNUZ AB2 TIMES ASHGAB;Lo;0;L;;;;;N;;;;; 1226F;CUNEIFORM SIGN NUNUZ AB2 TIMES BI;Lo;0;L;;;;;N;;;;; 12270;CUNEIFORM SIGN NUNUZ AB2 TIMES DUG;Lo;0;L;;;;;N;;;;; 12271;CUNEIFORM SIGN NUNUZ AB2 TIMES GUD;Lo;0;L;;;;;N;;;;; 12272;CUNEIFORM SIGN NUNUZ AB2 TIMES IGI GUNU;Lo;0;L;;;;;N;;;;; 12273;CUNEIFORM SIGN NUNUZ AB2 TIMES KAD3;Lo;0;L;;;;;N;;;;; 12274;CUNEIFORM SIGN NUNUZ AB2 TIMES LA;Lo;0;L;;;;;N;;;;; 12275;CUNEIFORM SIGN NUNUZ AB2 TIMES NE;Lo;0;L;;;;;N;;;;; 12276;CUNEIFORM SIGN NUNUZ AB2 TIMES SILA3;Lo;0;L;;;;;N;;;;; 12277;CUNEIFORM SIGN NUNUZ AB2 TIMES U2;Lo;0;L;;;;;N;;;;; 12278;CUNEIFORM SIGN NUNUZ KISIM5 TIMES BI;Lo;0;L;;;;;N;;;;; 12279;CUNEIFORM SIGN NUNUZ KISIM5 TIMES BI U;Lo;0;L;;;;;N;;;;; 1227A;CUNEIFORM SIGN PA;Lo;0;L;;;;;N;;;;; 1227B;CUNEIFORM SIGN PAD;Lo;0;L;;;;;N;;;;; 1227C;CUNEIFORM SIGN PAN;Lo;0;L;;;;;N;;;;; 1227D;CUNEIFORM SIGN PAP;Lo;0;L;;;;;N;;;;; 1227E;CUNEIFORM SIGN PESH2;Lo;0;L;;;;;N;;;;; 1227F;CUNEIFORM SIGN PI;Lo;0;L;;;;;N;;;;; 12280;CUNEIFORM SIGN PI TIMES A;Lo;0;L;;;;;N;;;;; 12281;CUNEIFORM SIGN PI TIMES AB;Lo;0;L;;;;;N;;;;; 12282;CUNEIFORM SIGN PI TIMES BI;Lo;0;L;;;;;N;;;;; 12283;CUNEIFORM SIGN PI TIMES BU;Lo;0;L;;;;;N;;;;; 12284;CUNEIFORM SIGN PI TIMES E;Lo;0;L;;;;;N;;;;; 12285;CUNEIFORM SIGN PI TIMES I;Lo;0;L;;;;;N;;;;; 12286;CUNEIFORM SIGN PI TIMES IB;Lo;0;L;;;;;N;;;;; 12287;CUNEIFORM SIGN PI TIMES U;Lo;0;L;;;;;N;;;;; 12288;CUNEIFORM SIGN PI TIMES U2;Lo;0;L;;;;;N;;;;; 12289;CUNEIFORM SIGN PI CROSSING PI;Lo;0;L;;;;;N;;;;; 1228A;CUNEIFORM SIGN PIRIG;Lo;0;L;;;;;N;;;;; 1228B;CUNEIFORM SIGN PIRIG TIMES KAL;Lo;0;L;;;;;N;;;;; 1228C;CUNEIFORM SIGN PIRIG TIMES UD;Lo;0;L;;;;;N;;;;; 1228D;CUNEIFORM SIGN PIRIG TIMES ZA;Lo;0;L;;;;;N;;;;; 1228E;CUNEIFORM SIGN PIRIG OPPOSING PIRIG;Lo;0;L;;;;;N;;;;; 1228F;CUNEIFORM SIGN RA;Lo;0;L;;;;;N;;;;; 12290;CUNEIFORM SIGN RAB;Lo;0;L;;;;;N;;;;; 12291;CUNEIFORM SIGN RI;Lo;0;L;;;;;N;;;;; 12292;CUNEIFORM SIGN RU;Lo;0;L;;;;;N;;;;; 12293;CUNEIFORM SIGN SA;Lo;0;L;;;;;N;;;;; 12294;CUNEIFORM SIGN SAG NUTILLU;Lo;0;L;;;;;N;;;;; 12295;CUNEIFORM SIGN SAG;Lo;0;L;;;;;N;;;;; 12296;CUNEIFORM SIGN SAG TIMES A;Lo;0;L;;;;;N;;;;; 12297;CUNEIFORM SIGN SAG TIMES DU;Lo;0;L;;;;;N;;;;; 12298;CUNEIFORM SIGN SAG TIMES DUB;Lo;0;L;;;;;N;;;;; 12299;CUNEIFORM SIGN SAG TIMES HA;Lo;0;L;;;;;N;;;;; 1229A;CUNEIFORM SIGN SAG TIMES KAK;Lo;0;L;;;;;N;;;;; 1229B;CUNEIFORM SIGN SAG TIMES KUR;Lo;0;L;;;;;N;;;;; 1229C;CUNEIFORM SIGN SAG TIMES LUM;Lo;0;L;;;;;N;;;;; 1229D;CUNEIFORM SIGN SAG TIMES MI;Lo;0;L;;;;;N;;;;; 1229E;CUNEIFORM SIGN SAG TIMES NUN;Lo;0;L;;;;;N;;;;; 1229F;CUNEIFORM SIGN SAG TIMES SAL;Lo;0;L;;;;;N;;;;; 122A0;CUNEIFORM SIGN SAG TIMES SHID;Lo;0;L;;;;;N;;;;; 122A1;CUNEIFORM SIGN SAG TIMES TAB;Lo;0;L;;;;;N;;;;; 122A2;CUNEIFORM SIGN SAG TIMES U2;Lo;0;L;;;;;N;;;;; 122A3;CUNEIFORM SIGN SAG TIMES UB;Lo;0;L;;;;;N;;;;; 122A4;CUNEIFORM SIGN SAG TIMES UM;Lo;0;L;;;;;N;;;;; 122A5;CUNEIFORM SIGN SAG TIMES UR;Lo;0;L;;;;;N;;;;; 122A6;CUNEIFORM SIGN SAG TIMES USH;Lo;0;L;;;;;N;;;;; 122A7;CUNEIFORM SIGN SAG OVER SAG;Lo;0;L;;;;;N;;;;; 122A8;CUNEIFORM SIGN SAG GUNU;Lo;0;L;;;;;N;;;;; 122A9;CUNEIFORM SIGN SAL;Lo;0;L;;;;;N;;;;; 122AA;CUNEIFORM SIGN SAL LAGAB TIMES ASH2;Lo;0;L;;;;;N;;;;; 122AB;CUNEIFORM SIGN SANGA2;Lo;0;L;;;;;N;;;;; 122AC;CUNEIFORM SIGN SAR;Lo;0;L;;;;;N;;;;; 122AD;CUNEIFORM SIGN SHA;Lo;0;L;;;;;N;;;;; 122AE;CUNEIFORM SIGN SHA3;Lo;0;L;;;;;N;;;;; 122AF;CUNEIFORM SIGN SHA3 TIMES A;Lo;0;L;;;;;N;;;;; 122B0;CUNEIFORM SIGN SHA3 TIMES BAD;Lo;0;L;;;;;N;;;;; 122B1;CUNEIFORM SIGN SHA3 TIMES GISH;Lo;0;L;;;;;N;;;;; 122B2;CUNEIFORM SIGN SHA3 TIMES NE;Lo;0;L;;;;;N;;;;; 122B3;CUNEIFORM SIGN SHA3 TIMES SHU2;Lo;0;L;;;;;N;;;;; 122B4;CUNEIFORM SIGN SHA3 TIMES TUR;Lo;0;L;;;;;N;;;;; 122B5;CUNEIFORM SIGN SHA3 TIMES U;Lo;0;L;;;;;N;;;;; 122B6;CUNEIFORM SIGN SHA3 TIMES U PLUS A;Lo;0;L;;;;;N;;;;; 122B7;CUNEIFORM SIGN SHA6;Lo;0;L;;;;;N;;;;; 122B8;CUNEIFORM SIGN SHAB6;Lo;0;L;;;;;N;;;;; 122B9;CUNEIFORM SIGN SHAR2;Lo;0;L;;;;;N;;;;; 122BA;CUNEIFORM SIGN SHE;Lo;0;L;;;;;N;;;;; 122BB;CUNEIFORM SIGN SHE HU;Lo;0;L;;;;;N;;;;; 122BC;CUNEIFORM SIGN SHE OVER SHE GAD OVER GAD GAR OVER GAR;Lo;0;L;;;;;N;;;;; 122BD;CUNEIFORM SIGN SHE OVER SHE TAB OVER TAB GAR OVER GAR;Lo;0;L;;;;;N;;;;; 122BE;CUNEIFORM SIGN SHEG9;Lo;0;L;;;;;N;;;;; 122BF;CUNEIFORM SIGN SHEN;Lo;0;L;;;;;N;;;;; 122C0;CUNEIFORM SIGN SHESH;Lo;0;L;;;;;N;;;;; 122C1;CUNEIFORM SIGN SHESH2;Lo;0;L;;;;;N;;;;; 122C2;CUNEIFORM SIGN SHESHLAM;Lo;0;L;;;;;N;;;;; 122C3;CUNEIFORM SIGN SHID;Lo;0;L;;;;;N;;;;; 122C4;CUNEIFORM SIGN SHID TIMES A;Lo;0;L;;;;;N;;;;; 122C5;CUNEIFORM SIGN SHID TIMES IM;Lo;0;L;;;;;N;;;;; 122C6;CUNEIFORM SIGN SHIM;Lo;0;L;;;;;N;;;;; 122C7;CUNEIFORM SIGN SHIM TIMES A;Lo;0;L;;;;;N;;;;; 122C8;CUNEIFORM SIGN SHIM TIMES BAL;Lo;0;L;;;;;N;;;;; 122C9;CUNEIFORM SIGN SHIM TIMES BULUG;Lo;0;L;;;;;N;;;;; 122CA;CUNEIFORM SIGN SHIM TIMES DIN;Lo;0;L;;;;;N;;;;; 122CB;CUNEIFORM SIGN SHIM TIMES GAR;Lo;0;L;;;;;N;;;;; 122CC;CUNEIFORM SIGN SHIM TIMES IGI;Lo;0;L;;;;;N;;;;; 122CD;CUNEIFORM SIGN SHIM TIMES IGI GUNU;Lo;0;L;;;;;N;;;;; 122CE;CUNEIFORM SIGN SHIM TIMES KUSHU2;Lo;0;L;;;;;N;;;;; 122CF;CUNEIFORM SIGN SHIM TIMES LUL;Lo;0;L;;;;;N;;;;; 122D0;CUNEIFORM SIGN SHIM TIMES MUG;Lo;0;L;;;;;N;;;;; 122D1;CUNEIFORM SIGN SHIM TIMES SAL;Lo;0;L;;;;;N;;;;; 122D2;CUNEIFORM SIGN SHINIG;Lo;0;L;;;;;N;;;;; 122D3;CUNEIFORM SIGN SHIR;Lo;0;L;;;;;N;;;;; 122D4;CUNEIFORM SIGN SHIR TENU;Lo;0;L;;;;;N;;;;; 122D5;CUNEIFORM SIGN SHIR OVER SHIR BUR OVER BUR;Lo;0;L;;;;;N;;;;; 122D6;CUNEIFORM SIGN SHITA;Lo;0;L;;;;;N;;;;; 122D7;CUNEIFORM SIGN SHU;Lo;0;L;;;;;N;;;;; 122D8;CUNEIFORM SIGN SHU OVER INVERTED SHU;Lo;0;L;;;;;N;;;;; 122D9;CUNEIFORM SIGN SHU2;Lo;0;L;;;;;N;;;;; 122DA;CUNEIFORM SIGN SHUBUR;Lo;0;L;;;;;N;;;;; 122DB;CUNEIFORM SIGN SI;Lo;0;L;;;;;N;;;;; 122DC;CUNEIFORM SIGN SI GUNU;Lo;0;L;;;;;N;;;;; 122DD;CUNEIFORM SIGN SIG;Lo;0;L;;;;;N;;;;; 122DE;CUNEIFORM SIGN SIG4;Lo;0;L;;;;;N;;;;; 122DF;CUNEIFORM SIGN SIG4 OVER SIG4 SHU2;Lo;0;L;;;;;N;;;;; 122E0;CUNEIFORM SIGN SIK2;Lo;0;L;;;;;N;;;;; 122E1;CUNEIFORM SIGN SILA3;Lo;0;L;;;;;N;;;;; 122E2;CUNEIFORM SIGN SU;Lo;0;L;;;;;N;;;;; 122E3;CUNEIFORM SIGN SU OVER SU;Lo;0;L;;;;;N;;;;; 122E4;CUNEIFORM SIGN SUD;Lo;0;L;;;;;N;;;;; 122E5;CUNEIFORM SIGN SUD2;Lo;0;L;;;;;N;;;;; 122E6;CUNEIFORM SIGN SUHUR;Lo;0;L;;;;;N;;;;; 122E7;CUNEIFORM SIGN SUM;Lo;0;L;;;;;N;;;;; 122E8;CUNEIFORM SIGN SUMASH;Lo;0;L;;;;;N;;;;; 122E9;CUNEIFORM SIGN SUR;Lo;0;L;;;;;N;;;;; 122EA;CUNEIFORM SIGN SUR9;Lo;0;L;;;;;N;;;;; 122EB;CUNEIFORM SIGN TA;Lo;0;L;;;;;N;;;;; 122EC;CUNEIFORM SIGN TA ASTERISK;Lo;0;L;;;;;N;;;;; 122ED;CUNEIFORM SIGN TA TIMES HI;Lo;0;L;;;;;N;;;;; 122EE;CUNEIFORM SIGN TA TIMES MI;Lo;0;L;;;;;N;;;;; 122EF;CUNEIFORM SIGN TA GUNU;Lo;0;L;;;;;N;;;;; 122F0;CUNEIFORM SIGN TAB;Lo;0;L;;;;;N;;;;; 122F1;CUNEIFORM SIGN TAB OVER TAB NI OVER NI DISH OVER DISH;Lo;0;L;;;;;N;;;;; 122F2;CUNEIFORM SIGN TAB SQUARED;Lo;0;L;;;;;N;;;;; 122F3;CUNEIFORM SIGN TAG;Lo;0;L;;;;;N;;;;; 122F4;CUNEIFORM SIGN TAG TIMES BI;Lo;0;L;;;;;N;;;;; 122F5;CUNEIFORM SIGN TAG TIMES GUD;Lo;0;L;;;;;N;;;;; 122F6;CUNEIFORM SIGN TAG TIMES SHE;Lo;0;L;;;;;N;;;;; 122F7;CUNEIFORM SIGN TAG TIMES SHU;Lo;0;L;;;;;N;;;;; 122F8;CUNEIFORM SIGN TAG TIMES TUG2;Lo;0;L;;;;;N;;;;; 122F9;CUNEIFORM SIGN TAG TIMES UD;Lo;0;L;;;;;N;;;;; 122FA;CUNEIFORM SIGN TAK4;Lo;0;L;;;;;N;;;;; 122FB;CUNEIFORM SIGN TAR;Lo;0;L;;;;;N;;;;; 122FC;CUNEIFORM SIGN TE;Lo;0;L;;;;;N;;;;; 122FD;CUNEIFORM SIGN TE GUNU;Lo;0;L;;;;;N;;;;; 122FE;CUNEIFORM SIGN TI;Lo;0;L;;;;;N;;;;; 122FF;CUNEIFORM SIGN TI TENU;Lo;0;L;;;;;N;;;;; 12300;CUNEIFORM SIGN TIL;Lo;0;L;;;;;N;;;;; 12301;CUNEIFORM SIGN TIR;Lo;0;L;;;;;N;;;;; 12302;CUNEIFORM SIGN TIR TIMES TAK4;Lo;0;L;;;;;N;;;;; 12303;CUNEIFORM SIGN TIR OVER TIR;Lo;0;L;;;;;N;;;;; 12304;CUNEIFORM SIGN TIR OVER TIR GAD OVER GAD GAR OVER GAR;Lo;0;L;;;;;N;;;;; 12305;CUNEIFORM SIGN TU;Lo;0;L;;;;;N;;;;; 12306;CUNEIFORM SIGN TUG2;Lo;0;L;;;;;N;;;;; 12307;CUNEIFORM SIGN TUK;Lo;0;L;;;;;N;;;;; 12308;CUNEIFORM SIGN TUM;Lo;0;L;;;;;N;;;;; 12309;CUNEIFORM SIGN TUR;Lo;0;L;;;;;N;;;;; 1230A;CUNEIFORM SIGN TUR OVER TUR ZA OVER ZA;Lo;0;L;;;;;N;;;;; 1230B;CUNEIFORM SIGN U;Lo;0;L;;;;;N;;;;; 1230C;CUNEIFORM SIGN U GUD;Lo;0;L;;;;;N;;;;; 1230D;CUNEIFORM SIGN U U U;Lo;0;L;;;;;N;;;;; 1230E;CUNEIFORM SIGN U OVER U PA OVER PA GAR OVER GAR;Lo;0;L;;;;;N;;;;; 1230F;CUNEIFORM SIGN U OVER U SUR OVER SUR;Lo;0;L;;;;;N;;;;; 12310;CUNEIFORM SIGN U OVER U U REVERSED OVER U REVERSED;Lo;0;L;;;;;N;;;;; 12311;CUNEIFORM SIGN U2;Lo;0;L;;;;;N;;;;; 12312;CUNEIFORM SIGN UB;Lo;0;L;;;;;N;;;;; 12313;CUNEIFORM SIGN UD;Lo;0;L;;;;;N;;;;; 12314;CUNEIFORM SIGN UD KUSHU2;Lo;0;L;;;;;N;;;;; 12315;CUNEIFORM SIGN UD TIMES BAD;Lo;0;L;;;;;N;;;;; 12316;CUNEIFORM SIGN UD TIMES MI;Lo;0;L;;;;;N;;;;; 12317;CUNEIFORM SIGN UD TIMES U PLUS U PLUS U;Lo;0;L;;;;;N;;;;; 12318;CUNEIFORM SIGN UD TIMES U PLUS U PLUS U GUNU;Lo;0;L;;;;;N;;;;; 12319;CUNEIFORM SIGN UD GUNU;Lo;0;L;;;;;N;;;;; 1231A;CUNEIFORM SIGN UD SHESHIG;Lo;0;L;;;;;N;;;;; 1231B;CUNEIFORM SIGN UD SHESHIG TIMES BAD;Lo;0;L;;;;;N;;;;; 1231C;CUNEIFORM SIGN UDUG;Lo;0;L;;;;;N;;;;; 1231D;CUNEIFORM SIGN UM;Lo;0;L;;;;;N;;;;; 1231E;CUNEIFORM SIGN UM TIMES LAGAB;Lo;0;L;;;;;N;;;;; 1231F;CUNEIFORM SIGN UM TIMES ME PLUS DA;Lo;0;L;;;;;N;;;;; 12320;CUNEIFORM SIGN UM TIMES SHA3;Lo;0;L;;;;;N;;;;; 12321;CUNEIFORM SIGN UM TIMES U;Lo;0;L;;;;;N;;;;; 12322;CUNEIFORM SIGN UMBIN;Lo;0;L;;;;;N;;;;; 12323;CUNEIFORM SIGN UMUM;Lo;0;L;;;;;N;;;;; 12324;CUNEIFORM SIGN UMUM TIMES KASKAL;Lo;0;L;;;;;N;;;;; 12325;CUNEIFORM SIGN UMUM TIMES PA;Lo;0;L;;;;;N;;;;; 12326;CUNEIFORM SIGN UN;Lo;0;L;;;;;N;;;;; 12327;CUNEIFORM SIGN UN GUNU;Lo;0;L;;;;;N;;;;; 12328;CUNEIFORM SIGN UR;Lo;0;L;;;;;N;;;;; 12329;CUNEIFORM SIGN UR CROSSING UR;Lo;0;L;;;;;N;;;;; 1232A;CUNEIFORM SIGN UR SHESHIG;Lo;0;L;;;;;N;;;;; 1232B;CUNEIFORM SIGN UR2;Lo;0;L;;;;;N;;;;; 1232C;CUNEIFORM SIGN UR2 TIMES A PLUS HA;Lo;0;L;;;;;N;;;;; 1232D;CUNEIFORM SIGN UR2 TIMES A PLUS NA;Lo;0;L;;;;;N;;;;; 1232E;CUNEIFORM SIGN UR2 TIMES AL;Lo;0;L;;;;;N;;;;; 1232F;CUNEIFORM SIGN UR2 TIMES HA;Lo;0;L;;;;;N;;;;; 12330;CUNEIFORM SIGN UR2 TIMES NUN;Lo;0;L;;;;;N;;;;; 12331;CUNEIFORM SIGN UR2 TIMES U2;Lo;0;L;;;;;N;;;;; 12332;CUNEIFORM SIGN UR2 TIMES U2 PLUS ASH;Lo;0;L;;;;;N;;;;; 12333;CUNEIFORM SIGN UR2 TIMES U2 PLUS BI;Lo;0;L;;;;;N;;;;; 12334;CUNEIFORM SIGN UR4;Lo;0;L;;;;;N;;;;; 12335;CUNEIFORM SIGN URI;Lo;0;L;;;;;N;;;;; 12336;CUNEIFORM SIGN URI3;Lo;0;L;;;;;N;;;;; 12337;CUNEIFORM SIGN URU;Lo;0;L;;;;;N;;;;; 12338;CUNEIFORM SIGN URU TIMES A;Lo;0;L;;;;;N;;;;; 12339;CUNEIFORM SIGN URU TIMES ASHGAB;Lo;0;L;;;;;N;;;;; 1233A;CUNEIFORM SIGN URU TIMES BAR;Lo;0;L;;;;;N;;;;; 1233B;CUNEIFORM SIGN URU TIMES DUN;Lo;0;L;;;;;N;;;;; 1233C;CUNEIFORM SIGN URU TIMES GA;Lo;0;L;;;;;N;;;;; 1233D;CUNEIFORM SIGN URU TIMES GAL;Lo;0;L;;;;;N;;;;; 1233E;CUNEIFORM SIGN URU TIMES GAN2 TENU;Lo;0;L;;;;;N;;;;; 1233F;CUNEIFORM SIGN URU TIMES GAR;Lo;0;L;;;;;N;;;;; 12340;CUNEIFORM SIGN URU TIMES GU;Lo;0;L;;;;;N;;;;; 12341;CUNEIFORM SIGN URU TIMES HA;Lo;0;L;;;;;N;;;;; 12342;CUNEIFORM SIGN URU TIMES IGI;Lo;0;L;;;;;N;;;;; 12343;CUNEIFORM SIGN URU TIMES IM;Lo;0;L;;;;;N;;;;; 12344;CUNEIFORM SIGN URU TIMES ISH;Lo;0;L;;;;;N;;;;; 12345;CUNEIFORM SIGN URU TIMES KI;Lo;0;L;;;;;N;;;;; 12346;CUNEIFORM SIGN URU TIMES LUM;Lo;0;L;;;;;N;;;;; 12347;CUNEIFORM SIGN URU TIMES MIN;Lo;0;L;;;;;N;;;;; 12348;CUNEIFORM SIGN URU TIMES PA;Lo;0;L;;;;;N;;;;; 12349;CUNEIFORM SIGN URU TIMES SHE;Lo;0;L;;;;;N;;;;; 1234A;CUNEIFORM SIGN URU TIMES SIG4;Lo;0;L;;;;;N;;;;; 1234B;CUNEIFORM SIGN URU TIMES TU;Lo;0;L;;;;;N;;;;; 1234C;CUNEIFORM SIGN URU TIMES U PLUS GUD;Lo;0;L;;;;;N;;;;; 1234D;CUNEIFORM SIGN URU TIMES UD;Lo;0;L;;;;;N;;;;; 1234E;CUNEIFORM SIGN URU TIMES URUDA;Lo;0;L;;;;;N;;;;; 1234F;CUNEIFORM SIGN URUDA;Lo;0;L;;;;;N;;;;; 12350;CUNEIFORM SIGN URUDA TIMES U;Lo;0;L;;;;;N;;;;; 12351;CUNEIFORM SIGN USH;Lo;0;L;;;;;N;;;;; 12352;CUNEIFORM SIGN USH TIMES A;Lo;0;L;;;;;N;;;;; 12353;CUNEIFORM SIGN USH TIMES KU;Lo;0;L;;;;;N;;;;; 12354;CUNEIFORM SIGN USH TIMES KUR;Lo;0;L;;;;;N;;;;; 12355;CUNEIFORM SIGN USH TIMES TAK4;Lo;0;L;;;;;N;;;;; 12356;CUNEIFORM SIGN USHX;Lo;0;L;;;;;N;;;;; 12357;CUNEIFORM SIGN USH2;Lo;0;L;;;;;N;;;;; 12358;CUNEIFORM SIGN USHUMX;Lo;0;L;;;;;N;;;;; 12359;CUNEIFORM SIGN UTUKI;Lo;0;L;;;;;N;;;;; 1235A;CUNEIFORM SIGN UZ3;Lo;0;L;;;;;N;;;;; 1235B;CUNEIFORM SIGN UZ3 TIMES KASKAL;Lo;0;L;;;;;N;;;;; 1235C;CUNEIFORM SIGN UZU;Lo;0;L;;;;;N;;;;; 1235D;CUNEIFORM SIGN ZA;Lo;0;L;;;;;N;;;;; 1235E;CUNEIFORM SIGN ZA TENU;Lo;0;L;;;;;N;;;;; 1235F;CUNEIFORM SIGN ZA SQUARED TIMES KUR;Lo;0;L;;;;;N;;;;; 12360;CUNEIFORM SIGN ZAG;Lo;0;L;;;;;N;;;;; 12361;CUNEIFORM SIGN ZAMX;Lo;0;L;;;;;N;;;;; 12362;CUNEIFORM SIGN ZE2;Lo;0;L;;;;;N;;;;; 12363;CUNEIFORM SIGN ZI;Lo;0;L;;;;;N;;;;; 12364;CUNEIFORM SIGN ZI OVER ZI;Lo;0;L;;;;;N;;;;; 12365;CUNEIFORM SIGN ZI3;Lo;0;L;;;;;N;;;;; 12366;CUNEIFORM SIGN ZIB;Lo;0;L;;;;;N;;;;; 12367;CUNEIFORM SIGN ZIB KABA TENU;Lo;0;L;;;;;N;;;;; 12368;CUNEIFORM SIGN ZIG;Lo;0;L;;;;;N;;;;; 12369;CUNEIFORM SIGN ZIZ2;Lo;0;L;;;;;N;;;;; 1236A;CUNEIFORM SIGN ZU;Lo;0;L;;;;;N;;;;; 1236B;CUNEIFORM SIGN ZU5;Lo;0;L;;;;;N;;;;; 1236C;CUNEIFORM SIGN ZU5 TIMES A;Lo;0;L;;;;;N;;;;; 1236D;CUNEIFORM SIGN ZUBUR;Lo;0;L;;;;;N;;;;; 1236E;CUNEIFORM SIGN ZUM;Lo;0;L;;;;;N;;;;; 1236F;CUNEIFORM SIGN KAP ELAMITE;Lo;0;L;;;;;N;;;;; 12370;CUNEIFORM SIGN AB TIMES NUN;Lo;0;L;;;;;N;;;;; 12371;CUNEIFORM SIGN AB2 TIMES A;Lo;0;L;;;;;N;;;;; 12372;CUNEIFORM SIGN AMAR TIMES KUG;Lo;0;L;;;;;N;;;;; 12373;CUNEIFORM SIGN DAG KISIM5 TIMES U2 PLUS MASH;Lo;0;L;;;;;N;;;;; 12374;CUNEIFORM SIGN DAG3;Lo;0;L;;;;;N;;;;; 12375;CUNEIFORM SIGN DISH PLUS SHU;Lo;0;L;;;;;N;;;;; 12376;CUNEIFORM SIGN DUB TIMES SHE;Lo;0;L;;;;;N;;;;; 12377;CUNEIFORM SIGN EZEN TIMES GUD;Lo;0;L;;;;;N;;;;; 12378;CUNEIFORM SIGN EZEN TIMES SHE;Lo;0;L;;;;;N;;;;; 12379;CUNEIFORM SIGN GA2 TIMES AN PLUS KAK PLUS A;Lo;0;L;;;;;N;;;;; 1237A;CUNEIFORM SIGN GA2 TIMES ASH2;Lo;0;L;;;;;N;;;;; 1237B;CUNEIFORM SIGN GE22;Lo;0;L;;;;;N;;;;; 1237C;CUNEIFORM SIGN GIG;Lo;0;L;;;;;N;;;;; 1237D;CUNEIFORM SIGN HUSH;Lo;0;L;;;;;N;;;;; 1237E;CUNEIFORM SIGN KA TIMES ANSHE;Lo;0;L;;;;;N;;;;; 1237F;CUNEIFORM SIGN KA TIMES ASH3;Lo;0;L;;;;;N;;;;; 12380;CUNEIFORM SIGN KA TIMES GISH;Lo;0;L;;;;;N;;;;; 12381;CUNEIFORM SIGN KA TIMES GUD;Lo;0;L;;;;;N;;;;; 12382;CUNEIFORM SIGN KA TIMES HI TIMES ASH2;Lo;0;L;;;;;N;;;;; 12383;CUNEIFORM SIGN KA TIMES LUM;Lo;0;L;;;;;N;;;;; 12384;CUNEIFORM SIGN KA TIMES PA;Lo;0;L;;;;;N;;;;; 12385;CUNEIFORM SIGN KA TIMES SHUL;Lo;0;L;;;;;N;;;;; 12386;CUNEIFORM SIGN KA TIMES TU;Lo;0;L;;;;;N;;;;; 12387;CUNEIFORM SIGN KA TIMES UR2;Lo;0;L;;;;;N;;;;; 12388;CUNEIFORM SIGN LAGAB TIMES GI;Lo;0;L;;;;;N;;;;; 12389;CUNEIFORM SIGN LU2 SHESHIG TIMES BAD;Lo;0;L;;;;;N;;;;; 1238A;CUNEIFORM SIGN LU2 TIMES ESH2 PLUS LAL;Lo;0;L;;;;;N;;;;; 1238B;CUNEIFORM SIGN LU2 TIMES SHU;Lo;0;L;;;;;N;;;;; 1238C;CUNEIFORM SIGN MESH;Lo;0;L;;;;;N;;;;; 1238D;CUNEIFORM SIGN MUSH3 TIMES ZA;Lo;0;L;;;;;N;;;;; 1238E;CUNEIFORM SIGN NA4;Lo;0;L;;;;;N;;;;; 1238F;CUNEIFORM SIGN NIN;Lo;0;L;;;;;N;;;;; 12390;CUNEIFORM SIGN NIN9;Lo;0;L;;;;;N;;;;; 12391;CUNEIFORM SIGN NINDA2 TIMES BAL;Lo;0;L;;;;;N;;;;; 12392;CUNEIFORM SIGN NINDA2 TIMES GI;Lo;0;L;;;;;N;;;;; 12393;CUNEIFORM SIGN NU11 ROTATED NINETY DEGREES;Lo;0;L;;;;;N;;;;; 12394;CUNEIFORM SIGN PESH2 ASTERISK;Lo;0;L;;;;;N;;;;; 12395;CUNEIFORM SIGN PIR2;Lo;0;L;;;;;N;;;;; 12396;CUNEIFORM SIGN SAG TIMES IGI GUNU;Lo;0;L;;;;;N;;;;; 12397;CUNEIFORM SIGN TI2;Lo;0;L;;;;;N;;;;; 12398;CUNEIFORM SIGN UM TIMES ME;Lo;0;L;;;;;N;;;;; 12400;CUNEIFORM NUMERIC SIGN TWO ASH;Nl;0;L;;;;2;N;;;;; 12401;CUNEIFORM NUMERIC SIGN THREE ASH;Nl;0;L;;;;3;N;;;;; 12402;CUNEIFORM NUMERIC SIGN FOUR ASH;Nl;0;L;;;;4;N;;;;; 12403;CUNEIFORM NUMERIC SIGN FIVE ASH;Nl;0;L;;;;5;N;;;;; 12404;CUNEIFORM NUMERIC SIGN SIX ASH;Nl;0;L;;;;6;N;;;;; 12405;CUNEIFORM NUMERIC SIGN SEVEN ASH;Nl;0;L;;;;7;N;;;;; 12406;CUNEIFORM NUMERIC SIGN EIGHT ASH;Nl;0;L;;;;8;N;;;;; 12407;CUNEIFORM NUMERIC SIGN NINE ASH;Nl;0;L;;;;9;N;;;;; 12408;CUNEIFORM NUMERIC SIGN THREE DISH;Nl;0;L;;;;3;N;;;;; 12409;CUNEIFORM NUMERIC SIGN FOUR DISH;Nl;0;L;;;;4;N;;;;; 1240A;CUNEIFORM NUMERIC SIGN FIVE DISH;Nl;0;L;;;;5;N;;;;; 1240B;CUNEIFORM NUMERIC SIGN SIX DISH;Nl;0;L;;;;6;N;;;;; 1240C;CUNEIFORM NUMERIC SIGN SEVEN DISH;Nl;0;L;;;;7;N;;;;; 1240D;CUNEIFORM NUMERIC SIGN EIGHT DISH;Nl;0;L;;;;8;N;;;;; 1240E;CUNEIFORM NUMERIC SIGN NINE DISH;Nl;0;L;;;;9;N;;;;; 1240F;CUNEIFORM NUMERIC SIGN FOUR U;Nl;0;L;;;;4;N;;;;; 12410;CUNEIFORM NUMERIC SIGN FIVE U;Nl;0;L;;;;5;N;;;;; 12411;CUNEIFORM NUMERIC SIGN SIX U;Nl;0;L;;;;6;N;;;;; 12412;CUNEIFORM NUMERIC SIGN SEVEN U;Nl;0;L;;;;7;N;;;;; 12413;CUNEIFORM NUMERIC SIGN EIGHT U;Nl;0;L;;;;8;N;;;;; 12414;CUNEIFORM NUMERIC SIGN NINE U;Nl;0;L;;;;9;N;;;;; 12415;CUNEIFORM NUMERIC SIGN ONE GESH2;Nl;0;L;;;;1;N;;;;; 12416;CUNEIFORM NUMERIC SIGN TWO GESH2;Nl;0;L;;;;2;N;;;;; 12417;CUNEIFORM NUMERIC SIGN THREE GESH2;Nl;0;L;;;;3;N;;;;; 12418;CUNEIFORM NUMERIC SIGN FOUR GESH2;Nl;0;L;;;;4;N;;;;; 12419;CUNEIFORM NUMERIC SIGN FIVE GESH2;Nl;0;L;;;;5;N;;;;; 1241A;CUNEIFORM NUMERIC SIGN SIX GESH2;Nl;0;L;;;;6;N;;;;; 1241B;CUNEIFORM NUMERIC SIGN SEVEN GESH2;Nl;0;L;;;;7;N;;;;; 1241C;CUNEIFORM NUMERIC SIGN EIGHT GESH2;Nl;0;L;;;;8;N;;;;; 1241D;CUNEIFORM NUMERIC SIGN NINE GESH2;Nl;0;L;;;;9;N;;;;; 1241E;CUNEIFORM NUMERIC SIGN ONE GESHU;Nl;0;L;;;;1;N;;;;; 1241F;CUNEIFORM NUMERIC SIGN TWO GESHU;Nl;0;L;;;;2;N;;;;; 12420;CUNEIFORM NUMERIC SIGN THREE GESHU;Nl;0;L;;;;3;N;;;;; 12421;CUNEIFORM NUMERIC SIGN FOUR GESHU;Nl;0;L;;;;4;N;;;;; 12422;CUNEIFORM NUMERIC SIGN FIVE GESHU;Nl;0;L;;;;5;N;;;;; 12423;CUNEIFORM NUMERIC SIGN TWO SHAR2;Nl;0;L;;;;2;N;;;;; 12424;CUNEIFORM NUMERIC SIGN THREE SHAR2;Nl;0;L;;;;3;N;;;;; 12425;CUNEIFORM NUMERIC SIGN THREE SHAR2 VARIANT FORM;Nl;0;L;;;;3;N;;;;; 12426;CUNEIFORM NUMERIC SIGN FOUR SHAR2;Nl;0;L;;;;4;N;;;;; 12427;CUNEIFORM NUMERIC SIGN FIVE SHAR2;Nl;0;L;;;;5;N;;;;; 12428;CUNEIFORM NUMERIC SIGN SIX SHAR2;Nl;0;L;;;;6;N;;;;; 12429;CUNEIFORM NUMERIC SIGN SEVEN SHAR2;Nl;0;L;;;;7;N;;;;; 1242A;CUNEIFORM NUMERIC SIGN EIGHT SHAR2;Nl;0;L;;;;8;N;;;;; 1242B;CUNEIFORM NUMERIC SIGN NINE SHAR2;Nl;0;L;;;;9;N;;;;; 1242C;CUNEIFORM NUMERIC SIGN ONE SHARU;Nl;0;L;;;;1;N;;;;; 1242D;CUNEIFORM NUMERIC SIGN TWO SHARU;Nl;0;L;;;;2;N;;;;; 1242E;CUNEIFORM NUMERIC SIGN THREE SHARU;Nl;0;L;;;;3;N;;;;; 1242F;CUNEIFORM NUMERIC SIGN THREE SHARU VARIANT FORM;Nl;0;L;;;;3;N;;;;; 12430;CUNEIFORM NUMERIC SIGN FOUR SHARU;Nl;0;L;;;;4;N;;;;; 12431;CUNEIFORM NUMERIC SIGN FIVE SHARU;Nl;0;L;;;;5;N;;;;; 12432;CUNEIFORM NUMERIC SIGN SHAR2 TIMES GAL PLUS DISH;Nl;0;L;;;;216000;N;;;;; 12433;CUNEIFORM NUMERIC SIGN SHAR2 TIMES GAL PLUS MIN;Nl;0;L;;;;432000;N;;;;; 12434;CUNEIFORM NUMERIC SIGN ONE BURU;Nl;0;L;;;;1;N;;;;; 12435;CUNEIFORM NUMERIC SIGN TWO BURU;Nl;0;L;;;;2;N;;;;; 12436;CUNEIFORM NUMERIC SIGN THREE BURU;Nl;0;L;;;;3;N;;;;; 12437;CUNEIFORM NUMERIC SIGN THREE BURU VARIANT FORM;Nl;0;L;;;;3;N;;;;; 12438;CUNEIFORM NUMERIC SIGN FOUR BURU;Nl;0;L;;;;4;N;;;;; 12439;CUNEIFORM NUMERIC SIGN FIVE BURU;Nl;0;L;;;;5;N;;;;; 1243A;CUNEIFORM NUMERIC SIGN THREE VARIANT FORM ESH16;Nl;0;L;;;;3;N;;;;; 1243B;CUNEIFORM NUMERIC SIGN THREE VARIANT FORM ESH21;Nl;0;L;;;;3;N;;;;; 1243C;CUNEIFORM NUMERIC SIGN FOUR VARIANT FORM LIMMU;Nl;0;L;;;;4;N;;;;; 1243D;CUNEIFORM NUMERIC SIGN FOUR VARIANT FORM LIMMU4;Nl;0;L;;;;4;N;;;;; 1243E;CUNEIFORM NUMERIC SIGN FOUR VARIANT FORM LIMMU A;Nl;0;L;;;;4;N;;;;; 1243F;CUNEIFORM NUMERIC SIGN FOUR VARIANT FORM LIMMU B;Nl;0;L;;;;4;N;;;;; 12440;CUNEIFORM NUMERIC SIGN SIX VARIANT FORM ASH9;Nl;0;L;;;;6;N;;;;; 12441;CUNEIFORM NUMERIC SIGN SEVEN VARIANT FORM IMIN3;Nl;0;L;;;;7;N;;;;; 12442;CUNEIFORM NUMERIC SIGN SEVEN VARIANT FORM IMIN A;Nl;0;L;;;;7;N;;;;; 12443;CUNEIFORM NUMERIC SIGN SEVEN VARIANT FORM IMIN B;Nl;0;L;;;;7;N;;;;; 12444;CUNEIFORM NUMERIC SIGN EIGHT VARIANT FORM USSU;Nl;0;L;;;;8;N;;;;; 12445;CUNEIFORM NUMERIC SIGN EIGHT VARIANT FORM USSU3;Nl;0;L;;;;8;N;;;;; 12446;CUNEIFORM NUMERIC SIGN NINE VARIANT FORM ILIMMU;Nl;0;L;;;;9;N;;;;; 12447;CUNEIFORM NUMERIC SIGN NINE VARIANT FORM ILIMMU3;Nl;0;L;;;;9;N;;;;; 12448;CUNEIFORM NUMERIC SIGN NINE VARIANT FORM ILIMMU4;Nl;0;L;;;;9;N;;;;; 12449;CUNEIFORM NUMERIC SIGN NINE VARIANT FORM ILIMMU A;Nl;0;L;;;;9;N;;;;; 1244A;CUNEIFORM NUMERIC SIGN TWO ASH TENU;Nl;0;L;;;;2;N;;;;; 1244B;CUNEIFORM NUMERIC SIGN THREE ASH TENU;Nl;0;L;;;;3;N;;;;; 1244C;CUNEIFORM NUMERIC SIGN FOUR ASH TENU;Nl;0;L;;;;4;N;;;;; 1244D;CUNEIFORM NUMERIC SIGN FIVE ASH TENU;Nl;0;L;;;;5;N;;;;; 1244E;CUNEIFORM NUMERIC SIGN SIX ASH TENU;Nl;0;L;;;;6;N;;;;; 1244F;CUNEIFORM NUMERIC SIGN ONE BAN2;Nl;0;L;;;;1;N;;;;; 12450;CUNEIFORM NUMERIC SIGN TWO BAN2;Nl;0;L;;;;2;N;;;;; 12451;CUNEIFORM NUMERIC SIGN THREE BAN2;Nl;0;L;;;;3;N;;;;; 12452;CUNEIFORM NUMERIC SIGN FOUR BAN2;Nl;0;L;;;;4;N;;;;; 12453;CUNEIFORM NUMERIC SIGN FOUR BAN2 VARIANT FORM;Nl;0;L;;;;4;N;;;;; 12454;CUNEIFORM NUMERIC SIGN FIVE BAN2;Nl;0;L;;;;5;N;;;;; 12455;CUNEIFORM NUMERIC SIGN FIVE BAN2 VARIANT FORM;Nl;0;L;;;;5;N;;;;; 12456;CUNEIFORM NUMERIC SIGN NIGIDAMIN;Nl;0;L;;;;2;N;;;;; 12457;CUNEIFORM NUMERIC SIGN NIGIDAESH;Nl;0;L;;;;3;N;;;;; 12458;CUNEIFORM NUMERIC SIGN ONE ESHE3;Nl;0;L;;;;1;N;;;;; 12459;CUNEIFORM NUMERIC SIGN TWO ESHE3;Nl;0;L;;;;2;N;;;;; 1245A;CUNEIFORM NUMERIC SIGN ONE THIRD DISH;Nl;0;L;;;;1/3;N;;;;; 1245B;CUNEIFORM NUMERIC SIGN TWO THIRDS DISH;Nl;0;L;;;;2/3;N;;;;; 1245C;CUNEIFORM NUMERIC SIGN FIVE SIXTHS DISH;Nl;0;L;;;;5/6;N;;;;; 1245D;CUNEIFORM NUMERIC SIGN ONE THIRD VARIANT FORM A;Nl;0;L;;;;1/3;N;;;;; 1245E;CUNEIFORM NUMERIC SIGN TWO THIRDS VARIANT FORM A;Nl;0;L;;;;2/3;N;;;;; 1245F;CUNEIFORM NUMERIC SIGN ONE EIGHTH ASH;Nl;0;L;;;;1/8;N;;;;; 12460;CUNEIFORM NUMERIC SIGN ONE QUARTER ASH;Nl;0;L;;;;1/4;N;;;;; 12461;CUNEIFORM NUMERIC SIGN OLD ASSYRIAN ONE SIXTH;Nl;0;L;;;;1/6;N;;;;; 12462;CUNEIFORM NUMERIC SIGN OLD ASSYRIAN ONE QUARTER;Nl;0;L;;;;1/4;N;;;;; 12463;CUNEIFORM NUMERIC SIGN ONE QUARTER GUR;Nl;0;L;;;;1/4;N;;;;; 12464;CUNEIFORM NUMERIC SIGN ONE HALF GUR;Nl;0;L;;;;1/2;N;;;;; 12465;CUNEIFORM NUMERIC SIGN ELAMITE ONE THIRD;Nl;0;L;;;;1/3;N;;;;; 12466;CUNEIFORM NUMERIC SIGN ELAMITE TWO THIRDS;Nl;0;L;;;;2/3;N;;;;; 12467;CUNEIFORM NUMERIC SIGN ELAMITE FORTY;Nl;0;L;;;;40;N;;;;; 12468;CUNEIFORM NUMERIC SIGN ELAMITE FIFTY;Nl;0;L;;;;50;N;;;;; 12469;CUNEIFORM NUMERIC SIGN FOUR U VARIANT FORM;Nl;0;L;;;;4;N;;;;; 1246A;CUNEIFORM NUMERIC SIGN FIVE U VARIANT FORM;Nl;0;L;;;;5;N;;;;; 1246B;CUNEIFORM NUMERIC SIGN SIX U VARIANT FORM;Nl;0;L;;;;6;N;;;;; 1246C;CUNEIFORM NUMERIC SIGN SEVEN U VARIANT FORM;Nl;0;L;;;;7;N;;;;; 1246D;CUNEIFORM NUMERIC SIGN EIGHT U VARIANT FORM;Nl;0;L;;;;8;N;;;;; 1246E;CUNEIFORM NUMERIC SIGN NINE U VARIANT FORM;Nl;0;L;;;;9;N;;;;; 12470;CUNEIFORM PUNCTUATION SIGN OLD ASSYRIAN WORD DIVIDER;Po;0;L;;;;;N;;;;; 12471;CUNEIFORM PUNCTUATION SIGN VERTICAL COLON;Po;0;L;;;;;N;;;;; 12472;CUNEIFORM PUNCTUATION SIGN DIAGONAL COLON;Po;0;L;;;;;N;;;;; 12473;CUNEIFORM PUNCTUATION SIGN DIAGONAL TRICOLON;Po;0;L;;;;;N;;;;; 12474;CUNEIFORM PUNCTUATION SIGN DIAGONAL QUADCOLON;Po;0;L;;;;;N;;;;; 13000;EGYPTIAN HIEROGLYPH A001;Lo;0;L;;;;;N;;;;; 13001;EGYPTIAN HIEROGLYPH A002;Lo;0;L;;;;;N;;;;; 13002;EGYPTIAN HIEROGLYPH A003;Lo;0;L;;;;;N;;;;; 13003;EGYPTIAN HIEROGLYPH A004;Lo;0;L;;;;;N;;;;; 13004;EGYPTIAN HIEROGLYPH A005;Lo;0;L;;;;;N;;;;; 13005;EGYPTIAN HIEROGLYPH A005A;Lo;0;L;;;;;N;;;;; 13006;EGYPTIAN HIEROGLYPH A006;Lo;0;L;;;;;N;;;;; 13007;EGYPTIAN HIEROGLYPH A006A;Lo;0;L;;;;;N;;;;; 13008;EGYPTIAN HIEROGLYPH A006B;Lo;0;L;;;;;N;;;;; 13009;EGYPTIAN HIEROGLYPH A007;Lo;0;L;;;;;N;;;;; 1300A;EGYPTIAN HIEROGLYPH A008;Lo;0;L;;;;;N;;;;; 1300B;EGYPTIAN HIEROGLYPH A009;Lo;0;L;;;;;N;;;;; 1300C;EGYPTIAN HIEROGLYPH A010;Lo;0;L;;;;;N;;;;; 1300D;EGYPTIAN HIEROGLYPH A011;Lo;0;L;;;;;N;;;;; 1300E;EGYPTIAN HIEROGLYPH A012;Lo;0;L;;;;;N;;;;; 1300F;EGYPTIAN HIEROGLYPH A013;Lo;0;L;;;;;N;;;;; 13010;EGYPTIAN HIEROGLYPH A014;Lo;0;L;;;;;N;;;;; 13011;EGYPTIAN HIEROGLYPH A014A;Lo;0;L;;;;;N;;;;; 13012;EGYPTIAN HIEROGLYPH A015;Lo;0;L;;;;;N;;;;; 13013;EGYPTIAN HIEROGLYPH A016;Lo;0;L;;;;;N;;;;; 13014;EGYPTIAN HIEROGLYPH A017;Lo;0;L;;;;;N;;;;; 13015;EGYPTIAN HIEROGLYPH A017A;Lo;0;L;;;;;N;;;;; 13016;EGYPTIAN HIEROGLYPH A018;Lo;0;L;;;;;N;;;;; 13017;EGYPTIAN HIEROGLYPH A019;Lo;0;L;;;;;N;;;;; 13018;EGYPTIAN HIEROGLYPH A020;Lo;0;L;;;;;N;;;;; 13019;EGYPTIAN HIEROGLYPH A021;Lo;0;L;;;;;N;;;;; 1301A;EGYPTIAN HIEROGLYPH A022;Lo;0;L;;;;;N;;;;; 1301B;EGYPTIAN HIEROGLYPH A023;Lo;0;L;;;;;N;;;;; 1301C;EGYPTIAN HIEROGLYPH A024;Lo;0;L;;;;;N;;;;; 1301D;EGYPTIAN HIEROGLYPH A025;Lo;0;L;;;;;N;;;;; 1301E;EGYPTIAN HIEROGLYPH A026;Lo;0;L;;;;;N;;;;; 1301F;EGYPTIAN HIEROGLYPH A027;Lo;0;L;;;;;N;;;;; 13020;EGYPTIAN HIEROGLYPH A028;Lo;0;L;;;;;N;;;;; 13021;EGYPTIAN HIEROGLYPH A029;Lo;0;L;;;;;N;;;;; 13022;EGYPTIAN HIEROGLYPH A030;Lo;0;L;;;;;N;;;;; 13023;EGYPTIAN HIEROGLYPH A031;Lo;0;L;;;;;N;;;;; 13024;EGYPTIAN HIEROGLYPH A032;Lo;0;L;;;;;N;;;;; 13025;EGYPTIAN HIEROGLYPH A032A;Lo;0;L;;;;;N;;;;; 13026;EGYPTIAN HIEROGLYPH A033;Lo;0;L;;;;;N;;;;; 13027;EGYPTIAN HIEROGLYPH A034;Lo;0;L;;;;;N;;;;; 13028;EGYPTIAN HIEROGLYPH A035;Lo;0;L;;;;;N;;;;; 13029;EGYPTIAN HIEROGLYPH A036;Lo;0;L;;;;;N;;;;; 1302A;EGYPTIAN HIEROGLYPH A037;Lo;0;L;;;;;N;;;;; 1302B;EGYPTIAN HIEROGLYPH A038;Lo;0;L;;;;;N;;;;; 1302C;EGYPTIAN HIEROGLYPH A039;Lo;0;L;;;;;N;;;;; 1302D;EGYPTIAN HIEROGLYPH A040;Lo;0;L;;;;;N;;;;; 1302E;EGYPTIAN HIEROGLYPH A040A;Lo;0;L;;;;;N;;;;; 1302F;EGYPTIAN HIEROGLYPH A041;Lo;0;L;;;;;N;;;;; 13030;EGYPTIAN HIEROGLYPH A042;Lo;0;L;;;;;N;;;;; 13031;EGYPTIAN HIEROGLYPH A042A;Lo;0;L;;;;;N;;;;; 13032;EGYPTIAN HIEROGLYPH A043;Lo;0;L;;;;;N;;;;; 13033;EGYPTIAN HIEROGLYPH A043A;Lo;0;L;;;;;N;;;;; 13034;EGYPTIAN HIEROGLYPH A044;Lo;0;L;;;;;N;;;;; 13035;EGYPTIAN HIEROGLYPH A045;Lo;0;L;;;;;N;;;;; 13036;EGYPTIAN HIEROGLYPH A045A;Lo;0;L;;;;;N;;;;; 13037;EGYPTIAN HIEROGLYPH A046;Lo;0;L;;;;;N;;;;; 13038;EGYPTIAN HIEROGLYPH A047;Lo;0;L;;;;;N;;;;; 13039;EGYPTIAN HIEROGLYPH A048;Lo;0;L;;;;;N;;;;; 1303A;EGYPTIAN HIEROGLYPH A049;Lo;0;L;;;;;N;;;;; 1303B;EGYPTIAN HIEROGLYPH A050;Lo;0;L;;;;;N;;;;; 1303C;EGYPTIAN HIEROGLYPH A051;Lo;0;L;;;;;N;;;;; 1303D;EGYPTIAN HIEROGLYPH A052;Lo;0;L;;;;;N;;;;; 1303E;EGYPTIAN HIEROGLYPH A053;Lo;0;L;;;;;N;;;;; 1303F;EGYPTIAN HIEROGLYPH A054;Lo;0;L;;;;;N;;;;; 13040;EGYPTIAN HIEROGLYPH A055;Lo;0;L;;;;;N;;;;; 13041;EGYPTIAN HIEROGLYPH A056;Lo;0;L;;;;;N;;;;; 13042;EGYPTIAN HIEROGLYPH A057;Lo;0;L;;;;;N;;;;; 13043;EGYPTIAN HIEROGLYPH A058;Lo;0;L;;;;;N;;;;; 13044;EGYPTIAN HIEROGLYPH A059;Lo;0;L;;;;;N;;;;; 13045;EGYPTIAN HIEROGLYPH A060;Lo;0;L;;;;;N;;;;; 13046;EGYPTIAN HIEROGLYPH A061;Lo;0;L;;;;;N;;;;; 13047;EGYPTIAN HIEROGLYPH A062;Lo;0;L;;;;;N;;;;; 13048;EGYPTIAN HIEROGLYPH A063;Lo;0;L;;;;;N;;;;; 13049;EGYPTIAN HIEROGLYPH A064;Lo;0;L;;;;;N;;;;; 1304A;EGYPTIAN HIEROGLYPH A065;Lo;0;L;;;;;N;;;;; 1304B;EGYPTIAN HIEROGLYPH A066;Lo;0;L;;;;;N;;;;; 1304C;EGYPTIAN HIEROGLYPH A067;Lo;0;L;;;;;N;;;;; 1304D;EGYPTIAN HIEROGLYPH A068;Lo;0;L;;;;;N;;;;; 1304E;EGYPTIAN HIEROGLYPH A069;Lo;0;L;;;;;N;;;;; 1304F;EGYPTIAN HIEROGLYPH A070;Lo;0;L;;;;;N;;;;; 13050;EGYPTIAN HIEROGLYPH B001;Lo;0;L;;;;;N;;;;; 13051;EGYPTIAN HIEROGLYPH B002;Lo;0;L;;;;;N;;;;; 13052;EGYPTIAN HIEROGLYPH B003;Lo;0;L;;;;;N;;;;; 13053;EGYPTIAN HIEROGLYPH B004;Lo;0;L;;;;;N;;;;; 13054;EGYPTIAN HIEROGLYPH B005;Lo;0;L;;;;;N;;;;; 13055;EGYPTIAN HIEROGLYPH B005A;Lo;0;L;;;;;N;;;;; 13056;EGYPTIAN HIEROGLYPH B006;Lo;0;L;;;;;N;;;;; 13057;EGYPTIAN HIEROGLYPH B007;Lo;0;L;;;;;N;;;;; 13058;EGYPTIAN HIEROGLYPH B008;Lo;0;L;;;;;N;;;;; 13059;EGYPTIAN HIEROGLYPH B009;Lo;0;L;;;;;N;;;;; 1305A;EGYPTIAN HIEROGLYPH C001;Lo;0;L;;;;;N;;;;; 1305B;EGYPTIAN HIEROGLYPH C002;Lo;0;L;;;;;N;;;;; 1305C;EGYPTIAN HIEROGLYPH C002A;Lo;0;L;;;;;N;;;;; 1305D;EGYPTIAN HIEROGLYPH C002B;Lo;0;L;;;;;N;;;;; 1305E;EGYPTIAN HIEROGLYPH C002C;Lo;0;L;;;;;N;;;;; 1305F;EGYPTIAN HIEROGLYPH C003;Lo;0;L;;;;;N;;;;; 13060;EGYPTIAN HIEROGLYPH C004;Lo;0;L;;;;;N;;;;; 13061;EGYPTIAN HIEROGLYPH C005;Lo;0;L;;;;;N;;;;; 13062;EGYPTIAN HIEROGLYPH C006;Lo;0;L;;;;;N;;;;; 13063;EGYPTIAN HIEROGLYPH C007;Lo;0;L;;;;;N;;;;; 13064;EGYPTIAN HIEROGLYPH C008;Lo;0;L;;;;;N;;;;; 13065;EGYPTIAN HIEROGLYPH C009;Lo;0;L;;;;;N;;;;; 13066;EGYPTIAN HIEROGLYPH C010;Lo;0;L;;;;;N;;;;; 13067;EGYPTIAN HIEROGLYPH C010A;Lo;0;L;;;;;N;;;;; 13068;EGYPTIAN HIEROGLYPH C011;Lo;0;L;;;;;N;;;;; 13069;EGYPTIAN HIEROGLYPH C012;Lo;0;L;;;;;N;;;;; 1306A;EGYPTIAN HIEROGLYPH C013;Lo;0;L;;;;;N;;;;; 1306B;EGYPTIAN HIEROGLYPH C014;Lo;0;L;;;;;N;;;;; 1306C;EGYPTIAN HIEROGLYPH C015;Lo;0;L;;;;;N;;;;; 1306D;EGYPTIAN HIEROGLYPH C016;Lo;0;L;;;;;N;;;;; 1306E;EGYPTIAN HIEROGLYPH C017;Lo;0;L;;;;;N;;;;; 1306F;EGYPTIAN HIEROGLYPH C018;Lo;0;L;;;;;N;;;;; 13070;EGYPTIAN HIEROGLYPH C019;Lo;0;L;;;;;N;;;;; 13071;EGYPTIAN HIEROGLYPH C020;Lo;0;L;;;;;N;;;;; 13072;EGYPTIAN HIEROGLYPH C021;Lo;0;L;;;;;N;;;;; 13073;EGYPTIAN HIEROGLYPH C022;Lo;0;L;;;;;N;;;;; 13074;EGYPTIAN HIEROGLYPH C023;Lo;0;L;;;;;N;;;;; 13075;EGYPTIAN HIEROGLYPH C024;Lo;0;L;;;;;N;;;;; 13076;EGYPTIAN HIEROGLYPH D001;Lo;0;L;;;;;N;;;;; 13077;EGYPTIAN HIEROGLYPH D002;Lo;0;L;;;;;N;;;;; 13078;EGYPTIAN HIEROGLYPH D003;Lo;0;L;;;;;N;;;;; 13079;EGYPTIAN HIEROGLYPH D004;Lo;0;L;;;;;N;;;;; 1307A;EGYPTIAN HIEROGLYPH D005;Lo;0;L;;;;;N;;;;; 1307B;EGYPTIAN HIEROGLYPH D006;Lo;0;L;;;;;N;;;;; 1307C;EGYPTIAN HIEROGLYPH D007;Lo;0;L;;;;;N;;;;; 1307D;EGYPTIAN HIEROGLYPH D008;Lo;0;L;;;;;N;;;;; 1307E;EGYPTIAN HIEROGLYPH D008A;Lo;0;L;;;;;N;;;;; 1307F;EGYPTIAN HIEROGLYPH D009;Lo;0;L;;;;;N;;;;; 13080;EGYPTIAN HIEROGLYPH D010;Lo;0;L;;;;;N;;;;; 13081;EGYPTIAN HIEROGLYPH D011;Lo;0;L;;;;;N;;;;; 13082;EGYPTIAN HIEROGLYPH D012;Lo;0;L;;;;;N;;;;; 13083;EGYPTIAN HIEROGLYPH D013;Lo;0;L;;;;;N;;;;; 13084;EGYPTIAN HIEROGLYPH D014;Lo;0;L;;;;;N;;;;; 13085;EGYPTIAN HIEROGLYPH D015;Lo;0;L;;;;;N;;;;; 13086;EGYPTIAN HIEROGLYPH D016;Lo;0;L;;;;;N;;;;; 13087;EGYPTIAN HIEROGLYPH D017;Lo;0;L;;;;;N;;;;; 13088;EGYPTIAN HIEROGLYPH D018;Lo;0;L;;;;;N;;;;; 13089;EGYPTIAN HIEROGLYPH D019;Lo;0;L;;;;;N;;;;; 1308A;EGYPTIAN HIEROGLYPH D020;Lo;0;L;;;;;N;;;;; 1308B;EGYPTIAN HIEROGLYPH D021;Lo;0;L;;;;;N;;;;; 1308C;EGYPTIAN HIEROGLYPH D022;Lo;0;L;;;;;N;;;;; 1308D;EGYPTIAN HIEROGLYPH D023;Lo;0;L;;;;;N;;;;; 1308E;EGYPTIAN HIEROGLYPH D024;Lo;0;L;;;;;N;;;;; 1308F;EGYPTIAN HIEROGLYPH D025;Lo;0;L;;;;;N;;;;; 13090;EGYPTIAN HIEROGLYPH D026;Lo;0;L;;;;;N;;;;; 13091;EGYPTIAN HIEROGLYPH D027;Lo;0;L;;;;;N;;;;; 13092;EGYPTIAN HIEROGLYPH D027A;Lo;0;L;;;;;N;;;;; 13093;EGYPTIAN HIEROGLYPH D028;Lo;0;L;;;;;N;;;;; 13094;EGYPTIAN HIEROGLYPH D029;Lo;0;L;;;;;N;;;;; 13095;EGYPTIAN HIEROGLYPH D030;Lo;0;L;;;;;N;;;;; 13096;EGYPTIAN HIEROGLYPH D031;Lo;0;L;;;;;N;;;;; 13097;EGYPTIAN HIEROGLYPH D031A;Lo;0;L;;;;;N;;;;; 13098;EGYPTIAN HIEROGLYPH D032;Lo;0;L;;;;;N;;;;; 13099;EGYPTIAN HIEROGLYPH D033;Lo;0;L;;;;;N;;;;; 1309A;EGYPTIAN HIEROGLYPH D034;Lo;0;L;;;;;N;;;;; 1309B;EGYPTIAN HIEROGLYPH D034A;Lo;0;L;;;;;N;;;;; 1309C;EGYPTIAN HIEROGLYPH D035;Lo;0;L;;;;;N;;;;; 1309D;EGYPTIAN HIEROGLYPH D036;Lo;0;L;;;;;N;;;;; 1309E;EGYPTIAN HIEROGLYPH D037;Lo;0;L;;;;;N;;;;; 1309F;EGYPTIAN HIEROGLYPH D038;Lo;0;L;;;;;N;;;;; 130A0;EGYPTIAN HIEROGLYPH D039;Lo;0;L;;;;;N;;;;; 130A1;EGYPTIAN HIEROGLYPH D040;Lo;0;L;;;;;N;;;;; 130A2;EGYPTIAN HIEROGLYPH D041;Lo;0;L;;;;;N;;;;; 130A3;EGYPTIAN HIEROGLYPH D042;Lo;0;L;;;;;N;;;;; 130A4;EGYPTIAN HIEROGLYPH D043;Lo;0;L;;;;;N;;;;; 130A5;EGYPTIAN HIEROGLYPH D044;Lo;0;L;;;;;N;;;;; 130A6;EGYPTIAN HIEROGLYPH D045;Lo;0;L;;;;;N;;;;; 130A7;EGYPTIAN HIEROGLYPH D046;Lo;0;L;;;;;N;;;;; 130A8;EGYPTIAN HIEROGLYPH D046A;Lo;0;L;;;;;N;;;;; 130A9;EGYPTIAN HIEROGLYPH D047;Lo;0;L;;;;;N;;;;; 130AA;EGYPTIAN HIEROGLYPH D048;Lo;0;L;;;;;N;;;;; 130AB;EGYPTIAN HIEROGLYPH D048A;Lo;0;L;;;;;N;;;;; 130AC;EGYPTIAN HIEROGLYPH D049;Lo;0;L;;;;;N;;;;; 130AD;EGYPTIAN HIEROGLYPH D050;Lo;0;L;;;;;N;;;;; 130AE;EGYPTIAN HIEROGLYPH D050A;Lo;0;L;;;;;N;;;;; 130AF;EGYPTIAN HIEROGLYPH D050B;Lo;0;L;;;;;N;;;;; 130B0;EGYPTIAN HIEROGLYPH D050C;Lo;0;L;;;;;N;;;;; 130B1;EGYPTIAN HIEROGLYPH D050D;Lo;0;L;;;;;N;;;;; 130B2;EGYPTIAN HIEROGLYPH D050E;Lo;0;L;;;;;N;;;;; 130B3;EGYPTIAN HIEROGLYPH D050F;Lo;0;L;;;;;N;;;;; 130B4;EGYPTIAN HIEROGLYPH D050G;Lo;0;L;;;;;N;;;;; 130B5;EGYPTIAN HIEROGLYPH D050H;Lo;0;L;;;;;N;;;;; 130B6;EGYPTIAN HIEROGLYPH D050I;Lo;0;L;;;;;N;;;;; 130B7;EGYPTIAN HIEROGLYPH D051;Lo;0;L;;;;;N;;;;; 130B8;EGYPTIAN HIEROGLYPH D052;Lo;0;L;;;;;N;;;;; 130B9;EGYPTIAN HIEROGLYPH D052A;Lo;0;L;;;;;N;;;;; 130BA;EGYPTIAN HIEROGLYPH D053;Lo;0;L;;;;;N;;;;; 130BB;EGYPTIAN HIEROGLYPH D054;Lo;0;L;;;;;N;;;;; 130BC;EGYPTIAN HIEROGLYPH D054A;Lo;0;L;;;;;N;;;;; 130BD;EGYPTIAN HIEROGLYPH D055;Lo;0;L;;;;;N;;;;; 130BE;EGYPTIAN HIEROGLYPH D056;Lo;0;L;;;;;N;;;;; 130BF;EGYPTIAN HIEROGLYPH D057;Lo;0;L;;;;;N;;;;; 130C0;EGYPTIAN HIEROGLYPH D058;Lo;0;L;;;;;N;;;;; 130C1;EGYPTIAN HIEROGLYPH D059;Lo;0;L;;;;;N;;;;; 130C2;EGYPTIAN HIEROGLYPH D060;Lo;0;L;;;;;N;;;;; 130C3;EGYPTIAN HIEROGLYPH D061;Lo;0;L;;;;;N;;;;; 130C4;EGYPTIAN HIEROGLYPH D062;Lo;0;L;;;;;N;;;;; 130C5;EGYPTIAN HIEROGLYPH D063;Lo;0;L;;;;;N;;;;; 130C6;EGYPTIAN HIEROGLYPH D064;Lo;0;L;;;;;N;;;;; 130C7;EGYPTIAN HIEROGLYPH D065;Lo;0;L;;;;;N;;;;; 130C8;EGYPTIAN HIEROGLYPH D066;Lo;0;L;;;;;N;;;;; 130C9;EGYPTIAN HIEROGLYPH D067;Lo;0;L;;;;;N;;;;; 130CA;EGYPTIAN HIEROGLYPH D067A;Lo;0;L;;;;;N;;;;; 130CB;EGYPTIAN HIEROGLYPH D067B;Lo;0;L;;;;;N;;;;; 130CC;EGYPTIAN HIEROGLYPH D067C;Lo;0;L;;;;;N;;;;; 130CD;EGYPTIAN HIEROGLYPH D067D;Lo;0;L;;;;;N;;;;; 130CE;EGYPTIAN HIEROGLYPH D067E;Lo;0;L;;;;;N;;;;; 130CF;EGYPTIAN HIEROGLYPH D067F;Lo;0;L;;;;;N;;;;; 130D0;EGYPTIAN HIEROGLYPH D067G;Lo;0;L;;;;;N;;;;; 130D1;EGYPTIAN HIEROGLYPH D067H;Lo;0;L;;;;;N;;;;; 130D2;EGYPTIAN HIEROGLYPH E001;Lo;0;L;;;;;N;;;;; 130D3;EGYPTIAN HIEROGLYPH E002;Lo;0;L;;;;;N;;;;; 130D4;EGYPTIAN HIEROGLYPH E003;Lo;0;L;;;;;N;;;;; 130D5;EGYPTIAN HIEROGLYPH E004;Lo;0;L;;;;;N;;;;; 130D6;EGYPTIAN HIEROGLYPH E005;Lo;0;L;;;;;N;;;;; 130D7;EGYPTIAN HIEROGLYPH E006;Lo;0;L;;;;;N;;;;; 130D8;EGYPTIAN HIEROGLYPH E007;Lo;0;L;;;;;N;;;;; 130D9;EGYPTIAN HIEROGLYPH E008;Lo;0;L;;;;;N;;;;; 130DA;EGYPTIAN HIEROGLYPH E008A;Lo;0;L;;;;;N;;;;; 130DB;EGYPTIAN HIEROGLYPH E009;Lo;0;L;;;;;N;;;;; 130DC;EGYPTIAN HIEROGLYPH E009A;Lo;0;L;;;;;N;;;;; 130DD;EGYPTIAN HIEROGLYPH E010;Lo;0;L;;;;;N;;;;; 130DE;EGYPTIAN HIEROGLYPH E011;Lo;0;L;;;;;N;;;;; 130DF;EGYPTIAN HIEROGLYPH E012;Lo;0;L;;;;;N;;;;; 130E0;EGYPTIAN HIEROGLYPH E013;Lo;0;L;;;;;N;;;;; 130E1;EGYPTIAN HIEROGLYPH E014;Lo;0;L;;;;;N;;;;; 130E2;EGYPTIAN HIEROGLYPH E015;Lo;0;L;;;;;N;;;;; 130E3;EGYPTIAN HIEROGLYPH E016;Lo;0;L;;;;;N;;;;; 130E4;EGYPTIAN HIEROGLYPH E016A;Lo;0;L;;;;;N;;;;; 130E5;EGYPTIAN HIEROGLYPH E017;Lo;0;L;;;;;N;;;;; 130E6;EGYPTIAN HIEROGLYPH E017A;Lo;0;L;;;;;N;;;;; 130E7;EGYPTIAN HIEROGLYPH E018;Lo;0;L;;;;;N;;;;; 130E8;EGYPTIAN HIEROGLYPH E019;Lo;0;L;;;;;N;;;;; 130E9;EGYPTIAN HIEROGLYPH E020;Lo;0;L;;;;;N;;;;; 130EA;EGYPTIAN HIEROGLYPH E020A;Lo;0;L;;;;;N;;;;; 130EB;EGYPTIAN HIEROGLYPH E021;Lo;0;L;;;;;N;;;;; 130EC;EGYPTIAN HIEROGLYPH E022;Lo;0;L;;;;;N;;;;; 130ED;EGYPTIAN HIEROGLYPH E023;Lo;0;L;;;;;N;;;;; 130EE;EGYPTIAN HIEROGLYPH E024;Lo;0;L;;;;;N;;;;; 130EF;EGYPTIAN HIEROGLYPH E025;Lo;0;L;;;;;N;;;;; 130F0;EGYPTIAN HIEROGLYPH E026;Lo;0;L;;;;;N;;;;; 130F1;EGYPTIAN HIEROGLYPH E027;Lo;0;L;;;;;N;;;;; 130F2;EGYPTIAN HIEROGLYPH E028;Lo;0;L;;;;;N;;;;; 130F3;EGYPTIAN HIEROGLYPH E028A;Lo;0;L;;;;;N;;;;; 130F4;EGYPTIAN HIEROGLYPH E029;Lo;0;L;;;;;N;;;;; 130F5;EGYPTIAN HIEROGLYPH E030;Lo;0;L;;;;;N;;;;; 130F6;EGYPTIAN HIEROGLYPH E031;Lo;0;L;;;;;N;;;;; 130F7;EGYPTIAN HIEROGLYPH E032;Lo;0;L;;;;;N;;;;; 130F8;EGYPTIAN HIEROGLYPH E033;Lo;0;L;;;;;N;;;;; 130F9;EGYPTIAN HIEROGLYPH E034;Lo;0;L;;;;;N;;;;; 130FA;EGYPTIAN HIEROGLYPH E034A;Lo;0;L;;;;;N;;;;; 130FB;EGYPTIAN HIEROGLYPH E036;Lo;0;L;;;;;N;;;;; 130FC;EGYPTIAN HIEROGLYPH E037;Lo;0;L;;;;;N;;;;; 130FD;EGYPTIAN HIEROGLYPH E038;Lo;0;L;;;;;N;;;;; 130FE;EGYPTIAN HIEROGLYPH F001;Lo;0;L;;;;;N;;;;; 130FF;EGYPTIAN HIEROGLYPH F001A;Lo;0;L;;;;;N;;;;; 13100;EGYPTIAN HIEROGLYPH F002;Lo;0;L;;;;;N;;;;; 13101;EGYPTIAN HIEROGLYPH F003;Lo;0;L;;;;;N;;;;; 13102;EGYPTIAN HIEROGLYPH F004;Lo;0;L;;;;;N;;;;; 13103;EGYPTIAN HIEROGLYPH F005;Lo;0;L;;;;;N;;;;; 13104;EGYPTIAN HIEROGLYPH F006;Lo;0;L;;;;;N;;;;; 13105;EGYPTIAN HIEROGLYPH F007;Lo;0;L;;;;;N;;;;; 13106;EGYPTIAN HIEROGLYPH F008;Lo;0;L;;;;;N;;;;; 13107;EGYPTIAN HIEROGLYPH F009;Lo;0;L;;;;;N;;;;; 13108;EGYPTIAN HIEROGLYPH F010;Lo;0;L;;;;;N;;;;; 13109;EGYPTIAN HIEROGLYPH F011;Lo;0;L;;;;;N;;;;; 1310A;EGYPTIAN HIEROGLYPH F012;Lo;0;L;;;;;N;;;;; 1310B;EGYPTIAN HIEROGLYPH F013;Lo;0;L;;;;;N;;;;; 1310C;EGYPTIAN HIEROGLYPH F013A;Lo;0;L;;;;;N;;;;; 1310D;EGYPTIAN HIEROGLYPH F014;Lo;0;L;;;;;N;;;;; 1310E;EGYPTIAN HIEROGLYPH F015;Lo;0;L;;;;;N;;;;; 1310F;EGYPTIAN HIEROGLYPH F016;Lo;0;L;;;;;N;;;;; 13110;EGYPTIAN HIEROGLYPH F017;Lo;0;L;;;;;N;;;;; 13111;EGYPTIAN HIEROGLYPH F018;Lo;0;L;;;;;N;;;;; 13112;EGYPTIAN HIEROGLYPH F019;Lo;0;L;;;;;N;;;;; 13113;EGYPTIAN HIEROGLYPH F020;Lo;0;L;;;;;N;;;;; 13114;EGYPTIAN HIEROGLYPH F021;Lo;0;L;;;;;N;;;;; 13115;EGYPTIAN HIEROGLYPH F021A;Lo;0;L;;;;;N;;;;; 13116;EGYPTIAN HIEROGLYPH F022;Lo;0;L;;;;;N;;;;; 13117;EGYPTIAN HIEROGLYPH F023;Lo;0;L;;;;;N;;;;; 13118;EGYPTIAN HIEROGLYPH F024;Lo;0;L;;;;;N;;;;; 13119;EGYPTIAN HIEROGLYPH F025;Lo;0;L;;;;;N;;;;; 1311A;EGYPTIAN HIEROGLYPH F026;Lo;0;L;;;;;N;;;;; 1311B;EGYPTIAN HIEROGLYPH F027;Lo;0;L;;;;;N;;;;; 1311C;EGYPTIAN HIEROGLYPH F028;Lo;0;L;;;;;N;;;;; 1311D;EGYPTIAN HIEROGLYPH F029;Lo;0;L;;;;;N;;;;; 1311E;EGYPTIAN HIEROGLYPH F030;Lo;0;L;;;;;N;;;;; 1311F;EGYPTIAN HIEROGLYPH F031;Lo;0;L;;;;;N;;;;; 13120;EGYPTIAN HIEROGLYPH F031A;Lo;0;L;;;;;N;;;;; 13121;EGYPTIAN HIEROGLYPH F032;Lo;0;L;;;;;N;;;;; 13122;EGYPTIAN HIEROGLYPH F033;Lo;0;L;;;;;N;;;;; 13123;EGYPTIAN HIEROGLYPH F034;Lo;0;L;;;;;N;;;;; 13124;EGYPTIAN HIEROGLYPH F035;Lo;0;L;;;;;N;;;;; 13125;EGYPTIAN HIEROGLYPH F036;Lo;0;L;;;;;N;;;;; 13126;EGYPTIAN HIEROGLYPH F037;Lo;0;L;;;;;N;;;;; 13127;EGYPTIAN HIEROGLYPH F037A;Lo;0;L;;;;;N;;;;; 13128;EGYPTIAN HIEROGLYPH F038;Lo;0;L;;;;;N;;;;; 13129;EGYPTIAN HIEROGLYPH F038A;Lo;0;L;;;;;N;;;;; 1312A;EGYPTIAN HIEROGLYPH F039;Lo;0;L;;;;;N;;;;; 1312B;EGYPTIAN HIEROGLYPH F040;Lo;0;L;;;;;N;;;;; 1312C;EGYPTIAN HIEROGLYPH F041;Lo;0;L;;;;;N;;;;; 1312D;EGYPTIAN HIEROGLYPH F042;Lo;0;L;;;;;N;;;;; 1312E;EGYPTIAN HIEROGLYPH F043;Lo;0;L;;;;;N;;;;; 1312F;EGYPTIAN HIEROGLYPH F044;Lo;0;L;;;;;N;;;;; 13130;EGYPTIAN HIEROGLYPH F045;Lo;0;L;;;;;N;;;;; 13131;EGYPTIAN HIEROGLYPH F045A;Lo;0;L;;;;;N;;;;; 13132;EGYPTIAN HIEROGLYPH F046;Lo;0;L;;;;;N;;;;; 13133;EGYPTIAN HIEROGLYPH F046A;Lo;0;L;;;;;N;;;;; 13134;EGYPTIAN HIEROGLYPH F047;Lo;0;L;;;;;N;;;;; 13135;EGYPTIAN HIEROGLYPH F047A;Lo;0;L;;;;;N;;;;; 13136;EGYPTIAN HIEROGLYPH F048;Lo;0;L;;;;;N;;;;; 13137;EGYPTIAN HIEROGLYPH F049;Lo;0;L;;;;;N;;;;; 13138;EGYPTIAN HIEROGLYPH F050;Lo;0;L;;;;;N;;;;; 13139;EGYPTIAN HIEROGLYPH F051;Lo;0;L;;;;;N;;;;; 1313A;EGYPTIAN HIEROGLYPH F051A;Lo;0;L;;;;;N;;;;; 1313B;EGYPTIAN HIEROGLYPH F051B;Lo;0;L;;;;;N;;;;; 1313C;EGYPTIAN HIEROGLYPH F051C;Lo;0;L;;;;;N;;;;; 1313D;EGYPTIAN HIEROGLYPH F052;Lo;0;L;;;;;N;;;;; 1313E;EGYPTIAN HIEROGLYPH F053;Lo;0;L;;;;;N;;;;; 1313F;EGYPTIAN HIEROGLYPH G001;Lo;0;L;;;;;N;;;;; 13140;EGYPTIAN HIEROGLYPH G002;Lo;0;L;;;;;N;;;;; 13141;EGYPTIAN HIEROGLYPH G003;Lo;0;L;;;;;N;;;;; 13142;EGYPTIAN HIEROGLYPH G004;Lo;0;L;;;;;N;;;;; 13143;EGYPTIAN HIEROGLYPH G005;Lo;0;L;;;;;N;;;;; 13144;EGYPTIAN HIEROGLYPH G006;Lo;0;L;;;;;N;;;;; 13145;EGYPTIAN HIEROGLYPH G006A;Lo;0;L;;;;;N;;;;; 13146;EGYPTIAN HIEROGLYPH G007;Lo;0;L;;;;;N;;;;; 13147;EGYPTIAN HIEROGLYPH G007A;Lo;0;L;;;;;N;;;;; 13148;EGYPTIAN HIEROGLYPH G007B;Lo;0;L;;;;;N;;;;; 13149;EGYPTIAN HIEROGLYPH G008;Lo;0;L;;;;;N;;;;; 1314A;EGYPTIAN HIEROGLYPH G009;Lo;0;L;;;;;N;;;;; 1314B;EGYPTIAN HIEROGLYPH G010;Lo;0;L;;;;;N;;;;; 1314C;EGYPTIAN HIEROGLYPH G011;Lo;0;L;;;;;N;;;;; 1314D;EGYPTIAN HIEROGLYPH G011A;Lo;0;L;;;;;N;;;;; 1314E;EGYPTIAN HIEROGLYPH G012;Lo;0;L;;;;;N;;;;; 1314F;EGYPTIAN HIEROGLYPH G013;Lo;0;L;;;;;N;;;;; 13150;EGYPTIAN HIEROGLYPH G014;Lo;0;L;;;;;N;;;;; 13151;EGYPTIAN HIEROGLYPH G015;Lo;0;L;;;;;N;;;;; 13152;EGYPTIAN HIEROGLYPH G016;Lo;0;L;;;;;N;;;;; 13153;EGYPTIAN HIEROGLYPH G017;Lo;0;L;;;;;N;;;;; 13154;EGYPTIAN HIEROGLYPH G018;Lo;0;L;;;;;N;;;;; 13155;EGYPTIAN HIEROGLYPH G019;Lo;0;L;;;;;N;;;;; 13156;EGYPTIAN HIEROGLYPH G020;Lo;0;L;;;;;N;;;;; 13157;EGYPTIAN HIEROGLYPH G020A;Lo;0;L;;;;;N;;;;; 13158;EGYPTIAN HIEROGLYPH G021;Lo;0;L;;;;;N;;;;; 13159;EGYPTIAN HIEROGLYPH G022;Lo;0;L;;;;;N;;;;; 1315A;EGYPTIAN HIEROGLYPH G023;Lo;0;L;;;;;N;;;;; 1315B;EGYPTIAN HIEROGLYPH G024;Lo;0;L;;;;;N;;;;; 1315C;EGYPTIAN HIEROGLYPH G025;Lo;0;L;;;;;N;;;;; 1315D;EGYPTIAN HIEROGLYPH G026;Lo;0;L;;;;;N;;;;; 1315E;EGYPTIAN HIEROGLYPH G026A;Lo;0;L;;;;;N;;;;; 1315F;EGYPTIAN HIEROGLYPH G027;Lo;0;L;;;;;N;;;;; 13160;EGYPTIAN HIEROGLYPH G028;Lo;0;L;;;;;N;;;;; 13161;EGYPTIAN HIEROGLYPH G029;Lo;0;L;;;;;N;;;;; 13162;EGYPTIAN HIEROGLYPH G030;Lo;0;L;;;;;N;;;;; 13163;EGYPTIAN HIEROGLYPH G031;Lo;0;L;;;;;N;;;;; 13164;EGYPTIAN HIEROGLYPH G032;Lo;0;L;;;;;N;;;;; 13165;EGYPTIAN HIEROGLYPH G033;Lo;0;L;;;;;N;;;;; 13166;EGYPTIAN HIEROGLYPH G034;Lo;0;L;;;;;N;;;;; 13167;EGYPTIAN HIEROGLYPH G035;Lo;0;L;;;;;N;;;;; 13168;EGYPTIAN HIEROGLYPH G036;Lo;0;L;;;;;N;;;;; 13169;EGYPTIAN HIEROGLYPH G036A;Lo;0;L;;;;;N;;;;; 1316A;EGYPTIAN HIEROGLYPH G037;Lo;0;L;;;;;N;;;;; 1316B;EGYPTIAN HIEROGLYPH G037A;Lo;0;L;;;;;N;;;;; 1316C;EGYPTIAN HIEROGLYPH G038;Lo;0;L;;;;;N;;;;; 1316D;EGYPTIAN HIEROGLYPH G039;Lo;0;L;;;;;N;;;;; 1316E;EGYPTIAN HIEROGLYPH G040;Lo;0;L;;;;;N;;;;; 1316F;EGYPTIAN HIEROGLYPH G041;Lo;0;L;;;;;N;;;;; 13170;EGYPTIAN HIEROGLYPH G042;Lo;0;L;;;;;N;;;;; 13171;EGYPTIAN HIEROGLYPH G043;Lo;0;L;;;;;N;;;;; 13172;EGYPTIAN HIEROGLYPH G043A;Lo;0;L;;;;;N;;;;; 13173;EGYPTIAN HIEROGLYPH G044;Lo;0;L;;;;;N;;;;; 13174;EGYPTIAN HIEROGLYPH G045;Lo;0;L;;;;;N;;;;; 13175;EGYPTIAN HIEROGLYPH G045A;Lo;0;L;;;;;N;;;;; 13176;EGYPTIAN HIEROGLYPH G046;Lo;0;L;;;;;N;;;;; 13177;EGYPTIAN HIEROGLYPH G047;Lo;0;L;;;;;N;;;;; 13178;EGYPTIAN HIEROGLYPH G048;Lo;0;L;;;;;N;;;;; 13179;EGYPTIAN HIEROGLYPH G049;Lo;0;L;;;;;N;;;;; 1317A;EGYPTIAN HIEROGLYPH G050;Lo;0;L;;;;;N;;;;; 1317B;EGYPTIAN HIEROGLYPH G051;Lo;0;L;;;;;N;;;;; 1317C;EGYPTIAN HIEROGLYPH G052;Lo;0;L;;;;;N;;;;; 1317D;EGYPTIAN HIEROGLYPH G053;Lo;0;L;;;;;N;;;;; 1317E;EGYPTIAN HIEROGLYPH G054;Lo;0;L;;;;;N;;;;; 1317F;EGYPTIAN HIEROGLYPH H001;Lo;0;L;;;;;N;;;;; 13180;EGYPTIAN HIEROGLYPH H002;Lo;0;L;;;;;N;;;;; 13181;EGYPTIAN HIEROGLYPH H003;Lo;0;L;;;;;N;;;;; 13182;EGYPTIAN HIEROGLYPH H004;Lo;0;L;;;;;N;;;;; 13183;EGYPTIAN HIEROGLYPH H005;Lo;0;L;;;;;N;;;;; 13184;EGYPTIAN HIEROGLYPH H006;Lo;0;L;;;;;N;;;;; 13185;EGYPTIAN HIEROGLYPH H006A;Lo;0;L;;;;;N;;;;; 13186;EGYPTIAN HIEROGLYPH H007;Lo;0;L;;;;;N;;;;; 13187;EGYPTIAN HIEROGLYPH H008;Lo;0;L;;;;;N;;;;; 13188;EGYPTIAN HIEROGLYPH I001;Lo;0;L;;;;;N;;;;; 13189;EGYPTIAN HIEROGLYPH I002;Lo;0;L;;;;;N;;;;; 1318A;EGYPTIAN HIEROGLYPH I003;Lo;0;L;;;;;N;;;;; 1318B;EGYPTIAN HIEROGLYPH I004;Lo;0;L;;;;;N;;;;; 1318C;EGYPTIAN HIEROGLYPH I005;Lo;0;L;;;;;N;;;;; 1318D;EGYPTIAN HIEROGLYPH I005A;Lo;0;L;;;;;N;;;;; 1318E;EGYPTIAN HIEROGLYPH I006;Lo;0;L;;;;;N;;;;; 1318F;EGYPTIAN HIEROGLYPH I007;Lo;0;L;;;;;N;;;;; 13190;EGYPTIAN HIEROGLYPH I008;Lo;0;L;;;;;N;;;;; 13191;EGYPTIAN HIEROGLYPH I009;Lo;0;L;;;;;N;;;;; 13192;EGYPTIAN HIEROGLYPH I009A;Lo;0;L;;;;;N;;;;; 13193;EGYPTIAN HIEROGLYPH I010;Lo;0;L;;;;;N;;;;; 13194;EGYPTIAN HIEROGLYPH I010A;Lo;0;L;;;;;N;;;;; 13195;EGYPTIAN HIEROGLYPH I011;Lo;0;L;;;;;N;;;;; 13196;EGYPTIAN HIEROGLYPH I011A;Lo;0;L;;;;;N;;;;; 13197;EGYPTIAN HIEROGLYPH I012;Lo;0;L;;;;;N;;;;; 13198;EGYPTIAN HIEROGLYPH I013;Lo;0;L;;;;;N;;;;; 13199;EGYPTIAN HIEROGLYPH I014;Lo;0;L;;;;;N;;;;; 1319A;EGYPTIAN HIEROGLYPH I015;Lo;0;L;;;;;N;;;;; 1319B;EGYPTIAN HIEROGLYPH K001;Lo;0;L;;;;;N;;;;; 1319C;EGYPTIAN HIEROGLYPH K002;Lo;0;L;;;;;N;;;;; 1319D;EGYPTIAN HIEROGLYPH K003;Lo;0;L;;;;;N;;;;; 1319E;EGYPTIAN HIEROGLYPH K004;Lo;0;L;;;;;N;;;;; 1319F;EGYPTIAN HIEROGLYPH K005;Lo;0;L;;;;;N;;;;; 131A0;EGYPTIAN HIEROGLYPH K006;Lo;0;L;;;;;N;;;;; 131A1;EGYPTIAN HIEROGLYPH K007;Lo;0;L;;;;;N;;;;; 131A2;EGYPTIAN HIEROGLYPH K008;Lo;0;L;;;;;N;;;;; 131A3;EGYPTIAN HIEROGLYPH L001;Lo;0;L;;;;;N;;;;; 131A4;EGYPTIAN HIEROGLYPH L002;Lo;0;L;;;;;N;;;;; 131A5;EGYPTIAN HIEROGLYPH L002A;Lo;0;L;;;;;N;;;;; 131A6;EGYPTIAN HIEROGLYPH L003;Lo;0;L;;;;;N;;;;; 131A7;EGYPTIAN HIEROGLYPH L004;Lo;0;L;;;;;N;;;;; 131A8;EGYPTIAN HIEROGLYPH L005;Lo;0;L;;;;;N;;;;; 131A9;EGYPTIAN HIEROGLYPH L006;Lo;0;L;;;;;N;;;;; 131AA;EGYPTIAN HIEROGLYPH L006A;Lo;0;L;;;;;N;;;;; 131AB;EGYPTIAN HIEROGLYPH L007;Lo;0;L;;;;;N;;;;; 131AC;EGYPTIAN HIEROGLYPH L008;Lo;0;L;;;;;N;;;;; 131AD;EGYPTIAN HIEROGLYPH M001;Lo;0;L;;;;;N;;;;; 131AE;EGYPTIAN HIEROGLYPH M001A;Lo;0;L;;;;;N;;;;; 131AF;EGYPTIAN HIEROGLYPH M001B;Lo;0;L;;;;;N;;;;; 131B0;EGYPTIAN HIEROGLYPH M002;Lo;0;L;;;;;N;;;;; 131B1;EGYPTIAN HIEROGLYPH M003;Lo;0;L;;;;;N;;;;; 131B2;EGYPTIAN HIEROGLYPH M003A;Lo;0;L;;;;;N;;;;; 131B3;EGYPTIAN HIEROGLYPH M004;Lo;0;L;;;;;N;;;;; 131B4;EGYPTIAN HIEROGLYPH M005;Lo;0;L;;;;;N;;;;; 131B5;EGYPTIAN HIEROGLYPH M006;Lo;0;L;;;;;N;;;;; 131B6;EGYPTIAN HIEROGLYPH M007;Lo;0;L;;;;;N;;;;; 131B7;EGYPTIAN HIEROGLYPH M008;Lo;0;L;;;;;N;;;;; 131B8;EGYPTIAN HIEROGLYPH M009;Lo;0;L;;;;;N;;;;; 131B9;EGYPTIAN HIEROGLYPH M010;Lo;0;L;;;;;N;;;;; 131BA;EGYPTIAN HIEROGLYPH M010A;Lo;0;L;;;;;N;;;;; 131BB;EGYPTIAN HIEROGLYPH M011;Lo;0;L;;;;;N;;;;; 131BC;EGYPTIAN HIEROGLYPH M012;Lo;0;L;;;;;N;;;;; 131BD;EGYPTIAN HIEROGLYPH M012A;Lo;0;L;;;;;N;;;;; 131BE;EGYPTIAN HIEROGLYPH M012B;Lo;0;L;;;;;N;;;;; 131BF;EGYPTIAN HIEROGLYPH M012C;Lo;0;L;;;;;N;;;;; 131C0;EGYPTIAN HIEROGLYPH M012D;Lo;0;L;;;;;N;;;;; 131C1;EGYPTIAN HIEROGLYPH M012E;Lo;0;L;;;;;N;;;;; 131C2;EGYPTIAN HIEROGLYPH M012F;Lo;0;L;;;;;N;;;;; 131C3;EGYPTIAN HIEROGLYPH M012G;Lo;0;L;;;;;N;;;;; 131C4;EGYPTIAN HIEROGLYPH M012H;Lo;0;L;;;;;N;;;;; 131C5;EGYPTIAN HIEROGLYPH M013;Lo;0;L;;;;;N;;;;; 131C6;EGYPTIAN HIEROGLYPH M014;Lo;0;L;;;;;N;;;;; 131C7;EGYPTIAN HIEROGLYPH M015;Lo;0;L;;;;;N;;;;; 131C8;EGYPTIAN HIEROGLYPH M015A;Lo;0;L;;;;;N;;;;; 131C9;EGYPTIAN HIEROGLYPH M016;Lo;0;L;;;;;N;;;;; 131CA;EGYPTIAN HIEROGLYPH M016A;Lo;0;L;;;;;N;;;;; 131CB;EGYPTIAN HIEROGLYPH M017;Lo;0;L;;;;;N;;;;; 131CC;EGYPTIAN HIEROGLYPH M017A;Lo;0;L;;;;;N;;;;; 131CD;EGYPTIAN HIEROGLYPH M018;Lo;0;L;;;;;N;;;;; 131CE;EGYPTIAN HIEROGLYPH M019;Lo;0;L;;;;;N;;;;; 131CF;EGYPTIAN HIEROGLYPH M020;Lo;0;L;;;;;N;;;;; 131D0;EGYPTIAN HIEROGLYPH M021;Lo;0;L;;;;;N;;;;; 131D1;EGYPTIAN HIEROGLYPH M022;Lo;0;L;;;;;N;;;;; 131D2;EGYPTIAN HIEROGLYPH M022A;Lo;0;L;;;;;N;;;;; 131D3;EGYPTIAN HIEROGLYPH M023;Lo;0;L;;;;;N;;;;; 131D4;EGYPTIAN HIEROGLYPH M024;Lo;0;L;;;;;N;;;;; 131D5;EGYPTIAN HIEROGLYPH M024A;Lo;0;L;;;;;N;;;;; 131D6;EGYPTIAN HIEROGLYPH M025;Lo;0;L;;;;;N;;;;; 131D7;EGYPTIAN HIEROGLYPH M026;Lo;0;L;;;;;N;;;;; 131D8;EGYPTIAN HIEROGLYPH M027;Lo;0;L;;;;;N;;;;; 131D9;EGYPTIAN HIEROGLYPH M028;Lo;0;L;;;;;N;;;;; 131DA;EGYPTIAN HIEROGLYPH M028A;Lo;0;L;;;;;N;;;;; 131DB;EGYPTIAN HIEROGLYPH M029;Lo;0;L;;;;;N;;;;; 131DC;EGYPTIAN HIEROGLYPH M030;Lo;0;L;;;;;N;;;;; 131DD;EGYPTIAN HIEROGLYPH M031;Lo;0;L;;;;;N;;;;; 131DE;EGYPTIAN HIEROGLYPH M031A;Lo;0;L;;;;;N;;;;; 131DF;EGYPTIAN HIEROGLYPH M032;Lo;0;L;;;;;N;;;;; 131E0;EGYPTIAN HIEROGLYPH M033;Lo;0;L;;;;;N;;;;; 131E1;EGYPTIAN HIEROGLYPH M033A;Lo;0;L;;;;;N;;;;; 131E2;EGYPTIAN HIEROGLYPH M033B;Lo;0;L;;;;;N;;;;; 131E3;EGYPTIAN HIEROGLYPH M034;Lo;0;L;;;;;N;;;;; 131E4;EGYPTIAN HIEROGLYPH M035;Lo;0;L;;;;;N;;;;; 131E5;EGYPTIAN HIEROGLYPH M036;Lo;0;L;;;;;N;;;;; 131E6;EGYPTIAN HIEROGLYPH M037;Lo;0;L;;;;;N;;;;; 131E7;EGYPTIAN HIEROGLYPH M038;Lo;0;L;;;;;N;;;;; 131E8;EGYPTIAN HIEROGLYPH M039;Lo;0;L;;;;;N;;;;; 131E9;EGYPTIAN HIEROGLYPH M040;Lo;0;L;;;;;N;;;;; 131EA;EGYPTIAN HIEROGLYPH M040A;Lo;0;L;;;;;N;;;;; 131EB;EGYPTIAN HIEROGLYPH M041;Lo;0;L;;;;;N;;;;; 131EC;EGYPTIAN HIEROGLYPH M042;Lo;0;L;;;;;N;;;;; 131ED;EGYPTIAN HIEROGLYPH M043;Lo;0;L;;;;;N;;;;; 131EE;EGYPTIAN HIEROGLYPH M044;Lo;0;L;;;;;N;;;;; 131EF;EGYPTIAN HIEROGLYPH N001;Lo;0;L;;;;;N;;;;; 131F0;EGYPTIAN HIEROGLYPH N002;Lo;0;L;;;;;N;;;;; 131F1;EGYPTIAN HIEROGLYPH N003;Lo;0;L;;;;;N;;;;; 131F2;EGYPTIAN HIEROGLYPH N004;Lo;0;L;;;;;N;;;;; 131F3;EGYPTIAN HIEROGLYPH N005;Lo;0;L;;;;;N;;;;; 131F4;EGYPTIAN HIEROGLYPH N006;Lo;0;L;;;;;N;;;;; 131F5;EGYPTIAN HIEROGLYPH N007;Lo;0;L;;;;;N;;;;; 131F6;EGYPTIAN HIEROGLYPH N008;Lo;0;L;;;;;N;;;;; 131F7;EGYPTIAN HIEROGLYPH N009;Lo;0;L;;;;;N;;;;; 131F8;EGYPTIAN HIEROGLYPH N010;Lo;0;L;;;;;N;;;;; 131F9;EGYPTIAN HIEROGLYPH N011;Lo;0;L;;;;;N;;;;; 131FA;EGYPTIAN HIEROGLYPH N012;Lo;0;L;;;;;N;;;;; 131FB;EGYPTIAN HIEROGLYPH N013;Lo;0;L;;;;;N;;;;; 131FC;EGYPTIAN HIEROGLYPH N014;Lo;0;L;;;;;N;;;;; 131FD;EGYPTIAN HIEROGLYPH N015;Lo;0;L;;;;;N;;;;; 131FE;EGYPTIAN HIEROGLYPH N016;Lo;0;L;;;;;N;;;;; 131FF;EGYPTIAN HIEROGLYPH N017;Lo;0;L;;;;;N;;;;; 13200;EGYPTIAN HIEROGLYPH N018;Lo;0;L;;;;;N;;;;; 13201;EGYPTIAN HIEROGLYPH N018A;Lo;0;L;;;;;N;;;;; 13202;EGYPTIAN HIEROGLYPH N018B;Lo;0;L;;;;;N;;;;; 13203;EGYPTIAN HIEROGLYPH N019;Lo;0;L;;;;;N;;;;; 13204;EGYPTIAN HIEROGLYPH N020;Lo;0;L;;;;;N;;;;; 13205;EGYPTIAN HIEROGLYPH N021;Lo;0;L;;;;;N;;;;; 13206;EGYPTIAN HIEROGLYPH N022;Lo;0;L;;;;;N;;;;; 13207;EGYPTIAN HIEROGLYPH N023;Lo;0;L;;;;;N;;;;; 13208;EGYPTIAN HIEROGLYPH N024;Lo;0;L;;;;;N;;;;; 13209;EGYPTIAN HIEROGLYPH N025;Lo;0;L;;;;;N;;;;; 1320A;EGYPTIAN HIEROGLYPH N025A;Lo;0;L;;;;;N;;;;; 1320B;EGYPTIAN HIEROGLYPH N026;Lo;0;L;;;;;N;;;;; 1320C;EGYPTIAN HIEROGLYPH N027;Lo;0;L;;;;;N;;;;; 1320D;EGYPTIAN HIEROGLYPH N028;Lo;0;L;;;;;N;;;;; 1320E;EGYPTIAN HIEROGLYPH N029;Lo;0;L;;;;;N;;;;; 1320F;EGYPTIAN HIEROGLYPH N030;Lo;0;L;;;;;N;;;;; 13210;EGYPTIAN HIEROGLYPH N031;Lo;0;L;;;;;N;;;;; 13211;EGYPTIAN HIEROGLYPH N032;Lo;0;L;;;;;N;;;;; 13212;EGYPTIAN HIEROGLYPH N033;Lo;0;L;;;;;N;;;;; 13213;EGYPTIAN HIEROGLYPH N033A;Lo;0;L;;;;;N;;;;; 13214;EGYPTIAN HIEROGLYPH N034;Lo;0;L;;;;;N;;;;; 13215;EGYPTIAN HIEROGLYPH N034A;Lo;0;L;;;;;N;;;;; 13216;EGYPTIAN HIEROGLYPH N035;Lo;0;L;;;;;N;;;;; 13217;EGYPTIAN HIEROGLYPH N035A;Lo;0;L;;;;;N;;;;; 13218;EGYPTIAN HIEROGLYPH N036;Lo;0;L;;;;;N;;;;; 13219;EGYPTIAN HIEROGLYPH N037;Lo;0;L;;;;;N;;;;; 1321A;EGYPTIAN HIEROGLYPH N037A;Lo;0;L;;;;;N;;;;; 1321B;EGYPTIAN HIEROGLYPH N038;Lo;0;L;;;;;N;;;;; 1321C;EGYPTIAN HIEROGLYPH N039;Lo;0;L;;;;;N;;;;; 1321D;EGYPTIAN HIEROGLYPH N040;Lo;0;L;;;;;N;;;;; 1321E;EGYPTIAN HIEROGLYPH N041;Lo;0;L;;;;;N;;;;; 1321F;EGYPTIAN HIEROGLYPH N042;Lo;0;L;;;;;N;;;;; 13220;EGYPTIAN HIEROGLYPH NL001;Lo;0;L;;;;;N;;;;; 13221;EGYPTIAN HIEROGLYPH NL002;Lo;0;L;;;;;N;;;;; 13222;EGYPTIAN HIEROGLYPH NL003;Lo;0;L;;;;;N;;;;; 13223;EGYPTIAN HIEROGLYPH NL004;Lo;0;L;;;;;N;;;;; 13224;EGYPTIAN HIEROGLYPH NL005;Lo;0;L;;;;;N;;;;; 13225;EGYPTIAN HIEROGLYPH NL005A;Lo;0;L;;;;;N;;;;; 13226;EGYPTIAN HIEROGLYPH NL006;Lo;0;L;;;;;N;;;;; 13227;EGYPTIAN HIEROGLYPH NL007;Lo;0;L;;;;;N;;;;; 13228;EGYPTIAN HIEROGLYPH NL008;Lo;0;L;;;;;N;;;;; 13229;EGYPTIAN HIEROGLYPH NL009;Lo;0;L;;;;;N;;;;; 1322A;EGYPTIAN HIEROGLYPH NL010;Lo;0;L;;;;;N;;;;; 1322B;EGYPTIAN HIEROGLYPH NL011;Lo;0;L;;;;;N;;;;; 1322C;EGYPTIAN HIEROGLYPH NL012;Lo;0;L;;;;;N;;;;; 1322D;EGYPTIAN HIEROGLYPH NL013;Lo;0;L;;;;;N;;;;; 1322E;EGYPTIAN HIEROGLYPH NL014;Lo;0;L;;;;;N;;;;; 1322F;EGYPTIAN HIEROGLYPH NL015;Lo;0;L;;;;;N;;;;; 13230;EGYPTIAN HIEROGLYPH NL016;Lo;0;L;;;;;N;;;;; 13231;EGYPTIAN HIEROGLYPH NL017;Lo;0;L;;;;;N;;;;; 13232;EGYPTIAN HIEROGLYPH NL017A;Lo;0;L;;;;;N;;;;; 13233;EGYPTIAN HIEROGLYPH NL018;Lo;0;L;;;;;N;;;;; 13234;EGYPTIAN HIEROGLYPH NL019;Lo;0;L;;;;;N;;;;; 13235;EGYPTIAN HIEROGLYPH NL020;Lo;0;L;;;;;N;;;;; 13236;EGYPTIAN HIEROGLYPH NU001;Lo;0;L;;;;;N;;;;; 13237;EGYPTIAN HIEROGLYPH NU002;Lo;0;L;;;;;N;;;;; 13238;EGYPTIAN HIEROGLYPH NU003;Lo;0;L;;;;;N;;;;; 13239;EGYPTIAN HIEROGLYPH NU004;Lo;0;L;;;;;N;;;;; 1323A;EGYPTIAN HIEROGLYPH NU005;Lo;0;L;;;;;N;;;;; 1323B;EGYPTIAN HIEROGLYPH NU006;Lo;0;L;;;;;N;;;;; 1323C;EGYPTIAN HIEROGLYPH NU007;Lo;0;L;;;;;N;;;;; 1323D;EGYPTIAN HIEROGLYPH NU008;Lo;0;L;;;;;N;;;;; 1323E;EGYPTIAN HIEROGLYPH NU009;Lo;0;L;;;;;N;;;;; 1323F;EGYPTIAN HIEROGLYPH NU010;Lo;0;L;;;;;N;;;;; 13240;EGYPTIAN HIEROGLYPH NU010A;Lo;0;L;;;;;N;;;;; 13241;EGYPTIAN HIEROGLYPH NU011;Lo;0;L;;;;;N;;;;; 13242;EGYPTIAN HIEROGLYPH NU011A;Lo;0;L;;;;;N;;;;; 13243;EGYPTIAN HIEROGLYPH NU012;Lo;0;L;;;;;N;;;;; 13244;EGYPTIAN HIEROGLYPH NU013;Lo;0;L;;;;;N;;;;; 13245;EGYPTIAN HIEROGLYPH NU014;Lo;0;L;;;;;N;;;;; 13246;EGYPTIAN HIEROGLYPH NU015;Lo;0;L;;;;;N;;;;; 13247;EGYPTIAN HIEROGLYPH NU016;Lo;0;L;;;;;N;;;;; 13248;EGYPTIAN HIEROGLYPH NU017;Lo;0;L;;;;;N;;;;; 13249;EGYPTIAN HIEROGLYPH NU018;Lo;0;L;;;;;N;;;;; 1324A;EGYPTIAN HIEROGLYPH NU018A;Lo;0;L;;;;;N;;;;; 1324B;EGYPTIAN HIEROGLYPH NU019;Lo;0;L;;;;;N;;;;; 1324C;EGYPTIAN HIEROGLYPH NU020;Lo;0;L;;;;;N;;;;; 1324D;EGYPTIAN HIEROGLYPH NU021;Lo;0;L;;;;;N;;;;; 1324E;EGYPTIAN HIEROGLYPH NU022;Lo;0;L;;;;;N;;;;; 1324F;EGYPTIAN HIEROGLYPH NU022A;Lo;0;L;;;;;N;;;;; 13250;EGYPTIAN HIEROGLYPH O001;Lo;0;L;;;;;N;;;;; 13251;EGYPTIAN HIEROGLYPH O001A;Lo;0;L;;;;;N;;;;; 13252;EGYPTIAN HIEROGLYPH O002;Lo;0;L;;;;;N;;;;; 13253;EGYPTIAN HIEROGLYPH O003;Lo;0;L;;;;;N;;;;; 13254;EGYPTIAN HIEROGLYPH O004;Lo;0;L;;;;;N;;;;; 13255;EGYPTIAN HIEROGLYPH O005;Lo;0;L;;;;;N;;;;; 13256;EGYPTIAN HIEROGLYPH O005A;Lo;0;L;;;;;N;;;;; 13257;EGYPTIAN HIEROGLYPH O006;Lo;0;L;;;;;N;;;;; 13258;EGYPTIAN HIEROGLYPH O006A;Lo;0;L;;;;;N;;;;; 13259;EGYPTIAN HIEROGLYPH O006B;Lo;0;L;;;;;N;;;;; 1325A;EGYPTIAN HIEROGLYPH O006C;Lo;0;L;;;;;N;;;;; 1325B;EGYPTIAN HIEROGLYPH O006D;Lo;0;L;;;;;N;;;;; 1325C;EGYPTIAN HIEROGLYPH O006E;Lo;0;L;;;;;N;;;;; 1325D;EGYPTIAN HIEROGLYPH O006F;Lo;0;L;;;;;N;;;;; 1325E;EGYPTIAN HIEROGLYPH O007;Lo;0;L;;;;;N;;;;; 1325F;EGYPTIAN HIEROGLYPH O008;Lo;0;L;;;;;N;;;;; 13260;EGYPTIAN HIEROGLYPH O009;Lo;0;L;;;;;N;;;;; 13261;EGYPTIAN HIEROGLYPH O010;Lo;0;L;;;;;N;;;;; 13262;EGYPTIAN HIEROGLYPH O010A;Lo;0;L;;;;;N;;;;; 13263;EGYPTIAN HIEROGLYPH O010B;Lo;0;L;;;;;N;;;;; 13264;EGYPTIAN HIEROGLYPH O010C;Lo;0;L;;;;;N;;;;; 13265;EGYPTIAN HIEROGLYPH O011;Lo;0;L;;;;;N;;;;; 13266;EGYPTIAN HIEROGLYPH O012;Lo;0;L;;;;;N;;;;; 13267;EGYPTIAN HIEROGLYPH O013;Lo;0;L;;;;;N;;;;; 13268;EGYPTIAN HIEROGLYPH O014;Lo;0;L;;;;;N;;;;; 13269;EGYPTIAN HIEROGLYPH O015;Lo;0;L;;;;;N;;;;; 1326A;EGYPTIAN HIEROGLYPH O016;Lo;0;L;;;;;N;;;;; 1326B;EGYPTIAN HIEROGLYPH O017;Lo;0;L;;;;;N;;;;; 1326C;EGYPTIAN HIEROGLYPH O018;Lo;0;L;;;;;N;;;;; 1326D;EGYPTIAN HIEROGLYPH O019;Lo;0;L;;;;;N;;;;; 1326E;EGYPTIAN HIEROGLYPH O019A;Lo;0;L;;;;;N;;;;; 1326F;EGYPTIAN HIEROGLYPH O020;Lo;0;L;;;;;N;;;;; 13270;EGYPTIAN HIEROGLYPH O020A;Lo;0;L;;;;;N;;;;; 13271;EGYPTIAN HIEROGLYPH O021;Lo;0;L;;;;;N;;;;; 13272;EGYPTIAN HIEROGLYPH O022;Lo;0;L;;;;;N;;;;; 13273;EGYPTIAN HIEROGLYPH O023;Lo;0;L;;;;;N;;;;; 13274;EGYPTIAN HIEROGLYPH O024;Lo;0;L;;;;;N;;;;; 13275;EGYPTIAN HIEROGLYPH O024A;Lo;0;L;;;;;N;;;;; 13276;EGYPTIAN HIEROGLYPH O025;Lo;0;L;;;;;N;;;;; 13277;EGYPTIAN HIEROGLYPH O025A;Lo;0;L;;;;;N;;;;; 13278;EGYPTIAN HIEROGLYPH O026;Lo;0;L;;;;;N;;;;; 13279;EGYPTIAN HIEROGLYPH O027;Lo;0;L;;;;;N;;;;; 1327A;EGYPTIAN HIEROGLYPH O028;Lo;0;L;;;;;N;;;;; 1327B;EGYPTIAN HIEROGLYPH O029;Lo;0;L;;;;;N;;;;; 1327C;EGYPTIAN HIEROGLYPH O029A;Lo;0;L;;;;;N;;;;; 1327D;EGYPTIAN HIEROGLYPH O030;Lo;0;L;;;;;N;;;;; 1327E;EGYPTIAN HIEROGLYPH O030A;Lo;0;L;;;;;N;;;;; 1327F;EGYPTIAN HIEROGLYPH O031;Lo;0;L;;;;;N;;;;; 13280;EGYPTIAN HIEROGLYPH O032;Lo;0;L;;;;;N;;;;; 13281;EGYPTIAN HIEROGLYPH O033;Lo;0;L;;;;;N;;;;; 13282;EGYPTIAN HIEROGLYPH O033A;Lo;0;L;;;;;N;;;;; 13283;EGYPTIAN HIEROGLYPH O034;Lo;0;L;;;;;N;;;;; 13284;EGYPTIAN HIEROGLYPH O035;Lo;0;L;;;;;N;;;;; 13285;EGYPTIAN HIEROGLYPH O036;Lo;0;L;;;;;N;;;;; 13286;EGYPTIAN HIEROGLYPH O036A;Lo;0;L;;;;;N;;;;; 13287;EGYPTIAN HIEROGLYPH O036B;Lo;0;L;;;;;N;;;;; 13288;EGYPTIAN HIEROGLYPH O036C;Lo;0;L;;;;;N;;;;; 13289;EGYPTIAN HIEROGLYPH O036D;Lo;0;L;;;;;N;;;;; 1328A;EGYPTIAN HIEROGLYPH O037;Lo;0;L;;;;;N;;;;; 1328B;EGYPTIAN HIEROGLYPH O038;Lo;0;L;;;;;N;;;;; 1328C;EGYPTIAN HIEROGLYPH O039;Lo;0;L;;;;;N;;;;; 1328D;EGYPTIAN HIEROGLYPH O040;Lo;0;L;;;;;N;;;;; 1328E;EGYPTIAN HIEROGLYPH O041;Lo;0;L;;;;;N;;;;; 1328F;EGYPTIAN HIEROGLYPH O042;Lo;0;L;;;;;N;;;;; 13290;EGYPTIAN HIEROGLYPH O043;Lo;0;L;;;;;N;;;;; 13291;EGYPTIAN HIEROGLYPH O044;Lo;0;L;;;;;N;;;;; 13292;EGYPTIAN HIEROGLYPH O045;Lo;0;L;;;;;N;;;;; 13293;EGYPTIAN HIEROGLYPH O046;Lo;0;L;;;;;N;;;;; 13294;EGYPTIAN HIEROGLYPH O047;Lo;0;L;;;;;N;;;;; 13295;EGYPTIAN HIEROGLYPH O048;Lo;0;L;;;;;N;;;;; 13296;EGYPTIAN HIEROGLYPH O049;Lo;0;L;;;;;N;;;;; 13297;EGYPTIAN HIEROGLYPH O050;Lo;0;L;;;;;N;;;;; 13298;EGYPTIAN HIEROGLYPH O050A;Lo;0;L;;;;;N;;;;; 13299;EGYPTIAN HIEROGLYPH O050B;Lo;0;L;;;;;N;;;;; 1329A;EGYPTIAN HIEROGLYPH O051;Lo;0;L;;;;;N;;;;; 1329B;EGYPTIAN HIEROGLYPH P001;Lo;0;L;;;;;N;;;;; 1329C;EGYPTIAN HIEROGLYPH P001A;Lo;0;L;;;;;N;;;;; 1329D;EGYPTIAN HIEROGLYPH P002;Lo;0;L;;;;;N;;;;; 1329E;EGYPTIAN HIEROGLYPH P003;Lo;0;L;;;;;N;;;;; 1329F;EGYPTIAN HIEROGLYPH P003A;Lo;0;L;;;;;N;;;;; 132A0;EGYPTIAN HIEROGLYPH P004;Lo;0;L;;;;;N;;;;; 132A1;EGYPTIAN HIEROGLYPH P005;Lo;0;L;;;;;N;;;;; 132A2;EGYPTIAN HIEROGLYPH P006;Lo;0;L;;;;;N;;;;; 132A3;EGYPTIAN HIEROGLYPH P007;Lo;0;L;;;;;N;;;;; 132A4;EGYPTIAN HIEROGLYPH P008;Lo;0;L;;;;;N;;;;; 132A5;EGYPTIAN HIEROGLYPH P009;Lo;0;L;;;;;N;;;;; 132A6;EGYPTIAN HIEROGLYPH P010;Lo;0;L;;;;;N;;;;; 132A7;EGYPTIAN HIEROGLYPH P011;Lo;0;L;;;;;N;;;;; 132A8;EGYPTIAN HIEROGLYPH Q001;Lo;0;L;;;;;N;;;;; 132A9;EGYPTIAN HIEROGLYPH Q002;Lo;0;L;;;;;N;;;;; 132AA;EGYPTIAN HIEROGLYPH Q003;Lo;0;L;;;;;N;;;;; 132AB;EGYPTIAN HIEROGLYPH Q004;Lo;0;L;;;;;N;;;;; 132AC;EGYPTIAN HIEROGLYPH Q005;Lo;0;L;;;;;N;;;;; 132AD;EGYPTIAN HIEROGLYPH Q006;Lo;0;L;;;;;N;;;;; 132AE;EGYPTIAN HIEROGLYPH Q007;Lo;0;L;;;;;N;;;;; 132AF;EGYPTIAN HIEROGLYPH R001;Lo;0;L;;;;;N;;;;; 132B0;EGYPTIAN HIEROGLYPH R002;Lo;0;L;;;;;N;;;;; 132B1;EGYPTIAN HIEROGLYPH R002A;Lo;0;L;;;;;N;;;;; 132B2;EGYPTIAN HIEROGLYPH R003;Lo;0;L;;;;;N;;;;; 132B3;EGYPTIAN HIEROGLYPH R003A;Lo;0;L;;;;;N;;;;; 132B4;EGYPTIAN HIEROGLYPH R003B;Lo;0;L;;;;;N;;;;; 132B5;EGYPTIAN HIEROGLYPH R004;Lo;0;L;;;;;N;;;;; 132B6;EGYPTIAN HIEROGLYPH R005;Lo;0;L;;;;;N;;;;; 132B7;EGYPTIAN HIEROGLYPH R006;Lo;0;L;;;;;N;;;;; 132B8;EGYPTIAN HIEROGLYPH R007;Lo;0;L;;;;;N;;;;; 132B9;EGYPTIAN HIEROGLYPH R008;Lo;0;L;;;;;N;;;;; 132BA;EGYPTIAN HIEROGLYPH R009;Lo;0;L;;;;;N;;;;; 132BB;EGYPTIAN HIEROGLYPH R010;Lo;0;L;;;;;N;;;;; 132BC;EGYPTIAN HIEROGLYPH R010A;Lo;0;L;;;;;N;;;;; 132BD;EGYPTIAN HIEROGLYPH R011;Lo;0;L;;;;;N;;;;; 132BE;EGYPTIAN HIEROGLYPH R012;Lo;0;L;;;;;N;;;;; 132BF;EGYPTIAN HIEROGLYPH R013;Lo;0;L;;;;;N;;;;; 132C0;EGYPTIAN HIEROGLYPH R014;Lo;0;L;;;;;N;;;;; 132C1;EGYPTIAN HIEROGLYPH R015;Lo;0;L;;;;;N;;;;; 132C2;EGYPTIAN HIEROGLYPH R016;Lo;0;L;;;;;N;;;;; 132C3;EGYPTIAN HIEROGLYPH R016A;Lo;0;L;;;;;N;;;;; 132C4;EGYPTIAN HIEROGLYPH R017;Lo;0;L;;;;;N;;;;; 132C5;EGYPTIAN HIEROGLYPH R018;Lo;0;L;;;;;N;;;;; 132C6;EGYPTIAN HIEROGLYPH R019;Lo;0;L;;;;;N;;;;; 132C7;EGYPTIAN HIEROGLYPH R020;Lo;0;L;;;;;N;;;;; 132C8;EGYPTIAN HIEROGLYPH R021;Lo;0;L;;;;;N;;;;; 132C9;EGYPTIAN HIEROGLYPH R022;Lo;0;L;;;;;N;;;;; 132CA;EGYPTIAN HIEROGLYPH R023;Lo;0;L;;;;;N;;;;; 132CB;EGYPTIAN HIEROGLYPH R024;Lo;0;L;;;;;N;;;;; 132CC;EGYPTIAN HIEROGLYPH R025;Lo;0;L;;;;;N;;;;; 132CD;EGYPTIAN HIEROGLYPH R026;Lo;0;L;;;;;N;;;;; 132CE;EGYPTIAN HIEROGLYPH R027;Lo;0;L;;;;;N;;;;; 132CF;EGYPTIAN HIEROGLYPH R028;Lo;0;L;;;;;N;;;;; 132D0;EGYPTIAN HIEROGLYPH R029;Lo;0;L;;;;;N;;;;; 132D1;EGYPTIAN HIEROGLYPH S001;Lo;0;L;;;;;N;;;;; 132D2;EGYPTIAN HIEROGLYPH S002;Lo;0;L;;;;;N;;;;; 132D3;EGYPTIAN HIEROGLYPH S002A;Lo;0;L;;;;;N;;;;; 132D4;EGYPTIAN HIEROGLYPH S003;Lo;0;L;;;;;N;;;;; 132D5;EGYPTIAN HIEROGLYPH S004;Lo;0;L;;;;;N;;;;; 132D6;EGYPTIAN HIEROGLYPH S005;Lo;0;L;;;;;N;;;;; 132D7;EGYPTIAN HIEROGLYPH S006;Lo;0;L;;;;;N;;;;; 132D8;EGYPTIAN HIEROGLYPH S006A;Lo;0;L;;;;;N;;;;; 132D9;EGYPTIAN HIEROGLYPH S007;Lo;0;L;;;;;N;;;;; 132DA;EGYPTIAN HIEROGLYPH S008;Lo;0;L;;;;;N;;;;; 132DB;EGYPTIAN HIEROGLYPH S009;Lo;0;L;;;;;N;;;;; 132DC;EGYPTIAN HIEROGLYPH S010;Lo;0;L;;;;;N;;;;; 132DD;EGYPTIAN HIEROGLYPH S011;Lo;0;L;;;;;N;;;;; 132DE;EGYPTIAN HIEROGLYPH S012;Lo;0;L;;;;;N;;;;; 132DF;EGYPTIAN HIEROGLYPH S013;Lo;0;L;;;;;N;;;;; 132E0;EGYPTIAN HIEROGLYPH S014;Lo;0;L;;;;;N;;;;; 132E1;EGYPTIAN HIEROGLYPH S014A;Lo;0;L;;;;;N;;;;; 132E2;EGYPTIAN HIEROGLYPH S014B;Lo;0;L;;;;;N;;;;; 132E3;EGYPTIAN HIEROGLYPH S015;Lo;0;L;;;;;N;;;;; 132E4;EGYPTIAN HIEROGLYPH S016;Lo;0;L;;;;;N;;;;; 132E5;EGYPTIAN HIEROGLYPH S017;Lo;0;L;;;;;N;;;;; 132E6;EGYPTIAN HIEROGLYPH S017A;Lo;0;L;;;;;N;;;;; 132E7;EGYPTIAN HIEROGLYPH S018;Lo;0;L;;;;;N;;;;; 132E8;EGYPTIAN HIEROGLYPH S019;Lo;0;L;;;;;N;;;;; 132E9;EGYPTIAN HIEROGLYPH S020;Lo;0;L;;;;;N;;;;; 132EA;EGYPTIAN HIEROGLYPH S021;Lo;0;L;;;;;N;;;;; 132EB;EGYPTIAN HIEROGLYPH S022;Lo;0;L;;;;;N;;;;; 132EC;EGYPTIAN HIEROGLYPH S023;Lo;0;L;;;;;N;;;;; 132ED;EGYPTIAN HIEROGLYPH S024;Lo;0;L;;;;;N;;;;; 132EE;EGYPTIAN HIEROGLYPH S025;Lo;0;L;;;;;N;;;;; 132EF;EGYPTIAN HIEROGLYPH S026;Lo;0;L;;;;;N;;;;; 132F0;EGYPTIAN HIEROGLYPH S026A;Lo;0;L;;;;;N;;;;; 132F1;EGYPTIAN HIEROGLYPH S026B;Lo;0;L;;;;;N;;;;; 132F2;EGYPTIAN HIEROGLYPH S027;Lo;0;L;;;;;N;;;;; 132F3;EGYPTIAN HIEROGLYPH S028;Lo;0;L;;;;;N;;;;; 132F4;EGYPTIAN HIEROGLYPH S029;Lo;0;L;;;;;N;;;;; 132F5;EGYPTIAN HIEROGLYPH S030;Lo;0;L;;;;;N;;;;; 132F6;EGYPTIAN HIEROGLYPH S031;Lo;0;L;;;;;N;;;;; 132F7;EGYPTIAN HIEROGLYPH S032;Lo;0;L;;;;;N;;;;; 132F8;EGYPTIAN HIEROGLYPH S033;Lo;0;L;;;;;N;;;;; 132F9;EGYPTIAN HIEROGLYPH S034;Lo;0;L;;;;;N;;;;; 132FA;EGYPTIAN HIEROGLYPH S035;Lo;0;L;;;;;N;;;;; 132FB;EGYPTIAN HIEROGLYPH S035A;Lo;0;L;;;;;N;;;;; 132FC;EGYPTIAN HIEROGLYPH S036;Lo;0;L;;;;;N;;;;; 132FD;EGYPTIAN HIEROGLYPH S037;Lo;0;L;;;;;N;;;;; 132FE;EGYPTIAN HIEROGLYPH S038;Lo;0;L;;;;;N;;;;; 132FF;EGYPTIAN HIEROGLYPH S039;Lo;0;L;;;;;N;;;;; 13300;EGYPTIAN HIEROGLYPH S040;Lo;0;L;;;;;N;;;;; 13301;EGYPTIAN HIEROGLYPH S041;Lo;0;L;;;;;N;;;;; 13302;EGYPTIAN HIEROGLYPH S042;Lo;0;L;;;;;N;;;;; 13303;EGYPTIAN HIEROGLYPH S043;Lo;0;L;;;;;N;;;;; 13304;EGYPTIAN HIEROGLYPH S044;Lo;0;L;;;;;N;;;;; 13305;EGYPTIAN HIEROGLYPH S045;Lo;0;L;;;;;N;;;;; 13306;EGYPTIAN HIEROGLYPH S046;Lo;0;L;;;;;N;;;;; 13307;EGYPTIAN HIEROGLYPH T001;Lo;0;L;;;;;N;;;;; 13308;EGYPTIAN HIEROGLYPH T002;Lo;0;L;;;;;N;;;;; 13309;EGYPTIAN HIEROGLYPH T003;Lo;0;L;;;;;N;;;;; 1330A;EGYPTIAN HIEROGLYPH T003A;Lo;0;L;;;;;N;;;;; 1330B;EGYPTIAN HIEROGLYPH T004;Lo;0;L;;;;;N;;;;; 1330C;EGYPTIAN HIEROGLYPH T005;Lo;0;L;;;;;N;;;;; 1330D;EGYPTIAN HIEROGLYPH T006;Lo;0;L;;;;;N;;;;; 1330E;EGYPTIAN HIEROGLYPH T007;Lo;0;L;;;;;N;;;;; 1330F;EGYPTIAN HIEROGLYPH T007A;Lo;0;L;;;;;N;;;;; 13310;EGYPTIAN HIEROGLYPH T008;Lo;0;L;;;;;N;;;;; 13311;EGYPTIAN HIEROGLYPH T008A;Lo;0;L;;;;;N;;;;; 13312;EGYPTIAN HIEROGLYPH T009;Lo;0;L;;;;;N;;;;; 13313;EGYPTIAN HIEROGLYPH T009A;Lo;0;L;;;;;N;;;;; 13314;EGYPTIAN HIEROGLYPH T010;Lo;0;L;;;;;N;;;;; 13315;EGYPTIAN HIEROGLYPH T011;Lo;0;L;;;;;N;;;;; 13316;EGYPTIAN HIEROGLYPH T011A;Lo;0;L;;;;;N;;;;; 13317;EGYPTIAN HIEROGLYPH T012;Lo;0;L;;;;;N;;;;; 13318;EGYPTIAN HIEROGLYPH T013;Lo;0;L;;;;;N;;;;; 13319;EGYPTIAN HIEROGLYPH T014;Lo;0;L;;;;;N;;;;; 1331A;EGYPTIAN HIEROGLYPH T015;Lo;0;L;;;;;N;;;;; 1331B;EGYPTIAN HIEROGLYPH T016;Lo;0;L;;;;;N;;;;; 1331C;EGYPTIAN HIEROGLYPH T016A;Lo;0;L;;;;;N;;;;; 1331D;EGYPTIAN HIEROGLYPH T017;Lo;0;L;;;;;N;;;;; 1331E;EGYPTIAN HIEROGLYPH T018;Lo;0;L;;;;;N;;;;; 1331F;EGYPTIAN HIEROGLYPH T019;Lo;0;L;;;;;N;;;;; 13320;EGYPTIAN HIEROGLYPH T020;Lo;0;L;;;;;N;;;;; 13321;EGYPTIAN HIEROGLYPH T021;Lo;0;L;;;;;N;;;;; 13322;EGYPTIAN HIEROGLYPH T022;Lo;0;L;;;;;N;;;;; 13323;EGYPTIAN HIEROGLYPH T023;Lo;0;L;;;;;N;;;;; 13324;EGYPTIAN HIEROGLYPH T024;Lo;0;L;;;;;N;;;;; 13325;EGYPTIAN HIEROGLYPH T025;Lo;0;L;;;;;N;;;;; 13326;EGYPTIAN HIEROGLYPH T026;Lo;0;L;;;;;N;;;;; 13327;EGYPTIAN HIEROGLYPH T027;Lo;0;L;;;;;N;;;;; 13328;EGYPTIAN HIEROGLYPH T028;Lo;0;L;;;;;N;;;;; 13329;EGYPTIAN HIEROGLYPH T029;Lo;0;L;;;;;N;;;;; 1332A;EGYPTIAN HIEROGLYPH T030;Lo;0;L;;;;;N;;;;; 1332B;EGYPTIAN HIEROGLYPH T031;Lo;0;L;;;;;N;;;;; 1332C;EGYPTIAN HIEROGLYPH T032;Lo;0;L;;;;;N;;;;; 1332D;EGYPTIAN HIEROGLYPH T032A;Lo;0;L;;;;;N;;;;; 1332E;EGYPTIAN HIEROGLYPH T033;Lo;0;L;;;;;N;;;;; 1332F;EGYPTIAN HIEROGLYPH T033A;Lo;0;L;;;;;N;;;;; 13330;EGYPTIAN HIEROGLYPH T034;Lo;0;L;;;;;N;;;;; 13331;EGYPTIAN HIEROGLYPH T035;Lo;0;L;;;;;N;;;;; 13332;EGYPTIAN HIEROGLYPH T036;Lo;0;L;;;;;N;;;;; 13333;EGYPTIAN HIEROGLYPH U001;Lo;0;L;;;;;N;;;;; 13334;EGYPTIAN HIEROGLYPH U002;Lo;0;L;;;;;N;;;;; 13335;EGYPTIAN HIEROGLYPH U003;Lo;0;L;;;;;N;;;;; 13336;EGYPTIAN HIEROGLYPH U004;Lo;0;L;;;;;N;;;;; 13337;EGYPTIAN HIEROGLYPH U005;Lo;0;L;;;;;N;;;;; 13338;EGYPTIAN HIEROGLYPH U006;Lo;0;L;;;;;N;;;;; 13339;EGYPTIAN HIEROGLYPH U006A;Lo;0;L;;;;;N;;;;; 1333A;EGYPTIAN HIEROGLYPH U006B;Lo;0;L;;;;;N;;;;; 1333B;EGYPTIAN HIEROGLYPH U007;Lo;0;L;;;;;N;;;;; 1333C;EGYPTIAN HIEROGLYPH U008;Lo;0;L;;;;;N;;;;; 1333D;EGYPTIAN HIEROGLYPH U009;Lo;0;L;;;;;N;;;;; 1333E;EGYPTIAN HIEROGLYPH U010;Lo;0;L;;;;;N;;;;; 1333F;EGYPTIAN HIEROGLYPH U011;Lo;0;L;;;;;N;;;;; 13340;EGYPTIAN HIEROGLYPH U012;Lo;0;L;;;;;N;;;;; 13341;EGYPTIAN HIEROGLYPH U013;Lo;0;L;;;;;N;;;;; 13342;EGYPTIAN HIEROGLYPH U014;Lo;0;L;;;;;N;;;;; 13343;EGYPTIAN HIEROGLYPH U015;Lo;0;L;;;;;N;;;;; 13344;EGYPTIAN HIEROGLYPH U016;Lo;0;L;;;;;N;;;;; 13345;EGYPTIAN HIEROGLYPH U017;Lo;0;L;;;;;N;;;;; 13346;EGYPTIAN HIEROGLYPH U018;Lo;0;L;;;;;N;;;;; 13347;EGYPTIAN HIEROGLYPH U019;Lo;0;L;;;;;N;;;;; 13348;EGYPTIAN HIEROGLYPH U020;Lo;0;L;;;;;N;;;;; 13349;EGYPTIAN HIEROGLYPH U021;Lo;0;L;;;;;N;;;;; 1334A;EGYPTIAN HIEROGLYPH U022;Lo;0;L;;;;;N;;;;; 1334B;EGYPTIAN HIEROGLYPH U023;Lo;0;L;;;;;N;;;;; 1334C;EGYPTIAN HIEROGLYPH U023A;Lo;0;L;;;;;N;;;;; 1334D;EGYPTIAN HIEROGLYPH U024;Lo;0;L;;;;;N;;;;; 1334E;EGYPTIAN HIEROGLYPH U025;Lo;0;L;;;;;N;;;;; 1334F;EGYPTIAN HIEROGLYPH U026;Lo;0;L;;;;;N;;;;; 13350;EGYPTIAN HIEROGLYPH U027;Lo;0;L;;;;;N;;;;; 13351;EGYPTIAN HIEROGLYPH U028;Lo;0;L;;;;;N;;;;; 13352;EGYPTIAN HIEROGLYPH U029;Lo;0;L;;;;;N;;;;; 13353;EGYPTIAN HIEROGLYPH U029A;Lo;0;L;;;;;N;;;;; 13354;EGYPTIAN HIEROGLYPH U030;Lo;0;L;;;;;N;;;;; 13355;EGYPTIAN HIEROGLYPH U031;Lo;0;L;;;;;N;;;;; 13356;EGYPTIAN HIEROGLYPH U032;Lo;0;L;;;;;N;;;;; 13357;EGYPTIAN HIEROGLYPH U032A;Lo;0;L;;;;;N;;;;; 13358;EGYPTIAN HIEROGLYPH U033;Lo;0;L;;;;;N;;;;; 13359;EGYPTIAN HIEROGLYPH U034;Lo;0;L;;;;;N;;;;; 1335A;EGYPTIAN HIEROGLYPH U035;Lo;0;L;;;;;N;;;;; 1335B;EGYPTIAN HIEROGLYPH U036;Lo;0;L;;;;;N;;;;; 1335C;EGYPTIAN HIEROGLYPH U037;Lo;0;L;;;;;N;;;;; 1335D;EGYPTIAN HIEROGLYPH U038;Lo;0;L;;;;;N;;;;; 1335E;EGYPTIAN HIEROGLYPH U039;Lo;0;L;;;;;N;;;;; 1335F;EGYPTIAN HIEROGLYPH U040;Lo;0;L;;;;;N;;;;; 13360;EGYPTIAN HIEROGLYPH U041;Lo;0;L;;;;;N;;;;; 13361;EGYPTIAN HIEROGLYPH U042;Lo;0;L;;;;;N;;;;; 13362;EGYPTIAN HIEROGLYPH V001;Lo;0;L;;;;;N;;;;; 13363;EGYPTIAN HIEROGLYPH V001A;Lo;0;L;;;;;N;;;;; 13364;EGYPTIAN HIEROGLYPH V001B;Lo;0;L;;;;;N;;;;; 13365;EGYPTIAN HIEROGLYPH V001C;Lo;0;L;;;;;N;;;;; 13366;EGYPTIAN HIEROGLYPH V001D;Lo;0;L;;;;;N;;;;; 13367;EGYPTIAN HIEROGLYPH V001E;Lo;0;L;;;;;N;;;;; 13368;EGYPTIAN HIEROGLYPH V001F;Lo;0;L;;;;;N;;;;; 13369;EGYPTIAN HIEROGLYPH V001G;Lo;0;L;;;;;N;;;;; 1336A;EGYPTIAN HIEROGLYPH V001H;Lo;0;L;;;;;N;;;;; 1336B;EGYPTIAN HIEROGLYPH V001I;Lo;0;L;;;;;N;;;;; 1336C;EGYPTIAN HIEROGLYPH V002;Lo;0;L;;;;;N;;;;; 1336D;EGYPTIAN HIEROGLYPH V002A;Lo;0;L;;;;;N;;;;; 1336E;EGYPTIAN HIEROGLYPH V003;Lo;0;L;;;;;N;;;;; 1336F;EGYPTIAN HIEROGLYPH V004;Lo;0;L;;;;;N;;;;; 13370;EGYPTIAN HIEROGLYPH V005;Lo;0;L;;;;;N;;;;; 13371;EGYPTIAN HIEROGLYPH V006;Lo;0;L;;;;;N;;;;; 13372;EGYPTIAN HIEROGLYPH V007;Lo;0;L;;;;;N;;;;; 13373;EGYPTIAN HIEROGLYPH V007A;Lo;0;L;;;;;N;;;;; 13374;EGYPTIAN HIEROGLYPH V007B;Lo;0;L;;;;;N;;;;; 13375;EGYPTIAN HIEROGLYPH V008;Lo;0;L;;;;;N;;;;; 13376;EGYPTIAN HIEROGLYPH V009;Lo;0;L;;;;;N;;;;; 13377;EGYPTIAN HIEROGLYPH V010;Lo;0;L;;;;;N;;;;; 13378;EGYPTIAN HIEROGLYPH V011;Lo;0;L;;;;;N;;;;; 13379;EGYPTIAN HIEROGLYPH V011A;Lo;0;L;;;;;N;;;;; 1337A;EGYPTIAN HIEROGLYPH V011B;Lo;0;L;;;;;N;;;;; 1337B;EGYPTIAN HIEROGLYPH V011C;Lo;0;L;;;;;N;;;;; 1337C;EGYPTIAN HIEROGLYPH V012;Lo;0;L;;;;;N;;;;; 1337D;EGYPTIAN HIEROGLYPH V012A;Lo;0;L;;;;;N;;;;; 1337E;EGYPTIAN HIEROGLYPH V012B;Lo;0;L;;;;;N;;;;; 1337F;EGYPTIAN HIEROGLYPH V013;Lo;0;L;;;;;N;;;;; 13380;EGYPTIAN HIEROGLYPH V014;Lo;0;L;;;;;N;;;;; 13381;EGYPTIAN HIEROGLYPH V015;Lo;0;L;;;;;N;;;;; 13382;EGYPTIAN HIEROGLYPH V016;Lo;0;L;;;;;N;;;;; 13383;EGYPTIAN HIEROGLYPH V017;Lo;0;L;;;;;N;;;;; 13384;EGYPTIAN HIEROGLYPH V018;Lo;0;L;;;;;N;;;;; 13385;EGYPTIAN HIEROGLYPH V019;Lo;0;L;;;;;N;;;;; 13386;EGYPTIAN HIEROGLYPH V020;Lo;0;L;;;;;N;;;;; 13387;EGYPTIAN HIEROGLYPH V020A;Lo;0;L;;;;;N;;;;; 13388;EGYPTIAN HIEROGLYPH V020B;Lo;0;L;;;;;N;;;;; 13389;EGYPTIAN HIEROGLYPH V020C;Lo;0;L;;;;;N;;;;; 1338A;EGYPTIAN HIEROGLYPH V020D;Lo;0;L;;;;;N;;;;; 1338B;EGYPTIAN HIEROGLYPH V020E;Lo;0;L;;;;;N;;;;; 1338C;EGYPTIAN HIEROGLYPH V020F;Lo;0;L;;;;;N;;;;; 1338D;EGYPTIAN HIEROGLYPH V020G;Lo;0;L;;;;;N;;;;; 1338E;EGYPTIAN HIEROGLYPH V020H;Lo;0;L;;;;;N;;;;; 1338F;EGYPTIAN HIEROGLYPH V020I;Lo;0;L;;;;;N;;;;; 13390;EGYPTIAN HIEROGLYPH V020J;Lo;0;L;;;;;N;;;;; 13391;EGYPTIAN HIEROGLYPH V020K;Lo;0;L;;;;;N;;;;; 13392;EGYPTIAN HIEROGLYPH V020L;Lo;0;L;;;;;N;;;;; 13393;EGYPTIAN HIEROGLYPH V021;Lo;0;L;;;;;N;;;;; 13394;EGYPTIAN HIEROGLYPH V022;Lo;0;L;;;;;N;;;;; 13395;EGYPTIAN HIEROGLYPH V023;Lo;0;L;;;;;N;;;;; 13396;EGYPTIAN HIEROGLYPH V023A;Lo;0;L;;;;;N;;;;; 13397;EGYPTIAN HIEROGLYPH V024;Lo;0;L;;;;;N;;;;; 13398;EGYPTIAN HIEROGLYPH V025;Lo;0;L;;;;;N;;;;; 13399;EGYPTIAN HIEROGLYPH V026;Lo;0;L;;;;;N;;;;; 1339A;EGYPTIAN HIEROGLYPH V027;Lo;0;L;;;;;N;;;;; 1339B;EGYPTIAN HIEROGLYPH V028;Lo;0;L;;;;;N;;;;; 1339C;EGYPTIAN HIEROGLYPH V028A;Lo;0;L;;;;;N;;;;; 1339D;EGYPTIAN HIEROGLYPH V029;Lo;0;L;;;;;N;;;;; 1339E;EGYPTIAN HIEROGLYPH V029A;Lo;0;L;;;;;N;;;;; 1339F;EGYPTIAN HIEROGLYPH V030;Lo;0;L;;;;;N;;;;; 133A0;EGYPTIAN HIEROGLYPH V030A;Lo;0;L;;;;;N;;;;; 133A1;EGYPTIAN HIEROGLYPH V031;Lo;0;L;;;;;N;;;;; 133A2;EGYPTIAN HIEROGLYPH V031A;Lo;0;L;;;;;N;;;;; 133A3;EGYPTIAN HIEROGLYPH V032;Lo;0;L;;;;;N;;;;; 133A4;EGYPTIAN HIEROGLYPH V033;Lo;0;L;;;;;N;;;;; 133A5;EGYPTIAN HIEROGLYPH V033A;Lo;0;L;;;;;N;;;;; 133A6;EGYPTIAN HIEROGLYPH V034;Lo;0;L;;;;;N;;;;; 133A7;EGYPTIAN HIEROGLYPH V035;Lo;0;L;;;;;N;;;;; 133A8;EGYPTIAN HIEROGLYPH V036;Lo;0;L;;;;;N;;;;; 133A9;EGYPTIAN HIEROGLYPH V037;Lo;0;L;;;;;N;;;;; 133AA;EGYPTIAN HIEROGLYPH V037A;Lo;0;L;;;;;N;;;;; 133AB;EGYPTIAN HIEROGLYPH V038;Lo;0;L;;;;;N;;;;; 133AC;EGYPTIAN HIEROGLYPH V039;Lo;0;L;;;;;N;;;;; 133AD;EGYPTIAN HIEROGLYPH V040;Lo;0;L;;;;;N;;;;; 133AE;EGYPTIAN HIEROGLYPH V040A;Lo;0;L;;;;;N;;;;; 133AF;EGYPTIAN HIEROGLYPH W001;Lo;0;L;;;;;N;;;;; 133B0;EGYPTIAN HIEROGLYPH W002;Lo;0;L;;;;;N;;;;; 133B1;EGYPTIAN HIEROGLYPH W003;Lo;0;L;;;;;N;;;;; 133B2;EGYPTIAN HIEROGLYPH W003A;Lo;0;L;;;;;N;;;;; 133B3;EGYPTIAN HIEROGLYPH W004;Lo;0;L;;;;;N;;;;; 133B4;EGYPTIAN HIEROGLYPH W005;Lo;0;L;;;;;N;;;;; 133B5;EGYPTIAN HIEROGLYPH W006;Lo;0;L;;;;;N;;;;; 133B6;EGYPTIAN HIEROGLYPH W007;Lo;0;L;;;;;N;;;;; 133B7;EGYPTIAN HIEROGLYPH W008;Lo;0;L;;;;;N;;;;; 133B8;EGYPTIAN HIEROGLYPH W009;Lo;0;L;;;;;N;;;;; 133B9;EGYPTIAN HIEROGLYPH W009A;Lo;0;L;;;;;N;;;;; 133BA;EGYPTIAN HIEROGLYPH W010;Lo;0;L;;;;;N;;;;; 133BB;EGYPTIAN HIEROGLYPH W010A;Lo;0;L;;;;;N;;;;; 133BC;EGYPTIAN HIEROGLYPH W011;Lo;0;L;;;;;N;;;;; 133BD;EGYPTIAN HIEROGLYPH W012;Lo;0;L;;;;;N;;;;; 133BE;EGYPTIAN HIEROGLYPH W013;Lo;0;L;;;;;N;;;;; 133BF;EGYPTIAN HIEROGLYPH W014;Lo;0;L;;;;;N;;;;; 133C0;EGYPTIAN HIEROGLYPH W014A;Lo;0;L;;;;;N;;;;; 133C1;EGYPTIAN HIEROGLYPH W015;Lo;0;L;;;;;N;;;;; 133C2;EGYPTIAN HIEROGLYPH W016;Lo;0;L;;;;;N;;;;; 133C3;EGYPTIAN HIEROGLYPH W017;Lo;0;L;;;;;N;;;;; 133C4;EGYPTIAN HIEROGLYPH W017A;Lo;0;L;;;;;N;;;;; 133C5;EGYPTIAN HIEROGLYPH W018;Lo;0;L;;;;;N;;;;; 133C6;EGYPTIAN HIEROGLYPH W018A;Lo;0;L;;;;;N;;;;; 133C7;EGYPTIAN HIEROGLYPH W019;Lo;0;L;;;;;N;;;;; 133C8;EGYPTIAN HIEROGLYPH W020;Lo;0;L;;;;;N;;;;; 133C9;EGYPTIAN HIEROGLYPH W021;Lo;0;L;;;;;N;;;;; 133CA;EGYPTIAN HIEROGLYPH W022;Lo;0;L;;;;;N;;;;; 133CB;EGYPTIAN HIEROGLYPH W023;Lo;0;L;;;;;N;;;;; 133CC;EGYPTIAN HIEROGLYPH W024;Lo;0;L;;;;;N;;;;; 133CD;EGYPTIAN HIEROGLYPH W024A;Lo;0;L;;;;;N;;;;; 133CE;EGYPTIAN HIEROGLYPH W025;Lo;0;L;;;;;N;;;;; 133CF;EGYPTIAN HIEROGLYPH X001;Lo;0;L;;;;;N;;;;; 133D0;EGYPTIAN HIEROGLYPH X002;Lo;0;L;;;;;N;;;;; 133D1;EGYPTIAN HIEROGLYPH X003;Lo;0;L;;;;;N;;;;; 133D2;EGYPTIAN HIEROGLYPH X004;Lo;0;L;;;;;N;;;;; 133D3;EGYPTIAN HIEROGLYPH X004A;Lo;0;L;;;;;N;;;;; 133D4;EGYPTIAN HIEROGLYPH X004B;Lo;0;L;;;;;N;;;;; 133D5;EGYPTIAN HIEROGLYPH X005;Lo;0;L;;;;;N;;;;; 133D6;EGYPTIAN HIEROGLYPH X006;Lo;0;L;;;;;N;;;;; 133D7;EGYPTIAN HIEROGLYPH X006A;Lo;0;L;;;;;N;;;;; 133D8;EGYPTIAN HIEROGLYPH X007;Lo;0;L;;;;;N;;;;; 133D9;EGYPTIAN HIEROGLYPH X008;Lo;0;L;;;;;N;;;;; 133DA;EGYPTIAN HIEROGLYPH X008A;Lo;0;L;;;;;N;;;;; 133DB;EGYPTIAN HIEROGLYPH Y001;Lo;0;L;;;;;N;;;;; 133DC;EGYPTIAN HIEROGLYPH Y001A;Lo;0;L;;;;;N;;;;; 133DD;EGYPTIAN HIEROGLYPH Y002;Lo;0;L;;;;;N;;;;; 133DE;EGYPTIAN HIEROGLYPH Y003;Lo;0;L;;;;;N;;;;; 133DF;EGYPTIAN HIEROGLYPH Y004;Lo;0;L;;;;;N;;;;; 133E0;EGYPTIAN HIEROGLYPH Y005;Lo;0;L;;;;;N;;;;; 133E1;EGYPTIAN HIEROGLYPH Y006;Lo;0;L;;;;;N;;;;; 133E2;EGYPTIAN HIEROGLYPH Y007;Lo;0;L;;;;;N;;;;; 133E3;EGYPTIAN HIEROGLYPH Y008;Lo;0;L;;;;;N;;;;; 133E4;EGYPTIAN HIEROGLYPH Z001;Lo;0;L;;;;;N;;;;; 133E5;EGYPTIAN HIEROGLYPH Z002;Lo;0;L;;;;;N;;;;; 133E6;EGYPTIAN HIEROGLYPH Z002A;Lo;0;L;;;;;N;;;;; 133E7;EGYPTIAN HIEROGLYPH Z002B;Lo;0;L;;;;;N;;;;; 133E8;EGYPTIAN HIEROGLYPH Z002C;Lo;0;L;;;;;N;;;;; 133E9;EGYPTIAN HIEROGLYPH Z002D;Lo;0;L;;;;;N;;;;; 133EA;EGYPTIAN HIEROGLYPH Z003;Lo;0;L;;;;;N;;;;; 133EB;EGYPTIAN HIEROGLYPH Z003A;Lo;0;L;;;;;N;;;;; 133EC;EGYPTIAN HIEROGLYPH Z003B;Lo;0;L;;;;;N;;;;; 133ED;EGYPTIAN HIEROGLYPH Z004;Lo;0;L;;;;;N;;;;; 133EE;EGYPTIAN HIEROGLYPH Z004A;Lo;0;L;;;;;N;;;;; 133EF;EGYPTIAN HIEROGLYPH Z005;Lo;0;L;;;;;N;;;;; 133F0;EGYPTIAN HIEROGLYPH Z005A;Lo;0;L;;;;;N;;;;; 133F1;EGYPTIAN HIEROGLYPH Z006;Lo;0;L;;;;;N;;;;; 133F2;EGYPTIAN HIEROGLYPH Z007;Lo;0;L;;;;;N;;;;; 133F3;EGYPTIAN HIEROGLYPH Z008;Lo;0;L;;;;;N;;;;; 133F4;EGYPTIAN HIEROGLYPH Z009;Lo;0;L;;;;;N;;;;; 133F5;EGYPTIAN HIEROGLYPH Z010;Lo;0;L;;;;;N;;;;; 133F6;EGYPTIAN HIEROGLYPH Z011;Lo;0;L;;;;;N;;;;; 133F7;EGYPTIAN HIEROGLYPH Z012;Lo;0;L;;;;;N;;;;; 133F8;EGYPTIAN HIEROGLYPH Z013;Lo;0;L;;;;;N;;;;; 133F9;EGYPTIAN HIEROGLYPH Z014;Lo;0;L;;;;;N;;;;; 133FA;EGYPTIAN HIEROGLYPH Z015;Lo;0;L;;;;;N;;;;; 133FB;EGYPTIAN HIEROGLYPH Z015A;Lo;0;L;;;;;N;;;;; 133FC;EGYPTIAN HIEROGLYPH Z015B;Lo;0;L;;;;;N;;;;; 133FD;EGYPTIAN HIEROGLYPH Z015C;Lo;0;L;;;;;N;;;;; 133FE;EGYPTIAN HIEROGLYPH Z015D;Lo;0;L;;;;;N;;;;; 133FF;EGYPTIAN HIEROGLYPH Z015E;Lo;0;L;;;;;N;;;;; 13400;EGYPTIAN HIEROGLYPH Z015F;Lo;0;L;;;;;N;;;;; 13401;EGYPTIAN HIEROGLYPH Z015G;Lo;0;L;;;;;N;;;;; 13402;EGYPTIAN HIEROGLYPH Z015H;Lo;0;L;;;;;N;;;;; 13403;EGYPTIAN HIEROGLYPH Z015I;Lo;0;L;;;;;N;;;;; 13404;EGYPTIAN HIEROGLYPH Z016;Lo;0;L;;;;;N;;;;; 13405;EGYPTIAN HIEROGLYPH Z016A;Lo;0;L;;;;;N;;;;; 13406;EGYPTIAN HIEROGLYPH Z016B;Lo;0;L;;;;;N;;;;; 13407;EGYPTIAN HIEROGLYPH Z016C;Lo;0;L;;;;;N;;;;; 13408;EGYPTIAN HIEROGLYPH Z016D;Lo;0;L;;;;;N;;;;; 13409;EGYPTIAN HIEROGLYPH Z016E;Lo;0;L;;;;;N;;;;; 1340A;EGYPTIAN HIEROGLYPH Z016F;Lo;0;L;;;;;N;;;;; 1340B;EGYPTIAN HIEROGLYPH Z016G;Lo;0;L;;;;;N;;;;; 1340C;EGYPTIAN HIEROGLYPH Z016H;Lo;0;L;;;;;N;;;;; 1340D;EGYPTIAN HIEROGLYPH AA001;Lo;0;L;;;;;N;;;;; 1340E;EGYPTIAN HIEROGLYPH AA002;Lo;0;L;;;;;N;;;;; 1340F;EGYPTIAN HIEROGLYPH AA003;Lo;0;L;;;;;N;;;;; 13410;EGYPTIAN HIEROGLYPH AA004;Lo;0;L;;;;;N;;;;; 13411;EGYPTIAN HIEROGLYPH AA005;Lo;0;L;;;;;N;;;;; 13412;EGYPTIAN HIEROGLYPH AA006;Lo;0;L;;;;;N;;;;; 13413;EGYPTIAN HIEROGLYPH AA007;Lo;0;L;;;;;N;;;;; 13414;EGYPTIAN HIEROGLYPH AA007A;Lo;0;L;;;;;N;;;;; 13415;EGYPTIAN HIEROGLYPH AA007B;Lo;0;L;;;;;N;;;;; 13416;EGYPTIAN HIEROGLYPH AA008;Lo;0;L;;;;;N;;;;; 13417;EGYPTIAN HIEROGLYPH AA009;Lo;0;L;;;;;N;;;;; 13418;EGYPTIAN HIEROGLYPH AA010;Lo;0;L;;;;;N;;;;; 13419;EGYPTIAN HIEROGLYPH AA011;Lo;0;L;;;;;N;;;;; 1341A;EGYPTIAN HIEROGLYPH AA012;Lo;0;L;;;;;N;;;;; 1341B;EGYPTIAN HIEROGLYPH AA013;Lo;0;L;;;;;N;;;;; 1341C;EGYPTIAN HIEROGLYPH AA014;Lo;0;L;;;;;N;;;;; 1341D;EGYPTIAN HIEROGLYPH AA015;Lo;0;L;;;;;N;;;;; 1341E;EGYPTIAN HIEROGLYPH AA016;Lo;0;L;;;;;N;;;;; 1341F;EGYPTIAN HIEROGLYPH AA017;Lo;0;L;;;;;N;;;;; 13420;EGYPTIAN HIEROGLYPH AA018;Lo;0;L;;;;;N;;;;; 13421;EGYPTIAN HIEROGLYPH AA019;Lo;0;L;;;;;N;;;;; 13422;EGYPTIAN HIEROGLYPH AA020;Lo;0;L;;;;;N;;;;; 13423;EGYPTIAN HIEROGLYPH AA021;Lo;0;L;;;;;N;;;;; 13424;EGYPTIAN HIEROGLYPH AA022;Lo;0;L;;;;;N;;;;; 13425;EGYPTIAN HIEROGLYPH AA023;Lo;0;L;;;;;N;;;;; 13426;EGYPTIAN HIEROGLYPH AA024;Lo;0;L;;;;;N;;;;; 13427;EGYPTIAN HIEROGLYPH AA025;Lo;0;L;;;;;N;;;;; 13428;EGYPTIAN HIEROGLYPH AA026;Lo;0;L;;;;;N;;;;; 13429;EGYPTIAN HIEROGLYPH AA027;Lo;0;L;;;;;N;;;;; 1342A;EGYPTIAN HIEROGLYPH AA028;Lo;0;L;;;;;N;;;;; 1342B;EGYPTIAN HIEROGLYPH AA029;Lo;0;L;;;;;N;;;;; 1342C;EGYPTIAN HIEROGLYPH AA030;Lo;0;L;;;;;N;;;;; 1342D;EGYPTIAN HIEROGLYPH AA031;Lo;0;L;;;;;N;;;;; 1342E;EGYPTIAN HIEROGLYPH AA032;Lo;0;L;;;;;N;;;;; 16800;BAMUM LETTER PHASE-A NGKUE MFON;Lo;0;L;;;;;N;;;;; 16801;BAMUM LETTER PHASE-A GBIEE FON;Lo;0;L;;;;;N;;;;; 16802;BAMUM LETTER PHASE-A PON MFON PIPAEMGBIEE;Lo;0;L;;;;;N;;;;; 16803;BAMUM LETTER PHASE-A PON MFON PIPAEMBA;Lo;0;L;;;;;N;;;;; 16804;BAMUM LETTER PHASE-A NAA MFON;Lo;0;L;;;;;N;;;;; 16805;BAMUM LETTER PHASE-A SHUENSHUET;Lo;0;L;;;;;N;;;;; 16806;BAMUM LETTER PHASE-A TITA MFON;Lo;0;L;;;;;N;;;;; 16807;BAMUM LETTER PHASE-A NZA MFON;Lo;0;L;;;;;N;;;;; 16808;BAMUM LETTER PHASE-A SHINDA PA NJI;Lo;0;L;;;;;N;;;;; 16809;BAMUM LETTER PHASE-A PON PA NJI PIPAEMGBIEE;Lo;0;L;;;;;N;;;;; 1680A;BAMUM LETTER PHASE-A PON PA NJI PIPAEMBA;Lo;0;L;;;;;N;;;;; 1680B;BAMUM LETTER PHASE-A MAEMBGBIEE;Lo;0;L;;;;;N;;;;; 1680C;BAMUM LETTER PHASE-A TU MAEMBA;Lo;0;L;;;;;N;;;;; 1680D;BAMUM LETTER PHASE-A NGANGU;Lo;0;L;;;;;N;;;;; 1680E;BAMUM LETTER PHASE-A MAEMVEUX;Lo;0;L;;;;;N;;;;; 1680F;BAMUM LETTER PHASE-A MANSUAE;Lo;0;L;;;;;N;;;;; 16810;BAMUM LETTER PHASE-A MVEUAENGAM;Lo;0;L;;;;;N;;;;; 16811;BAMUM LETTER PHASE-A SEUNYAM;Lo;0;L;;;;;N;;;;; 16812;BAMUM LETTER PHASE-A NTOQPEN;Lo;0;L;;;;;N;;;;; 16813;BAMUM LETTER PHASE-A KEUKEUTNDA;Lo;0;L;;;;;N;;;;; 16814;BAMUM LETTER PHASE-A NKINDI;Lo;0;L;;;;;N;;;;; 16815;BAMUM LETTER PHASE-A SUU;Lo;0;L;;;;;N;;;;; 16816;BAMUM LETTER PHASE-A NGKUENZEUM;Lo;0;L;;;;;N;;;;; 16817;BAMUM LETTER PHASE-A LAPAQ;Lo;0;L;;;;;N;;;;; 16818;BAMUM LETTER PHASE-A LET KUT;Lo;0;L;;;;;N;;;;; 16819;BAMUM LETTER PHASE-A NTAP MFAA;Lo;0;L;;;;;N;;;;; 1681A;BAMUM LETTER PHASE-A MAEKEUP;Lo;0;L;;;;;N;;;;; 1681B;BAMUM LETTER PHASE-A PASHAE;Lo;0;L;;;;;N;;;;; 1681C;BAMUM LETTER PHASE-A GHEUAERAE;Lo;0;L;;;;;N;;;;; 1681D;BAMUM LETTER PHASE-A PAMSHAE;Lo;0;L;;;;;N;;;;; 1681E;BAMUM LETTER PHASE-A MON NGGEUAET;Lo;0;L;;;;;N;;;;; 1681F;BAMUM LETTER PHASE-A NZUN MEUT;Lo;0;L;;;;;N;;;;; 16820;BAMUM LETTER PHASE-A U YUQ NAE;Lo;0;L;;;;;N;;;;; 16821;BAMUM LETTER PHASE-A GHEUAEGHEUAE;Lo;0;L;;;;;N;;;;; 16822;BAMUM LETTER PHASE-A NTAP NTAA;Lo;0;L;;;;;N;;;;; 16823;BAMUM LETTER PHASE-A SISA;Lo;0;L;;;;;N;;;;; 16824;BAMUM LETTER PHASE-A MGBASA;Lo;0;L;;;;;N;;;;; 16825;BAMUM LETTER PHASE-A MEUNJOMNDEUQ;Lo;0;L;;;;;N;;;;; 16826;BAMUM LETTER PHASE-A MOOMPUQ;Lo;0;L;;;;;N;;;;; 16827;BAMUM LETTER PHASE-A KAFA;Lo;0;L;;;;;N;;;;; 16828;BAMUM LETTER PHASE-A PA LEERAEWA;Lo;0;L;;;;;N;;;;; 16829;BAMUM LETTER PHASE-A NDA LEERAEWA;Lo;0;L;;;;;N;;;;; 1682A;BAMUM LETTER PHASE-A PET;Lo;0;L;;;;;N;;;;; 1682B;BAMUM LETTER PHASE-A MAEMKPEN;Lo;0;L;;;;;N;;;;; 1682C;BAMUM LETTER PHASE-A NIKA;Lo;0;L;;;;;N;;;;; 1682D;BAMUM LETTER PHASE-A PUP;Lo;0;L;;;;;N;;;;; 1682E;BAMUM LETTER PHASE-A TUAEP;Lo;0;L;;;;;N;;;;; 1682F;BAMUM LETTER PHASE-A LUAEP;Lo;0;L;;;;;N;;;;; 16830;BAMUM LETTER PHASE-A SONJAM;Lo;0;L;;;;;N;;;;; 16831;BAMUM LETTER PHASE-A TEUTEUWEN;Lo;0;L;;;;;N;;;;; 16832;BAMUM LETTER PHASE-A MAENYI;Lo;0;L;;;;;N;;;;; 16833;BAMUM LETTER PHASE-A KET;Lo;0;L;;;;;N;;;;; 16834;BAMUM LETTER PHASE-A NDAANGGEUAET;Lo;0;L;;;;;N;;;;; 16835;BAMUM LETTER PHASE-A KUOQ;Lo;0;L;;;;;N;;;;; 16836;BAMUM LETTER PHASE-A MOOMEUT;Lo;0;L;;;;;N;;;;; 16837;BAMUM LETTER PHASE-A SHUM;Lo;0;L;;;;;N;;;;; 16838;BAMUM LETTER PHASE-A LOMMAE;Lo;0;L;;;;;N;;;;; 16839;BAMUM LETTER PHASE-A FIRI;Lo;0;L;;;;;N;;;;; 1683A;BAMUM LETTER PHASE-A ROM;Lo;0;L;;;;;N;;;;; 1683B;BAMUM LETTER PHASE-A KPOQ;Lo;0;L;;;;;N;;;;; 1683C;BAMUM LETTER PHASE-A SOQ;Lo;0;L;;;;;N;;;;; 1683D;BAMUM LETTER PHASE-A MAP PIEET;Lo;0;L;;;;;N;;;;; 1683E;BAMUM LETTER PHASE-A SHIRAE;Lo;0;L;;;;;N;;;;; 1683F;BAMUM LETTER PHASE-A NTAP;Lo;0;L;;;;;N;;;;; 16840;BAMUM LETTER PHASE-A SHOQ NSHUT YUM;Lo;0;L;;;;;N;;;;; 16841;BAMUM LETTER PHASE-A NYIT MONGKEUAEQ;Lo;0;L;;;;;N;;;;; 16842;BAMUM LETTER PHASE-A PAARAE;Lo;0;L;;;;;N;;;;; 16843;BAMUM LETTER PHASE-A NKAARAE;Lo;0;L;;;;;N;;;;; 16844;BAMUM LETTER PHASE-A UNKNOWN;Lo;0;L;;;;;N;;;;; 16845;BAMUM LETTER PHASE-A NGGEN;Lo;0;L;;;;;N;;;;; 16846;BAMUM LETTER PHASE-A MAESI;Lo;0;L;;;;;N;;;;; 16847;BAMUM LETTER PHASE-A NJAM;Lo;0;L;;;;;N;;;;; 16848;BAMUM LETTER PHASE-A MBANYI;Lo;0;L;;;;;N;;;;; 16849;BAMUM LETTER PHASE-A NYET;Lo;0;L;;;;;N;;;;; 1684A;BAMUM LETTER PHASE-A TEUAEN;Lo;0;L;;;;;N;;;;; 1684B;BAMUM LETTER PHASE-A SOT;Lo;0;L;;;;;N;;;;; 1684C;BAMUM LETTER PHASE-A PAAM;Lo;0;L;;;;;N;;;;; 1684D;BAMUM LETTER PHASE-A NSHIEE;Lo;0;L;;;;;N;;;;; 1684E;BAMUM LETTER PHASE-A MAEM;Lo;0;L;;;;;N;;;;; 1684F;BAMUM LETTER PHASE-A NYI;Lo;0;L;;;;;N;;;;; 16850;BAMUM LETTER PHASE-A KAQ;Lo;0;L;;;;;N;;;;; 16851;BAMUM LETTER PHASE-A NSHA;Lo;0;L;;;;;N;;;;; 16852;BAMUM LETTER PHASE-A VEE;Lo;0;L;;;;;N;;;;; 16853;BAMUM LETTER PHASE-A LU;Lo;0;L;;;;;N;;;;; 16854;BAMUM LETTER PHASE-A NEN;Lo;0;L;;;;;N;;;;; 16855;BAMUM LETTER PHASE-A NAQ;Lo;0;L;;;;;N;;;;; 16856;BAMUM LETTER PHASE-A MBAQ;Lo;0;L;;;;;N;;;;; 16857;BAMUM LETTER PHASE-B NSHUET;Lo;0;L;;;;;N;;;;; 16858;BAMUM LETTER PHASE-B TU MAEMGBIEE;Lo;0;L;;;;;N;;;;; 16859;BAMUM LETTER PHASE-B SIEE;Lo;0;L;;;;;N;;;;; 1685A;BAMUM LETTER PHASE-B SET TU;Lo;0;L;;;;;N;;;;; 1685B;BAMUM LETTER PHASE-B LOM NTEUM;Lo;0;L;;;;;N;;;;; 1685C;BAMUM LETTER PHASE-B MBA MAELEE;Lo;0;L;;;;;N;;;;; 1685D;BAMUM LETTER PHASE-B KIEEM;Lo;0;L;;;;;N;;;;; 1685E;BAMUM LETTER PHASE-B YEURAE;Lo;0;L;;;;;N;;;;; 1685F;BAMUM LETTER PHASE-B MBAARAE;Lo;0;L;;;;;N;;;;; 16860;BAMUM LETTER PHASE-B KAM;Lo;0;L;;;;;N;;;;; 16861;BAMUM LETTER PHASE-B PEESHI;Lo;0;L;;;;;N;;;;; 16862;BAMUM LETTER PHASE-B YAFU LEERAEWA;Lo;0;L;;;;;N;;;;; 16863;BAMUM LETTER PHASE-B LAM NSHUT NYAM;Lo;0;L;;;;;N;;;;; 16864;BAMUM LETTER PHASE-B NTIEE SHEUOQ;Lo;0;L;;;;;N;;;;; 16865;BAMUM LETTER PHASE-B NDU NJAA;Lo;0;L;;;;;N;;;;; 16866;BAMUM LETTER PHASE-B GHEUGHEUAEM;Lo;0;L;;;;;N;;;;; 16867;BAMUM LETTER PHASE-B PIT;Lo;0;L;;;;;N;;;;; 16868;BAMUM LETTER PHASE-B TU NSIEE;Lo;0;L;;;;;N;;;;; 16869;BAMUM LETTER PHASE-B SHET NJAQ;Lo;0;L;;;;;N;;;;; 1686A;BAMUM LETTER PHASE-B SHEUAEQTU;Lo;0;L;;;;;N;;;;; 1686B;BAMUM LETTER PHASE-B MFON TEUAEQ;Lo;0;L;;;;;N;;;;; 1686C;BAMUM LETTER PHASE-B MBIT MBAAKET;Lo;0;L;;;;;N;;;;; 1686D;BAMUM LETTER PHASE-B NYI NTEUM;Lo;0;L;;;;;N;;;;; 1686E;BAMUM LETTER PHASE-B KEUPUQ;Lo;0;L;;;;;N;;;;; 1686F;BAMUM LETTER PHASE-B GHEUGHEN;Lo;0;L;;;;;N;;;;; 16870;BAMUM LETTER PHASE-B KEUYEUX;Lo;0;L;;;;;N;;;;; 16871;BAMUM LETTER PHASE-B LAANAE;Lo;0;L;;;;;N;;;;; 16872;BAMUM LETTER PHASE-B PARUM;Lo;0;L;;;;;N;;;;; 16873;BAMUM LETTER PHASE-B VEUM;Lo;0;L;;;;;N;;;;; 16874;BAMUM LETTER PHASE-B NGKINDI MVOP;Lo;0;L;;;;;N;;;;; 16875;BAMUM LETTER PHASE-B NGGEU MBU;Lo;0;L;;;;;N;;;;; 16876;BAMUM LETTER PHASE-B WUAET;Lo;0;L;;;;;N;;;;; 16877;BAMUM LETTER PHASE-B SAKEUAE;Lo;0;L;;;;;N;;;;; 16878;BAMUM LETTER PHASE-B TAAM;Lo;0;L;;;;;N;;;;; 16879;BAMUM LETTER PHASE-B MEUQ;Lo;0;L;;;;;N;;;;; 1687A;BAMUM LETTER PHASE-B NGGUOQ;Lo;0;L;;;;;N;;;;; 1687B;BAMUM LETTER PHASE-B NGGUOQ LARGE;Lo;0;L;;;;;N;;;;; 1687C;BAMUM LETTER PHASE-B MFIYAQ;Lo;0;L;;;;;N;;;;; 1687D;BAMUM LETTER PHASE-B SUE;Lo;0;L;;;;;N;;;;; 1687E;BAMUM LETTER PHASE-B MBEURI;Lo;0;L;;;;;N;;;;; 1687F;BAMUM LETTER PHASE-B MONTIEEN;Lo;0;L;;;;;N;;;;; 16880;BAMUM LETTER PHASE-B NYAEMAE;Lo;0;L;;;;;N;;;;; 16881;BAMUM LETTER PHASE-B PUNGAAM;Lo;0;L;;;;;N;;;;; 16882;BAMUM LETTER PHASE-B MEUT NGGEET;Lo;0;L;;;;;N;;;;; 16883;BAMUM LETTER PHASE-B FEUX;Lo;0;L;;;;;N;;;;; 16884;BAMUM LETTER PHASE-B MBUOQ;Lo;0;L;;;;;N;;;;; 16885;BAMUM LETTER PHASE-B FEE;Lo;0;L;;;;;N;;;;; 16886;BAMUM LETTER PHASE-B KEUAEM;Lo;0;L;;;;;N;;;;; 16887;BAMUM LETTER PHASE-B MA NJEUAENA;Lo;0;L;;;;;N;;;;; 16888;BAMUM LETTER PHASE-B MA NJUQA;Lo;0;L;;;;;N;;;;; 16889;BAMUM LETTER PHASE-B LET;Lo;0;L;;;;;N;;;;; 1688A;BAMUM LETTER PHASE-B NGGAAM;Lo;0;L;;;;;N;;;;; 1688B;BAMUM LETTER PHASE-B NSEN;Lo;0;L;;;;;N;;;;; 1688C;BAMUM LETTER PHASE-B MA;Lo;0;L;;;;;N;;;;; 1688D;BAMUM LETTER PHASE-B KIQ;Lo;0;L;;;;;N;;;;; 1688E;BAMUM LETTER PHASE-B NGOM;Lo;0;L;;;;;N;;;;; 1688F;BAMUM LETTER PHASE-C NGKUE MAEMBA;Lo;0;L;;;;;N;;;;; 16890;BAMUM LETTER PHASE-C NZA;Lo;0;L;;;;;N;;;;; 16891;BAMUM LETTER PHASE-C YUM;Lo;0;L;;;;;N;;;;; 16892;BAMUM LETTER PHASE-C WANGKUOQ;Lo;0;L;;;;;N;;;;; 16893;BAMUM LETTER PHASE-C NGGEN;Lo;0;L;;;;;N;;;;; 16894;BAMUM LETTER PHASE-C NDEUAEREE;Lo;0;L;;;;;N;;;;; 16895;BAMUM LETTER PHASE-C NGKAQ;Lo;0;L;;;;;N;;;;; 16896;BAMUM LETTER PHASE-C GHARAE;Lo;0;L;;;;;N;;;;; 16897;BAMUM LETTER PHASE-C MBEEKEET;Lo;0;L;;;;;N;;;;; 16898;BAMUM LETTER PHASE-C GBAYI;Lo;0;L;;;;;N;;;;; 16899;BAMUM LETTER PHASE-C NYIR MKPARAQ MEUN;Lo;0;L;;;;;N;;;;; 1689A;BAMUM LETTER PHASE-C NTU MBIT;Lo;0;L;;;;;N;;;;; 1689B;BAMUM LETTER PHASE-C MBEUM;Lo;0;L;;;;;N;;;;; 1689C;BAMUM LETTER PHASE-C PIRIEEN;Lo;0;L;;;;;N;;;;; 1689D;BAMUM LETTER PHASE-C NDOMBU;Lo;0;L;;;;;N;;;;; 1689E;BAMUM LETTER PHASE-C MBAA CABBAGE-TREE;Lo;0;L;;;;;N;;;;; 1689F;BAMUM LETTER PHASE-C KEUSHEUAEP;Lo;0;L;;;;;N;;;;; 168A0;BAMUM LETTER PHASE-C GHAP;Lo;0;L;;;;;N;;;;; 168A1;BAMUM LETTER PHASE-C KEUKAQ;Lo;0;L;;;;;N;;;;; 168A2;BAMUM LETTER PHASE-C YU MUOMAE;Lo;0;L;;;;;N;;;;; 168A3;BAMUM LETTER PHASE-C NZEUM;Lo;0;L;;;;;N;;;;; 168A4;BAMUM LETTER PHASE-C MBUE;Lo;0;L;;;;;N;;;;; 168A5;BAMUM LETTER PHASE-C NSEUAEN;Lo;0;L;;;;;N;;;;; 168A6;BAMUM LETTER PHASE-C MBIT;Lo;0;L;;;;;N;;;;; 168A7;BAMUM LETTER PHASE-C YEUQ;Lo;0;L;;;;;N;;;;; 168A8;BAMUM LETTER PHASE-C KPARAQ;Lo;0;L;;;;;N;;;;; 168A9;BAMUM LETTER PHASE-C KAA;Lo;0;L;;;;;N;;;;; 168AA;BAMUM LETTER PHASE-C SEUX;Lo;0;L;;;;;N;;;;; 168AB;BAMUM LETTER PHASE-C NDIDA;Lo;0;L;;;;;N;;;;; 168AC;BAMUM LETTER PHASE-C TAASHAE;Lo;0;L;;;;;N;;;;; 168AD;BAMUM LETTER PHASE-C NJUEQ;Lo;0;L;;;;;N;;;;; 168AE;BAMUM LETTER PHASE-C TITA YUE;Lo;0;L;;;;;N;;;;; 168AF;BAMUM LETTER PHASE-C SUAET;Lo;0;L;;;;;N;;;;; 168B0;BAMUM LETTER PHASE-C NGGUAEN NYAM;Lo;0;L;;;;;N;;;;; 168B1;BAMUM LETTER PHASE-C VEUX;Lo;0;L;;;;;N;;;;; 168B2;BAMUM LETTER PHASE-C NANSANAQ;Lo;0;L;;;;;N;;;;; 168B3;BAMUM LETTER PHASE-C MA KEUAERI;Lo;0;L;;;;;N;;;;; 168B4;BAMUM LETTER PHASE-C NTAA;Lo;0;L;;;;;N;;;;; 168B5;BAMUM LETTER PHASE-C NGGUON;Lo;0;L;;;;;N;;;;; 168B6;BAMUM LETTER PHASE-C LAP;Lo;0;L;;;;;N;;;;; 168B7;BAMUM LETTER PHASE-C MBIRIEEN;Lo;0;L;;;;;N;;;;; 168B8;BAMUM LETTER PHASE-C MGBASAQ;Lo;0;L;;;;;N;;;;; 168B9;BAMUM LETTER PHASE-C NTEUNGBA;Lo;0;L;;;;;N;;;;; 168BA;BAMUM LETTER PHASE-C TEUTEUX;Lo;0;L;;;;;N;;;;; 168BB;BAMUM LETTER PHASE-C NGGUM;Lo;0;L;;;;;N;;;;; 168BC;BAMUM LETTER PHASE-C FUE;Lo;0;L;;;;;N;;;;; 168BD;BAMUM LETTER PHASE-C NDEUT;Lo;0;L;;;;;N;;;;; 168BE;BAMUM LETTER PHASE-C NSA;Lo;0;L;;;;;N;;;;; 168BF;BAMUM LETTER PHASE-C NSHAQ;Lo;0;L;;;;;N;;;;; 168C0;BAMUM LETTER PHASE-C BUNG;Lo;0;L;;;;;N;;;;; 168C1;BAMUM LETTER PHASE-C VEUAEPEN;Lo;0;L;;;;;N;;;;; 168C2;BAMUM LETTER PHASE-C MBERAE;Lo;0;L;;;;;N;;;;; 168C3;BAMUM LETTER PHASE-C RU;Lo;0;L;;;;;N;;;;; 168C4;BAMUM LETTER PHASE-C NJAEM;Lo;0;L;;;;;N;;;;; 168C5;BAMUM LETTER PHASE-C LAM;Lo;0;L;;;;;N;;;;; 168C6;BAMUM LETTER PHASE-C TITUAEP;Lo;0;L;;;;;N;;;;; 168C7;BAMUM LETTER PHASE-C NSUOT NGOM;Lo;0;L;;;;;N;;;;; 168C8;BAMUM LETTER PHASE-C NJEEEE;Lo;0;L;;;;;N;;;;; 168C9;BAMUM LETTER PHASE-C KET;Lo;0;L;;;;;N;;;;; 168CA;BAMUM LETTER PHASE-C NGGU;Lo;0;L;;;;;N;;;;; 168CB;BAMUM LETTER PHASE-C MAESI;Lo;0;L;;;;;N;;;;; 168CC;BAMUM LETTER PHASE-C MBUAEM;Lo;0;L;;;;;N;;;;; 168CD;BAMUM LETTER PHASE-C LU;Lo;0;L;;;;;N;;;;; 168CE;BAMUM LETTER PHASE-C KUT;Lo;0;L;;;;;N;;;;; 168CF;BAMUM LETTER PHASE-C NJAM;Lo;0;L;;;;;N;;;;; 168D0;BAMUM LETTER PHASE-C NGOM;Lo;0;L;;;;;N;;;;; 168D1;BAMUM LETTER PHASE-C WUP;Lo;0;L;;;;;N;;;;; 168D2;BAMUM LETTER PHASE-C NGGUEET;Lo;0;L;;;;;N;;;;; 168D3;BAMUM LETTER PHASE-C NSOM;Lo;0;L;;;;;N;;;;; 168D4;BAMUM LETTER PHASE-C NTEN;Lo;0;L;;;;;N;;;;; 168D5;BAMUM LETTER PHASE-C KUOP NKAARAE;Lo;0;L;;;;;N;;;;; 168D6;BAMUM LETTER PHASE-C NSUN;Lo;0;L;;;;;N;;;;; 168D7;BAMUM LETTER PHASE-C NDAM;Lo;0;L;;;;;N;;;;; 168D8;BAMUM LETTER PHASE-C MA NSIEE;Lo;0;L;;;;;N;;;;; 168D9;BAMUM LETTER PHASE-C YAA;Lo;0;L;;;;;N;;;;; 168DA;BAMUM LETTER PHASE-C NDAP;Lo;0;L;;;;;N;;;;; 168DB;BAMUM LETTER PHASE-C SHUEQ;Lo;0;L;;;;;N;;;;; 168DC;BAMUM LETTER PHASE-C SETFON;Lo;0;L;;;;;N;;;;; 168DD;BAMUM LETTER PHASE-C MBI;Lo;0;L;;;;;N;;;;; 168DE;BAMUM LETTER PHASE-C MAEMBA;Lo;0;L;;;;;N;;;;; 168DF;BAMUM LETTER PHASE-C MBANYI;Lo;0;L;;;;;N;;;;; 168E0;BAMUM LETTER PHASE-C KEUSEUX;Lo;0;L;;;;;N;;;;; 168E1;BAMUM LETTER PHASE-C MBEUX;Lo;0;L;;;;;N;;;;; 168E2;BAMUM LETTER PHASE-C KEUM;Lo;0;L;;;;;N;;;;; 168E3;BAMUM LETTER PHASE-C MBAA PICKET;Lo;0;L;;;;;N;;;;; 168E4;BAMUM LETTER PHASE-C YUWOQ;Lo;0;L;;;;;N;;;;; 168E5;BAMUM LETTER PHASE-C NJEUX;Lo;0;L;;;;;N;;;;; 168E6;BAMUM LETTER PHASE-C MIEE;Lo;0;L;;;;;N;;;;; 168E7;BAMUM LETTER PHASE-C MUAE;Lo;0;L;;;;;N;;;;; 168E8;BAMUM LETTER PHASE-C SHIQ;Lo;0;L;;;;;N;;;;; 168E9;BAMUM LETTER PHASE-C KEN LAW;Lo;0;L;;;;;N;;;;; 168EA;BAMUM LETTER PHASE-C KEN FATIGUE;Lo;0;L;;;;;N;;;;; 168EB;BAMUM LETTER PHASE-C NGAQ;Lo;0;L;;;;;N;;;;; 168EC;BAMUM LETTER PHASE-C NAQ;Lo;0;L;;;;;N;;;;; 168ED;BAMUM LETTER PHASE-C LIQ;Lo;0;L;;;;;N;;;;; 168EE;BAMUM LETTER PHASE-C PIN;Lo;0;L;;;;;N;;;;; 168EF;BAMUM LETTER PHASE-C PEN;Lo;0;L;;;;;N;;;;; 168F0;BAMUM LETTER PHASE-C TET;Lo;0;L;;;;;N;;;;; 168F1;BAMUM LETTER PHASE-D MBUO;Lo;0;L;;;;;N;;;;; 168F2;BAMUM LETTER PHASE-D WAP;Lo;0;L;;;;;N;;;;; 168F3;BAMUM LETTER PHASE-D NJI;Lo;0;L;;;;;N;;;;; 168F4;BAMUM LETTER PHASE-D MFON;Lo;0;L;;;;;N;;;;; 168F5;BAMUM LETTER PHASE-D NJIEE;Lo;0;L;;;;;N;;;;; 168F6;BAMUM LETTER PHASE-D LIEE;Lo;0;L;;;;;N;;;;; 168F7;BAMUM LETTER PHASE-D NJEUT;Lo;0;L;;;;;N;;;;; 168F8;BAMUM LETTER PHASE-D NSHEE;Lo;0;L;;;;;N;;;;; 168F9;BAMUM LETTER PHASE-D NGGAAMAE;Lo;0;L;;;;;N;;;;; 168FA;BAMUM LETTER PHASE-D NYAM;Lo;0;L;;;;;N;;;;; 168FB;BAMUM LETTER PHASE-D WUAEN;Lo;0;L;;;;;N;;;;; 168FC;BAMUM LETTER PHASE-D NGKUN;Lo;0;L;;;;;N;;;;; 168FD;BAMUM LETTER PHASE-D SHEE;Lo;0;L;;;;;N;;;;; 168FE;BAMUM LETTER PHASE-D NGKAP;Lo;0;L;;;;;N;;;;; 168FF;BAMUM LETTER PHASE-D KEUAETMEUN;Lo;0;L;;;;;N;;;;; 16900;BAMUM LETTER PHASE-D TEUT;Lo;0;L;;;;;N;;;;; 16901;BAMUM LETTER PHASE-D SHEUAE;Lo;0;L;;;;;N;;;;; 16902;BAMUM LETTER PHASE-D NJAP;Lo;0;L;;;;;N;;;;; 16903;BAMUM LETTER PHASE-D SUE;Lo;0;L;;;;;N;;;;; 16904;BAMUM LETTER PHASE-D KET;Lo;0;L;;;;;N;;;;; 16905;BAMUM LETTER PHASE-D YAEMMAE;Lo;0;L;;;;;N;;;;; 16906;BAMUM LETTER PHASE-D KUOM;Lo;0;L;;;;;N;;;;; 16907;BAMUM LETTER PHASE-D SAP;Lo;0;L;;;;;N;;;;; 16908;BAMUM LETTER PHASE-D MFEUT;Lo;0;L;;;;;N;;;;; 16909;BAMUM LETTER PHASE-D NDEUX;Lo;0;L;;;;;N;;;;; 1690A;BAMUM LETTER PHASE-D MALEERI;Lo;0;L;;;;;N;;;;; 1690B;BAMUM LETTER PHASE-D MEUT;Lo;0;L;;;;;N;;;;; 1690C;BAMUM LETTER PHASE-D SEUAEQ;Lo;0;L;;;;;N;;;;; 1690D;BAMUM LETTER PHASE-D YEN;Lo;0;L;;;;;N;;;;; 1690E;BAMUM LETTER PHASE-D NJEUAEM;Lo;0;L;;;;;N;;;;; 1690F;BAMUM LETTER PHASE-D KEUOT MBUAE;Lo;0;L;;;;;N;;;;; 16910;BAMUM LETTER PHASE-D NGKEURI;Lo;0;L;;;;;N;;;;; 16911;BAMUM LETTER PHASE-D TU;Lo;0;L;;;;;N;;;;; 16912;BAMUM LETTER PHASE-D GHAA;Lo;0;L;;;;;N;;;;; 16913;BAMUM LETTER PHASE-D NGKYEE;Lo;0;L;;;;;N;;;;; 16914;BAMUM LETTER PHASE-D FEUFEUAET;Lo;0;L;;;;;N;;;;; 16915;BAMUM LETTER PHASE-D NDEE;Lo;0;L;;;;;N;;;;; 16916;BAMUM LETTER PHASE-D MGBOFUM;Lo;0;L;;;;;N;;;;; 16917;BAMUM LETTER PHASE-D LEUAEP;Lo;0;L;;;;;N;;;;; 16918;BAMUM LETTER PHASE-D NDON;Lo;0;L;;;;;N;;;;; 16919;BAMUM LETTER PHASE-D MONI;Lo;0;L;;;;;N;;;;; 1691A;BAMUM LETTER PHASE-D MGBEUN;Lo;0;L;;;;;N;;;;; 1691B;BAMUM LETTER PHASE-D PUUT;Lo;0;L;;;;;N;;;;; 1691C;BAMUM LETTER PHASE-D MGBIEE;Lo;0;L;;;;;N;;;;; 1691D;BAMUM LETTER PHASE-D MFO;Lo;0;L;;;;;N;;;;; 1691E;BAMUM LETTER PHASE-D LUM;Lo;0;L;;;;;N;;;;; 1691F;BAMUM LETTER PHASE-D NSIEEP;Lo;0;L;;;;;N;;;;; 16920;BAMUM LETTER PHASE-D MBAA;Lo;0;L;;;;;N;;;;; 16921;BAMUM LETTER PHASE-D KWAET;Lo;0;L;;;;;N;;;;; 16922;BAMUM LETTER PHASE-D NYET;Lo;0;L;;;;;N;;;;; 16923;BAMUM LETTER PHASE-D TEUAEN;Lo;0;L;;;;;N;;;;; 16924;BAMUM LETTER PHASE-D SOT;Lo;0;L;;;;;N;;;;; 16925;BAMUM LETTER PHASE-D YUWOQ;Lo;0;L;;;;;N;;;;; 16926;BAMUM LETTER PHASE-D KEUM;Lo;0;L;;;;;N;;;;; 16927;BAMUM LETTER PHASE-D RAEM;Lo;0;L;;;;;N;;;;; 16928;BAMUM LETTER PHASE-D TEEEE;Lo;0;L;;;;;N;;;;; 16929;BAMUM LETTER PHASE-D NGKEUAEQ;Lo;0;L;;;;;N;;;;; 1692A;BAMUM LETTER PHASE-D MFEUAE;Lo;0;L;;;;;N;;;;; 1692B;BAMUM LETTER PHASE-D NSIEET;Lo;0;L;;;;;N;;;;; 1692C;BAMUM LETTER PHASE-D KEUP;Lo;0;L;;;;;N;;;;; 1692D;BAMUM LETTER PHASE-D PIP;Lo;0;L;;;;;N;;;;; 1692E;BAMUM LETTER PHASE-D PEUTAE;Lo;0;L;;;;;N;;;;; 1692F;BAMUM LETTER PHASE-D NYUE;Lo;0;L;;;;;N;;;;; 16930;BAMUM LETTER PHASE-D LET;Lo;0;L;;;;;N;;;;; 16931;BAMUM LETTER PHASE-D NGGAAM;Lo;0;L;;;;;N;;;;; 16932;BAMUM LETTER PHASE-D MFIEE;Lo;0;L;;;;;N;;;;; 16933;BAMUM LETTER PHASE-D NGGWAEN;Lo;0;L;;;;;N;;;;; 16934;BAMUM LETTER PHASE-D YUOM;Lo;0;L;;;;;N;;;;; 16935;BAMUM LETTER PHASE-D PAP;Lo;0;L;;;;;N;;;;; 16936;BAMUM LETTER PHASE-D YUOP;Lo;0;L;;;;;N;;;;; 16937;BAMUM LETTER PHASE-D NDAM;Lo;0;L;;;;;N;;;;; 16938;BAMUM LETTER PHASE-D NTEUM;Lo;0;L;;;;;N;;;;; 16939;BAMUM LETTER PHASE-D SUAE;Lo;0;L;;;;;N;;;;; 1693A;BAMUM LETTER PHASE-D KUN;Lo;0;L;;;;;N;;;;; 1693B;BAMUM LETTER PHASE-D NGGEUX;Lo;0;L;;;;;N;;;;; 1693C;BAMUM LETTER PHASE-D NGKIEE;Lo;0;L;;;;;N;;;;; 1693D;BAMUM LETTER PHASE-D TUOT;Lo;0;L;;;;;N;;;;; 1693E;BAMUM LETTER PHASE-D MEUN;Lo;0;L;;;;;N;;;;; 1693F;BAMUM LETTER PHASE-D KUQ;Lo;0;L;;;;;N;;;;; 16940;BAMUM LETTER PHASE-D NSUM;Lo;0;L;;;;;N;;;;; 16941;BAMUM LETTER PHASE-D TEUN;Lo;0;L;;;;;N;;;;; 16942;BAMUM LETTER PHASE-D MAENJET;Lo;0;L;;;;;N;;;;; 16943;BAMUM LETTER PHASE-D NGGAP;Lo;0;L;;;;;N;;;;; 16944;BAMUM LETTER PHASE-D LEUM;Lo;0;L;;;;;N;;;;; 16945;BAMUM LETTER PHASE-D NGGUOM;Lo;0;L;;;;;N;;;;; 16946;BAMUM LETTER PHASE-D NSHUT;Lo;0;L;;;;;N;;;;; 16947;BAMUM LETTER PHASE-D NJUEQ;Lo;0;L;;;;;N;;;;; 16948;BAMUM LETTER PHASE-D GHEUAE;Lo;0;L;;;;;N;;;;; 16949;BAMUM LETTER PHASE-D KU;Lo;0;L;;;;;N;;;;; 1694A;BAMUM LETTER PHASE-D REN OLD;Lo;0;L;;;;;N;;;;; 1694B;BAMUM LETTER PHASE-D TAE;Lo;0;L;;;;;N;;;;; 1694C;BAMUM LETTER PHASE-D TOQ;Lo;0;L;;;;;N;;;;; 1694D;BAMUM LETTER PHASE-D NYI;Lo;0;L;;;;;N;;;;; 1694E;BAMUM LETTER PHASE-D RII;Lo;0;L;;;;;N;;;;; 1694F;BAMUM LETTER PHASE-D LEEEE;Lo;0;L;;;;;N;;;;; 16950;BAMUM LETTER PHASE-D MEEEE;Lo;0;L;;;;;N;;;;; 16951;BAMUM LETTER PHASE-D M;Lo;0;L;;;;;N;;;;; 16952;BAMUM LETTER PHASE-D SUU;Lo;0;L;;;;;N;;;;; 16953;BAMUM LETTER PHASE-D MU;Lo;0;L;;;;;N;;;;; 16954;BAMUM LETTER PHASE-D SHII;Lo;0;L;;;;;N;;;;; 16955;BAMUM LETTER PHASE-D SHEUX;Lo;0;L;;;;;N;;;;; 16956;BAMUM LETTER PHASE-D KYEE;Lo;0;L;;;;;N;;;;; 16957;BAMUM LETTER PHASE-D NU;Lo;0;L;;;;;N;;;;; 16958;BAMUM LETTER PHASE-D SHU;Lo;0;L;;;;;N;;;;; 16959;BAMUM LETTER PHASE-D NTEE;Lo;0;L;;;;;N;;;;; 1695A;BAMUM LETTER PHASE-D PEE;Lo;0;L;;;;;N;;;;; 1695B;BAMUM LETTER PHASE-D NI;Lo;0;L;;;;;N;;;;; 1695C;BAMUM LETTER PHASE-D SHOQ;Lo;0;L;;;;;N;;;;; 1695D;BAMUM LETTER PHASE-D PUQ;Lo;0;L;;;;;N;;;;; 1695E;BAMUM LETTER PHASE-D MVOP;Lo;0;L;;;;;N;;;;; 1695F;BAMUM LETTER PHASE-D LOQ;Lo;0;L;;;;;N;;;;; 16960;BAMUM LETTER PHASE-D REN MUCH;Lo;0;L;;;;;N;;;;; 16961;BAMUM LETTER PHASE-D TI;Lo;0;L;;;;;N;;;;; 16962;BAMUM LETTER PHASE-D NTUU;Lo;0;L;;;;;N;;;;; 16963;BAMUM LETTER PHASE-D MBAA SEVEN;Lo;0;L;;;;;N;;;;; 16964;BAMUM LETTER PHASE-D SAQ;Lo;0;L;;;;;N;;;;; 16965;BAMUM LETTER PHASE-D FAA;Lo;0;L;;;;;N;;;;; 16966;BAMUM LETTER PHASE-E NDAP;Lo;0;L;;;;;N;;;;; 16967;BAMUM LETTER PHASE-E TOON;Lo;0;L;;;;;N;;;;; 16968;BAMUM LETTER PHASE-E MBEUM;Lo;0;L;;;;;N;;;;; 16969;BAMUM LETTER PHASE-E LAP;Lo;0;L;;;;;N;;;;; 1696A;BAMUM LETTER PHASE-E VOM;Lo;0;L;;;;;N;;;;; 1696B;BAMUM LETTER PHASE-E LOON;Lo;0;L;;;;;N;;;;; 1696C;BAMUM LETTER PHASE-E PAA;Lo;0;L;;;;;N;;;;; 1696D;BAMUM LETTER PHASE-E SOM;Lo;0;L;;;;;N;;;;; 1696E;BAMUM LETTER PHASE-E RAQ;Lo;0;L;;;;;N;;;;; 1696F;BAMUM LETTER PHASE-E NSHUOP;Lo;0;L;;;;;N;;;;; 16970;BAMUM LETTER PHASE-E NDUN;Lo;0;L;;;;;N;;;;; 16971;BAMUM LETTER PHASE-E PUAE;Lo;0;L;;;;;N;;;;; 16972;BAMUM LETTER PHASE-E TAM;Lo;0;L;;;;;N;;;;; 16973;BAMUM LETTER PHASE-E NGKA;Lo;0;L;;;;;N;;;;; 16974;BAMUM LETTER PHASE-E KPEUX;Lo;0;L;;;;;N;;;;; 16975;BAMUM LETTER PHASE-E WUO;Lo;0;L;;;;;N;;;;; 16976;BAMUM LETTER PHASE-E SEE;Lo;0;L;;;;;N;;;;; 16977;BAMUM LETTER PHASE-E NGGEUAET;Lo;0;L;;;;;N;;;;; 16978;BAMUM LETTER PHASE-E PAAM;Lo;0;L;;;;;N;;;;; 16979;BAMUM LETTER PHASE-E TOO;Lo;0;L;;;;;N;;;;; 1697A;BAMUM LETTER PHASE-E KUOP;Lo;0;L;;;;;N;;;;; 1697B;BAMUM LETTER PHASE-E LOM;Lo;0;L;;;;;N;;;;; 1697C;BAMUM LETTER PHASE-E NSHIEE;Lo;0;L;;;;;N;;;;; 1697D;BAMUM LETTER PHASE-E NGOP;Lo;0;L;;;;;N;;;;; 1697E;BAMUM LETTER PHASE-E MAEM;Lo;0;L;;;;;N;;;;; 1697F;BAMUM LETTER PHASE-E NGKEUX;Lo;0;L;;;;;N;;;;; 16980;BAMUM LETTER PHASE-E NGOQ;Lo;0;L;;;;;N;;;;; 16981;BAMUM LETTER PHASE-E NSHUE;Lo;0;L;;;;;N;;;;; 16982;BAMUM LETTER PHASE-E RIMGBA;Lo;0;L;;;;;N;;;;; 16983;BAMUM LETTER PHASE-E NJEUX;Lo;0;L;;;;;N;;;;; 16984;BAMUM LETTER PHASE-E PEEM;Lo;0;L;;;;;N;;;;; 16985;BAMUM LETTER PHASE-E SAA;Lo;0;L;;;;;N;;;;; 16986;BAMUM LETTER PHASE-E NGGURAE;Lo;0;L;;;;;N;;;;; 16987;BAMUM LETTER PHASE-E MGBA;Lo;0;L;;;;;N;;;;; 16988;BAMUM LETTER PHASE-E GHEUX;Lo;0;L;;;;;N;;;;; 16989;BAMUM LETTER PHASE-E NGKEUAEM;Lo;0;L;;;;;N;;;;; 1698A;BAMUM LETTER PHASE-E NJAEMLI;Lo;0;L;;;;;N;;;;; 1698B;BAMUM LETTER PHASE-E MAP;Lo;0;L;;;;;N;;;;; 1698C;BAMUM LETTER PHASE-E LOOT;Lo;0;L;;;;;N;;;;; 1698D;BAMUM LETTER PHASE-E NGGEEEE;Lo;0;L;;;;;N;;;;; 1698E;BAMUM LETTER PHASE-E NDIQ;Lo;0;L;;;;;N;;;;; 1698F;BAMUM LETTER PHASE-E TAEN NTEUM;Lo;0;L;;;;;N;;;;; 16990;BAMUM LETTER PHASE-E SET;Lo;0;L;;;;;N;;;;; 16991;BAMUM LETTER PHASE-E PUM;Lo;0;L;;;;;N;;;;; 16992;BAMUM LETTER PHASE-E NDAA SOFTNESS;Lo;0;L;;;;;N;;;;; 16993;BAMUM LETTER PHASE-E NGGUAESHAE NYAM;Lo;0;L;;;;;N;;;;; 16994;BAMUM LETTER PHASE-E YIEE;Lo;0;L;;;;;N;;;;; 16995;BAMUM LETTER PHASE-E GHEUN;Lo;0;L;;;;;N;;;;; 16996;BAMUM LETTER PHASE-E TUAE;Lo;0;L;;;;;N;;;;; 16997;BAMUM LETTER PHASE-E YEUAE;Lo;0;L;;;;;N;;;;; 16998;BAMUM LETTER PHASE-E PO;Lo;0;L;;;;;N;;;;; 16999;BAMUM LETTER PHASE-E TUMAE;Lo;0;L;;;;;N;;;;; 1699A;BAMUM LETTER PHASE-E KEUAE;Lo;0;L;;;;;N;;;;; 1699B;BAMUM LETTER PHASE-E SUAEN;Lo;0;L;;;;;N;;;;; 1699C;BAMUM LETTER PHASE-E TEUAEQ;Lo;0;L;;;;;N;;;;; 1699D;BAMUM LETTER PHASE-E VEUAE;Lo;0;L;;;;;N;;;;; 1699E;BAMUM LETTER PHASE-E WEUX;Lo;0;L;;;;;N;;;;; 1699F;BAMUM LETTER PHASE-E LAAM;Lo;0;L;;;;;N;;;;; 169A0;BAMUM LETTER PHASE-E PU;Lo;0;L;;;;;N;;;;; 169A1;BAMUM LETTER PHASE-E TAAQ;Lo;0;L;;;;;N;;;;; 169A2;BAMUM LETTER PHASE-E GHAAMAE;Lo;0;L;;;;;N;;;;; 169A3;BAMUM LETTER PHASE-E NGEUREUT;Lo;0;L;;;;;N;;;;; 169A4;BAMUM LETTER PHASE-E SHEUAEQ;Lo;0;L;;;;;N;;;;; 169A5;BAMUM LETTER PHASE-E MGBEN;Lo;0;L;;;;;N;;;;; 169A6;BAMUM LETTER PHASE-E MBEE;Lo;0;L;;;;;N;;;;; 169A7;BAMUM LETTER PHASE-E NZAQ;Lo;0;L;;;;;N;;;;; 169A8;BAMUM LETTER PHASE-E NKOM;Lo;0;L;;;;;N;;;;; 169A9;BAMUM LETTER PHASE-E GBET;Lo;0;L;;;;;N;;;;; 169AA;BAMUM LETTER PHASE-E TUM;Lo;0;L;;;;;N;;;;; 169AB;BAMUM LETTER PHASE-E KUET;Lo;0;L;;;;;N;;;;; 169AC;BAMUM LETTER PHASE-E YAP;Lo;0;L;;;;;N;;;;; 169AD;BAMUM LETTER PHASE-E NYI CLEAVER;Lo;0;L;;;;;N;;;;; 169AE;BAMUM LETTER PHASE-E YIT;Lo;0;L;;;;;N;;;;; 169AF;BAMUM LETTER PHASE-E MFEUQ;Lo;0;L;;;;;N;;;;; 169B0;BAMUM LETTER PHASE-E NDIAQ;Lo;0;L;;;;;N;;;;; 169B1;BAMUM LETTER PHASE-E PIEEQ;Lo;0;L;;;;;N;;;;; 169B2;BAMUM LETTER PHASE-E YUEQ;Lo;0;L;;;;;N;;;;; 169B3;BAMUM LETTER PHASE-E LEUAEM;Lo;0;L;;;;;N;;;;; 169B4;BAMUM LETTER PHASE-E FUE;Lo;0;L;;;;;N;;;;; 169B5;BAMUM LETTER PHASE-E GBEUX;Lo;0;L;;;;;N;;;;; 169B6;BAMUM LETTER PHASE-E NGKUP;Lo;0;L;;;;;N;;;;; 169B7;BAMUM LETTER PHASE-E KET;Lo;0;L;;;;;N;;;;; 169B8;BAMUM LETTER PHASE-E MAE;Lo;0;L;;;;;N;;;;; 169B9;BAMUM LETTER PHASE-E NGKAAMI;Lo;0;L;;;;;N;;;;; 169BA;BAMUM LETTER PHASE-E GHET;Lo;0;L;;;;;N;;;;; 169BB;BAMUM LETTER PHASE-E FA;Lo;0;L;;;;;N;;;;; 169BC;BAMUM LETTER PHASE-E NTUM;Lo;0;L;;;;;N;;;;; 169BD;BAMUM LETTER PHASE-E PEUT;Lo;0;L;;;;;N;;;;; 169BE;BAMUM LETTER PHASE-E YEUM;Lo;0;L;;;;;N;;;;; 169BF;BAMUM LETTER PHASE-E NGGEUAE;Lo;0;L;;;;;N;;;;; 169C0;BAMUM LETTER PHASE-E NYI BETWEEN;Lo;0;L;;;;;N;;;;; 169C1;BAMUM LETTER PHASE-E NZUQ;Lo;0;L;;;;;N;;;;; 169C2;BAMUM LETTER PHASE-E POON;Lo;0;L;;;;;N;;;;; 169C3;BAMUM LETTER PHASE-E MIEE;Lo;0;L;;;;;N;;;;; 169C4;BAMUM LETTER PHASE-E FUET;Lo;0;L;;;;;N;;;;; 169C5;BAMUM LETTER PHASE-E NAE;Lo;0;L;;;;;N;;;;; 169C6;BAMUM LETTER PHASE-E MUAE;Lo;0;L;;;;;N;;;;; 169C7;BAMUM LETTER PHASE-E GHEUAE;Lo;0;L;;;;;N;;;;; 169C8;BAMUM LETTER PHASE-E FU I;Lo;0;L;;;;;N;;;;; 169C9;BAMUM LETTER PHASE-E MVI;Lo;0;L;;;;;N;;;;; 169CA;BAMUM LETTER PHASE-E PUAQ;Lo;0;L;;;;;N;;;;; 169CB;BAMUM LETTER PHASE-E NGKUM;Lo;0;L;;;;;N;;;;; 169CC;BAMUM LETTER PHASE-E KUT;Lo;0;L;;;;;N;;;;; 169CD;BAMUM LETTER PHASE-E PIET;Lo;0;L;;;;;N;;;;; 169CE;BAMUM LETTER PHASE-E NTAP;Lo;0;L;;;;;N;;;;; 169CF;BAMUM LETTER PHASE-E YEUAET;Lo;0;L;;;;;N;;;;; 169D0;BAMUM LETTER PHASE-E NGGUP;Lo;0;L;;;;;N;;;;; 169D1;BAMUM LETTER PHASE-E PA PEOPLE;Lo;0;L;;;;;N;;;;; 169D2;BAMUM LETTER PHASE-E FU CALL;Lo;0;L;;;;;N;;;;; 169D3;BAMUM LETTER PHASE-E FOM;Lo;0;L;;;;;N;;;;; 169D4;BAMUM LETTER PHASE-E NJEE;Lo;0;L;;;;;N;;;;; 169D5;BAMUM LETTER PHASE-E A;Lo;0;L;;;;;N;;;;; 169D6;BAMUM LETTER PHASE-E TOQ;Lo;0;L;;;;;N;;;;; 169D7;BAMUM LETTER PHASE-E O;Lo;0;L;;;;;N;;;;; 169D8;BAMUM LETTER PHASE-E I;Lo;0;L;;;;;N;;;;; 169D9;BAMUM LETTER PHASE-E LAQ;Lo;0;L;;;;;N;;;;; 169DA;BAMUM LETTER PHASE-E PA PLURAL;Lo;0;L;;;;;N;;;;; 169DB;BAMUM LETTER PHASE-E TAA;Lo;0;L;;;;;N;;;;; 169DC;BAMUM LETTER PHASE-E TAQ;Lo;0;L;;;;;N;;;;; 169DD;BAMUM LETTER PHASE-E NDAA MY HOUSE;Lo;0;L;;;;;N;;;;; 169DE;BAMUM LETTER PHASE-E SHIQ;Lo;0;L;;;;;N;;;;; 169DF;BAMUM LETTER PHASE-E YEUX;Lo;0;L;;;;;N;;;;; 169E0;BAMUM LETTER PHASE-E NGUAE;Lo;0;L;;;;;N;;;;; 169E1;BAMUM LETTER PHASE-E YUAEN;Lo;0;L;;;;;N;;;;; 169E2;BAMUM LETTER PHASE-E YOQ SWIMMING;Lo;0;L;;;;;N;;;;; 169E3;BAMUM LETTER PHASE-E YOQ COVER;Lo;0;L;;;;;N;;;;; 169E4;BAMUM LETTER PHASE-E YUQ;Lo;0;L;;;;;N;;;;; 169E5;BAMUM LETTER PHASE-E YUN;Lo;0;L;;;;;N;;;;; 169E6;BAMUM LETTER PHASE-E KEUX;Lo;0;L;;;;;N;;;;; 169E7;BAMUM LETTER PHASE-E PEUX;Lo;0;L;;;;;N;;;;; 169E8;BAMUM LETTER PHASE-E NJEE EPOCH;Lo;0;L;;;;;N;;;;; 169E9;BAMUM LETTER PHASE-E PUE;Lo;0;L;;;;;N;;;;; 169EA;BAMUM LETTER PHASE-E WUE;Lo;0;L;;;;;N;;;;; 169EB;BAMUM LETTER PHASE-E FEE;Lo;0;L;;;;;N;;;;; 169EC;BAMUM LETTER PHASE-E VEE;Lo;0;L;;;;;N;;;;; 169ED;BAMUM LETTER PHASE-E LU;Lo;0;L;;;;;N;;;;; 169EE;BAMUM LETTER PHASE-E MI;Lo;0;L;;;;;N;;;;; 169EF;BAMUM LETTER PHASE-E REUX;Lo;0;L;;;;;N;;;;; 169F0;BAMUM LETTER PHASE-E RAE;Lo;0;L;;;;;N;;;;; 169F1;BAMUM LETTER PHASE-E NGUAET;Lo;0;L;;;;;N;;;;; 169F2;BAMUM LETTER PHASE-E NGA;Lo;0;L;;;;;N;;;;; 169F3;BAMUM LETTER PHASE-E SHO;Lo;0;L;;;;;N;;;;; 169F4;BAMUM LETTER PHASE-E SHOQ;Lo;0;L;;;;;N;;;;; 169F5;BAMUM LETTER PHASE-E FU REMEDY;Lo;0;L;;;;;N;;;;; 169F6;BAMUM LETTER PHASE-E NA;Lo;0;L;;;;;N;;;;; 169F7;BAMUM LETTER PHASE-E PI;Lo;0;L;;;;;N;;;;; 169F8;BAMUM LETTER PHASE-E LOQ;Lo;0;L;;;;;N;;;;; 169F9;BAMUM LETTER PHASE-E KO;Lo;0;L;;;;;N;;;;; 169FA;BAMUM LETTER PHASE-E MEN;Lo;0;L;;;;;N;;;;; 169FB;BAMUM LETTER PHASE-E MA;Lo;0;L;;;;;N;;;;; 169FC;BAMUM LETTER PHASE-E MAQ;Lo;0;L;;;;;N;;;;; 169FD;BAMUM LETTER PHASE-E TEU;Lo;0;L;;;;;N;;;;; 169FE;BAMUM LETTER PHASE-E KI;Lo;0;L;;;;;N;;;;; 169FF;BAMUM LETTER PHASE-E MON;Lo;0;L;;;;;N;;;;; 16A00;BAMUM LETTER PHASE-E TEN;Lo;0;L;;;;;N;;;;; 16A01;BAMUM LETTER PHASE-E FAQ;Lo;0;L;;;;;N;;;;; 16A02;BAMUM LETTER PHASE-E GHOM;Lo;0;L;;;;;N;;;;; 16A03;BAMUM LETTER PHASE-F KA;Lo;0;L;;;;;N;;;;; 16A04;BAMUM LETTER PHASE-F U;Lo;0;L;;;;;N;;;;; 16A05;BAMUM LETTER PHASE-F KU;Lo;0;L;;;;;N;;;;; 16A06;BAMUM LETTER PHASE-F EE;Lo;0;L;;;;;N;;;;; 16A07;BAMUM LETTER PHASE-F REE;Lo;0;L;;;;;N;;;;; 16A08;BAMUM LETTER PHASE-F TAE;Lo;0;L;;;;;N;;;;; 16A09;BAMUM LETTER PHASE-F NYI;Lo;0;L;;;;;N;;;;; 16A0A;BAMUM LETTER PHASE-F LA;Lo;0;L;;;;;N;;;;; 16A0B;BAMUM LETTER PHASE-F RII;Lo;0;L;;;;;N;;;;; 16A0C;BAMUM LETTER PHASE-F RIEE;Lo;0;L;;;;;N;;;;; 16A0D;BAMUM LETTER PHASE-F MEEEE;Lo;0;L;;;;;N;;;;; 16A0E;BAMUM LETTER PHASE-F TAA;Lo;0;L;;;;;N;;;;; 16A0F;BAMUM LETTER PHASE-F NDAA;Lo;0;L;;;;;N;;;;; 16A10;BAMUM LETTER PHASE-F NJAEM;Lo;0;L;;;;;N;;;;; 16A11;BAMUM LETTER PHASE-F M;Lo;0;L;;;;;N;;;;; 16A12;BAMUM LETTER PHASE-F SUU;Lo;0;L;;;;;N;;;;; 16A13;BAMUM LETTER PHASE-F SHII;Lo;0;L;;;;;N;;;;; 16A14;BAMUM LETTER PHASE-F SI;Lo;0;L;;;;;N;;;;; 16A15;BAMUM LETTER PHASE-F SEUX;Lo;0;L;;;;;N;;;;; 16A16;BAMUM LETTER PHASE-F KYEE;Lo;0;L;;;;;N;;;;; 16A17;BAMUM LETTER PHASE-F KET;Lo;0;L;;;;;N;;;;; 16A18;BAMUM LETTER PHASE-F NUAE;Lo;0;L;;;;;N;;;;; 16A19;BAMUM LETTER PHASE-F NU;Lo;0;L;;;;;N;;;;; 16A1A;BAMUM LETTER PHASE-F NJUAE;Lo;0;L;;;;;N;;;;; 16A1B;BAMUM LETTER PHASE-F YOQ;Lo;0;L;;;;;N;;;;; 16A1C;BAMUM LETTER PHASE-F SHU;Lo;0;L;;;;;N;;;;; 16A1D;BAMUM LETTER PHASE-F YA;Lo;0;L;;;;;N;;;;; 16A1E;BAMUM LETTER PHASE-F NSHA;Lo;0;L;;;;;N;;;;; 16A1F;BAMUM LETTER PHASE-F PEUX;Lo;0;L;;;;;N;;;;; 16A20;BAMUM LETTER PHASE-F NTEE;Lo;0;L;;;;;N;;;;; 16A21;BAMUM LETTER PHASE-F WUE;Lo;0;L;;;;;N;;;;; 16A22;BAMUM LETTER PHASE-F PEE;Lo;0;L;;;;;N;;;;; 16A23;BAMUM LETTER PHASE-F RU;Lo;0;L;;;;;N;;;;; 16A24;BAMUM LETTER PHASE-F NI;Lo;0;L;;;;;N;;;;; 16A25;BAMUM LETTER PHASE-F REUX;Lo;0;L;;;;;N;;;;; 16A26;BAMUM LETTER PHASE-F KEN;Lo;0;L;;;;;N;;;;; 16A27;BAMUM LETTER PHASE-F NGKWAEN;Lo;0;L;;;;;N;;;;; 16A28;BAMUM LETTER PHASE-F NGGA;Lo;0;L;;;;;N;;;;; 16A29;BAMUM LETTER PHASE-F SHO;Lo;0;L;;;;;N;;;;; 16A2A;BAMUM LETTER PHASE-F PUAE;Lo;0;L;;;;;N;;;;; 16A2B;BAMUM LETTER PHASE-F FOM;Lo;0;L;;;;;N;;;;; 16A2C;BAMUM LETTER PHASE-F WA;Lo;0;L;;;;;N;;;;; 16A2D;BAMUM LETTER PHASE-F LI;Lo;0;L;;;;;N;;;;; 16A2E;BAMUM LETTER PHASE-F LOQ;Lo;0;L;;;;;N;;;;; 16A2F;BAMUM LETTER PHASE-F KO;Lo;0;L;;;;;N;;;;; 16A30;BAMUM LETTER PHASE-F MBEN;Lo;0;L;;;;;N;;;;; 16A31;BAMUM LETTER PHASE-F REN;Lo;0;L;;;;;N;;;;; 16A32;BAMUM LETTER PHASE-F MA;Lo;0;L;;;;;N;;;;; 16A33;BAMUM LETTER PHASE-F MO;Lo;0;L;;;;;N;;;;; 16A34;BAMUM LETTER PHASE-F MBAA;Lo;0;L;;;;;N;;;;; 16A35;BAMUM LETTER PHASE-F TET;Lo;0;L;;;;;N;;;;; 16A36;BAMUM LETTER PHASE-F KPA;Lo;0;L;;;;;N;;;;; 16A37;BAMUM LETTER PHASE-F SAMBA;Lo;0;L;;;;;N;;;;; 16A38;BAMUM LETTER PHASE-F VUEQ;Lo;0;L;;;;;N;;;;; 16A40;MRO LETTER TA;Lo;0;L;;;;;N;;;;; 16A41;MRO LETTER NGI;Lo;0;L;;;;;N;;;;; 16A42;MRO LETTER YO;Lo;0;L;;;;;N;;;;; 16A43;MRO LETTER MIM;Lo;0;L;;;;;N;;;;; 16A44;MRO LETTER BA;Lo;0;L;;;;;N;;;;; 16A45;MRO LETTER DA;Lo;0;L;;;;;N;;;;; 16A46;MRO LETTER A;Lo;0;L;;;;;N;;;;; 16A47;MRO LETTER PHI;Lo;0;L;;;;;N;;;;; 16A48;MRO LETTER KHAI;Lo;0;L;;;;;N;;;;; 16A49;MRO LETTER HAO;Lo;0;L;;;;;N;;;;; 16A4A;MRO LETTER DAI;Lo;0;L;;;;;N;;;;; 16A4B;MRO LETTER CHU;Lo;0;L;;;;;N;;;;; 16A4C;MRO LETTER KEAAE;Lo;0;L;;;;;N;;;;; 16A4D;MRO LETTER OL;Lo;0;L;;;;;N;;;;; 16A4E;MRO LETTER MAEM;Lo;0;L;;;;;N;;;;; 16A4F;MRO LETTER NIN;Lo;0;L;;;;;N;;;;; 16A50;MRO LETTER PA;Lo;0;L;;;;;N;;;;; 16A51;MRO LETTER OO;Lo;0;L;;;;;N;;;;; 16A52;MRO LETTER O;Lo;0;L;;;;;N;;;;; 16A53;MRO LETTER RO;Lo;0;L;;;;;N;;;;; 16A54;MRO LETTER SHI;Lo;0;L;;;;;N;;;;; 16A55;MRO LETTER THEA;Lo;0;L;;;;;N;;;;; 16A56;MRO LETTER EA;Lo;0;L;;;;;N;;;;; 16A57;MRO LETTER WA;Lo;0;L;;;;;N;;;;; 16A58;MRO LETTER E;Lo;0;L;;;;;N;;;;; 16A59;MRO LETTER KO;Lo;0;L;;;;;N;;;;; 16A5A;MRO LETTER LAN;Lo;0;L;;;;;N;;;;; 16A5B;MRO LETTER LA;Lo;0;L;;;;;N;;;;; 16A5C;MRO LETTER HAI;Lo;0;L;;;;;N;;;;; 16A5D;MRO LETTER RI;Lo;0;L;;;;;N;;;;; 16A5E;MRO LETTER TEK;Lo;0;L;;;;;N;;;;; 16A60;MRO DIGIT ZERO;Nd;0;L;;0;0;0;N;;;;; 16A61;MRO DIGIT ONE;Nd;0;L;;1;1;1;N;;;;; 16A62;MRO DIGIT TWO;Nd;0;L;;2;2;2;N;;;;; 16A63;MRO DIGIT THREE;Nd;0;L;;3;3;3;N;;;;; 16A64;MRO DIGIT FOUR;Nd;0;L;;4;4;4;N;;;;; 16A65;MRO DIGIT FIVE;Nd;0;L;;5;5;5;N;;;;; 16A66;MRO DIGIT SIX;Nd;0;L;;6;6;6;N;;;;; 16A67;MRO DIGIT SEVEN;Nd;0;L;;7;7;7;N;;;;; 16A68;MRO DIGIT EIGHT;Nd;0;L;;8;8;8;N;;;;; 16A69;MRO DIGIT NINE;Nd;0;L;;9;9;9;N;;;;; 16A6E;MRO DANDA;Po;0;L;;;;;N;;;;; 16A6F;MRO DOUBLE DANDA;Po;0;L;;;;;N;;;;; 16AD0;BASSA VAH LETTER ENNI;Lo;0;L;;;;;N;;;;; 16AD1;BASSA VAH LETTER KA;Lo;0;L;;;;;N;;;;; 16AD2;BASSA VAH LETTER SE;Lo;0;L;;;;;N;;;;; 16AD3;BASSA VAH LETTER FA;Lo;0;L;;;;;N;;;;; 16AD4;BASSA VAH LETTER MBE;Lo;0;L;;;;;N;;;;; 16AD5;BASSA VAH LETTER YIE;Lo;0;L;;;;;N;;;;; 16AD6;BASSA VAH LETTER GAH;Lo;0;L;;;;;N;;;;; 16AD7;BASSA VAH LETTER DHII;Lo;0;L;;;;;N;;;;; 16AD8;BASSA VAH LETTER KPAH;Lo;0;L;;;;;N;;;;; 16AD9;BASSA VAH LETTER JO;Lo;0;L;;;;;N;;;;; 16ADA;BASSA VAH LETTER HWAH;Lo;0;L;;;;;N;;;;; 16ADB;BASSA VAH LETTER WA;Lo;0;L;;;;;N;;;;; 16ADC;BASSA VAH LETTER ZO;Lo;0;L;;;;;N;;;;; 16ADD;BASSA VAH LETTER GBU;Lo;0;L;;;;;N;;;;; 16ADE;BASSA VAH LETTER DO;Lo;0;L;;;;;N;;;;; 16ADF;BASSA VAH LETTER CE;Lo;0;L;;;;;N;;;;; 16AE0;BASSA VAH LETTER UWU;Lo;0;L;;;;;N;;;;; 16AE1;BASSA VAH LETTER TO;Lo;0;L;;;;;N;;;;; 16AE2;BASSA VAH LETTER BA;Lo;0;L;;;;;N;;;;; 16AE3;BASSA VAH LETTER VU;Lo;0;L;;;;;N;;;;; 16AE4;BASSA VAH LETTER YEIN;Lo;0;L;;;;;N;;;;; 16AE5;BASSA VAH LETTER PA;Lo;0;L;;;;;N;;;;; 16AE6;BASSA VAH LETTER WADDA;Lo;0;L;;;;;N;;;;; 16AE7;BASSA VAH LETTER A;Lo;0;L;;;;;N;;;;; 16AE8;BASSA VAH LETTER O;Lo;0;L;;;;;N;;;;; 16AE9;BASSA VAH LETTER OO;Lo;0;L;;;;;N;;;;; 16AEA;BASSA VAH LETTER U;Lo;0;L;;;;;N;;;;; 16AEB;BASSA VAH LETTER EE;Lo;0;L;;;;;N;;;;; 16AEC;BASSA VAH LETTER E;Lo;0;L;;;;;N;;;;; 16AED;BASSA VAH LETTER I;Lo;0;L;;;;;N;;;;; 16AF0;BASSA VAH COMBINING HIGH TONE;Mn;1;NSM;;;;;N;;;;; 16AF1;BASSA VAH COMBINING LOW TONE;Mn;1;NSM;;;;;N;;;;; 16AF2;BASSA VAH COMBINING MID TONE;Mn;1;NSM;;;;;N;;;;; 16AF3;BASSA VAH COMBINING LOW-MID TONE;Mn;1;NSM;;;;;N;;;;; 16AF4;BASSA VAH COMBINING HIGH-LOW TONE;Mn;1;NSM;;;;;N;;;;; 16AF5;BASSA VAH FULL STOP;Po;0;L;;;;;N;;;;; 16B00;PAHAWH HMONG VOWEL KEEB;Lo;0;L;;;;;N;;;;; 16B01;PAHAWH HMONG VOWEL KEEV;Lo;0;L;;;;;N;;;;; 16B02;PAHAWH HMONG VOWEL KIB;Lo;0;L;;;;;N;;;;; 16B03;PAHAWH HMONG VOWEL KIV;Lo;0;L;;;;;N;;;;; 16B04;PAHAWH HMONG VOWEL KAUB;Lo;0;L;;;;;N;;;;; 16B05;PAHAWH HMONG VOWEL KAUV;Lo;0;L;;;;;N;;;;; 16B06;PAHAWH HMONG VOWEL KUB;Lo;0;L;;;;;N;;;;; 16B07;PAHAWH HMONG VOWEL KUV;Lo;0;L;;;;;N;;;;; 16B08;PAHAWH HMONG VOWEL KEB;Lo;0;L;;;;;N;;;;; 16B09;PAHAWH HMONG VOWEL KEV;Lo;0;L;;;;;N;;;;; 16B0A;PAHAWH HMONG VOWEL KAIB;Lo;0;L;;;;;N;;;;; 16B0B;PAHAWH HMONG VOWEL KAIV;Lo;0;L;;;;;N;;;;; 16B0C;PAHAWH HMONG VOWEL KOOB;Lo;0;L;;;;;N;;;;; 16B0D;PAHAWH HMONG VOWEL KOOV;Lo;0;L;;;;;N;;;;; 16B0E;PAHAWH HMONG VOWEL KAWB;Lo;0;L;;;;;N;;;;; 16B0F;PAHAWH HMONG VOWEL KAWV;Lo;0;L;;;;;N;;;;; 16B10;PAHAWH HMONG VOWEL KUAB;Lo;0;L;;;;;N;;;;; 16B11;PAHAWH HMONG VOWEL KUAV;Lo;0;L;;;;;N;;;;; 16B12;PAHAWH HMONG VOWEL KOB;Lo;0;L;;;;;N;;;;; 16B13;PAHAWH HMONG VOWEL KOV;Lo;0;L;;;;;N;;;;; 16B14;PAHAWH HMONG VOWEL KIAB;Lo;0;L;;;;;N;;;;; 16B15;PAHAWH HMONG VOWEL KIAV;Lo;0;L;;;;;N;;;;; 16B16;PAHAWH HMONG VOWEL KAB;Lo;0;L;;;;;N;;;;; 16B17;PAHAWH HMONG VOWEL KAV;Lo;0;L;;;;;N;;;;; 16B18;PAHAWH HMONG VOWEL KWB;Lo;0;L;;;;;N;;;;; 16B19;PAHAWH HMONG VOWEL KWV;Lo;0;L;;;;;N;;;;; 16B1A;PAHAWH HMONG VOWEL KAAB;Lo;0;L;;;;;N;;;;; 16B1B;PAHAWH HMONG VOWEL KAAV;Lo;0;L;;;;;N;;;;; 16B1C;PAHAWH HMONG CONSONANT VAU;Lo;0;L;;;;;N;;;;; 16B1D;PAHAWH HMONG CONSONANT NTSAU;Lo;0;L;;;;;N;;;;; 16B1E;PAHAWH HMONG CONSONANT LAU;Lo;0;L;;;;;N;;;;; 16B1F;PAHAWH HMONG CONSONANT HAU;Lo;0;L;;;;;N;;;;; 16B20;PAHAWH HMONG CONSONANT NLAU;Lo;0;L;;;;;N;;;;; 16B21;PAHAWH HMONG CONSONANT RAU;Lo;0;L;;;;;N;;;;; 16B22;PAHAWH HMONG CONSONANT NKAU;Lo;0;L;;;;;N;;;;; 16B23;PAHAWH HMONG CONSONANT QHAU;Lo;0;L;;;;;N;;;;; 16B24;PAHAWH HMONG CONSONANT YAU;Lo;0;L;;;;;N;;;;; 16B25;PAHAWH HMONG CONSONANT HLAU;Lo;0;L;;;;;N;;;;; 16B26;PAHAWH HMONG CONSONANT MAU;Lo;0;L;;;;;N;;;;; 16B27;PAHAWH HMONG CONSONANT CHAU;Lo;0;L;;;;;N;;;;; 16B28;PAHAWH HMONG CONSONANT NCHAU;Lo;0;L;;;;;N;;;;; 16B29;PAHAWH HMONG CONSONANT HNAU;Lo;0;L;;;;;N;;;;; 16B2A;PAHAWH HMONG CONSONANT PLHAU;Lo;0;L;;;;;N;;;;; 16B2B;PAHAWH HMONG CONSONANT NTHAU;Lo;0;L;;;;;N;;;;; 16B2C;PAHAWH HMONG CONSONANT NAU;Lo;0;L;;;;;N;;;;; 16B2D;PAHAWH HMONG CONSONANT AU;Lo;0;L;;;;;N;;;;; 16B2E;PAHAWH HMONG CONSONANT XAU;Lo;0;L;;;;;N;;;;; 16B2F;PAHAWH HMONG CONSONANT CAU;Lo;0;L;;;;;N;;;;; 16B30;PAHAWH HMONG MARK CIM TUB;Mn;230;NSM;;;;;N;;;;; 16B31;PAHAWH HMONG MARK CIM SO;Mn;230;NSM;;;;;N;;;;; 16B32;PAHAWH HMONG MARK CIM KES;Mn;230;NSM;;;;;N;;;;; 16B33;PAHAWH HMONG MARK CIM KHAV;Mn;230;NSM;;;;;N;;;;; 16B34;PAHAWH HMONG MARK CIM SUAM;Mn;230;NSM;;;;;N;;;;; 16B35;PAHAWH HMONG MARK CIM HOM;Mn;230;NSM;;;;;N;;;;; 16B36;PAHAWH HMONG MARK CIM TAUM;Mn;230;NSM;;;;;N;;;;; 16B37;PAHAWH HMONG SIGN VOS THOM;Po;0;L;;;;;N;;;;; 16B38;PAHAWH HMONG SIGN VOS TSHAB CEEB;Po;0;L;;;;;N;;;;; 16B39;PAHAWH HMONG SIGN CIM CHEEM;Po;0;L;;;;;N;;;;; 16B3A;PAHAWH HMONG SIGN VOS THIAB;Po;0;L;;;;;N;;;;; 16B3B;PAHAWH HMONG SIGN VOS FEEM;Po;0;L;;;;;N;;;;; 16B3C;PAHAWH HMONG SIGN XYEEM NTXIV;So;0;L;;;;;N;;;;; 16B3D;PAHAWH HMONG SIGN XYEEM RHO;So;0;L;;;;;N;;;;; 16B3E;PAHAWH HMONG SIGN XYEEM TOV;So;0;L;;;;;N;;;;; 16B3F;PAHAWH HMONG SIGN XYEEM FAIB;So;0;L;;;;;N;;;;; 16B40;PAHAWH HMONG SIGN VOS SEEV;Lm;0;L;;;;;N;;;;; 16B41;PAHAWH HMONG SIGN MEEJ SUAB;Lm;0;L;;;;;N;;;;; 16B42;PAHAWH HMONG SIGN VOS NRUA;Lm;0;L;;;;;N;;;;; 16B43;PAHAWH HMONG SIGN IB YAM;Lm;0;L;;;;;N;;;;; 16B44;PAHAWH HMONG SIGN XAUS;Po;0;L;;;;;N;;;;; 16B45;PAHAWH HMONG SIGN CIM TSOV ROG;So;0;L;;;;;N;;;;; 16B50;PAHAWH HMONG DIGIT ZERO;Nd;0;L;;0;0;0;N;;;;; 16B51;PAHAWH HMONG DIGIT ONE;Nd;0;L;;1;1;1;N;;;;; 16B52;PAHAWH HMONG DIGIT TWO;Nd;0;L;;2;2;2;N;;;;; 16B53;PAHAWH HMONG DIGIT THREE;Nd;0;L;;3;3;3;N;;;;; 16B54;PAHAWH HMONG DIGIT FOUR;Nd;0;L;;4;4;4;N;;;;; 16B55;PAHAWH HMONG DIGIT FIVE;Nd;0;L;;5;5;5;N;;;;; 16B56;PAHAWH HMONG DIGIT SIX;Nd;0;L;;6;6;6;N;;;;; 16B57;PAHAWH HMONG DIGIT SEVEN;Nd;0;L;;7;7;7;N;;;;; 16B58;PAHAWH HMONG DIGIT EIGHT;Nd;0;L;;8;8;8;N;;;;; 16B59;PAHAWH HMONG DIGIT NINE;Nd;0;L;;9;9;9;N;;;;; 16B5B;PAHAWH HMONG NUMBER TENS;No;0;L;;;;10;N;;;;; 16B5C;PAHAWH HMONG NUMBER HUNDREDS;No;0;L;;;;100;N;;;;; 16B5D;PAHAWH HMONG NUMBER TEN THOUSANDS;No;0;L;;;;10000;N;;;;; 16B5E;PAHAWH HMONG NUMBER MILLIONS;No;0;L;;;;1000000;N;;;;; 16B5F;PAHAWH HMONG NUMBER HUNDRED MILLIONS;No;0;L;;;;100000000;N;;;;; 16B60;PAHAWH HMONG NUMBER TEN BILLIONS;No;0;L;;;;10000000000;N;;;;; 16B61;PAHAWH HMONG NUMBER TRILLIONS;No;0;L;;;;1000000000000;N;;;;; 16B63;PAHAWH HMONG SIGN VOS LUB;Lo;0;L;;;;;N;;;;; 16B64;PAHAWH HMONG SIGN XYOO;Lo;0;L;;;;;N;;;;; 16B65;PAHAWH HMONG SIGN HLI;Lo;0;L;;;;;N;;;;; 16B66;PAHAWH HMONG SIGN THIRD-STAGE HLI;Lo;0;L;;;;;N;;;;; 16B67;PAHAWH HMONG SIGN ZWJ THAJ;Lo;0;L;;;;;N;;;;; 16B68;PAHAWH HMONG SIGN HNUB;Lo;0;L;;;;;N;;;;; 16B69;PAHAWH HMONG SIGN NQIG;Lo;0;L;;;;;N;;;;; 16B6A;PAHAWH HMONG SIGN XIAB;Lo;0;L;;;;;N;;;;; 16B6B;PAHAWH HMONG SIGN NTUJ;Lo;0;L;;;;;N;;;;; 16B6C;PAHAWH HMONG SIGN AV;Lo;0;L;;;;;N;;;;; 16B6D;PAHAWH HMONG SIGN TXHEEJ CEEV;Lo;0;L;;;;;N;;;;; 16B6E;PAHAWH HMONG SIGN MEEJ TSEEB;Lo;0;L;;;;;N;;;;; 16B6F;PAHAWH HMONG SIGN TAU;Lo;0;L;;;;;N;;;;; 16B70;PAHAWH HMONG SIGN LOS;Lo;0;L;;;;;N;;;;; 16B71;PAHAWH HMONG SIGN MUS;Lo;0;L;;;;;N;;;;; 16B72;PAHAWH HMONG SIGN CIM HAIS LUS NTOG NTOG;Lo;0;L;;;;;N;;;;; 16B73;PAHAWH HMONG SIGN CIM CUAM TSHOOJ;Lo;0;L;;;;;N;;;;; 16B74;PAHAWH HMONG SIGN CIM TXWV;Lo;0;L;;;;;N;;;;; 16B75;PAHAWH HMONG SIGN CIM TXWV CHWV;Lo;0;L;;;;;N;;;;; 16B76;PAHAWH HMONG SIGN CIM PUB DAWB;Lo;0;L;;;;;N;;;;; 16B77;PAHAWH HMONG SIGN CIM NRES TOS;Lo;0;L;;;;;N;;;;; 16B7D;PAHAWH HMONG CLAN SIGN TSHEEJ;Lo;0;L;;;;;N;;;;; 16B7E;PAHAWH HMONG CLAN SIGN YEEG;Lo;0;L;;;;;N;;;;; 16B7F;PAHAWH HMONG CLAN SIGN LIS;Lo;0;L;;;;;N;;;;; 16B80;PAHAWH HMONG CLAN SIGN LAUJ;Lo;0;L;;;;;N;;;;; 16B81;PAHAWH HMONG CLAN SIGN XYOOJ;Lo;0;L;;;;;N;;;;; 16B82;PAHAWH HMONG CLAN SIGN KOO;Lo;0;L;;;;;N;;;;; 16B83;PAHAWH HMONG CLAN SIGN HAWJ;Lo;0;L;;;;;N;;;;; 16B84;PAHAWH HMONG CLAN SIGN MUAS;Lo;0;L;;;;;N;;;;; 16B85;PAHAWH HMONG CLAN SIGN THOJ;Lo;0;L;;;;;N;;;;; 16B86;PAHAWH HMONG CLAN SIGN TSAB;Lo;0;L;;;;;N;;;;; 16B87;PAHAWH HMONG CLAN SIGN PHAB;Lo;0;L;;;;;N;;;;; 16B88;PAHAWH HMONG CLAN SIGN KHAB;Lo;0;L;;;;;N;;;;; 16B89;PAHAWH HMONG CLAN SIGN HAM;Lo;0;L;;;;;N;;;;; 16B8A;PAHAWH HMONG CLAN SIGN VAJ;Lo;0;L;;;;;N;;;;; 16B8B;PAHAWH HMONG CLAN SIGN FAJ;Lo;0;L;;;;;N;;;;; 16B8C;PAHAWH HMONG CLAN SIGN YAJ;Lo;0;L;;;;;N;;;;; 16B8D;PAHAWH HMONG CLAN SIGN TSWB;Lo;0;L;;;;;N;;;;; 16B8E;PAHAWH HMONG CLAN SIGN KWM;Lo;0;L;;;;;N;;;;; 16B8F;PAHAWH HMONG CLAN SIGN VWJ;Lo;0;L;;;;;N;;;;; 16F00;MIAO LETTER PA;Lo;0;L;;;;;N;;;;; 16F01;MIAO LETTER BA;Lo;0;L;;;;;N;;;;; 16F02;MIAO LETTER YI PA;Lo;0;L;;;;;N;;;;; 16F03;MIAO LETTER PLA;Lo;0;L;;;;;N;;;;; 16F04;MIAO LETTER MA;Lo;0;L;;;;;N;;;;; 16F05;MIAO LETTER MHA;Lo;0;L;;;;;N;;;;; 16F06;MIAO LETTER ARCHAIC MA;Lo;0;L;;;;;N;;;;; 16F07;MIAO LETTER FA;Lo;0;L;;;;;N;;;;; 16F08;MIAO LETTER VA;Lo;0;L;;;;;N;;;;; 16F09;MIAO LETTER VFA;Lo;0;L;;;;;N;;;;; 16F0A;MIAO LETTER TA;Lo;0;L;;;;;N;;;;; 16F0B;MIAO LETTER DA;Lo;0;L;;;;;N;;;;; 16F0C;MIAO LETTER YI TTA;Lo;0;L;;;;;N;;;;; 16F0D;MIAO LETTER YI TA;Lo;0;L;;;;;N;;;;; 16F0E;MIAO LETTER TTA;Lo;0;L;;;;;N;;;;; 16F0F;MIAO LETTER DDA;Lo;0;L;;;;;N;;;;; 16F10;MIAO LETTER NA;Lo;0;L;;;;;N;;;;; 16F11;MIAO LETTER NHA;Lo;0;L;;;;;N;;;;; 16F12;MIAO LETTER YI NNA;Lo;0;L;;;;;N;;;;; 16F13;MIAO LETTER ARCHAIC NA;Lo;0;L;;;;;N;;;;; 16F14;MIAO LETTER NNA;Lo;0;L;;;;;N;;;;; 16F15;MIAO LETTER NNHA;Lo;0;L;;;;;N;;;;; 16F16;MIAO LETTER LA;Lo;0;L;;;;;N;;;;; 16F17;MIAO LETTER LYA;Lo;0;L;;;;;N;;;;; 16F18;MIAO LETTER LHA;Lo;0;L;;;;;N;;;;; 16F19;MIAO LETTER LHYA;Lo;0;L;;;;;N;;;;; 16F1A;MIAO LETTER TLHA;Lo;0;L;;;;;N;;;;; 16F1B;MIAO LETTER DLHA;Lo;0;L;;;;;N;;;;; 16F1C;MIAO LETTER TLHYA;Lo;0;L;;;;;N;;;;; 16F1D;MIAO LETTER DLHYA;Lo;0;L;;;;;N;;;;; 16F1E;MIAO LETTER KA;Lo;0;L;;;;;N;;;;; 16F1F;MIAO LETTER GA;Lo;0;L;;;;;N;;;;; 16F20;MIAO LETTER YI KA;Lo;0;L;;;;;N;;;;; 16F21;MIAO LETTER QA;Lo;0;L;;;;;N;;;;; 16F22;MIAO LETTER QGA;Lo;0;L;;;;;N;;;;; 16F23;MIAO LETTER NGA;Lo;0;L;;;;;N;;;;; 16F24;MIAO LETTER NGHA;Lo;0;L;;;;;N;;;;; 16F25;MIAO LETTER ARCHAIC NGA;Lo;0;L;;;;;N;;;;; 16F26;MIAO LETTER HA;Lo;0;L;;;;;N;;;;; 16F27;MIAO LETTER XA;Lo;0;L;;;;;N;;;;; 16F28;MIAO LETTER GHA;Lo;0;L;;;;;N;;;;; 16F29;MIAO LETTER GHHA;Lo;0;L;;;;;N;;;;; 16F2A;MIAO LETTER TSSA;Lo;0;L;;;;;N;;;;; 16F2B;MIAO LETTER DZZA;Lo;0;L;;;;;N;;;;; 16F2C;MIAO LETTER NYA;Lo;0;L;;;;;N;;;;; 16F2D;MIAO LETTER NYHA;Lo;0;L;;;;;N;;;;; 16F2E;MIAO LETTER TSHA;Lo;0;L;;;;;N;;;;; 16F2F;MIAO LETTER DZHA;Lo;0;L;;;;;N;;;;; 16F30;MIAO LETTER YI TSHA;Lo;0;L;;;;;N;;;;; 16F31;MIAO LETTER YI DZHA;Lo;0;L;;;;;N;;;;; 16F32;MIAO LETTER REFORMED TSHA;Lo;0;L;;;;;N;;;;; 16F33;MIAO LETTER SHA;Lo;0;L;;;;;N;;;;; 16F34;MIAO LETTER SSA;Lo;0;L;;;;;N;;;;; 16F35;MIAO LETTER ZHA;Lo;0;L;;;;;N;;;;; 16F36;MIAO LETTER ZSHA;Lo;0;L;;;;;N;;;;; 16F37;MIAO LETTER TSA;Lo;0;L;;;;;N;;;;; 16F38;MIAO LETTER DZA;Lo;0;L;;;;;N;;;;; 16F39;MIAO LETTER YI TSA;Lo;0;L;;;;;N;;;;; 16F3A;MIAO LETTER SA;Lo;0;L;;;;;N;;;;; 16F3B;MIAO LETTER ZA;Lo;0;L;;;;;N;;;;; 16F3C;MIAO LETTER ZSA;Lo;0;L;;;;;N;;;;; 16F3D;MIAO LETTER ZZA;Lo;0;L;;;;;N;;;;; 16F3E;MIAO LETTER ZZSA;Lo;0;L;;;;;N;;;;; 16F3F;MIAO LETTER ARCHAIC ZZA;Lo;0;L;;;;;N;;;;; 16F40;MIAO LETTER ZZYA;Lo;0;L;;;;;N;;;;; 16F41;MIAO LETTER ZZSYA;Lo;0;L;;;;;N;;;;; 16F42;MIAO LETTER WA;Lo;0;L;;;;;N;;;;; 16F43;MIAO LETTER AH;Lo;0;L;;;;;N;;;;; 16F44;MIAO LETTER HHA;Lo;0;L;;;;;N;;;;; 16F50;MIAO LETTER NASALIZATION;Lo;0;L;;;;;N;;;;; 16F51;MIAO SIGN ASPIRATION;Mc;0;L;;;;;N;;;;; 16F52;MIAO SIGN REFORMED VOICING;Mc;0;L;;;;;N;;;;; 16F53;MIAO SIGN REFORMED ASPIRATION;Mc;0;L;;;;;N;;;;; 16F54;MIAO VOWEL SIGN A;Mc;0;L;;;;;N;;;;; 16F55;MIAO VOWEL SIGN AA;Mc;0;L;;;;;N;;;;; 16F56;MIAO VOWEL SIGN AHH;Mc;0;L;;;;;N;;;;; 16F57;MIAO VOWEL SIGN AN;Mc;0;L;;;;;N;;;;; 16F58;MIAO VOWEL SIGN ANG;Mc;0;L;;;;;N;;;;; 16F59;MIAO VOWEL SIGN O;Mc;0;L;;;;;N;;;;; 16F5A;MIAO VOWEL SIGN OO;Mc;0;L;;;;;N;;;;; 16F5B;MIAO VOWEL SIGN WO;Mc;0;L;;;;;N;;;;; 16F5C;MIAO VOWEL SIGN W;Mc;0;L;;;;;N;;;;; 16F5D;MIAO VOWEL SIGN E;Mc;0;L;;;;;N;;;;; 16F5E;MIAO VOWEL SIGN EN;Mc;0;L;;;;;N;;;;; 16F5F;MIAO VOWEL SIGN ENG;Mc;0;L;;;;;N;;;;; 16F60;MIAO VOWEL SIGN OEY;Mc;0;L;;;;;N;;;;; 16F61;MIAO VOWEL SIGN I;Mc;0;L;;;;;N;;;;; 16F62;MIAO VOWEL SIGN IA;Mc;0;L;;;;;N;;;;; 16F63;MIAO VOWEL SIGN IAN;Mc;0;L;;;;;N;;;;; 16F64;MIAO VOWEL SIGN IANG;Mc;0;L;;;;;N;;;;; 16F65;MIAO VOWEL SIGN IO;Mc;0;L;;;;;N;;;;; 16F66;MIAO VOWEL SIGN IE;Mc;0;L;;;;;N;;;;; 16F67;MIAO VOWEL SIGN II;Mc;0;L;;;;;N;;;;; 16F68;MIAO VOWEL SIGN IU;Mc;0;L;;;;;N;;;;; 16F69;MIAO VOWEL SIGN ING;Mc;0;L;;;;;N;;;;; 16F6A;MIAO VOWEL SIGN U;Mc;0;L;;;;;N;;;;; 16F6B;MIAO VOWEL SIGN UA;Mc;0;L;;;;;N;;;;; 16F6C;MIAO VOWEL SIGN UAN;Mc;0;L;;;;;N;;;;; 16F6D;MIAO VOWEL SIGN UANG;Mc;0;L;;;;;N;;;;; 16F6E;MIAO VOWEL SIGN UU;Mc;0;L;;;;;N;;;;; 16F6F;MIAO VOWEL SIGN UEI;Mc;0;L;;;;;N;;;;; 16F70;MIAO VOWEL SIGN UNG;Mc;0;L;;;;;N;;;;; 16F71;MIAO VOWEL SIGN Y;Mc;0;L;;;;;N;;;;; 16F72;MIAO VOWEL SIGN YI;Mc;0;L;;;;;N;;;;; 16F73;MIAO VOWEL SIGN AE;Mc;0;L;;;;;N;;;;; 16F74;MIAO VOWEL SIGN AEE;Mc;0;L;;;;;N;;;;; 16F75;MIAO VOWEL SIGN ERR;Mc;0;L;;;;;N;;;;; 16F76;MIAO VOWEL SIGN ROUNDED ERR;Mc;0;L;;;;;N;;;;; 16F77;MIAO VOWEL SIGN ER;Mc;0;L;;;;;N;;;;; 16F78;MIAO VOWEL SIGN ROUNDED ER;Mc;0;L;;;;;N;;;;; 16F79;MIAO VOWEL SIGN AI;Mc;0;L;;;;;N;;;;; 16F7A;MIAO VOWEL SIGN EI;Mc;0;L;;;;;N;;;;; 16F7B;MIAO VOWEL SIGN AU;Mc;0;L;;;;;N;;;;; 16F7C;MIAO VOWEL SIGN OU;Mc;0;L;;;;;N;;;;; 16F7D;MIAO VOWEL SIGN N;Mc;0;L;;;;;N;;;;; 16F7E;MIAO VOWEL SIGN NG;Mc;0;L;;;;;N;;;;; 16F8F;MIAO TONE RIGHT;Mn;0;NSM;;;;;N;;;;; 16F90;MIAO TONE TOP RIGHT;Mn;0;NSM;;;;;N;;;;; 16F91;MIAO TONE ABOVE;Mn;0;NSM;;;;;N;;;;; 16F92;MIAO TONE BELOW;Mn;0;NSM;;;;;N;;;;; 16F93;MIAO LETTER TONE-2;Lm;0;L;;;;;N;;;;; 16F94;MIAO LETTER TONE-3;Lm;0;L;;;;;N;;;;; 16F95;MIAO LETTER TONE-4;Lm;0;L;;;;;N;;;;; 16F96;MIAO LETTER TONE-5;Lm;0;L;;;;;N;;;;; 16F97;MIAO LETTER TONE-6;Lm;0;L;;;;;N;;;;; 16F98;MIAO LETTER TONE-7;Lm;0;L;;;;;N;;;;; 16F99;MIAO LETTER TONE-8;Lm;0;L;;;;;N;;;;; 16F9A;MIAO LETTER REFORMED TONE-1;Lm;0;L;;;;;N;;;;; 16F9B;MIAO LETTER REFORMED TONE-2;Lm;0;L;;;;;N;;;;; 16F9C;MIAO LETTER REFORMED TONE-4;Lm;0;L;;;;;N;;;;; 16F9D;MIAO LETTER REFORMED TONE-5;Lm;0;L;;;;;N;;;;; 16F9E;MIAO LETTER REFORMED TONE-6;Lm;0;L;;;;;N;;;;; 16F9F;MIAO LETTER REFORMED TONE-8;Lm;0;L;;;;;N;;;;; 1B000;KATAKANA LETTER ARCHAIC E;Lo;0;L;;;;;N;;;;; 1B001;HIRAGANA LETTER ARCHAIC YE;Lo;0;L;;;;;N;;;;; 1BC00;DUPLOYAN LETTER H;Lo;0;L;;;;;N;;;;; 1BC01;DUPLOYAN LETTER X;Lo;0;L;;;;;N;;;;; 1BC02;DUPLOYAN LETTER P;Lo;0;L;;;;;N;;;;; 1BC03;DUPLOYAN LETTER T;Lo;0;L;;;;;N;;;;; 1BC04;DUPLOYAN LETTER F;Lo;0;L;;;;;N;;;;; 1BC05;DUPLOYAN LETTER K;Lo;0;L;;;;;N;;;;; 1BC06;DUPLOYAN LETTER L;Lo;0;L;;;;;N;;;;; 1BC07;DUPLOYAN LETTER B;Lo;0;L;;;;;N;;;;; 1BC08;DUPLOYAN LETTER D;Lo;0;L;;;;;N;;;;; 1BC09;DUPLOYAN LETTER V;Lo;0;L;;;;;N;;;;; 1BC0A;DUPLOYAN LETTER G;Lo;0;L;;;;;N;;;;; 1BC0B;DUPLOYAN LETTER R;Lo;0;L;;;;;N;;;;; 1BC0C;DUPLOYAN LETTER P N;Lo;0;L;;;;;N;;;;; 1BC0D;DUPLOYAN LETTER D S;Lo;0;L;;;;;N;;;;; 1BC0E;DUPLOYAN LETTER F N;Lo;0;L;;;;;N;;;;; 1BC0F;DUPLOYAN LETTER K M;Lo;0;L;;;;;N;;;;; 1BC10;DUPLOYAN LETTER R S;Lo;0;L;;;;;N;;;;; 1BC11;DUPLOYAN LETTER TH;Lo;0;L;;;;;N;;;;; 1BC12;DUPLOYAN LETTER SLOAN DH;Lo;0;L;;;;;N;;;;; 1BC13;DUPLOYAN LETTER DH;Lo;0;L;;;;;N;;;;; 1BC14;DUPLOYAN LETTER KK;Lo;0;L;;;;;N;;;;; 1BC15;DUPLOYAN LETTER SLOAN J;Lo;0;L;;;;;N;;;;; 1BC16;DUPLOYAN LETTER HL;Lo;0;L;;;;;N;;;;; 1BC17;DUPLOYAN LETTER LH;Lo;0;L;;;;;N;;;;; 1BC18;DUPLOYAN LETTER RH;Lo;0;L;;;;;N;;;;; 1BC19;DUPLOYAN LETTER M;Lo;0;L;;;;;N;;;;; 1BC1A;DUPLOYAN LETTER N;Lo;0;L;;;;;N;;;;; 1BC1B;DUPLOYAN LETTER J;Lo;0;L;;;;;N;;;;; 1BC1C;DUPLOYAN LETTER S;Lo;0;L;;;;;N;;;;; 1BC1D;DUPLOYAN LETTER M N;Lo;0;L;;;;;N;;;;; 1BC1E;DUPLOYAN LETTER N M;Lo;0;L;;;;;N;;;;; 1BC1F;DUPLOYAN LETTER J M;Lo;0;L;;;;;N;;;;; 1BC20;DUPLOYAN LETTER S J;Lo;0;L;;;;;N;;;;; 1BC21;DUPLOYAN LETTER M WITH DOT;Lo;0;L;;;;;N;;;;; 1BC22;DUPLOYAN LETTER N WITH DOT;Lo;0;L;;;;;N;;;;; 1BC23;DUPLOYAN LETTER J WITH DOT;Lo;0;L;;;;;N;;;;; 1BC24;DUPLOYAN LETTER J WITH DOTS INSIDE AND ABOVE;Lo;0;L;;;;;N;;;;; 1BC25;DUPLOYAN LETTER S WITH DOT;Lo;0;L;;;;;N;;;;; 1BC26;DUPLOYAN LETTER S WITH DOT BELOW;Lo;0;L;;;;;N;;;;; 1BC27;DUPLOYAN LETTER M S;Lo;0;L;;;;;N;;;;; 1BC28;DUPLOYAN LETTER N S;Lo;0;L;;;;;N;;;;; 1BC29;DUPLOYAN LETTER J S;Lo;0;L;;;;;N;;;;; 1BC2A;DUPLOYAN LETTER S S;Lo;0;L;;;;;N;;;;; 1BC2B;DUPLOYAN LETTER M N S;Lo;0;L;;;;;N;;;;; 1BC2C;DUPLOYAN LETTER N M S;Lo;0;L;;;;;N;;;;; 1BC2D;DUPLOYAN LETTER J M S;Lo;0;L;;;;;N;;;;; 1BC2E;DUPLOYAN LETTER S J S;Lo;0;L;;;;;N;;;;; 1BC2F;DUPLOYAN LETTER J S WITH DOT;Lo;0;L;;;;;N;;;;; 1BC30;DUPLOYAN LETTER J N;Lo;0;L;;;;;N;;;;; 1BC31;DUPLOYAN LETTER J N S;Lo;0;L;;;;;N;;;;; 1BC32;DUPLOYAN LETTER S T;Lo;0;L;;;;;N;;;;; 1BC33;DUPLOYAN LETTER S T R;Lo;0;L;;;;;N;;;;; 1BC34;DUPLOYAN LETTER S P;Lo;0;L;;;;;N;;;;; 1BC35;DUPLOYAN LETTER S P R;Lo;0;L;;;;;N;;;;; 1BC36;DUPLOYAN LETTER T S;Lo;0;L;;;;;N;;;;; 1BC37;DUPLOYAN LETTER T R S;Lo;0;L;;;;;N;;;;; 1BC38;DUPLOYAN LETTER W;Lo;0;L;;;;;N;;;;; 1BC39;DUPLOYAN LETTER WH;Lo;0;L;;;;;N;;;;; 1BC3A;DUPLOYAN LETTER W R;Lo;0;L;;;;;N;;;;; 1BC3B;DUPLOYAN LETTER S N;Lo;0;L;;;;;N;;;;; 1BC3C;DUPLOYAN LETTER S M;Lo;0;L;;;;;N;;;;; 1BC3D;DUPLOYAN LETTER K R S;Lo;0;L;;;;;N;;;;; 1BC3E;DUPLOYAN LETTER G R S;Lo;0;L;;;;;N;;;;; 1BC3F;DUPLOYAN LETTER S K;Lo;0;L;;;;;N;;;;; 1BC40;DUPLOYAN LETTER S K R;Lo;0;L;;;;;N;;;;; 1BC41;DUPLOYAN LETTER A;Lo;0;L;;;;;N;;;;; 1BC42;DUPLOYAN LETTER SLOAN OW;Lo;0;L;;;;;N;;;;; 1BC43;DUPLOYAN LETTER OA;Lo;0;L;;;;;N;;;;; 1BC44;DUPLOYAN LETTER O;Lo;0;L;;;;;N;;;;; 1BC45;DUPLOYAN LETTER AOU;Lo;0;L;;;;;N;;;;; 1BC46;DUPLOYAN LETTER I;Lo;0;L;;;;;N;;;;; 1BC47;DUPLOYAN LETTER E;Lo;0;L;;;;;N;;;;; 1BC48;DUPLOYAN LETTER IE;Lo;0;L;;;;;N;;;;; 1BC49;DUPLOYAN LETTER SHORT I;Lo;0;L;;;;;N;;;;; 1BC4A;DUPLOYAN LETTER UI;Lo;0;L;;;;;N;;;;; 1BC4B;DUPLOYAN LETTER EE;Lo;0;L;;;;;N;;;;; 1BC4C;DUPLOYAN LETTER SLOAN EH;Lo;0;L;;;;;N;;;;; 1BC4D;DUPLOYAN LETTER ROMANIAN I;Lo;0;L;;;;;N;;;;; 1BC4E;DUPLOYAN LETTER SLOAN EE;Lo;0;L;;;;;N;;;;; 1BC4F;DUPLOYAN LETTER LONG I;Lo;0;L;;;;;N;;;;; 1BC50;DUPLOYAN LETTER YE;Lo;0;L;;;;;N;;;;; 1BC51;DUPLOYAN LETTER U;Lo;0;L;;;;;N;;;;; 1BC52;DUPLOYAN LETTER EU;Lo;0;L;;;;;N;;;;; 1BC53;DUPLOYAN LETTER XW;Lo;0;L;;;;;N;;;;; 1BC54;DUPLOYAN LETTER U N;Lo;0;L;;;;;N;;;;; 1BC55;DUPLOYAN LETTER LONG U;Lo;0;L;;;;;N;;;;; 1BC56;DUPLOYAN LETTER ROMANIAN U;Lo;0;L;;;;;N;;;;; 1BC57;DUPLOYAN LETTER UH;Lo;0;L;;;;;N;;;;; 1BC58;DUPLOYAN LETTER SLOAN U;Lo;0;L;;;;;N;;;;; 1BC59;DUPLOYAN LETTER OOH;Lo;0;L;;;;;N;;;;; 1BC5A;DUPLOYAN LETTER OW;Lo;0;L;;;;;N;;;;; 1BC5B;DUPLOYAN LETTER OU;Lo;0;L;;;;;N;;;;; 1BC5C;DUPLOYAN LETTER WA;Lo;0;L;;;;;N;;;;; 1BC5D;DUPLOYAN LETTER WO;Lo;0;L;;;;;N;;;;; 1BC5E;DUPLOYAN LETTER WI;Lo;0;L;;;;;N;;;;; 1BC5F;DUPLOYAN LETTER WEI;Lo;0;L;;;;;N;;;;; 1BC60;DUPLOYAN LETTER WOW;Lo;0;L;;;;;N;;;;; 1BC61;DUPLOYAN LETTER NASAL U;Lo;0;L;;;;;N;;;;; 1BC62;DUPLOYAN LETTER NASAL O;Lo;0;L;;;;;N;;;;; 1BC63;DUPLOYAN LETTER NASAL I;Lo;0;L;;;;;N;;;;; 1BC64;DUPLOYAN LETTER NASAL A;Lo;0;L;;;;;N;;;;; 1BC65;DUPLOYAN LETTER PERNIN AN;Lo;0;L;;;;;N;;;;; 1BC66;DUPLOYAN LETTER PERNIN AM;Lo;0;L;;;;;N;;;;; 1BC67;DUPLOYAN LETTER SLOAN EN;Lo;0;L;;;;;N;;;;; 1BC68;DUPLOYAN LETTER SLOAN AN;Lo;0;L;;;;;N;;;;; 1BC69;DUPLOYAN LETTER SLOAN ON;Lo;0;L;;;;;N;;;;; 1BC6A;DUPLOYAN LETTER VOCALIC M;Lo;0;L;;;;;N;;;;; 1BC70;DUPLOYAN AFFIX LEFT HORIZONTAL SECANT;Lo;0;L;;;;;N;;;;; 1BC71;DUPLOYAN AFFIX MID HORIZONTAL SECANT;Lo;0;L;;;;;N;;;;; 1BC72;DUPLOYAN AFFIX RIGHT HORIZONTAL SECANT;Lo;0;L;;;;;N;;;;; 1BC73;DUPLOYAN AFFIX LOW VERTICAL SECANT;Lo;0;L;;;;;N;;;;; 1BC74;DUPLOYAN AFFIX MID VERTICAL SECANT;Lo;0;L;;;;;N;;;;; 1BC75;DUPLOYAN AFFIX HIGH VERTICAL SECANT;Lo;0;L;;;;;N;;;;; 1BC76;DUPLOYAN AFFIX ATTACHED SECANT;Lo;0;L;;;;;N;;;;; 1BC77;DUPLOYAN AFFIX ATTACHED LEFT-TO-RIGHT SECANT;Lo;0;L;;;;;N;;;;; 1BC78;DUPLOYAN AFFIX ATTACHED TANGENT;Lo;0;L;;;;;N;;;;; 1BC79;DUPLOYAN AFFIX ATTACHED TAIL;Lo;0;L;;;;;N;;;;; 1BC7A;DUPLOYAN AFFIX ATTACHED E HOOK;Lo;0;L;;;;;N;;;;; 1BC7B;DUPLOYAN AFFIX ATTACHED I HOOK;Lo;0;L;;;;;N;;;;; 1BC7C;DUPLOYAN AFFIX ATTACHED TANGENT HOOK;Lo;0;L;;;;;N;;;;; 1BC80;DUPLOYAN AFFIX HIGH ACUTE;Lo;0;L;;;;;N;;;;; 1BC81;DUPLOYAN AFFIX HIGH TIGHT ACUTE;Lo;0;L;;;;;N;;;;; 1BC82;DUPLOYAN AFFIX HIGH GRAVE;Lo;0;L;;;;;N;;;;; 1BC83;DUPLOYAN AFFIX HIGH LONG GRAVE;Lo;0;L;;;;;N;;;;; 1BC84;DUPLOYAN AFFIX HIGH DOT;Lo;0;L;;;;;N;;;;; 1BC85;DUPLOYAN AFFIX HIGH CIRCLE;Lo;0;L;;;;;N;;;;; 1BC86;DUPLOYAN AFFIX HIGH LINE;Lo;0;L;;;;;N;;;;; 1BC87;DUPLOYAN AFFIX HIGH WAVE;Lo;0;L;;;;;N;;;;; 1BC88;DUPLOYAN AFFIX HIGH VERTICAL;Lo;0;L;;;;;N;;;;; 1BC90;DUPLOYAN AFFIX LOW ACUTE;Lo;0;L;;;;;N;;;;; 1BC91;DUPLOYAN AFFIX LOW TIGHT ACUTE;Lo;0;L;;;;;N;;;;; 1BC92;DUPLOYAN AFFIX LOW GRAVE;Lo;0;L;;;;;N;;;;; 1BC93;DUPLOYAN AFFIX LOW LONG GRAVE;Lo;0;L;;;;;N;;;;; 1BC94;DUPLOYAN AFFIX LOW DOT;Lo;0;L;;;;;N;;;;; 1BC95;DUPLOYAN AFFIX LOW CIRCLE;Lo;0;L;;;;;N;;;;; 1BC96;DUPLOYAN AFFIX LOW LINE;Lo;0;L;;;;;N;;;;; 1BC97;DUPLOYAN AFFIX LOW WAVE;Lo;0;L;;;;;N;;;;; 1BC98;DUPLOYAN AFFIX LOW VERTICAL;Lo;0;L;;;;;N;;;;; 1BC99;DUPLOYAN AFFIX LOW ARROW;Lo;0;L;;;;;N;;;;; 1BC9C;DUPLOYAN SIGN O WITH CROSS;So;0;L;;;;;N;;;;; 1BC9D;DUPLOYAN THICK LETTER SELECTOR;Mn;0;NSM;;;;;N;;;;; 1BC9E;DUPLOYAN DOUBLE MARK;Mn;1;NSM;;;;;N;;;;; 1BC9F;DUPLOYAN PUNCTUATION CHINOOK FULL STOP;Po;0;L;;;;;N;;;;; 1BCA0;SHORTHAND FORMAT LETTER OVERLAP;Cf;0;BN;;;;;N;;;;; 1BCA1;SHORTHAND FORMAT CONTINUING OVERLAP;Cf;0;BN;;;;;N;;;;; 1BCA2;SHORTHAND FORMAT DOWN STEP;Cf;0;BN;;;;;N;;;;; 1BCA3;SHORTHAND FORMAT UP STEP;Cf;0;BN;;;;;N;;;;; 1D000;BYZANTINE MUSICAL SYMBOL PSILI;So;0;L;;;;;N;;;;; 1D001;BYZANTINE MUSICAL SYMBOL DASEIA;So;0;L;;;;;N;;;;; 1D002;BYZANTINE MUSICAL SYMBOL PERISPOMENI;So;0;L;;;;;N;;;;; 1D003;BYZANTINE MUSICAL SYMBOL OXEIA EKFONITIKON;So;0;L;;;;;N;;;;; 1D004;BYZANTINE MUSICAL SYMBOL OXEIA DIPLI;So;0;L;;;;;N;;;;; 1D005;BYZANTINE MUSICAL SYMBOL VAREIA EKFONITIKON;So;0;L;;;;;N;;;;; 1D006;BYZANTINE MUSICAL SYMBOL VAREIA DIPLI;So;0;L;;;;;N;;;;; 1D007;BYZANTINE MUSICAL SYMBOL KATHISTI;So;0;L;;;;;N;;;;; 1D008;BYZANTINE MUSICAL SYMBOL SYRMATIKI;So;0;L;;;;;N;;;;; 1D009;BYZANTINE MUSICAL SYMBOL PARAKLITIKI;So;0;L;;;;;N;;;;; 1D00A;BYZANTINE MUSICAL SYMBOL YPOKRISIS;So;0;L;;;;;N;;;;; 1D00B;BYZANTINE MUSICAL SYMBOL YPOKRISIS DIPLI;So;0;L;;;;;N;;;;; 1D00C;BYZANTINE MUSICAL SYMBOL KREMASTI;So;0;L;;;;;N;;;;; 1D00D;BYZANTINE MUSICAL SYMBOL APESO EKFONITIKON;So;0;L;;;;;N;;;;; 1D00E;BYZANTINE MUSICAL SYMBOL EXO EKFONITIKON;So;0;L;;;;;N;;;;; 1D00F;BYZANTINE MUSICAL SYMBOL TELEIA;So;0;L;;;;;N;;;;; 1D010;BYZANTINE MUSICAL SYMBOL KENTIMATA;So;0;L;;;;;N;;;;; 1D011;BYZANTINE MUSICAL SYMBOL APOSTROFOS;So;0;L;;;;;N;;;;; 1D012;BYZANTINE MUSICAL SYMBOL APOSTROFOS DIPLI;So;0;L;;;;;N;;;;; 1D013;BYZANTINE MUSICAL SYMBOL SYNEVMA;So;0;L;;;;;N;;;;; 1D014;BYZANTINE MUSICAL SYMBOL THITA;So;0;L;;;;;N;;;;; 1D015;BYZANTINE MUSICAL SYMBOL OLIGON ARCHAION;So;0;L;;;;;N;;;;; 1D016;BYZANTINE MUSICAL SYMBOL GORGON ARCHAION;So;0;L;;;;;N;;;;; 1D017;BYZANTINE MUSICAL SYMBOL PSILON;So;0;L;;;;;N;;;;; 1D018;BYZANTINE MUSICAL SYMBOL CHAMILON;So;0;L;;;;;N;;;;; 1D019;BYZANTINE MUSICAL SYMBOL VATHY;So;0;L;;;;;N;;;;; 1D01A;BYZANTINE MUSICAL SYMBOL ISON ARCHAION;So;0;L;;;;;N;;;;; 1D01B;BYZANTINE MUSICAL SYMBOL KENTIMA ARCHAION;So;0;L;;;;;N;;;;; 1D01C;BYZANTINE MUSICAL SYMBOL KENTIMATA ARCHAION;So;0;L;;;;;N;;;;; 1D01D;BYZANTINE MUSICAL SYMBOL SAXIMATA;So;0;L;;;;;N;;;;; 1D01E;BYZANTINE MUSICAL SYMBOL PARICHON;So;0;L;;;;;N;;;;; 1D01F;BYZANTINE MUSICAL SYMBOL STAVROS APODEXIA;So;0;L;;;;;N;;;;; 1D020;BYZANTINE MUSICAL SYMBOL OXEIAI ARCHAION;So;0;L;;;;;N;;;;; 1D021;BYZANTINE MUSICAL SYMBOL VAREIAI ARCHAION;So;0;L;;;;;N;;;;; 1D022;BYZANTINE MUSICAL SYMBOL APODERMA ARCHAION;So;0;L;;;;;N;;;;; 1D023;BYZANTINE MUSICAL SYMBOL APOTHEMA;So;0;L;;;;;N;;;;; 1D024;BYZANTINE MUSICAL SYMBOL KLASMA;So;0;L;;;;;N;;;;; 1D025;BYZANTINE MUSICAL SYMBOL REVMA;So;0;L;;;;;N;;;;; 1D026;BYZANTINE MUSICAL SYMBOL PIASMA ARCHAION;So;0;L;;;;;N;;;;; 1D027;BYZANTINE MUSICAL SYMBOL TINAGMA;So;0;L;;;;;N;;;;; 1D028;BYZANTINE MUSICAL SYMBOL ANATRICHISMA;So;0;L;;;;;N;;;;; 1D029;BYZANTINE MUSICAL SYMBOL SEISMA;So;0;L;;;;;N;;;;; 1D02A;BYZANTINE MUSICAL SYMBOL SYNAGMA ARCHAION;So;0;L;;;;;N;;;;; 1D02B;BYZANTINE MUSICAL SYMBOL SYNAGMA META STAVROU;So;0;L;;;;;N;;;;; 1D02C;BYZANTINE MUSICAL SYMBOL OYRANISMA ARCHAION;So;0;L;;;;;N;;;;; 1D02D;BYZANTINE MUSICAL SYMBOL THEMA;So;0;L;;;;;N;;;;; 1D02E;BYZANTINE MUSICAL SYMBOL LEMOI;So;0;L;;;;;N;;;;; 1D02F;BYZANTINE MUSICAL SYMBOL DYO;So;0;L;;;;;N;;;;; 1D030;BYZANTINE MUSICAL SYMBOL TRIA;So;0;L;;;;;N;;;;; 1D031;BYZANTINE MUSICAL SYMBOL TESSERA;So;0;L;;;;;N;;;;; 1D032;BYZANTINE MUSICAL SYMBOL KRATIMATA;So;0;L;;;;;N;;;;; 1D033;BYZANTINE MUSICAL SYMBOL APESO EXO NEO;So;0;L;;;;;N;;;;; 1D034;BYZANTINE MUSICAL SYMBOL FTHORA ARCHAION;So;0;L;;;;;N;;;;; 1D035;BYZANTINE MUSICAL SYMBOL IMIFTHORA;So;0;L;;;;;N;;;;; 1D036;BYZANTINE MUSICAL SYMBOL TROMIKON ARCHAION;So;0;L;;;;;N;;;;; 1D037;BYZANTINE MUSICAL SYMBOL KATAVA TROMIKON;So;0;L;;;;;N;;;;; 1D038;BYZANTINE MUSICAL SYMBOL PELASTON;So;0;L;;;;;N;;;;; 1D039;BYZANTINE MUSICAL SYMBOL PSIFISTON;So;0;L;;;;;N;;;;; 1D03A;BYZANTINE MUSICAL SYMBOL KONTEVMA;So;0;L;;;;;N;;;;; 1D03B;BYZANTINE MUSICAL SYMBOL CHOREVMA ARCHAION;So;0;L;;;;;N;;;;; 1D03C;BYZANTINE MUSICAL SYMBOL RAPISMA;So;0;L;;;;;N;;;;; 1D03D;BYZANTINE MUSICAL SYMBOL PARAKALESMA ARCHAION;So;0;L;;;;;N;;;;; 1D03E;BYZANTINE MUSICAL SYMBOL PARAKLITIKI ARCHAION;So;0;L;;;;;N;;;;; 1D03F;BYZANTINE MUSICAL SYMBOL ICHADIN;So;0;L;;;;;N;;;;; 1D040;BYZANTINE MUSICAL SYMBOL NANA;So;0;L;;;;;N;;;;; 1D041;BYZANTINE MUSICAL SYMBOL PETASMA;So;0;L;;;;;N;;;;; 1D042;BYZANTINE MUSICAL SYMBOL KONTEVMA ALLO;So;0;L;;;;;N;;;;; 1D043;BYZANTINE MUSICAL SYMBOL TROMIKON ALLO;So;0;L;;;;;N;;;;; 1D044;BYZANTINE MUSICAL SYMBOL STRAGGISMATA;So;0;L;;;;;N;;;;; 1D045;BYZANTINE MUSICAL SYMBOL GRONTHISMATA;So;0;L;;;;;N;;;;; 1D046;BYZANTINE MUSICAL SYMBOL ISON NEO;So;0;L;;;;;N;;;;; 1D047;BYZANTINE MUSICAL SYMBOL OLIGON NEO;So;0;L;;;;;N;;;;; 1D048;BYZANTINE MUSICAL SYMBOL OXEIA NEO;So;0;L;;;;;N;;;;; 1D049;BYZANTINE MUSICAL SYMBOL PETASTI;So;0;L;;;;;N;;;;; 1D04A;BYZANTINE MUSICAL SYMBOL KOUFISMA;So;0;L;;;;;N;;;;; 1D04B;BYZANTINE MUSICAL SYMBOL PETASTOKOUFISMA;So;0;L;;;;;N;;;;; 1D04C;BYZANTINE MUSICAL SYMBOL KRATIMOKOUFISMA;So;0;L;;;;;N;;;;; 1D04D;BYZANTINE MUSICAL SYMBOL PELASTON NEO;So;0;L;;;;;N;;;;; 1D04E;BYZANTINE MUSICAL SYMBOL KENTIMATA NEO ANO;So;0;L;;;;;N;;;;; 1D04F;BYZANTINE MUSICAL SYMBOL KENTIMA NEO ANO;So;0;L;;;;;N;;;;; 1D050;BYZANTINE MUSICAL SYMBOL YPSILI;So;0;L;;;;;N;;;;; 1D051;BYZANTINE MUSICAL SYMBOL APOSTROFOS NEO;So;0;L;;;;;N;;;;; 1D052;BYZANTINE MUSICAL SYMBOL APOSTROFOI SYNDESMOS NEO;So;0;L;;;;;N;;;;; 1D053;BYZANTINE MUSICAL SYMBOL YPORROI;So;0;L;;;;;N;;;;; 1D054;BYZANTINE MUSICAL SYMBOL KRATIMOYPORROON;So;0;L;;;;;N;;;;; 1D055;BYZANTINE MUSICAL SYMBOL ELAFRON;So;0;L;;;;;N;;;;; 1D056;BYZANTINE MUSICAL SYMBOL CHAMILI;So;0;L;;;;;N;;;;; 1D057;BYZANTINE MUSICAL SYMBOL MIKRON ISON;So;0;L;;;;;N;;;;; 1D058;BYZANTINE MUSICAL SYMBOL VAREIA NEO;So;0;L;;;;;N;;;;; 1D059;BYZANTINE MUSICAL SYMBOL PIASMA NEO;So;0;L;;;;;N;;;;; 1D05A;BYZANTINE MUSICAL SYMBOL PSIFISTON NEO;So;0;L;;;;;N;;;;; 1D05B;BYZANTINE MUSICAL SYMBOL OMALON;So;0;L;;;;;N;;;;; 1D05C;BYZANTINE MUSICAL SYMBOL ANTIKENOMA;So;0;L;;;;;N;;;;; 1D05D;BYZANTINE MUSICAL SYMBOL LYGISMA;So;0;L;;;;;N;;;;; 1D05E;BYZANTINE MUSICAL SYMBOL PARAKLITIKI NEO;So;0;L;;;;;N;;;;; 1D05F;BYZANTINE MUSICAL SYMBOL PARAKALESMA NEO;So;0;L;;;;;N;;;;; 1D060;BYZANTINE MUSICAL SYMBOL ETERON PARAKALESMA;So;0;L;;;;;N;;;;; 1D061;BYZANTINE MUSICAL SYMBOL KYLISMA;So;0;L;;;;;N;;;;; 1D062;BYZANTINE MUSICAL SYMBOL ANTIKENOKYLISMA;So;0;L;;;;;N;;;;; 1D063;BYZANTINE MUSICAL SYMBOL TROMIKON NEO;So;0;L;;;;;N;;;;; 1D064;BYZANTINE MUSICAL SYMBOL EKSTREPTON;So;0;L;;;;;N;;;;; 1D065;BYZANTINE MUSICAL SYMBOL SYNAGMA NEO;So;0;L;;;;;N;;;;; 1D066;BYZANTINE MUSICAL SYMBOL SYRMA;So;0;L;;;;;N;;;;; 1D067;BYZANTINE MUSICAL SYMBOL CHOREVMA NEO;So;0;L;;;;;N;;;;; 1D068;BYZANTINE MUSICAL SYMBOL EPEGERMA;So;0;L;;;;;N;;;;; 1D069;BYZANTINE MUSICAL SYMBOL SEISMA NEO;So;0;L;;;;;N;;;;; 1D06A;BYZANTINE MUSICAL SYMBOL XIRON KLASMA;So;0;L;;;;;N;;;;; 1D06B;BYZANTINE MUSICAL SYMBOL TROMIKOPSIFISTON;So;0;L;;;;;N;;;;; 1D06C;BYZANTINE MUSICAL SYMBOL PSIFISTOLYGISMA;So;0;L;;;;;N;;;;; 1D06D;BYZANTINE MUSICAL SYMBOL TROMIKOLYGISMA;So;0;L;;;;;N;;;;; 1D06E;BYZANTINE MUSICAL SYMBOL TROMIKOPARAKALESMA;So;0;L;;;;;N;;;;; 1D06F;BYZANTINE MUSICAL SYMBOL PSIFISTOPARAKALESMA;So;0;L;;;;;N;;;;; 1D070;BYZANTINE MUSICAL SYMBOL TROMIKOSYNAGMA;So;0;L;;;;;N;;;;; 1D071;BYZANTINE MUSICAL SYMBOL PSIFISTOSYNAGMA;So;0;L;;;;;N;;;;; 1D072;BYZANTINE MUSICAL SYMBOL GORGOSYNTHETON;So;0;L;;;;;N;;;;; 1D073;BYZANTINE MUSICAL SYMBOL ARGOSYNTHETON;So;0;L;;;;;N;;;;; 1D074;BYZANTINE MUSICAL SYMBOL ETERON ARGOSYNTHETON;So;0;L;;;;;N;;;;; 1D075;BYZANTINE MUSICAL SYMBOL OYRANISMA NEO;So;0;L;;;;;N;;;;; 1D076;BYZANTINE MUSICAL SYMBOL THEMATISMOS ESO;So;0;L;;;;;N;;;;; 1D077;BYZANTINE MUSICAL SYMBOL THEMATISMOS EXO;So;0;L;;;;;N;;;;; 1D078;BYZANTINE MUSICAL SYMBOL THEMA APLOUN;So;0;L;;;;;N;;;;; 1D079;BYZANTINE MUSICAL SYMBOL THES KAI APOTHES;So;0;L;;;;;N;;;;; 1D07A;BYZANTINE MUSICAL SYMBOL KATAVASMA;So;0;L;;;;;N;;;;; 1D07B;BYZANTINE MUSICAL SYMBOL ENDOFONON;So;0;L;;;;;N;;;;; 1D07C;BYZANTINE MUSICAL SYMBOL YFEN KATO;So;0;L;;;;;N;;;;; 1D07D;BYZANTINE MUSICAL SYMBOL YFEN ANO;So;0;L;;;;;N;;;;; 1D07E;BYZANTINE MUSICAL SYMBOL STAVROS;So;0;L;;;;;N;;;;; 1D07F;BYZANTINE MUSICAL SYMBOL KLASMA ANO;So;0;L;;;;;N;;;;; 1D080;BYZANTINE MUSICAL SYMBOL DIPLI ARCHAION;So;0;L;;;;;N;;;;; 1D081;BYZANTINE MUSICAL SYMBOL KRATIMA ARCHAION;So;0;L;;;;;N;;;;; 1D082;BYZANTINE MUSICAL SYMBOL KRATIMA ALLO;So;0;L;;;;;N;;;;; 1D083;BYZANTINE MUSICAL SYMBOL KRATIMA NEO;So;0;L;;;;;N;;;;; 1D084;BYZANTINE MUSICAL SYMBOL APODERMA NEO;So;0;L;;;;;N;;;;; 1D085;BYZANTINE MUSICAL SYMBOL APLI;So;0;L;;;;;N;;;;; 1D086;BYZANTINE MUSICAL SYMBOL DIPLI;So;0;L;;;;;N;;;;; 1D087;BYZANTINE MUSICAL SYMBOL TRIPLI;So;0;L;;;;;N;;;;; 1D088;BYZANTINE MUSICAL SYMBOL TETRAPLI;So;0;L;;;;;N;;;;; 1D089;BYZANTINE MUSICAL SYMBOL KORONIS;So;0;L;;;;;N;;;;; 1D08A;BYZANTINE MUSICAL SYMBOL LEIMMA ENOS CHRONOU;So;0;L;;;;;N;;;;; 1D08B;BYZANTINE MUSICAL SYMBOL LEIMMA DYO CHRONON;So;0;L;;;;;N;;;;; 1D08C;BYZANTINE MUSICAL SYMBOL LEIMMA TRION CHRONON;So;0;L;;;;;N;;;;; 1D08D;BYZANTINE MUSICAL SYMBOL LEIMMA TESSARON CHRONON;So;0;L;;;;;N;;;;; 1D08E;BYZANTINE MUSICAL SYMBOL LEIMMA IMISEOS CHRONOU;So;0;L;;;;;N;;;;; 1D08F;BYZANTINE MUSICAL SYMBOL GORGON NEO ANO;So;0;L;;;;;N;;;;; 1D090;BYZANTINE MUSICAL SYMBOL GORGON PARESTIGMENON ARISTERA;So;0;L;;;;;N;;;;; 1D091;BYZANTINE MUSICAL SYMBOL GORGON PARESTIGMENON DEXIA;So;0;L;;;;;N;;;;; 1D092;BYZANTINE MUSICAL SYMBOL DIGORGON;So;0;L;;;;;N;;;;; 1D093;BYZANTINE MUSICAL SYMBOL DIGORGON PARESTIGMENON ARISTERA KATO;So;0;L;;;;;N;;;;; 1D094;BYZANTINE MUSICAL SYMBOL DIGORGON PARESTIGMENON ARISTERA ANO;So;0;L;;;;;N;;;;; 1D095;BYZANTINE MUSICAL SYMBOL DIGORGON PARESTIGMENON DEXIA;So;0;L;;;;;N;;;;; 1D096;BYZANTINE MUSICAL SYMBOL TRIGORGON;So;0;L;;;;;N;;;;; 1D097;BYZANTINE MUSICAL SYMBOL ARGON;So;0;L;;;;;N;;;;; 1D098;BYZANTINE MUSICAL SYMBOL IMIDIARGON;So;0;L;;;;;N;;;;; 1D099;BYZANTINE MUSICAL SYMBOL DIARGON;So;0;L;;;;;N;;;;; 1D09A;BYZANTINE MUSICAL SYMBOL AGOGI POLI ARGI;So;0;L;;;;;N;;;;; 1D09B;BYZANTINE MUSICAL SYMBOL AGOGI ARGOTERI;So;0;L;;;;;N;;;;; 1D09C;BYZANTINE MUSICAL SYMBOL AGOGI ARGI;So;0;L;;;;;N;;;;; 1D09D;BYZANTINE MUSICAL SYMBOL AGOGI METRIA;So;0;L;;;;;N;;;;; 1D09E;BYZANTINE MUSICAL SYMBOL AGOGI MESI;So;0;L;;;;;N;;;;; 1D09F;BYZANTINE MUSICAL SYMBOL AGOGI GORGI;So;0;L;;;;;N;;;;; 1D0A0;BYZANTINE MUSICAL SYMBOL AGOGI GORGOTERI;So;0;L;;;;;N;;;;; 1D0A1;BYZANTINE MUSICAL SYMBOL AGOGI POLI GORGI;So;0;L;;;;;N;;;;; 1D0A2;BYZANTINE MUSICAL SYMBOL MARTYRIA PROTOS ICHOS;So;0;L;;;;;N;;;;; 1D0A3;BYZANTINE MUSICAL SYMBOL MARTYRIA ALLI PROTOS ICHOS;So;0;L;;;;;N;;;;; 1D0A4;BYZANTINE MUSICAL SYMBOL MARTYRIA DEYTEROS ICHOS;So;0;L;;;;;N;;;;; 1D0A5;BYZANTINE MUSICAL SYMBOL MARTYRIA ALLI DEYTEROS ICHOS;So;0;L;;;;;N;;;;; 1D0A6;BYZANTINE MUSICAL SYMBOL MARTYRIA TRITOS ICHOS;So;0;L;;;;;N;;;;; 1D0A7;BYZANTINE MUSICAL SYMBOL MARTYRIA TRIFONIAS;So;0;L;;;;;N;;;;; 1D0A8;BYZANTINE MUSICAL SYMBOL MARTYRIA TETARTOS ICHOS;So;0;L;;;;;N;;;;; 1D0A9;BYZANTINE MUSICAL SYMBOL MARTYRIA TETARTOS LEGETOS ICHOS;So;0;L;;;;;N;;;;; 1D0AA;BYZANTINE MUSICAL SYMBOL MARTYRIA LEGETOS ICHOS;So;0;L;;;;;N;;;;; 1D0AB;BYZANTINE MUSICAL SYMBOL MARTYRIA PLAGIOS ICHOS;So;0;L;;;;;N;;;;; 1D0AC;BYZANTINE MUSICAL SYMBOL ISAKIA TELOUS ICHIMATOS;So;0;L;;;;;N;;;;; 1D0AD;BYZANTINE MUSICAL SYMBOL APOSTROFOI TELOUS ICHIMATOS;So;0;L;;;;;N;;;;; 1D0AE;BYZANTINE MUSICAL SYMBOL FANEROSIS TETRAFONIAS;So;0;L;;;;;N;;;;; 1D0AF;BYZANTINE MUSICAL SYMBOL FANEROSIS MONOFONIAS;So;0;L;;;;;N;;;;; 1D0B0;BYZANTINE MUSICAL SYMBOL FANEROSIS DIFONIAS;So;0;L;;;;;N;;;;; 1D0B1;BYZANTINE MUSICAL SYMBOL MARTYRIA VARYS ICHOS;So;0;L;;;;;N;;;;; 1D0B2;BYZANTINE MUSICAL SYMBOL MARTYRIA PROTOVARYS ICHOS;So;0;L;;;;;N;;;;; 1D0B3;BYZANTINE MUSICAL SYMBOL MARTYRIA PLAGIOS TETARTOS ICHOS;So;0;L;;;;;N;;;;; 1D0B4;BYZANTINE MUSICAL SYMBOL GORTHMIKON N APLOUN;So;0;L;;;;;N;;;;; 1D0B5;BYZANTINE MUSICAL SYMBOL GORTHMIKON N DIPLOUN;So;0;L;;;;;N;;;;; 1D0B6;BYZANTINE MUSICAL SYMBOL ENARXIS KAI FTHORA VOU;So;0;L;;;;;N;;;;; 1D0B7;BYZANTINE MUSICAL SYMBOL IMIFONON;So;0;L;;;;;N;;;;; 1D0B8;BYZANTINE MUSICAL SYMBOL IMIFTHORON;So;0;L;;;;;N;;;;; 1D0B9;BYZANTINE MUSICAL SYMBOL FTHORA ARCHAION DEYTEROU ICHOU;So;0;L;;;;;N;;;;; 1D0BA;BYZANTINE MUSICAL SYMBOL FTHORA DIATONIKI PA;So;0;L;;;;;N;;;;; 1D0BB;BYZANTINE MUSICAL SYMBOL FTHORA DIATONIKI NANA;So;0;L;;;;;N;;;;; 1D0BC;BYZANTINE MUSICAL SYMBOL FTHORA NAOS ICHOS;So;0;L;;;;;N;;;;; 1D0BD;BYZANTINE MUSICAL SYMBOL FTHORA DIATONIKI DI;So;0;L;;;;;N;;;;; 1D0BE;BYZANTINE MUSICAL SYMBOL FTHORA SKLIRON DIATONON DI;So;0;L;;;;;N;;;;; 1D0BF;BYZANTINE MUSICAL SYMBOL FTHORA DIATONIKI KE;So;0;L;;;;;N;;;;; 1D0C0;BYZANTINE MUSICAL SYMBOL FTHORA DIATONIKI ZO;So;0;L;;;;;N;;;;; 1D0C1;BYZANTINE MUSICAL SYMBOL FTHORA DIATONIKI NI KATO;So;0;L;;;;;N;;;;; 1D0C2;BYZANTINE MUSICAL SYMBOL FTHORA DIATONIKI NI ANO;So;0;L;;;;;N;;;;; 1D0C3;BYZANTINE MUSICAL SYMBOL FTHORA MALAKON CHROMA DIFONIAS;So;0;L;;;;;N;;;;; 1D0C4;BYZANTINE MUSICAL SYMBOL FTHORA MALAKON CHROMA MONOFONIAS;So;0;L;;;;;N;;;;; 1D0C5;BYZANTINE MUSICAL SYMBOL FHTORA SKLIRON CHROMA VASIS;So;0;L;;;;;N;;;;; 1D0C6;BYZANTINE MUSICAL SYMBOL FTHORA SKLIRON CHROMA SYNAFI;So;0;L;;;;;N;;;;; 1D0C7;BYZANTINE MUSICAL SYMBOL FTHORA NENANO;So;0;L;;;;;N;;;;; 1D0C8;BYZANTINE MUSICAL SYMBOL CHROA ZYGOS;So;0;L;;;;;N;;;;; 1D0C9;BYZANTINE MUSICAL SYMBOL CHROA KLITON;So;0;L;;;;;N;;;;; 1D0CA;BYZANTINE MUSICAL SYMBOL CHROA SPATHI;So;0;L;;;;;N;;;;; 1D0CB;BYZANTINE MUSICAL SYMBOL FTHORA I YFESIS TETARTIMORION;So;0;L;;;;;N;;;;; 1D0CC;BYZANTINE MUSICAL SYMBOL FTHORA ENARMONIOS ANTIFONIA;So;0;L;;;;;N;;;;; 1D0CD;BYZANTINE MUSICAL SYMBOL YFESIS TRITIMORION;So;0;L;;;;;N;;;;; 1D0CE;BYZANTINE MUSICAL SYMBOL DIESIS TRITIMORION;So;0;L;;;;;N;;;;; 1D0CF;BYZANTINE MUSICAL SYMBOL DIESIS TETARTIMORION;So;0;L;;;;;N;;;;; 1D0D0;BYZANTINE MUSICAL SYMBOL DIESIS APLI DYO DODEKATA;So;0;L;;;;;N;;;;; 1D0D1;BYZANTINE MUSICAL SYMBOL DIESIS MONOGRAMMOS TESSERA DODEKATA;So;0;L;;;;;N;;;;; 1D0D2;BYZANTINE MUSICAL SYMBOL DIESIS DIGRAMMOS EX DODEKATA;So;0;L;;;;;N;;;;; 1D0D3;BYZANTINE MUSICAL SYMBOL DIESIS TRIGRAMMOS OKTO DODEKATA;So;0;L;;;;;N;;;;; 1D0D4;BYZANTINE MUSICAL SYMBOL YFESIS APLI DYO DODEKATA;So;0;L;;;;;N;;;;; 1D0D5;BYZANTINE MUSICAL SYMBOL YFESIS MONOGRAMMOS TESSERA DODEKATA;So;0;L;;;;;N;;;;; 1D0D6;BYZANTINE MUSICAL SYMBOL YFESIS DIGRAMMOS EX DODEKATA;So;0;L;;;;;N;;;;; 1D0D7;BYZANTINE MUSICAL SYMBOL YFESIS TRIGRAMMOS OKTO DODEKATA;So;0;L;;;;;N;;;;; 1D0D8;BYZANTINE MUSICAL SYMBOL GENIKI DIESIS;So;0;L;;;;;N;;;;; 1D0D9;BYZANTINE MUSICAL SYMBOL GENIKI YFESIS;So;0;L;;;;;N;;;;; 1D0DA;BYZANTINE MUSICAL SYMBOL DIASTOLI APLI MIKRI;So;0;L;;;;;N;;;;; 1D0DB;BYZANTINE MUSICAL SYMBOL DIASTOLI APLI MEGALI;So;0;L;;;;;N;;;;; 1D0DC;BYZANTINE MUSICAL SYMBOL DIASTOLI DIPLI;So;0;L;;;;;N;;;;; 1D0DD;BYZANTINE MUSICAL SYMBOL DIASTOLI THESEOS;So;0;L;;;;;N;;;;; 1D0DE;BYZANTINE MUSICAL SYMBOL SIMANSIS THESEOS;So;0;L;;;;;N;;;;; 1D0DF;BYZANTINE MUSICAL SYMBOL SIMANSIS THESEOS DISIMOU;So;0;L;;;;;N;;;;; 1D0E0;BYZANTINE MUSICAL SYMBOL SIMANSIS THESEOS TRISIMOU;So;0;L;;;;;N;;;;; 1D0E1;BYZANTINE MUSICAL SYMBOL SIMANSIS THESEOS TETRASIMOU;So;0;L;;;;;N;;;;; 1D0E2;BYZANTINE MUSICAL SYMBOL SIMANSIS ARSEOS;So;0;L;;;;;N;;;;; 1D0E3;BYZANTINE MUSICAL SYMBOL SIMANSIS ARSEOS DISIMOU;So;0;L;;;;;N;;;;; 1D0E4;BYZANTINE MUSICAL SYMBOL SIMANSIS ARSEOS TRISIMOU;So;0;L;;;;;N;;;;; 1D0E5;BYZANTINE MUSICAL SYMBOL SIMANSIS ARSEOS TETRASIMOU;So;0;L;;;;;N;;;;; 1D0E6;BYZANTINE MUSICAL SYMBOL DIGRAMMA GG;So;0;L;;;;;N;;;;; 1D0E7;BYZANTINE MUSICAL SYMBOL DIFTOGGOS OU;So;0;L;;;;;N;;;;; 1D0E8;BYZANTINE MUSICAL SYMBOL STIGMA;So;0;L;;;;;N;;;;; 1D0E9;BYZANTINE MUSICAL SYMBOL ARKTIKO PA;So;0;L;;;;;N;;;;; 1D0EA;BYZANTINE MUSICAL SYMBOL ARKTIKO VOU;So;0;L;;;;;N;;;;; 1D0EB;BYZANTINE MUSICAL SYMBOL ARKTIKO GA;So;0;L;;;;;N;;;;; 1D0EC;BYZANTINE MUSICAL SYMBOL ARKTIKO DI;So;0;L;;;;;N;;;;; 1D0ED;BYZANTINE MUSICAL SYMBOL ARKTIKO KE;So;0;L;;;;;N;;;;; 1D0EE;BYZANTINE MUSICAL SYMBOL ARKTIKO ZO;So;0;L;;;;;N;;;;; 1D0EF;BYZANTINE MUSICAL SYMBOL ARKTIKO NI;So;0;L;;;;;N;;;;; 1D0F0;BYZANTINE MUSICAL SYMBOL KENTIMATA NEO MESO;So;0;L;;;;;N;;;;; 1D0F1;BYZANTINE MUSICAL SYMBOL KENTIMA NEO MESO;So;0;L;;;;;N;;;;; 1D0F2;BYZANTINE MUSICAL SYMBOL KENTIMATA NEO KATO;So;0;L;;;;;N;;;;; 1D0F3;BYZANTINE MUSICAL SYMBOL KENTIMA NEO KATO;So;0;L;;;;;N;;;;; 1D0F4;BYZANTINE MUSICAL SYMBOL KLASMA KATO;So;0;L;;;;;N;;;;; 1D0F5;BYZANTINE MUSICAL SYMBOL GORGON NEO KATO;So;0;L;;;;;N;;;;; 1D100;MUSICAL SYMBOL SINGLE BARLINE;So;0;L;;;;;N;;;;; 1D101;MUSICAL SYMBOL DOUBLE BARLINE;So;0;L;;;;;N;;;;; 1D102;MUSICAL SYMBOL FINAL BARLINE;So;0;L;;;;;N;;;;; 1D103;MUSICAL SYMBOL REVERSE FINAL BARLINE;So;0;L;;;;;N;;;;; 1D104;MUSICAL SYMBOL DASHED BARLINE;So;0;L;;;;;N;;;;; 1D105;MUSICAL SYMBOL SHORT BARLINE;So;0;L;;;;;N;;;;; 1D106;MUSICAL SYMBOL LEFT REPEAT SIGN;So;0;L;;;;;N;;;;; 1D107;MUSICAL SYMBOL RIGHT REPEAT SIGN;So;0;L;;;;;N;;;;; 1D108;MUSICAL SYMBOL REPEAT DOTS;So;0;L;;;;;N;;;;; 1D109;MUSICAL SYMBOL DAL SEGNO;So;0;L;;;;;N;;;;; 1D10A;MUSICAL SYMBOL DA CAPO;So;0;L;;;;;N;;;;; 1D10B;MUSICAL SYMBOL SEGNO;So;0;L;;;;;N;;;;; 1D10C;MUSICAL SYMBOL CODA;So;0;L;;;;;N;;;;; 1D10D;MUSICAL SYMBOL REPEATED FIGURE-1;So;0;L;;;;;N;;;;; 1D10E;MUSICAL SYMBOL REPEATED FIGURE-2;So;0;L;;;;;N;;;;; 1D10F;MUSICAL SYMBOL REPEATED FIGURE-3;So;0;L;;;;;N;;;;; 1D110;MUSICAL SYMBOL FERMATA;So;0;L;;;;;N;;;;; 1D111;MUSICAL SYMBOL FERMATA BELOW;So;0;L;;;;;N;;;;; 1D112;MUSICAL SYMBOL BREATH MARK;So;0;L;;;;;N;;;;; 1D113;MUSICAL SYMBOL CAESURA;So;0;L;;;;;N;;;;; 1D114;MUSICAL SYMBOL BRACE;So;0;L;;;;;N;;;;; 1D115;MUSICAL SYMBOL BRACKET;So;0;L;;;;;N;;;;; 1D116;MUSICAL SYMBOL ONE-LINE STAFF;So;0;L;;;;;N;;;;; 1D117;MUSICAL SYMBOL TWO-LINE STAFF;So;0;L;;;;;N;;;;; 1D118;MUSICAL SYMBOL THREE-LINE STAFF;So;0;L;;;;;N;;;;; 1D119;MUSICAL SYMBOL FOUR-LINE STAFF;So;0;L;;;;;N;;;;; 1D11A;MUSICAL SYMBOL FIVE-LINE STAFF;So;0;L;;;;;N;;;;; 1D11B;MUSICAL SYMBOL SIX-LINE STAFF;So;0;L;;;;;N;;;;; 1D11C;MUSICAL SYMBOL SIX-STRING FRETBOARD;So;0;L;;;;;N;;;;; 1D11D;MUSICAL SYMBOL FOUR-STRING FRETBOARD;So;0;L;;;;;N;;;;; 1D11E;MUSICAL SYMBOL G CLEF;So;0;L;;;;;N;;;;; 1D11F;MUSICAL SYMBOL G CLEF OTTAVA ALTA;So;0;L;;;;;N;;;;; 1D120;MUSICAL SYMBOL G CLEF OTTAVA BASSA;So;0;L;;;;;N;;;;; 1D121;MUSICAL SYMBOL C CLEF;So;0;L;;;;;N;;;;; 1D122;MUSICAL SYMBOL F CLEF;So;0;L;;;;;N;;;;; 1D123;MUSICAL SYMBOL F CLEF OTTAVA ALTA;So;0;L;;;;;N;;;;; 1D124;MUSICAL SYMBOL F CLEF OTTAVA BASSA;So;0;L;;;;;N;;;;; 1D125;MUSICAL SYMBOL DRUM CLEF-1;So;0;L;;;;;N;;;;; 1D126;MUSICAL SYMBOL DRUM CLEF-2;So;0;L;;;;;N;;;;; 1D129;MUSICAL SYMBOL MULTIPLE MEASURE REST;So;0;L;;;;;N;;;;; 1D12A;MUSICAL SYMBOL DOUBLE SHARP;So;0;L;;;;;N;;;;; 1D12B;MUSICAL SYMBOL DOUBLE FLAT;So;0;L;;;;;N;;;;; 1D12C;MUSICAL SYMBOL FLAT UP;So;0;L;;;;;N;;;;; 1D12D;MUSICAL SYMBOL FLAT DOWN;So;0;L;;;;;N;;;;; 1D12E;MUSICAL SYMBOL NATURAL UP;So;0;L;;;;;N;;;;; 1D12F;MUSICAL SYMBOL NATURAL DOWN;So;0;L;;;;;N;;;;; 1D130;MUSICAL SYMBOL SHARP UP;So;0;L;;;;;N;;;;; 1D131;MUSICAL SYMBOL SHARP DOWN;So;0;L;;;;;N;;;;; 1D132;MUSICAL SYMBOL QUARTER TONE SHARP;So;0;L;;;;;N;;;;; 1D133;MUSICAL SYMBOL QUARTER TONE FLAT;So;0;L;;;;;N;;;;; 1D134;MUSICAL SYMBOL COMMON TIME;So;0;L;;;;;N;;;;; 1D135;MUSICAL SYMBOL CUT TIME;So;0;L;;;;;N;;;;; 1D136;MUSICAL SYMBOL OTTAVA ALTA;So;0;L;;;;;N;;;;; 1D137;MUSICAL SYMBOL OTTAVA BASSA;So;0;L;;;;;N;;;;; 1D138;MUSICAL SYMBOL QUINDICESIMA ALTA;So;0;L;;;;;N;;;;; 1D139;MUSICAL SYMBOL QUINDICESIMA BASSA;So;0;L;;;;;N;;;;; 1D13A;MUSICAL SYMBOL MULTI REST;So;0;L;;;;;N;;;;; 1D13B;MUSICAL SYMBOL WHOLE REST;So;0;L;;;;;N;;;;; 1D13C;MUSICAL SYMBOL HALF REST;So;0;L;;;;;N;;;;; 1D13D;MUSICAL SYMBOL QUARTER REST;So;0;L;;;;;N;;;;; 1D13E;MUSICAL SYMBOL EIGHTH REST;So;0;L;;;;;N;;;;; 1D13F;MUSICAL SYMBOL SIXTEENTH REST;So;0;L;;;;;N;;;;; 1D140;MUSICAL SYMBOL THIRTY-SECOND REST;So;0;L;;;;;N;;;;; 1D141;MUSICAL SYMBOL SIXTY-FOURTH REST;So;0;L;;;;;N;;;;; 1D142;MUSICAL SYMBOL ONE HUNDRED TWENTY-EIGHTH REST;So;0;L;;;;;N;;;;; 1D143;MUSICAL SYMBOL X NOTEHEAD;So;0;L;;;;;N;;;;; 1D144;MUSICAL SYMBOL PLUS NOTEHEAD;So;0;L;;;;;N;;;;; 1D145;MUSICAL SYMBOL CIRCLE X NOTEHEAD;So;0;L;;;;;N;;;;; 1D146;MUSICAL SYMBOL SQUARE NOTEHEAD WHITE;So;0;L;;;;;N;;;;; 1D147;MUSICAL SYMBOL SQUARE NOTEHEAD BLACK;So;0;L;;;;;N;;;;; 1D148;MUSICAL SYMBOL TRIANGLE NOTEHEAD UP WHITE;So;0;L;;;;;N;;;;; 1D149;MUSICAL SYMBOL TRIANGLE NOTEHEAD UP BLACK;So;0;L;;;;;N;;;;; 1D14A;MUSICAL SYMBOL TRIANGLE NOTEHEAD LEFT WHITE;So;0;L;;;;;N;;;;; 1D14B;MUSICAL SYMBOL TRIANGLE NOTEHEAD LEFT BLACK;So;0;L;;;;;N;;;;; 1D14C;MUSICAL SYMBOL TRIANGLE NOTEHEAD RIGHT WHITE;So;0;L;;;;;N;;;;; 1D14D;MUSICAL SYMBOL TRIANGLE NOTEHEAD RIGHT BLACK;So;0;L;;;;;N;;;;; 1D14E;MUSICAL SYMBOL TRIANGLE NOTEHEAD DOWN WHITE;So;0;L;;;;;N;;;;; 1D14F;MUSICAL SYMBOL TRIANGLE NOTEHEAD DOWN BLACK;So;0;L;;;;;N;;;;; 1D150;MUSICAL SYMBOL TRIANGLE NOTEHEAD UP RIGHT WHITE;So;0;L;;;;;N;;;;; 1D151;MUSICAL SYMBOL TRIANGLE NOTEHEAD UP RIGHT BLACK;So;0;L;;;;;N;;;;; 1D152;MUSICAL SYMBOL MOON NOTEHEAD WHITE;So;0;L;;;;;N;;;;; 1D153;MUSICAL SYMBOL MOON NOTEHEAD BLACK;So;0;L;;;;;N;;;;; 1D154;MUSICAL SYMBOL TRIANGLE-ROUND NOTEHEAD DOWN WHITE;So;0;L;;;;;N;;;;; 1D155;MUSICAL SYMBOL TRIANGLE-ROUND NOTEHEAD DOWN BLACK;So;0;L;;;;;N;;;;; 1D156;MUSICAL SYMBOL PARENTHESIS NOTEHEAD;So;0;L;;;;;N;;;;; 1D157;MUSICAL SYMBOL VOID NOTEHEAD;So;0;L;;;;;N;;;;; 1D158;MUSICAL SYMBOL NOTEHEAD BLACK;So;0;L;;;;;N;;;;; 1D159;MUSICAL SYMBOL NULL NOTEHEAD;So;0;L;;;;;N;;;;; 1D15A;MUSICAL SYMBOL CLUSTER NOTEHEAD WHITE;So;0;L;;;;;N;;;;; 1D15B;MUSICAL SYMBOL CLUSTER NOTEHEAD BLACK;So;0;L;;;;;N;;;;; 1D15C;MUSICAL SYMBOL BREVE;So;0;L;;;;;N;;;;; 1D15D;MUSICAL SYMBOL WHOLE NOTE;So;0;L;;;;;N;;;;; 1D15E;MUSICAL SYMBOL HALF NOTE;So;0;L;1D157 1D165;;;;N;;;;; 1D15F;MUSICAL SYMBOL QUARTER NOTE;So;0;L;1D158 1D165;;;;N;;;;; 1D160;MUSICAL SYMBOL EIGHTH NOTE;So;0;L;1D15F 1D16E;;;;N;;;;; 1D161;MUSICAL SYMBOL SIXTEENTH NOTE;So;0;L;1D15F 1D16F;;;;N;;;;; 1D162;MUSICAL SYMBOL THIRTY-SECOND NOTE;So;0;L;1D15F 1D170;;;;N;;;;; 1D163;MUSICAL SYMBOL SIXTY-FOURTH NOTE;So;0;L;1D15F 1D171;;;;N;;;;; 1D164;MUSICAL SYMBOL ONE HUNDRED TWENTY-EIGHTH NOTE;So;0;L;1D15F 1D172;;;;N;;;;; 1D165;MUSICAL SYMBOL COMBINING STEM;Mc;216;L;;;;;N;;;;; 1D166;MUSICAL SYMBOL COMBINING SPRECHGESANG STEM;Mc;216;L;;;;;N;;;;; 1D167;MUSICAL SYMBOL COMBINING TREMOLO-1;Mn;1;NSM;;;;;N;;;;; 1D168;MUSICAL SYMBOL COMBINING TREMOLO-2;Mn;1;NSM;;;;;N;;;;; 1D169;MUSICAL SYMBOL COMBINING TREMOLO-3;Mn;1;NSM;;;;;N;;;;; 1D16A;MUSICAL SYMBOL FINGERED TREMOLO-1;So;0;L;;;;;N;;;;; 1D16B;MUSICAL SYMBOL FINGERED TREMOLO-2;So;0;L;;;;;N;;;;; 1D16C;MUSICAL SYMBOL FINGERED TREMOLO-3;So;0;L;;;;;N;;;;; 1D16D;MUSICAL SYMBOL COMBINING AUGMENTATION DOT;Mc;226;L;;;;;N;;;;; 1D16E;MUSICAL SYMBOL COMBINING FLAG-1;Mc;216;L;;;;;N;;;;; 1D16F;MUSICAL SYMBOL COMBINING FLAG-2;Mc;216;L;;;;;N;;;;; 1D170;MUSICAL SYMBOL COMBINING FLAG-3;Mc;216;L;;;;;N;;;;; 1D171;MUSICAL SYMBOL COMBINING FLAG-4;Mc;216;L;;;;;N;;;;; 1D172;MUSICAL SYMBOL COMBINING FLAG-5;Mc;216;L;;;;;N;;;;; 1D173;MUSICAL SYMBOL BEGIN BEAM;Cf;0;BN;;;;;N;;;;; 1D174;MUSICAL SYMBOL END BEAM;Cf;0;BN;;;;;N;;;;; 1D175;MUSICAL SYMBOL BEGIN TIE;Cf;0;BN;;;;;N;;;;; 1D176;MUSICAL SYMBOL END TIE;Cf;0;BN;;;;;N;;;;; 1D177;MUSICAL SYMBOL BEGIN SLUR;Cf;0;BN;;;;;N;;;;; 1D178;MUSICAL SYMBOL END SLUR;Cf;0;BN;;;;;N;;;;; 1D179;MUSICAL SYMBOL BEGIN PHRASE;Cf;0;BN;;;;;N;;;;; 1D17A;MUSICAL SYMBOL END PHRASE;Cf;0;BN;;;;;N;;;;; 1D17B;MUSICAL SYMBOL COMBINING ACCENT;Mn;220;NSM;;;;;N;;;;; 1D17C;MUSICAL SYMBOL COMBINING STACCATO;Mn;220;NSM;;;;;N;;;;; 1D17D;MUSICAL SYMBOL COMBINING TENUTO;Mn;220;NSM;;;;;N;;;;; 1D17E;MUSICAL SYMBOL COMBINING STACCATISSIMO;Mn;220;NSM;;;;;N;;;;; 1D17F;MUSICAL SYMBOL COMBINING MARCATO;Mn;220;NSM;;;;;N;;;;; 1D180;MUSICAL SYMBOL COMBINING MARCATO-STACCATO;Mn;220;NSM;;;;;N;;;;; 1D181;MUSICAL SYMBOL COMBINING ACCENT-STACCATO;Mn;220;NSM;;;;;N;;;;; 1D182;MUSICAL SYMBOL COMBINING LOURE;Mn;220;NSM;;;;;N;;;;; 1D183;MUSICAL SYMBOL ARPEGGIATO UP;So;0;L;;;;;N;;;;; 1D184;MUSICAL SYMBOL ARPEGGIATO DOWN;So;0;L;;;;;N;;;;; 1D185;MUSICAL SYMBOL COMBINING DOIT;Mn;230;NSM;;;;;N;;;;; 1D186;MUSICAL SYMBOL COMBINING RIP;Mn;230;NSM;;;;;N;;;;; 1D187;MUSICAL SYMBOL COMBINING FLIP;Mn;230;NSM;;;;;N;;;;; 1D188;MUSICAL SYMBOL COMBINING SMEAR;Mn;230;NSM;;;;;N;;;;; 1D189;MUSICAL SYMBOL COMBINING BEND;Mn;230;NSM;;;;;N;;;;; 1D18A;MUSICAL SYMBOL COMBINING DOUBLE TONGUE;Mn;220;NSM;;;;;N;;;;; 1D18B;MUSICAL SYMBOL COMBINING TRIPLE TONGUE;Mn;220;NSM;;;;;N;;;;; 1D18C;MUSICAL SYMBOL RINFORZANDO;So;0;L;;;;;N;;;;; 1D18D;MUSICAL SYMBOL SUBITO;So;0;L;;;;;N;;;;; 1D18E;MUSICAL SYMBOL Z;So;0;L;;;;;N;;;;; 1D18F;MUSICAL SYMBOL PIANO;So;0;L;;;;;N;;;;; 1D190;MUSICAL SYMBOL MEZZO;So;0;L;;;;;N;;;;; 1D191;MUSICAL SYMBOL FORTE;So;0;L;;;;;N;;;;; 1D192;MUSICAL SYMBOL CRESCENDO;So;0;L;;;;;N;;;;; 1D193;MUSICAL SYMBOL DECRESCENDO;So;0;L;;;;;N;;;;; 1D194;MUSICAL SYMBOL GRACE NOTE SLASH;So;0;L;;;;;N;;;;; 1D195;MUSICAL SYMBOL GRACE NOTE NO SLASH;So;0;L;;;;;N;;;;; 1D196;MUSICAL SYMBOL TR;So;0;L;;;;;N;;;;; 1D197;MUSICAL SYMBOL TURN;So;0;L;;;;;N;;;;; 1D198;MUSICAL SYMBOL INVERTED TURN;So;0;L;;;;;N;;;;; 1D199;MUSICAL SYMBOL TURN SLASH;So;0;L;;;;;N;;;;; 1D19A;MUSICAL SYMBOL TURN UP;So;0;L;;;;;N;;;;; 1D19B;MUSICAL SYMBOL ORNAMENT STROKE-1;So;0;L;;;;;N;;;;; 1D19C;MUSICAL SYMBOL ORNAMENT STROKE-2;So;0;L;;;;;N;;;;; 1D19D;MUSICAL SYMBOL ORNAMENT STROKE-3;So;0;L;;;;;N;;;;; 1D19E;MUSICAL SYMBOL ORNAMENT STROKE-4;So;0;L;;;;;N;;;;; 1D19F;MUSICAL SYMBOL ORNAMENT STROKE-5;So;0;L;;;;;N;;;;; 1D1A0;MUSICAL SYMBOL ORNAMENT STROKE-6;So;0;L;;;;;N;;;;; 1D1A1;MUSICAL SYMBOL ORNAMENT STROKE-7;So;0;L;;;;;N;;;;; 1D1A2;MUSICAL SYMBOL ORNAMENT STROKE-8;So;0;L;;;;;N;;;;; 1D1A3;MUSICAL SYMBOL ORNAMENT STROKE-9;So;0;L;;;;;N;;;;; 1D1A4;MUSICAL SYMBOL ORNAMENT STROKE-10;So;0;L;;;;;N;;;;; 1D1A5;MUSICAL SYMBOL ORNAMENT STROKE-11;So;0;L;;;;;N;;;;; 1D1A6;MUSICAL SYMBOL HAUPTSTIMME;So;0;L;;;;;N;;;;; 1D1A7;MUSICAL SYMBOL NEBENSTIMME;So;0;L;;;;;N;;;;; 1D1A8;MUSICAL SYMBOL END OF STIMME;So;0;L;;;;;N;;;;; 1D1A9;MUSICAL SYMBOL DEGREE SLASH;So;0;L;;;;;N;;;;; 1D1AA;MUSICAL SYMBOL COMBINING DOWN BOW;Mn;230;NSM;;;;;N;;;;; 1D1AB;MUSICAL SYMBOL COMBINING UP BOW;Mn;230;NSM;;;;;N;;;;; 1D1AC;MUSICAL SYMBOL COMBINING HARMONIC;Mn;230;NSM;;;;;N;;;;; 1D1AD;MUSICAL SYMBOL COMBINING SNAP PIZZICATO;Mn;230;NSM;;;;;N;;;;; 1D1AE;MUSICAL SYMBOL PEDAL MARK;So;0;L;;;;;N;;;;; 1D1AF;MUSICAL SYMBOL PEDAL UP MARK;So;0;L;;;;;N;;;;; 1D1B0;MUSICAL SYMBOL HALF PEDAL MARK;So;0;L;;;;;N;;;;; 1D1B1;MUSICAL SYMBOL GLISSANDO UP;So;0;L;;;;;N;;;;; 1D1B2;MUSICAL SYMBOL GLISSANDO DOWN;So;0;L;;;;;N;;;;; 1D1B3;MUSICAL SYMBOL WITH FINGERNAILS;So;0;L;;;;;N;;;;; 1D1B4;MUSICAL SYMBOL DAMP;So;0;L;;;;;N;;;;; 1D1B5;MUSICAL SYMBOL DAMP ALL;So;0;L;;;;;N;;;;; 1D1B6;MUSICAL SYMBOL MAXIMA;So;0;L;;;;;N;;;;; 1D1B7;MUSICAL SYMBOL LONGA;So;0;L;;;;;N;;;;; 1D1B8;MUSICAL SYMBOL BREVIS;So;0;L;;;;;N;;;;; 1D1B9;MUSICAL SYMBOL SEMIBREVIS WHITE;So;0;L;;;;;N;;;;; 1D1BA;MUSICAL SYMBOL SEMIBREVIS BLACK;So;0;L;;;;;N;;;;; 1D1BB;MUSICAL SYMBOL MINIMA;So;0;L;1D1B9 1D165;;;;N;;;;; 1D1BC;MUSICAL SYMBOL MINIMA BLACK;So;0;L;1D1BA 1D165;;;;N;;;;; 1D1BD;MUSICAL SYMBOL SEMIMINIMA WHITE;So;0;L;1D1BB 1D16E;;;;N;;;;; 1D1BE;MUSICAL SYMBOL SEMIMINIMA BLACK;So;0;L;1D1BC 1D16E;;;;N;;;;; 1D1BF;MUSICAL SYMBOL FUSA WHITE;So;0;L;1D1BB 1D16F;;;;N;;;;; 1D1C0;MUSICAL SYMBOL FUSA BLACK;So;0;L;1D1BC 1D16F;;;;N;;;;; 1D1C1;MUSICAL SYMBOL LONGA PERFECTA REST;So;0;L;;;;;N;;;;; 1D1C2;MUSICAL SYMBOL LONGA IMPERFECTA REST;So;0;L;;;;;N;;;;; 1D1C3;MUSICAL SYMBOL BREVIS REST;So;0;L;;;;;N;;;;; 1D1C4;MUSICAL SYMBOL SEMIBREVIS REST;So;0;L;;;;;N;;;;; 1D1C5;MUSICAL SYMBOL MINIMA REST;So;0;L;;;;;N;;;;; 1D1C6;MUSICAL SYMBOL SEMIMINIMA REST;So;0;L;;;;;N;;;;; 1D1C7;MUSICAL SYMBOL TEMPUS PERFECTUM CUM PROLATIONE PERFECTA;So;0;L;;;;;N;;;;; 1D1C8;MUSICAL SYMBOL TEMPUS PERFECTUM CUM PROLATIONE IMPERFECTA;So;0;L;;;;;N;;;;; 1D1C9;MUSICAL SYMBOL TEMPUS PERFECTUM CUM PROLATIONE PERFECTA DIMINUTION-1;So;0;L;;;;;N;;;;; 1D1CA;MUSICAL SYMBOL TEMPUS IMPERFECTUM CUM PROLATIONE PERFECTA;So;0;L;;;;;N;;;;; 1D1CB;MUSICAL SYMBOL TEMPUS IMPERFECTUM CUM PROLATIONE IMPERFECTA;So;0;L;;;;;N;;;;; 1D1CC;MUSICAL SYMBOL TEMPUS IMPERFECTUM CUM PROLATIONE IMPERFECTA DIMINUTION-1;So;0;L;;;;;N;;;;; 1D1CD;MUSICAL SYMBOL TEMPUS IMPERFECTUM CUM PROLATIONE IMPERFECTA DIMINUTION-2;So;0;L;;;;;N;;;;; 1D1CE;MUSICAL SYMBOL TEMPUS IMPERFECTUM CUM PROLATIONE IMPERFECTA DIMINUTION-3;So;0;L;;;;;N;;;;; 1D1CF;MUSICAL SYMBOL CROIX;So;0;L;;;;;N;;;;; 1D1D0;MUSICAL SYMBOL GREGORIAN C CLEF;So;0;L;;;;;N;;;;; 1D1D1;MUSICAL SYMBOL GREGORIAN F CLEF;So;0;L;;;;;N;;;;; 1D1D2;MUSICAL SYMBOL SQUARE B;So;0;L;;;;;N;;;;; 1D1D3;MUSICAL SYMBOL VIRGA;So;0;L;;;;;N;;;;; 1D1D4;MUSICAL SYMBOL PODATUS;So;0;L;;;;;N;;;;; 1D1D5;MUSICAL SYMBOL CLIVIS;So;0;L;;;;;N;;;;; 1D1D6;MUSICAL SYMBOL SCANDICUS;So;0;L;;;;;N;;;;; 1D1D7;MUSICAL SYMBOL CLIMACUS;So;0;L;;;;;N;;;;; 1D1D8;MUSICAL SYMBOL TORCULUS;So;0;L;;;;;N;;;;; 1D1D9;MUSICAL SYMBOL PORRECTUS;So;0;L;;;;;N;;;;; 1D1DA;MUSICAL SYMBOL PORRECTUS FLEXUS;So;0;L;;;;;N;;;;; 1D1DB;MUSICAL SYMBOL SCANDICUS FLEXUS;So;0;L;;;;;N;;;;; 1D1DC;MUSICAL SYMBOL TORCULUS RESUPINUS;So;0;L;;;;;N;;;;; 1D1DD;MUSICAL SYMBOL PES SUBPUNCTIS;So;0;L;;;;;N;;;;; 1D200;GREEK VOCAL NOTATION SYMBOL-1;So;0;ON;;;;;N;;;;; 1D201;GREEK VOCAL NOTATION SYMBOL-2;So;0;ON;;;;;N;;;;; 1D202;GREEK VOCAL NOTATION SYMBOL-3;So;0;ON;;;;;N;;;;; 1D203;GREEK VOCAL NOTATION SYMBOL-4;So;0;ON;;;;;N;;;;; 1D204;GREEK VOCAL NOTATION SYMBOL-5;So;0;ON;;;;;N;;;;; 1D205;GREEK VOCAL NOTATION SYMBOL-6;So;0;ON;;;;;N;;;;; 1D206;GREEK VOCAL NOTATION SYMBOL-7;So;0;ON;;;;;N;;;;; 1D207;GREEK VOCAL NOTATION SYMBOL-8;So;0;ON;;;;;N;;;;; 1D208;GREEK VOCAL NOTATION SYMBOL-9;So;0;ON;;;;;N;;;;; 1D209;GREEK VOCAL NOTATION SYMBOL-10;So;0;ON;;;;;N;;;;; 1D20A;GREEK VOCAL NOTATION SYMBOL-11;So;0;ON;;;;;N;;;;; 1D20B;GREEK VOCAL NOTATION SYMBOL-12;So;0;ON;;;;;N;;;;; 1D20C;GREEK VOCAL NOTATION SYMBOL-13;So;0;ON;;;;;N;;;;; 1D20D;GREEK VOCAL NOTATION SYMBOL-14;So;0;ON;;;;;N;;;;; 1D20E;GREEK VOCAL NOTATION SYMBOL-15;So;0;ON;;;;;N;;;;; 1D20F;GREEK VOCAL NOTATION SYMBOL-16;So;0;ON;;;;;N;;;;; 1D210;GREEK VOCAL NOTATION SYMBOL-17;So;0;ON;;;;;N;;;;; 1D211;GREEK VOCAL NOTATION SYMBOL-18;So;0;ON;;;;;N;;;;; 1D212;GREEK VOCAL NOTATION SYMBOL-19;So;0;ON;;;;;N;;;;; 1D213;GREEK VOCAL NOTATION SYMBOL-20;So;0;ON;;;;;N;;;;; 1D214;GREEK VOCAL NOTATION SYMBOL-21;So;0;ON;;;;;N;;;;; 1D215;GREEK VOCAL NOTATION SYMBOL-22;So;0;ON;;;;;N;;;;; 1D216;GREEK VOCAL NOTATION SYMBOL-23;So;0;ON;;;;;N;;;;; 1D217;GREEK VOCAL NOTATION SYMBOL-24;So;0;ON;;;;;N;;;;; 1D218;GREEK VOCAL NOTATION SYMBOL-50;So;0;ON;;;;;N;;;;; 1D219;GREEK VOCAL NOTATION SYMBOL-51;So;0;ON;;;;;N;;;;; 1D21A;GREEK VOCAL NOTATION SYMBOL-52;So;0;ON;;;;;N;;;;; 1D21B;GREEK VOCAL NOTATION SYMBOL-53;So;0;ON;;;;;N;;;;; 1D21C;GREEK VOCAL NOTATION SYMBOL-54;So;0;ON;;;;;N;;;;; 1D21D;GREEK INSTRUMENTAL NOTATION SYMBOL-1;So;0;ON;;;;;N;;;;; 1D21E;GREEK INSTRUMENTAL NOTATION SYMBOL-2;So;0;ON;;;;;N;;;;; 1D21F;GREEK INSTRUMENTAL NOTATION SYMBOL-4;So;0;ON;;;;;N;;;;; 1D220;GREEK INSTRUMENTAL NOTATION SYMBOL-5;So;0;ON;;;;;N;;;;; 1D221;GREEK INSTRUMENTAL NOTATION SYMBOL-7;So;0;ON;;;;;N;;;;; 1D222;GREEK INSTRUMENTAL NOTATION SYMBOL-8;So;0;ON;;;;;N;;;;; 1D223;GREEK INSTRUMENTAL NOTATION SYMBOL-11;So;0;ON;;;;;N;;;;; 1D224;GREEK INSTRUMENTAL NOTATION SYMBOL-12;So;0;ON;;;;;N;;;;; 1D225;GREEK INSTRUMENTAL NOTATION SYMBOL-13;So;0;ON;;;;;N;;;;; 1D226;GREEK INSTRUMENTAL NOTATION SYMBOL-14;So;0;ON;;;;;N;;;;; 1D227;GREEK INSTRUMENTAL NOTATION SYMBOL-17;So;0;ON;;;;;N;;;;; 1D228;GREEK INSTRUMENTAL NOTATION SYMBOL-18;So;0;ON;;;;;N;;;;; 1D229;GREEK INSTRUMENTAL NOTATION SYMBOL-19;So;0;ON;;;;;N;;;;; 1D22A;GREEK INSTRUMENTAL NOTATION SYMBOL-23;So;0;ON;;;;;N;;;;; 1D22B;GREEK INSTRUMENTAL NOTATION SYMBOL-24;So;0;ON;;;;;N;;;;; 1D22C;GREEK INSTRUMENTAL NOTATION SYMBOL-25;So;0;ON;;;;;N;;;;; 1D22D;GREEK INSTRUMENTAL NOTATION SYMBOL-26;So;0;ON;;;;;N;;;;; 1D22E;GREEK INSTRUMENTAL NOTATION SYMBOL-27;So;0;ON;;;;;N;;;;; 1D22F;GREEK INSTRUMENTAL NOTATION SYMBOL-29;So;0;ON;;;;;N;;;;; 1D230;GREEK INSTRUMENTAL NOTATION SYMBOL-30;So;0;ON;;;;;N;;;;; 1D231;GREEK INSTRUMENTAL NOTATION SYMBOL-32;So;0;ON;;;;;N;;;;; 1D232;GREEK INSTRUMENTAL NOTATION SYMBOL-36;So;0;ON;;;;;N;;;;; 1D233;GREEK INSTRUMENTAL NOTATION SYMBOL-37;So;0;ON;;;;;N;;;;; 1D234;GREEK INSTRUMENTAL NOTATION SYMBOL-38;So;0;ON;;;;;N;;;;; 1D235;GREEK INSTRUMENTAL NOTATION SYMBOL-39;So;0;ON;;;;;N;;;;; 1D236;GREEK INSTRUMENTAL NOTATION SYMBOL-40;So;0;ON;;;;;N;;;;; 1D237;GREEK INSTRUMENTAL NOTATION SYMBOL-42;So;0;ON;;;;;N;;;;; 1D238;GREEK INSTRUMENTAL NOTATION SYMBOL-43;So;0;ON;;;;;N;;;;; 1D239;GREEK INSTRUMENTAL NOTATION SYMBOL-45;So;0;ON;;;;;N;;;;; 1D23A;GREEK INSTRUMENTAL NOTATION SYMBOL-47;So;0;ON;;;;;N;;;;; 1D23B;GREEK INSTRUMENTAL NOTATION SYMBOL-48;So;0;ON;;;;;N;;;;; 1D23C;GREEK INSTRUMENTAL NOTATION SYMBOL-49;So;0;ON;;;;;N;;;;; 1D23D;GREEK INSTRUMENTAL NOTATION SYMBOL-50;So;0;ON;;;;;N;;;;; 1D23E;GREEK INSTRUMENTAL NOTATION SYMBOL-51;So;0;ON;;;;;N;;;;; 1D23F;GREEK INSTRUMENTAL NOTATION SYMBOL-52;So;0;ON;;;;;N;;;;; 1D240;GREEK INSTRUMENTAL NOTATION SYMBOL-53;So;0;ON;;;;;N;;;;; 1D241;GREEK INSTRUMENTAL NOTATION SYMBOL-54;So;0;ON;;;;;N;;;;; 1D242;COMBINING GREEK MUSICAL TRISEME;Mn;230;NSM;;;;;N;;;;; 1D243;COMBINING GREEK MUSICAL TETRASEME;Mn;230;NSM;;;;;N;;;;; 1D244;COMBINING GREEK MUSICAL PENTASEME;Mn;230;NSM;;;;;N;;;;; 1D245;GREEK MUSICAL LEIMMA;So;0;ON;;;;;N;;;;; 1D300;MONOGRAM FOR EARTH;So;0;ON;;;;;N;;;;; 1D301;DIGRAM FOR HEAVENLY EARTH;So;0;ON;;;;;N;;;;; 1D302;DIGRAM FOR HUMAN EARTH;So;0;ON;;;;;N;;;;; 1D303;DIGRAM FOR EARTHLY HEAVEN;So;0;ON;;;;;N;;;;; 1D304;DIGRAM FOR EARTHLY HUMAN;So;0;ON;;;;;N;;;;; 1D305;DIGRAM FOR EARTH;So;0;ON;;;;;N;;;;; 1D306;TETRAGRAM FOR CENTRE;So;0;ON;;;;;N;;;;; 1D307;TETRAGRAM FOR FULL CIRCLE;So;0;ON;;;;;N;;;;; 1D308;TETRAGRAM FOR MIRED;So;0;ON;;;;;N;;;;; 1D309;TETRAGRAM FOR BARRIER;So;0;ON;;;;;N;;;;; 1D30A;TETRAGRAM FOR KEEPING SMALL;So;0;ON;;;;;N;;;;; 1D30B;TETRAGRAM FOR CONTRARIETY;So;0;ON;;;;;N;;;;; 1D30C;TETRAGRAM FOR ASCENT;So;0;ON;;;;;N;;;;; 1D30D;TETRAGRAM FOR OPPOSITION;So;0;ON;;;;;N;;;;; 1D30E;TETRAGRAM FOR BRANCHING OUT;So;0;ON;;;;;N;;;;; 1D30F;TETRAGRAM FOR DEFECTIVENESS OR DISTORTION;So;0;ON;;;;;N;;;;; 1D310;TETRAGRAM FOR DIVERGENCE;So;0;ON;;;;;N;;;;; 1D311;TETRAGRAM FOR YOUTHFULNESS;So;0;ON;;;;;N;;;;; 1D312;TETRAGRAM FOR INCREASE;So;0;ON;;;;;N;;;;; 1D313;TETRAGRAM FOR PENETRATION;So;0;ON;;;;;N;;;;; 1D314;TETRAGRAM FOR REACH;So;0;ON;;;;;N;;;;; 1D315;TETRAGRAM FOR CONTACT;So;0;ON;;;;;N;;;;; 1D316;TETRAGRAM FOR HOLDING BACK;So;0;ON;;;;;N;;;;; 1D317;TETRAGRAM FOR WAITING;So;0;ON;;;;;N;;;;; 1D318;TETRAGRAM FOR FOLLOWING;So;0;ON;;;;;N;;;;; 1D319;TETRAGRAM FOR ADVANCE;So;0;ON;;;;;N;;;;; 1D31A;TETRAGRAM FOR RELEASE;So;0;ON;;;;;N;;;;; 1D31B;TETRAGRAM FOR RESISTANCE;So;0;ON;;;;;N;;;;; 1D31C;TETRAGRAM FOR EASE;So;0;ON;;;;;N;;;;; 1D31D;TETRAGRAM FOR JOY;So;0;ON;;;;;N;;;;; 1D31E;TETRAGRAM FOR CONTENTION;So;0;ON;;;;;N;;;;; 1D31F;TETRAGRAM FOR ENDEAVOUR;So;0;ON;;;;;N;;;;; 1D320;TETRAGRAM FOR DUTIES;So;0;ON;;;;;N;;;;; 1D321;TETRAGRAM FOR CHANGE;So;0;ON;;;;;N;;;;; 1D322;TETRAGRAM FOR DECISIVENESS;So;0;ON;;;;;N;;;;; 1D323;TETRAGRAM FOR BOLD RESOLUTION;So;0;ON;;;;;N;;;;; 1D324;TETRAGRAM FOR PACKING;So;0;ON;;;;;N;;;;; 1D325;TETRAGRAM FOR LEGION;So;0;ON;;;;;N;;;;; 1D326;TETRAGRAM FOR CLOSENESS;So;0;ON;;;;;N;;;;; 1D327;TETRAGRAM FOR KINSHIP;So;0;ON;;;;;N;;;;; 1D328;TETRAGRAM FOR GATHERING;So;0;ON;;;;;N;;;;; 1D329;TETRAGRAM FOR STRENGTH;So;0;ON;;;;;N;;;;; 1D32A;TETRAGRAM FOR PURITY;So;0;ON;;;;;N;;;;; 1D32B;TETRAGRAM FOR FULLNESS;So;0;ON;;;;;N;;;;; 1D32C;TETRAGRAM FOR RESIDENCE;So;0;ON;;;;;N;;;;; 1D32D;TETRAGRAM FOR LAW OR MODEL;So;0;ON;;;;;N;;;;; 1D32E;TETRAGRAM FOR RESPONSE;So;0;ON;;;;;N;;;;; 1D32F;TETRAGRAM FOR GOING TO MEET;So;0;ON;;;;;N;;;;; 1D330;TETRAGRAM FOR ENCOUNTERS;So;0;ON;;;;;N;;;;; 1D331;TETRAGRAM FOR STOVE;So;0;ON;;;;;N;;;;; 1D332;TETRAGRAM FOR GREATNESS;So;0;ON;;;;;N;;;;; 1D333;TETRAGRAM FOR ENLARGEMENT;So;0;ON;;;;;N;;;;; 1D334;TETRAGRAM FOR PATTERN;So;0;ON;;;;;N;;;;; 1D335;TETRAGRAM FOR RITUAL;So;0;ON;;;;;N;;;;; 1D336;TETRAGRAM FOR FLIGHT;So;0;ON;;;;;N;;;;; 1D337;TETRAGRAM FOR VASTNESS OR WASTING;So;0;ON;;;;;N;;;;; 1D338;TETRAGRAM FOR CONSTANCY;So;0;ON;;;;;N;;;;; 1D339;TETRAGRAM FOR MEASURE;So;0;ON;;;;;N;;;;; 1D33A;TETRAGRAM FOR ETERNITY;So;0;ON;;;;;N;;;;; 1D33B;TETRAGRAM FOR UNITY;So;0;ON;;;;;N;;;;; 1D33C;TETRAGRAM FOR DIMINISHMENT;So;0;ON;;;;;N;;;;; 1D33D;TETRAGRAM FOR CLOSED MOUTH;So;0;ON;;;;;N;;;;; 1D33E;TETRAGRAM FOR GUARDEDNESS;So;0;ON;;;;;N;;;;; 1D33F;TETRAGRAM FOR GATHERING IN;So;0;ON;;;;;N;;;;; 1D340;TETRAGRAM FOR MASSING;So;0;ON;;;;;N;;;;; 1D341;TETRAGRAM FOR ACCUMULATION;So;0;ON;;;;;N;;;;; 1D342;TETRAGRAM FOR EMBELLISHMENT;So;0;ON;;;;;N;;;;; 1D343;TETRAGRAM FOR DOUBT;So;0;ON;;;;;N;;;;; 1D344;TETRAGRAM FOR WATCH;So;0;ON;;;;;N;;;;; 1D345;TETRAGRAM FOR SINKING;So;0;ON;;;;;N;;;;; 1D346;TETRAGRAM FOR INNER;So;0;ON;;;;;N;;;;; 1D347;TETRAGRAM FOR DEPARTURE;So;0;ON;;;;;N;;;;; 1D348;TETRAGRAM FOR DARKENING;So;0;ON;;;;;N;;;;; 1D349;TETRAGRAM FOR DIMMING;So;0;ON;;;;;N;;;;; 1D34A;TETRAGRAM FOR EXHAUSTION;So;0;ON;;;;;N;;;;; 1D34B;TETRAGRAM FOR SEVERANCE;So;0;ON;;;;;N;;;;; 1D34C;TETRAGRAM FOR STOPPAGE;So;0;ON;;;;;N;;;;; 1D34D;TETRAGRAM FOR HARDNESS;So;0;ON;;;;;N;;;;; 1D34E;TETRAGRAM FOR COMPLETION;So;0;ON;;;;;N;;;;; 1D34F;TETRAGRAM FOR CLOSURE;So;0;ON;;;;;N;;;;; 1D350;TETRAGRAM FOR FAILURE;So;0;ON;;;;;N;;;;; 1D351;TETRAGRAM FOR AGGRAVATION;So;0;ON;;;;;N;;;;; 1D352;TETRAGRAM FOR COMPLIANCE;So;0;ON;;;;;N;;;;; 1D353;TETRAGRAM FOR ON THE VERGE;So;0;ON;;;;;N;;;;; 1D354;TETRAGRAM FOR DIFFICULTIES;So;0;ON;;;;;N;;;;; 1D355;TETRAGRAM FOR LABOURING;So;0;ON;;;;;N;;;;; 1D356;TETRAGRAM FOR FOSTERING;So;0;ON;;;;;N;;;;; 1D360;COUNTING ROD UNIT DIGIT ONE;No;0;L;;;;1;N;;;;; 1D361;COUNTING ROD UNIT DIGIT TWO;No;0;L;;;;2;N;;;;; 1D362;COUNTING ROD UNIT DIGIT THREE;No;0;L;;;;3;N;;;;; 1D363;COUNTING ROD UNIT DIGIT FOUR;No;0;L;;;;4;N;;;;; 1D364;COUNTING ROD UNIT DIGIT FIVE;No;0;L;;;;5;N;;;;; 1D365;COUNTING ROD UNIT DIGIT SIX;No;0;L;;;;6;N;;;;; 1D366;COUNTING ROD UNIT DIGIT SEVEN;No;0;L;;;;7;N;;;;; 1D367;COUNTING ROD UNIT DIGIT EIGHT;No;0;L;;;;8;N;;;;; 1D368;COUNTING ROD UNIT DIGIT NINE;No;0;L;;;;9;N;;;;; 1D369;COUNTING ROD TENS DIGIT ONE;No;0;L;;;;10;N;;;;; 1D36A;COUNTING ROD TENS DIGIT TWO;No;0;L;;;;20;N;;;;; 1D36B;COUNTING ROD TENS DIGIT THREE;No;0;L;;;;30;N;;;;; 1D36C;COUNTING ROD TENS DIGIT FOUR;No;0;L;;;;40;N;;;;; 1D36D;COUNTING ROD TENS DIGIT FIVE;No;0;L;;;;50;N;;;;; 1D36E;COUNTING ROD TENS DIGIT SIX;No;0;L;;;;60;N;;;;; 1D36F;COUNTING ROD TENS DIGIT SEVEN;No;0;L;;;;70;N;;;;; 1D370;COUNTING ROD TENS DIGIT EIGHT;No;0;L;;;;80;N;;;;; 1D371;COUNTING ROD TENS DIGIT NINE;No;0;L;;;;90;N;;;;; 1D400;MATHEMATICAL BOLD CAPITAL A;Lu;0;L; 0041;;;;N;;;;; 1D401;MATHEMATICAL BOLD CAPITAL B;Lu;0;L; 0042;;;;N;;;;; 1D402;MATHEMATICAL BOLD CAPITAL C;Lu;0;L; 0043;;;;N;;;;; 1D403;MATHEMATICAL BOLD CAPITAL D;Lu;0;L; 0044;;;;N;;;;; 1D404;MATHEMATICAL BOLD CAPITAL E;Lu;0;L; 0045;;;;N;;;;; 1D405;MATHEMATICAL BOLD CAPITAL F;Lu;0;L; 0046;;;;N;;;;; 1D406;MATHEMATICAL BOLD CAPITAL G;Lu;0;L; 0047;;;;N;;;;; 1D407;MATHEMATICAL BOLD CAPITAL H;Lu;0;L; 0048;;;;N;;;;; 1D408;MATHEMATICAL BOLD CAPITAL I;Lu;0;L; 0049;;;;N;;;;; 1D409;MATHEMATICAL BOLD CAPITAL J;Lu;0;L; 004A;;;;N;;;;; 1D40A;MATHEMATICAL BOLD CAPITAL K;Lu;0;L; 004B;;;;N;;;;; 1D40B;MATHEMATICAL BOLD CAPITAL L;Lu;0;L; 004C;;;;N;;;;; 1D40C;MATHEMATICAL BOLD CAPITAL M;Lu;0;L; 004D;;;;N;;;;; 1D40D;MATHEMATICAL BOLD CAPITAL N;Lu;0;L; 004E;;;;N;;;;; 1D40E;MATHEMATICAL BOLD CAPITAL O;Lu;0;L; 004F;;;;N;;;;; 1D40F;MATHEMATICAL BOLD CAPITAL P;Lu;0;L; 0050;;;;N;;;;; 1D410;MATHEMATICAL BOLD CAPITAL Q;Lu;0;L; 0051;;;;N;;;;; 1D411;MATHEMATICAL BOLD CAPITAL R;Lu;0;L; 0052;;;;N;;;;; 1D412;MATHEMATICAL BOLD CAPITAL S;Lu;0;L; 0053;;;;N;;;;; 1D413;MATHEMATICAL BOLD CAPITAL T;Lu;0;L; 0054;;;;N;;;;; 1D414;MATHEMATICAL BOLD CAPITAL U;Lu;0;L; 0055;;;;N;;;;; 1D415;MATHEMATICAL BOLD CAPITAL V;Lu;0;L; 0056;;;;N;;;;; 1D416;MATHEMATICAL BOLD CAPITAL W;Lu;0;L; 0057;;;;N;;;;; 1D417;MATHEMATICAL BOLD CAPITAL X;Lu;0;L; 0058;;;;N;;;;; 1D418;MATHEMATICAL BOLD CAPITAL Y;Lu;0;L; 0059;;;;N;;;;; 1D419;MATHEMATICAL BOLD CAPITAL Z;Lu;0;L; 005A;;;;N;;;;; 1D41A;MATHEMATICAL BOLD SMALL A;Ll;0;L; 0061;;;;N;;;;; 1D41B;MATHEMATICAL BOLD SMALL B;Ll;0;L; 0062;;;;N;;;;; 1D41C;MATHEMATICAL BOLD SMALL C;Ll;0;L; 0063;;;;N;;;;; 1D41D;MATHEMATICAL BOLD SMALL D;Ll;0;L; 0064;;;;N;;;;; 1D41E;MATHEMATICAL BOLD SMALL E;Ll;0;L; 0065;;;;N;;;;; 1D41F;MATHEMATICAL BOLD SMALL F;Ll;0;L; 0066;;;;N;;;;; 1D420;MATHEMATICAL BOLD SMALL G;Ll;0;L; 0067;;;;N;;;;; 1D421;MATHEMATICAL BOLD SMALL H;Ll;0;L; 0068;;;;N;;;;; 1D422;MATHEMATICAL BOLD SMALL I;Ll;0;L; 0069;;;;N;;;;; 1D423;MATHEMATICAL BOLD SMALL J;Ll;0;L; 006A;;;;N;;;;; 1D424;MATHEMATICAL BOLD SMALL K;Ll;0;L; 006B;;;;N;;;;; 1D425;MATHEMATICAL BOLD SMALL L;Ll;0;L; 006C;;;;N;;;;; 1D426;MATHEMATICAL BOLD SMALL M;Ll;0;L; 006D;;;;N;;;;; 1D427;MATHEMATICAL BOLD SMALL N;Ll;0;L; 006E;;;;N;;;;; 1D428;MATHEMATICAL BOLD SMALL O;Ll;0;L; 006F;;;;N;;;;; 1D429;MATHEMATICAL BOLD SMALL P;Ll;0;L; 0070;;;;N;;;;; 1D42A;MATHEMATICAL BOLD SMALL Q;Ll;0;L; 0071;;;;N;;;;; 1D42B;MATHEMATICAL BOLD SMALL R;Ll;0;L; 0072;;;;N;;;;; 1D42C;MATHEMATICAL BOLD SMALL S;Ll;0;L; 0073;;;;N;;;;; 1D42D;MATHEMATICAL BOLD SMALL T;Ll;0;L; 0074;;;;N;;;;; 1D42E;MATHEMATICAL BOLD SMALL U;Ll;0;L; 0075;;;;N;;;;; 1D42F;MATHEMATICAL BOLD SMALL V;Ll;0;L; 0076;;;;N;;;;; 1D430;MATHEMATICAL BOLD SMALL W;Ll;0;L; 0077;;;;N;;;;; 1D431;MATHEMATICAL BOLD SMALL X;Ll;0;L; 0078;;;;N;;;;; 1D432;MATHEMATICAL BOLD SMALL Y;Ll;0;L; 0079;;;;N;;;;; 1D433;MATHEMATICAL BOLD SMALL Z;Ll;0;L; 007A;;;;N;;;;; 1D434;MATHEMATICAL ITALIC CAPITAL A;Lu;0;L; 0041;;;;N;;;;; 1D435;MATHEMATICAL ITALIC CAPITAL B;Lu;0;L; 0042;;;;N;;;;; 1D436;MATHEMATICAL ITALIC CAPITAL C;Lu;0;L; 0043;;;;N;;;;; 1D437;MATHEMATICAL ITALIC CAPITAL D;Lu;0;L; 0044;;;;N;;;;; 1D438;MATHEMATICAL ITALIC CAPITAL E;Lu;0;L; 0045;;;;N;;;;; 1D439;MATHEMATICAL ITALIC CAPITAL F;Lu;0;L; 0046;;;;N;;;;; 1D43A;MATHEMATICAL ITALIC CAPITAL G;Lu;0;L; 0047;;;;N;;;;; 1D43B;MATHEMATICAL ITALIC CAPITAL H;Lu;0;L; 0048;;;;N;;;;; 1D43C;MATHEMATICAL ITALIC CAPITAL I;Lu;0;L; 0049;;;;N;;;;; 1D43D;MATHEMATICAL ITALIC CAPITAL J;Lu;0;L; 004A;;;;N;;;;; 1D43E;MATHEMATICAL ITALIC CAPITAL K;Lu;0;L; 004B;;;;N;;;;; 1D43F;MATHEMATICAL ITALIC CAPITAL L;Lu;0;L; 004C;;;;N;;;;; 1D440;MATHEMATICAL ITALIC CAPITAL M;Lu;0;L; 004D;;;;N;;;;; 1D441;MATHEMATICAL ITALIC CAPITAL N;Lu;0;L; 004E;;;;N;;;;; 1D442;MATHEMATICAL ITALIC CAPITAL O;Lu;0;L; 004F;;;;N;;;;; 1D443;MATHEMATICAL ITALIC CAPITAL P;Lu;0;L; 0050;;;;N;;;;; 1D444;MATHEMATICAL ITALIC CAPITAL Q;Lu;0;L; 0051;;;;N;;;;; 1D445;MATHEMATICAL ITALIC CAPITAL R;Lu;0;L; 0052;;;;N;;;;; 1D446;MATHEMATICAL ITALIC CAPITAL S;Lu;0;L; 0053;;;;N;;;;; 1D447;MATHEMATICAL ITALIC CAPITAL T;Lu;0;L; 0054;;;;N;;;;; 1D448;MATHEMATICAL ITALIC CAPITAL U;Lu;0;L; 0055;;;;N;;;;; 1D449;MATHEMATICAL ITALIC CAPITAL V;Lu;0;L; 0056;;;;N;;;;; 1D44A;MATHEMATICAL ITALIC CAPITAL W;Lu;0;L; 0057;;;;N;;;;; 1D44B;MATHEMATICAL ITALIC CAPITAL X;Lu;0;L; 0058;;;;N;;;;; 1D44C;MATHEMATICAL ITALIC CAPITAL Y;Lu;0;L; 0059;;;;N;;;;; 1D44D;MATHEMATICAL ITALIC CAPITAL Z;Lu;0;L; 005A;;;;N;;;;; 1D44E;MATHEMATICAL ITALIC SMALL A;Ll;0;L; 0061;;;;N;;;;; 1D44F;MATHEMATICAL ITALIC SMALL B;Ll;0;L; 0062;;;;N;;;;; 1D450;MATHEMATICAL ITALIC SMALL C;Ll;0;L; 0063;;;;N;;;;; 1D451;MATHEMATICAL ITALIC SMALL D;Ll;0;L; 0064;;;;N;;;;; 1D452;MATHEMATICAL ITALIC SMALL E;Ll;0;L; 0065;;;;N;;;;; 1D453;MATHEMATICAL ITALIC SMALL F;Ll;0;L; 0066;;;;N;;;;; 1D454;MATHEMATICAL ITALIC SMALL G;Ll;0;L; 0067;;;;N;;;;; 1D456;MATHEMATICAL ITALIC SMALL I;Ll;0;L; 0069;;;;N;;;;; 1D457;MATHEMATICAL ITALIC SMALL J;Ll;0;L; 006A;;;;N;;;;; 1D458;MATHEMATICAL ITALIC SMALL K;Ll;0;L; 006B;;;;N;;;;; 1D459;MATHEMATICAL ITALIC SMALL L;Ll;0;L; 006C;;;;N;;;;; 1D45A;MATHEMATICAL ITALIC SMALL M;Ll;0;L; 006D;;;;N;;;;; 1D45B;MATHEMATICAL ITALIC SMALL N;Ll;0;L; 006E;;;;N;;;;; 1D45C;MATHEMATICAL ITALIC SMALL O;Ll;0;L; 006F;;;;N;;;;; 1D45D;MATHEMATICAL ITALIC SMALL P;Ll;0;L; 0070;;;;N;;;;; 1D45E;MATHEMATICAL ITALIC SMALL Q;Ll;0;L; 0071;;;;N;;;;; 1D45F;MATHEMATICAL ITALIC SMALL R;Ll;0;L; 0072;;;;N;;;;; 1D460;MATHEMATICAL ITALIC SMALL S;Ll;0;L; 0073;;;;N;;;;; 1D461;MATHEMATICAL ITALIC SMALL T;Ll;0;L; 0074;;;;N;;;;; 1D462;MATHEMATICAL ITALIC SMALL U;Ll;0;L; 0075;;;;N;;;;; 1D463;MATHEMATICAL ITALIC SMALL V;Ll;0;L; 0076;;;;N;;;;; 1D464;MATHEMATICAL ITALIC SMALL W;Ll;0;L; 0077;;;;N;;;;; 1D465;MATHEMATICAL ITALIC SMALL X;Ll;0;L; 0078;;;;N;;;;; 1D466;MATHEMATICAL ITALIC SMALL Y;Ll;0;L; 0079;;;;N;;;;; 1D467;MATHEMATICAL ITALIC SMALL Z;Ll;0;L; 007A;;;;N;;;;; 1D468;MATHEMATICAL BOLD ITALIC CAPITAL A;Lu;0;L; 0041;;;;N;;;;; 1D469;MATHEMATICAL BOLD ITALIC CAPITAL B;Lu;0;L; 0042;;;;N;;;;; 1D46A;MATHEMATICAL BOLD ITALIC CAPITAL C;Lu;0;L; 0043;;;;N;;;;; 1D46B;MATHEMATICAL BOLD ITALIC CAPITAL D;Lu;0;L; 0044;;;;N;;;;; 1D46C;MATHEMATICAL BOLD ITALIC CAPITAL E;Lu;0;L; 0045;;;;N;;;;; 1D46D;MATHEMATICAL BOLD ITALIC CAPITAL F;Lu;0;L; 0046;;;;N;;;;; 1D46E;MATHEMATICAL BOLD ITALIC CAPITAL G;Lu;0;L; 0047;;;;N;;;;; 1D46F;MATHEMATICAL BOLD ITALIC CAPITAL H;Lu;0;L; 0048;;;;N;;;;; 1D470;MATHEMATICAL BOLD ITALIC CAPITAL I;Lu;0;L; 0049;;;;N;;;;; 1D471;MATHEMATICAL BOLD ITALIC CAPITAL J;Lu;0;L; 004A;;;;N;;;;; 1D472;MATHEMATICAL BOLD ITALIC CAPITAL K;Lu;0;L; 004B;;;;N;;;;; 1D473;MATHEMATICAL BOLD ITALIC CAPITAL L;Lu;0;L; 004C;;;;N;;;;; 1D474;MATHEMATICAL BOLD ITALIC CAPITAL M;Lu;0;L; 004D;;;;N;;;;; 1D475;MATHEMATICAL BOLD ITALIC CAPITAL N;Lu;0;L; 004E;;;;N;;;;; 1D476;MATHEMATICAL BOLD ITALIC CAPITAL O;Lu;0;L; 004F;;;;N;;;;; 1D477;MATHEMATICAL BOLD ITALIC CAPITAL P;Lu;0;L; 0050;;;;N;;;;; 1D478;MATHEMATICAL BOLD ITALIC CAPITAL Q;Lu;0;L; 0051;;;;N;;;;; 1D479;MATHEMATICAL BOLD ITALIC CAPITAL R;Lu;0;L; 0052;;;;N;;;;; 1D47A;MATHEMATICAL BOLD ITALIC CAPITAL S;Lu;0;L; 0053;;;;N;;;;; 1D47B;MATHEMATICAL BOLD ITALIC CAPITAL T;Lu;0;L; 0054;;;;N;;;;; 1D47C;MATHEMATICAL BOLD ITALIC CAPITAL U;Lu;0;L; 0055;;;;N;;;;; 1D47D;MATHEMATICAL BOLD ITALIC CAPITAL V;Lu;0;L; 0056;;;;N;;;;; 1D47E;MATHEMATICAL BOLD ITALIC CAPITAL W;Lu;0;L; 0057;;;;N;;;;; 1D47F;MATHEMATICAL BOLD ITALIC CAPITAL X;Lu;0;L; 0058;;;;N;;;;; 1D480;MATHEMATICAL BOLD ITALIC CAPITAL Y;Lu;0;L; 0059;;;;N;;;;; 1D481;MATHEMATICAL BOLD ITALIC CAPITAL Z;Lu;0;L; 005A;;;;N;;;;; 1D482;MATHEMATICAL BOLD ITALIC SMALL A;Ll;0;L; 0061;;;;N;;;;; 1D483;MATHEMATICAL BOLD ITALIC SMALL B;Ll;0;L; 0062;;;;N;;;;; 1D484;MATHEMATICAL BOLD ITALIC SMALL C;Ll;0;L; 0063;;;;N;;;;; 1D485;MATHEMATICAL BOLD ITALIC SMALL D;Ll;0;L; 0064;;;;N;;;;; 1D486;MATHEMATICAL BOLD ITALIC SMALL E;Ll;0;L; 0065;;;;N;;;;; 1D487;MATHEMATICAL BOLD ITALIC SMALL F;Ll;0;L; 0066;;;;N;;;;; 1D488;MATHEMATICAL BOLD ITALIC SMALL G;Ll;0;L; 0067;;;;N;;;;; 1D489;MATHEMATICAL BOLD ITALIC SMALL H;Ll;0;L; 0068;;;;N;;;;; 1D48A;MATHEMATICAL BOLD ITALIC SMALL I;Ll;0;L; 0069;;;;N;;;;; 1D48B;MATHEMATICAL BOLD ITALIC SMALL J;Ll;0;L; 006A;;;;N;;;;; 1D48C;MATHEMATICAL BOLD ITALIC SMALL K;Ll;0;L; 006B;;;;N;;;;; 1D48D;MATHEMATICAL BOLD ITALIC SMALL L;Ll;0;L; 006C;;;;N;;;;; 1D48E;MATHEMATICAL BOLD ITALIC SMALL M;Ll;0;L; 006D;;;;N;;;;; 1D48F;MATHEMATICAL BOLD ITALIC SMALL N;Ll;0;L; 006E;;;;N;;;;; 1D490;MATHEMATICAL BOLD ITALIC SMALL O;Ll;0;L; 006F;;;;N;;;;; 1D491;MATHEMATICAL BOLD ITALIC SMALL P;Ll;0;L; 0070;;;;N;;;;; 1D492;MATHEMATICAL BOLD ITALIC SMALL Q;Ll;0;L; 0071;;;;N;;;;; 1D493;MATHEMATICAL BOLD ITALIC SMALL R;Ll;0;L; 0072;;;;N;;;;; 1D494;MATHEMATICAL BOLD ITALIC SMALL S;Ll;0;L; 0073;;;;N;;;;; 1D495;MATHEMATICAL BOLD ITALIC SMALL T;Ll;0;L; 0074;;;;N;;;;; 1D496;MATHEMATICAL BOLD ITALIC SMALL U;Ll;0;L; 0075;;;;N;;;;; 1D497;MATHEMATICAL BOLD ITALIC SMALL V;Ll;0;L; 0076;;;;N;;;;; 1D498;MATHEMATICAL BOLD ITALIC SMALL W;Ll;0;L; 0077;;;;N;;;;; 1D499;MATHEMATICAL BOLD ITALIC SMALL X;Ll;0;L; 0078;;;;N;;;;; 1D49A;MATHEMATICAL BOLD ITALIC SMALL Y;Ll;0;L; 0079;;;;N;;;;; 1D49B;MATHEMATICAL BOLD ITALIC SMALL Z;Ll;0;L; 007A;;;;N;;;;; 1D49C;MATHEMATICAL SCRIPT CAPITAL A;Lu;0;L; 0041;;;;N;;;;; 1D49E;MATHEMATICAL SCRIPT CAPITAL C;Lu;0;L; 0043;;;;N;;;;; 1D49F;MATHEMATICAL SCRIPT CAPITAL D;Lu;0;L; 0044;;;;N;;;;; 1D4A2;MATHEMATICAL SCRIPT CAPITAL G;Lu;0;L; 0047;;;;N;;;;; 1D4A5;MATHEMATICAL SCRIPT CAPITAL J;Lu;0;L; 004A;;;;N;;;;; 1D4A6;MATHEMATICAL SCRIPT CAPITAL K;Lu;0;L; 004B;;;;N;;;;; 1D4A9;MATHEMATICAL SCRIPT CAPITAL N;Lu;0;L; 004E;;;;N;;;;; 1D4AA;MATHEMATICAL SCRIPT CAPITAL O;Lu;0;L; 004F;;;;N;;;;; 1D4AB;MATHEMATICAL SCRIPT CAPITAL P;Lu;0;L; 0050;;;;N;;;;; 1D4AC;MATHEMATICAL SCRIPT CAPITAL Q;Lu;0;L; 0051;;;;N;;;;; 1D4AE;MATHEMATICAL SCRIPT CAPITAL S;Lu;0;L; 0053;;;;N;;;;; 1D4AF;MATHEMATICAL SCRIPT CAPITAL T;Lu;0;L; 0054;;;;N;;;;; 1D4B0;MATHEMATICAL SCRIPT CAPITAL U;Lu;0;L; 0055;;;;N;;;;; 1D4B1;MATHEMATICAL SCRIPT CAPITAL V;Lu;0;L; 0056;;;;N;;;;; 1D4B2;MATHEMATICAL SCRIPT CAPITAL W;Lu;0;L; 0057;;;;N;;;;; 1D4B3;MATHEMATICAL SCRIPT CAPITAL X;Lu;0;L; 0058;;;;N;;;;; 1D4B4;MATHEMATICAL SCRIPT CAPITAL Y;Lu;0;L; 0059;;;;N;;;;; 1D4B5;MATHEMATICAL SCRIPT CAPITAL Z;Lu;0;L; 005A;;;;N;;;;; 1D4B6;MATHEMATICAL SCRIPT SMALL A;Ll;0;L; 0061;;;;N;;;;; 1D4B7;MATHEMATICAL SCRIPT SMALL B;Ll;0;L; 0062;;;;N;;;;; 1D4B8;MATHEMATICAL SCRIPT SMALL C;Ll;0;L; 0063;;;;N;;;;; 1D4B9;MATHEMATICAL SCRIPT SMALL D;Ll;0;L; 0064;;;;N;;;;; 1D4BB;MATHEMATICAL SCRIPT SMALL F;Ll;0;L; 0066;;;;N;;;;; 1D4BD;MATHEMATICAL SCRIPT SMALL H;Ll;0;L; 0068;;;;N;;;;; 1D4BE;MATHEMATICAL SCRIPT SMALL I;Ll;0;L; 0069;;;;N;;;;; 1D4BF;MATHEMATICAL SCRIPT SMALL J;Ll;0;L; 006A;;;;N;;;;; 1D4C0;MATHEMATICAL SCRIPT SMALL K;Ll;0;L; 006B;;;;N;;;;; 1D4C1;MATHEMATICAL SCRIPT SMALL L;Ll;0;L; 006C;;;;N;;;;; 1D4C2;MATHEMATICAL SCRIPT SMALL M;Ll;0;L; 006D;;;;N;;;;; 1D4C3;MATHEMATICAL SCRIPT SMALL N;Ll;0;L; 006E;;;;N;;;;; 1D4C5;MATHEMATICAL SCRIPT SMALL P;Ll;0;L; 0070;;;;N;;;;; 1D4C6;MATHEMATICAL SCRIPT SMALL Q;Ll;0;L; 0071;;;;N;;;;; 1D4C7;MATHEMATICAL SCRIPT SMALL R;Ll;0;L; 0072;;;;N;;;;; 1D4C8;MATHEMATICAL SCRIPT SMALL S;Ll;0;L; 0073;;;;N;;;;; 1D4C9;MATHEMATICAL SCRIPT SMALL T;Ll;0;L; 0074;;;;N;;;;; 1D4CA;MATHEMATICAL SCRIPT SMALL U;Ll;0;L; 0075;;;;N;;;;; 1D4CB;MATHEMATICAL SCRIPT SMALL V;Ll;0;L; 0076;;;;N;;;;; 1D4CC;MATHEMATICAL SCRIPT SMALL W;Ll;0;L; 0077;;;;N;;;;; 1D4CD;MATHEMATICAL SCRIPT SMALL X;Ll;0;L; 0078;;;;N;;;;; 1D4CE;MATHEMATICAL SCRIPT SMALL Y;Ll;0;L; 0079;;;;N;;;;; 1D4CF;MATHEMATICAL SCRIPT SMALL Z;Ll;0;L; 007A;;;;N;;;;; 1D4D0;MATHEMATICAL BOLD SCRIPT CAPITAL A;Lu;0;L; 0041;;;;N;;;;; 1D4D1;MATHEMATICAL BOLD SCRIPT CAPITAL B;Lu;0;L; 0042;;;;N;;;;; 1D4D2;MATHEMATICAL BOLD SCRIPT CAPITAL C;Lu;0;L; 0043;;;;N;;;;; 1D4D3;MATHEMATICAL BOLD SCRIPT CAPITAL D;Lu;0;L; 0044;;;;N;;;;; 1D4D4;MATHEMATICAL BOLD SCRIPT CAPITAL E;Lu;0;L; 0045;;;;N;;;;; 1D4D5;MATHEMATICAL BOLD SCRIPT CAPITAL F;Lu;0;L; 0046;;;;N;;;;; 1D4D6;MATHEMATICAL BOLD SCRIPT CAPITAL G;Lu;0;L; 0047;;;;N;;;;; 1D4D7;MATHEMATICAL BOLD SCRIPT CAPITAL H;Lu;0;L; 0048;;;;N;;;;; 1D4D8;MATHEMATICAL BOLD SCRIPT CAPITAL I;Lu;0;L; 0049;;;;N;;;;; 1D4D9;MATHEMATICAL BOLD SCRIPT CAPITAL J;Lu;0;L; 004A;;;;N;;;;; 1D4DA;MATHEMATICAL BOLD SCRIPT CAPITAL K;Lu;0;L; 004B;;;;N;;;;; 1D4DB;MATHEMATICAL BOLD SCRIPT CAPITAL L;Lu;0;L; 004C;;;;N;;;;; 1D4DC;MATHEMATICAL BOLD SCRIPT CAPITAL M;Lu;0;L; 004D;;;;N;;;;; 1D4DD;MATHEMATICAL BOLD SCRIPT CAPITAL N;Lu;0;L; 004E;;;;N;;;;; 1D4DE;MATHEMATICAL BOLD SCRIPT CAPITAL O;Lu;0;L; 004F;;;;N;;;;; 1D4DF;MATHEMATICAL BOLD SCRIPT CAPITAL P;Lu;0;L; 0050;;;;N;;;;; 1D4E0;MATHEMATICAL BOLD SCRIPT CAPITAL Q;Lu;0;L; 0051;;;;N;;;;; 1D4E1;MATHEMATICAL BOLD SCRIPT CAPITAL R;Lu;0;L; 0052;;;;N;;;;; 1D4E2;MATHEMATICAL BOLD SCRIPT CAPITAL S;Lu;0;L; 0053;;;;N;;;;; 1D4E3;MATHEMATICAL BOLD SCRIPT CAPITAL T;Lu;0;L; 0054;;;;N;;;;; 1D4E4;MATHEMATICAL BOLD SCRIPT CAPITAL U;Lu;0;L; 0055;;;;N;;;;; 1D4E5;MATHEMATICAL BOLD SCRIPT CAPITAL V;Lu;0;L; 0056;;;;N;;;;; 1D4E6;MATHEMATICAL BOLD SCRIPT CAPITAL W;Lu;0;L; 0057;;;;N;;;;; 1D4E7;MATHEMATICAL BOLD SCRIPT CAPITAL X;Lu;0;L; 0058;;;;N;;;;; 1D4E8;MATHEMATICAL BOLD SCRIPT CAPITAL Y;Lu;0;L; 0059;;;;N;;;;; 1D4E9;MATHEMATICAL BOLD SCRIPT CAPITAL Z;Lu;0;L; 005A;;;;N;;;;; 1D4EA;MATHEMATICAL BOLD SCRIPT SMALL A;Ll;0;L; 0061;;;;N;;;;; 1D4EB;MATHEMATICAL BOLD SCRIPT SMALL B;Ll;0;L; 0062;;;;N;;;;; 1D4EC;MATHEMATICAL BOLD SCRIPT SMALL C;Ll;0;L; 0063;;;;N;;;;; 1D4ED;MATHEMATICAL BOLD SCRIPT SMALL D;Ll;0;L; 0064;;;;N;;;;; 1D4EE;MATHEMATICAL BOLD SCRIPT SMALL E;Ll;0;L; 0065;;;;N;;;;; 1D4EF;MATHEMATICAL BOLD SCRIPT SMALL F;Ll;0;L; 0066;;;;N;;;;; 1D4F0;MATHEMATICAL BOLD SCRIPT SMALL G;Ll;0;L; 0067;;;;N;;;;; 1D4F1;MATHEMATICAL BOLD SCRIPT SMALL H;Ll;0;L; 0068;;;;N;;;;; 1D4F2;MATHEMATICAL BOLD SCRIPT SMALL I;Ll;0;L; 0069;;;;N;;;;; 1D4F3;MATHEMATICAL BOLD SCRIPT SMALL J;Ll;0;L; 006A;;;;N;;;;; 1D4F4;MATHEMATICAL BOLD SCRIPT SMALL K;Ll;0;L; 006B;;;;N;;;;; 1D4F5;MATHEMATICAL BOLD SCRIPT SMALL L;Ll;0;L; 006C;;;;N;;;;; 1D4F6;MATHEMATICAL BOLD SCRIPT SMALL M;Ll;0;L; 006D;;;;N;;;;; 1D4F7;MATHEMATICAL BOLD SCRIPT SMALL N;Ll;0;L; 006E;;;;N;;;;; 1D4F8;MATHEMATICAL BOLD SCRIPT SMALL O;Ll;0;L; 006F;;;;N;;;;; 1D4F9;MATHEMATICAL BOLD SCRIPT SMALL P;Ll;0;L; 0070;;;;N;;;;; 1D4FA;MATHEMATICAL BOLD SCRIPT SMALL Q;Ll;0;L; 0071;;;;N;;;;; 1D4FB;MATHEMATICAL BOLD SCRIPT SMALL R;Ll;0;L; 0072;;;;N;;;;; 1D4FC;MATHEMATICAL BOLD SCRIPT SMALL S;Ll;0;L; 0073;;;;N;;;;; 1D4FD;MATHEMATICAL BOLD SCRIPT SMALL T;Ll;0;L; 0074;;;;N;;;;; 1D4FE;MATHEMATICAL BOLD SCRIPT SMALL U;Ll;0;L; 0075;;;;N;;;;; 1D4FF;MATHEMATICAL BOLD SCRIPT SMALL V;Ll;0;L; 0076;;;;N;;;;; 1D500;MATHEMATICAL BOLD SCRIPT SMALL W;Ll;0;L; 0077;;;;N;;;;; 1D501;MATHEMATICAL BOLD SCRIPT SMALL X;Ll;0;L; 0078;;;;N;;;;; 1D502;MATHEMATICAL BOLD SCRIPT SMALL Y;Ll;0;L; 0079;;;;N;;;;; 1D503;MATHEMATICAL BOLD SCRIPT SMALL Z;Ll;0;L; 007A;;;;N;;;;; 1D504;MATHEMATICAL FRAKTUR CAPITAL A;Lu;0;L; 0041;;;;N;;;;; 1D505;MATHEMATICAL FRAKTUR CAPITAL B;Lu;0;L; 0042;;;;N;;;;; 1D507;MATHEMATICAL FRAKTUR CAPITAL D;Lu;0;L; 0044;;;;N;;;;; 1D508;MATHEMATICAL FRAKTUR CAPITAL E;Lu;0;L; 0045;;;;N;;;;; 1D509;MATHEMATICAL FRAKTUR CAPITAL F;Lu;0;L; 0046;;;;N;;;;; 1D50A;MATHEMATICAL FRAKTUR CAPITAL G;Lu;0;L; 0047;;;;N;;;;; 1D50D;MATHEMATICAL FRAKTUR CAPITAL J;Lu;0;L; 004A;;;;N;;;;; 1D50E;MATHEMATICAL FRAKTUR CAPITAL K;Lu;0;L; 004B;;;;N;;;;; 1D50F;MATHEMATICAL FRAKTUR CAPITAL L;Lu;0;L; 004C;;;;N;;;;; 1D510;MATHEMATICAL FRAKTUR CAPITAL M;Lu;0;L; 004D;;;;N;;;;; 1D511;MATHEMATICAL FRAKTUR CAPITAL N;Lu;0;L; 004E;;;;N;;;;; 1D512;MATHEMATICAL FRAKTUR CAPITAL O;Lu;0;L; 004F;;;;N;;;;; 1D513;MATHEMATICAL FRAKTUR CAPITAL P;Lu;0;L; 0050;;;;N;;;;; 1D514;MATHEMATICAL FRAKTUR CAPITAL Q;Lu;0;L; 0051;;;;N;;;;; 1D516;MATHEMATICAL FRAKTUR CAPITAL S;Lu;0;L; 0053;;;;N;;;;; 1D517;MATHEMATICAL FRAKTUR CAPITAL T;Lu;0;L; 0054;;;;N;;;;; 1D518;MATHEMATICAL FRAKTUR CAPITAL U;Lu;0;L; 0055;;;;N;;;;; 1D519;MATHEMATICAL FRAKTUR CAPITAL V;Lu;0;L; 0056;;;;N;;;;; 1D51A;MATHEMATICAL FRAKTUR CAPITAL W;Lu;0;L; 0057;;;;N;;;;; 1D51B;MATHEMATICAL FRAKTUR CAPITAL X;Lu;0;L; 0058;;;;N;;;;; 1D51C;MATHEMATICAL FRAKTUR CAPITAL Y;Lu;0;L; 0059;;;;N;;;;; 1D51E;MATHEMATICAL FRAKTUR SMALL A;Ll;0;L; 0061;;;;N;;;;; 1D51F;MATHEMATICAL FRAKTUR SMALL B;Ll;0;L; 0062;;;;N;;;;; 1D520;MATHEMATICAL FRAKTUR SMALL C;Ll;0;L; 0063;;;;N;;;;; 1D521;MATHEMATICAL FRAKTUR SMALL D;Ll;0;L; 0064;;;;N;;;;; 1D522;MATHEMATICAL FRAKTUR SMALL E;Ll;0;L; 0065;;;;N;;;;; 1D523;MATHEMATICAL FRAKTUR SMALL F;Ll;0;L; 0066;;;;N;;;;; 1D524;MATHEMATICAL FRAKTUR SMALL G;Ll;0;L; 0067;;;;N;;;;; 1D525;MATHEMATICAL FRAKTUR SMALL H;Ll;0;L; 0068;;;;N;;;;; 1D526;MATHEMATICAL FRAKTUR SMALL I;Ll;0;L; 0069;;;;N;;;;; 1D527;MATHEMATICAL FRAKTUR SMALL J;Ll;0;L; 006A;;;;N;;;;; 1D528;MATHEMATICAL FRAKTUR SMALL K;Ll;0;L; 006B;;;;N;;;;; 1D529;MATHEMATICAL FRAKTUR SMALL L;Ll;0;L; 006C;;;;N;;;;; 1D52A;MATHEMATICAL FRAKTUR SMALL M;Ll;0;L; 006D;;;;N;;;;; 1D52B;MATHEMATICAL FRAKTUR SMALL N;Ll;0;L; 006E;;;;N;;;;; 1D52C;MATHEMATICAL FRAKTUR SMALL O;Ll;0;L; 006F;;;;N;;;;; 1D52D;MATHEMATICAL FRAKTUR SMALL P;Ll;0;L; 0070;;;;N;;;;; 1D52E;MATHEMATICAL FRAKTUR SMALL Q;Ll;0;L; 0071;;;;N;;;;; 1D52F;MATHEMATICAL FRAKTUR SMALL R;Ll;0;L; 0072;;;;N;;;;; 1D530;MATHEMATICAL FRAKTUR SMALL S;Ll;0;L; 0073;;;;N;;;;; 1D531;MATHEMATICAL FRAKTUR SMALL T;Ll;0;L; 0074;;;;N;;;;; 1D532;MATHEMATICAL FRAKTUR SMALL U;Ll;0;L; 0075;;;;N;;;;; 1D533;MATHEMATICAL FRAKTUR SMALL V;Ll;0;L; 0076;;;;N;;;;; 1D534;MATHEMATICAL FRAKTUR SMALL W;Ll;0;L; 0077;;;;N;;;;; 1D535;MATHEMATICAL FRAKTUR SMALL X;Ll;0;L; 0078;;;;N;;;;; 1D536;MATHEMATICAL FRAKTUR SMALL Y;Ll;0;L; 0079;;;;N;;;;; 1D537;MATHEMATICAL FRAKTUR SMALL Z;Ll;0;L; 007A;;;;N;;;;; 1D538;MATHEMATICAL DOUBLE-STRUCK CAPITAL A;Lu;0;L; 0041;;;;N;;;;; 1D539;MATHEMATICAL DOUBLE-STRUCK CAPITAL B;Lu;0;L; 0042;;;;N;;;;; 1D53B;MATHEMATICAL DOUBLE-STRUCK CAPITAL D;Lu;0;L; 0044;;;;N;;;;; 1D53C;MATHEMATICAL DOUBLE-STRUCK CAPITAL E;Lu;0;L; 0045;;;;N;;;;; 1D53D;MATHEMATICAL DOUBLE-STRUCK CAPITAL F;Lu;0;L; 0046;;;;N;;;;; 1D53E;MATHEMATICAL DOUBLE-STRUCK CAPITAL G;Lu;0;L; 0047;;;;N;;;;; 1D540;MATHEMATICAL DOUBLE-STRUCK CAPITAL I;Lu;0;L; 0049;;;;N;;;;; 1D541;MATHEMATICAL DOUBLE-STRUCK CAPITAL J;Lu;0;L; 004A;;;;N;;;;; 1D542;MATHEMATICAL DOUBLE-STRUCK CAPITAL K;Lu;0;L; 004B;;;;N;;;;; 1D543;MATHEMATICAL DOUBLE-STRUCK CAPITAL L;Lu;0;L; 004C;;;;N;;;;; 1D544;MATHEMATICAL DOUBLE-STRUCK CAPITAL M;Lu;0;L; 004D;;;;N;;;;; 1D546;MATHEMATICAL DOUBLE-STRUCK CAPITAL O;Lu;0;L; 004F;;;;N;;;;; 1D54A;MATHEMATICAL DOUBLE-STRUCK CAPITAL S;Lu;0;L; 0053;;;;N;;;;; 1D54B;MATHEMATICAL DOUBLE-STRUCK CAPITAL T;Lu;0;L; 0054;;;;N;;;;; 1D54C;MATHEMATICAL DOUBLE-STRUCK CAPITAL U;Lu;0;L; 0055;;;;N;;;;; 1D54D;MATHEMATICAL DOUBLE-STRUCK CAPITAL V;Lu;0;L; 0056;;;;N;;;;; 1D54E;MATHEMATICAL DOUBLE-STRUCK CAPITAL W;Lu;0;L; 0057;;;;N;;;;; 1D54F;MATHEMATICAL DOUBLE-STRUCK CAPITAL X;Lu;0;L; 0058;;;;N;;;;; 1D550;MATHEMATICAL DOUBLE-STRUCK CAPITAL Y;Lu;0;L; 0059;;;;N;;;;; 1D552;MATHEMATICAL DOUBLE-STRUCK SMALL A;Ll;0;L; 0061;;;;N;;;;; 1D553;MATHEMATICAL DOUBLE-STRUCK SMALL B;Ll;0;L; 0062;;;;N;;;;; 1D554;MATHEMATICAL DOUBLE-STRUCK SMALL C;Ll;0;L; 0063;;;;N;;;;; 1D555;MATHEMATICAL DOUBLE-STRUCK SMALL D;Ll;0;L; 0064;;;;N;;;;; 1D556;MATHEMATICAL DOUBLE-STRUCK SMALL E;Ll;0;L; 0065;;;;N;;;;; 1D557;MATHEMATICAL DOUBLE-STRUCK SMALL F;Ll;0;L; 0066;;;;N;;;;; 1D558;MATHEMATICAL DOUBLE-STRUCK SMALL G;Ll;0;L; 0067;;;;N;;;;; 1D559;MATHEMATICAL DOUBLE-STRUCK SMALL H;Ll;0;L; 0068;;;;N;;;;; 1D55A;MATHEMATICAL DOUBLE-STRUCK SMALL I;Ll;0;L; 0069;;;;N;;;;; 1D55B;MATHEMATICAL DOUBLE-STRUCK SMALL J;Ll;0;L; 006A;;;;N;;;;; 1D55C;MATHEMATICAL DOUBLE-STRUCK SMALL K;Ll;0;L; 006B;;;;N;;;;; 1D55D;MATHEMATICAL DOUBLE-STRUCK SMALL L;Ll;0;L; 006C;;;;N;;;;; 1D55E;MATHEMATICAL DOUBLE-STRUCK SMALL M;Ll;0;L; 006D;;;;N;;;;; 1D55F;MATHEMATICAL DOUBLE-STRUCK SMALL N;Ll;0;L; 006E;;;;N;;;;; 1D560;MATHEMATICAL DOUBLE-STRUCK SMALL O;Ll;0;L; 006F;;;;N;;;;; 1D561;MATHEMATICAL DOUBLE-STRUCK SMALL P;Ll;0;L; 0070;;;;N;;;;; 1D562;MATHEMATICAL DOUBLE-STRUCK SMALL Q;Ll;0;L; 0071;;;;N;;;;; 1D563;MATHEMATICAL DOUBLE-STRUCK SMALL R;Ll;0;L; 0072;;;;N;;;;; 1D564;MATHEMATICAL DOUBLE-STRUCK SMALL S;Ll;0;L; 0073;;;;N;;;;; 1D565;MATHEMATICAL DOUBLE-STRUCK SMALL T;Ll;0;L; 0074;;;;N;;;;; 1D566;MATHEMATICAL DOUBLE-STRUCK SMALL U;Ll;0;L; 0075;;;;N;;;;; 1D567;MATHEMATICAL DOUBLE-STRUCK SMALL V;Ll;0;L; 0076;;;;N;;;;; 1D568;MATHEMATICAL DOUBLE-STRUCK SMALL W;Ll;0;L; 0077;;;;N;;;;; 1D569;MATHEMATICAL DOUBLE-STRUCK SMALL X;Ll;0;L; 0078;;;;N;;;;; 1D56A;MATHEMATICAL DOUBLE-STRUCK SMALL Y;Ll;0;L; 0079;;;;N;;;;; 1D56B;MATHEMATICAL DOUBLE-STRUCK SMALL Z;Ll;0;L; 007A;;;;N;;;;; 1D56C;MATHEMATICAL BOLD FRAKTUR CAPITAL A;Lu;0;L; 0041;;;;N;;;;; 1D56D;MATHEMATICAL BOLD FRAKTUR CAPITAL B;Lu;0;L; 0042;;;;N;;;;; 1D56E;MATHEMATICAL BOLD FRAKTUR CAPITAL C;Lu;0;L; 0043;;;;N;;;;; 1D56F;MATHEMATICAL BOLD FRAKTUR CAPITAL D;Lu;0;L; 0044;;;;N;;;;; 1D570;MATHEMATICAL BOLD FRAKTUR CAPITAL E;Lu;0;L; 0045;;;;N;;;;; 1D571;MATHEMATICAL BOLD FRAKTUR CAPITAL F;Lu;0;L; 0046;;;;N;;;;; 1D572;MATHEMATICAL BOLD FRAKTUR CAPITAL G;Lu;0;L; 0047;;;;N;;;;; 1D573;MATHEMATICAL BOLD FRAKTUR CAPITAL H;Lu;0;L; 0048;;;;N;;;;; 1D574;MATHEMATICAL BOLD FRAKTUR CAPITAL I;Lu;0;L; 0049;;;;N;;;;; 1D575;MATHEMATICAL BOLD FRAKTUR CAPITAL J;Lu;0;L; 004A;;;;N;;;;; 1D576;MATHEMATICAL BOLD FRAKTUR CAPITAL K;Lu;0;L; 004B;;;;N;;;;; 1D577;MATHEMATICAL BOLD FRAKTUR CAPITAL L;Lu;0;L; 004C;;;;N;;;;; 1D578;MATHEMATICAL BOLD FRAKTUR CAPITAL M;Lu;0;L; 004D;;;;N;;;;; 1D579;MATHEMATICAL BOLD FRAKTUR CAPITAL N;Lu;0;L; 004E;;;;N;;;;; 1D57A;MATHEMATICAL BOLD FRAKTUR CAPITAL O;Lu;0;L; 004F;;;;N;;;;; 1D57B;MATHEMATICAL BOLD FRAKTUR CAPITAL P;Lu;0;L; 0050;;;;N;;;;; 1D57C;MATHEMATICAL BOLD FRAKTUR CAPITAL Q;Lu;0;L; 0051;;;;N;;;;; 1D57D;MATHEMATICAL BOLD FRAKTUR CAPITAL R;Lu;0;L; 0052;;;;N;;;;; 1D57E;MATHEMATICAL BOLD FRAKTUR CAPITAL S;Lu;0;L; 0053;;;;N;;;;; 1D57F;MATHEMATICAL BOLD FRAKTUR CAPITAL T;Lu;0;L; 0054;;;;N;;;;; 1D580;MATHEMATICAL BOLD FRAKTUR CAPITAL U;Lu;0;L; 0055;;;;N;;;;; 1D581;MATHEMATICAL BOLD FRAKTUR CAPITAL V;Lu;0;L; 0056;;;;N;;;;; 1D582;MATHEMATICAL BOLD FRAKTUR CAPITAL W;Lu;0;L; 0057;;;;N;;;;; 1D583;MATHEMATICAL BOLD FRAKTUR CAPITAL X;Lu;0;L; 0058;;;;N;;;;; 1D584;MATHEMATICAL BOLD FRAKTUR CAPITAL Y;Lu;0;L; 0059;;;;N;;;;; 1D585;MATHEMATICAL BOLD FRAKTUR CAPITAL Z;Lu;0;L; 005A;;;;N;;;;; 1D586;MATHEMATICAL BOLD FRAKTUR SMALL A;Ll;0;L; 0061;;;;N;;;;; 1D587;MATHEMATICAL BOLD FRAKTUR SMALL B;Ll;0;L; 0062;;;;N;;;;; 1D588;MATHEMATICAL BOLD FRAKTUR SMALL C;Ll;0;L; 0063;;;;N;;;;; 1D589;MATHEMATICAL BOLD FRAKTUR SMALL D;Ll;0;L; 0064;;;;N;;;;; 1D58A;MATHEMATICAL BOLD FRAKTUR SMALL E;Ll;0;L; 0065;;;;N;;;;; 1D58B;MATHEMATICAL BOLD FRAKTUR SMALL F;Ll;0;L; 0066;;;;N;;;;; 1D58C;MATHEMATICAL BOLD FRAKTUR SMALL G;Ll;0;L; 0067;;;;N;;;;; 1D58D;MATHEMATICAL BOLD FRAKTUR SMALL H;Ll;0;L; 0068;;;;N;;;;; 1D58E;MATHEMATICAL BOLD FRAKTUR SMALL I;Ll;0;L; 0069;;;;N;;;;; 1D58F;MATHEMATICAL BOLD FRAKTUR SMALL J;Ll;0;L; 006A;;;;N;;;;; 1D590;MATHEMATICAL BOLD FRAKTUR SMALL K;Ll;0;L; 006B;;;;N;;;;; 1D591;MATHEMATICAL BOLD FRAKTUR SMALL L;Ll;0;L; 006C;;;;N;;;;; 1D592;MATHEMATICAL BOLD FRAKTUR SMALL M;Ll;0;L; 006D;;;;N;;;;; 1D593;MATHEMATICAL BOLD FRAKTUR SMALL N;Ll;0;L; 006E;;;;N;;;;; 1D594;MATHEMATICAL BOLD FRAKTUR SMALL O;Ll;0;L; 006F;;;;N;;;;; 1D595;MATHEMATICAL BOLD FRAKTUR SMALL P;Ll;0;L; 0070;;;;N;;;;; 1D596;MATHEMATICAL BOLD FRAKTUR SMALL Q;Ll;0;L; 0071;;;;N;;;;; 1D597;MATHEMATICAL BOLD FRAKTUR SMALL R;Ll;0;L; 0072;;;;N;;;;; 1D598;MATHEMATICAL BOLD FRAKTUR SMALL S;Ll;0;L; 0073;;;;N;;;;; 1D599;MATHEMATICAL BOLD FRAKTUR SMALL T;Ll;0;L; 0074;;;;N;;;;; 1D59A;MATHEMATICAL BOLD FRAKTUR SMALL U;Ll;0;L; 0075;;;;N;;;;; 1D59B;MATHEMATICAL BOLD FRAKTUR SMALL V;Ll;0;L; 0076;;;;N;;;;; 1D59C;MATHEMATICAL BOLD FRAKTUR SMALL W;Ll;0;L; 0077;;;;N;;;;; 1D59D;MATHEMATICAL BOLD FRAKTUR SMALL X;Ll;0;L; 0078;;;;N;;;;; 1D59E;MATHEMATICAL BOLD FRAKTUR SMALL Y;Ll;0;L; 0079;;;;N;;;;; 1D59F;MATHEMATICAL BOLD FRAKTUR SMALL Z;Ll;0;L; 007A;;;;N;;;;; 1D5A0;MATHEMATICAL SANS-SERIF CAPITAL A;Lu;0;L; 0041;;;;N;;;;; 1D5A1;MATHEMATICAL SANS-SERIF CAPITAL B;Lu;0;L; 0042;;;;N;;;;; 1D5A2;MATHEMATICAL SANS-SERIF CAPITAL C;Lu;0;L; 0043;;;;N;;;;; 1D5A3;MATHEMATICAL SANS-SERIF CAPITAL D;Lu;0;L; 0044;;;;N;;;;; 1D5A4;MATHEMATICAL SANS-SERIF CAPITAL E;Lu;0;L; 0045;;;;N;;;;; 1D5A5;MATHEMATICAL SANS-SERIF CAPITAL F;Lu;0;L; 0046;;;;N;;;;; 1D5A6;MATHEMATICAL SANS-SERIF CAPITAL G;Lu;0;L; 0047;;;;N;;;;; 1D5A7;MATHEMATICAL SANS-SERIF CAPITAL H;Lu;0;L; 0048;;;;N;;;;; 1D5A8;MATHEMATICAL SANS-SERIF CAPITAL I;Lu;0;L; 0049;;;;N;;;;; 1D5A9;MATHEMATICAL SANS-SERIF CAPITAL J;Lu;0;L; 004A;;;;N;;;;; 1D5AA;MATHEMATICAL SANS-SERIF CAPITAL K;Lu;0;L; 004B;;;;N;;;;; 1D5AB;MATHEMATICAL SANS-SERIF CAPITAL L;Lu;0;L; 004C;;;;N;;;;; 1D5AC;MATHEMATICAL SANS-SERIF CAPITAL M;Lu;0;L; 004D;;;;N;;;;; 1D5AD;MATHEMATICAL SANS-SERIF CAPITAL N;Lu;0;L; 004E;;;;N;;;;; 1D5AE;MATHEMATICAL SANS-SERIF CAPITAL O;Lu;0;L; 004F;;;;N;;;;; 1D5AF;MATHEMATICAL SANS-SERIF CAPITAL P;Lu;0;L; 0050;;;;N;;;;; 1D5B0;MATHEMATICAL SANS-SERIF CAPITAL Q;Lu;0;L; 0051;;;;N;;;;; 1D5B1;MATHEMATICAL SANS-SERIF CAPITAL R;Lu;0;L; 0052;;;;N;;;;; 1D5B2;MATHEMATICAL SANS-SERIF CAPITAL S;Lu;0;L; 0053;;;;N;;;;; 1D5B3;MATHEMATICAL SANS-SERIF CAPITAL T;Lu;0;L; 0054;;;;N;;;;; 1D5B4;MATHEMATICAL SANS-SERIF CAPITAL U;Lu;0;L; 0055;;;;N;;;;; 1D5B5;MATHEMATICAL SANS-SERIF CAPITAL V;Lu;0;L; 0056;;;;N;;;;; 1D5B6;MATHEMATICAL SANS-SERIF CAPITAL W;Lu;0;L; 0057;;;;N;;;;; 1D5B7;MATHEMATICAL SANS-SERIF CAPITAL X;Lu;0;L; 0058;;;;N;;;;; 1D5B8;MATHEMATICAL SANS-SERIF CAPITAL Y;Lu;0;L; 0059;;;;N;;;;; 1D5B9;MATHEMATICAL SANS-SERIF CAPITAL Z;Lu;0;L; 005A;;;;N;;;;; 1D5BA;MATHEMATICAL SANS-SERIF SMALL A;Ll;0;L; 0061;;;;N;;;;; 1D5BB;MATHEMATICAL SANS-SERIF SMALL B;Ll;0;L; 0062;;;;N;;;;; 1D5BC;MATHEMATICAL SANS-SERIF SMALL C;Ll;0;L; 0063;;;;N;;;;; 1D5BD;MATHEMATICAL SANS-SERIF SMALL D;Ll;0;L; 0064;;;;N;;;;; 1D5BE;MATHEMATICAL SANS-SERIF SMALL E;Ll;0;L; 0065;;;;N;;;;; 1D5BF;MATHEMATICAL SANS-SERIF SMALL F;Ll;0;L; 0066;;;;N;;;;; 1D5C0;MATHEMATICAL SANS-SERIF SMALL G;Ll;0;L; 0067;;;;N;;;;; 1D5C1;MATHEMATICAL SANS-SERIF SMALL H;Ll;0;L; 0068;;;;N;;;;; 1D5C2;MATHEMATICAL SANS-SERIF SMALL I;Ll;0;L; 0069;;;;N;;;;; 1D5C3;MATHEMATICAL SANS-SERIF SMALL J;Ll;0;L; 006A;;;;N;;;;; 1D5C4;MATHEMATICAL SANS-SERIF SMALL K;Ll;0;L; 006B;;;;N;;;;; 1D5C5;MATHEMATICAL SANS-SERIF SMALL L;Ll;0;L; 006C;;;;N;;;;; 1D5C6;MATHEMATICAL SANS-SERIF SMALL M;Ll;0;L; 006D;;;;N;;;;; 1D5C7;MATHEMATICAL SANS-SERIF SMALL N;Ll;0;L; 006E;;;;N;;;;; 1D5C8;MATHEMATICAL SANS-SERIF SMALL O;Ll;0;L; 006F;;;;N;;;;; 1D5C9;MATHEMATICAL SANS-SERIF SMALL P;Ll;0;L; 0070;;;;N;;;;; 1D5CA;MATHEMATICAL SANS-SERIF SMALL Q;Ll;0;L; 0071;;;;N;;;;; 1D5CB;MATHEMATICAL SANS-SERIF SMALL R;Ll;0;L; 0072;;;;N;;;;; 1D5CC;MATHEMATICAL SANS-SERIF SMALL S;Ll;0;L; 0073;;;;N;;;;; 1D5CD;MATHEMATICAL SANS-SERIF SMALL T;Ll;0;L; 0074;;;;N;;;;; 1D5CE;MATHEMATICAL SANS-SERIF SMALL U;Ll;0;L; 0075;;;;N;;;;; 1D5CF;MATHEMATICAL SANS-SERIF SMALL V;Ll;0;L; 0076;;;;N;;;;; 1D5D0;MATHEMATICAL SANS-SERIF SMALL W;Ll;0;L; 0077;;;;N;;;;; 1D5D1;MATHEMATICAL SANS-SERIF SMALL X;Ll;0;L; 0078;;;;N;;;;; 1D5D2;MATHEMATICAL SANS-SERIF SMALL Y;Ll;0;L; 0079;;;;N;;;;; 1D5D3;MATHEMATICAL SANS-SERIF SMALL Z;Ll;0;L; 007A;;;;N;;;;; 1D5D4;MATHEMATICAL SANS-SERIF BOLD CAPITAL A;Lu;0;L; 0041;;;;N;;;;; 1D5D5;MATHEMATICAL SANS-SERIF BOLD CAPITAL B;Lu;0;L; 0042;;;;N;;;;; 1D5D6;MATHEMATICAL SANS-SERIF BOLD CAPITAL C;Lu;0;L; 0043;;;;N;;;;; 1D5D7;MATHEMATICAL SANS-SERIF BOLD CAPITAL D;Lu;0;L; 0044;;;;N;;;;; 1D5D8;MATHEMATICAL SANS-SERIF BOLD CAPITAL E;Lu;0;L; 0045;;;;N;;;;; 1D5D9;MATHEMATICAL SANS-SERIF BOLD CAPITAL F;Lu;0;L; 0046;;;;N;;;;; 1D5DA;MATHEMATICAL SANS-SERIF BOLD CAPITAL G;Lu;0;L; 0047;;;;N;;;;; 1D5DB;MATHEMATICAL SANS-SERIF BOLD CAPITAL H;Lu;0;L; 0048;;;;N;;;;; 1D5DC;MATHEMATICAL SANS-SERIF BOLD CAPITAL I;Lu;0;L; 0049;;;;N;;;;; 1D5DD;MATHEMATICAL SANS-SERIF BOLD CAPITAL J;Lu;0;L; 004A;;;;N;;;;; 1D5DE;MATHEMATICAL SANS-SERIF BOLD CAPITAL K;Lu;0;L; 004B;;;;N;;;;; 1D5DF;MATHEMATICAL SANS-SERIF BOLD CAPITAL L;Lu;0;L; 004C;;;;N;;;;; 1D5E0;MATHEMATICAL SANS-SERIF BOLD CAPITAL M;Lu;0;L; 004D;;;;N;;;;; 1D5E1;MATHEMATICAL SANS-SERIF BOLD CAPITAL N;Lu;0;L; 004E;;;;N;;;;; 1D5E2;MATHEMATICAL SANS-SERIF BOLD CAPITAL O;Lu;0;L; 004F;;;;N;;;;; 1D5E3;MATHEMATICAL SANS-SERIF BOLD CAPITAL P;Lu;0;L; 0050;;;;N;;;;; 1D5E4;MATHEMATICAL SANS-SERIF BOLD CAPITAL Q;Lu;0;L; 0051;;;;N;;;;; 1D5E5;MATHEMATICAL SANS-SERIF BOLD CAPITAL R;Lu;0;L; 0052;;;;N;;;;; 1D5E6;MATHEMATICAL SANS-SERIF BOLD CAPITAL S;Lu;0;L; 0053;;;;N;;;;; 1D5E7;MATHEMATICAL SANS-SERIF BOLD CAPITAL T;Lu;0;L; 0054;;;;N;;;;; 1D5E8;MATHEMATICAL SANS-SERIF BOLD CAPITAL U;Lu;0;L; 0055;;;;N;;;;; 1D5E9;MATHEMATICAL SANS-SERIF BOLD CAPITAL V;Lu;0;L; 0056;;;;N;;;;; 1D5EA;MATHEMATICAL SANS-SERIF BOLD CAPITAL W;Lu;0;L; 0057;;;;N;;;;; 1D5EB;MATHEMATICAL SANS-SERIF BOLD CAPITAL X;Lu;0;L; 0058;;;;N;;;;; 1D5EC;MATHEMATICAL SANS-SERIF BOLD CAPITAL Y;Lu;0;L; 0059;;;;N;;;;; 1D5ED;MATHEMATICAL SANS-SERIF BOLD CAPITAL Z;Lu;0;L; 005A;;;;N;;;;; 1D5EE;MATHEMATICAL SANS-SERIF BOLD SMALL A;Ll;0;L; 0061;;;;N;;;;; 1D5EF;MATHEMATICAL SANS-SERIF BOLD SMALL B;Ll;0;L; 0062;;;;N;;;;; 1D5F0;MATHEMATICAL SANS-SERIF BOLD SMALL C;Ll;0;L; 0063;;;;N;;;;; 1D5F1;MATHEMATICAL SANS-SERIF BOLD SMALL D;Ll;0;L; 0064;;;;N;;;;; 1D5F2;MATHEMATICAL SANS-SERIF BOLD SMALL E;Ll;0;L; 0065;;;;N;;;;; 1D5F3;MATHEMATICAL SANS-SERIF BOLD SMALL F;Ll;0;L; 0066;;;;N;;;;; 1D5F4;MATHEMATICAL SANS-SERIF BOLD SMALL G;Ll;0;L; 0067;;;;N;;;;; 1D5F5;MATHEMATICAL SANS-SERIF BOLD SMALL H;Ll;0;L; 0068;;;;N;;;;; 1D5F6;MATHEMATICAL SANS-SERIF BOLD SMALL I;Ll;0;L; 0069;;;;N;;;;; 1D5F7;MATHEMATICAL SANS-SERIF BOLD SMALL J;Ll;0;L; 006A;;;;N;;;;; 1D5F8;MATHEMATICAL SANS-SERIF BOLD SMALL K;Ll;0;L; 006B;;;;N;;;;; 1D5F9;MATHEMATICAL SANS-SERIF BOLD SMALL L;Ll;0;L; 006C;;;;N;;;;; 1D5FA;MATHEMATICAL SANS-SERIF BOLD SMALL M;Ll;0;L; 006D;;;;N;;;;; 1D5FB;MATHEMATICAL SANS-SERIF BOLD SMALL N;Ll;0;L; 006E;;;;N;;;;; 1D5FC;MATHEMATICAL SANS-SERIF BOLD SMALL O;Ll;0;L; 006F;;;;N;;;;; 1D5FD;MATHEMATICAL SANS-SERIF BOLD SMALL P;Ll;0;L; 0070;;;;N;;;;; 1D5FE;MATHEMATICAL SANS-SERIF BOLD SMALL Q;Ll;0;L; 0071;;;;N;;;;; 1D5FF;MATHEMATICAL SANS-SERIF BOLD SMALL R;Ll;0;L; 0072;;;;N;;;;; 1D600;MATHEMATICAL SANS-SERIF BOLD SMALL S;Ll;0;L; 0073;;;;N;;;;; 1D601;MATHEMATICAL SANS-SERIF BOLD SMALL T;Ll;0;L; 0074;;;;N;;;;; 1D602;MATHEMATICAL SANS-SERIF BOLD SMALL U;Ll;0;L; 0075;;;;N;;;;; 1D603;MATHEMATICAL SANS-SERIF BOLD SMALL V;Ll;0;L; 0076;;;;N;;;;; 1D604;MATHEMATICAL SANS-SERIF BOLD SMALL W;Ll;0;L; 0077;;;;N;;;;; 1D605;MATHEMATICAL SANS-SERIF BOLD SMALL X;Ll;0;L; 0078;;;;N;;;;; 1D606;MATHEMATICAL SANS-SERIF BOLD SMALL Y;Ll;0;L; 0079;;;;N;;;;; 1D607;MATHEMATICAL SANS-SERIF BOLD SMALL Z;Ll;0;L; 007A;;;;N;;;;; 1D608;MATHEMATICAL SANS-SERIF ITALIC CAPITAL A;Lu;0;L; 0041;;;;N;;;;; 1D609;MATHEMATICAL SANS-SERIF ITALIC CAPITAL B;Lu;0;L; 0042;;;;N;;;;; 1D60A;MATHEMATICAL SANS-SERIF ITALIC CAPITAL C;Lu;0;L; 0043;;;;N;;;;; 1D60B;MATHEMATICAL SANS-SERIF ITALIC CAPITAL D;Lu;0;L; 0044;;;;N;;;;; 1D60C;MATHEMATICAL SANS-SERIF ITALIC CAPITAL E;Lu;0;L; 0045;;;;N;;;;; 1D60D;MATHEMATICAL SANS-SERIF ITALIC CAPITAL F;Lu;0;L; 0046;;;;N;;;;; 1D60E;MATHEMATICAL SANS-SERIF ITALIC CAPITAL G;Lu;0;L; 0047;;;;N;;;;; 1D60F;MATHEMATICAL SANS-SERIF ITALIC CAPITAL H;Lu;0;L; 0048;;;;N;;;;; 1D610;MATHEMATICAL SANS-SERIF ITALIC CAPITAL I;Lu;0;L; 0049;;;;N;;;;; 1D611;MATHEMATICAL SANS-SERIF ITALIC CAPITAL J;Lu;0;L; 004A;;;;N;;;;; 1D612;MATHEMATICAL SANS-SERIF ITALIC CAPITAL K;Lu;0;L; 004B;;;;N;;;;; 1D613;MATHEMATICAL SANS-SERIF ITALIC CAPITAL L;Lu;0;L; 004C;;;;N;;;;; 1D614;MATHEMATICAL SANS-SERIF ITALIC CAPITAL M;Lu;0;L; 004D;;;;N;;;;; 1D615;MATHEMATICAL SANS-SERIF ITALIC CAPITAL N;Lu;0;L; 004E;;;;N;;;;; 1D616;MATHEMATICAL SANS-SERIF ITALIC CAPITAL O;Lu;0;L; 004F;;;;N;;;;; 1D617;MATHEMATICAL SANS-SERIF ITALIC CAPITAL P;Lu;0;L; 0050;;;;N;;;;; 1D618;MATHEMATICAL SANS-SERIF ITALIC CAPITAL Q;Lu;0;L; 0051;;;;N;;;;; 1D619;MATHEMATICAL SANS-SERIF ITALIC CAPITAL R;Lu;0;L; 0052;;;;N;;;;; 1D61A;MATHEMATICAL SANS-SERIF ITALIC CAPITAL S;Lu;0;L; 0053;;;;N;;;;; 1D61B;MATHEMATICAL SANS-SERIF ITALIC CAPITAL T;Lu;0;L; 0054;;;;N;;;;; 1D61C;MATHEMATICAL SANS-SERIF ITALIC CAPITAL U;Lu;0;L; 0055;;;;N;;;;; 1D61D;MATHEMATICAL SANS-SERIF ITALIC CAPITAL V;Lu;0;L; 0056;;;;N;;;;; 1D61E;MATHEMATICAL SANS-SERIF ITALIC CAPITAL W;Lu;0;L; 0057;;;;N;;;;; 1D61F;MATHEMATICAL SANS-SERIF ITALIC CAPITAL X;Lu;0;L; 0058;;;;N;;;;; 1D620;MATHEMATICAL SANS-SERIF ITALIC CAPITAL Y;Lu;0;L; 0059;;;;N;;;;; 1D621;MATHEMATICAL SANS-SERIF ITALIC CAPITAL Z;Lu;0;L; 005A;;;;N;;;;; 1D622;MATHEMATICAL SANS-SERIF ITALIC SMALL A;Ll;0;L; 0061;;;;N;;;;; 1D623;MATHEMATICAL SANS-SERIF ITALIC SMALL B;Ll;0;L; 0062;;;;N;;;;; 1D624;MATHEMATICAL SANS-SERIF ITALIC SMALL C;Ll;0;L; 0063;;;;N;;;;; 1D625;MATHEMATICAL SANS-SERIF ITALIC SMALL D;Ll;0;L; 0064;;;;N;;;;; 1D626;MATHEMATICAL SANS-SERIF ITALIC SMALL E;Ll;0;L; 0065;;;;N;;;;; 1D627;MATHEMATICAL SANS-SERIF ITALIC SMALL F;Ll;0;L; 0066;;;;N;;;;; 1D628;MATHEMATICAL SANS-SERIF ITALIC SMALL G;Ll;0;L; 0067;;;;N;;;;; 1D629;MATHEMATICAL SANS-SERIF ITALIC SMALL H;Ll;0;L; 0068;;;;N;;;;; 1D62A;MATHEMATICAL SANS-SERIF ITALIC SMALL I;Ll;0;L; 0069;;;;N;;;;; 1D62B;MATHEMATICAL SANS-SERIF ITALIC SMALL J;Ll;0;L; 006A;;;;N;;;;; 1D62C;MATHEMATICAL SANS-SERIF ITALIC SMALL K;Ll;0;L; 006B;;;;N;;;;; 1D62D;MATHEMATICAL SANS-SERIF ITALIC SMALL L;Ll;0;L; 006C;;;;N;;;;; 1D62E;MATHEMATICAL SANS-SERIF ITALIC SMALL M;Ll;0;L; 006D;;;;N;;;;; 1D62F;MATHEMATICAL SANS-SERIF ITALIC SMALL N;Ll;0;L; 006E;;;;N;;;;; 1D630;MATHEMATICAL SANS-SERIF ITALIC SMALL O;Ll;0;L; 006F;;;;N;;;;; 1D631;MATHEMATICAL SANS-SERIF ITALIC SMALL P;Ll;0;L; 0070;;;;N;;;;; 1D632;MATHEMATICAL SANS-SERIF ITALIC SMALL Q;Ll;0;L; 0071;;;;N;;;;; 1D633;MATHEMATICAL SANS-SERIF ITALIC SMALL R;Ll;0;L; 0072;;;;N;;;;; 1D634;MATHEMATICAL SANS-SERIF ITALIC SMALL S;Ll;0;L; 0073;;;;N;;;;; 1D635;MATHEMATICAL SANS-SERIF ITALIC SMALL T;Ll;0;L; 0074;;;;N;;;;; 1D636;MATHEMATICAL SANS-SERIF ITALIC SMALL U;Ll;0;L; 0075;;;;N;;;;; 1D637;MATHEMATICAL SANS-SERIF ITALIC SMALL V;Ll;0;L; 0076;;;;N;;;;; 1D638;MATHEMATICAL SANS-SERIF ITALIC SMALL W;Ll;0;L; 0077;;;;N;;;;; 1D639;MATHEMATICAL SANS-SERIF ITALIC SMALL X;Ll;0;L; 0078;;;;N;;;;; 1D63A;MATHEMATICAL SANS-SERIF ITALIC SMALL Y;Ll;0;L; 0079;;;;N;;;;; 1D63B;MATHEMATICAL SANS-SERIF ITALIC SMALL Z;Ll;0;L; 007A;;;;N;;;;; 1D63C;MATHEMATICAL SANS-SERIF BOLD ITALIC CAPITAL A;Lu;0;L; 0041;;;;N;;;;; 1D63D;MATHEMATICAL SANS-SERIF BOLD ITALIC CAPITAL B;Lu;0;L; 0042;;;;N;;;;; 1D63E;MATHEMATICAL SANS-SERIF BOLD ITALIC CAPITAL C;Lu;0;L; 0043;;;;N;;;;; 1D63F;MATHEMATICAL SANS-SERIF BOLD ITALIC CAPITAL D;Lu;0;L; 0044;;;;N;;;;; 1D640;MATHEMATICAL SANS-SERIF BOLD ITALIC CAPITAL E;Lu;0;L; 0045;;;;N;;;;; 1D641;MATHEMATICAL SANS-SERIF BOLD ITALIC CAPITAL F;Lu;0;L; 0046;;;;N;;;;; 1D642;MATHEMATICAL SANS-SERIF BOLD ITALIC CAPITAL G;Lu;0;L; 0047;;;;N;;;;; 1D643;MATHEMATICAL SANS-SERIF BOLD ITALIC CAPITAL H;Lu;0;L; 0048;;;;N;;;;; 1D644;MATHEMATICAL SANS-SERIF BOLD ITALIC CAPITAL I;Lu;0;L; 0049;;;;N;;;;; 1D645;MATHEMATICAL SANS-SERIF BOLD ITALIC CAPITAL J;Lu;0;L; 004A;;;;N;;;;; 1D646;MATHEMATICAL SANS-SERIF BOLD ITALIC CAPITAL K;Lu;0;L; 004B;;;;N;;;;; 1D647;MATHEMATICAL SANS-SERIF BOLD ITALIC CAPITAL L;Lu;0;L; 004C;;;;N;;;;; 1D648;MATHEMATICAL SANS-SERIF BOLD ITALIC CAPITAL M;Lu;0;L; 004D;;;;N;;;;; 1D649;MATHEMATICAL SANS-SERIF BOLD ITALIC CAPITAL N;Lu;0;L; 004E;;;;N;;;;; 1D64A;MATHEMATICAL SANS-SERIF BOLD ITALIC CAPITAL O;Lu;0;L; 004F;;;;N;;;;; 1D64B;MATHEMATICAL SANS-SERIF BOLD ITALIC CAPITAL P;Lu;0;L; 0050;;;;N;;;;; 1D64C;MATHEMATICAL SANS-SERIF BOLD ITALIC CAPITAL Q;Lu;0;L; 0051;;;;N;;;;; 1D64D;MATHEMATICAL SANS-SERIF BOLD ITALIC CAPITAL R;Lu;0;L; 0052;;;;N;;;;; 1D64E;MATHEMATICAL SANS-SERIF BOLD ITALIC CAPITAL S;Lu;0;L; 0053;;;;N;;;;; 1D64F;MATHEMATICAL SANS-SERIF BOLD ITALIC CAPITAL T;Lu;0;L; 0054;;;;N;;;;; 1D650;MATHEMATICAL SANS-SERIF BOLD ITALIC CAPITAL U;Lu;0;L; 0055;;;;N;;;;; 1D651;MATHEMATICAL SANS-SERIF BOLD ITALIC CAPITAL V;Lu;0;L; 0056;;;;N;;;;; 1D652;MATHEMATICAL SANS-SERIF BOLD ITALIC CAPITAL W;Lu;0;L; 0057;;;;N;;;;; 1D653;MATHEMATICAL SANS-SERIF BOLD ITALIC CAPITAL X;Lu;0;L; 0058;;;;N;;;;; 1D654;MATHEMATICAL SANS-SERIF BOLD ITALIC CAPITAL Y;Lu;0;L; 0059;;;;N;;;;; 1D655;MATHEMATICAL SANS-SERIF BOLD ITALIC CAPITAL Z;Lu;0;L; 005A;;;;N;;;;; 1D656;MATHEMATICAL SANS-SERIF BOLD ITALIC SMALL A;Ll;0;L; 0061;;;;N;;;;; 1D657;MATHEMATICAL SANS-SERIF BOLD ITALIC SMALL B;Ll;0;L; 0062;;;;N;;;;; 1D658;MATHEMATICAL SANS-SERIF BOLD ITALIC SMALL C;Ll;0;L; 0063;;;;N;;;;; 1D659;MATHEMATICAL SANS-SERIF BOLD ITALIC SMALL D;Ll;0;L; 0064;;;;N;;;;; 1D65A;MATHEMATICAL SANS-SERIF BOLD ITALIC SMALL E;Ll;0;L; 0065;;;;N;;;;; 1D65B;MATHEMATICAL SANS-SERIF BOLD ITALIC SMALL F;Ll;0;L; 0066;;;;N;;;;; 1D65C;MATHEMATICAL SANS-SERIF BOLD ITALIC SMALL G;Ll;0;L; 0067;;;;N;;;;; 1D65D;MATHEMATICAL SANS-SERIF BOLD ITALIC SMALL H;Ll;0;L; 0068;;;;N;;;;; 1D65E;MATHEMATICAL SANS-SERIF BOLD ITALIC SMALL I;Ll;0;L; 0069;;;;N;;;;; 1D65F;MATHEMATICAL SANS-SERIF BOLD ITALIC SMALL J;Ll;0;L; 006A;;;;N;;;;; 1D660;MATHEMATICAL SANS-SERIF BOLD ITALIC SMALL K;Ll;0;L; 006B;;;;N;;;;; 1D661;MATHEMATICAL SANS-SERIF BOLD ITALIC SMALL L;Ll;0;L; 006C;;;;N;;;;; 1D662;MATHEMATICAL SANS-SERIF BOLD ITALIC SMALL M;Ll;0;L; 006D;;;;N;;;;; 1D663;MATHEMATICAL SANS-SERIF BOLD ITALIC SMALL N;Ll;0;L; 006E;;;;N;;;;; 1D664;MATHEMATICAL SANS-SERIF BOLD ITALIC SMALL O;Ll;0;L; 006F;;;;N;;;;; 1D665;MATHEMATICAL SANS-SERIF BOLD ITALIC SMALL P;Ll;0;L; 0070;;;;N;;;;; 1D666;MATHEMATICAL SANS-SERIF BOLD ITALIC SMALL Q;Ll;0;L; 0071;;;;N;;;;; 1D667;MATHEMATICAL SANS-SERIF BOLD ITALIC SMALL R;Ll;0;L; 0072;;;;N;;;;; 1D668;MATHEMATICAL SANS-SERIF BOLD ITALIC SMALL S;Ll;0;L; 0073;;;;N;;;;; 1D669;MATHEMATICAL SANS-SERIF BOLD ITALIC SMALL T;Ll;0;L; 0074;;;;N;;;;; 1D66A;MATHEMATICAL SANS-SERIF BOLD ITALIC SMALL U;Ll;0;L; 0075;;;;N;;;;; 1D66B;MATHEMATICAL SANS-SERIF BOLD ITALIC SMALL V;Ll;0;L; 0076;;;;N;;;;; 1D66C;MATHEMATICAL SANS-SERIF BOLD ITALIC SMALL W;Ll;0;L; 0077;;;;N;;;;; 1D66D;MATHEMATICAL SANS-SERIF BOLD ITALIC SMALL X;Ll;0;L; 0078;;;;N;;;;; 1D66E;MATHEMATICAL SANS-SERIF BOLD ITALIC SMALL Y;Ll;0;L; 0079;;;;N;;;;; 1D66F;MATHEMATICAL SANS-SERIF BOLD ITALIC SMALL Z;Ll;0;L; 007A;;;;N;;;;; 1D670;MATHEMATICAL MONOSPACE CAPITAL A;Lu;0;L; 0041;;;;N;;;;; 1D671;MATHEMATICAL MONOSPACE CAPITAL B;Lu;0;L; 0042;;;;N;;;;; 1D672;MATHEMATICAL MONOSPACE CAPITAL C;Lu;0;L; 0043;;;;N;;;;; 1D673;MATHEMATICAL MONOSPACE CAPITAL D;Lu;0;L; 0044;;;;N;;;;; 1D674;MATHEMATICAL MONOSPACE CAPITAL E;Lu;0;L; 0045;;;;N;;;;; 1D675;MATHEMATICAL MONOSPACE CAPITAL F;Lu;0;L; 0046;;;;N;;;;; 1D676;MATHEMATICAL MONOSPACE CAPITAL G;Lu;0;L; 0047;;;;N;;;;; 1D677;MATHEMATICAL MONOSPACE CAPITAL H;Lu;0;L; 0048;;;;N;;;;; 1D678;MATHEMATICAL MONOSPACE CAPITAL I;Lu;0;L; 0049;;;;N;;;;; 1D679;MATHEMATICAL MONOSPACE CAPITAL J;Lu;0;L; 004A;;;;N;;;;; 1D67A;MATHEMATICAL MONOSPACE CAPITAL K;Lu;0;L; 004B;;;;N;;;;; 1D67B;MATHEMATICAL MONOSPACE CAPITAL L;Lu;0;L; 004C;;;;N;;;;; 1D67C;MATHEMATICAL MONOSPACE CAPITAL M;Lu;0;L; 004D;;;;N;;;;; 1D67D;MATHEMATICAL MONOSPACE CAPITAL N;Lu;0;L; 004E;;;;N;;;;; 1D67E;MATHEMATICAL MONOSPACE CAPITAL O;Lu;0;L; 004F;;;;N;;;;; 1D67F;MATHEMATICAL MONOSPACE CAPITAL P;Lu;0;L; 0050;;;;N;;;;; 1D680;MATHEMATICAL MONOSPACE CAPITAL Q;Lu;0;L; 0051;;;;N;;;;; 1D681;MATHEMATICAL MONOSPACE CAPITAL R;Lu;0;L; 0052;;;;N;;;;; 1D682;MATHEMATICAL MONOSPACE CAPITAL S;Lu;0;L; 0053;;;;N;;;;; 1D683;MATHEMATICAL MONOSPACE CAPITAL T;Lu;0;L; 0054;;;;N;;;;; 1D684;MATHEMATICAL MONOSPACE CAPITAL U;Lu;0;L; 0055;;;;N;;;;; 1D685;MATHEMATICAL MONOSPACE CAPITAL V;Lu;0;L; 0056;;;;N;;;;; 1D686;MATHEMATICAL MONOSPACE CAPITAL W;Lu;0;L; 0057;;;;N;;;;; 1D687;MATHEMATICAL MONOSPACE CAPITAL X;Lu;0;L; 0058;;;;N;;;;; 1D688;MATHEMATICAL MONOSPACE CAPITAL Y;Lu;0;L; 0059;;;;N;;;;; 1D689;MATHEMATICAL MONOSPACE CAPITAL Z;Lu;0;L; 005A;;;;N;;;;; 1D68A;MATHEMATICAL MONOSPACE SMALL A;Ll;0;L; 0061;;;;N;;;;; 1D68B;MATHEMATICAL MONOSPACE SMALL B;Ll;0;L; 0062;;;;N;;;;; 1D68C;MATHEMATICAL MONOSPACE SMALL C;Ll;0;L; 0063;;;;N;;;;; 1D68D;MATHEMATICAL MONOSPACE SMALL D;Ll;0;L; 0064;;;;N;;;;; 1D68E;MATHEMATICAL MONOSPACE SMALL E;Ll;0;L; 0065;;;;N;;;;; 1D68F;MATHEMATICAL MONOSPACE SMALL F;Ll;0;L; 0066;;;;N;;;;; 1D690;MATHEMATICAL MONOSPACE SMALL G;Ll;0;L; 0067;;;;N;;;;; 1D691;MATHEMATICAL MONOSPACE SMALL H;Ll;0;L; 0068;;;;N;;;;; 1D692;MATHEMATICAL MONOSPACE SMALL I;Ll;0;L; 0069;;;;N;;;;; 1D693;MATHEMATICAL MONOSPACE SMALL J;Ll;0;L; 006A;;;;N;;;;; 1D694;MATHEMATICAL MONOSPACE SMALL K;Ll;0;L; 006B;;;;N;;;;; 1D695;MATHEMATICAL MONOSPACE SMALL L;Ll;0;L; 006C;;;;N;;;;; 1D696;MATHEMATICAL MONOSPACE SMALL M;Ll;0;L; 006D;;;;N;;;;; 1D697;MATHEMATICAL MONOSPACE SMALL N;Ll;0;L; 006E;;;;N;;;;; 1D698;MATHEMATICAL MONOSPACE SMALL O;Ll;0;L; 006F;;;;N;;;;; 1D699;MATHEMATICAL MONOSPACE SMALL P;Ll;0;L; 0070;;;;N;;;;; 1D69A;MATHEMATICAL MONOSPACE SMALL Q;Ll;0;L; 0071;;;;N;;;;; 1D69B;MATHEMATICAL MONOSPACE SMALL R;Ll;0;L; 0072;;;;N;;;;; 1D69C;MATHEMATICAL MONOSPACE SMALL S;Ll;0;L; 0073;;;;N;;;;; 1D69D;MATHEMATICAL MONOSPACE SMALL T;Ll;0;L; 0074;;;;N;;;;; 1D69E;MATHEMATICAL MONOSPACE SMALL U;Ll;0;L; 0075;;;;N;;;;; 1D69F;MATHEMATICAL MONOSPACE SMALL V;Ll;0;L; 0076;;;;N;;;;; 1D6A0;MATHEMATICAL MONOSPACE SMALL W;Ll;0;L; 0077;;;;N;;;;; 1D6A1;MATHEMATICAL MONOSPACE SMALL X;Ll;0;L; 0078;;;;N;;;;; 1D6A2;MATHEMATICAL MONOSPACE SMALL Y;Ll;0;L; 0079;;;;N;;;;; 1D6A3;MATHEMATICAL MONOSPACE SMALL Z;Ll;0;L; 007A;;;;N;;;;; 1D6A4;MATHEMATICAL ITALIC SMALL DOTLESS I;Ll;0;L; 0131;;;;N;;;;; 1D6A5;MATHEMATICAL ITALIC SMALL DOTLESS J;Ll;0;L; 0237;;;;N;;;;; 1D6A8;MATHEMATICAL BOLD CAPITAL ALPHA;Lu;0;L; 0391;;;;N;;;;; 1D6A9;MATHEMATICAL BOLD CAPITAL BETA;Lu;0;L; 0392;;;;N;;;;; 1D6AA;MATHEMATICAL BOLD CAPITAL GAMMA;Lu;0;L; 0393;;;;N;;;;; 1D6AB;MATHEMATICAL BOLD CAPITAL DELTA;Lu;0;L; 0394;;;;N;;;;; 1D6AC;MATHEMATICAL BOLD CAPITAL EPSILON;Lu;0;L; 0395;;;;N;;;;; 1D6AD;MATHEMATICAL BOLD CAPITAL ZETA;Lu;0;L; 0396;;;;N;;;;; 1D6AE;MATHEMATICAL BOLD CAPITAL ETA;Lu;0;L; 0397;;;;N;;;;; 1D6AF;MATHEMATICAL BOLD CAPITAL THETA;Lu;0;L; 0398;;;;N;;;;; 1D6B0;MATHEMATICAL BOLD CAPITAL IOTA;Lu;0;L; 0399;;;;N;;;;; 1D6B1;MATHEMATICAL BOLD CAPITAL KAPPA;Lu;0;L; 039A;;;;N;;;;; 1D6B2;MATHEMATICAL BOLD CAPITAL LAMDA;Lu;0;L; 039B;;;;N;;;;; 1D6B3;MATHEMATICAL BOLD CAPITAL MU;Lu;0;L; 039C;;;;N;;;;; 1D6B4;MATHEMATICAL BOLD CAPITAL NU;Lu;0;L; 039D;;;;N;;;;; 1D6B5;MATHEMATICAL BOLD CAPITAL XI;Lu;0;L; 039E;;;;N;;;;; 1D6B6;MATHEMATICAL BOLD CAPITAL OMICRON;Lu;0;L; 039F;;;;N;;;;; 1D6B7;MATHEMATICAL BOLD CAPITAL PI;Lu;0;L; 03A0;;;;N;;;;; 1D6B8;MATHEMATICAL BOLD CAPITAL RHO;Lu;0;L; 03A1;;;;N;;;;; 1D6B9;MATHEMATICAL BOLD CAPITAL THETA SYMBOL;Lu;0;L; 03F4;;;;N;;;;; 1D6BA;MATHEMATICAL BOLD CAPITAL SIGMA;Lu;0;L; 03A3;;;;N;;;;; 1D6BB;MATHEMATICAL BOLD CAPITAL TAU;Lu;0;L; 03A4;;;;N;;;;; 1D6BC;MATHEMATICAL BOLD CAPITAL UPSILON;Lu;0;L; 03A5;;;;N;;;;; 1D6BD;MATHEMATICAL BOLD CAPITAL PHI;Lu;0;L; 03A6;;;;N;;;;; 1D6BE;MATHEMATICAL BOLD CAPITAL CHI;Lu;0;L; 03A7;;;;N;;;;; 1D6BF;MATHEMATICAL BOLD CAPITAL PSI;Lu;0;L; 03A8;;;;N;;;;; 1D6C0;MATHEMATICAL BOLD CAPITAL OMEGA;Lu;0;L; 03A9;;;;N;;;;; 1D6C1;MATHEMATICAL BOLD NABLA;Sm;0;L; 2207;;;;N;;;;; 1D6C2;MATHEMATICAL BOLD SMALL ALPHA;Ll;0;L; 03B1;;;;N;;;;; 1D6C3;MATHEMATICAL BOLD SMALL BETA;Ll;0;L; 03B2;;;;N;;;;; 1D6C4;MATHEMATICAL BOLD SMALL GAMMA;Ll;0;L; 03B3;;;;N;;;;; 1D6C5;MATHEMATICAL BOLD SMALL DELTA;Ll;0;L; 03B4;;;;N;;;;; 1D6C6;MATHEMATICAL BOLD SMALL EPSILON;Ll;0;L; 03B5;;;;N;;;;; 1D6C7;MATHEMATICAL BOLD SMALL ZETA;Ll;0;L; 03B6;;;;N;;;;; 1D6C8;MATHEMATICAL BOLD SMALL ETA;Ll;0;L; 03B7;;;;N;;;;; 1D6C9;MATHEMATICAL BOLD SMALL THETA;Ll;0;L; 03B8;;;;N;;;;; 1D6CA;MATHEMATICAL BOLD SMALL IOTA;Ll;0;L; 03B9;;;;N;;;;; 1D6CB;MATHEMATICAL BOLD SMALL KAPPA;Ll;0;L; 03BA;;;;N;;;;; 1D6CC;MATHEMATICAL BOLD SMALL LAMDA;Ll;0;L; 03BB;;;;N;;;;; 1D6CD;MATHEMATICAL BOLD SMALL MU;Ll;0;L; 03BC;;;;N;;;;; 1D6CE;MATHEMATICAL BOLD SMALL NU;Ll;0;L; 03BD;;;;N;;;;; 1D6CF;MATHEMATICAL BOLD SMALL XI;Ll;0;L; 03BE;;;;N;;;;; 1D6D0;MATHEMATICAL BOLD SMALL OMICRON;Ll;0;L; 03BF;;;;N;;;;; 1D6D1;MATHEMATICAL BOLD SMALL PI;Ll;0;L; 03C0;;;;N;;;;; 1D6D2;MATHEMATICAL BOLD SMALL RHO;Ll;0;L; 03C1;;;;N;;;;; 1D6D3;MATHEMATICAL BOLD SMALL FINAL SIGMA;Ll;0;L; 03C2;;;;N;;;;; 1D6D4;MATHEMATICAL BOLD SMALL SIGMA;Ll;0;L; 03C3;;;;N;;;;; 1D6D5;MATHEMATICAL BOLD SMALL TAU;Ll;0;L; 03C4;;;;N;;;;; 1D6D6;MATHEMATICAL BOLD SMALL UPSILON;Ll;0;L; 03C5;;;;N;;;;; 1D6D7;MATHEMATICAL BOLD SMALL PHI;Ll;0;L; 03C6;;;;N;;;;; 1D6D8;MATHEMATICAL BOLD SMALL CHI;Ll;0;L; 03C7;;;;N;;;;; 1D6D9;MATHEMATICAL BOLD SMALL PSI;Ll;0;L; 03C8;;;;N;;;;; 1D6DA;MATHEMATICAL BOLD SMALL OMEGA;Ll;0;L; 03C9;;;;N;;;;; 1D6DB;MATHEMATICAL BOLD PARTIAL DIFFERENTIAL;Sm;0;ON; 2202;;;;Y;;;;; 1D6DC;MATHEMATICAL BOLD EPSILON SYMBOL;Ll;0;L; 03F5;;;;N;;;;; 1D6DD;MATHEMATICAL BOLD THETA SYMBOL;Ll;0;L; 03D1;;;;N;;;;; 1D6DE;MATHEMATICAL BOLD KAPPA SYMBOL;Ll;0;L; 03F0;;;;N;;;;; 1D6DF;MATHEMATICAL BOLD PHI SYMBOL;Ll;0;L; 03D5;;;;N;;;;; 1D6E0;MATHEMATICAL BOLD RHO SYMBOL;Ll;0;L; 03F1;;;;N;;;;; 1D6E1;MATHEMATICAL BOLD PI SYMBOL;Ll;0;L; 03D6;;;;N;;;;; 1D6E2;MATHEMATICAL ITALIC CAPITAL ALPHA;Lu;0;L; 0391;;;;N;;;;; 1D6E3;MATHEMATICAL ITALIC CAPITAL BETA;Lu;0;L; 0392;;;;N;;;;; 1D6E4;MATHEMATICAL ITALIC CAPITAL GAMMA;Lu;0;L; 0393;;;;N;;;;; 1D6E5;MATHEMATICAL ITALIC CAPITAL DELTA;Lu;0;L; 0394;;;;N;;;;; 1D6E6;MATHEMATICAL ITALIC CAPITAL EPSILON;Lu;0;L; 0395;;;;N;;;;; 1D6E7;MATHEMATICAL ITALIC CAPITAL ZETA;Lu;0;L; 0396;;;;N;;;;; 1D6E8;MATHEMATICAL ITALIC CAPITAL ETA;Lu;0;L; 0397;;;;N;;;;; 1D6E9;MATHEMATICAL ITALIC CAPITAL THETA;Lu;0;L; 0398;;;;N;;;;; 1D6EA;MATHEMATICAL ITALIC CAPITAL IOTA;Lu;0;L; 0399;;;;N;;;;; 1D6EB;MATHEMATICAL ITALIC CAPITAL KAPPA;Lu;0;L; 039A;;;;N;;;;; 1D6EC;MATHEMATICAL ITALIC CAPITAL LAMDA;Lu;0;L; 039B;;;;N;;;;; 1D6ED;MATHEMATICAL ITALIC CAPITAL MU;Lu;0;L; 039C;;;;N;;;;; 1D6EE;MATHEMATICAL ITALIC CAPITAL NU;Lu;0;L; 039D;;;;N;;;;; 1D6EF;MATHEMATICAL ITALIC CAPITAL XI;Lu;0;L; 039E;;;;N;;;;; 1D6F0;MATHEMATICAL ITALIC CAPITAL OMICRON;Lu;0;L; 039F;;;;N;;;;; 1D6F1;MATHEMATICAL ITALIC CAPITAL PI;Lu;0;L; 03A0;;;;N;;;;; 1D6F2;MATHEMATICAL ITALIC CAPITAL RHO;Lu;0;L; 03A1;;;;N;;;;; 1D6F3;MATHEMATICAL ITALIC CAPITAL THETA SYMBOL;Lu;0;L; 03F4;;;;N;;;;; 1D6F4;MATHEMATICAL ITALIC CAPITAL SIGMA;Lu;0;L; 03A3;;;;N;;;;; 1D6F5;MATHEMATICAL ITALIC CAPITAL TAU;Lu;0;L; 03A4;;;;N;;;;; 1D6F6;MATHEMATICAL ITALIC CAPITAL UPSILON;Lu;0;L; 03A5;;;;N;;;;; 1D6F7;MATHEMATICAL ITALIC CAPITAL PHI;Lu;0;L; 03A6;;;;N;;;;; 1D6F8;MATHEMATICAL ITALIC CAPITAL CHI;Lu;0;L; 03A7;;;;N;;;;; 1D6F9;MATHEMATICAL ITALIC CAPITAL PSI;Lu;0;L; 03A8;;;;N;;;;; 1D6FA;MATHEMATICAL ITALIC CAPITAL OMEGA;Lu;0;L; 03A9;;;;N;;;;; 1D6FB;MATHEMATICAL ITALIC NABLA;Sm;0;L; 2207;;;;N;;;;; 1D6FC;MATHEMATICAL ITALIC SMALL ALPHA;Ll;0;L; 03B1;;;;N;;;;; 1D6FD;MATHEMATICAL ITALIC SMALL BETA;Ll;0;L; 03B2;;;;N;;;;; 1D6FE;MATHEMATICAL ITALIC SMALL GAMMA;Ll;0;L; 03B3;;;;N;;;;; 1D6FF;MATHEMATICAL ITALIC SMALL DELTA;Ll;0;L; 03B4;;;;N;;;;; 1D700;MATHEMATICAL ITALIC SMALL EPSILON;Ll;0;L; 03B5;;;;N;;;;; 1D701;MATHEMATICAL ITALIC SMALL ZETA;Ll;0;L; 03B6;;;;N;;;;; 1D702;MATHEMATICAL ITALIC SMALL ETA;Ll;0;L; 03B7;;;;N;;;;; 1D703;MATHEMATICAL ITALIC SMALL THETA;Ll;0;L; 03B8;;;;N;;;;; 1D704;MATHEMATICAL ITALIC SMALL IOTA;Ll;0;L; 03B9;;;;N;;;;; 1D705;MATHEMATICAL ITALIC SMALL KAPPA;Ll;0;L; 03BA;;;;N;;;;; 1D706;MATHEMATICAL ITALIC SMALL LAMDA;Ll;0;L; 03BB;;;;N;;;;; 1D707;MATHEMATICAL ITALIC SMALL MU;Ll;0;L; 03BC;;;;N;;;;; 1D708;MATHEMATICAL ITALIC SMALL NU;Ll;0;L; 03BD;;;;N;;;;; 1D709;MATHEMATICAL ITALIC SMALL XI;Ll;0;L; 03BE;;;;N;;;;; 1D70A;MATHEMATICAL ITALIC SMALL OMICRON;Ll;0;L; 03BF;;;;N;;;;; 1D70B;MATHEMATICAL ITALIC SMALL PI;Ll;0;L; 03C0;;;;N;;;;; 1D70C;MATHEMATICAL ITALIC SMALL RHO;Ll;0;L; 03C1;;;;N;;;;; 1D70D;MATHEMATICAL ITALIC SMALL FINAL SIGMA;Ll;0;L; 03C2;;;;N;;;;; 1D70E;MATHEMATICAL ITALIC SMALL SIGMA;Ll;0;L; 03C3;;;;N;;;;; 1D70F;MATHEMATICAL ITALIC SMALL TAU;Ll;0;L; 03C4;;;;N;;;;; 1D710;MATHEMATICAL ITALIC SMALL UPSILON;Ll;0;L; 03C5;;;;N;;;;; 1D711;MATHEMATICAL ITALIC SMALL PHI;Ll;0;L; 03C6;;;;N;;;;; 1D712;MATHEMATICAL ITALIC SMALL CHI;Ll;0;L; 03C7;;;;N;;;;; 1D713;MATHEMATICAL ITALIC SMALL PSI;Ll;0;L; 03C8;;;;N;;;;; 1D714;MATHEMATICAL ITALIC SMALL OMEGA;Ll;0;L; 03C9;;;;N;;;;; 1D715;MATHEMATICAL ITALIC PARTIAL DIFFERENTIAL;Sm;0;ON; 2202;;;;Y;;;;; 1D716;MATHEMATICAL ITALIC EPSILON SYMBOL;Ll;0;L; 03F5;;;;N;;;;; 1D717;MATHEMATICAL ITALIC THETA SYMBOL;Ll;0;L; 03D1;;;;N;;;;; 1D718;MATHEMATICAL ITALIC KAPPA SYMBOL;Ll;0;L; 03F0;;;;N;;;;; 1D719;MATHEMATICAL ITALIC PHI SYMBOL;Ll;0;L; 03D5;;;;N;;;;; 1D71A;MATHEMATICAL ITALIC RHO SYMBOL;Ll;0;L; 03F1;;;;N;;;;; 1D71B;MATHEMATICAL ITALIC PI SYMBOL;Ll;0;L; 03D6;;;;N;;;;; 1D71C;MATHEMATICAL BOLD ITALIC CAPITAL ALPHA;Lu;0;L; 0391;;;;N;;;;; 1D71D;MATHEMATICAL BOLD ITALIC CAPITAL BETA;Lu;0;L; 0392;;;;N;;;;; 1D71E;MATHEMATICAL BOLD ITALIC CAPITAL GAMMA;Lu;0;L; 0393;;;;N;;;;; 1D71F;MATHEMATICAL BOLD ITALIC CAPITAL DELTA;Lu;0;L; 0394;;;;N;;;;; 1D720;MATHEMATICAL BOLD ITALIC CAPITAL EPSILON;Lu;0;L; 0395;;;;N;;;;; 1D721;MATHEMATICAL BOLD ITALIC CAPITAL ZETA;Lu;0;L; 0396;;;;N;;;;; 1D722;MATHEMATICAL BOLD ITALIC CAPITAL ETA;Lu;0;L; 0397;;;;N;;;;; 1D723;MATHEMATICAL BOLD ITALIC CAPITAL THETA;Lu;0;L; 0398;;;;N;;;;; 1D724;MATHEMATICAL BOLD ITALIC CAPITAL IOTA;Lu;0;L; 0399;;;;N;;;;; 1D725;MATHEMATICAL BOLD ITALIC CAPITAL KAPPA;Lu;0;L; 039A;;;;N;;;;; 1D726;MATHEMATICAL BOLD ITALIC CAPITAL LAMDA;Lu;0;L; 039B;;;;N;;;;; 1D727;MATHEMATICAL BOLD ITALIC CAPITAL MU;Lu;0;L; 039C;;;;N;;;;; 1D728;MATHEMATICAL BOLD ITALIC CAPITAL NU;Lu;0;L; 039D;;;;N;;;;; 1D729;MATHEMATICAL BOLD ITALIC CAPITAL XI;Lu;0;L; 039E;;;;N;;;;; 1D72A;MATHEMATICAL BOLD ITALIC CAPITAL OMICRON;Lu;0;L; 039F;;;;N;;;;; 1D72B;MATHEMATICAL BOLD ITALIC CAPITAL PI;Lu;0;L; 03A0;;;;N;;;;; 1D72C;MATHEMATICAL BOLD ITALIC CAPITAL RHO;Lu;0;L; 03A1;;;;N;;;;; 1D72D;MATHEMATICAL BOLD ITALIC CAPITAL THETA SYMBOL;Lu;0;L; 03F4;;;;N;;;;; 1D72E;MATHEMATICAL BOLD ITALIC CAPITAL SIGMA;Lu;0;L; 03A3;;;;N;;;;; 1D72F;MATHEMATICAL BOLD ITALIC CAPITAL TAU;Lu;0;L; 03A4;;;;N;;;;; 1D730;MATHEMATICAL BOLD ITALIC CAPITAL UPSILON;Lu;0;L; 03A5;;;;N;;;;; 1D731;MATHEMATICAL BOLD ITALIC CAPITAL PHI;Lu;0;L; 03A6;;;;N;;;;; 1D732;MATHEMATICAL BOLD ITALIC CAPITAL CHI;Lu;0;L; 03A7;;;;N;;;;; 1D733;MATHEMATICAL BOLD ITALIC CAPITAL PSI;Lu;0;L; 03A8;;;;N;;;;; 1D734;MATHEMATICAL BOLD ITALIC CAPITAL OMEGA;Lu;0;L; 03A9;;;;N;;;;; 1D735;MATHEMATICAL BOLD ITALIC NABLA;Sm;0;L; 2207;;;;N;;;;; 1D736;MATHEMATICAL BOLD ITALIC SMALL ALPHA;Ll;0;L; 03B1;;;;N;;;;; 1D737;MATHEMATICAL BOLD ITALIC SMALL BETA;Ll;0;L; 03B2;;;;N;;;;; 1D738;MATHEMATICAL BOLD ITALIC SMALL GAMMA;Ll;0;L; 03B3;;;;N;;;;; 1D739;MATHEMATICAL BOLD ITALIC SMALL DELTA;Ll;0;L; 03B4;;;;N;;;;; 1D73A;MATHEMATICAL BOLD ITALIC SMALL EPSILON;Ll;0;L; 03B5;;;;N;;;;; 1D73B;MATHEMATICAL BOLD ITALIC SMALL ZETA;Ll;0;L; 03B6;;;;N;;;;; 1D73C;MATHEMATICAL BOLD ITALIC SMALL ETA;Ll;0;L; 03B7;;;;N;;;;; 1D73D;MATHEMATICAL BOLD ITALIC SMALL THETA;Ll;0;L; 03B8;;;;N;;;;; 1D73E;MATHEMATICAL BOLD ITALIC SMALL IOTA;Ll;0;L; 03B9;;;;N;;;;; 1D73F;MATHEMATICAL BOLD ITALIC SMALL KAPPA;Ll;0;L; 03BA;;;;N;;;;; 1D740;MATHEMATICAL BOLD ITALIC SMALL LAMDA;Ll;0;L; 03BB;;;;N;;;;; 1D741;MATHEMATICAL BOLD ITALIC SMALL MU;Ll;0;L; 03BC;;;;N;;;;; 1D742;MATHEMATICAL BOLD ITALIC SMALL NU;Ll;0;L; 03BD;;;;N;;;;; 1D743;MATHEMATICAL BOLD ITALIC SMALL XI;Ll;0;L; 03BE;;;;N;;;;; 1D744;MATHEMATICAL BOLD ITALIC SMALL OMICRON;Ll;0;L; 03BF;;;;N;;;;; 1D745;MATHEMATICAL BOLD ITALIC SMALL PI;Ll;0;L; 03C0;;;;N;;;;; 1D746;MATHEMATICAL BOLD ITALIC SMALL RHO;Ll;0;L; 03C1;;;;N;;;;; 1D747;MATHEMATICAL BOLD ITALIC SMALL FINAL SIGMA;Ll;0;L; 03C2;;;;N;;;;; 1D748;MATHEMATICAL BOLD ITALIC SMALL SIGMA;Ll;0;L; 03C3;;;;N;;;;; 1D749;MATHEMATICAL BOLD ITALIC SMALL TAU;Ll;0;L; 03C4;;;;N;;;;; 1D74A;MATHEMATICAL BOLD ITALIC SMALL UPSILON;Ll;0;L; 03C5;;;;N;;;;; 1D74B;MATHEMATICAL BOLD ITALIC SMALL PHI;Ll;0;L; 03C6;;;;N;;;;; 1D74C;MATHEMATICAL BOLD ITALIC SMALL CHI;Ll;0;L; 03C7;;;;N;;;;; 1D74D;MATHEMATICAL BOLD ITALIC SMALL PSI;Ll;0;L; 03C8;;;;N;;;;; 1D74E;MATHEMATICAL BOLD ITALIC SMALL OMEGA;Ll;0;L; 03C9;;;;N;;;;; 1D74F;MATHEMATICAL BOLD ITALIC PARTIAL DIFFERENTIAL;Sm;0;ON; 2202;;;;Y;;;;; 1D750;MATHEMATICAL BOLD ITALIC EPSILON SYMBOL;Ll;0;L; 03F5;;;;N;;;;; 1D751;MATHEMATICAL BOLD ITALIC THETA SYMBOL;Ll;0;L; 03D1;;;;N;;;;; 1D752;MATHEMATICAL BOLD ITALIC KAPPA SYMBOL;Ll;0;L; 03F0;;;;N;;;;; 1D753;MATHEMATICAL BOLD ITALIC PHI SYMBOL;Ll;0;L; 03D5;;;;N;;;;; 1D754;MATHEMATICAL BOLD ITALIC RHO SYMBOL;Ll;0;L; 03F1;;;;N;;;;; 1D755;MATHEMATICAL BOLD ITALIC PI SYMBOL;Ll;0;L; 03D6;;;;N;;;;; 1D756;MATHEMATICAL SANS-SERIF BOLD CAPITAL ALPHA;Lu;0;L; 0391;;;;N;;;;; 1D757;MATHEMATICAL SANS-SERIF BOLD CAPITAL BETA;Lu;0;L; 0392;;;;N;;;;; 1D758;MATHEMATICAL SANS-SERIF BOLD CAPITAL GAMMA;Lu;0;L; 0393;;;;N;;;;; 1D759;MATHEMATICAL SANS-SERIF BOLD CAPITAL DELTA;Lu;0;L; 0394;;;;N;;;;; 1D75A;MATHEMATICAL SANS-SERIF BOLD CAPITAL EPSILON;Lu;0;L; 0395;;;;N;;;;; 1D75B;MATHEMATICAL SANS-SERIF BOLD CAPITAL ZETA;Lu;0;L; 0396;;;;N;;;;; 1D75C;MATHEMATICAL SANS-SERIF BOLD CAPITAL ETA;Lu;0;L; 0397;;;;N;;;;; 1D75D;MATHEMATICAL SANS-SERIF BOLD CAPITAL THETA;Lu;0;L; 0398;;;;N;;;;; 1D75E;MATHEMATICAL SANS-SERIF BOLD CAPITAL IOTA;Lu;0;L; 0399;;;;N;;;;; 1D75F;MATHEMATICAL SANS-SERIF BOLD CAPITAL KAPPA;Lu;0;L; 039A;;;;N;;;;; 1D760;MATHEMATICAL SANS-SERIF BOLD CAPITAL LAMDA;Lu;0;L; 039B;;;;N;;;;; 1D761;MATHEMATICAL SANS-SERIF BOLD CAPITAL MU;Lu;0;L; 039C;;;;N;;;;; 1D762;MATHEMATICAL SANS-SERIF BOLD CAPITAL NU;Lu;0;L; 039D;;;;N;;;;; 1D763;MATHEMATICAL SANS-SERIF BOLD CAPITAL XI;Lu;0;L; 039E;;;;N;;;;; 1D764;MATHEMATICAL SANS-SERIF BOLD CAPITAL OMICRON;Lu;0;L; 039F;;;;N;;;;; 1D765;MATHEMATICAL SANS-SERIF BOLD CAPITAL PI;Lu;0;L; 03A0;;;;N;;;;; 1D766;MATHEMATICAL SANS-SERIF BOLD CAPITAL RHO;Lu;0;L; 03A1;;;;N;;;;; 1D767;MATHEMATICAL SANS-SERIF BOLD CAPITAL THETA SYMBOL;Lu;0;L; 03F4;;;;N;;;;; 1D768;MATHEMATICAL SANS-SERIF BOLD CAPITAL SIGMA;Lu;0;L; 03A3;;;;N;;;;; 1D769;MATHEMATICAL SANS-SERIF BOLD CAPITAL TAU;Lu;0;L; 03A4;;;;N;;;;; 1D76A;MATHEMATICAL SANS-SERIF BOLD CAPITAL UPSILON;Lu;0;L; 03A5;;;;N;;;;; 1D76B;MATHEMATICAL SANS-SERIF BOLD CAPITAL PHI;Lu;0;L; 03A6;;;;N;;;;; 1D76C;MATHEMATICAL SANS-SERIF BOLD CAPITAL CHI;Lu;0;L; 03A7;;;;N;;;;; 1D76D;MATHEMATICAL SANS-SERIF BOLD CAPITAL PSI;Lu;0;L; 03A8;;;;N;;;;; 1D76E;MATHEMATICAL SANS-SERIF BOLD CAPITAL OMEGA;Lu;0;L; 03A9;;;;N;;;;; 1D76F;MATHEMATICAL SANS-SERIF BOLD NABLA;Sm;0;L; 2207;;;;N;;;;; 1D770;MATHEMATICAL SANS-SERIF BOLD SMALL ALPHA;Ll;0;L; 03B1;;;;N;;;;; 1D771;MATHEMATICAL SANS-SERIF BOLD SMALL BETA;Ll;0;L; 03B2;;;;N;;;;; 1D772;MATHEMATICAL SANS-SERIF BOLD SMALL GAMMA;Ll;0;L; 03B3;;;;N;;;;; 1D773;MATHEMATICAL SANS-SERIF BOLD SMALL DELTA;Ll;0;L; 03B4;;;;N;;;;; 1D774;MATHEMATICAL SANS-SERIF BOLD SMALL EPSILON;Ll;0;L; 03B5;;;;N;;;;; 1D775;MATHEMATICAL SANS-SERIF BOLD SMALL ZETA;Ll;0;L; 03B6;;;;N;;;;; 1D776;MATHEMATICAL SANS-SERIF BOLD SMALL ETA;Ll;0;L; 03B7;;;;N;;;;; 1D777;MATHEMATICAL SANS-SERIF BOLD SMALL THETA;Ll;0;L; 03B8;;;;N;;;;; 1D778;MATHEMATICAL SANS-SERIF BOLD SMALL IOTA;Ll;0;L; 03B9;;;;N;;;;; 1D779;MATHEMATICAL SANS-SERIF BOLD SMALL KAPPA;Ll;0;L; 03BA;;;;N;;;;; 1D77A;MATHEMATICAL SANS-SERIF BOLD SMALL LAMDA;Ll;0;L; 03BB;;;;N;;;;; 1D77B;MATHEMATICAL SANS-SERIF BOLD SMALL MU;Ll;0;L; 03BC;;;;N;;;;; 1D77C;MATHEMATICAL SANS-SERIF BOLD SMALL NU;Ll;0;L; 03BD;;;;N;;;;; 1D77D;MATHEMATICAL SANS-SERIF BOLD SMALL XI;Ll;0;L; 03BE;;;;N;;;;; 1D77E;MATHEMATICAL SANS-SERIF BOLD SMALL OMICRON;Ll;0;L; 03BF;;;;N;;;;; 1D77F;MATHEMATICAL SANS-SERIF BOLD SMALL PI;Ll;0;L; 03C0;;;;N;;;;; 1D780;MATHEMATICAL SANS-SERIF BOLD SMALL RHO;Ll;0;L; 03C1;;;;N;;;;; 1D781;MATHEMATICAL SANS-SERIF BOLD SMALL FINAL SIGMA;Ll;0;L; 03C2;;;;N;;;;; 1D782;MATHEMATICAL SANS-SERIF BOLD SMALL SIGMA;Ll;0;L; 03C3;;;;N;;;;; 1D783;MATHEMATICAL SANS-SERIF BOLD SMALL TAU;Ll;0;L; 03C4;;;;N;;;;; 1D784;MATHEMATICAL SANS-SERIF BOLD SMALL UPSILON;Ll;0;L; 03C5;;;;N;;;;; 1D785;MATHEMATICAL SANS-SERIF BOLD SMALL PHI;Ll;0;L; 03C6;;;;N;;;;; 1D786;MATHEMATICAL SANS-SERIF BOLD SMALL CHI;Ll;0;L; 03C7;;;;N;;;;; 1D787;MATHEMATICAL SANS-SERIF BOLD SMALL PSI;Ll;0;L; 03C8;;;;N;;;;; 1D788;MATHEMATICAL SANS-SERIF BOLD SMALL OMEGA;Ll;0;L; 03C9;;;;N;;;;; 1D789;MATHEMATICAL SANS-SERIF BOLD PARTIAL DIFFERENTIAL;Sm;0;ON; 2202;;;;Y;;;;; 1D78A;MATHEMATICAL SANS-SERIF BOLD EPSILON SYMBOL;Ll;0;L; 03F5;;;;N;;;;; 1D78B;MATHEMATICAL SANS-SERIF BOLD THETA SYMBOL;Ll;0;L; 03D1;;;;N;;;;; 1D78C;MATHEMATICAL SANS-SERIF BOLD KAPPA SYMBOL;Ll;0;L; 03F0;;;;N;;;;; 1D78D;MATHEMATICAL SANS-SERIF BOLD PHI SYMBOL;Ll;0;L; 03D5;;;;N;;;;; 1D78E;MATHEMATICAL SANS-SERIF BOLD RHO SYMBOL;Ll;0;L; 03F1;;;;N;;;;; 1D78F;MATHEMATICAL SANS-SERIF BOLD PI SYMBOL;Ll;0;L; 03D6;;;;N;;;;; 1D790;MATHEMATICAL SANS-SERIF BOLD ITALIC CAPITAL ALPHA;Lu;0;L; 0391;;;;N;;;;; 1D791;MATHEMATICAL SANS-SERIF BOLD ITALIC CAPITAL BETA;Lu;0;L; 0392;;;;N;;;;; 1D792;MATHEMATICAL SANS-SERIF BOLD ITALIC CAPITAL GAMMA;Lu;0;L; 0393;;;;N;;;;; 1D793;MATHEMATICAL SANS-SERIF BOLD ITALIC CAPITAL DELTA;Lu;0;L; 0394;;;;N;;;;; 1D794;MATHEMATICAL SANS-SERIF BOLD ITALIC CAPITAL EPSILON;Lu;0;L; 0395;;;;N;;;;; 1D795;MATHEMATICAL SANS-SERIF BOLD ITALIC CAPITAL ZETA;Lu;0;L; 0396;;;;N;;;;; 1D796;MATHEMATICAL SANS-SERIF BOLD ITALIC CAPITAL ETA;Lu;0;L; 0397;;;;N;;;;; 1D797;MATHEMATICAL SANS-SERIF BOLD ITALIC CAPITAL THETA;Lu;0;L; 0398;;;;N;;;;; 1D798;MATHEMATICAL SANS-SERIF BOLD ITALIC CAPITAL IOTA;Lu;0;L; 0399;;;;N;;;;; 1D799;MATHEMATICAL SANS-SERIF BOLD ITALIC CAPITAL KAPPA;Lu;0;L; 039A;;;;N;;;;; 1D79A;MATHEMATICAL SANS-SERIF BOLD ITALIC CAPITAL LAMDA;Lu;0;L; 039B;;;;N;;;;; 1D79B;MATHEMATICAL SANS-SERIF BOLD ITALIC CAPITAL MU;Lu;0;L; 039C;;;;N;;;;; 1D79C;MATHEMATICAL SANS-SERIF BOLD ITALIC CAPITAL NU;Lu;0;L; 039D;;;;N;;;;; 1D79D;MATHEMATICAL SANS-SERIF BOLD ITALIC CAPITAL XI;Lu;0;L; 039E;;;;N;;;;; 1D79E;MATHEMATICAL SANS-SERIF BOLD ITALIC CAPITAL OMICRON;Lu;0;L; 039F;;;;N;;;;; 1D79F;MATHEMATICAL SANS-SERIF BOLD ITALIC CAPITAL PI;Lu;0;L; 03A0;;;;N;;;;; 1D7A0;MATHEMATICAL SANS-SERIF BOLD ITALIC CAPITAL RHO;Lu;0;L; 03A1;;;;N;;;;; 1D7A1;MATHEMATICAL SANS-SERIF BOLD ITALIC CAPITAL THETA SYMBOL;Lu;0;L; 03F4;;;;N;;;;; 1D7A2;MATHEMATICAL SANS-SERIF BOLD ITALIC CAPITAL SIGMA;Lu;0;L; 03A3;;;;N;;;;; 1D7A3;MATHEMATICAL SANS-SERIF BOLD ITALIC CAPITAL TAU;Lu;0;L; 03A4;;;;N;;;;; 1D7A4;MATHEMATICAL SANS-SERIF BOLD ITALIC CAPITAL UPSILON;Lu;0;L; 03A5;;;;N;;;;; 1D7A5;MATHEMATICAL SANS-SERIF BOLD ITALIC CAPITAL PHI;Lu;0;L; 03A6;;;;N;;;;; 1D7A6;MATHEMATICAL SANS-SERIF BOLD ITALIC CAPITAL CHI;Lu;0;L; 03A7;;;;N;;;;; 1D7A7;MATHEMATICAL SANS-SERIF BOLD ITALIC CAPITAL PSI;Lu;0;L; 03A8;;;;N;;;;; 1D7A8;MATHEMATICAL SANS-SERIF BOLD ITALIC CAPITAL OMEGA;Lu;0;L; 03A9;;;;N;;;;; 1D7A9;MATHEMATICAL SANS-SERIF BOLD ITALIC NABLA;Sm;0;L; 2207;;;;N;;;;; 1D7AA;MATHEMATICAL SANS-SERIF BOLD ITALIC SMALL ALPHA;Ll;0;L; 03B1;;;;N;;;;; 1D7AB;MATHEMATICAL SANS-SERIF BOLD ITALIC SMALL BETA;Ll;0;L; 03B2;;;;N;;;;; 1D7AC;MATHEMATICAL SANS-SERIF BOLD ITALIC SMALL GAMMA;Ll;0;L; 03B3;;;;N;;;;; 1D7AD;MATHEMATICAL SANS-SERIF BOLD ITALIC SMALL DELTA;Ll;0;L; 03B4;;;;N;;;;; 1D7AE;MATHEMATICAL SANS-SERIF BOLD ITALIC SMALL EPSILON;Ll;0;L; 03B5;;;;N;;;;; 1D7AF;MATHEMATICAL SANS-SERIF BOLD ITALIC SMALL ZETA;Ll;0;L; 03B6;;;;N;;;;; 1D7B0;MATHEMATICAL SANS-SERIF BOLD ITALIC SMALL ETA;Ll;0;L; 03B7;;;;N;;;;; 1D7B1;MATHEMATICAL SANS-SERIF BOLD ITALIC SMALL THETA;Ll;0;L; 03B8;;;;N;;;;; 1D7B2;MATHEMATICAL SANS-SERIF BOLD ITALIC SMALL IOTA;Ll;0;L; 03B9;;;;N;;;;; 1D7B3;MATHEMATICAL SANS-SERIF BOLD ITALIC SMALL KAPPA;Ll;0;L; 03BA;;;;N;;;;; 1D7B4;MATHEMATICAL SANS-SERIF BOLD ITALIC SMALL LAMDA;Ll;0;L; 03BB;;;;N;;;;; 1D7B5;MATHEMATICAL SANS-SERIF BOLD ITALIC SMALL MU;Ll;0;L; 03BC;;;;N;;;;; 1D7B6;MATHEMATICAL SANS-SERIF BOLD ITALIC SMALL NU;Ll;0;L; 03BD;;;;N;;;;; 1D7B7;MATHEMATICAL SANS-SERIF BOLD ITALIC SMALL XI;Ll;0;L; 03BE;;;;N;;;;; 1D7B8;MATHEMATICAL SANS-SERIF BOLD ITALIC SMALL OMICRON;Ll;0;L; 03BF;;;;N;;;;; 1D7B9;MATHEMATICAL SANS-SERIF BOLD ITALIC SMALL PI;Ll;0;L; 03C0;;;;N;;;;; 1D7BA;MATHEMATICAL SANS-SERIF BOLD ITALIC SMALL RHO;Ll;0;L; 03C1;;;;N;;;;; 1D7BB;MATHEMATICAL SANS-SERIF BOLD ITALIC SMALL FINAL SIGMA;Ll;0;L; 03C2;;;;N;;;;; 1D7BC;MATHEMATICAL SANS-SERIF BOLD ITALIC SMALL SIGMA;Ll;0;L; 03C3;;;;N;;;;; 1D7BD;MATHEMATICAL SANS-SERIF BOLD ITALIC SMALL TAU;Ll;0;L; 03C4;;;;N;;;;; 1D7BE;MATHEMATICAL SANS-SERIF BOLD ITALIC SMALL UPSILON;Ll;0;L; 03C5;;;;N;;;;; 1D7BF;MATHEMATICAL SANS-SERIF BOLD ITALIC SMALL PHI;Ll;0;L; 03C6;;;;N;;;;; 1D7C0;MATHEMATICAL SANS-SERIF BOLD ITALIC SMALL CHI;Ll;0;L; 03C7;;;;N;;;;; 1D7C1;MATHEMATICAL SANS-SERIF BOLD ITALIC SMALL PSI;Ll;0;L; 03C8;;;;N;;;;; 1D7C2;MATHEMATICAL SANS-SERIF BOLD ITALIC SMALL OMEGA;Ll;0;L; 03C9;;;;N;;;;; 1D7C3;MATHEMATICAL SANS-SERIF BOLD ITALIC PARTIAL DIFFERENTIAL;Sm;0;ON; 2202;;;;Y;;;;; 1D7C4;MATHEMATICAL SANS-SERIF BOLD ITALIC EPSILON SYMBOL;Ll;0;L; 03F5;;;;N;;;;; 1D7C5;MATHEMATICAL SANS-SERIF BOLD ITALIC THETA SYMBOL;Ll;0;L; 03D1;;;;N;;;;; 1D7C6;MATHEMATICAL SANS-SERIF BOLD ITALIC KAPPA SYMBOL;Ll;0;L; 03F0;;;;N;;;;; 1D7C7;MATHEMATICAL SANS-SERIF BOLD ITALIC PHI SYMBOL;Ll;0;L; 03D5;;;;N;;;;; 1D7C8;MATHEMATICAL SANS-SERIF BOLD ITALIC RHO SYMBOL;Ll;0;L; 03F1;;;;N;;;;; 1D7C9;MATHEMATICAL SANS-SERIF BOLD ITALIC PI SYMBOL;Ll;0;L; 03D6;;;;N;;;;; 1D7CA;MATHEMATICAL BOLD CAPITAL DIGAMMA;Lu;0;L; 03DC;;;;N;;;;; 1D7CB;MATHEMATICAL BOLD SMALL DIGAMMA;Ll;0;L; 03DD;;;;N;;;;; 1D7CE;MATHEMATICAL BOLD DIGIT ZERO;Nd;0;EN; 0030;0;0;0;N;;;;; 1D7CF;MATHEMATICAL BOLD DIGIT ONE;Nd;0;EN; 0031;1;1;1;N;;;;; 1D7D0;MATHEMATICAL BOLD DIGIT TWO;Nd;0;EN; 0032;2;2;2;N;;;;; 1D7D1;MATHEMATICAL BOLD DIGIT THREE;Nd;0;EN; 0033;3;3;3;N;;;;; 1D7D2;MATHEMATICAL BOLD DIGIT FOUR;Nd;0;EN; 0034;4;4;4;N;;;;; 1D7D3;MATHEMATICAL BOLD DIGIT FIVE;Nd;0;EN; 0035;5;5;5;N;;;;; 1D7D4;MATHEMATICAL BOLD DIGIT SIX;Nd;0;EN; 0036;6;6;6;N;;;;; 1D7D5;MATHEMATICAL BOLD DIGIT SEVEN;Nd;0;EN; 0037;7;7;7;N;;;;; 1D7D6;MATHEMATICAL BOLD DIGIT EIGHT;Nd;0;EN; 0038;8;8;8;N;;;;; 1D7D7;MATHEMATICAL BOLD DIGIT NINE;Nd;0;EN; 0039;9;9;9;N;;;;; 1D7D8;MATHEMATICAL DOUBLE-STRUCK DIGIT ZERO;Nd;0;EN; 0030;0;0;0;N;;;;; 1D7D9;MATHEMATICAL DOUBLE-STRUCK DIGIT ONE;Nd;0;EN; 0031;1;1;1;N;;;;; 1D7DA;MATHEMATICAL DOUBLE-STRUCK DIGIT TWO;Nd;0;EN; 0032;2;2;2;N;;;;; 1D7DB;MATHEMATICAL DOUBLE-STRUCK DIGIT THREE;Nd;0;EN; 0033;3;3;3;N;;;;; 1D7DC;MATHEMATICAL DOUBLE-STRUCK DIGIT FOUR;Nd;0;EN; 0034;4;4;4;N;;;;; 1D7DD;MATHEMATICAL DOUBLE-STRUCK DIGIT FIVE;Nd;0;EN; 0035;5;5;5;N;;;;; 1D7DE;MATHEMATICAL DOUBLE-STRUCK DIGIT SIX;Nd;0;EN; 0036;6;6;6;N;;;;; 1D7DF;MATHEMATICAL DOUBLE-STRUCK DIGIT SEVEN;Nd;0;EN; 0037;7;7;7;N;;;;; 1D7E0;MATHEMATICAL DOUBLE-STRUCK DIGIT EIGHT;Nd;0;EN; 0038;8;8;8;N;;;;; 1D7E1;MATHEMATICAL DOUBLE-STRUCK DIGIT NINE;Nd;0;EN; 0039;9;9;9;N;;;;; 1D7E2;MATHEMATICAL SANS-SERIF DIGIT ZERO;Nd;0;EN; 0030;0;0;0;N;;;;; 1D7E3;MATHEMATICAL SANS-SERIF DIGIT ONE;Nd;0;EN; 0031;1;1;1;N;;;;; 1D7E4;MATHEMATICAL SANS-SERIF DIGIT TWO;Nd;0;EN; 0032;2;2;2;N;;;;; 1D7E5;MATHEMATICAL SANS-SERIF DIGIT THREE;Nd;0;EN; 0033;3;3;3;N;;;;; 1D7E6;MATHEMATICAL SANS-SERIF DIGIT FOUR;Nd;0;EN; 0034;4;4;4;N;;;;; 1D7E7;MATHEMATICAL SANS-SERIF DIGIT FIVE;Nd;0;EN; 0035;5;5;5;N;;;;; 1D7E8;MATHEMATICAL SANS-SERIF DIGIT SIX;Nd;0;EN; 0036;6;6;6;N;;;;; 1D7E9;MATHEMATICAL SANS-SERIF DIGIT SEVEN;Nd;0;EN; 0037;7;7;7;N;;;;; 1D7EA;MATHEMATICAL SANS-SERIF DIGIT EIGHT;Nd;0;EN; 0038;8;8;8;N;;;;; 1D7EB;MATHEMATICAL SANS-SERIF DIGIT NINE;Nd;0;EN; 0039;9;9;9;N;;;;; 1D7EC;MATHEMATICAL SANS-SERIF BOLD DIGIT ZERO;Nd;0;EN; 0030;0;0;0;N;;;;; 1D7ED;MATHEMATICAL SANS-SERIF BOLD DIGIT ONE;Nd;0;EN; 0031;1;1;1;N;;;;; 1D7EE;MATHEMATICAL SANS-SERIF BOLD DIGIT TWO;Nd;0;EN; 0032;2;2;2;N;;;;; 1D7EF;MATHEMATICAL SANS-SERIF BOLD DIGIT THREE;Nd;0;EN; 0033;3;3;3;N;;;;; 1D7F0;MATHEMATICAL SANS-SERIF BOLD DIGIT FOUR;Nd;0;EN; 0034;4;4;4;N;;;;; 1D7F1;MATHEMATICAL SANS-SERIF BOLD DIGIT FIVE;Nd;0;EN; 0035;5;5;5;N;;;;; 1D7F2;MATHEMATICAL SANS-SERIF BOLD DIGIT SIX;Nd;0;EN; 0036;6;6;6;N;;;;; 1D7F3;MATHEMATICAL SANS-SERIF BOLD DIGIT SEVEN;Nd;0;EN; 0037;7;7;7;N;;;;; 1D7F4;MATHEMATICAL SANS-SERIF BOLD DIGIT EIGHT;Nd;0;EN; 0038;8;8;8;N;;;;; 1D7F5;MATHEMATICAL SANS-SERIF BOLD DIGIT NINE;Nd;0;EN; 0039;9;9;9;N;;;;; 1D7F6;MATHEMATICAL MONOSPACE DIGIT ZERO;Nd;0;EN; 0030;0;0;0;N;;;;; 1D7F7;MATHEMATICAL MONOSPACE DIGIT ONE;Nd;0;EN; 0031;1;1;1;N;;;;; 1D7F8;MATHEMATICAL MONOSPACE DIGIT TWO;Nd;0;EN; 0032;2;2;2;N;;;;; 1D7F9;MATHEMATICAL MONOSPACE DIGIT THREE;Nd;0;EN; 0033;3;3;3;N;;;;; 1D7FA;MATHEMATICAL MONOSPACE DIGIT FOUR;Nd;0;EN; 0034;4;4;4;N;;;;; 1D7FB;MATHEMATICAL MONOSPACE DIGIT FIVE;Nd;0;EN; 0035;5;5;5;N;;;;; 1D7FC;MATHEMATICAL MONOSPACE DIGIT SIX;Nd;0;EN; 0036;6;6;6;N;;;;; 1D7FD;MATHEMATICAL MONOSPACE DIGIT SEVEN;Nd;0;EN; 0037;7;7;7;N;;;;; 1D7FE;MATHEMATICAL MONOSPACE DIGIT EIGHT;Nd;0;EN; 0038;8;8;8;N;;;;; 1D7FF;MATHEMATICAL MONOSPACE DIGIT NINE;Nd;0;EN; 0039;9;9;9;N;;;;; 1E800;MENDE KIKAKUI SYLLABLE M001 KI;Lo;0;R;;;;;N;;;;; 1E801;MENDE KIKAKUI SYLLABLE M002 KA;Lo;0;R;;;;;N;;;;; 1E802;MENDE KIKAKUI SYLLABLE M003 KU;Lo;0;R;;;;;N;;;;; 1E803;MENDE KIKAKUI SYLLABLE M065 KEE;Lo;0;R;;;;;N;;;;; 1E804;MENDE KIKAKUI SYLLABLE M095 KE;Lo;0;R;;;;;N;;;;; 1E805;MENDE KIKAKUI SYLLABLE M076 KOO;Lo;0;R;;;;;N;;;;; 1E806;MENDE KIKAKUI SYLLABLE M048 KO;Lo;0;R;;;;;N;;;;; 1E807;MENDE KIKAKUI SYLLABLE M179 KUA;Lo;0;R;;;;;N;;;;; 1E808;MENDE KIKAKUI SYLLABLE M004 WI;Lo;0;R;;;;;N;;;;; 1E809;MENDE KIKAKUI SYLLABLE M005 WA;Lo;0;R;;;;;N;;;;; 1E80A;MENDE KIKAKUI SYLLABLE M006 WU;Lo;0;R;;;;;N;;;;; 1E80B;MENDE KIKAKUI SYLLABLE M126 WEE;Lo;0;R;;;;;N;;;;; 1E80C;MENDE KIKAKUI SYLLABLE M118 WE;Lo;0;R;;;;;N;;;;; 1E80D;MENDE KIKAKUI SYLLABLE M114 WOO;Lo;0;R;;;;;N;;;;; 1E80E;MENDE KIKAKUI SYLLABLE M045 WO;Lo;0;R;;;;;N;;;;; 1E80F;MENDE KIKAKUI SYLLABLE M194 WUI;Lo;0;R;;;;;N;;;;; 1E810;MENDE KIKAKUI SYLLABLE M143 WEI;Lo;0;R;;;;;N;;;;; 1E811;MENDE KIKAKUI SYLLABLE M061 WVI;Lo;0;R;;;;;N;;;;; 1E812;MENDE KIKAKUI SYLLABLE M049 WVA;Lo;0;R;;;;;N;;;;; 1E813;MENDE KIKAKUI SYLLABLE M139 WVE;Lo;0;R;;;;;N;;;;; 1E814;MENDE KIKAKUI SYLLABLE M007 MIN;Lo;0;R;;;;;N;;;;; 1E815;MENDE KIKAKUI SYLLABLE M008 MAN;Lo;0;R;;;;;N;;;;; 1E816;MENDE KIKAKUI SYLLABLE M009 MUN;Lo;0;R;;;;;N;;;;; 1E817;MENDE KIKAKUI SYLLABLE M059 MEN;Lo;0;R;;;;;N;;;;; 1E818;MENDE KIKAKUI SYLLABLE M094 MON;Lo;0;R;;;;;N;;;;; 1E819;MENDE KIKAKUI SYLLABLE M154 MUAN;Lo;0;R;;;;;N;;;;; 1E81A;MENDE KIKAKUI SYLLABLE M189 MUEN;Lo;0;R;;;;;N;;;;; 1E81B;MENDE KIKAKUI SYLLABLE M010 BI;Lo;0;R;;;;;N;;;;; 1E81C;MENDE KIKAKUI SYLLABLE M011 BA;Lo;0;R;;;;;N;;;;; 1E81D;MENDE KIKAKUI SYLLABLE M012 BU;Lo;0;R;;;;;N;;;;; 1E81E;MENDE KIKAKUI SYLLABLE M150 BEE;Lo;0;R;;;;;N;;;;; 1E81F;MENDE KIKAKUI SYLLABLE M097 BE;Lo;0;R;;;;;N;;;;; 1E820;MENDE KIKAKUI SYLLABLE M103 BOO;Lo;0;R;;;;;N;;;;; 1E821;MENDE KIKAKUI SYLLABLE M138 BO;Lo;0;R;;;;;N;;;;; 1E822;MENDE KIKAKUI SYLLABLE M013 I;Lo;0;R;;;;;N;;;;; 1E823;MENDE KIKAKUI SYLLABLE M014 A;Lo;0;R;;;;;N;;;;; 1E824;MENDE KIKAKUI SYLLABLE M015 U;Lo;0;R;;;;;N;;;;; 1E825;MENDE KIKAKUI SYLLABLE M163 EE;Lo;0;R;;;;;N;;;;; 1E826;MENDE KIKAKUI SYLLABLE M100 E;Lo;0;R;;;;;N;;;;; 1E827;MENDE KIKAKUI SYLLABLE M165 OO;Lo;0;R;;;;;N;;;;; 1E828;MENDE KIKAKUI SYLLABLE M147 O;Lo;0;R;;;;;N;;;;; 1E829;MENDE KIKAKUI SYLLABLE M137 EI;Lo;0;R;;;;;N;;;;; 1E82A;MENDE KIKAKUI SYLLABLE M131 IN;Lo;0;R;;;;;N;;;;; 1E82B;MENDE KIKAKUI SYLLABLE M135 IN;Lo;0;R;;;;;N;;;;; 1E82C;MENDE KIKAKUI SYLLABLE M195 AN;Lo;0;R;;;;;N;;;;; 1E82D;MENDE KIKAKUI SYLLABLE M178 EN;Lo;0;R;;;;;N;;;;; 1E82E;MENDE KIKAKUI SYLLABLE M019 SI;Lo;0;R;;;;;N;;;;; 1E82F;MENDE KIKAKUI SYLLABLE M020 SA;Lo;0;R;;;;;N;;;;; 1E830;MENDE KIKAKUI SYLLABLE M021 SU;Lo;0;R;;;;;N;;;;; 1E831;MENDE KIKAKUI SYLLABLE M162 SEE;Lo;0;R;;;;;N;;;;; 1E832;MENDE KIKAKUI SYLLABLE M116 SE;Lo;0;R;;;;;N;;;;; 1E833;MENDE KIKAKUI SYLLABLE M136 SOO;Lo;0;R;;;;;N;;;;; 1E834;MENDE KIKAKUI SYLLABLE M079 SO;Lo;0;R;;;;;N;;;;; 1E835;MENDE KIKAKUI SYLLABLE M196 SIA;Lo;0;R;;;;;N;;;;; 1E836;MENDE KIKAKUI SYLLABLE M025 LI;Lo;0;R;;;;;N;;;;; 1E837;MENDE KIKAKUI SYLLABLE M026 LA;Lo;0;R;;;;;N;;;;; 1E838;MENDE KIKAKUI SYLLABLE M027 LU;Lo;0;R;;;;;N;;;;; 1E839;MENDE KIKAKUI SYLLABLE M084 LEE;Lo;0;R;;;;;N;;;;; 1E83A;MENDE KIKAKUI SYLLABLE M073 LE;Lo;0;R;;;;;N;;;;; 1E83B;MENDE KIKAKUI SYLLABLE M054 LOO;Lo;0;R;;;;;N;;;;; 1E83C;MENDE KIKAKUI SYLLABLE M153 LO;Lo;0;R;;;;;N;;;;; 1E83D;MENDE KIKAKUI SYLLABLE M110 LONG LE;Lo;0;R;;;;;N;;;;; 1E83E;MENDE KIKAKUI SYLLABLE M016 DI;Lo;0;R;;;;;N;;;;; 1E83F;MENDE KIKAKUI SYLLABLE M017 DA;Lo;0;R;;;;;N;;;;; 1E840;MENDE KIKAKUI SYLLABLE M018 DU;Lo;0;R;;;;;N;;;;; 1E841;MENDE KIKAKUI SYLLABLE M089 DEE;Lo;0;R;;;;;N;;;;; 1E842;MENDE KIKAKUI SYLLABLE M180 DOO;Lo;0;R;;;;;N;;;;; 1E843;MENDE KIKAKUI SYLLABLE M181 DO;Lo;0;R;;;;;N;;;;; 1E844;MENDE KIKAKUI SYLLABLE M022 TI;Lo;0;R;;;;;N;;;;; 1E845;MENDE KIKAKUI SYLLABLE M023 TA;Lo;0;R;;;;;N;;;;; 1E846;MENDE KIKAKUI SYLLABLE M024 TU;Lo;0;R;;;;;N;;;;; 1E847;MENDE KIKAKUI SYLLABLE M091 TEE;Lo;0;R;;;;;N;;;;; 1E848;MENDE KIKAKUI SYLLABLE M055 TE;Lo;0;R;;;;;N;;;;; 1E849;MENDE KIKAKUI SYLLABLE M104 TOO;Lo;0;R;;;;;N;;;;; 1E84A;MENDE KIKAKUI SYLLABLE M069 TO;Lo;0;R;;;;;N;;;;; 1E84B;MENDE KIKAKUI SYLLABLE M028 JI;Lo;0;R;;;;;N;;;;; 1E84C;MENDE KIKAKUI SYLLABLE M029 JA;Lo;0;R;;;;;N;;;;; 1E84D;MENDE KIKAKUI SYLLABLE M030 JU;Lo;0;R;;;;;N;;;;; 1E84E;MENDE KIKAKUI SYLLABLE M157 JEE;Lo;0;R;;;;;N;;;;; 1E84F;MENDE KIKAKUI SYLLABLE M113 JE;Lo;0;R;;;;;N;;;;; 1E850;MENDE KIKAKUI SYLLABLE M160 JOO;Lo;0;R;;;;;N;;;;; 1E851;MENDE KIKAKUI SYLLABLE M063 JO;Lo;0;R;;;;;N;;;;; 1E852;MENDE KIKAKUI SYLLABLE M175 LONG JO;Lo;0;R;;;;;N;;;;; 1E853;MENDE KIKAKUI SYLLABLE M031 YI;Lo;0;R;;;;;N;;;;; 1E854;MENDE KIKAKUI SYLLABLE M032 YA;Lo;0;R;;;;;N;;;;; 1E855;MENDE KIKAKUI SYLLABLE M033 YU;Lo;0;R;;;;;N;;;;; 1E856;MENDE KIKAKUI SYLLABLE M109 YEE;Lo;0;R;;;;;N;;;;; 1E857;MENDE KIKAKUI SYLLABLE M080 YE;Lo;0;R;;;;;N;;;;; 1E858;MENDE KIKAKUI SYLLABLE M141 YOO;Lo;0;R;;;;;N;;;;; 1E859;MENDE KIKAKUI SYLLABLE M121 YO;Lo;0;R;;;;;N;;;;; 1E85A;MENDE KIKAKUI SYLLABLE M034 FI;Lo;0;R;;;;;N;;;;; 1E85B;MENDE KIKAKUI SYLLABLE M035 FA;Lo;0;R;;;;;N;;;;; 1E85C;MENDE KIKAKUI SYLLABLE M036 FU;Lo;0;R;;;;;N;;;;; 1E85D;MENDE KIKAKUI SYLLABLE M078 FEE;Lo;0;R;;;;;N;;;;; 1E85E;MENDE KIKAKUI SYLLABLE M075 FE;Lo;0;R;;;;;N;;;;; 1E85F;MENDE KIKAKUI SYLLABLE M133 FOO;Lo;0;R;;;;;N;;;;; 1E860;MENDE KIKAKUI SYLLABLE M088 FO;Lo;0;R;;;;;N;;;;; 1E861;MENDE KIKAKUI SYLLABLE M197 FUA;Lo;0;R;;;;;N;;;;; 1E862;MENDE KIKAKUI SYLLABLE M101 FAN;Lo;0;R;;;;;N;;;;; 1E863;MENDE KIKAKUI SYLLABLE M037 NIN;Lo;0;R;;;;;N;;;;; 1E864;MENDE KIKAKUI SYLLABLE M038 NAN;Lo;0;R;;;;;N;;;;; 1E865;MENDE KIKAKUI SYLLABLE M039 NUN;Lo;0;R;;;;;N;;;;; 1E866;MENDE KIKAKUI SYLLABLE M117 NEN;Lo;0;R;;;;;N;;;;; 1E867;MENDE KIKAKUI SYLLABLE M169 NON;Lo;0;R;;;;;N;;;;; 1E868;MENDE KIKAKUI SYLLABLE M176 HI;Lo;0;R;;;;;N;;;;; 1E869;MENDE KIKAKUI SYLLABLE M041 HA;Lo;0;R;;;;;N;;;;; 1E86A;MENDE KIKAKUI SYLLABLE M186 HU;Lo;0;R;;;;;N;;;;; 1E86B;MENDE KIKAKUI SYLLABLE M040 HEE;Lo;0;R;;;;;N;;;;; 1E86C;MENDE KIKAKUI SYLLABLE M096 HE;Lo;0;R;;;;;N;;;;; 1E86D;MENDE KIKAKUI SYLLABLE M042 HOO;Lo;0;R;;;;;N;;;;; 1E86E;MENDE KIKAKUI SYLLABLE M140 HO;Lo;0;R;;;;;N;;;;; 1E86F;MENDE KIKAKUI SYLLABLE M083 HEEI;Lo;0;R;;;;;N;;;;; 1E870;MENDE KIKAKUI SYLLABLE M128 HOOU;Lo;0;R;;;;;N;;;;; 1E871;MENDE KIKAKUI SYLLABLE M053 HIN;Lo;0;R;;;;;N;;;;; 1E872;MENDE KIKAKUI SYLLABLE M130 HAN;Lo;0;R;;;;;N;;;;; 1E873;MENDE KIKAKUI SYLLABLE M087 HUN;Lo;0;R;;;;;N;;;;; 1E874;MENDE KIKAKUI SYLLABLE M052 HEN;Lo;0;R;;;;;N;;;;; 1E875;MENDE KIKAKUI SYLLABLE M193 HON;Lo;0;R;;;;;N;;;;; 1E876;MENDE KIKAKUI SYLLABLE M046 HUAN;Lo;0;R;;;;;N;;;;; 1E877;MENDE KIKAKUI SYLLABLE M090 NGGI;Lo;0;R;;;;;N;;;;; 1E878;MENDE KIKAKUI SYLLABLE M043 NGGA;Lo;0;R;;;;;N;;;;; 1E879;MENDE KIKAKUI SYLLABLE M082 NGGU;Lo;0;R;;;;;N;;;;; 1E87A;MENDE KIKAKUI SYLLABLE M115 NGGEE;Lo;0;R;;;;;N;;;;; 1E87B;MENDE KIKAKUI SYLLABLE M146 NGGE;Lo;0;R;;;;;N;;;;; 1E87C;MENDE KIKAKUI SYLLABLE M156 NGGOO;Lo;0;R;;;;;N;;;;; 1E87D;MENDE KIKAKUI SYLLABLE M120 NGGO;Lo;0;R;;;;;N;;;;; 1E87E;MENDE KIKAKUI SYLLABLE M159 NGGAA;Lo;0;R;;;;;N;;;;; 1E87F;MENDE KIKAKUI SYLLABLE M127 NGGUA;Lo;0;R;;;;;N;;;;; 1E880;MENDE KIKAKUI SYLLABLE M086 LONG NGGE;Lo;0;R;;;;;N;;;;; 1E881;MENDE KIKAKUI SYLLABLE M106 LONG NGGOO;Lo;0;R;;;;;N;;;;; 1E882;MENDE KIKAKUI SYLLABLE M183 LONG NGGO;Lo;0;R;;;;;N;;;;; 1E883;MENDE KIKAKUI SYLLABLE M155 GI;Lo;0;R;;;;;N;;;;; 1E884;MENDE KIKAKUI SYLLABLE M111 GA;Lo;0;R;;;;;N;;;;; 1E885;MENDE KIKAKUI SYLLABLE M168 GU;Lo;0;R;;;;;N;;;;; 1E886;MENDE KIKAKUI SYLLABLE M190 GEE;Lo;0;R;;;;;N;;;;; 1E887;MENDE KIKAKUI SYLLABLE M166 GUEI;Lo;0;R;;;;;N;;;;; 1E888;MENDE KIKAKUI SYLLABLE M167 GUAN;Lo;0;R;;;;;N;;;;; 1E889;MENDE KIKAKUI SYLLABLE M184 NGEN;Lo;0;R;;;;;N;;;;; 1E88A;MENDE KIKAKUI SYLLABLE M057 NGON;Lo;0;R;;;;;N;;;;; 1E88B;MENDE KIKAKUI SYLLABLE M177 NGUAN;Lo;0;R;;;;;N;;;;; 1E88C;MENDE KIKAKUI SYLLABLE M068 PI;Lo;0;R;;;;;N;;;;; 1E88D;MENDE KIKAKUI SYLLABLE M099 PA;Lo;0;R;;;;;N;;;;; 1E88E;MENDE KIKAKUI SYLLABLE M050 PU;Lo;0;R;;;;;N;;;;; 1E88F;MENDE KIKAKUI SYLLABLE M081 PEE;Lo;0;R;;;;;N;;;;; 1E890;MENDE KIKAKUI SYLLABLE M051 PE;Lo;0;R;;;;;N;;;;; 1E891;MENDE KIKAKUI SYLLABLE M102 POO;Lo;0;R;;;;;N;;;;; 1E892;MENDE KIKAKUI SYLLABLE M066 PO;Lo;0;R;;;;;N;;;;; 1E893;MENDE KIKAKUI SYLLABLE M145 MBI;Lo;0;R;;;;;N;;;;; 1E894;MENDE KIKAKUI SYLLABLE M062 MBA;Lo;0;R;;;;;N;;;;; 1E895;MENDE KIKAKUI SYLLABLE M122 MBU;Lo;0;R;;;;;N;;;;; 1E896;MENDE KIKAKUI SYLLABLE M047 MBEE;Lo;0;R;;;;;N;;;;; 1E897;MENDE KIKAKUI SYLLABLE M188 MBEE;Lo;0;R;;;;;N;;;;; 1E898;MENDE KIKAKUI SYLLABLE M072 MBE;Lo;0;R;;;;;N;;;;; 1E899;MENDE KIKAKUI SYLLABLE M172 MBOO;Lo;0;R;;;;;N;;;;; 1E89A;MENDE KIKAKUI SYLLABLE M174 MBO;Lo;0;R;;;;;N;;;;; 1E89B;MENDE KIKAKUI SYLLABLE M187 MBUU;Lo;0;R;;;;;N;;;;; 1E89C;MENDE KIKAKUI SYLLABLE M161 LONG MBE;Lo;0;R;;;;;N;;;;; 1E89D;MENDE KIKAKUI SYLLABLE M105 LONG MBOO;Lo;0;R;;;;;N;;;;; 1E89E;MENDE KIKAKUI SYLLABLE M142 LONG MBO;Lo;0;R;;;;;N;;;;; 1E89F;MENDE KIKAKUI SYLLABLE M132 KPI;Lo;0;R;;;;;N;;;;; 1E8A0;MENDE KIKAKUI SYLLABLE M092 KPA;Lo;0;R;;;;;N;;;;; 1E8A1;MENDE KIKAKUI SYLLABLE M074 KPU;Lo;0;R;;;;;N;;;;; 1E8A2;MENDE KIKAKUI SYLLABLE M044 KPEE;Lo;0;R;;;;;N;;;;; 1E8A3;MENDE KIKAKUI SYLLABLE M108 KPE;Lo;0;R;;;;;N;;;;; 1E8A4;MENDE KIKAKUI SYLLABLE M112 KPOO;Lo;0;R;;;;;N;;;;; 1E8A5;MENDE KIKAKUI SYLLABLE M158 KPO;Lo;0;R;;;;;N;;;;; 1E8A6;MENDE KIKAKUI SYLLABLE M124 GBI;Lo;0;R;;;;;N;;;;; 1E8A7;MENDE KIKAKUI SYLLABLE M056 GBA;Lo;0;R;;;;;N;;;;; 1E8A8;MENDE KIKAKUI SYLLABLE M148 GBU;Lo;0;R;;;;;N;;;;; 1E8A9;MENDE KIKAKUI SYLLABLE M093 GBEE;Lo;0;R;;;;;N;;;;; 1E8AA;MENDE KIKAKUI SYLLABLE M107 GBE;Lo;0;R;;;;;N;;;;; 1E8AB;MENDE KIKAKUI SYLLABLE M071 GBOO;Lo;0;R;;;;;N;;;;; 1E8AC;MENDE KIKAKUI SYLLABLE M070 GBO;Lo;0;R;;;;;N;;;;; 1E8AD;MENDE KIKAKUI SYLLABLE M171 RA;Lo;0;R;;;;;N;;;;; 1E8AE;MENDE KIKAKUI SYLLABLE M123 NDI;Lo;0;R;;;;;N;;;;; 1E8AF;MENDE KIKAKUI SYLLABLE M129 NDA;Lo;0;R;;;;;N;;;;; 1E8B0;MENDE KIKAKUI SYLLABLE M125 NDU;Lo;0;R;;;;;N;;;;; 1E8B1;MENDE KIKAKUI SYLLABLE M191 NDEE;Lo;0;R;;;;;N;;;;; 1E8B2;MENDE KIKAKUI SYLLABLE M119 NDE;Lo;0;R;;;;;N;;;;; 1E8B3;MENDE KIKAKUI SYLLABLE M067 NDOO;Lo;0;R;;;;;N;;;;; 1E8B4;MENDE KIKAKUI SYLLABLE M064 NDO;Lo;0;R;;;;;N;;;;; 1E8B5;MENDE KIKAKUI SYLLABLE M152 NJA;Lo;0;R;;;;;N;;;;; 1E8B6;MENDE KIKAKUI SYLLABLE M192 NJU;Lo;0;R;;;;;N;;;;; 1E8B7;MENDE KIKAKUI SYLLABLE M149 NJEE;Lo;0;R;;;;;N;;;;; 1E8B8;MENDE KIKAKUI SYLLABLE M134 NJOO;Lo;0;R;;;;;N;;;;; 1E8B9;MENDE KIKAKUI SYLLABLE M182 VI;Lo;0;R;;;;;N;;;;; 1E8BA;MENDE KIKAKUI SYLLABLE M185 VA;Lo;0;R;;;;;N;;;;; 1E8BB;MENDE KIKAKUI SYLLABLE M151 VU;Lo;0;R;;;;;N;;;;; 1E8BC;MENDE KIKAKUI SYLLABLE M173 VEE;Lo;0;R;;;;;N;;;;; 1E8BD;MENDE KIKAKUI SYLLABLE M085 VE;Lo;0;R;;;;;N;;;;; 1E8BE;MENDE KIKAKUI SYLLABLE M144 VOO;Lo;0;R;;;;;N;;;;; 1E8BF;MENDE KIKAKUI SYLLABLE M077 VO;Lo;0;R;;;;;N;;;;; 1E8C0;MENDE KIKAKUI SYLLABLE M164 NYIN;Lo;0;R;;;;;N;;;;; 1E8C1;MENDE KIKAKUI SYLLABLE M058 NYAN;Lo;0;R;;;;;N;;;;; 1E8C2;MENDE KIKAKUI SYLLABLE M170 NYUN;Lo;0;R;;;;;N;;;;; 1E8C3;MENDE KIKAKUI SYLLABLE M098 NYEN;Lo;0;R;;;;;N;;;;; 1E8C4;MENDE KIKAKUI SYLLABLE M060 NYON;Lo;0;R;;;;;N;;;;; 1E8C7;MENDE KIKAKUI DIGIT ONE;No;0;R;;;;1;N;;;;; 1E8C8;MENDE KIKAKUI DIGIT TWO;No;0;R;;;;2;N;;;;; 1E8C9;MENDE KIKAKUI DIGIT THREE;No;0;R;;;;3;N;;;;; 1E8CA;MENDE KIKAKUI DIGIT FOUR;No;0;R;;;;4;N;;;;; 1E8CB;MENDE KIKAKUI DIGIT FIVE;No;0;R;;;;5;N;;;;; 1E8CC;MENDE KIKAKUI DIGIT SIX;No;0;R;;;;6;N;;;;; 1E8CD;MENDE KIKAKUI DIGIT SEVEN;No;0;R;;;;7;N;;;;; 1E8CE;MENDE KIKAKUI DIGIT EIGHT;No;0;R;;;;8;N;;;;; 1E8CF;MENDE KIKAKUI DIGIT NINE;No;0;R;;;;9;N;;;;; 1E8D0;MENDE KIKAKUI COMBINING NUMBER TEENS;Mn;220;NSM;;;;;N;;;;; 1E8D1;MENDE KIKAKUI COMBINING NUMBER TENS;Mn;220;NSM;;;;;N;;;;; 1E8D2;MENDE KIKAKUI COMBINING NUMBER HUNDREDS;Mn;220;NSM;;;;;N;;;;; 1E8D3;MENDE KIKAKUI COMBINING NUMBER THOUSANDS;Mn;220;NSM;;;;;N;;;;; 1E8D4;MENDE KIKAKUI COMBINING NUMBER TEN THOUSANDS;Mn;220;NSM;;;;;N;;;;; 1E8D5;MENDE KIKAKUI COMBINING NUMBER HUNDRED THOUSANDS;Mn;220;NSM;;;;;N;;;;; 1E8D6;MENDE KIKAKUI COMBINING NUMBER MILLIONS;Mn;220;NSM;;;;;N;;;;; 1EE00;ARABIC MATHEMATICAL ALEF;Lo;0;AL; 0627;;;;N;;;;; 1EE01;ARABIC MATHEMATICAL BEH;Lo;0;AL; 0628;;;;N;;;;; 1EE02;ARABIC MATHEMATICAL JEEM;Lo;0;AL; 062C;;;;N;;;;; 1EE03;ARABIC MATHEMATICAL DAL;Lo;0;AL; 062F;;;;N;;;;; 1EE05;ARABIC MATHEMATICAL WAW;Lo;0;AL; 0648;;;;N;;;;; 1EE06;ARABIC MATHEMATICAL ZAIN;Lo;0;AL; 0632;;;;N;;;;; 1EE07;ARABIC MATHEMATICAL HAH;Lo;0;AL; 062D;;;;N;;;;; 1EE08;ARABIC MATHEMATICAL TAH;Lo;0;AL; 0637;;;;N;;;;; 1EE09;ARABIC MATHEMATICAL YEH;Lo;0;AL; 064A;;;;N;;;;; 1EE0A;ARABIC MATHEMATICAL KAF;Lo;0;AL; 0643;;;;N;;;;; 1EE0B;ARABIC MATHEMATICAL LAM;Lo;0;AL; 0644;;;;N;;;;; 1EE0C;ARABIC MATHEMATICAL MEEM;Lo;0;AL; 0645;;;;N;;;;; 1EE0D;ARABIC MATHEMATICAL NOON;Lo;0;AL; 0646;;;;N;;;;; 1EE0E;ARABIC MATHEMATICAL SEEN;Lo;0;AL; 0633;;;;N;;;;; 1EE0F;ARABIC MATHEMATICAL AIN;Lo;0;AL; 0639;;;;N;;;;; 1EE10;ARABIC MATHEMATICAL FEH;Lo;0;AL; 0641;;;;N;;;;; 1EE11;ARABIC MATHEMATICAL SAD;Lo;0;AL; 0635;;;;N;;;;; 1EE12;ARABIC MATHEMATICAL QAF;Lo;0;AL; 0642;;;;N;;;;; 1EE13;ARABIC MATHEMATICAL REH;Lo;0;AL; 0631;;;;N;;;;; 1EE14;ARABIC MATHEMATICAL SHEEN;Lo;0;AL; 0634;;;;N;;;;; 1EE15;ARABIC MATHEMATICAL TEH;Lo;0;AL; 062A;;;;N;;;;; 1EE16;ARABIC MATHEMATICAL THEH;Lo;0;AL; 062B;;;;N;;;;; 1EE17;ARABIC MATHEMATICAL KHAH;Lo;0;AL; 062E;;;;N;;;;; 1EE18;ARABIC MATHEMATICAL THAL;Lo;0;AL; 0630;;;;N;;;;; 1EE19;ARABIC MATHEMATICAL DAD;Lo;0;AL; 0636;;;;N;;;;; 1EE1A;ARABIC MATHEMATICAL ZAH;Lo;0;AL; 0638;;;;N;;;;; 1EE1B;ARABIC MATHEMATICAL GHAIN;Lo;0;AL; 063A;;;;N;;;;; 1EE1C;ARABIC MATHEMATICAL DOTLESS BEH;Lo;0;AL; 066E;;;;N;;;;; 1EE1D;ARABIC MATHEMATICAL DOTLESS NOON;Lo;0;AL; 06BA;;;;N;;;;; 1EE1E;ARABIC MATHEMATICAL DOTLESS FEH;Lo;0;AL; 06A1;;;;N;;;;; 1EE1F;ARABIC MATHEMATICAL DOTLESS QAF;Lo;0;AL; 066F;;;;N;;;;; 1EE21;ARABIC MATHEMATICAL INITIAL BEH;Lo;0;AL; 0628;;;;N;;;;; 1EE22;ARABIC MATHEMATICAL INITIAL JEEM;Lo;0;AL; 062C;;;;N;;;;; 1EE24;ARABIC MATHEMATICAL INITIAL HEH;Lo;0;AL; 0647;;;;N;;;;; 1EE27;ARABIC MATHEMATICAL INITIAL HAH;Lo;0;AL; 062D;;;;N;;;;; 1EE29;ARABIC MATHEMATICAL INITIAL YEH;Lo;0;AL; 064A;;;;N;;;;; 1EE2A;ARABIC MATHEMATICAL INITIAL KAF;Lo;0;AL; 0643;;;;N;;;;; 1EE2B;ARABIC MATHEMATICAL INITIAL LAM;Lo;0;AL; 0644;;;;N;;;;; 1EE2C;ARABIC MATHEMATICAL INITIAL MEEM;Lo;0;AL; 0645;;;;N;;;;; 1EE2D;ARABIC MATHEMATICAL INITIAL NOON;Lo;0;AL; 0646;;;;N;;;;; 1EE2E;ARABIC MATHEMATICAL INITIAL SEEN;Lo;0;AL; 0633;;;;N;;;;; 1EE2F;ARABIC MATHEMATICAL INITIAL AIN;Lo;0;AL; 0639;;;;N;;;;; 1EE30;ARABIC MATHEMATICAL INITIAL FEH;Lo;0;AL; 0641;;;;N;;;;; 1EE31;ARABIC MATHEMATICAL INITIAL SAD;Lo;0;AL; 0635;;;;N;;;;; 1EE32;ARABIC MATHEMATICAL INITIAL QAF;Lo;0;AL; 0642;;;;N;;;;; 1EE34;ARABIC MATHEMATICAL INITIAL SHEEN;Lo;0;AL; 0634;;;;N;;;;; 1EE35;ARABIC MATHEMATICAL INITIAL TEH;Lo;0;AL; 062A;;;;N;;;;; 1EE36;ARABIC MATHEMATICAL INITIAL THEH;Lo;0;AL; 062B;;;;N;;;;; 1EE37;ARABIC MATHEMATICAL INITIAL KHAH;Lo;0;AL; 062E;;;;N;;;;; 1EE39;ARABIC MATHEMATICAL INITIAL DAD;Lo;0;AL; 0636;;;;N;;;;; 1EE3B;ARABIC MATHEMATICAL INITIAL GHAIN;Lo;0;AL; 063A;;;;N;;;;; 1EE42;ARABIC MATHEMATICAL TAILED JEEM;Lo;0;AL; 062C;;;;N;;;;; 1EE47;ARABIC MATHEMATICAL TAILED HAH;Lo;0;AL; 062D;;;;N;;;;; 1EE49;ARABIC MATHEMATICAL TAILED YEH;Lo;0;AL; 064A;;;;N;;;;; 1EE4B;ARABIC MATHEMATICAL TAILED LAM;Lo;0;AL; 0644;;;;N;;;;; 1EE4D;ARABIC MATHEMATICAL TAILED NOON;Lo;0;AL; 0646;;;;N;;;;; 1EE4E;ARABIC MATHEMATICAL TAILED SEEN;Lo;0;AL; 0633;;;;N;;;;; 1EE4F;ARABIC MATHEMATICAL TAILED AIN;Lo;0;AL; 0639;;;;N;;;;; 1EE51;ARABIC MATHEMATICAL TAILED SAD;Lo;0;AL; 0635;;;;N;;;;; 1EE52;ARABIC MATHEMATICAL TAILED QAF;Lo;0;AL; 0642;;;;N;;;;; 1EE54;ARABIC MATHEMATICAL TAILED SHEEN;Lo;0;AL; 0634;;;;N;;;;; 1EE57;ARABIC MATHEMATICAL TAILED KHAH;Lo;0;AL; 062E;;;;N;;;;; 1EE59;ARABIC MATHEMATICAL TAILED DAD;Lo;0;AL; 0636;;;;N;;;;; 1EE5B;ARABIC MATHEMATICAL TAILED GHAIN;Lo;0;AL; 063A;;;;N;;;;; 1EE5D;ARABIC MATHEMATICAL TAILED DOTLESS NOON;Lo;0;AL; 06BA;;;;N;;;;; 1EE5F;ARABIC MATHEMATICAL TAILED DOTLESS QAF;Lo;0;AL; 066F;;;;N;;;;; 1EE61;ARABIC MATHEMATICAL STRETCHED BEH;Lo;0;AL; 0628;;;;N;;;;; 1EE62;ARABIC MATHEMATICAL STRETCHED JEEM;Lo;0;AL; 062C;;;;N;;;;; 1EE64;ARABIC MATHEMATICAL STRETCHED HEH;Lo;0;AL; 0647;;;;N;;;;; 1EE67;ARABIC MATHEMATICAL STRETCHED HAH;Lo;0;AL; 062D;;;;N;;;;; 1EE68;ARABIC MATHEMATICAL STRETCHED TAH;Lo;0;AL; 0637;;;;N;;;;; 1EE69;ARABIC MATHEMATICAL STRETCHED YEH;Lo;0;AL; 064A;;;;N;;;;; 1EE6A;ARABIC MATHEMATICAL STRETCHED KAF;Lo;0;AL; 0643;;;;N;;;;; 1EE6C;ARABIC MATHEMATICAL STRETCHED MEEM;Lo;0;AL; 0645;;;;N;;;;; 1EE6D;ARABIC MATHEMATICAL STRETCHED NOON;Lo;0;AL; 0646;;;;N;;;;; 1EE6E;ARABIC MATHEMATICAL STRETCHED SEEN;Lo;0;AL; 0633;;;;N;;;;; 1EE6F;ARABIC MATHEMATICAL STRETCHED AIN;Lo;0;AL; 0639;;;;N;;;;; 1EE70;ARABIC MATHEMATICAL STRETCHED FEH;Lo;0;AL; 0641;;;;N;;;;; 1EE71;ARABIC MATHEMATICAL STRETCHED SAD;Lo;0;AL; 0635;;;;N;;;;; 1EE72;ARABIC MATHEMATICAL STRETCHED QAF;Lo;0;AL; 0642;;;;N;;;;; 1EE74;ARABIC MATHEMATICAL STRETCHED SHEEN;Lo;0;AL; 0634;;;;N;;;;; 1EE75;ARABIC MATHEMATICAL STRETCHED TEH;Lo;0;AL; 062A;;;;N;;;;; 1EE76;ARABIC MATHEMATICAL STRETCHED THEH;Lo;0;AL; 062B;;;;N;;;;; 1EE77;ARABIC MATHEMATICAL STRETCHED KHAH;Lo;0;AL; 062E;;;;N;;;;; 1EE79;ARABIC MATHEMATICAL STRETCHED DAD;Lo;0;AL; 0636;;;;N;;;;; 1EE7A;ARABIC MATHEMATICAL STRETCHED ZAH;Lo;0;AL; 0638;;;;N;;;;; 1EE7B;ARABIC MATHEMATICAL STRETCHED GHAIN;Lo;0;AL; 063A;;;;N;;;;; 1EE7C;ARABIC MATHEMATICAL STRETCHED DOTLESS BEH;Lo;0;AL; 066E;;;;N;;;;; 1EE7E;ARABIC MATHEMATICAL STRETCHED DOTLESS FEH;Lo;0;AL; 06A1;;;;N;;;;; 1EE80;ARABIC MATHEMATICAL LOOPED ALEF;Lo;0;AL; 0627;;;;N;;;;; 1EE81;ARABIC MATHEMATICAL LOOPED BEH;Lo;0;AL; 0628;;;;N;;;;; 1EE82;ARABIC MATHEMATICAL LOOPED JEEM;Lo;0;AL; 062C;;;;N;;;;; 1EE83;ARABIC MATHEMATICAL LOOPED DAL;Lo;0;AL; 062F;;;;N;;;;; 1EE84;ARABIC MATHEMATICAL LOOPED HEH;Lo;0;AL; 0647;;;;N;;;;; 1EE85;ARABIC MATHEMATICAL LOOPED WAW;Lo;0;AL; 0648;;;;N;;;;; 1EE86;ARABIC MATHEMATICAL LOOPED ZAIN;Lo;0;AL; 0632;;;;N;;;;; 1EE87;ARABIC MATHEMATICAL LOOPED HAH;Lo;0;AL; 062D;;;;N;;;;; 1EE88;ARABIC MATHEMATICAL LOOPED TAH;Lo;0;AL; 0637;;;;N;;;;; 1EE89;ARABIC MATHEMATICAL LOOPED YEH;Lo;0;AL; 064A;;;;N;;;;; 1EE8B;ARABIC MATHEMATICAL LOOPED LAM;Lo;0;AL; 0644;;;;N;;;;; 1EE8C;ARABIC MATHEMATICAL LOOPED MEEM;Lo;0;AL; 0645;;;;N;;;;; 1EE8D;ARABIC MATHEMATICAL LOOPED NOON;Lo;0;AL; 0646;;;;N;;;;; 1EE8E;ARABIC MATHEMATICAL LOOPED SEEN;Lo;0;AL; 0633;;;;N;;;;; 1EE8F;ARABIC MATHEMATICAL LOOPED AIN;Lo;0;AL; 0639;;;;N;;;;; 1EE90;ARABIC MATHEMATICAL LOOPED FEH;Lo;0;AL; 0641;;;;N;;;;; 1EE91;ARABIC MATHEMATICAL LOOPED SAD;Lo;0;AL; 0635;;;;N;;;;; 1EE92;ARABIC MATHEMATICAL LOOPED QAF;Lo;0;AL; 0642;;;;N;;;;; 1EE93;ARABIC MATHEMATICAL LOOPED REH;Lo;0;AL; 0631;;;;N;;;;; 1EE94;ARABIC MATHEMATICAL LOOPED SHEEN;Lo;0;AL; 0634;;;;N;;;;; 1EE95;ARABIC MATHEMATICAL LOOPED TEH;Lo;0;AL; 062A;;;;N;;;;; 1EE96;ARABIC MATHEMATICAL LOOPED THEH;Lo;0;AL; 062B;;;;N;;;;; 1EE97;ARABIC MATHEMATICAL LOOPED KHAH;Lo;0;AL; 062E;;;;N;;;;; 1EE98;ARABIC MATHEMATICAL LOOPED THAL;Lo;0;AL; 0630;;;;N;;;;; 1EE99;ARABIC MATHEMATICAL LOOPED DAD;Lo;0;AL; 0636;;;;N;;;;; 1EE9A;ARABIC MATHEMATICAL LOOPED ZAH;Lo;0;AL; 0638;;;;N;;;;; 1EE9B;ARABIC MATHEMATICAL LOOPED GHAIN;Lo;0;AL; 063A;;;;N;;;;; 1EEA1;ARABIC MATHEMATICAL DOUBLE-STRUCK BEH;Lo;0;AL; 0628;;;;N;;;;; 1EEA2;ARABIC MATHEMATICAL DOUBLE-STRUCK JEEM;Lo;0;AL; 062C;;;;N;;;;; 1EEA3;ARABIC MATHEMATICAL DOUBLE-STRUCK DAL;Lo;0;AL; 062F;;;;N;;;;; 1EEA5;ARABIC MATHEMATICAL DOUBLE-STRUCK WAW;Lo;0;AL; 0648;;;;N;;;;; 1EEA6;ARABIC MATHEMATICAL DOUBLE-STRUCK ZAIN;Lo;0;AL; 0632;;;;N;;;;; 1EEA7;ARABIC MATHEMATICAL DOUBLE-STRUCK HAH;Lo;0;AL; 062D;;;;N;;;;; 1EEA8;ARABIC MATHEMATICAL DOUBLE-STRUCK TAH;Lo;0;AL; 0637;;;;N;;;;; 1EEA9;ARABIC MATHEMATICAL DOUBLE-STRUCK YEH;Lo;0;AL; 064A;;;;N;;;;; 1EEAB;ARABIC MATHEMATICAL DOUBLE-STRUCK LAM;Lo;0;AL; 0644;;;;N;;;;; 1EEAC;ARABIC MATHEMATICAL DOUBLE-STRUCK MEEM;Lo;0;AL; 0645;;;;N;;;;; 1EEAD;ARABIC MATHEMATICAL DOUBLE-STRUCK NOON;Lo;0;AL; 0646;;;;N;;;;; 1EEAE;ARABIC MATHEMATICAL DOUBLE-STRUCK SEEN;Lo;0;AL; 0633;;;;N;;;;; 1EEAF;ARABIC MATHEMATICAL DOUBLE-STRUCK AIN;Lo;0;AL; 0639;;;;N;;;;; 1EEB0;ARABIC MATHEMATICAL DOUBLE-STRUCK FEH;Lo;0;AL; 0641;;;;N;;;;; 1EEB1;ARABIC MATHEMATICAL DOUBLE-STRUCK SAD;Lo;0;AL; 0635;;;;N;;;;; 1EEB2;ARABIC MATHEMATICAL DOUBLE-STRUCK QAF;Lo;0;AL; 0642;;;;N;;;;; 1EEB3;ARABIC MATHEMATICAL DOUBLE-STRUCK REH;Lo;0;AL; 0631;;;;N;;;;; 1EEB4;ARABIC MATHEMATICAL DOUBLE-STRUCK SHEEN;Lo;0;AL; 0634;;;;N;;;;; 1EEB5;ARABIC MATHEMATICAL DOUBLE-STRUCK TEH;Lo;0;AL; 062A;;;;N;;;;; 1EEB6;ARABIC MATHEMATICAL DOUBLE-STRUCK THEH;Lo;0;AL; 062B;;;;N;;;;; 1EEB7;ARABIC MATHEMATICAL DOUBLE-STRUCK KHAH;Lo;0;AL; 062E;;;;N;;;;; 1EEB8;ARABIC MATHEMATICAL DOUBLE-STRUCK THAL;Lo;0;AL; 0630;;;;N;;;;; 1EEB9;ARABIC MATHEMATICAL DOUBLE-STRUCK DAD;Lo;0;AL; 0636;;;;N;;;;; 1EEBA;ARABIC MATHEMATICAL DOUBLE-STRUCK ZAH;Lo;0;AL; 0638;;;;N;;;;; 1EEBB;ARABIC MATHEMATICAL DOUBLE-STRUCK GHAIN;Lo;0;AL; 063A;;;;N;;;;; 1EEF0;ARABIC MATHEMATICAL OPERATOR MEEM WITH HAH WITH TATWEEL;Sm;0;ON;;;;;N;;;;; 1EEF1;ARABIC MATHEMATICAL OPERATOR HAH WITH DAL;Sm;0;ON;;;;;N;;;;; 1F000;MAHJONG TILE EAST WIND;So;0;ON;;;;;N;;;;; 1F001;MAHJONG TILE SOUTH WIND;So;0;ON;;;;;N;;;;; 1F002;MAHJONG TILE WEST WIND;So;0;ON;;;;;N;;;;; 1F003;MAHJONG TILE NORTH WIND;So;0;ON;;;;;N;;;;; 1F004;MAHJONG TILE RED DRAGON;So;0;ON;;;;;N;;;;; 1F005;MAHJONG TILE GREEN DRAGON;So;0;ON;;;;;N;;;;; 1F006;MAHJONG TILE WHITE DRAGON;So;0;ON;;;;;N;;;;; 1F007;MAHJONG TILE ONE OF CHARACTERS;So;0;ON;;;;;N;;;;; 1F008;MAHJONG TILE TWO OF CHARACTERS;So;0;ON;;;;;N;;;;; 1F009;MAHJONG TILE THREE OF CHARACTERS;So;0;ON;;;;;N;;;;; 1F00A;MAHJONG TILE FOUR OF CHARACTERS;So;0;ON;;;;;N;;;;; 1F00B;MAHJONG TILE FIVE OF CHARACTERS;So;0;ON;;;;;N;;;;; 1F00C;MAHJONG TILE SIX OF CHARACTERS;So;0;ON;;;;;N;;;;; 1F00D;MAHJONG TILE SEVEN OF CHARACTERS;So;0;ON;;;;;N;;;;; 1F00E;MAHJONG TILE EIGHT OF CHARACTERS;So;0;ON;;;;;N;;;;; 1F00F;MAHJONG TILE NINE OF CHARACTERS;So;0;ON;;;;;N;;;;; 1F010;MAHJONG TILE ONE OF BAMBOOS;So;0;ON;;;;;N;;;;; 1F011;MAHJONG TILE TWO OF BAMBOOS;So;0;ON;;;;;N;;;;; 1F012;MAHJONG TILE THREE OF BAMBOOS;So;0;ON;;;;;N;;;;; 1F013;MAHJONG TILE FOUR OF BAMBOOS;So;0;ON;;;;;N;;;;; 1F014;MAHJONG TILE FIVE OF BAMBOOS;So;0;ON;;;;;N;;;;; 1F015;MAHJONG TILE SIX OF BAMBOOS;So;0;ON;;;;;N;;;;; 1F016;MAHJONG TILE SEVEN OF BAMBOOS;So;0;ON;;;;;N;;;;; 1F017;MAHJONG TILE EIGHT OF BAMBOOS;So;0;ON;;;;;N;;;;; 1F018;MAHJONG TILE NINE OF BAMBOOS;So;0;ON;;;;;N;;;;; 1F019;MAHJONG TILE ONE OF CIRCLES;So;0;ON;;;;;N;;;;; 1F01A;MAHJONG TILE TWO OF CIRCLES;So;0;ON;;;;;N;;;;; 1F01B;MAHJONG TILE THREE OF CIRCLES;So;0;ON;;;;;N;;;;; 1F01C;MAHJONG TILE FOUR OF CIRCLES;So;0;ON;;;;;N;;;;; 1F01D;MAHJONG TILE FIVE OF CIRCLES;So;0;ON;;;;;N;;;;; 1F01E;MAHJONG TILE SIX OF CIRCLES;So;0;ON;;;;;N;;;;; 1F01F;MAHJONG TILE SEVEN OF CIRCLES;So;0;ON;;;;;N;;;;; 1F020;MAHJONG TILE EIGHT OF CIRCLES;So;0;ON;;;;;N;;;;; 1F021;MAHJONG TILE NINE OF CIRCLES;So;0;ON;;;;;N;;;;; 1F022;MAHJONG TILE PLUM;So;0;ON;;;;;N;;;;; 1F023;MAHJONG TILE ORCHID;So;0;ON;;;;;N;;;;; 1F024;MAHJONG TILE BAMBOO;So;0;ON;;;;;N;;;;; 1F025;MAHJONG TILE CHRYSANTHEMUM;So;0;ON;;;;;N;;;;; 1F026;MAHJONG TILE SPRING;So;0;ON;;;;;N;;;;; 1F027;MAHJONG TILE SUMMER;So;0;ON;;;;;N;;;;; 1F028;MAHJONG TILE AUTUMN;So;0;ON;;;;;N;;;;; 1F029;MAHJONG TILE WINTER;So;0;ON;;;;;N;;;;; 1F02A;MAHJONG TILE JOKER;So;0;ON;;;;;N;;;;; 1F02B;MAHJONG TILE BACK;So;0;ON;;;;;N;;;;; 1F030;DOMINO TILE HORIZONTAL BACK;So;0;ON;;;;;N;;;;; 1F031;DOMINO TILE HORIZONTAL-00-00;So;0;ON;;;;;N;;;;; 1F032;DOMINO TILE HORIZONTAL-00-01;So;0;ON;;;;;N;;;;; 1F033;DOMINO TILE HORIZONTAL-00-02;So;0;ON;;;;;N;;;;; 1F034;DOMINO TILE HORIZONTAL-00-03;So;0;ON;;;;;N;;;;; 1F035;DOMINO TILE HORIZONTAL-00-04;So;0;ON;;;;;N;;;;; 1F036;DOMINO TILE HORIZONTAL-00-05;So;0;ON;;;;;N;;;;; 1F037;DOMINO TILE HORIZONTAL-00-06;So;0;ON;;;;;N;;;;; 1F038;DOMINO TILE HORIZONTAL-01-00;So;0;ON;;;;;N;;;;; 1F039;DOMINO TILE HORIZONTAL-01-01;So;0;ON;;;;;N;;;;; 1F03A;DOMINO TILE HORIZONTAL-01-02;So;0;ON;;;;;N;;;;; 1F03B;DOMINO TILE HORIZONTAL-01-03;So;0;ON;;;;;N;;;;; 1F03C;DOMINO TILE HORIZONTAL-01-04;So;0;ON;;;;;N;;;;; 1F03D;DOMINO TILE HORIZONTAL-01-05;So;0;ON;;;;;N;;;;; 1F03E;DOMINO TILE HORIZONTAL-01-06;So;0;ON;;;;;N;;;;; 1F03F;DOMINO TILE HORIZONTAL-02-00;So;0;ON;;;;;N;;;;; 1F040;DOMINO TILE HORIZONTAL-02-01;So;0;ON;;;;;N;;;;; 1F041;DOMINO TILE HORIZONTAL-02-02;So;0;ON;;;;;N;;;;; 1F042;DOMINO TILE HORIZONTAL-02-03;So;0;ON;;;;;N;;;;; 1F043;DOMINO TILE HORIZONTAL-02-04;So;0;ON;;;;;N;;;;; 1F044;DOMINO TILE HORIZONTAL-02-05;So;0;ON;;;;;N;;;;; 1F045;DOMINO TILE HORIZONTAL-02-06;So;0;ON;;;;;N;;;;; 1F046;DOMINO TILE HORIZONTAL-03-00;So;0;ON;;;;;N;;;;; 1F047;DOMINO TILE HORIZONTAL-03-01;So;0;ON;;;;;N;;;;; 1F048;DOMINO TILE HORIZONTAL-03-02;So;0;ON;;;;;N;;;;; 1F049;DOMINO TILE HORIZONTAL-03-03;So;0;ON;;;;;N;;;;; 1F04A;DOMINO TILE HORIZONTAL-03-04;So;0;ON;;;;;N;;;;; 1F04B;DOMINO TILE HORIZONTAL-03-05;So;0;ON;;;;;N;;;;; 1F04C;DOMINO TILE HORIZONTAL-03-06;So;0;ON;;;;;N;;;;; 1F04D;DOMINO TILE HORIZONTAL-04-00;So;0;ON;;;;;N;;;;; 1F04E;DOMINO TILE HORIZONTAL-04-01;So;0;ON;;;;;N;;;;; 1F04F;DOMINO TILE HORIZONTAL-04-02;So;0;ON;;;;;N;;;;; 1F050;DOMINO TILE HORIZONTAL-04-03;So;0;ON;;;;;N;;;;; 1F051;DOMINO TILE HORIZONTAL-04-04;So;0;ON;;;;;N;;;;; 1F052;DOMINO TILE HORIZONTAL-04-05;So;0;ON;;;;;N;;;;; 1F053;DOMINO TILE HORIZONTAL-04-06;So;0;ON;;;;;N;;;;; 1F054;DOMINO TILE HORIZONTAL-05-00;So;0;ON;;;;;N;;;;; 1F055;DOMINO TILE HORIZONTAL-05-01;So;0;ON;;;;;N;;;;; 1F056;DOMINO TILE HORIZONTAL-05-02;So;0;ON;;;;;N;;;;; 1F057;DOMINO TILE HORIZONTAL-05-03;So;0;ON;;;;;N;;;;; 1F058;DOMINO TILE HORIZONTAL-05-04;So;0;ON;;;;;N;;;;; 1F059;DOMINO TILE HORIZONTAL-05-05;So;0;ON;;;;;N;;;;; 1F05A;DOMINO TILE HORIZONTAL-05-06;So;0;ON;;;;;N;;;;; 1F05B;DOMINO TILE HORIZONTAL-06-00;So;0;ON;;;;;N;;;;; 1F05C;DOMINO TILE HORIZONTAL-06-01;So;0;ON;;;;;N;;;;; 1F05D;DOMINO TILE HORIZONTAL-06-02;So;0;ON;;;;;N;;;;; 1F05E;DOMINO TILE HORIZONTAL-06-03;So;0;ON;;;;;N;;;;; 1F05F;DOMINO TILE HORIZONTAL-06-04;So;0;ON;;;;;N;;;;; 1F060;DOMINO TILE HORIZONTAL-06-05;So;0;ON;;;;;N;;;;; 1F061;DOMINO TILE HORIZONTAL-06-06;So;0;ON;;;;;N;;;;; 1F062;DOMINO TILE VERTICAL BACK;So;0;ON;;;;;N;;;;; 1F063;DOMINO TILE VERTICAL-00-00;So;0;ON;;;;;N;;;;; 1F064;DOMINO TILE VERTICAL-00-01;So;0;ON;;;;;N;;;;; 1F065;DOMINO TILE VERTICAL-00-02;So;0;ON;;;;;N;;;;; 1F066;DOMINO TILE VERTICAL-00-03;So;0;ON;;;;;N;;;;; 1F067;DOMINO TILE VERTICAL-00-04;So;0;ON;;;;;N;;;;; 1F068;DOMINO TILE VERTICAL-00-05;So;0;ON;;;;;N;;;;; 1F069;DOMINO TILE VERTICAL-00-06;So;0;ON;;;;;N;;;;; 1F06A;DOMINO TILE VERTICAL-01-00;So;0;ON;;;;;N;;;;; 1F06B;DOMINO TILE VERTICAL-01-01;So;0;ON;;;;;N;;;;; 1F06C;DOMINO TILE VERTICAL-01-02;So;0;ON;;;;;N;;;;; 1F06D;DOMINO TILE VERTICAL-01-03;So;0;ON;;;;;N;;;;; 1F06E;DOMINO TILE VERTICAL-01-04;So;0;ON;;;;;N;;;;; 1F06F;DOMINO TILE VERTICAL-01-05;So;0;ON;;;;;N;;;;; 1F070;DOMINO TILE VERTICAL-01-06;So;0;ON;;;;;N;;;;; 1F071;DOMINO TILE VERTICAL-02-00;So;0;ON;;;;;N;;;;; 1F072;DOMINO TILE VERTICAL-02-01;So;0;ON;;;;;N;;;;; 1F073;DOMINO TILE VERTICAL-02-02;So;0;ON;;;;;N;;;;; 1F074;DOMINO TILE VERTICAL-02-03;So;0;ON;;;;;N;;;;; 1F075;DOMINO TILE VERTICAL-02-04;So;0;ON;;;;;N;;;;; 1F076;DOMINO TILE VERTICAL-02-05;So;0;ON;;;;;N;;;;; 1F077;DOMINO TILE VERTICAL-02-06;So;0;ON;;;;;N;;;;; 1F078;DOMINO TILE VERTICAL-03-00;So;0;ON;;;;;N;;;;; 1F079;DOMINO TILE VERTICAL-03-01;So;0;ON;;;;;N;;;;; 1F07A;DOMINO TILE VERTICAL-03-02;So;0;ON;;;;;N;;;;; 1F07B;DOMINO TILE VERTICAL-03-03;So;0;ON;;;;;N;;;;; 1F07C;DOMINO TILE VERTICAL-03-04;So;0;ON;;;;;N;;;;; 1F07D;DOMINO TILE VERTICAL-03-05;So;0;ON;;;;;N;;;;; 1F07E;DOMINO TILE VERTICAL-03-06;So;0;ON;;;;;N;;;;; 1F07F;DOMINO TILE VERTICAL-04-00;So;0;ON;;;;;N;;;;; 1F080;DOMINO TILE VERTICAL-04-01;So;0;ON;;;;;N;;;;; 1F081;DOMINO TILE VERTICAL-04-02;So;0;ON;;;;;N;;;;; 1F082;DOMINO TILE VERTICAL-04-03;So;0;ON;;;;;N;;;;; 1F083;DOMINO TILE VERTICAL-04-04;So;0;ON;;;;;N;;;;; 1F084;DOMINO TILE VERTICAL-04-05;So;0;ON;;;;;N;;;;; 1F085;DOMINO TILE VERTICAL-04-06;So;0;ON;;;;;N;;;;; 1F086;DOMINO TILE VERTICAL-05-00;So;0;ON;;;;;N;;;;; 1F087;DOMINO TILE VERTICAL-05-01;So;0;ON;;;;;N;;;;; 1F088;DOMINO TILE VERTICAL-05-02;So;0;ON;;;;;N;;;;; 1F089;DOMINO TILE VERTICAL-05-03;So;0;ON;;;;;N;;;;; 1F08A;DOMINO TILE VERTICAL-05-04;So;0;ON;;;;;N;;;;; 1F08B;DOMINO TILE VERTICAL-05-05;So;0;ON;;;;;N;;;;; 1F08C;DOMINO TILE VERTICAL-05-06;So;0;ON;;;;;N;;;;; 1F08D;DOMINO TILE VERTICAL-06-00;So;0;ON;;;;;N;;;;; 1F08E;DOMINO TILE VERTICAL-06-01;So;0;ON;;;;;N;;;;; 1F08F;DOMINO TILE VERTICAL-06-02;So;0;ON;;;;;N;;;;; 1F090;DOMINO TILE VERTICAL-06-03;So;0;ON;;;;;N;;;;; 1F091;DOMINO TILE VERTICAL-06-04;So;0;ON;;;;;N;;;;; 1F092;DOMINO TILE VERTICAL-06-05;So;0;ON;;;;;N;;;;; 1F093;DOMINO TILE VERTICAL-06-06;So;0;ON;;;;;N;;;;; 1F0A0;PLAYING CARD BACK;So;0;ON;;;;;N;;;;; 1F0A1;PLAYING CARD ACE OF SPADES;So;0;ON;;;;;N;;;;; 1F0A2;PLAYING CARD TWO OF SPADES;So;0;ON;;;;;N;;;;; 1F0A3;PLAYING CARD THREE OF SPADES;So;0;ON;;;;;N;;;;; 1F0A4;PLAYING CARD FOUR OF SPADES;So;0;ON;;;;;N;;;;; 1F0A5;PLAYING CARD FIVE OF SPADES;So;0;ON;;;;;N;;;;; 1F0A6;PLAYING CARD SIX OF SPADES;So;0;ON;;;;;N;;;;; 1F0A7;PLAYING CARD SEVEN OF SPADES;So;0;ON;;;;;N;;;;; 1F0A8;PLAYING CARD EIGHT OF SPADES;So;0;ON;;;;;N;;;;; 1F0A9;PLAYING CARD NINE OF SPADES;So;0;ON;;;;;N;;;;; 1F0AA;PLAYING CARD TEN OF SPADES;So;0;ON;;;;;N;;;;; 1F0AB;PLAYING CARD JACK OF SPADES;So;0;ON;;;;;N;;;;; 1F0AC;PLAYING CARD KNIGHT OF SPADES;So;0;ON;;;;;N;;;;; 1F0AD;PLAYING CARD QUEEN OF SPADES;So;0;ON;;;;;N;;;;; 1F0AE;PLAYING CARD KING OF SPADES;So;0;ON;;;;;N;;;;; 1F0B1;PLAYING CARD ACE OF HEARTS;So;0;ON;;;;;N;;;;; 1F0B2;PLAYING CARD TWO OF HEARTS;So;0;ON;;;;;N;;;;; 1F0B3;PLAYING CARD THREE OF HEARTS;So;0;ON;;;;;N;;;;; 1F0B4;PLAYING CARD FOUR OF HEARTS;So;0;ON;;;;;N;;;;; 1F0B5;PLAYING CARD FIVE OF HEARTS;So;0;ON;;;;;N;;;;; 1F0B6;PLAYING CARD SIX OF HEARTS;So;0;ON;;;;;N;;;;; 1F0B7;PLAYING CARD SEVEN OF HEARTS;So;0;ON;;;;;N;;;;; 1F0B8;PLAYING CARD EIGHT OF HEARTS;So;0;ON;;;;;N;;;;; 1F0B9;PLAYING CARD NINE OF HEARTS;So;0;ON;;;;;N;;;;; 1F0BA;PLAYING CARD TEN OF HEARTS;So;0;ON;;;;;N;;;;; 1F0BB;PLAYING CARD JACK OF HEARTS;So;0;ON;;;;;N;;;;; 1F0BC;PLAYING CARD KNIGHT OF HEARTS;So;0;ON;;;;;N;;;;; 1F0BD;PLAYING CARD QUEEN OF HEARTS;So;0;ON;;;;;N;;;;; 1F0BE;PLAYING CARD KING OF HEARTS;So;0;ON;;;;;N;;;;; 1F0BF;PLAYING CARD RED JOKER;So;0;ON;;;;;N;;;;; 1F0C1;PLAYING CARD ACE OF DIAMONDS;So;0;ON;;;;;N;;;;; 1F0C2;PLAYING CARD TWO OF DIAMONDS;So;0;ON;;;;;N;;;;; 1F0C3;PLAYING CARD THREE OF DIAMONDS;So;0;ON;;;;;N;;;;; 1F0C4;PLAYING CARD FOUR OF DIAMONDS;So;0;ON;;;;;N;;;;; 1F0C5;PLAYING CARD FIVE OF DIAMONDS;So;0;ON;;;;;N;;;;; 1F0C6;PLAYING CARD SIX OF DIAMONDS;So;0;ON;;;;;N;;;;; 1F0C7;PLAYING CARD SEVEN OF DIAMONDS;So;0;ON;;;;;N;;;;; 1F0C8;PLAYING CARD EIGHT OF DIAMONDS;So;0;ON;;;;;N;;;;; 1F0C9;PLAYING CARD NINE OF DIAMONDS;So;0;ON;;;;;N;;;;; 1F0CA;PLAYING CARD TEN OF DIAMONDS;So;0;ON;;;;;N;;;;; 1F0CB;PLAYING CARD JACK OF DIAMONDS;So;0;ON;;;;;N;;;;; 1F0CC;PLAYING CARD KNIGHT OF DIAMONDS;So;0;ON;;;;;N;;;;; 1F0CD;PLAYING CARD QUEEN OF DIAMONDS;So;0;ON;;;;;N;;;;; 1F0CE;PLAYING CARD KING OF DIAMONDS;So;0;ON;;;;;N;;;;; 1F0CF;PLAYING CARD BLACK JOKER;So;0;ON;;;;;N;;;;; 1F0D1;PLAYING CARD ACE OF CLUBS;So;0;ON;;;;;N;;;;; 1F0D2;PLAYING CARD TWO OF CLUBS;So;0;ON;;;;;N;;;;; 1F0D3;PLAYING CARD THREE OF CLUBS;So;0;ON;;;;;N;;;;; 1F0D4;PLAYING CARD FOUR OF CLUBS;So;0;ON;;;;;N;;;;; 1F0D5;PLAYING CARD FIVE OF CLUBS;So;0;ON;;;;;N;;;;; 1F0D6;PLAYING CARD SIX OF CLUBS;So;0;ON;;;;;N;;;;; 1F0D7;PLAYING CARD SEVEN OF CLUBS;So;0;ON;;;;;N;;;;; 1F0D8;PLAYING CARD EIGHT OF CLUBS;So;0;ON;;;;;N;;;;; 1F0D9;PLAYING CARD NINE OF CLUBS;So;0;ON;;;;;N;;;;; 1F0DA;PLAYING CARD TEN OF CLUBS;So;0;ON;;;;;N;;;;; 1F0DB;PLAYING CARD JACK OF CLUBS;So;0;ON;;;;;N;;;;; 1F0DC;PLAYING CARD KNIGHT OF CLUBS;So;0;ON;;;;;N;;;;; 1F0DD;PLAYING CARD QUEEN OF CLUBS;So;0;ON;;;;;N;;;;; 1F0DE;PLAYING CARD KING OF CLUBS;So;0;ON;;;;;N;;;;; 1F0DF;PLAYING CARD WHITE JOKER;So;0;ON;;;;;N;;;;; 1F0E0;PLAYING CARD FOOL;So;0;ON;;;;;N;;;;; 1F0E1;PLAYING CARD TRUMP-1;So;0;ON;;;;;N;;;;; 1F0E2;PLAYING CARD TRUMP-2;So;0;ON;;;;;N;;;;; 1F0E3;PLAYING CARD TRUMP-3;So;0;ON;;;;;N;;;;; 1F0E4;PLAYING CARD TRUMP-4;So;0;ON;;;;;N;;;;; 1F0E5;PLAYING CARD TRUMP-5;So;0;ON;;;;;N;;;;; 1F0E6;PLAYING CARD TRUMP-6;So;0;ON;;;;;N;;;;; 1F0E7;PLAYING CARD TRUMP-7;So;0;ON;;;;;N;;;;; 1F0E8;PLAYING CARD TRUMP-8;So;0;ON;;;;;N;;;;; 1F0E9;PLAYING CARD TRUMP-9;So;0;ON;;;;;N;;;;; 1F0EA;PLAYING CARD TRUMP-10;So;0;ON;;;;;N;;;;; 1F0EB;PLAYING CARD TRUMP-11;So;0;ON;;;;;N;;;;; 1F0EC;PLAYING CARD TRUMP-12;So;0;ON;;;;;N;;;;; 1F0ED;PLAYING CARD TRUMP-13;So;0;ON;;;;;N;;;;; 1F0EE;PLAYING CARD TRUMP-14;So;0;ON;;;;;N;;;;; 1F0EF;PLAYING CARD TRUMP-15;So;0;ON;;;;;N;;;;; 1F0F0;PLAYING CARD TRUMP-16;So;0;ON;;;;;N;;;;; 1F0F1;PLAYING CARD TRUMP-17;So;0;ON;;;;;N;;;;; 1F0F2;PLAYING CARD TRUMP-18;So;0;ON;;;;;N;;;;; 1F0F3;PLAYING CARD TRUMP-19;So;0;ON;;;;;N;;;;; 1F0F4;PLAYING CARD TRUMP-20;So;0;ON;;;;;N;;;;; 1F0F5;PLAYING CARD TRUMP-21;So;0;ON;;;;;N;;;;; 1F100;DIGIT ZERO FULL STOP;No;0;EN; 0030 002E;;0;0;N;;;;; 1F101;DIGIT ZERO COMMA;No;0;EN; 0030 002C;;0;0;N;;;;; 1F102;DIGIT ONE COMMA;No;0;EN; 0031 002C;;1;1;N;;;;; 1F103;DIGIT TWO COMMA;No;0;EN; 0032 002C;;2;2;N;;;;; 1F104;DIGIT THREE COMMA;No;0;EN; 0033 002C;;3;3;N;;;;; 1F105;DIGIT FOUR COMMA;No;0;EN; 0034 002C;;4;4;N;;;;; 1F106;DIGIT FIVE COMMA;No;0;EN; 0035 002C;;5;5;N;;;;; 1F107;DIGIT SIX COMMA;No;0;EN; 0036 002C;;6;6;N;;;;; 1F108;DIGIT SEVEN COMMA;No;0;EN; 0037 002C;;7;7;N;;;;; 1F109;DIGIT EIGHT COMMA;No;0;EN; 0038 002C;;8;8;N;;;;; 1F10A;DIGIT NINE COMMA;No;0;EN; 0039 002C;;9;9;N;;;;; 1F10B;DINGBAT CIRCLED SANS-SERIF DIGIT ZERO;No;0;ON;;;;0;N;;;;; 1F10C;DINGBAT NEGATIVE CIRCLED SANS-SERIF DIGIT ZERO;No;0;ON;;;;0;N;;;;; 1F110;PARENTHESIZED LATIN CAPITAL LETTER A;So;0;L; 0028 0041 0029;;;;N;;;;; 1F111;PARENTHESIZED LATIN CAPITAL LETTER B;So;0;L; 0028 0042 0029;;;;N;;;;; 1F112;PARENTHESIZED LATIN CAPITAL LETTER C;So;0;L; 0028 0043 0029;;;;N;;;;; 1F113;PARENTHESIZED LATIN CAPITAL LETTER D;So;0;L; 0028 0044 0029;;;;N;;;;; 1F114;PARENTHESIZED LATIN CAPITAL LETTER E;So;0;L; 0028 0045 0029;;;;N;;;;; 1F115;PARENTHESIZED LATIN CAPITAL LETTER F;So;0;L; 0028 0046 0029;;;;N;;;;; 1F116;PARENTHESIZED LATIN CAPITAL LETTER G;So;0;L; 0028 0047 0029;;;;N;;;;; 1F117;PARENTHESIZED LATIN CAPITAL LETTER H;So;0;L; 0028 0048 0029;;;;N;;;;; 1F118;PARENTHESIZED LATIN CAPITAL LETTER I;So;0;L; 0028 0049 0029;;;;N;;;;; 1F119;PARENTHESIZED LATIN CAPITAL LETTER J;So;0;L; 0028 004A 0029;;;;N;;;;; 1F11A;PARENTHESIZED LATIN CAPITAL LETTER K;So;0;L; 0028 004B 0029;;;;N;;;;; 1F11B;PARENTHESIZED LATIN CAPITAL LETTER L;So;0;L; 0028 004C 0029;;;;N;;;;; 1F11C;PARENTHESIZED LATIN CAPITAL LETTER M;So;0;L; 0028 004D 0029;;;;N;;;;; 1F11D;PARENTHESIZED LATIN CAPITAL LETTER N;So;0;L; 0028 004E 0029;;;;N;;;;; 1F11E;PARENTHESIZED LATIN CAPITAL LETTER O;So;0;L; 0028 004F 0029;;;;N;;;;; 1F11F;PARENTHESIZED LATIN CAPITAL LETTER P;So;0;L; 0028 0050 0029;;;;N;;;;; 1F120;PARENTHESIZED LATIN CAPITAL LETTER Q;So;0;L; 0028 0051 0029;;;;N;;;;; 1F121;PARENTHESIZED LATIN CAPITAL LETTER R;So;0;L; 0028 0052 0029;;;;N;;;;; 1F122;PARENTHESIZED LATIN CAPITAL LETTER S;So;0;L; 0028 0053 0029;;;;N;;;;; 1F123;PARENTHESIZED LATIN CAPITAL LETTER T;So;0;L; 0028 0054 0029;;;;N;;;;; 1F124;PARENTHESIZED LATIN CAPITAL LETTER U;So;0;L; 0028 0055 0029;;;;N;;;;; 1F125;PARENTHESIZED LATIN CAPITAL LETTER V;So;0;L; 0028 0056 0029;;;;N;;;;; 1F126;PARENTHESIZED LATIN CAPITAL LETTER W;So;0;L; 0028 0057 0029;;;;N;;;;; 1F127;PARENTHESIZED LATIN CAPITAL LETTER X;So;0;L; 0028 0058 0029;;;;N;;;;; 1F128;PARENTHESIZED LATIN CAPITAL LETTER Y;So;0;L; 0028 0059 0029;;;;N;;;;; 1F129;PARENTHESIZED LATIN CAPITAL LETTER Z;So;0;L; 0028 005A 0029;;;;N;;;;; 1F12A;TORTOISE SHELL BRACKETED LATIN CAPITAL LETTER S;So;0;L; 3014 0053 3015;;;;N;;;;; 1F12B;CIRCLED ITALIC LATIN CAPITAL LETTER C;So;0;L; 0043;;;;N;;;;; 1F12C;CIRCLED ITALIC LATIN CAPITAL LETTER R;So;0;L; 0052;;;;N;;;;; 1F12D;CIRCLED CD;So;0;L; 0043 0044;;;;N;;;;; 1F12E;CIRCLED WZ;So;0;L; 0057 005A;;;;N;;;;; 1F130;SQUARED LATIN CAPITAL LETTER A;So;0;L; 0041;;;;N;;;;; 1F131;SQUARED LATIN CAPITAL LETTER B;So;0;L; 0042;;;;N;;;;; 1F132;SQUARED LATIN CAPITAL LETTER C;So;0;L; 0043;;;;N;;;;; 1F133;SQUARED LATIN CAPITAL LETTER D;So;0;L; 0044;;;;N;;;;; 1F134;SQUARED LATIN CAPITAL LETTER E;So;0;L; 0045;;;;N;;;;; 1F135;SQUARED LATIN CAPITAL LETTER F;So;0;L; 0046;;;;N;;;;; 1F136;SQUARED LATIN CAPITAL LETTER G;So;0;L; 0047;;;;N;;;;; 1F137;SQUARED LATIN CAPITAL LETTER H;So;0;L; 0048;;;;N;;;;; 1F138;SQUARED LATIN CAPITAL LETTER I;So;0;L; 0049;;;;N;;;;; 1F139;SQUARED LATIN CAPITAL LETTER J;So;0;L; 004A;;;;N;;;;; 1F13A;SQUARED LATIN CAPITAL LETTER K;So;0;L; 004B;;;;N;;;;; 1F13B;SQUARED LATIN CAPITAL LETTER L;So;0;L; 004C;;;;N;;;;; 1F13C;SQUARED LATIN CAPITAL LETTER M;So;0;L; 004D;;;;N;;;;; 1F13D;SQUARED LATIN CAPITAL LETTER N;So;0;L; 004E;;;;N;;;;; 1F13E;SQUARED LATIN CAPITAL LETTER O;So;0;L; 004F;;;;N;;;;; 1F13F;SQUARED LATIN CAPITAL LETTER P;So;0;L; 0050;;;;N;;;;; 1F140;SQUARED LATIN CAPITAL LETTER Q;So;0;L; 0051;;;;N;;;;; 1F141;SQUARED LATIN CAPITAL LETTER R;So;0;L; 0052;;;;N;;;;; 1F142;SQUARED LATIN CAPITAL LETTER S;So;0;L; 0053;;;;N;;;;; 1F143;SQUARED LATIN CAPITAL LETTER T;So;0;L; 0054;;;;N;;;;; 1F144;SQUARED LATIN CAPITAL LETTER U;So;0;L; 0055;;;;N;;;;; 1F145;SQUARED LATIN CAPITAL LETTER V;So;0;L; 0056;;;;N;;;;; 1F146;SQUARED LATIN CAPITAL LETTER W;So;0;L; 0057;;;;N;;;;; 1F147;SQUARED LATIN CAPITAL LETTER X;So;0;L; 0058;;;;N;;;;; 1F148;SQUARED LATIN CAPITAL LETTER Y;So;0;L; 0059;;;;N;;;;; 1F149;SQUARED LATIN CAPITAL LETTER Z;So;0;L; 005A;;;;N;;;;; 1F14A;SQUARED HV;So;0;L; 0048 0056;;;;N;;;;; 1F14B;SQUARED MV;So;0;L; 004D 0056;;;;N;;;;; 1F14C;SQUARED SD;So;0;L; 0053 0044;;;;N;;;;; 1F14D;SQUARED SS;So;0;L; 0053 0053;;;;N;;;;; 1F14E;SQUARED PPV;So;0;L; 0050 0050 0056;;;;N;;;;; 1F14F;SQUARED WC;So;0;L; 0057 0043;;;;N;;;;; 1F150;NEGATIVE CIRCLED LATIN CAPITAL LETTER A;So;0;L;;;;;N;;;;; 1F151;NEGATIVE CIRCLED LATIN CAPITAL LETTER B;So;0;L;;;;;N;;;;; 1F152;NEGATIVE CIRCLED LATIN CAPITAL LETTER C;So;0;L;;;;;N;;;;; 1F153;NEGATIVE CIRCLED LATIN CAPITAL LETTER D;So;0;L;;;;;N;;;;; 1F154;NEGATIVE CIRCLED LATIN CAPITAL LETTER E;So;0;L;;;;;N;;;;; 1F155;NEGATIVE CIRCLED LATIN CAPITAL LETTER F;So;0;L;;;;;N;;;;; 1F156;NEGATIVE CIRCLED LATIN CAPITAL LETTER G;So;0;L;;;;;N;;;;; 1F157;NEGATIVE CIRCLED LATIN CAPITAL LETTER H;So;0;L;;;;;N;;;;; 1F158;NEGATIVE CIRCLED LATIN CAPITAL LETTER I;So;0;L;;;;;N;;;;; 1F159;NEGATIVE CIRCLED LATIN CAPITAL LETTER J;So;0;L;;;;;N;;;;; 1F15A;NEGATIVE CIRCLED LATIN CAPITAL LETTER K;So;0;L;;;;;N;;;;; 1F15B;NEGATIVE CIRCLED LATIN CAPITAL LETTER L;So;0;L;;;;;N;;;;; 1F15C;NEGATIVE CIRCLED LATIN CAPITAL LETTER M;So;0;L;;;;;N;;;;; 1F15D;NEGATIVE CIRCLED LATIN CAPITAL LETTER N;So;0;L;;;;;N;;;;; 1F15E;NEGATIVE CIRCLED LATIN CAPITAL LETTER O;So;0;L;;;;;N;;;;; 1F15F;NEGATIVE CIRCLED LATIN CAPITAL LETTER P;So;0;L;;;;;N;;;;; 1F160;NEGATIVE CIRCLED LATIN CAPITAL LETTER Q;So;0;L;;;;;N;;;;; 1F161;NEGATIVE CIRCLED LATIN CAPITAL LETTER R;So;0;L;;;;;N;;;;; 1F162;NEGATIVE CIRCLED LATIN CAPITAL LETTER S;So;0;L;;;;;N;;;;; 1F163;NEGATIVE CIRCLED LATIN CAPITAL LETTER T;So;0;L;;;;;N;;;;; 1F164;NEGATIVE CIRCLED LATIN CAPITAL LETTER U;So;0;L;;;;;N;;;;; 1F165;NEGATIVE CIRCLED LATIN CAPITAL LETTER V;So;0;L;;;;;N;;;;; 1F166;NEGATIVE CIRCLED LATIN CAPITAL LETTER W;So;0;L;;;;;N;;;;; 1F167;NEGATIVE CIRCLED LATIN CAPITAL LETTER X;So;0;L;;;;;N;;;;; 1F168;NEGATIVE CIRCLED LATIN CAPITAL LETTER Y;So;0;L;;;;;N;;;;; 1F169;NEGATIVE CIRCLED LATIN CAPITAL LETTER Z;So;0;L;;;;;N;;;;; 1F16A;RAISED MC SIGN;So;0;ON; 004D 0043;;;;N;;;;; 1F16B;RAISED MD SIGN;So;0;ON; 004D 0044;;;;N;;;;; 1F170;NEGATIVE SQUARED LATIN CAPITAL LETTER A;So;0;L;;;;;N;;;;; 1F171;NEGATIVE SQUARED LATIN CAPITAL LETTER B;So;0;L;;;;;N;;;;; 1F172;NEGATIVE SQUARED LATIN CAPITAL LETTER C;So;0;L;;;;;N;;;;; 1F173;NEGATIVE SQUARED LATIN CAPITAL LETTER D;So;0;L;;;;;N;;;;; 1F174;NEGATIVE SQUARED LATIN CAPITAL LETTER E;So;0;L;;;;;N;;;;; 1F175;NEGATIVE SQUARED LATIN CAPITAL LETTER F;So;0;L;;;;;N;;;;; 1F176;NEGATIVE SQUARED LATIN CAPITAL LETTER G;So;0;L;;;;;N;;;;; 1F177;NEGATIVE SQUARED LATIN CAPITAL LETTER H;So;0;L;;;;;N;;;;; 1F178;NEGATIVE SQUARED LATIN CAPITAL LETTER I;So;0;L;;;;;N;;;;; 1F179;NEGATIVE SQUARED LATIN CAPITAL LETTER J;So;0;L;;;;;N;;;;; 1F17A;NEGATIVE SQUARED LATIN CAPITAL LETTER K;So;0;L;;;;;N;;;;; 1F17B;NEGATIVE SQUARED LATIN CAPITAL LETTER L;So;0;L;;;;;N;;;;; 1F17C;NEGATIVE SQUARED LATIN CAPITAL LETTER M;So;0;L;;;;;N;;;;; 1F17D;NEGATIVE SQUARED LATIN CAPITAL LETTER N;So;0;L;;;;;N;;;;; 1F17E;NEGATIVE SQUARED LATIN CAPITAL LETTER O;So;0;L;;;;;N;;;;; 1F17F;NEGATIVE SQUARED LATIN CAPITAL LETTER P;So;0;L;;;;;N;;;;; 1F180;NEGATIVE SQUARED LATIN CAPITAL LETTER Q;So;0;L;;;;;N;;;;; 1F181;NEGATIVE SQUARED LATIN CAPITAL LETTER R;So;0;L;;;;;N;;;;; 1F182;NEGATIVE SQUARED LATIN CAPITAL LETTER S;So;0;L;;;;;N;;;;; 1F183;NEGATIVE SQUARED LATIN CAPITAL LETTER T;So;0;L;;;;;N;;;;; 1F184;NEGATIVE SQUARED LATIN CAPITAL LETTER U;So;0;L;;;;;N;;;;; 1F185;NEGATIVE SQUARED LATIN CAPITAL LETTER V;So;0;L;;;;;N;;;;; 1F186;NEGATIVE SQUARED LATIN CAPITAL LETTER W;So;0;L;;;;;N;;;;; 1F187;NEGATIVE SQUARED LATIN CAPITAL LETTER X;So;0;L;;;;;N;;;;; 1F188;NEGATIVE SQUARED LATIN CAPITAL LETTER Y;So;0;L;;;;;N;;;;; 1F189;NEGATIVE SQUARED LATIN CAPITAL LETTER Z;So;0;L;;;;;N;;;;; 1F18A;CROSSED NEGATIVE SQUARED LATIN CAPITAL LETTER P;So;0;L;;;;;N;;;;; 1F18B;NEGATIVE SQUARED IC;So;0;L;;;;;N;;;;; 1F18C;NEGATIVE SQUARED PA;So;0;L;;;;;N;;;;; 1F18D;NEGATIVE SQUARED SA;So;0;L;;;;;N;;;;; 1F18E;NEGATIVE SQUARED AB;So;0;L;;;;;N;;;;; 1F18F;NEGATIVE SQUARED WC;So;0;L;;;;;N;;;;; 1F190;SQUARE DJ;So;0;L; 0044 004A;;;;N;;;;; 1F191;SQUARED CL;So;0;L;;;;;N;;;;; 1F192;SQUARED COOL;So;0;L;;;;;N;;;;; 1F193;SQUARED FREE;So;0;L;;;;;N;;;;; 1F194;SQUARED ID;So;0;L;;;;;N;;;;; 1F195;SQUARED NEW;So;0;L;;;;;N;;;;; 1F196;SQUARED NG;So;0;L;;;;;N;;;;; 1F197;SQUARED OK;So;0;L;;;;;N;;;;; 1F198;SQUARED SOS;So;0;L;;;;;N;;;;; 1F199;SQUARED UP WITH EXCLAMATION MARK;So;0;L;;;;;N;;;;; 1F19A;SQUARED VS;So;0;L;;;;;N;;;;; 1F1E6;REGIONAL INDICATOR SYMBOL LETTER A;So;0;L;;;;;N;;;;; 1F1E7;REGIONAL INDICATOR SYMBOL LETTER B;So;0;L;;;;;N;;;;; 1F1E8;REGIONAL INDICATOR SYMBOL LETTER C;So;0;L;;;;;N;;;;; 1F1E9;REGIONAL INDICATOR SYMBOL LETTER D;So;0;L;;;;;N;;;;; 1F1EA;REGIONAL INDICATOR SYMBOL LETTER E;So;0;L;;;;;N;;;;; 1F1EB;REGIONAL INDICATOR SYMBOL LETTER F;So;0;L;;;;;N;;;;; 1F1EC;REGIONAL INDICATOR SYMBOL LETTER G;So;0;L;;;;;N;;;;; 1F1ED;REGIONAL INDICATOR SYMBOL LETTER H;So;0;L;;;;;N;;;;; 1F1EE;REGIONAL INDICATOR SYMBOL LETTER I;So;0;L;;;;;N;;;;; 1F1EF;REGIONAL INDICATOR SYMBOL LETTER J;So;0;L;;;;;N;;;;; 1F1F0;REGIONAL INDICATOR SYMBOL LETTER K;So;0;L;;;;;N;;;;; 1F1F1;REGIONAL INDICATOR SYMBOL LETTER L;So;0;L;;;;;N;;;;; 1F1F2;REGIONAL INDICATOR SYMBOL LETTER M;So;0;L;;;;;N;;;;; 1F1F3;REGIONAL INDICATOR SYMBOL LETTER N;So;0;L;;;;;N;;;;; 1F1F4;REGIONAL INDICATOR SYMBOL LETTER O;So;0;L;;;;;N;;;;; 1F1F5;REGIONAL INDICATOR SYMBOL LETTER P;So;0;L;;;;;N;;;;; 1F1F6;REGIONAL INDICATOR SYMBOL LETTER Q;So;0;L;;;;;N;;;;; 1F1F7;REGIONAL INDICATOR SYMBOL LETTER R;So;0;L;;;;;N;;;;; 1F1F8;REGIONAL INDICATOR SYMBOL LETTER S;So;0;L;;;;;N;;;;; 1F1F9;REGIONAL INDICATOR SYMBOL LETTER T;So;0;L;;;;;N;;;;; 1F1FA;REGIONAL INDICATOR SYMBOL LETTER U;So;0;L;;;;;N;;;;; 1F1FB;REGIONAL INDICATOR SYMBOL LETTER V;So;0;L;;;;;N;;;;; 1F1FC;REGIONAL INDICATOR SYMBOL LETTER W;So;0;L;;;;;N;;;;; 1F1FD;REGIONAL INDICATOR SYMBOL LETTER X;So;0;L;;;;;N;;;;; 1F1FE;REGIONAL INDICATOR SYMBOL LETTER Y;So;0;L;;;;;N;;;;; 1F1FF;REGIONAL INDICATOR SYMBOL LETTER Z;So;0;L;;;;;N;;;;; 1F200;SQUARE HIRAGANA HOKA;So;0;L; 307B 304B;;;;N;;;;; 1F201;SQUARED KATAKANA KOKO;So;0;L; 30B3 30B3;;;;N;;;;; 1F202;SQUARED KATAKANA SA;So;0;L; 30B5;;;;N;;;;; 1F210;SQUARED CJK UNIFIED IDEOGRAPH-624B;So;0;L; 624B;;;;N;;;;; 1F211;SQUARED CJK UNIFIED IDEOGRAPH-5B57;So;0;L; 5B57;;;;N;;;;; 1F212;SQUARED CJK UNIFIED IDEOGRAPH-53CC;So;0;L; 53CC;;;;N;;;;; 1F213;SQUARED KATAKANA DE;So;0;L; 30C7;;;;N;;;;; 1F214;SQUARED CJK UNIFIED IDEOGRAPH-4E8C;So;0;L; 4E8C;;;;N;;;;; 1F215;SQUARED CJK UNIFIED IDEOGRAPH-591A;So;0;L; 591A;;;;N;;;;; 1F216;SQUARED CJK UNIFIED IDEOGRAPH-89E3;So;0;L; 89E3;;;;N;;;;; 1F217;SQUARED CJK UNIFIED IDEOGRAPH-5929;So;0;L; 5929;;;;N;;;;; 1F218;SQUARED CJK UNIFIED IDEOGRAPH-4EA4;So;0;L; 4EA4;;;;N;;;;; 1F219;SQUARED CJK UNIFIED IDEOGRAPH-6620;So;0;L; 6620;;;;N;;;;; 1F21A;SQUARED CJK UNIFIED IDEOGRAPH-7121;So;0;L; 7121;;;;N;;;;; 1F21B;SQUARED CJK UNIFIED IDEOGRAPH-6599;So;0;L; 6599;;;;N;;;;; 1F21C;SQUARED CJK UNIFIED IDEOGRAPH-524D;So;0;L; 524D;;;;N;;;;; 1F21D;SQUARED CJK UNIFIED IDEOGRAPH-5F8C;So;0;L; 5F8C;;;;N;;;;; 1F21E;SQUARED CJK UNIFIED IDEOGRAPH-518D;So;0;L; 518D;;;;N;;;;; 1F21F;SQUARED CJK UNIFIED IDEOGRAPH-65B0;So;0;L; 65B0;;;;N;;;;; 1F220;SQUARED CJK UNIFIED IDEOGRAPH-521D;So;0;L; 521D;;;;N;;;;; 1F221;SQUARED CJK UNIFIED IDEOGRAPH-7D42;So;0;L; 7D42;;;;N;;;;; 1F222;SQUARED CJK UNIFIED IDEOGRAPH-751F;So;0;L; 751F;;;;N;;;;; 1F223;SQUARED CJK UNIFIED IDEOGRAPH-8CA9;So;0;L; 8CA9;;;;N;;;;; 1F224;SQUARED CJK UNIFIED IDEOGRAPH-58F0;So;0;L; 58F0;;;;N;;;;; 1F225;SQUARED CJK UNIFIED IDEOGRAPH-5439;So;0;L; 5439;;;;N;;;;; 1F226;SQUARED CJK UNIFIED IDEOGRAPH-6F14;So;0;L; 6F14;;;;N;;;;; 1F227;SQUARED CJK UNIFIED IDEOGRAPH-6295;So;0;L; 6295;;;;N;;;;; 1F228;SQUARED CJK UNIFIED IDEOGRAPH-6355;So;0;L; 6355;;;;N;;;;; 1F229;SQUARED CJK UNIFIED IDEOGRAPH-4E00;So;0;L; 4E00;;;;N;;;;; 1F22A;SQUARED CJK UNIFIED IDEOGRAPH-4E09;So;0;L; 4E09;;;;N;;;;; 1F22B;SQUARED CJK UNIFIED IDEOGRAPH-904A;So;0;L; 904A;;;;N;;;;; 1F22C;SQUARED CJK UNIFIED IDEOGRAPH-5DE6;So;0;L; 5DE6;;;;N;;;;; 1F22D;SQUARED CJK UNIFIED IDEOGRAPH-4E2D;So;0;L; 4E2D;;;;N;;;;; 1F22E;SQUARED CJK UNIFIED IDEOGRAPH-53F3;So;0;L; 53F3;;;;N;;;;; 1F22F;SQUARED CJK UNIFIED IDEOGRAPH-6307;So;0;L; 6307;;;;N;;;;; 1F230;SQUARED CJK UNIFIED IDEOGRAPH-8D70;So;0;L; 8D70;;;;N;;;;; 1F231;SQUARED CJK UNIFIED IDEOGRAPH-6253;So;0;L; 6253;;;;N;;;;; 1F232;SQUARED CJK UNIFIED IDEOGRAPH-7981;So;0;L; 7981;;;;N;;;;; 1F233;SQUARED CJK UNIFIED IDEOGRAPH-7A7A;So;0;L; 7A7A;;;;N;;;;; 1F234;SQUARED CJK UNIFIED IDEOGRAPH-5408;So;0;L; 5408;;;;N;;;;; 1F235;SQUARED CJK UNIFIED IDEOGRAPH-6E80;So;0;L; 6E80;;;;N;;;;; 1F236;SQUARED CJK UNIFIED IDEOGRAPH-6709;So;0;L; 6709;;;;N;;;;; 1F237;SQUARED CJK UNIFIED IDEOGRAPH-6708;So;0;L; 6708;;;;N;;;;; 1F238;SQUARED CJK UNIFIED IDEOGRAPH-7533;So;0;L; 7533;;;;N;;;;; 1F239;SQUARED CJK UNIFIED IDEOGRAPH-5272;So;0;L; 5272;;;;N;;;;; 1F23A;SQUARED CJK UNIFIED IDEOGRAPH-55B6;So;0;L; 55B6;;;;N;;;;; 1F240;TORTOISE SHELL BRACKETED CJK UNIFIED IDEOGRAPH-672C;So;0;L; 3014 672C 3015;;;;N;;;;; 1F241;TORTOISE SHELL BRACKETED CJK UNIFIED IDEOGRAPH-4E09;So;0;L; 3014 4E09 3015;;;;N;;;;; 1F242;TORTOISE SHELL BRACKETED CJK UNIFIED IDEOGRAPH-4E8C;So;0;L; 3014 4E8C 3015;;;;N;;;;; 1F243;TORTOISE SHELL BRACKETED CJK UNIFIED IDEOGRAPH-5B89;So;0;L; 3014 5B89 3015;;;;N;;;;; 1F244;TORTOISE SHELL BRACKETED CJK UNIFIED IDEOGRAPH-70B9;So;0;L; 3014 70B9 3015;;;;N;;;;; 1F245;TORTOISE SHELL BRACKETED CJK UNIFIED IDEOGRAPH-6253;So;0;L; 3014 6253 3015;;;;N;;;;; 1F246;TORTOISE SHELL BRACKETED CJK UNIFIED IDEOGRAPH-76D7;So;0;L; 3014 76D7 3015;;;;N;;;;; 1F247;TORTOISE SHELL BRACKETED CJK UNIFIED IDEOGRAPH-52DD;So;0;L; 3014 52DD 3015;;;;N;;;;; 1F248;TORTOISE SHELL BRACKETED CJK UNIFIED IDEOGRAPH-6557;So;0;L; 3014 6557 3015;;;;N;;;;; 1F250;CIRCLED IDEOGRAPH ADVANTAGE;So;0;L; 5F97;;;;N;;;;; 1F251;CIRCLED IDEOGRAPH ACCEPT;So;0;L; 53EF;;;;N;;;;; 1F300;CYCLONE;So;0;ON;;;;;N;;;;; 1F301;FOGGY;So;0;ON;;;;;N;;;;; 1F302;CLOSED UMBRELLA;So;0;ON;;;;;N;;;;; 1F303;NIGHT WITH STARS;So;0;ON;;;;;N;;;;; 1F304;SUNRISE OVER MOUNTAINS;So;0;ON;;;;;N;;;;; 1F305;SUNRISE;So;0;ON;;;;;N;;;;; 1F306;CITYSCAPE AT DUSK;So;0;ON;;;;;N;;;;; 1F307;SUNSET OVER BUILDINGS;So;0;ON;;;;;N;;;;; 1F308;RAINBOW;So;0;ON;;;;;N;;;;; 1F309;BRIDGE AT NIGHT;So;0;ON;;;;;N;;;;; 1F30A;WATER WAVE;So;0;ON;;;;;N;;;;; 1F30B;VOLCANO;So;0;ON;;;;;N;;;;; 1F30C;MILKY WAY;So;0;ON;;;;;N;;;;; 1F30D;EARTH GLOBE EUROPE-AFRICA;So;0;ON;;;;;N;;;;; 1F30E;EARTH GLOBE AMERICAS;So;0;ON;;;;;N;;;;; 1F30F;EARTH GLOBE ASIA-AUSTRALIA;So;0;ON;;;;;N;;;;; 1F310;GLOBE WITH MERIDIANS;So;0;ON;;;;;N;;;;; 1F311;NEW MOON SYMBOL;So;0;ON;;;;;N;;;;; 1F312;WAXING CRESCENT MOON SYMBOL;So;0;ON;;;;;N;;;;; 1F313;FIRST QUARTER MOON SYMBOL;So;0;ON;;;;;N;;;;; 1F314;WAXING GIBBOUS MOON SYMBOL;So;0;ON;;;;;N;;;;; 1F315;FULL MOON SYMBOL;So;0;ON;;;;;N;;;;; 1F316;WANING GIBBOUS MOON SYMBOL;So;0;ON;;;;;N;;;;; 1F317;LAST QUARTER MOON SYMBOL;So;0;ON;;;;;N;;;;; 1F318;WANING CRESCENT MOON SYMBOL;So;0;ON;;;;;N;;;;; 1F319;CRESCENT MOON;So;0;ON;;;;;N;;;;; 1F31A;NEW MOON WITH FACE;So;0;ON;;;;;N;;;;; 1F31B;FIRST QUARTER MOON WITH FACE;So;0;ON;;;;;N;;;;; 1F31C;LAST QUARTER MOON WITH FACE;So;0;ON;;;;;N;;;;; 1F31D;FULL MOON WITH FACE;So;0;ON;;;;;N;;;;; 1F31E;SUN WITH FACE;So;0;ON;;;;;N;;;;; 1F31F;GLOWING STAR;So;0;ON;;;;;N;;;;; 1F320;SHOOTING STAR;So;0;ON;;;;;N;;;;; 1F321;THERMOMETER;So;0;ON;;;;;N;;;;; 1F322;BLACK DROPLET;So;0;ON;;;;;N;;;;; 1F323;WHITE SUN;So;0;ON;;;;;N;;;;; 1F324;WHITE SUN WITH SMALL CLOUD;So;0;ON;;;;;N;;;;; 1F325;WHITE SUN BEHIND CLOUD;So;0;ON;;;;;N;;;;; 1F326;WHITE SUN BEHIND CLOUD WITH RAIN;So;0;ON;;;;;N;;;;; 1F327;CLOUD WITH RAIN;So;0;ON;;;;;N;;;;; 1F328;CLOUD WITH SNOW;So;0;ON;;;;;N;;;;; 1F329;CLOUD WITH LIGHTNING;So;0;ON;;;;;N;;;;; 1F32A;CLOUD WITH TORNADO;So;0;ON;;;;;N;;;;; 1F32B;FOG;So;0;ON;;;;;N;;;;; 1F32C;WIND BLOWING FACE;So;0;ON;;;;;N;;;;; 1F330;CHESTNUT;So;0;ON;;;;;N;;;;; 1F331;SEEDLING;So;0;ON;;;;;N;;;;; 1F332;EVERGREEN TREE;So;0;ON;;;;;N;;;;; 1F333;DECIDUOUS TREE;So;0;ON;;;;;N;;;;; 1F334;PALM TREE;So;0;ON;;;;;N;;;;; 1F335;CACTUS;So;0;ON;;;;;N;;;;; 1F336;HOT PEPPER;So;0;ON;;;;;N;;;;; 1F337;TULIP;So;0;ON;;;;;N;;;;; 1F338;CHERRY BLOSSOM;So;0;ON;;;;;N;;;;; 1F339;ROSE;So;0;ON;;;;;N;;;;; 1F33A;HIBISCUS;So;0;ON;;;;;N;;;;; 1F33B;SUNFLOWER;So;0;ON;;;;;N;;;;; 1F33C;BLOSSOM;So;0;ON;;;;;N;;;;; 1F33D;EAR OF MAIZE;So;0;ON;;;;;N;;;;; 1F33E;EAR OF RICE;So;0;ON;;;;;N;;;;; 1F33F;HERB;So;0;ON;;;;;N;;;;; 1F340;FOUR LEAF CLOVER;So;0;ON;;;;;N;;;;; 1F341;MAPLE LEAF;So;0;ON;;;;;N;;;;; 1F342;FALLEN LEAF;So;0;ON;;;;;N;;;;; 1F343;LEAF FLUTTERING IN WIND;So;0;ON;;;;;N;;;;; 1F344;MUSHROOM;So;0;ON;;;;;N;;;;; 1F345;TOMATO;So;0;ON;;;;;N;;;;; 1F346;AUBERGINE;So;0;ON;;;;;N;;;;; 1F347;GRAPES;So;0;ON;;;;;N;;;;; 1F348;MELON;So;0;ON;;;;;N;;;;; 1F349;WATERMELON;So;0;ON;;;;;N;;;;; 1F34A;TANGERINE;So;0;ON;;;;;N;;;;; 1F34B;LEMON;So;0;ON;;;;;N;;;;; 1F34C;BANANA;So;0;ON;;;;;N;;;;; 1F34D;PINEAPPLE;So;0;ON;;;;;N;;;;; 1F34E;RED APPLE;So;0;ON;;;;;N;;;;; 1F34F;GREEN APPLE;So;0;ON;;;;;N;;;;; 1F350;PEAR;So;0;ON;;;;;N;;;;; 1F351;PEACH;So;0;ON;;;;;N;;;;; 1F352;CHERRIES;So;0;ON;;;;;N;;;;; 1F353;STRAWBERRY;So;0;ON;;;;;N;;;;; 1F354;HAMBURGER;So;0;ON;;;;;N;;;;; 1F355;SLICE OF PIZZA;So;0;ON;;;;;N;;;;; 1F356;MEAT ON BONE;So;0;ON;;;;;N;;;;; 1F357;POULTRY LEG;So;0;ON;;;;;N;;;;; 1F358;RICE CRACKER;So;0;ON;;;;;N;;;;; 1F359;RICE BALL;So;0;ON;;;;;N;;;;; 1F35A;COOKED RICE;So;0;ON;;;;;N;;;;; 1F35B;CURRY AND RICE;So;0;ON;;;;;N;;;;; 1F35C;STEAMING BOWL;So;0;ON;;;;;N;;;;; 1F35D;SPAGHETTI;So;0;ON;;;;;N;;;;; 1F35E;BREAD;So;0;ON;;;;;N;;;;; 1F35F;FRENCH FRIES;So;0;ON;;;;;N;;;;; 1F360;ROASTED SWEET POTATO;So;0;ON;;;;;N;;;;; 1F361;DANGO;So;0;ON;;;;;N;;;;; 1F362;ODEN;So;0;ON;;;;;N;;;;; 1F363;SUSHI;So;0;ON;;;;;N;;;;; 1F364;FRIED SHRIMP;So;0;ON;;;;;N;;;;; 1F365;FISH CAKE WITH SWIRL DESIGN;So;0;ON;;;;;N;;;;; 1F366;SOFT ICE CREAM;So;0;ON;;;;;N;;;;; 1F367;SHAVED ICE;So;0;ON;;;;;N;;;;; 1F368;ICE CREAM;So;0;ON;;;;;N;;;;; 1F369;DOUGHNUT;So;0;ON;;;;;N;;;;; 1F36A;COOKIE;So;0;ON;;;;;N;;;;; 1F36B;CHOCOLATE BAR;So;0;ON;;;;;N;;;;; 1F36C;CANDY;So;0;ON;;;;;N;;;;; 1F36D;LOLLIPOP;So;0;ON;;;;;N;;;;; 1F36E;CUSTARD;So;0;ON;;;;;N;;;;; 1F36F;HONEY POT;So;0;ON;;;;;N;;;;; 1F370;SHORTCAKE;So;0;ON;;;;;N;;;;; 1F371;BENTO BOX;So;0;ON;;;;;N;;;;; 1F372;POT OF FOOD;So;0;ON;;;;;N;;;;; 1F373;COOKING;So;0;ON;;;;;N;;;;; 1F374;FORK AND KNIFE;So;0;ON;;;;;N;;;;; 1F375;TEACUP WITHOUT HANDLE;So;0;ON;;;;;N;;;;; 1F376;SAKE BOTTLE AND CUP;So;0;ON;;;;;N;;;;; 1F377;WINE GLASS;So;0;ON;;;;;N;;;;; 1F378;COCKTAIL GLASS;So;0;ON;;;;;N;;;;; 1F379;TROPICAL DRINK;So;0;ON;;;;;N;;;;; 1F37A;BEER MUG;So;0;ON;;;;;N;;;;; 1F37B;CLINKING BEER MUGS;So;0;ON;;;;;N;;;;; 1F37C;BABY BOTTLE;So;0;ON;;;;;N;;;;; 1F37D;FORK AND KNIFE WITH PLATE;So;0;ON;;;;;N;;;;; 1F380;RIBBON;So;0;ON;;;;;N;;;;; 1F381;WRAPPED PRESENT;So;0;ON;;;;;N;;;;; 1F382;BIRTHDAY CAKE;So;0;ON;;;;;N;;;;; 1F383;JACK-O-LANTERN;So;0;ON;;;;;N;;;;; 1F384;CHRISTMAS TREE;So;0;ON;;;;;N;;;;; 1F385;FATHER CHRISTMAS;So;0;ON;;;;;N;;;;; 1F386;FIREWORKS;So;0;ON;;;;;N;;;;; 1F387;FIREWORK SPARKLER;So;0;ON;;;;;N;;;;; 1F388;BALLOON;So;0;ON;;;;;N;;;;; 1F389;PARTY POPPER;So;0;ON;;;;;N;;;;; 1F38A;CONFETTI BALL;So;0;ON;;;;;N;;;;; 1F38B;TANABATA TREE;So;0;ON;;;;;N;;;;; 1F38C;CROSSED FLAGS;So;0;ON;;;;;N;;;;; 1F38D;PINE DECORATION;So;0;ON;;;;;N;;;;; 1F38E;JAPANESE DOLLS;So;0;ON;;;;;N;;;;; 1F38F;CARP STREAMER;So;0;ON;;;;;N;;;;; 1F390;WIND CHIME;So;0;ON;;;;;N;;;;; 1F391;MOON VIEWING CEREMONY;So;0;ON;;;;;N;;;;; 1F392;SCHOOL SATCHEL;So;0;ON;;;;;N;;;;; 1F393;GRADUATION CAP;So;0;ON;;;;;N;;;;; 1F394;HEART WITH TIP ON THE LEFT;So;0;ON;;;;;N;;;;; 1F395;BOUQUET OF FLOWERS;So;0;ON;;;;;N;;;;; 1F396;MILITARY MEDAL;So;0;ON;;;;;N;;;;; 1F397;REMINDER RIBBON;So;0;ON;;;;;N;;;;; 1F398;MUSICAL KEYBOARD WITH JACKS;So;0;ON;;;;;N;;;;; 1F399;STUDIO MICROPHONE;So;0;ON;;;;;N;;;;; 1F39A;LEVEL SLIDER;So;0;ON;;;;;N;;;;; 1F39B;CONTROL KNOBS;So;0;ON;;;;;N;;;;; 1F39C;BEAMED ASCENDING MUSICAL NOTES;So;0;ON;;;;;N;;;;; 1F39D;BEAMED DESCENDING MUSICAL NOTES;So;0;ON;;;;;N;;;;; 1F39E;FILM FRAMES;So;0;ON;;;;;N;;;;; 1F39F;ADMISSION TICKETS;So;0;ON;;;;;N;;;;; 1F3A0;CAROUSEL HORSE;So;0;ON;;;;;N;;;;; 1F3A1;FERRIS WHEEL;So;0;ON;;;;;N;;;;; 1F3A2;ROLLER COASTER;So;0;ON;;;;;N;;;;; 1F3A3;FISHING POLE AND FISH;So;0;ON;;;;;N;;;;; 1F3A4;MICROPHONE;So;0;ON;;;;;N;;;;; 1F3A5;MOVIE CAMERA;So;0;ON;;;;;N;;;;; 1F3A6;CINEMA;So;0;ON;;;;;N;;;;; 1F3A7;HEADPHONE;So;0;ON;;;;;N;;;;; 1F3A8;ARTIST PALETTE;So;0;ON;;;;;N;;;;; 1F3A9;TOP HAT;So;0;ON;;;;;N;;;;; 1F3AA;CIRCUS TENT;So;0;ON;;;;;N;;;;; 1F3AB;TICKET;So;0;ON;;;;;N;;;;; 1F3AC;CLAPPER BOARD;So;0;ON;;;;;N;;;;; 1F3AD;PERFORMING ARTS;So;0;ON;;;;;N;;;;; 1F3AE;VIDEO GAME;So;0;ON;;;;;N;;;;; 1F3AF;DIRECT HIT;So;0;ON;;;;;N;;;;; 1F3B0;SLOT MACHINE;So;0;ON;;;;;N;;;;; 1F3B1;BILLIARDS;So;0;ON;;;;;N;;;;; 1F3B2;GAME DIE;So;0;ON;;;;;N;;;;; 1F3B3;BOWLING;So;0;ON;;;;;N;;;;; 1F3B4;FLOWER PLAYING CARDS;So;0;ON;;;;;N;;;;; 1F3B5;MUSICAL NOTE;So;0;ON;;;;;N;;;;; 1F3B6;MULTIPLE MUSICAL NOTES;So;0;ON;;;;;N;;;;; 1F3B7;SAXOPHONE;So;0;ON;;;;;N;;;;; 1F3B8;GUITAR;So;0;ON;;;;;N;;;;; 1F3B9;MUSICAL KEYBOARD;So;0;ON;;;;;N;;;;; 1F3BA;TRUMPET;So;0;ON;;;;;N;;;;; 1F3BB;VIOLIN;So;0;ON;;;;;N;;;;; 1F3BC;MUSICAL SCORE;So;0;ON;;;;;N;;;;; 1F3BD;RUNNING SHIRT WITH SASH;So;0;ON;;;;;N;;;;; 1F3BE;TENNIS RACQUET AND BALL;So;0;ON;;;;;N;;;;; 1F3BF;SKI AND SKI BOOT;So;0;ON;;;;;N;;;;; 1F3C0;BASKETBALL AND HOOP;So;0;ON;;;;;N;;;;; 1F3C1;CHEQUERED FLAG;So;0;ON;;;;;N;;;;; 1F3C2;SNOWBOARDER;So;0;ON;;;;;N;;;;; 1F3C3;RUNNER;So;0;ON;;;;;N;;;;; 1F3C4;SURFER;So;0;ON;;;;;N;;;;; 1F3C5;SPORTS MEDAL;So;0;ON;;;;;N;;;;; 1F3C6;TROPHY;So;0;ON;;;;;N;;;;; 1F3C7;HORSE RACING;So;0;ON;;;;;N;;;;; 1F3C8;AMERICAN FOOTBALL;So;0;ON;;;;;N;;;;; 1F3C9;RUGBY FOOTBALL;So;0;ON;;;;;N;;;;; 1F3CA;SWIMMER;So;0;ON;;;;;N;;;;; 1F3CB;WEIGHT LIFTER;So;0;ON;;;;;N;;;;; 1F3CC;GOLFER;So;0;ON;;;;;N;;;;; 1F3CD;RACING MOTORCYCLE;So;0;ON;;;;;N;;;;; 1F3CE;RACING CAR;So;0;ON;;;;;N;;;;; 1F3D4;SNOW CAPPED MOUNTAIN;So;0;ON;;;;;N;;;;; 1F3D5;CAMPING;So;0;ON;;;;;N;;;;; 1F3D6;BEACH WITH UMBRELLA;So;0;ON;;;;;N;;;;; 1F3D7;BUILDING CONSTRUCTION;So;0;ON;;;;;N;;;;; 1F3D8;HOUSE BUILDINGS;So;0;ON;;;;;N;;;;; 1F3D9;CITYSCAPE;So;0;ON;;;;;N;;;;; 1F3DA;DERELICT HOUSE BUILDING;So;0;ON;;;;;N;;;;; 1F3DB;CLASSICAL BUILDING;So;0;ON;;;;;N;;;;; 1F3DC;DESERT;So;0;ON;;;;;N;;;;; 1F3DD;DESERT ISLAND;So;0;ON;;;;;N;;;;; 1F3DE;NATIONAL PARK;So;0;ON;;;;;N;;;;; 1F3DF;STADIUM;So;0;ON;;;;;N;;;;; 1F3E0;HOUSE BUILDING;So;0;ON;;;;;N;;;;; 1F3E1;HOUSE WITH GARDEN;So;0;ON;;;;;N;;;;; 1F3E2;OFFICE BUILDING;So;0;ON;;;;;N;;;;; 1F3E3;JAPANESE POST OFFICE;So;0;ON;;;;;N;;;;; 1F3E4;EUROPEAN POST OFFICE;So;0;ON;;;;;N;;;;; 1F3E5;HOSPITAL;So;0;ON;;;;;N;;;;; 1F3E6;BANK;So;0;ON;;;;;N;;;;; 1F3E7;AUTOMATED TELLER MACHINE;So;0;ON;;;;;N;;;;; 1F3E8;HOTEL;So;0;ON;;;;;N;;;;; 1F3E9;LOVE HOTEL;So;0;ON;;;;;N;;;;; 1F3EA;CONVENIENCE STORE;So;0;ON;;;;;N;;;;; 1F3EB;SCHOOL;So;0;ON;;;;;N;;;;; 1F3EC;DEPARTMENT STORE;So;0;ON;;;;;N;;;;; 1F3ED;FACTORY;So;0;ON;;;;;N;;;;; 1F3EE;IZAKAYA LANTERN;So;0;ON;;;;;N;;;;; 1F3EF;JAPANESE CASTLE;So;0;ON;;;;;N;;;;; 1F3F0;EUROPEAN CASTLE;So;0;ON;;;;;N;;;;; 1F3F1;WHITE PENNANT;So;0;ON;;;;;N;;;;; 1F3F2;BLACK PENNANT;So;0;ON;;;;;N;;;;; 1F3F3;WAVING WHITE FLAG;So;0;ON;;;;;N;;;;; 1F3F4;WAVING BLACK FLAG;So;0;ON;;;;;N;;;;; 1F3F5;ROSETTE;So;0;ON;;;;;N;;;;; 1F3F6;BLACK ROSETTE;So;0;ON;;;;;N;;;;; 1F3F7;LABEL;So;0;ON;;;;;N;;;;; 1F400;RAT;So;0;ON;;;;;N;;;;; 1F401;MOUSE;So;0;ON;;;;;N;;;;; 1F402;OX;So;0;ON;;;;;N;;;;; 1F403;WATER BUFFALO;So;0;ON;;;;;N;;;;; 1F404;COW;So;0;ON;;;;;N;;;;; 1F405;TIGER;So;0;ON;;;;;N;;;;; 1F406;LEOPARD;So;0;ON;;;;;N;;;;; 1F407;RABBIT;So;0;ON;;;;;N;;;;; 1F408;CAT;So;0;ON;;;;;N;;;;; 1F409;DRAGON;So;0;ON;;;;;N;;;;; 1F40A;CROCODILE;So;0;ON;;;;;N;;;;; 1F40B;WHALE;So;0;ON;;;;;N;;;;; 1F40C;SNAIL;So;0;ON;;;;;N;;;;; 1F40D;SNAKE;So;0;ON;;;;;N;;;;; 1F40E;HORSE;So;0;ON;;;;;N;;;;; 1F40F;RAM;So;0;ON;;;;;N;;;;; 1F410;GOAT;So;0;ON;;;;;N;;;;; 1F411;SHEEP;So;0;ON;;;;;N;;;;; 1F412;MONKEY;So;0;ON;;;;;N;;;;; 1F413;ROOSTER;So;0;ON;;;;;N;;;;; 1F414;CHICKEN;So;0;ON;;;;;N;;;;; 1F415;DOG;So;0;ON;;;;;N;;;;; 1F416;PIG;So;0;ON;;;;;N;;;;; 1F417;BOAR;So;0;ON;;;;;N;;;;; 1F418;ELEPHANT;So;0;ON;;;;;N;;;;; 1F419;OCTOPUS;So;0;ON;;;;;N;;;;; 1F41A;SPIRAL SHELL;So;0;ON;;;;;N;;;;; 1F41B;BUG;So;0;ON;;;;;N;;;;; 1F41C;ANT;So;0;ON;;;;;N;;;;; 1F41D;HONEYBEE;So;0;ON;;;;;N;;;;; 1F41E;LADY BEETLE;So;0;ON;;;;;N;;;;; 1F41F;FISH;So;0;ON;;;;;N;;;;; 1F420;TROPICAL FISH;So;0;ON;;;;;N;;;;; 1F421;BLOWFISH;So;0;ON;;;;;N;;;;; 1F422;TURTLE;So;0;ON;;;;;N;;;;; 1F423;HATCHING CHICK;So;0;ON;;;;;N;;;;; 1F424;BABY CHICK;So;0;ON;;;;;N;;;;; 1F425;FRONT-FACING BABY CHICK;So;0;ON;;;;;N;;;;; 1F426;BIRD;So;0;ON;;;;;N;;;;; 1F427;PENGUIN;So;0;ON;;;;;N;;;;; 1F428;KOALA;So;0;ON;;;;;N;;;;; 1F429;POODLE;So;0;ON;;;;;N;;;;; 1F42A;DROMEDARY CAMEL;So;0;ON;;;;;N;;;;; 1F42B;BACTRIAN CAMEL;So;0;ON;;;;;N;;;;; 1F42C;DOLPHIN;So;0;ON;;;;;N;;;;; 1F42D;MOUSE FACE;So;0;ON;;;;;N;;;;; 1F42E;COW FACE;So;0;ON;;;;;N;;;;; 1F42F;TIGER FACE;So;0;ON;;;;;N;;;;; 1F430;RABBIT FACE;So;0;ON;;;;;N;;;;; 1F431;CAT FACE;So;0;ON;;;;;N;;;;; 1F432;DRAGON FACE;So;0;ON;;;;;N;;;;; 1F433;SPOUTING WHALE;So;0;ON;;;;;N;;;;; 1F434;HORSE FACE;So;0;ON;;;;;N;;;;; 1F435;MONKEY FACE;So;0;ON;;;;;N;;;;; 1F436;DOG FACE;So;0;ON;;;;;N;;;;; 1F437;PIG FACE;So;0;ON;;;;;N;;;;; 1F438;FROG FACE;So;0;ON;;;;;N;;;;; 1F439;HAMSTER FACE;So;0;ON;;;;;N;;;;; 1F43A;WOLF FACE;So;0;ON;;;;;N;;;;; 1F43B;BEAR FACE;So;0;ON;;;;;N;;;;; 1F43C;PANDA FACE;So;0;ON;;;;;N;;;;; 1F43D;PIG NOSE;So;0;ON;;;;;N;;;;; 1F43E;PAW PRINTS;So;0;ON;;;;;N;;;;; 1F43F;CHIPMUNK;So;0;ON;;;;;N;;;;; 1F440;EYES;So;0;ON;;;;;N;;;;; 1F441;EYE;So;0;ON;;;;;N;;;;; 1F442;EAR;So;0;ON;;;;;N;;;;; 1F443;NOSE;So;0;ON;;;;;N;;;;; 1F444;MOUTH;So;0;ON;;;;;N;;;;; 1F445;TONGUE;So;0;ON;;;;;N;;;;; 1F446;WHITE UP POINTING BACKHAND INDEX;So;0;ON;;;;;N;;;;; 1F447;WHITE DOWN POINTING BACKHAND INDEX;So;0;ON;;;;;N;;;;; 1F448;WHITE LEFT POINTING BACKHAND INDEX;So;0;ON;;;;;N;;;;; 1F449;WHITE RIGHT POINTING BACKHAND INDEX;So;0;ON;;;;;N;;;;; 1F44A;FISTED HAND SIGN;So;0;ON;;;;;N;;;;; 1F44B;WAVING HAND SIGN;So;0;ON;;;;;N;;;;; 1F44C;OK HAND SIGN;So;0;ON;;;;;N;;;;; 1F44D;THUMBS UP SIGN;So;0;ON;;;;;N;;;;; 1F44E;THUMBS DOWN SIGN;So;0;ON;;;;;N;;;;; 1F44F;CLAPPING HANDS SIGN;So;0;ON;;;;;N;;;;; 1F450;OPEN HANDS SIGN;So;0;ON;;;;;N;;;;; 1F451;CROWN;So;0;ON;;;;;N;;;;; 1F452;WOMANS HAT;So;0;ON;;;;;N;;;;; 1F453;EYEGLASSES;So;0;ON;;;;;N;;;;; 1F454;NECKTIE;So;0;ON;;;;;N;;;;; 1F455;T-SHIRT;So;0;ON;;;;;N;;;;; 1F456;JEANS;So;0;ON;;;;;N;;;;; 1F457;DRESS;So;0;ON;;;;;N;;;;; 1F458;KIMONO;So;0;ON;;;;;N;;;;; 1F459;BIKINI;So;0;ON;;;;;N;;;;; 1F45A;WOMANS CLOTHES;So;0;ON;;;;;N;;;;; 1F45B;PURSE;So;0;ON;;;;;N;;;;; 1F45C;HANDBAG;So;0;ON;;;;;N;;;;; 1F45D;POUCH;So;0;ON;;;;;N;;;;; 1F45E;MANS SHOE;So;0;ON;;;;;N;;;;; 1F45F;ATHLETIC SHOE;So;0;ON;;;;;N;;;;; 1F460;HIGH-HEELED SHOE;So;0;ON;;;;;N;;;;; 1F461;WOMANS SANDAL;So;0;ON;;;;;N;;;;; 1F462;WOMANS BOOTS;So;0;ON;;;;;N;;;;; 1F463;FOOTPRINTS;So;0;ON;;;;;N;;;;; 1F464;BUST IN SILHOUETTE;So;0;ON;;;;;N;;;;; 1F465;BUSTS IN SILHOUETTE;So;0;ON;;;;;N;;;;; 1F466;BOY;So;0;ON;;;;;N;;;;; 1F467;GIRL;So;0;ON;;;;;N;;;;; 1F468;MAN;So;0;ON;;;;;N;;;;; 1F469;WOMAN;So;0;ON;;;;;N;;;;; 1F46A;FAMILY;So;0;ON;;;;;N;;;;; 1F46B;MAN AND WOMAN HOLDING HANDS;So;0;ON;;;;;N;;;;; 1F46C;TWO MEN HOLDING HANDS;So;0;ON;;;;;N;;;;; 1F46D;TWO WOMEN HOLDING HANDS;So;0;ON;;;;;N;;;;; 1F46E;POLICE OFFICER;So;0;ON;;;;;N;;;;; 1F46F;WOMAN WITH BUNNY EARS;So;0;ON;;;;;N;;;;; 1F470;BRIDE WITH VEIL;So;0;ON;;;;;N;;;;; 1F471;PERSON WITH BLOND HAIR;So;0;ON;;;;;N;;;;; 1F472;MAN WITH GUA PI MAO;So;0;ON;;;;;N;;;;; 1F473;MAN WITH TURBAN;So;0;ON;;;;;N;;;;; 1F474;OLDER MAN;So;0;ON;;;;;N;;;;; 1F475;OLDER WOMAN;So;0;ON;;;;;N;;;;; 1F476;BABY;So;0;ON;;;;;N;;;;; 1F477;CONSTRUCTION WORKER;So;0;ON;;;;;N;;;;; 1F478;PRINCESS;So;0;ON;;;;;N;;;;; 1F479;JAPANESE OGRE;So;0;ON;;;;;N;;;;; 1F47A;JAPANESE GOBLIN;So;0;ON;;;;;N;;;;; 1F47B;GHOST;So;0;ON;;;;;N;;;;; 1F47C;BABY ANGEL;So;0;ON;;;;;N;;;;; 1F47D;EXTRATERRESTRIAL ALIEN;So;0;ON;;;;;N;;;;; 1F47E;ALIEN MONSTER;So;0;ON;;;;;N;;;;; 1F47F;IMP;So;0;ON;;;;;N;;;;; 1F480;SKULL;So;0;ON;;;;;N;;;;; 1F481;INFORMATION DESK PERSON;So;0;ON;;;;;N;;;;; 1F482;GUARDSMAN;So;0;ON;;;;;N;;;;; 1F483;DANCER;So;0;ON;;;;;N;;;;; 1F484;LIPSTICK;So;0;ON;;;;;N;;;;; 1F485;NAIL POLISH;So;0;ON;;;;;N;;;;; 1F486;FACE MASSAGE;So;0;ON;;;;;N;;;;; 1F487;HAIRCUT;So;0;ON;;;;;N;;;;; 1F488;BARBER POLE;So;0;ON;;;;;N;;;;; 1F489;SYRINGE;So;0;ON;;;;;N;;;;; 1F48A;PILL;So;0;ON;;;;;N;;;;; 1F48B;KISS MARK;So;0;ON;;;;;N;;;;; 1F48C;LOVE LETTER;So;0;ON;;;;;N;;;;; 1F48D;RING;So;0;ON;;;;;N;;;;; 1F48E;GEM STONE;So;0;ON;;;;;N;;;;; 1F48F;KISS;So;0;ON;;;;;N;;;;; 1F490;BOUQUET;So;0;ON;;;;;N;;;;; 1F491;COUPLE WITH HEART;So;0;ON;;;;;N;;;;; 1F492;WEDDING;So;0;ON;;;;;N;;;;; 1F493;BEATING HEART;So;0;ON;;;;;N;;;;; 1F494;BROKEN HEART;So;0;ON;;;;;N;;;;; 1F495;TWO HEARTS;So;0;ON;;;;;N;;;;; 1F496;SPARKLING HEART;So;0;ON;;;;;N;;;;; 1F497;GROWING HEART;So;0;ON;;;;;N;;;;; 1F498;HEART WITH ARROW;So;0;ON;;;;;N;;;;; 1F499;BLUE HEART;So;0;ON;;;;;N;;;;; 1F49A;GREEN HEART;So;0;ON;;;;;N;;;;; 1F49B;YELLOW HEART;So;0;ON;;;;;N;;;;; 1F49C;PURPLE HEART;So;0;ON;;;;;N;;;;; 1F49D;HEART WITH RIBBON;So;0;ON;;;;;N;;;;; 1F49E;REVOLVING HEARTS;So;0;ON;;;;;N;;;;; 1F49F;HEART DECORATION;So;0;ON;;;;;N;;;;; 1F4A0;DIAMOND SHAPE WITH A DOT INSIDE;So;0;ON;;;;;N;;;;; 1F4A1;ELECTRIC LIGHT BULB;So;0;ON;;;;;N;;;;; 1F4A2;ANGER SYMBOL;So;0;ON;;;;;N;;;;; 1F4A3;BOMB;So;0;ON;;;;;N;;;;; 1F4A4;SLEEPING SYMBOL;So;0;ON;;;;;N;;;;; 1F4A5;COLLISION SYMBOL;So;0;ON;;;;;N;;;;; 1F4A6;SPLASHING SWEAT SYMBOL;So;0;ON;;;;;N;;;;; 1F4A7;DROPLET;So;0;ON;;;;;N;;;;; 1F4A8;DASH SYMBOL;So;0;ON;;;;;N;;;;; 1F4A9;PILE OF POO;So;0;ON;;;;;N;;;;; 1F4AA;FLEXED BICEPS;So;0;ON;;;;;N;;;;; 1F4AB;DIZZY SYMBOL;So;0;ON;;;;;N;;;;; 1F4AC;SPEECH BALLOON;So;0;ON;;;;;N;;;;; 1F4AD;THOUGHT BALLOON;So;0;ON;;;;;N;;;;; 1F4AE;WHITE FLOWER;So;0;ON;;;;;N;;;;; 1F4AF;HUNDRED POINTS SYMBOL;So;0;ON;;;;;N;;;;; 1F4B0;MONEY BAG;So;0;ON;;;;;N;;;;; 1F4B1;CURRENCY EXCHANGE;So;0;ON;;;;;N;;;;; 1F4B2;HEAVY DOLLAR SIGN;So;0;ON;;;;;N;;;;; 1F4B3;CREDIT CARD;So;0;ON;;;;;N;;;;; 1F4B4;BANKNOTE WITH YEN SIGN;So;0;ON;;;;;N;;;;; 1F4B5;BANKNOTE WITH DOLLAR SIGN;So;0;ON;;;;;N;;;;; 1F4B6;BANKNOTE WITH EURO SIGN;So;0;ON;;;;;N;;;;; 1F4B7;BANKNOTE WITH POUND SIGN;So;0;ON;;;;;N;;;;; 1F4B8;MONEY WITH WINGS;So;0;ON;;;;;N;;;;; 1F4B9;CHART WITH UPWARDS TREND AND YEN SIGN;So;0;ON;;;;;N;;;;; 1F4BA;SEAT;So;0;ON;;;;;N;;;;; 1F4BB;PERSONAL COMPUTER;So;0;ON;;;;;N;;;;; 1F4BC;BRIEFCASE;So;0;ON;;;;;N;;;;; 1F4BD;MINIDISC;So;0;ON;;;;;N;;;;; 1F4BE;FLOPPY DISK;So;0;ON;;;;;N;;;;; 1F4BF;OPTICAL DISC;So;0;ON;;;;;N;;;;; 1F4C0;DVD;So;0;ON;;;;;N;;;;; 1F4C1;FILE FOLDER;So;0;ON;;;;;N;;;;; 1F4C2;OPEN FILE FOLDER;So;0;ON;;;;;N;;;;; 1F4C3;PAGE WITH CURL;So;0;ON;;;;;N;;;;; 1F4C4;PAGE FACING UP;So;0;ON;;;;;N;;;;; 1F4C5;CALENDAR;So;0;ON;;;;;N;;;;; 1F4C6;TEAR-OFF CALENDAR;So;0;ON;;;;;N;;;;; 1F4C7;CARD INDEX;So;0;ON;;;;;N;;;;; 1F4C8;CHART WITH UPWARDS TREND;So;0;ON;;;;;N;;;;; 1F4C9;CHART WITH DOWNWARDS TREND;So;0;ON;;;;;N;;;;; 1F4CA;BAR CHART;So;0;ON;;;;;N;;;;; 1F4CB;CLIPBOARD;So;0;ON;;;;;N;;;;; 1F4CC;PUSHPIN;So;0;ON;;;;;N;;;;; 1F4CD;ROUND PUSHPIN;So;0;ON;;;;;N;;;;; 1F4CE;PAPERCLIP;So;0;ON;;;;;N;;;;; 1F4CF;STRAIGHT RULER;So;0;ON;;;;;N;;;;; 1F4D0;TRIANGULAR RULER;So;0;ON;;;;;N;;;;; 1F4D1;BOOKMARK TABS;So;0;ON;;;;;N;;;;; 1F4D2;LEDGER;So;0;ON;;;;;N;;;;; 1F4D3;NOTEBOOK;So;0;ON;;;;;N;;;;; 1F4D4;NOTEBOOK WITH DECORATIVE COVER;So;0;ON;;;;;N;;;;; 1F4D5;CLOSED BOOK;So;0;ON;;;;;N;;;;; 1F4D6;OPEN BOOK;So;0;ON;;;;;N;;;;; 1F4D7;GREEN BOOK;So;0;ON;;;;;N;;;;; 1F4D8;BLUE BOOK;So;0;ON;;;;;N;;;;; 1F4D9;ORANGE BOOK;So;0;ON;;;;;N;;;;; 1F4DA;BOOKS;So;0;ON;;;;;N;;;;; 1F4DB;NAME BADGE;So;0;ON;;;;;N;;;;; 1F4DC;SCROLL;So;0;ON;;;;;N;;;;; 1F4DD;MEMO;So;0;ON;;;;;N;;;;; 1F4DE;TELEPHONE RECEIVER;So;0;ON;;;;;N;;;;; 1F4DF;PAGER;So;0;ON;;;;;N;;;;; 1F4E0;FAX MACHINE;So;0;ON;;;;;N;;;;; 1F4E1;SATELLITE ANTENNA;So;0;ON;;;;;N;;;;; 1F4E2;PUBLIC ADDRESS LOUDSPEAKER;So;0;ON;;;;;N;;;;; 1F4E3;CHEERING MEGAPHONE;So;0;ON;;;;;N;;;;; 1F4E4;OUTBOX TRAY;So;0;ON;;;;;N;;;;; 1F4E5;INBOX TRAY;So;0;ON;;;;;N;;;;; 1F4E6;PACKAGE;So;0;ON;;;;;N;;;;; 1F4E7;E-MAIL SYMBOL;So;0;ON;;;;;N;;;;; 1F4E8;INCOMING ENVELOPE;So;0;ON;;;;;N;;;;; 1F4E9;ENVELOPE WITH DOWNWARDS ARROW ABOVE;So;0;ON;;;;;N;;;;; 1F4EA;CLOSED MAILBOX WITH LOWERED FLAG;So;0;ON;;;;;N;;;;; 1F4EB;CLOSED MAILBOX WITH RAISED FLAG;So;0;ON;;;;;N;;;;; 1F4EC;OPEN MAILBOX WITH RAISED FLAG;So;0;ON;;;;;N;;;;; 1F4ED;OPEN MAILBOX WITH LOWERED FLAG;So;0;ON;;;;;N;;;;; 1F4EE;POSTBOX;So;0;ON;;;;;N;;;;; 1F4EF;POSTAL HORN;So;0;ON;;;;;N;;;;; 1F4F0;NEWSPAPER;So;0;ON;;;;;N;;;;; 1F4F1;MOBILE PHONE;So;0;ON;;;;;N;;;;; 1F4F2;MOBILE PHONE WITH RIGHTWARDS ARROW AT LEFT;So;0;ON;;;;;N;;;;; 1F4F3;VIBRATION MODE;So;0;ON;;;;;N;;;;; 1F4F4;MOBILE PHONE OFF;So;0;ON;;;;;N;;;;; 1F4F5;NO MOBILE PHONES;So;0;ON;;;;;N;;;;; 1F4F6;ANTENNA WITH BARS;So;0;ON;;;;;N;;;;; 1F4F7;CAMERA;So;0;ON;;;;;N;;;;; 1F4F8;CAMERA WITH FLASH;So;0;ON;;;;;N;;;;; 1F4F9;VIDEO CAMERA;So;0;ON;;;;;N;;;;; 1F4FA;TELEVISION;So;0;ON;;;;;N;;;;; 1F4FB;RADIO;So;0;ON;;;;;N;;;;; 1F4FC;VIDEOCASSETTE;So;0;ON;;;;;N;;;;; 1F4FD;FILM PROJECTOR;So;0;ON;;;;;N;;;;; 1F4FE;PORTABLE STEREO;So;0;ON;;;;;N;;;;; 1F500;TWISTED RIGHTWARDS ARROWS;So;0;ON;;;;;N;;;;; 1F501;CLOCKWISE RIGHTWARDS AND LEFTWARDS OPEN CIRCLE ARROWS;So;0;ON;;;;;N;;;;; 1F502;CLOCKWISE RIGHTWARDS AND LEFTWARDS OPEN CIRCLE ARROWS WITH CIRCLED ONE OVERLAY;So;0;ON;;;;;N;;;;; 1F503;CLOCKWISE DOWNWARDS AND UPWARDS OPEN CIRCLE ARROWS;So;0;ON;;;;;N;;;;; 1F504;ANTICLOCKWISE DOWNWARDS AND UPWARDS OPEN CIRCLE ARROWS;So;0;ON;;;;;N;;;;; 1F505;LOW BRIGHTNESS SYMBOL;So;0;ON;;;;;N;;;;; 1F506;HIGH BRIGHTNESS SYMBOL;So;0;ON;;;;;N;;;;; 1F507;SPEAKER WITH CANCELLATION STROKE;So;0;ON;;;;;N;;;;; 1F508;SPEAKER;So;0;ON;;;;;N;;;;; 1F509;SPEAKER WITH ONE SOUND WAVE;So;0;ON;;;;;N;;;;; 1F50A;SPEAKER WITH THREE SOUND WAVES;So;0;ON;;;;;N;;;;; 1F50B;BATTERY;So;0;ON;;;;;N;;;;; 1F50C;ELECTRIC PLUG;So;0;ON;;;;;N;;;;; 1F50D;LEFT-POINTING MAGNIFYING GLASS;So;0;ON;;;;;N;;;;; 1F50E;RIGHT-POINTING MAGNIFYING GLASS;So;0;ON;;;;;N;;;;; 1F50F;LOCK WITH INK PEN;So;0;ON;;;;;N;;;;; 1F510;CLOSED LOCK WITH KEY;So;0;ON;;;;;N;;;;; 1F511;KEY;So;0;ON;;;;;N;;;;; 1F512;LOCK;So;0;ON;;;;;N;;;;; 1F513;OPEN LOCK;So;0;ON;;;;;N;;;;; 1F514;BELL;So;0;ON;;;;;N;;;;; 1F515;BELL WITH CANCELLATION STROKE;So;0;ON;;;;;N;;;;; 1F516;BOOKMARK;So;0;ON;;;;;N;;;;; 1F517;LINK SYMBOL;So;0;ON;;;;;N;;;;; 1F518;RADIO BUTTON;So;0;ON;;;;;N;;;;; 1F519;BACK WITH LEFTWARDS ARROW ABOVE;So;0;ON;;;;;N;;;;; 1F51A;END WITH LEFTWARDS ARROW ABOVE;So;0;ON;;;;;N;;;;; 1F51B;ON WITH EXCLAMATION MARK WITH LEFT RIGHT ARROW ABOVE;So;0;ON;;;;;N;;;;; 1F51C;SOON WITH RIGHTWARDS ARROW ABOVE;So;0;ON;;;;;N;;;;; 1F51D;TOP WITH UPWARDS ARROW ABOVE;So;0;ON;;;;;N;;;;; 1F51E;NO ONE UNDER EIGHTEEN SYMBOL;So;0;ON;;;;;N;;;;; 1F51F;KEYCAP TEN;So;0;ON;;;;;N;;;;; 1F520;INPUT SYMBOL FOR LATIN CAPITAL LETTERS;So;0;ON;;;;;N;;;;; 1F521;INPUT SYMBOL FOR LATIN SMALL LETTERS;So;0;ON;;;;;N;;;;; 1F522;INPUT SYMBOL FOR NUMBERS;So;0;ON;;;;;N;;;;; 1F523;INPUT SYMBOL FOR SYMBOLS;So;0;ON;;;;;N;;;;; 1F524;INPUT SYMBOL FOR LATIN LETTERS;So;0;ON;;;;;N;;;;; 1F525;FIRE;So;0;ON;;;;;N;;;;; 1F526;ELECTRIC TORCH;So;0;ON;;;;;N;;;;; 1F527;WRENCH;So;0;ON;;;;;N;;;;; 1F528;HAMMER;So;0;ON;;;;;N;;;;; 1F529;NUT AND BOLT;So;0;ON;;;;;N;;;;; 1F52A;HOCHO;So;0;ON;;;;;N;;;;; 1F52B;PISTOL;So;0;ON;;;;;N;;;;; 1F52C;MICROSCOPE;So;0;ON;;;;;N;;;;; 1F52D;TELESCOPE;So;0;ON;;;;;N;;;;; 1F52E;CRYSTAL BALL;So;0;ON;;;;;N;;;;; 1F52F;SIX POINTED STAR WITH MIDDLE DOT;So;0;ON;;;;;N;;;;; 1F530;JAPANESE SYMBOL FOR BEGINNER;So;0;ON;;;;;N;;;;; 1F531;TRIDENT EMBLEM;So;0;ON;;;;;N;;;;; 1F532;BLACK SQUARE BUTTON;So;0;ON;;;;;N;;;;; 1F533;WHITE SQUARE BUTTON;So;0;ON;;;;;N;;;;; 1F534;LARGE RED CIRCLE;So;0;ON;;;;;N;;;;; 1F535;LARGE BLUE CIRCLE;So;0;ON;;;;;N;;;;; 1F536;LARGE ORANGE DIAMOND;So;0;ON;;;;;N;;;;; 1F537;LARGE BLUE DIAMOND;So;0;ON;;;;;N;;;;; 1F538;SMALL ORANGE DIAMOND;So;0;ON;;;;;N;;;;; 1F539;SMALL BLUE DIAMOND;So;0;ON;;;;;N;;;;; 1F53A;UP-POINTING RED TRIANGLE;So;0;ON;;;;;N;;;;; 1F53B;DOWN-POINTING RED TRIANGLE;So;0;ON;;;;;N;;;;; 1F53C;UP-POINTING SMALL RED TRIANGLE;So;0;ON;;;;;N;;;;; 1F53D;DOWN-POINTING SMALL RED TRIANGLE;So;0;ON;;;;;N;;;;; 1F53E;LOWER RIGHT SHADOWED WHITE CIRCLE;So;0;ON;;;;;N;;;;; 1F53F;UPPER RIGHT SHADOWED WHITE CIRCLE;So;0;ON;;;;;N;;;;; 1F540;CIRCLED CROSS POMMEE;So;0;ON;;;;;N;;;;; 1F541;CROSS POMMEE WITH HALF-CIRCLE BELOW;So;0;ON;;;;;N;;;;; 1F542;CROSS POMMEE;So;0;ON;;;;;N;;;;; 1F543;NOTCHED LEFT SEMICIRCLE WITH THREE DOTS;So;0;ON;;;;;N;;;;; 1F544;NOTCHED RIGHT SEMICIRCLE WITH THREE DOTS;So;0;ON;;;;;N;;;;; 1F545;SYMBOL FOR MARKS CHAPTER;So;0;ON;;;;;N;;;;; 1F546;WHITE LATIN CROSS;So;0;ON;;;;;N;;;;; 1F547;HEAVY LATIN CROSS;So;0;ON;;;;;N;;;;; 1F548;CELTIC CROSS;So;0;ON;;;;;N;;;;; 1F549;OM SYMBOL;So;0;ON;;;;;N;;;;; 1F54A;DOVE OF PEACE;So;0;ON;;;;;N;;;;; 1F550;CLOCK FACE ONE OCLOCK;So;0;ON;;;;;N;;;;; 1F551;CLOCK FACE TWO OCLOCK;So;0;ON;;;;;N;;;;; 1F552;CLOCK FACE THREE OCLOCK;So;0;ON;;;;;N;;;;; 1F553;CLOCK FACE FOUR OCLOCK;So;0;ON;;;;;N;;;;; 1F554;CLOCK FACE FIVE OCLOCK;So;0;ON;;;;;N;;;;; 1F555;CLOCK FACE SIX OCLOCK;So;0;ON;;;;;N;;;;; 1F556;CLOCK FACE SEVEN OCLOCK;So;0;ON;;;;;N;;;;; 1F557;CLOCK FACE EIGHT OCLOCK;So;0;ON;;;;;N;;;;; 1F558;CLOCK FACE NINE OCLOCK;So;0;ON;;;;;N;;;;; 1F559;CLOCK FACE TEN OCLOCK;So;0;ON;;;;;N;;;;; 1F55A;CLOCK FACE ELEVEN OCLOCK;So;0;ON;;;;;N;;;;; 1F55B;CLOCK FACE TWELVE OCLOCK;So;0;ON;;;;;N;;;;; 1F55C;CLOCK FACE ONE-THIRTY;So;0;ON;;;;;N;;;;; 1F55D;CLOCK FACE TWO-THIRTY;So;0;ON;;;;;N;;;;; 1F55E;CLOCK FACE THREE-THIRTY;So;0;ON;;;;;N;;;;; 1F55F;CLOCK FACE FOUR-THIRTY;So;0;ON;;;;;N;;;;; 1F560;CLOCK FACE FIVE-THIRTY;So;0;ON;;;;;N;;;;; 1F561;CLOCK FACE SIX-THIRTY;So;0;ON;;;;;N;;;;; 1F562;CLOCK FACE SEVEN-THIRTY;So;0;ON;;;;;N;;;;; 1F563;CLOCK FACE EIGHT-THIRTY;So;0;ON;;;;;N;;;;; 1F564;CLOCK FACE NINE-THIRTY;So;0;ON;;;;;N;;;;; 1F565;CLOCK FACE TEN-THIRTY;So;0;ON;;;;;N;;;;; 1F566;CLOCK FACE ELEVEN-THIRTY;So;0;ON;;;;;N;;;;; 1F567;CLOCK FACE TWELVE-THIRTY;So;0;ON;;;;;N;;;;; 1F568;RIGHT SPEAKER;So;0;ON;;;;;N;;;;; 1F569;RIGHT SPEAKER WITH ONE SOUND WAVE;So;0;ON;;;;;N;;;;; 1F56A;RIGHT SPEAKER WITH THREE SOUND WAVES;So;0;ON;;;;;N;;;;; 1F56B;BULLHORN;So;0;ON;;;;;N;;;;; 1F56C;BULLHORN WITH SOUND WAVES;So;0;ON;;;;;N;;;;; 1F56D;RINGING BELL;So;0;ON;;;;;N;;;;; 1F56E;BOOK;So;0;ON;;;;;N;;;;; 1F56F;CANDLE;So;0;ON;;;;;N;;;;; 1F570;MANTELPIECE CLOCK;So;0;ON;;;;;N;;;;; 1F571;BLACK SKULL AND CROSSBONES;So;0;ON;;;;;N;;;;; 1F572;NO PIRACY;So;0;ON;;;;;N;;;;; 1F573;HOLE;So;0;ON;;;;;N;;;;; 1F574;MAN IN BUSINESS SUIT LEVITATING;So;0;ON;;;;;N;;;;; 1F575;SLEUTH OR SPY;So;0;ON;;;;;N;;;;; 1F576;DARK SUNGLASSES;So;0;ON;;;;;N;;;;; 1F577;SPIDER;So;0;ON;;;;;N;;;;; 1F578;SPIDER WEB;So;0;ON;;;;;N;;;;; 1F579;JOYSTICK;So;0;ON;;;;;N;;;;; 1F57B;LEFT HAND TELEPHONE RECEIVER;So;0;ON;;;;;N;;;;; 1F57C;TELEPHONE RECEIVER WITH PAGE;So;0;ON;;;;;N;;;;; 1F57D;RIGHT HAND TELEPHONE RECEIVER;So;0;ON;;;;;N;;;;; 1F57E;WHITE TOUCHTONE TELEPHONE;So;0;ON;;;;;N;;;;; 1F57F;BLACK TOUCHTONE TELEPHONE;So;0;ON;;;;;N;;;;; 1F580;TELEPHONE ON TOP OF MODEM;So;0;ON;;;;;N;;;;; 1F581;CLAMSHELL MOBILE PHONE;So;0;ON;;;;;N;;;;; 1F582;BACK OF ENVELOPE;So;0;ON;;;;;N;;;;; 1F583;STAMPED ENVELOPE;So;0;ON;;;;;N;;;;; 1F584;ENVELOPE WITH LIGHTNING;So;0;ON;;;;;N;;;;; 1F585;FLYING ENVELOPE;So;0;ON;;;;;N;;;;; 1F586;PEN OVER STAMPED ENVELOPE;So;0;ON;;;;;N;;;;; 1F587;LINKED PAPERCLIPS;So;0;ON;;;;;N;;;;; 1F588;BLACK PUSHPIN;So;0;ON;;;;;N;;;;; 1F589;LOWER LEFT PENCIL;So;0;ON;;;;;N;;;;; 1F58A;LOWER LEFT BALLPOINT PEN;So;0;ON;;;;;N;;;;; 1F58B;LOWER LEFT FOUNTAIN PEN;So;0;ON;;;;;N;;;;; 1F58C;LOWER LEFT PAINTBRUSH;So;0;ON;;;;;N;;;;; 1F58D;LOWER LEFT CRAYON;So;0;ON;;;;;N;;;;; 1F58E;LEFT WRITING HAND;So;0;ON;;;;;N;;;;; 1F58F;TURNED OK HAND SIGN;So;0;ON;;;;;N;;;;; 1F590;RAISED HAND WITH FINGERS SPLAYED;So;0;ON;;;;;N;;;;; 1F591;REVERSED RAISED HAND WITH FINGERS SPLAYED;So;0;ON;;;;;N;;;;; 1F592;REVERSED THUMBS UP SIGN;So;0;ON;;;;;N;;;;; 1F593;REVERSED THUMBS DOWN SIGN;So;0;ON;;;;;N;;;;; 1F594;REVERSED VICTORY HAND;So;0;ON;;;;;N;;;;; 1F595;REVERSED HAND WITH MIDDLE FINGER EXTENDED;So;0;ON;;;;;N;;;;; 1F596;RAISED HAND WITH PART BETWEEN MIDDLE AND RING FINGERS;So;0;ON;;;;;N;;;;; 1F597;WHITE DOWN POINTING LEFT HAND INDEX;So;0;ON;;;;;N;;;;; 1F598;SIDEWAYS WHITE LEFT POINTING INDEX;So;0;ON;;;;;N;;;;; 1F599;SIDEWAYS WHITE RIGHT POINTING INDEX;So;0;ON;;;;;N;;;;; 1F59A;SIDEWAYS BLACK LEFT POINTING INDEX;So;0;ON;;;;;N;;;;; 1F59B;SIDEWAYS BLACK RIGHT POINTING INDEX;So;0;ON;;;;;N;;;;; 1F59C;BLACK LEFT POINTING BACKHAND INDEX;So;0;ON;;;;;N;;;;; 1F59D;BLACK RIGHT POINTING BACKHAND INDEX;So;0;ON;;;;;N;;;;; 1F59E;SIDEWAYS WHITE UP POINTING INDEX;So;0;ON;;;;;N;;;;; 1F59F;SIDEWAYS WHITE DOWN POINTING INDEX;So;0;ON;;;;;N;;;;; 1F5A0;SIDEWAYS BLACK UP POINTING INDEX;So;0;ON;;;;;N;;;;; 1F5A1;SIDEWAYS BLACK DOWN POINTING INDEX;So;0;ON;;;;;N;;;;; 1F5A2;BLACK UP POINTING BACKHAND INDEX;So;0;ON;;;;;N;;;;; 1F5A3;BLACK DOWN POINTING BACKHAND INDEX;So;0;ON;;;;;N;;;;; 1F5A5;DESKTOP COMPUTER;So;0;ON;;;;;N;;;;; 1F5A6;KEYBOARD AND MOUSE;So;0;ON;;;;;N;;;;; 1F5A7;THREE NETWORKED COMPUTERS;So;0;ON;;;;;N;;;;; 1F5A8;PRINTER;So;0;ON;;;;;N;;;;; 1F5A9;POCKET CALCULATOR;So;0;ON;;;;;N;;;;; 1F5AA;BLACK HARD SHELL FLOPPY DISK;So;0;ON;;;;;N;;;;; 1F5AB;WHITE HARD SHELL FLOPPY DISK;So;0;ON;;;;;N;;;;; 1F5AC;SOFT SHELL FLOPPY DISK;So;0;ON;;;;;N;;;;; 1F5AD;TAPE CARTRIDGE;So;0;ON;;;;;N;;;;; 1F5AE;WIRED KEYBOARD;So;0;ON;;;;;N;;;;; 1F5AF;ONE BUTTON MOUSE;So;0;ON;;;;;N;;;;; 1F5B0;TWO BUTTON MOUSE;So;0;ON;;;;;N;;;;; 1F5B1;THREE BUTTON MOUSE;So;0;ON;;;;;N;;;;; 1F5B2;TRACKBALL;So;0;ON;;;;;N;;;;; 1F5B3;OLD PERSONAL COMPUTER;So;0;ON;;;;;N;;;;; 1F5B4;HARD DISK;So;0;ON;;;;;N;;;;; 1F5B5;SCREEN;So;0;ON;;;;;N;;;;; 1F5B6;PRINTER ICON;So;0;ON;;;;;N;;;;; 1F5B7;FAX ICON;So;0;ON;;;;;N;;;;; 1F5B8;OPTICAL DISC ICON;So;0;ON;;;;;N;;;;; 1F5B9;DOCUMENT WITH TEXT;So;0;ON;;;;;N;;;;; 1F5BA;DOCUMENT WITH TEXT AND PICTURE;So;0;ON;;;;;N;;;;; 1F5BB;DOCUMENT WITH PICTURE;So;0;ON;;;;;N;;;;; 1F5BC;FRAME WITH PICTURE;So;0;ON;;;;;N;;;;; 1F5BD;FRAME WITH TILES;So;0;ON;;;;;N;;;;; 1F5BE;FRAME WITH AN X;So;0;ON;;;;;N;;;;; 1F5BF;BLACK FOLDER;So;0;ON;;;;;N;;;;; 1F5C0;FOLDER;So;0;ON;;;;;N;;;;; 1F5C1;OPEN FOLDER;So;0;ON;;;;;N;;;;; 1F5C2;CARD INDEX DIVIDERS;So;0;ON;;;;;N;;;;; 1F5C3;CARD FILE BOX;So;0;ON;;;;;N;;;;; 1F5C4;FILE CABINET;So;0;ON;;;;;N;;;;; 1F5C5;EMPTY NOTE;So;0;ON;;;;;N;;;;; 1F5C6;EMPTY NOTE PAGE;So;0;ON;;;;;N;;;;; 1F5C7;EMPTY NOTE PAD;So;0;ON;;;;;N;;;;; 1F5C8;NOTE;So;0;ON;;;;;N;;;;; 1F5C9;NOTE PAGE;So;0;ON;;;;;N;;;;; 1F5CA;NOTE PAD;So;0;ON;;;;;N;;;;; 1F5CB;EMPTY DOCUMENT;So;0;ON;;;;;N;;;;; 1F5CC;EMPTY PAGE;So;0;ON;;;;;N;;;;; 1F5CD;EMPTY PAGES;So;0;ON;;;;;N;;;;; 1F5CE;DOCUMENT;So;0;ON;;;;;N;;;;; 1F5CF;PAGE;So;0;ON;;;;;N;;;;; 1F5D0;PAGES;So;0;ON;;;;;N;;;;; 1F5D1;WASTEBASKET;So;0;ON;;;;;N;;;;; 1F5D2;SPIRAL NOTE PAD;So;0;ON;;;;;N;;;;; 1F5D3;SPIRAL CALENDAR PAD;So;0;ON;;;;;N;;;;; 1F5D4;DESKTOP WINDOW;So;0;ON;;;;;N;;;;; 1F5D5;MINIMIZE;So;0;ON;;;;;N;;;;; 1F5D6;MAXIMIZE;So;0;ON;;;;;N;;;;; 1F5D7;OVERLAP;So;0;ON;;;;;N;;;;; 1F5D8;CLOCKWISE RIGHT AND LEFT SEMICIRCLE ARROWS;So;0;ON;;;;;N;;;;; 1F5D9;CANCELLATION X;So;0;ON;;;;;N;;;;; 1F5DA;INCREASE FONT SIZE SYMBOL;So;0;ON;;;;;N;;;;; 1F5DB;DECREASE FONT SIZE SYMBOL;So;0;ON;;;;;N;;;;; 1F5DC;COMPRESSION;So;0;ON;;;;;N;;;;; 1F5DD;OLD KEY;So;0;ON;;;;;N;;;;; 1F5DE;ROLLED-UP NEWSPAPER;So;0;ON;;;;;N;;;;; 1F5DF;PAGE WITH CIRCLED TEXT;So;0;ON;;;;;N;;;;; 1F5E0;STOCK CHART;So;0;ON;;;;;N;;;;; 1F5E1;DAGGER KNIFE;So;0;ON;;;;;N;;;;; 1F5E2;LIPS;So;0;ON;;;;;N;;;;; 1F5E3;SPEAKING HEAD IN SILHOUETTE;So;0;ON;;;;;N;;;;; 1F5E4;THREE RAYS ABOVE;So;0;ON;;;;;N;;;;; 1F5E5;THREE RAYS BELOW;So;0;ON;;;;;N;;;;; 1F5E6;THREE RAYS LEFT;So;0;ON;;;;;N;;;;; 1F5E7;THREE RAYS RIGHT;So;0;ON;;;;;N;;;;; 1F5E8;LEFT SPEECH BUBBLE;So;0;ON;;;;;N;;;;; 1F5E9;RIGHT SPEECH BUBBLE;So;0;ON;;;;;N;;;;; 1F5EA;TWO SPEECH BUBBLES;So;0;ON;;;;;N;;;;; 1F5EB;THREE SPEECH BUBBLES;So;0;ON;;;;;N;;;;; 1F5EC;LEFT THOUGHT BUBBLE;So;0;ON;;;;;N;;;;; 1F5ED;RIGHT THOUGHT BUBBLE;So;0;ON;;;;;N;;;;; 1F5EE;LEFT ANGER BUBBLE;So;0;ON;;;;;N;;;;; 1F5EF;RIGHT ANGER BUBBLE;So;0;ON;;;;;N;;;;; 1F5F0;MOOD BUBBLE;So;0;ON;;;;;N;;;;; 1F5F1;LIGHTNING MOOD BUBBLE;So;0;ON;;;;;N;;;;; 1F5F2;LIGHTNING MOOD;So;0;ON;;;;;N;;;;; 1F5F3;BALLOT BOX WITH BALLOT;So;0;ON;;;;;N;;;;; 1F5F4;BALLOT SCRIPT X;So;0;ON;;;;;N;;;;; 1F5F5;BALLOT BOX WITH SCRIPT X;So;0;ON;;;;;N;;;;; 1F5F6;BALLOT BOLD SCRIPT X;So;0;ON;;;;;N;;;;; 1F5F7;BALLOT BOX WITH BOLD SCRIPT X;So;0;ON;;;;;N;;;;; 1F5F8;LIGHT CHECK MARK;So;0;ON;;;;;N;;;;; 1F5F9;BALLOT BOX WITH BOLD CHECK;So;0;ON;;;;;N;;;;; 1F5FA;WORLD MAP;So;0;ON;;;;;N;;;;; 1F5FB;MOUNT FUJI;So;0;ON;;;;;N;;;;; 1F5FC;TOKYO TOWER;So;0;ON;;;;;N;;;;; 1F5FD;STATUE OF LIBERTY;So;0;ON;;;;;N;;;;; 1F5FE;SILHOUETTE OF JAPAN;So;0;ON;;;;;N;;;;; 1F5FF;MOYAI;So;0;ON;;;;;N;;;;; 1F600;GRINNING FACE;So;0;ON;;;;;N;;;;; 1F601;GRINNING FACE WITH SMILING EYES;So;0;ON;;;;;N;;;;; 1F602;FACE WITH TEARS OF JOY;So;0;ON;;;;;N;;;;; 1F603;SMILING FACE WITH OPEN MOUTH;So;0;ON;;;;;N;;;;; 1F604;SMILING FACE WITH OPEN MOUTH AND SMILING EYES;So;0;ON;;;;;N;;;;; 1F605;SMILING FACE WITH OPEN MOUTH AND COLD SWEAT;So;0;ON;;;;;N;;;;; 1F606;SMILING FACE WITH OPEN MOUTH AND TIGHTLY-CLOSED EYES;So;0;ON;;;;;N;;;;; 1F607;SMILING FACE WITH HALO;So;0;ON;;;;;N;;;;; 1F608;SMILING FACE WITH HORNS;So;0;ON;;;;;N;;;;; 1F609;WINKING FACE;So;0;ON;;;;;N;;;;; 1F60A;SMILING FACE WITH SMILING EYES;So;0;ON;;;;;N;;;;; 1F60B;FACE SAVOURING DELICIOUS FOOD;So;0;ON;;;;;N;;;;; 1F60C;RELIEVED FACE;So;0;ON;;;;;N;;;;; 1F60D;SMILING FACE WITH HEART-SHAPED EYES;So;0;ON;;;;;N;;;;; 1F60E;SMILING FACE WITH SUNGLASSES;So;0;ON;;;;;N;;;;; 1F60F;SMIRKING FACE;So;0;ON;;;;;N;;;;; 1F610;NEUTRAL FACE;So;0;ON;;;;;N;;;;; 1F611;EXPRESSIONLESS FACE;So;0;ON;;;;;N;;;;; 1F612;UNAMUSED FACE;So;0;ON;;;;;N;;;;; 1F613;FACE WITH COLD SWEAT;So;0;ON;;;;;N;;;;; 1F614;PENSIVE FACE;So;0;ON;;;;;N;;;;; 1F615;CONFUSED FACE;So;0;ON;;;;;N;;;;; 1F616;CONFOUNDED FACE;So;0;ON;;;;;N;;;;; 1F617;KISSING FACE;So;0;ON;;;;;N;;;;; 1F618;FACE THROWING A KISS;So;0;ON;;;;;N;;;;; 1F619;KISSING FACE WITH SMILING EYES;So;0;ON;;;;;N;;;;; 1F61A;KISSING FACE WITH CLOSED EYES;So;0;ON;;;;;N;;;;; 1F61B;FACE WITH STUCK-OUT TONGUE;So;0;ON;;;;;N;;;;; 1F61C;FACE WITH STUCK-OUT TONGUE AND WINKING EYE;So;0;ON;;;;;N;;;;; 1F61D;FACE WITH STUCK-OUT TONGUE AND TIGHTLY-CLOSED EYES;So;0;ON;;;;;N;;;;; 1F61E;DISAPPOINTED FACE;So;0;ON;;;;;N;;;;; 1F61F;WORRIED FACE;So;0;ON;;;;;N;;;;; 1F620;ANGRY FACE;So;0;ON;;;;;N;;;;; 1F621;POUTING FACE;So;0;ON;;;;;N;;;;; 1F622;CRYING FACE;So;0;ON;;;;;N;;;;; 1F623;PERSEVERING FACE;So;0;ON;;;;;N;;;;; 1F624;FACE WITH LOOK OF TRIUMPH;So;0;ON;;;;;N;;;;; 1F625;DISAPPOINTED BUT RELIEVED FACE;So;0;ON;;;;;N;;;;; 1F626;FROWNING FACE WITH OPEN MOUTH;So;0;ON;;;;;N;;;;; 1F627;ANGUISHED FACE;So;0;ON;;;;;N;;;;; 1F628;FEARFUL FACE;So;0;ON;;;;;N;;;;; 1F629;WEARY FACE;So;0;ON;;;;;N;;;;; 1F62A;SLEEPY FACE;So;0;ON;;;;;N;;;;; 1F62B;TIRED FACE;So;0;ON;;;;;N;;;;; 1F62C;GRIMACING FACE;So;0;ON;;;;;N;;;;; 1F62D;LOUDLY CRYING FACE;So;0;ON;;;;;N;;;;; 1F62E;FACE WITH OPEN MOUTH;So;0;ON;;;;;N;;;;; 1F62F;HUSHED FACE;So;0;ON;;;;;N;;;;; 1F630;FACE WITH OPEN MOUTH AND COLD SWEAT;So;0;ON;;;;;N;;;;; 1F631;FACE SCREAMING IN FEAR;So;0;ON;;;;;N;;;;; 1F632;ASTONISHED FACE;So;0;ON;;;;;N;;;;; 1F633;FLUSHED FACE;So;0;ON;;;;;N;;;;; 1F634;SLEEPING FACE;So;0;ON;;;;;N;;;;; 1F635;DIZZY FACE;So;0;ON;;;;;N;;;;; 1F636;FACE WITHOUT MOUTH;So;0;ON;;;;;N;;;;; 1F637;FACE WITH MEDICAL MASK;So;0;ON;;;;;N;;;;; 1F638;GRINNING CAT FACE WITH SMILING EYES;So;0;ON;;;;;N;;;;; 1F639;CAT FACE WITH TEARS OF JOY;So;0;ON;;;;;N;;;;; 1F63A;SMILING CAT FACE WITH OPEN MOUTH;So;0;ON;;;;;N;;;;; 1F63B;SMILING CAT FACE WITH HEART-SHAPED EYES;So;0;ON;;;;;N;;;;; 1F63C;CAT FACE WITH WRY SMILE;So;0;ON;;;;;N;;;;; 1F63D;KISSING CAT FACE WITH CLOSED EYES;So;0;ON;;;;;N;;;;; 1F63E;POUTING CAT FACE;So;0;ON;;;;;N;;;;; 1F63F;CRYING CAT FACE;So;0;ON;;;;;N;;;;; 1F640;WEARY CAT FACE;So;0;ON;;;;;N;;;;; 1F641;SLIGHTLY FROWNING FACE;So;0;ON;;;;;N;;;;; 1F642;SLIGHTLY SMILING FACE;So;0;ON;;;;;N;;;;; 1F645;FACE WITH NO GOOD GESTURE;So;0;ON;;;;;N;;;;; 1F646;FACE WITH OK GESTURE;So;0;ON;;;;;N;;;;; 1F647;PERSON BOWING DEEPLY;So;0;ON;;;;;N;;;;; 1F648;SEE-NO-EVIL MONKEY;So;0;ON;;;;;N;;;;; 1F649;HEAR-NO-EVIL MONKEY;So;0;ON;;;;;N;;;;; 1F64A;SPEAK-NO-EVIL MONKEY;So;0;ON;;;;;N;;;;; 1F64B;HAPPY PERSON RAISING ONE HAND;So;0;ON;;;;;N;;;;; 1F64C;PERSON RAISING BOTH HANDS IN CELEBRATION;So;0;ON;;;;;N;;;;; 1F64D;PERSON FROWNING;So;0;ON;;;;;N;;;;; 1F64E;PERSON WITH POUTING FACE;So;0;ON;;;;;N;;;;; 1F64F;PERSON WITH FOLDED HANDS;So;0;ON;;;;;N;;;;; 1F650;NORTH WEST POINTING LEAF;So;0;ON;;;;;N;;;;; 1F651;SOUTH WEST POINTING LEAF;So;0;ON;;;;;N;;;;; 1F652;NORTH EAST POINTING LEAF;So;0;ON;;;;;N;;;;; 1F653;SOUTH EAST POINTING LEAF;So;0;ON;;;;;N;;;;; 1F654;TURNED NORTH WEST POINTING LEAF;So;0;ON;;;;;N;;;;; 1F655;TURNED SOUTH WEST POINTING LEAF;So;0;ON;;;;;N;;;;; 1F656;TURNED NORTH EAST POINTING LEAF;So;0;ON;;;;;N;;;;; 1F657;TURNED SOUTH EAST POINTING LEAF;So;0;ON;;;;;N;;;;; 1F658;NORTH WEST POINTING VINE LEAF;So;0;ON;;;;;N;;;;; 1F659;SOUTH WEST POINTING VINE LEAF;So;0;ON;;;;;N;;;;; 1F65A;NORTH EAST POINTING VINE LEAF;So;0;ON;;;;;N;;;;; 1F65B;SOUTH EAST POINTING VINE LEAF;So;0;ON;;;;;N;;;;; 1F65C;HEAVY NORTH WEST POINTING VINE LEAF;So;0;ON;;;;;N;;;;; 1F65D;HEAVY SOUTH WEST POINTING VINE LEAF;So;0;ON;;;;;N;;;;; 1F65E;HEAVY NORTH EAST POINTING VINE LEAF;So;0;ON;;;;;N;;;;; 1F65F;HEAVY SOUTH EAST POINTING VINE LEAF;So;0;ON;;;;;N;;;;; 1F660;NORTH WEST POINTING BUD;So;0;ON;;;;;N;;;;; 1F661;SOUTH WEST POINTING BUD;So;0;ON;;;;;N;;;;; 1F662;NORTH EAST POINTING BUD;So;0;ON;;;;;N;;;;; 1F663;SOUTH EAST POINTING BUD;So;0;ON;;;;;N;;;;; 1F664;HEAVY NORTH WEST POINTING BUD;So;0;ON;;;;;N;;;;; 1F665;HEAVY SOUTH WEST POINTING BUD;So;0;ON;;;;;N;;;;; 1F666;HEAVY NORTH EAST POINTING BUD;So;0;ON;;;;;N;;;;; 1F667;HEAVY SOUTH EAST POINTING BUD;So;0;ON;;;;;N;;;;; 1F668;HOLLOW QUILT SQUARE ORNAMENT;So;0;ON;;;;;N;;;;; 1F669;HOLLOW QUILT SQUARE ORNAMENT IN BLACK SQUARE;So;0;ON;;;;;N;;;;; 1F66A;SOLID QUILT SQUARE ORNAMENT;So;0;ON;;;;;N;;;;; 1F66B;SOLID QUILT SQUARE ORNAMENT IN BLACK SQUARE;So;0;ON;;;;;N;;;;; 1F66C;LEFTWARDS ROCKET;So;0;ON;;;;;N;;;;; 1F66D;UPWARDS ROCKET;So;0;ON;;;;;N;;;;; 1F66E;RIGHTWARDS ROCKET;So;0;ON;;;;;N;;;;; 1F66F;DOWNWARDS ROCKET;So;0;ON;;;;;N;;;;; 1F670;SCRIPT LIGATURE ET ORNAMENT;So;0;ON;;;;;N;;;;; 1F671;HEAVY SCRIPT LIGATURE ET ORNAMENT;So;0;ON;;;;;N;;;;; 1F672;LIGATURE OPEN ET ORNAMENT;So;0;ON;;;;;N;;;;; 1F673;HEAVY LIGATURE OPEN ET ORNAMENT;So;0;ON;;;;;N;;;;; 1F674;HEAVY AMPERSAND ORNAMENT;So;0;ON;;;;;N;;;;; 1F675;SWASH AMPERSAND ORNAMENT;So;0;ON;;;;;N;;;;; 1F676;SANS-SERIF HEAVY DOUBLE TURNED COMMA QUOTATION MARK ORNAMENT;So;0;ON;;;;;N;;;;; 1F677;SANS-SERIF HEAVY DOUBLE COMMA QUOTATION MARK ORNAMENT;So;0;ON;;;;;N;;;;; 1F678;SANS-SERIF HEAVY LOW DOUBLE COMMA QUOTATION MARK ORNAMENT;So;0;ON;;;;;N;;;;; 1F679;HEAVY INTERROBANG ORNAMENT;So;0;ON;;;;;N;;;;; 1F67A;SANS-SERIF INTERROBANG ORNAMENT;So;0;ON;;;;;N;;;;; 1F67B;HEAVY SANS-SERIF INTERROBANG ORNAMENT;So;0;ON;;;;;N;;;;; 1F67C;VERY HEAVY SOLIDUS;So;0;ON;;;;;N;;;;; 1F67D;VERY HEAVY REVERSE SOLIDUS;So;0;ON;;;;;N;;;;; 1F67E;CHECKER BOARD;So;0;ON;;;;;N;;;;; 1F67F;REVERSE CHECKER BOARD;So;0;ON;;;;;N;;;;; 1F680;ROCKET;So;0;ON;;;;;N;;;;; 1F681;HELICOPTER;So;0;ON;;;;;N;;;;; 1F682;STEAM LOCOMOTIVE;So;0;ON;;;;;N;;;;; 1F683;RAILWAY CAR;So;0;ON;;;;;N;;;;; 1F684;HIGH-SPEED TRAIN;So;0;ON;;;;;N;;;;; 1F685;HIGH-SPEED TRAIN WITH BULLET NOSE;So;0;ON;;;;;N;;;;; 1F686;TRAIN;So;0;ON;;;;;N;;;;; 1F687;METRO;So;0;ON;;;;;N;;;;; 1F688;LIGHT RAIL;So;0;ON;;;;;N;;;;; 1F689;STATION;So;0;ON;;;;;N;;;;; 1F68A;TRAM;So;0;ON;;;;;N;;;;; 1F68B;TRAM CAR;So;0;ON;;;;;N;;;;; 1F68C;BUS;So;0;ON;;;;;N;;;;; 1F68D;ONCOMING BUS;So;0;ON;;;;;N;;;;; 1F68E;TROLLEYBUS;So;0;ON;;;;;N;;;;; 1F68F;BUS STOP;So;0;ON;;;;;N;;;;; 1F690;MINIBUS;So;0;ON;;;;;N;;;;; 1F691;AMBULANCE;So;0;ON;;;;;N;;;;; 1F692;FIRE ENGINE;So;0;ON;;;;;N;;;;; 1F693;POLICE CAR;So;0;ON;;;;;N;;;;; 1F694;ONCOMING POLICE CAR;So;0;ON;;;;;N;;;;; 1F695;TAXI;So;0;ON;;;;;N;;;;; 1F696;ONCOMING TAXI;So;0;ON;;;;;N;;;;; 1F697;AUTOMOBILE;So;0;ON;;;;;N;;;;; 1F698;ONCOMING AUTOMOBILE;So;0;ON;;;;;N;;;;; 1F699;RECREATIONAL VEHICLE;So;0;ON;;;;;N;;;;; 1F69A;DELIVERY TRUCK;So;0;ON;;;;;N;;;;; 1F69B;ARTICULATED LORRY;So;0;ON;;;;;N;;;;; 1F69C;TRACTOR;So;0;ON;;;;;N;;;;; 1F69D;MONORAIL;So;0;ON;;;;;N;;;;; 1F69E;MOUNTAIN RAILWAY;So;0;ON;;;;;N;;;;; 1F69F;SUSPENSION RAILWAY;So;0;ON;;;;;N;;;;; 1F6A0;MOUNTAIN CABLEWAY;So;0;ON;;;;;N;;;;; 1F6A1;AERIAL TRAMWAY;So;0;ON;;;;;N;;;;; 1F6A2;SHIP;So;0;ON;;;;;N;;;;; 1F6A3;ROWBOAT;So;0;ON;;;;;N;;;;; 1F6A4;SPEEDBOAT;So;0;ON;;;;;N;;;;; 1F6A5;HORIZONTAL TRAFFIC LIGHT;So;0;ON;;;;;N;;;;; 1F6A6;VERTICAL TRAFFIC LIGHT;So;0;ON;;;;;N;;;;; 1F6A7;CONSTRUCTION SIGN;So;0;ON;;;;;N;;;;; 1F6A8;POLICE CARS REVOLVING LIGHT;So;0;ON;;;;;N;;;;; 1F6A9;TRIANGULAR FLAG ON POST;So;0;ON;;;;;N;;;;; 1F6AA;DOOR;So;0;ON;;;;;N;;;;; 1F6AB;NO ENTRY SIGN;So;0;ON;;;;;N;;;;; 1F6AC;SMOKING SYMBOL;So;0;ON;;;;;N;;;;; 1F6AD;NO SMOKING SYMBOL;So;0;ON;;;;;N;;;;; 1F6AE;PUT LITTER IN ITS PLACE SYMBOL;So;0;ON;;;;;N;;;;; 1F6AF;DO NOT LITTER SYMBOL;So;0;ON;;;;;N;;;;; 1F6B0;POTABLE WATER SYMBOL;So;0;ON;;;;;N;;;;; 1F6B1;NON-POTABLE WATER SYMBOL;So;0;ON;;;;;N;;;;; 1F6B2;BICYCLE;So;0;ON;;;;;N;;;;; 1F6B3;NO BICYCLES;So;0;ON;;;;;N;;;;; 1F6B4;BICYCLIST;So;0;ON;;;;;N;;;;; 1F6B5;MOUNTAIN BICYCLIST;So;0;ON;;;;;N;;;;; 1F6B6;PEDESTRIAN;So;0;ON;;;;;N;;;;; 1F6B7;NO PEDESTRIANS;So;0;ON;;;;;N;;;;; 1F6B8;CHILDREN CROSSING;So;0;ON;;;;;N;;;;; 1F6B9;MENS SYMBOL;So;0;ON;;;;;N;;;;; 1F6BA;WOMENS SYMBOL;So;0;ON;;;;;N;;;;; 1F6BB;RESTROOM;So;0;ON;;;;;N;;;;; 1F6BC;BABY SYMBOL;So;0;ON;;;;;N;;;;; 1F6BD;TOILET;So;0;ON;;;;;N;;;;; 1F6BE;WATER CLOSET;So;0;ON;;;;;N;;;;; 1F6BF;SHOWER;So;0;ON;;;;;N;;;;; 1F6C0;BATH;So;0;ON;;;;;N;;;;; 1F6C1;BATHTUB;So;0;ON;;;;;N;;;;; 1F6C2;PASSPORT CONTROL;So;0;ON;;;;;N;;;;; 1F6C3;CUSTOMS;So;0;ON;;;;;N;;;;; 1F6C4;BAGGAGE CLAIM;So;0;ON;;;;;N;;;;; 1F6C5;LEFT LUGGAGE;So;0;ON;;;;;N;;;;; 1F6C6;TRIANGLE WITH ROUNDED CORNERS;So;0;ON;;;;;N;;;;; 1F6C7;PROHIBITED SIGN;So;0;ON;;;;;N;;;;; 1F6C8;CIRCLED INFORMATION SOURCE;So;0;ON;;;;;N;;;;; 1F6C9;BOYS SYMBOL;So;0;ON;;;;;N;;;;; 1F6CA;GIRLS SYMBOL;So;0;ON;;;;;N;;;;; 1F6CB;COUCH AND LAMP;So;0;ON;;;;;N;;;;; 1F6CC;SLEEPING ACCOMMODATION;So;0;ON;;;;;N;;;;; 1F6CD;SHOPPING BAGS;So;0;ON;;;;;N;;;;; 1F6CE;BELLHOP BELL;So;0;ON;;;;;N;;;;; 1F6CF;BED;So;0;ON;;;;;N;;;;; 1F6E0;HAMMER AND WRENCH;So;0;ON;;;;;N;;;;; 1F6E1;SHIELD;So;0;ON;;;;;N;;;;; 1F6E2;OIL DRUM;So;0;ON;;;;;N;;;;; 1F6E3;MOTORWAY;So;0;ON;;;;;N;;;;; 1F6E4;RAILWAY TRACK;So;0;ON;;;;;N;;;;; 1F6E5;MOTOR BOAT;So;0;ON;;;;;N;;;;; 1F6E6;UP-POINTING MILITARY AIRPLANE;So;0;ON;;;;;N;;;;; 1F6E7;UP-POINTING AIRPLANE;So;0;ON;;;;;N;;;;; 1F6E8;UP-POINTING SMALL AIRPLANE;So;0;ON;;;;;N;;;;; 1F6E9;SMALL AIRPLANE;So;0;ON;;;;;N;;;;; 1F6EA;NORTHEAST-POINTING AIRPLANE;So;0;ON;;;;;N;;;;; 1F6EB;AIRPLANE DEPARTURE;So;0;ON;;;;;N;;;;; 1F6EC;AIRPLANE ARRIVING;So;0;ON;;;;;N;;;;; 1F6F0;SATELLITE;So;0;ON;;;;;N;;;;; 1F6F1;ONCOMING FIRE ENGINE;So;0;ON;;;;;N;;;;; 1F6F2;DIESEL LOCOMOTIVE;So;0;ON;;;;;N;;;;; 1F6F3;PASSENGER SHIP;So;0;ON;;;;;N;;;;; 1F700;ALCHEMICAL SYMBOL FOR QUINTESSENCE;So;0;ON;;;;;N;;;;; 1F701;ALCHEMICAL SYMBOL FOR AIR;So;0;ON;;;;;N;;;;; 1F702;ALCHEMICAL SYMBOL FOR FIRE;So;0;ON;;;;;N;;;;; 1F703;ALCHEMICAL SYMBOL FOR EARTH;So;0;ON;;;;;N;;;;; 1F704;ALCHEMICAL SYMBOL FOR WATER;So;0;ON;;;;;N;;;;; 1F705;ALCHEMICAL SYMBOL FOR AQUAFORTIS;So;0;ON;;;;;N;;;;; 1F706;ALCHEMICAL SYMBOL FOR AQUA REGIA;So;0;ON;;;;;N;;;;; 1F707;ALCHEMICAL SYMBOL FOR AQUA REGIA-2;So;0;ON;;;;;N;;;;; 1F708;ALCHEMICAL SYMBOL FOR AQUA VITAE;So;0;ON;;;;;N;;;;; 1F709;ALCHEMICAL SYMBOL FOR AQUA VITAE-2;So;0;ON;;;;;N;;;;; 1F70A;ALCHEMICAL SYMBOL FOR VINEGAR;So;0;ON;;;;;N;;;;; 1F70B;ALCHEMICAL SYMBOL FOR VINEGAR-2;So;0;ON;;;;;N;;;;; 1F70C;ALCHEMICAL SYMBOL FOR VINEGAR-3;So;0;ON;;;;;N;;;;; 1F70D;ALCHEMICAL SYMBOL FOR SULFUR;So;0;ON;;;;;N;;;;; 1F70E;ALCHEMICAL SYMBOL FOR PHILOSOPHERS SULFUR;So;0;ON;;;;;N;;;;; 1F70F;ALCHEMICAL SYMBOL FOR BLACK SULFUR;So;0;ON;;;;;N;;;;; 1F710;ALCHEMICAL SYMBOL FOR MERCURY SUBLIMATE;So;0;ON;;;;;N;;;;; 1F711;ALCHEMICAL SYMBOL FOR MERCURY SUBLIMATE-2;So;0;ON;;;;;N;;;;; 1F712;ALCHEMICAL SYMBOL FOR MERCURY SUBLIMATE-3;So;0;ON;;;;;N;;;;; 1F713;ALCHEMICAL SYMBOL FOR CINNABAR;So;0;ON;;;;;N;;;;; 1F714;ALCHEMICAL SYMBOL FOR SALT;So;0;ON;;;;;N;;;;; 1F715;ALCHEMICAL SYMBOL FOR NITRE;So;0;ON;;;;;N;;;;; 1F716;ALCHEMICAL SYMBOL FOR VITRIOL;So;0;ON;;;;;N;;;;; 1F717;ALCHEMICAL SYMBOL FOR VITRIOL-2;So;0;ON;;;;;N;;;;; 1F718;ALCHEMICAL SYMBOL FOR ROCK SALT;So;0;ON;;;;;N;;;;; 1F719;ALCHEMICAL SYMBOL FOR ROCK SALT-2;So;0;ON;;;;;N;;;;; 1F71A;ALCHEMICAL SYMBOL FOR GOLD;So;0;ON;;;;;N;;;;; 1F71B;ALCHEMICAL SYMBOL FOR SILVER;So;0;ON;;;;;N;;;;; 1F71C;ALCHEMICAL SYMBOL FOR IRON ORE;So;0;ON;;;;;N;;;;; 1F71D;ALCHEMICAL SYMBOL FOR IRON ORE-2;So;0;ON;;;;;N;;;;; 1F71E;ALCHEMICAL SYMBOL FOR CROCUS OF IRON;So;0;ON;;;;;N;;;;; 1F71F;ALCHEMICAL SYMBOL FOR REGULUS OF IRON;So;0;ON;;;;;N;;;;; 1F720;ALCHEMICAL SYMBOL FOR COPPER ORE;So;0;ON;;;;;N;;;;; 1F721;ALCHEMICAL SYMBOL FOR IRON-COPPER ORE;So;0;ON;;;;;N;;;;; 1F722;ALCHEMICAL SYMBOL FOR SUBLIMATE OF COPPER;So;0;ON;;;;;N;;;;; 1F723;ALCHEMICAL SYMBOL FOR CROCUS OF COPPER;So;0;ON;;;;;N;;;;; 1F724;ALCHEMICAL SYMBOL FOR CROCUS OF COPPER-2;So;0;ON;;;;;N;;;;; 1F725;ALCHEMICAL SYMBOL FOR COPPER ANTIMONIATE;So;0;ON;;;;;N;;;;; 1F726;ALCHEMICAL SYMBOL FOR SALT OF COPPER ANTIMONIATE;So;0;ON;;;;;N;;;;; 1F727;ALCHEMICAL SYMBOL FOR SUBLIMATE OF SALT OF COPPER;So;0;ON;;;;;N;;;;; 1F728;ALCHEMICAL SYMBOL FOR VERDIGRIS;So;0;ON;;;;;N;;;;; 1F729;ALCHEMICAL SYMBOL FOR TIN ORE;So;0;ON;;;;;N;;;;; 1F72A;ALCHEMICAL SYMBOL FOR LEAD ORE;So;0;ON;;;;;N;;;;; 1F72B;ALCHEMICAL SYMBOL FOR ANTIMONY ORE;So;0;ON;;;;;N;;;;; 1F72C;ALCHEMICAL SYMBOL FOR SUBLIMATE OF ANTIMONY;So;0;ON;;;;;N;;;;; 1F72D;ALCHEMICAL SYMBOL FOR SALT OF ANTIMONY;So;0;ON;;;;;N;;;;; 1F72E;ALCHEMICAL SYMBOL FOR SUBLIMATE OF SALT OF ANTIMONY;So;0;ON;;;;;N;;;;; 1F72F;ALCHEMICAL SYMBOL FOR VINEGAR OF ANTIMONY;So;0;ON;;;;;N;;;;; 1F730;ALCHEMICAL SYMBOL FOR REGULUS OF ANTIMONY;So;0;ON;;;;;N;;;;; 1F731;ALCHEMICAL SYMBOL FOR REGULUS OF ANTIMONY-2;So;0;ON;;;;;N;;;;; 1F732;ALCHEMICAL SYMBOL FOR REGULUS;So;0;ON;;;;;N;;;;; 1F733;ALCHEMICAL SYMBOL FOR REGULUS-2;So;0;ON;;;;;N;;;;; 1F734;ALCHEMICAL SYMBOL FOR REGULUS-3;So;0;ON;;;;;N;;;;; 1F735;ALCHEMICAL SYMBOL FOR REGULUS-4;So;0;ON;;;;;N;;;;; 1F736;ALCHEMICAL SYMBOL FOR ALKALI;So;0;ON;;;;;N;;;;; 1F737;ALCHEMICAL SYMBOL FOR ALKALI-2;So;0;ON;;;;;N;;;;; 1F738;ALCHEMICAL SYMBOL FOR MARCASITE;So;0;ON;;;;;N;;;;; 1F739;ALCHEMICAL SYMBOL FOR SAL-AMMONIAC;So;0;ON;;;;;N;;;;; 1F73A;ALCHEMICAL SYMBOL FOR ARSENIC;So;0;ON;;;;;N;;;;; 1F73B;ALCHEMICAL SYMBOL FOR REALGAR;So;0;ON;;;;;N;;;;; 1F73C;ALCHEMICAL SYMBOL FOR REALGAR-2;So;0;ON;;;;;N;;;;; 1F73D;ALCHEMICAL SYMBOL FOR AURIPIGMENT;So;0;ON;;;;;N;;;;; 1F73E;ALCHEMICAL SYMBOL FOR BISMUTH ORE;So;0;ON;;;;;N;;;;; 1F73F;ALCHEMICAL SYMBOL FOR TARTAR;So;0;ON;;;;;N;;;;; 1F740;ALCHEMICAL SYMBOL FOR TARTAR-2;So;0;ON;;;;;N;;;;; 1F741;ALCHEMICAL SYMBOL FOR QUICK LIME;So;0;ON;;;;;N;;;;; 1F742;ALCHEMICAL SYMBOL FOR BORAX;So;0;ON;;;;;N;;;;; 1F743;ALCHEMICAL SYMBOL FOR BORAX-2;So;0;ON;;;;;N;;;;; 1F744;ALCHEMICAL SYMBOL FOR BORAX-3;So;0;ON;;;;;N;;;;; 1F745;ALCHEMICAL SYMBOL FOR ALUM;So;0;ON;;;;;N;;;;; 1F746;ALCHEMICAL SYMBOL FOR OIL;So;0;ON;;;;;N;;;;; 1F747;ALCHEMICAL SYMBOL FOR SPIRIT;So;0;ON;;;;;N;;;;; 1F748;ALCHEMICAL SYMBOL FOR TINCTURE;So;0;ON;;;;;N;;;;; 1F749;ALCHEMICAL SYMBOL FOR GUM;So;0;ON;;;;;N;;;;; 1F74A;ALCHEMICAL SYMBOL FOR WAX;So;0;ON;;;;;N;;;;; 1F74B;ALCHEMICAL SYMBOL FOR POWDER;So;0;ON;;;;;N;;;;; 1F74C;ALCHEMICAL SYMBOL FOR CALX;So;0;ON;;;;;N;;;;; 1F74D;ALCHEMICAL SYMBOL FOR TUTTY;So;0;ON;;;;;N;;;;; 1F74E;ALCHEMICAL SYMBOL FOR CAPUT MORTUUM;So;0;ON;;;;;N;;;;; 1F74F;ALCHEMICAL SYMBOL FOR SCEPTER OF JOVE;So;0;ON;;;;;N;;;;; 1F750;ALCHEMICAL SYMBOL FOR CADUCEUS;So;0;ON;;;;;N;;;;; 1F751;ALCHEMICAL SYMBOL FOR TRIDENT;So;0;ON;;;;;N;;;;; 1F752;ALCHEMICAL SYMBOL FOR STARRED TRIDENT;So;0;ON;;;;;N;;;;; 1F753;ALCHEMICAL SYMBOL FOR LODESTONE;So;0;ON;;;;;N;;;;; 1F754;ALCHEMICAL SYMBOL FOR SOAP;So;0;ON;;;;;N;;;;; 1F755;ALCHEMICAL SYMBOL FOR URINE;So;0;ON;;;;;N;;;;; 1F756;ALCHEMICAL SYMBOL FOR HORSE DUNG;So;0;ON;;;;;N;;;;; 1F757;ALCHEMICAL SYMBOL FOR ASHES;So;0;ON;;;;;N;;;;; 1F758;ALCHEMICAL SYMBOL FOR POT ASHES;So;0;ON;;;;;N;;;;; 1F759;ALCHEMICAL SYMBOL FOR BRICK;So;0;ON;;;;;N;;;;; 1F75A;ALCHEMICAL SYMBOL FOR POWDERED BRICK;So;0;ON;;;;;N;;;;; 1F75B;ALCHEMICAL SYMBOL FOR AMALGAM;So;0;ON;;;;;N;;;;; 1F75C;ALCHEMICAL SYMBOL FOR STRATUM SUPER STRATUM;So;0;ON;;;;;N;;;;; 1F75D;ALCHEMICAL SYMBOL FOR STRATUM SUPER STRATUM-2;So;0;ON;;;;;N;;;;; 1F75E;ALCHEMICAL SYMBOL FOR SUBLIMATION;So;0;ON;;;;;N;;;;; 1F75F;ALCHEMICAL SYMBOL FOR PRECIPITATE;So;0;ON;;;;;N;;;;; 1F760;ALCHEMICAL SYMBOL FOR DISTILL;So;0;ON;;;;;N;;;;; 1F761;ALCHEMICAL SYMBOL FOR DISSOLVE;So;0;ON;;;;;N;;;;; 1F762;ALCHEMICAL SYMBOL FOR DISSOLVE-2;So;0;ON;;;;;N;;;;; 1F763;ALCHEMICAL SYMBOL FOR PURIFY;So;0;ON;;;;;N;;;;; 1F764;ALCHEMICAL SYMBOL FOR PUTREFACTION;So;0;ON;;;;;N;;;;; 1F765;ALCHEMICAL SYMBOL FOR CRUCIBLE;So;0;ON;;;;;N;;;;; 1F766;ALCHEMICAL SYMBOL FOR CRUCIBLE-2;So;0;ON;;;;;N;;;;; 1F767;ALCHEMICAL SYMBOL FOR CRUCIBLE-3;So;0;ON;;;;;N;;;;; 1F768;ALCHEMICAL SYMBOL FOR CRUCIBLE-4;So;0;ON;;;;;N;;;;; 1F769;ALCHEMICAL SYMBOL FOR CRUCIBLE-5;So;0;ON;;;;;N;;;;; 1F76A;ALCHEMICAL SYMBOL FOR ALEMBIC;So;0;ON;;;;;N;;;;; 1F76B;ALCHEMICAL SYMBOL FOR BATH OF MARY;So;0;ON;;;;;N;;;;; 1F76C;ALCHEMICAL SYMBOL FOR BATH OF VAPOURS;So;0;ON;;;;;N;;;;; 1F76D;ALCHEMICAL SYMBOL FOR RETORT;So;0;ON;;;;;N;;;;; 1F76E;ALCHEMICAL SYMBOL FOR HOUR;So;0;ON;;;;;N;;;;; 1F76F;ALCHEMICAL SYMBOL FOR NIGHT;So;0;ON;;;;;N;;;;; 1F770;ALCHEMICAL SYMBOL FOR DAY-NIGHT;So;0;ON;;;;;N;;;;; 1F771;ALCHEMICAL SYMBOL FOR MONTH;So;0;ON;;;;;N;;;;; 1F772;ALCHEMICAL SYMBOL FOR HALF DRAM;So;0;ON;;;;;N;;;;; 1F773;ALCHEMICAL SYMBOL FOR HALF OUNCE;So;0;ON;;;;;N;;;;; 1F780;BLACK LEFT-POINTING ISOSCELES RIGHT TRIANGLE;So;0;ON;;;;;N;;;;; 1F781;BLACK UP-POINTING ISOSCELES RIGHT TRIANGLE;So;0;ON;;;;;N;;;;; 1F782;BLACK RIGHT-POINTING ISOSCELES RIGHT TRIANGLE;So;0;ON;;;;;N;;;;; 1F783;BLACK DOWN-POINTING ISOSCELES RIGHT TRIANGLE;So;0;ON;;;;;N;;;;; 1F784;BLACK SLIGHTLY SMALL CIRCLE;So;0;ON;;;;;N;;;;; 1F785;MEDIUM BOLD WHITE CIRCLE;So;0;ON;;;;;N;;;;; 1F786;BOLD WHITE CIRCLE;So;0;ON;;;;;N;;;;; 1F787;HEAVY WHITE CIRCLE;So;0;ON;;;;;N;;;;; 1F788;VERY HEAVY WHITE CIRCLE;So;0;ON;;;;;N;;;;; 1F789;EXTREMELY HEAVY WHITE CIRCLE;So;0;ON;;;;;N;;;;; 1F78A;WHITE CIRCLE CONTAINING BLACK SMALL CIRCLE;So;0;ON;;;;;N;;;;; 1F78B;ROUND TARGET;So;0;ON;;;;;N;;;;; 1F78C;BLACK TINY SQUARE;So;0;ON;;;;;N;;;;; 1F78D;BLACK SLIGHTLY SMALL SQUARE;So;0;ON;;;;;N;;;;; 1F78E;LIGHT WHITE SQUARE;So;0;ON;;;;;N;;;;; 1F78F;MEDIUM WHITE SQUARE;So;0;ON;;;;;N;;;;; 1F790;BOLD WHITE SQUARE;So;0;ON;;;;;N;;;;; 1F791;HEAVY WHITE SQUARE;So;0;ON;;;;;N;;;;; 1F792;VERY HEAVY WHITE SQUARE;So;0;ON;;;;;N;;;;; 1F793;EXTREMELY HEAVY WHITE SQUARE;So;0;ON;;;;;N;;;;; 1F794;WHITE SQUARE CONTAINING BLACK VERY SMALL SQUARE;So;0;ON;;;;;N;;;;; 1F795;WHITE SQUARE CONTAINING BLACK MEDIUM SQUARE;So;0;ON;;;;;N;;;;; 1F796;SQUARE TARGET;So;0;ON;;;;;N;;;;; 1F797;BLACK TINY DIAMOND;So;0;ON;;;;;N;;;;; 1F798;BLACK VERY SMALL DIAMOND;So;0;ON;;;;;N;;;;; 1F799;BLACK MEDIUM SMALL DIAMOND;So;0;ON;;;;;N;;;;; 1F79A;WHITE DIAMOND CONTAINING BLACK VERY SMALL DIAMOND;So;0;ON;;;;;N;;;;; 1F79B;WHITE DIAMOND CONTAINING BLACK MEDIUM DIAMOND;So;0;ON;;;;;N;;;;; 1F79C;DIAMOND TARGET;So;0;ON;;;;;N;;;;; 1F79D;BLACK TINY LOZENGE;So;0;ON;;;;;N;;;;; 1F79E;BLACK VERY SMALL LOZENGE;So;0;ON;;;;;N;;;;; 1F79F;BLACK MEDIUM SMALL LOZENGE;So;0;ON;;;;;N;;;;; 1F7A0;WHITE LOZENGE CONTAINING BLACK SMALL LOZENGE;So;0;ON;;;;;N;;;;; 1F7A1;THIN GREEK CROSS;So;0;ON;;;;;N;;;;; 1F7A2;LIGHT GREEK CROSS;So;0;ON;;;;;N;;;;; 1F7A3;MEDIUM GREEK CROSS;So;0;ON;;;;;N;;;;; 1F7A4;BOLD GREEK CROSS;So;0;ON;;;;;N;;;;; 1F7A5;VERY BOLD GREEK CROSS;So;0;ON;;;;;N;;;;; 1F7A6;VERY HEAVY GREEK CROSS;So;0;ON;;;;;N;;;;; 1F7A7;EXTREMELY HEAVY GREEK CROSS;So;0;ON;;;;;N;;;;; 1F7A8;THIN SALTIRE;So;0;ON;;;;;N;;;;; 1F7A9;LIGHT SALTIRE;So;0;ON;;;;;N;;;;; 1F7AA;MEDIUM SALTIRE;So;0;ON;;;;;N;;;;; 1F7AB;BOLD SALTIRE;So;0;ON;;;;;N;;;;; 1F7AC;HEAVY SALTIRE;So;0;ON;;;;;N;;;;; 1F7AD;VERY HEAVY SALTIRE;So;0;ON;;;;;N;;;;; 1F7AE;EXTREMELY HEAVY SALTIRE;So;0;ON;;;;;N;;;;; 1F7AF;LIGHT FIVE SPOKED ASTERISK;So;0;ON;;;;;N;;;;; 1F7B0;MEDIUM FIVE SPOKED ASTERISK;So;0;ON;;;;;N;;;;; 1F7B1;BOLD FIVE SPOKED ASTERISK;So;0;ON;;;;;N;;;;; 1F7B2;HEAVY FIVE SPOKED ASTERISK;So;0;ON;;;;;N;;;;; 1F7B3;VERY HEAVY FIVE SPOKED ASTERISK;So;0;ON;;;;;N;;;;; 1F7B4;EXTREMELY HEAVY FIVE SPOKED ASTERISK;So;0;ON;;;;;N;;;;; 1F7B5;LIGHT SIX SPOKED ASTERISK;So;0;ON;;;;;N;;;;; 1F7B6;MEDIUM SIX SPOKED ASTERISK;So;0;ON;;;;;N;;;;; 1F7B7;BOLD SIX SPOKED ASTERISK;So;0;ON;;;;;N;;;;; 1F7B8;HEAVY SIX SPOKED ASTERISK;So;0;ON;;;;;N;;;;; 1F7B9;VERY HEAVY SIX SPOKED ASTERISK;So;0;ON;;;;;N;;;;; 1F7BA;EXTREMELY HEAVY SIX SPOKED ASTERISK;So;0;ON;;;;;N;;;;; 1F7BB;LIGHT EIGHT SPOKED ASTERISK;So;0;ON;;;;;N;;;;; 1F7BC;MEDIUM EIGHT SPOKED ASTERISK;So;0;ON;;;;;N;;;;; 1F7BD;BOLD EIGHT SPOKED ASTERISK;So;0;ON;;;;;N;;;;; 1F7BE;HEAVY EIGHT SPOKED ASTERISK;So;0;ON;;;;;N;;;;; 1F7BF;VERY HEAVY EIGHT SPOKED ASTERISK;So;0;ON;;;;;N;;;;; 1F7C0;LIGHT THREE POINTED BLACK STAR;So;0;ON;;;;;N;;;;; 1F7C1;MEDIUM THREE POINTED BLACK STAR;So;0;ON;;;;;N;;;;; 1F7C2;THREE POINTED BLACK STAR;So;0;ON;;;;;N;;;;; 1F7C3;MEDIUM THREE POINTED PINWHEEL STAR;So;0;ON;;;;;N;;;;; 1F7C4;LIGHT FOUR POINTED BLACK STAR;So;0;ON;;;;;N;;;;; 1F7C5;MEDIUM FOUR POINTED BLACK STAR;So;0;ON;;;;;N;;;;; 1F7C6;FOUR POINTED BLACK STAR;So;0;ON;;;;;N;;;;; 1F7C7;MEDIUM FOUR POINTED PINWHEEL STAR;So;0;ON;;;;;N;;;;; 1F7C8;REVERSE LIGHT FOUR POINTED PINWHEEL STAR;So;0;ON;;;;;N;;;;; 1F7C9;LIGHT FIVE POINTED BLACK STAR;So;0;ON;;;;;N;;;;; 1F7CA;HEAVY FIVE POINTED BLACK STAR;So;0;ON;;;;;N;;;;; 1F7CB;MEDIUM SIX POINTED BLACK STAR;So;0;ON;;;;;N;;;;; 1F7CC;HEAVY SIX POINTED BLACK STAR;So;0;ON;;;;;N;;;;; 1F7CD;SIX POINTED PINWHEEL STAR;So;0;ON;;;;;N;;;;; 1F7CE;MEDIUM EIGHT POINTED BLACK STAR;So;0;ON;;;;;N;;;;; 1F7CF;HEAVY EIGHT POINTED BLACK STAR;So;0;ON;;;;;N;;;;; 1F7D0;VERY HEAVY EIGHT POINTED BLACK STAR;So;0;ON;;;;;N;;;;; 1F7D1;HEAVY EIGHT POINTED PINWHEEL STAR;So;0;ON;;;;;N;;;;; 1F7D2;LIGHT TWELVE POINTED BLACK STAR;So;0;ON;;;;;N;;;;; 1F7D3;HEAVY TWELVE POINTED BLACK STAR;So;0;ON;;;;;N;;;;; 1F7D4;HEAVY TWELVE POINTED PINWHEEL STAR;So;0;ON;;;;;N;;;;; 1F800;LEFTWARDS ARROW WITH SMALL TRIANGLE ARROWHEAD;So;0;ON;;;;;N;;;;; 1F801;UPWARDS ARROW WITH SMALL TRIANGLE ARROWHEAD;So;0;ON;;;;;N;;;;; 1F802;RIGHTWARDS ARROW WITH SMALL TRIANGLE ARROWHEAD;So;0;ON;;;;;N;;;;; 1F803;DOWNWARDS ARROW WITH SMALL TRIANGLE ARROWHEAD;So;0;ON;;;;;N;;;;; 1F804;LEFTWARDS ARROW WITH MEDIUM TRIANGLE ARROWHEAD;So;0;ON;;;;;N;;;;; 1F805;UPWARDS ARROW WITH MEDIUM TRIANGLE ARROWHEAD;So;0;ON;;;;;N;;;;; 1F806;RIGHTWARDS ARROW WITH MEDIUM TRIANGLE ARROWHEAD;So;0;ON;;;;;N;;;;; 1F807;DOWNWARDS ARROW WITH MEDIUM TRIANGLE ARROWHEAD;So;0;ON;;;;;N;;;;; 1F808;LEFTWARDS ARROW WITH LARGE TRIANGLE ARROWHEAD;So;0;ON;;;;;N;;;;; 1F809;UPWARDS ARROW WITH LARGE TRIANGLE ARROWHEAD;So;0;ON;;;;;N;;;;; 1F80A;RIGHTWARDS ARROW WITH LARGE TRIANGLE ARROWHEAD;So;0;ON;;;;;N;;;;; 1F80B;DOWNWARDS ARROW WITH LARGE TRIANGLE ARROWHEAD;So;0;ON;;;;;N;;;;; 1F810;LEFTWARDS ARROW WITH SMALL EQUILATERAL ARROWHEAD;So;0;ON;;;;;N;;;;; 1F811;UPWARDS ARROW WITH SMALL EQUILATERAL ARROWHEAD;So;0;ON;;;;;N;;;;; 1F812;RIGHTWARDS ARROW WITH SMALL EQUILATERAL ARROWHEAD;So;0;ON;;;;;N;;;;; 1F813;DOWNWARDS ARROW WITH SMALL EQUILATERAL ARROWHEAD;So;0;ON;;;;;N;;;;; 1F814;LEFTWARDS ARROW WITH EQUILATERAL ARROWHEAD;So;0;ON;;;;;N;;;;; 1F815;UPWARDS ARROW WITH EQUILATERAL ARROWHEAD;So;0;ON;;;;;N;;;;; 1F816;RIGHTWARDS ARROW WITH EQUILATERAL ARROWHEAD;So;0;ON;;;;;N;;;;; 1F817;DOWNWARDS ARROW WITH EQUILATERAL ARROWHEAD;So;0;ON;;;;;N;;;;; 1F818;HEAVY LEFTWARDS ARROW WITH EQUILATERAL ARROWHEAD;So;0;ON;;;;;N;;;;; 1F819;HEAVY UPWARDS ARROW WITH EQUILATERAL ARROWHEAD;So;0;ON;;;;;N;;;;; 1F81A;HEAVY RIGHTWARDS ARROW WITH EQUILATERAL ARROWHEAD;So;0;ON;;;;;N;;;;; 1F81B;HEAVY DOWNWARDS ARROW WITH EQUILATERAL ARROWHEAD;So;0;ON;;;;;N;;;;; 1F81C;HEAVY LEFTWARDS ARROW WITH LARGE EQUILATERAL ARROWHEAD;So;0;ON;;;;;N;;;;; 1F81D;HEAVY UPWARDS ARROW WITH LARGE EQUILATERAL ARROWHEAD;So;0;ON;;;;;N;;;;; 1F81E;HEAVY RIGHTWARDS ARROW WITH LARGE EQUILATERAL ARROWHEAD;So;0;ON;;;;;N;;;;; 1F81F;HEAVY DOWNWARDS ARROW WITH LARGE EQUILATERAL ARROWHEAD;So;0;ON;;;;;N;;;;; 1F820;LEFTWARDS TRIANGLE-HEADED ARROW WITH NARROW SHAFT;So;0;ON;;;;;N;;;;; 1F821;UPWARDS TRIANGLE-HEADED ARROW WITH NARROW SHAFT;So;0;ON;;;;;N;;;;; 1F822;RIGHTWARDS TRIANGLE-HEADED ARROW WITH NARROW SHAFT;So;0;ON;;;;;N;;;;; 1F823;DOWNWARDS TRIANGLE-HEADED ARROW WITH NARROW SHAFT;So;0;ON;;;;;N;;;;; 1F824;LEFTWARDS TRIANGLE-HEADED ARROW WITH MEDIUM SHAFT;So;0;ON;;;;;N;;;;; 1F825;UPWARDS TRIANGLE-HEADED ARROW WITH MEDIUM SHAFT;So;0;ON;;;;;N;;;;; 1F826;RIGHTWARDS TRIANGLE-HEADED ARROW WITH MEDIUM SHAFT;So;0;ON;;;;;N;;;;; 1F827;DOWNWARDS TRIANGLE-HEADED ARROW WITH MEDIUM SHAFT;So;0;ON;;;;;N;;;;; 1F828;LEFTWARDS TRIANGLE-HEADED ARROW WITH BOLD SHAFT;So;0;ON;;;;;N;;;;; 1F829;UPWARDS TRIANGLE-HEADED ARROW WITH BOLD SHAFT;So;0;ON;;;;;N;;;;; 1F82A;RIGHTWARDS TRIANGLE-HEADED ARROW WITH BOLD SHAFT;So;0;ON;;;;;N;;;;; 1F82B;DOWNWARDS TRIANGLE-HEADED ARROW WITH BOLD SHAFT;So;0;ON;;;;;N;;;;; 1F82C;LEFTWARDS TRIANGLE-HEADED ARROW WITH HEAVY SHAFT;So;0;ON;;;;;N;;;;; 1F82D;UPWARDS TRIANGLE-HEADED ARROW WITH HEAVY SHAFT;So;0;ON;;;;;N;;;;; 1F82E;RIGHTWARDS TRIANGLE-HEADED ARROW WITH HEAVY SHAFT;So;0;ON;;;;;N;;;;; 1F82F;DOWNWARDS TRIANGLE-HEADED ARROW WITH HEAVY SHAFT;So;0;ON;;;;;N;;;;; 1F830;LEFTWARDS TRIANGLE-HEADED ARROW WITH VERY HEAVY SHAFT;So;0;ON;;;;;N;;;;; 1F831;UPWARDS TRIANGLE-HEADED ARROW WITH VERY HEAVY SHAFT;So;0;ON;;;;;N;;;;; 1F832;RIGHTWARDS TRIANGLE-HEADED ARROW WITH VERY HEAVY SHAFT;So;0;ON;;;;;N;;;;; 1F833;DOWNWARDS TRIANGLE-HEADED ARROW WITH VERY HEAVY SHAFT;So;0;ON;;;;;N;;;;; 1F834;LEFTWARDS FINGER-POST ARROW;So;0;ON;;;;;N;;;;; 1F835;UPWARDS FINGER-POST ARROW;So;0;ON;;;;;N;;;;; 1F836;RIGHTWARDS FINGER-POST ARROW;So;0;ON;;;;;N;;;;; 1F837;DOWNWARDS FINGER-POST ARROW;So;0;ON;;;;;N;;;;; 1F838;LEFTWARDS SQUARED ARROW;So;0;ON;;;;;N;;;;; 1F839;UPWARDS SQUARED ARROW;So;0;ON;;;;;N;;;;; 1F83A;RIGHTWARDS SQUARED ARROW;So;0;ON;;;;;N;;;;; 1F83B;DOWNWARDS SQUARED ARROW;So;0;ON;;;;;N;;;;; 1F83C;LEFTWARDS COMPRESSED ARROW;So;0;ON;;;;;N;;;;; 1F83D;UPWARDS COMPRESSED ARROW;So;0;ON;;;;;N;;;;; 1F83E;RIGHTWARDS COMPRESSED ARROW;So;0;ON;;;;;N;;;;; 1F83F;DOWNWARDS COMPRESSED ARROW;So;0;ON;;;;;N;;;;; 1F840;LEFTWARDS HEAVY COMPRESSED ARROW;So;0;ON;;;;;N;;;;; 1F841;UPWARDS HEAVY COMPRESSED ARROW;So;0;ON;;;;;N;;;;; 1F842;RIGHTWARDS HEAVY COMPRESSED ARROW;So;0;ON;;;;;N;;;;; 1F843;DOWNWARDS HEAVY COMPRESSED ARROW;So;0;ON;;;;;N;;;;; 1F844;LEFTWARDS HEAVY ARROW;So;0;ON;;;;;N;;;;; 1F845;UPWARDS HEAVY ARROW;So;0;ON;;;;;N;;;;; 1F846;RIGHTWARDS HEAVY ARROW;So;0;ON;;;;;N;;;;; 1F847;DOWNWARDS HEAVY ARROW;So;0;ON;;;;;N;;;;; 1F850;LEFTWARDS SANS-SERIF ARROW;So;0;ON;;;;;N;;;;; 1F851;UPWARDS SANS-SERIF ARROW;So;0;ON;;;;;N;;;;; 1F852;RIGHTWARDS SANS-SERIF ARROW;So;0;ON;;;;;N;;;;; 1F853;DOWNWARDS SANS-SERIF ARROW;So;0;ON;;;;;N;;;;; 1F854;NORTH WEST SANS-SERIF ARROW;So;0;ON;;;;;N;;;;; 1F855;NORTH EAST SANS-SERIF ARROW;So;0;ON;;;;;N;;;;; 1F856;SOUTH EAST SANS-SERIF ARROW;So;0;ON;;;;;N;;;;; 1F857;SOUTH WEST SANS-SERIF ARROW;So;0;ON;;;;;N;;;;; 1F858;LEFT RIGHT SANS-SERIF ARROW;So;0;ON;;;;;N;;;;; 1F859;UP DOWN SANS-SERIF ARROW;So;0;ON;;;;;N;;;;; 1F860;WIDE-HEADED LEFTWARDS LIGHT BARB ARROW;So;0;ON;;;;;N;;;;; 1F861;WIDE-HEADED UPWARDS LIGHT BARB ARROW;So;0;ON;;;;;N;;;;; 1F862;WIDE-HEADED RIGHTWARDS LIGHT BARB ARROW;So;0;ON;;;;;N;;;;; 1F863;WIDE-HEADED DOWNWARDS LIGHT BARB ARROW;So;0;ON;;;;;N;;;;; 1F864;WIDE-HEADED NORTH WEST LIGHT BARB ARROW;So;0;ON;;;;;N;;;;; 1F865;WIDE-HEADED NORTH EAST LIGHT BARB ARROW;So;0;ON;;;;;N;;;;; 1F866;WIDE-HEADED SOUTH EAST LIGHT BARB ARROW;So;0;ON;;;;;N;;;;; 1F867;WIDE-HEADED SOUTH WEST LIGHT BARB ARROW;So;0;ON;;;;;N;;;;; 1F868;WIDE-HEADED LEFTWARDS BARB ARROW;So;0;ON;;;;;N;;;;; 1F869;WIDE-HEADED UPWARDS BARB ARROW;So;0;ON;;;;;N;;;;; 1F86A;WIDE-HEADED RIGHTWARDS BARB ARROW;So;0;ON;;;;;N;;;;; 1F86B;WIDE-HEADED DOWNWARDS BARB ARROW;So;0;ON;;;;;N;;;;; 1F86C;WIDE-HEADED NORTH WEST BARB ARROW;So;0;ON;;;;;N;;;;; 1F86D;WIDE-HEADED NORTH EAST BARB ARROW;So;0;ON;;;;;N;;;;; 1F86E;WIDE-HEADED SOUTH EAST BARB ARROW;So;0;ON;;;;;N;;;;; 1F86F;WIDE-HEADED SOUTH WEST BARB ARROW;So;0;ON;;;;;N;;;;; 1F870;WIDE-HEADED LEFTWARDS MEDIUM BARB ARROW;So;0;ON;;;;;N;;;;; 1F871;WIDE-HEADED UPWARDS MEDIUM BARB ARROW;So;0;ON;;;;;N;;;;; 1F872;WIDE-HEADED RIGHTWARDS MEDIUM BARB ARROW;So;0;ON;;;;;N;;;;; 1F873;WIDE-HEADED DOWNWARDS MEDIUM BARB ARROW;So;0;ON;;;;;N;;;;; 1F874;WIDE-HEADED NORTH WEST MEDIUM BARB ARROW;So;0;ON;;;;;N;;;;; 1F875;WIDE-HEADED NORTH EAST MEDIUM BARB ARROW;So;0;ON;;;;;N;;;;; 1F876;WIDE-HEADED SOUTH EAST MEDIUM BARB ARROW;So;0;ON;;;;;N;;;;; 1F877;WIDE-HEADED SOUTH WEST MEDIUM BARB ARROW;So;0;ON;;;;;N;;;;; 1F878;WIDE-HEADED LEFTWARDS HEAVY BARB ARROW;So;0;ON;;;;;N;;;;; 1F879;WIDE-HEADED UPWARDS HEAVY BARB ARROW;So;0;ON;;;;;N;;;;; 1F87A;WIDE-HEADED RIGHTWARDS HEAVY BARB ARROW;So;0;ON;;;;;N;;;;; 1F87B;WIDE-HEADED DOWNWARDS HEAVY BARB ARROW;So;0;ON;;;;;N;;;;; 1F87C;WIDE-HEADED NORTH WEST HEAVY BARB ARROW;So;0;ON;;;;;N;;;;; 1F87D;WIDE-HEADED NORTH EAST HEAVY BARB ARROW;So;0;ON;;;;;N;;;;; 1F87E;WIDE-HEADED SOUTH EAST HEAVY BARB ARROW;So;0;ON;;;;;N;;;;; 1F87F;WIDE-HEADED SOUTH WEST HEAVY BARB ARROW;So;0;ON;;;;;N;;;;; 1F880;WIDE-HEADED LEFTWARDS VERY HEAVY BARB ARROW;So;0;ON;;;;;N;;;;; 1F881;WIDE-HEADED UPWARDS VERY HEAVY BARB ARROW;So;0;ON;;;;;N;;;;; 1F882;WIDE-HEADED RIGHTWARDS VERY HEAVY BARB ARROW;So;0;ON;;;;;N;;;;; 1F883;WIDE-HEADED DOWNWARDS VERY HEAVY BARB ARROW;So;0;ON;;;;;N;;;;; 1F884;WIDE-HEADED NORTH WEST VERY HEAVY BARB ARROW;So;0;ON;;;;;N;;;;; 1F885;WIDE-HEADED NORTH EAST VERY HEAVY BARB ARROW;So;0;ON;;;;;N;;;;; 1F886;WIDE-HEADED SOUTH EAST VERY HEAVY BARB ARROW;So;0;ON;;;;;N;;;;; 1F887;WIDE-HEADED SOUTH WEST VERY HEAVY BARB ARROW;So;0;ON;;;;;N;;;;; 1F890;LEFTWARDS TRIANGLE ARROWHEAD;So;0;ON;;;;;N;;;;; 1F891;UPWARDS TRIANGLE ARROWHEAD;So;0;ON;;;;;N;;;;; 1F892;RIGHTWARDS TRIANGLE ARROWHEAD;So;0;ON;;;;;N;;;;; 1F893;DOWNWARDS TRIANGLE ARROWHEAD;So;0;ON;;;;;N;;;;; 1F894;LEFTWARDS WHITE ARROW WITHIN TRIANGLE ARROWHEAD;So;0;ON;;;;;N;;;;; 1F895;UPWARDS WHITE ARROW WITHIN TRIANGLE ARROWHEAD;So;0;ON;;;;;N;;;;; 1F896;RIGHTWARDS WHITE ARROW WITHIN TRIANGLE ARROWHEAD;So;0;ON;;;;;N;;;;; 1F897;DOWNWARDS WHITE ARROW WITHIN TRIANGLE ARROWHEAD;So;0;ON;;;;;N;;;;; 1F898;LEFTWARDS ARROW WITH NOTCHED TAIL;So;0;ON;;;;;N;;;;; 1F899;UPWARDS ARROW WITH NOTCHED TAIL;So;0;ON;;;;;N;;;;; 1F89A;RIGHTWARDS ARROW WITH NOTCHED TAIL;So;0;ON;;;;;N;;;;; 1F89B;DOWNWARDS ARROW WITH NOTCHED TAIL;So;0;ON;;;;;N;;;;; 1F89C;HEAVY ARROW SHAFT WIDTH ONE;So;0;ON;;;;;N;;;;; 1F89D;HEAVY ARROW SHAFT WIDTH TWO THIRDS;So;0;ON;;;;;N;;;;; 1F89E;HEAVY ARROW SHAFT WIDTH ONE HALF;So;0;ON;;;;;N;;;;; 1F89F;HEAVY ARROW SHAFT WIDTH ONE THIRD;So;0;ON;;;;;N;;;;; 1F8A0;LEFTWARDS BOTTOM-SHADED WHITE ARROW;So;0;ON;;;;;N;;;;; 1F8A1;RIGHTWARDS BOTTOM SHADED WHITE ARROW;So;0;ON;;;;;N;;;;; 1F8A2;LEFTWARDS TOP SHADED WHITE ARROW;So;0;ON;;;;;N;;;;; 1F8A3;RIGHTWARDS TOP SHADED WHITE ARROW;So;0;ON;;;;;N;;;;; 1F8A4;LEFTWARDS LEFT-SHADED WHITE ARROW;So;0;ON;;;;;N;;;;; 1F8A5;RIGHTWARDS RIGHT-SHADED WHITE ARROW;So;0;ON;;;;;N;;;;; 1F8A6;LEFTWARDS RIGHT-SHADED WHITE ARROW;So;0;ON;;;;;N;;;;; 1F8A7;RIGHTWARDS LEFT-SHADED WHITE ARROW;So;0;ON;;;;;N;;;;; 1F8A8;LEFTWARDS BACK-TILTED SHADOWED WHITE ARROW;So;0;ON;;;;;N;;;;; 1F8A9;RIGHTWARDS BACK-TILTED SHADOWED WHITE ARROW;So;0;ON;;;;;N;;;;; 1F8AA;LEFTWARDS FRONT-TILTED SHADOWED WHITE ARROW;So;0;ON;;;;;N;;;;; 1F8AB;RIGHTWARDS FRONT-TILTED SHADOWED WHITE ARROW;So;0;ON;;;;;N;;;;; 1F8AC;WHITE ARROW SHAFT WIDTH ONE;So;0;ON;;;;;N;;;;; 1F8AD;WHITE ARROW SHAFT WIDTH TWO THIRDS;So;0;ON;;;;;N;;;;; 20000;;Lo;0;L;;;;;N;;;;; 2A6D6;;Lo;0;L;;;;;N;;;;; 2A700;;Lo;0;L;;;;;N;;;;; 2B734;;Lo;0;L;;;;;N;;;;; 2B740;;Lo;0;L;;;;;N;;;;; 2B81D;;Lo;0;L;;;;;N;;;;; 2F800;CJK COMPATIBILITY IDEOGRAPH-2F800;Lo;0;L;4E3D;;;;N;;;;; 2F801;CJK COMPATIBILITY IDEOGRAPH-2F801;Lo;0;L;4E38;;;;N;;;;; 2F802;CJK COMPATIBILITY IDEOGRAPH-2F802;Lo;0;L;4E41;;;;N;;;;; 2F803;CJK COMPATIBILITY IDEOGRAPH-2F803;Lo;0;L;20122;;;;N;;;;; 2F804;CJK COMPATIBILITY IDEOGRAPH-2F804;Lo;0;L;4F60;;;;N;;;;; 2F805;CJK COMPATIBILITY IDEOGRAPH-2F805;Lo;0;L;4FAE;;;;N;;;;; 2F806;CJK COMPATIBILITY IDEOGRAPH-2F806;Lo;0;L;4FBB;;;;N;;;;; 2F807;CJK COMPATIBILITY IDEOGRAPH-2F807;Lo;0;L;5002;;;;N;;;;; 2F808;CJK COMPATIBILITY IDEOGRAPH-2F808;Lo;0;L;507A;;;;N;;;;; 2F809;CJK COMPATIBILITY IDEOGRAPH-2F809;Lo;0;L;5099;;;;N;;;;; 2F80A;CJK COMPATIBILITY IDEOGRAPH-2F80A;Lo;0;L;50E7;;;;N;;;;; 2F80B;CJK COMPATIBILITY IDEOGRAPH-2F80B;Lo;0;L;50CF;;;;N;;;;; 2F80C;CJK COMPATIBILITY IDEOGRAPH-2F80C;Lo;0;L;349E;;;;N;;;;; 2F80D;CJK COMPATIBILITY IDEOGRAPH-2F80D;Lo;0;L;2063A;;;;N;;;;; 2F80E;CJK COMPATIBILITY IDEOGRAPH-2F80E;Lo;0;L;514D;;;;N;;;;; 2F80F;CJK COMPATIBILITY IDEOGRAPH-2F80F;Lo;0;L;5154;;;;N;;;;; 2F810;CJK COMPATIBILITY IDEOGRAPH-2F810;Lo;0;L;5164;;;;N;;;;; 2F811;CJK COMPATIBILITY IDEOGRAPH-2F811;Lo;0;L;5177;;;;N;;;;; 2F812;CJK COMPATIBILITY IDEOGRAPH-2F812;Lo;0;L;2051C;;;;N;;;;; 2F813;CJK COMPATIBILITY IDEOGRAPH-2F813;Lo;0;L;34B9;;;;N;;;;; 2F814;CJK COMPATIBILITY IDEOGRAPH-2F814;Lo;0;L;5167;;;;N;;;;; 2F815;CJK COMPATIBILITY IDEOGRAPH-2F815;Lo;0;L;518D;;;;N;;;;; 2F816;CJK COMPATIBILITY IDEOGRAPH-2F816;Lo;0;L;2054B;;;;N;;;;; 2F817;CJK COMPATIBILITY IDEOGRAPH-2F817;Lo;0;L;5197;;;;N;;;;; 2F818;CJK COMPATIBILITY IDEOGRAPH-2F818;Lo;0;L;51A4;;;;N;;;;; 2F819;CJK COMPATIBILITY IDEOGRAPH-2F819;Lo;0;L;4ECC;;;;N;;;;; 2F81A;CJK COMPATIBILITY IDEOGRAPH-2F81A;Lo;0;L;51AC;;;;N;;;;; 2F81B;CJK COMPATIBILITY IDEOGRAPH-2F81B;Lo;0;L;51B5;;;;N;;;;; 2F81C;CJK COMPATIBILITY IDEOGRAPH-2F81C;Lo;0;L;291DF;;;;N;;;;; 2F81D;CJK COMPATIBILITY IDEOGRAPH-2F81D;Lo;0;L;51F5;;;;N;;;;; 2F81E;CJK COMPATIBILITY IDEOGRAPH-2F81E;Lo;0;L;5203;;;;N;;;;; 2F81F;CJK COMPATIBILITY IDEOGRAPH-2F81F;Lo;0;L;34DF;;;;N;;;;; 2F820;CJK COMPATIBILITY IDEOGRAPH-2F820;Lo;0;L;523B;;;;N;;;;; 2F821;CJK COMPATIBILITY IDEOGRAPH-2F821;Lo;0;L;5246;;;;N;;;;; 2F822;CJK COMPATIBILITY IDEOGRAPH-2F822;Lo;0;L;5272;;;;N;;;;; 2F823;CJK COMPATIBILITY IDEOGRAPH-2F823;Lo;0;L;5277;;;;N;;;;; 2F824;CJK COMPATIBILITY IDEOGRAPH-2F824;Lo;0;L;3515;;;;N;;;;; 2F825;CJK COMPATIBILITY IDEOGRAPH-2F825;Lo;0;L;52C7;;;;N;;;;; 2F826;CJK COMPATIBILITY IDEOGRAPH-2F826;Lo;0;L;52C9;;;;N;;;;; 2F827;CJK COMPATIBILITY IDEOGRAPH-2F827;Lo;0;L;52E4;;;;N;;;;; 2F828;CJK COMPATIBILITY IDEOGRAPH-2F828;Lo;0;L;52FA;;;;N;;;;; 2F829;CJK COMPATIBILITY IDEOGRAPH-2F829;Lo;0;L;5305;;;;N;;;;; 2F82A;CJK COMPATIBILITY IDEOGRAPH-2F82A;Lo;0;L;5306;;;;N;;;;; 2F82B;CJK COMPATIBILITY IDEOGRAPH-2F82B;Lo;0;L;5317;;;;N;;;;; 2F82C;CJK COMPATIBILITY IDEOGRAPH-2F82C;Lo;0;L;5349;;;;N;;;;; 2F82D;CJK COMPATIBILITY IDEOGRAPH-2F82D;Lo;0;L;5351;;;;N;;;;; 2F82E;CJK COMPATIBILITY IDEOGRAPH-2F82E;Lo;0;L;535A;;;;N;;;;; 2F82F;CJK COMPATIBILITY IDEOGRAPH-2F82F;Lo;0;L;5373;;;;N;;;;; 2F830;CJK COMPATIBILITY IDEOGRAPH-2F830;Lo;0;L;537D;;;;N;;;;; 2F831;CJK COMPATIBILITY IDEOGRAPH-2F831;Lo;0;L;537F;;;;N;;;;; 2F832;CJK COMPATIBILITY IDEOGRAPH-2F832;Lo;0;L;537F;;;;N;;;;; 2F833;CJK COMPATIBILITY IDEOGRAPH-2F833;Lo;0;L;537F;;;;N;;;;; 2F834;CJK COMPATIBILITY IDEOGRAPH-2F834;Lo;0;L;20A2C;;;;N;;;;; 2F835;CJK COMPATIBILITY IDEOGRAPH-2F835;Lo;0;L;7070;;;;N;;;;; 2F836;CJK COMPATIBILITY IDEOGRAPH-2F836;Lo;0;L;53CA;;;;N;;;;; 2F837;CJK COMPATIBILITY IDEOGRAPH-2F837;Lo;0;L;53DF;;;;N;;;;; 2F838;CJK COMPATIBILITY IDEOGRAPH-2F838;Lo;0;L;20B63;;;;N;;;;; 2F839;CJK COMPATIBILITY IDEOGRAPH-2F839;Lo;0;L;53EB;;;;N;;;;; 2F83A;CJK COMPATIBILITY IDEOGRAPH-2F83A;Lo;0;L;53F1;;;;N;;;;; 2F83B;CJK COMPATIBILITY IDEOGRAPH-2F83B;Lo;0;L;5406;;;;N;;;;; 2F83C;CJK COMPATIBILITY IDEOGRAPH-2F83C;Lo;0;L;549E;;;;N;;;;; 2F83D;CJK COMPATIBILITY IDEOGRAPH-2F83D;Lo;0;L;5438;;;;N;;;;; 2F83E;CJK COMPATIBILITY IDEOGRAPH-2F83E;Lo;0;L;5448;;;;N;;;;; 2F83F;CJK COMPATIBILITY IDEOGRAPH-2F83F;Lo;0;L;5468;;;;N;;;;; 2F840;CJK COMPATIBILITY IDEOGRAPH-2F840;Lo;0;L;54A2;;;;N;;;;; 2F841;CJK COMPATIBILITY IDEOGRAPH-2F841;Lo;0;L;54F6;;;;N;;;;; 2F842;CJK COMPATIBILITY IDEOGRAPH-2F842;Lo;0;L;5510;;;;N;;;;; 2F843;CJK COMPATIBILITY IDEOGRAPH-2F843;Lo;0;L;5553;;;;N;;;;; 2F844;CJK COMPATIBILITY IDEOGRAPH-2F844;Lo;0;L;5563;;;;N;;;;; 2F845;CJK COMPATIBILITY IDEOGRAPH-2F845;Lo;0;L;5584;;;;N;;;;; 2F846;CJK COMPATIBILITY IDEOGRAPH-2F846;Lo;0;L;5584;;;;N;;;;; 2F847;CJK COMPATIBILITY IDEOGRAPH-2F847;Lo;0;L;5599;;;;N;;;;; 2F848;CJK COMPATIBILITY IDEOGRAPH-2F848;Lo;0;L;55AB;;;;N;;;;; 2F849;CJK COMPATIBILITY IDEOGRAPH-2F849;Lo;0;L;55B3;;;;N;;;;; 2F84A;CJK COMPATIBILITY IDEOGRAPH-2F84A;Lo;0;L;55C2;;;;N;;;;; 2F84B;CJK COMPATIBILITY IDEOGRAPH-2F84B;Lo;0;L;5716;;;;N;;;;; 2F84C;CJK COMPATIBILITY IDEOGRAPH-2F84C;Lo;0;L;5606;;;;N;;;;; 2F84D;CJK COMPATIBILITY IDEOGRAPH-2F84D;Lo;0;L;5717;;;;N;;;;; 2F84E;CJK COMPATIBILITY IDEOGRAPH-2F84E;Lo;0;L;5651;;;;N;;;;; 2F84F;CJK COMPATIBILITY IDEOGRAPH-2F84F;Lo;0;L;5674;;;;N;;;;; 2F850;CJK COMPATIBILITY IDEOGRAPH-2F850;Lo;0;L;5207;;;;N;;;;; 2F851;CJK COMPATIBILITY IDEOGRAPH-2F851;Lo;0;L;58EE;;;;N;;;;; 2F852;CJK COMPATIBILITY IDEOGRAPH-2F852;Lo;0;L;57CE;;;;N;;;;; 2F853;CJK COMPATIBILITY IDEOGRAPH-2F853;Lo;0;L;57F4;;;;N;;;;; 2F854;CJK COMPATIBILITY IDEOGRAPH-2F854;Lo;0;L;580D;;;;N;;;;; 2F855;CJK COMPATIBILITY IDEOGRAPH-2F855;Lo;0;L;578B;;;;N;;;;; 2F856;CJK COMPATIBILITY IDEOGRAPH-2F856;Lo;0;L;5832;;;;N;;;;; 2F857;CJK COMPATIBILITY IDEOGRAPH-2F857;Lo;0;L;5831;;;;N;;;;; 2F858;CJK COMPATIBILITY IDEOGRAPH-2F858;Lo;0;L;58AC;;;;N;;;;; 2F859;CJK COMPATIBILITY IDEOGRAPH-2F859;Lo;0;L;214E4;;;;N;;;;; 2F85A;CJK COMPATIBILITY IDEOGRAPH-2F85A;Lo;0;L;58F2;;;;N;;;;; 2F85B;CJK COMPATIBILITY IDEOGRAPH-2F85B;Lo;0;L;58F7;;;;N;;;;; 2F85C;CJK COMPATIBILITY IDEOGRAPH-2F85C;Lo;0;L;5906;;;;N;;;;; 2F85D;CJK COMPATIBILITY IDEOGRAPH-2F85D;Lo;0;L;591A;;;;N;;;;; 2F85E;CJK COMPATIBILITY IDEOGRAPH-2F85E;Lo;0;L;5922;;;;N;;;;; 2F85F;CJK COMPATIBILITY IDEOGRAPH-2F85F;Lo;0;L;5962;;;;N;;;;; 2F860;CJK COMPATIBILITY IDEOGRAPH-2F860;Lo;0;L;216A8;;;;N;;;;; 2F861;CJK COMPATIBILITY IDEOGRAPH-2F861;Lo;0;L;216EA;;;;N;;;;; 2F862;CJK COMPATIBILITY IDEOGRAPH-2F862;Lo;0;L;59EC;;;;N;;;;; 2F863;CJK COMPATIBILITY IDEOGRAPH-2F863;Lo;0;L;5A1B;;;;N;;;;; 2F864;CJK COMPATIBILITY IDEOGRAPH-2F864;Lo;0;L;5A27;;;;N;;;;; 2F865;CJK COMPATIBILITY IDEOGRAPH-2F865;Lo;0;L;59D8;;;;N;;;;; 2F866;CJK COMPATIBILITY IDEOGRAPH-2F866;Lo;0;L;5A66;;;;N;;;;; 2F867;CJK COMPATIBILITY IDEOGRAPH-2F867;Lo;0;L;36EE;;;;N;;;;; 2F868;CJK COMPATIBILITY IDEOGRAPH-2F868;Lo;0;L;36FC;;;;N;;;;; 2F869;CJK COMPATIBILITY IDEOGRAPH-2F869;Lo;0;L;5B08;;;;N;;;;; 2F86A;CJK COMPATIBILITY IDEOGRAPH-2F86A;Lo;0;L;5B3E;;;;N;;;;; 2F86B;CJK COMPATIBILITY IDEOGRAPH-2F86B;Lo;0;L;5B3E;;;;N;;;;; 2F86C;CJK COMPATIBILITY IDEOGRAPH-2F86C;Lo;0;L;219C8;;;;N;;;;; 2F86D;CJK COMPATIBILITY IDEOGRAPH-2F86D;Lo;0;L;5BC3;;;;N;;;;; 2F86E;CJK COMPATIBILITY IDEOGRAPH-2F86E;Lo;0;L;5BD8;;;;N;;;;; 2F86F;CJK COMPATIBILITY IDEOGRAPH-2F86F;Lo;0;L;5BE7;;;;N;;;;; 2F870;CJK COMPATIBILITY IDEOGRAPH-2F870;Lo;0;L;5BF3;;;;N;;;;; 2F871;CJK COMPATIBILITY IDEOGRAPH-2F871;Lo;0;L;21B18;;;;N;;;;; 2F872;CJK COMPATIBILITY IDEOGRAPH-2F872;Lo;0;L;5BFF;;;;N;;;;; 2F873;CJK COMPATIBILITY IDEOGRAPH-2F873;Lo;0;L;5C06;;;;N;;;;; 2F874;CJK COMPATIBILITY IDEOGRAPH-2F874;Lo;0;L;5F53;;;;N;;;;; 2F875;CJK COMPATIBILITY IDEOGRAPH-2F875;Lo;0;L;5C22;;;;N;;;;; 2F876;CJK COMPATIBILITY IDEOGRAPH-2F876;Lo;0;L;3781;;;;N;;;;; 2F877;CJK COMPATIBILITY IDEOGRAPH-2F877;Lo;0;L;5C60;;;;N;;;;; 2F878;CJK COMPATIBILITY IDEOGRAPH-2F878;Lo;0;L;5C6E;;;;N;;;;; 2F879;CJK COMPATIBILITY IDEOGRAPH-2F879;Lo;0;L;5CC0;;;;N;;;;; 2F87A;CJK COMPATIBILITY IDEOGRAPH-2F87A;Lo;0;L;5C8D;;;;N;;;;; 2F87B;CJK COMPATIBILITY IDEOGRAPH-2F87B;Lo;0;L;21DE4;;;;N;;;;; 2F87C;CJK COMPATIBILITY IDEOGRAPH-2F87C;Lo;0;L;5D43;;;;N;;;;; 2F87D;CJK COMPATIBILITY IDEOGRAPH-2F87D;Lo;0;L;21DE6;;;;N;;;;; 2F87E;CJK COMPATIBILITY IDEOGRAPH-2F87E;Lo;0;L;5D6E;;;;N;;;;; 2F87F;CJK COMPATIBILITY IDEOGRAPH-2F87F;Lo;0;L;5D6B;;;;N;;;;; 2F880;CJK COMPATIBILITY IDEOGRAPH-2F880;Lo;0;L;5D7C;;;;N;;;;; 2F881;CJK COMPATIBILITY IDEOGRAPH-2F881;Lo;0;L;5DE1;;;;N;;;;; 2F882;CJK COMPATIBILITY IDEOGRAPH-2F882;Lo;0;L;5DE2;;;;N;;;;; 2F883;CJK COMPATIBILITY IDEOGRAPH-2F883;Lo;0;L;382F;;;;N;;;;; 2F884;CJK COMPATIBILITY IDEOGRAPH-2F884;Lo;0;L;5DFD;;;;N;;;;; 2F885;CJK COMPATIBILITY IDEOGRAPH-2F885;Lo;0;L;5E28;;;;N;;;;; 2F886;CJK COMPATIBILITY IDEOGRAPH-2F886;Lo;0;L;5E3D;;;;N;;;;; 2F887;CJK COMPATIBILITY IDEOGRAPH-2F887;Lo;0;L;5E69;;;;N;;;;; 2F888;CJK COMPATIBILITY IDEOGRAPH-2F888;Lo;0;L;3862;;;;N;;;;; 2F889;CJK COMPATIBILITY IDEOGRAPH-2F889;Lo;0;L;22183;;;;N;;;;; 2F88A;CJK COMPATIBILITY IDEOGRAPH-2F88A;Lo;0;L;387C;;;;N;;;;; 2F88B;CJK COMPATIBILITY IDEOGRAPH-2F88B;Lo;0;L;5EB0;;;;N;;;;; 2F88C;CJK COMPATIBILITY IDEOGRAPH-2F88C;Lo;0;L;5EB3;;;;N;;;;; 2F88D;CJK COMPATIBILITY IDEOGRAPH-2F88D;Lo;0;L;5EB6;;;;N;;;;; 2F88E;CJK COMPATIBILITY IDEOGRAPH-2F88E;Lo;0;L;5ECA;;;;N;;;;; 2F88F;CJK COMPATIBILITY IDEOGRAPH-2F88F;Lo;0;L;2A392;;;;N;;;;; 2F890;CJK COMPATIBILITY IDEOGRAPH-2F890;Lo;0;L;5EFE;;;9;N;;;;; 2F891;CJK COMPATIBILITY IDEOGRAPH-2F891;Lo;0;L;22331;;;;N;;;;; 2F892;CJK COMPATIBILITY IDEOGRAPH-2F892;Lo;0;L;22331;;;;N;;;;; 2F893;CJK COMPATIBILITY IDEOGRAPH-2F893;Lo;0;L;8201;;;;N;;;;; 2F894;CJK COMPATIBILITY IDEOGRAPH-2F894;Lo;0;L;5F22;;;;N;;;;; 2F895;CJK COMPATIBILITY IDEOGRAPH-2F895;Lo;0;L;5F22;;;;N;;;;; 2F896;CJK COMPATIBILITY IDEOGRAPH-2F896;Lo;0;L;38C7;;;;N;;;;; 2F897;CJK COMPATIBILITY IDEOGRAPH-2F897;Lo;0;L;232B8;;;;N;;;;; 2F898;CJK COMPATIBILITY IDEOGRAPH-2F898;Lo;0;L;261DA;;;;N;;;;; 2F899;CJK COMPATIBILITY IDEOGRAPH-2F899;Lo;0;L;5F62;;;;N;;;;; 2F89A;CJK COMPATIBILITY IDEOGRAPH-2F89A;Lo;0;L;5F6B;;;;N;;;;; 2F89B;CJK COMPATIBILITY IDEOGRAPH-2F89B;Lo;0;L;38E3;;;;N;;;;; 2F89C;CJK COMPATIBILITY IDEOGRAPH-2F89C;Lo;0;L;5F9A;;;;N;;;;; 2F89D;CJK COMPATIBILITY IDEOGRAPH-2F89D;Lo;0;L;5FCD;;;;N;;;;; 2F89E;CJK COMPATIBILITY IDEOGRAPH-2F89E;Lo;0;L;5FD7;;;;N;;;;; 2F89F;CJK COMPATIBILITY IDEOGRAPH-2F89F;Lo;0;L;5FF9;;;;N;;;;; 2F8A0;CJK COMPATIBILITY IDEOGRAPH-2F8A0;Lo;0;L;6081;;;;N;;;;; 2F8A1;CJK COMPATIBILITY IDEOGRAPH-2F8A1;Lo;0;L;393A;;;;N;;;;; 2F8A2;CJK COMPATIBILITY IDEOGRAPH-2F8A2;Lo;0;L;391C;;;;N;;;;; 2F8A3;CJK COMPATIBILITY IDEOGRAPH-2F8A3;Lo;0;L;6094;;;;N;;;;; 2F8A4;CJK COMPATIBILITY IDEOGRAPH-2F8A4;Lo;0;L;226D4;;;;N;;;;; 2F8A5;CJK COMPATIBILITY IDEOGRAPH-2F8A5;Lo;0;L;60C7;;;;N;;;;; 2F8A6;CJK COMPATIBILITY IDEOGRAPH-2F8A6;Lo;0;L;6148;;;;N;;;;; 2F8A7;CJK COMPATIBILITY IDEOGRAPH-2F8A7;Lo;0;L;614C;;;;N;;;;; 2F8A8;CJK COMPATIBILITY IDEOGRAPH-2F8A8;Lo;0;L;614E;;;;N;;;;; 2F8A9;CJK COMPATIBILITY IDEOGRAPH-2F8A9;Lo;0;L;614C;;;;N;;;;; 2F8AA;CJK COMPATIBILITY IDEOGRAPH-2F8AA;Lo;0;L;617A;;;;N;;;;; 2F8AB;CJK COMPATIBILITY IDEOGRAPH-2F8AB;Lo;0;L;618E;;;;N;;;;; 2F8AC;CJK COMPATIBILITY IDEOGRAPH-2F8AC;Lo;0;L;61B2;;;;N;;;;; 2F8AD;CJK COMPATIBILITY IDEOGRAPH-2F8AD;Lo;0;L;61A4;;;;N;;;;; 2F8AE;CJK COMPATIBILITY IDEOGRAPH-2F8AE;Lo;0;L;61AF;;;;N;;;;; 2F8AF;CJK COMPATIBILITY IDEOGRAPH-2F8AF;Lo;0;L;61DE;;;;N;;;;; 2F8B0;CJK COMPATIBILITY IDEOGRAPH-2F8B0;Lo;0;L;61F2;;;;N;;;;; 2F8B1;CJK COMPATIBILITY IDEOGRAPH-2F8B1;Lo;0;L;61F6;;;;N;;;;; 2F8B2;CJK COMPATIBILITY IDEOGRAPH-2F8B2;Lo;0;L;6210;;;;N;;;;; 2F8B3;CJK COMPATIBILITY IDEOGRAPH-2F8B3;Lo;0;L;621B;;;;N;;;;; 2F8B4;CJK COMPATIBILITY IDEOGRAPH-2F8B4;Lo;0;L;625D;;;;N;;;;; 2F8B5;CJK COMPATIBILITY IDEOGRAPH-2F8B5;Lo;0;L;62B1;;;;N;;;;; 2F8B6;CJK COMPATIBILITY IDEOGRAPH-2F8B6;Lo;0;L;62D4;;;;N;;;;; 2F8B7;CJK COMPATIBILITY IDEOGRAPH-2F8B7;Lo;0;L;6350;;;;N;;;;; 2F8B8;CJK COMPATIBILITY IDEOGRAPH-2F8B8;Lo;0;L;22B0C;;;;N;;;;; 2F8B9;CJK COMPATIBILITY IDEOGRAPH-2F8B9;Lo;0;L;633D;;;;N;;;;; 2F8BA;CJK COMPATIBILITY IDEOGRAPH-2F8BA;Lo;0;L;62FC;;;;N;;;;; 2F8BB;CJK COMPATIBILITY IDEOGRAPH-2F8BB;Lo;0;L;6368;;;;N;;;;; 2F8BC;CJK COMPATIBILITY IDEOGRAPH-2F8BC;Lo;0;L;6383;;;;N;;;;; 2F8BD;CJK COMPATIBILITY IDEOGRAPH-2F8BD;Lo;0;L;63E4;;;;N;;;;; 2F8BE;CJK COMPATIBILITY IDEOGRAPH-2F8BE;Lo;0;L;22BF1;;;;N;;;;; 2F8BF;CJK COMPATIBILITY IDEOGRAPH-2F8BF;Lo;0;L;6422;;;;N;;;;; 2F8C0;CJK COMPATIBILITY IDEOGRAPH-2F8C0;Lo;0;L;63C5;;;;N;;;;; 2F8C1;CJK COMPATIBILITY IDEOGRAPH-2F8C1;Lo;0;L;63A9;;;;N;;;;; 2F8C2;CJK COMPATIBILITY IDEOGRAPH-2F8C2;Lo;0;L;3A2E;;;;N;;;;; 2F8C3;CJK COMPATIBILITY IDEOGRAPH-2F8C3;Lo;0;L;6469;;;;N;;;;; 2F8C4;CJK COMPATIBILITY IDEOGRAPH-2F8C4;Lo;0;L;647E;;;;N;;;;; 2F8C5;CJK COMPATIBILITY IDEOGRAPH-2F8C5;Lo;0;L;649D;;;;N;;;;; 2F8C6;CJK COMPATIBILITY IDEOGRAPH-2F8C6;Lo;0;L;6477;;;;N;;;;; 2F8C7;CJK COMPATIBILITY IDEOGRAPH-2F8C7;Lo;0;L;3A6C;;;;N;;;;; 2F8C8;CJK COMPATIBILITY IDEOGRAPH-2F8C8;Lo;0;L;654F;;;;N;;;;; 2F8C9;CJK COMPATIBILITY IDEOGRAPH-2F8C9;Lo;0;L;656C;;;;N;;;;; 2F8CA;CJK COMPATIBILITY IDEOGRAPH-2F8CA;Lo;0;L;2300A;;;;N;;;;; 2F8CB;CJK COMPATIBILITY IDEOGRAPH-2F8CB;Lo;0;L;65E3;;;;N;;;;; 2F8CC;CJK COMPATIBILITY IDEOGRAPH-2F8CC;Lo;0;L;66F8;;;;N;;;;; 2F8CD;CJK COMPATIBILITY IDEOGRAPH-2F8CD;Lo;0;L;6649;;;;N;;;;; 2F8CE;CJK COMPATIBILITY IDEOGRAPH-2F8CE;Lo;0;L;3B19;;;;N;;;;; 2F8CF;CJK COMPATIBILITY IDEOGRAPH-2F8CF;Lo;0;L;6691;;;;N;;;;; 2F8D0;CJK COMPATIBILITY IDEOGRAPH-2F8D0;Lo;0;L;3B08;;;;N;;;;; 2F8D1;CJK COMPATIBILITY IDEOGRAPH-2F8D1;Lo;0;L;3AE4;;;;N;;;;; 2F8D2;CJK COMPATIBILITY IDEOGRAPH-2F8D2;Lo;0;L;5192;;;;N;;;;; 2F8D3;CJK COMPATIBILITY IDEOGRAPH-2F8D3;Lo;0;L;5195;;;;N;;;;; 2F8D4;CJK COMPATIBILITY IDEOGRAPH-2F8D4;Lo;0;L;6700;;;;N;;;;; 2F8D5;CJK COMPATIBILITY IDEOGRAPH-2F8D5;Lo;0;L;669C;;;;N;;;;; 2F8D6;CJK COMPATIBILITY IDEOGRAPH-2F8D6;Lo;0;L;80AD;;;;N;;;;; 2F8D7;CJK COMPATIBILITY IDEOGRAPH-2F8D7;Lo;0;L;43D9;;;;N;;;;; 2F8D8;CJK COMPATIBILITY IDEOGRAPH-2F8D8;Lo;0;L;6717;;;;N;;;;; 2F8D9;CJK COMPATIBILITY IDEOGRAPH-2F8D9;Lo;0;L;671B;;;;N;;;;; 2F8DA;CJK COMPATIBILITY IDEOGRAPH-2F8DA;Lo;0;L;6721;;;;N;;;;; 2F8DB;CJK COMPATIBILITY IDEOGRAPH-2F8DB;Lo;0;L;675E;;;;N;;;;; 2F8DC;CJK COMPATIBILITY IDEOGRAPH-2F8DC;Lo;0;L;6753;;;;N;;;;; 2F8DD;CJK COMPATIBILITY IDEOGRAPH-2F8DD;Lo;0;L;233C3;;;;N;;;;; 2F8DE;CJK COMPATIBILITY IDEOGRAPH-2F8DE;Lo;0;L;3B49;;;;N;;;;; 2F8DF;CJK COMPATIBILITY IDEOGRAPH-2F8DF;Lo;0;L;67FA;;;;N;;;;; 2F8E0;CJK COMPATIBILITY IDEOGRAPH-2F8E0;Lo;0;L;6785;;;;N;;;;; 2F8E1;CJK COMPATIBILITY IDEOGRAPH-2F8E1;Lo;0;L;6852;;;;N;;;;; 2F8E2;CJK COMPATIBILITY IDEOGRAPH-2F8E2;Lo;0;L;6885;;;;N;;;;; 2F8E3;CJK COMPATIBILITY IDEOGRAPH-2F8E3;Lo;0;L;2346D;;;;N;;;;; 2F8E4;CJK COMPATIBILITY IDEOGRAPH-2F8E4;Lo;0;L;688E;;;;N;;;;; 2F8E5;CJK COMPATIBILITY IDEOGRAPH-2F8E5;Lo;0;L;681F;;;;N;;;;; 2F8E6;CJK COMPATIBILITY IDEOGRAPH-2F8E6;Lo;0;L;6914;;;;N;;;;; 2F8E7;CJK COMPATIBILITY IDEOGRAPH-2F8E7;Lo;0;L;3B9D;;;;N;;;;; 2F8E8;CJK COMPATIBILITY IDEOGRAPH-2F8E8;Lo;0;L;6942;;;;N;;;;; 2F8E9;CJK COMPATIBILITY IDEOGRAPH-2F8E9;Lo;0;L;69A3;;;;N;;;;; 2F8EA;CJK COMPATIBILITY IDEOGRAPH-2F8EA;Lo;0;L;69EA;;;;N;;;;; 2F8EB;CJK COMPATIBILITY IDEOGRAPH-2F8EB;Lo;0;L;6AA8;;;;N;;;;; 2F8EC;CJK COMPATIBILITY IDEOGRAPH-2F8EC;Lo;0;L;236A3;;;;N;;;;; 2F8ED;CJK COMPATIBILITY IDEOGRAPH-2F8ED;Lo;0;L;6ADB;;;;N;;;;; 2F8EE;CJK COMPATIBILITY IDEOGRAPH-2F8EE;Lo;0;L;3C18;;;;N;;;;; 2F8EF;CJK COMPATIBILITY IDEOGRAPH-2F8EF;Lo;0;L;6B21;;;;N;;;;; 2F8F0;CJK COMPATIBILITY IDEOGRAPH-2F8F0;Lo;0;L;238A7;;;;N;;;;; 2F8F1;CJK COMPATIBILITY IDEOGRAPH-2F8F1;Lo;0;L;6B54;;;;N;;;;; 2F8F2;CJK COMPATIBILITY IDEOGRAPH-2F8F2;Lo;0;L;3C4E;;;;N;;;;; 2F8F3;CJK COMPATIBILITY IDEOGRAPH-2F8F3;Lo;0;L;6B72;;;;N;;;;; 2F8F4;CJK COMPATIBILITY IDEOGRAPH-2F8F4;Lo;0;L;6B9F;;;;N;;;;; 2F8F5;CJK COMPATIBILITY IDEOGRAPH-2F8F5;Lo;0;L;6BBA;;;;N;;;;; 2F8F6;CJK COMPATIBILITY IDEOGRAPH-2F8F6;Lo;0;L;6BBB;;;;N;;;;; 2F8F7;CJK COMPATIBILITY IDEOGRAPH-2F8F7;Lo;0;L;23A8D;;;;N;;;;; 2F8F8;CJK COMPATIBILITY IDEOGRAPH-2F8F8;Lo;0;L;21D0B;;;;N;;;;; 2F8F9;CJK COMPATIBILITY IDEOGRAPH-2F8F9;Lo;0;L;23AFA;;;;N;;;;; 2F8FA;CJK COMPATIBILITY IDEOGRAPH-2F8FA;Lo;0;L;6C4E;;;;N;;;;; 2F8FB;CJK COMPATIBILITY IDEOGRAPH-2F8FB;Lo;0;L;23CBC;;;;N;;;;; 2F8FC;CJK COMPATIBILITY IDEOGRAPH-2F8FC;Lo;0;L;6CBF;;;;N;;;;; 2F8FD;CJK COMPATIBILITY IDEOGRAPH-2F8FD;Lo;0;L;6CCD;;;;N;;;;; 2F8FE;CJK COMPATIBILITY IDEOGRAPH-2F8FE;Lo;0;L;6C67;;;;N;;;;; 2F8FF;CJK COMPATIBILITY IDEOGRAPH-2F8FF;Lo;0;L;6D16;;;;N;;;;; 2F900;CJK COMPATIBILITY IDEOGRAPH-2F900;Lo;0;L;6D3E;;;;N;;;;; 2F901;CJK COMPATIBILITY IDEOGRAPH-2F901;Lo;0;L;6D77;;;;N;;;;; 2F902;CJK COMPATIBILITY IDEOGRAPH-2F902;Lo;0;L;6D41;;;;N;;;;; 2F903;CJK COMPATIBILITY IDEOGRAPH-2F903;Lo;0;L;6D69;;;;N;;;;; 2F904;CJK COMPATIBILITY IDEOGRAPH-2F904;Lo;0;L;6D78;;;;N;;;;; 2F905;CJK COMPATIBILITY IDEOGRAPH-2F905;Lo;0;L;6D85;;;;N;;;;; 2F906;CJK COMPATIBILITY IDEOGRAPH-2F906;Lo;0;L;23D1E;;;;N;;;;; 2F907;CJK COMPATIBILITY IDEOGRAPH-2F907;Lo;0;L;6D34;;;;N;;;;; 2F908;CJK COMPATIBILITY IDEOGRAPH-2F908;Lo;0;L;6E2F;;;;N;;;;; 2F909;CJK COMPATIBILITY IDEOGRAPH-2F909;Lo;0;L;6E6E;;;;N;;;;; 2F90A;CJK COMPATIBILITY IDEOGRAPH-2F90A;Lo;0;L;3D33;;;;N;;;;; 2F90B;CJK COMPATIBILITY IDEOGRAPH-2F90B;Lo;0;L;6ECB;;;;N;;;;; 2F90C;CJK COMPATIBILITY IDEOGRAPH-2F90C;Lo;0;L;6EC7;;;;N;;;;; 2F90D;CJK COMPATIBILITY IDEOGRAPH-2F90D;Lo;0;L;23ED1;;;;N;;;;; 2F90E;CJK COMPATIBILITY IDEOGRAPH-2F90E;Lo;0;L;6DF9;;;;N;;;;; 2F90F;CJK COMPATIBILITY IDEOGRAPH-2F90F;Lo;0;L;6F6E;;;;N;;;;; 2F910;CJK COMPATIBILITY IDEOGRAPH-2F910;Lo;0;L;23F5E;;;;N;;;;; 2F911;CJK COMPATIBILITY IDEOGRAPH-2F911;Lo;0;L;23F8E;;;;N;;;;; 2F912;CJK COMPATIBILITY IDEOGRAPH-2F912;Lo;0;L;6FC6;;;;N;;;;; 2F913;CJK COMPATIBILITY IDEOGRAPH-2F913;Lo;0;L;7039;;;;N;;;;; 2F914;CJK COMPATIBILITY IDEOGRAPH-2F914;Lo;0;L;701E;;;;N;;;;; 2F915;CJK COMPATIBILITY IDEOGRAPH-2F915;Lo;0;L;701B;;;;N;;;;; 2F916;CJK COMPATIBILITY IDEOGRAPH-2F916;Lo;0;L;3D96;;;;N;;;;; 2F917;CJK COMPATIBILITY IDEOGRAPH-2F917;Lo;0;L;704A;;;;N;;;;; 2F918;CJK COMPATIBILITY IDEOGRAPH-2F918;Lo;0;L;707D;;;;N;;;;; 2F919;CJK COMPATIBILITY IDEOGRAPH-2F919;Lo;0;L;7077;;;;N;;;;; 2F91A;CJK COMPATIBILITY IDEOGRAPH-2F91A;Lo;0;L;70AD;;;;N;;;;; 2F91B;CJK COMPATIBILITY IDEOGRAPH-2F91B;Lo;0;L;20525;;;;N;;;;; 2F91C;CJK COMPATIBILITY IDEOGRAPH-2F91C;Lo;0;L;7145;;;;N;;;;; 2F91D;CJK COMPATIBILITY IDEOGRAPH-2F91D;Lo;0;L;24263;;;;N;;;;; 2F91E;CJK COMPATIBILITY IDEOGRAPH-2F91E;Lo;0;L;719C;;;;N;;;;; 2F91F;CJK COMPATIBILITY IDEOGRAPH-2F91F;Lo;0;L;243AB;;;;N;;;;; 2F920;CJK COMPATIBILITY IDEOGRAPH-2F920;Lo;0;L;7228;;;;N;;;;; 2F921;CJK COMPATIBILITY IDEOGRAPH-2F921;Lo;0;L;7235;;;;N;;;;; 2F922;CJK COMPATIBILITY IDEOGRAPH-2F922;Lo;0;L;7250;;;;N;;;;; 2F923;CJK COMPATIBILITY IDEOGRAPH-2F923;Lo;0;L;24608;;;;N;;;;; 2F924;CJK COMPATIBILITY IDEOGRAPH-2F924;Lo;0;L;7280;;;;N;;;;; 2F925;CJK COMPATIBILITY IDEOGRAPH-2F925;Lo;0;L;7295;;;;N;;;;; 2F926;CJK COMPATIBILITY IDEOGRAPH-2F926;Lo;0;L;24735;;;;N;;;;; 2F927;CJK COMPATIBILITY IDEOGRAPH-2F927;Lo;0;L;24814;;;;N;;;;; 2F928;CJK COMPATIBILITY IDEOGRAPH-2F928;Lo;0;L;737A;;;;N;;;;; 2F929;CJK COMPATIBILITY IDEOGRAPH-2F929;Lo;0;L;738B;;;;N;;;;; 2F92A;CJK COMPATIBILITY IDEOGRAPH-2F92A;Lo;0;L;3EAC;;;;N;;;;; 2F92B;CJK COMPATIBILITY IDEOGRAPH-2F92B;Lo;0;L;73A5;;;;N;;;;; 2F92C;CJK COMPATIBILITY IDEOGRAPH-2F92C;Lo;0;L;3EB8;;;;N;;;;; 2F92D;CJK COMPATIBILITY IDEOGRAPH-2F92D;Lo;0;L;3EB8;;;;N;;;;; 2F92E;CJK COMPATIBILITY IDEOGRAPH-2F92E;Lo;0;L;7447;;;;N;;;;; 2F92F;CJK COMPATIBILITY IDEOGRAPH-2F92F;Lo;0;L;745C;;;;N;;;;; 2F930;CJK COMPATIBILITY IDEOGRAPH-2F930;Lo;0;L;7471;;;;N;;;;; 2F931;CJK COMPATIBILITY IDEOGRAPH-2F931;Lo;0;L;7485;;;;N;;;;; 2F932;CJK COMPATIBILITY IDEOGRAPH-2F932;Lo;0;L;74CA;;;;N;;;;; 2F933;CJK COMPATIBILITY IDEOGRAPH-2F933;Lo;0;L;3F1B;;;;N;;;;; 2F934;CJK COMPATIBILITY IDEOGRAPH-2F934;Lo;0;L;7524;;;;N;;;;; 2F935;CJK COMPATIBILITY IDEOGRAPH-2F935;Lo;0;L;24C36;;;;N;;;;; 2F936;CJK COMPATIBILITY IDEOGRAPH-2F936;Lo;0;L;753E;;;;N;;;;; 2F937;CJK COMPATIBILITY IDEOGRAPH-2F937;Lo;0;L;24C92;;;;N;;;;; 2F938;CJK COMPATIBILITY IDEOGRAPH-2F938;Lo;0;L;7570;;;;N;;;;; 2F939;CJK COMPATIBILITY IDEOGRAPH-2F939;Lo;0;L;2219F;;;;N;;;;; 2F93A;CJK COMPATIBILITY IDEOGRAPH-2F93A;Lo;0;L;7610;;;;N;;;;; 2F93B;CJK COMPATIBILITY IDEOGRAPH-2F93B;Lo;0;L;24FA1;;;;N;;;;; 2F93C;CJK COMPATIBILITY IDEOGRAPH-2F93C;Lo;0;L;24FB8;;;;N;;;;; 2F93D;CJK COMPATIBILITY IDEOGRAPH-2F93D;Lo;0;L;25044;;;;N;;;;; 2F93E;CJK COMPATIBILITY IDEOGRAPH-2F93E;Lo;0;L;3FFC;;;;N;;;;; 2F93F;CJK COMPATIBILITY IDEOGRAPH-2F93F;Lo;0;L;4008;;;;N;;;;; 2F940;CJK COMPATIBILITY IDEOGRAPH-2F940;Lo;0;L;76F4;;;;N;;;;; 2F941;CJK COMPATIBILITY IDEOGRAPH-2F941;Lo;0;L;250F3;;;;N;;;;; 2F942;CJK COMPATIBILITY IDEOGRAPH-2F942;Lo;0;L;250F2;;;;N;;;;; 2F943;CJK COMPATIBILITY IDEOGRAPH-2F943;Lo;0;L;25119;;;;N;;;;; 2F944;CJK COMPATIBILITY IDEOGRAPH-2F944;Lo;0;L;25133;;;;N;;;;; 2F945;CJK COMPATIBILITY IDEOGRAPH-2F945;Lo;0;L;771E;;;;N;;;;; 2F946;CJK COMPATIBILITY IDEOGRAPH-2F946;Lo;0;L;771F;;;;N;;;;; 2F947;CJK COMPATIBILITY IDEOGRAPH-2F947;Lo;0;L;771F;;;;N;;;;; 2F948;CJK COMPATIBILITY IDEOGRAPH-2F948;Lo;0;L;774A;;;;N;;;;; 2F949;CJK COMPATIBILITY IDEOGRAPH-2F949;Lo;0;L;4039;;;;N;;;;; 2F94A;CJK COMPATIBILITY IDEOGRAPH-2F94A;Lo;0;L;778B;;;;N;;;;; 2F94B;CJK COMPATIBILITY IDEOGRAPH-2F94B;Lo;0;L;4046;;;;N;;;;; 2F94C;CJK COMPATIBILITY IDEOGRAPH-2F94C;Lo;0;L;4096;;;;N;;;;; 2F94D;CJK COMPATIBILITY IDEOGRAPH-2F94D;Lo;0;L;2541D;;;;N;;;;; 2F94E;CJK COMPATIBILITY IDEOGRAPH-2F94E;Lo;0;L;784E;;;;N;;;;; 2F94F;CJK COMPATIBILITY IDEOGRAPH-2F94F;Lo;0;L;788C;;;;N;;;;; 2F950;CJK COMPATIBILITY IDEOGRAPH-2F950;Lo;0;L;78CC;;;;N;;;;; 2F951;CJK COMPATIBILITY IDEOGRAPH-2F951;Lo;0;L;40E3;;;;N;;;;; 2F952;CJK COMPATIBILITY IDEOGRAPH-2F952;Lo;0;L;25626;;;;N;;;;; 2F953;CJK COMPATIBILITY IDEOGRAPH-2F953;Lo;0;L;7956;;;;N;;;;; 2F954;CJK COMPATIBILITY IDEOGRAPH-2F954;Lo;0;L;2569A;;;;N;;;;; 2F955;CJK COMPATIBILITY IDEOGRAPH-2F955;Lo;0;L;256C5;;;;N;;;;; 2F956;CJK COMPATIBILITY IDEOGRAPH-2F956;Lo;0;L;798F;;;;N;;;;; 2F957;CJK COMPATIBILITY IDEOGRAPH-2F957;Lo;0;L;79EB;;;;N;;;;; 2F958;CJK COMPATIBILITY IDEOGRAPH-2F958;Lo;0;L;412F;;;;N;;;;; 2F959;CJK COMPATIBILITY IDEOGRAPH-2F959;Lo;0;L;7A40;;;;N;;;;; 2F95A;CJK COMPATIBILITY IDEOGRAPH-2F95A;Lo;0;L;7A4A;;;;N;;;;; 2F95B;CJK COMPATIBILITY IDEOGRAPH-2F95B;Lo;0;L;7A4F;;;;N;;;;; 2F95C;CJK COMPATIBILITY IDEOGRAPH-2F95C;Lo;0;L;2597C;;;;N;;;;; 2F95D;CJK COMPATIBILITY IDEOGRAPH-2F95D;Lo;0;L;25AA7;;;;N;;;;; 2F95E;CJK COMPATIBILITY IDEOGRAPH-2F95E;Lo;0;L;25AA7;;;;N;;;;; 2F95F;CJK COMPATIBILITY IDEOGRAPH-2F95F;Lo;0;L;7AEE;;;;N;;;;; 2F960;CJK COMPATIBILITY IDEOGRAPH-2F960;Lo;0;L;4202;;;;N;;;;; 2F961;CJK COMPATIBILITY IDEOGRAPH-2F961;Lo;0;L;25BAB;;;;N;;;;; 2F962;CJK COMPATIBILITY IDEOGRAPH-2F962;Lo;0;L;7BC6;;;;N;;;;; 2F963;CJK COMPATIBILITY IDEOGRAPH-2F963;Lo;0;L;7BC9;;;;N;;;;; 2F964;CJK COMPATIBILITY IDEOGRAPH-2F964;Lo;0;L;4227;;;;N;;;;; 2F965;CJK COMPATIBILITY IDEOGRAPH-2F965;Lo;0;L;25C80;;;;N;;;;; 2F966;CJK COMPATIBILITY IDEOGRAPH-2F966;Lo;0;L;7CD2;;;;N;;;;; 2F967;CJK COMPATIBILITY IDEOGRAPH-2F967;Lo;0;L;42A0;;;;N;;;;; 2F968;CJK COMPATIBILITY IDEOGRAPH-2F968;Lo;0;L;7CE8;;;;N;;;;; 2F969;CJK COMPATIBILITY IDEOGRAPH-2F969;Lo;0;L;7CE3;;;;N;;;;; 2F96A;CJK COMPATIBILITY IDEOGRAPH-2F96A;Lo;0;L;7D00;;;;N;;;;; 2F96B;CJK COMPATIBILITY IDEOGRAPH-2F96B;Lo;0;L;25F86;;;;N;;;;; 2F96C;CJK COMPATIBILITY IDEOGRAPH-2F96C;Lo;0;L;7D63;;;;N;;;;; 2F96D;CJK COMPATIBILITY IDEOGRAPH-2F96D;Lo;0;L;4301;;;;N;;;;; 2F96E;CJK COMPATIBILITY IDEOGRAPH-2F96E;Lo;0;L;7DC7;;;;N;;;;; 2F96F;CJK COMPATIBILITY IDEOGRAPH-2F96F;Lo;0;L;7E02;;;;N;;;;; 2F970;CJK COMPATIBILITY IDEOGRAPH-2F970;Lo;0;L;7E45;;;;N;;;;; 2F971;CJK COMPATIBILITY IDEOGRAPH-2F971;Lo;0;L;4334;;;;N;;;;; 2F972;CJK COMPATIBILITY IDEOGRAPH-2F972;Lo;0;L;26228;;;;N;;;;; 2F973;CJK COMPATIBILITY IDEOGRAPH-2F973;Lo;0;L;26247;;;;N;;;;; 2F974;CJK COMPATIBILITY IDEOGRAPH-2F974;Lo;0;L;4359;;;;N;;;;; 2F975;CJK COMPATIBILITY IDEOGRAPH-2F975;Lo;0;L;262D9;;;;N;;;;; 2F976;CJK COMPATIBILITY IDEOGRAPH-2F976;Lo;0;L;7F7A;;;;N;;;;; 2F977;CJK COMPATIBILITY IDEOGRAPH-2F977;Lo;0;L;2633E;;;;N;;;;; 2F978;CJK COMPATIBILITY IDEOGRAPH-2F978;Lo;0;L;7F95;;;;N;;;;; 2F979;CJK COMPATIBILITY IDEOGRAPH-2F979;Lo;0;L;7FFA;;;;N;;;;; 2F97A;CJK COMPATIBILITY IDEOGRAPH-2F97A;Lo;0;L;8005;;;;N;;;;; 2F97B;CJK COMPATIBILITY IDEOGRAPH-2F97B;Lo;0;L;264DA;;;;N;;;;; 2F97C;CJK COMPATIBILITY IDEOGRAPH-2F97C;Lo;0;L;26523;;;;N;;;;; 2F97D;CJK COMPATIBILITY IDEOGRAPH-2F97D;Lo;0;L;8060;;;;N;;;;; 2F97E;CJK COMPATIBILITY IDEOGRAPH-2F97E;Lo;0;L;265A8;;;;N;;;;; 2F97F;CJK COMPATIBILITY IDEOGRAPH-2F97F;Lo;0;L;8070;;;;N;;;;; 2F980;CJK COMPATIBILITY IDEOGRAPH-2F980;Lo;0;L;2335F;;;;N;;;;; 2F981;CJK COMPATIBILITY IDEOGRAPH-2F981;Lo;0;L;43D5;;;;N;;;;; 2F982;CJK COMPATIBILITY IDEOGRAPH-2F982;Lo;0;L;80B2;;;;N;;;;; 2F983;CJK COMPATIBILITY IDEOGRAPH-2F983;Lo;0;L;8103;;;;N;;;;; 2F984;CJK COMPATIBILITY IDEOGRAPH-2F984;Lo;0;L;440B;;;;N;;;;; 2F985;CJK COMPATIBILITY IDEOGRAPH-2F985;Lo;0;L;813E;;;;N;;;;; 2F986;CJK COMPATIBILITY IDEOGRAPH-2F986;Lo;0;L;5AB5;;;;N;;;;; 2F987;CJK COMPATIBILITY IDEOGRAPH-2F987;Lo;0;L;267A7;;;;N;;;;; 2F988;CJK COMPATIBILITY IDEOGRAPH-2F988;Lo;0;L;267B5;;;;N;;;;; 2F989;CJK COMPATIBILITY IDEOGRAPH-2F989;Lo;0;L;23393;;;;N;;;;; 2F98A;CJK COMPATIBILITY IDEOGRAPH-2F98A;Lo;0;L;2339C;;;;N;;;;; 2F98B;CJK COMPATIBILITY IDEOGRAPH-2F98B;Lo;0;L;8201;;;;N;;;;; 2F98C;CJK COMPATIBILITY IDEOGRAPH-2F98C;Lo;0;L;8204;;;;N;;;;; 2F98D;CJK COMPATIBILITY IDEOGRAPH-2F98D;Lo;0;L;8F9E;;;;N;;;;; 2F98E;CJK COMPATIBILITY IDEOGRAPH-2F98E;Lo;0;L;446B;;;;N;;;;; 2F98F;CJK COMPATIBILITY IDEOGRAPH-2F98F;Lo;0;L;8291;;;;N;;;;; 2F990;CJK COMPATIBILITY IDEOGRAPH-2F990;Lo;0;L;828B;;;;N;;;;; 2F991;CJK COMPATIBILITY IDEOGRAPH-2F991;Lo;0;L;829D;;;;N;;;;; 2F992;CJK COMPATIBILITY IDEOGRAPH-2F992;Lo;0;L;52B3;;;;N;;;;; 2F993;CJK COMPATIBILITY IDEOGRAPH-2F993;Lo;0;L;82B1;;;;N;;;;; 2F994;CJK COMPATIBILITY IDEOGRAPH-2F994;Lo;0;L;82B3;;;;N;;;;; 2F995;CJK COMPATIBILITY IDEOGRAPH-2F995;Lo;0;L;82BD;;;;N;;;;; 2F996;CJK COMPATIBILITY IDEOGRAPH-2F996;Lo;0;L;82E6;;;;N;;;;; 2F997;CJK COMPATIBILITY IDEOGRAPH-2F997;Lo;0;L;26B3C;;;;N;;;;; 2F998;CJK COMPATIBILITY IDEOGRAPH-2F998;Lo;0;L;82E5;;;;N;;;;; 2F999;CJK COMPATIBILITY IDEOGRAPH-2F999;Lo;0;L;831D;;;;N;;;;; 2F99A;CJK COMPATIBILITY IDEOGRAPH-2F99A;Lo;0;L;8363;;;;N;;;;; 2F99B;CJK COMPATIBILITY IDEOGRAPH-2F99B;Lo;0;L;83AD;;;;N;;;;; 2F99C;CJK COMPATIBILITY IDEOGRAPH-2F99C;Lo;0;L;8323;;;;N;;;;; 2F99D;CJK COMPATIBILITY IDEOGRAPH-2F99D;Lo;0;L;83BD;;;;N;;;;; 2F99E;CJK COMPATIBILITY IDEOGRAPH-2F99E;Lo;0;L;83E7;;;;N;;;;; 2F99F;CJK COMPATIBILITY IDEOGRAPH-2F99F;Lo;0;L;8457;;;;N;;;;; 2F9A0;CJK COMPATIBILITY IDEOGRAPH-2F9A0;Lo;0;L;8353;;;;N;;;;; 2F9A1;CJK COMPATIBILITY IDEOGRAPH-2F9A1;Lo;0;L;83CA;;;;N;;;;; 2F9A2;CJK COMPATIBILITY IDEOGRAPH-2F9A2;Lo;0;L;83CC;;;;N;;;;; 2F9A3;CJK COMPATIBILITY IDEOGRAPH-2F9A3;Lo;0;L;83DC;;;;N;;;;; 2F9A4;CJK COMPATIBILITY IDEOGRAPH-2F9A4;Lo;0;L;26C36;;;;N;;;;; 2F9A5;CJK COMPATIBILITY IDEOGRAPH-2F9A5;Lo;0;L;26D6B;;;;N;;;;; 2F9A6;CJK COMPATIBILITY IDEOGRAPH-2F9A6;Lo;0;L;26CD5;;;;N;;;;; 2F9A7;CJK COMPATIBILITY IDEOGRAPH-2F9A7;Lo;0;L;452B;;;;N;;;;; 2F9A8;CJK COMPATIBILITY IDEOGRAPH-2F9A8;Lo;0;L;84F1;;;;N;;;;; 2F9A9;CJK COMPATIBILITY IDEOGRAPH-2F9A9;Lo;0;L;84F3;;;;N;;;;; 2F9AA;CJK COMPATIBILITY IDEOGRAPH-2F9AA;Lo;0;L;8516;;;;N;;;;; 2F9AB;CJK COMPATIBILITY IDEOGRAPH-2F9AB;Lo;0;L;273CA;;;;N;;;;; 2F9AC;CJK COMPATIBILITY IDEOGRAPH-2F9AC;Lo;0;L;8564;;;;N;;;;; 2F9AD;CJK COMPATIBILITY IDEOGRAPH-2F9AD;Lo;0;L;26F2C;;;;N;;;;; 2F9AE;CJK COMPATIBILITY IDEOGRAPH-2F9AE;Lo;0;L;455D;;;;N;;;;; 2F9AF;CJK COMPATIBILITY IDEOGRAPH-2F9AF;Lo;0;L;4561;;;;N;;;;; 2F9B0;CJK COMPATIBILITY IDEOGRAPH-2F9B0;Lo;0;L;26FB1;;;;N;;;;; 2F9B1;CJK COMPATIBILITY IDEOGRAPH-2F9B1;Lo;0;L;270D2;;;;N;;;;; 2F9B2;CJK COMPATIBILITY IDEOGRAPH-2F9B2;Lo;0;L;456B;;;;N;;;;; 2F9B3;CJK COMPATIBILITY IDEOGRAPH-2F9B3;Lo;0;L;8650;;;;N;;;;; 2F9B4;CJK COMPATIBILITY IDEOGRAPH-2F9B4;Lo;0;L;865C;;;;N;;;;; 2F9B5;CJK COMPATIBILITY IDEOGRAPH-2F9B5;Lo;0;L;8667;;;;N;;;;; 2F9B6;CJK COMPATIBILITY IDEOGRAPH-2F9B6;Lo;0;L;8669;;;;N;;;;; 2F9B7;CJK COMPATIBILITY IDEOGRAPH-2F9B7;Lo;0;L;86A9;;;;N;;;;; 2F9B8;CJK COMPATIBILITY IDEOGRAPH-2F9B8;Lo;0;L;8688;;;;N;;;;; 2F9B9;CJK COMPATIBILITY IDEOGRAPH-2F9B9;Lo;0;L;870E;;;;N;;;;; 2F9BA;CJK COMPATIBILITY IDEOGRAPH-2F9BA;Lo;0;L;86E2;;;;N;;;;; 2F9BB;CJK COMPATIBILITY IDEOGRAPH-2F9BB;Lo;0;L;8779;;;;N;;;;; 2F9BC;CJK COMPATIBILITY IDEOGRAPH-2F9BC;Lo;0;L;8728;;;;N;;;;; 2F9BD;CJK COMPATIBILITY IDEOGRAPH-2F9BD;Lo;0;L;876B;;;;N;;;;; 2F9BE;CJK COMPATIBILITY IDEOGRAPH-2F9BE;Lo;0;L;8786;;;;N;;;;; 2F9BF;CJK COMPATIBILITY IDEOGRAPH-2F9BF;Lo;0;L;45D7;;;;N;;;;; 2F9C0;CJK COMPATIBILITY IDEOGRAPH-2F9C0;Lo;0;L;87E1;;;;N;;;;; 2F9C1;CJK COMPATIBILITY IDEOGRAPH-2F9C1;Lo;0;L;8801;;;;N;;;;; 2F9C2;CJK COMPATIBILITY IDEOGRAPH-2F9C2;Lo;0;L;45F9;;;;N;;;;; 2F9C3;CJK COMPATIBILITY IDEOGRAPH-2F9C3;Lo;0;L;8860;;;;N;;;;; 2F9C4;CJK COMPATIBILITY IDEOGRAPH-2F9C4;Lo;0;L;8863;;;;N;;;;; 2F9C5;CJK COMPATIBILITY IDEOGRAPH-2F9C5;Lo;0;L;27667;;;;N;;;;; 2F9C6;CJK COMPATIBILITY IDEOGRAPH-2F9C6;Lo;0;L;88D7;;;;N;;;;; 2F9C7;CJK COMPATIBILITY IDEOGRAPH-2F9C7;Lo;0;L;88DE;;;;N;;;;; 2F9C8;CJK COMPATIBILITY IDEOGRAPH-2F9C8;Lo;0;L;4635;;;;N;;;;; 2F9C9;CJK COMPATIBILITY IDEOGRAPH-2F9C9;Lo;0;L;88FA;;;;N;;;;; 2F9CA;CJK COMPATIBILITY IDEOGRAPH-2F9CA;Lo;0;L;34BB;;;;N;;;;; 2F9CB;CJK COMPATIBILITY IDEOGRAPH-2F9CB;Lo;0;L;278AE;;;;N;;;;; 2F9CC;CJK COMPATIBILITY IDEOGRAPH-2F9CC;Lo;0;L;27966;;;;N;;;;; 2F9CD;CJK COMPATIBILITY IDEOGRAPH-2F9CD;Lo;0;L;46BE;;;;N;;;;; 2F9CE;CJK COMPATIBILITY IDEOGRAPH-2F9CE;Lo;0;L;46C7;;;;N;;;;; 2F9CF;CJK COMPATIBILITY IDEOGRAPH-2F9CF;Lo;0;L;8AA0;;;;N;;;;; 2F9D0;CJK COMPATIBILITY IDEOGRAPH-2F9D0;Lo;0;L;8AED;;;;N;;;;; 2F9D1;CJK COMPATIBILITY IDEOGRAPH-2F9D1;Lo;0;L;8B8A;;;;N;;;;; 2F9D2;CJK COMPATIBILITY IDEOGRAPH-2F9D2;Lo;0;L;8C55;;;;N;;;;; 2F9D3;CJK COMPATIBILITY IDEOGRAPH-2F9D3;Lo;0;L;27CA8;;;;N;;;;; 2F9D4;CJK COMPATIBILITY IDEOGRAPH-2F9D4;Lo;0;L;8CAB;;;;N;;;;; 2F9D5;CJK COMPATIBILITY IDEOGRAPH-2F9D5;Lo;0;L;8CC1;;;;N;;;;; 2F9D6;CJK COMPATIBILITY IDEOGRAPH-2F9D6;Lo;0;L;8D1B;;;;N;;;;; 2F9D7;CJK COMPATIBILITY IDEOGRAPH-2F9D7;Lo;0;L;8D77;;;;N;;;;; 2F9D8;CJK COMPATIBILITY IDEOGRAPH-2F9D8;Lo;0;L;27F2F;;;;N;;;;; 2F9D9;CJK COMPATIBILITY IDEOGRAPH-2F9D9;Lo;0;L;20804;;;;N;;;;; 2F9DA;CJK COMPATIBILITY IDEOGRAPH-2F9DA;Lo;0;L;8DCB;;;;N;;;;; 2F9DB;CJK COMPATIBILITY IDEOGRAPH-2F9DB;Lo;0;L;8DBC;;;;N;;;;; 2F9DC;CJK COMPATIBILITY IDEOGRAPH-2F9DC;Lo;0;L;8DF0;;;;N;;;;; 2F9DD;CJK COMPATIBILITY IDEOGRAPH-2F9DD;Lo;0;L;208DE;;;;N;;;;; 2F9DE;CJK COMPATIBILITY IDEOGRAPH-2F9DE;Lo;0;L;8ED4;;;;N;;;;; 2F9DF;CJK COMPATIBILITY IDEOGRAPH-2F9DF;Lo;0;L;8F38;;;;N;;;;; 2F9E0;CJK COMPATIBILITY IDEOGRAPH-2F9E0;Lo;0;L;285D2;;;;N;;;;; 2F9E1;CJK COMPATIBILITY IDEOGRAPH-2F9E1;Lo;0;L;285ED;;;;N;;;;; 2F9E2;CJK COMPATIBILITY IDEOGRAPH-2F9E2;Lo;0;L;9094;;;;N;;;;; 2F9E3;CJK COMPATIBILITY IDEOGRAPH-2F9E3;Lo;0;L;90F1;;;;N;;;;; 2F9E4;CJK COMPATIBILITY IDEOGRAPH-2F9E4;Lo;0;L;9111;;;;N;;;;; 2F9E5;CJK COMPATIBILITY IDEOGRAPH-2F9E5;Lo;0;L;2872E;;;;N;;;;; 2F9E6;CJK COMPATIBILITY IDEOGRAPH-2F9E6;Lo;0;L;911B;;;;N;;;;; 2F9E7;CJK COMPATIBILITY IDEOGRAPH-2F9E7;Lo;0;L;9238;;;;N;;;;; 2F9E8;CJK COMPATIBILITY IDEOGRAPH-2F9E8;Lo;0;L;92D7;;;;N;;;;; 2F9E9;CJK COMPATIBILITY IDEOGRAPH-2F9E9;Lo;0;L;92D8;;;;N;;;;; 2F9EA;CJK COMPATIBILITY IDEOGRAPH-2F9EA;Lo;0;L;927C;;;;N;;;;; 2F9EB;CJK COMPATIBILITY IDEOGRAPH-2F9EB;Lo;0;L;93F9;;;;N;;;;; 2F9EC;CJK COMPATIBILITY IDEOGRAPH-2F9EC;Lo;0;L;9415;;;;N;;;;; 2F9ED;CJK COMPATIBILITY IDEOGRAPH-2F9ED;Lo;0;L;28BFA;;;;N;;;;; 2F9EE;CJK COMPATIBILITY IDEOGRAPH-2F9EE;Lo;0;L;958B;;;;N;;;;; 2F9EF;CJK COMPATIBILITY IDEOGRAPH-2F9EF;Lo;0;L;4995;;;;N;;;;; 2F9F0;CJK COMPATIBILITY IDEOGRAPH-2F9F0;Lo;0;L;95B7;;;;N;;;;; 2F9F1;CJK COMPATIBILITY IDEOGRAPH-2F9F1;Lo;0;L;28D77;;;;N;;;;; 2F9F2;CJK COMPATIBILITY IDEOGRAPH-2F9F2;Lo;0;L;49E6;;;;N;;;;; 2F9F3;CJK COMPATIBILITY IDEOGRAPH-2F9F3;Lo;0;L;96C3;;;;N;;;;; 2F9F4;CJK COMPATIBILITY IDEOGRAPH-2F9F4;Lo;0;L;5DB2;;;;N;;;;; 2F9F5;CJK COMPATIBILITY IDEOGRAPH-2F9F5;Lo;0;L;9723;;;;N;;;;; 2F9F6;CJK COMPATIBILITY IDEOGRAPH-2F9F6;Lo;0;L;29145;;;;N;;;;; 2F9F7;CJK COMPATIBILITY IDEOGRAPH-2F9F7;Lo;0;L;2921A;;;;N;;;;; 2F9F8;CJK COMPATIBILITY IDEOGRAPH-2F9F8;Lo;0;L;4A6E;;;;N;;;;; 2F9F9;CJK COMPATIBILITY IDEOGRAPH-2F9F9;Lo;0;L;4A76;;;;N;;;;; 2F9FA;CJK COMPATIBILITY IDEOGRAPH-2F9FA;Lo;0;L;97E0;;;;N;;;;; 2F9FB;CJK COMPATIBILITY IDEOGRAPH-2F9FB;Lo;0;L;2940A;;;;N;;;;; 2F9FC;CJK COMPATIBILITY IDEOGRAPH-2F9FC;Lo;0;L;4AB2;;;;N;;;;; 2F9FD;CJK COMPATIBILITY IDEOGRAPH-2F9FD;Lo;0;L;29496;;;;N;;;;; 2F9FE;CJK COMPATIBILITY IDEOGRAPH-2F9FE;Lo;0;L;980B;;;;N;;;;; 2F9FF;CJK COMPATIBILITY IDEOGRAPH-2F9FF;Lo;0;L;980B;;;;N;;;;; 2FA00;CJK COMPATIBILITY IDEOGRAPH-2FA00;Lo;0;L;9829;;;;N;;;;; 2FA01;CJK COMPATIBILITY IDEOGRAPH-2FA01;Lo;0;L;295B6;;;;N;;;;; 2FA02;CJK COMPATIBILITY IDEOGRAPH-2FA02;Lo;0;L;98E2;;;;N;;;;; 2FA03;CJK COMPATIBILITY IDEOGRAPH-2FA03;Lo;0;L;4B33;;;;N;;;;; 2FA04;CJK COMPATIBILITY IDEOGRAPH-2FA04;Lo;0;L;9929;;;;N;;;;; 2FA05;CJK COMPATIBILITY IDEOGRAPH-2FA05;Lo;0;L;99A7;;;;N;;;;; 2FA06;CJK COMPATIBILITY IDEOGRAPH-2FA06;Lo;0;L;99C2;;;;N;;;;; 2FA07;CJK COMPATIBILITY IDEOGRAPH-2FA07;Lo;0;L;99FE;;;;N;;;;; 2FA08;CJK COMPATIBILITY IDEOGRAPH-2FA08;Lo;0;L;4BCE;;;;N;;;;; 2FA09;CJK COMPATIBILITY IDEOGRAPH-2FA09;Lo;0;L;29B30;;;;N;;;;; 2FA0A;CJK COMPATIBILITY IDEOGRAPH-2FA0A;Lo;0;L;9B12;;;;N;;;;; 2FA0B;CJK COMPATIBILITY IDEOGRAPH-2FA0B;Lo;0;L;9C40;;;;N;;;;; 2FA0C;CJK COMPATIBILITY IDEOGRAPH-2FA0C;Lo;0;L;9CFD;;;;N;;;;; 2FA0D;CJK COMPATIBILITY IDEOGRAPH-2FA0D;Lo;0;L;4CCE;;;;N;;;;; 2FA0E;CJK COMPATIBILITY IDEOGRAPH-2FA0E;Lo;0;L;4CED;;;;N;;;;; 2FA0F;CJK COMPATIBILITY IDEOGRAPH-2FA0F;Lo;0;L;9D67;;;;N;;;;; 2FA10;CJK COMPATIBILITY IDEOGRAPH-2FA10;Lo;0;L;2A0CE;;;;N;;;;; 2FA11;CJK COMPATIBILITY IDEOGRAPH-2FA11;Lo;0;L;4CF8;;;;N;;;;; 2FA12;CJK COMPATIBILITY IDEOGRAPH-2FA12;Lo;0;L;2A105;;;;N;;;;; 2FA13;CJK COMPATIBILITY IDEOGRAPH-2FA13;Lo;0;L;2A20E;;;;N;;;;; 2FA14;CJK COMPATIBILITY IDEOGRAPH-2FA14;Lo;0;L;2A291;;;;N;;;;; 2FA15;CJK COMPATIBILITY IDEOGRAPH-2FA15;Lo;0;L;9EBB;;;;N;;;;; 2FA16;CJK COMPATIBILITY IDEOGRAPH-2FA16;Lo;0;L;4D56;;;;N;;;;; 2FA17;CJK COMPATIBILITY IDEOGRAPH-2FA17;Lo;0;L;9EF9;;;;N;;;;; 2FA18;CJK COMPATIBILITY IDEOGRAPH-2FA18;Lo;0;L;9EFE;;;;N;;;;; 2FA19;CJK COMPATIBILITY IDEOGRAPH-2FA19;Lo;0;L;9F05;;;;N;;;;; 2FA1A;CJK COMPATIBILITY IDEOGRAPH-2FA1A;Lo;0;L;9F0F;;;;N;;;;; 2FA1B;CJK COMPATIBILITY IDEOGRAPH-2FA1B;Lo;0;L;9F16;;;;N;;;;; 2FA1C;CJK COMPATIBILITY IDEOGRAPH-2FA1C;Lo;0;L;9F3B;;;;N;;;;; 2FA1D;CJK COMPATIBILITY IDEOGRAPH-2FA1D;Lo;0;L;2A600;;;;N;;;;; E0001;LANGUAGE TAG;Cf;0;BN;;;;;N;;;;; E0020;TAG SPACE;Cf;0;BN;;;;;N;;;;; E0021;TAG EXCLAMATION MARK;Cf;0;BN;;;;;N;;;;; E0022;TAG QUOTATION MARK;Cf;0;BN;;;;;N;;;;; E0023;TAG NUMBER SIGN;Cf;0;BN;;;;;N;;;;; E0024;TAG DOLLAR SIGN;Cf;0;BN;;;;;N;;;;; E0025;TAG PERCENT SIGN;Cf;0;BN;;;;;N;;;;; E0026;TAG AMPERSAND;Cf;0;BN;;;;;N;;;;; E0027;TAG APOSTROPHE;Cf;0;BN;;;;;N;;;;; E0028;TAG LEFT PARENTHESIS;Cf;0;BN;;;;;N;;;;; E0029;TAG RIGHT PARENTHESIS;Cf;0;BN;;;;;N;;;;; E002A;TAG ASTERISK;Cf;0;BN;;;;;N;;;;; E002B;TAG PLUS SIGN;Cf;0;BN;;;;;N;;;;; E002C;TAG COMMA;Cf;0;BN;;;;;N;;;;; E002D;TAG HYPHEN-MINUS;Cf;0;BN;;;;;N;;;;; E002E;TAG FULL STOP;Cf;0;BN;;;;;N;;;;; E002F;TAG SOLIDUS;Cf;0;BN;;;;;N;;;;; E0030;TAG DIGIT ZERO;Cf;0;BN;;;;;N;;;;; E0031;TAG DIGIT ONE;Cf;0;BN;;;;;N;;;;; E0032;TAG DIGIT TWO;Cf;0;BN;;;;;N;;;;; E0033;TAG DIGIT THREE;Cf;0;BN;;;;;N;;;;; E0034;TAG DIGIT FOUR;Cf;0;BN;;;;;N;;;;; E0035;TAG DIGIT FIVE;Cf;0;BN;;;;;N;;;;; E0036;TAG DIGIT SIX;Cf;0;BN;;;;;N;;;;; E0037;TAG DIGIT SEVEN;Cf;0;BN;;;;;N;;;;; E0038;TAG DIGIT EIGHT;Cf;0;BN;;;;;N;;;;; E0039;TAG DIGIT NINE;Cf;0;BN;;;;;N;;;;; E003A;TAG COLON;Cf;0;BN;;;;;N;;;;; E003B;TAG SEMICOLON;Cf;0;BN;;;;;N;;;;; E003C;TAG LESS-THAN SIGN;Cf;0;BN;;;;;N;;;;; E003D;TAG EQUALS SIGN;Cf;0;BN;;;;;N;;;;; E003E;TAG GREATER-THAN SIGN;Cf;0;BN;;;;;N;;;;; E003F;TAG QUESTION MARK;Cf;0;BN;;;;;N;;;;; E0040;TAG COMMERCIAL AT;Cf;0;BN;;;;;N;;;;; E0041;TAG LATIN CAPITAL LETTER A;Cf;0;BN;;;;;N;;;;; E0042;TAG LATIN CAPITAL LETTER B;Cf;0;BN;;;;;N;;;;; E0043;TAG LATIN CAPITAL LETTER C;Cf;0;BN;;;;;N;;;;; E0044;TAG LATIN CAPITAL LETTER D;Cf;0;BN;;;;;N;;;;; E0045;TAG LATIN CAPITAL LETTER E;Cf;0;BN;;;;;N;;;;; E0046;TAG LATIN CAPITAL LETTER F;Cf;0;BN;;;;;N;;;;; E0047;TAG LATIN CAPITAL LETTER G;Cf;0;BN;;;;;N;;;;; E0048;TAG LATIN CAPITAL LETTER H;Cf;0;BN;;;;;N;;;;; E0049;TAG LATIN CAPITAL LETTER I;Cf;0;BN;;;;;N;;;;; E004A;TAG LATIN CAPITAL LETTER J;Cf;0;BN;;;;;N;;;;; E004B;TAG LATIN CAPITAL LETTER K;Cf;0;BN;;;;;N;;;;; E004C;TAG LATIN CAPITAL LETTER L;Cf;0;BN;;;;;N;;;;; E004D;TAG LATIN CAPITAL LETTER M;Cf;0;BN;;;;;N;;;;; E004E;TAG LATIN CAPITAL LETTER N;Cf;0;BN;;;;;N;;;;; E004F;TAG LATIN CAPITAL LETTER O;Cf;0;BN;;;;;N;;;;; E0050;TAG LATIN CAPITAL LETTER P;Cf;0;BN;;;;;N;;;;; E0051;TAG LATIN CAPITAL LETTER Q;Cf;0;BN;;;;;N;;;;; E0052;TAG LATIN CAPITAL LETTER R;Cf;0;BN;;;;;N;;;;; E0053;TAG LATIN CAPITAL LETTER S;Cf;0;BN;;;;;N;;;;; E0054;TAG LATIN CAPITAL LETTER T;Cf;0;BN;;;;;N;;;;; E0055;TAG LATIN CAPITAL LETTER U;Cf;0;BN;;;;;N;;;;; E0056;TAG LATIN CAPITAL LETTER V;Cf;0;BN;;;;;N;;;;; E0057;TAG LATIN CAPITAL LETTER W;Cf;0;BN;;;;;N;;;;; E0058;TAG LATIN CAPITAL LETTER X;Cf;0;BN;;;;;N;;;;; E0059;TAG LATIN CAPITAL LETTER Y;Cf;0;BN;;;;;N;;;;; E005A;TAG LATIN CAPITAL LETTER Z;Cf;0;BN;;;;;N;;;;; E005B;TAG LEFT SQUARE BRACKET;Cf;0;BN;;;;;N;;;;; E005C;TAG REVERSE SOLIDUS;Cf;0;BN;;;;;N;;;;; E005D;TAG RIGHT SQUARE BRACKET;Cf;0;BN;;;;;N;;;;; E005E;TAG CIRCUMFLEX ACCENT;Cf;0;BN;;;;;N;;;;; E005F;TAG LOW LINE;Cf;0;BN;;;;;N;;;;; E0060;TAG GRAVE ACCENT;Cf;0;BN;;;;;N;;;;; E0061;TAG LATIN SMALL LETTER A;Cf;0;BN;;;;;N;;;;; E0062;TAG LATIN SMALL LETTER B;Cf;0;BN;;;;;N;;;;; E0063;TAG LATIN SMALL LETTER C;Cf;0;BN;;;;;N;;;;; E0064;TAG LATIN SMALL LETTER D;Cf;0;BN;;;;;N;;;;; E0065;TAG LATIN SMALL LETTER E;Cf;0;BN;;;;;N;;;;; E0066;TAG LATIN SMALL LETTER F;Cf;0;BN;;;;;N;;;;; E0067;TAG LATIN SMALL LETTER G;Cf;0;BN;;;;;N;;;;; E0068;TAG LATIN SMALL LETTER H;Cf;0;BN;;;;;N;;;;; E0069;TAG LATIN SMALL LETTER I;Cf;0;BN;;;;;N;;;;; E006A;TAG LATIN SMALL LETTER J;Cf;0;BN;;;;;N;;;;; E006B;TAG LATIN SMALL LETTER K;Cf;0;BN;;;;;N;;;;; E006C;TAG LATIN SMALL LETTER L;Cf;0;BN;;;;;N;;;;; E006D;TAG LATIN SMALL LETTER M;Cf;0;BN;;;;;N;;;;; E006E;TAG LATIN SMALL LETTER N;Cf;0;BN;;;;;N;;;;; E006F;TAG LATIN SMALL LETTER O;Cf;0;BN;;;;;N;;;;; E0070;TAG LATIN SMALL LETTER P;Cf;0;BN;;;;;N;;;;; E0071;TAG LATIN SMALL LETTER Q;Cf;0;BN;;;;;N;;;;; E0072;TAG LATIN SMALL LETTER R;Cf;0;BN;;;;;N;;;;; E0073;TAG LATIN SMALL LETTER S;Cf;0;BN;;;;;N;;;;; E0074;TAG LATIN SMALL LETTER T;Cf;0;BN;;;;;N;;;;; E0075;TAG LATIN SMALL LETTER U;Cf;0;BN;;;;;N;;;;; E0076;TAG LATIN SMALL LETTER V;Cf;0;BN;;;;;N;;;;; E0077;TAG LATIN SMALL LETTER W;Cf;0;BN;;;;;N;;;;; E0078;TAG LATIN SMALL LETTER X;Cf;0;BN;;;;;N;;;;; E0079;TAG LATIN SMALL LETTER Y;Cf;0;BN;;;;;N;;;;; E007A;TAG LATIN SMALL LETTER Z;Cf;0;BN;;;;;N;;;;; E007B;TAG LEFT CURLY BRACKET;Cf;0;BN;;;;;N;;;;; E007C;TAG VERTICAL LINE;Cf;0;BN;;;;;N;;;;; E007D;TAG RIGHT CURLY BRACKET;Cf;0;BN;;;;;N;;;;; E007E;TAG TILDE;Cf;0;BN;;;;;N;;;;; E007F;CANCEL TAG;Cf;0;BN;;;;;N;;;;; E0100;VARIATION SELECTOR-17;Mn;0;NSM;;;;;N;;;;; E0101;VARIATION SELECTOR-18;Mn;0;NSM;;;;;N;;;;; E0102;VARIATION SELECTOR-19;Mn;0;NSM;;;;;N;;;;; E0103;VARIATION SELECTOR-20;Mn;0;NSM;;;;;N;;;;; E0104;VARIATION SELECTOR-21;Mn;0;NSM;;;;;N;;;;; E0105;VARIATION SELECTOR-22;Mn;0;NSM;;;;;N;;;;; E0106;VARIATION SELECTOR-23;Mn;0;NSM;;;;;N;;;;; E0107;VARIATION SELECTOR-24;Mn;0;NSM;;;;;N;;;;; E0108;VARIATION SELECTOR-25;Mn;0;NSM;;;;;N;;;;; E0109;VARIATION SELECTOR-26;Mn;0;NSM;;;;;N;;;;; E010A;VARIATION SELECTOR-27;Mn;0;NSM;;;;;N;;;;; E010B;VARIATION SELECTOR-28;Mn;0;NSM;;;;;N;;;;; E010C;VARIATION SELECTOR-29;Mn;0;NSM;;;;;N;;;;; E010D;VARIATION SELECTOR-30;Mn;0;NSM;;;;;N;;;;; E010E;VARIATION SELECTOR-31;Mn;0;NSM;;;;;N;;;;; E010F;VARIATION SELECTOR-32;Mn;0;NSM;;;;;N;;;;; E0110;VARIATION SELECTOR-33;Mn;0;NSM;;;;;N;;;;; E0111;VARIATION SELECTOR-34;Mn;0;NSM;;;;;N;;;;; E0112;VARIATION SELECTOR-35;Mn;0;NSM;;;;;N;;;;; E0113;VARIATION SELECTOR-36;Mn;0;NSM;;;;;N;;;;; E0114;VARIATION SELECTOR-37;Mn;0;NSM;;;;;N;;;;; E0115;VARIATION SELECTOR-38;Mn;0;NSM;;;;;N;;;;; E0116;VARIATION SELECTOR-39;Mn;0;NSM;;;;;N;;;;; E0117;VARIATION SELECTOR-40;Mn;0;NSM;;;;;N;;;;; E0118;VARIATION SELECTOR-41;Mn;0;NSM;;;;;N;;;;; E0119;VARIATION SELECTOR-42;Mn;0;NSM;;;;;N;;;;; E011A;VARIATION SELECTOR-43;Mn;0;NSM;;;;;N;;;;; E011B;VARIATION SELECTOR-44;Mn;0;NSM;;;;;N;;;;; E011C;VARIATION SELECTOR-45;Mn;0;NSM;;;;;N;;;;; E011D;VARIATION SELECTOR-46;Mn;0;NSM;;;;;N;;;;; E011E;VARIATION SELECTOR-47;Mn;0;NSM;;;;;N;;;;; E011F;VARIATION SELECTOR-48;Mn;0;NSM;;;;;N;;;;; E0120;VARIATION SELECTOR-49;Mn;0;NSM;;;;;N;;;;; E0121;VARIATION SELECTOR-50;Mn;0;NSM;;;;;N;;;;; E0122;VARIATION SELECTOR-51;Mn;0;NSM;;;;;N;;;;; E0123;VARIATION SELECTOR-52;Mn;0;NSM;;;;;N;;;;; E0124;VARIATION SELECTOR-53;Mn;0;NSM;;;;;N;;;;; E0125;VARIATION SELECTOR-54;Mn;0;NSM;;;;;N;;;;; E0126;VARIATION SELECTOR-55;Mn;0;NSM;;;;;N;;;;; E0127;VARIATION SELECTOR-56;Mn;0;NSM;;;;;N;;;;; E0128;VARIATION SELECTOR-57;Mn;0;NSM;;;;;N;;;;; E0129;VARIATION SELECTOR-58;Mn;0;NSM;;;;;N;;;;; E012A;VARIATION SELECTOR-59;Mn;0;NSM;;;;;N;;;;; E012B;VARIATION SELECTOR-60;Mn;0;NSM;;;;;N;;;;; E012C;VARIATION SELECTOR-61;Mn;0;NSM;;;;;N;;;;; E012D;VARIATION SELECTOR-62;Mn;0;NSM;;;;;N;;;;; E012E;VARIATION SELECTOR-63;Mn;0;NSM;;;;;N;;;;; E012F;VARIATION SELECTOR-64;Mn;0;NSM;;;;;N;;;;; E0130;VARIATION SELECTOR-65;Mn;0;NSM;;;;;N;;;;; E0131;VARIATION SELECTOR-66;Mn;0;NSM;;;;;N;;;;; E0132;VARIATION SELECTOR-67;Mn;0;NSM;;;;;N;;;;; E0133;VARIATION SELECTOR-68;Mn;0;NSM;;;;;N;;;;; E0134;VARIATION SELECTOR-69;Mn;0;NSM;;;;;N;;;;; E0135;VARIATION SELECTOR-70;Mn;0;NSM;;;;;N;;;;; E0136;VARIATION SELECTOR-71;Mn;0;NSM;;;;;N;;;;; E0137;VARIATION SELECTOR-72;Mn;0;NSM;;;;;N;;;;; E0138;VARIATION SELECTOR-73;Mn;0;NSM;;;;;N;;;;; E0139;VARIATION SELECTOR-74;Mn;0;NSM;;;;;N;;;;; E013A;VARIATION SELECTOR-75;Mn;0;NSM;;;;;N;;;;; E013B;VARIATION SELECTOR-76;Mn;0;NSM;;;;;N;;;;; E013C;VARIATION SELECTOR-77;Mn;0;NSM;;;;;N;;;;; E013D;VARIATION SELECTOR-78;Mn;0;NSM;;;;;N;;;;; E013E;VARIATION SELECTOR-79;Mn;0;NSM;;;;;N;;;;; E013F;VARIATION SELECTOR-80;Mn;0;NSM;;;;;N;;;;; E0140;VARIATION SELECTOR-81;Mn;0;NSM;;;;;N;;;;; E0141;VARIATION SELECTOR-82;Mn;0;NSM;;;;;N;;;;; E0142;VARIATION SELECTOR-83;Mn;0;NSM;;;;;N;;;;; E0143;VARIATION SELECTOR-84;Mn;0;NSM;;;;;N;;;;; E0144;VARIATION SELECTOR-85;Mn;0;NSM;;;;;N;;;;; E0145;VARIATION SELECTOR-86;Mn;0;NSM;;;;;N;;;;; E0146;VARIATION SELECTOR-87;Mn;0;NSM;;;;;N;;;;; E0147;VARIATION SELECTOR-88;Mn;0;NSM;;;;;N;;;;; E0148;VARIATION SELECTOR-89;Mn;0;NSM;;;;;N;;;;; E0149;VARIATION SELECTOR-90;Mn;0;NSM;;;;;N;;;;; E014A;VARIATION SELECTOR-91;Mn;0;NSM;;;;;N;;;;; E014B;VARIATION SELECTOR-92;Mn;0;NSM;;;;;N;;;;; E014C;VARIATION SELECTOR-93;Mn;0;NSM;;;;;N;;;;; E014D;VARIATION SELECTOR-94;Mn;0;NSM;;;;;N;;;;; E014E;VARIATION SELECTOR-95;Mn;0;NSM;;;;;N;;;;; E014F;VARIATION SELECTOR-96;Mn;0;NSM;;;;;N;;;;; E0150;VARIATION SELECTOR-97;Mn;0;NSM;;;;;N;;;;; E0151;VARIATION SELECTOR-98;Mn;0;NSM;;;;;N;;;;; E0152;VARIATION SELECTOR-99;Mn;0;NSM;;;;;N;;;;; E0153;VARIATION SELECTOR-100;Mn;0;NSM;;;;;N;;;;; E0154;VARIATION SELECTOR-101;Mn;0;NSM;;;;;N;;;;; E0155;VARIATION SELECTOR-102;Mn;0;NSM;;;;;N;;;;; E0156;VARIATION SELECTOR-103;Mn;0;NSM;;;;;N;;;;; E0157;VARIATION SELECTOR-104;Mn;0;NSM;;;;;N;;;;; E0158;VARIATION SELECTOR-105;Mn;0;NSM;;;;;N;;;;; E0159;VARIATION SELECTOR-106;Mn;0;NSM;;;;;N;;;;; E015A;VARIATION SELECTOR-107;Mn;0;NSM;;;;;N;;;;; E015B;VARIATION SELECTOR-108;Mn;0;NSM;;;;;N;;;;; E015C;VARIATION SELECTOR-109;Mn;0;NSM;;;;;N;;;;; E015D;VARIATION SELECTOR-110;Mn;0;NSM;;;;;N;;;;; E015E;VARIATION SELECTOR-111;Mn;0;NSM;;;;;N;;;;; E015F;VARIATION SELECTOR-112;Mn;0;NSM;;;;;N;;;;; E0160;VARIATION SELECTOR-113;Mn;0;NSM;;;;;N;;;;; E0161;VARIATION SELECTOR-114;Mn;0;NSM;;;;;N;;;;; E0162;VARIATION SELECTOR-115;Mn;0;NSM;;;;;N;;;;; E0163;VARIATION SELECTOR-116;Mn;0;NSM;;;;;N;;;;; E0164;VARIATION SELECTOR-117;Mn;0;NSM;;;;;N;;;;; E0165;VARIATION SELECTOR-118;Mn;0;NSM;;;;;N;;;;; E0166;VARIATION SELECTOR-119;Mn;0;NSM;;;;;N;;;;; E0167;VARIATION SELECTOR-120;Mn;0;NSM;;;;;N;;;;; E0168;VARIATION SELECTOR-121;Mn;0;NSM;;;;;N;;;;; E0169;VARIATION SELECTOR-122;Mn;0;NSM;;;;;N;;;;; E016A;VARIATION SELECTOR-123;Mn;0;NSM;;;;;N;;;;; E016B;VARIATION SELECTOR-124;Mn;0;NSM;;;;;N;;;;; E016C;VARIATION SELECTOR-125;Mn;0;NSM;;;;;N;;;;; E016D;VARIATION SELECTOR-126;Mn;0;NSM;;;;;N;;;;; E016E;VARIATION SELECTOR-127;Mn;0;NSM;;;;;N;;;;; E016F;VARIATION SELECTOR-128;Mn;0;NSM;;;;;N;;;;; E0170;VARIATION SELECTOR-129;Mn;0;NSM;;;;;N;;;;; E0171;VARIATION SELECTOR-130;Mn;0;NSM;;;;;N;;;;; E0172;VARIATION SELECTOR-131;Mn;0;NSM;;;;;N;;;;; E0173;VARIATION SELECTOR-132;Mn;0;NSM;;;;;N;;;;; E0174;VARIATION SELECTOR-133;Mn;0;NSM;;;;;N;;;;; E0175;VARIATION SELECTOR-134;Mn;0;NSM;;;;;N;;;;; E0176;VARIATION SELECTOR-135;Mn;0;NSM;;;;;N;;;;; E0177;VARIATION SELECTOR-136;Mn;0;NSM;;;;;N;;;;; E0178;VARIATION SELECTOR-137;Mn;0;NSM;;;;;N;;;;; E0179;VARIATION SELECTOR-138;Mn;0;NSM;;;;;N;;;;; E017A;VARIATION SELECTOR-139;Mn;0;NSM;;;;;N;;;;; E017B;VARIATION SELECTOR-140;Mn;0;NSM;;;;;N;;;;; E017C;VARIATION SELECTOR-141;Mn;0;NSM;;;;;N;;;;; E017D;VARIATION SELECTOR-142;Mn;0;NSM;;;;;N;;;;; E017E;VARIATION SELECTOR-143;Mn;0;NSM;;;;;N;;;;; E017F;VARIATION SELECTOR-144;Mn;0;NSM;;;;;N;;;;; E0180;VARIATION SELECTOR-145;Mn;0;NSM;;;;;N;;;;; E0181;VARIATION SELECTOR-146;Mn;0;NSM;;;;;N;;;;; E0182;VARIATION SELECTOR-147;Mn;0;NSM;;;;;N;;;;; E0183;VARIATION SELECTOR-148;Mn;0;NSM;;;;;N;;;;; E0184;VARIATION SELECTOR-149;Mn;0;NSM;;;;;N;;;;; E0185;VARIATION SELECTOR-150;Mn;0;NSM;;;;;N;;;;; E0186;VARIATION SELECTOR-151;Mn;0;NSM;;;;;N;;;;; E0187;VARIATION SELECTOR-152;Mn;0;NSM;;;;;N;;;;; E0188;VARIATION SELECTOR-153;Mn;0;NSM;;;;;N;;;;; E0189;VARIATION SELECTOR-154;Mn;0;NSM;;;;;N;;;;; E018A;VARIATION SELECTOR-155;Mn;0;NSM;;;;;N;;;;; E018B;VARIATION SELECTOR-156;Mn;0;NSM;;;;;N;;;;; E018C;VARIATION SELECTOR-157;Mn;0;NSM;;;;;N;;;;; E018D;VARIATION SELECTOR-158;Mn;0;NSM;;;;;N;;;;; E018E;VARIATION SELECTOR-159;Mn;0;NSM;;;;;N;;;;; E018F;VARIATION SELECTOR-160;Mn;0;NSM;;;;;N;;;;; E0190;VARIATION SELECTOR-161;Mn;0;NSM;;;;;N;;;;; E0191;VARIATION SELECTOR-162;Mn;0;NSM;;;;;N;;;;; E0192;VARIATION SELECTOR-163;Mn;0;NSM;;;;;N;;;;; E0193;VARIATION SELECTOR-164;Mn;0;NSM;;;;;N;;;;; E0194;VARIATION SELECTOR-165;Mn;0;NSM;;;;;N;;;;; E0195;VARIATION SELECTOR-166;Mn;0;NSM;;;;;N;;;;; E0196;VARIATION SELECTOR-167;Mn;0;NSM;;;;;N;;;;; E0197;VARIATION SELECTOR-168;Mn;0;NSM;;;;;N;;;;; E0198;VARIATION SELECTOR-169;Mn;0;NSM;;;;;N;;;;; E0199;VARIATION SELECTOR-170;Mn;0;NSM;;;;;N;;;;; E019A;VARIATION SELECTOR-171;Mn;0;NSM;;;;;N;;;;; E019B;VARIATION SELECTOR-172;Mn;0;NSM;;;;;N;;;;; E019C;VARIATION SELECTOR-173;Mn;0;NSM;;;;;N;;;;; E019D;VARIATION SELECTOR-174;Mn;0;NSM;;;;;N;;;;; E019E;VARIATION SELECTOR-175;Mn;0;NSM;;;;;N;;;;; E019F;VARIATION SELECTOR-176;Mn;0;NSM;;;;;N;;;;; E01A0;VARIATION SELECTOR-177;Mn;0;NSM;;;;;N;;;;; E01A1;VARIATION SELECTOR-178;Mn;0;NSM;;;;;N;;;;; E01A2;VARIATION SELECTOR-179;Mn;0;NSM;;;;;N;;;;; E01A3;VARIATION SELECTOR-180;Mn;0;NSM;;;;;N;;;;; E01A4;VARIATION SELECTOR-181;Mn;0;NSM;;;;;N;;;;; E01A5;VARIATION SELECTOR-182;Mn;0;NSM;;;;;N;;;;; E01A6;VARIATION SELECTOR-183;Mn;0;NSM;;;;;N;;;;; E01A7;VARIATION SELECTOR-184;Mn;0;NSM;;;;;N;;;;; E01A8;VARIATION SELECTOR-185;Mn;0;NSM;;;;;N;;;;; E01A9;VARIATION SELECTOR-186;Mn;0;NSM;;;;;N;;;;; E01AA;VARIATION SELECTOR-187;Mn;0;NSM;;;;;N;;;;; E01AB;VARIATION SELECTOR-188;Mn;0;NSM;;;;;N;;;;; E01AC;VARIATION SELECTOR-189;Mn;0;NSM;;;;;N;;;;; E01AD;VARIATION SELECTOR-190;Mn;0;NSM;;;;;N;;;;; E01AE;VARIATION SELECTOR-191;Mn;0;NSM;;;;;N;;;;; E01AF;VARIATION SELECTOR-192;Mn;0;NSM;;;;;N;;;;; E01B0;VARIATION SELECTOR-193;Mn;0;NSM;;;;;N;;;;; E01B1;VARIATION SELECTOR-194;Mn;0;NSM;;;;;N;;;;; E01B2;VARIATION SELECTOR-195;Mn;0;NSM;;;;;N;;;;; E01B3;VARIATION SELECTOR-196;Mn;0;NSM;;;;;N;;;;; E01B4;VARIATION SELECTOR-197;Mn;0;NSM;;;;;N;;;;; E01B5;VARIATION SELECTOR-198;Mn;0;NSM;;;;;N;;;;; E01B6;VARIATION SELECTOR-199;Mn;0;NSM;;;;;N;;;;; E01B7;VARIATION SELECTOR-200;Mn;0;NSM;;;;;N;;;;; E01B8;VARIATION SELECTOR-201;Mn;0;NSM;;;;;N;;;;; E01B9;VARIATION SELECTOR-202;Mn;0;NSM;;;;;N;;;;; E01BA;VARIATION SELECTOR-203;Mn;0;NSM;;;;;N;;;;; E01BB;VARIATION SELECTOR-204;Mn;0;NSM;;;;;N;;;;; E01BC;VARIATION SELECTOR-205;Mn;0;NSM;;;;;N;;;;; E01BD;VARIATION SELECTOR-206;Mn;0;NSM;;;;;N;;;;; E01BE;VARIATION SELECTOR-207;Mn;0;NSM;;;;;N;;;;; E01BF;VARIATION SELECTOR-208;Mn;0;NSM;;;;;N;;;;; E01C0;VARIATION SELECTOR-209;Mn;0;NSM;;;;;N;;;;; E01C1;VARIATION SELECTOR-210;Mn;0;NSM;;;;;N;;;;; E01C2;VARIATION SELECTOR-211;Mn;0;NSM;;;;;N;;;;; E01C3;VARIATION SELECTOR-212;Mn;0;NSM;;;;;N;;;;; E01C4;VARIATION SELECTOR-213;Mn;0;NSM;;;;;N;;;;; E01C5;VARIATION SELECTOR-214;Mn;0;NSM;;;;;N;;;;; E01C6;VARIATION SELECTOR-215;Mn;0;NSM;;;;;N;;;;; E01C7;VARIATION SELECTOR-216;Mn;0;NSM;;;;;N;;;;; E01C8;VARIATION SELECTOR-217;Mn;0;NSM;;;;;N;;;;; E01C9;VARIATION SELECTOR-218;Mn;0;NSM;;;;;N;;;;; E01CA;VARIATION SELECTOR-219;Mn;0;NSM;;;;;N;;;;; E01CB;VARIATION SELECTOR-220;Mn;0;NSM;;;;;N;;;;; E01CC;VARIATION SELECTOR-221;Mn;0;NSM;;;;;N;;;;; E01CD;VARIATION SELECTOR-222;Mn;0;NSM;;;;;N;;;;; E01CE;VARIATION SELECTOR-223;Mn;0;NSM;;;;;N;;;;; E01CF;VARIATION SELECTOR-224;Mn;0;NSM;;;;;N;;;;; E01D0;VARIATION SELECTOR-225;Mn;0;NSM;;;;;N;;;;; E01D1;VARIATION SELECTOR-226;Mn;0;NSM;;;;;N;;;;; E01D2;VARIATION SELECTOR-227;Mn;0;NSM;;;;;N;;;;; E01D3;VARIATION SELECTOR-228;Mn;0;NSM;;;;;N;;;;; E01D4;VARIATION SELECTOR-229;Mn;0;NSM;;;;;N;;;;; E01D5;VARIATION SELECTOR-230;Mn;0;NSM;;;;;N;;;;; E01D6;VARIATION SELECTOR-231;Mn;0;NSM;;;;;N;;;;; E01D7;VARIATION SELECTOR-232;Mn;0;NSM;;;;;N;;;;; E01D8;VARIATION SELECTOR-233;Mn;0;NSM;;;;;N;;;;; E01D9;VARIATION SELECTOR-234;Mn;0;NSM;;;;;N;;;;; E01DA;VARIATION SELECTOR-235;Mn;0;NSM;;;;;N;;;;; E01DB;VARIATION SELECTOR-236;Mn;0;NSM;;;;;N;;;;; E01DC;VARIATION SELECTOR-237;Mn;0;NSM;;;;;N;;;;; E01DD;VARIATION SELECTOR-238;Mn;0;NSM;;;;;N;;;;; E01DE;VARIATION SELECTOR-239;Mn;0;NSM;;;;;N;;;;; E01DF;VARIATION SELECTOR-240;Mn;0;NSM;;;;;N;;;;; E01E0;VARIATION SELECTOR-241;Mn;0;NSM;;;;;N;;;;; E01E1;VARIATION SELECTOR-242;Mn;0;NSM;;;;;N;;;;; E01E2;VARIATION SELECTOR-243;Mn;0;NSM;;;;;N;;;;; E01E3;VARIATION SELECTOR-244;Mn;0;NSM;;;;;N;;;;; E01E4;VARIATION SELECTOR-245;Mn;0;NSM;;;;;N;;;;; E01E5;VARIATION SELECTOR-246;Mn;0;NSM;;;;;N;;;;; E01E6;VARIATION SELECTOR-247;Mn;0;NSM;;;;;N;;;;; E01E7;VARIATION SELECTOR-248;Mn;0;NSM;;;;;N;;;;; E01E8;VARIATION SELECTOR-249;Mn;0;NSM;;;;;N;;;;; E01E9;VARIATION SELECTOR-250;Mn;0;NSM;;;;;N;;;;; E01EA;VARIATION SELECTOR-251;Mn;0;NSM;;;;;N;;;;; E01EB;VARIATION SELECTOR-252;Mn;0;NSM;;;;;N;;;;; E01EC;VARIATION SELECTOR-253;Mn;0;NSM;;;;;N;;;;; E01ED;VARIATION SELECTOR-254;Mn;0;NSM;;;;;N;;;;; E01EE;VARIATION SELECTOR-255;Mn;0;NSM;;;;;N;;;;; E01EF;VARIATION SELECTOR-256;Mn;0;NSM;;;;;N;;;;; F0000;;Co;0;L;;;;;N;;;;; FFFFD;;Co;0;L;;;;;N;;;;; 100000;;Co;0;L;;;;;N;;;;; 10FFFD;;Co;0;L;;;;;N;;;;; cyrus-imapd-2.5.10/lib/charset/windows-1258.t0000644000175000017500000002174613001236020015425 00000000000000# # Copyright (c) 1994-2014 Carnegie Mellon University. All rights reserved. # # Redistribution and use in source and binary forms, with or without # modification, are permitted provided that the following conditions # are met: # # 1. Redistributions of source code must retain the above copyright # notice, this list of conditions and the following disclaimer. # # 2. Redistributions in binary form must reproduce the above copyright # notice, this list of conditions and the following disclaimer in # the documentation and/or other materials provided with the # distribution. # # 3. The name "Carnegie Mellon University" must not be used to # endorse or promote products derived from this software without # prior written permission. For permission or any legal # details, please contact # Carnegie Mellon University # Center for Technology Transfer and Enterprise Creation # 4615 Forbes Avenue # Suite 302 # Pittsburgh, PA 15213 # (412) 268-7393, fax: (412) 268-7395 # innovation@andrew.cmu.edu # # 4. Redistributions of any form whatsoever must retain the following # acknowledgment: # "This product includes software developed by Computing Services # at Carnegie Mellon University (http://www.cmu.edu/computing/)." # # CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO # THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY # AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE # FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES # WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN # AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING # OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. # # Charset put together by Bron Gondwana # Reference: http://msdn.microsoft.com/en-us/goglobal/cc305151 00 0000 NULL 01 0001 START OF HEADING 02 0002 START OF TEXT 03 0003 END OF TEXT 04 0004 END OF TRANSMISSION 05 0005 ENQUIRY 06 0006 ACKNOWLEDGE 07 0007 BELL 08 0008 BACKSPACE 09 0009 HORIZONTAL TABULATION 0A 000A LINE FEED 0B 000B VERTICAL TABULATION 0C 000C FORM FEED 0D 000D CARRIAGE RETURN 0E 000E SHIFT OUT 0F 000F SHIFT IN 10 0010 DATA LINK ESCAPE 11 0011 DEVICE CONTROL ONE 12 0012 DEVICE CONTROL TWO 13 0013 DEVICE CONTROL THREE 14 0014 DEVICE CONTROL FOUR 15 0015 NEGATIVE ACKNOWLEDGE 16 0016 SYNCHRONOUS IDLE 17 0017 END OF TRANSMISSION BLOCK 18 0018 CANCEL 19 0019 END OF MEDIUM 1A 001A SUBSTITUTE 1B 001B ESCAPE 1C 001C FILE SEPARATOR 1D 001D GROUP SEPARATOR 1E 001E RECORD SEPARATOR 1F 001F UNIT SEPARATOR 20 0020 SPACE 21 0021 EXCLAMATION MARK 22 0022 QUOTATION MARK 23 0023 NUMBER SIGN 24 0024 DOLLAR SIGN 25 0025 PERCENT SIGN 26 0026 AMPERSAND 27 0027 APOSTROPHE 28 0028 LEFT PARENTHESIS 29 0029 RIGHT PARENTHESIS 2A 002A ASTERISK 2B 002B PLUS SIGN 2C 002C COMMA 2D 002D HYPHEN-MINUS 2E 002E FULL STOP 2F 002F SOLIDUS 30 0030 DIGIT ZERO 31 0031 DIGIT ONE 32 0032 DIGIT TWO 33 0033 DIGIT THREE 34 0034 DIGIT FOUR 35 0035 DIGIT FIVE 36 0036 DIGIT SIX 37 0037 DIGIT SEVEN 38 0038 DIGIT EIGHT 39 0039 DIGIT NINE 3A 003A COLON 3B 003B SEMICOLON 3C 003C LESS-THAN SIGN 3D 003D EQUALS SIGN 3E 003E GREATER-THAN SIGN 3F 003F QUESTION MARK 40 0040 COMMERCIAL AT 41 0041 LATIN CAPITAL LETTER A 42 0042 LATIN CAPITAL LETTER B 43 0043 LATIN CAPITAL LETTER C 44 0044 LATIN CAPITAL LETTER D 45 0045 LATIN CAPITAL LETTER E 46 0046 LATIN CAPITAL LETTER F 47 0047 LATIN CAPITAL LETTER G 48 0048 LATIN CAPITAL LETTER H 49 0049 LATIN CAPITAL LETTER I 4A 004A LATIN CAPITAL LETTER J 4B 004B LATIN CAPITAL LETTER K 4C 004C LATIN CAPITAL LETTER L 4D 004D LATIN CAPITAL LETTER M 4E 004E LATIN CAPITAL LETTER N 4F 004F LATIN CAPITAL LETTER O 50 0050 LATIN CAPITAL LETTER P 51 0051 LATIN CAPITAL LETTER Q 52 0052 LATIN CAPITAL LETTER R 53 0053 LATIN CAPITAL LETTER S 54 0054 LATIN CAPITAL LETTER T 55 0055 LATIN CAPITAL LETTER U 56 0056 LATIN CAPITAL LETTER V 57 0057 LATIN CAPITAL LETTER W 58 0058 LATIN CAPITAL LETTER X 59 0059 LATIN CAPITAL LETTER Y 5A 005A LATIN CAPITAL LETTER Z 5B 005B LEFT SQUARE BRACKET 5C 005C REVERSE SOLIDUS 5D 005D RIGHT SQUARE BRACKET 5E 005E CIRCUMFLEX ACCENT 5F 005F LOW LINE 60 0060 GRAVE ACCENT 61 0061 LATIN SMALL LETTER A 62 0062 LATIN SMALL LETTER B 63 0063 LATIN SMALL LETTER C 64 0064 LATIN SMALL LETTER D 65 0065 LATIN SMALL LETTER E 66 0066 LATIN SMALL LETTER F 67 0067 LATIN SMALL LETTER G 68 0068 LATIN SMALL LETTER H 69 0069 LATIN SMALL LETTER I 6A 006A LATIN SMALL LETTER J 6B 006B LATIN SMALL LETTER K 6C 006C LATIN SMALL LETTER L 6D 006D LATIN SMALL LETTER M 6E 006E LATIN SMALL LETTER N 6F 006F LATIN SMALL LETTER O 70 0070 LATIN SMALL LETTER P 71 0071 LATIN SMALL LETTER Q 72 0072 LATIN SMALL LETTER R 73 0073 LATIN SMALL LETTER S 74 0074 LATIN SMALL LETTER T 75 0075 LATIN SMALL LETTER U 76 0076 LATIN SMALL LETTER V 77 0077 LATIN SMALL LETTER W 78 0078 LATIN SMALL LETTER X 79 0079 LATIN SMALL LETTER Y 7A 007A LATIN SMALL LETTER Z 7B 007B LEFT CURLY BRACKET 7C 007C VERTICAL LINE 7D 007D RIGHT CURLY BRACKET 7E 007E TILDE 7F 007F DELETE 80 20AC EURO SIGN 82 201A SINGLE LOW-9 QUOTATION MARK 83 0192 LATIN SMALL LETTER F WITH HOOK 84 201E DOUBLE LOW-9 QUOTATION MARK 85 2026 HORIZONTAL ELLIPSIS 86 2020 DAGGER 87 2021 DOUBLE DAGGER 88 02C6 MODIFIER LETTER CIRCUMFLEX ACCENT 89 2030 PER MILLE SIGN 8B 2039 SINGLE LEFT-POINTING ANGLE QUOTATION MARK 8C 0152 LATIN CAPITAL LIGATURE OE 91 2018 LEFT SINGLE QUOTATION MARK 92 2019 RIGHT SINGLE QUOTATION MARK 93 201C LEFT DOUBLE QUOTATION MARK 94 201D RIGHT DOUBLE QUOTATION MARK 95 2022 BULLET 96 2013 EN DASH 97 2014 EM DASH 98 02DC SMALL TILDE 99 2122 TRADE MARK SIGN 9B 203A SINGLE RIGHT-POINTING ANGLE QUOTATION MARK 9C 0153 LATIN SMALL LIGATURE OE 9F 0178 LATIN CAPITAL LETTER Y WITH DIAERESIS A0 00A0 NO-BREAK SPACE A1 00A1 INVERTED EXCLAMATION MARK A2 00A2 CENT SIGN A3 00A3 POUND SIGN A4 00A4 CURRENCY SIGN A5 00A5 YEN SIGN A6 00A6 BROKEN BAR A7 00A7 SECTION SIGN A8 00A8 DIAERESIS A9 00A9 COPYRIGHT SIGN AA 00AA FEMININE ORDINAL INDICATOR AB 00AB LEFT-POINTING DOUBLE ANGLE QUOTATION MARK AC 00AC NOT SIGN AD 00AD SOFT HYPHEN AE 00AE REGISTERED SIGN AF 00AF MACRON B0 00B0 DEGREE SIGN B1 00B1 PLUS-MINUS SIGN B2 00B2 SUPERSCRIPT TWO B3 00B3 SUPERSCRIPT THREE B4 00B4 ACUTE ACCENT B5 00B5 MICRO SIGN B6 00B6 PILCROW SIGN B7 00B7 MIDDLE DOT B8 00B8 CEDILLA B9 00B9 SUPERSCRIPT ONE BA 00BA MASCULINE ORDINAL INDICATOR BB 00BB RIGHT-POINTING DOUBLE ANGLE QUOTATION MARK BC 00BC VULGAR FRACTION ONE QUARTER BD 00BD VULGAR FRACTION ONE HALF BE 00BE VULGAR FRACTION THREE QUARTERS BF 00BF INVERTED QUESTION MARK C0 00C0 LATIN CAPITAL LETTER A WITH GRAVE C1 00C1 LATIN CAPITAL LETTER A WITH ACUTE C2 00C2 LATIN CAPITAL LETTER A WITH CIRCUMFLEX C3 0102 LATIN CAPITAL LETTER A WITH BREVE C4 00C4 LATIN CAPITAL LETTER A WITH DIAERESIS C5 00C5 LATIN CAPITAL LETTER A WITH RING ABOVE C6 00C6 LATIN CAPITAL LETTER AE C7 00C7 LATIN CAPITAL LETTER C WITH CEDILLA C8 00C8 LATIN CAPITAL LETTER E WITH GRAVE C9 00C9 LATIN CAPITAL LETTER E WITH ACUTE CA 00CA LATIN CAPITAL LETTER E WITH CIRCUMFLEX CB 00CB LATIN CAPITAL LETTER E WITH DIAERESIS CC 0300 COMBINING GRAVE ACCENT CD 00CD LATIN CAPITAL LETTER I WITH ACUTE CE 00CE LATIN CAPITAL LETTER I WITH CIRCUMFLEX CF 00CF LATIN CAPITAL LETTER I WITH DIAERESIS D0 0110 LATIN CAPITAL LETTER D WITH STROKE D1 00D1 LATIN CAPITAL LETTER N WITH TILDE D2 0309 COMBINING HOOK ABOVE D3 00D3 LATIN CAPITAL LETTER O WITH ACUTE D4 00D4 LATIN CAPITAL LETTER O WITH CIRCUMFLEX D5 01A0 LATIN CAPITAL LETTER O WITH HORN D6 00D6 LATIN CAPITAL LETTER O WITH DIAERESIS D7 00D7 MULTIPLICATION SIGN D8 00D8 LATIN CAPITAL LETTER O WITH STROKE D9 00D9 LATIN CAPITAL LETTER U WITH GRAVE DA 00DA LATIN CAPITAL LETTER U WITH ACUTE DB 00DB LATIN CAPITAL LETTER U WITH CIRCUMFLEX DC 00DC LATIN CAPITAL LETTER U WITH DIAERESIS DD 01AF LATIN CAPITAL LETTER U WITH HORN DE 0303 COMBINING TILDE DF 00DF LATIN SMALL LETTER SHARP S E0 00E0 LATIN SMALL LETTER A WITH GRAVE E1 00E1 LATIN SMALL LETTER A WITH ACUTE E2 00E2 LATIN SMALL LETTER A WITH CIRCUMFLEX E3 0103 LATIN SMALL LETTER A WITH BREVE E4 00E4 LATIN SMALL LETTER A WITH DIAERESIS E5 00E5 LATIN SMALL LETTER A WITH RING ABOVE E6 00E6 LATIN SMALL LETTER AE E7 00E7 LATIN SMALL LETTER C WITH CEDILLA E8 00E8 LATIN SMALL LETTER E WITH GRAVE E9 00E9 LATIN SMALL LETTER E WITH ACUTE EA 00EA LATIN SMALL LETTER E WITH CIRCUMFLEX EB 00EB LATIN SMALL LETTER E WITH DIAERESIS EC 0301 COMBINING ACUTE ACCENT ED 00ED LATIN SMALL LETTER I WITH ACUTE EE 00EE LATIN SMALL LETTER I WITH CIRCUMFLEX EF 00EF LATIN SMALL LETTER I WITH DIAERESIS F0 0111 LATIN SMALL LETTER D WITH STROKE F1 00F1 LATIN SMALL LETTER N WITH TILDE F2 0323 COMBINING DOT BELOW F3 00F3 LATIN SMALL LETTER O WITH ACUTE F4 00F4 LATIN SMALL LETTER O WITH CIRCUMFLEX F5 01A1 LATIN SMALL LETTER O WITH HORN F6 00F6 LATIN SMALL LETTER O WITH DIAERESIS F7 00F7 DIVISION SIGN F8 00F8 LATIN SMALL LETTER O WITH STROKE F9 00F9 LATIN SMALL LETTER U WITH GRAVE FA 00FA LATIN SMALL LETTER U WITH ACUTE FB 00FB LATIN SMALL LETTER U WITH CIRCUMFLEX FC 00FC LATIN SMALL LETTER U WITH DIAERESIS FD 01B0 LATIN SMALL LETTER U WITH HORN FE 20AB DONG SIGN FF 00FF LATIN SMALL LETTER Y WITH DIAERESIS cyrus-imapd-2.5.10/lib/charset/aliases.txt0000644000175000017500000000436013001236020015324 00000000000000# funky names for UTF charsets utf8 utf-8 utf7 utf-7 unicode-1-1-utf-8 utf-8 # even ASCII is not exempt ascii us-ascii ANSI_X3.4-1968 us-ascii # Yes, the world does contain a lot of rubbish # ways of saying iso-8859-1 ISO_8859_1 iso-8859-1 ISO_8859 iso-8859-1 ISO-8859 iso-8859-1 8859_1 iso-8859-1 so-8859-1 iso-8859-1 x-mac-roman iso-8859-1 macintosh iso-8859-1 mac iso-8859-1 en_GB iso-8859-1 auto iso-8859-1 unknown iso-8859-1 unknown-8bit iso-8859-1 x-unknown iso-8859-1 x-user-defined iso-8859-1 none iso-8859-1 latin1 iso-8859-1 ISO8859-1 iso-8859-1 8859-1 iso-8859-1 DISPLAY iso-8859-1 Any iso-8859-1 # sort-of - see Filter::Trigraph 646 iso-8859-1 ISO646-US iso-8859-1 # other aliases 8859_2 iso-8859-2 x-mac-turkish iso-8859-9 greek-ccitt iso-8859-7 iso-8859-8-i iso-8859-8 ISO8859_15_FDIS iso-8859-15 ISO8859-15 iso-8859-15 tis-620 iso-8859-11 ASMO-708 iso-8859-6 WIN-KOI8 koi8-r # windows codepages - these are the ones we have 1250 windows-1250 cp1250 windows-1250 win-1250 windows-1250 1251 windows-1251 cp1251 windows-1251 win-1251 windows-1251 1252 windows-1252 cp1252 windows-1252 win-1252 windows-1252 1254 windows-1254 cp1254 windows-1254 win-1254 windows-1254 1255 windows-1255 cp1255 windows-1255 win-1255 windows-1255 1256 windows-1256 cp1256 windows-1256 win-1256 windows-1256 1258 windows-1258 cp1258 windows-1258 win-1258 windows-1258 # stuff from the FastMail Perl mapping that we # don't have support for in Cyrus #x-gbk gbk #UTS-16 UCS-2BE #gb2312 gbk #SHIFT_JIS shiftjis #ksc5601 ksc5601-raw #ks_c_5601 ksc5601-raw cyrus-imapd-2.5.10/lib/charset/big5.t0000644000175000017500000100560113001236020014155 00000000000000# # Name: BIG5 to Unicode table (complete) # Unicode version: 1.1 # Table version: 0.0d3 # Table format: Format A # Date: 11 February 1994 # Authors: Glenn Adams # John H. Jenkins # # Copyright (c) 1991-1994 Unicode, Inc. All Rights reserved. # # This file is provided as-is by Unicode, Inc. (The Unicode Consortium). # No claims are made as to fitness for any particular purpose. No # warranties of any kind are expressed or implied. The recipient # agrees to determine applicability of information provided. If this # file has been provided on magnetic media by Unicode, Inc., the sole # remedy for any claim will be exchange of defective media within 90 # days of receipt. # # Recipient is granted the right to make copies in any form for # internal distribution and to freely use the information supplied # in the creation of products supporting Unicode. Unicode, Inc. # specifically excludes the right to re-distribute this file directly # to third parties or other organizations whether for profit or not. # # General notes: # # This table contains the data Metis and Taligent currently have on how # BIG5 characters map into Unicode. # # WARNING! It is currently impossible to provide round-trip compatibility # between BIG5 and Unicode. # # A number of characters are not currently mapped because # of conflicts with other mappings. They are as follows: # # BIG5 Description Comments # # 0xA1C3 SPACING HEAVY OVERSCORE not in Unicode # 0xA1C5 SPACING HEAVY UNDERSCORE not in Unicode # # We currently map all of these characters to U+FFFD REPLACEMENT CHARACTER. # It is also possible to map these characters to their duplicates, or to # the user zone. # # Notes: # # 1. In addition to the above, there is some uncertainty about the # mappings in the range C6A1 - C8FE, and F9DD - F9FE. The ETEN # version of BIG5 organizes the former range differently, and adds # additional characters in the latter range. The correct mappings # these ranges need to be determined. # # 2. There is an uncertainty in the mapping of the Big Five character # 0xA3BC. This character occurs within the Big Five block of tone marks # for bopomofo and is intended to be the tone mark for the first tone in # Mandarin Chinese. We have selected the mapping U+02C9 MODIFIER LETTER # MACRON (Mandarin Chinese first tone) to reflect this semantic. # However, because bopomofo uses the absense of a tone mark to indicate # the first Mandarin tone, most implementations of Big Five represent # this character with a blank space, and so a mapping such as U+2003 EM SPACE # might be preferred. # # # # Format: Three tab-separated columns # Column #1 is the BIG5 code (in hex as 0xXXXX) # Column #2 is the Unicode (in hex as 0xXXXX) # Column #3 is the Unicode name (follows a comment sign, '#') # The official names for Unicode characters U+4E00 # to U+9FA5, inclusive, is "CJK UNIFIED IDEOGRAPH-XXXX", # where XXXX is the code point. Including all these # names in this file increases its size substantially # and needlessly. The token "" is used for the # name of these characters. If necessary, it can be # expanded algorithmically by a parser or editor. # # The entries are in BIG5 order # # Any comments or problems, contact # # 0 0000 NULL (NUL) 1 0001 START OF HEADING (SOH) 2 0002 START OF TEXT (STX) 3 0003 END OF TEXT (ETX) 4 0004 END OF TRANSMISSION (EOT) 5 0005 ENQUIRY (ENQ) 6 0006 ACKNOWLEDGE (ACK) 7 0007 BELL (BEL) 8 0008 BACKSPACE (BS) 9 0009 CHARACTER TABULATION (HT) A 000a LINE FEED (LF) B 000b LINE TABULATION (VT) C 000c FORM FEED (FF) D 000d CARRIAGE RETURN (CR) E 000e SHIFT OUT (SO) F 000f SHIFT IN (SI) 10 0010 DATALINK ESCAPE (DLE) 11 0011 DEVICE CONTROL ONE (DC1) 12 0012 DEVICE CONTROL TWO (DC2) 13 0013 DEVICE CONTROL THREE (DC3) 14 0014 DEVICE CONTROL FOUR (DC4) 15 0015 NEGATIVE ACKNOWLEDGE (NAK) 16 0016 SYNCRONOUS IDLE (SYN) 17 0017 END OF TRANSMISSION BLOCK (ETB) 18 0018 CANCEL (CAN) 19 0019 END OF MEDIUM (EM) 1A 001a SUBSTITUTE (SUB) 1B 001b ESCAPE (ESC) 1C 001c FILE SEPARATOR (IS4) 1D 001d GROUP SEPARATOR (IS3) 1E 001e RECORD SEPARATOR (IS2) 1F 001f UNIT SEPARATOR (IS1) 20 0020 SPACE 21 0021 EXCLAMATION MARK 22 0022 QUOTATION MARK 23 0023 NUMBER SIGN 24 0024 DOLLAR SIGN 25 0025 PERCENT SIGN 26 0026 AMPERSAND 27 0027 APOSTROPHE 28 0028 LEFT PARENTHESIS 29 0029 RIGHT PARENTHESIS 2A 002a ASTERISK 2B 002b PLUS SIGN 2C 002c COMMA 2D 002d HYPHEN-MINUS 2E 002e FULL STOP 2F 002f SOLIDUS 30 0030 DIGIT ZERO 31 0031 DIGIT ONE 32 0032 DIGIT TWO 33 0033 DIGIT THREE 34 0034 DIGIT FOUR 35 0035 DIGIT FIVE 36 0036 DIGIT SIX 37 0037 DIGIT SEVEN 38 0038 DIGIT EIGHT 39 0039 DIGIT NINE 3A 003a COLON 3B 003b SEMICOLON 3C 003c LESS-THAN SIGN 3D 003d EQUALS SIGN 3E 003e GREATER-THAN SIGN 3F 003f QUESTION MARK 40 0040 COMMERCIAL AT 41 0041 LATIN CAPITAL LETTER A 42 0042 LATIN CAPITAL LETTER B 43 0043 LATIN CAPITAL LETTER C 44 0044 LATIN CAPITAL LETTER D 45 0045 LATIN CAPITAL LETTER E 46 0046 LATIN CAPITAL LETTER F 47 0047 LATIN CAPITAL LETTER G 48 0048 LATIN CAPITAL LETTER H 49 0049 LATIN CAPITAL LETTER I 4A 004a LATIN CAPITAL LETTER J 4B 004b LATIN CAPITAL LETTER K 4C 004c LATIN CAPITAL LETTER L 4D 004d LATIN CAPITAL LETTER M 4E 004e LATIN CAPITAL LETTER N 4F 004f LATIN CAPITAL LETTER O 50 0050 LATIN CAPITAL LETTER P 51 0051 LATIN CAPITAL LETTER Q 52 0052 LATIN CAPITAL LETTER R 53 0053 LATIN CAPITAL LETTER S 54 0054 LATIN CAPITAL LETTER T 55 0055 LATIN CAPITAL LETTER U 56 0056 LATIN CAPITAL LETTER V 57 0057 LATIN CAPITAL LETTER W 58 0058 LATIN CAPITAL LETTER X 59 0059 LATIN CAPITAL LETTER Y 5A 005a LATIN CAPITAL LETTER Z 5B 005b LEFT SQUARE BRACKET 5C 005c REVERSE SOLIDUS 5D 005d RIGHT SQUARE BRACKET 5E 005e CIRCUMFLEX ACCENT 5F 005f LOW LINE 60 0060 GRAVE ACCENT 61 0061 LATIN SMALL LETTER A 62 0062 LATIN SMALL LETTER B 63 0063 LATIN SMALL LETTER C 64 0064 LATIN SMALL LETTER D 65 0065 LATIN SMALL LETTER E 66 0066 LATIN SMALL LETTER F 67 0067 LATIN SMALL LETTER G 68 0068 LATIN SMALL LETTER H 69 0069 LATIN SMALL LETTER I 6A 006a LATIN SMALL LETTER J 6B 006b LATIN SMALL LETTER K 6C 006c LATIN SMALL LETTER L 6D 006d LATIN SMALL LETTER M 6E 006e LATIN SMALL LETTER N 6F 006f LATIN SMALL LETTER O 70 0070 LATIN SMALL LETTER P 71 0071 LATIN SMALL LETTER Q 72 0072 LATIN SMALL LETTER R 73 0073 LATIN SMALL LETTER S 74 0074 LATIN SMALL LETTER T 75 0075 LATIN SMALL LETTER U 76 0076 LATIN SMALL LETTER V 77 0077 LATIN SMALL LETTER W 78 0078 LATIN SMALL LETTER X 79 0079 LATIN SMALL LETTER Y 7A 007a LATIN SMALL LETTER Z 7B 007b LEFT CURLY BRACKET 7C 007c VERTICAL LINE 7D 007d RIGHT CURLY BRACKET 7E 007e TILDE 7F 007f DELETE (DEL) A140 3000 # IDEOGRAPHIC SPACE A141 FF0C # FULLWIDTH COMMA A142 3001 # IDEOGRAPHIC COMMA A143 3002 # IDEOGRAPHIC FULL STOP A144 FF0E # FULLWIDTH FULL STOP A145 2022 # BULLET A146 FF1B # FULLWIDTH SEMICOLON A147 FF1A # FULLWIDTH COLON A148 FF1F # FULLWIDTH QUESTION MARK A149 FF01 # FULLWIDTH EXCLAMATION MARK A14A FE30 # PRESENTATION FORM FOR VERTICAL TWO DOT LEADER A14B 2026 # HORIZONTAL ELLIPSIS A14C 2025 # TWO DOT LEADER A14D FE50 # SMALL COMMA A14E FF64 # HALFWIDTH IDEOGRAPHIC COMMA A14F FE52 # SMALL FULL STOP A150 00B7 # MIDDLE DOT A151 FE54 # SMALL SEMICOLON A152 FE55 # SMALL COLON A153 FE56 # SMALL QUESTION MARK A154 FE57 # SMALL EXCLAMATION MARK A155 FF5C # FULLWIDTH VERTICAL BAR A156 2013 # EN DASH A157 FE31 # PRESENTATION FORM FOR VERTICAL EM DASH A158 2014 # EM DASH A159 FE33 # PRESENTATION FORM FOR VERTICAL LOW LINE A15A FF3F # SPACING UNDERSCORE duplicates A1C4 A15B FE34 # PRESENTATION FORM FOR VERTICAL WAVY LOW LINE A15C FE4F # WAVY LOW LINE A15D FF08 # FULLWIDTH LEFT PARENTHESIS A15E FF09 # FULLWIDTH RIGHT PARENTHESIS A15F FE35 # PRESENTATION FORM FOR VERTICAL LEFT PARENTHESIS A160 FE36 # PRESENTATION FORM FOR VERTICAL RIGHT PARENTHESIS A161 FF5B # FULLWIDTH LEFT CURLY BRACKET A162 FF5D # FULLWIDTH RIGHT CURLY BRACKET A163 FE37 # PRESENTATION FORM FOR VERTICAL LEFT CURLY BRACKET A164 FE38 # PRESENTATION FORM FOR VERTICAL RIGHT CURLY BRACKET A165 3014 # LEFT TORTOISE SHELL BRACKET A166 3015 # RIGHT TORTOISE SHELL BRACKET A167 FE39 # PRESENTATION FORM FOR VERTICAL LEFT TORTOISE SHELL BRACKET A168 FE3A # PRESENTATION FORM FOR VERTICAL RIGHT TORTOISE SHELL BRACKET A169 3010 # LEFT BLACK LENTICULAR BRACKET A16A 3011 # RIGHT BLACK LENTICULAR BRACKET A16B FE3B # PRESENTATION FORM FOR VERTICAL LEFT BLACK LENTICULAR BRACKET A16C FE3C # PRESENTATION FORM FOR VERTICAL RIGHT BLACK LENTICULAR BRACKET A16D 300A # LEFT DOUBLE ANGLE BRACKET A16E 300B # RIGHT DOUBLE ANGLE BRACKET A16F FE3D # PRESENTATION FORM FOR VERTICAL LEFT DOUBLE ANGLE BRACKET A170 FE3E # PRESENTATION FORM FOR VERTICAL RIGHT DOUBLE ANGLE BRACKET A171 3008 # LEFT ANGLE BRACKET A172 3009 # RIGHT ANGLE BRACKET A173 FE3F # PRESENTATION FORM FOR VERTICAL LEFT ANGLE BRACKET A174 FE40 # PRESENTATION FORM FOR VERTICAL RIGHT ANGLE BRACKET A175 300C # LEFT CORNER BRACKET A176 300D # RIGHT CORNER BRACKET A177 FE41 # PRESENTATION FORM FOR VERTICAL LEFT CORNER BRACKET A178 FE42 # PRESENTATION FORM FOR VERTICAL RIGHT CORNER BRACKET A179 300E # LEFT WHITE CORNER BRACKET A17A 300F # RIGHT WHITE CORNER BRACKET A17B FE43 # PRESENTATION FORM FOR VERTICAL LEFT WHITE CORNER BRACKET A17C FE44 # PRESENTATION FORM FOR VERTICAL RIGHT WHITE CORNER BRACKET A17D FE59 # SMALL LEFT PARENTHESIS A17E FE5A # SMALL RIGHT PARENTHESIS A1A1 FE5B # SMALL LEFT CURLY BRACKET A1A2 FE5C # SMALL RIGHT CURLY BRACKET A1A3 FE5D # SMALL LEFT TORTOISE SHELL BRACKET A1A4 FE5E # SMALL RIGHT TORTOISE SHELL BRACKET A1A5 2018 # LEFT SINGLE QUOTATION MARK A1A6 2019 # RIGHT SINGLE QUOTATION MARK A1A7 201C # LEFT DOUBLE QUOTATION MARK A1A8 201D # RIGHT DOUBLE QUOTATION MARK A1A9 301D # REVERSED DOUBLE PRIME QUOTATION MARK A1AA 301E # DOUBLE PRIME QUOTATION MARK A1AB 2035 # REVERSED PRIME A1AC 2032 # PRIME A1AD FF03 # FULLWIDTH NUMBER SIGN A1AE FF06 # FULLWIDTH AMPERSAND A1AF FF0A # FULLWIDTH ASTERISK A1B0 203B # REFERENCE MARK A1B1 00A7 # SECTION SIGN A1B2 3003 # DITTO MARK A1B3 25CB # WHITE CIRCLE A1B4 25CF # BLACK CIRCLE A1B5 25B3 # WHITE UP-POINTING TRIANGLE A1B6 25B2 # BLACK UP-POINTING TRIANGLE A1B7 25CE # BULLSEYE A1B8 2606 # WHITE STAR A1B9 2605 # BLACK STAR A1BA 25C7 # WHITE DIAMOND A1BB 25C6 # BLACK DIAMOND A1BC 25A1 # WHITE SQUARE A1BD 25A0 # BLACK SQUARE A1BE 25BD # WHITE DOWN-POINTING TRIANGLE A1BF 25BC # BLACK DOWN-POINTING TRIANGLE A1C0 32A3 # CIRCLED IDEOGRAPH CORRECT A1C1 2105 # CARE OF A1C2 203E # OVERLINE A1C3 FFFD # *** NO MAPPING *** A1C4 FF3F # FULLWIDTH LOW LINE A1C5 FFFD # *** NO MAPPING *** A1C6 FE49 # DASHED OVERLINE A1C7 FE4A # CENTRELINE OVERLINE A1C8 FE4D # DASHED LOW LINE A1C9 FE4E # CENTRELINE LOW LINE A1CA FE4B # WAVY OVERLINE A1CB FE4C # DOUBLE WAVY OVERLINE A1CC FE5F # SMALL NUMBER SIGN A1CD FE60 # SMALL AMPERSAND A1CE FE61 # SMALL ASTERISK A1CF FF0B # FULLWIDTH PLUS SIGN A1D0 FF0D # FULLWIDTH HYPHEN-MINUS A1D1 00D7 # MULTIPLICATION SIGN A1D2 00F7 # DIVISION SIGN A1D3 00B1 # PLUS-MINUS SIGN A1D4 221A # SQUARE ROOT A1D5 FF1C # FULLWIDTH LESS-THAN SIGN A1D6 FF1E # FULLWIDTH GREATER-THAN SIGN A1D7 FF1D # FULLWIDTH EQUALS SIGN A1D8 2266 # LESS THAN OVER EQUAL TO A1D9 2267 # GREATER THAN OVER EQUAL TO A1DA 2260 # NOT EQUAL TO A1DB 221E # INFINITY A1DC 2252 # APPROXIMATELY EQUAL TO OR THE IMAGE OF A1DD 2261 # IDENTICAL TO A1DE FE62 # SMALL PLUS SIGN A1DF FE63 # SMALL HYPHEN-MINUS A1E0 FE64 # SMALL LESS-THAN SIGN A1E1 FE65 # SMALL GREATER-THAN SIGN A1E2 FE66 # SMALL EQUALS SIGN A1E3 223C # TILDE OPERATOR A1E4 2229 # INTERSECTION A1E5 222A # UNION A1E6 22A5 # UP TACK A1E7 2220 # ANGLE A1E8 221F # RIGHT ANGLE A1E9 22BF # RIGHT TRIANGLE A1EA 33D2 # SQUARE LOG A1EB 33D1 # SQUARE LN A1EC 222B # INTEGRAL A1ED 222E # CONTOUR INTEGRAL A1EE 2235 # BECAUSE A1EF 2234 # THEREFORE A1F0 2640 # FEMALE SIGN A1F1 2642 # MALE SIGN A1F2 2641 # EARTH A1F3 2609 # SUN A1F4 2191 # UPWARDS ARROW A1F5 2193 # DOWNWARDS ARROW A1F6 2190 # LEFTWARDS ARROW A1F7 2192 # RIGHTWARDS ARROW A1F8 2196 # NORTH WEST ARROW A1F9 2197 # NORTH EAST ARROW A1FA 2199 # SOUTH WEST ARROW A1FB 2198 # SOUTH EAST ARROW A1FC 2225 # PARALLEL TO A1FD 2223 # DIVIDES A1FE 2571 # LT DIAG UP RIGHT TO LOW LEFT duplicates A2AC A240 2572 # LT DIAG UP LEFT TO LOW RIGHT duplicates A2ADp A241 FF0F # FULLWIDTH SOLIDUS A242 FF3C # FULLWIDTH REVERSE SOLIDUS A243 FF04 # FULLWIDTH DOLLAR SIGN A244 00A5 # YEN SIGN A245 3012 # POSTAL MARK A246 00A2 # CENT SIGN A247 00A3 # POUND SIGN A248 FF05 # FULLWIDTH PERCENT SIGN A249 FF20 # FULLWIDTH COMMERCIAL AT A24A 2103 # DEGREE CELSIUS A24B 2109 # DEGREE FAHRENHEIT A24C FE69 # SMALL DOLLAR SIGN A24D FE6A # SMALL PERCENT SIGN A24E FE6B # SMALL COMMERCIAL AT A24F 33D5 # SQUARE MIL A250 339C # SQUARE MM A251 339D # SQUARE CM A252 339E # SQUARE KM A253 33CE # SQUARE KM CAPITAL A254 33A1 # SQUARE M SQUARED A255 338E # SQUARE MG A256 338F # SQUARE KG A257 33C4 # SQUARE CC A258 00B0 # DEGREE SIGN A259 5159 # A25A 515B # A25B 515E # A25C 515D # A25D 5161 # A25E 5163 # A25F 55E7 # A260 74E9 # A261 7CCE # A262 2581 # LOWER ONE EIGHTH BLOCK A263 2582 # LOWER ONE QUARTER BLOCK A264 2583 # LOWER THREE EIGHTHS BLOCK A265 2584 # LOWER HALF BLOCK A266 2585 # LOWER FIVE EIGHTHS BLOCK A267 2586 # LOWER THREE QUARTERS BLOCK A268 2587 # LOWER SEVEN EIGHTHS BLOCK A269 2588 # FULL BLOCK A26A 258F # LEFT ONE EIGHTH BLOCK A26B 258E # LEFT ONE QUARTER BLOCK A26C 258D # LEFT THREE EIGHTHS BLOCK A26D 258C # LEFT HALF BLOCK A26E 258B # LEFT FIVE EIGHTHS BLOCK A26F 258A # LEFT THREE QUARTERS BLOCK A270 2589 # LEFT SEVEN EIGHTHS BLOCK A271 253C # BOX DRAWINGS LIGHT VERTICAL AND HORIZONTAL A272 2534 # BOX DRAWINGS LIGHT UP AND HORIZONTAL A273 252C # BOX DRAWINGS LIGHT DOWN AND HORIZONTAL A274 2524 # BOX DRAWINGS LIGHT VERTICAL AND LEFT A275 251C # BOX DRAWINGS LIGHT VERTICAL AND RIGHT A276 2594 # UPPER ONE EIGHTH BLOCK A277 2500 # BOX DRAWINGS LIGHT HORIZONTAL A278 2502 # BOX DRAWINGS LIGHT VERTICAL A279 2595 # RIGHT ONE EIGHTH BLOCK A27A 250C # BOX DRAWINGS LIGHT DOWN AND RIGHT A27B 2510 # BOX DRAWINGS LIGHT DOWN AND LEFT A27C 2514 # BOX DRAWINGS LIGHT UP AND RIGHT A27D 2518 # BOX DRAWINGS LIGHT UP AND LEFT A27E 256D # BOX DRAWINGS LIGHT ARC DOWN AND RIGHT A2A1 256E # BOX DRAWINGS LIGHT ARC DOWN AND LEFT A2A2 2570 # BOX DRAWINGS LIGHT ARC UP AND RIGHT A2A3 256F # BOX DRAWINGS LIGHT ARC UP AND LEFT A2A4 2550 # BOX DRAWINGS DOUBLE HORIZONTAL A2A5 255E # BOX DRAWINGS VERTICAL SINGLE AND RIGHT DOUBLE A2A6 256A # BOX DRAWINGS VERTICAL SINGLE AND HORIZONTAL DOUBLE A2A7 2561 # BOX DRAWINGS VERTICAL SINGLE AND LEFT DOUBLE A2A8 25E2 # BLACK LOWER RIGHT TRIANGLE A2A9 25E3 # BLACK LOWER LEFT TRIANGLE A2AA 25E5 # BLACK UPPER RIGHT TRIANGLE A2AB 25E4 # BLACK UPPER LEFT TRIANGLE A2AC 2571 # BOX DRAWINGS LIGHT DIAGONAL UPPER RIGHT TO LOWER LEFT A2AD 2572 # BOX DRAWINGS LIGHT DIAGONAL UPPER LEFT TO LOWER RIGHT A2AE 2573 # BOX DRAWINGS LIGHT DIAGONAL CROSS A2AF FF10 # FULLWIDTH DIGIT ZERO A2B0 FF11 # FULLWIDTH DIGIT ONE A2B1 FF12 # FULLWIDTH DIGIT TWO A2B2 FF13 # FULLWIDTH DIGIT THREE A2B3 FF14 # FULLWIDTH DIGIT FOUR A2B4 FF15 # FULLWIDTH DIGIT FIVE A2B5 FF16 # FULLWIDTH DIGIT SIX A2B6 FF17 # FULLWIDTH DIGIT SEVEN A2B7 FF18 # FULLWIDTH DIGIT EIGHT A2B8 FF19 # FULLWIDTH DIGIT NINE A2B9 2160 # ROMAN NUMERAL ONE A2BA 2161 # ROMAN NUMERAL TWO A2BB 2162 # ROMAN NUMERAL THREE A2BC 2163 # ROMAN NUMERAL FOUR A2BD 2164 # ROMAN NUMERAL FIVE A2BE 2165 # ROMAN NUMERAL SIX A2BF 2166 # ROMAN NUMERAL SEVEN A2C0 2167 # ROMAN NUMERAL EIGHT A2C1 2168 # ROMAN NUMERAL NINE A2C2 2169 # ROMAN NUMERAL TEN A2C3 3021 # HANGZHOU NUMERAL ONE A2C4 3022 # HANGZHOU NUMERAL TWO A2C5 3023 # HANGZHOU NUMERAL THREE A2C6 3024 # HANGZHOU NUMERAL FOUR A2C7 3025 # HANGZHOU NUMERAL FIVE A2C8 3026 # HANGZHOU NUMERAL SIX A2C9 3027 # HANGZHOU NUMERAL SEVEN A2CA 3028 # HANGZHOU NUMERAL EIGHT A2CB 3029 # HANGZHOU NUMERAL NINE A2CC 5341 # HANGZHOU NUMERAL TEN conflicts with A451 mapping A2CD 5344 # A2CE 5345 # HANGZHOU NUMERAL THIRTY conflicts with A4CA mapping A2CF FF21 # FULLWIDTH LATIN CAPITAL LETTER A A2D0 FF22 # FULLWIDTH LATIN CAPITAL LETTER B A2D1 FF23 # FULLWIDTH LATIN CAPITAL LETTER C A2D2 FF24 # FULLWIDTH LATIN CAPITAL LETTER D A2D3 FF25 # FULLWIDTH LATIN CAPITAL LETTER E A2D4 FF26 # FULLWIDTH LATIN CAPITAL LETTER F A2D5 FF27 # FULLWIDTH LATIN CAPITAL LETTER G A2D6 FF28 # FULLWIDTH LATIN CAPITAL LETTER H A2D7 FF29 # FULLWIDTH LATIN CAPITAL LETTER I A2D8 FF2A # FULLWIDTH LATIN CAPITAL LETTER J A2D9 FF2B # FULLWIDTH LATIN CAPITAL LETTER K A2DA FF2C # FULLWIDTH LATIN CAPITAL LETTER L A2DB FF2D # FULLWIDTH LATIN CAPITAL LETTER M A2DC FF2E # FULLWIDTH LATIN CAPITAL LETTER N A2DD FF2F # FULLWIDTH LATIN CAPITAL LETTER O A2DE FF30 # FULLWIDTH LATIN CAPITAL LETTER P A2DF FF31 # FULLWIDTH LATIN CAPITAL LETTER Q A2E0 FF32 # FULLWIDTH LATIN CAPITAL LETTER R A2E1 FF33 # FULLWIDTH LATIN CAPITAL LETTER S A2E2 FF34 # FULLWIDTH LATIN CAPITAL LETTER T A2E3 FF35 # FULLWIDTH LATIN CAPITAL LETTER U A2E4 FF36 # FULLWIDTH LATIN CAPITAL LETTER V A2E5 FF37 # FULLWIDTH LATIN CAPITAL LETTER W A2E6 FF38 # FULLWIDTH LATIN CAPITAL LETTER X A2E7 FF39 # FULLWIDTH LATIN CAPITAL LETTER Y A2E8 FF3A # FULLWIDTH LATIN CAPITAL LETTER Z A2E9 FF41 # FULLWIDTH LATIN SMALL LETTER A A2EA FF42 # FULLWIDTH LATIN SMALL LETTER B A2EB FF43 # FULLWIDTH LATIN SMALL LETTER C A2EC FF44 # FULLWIDTH LATIN SMALL LETTER D A2ED FF45 # FULLWIDTH LATIN SMALL LETTER E A2EE FF46 # FULLWIDTH LATIN SMALL LETTER F A2EF FF47 # FULLWIDTH LATIN SMALL LETTER G A2F0 FF48 # FULLWIDTH LATIN SMALL LETTER H A2F1 FF49 # FULLWIDTH LATIN SMALL LETTER I A2F2 FF4A # FULLWIDTH LATIN SMALL LETTER J A2F3 FF4B # FULLWIDTH LATIN SMALL LETTER K A2F4 FF4C # FULLWIDTH LATIN SMALL LETTER L A2F5 FF4D # FULLWIDTH LATIN SMALL LETTER M A2F6 FF4E # FULLWIDTH LATIN SMALL LETTER N A2F7 FF4F # FULLWIDTH LATIN SMALL LETTER O A2F8 FF50 # FULLWIDTH LATIN SMALL LETTER P A2F9 FF51 # FULLWIDTH LATIN SMALL LETTER Q A2FA FF52 # FULLWIDTH LATIN SMALL LETTER R A2FB FF53 # FULLWIDTH LATIN SMALL LETTER S A2FC FF54 # FULLWIDTH LATIN SMALL LETTER T A2FD FF55 # FULLWIDTH LATIN SMALL LETTER U A2FE FF56 # FULLWIDTH LATIN SMALL LETTER V A340 FF57 # FULLWIDTH LATIN SMALL LETTER W A341 FF58 # FULLWIDTH LATIN SMALL LETTER X A342 FF59 # FULLWIDTH LATIN SMALL LETTER Y A343 FF5A # FULLWIDTH LATIN SMALL LETTER Z A344 0391 # GREEK CAPITAL LETTER ALPHA A345 0392 # GREEK CAPITAL LETTER BETA A346 0393 # GREEK CAPITAL LETTER GAMMA A347 0394 # GREEK CAPITAL LETTER DELTA A348 0395 # GREEK CAPITAL LETTER EPSILON A349 0396 # GREEK CAPITAL LETTER ZETA A34A 0397 # GREEK CAPITAL LETTER ETA A34B 0398 # GREEK CAPITAL LETTER THETA A34C 0399 # GREEK CAPITAL LETTER IOTA A34D 039A # GREEK CAPITAL LETTER KAPPA A34E 039B # GREEK CAPITAL LETTER LAMDA A34F 039C # GREEK CAPITAL LETTER MU A350 039D # GREEK CAPITAL LETTER NU A351 039E # GREEK CAPITAL LETTER XI A352 039F # GREEK CAPITAL LETTER OMICRON A353 03A0 # GREEK CAPITAL LETTER PI A354 03A1 # GREEK CAPITAL LETTER RHO A355 03A3 # GREEK CAPITAL LETTER SIGMA A356 03A4 # GREEK CAPITAL LETTER TAU A357 03A5 # GREEK CAPITAL LETTER UPSILON A358 03A6 # GREEK CAPITAL LETTER PHI A359 03A7 # GREEK CAPITAL LETTER CHI A35A 03A8 # GREEK CAPITAL LETTER PSI A35B 03A9 # GREEK CAPITAL LETTER OMEGA A35C 03B1 # GREEK SMALL LETTER ALPHA A35D 03B2 # GREEK SMALL LETTER BETA A35E 03B3 # GREEK SMALL LETTER GAMMA A35F 03B4 # GREEK SMALL LETTER DELTA A360 03B5 # GREEK SMALL LETTER EPSILON A361 03B6 # GREEK SMALL LETTER ZETA A362 03B7 # GREEK SMALL LETTER ETA A363 03B8 # GREEK SMALL LETTER THETA A364 03B9 # GREEK SMALL LETTER IOTA A365 03BA # GREEK SMALL LETTER KAPPA A366 03BB # GREEK SMALL LETTER LAMDA A367 03BC # GREEK SMALL LETTER MU A368 03BD # GREEK SMALL LETTER NU A369 03BE # GREEK SMALL LETTER XI A36A 03BF # GREEK SMALL LETTER OMICRON A36B 03C0 # GREEK SMALL LETTER PI A36C 03C1 # GREEK SMALL LETTER RHO A36D 03C3 # GREEK SMALL LETTER SIGMA A36E 03C4 # GREEK SMALL LETTER TAU A36F 03C5 # GREEK SMALL LETTER UPSILON A370 03C6 # GREEK SMALL LETTER PHI A371 03C7 # GREEK SMALL LETTER CHI A372 03C8 # GREEK SMALL LETTER PSI A373 03C9 # GREEK SMALL LETTER OMEGA A374 3105 # BOPOMOFO LETTER B A375 3106 # BOPOMOFO LETTER P A376 3107 # BOPOMOFO LETTER M A377 3108 # BOPOMOFO LETTER F A378 3109 # BOPOMOFO LETTER D A379 310A # BOPOMOFO LETTER T A37A 310B # BOPOMOFO LETTER N A37B 310C # BOPOMOFO LETTER L A37C 310D # BOPOMOFO LETTER G A37D 310E # BOPOMOFO LETTER K A37E 310F # BOPOMOFO LETTER H A3A1 3110 # BOPOMOFO LETTER J A3A2 3111 # BOPOMOFO LETTER Q A3A3 3112 # BOPOMOFO LETTER X A3A4 3113 # BOPOMOFO LETTER ZH A3A5 3114 # BOPOMOFO LETTER CH A3A6 3115 # BOPOMOFO LETTER SH A3A7 3116 # BOPOMOFO LETTER R A3A8 3117 # BOPOMOFO LETTER Z A3A9 3118 # BOPOMOFO LETTER C A3AA 3119 # BOPOMOFO LETTER S A3AB 311A # BOPOMOFO LETTER A A3AC 311B # BOPOMOFO LETTER O A3AD 311C # BOPOMOFO LETTER E A3AE 311D # BOPOMOFO LETTER EH A3AF 311E # BOPOMOFO LETTER AI A3B0 311F # BOPOMOFO LETTER EI A3B1 3120 # BOPOMOFO LETTER AU A3B2 3121 # BOPOMOFO LETTER OU A3B3 3122 # BOPOMOFO LETTER AN A3B4 3123 # BOPOMOFO LETTER EN A3B5 3124 # BOPOMOFO LETTER ANG A3B6 3125 # BOPOMOFO LETTER ENG A3B7 3126 # BOPOMOFO LETTER ER A3B8 3127 # BOPOMOFO LETTER I A3B9 3128 # BOPOMOFO LETTER U A3BA 3129 # BOPOMOFO LETTER IU A3BB 02D9 # DOT ABOVE (Mandarin Chinese light tone) A3BC 02C9 # MODIFIER LETTER MACRON (Mandarin Chinese first tone) A3BD 02CA # MODIFIER LETTER ACUTE ACCENT (Mandarin Chinese second tone) A3BE 02C7 # CARON (Mandarin Chinese third tone) A3BF 02CB # MODIFIER LETTER GRAVE ACCENT (Mandarin Chinese fourth tone) A440 4E00 # A441 4E59 # A442 4E01 # A443 4E03 # A444 4E43 # A445 4E5D # A446 4E86 # A447 4E8C # A448 4EBA # A449 513F # A44A 5165 # A44B 516B # A44C 51E0 # A44D 5200 # A44E 5201 # A44F 529B # A450 5315 # A451 5341 # A452 535C # A453 53C8 # A454 4E09 # A455 4E0B # A456 4E08 # A457 4E0A # A458 4E2B # A459 4E38 # A45A 51E1 # A45B 4E45 # A45C 4E48 # A45D 4E5F # A45E 4E5E # A45F 4E8E # A460 4EA1 # A461 5140 # A462 5203 # A463 52FA # A464 5343 # A465 53C9 # A466 53E3 # A467 571F # A468 58EB # A469 5915 # A46A 5927 # A46B 5973 # A46C 5B50 # A46D 5B51 # A46E 5B53 # A46F 5BF8 # A470 5C0F # A471 5C22 # A472 5C38 # A473 5C71 # A474 5DDD # A475 5DE5 # A476 5DF1 # A477 5DF2 # A478 5DF3 # A479 5DFE # A47A 5E72 # A47B 5EFE # A47C 5F0B # A47D 5F13 # A47E 624D # A4A1 4E11 # A4A2 4E10 # A4A3 4E0D # A4A4 4E2D # A4A5 4E30 # A4A6 4E39 # A4A7 4E4B # A4A8 5C39 # A4A9 4E88 # A4AA 4E91 # A4AB 4E95 # A4AC 4E92 # A4AD 4E94 # A4AE 4EA2 # A4AF 4EC1 # A4B0 4EC0 # A4B1 4EC3 # A4B2 4EC6 # A4B3 4EC7 # A4B4 4ECD # A4B5 4ECA # A4B6 4ECB # A4B7 4EC4 # A4B8 5143 # A4B9 5141 # A4BA 5167 # A4BB 516D # A4BC 516E # A4BD 516C # A4BE 5197 # A4BF 51F6 # A4C0 5206 # A4C1 5207 # A4C2 5208 # A4C3 52FB # A4C4 52FE # A4C5 52FF # A4C6 5316 # A4C7 5339 # A4C8 5348 # A4C9 5347 # A4CA 5345 # A4CB 535E # A4CC 5384 # A4CD 53CB # A4CE 53CA # A4CF 53CD # A4D0 58EC # A4D1 5929 # A4D2 592B # A4D3 592A # A4D4 592D # A4D5 5B54 # A4D6 5C11 # A4D7 5C24 # A4D8 5C3A # A4D9 5C6F # A4DA 5DF4 # A4DB 5E7B # A4DC 5EFF # A4DD 5F14 # A4DE 5F15 # A4DF 5FC3 # A4E0 6208 # A4E1 6236 # A4E2 624B # A4E3 624E # A4E4 652F # A4E5 6587 # A4E6 6597 # A4E7 65A4 # A4E8 65B9 # A4E9 65E5 # A4EA 66F0 # A4EB 6708 # A4EC 6728 # A4ED 6B20 # A4EE 6B62 # A4EF 6B79 # A4F0 6BCB # A4F1 6BD4 # A4F2 6BDB # A4F3 6C0F # A4F4 6C34 # A4F5 706B # A4F6 722A # A4F7 7236 # A4F8 723B # A4F9 7247 # A4FA 7259 # A4FB 725B # A4FC 72AC # A4FD 738B # A4FE 4E19 # A540 4E16 # A541 4E15 # A542 4E14 # A543 4E18 # A544 4E3B # A545 4E4D # A546 4E4F # A547 4E4E # A548 4EE5 # A549 4ED8 # A54A 4ED4 # A54B 4ED5 # A54C 4ED6 # A54D 4ED7 # A54E 4EE3 # A54F 4EE4 # A550 4ED9 # A551 4EDE # A552 5145 # A553 5144 # A554 5189 # A555 518A # A556 51AC # A557 51F9 # A558 51FA # A559 51F8 # A55A 520A # A55B 52A0 # A55C 529F # A55D 5305 # A55E 5306 # A55F 5317 # A560 531D # A561 4EDF # A562 534A # A563 5349 # A564 5361 # A565 5360 # A566 536F # A567 536E # A568 53BB # A569 53EF # A56A 53E4 # A56B 53F3 # A56C 53EC # A56D 53EE # A56E 53E9 # A56F 53E8 # A570 53FC # A571 53F8 # A572 53F5 # A573 53EB # A574 53E6 # A575 53EA # A576 53F2 # A577 53F1 # A578 53F0 # A579 53E5 # A57A 53ED # A57B 53FB # A57C 56DB # A57D 56DA # A57E 5916 # A5A1 592E # A5A2 5931 # A5A3 5974 # A5A4 5976 # A5A5 5B55 # A5A6 5B83 # A5A7 5C3C # A5A8 5DE8 # A5A9 5DE7 # A5AA 5DE6 # A5AB 5E02 # A5AC 5E03 # A5AD 5E73 # A5AE 5E7C # A5AF 5F01 # A5B0 5F18 # A5B1 5F17 # A5B2 5FC5 # A5B3 620A # A5B4 6253 # A5B5 6254 # A5B6 6252 # A5B7 6251 # A5B8 65A5 # A5B9 65E6 # A5BA 672E # A5BB 672C # A5BC 672A # A5BD 672B # A5BE 672D # A5BF 6B63 # A5C0 6BCD # A5C1 6C11 # A5C2 6C10 # A5C3 6C38 # A5C4 6C41 # A5C5 6C40 # A5C6 6C3E # A5C7 72AF # A5C8 7384 # A5C9 7389 # A5CA 74DC # A5CB 74E6 # A5CC 7518 # A5CD 751F # A5CE 7528 # A5CF 7529 # A5D0 7530 # A5D1 7531 # A5D2 7532 # A5D3 7533 # A5D4 758B # A5D5 767D # A5D6 76AE # A5D7 76BF # A5D8 76EE # A5D9 77DB # A5DA 77E2 # A5DB 77F3 # A5DC 793A # A5DD 79BE # A5DE 7A74 # A5DF 7ACB # A5E0 4E1E # A5E1 4E1F # A5E2 4E52 # A5E3 4E53 # A5E4 4E69 # A5E5 4E99 # A5E6 4EA4 # A5E7 4EA6 # A5E8 4EA5 # A5E9 4EFF # A5EA 4F09 # A5EB 4F19 # A5EC 4F0A # A5ED 4F15 # A5EE 4F0D # A5EF 4F10 # A5F0 4F11 # A5F1 4F0F # A5F2 4EF2 # A5F3 4EF6 # A5F4 4EFB # A5F5 4EF0 # A5F6 4EF3 # A5F7 4EFD # A5F8 4F01 # A5F9 4F0B # A5FA 5149 # A5FB 5147 # A5FC 5146 # A5FD 5148 # A5FE 5168 # A640 5171 # A641 518D # A642 51B0 # A643 5217 # A644 5211 # A645 5212 # A646 520E # A647 5216 # A648 52A3 # A649 5308 # A64A 5321 # A64B 5320 # A64C 5370 # A64D 5371 # A64E 5409 # A64F 540F # A650 540C # A651 540A # A652 5410 # A653 5401 # A654 540B # A655 5404 # A656 5411 # A657 540D # A658 5408 # A659 5403 # A65A 540E # A65B 5406 # A65C 5412 # A65D 56E0 # A65E 56DE # A65F 56DD # A660 5733 # A661 5730 # A662 5728 # A663 572D # A664 572C # A665 572F # A666 5729 # A667 5919 # A668 591A # A669 5937 # A66A 5938 # A66B 5984 # A66C 5978 # A66D 5983 # A66E 597D # A66F 5979 # A670 5982 # A671 5981 # A672 5B57 # A673 5B58 # A674 5B87 # A675 5B88 # A676 5B85 # A677 5B89 # A678 5BFA # A679 5C16 # A67A 5C79 # A67B 5DDE # A67C 5E06 # A67D 5E76 # A67E 5E74 # A6A1 5F0F # A6A2 5F1B # A6A3 5FD9 # A6A4 5FD6 # A6A5 620E # A6A6 620C # A6A7 620D # A6A8 6210 # A6A9 6263 # A6AA 625B # A6AB 6258 # A6AC 6536 # A6AD 65E9 # A6AE 65E8 # A6AF 65EC # A6B0 65ED # A6B1 66F2 # A6B2 66F3 # A6B3 6709 # A6B4 673D # A6B5 6734 # A6B6 6731 # A6B7 6735 # A6B8 6B21 # A6B9 6B64 # A6BA 6B7B # A6BB 6C16 # A6BC 6C5D # A6BD 6C57 # A6BE 6C59 # A6BF 6C5F # A6C0 6C60 # A6C1 6C50 # A6C2 6C55 # A6C3 6C61 # A6C4 6C5B # A6C5 6C4D # A6C6 6C4E # A6C7 7070 # A6C8 725F # A6C9 725D # A6CA 767E # A6CB 7AF9 # A6CC 7C73 # A6CD 7CF8 # A6CE 7F36 # A6CF 7F8A # A6D0 7FBD # A6D1 8001 # A6D2 8003 # A6D3 800C # A6D4 8012 # A6D5 8033 # A6D6 807F # A6D7 8089 # A6D8 808B # A6D9 808C # A6DA 81E3 # A6DB 81EA # A6DC 81F3 # A6DD 81FC # A6DE 820C # A6DF 821B # A6E0 821F # A6E1 826E # A6E2 8272 # A6E3 827E # A6E4 866B # A6E5 8840 # A6E6 884C # A6E7 8863 # A6E8 897F # A6E9 9621 # A6EA 4E32 # A6EB 4EA8 # A6EC 4F4D # A6ED 4F4F # A6EE 4F47 # A6EF 4F57 # A6F0 4F5E # A6F1 4F34 # A6F2 4F5B # A6F3 4F55 # A6F4 4F30 # A6F5 4F50 # A6F6 4F51 # A6F7 4F3D # A6F8 4F3A # A6F9 4F38 # A6FA 4F43 # A6FB 4F54 # A6FC 4F3C # A6FD 4F46 # A6FE 4F63 # A740 4F5C # A741 4F60 # A742 4F2F # A743 4F4E # A744 4F36 # A745 4F59 # A746 4F5D # A747 4F48 # A748 4F5A # A749 514C # A74A 514B # A74B 514D # A74C 5175 # A74D 51B6 # A74E 51B7 # A74F 5225 # A750 5224 # A751 5229 # A752 522A # A753 5228 # A754 52AB # A755 52A9 # A756 52AA # A757 52AC # A758 5323 # A759 5373 # A75A 5375 # A75B 541D # A75C 542D # A75D 541E # A75E 543E # A75F 5426 # A760 544E # A761 5427 # A762 5446 # A763 5443 # A764 5433 # A765 5448 # A766 5442 # A767 541B # A768 5429 # A769 544A # A76A 5439 # A76B 543B # A76C 5438 # A76D 542E # A76E 5435 # A76F 5436 # A770 5420 # A771 543C # A772 5440 # A773 5431 # A774 542B # A775 541F # A776 542C # A777 56EA # A778 56F0 # A779 56E4 # A77A 56EB # A77B 574A # A77C 5751 # A77D 5740 # A77E 574D # A7A1 5747 # A7A2 574E # A7A3 573E # A7A4 5750 # A7A5 574F # A7A6 573B # A7A7 58EF # A7A8 593E # A7A9 599D # A7AA 5992 # A7AB 59A8 # A7AC 599E # A7AD 59A3 # A7AE 5999 # A7AF 5996 # A7B0 598D # A7B1 59A4 # A7B2 5993 # A7B3 598A # A7B4 59A5 # A7B5 5B5D # A7B6 5B5C # A7B7 5B5A # A7B8 5B5B # A7B9 5B8C # A7BA 5B8B # A7BB 5B8F # A7BC 5C2C # A7BD 5C40 # A7BE 5C41 # A7BF 5C3F # A7C0 5C3E # A7C1 5C90 # A7C2 5C91 # A7C3 5C94 # A7C4 5C8C # A7C5 5DEB # A7C6 5E0C # A7C7 5E8F # A7C8 5E87 # A7C9 5E8A # A7CA 5EF7 # A7CB 5F04 # A7CC 5F1F # A7CD 5F64 # A7CE 5F62 # A7CF 5F77 # A7D0 5F79 # A7D1 5FD8 # A7D2 5FCC # A7D3 5FD7 # A7D4 5FCD # A7D5 5FF1 # A7D6 5FEB # A7D7 5FF8 # A7D8 5FEA # A7D9 6212 # A7DA 6211 # A7DB 6284 # A7DC 6297 # A7DD 6296 # A7DE 6280 # A7DF 6276 # A7E0 6289 # A7E1 626D # A7E2 628A # A7E3 627C # A7E4 627E # A7E5 6279 # A7E6 6273 # A7E7 6292 # A7E8 626F # A7E9 6298 # A7EA 626E # A7EB 6295 # A7EC 6293 # A7ED 6291 # A7EE 6286 # A7EF 6539 # A7F0 653B # A7F1 6538 # A7F2 65F1 # A7F3 66F4 # A7F4 675F # A7F5 674E # A7F6 674F # A7F7 6750 # A7F8 6751 # A7F9 675C # A7FA 6756 # A7FB 675E # A7FC 6749 # A7FD 6746 # A7FE 6760 # A840 6753 # A841 6757 # A842 6B65 # A843 6BCF # A844 6C42 # A845 6C5E # A846 6C99 # A847 6C81 # A848 6C88 # A849 6C89 # A84A 6C85 # A84B 6C9B # A84C 6C6A # A84D 6C7A # A84E 6C90 # A84F 6C70 # A850 6C8C # A851 6C68 # A852 6C96 # A853 6C92 # A854 6C7D # A855 6C83 # A856 6C72 # A857 6C7E # A858 6C74 # A859 6C86 # A85A 6C76 # A85B 6C8D # A85C 6C94 # A85D 6C98 # A85E 6C82 # A85F 7076 # A860 707C # A861 707D # A862 7078 # A863 7262 # A864 7261 # A865 7260 # A866 72C4 # A867 72C2 # A868 7396 # A869 752C # A86A 752B # A86B 7537 # A86C 7538 # A86D 7682 # A86E 76EF # A86F 77E3 # A870 79C1 # A871 79C0 # A872 79BF # A873 7A76 # A874 7CFB # A875 7F55 # A876 8096 # A877 8093 # A878 809D # A879 8098 # A87A 809B # A87B 809A # A87C 80B2 # A87D 826F # A87E 8292 # A8A1 828B # A8A2 828D # A8A3 898B # A8A4 89D2 # A8A5 8A00 # A8A6 8C37 # A8A7 8C46 # A8A8 8C55 # A8A9 8C9D # A8AA 8D64 # A8AB 8D70 # A8AC 8DB3 # A8AD 8EAB # A8AE 8ECA # A8AF 8F9B # A8B0 8FB0 # A8B1 8FC2 # A8B2 8FC6 # A8B3 8FC5 # A8B4 8FC4 # A8B5 5DE1 # A8B6 9091 # A8B7 90A2 # A8B8 90AA # A8B9 90A6 # A8BA 90A3 # A8BB 9149 # A8BC 91C6 # A8BD 91CC # A8BE 9632 # A8BF 962E # A8C0 9631 # A8C1 962A # A8C2 962C # A8C3 4E26 # A8C4 4E56 # A8C5 4E73 # A8C6 4E8B # A8C7 4E9B # A8C8 4E9E # A8C9 4EAB # A8CA 4EAC # A8CB 4F6F # A8CC 4F9D # A8CD 4F8D # A8CE 4F73 # A8CF 4F7F # A8D0 4F6C # A8D1 4F9B # A8D2 4F8B # A8D3 4F86 # A8D4 4F83 # A8D5 4F70 # A8D6 4F75 # A8D7 4F88 # A8D8 4F69 # A8D9 4F7B # A8DA 4F96 # A8DB 4F7E # A8DC 4F8F # A8DD 4F91 # A8DE 4F7A # A8DF 5154 # A8E0 5152 # A8E1 5155 # A8E2 5169 # A8E3 5177 # A8E4 5176 # A8E5 5178 # A8E6 51BD # A8E7 51FD # A8E8 523B # A8E9 5238 # A8EA 5237 # A8EB 523A # A8EC 5230 # A8ED 522E # A8EE 5236 # A8EF 5241 # A8F0 52BE # A8F1 52BB # A8F2 5352 # A8F3 5354 # A8F4 5353 # A8F5 5351 # A8F6 5366 # A8F7 5377 # A8F8 5378 # A8F9 5379 # A8FA 53D6 # A8FB 53D4 # A8FC 53D7 # A8FD 5473 # A8FE 5475 # A940 5496 # A941 5478 # A942 5495 # A943 5480 # A944 547B # A945 5477 # A946 5484 # A947 5492 # A948 5486 # A949 547C # A94A 5490 # A94B 5471 # A94C 5476 # A94D 548C # A94E 549A # A94F 5462 # A950 5468 # A951 548B # A952 547D # A953 548E # A954 56FA # A955 5783 # A956 5777 # A957 576A # A958 5769 # A959 5761 # A95A 5766 # A95B 5764 # A95C 577C # A95D 591C # A95E 5949 # A95F 5947 # A960 5948 # A961 5944 # A962 5954 # A963 59BE # A964 59BB # A965 59D4 # A966 59B9 # A967 59AE # A968 59D1 # A969 59C6 # A96A 59D0 # A96B 59CD # A96C 59CB # A96D 59D3 # A96E 59CA # A96F 59AF # A970 59B3 # A971 59D2 # A972 59C5 # A973 5B5F # A974 5B64 # A975 5B63 # A976 5B97 # A977 5B9A # A978 5B98 # A979 5B9C # A97A 5B99 # A97B 5B9B # A97C 5C1A # A97D 5C48 # A97E 5C45 # A9A1 5C46 # A9A2 5CB7 # A9A3 5CA1 # A9A4 5CB8 # A9A5 5CA9 # A9A6 5CAB # A9A7 5CB1 # A9A8 5CB3 # A9A9 5E18 # A9AA 5E1A # A9AB 5E16 # A9AC 5E15 # A9AD 5E1B # A9AE 5E11 # A9AF 5E78 # A9B0 5E9A # A9B1 5E97 # A9B2 5E9C # A9B3 5E95 # A9B4 5E96 # A9B5 5EF6 # A9B6 5F26 # A9B7 5F27 # A9B8 5F29 # A9B9 5F80 # A9BA 5F81 # A9BB 5F7F # A9BC 5F7C # A9BD 5FDD # A9BE 5FE0 # A9BF 5FFD # A9C0 5FF5 # A9C1 5FFF # A9C2 600F # A9C3 6014 # A9C4 602F # A9C5 6035 # A9C6 6016 # A9C7 602A # A9C8 6015 # A9C9 6021 # A9CA 6027 # A9CB 6029 # A9CC 602B # A9CD 601B # A9CE 6216 # A9CF 6215 # A9D0 623F # A9D1 623E # A9D2 6240 # A9D3 627F # A9D4 62C9 # A9D5 62CC # A9D6 62C4 # A9D7 62BF # A9D8 62C2 # A9D9 62B9 # A9DA 62D2 # A9DB 62DB # A9DC 62AB # A9DD 62D3 # A9DE 62D4 # A9DF 62CB # A9E0 62C8 # A9E1 62A8 # A9E2 62BD # A9E3 62BC # A9E4 62D0 # A9E5 62D9 # A9E6 62C7 # A9E7 62CD # A9E8 62B5 # A9E9 62DA # A9EA 62B1 # A9EB 62D8 # A9EC 62D6 # A9ED 62D7 # A9EE 62C6 # A9EF 62AC # A9F0 62CE # A9F1 653E # A9F2 65A7 # A9F3 65BC # A9F4 65FA # A9F5 6614 # A9F6 6613 # A9F7 660C # A9F8 6606 # A9F9 6602 # A9FA 660E # A9FB 6600 # A9FC 660F # A9FD 6615 # A9FE 660A # AA40 6607 # AA41 670D # AA42 670B # AA43 676D # AA44 678B # AA45 6795 # AA46 6771 # AA47 679C # AA48 6773 # AA49 6777 # AA4A 6787 # AA4B 679D # AA4C 6797 # AA4D 676F # AA4E 6770 # AA4F 677F # AA50 6789 # AA51 677E # AA52 6790 # AA53 6775 # AA54 679A # AA55 6793 # AA56 677C # AA57 676A # AA58 6772 # AA59 6B23 # AA5A 6B66 # AA5B 6B67 # AA5C 6B7F # AA5D 6C13 # AA5E 6C1B # AA5F 6CE3 # AA60 6CE8 # AA61 6CF3 # AA62 6CB1 # AA63 6CCC # AA64 6CE5 # AA65 6CB3 # AA66 6CBD # AA67 6CBE # AA68 6CBC # AA69 6CE2 # AA6A 6CAB # AA6B 6CD5 # AA6C 6CD3 # AA6D 6CB8 # AA6E 6CC4 # AA6F 6CB9 # AA70 6CC1 # AA71 6CAE # AA72 6CD7 # AA73 6CC5 # AA74 6CF1 # AA75 6CBF # AA76 6CBB # AA77 6CE1 # AA78 6CDB # AA79 6CCA # AA7A 6CAC # AA7B 6CEF # AA7C 6CDC # AA7D 6CD6 # AA7E 6CE0 # AAA1 7095 # AAA2 708E # AAA3 7092 # AAA4 708A # AAA5 7099 # AAA6 722C # AAA7 722D # AAA8 7238 # AAA9 7248 # AAAA 7267 # AAAB 7269 # AAAC 72C0 # AAAD 72CE # AAAE 72D9 # AAAF 72D7 # AAB0 72D0 # AAB1 73A9 # AAB2 73A8 # AAB3 739F # AAB4 73AB # AAB5 73A5 # AAB6 753D # AAB7 759D # AAB8 7599 # AAB9 759A # AABA 7684 # AABB 76C2 # AABC 76F2 # AABD 76F4 # AABE 77E5 # AABF 77FD # AAC0 793E # AAC1 7940 # AAC2 7941 # AAC3 79C9 # AAC4 79C8 # AAC5 7A7A # AAC6 7A79 # AAC7 7AFA # AAC8 7CFE # AAC9 7F54 # AACA 7F8C # AACB 7F8B # AACC 8005 # AACD 80BA # AACE 80A5 # AACF 80A2 # AAD0 80B1 # AAD1 80A1 # AAD2 80AB # AAD3 80A9 # AAD4 80B4 # AAD5 80AA # AAD6 80AF # AAD7 81E5 # AAD8 81FE # AAD9 820D # AADA 82B3 # AADB 829D # AADC 8299 # AADD 82AD # AADE 82BD # AADF 829F # AAE0 82B9 # AAE1 82B1 # AAE2 82AC # AAE3 82A5 # AAE4 82AF # AAE5 82B8 # AAE6 82A3 # AAE7 82B0 # AAE8 82BE # AAE9 82B7 # AAEA 864E # AAEB 8671 # AAEC 521D # AAED 8868 # AAEE 8ECB # AAEF 8FCE # AAF0 8FD4 # AAF1 8FD1 # AAF2 90B5 # AAF3 90B8 # AAF4 90B1 # AAF5 90B6 # AAF6 91C7 # AAF7 91D1 # AAF8 9577 # AAF9 9580 # AAFA 961C # AAFB 9640 # AAFC 963F # AAFD 963B # AAFE 9644 # AB40 9642 # AB41 96B9 # AB42 96E8 # AB43 9752 # AB44 975E # AB45 4E9F # AB46 4EAD # AB47 4EAE # AB48 4FE1 # AB49 4FB5 # AB4A 4FAF # AB4B 4FBF # AB4C 4FE0 # AB4D 4FD1 # AB4E 4FCF # AB4F 4FDD # AB50 4FC3 # AB51 4FB6 # AB52 4FD8 # AB53 4FDF # AB54 4FCA # AB55 4FD7 # AB56 4FAE # AB57 4FD0 # AB58 4FC4 # AB59 4FC2 # AB5A 4FDA # AB5B 4FCE # AB5C 4FDE # AB5D 4FB7 # AB5E 5157 # AB5F 5192 # AB60 5191 # AB61 51A0 # AB62 524E # AB63 5243 # AB64 524A # AB65 524D # AB66 524C # AB67 524B # AB68 5247 # AB69 52C7 # AB6A 52C9 # AB6B 52C3 # AB6C 52C1 # AB6D 530D # AB6E 5357 # AB6F 537B # AB70 539A # AB71 53DB # AB72 54AC # AB73 54C0 # AB74 54A8 # AB75 54CE # AB76 54C9 # AB77 54B8 # AB78 54A6 # AB79 54B3 # AB7A 54C7 # AB7B 54C2 # AB7C 54BD # AB7D 54AA # AB7E 54C1 # ABA1 54C4 # ABA2 54C8 # ABA3 54AF # ABA4 54AB # ABA5 54B1 # ABA6 54BB # ABA7 54A9 # ABA8 54A7 # ABA9 54BF # ABAA 56FF # ABAB 5782 # ABAC 578B # ABAD 57A0 # ABAE 57A3 # ABAF 57A2 # ABB0 57CE # ABB1 57AE # ABB2 5793 # ABB3 5955 # ABB4 5951 # ABB5 594F # ABB6 594E # ABB7 5950 # ABB8 59DC # ABB9 59D8 # ABBA 59FF # ABBB 59E3 # ABBC 59E8 # ABBD 5A03 # ABBE 59E5 # ABBF 59EA # ABC0 59DA # ABC1 59E6 # ABC2 5A01 # ABC3 59FB # ABC4 5B69 # ABC5 5BA3 # ABC6 5BA6 # ABC7 5BA4 # ABC8 5BA2 # ABC9 5BA5 # ABCA 5C01 # ABCB 5C4E # ABCC 5C4F # ABCD 5C4D # ABCE 5C4B # ABCF 5CD9 # ABD0 5CD2 # ABD1 5DF7 # ABD2 5E1D # ABD3 5E25 # ABD4 5E1F # ABD5 5E7D # ABD6 5EA0 # ABD7 5EA6 # ABD8 5EFA # ABD9 5F08 # ABDA 5F2D # ABDB 5F65 # ABDC 5F88 # ABDD 5F85 # ABDE 5F8A # ABDF 5F8B # ABE0 5F87 # ABE1 5F8C # ABE2 5F89 # ABE3 6012 # ABE4 601D # ABE5 6020 # ABE6 6025 # ABE7 600E # ABE8 6028 # ABE9 604D # ABEA 6070 # ABEB 6068 # ABEC 6062 # ABED 6046 # ABEE 6043 # ABEF 606C # ABF0 606B # ABF1 606A # ABF2 6064 # ABF3 6241 # ABF4 62DC # ABF5 6316 # ABF6 6309 # ABF7 62FC # ABF8 62ED # ABF9 6301 # ABFA 62EE # ABFB 62FD # ABFC 6307 # ABFD 62F1 # ABFE 62F7 # AC40 62EF # AC41 62EC # AC42 62FE # AC43 62F4 # AC44 6311 # AC45 6302 # AC46 653F # AC47 6545 # AC48 65AB # AC49 65BD # AC4A 65E2 # AC4B 6625 # AC4C 662D # AC4D 6620 # AC4E 6627 # AC4F 662F # AC50 661F # AC51 6628 # AC52 6631 # AC53 6624 # AC54 66F7 # AC55 67FF # AC56 67D3 # AC57 67F1 # AC58 67D4 # AC59 67D0 # AC5A 67EC # AC5B 67B6 # AC5C 67AF # AC5D 67F5 # AC5E 67E9 # AC5F 67EF # AC60 67C4 # AC61 67D1 # AC62 67B4 # AC63 67DA # AC64 67E5 # AC65 67B8 # AC66 67CF # AC67 67DE # AC68 67F3 # AC69 67B0 # AC6A 67D9 # AC6B 67E2 # AC6C 67DD # AC6D 67D2 # AC6E 6B6A # AC6F 6B83 # AC70 6B86 # AC71 6BB5 # AC72 6BD2 # AC73 6BD7 # AC74 6C1F # AC75 6CC9 # AC76 6D0B # AC77 6D32 # AC78 6D2A # AC79 6D41 # AC7A 6D25 # AC7B 6D0C # AC7C 6D31 # AC7D 6D1E # AC7E 6D17 # ACA1 6D3B # ACA2 6D3D # ACA3 6D3E # ACA4 6D36 # ACA5 6D1B # ACA6 6CF5 # ACA7 6D39 # ACA8 6D27 # ACA9 6D38 # ACAA 6D29 # ACAB 6D2E # ACAC 6D35 # ACAD 6D0E # ACAE 6D2B # ACAF 70AB # ACB0 70BA # ACB1 70B3 # ACB2 70AC # ACB3 70AF # ACB4 70AD # ACB5 70B8 # ACB6 70AE # ACB7 70A4 # ACB8 7230 # ACB9 7272 # ACBA 726F # ACBB 7274 # ACBC 72E9 # ACBD 72E0 # ACBE 72E1 # ACBF 73B7 # ACC0 73CA # ACC1 73BB # ACC2 73B2 # ACC3 73CD # ACC4 73C0 # ACC5 73B3 # ACC6 751A # ACC7 752D # ACC8 754F # ACC9 754C # ACCA 754E # ACCB 754B # ACCC 75AB # ACCD 75A4 # ACCE 75A5 # ACCF 75A2 # ACD0 75A3 # ACD1 7678 # ACD2 7686 # ACD3 7687 # ACD4 7688 # ACD5 76C8 # ACD6 76C6 # ACD7 76C3 # ACD8 76C5 # ACD9 7701 # ACDA 76F9 # ACDB 76F8 # ACDC 7709 # ACDD 770B # ACDE 76FE # ACDF 76FC # ACE0 7707 # ACE1 77DC # ACE2 7802 # ACE3 7814 # ACE4 780C # ACE5 780D # ACE6 7946 # ACE7 7949 # ACE8 7948 # ACE9 7947 # ACEA 79B9 # ACEB 79BA # ACEC 79D1 # ACED 79D2 # ACEE 79CB # ACEF 7A7F # ACF0 7A81 # ACF1 7AFF # ACF2 7AFD # ACF3 7C7D # ACF4 7D02 # ACF5 7D05 # ACF6 7D00 # ACF7 7D09 # ACF8 7D07 # ACF9 7D04 # ACFA 7D06 # ACFB 7F38 # ACFC 7F8E # ACFD 7FBF # ACFE 8004 # AD40 8010 # AD41 800D # AD42 8011 # AD43 8036 # AD44 80D6 # AD45 80E5 # AD46 80DA # AD47 80C3 # AD48 80C4 # AD49 80CC # AD4A 80E1 # AD4B 80DB # AD4C 80CE # AD4D 80DE # AD4E 80E4 # AD4F 80DD # AD50 81F4 # AD51 8222 # AD52 82E7 # AD53 8303 # AD54 8305 # AD55 82E3 # AD56 82DB # AD57 82E6 # AD58 8304 # AD59 82E5 # AD5A 8302 # AD5B 8309 # AD5C 82D2 # AD5D 82D7 # AD5E 82F1 # AD5F 8301 # AD60 82DC # AD61 82D4 # AD62 82D1 # AD63 82DE # AD64 82D3 # AD65 82DF # AD66 82EF # AD67 8306 # AD68 8650 # AD69 8679 # AD6A 867B # AD6B 867A # AD6C 884D # AD6D 886B # AD6E 8981 # AD6F 89D4 # AD70 8A08 # AD71 8A02 # AD72 8A03 # AD73 8C9E # AD74 8CA0 # AD75 8D74 # AD76 8D73 # AD77 8DB4 # AD78 8ECD # AD79 8ECC # AD7A 8FF0 # AD7B 8FE6 # AD7C 8FE2 # AD7D 8FEA # AD7E 8FE5 # ADA1 8FED # ADA2 8FEB # ADA3 8FE4 # ADA4 8FE8 # ADA5 90CA # ADA6 90CE # ADA7 90C1 # ADA8 90C3 # ADA9 914B # ADAA 914A # ADAB 91CD # ADAC 9582 # ADAD 9650 # ADAE 964B # ADAF 964C # ADB0 964D # ADB1 9762 # ADB2 9769 # ADB3 97CB # ADB4 97ED # ADB5 97F3 # ADB6 9801 # ADB7 98A8 # ADB8 98DB # ADB9 98DF # ADBA 9996 # ADBB 9999 # ADBC 4E58 # ADBD 4EB3 # ADBE 500C # ADBF 500D # ADC0 5023 # ADC1 4FEF # ADC2 5026 # ADC3 5025 # ADC4 4FF8 # ADC5 5029 # ADC6 5016 # ADC7 5006 # ADC8 503C # ADC9 501F # ADCA 501A # ADCB 5012 # ADCC 5011 # ADCD 4FFA # ADCE 5000 # ADCF 5014 # ADD0 5028 # ADD1 4FF1 # ADD2 5021 # ADD3 500B # ADD4 5019 # ADD5 5018 # ADD6 4FF3 # ADD7 4FEE # ADD8 502D # ADD9 502A # ADDA 4FFE # ADDB 502B # ADDC 5009 # ADDD 517C # ADDE 51A4 # ADDF 51A5 # ADE0 51A2 # ADE1 51CD # ADE2 51CC # ADE3 51C6 # ADE4 51CB # ADE5 5256 # ADE6 525C # ADE7 5254 # ADE8 525B # ADE9 525D # ADEA 532A # ADEB 537F # ADEC 539F # ADED 539D # ADEE 53DF # ADEF 54E8 # ADF0 5510 # ADF1 5501 # ADF2 5537 # ADF3 54FC # ADF4 54E5 # ADF5 54F2 # ADF6 5506 # ADF7 54FA # ADF8 5514 # ADF9 54E9 # ADFA 54ED # ADFB 54E1 # ADFC 5509 # ADFD 54EE # ADFE 54EA # AE40 54E6 # AE41 5527 # AE42 5507 # AE43 54FD # AE44 550F # AE45 5703 # AE46 5704 # AE47 57C2 # AE48 57D4 # AE49 57CB # AE4A 57C3 # AE4B 5809 # AE4C 590F # AE4D 5957 # AE4E 5958 # AE4F 595A # AE50 5A11 # AE51 5A18 # AE52 5A1C # AE53 5A1F # AE54 5A1B # AE55 5A13 # AE56 59EC # AE57 5A20 # AE58 5A23 # AE59 5A29 # AE5A 5A25 # AE5B 5A0C # AE5C 5A09 # AE5D 5B6B # AE5E 5C58 # AE5F 5BB0 # AE60 5BB3 # AE61 5BB6 # AE62 5BB4 # AE63 5BAE # AE64 5BB5 # AE65 5BB9 # AE66 5BB8 # AE67 5C04 # AE68 5C51 # AE69 5C55 # AE6A 5C50 # AE6B 5CED # AE6C 5CFD # AE6D 5CFB # AE6E 5CEA # AE6F 5CE8 # AE70 5CF0 # AE71 5CF6 # AE72 5D01 # AE73 5CF4 # AE74 5DEE # AE75 5E2D # AE76 5E2B # AE77 5EAB # AE78 5EAD # AE79 5EA7 # AE7A 5F31 # AE7B 5F92 # AE7C 5F91 # AE7D 5F90 # AE7E 6059 # AEA1 6063 # AEA2 6065 # AEA3 6050 # AEA4 6055 # AEA5 606D # AEA6 6069 # AEA7 606F # AEA8 6084 # AEA9 609F # AEAA 609A # AEAB 608D # AEAC 6094 # AEAD 608C # AEAE 6085 # AEAF 6096 # AEB0 6247 # AEB1 62F3 # AEB2 6308 # AEB3 62FF # AEB4 634E # AEB5 633E # AEB6 632F # AEB7 6355 # AEB8 6342 # AEB9 6346 # AEBA 634F # AEBB 6349 # AEBC 633A # AEBD 6350 # AEBE 633D # AEBF 632A # AEC0 632B # AEC1 6328 # AEC2 634D # AEC3 634C # AEC4 6548 # AEC5 6549 # AEC6 6599 # AEC7 65C1 # AEC8 65C5 # AEC9 6642 # AECA 6649 # AECB 664F # AECC 6643 # AECD 6652 # AECE 664C # AECF 6645 # AED0 6641 # AED1 66F8 # AED2 6714 # AED3 6715 # AED4 6717 # AED5 6821 # AED6 6838 # AED7 6848 # AED8 6846 # AED9 6853 # AEDA 6839 # AEDB 6842 # AEDC 6854 # AEDD 6829 # AEDE 68B3 # AEDF 6817 # AEE0 684C # AEE1 6851 # AEE2 683D # AEE3 67F4 # AEE4 6850 # AEE5 6840 # AEE6 683C # AEE7 6843 # AEE8 682A # AEE9 6845 # AEEA 6813 # AEEB 6818 # AEEC 6841 # AEED 6B8A # AEEE 6B89 # AEEF 6BB7 # AEF0 6C23 # AEF1 6C27 # AEF2 6C28 # AEF3 6C26 # AEF4 6C24 # AEF5 6CF0 # AEF6 6D6A # AEF7 6D95 # AEF8 6D88 # AEF9 6D87 # AEFA 6D66 # AEFB 6D78 # AEFC 6D77 # AEFD 6D59 # AEFE 6D93 # AF40 6D6C # AF41 6D89 # AF42 6D6E # AF43 6D5A # AF44 6D74 # AF45 6D69 # AF46 6D8C # AF47 6D8A # AF48 6D79 # AF49 6D85 # AF4A 6D65 # AF4B 6D94 # AF4C 70CA # AF4D 70D8 # AF4E 70E4 # AF4F 70D9 # AF50 70C8 # AF51 70CF # AF52 7239 # AF53 7279 # AF54 72FC # AF55 72F9 # AF56 72FD # AF57 72F8 # AF58 72F7 # AF59 7386 # AF5A 73ED # AF5B 7409 # AF5C 73EE # AF5D 73E0 # AF5E 73EA # AF5F 73DE # AF60 7554 # AF61 755D # AF62 755C # AF63 755A # AF64 7559 # AF65 75BE # AF66 75C5 # AF67 75C7 # AF68 75B2 # AF69 75B3 # AF6A 75BD # AF6B 75BC # AF6C 75B9 # AF6D 75C2 # AF6E 75B8 # AF6F 768B # AF70 76B0 # AF71 76CA # AF72 76CD # AF73 76CE # AF74 7729 # AF75 771F # AF76 7720 # AF77 7728 # AF78 77E9 # AF79 7830 # AF7A 7827 # AF7B 7838 # AF7C 781D # AF7D 7834 # AF7E 7837 # AFA1 7825 # AFA2 782D # AFA3 7820 # AFA4 781F # AFA5 7832 # AFA6 7955 # AFA7 7950 # AFA8 7960 # AFA9 795F # AFAA 7956 # AFAB 795E # AFAC 795D # AFAD 7957 # AFAE 795A # AFAF 79E4 # AFB0 79E3 # AFB1 79E7 # AFB2 79DF # AFB3 79E6 # AFB4 79E9 # AFB5 79D8 # AFB6 7A84 # AFB7 7A88 # AFB8 7AD9 # AFB9 7B06 # AFBA 7B11 # AFBB 7C89 # AFBC 7D21 # AFBD 7D17 # AFBE 7D0B # AFBF 7D0A # AFC0 7D20 # AFC1 7D22 # AFC2 7D14 # AFC3 7D10 # AFC4 7D15 # AFC5 7D1A # AFC6 7D1C # AFC7 7D0D # AFC8 7D19 # AFC9 7D1B # AFCA 7F3A # AFCB 7F5F # AFCC 7F94 # AFCD 7FC5 # AFCE 7FC1 # AFCF 8006 # AFD0 8018 # AFD1 8015 # AFD2 8019 # AFD3 8017 # AFD4 803D # AFD5 803F # AFD6 80F1 # AFD7 8102 # AFD8 80F0 # AFD9 8105 # AFDA 80ED # AFDB 80F4 # AFDC 8106 # AFDD 80F8 # AFDE 80F3 # AFDF 8108 # AFE0 80FD # AFE1 810A # AFE2 80FC # AFE3 80EF # AFE4 81ED # AFE5 81EC # AFE6 8200 # AFE7 8210 # AFE8 822A # AFE9 822B # AFEA 8228 # AFEB 822C # AFEC 82BB # AFED 832B # AFEE 8352 # AFEF 8354 # AFF0 834A # AFF1 8338 # AFF2 8350 # AFF3 8349 # AFF4 8335 # AFF5 8334 # AFF6 834F # AFF7 8332 # AFF8 8339 # AFF9 8336 # AFFA 8317 # AFFB 8340 # AFFC 8331 # AFFD 8328 # AFFE 8343 # B040 8654 # B041 868A # B042 86AA # B043 8693 # B044 86A4 # B045 86A9 # B046 868C # B047 86A3 # B048 869C # B049 8870 # B04A 8877 # B04B 8881 # B04C 8882 # B04D 887D # B04E 8879 # B04F 8A18 # B050 8A10 # B051 8A0E # B052 8A0C # B053 8A15 # B054 8A0A # B055 8A17 # B056 8A13 # B057 8A16 # B058 8A0F # B059 8A11 # B05A 8C48 # B05B 8C7A # B05C 8C79 # B05D 8CA1 # B05E 8CA2 # B05F 8D77 # B060 8EAC # B061 8ED2 # B062 8ED4 # B063 8ECF # B064 8FB1 # B065 9001 # B066 9006 # B067 8FF7 # B068 9000 # B069 8FFA # B06A 8FF4 # B06B 9003 # B06C 8FFD # B06D 9005 # B06E 8FF8 # B06F 9095 # B070 90E1 # B071 90DD # B072 90E2 # B073 9152 # B074 914D # B075 914C # B076 91D8 # B077 91DD # B078 91D7 # B079 91DC # B07A 91D9 # B07B 9583 # B07C 9662 # B07D 9663 # B07E 9661 # B0A1 965B # B0A2 965D # B0A3 9664 # B0A4 9658 # B0A5 965E # B0A6 96BB # B0A7 98E2 # B0A8 99AC # B0A9 9AA8 # B0AA 9AD8 # B0AB 9B25 # B0AC 9B32 # B0AD 9B3C # B0AE 4E7E # B0AF 507A # B0B0 507D # B0B1 505C # B0B2 5047 # B0B3 5043 # B0B4 504C # B0B5 505A # B0B6 5049 # B0B7 5065 # B0B8 5076 # B0B9 504E # B0BA 5055 # B0BB 5075 # B0BC 5074 # B0BD 5077 # B0BE 504F # B0BF 500F # B0C0 506F # B0C1 506D # B0C2 515C # B0C3 5195 # B0C4 51F0 # B0C5 526A # B0C6 526F # B0C7 52D2 # B0C8 52D9 # B0C9 52D8 # B0CA 52D5 # B0CB 5310 # B0CC 530F # B0CD 5319 # B0CE 533F # B0CF 5340 # B0D0 533E # B0D1 53C3 # B0D2 66FC # B0D3 5546 # B0D4 556A # B0D5 5566 # B0D6 5544 # B0D7 555E # B0D8 5561 # B0D9 5543 # B0DA 554A # B0DB 5531 # B0DC 5556 # B0DD 554F # B0DE 5555 # B0DF 552F # B0E0 5564 # B0E1 5538 # B0E2 552E # B0E3 555C # B0E4 552C # B0E5 5563 # B0E6 5533 # B0E7 5541 # B0E8 5557 # B0E9 5708 # B0EA 570B # B0EB 5709 # B0EC 57DF # B0ED 5805 # B0EE 580A # B0EF 5806 # B0F0 57E0 # B0F1 57E4 # B0F2 57FA # B0F3 5802 # B0F4 5835 # B0F5 57F7 # B0F6 57F9 # B0F7 5920 # B0F8 5962 # B0F9 5A36 # B0FA 5A41 # B0FB 5A49 # B0FC 5A66 # B0FD 5A6A # B0FE 5A40 # B140 5A3C # B141 5A62 # B142 5A5A # B143 5A46 # B144 5A4A # B145 5B70 # B146 5BC7 # B147 5BC5 # B148 5BC4 # B149 5BC2 # B14A 5BBF # B14B 5BC6 # B14C 5C09 # B14D 5C08 # B14E 5C07 # B14F 5C60 # B150 5C5C # B151 5C5D # B152 5D07 # B153 5D06 # B154 5D0E # B155 5D1B # B156 5D16 # B157 5D22 # B158 5D11 # B159 5D29 # B15A 5D14 # B15B 5D19 # B15C 5D24 # B15D 5D27 # B15E 5D17 # B15F 5DE2 # B160 5E38 # B161 5E36 # B162 5E33 # B163 5E37 # B164 5EB7 # B165 5EB8 # B166 5EB6 # B167 5EB5 # B168 5EBE # B169 5F35 # B16A 5F37 # B16B 5F57 # B16C 5F6C # B16D 5F69 # B16E 5F6B # B16F 5F97 # B170 5F99 # B171 5F9E # B172 5F98 # B173 5FA1 # B174 5FA0 # B175 5F9C # B176 607F # B177 60A3 # B178 6089 # B179 60A0 # B17A 60A8 # B17B 60CB # B17C 60B4 # B17D 60E6 # B17E 60BD # B1A1 60C5 # B1A2 60BB # B1A3 60B5 # B1A4 60DC # B1A5 60BC # B1A6 60D8 # B1A7 60D5 # B1A8 60C6 # B1A9 60DF # B1AA 60B8 # B1AB 60DA # B1AC 60C7 # B1AD 621A # B1AE 621B # B1AF 6248 # B1B0 63A0 # B1B1 63A7 # B1B2 6372 # B1B3 6396 # B1B4 63A2 # B1B5 63A5 # B1B6 6377 # B1B7 6367 # B1B8 6398 # B1B9 63AA # B1BA 6371 # B1BB 63A9 # B1BC 6389 # B1BD 6383 # B1BE 639B # B1BF 636B # B1C0 63A8 # B1C1 6384 # B1C2 6388 # B1C3 6399 # B1C4 63A1 # B1C5 63AC # B1C6 6392 # B1C7 638F # B1C8 6380 # B1C9 637B # B1CA 6369 # B1CB 6368 # B1CC 637A # B1CD 655D # B1CE 6556 # B1CF 6551 # B1D0 6559 # B1D1 6557 # B1D2 555F # B1D3 654F # B1D4 6558 # B1D5 6555 # B1D6 6554 # B1D7 659C # B1D8 659B # B1D9 65AC # B1DA 65CF # B1DB 65CB # B1DC 65CC # B1DD 65CE # B1DE 665D # B1DF 665A # B1E0 6664 # B1E1 6668 # B1E2 6666 # B1E3 665E # B1E4 66F9 # B1E5 52D7 # B1E6 671B # B1E7 6881 # B1E8 68AF # B1E9 68A2 # B1EA 6893 # B1EB 68B5 # B1EC 687F # B1ED 6876 # B1EE 68B1 # B1EF 68A7 # B1F0 6897 # B1F1 68B0 # B1F2 6883 # B1F3 68C4 # B1F4 68AD # B1F5 6886 # B1F6 6885 # B1F7 6894 # B1F8 689D # B1F9 68A8 # B1FA 689F # B1FB 68A1 # B1FC 6882 # B1FD 6B32 # B1FE 6BBA # B240 6BEB # B241 6BEC # B242 6C2B # B243 6D8E # B244 6DBC # B245 6DF3 # B246 6DD9 # B247 6DB2 # B248 6DE1 # B249 6DCC # B24A 6DE4 # B24B 6DFB # B24C 6DFA # B24D 6E05 # B24E 6DC7 # B24F 6DCB # B250 6DAF # B251 6DD1 # B252 6DAE # B253 6DDE # B254 6DF9 # B255 6DB8 # B256 6DF7 # B257 6DF5 # B258 6DC5 # B259 6DD2 # B25A 6E1A # B25B 6DB5 # B25C 6DDA # B25D 6DEB # B25E 6DD8 # B25F 6DEA # B260 6DF1 # B261 6DEE # B262 6DE8 # B263 6DC6 # B264 6DC4 # B265 6DAA # B266 6DEC # B267 6DBF # B268 6DE6 # B269 70F9 # B26A 7109 # B26B 710A # B26C 70FD # B26D 70EF # B26E 723D # B26F 727D # B270 7281 # B271 731C # B272 731B # B273 7316 # B274 7313 # B275 7319 # B276 7387 # B277 7405 # B278 740A # B279 7403 # B27A 7406 # B27B 73FE # B27C 740D # B27D 74E0 # B27E 74F6 # B2A1 74F7 # B2A2 751C # B2A3 7522 # B2A4 7565 # B2A5 7566 # B2A6 7562 # B2A7 7570 # B2A8 758F # B2A9 75D4 # B2AA 75D5 # B2AB 75B5 # B2AC 75CA # B2AD 75CD # B2AE 768E # B2AF 76D4 # B2B0 76D2 # B2B1 76DB # B2B2 7737 # B2B3 773E # B2B4 773C # B2B5 7736 # B2B6 7738 # B2B7 773A # B2B8 786B # B2B9 7843 # B2BA 784E # B2BB 7965 # B2BC 7968 # B2BD 796D # B2BE 79FB # B2BF 7A92 # B2C0 7A95 # B2C1 7B20 # B2C2 7B28 # B2C3 7B1B # B2C4 7B2C # B2C5 7B26 # B2C6 7B19 # B2C7 7B1E # B2C8 7B2E # B2C9 7C92 # B2CA 7C97 # B2CB 7C95 # B2CC 7D46 # B2CD 7D43 # B2CE 7D71 # B2CF 7D2E # B2D0 7D39 # B2D1 7D3C # B2D2 7D40 # B2D3 7D30 # B2D4 7D33 # B2D5 7D44 # B2D6 7D2F # B2D7 7D42 # B2D8 7D32 # B2D9 7D31 # B2DA 7F3D # B2DB 7F9E # B2DC 7F9A # B2DD 7FCC # B2DE 7FCE # B2DF 7FD2 # B2E0 801C # B2E1 804A # B2E2 8046 # B2E3 812F # B2E4 8116 # B2E5 8123 # B2E6 812B # B2E7 8129 # B2E8 8130 # B2E9 8124 # B2EA 8202 # B2EB 8235 # B2EC 8237 # B2ED 8236 # B2EE 8239 # B2EF 838E # B2F0 839E # B2F1 8398 # B2F2 8378 # B2F3 83A2 # B2F4 8396 # B2F5 83BD # B2F6 83AB # B2F7 8392 # B2F8 838A # B2F9 8393 # B2FA 8389 # B2FB 83A0 # B2FC 8377 # B2FD 837B # B2FE 837C # B340 8386 # B341 83A7 # B342 8655 # B343 5F6A # B344 86C7 # B345 86C0 # B346 86B6 # B347 86C4 # B348 86B5 # B349 86C6 # B34A 86CB # B34B 86B1 # B34C 86AF # B34D 86C9 # B34E 8853 # B34F 889E # B350 8888 # B351 88AB # B352 8892 # B353 8896 # B354 888D # B355 888B # B356 8993 # B357 898F # B358 8A2A # B359 8A1D # B35A 8A23 # B35B 8A25 # B35C 8A31 # B35D 8A2D # B35E 8A1F # B35F 8A1B # B360 8A22 # B361 8C49 # B362 8C5A # B363 8CA9 # B364 8CAC # B365 8CAB # B366 8CA8 # B367 8CAA # B368 8CA7 # B369 8D67 # B36A 8D66 # B36B 8DBE # B36C 8DBA # B36D 8EDB # B36E 8EDF # B36F 9019 # B370 900D # B371 901A # B372 9017 # B373 9023 # B374 901F # B375 901D # B376 9010 # B377 9015 # B378 901E # B379 9020 # B37A 900F # B37B 9022 # B37C 9016 # B37D 901B # B37E 9014 # B3A1 90E8 # B3A2 90ED # B3A3 90FD # B3A4 9157 # B3A5 91CE # B3A6 91F5 # B3A7 91E6 # B3A8 91E3 # B3A9 91E7 # B3AA 91ED # B3AB 91E9 # B3AC 9589 # B3AD 966A # B3AE 9675 # B3AF 9673 # B3B0 9678 # B3B1 9670 # B3B2 9674 # B3B3 9676 # B3B4 9677 # B3B5 966C # B3B6 96C0 # B3B7 96EA # B3B8 96E9 # B3B9 7AE0 # B3BA 7ADF # B3BB 9802 # B3BC 9803 # B3BD 9B5A # B3BE 9CE5 # B3BF 9E75 # B3C0 9E7F # B3C1 9EA5 # B3C2 9EBB # B3C3 50A2 # B3C4 508D # B3C5 5085 # B3C6 5099 # B3C7 5091 # B3C8 5080 # B3C9 5096 # B3CA 5098 # B3CB 509A # B3CC 6700 # B3CD 51F1 # B3CE 5272 # B3CF 5274 # B3D0 5275 # B3D1 5269 # B3D2 52DE # B3D3 52DD # B3D4 52DB # B3D5 535A # B3D6 53A5 # B3D7 557B # B3D8 5580 # B3D9 55A7 # B3DA 557C # B3DB 558A # B3DC 559D # B3DD 5598 # B3DE 5582 # B3DF 559C # B3E0 55AA # B3E1 5594 # B3E2 5587 # B3E3 558B # B3E4 5583 # B3E5 55B3 # B3E6 55AE # B3E7 559F # B3E8 553E # B3E9 55B2 # B3EA 559A # B3EB 55BB # B3EC 55AC # B3ED 55B1 # B3EE 557E # B3EF 5589 # B3F0 55AB # B3F1 5599 # B3F2 570D # B3F3 582F # B3F4 582A # B3F5 5834 # B3F6 5824 # B3F7 5830 # B3F8 5831 # B3F9 5821 # B3FA 581D # B3FB 5820 # B3FC 58F9 # B3FD 58FA # B3FE 5960 # B440 5A77 # B441 5A9A # B442 5A7F # B443 5A92 # B444 5A9B # B445 5AA7 # B446 5B73 # B447 5B71 # B448 5BD2 # B449 5BCC # B44A 5BD3 # B44B 5BD0 # B44C 5C0A # B44D 5C0B # B44E 5C31 # B44F 5D4C # B450 5D50 # B451 5D34 # B452 5D47 # B453 5DFD # B454 5E45 # B455 5E3D # B456 5E40 # B457 5E43 # B458 5E7E # B459 5ECA # B45A 5EC1 # B45B 5EC2 # B45C 5EC4 # B45D 5F3C # B45E 5F6D # B45F 5FA9 # B460 5FAA # B461 5FA8 # B462 60D1 # B463 60E1 # B464 60B2 # B465 60B6 # B466 60E0 # B467 611C # B468 6123 # B469 60FA # B46A 6115 # B46B 60F0 # B46C 60FB # B46D 60F4 # B46E 6168 # B46F 60F1 # B470 610E # B471 60F6 # B472 6109 # B473 6100 # B474 6112 # B475 621F # B476 6249 # B477 63A3 # B478 638C # B479 63CF # B47A 63C0 # B47B 63E9 # B47C 63C9 # B47D 63C6 # B47E 63CD # B4A1 63D2 # B4A2 63E3 # B4A3 63D0 # B4A4 63E1 # B4A5 63D6 # B4A6 63ED # B4A7 63EE # B4A8 6376 # B4A9 63F4 # B4AA 63EA # B4AB 63DB # B4AC 6452 # B4AD 63DA # B4AE 63F9 # B4AF 655E # B4B0 6566 # B4B1 6562 # B4B2 6563 # B4B3 6591 # B4B4 6590 # B4B5 65AF # B4B6 666E # B4B7 6670 # B4B8 6674 # B4B9 6676 # B4BA 666F # B4BB 6691 # B4BC 667A # B4BD 667E # B4BE 6677 # B4BF 66FE # B4C0 66FF # B4C1 671F # B4C2 671D # B4C3 68FA # B4C4 68D5 # B4C5 68E0 # B4C6 68D8 # B4C7 68D7 # B4C8 6905 # B4C9 68DF # B4CA 68F5 # B4CB 68EE # B4CC 68E7 # B4CD 68F9 # B4CE 68D2 # B4CF 68F2 # B4D0 68E3 # B4D1 68CB # B4D2 68CD # B4D3 690D # B4D4 6912 # B4D5 690E # B4D6 68C9 # B4D7 68DA # B4D8 696E # B4D9 68FB # B4DA 6B3E # B4DB 6B3A # B4DC 6B3D # B4DD 6B98 # B4DE 6B96 # B4DF 6BBC # B4E0 6BEF # B4E1 6C2E # B4E2 6C2F # B4E3 6C2C # B4E4 6E2F # B4E5 6E38 # B4E6 6E54 # B4E7 6E21 # B4E8 6E32 # B4E9 6E67 # B4EA 6E4A # B4EB 6E20 # B4EC 6E25 # B4ED 6E23 # B4EE 6E1B # B4EF 6E5B # B4F0 6E58 # B4F1 6E24 # B4F2 6E56 # B4F3 6E6E # B4F4 6E2D # B4F5 6E26 # B4F6 6E6F # B4F7 6E34 # B4F8 6E4D # B4F9 6E3A # B4FA 6E2C # B4FB 6E43 # B4FC 6E1D # B4FD 6E3E # B4FE 6ECB # B540 6E89 # B541 6E19 # B542 6E4E # B543 6E63 # B544 6E44 # B545 6E72 # B546 6E69 # B547 6E5F # B548 7119 # B549 711A # B54A 7126 # B54B 7130 # B54C 7121 # B54D 7136 # B54E 716E # B54F 711C # B550 724C # B551 7284 # B552 7280 # B553 7336 # B554 7325 # B555 7334 # B556 7329 # B557 743A # B558 742A # B559 7433 # B55A 7422 # B55B 7425 # B55C 7435 # B55D 7436 # B55E 7434 # B55F 742F # B560 741B # B561 7426 # B562 7428 # B563 7525 # B564 7526 # B565 756B # B566 756A # B567 75E2 # B568 75DB # B569 75E3 # B56A 75D9 # B56B 75D8 # B56C 75DE # B56D 75E0 # B56E 767B # B56F 767C # B570 7696 # B571 7693 # B572 76B4 # B573 76DC # B574 774F # B575 77ED # B576 785D # B577 786C # B578 786F # B579 7A0D # B57A 7A08 # B57B 7A0B # B57C 7A05 # B57D 7A00 # B57E 7A98 # B5A1 7A97 # B5A2 7A96 # B5A3 7AE5 # B5A4 7AE3 # B5A5 7B49 # B5A6 7B56 # B5A7 7B46 # B5A8 7B50 # B5A9 7B52 # B5AA 7B54 # B5AB 7B4D # B5AC 7B4B # B5AD 7B4F # B5AE 7B51 # B5AF 7C9F # B5B0 7CA5 # B5B1 7D5E # B5B2 7D50 # B5B3 7D68 # B5B4 7D55 # B5B5 7D2B # B5B6 7D6E # B5B7 7D72 # B5B8 7D61 # B5B9 7D66 # B5BA 7D62 # B5BB 7D70 # B5BC 7D73 # B5BD 5584 # B5BE 7FD4 # B5BF 7FD5 # B5C0 800B # B5C1 8052 # B5C2 8085 # B5C3 8155 # B5C4 8154 # B5C5 814B # B5C6 8151 # B5C7 814E # B5C8 8139 # B5C9 8146 # B5CA 813E # B5CB 814C # B5CC 8153 # B5CD 8174 # B5CE 8212 # B5CF 821C # B5D0 83E9 # B5D1 8403 # B5D2 83F8 # B5D3 840D # B5D4 83E0 # B5D5 83C5 # B5D6 840B # B5D7 83C1 # B5D8 83EF # B5D9 83F1 # B5DA 83F4 # B5DB 8457 # B5DC 840A # B5DD 83F0 # B5DE 840C # B5DF 83CC # B5E0 83FD # B5E1 83F2 # B5E2 83CA # B5E3 8438 # B5E4 840E # B5E5 8404 # B5E6 83DC # B5E7 8407 # B5E8 83D4 # B5E9 83DF # B5EA 865B # B5EB 86DF # B5EC 86D9 # B5ED 86ED # B5EE 86D4 # B5EF 86DB # B5F0 86E4 # B5F1 86D0 # B5F2 86DE # B5F3 8857 # B5F4 88C1 # B5F5 88C2 # B5F6 88B1 # B5F7 8983 # B5F8 8996 # B5F9 8A3B # B5FA 8A60 # B5FB 8A55 # B5FC 8A5E # B5FD 8A3C # B5FE 8A41 # B640 8A54 # B641 8A5B # B642 8A50 # B643 8A46 # B644 8A34 # B645 8A3A # B646 8A36 # B647 8A56 # B648 8C61 # B649 8C82 # B64A 8CAF # B64B 8CBC # B64C 8CB3 # B64D 8CBD # B64E 8CC1 # B64F 8CBB # B650 8CC0 # B651 8CB4 # B652 8CB7 # B653 8CB6 # B654 8CBF # B655 8CB8 # B656 8D8A # B657 8D85 # B658 8D81 # B659 8DCE # B65A 8DDD # B65B 8DCB # B65C 8DDA # B65D 8DD1 # B65E 8DCC # B65F 8DDB # B660 8DC6 # B661 8EFB # B662 8EF8 # B663 8EFC # B664 8F9C # B665 902E # B666 9035 # B667 9031 # B668 9038 # B669 9032 # B66A 9036 # B66B 9102 # B66C 90F5 # B66D 9109 # B66E 90FE # B66F 9163 # B670 9165 # B671 91CF # B672 9214 # B673 9215 # B674 9223 # B675 9209 # B676 921E # B677 920D # B678 9210 # B679 9207 # B67A 9211 # B67B 9594 # B67C 958F # B67D 958B # B67E 9591 # B6A1 9593 # B6A2 9592 # B6A3 958E # B6A4 968A # B6A5 968E # B6A6 968B # B6A7 967D # B6A8 9685 # B6A9 9686 # B6AA 968D # B6AB 9672 # B6AC 9684 # B6AD 96C1 # B6AE 96C5 # B6AF 96C4 # B6B0 96C6 # B6B1 96C7 # B6B2 96EF # B6B3 96F2 # B6B4 97CC # B6B5 9805 # B6B6 9806 # B6B7 9808 # B6B8 98E7 # B6B9 98EA # B6BA 98EF # B6BB 98E9 # B6BC 98F2 # B6BD 98ED # B6BE 99AE # B6BF 99AD # B6C0 9EC3 # B6C1 9ECD # B6C2 9ED1 # B6C3 4E82 # B6C4 50AD # B6C5 50B5 # B6C6 50B2 # B6C7 50B3 # B6C8 50C5 # B6C9 50BE # B6CA 50AC # B6CB 50B7 # B6CC 50BB # B6CD 50AF # B6CE 50C7 # B6CF 527F # B6D0 5277 # B6D1 527D # B6D2 52DF # B6D3 52E6 # B6D4 52E4 # B6D5 52E2 # B6D6 52E3 # B6D7 532F # B6D8 55DF # B6D9 55E8 # B6DA 55D3 # B6DB 55E6 # B6DC 55CE # B6DD 55DC # B6DE 55C7 # B6DF 55D1 # B6E0 55E3 # B6E1 55E4 # B6E2 55EF # B6E3 55DA # B6E4 55E1 # B6E5 55C5 # B6E6 55C6 # B6E7 55E5 # B6E8 55C9 # B6E9 5712 # B6EA 5713 # B6EB 585E # B6EC 5851 # B6ED 5858 # B6EE 5857 # B6EF 585A # B6F0 5854 # B6F1 586B # B6F2 584C # B6F3 586D # B6F4 584A # B6F5 5862 # B6F6 5852 # B6F7 584B # B6F8 5967 # B6F9 5AC1 # B6FA 5AC9 # B6FB 5ACC # B6FC 5ABE # B6FD 5ABD # B6FE 5ABC # B740 5AB3 # B741 5AC2 # B742 5AB2 # B743 5D69 # B744 5D6F # B745 5E4C # B746 5E79 # B747 5EC9 # B748 5EC8 # B749 5F12 # B74A 5F59 # B74B 5FAC # B74C 5FAE # B74D 611A # B74E 610F # B74F 6148 # B750 611F # B751 60F3 # B752 611B # B753 60F9 # B754 6101 # B755 6108 # B756 614E # B757 614C # B758 6144 # B759 614D # B75A 613E # B75B 6134 # B75C 6127 # B75D 610D # B75E 6106 # B75F 6137 # B760 6221 # B761 6222 # B762 6413 # B763 643E # B764 641E # B765 642A # B766 642D # B767 643D # B768 642C # B769 640F # B76A 641C # B76B 6414 # B76C 640D # B76D 6436 # B76E 6416 # B76F 6417 # B770 6406 # B771 656C # B772 659F # B773 65B0 # B774 6697 # B775 6689 # B776 6687 # B777 6688 # B778 6696 # B779 6684 # B77A 6698 # B77B 668D # B77C 6703 # B77D 6994 # B77E 696D # B7A1 695A # B7A2 6977 # B7A3 6960 # B7A4 6954 # B7A5 6975 # B7A6 6930 # B7A7 6982 # B7A8 694A # B7A9 6968 # B7AA 696B # B7AB 695E # B7AC 6953 # B7AD 6979 # B7AE 6986 # B7AF 695D # B7B0 6963 # B7B1 695B # B7B2 6B47 # B7B3 6B72 # B7B4 6BC0 # B7B5 6BBF # B7B6 6BD3 # B7B7 6BFD # B7B8 6EA2 # B7B9 6EAF # B7BA 6ED3 # B7BB 6EB6 # B7BC 6EC2 # B7BD 6E90 # B7BE 6E9D # B7BF 6EC7 # B7C0 6EC5 # B7C1 6EA5 # B7C2 6E98 # B7C3 6EBC # B7C4 6EBA # B7C5 6EAB # B7C6 6ED1 # B7C7 6E96 # B7C8 6E9C # B7C9 6EC4 # B7CA 6ED4 # B7CB 6EAA # B7CC 6EA7 # B7CD 6EB4 # B7CE 714E # B7CF 7159 # B7D0 7169 # B7D1 7164 # B7D2 7149 # B7D3 7167 # B7D4 715C # B7D5 716C # B7D6 7166 # B7D7 714C # B7D8 7165 # B7D9 715E # B7DA 7146 # B7DB 7168 # B7DC 7156 # B7DD 723A # B7DE 7252 # B7DF 7337 # B7E0 7345 # B7E1 733F # B7E2 733E # B7E3 746F # B7E4 745A # B7E5 7455 # B7E6 745F # B7E7 745E # B7E8 7441 # B7E9 743F # B7EA 7459 # B7EB 745B # B7EC 745C # B7ED 7576 # B7EE 7578 # B7EF 7600 # B7F0 75F0 # B7F1 7601 # B7F2 75F2 # B7F3 75F1 # B7F4 75FA # B7F5 75FF # B7F6 75F4 # B7F7 75F3 # B7F8 76DE # B7F9 76DF # B7FA 775B # B7FB 776B # B7FC 7766 # B7FD 775E # B7FE 7763 # B840 7779 # B841 776A # B842 776C # B843 775C # B844 7765 # B845 7768 # B846 7762 # B847 77EE # B848 788E # B849 78B0 # B84A 7897 # B84B 7898 # B84C 788C # B84D 7889 # B84E 787C # B84F 7891 # B850 7893 # B851 787F # B852 797A # B853 797F # B854 7981 # B855 842C # B856 79BD # B857 7A1C # B858 7A1A # B859 7A20 # B85A 7A14 # B85B 7A1F # B85C 7A1E # B85D 7A9F # B85E 7AA0 # B85F 7B77 # B860 7BC0 # B861 7B60 # B862 7B6E # B863 7B67 # B864 7CB1 # B865 7CB3 # B866 7CB5 # B867 7D93 # B868 7D79 # B869 7D91 # B86A 7D81 # B86B 7D8F # B86C 7D5B # B86D 7F6E # B86E 7F69 # B86F 7F6A # B870 7F72 # B871 7FA9 # B872 7FA8 # B873 7FA4 # B874 8056 # B875 8058 # B876 8086 # B877 8084 # B878 8171 # B879 8170 # B87A 8178 # B87B 8165 # B87C 816E # B87D 8173 # B87E 816B # B8A1 8179 # B8A2 817A # B8A3 8166 # B8A4 8205 # B8A5 8247 # B8A6 8482 # B8A7 8477 # B8A8 843D # B8A9 8431 # B8AA 8475 # B8AB 8466 # B8AC 846B # B8AD 8449 # B8AE 846C # B8AF 845B # B8B0 843C # B8B1 8435 # B8B2 8461 # B8B3 8463 # B8B4 8469 # B8B5 846D # B8B6 8446 # B8B7 865E # B8B8 865C # B8B9 865F # B8BA 86F9 # B8BB 8713 # B8BC 8708 # B8BD 8707 # B8BE 8700 # B8BF 86FE # B8C0 86FB # B8C1 8702 # B8C2 8703 # B8C3 8706 # B8C4 870A # B8C5 8859 # B8C6 88DF # B8C7 88D4 # B8C8 88D9 # B8C9 88DC # B8CA 88D8 # B8CB 88DD # B8CC 88E1 # B8CD 88CA # B8CE 88D5 # B8CF 88D2 # B8D0 899C # B8D1 89E3 # B8D2 8A6B # B8D3 8A72 # B8D4 8A73 # B8D5 8A66 # B8D6 8A69 # B8D7 8A70 # B8D8 8A87 # B8D9 8A7C # B8DA 8A63 # B8DB 8AA0 # B8DC 8A71 # B8DD 8A85 # B8DE 8A6D # B8DF 8A62 # B8E0 8A6E # B8E1 8A6C # B8E2 8A79 # B8E3 8A7B # B8E4 8A3E # B8E5 8A68 # B8E6 8C62 # B8E7 8C8A # B8E8 8C89 # B8E9 8CCA # B8EA 8CC7 # B8EB 8CC8 # B8EC 8CC4 # B8ED 8CB2 # B8EE 8CC3 # B8EF 8CC2 # B8F0 8CC5 # B8F1 8DE1 # B8F2 8DDF # B8F3 8DE8 # B8F4 8DEF # B8F5 8DF3 # B8F6 8DFA # B8F7 8DEA # B8F8 8DE4 # B8F9 8DE6 # B8FA 8EB2 # B8FB 8F03 # B8FC 8F09 # B8FD 8EFE # B8FE 8F0A # B940 8F9F # B941 8FB2 # B942 904B # B943 904A # B944 9053 # B945 9042 # B946 9054 # B947 903C # B948 9055 # B949 9050 # B94A 9047 # B94B 904F # B94C 904E # B94D 904D # B94E 9051 # B94F 903E # B950 9041 # B951 9112 # B952 9117 # B953 916C # B954 916A # B955 9169 # B956 91C9 # B957 9237 # B958 9257 # B959 9238 # B95A 923D # B95B 9240 # B95C 923E # B95D 925B # B95E 924B # B95F 9264 # B960 9251 # B961 9234 # B962 9249 # B963 924D # B964 9245 # B965 9239 # B966 923F # B967 925A # B968 9598 # B969 9698 # B96A 9694 # B96B 9695 # B96C 96CD # B96D 96CB # B96E 96C9 # B96F 96CA # B970 96F7 # B971 96FB # B972 96F9 # B973 96F6 # B974 9756 # B975 9774 # B976 9776 # B977 9810 # B978 9811 # B979 9813 # B97A 980A # B97B 9812 # B97C 980C # B97D 98FC # B97E 98F4 # B9A1 98FD # B9A2 98FE # B9A3 99B3 # B9A4 99B1 # B9A5 99B4 # B9A6 9AE1 # B9A7 9CE9 # B9A8 9E82 # B9A9 9F0E # B9AA 9F13 # B9AB 9F20 # B9AC 50E7 # B9AD 50EE # B9AE 50E5 # B9AF 50D6 # B9B0 50ED # B9B1 50DA # B9B2 50D5 # B9B3 50CF # B9B4 50D1 # B9B5 50F1 # B9B6 50CE # B9B7 50E9 # B9B8 5162 # B9B9 51F3 # B9BA 5283 # B9BB 5282 # B9BC 5331 # B9BD 53AD # B9BE 55FE # B9BF 5600 # B9C0 561B # B9C1 5617 # B9C2 55FD # B9C3 5614 # B9C4 5606 # B9C5 5609 # B9C6 560D # B9C7 560E # B9C8 55F7 # B9C9 5616 # B9CA 561F # B9CB 5608 # B9CC 5610 # B9CD 55F6 # B9CE 5718 # B9CF 5716 # B9D0 5875 # B9D1 587E # B9D2 5883 # B9D3 5893 # B9D4 588A # B9D5 5879 # B9D6 5885 # B9D7 587D # B9D8 58FD # B9D9 5925 # B9DA 5922 # B9DB 5924 # B9DC 596A # B9DD 5969 # B9DE 5AE1 # B9DF 5AE6 # B9E0 5AE9 # B9E1 5AD7 # B9E2 5AD6 # B9E3 5AD8 # B9E4 5AE3 # B9E5 5B75 # B9E6 5BDE # B9E7 5BE7 # B9E8 5BE1 # B9E9 5BE5 # B9EA 5BE6 # B9EB 5BE8 # B9EC 5BE2 # B9ED 5BE4 # B9EE 5BDF # B9EF 5C0D # B9F0 5C62 # B9F1 5D84 # B9F2 5D87 # B9F3 5E5B # B9F4 5E63 # B9F5 5E55 # B9F6 5E57 # B9F7 5E54 # B9F8 5ED3 # B9F9 5ED6 # B9FA 5F0A # B9FB 5F46 # B9FC 5F70 # B9FD 5FB9 # B9FE 6147 # BA40 613F # BA41 614B # BA42 6177 # BA43 6162 # BA44 6163 # BA45 615F # BA46 615A # BA47 6158 # BA48 6175 # BA49 622A # BA4A 6487 # BA4B 6458 # BA4C 6454 # BA4D 64A4 # BA4E 6478 # BA4F 645F # BA50 647A # BA51 6451 # BA52 6467 # BA53 6434 # BA54 646D # BA55 647B # BA56 6572 # BA57 65A1 # BA58 65D7 # BA59 65D6 # BA5A 66A2 # BA5B 66A8 # BA5C 669D # BA5D 699C # BA5E 69A8 # BA5F 6995 # BA60 69C1 # BA61 69AE # BA62 69D3 # BA63 69CB # BA64 699B # BA65 69B7 # BA66 69BB # BA67 69AB # BA68 69B4 # BA69 69D0 # BA6A 69CD # BA6B 69AD # BA6C 69CC # BA6D 69A6 # BA6E 69C3 # BA6F 69A3 # BA70 6B49 # BA71 6B4C # BA72 6C33 # BA73 6F33 # BA74 6F14 # BA75 6EFE # BA76 6F13 # BA77 6EF4 # BA78 6F29 # BA79 6F3E # BA7A 6F20 # BA7B 6F2C # BA7C 6F0F # BA7D 6F02 # BA7E 6F22 # BAA1 6EFF # BAA2 6EEF # BAA3 6F06 # BAA4 6F31 # BAA5 6F38 # BAA6 6F32 # BAA7 6F23 # BAA8 6F15 # BAA9 6F2B # BAAA 6F2F # BAAB 6F88 # BAAC 6F2A # BAAD 6EEC # BAAE 6F01 # BAAF 6EF2 # BAB0 6ECC # BAB1 6EF7 # BAB2 7194 # BAB3 7199 # BAB4 717D # BAB5 718A # BAB6 7184 # BAB7 7192 # BAB8 723E # BAB9 7292 # BABA 7296 # BABB 7344 # BABC 7350 # BABD 7464 # BABE 7463 # BABF 746A # BAC0 7470 # BAC1 746D # BAC2 7504 # BAC3 7591 # BAC4 7627 # BAC5 760D # BAC6 760B # BAC7 7609 # BAC8 7613 # BAC9 76E1 # BACA 76E3 # BACB 7784 # BACC 777D # BACD 777F # BACE 7761 # BACF 78C1 # BAD0 789F # BAD1 78A7 # BAD2 78B3 # BAD3 78A9 # BAD4 78A3 # BAD5 798E # BAD6 798F # BAD7 798D # BAD8 7A2E # BAD9 7A31 # BADA 7AAA # BADB 7AA9 # BADC 7AED # BADD 7AEF # BADE 7BA1 # BADF 7B95 # BAE0 7B8B # BAE1 7B75 # BAE2 7B97 # BAE3 7B9D # BAE4 7B94 # BAE5 7B8F # BAE6 7BB8 # BAE7 7B87 # BAE8 7B84 # BAE9 7CB9 # BAEA 7CBD # BAEB 7CBE # BAEC 7DBB # BAED 7DB0 # BAEE 7D9C # BAEF 7DBD # BAF0 7DBE # BAF1 7DA0 # BAF2 7DCA # BAF3 7DB4 # BAF4 7DB2 # BAF5 7DB1 # BAF6 7DBA # BAF7 7DA2 # BAF8 7DBF # BAF9 7DB5 # BAFA 7DB8 # BAFB 7DAD # BAFC 7DD2 # BAFD 7DC7 # BAFE 7DAC # BB40 7F70 # BB41 7FE0 # BB42 7FE1 # BB43 7FDF # BB44 805E # BB45 805A # BB46 8087 # BB47 8150 # BB48 8180 # BB49 818F # BB4A 8188 # BB4B 818A # BB4C 817F # BB4D 8182 # BB4E 81E7 # BB4F 81FA # BB50 8207 # BB51 8214 # BB52 821E # BB53 824B # BB54 84C9 # BB55 84BF # BB56 84C6 # BB57 84C4 # BB58 8499 # BB59 849E # BB5A 84B2 # BB5B 849C # BB5C 84CB # BB5D 84B8 # BB5E 84C0 # BB5F 84D3 # BB60 8490 # BB61 84BC # BB62 84D1 # BB63 84CA # BB64 873F # BB65 871C # BB66 873B # BB67 8722 # BB68 8725 # BB69 8734 # BB6A 8718 # BB6B 8755 # BB6C 8737 # BB6D 8729 # BB6E 88F3 # BB6F 8902 # BB70 88F4 # BB71 88F9 # BB72 88F8 # BB73 88FD # BB74 88E8 # BB75 891A # BB76 88EF # BB77 8AA6 # BB78 8A8C # BB79 8A9E # BB7A 8AA3 # BB7B 8A8D # BB7C 8AA1 # BB7D 8A93 # BB7E 8AA4 # BBA1 8AAA # BBA2 8AA5 # BBA3 8AA8 # BBA4 8A98 # BBA5 8A91 # BBA6 8A9A # BBA7 8AA7 # BBA8 8C6A # BBA9 8C8D # BBAA 8C8C # BBAB 8CD3 # BBAC 8CD1 # BBAD 8CD2 # BBAE 8D6B # BBAF 8D99 # BBB0 8D95 # BBB1 8DFC # BBB2 8F14 # BBB3 8F12 # BBB4 8F15 # BBB5 8F13 # BBB6 8FA3 # BBB7 9060 # BBB8 9058 # BBB9 905C # BBBA 9063 # BBBB 9059 # BBBC 905E # BBBD 9062 # BBBE 905D # BBBF 905B # BBC0 9119 # BBC1 9118 # BBC2 911E # BBC3 9175 # BBC4 9178 # BBC5 9177 # BBC6 9174 # BBC7 9278 # BBC8 9280 # BBC9 9285 # BBCA 9298 # BBCB 9296 # BBCC 927B # BBCD 9293 # BBCE 929C # BBCF 92A8 # BBD0 927C # BBD1 9291 # BBD2 95A1 # BBD3 95A8 # BBD4 95A9 # BBD5 95A3 # BBD6 95A5 # BBD7 95A4 # BBD8 9699 # BBD9 969C # BBDA 969B # BBDB 96CC # BBDC 96D2 # BBDD 9700 # BBDE 977C # BBDF 9785 # BBE0 97F6 # BBE1 9817 # BBE2 9818 # BBE3 98AF # BBE4 98B1 # BBE5 9903 # BBE6 9905 # BBE7 990C # BBE8 9909 # BBE9 99C1 # BBEA 9AAF # BBEB 9AB0 # BBEC 9AE6 # BBED 9B41 # BBEE 9B42 # BBEF 9CF4 # BBF0 9CF6 # BBF1 9CF3 # BBF2 9EBC # BBF3 9F3B # BBF4 9F4A # BBF5 5104 # BBF6 5100 # BBF7 50FB # BBF8 50F5 # BBF9 50F9 # BBFA 5102 # BBFB 5108 # BBFC 5109 # BBFD 5105 # BBFE 51DC # BC40 5287 # BC41 5288 # BC42 5289 # BC43 528D # BC44 528A # BC45 52F0 # BC46 53B2 # BC47 562E # BC48 563B # BC49 5639 # BC4A 5632 # BC4B 563F # BC4C 5634 # BC4D 5629 # BC4E 5653 # BC4F 564E # BC50 5657 # BC51 5674 # BC52 5636 # BC53 562F # BC54 5630 # BC55 5880 # BC56 589F # BC57 589E # BC58 58B3 # BC59 589C # BC5A 58AE # BC5B 58A9 # BC5C 58A6 # BC5D 596D # BC5E 5B09 # BC5F 5AFB # BC60 5B0B # BC61 5AF5 # BC62 5B0C # BC63 5B08 # BC64 5BEE # BC65 5BEC # BC66 5BE9 # BC67 5BEB # BC68 5C64 # BC69 5C65 # BC6A 5D9D # BC6B 5D94 # BC6C 5E62 # BC6D 5E5F # BC6E 5E61 # BC6F 5EE2 # BC70 5EDA # BC71 5EDF # BC72 5EDD # BC73 5EE3 # BC74 5EE0 # BC75 5F48 # BC76 5F71 # BC77 5FB7 # BC78 5FB5 # BC79 6176 # BC7A 6167 # BC7B 616E # BC7C 615D # BC7D 6155 # BC7E 6182 # BCA1 617C # BCA2 6170 # BCA3 616B # BCA4 617E # BCA5 61A7 # BCA6 6190 # BCA7 61AB # BCA8 618E # BCA9 61AC # BCAA 619A # BCAB 61A4 # BCAC 6194 # BCAD 61AE # BCAE 622E # BCAF 6469 # BCB0 646F # BCB1 6479 # BCB2 649E # BCB3 64B2 # BCB4 6488 # BCB5 6490 # BCB6 64B0 # BCB7 64A5 # BCB8 6493 # BCB9 6495 # BCBA 64A9 # BCBB 6492 # BCBC 64AE # BCBD 64AD # BCBE 64AB # BCBF 649A # BCC0 64AC # BCC1 6499 # BCC2 64A2 # BCC3 64B3 # BCC4 6575 # BCC5 6577 # BCC6 6578 # BCC7 66AE # BCC8 66AB # BCC9 66B4 # BCCA 66B1 # BCCB 6A23 # BCCC 6A1F # BCCD 69E8 # BCCE 6A01 # BCCF 6A1E # BCD0 6A19 # BCD1 69FD # BCD2 6A21 # BCD3 6A13 # BCD4 6A0A # BCD5 69F3 # BCD6 6A02 # BCD7 6A05 # BCD8 69ED # BCD9 6A11 # BCDA 6B50 # BCDB 6B4E # BCDC 6BA4 # BCDD 6BC5 # BCDE 6BC6 # BCDF 6F3F # BCE0 6F7C # BCE1 6F84 # BCE2 6F51 # BCE3 6F66 # BCE4 6F54 # BCE5 6F86 # BCE6 6F6D # BCE7 6F5B # BCE8 6F78 # BCE9 6F6E # BCEA 6F8E # BCEB 6F7A # BCEC 6F70 # BCED 6F64 # BCEE 6F97 # BCEF 6F58 # BCF0 6ED5 # BCF1 6F6F # BCF2 6F60 # BCF3 6F5F # BCF4 719F # BCF5 71AC # BCF6 71B1 # BCF7 71A8 # BCF8 7256 # BCF9 729B # BCFA 734E # BCFB 7357 # BCFC 7469 # BCFD 748B # BCFE 7483 # BD40 747E # BD41 7480 # BD42 757F # BD43 7620 # BD44 7629 # BD45 761F # BD46 7624 # BD47 7626 # BD48 7621 # BD49 7622 # BD4A 769A # BD4B 76BA # BD4C 76E4 # BD4D 778E # BD4E 7787 # BD4F 778C # BD50 7791 # BD51 778B # BD52 78CB # BD53 78C5 # BD54 78BA # BD55 78CA # BD56 78BE # BD57 78D5 # BD58 78BC # BD59 78D0 # BD5A 7A3F # BD5B 7A3C # BD5C 7A40 # BD5D 7A3D # BD5E 7A37 # BD5F 7A3B # BD60 7AAF # BD61 7AAE # BD62 7BAD # BD63 7BB1 # BD64 7BC4 # BD65 7BB4 # BD66 7BC6 # BD67 7BC7 # BD68 7BC1 # BD69 7BA0 # BD6A 7BCC # BD6B 7CCA # BD6C 7DE0 # BD6D 7DF4 # BD6E 7DEF # BD6F 7DFB # BD70 7DD8 # BD71 7DEC # BD72 7DDD # BD73 7DE8 # BD74 7DE3 # BD75 7DDA # BD76 7DDE # BD77 7DE9 # BD78 7D9E # BD79 7DD9 # BD7A 7DF2 # BD7B 7DF9 # BD7C 7F75 # BD7D 7F77 # BD7E 7FAF # BDA1 7FE9 # BDA2 8026 # BDA3 819B # BDA4 819C # BDA5 819D # BDA6 81A0 # BDA7 819A # BDA8 8198 # BDA9 8517 # BDAA 853D # BDAB 851A # BDAC 84EE # BDAD 852C # BDAE 852D # BDAF 8513 # BDB0 8511 # BDB1 8523 # BDB2 8521 # BDB3 8514 # BDB4 84EC # BDB5 8525 # BDB6 84FF # BDB7 8506 # BDB8 8782 # BDB9 8774 # BDBA 8776 # BDBB 8760 # BDBC 8766 # BDBD 8778 # BDBE 8768 # BDBF 8759 # BDC0 8757 # BDC1 874C # BDC2 8753 # BDC3 885B # BDC4 885D # BDC5 8910 # BDC6 8907 # BDC7 8912 # BDC8 8913 # BDC9 8915 # BDCA 890A # BDCB 8ABC # BDCC 8AD2 # BDCD 8AC7 # BDCE 8AC4 # BDCF 8A95 # BDD0 8ACB # BDD1 8AF8 # BDD2 8AB2 # BDD3 8AC9 # BDD4 8AC2 # BDD5 8ABF # BDD6 8AB0 # BDD7 8AD6 # BDD8 8ACD # BDD9 8AB6 # BDDA 8AB9 # BDDB 8ADB # BDDC 8C4C # BDDD 8C4E # BDDE 8C6C # BDDF 8CE0 # BDE0 8CDE # BDE1 8CE6 # BDE2 8CE4 # BDE3 8CEC # BDE4 8CED # BDE5 8CE2 # BDE6 8CE3 # BDE7 8CDC # BDE8 8CEA # BDE9 8CE1 # BDEA 8D6D # BDEB 8D9F # BDEC 8DA3 # BDED 8E2B # BDEE 8E10 # BDEF 8E1D # BDF0 8E22 # BDF1 8E0F # BDF2 8E29 # BDF3 8E1F # BDF4 8E21 # BDF5 8E1E # BDF6 8EBA # BDF7 8F1D # BDF8 8F1B # BDF9 8F1F # BDFA 8F29 # BDFB 8F26 # BDFC 8F2A # BDFD 8F1C # BDFE 8F1E # BE40 8F25 # BE41 9069 # BE42 906E # BE43 9068 # BE44 906D # BE45 9077 # BE46 9130 # BE47 912D # BE48 9127 # BE49 9131 # BE4A 9187 # BE4B 9189 # BE4C 918B # BE4D 9183 # BE4E 92C5 # BE4F 92BB # BE50 92B7 # BE51 92EA # BE52 92AC # BE53 92E4 # BE54 92C1 # BE55 92B3 # BE56 92BC # BE57 92D2 # BE58 92C7 # BE59 92F0 # BE5A 92B2 # BE5B 95AD # BE5C 95B1 # BE5D 9704 # BE5E 9706 # BE5F 9707 # BE60 9709 # BE61 9760 # BE62 978D # BE63 978B # BE64 978F # BE65 9821 # BE66 982B # BE67 981C # BE68 98B3 # BE69 990A # BE6A 9913 # BE6B 9912 # BE6C 9918 # BE6D 99DD # BE6E 99D0 # BE6F 99DF # BE70 99DB # BE71 99D1 # BE72 99D5 # BE73 99D2 # BE74 99D9 # BE75 9AB7 # BE76 9AEE # BE77 9AEF # BE78 9B27 # BE79 9B45 # BE7A 9B44 # BE7B 9B77 # BE7C 9B6F # BE7D 9D06 # BE7E 9D09 # BEA1 9D03 # BEA2 9EA9 # BEA3 9EBE # BEA4 9ECE # BEA5 58A8 # BEA6 9F52 # BEA7 5112 # BEA8 5118 # BEA9 5114 # BEAA 5110 # BEAB 5115 # BEAC 5180 # BEAD 51AA # BEAE 51DD # BEAF 5291 # BEB0 5293 # BEB1 52F3 # BEB2 5659 # BEB3 566B # BEB4 5679 # BEB5 5669 # BEB6 5664 # BEB7 5678 # BEB8 566A # BEB9 5668 # BEBA 5665 # BEBB 5671 # BEBC 566F # BEBD 566C # BEBE 5662 # BEBF 5676 # BEC0 58C1 # BEC1 58BE # BEC2 58C7 # BEC3 58C5 # BEC4 596E # BEC5 5B1D # BEC6 5B34 # BEC7 5B78 # BEC8 5BF0 # BEC9 5C0E # BECA 5F4A # BECB 61B2 # BECC 6191 # BECD 61A9 # BECE 618A # BECF 61CD # BED0 61B6 # BED1 61BE # BED2 61CA # BED3 61C8 # BED4 6230 # BED5 64C5 # BED6 64C1 # BED7 64CB # BED8 64BB # BED9 64BC # BEDA 64DA # BEDB 64C4 # BEDC 64C7 # BEDD 64C2 # BEDE 64CD # BEDF 64BF # BEE0 64D2 # BEE1 64D4 # BEE2 64BE # BEE3 6574 # BEE4 66C6 # BEE5 66C9 # BEE6 66B9 # BEE7 66C4 # BEE8 66C7 # BEE9 66B8 # BEEA 6A3D # BEEB 6A38 # BEEC 6A3A # BEED 6A59 # BEEE 6A6B # BEEF 6A58 # BEF0 6A39 # BEF1 6A44 # BEF2 6A62 # BEF3 6A61 # BEF4 6A4B # BEF5 6A47 # BEF6 6A35 # BEF7 6A5F # BEF8 6A48 # BEF9 6B59 # BEFA 6B77 # BEFB 6C05 # BEFC 6FC2 # BEFD 6FB1 # BEFE 6FA1 # BF40 6FC3 # BF41 6FA4 # BF42 6FC1 # BF43 6FA7 # BF44 6FB3 # BF45 6FC0 # BF46 6FB9 # BF47 6FB6 # BF48 6FA6 # BF49 6FA0 # BF4A 6FB4 # BF4B 71BE # BF4C 71C9 # BF4D 71D0 # BF4E 71D2 # BF4F 71C8 # BF50 71D5 # BF51 71B9 # BF52 71CE # BF53 71D9 # BF54 71DC # BF55 71C3 # BF56 71C4 # BF57 7368 # BF58 749C # BF59 74A3 # BF5A 7498 # BF5B 749F # BF5C 749E # BF5D 74E2 # BF5E 750C # BF5F 750D # BF60 7634 # BF61 7638 # BF62 763A # BF63 76E7 # BF64 76E5 # BF65 77A0 # BF66 779E # BF67 779F # BF68 77A5 # BF69 78E8 # BF6A 78DA # BF6B 78EC # BF6C 78E7 # BF6D 79A6 # BF6E 7A4D # BF6F 7A4E # BF70 7A46 # BF71 7A4C # BF72 7A4B # BF73 7ABA # BF74 7BD9 # BF75 7C11 # BF76 7BC9 # BF77 7BE4 # BF78 7BDB # BF79 7BE1 # BF7A 7BE9 # BF7B 7BE6 # BF7C 7CD5 # BF7D 7CD6 # BF7E 7E0A # BFA1 7E11 # BFA2 7E08 # BFA3 7E1B # BFA4 7E23 # BFA5 7E1E # BFA6 7E1D # BFA7 7E09 # BFA8 7E10 # BFA9 7F79 # BFAA 7FB2 # BFAB 7FF0 # BFAC 7FF1 # BFAD 7FEE # BFAE 8028 # BFAF 81B3 # BFB0 81A9 # BFB1 81A8 # BFB2 81FB # BFB3 8208 # BFB4 8258 # BFB5 8259 # BFB6 854A # BFB7 8559 # BFB8 8548 # BFB9 8568 # BFBA 8569 # BFBB 8543 # BFBC 8549 # BFBD 856D # BFBE 856A # BFBF 855E # BFC0 8783 # BFC1 879F # BFC2 879E # BFC3 87A2 # BFC4 878D # BFC5 8861 # BFC6 892A # BFC7 8932 # BFC8 8925 # BFC9 892B # BFCA 8921 # BFCB 89AA # BFCC 89A6 # BFCD 8AE6 # BFCE 8AFA # BFCF 8AEB # BFD0 8AF1 # BFD1 8B00 # BFD2 8ADC # BFD3 8AE7 # BFD4 8AEE # BFD5 8AFE # BFD6 8B01 # BFD7 8B02 # BFD8 8AF7 # BFD9 8AED # BFDA 8AF3 # BFDB 8AF6 # BFDC 8AFC # BFDD 8C6B # BFDE 8C6D # BFDF 8C93 # BFE0 8CF4 # BFE1 8E44 # BFE2 8E31 # BFE3 8E34 # BFE4 8E42 # BFE5 8E39 # BFE6 8E35 # BFE7 8F3B # BFE8 8F2F # BFE9 8F38 # BFEA 8F33 # BFEB 8FA8 # BFEC 8FA6 # BFED 9075 # BFEE 9074 # BFEF 9078 # BFF0 9072 # BFF1 907C # BFF2 907A # BFF3 9134 # BFF4 9192 # BFF5 9320 # BFF6 9336 # BFF7 92F8 # BFF8 9333 # BFF9 932F # BFFA 9322 # BFFB 92FC # BFFC 932B # BFFD 9304 # BFFE 931A # C040 9310 # C041 9326 # C042 9321 # C043 9315 # C044 932E # C045 9319 # C046 95BB # C047 96A7 # C048 96A8 # C049 96AA # C04A 96D5 # C04B 970E # C04C 9711 # C04D 9716 # C04E 970D # C04F 9713 # C050 970F # C051 975B # C052 975C # C053 9766 # C054 9798 # C055 9830 # C056 9838 # C057 983B # C058 9837 # C059 982D # C05A 9839 # C05B 9824 # C05C 9910 # C05D 9928 # C05E 991E # C05F 991B # C060 9921 # C061 991A # C062 99ED # C063 99E2 # C064 99F1 # C065 9AB8 # C066 9ABC # C067 9AFB # C068 9AED # C069 9B28 # C06A 9B91 # C06B 9D15 # C06C 9D23 # C06D 9D26 # C06E 9D28 # C06F 9D12 # C070 9D1B # C071 9ED8 # C072 9ED4 # C073 9F8D # C074 9F9C # C075 512A # C076 511F # C077 5121 # C078 5132 # C079 52F5 # C07A 568E # C07B 5680 # C07C 5690 # C07D 5685 # C07E 5687 # C0A1 568F # C0A2 58D5 # C0A3 58D3 # C0A4 58D1 # C0A5 58CE # C0A6 5B30 # C0A7 5B2A # C0A8 5B24 # C0A9 5B7A # C0AA 5C37 # C0AB 5C68 # C0AC 5DBC # C0AD 5DBA # C0AE 5DBD # C0AF 5DB8 # C0B0 5E6B # C0B1 5F4C # C0B2 5FBD # C0B3 61C9 # C0B4 61C2 # C0B5 61C7 # C0B6 61E6 # C0B7 61CB # C0B8 6232 # C0B9 6234 # C0BA 64CE # C0BB 64CA # C0BC 64D8 # C0BD 64E0 # C0BE 64F0 # C0BF 64E6 # C0C0 64EC # C0C1 64F1 # C0C2 64E2 # C0C3 64ED # C0C4 6582 # C0C5 6583 # C0C6 66D9 # C0C7 66D6 # C0C8 6A80 # C0C9 6A94 # C0CA 6A84 # C0CB 6AA2 # C0CC 6A9C # C0CD 6ADB # C0CE 6AA3 # C0CF 6A7E # C0D0 6A97 # C0D1 6A90 # C0D2 6AA0 # C0D3 6B5C # C0D4 6BAE # C0D5 6BDA # C0D6 6C08 # C0D7 6FD8 # C0D8 6FF1 # C0D9 6FDF # C0DA 6FE0 # C0DB 6FDB # C0DC 6FE4 # C0DD 6FEB # C0DE 6FEF # C0DF 6F80 # C0E0 6FEC # C0E1 6FE1 # C0E2 6FE9 # C0E3 6FD5 # C0E4 6FEE # C0E5 6FF0 # C0E6 71E7 # C0E7 71DF # C0E8 71EE # C0E9 71E6 # C0EA 71E5 # C0EB 71ED # C0EC 71EC # C0ED 71F4 # C0EE 71E0 # C0EF 7235 # C0F0 7246 # C0F1 7370 # C0F2 7372 # C0F3 74A9 # C0F4 74B0 # C0F5 74A6 # C0F6 74A8 # C0F7 7646 # C0F8 7642 # C0F9 764C # C0FA 76EA # C0FB 77B3 # C0FC 77AA # C0FD 77B0 # C0FE 77AC # C140 77A7 # C141 77AD # C142 77EF # C143 78F7 # C144 78FA # C145 78F4 # C146 78EF # C147 7901 # C148 79A7 # C149 79AA # C14A 7A57 # C14B 7ABF # C14C 7C07 # C14D 7C0D # C14E 7BFE # C14F 7BF7 # C150 7C0C # C151 7BE0 # C152 7CE0 # C153 7CDC # C154 7CDE # C155 7CE2 # C156 7CDF # C157 7CD9 # C158 7CDD # C159 7E2E # C15A 7E3E # C15B 7E46 # C15C 7E37 # C15D 7E32 # C15E 7E43 # C15F 7E2B # C160 7E3D # C161 7E31 # C162 7E45 # C163 7E41 # C164 7E34 # C165 7E39 # C166 7E48 # C167 7E35 # C168 7E3F # C169 7E2F # C16A 7F44 # C16B 7FF3 # C16C 7FFC # C16D 8071 # C16E 8072 # C16F 8070 # C170 806F # C171 8073 # C172 81C6 # C173 81C3 # C174 81BA # C175 81C2 # C176 81C0 # C177 81BF # C178 81BD # C179 81C9 # C17A 81BE # C17B 81E8 # C17C 8209 # C17D 8271 # C17E 85AA # C1A1 8584 # C1A2 857E # C1A3 859C # C1A4 8591 # C1A5 8594 # C1A6 85AF # C1A7 859B # C1A8 8587 # C1A9 85A8 # C1AA 858A # C1AB 8667 # C1AC 87C0 # C1AD 87D1 # C1AE 87B3 # C1AF 87D2 # C1B0 87C6 # C1B1 87AB # C1B2 87BB # C1B3 87BA # C1B4 87C8 # C1B5 87CB # C1B6 893B # C1B7 8936 # C1B8 8944 # C1B9 8938 # C1BA 893D # C1BB 89AC # C1BC 8B0E # C1BD 8B17 # C1BE 8B19 # C1BF 8B1B # C1C0 8B0A # C1C1 8B20 # C1C2 8B1D # C1C3 8B04 # C1C4 8B10 # C1C5 8C41 # C1C6 8C3F # C1C7 8C73 # C1C8 8CFA # C1C9 8CFD # C1CA 8CFC # C1CB 8CF8 # C1CC 8CFB # C1CD 8DA8 # C1CE 8E49 # C1CF 8E4B # C1D0 8E48 # C1D1 8E4A # C1D2 8F44 # C1D3 8F3E # C1D4 8F42 # C1D5 8F45 # C1D6 8F3F # C1D7 907F # C1D8 907D # C1D9 9084 # C1DA 9081 # C1DB 9082 # C1DC 9080 # C1DD 9139 # C1DE 91A3 # C1DF 919E # C1E0 919C # C1E1 934D # C1E2 9382 # C1E3 9328 # C1E4 9375 # C1E5 934A # C1E6 9365 # C1E7 934B # C1E8 9318 # C1E9 937E # C1EA 936C # C1EB 935B # C1EC 9370 # C1ED 935A # C1EE 9354 # C1EF 95CA # C1F0 95CB # C1F1 95CC # C1F2 95C8 # C1F3 95C6 # C1F4 96B1 # C1F5 96B8 # C1F6 96D6 # C1F7 971C # C1F8 971E # C1F9 97A0 # C1FA 97D3 # C1FB 9846 # C1FC 98B6 # C1FD 9935 # C1FE 9A01 # C240 99FF # C241 9BAE # C242 9BAB # C243 9BAA # C244 9BAD # C245 9D3B # C246 9D3F # C247 9E8B # C248 9ECF # C249 9EDE # C24A 9EDC # C24B 9EDD # C24C 9EDB # C24D 9F3E # C24E 9F4B # C24F 53E2 # C250 5695 # C251 56AE # C252 58D9 # C253 58D8 # C254 5B38 # C255 5F5D # C256 61E3 # C257 6233 # C258 64F4 # C259 64F2 # C25A 64FE # C25B 6506 # C25C 64FA # C25D 64FB # C25E 64F7 # C25F 65B7 # C260 66DC # C261 6726 # C262 6AB3 # C263 6AAC # C264 6AC3 # C265 6ABB # C266 6AB8 # C267 6AC2 # C268 6AAE # C269 6AAF # C26A 6B5F # C26B 6B78 # C26C 6BAF # C26D 7009 # C26E 700B # C26F 6FFE # C270 7006 # C271 6FFA # C272 7011 # C273 700F # C274 71FB # C275 71FC # C276 71FE # C277 71F8 # C278 7377 # C279 7375 # C27A 74A7 # C27B 74BF # C27C 7515 # C27D 7656 # C27E 7658 # C2A1 7652 # C2A2 77BD # C2A3 77BF # C2A4 77BB # C2A5 77BC # C2A6 790E # C2A7 79AE # C2A8 7A61 # C2A9 7A62 # C2AA 7A60 # C2AB 7AC4 # C2AC 7AC5 # C2AD 7C2B # C2AE 7C27 # C2AF 7C2A # C2B0 7C1E # C2B1 7C23 # C2B2 7C21 # C2B3 7CE7 # C2B4 7E54 # C2B5 7E55 # C2B6 7E5E # C2B7 7E5A # C2B8 7E61 # C2B9 7E52 # C2BA 7E59 # C2BB 7F48 # C2BC 7FF9 # C2BD 7FFB # C2BE 8077 # C2BF 8076 # C2C0 81CD # C2C1 81CF # C2C2 820A # C2C3 85CF # C2C4 85A9 # C2C5 85CD # C2C6 85D0 # C2C7 85C9 # C2C8 85B0 # C2C9 85BA # C2CA 85B9 # C2CB 85A6 # C2CC 87EF # C2CD 87EC # C2CE 87F2 # C2CF 87E0 # C2D0 8986 # C2D1 89B2 # C2D2 89F4 # C2D3 8B28 # C2D4 8B39 # C2D5 8B2C # C2D6 8B2B # C2D7 8C50 # C2D8 8D05 # C2D9 8E59 # C2DA 8E63 # C2DB 8E66 # C2DC 8E64 # C2DD 8E5F # C2DE 8E55 # C2DF 8EC0 # C2E0 8F49 # C2E1 8F4D # C2E2 9087 # C2E3 9083 # C2E4 9088 # C2E5 91AB # C2E6 91AC # C2E7 91D0 # C2E8 9394 # C2E9 938A # C2EA 9396 # C2EB 93A2 # C2EC 93B3 # C2ED 93AE # C2EE 93AC # C2EF 93B0 # C2F0 9398 # C2F1 939A # C2F2 9397 # C2F3 95D4 # C2F4 95D6 # C2F5 95D0 # C2F6 95D5 # C2F7 96E2 # C2F8 96DC # C2F9 96D9 # C2FA 96DB # C2FB 96DE # C2FC 9724 # C2FD 97A3 # C2FE 97A6 # C340 97AD # C341 97F9 # C342 984D # C343 984F # C344 984C # C345 984E # C346 9853 # C347 98BA # C348 993E # C349 993F # C34A 993D # C34B 992E # C34C 99A5 # C34D 9A0E # C34E 9AC1 # C34F 9B03 # C350 9B06 # C351 9B4F # C352 9B4E # C353 9B4D # C354 9BCA # C355 9BC9 # C356 9BFD # C357 9BC8 # C358 9BC0 # C359 9D51 # C35A 9D5D # C35B 9D60 # C35C 9EE0 # C35D 9F15 # C35E 9F2C # C35F 5133 # C360 56A5 # C361 58DE # C362 58DF # C363 58E2 # C364 5BF5 # C365 9F90 # C366 5EEC # C367 61F2 # C368 61F7 # C369 61F6 # C36A 61F5 # C36B 6500 # C36C 650F # C36D 66E0 # C36E 66DD # C36F 6AE5 # C370 6ADD # C371 6ADA # C372 6AD3 # C373 701B # C374 701F # C375 7028 # C376 701A # C377 701D # C378 7015 # C379 7018 # C37A 7206 # C37B 720D # C37C 7258 # C37D 72A2 # C37E 7378 # C3A1 737A # C3A2 74BD # C3A3 74CA # C3A4 74E3 # C3A5 7587 # C3A6 7586 # C3A7 765F # C3A8 7661 # C3A9 77C7 # C3AA 7919 # C3AB 79B1 # C3AC 7A6B # C3AD 7A69 # C3AE 7C3E # C3AF 7C3F # C3B0 7C38 # C3B1 7C3D # C3B2 7C37 # C3B3 7C40 # C3B4 7E6B # C3B5 7E6D # C3B6 7E79 # C3B7 7E69 # C3B8 7E6A # C3B9 7F85 # C3BA 7E73 # C3BB 7FB6 # C3BC 7FB9 # C3BD 7FB8 # C3BE 81D8 # C3BF 85E9 # C3C0 85DD # C3C1 85EA # C3C2 85D5 # C3C3 85E4 # C3C4 85E5 # C3C5 85F7 # C3C6 87FB # C3C7 8805 # C3C8 880D # C3C9 87F9 # C3CA 87FE # C3CB 8960 # C3CC 895F # C3CD 8956 # C3CE 895E # C3CF 8B41 # C3D0 8B5C # C3D1 8B58 # C3D2 8B49 # C3D3 8B5A # C3D4 8B4E # C3D5 8B4F # C3D6 8B46 # C3D7 8B59 # C3D8 8D08 # C3D9 8D0A # C3DA 8E7C # C3DB 8E72 # C3DC 8E87 # C3DD 8E76 # C3DE 8E6C # C3DF 8E7A # C3E0 8E74 # C3E1 8F54 # C3E2 8F4E # C3E3 8FAD # C3E4 908A # C3E5 908B # C3E6 91B1 # C3E7 91AE # C3E8 93E1 # C3E9 93D1 # C3EA 93DF # C3EB 93C3 # C3EC 93C8 # C3ED 93DC # C3EE 93DD # C3EF 93D6 # C3F0 93E2 # C3F1 93CD # C3F2 93D8 # C3F3 93E4 # C3F4 93D7 # C3F5 93E8 # C3F6 95DC # C3F7 96B4 # C3F8 96E3 # C3F9 972A # C3FA 9727 # C3FB 9761 # C3FC 97DC # C3FD 97FB # C3FE 985E # C440 9858 # C441 985B # C442 98BC # C443 9945 # C444 9949 # C445 9A16 # C446 9A19 # C447 9B0D # C448 9BE8 # C449 9BE7 # C44A 9BD6 # C44B 9BDB # C44C 9D89 # C44D 9D61 # C44E 9D72 # C44F 9D6A # C450 9D6C # C451 9E92 # C452 9E97 # C453 9E93 # C454 9EB4 # C455 52F8 # C456 56A8 # C457 56B7 # C458 56B6 # C459 56B4 # C45A 56BC # C45B 58E4 # C45C 5B40 # C45D 5B43 # C45E 5B7D # C45F 5BF6 # C460 5DC9 # C461 61F8 # C462 61FA # C463 6518 # C464 6514 # C465 6519 # C466 66E6 # C467 6727 # C468 6AEC # C469 703E # C46A 7030 # C46B 7032 # C46C 7210 # C46D 737B # C46E 74CF # C46F 7662 # C470 7665 # C471 7926 # C472 792A # C473 792C # C474 792B # C475 7AC7 # C476 7AF6 # C477 7C4C # C478 7C43 # C479 7C4D # C47A 7CEF # C47B 7CF0 # C47C 8FAE # C47D 7E7D # C47E 7E7C # C4A1 7E82 # C4A2 7F4C # C4A3 8000 # C4A4 81DA # C4A5 8266 # C4A6 85FB # C4A7 85F9 # C4A8 8611 # C4A9 85FA # C4AA 8606 # C4AB 860B # C4AC 8607 # C4AD 860A # C4AE 8814 # C4AF 8815 # C4B0 8964 # C4B1 89BA # C4B2 89F8 # C4B3 8B70 # C4B4 8B6C # C4B5 8B66 # C4B6 8B6F # C4B7 8B5F # C4B8 8B6B # C4B9 8D0F # C4BA 8D0D # C4BB 8E89 # C4BC 8E81 # C4BD 8E85 # C4BE 8E82 # C4BF 91B4 # C4C0 91CB # C4C1 9418 # C4C2 9403 # C4C3 93FD # C4C4 95E1 # C4C5 9730 # C4C6 98C4 # C4C7 9952 # C4C8 9951 # C4C9 99A8 # C4CA 9A2B # C4CB 9A30 # C4CC 9A37 # C4CD 9A35 # C4CE 9C13 # C4CF 9C0D # C4D0 9E79 # C4D1 9EB5 # C4D2 9EE8 # C4D3 9F2F # C4D4 9F5F # C4D5 9F63 # C4D6 9F61 # C4D7 5137 # C4D8 5138 # C4D9 56C1 # C4DA 56C0 # C4DB 56C2 # C4DC 5914 # C4DD 5C6C # C4DE 5DCD # C4DF 61FC # C4E0 61FE # C4E1 651D # C4E2 651C # C4E3 6595 # C4E4 66E9 # C4E5 6AFB # C4E6 6B04 # C4E7 6AFA # C4E8 6BB2 # C4E9 704C # C4EA 721B # C4EB 72A7 # C4EC 74D6 # C4ED 74D4 # C4EE 7669 # C4EF 77D3 # C4F0 7C50 # C4F1 7E8F # C4F2 7E8C # C4F3 7FBC # C4F4 8617 # C4F5 862D # C4F6 861A # C4F7 8823 # C4F8 8822 # C4F9 8821 # C4FA 881F # C4FB 896A # C4FC 896C # C4FD 89BD # C4FE 8B74 # C540 8B77 # C541 8B7D # C542 8D13 # C543 8E8A # C544 8E8D # C545 8E8B # C546 8F5F # C547 8FAF # C548 91BA # C549 942E # C54A 9433 # C54B 9435 # C54C 943A # C54D 9438 # C54E 9432 # C54F 942B # C550 95E2 # C551 9738 # C552 9739 # C553 9732 # C554 97FF # C555 9867 # C556 9865 # C557 9957 # C558 9A45 # C559 9A43 # C55A 9A40 # C55B 9A3E # C55C 9ACF # C55D 9B54 # C55E 9B51 # C55F 9C2D # C560 9C25 # C561 9DAF # C562 9DB4 # C563 9DC2 # C564 9DB8 # C565 9E9D # C566 9EEF # C567 9F19 # C568 9F5C # C569 9F66 # C56A 9F67 # C56B 513C # C56C 513B # C56D 56C8 # C56E 56CA # C56F 56C9 # C570 5B7F # C571 5DD4 # C572 5DD2 # C573 5F4E # C574 61FF # C575 6524 # C576 6B0A # C577 6B61 # C578 7051 # C579 7058 # C57A 7380 # C57B 74E4 # C57C 758A # C57D 766E # C57E 766C # C5A1 79B3 # C5A2 7C60 # C5A3 7C5F # C5A4 807E # C5A5 807D # C5A6 81DF # C5A7 8972 # C5A8 896F # C5A9 89FC # C5AA 8B80 # C5AB 8D16 # C5AC 8D17 # C5AD 8E91 # C5AE 8E93 # C5AF 8F61 # C5B0 9148 # C5B1 9444 # C5B2 9451 # C5B3 9452 # C5B4 973D # C5B5 973E # C5B6 97C3 # C5B7 97C1 # C5B8 986B # C5B9 9955 # C5BA 9A55 # C5BB 9A4D # C5BC 9AD2 # C5BD 9B1A # C5BE 9C49 # C5BF 9C31 # C5C0 9C3E # C5C1 9C3B # C5C2 9DD3 # C5C3 9DD7 # C5C4 9F34 # C5C5 9F6C # C5C6 9F6A # C5C7 9F94 # C5C8 56CC # C5C9 5DD6 # C5CA 6200 # C5CB 6523 # C5CC 652B # C5CD 652A # C5CE 66EC # C5CF 6B10 # C5D0 74DA # C5D1 7ACA # C5D2 7C64 # C5D3 7C63 # C5D4 7C65 # C5D5 7E93 # C5D6 7E96 # C5D7 7E94 # C5D8 81E2 # C5D9 8638 # C5DA 863F # C5DB 8831 # C5DC 8B8A # C5DD 9090 # C5DE 908F # C5DF 9463 # C5E0 9460 # C5E1 9464 # C5E2 9768 # C5E3 986F # C5E4 995C # C5E5 9A5A # C5E6 9A5B # C5E7 9A57 # C5E8 9AD3 # C5E9 9AD4 # C5EA 9AD1 # C5EB 9C54 # C5EC 9C57 # C5ED 9C56 # C5EE 9DE5 # C5EF 9E9F # C5F0 9EF4 # C5F1 56D1 # C5F2 58E9 # C5F3 652C # C5F4 705E # C5F5 7671 # C5F6 7672 # C5F7 77D7 # C5F8 7F50 # C5F9 7F88 # C5FA 8836 # C5FB 8839 # C5FC 8862 # C5FD 8B93 # C5FE 8B92 # C640 8B96 # C641 8277 # C642 8D1B # C643 91C0 # C644 946A # C645 9742 # C646 9748 # C647 9744 # C648 97C6 # C649 9870 # C64A 9A5F # C64B 9B22 # C64C 9B58 # C64D 9C5F # C64E 9DF9 # C64F 9DFA # C650 9E7C # C651 9E7D # C652 9F07 # C653 9F77 # C654 9F72 # C655 5EF3 # C656 6B16 # C657 7063 # C658 7C6C # C659 7C6E # C65A 883B # C65B 89C0 # C65C 8EA1 # C65D 91C1 # C65E 9472 # C65F 9470 # C660 9871 # C661 995E # C662 9AD6 # C663 9B23 # C664 9ECC # C665 7064 # C666 77DA # C667 8B9A # C668 9477 # C669 97C9 # C66A 9A62 # C66B 9A65 # C66C 7E9C # C66D 8B9C # C66E 8EAA # C66F 91C5 # C670 947D # C671 947E # C672 947C # C673 9C77 # C674 9C78 # C675 9EF7 # C676 8C54 # C677 947F # C678 9E1A # C679 7228 # C67A 9A6A # C67B 9B31 # C67C 9E1B # C67D 9E1E # C67E 7C72 # C6A1 30FE # KATAKANA VOICED ITERATION MARK C6A2 309D # HIRAGANA ITERATION MARK C6A3 309E # HIRAGANA VOICED ITERATION MARK C6A4 3005 # IDEOGRAPHIC ITERATION MARK C6A5 3041 # HIRAGANA LETTER SMALL A C6A6 3042 # HIRAGANA LETTER A C6A7 3043 # HIRAGANA LETTER SMALL I C6A8 3044 # HIRAGANA LETTER I C6A9 3045 # HIRAGANA LETTER SMALL U C6AA 3046 # HIRAGANA LETTER U C6AB 3047 # HIRAGANA LETTER SMALL E C6AC 3048 # HIRAGANA LETTER E C6AD 3049 # HIRAGANA LETTER SMALL O C6AE 304A # HIRAGANA LETTER O C6AF 304B # HIRAGANA LETTER KA C6B0 304C # HIRAGANA LETTER GA C6B1 304D # HIRAGANA LETTER KI C6B2 304E # HIRAGANA LETTER GI C6B3 304F # HIRAGANA LETTER KU C6B4 3050 # HIRAGANA LETTER GU C6B5 3051 # HIRAGANA LETTER KE C6B6 3052 # HIRAGANA LETTER GE C6B7 3053 # HIRAGANA LETTER KO C6B8 3054 # HIRAGANA LETTER GO C6B9 3055 # HIRAGANA LETTER SA C6BA 3056 # HIRAGANA LETTER ZA C6BB 3057 # HIRAGANA LETTER SI C6BC 3058 # HIRAGANA LETTER ZI C6BD 3059 # HIRAGANA LETTER SU C6BE 305A # HIRAGANA LETTER ZU C6BF 305B # HIRAGANA LETTER SE C6C0 305C # HIRAGANA LETTER ZE C6C1 305D # HIRAGANA LETTER SO C6C2 305E # HIRAGANA LETTER ZO C6C3 305F # HIRAGANA LETTER TA C6C4 3060 # HIRAGANA LETTER DA C6C5 3061 # HIRAGANA LETTER TI C6C6 3062 # HIRAGANA LETTER DI C6C7 3063 # HIRAGANA LETTER SMALL TU C6C8 3064 # HIRAGANA LETTER TU C6C9 3065 # HIRAGANA LETTER DU C6CA 3066 # HIRAGANA LETTER TE C6CB 3067 # HIRAGANA LETTER DE C6CC 3068 # HIRAGANA LETTER TO C6CD 3069 # HIRAGANA LETTER DO C6CE 306A # HIRAGANA LETTER NA C6CF 306B # HIRAGANA LETTER NI C6D0 306C # HIRAGANA LETTER NU C6D1 306D # HIRAGANA LETTER NE C6D2 306E # HIRAGANA LETTER NO C6D3 306F # HIRAGANA LETTER HA C6D4 3070 # HIRAGANA LETTER BA C6D5 3071 # HIRAGANA LETTER PA C6D6 3072 # HIRAGANA LETTER HI C6D7 3073 # HIRAGANA LETTER BI C6D8 3074 # HIRAGANA LETTER PI C6D9 3075 # HIRAGANA LETTER HU C6DA 3076 # HIRAGANA LETTER BU C6DB 3077 # HIRAGANA LETTER PU C6DC 3078 # HIRAGANA LETTER HE C6DD 3079 # HIRAGANA LETTER BE C6DE 307A # HIRAGANA LETTER PE C6DF 307B # HIRAGANA LETTER HO C6E0 307C # HIRAGANA LETTER BO C6E1 307D # HIRAGANA LETTER PO C6E2 307E # HIRAGANA LETTER MA C6E3 307F # HIRAGANA LETTER MI C6E4 3080 # HIRAGANA LETTER MU C6E5 3081 # HIRAGANA LETTER ME C6E6 3082 # HIRAGANA LETTER MO C6E7 3083 # HIRAGANA LETTER SMALL YA C6E8 3084 # HIRAGANA LETTER YA C6E9 3085 # HIRAGANA LETTER SMALL YU C6EA 3086 # HIRAGANA LETTER YU C6EB 3087 # HIRAGANA LETTER SMALL YO C6EC 3088 # HIRAGANA LETTER YO C6ED 3089 # HIRAGANA LETTER RA C6EE 308A # HIRAGANA LETTER RI C6EF 308B # HIRAGANA LETTER RU C6F0 308C # HIRAGANA LETTER RE C6F1 308D # HIRAGANA LETTER RO C6F2 308E # HIRAGANA LETTER SMALL WA C6F3 308F # HIRAGANA LETTER WA C6F4 3090 # HIRAGANA LETTER WI C6F5 3091 # HIRAGANA LETTER WE C6F6 3092 # HIRAGANA LETTER WO C6F7 3093 # HIRAGANA LETTER N C6F8 30A1 # KATAKANA LETTER SMALL A C6F9 30A2 # KATAKANA LETTER A C6FA 30A3 # KATAKANA LETTER SMALL I C6FB 30A4 # KATAKANA LETTER I C6FC 30A5 # KATAKANA LETTER SMALL U C6FD 30A6 # KATAKANA LETTER U C6FE 30A7 # KATAKANA LETTER SMALL E C740 30A8 # KATAKANA LETTER E C741 30A9 # KATAKANA LETTER SMALL O C742 30AA # KATAKANA LETTER O C743 30AB # KATAKANA LETTER KA C744 30AC # KATAKANA LETTER GA C745 30AD # KATAKANA LETTER KI C746 30AE # KATAKANA LETTER GI C747 30AF # KATAKANA LETTER KU C748 30B0 # KATAKANA LETTER GU C749 30B1 # KATAKANA LETTER KE C74A 30B2 # KATAKANA LETTER GE C74B 30B3 # KATAKANA LETTER KO C74C 30B4 # KATAKANA LETTER GO C74D 30B5 # KATAKANA LETTER SA C74E 30B6 # KATAKANA LETTER ZA C74F 30B7 # KATAKANA LETTER SI C750 30B8 # KATAKANA LETTER ZI C751 30B9 # KATAKANA LETTER SU C752 30BA # KATAKANA LETTER ZU C753 30BB # KATAKANA LETTER SE C754 30BC # KATAKANA LETTER ZE C755 30BD # KATAKANA LETTER SO C756 30BE # KATAKANA LETTER ZO C757 30BF # KATAKANA LETTER TA C758 30C0 # KATAKANA LETTER DA C759 30C1 # KATAKANA LETTER TI C75A 30C2 # KATAKANA LETTER DI C75B 30C3 # KATAKANA LETTER SMALL TU C75C 30C4 # KATAKANA LETTER TU C75D 30C5 # KATAKANA LETTER DU C75E 30C6 # KATAKANA LETTER TE C75F 30C7 # KATAKANA LETTER DE C760 30C8 # KATAKANA LETTER TO C761 30C9 # KATAKANA LETTER DO C762 30CA # KATAKANA LETTER NA C763 30CB # KATAKANA LETTER NI C764 30CC # KATAKANA LETTER NU C765 30CD # KATAKANA LETTER NE C766 30CE # KATAKANA LETTER NO C767 30CF # KATAKANA LETTER HA C768 30D0 # KATAKANA LETTER BA C769 30D1 # KATAKANA LETTER PA C76A 30D2 # KATAKANA LETTER HI C76B 30D3 # KATAKANA LETTER BI C76C 30D4 # KATAKANA LETTER PI C76D 30D5 # KATAKANA LETTER HU C76E 30D6 # KATAKANA LETTER BU C76F 30D7 # KATAKANA LETTER PU C770 30D8 # KATAKANA LETTER HE C771 30D9 # KATAKANA LETTER BE C772 30DA # KATAKANA LETTER PE C773 30DB # KATAKANA LETTER HO C774 30DC # KATAKANA LETTER BO C775 30DD # KATAKANA LETTER PO C776 30DE # KATAKANA LETTER MA C777 30DF # KATAKANA LETTER MI C778 30E0 # KATAKANA LETTER MU C779 30E1 # KATAKANA LETTER ME C77A 30E2 # KATAKANA LETTER MO C77B 30E3 # KATAKANA LETTER SMALL YA C77C 30E4 # KATAKANA LETTER YA C77D 30E5 # KATAKANA LETTER SMALL YU C77E 30E6 # KATAKANA LETTER YU C7A1 30E7 # KATAKANA LETTER SMALL YO C7A2 30E8 # KATAKANA LETTER YO C7A3 30E9 # KATAKANA LETTER RA C7A4 30EA # KATAKANA LETTER RI C7A5 30EB # KATAKANA LETTER RU C7A6 30EC # KATAKANA LETTER RE C7A7 30ED # KATAKANA LETTER RO C7A8 30EE # KATAKANA LETTER SMALL WA C7A9 30EF # KATAKANA LETTER WA C7AA 30F0 # KATAKANA LETTER WI C7AB 30F1 # KATAKANA LETTER WE C7AC 30F2 # KATAKANA LETTER WO C7AD 30F3 # KATAKANA LETTER N C7AE 30F4 # KATAKANA LETTER VU C7AF 30F5 # KATAKANA LETTER SMALL KA C7B0 30F6 # KATAKANA LETTER SMALL KE C7B1 0414 # CYRILLIC CAPITAL LETTER DE C7B2 0415 # CYRILLIC CAPITAL LETTER IE C7B3 0401 # CYRILLIC CAPITAL LETTER IO C7B4 0416 # CYRILLIC CAPITAL LETTER ZHE C7B5 0417 # CYRILLIC CAPITAL LETTER ZE C7B6 0418 # CYRILLIC CAPITAL LETTER I C7B7 0419 # CYRILLIC CAPITAL LETTER SHORT I C7B8 041A # CYRILLIC CAPITAL LETTER KA C7B9 041B # CYRILLIC CAPITAL LETTER EL C7BA 041C # CYRILLIC CAPITAL LETTER EM C7BB 0423 # CYRILLIC CAPITAL LETTER U C7BC 0424 # CYRILLIC CAPITAL LETTER EF C7BD 0425 # CYRILLIC CAPITAL LETTER HA C7BE 0426 # CYRILLIC CAPITAL LETTER TSE C7BF 0427 # CYRILLIC CAPITAL LETTER CHE C7C0 0428 # CYRILLIC CAPITAL LETTER SHA C7C1 0429 # CYRILLIC CAPITAL LETTER SHCHA C7C2 042A # CYRILLIC CAPITAL LETTER HARD SIGN C7C3 042B # CYRILLIC CAPITAL LETTER YERU C7C4 042C # CYRILLIC CAPITAL LETTER SOFT SIGN C7C5 042D # CYRILLIC CAPITAL LETTER E C7C6 042E # CYRILLIC CAPITAL LETTER YU C7C7 042F # CYRILLIC CAPITAL LETTER YA C7C8 0430 # CYRILLIC SMALL LETTER A C7C9 0431 # CYRILLIC SMALL LETTER BE C7CA 0432 # CYRILLIC SMALL LETTER VE C7CB 0433 # CYRILLIC SMALL LETTER GHE C7CC 0434 # CYRILLIC SMALL LETTER DE C7CD 0435 # CYRILLIC SMALL LETTER IE C7CE 0451 # CYRILLIC SMALL LETTER IO C7CF 0436 # CYRILLIC SMALL LETTER ZHE C7D0 0437 # CYRILLIC SMALL LETTER ZE C7D1 0438 # CYRILLIC SMALL LETTER I C7D2 0439 # CYRILLIC SMALL LETTER SHORT I C7D3 043A # CYRILLIC SMALL LETTER KA C7D4 043B # CYRILLIC SMALL LETTER EL C7D5 043C # CYRILLIC SMALL LETTER EM C7D6 043D # CYRILLIC SMALL LETTER EN C7D7 043E # CYRILLIC SMALL LETTER O C7D8 043F # CYRILLIC SMALL LETTER PE C7D9 0440 # CYRILLIC SMALL LETTER ER C7DA 0441 # CYRILLIC SMALL LETTER ES C7DB 0442 # CYRILLIC SMALL LETTER TE C7DC 0443 # CYRILLIC SMALL LETTER U C7DD 0444 # CYRILLIC SMALL LETTER EF C7DE 0445 # CYRILLIC SMALL LETTER HA C7DF 0446 # CYRILLIC SMALL LETTER TSE C7E0 0447 # CYRILLIC SMALL LETTER CHE C7E1 0448 # CYRILLIC SMALL LETTER SHA C7E2 0449 # CYRILLIC SMALL LETTER SHCHA C7E3 044A # CYRILLIC SMALL LETTER HARD SIGN C7E4 044B # CYRILLIC SMALL LETTER YERU C7E5 044C # CYRILLIC SMALL LETTER SOFT SIGN C7E6 044D # CYRILLIC SMALL LETTER E C7E7 044E # CYRILLIC SMALL LETTER YU C7E8 044F # CYRILLIC SMALL LETTER YA C7E9 2460 # CIRCLED DIGIT ONE C7EA 2461 # CIRCLED DIGIT TWO C7EB 2462 # CIRCLED DIGIT THREE C7EC 2463 # CIRCLED DIGIT FOUR C7ED 2464 # CIRCLED DIGIT FIVE C7EE 2465 # CIRCLED DIGIT SIX C7EF 2466 # CIRCLED DIGIT SEVEN C7F0 2467 # CIRCLED DIGIT EIGHT C7F1 2468 # CIRCLED DIGIT NINE C7F2 2469 # CIRCLED NUMBER TEN C7F3 2474 # PARENTHESIZED DIGIT ONE C7F4 2475 # PARENTHESIZED DIGIT TWO C7F5 2476 # PARENTHESIZED DIGIT THREE C7F6 2477 # PARENTHESIZED DIGIT FOUR C7F7 2478 # PARENTHESIZED DIGIT FIVE C7F8 2479 # PARENTHESIZED DIGIT SIX C7F9 247A # PARENTHESIZED DIGIT SEVEN C7FA 247B # PARENTHESIZED DIGIT EIGHT C7FB 247C # PARENTHESIZED DIGIT NINE C7FC 247D # PARENTHESIZED NUMBER TEN C940 4E42 # C941 4E5C # C942 51F5 # C943 531A # C944 5382 # C945 4E07 # C946 4E0C # C947 4E47 # C948 4E8D # C949 56D7 # C94A FA0C # CJK COMPATIBILITY IDEOGRAPH-FA0C C94B 5C6E # C94C 5F73 # C94D 4E0F # C94E 5187 # C94F 4E0E # C950 4E2E # C951 4E93 # C952 4EC2 # C953 4EC9 # C954 4EC8 # C955 5198 # C956 52FC # C957 536C # C958 53B9 # C959 5720 # C95A 5903 # C95B 592C # C95C 5C10 # C95D 5DFF # C95E 65E1 # C95F 6BB3 # C960 6BCC # C961 6C14 # C962 723F # C963 4E31 # C964 4E3C # C965 4EE8 # C966 4EDC # C967 4EE9 # C968 4EE1 # C969 4EDD # C96A 4EDA # C96B 520C # C96C 531C # C96D 534C # C96E 5722 # C96F 5723 # C970 5917 # C971 592F # C972 5B81 # C973 5B84 # C974 5C12 # C975 5C3B # C976 5C74 # C977 5C73 # C978 5E04 # C979 5E80 # C97A 5E82 # C97B 5FC9 # C97C 6209 # C97D 6250 # C97E 6C15 # C9A1 6C36 # C9A2 6C43 # C9A3 6C3F # C9A4 6C3B # C9A5 72AE # C9A6 72B0 # C9A7 738A # C9A8 79B8 # C9A9 808A # C9AA 961E # C9AB 4F0E # C9AC 4F18 # C9AD 4F2C # C9AE 4EF5 # C9AF 4F14 # C9B0 4EF1 # C9B1 4F00 # C9B2 4EF7 # C9B3 4F08 # C9B4 4F1D # C9B5 4F02 # C9B6 4F05 # C9B7 4F22 # C9B8 4F13 # C9B9 4F04 # C9BA 4EF4 # C9BB 4F12 # C9BC 51B1 # C9BD 5213 # C9BE 5209 # C9BF 5210 # C9C0 52A6 # C9C1 5322 # C9C2 531F # C9C3 534D # C9C4 538A # C9C5 5407 # C9C6 56E1 # C9C7 56DF # C9C8 572E # C9C9 572A # C9CA 5734 # C9CB 593C # C9CC 5980 # C9CD 597C # C9CE 5985 # C9CF 597B # C9D0 597E # C9D1 5977 # C9D2 597F # C9D3 5B56 # C9D4 5C15 # C9D5 5C25 # C9D6 5C7C # C9D7 5C7A # C9D8 5C7B # C9D9 5C7E # C9DA 5DDF # C9DB 5E75 # C9DC 5E84 # C9DD 5F02 # C9DE 5F1A # C9DF 5F74 # C9E0 5FD5 # C9E1 5FD4 # C9E2 5FCF # C9E3 625C # C9E4 625E # C9E5 6264 # C9E6 6261 # C9E7 6266 # C9E8 6262 # C9E9 6259 # C9EA 6260 # C9EB 625A # C9EC 6265 # C9ED 65EF # C9EE 65EE # C9EF 673E # C9F0 6739 # C9F1 6738 # C9F2 673B # C9F3 673A # C9F4 673F # C9F5 673C # C9F6 6733 # C9F7 6C18 # C9F8 6C46 # C9F9 6C52 # C9FA 6C5C # C9FB 6C4F # C9FC 6C4A # C9FD 6C54 # C9FE 6C4B # CA40 6C4C # CA41 7071 # CA42 725E # CA43 72B4 # CA44 72B5 # CA45 738E # CA46 752A # CA47 767F # CA48 7A75 # CA49 7F51 # CA4A 8278 # CA4B 827C # CA4C 8280 # CA4D 827D # CA4E 827F # CA4F 864D # CA50 897E # CA51 9099 # CA52 9097 # CA53 9098 # CA54 909B # CA55 9094 # CA56 9622 # CA57 9624 # CA58 9620 # CA59 9623 # CA5A 4F56 # CA5B 4F3B # CA5C 4F62 # CA5D 4F49 # CA5E 4F53 # CA5F 4F64 # CA60 4F3E # CA61 4F67 # CA62 4F52 # CA63 4F5F # CA64 4F41 # CA65 4F58 # CA66 4F2D # CA67 4F33 # CA68 4F3F # CA69 4F61 # CA6A 518F # CA6B 51B9 # CA6C 521C # CA6D 521E # CA6E 5221 # CA6F 52AD # CA70 52AE # CA71 5309 # CA72 5363 # CA73 5372 # CA74 538E # CA75 538F # CA76 5430 # CA77 5437 # CA78 542A # CA79 5454 # CA7A 5445 # CA7B 5419 # CA7C 541C # CA7D 5425 # CA7E 5418 # CAA1 543D # CAA2 544F # CAA3 5441 # CAA4 5428 # CAA5 5424 # CAA6 5447 # CAA7 56EE # CAA8 56E7 # CAA9 56E5 # CAAA 5741 # CAAB 5745 # CAAC 574C # CAAD 5749 # CAAE 574B # CAAF 5752 # CAB0 5906 # CAB1 5940 # CAB2 59A6 # CAB3 5998 # CAB4 59A0 # CAB5 5997 # CAB6 598E # CAB7 59A2 # CAB8 5990 # CAB9 598F # CABA 59A7 # CABB 59A1 # CABC 5B8E # CABD 5B92 # CABE 5C28 # CABF 5C2A # CAC0 5C8D # CAC1 5C8F # CAC2 5C88 # CAC3 5C8B # CAC4 5C89 # CAC5 5C92 # CAC6 5C8A # CAC7 5C86 # CAC8 5C93 # CAC9 5C95 # CACA 5DE0 # CACB 5E0A # CACC 5E0E # CACD 5E8B # CACE 5E89 # CACF 5E8C # CAD0 5E88 # CAD1 5E8D # CAD2 5F05 # CAD3 5F1D # CAD4 5F78 # CAD5 5F76 # CAD6 5FD2 # CAD7 5FD1 # CAD8 5FD0 # CAD9 5FED # CADA 5FE8 # CADB 5FEE # CADC 5FF3 # CADD 5FE1 # CADE 5FE4 # CADF 5FE3 # CAE0 5FFA # CAE1 5FEF # CAE2 5FF7 # CAE3 5FFB # CAE4 6000 # CAE5 5FF4 # CAE6 623A # CAE7 6283 # CAE8 628C # CAE9 628E # CAEA 628F # CAEB 6294 # CAEC 6287 # CAED 6271 # CAEE 627B # CAEF 627A # CAF0 6270 # CAF1 6281 # CAF2 6288 # CAF3 6277 # CAF4 627D # CAF5 6272 # CAF6 6274 # CAF7 6537 # CAF8 65F0 # CAF9 65F4 # CAFA 65F3 # CAFB 65F2 # CAFC 65F5 # CAFD 6745 # CAFE 6747 # CB40 6759 # CB41 6755 # CB42 674C # CB43 6748 # CB44 675D # CB45 674D # CB46 675A # CB47 674B # CB48 6BD0 # CB49 6C19 # CB4A 6C1A # CB4B 6C78 # CB4C 6C67 # CB4D 6C6B # CB4E 6C84 # CB4F 6C8B # CB50 6C8F # CB51 6C71 # CB52 6C6F # CB53 6C69 # CB54 6C9A # CB55 6C6D # CB56 6C87 # CB57 6C95 # CB58 6C9C # CB59 6C66 # CB5A 6C73 # CB5B 6C65 # CB5C 6C7B # CB5D 6C8E # CB5E 7074 # CB5F 707A # CB60 7263 # CB61 72BF # CB62 72BD # CB63 72C3 # CB64 72C6 # CB65 72C1 # CB66 72BA # CB67 72C5 # CB68 7395 # CB69 7397 # CB6A 7393 # CB6B 7394 # CB6C 7392 # CB6D 753A # CB6E 7539 # CB6F 7594 # CB70 7595 # CB71 7681 # CB72 793D # CB73 8034 # CB74 8095 # CB75 8099 # CB76 8090 # CB77 8092 # CB78 809C # CB79 8290 # CB7A 828F # CB7B 8285 # CB7C 828E # CB7D 8291 # CB7E 8293 # CBA1 828A # CBA2 8283 # CBA3 8284 # CBA4 8C78 # CBA5 8FC9 # CBA6 8FBF # CBA7 909F # CBA8 90A1 # CBA9 90A5 # CBAA 909E # CBAB 90A7 # CBAC 90A0 # CBAD 9630 # CBAE 9628 # CBAF 962F # CBB0 962D # CBB1 4E33 # CBB2 4F98 # CBB3 4F7C # CBB4 4F85 # CBB5 4F7D # CBB6 4F80 # CBB7 4F87 # CBB8 4F76 # CBB9 4F74 # CBBA 4F89 # CBBB 4F84 # CBBC 4F77 # CBBD 4F4C # CBBE 4F97 # CBBF 4F6A # CBC0 4F9A # CBC1 4F79 # CBC2 4F81 # CBC3 4F78 # CBC4 4F90 # CBC5 4F9C # CBC6 4F94 # CBC7 4F9E # CBC8 4F92 # CBC9 4F82 # CBCA 4F95 # CBCB 4F6B # CBCC 4F6E # CBCD 519E # CBCE 51BC # CBCF 51BE # CBD0 5235 # CBD1 5232 # CBD2 5233 # CBD3 5246 # CBD4 5231 # CBD5 52BC # CBD6 530A # CBD7 530B # CBD8 533C # CBD9 5392 # CBDA 5394 # CBDB 5487 # CBDC 547F # CBDD 5481 # CBDE 5491 # CBDF 5482 # CBE0 5488 # CBE1 546B # CBE2 547A # CBE3 547E # CBE4 5465 # CBE5 546C # CBE6 5474 # CBE7 5466 # CBE8 548D # CBE9 546F # CBEA 5461 # CBEB 5460 # CBEC 5498 # CBED 5463 # CBEE 5467 # CBEF 5464 # CBF0 56F7 # CBF1 56F9 # CBF2 576F # CBF3 5772 # CBF4 576D # CBF5 576B # CBF6 5771 # CBF7 5770 # CBF8 5776 # CBF9 5780 # CBFA 5775 # CBFB 577B # CBFC 5773 # CBFD 5774 # CBFE 5762 # CC40 5768 # CC41 577D # CC42 590C # CC43 5945 # CC44 59B5 # CC45 59BA # CC46 59CF # CC47 59CE # CC48 59B2 # CC49 59CC # CC4A 59C1 # CC4B 59B6 # CC4C 59BC # CC4D 59C3 # CC4E 59D6 # CC4F 59B1 # CC50 59BD # CC51 59C0 # CC52 59C8 # CC53 59B4 # CC54 59C7 # CC55 5B62 # CC56 5B65 # CC57 5B93 # CC58 5B95 # CC59 5C44 # CC5A 5C47 # CC5B 5CAE # CC5C 5CA4 # CC5D 5CA0 # CC5E 5CB5 # CC5F 5CAF # CC60 5CA8 # CC61 5CAC # CC62 5C9F # CC63 5CA3 # CC64 5CAD # CC65 5CA2 # CC66 5CAA # CC67 5CA7 # CC68 5C9D # CC69 5CA5 # CC6A 5CB6 # CC6B 5CB0 # CC6C 5CA6 # CC6D 5E17 # CC6E 5E14 # CC6F 5E19 # CC70 5F28 # CC71 5F22 # CC72 5F23 # CC73 5F24 # CC74 5F54 # CC75 5F82 # CC76 5F7E # CC77 5F7D # CC78 5FDE # CC79 5FE5 # CC7A 602D # CC7B 6026 # CC7C 6019 # CC7D 6032 # CC7E 600B # CCA1 6034 # CCA2 600A # CCA3 6017 # CCA4 6033 # CCA5 601A # CCA6 601E # CCA7 602C # CCA8 6022 # CCA9 600D # CCAA 6010 # CCAB 602E # CCAC 6013 # CCAD 6011 # CCAE 600C # CCAF 6009 # CCB0 601C # CCB1 6214 # CCB2 623D # CCB3 62AD # CCB4 62B4 # CCB5 62D1 # CCB6 62BE # CCB7 62AA # CCB8 62B6 # CCB9 62CA # CCBA 62AE # CCBB 62B3 # CCBC 62AF # CCBD 62BB # CCBE 62A9 # CCBF 62B0 # CCC0 62B8 # CCC1 653D # CCC2 65A8 # CCC3 65BB # CCC4 6609 # CCC5 65FC # CCC6 6604 # CCC7 6612 # CCC8 6608 # CCC9 65FB # CCCA 6603 # CCCB 660B # CCCC 660D # CCCD 6605 # CCCE 65FD # CCCF 6611 # CCD0 6610 # CCD1 66F6 # CCD2 670A # CCD3 6785 # CCD4 676C # CCD5 678E # CCD6 6792 # CCD7 6776 # CCD8 677B # CCD9 6798 # CCDA 6786 # CCDB 6784 # CCDC 6774 # CCDD 678D # CCDE 678C # CCDF 677A # CCE0 679F # CCE1 6791 # CCE2 6799 # CCE3 6783 # CCE4 677D # CCE5 6781 # CCE6 6778 # CCE7 6779 # CCE8 6794 # CCE9 6B25 # CCEA 6B80 # CCEB 6B7E # CCEC 6BDE # CCED 6C1D # CCEE 6C93 # CCEF 6CEC # CCF0 6CEB # CCF1 6CEE # CCF2 6CD9 # CCF3 6CB6 # CCF4 6CD4 # CCF5 6CAD # CCF6 6CE7 # CCF7 6CB7 # CCF8 6CD0 # CCF9 6CC2 # CCFA 6CBA # CCFB 6CC3 # CCFC 6CC6 # CCFD 6CED # CCFE 6CF2 # CD40 6CD2 # CD41 6CDD # CD42 6CB4 # CD43 6C8A # CD44 6C9D # CD45 6C80 # CD46 6CDE # CD47 6CC0 # CD48 6D30 # CD49 6CCD # CD4A 6CC7 # CD4B 6CB0 # CD4C 6CF9 # CD4D 6CCF # CD4E 6CE9 # CD4F 6CD1 # CD50 7094 # CD51 7098 # CD52 7085 # CD53 7093 # CD54 7086 # CD55 7084 # CD56 7091 # CD57 7096 # CD58 7082 # CD59 709A # CD5A 7083 # CD5B 726A # CD5C 72D6 # CD5D 72CB # CD5E 72D8 # CD5F 72C9 # CD60 72DC # CD61 72D2 # CD62 72D4 # CD63 72DA # CD64 72CC # CD65 72D1 # CD66 73A4 # CD67 73A1 # CD68 73AD # CD69 73A6 # CD6A 73A2 # CD6B 73A0 # CD6C 73AC # CD6D 739D # CD6E 74DD # CD6F 74E8 # CD70 753F # CD71 7540 # CD72 753E # CD73 758C # CD74 7598 # CD75 76AF # CD76 76F3 # CD77 76F1 # CD78 76F0 # CD79 76F5 # CD7A 77F8 # CD7B 77FC # CD7C 77F9 # CD7D 77FB # CD7E 77FA # CDA1 77F7 # CDA2 7942 # CDA3 793F # CDA4 79C5 # CDA5 7A78 # CDA6 7A7B # CDA7 7AFB # CDA8 7C75 # CDA9 7CFD # CDAA 8035 # CDAB 808F # CDAC 80AE # CDAD 80A3 # CDAE 80B8 # CDAF 80B5 # CDB0 80AD # CDB1 8220 # CDB2 82A0 # CDB3 82C0 # CDB4 82AB # CDB5 829A # CDB6 8298 # CDB7 829B # CDB8 82B5 # CDB9 82A7 # CDBA 82AE # CDBB 82BC # CDBC 829E # CDBD 82BA # CDBE 82B4 # CDBF 82A8 # CDC0 82A1 # CDC1 82A9 # CDC2 82C2 # CDC3 82A4 # CDC4 82C3 # CDC5 82B6 # CDC6 82A2 # CDC7 8670 # CDC8 866F # CDC9 866D # CDCA 866E # CDCB 8C56 # CDCC 8FD2 # CDCD 8FCB # CDCE 8FD3 # CDCF 8FCD # CDD0 8FD6 # CDD1 8FD5 # CDD2 8FD7 # CDD3 90B2 # CDD4 90B4 # CDD5 90AF # CDD6 90B3 # CDD7 90B0 # CDD8 9639 # CDD9 963D # CDDA 963C # CDDB 963A # CDDC 9643 # CDDD 4FCD # CDDE 4FC5 # CDDF 4FD3 # CDE0 4FB2 # CDE1 4FC9 # CDE2 4FCB # CDE3 4FC1 # CDE4 4FD4 # CDE5 4FDC # CDE6 4FD9 # CDE7 4FBB # CDE8 4FB3 # CDE9 4FDB # CDEA 4FC7 # CDEB 4FD6 # CDEC 4FBA # CDED 4FC0 # CDEE 4FB9 # CDEF 4FEC # CDF0 5244 # CDF1 5249 # CDF2 52C0 # CDF3 52C2 # CDF4 533D # CDF5 537C # CDF6 5397 # CDF7 5396 # CDF8 5399 # CDF9 5398 # CDFA 54BA # CDFB 54A1 # CDFC 54AD # CDFD 54A5 # CDFE 54CF # CE40 54C3 # CE41 830D # CE42 54B7 # CE43 54AE # CE44 54D6 # CE45 54B6 # CE46 54C5 # CE47 54C6 # CE48 54A0 # CE49 5470 # CE4A 54BC # CE4B 54A2 # CE4C 54BE # CE4D 5472 # CE4E 54DE # CE4F 54B0 # CE50 57B5 # CE51 579E # CE52 579F # CE53 57A4 # CE54 578C # CE55 5797 # CE56 579D # CE57 579B # CE58 5794 # CE59 5798 # CE5A 578F # CE5B 5799 # CE5C 57A5 # CE5D 579A # CE5E 5795 # CE5F 58F4 # CE60 590D # CE61 5953 # CE62 59E1 # CE63 59DE # CE64 59EE # CE65 5A00 # CE66 59F1 # CE67 59DD # CE68 59FA # CE69 59FD # CE6A 59FC # CE6B 59F6 # CE6C 59E4 # CE6D 59F2 # CE6E 59F7 # CE6F 59DB # CE70 59E9 # CE71 59F3 # CE72 59F5 # CE73 59E0 # CE74 59FE # CE75 59F4 # CE76 59ED # CE77 5BA8 # CE78 5C4C # CE79 5CD0 # CE7A 5CD8 # CE7B 5CCC # CE7C 5CD7 # CE7D 5CCB # CE7E 5CDB # CEA1 5CDE # CEA2 5CDA # CEA3 5CC9 # CEA4 5CC7 # CEA5 5CCA # CEA6 5CD6 # CEA7 5CD3 # CEA8 5CD4 # CEA9 5CCF # CEAA 5CC8 # CEAB 5CC6 # CEAC 5CCE # CEAD 5CDF # CEAE 5CF8 # CEAF 5DF9 # CEB0 5E21 # CEB1 5E22 # CEB2 5E23 # CEB3 5E20 # CEB4 5E24 # CEB5 5EB0 # CEB6 5EA4 # CEB7 5EA2 # CEB8 5E9B # CEB9 5EA3 # CEBA 5EA5 # CEBB 5F07 # CEBC 5F2E # CEBD 5F56 # CEBE 5F86 # CEBF 6037 # CEC0 6039 # CEC1 6054 # CEC2 6072 # CEC3 605E # CEC4 6045 # CEC5 6053 # CEC6 6047 # CEC7 6049 # CEC8 605B # CEC9 604C # CECA 6040 # CECB 6042 # CECC 605F # CECD 6024 # CECE 6044 # CECF 6058 # CED0 6066 # CED1 606E # CED2 6242 # CED3 6243 # CED4 62CF # CED5 630D # CED6 630B # CED7 62F5 # CED8 630E # CED9 6303 # CEDA 62EB # CEDB 62F9 # CEDC 630F # CEDD 630C # CEDE 62F8 # CEDF 62F6 # CEE0 6300 # CEE1 6313 # CEE2 6314 # CEE3 62FA # CEE4 6315 # CEE5 62FB # CEE6 62F0 # CEE7 6541 # CEE8 6543 # CEE9 65AA # CEEA 65BF # CEEB 6636 # CEEC 6621 # CEED 6632 # CEEE 6635 # CEEF 661C # CEF0 6626 # CEF1 6622 # CEF2 6633 # CEF3 662B # CEF4 663A # CEF5 661D # CEF6 6634 # CEF7 6639 # CEF8 662E # CEF9 670F # CEFA 6710 # CEFB 67C1 # CEFC 67F2 # CEFD 67C8 # CEFE 67BA # CF40 67DC # CF41 67BB # CF42 67F8 # CF43 67D8 # CF44 67C0 # CF45 67B7 # CF46 67C5 # CF47 67EB # CF48 67E4 # CF49 67DF # CF4A 67B5 # CF4B 67CD # CF4C 67B3 # CF4D 67F7 # CF4E 67F6 # CF4F 67EE # CF50 67E3 # CF51 67C2 # CF52 67B9 # CF53 67CE # CF54 67E7 # CF55 67F0 # CF56 67B2 # CF57 67FC # CF58 67C6 # CF59 67ED # CF5A 67CC # CF5B 67AE # CF5C 67E6 # CF5D 67DB # CF5E 67FA # CF5F 67C9 # CF60 67CA # CF61 67C3 # CF62 67EA # CF63 67CB # CF64 6B28 # CF65 6B82 # CF66 6B84 # CF67 6BB6 # CF68 6BD6 # CF69 6BD8 # CF6A 6BE0 # CF6B 6C20 # CF6C 6C21 # CF6D 6D28 # CF6E 6D34 # CF6F 6D2D # CF70 6D1F # CF71 6D3C # CF72 6D3F # CF73 6D12 # CF74 6D0A # CF75 6CDA # CF76 6D33 # CF77 6D04 # CF78 6D19 # CF79 6D3A # CF7A 6D1A # CF7B 6D11 # CF7C 6D00 # CF7D 6D1D # CF7E 6D42 # CFA1 6D01 # CFA2 6D18 # CFA3 6D37 # CFA4 6D03 # CFA5 6D0F # CFA6 6D40 # CFA7 6D07 # CFA8 6D20 # CFA9 6D2C # CFAA 6D08 # CFAB 6D22 # CFAC 6D09 # CFAD 6D10 # CFAE 70B7 # CFAF 709F # CFB0 70BE # CFB1 70B1 # CFB2 70B0 # CFB3 70A1 # CFB4 70B4 # CFB5 70B5 # CFB6 70A9 # CFB7 7241 # CFB8 7249 # CFB9 724A # CFBA 726C # CFBB 7270 # CFBC 7273 # CFBD 726E # CFBE 72CA # CFBF 72E4 # CFC0 72E8 # CFC1 72EB # CFC2 72DF # CFC3 72EA # CFC4 72E6 # CFC5 72E3 # CFC6 7385 # CFC7 73CC # CFC8 73C2 # CFC9 73C8 # CFCA 73C5 # CFCB 73B9 # CFCC 73B6 # CFCD 73B5 # CFCE 73B4 # CFCF 73EB # CFD0 73BF # CFD1 73C7 # CFD2 73BE # CFD3 73C3 # CFD4 73C6 # CFD5 73B8 # CFD6 73CB # CFD7 74EC # CFD8 74EE # CFD9 752E # CFDA 7547 # CFDB 7548 # CFDC 75A7 # CFDD 75AA # CFDE 7679 # CFDF 76C4 # CFE0 7708 # CFE1 7703 # CFE2 7704 # CFE3 7705 # CFE4 770A # CFE5 76F7 # CFE6 76FB # CFE7 76FA # CFE8 77E7 # CFE9 77E8 # CFEA 7806 # CFEB 7811 # CFEC 7812 # CFED 7805 # CFEE 7810 # CFEF 780F # CFF0 780E # CFF1 7809 # CFF2 7803 # CFF3 7813 # CFF4 794A # CFF5 794C # CFF6 794B # CFF7 7945 # CFF8 7944 # CFF9 79D5 # CFFA 79CD # CFFB 79CF # CFFC 79D6 # CFFD 79CE # CFFE 7A80 # D040 7A7E # D041 7AD1 # D042 7B00 # D043 7B01 # D044 7C7A # D045 7C78 # D046 7C79 # D047 7C7F # D048 7C80 # D049 7C81 # D04A 7D03 # D04B 7D08 # D04C 7D01 # D04D 7F58 # D04E 7F91 # D04F 7F8D # D050 7FBE # D051 8007 # D052 800E # D053 800F # D054 8014 # D055 8037 # D056 80D8 # D057 80C7 # D058 80E0 # D059 80D1 # D05A 80C8 # D05B 80C2 # D05C 80D0 # D05D 80C5 # D05E 80E3 # D05F 80D9 # D060 80DC # D061 80CA # D062 80D5 # D063 80C9 # D064 80CF # D065 80D7 # D066 80E6 # D067 80CD # D068 81FF # D069 8221 # D06A 8294 # D06B 82D9 # D06C 82FE # D06D 82F9 # D06E 8307 # D06F 82E8 # D070 8300 # D071 82D5 # D072 833A # D073 82EB # D074 82D6 # D075 82F4 # D076 82EC # D077 82E1 # D078 82F2 # D079 82F5 # D07A 830C # D07B 82FB # D07C 82F6 # D07D 82F0 # D07E 82EA # D0A1 82E4 # D0A2 82E0 # D0A3 82FA # D0A4 82F3 # D0A5 82ED # D0A6 8677 # D0A7 8674 # D0A8 867C # D0A9 8673 # D0AA 8841 # D0AB 884E # D0AC 8867 # D0AD 886A # D0AE 8869 # D0AF 89D3 # D0B0 8A04 # D0B1 8A07 # D0B2 8D72 # D0B3 8FE3 # D0B4 8FE1 # D0B5 8FEE # D0B6 8FE0 # D0B7 90F1 # D0B8 90BD # D0B9 90BF # D0BA 90D5 # D0BB 90C5 # D0BC 90BE # D0BD 90C7 # D0BE 90CB # D0BF 90C8 # D0C0 91D4 # D0C1 91D3 # D0C2 9654 # D0C3 964F # D0C4 9651 # D0C5 9653 # D0C6 964A # D0C7 964E # D0C8 501E # D0C9 5005 # D0CA 5007 # D0CB 5013 # D0CC 5022 # D0CD 5030 # D0CE 501B # D0CF 4FF5 # D0D0 4FF4 # D0D1 5033 # D0D2 5037 # D0D3 502C # D0D4 4FF6 # D0D5 4FF7 # D0D6 5017 # D0D7 501C # D0D8 5020 # D0D9 5027 # D0DA 5035 # D0DB 502F # D0DC 5031 # D0DD 500E # D0DE 515A # D0DF 5194 # D0E0 5193 # D0E1 51CA # D0E2 51C4 # D0E3 51C5 # D0E4 51C8 # D0E5 51CE # D0E6 5261 # D0E7 525A # D0E8 5252 # D0E9 525E # D0EA 525F # D0EB 5255 # D0EC 5262 # D0ED 52CD # D0EE 530E # D0EF 539E # D0F0 5526 # D0F1 54E2 # D0F2 5517 # D0F3 5512 # D0F4 54E7 # D0F5 54F3 # D0F6 54E4 # D0F7 551A # D0F8 54FF # D0F9 5504 # D0FA 5508 # D0FB 54EB # D0FC 5511 # D0FD 5505 # D0FE 54F1 # D140 550A # D141 54FB # D142 54F7 # D143 54F8 # D144 54E0 # D145 550E # D146 5503 # D147 550B # D148 5701 # D149 5702 # D14A 57CC # D14B 5832 # D14C 57D5 # D14D 57D2 # D14E 57BA # D14F 57C6 # D150 57BD # D151 57BC # D152 57B8 # D153 57B6 # D154 57BF # D155 57C7 # D156 57D0 # D157 57B9 # D158 57C1 # D159 590E # D15A 594A # D15B 5A19 # D15C 5A16 # D15D 5A2D # D15E 5A2E # D15F 5A15 # D160 5A0F # D161 5A17 # D162 5A0A # D163 5A1E # D164 5A33 # D165 5B6C # D166 5BA7 # D167 5BAD # D168 5BAC # D169 5C03 # D16A 5C56 # D16B 5C54 # D16C 5CEC # D16D 5CFF # D16E 5CEE # D16F 5CF1 # D170 5CF7 # D171 5D00 # D172 5CF9 # D173 5E29 # D174 5E28 # D175 5EA8 # D176 5EAE # D177 5EAA # D178 5EAC # D179 5F33 # D17A 5F30 # D17B 5F67 # D17C 605D # D17D 605A # D17E 6067 # D1A1 6041 # D1A2 60A2 # D1A3 6088 # D1A4 6080 # D1A5 6092 # D1A6 6081 # D1A7 609D # D1A8 6083 # D1A9 6095 # D1AA 609B # D1AB 6097 # D1AC 6087 # D1AD 609C # D1AE 608E # D1AF 6219 # D1B0 6246 # D1B1 62F2 # D1B2 6310 # D1B3 6356 # D1B4 632C # D1B5 6344 # D1B6 6345 # D1B7 6336 # D1B8 6343 # D1B9 63E4 # D1BA 6339 # D1BB 634B # D1BC 634A # D1BD 633C # D1BE 6329 # D1BF 6341 # D1C0 6334 # D1C1 6358 # D1C2 6354 # D1C3 6359 # D1C4 632D # D1C5 6347 # D1C6 6333 # D1C7 635A # D1C8 6351 # D1C9 6338 # D1CA 6357 # D1CB 6340 # D1CC 6348 # D1CD 654A # D1CE 6546 # D1CF 65C6 # D1D0 65C3 # D1D1 65C4 # D1D2 65C2 # D1D3 664A # D1D4 665F # D1D5 6647 # D1D6 6651 # D1D7 6712 # D1D8 6713 # D1D9 681F # D1DA 681A # D1DB 6849 # D1DC 6832 # D1DD 6833 # D1DE 683B # D1DF 684B # D1E0 684F # D1E1 6816 # D1E2 6831 # D1E3 681C # D1E4 6835 # D1E5 682B # D1E6 682D # D1E7 682F # D1E8 684E # D1E9 6844 # D1EA 6834 # D1EB 681D # D1EC 6812 # D1ED 6814 # D1EE 6826 # D1EF 6828 # D1F0 682E # D1F1 684D # D1F2 683A # D1F3 6825 # D1F4 6820 # D1F5 6B2C # D1F6 6B2F # D1F7 6B2D # D1F8 6B31 # D1F9 6B34 # D1FA 6B6D # D1FB 8082 # D1FC 6B88 # D1FD 6BE6 # D1FE 6BE4 # D240 6BE8 # D241 6BE3 # D242 6BE2 # D243 6BE7 # D244 6C25 # D245 6D7A # D246 6D63 # D247 6D64 # D248 6D76 # D249 6D0D # D24A 6D61 # D24B 6D92 # D24C 6D58 # D24D 6D62 # D24E 6D6D # D24F 6D6F # D250 6D91 # D251 6D8D # D252 6DEF # D253 6D7F # D254 6D86 # D255 6D5E # D256 6D67 # D257 6D60 # D258 6D97 # D259 6D70 # D25A 6D7C # D25B 6D5F # D25C 6D82 # D25D 6D98 # D25E 6D2F # D25F 6D68 # D260 6D8B # D261 6D7E # D262 6D80 # D263 6D84 # D264 6D16 # D265 6D83 # D266 6D7B # D267 6D7D # D268 6D75 # D269 6D90 # D26A 70DC # D26B 70D3 # D26C 70D1 # D26D 70DD # D26E 70CB # D26F 7F39 # D270 70E2 # D271 70D7 # D272 70D2 # D273 70DE # D274 70E0 # D275 70D4 # D276 70CD # D277 70C5 # D278 70C6 # D279 70C7 # D27A 70DA # D27B 70CE # D27C 70E1 # D27D 7242 # D27E 7278 # D2A1 7277 # D2A2 7276 # D2A3 7300 # D2A4 72FA # D2A5 72F4 # D2A6 72FE # D2A7 72F6 # D2A8 72F3 # D2A9 72FB # D2AA 7301 # D2AB 73D3 # D2AC 73D9 # D2AD 73E5 # D2AE 73D6 # D2AF 73BC # D2B0 73E7 # D2B1 73E3 # D2B2 73E9 # D2B3 73DC # D2B4 73D2 # D2B5 73DB # D2B6 73D4 # D2B7 73DD # D2B8 73DA # D2B9 73D7 # D2BA 73D8 # D2BB 73E8 # D2BC 74DE # D2BD 74DF # D2BE 74F4 # D2BF 74F5 # D2C0 7521 # D2C1 755B # D2C2 755F # D2C3 75B0 # D2C4 75C1 # D2C5 75BB # D2C6 75C4 # D2C7 75C0 # D2C8 75BF # D2C9 75B6 # D2CA 75BA # D2CB 768A # D2CC 76C9 # D2CD 771D # D2CE 771B # D2CF 7710 # D2D0 7713 # D2D1 7712 # D2D2 7723 # D2D3 7711 # D2D4 7715 # D2D5 7719 # D2D6 771A # D2D7 7722 # D2D8 7727 # D2D9 7823 # D2DA 782C # D2DB 7822 # D2DC 7835 # D2DD 782F # D2DE 7828 # D2DF 782E # D2E0 782B # D2E1 7821 # D2E2 7829 # D2E3 7833 # D2E4 782A # D2E5 7831 # D2E6 7954 # D2E7 795B # D2E8 794F # D2E9 795C # D2EA 7953 # D2EB 7952 # D2EC 7951 # D2ED 79EB # D2EE 79EC # D2EF 79E0 # D2F0 79EE # D2F1 79ED # D2F2 79EA # D2F3 79DC # D2F4 79DE # D2F5 79DD # D2F6 7A86 # D2F7 7A89 # D2F8 7A85 # D2F9 7A8B # D2FA 7A8C # D2FB 7A8A # D2FC 7A87 # D2FD 7AD8 # D2FE 7B10 # D340 7B04 # D341 7B13 # D342 7B05 # D343 7B0F # D344 7B08 # D345 7B0A # D346 7B0E # D347 7B09 # D348 7B12 # D349 7C84 # D34A 7C91 # D34B 7C8A # D34C 7C8C # D34D 7C88 # D34E 7C8D # D34F 7C85 # D350 7D1E # D351 7D1D # D352 7D11 # D353 7D0E # D354 7D18 # D355 7D16 # D356 7D13 # D357 7D1F # D358 7D12 # D359 7D0F # D35A 7D0C # D35B 7F5C # D35C 7F61 # D35D 7F5E # D35E 7F60 # D35F 7F5D # D360 7F5B # D361 7F96 # D362 7F92 # D363 7FC3 # D364 7FC2 # D365 7FC0 # D366 8016 # D367 803E # D368 8039 # D369 80FA # D36A 80F2 # D36B 80F9 # D36C 80F5 # D36D 8101 # D36E 80FB # D36F 8100 # D370 8201 # D371 822F # D372 8225 # D373 8333 # D374 832D # D375 8344 # D376 8319 # D377 8351 # D378 8325 # D379 8356 # D37A 833F # D37B 8341 # D37C 8326 # D37D 831C # D37E 8322 # D3A1 8342 # D3A2 834E # D3A3 831B # D3A4 832A # D3A5 8308 # D3A6 833C # D3A7 834D # D3A8 8316 # D3A9 8324 # D3AA 8320 # D3AB 8337 # D3AC 832F # D3AD 8329 # D3AE 8347 # D3AF 8345 # D3B0 834C # D3B1 8353 # D3B2 831E # D3B3 832C # D3B4 834B # D3B5 8327 # D3B6 8348 # D3B7 8653 # D3B8 8652 # D3B9 86A2 # D3BA 86A8 # D3BB 8696 # D3BC 868D # D3BD 8691 # D3BE 869E # D3BF 8687 # D3C0 8697 # D3C1 8686 # D3C2 868B # D3C3 869A # D3C4 8685 # D3C5 86A5 # D3C6 8699 # D3C7 86A1 # D3C8 86A7 # D3C9 8695 # D3CA 8698 # D3CB 868E # D3CC 869D # D3CD 8690 # D3CE 8694 # D3CF 8843 # D3D0 8844 # D3D1 886D # D3D2 8875 # D3D3 8876 # D3D4 8872 # D3D5 8880 # D3D6 8871 # D3D7 887F # D3D8 886F # D3D9 8883 # D3DA 887E # D3DB 8874 # D3DC 887C # D3DD 8A12 # D3DE 8C47 # D3DF 8C57 # D3E0 8C7B # D3E1 8CA4 # D3E2 8CA3 # D3E3 8D76 # D3E4 8D78 # D3E5 8DB5 # D3E6 8DB7 # D3E7 8DB6 # D3E8 8ED1 # D3E9 8ED3 # D3EA 8FFE # D3EB 8FF5 # D3EC 9002 # D3ED 8FFF # D3EE 8FFB # D3EF 9004 # D3F0 8FFC # D3F1 8FF6 # D3F2 90D6 # D3F3 90E0 # D3F4 90D9 # D3F5 90DA # D3F6 90E3 # D3F7 90DF # D3F8 90E5 # D3F9 90D8 # D3FA 90DB # D3FB 90D7 # D3FC 90DC # D3FD 90E4 # D3FE 9150 # D440 914E # D441 914F # D442 91D5 # D443 91E2 # D444 91DA # D445 965C # D446 965F # D447 96BC # D448 98E3 # D449 9ADF # D44A 9B2F # D44B 4E7F # D44C 5070 # D44D 506A # D44E 5061 # D44F 505E # D450 5060 # D451 5053 # D452 504B # D453 505D # D454 5072 # D455 5048 # D456 504D # D457 5041 # D458 505B # D459 504A # D45A 5062 # D45B 5015 # D45C 5045 # D45D 505F # D45E 5069 # D45F 506B # D460 5063 # D461 5064 # D462 5046 # D463 5040 # D464 506E # D465 5073 # D466 5057 # D467 5051 # D468 51D0 # D469 526B # D46A 526D # D46B 526C # D46C 526E # D46D 52D6 # D46E 52D3 # D46F 532D # D470 539C # D471 5575 # D472 5576 # D473 553C # D474 554D # D475 5550 # D476 5534 # D477 552A # D478 5551 # D479 5562 # D47A 5536 # D47B 5535 # D47C 5530 # D47D 5552 # D47E 5545 # D4A1 550C # D4A2 5532 # D4A3 5565 # D4A4 554E # D4A5 5539 # D4A6 5548 # D4A7 552D # D4A8 553B # D4A9 5540 # D4AA 554B # D4AB 570A # D4AC 5707 # D4AD 57FB # D4AE 5814 # D4AF 57E2 # D4B0 57F6 # D4B1 57DC # D4B2 57F4 # D4B3 5800 # D4B4 57ED # D4B5 57FD # D4B6 5808 # D4B7 57F8 # D4B8 580B # D4B9 57F3 # D4BA 57CF # D4BB 5807 # D4BC 57EE # D4BD 57E3 # D4BE 57F2 # D4BF 57E5 # D4C0 57EC # D4C1 57E1 # D4C2 580E # D4C3 57FC # D4C4 5810 # D4C5 57E7 # D4C6 5801 # D4C7 580C # D4C8 57F1 # D4C9 57E9 # D4CA 57F0 # D4CB 580D # D4CC 5804 # D4CD 595C # D4CE 5A60 # D4CF 5A58 # D4D0 5A55 # D4D1 5A67 # D4D2 5A5E # D4D3 5A38 # D4D4 5A35 # D4D5 5A6D # D4D6 5A50 # D4D7 5A5F # D4D8 5A65 # D4D9 5A6C # D4DA 5A53 # D4DB 5A64 # D4DC 5A57 # D4DD 5A43 # D4DE 5A5D # D4DF 5A52 # D4E0 5A44 # D4E1 5A5B # D4E2 5A48 # D4E3 5A8E # D4E4 5A3E # D4E5 5A4D # D4E6 5A39 # D4E7 5A4C # D4E8 5A70 # D4E9 5A69 # D4EA 5A47 # D4EB 5A51 # D4EC 5A56 # D4ED 5A42 # D4EE 5A5C # D4EF 5B72 # D4F0 5B6E # D4F1 5BC1 # D4F2 5BC0 # D4F3 5C59 # D4F4 5D1E # D4F5 5D0B # D4F6 5D1D # D4F7 5D1A # D4F8 5D20 # D4F9 5D0C # D4FA 5D28 # D4FB 5D0D # D4FC 5D26 # D4FD 5D25 # D4FE 5D0F # D540 5D30 # D541 5D12 # D542 5D23 # D543 5D1F # D544 5D2E # D545 5E3E # D546 5E34 # D547 5EB1 # D548 5EB4 # D549 5EB9 # D54A 5EB2 # D54B 5EB3 # D54C 5F36 # D54D 5F38 # D54E 5F9B # D54F 5F96 # D550 5F9F # D551 608A # D552 6090 # D553 6086 # D554 60BE # D555 60B0 # D556 60BA # D557 60D3 # D558 60D4 # D559 60CF # D55A 60E4 # D55B 60D9 # D55C 60DD # D55D 60C8 # D55E 60B1 # D55F 60DB # D560 60B7 # D561 60CA # D562 60BF # D563 60C3 # D564 60CD # D565 60C0 # D566 6332 # D567 6365 # D568 638A # D569 6382 # D56A 637D # D56B 63BD # D56C 639E # D56D 63AD # D56E 639D # D56F 6397 # D570 63AB # D571 638E # D572 636F # D573 6387 # D574 6390 # D575 636E # D576 63AF # D577 6375 # D578 639C # D579 636D # D57A 63AE # D57B 637C # D57C 63A4 # D57D 633B # D57E 639F # D5A1 6378 # D5A2 6385 # D5A3 6381 # D5A4 6391 # D5A5 638D # D5A6 6370 # D5A7 6553 # D5A8 65CD # D5A9 6665 # D5AA 6661 # D5AB 665B # D5AC 6659 # D5AD 665C # D5AE 6662 # D5AF 6718 # D5B0 6879 # D5B1 6887 # D5B2 6890 # D5B3 689C # D5B4 686D # D5B5 686E # D5B6 68AE # D5B7 68AB # D5B8 6956 # D5B9 686F # D5BA 68A3 # D5BB 68AC # D5BC 68A9 # D5BD 6875 # D5BE 6874 # D5BF 68B2 # D5C0 688F # D5C1 6877 # D5C2 6892 # D5C3 687C # D5C4 686B # D5C5 6872 # D5C6 68AA # D5C7 6880 # D5C8 6871 # D5C9 687E # D5CA 689B # D5CB 6896 # D5CC 688B # D5CD 68A0 # D5CE 6889 # D5CF 68A4 # D5D0 6878 # D5D1 687B # D5D2 6891 # D5D3 688C # D5D4 688A # D5D5 687D # D5D6 6B36 # D5D7 6B33 # D5D8 6B37 # D5D9 6B38 # D5DA 6B91 # D5DB 6B8F # D5DC 6B8D # D5DD 6B8E # D5DE 6B8C # D5DF 6C2A # D5E0 6DC0 # D5E1 6DAB # D5E2 6DB4 # D5E3 6DB3 # D5E4 6E74 # D5E5 6DAC # D5E6 6DE9 # D5E7 6DE2 # D5E8 6DB7 # D5E9 6DF6 # D5EA 6DD4 # D5EB 6E00 # D5EC 6DC8 # D5ED 6DE0 # D5EE 6DDF # D5EF 6DD6 # D5F0 6DBE # D5F1 6DE5 # D5F2 6DDC # D5F3 6DDD # D5F4 6DDB # D5F5 6DF4 # D5F6 6DCA # D5F7 6DBD # D5F8 6DED # D5F9 6DF0 # D5FA 6DBA # D5FB 6DD5 # D5FC 6DC2 # D5FD 6DCF # D5FE 6DC9 # D640 6DD0 # D641 6DF2 # D642 6DD3 # D643 6DFD # D644 6DD7 # D645 6DCD # D646 6DE3 # D647 6DBB # D648 70FA # D649 710D # D64A 70F7 # D64B 7117 # D64C 70F4 # D64D 710C # D64E 70F0 # D64F 7104 # D650 70F3 # D651 7110 # D652 70FC # D653 70FF # D654 7106 # D655 7113 # D656 7100 # D657 70F8 # D658 70F6 # D659 710B # D65A 7102 # D65B 710E # D65C 727E # D65D 727B # D65E 727C # D65F 727F # D660 731D # D661 7317 # D662 7307 # D663 7311 # D664 7318 # D665 730A # D666 7308 # D667 72FF # D668 730F # D669 731E # D66A 7388 # D66B 73F6 # D66C 73F8 # D66D 73F5 # D66E 7404 # D66F 7401 # D670 73FD # D671 7407 # D672 7400 # D673 73FA # D674 73FC # D675 73FF # D676 740C # D677 740B # D678 73F4 # D679 7408 # D67A 7564 # D67B 7563 # D67C 75CE # D67D 75D2 # D67E 75CF # D6A1 75CB # D6A2 75CC # D6A3 75D1 # D6A4 75D0 # D6A5 768F # D6A6 7689 # D6A7 76D3 # D6A8 7739 # D6A9 772F # D6AA 772D # D6AB 7731 # D6AC 7732 # D6AD 7734 # D6AE 7733 # D6AF 773D # D6B0 7725 # D6B1 773B # D6B2 7735 # D6B3 7848 # D6B4 7852 # D6B5 7849 # D6B6 784D # D6B7 784A # D6B8 784C # D6B9 7826 # D6BA 7845 # D6BB 7850 # D6BC 7964 # D6BD 7967 # D6BE 7969 # D6BF 796A # D6C0 7963 # D6C1 796B # D6C2 7961 # D6C3 79BB # D6C4 79FA # D6C5 79F8 # D6C6 79F6 # D6C7 79F7 # D6C8 7A8F # D6C9 7A94 # D6CA 7A90 # D6CB 7B35 # D6CC 7B47 # D6CD 7B34 # D6CE 7B25 # D6CF 7B30 # D6D0 7B22 # D6D1 7B24 # D6D2 7B33 # D6D3 7B18 # D6D4 7B2A # D6D5 7B1D # D6D6 7B31 # D6D7 7B2B # D6D8 7B2D # D6D9 7B2F # D6DA 7B32 # D6DB 7B38 # D6DC 7B1A # D6DD 7B23 # D6DE 7C94 # D6DF 7C98 # D6E0 7C96 # D6E1 7CA3 # D6E2 7D35 # D6E3 7D3D # D6E4 7D38 # D6E5 7D36 # D6E6 7D3A # D6E7 7D45 # D6E8 7D2C # D6E9 7D29 # D6EA 7D41 # D6EB 7D47 # D6EC 7D3E # D6ED 7D3F # D6EE 7D4A # D6EF 7D3B # D6F0 7D28 # D6F1 7F63 # D6F2 7F95 # D6F3 7F9C # D6F4 7F9D # D6F5 7F9B # D6F6 7FCA # D6F7 7FCB # D6F8 7FCD # D6F9 7FD0 # D6FA 7FD1 # D6FB 7FC7 # D6FC 7FCF # D6FD 7FC9 # D6FE 801F # D740 801E # D741 801B # D742 8047 # D743 8043 # D744 8048 # D745 8118 # D746 8125 # D747 8119 # D748 811B # D749 812D # D74A 811F # D74B 812C # D74C 811E # D74D 8121 # D74E 8115 # D74F 8127 # D750 811D # D751 8122 # D752 8211 # D753 8238 # D754 8233 # D755 823A # D756 8234 # D757 8232 # D758 8274 # D759 8390 # D75A 83A3 # D75B 83A8 # D75C 838D # D75D 837A # D75E 8373 # D75F 83A4 # D760 8374 # D761 838F # D762 8381 # D763 8395 # D764 8399 # D765 8375 # D766 8394 # D767 83A9 # D768 837D # D769 8383 # D76A 838C # D76B 839D # D76C 839B # D76D 83AA # D76E 838B # D76F 837E # D770 83A5 # D771 83AF # D772 8388 # D773 8397 # D774 83B0 # D775 837F # D776 83A6 # D777 8387 # D778 83AE # D779 8376 # D77A 839A # D77B 8659 # D77C 8656 # D77D 86BF # D77E 86B7 # D7A1 86C2 # D7A2 86C1 # D7A3 86C5 # D7A4 86BA # D7A5 86B0 # D7A6 86C8 # D7A7 86B9 # D7A8 86B3 # D7A9 86B8 # D7AA 86CC # D7AB 86B4 # D7AC 86BB # D7AD 86BC # D7AE 86C3 # D7AF 86BD # D7B0 86BE # D7B1 8852 # D7B2 8889 # D7B3 8895 # D7B4 88A8 # D7B5 88A2 # D7B6 88AA # D7B7 889A # D7B8 8891 # D7B9 88A1 # D7BA 889F # D7BB 8898 # D7BC 88A7 # D7BD 8899 # D7BE 889B # D7BF 8897 # D7C0 88A4 # D7C1 88AC # D7C2 888C # D7C3 8893 # D7C4 888E # D7C5 8982 # D7C6 89D6 # D7C7 89D9 # D7C8 89D5 # D7C9 8A30 # D7CA 8A27 # D7CB 8A2C # D7CC 8A1E # D7CD 8C39 # D7CE 8C3B # D7CF 8C5C # D7D0 8C5D # D7D1 8C7D # D7D2 8CA5 # D7D3 8D7D # D7D4 8D7B # D7D5 8D79 # D7D6 8DBC # D7D7 8DC2 # D7D8 8DB9 # D7D9 8DBF # D7DA 8DC1 # D7DB 8ED8 # D7DC 8EDE # D7DD 8EDD # D7DE 8EDC # D7DF 8ED7 # D7E0 8EE0 # D7E1 8EE1 # D7E2 9024 # D7E3 900B # D7E4 9011 # D7E5 901C # D7E6 900C # D7E7 9021 # D7E8 90EF # D7E9 90EA # D7EA 90F0 # D7EB 90F4 # D7EC 90F2 # D7ED 90F3 # D7EE 90D4 # D7EF 90EB # D7F0 90EC # D7F1 90E9 # D7F2 9156 # D7F3 9158 # D7F4 915A # D7F5 9153 # D7F6 9155 # D7F7 91EC # D7F8 91F4 # D7F9 91F1 # D7FA 91F3 # D7FB 91F8 # D7FC 91E4 # D7FD 91F9 # D7FE 91EA # D840 91EB # D841 91F7 # D842 91E8 # D843 91EE # D844 957A # D845 9586 # D846 9588 # D847 967C # D848 966D # D849 966B # D84A 9671 # D84B 966F # D84C 96BF # D84D 976A # D84E 9804 # D84F 98E5 # D850 9997 # D851 509B # D852 5095 # D853 5094 # D854 509E # D855 508B # D856 50A3 # D857 5083 # D858 508C # D859 508E # D85A 509D # D85B 5068 # D85C 509C # D85D 5092 # D85E 5082 # D85F 5087 # D860 515F # D861 51D4 # D862 5312 # D863 5311 # D864 53A4 # D865 53A7 # D866 5591 # D867 55A8 # D868 55A5 # D869 55AD # D86A 5577 # D86B 5645 # D86C 55A2 # D86D 5593 # D86E 5588 # D86F 558F # D870 55B5 # D871 5581 # D872 55A3 # D873 5592 # D874 55A4 # D875 557D # D876 558C # D877 55A6 # D878 557F # D879 5595 # D87A 55A1 # D87B 558E # D87C 570C # D87D 5829 # D87E 5837 # D8A1 5819 # D8A2 581E # D8A3 5827 # D8A4 5823 # D8A5 5828 # D8A6 57F5 # D8A7 5848 # D8A8 5825 # D8A9 581C # D8AA 581B # D8AB 5833 # D8AC 583F # D8AD 5836 # D8AE 582E # D8AF 5839 # D8B0 5838 # D8B1 582D # D8B2 582C # D8B3 583B # D8B4 5961 # D8B5 5AAF # D8B6 5A94 # D8B7 5A9F # D8B8 5A7A # D8B9 5AA2 # D8BA 5A9E # D8BB 5A78 # D8BC 5AA6 # D8BD 5A7C # D8BE 5AA5 # D8BF 5AAC # D8C0 5A95 # D8C1 5AAE # D8C2 5A37 # D8C3 5A84 # D8C4 5A8A # D8C5 5A97 # D8C6 5A83 # D8C7 5A8B # D8C8 5AA9 # D8C9 5A7B # D8CA 5A7D # D8CB 5A8C # D8CC 5A9C # D8CD 5A8F # D8CE 5A93 # D8CF 5A9D # D8D0 5BEA # D8D1 5BCD # D8D2 5BCB # D8D3 5BD4 # D8D4 5BD1 # D8D5 5BCA # D8D6 5BCE # D8D7 5C0C # D8D8 5C30 # D8D9 5D37 # D8DA 5D43 # D8DB 5D6B # D8DC 5D41 # D8DD 5D4B # D8DE 5D3F # D8DF 5D35 # D8E0 5D51 # D8E1 5D4E # D8E2 5D55 # D8E3 5D33 # D8E4 5D3A # D8E5 5D52 # D8E6 5D3D # D8E7 5D31 # D8E8 5D59 # D8E9 5D42 # D8EA 5D39 # D8EB 5D49 # D8EC 5D38 # D8ED 5D3C # D8EE 5D32 # D8EF 5D36 # D8F0 5D40 # D8F1 5D45 # D8F2 5E44 # D8F3 5E41 # D8F4 5F58 # D8F5 5FA6 # D8F6 5FA5 # D8F7 5FAB # D8F8 60C9 # D8F9 60B9 # D8FA 60CC # D8FB 60E2 # D8FC 60CE # D8FD 60C4 # D8FE 6114 # D940 60F2 # D941 610A # D942 6116 # D943 6105 # D944 60F5 # D945 6113 # D946 60F8 # D947 60FC # D948 60FE # D949 60C1 # D94A 6103 # D94B 6118 # D94C 611D # D94D 6110 # D94E 60FF # D94F 6104 # D950 610B # D951 624A # D952 6394 # D953 63B1 # D954 63B0 # D955 63CE # D956 63E5 # D957 63E8 # D958 63EF # D959 63C3 # D95A 649D # D95B 63F3 # D95C 63CA # D95D 63E0 # D95E 63F6 # D95F 63D5 # D960 63F2 # D961 63F5 # D962 6461 # D963 63DF # D964 63BE # D965 63DD # D966 63DC # D967 63C4 # D968 63D8 # D969 63D3 # D96A 63C2 # D96B 63C7 # D96C 63CC # D96D 63CB # D96E 63C8 # D96F 63F0 # D970 63D7 # D971 63D9 # D972 6532 # D973 6567 # D974 656A # D975 6564 # D976 655C # D977 6568 # D978 6565 # D979 658C # D97A 659D # D97B 659E # D97C 65AE # D97D 65D0 # D97E 65D2 # D9A1 667C # D9A2 666C # D9A3 667B # D9A4 6680 # D9A5 6671 # D9A6 6679 # D9A7 666A # D9A8 6672 # D9A9 6701 # D9AA 690C # D9AB 68D3 # D9AC 6904 # D9AD 68DC # D9AE 692A # D9AF 68EC # D9B0 68EA # D9B1 68F1 # D9B2 690F # D9B3 68D6 # D9B4 68F7 # D9B5 68EB # D9B6 68E4 # D9B7 68F6 # D9B8 6913 # D9B9 6910 # D9BA 68F3 # D9BB 68E1 # D9BC 6907 # D9BD 68CC # D9BE 6908 # D9BF 6970 # D9C0 68B4 # D9C1 6911 # D9C2 68EF # D9C3 68C6 # D9C4 6914 # D9C5 68F8 # D9C6 68D0 # D9C7 68FD # D9C8 68FC # D9C9 68E8 # D9CA 690B # D9CB 690A # D9CC 6917 # D9CD 68CE # D9CE 68C8 # D9CF 68DD # D9D0 68DE # D9D1 68E6 # D9D2 68F4 # D9D3 68D1 # D9D4 6906 # D9D5 68D4 # D9D6 68E9 # D9D7 6915 # D9D8 6925 # D9D9 68C7 # D9DA 6B39 # D9DB 6B3B # D9DC 6B3F # D9DD 6B3C # D9DE 6B94 # D9DF 6B97 # D9E0 6B99 # D9E1 6B95 # D9E2 6BBD # D9E3 6BF0 # D9E4 6BF2 # D9E5 6BF3 # D9E6 6C30 # D9E7 6DFC # D9E8 6E46 # D9E9 6E47 # D9EA 6E1F # D9EB 6E49 # D9EC 6E88 # D9ED 6E3C # D9EE 6E3D # D9EF 6E45 # D9F0 6E62 # D9F1 6E2B # D9F2 6E3F # D9F3 6E41 # D9F4 6E5D # D9F5 6E73 # D9F6 6E1C # D9F7 6E33 # D9F8 6E4B # D9F9 6E40 # D9FA 6E51 # D9FB 6E3B # D9FC 6E03 # D9FD 6E2E # D9FE 6E5E # DA40 6E68 # DA41 6E5C # DA42 6E61 # DA43 6E31 # DA44 6E28 # DA45 6E60 # DA46 6E71 # DA47 6E6B # DA48 6E39 # DA49 6E22 # DA4A 6E30 # DA4B 6E53 # DA4C 6E65 # DA4D 6E27 # DA4E 6E78 # DA4F 6E64 # DA50 6E77 # DA51 6E55 # DA52 6E79 # DA53 6E52 # DA54 6E66 # DA55 6E35 # DA56 6E36 # DA57 6E5A # DA58 7120 # DA59 711E # DA5A 712F # DA5B 70FB # DA5C 712E # DA5D 7131 # DA5E 7123 # DA5F 7125 # DA60 7122 # DA61 7132 # DA62 711F # DA63 7128 # DA64 713A # DA65 711B # DA66 724B # DA67 725A # DA68 7288 # DA69 7289 # DA6A 7286 # DA6B 7285 # DA6C 728B # DA6D 7312 # DA6E 730B # DA6F 7330 # DA70 7322 # DA71 7331 # DA72 7333 # DA73 7327 # DA74 7332 # DA75 732D # DA76 7326 # DA77 7323 # DA78 7335 # DA79 730C # DA7A 742E # DA7B 742C # DA7C 7430 # DA7D 742B # DA7E 7416 # DAA1 741A # DAA2 7421 # DAA3 742D # DAA4 7431 # DAA5 7424 # DAA6 7423 # DAA7 741D # DAA8 7429 # DAA9 7420 # DAAA 7432 # DAAB 74FB # DAAC 752F # DAAD 756F # DAAE 756C # DAAF 75E7 # DAB0 75DA # DAB1 75E1 # DAB2 75E6 # DAB3 75DD # DAB4 75DF # DAB5 75E4 # DAB6 75D7 # DAB7 7695 # DAB8 7692 # DAB9 76DA # DABA 7746 # DABB 7747 # DABC 7744 # DABD 774D # DABE 7745 # DABF 774A # DAC0 774E # DAC1 774B # DAC2 774C # DAC3 77DE # DAC4 77EC # DAC5 7860 # DAC6 7864 # DAC7 7865 # DAC8 785C # DAC9 786D # DACA 7871 # DACB 786A # DACC 786E # DACD 7870 # DACE 7869 # DACF 7868 # DAD0 785E # DAD1 7862 # DAD2 7974 # DAD3 7973 # DAD4 7972 # DAD5 7970 # DAD6 7A02 # DAD7 7A0A # DAD8 7A03 # DAD9 7A0C # DADA 7A04 # DADB 7A99 # DADC 7AE6 # DADD 7AE4 # DADE 7B4A # DADF 7B3B # DAE0 7B44 # DAE1 7B48 # DAE2 7B4C # DAE3 7B4E # DAE4 7B40 # DAE5 7B58 # DAE6 7B45 # DAE7 7CA2 # DAE8 7C9E # DAE9 7CA8 # DAEA 7CA1 # DAEB 7D58 # DAEC 7D6F # DAED 7D63 # DAEE 7D53 # DAEF 7D56 # DAF0 7D67 # DAF1 7D6A # DAF2 7D4F # DAF3 7D6D # DAF4 7D5C # DAF5 7D6B # DAF6 7D52 # DAF7 7D54 # DAF8 7D69 # DAF9 7D51 # DAFA 7D5F # DAFB 7D4E # DAFC 7F3E # DAFD 7F3F # DAFE 7F65 # DB40 7F66 # DB41 7FA2 # DB42 7FA0 # DB43 7FA1 # DB44 7FD7 # DB45 8051 # DB46 804F # DB47 8050 # DB48 80FE # DB49 80D4 # DB4A 8143 # DB4B 814A # DB4C 8152 # DB4D 814F # DB4E 8147 # DB4F 813D # DB50 814D # DB51 813A # DB52 81E6 # DB53 81EE # DB54 81F7 # DB55 81F8 # DB56 81F9 # DB57 8204 # DB58 823C # DB59 823D # DB5A 823F # DB5B 8275 # DB5C 833B # DB5D 83CF # DB5E 83F9 # DB5F 8423 # DB60 83C0 # DB61 83E8 # DB62 8412 # DB63 83E7 # DB64 83E4 # DB65 83FC # DB66 83F6 # DB67 8410 # DB68 83C6 # DB69 83C8 # DB6A 83EB # DB6B 83E3 # DB6C 83BF # DB6D 8401 # DB6E 83DD # DB6F 83E5 # DB70 83D8 # DB71 83FF # DB72 83E1 # DB73 83CB # DB74 83CE # DB75 83D6 # DB76 83F5 # DB77 83C9 # DB78 8409 # DB79 840F # DB7A 83DE # DB7B 8411 # DB7C 8406 # DB7D 83C2 # DB7E 83F3 # DBA1 83D5 # DBA2 83FA # DBA3 83C7 # DBA4 83D1 # DBA5 83EA # DBA6 8413 # DBA7 83C3 # DBA8 83EC # DBA9 83EE # DBAA 83C4 # DBAB 83FB # DBAC 83D7 # DBAD 83E2 # DBAE 841B # DBAF 83DB # DBB0 83FE # DBB1 86D8 # DBB2 86E2 # DBB3 86E6 # DBB4 86D3 # DBB5 86E3 # DBB6 86DA # DBB7 86EA # DBB8 86DD # DBB9 86EB # DBBA 86DC # DBBB 86EC # DBBC 86E9 # DBBD 86D7 # DBBE 86E8 # DBBF 86D1 # DBC0 8848 # DBC1 8856 # DBC2 8855 # DBC3 88BA # DBC4 88D7 # DBC5 88B9 # DBC6 88B8 # DBC7 88C0 # DBC8 88BE # DBC9 88B6 # DBCA 88BC # DBCB 88B7 # DBCC 88BD # DBCD 88B2 # DBCE 8901 # DBCF 88C9 # DBD0 8995 # DBD1 8998 # DBD2 8997 # DBD3 89DD # DBD4 89DA # DBD5 89DB # DBD6 8A4E # DBD7 8A4D # DBD8 8A39 # DBD9 8A59 # DBDA 8A40 # DBDB 8A57 # DBDC 8A58 # DBDD 8A44 # DBDE 8A45 # DBDF 8A52 # DBE0 8A48 # DBE1 8A51 # DBE2 8A4A # DBE3 8A4C # DBE4 8A4F # DBE5 8C5F # DBE6 8C81 # DBE7 8C80 # DBE8 8CBA # DBE9 8CBE # DBEA 8CB0 # DBEB 8CB9 # DBEC 8CB5 # DBED 8D84 # DBEE 8D80 # DBEF 8D89 # DBF0 8DD8 # DBF1 8DD3 # DBF2 8DCD # DBF3 8DC7 # DBF4 8DD6 # DBF5 8DDC # DBF6 8DCF # DBF7 8DD5 # DBF8 8DD9 # DBF9 8DC8 # DBFA 8DD7 # DBFB 8DC5 # DBFC 8EEF # DBFD 8EF7 # DBFE 8EFA # DC40 8EF9 # DC41 8EE6 # DC42 8EEE # DC43 8EE5 # DC44 8EF5 # DC45 8EE7 # DC46 8EE8 # DC47 8EF6 # DC48 8EEB # DC49 8EF1 # DC4A 8EEC # DC4B 8EF4 # DC4C 8EE9 # DC4D 902D # DC4E 9034 # DC4F 902F # DC50 9106 # DC51 912C # DC52 9104 # DC53 90FF # DC54 90FC # DC55 9108 # DC56 90F9 # DC57 90FB # DC58 9101 # DC59 9100 # DC5A 9107 # DC5B 9105 # DC5C 9103 # DC5D 9161 # DC5E 9164 # DC5F 915F # DC60 9162 # DC61 9160 # DC62 9201 # DC63 920A # DC64 9225 # DC65 9203 # DC66 921A # DC67 9226 # DC68 920F # DC69 920C # DC6A 9200 # DC6B 9212 # DC6C 91FF # DC6D 91FD # DC6E 9206 # DC6F 9204 # DC70 9227 # DC71 9202 # DC72 921C # DC73 9224 # DC74 9219 # DC75 9217 # DC76 9205 # DC77 9216 # DC78 957B # DC79 958D # DC7A 958C # DC7B 9590 # DC7C 9687 # DC7D 967E # DC7E 9688 # DCA1 9689 # DCA2 9683 # DCA3 9680 # DCA4 96C2 # DCA5 96C8 # DCA6 96C3 # DCA7 96F1 # DCA8 96F0 # DCA9 976C # DCAA 9770 # DCAB 976E # DCAC 9807 # DCAD 98A9 # DCAE 98EB # DCAF 9CE6 # DCB0 9EF9 # DCB1 4E83 # DCB2 4E84 # DCB3 4EB6 # DCB4 50BD # DCB5 50BF # DCB6 50C6 # DCB7 50AE # DCB8 50C4 # DCB9 50CA # DCBA 50B4 # DCBB 50C8 # DCBC 50C2 # DCBD 50B0 # DCBE 50C1 # DCBF 50BA # DCC0 50B1 # DCC1 50CB # DCC2 50C9 # DCC3 50B6 # DCC4 50B8 # DCC5 51D7 # DCC6 527A # DCC7 5278 # DCC8 527B # DCC9 527C # DCCA 55C3 # DCCB 55DB # DCCC 55CC # DCCD 55D0 # DCCE 55CB # DCCF 55CA # DCD0 55DD # DCD1 55C0 # DCD2 55D4 # DCD3 55C4 # DCD4 55E9 # DCD5 55BF # DCD6 55D2 # DCD7 558D # DCD8 55CF # DCD9 55D5 # DCDA 55E2 # DCDB 55D6 # DCDC 55C8 # DCDD 55F2 # DCDE 55CD # DCDF 55D9 # DCE0 55C2 # DCE1 5714 # DCE2 5853 # DCE3 5868 # DCE4 5864 # DCE5 584F # DCE6 584D # DCE7 5849 # DCE8 586F # DCE9 5855 # DCEA 584E # DCEB 585D # DCEC 5859 # DCED 5865 # DCEE 585B # DCEF 583D # DCF0 5863 # DCF1 5871 # DCF2 58FC # DCF3 5AC7 # DCF4 5AC4 # DCF5 5ACB # DCF6 5ABA # DCF7 5AB8 # DCF8 5AB1 # DCF9 5AB5 # DCFA 5AB0 # DCFB 5ABF # DCFC 5AC8 # DCFD 5ABB # DCFE 5AC6 # DD40 5AB7 # DD41 5AC0 # DD42 5ACA # DD43 5AB4 # DD44 5AB6 # DD45 5ACD # DD46 5AB9 # DD47 5A90 # DD48 5BD6 # DD49 5BD8 # DD4A 5BD9 # DD4B 5C1F # DD4C 5C33 # DD4D 5D71 # DD4E 5D63 # DD4F 5D4A # DD50 5D65 # DD51 5D72 # DD52 5D6C # DD53 5D5E # DD54 5D68 # DD55 5D67 # DD56 5D62 # DD57 5DF0 # DD58 5E4F # DD59 5E4E # DD5A 5E4A # DD5B 5E4D # DD5C 5E4B # DD5D 5EC5 # DD5E 5ECC # DD5F 5EC6 # DD60 5ECB # DD61 5EC7 # DD62 5F40 # DD63 5FAF # DD64 5FAD # DD65 60F7 # DD66 6149 # DD67 614A # DD68 612B # DD69 6145 # DD6A 6136 # DD6B 6132 # DD6C 612E # DD6D 6146 # DD6E 612F # DD6F 614F # DD70 6129 # DD71 6140 # DD72 6220 # DD73 9168 # DD74 6223 # DD75 6225 # DD76 6224 # DD77 63C5 # DD78 63F1 # DD79 63EB # DD7A 6410 # DD7B 6412 # DD7C 6409 # DD7D 6420 # DD7E 6424 # DDA1 6433 # DDA2 6443 # DDA3 641F # DDA4 6415 # DDA5 6418 # DDA6 6439 # DDA7 6437 # DDA8 6422 # DDA9 6423 # DDAA 640C # DDAB 6426 # DDAC 6430 # DDAD 6428 # DDAE 6441 # DDAF 6435 # DDB0 642F # DDB1 640A # DDB2 641A # DDB3 6440 # DDB4 6425 # DDB5 6427 # DDB6 640B # DDB7 63E7 # DDB8 641B # DDB9 642E # DDBA 6421 # DDBB 640E # DDBC 656F # DDBD 6592 # DDBE 65D3 # DDBF 6686 # DDC0 668C # DDC1 6695 # DDC2 6690 # DDC3 668B # DDC4 668A # DDC5 6699 # DDC6 6694 # DDC7 6678 # DDC8 6720 # DDC9 6966 # DDCA 695F # DDCB 6938 # DDCC 694E # DDCD 6962 # DDCE 6971 # DDCF 693F # DDD0 6945 # DDD1 696A # DDD2 6939 # DDD3 6942 # DDD4 6957 # DDD5 6959 # DDD6 697A # DDD7 6948 # DDD8 6949 # DDD9 6935 # DDDA 696C # DDDB 6933 # DDDC 693D # DDDD 6965 # DDDE 68F0 # DDDF 6978 # DDE0 6934 # DDE1 6969 # DDE2 6940 # DDE3 696F # DDE4 6944 # DDE5 6976 # DDE6 6958 # DDE7 6941 # DDE8 6974 # DDE9 694C # DDEA 693B # DDEB 694B # DDEC 6937 # DDED 695C # DDEE 694F # DDEF 6951 # DDF0 6932 # DDF1 6952 # DDF2 692F # DDF3 697B # DDF4 693C # DDF5 6B46 # DDF6 6B45 # DDF7 6B43 # DDF8 6B42 # DDF9 6B48 # DDFA 6B41 # DDFB 6B9B # DDFC FA0D # CJK COMPATIBILITY IDEOGRAPH-FA0D DDFD 6BFB # DDFE 6BFC # DE40 6BF9 # DE41 6BF7 # DE42 6BF8 # DE43 6E9B # DE44 6ED6 # DE45 6EC8 # DE46 6E8F # DE47 6EC0 # DE48 6E9F # DE49 6E93 # DE4A 6E94 # DE4B 6EA0 # DE4C 6EB1 # DE4D 6EB9 # DE4E 6EC6 # DE4F 6ED2 # DE50 6EBD # DE51 6EC1 # DE52 6E9E # DE53 6EC9 # DE54 6EB7 # DE55 6EB0 # DE56 6ECD # DE57 6EA6 # DE58 6ECF # DE59 6EB2 # DE5A 6EBE # DE5B 6EC3 # DE5C 6EDC # DE5D 6ED8 # DE5E 6E99 # DE5F 6E92 # DE60 6E8E # DE61 6E8D # DE62 6EA4 # DE63 6EA1 # DE64 6EBF # DE65 6EB3 # DE66 6ED0 # DE67 6ECA # DE68 6E97 # DE69 6EAE # DE6A 6EA3 # DE6B 7147 # DE6C 7154 # DE6D 7152 # DE6E 7163 # DE6F 7160 # DE70 7141 # DE71 715D # DE72 7162 # DE73 7172 # DE74 7178 # DE75 716A # DE76 7161 # DE77 7142 # DE78 7158 # DE79 7143 # DE7A 714B # DE7B 7170 # DE7C 715F # DE7D 7150 # DE7E 7153 # DEA1 7144 # DEA2 714D # DEA3 715A # DEA4 724F # DEA5 728D # DEA6 728C # DEA7 7291 # DEA8 7290 # DEA9 728E # DEAA 733C # DEAB 7342 # DEAC 733B # DEAD 733A # DEAE 7340 # DEAF 734A # DEB0 7349 # DEB1 7444 # DEB2 744A # DEB3 744B # DEB4 7452 # DEB5 7451 # DEB6 7457 # DEB7 7440 # DEB8 744F # DEB9 7450 # DEBA 744E # DEBB 7442 # DEBC 7446 # DEBD 744D # DEBE 7454 # DEBF 74E1 # DEC0 74FF # DEC1 74FE # DEC2 74FD # DEC3 751D # DEC4 7579 # DEC5 7577 # DEC6 6983 # DEC7 75EF # DEC8 760F # DEC9 7603 # DECA 75F7 # DECB 75FE # DECC 75FC # DECD 75F9 # DECE 75F8 # DECF 7610 # DED0 75FB # DED1 75F6 # DED2 75ED # DED3 75F5 # DED4 75FD # DED5 7699 # DED6 76B5 # DED7 76DD # DED8 7755 # DED9 775F # DEDA 7760 # DEDB 7752 # DEDC 7756 # DEDD 775A # DEDE 7769 # DEDF 7767 # DEE0 7754 # DEE1 7759 # DEE2 776D # DEE3 77E0 # DEE4 7887 # DEE5 789A # DEE6 7894 # DEE7 788F # DEE8 7884 # DEE9 7895 # DEEA 7885 # DEEB 7886 # DEEC 78A1 # DEED 7883 # DEEE 7879 # DEEF 7899 # DEF0 7880 # DEF1 7896 # DEF2 787B # DEF3 797C # DEF4 7982 # DEF5 797D # DEF6 7979 # DEF7 7A11 # DEF8 7A18 # DEF9 7A19 # DEFA 7A12 # DEFB 7A17 # DEFC 7A15 # DEFD 7A22 # DEFE 7A13 # DF40 7A1B # DF41 7A10 # DF42 7AA3 # DF43 7AA2 # DF44 7A9E # DF45 7AEB # DF46 7B66 # DF47 7B64 # DF48 7B6D # DF49 7B74 # DF4A 7B69 # DF4B 7B72 # DF4C 7B65 # DF4D 7B73 # DF4E 7B71 # DF4F 7B70 # DF50 7B61 # DF51 7B78 # DF52 7B76 # DF53 7B63 # DF54 7CB2 # DF55 7CB4 # DF56 7CAF # DF57 7D88 # DF58 7D86 # DF59 7D80 # DF5A 7D8D # DF5B 7D7F # DF5C 7D85 # DF5D 7D7A # DF5E 7D8E # DF5F 7D7B # DF60 7D83 # DF61 7D7C # DF62 7D8C # DF63 7D94 # DF64 7D84 # DF65 7D7D # DF66 7D92 # DF67 7F6D # DF68 7F6B # DF69 7F67 # DF6A 7F68 # DF6B 7F6C # DF6C 7FA6 # DF6D 7FA5 # DF6E 7FA7 # DF6F 7FDB # DF70 7FDC # DF71 8021 # DF72 8164 # DF73 8160 # DF74 8177 # DF75 815C # DF76 8169 # DF77 815B # DF78 8162 # DF79 8172 # DF7A 6721 # DF7B 815E # DF7C 8176 # DF7D 8167 # DF7E 816F # DFA1 8144 # DFA2 8161 # DFA3 821D # DFA4 8249 # DFA5 8244 # DFA6 8240 # DFA7 8242 # DFA8 8245 # DFA9 84F1 # DFAA 843F # DFAB 8456 # DFAC 8476 # DFAD 8479 # DFAE 848F # DFAF 848D # DFB0 8465 # DFB1 8451 # DFB2 8440 # DFB3 8486 # DFB4 8467 # DFB5 8430 # DFB6 844D # DFB7 847D # DFB8 845A # DFB9 8459 # DFBA 8474 # DFBB 8473 # DFBC 845D # DFBD 8507 # DFBE 845E # DFBF 8437 # DFC0 843A # DFC1 8434 # DFC2 847A # DFC3 8443 # DFC4 8478 # DFC5 8432 # DFC6 8445 # DFC7 8429 # DFC8 83D9 # DFC9 844B # DFCA 842F # DFCB 8442 # DFCC 842D # DFCD 845F # DFCE 8470 # DFCF 8439 # DFD0 844E # DFD1 844C # DFD2 8452 # DFD3 846F # DFD4 84C5 # DFD5 848E # DFD6 843B # DFD7 8447 # DFD8 8436 # DFD9 8433 # DFDA 8468 # DFDB 847E # DFDC 8444 # DFDD 842B # DFDE 8460 # DFDF 8454 # DFE0 846E # DFE1 8450 # DFE2 870B # DFE3 8704 # DFE4 86F7 # DFE5 870C # DFE6 86FA # DFE7 86D6 # DFE8 86F5 # DFE9 874D # DFEA 86F8 # DFEB 870E # DFEC 8709 # DFED 8701 # DFEE 86F6 # DFEF 870D # DFF0 8705 # DFF1 88D6 # DFF2 88CB # DFF3 88CD # DFF4 88CE # DFF5 88DE # DFF6 88DB # DFF7 88DA # DFF8 88CC # DFF9 88D0 # DFFA 8985 # DFFB 899B # DFFC 89DF # DFFD 89E5 # DFFE 89E4 # E040 89E1 # E041 89E0 # E042 89E2 # E043 89DC # E044 89E6 # E045 8A76 # E046 8A86 # E047 8A7F # E048 8A61 # E049 8A3F # E04A 8A77 # E04B 8A82 # E04C 8A84 # E04D 8A75 # E04E 8A83 # E04F 8A81 # E050 8A74 # E051 8A7A # E052 8C3C # E053 8C4B # E054 8C4A # E055 8C65 # E056 8C64 # E057 8C66 # E058 8C86 # E059 8C84 # E05A 8C85 # E05B 8CCC # E05C 8D68 # E05D 8D69 # E05E 8D91 # E05F 8D8C # E060 8D8E # E061 8D8F # E062 8D8D # E063 8D93 # E064 8D94 # E065 8D90 # E066 8D92 # E067 8DF0 # E068 8DE0 # E069 8DEC # E06A 8DF1 # E06B 8DEE # E06C 8DD0 # E06D 8DE9 # E06E 8DE3 # E06F 8DE2 # E070 8DE7 # E071 8DF2 # E072 8DEB # E073 8DF4 # E074 8F06 # E075 8EFF # E076 8F01 # E077 8F00 # E078 8F05 # E079 8F07 # E07A 8F08 # E07B 8F02 # E07C 8F0B # E07D 9052 # E07E 903F # E0A1 9044 # E0A2 9049 # E0A3 903D # E0A4 9110 # E0A5 910D # E0A6 910F # E0A7 9111 # E0A8 9116 # E0A9 9114 # E0AA 910B # E0AB 910E # E0AC 916E # E0AD 916F # E0AE 9248 # E0AF 9252 # E0B0 9230 # E0B1 923A # E0B2 9266 # E0B3 9233 # E0B4 9265 # E0B5 925E # E0B6 9283 # E0B7 922E # E0B8 924A # E0B9 9246 # E0BA 926D # E0BB 926C # E0BC 924F # E0BD 9260 # E0BE 9267 # E0BF 926F # E0C0 9236 # E0C1 9261 # E0C2 9270 # E0C3 9231 # E0C4 9254 # E0C5 9263 # E0C6 9250 # E0C7 9272 # E0C8 924E # E0C9 9253 # E0CA 924C # E0CB 9256 # E0CC 9232 # E0CD 959F # E0CE 959C # E0CF 959E # E0D0 959B # E0D1 9692 # E0D2 9693 # E0D3 9691 # E0D4 9697 # E0D5 96CE # E0D6 96FA # E0D7 96FD # E0D8 96F8 # E0D9 96F5 # E0DA 9773 # E0DB 9777 # E0DC 9778 # E0DD 9772 # E0DE 980F # E0DF 980D # E0E0 980E # E0E1 98AC # E0E2 98F6 # E0E3 98F9 # E0E4 99AF # E0E5 99B2 # E0E6 99B0 # E0E7 99B5 # E0E8 9AAD # E0E9 9AAB # E0EA 9B5B # E0EB 9CEA # E0EC 9CED # E0ED 9CE7 # E0EE 9E80 # E0EF 9EFD # E0F0 50E6 # E0F1 50D4 # E0F2 50D7 # E0F3 50E8 # E0F4 50F3 # E0F5 50DB # E0F6 50EA # E0F7 50DD # E0F8 50E4 # E0F9 50D3 # E0FA 50EC # E0FB 50F0 # E0FC 50EF # E0FD 50E3 # E0FE 50E0 # E140 51D8 # E141 5280 # E142 5281 # E143 52E9 # E144 52EB # E145 5330 # E146 53AC # E147 5627 # E148 5615 # E149 560C # E14A 5612 # E14B 55FC # E14C 560F # E14D 561C # E14E 5601 # E14F 5613 # E150 5602 # E151 55FA # E152 561D # E153 5604 # E154 55FF # E155 55F9 # E156 5889 # E157 587C # E158 5890 # E159 5898 # E15A 5886 # E15B 5881 # E15C 587F # E15D 5874 # E15E 588B # E15F 587A # E160 5887 # E161 5891 # E162 588E # E163 5876 # E164 5882 # E165 5888 # E166 587B # E167 5894 # E168 588F # E169 58FE # E16A 596B # E16B 5ADC # E16C 5AEE # E16D 5AE5 # E16E 5AD5 # E16F 5AEA # E170 5ADA # E171 5AED # E172 5AEB # E173 5AF3 # E174 5AE2 # E175 5AE0 # E176 5ADB # E177 5AEC # E178 5ADE # E179 5ADD # E17A 5AD9 # E17B 5AE8 # E17C 5ADF # E17D 5B77 # E17E 5BE0 # E1A1 5BE3 # E1A2 5C63 # E1A3 5D82 # E1A4 5D80 # E1A5 5D7D # E1A6 5D86 # E1A7 5D7A # E1A8 5D81 # E1A9 5D77 # E1AA 5D8A # E1AB 5D89 # E1AC 5D88 # E1AD 5D7E # E1AE 5D7C # E1AF 5D8D # E1B0 5D79 # E1B1 5D7F # E1B2 5E58 # E1B3 5E59 # E1B4 5E53 # E1B5 5ED8 # E1B6 5ED1 # E1B7 5ED7 # E1B8 5ECE # E1B9 5EDC # E1BA 5ED5 # E1BB 5ED9 # E1BC 5ED2 # E1BD 5ED4 # E1BE 5F44 # E1BF 5F43 # E1C0 5F6F # E1C1 5FB6 # E1C2 612C # E1C3 6128 # E1C4 6141 # E1C5 615E # E1C6 6171 # E1C7 6173 # E1C8 6152 # E1C9 6153 # E1CA 6172 # E1CB 616C # E1CC 6180 # E1CD 6174 # E1CE 6154 # E1CF 617A # E1D0 615B # E1D1 6165 # E1D2 613B # E1D3 616A # E1D4 6161 # E1D5 6156 # E1D6 6229 # E1D7 6227 # E1D8 622B # E1D9 642B # E1DA 644D # E1DB 645B # E1DC 645D # E1DD 6474 # E1DE 6476 # E1DF 6472 # E1E0 6473 # E1E1 647D # E1E2 6475 # E1E3 6466 # E1E4 64A6 # E1E5 644E # E1E6 6482 # E1E7 645E # E1E8 645C # E1E9 644B # E1EA 6453 # E1EB 6460 # E1EC 6450 # E1ED 647F # E1EE 643F # E1EF 646C # E1F0 646B # E1F1 6459 # E1F2 6465 # E1F3 6477 # E1F4 6573 # E1F5 65A0 # E1F6 66A1 # E1F7 66A0 # E1F8 669F # E1F9 6705 # E1FA 6704 # E1FB 6722 # E1FC 69B1 # E1FD 69B6 # E1FE 69C9 # E240 69A0 # E241 69CE # E242 6996 # E243 69B0 # E244 69AC # E245 69BC # E246 6991 # E247 6999 # E248 698E # E249 69A7 # E24A 698D # E24B 69A9 # E24C 69BE # E24D 69AF # E24E 69BF # E24F 69C4 # E250 69BD # E251 69A4 # E252 69D4 # E253 69B9 # E254 69CA # E255 699A # E256 69CF # E257 69B3 # E258 6993 # E259 69AA # E25A 69A1 # E25B 699E # E25C 69D9 # E25D 6997 # E25E 6990 # E25F 69C2 # E260 69B5 # E261 69A5 # E262 69C6 # E263 6B4A # E264 6B4D # E265 6B4B # E266 6B9E # E267 6B9F # E268 6BA0 # E269 6BC3 # E26A 6BC4 # E26B 6BFE # E26C 6ECE # E26D 6EF5 # E26E 6EF1 # E26F 6F03 # E270 6F25 # E271 6EF8 # E272 6F37 # E273 6EFB # E274 6F2E # E275 6F09 # E276 6F4E # E277 6F19 # E278 6F1A # E279 6F27 # E27A 6F18 # E27B 6F3B # E27C 6F12 # E27D 6EED # E27E 6F0A # E2A1 6F36 # E2A2 6F73 # E2A3 6EF9 # E2A4 6EEE # E2A5 6F2D # E2A6 6F40 # E2A7 6F30 # E2A8 6F3C # E2A9 6F35 # E2AA 6EEB # E2AB 6F07 # E2AC 6F0E # E2AD 6F43 # E2AE 6F05 # E2AF 6EFD # E2B0 6EF6 # E2B1 6F39 # E2B2 6F1C # E2B3 6EFC # E2B4 6F3A # E2B5 6F1F # E2B6 6F0D # E2B7 6F1E # E2B8 6F08 # E2B9 6F21 # E2BA 7187 # E2BB 7190 # E2BC 7189 # E2BD 7180 # E2BE 7185 # E2BF 7182 # E2C0 718F # E2C1 717B # E2C2 7186 # E2C3 7181 # E2C4 7197 # E2C5 7244 # E2C6 7253 # E2C7 7297 # E2C8 7295 # E2C9 7293 # E2CA 7343 # E2CB 734D # E2CC 7351 # E2CD 734C # E2CE 7462 # E2CF 7473 # E2D0 7471 # E2D1 7475 # E2D2 7472 # E2D3 7467 # E2D4 746E # E2D5 7500 # E2D6 7502 # E2D7 7503 # E2D8 757D # E2D9 7590 # E2DA 7616 # E2DB 7608 # E2DC 760C # E2DD 7615 # E2DE 7611 # E2DF 760A # E2E0 7614 # E2E1 76B8 # E2E2 7781 # E2E3 777C # E2E4 7785 # E2E5 7782 # E2E6 776E # E2E7 7780 # E2E8 776F # E2E9 777E # E2EA 7783 # E2EB 78B2 # E2EC 78AA # E2ED 78B4 # E2EE 78AD # E2EF 78A8 # E2F0 787E # E2F1 78AB # E2F2 789E # E2F3 78A5 # E2F4 78A0 # E2F5 78AC # E2F6 78A2 # E2F7 78A4 # E2F8 7998 # E2F9 798A # E2FA 798B # E2FB 7996 # E2FC 7995 # E2FD 7994 # E2FE 7993 # E340 7997 # E341 7988 # E342 7992 # E343 7990 # E344 7A2B # E345 7A4A # E346 7A30 # E347 7A2F # E348 7A28 # E349 7A26 # E34A 7AA8 # E34B 7AAB # E34C 7AAC # E34D 7AEE # E34E 7B88 # E34F 7B9C # E350 7B8A # E351 7B91 # E352 7B90 # E353 7B96 # E354 7B8D # E355 7B8C # E356 7B9B # E357 7B8E # E358 7B85 # E359 7B98 # E35A 5284 # E35B 7B99 # E35C 7BA4 # E35D 7B82 # E35E 7CBB # E35F 7CBF # E360 7CBC # E361 7CBA # E362 7DA7 # E363 7DB7 # E364 7DC2 # E365 7DA3 # E366 7DAA # E367 7DC1 # E368 7DC0 # E369 7DC5 # E36A 7D9D # E36B 7DCE # E36C 7DC4 # E36D 7DC6 # E36E 7DCB # E36F 7DCC # E370 7DAF # E371 7DB9 # E372 7D96 # E373 7DBC # E374 7D9F # E375 7DA6 # E376 7DAE # E377 7DA9 # E378 7DA1 # E379 7DC9 # E37A 7F73 # E37B 7FE2 # E37C 7FE3 # E37D 7FE5 # E37E 7FDE # E3A1 8024 # E3A2 805D # E3A3 805C # E3A4 8189 # E3A5 8186 # E3A6 8183 # E3A7 8187 # E3A8 818D # E3A9 818C # E3AA 818B # E3AB 8215 # E3AC 8497 # E3AD 84A4 # E3AE 84A1 # E3AF 849F # E3B0 84BA # E3B1 84CE # E3B2 84C2 # E3B3 84AC # E3B4 84AE # E3B5 84AB # E3B6 84B9 # E3B7 84B4 # E3B8 84C1 # E3B9 84CD # E3BA 84AA # E3BB 849A # E3BC 84B1 # E3BD 84D0 # E3BE 849D # E3BF 84A7 # E3C0 84BB # E3C1 84A2 # E3C2 8494 # E3C3 84C7 # E3C4 84CC # E3C5 849B # E3C6 84A9 # E3C7 84AF # E3C8 84A8 # E3C9 84D6 # E3CA 8498 # E3CB 84B6 # E3CC 84CF # E3CD 84A0 # E3CE 84D7 # E3CF 84D4 # E3D0 84D2 # E3D1 84DB # E3D2 84B0 # E3D3 8491 # E3D4 8661 # E3D5 8733 # E3D6 8723 # E3D7 8728 # E3D8 876B # E3D9 8740 # E3DA 872E # E3DB 871E # E3DC 8721 # E3DD 8719 # E3DE 871B # E3DF 8743 # E3E0 872C # E3E1 8741 # E3E2 873E # E3E3 8746 # E3E4 8720 # E3E5 8732 # E3E6 872A # E3E7 872D # E3E8 873C # E3E9 8712 # E3EA 873A # E3EB 8731 # E3EC 8735 # E3ED 8742 # E3EE 8726 # E3EF 8727 # E3F0 8738 # E3F1 8724 # E3F2 871A # E3F3 8730 # E3F4 8711 # E3F5 88F7 # E3F6 88E7 # E3F7 88F1 # E3F8 88F2 # E3F9 88FA # E3FA 88FE # E3FB 88EE # E3FC 88FC # E3FD 88F6 # E3FE 88FB # E440 88F0 # E441 88EC # E442 88EB # E443 899D # E444 89A1 # E445 899F # E446 899E # E447 89E9 # E448 89EB # E449 89E8 # E44A 8AAB # E44B 8A99 # E44C 8A8B # E44D 8A92 # E44E 8A8F # E44F 8A96 # E450 8C3D # E451 8C68 # E452 8C69 # E453 8CD5 # E454 8CCF # E455 8CD7 # E456 8D96 # E457 8E09 # E458 8E02 # E459 8DFF # E45A 8E0D # E45B 8DFD # E45C 8E0A # E45D 8E03 # E45E 8E07 # E45F 8E06 # E460 8E05 # E461 8DFE # E462 8E00 # E463 8E04 # E464 8F10 # E465 8F11 # E466 8F0E # E467 8F0D # E468 9123 # E469 911C # E46A 9120 # E46B 9122 # E46C 911F # E46D 911D # E46E 911A # E46F 9124 # E470 9121 # E471 911B # E472 917A # E473 9172 # E474 9179 # E475 9173 # E476 92A5 # E477 92A4 # E478 9276 # E479 929B # E47A 927A # E47B 92A0 # E47C 9294 # E47D 92AA # E47E 928D # E4A1 92A6 # E4A2 929A # E4A3 92AB # E4A4 9279 # E4A5 9297 # E4A6 927F # E4A7 92A3 # E4A8 92EE # E4A9 928E # E4AA 9282 # E4AB 9295 # E4AC 92A2 # E4AD 927D # E4AE 9288 # E4AF 92A1 # E4B0 928A # E4B1 9286 # E4B2 928C # E4B3 9299 # E4B4 92A7 # E4B5 927E # E4B6 9287 # E4B7 92A9 # E4B8 929D # E4B9 928B # E4BA 922D # E4BB 969E # E4BC 96A1 # E4BD 96FF # E4BE 9758 # E4BF 977D # E4C0 977A # E4C1 977E # E4C2 9783 # E4C3 9780 # E4C4 9782 # E4C5 977B # E4C6 9784 # E4C7 9781 # E4C8 977F # E4C9 97CE # E4CA 97CD # E4CB 9816 # E4CC 98AD # E4CD 98AE # E4CE 9902 # E4CF 9900 # E4D0 9907 # E4D1 999D # E4D2 999C # E4D3 99C3 # E4D4 99B9 # E4D5 99BB # E4D6 99BA # E4D7 99C2 # E4D8 99BD # E4D9 99C7 # E4DA 9AB1 # E4DB 9AE3 # E4DC 9AE7 # E4DD 9B3E # E4DE 9B3F # E4DF 9B60 # E4E0 9B61 # E4E1 9B5F # E4E2 9CF1 # E4E3 9CF2 # E4E4 9CF5 # E4E5 9EA7 # E4E6 50FF # E4E7 5103 # E4E8 5130 # E4E9 50F8 # E4EA 5106 # E4EB 5107 # E4EC 50F6 # E4ED 50FE # E4EE 510B # E4EF 510C # E4F0 50FD # E4F1 510A # E4F2 528B # E4F3 528C # E4F4 52F1 # E4F5 52EF # E4F6 5648 # E4F7 5642 # E4F8 564C # E4F9 5635 # E4FA 5641 # E4FB 564A # E4FC 5649 # E4FD 5646 # E4FE 5658 # E540 565A # E541 5640 # E542 5633 # E543 563D # E544 562C # E545 563E # E546 5638 # E547 562A # E548 563A # E549 571A # E54A 58AB # E54B 589D # E54C 58B1 # E54D 58A0 # E54E 58A3 # E54F 58AF # E550 58AC # E551 58A5 # E552 58A1 # E553 58FF # E554 5AFF # E555 5AF4 # E556 5AFD # E557 5AF7 # E558 5AF6 # E559 5B03 # E55A 5AF8 # E55B 5B02 # E55C 5AF9 # E55D 5B01 # E55E 5B07 # E55F 5B05 # E560 5B0F # E561 5C67 # E562 5D99 # E563 5D97 # E564 5D9F # E565 5D92 # E566 5DA2 # E567 5D93 # E568 5D95 # E569 5DA0 # E56A 5D9C # E56B 5DA1 # E56C 5D9A # E56D 5D9E # E56E 5E69 # E56F 5E5D # E570 5E60 # E571 5E5C # E572 7DF3 # E573 5EDB # E574 5EDE # E575 5EE1 # E576 5F49 # E577 5FB2 # E578 618B # E579 6183 # E57A 6179 # E57B 61B1 # E57C 61B0 # E57D 61A2 # E57E 6189 # E5A1 619B # E5A2 6193 # E5A3 61AF # E5A4 61AD # E5A5 619F # E5A6 6192 # E5A7 61AA # E5A8 61A1 # E5A9 618D # E5AA 6166 # E5AB 61B3 # E5AC 622D # E5AD 646E # E5AE 6470 # E5AF 6496 # E5B0 64A0 # E5B1 6485 # E5B2 6497 # E5B3 649C # E5B4 648F # E5B5 648B # E5B6 648A # E5B7 648C # E5B8 64A3 # E5B9 649F # E5BA 6468 # E5BB 64B1 # E5BC 6498 # E5BD 6576 # E5BE 657A # E5BF 6579 # E5C0 657B # E5C1 65B2 # E5C2 65B3 # E5C3 66B5 # E5C4 66B0 # E5C5 66A9 # E5C6 66B2 # E5C7 66B7 # E5C8 66AA # E5C9 66AF # E5CA 6A00 # E5CB 6A06 # E5CC 6A17 # E5CD 69E5 # E5CE 69F8 # E5CF 6A15 # E5D0 69F1 # E5D1 69E4 # E5D2 6A20 # E5D3 69FF # E5D4 69EC # E5D5 69E2 # E5D6 6A1B # E5D7 6A1D # E5D8 69FE # E5D9 6A27 # E5DA 69F2 # E5DB 69EE # E5DC 6A14 # E5DD 69F7 # E5DE 69E7 # E5DF 6A40 # E5E0 6A08 # E5E1 69E6 # E5E2 69FB # E5E3 6A0D # E5E4 69FC # E5E5 69EB # E5E6 6A09 # E5E7 6A04 # E5E8 6A18 # E5E9 6A25 # E5EA 6A0F # E5EB 69F6 # E5EC 6A26 # E5ED 6A07 # E5EE 69F4 # E5EF 6A16 # E5F0 6B51 # E5F1 6BA5 # E5F2 6BA3 # E5F3 6BA2 # E5F4 6BA6 # E5F5 6C01 # E5F6 6C00 # E5F7 6BFF # E5F8 6C02 # E5F9 6F41 # E5FA 6F26 # E5FB 6F7E # E5FC 6F87 # E5FD 6FC6 # E5FE 6F92 # E640 6F8D # E641 6F89 # E642 6F8C # E643 6F62 # E644 6F4F # E645 6F85 # E646 6F5A # E647 6F96 # E648 6F76 # E649 6F6C # E64A 6F82 # E64B 6F55 # E64C 6F72 # E64D 6F52 # E64E 6F50 # E64F 6F57 # E650 6F94 # E651 6F93 # E652 6F5D # E653 6F00 # E654 6F61 # E655 6F6B # E656 6F7D # E657 6F67 # E658 6F90 # E659 6F53 # E65A 6F8B # E65B 6F69 # E65C 6F7F # E65D 6F95 # E65E 6F63 # E65F 6F77 # E660 6F6A # E661 6F7B # E662 71B2 # E663 71AF # E664 719B # E665 71B0 # E666 71A0 # E667 719A # E668 71A9 # E669 71B5 # E66A 719D # E66B 71A5 # E66C 719E # E66D 71A4 # E66E 71A1 # E66F 71AA # E670 719C # E671 71A7 # E672 71B3 # E673 7298 # E674 729A # E675 7358 # E676 7352 # E677 735E # E678 735F # E679 7360 # E67A 735D # E67B 735B # E67C 7361 # E67D 735A # E67E 7359 # E6A1 7362 # E6A2 7487 # E6A3 7489 # E6A4 748A # E6A5 7486 # E6A6 7481 # E6A7 747D # E6A8 7485 # E6A9 7488 # E6AA 747C # E6AB 7479 # E6AC 7508 # E6AD 7507 # E6AE 757E # E6AF 7625 # E6B0 761E # E6B1 7619 # E6B2 761D # E6B3 761C # E6B4 7623 # E6B5 761A # E6B6 7628 # E6B7 761B # E6B8 769C # E6B9 769D # E6BA 769E # E6BB 769B # E6BC 778D # E6BD 778F # E6BE 7789 # E6BF 7788 # E6C0 78CD # E6C1 78BB # E6C2 78CF # E6C3 78CC # E6C4 78D1 # E6C5 78CE # E6C6 78D4 # E6C7 78C8 # E6C8 78C3 # E6C9 78C4 # E6CA 78C9 # E6CB 799A # E6CC 79A1 # E6CD 79A0 # E6CE 799C # E6CF 79A2 # E6D0 799B # E6D1 6B76 # E6D2 7A39 # E6D3 7AB2 # E6D4 7AB4 # E6D5 7AB3 # E6D6 7BB7 # E6D7 7BCB # E6D8 7BBE # E6D9 7BAC # E6DA 7BCE # E6DB 7BAF # E6DC 7BB9 # E6DD 7BCA # E6DE 7BB5 # E6DF 7CC5 # E6E0 7CC8 # E6E1 7CCC # E6E2 7CCB # E6E3 7DF7 # E6E4 7DDB # E6E5 7DEA # E6E6 7DE7 # E6E7 7DD7 # E6E8 7DE1 # E6E9 7E03 # E6EA 7DFA # E6EB 7DE6 # E6EC 7DF6 # E6ED 7DF1 # E6EE 7DF0 # E6EF 7DEE # E6F0 7DDF # E6F1 7F76 # E6F2 7FAC # E6F3 7FB0 # E6F4 7FAD # E6F5 7FED # E6F6 7FEB # E6F7 7FEA # E6F8 7FEC # E6F9 7FE6 # E6FA 7FE8 # E6FB 8064 # E6FC 8067 # E6FD 81A3 # E6FE 819F # E740 819E # E741 8195 # E742 81A2 # E743 8199 # E744 8197 # E745 8216 # E746 824F # E747 8253 # E748 8252 # E749 8250 # E74A 824E # E74B 8251 # E74C 8524 # E74D 853B # E74E 850F # E74F 8500 # E750 8529 # E751 850E # E752 8509 # E753 850D # E754 851F # E755 850A # E756 8527 # E757 851C # E758 84FB # E759 852B # E75A 84FA # E75B 8508 # E75C 850C # E75D 84F4 # E75E 852A # E75F 84F2 # E760 8515 # E761 84F7 # E762 84EB # E763 84F3 # E764 84FC # E765 8512 # E766 84EA # E767 84E9 # E768 8516 # E769 84FE # E76A 8528 # E76B 851D # E76C 852E # E76D 8502 # E76E 84FD # E76F 851E # E770 84F6 # E771 8531 # E772 8526 # E773 84E7 # E774 84E8 # E775 84F0 # E776 84EF # E777 84F9 # E778 8518 # E779 8520 # E77A 8530 # E77B 850B # E77C 8519 # E77D 852F # E77E 8662 # E7A1 8756 # E7A2 8763 # E7A3 8764 # E7A4 8777 # E7A5 87E1 # E7A6 8773 # E7A7 8758 # E7A8 8754 # E7A9 875B # E7AA 8752 # E7AB 8761 # E7AC 875A # E7AD 8751 # E7AE 875E # E7AF 876D # E7B0 876A # E7B1 8750 # E7B2 874E # E7B3 875F # E7B4 875D # E7B5 876F # E7B6 876C # E7B7 877A # E7B8 876E # E7B9 875C # E7BA 8765 # E7BB 874F # E7BC 877B # E7BD 8775 # E7BE 8762 # E7BF 8767 # E7C0 8769 # E7C1 885A # E7C2 8905 # E7C3 890C # E7C4 8914 # E7C5 890B # E7C6 8917 # E7C7 8918 # E7C8 8919 # E7C9 8906 # E7CA 8916 # E7CB 8911 # E7CC 890E # E7CD 8909 # E7CE 89A2 # E7CF 89A4 # E7D0 89A3 # E7D1 89ED # E7D2 89F0 # E7D3 89EC # E7D4 8ACF # E7D5 8AC6 # E7D6 8AB8 # E7D7 8AD3 # E7D8 8AD1 # E7D9 8AD4 # E7DA 8AD5 # E7DB 8ABB # E7DC 8AD7 # E7DD 8ABE # E7DE 8AC0 # E7DF 8AC5 # E7E0 8AD8 # E7E1 8AC3 # E7E2 8ABA # E7E3 8ABD # E7E4 8AD9 # E7E5 8C3E # E7E6 8C4D # E7E7 8C8F # E7E8 8CE5 # E7E9 8CDF # E7EA 8CD9 # E7EB 8CE8 # E7EC 8CDA # E7ED 8CDD # E7EE 8CE7 # E7EF 8DA0 # E7F0 8D9C # E7F1 8DA1 # E7F2 8D9B # E7F3 8E20 # E7F4 8E23 # E7F5 8E25 # E7F6 8E24 # E7F7 8E2E # E7F8 8E15 # E7F9 8E1B # E7FA 8E16 # E7FB 8E11 # E7FC 8E19 # E7FD 8E26 # E7FE 8E27 # E840 8E14 # E841 8E12 # E842 8E18 # E843 8E13 # E844 8E1C # E845 8E17 # E846 8E1A # E847 8F2C # E848 8F24 # E849 8F18 # E84A 8F1A # E84B 8F20 # E84C 8F23 # E84D 8F16 # E84E 8F17 # E84F 9073 # E850 9070 # E851 906F # E852 9067 # E853 906B # E854 912F # E855 912B # E856 9129 # E857 912A # E858 9132 # E859 9126 # E85A 912E # E85B 9185 # E85C 9186 # E85D 918A # E85E 9181 # E85F 9182 # E860 9184 # E861 9180 # E862 92D0 # E863 92C3 # E864 92C4 # E865 92C0 # E866 92D9 # E867 92B6 # E868 92CF # E869 92F1 # E86A 92DF # E86B 92D8 # E86C 92E9 # E86D 92D7 # E86E 92DD # E86F 92CC # E870 92EF # E871 92C2 # E872 92E8 # E873 92CA # E874 92C8 # E875 92CE # E876 92E6 # E877 92CD # E878 92D5 # E879 92C9 # E87A 92E0 # E87B 92DE # E87C 92E7 # E87D 92D1 # E87E 92D3 # E8A1 92B5 # E8A2 92E1 # E8A3 92C6 # E8A4 92B4 # E8A5 957C # E8A6 95AC # E8A7 95AB # E8A8 95AE # E8A9 95B0 # E8AA 96A4 # E8AB 96A2 # E8AC 96D3 # E8AD 9705 # E8AE 9708 # E8AF 9702 # E8B0 975A # E8B1 978A # E8B2 978E # E8B3 9788 # E8B4 97D0 # E8B5 97CF # E8B6 981E # E8B7 981D # E8B8 9826 # E8B9 9829 # E8BA 9828 # E8BB 9820 # E8BC 981B # E8BD 9827 # E8BE 98B2 # E8BF 9908 # E8C0 98FA # E8C1 9911 # E8C2 9914 # E8C3 9916 # E8C4 9917 # E8C5 9915 # E8C6 99DC # E8C7 99CD # E8C8 99CF # E8C9 99D3 # E8CA 99D4 # E8CB 99CE # E8CC 99C9 # E8CD 99D6 # E8CE 99D8 # E8CF 99CB # E8D0 99D7 # E8D1 99CC # E8D2 9AB3 # E8D3 9AEC # E8D4 9AEB # E8D5 9AF3 # E8D6 9AF2 # E8D7 9AF1 # E8D8 9B46 # E8D9 9B43 # E8DA 9B67 # E8DB 9B74 # E8DC 9B71 # E8DD 9B66 # E8DE 9B76 # E8DF 9B75 # E8E0 9B70 # E8E1 9B68 # E8E2 9B64 # E8E3 9B6C # E8E4 9CFC # E8E5 9CFA # E8E6 9CFD # E8E7 9CFF # E8E8 9CF7 # E8E9 9D07 # E8EA 9D00 # E8EB 9CF9 # E8EC 9CFB # E8ED 9D08 # E8EE 9D05 # E8EF 9D04 # E8F0 9E83 # E8F1 9ED3 # E8F2 9F0F # E8F3 9F10 # E8F4 511C # E8F5 5113 # E8F6 5117 # E8F7 511A # E8F8 5111 # E8F9 51DE # E8FA 5334 # E8FB 53E1 # E8FC 5670 # E8FD 5660 # E8FE 566E # E940 5673 # E941 5666 # E942 5663 # E943 566D # E944 5672 # E945 565E # E946 5677 # E947 571C # E948 571B # E949 58C8 # E94A 58BD # E94B 58C9 # E94C 58BF # E94D 58BA # E94E 58C2 # E94F 58BC # E950 58C6 # E951 5B17 # E952 5B19 # E953 5B1B # E954 5B21 # E955 5B14 # E956 5B13 # E957 5B10 # E958 5B16 # E959 5B28 # E95A 5B1A # E95B 5B20 # E95C 5B1E # E95D 5BEF # E95E 5DAC # E95F 5DB1 # E960 5DA9 # E961 5DA7 # E962 5DB5 # E963 5DB0 # E964 5DAE # E965 5DAA # E966 5DA8 # E967 5DB2 # E968 5DAD # E969 5DAF # E96A 5DB4 # E96B 5E67 # E96C 5E68 # E96D 5E66 # E96E 5E6F # E96F 5EE9 # E970 5EE7 # E971 5EE6 # E972 5EE8 # E973 5EE5 # E974 5F4B # E975 5FBC # E976 619D # E977 61A8 # E978 6196 # E979 61C5 # E97A 61B4 # E97B 61C6 # E97C 61C1 # E97D 61CC # E97E 61BA # E9A1 61BF # E9A2 61B8 # E9A3 618C # E9A4 64D7 # E9A5 64D6 # E9A6 64D0 # E9A7 64CF # E9A8 64C9 # E9A9 64BD # E9AA 6489 # E9AB 64C3 # E9AC 64DB # E9AD 64F3 # E9AE 64D9 # E9AF 6533 # E9B0 657F # E9B1 657C # E9B2 65A2 # E9B3 66C8 # E9B4 66BE # E9B5 66C0 # E9B6 66CA # E9B7 66CB # E9B8 66CF # E9B9 66BD # E9BA 66BB # E9BB 66BA # E9BC 66CC # E9BD 6723 # E9BE 6A34 # E9BF 6A66 # E9C0 6A49 # E9C1 6A67 # E9C2 6A32 # E9C3 6A68 # E9C4 6A3E # E9C5 6A5D # E9C6 6A6D # E9C7 6A76 # E9C8 6A5B # E9C9 6A51 # E9CA 6A28 # E9CB 6A5A # E9CC 6A3B # E9CD 6A3F # E9CE 6A41 # E9CF 6A6A # E9D0 6A64 # E9D1 6A50 # E9D2 6A4F # E9D3 6A54 # E9D4 6A6F # E9D5 6A69 # E9D6 6A60 # E9D7 6A3C # E9D8 6A5E # E9D9 6A56 # E9DA 6A55 # E9DB 6A4D # E9DC 6A4E # E9DD 6A46 # E9DE 6B55 # E9DF 6B54 # E9E0 6B56 # E9E1 6BA7 # E9E2 6BAA # E9E3 6BAB # E9E4 6BC8 # E9E5 6BC7 # E9E6 6C04 # E9E7 6C03 # E9E8 6C06 # E9E9 6FAD # E9EA 6FCB # E9EB 6FA3 # E9EC 6FC7 # E9ED 6FBC # E9EE 6FCE # E9EF 6FC8 # E9F0 6F5E # E9F1 6FC4 # E9F2 6FBD # E9F3 6F9E # E9F4 6FCA # E9F5 6FA8 # E9F6 7004 # E9F7 6FA5 # E9F8 6FAE # E9F9 6FBA # E9FA 6FAC # E9FB 6FAA # E9FC 6FCF # E9FD 6FBF # E9FE 6FB8 # EA40 6FA2 # EA41 6FC9 # EA42 6FAB # EA43 6FCD # EA44 6FAF # EA45 6FB2 # EA46 6FB0 # EA47 71C5 # EA48 71C2 # EA49 71BF # EA4A 71B8 # EA4B 71D6 # EA4C 71C0 # EA4D 71C1 # EA4E 71CB # EA4F 71D4 # EA50 71CA # EA51 71C7 # EA52 71CF # EA53 71BD # EA54 71D8 # EA55 71BC # EA56 71C6 # EA57 71DA # EA58 71DB # EA59 729D # EA5A 729E # EA5B 7369 # EA5C 7366 # EA5D 7367 # EA5E 736C # EA5F 7365 # EA60 736B # EA61 736A # EA62 747F # EA63 749A # EA64 74A0 # EA65 7494 # EA66 7492 # EA67 7495 # EA68 74A1 # EA69 750B # EA6A 7580 # EA6B 762F # EA6C 762D # EA6D 7631 # EA6E 763D # EA6F 7633 # EA70 763C # EA71 7635 # EA72 7632 # EA73 7630 # EA74 76BB # EA75 76E6 # EA76 779A # EA77 779D # EA78 77A1 # EA79 779C # EA7A 779B # EA7B 77A2 # EA7C 77A3 # EA7D 7795 # EA7E 7799 # EAA1 7797 # EAA2 78DD # EAA3 78E9 # EAA4 78E5 # EAA5 78EA # EAA6 78DE # EAA7 78E3 # EAA8 78DB # EAA9 78E1 # EAAA 78E2 # EAAB 78ED # EAAC 78DF # EAAD 78E0 # EAAE 79A4 # EAAF 7A44 # EAB0 7A48 # EAB1 7A47 # EAB2 7AB6 # EAB3 7AB8 # EAB4 7AB5 # EAB5 7AB1 # EAB6 7AB7 # EAB7 7BDE # EAB8 7BE3 # EAB9 7BE7 # EABA 7BDD # EABB 7BD5 # EABC 7BE5 # EABD 7BDA # EABE 7BE8 # EABF 7BF9 # EAC0 7BD4 # EAC1 7BEA # EAC2 7BE2 # EAC3 7BDC # EAC4 7BEB # EAC5 7BD8 # EAC6 7BDF # EAC7 7CD2 # EAC8 7CD4 # EAC9 7CD7 # EACA 7CD0 # EACB 7CD1 # EACC 7E12 # EACD 7E21 # EACE 7E17 # EACF 7E0C # EAD0 7E1F # EAD1 7E20 # EAD2 7E13 # EAD3 7E0E # EAD4 7E1C # EAD5 7E15 # EAD6 7E1A # EAD7 7E22 # EAD8 7E0B # EAD9 7E0F # EADA 7E16 # EADB 7E0D # EADC 7E14 # EADD 7E25 # EADE 7E24 # EADF 7F43 # EAE0 7F7B # EAE1 7F7C # EAE2 7F7A # EAE3 7FB1 # EAE4 7FEF # EAE5 802A # EAE6 8029 # EAE7 806C # EAE8 81B1 # EAE9 81A6 # EAEA 81AE # EAEB 81B9 # EAEC 81B5 # EAED 81AB # EAEE 81B0 # EAEF 81AC # EAF0 81B4 # EAF1 81B2 # EAF2 81B7 # EAF3 81A7 # EAF4 81F2 # EAF5 8255 # EAF6 8256 # EAF7 8257 # EAF8 8556 # EAF9 8545 # EAFA 856B # EAFB 854D # EAFC 8553 # EAFD 8561 # EAFE 8558 # EB40 8540 # EB41 8546 # EB42 8564 # EB43 8541 # EB44 8562 # EB45 8544 # EB46 8551 # EB47 8547 # EB48 8563 # EB49 853E # EB4A 855B # EB4B 8571 # EB4C 854E # EB4D 856E # EB4E 8575 # EB4F 8555 # EB50 8567 # EB51 8560 # EB52 858C # EB53 8566 # EB54 855D # EB55 8554 # EB56 8565 # EB57 856C # EB58 8663 # EB59 8665 # EB5A 8664 # EB5B 879B # EB5C 878F # EB5D 8797 # EB5E 8793 # EB5F 8792 # EB60 8788 # EB61 8781 # EB62 8796 # EB63 8798 # EB64 8779 # EB65 8787 # EB66 87A3 # EB67 8785 # EB68 8790 # EB69 8791 # EB6A 879D # EB6B 8784 # EB6C 8794 # EB6D 879C # EB6E 879A # EB6F 8789 # EB70 891E # EB71 8926 # EB72 8930 # EB73 892D # EB74 892E # EB75 8927 # EB76 8931 # EB77 8922 # EB78 8929 # EB79 8923 # EB7A 892F # EB7B 892C # EB7C 891F # EB7D 89F1 # EB7E 8AE0 # EBA1 8AE2 # EBA2 8AF2 # EBA3 8AF4 # EBA4 8AF5 # EBA5 8ADD # EBA6 8B14 # EBA7 8AE4 # EBA8 8ADF # EBA9 8AF0 # EBAA 8AC8 # EBAB 8ADE # EBAC 8AE1 # EBAD 8AE8 # EBAE 8AFF # EBAF 8AEF # EBB0 8AFB # EBB1 8C91 # EBB2 8C92 # EBB3 8C90 # EBB4 8CF5 # EBB5 8CEE # EBB6 8CF1 # EBB7 8CF0 # EBB8 8CF3 # EBB9 8D6C # EBBA 8D6E # EBBB 8DA5 # EBBC 8DA7 # EBBD 8E33 # EBBE 8E3E # EBBF 8E38 # EBC0 8E40 # EBC1 8E45 # EBC2 8E36 # EBC3 8E3C # EBC4 8E3D # EBC5 8E41 # EBC6 8E30 # EBC7 8E3F # EBC8 8EBD # EBC9 8F36 # EBCA 8F2E # EBCB 8F35 # EBCC 8F32 # EBCD 8F39 # EBCE 8F37 # EBCF 8F34 # EBD0 9076 # EBD1 9079 # EBD2 907B # EBD3 9086 # EBD4 90FA # EBD5 9133 # EBD6 9135 # EBD7 9136 # EBD8 9193 # EBD9 9190 # EBDA 9191 # EBDB 918D # EBDC 918F # EBDD 9327 # EBDE 931E # EBDF 9308 # EBE0 931F # EBE1 9306 # EBE2 930F # EBE3 937A # EBE4 9338 # EBE5 933C # EBE6 931B # EBE7 9323 # EBE8 9312 # EBE9 9301 # EBEA 9346 # EBEB 932D # EBEC 930E # EBED 930D # EBEE 92CB # EBEF 931D # EBF0 92FA # EBF1 9325 # EBF2 9313 # EBF3 92F9 # EBF4 92F7 # EBF5 9334 # EBF6 9302 # EBF7 9324 # EBF8 92FF # EBF9 9329 # EBFA 9339 # EBFB 9335 # EBFC 932A # EBFD 9314 # EBFE 930C # EC40 930B # EC41 92FE # EC42 9309 # EC43 9300 # EC44 92FB # EC45 9316 # EC46 95BC # EC47 95CD # EC48 95BE # EC49 95B9 # EC4A 95BA # EC4B 95B6 # EC4C 95BF # EC4D 95B5 # EC4E 95BD # EC4F 96A9 # EC50 96D4 # EC51 970B # EC52 9712 # EC53 9710 # EC54 9799 # EC55 9797 # EC56 9794 # EC57 97F0 # EC58 97F8 # EC59 9835 # EC5A 982F # EC5B 9832 # EC5C 9924 # EC5D 991F # EC5E 9927 # EC5F 9929 # EC60 999E # EC61 99EE # EC62 99EC # EC63 99E5 # EC64 99E4 # EC65 99F0 # EC66 99E3 # EC67 99EA # EC68 99E9 # EC69 99E7 # EC6A 9AB9 # EC6B 9ABF # EC6C 9AB4 # EC6D 9ABB # EC6E 9AF6 # EC6F 9AFA # EC70 9AF9 # EC71 9AF7 # EC72 9B33 # EC73 9B80 # EC74 9B85 # EC75 9B87 # EC76 9B7C # EC77 9B7E # EC78 9B7B # EC79 9B82 # EC7A 9B93 # EC7B 9B92 # EC7C 9B90 # EC7D 9B7A # EC7E 9B95 # ECA1 9B7D # ECA2 9B88 # ECA3 9D25 # ECA4 9D17 # ECA5 9D20 # ECA6 9D1E # ECA7 9D14 # ECA8 9D29 # ECA9 9D1D # ECAA 9D18 # ECAB 9D22 # ECAC 9D10 # ECAD 9D19 # ECAE 9D1F # ECAF 9E88 # ECB0 9E86 # ECB1 9E87 # ECB2 9EAE # ECB3 9EAD # ECB4 9ED5 # ECB5 9ED6 # ECB6 9EFA # ECB7 9F12 # ECB8 9F3D # ECB9 5126 # ECBA 5125 # ECBB 5122 # ECBC 5124 # ECBD 5120 # ECBE 5129 # ECBF 52F4 # ECC0 5693 # ECC1 568C # ECC2 568D # ECC3 5686 # ECC4 5684 # ECC5 5683 # ECC6 567E # ECC7 5682 # ECC8 567F # ECC9 5681 # ECCA 58D6 # ECCB 58D4 # ECCC 58CF # ECCD 58D2 # ECCE 5B2D # ECCF 5B25 # ECD0 5B32 # ECD1 5B23 # ECD2 5B2C # ECD3 5B27 # ECD4 5B26 # ECD5 5B2F # ECD6 5B2E # ECD7 5B7B # ECD8 5BF1 # ECD9 5BF2 # ECDA 5DB7 # ECDB 5E6C # ECDC 5E6A # ECDD 5FBE # ECDE 5FBB # ECDF 61C3 # ECE0 61B5 # ECE1 61BC # ECE2 61E7 # ECE3 61E0 # ECE4 61E5 # ECE5 61E4 # ECE6 61E8 # ECE7 61DE # ECE8 64EF # ECE9 64E9 # ECEA 64E3 # ECEB 64EB # ECEC 64E4 # ECED 64E8 # ECEE 6581 # ECEF 6580 # ECF0 65B6 # ECF1 65DA # ECF2 66D2 # ECF3 6A8D # ECF4 6A96 # ECF5 6A81 # ECF6 6AA5 # ECF7 6A89 # ECF8 6A9F # ECF9 6A9B # ECFA 6AA1 # ECFB 6A9E # ECFC 6A87 # ECFD 6A93 # ECFE 6A8E # ED40 6A95 # ED41 6A83 # ED42 6AA8 # ED43 6AA4 # ED44 6A91 # ED45 6A7F # ED46 6AA6 # ED47 6A9A # ED48 6A85 # ED49 6A8C # ED4A 6A92 # ED4B 6B5B # ED4C 6BAD # ED4D 6C09 # ED4E 6FCC # ED4F 6FA9 # ED50 6FF4 # ED51 6FD4 # ED52 6FE3 # ED53 6FDC # ED54 6FED # ED55 6FE7 # ED56 6FE6 # ED57 6FDE # ED58 6FF2 # ED59 6FDD # ED5A 6FE2 # ED5B 6FE8 # ED5C 71E1 # ED5D 71F1 # ED5E 71E8 # ED5F 71F2 # ED60 71E4 # ED61 71F0 # ED62 71E2 # ED63 7373 # ED64 736E # ED65 736F # ED66 7497 # ED67 74B2 # ED68 74AB # ED69 7490 # ED6A 74AA # ED6B 74AD # ED6C 74B1 # ED6D 74A5 # ED6E 74AF # ED6F 7510 # ED70 7511 # ED71 7512 # ED72 750F # ED73 7584 # ED74 7643 # ED75 7648 # ED76 7649 # ED77 7647 # ED78 76A4 # ED79 76E9 # ED7A 77B5 # ED7B 77AB # ED7C 77B2 # ED7D 77B7 # ED7E 77B6 # EDA1 77B4 # EDA2 77B1 # EDA3 77A8 # EDA4 77F0 # EDA5 78F3 # EDA6 78FD # EDA7 7902 # EDA8 78FB # EDA9 78FC # EDAA 78F2 # EDAB 7905 # EDAC 78F9 # EDAD 78FE # EDAE 7904 # EDAF 79AB # EDB0 79A8 # EDB1 7A5C # EDB2 7A5B # EDB3 7A56 # EDB4 7A58 # EDB5 7A54 # EDB6 7A5A # EDB7 7ABE # EDB8 7AC0 # EDB9 7AC1 # EDBA 7C05 # EDBB 7C0F # EDBC 7BF2 # EDBD 7C00 # EDBE 7BFF # EDBF 7BFB # EDC0 7C0E # EDC1 7BF4 # EDC2 7C0B # EDC3 7BF3 # EDC4 7C02 # EDC5 7C09 # EDC6 7C03 # EDC7 7C01 # EDC8 7BF8 # EDC9 7BFD # EDCA 7C06 # EDCB 7BF0 # EDCC 7BF1 # EDCD 7C10 # EDCE 7C0A # EDCF 7CE8 # EDD0 7E2D # EDD1 7E3C # EDD2 7E42 # EDD3 7E33 # EDD4 9848 # EDD5 7E38 # EDD6 7E2A # EDD7 7E49 # EDD8 7E40 # EDD9 7E47 # EDDA 7E29 # EDDB 7E4C # EDDC 7E30 # EDDD 7E3B # EDDE 7E36 # EDDF 7E44 # EDE0 7E3A # EDE1 7F45 # EDE2 7F7F # EDE3 7F7E # EDE4 7F7D # EDE5 7FF4 # EDE6 7FF2 # EDE7 802C # EDE8 81BB # EDE9 81C4 # EDEA 81CC # EDEB 81CA # EDEC 81C5 # EDED 81C7 # EDEE 81BC # EDEF 81E9 # EDF0 825B # EDF1 825A # EDF2 825C # EDF3 8583 # EDF4 8580 # EDF5 858F # EDF6 85A7 # EDF7 8595 # EDF8 85A0 # EDF9 858B # EDFA 85A3 # EDFB 857B # EDFC 85A4 # EDFD 859A # EDFE 859E # EE40 8577 # EE41 857C # EE42 8589 # EE43 85A1 # EE44 857A # EE45 8578 # EE46 8557 # EE47 858E # EE48 8596 # EE49 8586 # EE4A 858D # EE4B 8599 # EE4C 859D # EE4D 8581 # EE4E 85A2 # EE4F 8582 # EE50 8588 # EE51 8585 # EE52 8579 # EE53 8576 # EE54 8598 # EE55 8590 # EE56 859F # EE57 8668 # EE58 87BE # EE59 87AA # EE5A 87AD # EE5B 87C5 # EE5C 87B0 # EE5D 87AC # EE5E 87B9 # EE5F 87B5 # EE60 87BC # EE61 87AE # EE62 87C9 # EE63 87C3 # EE64 87C2 # EE65 87CC # EE66 87B7 # EE67 87AF # EE68 87C4 # EE69 87CA # EE6A 87B4 # EE6B 87B6 # EE6C 87BF # EE6D 87B8 # EE6E 87BD # EE6F 87DE # EE70 87B2 # EE71 8935 # EE72 8933 # EE73 893C # EE74 893E # EE75 8941 # EE76 8952 # EE77 8937 # EE78 8942 # EE79 89AD # EE7A 89AF # EE7B 89AE # EE7C 89F2 # EE7D 89F3 # EE7E 8B1E # EEA1 8B18 # EEA2 8B16 # EEA3 8B11 # EEA4 8B05 # EEA5 8B0B # EEA6 8B22 # EEA7 8B0F # EEA8 8B12 # EEA9 8B15 # EEAA 8B07 # EEAB 8B0D # EEAC 8B08 # EEAD 8B06 # EEAE 8B1C # EEAF 8B13 # EEB0 8B1A # EEB1 8C4F # EEB2 8C70 # EEB3 8C72 # EEB4 8C71 # EEB5 8C6F # EEB6 8C95 # EEB7 8C94 # EEB8 8CF9 # EEB9 8D6F # EEBA 8E4E # EEBB 8E4D # EEBC 8E53 # EEBD 8E50 # EEBE 8E4C # EEBF 8E47 # EEC0 8F43 # EEC1 8F40 # EEC2 9085 # EEC3 907E # EEC4 9138 # EEC5 919A # EEC6 91A2 # EEC7 919B # EEC8 9199 # EEC9 919F # EECA 91A1 # EECB 919D # EECC 91A0 # EECD 93A1 # EECE 9383 # EECF 93AF # EED0 9364 # EED1 9356 # EED2 9347 # EED3 937C # EED4 9358 # EED5 935C # EED6 9376 # EED7 9349 # EED8 9350 # EED9 9351 # EEDA 9360 # EEDB 936D # EEDC 938F # EEDD 934C # EEDE 936A # EEDF 9379 # EEE0 9357 # EEE1 9355 # EEE2 9352 # EEE3 934F # EEE4 9371 # EEE5 9377 # EEE6 937B # EEE7 9361 # EEE8 935E # EEE9 9363 # EEEA 9367 # EEEB 9380 # EEEC 934E # EEED 9359 # EEEE 95C7 # EEEF 95C0 # EEF0 95C9 # EEF1 95C3 # EEF2 95C5 # EEF3 95B7 # EEF4 96AE # EEF5 96B0 # EEF6 96AC # EEF7 9720 # EEF8 971F # EEF9 9718 # EEFA 971D # EEFB 9719 # EEFC 979A # EEFD 97A1 # EEFE 979C # EF40 979E # EF41 979D # EF42 97D5 # EF43 97D4 # EF44 97F1 # EF45 9841 # EF46 9844 # EF47 984A # EF48 9849 # EF49 9845 # EF4A 9843 # EF4B 9925 # EF4C 992B # EF4D 992C # EF4E 992A # EF4F 9933 # EF50 9932 # EF51 992F # EF52 992D # EF53 9931 # EF54 9930 # EF55 9998 # EF56 99A3 # EF57 99A1 # EF58 9A02 # EF59 99FA # EF5A 99F4 # EF5B 99F7 # EF5C 99F9 # EF5D 99F8 # EF5E 99F6 # EF5F 99FB # EF60 99FD # EF61 99FE # EF62 99FC # EF63 9A03 # EF64 9ABE # EF65 9AFE # EF66 9AFD # EF67 9B01 # EF68 9AFC # EF69 9B48 # EF6A 9B9A # EF6B 9BA8 # EF6C 9B9E # EF6D 9B9B # EF6E 9BA6 # EF6F 9BA1 # EF70 9BA5 # EF71 9BA4 # EF72 9B86 # EF73 9BA2 # EF74 9BA0 # EF75 9BAF # EF76 9D33 # EF77 9D41 # EF78 9D67 # EF79 9D36 # EF7A 9D2E # EF7B 9D2F # EF7C 9D31 # EF7D 9D38 # EF7E 9D30 # EFA1 9D45 # EFA2 9D42 # EFA3 9D43 # EFA4 9D3E # EFA5 9D37 # EFA6 9D40 # EFA7 9D3D # EFA8 7FF5 # EFA9 9D2D # EFAA 9E8A # EFAB 9E89 # EFAC 9E8D # EFAD 9EB0 # EFAE 9EC8 # EFAF 9EDA # EFB0 9EFB # EFB1 9EFF # EFB2 9F24 # EFB3 9F23 # EFB4 9F22 # EFB5 9F54 # EFB6 9FA0 # EFB7 5131 # EFB8 512D # EFB9 512E # EFBA 5698 # EFBB 569C # EFBC 5697 # EFBD 569A # EFBE 569D # EFBF 5699 # EFC0 5970 # EFC1 5B3C # EFC2 5C69 # EFC3 5C6A # EFC4 5DC0 # EFC5 5E6D # EFC6 5E6E # EFC7 61D8 # EFC8 61DF # EFC9 61ED # EFCA 61EE # EFCB 61F1 # EFCC 61EA # EFCD 61F0 # EFCE 61EB # EFCF 61D6 # EFD0 61E9 # EFD1 64FF # EFD2 6504 # EFD3 64FD # EFD4 64F8 # EFD5 6501 # EFD6 6503 # EFD7 64FC # EFD8 6594 # EFD9 65DB # EFDA 66DA # EFDB 66DB # EFDC 66D8 # EFDD 6AC5 # EFDE 6AB9 # EFDF 6ABD # EFE0 6AE1 # EFE1 6AC6 # EFE2 6ABA # EFE3 6AB6 # EFE4 6AB7 # EFE5 6AC7 # EFE6 6AB4 # EFE7 6AAD # EFE8 6B5E # EFE9 6BC9 # EFEA 6C0B # EFEB 7007 # EFEC 700C # EFED 700D # EFEE 7001 # EFEF 7005 # EFF0 7014 # EFF1 700E # EFF2 6FFF # EFF3 7000 # EFF4 6FFB # EFF5 7026 # EFF6 6FFC # EFF7 6FF7 # EFF8 700A # EFF9 7201 # EFFA 71FF # EFFB 71F9 # EFFC 7203 # EFFD 71FD # EFFE 7376 # F040 74B8 # F041 74C0 # F042 74B5 # F043 74C1 # F044 74BE # F045 74B6 # F046 74BB # F047 74C2 # F048 7514 # F049 7513 # F04A 765C # F04B 7664 # F04C 7659 # F04D 7650 # F04E 7653 # F04F 7657 # F050 765A # F051 76A6 # F052 76BD # F053 76EC # F054 77C2 # F055 77BA # F056 78FF # F057 790C # F058 7913 # F059 7914 # F05A 7909 # F05B 7910 # F05C 7912 # F05D 7911 # F05E 79AD # F05F 79AC # F060 7A5F # F061 7C1C # F062 7C29 # F063 7C19 # F064 7C20 # F065 7C1F # F066 7C2D # F067 7C1D # F068 7C26 # F069 7C28 # F06A 7C22 # F06B 7C25 # F06C 7C30 # F06D 7E5C # F06E 7E50 # F06F 7E56 # F070 7E63 # F071 7E58 # F072 7E62 # F073 7E5F # F074 7E51 # F075 7E60 # F076 7E57 # F077 7E53 # F078 7FB5 # F079 7FB3 # F07A 7FF7 # F07B 7FF8 # F07C 8075 # F07D 81D1 # F07E 81D2 # F0A1 81D0 # F0A2 825F # F0A3 825E # F0A4 85B4 # F0A5 85C6 # F0A6 85C0 # F0A7 85C3 # F0A8 85C2 # F0A9 85B3 # F0AA 85B5 # F0AB 85BD # F0AC 85C7 # F0AD 85C4 # F0AE 85BF # F0AF 85CB # F0B0 85CE # F0B1 85C8 # F0B2 85C5 # F0B3 85B1 # F0B4 85B6 # F0B5 85D2 # F0B6 8624 # F0B7 85B8 # F0B8 85B7 # F0B9 85BE # F0BA 8669 # F0BB 87E7 # F0BC 87E6 # F0BD 87E2 # F0BE 87DB # F0BF 87EB # F0C0 87EA # F0C1 87E5 # F0C2 87DF # F0C3 87F3 # F0C4 87E4 # F0C5 87D4 # F0C6 87DC # F0C7 87D3 # F0C8 87ED # F0C9 87D8 # F0CA 87E3 # F0CB 87A4 # F0CC 87D7 # F0CD 87D9 # F0CE 8801 # F0CF 87F4 # F0D0 87E8 # F0D1 87DD # F0D2 8953 # F0D3 894B # F0D4 894F # F0D5 894C # F0D6 8946 # F0D7 8950 # F0D8 8951 # F0D9 8949 # F0DA 8B2A # F0DB 8B27 # F0DC 8B23 # F0DD 8B33 # F0DE 8B30 # F0DF 8B35 # F0E0 8B47 # F0E1 8B2F # F0E2 8B3C # F0E3 8B3E # F0E4 8B31 # F0E5 8B25 # F0E6 8B37 # F0E7 8B26 # F0E8 8B36 # F0E9 8B2E # F0EA 8B24 # F0EB 8B3B # F0EC 8B3D # F0ED 8B3A # F0EE 8C42 # F0EF 8C75 # F0F0 8C99 # F0F1 8C98 # F0F2 8C97 # F0F3 8CFE # F0F4 8D04 # F0F5 8D02 # F0F6 8D00 # F0F7 8E5C # F0F8 8E62 # F0F9 8E60 # F0FA 8E57 # F0FB 8E56 # F0FC 8E5E # F0FD 8E65 # F0FE 8E67 # F140 8E5B # F141 8E5A # F142 8E61 # F143 8E5D # F144 8E69 # F145 8E54 # F146 8F46 # F147 8F47 # F148 8F48 # F149 8F4B # F14A 9128 # F14B 913A # F14C 913B # F14D 913E # F14E 91A8 # F14F 91A5 # F150 91A7 # F151 91AF # F152 91AA # F153 93B5 # F154 938C # F155 9392 # F156 93B7 # F157 939B # F158 939D # F159 9389 # F15A 93A7 # F15B 938E # F15C 93AA # F15D 939E # F15E 93A6 # F15F 9395 # F160 9388 # F161 9399 # F162 939F # F163 938D # F164 93B1 # F165 9391 # F166 93B2 # F167 93A4 # F168 93A8 # F169 93B4 # F16A 93A3 # F16B 93A5 # F16C 95D2 # F16D 95D3 # F16E 95D1 # F16F 96B3 # F170 96D7 # F171 96DA # F172 5DC2 # F173 96DF # F174 96D8 # F175 96DD # F176 9723 # F177 9722 # F178 9725 # F179 97AC # F17A 97AE # F17B 97A8 # F17C 97AB # F17D 97A4 # F17E 97AA # F1A1 97A2 # F1A2 97A5 # F1A3 97D7 # F1A4 97D9 # F1A5 97D6 # F1A6 97D8 # F1A7 97FA # F1A8 9850 # F1A9 9851 # F1AA 9852 # F1AB 98B8 # F1AC 9941 # F1AD 993C # F1AE 993A # F1AF 9A0F # F1B0 9A0B # F1B1 9A09 # F1B2 9A0D # F1B3 9A04 # F1B4 9A11 # F1B5 9A0A # F1B6 9A05 # F1B7 9A07 # F1B8 9A06 # F1B9 9AC0 # F1BA 9ADC # F1BB 9B08 # F1BC 9B04 # F1BD 9B05 # F1BE 9B29 # F1BF 9B35 # F1C0 9B4A # F1C1 9B4C # F1C2 9B4B # F1C3 9BC7 # F1C4 9BC6 # F1C5 9BC3 # F1C6 9BBF # F1C7 9BC1 # F1C8 9BB5 # F1C9 9BB8 # F1CA 9BD3 # F1CB 9BB6 # F1CC 9BC4 # F1CD 9BB9 # F1CE 9BBD # F1CF 9D5C # F1D0 9D53 # F1D1 9D4F # F1D2 9D4A # F1D3 9D5B # F1D4 9D4B # F1D5 9D59 # F1D6 9D56 # F1D7 9D4C # F1D8 9D57 # F1D9 9D52 # F1DA 9D54 # F1DB 9D5F # F1DC 9D58 # F1DD 9D5A # F1DE 9E8E # F1DF 9E8C # F1E0 9EDF # F1E1 9F01 # F1E2 9F00 # F1E3 9F16 # F1E4 9F25 # F1E5 9F2B # F1E6 9F2A # F1E7 9F29 # F1E8 9F28 # F1E9 9F4C # F1EA 9F55 # F1EB 5134 # F1EC 5135 # F1ED 5296 # F1EE 52F7 # F1EF 53B4 # F1F0 56AB # F1F1 56AD # F1F2 56A6 # F1F3 56A7 # F1F4 56AA # F1F5 56AC # F1F6 58DA # F1F7 58DD # F1F8 58DB # F1F9 5912 # F1FA 5B3D # F1FB 5B3E # F1FC 5B3F # F1FD 5DC3 # F1FE 5E70 # F240 5FBF # F241 61FB # F242 6507 # F243 6510 # F244 650D # F245 6509 # F246 650C # F247 650E # F248 6584 # F249 65DE # F24A 65DD # F24B 66DE # F24C 6AE7 # F24D 6AE0 # F24E 6ACC # F24F 6AD1 # F250 6AD9 # F251 6ACB # F252 6ADF # F253 6ADC # F254 6AD0 # F255 6AEB # F256 6ACF # F257 6ACD # F258 6ADE # F259 6B60 # F25A 6BB0 # F25B 6C0C # F25C 7019 # F25D 7027 # F25E 7020 # F25F 7016 # F260 702B # F261 7021 # F262 7022 # F263 7023 # F264 7029 # F265 7017 # F266 7024 # F267 701C # F268 702A # F269 720C # F26A 720A # F26B 7207 # F26C 7202 # F26D 7205 # F26E 72A5 # F26F 72A6 # F270 72A4 # F271 72A3 # F272 72A1 # F273 74CB # F274 74C5 # F275 74B7 # F276 74C3 # F277 7516 # F278 7660 # F279 77C9 # F27A 77CA # F27B 77C4 # F27C 77F1 # F27D 791D # F27E 791B # F2A1 7921 # F2A2 791C # F2A3 7917 # F2A4 791E # F2A5 79B0 # F2A6 7A67 # F2A7 7A68 # F2A8 7C33 # F2A9 7C3C # F2AA 7C39 # F2AB 7C2C # F2AC 7C3B # F2AD 7CEC # F2AE 7CEA # F2AF 7E76 # F2B0 7E75 # F2B1 7E78 # F2B2 7E70 # F2B3 7E77 # F2B4 7E6F # F2B5 7E7A # F2B6 7E72 # F2B7 7E74 # F2B8 7E68 # F2B9 7F4B # F2BA 7F4A # F2BB 7F83 # F2BC 7F86 # F2BD 7FB7 # F2BE 7FFD # F2BF 7FFE # F2C0 8078 # F2C1 81D7 # F2C2 81D5 # F2C3 8264 # F2C4 8261 # F2C5 8263 # F2C6 85EB # F2C7 85F1 # F2C8 85ED # F2C9 85D9 # F2CA 85E1 # F2CB 85E8 # F2CC 85DA # F2CD 85D7 # F2CE 85EC # F2CF 85F2 # F2D0 85F8 # F2D1 85D8 # F2D2 85DF # F2D3 85E3 # F2D4 85DC # F2D5 85D1 # F2D6 85F0 # F2D7 85E6 # F2D8 85EF # F2D9 85DE # F2DA 85E2 # F2DB 8800 # F2DC 87FA # F2DD 8803 # F2DE 87F6 # F2DF 87F7 # F2E0 8809 # F2E1 880C # F2E2 880B # F2E3 8806 # F2E4 87FC # F2E5 8808 # F2E6 87FF # F2E7 880A # F2E8 8802 # F2E9 8962 # F2EA 895A # F2EB 895B # F2EC 8957 # F2ED 8961 # F2EE 895C # F2EF 8958 # F2F0 895D # F2F1 8959 # F2F2 8988 # F2F3 89B7 # F2F4 89B6 # F2F5 89F6 # F2F6 8B50 # F2F7 8B48 # F2F8 8B4A # F2F9 8B40 # F2FA 8B53 # F2FB 8B56 # F2FC 8B54 # F2FD 8B4B # F2FE 8B55 # F340 8B51 # F341 8B42 # F342 8B52 # F343 8B57 # F344 8C43 # F345 8C77 # F346 8C76 # F347 8C9A # F348 8D06 # F349 8D07 # F34A 8D09 # F34B 8DAC # F34C 8DAA # F34D 8DAD # F34E 8DAB # F34F 8E6D # F350 8E78 # F351 8E73 # F352 8E6A # F353 8E6F # F354 8E7B # F355 8EC2 # F356 8F52 # F357 8F51 # F358 8F4F # F359 8F50 # F35A 8F53 # F35B 8FB4 # F35C 9140 # F35D 913F # F35E 91B0 # F35F 91AD # F360 93DE # F361 93C7 # F362 93CF # F363 93C2 # F364 93DA # F365 93D0 # F366 93F9 # F367 93EC # F368 93CC # F369 93D9 # F36A 93A9 # F36B 93E6 # F36C 93CA # F36D 93D4 # F36E 93EE # F36F 93E3 # F370 93D5 # F371 93C4 # F372 93CE # F373 93C0 # F374 93D2 # F375 93E7 # F376 957D # F377 95DA # F378 95DB # F379 96E1 # F37A 9729 # F37B 972B # F37C 972C # F37D 9728 # F37E 9726 # F3A1 97B3 # F3A2 97B7 # F3A3 97B6 # F3A4 97DD # F3A5 97DE # F3A6 97DF # F3A7 985C # F3A8 9859 # F3A9 985D # F3AA 9857 # F3AB 98BF # F3AC 98BD # F3AD 98BB # F3AE 98BE # F3AF 9948 # F3B0 9947 # F3B1 9943 # F3B2 99A6 # F3B3 99A7 # F3B4 9A1A # F3B5 9A15 # F3B6 9A25 # F3B7 9A1D # F3B8 9A24 # F3B9 9A1B # F3BA 9A22 # F3BB 9A20 # F3BC 9A27 # F3BD 9A23 # F3BE 9A1E # F3BF 9A1C # F3C0 9A14 # F3C1 9AC2 # F3C2 9B0B # F3C3 9B0A # F3C4 9B0E # F3C5 9B0C # F3C6 9B37 # F3C7 9BEA # F3C8 9BEB # F3C9 9BE0 # F3CA 9BDE # F3CB 9BE4 # F3CC 9BE6 # F3CD 9BE2 # F3CE 9BF0 # F3CF 9BD4 # F3D0 9BD7 # F3D1 9BEC # F3D2 9BDC # F3D3 9BD9 # F3D4 9BE5 # F3D5 9BD5 # F3D6 9BE1 # F3D7 9BDA # F3D8 9D77 # F3D9 9D81 # F3DA 9D8A # F3DB 9D84 # F3DC 9D88 # F3DD 9D71 # F3DE 9D80 # F3DF 9D78 # F3E0 9D86 # F3E1 9D8B # F3E2 9D8C # F3E3 9D7D # F3E4 9D6B # F3E5 9D74 # F3E6 9D75 # F3E7 9D70 # F3E8 9D69 # F3E9 9D85 # F3EA 9D73 # F3EB 9D7B # F3EC 9D82 # F3ED 9D6F # F3EE 9D79 # F3EF 9D7F # F3F0 9D87 # F3F1 9D68 # F3F2 9E94 # F3F3 9E91 # F3F4 9EC0 # F3F5 9EFC # F3F6 9F2D # F3F7 9F40 # F3F8 9F41 # F3F9 9F4D # F3FA 9F56 # F3FB 9F57 # F3FC 9F58 # F3FD 5337 # F3FE 56B2 # F440 56B5 # F441 56B3 # F442 58E3 # F443 5B45 # F444 5DC6 # F445 5DC7 # F446 5EEE # F447 5EEF # F448 5FC0 # F449 5FC1 # F44A 61F9 # F44B 6517 # F44C 6516 # F44D 6515 # F44E 6513 # F44F 65DF # F450 66E8 # F451 66E3 # F452 66E4 # F453 6AF3 # F454 6AF0 # F455 6AEA # F456 6AE8 # F457 6AF9 # F458 6AF1 # F459 6AEE # F45A 6AEF # F45B 703C # F45C 7035 # F45D 702F # F45E 7037 # F45F 7034 # F460 7031 # F461 7042 # F462 7038 # F463 703F # F464 703A # F465 7039 # F466 7040 # F467 703B # F468 7033 # F469 7041 # F46A 7213 # F46B 7214 # F46C 72A8 # F46D 737D # F46E 737C # F46F 74BA # F470 76AB # F471 76AA # F472 76BE # F473 76ED # F474 77CC # F475 77CE # F476 77CF # F477 77CD # F478 77F2 # F479 7925 # F47A 7923 # F47B 7927 # F47C 7928 # F47D 7924 # F47E 7929 # F4A1 79B2 # F4A2 7A6E # F4A3 7A6C # F4A4 7A6D # F4A5 7AF7 # F4A6 7C49 # F4A7 7C48 # F4A8 7C4A # F4A9 7C47 # F4AA 7C45 # F4AB 7CEE # F4AC 7E7B # F4AD 7E7E # F4AE 7E81 # F4AF 7E80 # F4B0 7FBA # F4B1 7FFF # F4B2 8079 # F4B3 81DB # F4B4 81D9 # F4B5 820B # F4B6 8268 # F4B7 8269 # F4B8 8622 # F4B9 85FF # F4BA 8601 # F4BB 85FE # F4BC 861B # F4BD 8600 # F4BE 85F6 # F4BF 8604 # F4C0 8609 # F4C1 8605 # F4C2 860C # F4C3 85FD # F4C4 8819 # F4C5 8810 # F4C6 8811 # F4C7 8817 # F4C8 8813 # F4C9 8816 # F4CA 8963 # F4CB 8966 # F4CC 89B9 # F4CD 89F7 # F4CE 8B60 # F4CF 8B6A # F4D0 8B5D # F4D1 8B68 # F4D2 8B63 # F4D3 8B65 # F4D4 8B67 # F4D5 8B6D # F4D6 8DAE # F4D7 8E86 # F4D8 8E88 # F4D9 8E84 # F4DA 8F59 # F4DB 8F56 # F4DC 8F57 # F4DD 8F55 # F4DE 8F58 # F4DF 8F5A # F4E0 908D # F4E1 9143 # F4E2 9141 # F4E3 91B7 # F4E4 91B5 # F4E5 91B2 # F4E6 91B3 # F4E7 940B # F4E8 9413 # F4E9 93FB # F4EA 9420 # F4EB 940F # F4EC 9414 # F4ED 93FE # F4EE 9415 # F4EF 9410 # F4F0 9428 # F4F1 9419 # F4F2 940D # F4F3 93F5 # F4F4 9400 # F4F5 93F7 # F4F6 9407 # F4F7 940E # F4F8 9416 # F4F9 9412 # F4FA 93FA # F4FB 9409 # F4FC 93F8 # F4FD 940A # F4FE 93FF # F540 93FC # F541 940C # F542 93F6 # F543 9411 # F544 9406 # F545 95DE # F546 95E0 # F547 95DF # F548 972E # F549 972F # F54A 97B9 # F54B 97BB # F54C 97FD # F54D 97FE # F54E 9860 # F54F 9862 # F550 9863 # F551 985F # F552 98C1 # F553 98C2 # F554 9950 # F555 994E # F556 9959 # F557 994C # F558 994B # F559 9953 # F55A 9A32 # F55B 9A34 # F55C 9A31 # F55D 9A2C # F55E 9A2A # F55F 9A36 # F560 9A29 # F561 9A2E # F562 9A38 # F563 9A2D # F564 9AC7 # F565 9ACA # F566 9AC6 # F567 9B10 # F568 9B12 # F569 9B11 # F56A 9C0B # F56B 9C08 # F56C 9BF7 # F56D 9C05 # F56E 9C12 # F56F 9BF8 # F570 9C40 # F571 9C07 # F572 9C0E # F573 9C06 # F574 9C17 # F575 9C14 # F576 9C09 # F577 9D9F # F578 9D99 # F579 9DA4 # F57A 9D9D # F57B 9D92 # F57C 9D98 # F57D 9D90 # F57E 9D9B # F5A1 9DA0 # F5A2 9D94 # F5A3 9D9C # F5A4 9DAA # F5A5 9D97 # F5A6 9DA1 # F5A7 9D9A # F5A8 9DA2 # F5A9 9DA8 # F5AA 9D9E # F5AB 9DA3 # F5AC 9DBF # F5AD 9DA9 # F5AE 9D96 # F5AF 9DA6 # F5B0 9DA7 # F5B1 9E99 # F5B2 9E9B # F5B3 9E9A # F5B4 9EE5 # F5B5 9EE4 # F5B6 9EE7 # F5B7 9EE6 # F5B8 9F30 # F5B9 9F2E # F5BA 9F5B # F5BB 9F60 # F5BC 9F5E # F5BD 9F5D # F5BE 9F59 # F5BF 9F91 # F5C0 513A # F5C1 5139 # F5C2 5298 # F5C3 5297 # F5C4 56C3 # F5C5 56BD # F5C6 56BE # F5C7 5B48 # F5C8 5B47 # F5C9 5DCB # F5CA 5DCF # F5CB 5EF1 # F5CC 61FD # F5CD 651B # F5CE 6B02 # F5CF 6AFC # F5D0 6B03 # F5D1 6AF8 # F5D2 6B00 # F5D3 7043 # F5D4 7044 # F5D5 704A # F5D6 7048 # F5D7 7049 # F5D8 7045 # F5D9 7046 # F5DA 721D # F5DB 721A # F5DC 7219 # F5DD 737E # F5DE 7517 # F5DF 766A # F5E0 77D0 # F5E1 792D # F5E2 7931 # F5E3 792F # F5E4 7C54 # F5E5 7C53 # F5E6 7CF2 # F5E7 7E8A # F5E8 7E87 # F5E9 7E88 # F5EA 7E8B # F5EB 7E86 # F5EC 7E8D # F5ED 7F4D # F5EE 7FBB # F5EF 8030 # F5F0 81DD # F5F1 8618 # F5F2 862A # F5F3 8626 # F5F4 861F # F5F5 8623 # F5F6 861C # F5F7 8619 # F5F8 8627 # F5F9 862E # F5FA 8621 # F5FB 8620 # F5FC 8629 # F5FD 861E # F5FE 8625 # F640 8829 # F641 881D # F642 881B # F643 8820 # F644 8824 # F645 881C # F646 882B # F647 884A # F648 896D # F649 8969 # F64A 896E # F64B 896B # F64C 89FA # F64D 8B79 # F64E 8B78 # F64F 8B45 # F650 8B7A # F651 8B7B # F652 8D10 # F653 8D14 # F654 8DAF # F655 8E8E # F656 8E8C # F657 8F5E # F658 8F5B # F659 8F5D # F65A 9146 # F65B 9144 # F65C 9145 # F65D 91B9 # F65E 943F # F65F 943B # F660 9436 # F661 9429 # F662 943D # F663 943C # F664 9430 # F665 9439 # F666 942A # F667 9437 # F668 942C # F669 9440 # F66A 9431 # F66B 95E5 # F66C 95E4 # F66D 95E3 # F66E 9735 # F66F 973A # F670 97BF # F671 97E1 # F672 9864 # F673 98C9 # F674 98C6 # F675 98C0 # F676 9958 # F677 9956 # F678 9A39 # F679 9A3D # F67A 9A46 # F67B 9A44 # F67C 9A42 # F67D 9A41 # F67E 9A3A # F6A1 9A3F # F6A2 9ACD # F6A3 9B15 # F6A4 9B17 # F6A5 9B18 # F6A6 9B16 # F6A7 9B3A # F6A8 9B52 # F6A9 9C2B # F6AA 9C1D # F6AB 9C1C # F6AC 9C2C # F6AD 9C23 # F6AE 9C28 # F6AF 9C29 # F6B0 9C24 # F6B1 9C21 # F6B2 9DB7 # F6B3 9DB6 # F6B4 9DBC # F6B5 9DC1 # F6B6 9DC7 # F6B7 9DCA # F6B8 9DCF # F6B9 9DBE # F6BA 9DC5 # F6BB 9DC3 # F6BC 9DBB # F6BD 9DB5 # F6BE 9DCE # F6BF 9DB9 # F6C0 9DBA # F6C1 9DAC # F6C2 9DC8 # F6C3 9DB1 # F6C4 9DAD # F6C5 9DCC # F6C6 9DB3 # F6C7 9DCD # F6C8 9DB2 # F6C9 9E7A # F6CA 9E9C # F6CB 9EEB # F6CC 9EEE # F6CD 9EED # F6CE 9F1B # F6CF 9F18 # F6D0 9F1A # F6D1 9F31 # F6D2 9F4E # F6D3 9F65 # F6D4 9F64 # F6D5 9F92 # F6D6 4EB9 # F6D7 56C6 # F6D8 56C5 # F6D9 56CB # F6DA 5971 # F6DB 5B4B # F6DC 5B4C # F6DD 5DD5 # F6DE 5DD1 # F6DF 5EF2 # F6E0 6521 # F6E1 6520 # F6E2 6526 # F6E3 6522 # F6E4 6B0B # F6E5 6B08 # F6E6 6B09 # F6E7 6C0D # F6E8 7055 # F6E9 7056 # F6EA 7057 # F6EB 7052 # F6EC 721E # F6ED 721F # F6EE 72A9 # F6EF 737F # F6F0 74D8 # F6F1 74D5 # F6F2 74D9 # F6F3 74D7 # F6F4 766D # F6F5 76AD # F6F6 7935 # F6F7 79B4 # F6F8 7A70 # F6F9 7A71 # F6FA 7C57 # F6FB 7C5C # F6FC 7C59 # F6FD 7C5B # F6FE 7C5A # F740 7CF4 # F741 7CF1 # F742 7E91 # F743 7F4F # F744 7F87 # F745 81DE # F746 826B # F747 8634 # F748 8635 # F749 8633 # F74A 862C # F74B 8632 # F74C 8636 # F74D 882C # F74E 8828 # F74F 8826 # F750 882A # F751 8825 # F752 8971 # F753 89BF # F754 89BE # F755 89FB # F756 8B7E # F757 8B84 # F758 8B82 # F759 8B86 # F75A 8B85 # F75B 8B7F # F75C 8D15 # F75D 8E95 # F75E 8E94 # F75F 8E9A # F760 8E92 # F761 8E90 # F762 8E96 # F763 8E97 # F764 8F60 # F765 8F62 # F766 9147 # F767 944C # F768 9450 # F769 944A # F76A 944B # F76B 944F # F76C 9447 # F76D 9445 # F76E 9448 # F76F 9449 # F770 9446 # F771 973F # F772 97E3 # F773 986A # F774 9869 # F775 98CB # F776 9954 # F777 995B # F778 9A4E # F779 9A53 # F77A 9A54 # F77B 9A4C # F77C 9A4F # F77D 9A48 # F77E 9A4A # F7A1 9A49 # F7A2 9A52 # F7A3 9A50 # F7A4 9AD0 # F7A5 9B19 # F7A6 9B2B # F7A7 9B3B # F7A8 9B56 # F7A9 9B55 # F7AA 9C46 # F7AB 9C48 # F7AC 9C3F # F7AD 9C44 # F7AE 9C39 # F7AF 9C33 # F7B0 9C41 # F7B1 9C3C # F7B2 9C37 # F7B3 9C34 # F7B4 9C32 # F7B5 9C3D # F7B6 9C36 # F7B7 9DDB # F7B8 9DD2 # F7B9 9DDE # F7BA 9DDA # F7BB 9DCB # F7BC 9DD0 # F7BD 9DDC # F7BE 9DD1 # F7BF 9DDF # F7C0 9DE9 # F7C1 9DD9 # F7C2 9DD8 # F7C3 9DD6 # F7C4 9DF5 # F7C5 9DD5 # F7C6 9DDD # F7C7 9EB6 # F7C8 9EF0 # F7C9 9F35 # F7CA 9F33 # F7CB 9F32 # F7CC 9F42 # F7CD 9F6B # F7CE 9F95 # F7CF 9FA2 # F7D0 513D # F7D1 5299 # F7D2 58E8 # F7D3 58E7 # F7D4 5972 # F7D5 5B4D # F7D6 5DD8 # F7D7 882F # F7D8 5F4F # F7D9 6201 # F7DA 6203 # F7DB 6204 # F7DC 6529 # F7DD 6525 # F7DE 6596 # F7DF 66EB # F7E0 6B11 # F7E1 6B12 # F7E2 6B0F # F7E3 6BCA # F7E4 705B # F7E5 705A # F7E6 7222 # F7E7 7382 # F7E8 7381 # F7E9 7383 # F7EA 7670 # F7EB 77D4 # F7EC 7C67 # F7ED 7C66 # F7EE 7E95 # F7EF 826C # F7F0 863A # F7F1 8640 # F7F2 8639 # F7F3 863C # F7F4 8631 # F7F5 863B # F7F6 863E # F7F7 8830 # F7F8 8832 # F7F9 882E # F7FA 8833 # F7FB 8976 # F7FC 8974 # F7FD 8973 # F7FE 89FE # F840 8B8C # F841 8B8E # F842 8B8B # F843 8B88 # F844 8C45 # F845 8D19 # F846 8E98 # F847 8F64 # F848 8F63 # F849 91BC # F84A 9462 # F84B 9455 # F84C 945D # F84D 9457 # F84E 945E # F84F 97C4 # F850 97C5 # F851 9800 # F852 9A56 # F853 9A59 # F854 9B1E # F855 9B1F # F856 9B20 # F857 9C52 # F858 9C58 # F859 9C50 # F85A 9C4A # F85B 9C4D # F85C 9C4B # F85D 9C55 # F85E 9C59 # F85F 9C4C # F860 9C4E # F861 9DFB # F862 9DF7 # F863 9DEF # F864 9DE3 # F865 9DEB # F866 9DF8 # F867 9DE4 # F868 9DF6 # F869 9DE1 # F86A 9DEE # F86B 9DE6 # F86C 9DF2 # F86D 9DF0 # F86E 9DE2 # F86F 9DEC # F870 9DF4 # F871 9DF3 # F872 9DE8 # F873 9DED # F874 9EC2 # F875 9ED0 # F876 9EF2 # F877 9EF3 # F878 9F06 # F879 9F1C # F87A 9F38 # F87B 9F37 # F87C 9F36 # F87D 9F43 # F87E 9F4F # F8A1 9F71 # F8A2 9F70 # F8A3 9F6E # F8A4 9F6F # F8A5 56D3 # F8A6 56CD # F8A7 5B4E # F8A8 5C6D # F8A9 652D # F8AA 66ED # F8AB 66EE # F8AC 6B13 # F8AD 705F # F8AE 7061 # F8AF 705D # F8B0 7060 # F8B1 7223 # F8B2 74DB # F8B3 74E5 # F8B4 77D5 # F8B5 7938 # F8B6 79B7 # F8B7 79B6 # F8B8 7C6A # F8B9 7E97 # F8BA 7F89 # F8BB 826D # F8BC 8643 # F8BD 8838 # F8BE 8837 # F8BF 8835 # F8C0 884B # F8C1 8B94 # F8C2 8B95 # F8C3 8E9E # F8C4 8E9F # F8C5 8EA0 # F8C6 8E9D # F8C7 91BE # F8C8 91BD # F8C9 91C2 # F8CA 946B # F8CB 9468 # F8CC 9469 # F8CD 96E5 # F8CE 9746 # F8CF 9743 # F8D0 9747 # F8D1 97C7 # F8D2 97E5 # F8D3 9A5E # F8D4 9AD5 # F8D5 9B59 # F8D6 9C63 # F8D7 9C67 # F8D8 9C66 # F8D9 9C62 # F8DA 9C5E # F8DB 9C60 # F8DC 9E02 # F8DD 9DFE # F8DE 9E07 # F8DF 9E03 # F8E0 9E06 # F8E1 9E05 # F8E2 9E00 # F8E3 9E01 # F8E4 9E09 # F8E5 9DFF # F8E6 9DFD # F8E7 9E04 # F8E8 9EA0 # F8E9 9F1E # F8EA 9F46 # F8EB 9F74 # F8EC 9F75 # F8ED 9F76 # F8EE 56D4 # F8EF 652E # F8F0 65B8 # F8F1 6B18 # F8F2 6B19 # F8F3 6B17 # F8F4 6B1A # F8F5 7062 # F8F6 7226 # F8F7 72AA # F8F8 77D8 # F8F9 77D9 # F8FA 7939 # F8FB 7C69 # F8FC 7C6B # F8FD 7CF6 # F8FE 7E9A # F940 7E98 # F941 7E9B # F942 7E99 # F943 81E0 # F944 81E1 # F945 8646 # F946 8647 # F947 8648 # F948 8979 # F949 897A # F94A 897C # F94B 897B # F94C 89FF # F94D 8B98 # F94E 8B99 # F94F 8EA5 # F950 8EA4 # F951 8EA3 # F952 946E # F953 946D # F954 946F # F955 9471 # F956 9473 # F957 9749 # F958 9872 # F959 995F # F95A 9C68 # F95B 9C6E # F95C 9C6D # F95D 9E0B # F95E 9E0D # F95F 9E10 # F960 9E0F # F961 9E12 # F962 9E11 # F963 9EA1 # F964 9EF5 # F965 9F09 # F966 9F47 # F967 9F78 # F968 9F7B # F969 9F7A # F96A 9F79 # F96B 571E # F96C 7066 # F96D 7C6F # F96E 883C # F96F 8DB2 # F970 8EA6 # F971 91C3 # F972 9474 # F973 9478 # F974 9476 # F975 9475 # F976 9A60 # F977 9C74 # F978 9C73 # F979 9C71 # F97A 9C75 # F97B 9E14 # F97C 9E13 # F97D 9EF6 # F97E 9F0A # F9A1 9FA4 # F9A2 7068 # F9A3 7065 # F9A4 7CF7 # F9A5 866A # F9A6 883E # F9A7 883D # F9A8 883F # F9A9 8B9E # F9AA 8C9C # F9AB 8EA9 # F9AC 8EC9 # F9AD 974B # F9AE 9873 # F9AF 9874 # F9B0 98CC # F9B1 9961 # F9B2 99AB # F9B3 9A64 # F9B4 9A66 # F9B5 9A67 # F9B6 9B24 # F9B7 9E15 # F9B8 9E17 # F9B9 9F48 # F9BA 6207 # F9BB 6B1E # F9BC 7227 # F9BD 864C # F9BE 8EA8 # F9BF 9482 # F9C0 9480 # F9C1 9481 # F9C2 9A69 # F9C3 9A68 # F9C4 9B2E # F9C5 9E19 # F9C6 7229 # F9C7 864B # F9C8 8B9F # F9C9 9483 # F9CA 9C79 # F9CB 9EB7 # F9CC 7675 # F9CD 9A6B # F9CE 9C7A # F9CF 9E1D # F9D0 7069 # F9D1 706A # F9D2 9EA4 # F9D3 9F7E # F9D4 9F49 # F9D5 9F98 # cyrus-imapd-2.5.10/lib/hash.h0000644000175000017500000000557513001236020012616 00000000000000/* +++Date last modified: 05-Jul-1997 */ #ifndef HASH__H #define HASH__H #include /* For size_t */ #include "mpool.h" #define HASH_TABLE_INITIALIZER {0, NULL, NULL} /* ** A hash table consists of an array of these buckets. Each bucket ** holds a copy of the key, a pointer to the data associated with the ** key, and a pointer to the next bucket that collided with this one, ** if there was one. */ typedef struct bucket { char *key; void *data; struct bucket *next; } bucket; /* ** This is what you actually declare an instance of to create a table. ** You then call 'construct_table' with the address of this structure, ** and a guess at the size of the table. Note that more nodes than this ** can be inserted in the table, but performance degrades as this ** happens. Performance should still be quite adequate until 2 or 3 ** times as many nodes have been inserted as the table was created with. */ typedef struct hash_table { size_t size; bucket **table; struct mpool *pool; } hash_table; /* ** This is used to construct the table. If it doesn't succeed, it sets ** the table's size to 0, and the pointer to the table to NULL. */ hash_table *construct_hash_table(hash_table *table, size_t size, int use_mpool); /* ** Inserts a pointer to 'data' in the table, with a copy of 'key' as its ** key. Note that this makes a copy of the key, but NOT of the ** associated data. */ void *hash_insert(const char *key,void *data,hash_table *table); /* ** Returns a pointer to the data associated with a key. If the key has ** not been inserted in the table, returns NULL. */ void *hash_lookup(const char *key,hash_table *table); /* ** Deletes an entry from the table. Returns a pointer to the data that ** was associated with the key so the calling code can dispose of it ** properly. */ /* Warning: use this function judiciously if you are using memory pools, * since it will leak memory until you get rid of the entire hash table */ void *hash_del(const char *key,hash_table *table); /* ** Goes through a hash table and calls the function passed to it ** for each node that has been inserted. The function is passed ** a pointer to the key, a pointer to the data associated ** with it and 'rock'. */ void hash_enumerate(hash_table *table,void (*func)(const char *,void *,void *), void *rock); /* ** Frees a hash table. For each node that was inserted in the table, ** it calls the function whose address it was passed, with a pointer ** to the data that was in the table. The function is expected to ** free the data. Typical usage would be: ** free_table(&table, free); ** if the data placed in the table was dynamically allocated, or: ** free_table(&table, NULL); ** if not. ( If the parameter passed is NULL, it knows not to call ** any function with the data. ) */ void free_hash_table(hash_table *table, void (*func)(void *)); #endif /* HASH__H */ cyrus-imapd-2.5.10/lib/iostat.h0000644000175000017500000000016412772415051013204 00000000000000struct io_count { int io_read_count; int io_write_count; }; void read_io_count(struct io_count *iocount); cyrus-imapd-2.5.10/lib/retry.c0000644000175000017500000001106713001236020013024 00000000000000/* retry.c -- keep trying write system calls * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include #include #include #include #ifdef HAVE_UNISTD_H #include #endif #include "exitcodes.h" #include "retry.h" #include "xmalloc.h" /* * Keep calling the read() system call with 'fd', 'buf', and 'nbyte' * until all the data is read in or an error occurs. */ EXPORTED ssize_t retry_read(int fd, void *vbuf, size_t nbyte) { size_t nread; char *buf = vbuf; for (nread = 0; nread < nbyte; ) { ssize_t n = read(fd, buf + nread, nbyte - nread); if (n == 0) { /* end of file */ return -1; } if (n == -1) { if (errno == EINTR || errno == EAGAIN) continue; return -1; } nread += n; } return nread; } /* * Keep calling the write() system call with 'fd', 'buf', and 'nbyte' * until all the data is written out or an error occurs. */ EXPORTED ssize_t retry_write(int fd, const void *vbuf, size_t nbyte) { const char *buf = vbuf; size_t written = 0; if (nbyte == 0) return 0; for (written = 0; written < nbyte; ) { ssize_t n = write(fd, buf + written, nbyte - written); if (n == -1) { if (errno == EINTR) continue; return -1; } written += n; } return written; } /* * Keep calling the writev() system call with 'fd', 'iov', and 'iovcnt' * until all the data is written out or an error occurs. * * Now no longer destructive of parameters! */ EXPORTED ssize_t retry_writev(int fd, const struct iovec *srciov, int iovcnt) { int i; ssize_t n; size_t written = 0; size_t len = 0; struct iovec *iov, *baseiov = NULL; static int iov_max = #ifdef MAXIOV MAXIOV #else #ifdef IOV_MAX IOV_MAX #else 8192 #endif #endif ; if (!iovcnt) return 0; for (i = 0; i < iovcnt; i++) { len += srciov[i].iov_len; } n = written = writev(fd, srciov, iovcnt > iov_max ? iov_max : iovcnt); /* did we get lucky and write it all? */ if (written == len) return written; /* oh well, welcome to the slow path - we have copies */ baseiov = iov = (struct iovec *)xmalloc(iovcnt * sizeof(struct iovec)); for (i = 0; i < iovcnt; i++) { iov[i].iov_base = srciov[i].iov_base; iov[i].iov_len = srciov[i].iov_len; } for (;;) { for (i = 0; i < iovcnt; i++) { if (iov[i].iov_len > (size_t)n) { iov[i].iov_base += n; iov[i].iov_len -= n; break; } n -= iov[i].iov_len; iov++; iovcnt--; if (!iovcnt) fatal("ran out of iov", EC_SOFTWARE); } n = writev(fd, iov, iovcnt > iov_max ? iov_max : iovcnt); if (n == -1) { if (errno == EINVAL && iov_max > 10) { iov_max /= 2; continue; } if (errno == EINTR) continue; free(baseiov); return -1; } written += n; if (written == len) break; } free(baseiov); return written; } cyrus-imapd-2.5.10/lib/libconfig.c0000644000175000017500000006153613001236020013621 00000000000000/* libconfig.c -- imapd.conf handling * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include #include #include #include #include #include #include #include #include #include #include "assert.h" #include "exitcodes.h" #include "hash.h" #include "libconfig.h" #include "xmalloc.h" #include "xstrlcat.h" #include "xstrlcpy.h" #include "util.h" #define CONFIGHASHSIZE 30 /* relatively small, * because it is for overflow only */ #define INCLUDEHASHSIZE 5 /* relatively small, * but how many includes are reasonable? */ static struct hash_table confighash, includehash; /* cached configuration variables accessible to the external world */ EXPORTED const char *config_filename= NULL; /* filename of configuration file */ EXPORTED const char *config_dir = NULL; /* ie /var/imap */ EXPORTED const char *config_defpartition = NULL; /* /var/spool/imap */ EXPORTED const char *config_servername= NULL; /* gethostname() */ EXPORTED enum enum_value config_serverinfo; /* on */ EXPORTED const char *config_mupdate_server = NULL;/* NULL */ EXPORTED const char *config_defdomain = NULL; /* NULL */ EXPORTED const char *config_ident = NULL; /* the service name */ EXPORTED int config_hashimapspool; /* f */ EXPORTED enum enum_value config_virtdomains; /* f */ EXPORTED enum enum_value config_mupdate_config; /* IMAP_ENUM_MUPDATE_CONFIG_STANDARD */ EXPORTED int config_auditlog; EXPORTED int config_iolog; EXPORTED unsigned config_maxword; EXPORTED unsigned config_maxquoted; EXPORTED int config_qosmarking; EXPORTED int config_debug; extern void fatal(const char *fatal_message, int fatal_code) __attribute__ ((noreturn)); /* prototype to allow for sane function ordering */ static void config_read_file(const char *filename); EXPORTED const char *config_getstring(enum imapopt opt) { assert(opt > IMAPOPT_ZERO && opt < IMAPOPT_LAST); assert((imapopts[opt].t == OPT_STRING) || (imapopts[opt].t == OPT_STRINGLIST)); return imapopts[opt].val.s; } EXPORTED int config_getint(enum imapopt opt) { assert(opt > IMAPOPT_ZERO && opt < IMAPOPT_LAST); assert(imapopts[opt].t == OPT_INT); #if (SIZEOF_LONG != 4) if ((imapopts[opt].val.i > 0x7fffffff)|| (imapopts[opt].val.i < -0x7fffffff)) { syslog(LOG_ERR, "config_getint: %s: %ld too large for type", imapopts[opt].optname, imapopts[opt].val.i); } #endif return imapopts[opt].val.i; } EXPORTED int config_getswitch(enum imapopt opt) { assert(opt > IMAPOPT_ZERO && opt < IMAPOPT_LAST); assert(imapopts[opt].t == OPT_SWITCH); #if (SIZEOF_LONG != 4) if ((imapopts[opt].val.b > 0x7fffffff)|| (imapopts[opt].val.b < -0x7fffffff)) { syslog(LOG_ERR, "config_getswitch: %s: %ld too large for type", imapopts[opt].optname, imapopts[opt].val.b); } #endif return imapopts[opt].val.b; } EXPORTED enum enum_value config_getenum(enum imapopt opt) { assert(opt > IMAPOPT_ZERO && opt < IMAPOPT_LAST); assert(imapopts[opt].t == OPT_ENUM); return imapopts[opt].val.e; } EXPORTED unsigned long config_getbitfield(enum imapopt opt) { assert(opt > IMAPOPT_ZERO && opt < IMAPOPT_LAST); assert(imapopts[opt].t == OPT_BITFIELD); return imapopts[opt].val.x; } EXPORTED const char *config_getoverflowstring(const char *key, const char *def) { char buf[256]; char *ret = NULL; if (!config_filename) return 0; /* First lookup _key, to see if we have a service-specific * override */ if (config_ident) { if (snprintf(buf,sizeof(buf),"%s_%s",config_ident,key) == -1) fatal("key too long in config_getoverflowstring", EC_TEMPFAIL); lcase(buf); ret = hash_lookup(buf, &confighash); } /* No service-specific override, check the actual key */ if (!ret) ret = hash_lookup(key, &confighash); /* Return what we got or the default */ return ret ? ret : def; } EXPORTED void config_foreachoverflowstring(void (*func)(const char *, const char *, void *), void *rock) { if (!config_filename) return; hash_enumerate(&confighash, (void (*)(const char *, void *, void *)) func, rock); } EXPORTED const char *config_partitiondir(const char *partition) { char buf[80]; if (strlcpy(buf, "partition-", sizeof(buf)) >= sizeof(buf)) return 0; if (strlcat(buf, partition, sizeof(buf)) >= sizeof(buf)) return 0; return config_getoverflowstring(buf, NULL); } EXPORTED const char *config_metapartitiondir(const char *partition) { char buf[80]; if (strlcpy(buf, "metapartition-", sizeof(buf)) >= sizeof(buf)) return 0; if (strlcat(buf, partition, sizeof(buf)) >= sizeof(buf)) return 0; return config_getoverflowstring(buf, NULL); } static void config_ispartition(const char *key, const char *val __attribute__((unused)), void *rock) { int *found = (int *) rock; if (!strncmp("partition-", key, 10)) *found = 1; } static void config_option_deprecate(const int dopt, const int opt, char *since) { syslog( LOG_WARNING, "Option '%s' is deprecated in favor of '%s' since version %s.", imapopts[dopt].optname, imapopts[opt].optname, since ); switch (imapopts[dopt].t) { case OPT_BITFIELD: { imapopts[opt].val.x = imapopts[dopt].val.x; break; } case OPT_ENUM: { imapopts[opt].val.e = imapopts[dopt].val.e; break; } case OPT_SWITCH: { imapopts[opt].val.b = imapopts[dopt].val.b; break; } case OPT_INT: { imapopts[opt].val.i = imapopts[dopt].val.i; break; } case OPT_STRINGLIST: case OPT_STRING: { imapopts[opt].val.s = xstrdup(imapopts[dopt].val.s); free((char *)imapopts[dopt].val.s); break; } default: { break; } } } static void config_option_deprecated(const int opt) { switch (opt) { case IMAPOPT_AUTOCREATEINBOXFOLDERS: { config_option_deprecate(opt, IMAPOPT_AUTOCREATE_INBOX_FOLDERS, "2.5.0"); break; } case IMAPOPT_AUTOCREATEQUOTA: { config_option_deprecate(opt, IMAPOPT_AUTOCREATE_QUOTA, "2.5.0"); break; } case IMAPOPT_AUTOCREATEQUOTAMSG: { config_option_deprecate(opt, IMAPOPT_AUTOCREATE_QUOTA_MESSAGES, "2.5.0"); break; } case IMAPOPT_AUTOSIEVEFOLDERS: { config_option_deprecate(opt, IMAPOPT_AUTOCREATE_SIEVE_FOLDERS, "2.5.0"); break; } case IMAPOPT_AUTOCREATE_SIEVE_COMPILED_SCRIPT: { config_option_deprecate(opt, IMAPOPT_AUTOCREATE_SIEVE_SCRIPT_COMPILED, "2.5.0"); break; } case IMAPOPT_AUTOSUBSCRIBEINBOXFOLDERS: { config_option_deprecate(opt, IMAPOPT_AUTOCREATE_SUBSCRIBE_FOLDERS, "2.5.0"); break; } case IMAPOPT_AUTOSUBSCRIBESHAREDFOLDERS: { config_option_deprecate(opt, IMAPOPT_AUTOCREATE_SUBSCRIBE_SHAREDFOLDERS, "2.5.0"); break; } case IMAPOPT_AUTOSUBSCRIBE_ALL_SHAREDFOLDERS: { config_option_deprecate(opt, IMAPOPT_AUTOCREATE_SUBSCRIBE_SHAREDFOLDERS_ALL, "2.5.0"); break; } case IMAPOPT_CREATEONPOST: { config_option_deprecate(opt, IMAPOPT_AUTOCREATE_POST, "2.5.0"); break; } case IMAPOPT_FLUSHSEENSTATE: { syslog( LOG_WARNING, "Option '%s' is deprecated in version 2.5.0.", imapopts[opt].optname ); break; } case IMAPOPT_GENERATE_COMPILED_SIEVE_SCRIPT: { config_option_deprecate(opt, IMAPOPT_AUTOCREATE_SIEVE_SCRIPT_COMPILE, "2.5.0"); break; } case IMAPOPT_LDAP_TLS_CACERT_DIR: { config_option_deprecate(opt, IMAPOPT_LDAP_CA_DIR, "2.5.0"); break; } case IMAPOPT_LDAP_TLS_CACERT_FILE: { config_option_deprecate(opt, IMAPOPT_LDAP_CA_FILE, "2.5.0"); break; } case IMAPOPT_LDAP_TLS_CERT: { config_option_deprecate(opt, IMAPOPT_LDAP_CLIENT_CERT, "2.5.0"); break; } case IMAPOPT_LDAP_TLS_CHECK_PEER: { config_option_deprecate(opt, IMAPOPT_LDAP_VERIFY_PEER, "2.5.0"); break; } case IMAPOPT_LDAP_TLS_CIPHERS: { config_option_deprecate(opt, IMAPOPT_LDAP_CIPHERS, "2.5.0"); break; } case IMAPOPT_LDAP_TLS_KEY: { config_option_deprecate(opt, IMAPOPT_LDAP_CLIENT_KEY, "2.5.0"); break; } case IMAPOPT_TLS_CA_FILE: { config_option_deprecate(opt, IMAPOPT_TLS_CLIENT_CA_FILE, "2.5.0"); break; } case IMAPOPT_TLS_CA_PATH: { config_option_deprecate(opt, IMAPOPT_TLS_CLIENT_CA_DIR, "2.5.0"); break; } case IMAPOPT_TLS_CERT_FILE: { config_option_deprecate(opt, IMAPOPT_TLS_SERVER_CERT, "2.5.0"); break; } case IMAPOPT_TLS_CIPHER_LIST: { config_option_deprecate(opt, IMAPOPT_TLS_CIPHERS, "2.5.0"); break; } case IMAPOPT_TLS_KEY_FILE: { config_option_deprecate(opt, IMAPOPT_TLS_SERVER_KEY, "2.5.0"); break; } case IMAPOPT_TLSCACHE_DB: { config_option_deprecate(opt, IMAPOPT_TLS_SESSIONS_DB, "2.5.0"); break; } case IMAPOPT_TLSCACHE_DB_PATH: { config_option_deprecate(opt, IMAPOPT_TLS_SESSIONS_DB_PATH, "2.5.0"); break; } } } /* * Reset the global configuration to a virginal state. This is * only useful for unit tests. */ EXPORTED void config_reset(void) { enum imapopt opt; if (!config_filename) return; free((char *)config_filename); config_filename = NULL; if (config_servername != config_getstring(IMAPOPT_SERVERNAME)) free((char *)config_servername); config_servername = NULL; config_defpartition = NULL; config_mupdate_server = NULL; config_mupdate_config = 0; config_hashimapspool = 0; config_virtdomains = 0; config_defdomain = NULL; config_auditlog = 0; config_serverinfo = 0; config_maxquoted = 0; config_maxword = 0; config_qosmarking = 0; config_debug = 0; /* reset all the options */ for (opt = IMAPOPT_ZERO; opt < IMAPOPT_LAST; opt++) { if (imapopts[opt].t == OPT_STRING && (imapopts[opt].seen || (imapopts[opt].def.s && !strncasecmp(imapopts[opt].def.s, "{configdirectory}", 17)))) free((char *)imapopts[opt].val.s); memcpy(&imapopts[opt].val, &imapopts[opt].def, sizeof(imapopts[opt].val)); imapopts[opt].seen = 0; } config_dir = NULL; /* free the overflow table */ free_hash_table(&confighash, free); } static const unsigned char qos[] = { /* cs0..cs7 */ 0x00, 0x20, 0x40, 0x60, 0x80, 0xa0, 0xc0, 0xe0, /* af11..af13 */ 0x28, 0x30, 0x38, /* af21..af23 */ 0x48, 0x50, 0x58, /* af31..af33 */ 0x68, 0x70, 0x78, /* af41..af43 */ 0x88, 0x90, 0x98, /* ef */ 0xb8 }; EXPORTED void config_read(const char *alt_config, const int config_need_data) { enum imapopt opt = IMAPOPT_ZERO; char buf[4096]; char *p; int ival; /* xxx this is leaked, this may be able to be better in 2.2 (cyrus_done) */ if (alt_config) config_filename = xstrdup(alt_config); else config_filename = xstrdup(CONFIG_FILENAME); if (!construct_hash_table(&confighash, CONFIGHASHSIZE, 1)) { fatal("could not construct configuration hash table", EC_CONFIG); } if (!construct_hash_table(&includehash, INCLUDEHASHSIZE, 1)) { fatal("could not construct include file hash table", EC_CONFIG); } config_read_file(config_filename); free_hash_table(&includehash, NULL); /* Check configdirectory config option */ if (!config_dir) { fatal("configdirectory option not specified in configuration file", EC_CONFIG); } for (opt = IMAPOPT_ZERO; opt < IMAPOPT_LAST; opt++) { /* Scan options to see if we need to replace {configdirectory} */ /* xxx need to scan overflow options as well! */ /* Skip options that have a NULL value, aren't strings, or * are the configdirectory option */ if ( !imapopts[opt].val.s || imapopts[opt].t != OPT_STRING || opt == IMAPOPT_CONFIGDIRECTORY ) { continue; } /* We use some magic numbers here, * 17 is the length of "{configdirectory}", * 16 is one less than that length, so that the replacement string * that is malloced has room for the '\0' */ if (!strncasecmp(imapopts[opt].val.s,"{configdirectory}",17)) { const char *str = imapopts[opt].val.s; char *newstring = xmalloc(strlen(config_dir) + strlen(str) - 16); char *freeme = NULL; /* we need to replace this string, will we need to free * the current value? -- only if we've actually seen it in * the config file. */ if (imapopts[opt].seen) freeme = (char *)str; /* Build replacement string from configdirectory option */ strcpy(newstring, config_dir); strcat(newstring, str + 17); imapopts[opt].val.s = newstring; if (freeme) free(freeme); } } for (opt = IMAPOPT_ZERO; opt < IMAPOPT_LAST; opt++) { /* See if the option configured is a part of the deprecated hash. */ if (imapopts[opt].seen) { config_option_deprecated(opt); } } /* Look up default partition */ config_defpartition = config_getstring(IMAPOPT_DEFAULTPARTITION); for (p = (char *)config_defpartition; p && *p; p++) { if (!Uisalnum(*p)) { syslog(LOG_ERR, "INVALID defaultpartition: %s", config_defpartition); fatal("defaultpartition option contains non-alnum character", EC_CONFIG); } if (Uisupper(*p)) *p = tolower((unsigned char) *p); } config_mupdate_server = config_getstring(IMAPOPT_MUPDATE_SERVER); if (config_mupdate_server) { config_mupdate_config = config_getenum(IMAPOPT_MUPDATE_CONFIG); } if (config_need_data & CONFIG_NEED_PARTITION_DATA) { int found = 0; if (config_defpartition) { /* see if defaultpartition is specified properly */ if (config_partitiondir(config_defpartition)) found = 1; } else if ((config_mupdate_config == IMAP_ENUM_MUPDATE_CONFIG_STANDARD) && !config_getstring(IMAPOPT_PROXYSERVERS)) { found = 1; /* don't need partitions on the frontend */ } else { /* see if we have ANY partition- options */ config_foreachoverflowstring(config_ispartition, &found); } if (!found) { snprintf(buf, sizeof(buf), "partition-%s option not specified in configuration file", config_defpartition ? config_defpartition : ""); fatal(buf, EC_CONFIG); } } /* look up mailbox hashing */ config_hashimapspool = config_getswitch(IMAPOPT_HASHIMAPSPOOL); /* are we supporting virtual domains? */ config_virtdomains = config_getenum(IMAPOPT_VIRTDOMAINS); config_defdomain = config_getstring(IMAPOPT_DEFAULTDOMAIN); /* are we auditlogging */ config_auditlog = config_getswitch(IMAPOPT_AUDITLOG); /* are we doing I/O logging */ config_iolog = config_getswitch(IMAPOPT_IOLOG); if (config_iolog) { if (access("/proc/self/io", R_OK)) { config_iolog = 0; syslog(LOG_WARNING,"iolog directive needs a kernel built with I/O accounting"); } } /* look up the hostname and info we should present to the user */ config_servername = config_getstring(IMAPOPT_SERVERNAME); if (!config_servername) { config_servername = xmalloc(sizeof(char) * 256); gethostname((char *) config_servername, 256); } config_serverinfo = config_getenum(IMAPOPT_SERVERINFO); /* set some limits */ config_maxquoted = config_getint(IMAPOPT_MAXQUOTED); config_maxword = config_getint(IMAPOPT_MAXWORD); ival = config_getenum(IMAPOPT_QOSMARKING); config_qosmarking = qos[ival]; /* allow debug logging */ config_debug = config_getswitch(IMAPOPT_DEBUG); } #define GROWSIZE 4096 static void config_read_file(const char *filename) { FILE *infile = NULL; enum imapopt opt = IMAPOPT_ZERO; int lineno = 0; char *buf, errbuf[1024]; const char *cyrus_path; unsigned bufsize, len; char *p, *q, *key, *fullkey, *srvkey, *val, *newval; int service_specific; int idlen = (config_ident ? strlen(config_ident) : 0); bufsize = GROWSIZE; buf = xmalloc(bufsize); /* read in config file Check if we have CYRUS_PREFIX defined, and then use that config */ cyrus_path = getenv("CYRUS_PREFIX"); if (cyrus_path) { strlcpy(buf, cyrus_path, bufsize); strlcat(buf, filename, bufsize); infile = fopen(buf, "r"); } if (!infile) infile = fopen(filename, "r"); if (!infile) { snprintf(buf, bufsize, "can't open configuration file %s: %s", filename, strerror(errno)); fatal(buf, EC_CONFIG); } /* check to see if we've already read this file */ if (hash_lookup(filename, &includehash)) { snprintf(buf, bufsize, "configuration file %s included twice", filename); fatal(buf, EC_CONFIG); } else { hash_insert(filename, (void*) 0xDEADBEEF, &includehash); } len = 0; while (fgets(buf+len, bufsize-len, infile)) { if (buf[len]) { len = strlen(buf); if (buf[len-1] == '\n') { /* end of line */ buf[--len] = '\0'; if (len && buf[len-1] == '\\') { /* line continuation */ len--; lineno++; continue; } } else if (!feof(infile) && len == bufsize-1) { /* line is longer than the buffer */ bufsize += GROWSIZE; buf = xrealloc(buf, bufsize); continue; } } len = 0; lineno++; service_specific = 0; /* remove leading whitespace */ for (p = buf; *p && Uisspace(*p); p++); /* skip comments */ if (!*p || *p == '#') continue; fullkey = key = p; if (*p == '@') p++; /* allow @ as the first char (for directives) */ while (*p && (Uisalnum(*p) || *p == '-' || *p == '_')) { if (Uisupper(*p)) *p = tolower((unsigned char) *p); p++; } if (*p != ':') { snprintf(errbuf, sizeof(errbuf), "invalid option name on line %d of configuration file %s", lineno, filename); fatal(errbuf, EC_CONFIG); } *p++ = '\0'; /* remove leading whitespace */ while (*p && Uisspace(*p)) p++; /* remove trailing whitespace */ for (q = p + strlen(p) - 1; q > p && Uisspace(*q); q--) { *q = '\0'; } if (!*p) { snprintf(errbuf, sizeof(errbuf), "empty option value on line %d of configuration file", lineno); fatal(errbuf, EC_CONFIG); } srvkey = NULL; /* Look for directives */ if (key[0] == '@') { if (!strcasecmp(key, "@include")) { config_read_file(p); continue; } else { snprintf(errbuf, sizeof(errbuf), "invalid directive on line %d of configuration file %s", lineno, filename); fatal(errbuf, EC_CONFIG); } } /* Find if there is a _ prefix */ if (config_ident && !strncasecmp(key, config_ident, idlen) && key[idlen] == '_') { /* skip service_ prefix */ srvkey = key + idlen + 1; } /* look for a service_ prefix match in imapopts */ if (srvkey) { for (opt = IMAPOPT_ZERO; opt < IMAPOPT_LAST; opt++) { if (!strcasecmp(imapopts[opt].optname, srvkey)) { key = srvkey; service_specific = 1; break; } } } /* Did not find a service_ specific match, try looking for an * exact match */ if (!service_specific) { for (opt = IMAPOPT_ZERO; opt < IMAPOPT_LAST; opt++) { if (!strcasecmp(imapopts[opt].optname, key)) { break; } } } /* If both of those loops failed, it goes verbatim into the * overflow hash table. */ if (opt < IMAPOPT_LAST) { /* Okay, we know about this configure option. * So first check that we have either * 1. not seen it * 2. seen its generic form, but this is a service specific form * * If we have already seen a service-specific form, and this is * a generic form, just skip it and don't moan. */ if ( (imapopts[opt].seen == 1 && !service_specific) || (imapopts[opt].seen == 2 && service_specific) ) { sprintf(errbuf, "option '%s' was specified twice in config file (second occurance on line %d)", fullkey, lineno); fatal(errbuf, EC_CONFIG); } else if (imapopts[opt].seen == 2 && !service_specific) { continue; } /* If we've seen it already, we're replacing it, so we need * to free the current string if there is one */ if (imapopts[opt].seen && imapopts[opt].t == OPT_STRING) free((char *)imapopts[opt].val.s); if (service_specific) imapopts[opt].seen = 2; else imapopts[opt].seen = 1; /* this is a known option */ switch (imapopts[opt].t) { case OPT_STRING: { imapopts[opt].val.s = xstrdup(p); if (opt == IMAPOPT_CONFIGDIRECTORY) config_dir = imapopts[opt].val.s; break; } case OPT_INT: { long val; char *ptr; val = strtol(p, &ptr, 0); if (!ptr || *ptr != '\0') { /* error during conversion */ sprintf(errbuf, "non-integer value for %s in line %d", imapopts[opt].optname, lineno); fatal(errbuf, EC_CONFIG); } imapopts[opt].val.i = val; break; } case OPT_SWITCH: { if (*p == '0' || *p == 'n' || (*p == 'o' && p[1] == 'f') || *p == 'f') { imapopts[opt].val.b = 0; } else if (*p == '1' || *p == 'y' || (*p == 'o' && p[1] == 'n') || *p == 't') { imapopts[opt].val.b = 1; } else { /* error during conversion */ sprintf(errbuf, "non-switch value for %s in line %d", imapopts[opt].optname, lineno); fatal(errbuf, EC_CONFIG); } break; } case OPT_ENUM: case OPT_STRINGLIST: case OPT_BITFIELD: { const struct enum_option_s *e; /* zero the value */ memset(&imapopts[opt].val, 0, sizeof(imapopts[opt].val)); /* q is already at EOS so we'll process entire the string as one value unless told otherwise */ if (imapopts[opt].t == OPT_ENUM) { /* normalize on/off values */ if (!strcmp(p, "1") || !strcmp(p, "yes") || !strcmp(p, "t") || !strcmp(p, "true")) { p = "on"; } else if (!strcmp(p, "0") || !strcmp(p, "no") || !strcmp(p, "f") || !strcmp(p, "false")) { p = "off"; } } else if (imapopts[opt].t == OPT_BITFIELD) { /* split the string into separate values */ q = p; } while (*p) { /* find the end of the first value */ for (; *q && !Uisspace(*q); q++); if (*q) *q++ = '\0'; /* see if its a legal value */ for (e = imapopts[opt].enum_options; e->name && strcmp(e->name, p); e++); if (!e->name) { /* error during conversion */ sprintf(errbuf, "invalid value '%s' for %s in line %d", p, imapopts[opt].optname, lineno); fatal(errbuf, EC_CONFIG); } else if (imapopts[opt].t == OPT_STRINGLIST) imapopts[opt].val.s = e->name; else if (imapopts[opt].t == OPT_ENUM) imapopts[opt].val.e = e->val; else imapopts[opt].val.x |= e->val; /* find the start of the next value */ for (p = q; *p && Uisspace(*p); p++); q = p; } break; } case OPT_NOTOPT: default: abort(); } } else { /* check to make sure it's valid for overflow */ /* that is, partition names and anything that might be * used by SASL */ /* xxx this would be nice if it wasn't for other services who might be sharing this config file and whose names we cannot predict if (strncasecmp(key,"sasl_",5) && strncasecmp(key,"partition-",10)) { sprintf(errbuf, "option '%s' is unknown on line %d of config file", fullkey, lineno); fatal(errbuf, EC_CONFIG); } */ /* Put it in the overflow hash table */ newval = xstrdup(p); val = hash_insert(key, newval, &confighash); if (val != newval) { snprintf(errbuf, sizeof(errbuf), "option '%s' was specified twice in config file (second occurance on line %d)", fullkey, lineno); fatal(errbuf, EC_CONFIG); } } } fclose(infile); free(buf); } cyrus-imapd-2.5.10/lib/acl_afs.c0000644000175000017500000001456213001236020013252 00000000000000/* * AFS-style ACL interpretation * * The user gets the cumulative set of rights granted to identifiers * of which they are a member. Then, the cumulative set of negative * rights (rights granted to identifiers with '-' prepended to an * identifier of which they are a member) are removed. * */ /* * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include #include #include #include #include "acl.h" #include "auth.h" #include "xmalloc.h" /* * Calculate the set of rights the user in 'auth_state' has in the ACL 'acl'. * 'acl' must be writable, but is restored to its original condition. */ EXPORTED int cyrus_acl_myrights(struct auth_state *auth_state, const char *origacl) { char *acl = xstrdupsafe(origacl); char *thisid, *rights, *nextid; long acl_positive = 0, acl_negative = 0; long *acl_ptr; for (thisid = acl; *thisid; thisid = nextid) { acl_ptr = &acl_positive; rights = strchr(thisid, '\t'); if (!rights) { break; } *rights++ = '\0'; nextid = strchr(rights, '\t'); if (!nextid) { rights[-1] = '\t'; break; } *nextid++ = '\0'; if (*thisid == '-') { acl_ptr = &acl_negative; thisid++; } if (auth_memberof(auth_state, thisid)) { *acl_ptr |= cyrus_acl_strtomask(rights); } } free(acl); return acl_positive & ~acl_negative; } /* * Modify the ACL pointed to by 'acl' to make the rights granted to * 'identifier' the set specified in the mask 'access'. The pointer * pointed to by 'acl' must have been obtained from malloc(). */ EXPORTED int cyrus_acl_set(char **acl, const char *identifier, int mode, int access, cyrus_acl_canonproc_t *canonproc, void *canonrock) { const char *canonid; char *newidentifier = 0; char *newacl; char *thisid, *nextid; int oldaccess = 0; char *rights; if (!identifier) return -1; /* Convert 'identifier' into canonical form */ canonid = auth_canonifyid(*identifier == '-' ? identifier+1 : identifier, 0); if (canonid) { if (*identifier == '-') { newidentifier = xmalloc(strlen(canonid)+2); newidentifier[0] = '-'; strcpy(newidentifier+1, canonid); identifier = newidentifier; } else { identifier = canonid; } } else if (access != 0L) { return -1; } else { /* trying to delete invalid/non-existent identifier */ } /* Find any existing entry for 'identifier' in 'acl' */ for (thisid = nextid = *acl; *thisid; thisid = nextid) { rights = strchr(thisid, '\t'); if (!rights) { /* ACK, nuke trailing garbage */ *thisid = '\0'; nextid = thisid; break; } *rights++ = '\0'; nextid = strchr(rights, '\t'); if (!nextid) { /* ACK, nuke trailing garbage */ *thisid = '\0'; nextid = thisid; break; } *nextid++ = '\0'; if (strcmp(identifier, thisid) == 0) { oldaccess = cyrus_acl_strtomask(rights); break; } rights[-1] = '\t'; nextid[-1] = '\t'; } switch (mode) { case ACL_MODE_SET: break; case ACL_MODE_ADD: access |= oldaccess; break; case ACL_MODE_REMOVE: access = oldaccess & ~access; break; } if (canonproc) { if (*identifier == '-') access = ~(canonproc(canonrock, identifier+1, ~access)); else access = canonproc(canonrock, identifier, access); } if (access == 0L) { /* Remove any existing entry for 'identifier'. Special case: When we try to delete an invalid/non-existent identifier, both 'thisid' and 'nextid' point to the end of *acl. */ newacl = xmalloc(strlen(*acl) + strlen(nextid) - strlen(thisid) + 1); /* Copy existing ACLs without the current identifier. Note: The buffer will not be zero terminated. */ strncpy(newacl, *acl, (thisid - *acl)); /* Append the remaining ACL string. Zero-terminates the string. */ strcpy(newacl + (thisid - *acl), nextid); free(*acl); *acl = newacl; } else { /* Replace any existing entry for 'identifier' */ newacl = xmalloc((thisid - *acl) + strlen(identifier) + 40 + strlen(nextid)); strncpy(newacl, *acl, (thisid - *acl)); strcpy(newacl + (thisid - *acl), identifier); strcat(newacl, "\t"); (void) cyrus_acl_masktostr(access, newacl + strlen(newacl)); strcat(newacl, "\t"); strcat(newacl, nextid); free(*acl); *acl = newacl; } if (newidentifier) free(newidentifier); return 0; } /* * Remove any entry for 'identifier' in the ACL pointed to by 'acl'. * The pointer pointed to by 'acl' must have been obtained from malloc(). */ EXPORTED int cyrus_acl_remove(char **acl, const char *identifier, cyrus_acl_canonproc_t canonproc, void *canonrock) { return cyrus_acl_set(acl, identifier, ACL_MODE_SET, 0, canonproc, canonrock); } cyrus-imapd-2.5.10/lib/bsearch.c0000644000175000017500000001653113001236020013267 00000000000000/* bsearch.c -- binary search newline-separated fields in memory * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include #include #include "bsearch.h" #include "util.h" /* Case-dependent comparison converter. * Treats \r and \t as end-of-string and treats '.' lower than * everything else. */ #define TOCOMPARE(c) (convert_to_compare[(unsigned char)(c)]) static unsigned char convert_to_compare[256] = { 0x00, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0a, 0x01, 0x01, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f, 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17, 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f, 0x20, 0x21, 0x22, 0x23, 0x24, 0x25, 0x26, 0x27, 0x28, 0x29, 0x2a, 0x2b, 0x2c, 0x2d, 0x02, 0x2f, 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37, 0x38, 0x39, 0x3a, 0x3b, 0x3c, 0x3d, 0x3e, 0x3f, 0x40, 'A', 'B', 'C', 'D', 'E', 'F', 'G', 'H', 'I', 'J', 'K', 'L', 'M', 'N', 'O', 'P', 'Q', 'R', 'S', 'T', 'U', 'V', 'W', 'X', 'Y', 'Z', 0x5b, 0x5c, 0x5d, 0x5e, 0x5f, 0x60, 'a', 'b', 'c', 'd', 'e', 'f', 'g', 'h', 'i', 'j', 'k', 'l', 'm', 'n', 'o', 'p', 'q', 'r', 's', 't', 'u', 'v', 'w', 'x', 'y', 'z', 0x7b, 0x7c, 0x7d, 0x7e, 0x7f, 0x80, 0x81, 0x82, 0x83, 0x84, 0x85, 0x86, 0x87, 0x88, 0x89, 0x8a, 0x8b, 0x8c, 0x8d, 0x8e, 0x8f, 0x90, 0x91, 0x92, 0x93, 0x94, 0x95, 0x96, 0x97, 0x98, 0x99, 0x9a, 0x9b, 0x9c, 0x9d, 0x9e, 0x9f, 0xa0, 0xa1, 0xa2, 0xa3, 0xa4, 0xa5, 0xa6, 0xa7, 0xa8, 0xa9, 0xaa, 0xab, 0xac, 0xad, 0xae, 0xaf, 0xb0, 0xb1, 0xb2, 0xb3, 0xb4, 0xb5, 0xb6, 0xb7, 0xb8, 0xb9, 0xba, 0xbb, 0xbc, 0xbd, 0xbe, 0xbf, 0xc0, 0xc1, 0xc2, 0xc3, 0xc4, 0xc5, 0xc6, 0xc7, 0xc8, 0xc9, 0xca, 0xcb, 0xcc, 0xcd, 0xce, 0xcf, 0xd0, 0xd1, 0xd2, 0xd3, 0xd4, 0xd5, 0xd6, 0xd7, 0xd8, 0xd9, 0xda, 0xdb, 0xdc, 0xdd, 0xde, 0xdf, 0xe0, 0xe1, 0xe2, 0xe3, 0xe4, 0xe5, 0xe6, 0xe7, 0xe8, 0xe9, 0xea, 0xeb, 0xec, 0xed, 0xee, 0xef, 0xf0, 0xf1, 0xf2, 0xf3, 0xf4, 0xf5, 0xf6, 0xf7, 0xf8, 0xf9, 0xfa, 0xfb, 0xfc, 0xfd, 0xfe, 0xff }; /* * Search for a line starting with 'word'. The search respects case. * The search is performed in 'base', which is of length 'len'. * 'hint' gives a idea of where to start looking. * * On success, the offset in 'base' of the found line is returned and * the length of the found line is put in the unsigned long pointed to * by 'linelenp'. On failure, the offset in 'base' of where a new line should * be inserted is returned and zero is put in the unsigned long pointed to * by 'linelenp'. */ HIDDEN int bsearch_mem_mbox(const char *word, const char *base, unsigned long len, unsigned long hint, unsigned long *linelenp) { int firstsearch = 1; unsigned long start = 0, end = len - 1, mid, offset; unsigned long linelen; long n; int cmp = 0; const char *wordp, *p; while (start < end + 1) { if (firstsearch) { /* Use hint supplied by caller */ firstsearch = 0; mid = offset = hint; if (mid <= start || mid > end) mid = offset = start; } else { /* Calculate position of middle of this range */ offset = mid = (start + end)/2; } if (mid) { p = memchr(base+mid, '\n', (end + 1) - mid); if (!p) { end = mid - 1; continue; } offset = p - base + 1; } p = memchr(base+offset, '\n', len-offset); if (p) { linelen = p - (base+offset) + 1; } else { end = mid - 1; continue; } n = linelen; wordp = word; p = base+offset; while (n-- > 0 && (cmp = TOCOMPARE(*wordp) - TOCOMPARE(*p)) == 0) { wordp++; p++; } if (n >= 0 && !*wordp) { cmp = TOCOMPARE('\t') - TOCOMPARE(*p); } else if (!cmp) { cmp = 1; } if (!cmp) { if (linelenp) *linelenp = linelen; return offset; } if (cmp < 0) { if (mid == 0) break; end = mid - 1; } else { start = offset + 1; } } /* Word was not found. Return offset where word should be inserted */ if (linelenp) *linelenp = 0; if (start > len) return len; if (!start) return 0; p = memchr(base+start, '\n', len-start); return p - base + 1; } EXPORTED int bsearch_compare_mbox(const char *s1, const char *s2) { int cmp; char c2; for (;;) { if ((c2 = *s2) == 0) { return (unsigned char)*s1; } cmp = TOCOMPARE(*s1) - TOCOMPARE(c2); if (cmp) return cmp; if (TOCOMPARE(c2) == TOCOMPARE('\t')) { return 0; } s1++; s2++; } } HIDDEN int bsearch_ncompare_mbox(const char *s1, int l1, const char *s2, int l2) { int min = l1 < l2 ? l1 : l2; int cmp = 0; while (min-- > 0 && (cmp = TOCOMPARE(*s1) - TOCOMPARE(*s2)) == 0) { s1++; s2++; } if (min >= 0) { return cmp; } else { if (l2 > l1) return -1; else if (l1 > l2) return 1; else return 0; } } /* direct from the qsort manpage */ EXPORTED int cmpstringp_raw(const void *p1, const void *p2) { /* The actual arguments to this function are "pointers to pointers to char", but strcmp(3) arguments are "pointers to char", hence the following cast plus dereference */ return strcmpsafe(* (char * const *) p1, * (char * const *) p2); } EXPORTED int cmpstringp_mbox(const void *p1, const void *p2) { const char *s1 = *((const char **)p1); const char *s2 = *((const char **)p2); int cmp = 0; while (*s1 && *s2 && (cmp = TOCOMPARE(*s1) - TOCOMPARE(*s2)) == 0) { s1++; s2++; } return cmp; } HIDDEN int bsearch_ncompare_raw(const char *s1, int l1, const char *s2, int l2) { int min = l1 < l2 ? l1 : l2; int r = memcmp(s1, s2, min); if (!r) { if (l1 > l2) r = 1; else if (l2 > l1) r = -1; } return r; } cyrus-imapd-2.5.10/lib/signals.h0000644000175000017500000000440213001236020013317 00000000000000/* signals.h -- signal handling functions to allow clean shutdown * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #ifndef INCLUDED_SIGNALS_H #define INCLUDED_SIGNALS_H #include #include typedef void shutdownfn(int); void signals_add_handlers(int alarm); void signals_reset_sighup_handler(int restartable); void signals_set_shutdown(shutdownfn *s); int signals_poll(void); int signals_select(int nfds, fd_set *rfds, fd_set *wfds, fd_set *efds, struct timeval *tout); #endif /* INCLUDED_SIGNALS_H */ cyrus-imapd-2.5.10/lib/xstrlcpy.c0000644000175000017500000000460113001236020013543 00000000000000/* xmalloc.c -- Allocation package that calls fatal() when out of memory * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include "xstrlcpy.h" #ifndef HAVE_STRLCPY /* strlcpy -- copy string smartly. * * i believe/hope this is compatible with the BSD strlcpy(). */ EXPORTED size_t strlcpy(char *dst, const char *src, size_t len) { size_t n; if (len <= 0) { /* we can't do anything ! */ return strlen(src); } /* assert(len >= 1); */ for (n = 0; n < len-1; n++) { if ((dst[n] = src[n]) == '\0') break; } if (n >= len-1) { /* ran out of space */ dst[n] = '\0'; while(src[n]) n++; } return n; } #endif cyrus-imapd-2.5.10/lib/arrayu64.h0000644000175000017500000000633413001236020013342 00000000000000/* arrayu64.h - an expanding array of 64 bit unsigned integers * * Copyright (c) 1994-2011 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. * * Author: Greg Banks * Start Date: 2011/01/11 */ #ifndef __CYRUS_ARRAYU64_H__ #define __CYRUS_ARRAYU64_H__ #include #include "util.h" typedef struct { int count; int alloc; uint64_t *data; } arrayu64_t; #define ARRAYU64_INITIALIZER { 0, 0, NULL } #define arrayu64_init(sa) (memset((sa), 0, sizeof(arrayu64_t))) void arrayu64_fini(arrayu64_t *); arrayu64_t *arrayu64_new(void); void arrayu64_free(arrayu64_t *); int arrayu64_append(arrayu64_t *, uint64_t); int arrayu64_add(arrayu64_t *, uint64_t); int arrayu64_find(arrayu64_t *, uint64_t, int start); void arrayu64_set(arrayu64_t *, int idx, uint64_t); void arrayu64_insert(arrayu64_t *, int idx, uint64_t); uint64_t arrayu64_remove(arrayu64_t *, int idx); /* returns number removed */ int arrayu64_remove_all(arrayu64_t *, uint64_t); uint64_t arrayu64_nth(const arrayu64_t *, int idx); void arrayu64_truncate(arrayu64_t *, int newlen); arrayu64_t *arrayu64_dup(const arrayu64_t *); uint64_t arrayu64_max(const arrayu64_t *); #define arrayu64_shift(sa) arrayu64_remove((sa), 0) #define arrayu64_unshift(sa, s) arrayu64_insert((sa), 0, (s)) #define arrayu64_pop(sa) arrayu64_remove((sa), -1) #define arrayu64_push(sa, s) arrayu64_append((sa), (s)) void arrayu64_sort(arrayu64_t *, compar_t *); void arrayu64_uniq(arrayu64_t *); int arrayu64_size(const arrayu64_t *); #endif /* __CYRUS_ARRAYU64_H__ */ cyrus-imapd-2.5.10/lib/xmalloc.c0000644000175000017500000000670413001236020013320 00000000000000/* xmalloc.c -- Allocation package that calls fatal() when out of memory * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include #include #include #include #include "xmalloc.h" #include "exitcodes.h" EXPORTED void* xmalloc(unsigned size) { void *ret; ret = malloc(size); if (ret != NULL) return ret; fatal("Virtual memory exhausted", EC_TEMPFAIL); return 0; /*NOTREACHED*/ } EXPORTED void* xzmalloc(unsigned size) { void *ret; ret = malloc(size); if (ret != NULL) { memset(ret, 0, size); return ret; } fatal("Virtual memory exhausted", EC_TEMPFAIL); return 0; /*NOTREACHED*/ } EXPORTED void *xcalloc(unsigned nmemb, unsigned size) { return xzmalloc(nmemb * size); } EXPORTED void *xrealloc (void* ptr, unsigned size) { void *ret; /* xrealloc (NULL, size) behaves like xmalloc (size), as in ANSI C */ ret = (!ptr ? malloc (size) : realloc (ptr, size)); if (ret != NULL) return ret; fatal("Virtual memory exhausted", EC_TEMPFAIL); return 0; /*NOTREACHED*/ } EXPORTED char *xstrdup(const char* str) { char *p = xmalloc(strlen(str)+1); strcpy(p, str); return p; } /* return a malloced "" if NULL is passed */ EXPORTED char *xstrdupsafe(const char *str) { return str ? xstrdup(str) : xstrdup(""); } /* return NULL if NULL is passed */ EXPORTED char *xstrdupnull(const char *str) { return str ? xstrdup(str) : NULL; } EXPORTED char *xstrndup(const char* str, unsigned len) { char *p = xmalloc(len+1); if (len) strncpy(p, str, len); p[len] = '\0'; return p; } EXPORTED void *xmemdup(const void *ptr, unsigned size) { void *p = xmalloc(size); memcpy(p, ptr, size); return p; } cyrus-imapd-2.5.10/lib/mkgmtime.h0000644000175000017500000000410312772415051013510 00000000000000/* mkgmtime.h -- make a time_t from a gmtime struct tm * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #ifndef INCLUDED_MKGMTIME_H #define INCLUDED_MKGMTIME_H #ifndef P #ifdef __STDC__ #define P(x) x #else #define P(x) () #endif #endif #include extern time_t mkgmtime P((struct tm * const tmp)); #endif /* INCLUDED_MKGMTIME_H */ cyrus-imapd-2.5.10/lib/signals.c0000644000175000017500000001707313001236020013322 00000000000000/* signals.c -- signal handling functions to allow clean shutdown * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ #include #include #include #include #include #include #include #include "signals.h" #include "xmalloc.h" #include "exitcodes.h" #include "util.h" #ifndef _NSIG #define _NSIG 65 #endif static volatile sig_atomic_t gotsignal[_NSIG]; static volatile pid_t killer_pid; static void sighandler(int sig, siginfo_t *si, void *ucontext __attribute__((unused))) { if (sig < 1 || sig >= _NSIG) sig = _NSIG-1; gotsignal[sig] = 1; /* remember a process that sent us a fatal signal */ if ((sig == SIGINT || sig == SIGQUIT || sig == SIGTERM) && si && si->si_code == SI_USER) killer_pid = si->si_pid; } EXPORTED void signals_add_handlers(int alarm) { struct sigaction action; memset(&action, 0, sizeof(action)); sigemptyset(&action.sa_mask); action.sa_flags = 0; #ifdef SA_RESETHAND action.sa_flags |= SA_RESETHAND; #endif action.sa_sigaction = sighandler; action.sa_flags |= SA_SIGINFO; /* SIGALRM used as a syscall timeout, so we don't set SA_RESTART */ if (alarm && sigaction(SIGALRM, &action, NULL) < 0) { fatal("unable to install signal handler for SIGALRM", EC_TEMPFAIL); } /* no restartable SIGQUIT thanks */ if (sigaction(SIGQUIT, &action, NULL) < 0) fatal("unable to install signal handler for SIGQUIT", EC_TEMPFAIL); if (sigaction(SIGINT, &action, NULL) < 0) fatal("unable to install signal handler for SIGINT", EC_TEMPFAIL); if (sigaction(SIGTERM, &action, NULL) < 0) fatal("unable to install signal handler for SIGTERM", EC_TEMPFAIL); signals_reset_sighup_handler(1); } EXPORTED void signals_reset_sighup_handler(int restartable) { struct sigaction action; memset(&action, 0, sizeof(action)); sigemptyset(&action.sa_mask); action.sa_flags = 0; #ifdef SA_RESTART if (restartable) { action.sa_flags |= SA_RESTART; } #endif action.sa_sigaction = sighandler; action.sa_flags |= SA_SIGINFO; if (sigaction(SIGHUP, &action, NULL) < 0) fatal("unable to install signal handler for SIGHUP", EC_TEMPFAIL); } static shutdownfn *shutdown_cb = NULL; static int signals_in_shutdown = 0; EXPORTED void signals_set_shutdown(shutdownfn *s) { shutdown_cb = s; } /* Build a human-readable description of another process from just the * process id. On some platforms this is enough to tell us something * useful about the other process. Returns a new string which must be * free()d by the caller. */ static char *describe_process(pid_t pid) { #if defined(__linux__) int i; int fd; int n; char buf[1024+32]; char cmdline[1024]; snprintf(buf, sizeof(buf), "/proc/%d/cmdline", (int)pid); cmdline[0] = '\0'; fd = open(buf, O_RDONLY, 0); if (fd >= 0) { n = read(fd, cmdline, sizeof(cmdline)-1); if (n > 0) { if (!cmdline[n-1]) n--; /* ignore trailing nul */ for (i = 0 ; i < n ; i++) { if (cmdline[i] == '\0') cmdline[i] = ' '; } cmdline[n] = '\0'; } close(fd); } if (!cmdline[0]) strcpy(cmdline, "unknown"); snprintf(buf, sizeof(buf), "%d (%s)", (int)pid, cmdline); return xstrdup(buf); #else char buf[32]; snprintf(buf, sizeof(buf), "%d", (int)pid); return xstrdup(buf); #endif } static int signals_poll_mask(sigset_t *oldmaskp) { int sig; if (!signals_in_shutdown && (gotsignal[SIGINT] || gotsignal[SIGQUIT] || gotsignal[SIGTERM])) { if (killer_pid && killer_pid != getppid()) { /* whine in syslog if we were sent a graceful shutdown signal * by anyone other than the master process. */ char *desc = describe_process(killer_pid); syslog(LOG_NOTICE, "graceful shutdown initiated by " "unexpected process %s", desc); free(desc); } else { syslog(LOG_NOTICE, "graceful shutdown"); } if (oldmaskp) sigprocmask(SIG_SETMASK, oldmaskp, NULL); if (shutdown_cb) { signals_in_shutdown = 1; shutdown_cb(EC_TEMPFAIL); } else exit(EC_TEMPFAIL); } for (sig = 1 ; sig < _NSIG ; sig++) { if (gotsignal[sig]) return sig; } return 0; } EXPORTED int signals_poll(void) { return signals_poll_mask(NULL); } /* * Same interface as select() but closes the race between * select() blocking and delivery of some signficant signals * like SIGTERM. This is necessary to ensure clean shutdown * of Cyrus processes. */ EXPORTED int signals_select(int nfds, fd_set *rfds, fd_set *wfds, fd_set *efds, struct timeval *tout) { #if HAVE_PSELECT /* pselect() closes the race between SIGCHLD arriving * and select() sleeping for up to 10 seconds. */ struct timespec ts, *tsptr = NULL; sigset_t blocked; sigset_t oldmask; int saved_errno; int r; /* temporarily block all the signals we want * to be caught reliably */ sigemptyset(&blocked); sigaddset(&blocked, SIGCHLD); sigaddset(&blocked, SIGALRM); sigaddset(&blocked, SIGQUIT); sigaddset(&blocked, SIGINT); sigaddset(&blocked, SIGTERM); sigprocmask(SIG_BLOCK, &blocked, &oldmask); /* Those signals will not arrive now. Check to see if any * of them arrived before we blocked them */ signals_poll_mask(&oldmask); if (tout) { ts.tv_sec = tout->tv_sec; ts.tv_nsec = tout->tv_usec * 1000; tsptr = &ts; } /* pselect() allows the restartable signals to arrive */ r = pselect(nfds, rfds, wfds, efds, tsptr, &oldmask); if (r < 0 && (errno == EAGAIN || errno == EINTR)) signals_poll_mask(&oldmask); /* restore the old signal mask */ saved_errno = errno; sigprocmask(SIG_SETMASK, &oldmask, NULL); errno = saved_errno; return r; #else int r; r = select(nfds, rfds, wfds, efds, tout); if (r < 0 && (errno == EAGAIN || errno == EINTR)) signals_poll(); return r; #endif } cyrus-imapd-2.5.10/lib/md5.h0000644000175000017500000000335613001236020012353 00000000000000/* MD5.H - wrapper for MD5 message digest routines */ #ifndef _CYRUS_MD5_H_ #define _CYRUS_MD5_H_ 1 #ifdef HAVE_CONFIG_H #include #endif /* * This is gnarly, sorry :( We might have been configured to build * with OpenSSL, or we might not. Some older versions of OpenSSL * will drag in their own md5.h when we include , but * newer ones don't. The OpenSSL header might be included before or * after this header file is included. * * So, we *might* have a definition of the MD5_CTX structure from * OpenSSL, now or later, or not. * * LibSASL also has MD5 routines, declared in , and that * header also defines a MD5_CTX structure. So we can't include * both md5.h's, but we need one. * * So we explicitly include the OpenSSL md5.h if OpenSSL is configured * in, otherwise we fallback to the libSASL routines. Note that we * cannot build without libSASL anyway, so we don't need to fallback * any further. * * The MD5 API varies slightly from library to library. Here's a * description of the API that Cyrus is expecting and that we try * to provide on top of whatever the library has. * * typedef struct ... { ... } MD5_CTX; * void MD5Init(MD5_CTX *); * void MD5Update(MD5_CTX *, const void *data, size_t len); * void MD5Final(unsigned char[MD5_DIGEST_LENGTH], MD5_CTX *); */ #ifdef HAVE_SSL #include #define MD5Init MD5_Init #define MD5Update MD5_Update #define MD5Final MD5_Final #else #include #include #define MD5Init _sasl_MD5Init #define MD5Update _sasl_MD5Update #define MD5Final _sasl_MD5Final #endif /* !HAVE_SSL */ #ifndef MD5_DIGEST_LENGTH #define MD5_DIGEST_LENGTH 16 #endif #endif /* _CYRUS_MD5_H_ */ cyrus-imapd-2.5.10/lib/memmove.c0000644000175000017500000000424513001236020013324 00000000000000/* memmove.c -- replacement memmove() routine * Only handles overlapping strings when moving data upwards * * Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in * the documentation and/or other materials provided with the * distribution. * * 3. The name "Carnegie Mellon University" must not be used to * endorse or promote products derived from this software without * prior written permission. For permission or any legal * details, please contact * Carnegie Mellon University * Center for Technology Transfer and Enterprise Creation * 4615 Forbes Avenue * Suite 302 * Pittsburgh, PA 15213 * (412) 268-7393, fax: (412) 268-7395 * innovation@andrew.cmu.edu * * 4. Redistributions of any form whatsoever must retain the following * acknowledgment: * "This product includes software developed by Computing Services * at Carnegie Mellon University (http://www.cmu.edu/computing/)." * * CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY * AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE * FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN * AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */ /* for size_t */ #include void *memmove(void *s, const void *ct, size_t n) { char *c_s = s; const char *c_ct = ct; if (c_s <= c_ct) { while (n--) { *c_s++ = *c_ct++; } } else { while (n--) { c_s[n] = c_ct[n]; } } return s; } cyrus-imapd-2.5.10/lib/mkchartable.pl0000644000175000017500000003741513001236020014332 00000000000000#!/usr/bin/perl # # mkchartable.pl -- Generate character set mapping table # # Copyright (c) 1994-2008 Carnegie Mellon University. All rights reserved. # # Redistribution and use in source and binary forms, with or without # modification, are permitted provided that the following conditions # are met: # # 1. Redistributions of source code must retain the above copyright # notice, this list of conditions and the following disclaimer. # # 2. Redistributions in binary form must reproduce the above copyright # notice, this list of conditions and the following disclaimer in # the documentation and/or other materials provided with the # distribution. # # 3. The name "Carnegie Mellon University" must not be used to # endorse or promote products derived from this software without # prior written permission. For permission or any legal # details, please contact # Carnegie Mellon University # Center for Technology Transfer and Enterprise Creation # 4615 Forbes Avenue # Suite 302 # Pittsburgh, PA 15213 # (412) 268-7393, fax: (412) 268-7395 # innovation@andrew.cmu.edu # # 4. Redistributions of any form whatsoever must retain the following # acknowledgment: # "This product includes software developed by Computing Services # at Carnegie Mellon University (http://www.cmu.edu/computing/)." # # CARNEGIE MELLON UNIVERSITY DISCLAIMS ALL WARRANTIES WITH REGARD TO # THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY # AND FITNESS, IN NO EVENT SHALL CARNEGIE MELLON UNIVERSITY BE LIABLE # FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES # WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN # AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING # OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. use strict; use warnings; use IO::File; use Getopt::Long; my @maps; my $aliasfile; my %codemap; my $output; GetOptions( 'map|m=s' => \@maps, #strings 'aliases|a=s' => \$aliasfile, #string 'output|o=s' => \$output); #string open (OUTPUT, ">$output"); printheader(\@maps, \@ARGV); # first we parse the chartable unicode mappings and the fixes # file to build the unicode to search canonical form tables. foreach my $map (@maps) { readmapfile(\%codemap, $map); } # we follow any mappings repeatedly until nothing in the # table doesn't change any more mungemap(\%codemap); # then print out the translation tables printmap(\%codemap, $aliasfile); # XXX - should probably require all files that are # mentioned in the lookup table to be specified, # or this sucker aintn't gunna compile. foreach my $opt (@ARGV) { print "mkchartable: mapping $opt...\n"; my $table = readcharfile($opt); printtable($table, $opt); } printlookup(); close (OUTPUT); exit 0; sub usage { print "usage: mkchartable -m mapfile -o outputfile charsetfile...\n"; exit(1); } # Read a Unicode table, deriving useful mappings from it sub readmapfile { my ($codemap, $name) = @_; my $mapfile = IO::File->new($name, 'r') || die "Failed to open $name\n"; while (my $line = $mapfile->getline()) { chomp $line; $line =~ s/^\s+//; # strip leading space next if $line =~ m/^\#/; # comment next if $line eq ''; # blank my ($hexcode, $name, $category, $combiningclass, $bidicat, $decomposition, $decimal, $digit, $numeric, $mirroredchar, $uni1name, $comment, $upper, $lower, $title, @rest) = split ';', $line; my $code = hex($hexcode); # This is not RFC5051 if ($code != 32 and $category =~ m/^Z/) { $codemap->{$code}{chars} = [32]; # space next; } # has a mapping to titlecase $codemap->{$code}{title} = hex($title) if $title; # Compatability mapping, skip over the while ($decomposition ne '') { # This is not RFC5051 if ($decomposition =~ s/^<[^>]*>\s+//) { # Ignore compat mappings to SP followed by combining char $decomposition = '' if $decomposition =~ m/^0020 / } if ($decomposition =~ s/([0-9a-fA-F]+)\s*//) { push @{$codemap->{$code}{chars}}, hex($1); } } $codemap->{$code}{chars} ||= [$code]; } } # Perform the transitive closure on the unicode mapping table # Calculate translations for mappings sub mungemap { my ($codemap) = @_; my $total = keys %$codemap; my $changed; # Keep scanning the table until no changes are made do { $changed = 0; foreach my $code (sort { $a <=> $b } keys %$codemap) { my @new; my $chars = $codemap->{$code}{chars}; # check if there are any translations for the mapped chars foreach my $char (@$chars) { if ($codemap->{$char}) { my $newchars = $codemap->{$char}{chars}; push @new, @$newchars; } else { push @new, $char; } } # strip all whitespace, but put back one if nothing left if (grep { $_ == 32 } @new) { @new = grep { $_ != 32 } @new; @new = (32) unless @new; } # no change next if ("@new" eq "@$chars"); $changed++; $codemap->{$code}{chars} = \@new; } print "mkchartable: expanded unicode mappings... ($changed/$total)\n" if $changed; } while ($changed); print "mkchartable: building expansion table...\n"; print OUTPUT <