From d5090bb8f19f4b0fd868a5f9af367ebbb67b7f5a Mon Sep 17 00:00:00 2001 From: Mark Pulford Date: Sat, 3 Mar 2012 10:48:09 +1030 Subject: Use Javascript compat values for Infinity/NaN Use Javascript compatible values for Infinity/NaN when encoding invalid numbers. --- dtoa.c | 4 ++-- lua_cjson.c | 16 ++++++++++++---- manual.txt | 9 +++++---- tests/test.lua | 12 +++++++----- 4 files changed, 26 insertions(+), 15 deletions(-) diff --git a/dtoa.c b/dtoa.c index 520926c..56398ba 100644 --- a/dtoa.c +++ b/dtoa.c @@ -3748,9 +3748,9 @@ dtoa *decpt = 9999; #ifdef IEEE_Arith if (!word1(&u) && !(word0(&u) & 0xfffff)) - return nrv_alloc("inf", rve, 8); + return nrv_alloc("Infinity", rve, 8); #endif - return nrv_alloc("nan", rve, 3); + return nrv_alloc("NaN", rve, 3); } #endif #ifdef IBM diff --git a/lua_cjson.c b/lua_cjson.c index ca5b88d..c14a1c5 100644 --- a/lua_cjson.c +++ b/lua_cjson.c @@ -592,12 +592,20 @@ static void json_append_number(lua_State *l, json_config_t *cfg, if (cfg->encode_invalid_numbers == 0) { /* Prevent encoding invalid numbers */ if (isinf(num) || isnan(num)) - json_encode_exception(l, cfg, json, lindex, "must not be NaN or Inf"); + json_encode_exception(l, cfg, json, lindex, + "must not be NaN or Infinity"); } else if (cfg->encode_invalid_numbers == 1) { - /* Encode invalid numbers, but handle "nan" separately - * since some platforms may encode as "-nan". */ + /* Encode NaN/Infinity separately to ensure Javascript compatible + * values are used. */ if (isnan(num)) { - strbuf_append_mem(json, "nan", 3); + strbuf_append_mem(json, "NaN", 3); + return; + } + if (isinf(num)) { + if (num < 0) + strbuf_append_mem(json, "-Infinity", 9); + else + strbuf_append_mem(json, "Infinity", 8); return; } } else { diff --git a/manual.txt b/manual.txt index 3977f1f..a12e378 100644 --- a/manual.txt +++ b/manual.txt @@ -290,7 +290,7 @@ Lua CJSON may generate an error when trying to decode numbers not supported by the JSON specification. _Invalid numbers_ are defined as: - infinity -- not-a-number (NaN) +- NaN - hexadecimal Available settings: @@ -438,12 +438,13 @@ Lua CJSON may generate an error when encoding floating point numbers not supported by the JSON specification (_invalid numbers_): - infinity -- not-a-number (NaN) +- NaN Available settings: -+true+:: Allow _invalid numbers_ to be encoded. This will generate - non-standard JSON, but this output is supported by some libraries. ++true+:: Allow _invalid numbers_ to be encoded using the Javascript + compatible values +NaN+ and +Infinity+. This will generate + non-standard JSON, but these values are supported by some libraries. +"null"+:: Encode _invalid numbers_ as a JSON +null+ value. This allows infinity and NaN to be encoded into valid JSON. +false+:: Throw an error when attempting to encode _invalid numbers_. diff --git a/tests/test.lua b/tests/test.lua index 96a3201..b8fce84 100755 --- a/tests/test.lua +++ b/tests/test.lua @@ -261,10 +261,10 @@ local cjson_tests = { json.encode_invalid_numbers, { false }, true, { false } }, { "Encode NaN [throw error]", json.encode, { NaN }, - false, { "Cannot serialise number: must not be NaN or Inf" } }, + false, { "Cannot serialise number: must not be NaN or Infinity" } }, { "Encode Infinity [throw error]", json.encode, { Inf }, - false, { "Cannot serialise number: must not be NaN or Inf" } }, + false, { "Cannot serialise number: must not be NaN or Infinity" } }, { "Set encode_invalid_numbers(\"null\")", json.encode_invalid_numbers, { "null" }, true, { "null" } }, { "Encode NaN as null", @@ -274,9 +274,11 @@ local cjson_tests = { { "Set encode_invalid_numbers(true)", json.encode_invalid_numbers, { true }, true, { true } }, { "Encode NaN", - json.encode, { NaN }, true, { "nan" } }, - { "Encode Infinity", - json.encode, { Inf }, true, { "inf" } }, + json.encode, { NaN }, true, { "NaN" } }, + { "Encode +Infinity", + json.encode, { Inf }, true, { "Infinity" } }, + { "Encode -Infinity", + json.encode, { -Inf }, true, { "-Infinity" } }, { 'Set encode_invalid_numbers("off")', json.encode_invalid_numbers, { "off" }, true, { false } }, -- cgit v1.2.3