2007年12月27日

最近在IBM的网站上看到一些有趣的东西,链接如下,方便自己以后查找

http://www.ibm.com/developerworks/cn/linux/l-lob800-1.html?S_TACT=105AGX52&S_CMP=NL&ca=dnl-cn-12192007

2007年01月22日

摘至IBM, 原文URL:http://www.ibm.com/developerworks/cn/opensource/os-linuxthinkpad/index.html?ca=dwcn-newsletter-opensource

 

级别: 中级

Nathan Harrington (haringtn@us.ibm.com), 编程人员, IBM

2007 年 1 月 15 日

通过修改内核以在受震动导致内核出现紧急情况时自动重置 Linux 膝上型计算机,让您的计算机处于受保护的状态。在内核空间和用户空间中实现震动检测算法,从而执行自动关闭并在特定动力条件得到满足时重新启动。

2003 年,IBM® 开始销售在商业操作系统中集成了加速度传感器及相关软件的 ThinkPad 膝上型计算机,以便在 ThinkPad 坠地时对硬盘进行保护。来自 IBM 和其他地方的富有魄力的计算机程序高手们已经为 Linux 内核开发了利用这些传感器的模块。膝上型计算机的屏幕显示方向、桌面切换、甚至是游戏控制和实时 3D 模型等特性均已实现。

2006 年中期,适用于 Linux 膝上型计算机的基于敲击的命令开始可用于用户空间 Perl 脚本(与内核空间中的基于 C 的代码相对),允许用户运行基于特定敲击序列的随机命令。本文描述了修改 Linux 内核以添加经常需要的功能的过程:对物理输入做出反馈。当 Linux 内核出现紧急情况时,用户可以震动计算机(或对膝上型计算机执行开发人员可配置的任意次数的物理移动),计算机将重置。

本文还介绍了在非紧急情况模式下执行正常关闭的方法。例如,如果用户不注意将计算机放在尚未拉好的计算机包中,则需要计算机检测到正常行走或开车的动作,并关闭计算机。

先决条件

硬件

许多在 2003 年以后(包括 2003 年)制造的 IBM ThinkPad 都配有 HDAPS 硬件。如果不能确定硬件配置,可以到 Lenovo 的 Web 站点中查看详细的技术信息。要运行以下代码,必须有 ThinkPad。某些 MacBook 配有加速度传感器及同样的通过内核访问这些传感器的通用方法。但是,此处的代码并未在 Apple 硬件上做测试,而是基于两个 IBM ThinkPad T42p 型号开发及测试的。有关如何查找在物理上支持膝上型计算机所需的 ThinkPad 硬件的链接,请参阅 参考资料

软件

本文假定您熟悉内核构建过程,并了解内核编译所带来的发行版间的不一致性。有关内核构建过程的简介,以及一些优秀的入门示例,请参阅 参考资料

从 kernel V2.6.15 起,HDAPS 驱动程序已经包含在 Linux 内核中。为了简单起见,请获取最新的内核程序。为了便于开发及管理,本文是基于 Fedora Core V5 开发的。下面用于设置内核构建环境的指导信息是专门针对 Fedora Core 的,但是一般原理适用于所有 Linux 发行版。


回页首

内核开发设置

内核配置、编译和测试

要修改内核,需要按照版本信息中的指导信息进行操作。打开 Web 浏览器并开始按照第 8.6 节:“Preparing for Kernel Development” 中的指导信息进行操作。执行到第 2 部分时,可能会在执行第二条命令 su -c 'yumdownloader --source kernel' 时遇到问题。如果该命令未能把 kernel-2.6.15-1.2054_FC5.src.rpm 软件包下载下来,请使用 wget 命令 wget ftp://ftp.linux.ncsu.edu/pub/fedora/linux/core/5/source/SRPMS/kernel-2.6.15-1.2054_FC5.src.rpm 来获取该软件包。

在执行步骤 5 时,请用 cp configs/kernel-2.6.15-i686.config .config 命令选择基本的 i686 默认配置。确保将 makefile 中的 EXTRAVERSION 部分从 -prep 更改为 -1.2054_FC5。用 make oldconfig 更新构建配置。然后用 su -c "yum install kernel-devel" 命令安装内核开发模块。该模块将用于编译紧急情况触发模块。

