linux学习笔记(未完)

=======================================================================
Linux文件隐藏属性


文件都具有隐藏属性,隐藏属性对于系统安全来说很重要。
① 设置文件隐藏属性
[root@localhost /]#chattr [-R] [-+=] [AacDdijsSu] 文件名
(A)no atime updates;
(a)append only;
(c)compressed;
(D)synchronous directory updates;
(d)no dump;
(i)immutable;
(j)data journalling;
(s)secure deletion;
(S)synchronous updates;
(u)undeletable;
(T)and top of directory hierarchy;
(t)no tail-merging。
常用参数意义:
-R:递归处理。
-:删除某个隐藏属性,其他原本存在的属性不改变。
+:添加某个隐藏属性,其他原本存在的属性不改变。
=:将隐藏属性设置为指定的参数,其他原本存在的属性会被改掉。
A(atime):如果设置了A属性,则这个文件的最后访问时间atime不能被修改。
a(append only):如果设置了a属性,则这个文件只能增加数据,不允许任何进程覆盖或截断这个文件。如果某个目录具有这个属性,那么只能在这个目录下建立和修改文件,而不能删除任何文件。
i(immutable):如果设置了i属性,则不能对这个文件做任何修该。如果某个目录具有这个属性,那么只能修改该目录下的文件,而不能建立和删除文件。
s(secure deletion):如果设置了s属性,则这个文件将从硬盘空间中完全删除。
u(undeletable):与s完全相反。如果设置了u属性,则这个文件虽然被删除了,但是还在硬盘空间中存在,还可以用来还原恢复。
 
② 查看文件隐藏属性
文件既然有隐藏属性,那么我们如何查看这些文件的隐藏属性呢?
[root@localhost /]#lsattr [-RVadlv] 文件名
-R:递归显示目录文件下的所有文件。
-a:显示隐藏文件的属性。


lsattr
查看文件的扩展属性,
如果文件被 chattr +i   添加了写保护,
用lsattr可以看到添加的属性

file
查看文件的类型

stat
查看文件的状态

=======================================================================

linux kernel compile


step1:
(if needed ;sudo su for root for all acts)
install  ncurses : ftp://invisible-island.net/ncurses/ (choose ncurses-5.7.tar.gz for my process)
step2:
: cat /proc/version (check the version your kernel to run )
download linux source code for kernel(choose 2.6.31 for my process)
: cp linux-2.6.31.tar.gz(tar.bz2) /usr/src/
: cd /usr/src
: tar -xvvzf linux-2.6.30.tar.gz(tar  xvjf linux-2.6.31.tar.bz2)
: cd linux-2.6.31
(if needed ;sudo su for root)
step3:
: make menuconfig (configure the module as you want )
step4:
compile the kernel
: make
step5:
compile the modules
: make modules
step6:
install the modules
: make modules_install
step7:
: make install   
step8:
Copy this image to boot directory(note:where the bzImage is created can get from the make install message, match it indeed )
: cp arch/x86/boot/bzImage /boot/vmlinuz-2.6.31
step9:
: cd /boot
: mkinitramfs -o initrd.img-2.6.31 2.6.31(match the version for yours)
step10:
: cp /boot/grub/menu.lst /boot/grub/menu.lst.old( backup the menu.lst)
: update-grub(note :choose the first one to create new menu.lst)
step11:
modify the value if necessary (note : if the title no match initrd, copy other for it )
: gedit /boot/grub/menu.lst(save if need)
step12:
: reboot

=======================================================================

PCI驱动编写流程


step1:
define the PCI ID table
step2:
create probe() callback
step3:
create remove() callback
step4:
create a pci_driver structure containing the three pointers above
step5:
create an init() function just calling the pci_register_driver() to register the pci_driver
table defined above.
step6:
create an exit() function to call the pci_unregister_driver() function.

=======================================================================

驱动程序的基本函数


类别

函数名

功能

函数形成

参数

描述

