Macbook pro 8,1引导ubuntu的方法

按理说,在macbook中安装ubuntu应该像在macbook中安装windows一样简单,刻张光盘,然后引导就是了,可是偏偏2011年的MBP机型使用的硬件使用现有各种版本的ubuntu都引导不起来(包括linux3.0内核的ubuntu 11.10 beta1)。如果简单地使用光盘引导,在splash screen之后就会看到:

“(initramfs) Unable to finda medium containing a live file system”

这个问题困扰了我很久,在ubuntu.org.cn的论坛中提问也没有得到满意的答案。后来在国外网站上google了很久,才发现这是Linux内核在这个主板上面的一个bug,引导一半之后,系统就不认识光驱了。这个bug至今还没解决。

不过国外论坛上面已经有人给出了一个非常山寨,但是可行的解决办法,这个方法的操作如下:

解压ubuntu的iso镜像,将里面的文件全部拷贝到U盘里(注意ubuntu 11.10采用了新的技术,可能使mac os x认为iso镜像是损坏的,只能自己想办法把里面的内容提取出来了)。然后插着U盘开始用刻录好的ubuntu的光盘引导。引导到一半,系统不认识光驱了,但是它会发现U盘里存有live CD的文件,于是开始从U盘读取文件了,这样就能顺利地进入Ubuntu,并且可以进行安装。

当然,这只是在Mbp中使用linux的起点,安装好Ubuntu之后,你会发现各种各样的驱动问题。Ubuntu 11.10 beta1开始有专门的for mac版本,看说明似乎是对mac电脑进行过优化,所以推荐使用这个版本的镜像。就我今晚的测试来看,键盘和摄像头的驱动是可用的,无线网卡驱动无法找到,google了一下发现现有的内核还没法支持这个网卡,触摸板驱动是正常的,但是触摸板在Ubuntu下面的表现跟一坨屎一样,不知道怎么调整。

That’s all. Enjoy yourself.

玩玩XBMC

之前我的华硕笔记本屏幕坏掉以后一直想把它专用为电影播放器,接我房间里的那个电脑。

一开始我是直接进windows,用无线鼠标控制电脑进行播放。但是这样看电影非常非常不爽,因为windows的文件管理器字都非常小,坐在床上基本看不见,而无线鼠标距离一远也有点失灵。

最近在做ST的那个项目的时候,把之前玩过的XBMC又拿出来做例子,于是萌发了用XBMC配置一个真正的HTPC的想法。由于XBMC是全平台支持的,而我也是主要使用Linux的,所以可以完全抛开windows建立这个HTPC。

安装XBMC是很简单的,我使用ubuntu,所以只要添加PPA源就行。不过stable的XBMC是不支持ubuntu 11.04的,必须使用unstable版本。当然,XBMC是有Live CD的,是基于Ubuntu 10.04的。不过我拿来跑的时候不知道怎么连接无线网络。而且它的安装方式是alternative的,我用U盘引导时会找不到光盘(光驱是彻底坏了)。所以干脆在原来的ubuntu基础上装一个XBMC。

装好XBMC之后,还要做一些配置,否则中文是没办法显示的,最简单的办法就是找到系统里面文泉驿微米黑的ttc文件,复制到xbmc的配置目录的Media/fonts下面,并且改名为arial.ttc。并且在XBMC中设置字体为arial based(不知道这步是不是多余)。然后在就可以把language调成简体中文了。并且顺带在视频的选项里面把字幕编码改成GBK,这样字幕不会乱码了。

做完这些步骤把电脑接到电视机上面就行了。接下来就遇到遥控的问题。我不知道MCE的遥控器是不是能够工作,反正我没这个玩意儿。Google了一下,发现XBMC有android手机遥控软件,通过局域网就能遥控XBMC工作了。下载了一下蛮好用的。

另外,XBMC还支持从uPnP media server上面读取多媒体文件。所以我也试了一下配一台media server。

Media server依旧是Linux配置,也是使用了ubuntu 11.04。用的软件是MediaTomb。这个软件在ubuntu的软件源里面是有的。安装之后发现UI没开,得修改/etc/mediatomb/config.xml:

<ui enabled=”yes” show-tooltips=”yes”>

<transcoding enabled=”yes”>

接下去打开软件,就能出来web ui界面。可以添加文件到数据库。而客户端的XBMC能够自动检测到upnp服务器,到时候添加目录就是了。

Linux下mp3乱码问题最佳解决方案及其原理

要说mp3乱码的问题,首先要从乱码的源头说起。

为什么播放器能识别一首歌的歌名、艺术家、专辑等内容,即便你的文件名是乱打的。这是因为mp3文件里面有ID3tags这么一个东西(MP3文件曲目标签)。

wikipedia:

ID3是一种metadata容器,多应用于MP3格式的音频文件中。它可以将相关的曲名、演唱者、专辑、音轨数等信息存储在MP3文件中。

ID3有两个版本,分别是ID3V1和ID3V2。

windows系统本身只支持ID3V1这个版本。对于ID3V2,在系统自带的软件中都是忽略不计的。所以,如果一首歌只有ID3V2而没有ID3V1的话,用windows media player,或者别的一些windows软件(比如real player),都不能显示出歌曲的信息。不过很多比较流行的软件,比如千千静听,是能识别出ID3V2的。而在linux下面,默认是支持ID3V2的。

图1:本歌有ID3V2,没有ID3V1,windows无法识别ID3V2.

乱码问题就出在对ID3的编码上面。windows默认是GB2312编码,而linux却是UTF-8编码。中国绝大多数的MP3都是给windows用户使用的,所以绝大多数的MP3都会使用GB2312来编码ID3。这就造成了乱码。

早些时候,网上搜索linux乱码问题,给出的答案都是把ID3转成UTF-8格式,这样在linux下面就不会乱码。但是这样做有一个很大的副作用——就是在windows下面,这些MP3就乱码了。所以把ID3V1和V2全部转成UTF-8格式显然不是万全之策。

要让MP3在windows下面和linux下面都不乱码,解决办法是ID3V1和ID3V2使用不同的编码。

现在的linux播放器,以及主流的支持ID3V2的windows播放器在读取ID3的时候都遵照先读V2,再读V1的顺序。而且,windows下主流播放器,比如千千静听等,是支持UTF-8编码的识别的。所以要让MP3在两个系统下都不乱码,只要解决windows media player和linux播放器的乱码问题就行了。

图2:千千静听的MP3标签读取优先级

根据以上,可以分析出,出现乱码的情况无外乎以下几种:

  • linux下乱码:
    • ID3V2为GB2312编码,ID3V1为任意编码;//由于播放器的V2优先,所以读取了GB2312编码的V2标签,导致乱码。
    • ID3V1为GB2312编码,ID3V2缺失;//此时没有V2,所以只能读取V1。
  • windows下乱码:
    • ID3V1为UTF-8编码;//windows media player不支持V2,故读取V1
    • ID3V1缺失;//windows media player无法读取任何歌曲信息。

 

所以,只要把ID3V2编码为utf-8,而将ID3V1编码成GB2312,就可以达到都不乱码的效果。

要将现有的音乐批量用上述组合编码,我使用linux下面的kid这个软件。

打开软件,首先进行设置(settings)。将ID3V1和ID3V2分别指定为GB18030和UTF-8。

图3:kid设置

接下来,用kid打开MP3文件。如果发现右边TAG任何一部分有乱码,说明这个MP3tag需要转码。

图4:需要转码

由于绝大部分的MP3都是有GB2312编码的ID3V1.所以将所有的歌选中,在右边栏里的TAG2下面,点击from tag1。

图5:批量操作

然后将他们保存。这样就可以看见所有的歌曲都拥有V1和V2的标签,并且都不乱码了,此时V1已经用GB18030编码,V2用UTF-8编码。在win和lin都不会乱码了。

Linux使用puff的非wine方法

puff实质上就是ssh,只不过它支持443端口连入。这样做就很好,除非TG全面封锁了443端口(也就是名正言顺地封锁HTTPS),否则就不会有问题。