我们现在已经完成了 Fedora Core V5 Release Notes 文档中介绍的内核配置的相关部分。其余步骤都是所有内核构建过程通用的标准步骤。建议现在构建并安装新内核、模块和 RAM 磁盘设置以确保一切按预期运行。如果您对自己的新内核配置很有信心,可以跳过以下步骤并直接转到内核修改部分。

make 命令构建新内核。成功构建内核后,请用 su -c "cp ./arch/i386/boot/bzImage /boot/vmlinuz-2.6.15hdaps" 命令将其复制到 /boot 目录。您需要使用 su -c "make modules_install" 命令构建模块。最后一个构建步骤是用 su -c "/sbin/mkinitrd hdapsInitrd.img 2.6.15-1.2054_FC5" 命令为 HDAPS 内核创建 RAM 磁盘。用 su -c "cp hdapsInitrd.img /boot/" 命令将这个新的 RAM 磁盘复制到引导区。引导时,用以下行更新 grub.conf 文件:

清单 1. grub 配置

title Fedora Core (2.6.15hdaps)
    root (hd0,0)
    kernel /vmlinuz-2.6.15hdaps ro root=/dev/VolGroup00/LogVol00 rhgb quiet
    initrd /hdapsInitrd.img

修改 panic.c 和 hdaps.c

现在已经准备好开始一些可快速完成的内核配置。确保位于 ~/rpmbuild/BUILD/kernel-2.6.15/linux-2.6.15.i686 目录。一定要先包含 hdaps 模块作为内核的内置组件,从而准备好在计算机的运行模式中提供对各处的震动检查。

使用 make menuconfig 命令并选择 Device Drivers > Hardware Monitoring Support。键入 Y 以包含 Hardware Monitoring Support 模块,因为 HDAPS 模块依赖于此模块。滚动到清单底部,并在 IBM Hard Drive Active Protection System (hdaps) 条目的旁边再次键入 Y。退出菜单并保存配置。

打开 drivers/hwmon/hdaps.c 文件,然后将以下文本添加到 include 部分中:#include <linux/reboot.h>。并紧挨着 hdaps_read_pair 子程序后面添加下面的新子程序:

清单 2. 来自 hdaps.c 的完整的 panicShake 子程序

/*
 * panicShake - reboot the machine if shaken
 */
extern void panicShake(void)
{
 int ret, x, y; // return value and x,y from hdaps
 int int baseX = -5000; // off scale default values
 int baseY = -5000;
 int totalDev = 0; // running total of deviations from rest (shaking total)
 int devThreshold = 4000; // larger threshold for more shaking
 int dimShiftX = 150; // in case your users shake more in a certain dimension
 int dimShiftY = 150;

 while(1)
 {
  ret = hdaps_read_pair(HDAPS_PORT_XPOS, HDAPS_PORT_YPOS, &x, &y);
  if (!ret)
  {
   if( x != 0 && y != 0 )
   {
    // if its a successful read and not a zero read
    if( baseX == -5000 )
    {
     baseX = x;
     baseY = y;
    }
    if( abs(baseX - x) > dimShiftX || abs(baseY - y) > dimShiftY )
    {
     totalDev += abs(baseX - x);
     totalDev += abs(baseY - y);
    }
    if( totalDev > devThreshold )
    {
     printk(KERN_EMERG "ok, ok! you're shaking my substrate - restarting");
     emergency_restart();
    }
   }//if not a zero value
  }//if successful read of hdaps data

 }//infinite while

}//panicShake

震动检测程序就绪后,需要在系统出现紧急情况时调用该检测程序。打开 kernel/panic.c 文件,并在紧挨着 panicBlink 条件部分之前的位置上放置一个对 panicShake(); 子程序的调用。发出 make 命令。趁着对内核进行重新构建时,让我们复查一下震动检测代码。首先,设置一些变量:

清单 3. panicShake 变量

 int ret, x, y; // return value and x,y from hdaps
 int baseX = -5000; // off scale default values
 int baseY = -5000;
 int totalDev = 0; // running total of deviations from rest (shaking total)
 int devThreshold = 4000; // larger threshold for more shaking
 int dimShiftX = 150; // in case your users shake more in a certain dimension
 int dimShiftY = 150;
 

