2008年7月31日星期四

oracle11g自启动中的错误解决(ORACLE_HOME_LISTNER is not SET)

Oracle提供了两个脚本dbstart和dbshut用来启动和关闭数据库.
这两个脚本首先读取oratab(/etc/oratab)文件来决定哪个数据库是需要自动启动和关闭,然后启动和关闭那些数据库,
oratab文件通过root.sh创建.


[oracle@chicago oracle]$ cat /etc/oratab
#

# This file is used by ORACLE utilities. It is created by root.sh
# and updated by the Database Configuration Assistant when creating
# a database.

# A colon, ':', is used as the field terminator. A new line terminates
# the entry. Lines beginning with a pound sign, '#', are comments.
#
# Entries are of the form:
# $ORACLE_SID:$ORACLE_HOME::
#
# The first and second fields are the system identifier and home
# directory of the database respectively. The third filed indicates
# to the dbstart utility that the database should , "Y", or should not,
# "N", be brought up at system boot time.
#
# Multiple entries with the same $ORACLE_SID are not allowed.
#
#
orcl:/u01/app/oracle/oracle/product/10.2.0/db_1:Y

不过,dbstart/dbshut脚本中都包含有错误.
需要修改ORACLE_HOME_LISTNER=$ORACLE_HOME
[oracle@chicago oracle]$ dbstart
ORACLE_HOME_LISTNER is not SET, unable to auto-start Oracle Net Listener
Usage: /u01/app/oracle/oracle/product/10.2.0/db_1/bin/dbstart ORACLE_HOME

[oracle@chicago oracle]$ vi $ORACLE_HOME/bin/dbstart

:
#
# $Id: dbstart.sh.pp 25-may-2005.14:52:00 vikrkuma Exp $
# Copyright (c) 1991, 2005, Oracle. All rights reserved.
#

###################################
#
# usage: dbstart $ORACLE_HOME
#
# This script is used to start ORACLE from /etc/rc(.local).
# It should ONLY be executed as part of the system boot procedure.
#
# This script will start all databases listed in the oratab file
# whose third field is a "Y". If the third field is set to "Y" and
# there is no ORACLE_SID for an entry (the first field is a *),
# then this script will ignore that entry.
#
# This script requires that ASM ORACLE_SID's start with a +, and
# that non-ASM instance ORACLE_SID's do not start with a +.
#
# If ASM instances are to be started with this script, it cannot
# be used inside an rc*.d directory, and should be invoked from
# rc.local only. Otherwise, the CSS service may not be available
# yet, and this script will block init from completing the boot
# cycle.
#
# If you want dbstart to auto-start a single-instance database that uses
# an ASM server that is auto-started by CRS (this is the default behavior
# for an ASM cluster), you must change the database's ORATAB entry to use
# a third field of "W" and the ASM's ORATAB entry to use a third field of "N".
# These values specify that dbstart auto-starts the database only after
# the ASM instance is up and running.
#
# Note:
# Use ORACLE_TRACE=T for tracing this script.
#
# The progress log for each instance bringup plus Error and Warning message[s]
# are logged in file $ORACLE_HOME/startup.log. The error messages related to
# instance bringup are also logged to syslog (system log module).
# The Listener log is located at $ORACLE_HOME_LISTNER/listener.log
#
# To configure:
# 1) Set ORATAB:
# On Solaris
# ORATAB=/var/opt/oracle/oratab
# All other UNIX platforms
# ORATAB=/etc/oratab
#
# 2) Update $ORATAB/oratab with Database Instances that need to be started up.
# Entries are of the form:
# $ORACLE_SID:$ORACLE_HOME::
# An example entry:
# main:/usr/lib/oracle/emagent_10g:Y
#
# Overall algorithm:
# 1) Bring up all ASM instances with 'Y' entry in status field in oratab entry
# 2) Bring up all Database instances with 'Y' entry in status field in
# oratab entry
# 3) If there are Database instances with 'W' entry in status field
# then
# iterate over all ASM instances (irrespective of 'Y' or 'N') AND
# wait for all of them to be started
# fi
# 4) Bring up all Database instances with 'W' entry in status field in
# oratab entry
#
#####################################

LOGMSG="logger -puser.alert -s "

trap 'exit' 1 2 3

# for script tracing
case $ORACLE_TRACE in
T) set -x ;;
esac

# Set path if path not set (if called from /etc/rc)
case $PATH in
"") PATH=/bin:/usr/bin:/etc
export PATH ;;
esac
# Save LD_LIBRARY_PATH
SAVE_LLP=$LD_LIBRARY_PATH

# First argument is used to bring up Oracle Net Listener
ORACLE_HOME_LISTNER=$ORACLE_HOME
if [ ! $ORACLE_HOME_LISTNER ] ; then
echo "ORACLE_HOME_LISTNER is not SET, unable to auto-start Oracle Net Listener"
echo "Usage: $0 ORACLE_HOME"
else
LOG=$ORACLE_HOME_LISTNER/listener.log

# Start Oracle Net Listener
if [ -x $ORACLE_HOME_LISTNER/bin/tnslsnr ] ; then
echo "$0: Starting Oracle Net Listener" >> $LOG 2>&1
"/u01/app/oracle/oracle/product/10.2.0/db_1/bin/dbstart" 461L, 13926C written
[oracle@chicago oracle]$ dbstart
Processing Database instance "orcl": log file /u01/app/oracle/oracle/product/10.2.0/db_1/startup.log
[oracle@chicago oracle]$ dbshut
ORACLE_HOME_LISTNER is not SET, unable to auto-stop Oracle Net Listener
Usage: /u01/app/oracle/oracle/product/10.2.0/db_1/bin/dbshut ORACLE_HOME
Processing Database instance "orcl": log file /u01/app/oracle/oracle/product/10.2.0/db_1/shutdown.log
[oracle@chicago oracle]$ vi $ORACLE_HOME/bin/dbshut

:
#
# $Id: dbshut.sh.pp 11-may-2005.19:37:00 vikrkuma Exp $
# Copyright (c) 1991, 2005, Oracle. All rights reserved.
#

###################################
#
# usage: dbshut $ORACLE_HOME
#
# This script is used to shutdown ORACLE from /etc/rc(.local).
# It should ONLY be executed as part of the system boot procedure.
#
# This script will shutdown all databases listed in the oratab file
# whose third field is a "Y" or "W". If the third field is set to "Y" and
# there is no ORACLE_SID for an entry (the first field is a *),
# then this script will ignore that entry.
#
# This script requires that ASM ORACLE_SID's start with a +, and
# that non-ASM instance ORACLE_SID's do not start with a +.
#
# Note:
# Use ORACLE_TRACE=T for tracing this script.
# Oracle Net Listener is also shutdown using this script.
#
# The progress log for each instance shutdown is logged in file
# $ORACLE_HOME/shutdown.log.
#
# To configure:
# 1) Set ORATAB:
# On Solaris
# ORATAB=/var/opt/oracle/oratab
# All other UNIX platforms
# ORATAB=/etc/oratab
#
# 2) Update $ORATAB/oratab with Database Instances that need to be shutdown.
# Entries are of the form:
# $ORACLE_SID:$ORACLE_HOME::
# An example entry:
# main:/usr/lib/oracle/emagent_10g:Y
#
# Note:
# Use ORACLE_TRACE=T for tracing this script.
# Oracle Net Listener is NOT shutdown using this script.
#
# The progress log for each instance shutdown is logged in file
# $ORACLE_HOME/shutdown.log.
#
# To configure:
# 1) Set ORATAB:
# On Solaris
# ORATAB=/var/opt/oracle/oratab
# All other UNIX platforms
# ORATAB=/etc/oratab
#
# 2) Update $ORATAB/oratab with Database Instances that need to be shutdown.
# Entries are of the form:
# $ORACLE_SID:$ORACLE_HOME::
# An example entry:
# main:/usr/lib/oracle/emagent_10g:Y
#
#####################################

trap 'exit' 1 2 3
case $ORACLE_TRACE in
T) set -x ;;
esac
# Set path if path not set (if called from /etc/rc)
case $PATH in
"") PATH=/bin:/usr/bin:/etc
export PATH ;;
esac
# Save LD_LIBRARY_PATH
SAVE_LLP=$LD_LIBRARY_PATH

# The this to bring down Oracle Net Listener
ORACLE_HOME_LISTNER=$ORACLE_HOME
if [ ! $ORACLE_HOME_LISTNER ] ; then
echo "ORACLE_HOME_LISTNER is not SET, unable to auto-stop Oracle Net Listener"
echo "Usage: $0 ORACLE_HOME"
else
LOG=$ORACLE_HOME_LISTNER/listener.log

# Stop Oracle Net Listener
if [ -f $ORACLE_HOME_LISTNER/bin/tnslsnr ] ; then
"/u01/app/oracle/oracle/product/10.2.0/db_1/bin/dbshut" 246L, 6592C written
[oracle@chicago oracle]$ dbstart
Processing Database instance "orcl": log file /u01/app/oracle/oracle/product/10.2.0/db_1/startup.log
[oracle@chicago oracle]$ dbshut
Processing Database instance "orcl": log file /u01/app/oracle/oracle/product/10.2.0/db_1/shutdown.log
[oracle@chicago oracle]$

2008年7月30日星期三

关于SGA设置的一点总结

关于SGA设置的一点总结
作者:Biti_rainy
说明:
本总结不针对特例,仅对服务器只存在OS + ORACLE 为例,如果存在其他应用请酌情考虑。写这个也是因为近来这种重复性的问题发生的太多所导致的。

首先不要迷信STS、OCP SG以及某些专家给出的任何建议、内存百分比的说法。基本掌握的原则是:

l data buffer 通常可以尽可能的大

l shared_pool_size 要适度

l log_buffer 通常大到几百K到1M就差不多了

设置之前,首先要明确2个问题
1:除去OS和一些其他开销,能给ORACLE使用的内存有多大?
2:Oracle是64 bit 还是 32 bit ?32bit 通常 SGA有 1.7G 的限制(某些OS有特定处理或者WINDOWS上有特定设定可以支持到2G以上甚至达到3.7G,本人无这方面经验)。

下面是我的Windows2000下的Oracle :

SQL> select * from v$version;

BANNER
----------------------------------------------------------------
Oracle8i Enterprise Edition Release 8.1.7.0.0 - Production
PL/SQL Release 8.1.7.0.0 - Production
CORE 8.1.7.0.0 Production
TNS for 32-bit Windows: Version 8.1.7.0.0 - Production
NLSRTL Version 3.4.1.0.0 - Production

SQL>

windows上存在32bit的限制,如AIX、HP-UX 等有明确的64 bit OS 和ORACLE的版本,32 bit Oracle可以装在64 bit OS 上,64 bit Oracle不能装在32 bit OS上。

不管Oracle是32 bit 还是 64 bit 的,假定应用存在没有很好的使用bind var 的情况,也不能设置 shared_pool_size 过大,通常应该控制在100M--200M,除非是 ORACLE ERP 一类的使用了很多存储过程函数、包 ,这样的很大的系统,可以考虑增大shared_pool_size,但是如果超过500M可能是危险的,达到1G几乎就会造成CPU的严重负担,系统甚至瘫痪。所以shared_pool_size 如果超过200M还命中率不高,那么应该从应用上找原因而不是一味的增加内存,shared_pool_size 过大主要增加了管理负担和latch 的开销。

log_buffer :128K -- 1M 之间通常问题不大,不应该太大。

large_pool_size :如果不设置MTS,通常在 RMAN 、OPQ 会使用到,但是在10M --50M 应该差不多了。假如设置 MTS,则由于 UGA 放到large_pool_size 的缘故,这个时候依据 session最大数量和 sort_ares_size 等参数设置,必须增大large_pool_size 的设置,可以考虑为 session * (sort_area_size + 2M)。这里要提醒一点,不是必须使用MTS,我们都不主张使用MTS,尤其同时在线用户数小于500的情况下。

java_pool_size : 若不使用java,给30M通常就够了。

data buffer :在做了前面的设置后,凡可以提供给Oracle的内存,都应该给data buffer = (db_block_size * db_block_buffers) 在9i 中可以是 db_cache_size。

还有2个重要参数我们需要注意:

sort_area_size
hash_area_size
这两个参数在非MTS下都是属于PGA ,不属于SGA。它是为每个session单独分配的,在我们的服务器上除了OS + SGA,一定要考虑这两部分。

(****) : OS 使用内存+ SGA + session*(sort_area_size + hash_area_size + 2M) < 总物理RAM 为好 。

这样归结过来,假定Oracle是 32 bit ,服务器RAM大于2G ,注意你的PGA的情况,则建议:

shared_pool_size + data buffer +large_pool_size + java_pool_size < 1.6G

再具体化,注意满足上面(****) 的原则的基础上可以参考如下设置:
如果512M RAM
建议 shared_pool_size = 50M, data buffer = 200M ;

如果1G RAM
shared_pool_size = 100M , data buffer = 500M ;

如果2G RAM
shared_pool_size = 150M ,data buffer = 1.2G。

物理内存再大已经跟参数没有关系了 。

举例来说:
假定64 bit ORACLE

内存4G
shared_pool_size = 200M , data buffer = 2.5G

内存8G
shared_pool_size = 200M , data buffer = 5G

内存 12G
shared_pool_size = 300M , data buffer = 8G



总结:

以上仅为参考值,建议在设置参数的同时,init中使用 lock_sga ,在不同的平台上可能有不同的方式,使得SGA锁定在物理内存中而不被放入 SWAP 中,这样对效率有好处。(关于内存的设置,要再进行细致的调整,起的作用不大,但可根据statspack信息和v$system_event,v$sysstat,v$sesstat,v$latch 等视图信息来考虑微调。)


编辑注: 关于此贴的详细情况请参考论坛的帖子:
http://www.itpub.net/showthread.php?s=&threadid=109787

2008年7月28日星期一

openvpn构建要点

第一,如果是rpm包直接跑的,没啥好说的。如果是源码包编译出来的,那就要注意./configure。

一般是先装LZO,如果没有装也没关系。configure的时候加上:./configure --disable-lzo。make make install。

服务端启动:openvpn --config server0728.conf
客户端启动:openvpn --config client0728.conf


几个注意点:
1.如果两个客户端互相ping不通对方,就检查一下以下选项是否开启。

#不用发送到tun或者tap设备后重新转发,优化Client to Client的访问效率
client-to-client

2.如果报lzo的错误,就看看是不是客户端和服务端的lzo压缩不一致,或根本没装。
#comp-lzo

3.如果双网卡的一个服务端,有个内网的客户端连不上。注意检查
# listen on? (optional)
#local 211.124.162.91

4.一个机器不要开多个客户端,以免造成冲突,也不要同一个密钥多个机器使用,也会造成冲突。

5.一定要注意先检查服务器时间,不要生成密钥的时候比连接时候还晚,服务端会认为,我还没生成密钥,你客户端就连上来了。

这里附上openvpn2.1的一些命令:

./pkitool
source ./vars
./clean-all
./build-dh
./pkitool --initca
./pkitool --server linuxserver91
./pkitool windows97
./pkitool windowszhv
./pkitool linux10
# vi openvpn-startup.sh
然后就可以启动了。

有必要的话注释掉。

2008年7月21日星期一

MySQL多表查询

