1 /*
2 psftools: Manipulate console fonts in the .PSF format
3 Copyright (C) 2000, 2005, 2007 John Elliott
4
5 This program is free software; you can redistribute it and/or modify
6 it under the terms of the GNU General Public License as published by
7 the Free Software Foundation; either version 2 of the License, or
8 (at your option) any later version.
9
10 This program is distributed in the hope that it will be useful,
11 but WITHOUT ANY WARRANTY; without even the implied warranty of
12 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 GNU General Public License for more details.
14
15 You should have received a copy of the GNU General Public License
16 along with this program; if not, write to the Free Software
17 Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
18 */
19
20 /* Convert a PSF file to a C include file in the format used by the
21 * NetBSD kernel. */
22
23 #include "cnvshell.h"
24 #include "psflib.h"
25
26 char *cnv_progname = "PSF2BSD";
27
28 static char helpbuf[2000];
29 static char *cpbuf;
30 static char *fnbuf;
31 static char *tnbuf;
32 static char *fontname = NULL;
33 static char *typename = NULL;
34 static char *codepage = NULL;
35 static int first = -1;
36 static int last = -1;
37
cnv_set_option(int ddash,char * variable,char * value)38 char *cnv_set_option(int ddash, char *variable, char *value)
39 {
40 if (!strcmp(variable, "name"))
41 {
42 fnbuf = malloc(1 + strlen(value));
43 if (!fnbuf) return "Out of memory";
44 strcpy(fnbuf, value);
45 fontname = fnbuf;
46 return NULL;
47 }
48 if (!strcmp(variable, "typeface"))
49 {
50 tnbuf = malloc(1 + strlen(value));
51 if (!tnbuf) return "Out of memory";
52 strcpy(tnbuf, value);
53 typename = tnbuf;
54 return NULL;
55 }
56 if (!strcmp(variable, "encoding"))
57 {
58 if (!strcmp(value, "437"))
59 codepage = "WSDISPLAY_FONTENC_IBM";
60 else if (!strcmp(value, "819"))
61 codepage = "WSDISPLAY_FONTENC_ISO";
62 else if (!strcmp(value, "28591"))
63 codepage = "WSDISPLAY_FONTENC_ISO";
64 else
65 {
66 cpbuf = malloc(1 + strlen(value));
67 if (!cpbuf) return "Out of memory";
68 strcpy(cpbuf, value);
69 codepage = cpbuf;
70 }
71 return NULL;
72 }
73 if (!strcmp(variable, "first"))
74 {
75 first = atoi(value);
76 return NULL;
77 }
78 if (!strcmp(variable, "last"))
79 {
80 last = atoi(value);
81 return NULL;
82 }
83 if (strlen(variable) > 2000) variable[2000] = 0;
84 if (strlen(variable) > 2000) variable[2000] = 0;
85 sprintf(helpbuf, "Unknown option: %s\n", variable);
86 return helpbuf;
87 }
88
89 /* Return help string */
cnv_help(void)90 char *cnv_help(void)
91 {
92 sprintf(helpbuf, "Syntax: %s psffile incfile { options }\n\n",
93 cnv_progname);
94 strcat (helpbuf, "Options: \n"
95 " --name=name Set structure name (default: 'font')\n"
96 " --typeface=name Set typeface name (default: match structure name)\n"
97 " --encoding=437 Select IBM encoding\n"
98 " --encoding=819 Select ISO-8859-1 encoding\n"
99 " --encoding=... Set literal encoding name\n"
100 " --first=nnn Set first character to include\n"
101 " --last=nnn Set last character to include\n"
102 );
103
104 return helpbuf;
105 }
106
dumpbyte(FILE * fp,psf_byte value)107 void dumpbyte(FILE *fp, psf_byte value)
108 {
109 int mask;
110
111 for (mask = 0x80; mask != 0; mask = mask >> 1)
112 {
113 fprintf(fp, "%c", (value & mask) ? '#' : '-');
114 }
115 }
116
cnv_execute(FILE * infile,FILE * outfile)117 char *cnv_execute(FILE *infile, FILE *outfile)
118 {
119 int rv, stride, nstr;
120 psf_dword nchar, nrow;
121 PSF_FILE psf;
122
123 if (fontname == NULL)
124 {
125 fontname = "font";
126 }
127 if (codepage == NULL)
128 {
129 codepage = "WSDISPLAY_FONTENC_ISO";
130 }
131 if (typename == NULL)
132 {
133 typename = fontname;
134 }
135 psf_file_new(&psf);
136 rv = psf_file_read(&psf, infile);
137
138 if (rv != PSF_E_OK) return psf_error_string(rv);
139 if (first == -1 || first >= psf.psf_length)
140 {
141 first = 0;
142 }
143 if (last == -1 || last >= psf.psf_length)
144 {
145 last = psf.psf_length - 1;
146 }
147 if (last < first)
148 {
149 last = first;
150 }
151
152 stride = (psf.psf_width + 7) / 8;
153 fprintf(outfile, "static u_char %s_data[];\n\n", fontname);
154 fprintf(outfile, "static struct wsdisplay_font %s = {\n", fontname);
155 fprintf(outfile, "\t\"%s\",\t\t\t\t/* typeface name */\n", typename);
156 fprintf(outfile, "\t%d,\t\t\t\t/* firstchar */\n", first);
157 fprintf(outfile, "\t%d,\t\t\t\t/* numchars */\n", last - first + 1);
158 fprintf(outfile, "\t%s,\t\t/* encoding */\n", codepage);
159 fprintf(outfile, "\t%ld,\t\t\t\t/* width */\n", psf.psf_width);
160 fprintf(outfile, "\t%ld,\t\t\t\t/* height */\n", psf.psf_height);
161 fprintf(outfile, "\t%d,\t\t\t\t/* stride */\n", stride);
162 fprintf(outfile, "\tWSDISPLAY_FONTORDER_L2R,\t/* bit order */\n");
163 fprintf(outfile, "\tWSDISPLAY_FONTORDER_L2R,\t/* byte order */\n");
164 fprintf(outfile, "\t%s_data\t\t\t/* data */\n", fontname);
165 fprintf(outfile, "};\n\n");
166
167 fprintf(outfile, "static u_char %s_data[] = {\n", fontname);
168 for (nchar = first; nchar <= last; nchar++)
169 {
170 if (stride > 1) fprintf(outfile, "\t");
171 fprintf(outfile, "\t\t/* 0x%02lx ", nchar);
172 if (nchar >= 0x20 && nchar < 0x7F)
173 fprintf(outfile, "('%c')", (int)nchar);
174 else fprintf(outfile, " ");
175 fprintf(outfile, " */\n");
176 for (nrow = 0; nrow < psf.psf_height; nrow++)
177 {
178 psf_byte *ptr = psf.psf_data + nchar * psf.psf_charlen;
179
180 ptr += nrow * stride;
181 fprintf(outfile, "\t");
182 for (nstr = 0; nstr < stride; nstr++)
183 {
184 fprintf(outfile, "0x%02x, ", ptr[nstr]);
185 }
186 fprintf(outfile, "\t/* ");
187 for (nstr = 0; nstr < stride; nstr++)
188 {
189 dumpbyte(outfile, ptr[nstr]);
190 }
191 fprintf(outfile, " */\n");
192 }
193 fprintf(outfile, "\n");
194 }
195 fprintf(outfile, "};\n");
196 psf_file_delete(&psf);
197 return NULL;
198 }
199
200