驱动程序入口和出口点

module_init

驱动程序初始化入口点

module_init ( x)

x为启动时或插入模块时要运行的函数

如果在启动时就确认把这个驱动程序 插入内核或以静态形成链接,则module_init 将其初始化例程加入到"__initcall.int"代码段,否则将用init_module封装其初始化例程,以便该驱动程序作为模块来使用。

module_exit

驱动程序退出出口点

module_exit ( x)

x为驱动程序被卸载时要运行的函数

当驱动程序是一个模块,用rmmod卸载一个模块时module_exit()将用cleanup_module()封装clean-up代码。如果驱动程序是静态地链接进内核,则module_exit()函数不起任何作用。

原子和指针操作

atomic_read

读取原子变量

atomic_read ( v)

v为指向atomic_t类型的指针

原子地读取v的值。注意要保证atomic的有用范围只有24位。

atomic_set

设置原子变量

atomic_set ( v, i)

v为指向atomic_t类型的指针,i为待设置的值

原子地把v的值设置为i。注意要保证atomic的有用范围只有24位。

atomic_add

把整数增加到原子变量

void atomic_add (int i, atomic_t * v)

i为要增加的值,v为指向atomic_t类型的指针。

原子地把i 增加到v。注意要保证atomic的有用范围只有24位。

atomic_sub

减原子变量的值

void atomic_sub (int i, atomic_t * v)

i为要减取的值,v为指向atomic_t类型的指针。

原子地从v减取i。注意要保证atomic的有用范围只有24位。

atomic_sub_and_test

从变量中减去值,并测试结果

int atomic_sub_and_test (int i, atomic_t * v)

i为要减取的值,v为指向atomic_t类型的指针。

原子地从v减取i的值,如果结果为0,则返回真,其他所有情况都返回假。注意要保证atomic的有用范围只有24位。

atomic_inc

增加原子变量的值

void atomic_inc (atomic_t * v)

v为指向atomic_t类型的指针。

原子地从v减取1。注意要保证atomic的有用范围只有24位。

atomic_dec

减取原子变量的值

void atomic_dec (atomic_t * v)

v为指向atomic_t类型的指针。

原子地给v增加1。注意要保证atomic的有用范围只有24位。

atomic_dec_and_test

减少和测试

int atomic_dec_and_test (atomic_t * v)

 v为指向atomic_t类型的指针。

原子地给v减取1,如果结果为0,则返回真,其他所有情况都返回假。注意要保证atomic的有用范围只有24位。

atomic_inc_and_test

增加和测试

int atomic_ inc _and_test (atomic_t * v)

 v为指向atomic_t类型的指针。

原子地给v增加1,如果结果为0,则返回真,其他所有情况都返回假。注意要保证atomic的有用范围只有24位。

atomic_add_negative

如果结果为负数,增加并测试

int atomic_add_negative (int i, atomic_t * v)

i为要减取的值,v为指向atomic_t类型的指针。

原子地给v增加i,如果结果为负数,则返回真,如果结果大于等于0,则返回假。注意要保证atomic的有用范围只有24位。

et_unaligned

从非对齐位置获取值

get_unaligned ( ptr)

ptr指向获取的值

 

这个宏应该用来访问大于单个字节的值,该值所处的位置不在按字节对齐的位置,例如从非u16对齐的位置检索一个u16的值。注意,在某些体系结构中,非对齐访问要化费较高的代价。

put_unaligned

把值放在一个非对齐位置

put_unaligned ( val, ptr)

val为要放置的值,ptr指向要放置的位置

 

这个宏用来把大于单个字节的值放置在不按字节对齐的位置,例如把一个u16值写到一个非u16对齐的位置。注意事项同上。

延时、调度及定时器例程

schedule_timeout

睡眠到定时时间到

signed long schedule_timeout (signed long timeout)

timeout为以jiffies为单位的到期时间

