summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorP. J. McDermott <pj@pehjota.net>2014-07-11 13:50:09 (EDT)
committer P. J. McDermott <pj@pehjota.net>2014-07-11 13:50:09 (EDT)
commit54e15c8da9a7c1bf1e291c4a174f17e6d2186d7a (patch)
tree5bd224a56a22ef30fd708f2af97aacf87f734d81
Initial commit
-rwxr-xr-xbin/bdf2fbcon299
1 files changed, 299 insertions, 0 deletions
diff --git a/bin/bdf2fbcon b/bin/bdf2fbcon
new file mode 100755
index 0000000..364ccab
--- /dev/null
+++ b/bin/bdf2fbcon
@@ -0,0 +1,299 @@
+#!/usr/bin/perl
+
+=head1 NAME
+
+bdf2fbcon - Convert Glyph Bitmap Distribution Format fonts to Linux fbcon fonts
+
+=cut
+
+use strict;
+use warnings;
+
+use Getopt::Long;
+
+use constant {
+ BDF_2_1_SECTION_NONE => 0,
+ BDF_2_1_SECTION_PROPERTIES => 1,
+ BDF_2_1_SECTION_CHAR => 2,
+};
+
+my $VERSION;
+$VERSION = '0.1.0';
+
+sub main
+{
+ my %opts;
+ my %convert_opts;
+ my $input;
+ my $output;
+
+ $SIG{'__WARN__'} = \&warning;
+
+ Getopt::Long::Configure("no_ignore_case", "bundling", "gnu_compat",
+ "no_getopt_compat");
+ if (not GetOptions(\%opts,
+ "o=s",
+ "s=s",
+ "h|help",
+ "V|version",
+ )) {
+ usage(*STDERR);
+ exit(4);
+ }
+
+ if (exists($opts{'h'})) {
+ help(*STDOUT);
+ exit(0);
+ }
+ if (exists($opts{'V'})) {
+ version(*STDOUT);
+ exit(0);
+ }
+ if (exists($opts{'s'})) {
+ $convert_opts{'w'} = $convert_opts{'h'} = $opts{'s'};
+ $convert_opts{'w'} =~ s/x.*//;
+ $convert_opts{'h'} =~ s/.*x//;
+ }
+
+ if ($#ARGV lt 0) {
+ error(4, "No input files\n");
+ }
+
+ if (exists($opts{'o'})) {
+ if ($#ARGV gt 0) {
+ error(4, "Cannot specify -o with multiple files\n");
+ }
+ convert($ARGV[0], $opts{'o'}, %convert_opts);
+ } else {
+ for $input (@ARGV) {
+ $output = $input;
+ $output =~ s/\.bdf$/.c/;
+ convert($input, $output, %convert_opts);
+ }
+ }
+}
+
+sub usage
+{
+ my ($fh) = @_;
+
+ printf($fh "Usage: %s [-o <output>] <input> ...\n", $0);
+}
+
+sub help
+{
+ my ($fh) = @_;
+
+ usage($fh);
+ print($fh "Options:\n");
+ print($fh " -o <output> Place the output into <output>\n");
+ print($fh " -s <w>x<h> Override the font size\n");
+ print($fh " -h, --help Display this information\n");
+ print($fh " -V, --version Display version information\n");
+}
+
+sub version
+{
+ my ($fh) = @_;
+
+ printf($fh "bdf2fbcon %s\n", $VERSION);
+ print($fh "Copyright (C) 2013, 2014 Patrick \"P. J.\" McDermott\n");
+ print($fh "License GPLv3+: GNU GPL version 3 or later " .
+ "<http://gnu.org/licenses/gpl.html>.\n");
+ print($fh "This is free software: you are free to change and " .
+ "redistribute it.\n");
+ print($fh "There is NO WARRANTY, to the extent permitted by law.\n");
+}
+
+sub warning
+{
+ my ($fmt, @args) = @_;
+
+ printf(STDERR "bdf2fbcon: Warning: " . $fmt . "\n", @args);
+}
+
+sub error
+{
+ my ($status, $fmt, @args) = @_;
+
+ printf(STDERR "bdf2fbcon: Error: " . $fmt . "\n", @args);
+ exit($status);
+}
+
+sub convert
+{
+ my ($input, $output, %opts) = @_;
+ my $input_fh;
+ my $output_fh;
+ my $line;
+
+ if ($input eq $output and $input ne "-") {
+ warning("Input and output files are equal");
+ }
+
+ if ($input eq "-") {
+ $input_fh = *STDIN;
+ } else {
+ if (not open($input_fh, "<", $input)) {
+ error(4, "%s: %s", $input, $!);
+ }
+ }
+ if ($output eq "-") {
+ $output_fh = *STDOUT;
+ } else {
+ if (not open($output_fh, ">", $output . "~")) {
+ error(4, "%s: %s", $output . "~", $!);
+ }
+ }
+
+ $line = readline($input_fh);
+ if ($line =~ m/^STARTFONT 2.[12]$/) {
+ convert_bdf_2_1($input_fh, $output_fh, %opts);
+ } else {
+ error(4, "Unsupported input format");
+ }
+
+ if ($input ne "-") {
+ close($input_fh);
+ }
+ if ($output ne "-") {
+ close($output_fh);
+ if (not rename($output . "~", $output)) {
+ error(4, "%s: %s", $output, $!);
+ }
+ }
+}
+
+sub convert_bdf_2_1
+{
+ my ($input_fh, $output_fh, %opts) = @_;
+ my $font_w;
+ my $font_h;
+ my $section;
+ my $found_end;
+ my $line;
+ my $stmt;
+ my $arg;
+ my @argv;
+ my $font_idx;
+ my $font_name;
+
+ $font_w = $opts{'w'} if (exists($opts{'w'}));
+ $font_h = $opts{'h'} if (exists($opts{'h'}));
+
+ $section = BDF_2_1_SECTION_NONE;
+ $found_end = 0;
+ while ($line = readline($input_fh)) {
+ chomp($line);
+ ($stmt, $arg) = split(/[ \t]+/, $line, 2);
+ $arg =~ s/^"(.*)"$/$1/ if ($arg);
+ ($stmt, @argv) = split(/[ \t]+/, $line);
+ if ($section == BDF_2_1_SECTION_NONE) {
+ if ($stmt eq 'FONTBOUNDINGBOX') {
+ $font_w = $argv[0] unless ($font_w);
+ $font_h = $argv[1] unless ($font_h);
+ } elsif ($stmt eq 'COMMENT') {
+ printf($output_fh "/* %s */\n", $arg);
+ } elsif ($stmt eq 'STARTPROPERTIES') {
+ print($output_fh
+ "/* Generated by bdf2fbcon */\n\n");
+ print($output_fh "#include <linux/font.h>\n\n");
+ $section = BDF_2_1_SECTION_PROPERTIES;
+ } elsif ($stmt eq 'CHARS') {
+ # XXX
+ printf($output_fh "#define FONTDATAMAX %d\n\n",
+ 0);
+ printf($output_fh "static const unsigned char" .
+ " fontdata_%s[FONTDATAMAX] = {\n",
+ $font_name);
+ } elsif ($stmt eq 'STARTCHAR') {
+ $section = BDF_2_1_SECTION_CHAR;
+ } elsif ($stmt eq 'ENDFONT') {
+ $found_end = 1;
+ last;
+ }
+ } elsif ($section == BDF_2_1_SECTION_PROPERTIES) {
+ if ($stmt eq 'FONT_NAME') {
+ $font_idx = uc($arg);
+ $font_idx =~ s/[^A-Z0-9_]//g;
+ $font_name = lc($arg);
+ $font_name =~ s/[^a-z0-9_]/_/g;
+ } elsif ($stmt eq 'ENDPROPERTIES') {
+ $section = BDF_2_1_SECTION_NONE;
+ }
+ } elsif ($section == BDF_2_1_SECTION_CHAR) {
+ if ($stmt eq 'ENDCHAR') {
+ $section = BDF_2_1_SECTION_NONE;
+ }
+ }
+ }
+
+ warning("Missing end of font") unless ($found_end);
+
+ printf($output_fh "\n};\n\n");
+ printf($output_fh "const struct font_desc font_%s = {\n", $font_name);
+ printf($output_fh "\t.idx\t= %s_IDX,\n", $font_idx);
+ printf($output_fh "\t.name\t= \"%s\",\n", $font_idx);
+ printf($output_fh "\t.width\t= %d,\n", $font_w);
+ printf($output_fh "\t.height\t= %d,\n", $font_h);
+ printf($output_fh "\t.data\t= fontdata_%s,\n", $font_name);
+ # XXX
+ printf($output_fh "\t.pref\t= ???,\n");
+ printf($output_fh "};\n");
+}
+
+main();
+
+__END__
+
+=head1 SYNOPSIS
+
+B<bdf2fbcon>
+[B<-o> I<output>] [B<-s> I<w>xI<h>]
+I<input> ...
+
+=head1 DESCRIPTION
+
+B<bdf2fbcon> converts Glyph Bitmap Distribution Format fonts to Linux fbcon
+fonts.
+
+=head1 OPTIONS
+
+=over 4
+
+=item B<-o> I<output>
+
+Place the output into I<output>.
+
+=item B<-s> I<w>xI<h>
+
+Override the font size.
+
+=item B<-h>, B<--help>
+
+Display help information.
+
+=item B<-V>, B<--version>
+
+Display version information.
+
+=back
+
+=head1 COPYRIGHT
+
+Copyright (C) 2013, 2014 Patrick "P. J." McDermott
+
+This program is free software: you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation, either version 3 of the License, or
+(at your option) any later version.
+
+This program is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with this program. If not, see <http://www.gnu.org/licenses/>.
+
+=cut