在一个数据库中,可能存在多个表,这些表都是相互关联的。我们继续使用前面的例子。前面建立的表中包含了员工的一些基本信息,如姓名、性别、出生日期、出生地。我们再创建一个表,该表用于描述员工所发表的文章,内容包括作者姓名、文章标题、发表日期。
  1、查看第一个表 mytable 的内容:
  mysql> select * from mytable;
  +----------+------+------------+-----------+
  | name | sex | birth | birthaddr |
  +----------+------+------------+-----------+
  | abccs |f | 1977-07-07 | china |
  | mary |f | 1978-12-12 | usa |
  | tom |m | 1970-09-02 | usa |
  +----------+------+------------+-----------+
  2、创建第二个表 title (包括作者、文章标题、发表日期):
  mysql> create table title(writer varchar(20) not null,
  -> title varchar(40) not null,
  -> senddate date);
   向该表中填加记录,最后表的内容如下:
  mysql> select * from title;
  +--------+-------+------------+
  | writer | title | senddate |
  +--------+-------+------------+
  | abccs | a1 | 2000-01-23 |
  | mary | b1 | 1998-03-21 |
  | abccs | a2 | 2000-12-04 |
  | tom | c1 | 1992-05-16 |
  | tom | c2 | 1999-12-12 |
  +--------+-------+------------+
  5 rows in set (0.00sec)
  3、多表查询
  现在我们有了两个表: mytable 和 title。利用这两个表我们可以进行组合查询:
  上面例子中,由于作者姓名、性别、文章记录在两个不同表内,因此必须使用组合来进行查询。必须要指定一个表中的记录如何与其它表中的记录进行匹配。
  注意:如果第二个表 title 中的 writer 列也取名为 name(与mytable表中的name列相同)而不是 write r时,就必须用 mytable.name 和 title.name 表示,以示区别。
  再举一个例子,用于查询文章 a2 的作者、出生地和出生日期:
  mysql> select title,writer,birthaddr,birth from mytable,title
  -> where mytable.name=title.writer and title=′a2′;
  +-------+--------+-----------+------------+
  | title | writer | birthaddr | birth |
  +-------+--------+-----------+------------+
  | a2 | abccs | china | 1977-07-07 |
  +-------+--------+-----------+------------+
  修改和备份、批处理
  有时我们要对数据库表和数据库进行修改和删除,可以用如下方法实现:
  1、增加一列:
  如在前面例子中的 mytable 表中增加一列表示是否单身 single:
  mysql> alter table mytable add column single char(1);
  2、修改记录
  将 abccs 的 single 记录修改为“y”:
  mysql> update mytable set single=′y′ where name=′abccs′; 现在来看看发生了什么:
  mysql> select * from mytable;
  +----------+------+------------+-----------+--------+
  | name | sex | birth | birthaddr | single |
  +----------+------+------------+-----------+--------+
  | abccs |f | 1977-07-07 | china | y |
  | mary |f | 1978-12-12 | usa | NULL |
  | tom |m | 1970-09-02 | usa | NULL |
  +----------+------+------------+-----------+--------+
  3、增加记录
  前面已经讲过如何增加一条记录,为便于查看,重复与此:
  mysql> insert into mytable
  -> values (′abc′,′f′,′1966-08-17′,′china′,′n′);
  Query OK, 1 row affected (0.05 sec)
  查看一下:
  mysql> select * from mytable;
  +----------+------+------------+-----------+--------+
  | name | sex | birth | birthaddr | single |
  +----------+------+------------+-----------+--------+
  | abccs |f | 1977-07-07 | china | y |
  | mary |f | 1978-12-12 | usa | NULL |
  | tom |m | 1970-09-02 | usa | NULL |
  | abc |f | 1966-08-17 | china | n |
  +----------+------+------------+-----------+--------+
  4、删除记录
  用如下命令删除表中的一条记录:mysql> delete from mytable where name=′abc′;
  DELETE 从表中删除满足由 where 给出的条件的一条记录。再显示一下结果:
  mysql> select * from mytable;
  +----------+------+------------+-----------+--------+
  | name | sex | birth | birthaddr | single |
  +----------+------+------------+-----------+--------+
  | abccs |f | 1977-07-07 | china | y |
  | mary |f | 1978-12-12 | usa | NULL |
  | tom |m | 1970-09-02 | usa | NULL |
  +----------+------+------------+-----------+--------+
  5、删除表:
  mysql> drop table ****(表 1 的名字),*** 表 2 的名字; 可以删除一个或多个表,小心使用。
  6、数据库的删除:
  mysql> drop database 数据库名; 小心使用。
  7、数据库的备份:
  退回到 DOS:
  mysql> quit
  d:\mysqlbin
  使用如下命令对数据库 abccs 进行备份:
  mysqldump --opt abccs>abccs.dbb
  abccs.dbb 就是你的数据库 abccs 的备份文件。
  8、用批处理方式使用 MySQL:
  首先建立一个批处理文件 mytest.sql,内容如下:
  use abccs;
  select * from mytable;
  select name,sex from mytable where name=′abccs′;
  在 DOS 下运行如下命令:d:mysqlbin mysql < mytest.sql
  在屏幕上会显示执行结果。
  如果想看结果,而输出结果很多,则可以用这样的命令: mysql < mytest.sql | more
  我们还可以将结果输出到一个文件中: mysql < mytest.sql > mytest.out

2008年7月20日星期日

RedHat Linux常见的日志文件和常用命令

成功地管理任何系统的关键之一,是要知道系统中正在发生什么事。Linux 中提供了异常日志,并且日志的细节是可配置的。Linux 日志都以明文形式存储,所以用户不需要特殊的工具就可以搜索和阅读它们。还可以编写脚本,来扫描这些日志,并基于它们的内容去自动执行某些功能。Linux 日志存储在 /var/log 目录中。这里有几个由系统维护的日志文件,但其他服务和程序也可能会把它们的日志放在这里。大多数日志只有root账户才可以读,不过修改文件的访问权限就可以让其他人可读。

  RedHat Linux常用的日志文件

  RedHat Linux常见的日志文件详述如下
  /var/log/boot.log
  该文件记录了系统在引导过程中发生的事件,就是Linux系统开机自检过程显示的信息。

  /var/log/cron
  该日志文件记录crontab守护进程crond所派生的子进程的动作,前面加上用户、登录时间和PID,以及派生出的进程的动作。CMD的一个动作是cron派生出一个调度进程的常见情况。REPLACE(替换)动作记录用户对它的cron文件的更新,该文件列出了要周期性执行的任务调度。RELOAD动作在REPLACE动作后不久发生,这意味着cron注意到一个用户的cron文件被更新而cron需要把它重新装入内存。该文件可能会查到一些反常的情况。

  /var/log/maillog
  该日志文件记录了每一个发送到系统或从系统发出的电子邮件的活动。它可以用来查看用户使用哪个系统发送工具或把数据发送到哪个系统。下面是该日志文件的片段:

Sep 4 17:23:52 UNIX sendmail[1950]: g849Npp01950: from=root, size=25, class=0, nrcpts=1, msgid=<200209040923.g849Npp01950@redhat.pfcc.com.cn>,relay=root@localhostSep 4 17:23:55 UNIX sendmail[1950]: g849Npp01950: to=lzy@fcceec.net, ctladdr=root (0/0), delay=00:00:04, xdelay=00:00:03, mailer=esmtp, pri=30025, relay=fcceec.net. [10.152.8.2], dsn=2.0.0, stat=Sent (Message queued)/var/log/messages



  该日志文件是许多进程日志文件的汇总,从该文件可以看出任何入侵企图或成功的入侵。如以下几行:


Sep 3 08:30:17 UNIX login[1275]: FAILED LOGIN 2 FROM (null) FOR suying, Authentication failureSep 4 17:40:28 UNIX -- suying[2017]: LOGIN ON pts/1 BY suying FROMfcceec.www.ec8.pfcc.com.cnSep 4 17:40:39 UNIX su(pam_unix)[2048]: session opened for user root by suying(uid=999)


  该文件的格式是每一行包含日期、主机名、程序名,后面是包含PID或内核标识的方括号、一个冒号和一个空格,最后是消息。该文件有一个不足,就是被记录的入侵企图和成功的入侵事件,被淹没在大量的正常进程的记录中。但该文件可以由/etc/syslog文件进行定制。由/etc/syslog.conf配置文件决定系统如何写入/var/messages。有关如何配置/etc/syslog.conf文件决定系统日志记录的行为,将在后面详细叙述。

  /var/log/syslog
  默认RedHat Linux不生成该日志文件,但可以配置/etc/syslog.conf让系统生成该日志文件。它和/etc/log/messages日志文件不同,它只记录警告信息,常常是系统出问题的信息,所以更应该关注该文件。要让系统生成该日志文件,在/etc/syslog.conf文件中加上:*.warning /var/log/syslog   该日志文件能记录当用户登录时login记录下的错误口令、Sendmail的问题、su命令执行失败等信息。下面是一条记录:

Sep 6 16:47:52 UNIX login(pam_unix)[2384]: check pass; user unknown/var/log/secure该日志文件记录与安全相关的信息。该日志文件的部分内容如下:Sep 4 16:05:09 UNIX xinetd[711]: START: ftp pid=1815 from=127.0.0.1Sep 4 16:05:09 UNIX xinetd[1815]: USERID: ftp OTHER :rootSep 4 16:07:24 UNIX xinetd[711]: EXIT: ftp pid=1815 duration=135(sec)Sep 4 16:10:05 UNIX xinetd[711]: START: ftp pid=1846 from=127.0.0.1Sep 4 16:10:05 UNIX xinetd[1846]: USERID: ftp OTHER :rootSep 4 16:16:26 UNIX xinetd[711]: EXIT: ftp pid=1846 duration=381(sec)Sep 4 17:40:20 UNIX xinetd[711]: START: telnet pid=2016 from=10.152.8.2/var/log/lastlog


  该日志文件记录最近成功登录的事件和最后一次不成功的登录事件,由login生成。在每次用户登录时被查询,该文件是二进制文件,需要使用lastlog命令查看,根据UID排序显示登录名、端口号和上次登录时间。如果某用户从来没有登录过,就显示为"**Never logged in**"。该命令只能以root权限执行。简单地输入lastlog命令后就会看到类似如下的信息:

Username Port From Latestroot tty2 Tue Sep 3 08:32:27 +0800 2002bin **Never logged in**daemon **Never logged in**adm **Never logged in**lp **Never logged in**sync **Never logged in**shutdown **Never logged in**halt **Never logged in**mail **Never logged in**news **Never logged in**uucp **Never logged in**operator **Never logged in**games **Never logged in**gopher **Never logged in**ftp ftp UNIX Tue Sep 3 14:49:04 +0800 2002nobody **Never logged in**nscd **Never logged in**mailnull **Never logged in**ident **Never logged in**rpc **Never logged in**rpcuser **Never logged in**xfs **Never logged in**gdm **Never logged in**postgres **Never logged in**apache **Never logged in**lzy tty2 Mon Jul 15 08:50:37 +0800 2002suying tty2 Tue Sep 3 08:31:17 +0800 2002


  系统账户诸如bin、daemon、adm、uucp、mail等决不应该登录,如果发现这些账户已经登录,就说明系统可能已经被入侵了。若发现记录的时间不是用户上次登录的时间,则说明该用户的账户已经泄密了。

  /var/log/wtmp

  该日志文件永久记录每个用户登录、注销及系统的启动、停机的事件。因此随着系统正常运行时间的增加,该文件的大小也会越来越大,增加的速度取决于系统用户登录的次数。该日志文件可以用来查看用户的登录记录,last命令就通过访问这个文件获得这些信息,并以反序从后向前显示用户的登录记录,last也能根据用户、终端 tty或时间显示相应的记录。

  命令last有两个可选参数:

  last -u 用户名 显示用户上次登录的情况。

  last -t 天数 显示指定天数之前的用户登录情况。

  /var/run/utmp

  该日志文件记录有关当前登录的每个用户的信息。因此这个文件会随着用户登录和注销系统而不断变化,它只保留当时联机的用户记录,不会为用户保留永久的记录。系统中需要查询当前用户状态的程序,如 who、w、users、finger等就需要访问这个文件。该日志文件并不能包括所有精确的信息,因为某些突发错误会终止用户登录会话,而系统没有及时更新 utmp记录,因此该日志文件的记录不是百分之百值得信赖的。

  以上提及的3个文件(/var/log/wtmp、/var/run/utmp、/var/log/lastlog)是日志子系统的关键文件,都记录了用户登录的情况。这些文件的所有记录都包含了时间戳。这些文件是按二进制保存的,故不能用less、cat之类的命令直接查看这些文件,而是需要使用相关命令通过这些文件而查看。其中,utmp和wtmp文件的数据结构是一样的,而lastlog文件则使用另外的数据结构,关于它们的具体的数据结构可以使用man命令查询。

  每次有一个用户登录时,login程序在文件lastlog中查看用户的UID。如果存在,则把用户上次登录、注销时间和主机名写到标准输出中,然后login程序在lastlog中记录新的登录时间,打开utmp文件并插入用户的utmp记录。该记录一直用到用户登录退出时删除。utmp文件被各种命令使用,包括who、w、users和finger。

  下一步,login程序打开文件wtmp附加用户的utmp记录。当用户登录退出时,具有更新时间戳的同一utmp记录附加到文件中。wtmp文件被程序last使用。

  /var/log/xferlog

  该日志文件记录FTP会话,可以显示出用户向FTP服务器或从服务器拷贝了什么文件。该文件会显示用户拷贝到服务器上的用来入侵服务器的恶意程序,以及该用户拷贝了哪些文件供他使用。

  该文件的格式为:第一个域是日期和时间,第二个域是下载文件所花费的秒数、远程系统名称、文件大小、本地路径名、传输类型(a:ASCII,b:二进制)、与压缩相关的标志或tar,或"_"(如果没有压缩的话)、传输方向(相对于服务器而言:i代表进,o代表出)、访问模式(a:匿名,g:输入口令,r:真实用户)、用户名、服务名(通常是ftp)、认证方法(l:RFC931,或0),认证用户的ID或"*"。下面是该文件的一条记录:

Wed Sep 4 08:14:03 2002 1 UNIX 275531 /var/ftp/lib/libnss_files-2.2.2.so b _ o a -root@UNIX ftp 0 * c/var/log/kernlog



   RedHat Linux默认没有记录该日志文件。要启用该日志文件,必须在/etc/syslog.conf文件中添加一行:kern.* /var/log/kernlog 。这样就启用了向/var/log/kernlog文件中记录所有内核消息的功能。该文件记录了系统启动时加载设备或使用设备的情况。一般是正常的操作,但如果记录了没有授权的用户进行的这些操作,就要注意,因为有可能这就是恶意用户的行为。下面是该文件的部分内容:

Sep 5 09:38:42 UNIX kernel: NET4: Linux TCP/IP 1.0 for NET4.0 Sep 5 09:38:42 UNIX kernel: IP Protocols: ICMP, UDP, TCP, IGMPSep 5 09:38:42 UNIX kernel: IP: routing cache hash table of 512 buckets, 4KbytesSep 5 09:38:43 UNIX kernel: TCP: Hash tables configured (established 4096 bind 4096)Sep 5 09:38:43 UNIX kernel: Linux IP multicast router 0.06 plus PIM-SMSep 5 09:38:43 UNIX kernel: NET4: Unix domain sockets 1.0/SMP for Linux NET4.0.Sep 5 09:38:44 UNIX kernel: EXT2-fs warning: checktime reached, running e2fsck is recommendedSep 5 09:38:44 UNIX kernel: VFS: Mounted root (ext2 filesystem).Sep 5 09:38:44 UNIX kernel: SCSI subsystem driver Revision: 1.00/var/log/Xfree86.x.log



  该日志文件记录了X-Window启动的情况。另外,除了/var/log/外,恶意用户也可能在别的地方留下痕迹,应该注意以下几个地方:root和其他账户的shell历史文件;用户的各种邮箱,如.sent、mbox,以及存放在/var/spool/mail/ 和 /var/spool/mqueue中的邮箱;临时文件/tmp、/usr/tmp、/var/tmp;隐藏的目录;其他恶意用户创建的文件,通常是以"."开头的具有隐藏属性的文件等。

  具体命令

  wtmp和utmp文件都是二进制文件,它们不能被诸如tail之类的命令剪贴或合并(使用cat命令)。用户需要使用who、w、users、last和ac等命令来使用这两个文件包含的信息。

  who命令

  who命令查询utmp文件并报告当前登录的每个用户。who的默认输出包括用户名、终端类型、登录日期及远程主机。例如,键入who命令,然后按回车键,将显示如下内容:



chyang pts/0 Aug 18 15:06 ynguo pts/2 Aug 18 15:32 ynguo pts/3 Aug 18 13:55 lewis pts/4 Aug 18 13:35 ynguo pts/7 Aug 18 14:12 ylou pts/8 Aug 18 14:15



  如果指明了wtmp文件名,则who命令查询所有以前的记录。命令who /var/log/wtmp将报告自从wtmp文件创建或删改以来的每一次登录。

  w命令

  w命令查询utmp文件并显示当前系统中每个用户和它所运行的进程信息。例如,键入w命令,然后按回车键,将显示如下内容:




3:36pm up 1 day, 22:34, 6 users, load average: 0.23, 0.29, 0.27 USER TTY FROM LOGIN@ IDLE JCPU PCPU WHAT chyang pts/0 202.38.68.242 3:06pm 2:04 0.08s 0.04s -bash ynguo pts/2 202.38.79.47 3:32pm 0.00s 0.14s 0.05 w lewis pts/3 202.38.64.233 1:55pm 30:39 0.27s 0.22s -bash lewis pts/4 202.38.64.233 1:35pm 6.00s 4.03s 0.01s sh /home/users/ ynguo pts/7 simba.nic.ustc.e 2:12pm 0.00s 0.47s 0.24s telnet mail ylou pts/8 202.38.64.235 2:15pm 1:09m 0.10s 0.04s -bash



  users命令

  users命令用单独的一行打印出当前登录的用户,每个显示的用户名对应一个登录会话。如果一个用户有不止一个登录会话,那他的用户名将显示相同的次数。例如,键入users命令,然后按回车键,将显示如下内容:

  chyang lewis lewis ylou ynguo ynguo

  last命令

  last命令往回搜索wtmp来显示自从文件第一次创建以来登录过的用户。例如:

