checkpoint: VT1200 reverse-engineering workspace before board-model work

This commit is contained in:
SDD committed 2026-10-16 01:37:50 +03:00
commit acb92d3e44
325 files changed
+951894

No files matched your search

+18
View File
@@ -0,0 +1,18 @@
DEC VT-1000 v1.2
Firmware read by Dave McGuire <mcguire@lssmuseum.org> on 12/13/2025.
EPROM type: 27C010
102e9.hex
103e9.hex
104e9.hex
105e9.hex
106e9.hex
107e9.hex
108e9.hex
109e9.hex
110e9.hex
111e9.hex
112e9.hex
113e9.hex
Binary file not shown.
+171
View File
@@ -0,0 +1,171 @@
000000: a7c5 MOVE -*A14,A5,1
000010: a7c6 MOVE -*A14,A6,1
000020: a7c3 MOVE -*A14,A3,1
000030: a7c4 MOVE -*A14,A4,1
000040: 4c61 MOVE A3,A1
000050: 4ca2 MOVE A5,A2
000060: 2583 SLL Ch,A3
000070: 2fc3 SRL 2h,A3
000080: 4c88 MOVE A4,A8
000090: ca03 JREQ D0h
0000a0: 2d48 SRL 16h,A8
0000b0: 5503 OR A8,A3
0000c0: 2544 SLL Ah,A4
0000d0: 2585 SLL Ch,A5
0000e0: 2fc5 SRL 2h,A5
0000f0: 4cc8 MOVE A6,A8
000100: ca03 JREQ 140h
000110: 2d48 SRL 16h,A8
000120: 5505 OR A8,A5
000130: 2546 SLL Ah,A6
000140: 2421 SLL 1h,A1
000150: 4600 SUBB A0,A0
000160: 2422 SLL 1h,A2
000170: 4708 SUBB A8,A8
000180: 2d61 SRL 15h,A1
000190: 2d62 SRL 15h,A2
0001a0: 09c7 07ff MOVI 7FFh,A7
0001c0: 48e1 CMP A7,A1
0001d0: ca00 0082 JREQ A10h
0001f0: 48e2 CMP A7,A2
000200: ca00 0084 JREQ A60h
000220: 4441 SUB A2,A1
000230: ca03 JREQ 270h
000240: c608 JRLE 2D0h
000250: 4022 ADD A1,A2
000260: c010 JR 370h
000270: 4865 CMP A3,A5
000280: c40e JRLT 370h
000290: c704 JRGT 2E0h
0002a0: 4886 CMP A4,A6
0002b0: c20b JRLS 370h
0002c0: c004 JR 310h
0002d0: 03a1 NEG A1
0002e0: 4c67 MOVE A3,A7
0002f0: 4ca3 MOVE A5,A3
000300: 4ce5 MOVE A7,A5
000310: 4c87 MOVE A4,A7
000320: 4cc4 MOVE A6,A4
000330: 4ce6 MOVE A7,A6
000340: 4c07 MOVE A0,A7
000350: 4d00 MOVE A8,A0
000360: 4ce8 MOVE A7,A8
000370: 4c21 MOVE A1,A1
000380: ca18 JREQ 510h
000390: 0b41 ffe1 CMPI 1Eh,A1
0003b0: c40e JRLT 4A0h
0003c0: 0b41 ffc2 CMPI 3Dh,A1
0003e0: c708 JRGT 470h
0003f0: 17c1 SUBK 1Eh,A1
000400: 2445 SLL 2h,A5
000410: 2c46 SRL 1Eh,A6
000420: 54a6 OR A5,A6
000430: 56a5 CLR A5
000440: 03a1 NEG A1
000450: 6626 SRL A1,A6
000460: c00a JR 510h
000470: 56a5 CLR A5
000480: 56c6 CLR A6
000490: c007 JR 510h
0004a0: 4ca7 MOVE A5,A7
0004b0: 03a1 NEG A1
0004c0: 6625 SRL A1,A5
0004d0: 6626 SRL A1,A6
0004e0: 1001 ADDK 20h,A1
0004f0: 6227 SLL A1,A7
000500: 54e6 OR A7,A6
000510: 4808 CMP A0,A8
000520: ca26 JREQ 790h
000530: 44c4 SUB A6,A4
000540: 46a3 SUBB A5,A3
000550: 6a67 LMO A3,A7
000560: ca0a JREQ 610h
000570: 1447 SUBK 2h,A7
000580: ca10 JREQ 690h
000590: 44e2 SUB A7,A2
0005a0: 62e3 SLL A7,A3
0005b0: 4c81 MOVE A4,A1
0005c0: 62e4 SLL A7,A4
0005d0: 1407 SUBK 20h,A7
0005e0: 66e1 SRL A7,A1
0005f0: 5423 OR A1,A3
000600: c008 JR 690h
000610: 6a87 LMO A4,A7
000620: ca3b JREQ 9E0h
000630: 17c2 SUBK 1Eh,A2
000640: 68e4 RL A7,A4
000650: 4c83 MOVE A4,A3
000660: 2fc3 SRL 2h,A3
000670: 27c4 SLL 1Eh,A4
000680: 44e2 SUB A7,A2
000690: 1ec4 BTST 9h,A4
0006a0: ca1a JREQ 850h
0006b0: 56e7 CLR A7
0006c0: 0b04 0400 ADDI 400h,A4
0006e0: 42e3 ADDC A7,A3
0006f0: 1c23 BTST 1Eh,A3
000700: ca14 JREQ 850h
000710: 1022 INC A2
000720: 2fe4 SRL 1h,A4
000730: 2fe3 SRL 1h,A3
000740: c910 JRNC 850h
000750: 0ba4 0000 8000 ORI 80000000h,A4
000780: c00c JR 850h
000790: 40c4 ADD A6,A4
0007a0: 42a3 ADDC A5,A3
0007b0: 1c23 BTST 1Eh,A3
0007c0: caec JREQ 690h
0007d0: 1022 INC A2
0007e0: 2fe4 SRL 1h,A4
0007f0: 2fe3 SRL 1h,A3
000800: c9e8 JRNC 690h
000810: 0ba4 0000 8000 ORI 80000000h,A4
000840: c0e4 JR 690h
000850: 4c42 MOVE A2,A2
000860: c433 JRLT BA0h
000870: cb05 JRNE 8D0h
000880: 4c63 MOVE A3,A3
000890: cb30 JRNE BA0h
0008a0: 4c84 MOVE A4,A4
0008b0: cb2e JRNE BA0h
0008c0: c011 JR 9E0h
0008d0: 0b42 f800 CMPI 7FFh,A2
0008f0: c524 JRGE B40h
000900: 4c68 MOVE A3,A8
000910: 2ec3 SRL Ah,A3
000920: 2ec4 SRL Ah,A4
000930: 26c8 SLL 16h,A8
000940: 5504 OR A8,A4
000950: 27e0 SLL 1Fh,A0
000960: 2682 SLL 14h,A2
000970: 5443 OR A2,A3
000980: 5403 OR A0,A3
000990: 928e MOVE A4,*A14+,1
0009a0: 926e MOVE A3,*A14+,1
0009b0: 09af 00ff MMFM SP,A0-A7
0009d0: 0960 RETS
0009e0: 5663 CLR A3
0009f0: 5684 CLR A4
000a00: c0f8 JR 990h
000a10: 48e2 CMP A7,A2
000a20: cb04 JRNE A70h
000a30: 4808 CMP A0,A8
000a40: cb0c JRNE B10h
000a50: c001 JR A70h
000a60: 4d00 MOVE A8,A0
000a70: 5621 CLR A1
000a80: 27e0 SLL 1Fh,A0
000a90: 0ba0 0000 7ff0 ORI 7FF00000h,A0
000ac0: 922e MOVE A1,*A14+,1
000ad0: 920e MOVE A0,*A14+,1
000ae0: 09af 00ff MMFM SP,A0-A7
000b00: 0960 RETS
000b10: 1887 MOVK 4h,A7
000b20: 5600 CLR A0
000b30: c008 JR BC0h
000b40: 18a7 MOVK 5h,A7
000b50: 27e0 SLL 1Fh,A0
000b60: 0ba0 0000 7ff0 ORI 7FF00000h,A0
000b90: c002 JR BC0h
000ba0: 1987 MOVK Ch,A7
000bb0: 5600 CLR A0
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
+2
View File
@@ -0,0 +1,2 @@
1
probe-dec2.snf VT1200PROBE1
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
File diff suppressed because it is too large. Load diff
Binary file not shown.

After

Width:  |  Height:  |  Size: 3.1 MiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 328 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 455 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.0 MiB

