1 /* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*-
2 * vim: sw=2 ts=2 et lcs=trail\:.,tab\:>~ :
3 * This Source Code Form is subject to the terms of the Mozilla Public
4 * License, v. 2.0. If a copy of the MPL was not distributed with this
5 * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
7 #include "mozilla/ArrayUtils.h"
9 #include "SQLCollations.h"
14 ////////////////////////////////////////////////////////////////////////////////
15 //// Local Helper Functions
20 * Helper function for the UTF-8 locale collations.
23 * The Service that owns the nsICollation used by this collation.
25 * The number of bytes in aStr1.
27 * The string to be compared against aStr2 as provided by SQLite. It
28 * must be a non-null-terminated char* buffer.
30 * The number of bytes in aStr2.
32 * The string to be compared against aStr1 as provided by SQLite. It
33 * must be a non-null-terminated char* buffer.
34 * @param aComparisonStrength
35 * The sorting strength, one of the nsICollation constants.
36 * @return aStr1 - aStr2. That is, if aStr1 < aStr2, returns a negative number.
37 * If aStr1 > aStr2, returns a positive number. If aStr1 == aStr2,
40 int localeCollationHelper8(void* aService
, int aLen1
, const void* aStr1
,
41 int aLen2
, const void* aStr2
,
42 int32_t aComparisonStrength
) {
43 NS_ConvertUTF8toUTF16
str1(static_cast<const char*>(aStr1
), aLen1
);
44 NS_ConvertUTF8toUTF16
str2(static_cast<const char*>(aStr2
), aLen2
);
45 Service
* serv
= static_cast<Service
*>(aService
);
46 return serv
->localeCompareStrings(str1
, str2
, aComparisonStrength
);
50 * Helper function for the UTF-16 locale collations.
53 * The Service that owns the nsICollation used by this collation.
55 * The number of bytes (not characters) in aStr1.
57 * The string to be compared against aStr2 as provided by SQLite. It
58 * must be a non-null-terminated char16_t* buffer.
60 * The number of bytes (not characters) in aStr2.
62 * The string to be compared against aStr1 as provided by SQLite. It
63 * must be a non-null-terminated char16_t* buffer.
64 * @param aComparisonStrength
65 * The sorting strength, one of the nsICollation constants.
66 * @return aStr1 - aStr2. That is, if aStr1 < aStr2, returns a negative number.
67 * If aStr1 > aStr2, returns a positive number. If aStr1 == aStr2,
70 int localeCollationHelper16(void* aService
, int aLen1
, const void* aStr1
,
71 int aLen2
, const void* aStr2
,
72 int32_t aComparisonStrength
) {
73 const char16_t
* buf1
= static_cast<const char16_t
*>(aStr1
);
74 const char16_t
* buf2
= static_cast<const char16_t
*>(aStr2
);
76 // The second argument to the nsDependentSubstring constructor is exclusive:
77 // It points to the char16_t immediately following the last one in the target
78 // substring. Since aLen1 and aLen2 are in bytes, divide by sizeof(char16_t)
79 // so that the pointer arithmetic is correct.
80 nsDependentSubstring
str1(buf1
, buf1
+ (aLen1
/ sizeof(char16_t
)));
81 nsDependentSubstring
str2(buf2
, buf2
+ (aLen2
/ sizeof(char16_t
)));
82 Service
* serv
= static_cast<Service
*>(aService
);
83 return serv
->localeCompareStrings(str1
, str2
, aComparisonStrength
);
86 // This struct is used only by registerCollations below, but ISO C++98 forbids
87 // instantiating a template dependent on a locally-defined type. Boo-urns!
91 int (*xCompare
)(void*, int, const void*, int, const void*);
96 ////////////////////////////////////////////////////////////////////////////////
97 //// Exposed Functions
99 int registerCollations(sqlite3
* aDB
, Service
* aService
) {
100 Collations collations
[] = {
101 {"locale", SQLITE_UTF8
, localeCollation8
},
102 {"locale_case_sensitive", SQLITE_UTF8
, localeCollationCaseSensitive8
},
103 {"locale_accent_sensitive", SQLITE_UTF8
, localeCollationAccentSensitive8
},
104 {"locale_case_accent_sensitive", SQLITE_UTF8
,
105 localeCollationCaseAccentSensitive8
},
106 {"locale", SQLITE_UTF16
, localeCollation16
},
107 {"locale_case_sensitive", SQLITE_UTF16
, localeCollationCaseSensitive16
},
108 {"locale_accent_sensitive", SQLITE_UTF16
,
109 localeCollationAccentSensitive16
},
110 {"locale_case_accent_sensitive", SQLITE_UTF16
,
111 localeCollationCaseAccentSensitive16
},
115 for (size_t i
= 0; SQLITE_OK
== rv
&& i
< ArrayLength(collations
); ++i
) {
116 struct Collations
* p
= &collations
[i
];
117 rv
= ::sqlite3_create_collation(aDB
, p
->zName
, p
->enc
, aService
,
124 ////////////////////////////////////////////////////////////////////////////////
127 int localeCollation8(void* aService
, int aLen1
, const void* aStr1
, int aLen2
,
129 return localeCollationHelper8(aService
, aLen1
, aStr1
, aLen2
, aStr2
,
130 nsICollation::kCollationCaseInSensitive
);
133 int localeCollationCaseSensitive8(void* aService
, int aLen1
, const void* aStr1
,
134 int aLen2
, const void* aStr2
) {
135 return localeCollationHelper8(aService
, aLen1
, aStr1
, aLen2
, aStr2
,
136 nsICollation::kCollationAccentInsenstive
);
139 int localeCollationAccentSensitive8(void* aService
, int aLen1
,
140 const void* aStr1
, int aLen2
,
142 return localeCollationHelper8(aService
, aLen1
, aStr1
, aLen2
, aStr2
,
143 nsICollation::kCollationCaseInsensitiveAscii
);
146 int localeCollationCaseAccentSensitive8(void* aService
, int aLen1
,
147 const void* aStr1
, int aLen2
,
149 return localeCollationHelper8(aService
, aLen1
, aStr1
, aLen2
, aStr2
,
150 nsICollation::kCollationCaseSensitive
);
153 int localeCollation16(void* aService
, int aLen1
, const void* aStr1
, int aLen2
,
155 return localeCollationHelper16(aService
, aLen1
, aStr1
, aLen2
, aStr2
,
156 nsICollation::kCollationCaseInSensitive
);
159 int localeCollationCaseSensitive16(void* aService
, int aLen1
, const void* aStr1
,
160 int aLen2
, const void* aStr2
) {
161 return localeCollationHelper16(aService
, aLen1
, aStr1
, aLen2
, aStr2
,
162 nsICollation::kCollationAccentInsenstive
);
165 int localeCollationAccentSensitive16(void* aService
, int aLen1
,
166 const void* aStr1
, int aLen2
,
168 return localeCollationHelper16(aService
, aLen1
, aStr1
, aLen2
, aStr2
,
169 nsICollation::kCollationCaseInsensitiveAscii
);
172 int localeCollationCaseAccentSensitive16(void* aService
, int aLen1
,
173 const void* aStr1
, int aLen2
,
175 return localeCollationHelper16(aService
, aLen1
, aStr1
, aLen2
, aStr2
,
176 nsICollation::kCollationCaseSensitive
);
179 } // namespace storage
180 } // namespace mozilla