之前在linux下面用puff,我都是用很2的方法:就是wine一下puff的windows客户端。然后用windows的方法穿越。这样有很大的风险,比如wine了以后就有中windows病毒的风险,puff这个软件本身也不开源,也有危险。

既然是ssh,在linux下面总有办法搞出ssh tunnel的。其实一个命令就行了,但是我一直没成功,主要原因是我在ff上面都配成了http代理,而事实上应该使用socks代理才对。

下面,就完整地示范一下怎么连:这里使用了gstm,图形化界面。不过gstm不记密码的,很恶心。

如上图,配好账户。login是登录名,密码不用设,privkey可以不用设,我这里设成密码,因为gstm不能保存密码,所以我在这里打上以便提示。下面的端口转发,选择dynamic,port为7070(这个也可以设别的,主要是浏览器上面设置代理要跟这个一样)。后面两个都是n/a。

这样就设好了gstm。然后点击start,提示输入密码,puff就连接好了。

接下来设置浏览器就至关重要。

ff设置里面,http proxy什么都不要设置,只设置socks v5就行了

到这一步,看似设置好了,其实不然(之前也上当了,所以还是没穿越)。问题在于,虽然这里指明了socks v5,但是ff貌似还是没用remote dns。所以DNS污染依然起作用。

办法就是在地址栏输入about:config,讲里面的dns设置设置成下图的模式:

至此,穿越设置完成。

 

模拟LRU页面请求

长久没编C++了,指针什么全乱指,搞到后面都segmentation fault了,然后用netbeans终于调好了。

 

用栈的LRU算法,原样模拟LRU算法用的硬件栈变化情况。

my_stack.h:

 

my_stack.cpp

 

 

main.cpp:

 

关于linux c的wait(int *status)函数

上操作系统课的时候,老师举例linux进程时说了wait函数,当时老师说wait(args)函数里面的参数的意思是等待指定时间,过了这个时间之后就不等待了。起初也没什么异议,因为我知道java的线程里面wait()确实是这样用的。但是今天编了一点程序,就发现完全不是这样的。

我编了这么一个程序:

 

那么,如果wait(2)的意思真的是等待3秒的话,在child wakes up语句执行之前,parent应该会被唤醒。但是事实并非如此,在子进程完全执行完毕之后,父进程才被唤醒,而且s的值是-1,也就是失败的意思。

然后看了wait()函数的说明,发现确实里面的参数完全不是等待时间,而是一个int型指针。所以,wait(3)这样的调用根本是不对的。

在此,我发现了一个linux C语言很奇怪的现象,wait函数明明是在<sys/wait.h>里面,但是我根本没有include它,却居然也能用。只不过编译的时候会出现|warning: implicit declaration of function ‘wait’|。也就是说,编译器会自动的隐式的把这个头文件给include进去。这样编译器看起来很智能,可惜编译器智能的还不够,因为它之后就忘了检查函数的参数类型了。于是wait(3)这样的语句居然就通过编译了,而且显然调用是出错的,返回值是-1.

于是我把#include<sys/wait.h>显式地写在文件里,一编译,wait(3)马上报错,参数不对。恩。这个应该是c语言编译器的问题了。

那么wait(int *status)的参数到底是什么呢?经过我查阅资料,大致认为是这样的:

wait()函数应该会返回两个东西,一个是子进程的pid,另外是子进程退出的时候的状态。由于return只可能出一个值,所以另外一个值得通过指针参数对外部变量值修改,由这个status外部变量体现出子进程退出的状态。

比如我子进程是正常退出,而且退出的时候运行的是exit(5).那么在父进程中,有这么一段话:

 

这样,c_pid就等于子进程的id,status是对应于子进程执行exit(5)后的一个值,这个值不是5,因为它不仅要返回exit的值,而且要返回是正常退出还是非正常退出。

从status中,可以判断出很多东西,当然不许要自己判断。linux提供了8个宏来判断这个status代表的意思。

比如要知道子进程exit()的值,就要用WEXITSTATUS(status)这个宏。

接着上面:

 

最后给出完整的测试程序:

 

 

另外,实验书上,有wait(0);这样调用的。这样调用是对的,等同于wait(NULL);,但是wait(非0数)一定是错的。