chyang pts/9 202.38.68.242 Tue Aug 1 08:34 - 11:23 (02:49) cfan pts/6 202.38.64.224 Tue Aug 1 08:33 - 08:48 (00:14) chyang pts/4 202.38.68.242 Tue Aug 1 08:32 - 12:13 (03:40) lewis pts/3 202.38.64.233 Tue Aug 1 08:06 - 11:09 (03:03) lewis pts/2 202.38.64.233 Tue Aug 1 07:56 - 11:09 (03:12)



  如果指明了用户,那么last只报告该用户的近期活动,例如,键入last ynguo命令,然后按回车键,将显示如下内容:

ynguo pts/4 simba.nic.ustc.e Fri Aug 4 16:50 - 08:20 (15:30) ynguo pts/4 simba.nic.ustc.e Thu Aug 3 23:55 - 04:40 (04:44) ynguo pts/11 simba.nic.ustc.e Thu Aug 3 20:45 - 22:02 (01:16) ynguo pts/0 simba.nic.ustc.e Thu Aug 3 03:17 - 05:42 (02:25) ynguo pts/0 simba.nic.ustc.e Wed Aug 2 01:04 - 03:16 1+02:12) ynguo pts/0 simba.nic.ustc.e Wed Aug 2 00:43 - 00:54 (00:11) ynguo pts/9 simba.nic.ustc.e Thu Aug 1 20:30 - 21:26 (00:55)



  ac命令

  ac命令根据当前的/var/log/wtmp文件中的登录进入和退出来报告用户连接的时间(小时),如果不使用标志,则报告总的时间。例如,键入ac命令,然后按回车键,将显示如下内容:

  total 5177.47

键入ac -d命令,然后按回车键,将显示每天的总的连接时间:

Aug 12 total 261.87 Aug 13 total 351.39 Aug 14 total 396.09 Aug 15 total 462.63 Aug 16 total 270.45 Aug 17 total 104.29 Today total 179.02



  键入ac -p命令,然后按回车键,将显示每个用户的总的连接时间:

ynguo 193.23 yucao 3.35 rong 133.40 hdai 10.52 zjzhu 52.87 zqzhou 13.14 liangliu 24.34 total 5178.24

tomcat自动启动实现方法

tomcat自动启动实现方法



Tomcat 5 本身提供了配置为自动启动服务的方案,实施方法如下:

你所使用的 Tomcat 5.0.28 的 bin目录中有一个 fsvc.tar.gz,将其解压,得到/bin/fsvc- src文件夹。在终端运行:

QUOTE:
cd /bin/fsvc-src
./configure --with-java=/usr/local/jdk #此处填写你的 JAVA_HOME
make


然后会生成 bin/fsvc-src/fsvc文件。将 /bin/fsvc- src/native/tomcat5.sh 脚本文件拷贝到/etc/init.d下然后对 /etc/init.d/tomcat5.sh 做一定的修改,在文件头部有一些环境变量设置,请按您系统的真实环境设置。例如:

QUOTE:
JAVA_HOME=/usr/lib/j2sdk1.4-sun
CATALINA_HOME=/usr/share/tomcat5
DAEMON_HOME=/usr/share/tomcat5


TOMCAT_USER=tomcat5 #这里改为一个系统中存在的普通用户的用户名,如果不担心安全问题,可以设置为 root 用户

QUOTE:
TMP_DIR=/var/tmp
CATALINA_OPTS=
CLASSPATH=\
$JAVA_HOME/lib/tools.jar:\
$CATALINA_HOME/bin/commons-daemon.jar:\
$CATALINA_HOME/bin/bootstrap.jar


配置完成后,运行/etc/init.d/tomcat5.sh start,然后打开浏览器测试服务是否正常运行。再运行/etc/init.d/tomcat5.sh stop看是否能停止。

如果确认没有问题,执行如下操作:

QUOTE:
#chkconfig --add tomcat5
#chkconfig --level 2345 on


然后重启系统,服务应当能够正常启动,如果过程中遇到什么问题,请参见 Tomcat 网站常见问题解答:
http://jakarta.apache.org/commons/daemon/faq.html


修改tomcat运行环境jvm虚拟内存大小的方法

Tomcat默认可以使用的内存为128MB,在较大型的应用项目中,这点内存是不够的,需要调大。Windows下,在文件/bin/catalina.bat,Unix下,在文件/bin/catalina.sh的前面,增加如下设置:JAVA_OPTS='-Xms【初始化内存大小】 -Xmx【可以使用的最大内存】'需要把这个两个参数值调大。例如:

QUOTE:
JAVA_OPTS='-Xms256m -Xmx512m'


表示初始化内存为256MB,可以使用的最大内存为512MB。

JAVA_OPTS是增加Java虚拟机的虚拟内存大小。如果要调整Tomcat自己使用的虚拟内存大小,它自己也有一个相应的参数叫CATALINA_OPTS,这两个参数的用法是一样的。

2008年7月18日星期五

如何重新配置Oracle的EM Database Control

今天打算启用一下Oracle Database 11g的Database Control,发现初始并未安装:

[oracle@test126 ~]$ emctl start
EM Configuration issue. /opt/oracle/product/11.1.0/test126.hurray.com.cn_dodd not found.

遇到这类问题,可以通过重新配置,来创建EM的配置文件:

[oracle@test126 11.1.0]$ emca -config dbcontrol db -repos recreate

STARTED EMCA at Aug 28, 2007 11:54:40 AM
EM Configuration Assistant, Version 11.1.0.5.0 Production
Copyright (c) 2003, 2005, Oracle. All rights reserved.

Enter the following information:
Database SID: dodd
Listener port number: 1521
Password for SYS user:
Password for DBSNMP user:
Password for SYSMAN user:
Password for SYSMAN user: Email address for notifications (optional): eygle@eygle.com
Outgoing Mail (SMTP) server for notifications (optional):
-----------------------------------------------------------------

You have specified the following settings

Database ORACLE_HOME ................ /opt/oracle/product/11.1.0

Local hostname ................ test126.hurray.com.cn
Listener port number ................ 1521
Database SID ................ dodd
Email address for notifications ............... eygle@eygle.com
Outgoing Mail (SMTP) server for notifications ...............

-----------------------------------------------------------------
Do you wish to continue? [yes(Y)/no(N)]: Y
Aug 28, 2007 11:56:58 AM oracle.sysman.emcp.EMConfig perform
INFO: This operation is being logged at /opt/oracle/cfgtoollogs/emca/dodd/emca_2007_08_28_11_54_40.log.
Aug 28, 2007 11:57:01 AM oracle.sysman.emcp.EMReposConfig invoke
INFO: Dropping the EM repository (this may take a while) ...
Aug 28, 2007 11:57:16 AM oracle.sysman.emcp.EMReposConfig invoke
INFO: Repository successfully dropped
Aug 28, 2007 11:57:16 AM oracle.sysman.emcp.EMReposConfig createRepository
INFO: Creating the EM repository (this may take a while) ...


Aug 28, 2007 12:08:35 PM oracle.sysman.emcp.EMReposConfig invoke
INFO: Repository successfully created
Aug 28, 2007 12:08:47 PM oracle.sysman.emcp.EMReposConfig uploadConfigDataToRepository
INFO: Uploading configuration data to EM repository (this may take a while) ...
Aug 28, 2007 12:11:45 PM oracle.sysman.emcp.EMReposConfig invoke
INFO: Uploaded configuration data successfully
Aug 28, 2007 12:11:51 PM oracle.sysman.emcp.util.DBControlUtil configureSoftwareLib
INFO: Software library configured successfully.
Aug 28, 2007 12:11:51 PM oracle.sysman.emcp.EMDBPostConfig configureSoftwareLibrary
INFO: Deploying Provisioning archives ...
Aug 28, 2007 12:12:13 PM oracle.sysman.emcp.EMDBPostConfig configureSoftwareLibrary
INFO: Provisioning archives deployed successfully.
Aug 28, 2007 12:12:13 PM oracle.sysman.emcp.util.DBControlUtil secureDBConsole
INFO: Securing Database Control (this may take a while) ...
Aug 28, 2007 12:12:39 PM oracle.sysman.emcp.util.DBControlUtil secureDBConsole
INFO: Database Control secured successfully.
Aug 28, 2007 12:12:39 PM oracle.sysman.emcp.util.DBControlUtil startOMS
INFO: Starting Database Control (this may take a while) ...
Aug 28, 2007 12:14:04 PM oracle.sysman.emcp.EMDBPostConfig performConfiguration
INFO: Database Control started successfully
Aug 28, 2007 12:14:04 PM oracle.sysman.emcp.EMDBPostConfig performConfiguration
INFO: >>>>>>>>>>> The Database Control URL is https://test126.hurray.com.cn:1158/em <<<<<<<<<<<
Aug 28, 2007 12:14:16 PM oracle.sysman.emcp.EMDBPostConfig invoke
WARNING:
************************ WARNING ************************

Management Repository has been placed in secure mode wherein Enterprise Manager data will be encrypted. The encryption key has been placed in the file: /opt/oracle/product/11.1.0/test126.hurray.com.cn_dodd/sysman/config/emkey.ora. Please ensure this file is backed up as the encrypted data will become unusable if this file is lost.

***********************************************************
Enterprise Manager configuration completed successfully
FINISHED EMCA at Aug 28, 2007 12:14:16 PM

Oracle 10g中,配置方法与此相同。
配置完成之后就可以启动EM了:

[oracle@test126 11.1.0]$ emctl start dbconsole
Oracle Enterprise Manager 11g Database Control Release 11.1.0.6.0
Copyright (c) 1996, 2007 Oracle Corporation. All rights reserved.
https://test126.hurray.com.cn:1158/em/console/aboutApplication
Starting Oracle Enterprise Manager 11g Database Control ........ started.
------------------------------------------------------------------
Logs are generated in directory /opt/oracle/product/11.1.0/test126.hurray.com.cn_dodd/sysman/log

如果是Linux环境,你可能还需要在iptables中开放1158端口,增加如下一行:
-A RH-Firewall-1-INPUT -m state --state NEW -m tcp -p tcp --dport 1158 -j ACCEPT

重新启动防火墙之后就可以通过IE在远端连接EM的Database Control了:

[root@test126 sysconfig]# service iptables restart
Flushing firewall rules: [ OK ]
Setting chains to policy ACCEPT: filter [ OK ]
Unloading iptables modules: [ OK ]
Applying iptables firewall rules: [ OK ]
Loading additional iptables modules: ip_conntrack_netbios_ns [ OK ]

学好linux下的c开发,视频教程免费下载

学好linux下的c开发,视频教程免费下载


http://bbs.uying.com/Attachment/20060411/20060411tSRlhL_bK48m5M2oqcvUuLBcRIiwdP.torrent
请直接用迅雷BT,或者超级旋风下载

2008年7月17日星期四

nice命令详解

【命令】nice — 调整程序运行的优先级
【格式】nice [OPTION] [command [arguments...]]
【说明】

当前程序运行优先级基础之上调整指定值得到新的程序运行优先级,用新的程序运行优先级运行命令行"command
[arguments...]"。优先级的范围为-20 ~ 19
等40个等级,其中数值越小优先级越高,数值越大优先级越低,既-20的优先级最高,
19的优先级最低。若调整后的程序运行优先级高于-20,则就以优先级-20来运行命令行;若调整后的程序运行优先级低于19,则就以优先级19来运行命
令行。若 nice命令未指定优先级的调整值,则以缺省值10来调整程序运行优先级,既在当前程序运行优先级基础之上增加10。
若不带任何参数运行命令nice,则显示出当前的程序运行优先级。
例1:
1. # nice
2. 0
3. #在例1中,不用任何参数执行命令"nice"(见第1行),所以显示出当前的程序运行优先级为0(见第2行)。由此可知系统缺省的程序运行优先级为0。
例2:
1. # nice nice
2. 10
3. #在例2中,第1个nice命令以缺省值来调整第2个nice命令运行的优先级,既在系统缺省的程序运行优先级0的基础之上增加10,得到新的程序运行优先级10,然后以优先级10来运行第2个nice命令;第2个nice命令显示当前程序运行的优先级为10。
例3:
1. # nice nice nice
2. 19
3. #在
例3中,第1个nice命令以缺省值来调整第2个nice命令运行的优先级,既在系统缺省的程序运行优先级0的基础之上增加10,得到新的程序运行优先级
10,然后以优先级10来运行第2个nice命令;第2个nice命令又以缺省值来调整第3个nice命令运行的优先级,既在第2个nice命令运行优先
级基础之上再增加10,得到新的程序运行优先级20,但20大于最高程序运行优先级19,所以以优先级19来运行第3个nice命令;第3个nice命令
显示当前程序运行的优先级为19。
【参数说明】
-n, --adjustment=ADJUST 指定程序运行优先级的调整值。
优先级的范围为-20~19,当调整后的优先级小于-20时,以优先级-20 来运行程序(见例4);当调整后的优先级大于19时,则以19的优先级运行程序(见例5)。
例4:
1. # nice -n -21 nice
2. -20
3. #在例4中,以参数“-n”的形式指定程序运行优先级的调整值,系统缺省优先级0加上调整值-21得到新的优先级-21(小于-20),因此程序最终的运行优先级为-20。
例5:
1. # nice --adjustment=20 nice
2. 19
3. #在例5中,以参数“--adjustment=ADJUST”的形式指定程序运行优先级的调整值,系统缺省优先级0加上调整值20得到新的优先级20(大于19),因此程序最终的运行优先级为19。
注意:在使用“--adjustment=ADJUST”形式指定程序运行优先级的调整值时,中间的等号可以省略。在例5中,也可运行命令行“nice --adjustment 20 nice”。
还可以使用参数“-ADJUST”的形式来指定程序运行优先级的调整值,其中,ADJUST为指定的程序运行优先级调整值,可以为负数,也可以为正数,如例6所示。
例6:
1. # nice --1 nice
2. -1
3. # nice -+1 nice
4. 1
5. # nice -1 nice
6. 1
7. #在例6中,参数“--1”、“-+1”和 “-1”中的第一个字符“-”都是语法定义的指定程序运行优先级调整值的标志符,第一个字符“-”之后的值为指定的程序运行优先级的调整值。
在nice命令中,可以同时指定多个程序运行优先级调整值,但只有最后一次指定的数值有效,如例7所示。
例7:
1. # nice -n -20 --adjustment +19 -3 nice
2. 3
3. #在例7中,通过命令行同时指定了优先级调整值“-20”、“+9”和“3”,但最后生效的程序运行优先级调整值为最后指定的数值“3”。
注意:只有具有root权限的用户才可以调整高程序运行的优先级,既指定的调整值可以为负数,如例8所示。
例8:
1. # su thinkerABC
2. $ nice -n -1 nice
3. nice: cannot set priority: Permission denied
4. $ nice -n 1 nice
5. 1
6. $在例8中,我们将用户改为非root用户权限的thinkerABC,这时调高程序运行优先级1个级别时操作失败,系统提示权限不足。而调低优先级1个级别时,操作就可以成功。
--help 显示nice命令的帮助信息,详见例9。
例9:
1. # nice --help
2. Usage: nice [OPTION] [COMMAND [ARG]...]
3. Run COMMAND with an adjusted scheduling priority.
4. With no COMMAND, print the current scheduling priority. ADJUST is 10
5. by default. Range goes from -20 (highest priority) to 19 (lowest).
6.
7. -n, --adjustment=ADJUST increment priority by ADJUST first
8. --help display this help and exit
9. --version output version information and exit
10.
11. Report bugs to .
12. #在例9中,用参数“--help”执行nice命令,则显示该命令的帮助信息,见例9的第2行~第11行。
--version 输出nice命令的版本信息,详见例10。
例10:
1. # nice --version
2. nice (GNU sh-utils) 2.0.12
3. Written by David MacKenzie.
4.
5. Copyright (C) 2002 Free Software Foundation, Inc.
6. This is free software; see the source for copying conditions. There is NO
7. warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
8. #在例10中,用参数“--version”运行nice命令,则显示该命令的版本信息,见例10的第2行~第7行。(注:本例是在Red Hat 8.0下运行的结果。)
参考文献:
[1] Linux man pages

删除表空间的操作

一个用户要删除数据库的表空间,首先该用户要具备drop tablespace的权限

在当前用户下执行以下语句来查询确认

select a2.username,a1.privilege from dba_sys_privs a1 , user_role_privs a2
where a1.privilege = 'DROP TABLESPACE'
and a1.grantee =a2.granted_role


