Software / code / prosody
Comparison
util/json.lua @ 5436:a4ba5819bf50
util.json: Convert \uXXXX to UTF-8 when decoding
| author | Matthew Wild <mwild1@gmail.com> |
|---|---|
| date | Sat, 06 Apr 2013 12:20:31 +0100 |
| parent | 5395:ec33d72a08b6 |
| child | 5516:9733836629f9 |
comparison
equal
deleted
inserted
replaced
| 5435:f56e449a63e3 | 5436:a4ba5819bf50 |
|---|---|
| 1 -- Prosody IM | |
| 2 -- Copyright (C) 2008-2010 Matthew Wild | |
| 3 -- Copyright (C) 2008-2010 Waqas Hussain | |
| 4 -- | |
| 5 -- utf8char copyright (C) 2007 Rici Lake | |
| 6 -- | |
| 7 -- This project is MIT/X11 licensed. Please see the | |
| 8 -- COPYING file in the source package for more information. | |
| 9 -- | |
| 1 | 10 |
| 2 local type = type; | 11 local type = type; |
| 3 local t_insert, t_concat, t_remove, t_sort = table.insert, table.concat, table.remove, table.sort; | 12 local t_insert, t_concat, t_remove, t_sort = table.insert, table.concat, table.remove, table.sort; |
| 4 local s_char = string.char; | 13 local s_char = string.char; |
| 5 local tostring, tonumber = tostring, tonumber; | 14 local tostring, tonumber = tostring, tonumber; |
| 26 b = "\b", f = "\f", n = "\n", r = "\r", t = "\t"}; | 35 b = "\b", f = "\f", n = "\n", r = "\r", t = "\t"}; |
| 27 for i=0,31 do | 36 for i=0,31 do |
| 28 local ch = s_char(i); | 37 local ch = s_char(i); |
| 29 if not escapes[ch] then escapes[ch] = ("\\u%.4X"):format(i); end | 38 if not escapes[ch] then escapes[ch] = ("\\u%.4X"):format(i); end |
| 30 end | 39 end |
| 40 | |
| 41 local function utf8char(i) | |
| 42 if i >= 0 then | |
| 43 i = i - i%1 | |
| 44 if i < 128 then | |
| 45 return s_char(i) | |
| 46 else | |
| 47 local c1 = i % 64 | |
| 48 i = (i - c1) / 64 | |
| 49 if i < 32 then | |
| 50 return s_char(0xC0+i, 0x80+c1) | |
| 51 else | |
| 52 local c2 = i % 64 | |
| 53 i = (i - c2) / 64 | |
| 54 if i < 16 and (i ~= 13 or c2 < 32) then | |
| 55 return s_char(0xE0+i, 0x80+c2, 0x80+c1) | |
| 56 elseif i >= 16 and i < 0x110 then | |
| 57 local c3 = i % 64 | |
| 58 i = (i - c3) / 64 | |
| 59 return s_char(0xF0+i, 0x80+c3, 0x80+c2, 0x80+c1) | |
| 60 end | |
| 61 end | |
| 62 end | |
| 63 end | |
| 64 end | |
| 65 | |
| 31 | 66 |
| 32 local valid_types = { | 67 local valid_types = { |
| 33 number = true, | 68 number = true, |
| 34 string = true, | 69 string = true, |
| 35 table = true, | 70 table = true, |
| 247 next(); | 282 next(); |
| 248 if not ch then error("unexpected eof in string"); end | 283 if not ch then error("unexpected eof in string"); end |
| 249 if not ch:match("[0-9a-fA-F]") then error("invalid unicode escape sequence in string"); end | 284 if not ch:match("[0-9a-fA-F]") then error("invalid unicode escape sequence in string"); end |
| 250 seq = seq..ch; | 285 seq = seq..ch; |
| 251 end | 286 end |
| 252 s = s..s.char(tonumber(seq, 16)); -- FIXME do proper utf-8 | 287 s = s..utf8char(tonumber(seq, 16)); |
| 253 next(); | 288 next(); |
| 254 else error("invalid escape sequence in string"); end | 289 else error("invalid escape sequence in string"); end |
| 255 end | 290 end |
| 256 if ch == "\"" then | 291 if ch == "\"" then |
| 257 next(); | 292 next(); |