]> git.proxmox.com Git - spiceterm.git/blame - genfont.c
avoid warning when started with 0 timeout
[spiceterm.git] / genfont.c
CommitLineData
31b5cce2
DM
1/*
2
3 Copyright (C) 2007-2013 Proxmox Server Solutions GmbH
4
5 Copyright: spiceterm is under GNU GPL, the GNU General Public License.
6
7 This program is free software; you can redistribute it and/or modify
8 it under the terms of the GNU General Public License as published by
9 the Free Software Foundation; version 2 dated June, 1991.
10
11 This program is distributed in the hope that it will be useful,
12 but WITHOUT ANY WARRANTY; without even the implied warranty of
13 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 GNU General Public License for more details.
15
16 You should have received a copy of the GNU General Public License
17 along with this program; if not, write to the Free Software
18 Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA
19 02111-1307, USA.
20
21 Author: Dietmar Maurer <dietmar@proxmox.com>
22
23*/
24
25#include <stdio.h>
26#include <stdlib.h>
27#include <zlib.h> /* read compressed console fonts */
28#include <glob.h>
29#include <string.h>
30
31
32/* map unicode to font */
33static unsigned short vt_fontmap[65536];
34
35/* font glyph storage */
36static unsigned char *vt_font_data = NULL;
37static int vt_font_size = 0;
38static int vt_font_maxsize = 0;
39
40/* PSF stuff */
41
42
43#define PSF_MAGIC1 0x36
44#define PSF_MAGIC2 0x04
45
46#define PSF_MODE256NOSFM 0
47#define PSF_MODE512NOSFM 1
48#define PSF_MODE256SFM 2
49#define PSF_MODE512SFM 3
50
51#define PSF_SEPARATOR 0xFFFF
52
53struct psf_header
54{
55 unsigned char magic1, magic2; /* Magic number */
56 unsigned char mode; /* PSF font mode */
57 unsigned char charheight; /* Character size */
58};
59
60#define PSF_MAGIC_OK(x) ((x).magic1 == PSF_MAGIC1 && (x).magic2 == PSF_MAGIC2)
61#define PSF_MODE_VALID(x) ((x) <= PSF_MODE512SFM)
62#define PSF_MODE_HAS512(x) (((x) == 1) || ((x) == 3))
63#define PSF_MODE_HASSFM(x) (((x) == 2) || ((x) == 3))
64
65typedef unsigned short unicode;
66
67static int
68font_add_glyph (const char *data)
69{
70
71 if (vt_font_size >= vt_font_maxsize) {
72 vt_font_maxsize += 256;
73 vt_font_data = realloc (vt_font_data, vt_font_maxsize*16);
74 }
75
76 memcpy (vt_font_data + vt_font_size*16, data, 16);
77
78 vt_font_size += 1;
79
80 return vt_font_size - 1;
81}
82
83static int
84load_psf_font (const char *filename, int is_default)
85{
86 struct psf_header psfhdr;
87
88 gzFile f = gzopen (filename, "rb");
89 if (f == NULL) {
90 fprintf (stderr, "unable to read file %s\n", filename);
91 exit(-1);
92 }
93
94 // read psf header
95 if (gzread(f, &psfhdr, sizeof(struct psf_header)) != sizeof(struct psf_header)) {
96 fprintf (stderr, "unable to read psf font header (%s)\n", filename);
97 gzclose (f);
98 return -1;
99 }
100
101 if (!PSF_MAGIC_OK(psfhdr) || !PSF_MODE_VALID(psfhdr.mode) ||
102 !PSF_MODE_HASSFM(psfhdr.mode) || (psfhdr.charheight != 16)) {
103 fprintf (stderr, "no valid 8*16 psf font (%s)\n", filename);
104 gzclose (f);
105 return -1;
106 }
107
108 int charcount = ((PSF_MODE_HAS512(psfhdr.mode)) ? 512 : 256);
109
110 int size = 16*charcount;
111
112 char *chardata = (char *)malloc (size);
113
114 if (size != gzread(f, chardata, size)) {
115 fprintf (stderr, "unable to read font character data (%s)\n", filename);
116 gzclose (f);
117 return -1;
118 }
119
120 unicode unichar;
121 int glyph;
122
123 for (glyph = 0 ;glyph < charcount ;glyph++) {
124 int fi = 0;
125 while (gzread (f, &unichar, sizeof(unicode)) == sizeof(unicode) &&
126 (unichar != PSF_SEPARATOR)) {
127 if (!vt_fontmap[unichar]) {
128 if (!fi) {
129 fi = font_add_glyph (chardata + glyph*16);
130 }
131 vt_fontmap[unichar] = fi;
132 }
133 }
134
135 if (is_default && fi && glyph < 256) {
136 vt_fontmap[0xf000 + glyph] = fi;
137 }
138 }
139
140 free (chardata);
141 gzclose (f);
142
143 return 0;
144}
145
146void
147print_glyphs ()
148{
149 int i, j;
150
151 printf ("int vt_font_size = %d;\n\n", vt_font_size);
152
153 printf ("unsigned char vt_font_data[] = {\n");
154 for (i = 0; i < vt_font_size; i++) {
155 printf ("\t/* %d 0x%02x */\n", i, i);
156 for (j = 0; j < 16; j++) {
157 unsigned char d = vt_font_data[i*16+j];
158 printf ("\t0x%02X, /* ", d);
159 int k;
160 for (k = 128; k > 0; k = k>>1) {
161 printf ("%c", (d & k) ? '1': '0');
162 }
163 printf (" */\n");
164 }
165 printf ("\n");
166 }
167 printf ("};\n\n");
168
169 printf ("unsigned short vt_fontmap[65536] = {\n");
170 for (i = 0; i < 0x0ffff; i++) {
171 printf ("\t/* 0x%04X => */ %d,\n", i, vt_fontmap[i]);
172 }
173 printf ("};\n\n");
174
175}
176
177int
178main (int argc, char** argv)
179{
180 char empty[] = { 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 };
181 glob_t globbuf;
182
183 font_add_glyph (empty);
184
185 /* font load order is only important if glyphs are redefined */
31b5cce2 186 load_psf_font ("/usr/share/consolefonts/lat1u-16.psf.gz", 0); /* Latin-1 */
b97b3a63 187 load_psf_font ("/usr/share/consolefonts/default8x16.psf.gz", 1); /* vga default */
31b5cce2
DM
188 load_psf_font ("/usr/share/consolefonts/lat2u-16.psf.gz", 0); /* Latin-2 */
189 load_psf_font ("/usr/share/consolefonts/lat4u-16.psf.gz", 0); /* Baltic */
190
191 load_psf_font ("/usr/share/consolefonts/iso07.f16.psf.gz", 0); /* Greek */
192 load_psf_font ("/usr/share/consolefonts/Goha-16.psf.gz", 0); /* Ethiopic */
ca84c6f1 193 load_psf_font ("/usr/share/consolefonts/Arabic-Fixed16.psf.gz", 0); /* Arabic */
31b5cce2 194
ca84c6f1 195 /* fixme: Japanese letters ? */
31b5cce2 196
ca84c6f1 197 glob("/usr/share/consolefonts/*", GLOB_ERR, NULL, &globbuf);
31b5cce2 198
ca84c6f1
DM
199 int i;
200 for (i = 0; i < globbuf.gl_pathc; i++) {
31b5cce2
DM
201 int pc = vt_font_size;
202 load_psf_font (globbuf.gl_pathv[i], 0);
203 if (vt_font_size > pc) {
ca84c6f1 204 //fprintf(stderr, "TEST: %s %d\n", globbuf.gl_pathv[i], vt_font_size - pc);
31b5cce2 205 }
31b5cce2
DM
206 }
207
ca84c6f1
DM
208 print_glyphs ();
209
31b5cce2
DM
210 exit (0);
211}