diff options
Diffstat (limited to 'erts/emulator/beam')
-rw-r--r-- | erts/emulator/beam/atom.names | 1 | ||||
-rw-r--r-- | erts/emulator/beam/beam_load.c | 5 | ||||
-rw-r--r-- | erts/emulator/beam/bif.c | 17 | ||||
-rw-r--r-- | erts/emulator/beam/bif.tab | 1 | ||||
-rw-r--r-- | erts/emulator/beam/erl_alloc_util.c | 10 | ||||
-rwxr-xr-x | erts/emulator/beam/erl_bif_info.c | 4 | ||||
-rw-r--r-- | erts/emulator/beam/erl_init.c | 53 | ||||
-rw-r--r-- | erts/emulator/beam/erl_unicode.c | 63 | ||||
-rw-r--r-- | erts/emulator/beam/ops.tab | 2 | ||||
-rw-r--r-- | erts/emulator/beam/packet_parser.c | 2 | ||||
-rw-r--r-- | erts/emulator/beam/sys.h | 14 |
11 files changed, 148 insertions, 24 deletions
diff --git a/erts/emulator/beam/atom.names b/erts/emulator/beam/atom.names index f138324e1f..ce60bb9bbc 100644 --- a/erts/emulator/beam/atom.names +++ b/erts/emulator/beam/atom.names @@ -269,6 +269,7 @@ atom hipe_architecture atom http httph https http_response http_request http_header http_eoh http_error http_bin httph_bin atom id atom if_clause +atom ignore atom imports atom in atom in_exiting diff --git a/erts/emulator/beam/beam_load.c b/erts/emulator/beam/beam_load.c index f57fa2bfbb..81c1ea749a 100644 --- a/erts/emulator/beam/beam_load.c +++ b/erts/emulator/beam/beam_load.c @@ -1853,7 +1853,10 @@ load_code(LoaderState* stp) unsigned tag; switch (last_op->a[arg].val) { - case 0: /* Floating point number */ + case 0: + /* Floating point number. + * Not generated by the compiler in R16B and later. + */ { Eterm* hp; /* XXX:PaN - Halfword should use ARCH_64 variant instead */ diff --git a/erts/emulator/beam/bif.c b/erts/emulator/beam/bif.c index 46f76624a5..df084e1185 100644 --- a/erts/emulator/beam/bif.c +++ b/erts/emulator/beam/bif.c @@ -2963,15 +2963,14 @@ BIF_RETTYPE float_to_list_2(BIF_ALIST_2) Eterm* tp = tuple_val(arg); if (*tp == arity_two && is_small(tp[2])) { decimals = signed_val(tp[2]); - if (decimals > 0 && decimals < sizeof(fbuf) - 6 /* "X." ++ "e+YY" */) - switch (tp[1]) { - case am_decimals: - fmt_type = FMT_FIXED; - continue; - case am_scientific: - fmt_type = FMT_SCIENTIFIC; - continue; - } + switch (tp[1]) { + case am_decimals: + fmt_type = FMT_FIXED; + continue; + case am_scientific: + fmt_type = FMT_SCIENTIFIC; + continue; + } } } goto badarg; diff --git a/erts/emulator/beam/bif.tab b/erts/emulator/beam/bif.tab index 4aaf466008..e313188901 100644 --- a/erts/emulator/beam/bif.tab +++ b/erts/emulator/beam/bif.tab @@ -522,6 +522,7 @@ bif erlang:nif_error/2 bif prim_file:internal_name2native/1 bif prim_file:internal_native2name/1 bif prim_file:internal_normalize_utf8/1 +bif prim_file:is_translatable/1 bif file:native_name_encoding/0 # diff --git a/erts/emulator/beam/erl_alloc_util.c b/erts/emulator/beam/erl_alloc_util.c index 187bc2b48b..ac7f420708 100644 --- a/erts/emulator/beam/erl_alloc_util.c +++ b/erts/emulator/beam/erl_alloc_util.c @@ -643,9 +643,9 @@ alcu_mseg_realloc(Allctr_t *allctr, void *seg, Uint old_size, Uint *new_size_p) } static ERTS_INLINE void -alcu_mseg_dealloc(Allctr_t *allctr, void *seg, Uint size) +alcu_mseg_dealloc(Allctr_t *allctr, void *seg, Uint size, Uint flags) { - erts_mseg_dealloc_opt(allctr->alloc_no, seg, size, &allctr->mseg_opt); + erts_mseg_dealloc_opt(allctr->alloc_no, seg, size, flags, &allctr->mseg_opt); INC_CC(allctr->calls.mseg_dealloc); } @@ -2276,7 +2276,7 @@ resize_carrier(Allctr_t *allctr, Block_t *old_blk, Uint umem_sz, UWord flags) (void *) BLK2UMEM(old_blk), MIN(new_blk_sz, old_blk_sz) - ABLK_HDR_SZ); unlink_carrier(&allctr->sbc_list, old_crr); - alcu_mseg_dealloc(allctr, old_crr, old_crr_sz); + alcu_mseg_dealloc(allctr, old_crr, old_crr_sz, ERTS_MSEG_FLG_NONE); } else { /* Old carrier unchanged; restore stat */ @@ -2352,6 +2352,7 @@ destroy_carrier(Allctr_t *allctr, Block_t *blk) Carrier_t *crr; #if HAVE_ERTS_MSEG Uint is_mseg = 0; + Uint mseg_flags = ERTS_MSEG_FLG_NONE; #endif if (IS_SBC_BLK(blk)) { @@ -2398,6 +2399,7 @@ destroy_carrier(Allctr_t *allctr, Block_t *blk) is_mseg++; ASSERT(crr_sz % MSEG_UNIT_SZ == 0); STAT_MSEG_MBC_FREE(allctr, crr_sz); + mseg_flags = ERTS_MSEG_FLG_2POW; } else #endif @@ -2411,7 +2413,7 @@ destroy_carrier(Allctr_t *allctr, Block_t *blk) #if HAVE_ERTS_MSEG if (is_mseg) { - alcu_mseg_dealloc(allctr, crr, crr_sz); + alcu_mseg_dealloc(allctr, crr, crr_sz, mseg_flags); } else #endif diff --git a/erts/emulator/beam/erl_bif_info.c b/erts/emulator/beam/erl_bif_info.c index a601e4fb39..8582a8954b 100755 --- a/erts/emulator/beam/erl_bif_info.c +++ b/erts/emulator/beam/erl_bif_info.c @@ -69,7 +69,11 @@ static char erts_system_version[] = ("Erlang " ERLANG_OTP_RELEASE " [no-c-stack-objects]" #endif #ifndef OTP_RELEASE +#ifdef ERLANG_GIT_VERSION + " [source-" ERLANG_GIT_VERSION "]" +#else " [source]" +#endif #endif #ifdef ARCH_64 #if HALFWORD_HEAP diff --git a/erts/emulator/beam/erl_init.c b/erts/emulator/beam/erl_init.c index 223c9c4d7e..ec3e0d54cb 100644 --- a/erts/emulator/beam/erl_init.c +++ b/erts/emulator/beam/erl_init.c @@ -981,19 +981,64 @@ erl_start(int argc, char **argv) break; case 'f': if (!strncmp(argv[i],"-fn",3)) { + int warning_type = ERL_FILENAME_WARNING_WARNING; arg = get_arg(argv[i]+3, argv[i+1], &i); switch (*arg) { case 'u': - erts_set_user_requested_filename_encoding(ERL_FILENAME_UTF8); + switch (*(argv[i]+4)) { + case 'w': + case 0: + break; + case 'i': + warning_type = ERL_FILENAME_WARNING_IGNORE; + break; + case 'e': + warning_type = ERL_FILENAME_WARNING_ERROR; + break; + default: + erts_fprintf(stderr, "bad type of warnings for " + "wrongly coded filename: %s\n", argv[i]+4); + erts_usage(); + } + erts_set_user_requested_filename_encoding + ( + ERL_FILENAME_UTF8, + warning_type + ); break; case 'l': - erts_set_user_requested_filename_encoding(ERL_FILENAME_LATIN1); + erts_set_user_requested_filename_encoding + ( + ERL_FILENAME_LATIN1, + warning_type + ); break; case 'a': - erts_set_user_requested_filename_encoding(ERL_FILENAME_UNKNOWN); + switch (*(argv[i]+4)) { + case 'w': + case 0: + break; + case 'i': + warning_type = ERL_FILENAME_WARNING_IGNORE; + break; + case 'e': + warning_type = ERL_FILENAME_WARNING_ERROR; + break; + default: + erts_fprintf(stderr, "bad type of warnings for " + "wrongly coded filename: %s\n", argv[i]+4); + erts_usage(); + } + erts_set_user_requested_filename_encoding + ( + ERL_FILENAME_UNKNOWN, + warning_type + ); break; default: - erts_fprintf(stderr, "bad filename encoding %s, can be (l,u or a)\n", arg); + erts_fprintf(stderr, "bad filename encoding %s, can be " + "(l,u or a, optionally followed by w, " + "i or e)\n", arg); erts_usage(); } break; diff --git a/erts/emulator/beam/erl_unicode.c b/erts/emulator/beam/erl_unicode.c index 99108af937..80982f3760 100644 --- a/erts/emulator/beam/erl_unicode.c +++ b/erts/emulator/beam/erl_unicode.c @@ -2573,8 +2573,20 @@ BIF_RETTYPE prim_file_internal_native2name_1(BIF_ALIST_1) case ERL_FILENAME_UTF8: bytes = erts_get_aligned_binary_bytes(BIF_ARG_1, &temp_alloc); if (erts_analyze_utf8(bytes,size,&err_pos,&num_chars,NULL) != ERTS_UTF8_OK) { + Eterm *hp = HAlloc(BIF_P,3); + Eterm warn_type = NIL; erts_free_aligned_binary_bytes(temp_alloc); - goto noconvert; + switch (erts_get_filename_warning_type()) { + case ERL_FILENAME_WARNING_IGNORE: + warn_type = am_ignore; + break; + case ERL_FILENAME_WARNING_ERROR: + warn_type = am_error; + break; + default: + warn_type = am_warning; + } + BIF_RET(TUPLE2(hp,am_error,warn_type)); } num_built = 0; num_eaten = 0; @@ -2607,9 +2619,8 @@ BIF_RETTYPE prim_file_internal_native2name_1(BIF_ALIST_1) erts_free_aligned_binary_bytes(temp_alloc); BIF_RET(ret); default: - goto noconvert; + break; } - noconvert: BIF_RET(BIF_ARG_1); } @@ -2646,6 +2657,52 @@ BIF_RETTYPE prim_file_internal_normalize_utf8_1(BIF_ALIST_1) BIF_RET(ret); } +BIF_RETTYPE prim_file_is_translatable_1(BIF_ALIST_1) +{ + ERTS_DECLARE_DUMMY(Eterm real_bin); + ERTS_DECLARE_DUMMY(Uint offset); + Uint size; + Uint num_chars; + Uint bitsize; + ERTS_DECLARE_DUMMY(Uint bitoffs); + byte *temp_alloc = NULL; + byte *bytes; + byte *err_pos; + int status; + + if (is_not_binary(BIF_ARG_1)) { + BIF_ERROR(BIF_P,BADARG); + } + size = binary_size(BIF_ARG_1); + ERTS_GET_REAL_BIN(BIF_ARG_1, real_bin, offset, bitoffs, bitsize); + if (bitsize != 0) { + BIF_ERROR(BIF_P,BADARG); + } + if (size == 0) { + BIF_RET(am_true); + } + + /* + * If the encoding is latin1, the pathname is always translatable. + */ + switch (erts_get_native_filename_encoding()) { + case ERL_FILENAME_LATIN1: + BIF_RET(am_true); + case ERL_FILENAME_WIN_WCHAR: + if (erts_get_user_requested_filename_encoding() == ERL_FILENAME_LATIN1) { + BIF_RET(am_true); + } + } + + /* + * Check whether the binary contains legal UTF-8 sequences. + */ + bytes = erts_get_aligned_binary_bytes(BIF_ARG_1, &temp_alloc); + status = erts_analyze_utf8(bytes, size, &err_pos, &num_chars, NULL); + erts_free_aligned_binary_bytes(temp_alloc); + BIF_RET(status == ERTS_UTF8_OK ? am_true : am_false); +} + BIF_RETTYPE file_native_name_encoding_0(BIF_ALIST_0) { switch (erts_get_native_filename_encoding()) { diff --git a/erts/emulator/beam/ops.tab b/erts/emulator/beam/ops.tab index 6764e88c81..8a79b4910e 100644 --- a/erts/emulator/beam/ops.tab +++ b/erts/emulator/beam/ops.tab @@ -1021,7 +1021,7 @@ bif0 u$bif:erlang:node/0 Dst=d => node Dst bif1 Fail Bif=u$bif:erlang:get/1 Src=s Dst=d => i_get Src Dst -bif2 Jump=j u$bif:erlang:element/2 S1=s S2=s Dst=d => gen_element(Jump, S1, S2, Dst) +bif2 Jump=j u$bif:erlang:element/2 S1=s S2=rxy Dst=d => gen_element(Jump, S1, S2, Dst) bif1 Fail Bif Literal=q Dst => move Literal x | bif1 Fail Bif x Dst bif1 p Bif S1 Dst => bif1_body Bif S1 Dst diff --git a/erts/emulator/beam/packet_parser.c b/erts/emulator/beam/packet_parser.c index 1e301e3593..7c9b2d444a 100644 --- a/erts/emulator/beam/packet_parser.c +++ b/erts/emulator/beam/packet_parser.c @@ -67,7 +67,7 @@ static int my_strncasecmp(const char *s1, const char *s2, size_t n) #define HTTP_HDR_HASH_SIZE 53 #define HTTP_METH_HASH_SIZE 13 -#define HTTP_MAX_NAME_LEN 20 +#define HTTP_MAX_NAME_LEN 50 static char tspecial[128]; diff --git a/erts/emulator/beam/sys.h b/erts/emulator/beam/sys.h index 249a9c05c2..9416a91480 100644 --- a/erts/emulator/beam/sys.h +++ b/erts/emulator/beam/sys.h @@ -1029,10 +1029,22 @@ char* win32_errorstr(int); #define ERL_FILENAME_UTF8_MAC (3) #define ERL_FILENAME_WIN_WCHAR (4) +/************************************************************************ + * If a filename in for example list_dir is not in the right encoding, it + * will be skipped in the resulting list, but depending on a startup setting + * we will inform the user in different ways. These macros define the + * different reactions to wrongly coded filenames. In the error case an + * exception will be thrown by prim_file. + ************************************************************************/ +#define ERL_FILENAME_WARNING_WARNING (0) +#define ERL_FILENAME_WARNING_IGNORE (1) +#define ERL_FILENAME_WARNING_ERROR (2) + int erts_get_native_filename_encoding(void); /* The set function is only to be used by erl_init! */ -void erts_set_user_requested_filename_encoding(int encoding); +void erts_set_user_requested_filename_encoding(int encoding, int warning); int erts_get_user_requested_filename_encoding(void); +int erts_get_filename_warning_type(void); void erts_init_sys_common_misc(void); |