From 6c2b0ff5eb6009efdfdb3fa7b4ee794804e01bf0 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Bj=C3=B6rn=20Gustavsson?= Date: Fri, 10 Nov 2017 14:43:13 +0100 Subject: Refuse to load "literals" that can be confused with registers The 's' operand overloads the tags for pids and ports to represent X and Y registers, respectively. At load time, refuse to load the module if the "literal" term is not a pid or port, as it would be interpreted as a register. This does not happen with normally compiled code, but it can happen if the compiler (or beam_asm) is abused like in the following example: make_bad() -> Pid = self(), Forms = [{attribute, 0, module, bad_s_operand}, {attribute, 0, export, [{test, 0}]}, {function, 0, test, 0, [{clause, 0, [], [], [{call,0,{atom,0,tuple_size},[{integer, 0, Pid}]}]}]}], {ok, Module, Bin} = compile:forms(Forms, [no_copt,no_postopt,report_errors]), code:load_binary(Module, "bad_s_operand.erl", Bin). With this commit applied, the following message will be printed when make_bad() is run: =ERROR REPORT==== 10-Nov-2017::14:47:59 === Loading of bad_s_operand.erl failed: badfile =ERROR REPORT==== 10-Nov-2017::14:47:59 === beam/beam_load.c(2396): Error loading function bad_s_operand:test/0: op bif1_body: bsd: the term '<0.60.0>' would be confused with a register --- erts/emulator/beam/beam_load.c | 14 ++++++++++++-- 1 file changed, 12 insertions(+), 2 deletions(-) diff --git a/erts/emulator/beam/beam_load.c b/erts/emulator/beam/beam_load.c index 7331c331a6..4fcfea527c 100644 --- a/erts/emulator/beam/beam_load.c +++ b/erts/emulator/beam/beam_load.c @@ -2384,8 +2384,18 @@ load_code(LoaderState* stp) code[ci++] = NIL; break; case TAG_q: - new_literal_patch(stp, ci); - code[ci++] = tmp_op->a[arg].val; + { + BeamInstr val = tmp_op->a[arg].val; + Eterm term = stp->literals[val].term; + new_literal_patch(stp, ci); + code[ci++] = val; + switch (loader_tag(term)) { + case LOADER_X_REG: + case LOADER_Y_REG: + LoadError1(stp, "the term '%T' would be confused " + "with a register", term); + } + } break; default: LoadError1(stp, "bad tag %d for general source", -- cgit v1.2.3