aboutsummaryrefslogtreecommitdiffstats
path: root/lib
diff options
context:
space:
mode:
authorSverker Eriksson <sverker@erlang.org>2017-04-12 19:34:44 +0200
committerSverker Eriksson <sverker@erlang.org>2017-04-12 19:34:44 +0200
commit82e849adee6e2fd20e2a3faa6ecb463cc2c7256e (patch)
treee114f79d16681ab05e9723e0f3ac5a87c46a8527 /lib
parent4eeaec9bb5dcf94139d3907f2489a44674753153 (diff)
parenta72e675fce23b9bebb7c9ff8beb6f962c4f9930a (diff)
downloadotp-82e849adee6e2fd20e2a3faa6ecb463cc2c7256e.tar.gz
otp-82e849adee6e2fd20e2a3faa6ecb463cc2c7256e.tar.bz2
otp-82e849adee6e2fd20e2a3faa6ecb463cc2c7256e.zip
Merge branch sverker/remove-latin1-atom-encoding/OTP-14337
* sverker/remove-latin1-atom-encoding: kernel: Fix erl_distribution_wb_SUITE:whitebox kernel: Remove pg2_SUITE:compat erts: Remove fun_r13_SUITE stdlib: Remove test cases for R12 io protocol kernel: Make DFLAG_UTF8_ATOMS mandatory kernel: Rewrite distribution flag verification tools: Update assumptions in lcnt about external atom format stdlib: Tweak beam_lib_SUITE whitebox assumptions orber: Remove hard dependency to external atom format kernel: Try mend disk_log whitebox tests erts: Mark latin1 atom encoding as deprecated jinterface: Do not generate atoms on old latin1 external format erl_interface: Do not generate atoms on old latin1 ext format erts: Do not generate atoms on old latin1 external format erts: Fix faulty ASSERT for failed dec_term
Diffstat (limited to 'lib')
-rw-r--r--lib/erl_interface/doc/src/ei.xml20
-rw-r--r--lib/erl_interface/src/encode/encode_atom.c64
-rw-r--r--lib/erl_interface/src/encode/encode_boolean.c8
-rw-r--r--lib/erl_interface/src/legacy/erl_eterm.c16
-rw-r--r--lib/erl_interface/src/legacy/erl_marshal.c13
-rw-r--r--lib/erl_interface/test/ei_decode_SUITE.erl25
-rw-r--r--lib/erl_interface/test/ei_decode_SUITE_data/ei_decode_test.c18
-rw-r--r--lib/erl_interface/test/ei_decode_encode_SUITE.erl1
-rw-r--r--lib/erl_interface/test/ei_encode_SUITE.erl36
-rw-r--r--lib/erl_interface/test/erl_ext_SUITE_data/ext_test.c10
-rw-r--r--lib/jinterface/java_src/com/ericsson/otp/erlang/OtpOutputStream.java29
-rw-r--r--lib/jinterface/test/jinterface_SUITE_data/Maps.java10
-rw-r--r--lib/kernel/src/dist_util.erl49
-rw-r--r--lib/kernel/test/disk_log_SUITE.erl50
-rw-r--r--lib/kernel/test/erl_distribution_wb_SUITE.erl6
-rw-r--r--lib/kernel/test/pg2_SUITE.erl27
-rw-r--r--lib/orber/COSS/CosNaming/CosNaming_NamingContextExt_impl.erl15
-rw-r--r--lib/stdlib/test/beam_lib_SUITE.erl4
-rw-r--r--lib/stdlib/test/io_proto_SUITE.erl271
-rw-r--r--lib/tools/src/lcnt.erl23
20 files changed, 184 insertions, 511 deletions
diff --git a/lib/erl_interface/doc/src/ei.xml b/lib/erl_interface/doc/src/ei.xml
index ddfb4d88a8..c3c776296c 100644
--- a/lib/erl_interface/doc/src/ei.xml
+++ b/lib/erl_interface/doc/src/ei.xml
@@ -421,22 +421,16 @@ typedef enum {
<name><ret>int</ret><nametext>ei_x_encode_atom_len_as(ei_x_buff* x, const char *p, int len, erlang_char_encoding from_enc, erlang_char_encoding to_enc)</nametext></name>
<fsummary>Encode an atom.</fsummary>
<desc>
- <p>Encodes an atom in the binary format with character encoding
- <seealso marker="#erlang_char_encoding"><c>to_enc</c></seealso>
- (Latin-1 or UTF-8). Parameter <c>p</c> is the name of the atom with
+ <p>Encodes an atom in the binary format. Parameter <c>p</c> is the name of the atom with
character encoding
<seealso marker="#erlang_char_encoding"><c>from_enc</c></seealso>
(ASCII, Latin-1, or UTF-8). The name must either be <c>NULL</c>-terminated or
- a function variant with a <c>len</c> parameter must be used.
- If <c>to_enc</c> is set to the bitwise OR'd combination
- <c>(ERLANG_LATIN1|ERLANG_UTF8)</c>, UTF-8 encoding is only used if the
- atom string cannot be represented in Latin-1 encoding.</p>
- <p>The encoding fails if <c>p</c> is an invalid string in encoding
- <c>from_enc</c>, if the string is too long, or if it cannot be
- represented with character encoding <c>to_enc</c>.</p>
- <p>These functions were introduced in Erlang/OTP R16 as part of a first
- step to support UTF-8 atoms. Atoms encoded with <c>ERLANG_UTF8</c>
- cannot be decoded by earlier releases than R16.</p>
+ a function variant with a <c>len</c> parameter must be used.</p>
+ <p>The encoding fails if <c>p</c> is not a valid string in encoding
+ <c>from_enc</c>.</p>
+
+ <p>Argument <c>to_enc</c> is ignored. As from Erlang/OTP 20 the encoding is always
+ done in UTF-8 which is readable by nodes as old as Erlang/OTP R16.</p>
</desc>
</func>
diff --git a/lib/erl_interface/src/encode/encode_atom.c b/lib/erl_interface/src/encode/encode_atom.c
index c1817628e5..1fd7811a0e 100644
--- a/lib/erl_interface/src/encode/encode_atom.c
+++ b/lib/erl_interface/src/encode/encode_atom.c
@@ -26,7 +26,6 @@
static int verify_ascii_atom(const char* src, int slen);
static int verify_utf8_atom(const char* src, int slen);
-static int is_latin1_as_utf8(const char *p, int len);
int ei_encode_atom(char *buf, int *index, const char *p)
{
@@ -34,7 +33,7 @@ int ei_encode_atom(char *buf, int *index, const char *p)
if (len >= MAXATOMLEN)
len = MAXATOMLEN - 1;
- return ei_encode_atom_len_as(buf, index, p, len, ERLANG_LATIN1, ERLANG_LATIN1);
+ return ei_encode_atom_len_as(buf, index, p, len, ERLANG_LATIN1, 0);
}
int ei_encode_atom_len(char *buf, int *index, const char *p, int len)
@@ -42,7 +41,7 @@ int ei_encode_atom_len(char *buf, int *index, const char *p, int len)
/* This function is documented to truncate at MAXATOMLEN (256) */
if (len >= MAXATOMLEN)
len = MAXATOMLEN - 1;
- return ei_encode_atom_len_as(buf, index, p, len, ERLANG_LATIN1, ERLANG_LATIN1);
+ return ei_encode_atom_len_as(buf, index, p, len, ERLANG_LATIN1, 0);
}
int ei_encode_atom_as(char *buf, int *index, const char *p,
@@ -64,46 +63,11 @@ int ei_encode_atom_len_as(char *buf, int *index, const char *p, int len,
return -1;
}
- if (to_enc == (ERLANG_LATIN1 | ERLANG_UTF8)) {
- if (from_enc == ERLANG_UTF8) {
- to_enc = is_latin1_as_utf8(p, len) ? ERLANG_LATIN1 : ERLANG_UTF8;
- }
- else {
- to_enc = from_enc;
- }
- }
- switch(to_enc) {
- case ERLANG_LATIN1:
- if (buf) {
- put8(s,ERL_ATOM_EXT);
- switch (from_enc) {
- case ERLANG_UTF8:
- len = utf8_to_latin1(s+2, p, len, MAXATOMLEN-1, NULL);
- if (len < 0) return -1;
- break;
- case ERLANG_ASCII:
- if (verify_ascii_atom(p, len) < 0) return -1;
- memcpy(s+2, p, len);
- break;
- case ERLANG_LATIN1:
- memcpy(s+2, p, len);
- break;
- default:
- return -1;
- }
- put16be(s,len);
- }
- else {
- s += 3;
- if (from_enc == ERLANG_UTF8) {
- len = utf8_to_latin1(NULL, p, len, MAXATOMLEN-1, NULL);
- if (len < 0) return -1;
- } else if (from_enc == ERLANG_ASCII)
- if (verify_ascii_atom(p, len) < 0) return -1;
- }
- break;
-
- case ERLANG_UTF8:
+ /*
+ * Since OTP 20 we totally ignore 'to_enc'
+ * and alway encode as UTF8.
+ */
+ {
offs = 1 + 1;
switch (from_enc) {
case ERLANG_LATIN1:
@@ -133,10 +97,6 @@ int ei_encode_atom_len_as(char *buf, int *index, const char *p, int len,
}
}
else s+= offs;
- break;
-
- default:
- return -1;
}
s += len;
@@ -197,13 +157,3 @@ static int verify_utf8_atom(const char* src, int slen)
return 0;
}
-/* Only latin1 code points in utf8 string?
- */
-static int is_latin1_as_utf8(const char *p, int len)
-{
- int i;
- for (i=0; i<len; i++) {
- if ((unsigned char)p[i] > 0xC3) return 0;
- }
- return 1;
-}
diff --git a/lib/erl_interface/src/encode/encode_boolean.c b/lib/erl_interface/src/encode/encode_boolean.c
index 61e7e5e6e7..053029af05 100644
--- a/lib/erl_interface/src/encode/encode_boolean.c
+++ b/lib/erl_interface/src/encode/encode_boolean.c
@@ -32,12 +32,12 @@ int ei_encode_boolean(char *buf, int *index, int p)
val = p ? "true" : "false";
len = strlen(val);
- if (!buf) s += 3;
+ if (!buf) s += 2;
else {
- put8(s,ERL_ATOM_EXT);
- put16be(s,len);
+ put8(s, ERL_SMALL_ATOM_UTF8_EXT);
+ put8(s, len);
- memmove(s,val,len); /* unterminated string */
+ memcpy(s,val,len); /* unterminated string */
}
s += len;
diff --git a/lib/erl_interface/src/legacy/erl_eterm.c b/lib/erl_interface/src/legacy/erl_eterm.c
index e4b3b49c7d..5153d0f2e7 100644
--- a/lib/erl_interface/src/legacy/erl_eterm.c
+++ b/lib/erl_interface/src/legacy/erl_eterm.c
@@ -188,14 +188,20 @@ char* erl_atom_ptr_latin1(Erl_Atom_data* a)
char* erl_atom_ptr_utf8(Erl_Atom_data* a)
{
if (a->utf8 == NULL) {
- int dlen = a->lenL * 2; /* over estimation */
- a->utf8 = malloc(dlen + 1);
- a->lenU = latin1_to_utf8(a->utf8, a->latin1, a->lenL, dlen, NULL);
- a->utf8[a->lenU] = '\0';
+ erlang_char_encoding enc;
+ a->lenU = latin1_to_utf8(NULL, a->latin1, a->lenL, a->lenL*2, &enc);
+ if (enc == ERLANG_ASCII) {
+ a->utf8 = a->latin1;
+ }
+ else {
+ a->utf8 = malloc(a->lenU + 1);
+ latin1_to_utf8(a->utf8, a->latin1, a->lenL, a->lenU, NULL);
+ a->utf8[a->lenU] = '\0';
+ }
}
return a->utf8;
-
}
+
int erl_atom_size_latin1(Erl_Atom_data* a)
{
if (a->latin1 == NULL) {
diff --git a/lib/erl_interface/src/legacy/erl_marshal.c b/lib/erl_interface/src/legacy/erl_marshal.c
index 527ae0ef8f..b7a8455313 100644
--- a/lib/erl_interface/src/legacy/erl_marshal.c
+++ b/lib/erl_interface/src/legacy/erl_marshal.c
@@ -175,10 +175,9 @@ static void encode_atom(Erl_Atom_data* a, unsigned char **ext)
int ix = 0;
if (a->latin1) {
ei_encode_atom_len_as((char*)*ext, &ix, a->latin1, a->lenL,
- ERLANG_LATIN1, ERLANG_LATIN1);
+ ERLANG_LATIN1, ERLANG_UTF8);
}
- else if (ei_encode_atom_len_as((char*)*ext, &ix, a->utf8, a->lenU,
- ERLANG_UTF8, ERLANG_LATIN1) < 0) {
+ else {
ei_encode_atom_len_as((char*)*ext, &ix, a->utf8, a->lenU,
ERLANG_UTF8, ERLANG_UTF8);
}
@@ -542,12 +541,8 @@ int erl_term_len(ETERM *ep)
static int atom_len_helper(Erl_Atom_data* a)
{
- if (erl_atom_ptr_latin1(a)) {
- return 1 + 2 + a->lenL; /* ERL_ATOM_EXT */
- }
- else {
- return 1 + 1 + (a->lenU > 255) + a->lenU;
- }
+ (void) erl_atom_ptr_utf8(a);
+ return 1 + 1 + (a->lenU > 255) + a->lenU;
}
static int erl_term_len_helper(ETERM *ep, int dist)
diff --git a/lib/erl_interface/test/ei_decode_SUITE.erl b/lib/erl_interface/test/ei_decode_SUITE.erl
index 10e90685c8..8612450692 100644
--- a/lib/erl_interface/test/ei_decode_SUITE.erl
+++ b/lib/erl_interface/test/ei_decode_SUITE.erl
@@ -179,7 +179,8 @@ test_ei_decode_misc(Config) when is_list(Config) ->
send_term_as_binary(P,foo),
send_term_as_binary(P,''),
- send_term_as_binary(P,'ÅÄÖåäö'),
+ %%send_term_as_binary(P,'ÅÄÖåäö'),
+ send_latin1_atom_as_binary(P, "ÅÄÖåäö"),
send_term_as_binary(P,"foo"),
send_term_as_binary(P,""),
@@ -200,18 +201,19 @@ test_ei_decode_misc(Config) when is_list(Config) ->
test_ei_decode_utf8_atom(Config) ->
P = runner:start(?test_ei_decode_utf8_atom),
- send_utf8_atom_as_binary(P,"å"),
- send_utf8_atom_as_binary(P,"ä"),
- send_term_as_binary(P,'ö'),
- send_term_as_binary(P,'õ'),
+ send_latin1_atom_as_binary(P,"å"),
+ send_latin1_atom_as_binary(P,"ä"),
+ send_latin1_atom_as_binary(P,"ö"),
+ send_latin1_atom_as_binary(P,"õ"),
send_utf8_atom_as_binary(P,[1758]),
send_utf8_atom_as_binary(P,[1758,1758]),
send_utf8_atom_as_binary(P,[1758,1758,1758]),
send_utf8_atom_as_binary(P,[1758,1758,1758,1758]),
- send_utf8_atom_as_binary(P,"a"),
- send_utf8_atom_as_binary(P,"b"),
+ send_latin1_atom_as_binary(P,"a"),
+ send_latin1_atom_as_binary(P,"b"),
+
send_term_as_binary(P,'c'),
send_term_as_binary(P,'d'),
@@ -230,6 +232,9 @@ send_raw(Port, Bin) when is_port(Port) ->
send_utf8_atom_as_binary(Port, String) ->
Port ! {self(), {command, term_to_binary(uc_atup(String))}}.
+send_latin1_atom_as_binary(Port, String) ->
+ Port ! {self(), {command, encode_latin1_atom(String)}}.
+
send_integers(P) ->
send_term_as_binary(P,0), % SMALL_INTEGER_EXT smallest
send_term_as_binary(P,255), % SMALL_INTEGER_EXT largest
@@ -304,6 +309,12 @@ send_integers2(P) ->
send_term_as_binary(P, []), % illegal type
ok.
+encode_latin1_atom(String) ->
+ Len = length(String),
+ %% Use ATOM_EXT (not SMALL_*) to simulate old term_to_binary
+ TagLen = [$d, Len bsr 8, Len band 16#ff],
+ list_to_binary([131, TagLen, String]).
+
uc_atup(ATxt) ->
string_to_atom(ATxt).
diff --git a/lib/erl_interface/test/ei_decode_SUITE_data/ei_decode_test.c b/lib/erl_interface/test/ei_decode_SUITE_data/ei_decode_test.c
index cfe9083065..649dc9a677 100644
--- a/lib/erl_interface/test/ei_decode_SUITE_data/ei_decode_test.c
+++ b/lib/erl_interface/test/ei_decode_SUITE_data/ei_decode_test.c
@@ -102,7 +102,7 @@ int ei_decode_my_string(const char *buf, int *index, char *to,
} \
\
if (size1 != SIZE) { \
- fail("size of encoded data is incorrect"); \
+ fail1("size of encoded data (%d) is incorrect", size1); \
return; \
} \
} \
@@ -614,11 +614,11 @@ TESTCASE(test_ei_decode_misc)
EI_DECODE_2(decode_double, 9, double, -1.0);
EI_DECODE_2(decode_double, 9, double, 1.0);
- EI_DECODE_2(decode_boolean, 8, int, 0);
- EI_DECODE_2(decode_boolean, 7, int, 1);
+ EI_DECODE_2(decode_boolean, 7, int, 0);
+ EI_DECODE_2(decode_boolean, 6, int, 1);
- EI_DECODE_STRING(decode_my_atom, 6, "foo");
- EI_DECODE_STRING(decode_my_atom, 3, "");
+ EI_DECODE_STRING(decode_my_atom, 5, "foo");
+ EI_DECODE_STRING(decode_my_atom, 2, "");
EI_DECODE_STRING(decode_my_atom, 9, "������");
EI_DECODE_STRING(decode_my_string, 6, "foo");
@@ -665,10 +665,10 @@ TESTCASE(test_ei_decode_utf8_atom)
P99({ERLANG_ANY,ERLANG_LATIN1,ERLANG_ASCII}));
EI_DECODE_STRING_4(decode_my_atom_as, 4, "b",
P99({ERLANG_UTF8,ERLANG_LATIN1,ERLANG_ASCII}));
- EI_DECODE_STRING_4(decode_my_atom_as, 4, "c",
- P99({ERLANG_LATIN1,ERLANG_LATIN1,ERLANG_ASCII}));
- EI_DECODE_STRING_4(decode_my_atom_as, 4, "d",
- P99({ERLANG_ASCII,ERLANG_LATIN1,ERLANG_ASCII}));
+ EI_DECODE_STRING_4(decode_my_atom_as, 3, "c",
+ P99({ERLANG_LATIN1,ERLANG_UTF8,ERLANG_ASCII}));
+ EI_DECODE_STRING_4(decode_my_atom_as, 3, "d",
+ P99({ERLANG_ASCII,ERLANG_UTF8,ERLANG_ASCII}));
report(1);
}
diff --git a/lib/erl_interface/test/ei_decode_encode_SUITE.erl b/lib/erl_interface/test/ei_decode_encode_SUITE.erl
index 570a91e2da..108a1f5142 100644
--- a/lib/erl_interface/test/ei_decode_encode_SUITE.erl
+++ b/lib/erl_interface/test/ei_decode_encode_SUITE.erl
@@ -170,7 +170,6 @@ get_binary(P) ->
-define(VERSION_MAGIC, 131).
--define(ATOM_EXT, 100).
-define(REFERENCE_EXT, 101).
-define(PORT_EXT, 102).
-define(PID_EXT, 103).
diff --git a/lib/erl_interface/test/ei_encode_SUITE.erl b/lib/erl_interface/test/ei_encode_SUITE.erl
index ac6ec9cf4e..43484a1319 100644
--- a/lib/erl_interface/test/ei_encode_SUITE.erl
+++ b/lib/erl_interface/test/ei_encode_SUITE.erl
@@ -184,17 +184,17 @@ test_ei_encode_misc(Config) when is_list(Config) ->
{<<70,_:8/binary>>,Fp1} = get_buf_and_term(P),
true = match_float(Fp1, 1.0),
- {<<100,0,5,"false">>,false} = get_buf_and_term(P),
- {<<100,0,4,"true">> ,true} = get_buf_and_term(P),
- {<<100,0,4,"true">> ,true} = get_buf_and_term(P),
- {<<100,0,4,"true">> ,true} = get_buf_and_term(P),
-
- {<<100,0,3,"foo">>,foo} = get_buf_and_term(P),
- {<<100,0,3,"foo">>,foo} = get_buf_and_term(P),
- {<<100,0,0,"">>,''} = get_buf_and_term(P),
- {<<100,0,0,"">>,''} = get_buf_and_term(P),
- {<<100,0,6,"ÅÄÖåäö">>,'ÅÄÖåäö'} = get_buf_and_term(P),
- {<<100,0,6,"ÅÄÖåäö">>,'ÅÄÖåäö'} = get_buf_and_term(P),
+ {<<$w,5,"false">>,false} = get_buf_and_term(P),
+ {<<$w,4,"true">> ,true} = get_buf_and_term(P),
+ {<<$w,4,"true">> ,true} = get_buf_and_term(P),
+ {<<$w,4,"true">> ,true} = get_buf_and_term(P),
+
+ {<<$w,3,"foo">>,foo} = get_buf_and_term(P),
+ {<<$w,3,"foo">>,foo} = get_buf_and_term(P),
+ {<<$w,0,"">>,''} = get_buf_and_term(P),
+ {<<$w,0,"">>,''} = get_buf_and_term(P),
+ {<<$w,12,"ÅÄÖåäö"/utf8>>,'ÅÄÖåäö'} = get_buf_and_term(P),
+ {<<$w,12,"ÅÄÖåäö"/utf8>>,'ÅÄÖåäö'} = get_buf_and_term(P),
{<<107,0,3,"foo">>,"foo"} = get_buf_and_term(P),
{<<107,0,3,"foo">>,"foo"} = get_buf_and_term(P),
@@ -239,12 +239,12 @@ test_ei_encode_utf8_atom(Config) ->
P = runner:start(?test_ei_encode_utf8_atom),
{<<119,2,195,133>>,'Å'} = get_buf_and_term(P),
- {<<100,0,1,197>>,'Å'} = get_buf_and_term(P),
- {<<100,0,1,197>>,'Å'} = get_buf_and_term(P),
+ {<<119,2,195,133>>,'Å'} = get_buf_and_term(P),
+ {<<119,2,195,133>>,'Å'} = get_buf_and_term(P),
{<<119,2,195,133>>,'Å'} = get_buf_and_term(P),
{<<119,1,$A>>,'A'} = get_buf_and_term(P),
- {<<100,0,1,$A>>,'A'} = get_buf_and_term(P),
+ {<<119,1,$A>>,'A'} = get_buf_and_term(P),
runner:recv_eot(P),
ok.
@@ -254,13 +254,13 @@ test_ei_encode_utf8_atom_len(Config) ->
P = runner:start(?test_ei_encode_utf8_atom_len),
{<<119,2,195,133>>,'Å'} = get_buf_and_term(P),
- {<<100,0,2,197,196>>,'ÅÄ'} = get_buf_and_term(P),
- {<<100,0,1,197>>,'Å'} = get_buf_and_term(P),
+ {<<119,4,195,133,195,132>>,'ÅÄ'} = get_buf_and_term(P),
+ {<<119,2,195,133>>,'Å'} = get_buf_and_term(P),
{<<119,4,195,133,195,132>>,'ÅÄ'} = get_buf_and_term(P),
{<<119,1,$A>>,'A'} = get_buf_and_term(P),
- {<<100,0,2,$A,$B>>,'AB'} = get_buf_and_term(P),
- {<<100,0,255,_:(255*8)>>,_} = get_buf_and_term(P),
+ {<<119,2,$A,$B>>,'AB'} = get_buf_and_term(P),
+ {<<119,255,_:(255*8)>>,_} = get_buf_and_term(P),
runner:recv_eot(P),
ok.
diff --git a/lib/erl_interface/test/erl_ext_SUITE_data/ext_test.c b/lib/erl_interface/test/erl_ext_SUITE_data/ext_test.c
index 36cf086ed2..afac5485e8 100644
--- a/lib/erl_interface/test/erl_ext_SUITE_data/ext_test.c
+++ b/lib/erl_interface/test/erl_ext_SUITE_data/ext_test.c
@@ -407,7 +407,7 @@ test_compare_ext(char *test_desc,
}
-#define ATOM_EXT (100)
+#define SMALL_ATOM_UTF8_EXT (119)
#define REFERENCE_EXT (101)
#define PORT_EXT (102)
#define PID_EXT (103)
@@ -429,13 +429,13 @@ write_atom(unsigned char *buf, char *atom)
len = 0;
while(atom[len]) {
- buf[len + 3] = atom[len];
+ buf[len + 2] = atom[len];
len++;
}
- buf[0] = ATOM_EXT;
- PUT_UINT16(&buf[1], len);
+ buf[0] = SMALL_ATOM_UTF8_EXT;
+ buf[1] = len;
- return buf + 3 + len;
+ return buf + 2 + len;
}
static unsigned char *
diff --git a/lib/jinterface/java_src/com/ericsson/otp/erlang/OtpOutputStream.java b/lib/jinterface/java_src/com/ericsson/otp/erlang/OtpOutputStream.java
index dca2eb7c51..e1718f8380 100644
--- a/lib/jinterface/java_src/com/ericsson/otp/erlang/OtpOutputStream.java
+++ b/lib/jinterface/java_src/com/ericsson/otp/erlang/OtpOutputStream.java
@@ -403,7 +403,6 @@ public class OtpOutputStream extends ByteArrayOutputStream {
public void write_atom(final String atom) {
String enc_atom;
byte[] bytes;
- boolean isLatin1 = true;
if (atom.codePointCount(0, atom.length()) <= OtpExternal.maxAtomLength) {
enc_atom = atom;
@@ -416,29 +415,15 @@ public class OtpOutputStream extends ByteArrayOutputStream {
OtpExternal.maxAtomLength);
}
- for (int offset = 0; offset < enc_atom.length();) {
- final int cp = enc_atom.codePointAt(offset);
- if ((cp & ~0xFF) != 0) {
- isLatin1 = false;
- break;
- }
- offset += Character.charCount(cp);
- }
try {
- if (isLatin1) {
- bytes = enc_atom.getBytes("ISO-8859-1");
- write1(OtpExternal.atomTag);
- write2BE(bytes.length);
+ bytes = enc_atom.getBytes("UTF-8");
+ final int length = bytes.length;
+ if (length < 256) {
+ write1(OtpExternal.smallAtomUtf8Tag);
+ write1(length);
} else {
- bytes = enc_atom.getBytes("UTF-8");
- final int length = bytes.length;
- if (length < 256) {
- write1(OtpExternal.smallAtomUtf8Tag);
- write1(length);
- } else {
- write1(OtpExternal.atomUtf8Tag);
- write2BE(length);
- }
+ write1(OtpExternal.atomUtf8Tag);
+ write2BE(length);
}
writeN(bytes);
} catch (final java.io.UnsupportedEncodingException e) {
diff --git a/lib/jinterface/test/jinterface_SUITE_data/Maps.java b/lib/jinterface/test/jinterface_SUITE_data/Maps.java
index e8a05245da..a1b6fa73c9 100644
--- a/lib/jinterface/test/jinterface_SUITE_data/Maps.java
+++ b/lib/jinterface/test/jinterface_SUITE_data/Maps.java
@@ -40,19 +40,19 @@ class Maps {
public static void main(final String argv[]) {
runTest(new byte[] { (byte) 131, 116, 0, 0, 0, 0 }, "#{}", 1);
- runTest(new byte[] { (byte) 131, 116, 0, 0, 0, 1, 100, 0, 1, 97, 100,
- 0, 1, 98 }, "#{a => b}", 2);
+ runTest(new byte[] { (byte) 131, 116, 0, 0, 0, 1, 119, 1, 97, 119,
+ 1, 98 }, "#{a => b}", 2);
// make sure keys are sorted here, jinterface doesn't reorder them
runTest(new byte[] { (byte) 131, 116, 0, 0, 0, 2, 97, 2, 106,
- 100, 0, 1, 97, 97, 1 }, "#{2 => [],a => 1}", 3);
+ 119, 1, 97, 97, 1 }, "#{2 => [],a => 1}", 3);
runTest(new byte[] { (byte) 131, 116, 0, 0, 0, 1, 104, 1, 97, 3, 108,
- 0, 0, 0, 1, 100, 0, 1, 114, 106 }, "#{{3} => [r]}", 4);
+ 0, 0, 0, 1, 119, 1, 114, 106 }, "#{{3} => [r]}", 4);
try {
// #{2 => [],a => 1}
final OtpErlangMap map = new OtpErlangMap(new OtpInputStream(
new byte[] { (byte) 131, 116, 0, 0, 0, 2, 97, 2, 106,
- 100, 0, 1, 97, 97, 1 }));
+ 119, 1, 97, 97, 1 }));
if (map.arity() != 2) {
fail(5);
diff --git a/lib/kernel/src/dist_util.erl b/lib/kernel/src/dist_util.erl
index 8d2fc4d4b7..d929179715 100644
--- a/lib/kernel/src/dist_util.erl
+++ b/lib/kernel/src/dist_util.erl
@@ -131,7 +131,7 @@ handshake_other_started(#hs_data{request_type=ReqType}=HSData0) ->
other_version=Version,
other_node=Node,
other_started=true},
- check_dflag_xnc(HSData),
+ check_dflags(HSData),
is_allowed(HSData),
?debug({"MD5 connection from ~p (V~p)~n",
[Node, HSData#hs_data.other_version]}),
@@ -168,27 +168,24 @@ is_allowed(#hs_data{other_node = Node,
%% Check that both nodes can handle the same types of extended
%% node containers. If they can not, abort the connection.
%%
-check_dflag_xnc(#hs_data{other_node = Node,
- other_flags = OtherFlags,
- other_started = OtherStarted} = HSData) ->
- XRFlg = ?DFLAG_EXTENDED_REFERENCES,
- XPPFlg = case erlang:system_info(compat_rel) of
- R when R >= 10 ->
- ?DFLAG_EXTENDED_PIDS_PORTS;
- _ ->
- 0
- end,
- ReqXncFlags = XRFlg bor XPPFlg,
- case OtherFlags band ReqXncFlags =:= ReqXncFlags of
- true ->
- ok;
- false ->
- What = case {OtherFlags band XRFlg =:= XRFlg,
- OtherFlags band XPPFlg =:= XPPFlg} of
- {false, false} -> "references, pids and ports";
- {true, false} -> "pids and ports";
- {false, true} -> "references"
- end,
+check_dflags(#hs_data{other_node = Node,
+ other_flags = OtherFlags,
+ other_started = OtherStarted} = HSData) ->
+
+ Mandatory = [{?DFLAG_EXTENDED_REFERENCES, "EXTENDED_REFERENCES"},
+ {?DFLAG_EXTENDED_PIDS_PORTS, "EXTENDED_PIDS_PORTS"},
+ {?DFLAG_UTF8_ATOMS, "UTF8_ATOMS"}],
+ Missing = lists:filtermap(fun({Bit, Str}) ->
+ case Bit band OtherFlags of
+ Bit -> false;
+ 0 -> {true, Str}
+ end
+ end,
+ Mandatory),
+ case Missing of
+ [] ->
+ ok;
+ _ ->
case OtherStarted of
true ->
send_status(HSData, not_allowed),
@@ -199,9 +196,9 @@ check_dflag_xnc(#hs_data{other_node = Node,
How = "aborted"
end,
error_msg("** ~w: Connection attempt ~s node ~w ~s "
- "since it cannot handle extended ~s. "
- "**~n", [node(), Dir, Node, How, What]),
- ?shutdown2(Node, {check_dflag_xnc_failed, What})
+ "since it cannot handle ~p."
+ "**~n", [node(), Dir, Node, How, Missing]),
+ ?shutdown2(Node, {check_dflags_failed, Missing})
end.
@@ -327,7 +324,7 @@ handshake_we_started(#hs_data{request_type=ReqType,
NewHSData = HSData#hs_data{this_flags = ThisFlags,
other_flags = OtherFlags,
other_started = false},
- check_dflag_xnc(NewHSData),
+ check_dflags(NewHSData),
MyChallenge = gen_challenge(),
{MyCookie,HisCookie} = get_cookies(Node),
send_challenge_reply(NewHSData,MyChallenge,
diff --git a/lib/kernel/test/disk_log_SUITE.erl b/lib/kernel/test/disk_log_SUITE.erl
index 23fe975ef7..079cc2f90f 100644
--- a/lib/kernel/test/disk_log_SUITE.erl
+++ b/lib/kernel/test/disk_log_SUITE.erl
@@ -481,7 +481,7 @@ halt_ro_crash(Conf) when is_list(Conf) ->
%% This is how it was before R6B:
%% {C1,T1,15} = disk_log:chunk(a,start),
%% {C2,T2} = disk_log:chunk(a,C1),
- {C1,_OneItem,7478} = disk_log:chunk(a,start),
+ {C1,_OneItem,7476} = disk_log:chunk(a,start),
{C2, [], 7} = disk_log:chunk(a,C1),
eof = disk_log:chunk(a,C2),
ok = disk_log:close(a),
@@ -2502,8 +2502,8 @@ error_repair(Conf) when is_list(Conf) ->
ok = disk_log:close(n),
BadFile = add_ext(File, 2), % current file
set_opened(BadFile),
- crash(BadFile, 28), % the binary is now invalid
- {repaired,n,{recovered,0},{badbytes,26}} =
+ crash(BadFile, 26), % the binary is now invalid
+ {repaired,n,{recovered,0},{badbytes,24}} =
disk_log:open([{name, n}, {file, File}, {type, wrap},
{format, internal}, {size, {40,No}}]),
ok = disk_log:close(n),
@@ -2518,8 +2518,8 @@ error_repair(Conf) when is_list(Conf) ->
ok = disk_log:close(n),
BadFile2 = add_ext(File, 1), % current file
set_opened(BadFile2),
- crash(BadFile2, 51), % the second binary is now invalid
- {repaired,n,{recovered,1},{badbytes,26}} =
+ crash(BadFile2, 47), % the second binary is now invalid
+ {repaired,n,{recovered,1},{badbytes,24}} =
disk_log:open([{name, n}, {file, File}, {type, wrap},
{format, internal}, {size, {4000,No}}]),
ok = disk_log:close(n),
@@ -2571,7 +2571,7 @@ error_repair(Conf) when is_list(Conf) ->
ok = disk_log:close(n),
set_opened(File),
crash(File, 30),
- {repaired,n,{recovered,3},{badbytes,16}} =
+ {repaired,n,{recovered,3},{badbytes,15}} =
disk_log:open([{name, n}, {file, File}, {type, halt},
{format, internal},{repair,true},
{head_func, {?MODULE, head_fun, [{ok,"head"}]}}]),
@@ -2797,7 +2797,7 @@ chunk(Conf) when is_list(Conf) ->
ok = disk_log:log_terms(n, [{some,terms}]), % second file full
2 = curf(n),
BadFile = add_ext(File, 1),
- crash(BadFile, 28), % the _binary_ is now invalid
+ crash(BadFile, 26), % the _binary_ is now invalid
{error, {corrupt_log_file, BFile}} = disk_log:chunk(n, start, 1),
BadFile = BFile,
ok = disk_log:close(n),
@@ -2807,7 +2807,7 @@ chunk(Conf) when is_list(Conf) ->
{format, internal}]),
ok = disk_log:log_terms(n, [{this,is}]),
ok = disk_log:sync(n),
- crash(File, 28), % the _binary_ is now invalid
+ crash(File, 26), % the _binary_ is now invalid
{error, {corrupt_log_file, File2}} = disk_log:chunk(n, start, 1),
crash(File, 10),
{error,{corrupt_log_file,_}} = disk_log:bchunk(n, start, 1),
@@ -2901,8 +2901,8 @@ chunk(Conf) when is_list(Conf) ->
{ok, n} = disk_log:open([{name, n}, {file, File}, {type, wrap},
{format, internal}, {mode, read_only}]),
CrashFile = add_ext(File, 1),
- crash(CrashFile, 51), % the binary term {some,terms} is now bad
- {H1, [{this,is}], 18} = disk_log:chunk(n, start, 10),
+ crash(CrashFile, 46), % the binary term {some,terms} is now bad
+ {H1, [{this,is}], 16} = disk_log:chunk(n, start, 10),
{H2, [{on,a},{wrap,file}]} = disk_log:chunk(n, H1),
eof = disk_log:chunk(n, H2),
ok = disk_log:close(n),
@@ -2916,8 +2916,8 @@ chunk(Conf) when is_list(Conf) ->
ok = disk_log:close(n),
{ok, n} = disk_log:open([{name, n}, {file, File}, {type, halt},
{format, internal}, {mode, read_only}]),
- crash(File, 51), % the binary term {some,terms} is now bad
- {J1, [{this,is}], 18} = disk_log:chunk(n, start, 10),
+ crash(File, 46), % the binary term {some,terms} is now bad
+ {J1, [{this,is}], 16} = disk_log:chunk(n, start, 10),
{J2, [{on,a},{halt,file}]} = disk_log:chunk(n, J1),
eof = disk_log:chunk(n, J2),
ok = disk_log:close(n),
@@ -2932,8 +2932,8 @@ chunk(Conf) when is_list(Conf) ->
ok = disk_log:close(n),
{ok, n} = disk_log:open([{name, n}, {file, File}, {type, halt},
{format, internal}, {mode, read_only}]),
- crash(File, 44), % the binary term {s} is now bad
- {J11, [{this,is}], 7} = disk_log:chunk(n, start, 10),
+ crash(File, 40), % the binary term {s} is now bad
+ {J11, [{this,is}], 6} = disk_log:chunk(n, start, 10),
{J21, [{on,a},{halt,file}]} = disk_log:chunk(n, J11),
eof = disk_log:chunk(n, J21),
ok = disk_log:close(n),
@@ -3052,7 +3052,7 @@ truncate(Conf) when is_list(Conf) ->
ok = disk_log:truncate(n, apa),
rec(1, {disk_log, node(), n, {truncated, 6}}),
{0, 0} = no_overflows(n),
- 23 = curb(n),
+ 22 = curb(n),
1 = curf(n),
1 = cur_cnt(n),
true = (Size == sz(n)),
@@ -3072,7 +3072,7 @@ truncate(Conf) when is_list(Conf) ->
ok = disk_log:truncate(n, apa),
rec(1, {disk_log, node(), n, {truncated, 3}}),
{0, 0} = no_overflows(n),
- 23 = curb(n),
+ 22 = curb(n),
1 = curf(n),
1 = cur_cnt(n),
true = (Size == sz(n)),
@@ -3181,45 +3181,45 @@ info_current(Conf) when is_list(Conf) ->
%% Internal with header.
{ok, n} = disk_log:open([{name, n}, {file, File}, {type, wrap},
{head, header}, {size, {100,No}}]),
- {26, 1} = {curb(n), cur_cnt(n)},
+ {25, 1} = {curb(n), cur_cnt(n)},
{1, 1} = {no_written_items(n), no_items(n)},
ok = disk_log:log(n, B),
- {94, 2} = {curb(n), cur_cnt(n)},
+ {93, 2} = {curb(n), cur_cnt(n)},
{2, 2} = {no_written_items(n), no_items(n)},
ok = disk_log:close(n),
{ok, n} = disk_log:open([{name, n}, {file, File}, {type, wrap},
{notify, true},
{head, header}, {size, {100,No}}]),
- {94, 2} = {curb(n), cur_cnt(n)},
+ {93, 2} = {curb(n), cur_cnt(n)},
{0, 2} = {no_written_items(n), no_items(n)},
ok = disk_log:log(n, B),
rec(1, {disk_log, node(), n, {wrap, 0}}),
- {94, 2} = {curb(n), cur_cnt(n)},
+ {93, 2} = {curb(n), cur_cnt(n)},
{2, 4} = {no_written_items(n), no_items(n)},
disk_log:inc_wrap_file(n),
rec(1, {disk_log, node(), n, {wrap, 0}}),
- {26, 1} = {curb(n), cur_cnt(n)},
+ {25, 1} = {curb(n), cur_cnt(n)},
{3, 4} = {no_written_items(n), no_items(n)},
ok = disk_log:log_terms(n, [B,B,B]),
%% Used to be one message, but now one per wrapped file.
rec(1, {disk_log, node(), n, {wrap, 0}}),
rec(1, {disk_log, node(), n, {wrap, 2}}),
- {94, 2} = {curb(n), cur_cnt(n)},
+ {93, 2} = {curb(n), cur_cnt(n)},
{8, 7} = {no_written_items(n), no_items(n)},
ok = disk_log:log_terms(n, [B]),
rec(1, {disk_log, node(), n, {wrap, 2}}),
ok = disk_log:log_terms(n, [B]),
rec(1, {disk_log, node(), n, {wrap, 2}}),
- {94, 2} = {curb(n), cur_cnt(n)},
+ {93, 2} = {curb(n), cur_cnt(n)},
{12, 7} = {no_written_items(n), no_items(n)},
ok = disk_log:log_terms(n, [BB,BB]),
%% Used to be one message, but now one per wrapped file.
rec(2, {disk_log, node(), n, {wrap, 2}}),
- {194, 2} = {curb(n), cur_cnt(n)},
+ {193, 2} = {curb(n), cur_cnt(n)},
{16, 7} = {no_written_items(n), no_items(n)},
ok = disk_log:log_terms(n, [SB,SB,SB]),
rec(1, {disk_log, node(), n, {wrap, 2}}),
- {80, 4} = {curb(n), cur_cnt(n)},
+ {79, 4} = {curb(n), cur_cnt(n)},
{20, 9} = {no_written_items(n), no_items(n)},
ok = disk_log:close(n),
del(File, No),
diff --git a/lib/kernel/test/erl_distribution_wb_SUITE.erl b/lib/kernel/test/erl_distribution_wb_SUITE.erl
index 61aa3b32ee..c1dc208cc1 100644
--- a/lib/kernel/test/erl_distribution_wb_SUITE.erl
+++ b/lib/kernel/test/erl_distribution_wb_SUITE.erl
@@ -56,10 +56,14 @@
-define(DFLAG_HIDDEN_ATOM_CACHE,16#40).
-define(DFLAG_NEW_FUN_TAGS,16#80).
-define(DFLAG_EXTENDED_PIDS_PORTS,16#100).
+-define(DFLAG_UTF8_ATOMS, 16#10000).
%% From R9 and forward extended references is compulsory
%% From R10 and forward extended pids and ports are compulsory
--define(COMPULSORY_DFLAGS, (?DFLAG_EXTENDED_REFERENCES bor ?DFLAG_EXTENDED_PIDS_PORTS)).
+%% From R20 and forward UTF8 atoms are compulsory
+-define(COMPULSORY_DFLAGS, (?DFLAG_EXTENDED_REFERENCES bor
+ ?DFLAG_EXTENDED_PIDS_PORTS bor
+ ?DFLAG_UTF8_ATOMS)).
-define(shutdown(X), exit(X)).
diff --git a/lib/kernel/test/pg2_SUITE.erl b/lib/kernel/test/pg2_SUITE.erl
index fdc268cb5a..9460608a3e 100644
--- a/lib/kernel/test/pg2_SUITE.erl
+++ b/lib/kernel/test/pg2_SUITE.erl
@@ -31,7 +31,7 @@
-export([
otp_7277/1, otp_8259/1, otp_8653/1,
- compat/1, basic/1]).
+ basic/1]).
-define(TESTCASE, testcase_name).
-define(testcase, proplists:get_value(?TESTCASE, Config)).
@@ -56,7 +56,7 @@ all() ->
groups() ->
[{tickets, [],
- [otp_7277, otp_8259, otp_8653, compat, basic]}].
+ [otp_7277, otp_8259, otp_8653, basic]}].
init_per_suite(Config) ->
Config.
@@ -218,29 +218,6 @@ loop() ->
exit(normal)
end.
-%% OTP-8259. Check that 'exchange' and 'del_member' work.
-compat(Config) when is_list(Config) ->
- case test_server:is_release_available("r13b") of
- true ->
- Pid = spawn(forever()),
- G = a,
- ok = pg2:create(G),
- ok = pg2:join(G, Pid),
- ok = pg2:join(G, Pid),
- {ok, A} = start_node_rel(r13, r13b, slave),
- pong = net_adm:ping(A),
- wait_for_ready_net(Config),
- {ok, _} = rpc:call(A, pg2, start, []),
- ?UNTIL([Pid,Pid] =:= rpc:call(A, pg2, get_members, [a])),
- true = exit(Pid, kill),
- ?UNTIL([] =:= pg2:get_members(a)),
- ?UNTIL([] =:= rpc:call(A, pg2, get_members, [a])),
- test_server:stop_node(A),
- ok;
- false ->
- {skipped, "No support for old node"}
- end.
-
%% OTP-8259. Some basic tests.
basic(Config) when is_list(Config) ->
_ = [pg2:delete(G) || G <- pg2:which_groups()],
diff --git a/lib/orber/COSS/CosNaming/CosNaming_NamingContextExt_impl.erl b/lib/orber/COSS/CosNaming/CosNaming_NamingContextExt_impl.erl
index 8f7da2425b..620c91d406 100644
--- a/lib/orber/COSS/CosNaming/CosNaming_NamingContextExt_impl.erl
+++ b/lib/orber/COSS/CosNaming/CosNaming_NamingContextExt_impl.erl
@@ -610,11 +610,16 @@ convert_list([{N, T, _O}|Rest], HowMany, Counter, Acc) ->
%% Returns :
%%----------------------------------------------------------------------
destroy(OE_THIS, OE_State) ->
- case corba:get_subobject_key(OE_THIS) of
- <<131,100,0,9,117,110,100,101,102,105,110,101,100>> ->
- %% undefined binary.
- corba:raise(#'NO_PERMISSION'{completion_status=?COMPLETED_NO});
- SubobjKey ->
+ SubobjKey = corba:get_subobject_key(OE_THIS),
+ try begin
+ true = (byte_size(SubobjKey) < 20),
+ undefined = binary_to_term(SubobjKey)
+ end
+ of
+ _ ->
+ corba:raise(#'NO_PERMISSION'{completion_status=?COMPLETED_NO})
+ catch
+ error:_ -> %% Not atom 'undefined', carry on...
_DF =
fun() ->
case mnesia:wread({orber_CosNaming, SubobjKey}) of
diff --git a/lib/stdlib/test/beam_lib_SUITE.erl b/lib/stdlib/test/beam_lib_SUITE.erl
index 279e15f703..1baf7d0a94 100644
--- a/lib/stdlib/test/beam_lib_SUITE.erl
+++ b/lib/stdlib/test/beam_lib_SUITE.erl
@@ -240,7 +240,7 @@ do_error(BeamFile, ACopy) ->
verify(missing_chunk, beam_lib:chunks(BF3, [imports])),
BF4 = set_byte(ACopy, BeamFile, AbstractStart+10, 17),
verify(invalid_chunk, beam_lib:chunks(BF4, [abstract_code])),
- BF5 = set_byte(ACopy, BeamFile, AttributesStart+10, 17),
+ BF5 = set_byte(ACopy, BeamFile, AttributesStart+8, 17),
verify(invalid_chunk, beam_lib:chunks(BF5, [attributes])),
BF6 = set_byte(ACopy, BeamFile, 1, 17),
@@ -251,7 +251,7 @@ do_error(BeamFile, ACopy) ->
BF8 = set_byte(ACopy, BeamFile, 13, 17),
verify(missing_chunk, beam_lib:chunks(BF8, ["AtU8"])),
- BF9 = set_byte(ACopy, BeamFile, CompileInfoStart+10, 17),
+ BF9 = set_byte(ACopy, BeamFile, CompileInfoStart+8, 17),
verify(invalid_chunk, beam_lib:chunks(BF9, [compile_info])).
diff --git a/lib/stdlib/test/io_proto_SUITE.erl b/lib/stdlib/test/io_proto_SUITE.erl
index db321d7490..4cc4e3292c 100644
--- a/lib/stdlib/test/io_proto_SUITE.erl
+++ b/lib/stdlib/test/io_proto_SUITE.erl
@@ -26,15 +26,14 @@
-export([init_per_testcase/2, end_per_testcase/2]).
-export([setopts_getopts/1,unicode_options/1,unicode_options_gen/1,
- binary_options/1, bc_with_r12/1,
- bc_with_r12_gl/1, read_modes_gl/1,bc_with_r12_ogl/1,
+ binary_options/1, read_modes_gl/1,
read_modes_ogl/1, broken_unicode/1,eof_on_pipe/1,unicode_prompt/1]).
-export([io_server_proxy/1,start_io_server_proxy/0, proxy_getall/1,
proxy_setnext/2, proxy_quit/1]).
%% For spawn
--export([toerl_server/3,hold_the_line/3,answering_machine1/3,
+-export([toerl_server/3,answering_machine1/3,
answering_machine2/3]).
-export([uprompt/1]).
@@ -79,8 +78,7 @@ suite() ->
all() ->
[setopts_getopts, unicode_options, unicode_options_gen,
- binary_options, bc_with_r12, bc_with_r12_gl,
- bc_with_r12_ogl, read_modes_gl, read_modes_ogl,
+ binary_options, read_modes_gl, read_modes_ogl,
broken_unicode, eof_on_pipe, unicode_prompt].
groups() ->
@@ -742,263 +740,7 @@ binary_options(Config) when is_list(Config) ->
],[],[],"-oldshell"),
ok.
-%% Test io protocol compatibility with R12 nodes.
-bc_with_r12(Config) when is_list(Config) ->
- case test_server:is_release_available("r12b") of
- true -> bc_with_r12_1(Config);
- false -> {skip,"No R12B found"}
- end.
-
-bc_with_r12_1(Config) ->
- PA = filename:dirname(code:which(?MODULE)),
- Name1 = io_proto_r12_1,
- N1 = list_to_atom(atom_to_list(Name1) ++ "@" ++ hostname()),
- test_server:start_node(Name1, peer, [{args, "-pz \""++PA++"\""},
- {erl,[{release,"r12b"}]}]),
- DataDir = proplists:get_value(data_dir,Config),
- FileName1 = filename:join([DataDir,"testdata_latin1.dat"]),
- TestDataLine1 = [229,228,246],
- TestDataLine2 = [197,196,214],
- SPid1 = rpc:call(N1,erlang,spawn,[?MODULE,hold_the_line,[self(),FileName1,[read]]]),
- {ok,F1} = receive
- {SPid1,Res1} ->
- Res1
- after 5000 ->
- exit(timeout)
- end,
- TestDataLine1 = chomp(io:get_line(F1,'')),
- SPid1 ! die,
- receive after 1000 -> ok end,
- SPid2 = rpc:call(N1,erlang,spawn,[?MODULE,hold_the_line,[self(),FileName1,[read,binary]]]),
- {ok,F2} = receive
- {SPid2,Res2} ->
- Res2
- after 5000 ->
- exit(timeout)
- end,
- TestDataLine1BinUtf = unicode:characters_to_binary(TestDataLine1),
- TestDataLine1BinLatin = list_to_binary(TestDataLine1),
- TestDataLine2BinUtf = unicode:characters_to_binary(TestDataLine2),
- TestDataLine2BinLatin = list_to_binary(TestDataLine2),
- TestDataLine1BinUtf = chomp(io:get_line(F2,'')),
- TestDataLine2BinUtf = chomp(io:get_line(F2,'')),
- %%io:format(standard_error,"Exec:~s\r\n",[rpc:call(N1,os,find_executable,["erl"])]),
- %%io:format(standard_error,"Io:~s\r\n",[rpc:call(N1,code,which,[io])]),
- %%io:format(standard_error,"File_io_server:~s\r\n",[rpc:call(N1,code,which,[file_io_server])]),
- file:position(F2,0),
- TestDataLine1BinLatin = chomp(rpc:call(N1,io,get_line,[F2,''])),
- TestDataLine2BinUtf = chomp(io:get_line(F2,'')),
- file:position(F2,0),
- TestDataLine1BinUtf = chomp(io:get_line(F2,'')),
- TestDataLine2BinLatin = chomp(rpc:call(N1,io,get_line,[F2,''])),
- eof = chomp(rpc:call(N1,io,get_line,[F2,''])),
- file:position(F2,0),
- TestDataLine1BinLatin = rpc:call(N1,io,get_chars,[F2,'',3]),
- io:get_chars(F2,'',1),
- TestDataLine2BinLatin = chomp(rpc:call(N1,io,get_line,[F2,''])),
- file:position(F2,0),
- {ok,[TestDataLine1]} = io:fread(F2,'',"~s"),
- {ok,[TestDataLine2]} = rpc:call(N1,io,fread,[F2,'',"~s"]),
-
- DataLen1 = length(TestDataLine1),
- DataLen2 = length(TestDataLine2),
- file:position(F2,0),
- {ok,TestDataLine1BinLatin} = file:read(F2,DataLen1),
- {ok,_} = file:read(F2,1),
- {ok,TestDataLine2BinLatin} = rpc:call(N1,file,read,[F2,DataLen2]),
- {ok,_} = file:read(F2,1),
- eof = rpc:call(N1,file,read,[F2,1]),
- %% As r12 has a bug when setting options with setopts, we need
- %% to reopen the file...
- SPid2 ! die,
- receive after 1000 -> ok end,
- SPid3 = rpc:call(N1,erlang,spawn,[?MODULE,hold_the_line,[self(),FileName1,[read]]]),
- {ok,F3} = receive
- {SPid3,Res3} ->
- Res3
- after 5000 ->
- exit(timeout)
- end,
-
- file:position(F3,0),
- {ok,[TestDataLine1]} = io:fread(F3,'',"~s"),
- {ok,[TestDataLine2]} = rpc:call(N1,io,fread,[F3,'',"~s"]),
-
-
- file:position(F3,0),
- {ok,TestDataLine1} = file:read(F3,DataLen1),
- {ok,_} = file:read(F3,1),
- {ok,TestDataLine2} = rpc:call(N1,file,read,[F3,DataLen2]),
- {ok,_} = file:read(F3,1),
- eof = rpc:call(N1,file,read,[F3,1]),
-
-
- %% So, lets do it all again, but the other way around
- {ok,F4} = file:open(FileName1,[read]),
- TestDataLine1 = chomp(io:get_line(F4,'')),
- file:position(F4,0),
- io:setopts(F4,[binary]),
- TestDataLine1BinUtf = chomp(io:get_line(F4,'')),
- TestDataLine2BinUtf = chomp(io:get_line(F4,'')),
- file:position(F4,0),
- TestDataLine1BinUtf = chomp(io:get_line(F4,'')),
- TestDataLine2BinUtf = chomp(io:get_line(F4,'')),
- file:position(F4,0),
- TestDataLine1BinUtf = chomp(io:get_line(F4,'')),
- TestDataLine2BinLatin = chomp(rpc:call(N1,io,get_line,[F4,''])),
- file:position(F4,0),
- TestDataLine1BinLatin = chomp(rpc:call(N1,io,get_line,[F4,''])),
- TestDataLine2BinUtf = chomp(io:get_line(F4,'')),
- eof = chomp(rpc:call(N1,io,get_line,[F4,''])),
- file:position(F4,0),
- TestDataLine1BinLatin = rpc:call(N1,io,get_chars,[F4,'',3]),
- io:get_chars(F4,'',1),
- TestDataLine2BinLatin = chomp(rpc:call(N1,io,get_line,[F4,''])),
- file:position(F4,0),
- {ok,[TestDataLine1]} = io:fread(F4,'',"~s"),
- {ok,[TestDataLine2]} = rpc:call(N1,io,fread,[F4,'',"~s"]),
- file:position(F4,0),
- {ok,TestDataLine1BinLatin} = file:read(F4,DataLen1),
- {ok,_} = file:read(F4,1),
- {ok,TestDataLine2BinLatin} = rpc:call(N1,file,read,[F4,DataLen2]),
- {ok,_} = file:read(F4,1),
- eof = rpc:call(N1,file,read,[F4,1]),
- io:setopts(F4,[list]),
-
- file:position(F4,0),
- {ok,[TestDataLine1]} = io:fread(F4,'',"~s"),
- {ok,[TestDataLine2]} = rpc:call(N1,io,fread,[F4,'',"~s"]),
-
-
- file:position(F4,0),
- {ok,TestDataLine1} = file:read(F4,DataLen1),
- {ok,_} = file:read(F4,1),
- {ok,TestDataLine2} = rpc:call(N1,file,read,[F4,DataLen2]),
- {ok,_} = file:read(F4,1),
- eof = rpc:call(N1,file,read,[F4,1]),
-
- file:close(F4),
- test_server:stop_node(N1),
- ok.
-
-hold_the_line(Parent,Filename,Options) ->
- Parent ! {self(), file:open(Filename,Options)},
- receive
- die ->
- ok
- end.
-
-
-%% Test io protocol compatibility with R12 nodes (terminals).
-bc_with_r12_gl(Config) when is_list(Config) ->
- case test_server:is_release_available("r12b") of
- true ->
- case get_progs() of
- {error,Reason} ->
- {skip, Reason};
- _ ->
- bc_with_r12_gl_1(Config,answering_machine1)
- end;
- false ->
- {skip,"No R12B found"}
- end.
-
-%% Test io protocol compatibility with R12 nodes (oldshell).
-bc_with_r12_ogl(Config) when is_list(Config) ->
- case test_server:is_release_available("r12b") of
- true ->
- case get_progs() of
- {error,Reason} ->
- {skip, Reason};
- _ ->
- bc_with_r12_gl_1(Config,answering_machine2)
- end;
- false ->
- {skip,"No R12B found"}
- end.
-
-bc_with_r12_gl_1(_Config,Machine) ->
- PA = filename:dirname(code:which(?MODULE)),
- Name1 = io_proto_r12_gl_1,
- N1 = list_to_atom(atom_to_list(Name1) ++ "@" ++ hostname()),
- test_server:start_node(Name1, peer, [{args, "-pz \""++PA++"\""},
- {erl,[{release,"r12b"}]}]),
- TestDataLine1 = [229,228,246],
- TestDataLine1BinUtf = unicode:characters_to_binary(TestDataLine1),
- TestDataLine1BinLatin = list_to_binary(TestDataLine1),
-
- {ok,N2List} = create_nodename(),
- MyNodeList = atom2list(node()),
- register(io_proto_suite,self()),
- AM1 = spawn(?MODULE,Machine,
- [MyNodeList, "io_proto_suite", N2List]),
-
- GL = receive X when is_pid(X) -> X end,
- %% get_line
- "Hej\n" = rpc:call(N1,io,get_line,[GL,"Prompt\n"]),
- io:setopts(GL,[binary]),
- io:format(GL,"Okej~n",[]),
- <<"Hej\n">> = rpc:call(N1,io,get_line,[GL,"Prompt\n"]),
- io:setopts(GL,[{encoding,latin1}]),
- io:format(GL,"Okej~n",[]),
- TestDataLine1BinLatin = chomp(rpc:call(N1,io,get_line,[GL,"Prompt\n"])),
- io:format(GL,"Okej~n",[]),
- TestDataLine1BinUtf = chomp(io:get_line(GL,"Prompt\n")),
- io:setopts(GL,[{encoding,unicode}]),
-
- io:format(GL,"Okej~n",[]),
- TestDataLine1BinLatin = chomp(rpc:call(N1,io,get_line,[GL,"Prompt\n"])),
- io:format(GL,"Okej~n",[]),
- TestDataLine1BinUtf = chomp(io:get_line(GL,"Prompt\n")),
- io:setopts(GL,[list]),
- io:format(GL,"Okej~n",[]),
-
- %%get_chars
- "Hej" = rpc:call(N1,io,get_chars,[GL,"Prompt\n",3]),
- io:setopts(GL,[binary]),
- io:format(GL,"Okej~n",[]),
- <<"Hej">> = rpc:call(N1,io,get_chars,[GL,"Prompt\n",3]),
- io:setopts(GL,[{encoding,latin1}]),
- io:format(GL,"Okej~n",[]),
- TestDataLine1BinLatin = rpc:call(N1,io,get_chars,[GL,"Prompt\n",3]),
- io:format(GL,"Okej~n",[]),
- TestDataLine1BinUtf = io:get_chars(GL,"Prompt\n",3),
- io:setopts(GL,[{encoding,unicode}]),
-
- io:format(GL,"Okej~n",[]),
- TestDataLine1BinLatin = rpc:call(N1,io,get_chars,[GL,"Prompt\n",3]),
- io:format(GL,"Okej~n",[]),
- TestDataLine1BinUtf = io:get_chars(GL,"Prompt\n",3),
- io:setopts(GL,[list]),
- io:format(GL,"Okej~n",[]),
- %%fread
- {ok,["Hej"]} = rpc:call(N1,io,fread,[GL,"Prompt\n","~s"]),
- io:setopts(GL,[binary]),
- io:format(GL,"Okej~n",[]),
- {ok,["Hej"]} = rpc:call(N1,io,fread,[GL,"Prompt\n","~s"]),
- io:setopts(GL,[{encoding,latin1}]),
- io:format(GL,"Okej~n",[]),
- {ok,[TestDataLine1]} = rpc:call(N1,io,fread,[GL,"Prompt\n","~s"]),
- io:format(GL,"Okej~n",[]),
- {ok,[TestDataLine1]} = io:fread(GL,"Prompt\n","~s"),
- io:setopts(GL,[{encoding,unicode}]),
- io:format(GL,"Okej~n",[]),
- {ok,[TestDataLine1]} = rpc:call(N1,io,fread,[GL,"Prompt\n","~s"]),
- io:format(GL,"Okej~n",[]),
- {ok,[TestDataLine1]} = io:fread(GL,"Prompt\n","~s"),
- io:setopts(GL,[list]),
- io:format(GL,"Okej~n",[]),
-
-
- receive
- {AM1,done} ->
- ok
- after 5000 ->
- exit(timeout)
- end,
- test_server:stop_node(N1),
- ok.
answering_machine1(OthNode,OthReg,Me) ->
@@ -1900,13 +1642,6 @@ convert(Data, latin1, binary) ->
{error, {cannot_convert, unicode, latin1}}
end.
-hostname() ->
- from($@, atom_to_list(node())).
-
-from(H, [H | T]) -> T;
-from(H, [_ | T]) -> from(H, T);
-from(_, []) -> [].
-
atom2list(A) ->
lists:flatten(io_lib:format("~w", [A])).
diff --git a/lib/tools/src/lcnt.erl b/lib/tools/src/lcnt.erl
index 23d66b084e..22db947e7a 100644
--- a/lib/tools/src/lcnt.erl
+++ b/lib/tools/src/lcnt.erl
@@ -932,16 +932,31 @@ strings([{space, N, S} | Ss], Out) -> strings(Ss, Out ++ term2string(term2
strings([{left, N, S} | Ss], Out) -> strings(Ss, Out ++ term2string(term2string(" ~~s~~~ws", [N]), [S,""]));
strings([S|Ss], Out) -> strings(Ss, Out ++ term2string("~ts", [S])).
+-define(SMALL_ATOM_UTF8_EXT, $w).
+-define(ATOM_UTF8_EXT, $v).
+-define(ATOM_EXT, $d).
term2string({M,F,A}) when is_atom(M), is_atom(F), is_integer(A) -> term2string("~p:~p/~p", [M,F,A]);
term2string(Term) when is_port(Term) ->
% ex #Port<6442.816>
- <<_:3/binary, L:16, Node:L/binary, Ids:32, _/binary>> = term_to_binary(Term),
- term2string("#Port<~s.~w>", [Node, Ids]);
+ case term_to_binary(Term) of
+ <<_:2/binary, ?SMALL_ATOM_UTF8_EXT, L:8, Node:L/binary, Ids:32, _/binary>> ->
+ term2string("#Port<~ts.~w>", [Node, Ids]);
+ <<_:2/binary, ?ATOM_UTF8_EXT, L:16, Node:L/binary, Ids:32, _/binary>> ->
+ term2string("#Port<~ts.~w>", [Node, Ids]);
+ <<_:2/binary, ?ATOM_EXT, L:16, Node:L/binary, Ids:32, _/binary>> ->
+ term2string("#Port<~s.~w>", [Node, Ids])
+ end;
term2string(Term) when is_pid(Term) ->
% ex <0.80.0>
- <<_:3/binary, L:16, Node:L/binary, Ids:32, Serial:32, _/binary>> = term_to_binary(Term),
- term2string("<~s.~w.~w>", [Node, Ids, Serial]);
+ case term_to_binary(Term) of
+ <<_:2/binary, ?SMALL_ATOM_UTF8_EXT, L:8, Node:L/binary, Ids:32, Serial:32, _/binary>> ->
+ term2string("<~ts.~w.~w>", [Node, Ids, Serial]);
+ <<_:2/binary, ?ATOM_UTF8_EXT, L:16, Node:L/binary, Ids:32, Serial:32, _/binary>> ->
+ term2string("<~ts.~w.~w>", [Node, Ids, Serial]);
+ <<_:2/binary, ?ATOM_EXT, L:16, Node:L/binary, Ids:32, Serial:32, _/binary>> ->
+ term2string("<~s.~w.~w>", [Node, Ids, Serial])
+ end;
term2string(Term) -> term2string("~w", [Term]).
term2string(Format, Terms) -> lists:flatten(io_lib:format(Format, Terms)).