SQL> conn wulw/123@ibm
已连接。
SQL> select a2.username,a1.privilege from dba_sys_privs a1 , user_role_privs a2
2 where a1.privilege = 'DROP TABLESPACE'
3 and a1.grantee =a2.granted_role;

USERNAME PRIVILEGE
------------------------------ ----------------------------------------
WULW DROP TABLESPACE

如果没有 drop tablespace,请先用更高级的用户(如sys)给予授权

SQL> conn sys/oracle@ibm as sysdba;
已连接。
SQL> grant drop tablespace to wulw ;

授权成功。


以上前提条件确认完,下面开始实验.

确认已有的表空间

SQL> select a.TS# ,a.NAME , b.NAME from v$tablespace a,v$datafile b
2 where a.TS# = b.TS#;

TS# NAME NAME
0 SYSTEM L:\ORACLE\ORADATA\IBM\SYSTEM01.DBF
1 UNDOTBS1 L:\ORACLE\ORADATA\IBM\UNDOTBS01.DBF
3 CWMLITE L:\ORACLE\ORADATA\IBM\CWMLITE01.DBF
4 DRSYS L:\ORACLE\ORADATA\IBM\DRSYS01.DBF
5 EXAMPLE L:\ORACLE\ORADATA\IBM\EXAMPLE01.DBF
6 INDX L:\ORACLE\ORADATA\IBM\INDX01.DBF
7 ODM L:\ORACLE\ORADATA\IBM\ODM01.DBF
8 TOOLS L:\ORACLE\ORADATA\IBM\TOOLS01.DBF
9 USERS L:\ORACLE\ORADATA\IBM\USERS01.DBF
10 XDB L:\ORACLE\ORADATA\IBM\XDB01.DBF
12 TDATA_01 L:\ORACLE\ORADATA\IBM\TDATA_01.ORA
14 TINDEX_01 L:\ORACLE\ORADATA\IBM\TINDEX_01.ORA

已选择12行。(为看起来直观,上面的显示作了手工格式化)

创建新的测试表空间:

SQL> create tablespace mytbs01
2 logging
3 datafile 'L:\ORACLE\ORADATA\IBM\mytbs01.dbf' size 10m REUSE ;

表空间已创建。

SQL> CREATE TABLESPACE "MYTBS02"
2 LOGGING
3 DATAFILE 'L:\ORACLE\ORADATA\IBM\MYTBS02.dbf' SIZE 10M REUSE ;

表空间已创建。

如果表空间里面没有任何数据对象,可以直接删除.


SQL> drop tablespace mytbs01;

表空间已丢弃。

这种删除方式相关的数据文件仍然存在于磁盘上.

(可以进入数据文件所在目录L:\ORACLE\ORADATA\IBM 进行查看 MYTBS01.DBF )


如果表空间里面含有数据对象,那么该表空间就不能像上面那样做直接删除了.


SQL> create tablespace mytbs01
2 logging
3 datafile 'L:\ORACLE\ORADATA\IBM\mytbs01.dbf' size 10m REUSE;

表空间已创建。

SQL> create table test(mobile number(13))
2 tablespace mytbs01;

表已创建。

SQL> drop tablespace mytbs01;
drop tablespace mytbs01
*
ERROR 位于第 1 行:
ORA-01549: 表空间非空,请使用 INCLUDING CONTENTS 选项

看到了吧,提示ora-01549错误.

如果要删除该表空间,可加上including contents子句.

如: drop tablespace mytbs01 including contents ;

如果想在删除表空间的同事也删除掉对应的数据文件,那就在上面的语句最后加上 and datafiles

成为 drop tablespace mytbs01
including contents and datafiles;


SQL> drop tablespace mytbs01
2 including contents and datafiles;

表空间已丢弃。

要注意的一点是,如果drop tablespace语句中含有datafiles,那datafiles之前必须有contents关键字,不然会提示ora-01911错误:


SQL> drop tablespace mytbs02
2 including datafiles;
including datafiles
*
ERROR 位于第 2 行:
ORA-01911: 需要 CONTENTS 关键字

接下来的实验是:

如果表空间A中有一个表ta,表空间B中有一个表tb,而ta与tb有着某种关系,那么是否可以按上面的方法直接干掉表空间A和表空间B呢?

看试验过程:


SQL> create tablespace mytbs01
2 logging
3 datafile 'L:\ORACLE\ORADATA\IBM\mytbs01.dbf' size 10m REUSE;

表空间已创建。

SQL> CREATE TABLESPACE "MYTBS02"
2 LOGGING
3 DATAFILE 'L:\ORACLE\ORADATA\IBM\MYTBS02.dbf' SIZE 10M REUSE ;
CREATE TABLESPACE "MYTBS02"
*
ERROR 位于第 1 行:
ORA-01543: 表空间 'MYTBS02' 已经存在


SQL> create table test(mobile number(13))
2 tablespace mytbs01;

表已创建。

SQL> create table test2(mobile number(13))
2 tablespace mytbs02;

表已创建。

SQL> alter table TEST2
2 add primary key (mobile);

表已更改。

SQL> ALTER TABLE test
2 ADD CONSTRAINT FOREIGN con_mobile REFERENCES test2(mobile);

表已更改。

以上的意思是:在表空间mytbs01上创建表test,在表空间mytbs02上创建表test2,两个表test和test2以外键相关联,test2为主表,test为从表.

现在尝试能否用上面的语句直接干掉mytbs02:


SQL> drop tablespace mytbs02;
drop tablespace mytbs02
*
ERROR 位于第 1 行:
ORA-01549: 表空间非空,请使用 INCLUDING CONTENTS 选项


SQL> drop tablespace mytbs02
2 including contents;
drop tablespace mytbs02
*
ERROR 位于第 1 行:
ORA-02449: 表中的唯一/主键被外部关键字引用


SQL> drop tablespace mytbs02
2 including contents and datafiles;
drop tablespace mytbs02
*
ERROR 位于第 1 行:
ORA-02449: 表中的唯一/主键被外部关键字引用

可见主表所在表空间因为表与其他空间上的表有联系,所以没办法直接删掉.


那mytbs01表空间能不能干掉?请看:

SQL> drop tablespace mytbs01
2 including contents and datafiles;

表空间已丢弃。

SQL> drop tablespace mytbs02
2 including contents and datafiles ;

表空间已丢弃。


嘿嘿,从表test所在的表空间mytbs01能直接干掉,而且从表的表空间干掉后,主表test2所在的表空间mytbs02也能干掉了!

那么,如果我只想干掉主表所在的表空间,又不想干掉从表所在的表空间那怎么办?

很简单,最笨的一招就是想把两个表的关联关系给灭了,(在上面的两个表中,就是把那个外键给删了)再把主表表所在的表空间删了.但这种方法可不太现实,如果一个表空间里有成百上千个对象与别的表空间里的对象有联系,总不能一个一个去"解铃"吧? 即使你本人就是"系铃"人,估计你也要"解"到郁闷死!

一个更简单的方法当然是级联删除了!

drop tablespace mytbs02
including contents and datafiles cascade constraints

试验如下:


SQL> create tablespace mytbs01
2 logging
3 datafile 'L:\ORACLE\ORADATA\IBM\mytbs01.dbf' size 10m REUSE;

表空间已创建。

SQL> CREATE TABLESPACE "MYTBS02"
2 LOGGING
3 DATAFILE 'L:\ORACLE\ORADATA\IBM\MYTBS02.dbf' SIZE 10M REUSE ;

表空间已创建。

SQL> create table test(mobile number(13))
2 tablespace mytbs01;

表已创建。

SQL> create table test2(mobile number(13))
2 tablespace mytbs02;

表已创建。

SQL> alter table TEST2
2 add primary key (mobile);

表已更改。

SQL> ALTER TABLE test
2 ADD CONSTRAINT FOREIGN con_mobile REFERENCES test2(mobile);

表已更改。

SQL> drop tablespace mytbs02
2 including contents and datafiles cascade constraints;

表空间已丢弃。


OK!正常搞定!


补充一句:以上试验环境为 windows2000+oracle9iR2

oracle10g创建表空间

create tablespace tools datafile 'D:\oraclexe\oradata\XE\tools.dbf' size 300M;


alter user ORABM default tablespace tools quota 500M;

一般第一句就行啦。

2008年7月16日星期三

批量改名的一个DOS脚本

@echo off
set num=0
set savefile=恢复改名
if {%1}=={} goto :useageexit
if {%2}=={} goto :useageexit
if {%3}=={} goto :useageexit
if exist %savefile%.bat (
attrib %savefile%.bat -h -s -r
)
echo @echo off >%savefile%.bat
for /R %3 %%v IN (%1.%2) DO (
call:rn %%v %2
)
echo 已经执行完改名!
echo echo 恢复完毕!>>%savefile%.bat
echo del %savefile%.bat >>%savefile%.bat
echo pause >>%savefile%.bat
goto :EOF
:useageexit
echo ● 站好了听 ● 
echo █┳ 我给你说使 ┗█┛
echo ┏┓ 用方法! ┛┗
echo ----------------------------------------------------------
echo 本程序由小朱制造
echo ----------------------------------------------------------
echo 使用方法: %~n0 文件名 扩展名 路径
echo ----------------------------------------------------------
echo 功能:
echo 本程序将指定类型的文件批量改名为以数字递增表示的文件名;
echo 参数说明:
echo ----------------------------------------------------------
pause
echo 文件名:
echo 指不包括扩展名的纯文件名,可以使用通配符('*','?');
echo 扩展名:
echo 就是扩展名了啊,不要加点('.'),也可以使用通配符号('*','?');
echo 路径:
echo 就是路径,当用点(.)的时候表示当前路径(程序所在路径);
echo 注意:
echo 指定一个路径后,此路径下以及它的所有子路径下的所有符合的文件都会被改名;
echo ----------------------------------------------------------
echo 例子:
echo 如你要将整个D:盘'a'开头的jpg文件都改名
echo %~n0 a* jpg D:\

echo 如你要将当前目录及其下级所有目录中的所有jpg文件都改名
echo %~n0 * jpg .
echo ----------------------------------------------------------
echo 恢复:
echo 每运行一次后,我都会在你指定的最高路径下建立一个可以恢复改名的".bat"文件
echo 命名为"%savefile%.bat",当然如果目录已经有这样一个文件,我会覆盖它
echo 然后你只要双击运行"%savefile%.bat"(或直接在Dos窗口运行它)就可以把最近一次改
echo 名操作恢复;
echo ----------------------------------------------------------
pause
echo 最后,可能是dos本身的问题,当文件名中包含空格的时候,dos好象会出错,只取空格前的
echo 部分为文件名,哎,当初纯dos下可没有带空格的文件的呀!
goto :EOF
:rn
set /a num+=1
if exist %~p1%num%.%2 goto :rn
ren %1 %num%.%2
echo ren %~dp1%num%.%2 %~nx1 >>%savefile%.bat

2008年7月15日星期二

如何查看Oracle版本及安装了哪些选项?

系统环境:
1、操作系统:Windows 2000
2、数据库: Oracle 8i R2 (8.1.6) for NT 企业版
3、安装路径:C:\ORACLE

说明:

1、查看数据库版本
SQL> select banner from sys.v_$version;

BANNER
----------------------------------------------------------
Oracle8i Enterprise Edition Release 8.1.6.0.0 - Production
PL/SQL Release 8.1.6.0.0 - Production
CORE 8.1.6.0.0 Production
TNS for 32-bit Windows: Version 8.1.6.0.0 - Production
NLSRTL Version 3.4.1.0.0 - Production

2、查看安装了哪些选项
SQL> col PARAMETER format a60
SQL> col VALUE format a10
SQL> select * from sys.v_$option;

PARAMETER VALUE
------------------------------------------------------------ ----------
Partitioning TRUE
Objects TRUE
Parallel Server FALSE
Advanced replication TRUE
Bit-mapped indexes TRUE
Connection multiplexing TRUE
Connection pooling TRUE
Database queuing TRUE
Incremental backup and recovery TRUE
Instead-of triggers TRUE
Parallel backup and recovery TRUE

PARAMETER VALUE
------------------------------------------------------------ ----------
Parallel execution TRUE
Parallel load TRUE
Point-in-time tablespace recovery TRUE
Fine-grained access control TRUE
N-Tier authentication/authorization TRUE
Function-based indexes TRUE
Plan Stability TRUE
Online Index Build TRUE
Coalesce Index TRUE
Managed Standby TRUE
Materialized view rewrite TRUE

PARAMETER VALUE
------------------------------------------------------------ ----------
Materialized view warehouse refresh TRUE
Database resource manager TRUE
Spatial TRUE
Visual Information Retrieval TRUE
Export transportable tablespaces TRUE
Transparent Application Failover TRUE
Fast-Start Fault Recovery TRUE
Sample Scan TRUE
Duplexed backups TRUE
Java FALSE
OLAP Window Functions TRUE

已选择33行。

SQL> set head off feed off pages 0 serveroutput on
SQL> begin
2 dbms_output.put_line('Port String: '||dbms_utility.port_string);
3 end;
4 /
Port String: IBMPC/WIN_NT-8.1.0

2008年7月8日星期二

Oracle11g 在RHEL5上的安装

一、环境

新鲜出来的Oracle 11.1.0.6的文档中对以下Linux发行版提供了对

Asianux 2.0

Asianux 3.0

Oracle Enterprise Linux 4.0

Oracle Enterprise Linux 5.0

Red Hat Enterprise Linux 4.0

Red Hat Enterprise Linux 5.0

SUSE Enterprise Linux 10.0 等linux系统的支持。

目前我们选择的系统环境是在Red Had Enterprise L5上安装Oracle11g。



二、oracle11g的安装

2.1系统要求:

  2.1.1 物理内存:1G(根据oracle的推荐)

2.1.2 交换空间 1.5G (如果物理内存小于512M,那么swap=2*RAM 设置2G,

如果物理内存大于2G,那么swap=RAM,

如果物理内存大于8G,那么swap=0.75*RAM

512-2G之间的,1.5*RAM就可以了)

/tmp需要400MB,安装企业版的Oracle需要3.47GB,默认库又需要1.6GB。

可以用grep MemTotal /proc/meminfo检查。如下可以临时转移/tmp到有空闲资源的地方。/boot 200m

2.1.3 禁用secure Linux (SELinux)和防火墙

关于禁用secure Linux有很多办法,可以在安装LINUX的过程中禁用,也可以在系统里面进行禁用,通过编辑/etc/selinux/config 文件禁用secure linux,确认其中的SELINUX标记如下:SELINUX=disabled。也可以通过GUI工具(Applications > System Settings > Security Level),选择SELinux禁用该属性;



禁 禁用防火墙

iptables –F

service iptables save



2.1.4 已经安装下列包(为简单起见,安装RHEL5时最好选择全部安装):

检查如下的包是否装全了(rpm -qa | grep 包名)

rpm -qa | grep binutils-2.17.50.0.6-2.el5

rpm -qa | grep compat-libstdc++-33-3.2.3-61

rpm -qa | grep elfutils-libelf-0.125-3.el5

rpm -qa | grep elfutils-libelf-devel-0.125

rpm -qa | grep glibc-2.5-12

rpm -qa | grep glibc-common-2.5-12

rpm -qa | grep glibc-devel-2.5-12

rpm -qa | grep gcc-4.1.1-52

rpm -qa | grep gcc-c++-4.1.1-52



rpm -qa | grep libaio-0.3.106

rpm -qa | grep libaio-devel-0.3.106

rpm -qa | grep libgcc-4.1.1-52

rpm -qa | grep libstdc++-4.1.1

rpm -qa | grep libstdc++-devel-4.1.1-52

rpm -qa | grep make-3.81-1.1

rpm -qa | grep sysstat-7.0.0

rpm -qa | grep unixODBC-2.2.11

rpm -qa | grep unixODBC-devel-2.2.11



第2张盘 Server下

rpm -Uvh compat-libstdc++-33-3.2.3-61.i386.rpm

rpm -Uvh libaio-devel-0.3.106-3.2.i386.rpm

rpm -Uvh libstdc++-devel-4.1.1-52.el5.i386.rpm

rpm -Uvh unixODBC-2.2.11-7.1.i386.rpm

rpm -Uvh unixODBC-devel-2.2.11-7.1.i386.rpm



第3张盘 Server下

rpm -Uvh sysstat-7.0.0-3.el5.i386.rpm

rpm -Uvh compat-db-4.2.52-5.1.i386.rpm





三、增加用户:

su - root

groupadd dba

groupadd oinstall

useradd -c "Oracle Owner" -g oinstall -G dba oracle

passwd oracle





四、创建安装oracle的目录

su – root

mkdir -p /opt/app/oracle/product/11.1.0/db_1