使当前进程睡眠,直到所设定的时间到期。如果当前进程的状态没有进行专门的设置,则睡眠时间一到该例程就立即返回。如果当前进程的状态设置为:

TASK_UNINTERRUPTIBLE:则睡眠到期该例程返回0

:TASK_INTERRUPTIBLE:如果当前进程接收到一个信号,则该例程就返回,返回值取决于剩余到期时间。

  当该例程返回时,要确保当前进程处于TASK_RUNNING状态。

 

=======================================================================

查看Linux内核、CPU、内存及各组件版本的命令和方法



查看内核版本:
uname -a
more /etc/*release
more /etc/redhat-release
more /proc/version
查看CPU信息:
grep "model name" /proc/cpuinfo                   
more /proc/cpuinfo
查看CPU位数:
getconf LONG_BIT                 
查看libc、gcc版本:
ldd /sbin/mii-tool                              
rpm -qa | grep glibc
gcc –v
查看内存信息:
more /proc/meminfo
grep MemTotal /proc/meminfo

=======================================================================

linux管理命令

ps:查看系统中的进程,Linux中可以使用ps -aux查看所有进程

top:显示系统内存、cpu使用情况,并可自动刷新进程列表

vmstat:显示当前的内存使用情况

netstat:显示网络状况,使用参数p可以查看对应的进程号及程序名,

ifconfig:查看(或设置)网络设备信息

ifconfig -a:查看所有网络设置信息

last:显示登录到服务器的情况以及服务器重启情况

lsof:显示当前打开的文件列表,包括建立的socket连接等。

sysctl:显示(或设置)系统内核参数

sysctl -a 显示所有内核参数

sysctl -w 参数名=参数值

ulimit:显示(或设置)用户可以使用的资源限制

ulimit -a 显示用户可以使用的资源限制

df:显示硬盘空间及使用情况,Linux下可以带参数h,显示结果更人性化。例如:

df -h 硬盘空间按人性化显示

df -k 硬盘空间按KB显示

df -m 硬盘空间按MB显示

w:显示登录到服务器上的用户列表

COMMAND 命令 DESCRIPTION 注解
System information
系统信息
arch show architecture of machine
显示主机的体系结构
uname -r show used kernel version
显示kernel版本信息
dmidecode -q show hardware system components - (SMBIOS / DMI)
显示硬件系统部件
hdaparm -i /dev/hda displays the characteristics of a hard-disk
显示某一硬盘特点
hdparm -tT /dev/sda perform test reading on a hard-disk
执行某一硬盘读取测试
cat /proc/cpuinfo show information CPU info
显示CPU信息
cat /proc/interrupts show interrupts
显示中断信息
cat /proc/meminfo verify memory use
核实内存使用情况
cat /proc/swaps show file(s) swap
显示文件swap情况
cat /proc/version show version of the kernel
显示kernel版本信息
cat /proc/net/dev show network adpters and statistics
显示网络信息
cat /proc/mounts show mounted file system(s)
显示挂载系统信息
lspci -tv display PCI devices
显示PCI设备
lsusb -tv show USB devices
显示USB设备
date show system date
显示系统日期
cal 2007 show the timetable of 2007
显示2007年日历
date 041217002007.00 set date and time
- MonthDayhoursMinutesYear.Second
设置时间和日期 - 格式:月日时分年.秒
clock -w save changes on BIOS
保存BIOS设置
 

COMMAND 命令 DESCRIPTION 注解
Shutdown, Restart of a system and Logout
系统关机,重启或注销
shutdown -h now shutdown system
关闭系统
init 0
shutdown -r hours:minutes planned shutdown of the system
定时关机
shutdown -c cancel a planned shutdown of the system
取消定时关机
shutdown -r now reboot
重启系统
reboot
logout leaving session
注销用户
 


COMMAND 命令 DESCRIPTION 注解
Mounting a Filesystem
挂载文件系统
mount /dev/hda2 /mnt/hda2 mount disk called hda2 - verify existence of the directory '/ mnt/hda2'
挂载名为hda2的硬盘设备
umount /dev/hda2 unmount disk called hda2 - exit from mount point '/ mnt/hda2' first
取消挂载名为hda2的硬盘设备
fuser -km /mnt/hda2 force umount when the device is busy
强行取消挂载设备
umount -n /mnt/hda2 run umount without writing the file /etc/mtab - useful when the file is read-only or the hard disk is full
不记录挂载信息直接取消挂载
- 当硬盘为只读或硬盘已满时很实用
mount /dev/fd0 /mnt/floppy mount a floppy disk
挂载软盘
mount /dev/cdrom /mnt/cdrom mount a cdrom / dvdrom
挂载CDrom或DVDrom
mount /dev/hdc /mnt/cdrecorder mount a cdrw / dvdrom
挂载CD-RW或DVDrom
mount /dev/hdb /mnt/cdrecorder mount a cdrw / dvdrom
挂载CD-RW或DVDrom
mount -o loop file.iso /mnt/cdrom mount a file or iso image
挂载一个文件或ISO光盘镜像
mount -t vfat /dev/hda5 /mnt/hda5 mount a Windows FAT32 file system
挂载windows FAT32文件系统
mount /dev/sda1 /mnt/usbdisk mount a usb pen-drive or flash-drive
挂载USB闪存设备
mount -t smbfs -o username=user,password=pass //winclient/share /mnt/share mount a windows network share
挂载windows网络共享
 

pstree  显示进程衍生关系

=======================================================================

NFS相关

host
1  NFS安装
    ####sudo apt-get install nfs-kernel-server
    ####sudo apt-get install portmap nfs-kernel-server
    sudo apt-get install nfs-kernel-server nfs-common portmap



    配置NFS:
        配置portmap$ sudo dpkg-reconfigure portmap ,
        对Should portmap be bound to the loopback address? 选N.

    In /etc/default/nfs-common we set:
        NEED_IDMAPD=yes
        NEED_GSSD=no # no is default
    
     /etc/idmapd.conf file
        [Mapping]
            Nobody-User = nobody
            Nobody-Group = nogroup


    配置/etc/hosts.deny
        禁止任何host(主机)能和你的NFS服务器进行NFS连接,加入:
            ### NFS DAEMONS
            portmap:ALL
            lockd:ALL
            mountd:ALL
            rquotad:ALL
            statd:ALL

    配置/etc/hosts.allow
        允许那些你想要的主机和你的NFS服务器建立连接。
        下列步骤将允许任何IP地址以192.168.1开头的主机(连接到NFS服务器上),
        也可以指定特定的IP地址。参看man页 hosts_access(5), hosts_options(5)。
        ### NFS DAEMONS
        portmap: 192.168.1.
        lockd: 192.168.1.
        rquotad: 192.168.1.
        mountd: 192.168.1.
        statd: 192.168.1.

    /etc/hosts.deny 和 /etc/hosts.allow 设置对portmap的访问.
    采用这两个配置文件有点类似"mask"的意思.
    先在/etc/hosts.deny中禁止所有用户对portmap的访问.
    再在/etc/hosts.allow 中允许某些用户对portmap的访问.

        运行 $ sudo /etc/init.d/portmap restart 重启portmap daemon.
            (sudo service portmap restart)

2  修改配置文件/etc/exports
    /directory   *(rw,sync,no_root_squash)
        no_root_squash,挂载此目录的客户机享有主机root的权利;
        最好加上sync,否则$ sudo exportfs -r 时会给出警告, sync是NFS的默认选项.

    修改目录权限 :chmod 777 -R /directory

3  exportfs –rv来使配置文件生效
    sudo exportfs -arv
    
    运行 $ showmount -e 查看NFS server的export list

4  配置宿主机的IP
    # ifconfig eth0 192.168.x.xx
5  启动宿主机NFS服务
    //-----/etc/init.d/portmap restart
    /etc/init.d/nfs-kernel-server restart
    $ sudo iptables -F

client
    $ sudo apt-get install nfs-commmon
    #sudo /etc/init.d/portmap start
    将portmap服务开启。
    然后执行(192.168.1.121这是我的服务器IP地址):
    # showmount -e 192.168.1.121

    mount -t nfs -o intr,nolock,rsize=1024,wsize=1024 <host ip>:/主机nfs目录 /挂载路径

    auto mount by fstab

        sudo gedit /etc/fstab

                      192.168.1.121:/home/zhaohui/NFS_11_04 /home/zhaohui/NFS_client nfs auto,rw,user 0 0
                      192.168.1.121:/home/zhaohui/NFS_10_04 /home/zhaohui/NFS_client nfs auto,rw,user 0 0
                      192.168.1.121:/home/zhaohui/NFS_09_10 /home/zhaohui/NFS_client nfs auto,rw,user 0 0


Ubuntu nfs常用的参数有:
        ro 只读访问
        rw 读写访问sync 所有数据在请求时写入共享
        async nfs在写入数据前可以响应请求
        secure nfs通过1024以下的安全TCP/IP端口发送
        insecure nfs通过1024以上的端口发送
        wdelay 如果多个用户要写入nfs目录,则归组写入(默认)
        no_wdelay 如果多个用户要写入nfs目录,则立即写入,当使用async时,无需此设置。
        hide 在nfs共享目录中不共享其子目录
        no_hide 共享nfs目录的子目录
        subtree_check 如果共享/usr/bin之类的子目录时,强制nfs检查父目录的权限(默认)
        no_subtree_check 和上面相对,不检查父目录权限
        all_squash 共享文件的UID和GID映射匿名用户anonymous,适合公用目录。
        no_all_squash 保留共享文件的UID和GID(默认)
        root_squash root用户的所有请求映射成如anonymous用户一样的权限(默认)
        no_root_squas root用户具有根目录的完全管理访问权限
        anonuid=xxx 指定nfs服务器/etc/passwd文件中匿名用户的UID
        anongid=xxx 指定nfs服务器/etc/passwd文件中匿名用户的GID

NFS相关的几个文件, 命令:
    1, /etc/exports
    对NFS卷的访问是由exports来批准, 它枚举了若干有权访问NFS服务器上文件系统的主机名.
    2, /usr/sbin/exportfs
    维护NFS的资源共享. 可以通过它重新设定 /etc/exports 的共享目录, 卸载NFS Server共享的目录或者重新共享等.
    3, /usr/sbin/showmount
    用在 NFS Server 端,而 showmount 则主要用在 Client 端. showmount 可以用來查看 NFS 共享的目录资源.
    4, /var/lib/nfs/xtab
    NFS的记录文档: 通过它可以查看有哪些Client 连接到NFS主机的记录.

RPC相关的几个文件
    5, /etc/default/portmap
    实际上, portmap负责映射所有的RPC服务端口, 它的内容非常非常之简单(后面详述)
    6, /etc/hosts
    设定拒绝\允许portmap服务的主机


other for ubuntu
安装解压文件!
    sudo apt-get install unace unrar zip unzip p7zip-full p7zip-rar
                sharutils rar uudeview mpack lha arj
                cabextract file-roller
备份数据Deja Dup!
    sudo apt-get install deja-dup


=======================================================================

GNU binutils工具使用


GNU binutils 是一组二进制工具集。包括:addr2line   ar   gprof   nm   objcopy   objdump   ranlib   size   strings   strip. 本文归纳他们的常用法。

ar
    ar 用于建立、修改、提取档案文件(archive)。archive是一个包含多个被包含文件的单一文件(也称之为库文件),其结构保证了可以从中检索并得到原始的被包含文件(称之为archive中的member)。member的原始文件内容、模式(权限)、时间戳、所有着和组等属性都被保存在archive中。member被提取后,他们的属性被恢复到初始状态。
   
    ar主要用于创建C库文件(关于.o目标文件的生成和共享库的详细介绍,参考gcc笔记创建静态库 
    (1) 生成目标文件:   )

$ gcc -Wall -c file1.c file2.c file3.c
   
   
不用指定生成.o文件名(默认生成file1.o, file2.o, file3.o)。

    (2) 从.o目标文件创建静态连接库:
   
$ ar rv libNAME.a file1.o file2.o file3.o
   
    ar
生成了libNAME.a库,并列出库中的文件。
    r : 将flie1.o, file2,o, file3.o插入archive,如故原先archive中已经存在某文件,则先将该文件删除。
    v : 显示ar操作的附加信息(如被处理的member文件名)

注: 对于BSD系统, 还需要在创建静态库之后创建索引: $ ranlib libNAME.a Linux中不需要这一步(运行它也是无害的).
创建动态库(利用gcc,未用ar)

(1) 生成目标文件
 
$ gcc -Wall -c -fpic file1.c file2.c file3.c

-fpic:
指定生成的.o目标文件可被重定址. pic是position idependent code的缩写: 位置无关代码.

(2)生成动态库文件
$ gcc -shared -o libNAME.so file1.o file2.o file3.o

一般地, 连接器使用main()函数作为程序入口. 但在动态共享库中没有这样的入口. 所以就要指定-shared选项来避免编译器显示出错信息.

实际上, 上述的两条命令可以合并为下面这条:
$ gcc -Wall -shared -fpic -o libNAME.so file1.c file2.c file3.c


此后,将main函数所在的程序与libNAME.so连接(注意库连接路径和头文件包含路径,以及连接顺序!参考gcc笔记
   
至此,与动态库连接的函数编译成了一个可执行文件。貌似成功了,但还差最后一步。如果直接运行该程序,会给出这样的错误信息:
error while loading shared libraries: libhello.so:
cannot open shared object file: No such file or directory

这是因为与动态库连接的程序在运行时,首先将该动态库加载到内存中,而gcc默认加载动态库文件所在目录为/usr/local/lib, /usr/lib。刚才的程序虽然能编译成功,但如果我们自己建立的动态库没有位于默认目录中,则执行时会应为无法找到它而失败。
  
解决办法:改变加载路径对应的环境变量,然后再执行。
   
export LD_LIBRARY_PATH= 动态库所在目录 :$LD_LIBRARY_PATH

查看archive内容
$ ar tv archiveNAME

t :
显示archive中member的内容,若不指定member,则列出所有。
v : 与t结合使用时,显示member的详细信息。

要想进了解ar的详细选项,参考ar的on-line manual


nm
    nm 用来列出目标文件中的符号,可以帮助程序员定位和分析执行程序和目标文件中的符号信息和它的属性。
    如果没有目标文件作为参数传递给nm, nm假定目标文件为a.out.
    这里用一个简单的示例程序来介绍nm的用法:

main.c:
int main(int argc, char *argv[])
{
  hello();
  bye();
  return 0;
}

hello.c:  
void hello(void)
{
  printf("hello!/n");
}

bye.c:
   
void bye(void)
{
  printf("good bye!/n");
}

   
运行下列命令:
    $ gcc -Wall -c main.c hello.c bye.c
    gcc
生成main.o, hello.o, bye.o三个目标文件(这里没有声明函数原型,加了-Wall,gcc会给出警告)
    $ nm main.o hello.o bye.o

结果显示如下:  
main.o:
                 U bye
                 U hello
00000000 T main

hello.o:
00000000 T hello
                 U puts

bye.o:
00000000 T bye
                 U puts

   
结合这些输出结果,以及程序代码,可以知道:
    对于main.o, bye和hello未被定义, main被定义了
    对于hello.o, hello被定义了, puts未被定义
    对于bye.o, bye被定义了,puts未被定义

几个值得注意的问题:
    (1)"目标文件"指.o文件, 库文件, 最终的可执行文件
    .o  : 编译后的目标文件,即含有最终编译出的机器码,但它里面所引用的其他文件中函数的内存位置尚未定义.
    (2)如果用nm查看可执行文件, 输出会比较多, 仔细研究输出, 可以对nm用法有更清醒的认识.
   (3)在上述hello.c, bye.c中, 调用的是printf(), 而nm输出中显示调用的是puts(),说明最终程序实际调用的puts(), 如果令hello.c或bye.c中的printf()使用格式化输出,则nm显示调用printf(). (如: printf("%d", 1); )
   
    关于nm的参数选项,参考on-line manual


objcopy
    objcopy 可以将一种格式的目标文件转化为另外一种格式的目标文件. 它使用GNU BFD库进行读/写目标文件.使用BFD, objcopy就能将原格式的目标文件转化为不同格式的目标文件.
    以我们在nm中使用的hello.o目标文件和hello可执行为例:
$ file hello.o hello
  
    file
命令用来判别文件类型, 输出如下:
   
hello.o: ELF 32-bit LSB relocatable, Intel 80386, version 1 (SYSV), not stripped
hello: ELF 32-bit LSB executable, Intel 80386, version 1 (SYSV), for GNU/Linux2.2.0, dynamically linked (uses shared libs), not stripped
   

   
现在运行objcopy来改变hello的文件类型: 原先它是ELF格式的可执行程序, 现将它转换为srec格式. srec格式文件是Motolora S-Record格式的文件, 主要用来在主机和目标机之间传输数据.
   
$ objcopy -O srec hello hello_srec
$ file hello.o hello

    file
命令结果: hello_srec: Motorola S-Record; binary data in text format

    注意objcopy的格式, "-O"指定输出文件类型; 输入文件名和输出文件名位于命令末尾. 关于objcopy命令的详细选项, 参考on-line manual


objdump
    objdump 用来显示目标文件的信息. 可以通过选项控制显示那些特定信息. objdump一个最大的用处恐怕就是将C代码反汇编了. 在嵌入式软件开发过程中, 也可以用它查看执行文件或库文件的信息.
    下面我们用上文提到的hello可执行文件和hello_srec可执行文件为例, 介绍objdump的简单用法:
   
$ objdump -f hello hello_srec

输出如下:
hello:     file format elf32-i386
architecture: i386, flags 0x00000112:
EXEC_P, HAS_SYMS, D_PAGED
start address 0x080482c0

hello_srec:     file format srec
architecture: UNKNOWN!, flags 0x00000000:
start address 0x00000000080482c0
   

-f :
显示目标文件的头文件概要信息.

生成反汇编代码:
   
$ objdump -d hello.o

显示如下:
hello.o:     file format elf32-i386

Disassembly of section .text:

00000000 <hello>:
   0:   55                      push   %ebp
   1:   89 e5                   mov    %esp,%ebp
   3:   83 ec 08                sub    $0x8,%esp
   6:   83 ec 0c                sub    $0xc,%esp
   9:   68 00 00 00 00          push   $0x0
   e:   e8 fc ff ff ff          call   f <hello+0xf>
  13:   83 c4 10                add    $0x10,%esp
  16:   c9                      leave
  17:   c3                      ret

    -d :
显示目标文件中机器指令使用的汇编语言. 只反汇编那些应该含有指令机器码的节(显示.text段); 如果用-D, 则反汇编所有节的内容.
    关于objcopy命令的详细选项, 参考on-line manual


readelf
    readelf 用来显示ELF格式目标文件的信息.可通过参数选项来控制显示哪些特定信息.(注意: readelf不支持显示archive文档, 也不支持64位的ELF文件).
    下面利用先前的hello可执行文件演示readelf的简单用法:
   
$ readelf -h hello

ELF Header:
  Magic:   7f 45 4c 46 01 01 01 00 00 00 00 00 00 00 00 00
  Class:                                           ELF32
  Data:                                            2's complement, little endian
  Version:                                        1 (current)
  OS/ABI:                                          UNIX - System V
  ABI Version:                                   0
  Type:                                              EXEC (Executable file)
  Machine:                                        Intel 80386
  Version:                                          0x1
  Entry point address:                       0x80482c0
  Start of program headers:              52 (bytes into file)
  Start of section headers:                 3848 (bytes into file)
  Flags:                                               0x0
  Size of this header:                          52 (bytes)
  Size of program headers:                32 (bytes)
  Number of program headers:          7
  Size of section headers:                  40 (bytes)
  Number of section headers:            34
  Section header string table index:   31

注意: readelf只能用于ELF格式目标文件, 且选项中至少要指定一个(除V, H外)的选项!


gprof
    gprof 被用来测量程序的性能. 它记录每个函数被调用的次数以及相应的执行时间. 这样就能锁定程序执行时花费时间最多的部分, 对程序的优化就可集中于对它们的优化.
   
    用一个简单的数值计算程序来掩饰gprof的用法:
collatz.c:
#include <stdio.h>
/* Computes the length of Collatz sequences */
unsigned int step (unsigned int x)
{
     if (x % 2 == 0)
     {
      return (x / 2);
     }
     else
     {
      return (3 * x + 1);
     }
}