需要特别注意的是偏差阈值参数和空间移位参数。这些参数可能需要根据尝试检测的动作的独特性质做出调整。例如,如果感觉迫切需要像完成篮球传球动作一样震动计算机,可尝试减少 dimShiftX 参数以更轻松地检测垂直于计算机屏幕的动作。反过来,如果震动脉冲触发剧烈的锯齿状动作,则考虑减少 dimShiftY 参数,以便快速地检测平行于屏幕的震动并在发生进一步的损害之前重置计算机。

空间参数选择 150 及总偏差选择 4000 都旨在检测一般用户的典型震动动作。要立即响应输入,请尝试将空间移位参数减少到 10 或更少,并将总偏差参数减少到 10 或更少。这些值将导致其他类型的输入被立即识别出来,例如猛击键盘或拍打显示器外壳。

接下来,考虑无限循环语句和条件。

清单 4. panicShake hdaps 读取和基本设置

 while(1)
 {
  ret = hdaps_read_pair(HDAPS_PORT_XPOS, HDAPS_PORT_YPOS, &x, &y);
  if (!ret)
  {
   if( x != 0 && y != 0 )
   {
    // if its a successful read and not a zero read
    if( baseX == -5000 )
    {
     baseX = x;
     baseY = y;
    }

代码运行如下:其余时间里,从 Hdaps 传感器中读取当前加速度传感器读数。读数经常是不成功的或者两个值都等于 0,0,这是不能用的数据。需要避免这些虚假的 0,0 读数,来自传感器各个方向上的每 10 个读数中就会有一个读数是 0,0 —— 无效的数据,确实如此。如果是首次成功读取,则将基本参数设为第一个 x 值和 y 值。如果计算机被放在不平的表面(例如人的膝盖上)时发生紧急情况,这将允许我们更有力地检测震动或其他动作。

子程序的其余部分实现简单的震动检测算法。

清单 5. panicShake 震动检测

    if( abs(baseX - x) > dimShiftX || abs(baseY - y) > dimShiftY )
    {
     totalDev += abs(baseX - x);
     totalDev += abs(baseY - y);
     baseX = x;
     baseY = y;
    }
    if( totalDev > devThreshold )
    {
     printk(KERN_EMERG "ok, ok! you're shaking my substrate - restarting");
     emergency_restart();
    }
   }//if not a zero value
  }//if successful read of hdaps data

 }//infinite while

如果在任意方向上的空间移位大于我们先前设定的阈值,就按照两个方向上移动的量增加总偏差。然后将当前的基数设为现有的加速度级别。这样重复地重新初始化基数值要求用户持续超出空间移位值以增加检测到的总偏差。这允许用户在紧急模式下移动并存储 ThinkPad,从而安全地将机器送到系统管理员那里。如果仅需要侧立、倾斜和持拿 ThinkPad 以触发重新启动,请删除重新初始化设定。


回页首

测试 panicShake() 内核

要发动一种紧急情况,需要在内核中调用紧急情况子程序。创建以下 makefile:obj-m := panicCall.o,程序 panicCall.c 在编译时将使用该文件:

清单 6. panicCall.c 内核模块源代码

/*
 * panicCall.c - Instigate a kernel panic
 */
#include <linux/module.h> /* Needed by all modules */
#lincude <linux/kernel.h> /* Needed for KERN_INFO */

static char *pMesgStr = "PANIC SHAKE AND BAKE";

int init_module(void)
{
 printk(KERN_INFO,"panicCall module loaded\n");
 panic(pMesgStr);
 return(0);
}

void cleanup_module(void)
{
 printk(KERN_INFO,"panicCall module unloaded, beyond possible");
}

以超级用户身份用 make -C /lib/modules/$(uname -r)/build SUBDIRS=$PWD modules 命令编译 panicCall 模块。现在就有了一个可调用的模块可以使用 insmod panicCall.ko 命令触发紧急情况。如果还没有该模块则重新引导(以激活 hdaps 紧急情况下触发启用震动的内核),并运行 insmod panicCall.ko。应当会看到类似以下内容:

清单 7. 内核紧急情况堆栈

panicCall: module license 'unspecified' taints kernel.
Kernel panic - not syncing: PANIC SHAKE AND BAKE ACTIVE
 [<c011a32e>] panic+0x3e/0x174   [<f8a97017>] init_module+0xb/0xc [panicCall]
 [<c013050a>] sys_init_module+0x1382/0x1514   [<c0152413>] do_sync_read+0xb8/0xf3
 [<c012a17f>] autoremove_wake_function+0x0/0x2d   [<c01c0672>]
 	 _atomic_dec_and_lock+0x22/0x2c
 [<c0169c32>] mntput_no_expire+0x11/0x6d   [<c0102bc1>] syscall_call+0x7/0xb

现在拿起计算机,然后用力地晃动它,计算机将打印出 “shaking substrate” 消息并执行重新启动。如果您不希望晃动可能活动的磁盘驱动器,请以超级用户身份发出以下命令:

清单 8. RAM 磁盘创建和模块复制

mkdir /tmp/ramdisk0
mke2fs /dev/ram0
mount /dev/ram0 /tmp/ramdisk0/
cp /root/panicCall.ko /tmp/ramdisk0/
cp /sbin/insmod /tmp/ramdisk0/

现在有了将模块插入位于 RAM 磁盘的内核所需的两个文件。用以下部分更新 /etc/init.d/halt 脚本,将其放在刚好位于 fsck check 部分之下 halt execute 部分之上的位置:

清单 9. 修改 /etc/init.d/halt

echo "disks now mounted in readonly mode, spin down in 5 seconds";
/sbin/hdparm -S 1 /dev/hda
echo "spin down hda called, waiting 10 seconds";
sleep 10
echo "calling panic from ramdisk location";
/tmp/ramdisk0/insmod /tmp/ramdisk0/panicCall.ko

以超级用户身份执行命令 init 0 以将计算机转入关闭模式中。在调用关闭程序前,计算机将把紧急情况触发模块装入内核,并调用震动检测程序。如果在系统关闭时仔细听硬盘的声音,可以听到明显比以往更长的喀哒声,然后多普勒磁盘将随着机械臂逐渐下降的 “积载” 位置而降低并且磁盘旋转停止。再过大约五秒钟后,将从 RAM 磁盘执行紧急情况模块,而物理磁盘头仍停止不动。现在,您可以随心所欲地晃动 ThinkPad 而无需考虑磁盘的运行状况。


回页首

用户空间关闭和动作检测

很多 IT 管理员都十分怀念能够随时获知硬件物理历史记录的功能。使用同一个简单的震动检测算法、一个 Perl 脚本和一种监视策略,管理员将能够更好地跟踪硬件的状态。例如,使用下面的 Perl 脚本在计算机遭到用户震动时平稳地关闭计算机。根据用户对 ThinkPad 的操作发送一封电子邮件、闪烁 “ThinkLight” 或播放一个声音文件,这些都可以轻松地完成。

清单 10. 用于检测震动的 Perl 脚本,第 1 部分

#!/usr/bin/perl -w
# shakeShutdown.pl - shutdown (or other command) when the computer is shaken
use strict;
my $file = "/sys/devices/platform/hdaps/position";
my $baseX = -5000;
my $baseY = -5000;
my $totalDev = 0;
if( @ARGV != 1 ){ die "specify a threshold value" }
my $devThreshold = $ARGV[0];
my $dimShiftX = 150;
my $dimShiftY = 150;
while(1)
{
 open(HD,"$file") or die "can't open file";
  my $line$line$line = <HD>;
  chomp($line$line$line);
  $line$line$line =~ s/\(//g;
  $line$line$line =~ s/\)//g;
  $line$line$line =~ s/\,/ /g;
  my( $x, $y ) = split " ", $line$line$line;

正如您所见,初始的程序设置几乎与 hdaps 内核代码完全相同。正则表达式和 split 命令仅将 x 值和 y 值从 (5,4) 更改为 5 和 4。程序的其余部分实质上也是相同的:

清单 11. 用于检测震动的 Perl 脚本,第 2 部分

  if( $x != 0 >> $y != 0 )
  {
   if( $baseX == -5000 )
   {
    $baseX = $x;
    $baseY = $y;
   }
   if( abs($baseX - $x) > $dimShiftX || abs($baseY - $y) > $dimShiftY )
   {
    $totalDev += abs($baseX -$x);
    $totalDev += abs($baseY -$y);
    $baseX = $x;
    $baseY = $y;
   }
   if( $totalDev > $devThreshold )
   {
    print "threshold passed $totalDev\n";
    my $res=`/sbin/shutdown -h 1`;
   }
  }
 close(HD);
}