chown -R oracle.oinstall /opt/app

chmod -R 775 /opt/app



五、配置oracle初始化参数:(root用户)修改 /etc/sysctl.conf,追加如下内容:

# First line:SEMMSL SEMMNS SEMOPM SEMMNI

kernel.sem=1055 32000 100 128

kernel.shmmax=2147483648

kernel.shmall = 2097152

net.ipv4.tcp_sack = 0

net.ipv4.tcp_timestamps = 0

net.ipv4.conf.default.rp_filter = 0

net.core.optmem_max = 65535

net.core.rmem_default = 4194304



net.core.wmem_default = 262144

net.core.rmem_max = 4194304

net.core.wmem_max = 262144

fs.file-max = 6553600

net.ipv4.ip_local_port_range = 1024 65000

上述值中fs.file-max一项,Oracle的建议是512 * PROCESSES。

然后执行/sbin/sysctl -p激活(root用户)。



六、(root用户)修改Shell限制

在/etc/security/limits.conf中增加:

oracle soft nproc 2047

oracle hard nproc 16384

oracle soft nofile 1024

oracle hard nofile 65536



在/etc/pam.d/login增加或创建:

session required /lib/security/pam_limits.so //对64位系统这条不需要

session required pam_limits.so





对Bourne、Bash或Korn shell,编辑/etc/profile增加:

if [ $USER = "oracle" ]; then

if [ $SHELL = "/bin/ksh" ]; then

ulimit -p 16384

ulimit -n 65536

else

ulimit -u 16384 -n 65536

fi

fi





对C shell,编辑/etc/csh.login增加:

if ( $USER == "oracle" ) then

limit maxproc 16384

limit descriptors 65536

endif





七、(oracle用户)修改环境变量。选择好你的安装目录后,直接编辑上面提到的shell环境文件

用oracle登录把下列行加在.bash_profile文件末尾,注意把其中ORACLE_SID换成自己的实例名:



export ORACLE_BASE=/opt/app/oracle //安装路径

export ORACLE_BASE

#export ORACLE_HOME=/opt/app/oracle/product/11.1.0/db_1

#export ORACLE_HOME

export ORACLE_SID=orcl

export ORACLE_SID

#export PATH=$PATH:$ORACLE_HOME/bin

#export LD_LIBRARY_PATH=$ORACLE_HOME/lib



TMPDIR=/tmp

export TMPDIR



export DISPLAY=:0.0



你的IP:0.0(如果是在本地安装,不要加IP,直接DISPLAY=:0.0就可以了)

/********

完成安装以后还要加上:

export ORACLE_HOME=$ORACLE_BASE/product/11.1.0/ db_1 //HOME路径

export PATH=$PATH:$ORACLE_HOME/bin

export LD_LIBRARY_PATH=$ORACLE_HOME/lib



*************/





八、(在oracle用户下登录图形界面)执行./runInstaller

2008年7月3日星期四

用Debian建设一个自己的Linux发行版(转)

建设一个自己的Linux发行版是每个自由开源软件爱好者的一个梦想.这曾经是一件难度非常高的事情,能做一个Linux发行版的人也是凤毛麟角,自己能 做一个Linux发行版曾经也是极其荣耀的事情.但是,本身提倡发挥自身潜力,提倡自己亲身实践精神的自由开源世界,是不会把大家都期盼的事情故意打扮成 远离大众的冰雪美人,她会不断地改革自身的发展机制,让每个人都逐渐地参与到自己的发展中间来,从而也促进自身的发展.

简而言之,现在,做一个Linux发行版并不是困难的事情.
一 做一个Linux发行版的基础问题.
我想,要做一个Linux发行版,你首先要考虑的问题是:
1 为什么要一个Linux发行版?
2 是打算从无做起,还是在其他的Linux发行版的基础上进行修改?
3 做一个自己的Linux发行版的关键和难点是什么?
4 选择哪个现有的Linux发行版开始自己的工作.

先来看第一个问题,为什么要一个Linux发行版?
这个问题的答案很多,比较普遍的一种就是我就想做,没有理由,一定要说理由的话,我就借用一句时髦的话:Just for Fun!,这就是很好的理由了.

然 后一个重要的理由是:我需要一个满足我自己的特殊需要的Linux发行版,比如说:我正在学习Perl编程,我需要一个小型的,随时跟着我的perl编译 系统,其他的东西都可以不要,那么我需要制作一个支持USB启动的Linux发行版,上面只有基本系统加编辑器加Perl,我可以随身携带,只要有电脑我 就可以随时开始我的学习.

至于我为什么想做一个Linux发行版,原因很简单:我是一个老师!我觉得做一个符合教育规律,以教育相关软件 为主的Linux发行版很有必要,再具体一点,我是一个地理老师,现在的新课程标准与时俱进,要求学生学习GIS知识,无论是必修模块还是选修模块都有要 求.我看不惯我们的地理教育者们一讲到 GIS教育,就言必称ArcInfo和MapInfo,仿佛那些即便是国内很富有的学术研究机构都不舍得破费购买的软件是随处可拣一样.在在自由开源的软 件世界里,有着极其丰富的3S(GIS,GPS,RS)地理软件.就GIS软件而言,就有几十上百种之多,著名的如Grass QGis等,这些免费的软件虽然在功能上比不上商业软件,但是足以满足以理解基本GIS基本概念为目的的一般GIS教学.而且这些软件还有一些自己的优点 和长处.再考虑到我们目前的学校电脑都是运行Window这一现实,我就想做一个自己的,以光盘形式启动和运行的,以GIS软件为主的,性能和运行速度都 令人满意的Linux发行版.
(注:类似的系统目前世界上已经有多个,包括联合国教科文组织的FreeDUC,即含有QGis,只不过还没有支持中文的)

自 己要做一个Linux发行版的第三个理由就是为名为利,有些人做一个发行版是为了赚钱和盈利,这并不与自由软件以及GPL版权发生冲突,RedHat近来 的盈利给许多的年轻人带来了新的幻想,都期待自己也许能够成为下一代的比尔盖茨.另外一些人做了自己的发行版就在网络上提供免费下载,使用的人越多他就越 高兴,他只收获自己所看重的善名和对自己技术的赞誉.

总之,有很多的理由使我们需要建设一个自己的Linux发行版,尤其是工作在教育第一线的广大教师!

2 如何开始做一个自己的Linux发行版
然后我们要解决第二个问题,我做一个Linux发行版是选择从零做起还是在别人的Linux发行版的基础上,加以以自己的意愿而进行的修改呢?

其实,我们所说的从零开始是相对而言.你从哪个零开始呢?是从自己编写一个OS开始?还是从自己编译配置现有的Linux内核开始?

我想我们是不可能从真正的零开始的,那也绝对不可能是一个人所能完成的工作,我们应该在前人的工作的基础上开始自己的工作.就制作自己的Linux发行版而言,就是这种对前人工作的继承可以划分为这么两种情况:

A 只基于现有的Linux内核及其他源码做自己的Linux发行版
这 种情况其实就是基于LFS(Linux from Scratch)制作自己的Linux发行版.由于LFS是在利用源代码的基础上,从零开始建设自己的Linux发行版,因此,采用这种方法制作自己的发 行版最能使制作者深入了解Linux中各种软件之间的关系,深入了解Linux内部的一些运行机制.但这种方式耗时长,难度相对较大,适合对事情喜欢刨根 问底的人士.
基于LFS制作的Linux发行版看起来都是个人玩赏的作品,闻名于大众的作品很少.

B 基于现有的其他Linux发行版制作自己的Linux发行版
这种情况就是在现有的著名的Linux发行版中,挑选自己中意的Linux发行版再按照自己的意愿进行剪裁,添加,加工,然后做成自己的Linux发行版.

这种方式简单快速,适合于一般用户或者急于制作出成品的用户.现在采用这种方式制作的Linux发行版犹如恒河沙数,已经难以统计,其中著名的作品不少,是否会有一两个成为下一代的OS霸主那也难说。

为了快速简便地达到做一个自己的Linux发行版的目的,我们选择在已有的Linux发行版的基础上加以改造以建立自己的发行版的方式。那么,我们选择哪个发行版作为我们的起点呢?回答这个问题之前,我们先来解决第三个问题。

3 做一个自己的Linux发行版的关键和难点是什么?
做一个自己的Linux发行版的关键和难点在哪里呢?初入门者可能觉得难点在于如何启动一个自己的Linux系统,其实不然。我想定制一个自己的Linux发行版的关键就在于解决发行版之中的各种软件包之间的以来关系。

自 由开源软件既使用前人的源码,也对后人开放自己的源码,所以,自由开源软件总是相互使用各种不同的软件包,这一方面给软件的开发带来了极大的便利,另一方 面也使各个软件包的之间的关系错综复杂,常给软件的集成带来灾难性的后果。比如说,你打算在你的发行版中安装软件A,B和C,而A的运行需要依赖包 A1,A2和A3,B的运行需要依赖B1和B2,C的运行需要依赖C1,为了安装软件A,B,C,你就必须安装A1,A2,A3,B1,B2,C1,安装 好了后,发现A1的运行又要使用库A11和A12,C1的运行需要使用库C11,等你费了九牛二虎之力找到A11,A12和C11的源码来编译,安装之 后,才发现A12和C11是相互冲突的!你哭吧!

所以,我认为做一个自己的Linux发行版的关键在于正确地解决好各个软件包之间的依赖关系。

4 选择哪个现有的Linux发行版开始自己的工作
那 么到底选择哪个现有的Linux发行版开始自己的工作呢?我想这会司一个萝卜和青菜的问题,你可以选择FC,你也可以选择Slackware,但是从我上 面的叙述来看,显然我是倾向于选择基于Debian来开发定制自己的发行版的。我认为Debian的最大长处就在于其先进的,独特的软件包管理方式,通过 世界各地的优秀的程序员的辛勤无私的工作,很好地解决了各种自由开源软件之间的依赖,冲突等关系,使Debian拥护可以采用一种所有操作系统中最便利的 方式安装软件,同时也给基于Debian开发定制自己的发行版带来了极大的便利性。

当然,也有人可能会说,FreeBSD的软件包的管理方式也很便利和强大,为什么不选择FreeBSD呢?这是因为FreeBSD并不遵守GPL版权,其自己的FreeBSD许可证并不允许基于FreeBSD开发个性化的发行版,所以我们只有望洋兴叹。

现 在我打算基于Debian开发定制我的发行版了,还能不能有更简便的开发之道呢?考虑到我的实际开发需求,我只需要开发一个用于教学用的演示系统,我最好 做成一个LiveCD,即在光盘上运行的Linux定制系统,我打算基于Knoppix或Morphix系统来开发我的定制系统。

Knoppix 是一套基于Debian开发的著名的LiveCD系统,使用了一些独特的技术使得在它上面的再开发又比在Debian上面开发更容易,而 Morphix又是基于Knoppix开发的模块式的LiveCD,从它的名字看,Morphix的意思就是变形Linux,它是为定制个性化Linux 而生的!它把定制Linux系统的简便性又推进了一步!

但人们还是不满足,有人还在开发remaster,开发TROM等,他们的目标在 于:在一个图形界面下,点几下鼠标,新的定制的发行版就产生了!这一天可能不要多久就要来到!这是令人振奋的消息还是令人恐怖的消息呢?至少我是感觉挺紧 张的,我要快点写这篇文章,赶在那种软件产生之前完成这篇文章,否则的话,只要点几下鼠标就可以造出自己的发行版,谁还来看我的文章呢?

Debian -->Knoppix-->Morphix,基于这三个发行版的定制开发越来越容易,但在我的实际运用中,基于Morphix以及更简便的 TROM工具的开发经常出错,而基于Knoppix的开发却很稳定,所以,我决定基于Knoppix开发一个中文版的GIS发行版。

二 具体的开发过程。
以下是我的具体开发过程,当然是在参照各位前贤的文章基础上写的,但根据我自己的理解,并针对新的Knoppix版本做了一些变动。文章完全是在一台Windows机器上凭记忆所写,所以有些细节上的错误。

1 准备工作:
我 想准备工作的第一步就是看一下你的电脑是否足够强大!最好一G内存,二G交换分区,十G以上硬盘!当然256M内存+1G交换分区也能工作,慢一些而已。 硬盘空间尽可能大,我开始的时候大手大脚地进行定制,竟然搞到8G硬盘不够空间!当然,我下面写的过程是小心翼翼地使用硬盘空间,及时地删除和卸载不用的 空间,应该有3-4G硬盘空余就可以了。

然后要安装cloop的相关软件。引入cloop我想是Knoppix的最大特点,我使用的是Debian系统,那么:
#apt-get install cloop-utils
就可以了。

  再然后就是获得最新版本的Knoppix了,当前的最新版本是3.7了,但似乎还没有正式宣布,我们就使用3.6的版本吧,后面假设我下载来的是knoppix36.iso吧。刻不刻盘不影响后面的定制工作,我就不刻盘了。

  再就是建立工作目录,我在工作目录中建立了一个/wen的目录,其中又建立了old和new两个子目录,显然前者是存放knoppix36.iso的原有内容,而后者将存放经过我改造后的内容。

2 开始定制改造。
  先要挂载knoppix36.iso这个滚滚盘映像文件:
  #mount -o loop -t iso9660 /root/knoppix36.iso /mnt/cdrom
显然我下载的knoppix在root目录下而我把它挂载在/mnt/cdrom下,后面这两个参数都可以根据实际情况修改。

   现在你可以进入到/mnt/cdrom中去看一下knoppix中到底有些什么东西了,有一个boot目录,显然这还启动有关,以后你要修改启动画面 等,就要去修改这里面的东西了,我们现在暂时不理会这些。还有一个Knoppix目录,它下面有一些文件,其中一个KNOPPIX文件巨大达到近 700M!这个就是我们要修改的主体了!

  下面我们先把/mnt/cdrom下的所有内容拷贝到/wen/new下面,因为我们需要修改的只有KNOPPIX这一个文件,等下我们会删除的,但现在还有用:
  #cd /mnt/cdrom
# cp -R * /wen/new/
#umount /mnt/cdrom
你现在甚至可以删除knoppix36.iso文件以节约硬盘空间了。
   
  下面我们要对/wen/new/KNOPPIX/KNOPPIX文件动手术了,这个文件巨达700M,还是使用cloop压缩的,所以我们首先要解压:
  #cd /wen/new/KNOPPIX/
#extract_compressed_fs KNOPPIX > tmp.iso
将解压的结果以tmp.iso的形式放在根目录下。注意这个解压过程极其漫长,我一般这时候烧开水,泡方便面,慢慢吃,打扫桌面,解压完了吗?
  No!早着呢!出去运动一下吧,等你把方便面消耗得差不多了,解压就基本完成了,看一下根目录,吓你一跳,tmp.iso竟然将近2G!
现在一定要删除文件/wen/new/KNOPPIX/KNOPPIX,因为我们要对tmp.iso进行改造以生成新的KNOPPIX文件,切记! 

再挂载tmp.iso并把所有内容拷贝到/wen/old/KNOPPIX下面,你应该相当熟悉了:
  #mount -o loop -t iso9660 /tmp.iso /mnt/cdrom
#mkdir /wen/old/KNOPPIX
  #cd /mnt/cdrom
#cp -r * /wen/old/KNOPPIX  
  #umount /mnt/cdrom  
为了节约硬盘,你现在连/tmp.iso也可以删除。

再下面就要进入具体改造工作阶段了,这里主要是使用了chroot这个命令以及Debian系统便利的apt-get的安装、卸载软件,需要注意的事情有:
  为了使用网络,你需要在chroot环境下挂载proc,还要注意chroot环境下能够正确解析域名。后面这个问题我是这样解决的,再开一个console窗口,执行:
  #cp /etc/apt/sources.list /wen/old/KNOPPIX/etc/apt/sources.list
#cp /etc/resolv.conf /wen/old/KNOPPIX/etc/resolv.conf
这样做的前提是你没有chroot之前你的网络是通畅的。还有一个解决方法是我先ping一下自己sources.list表中的apt源以获得IP,直接写入到chroot后的sources.list文件之中以省却DNS解析的麻烦。
#chroot /wen/old/KNOPPIX/
$ mount -t proc /proc proc

现在你就进入到旧的KNOPPIX3.6之中了,你完全可以把它当作一个普通的Debian系统来对待,使用常用的命令来改造旧的系统:
$ apt-get remove openoffice.org
$ apt-get remove kde-i18n-{es,de,fr,it,nl}
(先删除几个我不常用的大的软件包,上面可以节约300-400M空间。你可以使用命令dpkg-query -l查看安装了哪些软件包,再根据自己的意愿进行删除)
$ apt-get install grass
$ apt-get install qgis
(安装了两个我需要的软件)