+908
View File
@@ -0,0 +1,908 @@
/************************************************************************
Copyright 1989 by Digital Equipment Corporation, Maynard, Massachusetts,
and the Massachusetts Institute of Technology, Cambridge, Massachusetts.
All Rights Reserved
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 Digital or MIT not be
used in advertising or publicity pertaining to distribution of the
software without specific, written prior permission.
DIGITAL DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE, INCLUDING
ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO EVENT SHALL
DIGITAL BE LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR
ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS,
WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION,
ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS
SOFTWARE.
************************************************************************/
/* $XConsortium: bdfread.c,v 1.13 92/05/12 18:07:40 gildea Exp $ */
#include <ctype.h>
#include "fontfilest.h"
/* use bitmap structure */
#include "bitmap.h"
#include "bdfint.h"
#define INDICES 256
#define MAXENCODING 0xFFFF
#define BDFLINELEN 1024
extern int bitmapGetGlyphs(), bitmapGetMetrics();
extern int bitmapGetBitmaps(), bitmapGetExtents();
void bdfUnloadFont();
static Bool bdfPadToTerminal();
/***====================================================================***/
static Bool
bdfReadBitmap(pCI, file, bit, byte, glyph, scan, sizes)
CharInfoPtr pCI;
FontFilePtr file;
int bit,
byte,
glyph,
scan;
int sizes[GLYPHPADOPTIONS];
{
int widthBits,
widthBytes,
widthHexChars;
int height,
row;
int i,
inLineLen,
nextByte;
Bool badbits;
unsigned char *pInBits,
*picture,
*line = NULL;
char lineBuf[BDFLINELEN];
widthBits = GLYPHWIDTHPIXELS(pCI);
height = GLYPHHEIGHTPIXELS(pCI);
widthBytes = BYTES_PER_ROW(widthBits, glyph);
if (widthBytes * height > 0) {
picture = (unsigned char *) xalloc(widthBytes * height);
if (!picture)
goto BAILOUT;
} else
picture = NULL;
pCI->bits = (char *) picture;
if (sizes) {
for (i = 0; i < GLYPHPADOPTIONS; i++)
sizes[i] += BYTES_PER_ROW(widthBits, (1 << i)) * height;
}
badbits = FALSE;
nextByte = 0;
widthHexChars = BYTES_PER_ROW(widthBits, 1);
/* 5/31/89 (ef) -- hack, hack, hack. what *am* I supposed to do with */
/* 0 width characters? */
for (row = 0; row < height; row++) {
line = bdfGetLine(file, lineBuf, BDFLINELEN);
if (!line)
break;
if (widthBits == 0) {
if ((!line) || (bdfIsPrefix(line, "ENDCHAR")))
break;
else
continue;
}
pInBits = line;
inLineLen = strlen((char *) pInBits);
if (inLineLen & 1) {
bdfError("odd number of characters in hex encoding\n");
line[inLineLen++] = '0';
line[inLineLen] = '\0';
}
inLineLen >>= 1;
i = inLineLen;
if (i > widthHexChars)
i = widthHexChars;
for (; i > 0; i--, pInBits += 2)
picture[nextByte++] = bdfHexByte(pInBits);
/* pad if line is too short */
if (inLineLen < widthHexChars) {
for (i = widthHexChars - inLineLen; i > 0; i--)
picture[nextByte++] = 0;
} else {
unsigned char mask;
mask = 0xff << (8 - (widthBits & 0x7));
if (mask && picture[nextByte - 1] & ~mask) {
picture[nextByte - 1] &= mask;
badbits = TRUE;
} else if (inLineLen > widthHexChars)
badbits = TRUE;
}
if (widthBytes > widthHexChars) {
i = widthBytes - widthHexChars;
while (i-- > 0)
picture[nextByte++] = 0;
}
}
if ((line && (!bdfIsPrefix(line, "ENDCHAR"))) || (height == 0))
line = bdfGetLine(file, lineBuf, BDFLINELEN);
if ((!line) || (!bdfIsPrefix(line, "ENDCHAR"))) {
bdfError("missing 'ENDCHAR'\n");
goto BAILOUT;
}
if (nextByte != height * widthBytes) {
bdfError("bytes != rows * bytes_per_row (%d != %d * %d)\n",
nextByte, height, widthBytes);
goto BAILOUT;
}
if (picture != NULL) {
if (bit == LSBFirst)
BitOrderInvert(picture, nextByte);
if (bit != byte) {
if (scan == 2)
TwoByteSwap(picture, nextByte);
else if (scan == 4)
FourByteSwap(picture, nextByte);
}
}
return (TRUE);
BAILOUT:
if (picture)
xfree(picture);
pCI->bits = NULL;
return (FALSE);
}
/***====================================================================***/
static Bool
bdfSkipBitmap(file, height)
FontFilePtr file;
int height;
{
unsigned char *line;
int i = 0;
char lineBuf[BDFLINELEN];
do {
line = bdfGetLine(file, lineBuf, BDFLINELEN);
i++;
} while (line && !bdfIsPrefix(line, "ENDCHAR") && i <= height);
if (i > 1 && line && !bdfIsPrefix(line, "ENDCHAR")) {
bdfError("Error in bitmap, missing 'ENDCHAR'\n");
return (FALSE);
}
return (TRUE);
}
/***====================================================================***/
static Bool
bdfReadCharacters(file, pFont, pState, bit, byte, glyph, scan)
FontFilePtr file;
FontPtr pFont;
bdfFileState *pState;
int bit,
byte,
glyph,
scan;
{
unsigned char *line;
register CharInfoPtr ci;
int i,
ndx,
nchars,
nignored;
unsigned int char_row, char_col;
int numEncodedGlyphs = 0;
CharInfoPtr *bdfEncoding[256];
BitmapFontPtr bitmapFont;
BitmapExtraPtr bitmapExtra;
CARD32 *bitmapsSizes;
char lineBuf[BDFLINELEN];
int nencoding;
bitmapFont = (BitmapFontPtr) pFont->fontPrivate;
bitmapExtra = (BitmapExtraPtr) bitmapFont->bitmapExtra;
if (bitmapExtra) {
bitmapsSizes = bitmapExtra->bitmapsSizes;
for (i = 0; i < GLYPHPADOPTIONS; i++)
bitmapsSizes[i] = 0;
} else
bitmapsSizes = NULL;
bzero(bdfEncoding, sizeof(bdfEncoding));
bitmapFont->metrics = NULL;
ndx = 0;
line = bdfGetLine(file, lineBuf, BDFLINELEN);
if ((!line) || (sscanf((char *) line, "CHARS %d", &nchars) != 1)) {
bdfError("bad 'CHARS' in bdf file\n");
return (FALSE);
}
if (nchars < 1) {
bdfError("invalid number of CHARS in BDF file\n");
return (FALSE);
}
ci = (CharInfoPtr) xalloc(nchars * sizeof(CharInfoRec));
if (!ci) {
bdfError("Couldn't allocate pCI (%d*%d)\n", nchars,
sizeof(CharInfoRec));
goto BAILOUT;
}
bitmapFont->metrics = ci;
if (bitmapExtra) {
bitmapExtra->glyphNames = (Atom *) xalloc(nchars * sizeof(Atom));
if (!bitmapExtra->glyphNames) {
bdfError("Couldn't allocate glyphNames (%d*%d)\n",
nchars, sizeof(Atom));
goto BAILOUT;
}
}
if (bitmapExtra) {
bitmapExtra->sWidths = (int *) xalloc(nchars * sizeof(int));
if (!bitmapExtra->sWidths) {
bdfError("Couldn't allocate sWidth (%d *%d)\n",
nchars, sizeof(int));
return FALSE;
}
}
line = bdfGetLine(file, lineBuf, BDFLINELEN);
pFont->info.firstRow = 256;
pFont->info.lastRow = 0;
pFont->info.firstCol = 256;
pFont->info.lastCol = 0;
nignored = 0;
for (ndx = 0; (ndx < nchars) && (line) && (bdfIsPrefix(line, "STARTCHAR"));) {
int t;
int wx; /* x component of width */
int wy; /* y component of width */
int bw; /* bounding-box width */
int bh; /* bounding-box height */
int bl; /* bounding-box left */
int bb; /* bounding-box bottom */
int enc,
enc2; /* encoding */
unsigned char *p; /* temp pointer into line */
char charName[100];
int ignore;
if (sscanf((char *) line, "STARTCHAR %s", charName) != 1) {
bdfError("bad character name in BDF file\n");
goto BAILOUT; /* bottom of function, free and return error */
}
if (bitmapExtra)
bitmapExtra->glyphNames[ndx] = bdfForceMakeAtom(charName, NULL);
line = bdfGetLine(file, lineBuf, BDFLINELEN);
if (!line || (t = sscanf((char *) line, "ENCODING %d %d", &enc, &enc2)) < 1) {
bdfError("bad 'ENCODING' in BDF file\n");
goto BAILOUT;
}
if (enc < -1 || t == 2 && enc2 < -1) {
bdfError("bad ENCODING value");
goto BAILOUT;
}
if (t == 2 && enc == -1)
enc = enc2;
ignore = 0;
if (enc == -1) {
if (!bitmapExtra) {
nignored++;
ignore = 1;
}
} else if (enc > MAXENCODING) {
bdfError("char '%s' has encoding too large (%d)\n",
charName, enc);
} else {
char_row = (enc >> 8) & 0xFF;
char_col = enc & 0xFF;
if (char_row < pFont->info.firstRow)
pFont->info.firstRow = char_row;
if (char_row > pFont->info.lastRow)
pFont->info.lastRow = char_row;
if (char_col < pFont->info.firstCol)
pFont->info.firstCol = char_col;
if (char_col > pFont->info.lastCol)
pFont->info.lastCol = char_col;
if (bdfEncoding[char_row] == (CharInfoPtr *) NULL) {
bdfEncoding[char_row] =
(CharInfoPtr *) xalloc(256 * sizeof(CharInfoPtr));
if (!bdfEncoding[char_row]) {
bdfError("Couldn't allocate row %d of encoding (%d*%d)\n",
char_row, INDICES, sizeof(CharInfoPtr));
goto BAILOUT;
}
for (i = 0; i < 256; i++)
bdfEncoding[char_row][i] = (CharInfoPtr) NULL;
}
if (bdfEncoding[char_row] != NULL) {
bdfEncoding[char_row][char_col] = ci;
numEncodedGlyphs++;
}
}
line = bdfGetLine(file, lineBuf, BDFLINELEN);
if ((!line) || (sscanf((char *) line, "SWIDTH %d %d", &wx, &wy) != 2)) {
bdfError("bad 'SWIDTH'\n");
goto BAILOUT;
}
if (wy != 0) {
bdfError("SWIDTH y value must be zero\n");
goto BAILOUT;
}
if (bitmapExtra)
bitmapExtra->sWidths[ndx] = wx;
/* 5/31/89 (ef) -- we should be able to ditch the character and recover */
/* from all of these. */
line = bdfGetLine(file, lineBuf, BDFLINELEN);
if ((!line) || (sscanf((char *) line, "DWIDTH %d %d", &wx, &wy) != 2)) {
bdfError("bad 'DWIDTH'\n");
goto BAILOUT;
}
if (wy != 0) {
bdfError("DWIDTH y value must be zero\n");
goto BAILOUT;
}
line = bdfGetLine(file, lineBuf, BDFLINELEN);
if ((!line) || (sscanf((char *) line, "BBX %d %d %d %d", &bw, &bh, &bl, &bb) != 4)) {
bdfError("bad 'BBX'\n");
goto BAILOUT;
}
if ((bh < 0) || (bw < 0)) {
bdfError("character '%s' has a negative sized bitmap, %dx%d\n",
charName, bw, bh);
goto BAILOUT;
}
line = bdfGetLine(file, lineBuf, BDFLINELEN);
if ((line) && (bdfIsPrefix(line, "ATTRIBUTES"))) {
for (p = line + strlen("ATTRIBUTES ");
(*p == ' ') || (*p == '\t');
p++)
/* empty for loop */ ;
ci->metrics.attributes = bdfHexByte(p) << 8 + bdfHexByte(p + 2);
line = bdfGetLine(file, lineBuf, BDFLINELEN);
} else
ci->metrics.attributes = 0;
if (!line || !bdfIsPrefix(line, "BITMAP")) {
bdfError("missing 'BITMAP'\n");
goto BAILOUT;
}
/* collect data for generated properties */
if ((strlen(charName) == 1)) {
if ((charName[0] >= '0') && (charName[0] <= '9')) {
pState->digitWidths += wx;
pState->digitCount++;
} else if (charName[0] == 'x') {
pState->exHeight = (bh + bb) <= 0 ? bh : bh + bb;
}
}
if (!ignore) {
ci->metrics.leftSideBearing = bl;
ci->metrics.rightSideBearing = bl + bw;
ci->metrics.ascent = bh + bb;
ci->metrics.descent = -bb;
ci->metrics.characterWidth = wx;
ci->bits = NULL;
bdfReadBitmap(ci, file, bit, byte, glyph, scan, bitmapsSizes);
ci++;
ndx++;
} else
bdfSkipBitmap(file, bh);
line = bdfGetLine(file, lineBuf, BDFLINELEN); /* get STARTCHAR or
* ENDFONT */
}
if (ndx + nignored != nchars) {
bdfError("%d too few characters\n", nchars - (ndx + nignored));
goto BAILOUT;
}
nchars = ndx;
bitmapFont->num_chars = nchars;
if ((line) && (bdfIsPrefix(line, "STARTCHAR"))) {
bdfError("more characters than specified\n");
goto BAILOUT;
}
if ((!line) || (!bdfIsPrefix(line, "ENDFONT"))) {
bdfError("missing 'ENDFONT'\n");
goto BAILOUT;
}
if (numEncodedGlyphs == 0)
bdfWarning("No characters with valid encodings\n");
nencoding = (pFont->info.lastRow - pFont->info.firstRow + 1) *
(pFont->info.lastCol - pFont->info.firstCol + 1);
bitmapFont->encoding = (CharInfoPtr *) xalloc(nencoding * sizeof(CharInfoPtr));
if (!bitmapFont->encoding) {
bdfError("Couldn't allocate ppCI (%d,%d)\n",
nencoding,
sizeof(CharInfoPtr));
goto BAILOUT;
}
pFont->info.allExist = TRUE;
i = 0;
for (char_row = pFont->info.firstRow;
char_row <= pFont->info.lastRow;
char_row++) {
if (bdfEncoding[char_row] == (CharInfoPtr *) NULL) {
pFont->info.allExist = FALSE;
for (char_col = pFont->info.firstCol;
char_col <= pFont->info.lastCol;
char_col++) {
bitmapFont->encoding[i++] = NullCharInfo;
}
} else {
for (char_col = pFont->info.firstCol;
char_col <= pFont->info.lastCol;
char_col++) {
if (!bdfEncoding[char_row][char_col])
pFont->info.allExist = FALSE;
bitmapFont->encoding[i++] = bdfEncoding[char_row][char_col];
}
}
}
for (i = 0; i < 256; i++)
if (bdfEncoding[i])
xfree(bdfEncoding[i]);
return (TRUE);
BAILOUT:
for (i = 0; i < 256; i++)
if (bdfEncoding[i])
xfree(bdfEncoding[i]);
/* bdfFreeFontBits will clean up the rest */
return (FALSE);
}
/***====================================================================***/
Bool
bdfReadHeader(file, pState)
FontFilePtr file;
bdfFileState *pState;
{
unsigned char *line;
char namebuf[BDFLINELEN];
int tmp;
char lineBuf[BDFLINELEN];
line = bdfGetLine(file, lineBuf, BDFLINELEN);
if (!line || sscanf((char *) line, "STARTFONT %s", namebuf) != 1 ||
!bdfStrEqual(namebuf, "2.1")) {
bdfError("bad 'STARTFONT'\n");
return (FALSE);
}
line = bdfGetLine(file, lineBuf, BDFLINELEN);
if (!line || sscanf((char *) line, "FONT %[^\n]", pState->fontName) != 1) {
bdfError("bad 'FONT'\n");
return (FALSE);
}
line = bdfGetLine(file, lineBuf, BDFLINELEN);
if (!line || !bdfIsPrefix(line, "SIZE")) {
bdfError("missing 'SIZE'\n");
return (FALSE);
}
if (sscanf((char *) line, "SIZE %f%d%d", &pState->pointSize,
&pState->resolution_x, &pState->resolution_y) != 3) {
bdfError("bad 'SIZE'\n");
return (FALSE);
}
if (pState->pointSize < 1 ||
pState->resolution_x < 1 || pState->resolution_y < 1) {
bdfError("SIZE values must be > 0\n");
return (FALSE);
}
line = bdfGetLine(file, lineBuf, BDFLINELEN);
if (!line || !bdfIsPrefix(line, "FONTBOUNDINGBOX")) {
bdfError("missing 'FONTBOUNDINGBOX'\n");
return (FALSE);
}
return (TRUE);
}
/***====================================================================***/
static Bool
bdfReadProperties(file, pFont, pState)
FontFilePtr file;
FontPtr pFont;
bdfFileState *pState;
{
int nProps,
nextProp;
char *stringProps;
FontPropPtr props;
char namebuf[BDFLINELEN],
secondbuf[BDFLINELEN],
thirdbuf[BDFLINELEN];
unsigned char *line;
char lineBuf[BDFLINELEN];
BitmapFontPtr bitmapFont = (BitmapFontPtr) pFont->fontPrivate;
line = bdfGetLine(file, lineBuf, BDFLINELEN);
if (!line || !bdfIsPrefix(line, "STARTPROPERTIES")) {
bdfError(file, "missing 'STARTPROPERTIES'\n");
return (FALSE);
}
if (sscanf((char *) line, "STARTPROPERTIES %d", &nProps) != 1) {
bdfError("bad 'STARTPROPERTIES'\n");
return (FALSE);
}
pFont->info.isStringProp = NULL;
pFont->info.props = NULL;
stringProps = (char *) xalloc((nProps + BDF_GENPROPS) * sizeof(char));
pFont->info.isStringProp = stringProps;
if (stringProps == NULL) {
bdfError("Couldn't allocate stringProps (%d*%d)\n",
(nProps + BDF_GENPROPS), sizeof(Bool));
goto BAILOUT;
}
pFont->info.props = props = (FontPropPtr) xalloc((nProps + BDF_GENPROPS) *
sizeof(FontPropRec));
if (props == NULL) {
bdfError("Couldn't allocate props (%d*%d)\n", (nProps + BDF_GENPROPS,
sizeof(FontPropRec)));
goto BAILOUT;
}
nextProp = 0;
while (nProps-- > 0) {
line = bdfGetLine(file, lineBuf, BDFLINELEN);
if (line == NULL || bdfIsPrefix(line, "ENDPROPERTIES")) {
bdfError("%d too few properites\n", nProps + 1);
goto BAILOUT;
}
while (*line && isspace(*line))
line++;
switch (sscanf((char *) line, "%s%s%s", namebuf, secondbuf, thirdbuf)) {
default:
bdfError("missing '%s' parameter value\n", namebuf);
goto BAILOUT;
break;
case 2:
/*
* Possibilites include: valid quoted string with no white space
* valid integer value invalid value
*/
if (secondbuf[0] == '"') {
stringProps[nextProp] = TRUE;
props[nextProp].value =
bdfGetPropertyValue(line + strlen(namebuf) + 1);
if (!props[nextProp].value)
goto BAILOUT;
break;
} else if (bdfIsInteger(secondbuf)) {
stringProps[nextProp] = FALSE;
props[nextProp].value = atoi(secondbuf);
break;
} else {
bdfError("invalid '%s' parameter value\n", namebuf);
goto BAILOUT;
}
case 3:
/*
* Possibilites include: valid quoted string with some white space
* invalid value (reject even if second string is integer)
*/
if (secondbuf[0] == '"') {
stringProps[nextProp] = TRUE;
props[nextProp].value =
bdfGetPropertyValue(line + strlen(namebuf) + 1);
if (!props[nextProp].value)
goto BAILOUT;
break;
} else {
bdfError("invalid '%s' parameter value\n", namebuf);
goto BAILOUT;
}
}
props[nextProp].name = bdfForceMakeAtom(namebuf, NULL);
if (props[nextProp].name == None) {
bdfError("Empty property name.\n");
goto BAILOUT;
}
if (!bdfSpecialProperty(pFont, &props[nextProp],
stringProps[nextProp], pState))
nextProp++;
}
line = bdfGetLine(file, lineBuf, BDFLINELEN);
if (!line || !bdfIsPrefix(line, "ENDPROPERTIES")) {
bdfError("missing 'ENDPROPERTIES'\n");
goto BAILOUT;
}
if (!pState->haveFontAscent || !pState->haveFontDescent) {
bdfError("missing 'FONT_ASCENT' or 'FONT_DESCENT' properties\n");
goto BAILOUT;
}
if (bitmapFont->bitmapExtra) {
bitmapFont->bitmapExtra->info.fontAscent = pFont->info.fontAscent;
bitmapFont->bitmapExtra->info.fontDescent = pFont->info.fontDescent;
}
if (!pState->pointSizeProp) {
props[nextProp].name = bdfForceMakeAtom("POINT_SIZE", NULL);
props[nextProp].value = (INT32) (pState->pointSize * 10.0);
stringProps[nextProp] = FALSE;
pState->pointSizeProp = &props[nextProp];
nextProp++;
}
if (!pState->fontProp) {
props[nextProp].name = bdfForceMakeAtom("FONT", NULL);
props[nextProp].value = (INT32) bdfForceMakeAtom(pState->fontName, NULL);
stringProps[nextProp] = TRUE;
pState->fontProp = &props[nextProp];
nextProp++;
}
if (!pState->weightProp) {
props[nextProp].name = bdfForceMakeAtom("WEIGHT", NULL);
props[nextProp].value = -1; /* computed later */
stringProps[nextProp] = FALSE;
pState->weightProp = &props[nextProp];
nextProp++;
}
if (!pState->resolutionProp &&
pState->resolution_x == pState->resolution_y) {
props[nextProp].name = bdfForceMakeAtom("RESOLUTION", NULL);
props[nextProp].value = (INT32) ((pState->resolution_x * 100.0) / 72.27);
stringProps[nextProp] = FALSE;
pState->resolutionProp = &props[nextProp];
nextProp++;
}
if (!pState->resolutionXProp) {
props[nextProp].name = bdfForceMakeAtom("RESOLUTION_X", NULL);
props[nextProp].value = (INT32) pState->resolution_x;
stringProps[nextProp] = FALSE;
pState->resolutionProp = &props[nextProp];
nextProp++;
}
if (!pState->resolutionYProp) {
props[nextProp].name = bdfForceMakeAtom("RESOLUTION_Y", NULL);
props[nextProp].value = (INT32) pState->resolution_y;
stringProps[nextProp] = FALSE;
pState->resolutionProp = &props[nextProp];
nextProp++;
}
if (!pState->xHeightProp) {
props[nextProp].name = bdfForceMakeAtom("X_HEIGHT", NULL);
props[nextProp].value = -1; /* computed later */
stringProps[nextProp] = FALSE;
pState->xHeightProp = &props[nextProp];
nextProp++;
}
if (!pState->quadWidthProp) {
props[nextProp].name = bdfForceMakeAtom("QUAD_WIDTH", NULL);
props[nextProp].value = -1; /* computed later */
stringProps[nextProp] = FALSE;
pState->quadWidthProp = &props[nextProp];
nextProp++;
}
pFont->info.nprops = nextProp;
return (TRUE);
BAILOUT:
if (pFont->info.isStringProp) {
xfree(pFont->info.isStringProp);
pFont->info.isStringProp = NULL;
}
if (pFont->info.props) {
xfree(pFont->info.props);
pFont->info.props = NULL;
}
while (line && bdfIsPrefix(line, "ENDPROPERTIES"))
line = bdfGetLine(file, lineBuf, BDFLINELEN);
return (FALSE);
}
/***====================================================================***/
int
bdfReadFont(pFont, file, bit, byte, glyph, scan)
FontPtr pFont;
FontFilePtr file;
int bit,
byte,
glyph,
scan;
{
bdfFileState state;
xCharInfo *min,
*max;
BitmapFontPtr bitmapFont;
pFont->fontPrivate = 0;
bzero(&state, sizeof(bdfFileState));
if (!bdfReadHeader(file, &state))
goto BAILOUT;
bitmapFont = (BitmapFontPtr) xalloc(sizeof(BitmapFontRec));
if (!bitmapFont)
goto BAILOUT;
pFont->fontPrivate = (pointer) bitmapFont;
bitmapFont->metrics = 0;
bitmapFont->ink_metrics = 0;
bitmapFont->bitmaps = 0;
bitmapFont->encoding = 0;
bitmapFont->pDefault = NULL;
bitmapFont->bitmapExtra = (BitmapExtraPtr) xalloc(sizeof(BitmapExtraRec));
bitmapFont->bitmapExtra->glyphNames = 0;
bitmapFont->bitmapExtra->sWidths = 0;
if (!bdfReadProperties(file, pFont, &state))
goto BAILOUT;
if (!bdfReadCharacters(file, pFont, &state, bit, byte, glyph, scan))
goto BAILOUT;
if (state.haveDefaultCh) {
unsigned int r, c, cols;
r = pFont->info.defaultCh >> 8;
c = pFont->info.defaultCh & 0xFF;
if (pFont->info.firstRow <= r && r <= pFont->info.lastRow &&
pFont->info.firstCol <= c && c <= pFont->info.lastCol) {
cols = pFont->info.lastCol - pFont->info.firstCol + 1;
r = r - pFont->info.firstRow;
c = c - pFont->info.firstCol;
bitmapFont->pDefault = bitmapFont->encoding[r * cols + c];
}
}
pFont->bit = bit;
pFont->byte = byte;
pFont->glyph = glyph;
pFont->scan = scan;
pFont->info.anamorphic = FALSE;
bitmapComputeFontBounds(pFont);
if (FontCouldBeTerminal(&pFont->info)) {
bdfPadToTerminal(pFont);
bitmapComputeFontBounds(pFont);
}
FontComputeInfoAccelerators(&pFont->info);
if (bitmapFont->bitmapExtra)
FontComputeInfoAccelerators(&bitmapFont->bitmapExtra->info);
if (pFont->info.constantMetrics)
bitmapAddInkMetrics(pFont);
if (bitmapFont->bitmapExtra)
bitmapFont->bitmapExtra->info.inkMetrics = pFont->info.inkMetrics;
bitmapComputeFontInkBounds(pFont);
/* ComputeFontAccelerators (pFont); */
/* generate properties */
min = &pFont->info.ink_minbounds;
max = &pFont->info.ink_maxbounds;
if (state.xHeightProp && (state.xHeightProp->value == -1))
state.xHeightProp->value = state.exHeight ?
state.exHeight : min->ascent;
if (state.quadWidthProp && (state.quadWidthProp->value == -1))
state.quadWidthProp->value = state.digitCount ?
(INT32) ((float) state.digitWidths / (float) state.digitCount) :
(min->characterWidth + max->characterWidth) / 2;
if (state.weightProp && (state.weightProp->value == -1))
state.weightProp->value = bitmapComputeWeight(pFont);
pFont->get_glyphs = bitmapGetGlyphs;
pFont->get_metrics = bitmapGetMetrics;
pFont->unload_font = bdfUnloadFont;
return Successful;
BAILOUT:
if (pFont->fontPrivate)
bdfFreeFontBits (pFont);
return AllocError;
}
bdfFreeFontBits(pFont)
FontPtr pFont;
{
BitmapFontPtr bitmapFont;
BitmapExtraPtr bitmapExtra;
int i;
bitmapFont = (BitmapFontPtr) pFont->fontPrivate;
bitmapExtra = (BitmapExtraPtr) bitmapFont->bitmapExtra;
xfree(bitmapFont->ink_metrics);
xfree(bitmapFont->encoding);
for (i = 0; i < bitmapFont->num_chars; i++)
xfree(bitmapFont->metrics[i].bits);
xfree(bitmapFont->metrics);
if (bitmapExtra)
{
xfree (bitmapExtra->glyphNames);
xfree (bitmapExtra->sWidths);
xfree (bitmapExtra);
}
xfree(pFont->info.props);
xfree(bitmapFont);
}
int
bdfReadFontInfo(pFontInfo, file)
FontInfoPtr pFontInfo;
FontFilePtr file;
{
FontRec font;
int ret;
ret = bdfReadFont(&font, file, MSBFirst, LSBFirst, 1, 1);
if (ret == Successful) {
*pFontInfo = font.info;
font.info.props = 0;
font.info.isStringProp = 0;
font.info.nprops = 0;
bdfFreeFontBits (&font);
}
return ret;
}
void
bdfUnloadFont(pFont)
FontPtr pFont;
{
bdfFreeFontBits (pFont);
xfree(pFont);
}
static Bool
bdfPadToTerminal(pFont)
FontPtr pFont;
{
BitmapFontPtr bitmapFont;
BitmapExtraPtr bitmapExtra;
int i;
int new_size;
CharInfoRec new;
int w,
h;
bitmapFont = (BitmapFontPtr) pFont->fontPrivate;
new.metrics.ascent = pFont->info.fontAscent;
new.metrics.descent = pFont->info.fontDescent;
new.metrics.leftSideBearing = 0;
new.metrics.rightSideBearing = pFont->info.minbounds.characterWidth;
new.metrics.characterWidth = new.metrics.rightSideBearing;
new_size = BYTES_FOR_GLYPH(&new, pFont->glyph);
for (i = 0; i < bitmapFont->num_chars; i++) {
new.bits = (char *) xalloc(new_size);
if (!new.bits)
return FALSE;
FontCharReshape(pFont, &bitmapFont->metrics[i], &new);
xfree(bitmapFont->metrics[i].bits);
bitmapFont->metrics[i] = new;
}
bitmapExtra = bitmapFont->bitmapExtra;
if (bitmapExtra) {
w = GLYPHWIDTHPIXELS(&new);
h = GLYPHHEIGHTPIXELS(&new);
for (i = 0; i < GLYPHPADOPTIONS; i++)
bitmapExtra->bitmapsSizes[i] = bitmapFont->num_chars *
(BYTES_PER_ROW(w, 1 << i) * h);
}
return TRUE;
}
+331
View File
@@ -0,0 +1,331 @@
/************************************************************************
Copyright 1989 by Digital Equipment Corporation, Maynard, Massachusetts,
and the Massachusetts Institute of Technology, Cambridge, Massachusetts.
All Rights Reserved
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 Digital or MIT not be
used in advertising or publicity pertaining to distribution of the
software without specific, written prior permission.
DIGITAL DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE, INCLUDING
ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO EVENT SHALL
DIGITAL BE LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR
ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS,
WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION,
ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS
SOFTWARE.
************************************************************************/
/* $XConsortium: bdfutils.c,v 1.6 92/04/16 09:20:57 gildea Exp $ */
#include <ctype.h>
#include <stdio.h>
#include "fontfilest.h"
#include "fontstruct.h"
/* use bitmap structure */
#include "bitmap.h"
#include "bdfint.h"
/***====================================================================***/
void
bdfError(message, a0, a1, a2, a3, a4, a5)
char *message;
pointer a0,
a1,
a2,
a3,
a4,
a5;
{
fprintf(stderr, "BDF Error: ");
fprintf(stderr, message, a0, a1, a2, a3, a4, a5);
}
/***====================================================================***/
void
bdfWarning(message, a0, a1, a2, a3, a4, a5)
char *message;
pointer a0,
a1,
a2,
a3,
a4,
a5;
{
fprintf(stderr, "BDF Warning: ");
fprintf(stderr, message, a0, a1, a2, a3, a4, a5);
}
/***====================================================================***/
/*ARGSUSED*/
void
bdfInformation(pFile, message, a0, a1, a2, a3, a4, a5)
char *message;
pointer a0,
a1,
a2,
a3,
a4,
a5;
{
fprintf(stderr, "BDF Information: ");
fprintf(stderr, message, a0, a1, a2, a3, a4, a5);
}
/***====================================================================***/
/*
* read the next (non-comment) line and keep a count for error messages.
* Returns buf, or NULL if EOF.
*/
unsigned char *
bdfGetLine(file, buf, len)
FontFilePtr file;
unsigned char *buf;
int len;
{
int c;
unsigned char *b;
for (;;) {
b = buf;
while ((c = FontFileGetc(file)) != FontFileEOF) {
if (c == '\r')
continue;
if (c == '\n')
break;
if (b - buf >= (len - 1))
break;
*b++ = c;
}
*b = '\0';
if (c == FontFileEOF)
return NULL;
if (b != buf && !bdfIsPrefix(buf, "COMMENT"))
break;
}
return buf;
}
/***====================================================================***/
Atom
bdfForceMakeAtom(str, size)
register char *str;
register int *size;
{
register int len = strlen(str);
extern Atom MakeAtom();
if (size != NULL)
*size += len + 1;
return MakeAtom(str, len, TRUE);
}
/***====================================================================***/
/*
* Handle quoted strings.
*/
Atom
bdfGetPropertyValue(s)
char *s;
{
register char *p,
*pp;
char *orig_s = s;
Atom atom;
/* strip leading white space */
while (*s && (*s == ' ' || *s == '\t'))
s++;
if (*s == 0) {
return bdfForceMakeAtom(s, NULL);
}
if (*s != '"') {
pp = s;
/* no white space in value */
for (pp = s; *pp; pp++)
if (*pp == ' ' || *pp == '\t' || *pp == '\015' || *pp == '\n') {
*pp = 0;
break;
}
return bdfForceMakeAtom(s, NULL);
}
/* quoted string: strip outer quotes and undouble inner quotes */
s++;
pp = p = (char *) xalloc((unsigned) strlen(s) + 1);
while (*s) {
if (*s == '"') {
if (*(s + 1) != '"') {
*p++ = 0;
atom = bdfForceMakeAtom(pp, NULL);
xfree(pp);
return atom;
} else {
s++;
}
}
*p++ = *s++;
}
xfree (pp);
bdfError("unterminated quoted string property: %s\n", orig_s);
return None;
}
/***====================================================================***/
/*
* return TRUE if string is a valid integer
*/
int
bdfIsInteger(str)
char *str;
{
char c;
c = *str++;
if (!(isdigit(c) || c == '-' || c == '+'))
return (FALSE);
while (c = *str++)
if (!isdigit(c))
return (FALSE);
return (TRUE);
}
/***====================================================================***/
/*
* make a byte from the first two hex characters in glyph picture
*/
unsigned char
bdfHexByte(s)
char *s;
{
unsigned char b = 0;
register char c;
int i;
for (i = 2; i; i--) {
c = *s++;
if ((c >= '0') && (c <= '9'))
b = (b << 4) + (c - '0');
else if ((c >= 'A') && (c <= 'F'))
b = (b << 4) + 10 + (c - 'A');
else if ((c >= 'a') && (c <= 'f'))
b = (b << 4) + 10 + (c - 'a');
else
bdfError("bad hex char '%c'", c);
}
return b;
}
/***====================================================================***/
/*
* check for known special property values
*/
static char *SpecialAtoms[] = {
"FONT_ASCENT",
#define BDF_FONT_ASCENT 0
"FONT_DESCENT",
#define BDF_FONT_DESCENT 1
"DEFAULT_CHAR",
#define BDF_DEFAULT_CHAR 2
"POINT_SIZE",
#define BDF_POINT_SIZE 3
"RESOLUTION",
#define BDF_RESOLUTION 4
"X_HEIGHT",
#define BDF_X_HEIGHT 5
"WEIGHT",
#define BDF_WEIGHT 6
"QUAD_WIDTH",
#define BDF_QUAD_WIDTH 7
"FONT",
#define BDF_FONT 8
"RESOLUTION_X",
#define BDF_RESOLUTION_X 9
"RESOLUTION_Y",
#define BDF_RESOLUTION_Y 10
0,
};
Bool
bdfSpecialProperty(pFont, prop, isString, bdfState)
FontPtr pFont;
FontPropPtr prop;
char isString;
bdfFileState *bdfState;
{
char **special;
char *name;
name = NameForAtom(prop->name);
for (special = SpecialAtoms; *special; special++)
if (!strcmp(name, *special))
break;
switch (special - SpecialAtoms) {
case BDF_FONT_ASCENT:
if (!isString) {
pFont->info.fontAscent = prop->value;
bdfState->haveFontAscent = TRUE;
}
return TRUE;
case BDF_FONT_DESCENT:
if (!isString) {
pFont->info.fontDescent = prop->value;
bdfState->haveFontDescent = TRUE;
}
return TRUE;
case BDF_DEFAULT_CHAR:
if (!isString) {
pFont->info.defaultCh = prop->value;
bdfState->haveDefaultCh = TRUE;
}
return TRUE;
case BDF_POINT_SIZE:
bdfState->pointSizeProp = prop;
return FALSE;
case BDF_RESOLUTION:
bdfState->resolutionProp = prop;
return FALSE;
case BDF_X_HEIGHT:
bdfState->xHeightProp = prop;
return FALSE;
case BDF_WEIGHT:
bdfState->weightProp = prop;
return FALSE;
case BDF_QUAD_WIDTH:
bdfState->quadWidthProp = prop;
return FALSE;
case BDF_FONT:
bdfState->fontProp = prop;
return FALSE;
case BDF_RESOLUTION_X:
bdfState->resolutionXProp = prop;
return FALSE;
case BDF_RESOLUTION_Y:
bdfState->resolutionYProp = prop;
return FALSE;
default:
return FALSE;
}
}
+666
View File
@@ -0,0 +1,666 @@
/*
* $XConsortium: pcfread.c,v 1.10 92/05/12 18:07:47 gildea Exp $
*
* Copyright 1990 Massachusetts Institute of Technology
*
* Permission to use, copy, modify, distribute, and sell this software and its
* documentation for any purpose is hereby granted without fee, 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 name of M.I.T. not be used in advertising or
* publicity pertaining to distribution of the software without specific,
* written prior permission. M.I.T. makes no representations about the
* suitability of this software for any purpose. It is provided "as is"
* without express or implied warranty.
*
* M.I.T. DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE, INCLUDING ALL
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO EVENT SHALL M.I.T.
* BE LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
* WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER 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: Keith Packard, MIT X Consortium
*/
#include "fontfilest.h"
#include "bitmap.h"
#include "pcf.h"
/* Read PCF font files */
void pcfUnloadFont();
static int position;
static int
pcfGetLSB32(file)
FontFilePtr file;
{
int c;
c = FontFileGetc(file);
c |= FontFileGetc(file) << 8;
c |= FontFileGetc(file) << 16;
c |= FontFileGetc(file) << 24;
position += 4;
return c;
}
static int
pcfGetINT32(file, format)
FontFilePtr file;
CARD32 format;
{
int c;
if (PCF_BYTE_ORDER(format) == MSBFirst) {
c = FontFileGetc(file) << 24;
c |= FontFileGetc(file) << 16;
c |= FontFileGetc(file) << 8;
c |= FontFileGetc(file);
} else {
c = FontFileGetc(file);
c |= FontFileGetc(file) << 8;
c |= FontFileGetc(file) << 16;
c |= FontFileGetc(file) << 24;
}
position += 4;
return c;
}
static int
pcfGetINT16(file, format)
FontFilePtr file;
CARD32 format;
{
int c;
if (PCF_BYTE_ORDER(format) == MSBFirst) {
c = FontFileGetc(file) << 8;
c |= FontFileGetc(file);
} else {
c = FontFileGetc(file);
c |= FontFileGetc(file) << 8;
}
position += 2;
return c;
}
#define pcfGetINT8(file, format) (position++, FontFileGetc(file))
static PCFTablePtr
pcfReadTOC(file, countp)
FontFilePtr file;
int *countp;
{
CARD32 version;
PCFTablePtr tables;
int count;
int i;
position = 0;
version = pcfGetLSB32(file);
if (version != PCF_FILE_VERSION)
return (PCFTablePtr) NULL;
count = pcfGetLSB32(file);
tables = (PCFTablePtr) xalloc(count * sizeof(PCFTableRec));
if (!tables)
return (PCFTablePtr) NULL;
for (i = 0; i < count; i++) {
tables[i].type = pcfGetLSB32(file);
tables[i].format = pcfGetLSB32(file);
tables[i].size = pcfGetLSB32(file);
tables[i].offset = pcfGetLSB32(file);
}
*countp = count;
return tables;
}
/*
* PCF supports two formats for metrics, both the regular
* jumbo size, and 'lite' metrics, which are useful
* for most fonts which have even vaguely reasonable
* metrics
*/
static
pcfGetMetric(file, format, metric)
FontFilePtr file;
CARD32 format;
xCharInfo *metric;
{
metric->leftSideBearing = pcfGetINT16(file, format);
metric->rightSideBearing = pcfGetINT16(file, format);
metric->characterWidth = pcfGetINT16(file, format);
metric->ascent = pcfGetINT16(file, format);
metric->descent = pcfGetINT16(file, format);
metric->attributes = pcfGetINT16(file, format);
}
static
pcfGetCompressedMetric(file, format, metric)
FontFilePtr file;
CARD32 format;
xCharInfo *metric;
{
metric->leftSideBearing = pcfGetINT8(file, format) - 0x80;
metric->rightSideBearing = pcfGetINT8(file, format) - 0x80;
metric->characterWidth = pcfGetINT8(file, format) - 0x80;
metric->ascent = pcfGetINT8(file, format) - 0x80;
metric->descent = pcfGetINT8(file, format) - 0x80;
metric->attributes = 0;
}
/*
* Position the file to the begining of the specified table
* in the font file
*/
static Bool
pcfSeekToType(file, tables, ntables, type, formatp, sizep)
FontFilePtr file;
PCFTablePtr tables;
int ntables;
CARD32 type;
CARD32 *formatp;
CARD32 *sizep;
{
int i;
for (i = 0; i < ntables; i++)
if (tables[i].type == type) {
if (position > tables[i].offset)
return FALSE;
if (!FontFileSkip(file, tables[i].offset - position))
return FALSE;
position = tables[i].offset;
*sizep = tables[i].size;
*formatp = tables[i].format;
return TRUE;
}
return FALSE;
}
static Bool
pcfHasType (tables, ntables, type)
PCFTablePtr tables;
int ntables;
CARD32 type;
{
int i;
for (i = 0; i < ntables; i++)
if (tables[i].type == type)
return TRUE;
return FALSE;
}
/*
* pcfGetProperties
*
* Reads the font properties from the font file, filling in the FontInfo rec
* supplied. Used by by both ReadFont and ReadFontInfo routines.
*/
static Bool
pcfGetProperties(pFontInfo, file, tables, ntables)
FontInfoPtr pFontInfo;
FontFilePtr file;
PCFTablePtr tables;
int ntables;
{
FontPropPtr props = 0;
int nprops;
char *isStringProp = 0;
CARD32 format;
int i;
int size;
int string_size;
char *strings;
/* font properties */
if (!pcfSeekToType(file, tables, ntables, PCF_PROPERTIES, &format, &size))
goto Bail;
format = pcfGetLSB32(file);
if (!PCF_FORMAT_MATCH(format, PCF_DEFAULT_FORMAT))
goto Bail;
nprops = pcfGetINT32(file, format);
props = (FontPropPtr) xalloc(nprops * sizeof(FontPropRec));
if (!props)
goto Bail;
isStringProp = (char *) xalloc(nprops * sizeof(char));
if (!isStringProp)
goto Bail;
for (i = 0; i < nprops; i++) {
props[i].name = pcfGetINT32(file, format);
isStringProp[i] = pcfGetINT8(file, format);
props[i].value = pcfGetINT32(file, format);
}
/* pad the property array */
/*
* clever here - nprops is the same as the number of odd-units read, as
* only isStringProp are odd length
*/
if (nprops & 3)
{
i = 4 - (nprops & 3);
FontFileSkip(file, i);
position += i;
}
string_size = pcfGetINT32(file, format);
strings = (char *) xalloc(string_size);
if (!strings) {
goto Bail;
}
FontFileRead(file, strings, string_size);
position += string_size;
for (i = 0; i < nprops; i++) {
props[i].name = MakeAtom(strings + props[i].name,
strlen(strings + props[i].name), TRUE);
if (isStringProp[i]) {
props[i].value = MakeAtom(strings + props[i].value,
strlen(strings + props[i].value), TRUE);
}
}
xfree(strings);
pFontInfo->isStringProp = isStringProp;
pFontInfo->props = props;
pFontInfo->nprops = nprops;
return TRUE;
Bail:
xfree(isStringProp);
xfree(props);
return FALSE;
}
/*
* pcfReadAccel
*
* Fill in the accelerator information from the font file; used
* to read both BDF_ACCELERATORS and old style ACCELERATORS
*/
static Bool
pcfGetAccel(pFontInfo, file, tables, ntables, type)
FontInfoPtr pFontInfo;
FontFilePtr file;
PCFTablePtr tables;
int ntables;
CARD32 type;
{
CARD32 format;
int size;
if (!pcfSeekToType(file, tables, ntables, type, &format, &size))
goto Bail;
format = pcfGetLSB32(file);
if (!PCF_FORMAT_MATCH(format, PCF_DEFAULT_FORMAT) &&
!PCF_FORMAT_MATCH(format, PCF_ACCEL_W_INKBOUNDS))
{
goto Bail;
}
pFontInfo->noOverlap = pcfGetINT8(file, format);
pFontInfo->constantMetrics = pcfGetINT8(file, format);
pFontInfo->terminalFont = pcfGetINT8(file, format);
pFontInfo->constantWidth = pcfGetINT8(file, format);
pFontInfo->inkInside = pcfGetINT8(file, format);
pFontInfo->inkMetrics = pcfGetINT8(file, format);
pFontInfo->drawDirection = pcfGetINT8(file, format);
pFontInfo->anamorphic = FALSE;
/* natural alignment */ pcfGetINT8(file, format);
pFontInfo->fontAscent = pcfGetINT32(file, format);
pFontInfo->fontDescent = pcfGetINT32(file, format);
pFontInfo->maxOverlap = pcfGetINT32(file, format);
pcfGetMetric(file, format, &pFontInfo->minbounds);
pcfGetMetric(file, format, &pFontInfo->maxbounds);
if (PCF_FORMAT_MATCH(format, PCF_ACCEL_W_INKBOUNDS)) {
pcfGetMetric(file, format, &pFontInfo->ink_minbounds);
pcfGetMetric(file, format, &pFontInfo->ink_maxbounds);
} else {
pFontInfo->ink_minbounds = pFontInfo->minbounds;
pFontInfo->ink_maxbounds = pFontInfo->maxbounds;
}
return TRUE;
Bail:
return FALSE;
}
int
pcfReadFont(pFont, file, bit, byte, glyph, scan)
FontPtr pFont;
FontFilePtr file;
int bit,
byte,
glyph,
scan;
{
CARD32 format;
CARD32 size;
BitmapFontPtr bitmapFont = 0;
int i;
PCFTablePtr tables = 0;
int ntables;
int nmetrics;
int nbitmaps;
int sizebitmaps;
int nink_metrics;
CharInfoPtr metrics = 0;
xCharInfo *ink_metrics = 0;
char *bitmaps = 0;
CharInfoPtr *encoding = 0;
int nencoding;
int encodingOffset;
CARD32 bitmapSizes[GLYPHPADOPTIONS];
CARD32 *offsets = 0;
Bool hasBDFAccelerators;
pFont->info.props = 0;
if (!(tables = pcfReadTOC(file, &ntables)))
goto Bail;
/* properties */
if (!pcfGetProperties(&pFont->info, file, tables, ntables))
goto Bail;
/* Use the old accelerators if no BDF accelerators are in the file */
hasBDFAccelerators = pcfHasType (tables, ntables, PCF_BDF_ACCELERATORS);
if (!hasBDFAccelerators)
if (!pcfGetAccel (&pFont->info, file, tables, ntables, PCF_ACCELERATORS))
goto Bail;
/* metrics */
if (!pcfSeekToType(file, tables, ntables, PCF_METRICS, &format, &size)) {
goto Bail;
}
format = pcfGetLSB32(file);
if (!PCF_FORMAT_MATCH(format, PCF_DEFAULT_FORMAT) &&
!PCF_FORMAT_MATCH(format, PCF_COMPRESSED_METRICS)) {
goto Bail;
}
if (PCF_FORMAT_MATCH(format, PCF_DEFAULT_FORMAT))
nmetrics = pcfGetINT32(file, format);
else
nmetrics = pcfGetINT16(file, format);
metrics = (CharInfoPtr) xalloc(nmetrics * sizeof(CharInfoRec));
if (!metrics) {
goto Bail;
}
for (i = 0; i < nmetrics; i++)
if (PCF_FORMAT_MATCH(format, PCF_DEFAULT_FORMAT))
pcfGetMetric(file, format, &(metrics + i)->metrics);
else
pcfGetCompressedMetric(file, format, &(metrics + i)->metrics);
/* bitmaps */
if (!pcfSeekToType(file, tables, ntables, PCF_BITMAPS, &format, &size))
goto Bail;
format = pcfGetLSB32(file);
if (!PCF_FORMAT_MATCH(format, PCF_DEFAULT_FORMAT))
goto Bail;
nbitmaps = pcfGetINT32(file, format);
if (nbitmaps != nmetrics)
goto Bail;
offsets = (CARD32 *) xalloc(nbitmaps * sizeof(CARD32));
if (!offsets)
goto Bail;
for (i = 0; i < nbitmaps; i++)
offsets[i] = pcfGetINT32(file, format);
for (i = 0; i < GLYPHPADOPTIONS; i++)
bitmapSizes[i] = pcfGetINT32(file, format);
sizebitmaps = bitmapSizes[PCF_GLYPH_PAD_INDEX(format)];
bitmaps = (char *) xalloc(sizebitmaps);
if (!bitmaps)
goto Bail;
FontFileRead(file, bitmaps, sizebitmaps);
position += sizebitmaps;
if (PCF_BIT_ORDER(format) != bit)
BitOrderInvert(bitmaps, sizebitmaps);
if ((PCF_BYTE_ORDER(format) == PCF_BIT_ORDER(format)) != (bit == byte)) {
switch (bit == byte ? PCF_SCAN_UNIT(format) : scan) {
case 1:
break;
case 2:
TwoByteSwap(bitmaps, sizebitmaps);
break;
case 4:
FourByteSwap(bitmaps, sizebitmaps);
break;
}
}
if (PCF_GLYPH_PAD(format) != glyph) {
char *padbitmaps;
int sizepadbitmaps;
int old,
new;
xCharInfo *metric;
sizepadbitmaps = bitmapSizes[PCF_SIZE_TO_INDEX(glyph)];
padbitmaps = (char *) xalloc(sizepadbitmaps);
if (!padbitmaps) {
goto Bail;
}
new = 0;
for (i = 0; i < nbitmaps; i++) {
old = offsets[i];
metric = &metrics[i].metrics;
offsets[i] = new;
new += RepadBitmap(bitmaps + old, padbitmaps + new,
PCF_GLYPH_PAD(format), glyph,
metric->rightSideBearing - metric->leftSideBearing,
metric->ascent + metric->descent);
}
xfree(bitmaps);
bitmaps = padbitmaps;
}
for (i = 0; i < nbitmaps; i++)
metrics[i].bits = bitmaps + offsets[i];
xfree(offsets);
/* ink metrics ? */
ink_metrics = NULL;
if (pcfSeekToType(file, tables, ntables, PCF_INK_METRICS, &format, &size)) {
format = pcfGetLSB32(file);
if (!PCF_FORMAT_MATCH(format, PCF_DEFAULT_FORMAT) &&
!PCF_FORMAT_MATCH(format, PCF_COMPRESSED_METRICS)) {
goto Bail;
}
if (PCF_FORMAT_MATCH(format, PCF_DEFAULT_FORMAT))
nink_metrics = pcfGetINT32(file, format);
else
nink_metrics = pcfGetINT16(file, format);
if (nink_metrics != nmetrics)
goto Bail;
ink_metrics = (xCharInfo *) xalloc(nink_metrics * sizeof(xCharInfo));
if (!ink_metrics)
goto Bail;
for (i = 0; i < nink_metrics; i++)
if (PCF_FORMAT_MATCH(format, PCF_DEFAULT_FORMAT))
pcfGetMetric(file, format, ink_metrics + i);
else
pcfGetCompressedMetric(file, format, ink_metrics + i);
}
/* encoding */
if (!pcfSeekToType(file, tables, ntables, PCF_BDF_ENCODINGS, &format, &size))
goto Bail;
format = pcfGetLSB32(file);
if (!PCF_FORMAT_MATCH(format, PCF_DEFAULT_FORMAT))
goto Bail;
pFont->info.firstCol = pcfGetINT16(file, format);
pFont->info.lastCol = pcfGetINT16(file, format);
pFont->info.firstRow = pcfGetINT16(file, format);
pFont->info.lastRow = pcfGetINT16(file, format);
pFont->info.defaultCh = pcfGetINT16(file, format);
nencoding = (pFont->info.lastCol - pFont->info.firstCol + 1) *
(pFont->info.lastRow - pFont->info.firstRow + 1);
encoding = (CharInfoPtr *) xalloc(nencoding * sizeof(CharInfoPtr));
if (!encoding)
goto Bail;
pFont->info.allExist = TRUE;
for (i = 0; i < nencoding; i++) {
encodingOffset = pcfGetINT16(file, format);
if (encodingOffset == 0xFFFF) {
pFont->info.allExist = FALSE;
encoding[i] = 0;
} else
encoding[i] = metrics + encodingOffset;
}
/* BDF style accelerators (i.e. bounds based on encoded glyphs) */
if (hasBDFAccelerators)
if (!pcfGetAccel (&pFont->info, file, tables, ntables, PCF_BDF_ACCELERATORS))
goto Bail;
bitmapFont = (BitmapFontPtr) xalloc(sizeof *bitmapFont);
if (!bitmapFont)
goto Bail;
bitmapFont->version_num = PCF_FILE_VERSION;
bitmapFont->num_chars = nmetrics;
bitmapFont->num_tables = ntables;
bitmapFont->metrics = metrics;
bitmapFont->ink_metrics = ink_metrics;
bitmapFont->bitmaps = bitmaps;
bitmapFont->encoding = encoding;
bitmapFont->pDefault = (CharInfoPtr) 0;
if (pFont->info.defaultCh != (unsigned short) NO_SUCH_CHAR) {
int r,
c,
cols;
r = pFont->info.defaultCh >> 8;
c = pFont->info.defaultCh & 0xFF;
if (pFont->info.firstRow <= r && r <= pFont->info.lastRow &&
pFont->info.firstCol <= c && c <= pFont->info.lastCol) {
cols = pFont->info.lastCol - pFont->info.firstCol + 1;
r = r - pFont->info.firstRow;
c = c - pFont->info.firstCol;
bitmapFont->pDefault = encoding[r * cols + c];
}
}
bitmapFont->bitmapExtra = (BitmapExtraPtr) 0;
pFont->fontPrivate = (pointer) bitmapFont;
pFont->get_glyphs = bitmapGetGlyphs;
pFont->get_metrics = bitmapGetMetrics;
pFont->unload_font = pcfUnloadFont;
pFont->bit = bit;
pFont->byte = byte;
pFont->glyph = glyph;
pFont->scan = scan;
xfree(tables);
return Successful;
Bail:
xfree(ink_metrics);
xfree(encoding);
xfree(bitmaps);
xfree(offsets);
xfree(metrics);
xfree(pFont->info.props);
pFont->info.props = 0;
xfree(bitmapFont);
xfree(tables);
return AllocError;
}
int
pcfReadFontInfo(pFontInfo, file)
FontInfoPtr pFontInfo;
FontFilePtr file;
{
PCFTablePtr tables;
int ntables;
CARD32 format;
CARD32 size;
int nencoding;
Bool hasBDFAccelerators;
pFontInfo->isStringProp = NULL;
pFontInfo->props = NULL;
if (!(tables = pcfReadTOC(file, &ntables)))
goto Bail;
/* properties */
if (!pcfGetProperties(pFontInfo, file, tables, ntables))
goto Bail;
/* Use the old accelerators if no BDF accelerators are in the file */
hasBDFAccelerators = pcfHasType (tables, ntables, PCF_BDF_ACCELERATORS);
if (!hasBDFAccelerators)
if (!pcfGetAccel (pFontInfo, file, tables, ntables, PCF_ACCELERATORS))
goto Bail;
/* encoding */
if (!pcfSeekToType(file, tables, ntables, PCF_BDF_ENCODINGS, &format, &size))
goto Bail;
format = pcfGetLSB32(file);
if (!PCF_FORMAT_MATCH(format, PCF_DEFAULT_FORMAT))
goto Bail;
pFontInfo->firstCol = pcfGetINT16(file, format);
pFontInfo->lastCol = pcfGetINT16(file, format);
pFontInfo->firstRow = pcfGetINT16(file, format);
pFontInfo->lastRow = pcfGetINT16(file, format);
pFontInfo->defaultCh = pcfGetINT16(file, format);
nencoding = (pFontInfo->lastCol - pFontInfo->firstCol + 1) *
(pFontInfo->lastRow - pFontInfo->firstRow + 1);
pFontInfo->allExist = TRUE;
while (nencoding--) {
if (pcfGetINT16(file, format) == 0xFFFF)
pFontInfo->allExist = FALSE;
}
/* BDF style accelerators (i.e. bounds based on encoded glyphs) */
if (hasBDFAccelerators)
if (!pcfGetAccel (pFontInfo, file, tables, ntables, PCF_BDF_ACCELERATORS))
goto Bail;
xfree(tables);
return Successful;
Bail:
xfree (pFontInfo->props);
xfree (pFontInfo->isStringProp);
xfree(tables);
return AllocError;
}
void
pcfUnloadFont(pFont)
FontPtr pFont;
{
BitmapFontPtr bitmapFont;
bitmapFont = (BitmapFontPtr) pFont->fontPrivate;
xfree(bitmapFont->ink_metrics);
xfree(bitmapFont->encoding);
xfree(bitmapFont->bitmaps);
xfree(bitmapFont->metrics);
xfree(pFont->info.isStringProp);
xfree(pFont->info.props);
xfree(bitmapFont);
xfree(pFont);
}
+457
View File
@@ -0,0 +1,457 @@
/************************************************************************
Copyright 1989 by Digital Equipment Corporation, Maynard, Massachusetts,
and the Massachusetts Institute of Technology, Cambridge, Massachusetts.
All Rights Reserved
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 Digital or MIT not be
used in advertising or publicity pertaining to distribution of the
software without specific, written prior permission.
DIGITAL DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE, INCLUDING
ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO EVENT SHALL
DIGITAL BE LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR
ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS,
WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION,
ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS
SOFTWARE.
************************************************************************/
/* $XConsortium: snfread.c,v 1.11 92/05/12 18:07:49 gildea Exp $ */
#include <ctype.h>
#include "fontfilest.h"
#include "bitmap.h"
#include "snfstr.h"
static void snfUnloadFont();
static int
snfReadCharInfo(file, charInfo, base)
FontFilePtr file;
CharInfoPtr charInfo;
char *base;
{
snfCharInfoRec snfCharInfo;
#define Width(m) ((m).rightSideBearing - (m).leftSideBearing)
#define Height(m) ((m).ascent + (m).descent)
if (FontFileRead(file, (char *) &snfCharInfo, sizeof snfCharInfo) !=
sizeof(snfCharInfo)) {
return BadFontName;
}
charInfo->metrics = snfCharInfo.metrics;
if (snfCharInfo.exists)
charInfo->bits = base + snfCharInfo.byteOffset;
else
charInfo->bits = 0;
return Successful;
}
static int
snfReadxCharInfo(file, charInfo)
FontFilePtr file;
xCharInfo *charInfo;
{
snfCharInfoRec snfCharInfo;
if (FontFileRead(file, (char *) &snfCharInfo, sizeof snfCharInfo) !=
sizeof(snfCharInfo)) {
return BadFontName;
}
*charInfo = snfCharInfo.metrics;
return Successful;
}
static
snfCopyInfo(snfInfo, pFontInfo)
snfFontInfoPtr snfInfo;
FontInfoPtr pFontInfo;
{
pFontInfo->firstCol = snfInfo->firstCol;
pFontInfo->lastCol = snfInfo->lastCol;
pFontInfo->firstRow = snfInfo->firstRow;
pFontInfo->lastRow = snfInfo->lastRow;
pFontInfo->defaultCh = snfInfo->chDefault;
pFontInfo->noOverlap = snfInfo->noOverlap;
pFontInfo->terminalFont = snfInfo->terminalFont;
pFontInfo->constantMetrics = snfInfo->constantMetrics;
pFontInfo->constantWidth = snfInfo->constantWidth;
pFontInfo->inkInside = snfInfo->inkInside;
pFontInfo->inkMetrics = snfInfo->inkMetrics;
pFontInfo->allExist = snfInfo->allExist;
pFontInfo->drawDirection = snfInfo->drawDirection;
pFontInfo->anamorphic = FALSE;
pFontInfo->maxOverlap = 0;
pFontInfo->minbounds = snfInfo->minbounds.metrics;
pFontInfo->maxbounds = snfInfo->maxbounds.metrics;
pFontInfo->fontAscent = snfInfo->fontAscent;
pFontInfo->fontDescent = snfInfo->fontDescent;
pFontInfo->nprops = snfInfo->nProps;
}
static int
snfReadProps(snfInfo, pFontInfo, file)
snfFontInfoPtr snfInfo;
FontInfoPtr pFontInfo;
FontFilePtr file;
{
char *strings;
FontPropPtr pfp;
snfFontPropPtr psnfp;
char *propspace;
int bytestoalloc;
int i;
bytestoalloc = snfInfo->nProps * sizeof(snfFontPropRec) +
BYTESOFSTRINGINFO(snfInfo);
propspace = (char *) xalloc(bytestoalloc);
if (!propspace)
return AllocError;
if (FontFileRead(file, propspace, bytestoalloc) != bytestoalloc) {
xfree(propspace);
return BadFontName;
}
psnfp = (snfFontPropPtr) propspace;
strings = propspace + BYTESOFPROPINFO(snfInfo);
for (i = 0, pfp = pFontInfo->props; i < snfInfo->nProps; i++, pfp++, psnfp++) {
pfp->name = MakeAtom(&strings[psnfp->name],
(unsigned) strlen(&strings[psnfp->name]), 1);
pFontInfo->isStringProp[i] = psnfp->indirect;
if (psnfp->indirect)
pfp->value = (INT32) MakeAtom(&strings[psnfp->value],
(unsigned) strlen(&strings[psnfp->value]), 1);
else
pfp->value = psnfp->value;
}
xfree(propspace);
return Successful;
}
int
snfReadHeader(snfInfo, file)
snfFontInfoPtr snfInfo;
FontFilePtr file;
{
if (FontFileRead(file, (char *) snfInfo, sizeof *snfInfo) != sizeof *snfInfo)
return BadFontName;
if (snfInfo->version1 != FONT_FILE_VERSION ||
snfInfo->version2 != FONT_FILE_VERSION)
return BadFontName;
return Successful;
}
int
snfReadFont(pFont, file, bit, byte, glyph, scan)
FontPtr pFont;
FontFilePtr file;
int bit,
byte,
glyph,
scan;
{
snfFontInfoRec fi;
unsigned bytestoalloc;
int i;
char *fontspace;
BitmapFontPtr bitmapFont;
int num_chars;
int bitmapsSize;
int ret;
int metrics_off;
int bitmaps_off;
int encoding_off;
int props_off;
int isStringProp_off;
int ink_off;
char *bitmaps, *repad_bitmaps;
int def_bit, def_byte, def_glyph, def_scan;
ret = snfReadHeader(&fi, file);
if (ret != Successful)
return ret;
SnfGetFormat (&def_bit, &def_byte, &def_glyph, &def_scan);
/*
* we'll allocate one chunk of memory and split it among the various parts
* of the font:
*
* BitmapFontRec CharInfoRec's Glyphs Encoding DIX Properties Ink CharInfoRec's
*
* If the glyphpad is not the same as the font file, then the glyphs
* are allocated separately, to be later realloc'ed when we know
* how big to make them.
*/
bitmapsSize = BYTESOFGLYPHINFO(&fi);
num_chars = n2dChars(&fi);
bytestoalloc = sizeof(BitmapFontRec); /* bitmapFont */
metrics_off = bytestoalloc;
bytestoalloc += num_chars * sizeof(CharInfoRec); /* metrics */
encoding_off = bytestoalloc;
bytestoalloc += num_chars * sizeof(CharInfoPtr); /* encoding */
props_off = bytestoalloc;
bytestoalloc += fi.nProps * sizeof(FontPropRec); /* props */
isStringProp_off = bytestoalloc;
bytestoalloc += fi.nProps * sizeof(char); /* isStringProp */
bytestoalloc = (bytestoalloc + 3) & ~3;
ink_off = bytestoalloc;
if (fi.inkMetrics)
bytestoalloc += num_chars * sizeof(xCharInfo); /* ink_metrics */
fontspace = (char *) xalloc(bytestoalloc);
if (!fontspace)
return AllocError;
bitmaps = (char *) xalloc (bitmapsSize);
if (!bitmaps)
{
xfree (fontspace);
return AllocError;
}
/*
* now fix up pointers
*/
bitmapFont = (BitmapFontPtr) fontspace;
bitmapFont->num_chars = num_chars;
bitmapFont->metrics = (CharInfoPtr) (fontspace + metrics_off);
bitmapFont->encoding = (CharInfoPtr *) (fontspace + encoding_off);
bitmapFont->bitmaps = bitmaps;
bitmapFont->pDefault = NULL;
bitmapFont->bitmapExtra = NULL;
pFont->info.props = (FontPropPtr) (fontspace + props_off);
pFont->info.isStringProp = (char *) (fontspace + isStringProp_off);
if (fi.inkMetrics)
bitmapFont->ink_metrics = (xCharInfo *) (fontspace + ink_off);
else
bitmapFont->ink_metrics = 0;
/*
* read the CharInfo
*/
ret = Successful;
for (i = 0; ret == Successful && i < num_chars; i++) {
ret = snfReadCharInfo(file, &bitmapFont->metrics[i], bitmaps);
if (bitmapFont->metrics[i].bits)
bitmapFont->encoding[i] = &bitmapFont->metrics[i];
else
bitmapFont->encoding[i] = 0;
}
if (ret != Successful) {
xfree(fontspace);
return ret;
}
/*
* read the glyphs
*/
if (FontFileRead(file, (char *) bitmaps, bitmapsSize) != bitmapsSize) {
xfree(bitmaps);
xfree(fontspace);
return BadFontName;
}
if (def_bit != bit)
BitOrderInvert(bitmaps, bitmapsSize);
if ((def_byte == def_bit) != (bit == byte)) {
switch (bit == byte ? def_scan : scan) {
case 1:
break;
case 2:
TwoByteSwap(bitmaps, bitmapsSize);
break;
case 4:
FourByteSwap(bitmaps, bitmapsSize);
break;
}
}
if (def_glyph != glyph) {
char *padbitmaps;
int sizepadbitmaps;
int sizechar;
CharInfoPtr metric;
sizepadbitmaps = 0;
metric = bitmapFont->metrics;
for (i = 0; i < num_chars; i++)
{
if (metric->bits)
sizepadbitmaps += BYTES_FOR_GLYPH(metric,glyph);
metric++;
}
padbitmaps = (char *) xalloc(sizepadbitmaps);
if (!padbitmaps) {
xfree (bitmaps);
xfree (fontspace);
return AllocError;
}
metric = bitmapFont->metrics;
bitmapFont->bitmaps = padbitmaps;
for (i = 0; i < num_chars; i++) {
sizechar = RepadBitmap(metric->bits, padbitmaps,
def_glyph, glyph,
metric->metrics.rightSideBearing -
metric->metrics.leftSideBearing,
metric->metrics.ascent + metric->metrics.descent);
metric->bits = padbitmaps;
padbitmaps += sizechar;
metric++;
}
xfree(bitmaps);
}
/* now read and atom'ize properties */
ret = snfReadProps(&fi, &pFont->info, file);
if (ret != Successful) {
xfree(fontspace);
return ret;
}
snfCopyInfo(&fi, &pFont->info);
/* finally, read the ink metrics if the exist */
if (fi.inkMetrics) {
ret = Successful;
ret = snfReadxCharInfo(file, &pFont->info.ink_minbounds);
ret = snfReadxCharInfo(file, &pFont->info.ink_maxbounds);
for (i = 0; ret == Successful && i < num_chars; i++)
ret = snfReadxCharInfo(file, &bitmapFont->ink_metrics[i]);
if (ret != Successful) {
xfree(fontspace);
return ret;
}
} else {
pFont->info.ink_minbounds = pFont->info.minbounds;
pFont->info.ink_maxbounds = pFont->info.maxbounds;
}
if (pFont->info.defaultCh != (unsigned short) NO_SUCH_CHAR) {
int r,
c,
cols;
r = pFont->info.defaultCh >> 8;
c = pFont->info.defaultCh & 0xFF;
if (pFont->info.firstRow <= r && r <= pFont->info.lastRow &&
pFont->info.firstCol <= c && c <= pFont->info.lastCol) {
cols = pFont->info.lastCol - pFont->info.firstCol + 1;
r = r - pFont->info.firstRow;
c = c - pFont->info.firstCol;
bitmapFont->pDefault = &bitmapFont->metrics[r * cols + c];
}
}
bitmapFont->bitmapExtra = (BitmapExtraPtr) 0;
pFont->fontPrivate = (pointer) bitmapFont;
pFont->get_glyphs = bitmapGetGlyphs;
pFont->get_metrics = bitmapGetMetrics;
pFont->unload_font = snfUnloadFont;
pFont->bit = bit;
pFont->byte = byte;
pFont->glyph = glyph;
pFont->scan = scan;
return Successful;
}
int
snfReadFontInfo(pFontInfo, file)
FontInfoPtr pFontInfo;
FontFilePtr file;
{
int ret;
snfFontInfoRec fi;
int bytestoskip;
int num_chars;
ret = snfReadHeader(&fi, file);
if (ret != Successful)
return ret;
snfCopyInfo(&fi, pFontInfo);
pFontInfo->props = (FontPropPtr) xalloc(fi.nProps * sizeof(FontPropRec));
if (!pFontInfo->props)
return AllocError;
pFontInfo->isStringProp = (char *) xalloc(fi.nProps * sizeof(char));
if (!pFontInfo->isStringProp) {
xfree(pFontInfo->props);
return AllocError;
}
num_chars = n2dChars(&fi);
bytestoskip = num_chars * sizeof(snfCharInfoRec); /* charinfos */
bytestoskip += BYTESOFGLYPHINFO(&fi);
FontFileSkip(file, bytestoskip);
ret = snfReadProps(&fi, pFontInfo, file);
if (ret != Successful) {
xfree(pFontInfo->props);
xfree(pFontInfo->isStringProp);
return ret;
}
if (fi.inkMetrics) {
ret = snfReadxCharInfo(file, &pFontInfo->ink_minbounds);
if (ret != Successful) {
xfree(pFontInfo->props);
xfree(pFontInfo->isStringProp);
return ret;
}
ret = snfReadxCharInfo(file, &pFontInfo->ink_maxbounds);
if (ret != Successful) {
xfree(pFontInfo->props);
xfree(pFontInfo->isStringProp);
return ret;
}
}
return Successful;
}
static void
snfUnloadFont(pFont)
FontPtr pFont;
{
BitmapFontPtr bitmapFont;
bitmapFont = (BitmapFontPtr) pFont->fontPrivate;
xfree (bitmapFont->bitmaps);
xfree (bitmapFont);
xfree (pFont);
}
static int snf_set;
static int snf_bit, snf_byte, snf_glyph, snf_scan;
SnfSetFormat (bit, byte, glyph, scan)
int bit, byte, glyph, scan;
{
snf_bit = bit;
snf_byte = byte;
snf_glyph = glyph;
snf_scan = scan;
snf_set = 1;
}
SnfGetFormat (bit, byte, glyph, scan)
int *bit, *byte, *glyph, *scan;
{
if (!snf_set)
FontDefaultFormat (&snf_bit, &snf_byte, &snf_glyph, &snf_scan);
*bit = snf_bit;
*byte = snf_byte;
*glyph = snf_glyph;
*scan = snf_scan;
}
+1
Submodule reference/x11/r4 added at 61c1efa721.
+1
Submodule reference/x11/r5 added at e033053cda.