请注意 shutdown -h 1 命令。这将给用户提供 60 秒的时间更改方法并发出关闭中止。更改此命令以运行您最喜欢的邮件程序,用户滥用设备时可以让系统管理员知道此情况。将消息记录到系统日志中,或让 PC 扬声器发出声响以便对获得的物理输入发出即时用户反馈。用 perl shakeShutdown.lp 1000 命令运行脚本。偏差阈值变得更小,因为加速度传感器的每次读取间隔与内核空间的每次读取间隔比较而言减少了。

修改空间移位参数和偏差阈值可以提供有益的对内核空间外部的物理活动的额外监视。例如,要采集 “行走” 行为的数据,需要将空间移位参数设为大约 20,并将偏差阈值设为大约 5000。这将检测到大约 63 个双坐标轴空间移位,这与膝上型计算机在处于运行状态时被放在典型的单肩背膝上型计算机包中的情况一致。检测到这种长距离行走后(不同于从办公位置到会议室的短距离行走),计算机将进入关闭程序以避免过热,因为空气在背包中不流通。修改空间移位参数使其具有高灵敏度,任何较大的撞击、坠落或震动都会被记录下来。


回页首

结束语

通过使用针对用户空间和内核级代码的这些简单算法,现在能够检测、记录和响应来自用户的各种物理输入。使用这些代码示例,从根据连续的加速度计算出来的高度修改硬盘性能参数,到丈量从办公位置到会议室的距离,并将其用邮件发送给空间规划师,您都可以应对自如。

参考资料

学习

获得产品和技术

  • Fedora Core V5 发行版的内核中包括 hdaps。
  • 使用 IBM 试用软件 改进您的下一个开放源码开发项目,这些软件可以通过下载或从 DVD 中获得。

讨论

关于作者

 

Nathan Harrington 是 IBM 的编程人员,目前从事 Linux、WatchPad 1.5 和资源定位技术的工作。

2006年10月26日

    项目终于到了后期了,测试也进行了一段时间了。相对于程序来说,美术在这个阶段已经没有太多的任务了。我们版本的美术同学就向成都boss申请回成都,结 果不置可否。对于美术来说,每天最痛苦的就是怎么挨到下班。他们也真够痛苦的,每天的任务不多,但还是要陪着程序一起深更半夜才下班。因为就算他们可以下 班,回到住的地方也不知道怎么打发剩下的时间,在北京不象在成都,家人、朋友都在,而且北京也没什么娱乐,也没钱没时间去娱乐!只有在公司呆着,好歹能上 上网,打打游戏来打发时间。
     也不知道boss是怎么想的,不管从项目本身还是从人力财力来说,让美术现在回成都都是一个不错的选择。对美术来说,可以回成都好好的休息下;对公司来说,可以节约支出(虽然我们出差补贴的金额都不好意思说出口),以便调配人力物力进行下一个项目。
     回家的日子一天天近了!终于快要离开这个我很不喜欢的地方了!go home……