简单的改造工作完成,现在再做一点清理工作就可以退出了:
$ apt-get clean
(删除刚下载的软件包,免得被包含到新的发行版中)
$ updatedb
(更新软件数据库)
$ update-menus
(更新菜单)
$ umount proc
(切记!)

下 面就使用ctrl-d退出chroot环境,最后我们还要做两件事情:一是将改造后的/wen/old/KNOPPIX重新压缩为KNOPPIX文件并写 入/wen/new/KNOPPIX,二是/wen/new/做成一个光盘映像文件。这两步都要使用makeisofs命令,系统中没有的话要先自行安 装。这两个命令都很长,我一般把它们写成脚本文件,以方便重复使用。
#mkisofs -R -U -V "www.wen.net" -P "www.wen.net" -hide-rr-moved -cache-inodes -no-bak -pad /wen/old/KNOPPIX nice -5 create_compressed_fs - 65536 > /wen/new/KNOPPIX/KNOPPIX
注意以上要写在一行之内,这个压缩过程需要的时间和前面解压的时间一样漫长,再吃一包方便面吧!
/wen/old目录不要删除,以后还可以在它的基础继续改造。

制作光盘映像文件:(针对3.6版本而言, 3.3版本有所差别)
#mkisofs -pad -l -r -J -v -V "WENPPIX" -no-emul-boot -boot-load-size 4 -boot-info-table -b boot/isolinux/isolinux.bin -c boot/isolinux/boot.cat -hide-rr-moved -o /home/ftp/knoppix.iso /wen/new
倒数第二个参数是指新生成的iso的位置,可自己调整。执行这个命令注意执行时的目录位置!虽然使用了绝对路径,似乎这个命令也不能在其他目录执行。

新的发行版就做好了,很简单,但是要做好就难了,我们还有许多细节的工作要做:
1 修改启动画面等
2 修改启动脚本
3 删除软件包以使自己的发行版尽量小,这可是费时费神的事情。
4 自己改造的发行版通常运行比原版的慢,要进行优化。
5 如何安装在硬盘和U盘。
.......

总之,做一个发行版,做好就难,维护就更难了。

最小的Linux系统制作过程详解

BabyLinux制作过程详解

作者:GuCuiwen email:win2linux@163.com

版权声明:
本文档可以在网络上在非商业范围内自由转载,转载请注明出处
如果转载版面包含商业广告,请向作者支付至少每千字100园的稿费
以书面,书籍形式转载和出版请按至少每千字100园人民币的标准向作者支付稿费

一,什么是BabyLinux
二,为什么要做这样一个linux
三,什么人适合读这篇文档
四,应该具备的知识
五,linux系统引导过程简介
六,编译内核
七,编译busybox
八,制作根文件系统
九,制作ramdisk映象文件
十,内核与busybox的整合
十一,安装测试和内容调整
十二,babylinux中的BUG
十三,接下来要做的事情
十四,参考文献

一,什么是BabyLinux

BabyLinux不是一个完整的发行版,他是利用原有的一套完整的linux系统的内核原代码和编译工具,利用busybox内建的强大功能,在 一张软盘上做的一个很小的linux系统.他具备一个linux系统的基本特征,支持linux系统最常用的一百多个命令,支持多种文件系统,支持网络等 等,你可以把他当做一张linux起动盘和修复盘来用,你也可以把他当做一个静态路由的路由器软件,当然,你也可以把他当做一个linux玩具,向你的朋 友炫耀linux可以做的多么小.我把他叫做BabyLinux因为他很小巧,小的很可爱,像一个刚刚出生的小baby.

二,为什么要作这样一个linux

先说说我一开始的想法,当我一开始接触linux的时候,看到书上说,linux通常安装只需要60M左右的空间,但是我发现装在我硬盘上的 Redhat 6.0确要占据好几百M的空间.为什么我的linux这么大呢? 后来我发现,装在我机器上的那么多东西只有不到30%是我平时常用的,还有30%是我极少用到的,另外的40%基本上是不用的.于是,我和大多数初学者一 样,开始抱怨,为什么linux不能做的精简一点呢?于是,我萌发了自己裁减系统的想法.可惜那个时候我还没有听说过有LFS和Debain.等到我积累 了足够的linux知识后,我开始制作这样一个小系统.
制作这样一个小系统最大的意义在于,你可以通过制作系统了解linux的启动过程,学 会ramdisk的使用,让你在短时间内学到更多的linux知识.当然,你会得到很大的乐趣.这个项目只是做一个具有基本特征的linux系统,如果你 想自己做一个具有完整功能的linux,请阅读Linux From Scratch (LFS)文档.

三,什么人适合读这篇文档

如果你是一个linux爱好者,并且很想了解linux的启动过程和系统的基本结构,而且是一个喜欢动手研究小玩意的人,那么这个文档可以满足你的 需求.如果你仅仅是用linux来做一些普通的日常工作,而不在乎你的linux到底怎么工作,那么这份文档也许不太适合你.另外,如果你是linux爱 好者,但是目前还是一个刚刚入门的newbi,我建议你先把linux命令学好.不过我想我会尽可能的把这份文档写详细一些,如果你有足够的毅力,或许一 个newbi也能成功做一个babylinux.或者,你遇到一件很不巧的事情,比如你的老婆来例假了,你的这个周末就泡汤了,那么阅读这篇文档并做一个 linux小玩具可以打发你的时间.

四,应该具备的知识

在做一个babylinux之前,你应当已经会应用linux最常用的命令.并且至少有一次成功编译并安装系统内核的经历,会通过编译源代码来安装 软件.如果你具备了这些条件,那么做这样一个小系统会很顺利,如果你还没有掌握这些知识,你可能会遇到一些困难.但是只要有毅力,也可以成功.你不需要具 备编程的知识,因为我的目标是:让具有中等以上linux水平的爱好者可以通过阅读文档轻松完成这个项目.关于一张软盘上的linux还有一个很著名的 linux叫LOAP (Linux On A
Floppy) 但是他是由比较专业的人员需要编写很多程序完成的.而且没有关于他制作过程的文档.

五,linux系统引导过程简介

首先,主板的BIOS会读取硬盘的主引导记录(MBR),MBR中存放的是一段很小的程序,他的功能是从硬盘读取操作系统核心文件并运行,因为这个 小程序太小了,因此通常这个小程序不具备直接引导系统内核的能力,他先去引导另一个稍微大一点的小程序,再由这个大一点的小程序去引导系统内核.在 linux系统中这样的小程序有LILO和GRUB.在这个项目中,我决定用LILO来做系统引导程序.在软盘上启动linux系统的过程和在硬盘上启动 的过程相似.

Linux系统内核被引导程序装入内核并运行后,linux内核会检测系统中的各种硬件.并做好各种硬件的初始化工作,使他们在系统正式运行后能正常工作.之后内核做的最后一个工作是运行
/sbin 下的init程序,init是英文单词initialization(初始化)的简称,init程序的工作是读取/etc/inittab文件中描述的指 令,对系统的各种软硬件环境做最初化设定.最后运行mingetty等待用户输入用户名登录系统.所有的工作就这么简单,虽然linux启动的时候有很多 内容,看上去十分高深,但是都不过是对这个过程的扩充.明白了这个道理,你可以写一些脚本程序让他在系统启动的特定时间运行完成任务.事实上系统内核并不 关心/sbin下的init是不是真的init,只要是放在/sbin下名叫init的可执行程序他都可以执行.可以做以下实验:

编写一个非常简单的C程序:

main()
{
printf(“hello,world!\n”);
}

保存后以init.c保存他,并用gcc编译.
#gcc –-static -o init init.c
这里的--static 参数告诉gcc把这个程序静态联接,这样这个程序不倚赖任何库就能运行.把编译好的init程序拷贝到/sbin下,备份好原来的那个.重新启动系统最后系统的输出结果是: hello,world!
然 后停在那里.做这个实验以前先确定你知道如何把系统恢复到原来的状态,有一个简单的方法,在内核启动前给他加上init=参数,比如你原先的init被你 改成了init.bak 只要在启动的时候给内核加上init=/sbin/init.bak就可以用原来的init程序启动系统.
做完以上 实验,就明白了内核和init程序之间的关系.此外,init程序不一定是一个二进制可执行程序,他可以是一个bash脚本,一个指向另一个程序的联接, 他的位置也并不一定要在/sbin下,只要在启动内核时,给内核加上init参数就能被运行,比如,开始时给内核加上init=/bin/bash参数, 内核在最后一步就直接运行bash给出提示符,不用登录系统就可以输入命令了.其功能类似单用户模式启动系统. /sbin/init 程序只是内核默认运行的第一个程序.

六,编译一个linux系统内核

1,编译前的规划和准备

在编译内核前,请先确定你的需求,把你的需求罗列成一张详细的表格.你需要让内核支持什么硬件,支持多少种分区类型和文件系统,支持哪些网卡,支持 哪些网络协议.等等.请尽可能详细的罗列这些内容,但是你也不要太贪心,因为你所有能利用的空间只有1440K,如果你编译出一个大于1440K或很接近 这个数字的内核,你的这个项目就不能完成了,你已经没有空间再放ramdisk映象文件,除非你原意再多出一张软盘,做一个两张软盘的小linux系统. 对于声卡驱动之类,我劝你还是放弃吧,因为一个声卡驱动也许只让你的内核增大了十多K,但是你有了一个声卡驱动就务必要有一个播放器吧,否则声卡驱动就没 有意义,可一个播放器的大小可不是一张软盘可以装得下的.在我先前制作的babylinux内核有900多K,其中,文件系统部分站了大部分,因为我的目 标是把他做成一个系统修复盘.因此我在内核中编译7种文件系统的支持,每减少一个文件系统就可以减小几十甚至200多K的内核大小.越是复杂,越是安全的 文件系统,其支持模块也越大,比如在linux下FAT模块只有32K,VFAT只有17K,但是ext3的模块就有86K,JFS达到216K, reiserfs模块是224K,可以想像,编译一个支持7个文件系统的900多K的内核,文件系统部分就占了600K以上的空间,所以如果某一个文件系 统是你根本不用的,那么还是不要编译进内核把,这样至少可以省下100多K的空间.对于其他的驱动,比如网卡,通常大小只有8,9K,最大的也不过10多 K,因此可以把常用的网卡芯片的驱动都编译进去.另外如果你想让你的babylinux支持U盘,那么scsi的驱动模块也是不可小看的,他通常要接近 150K,因为U盘是被当做scsi设备来驱动的.另外你还需要让你的内核支持即插即用,这些都是不小的空间开销,我的建议是你放弃一两个你不用的文件系 统.总之,你最后编译出来的内核大小最好不要超过900K,否则你在busybox里只能编译进去很少的命令.

在我编译的busybox中,我编译进去120多个命令,基本上把busybox支持的命令都包括进去了.加上小系统所必需的文件系统目录, /dev下的设备文件,以及/etc下几个必需的配置文件,做成ramdisk压缩后的大小是440多K, 加上900K左右的内核刚好可以放入一张1440K软盘,请注意,你应该留下至少50K的空间,因为我们要在软盘上创建一个ext2文件系统,而文件系统 本生需要占据大概25K的磁盘空间.另外lilo的引导文件boot.b的大小是5.7K,还有装上lilo后自动产生的map文件也要10多K的空间, map文件的具体大小由内核安装的实际大小决定,通常不会超过30K.
综上所述,请遵循下面的公式:

内核大小+文件系统压缩印象文件+50K <= 1440K

另外一点需要说明的是:以上所罗列的文件系统模块大小是察看我现在使用的Redhat 9 的
/lib/modules下的模块文件得到的,实际编译进内核大小会小一点,因为我们用make bzImage
在内核源代码目录树下生成的内核是经过压缩过的.

如果你对以上说的内容不太明白也没有关系,我会在下面的内容中做详细的说明.

2,必需编译进内核的内容

首先,我们制作的这个小系统是基于一张软盘的,因此,你的内核必需支持软盘.另外对IDE硬盘和cdrom的支持也是不可少的,否则做出来的 babylinux就没有实用价值,因为他不能访问硬盘和光盘上的内容这样的linux虽然可以做的更小,但是制造一个完全没有用的东西是浪费时间.其他 的包括framebuffer等,如果你需要支持在字符界面下以高分辨率显示,以看到更多的屏幕内容,那么就必需把framebuffer支持编译进内 核,此外在高分辨率下使用的8x8字体也必需编译进去.否则即使你给内核传递了vga= 参数,内核会因为没有可用的小字体而自动转跳到低分辨率模式下,这是以前困扰我好几天想不明白的事情,后来通过反复试验才明白原来是缺少字体的文体.这里 我先大致提一下需要注意的事情.在下一小节具体编译时,我会继续就某些细节问题说明.

3,关于内核的版本

我是在Redhat 9 linux系统下打造的babylinux小系统.使用的是Redhat 9 自带的2.4.20版的内核.
为什么我不用最新的2.6的内核?
一 开始我也企图用最新的内核,但是通过试验我发现,在用最新的2.6.9内核的情况下,我编译一个all-no的(即所有内容都选N,不支持任何硬件,只有 一个最基本的内核)最小化内核就要460K左右,如果我在这个基础上再加入几种文件系统和必要的驱动,那么内核的大小就不能装下一张1440K
的 软盘,而我用2.4.20的内核编译一个最小化的内核只需要217K,的大小.如果优化了gcc参数他还能再小些.这样我就立即省下了200多K的空间, 在平时,200多K的内容微不足道,但是在babylinux里,这个数目是整个空间的 1/7,相当于一个reiserfs文件系统模块的大小.当然,我也尝试了2.2以及更老的内核,但是他们缺少我需要的东西,因此最后权衡下来用2.4的 内核是比较合理的.如果你用的是2.6内核的FC系统,那么最好还是去下载一个2.4版的内核,www.kernel.org 有各个时期的内核可以下载.

4, 内核的配置

如果你对linux内核的配置和编译已经很熟悉了,请跳过这一段,直接看busybox的编译.

以root身份登录系统
进入/usr/src/linux目录
[root@gucuiwen root]# cd /usr/src/linux
如 果你下载了一个2.4版本的内核,为了避免麻烦,请将他拷贝到/usr/src下,然后接压缩,再做一个指向他的名为linux的链接.虽然这并不是必需 的,但是根据我以往的经验,如果我把linux源代码放在其他目录下解开并编译,偶然会有一些莫名其妙的小问题发生.

#cp linux-2.4.20.bz2 /usr/src/
#cd /usr/src
#tar xfvj linux-2.4.20.bz2
如果是tar.gz格式,可以这样解开
#tar xfvz linux-2.4.20.tar.gz
为了方便,做一个到目录linux-2.4.20的连接:
#ln -s linux-2.4.20 linux
进入linux源代码目录:
#cd linux
清理源代码树:
#make mrproper
运行配置程序:
#make xconfig

code maturity level options
先选择N,当我们配置好常规的东西,要加入framebuffer支持时再将这 一项选择Y,因为在2.4.20中,framebuffer支持尚属于实验性代码.如果不在code maturity level options选择为Y,将不能配置framebuffer.

Loadable module support
选择N,为了简化系统的制作,我在这个项目中不选择可加载内核模块的支持.

processor type and features

processor family 中选择你需要的CPU类型,如果你想让老至386,新到P4的CPU都能运行babaylinux那么请选择386CPU,否则请按自己的实际情况选择.

其他选项都选择N.这些在babylinux中都是不需要的.

General setup
networking support 选择Y
PCI support 选择Y 除非你不用PCI设备,不过一般人都是需要的,因为现在网卡大部分是PCI的.

System V ipc 选择Y
systrl support选择Y
kernel support for ELF 选择Y
其余内容都可以选择N,如果有特殊需求,比如的网卡是ISA的,那么请将相应的内容选上.但是不能贪心,时刻牢记,我们能利用的空间只有 1440K ,内核的大小绝不能超过 900K,任何不必要的东西都应该从内核中去除.

memory technology devices (MTD)
Parallel port support
Plug and Play configuration
以上三个大项中的所有内容选择N

block devices

Normal floppy disk support
Loopback device support
RAM disk support
initial RAM disk (initrd) support
Per partition statics in /proc/partitions

以上几项选择Y,其余全部选择N.

这里的选项比较重要,我想重点说明一下.对于软盘的支持,那是不必说的,那是必备的.
loopback device 即回环设备,我们平时用命令

#mount -o loop somecd.ISO /mnt/cdrom

挂装光盘映象文件,或者其他文件系统映象文件时就用到了内核中的loopback 模块,如果没有编译进这个模块,你将不能用上面的命令挂装光盘映象和文件系统映象.
个人认为这个功能是非常重要的,所以编译了进去.

