移植内核过程中出现界面卡在"Uncompressing Linux... done, booting the kernel."

本文解决了Linux内核启动过程中的多个问题,包括启动时卡住、启动参数设置、根文件系统支持等,并提供了移植步骤及注意事项。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

转载:http://blog.youkuaiyun.com/comwise/article/details/16995451

移植平台:Linux 3.4.2 Mini2440  U-Boot 2012.04.01

1.移植内核过程中出现界面卡在"Uncompressing Linux... done, booting the kernel."

在Linux内核中搜素"Uncompressing Linux... ", 找到如下

  1. Misc.c (arch\arm\boot\compressed):    putstr("Uncompressing Linux...");  
  2. Serial.txt (documentation\ia64):    No kernel output after elilo prints "Uncompressing Linux... done":  
  3. Serial.txt (documentation\ia64):    Long pause (60+ seconds) between "Uncompressing Linux... done" and  
先看代码出错处
  1. putstr("Uncompressing Linux...");  
  2. ret = do_decompress(input_data, input_data_end - input_data,  
  3.             output_data, error);  
  4. if (ret)  
  5.     error("decompressor returned an error");  
  6. else  
  7.     putstr(" done, booting the kernel.\n");  

这里可以看到解压缩是正确的,那为什么不能正常启动呢?再看搜索到的文档

  1. No kernel output after elilo prints "Uncompressing Linux... done":  
  2. - You specified "console=ttyS0" but Linux changed the device to which ttyS0 refers.  Configure exactly one EFI console  
  3.   device[3] and remove the "console=" option.  
  4. - The EFI console path contains both a VGA device and a UART. EFI and elilo use both, but Linux defaults to VGA.  Remove  
  5.   the VGA device from the EFI console path[3].  
  6. - Multiple UARTs selected as EFI console devices.  EFI and elilo use all selected devices, but Linux uses only one.  
  7.   Make sure only one UART is selected in the EFI console  
  8.   path[3].  
  9. - You're connected to an HP MP port[2] but have a non-MP UART selected as EFI console device.  EFI uses the MP as a  
  10.   console device even when it isn't explicitly selected.  
  11.   Either move the console cable to the non-MP UART, or change  
  12.   the EFI console path[3] to the MP UART.  
我扫了一眼,意思就是如果启用EFI就不需要设备,如果没有需要设置参数,我就想先设置了启动参数

set bootargs 'console=ttySAC0' 

注意:也会有其他情况,以下几种为网上的方法:

1)u-boot中的参数(console)没有传到内核。
2)u-boot的时钟设置不在405MHz,与Kernel的不一致。
3)u-boot中的Machine ID设置的与Kernel不一致。

具体可参考文章:http://blog.youkuaiyun.com/delphityro/article/details/7520629

2. 设置之后启动乱码

网上有提供说加入波特率,那就试试 set bootargs 'console=ttySAC0,115200' 

注意:这里ttySAC0,115200之间一定要有,否则还是会出错的.

3. 再试启动成功了,但是后面出现了崩溃,代码如下:

VFS: Cannot open root device "(null)" or unknown-block(0,0): error -6
Please append a correct "root=" boot option; here are the available partitions:

意思是我启动参数里面没有加入root选项,加入里面再看看

set bootargs 'noinitrd root=/dev/mtdblock3 console=ttySAC0,115200'

具体参数说明:http://blog.youkuaiyun.com/comwise/article/details/15804875

4. 启动之后发现又出现了新问题,如下

No filesystem could mount root, tried:  ext3 cramfs vfat msdos romfs
Kernel panic - not syncing: VFS: Unable to mount root fs on unknown-block(31,3)

意思就是根文件系统不支持,所以下一步需要增加根文件系统的支持:

这里需要下载网上提供的busybox1.20(这里先制作jffs2格式的根文件系统)

具体怎么移植可参考网上步骤,这里一定要参考busybox下面的README和INSTALL还有docs文件下的文件,这里要注意几点:

1)一定要有脚本inittab,在里面会进行网络的配置和根文件的挂接,

2)在上面脚本中不要忘记串口的设备,否则界面会卡在串口无初始化或者不能打开串口/dev/console之类的

3)如果使用动态链接库,需要将编译的库文件拷进去

4)就是mdev的创建,mdev是通过init进程启动的,至少需要设备文件console和null,null是在没有串口输出的后备,一定需要

以下为制作好jffs2文件后,会出现的问题

1)uboot bootargs参数设置要正确

bootargs=console=ttySAC0,115200 root=/dev/mtdblock3 rootfstype=jffs2

这里默认的启动init=/linuxrc已经在脚本中写入,所以需要;文件系统、波特率一定也要加上

