|
|
DataMuseum.dkPresents historical artifacts from the history of: DKUUG/EUUG Conference tapes |
This is an automatic "excavation" of a thematic subset of
See our Wiki for more about DKUUG/EUUG Conference tapes Excavated with: AutoArchaeologist - Free & Open Source Software. |
top - metrics - downloadIndex: T f
Length: 20259 (0x4f23)
Types: TextFile
Names: »font.c«
└─⟦a0efdde77⟧ Bits:30001252 EUUGD11 Tape, 1987 Spring Conference Helsinki
└─⟦526ad3590⟧ »EUUGD11/gnu-31mar87/X.V10.R4.tar.Z«
└─⟦2109abc41⟧
└─⟦this⟧ »./X.V10R4/libsun/font.c«
/*
* font.c
*
* Copyright (c) 1985 Massachusetts Institue of Technology
* Copyright (c) 1986 Sun Microsystems, Inc.
* Copyright (c) 1986 David C. Martin, UC Berkeley
*
* David C. Martin
* ARPA: dcmartin@ingres.Berkeley.EDU
* UUCP: ...!ucbvax!dcmartin
*
* $Log: font.c,v $
* Revision 10.4 86/11/29 13:48:04 jg
* fixes from Berkeley
*
* Revision 1.20 86/07/27 13:46:41 dcmartin
* more modifications to LoadVFont() to fix bugs w/ invalid pixrect pointers
* and variable height fonts.
*
* Revision 1.19 86/07/25 15:36:56 dcmartin
* modified code in StrikeToPixfont() to free all sub-structures in
* FontPriv pointer.
*
* Revision 1.18 86/07/25 15:30:46 dcmartin
* changed all calls to Xalloc() to malloc() due to necessity of getting NULLs
* when ENOMEM.
*
* Revision 1.17 86/07/25 14:40:18 dcmartin
* changed the algorithm for determining variable width.
* should work for all fonts, now.
*
* Revision 1.16 86/07/17 10:47:00 dcmartin
* can't include <sys/param.h> on Sun release 2.x due to brain damage in
* compiler as <sys/param.h> wants to include <sys/types.h> and so does
* <pixrect/pixrect_hs.h> in Xsun.h
*
* Revision 1.15 86/07/17 10:36:33 dcmartin
* release version w/ new LoadXFont() and support for Sun vfont files.
*
* Revision 1.14 86/07/17 10:31:49 dcmartin
*
*/
#ifndef lint
static char rcs_id[] = "$Header: font.c,v 10.4 86/11/29 13:48:04 jg Rel $";
#endif lint
#include <X/mit-copyright.h>
/*
* The Sun X drivers are a product of Sun Microsystems, Inc. and are provided
* for unrestricted use provided that this legend is included on all tape
* media and as a part of the software program in whole or part. Users
* may copy or modify these drivers without charge, but are not authorized
* to license or distribute them to anyone else except as part of a product or
* program developed by the user.
*
* THE SUN X DRIVERS ARE PROVIDED AS IS WITH NO WARRANTIES OF ANY KIND
* INCLUDING THE WARRANTIES OF DESIGN, MERCHANTIBILITY AND FITNESS FOR A
* PARTICULAR PURPOSE, OR ARISING FROM A COURSE OF DEALING, USAGE OR TRADE
* PRACTICE.
*
* The Sun X Drivers are provided with no support and without any obligation
* on the part of Sun Microsystems, Inc. to assist in their use, correction,
* modification or enhancement.
*
* SUN MICROSYSTEMS, INC. SHALL HAVE NO LIABILITY WITH RESPECT TO THE
* INFRINGEMENT OF COPYRIGHTS, TRADE SECRETS OR ANY PATENTS BY THE SUN X
* DRIVERS OR ANY PART THEREOF.
*
* In no event will Sun Microsystems, Inc. be liable for any lost revenue
* or profits or other special, indirect and consequential damages, even if
* Sun has been advised of the possibility of such damages.
*
* Sun Microsystems, Inc.
* 2550 Garcia Avenue
* Mountain View, California 94043
*/
#ifdef sun
#include "Xsun.h"
#include "vssite.h"
#include "../libvs100/param.h"
#include <vfont.h>
#include <sys/file.h>
#include <sys/stat.h>
#include <errno.h>
#include <strings.h>
/*
* from /usr/include/sys/param.h
*/
#define MAXPATHLEN 1024
extern int errno;
extern char *getenv();
extern char *malloc();
extern long lseek();
#define XFONT 0
#define VFONT 1
#define ReverseShort(s) ((ReverseByte[(unsigned char)(s)]<<8) \
| ReverseByte[(unsigned char)((s)>>8)])
static short ReverseByte[256] = {
0x00,0x80,0x40,0xc0,0x20,0xa0,0x60,0xe0,
0x10,0x90,0x50,0xd0,0x30,0xb0,0x70,0xf0,
0x08,0x88,0x48,0xc8,0x28,0xa8,0x68,0xe8,
0x18,0x98,0x58,0xd8,0x38,0xb8,0x78,0xf8,
0x04,0x84,0x44,0xc4,0x24,0xa4,0x64,0xe4,
0x14,0x94,0x54,0xd4,0x34,0xb4,0x74,0xf4,
0x0c,0x8c,0x4c,0xcc,0x2c,0xac,0x6c,0xec,
0x1c,0x9c,0x5c,0xdc,0x3c,0xbc,0x7c,0xfc,
0x02,0x82,0x42,0xc2,0x22,0xa2,0x62,0xe2,
0x12,0x92,0x52,0xd2,0x32,0xb2,0x72,0xf2,
0x0a,0x8a,0x4a,0xca,0x2a,0xaa,0x6a,0xea,
0x1a,0x9a,0x5a,0xda,0x3a,0xba,0x7a,0xfa,
0x06,0x86,0x46,0xc6,0x26,0xa6,0x66,0xe6,
0x16,0x96,0x56,0xd6,0x36,0xb6,0x76,0xf6,
0x0e,0x8e,0x4e,0xce,0x2e,0xae,0x6e,0xee,
0x1e,0x9e,0x5e,0xde,0x3e,0xbe,0x7e,0xfe,
0x01,0x81,0x41,0xc1,0x21,0xa1,0x61,0xe1,
0x11,0x91,0x51,0xd1,0x31,0xb1,0x71,0xf1,
0x09,0x89,0x49,0xc9,0x29,0xa9,0x69,0xe9,
0x19,0x99,0x59,0xd9,0x39,0xb9,0x79,0xf9,
0x05,0x85,0x45,0xc5,0x25,0xa5,0x65,0xe5,
0x15,0x95,0x55,0xd5,0x35,0xb5,0x75,0xf5,
0x0d,0x8d,0x4d,0xcd,0x2d,0xad,0x6d,0xed,
0x1d,0x9d,0x5d,0xdd,0x3d,0xbd,0x7d,0xfd,
0x03,0x83,0x43,0xc3,0x23,0xa3,0x63,0xe3,
0x13,0x93,0x53,0xd3,0x33,0xb3,0x73,0xf3,
0x0b,0x8b,0x4b,0xcb,0x2b,0xab,0x6b,0xeb,
0x1b,0x9b,0x5b,0xdb,0x3b,0xbb,0x7b,0xfb,
0x07,0x87,0x47,0xc7,0x27,0xa7,0x67,0xe7,
0x17,0x97,0x57,0xd7,0x37,0xb7,0x77,0xf7,
0x0f,0x8f,0x4f,0xcf,0x2f,0xaf,0x6f,0xef,
0x1f,0x9f,0x5f,0xdf,0x3f,0xbf,0x7f,0xff
};
extern struct pixrectops mem_ops;
static struct mpr_data mprd;
/*
* These define the biggest font that will successfully load.
*/
#define MAX_FONT_WIDTH 60
#define MAX_FONT_HEIGHT 60
static struct pixrect spr = {
&mem_ops,
256 * MAX_FONT_WIDTH,
MAX_FONT_HEIGHT,
1,
(caddr_t) &mprd
};
static struct pixfont *
StrikeToPixfont(fp)
FONT *fp;
{
register FontPriv *fpp = (FontPriv *) fp->data;
register struct pixfont *pf;
register int i, w;
register short *sh, limit;
register struct pixchar *pc;
pf = (struct pixfont *) malloc(sizeof(struct pixfont));
if (pf == (struct pixfont *) NULL) {
errno = ENOMEM;
return(pf);
}
bzero(pf, sizeof(struct pixfont));
limit = (fpp->wpitch / 2) * fp->height;
sh = (short *) fpp->fltable[0];
do {
*sh = ReverseShort(*sh);
sh++;
} while (--limit != -1);
mprd.md_linebytes = fpp->wpitch;
mprd.md_image = (short *) fpp->fltable[0];
bzero((caddr_t) pf, sizeof(struct pixfont));
pf->pf_defaultsize.y = fp->height;
if (fp->fixed) {
pf->pf_defaultsize.x = fp->avg_width;
}
/* for all the characters */
for (i = fp->first; i <= fp->last; i++) {
if ((w = fpp->widths[i]) < 0)
continue;
pc = &(pf->pf_char[i]);
pc->pc_pr = mem_create(w, fp->height, 1);
pc->pc_home.x = 0;
pc->pc_home.y = fp->height - fp->base;
pc->pc_adv.x = w;
pc->pc_adv.y = 0;
pr_rop(pc->pc_pr, 0, 0, w, fp->height, PIX_SRC,
&spr, fpp->leftarray[i], 0);
}
free((caddr_t) fpp->leftarray);
free((caddr_t) fpp->widths);
free((caddr_t) fpp->strike);
free((caddr_t) fpp->fltable);
free((caddr_t) fpp);
return(pf);
} /* end StrikeToPixfont() */
/*
* LoadXFont - load an xfont format file
*
* The FontData structure consists of {
* short f_characters[5]
* short f_firstChar
* short f_lastChar
* short f_leftArray[2]
* short f_baseline
* short f_spaceIndex
* short f_fixedWidth
* }
*
* The five shorts of f_characters[] are:
* [0] - location (in bytes) from start of file where font data begins
* [1] - unused
* [2] - width of font bitmap pointed at by [0]
* [3] - height of font bitmap
* [4] - bits per pixel of font bitmap
*
* The two shorts of f_leftArray[] are:
* [0] - location (in bytes) from start of file of bitmap offset array
* [1] - unused
*
*/
static FONT *
LoadXFont(fildes, name)
int fildes;
caddr_t name;
{
register int i, j;
int font_nbytes, totalWidth, datasiz, tablesiz;
char *fontdata;
short *offset_table, *width_table;
FONT *fp;
FontData font;
FontPriv *fpriv;
struct stat stb;
/* read in the xfont header */
if (read(fildes, (caddr_t) &font, sizeof(FontData)) !=
sizeof(FontData)) {
errno = EINVAL;
return (NULL);
}
/* byte swap */
Swap_shorts((short *) &font, sizeof(FontData) / sizeof(short));
/* determine the number of bytes in the bitmap */
font_nbytes = BitmapSize(font.f_characters[2], font.f_characters[3]);
/* stat the file to determine size */
fstat(fildes, &stb);
/* if the location of the offset table is > location of bitmap ... */
if (font.f_leftArray[0] > font.f_characters[0]) {
/* check for sufficient space for font bitmap */
if (font.f_leftArray[0] - font.f_characters[0] < font_nbytes) {
/* no */
errno = EINVAL;
return(NULL);
}
/* determine the space allocated for the offset table */
tablesiz = stb.st_size - font.f_leftArray[0];
/* determine the space allocated for the font data */
datasiz = font.f_leftArray[0] - font.f_characters[0];
} else {
/* check for sufficient space for font bitmap */
if (font_nbytes + font.f_characters[0] > stb.st_size) {
errno = EINVAL;
return(NULL);
}
/* determine the space allocated for the offset table */
tablesiz = font.f_characters[0] - font.f_leftArray[0];
/* determine the space allocated for the font data */
datasiz = stb.st_size - font.f_characters[0];
}
/* are we going to ask for more than we have? */
if (font_nbytes > datasiz) {
errno = EINVAL;
return(NULL);
}
/* allocate space for the font bitmap */
fontdata = (caddr_t) malloc(font_nbytes);
if (fontdata == (caddr_t) NULL) {
errno = ENOMEM;
return(NULL);
}
/* seek to start of bitmap */
lseek(fildes, (long) font.f_characters[0], 0);
/* read it in */
if (read(fildes, fontdata, font_nbytes) != font_nbytes) {
free(fontdata);
errno = EINVAL;
return (NULL);
}
/* byte swap */
Swap_shorts((short *) fontdata, font_nbytes / sizeof(short));
/* is there an offset table? */
if (tablesiz == 0) {
/* no -- this had better be a fixed width font */
if (font.f_fixedWidth == 0) {
free(fontdata);
errno = EINVAL;
return(NULL);
}
/* determine table size */
tablesiz = sizeof(short) *
(font.f_lastChar - font.f_firstChar + 2);
/* allocate space for table */
offset_table = (short *) malloc(tablesiz);
if (offset_table == (short *) NULL) {
free(fontdata);
errno = ENOMEM;
return(NULL);
}
/* zero out the offset table */
bzero(offset_table, tablesiz);
/* build the offset table */
for (j=0, i = font.f_firstChar; i < font.f_lastChar + 2; i++) {
offset_table[i] = j;
j += font.f_fixedWidth;
}
} else {
/* allocate space for table */
offset_table = (short *) malloc(tablesiz);
if (offset_table == (short *) NULL) {
free(fontdata);
errno = ENOMEM;
return(NULL);
}
/* zero out the offset table */
bzero(offset_table, tablesiz);
/* seek to offset array */
lseek(fildes, (long) font.f_leftArray[0], 0);
/* read the offset array */
if (read(fildes, (caddr_t) &offset_table[font.f_firstChar],
tablesiz) != tablesiz) {
free(fontdata);
free((caddr_t) offset_table);
errno = EINVAL;
return (NULL);
}
Swap_shorts(offset_table, tablesiz / sizeof(short));
}
/* allocate a width table -- to be built from the offset table */
width_table = (short *) malloc(tablesiz);
if (width_table == (short *) NULL) {
free(fontdata);
free((caddr_t) offset_table);
errno = ENOMEM;
return(NULL);
}
/* allocate space for the device dependent private font data */
fpriv = (FontPriv *) malloc(sizeof(FontPriv));
if (fpriv == (FontPriv *) NULL) {
free(fontdata);
free((caddr_t) offset_table);
free((caddr_t) width_table);
errno = ENOMEM;
return(NULL);
}
/* initialize */
fpriv->maxwidth = 0;
totalWidth = 0;
/* convert the offset table to the width table */
for (i = font.f_firstChar; i <= font.f_lastChar; i++) {
width_table[i] = offset_table[i + 1] - offset_table[i];
if (width_table[i] > fpriv->maxwidth) {
fpriv->maxwidth = width_table[i];
}
if (width_table[i] < 0) {
errno = EINVAL;
return(NULL);
}
totalWidth += width_table[i];
}
fpriv->widths = width_table;
fpriv->leftarray = offset_table;
/* allocate space for the strike font */
fpriv->strike = (BITMAP *) malloc(sizeof(BITMAP));
if (fpriv->strike == (BITMAP *) NULL) {
free(fontdata);
free((caddr_t) offset_table);
free((caddr_t) width_table);
free((caddr_t) fpriv);
errno = ENOMEM;
return(NULL);
}
/* determine the number of bytes per line of the bitmap */
fpriv->wpitch = (((font.f_characters[2] + 15) >> 3) & ~1);
/* set other strike stuff .. */
fpriv->strike->width = font.f_characters[2];
fpriv->strike->height = font.f_characters[3];
fpriv->strike->refcnt = 1;
fpriv->strike->data = (caddr_t) fontdata;
/* allocate space for the font line table */
fpriv->fltable = (char **) malloc(font.f_characters[3]*sizeof(char *));
if (fpriv->fltable == (char **) NULL) {
free(fontdata);
free((caddr_t) offset_table);
free((caddr_t) width_table);
free((caddr_t) fpriv->strike);
free((caddr_t) fpriv);
errno = ENOMEM;
return(NULL);
}
/* compute the font line table entries */
for (i = 0; i < font.f_characters[3]; i++) {
fpriv->fltable[i] = ((caddr_t) fontdata) + i * fpriv->wpitch;
}
/* allocate an xfont */
fp = (FONT *) malloc(sizeof(FONT));
if (fp == (FONT *) NULL) {
free(fontdata);
free((caddr_t) offset_table);
free((caddr_t) width_table);
free((caddr_t) fpriv->strike);
free((caddr_t) fpriv->fltable);
free((caddr_t) fpriv);
errno = ENOMEM;
return(NULL);
}
fp->first = font.f_firstChar;
fp->last = font.f_lastChar;
fp->height = font.f_characters[3];
fp->base = font.f_baseline;
fp->space = font.f_spaceIndex + font.f_firstChar;
fp->refcnt = 1;
/* set the average width */
fp->avg_width = totalWidth / (fp->last - fp->first + 1);
if (fp->avg_width == font.f_fixedWidth) {
fp->fixed = 1;
fpriv->maxwidth = fp->avg_width;
} else {
fp->fixed = 0;
}
/* allocate space for the name */
fp->name = (caddr_t) malloc(strlen(name) + 1);
if (fp->name == (caddr_t) NULL) {
free(fontdata);
free((caddr_t) offset_table);
free((caddr_t) width_table);
free((caddr_t) fpriv->fltable);
free((caddr_t) fpriv->strike);
free((caddr_t) fpriv);
free((caddr_t) fp);
errno = ENOMEM;
return(NULL);
}
/* copy the name */
(void) strcpy(fp->name, name);
/* change private font to pixfont */
fp->data = (caddr_t) fpriv;
fp->data = (caddr_t) StrikeToPixfont(fp);
return (fp);
} /* end LoadXFont() */
static FONT *
LoadVFont(fd, name)
int fd;
caddr_t name;
{
register int i;
int fixed = 1;
register struct pixfont *pf = (struct pixfont *) NULL;
register struct pixchar *pc;
FONT *fp;
FILE *fonts;
short magic;
struct header hd;
struct dispatch disp[NUM_DISPATCH];
struct stat stb;
int maxheight, maxwidth, maxup, maxdown;
#define fbase (sizeof hd + sizeof disp)
fonts = fdopen(fd, "r");
if (fonts == 0)
return (0);
if (fread(&hd, sizeof hd, 1, fonts) != 1 ||
fread(disp, sizeof disp, 1, fonts) != 1)
goto bad;
if (hd.magic != VFONT_MAGIC)
goto bad;
fstat(fd, &stb);
if (stb.st_size != fbase + hd.size)
goto bad;
/*
* Allocate font header and set default sizes. The default width of the
* font is taken to be the width of a lower-case a, if there is one.
* The default interline spacing is taken to be 3/2 the height of an
* upper-case A above the baseline.
*/
pf = (struct pixfont *) malloc(sizeof(struct pixfont));
if (pf == (struct pixfont *) NULL)
goto bad;
/* zero out the pixfont */
bzero(pf, sizeof(struct pixfont));
/* initialize */
maxwidth = maxup = maxdown = 0;
/* determine maximum width, up and down for font */
for (i = 0; i < NUM_DISPATCH; i++) {
register struct dispatch *d = &disp[i];
if (d->left + d->right > maxwidth)
maxwidth = d->left + d->right;
if (d->up > maxup)
maxup = d->up;
if (d->down > maxdown)
maxdown = d->down;
}
maxheight = maxup + maxdown;
pf->pf_defaultsize.x = maxwidth;
pf->pf_defaultsize.y = maxheight;
/* Create memory pixrects for characters of font. */
for (i = 0; i < NUM_DISPATCH; i++) {
register struct dispatch *d = &disp[i];
struct pr_size size;
struct pixrect *cpr;
int j, wb, ww;
short *sp;
/* pointer to character */
pc = &pf->pf_char[i];
/* if there is no glyph, there is no character */
if (d->nbytes == 0) {
pc->pc_pr = (struct pixrect *) NULL;
pc->pc_home.x = 0;
pc->pc_home.y = 0;
pc->pc_adv.x = 0;
pc->pc_adv.y = 0;
continue;
}
/* total character width */
size.x = d->left + d->right;
/* total character height */
size.y = d->up + d->down;
/* check for variable width */
if (size.x != 0 && pf->pf_defaultsize.x != size.x)
fixed = 0;
/* get width in bytes and words */
wb = (size.x + 7) >> 3;
ww = (size.x + 15) >> 4;
/* create a memory pixrect for character */
if ((cpr = mem_create(size, 1)) == (struct pixrect *) NULL)
goto bad;
/* pointer to pixrect data */
sp = mpr_d(cpr)->md_image;
/* seek to character */
fseek(fonts, fbase + d->addr, 0);
/* read in the bytes */
for (j = 0; j < size.y; j++) {
fread((caddr_t) sp, wb, 1, fonts);
sp += ww;
}
/* check to make sure all characters are the same height */
if (size.y != maxheight) {
register struct pixrect *npr;
npr = mem_create(size.x, maxheight, 1);
if (npr == (struct pixrect *) NULL)
goto bad;
d->up = maxup - d->up;
pr_rop(npr, 0, d->up, size.x, maxheight,
PIX_SRC, cpr, 0, 0);
(void) pr_destroy(cpr);
cpr = npr;
}
/* set character pixrect pointer */
pc->pc_pr = cpr;
/* home from left edge */
pc->pc_home.x = -d->left;
/* home from baseline */
pc->pc_home.y = -d->up;
/* character horizonal advance */
pc->pc_adv.x = d->width;
/* character vertical advance (vfont == 0) */
pc->pc_adv.y = 0;
}
goto good;
bad:
free(pf);
errno = EINVAL;
return(NULL);
good:
fclose(fonts);
/* allocate space for the X font description */
if ((fp = (FONT *) malloc(sizeof(FONT))) == (FONT *) NULL) {
free((caddr_t) pf);
errno = ENOMEM;
return(NULL);
}
/* allocate space for font name */
if ((fp->name = malloc(strlen(name) + 1)) == NULL) {
free((caddr_t) pf);
free((caddr_t) fp);
errno = ENOMEM;
return(NULL);
}
/* copy the name */
(void) strcpy(name, fp->name);
/* set the X font attributes */
if (fixed == 1) {
fp->fixed = 1;
fp->avg_width = pf->pf_defaultsize.x;
} else {
fp->fixed = 0;
fp->avg_width = 0;
}
fp->first = 0;
fp->last = 255;
fp->space = 32;
fp->height = maxheight;
fp->base = maxdown;
fp->refcnt = 1;
fp->data = (caddr_t) pf;
return(fp);
} /* end LoadVFont() */
static int
OpenFile(FileName, type_ptr)
char *FileName;
int *type_ptr;
{
int fd;
struct header hdrbuf;
/* open the file */
if ((fd = open(FileName, O_RDONLY, 0)) < 0) {
return(-1);
}
/* read header buffer */
if (read(fd, (caddr_t) &hdrbuf, sizeof(struct header)) ==
sizeof(struct header)) {
/* read \something/ -- now check the magic number */
if (hdrbuf.magic == VFONT_MAGIC) {
/* VFONT */
*type_ptr = VFONT;
} else {
/* XFONT */
*type_ptr = XFONT;
}
/* rewind */
(void) lseek(fd, (long) 0, 0);
/* return the file descriptor */
return(fd);
}
/* bad read -- close and return -1 */
close(fd);
return(-1);
} /* end OpenFile() */
static caddr_t
SearchXFontPath(fname)
register caddr_t fname;
{
register caddr_t cp, pp, c2p;
static char xfontpath[MAXPATHLEN];
/* check for an absolute pathname */
if (*fname == '/') {
if (access(fname, R_OK) == 0)
return(fname);
else
return((caddr_t) NULL);
}
/* get the environment variable for XFONTPATH */
if ((pp = getenv("XFONTPATH")) == (caddr_t) NULL) {
pp = DEFAULT_FONT_PATH;
}
for (; *pp != '\0'; pp++) {
for (cp = xfontpath; *pp != ':' && *pp != '\0'; *cp++ = *pp++);
*cp++ = '/';
for (c2p = fname; *c2p != '\0'; *cp++ = *c2p++);
for (c2p = DEFAULT_FONT_SUFFIX; *c2p != '\0'; *cp++ = *c2p++);
*cp = '\0';
if (access(xfontpath, R_OK) == 0) {
return(xfontpath);
}
}
return ((caddr_t) NULL);
} /* end SearchXFontPath() */
static int
FindFile(name, font_type)
char *name;
int *font_type;
{
caddr_t pathname;
int fd;
if ((pathname = SearchXFontPath(name)) == (caddr_t) NULL) {
return(-1);
}
if ((fd = OpenFile(pathname, font_type)) < 0) {
return(-1);
}
return(fd);
} /* end FindFile() */
extern FONT *
GetFont(name)
caddr_t name;
{
int fd, type;
FONT *fp;
if ((fd = FindFile(name, &type)) < 0) {
errno = EINVAL;
return ((FONT *) NULL);
}
switch (type) {
case VFONT:
fp = LoadVFont(fd, name);
break;
case XFONT:
fp = LoadXFont(fd, name);
break;
default:
close(fd);
errno = EINVAL;
return((FONT *) NULL);
} /* end switch */
close(fd);
if (fp == (FONT *) NULL) {
errno = EINVAL;
return((FONT *) NULL);
}
return(fp);
} /* end GetFont() */
FreeFont(font)
FONT *font;
{
pf_close((caddr_t) font->data);
free(font->name);
free((caddr_t) font);
}
#endif sun