RAM disk support 即内存磁盘(比较贴切的说法是虚拟磁盘,即拨出一部分内存当做磁盘用).这是制作babylinux项目中的核心内容,由于一张软盘的空间有限, babylinux的根文件系统是用gzip压缩法高度压缩的,在运行时,将解压缩后的文件拷贝到一个RAM disk运行,所以在运行时,你在根文件系统上的所有操作实际上是在内存上进行的.但是在形式上和在真正的磁盘上运行一样.只不过放在RAM disk上的所有内容会在系统关机后全部消失.
不仅在运行babylinux时用到ramdisk,我们在制作压缩的根文件系统时也要用到ramdisk,学习ramdisk的使用是做一个babylinux的重要目的之一. 在linux中,还支持另外一种虚拟磁盘,叫做shm,
(shared memory),这种虚拟磁盘机制比ramdisk更加先进,ramdisk的大小是固定的,由编译内核时候的default ram disk size 决定.默认为4096K(4M),也可以在内核装载前加上ramdisk_size=参数来决定他的大小,但是系统一旦启动,ramdisk的大小是不能 改变的,而shm的大小却动态的改变.默认情况下为物理内存的一半,当系统需要更多内存的时,他就自动缩小.系统内存富余时,他自动增大,这样可以充分灵 活的利用内存空间,shm通常用来作为系统的磁盘高速缓存,存放系统运行中的临时文件等.redaht 的linux在默认情况下都有shm的支持,可以用mount和df察看他的挂装点和大小,如下命令:

[root@gucuiwen linux]# mount
/dev/hda1 on / type ext3 (rw)
none on /proc type proc (rw)
usbdevfs on /proc/bus/usb type usbdevfs (rw)
none on /dev/pts type devpts (rw,gid=5,mode=620)
/dev/hda6 on /home type ext3 (rw)
/dev/hda5 on /oracle type ext3 (rw)
none on /dev/shm type tmpfs (rw)
/dev/hda7 on /var type ext3 (rw)

[root@gucuiwen linux]# df -h
文件系统 容量 已用 可用 已用% 挂载点
/dev/hda1 2.9G 2.7G 26M 100% /
/dev/hda6 3.8G 1.8G 1.8G 50% /home
/dev/hda5 5.7G 677M 4.8G 13% /oracle
none 125M 0 125M 0% /dev/shm
/dev/hda7 711M 91M 584M 14% /var

虽然shm有这么多的优点,我还是选择了ramdisk,因为ramdisk可以很方便地在系统启动的时候加载,而shm却没那么容易,下面就来讲一下关于内核启动时加载ramdisk映象的相关内容.

initial RAM disk (initrd) support
即初始化ramdisk支持,这个选项让内核有能力在内核加载阶段 就能装入RAMDISK,并运行其中的内容,否则只能在系统运行阶段用ramdisk ,我们平时在编译了一个新内核后,如果你的根文件系统用的是ext3,而你没有把ext3编译进内核,而只作为一个模块编译了,那么就需要用 mkinitrd命令做一个initrd (initializtion ramdisk),这个ramdisk里放了ext3的模块,这样内核在加载根文件系统前就能正确识别ext3文件系统.否则,内核加载的最后一步就会出 现kernel panic cant not find init .... 的错误.

在babylinux项目中,这个选项是必需的,这里的作用是把解压的根文件系统映象装入ramdisk.

Per partition statics in /proc/partitions
这个选项不是必需的,但是我发现如果我不把这个功 能编译进内核,那么当我在挂装文件系统的时候会有些小问题,比如我不能以简写的挂装命令来挂装文件系统.我不确定到底是不是这个选项的关系,但是把这个选 项编译进内核只增大一点点内核空间,所以为了避免麻烦,我把他编译了进去.

Multi-device support (RAID and LVM)
Cryptography support (CryptoAPI)
这两个大项全部选择N,因为在个人用PC上,及少牵涉到这两项,如果你真的有RAID设备或者LVM,那么就自己摸索着配置一下吧.

Networking options

这一大项中,只需要把下列项目编译进内核:
Packet socket :mmapped IO
TCP/IP networking

对于IP:advanced router这项,如果你想重点把babylinux用做静态路由软件,那么把这项编译进去,而对于network packet filtering (replaces ipchains)这一项,没有必要编译进去了,因为busybox没有提供iptables工具来设置包过滤防火墙.同样,unix domain sockets这项也不必选择,只有运行X的情况下才需要选这项.

Telephony Support 选择N

ATA/IDE/MFM/RLL support
选择Y,然后下面的'IDE,ATA and ATAPI Block Devices'按钮就被激活

下面几项请选择Y,其余都可以是N.
Enhanced IDE/MFM/RLL disk/cdrom/tape/floppy support
Include IDE/ATA-2 DISK support
Auto-Geometry Resizing support
Include IDE/ATA CDROM support

如果你的内核要运行在一台很老的pentium或486上,请把CMD640 chipset bugfix/support编译进去,因为那时候主板的CMD640 IDE控制芯片大多有莫名其妙的BUG,把这项编译进去会修复这个bug.

下面几个大项:
SCSI support
Fusion MPT device support
IEEE 1394(FireWire) support
I2O device support
全部选择N,这里可能有你想要的好东西,比如1394接口驱动,但是在babylinux上意义不大,而且我们的空间只有1440K.

下面一个大项:
Network device support
选择Y,这样就可以支持网卡了,其余都选择N.然后点 Ethernet(10 or 100 Mbit)按钮选择你需要的网卡驱动,你可以把最常见的几种Reltek8139,NE2000,3COM等网卡编译进内核.虽然网卡的驱动通常都很小, 但是不要太贪心,选2~3个就足够了,否则你的内核就会一下子多出几十K.在我先前编译的babylinux内核中,我把via-rhine网卡编译了进 去,是因为我打造babylinux的机器上只有一块那个芯片的网卡.

如果你发现你需要的网卡是灰色的,不能点,那么先确定他上一级的选项已经点了,比如你想选NE2000的网卡,就必需先选择ELSA,VLB, PCI and on board controllers.如果还不能点,那么请确定是否已经把PCI的支持选项选上了,(在Geneal setup)里.没有PCI的支持,PCI的网卡将不能选.

可能你是个有钱人,在自己的PC上用千兆网卡,那么请在千兆网卡那一栏选择.

接下来几个大项:
Amateur Radio support
IrDA (infrared) support
ISDN subsystem
Old CD-ROM drivers (not SCSI,not IDE)
Input core support
全部选择N.

接下来的Charcter devices是很重要的一项,他和Bloack devices一样重要,我将重点讲述.
除了Virtual terminal和Support for console on terminal两项,其他全选N.

Virtual terminal 即虚拟终端,这是一般linux必备选项.否则你的linux启动后,在屏幕看不到任何东西.另外还负责键盘输入信息等等.只有在某些嵌入式linux应用场合才会不要这个选项,因为这些linux通常都不用操作.

Support for console on terminal
在虚拟终端上的控制台.他支持在终端上各种信息的输出,这也是必备的.

接下来的几个大项:
Multimedia devices
Crypto Hardware support
全部选择N.

再接下来的那部分File sytems可是重头戏喔.
这部分不用我太罗嗦了吧,自己需要支持什么就选什么.
但是其中有三个是你必需选的:
/proc file system support 缺了他,很多命令和软件就不能运行.
Second extended fs support BabyLinux的基本文件系统.
ISO 9660 CDROM filesytem support 除非你不想用光盘.
另外,诸如磁盘限额(Quota support),Reiserfs的DEBUG模式(Enable reiserfs debug mode)
等就不用编译进去了.这些东西意义不大,确要无端的增大内核大小.请牢记一点:编译出来的内核大小不要超过900K.

Tip:是不是看的很累啊,我写得更累,别急,内核配置部分马上要好了.

最后一个Console drivers
这是支持linux在字符模式下高分辨率显示的内核模块.前面三个全部选择Y,
Frame-buffer support按钮是灰色的不能选,别急,回到第一个大选项:
Code maturity level options 选择Y,就可以激活这个按钮了.

下面几个选项需要选择Y:
Support for framebuffer devices
VESA VGA graphics console
你也可以选择其他的显卡驱动,比如nVidia的,但是VESA和VGA是通用性最好的,只要不是几十年前的黑白显卡(我只听说过,没见过),都兼容VESA和VGA,因此,为了制作好的BabyLinux的通用性,请选择这个驱动.

Support only 8 pixels wide fonts
这个一定要选,否当你给内核传递vga=788参数,让linux在字符界面下高分辨率显示的时候,系统会因为找不到合适的小字体而返回到低分辨率模式.

好了!所有内核的配置工作到这里就全部完成了,剩下的几个大项全部选N就行了.
保存后退出,配置程序会自动生成一个隐藏的配置文件.config

