2 source [file join [file dirname
[info script
]] parseunicode.tcl
]
10 set iFirst
[lindex $map 0 0]
11 set cPrev
[lindex $map 0 1]
12 set fPrev
[lindex $map 0 2]
14 foreach m
[lrange $map 1 end
] {
17 if {$cPrev == $c && $fPrev==$f} {
18 for {set j
[expr $iFirst+$nRange]} {$j<$i} {incr j
} {
19 if {[info exists tl_lookup_table
($j)]==0} break
23 set nNew
[expr {(1 + $i - $iFirst)}]
31 lappend lRange
[list $iFirst $nRange]
40 lappend lRange
[list $iFirst $nRange]
45 puts "** If the argument is a codepoint corresponding to a lowercase letter"
46 puts "** in the ASCII range with a diacritic added, return the codepoint"
47 puts "** of the ASCII letter only. For example, if passed 235 - \"LATIN"
48 puts "** SMALL LETTER E WITH DIAERESIS\" - return 65 (\"LATIN SMALL LETTER"
49 puts "** E\"). The resuls of passing a codepoint that corresponds to an"
50 puts "** uppercase letter are undefined."
52 puts "static int ${::remove_diacritic}(int c, int bComplex)\{"
53 puts " unsigned short aDia\[\] = \{"
54 puts -nonewline " 0, "
57 foreach {iCode nRange
} $r {}
58 if {($i % 8)==0} {puts "" ; puts -nonewline " " }
61 puts -nonewline [format "%5d" [expr ($iCode<<3) + $nRange-1]]
66 puts "#define HIBIT ((unsigned char)0x80)"
67 puts " unsigned char aChar\[\] = \{"
68 puts -nonewline " '\\0', "
70 foreach c
$aChar f
$aFlag {
72 set str
"'$c'|HIBIT, "
76 if {$c == ""} { set str
"'\\0', " }
78 if {($i % 6)==0} {puts "" ; puts -nonewline " " }
80 puts -nonewline "$str"
85 unsigned int key
= (((unsigned int
)c
)<<3) |
0x00000007;
87 int iHi
= sizeof
(aDia
)/sizeof
(aDia
[0]) - 1;
90 int iTest
= (iHi
+ iLo
) / 2;
91 if( key
>= aDia
[iTest
] ){
98 assert
( key
>=aDia
[iRes
] );
99 if( bComplex
==0 && (aChar
[iRes
] & 0x80) ) return c
;
100 return (c
> (aDia
[iRes
]>>3) + (aDia
[iRes
]&0x07)) ? c
: ((int
)aChar
[iRes
] & 0x7F);}
104 proc print_isdiacritic
{zFunc map
} {
108 foreach {code char flag
} $m {}
110 if {$code && $char == ""} { lappend lCode
$code }
112 set lCode
[lsort -integer $lCode]
113 set iFirst
[lindex $lCode 0]
114 set iLast
[lindex $lCode end
]
120 set i
[expr $c - $iFirst]
122 set i1
[expr {$i1 |
(1<<$i)}]
124 set i2
[expr {$i2 |
(1<<($i-32))}]
129 puts "** Return true if the argument interpreted as a unicode codepoint"
130 puts "** is a diacritical modifier character."
132 puts "int ${zFunc}\(int c)\{"
133 puts " unsigned int mask0 = [format "0x
%08X
" $i1];"
134 puts " unsigned int mask1 = [format "0x
%08X
" $i2];"
136 puts " if( c<$iFirst || c>$iLast ) return 0;"
137 puts " return (c < $iFirst+32) ?"
138 puts " (mask0 & ((unsigned int)1 << (c-$iFirst))) :"
139 puts " (mask1 & ((unsigned int)1 << (c-$iFirst-32)));"
144 #-------------------------------------------------------------------------
146 proc an_load_separator_ranges
{} {
147 global unicodedata.txt
148 set lSep
[an_load_unicodedata_text
${unicodedata.txt
}]
149 unset -nocomplain iFirst
150 unset -nocomplain nRange
153 if {0==[info exists iFirst
]} {
156 } elseif
{ $sep == ($iFirst+$nRange) } {
159 lappend lRange
[list $iFirst $nRange]
164 lappend lRange
[list $iFirst $nRange]
168 proc an_print_range_array
{lRange
} {
171 foreach range
$lRange {
172 foreach {iFirst nRange
} $range {}
173 if {$iFirst > $iFirstMax} {set iFirstMax
$iFirst}
174 if {$nRange > $nRangeMax} {set nRangeMax
$nRange}
176 if {$iFirstMax >= (1<<22)} {error "first-max is too large for format"}
177 if {$nRangeMax >= (1<<10)} {error "range-max is too large for format"}
181 /* Each unsigned integer in the following
array corresponds to a contiguous
182 ** range of unicode codepoints that are not either letters or numbers
(i.e.
183 ** codepoints
for which this function should
return 0).
185 ** The most significant
22 bits in each
32-bit value contain the first
186 ** codepoint in the range. The least significant
10 bits are used to store
187 ** the size of the range
(always at least
1). In other words
, the value
188 ** ((C
<<22) + N
) represents a range of N codepoints starting with codepoint
189 ** C. It is not possible to represent a range larger than
1023 codepoints
190 ** using this
format.
193 puts -nonewline " static const unsigned int aEntry\[\] = \{"
195 foreach range
$lRange {
196 foreach {iFirst nRange
} $range {}
197 set u32
[format "0x%08X" [expr ($iFirst<<10) + $nRange]]
199 if {($i % 5)==0} {puts "" ; puts -nonewline " "}
200 puts -nonewline " $u32,"
207 proc an_print_ascii_bitmap
{lRange
} {
208 foreach range
$lRange {
209 foreach {iFirst nRange
} $range {}
210 for {set i
$iFirst} {$i < ($iFirst+$nRange)} {incr i
} {
211 if {$i<=127} { set a
($i) 1 }
215 set aAscii
[list 0 0 0 0]
216 foreach key
[array names a
] {
217 set idx
[expr $key >> 5]
218 lset aAscii
$idx [expr [lindex $aAscii $idx] |
(1 << ($key&0x001F))]
221 puts " static const unsigned int aAscii\[4\] = \{"
223 foreach v
$aAscii { puts -nonewline [format " 0x%08X," $v] }
228 proc print_isalnum
{zFunc lRange
} {
230 puts "** Return true if the argument corresponds to a unicode codepoint"
231 puts "** classified as either a letter or a number. Otherwise false."
233 puts "** The results are undefined if the value passed to this function"
234 puts "** is less than zero."
236 puts "int ${zFunc}\(int c)\{"
237 an_print_range_array
$lRange
238 an_print_ascii_bitmap
$lRange
240 if( (unsigned int
)c
<128 ){
241 return ( (aAscii
[c
>> 5] & ((unsigned int
)1 << (c
& 0x001F)))==0 );
242 }else if( (unsigned int
)c
<(1<<22) ){
243 unsigned int key
= (((unsigned int
)c
)<<10) |
0x000003FF;
245 int iHi
= sizeof
(aEntry
)/sizeof
(aEntry
[0]) - 1;
248 int iTest
= (iHi
+ iLo
) / 2;
249 if( key
>= aEntry
[iTest
] ){
256 assert
( aEntry
[0]<key
);
257 assert
( key
>=aEntry
[iRes
] );
258 return (((unsigned int
)c
) >= ((aEntry
[iRes
]>>10) + (aEntry
[iRes
]&0x3FF)));
264 proc print_test_isalnum
{zFunc lRange
} {
265 foreach range
$lRange {
266 foreach {iFirst nRange
} $range {}
267 for {set i
$iFirst} {$i < ($iFirst+$nRange)} {incr i
} { set a
($i) 1 }
270 puts "static int isalnum_test(int *piCode)\{"
271 puts -nonewline " unsigned char aAlnum\[\] = \{"
272 for {set i
0} {$i < 70000} {incr i
} {
273 if {($i % 32)==0} { puts "" ; puts -nonewline " " }
274 set bFlag
[expr ![info exists a
($i)]]
275 puts -nonewline "${bFlag},"
280 puts -nonewline " int aLargeSep\[\] = \{"
282 foreach iSep
[lsort -integer [array names a
]] {
283 if {$iSep<70000} continue
284 if {($i % 8)==0} { puts "" ; puts -nonewline " " }
285 puts -nonewline " $iSep,"
290 puts -nonewline " int aLargeOther\[\] = \{"
292 foreach iSep
[lsort -integer [array names a
]] {
293 if {$iSep<70000} continue
294 if {[info exists a
([expr $iSep-1])]==0} {
295 if {($i % 8)==0} { puts "" ; puts -nonewline " " }
296 puts -nonewline " [expr $iSep-1],"
299 if {[info exists a
([expr $iSep+1])]==0} {
300 if {($i % 8)==0} { puts "" ; puts -nonewline " " }
301 puts -nonewline " [expr $iSep+1],"
308 puts [subst -nocommands {
310 for(i
=0; i
<sizeof
(aAlnum
)/sizeof
(aAlnum
[0]); i
++){
311 if( ${zFunc
}(i
)!=aAlnum
[i
] ){
316 for(i
=0; i
<sizeof
(aLargeSep
)/sizeof
(aLargeSep
[0]); i
++){
317 if( ${zFunc
}(aLargeSep
[i
])!=0 ){
318 *piCode
= aLargeSep
[i
];
322 for(i
=0; i
<sizeof
(aLargeOther
)/sizeof
(aLargeOther
[0]); i
++){
323 if( ${zFunc
}(aLargeOther
[i
])!=1 ){
324 *piCode
= aLargeOther
[i
];
333 #-------------------------------------------------------------------------
335 proc tl_create_records
{} {
336 global tl_lookup_table
344 foreach code
[lsort -integer [array names tl_lookup_table
]] {
345 set mapping
$tl_lookup_table($code)
348 set nOff
[expr $mapping - $code]
352 set diff
[expr $code - ($iFirst + ($nIncr * ($nRange - 1)))]
353 if { $nRange==1 && ($diff==1 ||
$diff==2) } {
357 if {$diff != $nIncr ||
($mapping - $code)!=$nOff} {
358 if { $nRange==1 } {set nIncr
1}
359 lappend lRecord
[list $iFirst $nIncr $nRange $nOff]
361 set nOff
[expr $mapping - $code]
370 lappend lRecord
[list $iFirst $nIncr $nRange $nOff]
375 proc tl_print_table_header
{} {
378 /* Each
entry in the following
array defines a rule
for folding a range
379 ** of codepoints to
lower case. The rule applies to a range of nRange
380 ** codepoints starting at codepoint iCode.
382 ** If the least significant bit in flags is clear
, then the rule applies
383 ** to all nRange codepoints
(i.e. all nRange codepoints are upper case and
384 ** need to be folded
). Or
, if it is
set, then the rule only applies to
385 ** every second codepoint in the range
, starting with codepoint C.
387 ** The
7 most significant bits in flags are an index into the aiOff
[]
388 ** array. If a specific codepoint C does require folding
, then its
lower
389 ** case equivalent is
((C
+ aiOff
[flags
>>1]) & 0xFFFF).
391 ** The contents of this
array are generated by parsing the CaseFolding.txt
392 ** file distributed as part of the
"Unicode Character Database". See
393 ** http://www.unicode.org
for details.
396 puts " static const struct TableEntry \{"
397 puts " unsigned short iCode;"
398 puts " unsigned char flags;"
399 puts " unsigned char nRange;"
400 puts " \} aEntry\[\] = \{"
403 proc tl_print_table_entry
{togglevar
entry liOff
} {
405 foreach {iFirst nIncr nRange nOff
} $entry {}
407 if {$iFirst > (1<<16)} { return 1 }
409 if {[info exists t
]==0} {set t
0}
410 if {$t==0} { puts -nonewline " " }
413 if {$nIncr==2} { set flags
1 ; set nRange
[expr $nRange * 2]}
414 if {$nOff<0} { incr nOff
[expr (1<<16)] }
416 set idx
[lsearch $liOff $nOff]
417 if {$idx<0} {error "malfunction generating aiOff"}
418 set flags
[expr $flags + $idx*2]
420 set txt
"{$iFirst, $flags, $nRange},"
424 puts -nonewline [format "% -23s" $txt]
426 set t
[expr ($t+1)%3]
431 proc tl_print_table_footer
{togglevar
} {
437 proc tl_print_if_entry
{entry} {
438 foreach {iFirst nIncr nRange nOff
} $entry {}
439 if {$nIncr==2} {error "tl_print_if_entry needs improvement!"}
441 puts " else if( c>=$iFirst && c<[expr $iFirst+$nRange] )\{"
442 puts " ret = c + $nOff;"
446 proc tl_generate_ioff_table
{lRecord
} {
447 foreach entry $lRecord {
448 foreach {iFirst nIncr nRange iOff
} $entry {}
449 if {$iOff<0} { incr iOff
[expr (1<<16)] }
450 if {[info exists a
($iOff)]} continue
454 set liOff
[lsort -integer [array names a
]]
455 if {[llength $liOff]>128} { error "Too many distinct ioffs" }
459 proc tl_print_ioff_table
{liOff
} {
460 puts -nonewline " static const unsigned short aiOff\[\] = \{"
463 if {($i % 8)==0} {puts "" ; puts -nonewline " "}
464 puts -nonewline [format "% -7s" "$off,"]
472 proc print_fold
{zFunc
} {
474 set lRecord
[tl_create_records
]
478 puts "** Interpret the argument as a unicode codepoint. If the codepoint"
479 puts "** is an upper case character that has a lower case equivalent,"
480 puts "** return the codepoint corresponding to the lower case version."
481 puts "** Otherwise, return a copy of the argument."
483 puts "** The results are undefined if the value passed to this function"
484 puts "** is less than zero."
486 puts "int ${zFunc}\(int c, int eRemoveDiacritic)\{"
488 set liOff
[tl_generate_ioff_table
$lRecord]
489 tl_print_table_header
490 foreach entry $lRecord {
491 if {[tl_print_table_entry toggle
$entry $liOff]} {
495 tl_print_table_footer toggle
496 tl_print_ioff_table
$liOff
498 puts [subst -nocommands {
501 assert
( sizeof
(unsigned short
)==2 && sizeof
(unsigned char
)==1 );
504 if( c
>='A'
&& c
<='Z'
) ret
= c
+ ('a'
- 'A'
);
506 const struct TableEntry
*p
;
507 int iHi
= sizeof
(aEntry
)/sizeof
(aEntry
[0]) - 1;
511 assert
( c
>aEntry
[0].iCode
);
513 int iTest
= (iHi
+ iLo
) / 2;
514 int cmp
= (c
- aEntry
[iTest
].iCode
);
523 assert
( iRes
>=0 && c
>=aEntry
[iRes
].iCode
);
525 if( c
<(p-
>iCode
+ p-
>nRange
) && 0==(0x01 & p-
>flags
& (p-
>iCode ^ c
)) ){
526 ret
= (c
+ (aiOff
[p-
>flags
>>1])) & 0x0000FFFF;
530 if( eRemoveDiacritic
){
531 ret
= ${::remove_diacritic}(ret
, eRemoveDiacritic
==2);
536 foreach entry $lHigh {
537 tl_print_if_entry
$entry
546 set txt
[string trimright
$txt]
547 set txt
[string trimleft
$txt "\n"]
548 set n
[expr {[string length
$txt] - [string length
[string trim
$txt]]}]
550 foreach L
[split $txt "\n"] {
551 append ret
"[string range $L $n end]\n"
553 return [uplevel "subst -nocommands {$ret}"]
556 proc intarray
{lInt
} {
558 set n
[llength $lInt]
559 for {set i
0} {$i < $n} {incr i
10} {
561 foreach int
[lrange $lInt $i [expr $i+9]] {
562 append ret
[format "%-7s" "$int, "]
569 proc categories_switch
{Cvar first lSecond
} {
572 append ret
"case '$first':\n"
573 append ret
" switch( zCat\[1\] ){\n"
575 append ret
" case '$s': aArray\[$C($first$s)\] = 1; break;\n"
577 append ret
" case '*': \n"
579 append ret
" aArray\[$C($first$s)\] = 1;\n"
581 append ret
" break;\n"
582 append ret
" default: return 1;"
584 append ret
" break;\n"
587 # Argument is a list. Each element of which is itself a list of two elements:
592 # List elements are sorted in order of codepoint.
594 proc print_categories
{lMap
} {
607 for {set i
0} {$i < [llength $categories]} {incr i
} {
608 set C
([lindex $categories $i]) [expr 1+$i]
611 set caseC
[categories_switch C C
{c f n s o
}]
612 set caseL
[categories_switch C L
{l m o t u C
}]
613 set caseM
[categories_switch C M
{c e n
}]
614 set caseN
[categories_switch C N
{d l o
}]
615 set caseP
[categories_switch C P
{c d e f i o s
}]
616 set caseS
[categories_switch C S
{c k m o
}]
617 set caseZ
[categories_switch C Z
{l p s
}]
619 set nCat
[expr [llength [array names C
]] + 1]
621 int sqlite3Fts5UnicodeCatParse
(const char
*zCat
, u8
*aArray
){
637 set first
[lindex $lMap 0 0]
638 set class
[lindex $lMap 0 1]
645 foreach {codepoint cl
} $m {}
646 set codepoint
[expr "0x$codepoint"]
647 if {$codepoint>=(1<<20)} continue
650 if {$codepoint!=($prev+1)} {
653 $cl==$class ||
($class=="LC" && $cl==$CASE([expr $nRepeat & 0x01]))
656 } elseif
{$class=="Lu" && $nRepeat==1 && $cl=="Ll"} {
663 lappend lEntries
[list $first $class $nRepeat]
671 lappend lEntries
[list $first $class $nRepeat]
674 set aBlock
[list 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0]
676 foreach e
$lEntries {
677 foreach {cp class nRepeat
} $e {}
678 set block
[expr ($cp>>16)]
679 if {$block>0 && [lindex $aBlock $block]==0} {
680 for {set i
1} {$i<=$block} {incr i
} {
681 if {[lindex $aBlock $i]==0} {
682 lset aBlock
$i [llength $aMap]
686 lappend aMap
[expr {$cp & 0xFFFF}]
687 lappend aData
[expr {($nRepeat << 5) + $C($class)}]
689 for {set i
1} {$i<[llength $aBlock]} {incr i
} {
690 if {[lindex $aBlock $i]==0} {
691 lset aBlock
$i [llength $aMap]
695 set aBlockArray
[intarray
$aBlock]
696 set aMapArray
[intarray
$aMap]
697 set aDataArray
[intarray
$aData]
699 static u16 aFts5UnicodeBlock
[] = {$aBlockArray};
700 static u16 aFts5UnicodeMap
[] = {$aMapArray};
701 static u16 aFts5UnicodeData
[] = {$aDataArray};
703 int sqlite3Fts5UnicodeCategory
(u32 iCode
) {
710 if( iCode
>=(1<<20) ){
713 iLo
= aFts5UnicodeBlock
[(iCode
>>16)];
714 iHi
= aFts5UnicodeBlock
[1+(iCode
>>16)];
715 iKey
= (iCode
& 0xFFFF);
717 int iTest
= (iHi
+ iLo
) / 2;
718 assert
( iTest
>=iLo
&& iTest
<iHi
);
719 if( iKey
>=aFts5UnicodeMap
[iTest
] ){
727 if( iRes
<0 ) return 0;
728 if( iKey
>=(aFts5UnicodeMap
[iRes
]+(aFts5UnicodeData
[iRes
]>>5)) ) return 0;
729 ret
= aFts5UnicodeData
[iRes
] & 0x1F;
730 if( ret
!=$C(LC
) ) return ret
;
731 return ((iKey
- aFts5UnicodeMap
[iRes
]) & 0x01) ?
$C(Ll
) : $C(Lu
);
734 void sqlite3Fts5UnicodeAscii
(u8
*aArray
, u8
*aAscii
){
738 int bToken
= aArray
[ aFts5UnicodeData
[iTbl
] & 0x1F ];
739 int n
= (aFts5UnicodeData
[iTbl
] >> 5) + i
;
740 for(; i
<128 && i
<n
; i
++){
741 aAscii
[i
] = (u8
)bToken
;
745 aAscii
[0] = 0; /* 0x00 is never a token character
*/
750 proc print_test_categories
{lMap
} {
754 foreach {cp cat
} $e {}
755 if {[expr 0x
$cp] < (1<<20)} {
756 lappend lCP
"{0x$cp, \"$cat\"}, "
761 for {set i
0} {$i < [llength $lCP]} {incr i
4} {
762 append aCP
" [join [lrange $lCP $i $i+3]]\n"
767 static int categories_test
(int
*piCode
){
775 for(i
=0; i
<1000000; i
++){
779 memset
(aArray
, 0, sizeof
(aArray
));
780 if( aCP
[iCP
].iCode
==i
){
781 sqlite3Fts5UnicodeCatParse
(aCP
[iCP
].zCat
, aArray
);
787 c
= sqlite3Fts5UnicodeCategory
((u32
)i
);
799 proc print_fold_test
{zFunc mappings
} {
800 global tl_lookup_table
802 foreach m
$mappings {
805 set extra
([lindex $m 0]) 0
808 set extra
([lindex $m 0]) $i
812 puts "static int fold_test(int *piCode)\{"
813 puts -nonewline " static int aLookup\[\] = \{"
814 for {set i
0} {$i < 70000} {incr i
} {
817 catch { set expected
$tl_lookup_table($i) }
818 set expected2
$expected
819 catch { set expected2
$extra($expected2) }
821 if {($i % 4)==0} { puts "" ; puts -nonewline " " }
822 puts -nonewline "$expected, $expected2, "
826 puts " for(i=0; i<sizeof(aLookup)/sizeof(aLookup\[0\]); i++)\{"
827 puts " int iCode = (i/2);"
828 puts " int bFlag = i & 0x0001;"
829 puts " if( ${zFunc}\(iCode, bFlag)!=aLookup\[i\] )\{"
830 puts " *piCode = iCode;"
839 proc print_fileheader
{} {
844 ** The author disclaims copyright to this
source code. In
place of
845 ** a legal notice
, here is a blessing
:
847 ** May you do good and not evil.
848 ** May you find forgiveness
for yourself and forgive others.
849 ** May you share freely
, never taking more than you give.
851 ******************************************************************************
855 ** DO NOT EDIT THIS MACHINE GENERATED FILE.
859 if {$::generate_fts5_code} {
862 puts "#ifndef SQLITE_DISABLE_FTS3_UNICODE"
863 puts "#if defined(SQLITE_ENABLE_FTS3) || defined(SQLITE_ENABLE_FTS4)"
866 puts "#include <assert.h>"
870 proc print_test_main
{} {
872 puts "#include <stdio.h>"
874 puts "int main(int argc, char **argv)\{"
875 puts " int r1, r2, r3;"
878 puts " r1 = isalnum_test(&code);"
879 puts " if( r1 ) printf(\"isalnum(): Problem with code %d\\n\",code);"
880 puts " else printf(\"isalnum(): test passed\\n\");"
881 puts " r2 = fold_test(&code);"
882 puts " if( r2 ) printf(\"fold(): Problem with code %d\\n\",code);"
883 puts " else printf(\"fold(): test passed\\n\");"
884 if {$::generate_fts5_code} {
885 puts " r3 = categories_test(&code);"
886 puts " if( r3 ) printf(\"categories(): Problem with code %d\\n\",code);"
887 puts " else printf(\"categories(): test passed\\n\");"
889 puts " return (r1 || r2 || r3);"
893 # Proces the command line arguments. Exit early if they are not to
897 puts -nonewline stderr
"Usage: $::argv0 ?-test? ?-fts5? "
898 puts stderr
"<CaseFolding.txt file> <UnicodeData.txt file>"
901 if {[llength $argv]<2} usage
902 set unicodedata.txt
[lindex $argv end
]
903 set casefolding.txt
[lindex $argv end-1
]
905 set remove_diacritic remove_diacritic
906 set generate_test_code
0
907 set generate_fts5_code
0
908 set function_prefix
"sqlite3Fts"
909 for {set i
0} {$i < [llength $argv]-2} {incr i
} {
910 switch -- [lindex $argv $i] {
912 set generate_test_code
1
915 set function_prefix sqlite3Fts5
916 set generate_fts5_code
1
917 set remove_diacritic fts5_remove_diacritic
927 if {$::generate_test_code} {
928 puts "typedef unsigned short int u16;"
929 puts "typedef unsigned char u8;"
930 puts "#include <string.h>"
933 # Print the isalnum() function to stdout.
935 set lRange
[an_load_separator_ranges
]
936 if {$generate_fts5_code==0} {
937 print_isalnum
${function_prefix
}UnicodeIsalnum
$lRange
940 # Leave a gap between the two generated C functions.
945 # Load the fold data. This is used by the [rd_XXX] commands
946 # as well as [print_fold].
947 tl_load_casefolding_txt
${casefolding.txt
}
949 set mappings
[rd_load_unicodedata_text
${unicodedata.txt
}]
953 print_isdiacritic
${function_prefix
}UnicodeIsdiacritic
$mappings
957 # Print the fold() function to stdout.
959 print_fold
${function_prefix
}UnicodeFold
961 if {$generate_fts5_code} {
964 print_categories
[cc_load_unicodedata_text
${unicodedata.txt
}]
967 # Print the test routines and main() function to stdout, if -test
970 if {$::generate_test_code} {
971 if {$generate_fts5_code==0} {
972 print_test_isalnum
${function_prefix
}UnicodeIsalnum
$lRange
974 print_fold_test
${function_prefix
}UnicodeFold
$mappings
975 print_test_categories
[cc_load_unicodedata_text
${unicodedata.txt
}]
979 if {$generate_fts5_code} {
982 puts "#endif /* defined(SQLITE_ENABLE_FTS3) || defined(SQLITE_ENABLE_FTS4) */"
983 puts "#endif /* !defined(SQLITE_DISABLE_FTS3_UNICODE) */"