get rid of byte code argument to create_calldata
This means that there is less type checking at calldata creation time. Make sure that we check that the function hash exists before calling a contract!
This commit is contained in:
parent
5a4a84805f
commit
e0fff00e64
@ -11,7 +11,7 @@
|
|||||||
-define(HASH_SIZE, 32).
|
-define(HASH_SIZE, 32).
|
||||||
|
|
||||||
-export([ old_create_calldata/3
|
-export([ old_create_calldata/3
|
||||||
, create_calldata/5
|
, create_calldata/4
|
||||||
, check_calldata/2
|
, check_calldata/2
|
||||||
, function_type_info/3
|
, function_type_info/3
|
||||||
, function_type_hash/3
|
, function_type_hash/3
|
||||||
@ -39,22 +39,11 @@
|
|||||||
%%%===================================================================
|
%%%===================================================================
|
||||||
%%% Handle calldata
|
%%% Handle calldata
|
||||||
|
|
||||||
create_calldata(Contract, FunName, Args, ArgTypes, RetType) ->
|
create_calldata(FunName, Args, ArgTypes, RetType) ->
|
||||||
case get_type_info_and_hash(Contract, FunName) of
|
<<TypeHashInt:?HASH_SIZE/unit:8>> =
|
||||||
{ok, TypeInfo, TypeHashInt} ->
|
function_type_hash(list_to_binary(FunName), ArgTypes, RetType),
|
||||||
Data = aeso_heap:to_binary({TypeHashInt, list_to_tuple(Args)}),
|
Data = aeso_heap:to_binary({TypeHashInt, list_to_tuple(Args)}),
|
||||||
case check_calldata(Data, TypeInfo) of
|
{ok, Data, {tuple, [word, {tuple, ArgTypes}]}, RetType}.
|
||||||
{ok, CallDataType, OutType} ->
|
|
||||||
case check_given_type(FunName, ArgTypes, RetType, CallDataType, OutType) of
|
|
||||||
ok ->
|
|
||||||
{ok, Data, CallDataType, OutType};
|
|
||||||
{error, _} = Err ->
|
|
||||||
Err
|
|
||||||
end;
|
|
||||||
{error,_What} = Err -> Err
|
|
||||||
end;
|
|
||||||
{error, _} = Err -> Err
|
|
||||||
end.
|
|
||||||
|
|
||||||
get_type_info_and_hash(#{type_info := TypeInfo}, FunName) ->
|
get_type_info_and_hash(#{type_info := TypeInfo}, FunName) ->
|
||||||
FunBin = list_to_binary(FunName),
|
FunBin = list_to_binary(FunName),
|
||||||
@ -64,26 +53,6 @@ get_type_info_and_hash(#{type_info := TypeInfo}, FunName) ->
|
|||||||
{error, _} = Err -> Err
|
{error, _} = Err -> Err
|
||||||
end.
|
end.
|
||||||
|
|
||||||
%% Check that the given type matches the type from the metadata.
|
|
||||||
check_given_type(FunName, GivenArgs, GivenRet, CalldataType, ExpectRet) ->
|
|
||||||
{tuple, [word, {tuple, ExpectArgs}]} = CalldataType,
|
|
||||||
ReturnOk = if FunName == "init" -> true;
|
|
||||||
GivenRet == any -> true;
|
|
||||||
true -> GivenRet == ExpectRet
|
|
||||||
end,
|
|
||||||
ArgsOk = ExpectArgs == GivenArgs,
|
|
||||||
case ReturnOk andalso ArgsOk of
|
|
||||||
true -> ok;
|
|
||||||
false when FunName == "init" ->
|
|
||||||
{error, {init_args_mismatch,
|
|
||||||
{given, GivenArgs},
|
|
||||||
{expected, ExpectArgs}}};
|
|
||||||
false ->
|
|
||||||
{error, {call_type_mismatch,
|
|
||||||
{given, GivenArgs, '=>', GivenRet},
|
|
||||||
{expected, ExpectArgs, '=>', ExpectRet}}}
|
|
||||||
end.
|
|
||||||
|
|
||||||
-spec check_calldata(binary(), type_info()) ->
|
-spec check_calldata(binary(), type_info()) ->
|
||||||
{'ok', typerep(), typerep()} | {'error', atom()}.
|
{'ok', typerep(), typerep()} | {'error', atom()}.
|
||||||
check_calldata(CallData, TypeInfo) ->
|
check_calldata(CallData, TypeInfo) ->
|
||||||
|
@ -12,7 +12,7 @@
|
|||||||
, file/2
|
, file/2
|
||||||
, from_string/2
|
, from_string/2
|
||||||
, check_call/4
|
, check_call/4
|
||||||
, create_calldata/4
|
, create_calldata/3
|
||||||
, version/0
|
, version/0
|
||||||
, sophia_type_to_typerep/1
|
, sophia_type_to_typerep/1
|
||||||
, to_sophia_value/4
|
, to_sophia_value/4
|
||||||
@ -271,13 +271,13 @@ translate_vm_value(VmTypes, {constr_t, _, Con, Types}, Args)
|
|||||||
translate_vm_value(_VmType, _Type, _Data) ->
|
translate_vm_value(_VmType, _Type, _Data) ->
|
||||||
throw(cannot_translate_to_sophia).
|
throw(cannot_translate_to_sophia).
|
||||||
|
|
||||||
-spec create_calldata(map(), string(), string(), [string()]) ->
|
-spec create_calldata(string(), string(), [string()]) ->
|
||||||
{ok, binary(), aeso_sophia:type(), aeso_sophia:type()}
|
{ok, binary(), aeso_sophia:type(), aeso_sophia:type()}
|
||||||
| {error, argument_syntax_error}.
|
| {error, argument_syntax_error}.
|
||||||
create_calldata(Contract, Code, Fun, Args) when is_map(Contract) ->
|
create_calldata(Code, Fun, Args) ->
|
||||||
case check_call(Code, Fun, Args, []) of
|
case check_call(Code, Fun, Args, []) of
|
||||||
{ok, FunName, {ArgTypes, RetType}, Args} ->
|
{ok, FunName, {ArgTypes, RetType}, VMArgs} ->
|
||||||
aeso_abi:create_calldata(Contract, FunName, Args, ArgTypes, RetType);
|
aeso_abi:create_calldata(FunName, VMArgs, ArgTypes, RetType);
|
||||||
{error, _} = Err -> Err
|
{error, _} = Err -> Err
|
||||||
end.
|
end.
|
||||||
|
|
||||||
|
Loading…
x
Reference in New Issue
Block a user