Linux修改eth2到eth0

没有评论

2012 年 11 月 28 日 at 下午 10:22分类:Linux

之前在公司提供的虚拟机器上面,一直有个问题用着很不舒服,为什么它的IP选择的设备的eth2的,但是我在/etc/sysconfig/network-scrpts/下面也没有找到ifcfg-eth2的配置文件,这样子,我就没法修改IP了,也没法使用静态IP了,每次都是虚拟机动态分配的IP,这个太麻烦了。有时间解决了下这个问题。首先我声明下,我这里是用的NAT的方式与主机相连的。其实我到现在也还没有弄清楚,为什么没有eth2的配置文件,这种情况下 我该如何去修改IP,但是我想这些肯定跟现有的网卡有关,也即是跟现在的mac地址有关系,因为我解决上面的那个问题主要是通过mac出发的。
经查明,Linux是用/etc/network/interfaces这个配置文件来载入网卡的。默认配置中,它指示Linux会自动寻找eth0网卡,并自动分配IP。但是,当虚拟网卡的MAC地址更改后,网卡在Linux中不是eth0了,而是eth1或其它值。因此才会找不到。而现有系统中,有哪些网卡是可用的,可以通过下面的命令查看:
ifconfig -a
使用这个命令后确实,发现每刷新一次mac地址,就生成一个新的eth。
在Linux中,还有一个配置文件:/etc/udev/rules.d/70-persistent-net.rules,打开这个配置文件后,会发现里面列出了所有Linux找到的网卡,包括历史的。因此,解决无法加载网卡的问题就有两个解决办法:
1.修改interfaces配置文件,使其使用最新的eth网卡
2.删除.rules文件,让linux重新将网卡认为是eth0
我找了下interfaces这个文件没有找到,于是我选择了第二个方法,删除rules配置文件,让他重新选择网卡。重启机器之后,敲了ifconfig,出现的不再是eth2了,但是使用的居然是eth1了, 这又让我迷茫了,怎么会变成是eth1了呢? 同时 也没有发现eth1的配置文件,这样子,我还是没法控制IP啊。我查看了下ifconfig命令中的mac地址和ifcfg-eth0中的mac地址比较下,发现两者的mac地址不一样,使用/etc/init.d/network restart 重启网卡,居然报eth0没有这个设备,由此断定,eth0配置文件中的mac地址是错误,于是把eth0配文件中的mac地址改成了ifocnfig中出来的mac地址,然后再次删除/etc/udev/rules.d/70-persistent-net.rules文件,重启机器,让他再次重新选择网卡,启动之后,查看了ifocnfig,这时候变成了eth0,看来是正常了,然后修改下ifcfg-eth0的ip,重启网络服务,没有报错,正常,查看下IP,改过来了,OK,一切正常。
这时又发现新问题了,我在这个虚拟机中常识去访问主机所在网段的机器时,居然报:network unreachable,断定是网关的问题,查看下网关,果然没有设置,在终端是命令:arp -a ,查看本机器的网关,然后修改ifgcfg-eth0,重启服务器,OK,搞定!

linux中sed命令的使用

没有评论

2012 年 11 月 21 日 at 下午 10:25分类:Linux

sed是一个很好的文件处理工具,本身是一个管道命令,主要是以行为单位进行处理,可以将数据行进行替换、删除、新增、选取等特定工作,下面先了解一下sed的用法
sed命令行格式为:sed [-nefri] ‘command’ 输入文本
常用选项:
-n∶使用安静(silent)模式。在一般 sed 的用法中,所有来自 STDIN的资料一般都会被列出到萤幕上。但如果加上 -n 参数后,则只有经过sed
特殊处理的那一行(或者动作)才会被列出来。

-e∶直接在指令列模式上进行 sed 的动作编辑;
-f∶直接将 sed 的动作写在一个档案内, -f filename 则可以执行 filename 内的sed 动作;
-r∶sed 的动作支援的是延伸型正规表示法的语法。(预设是基础正规表示法语法)
-i∶直接修改读取的档案内容,而不是由萤幕输出。
常用命令:
a∶新增, a 的后面可以接字串,而这些字串会在新的一行出现(目前的下一行)~
c∶取代, c 的后面可以接字串,这些字串可以取代 n1,n2 之间的行!
d∶删除,因为是删除啊,所以 d 后面通常不接任何咚咚;
i∶插入, i 的后面可以接字串,而这些字串会在新的一行出现(目前的上一行);
p∶列印,亦即将某个选择的资料印出。通常 p 会与参数 sed -n 一起运作~
s∶取代,可以直接进行取代的工作哩!通常这个 s 的动作可以搭配正规表示法!例如 1,20s/old/new/g 就是啦!