2006年10月24日
    第二次到北京了。上次是6月20日来的,7月21号回成都的。其间总共加起来的休息就2天,每天都是22点以后才下班,早上还要9点就到公司。那个累啊!这次是8月7号来的,到9月29日其间就休息了半天,快两个月啊,就这样连续的上班,而且比上次还累,每天都是23点以后才走, 还经常都是凌晨1,2点才回住的地方,早上还不能太晚到公司。
 
      项目时间非常紧张,我们无尽的加班还被别人认为是我们做事没效率,也不想想无尽的反馈要修改,无数的意见要听取,头上的boss又多,这个来给点意见,那个来给点意见,意见和意见还有冲突,做了这个那个又有意见,说他的意见怎么没有做。
 
       现在都凌晨一点多了,还在公司,偷闲写写blog。太多的苦水了,现在头脑都是很不清醒的,想多写点什么都想不起来。唉,这样的日子什么时候能结束啊!!!!

        最近一直在北京公司做项目。周日加班结束了,PD说大家明天最迟13点以前到。心里还觉得挺好的,明天可以睡个懒觉再到公司。结果第二天到公司填加班单,被告知要扣除倒休的时间。实际的加班时间=总的加班时间-中午、晚上吃饭的时间-倒休的时间。而倒休时间是以周一早上9点为基准的,如果你10点来就算倒休一小时,以此类推。结果我们12点后来的,倒休时间算下来就是3个小时。因为周日加班是双薪,而周一是单薪,所以我们在填加班单的时候把倒休时间换算成了1.5小时。结果又被告知,倒休时间是多少小时就是多少小时,不能换算!这就相当于我们的加班时间被平白的减少了1.5个小时。问为什么这么算?统一一句“这是公司的规定”。对公司来说,我们是弱势群体,我们只能被公司剥削,唯一可以安慰自己的是,没有全被剥削了,至少还能拿到一部分。对于平时的加班来说,是没有加班费的。而且经常24点后下班,被要求第二天10点前到。为什么呢?因为有加班费的时候你倒休公司就可以少付薪水给你,而平时就随便怎么剥削你了!(对于周末双薪我也不是很肯定,有时候会觉得加班时间没有计算正确!)

2006年05月22日

http://www.tianya.cn/new/publicforum/content.asp?idarticle=303040&stritem=no11&idwriter=0&key=0

2006年04月07日

ASCII码表,需要的时候总是找不到,干脆放一个在网站上得了,以后找的时候也方便。

Table of ASCII Characters

This table lists the ASCII characters and their decimal, octal and hexadecimal numbers. Characters which appear as names in parentheses (e.g., (nl)) are non-printing characters. A table of the common non-printing characters appears after this table.

