make_unicode: Create tables with data needed by nameprep algorithm.

This commit is contained in:
Piotr Caban 2012-04-25 17:56:33 +02:00 committed by Alexandre Julliard
parent 5c09a11e08
commit 047793e1aa
3 changed files with 1621 additions and 0 deletions

View File

@ -26,6 +26,7 @@ C_SRCS = \
locale.c \
lzexpand.c \
module.c \
nameprep.c \
oldconfig.c \
path.c \
powermgnt.c \

1430
dlls/kernel32/nameprep.c Normal file

File diff suppressed because it is too large Load Diff

View File

@ -28,6 +28,9 @@ my $UNIDATA = "http://www.unicode.org/Public/6.0.0/ucd";
# Sort keys file
my $SORTKEYS = "http://www.unicode.org/reports/tr10/allkeys.txt";
# RFC3454 (stringprep data)
my $STRINGPREP = "http://www.rfc-editor.org/rfc/rfc3454.txt";
# Defaults mapping
my $DEFAULTS = "tools/unicode-defaults";
@ -158,6 +161,14 @@ my %matra_types =
"Invisible" => 0x0e
);
my %nameprep_flags =
(
"unassigned" => 0x01,
"prohibited" => 0x02,
"bidi_ral" => 0x04,
"bidi_l" => 0x08
);
my %break_types =
(
"BK" => 0x0001,
@ -1491,6 +1502,184 @@ sub dump_intl_nls($)
}
sub load_nameprep_range_table($$$)
{
my ($INPUT, $val, $table_ref) = @_;
while (<$INPUT>)
{
if (/^\s*([0-9a-fA-F]+)-([0-9a-fA-F]+)/)
{
my $last = hex $2;
$last = 65535 if($last >= 65536);
foreach my $i (hex $1 .. $last)
{
$table_ref->[$i] |= $val;
}
next;
}
elsif (/^\s*([0-9a-fA-F]+)/)
{
if (hex $1 < 65536)
{
$table_ref->[hex $1] |= $val;
}
next;
}
return if (/End\sTable/);
}
}
sub load_nameprep_map_table($$)
{
my ($INPUT, $table_ref) = @_;
while (<$INPUT>)
{
if (/^\s*([0-9a-fA-F]+);\s;/)
{
# special value for map to nothing
$table_ref->[hex $1] = [0xffff, 0xffff, 0xffff];
next;
}
elsif (/^\s*([0-9a-fA-F]+);\s([0-9a-fA-F]+);/)
{
$table_ref->[hex $1] = [hex $2, 0, 0];
next;
}
elsif (/^\s*([0-9a-fA-F]+);\s([0-9a-fA-F]+)\s([0-9a-fA-F]+);/)
{
$table_ref->[hex $1] = [hex $2, hex $3, 0];
next;
}
elsif (/^\s*([0-9a-fA-F]+);\s([0-9a-fA-F]+)\s([0-9a-fA-F]+)\s([0-9a-fA-F]+);/)
{
$table_ref->[hex $1] = [hex $2, hex $3, hex $4];
next;
}
return if (/End\sTable/);
}
}
################################################################
# dump mapping table, prohibited characters set, unassigned
# characters, bidirectional rules used by nameprep algorithm
sub dump_nameprep($)
{
my $filename = shift;
my @mapping_table = ();
my @flags_table = (0) x 65536;
my $INPUT = open_data_file $STRINGPREP;
while (<$INPUT>)
{
next unless /Start\sTable/;
load_nameprep_range_table($INPUT, $nameprep_flags{"unassigned"}, \@flags_table) if (/A.1/);
load_nameprep_range_table($INPUT, $nameprep_flags{"prohibited"}, \@flags_table) if (/C.1.2/);
load_nameprep_range_table($INPUT, $nameprep_flags{"prohibited"}, \@flags_table) if (/C.2.2/);
load_nameprep_range_table($INPUT, $nameprep_flags{"prohibited"}, \@flags_table) if (/C.3/);
load_nameprep_range_table($INPUT, $nameprep_flags{"prohibited"}, \@flags_table) if (/C.4/);
load_nameprep_range_table($INPUT, $nameprep_flags{"prohibited"}, \@flags_table) if (/C.5/);
load_nameprep_range_table($INPUT, $nameprep_flags{"prohibited"}, \@flags_table) if (/C.6/);
load_nameprep_range_table($INPUT, $nameprep_flags{"prohibited"}, \@flags_table) if (/C.7/);
load_nameprep_range_table($INPUT, $nameprep_flags{"prohibited"}, \@flags_table) if (/C.8/);
load_nameprep_range_table($INPUT, $nameprep_flags{"prohibited"}, \@flags_table) if (/C.9/);
load_nameprep_range_table($INPUT, $nameprep_flags{"bidi_ral"}, \@flags_table) if (/D.1/);
load_nameprep_range_table($INPUT, $nameprep_flags{"bidi_l"}, \@flags_table) if (/D.2/);
load_nameprep_map_table($INPUT, \@mapping_table) if (/B.1/);
load_nameprep_map_table($INPUT, \@mapping_table) if (/B.2/);
}
close $INPUT;
open OUTPUT,">$filename.new" or die "Cannot create $filename";
print "Building $filename\n";
print OUTPUT "/* Nameprep algorithm related data */\n";
print OUTPUT "/* generated from $STRINGPREP */\n";
print OUTPUT "/* DO NOT EDIT!! */\n\n";
print OUTPUT "#include \"wine/unicode.h\"\n\n";
dump_two_level_mapping( "nameprep_char_type", @flags_table );
######### mapping table
# first determine all the 16-char subsets that contain something
my @filled = ();
my $pos = 16*3; # for the null subset
for (my $i = 0; $i < 65536; $i++)
{
next unless defined $mapping_table[$i];
$filled[$i >> 4] = $pos;
$pos += 16*3;
$i |= 15;
}
my $total = $pos;
# now count the 256-char subsets that contain something
my @filled_idx = (256) x 256;
$pos = 256 + 16;
for (my $i = 0; $i < 4096; $i++)
{
next unless $filled[$i];
$filled_idx[$i >> 4] = $pos;
$pos += 16;
$i |= 15;
}
my $null_offset = $pos;
$total += $pos;
# add the index offsets to the subsets positions
for (my $i = 0; $i < 4096; $i++)
{
next unless $filled[$i];
$filled[$i] += $null_offset;
}
# dump the main index
printf OUTPUT "const WCHAR nameprep_mapping[%d] =\n", $total;
printf OUTPUT "{\n /* index */\n";
printf OUTPUT "%s", DUMP_ARRAY( "0x%04x", 0, @filled_idx );
printf OUTPUT ",\n /* null sub-index */\n%s", DUMP_ARRAY( "0x%04x", 0, ($null_offset) x 16 );
# dump the second-level indexes
for (my $i = 0; $i < 256; $i++)
{
next unless ($filled_idx[$i] > 256);
my @table = @filled[($i<<4)..($i<<4)+15];
for (my $j = 0; $j < 16; $j++) { $table[$j] ||= $null_offset; }
printf OUTPUT ",\n /* sub-index %02x */\n", $i;
printf OUTPUT "%s", DUMP_ARRAY( "0x%04x", 0, @table );
}
# dump the 16-char subsets
printf OUTPUT ",\n /* null mapping */\n";
printf OUTPUT "%s", DUMP_ARRAY( "0x%04x", 0, (0) x 48 );
for (my $i = 0; $i < 4096; $i++)
{
next unless $filled[$i];
my @table = (0) x 48;
for (my $j = 0; $j < 16; $j++)
{
if (defined $mapping_table[($i<<4) + $j])
{
$table[3 * $j] = ${$mapping_table[($i << 4) + $j]}[0];
$table[3 * $j + 1] = ${$mapping_table[($i << 4) + $j]}[1];
$table[3 * $j + 2] = ${$mapping_table[($i << 4) + $j]}[2];
}
}
printf OUTPUT ",\n /* 0x%03x0 .. 0x%03xf */\n", $i, $i;
printf OUTPUT "%s", DUMP_ARRAY( "0x%04x", 0, @table );
}
printf OUTPUT "\n};\n";
close OUTPUT;
save_file($filename);
}
################################################################
# dump the ctype tables
sub DUMP_CTYPE_TABLES($)
@ -1890,6 +2079,7 @@ dump_shaping( "dlls/usp10/shaping.c" );
dump_linebreak( "dlls/usp10/linebreak.c" );
dump_indic( "dlls/usp10/indicsyllable.c" );
dump_intl_nls("tools/l_intl.nls");
dump_nameprep( "dlls/kernel32/nameprep.c" );
foreach my $file (@allfiles) { HANDLE_FILE( @{$file} ); }