举例:(假设我们有一文件名为ab)
删除某行
[root@localhost www] # sed ’1d’ ab #删除第一行
[root@localhost www] # sed ‘$d’ ab #删除最后一行
[root@localhost www] # sed ’1,2d’ ab #删除第一行到第二行
[root@localhost www] # sed ’2,$d’ ab #删除第二行到最后一行

显示某行
. [root@localhost www] # sed -n ’1p’ ab #显示第一行
[root@localhost www] # sed -n ‘$p’ ab #显示最后一行
[root@localhost www] # sed -n ’1,2p’ ab #显示第一行到第二行
[root@localhost www] # sed -n ’2,$p’ ab #显示第二行到最后一行

使用模式进行查询
[root@localhost www] # sed -n ‘/ruby/p’ ab #查询包括关键字ruby所在所有行
[root@localhost www] # sed -n ‘/\$/p’ ab #查询包括关键字$所在所有行,使用反斜线\屏蔽特殊含义
[root@localhost www] # sed -n ‘/func/p’ app.php | cut -d ‘ ‘ -f 2 |cut -d ‘(‘ -f1 #显示这个文件所有函数名

新增某行(这里没有使用-n,是想让全部显示出来)
[root@localhost www] # sed ’1a drink tea’ ab #第一行后增加字符串”drink tea”
[root@localhost www] # sed ’1,3a drink tea’ ab #第一行到第三行后增加字符串”drink tea”
[root@localhost www] # sed ’1a drink tea\nor coffee’ ab #第一行后增加多行,使用换行符\n

代替一行或多行
[root@localhost www] # sed ’1c Hi’ ab #第一行代替为Hi
[root@localhost www] # sed ’1,2c Hi’ ab #第一行到第二行代替为Hi

插入一行活多行(-i 直接修改文件了)
[root@localhost www] # sed -i ‘$a bye’ ab #在文件ab中最后一行直接输入”bye”

替换一行中的某部分
   格式:sed ‘s/要替换的字符串/新的字符串/g’ (要替换的字符串可以用正则表达式)
[root@localhost www] # sed -n ‘/app/p’ ab | sed ‘s/app/bird/g’ #替换app为bird
  [root@localhost www] # sed -n ‘/app/p’ ab | sed ‘s/app//g’ #删除app

简洁的bash编程技巧

没有评论

2012 年 11 月 08 日 at 下午 7:48分类:Linux

下面这几条是我自己在写shell代码的时候,比较喜欢的几种写法,抛砖引玉。

1) 检查命令执行是否成功
第一种写法,比较常见:

echo abcdee | grep -q abcd
 
if [ $? -eq 0 ]; then
    echo "Found"
else
    echo "Not found"
fi

简洁的写法:

if echo abcdee | grep -q abc; then
    echo "Found"
else
    echo "Not found"
fi

当然你也可以不要if/else,不过这样可读性比较差:

[Sun Nov 04 05:58 AM] [kodango@devops] ~/workspace 
$ echo abcdee | grep -q abc && echo "Found" || echo "Not found"
Found

2) 将标准输出与标准错误输出重定向到/dev/null

第一种写法,比较常见:

grep "abc" test.txt 1>/dev/null 2>&1

常见的错误写法:

grep "abc" test.txt 2>&1 1>/dev/null

简洁的写法:

grep "abc" test.txt &> /dev/null

3) awk的使用
举一个实际的例子,获取Xen DomU的id。
常见的写法:

sudo xm li | grep vm_name | awk '{print $2}'

简洁的写法:

sudo xm li | awk '/vm_name/{print $2}'

4) 将一个文本的所有行用逗号连接起来
假设文件内容如下所示:

[Sat Nov 03 10:04 PM] [kodango@devops] ~/workspace 
$ cat /tmp/test.txt 
1
2
3

使用Sed命令:

[Sat Nov 03 10:14 PM] [kodango@devops] ~/workspace 
$ sed ':a;$!N;s/\n/,/;ta' /tmp/test.txt 
1,2,3

简洁的写法:

