mirror of
https://github.com/reactos/reactos.git
synced 2025-02-23 17:05:46 +00:00
[KERNEL32_VISTA] Add and export IdnTo{Ascii,Unicode}. CORE-9246
svn path=/trunk/; revision=67120
This commit is contained in:
parent
175ee4b5c5
commit
b0dd365b65
5 changed files with 2000 additions and 2 deletions
|
@ -1,6 +1,6 @@
|
|||
|
||||
remove_definitions(-D_WIN32_WINNT=0x502)
|
||||
add_definitions(-D_WIN32_WINNT=0x600)
|
||||
remove_definitions(-D_WIN32_WINNT=0x502 -DWINVER=0x502)
|
||||
add_definitions(-D_WIN32_WINNT=0x600 -DWINVER=0x600)
|
||||
|
||||
add_definitions(-D_KERNEL32_)
|
||||
spec2def(kernel32_vista.dll kernel32_vista.spec ADD_IMPORTLIB)
|
||||
|
@ -8,7 +8,10 @@ spec2def(kernel32_vista.dll kernel32_vista.spec ADD_IMPORTLIB)
|
|||
list(APPEND SOURCE
|
||||
DllMain.c
|
||||
GetTickCount64.c
|
||||
IdnToAscii.c
|
||||
IdnToUnicode.c
|
||||
InitOnceExecuteOnce.c
|
||||
nameprep.c
|
||||
${CMAKE_CURRENT_BINARY_DIR}/kernel32_vista.def)
|
||||
|
||||
add_library(kernel32_vista SHARED ${SOURCE})
|
||||
|
|
380
reactos/dll/win32/kernel32_vista/IdnToAscii.c
Normal file
380
reactos/dll/win32/kernel32_vista/IdnToAscii.c
Normal file
|
@ -0,0 +1,380 @@
|
|||
|
||||
#define WIN32_NO_STATUS
|
||||
#include <wine/unicode.h>
|
||||
#include <debug.h>
|
||||
|
||||
/* Taken from Wine kernel32/locale.c */
|
||||
|
||||
enum {
|
||||
BASE = 36,
|
||||
TMIN = 1,
|
||||
TMAX = 26,
|
||||
SKEW = 38,
|
||||
DAMP = 700,
|
||||
INIT_BIAS = 72,
|
||||
INIT_N = 128
|
||||
};
|
||||
|
||||
static inline INT adapt(INT delta, INT numpoints, BOOL firsttime)
|
||||
{
|
||||
INT k;
|
||||
|
||||
delta /= (firsttime ? DAMP : 2);
|
||||
delta += delta/numpoints;
|
||||
|
||||
for(k=0; delta>((BASE-TMIN)*TMAX)/2; k+=BASE)
|
||||
delta /= BASE-TMIN;
|
||||
return k+((BASE-TMIN+1)*delta)/(delta+SKEW);
|
||||
}
|
||||
|
||||
static inline unsigned short get_table_entry( const unsigned short *table, WCHAR ch )
|
||||
{
|
||||
return table[table[table[ch >> 8] + ((ch >> 4) & 0x0f)] + (ch & 0xf)];
|
||||
}
|
||||
|
||||
INT WINAPI IdnToNameprepUnicode(DWORD dwFlags, LPCWSTR lpUnicodeCharStr, INT cchUnicodeChar,
|
||||
LPWSTR lpNameprepCharStr, INT cchNameprepChar)
|
||||
{
|
||||
enum {
|
||||
UNASSIGNED = 0x1,
|
||||
PROHIBITED = 0x2,
|
||||
BIDI_RAL = 0x4,
|
||||
BIDI_L = 0x8
|
||||
};
|
||||
|
||||
extern const unsigned short nameprep_char_type[];
|
||||
extern const WCHAR nameprep_mapping[];
|
||||
const WCHAR *ptr;
|
||||
WORD flags;
|
||||
WCHAR buf[64], *map_str, norm_str[64], ch;
|
||||
DWORD i, map_len, norm_len, mask, label_start, label_end, out = 0;
|
||||
BOOL have_bidi_ral, prohibit_bidi_ral, ascii_only;
|
||||
|
||||
DPRINT("%x %p %d %p %d\n", dwFlags, lpUnicodeCharStr, cchUnicodeChar,
|
||||
lpNameprepCharStr, cchNameprepChar);
|
||||
|
||||
if(dwFlags & ~(IDN_ALLOW_UNASSIGNED|IDN_USE_STD3_ASCII_RULES)) {
|
||||
SetLastError(ERROR_INVALID_FLAGS);
|
||||
return 0;
|
||||
}
|
||||
|
||||
if(!lpUnicodeCharStr || cchUnicodeChar<-1) {
|
||||
SetLastError(ERROR_INVALID_PARAMETER);
|
||||
return 0;
|
||||
}
|
||||
|
||||
if(cchUnicodeChar == -1)
|
||||
cchUnicodeChar = strlenW(lpUnicodeCharStr)+1;
|
||||
if(!cchUnicodeChar || (cchUnicodeChar==1 && lpUnicodeCharStr[0]==0)) {
|
||||
SetLastError(ERROR_INVALID_NAME);
|
||||
return 0;
|
||||
}
|
||||
|
||||
for(label_start=0; label_start<cchUnicodeChar;) {
|
||||
ascii_only = TRUE;
|
||||
for(i=label_start; i<cchUnicodeChar; i++) {
|
||||
ch = lpUnicodeCharStr[i];
|
||||
|
||||
if(i!=cchUnicodeChar-1 && !ch) {
|
||||
SetLastError(ERROR_INVALID_NAME);
|
||||
return 0;
|
||||
}
|
||||
/* check if ch is one of label separators defined in RFC3490 */
|
||||
if(!ch || ch=='.' || ch==0x3002 || ch==0xff0e || ch==0xff61)
|
||||
break;
|
||||
|
||||
if(ch > 0x7f) {
|
||||
ascii_only = FALSE;
|
||||
continue;
|
||||
}
|
||||
|
||||
if((dwFlags&IDN_USE_STD3_ASCII_RULES) == 0)
|
||||
continue;
|
||||
if((ch>='a' && ch<='z') || (ch>='A' && ch<='Z')
|
||||
|| (ch>='0' && ch<='9') || ch=='-')
|
||||
continue;
|
||||
|
||||
SetLastError(ERROR_INVALID_NAME);
|
||||
return 0;
|
||||
}
|
||||
label_end = i;
|
||||
/* last label may be empty */
|
||||
if(label_start==label_end && ch) {
|
||||
SetLastError(ERROR_INVALID_NAME);
|
||||
return 0;
|
||||
}
|
||||
|
||||
if((dwFlags&IDN_USE_STD3_ASCII_RULES) && (lpUnicodeCharStr[label_start]=='-' ||
|
||||
lpUnicodeCharStr[label_end-1]=='-')) {
|
||||
SetLastError(ERROR_INVALID_NAME);
|
||||
return 0;
|
||||
}
|
||||
|
||||
if(ascii_only) {
|
||||
/* maximal label length is 63 characters */
|
||||
if(label_end-label_start > 63) {
|
||||
SetLastError(ERROR_INVALID_NAME);
|
||||
return 0;
|
||||
}
|
||||
if(label_end < cchUnicodeChar)
|
||||
label_end++;
|
||||
|
||||
if(!lpNameprepCharStr) {
|
||||
out += label_end-label_start;
|
||||
}else if(out+label_end-label_start <= cchNameprepChar) {
|
||||
memcpy(lpNameprepCharStr+out, lpUnicodeCharStr+label_start,
|
||||
(label_end-label_start)*sizeof(WCHAR));
|
||||
if(lpUnicodeCharStr[label_end-1] > 0x7f)
|
||||
lpNameprepCharStr[out+label_end-label_start-1] = '.';
|
||||
out += label_end-label_start;
|
||||
}else {
|
||||
SetLastError(ERROR_INSUFFICIENT_BUFFER);
|
||||
return 0;
|
||||
}
|
||||
|
||||
label_start = label_end;
|
||||
continue;
|
||||
}
|
||||
|
||||
map_len = 0;
|
||||
for(i=label_start; i<label_end; i++) {
|
||||
ch = lpUnicodeCharStr[i];
|
||||
ptr = nameprep_mapping + nameprep_mapping[ch>>8];
|
||||
ptr = nameprep_mapping + ptr[(ch>>4)&0x0f] + 3*(ch&0x0f);
|
||||
|
||||
if(!ptr[0]) map_len++;
|
||||
else if(!ptr[1]) map_len++;
|
||||
else if(!ptr[2]) map_len += 2;
|
||||
else if(ptr[0]!=0xffff || ptr[1]!=0xffff || ptr[2]!=0xffff) map_len += 3;
|
||||
}
|
||||
if(map_len*sizeof(WCHAR) > sizeof(buf)) {
|
||||
map_str = HeapAlloc(GetProcessHeap(), 0, map_len*sizeof(WCHAR));
|
||||
if(!map_str) {
|
||||
SetLastError(ERROR_NOT_ENOUGH_MEMORY);
|
||||
return 0;
|
||||
}
|
||||
}else {
|
||||
map_str = buf;
|
||||
}
|
||||
map_len = 0;
|
||||
for(i=label_start; i<label_end; i++) {
|
||||
ch = lpUnicodeCharStr[i];
|
||||
ptr = nameprep_mapping + nameprep_mapping[ch>>8];
|
||||
ptr = nameprep_mapping + ptr[(ch>>4)&0x0f] + 3*(ch&0x0f);
|
||||
|
||||
if(!ptr[0]) {
|
||||
map_str[map_len++] = ch;
|
||||
}else if(!ptr[1]) {
|
||||
map_str[map_len++] = ptr[0];
|
||||
}else if(!ptr[2]) {
|
||||
map_str[map_len++] = ptr[0];
|
||||
map_str[map_len++] = ptr[1];
|
||||
}else if(ptr[0]!=0xffff || ptr[1]!=0xffff || ptr[2]!=0xffff) {
|
||||
map_str[map_len++] = ptr[0];
|
||||
map_str[map_len++] = ptr[1];
|
||||
map_str[map_len++] = ptr[2];
|
||||
}
|
||||
}
|
||||
|
||||
norm_len = FoldStringW(MAP_FOLDCZONE, map_str, map_len,
|
||||
norm_str, sizeof(norm_str)/sizeof(WCHAR)-1);
|
||||
if(map_str != buf)
|
||||
HeapFree(GetProcessHeap(), 0, map_str);
|
||||
if(!norm_len) {
|
||||
if(GetLastError() == ERROR_INSUFFICIENT_BUFFER)
|
||||
SetLastError(ERROR_INVALID_NAME);
|
||||
return 0;
|
||||
}
|
||||
|
||||
if(label_end < cchUnicodeChar) {
|
||||
norm_str[norm_len++] = lpUnicodeCharStr[label_end] ? '.' : 0;
|
||||
label_end++;
|
||||
}
|
||||
|
||||
if(!lpNameprepCharStr) {
|
||||
out += norm_len;
|
||||
}else if(out+norm_len <= cchNameprepChar) {
|
||||
memcpy(lpNameprepCharStr+out, norm_str, norm_len*sizeof(WCHAR));
|
||||
out += norm_len;
|
||||
}else {
|
||||
SetLastError(ERROR_INSUFFICIENT_BUFFER);
|
||||
return 0;
|
||||
}
|
||||
|
||||
have_bidi_ral = prohibit_bidi_ral = FALSE;
|
||||
mask = PROHIBITED;
|
||||
if((dwFlags&IDN_ALLOW_UNASSIGNED) == 0)
|
||||
mask |= UNASSIGNED;
|
||||
for(i=0; i<norm_len; i++) {
|
||||
ch = norm_str[i];
|
||||
flags = get_table_entry( nameprep_char_type, ch );
|
||||
|
||||
if(flags & mask) {
|
||||
SetLastError((flags & PROHIBITED) ? ERROR_INVALID_NAME
|
||||
: ERROR_NO_UNICODE_TRANSLATION);
|
||||
return 0;
|
||||
}
|
||||
|
||||
if(flags & BIDI_RAL)
|
||||
have_bidi_ral = TRUE;
|
||||
if(flags & BIDI_L)
|
||||
prohibit_bidi_ral = TRUE;
|
||||
}
|
||||
|
||||
if(have_bidi_ral) {
|
||||
ch = norm_str[0];
|
||||
flags = get_table_entry( nameprep_char_type, ch );
|
||||
if((flags & BIDI_RAL) == 0)
|
||||
prohibit_bidi_ral = TRUE;
|
||||
|
||||
ch = norm_str[norm_len-1];
|
||||
flags = get_table_entry( nameprep_char_type, ch );
|
||||
if((flags & BIDI_RAL) == 0)
|
||||
prohibit_bidi_ral = TRUE;
|
||||
}
|
||||
|
||||
if(have_bidi_ral && prohibit_bidi_ral) {
|
||||
SetLastError(ERROR_INVALID_NAME);
|
||||
return 0;
|
||||
}
|
||||
|
||||
label_start = label_end;
|
||||
}
|
||||
|
||||
return out;
|
||||
}
|
||||
|
||||
INT WINAPI IdnToAscii(DWORD dwFlags, LPCWSTR lpUnicodeCharStr, INT cchUnicodeChar,
|
||||
LPWSTR lpASCIICharStr, INT cchASCIIChar)
|
||||
{
|
||||
static const WCHAR prefixW[] = {'x','n','-','-'};
|
||||
|
||||
WCHAR *norm_str;
|
||||
INT i, label_start, label_end, norm_len, out_label, out = 0;
|
||||
|
||||
DPRINT("%x %p %d %p %d\n", dwFlags, lpUnicodeCharStr, cchUnicodeChar,
|
||||
lpASCIICharStr, cchASCIIChar);
|
||||
|
||||
norm_len = IdnToNameprepUnicode(dwFlags, lpUnicodeCharStr, cchUnicodeChar, NULL, 0);
|
||||
if(!norm_len)
|
||||
return 0;
|
||||
norm_str = HeapAlloc(GetProcessHeap(), 0, norm_len*sizeof(WCHAR));
|
||||
if(!norm_str) {
|
||||
SetLastError(ERROR_NOT_ENOUGH_MEMORY);
|
||||
return 0;
|
||||
}
|
||||
norm_len = IdnToNameprepUnicode(dwFlags, lpUnicodeCharStr,
|
||||
cchUnicodeChar, norm_str, norm_len);
|
||||
if(!norm_len) {
|
||||
HeapFree(GetProcessHeap(), 0, norm_str);
|
||||
return 0;
|
||||
}
|
||||
|
||||
for(label_start=0; label_start<norm_len;) {
|
||||
INT n = INIT_N, bias = INIT_BIAS;
|
||||
INT delta = 0, b = 0, h;
|
||||
|
||||
out_label = out;
|
||||
for(i=label_start; i<norm_len && norm_str[i]!='.' &&
|
||||
norm_str[i]!=0x3002 && norm_str[i]!='\0'; i++)
|
||||
if(norm_str[i] < 0x80)
|
||||
b++;
|
||||
label_end = i;
|
||||
|
||||
if(b == label_end-label_start) {
|
||||
if(label_end < norm_len)
|
||||
b++;
|
||||
if(!lpASCIICharStr) {
|
||||
out += b;
|
||||
}else if(out+b <= cchASCIIChar) {
|
||||
memcpy(lpASCIICharStr+out, norm_str+label_start, b*sizeof(WCHAR));
|
||||
out += b;
|
||||
}else {
|
||||
HeapFree(GetProcessHeap(), 0, norm_str);
|
||||
SetLastError(ERROR_INSUFFICIENT_BUFFER);
|
||||
return 0;
|
||||
}
|
||||
label_start = label_end+1;
|
||||
continue;
|
||||
}
|
||||
|
||||
if(!lpASCIICharStr) {
|
||||
out += 5+b; /* strlen(xn--...-) */
|
||||
}else if(out+5+b <= cchASCIIChar) {
|
||||
memcpy(lpASCIICharStr+out, prefixW, sizeof(prefixW));
|
||||
out += 4;
|
||||
for(i=label_start; i<label_end; i++)
|
||||
if(norm_str[i] < 0x80)
|
||||
lpASCIICharStr[out++] = norm_str[i];
|
||||
lpASCIICharStr[out++] = '-';
|
||||
}else {
|
||||
HeapFree(GetProcessHeap(), 0, norm_str);
|
||||
SetLastError(ERROR_INSUFFICIENT_BUFFER);
|
||||
return 0;
|
||||
}
|
||||
if(!b)
|
||||
out--;
|
||||
|
||||
for(h=b; h<label_end-label_start;) {
|
||||
INT m = 0xffff, q, k;
|
||||
|
||||
for(i=label_start; i<label_end; i++) {
|
||||
if(norm_str[i]>=n && m>norm_str[i])
|
||||
m = norm_str[i];
|
||||
}
|
||||
delta += (m-n)*(h+1);
|
||||
n = m;
|
||||
|
||||
for(i=label_start; i<label_end; i++) {
|
||||
if(norm_str[i] < n) {
|
||||
delta++;
|
||||
}else if(norm_str[i] == n) {
|
||||
for(q=delta, k=BASE; ; k+=BASE) {
|
||||
INT t = k<=bias ? TMIN : k>=bias+TMAX ? TMAX : k-bias;
|
||||
INT disp = q<t ? q : t+(q-t)%(BASE-t);
|
||||
if(!lpASCIICharStr) {
|
||||
out++;
|
||||
}else if(out+1 <= cchASCIIChar) {
|
||||
lpASCIICharStr[out++] = disp<='z'-'a' ?
|
||||
'a'+disp : '0'+disp-'z'+'a'-1;
|
||||
}else {
|
||||
HeapFree(GetProcessHeap(), 0, norm_str);
|
||||
SetLastError(ERROR_INSUFFICIENT_BUFFER);
|
||||
return 0;
|
||||
}
|
||||
if(q < t)
|
||||
break;
|
||||
q = (q-t)/(BASE-t);
|
||||
}
|
||||
bias = adapt(delta, h+1, h==b);
|
||||
delta = 0;
|
||||
h++;
|
||||
}
|
||||
}
|
||||
delta++;
|
||||
n++;
|
||||
}
|
||||
|
||||
if(out-out_label > 63) {
|
||||
HeapFree(GetProcessHeap(), 0, norm_str);
|
||||
SetLastError(ERROR_INVALID_NAME);
|
||||
return 0;
|
||||
}
|
||||
|
||||
if(label_end < norm_len) {
|
||||
if(!lpASCIICharStr) {
|
||||
out++;
|
||||
}else if(out+1 <= cchASCIIChar) {
|
||||
lpASCIICharStr[out++] = norm_str[label_end] ? '.' : 0;
|
||||
}else {
|
||||
HeapFree(GetProcessHeap(), 0, norm_str);
|
||||
SetLastError(ERROR_INSUFFICIENT_BUFFER);
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
label_start = label_end+1;
|
||||
}
|
||||
|
||||
HeapFree(GetProcessHeap(), 0, norm_str);
|
||||
return out;
|
||||
}
|
185
reactos/dll/win32/kernel32_vista/IdnToUnicode.c
Normal file
185
reactos/dll/win32/kernel32_vista/IdnToUnicode.c
Normal file
|
@ -0,0 +1,185 @@
|
|||
|
||||
#define WIN32_NO_STATUS
|
||||
#include <wine/unicode.h>
|
||||
#include <debug.h>
|
||||
|
||||
/* Taken from Wine kernel32/locale.c */
|
||||
|
||||
enum {
|
||||
BASE = 36,
|
||||
TMIN = 1,
|
||||
TMAX = 26,
|
||||
SKEW = 38,
|
||||
DAMP = 700,
|
||||
INIT_BIAS = 72,
|
||||
INIT_N = 128
|
||||
};
|
||||
|
||||
static inline INT adapt(INT delta, INT numpoints, BOOL firsttime)
|
||||
{
|
||||
INT k;
|
||||
|
||||
delta /= (firsttime ? DAMP : 2);
|
||||
delta += delta/numpoints;
|
||||
|
||||
for(k=0; delta>((BASE-TMIN)*TMAX)/2; k+=BASE)
|
||||
delta /= BASE-TMIN;
|
||||
return k+((BASE-TMIN+1)*delta)/(delta+SKEW);
|
||||
}
|
||||
|
||||
static inline unsigned short get_table_entry( const unsigned short *table, WCHAR ch )
|
||||
{
|
||||
return table[table[table[ch >> 8] + ((ch >> 4) & 0x0f)] + (ch & 0xf)];
|
||||
}
|
||||
|
||||
INT WINAPI IdnToUnicode(DWORD dwFlags, LPCWSTR lpASCIICharStr, INT cchASCIIChar,
|
||||
LPWSTR lpUnicodeCharStr, INT cchUnicodeChar)
|
||||
{
|
||||
extern const unsigned short nameprep_char_type[];
|
||||
|
||||
INT i, label_start, label_end, out_label, out = 0;
|
||||
WCHAR ch;
|
||||
|
||||
DPRINT("%x %p %d %p %d\n", dwFlags, lpASCIICharStr, cchASCIIChar,
|
||||
lpUnicodeCharStr, cchUnicodeChar);
|
||||
|
||||
for(label_start=0; label_start<cchASCIIChar;) {
|
||||
INT n = INIT_N, pos = 0, old_pos, w, k, bias = INIT_BIAS, delim=0, digit, t;
|
||||
|
||||
out_label = out;
|
||||
for(i=label_start; i<cchASCIIChar; i++) {
|
||||
ch = lpASCIICharStr[i];
|
||||
|
||||
if(ch>0x7f || (i!=cchASCIIChar-1 && !ch)) {
|
||||
SetLastError(ERROR_INVALID_NAME);
|
||||
return 0;
|
||||
}
|
||||
|
||||
if(!ch || ch=='.')
|
||||
break;
|
||||
if(ch == '-')
|
||||
delim = i;
|
||||
|
||||
if((dwFlags&IDN_USE_STD3_ASCII_RULES) == 0)
|
||||
continue;
|
||||
if((ch>='a' && ch<='z') || (ch>='A' && ch<='Z')
|
||||
|| (ch>='0' && ch<='9') || ch=='-')
|
||||
continue;
|
||||
|
||||
SetLastError(ERROR_INVALID_NAME);
|
||||
return 0;
|
||||
}
|
||||
label_end = i;
|
||||
/* last label may be empty */
|
||||
if(label_start==label_end && ch) {
|
||||
SetLastError(ERROR_INVALID_NAME);
|
||||
return 0;
|
||||
}
|
||||
|
||||
if((dwFlags&IDN_USE_STD3_ASCII_RULES) && (lpASCIICharStr[label_start]=='-' ||
|
||||
lpASCIICharStr[label_end-1]=='-')) {
|
||||
SetLastError(ERROR_INVALID_NAME);
|
||||
return 0;
|
||||
}
|
||||
if(label_end-label_start > 63) {
|
||||
SetLastError(ERROR_INVALID_NAME);
|
||||
return 0;
|
||||
}
|
||||
|
||||
if(label_end-label_start<4 ||
|
||||
tolowerW(lpASCIICharStr[label_start])!='x' ||
|
||||
tolowerW(lpASCIICharStr[label_start+1])!='n' ||
|
||||
lpASCIICharStr[label_start+2]!='-' || lpASCIICharStr[label_start+3]!='-') {
|
||||
if(label_end < cchASCIIChar)
|
||||
label_end++;
|
||||
|
||||
if(!lpUnicodeCharStr) {
|
||||
out += label_end-label_start;
|
||||
}else if(out+label_end-label_start <= cchUnicodeChar) {
|
||||
memcpy(lpUnicodeCharStr+out, lpASCIICharStr+label_start,
|
||||
(label_end-label_start)*sizeof(WCHAR));
|
||||
out += label_end-label_start;
|
||||
}else {
|
||||
SetLastError(ERROR_INSUFFICIENT_BUFFER);
|
||||
return 0;
|
||||
}
|
||||
|
||||
label_start = label_end;
|
||||
continue;
|
||||
}
|
||||
|
||||
if(delim == label_start+3)
|
||||
delim++;
|
||||
if(!lpUnicodeCharStr) {
|
||||
out += delim-label_start-4;
|
||||
}else if(out+delim-label_start-4 <= cchUnicodeChar) {
|
||||
memcpy(lpUnicodeCharStr+out, lpASCIICharStr+label_start+4,
|
||||
(delim-label_start-4)*sizeof(WCHAR));
|
||||
out += delim-label_start-4;
|
||||
}else {
|
||||
SetLastError(ERROR_INSUFFICIENT_BUFFER);
|
||||
return 0;
|
||||
}
|
||||
if(out != out_label)
|
||||
delim++;
|
||||
|
||||
for(i=delim; i<label_end;) {
|
||||
old_pos = pos;
|
||||
w = 1;
|
||||
for(k=BASE; ; k+=BASE) {
|
||||
ch = i<label_end ? tolowerW(lpASCIICharStr[i++]) : 0;
|
||||
if((ch<'a' || ch>'z') && (ch<'0' || ch>'9')) {
|
||||
SetLastError(ERROR_INVALID_NAME);
|
||||
return 0;
|
||||
}
|
||||
digit = ch<='9' ? ch-'0'+'z'-'a'+1 : ch-'a';
|
||||
pos += digit*w;
|
||||
t = k<=bias ? TMIN : k>=bias+TMAX ? TMAX : k-bias;
|
||||
if(digit < t)
|
||||
break;
|
||||
w *= BASE-t;
|
||||
}
|
||||
bias = adapt(pos-old_pos, out-out_label+1, old_pos==0);
|
||||
n += pos/(out-out_label+1);
|
||||
pos %= out-out_label+1;
|
||||
|
||||
if((dwFlags&IDN_ALLOW_UNASSIGNED)==0 &&
|
||||
get_table_entry(nameprep_char_type, n)==1/*UNASSIGNED*/) {
|
||||
SetLastError(ERROR_INVALID_NAME);
|
||||
return 0;
|
||||
}
|
||||
if(!lpUnicodeCharStr) {
|
||||
out++;
|
||||
}else if(out+1 <= cchASCIIChar) {
|
||||
memmove(lpUnicodeCharStr+out_label+pos+1,
|
||||
lpUnicodeCharStr+out_label+pos,
|
||||
(out-out_label-pos)*sizeof(WCHAR));
|
||||
lpUnicodeCharStr[out_label+pos] = n;
|
||||
out++;
|
||||
}else {
|
||||
SetLastError(ERROR_INSUFFICIENT_BUFFER);
|
||||
return 0;
|
||||
}
|
||||
pos++;
|
||||
}
|
||||
|
||||
if(out-out_label > 63) {
|
||||
SetLastError(ERROR_INVALID_NAME);
|
||||
return 0;
|
||||
}
|
||||
|
||||
if(label_end < cchASCIIChar) {
|
||||
if(!lpUnicodeCharStr) {
|
||||
out++;
|
||||
}else if(out+1 <= cchUnicodeChar) {
|
||||
lpUnicodeCharStr[out++] = lpASCIICharStr[label_end];
|
||||
}else {
|
||||
SetLastError(ERROR_INSUFFICIENT_BUFFER);
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
label_start = label_end+1;
|
||||
}
|
||||
|
||||
return out;
|
||||
}
|
|
@ -1,3 +1,5 @@
|
|||
|
||||
@ stdcall -ret64 GetTickCount64()
|
||||
@ stdcall IdnToAscii(long wstr long ptr long)
|
||||
@ stdcall IdnToUnicode(long wstr long ptr long)
|
||||
@ stdcall InitOnceExecuteOnce(ptr ptr ptr ptr)
|
||||
|
|
1428
reactos/dll/win32/kernel32_vista/nameprep.c
Normal file
1428
reactos/dll/win32/kernel32_vista/nameprep.c
Normal file
File diff suppressed because it is too large
Load diff
Loading…
Reference in a new issue