Char  Dec  Oct  Hex | Char  Dec  Oct  Hex | Char  Dec  Oct  Hex | Char Dec  Oct   Hex
-------------------------------------------------------------------------------------
(nul)   0 0000 0x00 | (sp)   32 0040 0x20 | @      64 0100 0x40 | `      96 0140 0x60
(soh)   1 0001 0x01 | !      33 0041 0x21 | A      65 0101 0x41 | a      97 0141 0x61
(stx)   2 0002 0x02 | "      34 0042 0x22 | B      66 0102 0x42 | b      98 0142 0x62
(etx)   3 0003 0x03 | #      35 0043 0x23 | C      67 0103 0x43 | c      99 0143 0x63
(eot)   4 0004 0x04 | $      36 0044 0x24 | D      68 0104 0x44 | d     100 0144 0x64
(enq)   5 0005 0x05 | %      37 0045 0x25 | E      69 0105 0x45 | e     101 0145 0x65
(ack)   6 0006 0x06 | &      38 0046 0x26 | F      70 0106 0x46 | f     102 0146 0x66
(bel)   7 0007 0x07 | '      39 0047 0x27 | G      71 0107 0x47 | g     103 0147 0x67
(bs)    8 0010 0x08 | (      40 0050 0x28 | H      72 0110 0x48 | h     104 0150 0x68
(ht)    9 0011 0x09 | )      41 0051 0x29 | I      73 0111 0x49 | i     105 0151 0x69
(nl)   10 0012 0x0a | *      42 0052 0x2a | J      74 0112 0x4a | j     106 0152 0x6a
(vt)   11 0013 0x0b | +      43 0053 0x2b | K      75 0113 0x4b | k     107 0153 0x6b
(np)   12 0014 0x0c | ,      44 0054 0x2c | L      76 0114 0x4c | l     108 0154 0x6c
(cr)   13 0015 0x0d | -      45 0055 0x2d | M      77 0115 0x4d | m     109 0155 0x6d
(so)   14 0016 0x0e | .      46 0056 0x2e | N      78 0116 0x4e | n     110 0156 0x6e
(si)   15 0017 0x0f | /      47 0057 0x2f | O      79 0117 0x4f | o     111 0157 0x6f
(dle)  16 0020 0x10 | 0      48 0060 0x30 | P      80 0120 0x50 | p     112 0160 0x70
(dc1)  17 0021 0x11 | 1      49 0061 0x31 | Q      81 0121 0x51 | q     113 0161 0x71
(dc2)  18 0022 0x12 | 2      50 0062 0x32 | R      82 0122 0x52 | r     114 0162 0x72
(dc3)  19 0023 0x13 | 3      51 0063 0x33 | S      83 0123 0x53 | s     115 0163 0x73
(dc4)  20 0024 0x14 | 4      52 0064 0x34 | T      84 0124 0x54 | t     116 0164 0x74
(nak)  21 0025 0x15 | 5      53 0065 0x35 | U      85 0125 0x55 | u     117 0165 0x75
(syn)  22 0026 0x16 | 6      54 0066 0x36 | V      86 0126 0x56 | v     118 0166 0x76
(etb)  23 0027 0x17 | 7      55 0067 0x37 | W      87 0127 0x57 | w     119 0167 0x77
(can)  24 0030 0x18 | 8      56 0070 0x38 | X      88 0130 0x58 | x     120 0170 0x78
(em)   25 0031 0x19 | 9      57 0071 0x39 | Y      89 0131 0x59 | y     121 0171 0x79
(sub)  26 0032 0x1a | :      58 0072 0x3a | Z      90 0132 0x5a | z     122 0172 0x7a
(esc)  27 0033 0x1b | ;      59 0073 0x3b | [      91 0133 0x5b | {     123 0173 0x7b
(fs)   28 0034 0x1c | <      60 0074 0x3c | \      92 0134 0x5c | |     124 0174 0x7c
(gs)   29 0035 0x1d | =      61 0075 0x3d | ]      93 0135 0x5d | }     125 0175 0x7d
(rs)   30 0036 0x1e | >      62 0076 0x3e | ^      94 0136 0x5e | ~     126 0176 0x7e
(us)   31 0037 0x1f | ?      63 0077 0x3f | _      95 0137 0x5f | (del) 127 0177 0x7f
ASCII Name Description C Escape Sequence
nul null byte \0
bel bell character \a
bs backspace \b
ht horizontal tab \t
np formfeed \f
nl newline \n
cr carriage return \r
vt vertical tab
esc escape
sp space
2006年03月03日

         今天晚上本来约了朋友9点打乒乓球的,结果9点给他们打电话的时候,居然说他们才开始吃饭,我晕!等他们吃了饭都不知道几点了,最烦当时只有我一个人,等也不好等的,瓜滕了!结果活动取消。

          做为一个很守时的人,我强烈的鄙视那些不守时的人,女人除外。迟到30分钟可以接受,但放鸽子就太不厚道了!

           再一次的鄙视你们!!!

2006年03月01日

         突然觉得工作挺没劲的!一切都不在掌握中,自己负责的版本一直都在delay,虽然各个方面的原因都有,但总归感到很不爽!今天和昨天程序方面其实也没做多大的改动,主要是现在程序要做的内存减容工作的确不太好做,感到自己有点无所事事,需要的资源也迟迟拿不到,自己又不想切催,就这样耗起。

          唉,反正现在情绪很低落!不写了。

2006年02月22日

     最近又开始看《达芬奇密码》了。原因是5月电影版的《达芬奇密码》就要上映了,想在上映前重温下这部经典的小说。

     宗教历来是披着神秘的面纱,不管是基督教,天主教,伊斯兰教,佛教,道教,无疑都有无数的传奇和各种各样的秘密流传下来,很多因为年代久远,而又没有记载而无法考证,更增添了神秘感。

     密码学是近代才兴起的新兴科学,但很早就被应用在各种领域,用来记载一些不想被外人所知的东西。当宗教和密码学结合在一样,呵呵,就有了《达芬奇密码》。

      突然在想,如果自己把睡前的这半个小时拿来学英语,会是个什么情况?呵呵,多半上下眼皮直接打架!最近老是加班,实在是没有多少精力可以在12点以后认真的学习了。还是消遣一下,放松自己来的愉快!

       今年期待的电影很多,希望自己都能到电影院看!