unsigned int nseq (unsigned int x0)
{
     unsigned int i = 1, x;
     if (x0 == 1 || x0 == 0)
      return i;
     x = step (x0);
     while (x != 1 && x != 0)
     {
      x = step (x);
      i++;
     }
     return i;
}

int main (void)
{
     unsigned int i, m = 0, im = 0;
     for (i = 1; i < 500000; i++)
     {
      unsigned int k = nseq (i);
      if (k > m)
      {
           m = k;
           im = i;
           printf ("sequence length = %u for %u/n", m, im);
      }
     }
     return 0;
}

   
先将collatz.c编译成目标文件collatz.o, gcc通过 -pg选项来打开gprof支持:
   
$ gcc -Wall -c -pg collatz.c
 
$ gcc -Wall -pg -o collatz collatz.o

   
注意:两条命令都要加 "-pg"选项。前一条命令生成collatz.o目标文件。后一条命令生成可执行文件,该可执行文件中包含了记录函数执行时间的指令。
    生成collatz可执行文件后,现执行它,结果与一般程序的执行无疑。但此时在PWD目录生成一个名为"gmon.out"的文件,gprof通过它来分析程序的执行。
    如果不现执行程序,而直接用gprof来分析它,会提示“gmon.out: No such file or directory”。
    gprof用法:
   
$ gprof ./collatz

=======================================================================

嵌入式开发基本工具



minicom    
    sudo apt-get install minicom
NFS    
    sudo apt-get install nfs-kernel-server
    sudo gedit /etc/exports
    echo '/home/zhaohui/dvsdk/filesys *(rw,no_root_squash,no_all_squash,sync,no_subtree_check)' >> /etc/exports
    sudo /usr/sbin/exportfs -va
    sudo service nfs-kernel-server restart
tftp    
    sudo apt-get install tftpd-hpa
    sudo gedit /etc/default/tftpd-hpa
        TFTP_USERNAME="tftp"
        TFTP_DIRECTORY="/var/lib/tftpboot"
        TFTP_ADDRESS="0.0.0.0:69"
        TFTP_OPTIONS="-c --secure"
    sudo service tftpd-hpa restart
Uboot-mkimage    
    sudo apt-get install uboot-mkimage
Nautilus-open-terminal    
    sudo apt-get install nautilus-open-terminal
Ibus-pinyin   
    sudo apt-get install ibus-pinyin
rapidsvn   
    sudo apt-get install rapidsvn
meld    
    sudo apt-get install meld





=======================================================================

=======================================================================

你可能感兴趣的:(linux学习笔记(未完))