2)如果这里设置了如下的bootcmd,会出现如下类似启动信息

  1. jffs2: Empty flash at 0x00438fd8 ends at 0x00439000  
  2. jffs2: Empty flash at 0x096e8474 ends at 0x096e8800  
  3. VFS: Mounted root (jffs2 filesystem) on device 31:3.  
  4. Freeing init memory: 148K  
  5. BUG: scheduling while atomic: init/1/0x00000100  
  6. Modules linked in:  
  7. [<c000dc1c>] (unwind_backtrace+0x0/0xf8) from [<c03423c8>] (__schedule+0x2ac/0x318)  
  8. [<c03423c8>] (__schedule+0x2ac/0x318) from [<c0341588>] (__mutex_lock_slowpath+0x68/0x98)  
  9. [<c0341588>] (__mutex_lock_slowpath+0x68/0x98) from [<c019b530>] (gpio_unexport+0x18/0xb4)  

由于0x30000000地址处,存有系统放置的代码,导致数据损坏,所以一定要将启动的地址设备大一些,比如32000000

注意:后期我再次烧写使用0x30000000,发现并没有出现崩溃,其实这个根本没有多大关系。
<think>我们正在处理用户关于QEMU启动OpenWrt镜像时出现的两个错误: 1. /etc/qemu-ifup: no bridge for guest interface found 2. pulseaudio设置失败 首先,我们需要理解这两个错误的含义和原因,然后提供解决方法。 错误1:/etc/qemu-ifup: no bridge for guest interface found 这个错误发生在QEMU尝试为虚拟机设置网络接口时。QEMU使用一个脚本(通常是/etc/qemu-ifup)来在宿主机上配置网络桥接。这个错误表明脚本无法找到可用的桥接接口。 可能的原因: - 宿主机上没有配置网络桥接。 - 桥接接口的名称与脚本中期望的不匹配。 - 执行脚本的用户权限不足(通常需要root权限)。 错误2:pulseaudio设置失败 这个错误与音频设备有关。QEMU尝试使用PulseAudio作为音频后端,但可能由于PulseAudio服务未运行或配置问题导致失败。 可能的原因: - 宿主机上未安装PulseAudio。 - PulseAudio服务未运行。 - 权限问题(用户没有访问PulseAudio的权限)。 接下来,我们分别提供解决方法。 对于错误1:网络桥接问题 步骤1:检查宿主机上的桥接配置 在宿主机上,我们可以使用以下命令检查现有的桥接接口: ```bash brctl show ``` 或者(如果使用iproute2): ```bash ip link show type bridge ``` 如果没有桥接接口,我们需要创建一个。 步骤2:创建桥接接口(以br0为例) 创建桥接接口并添加物理接口(例如eth0)到桥接中。注意:这可能会暂时中断网络连接。 编辑网络配置文件(以Ubuntu为例,使用netplan): 创建或编辑/etc/netplan/01-netcfg.yaml,添加类似以下内容: ```yaml network: version: 2 renderer: networkd ethernets: eth0: dhcp4: no bridges: br0: interfaces: [eth0] dhcp4: yes ``` 然后应用配置: ```bash sudo netplan apply ``` 或者,手动创建(临时): ```bash sudo ip link add name br0 type bridge sudo ip link set br0 up sudo ip link set eth0 master br0 ``` 步骤3:确保QEMU使用的网络脚本正确 QEMU通常使用/etc/qemu-ifup和/etc/qemu-ifdown脚本。检查/etc/qemu-ifup脚本,确保它能够识别你创建的桥接接口(如br0)。 一个简单的/etc/qemu-ifup脚本示例: ```bash #!/bin/sh # 脚本参数:网络接口名(由QEMU提供) if [ -n "$1" ]; then # 将接口添加到桥接br0 sudo ip link set $1 up sudo ip link set $1 master br0 exit 0 else echo "Error: no interface specified" exit 1 fi ``` 确保脚本有执行权限,并且使用QEMU时以root权限运行(或者使用sudo)或者配置sudoers免密执行相关命令。 步骤4:运行QEMU时指定网络参数 在启动QEMU时,确保指定了正确的网络选项。例如: ```bash qemu-system-x86_64 -net nic -net tap,script=/etc/qemu-ifup ... ``` 或者使用更现代的选项: ```bash qemu-system-x86_64 -device virtio-net-pci,netdev=net0 -netdev tap,id=net0,script=/etc/qemu-ifup ... ``` 对于错误2:PulseAudio设置失败 步骤1:检查PulseAudio服务 确保宿主机上安装了PulseAudio并且服务正在运行: ```bash pulseaudio --check ``` 如果返回非0,可以尝试启动: ```bash pulseaudio --start ``` 步骤2:权限配置 确保当前用户有权限使用PulseAudio。通常,用户需要是audio组的成员。 检查用户组: ```bash groups ``` 如果没有audio组,添加用户到audio组: ```bash sudo usermod -aG audio $USER ``` 然后重新登录。 步骤3:配置QEMU使用正确的音频后端 如果不需要音频,可以直接在QEMU中禁用音频设备。但OpenWrt通常不需要音频,所以禁用可能是最简单的方案。 在QEMU启动参数中,可以禁用音频: ```bash -soundhw none ``` 或者不添加任何音频设备。 如果希望保留音频,可以尝试使用其他音频后端,例如ALSA: ```bash -audiodev alsa,id=audio0 -device ich9-intel-hda -device hda-output,audiodev=audio0 ``` 但是,对于OpenWrt镜像,通常不需要音频设备,所以禁用是最佳选择。 综合解决方案: 1. 配置宿主机桥接网络,并确保/etc/qemu-ifup脚本正确设置。 2. 在启动QEMU时,使用正确的网络参数,确保脚本被调用。 3. 禁用音频(推荐)或者修复PulseAudio配置。 示例启动命令(禁用音频): ```bash qemu-system-x86_64 \ -M pc \ -nographic \ -drive file=openwrt.img,format=raw \ -device virtio-net-pci,netdev=net0 \ -netdev tap,id=net0,script=/etc/qemu-ifup \ -soundhw none ``` 注意:如果使用非root用户运行QEMU,需要配置sudo权限来执行网络脚本中的命令(如ip命令),或者使用qemu-bridge-helper(推荐)。 另外,关于qemu-bridge-helper: QEMU提供了一个更安全的方式来管理桥接网络,即使用qemu-bridge-helper。配置方法: 步骤1:创建配置文件/etc/qemu/bridge.conf ```bash allow br0 ``` 步骤2:在QEMU启动参数中使用: ```bash -netdev bridge,id=net0,br=br0 -device virtio-net-pci,netdev=net0 ``` 这样就不需要/etc/qemu-ifup脚本了。 总结: 我们提供了两个错误的详细原因和解决方法。用户可以根据实际情况选择配置桥接网络和禁用音频设备(或修复音频)来解决。 最后,生成相关问题: 1. 如何为QEMU虚拟机配置桥接网络? 2. QEMU中如何禁用不需要的硬件设备(如音频)? 3. 如何解决QEMU中PulseAudio的权限问题? 4. 使用qemu-bridge-helper有什么优势? 5. OpenWrt镜像在QEMU中运行还需要哪些特殊配置?</think>### QEMU启动OpenWrt镜像错误分析与解决 #### 错误1:`/etc/qemu-ifup: no bridge for guest interface found` **原因分析** 此错误表明QEMU无法为虚拟机找到有效的网络桥接接口。当使用`-net tap`参数时,QEMU会调用`/etc/qemu-ifup`脚本配置宿主机网络桥接,但未找到可用的桥接设备[^1]。 **解决方案** 1. **创建网络桥接** 在宿主机上创建桥接接口(如`br0`)并绑定物理网: ```bash sudo ip link add name br0 type bridge sudo ip link set eth0 master br0 # eth0替换为你的物理网名 sudo ip link set br0 up ``` 2. **配置脚本权限** 确保`/etc/qemu-ifup`脚本有可执行权限: ```bash sudo chmod +x /etc/qemu-ifup ``` 3. **使用qemu-bridge-helper(推荐)** 修改QEMU启动参数: ```bash -netdev bridge,id=net0,br=br0 -device virtio-net-pci,netdev=net0 ``` 创建配置文件允许桥接: ```bash echo "allow br0" | sudo tee /etc/qemu/bridge.conf ``` #### 错误2:PulseAudio设置失败 **原因分析** 通常因宿主机未运行PulseAudio服务或权限不足导致,常见于无桌面环境的服务器系统[^2]。 **解决方案** 1. **禁用音频设备(推荐)** 在QEMU启动参数中添加: ```bash -soundhw none ``` OpenWrt作为路由器系统通常无需音频支持。 2. **修复PulseAudio服务** 若需保留音频: ```bash # 启动PulseAudio服务 pulseaudio --start --exit-idle-time=-1 # 添加用户到audio组 sudo usermod -aG audio $USER ``` 3. **改用ALSA后端** 替换音频驱动: ```bash -audiodev alsa,id=audio0 -device ich9-intel-hda -device hda-output,audiodev=audio0 ``` --- #### 完整启动示例 ```bash qemu-system-x86_64 \ -M virt -nographic -m 512 \ -drive file=openwrt.img,format=raw \ -netdev bridge,id=net0,br=br0 \ -device virtio-net-pci,netdev=net0 \ -soundhw none ``` #### 关键验证步骤 1. 检查桥接状态: ```bash ip link show br0 ``` 2. 确认镜像网络配置: ```bash fdisk -l openwrt.img # 确保包含网络驱动 ```
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值