下面是我配置好的.config文件内容.如果你懒的自己去配置,那么直接把这个.config拷贝到你的源代码目录下就能直接用了.(已经去掉了#开头的注释行)
CONFIG_X86=y
CONFIG_UID16=y
CONFIG_EXPERIMENTAL=y
CONFIG_M586=y
CONFIG_X86_WP_WORKS_OK=y
CONFIG_X86_INVLPG=y
CONFIG_X86_CMPXCHG=y
CONFIG_X86_XADD=y
CONFIG_X86_BSWAP=y
CONFIG_X86_POPAD_OK=y
CONFIG_RWSEM_XCHGADD_ALGORITHM=y
CONFIG_X86_L1_CACHE_SHIFT=5
CONFIG_X86_USE_STRING_486=y
CONFIG_X86_ALIGNMENT_16=y
CONFIG_X86_PPRO_FENCE=y
CONFIG_NOHIGHMEM=y
CONFIG_NET=y
CONFIG_PCI=y
CONFIG_PCI_GODIRECT=y
CONFIG_PCI_DIRECT=y
CONFIG_SYSVIPC=y
CONFIG_SYSCTL=y
CONFIG_KCORE_ELF=y
CONFIG_BINFMT_ELF=y
CONFIG_BLK_DEV_FD=y
CONFIG_BLK_DEV_LOOP=y
CONFIG_BLK_DEV_RAM=y
CONFIG_BLK_DEV_RAM_SIZE=4096
CONFIG_BLK_DEV_INITRD=y
CONFIG_PACKET=y
CONFIG_INET=y
CONFIG_IP_MULTICAST=y
CONFIG_IDE=y
CONFIG_BLK_DEV_IDE=y
CONFIG_BLK_DEV_IDEDISK=y
CONFIG_IDEDISK_MULTI_MODE=y
CONFIG_BLK_DEV_IDECD=y
CONFIG_BLK_DEV_IDE_MODES=y
CONFIG_NETDEVICES=y
CONFIG_NET_ETHERNET=y
CONFIG_INPUT_MOUSEDEV_SCREEN_X=1024
CONFIG_INPUT_MOUSEDEV_SCREEN_Y=768
CONFIG_VT=y
CONFIG_VT_CONSOLE=y
CONFIG_REISERFS_FS=y
CONFIG_EXT3_FS=y
CONFIG_JBD=y
CONFIG_FAT_FS=y
CONFIG_VFAT_FS=y
CONFIG_RAMFS=y
CONFIG_ISO9660_FS=y
CONFIG_JFS_FS=y
CONFIG_NTFS_FS=y
CONFIG_PROC_FS=y
CONFIG_EXT2_FS=y
CONFIG_MSDOS_PARTITION=y
CONFIG_NLS=y
CONFIG_NLS_DEFAULT="iso8859-1"
CONFIG_VGA_CONSOLE=y
CONFIG_VIDEO_SELECT=y
CONFIG_VIDEO_IGNORE_BAD_MODE=y
CONFIG_FB=y
CONFIG_DUMMY_CONSOLE=y
CONFIG_FB_VESA=y
CONFIG_VIDEO_SELECT=y
CONFIG_FBCON_CFB8=y
CONFIG_FBCON_CFB16=y
CONFIG_FBCON_CFB24=y
CONFIG_FBCON_CFB32=y
CONFIG_FBCON_FONTWIDTH8_ONLY=y
CONFIG_FONT_8x8=y
CONFIG_FONT_8x16=y

5,编译内核
#make dep
#make bzImage

下面是最后编译结果:
Boot sector 512 bytes.
Setup is 4733 bytes.
System is 845 kB
make[1]: Leaving directory `/usr/src/linux-2.4.20-8/arch/i386/boot'

我用上面的配置得到了一个845k的内核.
编译好的内核放在/usr/src/linux-2.4.20-8/arch/i386/boot下.将他拷贝在一个安全的地方备用.

建立一个专放babylinux材料的目录
#mkdir /babylinux
建立一个做babylinux根文件系统的目录
#mkdir /babylinux/rootfs
备份内核
#cp /usr/src/linux-2.4.20-8/arch/i386/boot/bzImage /babylinux/

七,编译busybox

1,busybox简介

busybox是一个集成了一百多个最常用linux命令和工具的软件,他甚至还集成了一个http服务器和一个telnet服务器,而所有这一切 功能却只有区区1M左右的大小.我们平时用的那些linux命令就好比是分力式的电子元件,而busybox就好比是一个集成电路,把常用的工具和命令集 成压缩在一个可执行文件里,功能基本不变,而大小却小很多倍,在嵌入式linux应用中,busybox有非常广的应用,另外,大多数linux发行版的 安装程序中都有busybox的身影,安装linux的时候案ctrl+alt+F2就能得到一个控制台,而这个控制台中的所有命令都是指向 busybox的链接.
Busybox的小身材大作用的特性,给制作一张软盘的linux带来了及大方便.

2,busybox的用法

可以这样用busybox
#busybox ls
他的功能就相当运行ls命令
最常用的用法是建立指向busybox的链接,不同的链接名完成不同的功能.
#ln -s busybox ls
#ln -s busybox rm
#ln -s busybox mkdir

然后分别运行这三个链接:
#./ls
#./rm
#./mkdir

就可以分别完成了ls rm 和mkdir命令的功能.虽然他们都指向同一个可执行程序busybox
但是只要链接名不同,完成的功能就不同,busybox就是这么的神奇.
很多linux网站都提供busybox的源代码下载.目前版本是busybox1.0正式版.

3,配置busybox

busybox的配置程序和linux内核菜单配置方式简直一模一样.熟悉用make menuconfig方式配置linux内核的朋友很容易上手.

#cp busybox-1.00.tar.gz /babylinux
#cd /babylinux
#tar xvfz busybox-1.00.tar.gz
#cd busybox-1.00
#make menuconfig

下面是需要编译进busybox的功能选项,其他的可以根据需要自选,但是同样不要太贪心.
General Configuration应该选的选项
Show verbose applet usage messages
Runtime SUID/SGID configuration via /etc/busybox.conf

Build Options
Build BusyBox as a static binary (no shared libs)
这个选项是一定要选择的,这样才能把busybox编译成静态链接的可执行文件,运行时才独立于其他函数库.否则必需要其他库文件才能运行,在单一个linux内核不能使他正常工作.

Installation Options
Don't use /usr
这个选项也一定要选,否则make install 后busybox将安装在原系统的/usr下,这将覆盖掉系统原有的命令.选择这个选项后,make install后会在busybox目录下生成一个叫_install的目录,里面有busybox和指向他的链接.

其他选项都是一些linux基本命令选项,自己需要哪些命令就编译进去,一般用默认的就可以了.

配置好后退出并保存.

4,编译并安装busybox

#make
#make install

编译好后在busybox目录下生成子目录_install,里面的内容:
drwxr-xr-x 2 root root 4096 11月 24 15:28 bin
lrwxrwxrwx 1 root root 11 11月 24 15:28 linuxrc -> bin/busybox
drwxr-xr-x 2 root root 4096 11月 24 15:28 sbin
其中可执行文件busybox在bin目录下,其他的都是指向他的符号链接.
我编译出来的busybox可执行文件是935K,加上符号链接,整个_install目录是952K.加上845K的内核不是已经超过1440K了吗?别担心,我们将对整个根文件系统做大幅度的压缩.

八,制作根文件系统

1,基本目录结构

#cd /babylinux/rootfs
#mkdir etc usr var tmp proc home root dev
其中etc,proc和dev是一定要建的,bin和sbin不用建,因为busybox中已经有了.
其他的可以象征性的建几个就可以了.

拷贝busybox
#cp -R /babylinux/busybox-1.00/_install/* /babylinux/rootfs/

2,建立设备文件名

#cd /babylinux/rootfs/dev
你可以用mknod手工建立,也可以直接从原系统的/dev目录下拷贝过来.

手工建立的方法:
#ls -l /dev/console
crw------- 1 root root 5, 1 11月 30 09:02 /dev/console
这样就查看到了console设备的主设备号是5,辅设备号是1,是一个标记为C的字符设备.
于是,我们可以用mknod建立一个同样的设备文件:

#mknod console c 5 1

但是手工方法建立太麻烦了,通常直接从/dev下把需要的设备文件拷贝过来.
这些设备文件是特殊文件,在拷贝时一定要加上-R参数才能拷贝.

#cp -R /dev/console ./
#cp -R /dev/null ./
#cp -R /dev/zero ./
...

以下是我认为需要的设备名:
cdrom fd0 hda14 hda4 hdb11 hdb19 hdc hdc16 hdc6 hdd13 hdd3 loop2 ram2
console fd0H1440 hda15 hda5 hdb12 hdb2 hdc1 hdc17 hdc7 hdd14 hdd4 loop3 tty0
fb hda hda16 hda6 hdb13 hdb3 hdc10 hdc18 hdc8 hdd15 hdd5 loop4 tty1
fb0 hda1 hda17 hda7 hdb14 hdb4 hdc11 hdc19 hdd hdd16 hdd6 loop5 tty2
fb1 hda10 hda18 hda8 hdb15 hdb5 hdc12 hdc2 hdd1 hdd17 hdd7 null tty3
fb2 hda11 hda19 hdb hdb16 hdb6 hdc13 hdc3 hdd10 hdd18 hdd8 ram tty4
fb3 hda12 hda2 hdb1 hdb17 hdb7 hdc14 hdc4 hdd11 hdd19 initctl ram0 tty5
fb4 hda13 hda3 hdb10 hdb18 hdb8 hdc15 hdc5 hdd12 hdd2 loop1 ram1 zero

其中,fd0,hda,ram,ram1,tty1,null,zero,loop1,fb0,fb等是必备的.
其它的hda,hda1,hdb等可以根据实际需要决定.但是上表中的选择是比较合理的,即能满足大部分的需要,有没有不用的设备浪费空间.注意,千万不要把/dev下的设备全拷贝过来,那将产生大约420K的/dev目录,这对babylinux来说太大了.

3,建立etc目录下的配置文件

busybox.conf group inittab motd passwd resolv.conf shadow-
fstab init.d issue mtab profile shadow

其中init.d是一个目录,从busybox-1.00源代码目录下拷贝过来.

#cp -R /babylinux/busybox-1.00/examples/bootflopyp/etc/init.d /babylinux/rootfs/etc/

busybox.conf是一个空文件.
其他文件的内容如下:

fstab
/dev/fd0 / ext2 defaults 0 0
none /proc proc defaults 0 0
/dev/cdrom /mnt/cdrom udf,iso9660 noauto,owner,kudzu,ro 0 0
/dev/fd0 /mnt/floppy auto noauto,owner,kudzu 0 0
group
root:x:0:root
inittab
::sysinit:/etc/init.d/rcS

::askfirst:/bin/sh
tty2::respawn:/bin/getty 38400 tty2
tty3::respawn:/bin/getty 38400 tty3
tty4::respawn:/bin/getty 38400 tty4

# Stuff to do when restarting the init process
::restart:/bin/init

# Stuff to do before rebooting
::ctrlaltdel:/bin/reboot
::shutdown:/bin/umount -a -r
::shutdown:/bin/swapoff -a

issue
Baby Linux release 0.1

motd

mtab

passwd
root::0:0:root:/root:/bin/ash
profile
# /etc/profile: system-wide .profile file for the Bourne shells

echo
echo
export PS1="[\u@\h \w]\$"
echo "Done"
alias ll='ls -l'
alias du='du -h'
alias df='df -h'
alias rm='rm -i'
echo

resolv.conf
nameserver 202.96.209.5
nameserver 202.96.209.6
shadow
root:$1$$adltAB9Sr/MSKqylIvSJT/:12705:0:99999:7:::
shadow-
root:$1$DWU.tenP$B7ANiXoGoiZMwJR6Ih8810:12705:0:99999:7:::
其 中有很多是从原系统的/etc下拷贝过来修改的,如果你是一个具有中等以上水平的linux爱好者,那么应该一看就明白了,当然,你也可以根据自己的需要 修改这些文件.其中最重要的是fstab和inittab,busybox内建的init程序用到的inittab文件的语法和一般的不一样,不能直接把 原系统/etc下inittab文件拷贝过来.可以把busybox-1.00目录下的示例文件拷贝过来修改用.具体请看busybox的文档. busybox的init也可以不用inittab.但是在我制作babylinux过程中有一个非常奇怪的bug.所有/sbin下的busybox链 接在做成压缩的根文件系统,解压后都不能正常运行,显示找不到该命令.只有当我在/bin下做这些链接时才能运行.具体原因还不太清除,所以你需要做下面 的工作:

#cd /babylinux/rootfs/sbin
#ls
chroot getty ifconfig losetup pivot_root reboot swapoff sysctl
fdisk halt init mkswap poweroff route swapon telnetd
查看到sbin下有上述链接

转到bin下
#cd /babylinux/rootfs/bin
重新做这些链接:
#ln -s busybox chroot
#ln -s busybox getty
#ln -s busybox ifconfig
...


然后把sbin下的链接删除,以节省空间
#rm -rf /babylinux/rootfs/sbin/*

再把原先inittab中所有的sbin改成bin

init.d下的文件:
rcS
请确保这个文件是可执行的,否则请改成可执行的:
#chmod u+x rcS

rcS的内容:
#! /bin/sh
mount -o remount,rw /

/bin/mount -a
>/etc/mtab
echo
echo
echo
echo
echo -en "\t\tWelcom to \\033[0;32mBabyLinux\\033][0;39m\n"
echo -en "\\033][0;36m\n"
echo
echo -en "++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++\t\t\n"
echo -en "+ This is a tiny linux system based on a floppy.It contains \t\t\n"
echo -en "+ more than 100 basic Linux commands and tools.The kernel of \t\t\n"
echo -en "+ this tiny system support all kinds of normal filesystems. \t\t\n"
echo -en "+ linux ext2,ext3,jfs,reiserfs and windows fat,vfat,ntfs][readonly]\t\t\n"
echo -en "+ is supported! So it is a powerful small system you can use it \t\t\n"
echo -en "+ as a linux and windows rescue disk.Beside this,the kernel also\t\t\n"
echo -en "+ contains the drivers of Reltek8139,NE2000,via-rhine ethernet\t\t\n"
echo -en "+ adpater. you can configure the IPaddress and netmask with tools\t\t\n"
echo -en "+ 'ifconfig' and config the default gateway with command 'route'. \t\t\n"
echo -en "+ Is there anything else? Haha,this is a telnet server build-in\t\t\n"
echo -en "+ you can type 'telnetd' to startd it and thus your friends can\t\t\n"
echo -en "+ logon to your system to help you solve the problem.\t\t\n"
echo -en "+ \\033[0;32mAll these great features are powered by BusyBox 1.0\\033][0;36m\t\t\n"
echo -en "+ This is a free system tool developed by GuCuiwen.\t\t\n"
echo -en "+ RUN YOUR OWN RISK of using it ! if you have any problem please\t\t\n"
echo -en "+ mailto : win2linux@163.com Enjoy!!\t\t\n"
echo -en "++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++\t\t\n"
echo -en "\\033][0;39m\n"
hostname BabyLinux
可以自己作相应的修改.
以上是babylinux根文件系统的所有内容,他的总大小应该在1M左右.
][root@gucuiwen baby]# du -hs
1.1M .

九,制作ramdisk映象文件


babylinux根文件系统所有东西都放在/babylinux/rootfs下,我们将利用ramdisk把这些内容做成ramdisk映象文件并压缩他.

以下主要是ramdisk的用法,看完以下内容,你应当学会ramdisk的使用.

[root@gucuiwen babylinux]# dd if=/dev/zero of=/dev/ram1
dd: 正在写入 ‘/dev/ram1’: 设备上没有空间
读入了 8193+0 个块
输出了 8192+0 个块

zero是一个特殊的设备,表示全部为0的字符块.上面这条命令的意思是把系统的第一个ramdisk用全部为0的数据填充,因为ramdisk默 认大小为4M,因此当读满8192个块(每块512字节)后,显示'设备上没空间'.这很正常,/dev/ram1已经被填充满了.
如果指定块的大小:

[root@gucuiwen babylinux]# dd if=/dev/zero of=/dev/ram1 bs=1M count=4
读入了 4+0 个块
输出了 4+0 个块

不会有错误提示,这里演示了dd的一般用法,接下来还要频繁用到dd命令.

在/dev下有很多ramdisk设备,ram1,ram2,ram3....
一般用第一个就可以了.

填充后,ram1就有可空间,可以在这个空间上创见一个文件系统:
[root@gucuiwen babylinux]# mkfs.ext2 -m0 /dev/ram1
mke2fs 1.32 (09-Nov-2002)
Filesystem label=
OS type: Linux
Block size=1024 (log=0)
Fragment size=1024 (log=0)
1024 inodes, 4096 blocks
0 blocks (0.00%) reserved for the super user
First data block=1
1 block group
8192 blocks per group, 8192 fragments per group
1024 inodes per group

Writing inode tables: done
Writing superblocks and filesystem accounting information: done

This filesystem will be automatically checked every 37 mounts or
180 days, whichever comes first. Use tune2fs -c or -i to override.

将ram1挂装到文件系统中:
先建立一个挂装点:
#mkdir /mnt/ram
挂上ram1:
#mount /dev/ram1 /mnt/ram
将先前做好的babylinux根文件系统拷贝到ram1上.
#cp -R /babylinux/rootfs/* /mnt/ram

做完以上几步,你应就白了ramdisk设备的含义,他是和hda1,hdb1,一样的块设备,用mount挂到文件系统下后就可以访问,往里放东西,但是所有的东西在内存上.关机将丢失所有东西.

拷贝好babylinux根文件系统后卸载ram1:
#umount /dev/ram1
这时,虽然不能通过/mnt/ram这个挂装点访问ram1中的内容了,但是他却切切实实得在内存中存在.


再用dd把这个ram1以映象方式取出来:

[root@gucuiwen babylinux]# dd if=/dev/ram1 of=/babylinux/ramdisk.img
读入了 8192+0 个块
输出了 8192+0 个块

验证一下取出来的内容:
[root@gucuiwen babylinux]# file ramdisk.img
ramdisk.img: Linux rev 1.0 ext2 filesystem data

他是一个ext2 文件系统,类似一个ISO光盘映象文件.
因次,我们可以用loop设备来把他重新挂装到文件系统里:

[root@gucuiwen babylinux]# mount -o loop ramdisk.img /mnt/ram/

为了方便,我仍旧把他挂在/mnt/ram下,因此,在先前一定要把/dev/ram1 umount掉

查看/mnt/ram下的内容,他应该和/babylinux/rootfs下的一模一样,否则就是出错了:
[root@gucuiwen babylinux]# ls /mnt/ram
bin dev etc home lost+found mnt proc root sbin tmp usr var

这样,我们就得到了一个ramdisk根文件系统映象:ramdisk.img
把他umount掉:
#umount /mnt/ram

如果是第一次接触ramdisk,你可能对上述的内容很迷惑,如果这样,请反复阅读和理解上面的内容,自己多动手做几次试验,就可以理解.

压缩ramdisk.img印象文件:
[root@gucuiwen babylinux]# gzip -v9 ramdisk.img
ramdisk.img: 87.9% -- replaced with ramdisk.img.gz

查看压缩后的大小:
[root@gucuiwen babylinux]# ls -lh ramdisk.img.gz
-rw-r--r-- 1 root root 495K 11月 30 11:32 ramdisk.img.gz

我得到的压缩ramdisk映象文件安是495K. 加上内核的845K,是1340K
符合公式:

内核大小+文件系统压缩印象文件+50K <= 1440K

如果你做出来的kernel和ramdisk.img.gz太大了,请重新制作kernel或ramdisk.img.gz,在其中做一些取舍,如 果你的kernel和ramdisk.img.gz太小了,那么可以再往里面添加一些内容,使你的babylinux功能更强.


十,内核与busybox的整合

准备一张完好的空白软盘

创建一个比内核大小略大的文件系统:
比如内核大小是845K,那么我我创见一个920K的文件系统:
#mkfs.ext2 -m0 /dev/fd0 920

如果空间允许,还可以再大一些,但是必需保证
1440K-文件系统大小>=ramdisk.img.gz的大小.

挂上软盘
#mount /dev/fd0
将内核拷贝到软盘:
#cp /babylinux/bzImage /mnt/floppy/
将lilo引导文件安boot.b 拷贝到软盘
#cp /boot/boot.b /mnt/floppy

新建一个lilo.conf 配置文件:

prompt
timeout=60
default=linux
boot=/dev/fd0
map=/mnt/floppy/map
install=/mnt/floppy/boot.b
linear

image=/mnt/floppy/bzImage
label=linux
read-only
vga=788
root=/dev/fd0
append="load_ramdisk=1 ramdisk_start=940"

vga=788表示让内核支持字符界面的高分辨率显示,你可以改成vga=ask,这样可以在启动的时候选择分辨率.

红色一行是关键,load_ramdisk=1告诉内核在启动的时候转载压缩的ramdisk印象文件,
ramdisk_start=940 告诉内核从软盘的第940K的地方去寻找并装载压缩的ramdisk印象文件.

关于ramdisk的用法和更多参数请查看linux0内核文档/usr/src/linux/Documents/ramdisk.txt

接下来再用dd命令把ramdisk.img.gz装到软盘上.

#dd if=/babylinux/ramdisk.img.gz of=/dev/fd0 bs=1k seek=940

这里的seek=940 表示把ramdisk.img.gz装到软盘的第940K开始的地方.

详细内容请看dd的联机文档 man dd

为什么要从940k开始呢?
因为刚才作了一个920K的文件系统.我把他装在文件系统20K以后的地方.
当然,如果你的空间十分紧张,连这20K都不舍得浪费,那么可以这样:

#dd if=/babylinux/ramdisk.img.gz of=/dev/fd0 bs=1k seek=921

当然,别忘记修改lilo.conf文件. ramdisk_start=921

接下来装lilo引导程序就大功告成了.

#lilo -C lilo.conf

如果你的磁盘上还有一点点空余空间,那么可以把lilo.conf也拷贝上去,以备将来使用.
#cp lilo.conf /mnt/floppy

#umount /dev/fd0


整个工程已经完成了,你可以重新启动机器,设置电脑从软盘启动.看看有没有成功.

十一,安装测试和内容调整

如果在整合内核和ramdisk映象过程中,出现磁盘空间不够的情况,请重新编译内核和busybox
可以根据实际需要,调整内核和busybox,比如你要内核支持很多东西,但是只需要一个支持50个命令的busybox,那么可以自己做相应调整.

十二,babylinux中的BUG

有些命令的输出结果会有偏差,比如用 busybox的df 看磁盘使用情况,和实际的不一样.

十三,接下来要做的事情

做一个基于64M U盘的linux小系统.
计划支持如下特征:

a.软盘babylinux的所有功能
b.图形界面的支持.
c.一个轻量级的窗口管理器(window maker)
d.网络的支持,
e.至少一个图形web浏览器,可以上网.
f.一个音乐播放器和一个视频播放器.
g.支持中文的显示和输入.
h.可以修改配置并保存数据

我还计划做一个live CD,但是目前已经有很多live CD了,而且都做的非常好.
但是我会自己做一个作为学习linux的一种手段.如果有时间,可能写一个做U盘linux和live CD
的教程.但是,我想不会写的和这个文档一样详细了,我的时间有限.可能大概讲一下原理和步骤.有经验的linux爱好者应该可以通过阅读文档完成制作.

十四,参考文献

2008年7月1日星期二

RHAS4下samba服务包的安装过程

RHAS4下samba服务包的安装过程
本文简单描述了在RHAS4下samba服务包的安装过程,希望对需要的朋友有所帮助。

安装samba软件包
1)安装rpmdb-redhat-4-0.20050107.i386.rpm软件包(该包在RHAS4的CD2中)
#rpm -ivh rpmdb-redhat-4-0.20050107.i386.rpm
2)安装samba软件包(也在RHAS4的CD2中)
#rpm -ivh --aid samba*.rpm
3)检查软件包的内容
#rpm -ql samba
#rpm -ql samba-common
#rpm -ql samba-client

安装过程
#cd /misc/cd/RedHat/RPMS/
#rpm -ivh samba-client- // 报依赖性错误
#rpm -ivh samba-common //同样报依赖性错误
#ls grep rpmdb
#rpm -ivh rpmdb-redhat-4-0.20050107.i386.rpm
#rpm -ivh --aid samba*.rpm //供rpmdb辅助安装所需软件包,--aid选项必须进入RPMS目录才可用
#rpm -qa grep samba
#rpm -ql samba more
#ls ls /usr/share/doc/samba-3.0.10/ //查看帮助文档