Chinavasion 掌上投影仪
如今看来,Linux 似乎可以运行在所有设备上,从手机到电视,正如我在 2010 年 8 月的专栏文章中展示的那样,它甚至可以驱动冰箱。事实上,我敢打赌,许多 Linux 用户对此已经习以为常,甚至期望电子设备内部都搭载 Linux——我知道我是这样的。即便如此,当我听说 Chinavasion 出售的一款运行 Linux 的掌上投影仪时,我还是感到惊讶和好奇 (www.chinavasion.com/product_info.php/pName/mini-projector-with-wifi-wireless-remote)。一旦我阅读了规格,发现它内置了无线网络、SD 卡插槽并支持 USB Host 模式,我就开始幻想各种可能性。当然,你可以将这款投影仪用于其预期用途——播放媒体文件——但想象一下,如果你可以访问底层的 Linux 用户空间。我知道我必须搞到一台,而且我必须尝试破解它。请继续阅读我对这款设备的评测,以及我目前为止的冒险经历的纪实。
从某种意义上说,这篇文章包含两篇评测。首先,我评测这款产品的销售版本,然后我讨论我在研究其内部构造时发现的东西。Chinavasion 非常慷慨地寄给我一台评测样机,甚至对我的破解行为持开放态度,只要我明确表示拆卸或摆弄内部构造将使保修失效。在撰写本文时,这款投影仪的售价为 235 美元,包括投影仪本身、一个红外遥控器、一个小巧的红外键盘、电源线和美国插座适配器、一个三脚架和一条 RCA 线缆。投影仪本身的规格参数如下,均来自产品页面
尺寸:137 毫米 x 77 毫米 x 23 毫米
投影仪:10 流明 LED 投影仪,分辨率 640x480
802.11b/g 无线支持
SD 卡插槽
带 USB Host 适配器支持的 USB 端口
两小时电池续航
两千小时灯泡寿命
视频:VOB、MPEG1/2/4 AVI、XVID
音频:MP3、WMA、AAC
照片:JPEG、PNG、GIF、BMP
我必须说,我对掌上投影仪仍然很陌生,它们能够将投影仪集成到如此小的空间里(图 1)让我感到惊叹。我的意思是,我可以将这款投影仪放进我的后口袋,它的大小大约相当于一包扑克牌,只是更长一些。然而,这种小尺寸是有代价的——亮度。普通的全尺寸投影仪可能拥有超过 2000 流明,而这款投影仪的亮度仅为 10 流明,只是前者的零头。这意味着你需要在相当黑暗的房间里使用它,最好是在晚上。此外,尽管网站上列出这款投影仪支持高达 70 英寸的投影尺寸,但你会发现投影仪离投影面越近,效果越好。
当你打开投影仪电源时,你首先注意到的不是亮度,而是声音。不,那不是喷气发动机的声音——那是风扇的声音。事实证明,LED 灯会变得非常热,而且任何超频玩家都知道,如果你想安静地冷却电脑,你需要一个大风扇,这样叶片就可以以较低的 RPM 旋转。当你的空间很小,必须使用小风扇时,你必须求助于非常高的 RPM,才能将足够的冷空气吸入系统。这听起来很像你在许多 1U 服务器中会听到的风扇声音。即使有风扇,你也会注意到,在投影仪开启一段时间后,金属表面会变得相当热。显然这是预期的,但我仍然不会把这款投影仪放在床上或你的腿上。幸运的是,扬声器的音量足够大,可以盖过大部分风扇噪音。我个人觉得风扇的声音很舒缓(我多年来一直睡在装有风扇且 24x7 运行的台式电脑旁边),但我认为风扇噪音会困扰一些人。
这款投影仪有一个简单的界面,你可以通过设备本身的按钮或随附的红外遥控器或键盘(图 2)进行导航。基本上,你在不同的操作模式之间左右移动,然后按 Enter 键选择特定模式。我收到的设备包含播放视频和音乐、显示照片、进行有限的视频和音乐流媒体播放的模式,并且还有一个日历和天气应用程序。我不得不说,界面本身一点也不令人印象深刻或花哨——它只是一些图标和简单的菜单,引导你找到想要播放的媒体。
这款投影仪支持相当多的媒体格式,我能够播放我刻录成 AVI 文件的电影。我遇到的唯一真正的问题是,有些视频的音量有点小,所以风扇确实会稍微盖过声音,但这会因视频而异。好处是你可以让它播放存储在 SD 卡、普通 USB 硬盘甚至其 ~400MB 板载可用空间上的媒体。由于它支持 USB 硬盘,你基本上拥有无限的存储选择,但如果他们能利用无线网卡来实现网络存储,那就更好了。该设备确实有一个流媒体应用程序,但你的选择仅限于 YouTube 和一些据推测是中国的流媒体网站。YouTube 流媒体播放效果尚可,尽管界面笨拙且有些难以使用。其他应用程序似乎也像宣传的那样工作,但只提供基本功能。
你可能已经注意到我没有提到任何演示应用程序,那是因为根本没有!这款投影仪严格来说是用于媒体播放的,所以目前,你必须从其他设备上运行演示文稿。该设备有一个端口可以连接 RCA 线缆,但那是视频输出,而不是视频输入。
无线网络可以通过设置页面进行配置,虽然界面很简单,但它确实可以正常工作,并且可以检测并连接到我的无线网络。当你进入该菜单时,你会像我一样感到兴奋,因为你注意到它不仅列出了无线,还列出了有线、GPRS/WCDMA 和 TD-SDCMA 配置;然而,这些都不是实际有效的选项,这让我怀疑为什么要将它们添加到该菜单中。
老实说。尽管他们能够在如此小的设备中集成所有这些功能很酷,但如果不是因为其内部运行着一台 Linux 计算机,我不知道我会对它有多兴奋。它在媒体播放方面表现尚可,但界面感觉不完整。以 235 美元的价格,它是一个有趣的玩具,但如果我们将评测到此为止,我不知道是否会向正在阅读本文的你们推荐它。幸运的是,这仅仅是开始。
在投影仪到货之前,我向 Chinavasion 提出的首要问题之一是如何访问界面背后的 Linux 操作系统。他们与制造商核实后表示,无法访问操作系统,因为它“硬连接到设备中”。好吧,这听起来对我来说是一个挑战,所以我的后续问题是我是否可以破解该设备。正如我之前提到但想再次重申的那样,如果你执行以下我提到的任何操作,你将失去保修,并且如果你弄坏了投影仪,Chinavasion 将不接受退货。既然我已经说过了,那就让我们开始玩得开心吧。
当投影仪到货时,我摆弄了一下常规界面,然后决定我等不及了——我必须在这个设备上获得 root 权限。从系统启动方式来看,似乎没有办法切换到不同的虚拟终端 (VT),所以我认为我获得 shell 的主要途径是通过网络。在将设备连接到我的无线网络后,我运行了端口扫描,结果你猜怎么着,端口 21 是打开的。“嗯”,我想,“他们不可能在这个设备上运行 telnet 吧。” 然而,当我连接到该端口时,我看到了漂亮的 ASCII 艺术启动画面和一个登录提示符。我准备好进行一天的暴力破解攻击,但令我惊喜的是,我可以使用 root 登录,而且没有密码。中大奖了。
在详细介绍投影仪的用户空间之前,这里是一个列出我发现的另一种 root 该设备的方法的好地方,以防未来版本不再附带启用 telnet。当我在文件系统中浏览时,我注意到一个在启动时加载的脚本,可以很容易地被利用,名为 /etc/init.d/S98z_auto_upgrade。这个脚本是 init 过程的一部分,包含以下代码
#!/bin/sh if [ -e /mnt/mmc/autorun.sh ] then chmod 777 /mnt/mmc/autorun.sh sh /mnt/mmc/autorun.sh rm -rf /mnt/mmc/autorun.sh sync reboot fi
似乎这个脚本的设置是为了让制造商可以轻松升级设备上的软件。之前的 init 脚本会扫描并自动挂载 /mnt/mmc 下的任何 SD 或 USB 驱动器。这个脚本会自动执行它在设备根目录中找到的任何 autorun.sh 文件,因此如果 telnet 被禁用(或者 root 被赋予密码),你所要做的就是创建一个 shell 脚本来运行你想要的命令。
这就是我在用户空间中发现的东西。该系统运行 2.6.10 内核和一个我以前从未见过的独特的 ARM 处理器。以下是 /proc/cpuinfo 中的一些选定行
Processor : ARM926EJ-Sid(wt) rev 5 (v5l) BogoMIPS : 124.51 Features : swp half thumb fastmult edsp java CPU implementer : 0x41 CPU architecture: 5TEJ Hardware : VIA-VT8430
该设备本身有 256MB 的 RAM 和 512MB 的闪存,分为两个分区:一个较小的分区用于 /,一个较大的、大部分为空的分区用于 /mnt/mtd。你可以在标准的 BusyBox shell 中浏览文件结构,你会看到你可能期望的标准根级目录,尽管安装的应用程序数量非常有限,自定义软件位于 /usr/dpf 下。我确实注意到它包含一个 MPlayer 版本,该版本输出到 framebuffer 并使用硬件加速进行视频解码,我觉得这很有趣。
我的简单目标是找到某种方法在投影仪上显示 shell。我想至少有了 shell,我可以ssh连接到另一台机器并运行其他应用程序。事实证明,这比我想象的要困难得多。第一个挑战是事实上没有为控制台设置虚拟终端,当我查看 /etc/inittab 时,我注意到唯一正在运行的 getty 进程是 ttyS0,我假设它是用于我从外部看不到的某个内部串口
ttyS0::respawn:/sbin/getty -L ttyS0 115200 vt100
尽管你可能认为你可以简单地运行另一个 getty 实例,但事实证明,此设备附带的 getty 版本不支持 framebuffer 输出,也没有包含另一个 getty,例如 fbgetty。现在,你们中的一些人可能会想,“内核 framebuffer 呢?” 尽管内核当然可能支持硬件 framebuffer,但它在启动时并未启用。事实上,这是完整的内核命令行
mem=244M root=/dev/mtdblock1 rootfstype=yaffs2 rw ↪noinitrd console=ttyS0,115200n8 init=/linuxrc ↪lcdbpp=16 lcdpath=GOV display=TV tvsys=NTSC loadtime=0
因为我没有找到任何正常发行版引导加载程序的证据,所以我假设这个系统使用 Uboot,因此如果没有通过 JTAG 接头串行访问设备,我将无法更改启动参数。这意味着我必须找到一个为 ARM 编译的 framebuffer getty。起初,这似乎是一项简单的任务。毕竟,Debian 已经发布 ARM 软件包很长一段时间了,而我所要做的就是找到正确的软件包并提取我需要的二进制文件。简单,对吧?
当我在投影仪上提取并尝试运行各种 ARM 编译的 Debian 二进制文件时,出现了一个常见问题——要么我的 glibc 太新,要么太旧。glibc 库是 Linux 系统的核心库之一,基本上每个 C 程序都需要运行它,而这款投影仪的版本似乎介于 Debian Etch 和 Debian Lenny 之间,前者的二进制文件无法执行,而后者的二进制文件则抱怨 glibc 有点太旧。Lenny 似乎是最接近此版本的发行版,但我真的不确定这个 Linux 安装是基于哪个发行版或版本的。libc-2.3.3.so 可能来自某些 ARM 编译的 Fedora 发行版。无论如何,在没有 glibc 支持的情况下,基本上我无法让我的大多数二进制文件运行,而且我不想冒险通过覆盖现有库来弄坏设备,所以我不得不寻找不同的方法。
我的下一个计划是找到一个小的基于 Debian Lenny 的 ARM 发行版,这样我就可以将完整的根文件系统复制到 400MB 的 /mnt/mtd 分区。然后,我就可以 chroot 到其中并运行我想要的命令。这样,所有命令都将使用该 glibc,并且我可以添加额外的 ARM 编译的 Lenny 软件包。我很快遇到的问题是,好吧,chroot 发生了段错误。投影仪上包含的 chroot 二进制文件和我 Lenny 安装中的版本都无法工作。
此时,我开始回忆起 LD_LIBRARY_PATH、LD_PRELOAD 和其他变量,我可以使用它们来告诉二进制文件使用我安装在 /mnt/mtd 下的库版本。事实证明,这让我取得了更大的进展。我可以启动ls以及许多其他控制台应用程序,包括像 strace 和 lsof 这样的实用程序;然而,fbgetty 在 Debian Lenny 之前就被放弃了,所以我不得不尝试 Lenny 中的其他 framebuffer 终端应用程序,例如 jfbterm。该应用程序会启动,但似乎永远无法附加到它想要的 tty,最终会报错。在尝试了一些方法,包括将 /dev/console 上的权限更改为更宽松之后,我暂时放弃了,并关闭了投影仪。
下次我打开投影仪时,启动画面开始显示其滚动的进度条,但在一两分钟后,进度条似乎冻结了,系统没有响应。太棒了,我把它弄坏了。但是怎么弄坏的?毕竟,我只是在基本上为空的挂载点上添加了一些文件,并更改了 /dev/console 上的权限。至少,这就是我能记得做的所有事情。此时,我不确定该怎么办。我不想拆开设备(至少现在还不想),所以我重启了几次,试图看看是否可以获得任何信息。我想到的一件事是,系统可能需要我填满的 /mnt/mtd 中的所有空间,或者可能我更改 VT 的所有操作都可能以某种方式被记住(即使这似乎不太可能)。
此时,我想起了自动升级设备的 init 脚本,所以我决定制作一个带有测试脚本的 USB 密钥,该脚本会将文件写回 USB 驱动器。如果这可行,我可以只用 USB 密钥连续启动设备,并构建一个可以修复我可能造成的任何损坏的脚本。不幸的是,当我尝试这种方法时,我注意到设备似乎没有进入启动过程——脚本似乎从未运行。
接下来,我决定连接一个 USB 键盘,看看系统是否甚至加载了内核。结果证明键盘确实可以工作,因为 Caps-Lock 键亮起,并且在正确的时间按下 Ctrl-Alt-Del 确实重启了设备。不幸的是,当系统冻结时,键盘也冻结了。此时,我尝试了启动期间的所有键盘组合来来回切换 VT,试图通过 Ctrl-C 终止一些可能已停止的脚本,并通过某种神奇的巫术,无论是我在键盘上敲击了什么,还是像我开始怀疑的那样,硬件上的某些东西再次开始工作,最终系统完全启动了。
在我松了一口气之后,我意识到我需要立即备份文件系统,这样我就有了一些关于其中内容的记录。我还决定取下外壳,看看是否可以在硬件上找到串口并访问启动提示符和启动消息。如果你看图 3,你可以看到设备主板的底部,在图片的顶部是一个小的五针白色连接器,标记为 Program,我假设它是某种串行接口。不幸的是,这个连接器非常小,所以我还没有找到兼容的连接器来测试这个理论。图 4 显示了主板的顶部——如果你只是拧下螺丝并抬起投影仪的顶部,你就会看到它。当我查看电路板时,我注意到额外的 USB 端口和 VGA 的额外焊接点。更有经验的硬件黑客可能会在他们查看电路板后发现更有趣的东西。
不幸的是,在我拆开它之后,我在启动时遇到了同样的进度条冻结问题。在多次重启之后,我终于以某种方式让它完全启动,但从那时起,我又经历过几次同样的问题。最终,系统会启动,但到目前为止,我一直无法追踪到问题的根源。此时,我倾向于认为是设备上的某种短路。
Kyle Rankin 是旧金山湾区的系统架构师,也是多本书籍的作者,包括The Official Ubuntu Server Book、Knoppix Hacks 和 Ubuntu Hacks。他目前是 North Bay Linux Users' Group 的主席。