1114402Sru// -*- C++ -*- 2151497Sru/* Copyright (C) 1989, 1990, 1991, 1992, 2000, 2001, 2002, 2003, 2004 3114402Sru Free Software Foundation, Inc. 4114402Sru Written by James Clark (jjc@jclark.com) 5114402Sru 6114402SruThis file is part of groff. 7114402Sru 8114402Srugroff is free software; you can redistribute it and/or modify it under 9114402Sruthe terms of the GNU General Public License as published by the Free 10114402SruSoftware Foundation; either version 2, or (at your option) any later 11114402Sruversion. 12114402Sru 13114402Srugroff is distributed in the hope that it will be useful, but WITHOUT ANY 14114402SruWARRANTY; without even the implied warranty of MERCHANTABILITY or 15114402SruFITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License 16114402Srufor more details. 17114402Sru 18114402SruYou should have received a copy of the GNU General Public License along 19114402Sruwith groff; see the file COPYING. If not, write to the Free Software 20151497SruFoundation, 51 Franklin St - Fifth Floor, Boston, MA 02110-1301, USA. */ 21114402Sru 22114402Sru#include "lib.h" 23114402Sru 24114402Sru#include <ctype.h> 25114402Sru#include <assert.h> 26114402Sru#include <stdlib.h> 27114402Sru#include "errarg.h" 28114402Sru#include "error.h" 29114402Sru#include "font.h" 30114402Sru#include "ptable.h" 31114402Sru 32114402Srudeclare_ptable(int) 33114402Sruimplement_ptable(int) 34114402Sru 35114402Sruclass character_indexer { 36114402Srupublic: 37114402Sru character_indexer(); 38114402Sru ~character_indexer(); 39114402Sru int ascii_char_index(unsigned char); 40114402Sru int named_char_index(const char *); 41114402Sru int numbered_char_index(int); 42114402Sruprivate: 43114402Sru enum { NSMALL = 256 }; 44114402Sru int next_index; 45114402Sru int ascii_index[256]; 46114402Sru int small_number_index[NSMALL]; 47114402Sru PTABLE(int) table; 48114402Sru}; 49114402Sru 50114402Srucharacter_indexer::character_indexer() 51114402Sru: next_index(0) 52114402Sru{ 53114402Sru int i; 54114402Sru for (i = 0; i < 256; i++) 55114402Sru ascii_index[i] = -1; 56114402Sru for (i = 0; i < NSMALL; i++) 57114402Sru small_number_index[i] = -1; 58114402Sru} 59114402Sru 60114402Srucharacter_indexer::~character_indexer() 61114402Sru{ 62114402Sru} 63114402Sru 64114402Sruint character_indexer::ascii_char_index(unsigned char c) 65114402Sru{ 66114402Sru if (ascii_index[c] < 0) 67114402Sru ascii_index[c] = next_index++; 68114402Sru return ascii_index[c]; 69114402Sru} 70114402Sru 71114402Sruint character_indexer::numbered_char_index(int n) 72114402Sru{ 73114402Sru if (n >= 0 && n < NSMALL) { 74114402Sru if (small_number_index[n] < 0) 75114402Sru small_number_index[n] = next_index++; 76114402Sru return small_number_index[n]; 77114402Sru } 78114402Sru // Not the most efficient possible implementation. 79114402Sru char buf[INT_DIGITS + 3]; 80114402Sru buf[0] = ' '; 81114402Sru strcpy(buf + 1, i_to_a(n)); 82114402Sru return named_char_index(buf); 83114402Sru} 84114402Sru 85114402Sruint character_indexer::named_char_index(const char *s) 86114402Sru{ 87114402Sru int *np = table.lookup(s); 88114402Sru if (!np) { 89114402Sru np = new int[1]; 90114402Sru *np = next_index++; 91114402Sru table.define(s, np); 92114402Sru } 93114402Sru return *np; 94114402Sru} 95114402Sru 96114402Srustatic character_indexer indexer; 97114402Sru 98114402Sruint font::number_to_index(int n) 99114402Sru{ 100114402Sru return indexer.numbered_char_index(n); 101114402Sru} 102114402Sru 103114402Sruint font::name_to_index(const char *s) 104114402Sru{ 105114402Sru assert(s != 0 && s[0] != '\0' && s[0] != ' '); 106114402Sru if (s[1] == '\0') 107114402Sru return indexer.ascii_char_index(s[0]); 108114402Sru /* char128 and \200 are synonyms */ 109114402Sru if (s[0] == 'c' && s[1] == 'h' && s[2] == 'a' && s[3] == 'r') { 110151497Sru char *val; 111151497Sru long n = strtol(s + 4, &val, 10); 112151497Sru if (val != s + 4 && *val == '\0' && n >= 0 && n < 256) 113114402Sru return indexer.ascii_char_index((unsigned char)n); 114114402Sru } 115114402Sru return indexer.named_char_index(s); 116114402Sru} 117114402Sru 118