summaryrefslogtreecommitdiffstats
path: root/kspell2/plugins/ispell/tgood.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'kspell2/plugins/ispell/tgood.cpp')
-rw-r--r--kspell2/plugins/ispell/tgood.cpp810
1 files changed, 0 insertions, 810 deletions
diff --git a/kspell2/plugins/ispell/tgood.cpp b/kspell2/plugins/ispell/tgood.cpp
deleted file mode 100644
index 06fbc99ef..000000000
--- a/kspell2/plugins/ispell/tgood.cpp
+++ /dev/null
@@ -1,810 +0,0 @@
-/* vim: set sw=8: -*- Mode: C; tab-width: 8; indent-tabs-mode: t; c-basic-offset: 8 -*- */
-/* enchant
- * Copyright (C) 2003 Dom Lachowicz
- *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Lesser General Public
- * License as published by the Free Software Foundation; either
- * version 2.1 of the License, or (at your option) any later version.
- *
- * This library 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
- * Lesser General Public License for more details.
- *
- * You should have received a copy of the GNU Lesser General Public
- * License along with this library; if not, write to the
- * Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
- * Boston, MA 02110-1301, USA.
- *
- * In addition, as a special exception, Dom Lachowicz
- * gives permission to link the code of this program with
- * non-LGPL Spelling Provider libraries (eg: a MSFT Office
- * spell checker backend) and distribute linked combinations including
- * the two. You must obey the GNU Lesser General Public License in all
- * respects for all of the code used other than said providers. If you modify
- * this file, you may extend this exception to your version of the
- * file, but you are not obligated to do so. If you do not wish to
- * do so, delete this exception statement from your version.
- */
-
-/*
- * Copyright 1987, 1988, 1989, 1992, 1993, Geoff Kuenning, Granada Hills, CA
- * All rights reserved.
- *
- * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions
- * are met:
- *
- * 1. Redistributions of source code must retain the above copyright
- * notice, this list of conditions and the following disclaimer.
- * 2. Redistributions in binary form must reproduce the above copyright
- * notice, this list of conditions and the following disclaimer in the
- * documentation and/or other materials provided with the distribution.
- * 3. All modifications to the source code must be clearly marked as
- * such. Binary redistributions based on modified source code
- * must be clearly marked as modified versions in the documentation
- * and/or other materials provided with the distribution.
- * 4. All advertising materials mentioning features or use of this software
- * must display the following acknowledgment:
- * This product includes software developed by Geoff Kuenning and
- * other unpaid contributors.
- * 5. The name of Geoff Kuenning may not be used to endorse or promote
- * products derived from this software without specific prior
- * written permission.
- *
- * THIS SOFTWARE IS PROVIDED BY GEOFF KUENNING AND CONTRIBUTORS ``AS IS'' AND
- * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
- * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
- * ARE DISCLAIMED. IN NO EVENT SHALL GEOFF KUENNING OR CONTRIBUTORS BE LIABLE
- * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
- * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
- * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
- * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
- * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
- * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
- * SUCH DAMAGE.
- */
-
-/*
- * Table-driven version of good.c.
- *
- * Geoff Kuenning, July 1987
- */
-
-/*
- * $Log$
- * Revision 1.1 2004/01/31 16:44:12 zrusin
- * ISpell plugin.
- *
- * Revision 1.4 2003/08/14 17:51:29 dom
- * update license - exception clause should be Lesser GPL
- *
- * Revision 1.3 2003/07/28 20:40:28 dom
- * fix up the license clause, further win32-registry proof some directory getting functions
- *
- * Revision 1.2 2003/07/16 22:52:56 dom
- * LGPL + exception license
- *
- * Revision 1.1 2003/07/15 01:15:09 dom
- * ispell enchant backend
- *
- * Revision 1.2 2003/01/29 05:50:12 hippietrail
- *
- * Fixed my mess in EncodingManager.
- * Changed many C casts to C++ casts.
- *
- * Revision 1.1 2003/01/24 05:52:36 hippietrail
- *
- * Refactored ispell code. Old ispell global variables had been put into
- * an allocated structure, a pointer to which was passed to many functions.
- * I have now made all such functions and variables private members of the
- * ISpellChecker class. It was C OO, now it's C++ OO.
- *
- * I've fixed the makefiles and tested compilation but am unable to test
- * operation. Please back out my changes if they cause problems which
- * are not obvious or easy to fix.
- *
- * Revision 1.6 2003/01/06 18:48:42 dom
- * ispell cleanup, start of using new 'add' save features
- *
- * Revision 1.5 2002/09/19 05:31:20 hippietrail
- *
- * More Ispell cleanup. Conditional globals and DEREF macros are removed.
- * K&R function declarations removed, converted to Doxygen style comments
- * where possible. No code has been changed (I hope). Compiles for me but
- * unable to test.
- *
- * Revision 1.4 2002/09/17 03:03:31 hippietrail
- *
- * After seeking permission on the developer list I've reformatted all the
- * spelling source which seemed to have parts which used 2, 3, 4, and 8
- * spaces for tabs. It should all look good with our standard 4-space
- * tabs now.
- * I've concentrated just on indentation in the actual code. More prettying
- * could be done.
- * * NO code changes were made *
- *
- * Revision 1.3 2002/09/13 17:20:14 mpritchett
- * Fix more warnings for Linux build
- *
- * Revision 1.2 2001/05/12 16:05:42 thomasf
- * Big pseudo changes to ispell to make it pass around a structure rather
- * than rely on all sorts of gloabals willy nilly here and there. Also
- * fixed our spelling class to work with accepting suggestions once more.
- * This code is dirty, gross and ugly (not to mention still not supporting
- * multiple hash sized just yet) but it works on my machine and will no
- * doubt break other machines.
- *
- * Revision 1.1 2001/04/15 16:01:24 tomas_f
- * moving to spell/xp
- *
- * Revision 1.7 1999/10/20 06:03:56 sterwill
- * Changed C++-style comments to C-style comments in C code.
- *
- * Revision 1.6 1999/10/20 03:19:35 paul
- * Hacked ispell code to ignore any characters that don't fit in the lookup tables loaded from the dictionary. It ain't pretty, but at least we don't crash there any more.
- *
- * Revision 1.5 1999/04/13 17:12:51 jeff
- * Applied "Darren O. Benham" <[email protected]> spell check changes.
- * Fixed crash on Win32 with the new code.
- *
- * Revision 1.4 1998/12/29 14:55:33 eric
- *
- * I've doctored the ispell code pretty extensively here. It is now
- * warning-free on Win32. It also *works* on Win32 now, since I
- * replaced all the I/O calls with ANSI standard ones.
- *
- * Revision 1.4 1998/12/29 14:55:33 eric
- *
- * I've doctored the ispell code pretty extensively here. It is now
- * warning-free on Win32. It also *works* on Win32 now, since I
- * replaced all the I/O calls with ANSI standard ones.
- *
- * Revision 1.3 1998/12/28 23:11:30 eric
- *
- * modified spell code and integration to build on Windows.
- * This is still a hack.
- *
- * Actually, it doesn't yet WORK on Windows. It just builds.
- * SpellCheckInit is failing for some reason.
- *
- * Revision 1.2 1998/12/28 22:16:22 eric
- *
- * These changes begin to incorporate the spell checker into AbiWord. Most
- * of this is a hack.
- *
- * 1. added other/spell to the -I list in config/abi_defs
- * 2. replaced other/spell/Makefile with one which is more like
- * our build system.
- * 3. added other/spell to other/Makefile so that the build will now
- * dive down and build the spell check library.
- * 4. added the AbiSpell library to the Makefiles in wp/main
- * 5. added a call to SpellCheckInit in wp/main/unix/UnixMain.cpp.
- * This call is a HACK and should be replaced with something
- * proper later.
- * 6. added code to fv_View.cpp as follows:
- * whenever you double-click on a word, the spell checker
- * verifies that word and prints its status to stdout.
- *
- * Caveats:
- * 1. This will break the Windows build. I'm going to work on fixing it
- * now.
- * 2. This only works if your dictionary is in /usr/lib/ispell/american.hash.
- * The dictionary location is currently hard-coded. This will be
- * fixed as well.
- *
- * Anyway, such as it is, it works.
- *
- * Revision 1.1 1998/12/28 18:04:43 davet
- * Spell checker code stripped from ispell. At this point, there are
- * two external routines... the Init routine, and a check-a-word routine
- * which returns a boolean value, and takes a 16 bit char string.
- * The code resembles the ispell code as much as possible still.
- *
- * Revision 1.32 1994/11/02 06:56:16 geoff
- * Remove the anyword feature, which I've decided is a bad idea.
- *
- * Revision 1.31 1994/10/25 05:46:25 geoff
- * Add support for the FF_ANYWORD (affix applies to all words, even if
- * flag bit isn't set) flag option.
- *
- * Revision 1.30 1994/05/24 06:23:08 geoff
- * Don't create a hit if "allhits" is clear and capitalization
- * mismatches. This cures a bug where a word could be in the dictionary
- * and yet not found.
- *
- * Revision 1.29 1994/05/17 06:44:21 geoff
- * Add support for controlled compound formation and the COMPOUNDONLY
- * option to affix flags.
- *
- * Revision 1.28 1994/01/25 07:12:13 geoff
- * Get rid of all old RCS log lines in preparation for the 3.1 release.
- *
- */
-
-#include <ctype.h>
-#include <stdlib.h>
-#include <string.h>
-
-#include "ispell_checker.h"
-
-/*!
- * Check possible affixes
- *
- * \param word Word to be checked
- * \param ucword Upper-case-only copy of word
- * \param len The length of word/ucword
- * \param ignoreflagbits Ignore whether affix is legal
- * \param allhits Keep going after first hit
- * \param pfxopts Options to apply to prefixes
- * \param sfxopts Options to apply to suffixes
- */
-void ISpellChecker::chk_aff (ichar_t *word, ichar_t *ucword,
- int len, int ignoreflagbits, int allhits, int pfxopts, int sfxopts)
-{
- register ichar_t * cp; /* Pointer to char to index on */
- struct flagptr * ind; /* Flag index table to test */
-
- pfx_list_chk (word, ucword, len, pfxopts, sfxopts, &m_pflagindex[0],
- ignoreflagbits, allhits);
- cp = ucword;
- /* HACK: bail on unrecognized chars */
- if (*cp >= (SET_SIZE + MAXSTRINGCHARS))
- return;
- ind = &m_pflagindex[*cp++];
- while (ind->numents == 0 && ind->pu.fp != NULL)
- {
- if (*cp == 0)
- return;
- if (ind->pu.fp[0].numents)
- {
- pfx_list_chk (word, ucword, len, pfxopts, sfxopts, &ind->pu.fp[0],
- ignoreflagbits, allhits);
- if (m_numhits && !allhits && /* !cflag && */ !ignoreflagbits)
- return;
- }
- /* HACK: bail on unrecognized chars */
- if (*cp >= (SET_SIZE + MAXSTRINGCHARS))
- return;
- ind = &ind->pu.fp[*cp++];
- }
- pfx_list_chk (word, ucword, len, pfxopts, sfxopts, ind, ignoreflagbits,
- allhits);
- if (m_numhits && !allhits && /* !cflag &&*/ !ignoreflagbits)
- return;
- chk_suf (word, ucword, len, sfxopts, static_cast<struct flagent *>(NULL),
- ignoreflagbits, allhits);
-}
-
-/*!
- * Check some prefix flags
- *
- * \param word Word to be checked
- * \param ucword Upper-case-only word
- * \param len The length of ucword
- * \param optflags Options to apply
- * \param sfxopts Options to apply to suffixes
- * \param ind Flag index table
- * \param ignoreflagbits Ignore whether affix is legal
- * \param allhits Keep going after first hit
- * */
-void ISpellChecker::pfx_list_chk (ichar_t *word, ichar_t *ucword, int len, int optflags,
- int sfxopts, struct flagptr * ind, int ignoreflagbits, int allhits)
-{
- int cond; /* Condition number */
- register ichar_t * cp; /* Pointer into end of ucword */
- struct dent * dent; /* Dictionary entry we found */
- int entcount; /* Number of entries to process */
- register struct flagent *
- flent; /* Current table entry */
- int preadd; /* Length added to tword2 as prefix */
- register int tlen; /* Length of tword */
- ichar_t tword[INPUTWORDLEN + 4 * MAXAFFIXLEN + 4]; /* Tmp cpy */
- ichar_t tword2[sizeof tword]; /* 2nd copy for ins_root_cap */
-
- for (flent = ind->pu.ent, entcount = ind->numents;
- entcount > 0;
- flent++, entcount--)
- {
- /*
- * If this is a compound-only affix, ignore it unless we're
- * looking for that specific thing.
- */
- if ((flent->flagflags & FF_COMPOUNDONLY) != 0
- && (optflags & FF_COMPOUNDONLY) == 0)
- continue;
-
- /*
- * See if the prefix matches.
- */
- tlen = len - flent->affl;
- if (tlen > 0
- && (flent->affl == 0
- || icharncmp (flent->affix, ucword, flent->affl) == 0)
- && tlen + flent->stripl >= flent->numconds)
- {
- /*
- * The prefix matches. Remove it, replace it by the "strip"
- * string (if any), and check the original conditions.
- */
- if (flent->stripl)
- icharcpy (tword, flent->strip);
- icharcpy (tword + flent->stripl, ucword + flent->affl);
- cp = tword;
- for (cond = 0; cond < flent->numconds; cond++)
- {
- if ((flent->conds[*cp++] & (1 << cond)) == 0)
- break;
- }
- if (cond >= flent->numconds)
- {
- /*
- * The conditions match. See if the word is in the
- * dictionary.
- */
- tlen += flent->stripl;
-
- if (ignoreflagbits)
- {
- if ((dent = ispell_lookup (tword, 1)) != NULL)
- {
- cp = tword2;
- if (flent->affl)
- {
- icharcpy (cp, flent->affix);
- cp += flent->affl;
- *cp++ = '+';
- }
- preadd = cp - tword2;
- icharcpy (cp, tword);
- cp += tlen;
- if (flent->stripl)
- {
- *cp++ = '-';
- icharcpy (cp, flent->strip);
- }
- }
- }
- else if ((dent = ispell_lookup (tword, 1)) != NULL
- && TSTMASKBIT (dent->mask, flent->flagbit))
- {
- if (m_numhits < MAX_HITS)
- {
- m_hits[m_numhits].dictent = dent;
- m_hits[m_numhits].prefix = flent;
- m_hits[m_numhits].suffix = NULL;
- m_numhits++;
- }
- if (!allhits)
- {
-#ifndef NO_CAPITALIZATION_SUPPORT
- if (cap_ok (word, &m_hits[0], len))
- return;
- m_numhits = 0;
-#else /* NO_CAPITALIZATION_SUPPORT */
- return;
-#endif /* NO_CAPITALIZATION_SUPPORT */
- }
- }
- /*
- * Handle cross-products.
- */
- if (flent->flagflags & FF_CROSSPRODUCT)
- chk_suf (word, tword, tlen, sfxopts | FF_CROSSPRODUCT,
- flent, ignoreflagbits, allhits);
- }
- }
- }
-}
-
-/*!
- * Check possible suffixes
- *
- * \param word Word to be checked
- * \param ucword Upper-case-only word
- * \param len The length of ucword
- * \param optflags Affix option flags
- * \param pfxent Prefix flag entry if cross-prod
- * \param ignoreflagbits Ignore whether affix is legal
- * \param allhits Keep going after first hit
- */
-void
-ISpellChecker::chk_suf (ichar_t *word, ichar_t *ucword,
- int len, int optflags, struct flagent *pfxent,
- int ignoreflagbits, int allhits)
-{
- register ichar_t * cp; /* Pointer to char to index on */
- struct flagptr * ind; /* Flag index table to test */
-
- suf_list_chk (word, ucword, len, &m_sflagindex[0], optflags, pfxent,
- ignoreflagbits, allhits);
- cp = ucword + len - 1;
- /* HACK: bail on unrecognized chars */
- if (*cp >= (SET_SIZE + MAXSTRINGCHARS))
- return;
- ind = &m_sflagindex[*cp];
- while (ind->numents == 0 && ind->pu.fp != NULL)
- {
- if (cp == ucword)
- return;
- if (ind->pu.fp[0].numents)
- {
- suf_list_chk (word, ucword, len, &ind->pu.fp[0],
- optflags, pfxent, ignoreflagbits, allhits);
- if (m_numhits != 0 && !allhits && /* !cflag && */ !ignoreflagbits)
- return;
- }
- /* HACK: bail on unrecognized chars */
- if (*(cp-1) >= (SET_SIZE + MAXSTRINGCHARS))
- return;
- ind = &ind->pu.fp[*--cp];
- }
- suf_list_chk (word, ucword, len, ind, optflags, pfxent,
- ignoreflagbits, allhits);
-}
-
-/*!
- * \param word Word to be checked
- * \param ucword Upper-case-only word
- * \param len The length of ucword
- * \param ind Flag index table
- * \param optflags Affix option flags
- * \param pfxent Prefix flag entry if crossonly
- * \param ignoreflagbits Ignore whether affix is legal
- * \pram allhits Keep going after first hit
- */
-void ISpellChecker::suf_list_chk (ichar_t *word, ichar_t *ucword,
- int len, struct flagptr *ind, int optflags,
- struct flagent *pfxent, int ignoreflagbits, int allhits)
-{
- register ichar_t * cp; /* Pointer into end of ucword */
- int cond; /* Condition number */
- struct dent * dent; /* Dictionary entry we found */
- int entcount; /* Number of entries to process */
- register struct flagent *
- flent; /* Current table entry */
- int preadd; /* Length added to tword2 as prefix */
- register int tlen; /* Length of tword */
- ichar_t tword[INPUTWORDLEN + 4 * MAXAFFIXLEN + 4]; /* Tmp cpy */
- ichar_t tword2[sizeof tword]; /* 2nd copy for ins_root_cap */
-
- icharcpy (tword, ucword);
- for (flent = ind->pu.ent, entcount = ind->numents;
- entcount > 0;
- flent++, entcount--)
- {
- if ((optflags & FF_CROSSPRODUCT) != 0
- && (flent->flagflags & FF_CROSSPRODUCT) == 0)
- continue;
- /*
- * If this is a compound-only affix, ignore it unless we're
- * looking for that specific thing.
- */
- if ((flent->flagflags & FF_COMPOUNDONLY) != 0
- && (optflags & FF_COMPOUNDONLY) == 0)
- continue;
-
- /*
- * See if the suffix matches.
- */
- tlen = len - flent->affl;
- if (tlen > 0
- && (flent->affl == 0
- || icharcmp (flent->affix, ucword + tlen) == 0)
- && tlen + flent->stripl >= flent->numconds)
- {
- /*
- * The suffix matches. Remove it, replace it by the "strip"
- * string (if any), and check the original conditions.
- */
- icharcpy (tword, ucword);
- cp = tword + tlen;
- if (flent->stripl)
- {
- icharcpy (cp, flent->strip);
- tlen += flent->stripl;
- cp = tword + tlen;
- }
- else
- *cp = '\0';
- for (cond = flent->numconds; --cond >= 0; )
- {
- if ((flent->conds[*--cp] & (1 << cond)) == 0)
- break;
- }
- if (cond < 0)
- {
- /*
- * The conditions match. See if the word is in the
- * dictionary.
- */
- if (ignoreflagbits)
- {
- if ((dent = ispell_lookup (tword, 1)) != NULL)
- {
- cp = tword2;
- if ((optflags & FF_CROSSPRODUCT)
- && pfxent->affl != 0)
- {
- icharcpy (cp, pfxent->affix);
- cp += pfxent->affl;
- *cp++ = '+';
- }
- preadd = cp - tword2;
- icharcpy (cp, tword);
- cp += tlen;
- if ((optflags & FF_CROSSPRODUCT)
- && pfxent->stripl != 0)
- {
- *cp++ = '-';
- icharcpy (cp, pfxent->strip);
- cp += pfxent->stripl;
- }
- if (flent->stripl)
- {
- *cp++ = '-';
- icharcpy (cp, flent->strip);
- cp += flent->stripl;
- }
- if (flent->affl)
- {
- *cp++ = '+';
- icharcpy (cp, flent->affix);
- cp += flent->affl;
- }
- }
- }
- else if ((dent = ispell_lookup (tword, 1)) != NULL
- && TSTMASKBIT (dent->mask, flent->flagbit)
- && ((optflags & FF_CROSSPRODUCT) == 0
- || TSTMASKBIT (dent->mask, pfxent->flagbit)))
- {
- if (m_numhits < MAX_HITS)
- {
- m_hits[m_numhits].dictent = dent;
- m_hits[m_numhits].prefix = pfxent;
- m_hits[m_numhits].suffix = flent;
- m_numhits++;
- }
- if (!allhits)
- {
-#ifndef NO_CAPITALIZATION_SUPPORT
- if (cap_ok (word, &m_hits[0], len))
- return;
- m_numhits = 0;
-#else /* NO_CAPITALIZATION_SUPPORT */
- return;
-#endif /* NO_CAPITALIZATION_SUPPORT */
- }
- }
- }
- }
- }
-}
-
-/*!
- * Expand a dictionary prefix entry
- *
- * \param croot Char version of rootword
- * \param rootword Root word to expand
- * \param mask Mask bits to expand on
- * \param option Option, see expandmode
- * \param extra Extra info to add to line
- *
- * \return
- */
-int ISpellChecker::expand_pre (char *croot, ichar_t *rootword, MASKTYPE mask[],
- int option, char *extra)
-{
- int entcount; /* No. of entries to process */
- int explength; /* Length of expansions */
- register struct flagent *
- flent; /* Current table entry */
-
- for (flent = m_pflaglist, entcount = m_numpflags, explength = 0;
- entcount > 0;
- flent++, entcount--)
- {
- if (TSTMASKBIT (mask, flent->flagbit))
- explength +=
- pr_pre_expansion (croot, rootword, flent, mask, option, extra);
- }
- return explength;
-}
-
-/*!
- * Print a prefix expansion
- *
- * \param croot Char version of rootword
- * \param rootword Root word to expand
- * \param flent Current table entry
- * \param mask Mask bits to expand on
- * \param option Option, see expandmode
- * \param extra Extra info to add to line
- *
- * \return
- */
-int ISpellChecker::pr_pre_expansion ( char *croot, ichar_t *rootword,
- struct flagent *flent, MASKTYPE mask[], int option,
- char *extra)
-{
- int cond; /* Current condition number */
- register ichar_t * nextc; /* Next case choice */
- int tlen; /* Length of tword */
- ichar_t tword[INPUTWORDLEN + MAXAFFIXLEN]; /* Temp */
-
- tlen = icharlen (rootword);
- if (flent->numconds > tlen)
- return 0;
- tlen -= flent->stripl;
- if (tlen <= 0)
- return 0;
- tlen += flent->affl;
- for (cond = 0, nextc = rootword; cond < flent->numconds; cond++)
- {
- if ((flent->conds[mytoupper (*nextc++)] & (1 << cond)) == 0)
- return 0;
- }
- /*
- * The conditions are satisfied. Copy the word, add the prefix,
- * and make it the proper case. This code is carefully written
- * to match that ins_cap and cap_ok. Note that the affix, as
- * inserted, is uppercase.
- *
- * There is a tricky bit here: if the root is capitalized, we
- * want a capitalized result. If the root is followcase, however,
- * we want to duplicate the case of the first remaining letter
- * of the root. In other words, "Loved/U" should generate "Unloved",
- * but "LOved/U" should generate "UNLOved" and "lOved/U" should
- * produce "unlOved".
- */
- if (flent->affl)
- {
- icharcpy (tword, flent->affix);
- nextc = tword + flent->affl;
- }
- icharcpy (nextc, rootword + flent->stripl);
- if (myupper (rootword[0]))
- {
- /* We must distinguish followcase from capitalized and all-upper */
- for (nextc = rootword + 1; *nextc; nextc++)
- {
- if (!myupper (*nextc))
- break;
- }
- if (*nextc)
- {
- /* It's a followcase or capitalized word. Figure out which. */
- for ( ; *nextc; nextc++)
- {
- if (myupper (*nextc))
- break;
- }
- if (*nextc)
- {
- /* It's followcase. */
- if (!myupper (tword[flent->affl]))
- forcelc (tword, flent->affl);
- }
- else
- {
- /* It's capitalized */
- forcelc (tword + 1, tlen - 1);
- }
- }
- }
- else
- {
- /* Followcase or all-lower, we don't care which */
- if (!myupper (*nextc))
- forcelc (tword, flent->affl);
- }
- if (option == 3)
- printf ("\n%s", croot);
- if (option != 4)
- printf (" %s%s", ichartosstr (tword, 1), extra);
- if (flent->flagflags & FF_CROSSPRODUCT)
- return tlen
- + expand_suf (croot, tword, mask, FF_CROSSPRODUCT, option, extra);
- else
- return tlen;
-}
-
-/*!
- * Expand a dictionary suffix entry
- *
- * \param croot Char version of rootword
- * \param rootword Root word to expand
- * \param mask Mask bits to expand on
- * \param optflags Affix option flags
- * \param option Option, see expandmode
- * \param extra Extra info to add to line
- *
- * \return
- */
-int ISpellChecker::expand_suf (char *croot, ichar_t *rootword, MASKTYPE mask[],
- int optflags, int option, char *extra)
-{
- int entcount; /* No. of entries to process */
- int explength; /* Length of expansions */
- register struct flagent *
- flent; /* Current table entry */
-
- for (flent = m_sflaglist, entcount = m_numsflags, explength = 0;
- entcount > 0;
- flent++, entcount--)
- {
- if (TSTMASKBIT (mask, flent->flagbit))
- {
- if ((optflags & FF_CROSSPRODUCT) == 0
- || (flent->flagflags & FF_CROSSPRODUCT))
- explength +=
- pr_suf_expansion (croot, rootword, flent, option, extra);
- }
- }
- return explength;
-}
-
-/*!
- * Print a suffix expansion
- *
- * \param croot Char version of rootword
- * \param rootword Root word to expand
- * \param flent Current table entry
- * \param option Option, see expandmode
- * \param extra Extra info to add to line
- *
- * \return
- */
-int ISpellChecker::pr_suf_expansion (char *croot, ichar_t *rootword,
- struct flagent *flent, int option, char *extra)
-{
- int cond; /* Current condition number */
- register ichar_t * nextc; /* Next case choice */
- int tlen; /* Length of tword */
- ichar_t tword[INPUTWORDLEN + MAXAFFIXLEN]; /* Temp */
-
- tlen = icharlen (rootword);
- cond = flent->numconds;
- if (cond > tlen)
- return 0;
- if (tlen - flent->stripl <= 0)
- return 0;
- for (nextc = rootword + tlen; --cond >= 0; )
- {
- if ((flent->conds[mytoupper (*--nextc)] & (1 << cond)) == 0)
- return 0;
- }
- /*
- * The conditions are satisfied. Copy the word, add the suffix,
- * and make it match the case of the last remaining character of the
- * root. Again, this code carefully matches ins_cap and cap_ok.
- */
- icharcpy (tword, rootword);
- nextc = tword + tlen - flent->stripl;
- if (flent->affl)
- {
- icharcpy (nextc, flent->affix);
- if (!myupper (nextc[-1]))
- forcelc (nextc, flent->affl);
- }
- else
- *nextc = 0;
- if (option == 3)
- printf ("\n%s", croot);
- if (option != 4)
- printf (" %s%s", ichartosstr (tword, 1), extra);
- return tlen + flent->affl - flent->stripl;
-}
-
-/*!
- * \param dst Destination to modify
- * \param len Length to copy
- */
-void ISpellChecker::forcelc (ichar_t *dst, int len) /* Force to lowercase */
-{
-
- for ( ; --len >= 0; dst++)
- *dst = mytolower (*dst);
-}