File 1494-ssh-fix-decode-uid-gid.patch of Package erlang
From 1a12aa31d77de76cf81827289b6caf0224270337 Mon Sep 17 00:00:00 2001
From: Jakub Witczak <kuba@erlang.org>
Date: Mon, 4 Mar 2024 13:25:35 +0100
Subject: [PATCH] ssh: fix decode uid, gid
- adds missing list_to_integer conversion upon decoding
- fix version typo
- enhanced tests
---
lib/ssh/src/ssh_xfer.erl | 7 ++--
lib/ssh/test/ssh_sftp_SUITE.erl | 57 +++++++++++++++++++++++++++------
2 files changed, 49 insertions(+), 15 deletions(-)
diff --git a/lib/ssh/src/ssh_xfer.erl b/lib/ssh/src/ssh_xfer.erl
index 212798f2d7..05f420b1a7 100644
--- a/lib/ssh/src/ssh_xfer.erl
+++ b/lib/ssh/src/ssh_xfer.erl
@@ -660,7 +660,7 @@ encode_As(Vsn, [{AName, X}|As], Flags, Acc) ->
encode_As(Vsn, As,Flags bor ?SSH_FILEXFER_ATTR_UIDGID,
[?uint32(X) | Acc]);
ownergroup when Vsn>=5 ->
- X1 = list_to_binary(integer_to_list(X)), % TODO: check owner and group
+ X1 = integer_to_binary(X), % TODO: check owner and group
encode_As(Vsn, As,Flags bor ?SSH_FILEXFER_ATTR_OWNERGROUP,
[?binary(X1) | Acc]);
permissions ->
@@ -736,13 +736,11 @@ decode_As(Vsn, [{AName, AField}|As], R, Flags, Tail) ->
decode_As(Vsn, As, setelement(AField, R, X), Flags, Tail2);
ownergroup when ?is_set(?SSH_FILEXFER_ATTR_OWNERGROUP, Flags),Vsn>=5 ->
<<?UINT32(Len), Bin:Len/binary, Tail2/binary>> = Tail,
- X = binary_to_list(Bin),
+ X = binary_to_integer(Bin),
decode_As(Vsn, As, setelement(AField, R, X), Flags, Tail2);
-
permissions when ?is_set(?SSH_FILEXFER_ATTR_PERMISSIONS,Flags),Vsn>=5->
<<?UINT32(X), Tail2/binary>> = Tail,
decode_As(Vsn, As, setelement(AField, R, X), Flags, Tail2);
-
permissions when ?is_set(?SSH_FILEXFER_ATTR_PERMISSIONS,Flags),Vsn=<3->
<<?UINT32(X), Tail2/binary>> = Tail,
R1 = setelement(AField, R, X),
@@ -757,7 +755,6 @@ decode_As(Vsn, [{AName, AField}|As], R, Flags, Tail) ->
_ -> unknown
end,
decode_As(Vsn, As, R1#ssh_xfer_attr { type=Type}, Flags, Tail2);
-
acmodtime when ?is_set(?SSH_FILEXFER_ATTR_ACMODTIME,Flags),Vsn=<3 ->
<<?UINT32(X), Tail2/binary>> = Tail,
decode_As(Vsn, As, setelement(AField, R, X), Flags, Tail2);
diff --git a/lib/ssh/test/ssh_sftp_SUITE.erl b/lib/ssh/test/ssh_sftp_SUITE.erl
index 5f5129d9b6..528708ba9d 100644
--- a/lib/ssh/test/ssh_sftp_SUITE.erl
+++ b/lib/ssh/test/ssh_sftp_SUITE.erl
@@ -81,7 +81,8 @@
-include_lib("common_test/include/ct.hrl").
-include_lib("kernel/include/file.hrl").
-include("ssh_test_lib.hrl").
- % Default timetrap timeout
+-include_lib("stdlib/include/assert.hrl").
+%% Default timetrap timeout
-define(default_timeout, ?t:minutes(1)).
%%--------------------------------------------------------------------
@@ -563,26 +564,62 @@ links(Config) when is_list(Config) ->
retrieve_attributes(Config) when is_list(Config) ->
FileName = proplists:get_value(filename, Config),
SftpFileName = w2l(Config, FileName),
-
{Sftp, _} = proplists:get_value(sftp, Config),
{ok, FileInfo} = ssh_sftp:read_file_info(Sftp, SftpFileName),
{ok, NewFileInfo} = file:read_file_info(FileName),
-
- %% TODO comparison. There are some differences now is that ok?
- ct:log("SFTP: ~p FILE: ~p~n", [FileInfo, NewFileInfo]).
+ ct:log("ssh_sftp:read_file_info(~p): ~p~n"
+ "file:read_file_info(~p): ~p",
+ [SftpFileName, FileInfo, FileName, NewFileInfo]),
+ {ExpectedUid, ExpectedGid} =
+ case {os:type(), proplists:get_value(group,Config)} of
+ {{win32, _}, openssh_server} ->
+ %% Windows compiled Erlang is expected will return 0;
+ %% but when Erlang(Windows) client interacts with
+ %% OpenSSH server - value 1000 is received by client
+ %% over SFTP (because OpenSSH is compiled for Linux
+ %% and runs on WSL)
+ {1000, 1000};
+ _ ->
+ {FileInfo#file_info.uid, FileInfo#file_info.gid}
+ end,
+ ?assertEqual(ExpectedUid, NewFileInfo#file_info.uid),
+ ?assertEqual(ExpectedGid, NewFileInfo#file_info.gid),
+ ok.
%%--------------------------------------------------------------------
set_attributes(Config) when is_list(Config) ->
FileName = proplists:get_value(testfile, Config),
SftpFileName = w2l(Config, FileName),
-
{Sftp, _} = proplists:get_value(sftp, Config),
{ok,Fd} = file:open(FileName, write),
io:put_chars(Fd,"foo"),
- ok = ssh_sftp:write_file_info(Sftp, SftpFileName, #file_info{mode=8#400}),
- {error, eacces} = file:write_file(FileName, "hello again"),
- ok = ssh_sftp:write_file_info(Sftp, SftpFileName, #file_info{mode=8#600}),
- ok = file:write_file(FileName, "hello again").
+ TestWriting =
+ fun(FInfo) ->
+ ok = ssh_sftp:write_file_info(Sftp, SftpFileName,
+ FInfo#file_info{mode=8#400}),
+ {error, eacces} = file:write_file(FileName, "hello again"),
+ ok = ssh_sftp:write_file_info(Sftp, SftpFileName,
+ FInfo#file_info{mode=8#600}),
+ ok = file:write_file(FileName, "hello again")
+ end,
+ TestWriting(#file_info{}),
+ IsErlangServer =
+ fun() ->
+ TcGroupPath = proplists:get_value(tc_group_path, Config),
+ {_, Path} = lists:unzip(lists:flatten(TcGroupPath)),
+ lists:member(erlang_server, Path)
+ end,
+ case IsErlangServer() of
+ true ->
+ ct:log("Testing with writing a complete #file_info record"),
+ {ok, FileInfo} = file:read_file_info(SftpFileName),
+ TestWriting(FileInfo);
+ _ ->
+ %% with OpenSSH daemon started by other user above instruction end
+ %% up with permission denied
+ ok
+ end,
+ ok.
%%--------------------------------------------------------------------
file_owner_access(Config) when is_list(Config) ->
--
2.35.3