1 /* $OpenBSD: ntfs_conv.c,v 1.9 2013/11/24 16:02:30 jsing Exp $ */ 2 /* $NetBSD: ntfs_conv.c,v 1.1 2002/12/23 17:38:32 jdolecek Exp $ */ 3 4 /*- 5 * Copyright (c) 2001 The NetBSD Foundation, Inc. 6 * All rights reserved. 7 * 8 * Redistribution and use in source and binary forms, with or without 9 * modification, are permitted provided that the following conditions 10 * are met: 11 * 1. Redistributions of source code must retain the above copyright 12 * notice, this list of conditions and the following disclaimer. 13 * 2. Redistributions in binary form must reproduce the above copyright 14 * notice, this list of conditions and the following disclaimer in the 15 * documentation and/or other materials provided with the distribution. 16 * 17 * THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS 18 * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED 19 * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR 20 * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS 21 * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR 22 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF 23 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS 24 * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN 25 * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) 26 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE 27 * POSSIBILITY OF SUCH DAMAGE. 28 */ 29 30 /* 31 * File name recode stuff. 32 * 33 * The utf-8 routines were derived from src/lib/libc/locale/utf2.c. 34 */ 35 36 #include <sys/param.h> 37 #include <sys/systm.h> 38 #include <sys/namei.h> 39 #include <sys/mount.h> 40 41 /* #define NTFS_DEBUG 1 */ 42 #include <ntfs/ntfs.h> 43 #include <ntfs/ntfs_inode.h> 44 #include <ntfs/ntfs_subr.h> 45 46 /* UTF-8 encoding stuff */ 47 48 static const int _utf_count[16] = { 49 1, 1, 1, 1, 1, 1, 1, 1, 50 0, 0, 0, 0, 2, 2, 3, 0, 51 }; 52 53 /* 54 * Read one wide character off the string, shift the string pointer 55 * and return the character. 56 */ 57 wchar 58 ntfs_utf8_wget(const char **str) 59 { 60 int c; 61 wchar rune = 0; 62 const char *s = *str; 63 64 c = _utf_count[(s[0] >> 4) & 0xf]; 65 if (c == 0) { 66 c = 1; 67 goto encoding_error; 68 } 69 70 switch (c) { 71 case 1: 72 rune = s[0] & 0xff; 73 break; 74 case 2: 75 if ((s[1] & 0xc0) != 0x80) 76 goto encoding_error; 77 rune = ((s[0] & 0x1F) << 6) | (s[1] & 0x3F); 78 break; 79 case 3: 80 if ((s[1] & 0xC0) != 0x80 || (s[2] & 0xC0) != 0x80) 81 goto encoding_error; 82 rune = ((s[0] & 0x1F) << 12) | ((s[1] & 0x3F) << 6) | 83 (s[2] & 0x3F); 84 break; 85 } 86 87 encoding_error: 88 *str = *str + c; 89 return rune; 90 } 91 92 /* 93 * Encode wide character and write it to the string. 'n' specifies 94 * how much space there is in the string. Returns number of bytes written 95 * to the target string. 96 */ 97 int 98 ntfs_utf8_wput(char *s, size_t n, wchar wc) 99 { 100 if (wc & 0xf800) { 101 if (n < 3) { 102 /* bound check failure */ 103 DDPRINTF("ntfs_utf8_wput: need 3 bytes\n"); 104 return 0; 105 } 106 107 s[0] = 0xE0 | ((wc >> 12) & 0x0F); 108 s[1] = 0x80 | ((wc >> 6) & 0x3F); 109 s[2] = 0x80 | ((wc) & 0x3F); 110 return 3; 111 } else { 112 if (wc & 0x0780) { 113 if (n < 2) { 114 /* bound check failure */ 115 DDPRINTF("ntfs_utf8_wput: need 2 bytes\n"); 116 return 0; 117 } 118 119 s[0] = 0xC0 | ((wc >> 6) & 0x1F); 120 s[1] = 0x80 | ((wc) & 0x3F); 121 return 2; 122 } else { 123 if (n < 1) { 124 /* bound check failure */ 125 DDPRINTF("ntfs_utf8_wput: need 1 byte\n"); 126 return 0; 127 } 128 129 s[0] = wc; 130 return 1; 131 } 132 } 133 } 134 135 /* 136 * Compare two wide characters, returning 1, 0, -1 if the first is 137 * bigger, equal or lower than the second. 138 */ 139 int 140 ntfs_utf8_wcmp(wchar wc1, wchar wc2) 141 { 142 /* no conversions needed for utf8 */ 143 144 if (wc1 == wc2) 145 return 0; 146 else 147 return (int) wc1 - (int) wc2; 148 } 149