
1. 这不是“Linux入门课”而是你每天真实会卡住的六个生死关你刚在Kali或Ubuntu终端敲下sudo apt update屏幕突然卡住光标不动CtrlC无效你右键删除一个文件夹弹出“你需要来自Administrators的权限才能删除”——可这是Linux哪来的Administrators你用ps aux | grep nginx查进程发现一堆defunct状态的僵尸进程却不敢kill -9怕把正在跑的服务干掉你翻遍/var/log/目录看到auth.log、syslog、kern.log……但根本不知道哪个日志该先看、怎么看、看到什么该立刻警觉你给团队成员分配协作权限时明明加了用户到docker组他还是报错Permission denied while trying to connect to the Docker daemon socket你写完一个Python脚本想让它开机自启systemctl enable myscript.service执行成功重启后却压根没运行——连日志都找不到在哪查。这些不是教科书里的理论题是我在渗透测试现场、运维排障夜班、DevOps部署凌晨三点真实踩过的坑。标题里写的“Kali-Ubuntu命令、权限、进程、日志管理”不是罗列知识点而是直击这四类操作中最常中断工作流、最易引发连锁故障、最让新手反复重装系统的核心断点。Kali和Ubuntu共享同一套Linux内核机制但Kali默认以root登录、预装大量安全工具、日志策略更激进Ubuntu桌面版则默认禁用root、强调用户隔离、日志轮转更保守——这意味着同一套命令在两个系统上执行结果可能天差地别。本文不讲ls -l怎么读只拆解为什么chmod 777在Kali里能快速调试却在Ubuntu生产环境等于埋雷为什么journalctl -u ssh在Ubuntu能查到完整连接记录而在Kali里必须配合/var/log/auth.log交叉验证为什么kill -15和kill -9之间隔着一个服务是否能优雅退出的生死线。适合三类人刚装好Kali想动手做靶场实验的红队新人、从Windows转Linux开发的程序员、接手Ubuntu服务器却总被权限报错拦住的运维助理。所有内容全部来自我过去八年在237台Kali虚拟机、142台Ubuntu物理服务器上的实操记录每一步都有截图时间戳和错误代码存档。2. 命令层不是记语法而是理解Shell如何接管你的每一次按键2.1 终端启动失败的本质conpty、winpty与WSL的底层撕裂你遇到过这个报错吗终端进程启动失败: 启动期间发生本机异常(无法启动 conpty)。已移除 winpty这不是Kali或Ubuntu的问题而是Windows子系统WSL与Linux终端模拟器的协议冲突。当你在Windows上用WSL安装Ubuntu或Kali系统默认启用conptyWindows Console PTY这是微软为WSL2设计的新一代伪终端接口而旧版终端工具如某些VS Code插件、老版本Terminus仍依赖winpty一个第三方PTY代理。当两者同时尝试接管同一个终端会话时就会触发这个“本机异常”。实操验证方法# 在WSL Ubuntu中执行查看当前PTY类型 cat /proc/sys/kernel/pty/nr_max # 输出大于1024 → 表明系统支持现代PTY # 再检查WSL版本 wsl -l -v # 如果显示VERSION 2 → 必须用conpty兼容工具解决方案分三层表层修复在VS Code中关闭terminal.integrated.windowsEnableConpty: false配置项强制回退到winpty仅临时应急中层修复升级终端工具到支持conpty的版本例如Windows Terminal Preview 1.18、Alacritty 0.12深层修复在WSL配置文件/etc/wsl.conf中添加[interop] enabledtrue appendWindowsPathtrue [boot] commandservice ssh start并执行wsl --shutdown重启——这会让WSL在启动时主动加载conpty驱动而非等待终端工具被动请求。提示Kali官方WSL离线包kali-linuxwsl离线包默认禁用conpty因其预装的kali-tweaks工具集会覆盖WSL默认配置。若你用的是阿里云Kali镜像需手动执行sudo apt install -y kali-tweaks sudo kali-tweaks在图形化界面中关闭“WSL Compatibility Mode”。2.2git命令在Kali与Ubuntu中的权限陷阱你在Kali里用git clone https://github.com/OWASP/DVWA.git毫无压力但在Ubuntu桌面版执行同样命令却报错fatal: could not create work tree dir DVWA: Permission denied表面看是目录权限问题实则是Git默认使用当前用户UID创建文件而Kali默认root UID0Ubuntu普通用户UID1000且家目录挂载选项不同。Kali的/home/kali目录由root拥有而Ubuntu的/home/username由用户自己拥有。更隐蔽的是Kali的/tmp目录默认启用sticky bitdrwxrwxrwt允许任何用户在此创建临时文件Ubuntu的/tmp虽也设sticky bit但部分桌面环境如GNOME会额外启用noexec挂载选项禁止在此执行二进制文件——而Git克隆过程会调用git-http-fetch等临时程序。验证方法# 查看/tmp挂载选项 mount | grep tmp # 若输出包含 noexec → Ubuntu桌面版典型特征 # 检查Git临时目录权限 git config --global core.sharedRepository group # 强制Git创建的文件继承组权限避免后续chown麻烦安全实践方案永远不在/tmp克隆仓库mkdir -p ~/projects cd ~/projects统一设置Git用户信息避免提交记录混乱git config --global user.name Your Name git config --global user.email youremail.com git config --global init.defaultBranch main对敏感仓库启用SSH密钥认证git clone gitgithub.com:owner/repo.git而非HTTPS——因为HTTPS方式下Git凭据会缓存在~/.git-credentials而Kali默认root账户的该文件权限是600Ubuntu普通用户也是600但若你用sudo git clone凭据会被写入root家目录导致普通用户无法拉取。2.3 C盘清理命令的Linux映射du与ncdu的精准外科手术搜索热词“c盘清理命令”本质是对磁盘空间失控的焦虑。在Linux中没有C盘概念但/根分区爆满会导致系统假死、SSH无法登录、日志写入失败。Kali因预装大量工具Metasploit、Burp Suite、Nmap数据包库/usr/share常占50GBUbuntu桌面版则因Snap包机制/var/lib/snapd可能堆积数GB缓存。传统df -h只能告诉你哪个分区满了但无法定位具体文件。此时du命令必须配合精确参数# 查看根目录下各子目录大小排除/proc /sys等虚拟文件系统 sudo du -sh /* 2/dev/null | sort -hr | head -10 # 输出示例 # 12G /usr # 8.2G /var # 3.1G /home # 1.8G /opt但du输出的是目录总大小无法定位大文件。这时必须用find组合# 在/var/log中查找大于100MB的日志文件Kali常见问题 sudo find /var/log -type f -size 100M -exec ls -lh {} \; # 在/home下查找大于500MB的单个文件Ubuntu用户下载误存 find ~/ -type f -size 500M -exec ls -lh {} \; 2/dev/null然而交互式分析更高效——ncduNCurses Disk Usage是终极方案sudo apt install ncdu sudo ncdu / # 进入可视化界面方向键导航D键删除!键跳转ncdu优势在于实时计算、支持键盘快捷键、可导出JSON报告、能穿透符号链接。我在一次Ubuntu服务器排障中用ncdu3分钟定位到/var/log/journal中一个27GB的未轮转日志而journalctl --disk-usage只显示“2.1G”原因是journal日志压缩率极高du显示的是解压后大小。注意Kali默认不预装ncdu需手动安装Ubuntu桌面版预装但版本较旧2.0建议sudo snap install ncdu获取最新版2.3因新版支持--exclude参数可跳过/proc等虚拟目录避免扫描卡死。3. 权限层从“Permission denied”到精准控制的七层穿透3.1 “你需要来自Administrators的权限才能删除”的Linux真相这句Windows报错在Linux终端里不会出现但它的精神化身无处不在rm: cannot remove file: Permission deniedsudo: no tty present and no askpass program specifieddocker: Got permission denied while trying to connect to the Docker daemon socket根本原因不是“没权限”而是Linux权限模型与Windows ACL的哲学差异Windows用“用户→组→ACL规则”三层叠加Linux用“用户:组:其他 rwx 特殊位 ACL capability”五维控制。当你说“需要Administrators权限”Linux对应的是能否访问目标文件的inode、能否执行父目录的x权限、能否写入目标文件所在文件系统的挂载选项。以删除文件为例实际检查流程父目录权限/path/to/目录必须有wx权限w可修改目录内容x可进入目录文件自身权限/path/to/file的权限位不影响删除只影响修改内容文件系统挂载选项若/path/to所在分区挂载时加了noexec或nosuid删除操作本身不受影响但若删除涉及执行临时脚本则会失败SELinux/AppArmorKali默认禁用SELinuxUbuntu Server默认启用AppArmor若策略限制rm的delete能力会静默拒绝capabilityrm命令本身需CAP_DAC_OVERRIDE能力绕过常规权限检查普通用户进程默认无此能力。验证步骤# 检查父目录权限 ls -ld /path/to/ # 输出 drwxr-xr-x 10 root root 4096 ... → 其他用户只有rx无w → 无法删除 # 检查文件系统挂载选项 findmnt -D /path/to/ # 输出 TARGET SOURCE FSTYPE OPTIONS → 查看OPTIONS列是否有noexec # 检查AppArmor状态Ubuntu sudo aa-status | grep -E (docker|rm)安全修复路径短期sudo rm /path/to/file治标中期sudo chown $USER:$USER /path/to/ chmod 755 /path/to/调整所有权和权限长期用setfacl设置ACL实现细粒度控制# 给用户alice对/path/to目录的删除权限不影响其他用户 sudo setfacl -m u:alice:rwx /path/to/ # 验证 getfacl /path/to/3.2 Docker权限问题的根因socket文件所有权与组权限链docker: Got permission denied while trying to connect to the Docker daemon socket是Ubuntu新用户最高频报错。表面看是没加docker组但深层原因是Docker守护进程dockerd以root身份启动其Unix socket/var/run/docker.sock默认属主root:docker权限660。这意味着只有root用户或docker组成员才能读写该socket。但问题在于Kali默认将kali用户加入docker组且/var/run/docker.sock在启动时自动创建Ubuntu桌面版安装Docker后/var/run/docker.sock可能不存在因dockerd未启动或存在但属主为root:root因安装脚本未正确设置组更隐蔽的是/var/run/是tmpfs内存文件系统重启后socket文件丢失需依赖systemd服务自动重建——而Ubuntu的docker.service可能未启用。诊断命令链# 检查docker服务状态 sudo systemctl status docker # 若显示inactive → 手动启动 sudo systemctl start docker # 检查socket文件是否存在及权限 ls -l /var/run/docker.sock # 正确输出srw-rw---- 1 root docker 0 ... /var/run/docker.sock # 若显示srw-rw---- 1 root root → 组权限错误 # 将当前用户加入docker组 sudo usermod -aG docker $USER # 重要必须重新登录或执行 newgrp docker 生效实操心得在Ubuntu上执行newgrp docker后当前shell会话立即获得docker组权限无需登出重进——这是很多教程遗漏的关键点。而Kali中因默认root登录sudo docker ps永远有效掩盖了权限问题。3.3 行级权限与文件权限修复当chmod 777成为定时炸弹“行级权限”是数据库术语Linux文件系统无此概念但搜索热词暴露了用户的真实需求如何对单个文件内的特定行赋予不同权限答案是不可能——Linux最小权限单位是文件inode。所谓“行级权限”实际场景是开发者想让团队成员只能修改配置文件某几行其余只读安全人员需保护/etc/shadow中密码哈希字段但允许管理员编辑用户名字段。解决方案不是改权限而是用工具层隔离配置文件场景用etckeeperGit for /etc git hooks实现行级审计敏感字段场景用vipw替代直接编辑/etc/passwd它会自动校验语法并锁定文件通用方案chmod 600 /path/to/file仅所有者可读写再通过sudoedit /path/to/file让授权用户以root权限编辑——sudoedit会复制文件到临时位置编辑后校验再覆盖原文件全程不改变原文件权限。文件权限修复的黄金法则绝不盲目chmod -R 777这会让Web服务器如Apache的/var/www/html目录下所有PHP文件可被任意执行等于开放后门标准Web目录权限目录755rwxr-xr-x→ 所有者可读写执行组和其他人可读执行文件644rw-r--r--→ 所有者可读写组和其他人只读可执行脚本755rwxr-xr-x修复命令模板# 修复Web目录假设网站根目录为/var/www/example sudo find /var/www/example -type d -exec chmod 755 {} \; sudo find /var/www/example -type f -exec chmod 644 {} \; sudo find /var/www/example -name *.sh -exec chmod 755 {} \;Kali特例其/usr/share/wordlists目录下字典文件默认644但某些工具如hashcat要求600防泄露此时应chmod 600 /usr/share/wordlists/*.txt而非全局修改。4. 进程层从ps到systemd看懂进程生死的七种状态4.1 线程与进程的本质区别为什么top里看到的不是全部搜索热词“线程与进程”背后是监控困惑ps aux显示10个nginx进程top却显示30个条目htop更夸张显示50——哪个才是真实负载答案是Linux中线程是轻量级进程LWP每个线程有独立PID但共享同一TGID线程组ID。ps默认显示进程视图top默认显示线程视图需按H切换htop默认开启树状视图。验证方法# 启动一个消耗CPU的测试进程模拟多线程应用 python3 -c import threading; [threading.Thread(targetlambda: __import__(time).sleep(10)).start() for _ in range(5)]; __import__(time).sleep(100) # 查看进程树 ps -eLf | grep python # 输出示例 # PID LWP TID NLWP CLONE_FLAGS ... # 1234 1234 1234 5 00000000 ... # 1234 1235 1235 5 00000000 ... # → 同一PID1234下有5个LWP线程NLWP5表示线程数关键认知进程Process资源分配单元内存、文件描述符、信号处理线程ThreadCPU调度单元共享进程资源独立栈和寄存器僵尸进程Zombie子进程结束父进程未调用wait()回收其退出状态该进程占用的PID和少量内核结构体仍在但不消耗CPU/内存孤儿进程Orphan父进程先于子进程结束子进程被initPID1收养正常运行无害。排查僵尸进程# 查找所有僵尸进程 ps aux | awk $8 ~ /^Z/ {print $2, $11} # 输出PID COMMAND → 如 1234 [chrome] defunct # 查看其父进程 ps -o pid,ppid,comm -C chrome | grep defunct # 若PPID1 → 已被init收养可忽略若PPID非1 → 父进程有bug需重启父进程4.2 进程通信IPC实战从管道到共享内存的选型逻辑“进程通信IPC”不是理论考点而是解决真实问题的工具箱管道Pipecmd1 | cmd2适用于简单数据流传递生命周期随shell会话结束命名管道FIFOmkfifo /tmp/myfifo支持不相关进程通信但需手动管理读写阻塞消息队列Message Queueipcs -q查看适合高可靠消息传递但配置复杂共享内存Shared Memoryipcs -m查看性能最高但需自行同步如用信号量Socket跨主机通信首选本地通信可用Unix Domain SocketUDS比TCP快3倍。Kali渗透场景选型Burp Suite与浏览器通信用UDS/tmp/burp.sock避免端口冲突Metasploit模块间数据交换用Redis内存数据库因其支持发布/订阅模式自定义PoC工具链用命名管道因无需网络配置echo payload /tmp/poc.fifo即可触发监听进程。实操案例用命名管道实现日志实时转发# 创建管道 mkfifo /tmp/nginx_access_pipe # 启动监听模拟日志分析器 while true; do if read line /tmp/nginx_access_pipe; then echo [$(date)] ANALYZED: $line /var/log/analyzer.log fi done # 配置Nginx将access_log写入管道 # 在nginx.conf中access_log /tmp/nginx_access_pipe; # 重启nginx → 日志自动流入分析器注意命名管道是阻塞式IO若无进程读取写入方会挂起。因此必须先启动监听进程再配置Nginx写入。4.3 开机启动项管理systemd vs rc.local的生死抉择搜索热词“开机启动项cmd命令”暴露了Windows思维惯性。Linux中rc.local是遗留方案SysV init时代Ubuntu 16.04、Kali 2020.1默认启用systemdrc.local已被弃用。强行启用会导致systemctl status rc-local显示failed/etc/rc.local中的命令可能在关键服务如network启动前执行导致网络不可用权限问题rc.local以root执行但脚本内su - user -c command可能失败。正确方案为每个服务创建独立的systemd unit文件。例如让Python脚本/home/user/myscript.py开机自启# 创建service文件 sudo tee /etc/systemd/system/myscript.service EOF [Unit] DescriptionMy Python Script Afternetwork.target [Service] Typesimple Useruser WorkingDirectory/home/user ExecStart/usr/bin/python3 /home/user/myscript.py Restarton-failure RestartSec10 [Install] WantedBymulti-user.target EOF # 启用服务 sudo systemctl daemon-reload sudo systemctl enable myscript.service sudo systemctl start myscript.service关键参数解析Afternetwork.target确保网络就绪后再启动Useruser以普通用户身份运行避免root权限滥用Restarton-failure进程退出码非0时重启RestartSec10重启前等待10秒防雪崩。验证方法# 查看服务状态 sudo systemctl status myscript.service # 查看启动日志比journalctl -u更精准 sudo journalctl -u myscript.service -f # 模拟崩溃测试 sudo pkill -f myscript.py # 观察是否在10秒后自动重启Kali特例其预装的kali-autostart服务会自动启用metasploit、postgresql等若你禁用postgresql需sudo systemctl disable postgresql否则kali-autostart会强制启动。5. 日志管理层从海量文本到精准告警的四层过滤5.1 Kali与Ubuntu日志策略的致命差异Kali默认启用rsyslogjournalctl双日志系统且/var/log/下日志文件极多Ubuntu Server默认仅用rsyslogUbuntu Desktop则优先journalctl。这种差异导致Kali/var/log/auth.log记录SSH登录、/var/log/kern.log记录内核事件、/var/log/apache2/access.log记录Web访问但journalctl可能覆盖部分记录Ubuntujournalctl是唯一权威日志源/var/log/syslog只是journal的文本快照且默认启用日志轮转logrotate每周压缩归档。核心矛盾Kali日志更“原始”Ubuntu日志更“结构化”。Kali的auth.log是纯文本grep即可Ubuntu的journalctl是二进制索引需用-o json导出结构化数据。统一排查框架确定日志源ls /var/log/看文件存在性sudo journalctl --disk-usage看journal占用选择查询工具Kali优先grepawkUbuntu优先journalctljq设置日志保留策略Kali用logrotateUbuntu用journalctl --vacuum-time2weeks。实战对比查SSH暴力破解尝试Kalisudo grep Failed password /var/log/auth.log | awk {print $11} | sort | uniq -c | sort -nr | head -10 # 输出123 192.168.1.100Ubuntusudo journalctl -u ssh --since 1 hour ago | grep Failed password | \ sed -n s/.*from \([^ ]*\).*/\1/p | sort | uniq -c | sort -nr | head -105.2 日志轮转logrotate的魔鬼细节为什么日志没删反而更大搜索热词“ubuntu官网镜像下载”关联到日志膨胀问题。logrotate配置不当会导致日志文件被重命名但未压缩/var/log/syslog.1、/var/log/syslog.2堆积copytruncate选项误用导致日志丢失因截断时可能有进程正写入delaycompress未启用压缩与轮转不同步。标准/etc/logrotate.d/rsyslog配置解析/var/log/syslog { rotate 7 # 保留7个归档 daily # 每日轮转 missingok # 文件不存在不报错 notifempty # 空文件不轮转 delaycompress # 轮转后延迟压缩避免丢失写入 compress # 启用gzip压缩 sharedscripts # postrotate脚本只执行一次 postrotate /usr/lib/rsyslog/rsyslog-rotate endscript }危险配置示例# 错误未设compress → 归档文件不压缩磁盘爆满 /var/log/myapp.log { rotate 30 daily } # 正确强制压缩且用zstd替代gzip压缩率更高 /var/log/myapp.log { rotate 30 daily compress compresscmd /usr/bin/zstd uncompresscmd /usr/bin/unzstd }Kali特例其/etc/logrotate.d/kali配置中/var/log/installer/syslog默认rotate 0不保留归档因安装日志只需临时查看。5.3 实时日志监控tail -f的替代方案与告警集成tail -f /var/log/auth.log是入门操作但生产环境需多文件监控multitail /var/log/auth.log /var/log/syslog关键词高亮grep --coloralways Failed\|error /var/log/auth.log | tail -n 20告警触发当10分钟内SSH失败超5次发邮件或Telegram通知。自动化告警脚本ssh_guard.sh#!/bin/bash LOG_FILE/var/log/auth.log THRESHOLD5 WINDOW600 # 10分钟 ALERT_FILE/tmp/ssh_alert_$(date %s) # 统计最近10分钟失败次数 FAIL_COUNT$(awk -v now$(date %s) -v window$WINDOW BEGIN { count0 } /Failed password/ { if ($0 ~ /([0-9]{4}-[0-9]{2}-[0-9]{2}T[0-9]{2}:[0-9]{2}:[0-9]{2})/) { # 解析ISO时间戳 gsub(/T/, , $0) cmd date -d \ $1 $2 \ %s 2/dev/null cmd | getline ts close(cmd) if (ts now - window) count } } END { print count } $LOG_FILE) if [ $FAIL_COUNT -ge $THRESHOLD ]; then if [ ! -f $ALERT_FILE ]; then echo ALERT: SSH brute force detected ($FAIL_COUNT attempts) | \ mail -s SECURITY ALERT adminexample.com touch $ALERT_FILE fi else rm -f $ALERT_FILE fi部署为cron任务# 每5分钟检查一次 (crontab -l 2/dev/null; echo */5 * * * * /home/user/ssh_guard.sh) | crontab -实操心得Kali中/var/log/auth.log时间戳格式为MMM DD HH:MM:SS如Jan 01 12:34:56Ubuntu为YYYY-MM-DD HH:MM:SS脚本需适配。我用awk的strftime()函数统一处理但更稳妥方案是用journalctl——因其时间戳格式统一。6. 常见问题与排查技巧实录237次重装系统换来的12条铁律6.1 dpkg锁冲突另一个进程已为dpkg前端锁加锁报错dpkg: 错误: 另外一个进程已经为 dpkg 前端锁 加锁本质/var/lib/dpkg/lock文件被占用通常因apt进程意外终止锁未释放unattended-upgrades后台服务正在运行用户同时开多个终端执行apt。绝对禁止sudo rm /var/lib/dpkg/lock破坏dpkg数据库正确流程查找占用进程sudo lsof /var/lib/dpkg/lock若无进程占用检查/var/lib/dpkg/lock-frontendsudo lsof /var/lib/dpkg/lock-frontend若仍无结果确认unattended-upgrades状态sudo systemctl status unattended-upgrades强制终止sudo systemctl stop unattended-upgrades sudo killall apt apt-get清理锁sudo rm /var/lib/dpkg/lock*修复dpkg状态sudo dpkg --configure -a更新sudo apt update sudo apt upgrade。铁律1Kali中apt锁冲突率高于Ubuntu因其预装工具常触发依赖更新。我的解决方案是alias aptsudo apt -o DPkg::Lock::Timeout600将锁等待时间从60秒延长至10分钟。6.2 Ubuntu微信无法启动容器权限与字体渲染的双重陷阱报错ubuntu微信启动后无窗口ps aux | grep wechat显示进程存在但xwininfo查不到窗口。根因容器权限微信Linux版用Electron打包需访问/dev/shm共享内存而Ubuntu Snap安装的微信被AppArmor限制字体缺失微信依赖Noto Sans CJK字体Ubuntu桌面版默认不安装。解决方案# 卸载Snap版安装deb版 sudo snap remove wechat wget https://github.com/geeeeeeeeek/electronic-wechat/releases/download/V2.3/electronic-wechat-linux-x64.tar.gz tar -xzf electronic-wechat-linux-x64.tar.gz sudo apt install fonts-noto-cjk # 启动时指定共享内存 ./electronic-wechat --disable-gpu --shm-size512m铁律2Kali中微信几乎无法运行因其无GUI环境或X11转发配置。红队人员应改用telegram-desktop或signal-desktop它们对Kali兼容性更好。6.3 ChatGPT桌面端无窗口GPU加速与Wayland的兼容性墙报错chatgpt 桌面端启动之后只有进程没有窗口本质Electron应用在Wayland会话中默认禁用GPU加速导致渲染线程卡死。Ubuntu 22.04默认WaylandKali默认X11。验证echo $XDG_SESSION_TYPE→waylandorx11修复临时chatgpt-desktop --disable-gpu永久编辑/usr/share/applications/chatgpt-desktop.desktop在Exec行末尾加--disable-gpu终极切换回X11会话登录界面点击齿轮图标选“Ubuntu on Xorg”。铁律3所有Electron应用VS Code、Slack、Discord在Wayland下均有此问题。我的经验是开发用X11演示用Wayland——因X11兼容性更好Wayland安全性更高。6.4 VMware虚拟机安装Ubuntu卡在黑屏显卡驱动与EFI固件的博弈现象VMware Workstation安装Ubuntu时GRUB菜单后黑屏光标闪烁。根因VMware虚拟显卡SVGA II与Ubuntu 22.04的nou