[Sat Nov 03 10:04 PM] [kodango@devops] ~/workspace 
$ paste -sd, /tmp/test.txt 
1,2,3

5) 过滤重复行
假设文件内容如下所示:

[Sat Nov 03 10:16 PM] [kodango@devops] ~/workspace 
$ sort /tmp/test.txt 
1
1
2
3

常用的方法:

[Sat Nov 03 10:16 PM] [kodango@devops] ~/workspace 
$ sort /tmp/test.txt | uniq
1
2
3

简单的写法:

[Sat Nov 03 10:16 PM] [kodango@devops] ~/workspace 
$ sort /tmp/test.txt -u
1
2
3

6) grep查找单词
假设一个文本的每一行是一个ip地址,例如

[Sat Nov 03 10:20 PM] [kodango@devops] ~/workspace 
$ cat /tmp/ip.list 
10.0.0.1
10.0.0.12
10.0.0.123

使用grep查找是否包括10.0.0.1这个ip地址。常见的写法:

[Sat Nov 03 10:22 PM] [kodango@devops] ~/workspace 
$ grep '10.0.0.1\>' /tmp/ip.list 
10.0.0.1

简单的方法(其实这方法不见得简单,只是为了说明-w这个参数还是很有用的)

[Sat Nov 03 10:23 PM] [kodango@devops] ~/workspace 
$ grep -w '10.0.0.1' /tmp/ip.list 
10.0.0.1

顺便grep的-n/-H/-v/-f/-c这几参数都很有用。

7) 临时设置环境变量
常见的写法:

[Sat Nov 03 10:26 PM] [kodango@devops] ~/workspace 
$ export LC_ALL=zh_CN.UTF-8 
 
[六 11月 03 10:26 下午] [kodango@devops] ~/workspace 
$ date
2012年 11月 03日 星期六 22:26:55 CST

简洁的写法:

[六 11月 03 10:26 下午] [kodango@devops] ~/workspace 
$ unset LC_ALL
 
[Sat Nov 03 10:27 PM] [kodango@devops] ~/workspace 
$ LC_ALL=zh_CN.UTF-8 date 
2012年 11月 03日 星期六 22:27:43 CST

在命令之前加上环境变更的设置,只是临时改变当前执行命令的环境。

8) $1,$2…等位置参数的使用
假设只想使用$2,$3..这几个参数,常见的做法是:

shift
echo "$@"

为什么不这样写呢?

echo "${@:2}"

9)退而求其次的写法
相信大家会有这种需求,当一个参数值没有提供时,可以使用默认值。常见的写法是:

arg=$1
 
if [ -z "$arg" ]; then
   arg=0
fi

简洁的写法是这样的:

arg=${1:-0}

10)bash特殊参数–的用法

假设要用grep查找字符串中是否包含-i,我们会这样尝试:

[Sat Nov 03 10:45 PM] [kodango@devops] ~/workspace 
$ echo 'abc-i' | grep "-i"
Usage: grep [OPTION]... PATTERN [FILE]...
Try 'grep --help' for more information.
 
[Sat Nov 03 10:45 PM] [kodango@devops] ~/workspace 
$ echo 'abc-i' | grep "\-i"
abc-i

简洁的方法是:

[Sat Nov 03 10:45 PM] [kodango@devops] ~/workspace 
$ echo 'abc-i' | grep -- -i
abc-i

bash中–后面的参数不会被当作选项解析。

11)函数的返回值默认是最后一行语句的返回值

# Check whether an item is a function
# $1: the function name
# Return: 0(yes) or 1(no)
function is_function()
{
    local func_name=$1
    test "`type -t $1 2>/dev/null`" = "function"
}

不要画蛇添足再在后面加一行return $?了。

12) 将printf格式化的结果赋值给变量

例如将数字转换成其十六进制形式,常见的写法是:

[Sat Nov 03 10:55 PM] [kodango@devops] ~/workspace 
$ var=$(printf '%%%02x' 111)

简单的写法是:

[Sat Nov 03 10:54 PM] [kodango@devops] ~/workspace 
$ printf -v var '%%%02x' 111

看看printf的help

[Sat Nov 03 10:53 PM] [kodango@devops] ~/workspace 
$ help printf | grep -A 1 -B 1 -- -v
printf: printf [-v var] format [arguments]
    Formats and prints ARGUMENTS under control of the FORMAT.
--
    Options:
      -v var	assign the output to shell variable VAR rather than
    		display it on the standard output

