-
Notifications
You must be signed in to change notification settings - Fork 14.5k
Fix modules\auxiliary\scanner\redis\redis_server #20408
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Conversation
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
For some reason, this module was using different approach to send redis commands than other modules:
./exploits/linux/redis/redis_debian_sandbox_escape.rb:144: info_output = redis_command('INFO')
./exploits/linux/redis/redis_debian_sandbox_escape.rb:168: info_output = redis_command('INFO')
./exploits/linux/redis/redis_replication_cmd_exec.rb:79: return CheckCode::Safe unless (config_data = redis_command('CONFIG', 'GET', '*')) && config_data =~ /dbfilename/
./exploits/linux/redis/redis_replication_cmd_exec.rb:81: if (info_data = redis_command('INFO')) && /redis_version:(?<redis_version>\S+)/ =~ info_data
./exploits/linux/redis/redis_replication_cmd_exec.rb:136: redis_command('SLAVEOF', srvhost, srvport.to_s)
./exploits/linux/redis/redis_replication_cmd_exec.rb:137: redis_command('CONFIG', 'SET', 'dbfilename', module_file.to_s)
./exploits/linux/redis/redis_replication_cmd_exec.rb:144: redis_command('MODULE', 'LOAD', "./#{module_file}")
./exploits/linux/redis/redis_replication_cmd_exec.rb:145: redis_command('SLAVEOF', 'NO', 'ONE')
./exploits/linux/redis/redis_replication_cmd_exec.rb:154: # redis_command('CONFIG', 'SET', 'dbfilename', 'dump.rdb')
./exploits/linux/redis/redis_replication_cmd_exec.rb:155: # redis_command('MODULE', 'UNLOAD', "#{@module_init_name}")
./exploits/linux/redis/redis_replication_cmd_exec.rb:213: redis_command(@module_cmd.to_s)
./exploits/linux/redis/redis_replication_cmd_exec.rb:224: redis_command('shell.exec', cmd.to_s)
./auxiliary/gather/redis_extractor.rb:38: response = redis_command('scan', offset)
./auxiliary/gather/redis_extractor.rb:55: key_type = redis_command('TYPE', key)
./auxiliary/gather/redis_extractor.rb:61: string_content = redis_command('get', key)
./auxiliary/gather/redis_extractor.rb:66: list_content = redis_command('LRANGE', key, '0', '-1')
./auxiliary/gather/redis_extractor.rb:71: set_content = redis_command('SMEMBERS', key)
./auxiliary/gather/redis_extractor.rb:76: set_content = redis_command('ZRANGE', key, '0', '-1')
./auxiliary/gather/redis_extractor.rb:81: hash_content = parse_redis_response(redis_command('HGETALL', key))
./auxiliary/gather/redis_extractor.rb:101: if (info_data = redis_command('INFO', 'server')) && /redis_version:(?<redis_version>\S+)/ =~ info_data
./auxiliary/gather/redis_extractor.rb:154: ks = redis_command('INFO', 'keyspace')
./auxiliary/gather/redis_extractor.rb:181: redis_command('SELECT', space[0])
./auxiliary/scanner/redis/redis_server.rb:49: return unless (data = redis_command(*command_parts))
grep: ./auxiliary/scanner/redis/.redis_server.rb.swp: binary file matches
./auxiliary/scanner/redis/file_upload.rb:61: original_dir = (redis_command('CONFIG', 'GET', 'dir') || '').split(/\r\n/).last
./auxiliary/scanner/redis/file_upload.rb:62: original_dbfilename = (redis_command('CONFIG', 'GET', 'dbfilename') || '').split(/\r\n/).last
./auxiliary/scanner/redis/file_upload.rb:64: original_rdbcompression = (redis_command('CONFIG', 'GET', 'rdbcompression') || '').split(/\r\n/).last
./auxiliary/scanner/redis/file_upload.rb:68: data = redis_command('CONFIG', 'SET', 'dir', dirname) || ''
./auxiliary/scanner/redis/file_upload.rb:72: data = redis_command('CONFIG', 'SET', 'dbfilename', basename) || ''
./auxiliary/scanner/redis/file_upload.rb:81: data = redis_command('CONFIG', 'SET', 'rdbcompression', 'no') || ''
./auxiliary/scanner/redis/file_upload.rb:91: data = redis_command('FLUSHALL') || ''
./auxiliary/scanner/redis/file_upload.rb:102: data = redis_command('SET', key, content) || ''
./auxiliary/scanner/redis/file_upload.rb:105: data = redis_command('SAVE') || ''
./auxiliary/scanner/redis/file_upload.rb:116: redis_command('CONFIG', 'SET', 'dir', original_dir)
./auxiliary/scanner/redis/file_upload.rb:117: redis_command('CONFIG', 'SET', 'dbfilename', original_dbfilename)
./auxiliary/scanner/redis/file_upload.rb:119: redis_command('CONFIG', 'SET', 'rdbcompression', original_rdbcompression)
./auxiliary/scanner/redis/file_upload.rb:121: redis_command('DEL', key)
./auxiliary/scanner/redis/file_upload.rb:122: redis_command('SAVE')
./auxiliary/scanner/redis/file_upload.rb:128: return Exploit::CheckCode::Safe unless (config_data = redis_command('CONFIG', 'GET', '*')) && config_data =~ /dbfilename/
./auxiliary/scanner/redis/file_upload.rb:130: if (info_data = redis_command('INFO')) && /redis_version:(?<redis_version>\S+)/ =~ info_data
All other modules are sending each word of command as separate argument. My educated guess is that this module was overlooked or someone was considering only single-word commands.
Release NotesFixes argument passing to the |
This change updates the redis_server module to correctly parse Redis commands that contain multiple words (e.g., CONFIG SET dir /tmp). Previously, the module would incorrectly split command arguments, potentially leading to execution failures or unexpected behavior.
Verification
msfconsole
use auxiliary/scanner/redis/redis_server
set RHOSTS <IP>
(target a Redis server with unauthorized access enabled, i.e., no password)set redis.command "MODULE LIST"
or any multi-word Redis command (e.g.,"CONFIG SET dir /tmp"
)Before and after the modification, the module can correctly execute single-argument commands, such as INFO.




However, before the fix, the module was unable to properly handle multi-argument commands like MODULE LIST or MODULE LOAD ./exp.so.
After the fix, these multi-argument commands can now be executed successfully.
This issue was fundamentally caused by incorrect string splitting logic in the original implementation. The module treated multi-word strings as a single command word, which led to command parsing failures and prevented the correct command from being recognized.