10Sstevel@tonic-gate /*
20Sstevel@tonic-gate * CDDL HEADER START
30Sstevel@tonic-gate *
40Sstevel@tonic-gate * The contents of this file are subject to the terms of the
50Sstevel@tonic-gate * Common Development and Distribution License, Version 1.0 only
60Sstevel@tonic-gate * (the "License"). You may not use this file except in compliance
70Sstevel@tonic-gate * with the License.
80Sstevel@tonic-gate *
90Sstevel@tonic-gate * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
100Sstevel@tonic-gate * or http://www.opensolaris.org/os/licensing.
110Sstevel@tonic-gate * See the License for the specific language governing permissions
120Sstevel@tonic-gate * and limitations under the License.
130Sstevel@tonic-gate *
140Sstevel@tonic-gate * When distributing Covered Code, include this CDDL HEADER in each
150Sstevel@tonic-gate * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
160Sstevel@tonic-gate * If applicable, add the following below this CDDL HEADER, with the
170Sstevel@tonic-gate * fields enclosed by brackets "[]" replaced with your own identifying
180Sstevel@tonic-gate * information: Portions Copyright [yyyy] [name of copyright owner]
190Sstevel@tonic-gate *
200Sstevel@tonic-gate * CDDL HEADER END
210Sstevel@tonic-gate */
220Sstevel@tonic-gate /*
230Sstevel@tonic-gate * Copyright 2003 Sun Microsystems, Inc. All rights reserved.
240Sstevel@tonic-gate * Use is subject to license terms.
250Sstevel@tonic-gate */
260Sstevel@tonic-gate
270Sstevel@tonic-gate /* Copyright (c) 1984, 1986, 1987, 1988, 1989 AT&T */
280Sstevel@tonic-gate /* All Rights Reserved */
290Sstevel@tonic-gate
300Sstevel@tonic-gate /*
310Sstevel@tonic-gate * University Copyright- Copyright (c) 1982, 1986, 1988
320Sstevel@tonic-gate * The Regents of the University of California
330Sstevel@tonic-gate * All Rights Reserved
340Sstevel@tonic-gate *
350Sstevel@tonic-gate * University Acknowledgment- Portions of this document are derived from
360Sstevel@tonic-gate * software developed by the University of California, Berkeley, and its
370Sstevel@tonic-gate * contributors.
380Sstevel@tonic-gate */
390Sstevel@tonic-gate
40*217Smuffin #pragma ident "%Z%%M% %I% %E% SMI"
41*217Smuffin
420Sstevel@tonic-gate #include <ctype.h>
430Sstevel@tonic-gate #include "tdef.h"
440Sstevel@tonic-gate #include "ext.h"
450Sstevel@tonic-gate #define HY_BIT 0200 /* stuff in here only works for ascii */
460Sstevel@tonic-gate
470Sstevel@tonic-gate /*
480Sstevel@tonic-gate * troff8.c
490Sstevel@tonic-gate *
500Sstevel@tonic-gate * hyphenation
510Sstevel@tonic-gate */
520Sstevel@tonic-gate
530Sstevel@tonic-gate char hbuf[NHEX];
540Sstevel@tonic-gate char *nexth = hbuf;
550Sstevel@tonic-gate tchar *hyend;
560Sstevel@tonic-gate #define THRESH 160 /*digram goodness threshold*/
570Sstevel@tonic-gate int thresh = THRESH;
580Sstevel@tonic-gate
59*217Smuffin int
hyphen(wp)600Sstevel@tonic-gate hyphen(wp)
610Sstevel@tonic-gate tchar *wp;
620Sstevel@tonic-gate {
63*217Smuffin int j;
64*217Smuffin tchar *i;
650Sstevel@tonic-gate
660Sstevel@tonic-gate i = wp;
670Sstevel@tonic-gate while (punct(cbits(*i++)))
680Sstevel@tonic-gate ;
690Sstevel@tonic-gate if (!alph(cbits(*--i)))
70*217Smuffin return (0);
710Sstevel@tonic-gate wdstart = i++;
720Sstevel@tonic-gate while (alph(cbits(*i++)))
730Sstevel@tonic-gate ;
740Sstevel@tonic-gate hyend = wdend = --i - 1;
750Sstevel@tonic-gate while (punct(cbits(*i++)))
760Sstevel@tonic-gate ;
770Sstevel@tonic-gate if (*--i)
78*217Smuffin return (0);
790Sstevel@tonic-gate if ((wdend - wdstart - 4) < 0)
80*217Smuffin return (0);
810Sstevel@tonic-gate hyp = hyptr;
820Sstevel@tonic-gate *hyp = 0;
830Sstevel@tonic-gate hyoff = 2;
840Sstevel@tonic-gate if (!exword() && !suffix())
850Sstevel@tonic-gate digram();
860Sstevel@tonic-gate *hyp++ = 0;
870Sstevel@tonic-gate if (*hyptr)
880Sstevel@tonic-gate for (j = 1; j; ) {
890Sstevel@tonic-gate j = 0;
900Sstevel@tonic-gate for (hyp = hyptr + 1; *hyp != 0; hyp++) {
910Sstevel@tonic-gate if (*(hyp - 1) > *hyp) {
920Sstevel@tonic-gate j++;
930Sstevel@tonic-gate i = *hyp;
940Sstevel@tonic-gate *hyp = *(hyp - 1);
950Sstevel@tonic-gate *(hyp - 1) = i;
960Sstevel@tonic-gate }
970Sstevel@tonic-gate }
980Sstevel@tonic-gate }
99*217Smuffin
100*217Smuffin return (0);
1010Sstevel@tonic-gate }
1020Sstevel@tonic-gate
1030Sstevel@tonic-gate
104*217Smuffin int
punct(i)1050Sstevel@tonic-gate punct(i)
1060Sstevel@tonic-gate {
1070Sstevel@tonic-gate if (!i || alph(i))
1080Sstevel@tonic-gate return(0);
1090Sstevel@tonic-gate else
1100Sstevel@tonic-gate return(1);
1110Sstevel@tonic-gate }
1120Sstevel@tonic-gate
1130Sstevel@tonic-gate
114*217Smuffin int
alph(i)1150Sstevel@tonic-gate alph(i)
1160Sstevel@tonic-gate {
1170Sstevel@tonic-gate if (i >= 'a' && i <= 'z' || i >= 'A' && i <= 'Z')
1180Sstevel@tonic-gate return(1);
1190Sstevel@tonic-gate else
1200Sstevel@tonic-gate return(0);
1210Sstevel@tonic-gate }
1220Sstevel@tonic-gate
1230Sstevel@tonic-gate
124*217Smuffin int
caseht()1250Sstevel@tonic-gate caseht()
1260Sstevel@tonic-gate {
1270Sstevel@tonic-gate thresh = THRESH;
1280Sstevel@tonic-gate if (skip())
129*217Smuffin return (0);
1300Sstevel@tonic-gate noscale++;
1310Sstevel@tonic-gate thresh = atoi();
1320Sstevel@tonic-gate noscale = 0;
133*217Smuffin
134*217Smuffin return (0);
1350Sstevel@tonic-gate }
1360Sstevel@tonic-gate
1370Sstevel@tonic-gate
138*217Smuffin int
casehw()1390Sstevel@tonic-gate casehw()
1400Sstevel@tonic-gate {
141*217Smuffin int i, k;
142*217Smuffin char *j;
1430Sstevel@tonic-gate tchar t;
1440Sstevel@tonic-gate
1450Sstevel@tonic-gate k = 0;
1460Sstevel@tonic-gate while (!skip()) {
1470Sstevel@tonic-gate if ((j = nexth) >= (hbuf + NHEX - 2))
1480Sstevel@tonic-gate goto full;
1490Sstevel@tonic-gate for (; ; ) {
1500Sstevel@tonic-gate if (ismot(t = getch()))
1510Sstevel@tonic-gate continue;
1520Sstevel@tonic-gate i = cbits(t);
1530Sstevel@tonic-gate if (i == ' ' || i == '\n') {
1540Sstevel@tonic-gate *j++ = 0;
1550Sstevel@tonic-gate nexth = j;
1560Sstevel@tonic-gate *j = 0;
1570Sstevel@tonic-gate if (i == ' ')
1580Sstevel@tonic-gate break;
1590Sstevel@tonic-gate else
160*217Smuffin return (0);
1610Sstevel@tonic-gate }
1620Sstevel@tonic-gate if (i == '-') {
1630Sstevel@tonic-gate k = HY_BIT;
1640Sstevel@tonic-gate continue;
1650Sstevel@tonic-gate }
1660Sstevel@tonic-gate *j++ = maplow(i) | k;
1670Sstevel@tonic-gate k = 0;
1680Sstevel@tonic-gate if (j >= (hbuf + NHEX - 2))
1690Sstevel@tonic-gate goto full;
1700Sstevel@tonic-gate }
1710Sstevel@tonic-gate }
172*217Smuffin return (0);
1730Sstevel@tonic-gate full:
1740Sstevel@tonic-gate errprint(gettext("exception word list full."));
1750Sstevel@tonic-gate *nexth = 0;
176*217Smuffin
177*217Smuffin return (0);
1780Sstevel@tonic-gate }
1790Sstevel@tonic-gate
1800Sstevel@tonic-gate
181*217Smuffin int
exword()1820Sstevel@tonic-gate exword()
1830Sstevel@tonic-gate {
184*217Smuffin tchar *w;
185*217Smuffin char *e;
1860Sstevel@tonic-gate char *save;
1870Sstevel@tonic-gate
1880Sstevel@tonic-gate e = hbuf;
1890Sstevel@tonic-gate while (1) {
1900Sstevel@tonic-gate save = e;
1910Sstevel@tonic-gate if (*e == 0)
1920Sstevel@tonic-gate return(0);
1930Sstevel@tonic-gate w = wdstart;
1940Sstevel@tonic-gate while (*e && w <= hyend && (*e & 0177) == maplow(cbits(*w))) {
1950Sstevel@tonic-gate e++;
1960Sstevel@tonic-gate w++;
1970Sstevel@tonic-gate };
1980Sstevel@tonic-gate if (!*e) {
1990Sstevel@tonic-gate if (w-1 == hyend || (w == wdend && maplow(cbits(*w)) == 's')) {
2000Sstevel@tonic-gate w = wdstart;
2010Sstevel@tonic-gate for (e = save; *e; e++) {
2020Sstevel@tonic-gate if (*e & HY_BIT)
2030Sstevel@tonic-gate *hyp++ = w;
2040Sstevel@tonic-gate if (hyp > (hyptr + NHYP - 1))
2050Sstevel@tonic-gate hyp = hyptr + NHYP - 1;
2060Sstevel@tonic-gate w++;
2070Sstevel@tonic-gate }
2080Sstevel@tonic-gate return(1);
2090Sstevel@tonic-gate } else {
2100Sstevel@tonic-gate e++;
2110Sstevel@tonic-gate continue;
2120Sstevel@tonic-gate }
2130Sstevel@tonic-gate } else
2140Sstevel@tonic-gate while (*e++)
2150Sstevel@tonic-gate ;
2160Sstevel@tonic-gate }
217*217Smuffin
218*217Smuffin return (0);
2190Sstevel@tonic-gate }
2200Sstevel@tonic-gate
2210Sstevel@tonic-gate
222*217Smuffin int
suffix()2230Sstevel@tonic-gate suffix()
2240Sstevel@tonic-gate {
225*217Smuffin tchar *w;
226*217Smuffin char *s, *s0;
2270Sstevel@tonic-gate tchar i;
2280Sstevel@tonic-gate extern char *suftab[];
2290Sstevel@tonic-gate extern tchar *chkvow();
2300Sstevel@tonic-gate
2310Sstevel@tonic-gate again:
2320Sstevel@tonic-gate if (!alph(cbits(i = cbits(*hyend))))
2330Sstevel@tonic-gate return(0);
2340Sstevel@tonic-gate if (i < 'a')
2350Sstevel@tonic-gate i -= 'A' - 'a';
2360Sstevel@tonic-gate if ((s0 = suftab[i-'a']) == 0)
2370Sstevel@tonic-gate return(0);
2380Sstevel@tonic-gate for (; ; ) {
2390Sstevel@tonic-gate if ((i = *s0 & 017) == 0)
2400Sstevel@tonic-gate return(0);
2410Sstevel@tonic-gate s = s0 + i - 1;
2420Sstevel@tonic-gate w = hyend - 1;
2430Sstevel@tonic-gate while (s > s0 && w >= wdstart && (*s & 0177) == maplow(cbits(*w))) {
2440Sstevel@tonic-gate s--;
2450Sstevel@tonic-gate w--;
2460Sstevel@tonic-gate }
2470Sstevel@tonic-gate if (s == s0)
2480Sstevel@tonic-gate break;
2490Sstevel@tonic-gate s0 += i;
2500Sstevel@tonic-gate }
2510Sstevel@tonic-gate s = s0 + i - 1;
2520Sstevel@tonic-gate w = hyend;
2530Sstevel@tonic-gate if (*s0 & HY_BIT)
2540Sstevel@tonic-gate goto mark;
2550Sstevel@tonic-gate while (s > s0) {
2560Sstevel@tonic-gate w--;
2570Sstevel@tonic-gate if (*s-- & HY_BIT) {
2580Sstevel@tonic-gate mark:
2590Sstevel@tonic-gate hyend = w - 1;
2600Sstevel@tonic-gate if (*s0 & 0100)
2610Sstevel@tonic-gate continue;
2620Sstevel@tonic-gate if (!chkvow(w))
2630Sstevel@tonic-gate return(0);
2640Sstevel@tonic-gate *hyp++ = w;
2650Sstevel@tonic-gate }
2660Sstevel@tonic-gate }
2670Sstevel@tonic-gate if (*s0 & 040)
2680Sstevel@tonic-gate return(0);
2690Sstevel@tonic-gate if (exword())
2700Sstevel@tonic-gate return(1);
2710Sstevel@tonic-gate goto again;
2720Sstevel@tonic-gate }
2730Sstevel@tonic-gate
2740Sstevel@tonic-gate
275*217Smuffin int
maplow(i)2760Sstevel@tonic-gate maplow(i)
277*217Smuffin int i;
2780Sstevel@tonic-gate {
2790Sstevel@tonic-gate if (ischar(i) && isupper(i))
2800Sstevel@tonic-gate i = tolower(i);
2810Sstevel@tonic-gate return(i);
2820Sstevel@tonic-gate }
2830Sstevel@tonic-gate
2840Sstevel@tonic-gate
285*217Smuffin int
vowel(i)2860Sstevel@tonic-gate vowel(i)
2870Sstevel@tonic-gate int i;
2880Sstevel@tonic-gate {
2890Sstevel@tonic-gate switch (maplow(i)) {
2900Sstevel@tonic-gate case 'a':
2910Sstevel@tonic-gate case 'e':
2920Sstevel@tonic-gate case 'i':
2930Sstevel@tonic-gate case 'o':
2940Sstevel@tonic-gate case 'u':
2950Sstevel@tonic-gate case 'y':
2960Sstevel@tonic-gate return(1);
2970Sstevel@tonic-gate default:
2980Sstevel@tonic-gate return(0);
2990Sstevel@tonic-gate }
3000Sstevel@tonic-gate }
3010Sstevel@tonic-gate
3020Sstevel@tonic-gate
chkvow(w)3030Sstevel@tonic-gate tchar *chkvow(w)
3040Sstevel@tonic-gate tchar *w;
3050Sstevel@tonic-gate {
3060Sstevel@tonic-gate while (--w >= wdstart)
3070Sstevel@tonic-gate if (vowel(cbits(*w)))
3080Sstevel@tonic-gate return(w);
3090Sstevel@tonic-gate return(0);
3100Sstevel@tonic-gate }
3110Sstevel@tonic-gate
3120Sstevel@tonic-gate
313*217Smuffin int
digram()3140Sstevel@tonic-gate digram()
3150Sstevel@tonic-gate {
316*217Smuffin tchar *w;
317*217Smuffin int val;
3180Sstevel@tonic-gate tchar * nhyend, *maxw;
3190Sstevel@tonic-gate int maxval;
3200Sstevel@tonic-gate extern char bxh[26][13], bxxh[26][13], xxh[26][13], xhx[26][13], hxx[26][13];
3210Sstevel@tonic-gate
3220Sstevel@tonic-gate again:
3230Sstevel@tonic-gate if (!(w = chkvow(hyend + 1)))
324*217Smuffin return (0);
3250Sstevel@tonic-gate hyend = w;
3260Sstevel@tonic-gate if (!(w = chkvow(hyend)))
327*217Smuffin return (0);
3280Sstevel@tonic-gate nhyend = w;
3290Sstevel@tonic-gate maxval = 0;
3300Sstevel@tonic-gate w--;
3310Sstevel@tonic-gate while ((++w < hyend) && (w < (wdend - 1))) {
3320Sstevel@tonic-gate val = 1;
3330Sstevel@tonic-gate if (w == wdstart)
3340Sstevel@tonic-gate val *= dilook('a', cbits(*w), bxh);
3350Sstevel@tonic-gate else if (w == wdstart + 1)
3360Sstevel@tonic-gate val *= dilook(cbits(*(w-1)), cbits(*w), bxxh);
3370Sstevel@tonic-gate else
3380Sstevel@tonic-gate val *= dilook(cbits(*(w-1)), cbits(*w), xxh);
3390Sstevel@tonic-gate val *= dilook(cbits(*w), cbits(*(w+1)), xhx);
3400Sstevel@tonic-gate val *= dilook(cbits(*(w+1)), cbits(*(w+2)), hxx);
3410Sstevel@tonic-gate if (val > maxval) {
3420Sstevel@tonic-gate maxval = val;
3430Sstevel@tonic-gate maxw = w + 1;
3440Sstevel@tonic-gate }
3450Sstevel@tonic-gate }
3460Sstevel@tonic-gate hyend = nhyend;
3470Sstevel@tonic-gate if (maxval > thresh)
3480Sstevel@tonic-gate *hyp++ = maxw;
3490Sstevel@tonic-gate goto again;
3500Sstevel@tonic-gate }
3510Sstevel@tonic-gate
3520Sstevel@tonic-gate
353*217Smuffin int
dilook(a,b,t)3540Sstevel@tonic-gate dilook(a, b, t)
3550Sstevel@tonic-gate int a, b;
3560Sstevel@tonic-gate char t[26][13];
3570Sstevel@tonic-gate {
358*217Smuffin int i, j;
3590Sstevel@tonic-gate
3600Sstevel@tonic-gate i = t[maplow(a)-'a'][(j = maplow(b)-'a')/2];
3610Sstevel@tonic-gate if (!(j & 01))
3620Sstevel@tonic-gate i >>= 4;
3630Sstevel@tonic-gate return(i & 017);
3640Sstevel@tonic-gate }
3650Sstevel@tonic-gate
3660Sstevel@tonic-gate
367