13)打印文件行

打印文件的第一行:

head -1 test.txt

打印文件的第2行:

sed -n '2p' test.txt

打印文件的第2到5行:

sed -n '2,5p' test.txt

打印文件的第2行始(包括第2行在内)5行的内容:

sed -n '2,+4p' test.txt

打印倒数第二行:

$ tail -2 test.txt | head -1
$ tac test.txt | sed -n '2p'

14)善用let或者(())命令做算术运算

如何对一个数字做++运算,可能你会这样用:

a=1
a=`expr a + 1`

为何不用你熟悉的:

a=1
let a++
let a+=2

15)获取软连接指定的真实文件名

如果你不知道,你可能会这样获取:

[Sat Nov 03 11:12 PM] [kodango@devops] ~/workspace 
$ ls -l /usr/bin/python | awk -F'->' '{print $2}' | tr -d ' '
/usr/bin/python2

如果你知道有一个叫readlink的命令,那么:

[Sat Nov 03 11:13 PM] [kodango@devops] ~/workspace 
$ readlink /usr/bin/python
/usr/bin/python2

16)获取一个字符的ASCII码

[Sat Nov 03 11:14 PM] [kodango@devops] ~/workspace 
$ printf '%02x' "'+"
2b
[Sat Nov 03 11:30 PM] [kodango@devops] ~/workspace 
$ echo -n '+' | od -tx1 -An | tr -d ' '
2b

17)清空一个文件

常见的用法:

echo "" > test.txt

简单的写法:

> test.txt

18) 不要忘记有here document

下面一段代码:

grep -v 1 /tmp/test.txt | while read line; do
    let a++
    echo --$line--
done
 
echo a:$a

执行后有什么问题吗?

[Sun Nov 04 05:35 AM] [kodango@devops] ~/workspace 
$ sh test.sh 
--2--
--3--
a:

发现a这个变量没有被赋值,为什么呢?因为管道后面的代码是在在一个子shell中执行的,所做的任何更改都不会对当前shell有影响,自然a这个变量就不会有赋值了。

换一种思路,可以这样做:

grep -v 1 /tmp/test.txt > /tmp/test.tmp

while read line; do
let a++
echo –$line–
done < /tmp/test.tmp echo a:$a rm -f /tmp/test.tmp 不过多了一个临时文件,最后还要删除。这里其实可以用到here document: b=1 while read line2; do let b++ echo ??$line2?? done < < EOF `grep -v 1 /tmp/test.txt` EOF echo b: $b here document往往用于需要输出一大段文本的地方,例如脚本的help函数。 19)删除字符串中的第一个或者最后一个字符 假设字符串为: [Sun Nov 04 10:21 AM] [kodango@devops] ~/workspace $ str=”aremoveb” 可能你第一个想法是通过sed或者其它命令来完成这个功能,但是其实有很简单的方法: [Sun Nov 04 10:24 AM] [kodango@devops] ~/workspace $ echo “${str#?}” removeb [Sun Nov 04 10:24 AM] [kodango@devops] ~/workspace $ echo “${str%?}” aremove 类似地,你也可以删除2个、3个、4个…… 有没有一次性删除第一个和最后一个字符的方法呢?答案当然是肯定的: [Sun Nov 04 10:26 AM] [kodango@devops] ~/workspace $ echo “${str:1:-1}” remove 关于这些变量替换的内容在bash的man手册中都有说明。 20)使用逗号join数组元素 假设数组元素没有空格,可以用这种方法: [Sun Nov 04 10:14 AM] [kodango@devops] ~/workspace $ a=(1 2 3) $ b=”${a[*]}” [Sun Nov 04 10:15 AM] [kodango@devops] ~/workspace $ echo ${b// /,} 1,2,3 假设数组元素包含有空格,可以借用printf命令来达到: [Sun Nov 04 10:15 AM] [kodango@devops] ~/workspace $ a=(1 “2 3″ 4) [Sun Nov 04 10:15 AM] [kodango@devops] ~/workspace $ printf “,%s” “${a[@]}” | cut -c2- 1,2 3,4 21) Shell中的多进程 在命令行下,我们会在命令行后面加上&符号来让该命令在后台执行,在shell脚本中,使用”(cmd)”可以让fork一个子shell来执行该命令。利用这两点,可以实现shell的多线程: job_num=10 function do_work() { echo “Do work..” } for ((i=0; i