sftp icon indicating copy to clipboard operation
sftp copied to clipboard

Request attributes are not being propagated for SSH_FXP_OPEN operation

Open pavan-aeturi opened this issue 2 years ago • 5 comments

Hi Team, I'm facing the below issue where I'm looking for ways to block interrupted uploads (similar issue). So I want to access request attributes such as file-size during a put command. Even though the client sends the attributes during a put command, sftp-go server library doesn't seem to propagate it to handler

The restriction might be intentional and have a good reason behind it, in which case may I know the details of the reasoning? The library specification document too, doesn't talk about having this restriction. Please correct me if I'm wrong. Thanks in the advance.

Screenshot 2023-09-08 at 2 03 28 PM

`// New Request initialized based on packet data func requestFromPacket(ctx context.Context, pkt hasPath, baseDir string) *Request { request := &Request{ Method: requestMethod(pkt), Filepath: cleanPathWithBase(baseDir, pkt.getPath()), } request.ctx, request.cancelCtx = context.WithCancel(ctx)

switch p := pkt.(type) {
case *sshFxpOpenPacket:
	request.Flags = p.Pflags
case *sshFxpSetstatPacket:
	request.Flags = p.Flags
	request.Attrs = p.Attrs.([]byte)
case *sshFxpRenamePacket:
	request.Target = cleanPathWithBase(baseDir, p.Newpath)
case *sshFxpSymlinkPacket:
	// NOTE: given a POSIX compliant signature: symlink(target, linkpath string)
	// this makes Request.Target the linkpath, and Request.Filepath the target.
	request.Target = cleanPathWithBase(baseDir, p.Linkpath)
	request.Filepath = p.Targetpath
case *sshFxpExtendedPacketHardlink:
	request.Target = cleanPathWithBase(baseDir, p.Newpath)
}
return request

} `

pavan-aeturi avatar Sep 08 '23 08:09 pavan-aeturi

There are unfortunately known issues with the opening of files and handling of attributes. I’ve done a complete rewrite of the client before, but due to early design decisions some of these just aren’t possible to address.

Though… in this case, :squint: it might be possible to bodge in request.Attrs if we make sure the sshFxpOpenPacket contains them at least.

puellanivis avatar Sep 08 '23 18:09 puellanivis

If a client sends size 0 because it does not support this optional attribute it will be difficult to distinguish it from clients that support the attribute if they upload a 0 byte file

drakkan avatar Sep 08 '23 18:09 drakkan

Wouldn’t a client that does not support the optional attribute just not even set SSH_FILEXFER_ATTR_SIZE and thus be distinct from those that do support the attribute?

puellanivis avatar Sep 11 '23 09:09 puellanivis

yes @puellanivis, that makes sense, SSH_FILEXFER_ATTR_SIZE check should help figure out if it is actually set and something like the below should help resolve file-size on server side

// r *sftp.Request
if r.AttrFlags().Size && r.Attributes() != nil && r.Attributes().Size > 0 {
  h.logger.Info("File size of upload file_length: %d", r.Attributes().Size)
}

pavan-aeturi avatar Sep 11 '23 13:09 pavan-aeturi

I ended up implementing attrs for the old Server in #567, should be possible to use in the request server as well, I think. There are probably edge cases I haven't considered, though.

mafredri avatar Dec 12 '23 15:12 mafredri