免费注册 查看新帖 |

Chinaunix

  平台 论坛 博客 文库
12下一页
最近访问板块 发新帖
查看: 9719 | 回复: 13
打印 上一主题 下一主题

[文件系统] 关于unpack_to_rootfs()的疑问 [复制链接]

论坛徽章:
4
酉鸡
日期:2014-03-21 23:19:50狮子座
日期:2014-08-01 22:11:40酉鸡
日期:2015-01-10 21:31:442015年辞旧岁徽章
日期:2015-03-03 16:54:15
跳转到指定楼层
1 [收藏(0)] [报告]
发表于 2013-01-24 19:06 |只看该作者 |倒序浏览
20可用积分
本帖最后由 chishanmingshen 于 2013-01-25 09:30 编辑

from 3.6.10
populate_rootfs()->unpack_to_rootfs() 做新的initramfs或者旧的initrd的文件拷贝操作。
1. 可是我不明白的是拷贝到哪里去?不用指定文件名字么?比如initrd方式(非cpio)时,内核会建好文件/initrd.image,然后写入。
2. 此时是实际根文件系统是哪里加载的?因为后续才会加载实际根文件系统.
3. header_buf symlink_buf name_buf : 这几个全局变量的作用是?
4. 请指点这个函数的具体机制.
谢谢!

  1. static char * __init unpack_to_rootfs(char *buf, unsigned len)
  2. {
  3.         int written, res;
  4.         decompress_fn decompress;
  5.         const char *compress_name;
  6.         static __initdata char msg_buf[64];

  7.         header_buf = kmalloc(110, GFP_KERNEL);
  8.         symlink_buf = kmalloc(PATH_MAX + N_ALIGN(PATH_MAX) + 1, GFP_KERNEL);
  9.         name_buf = kmalloc(N_ALIGN(PATH_MAX), GFP_KERNEL);

  10.         if (!header_buf || !symlink_buf || !name_buf)
  11.                 panic("can't allocate buffers");

  12.         state = Start;
  13.         this_header = 0;
  14.         message = NULL;
  15.         while (!message && len) {
  16.                 loff_t saved_offset = this_header;
  17.                 if (*buf == '0' && !(this_header & 3)) {
  18.                         state = Start;
  19.                         written = write_buffer(buf, len);<---(*actions[])将数据写到哪里去了?求详解。。
  20.                         buf += written;
  21.                         len -= written;
  22.                         continue;
  23.                 }
  24.                 if (!*buf) {
  25.                         buf++;
  26.                         len--;
  27.                         this_header++;
  28.                         continue;
  29.                 }
  30.                 this_header = 0;
  31.                 decompress = decompress_method(buf, len, &compress_name);
  32.                 if (decompress) {
  33.                         res = decompress(buf, len, NULL, flush_buffer, NULL,
  34.                                    &my_inptr, error);
  35.                         if (res)
  36.                                 error("decompressor failed");
  37.                 } else if (compress_name) {
  38.                         if (!message) {
  39.                                 snprintf(msg_buf, sizeof msg_buf,
  40.                                          "compression method %s not configured",
  41.                                          compress_name);
  42.                                 message = msg_buf;
  43.                         }
  44.                 } else
  45.                         error("junk in compressed archive");
  46.                 if (state != Reset)
  47.                         error("junk in compressed archive");
  48.                 this_header = saved_offset + my_inptr;
  49.                 buf += my_inptr;
  50.                 len -= my_inptr;
  51.         }
  52.         dir_utime();
  53.         kfree(name_buf);
  54.         kfree(symlink_buf);
  55.         kfree(header_buf);
  56.         return message;
  57. }
复制代码

最佳答案

查看完整内容

回复 3# chishanmingshen 就是这个"unpack_to_rootfs就是将initramfs或者initrd的内容释放到"/"那里", 我搞不明白其中的奥秘...任何文件系统的访问都要以来于建立在RAM中的文件系统相关的数据结构,这些最基本的数据结构就是位于RAM中的"/",当需要访问外部的存储器而不是在RAM中的该如何办呢?在RAM中的“/”留一个挂在点去mount,来搭建一条访问的路径。unpack_to_rootfs做的就是在RAM的“/”建立ramdisk中事先建立好的一些 ...

论坛徽章:
0
2 [报告]
发表于 2013-01-24 19:06 |只看该作者
提示: 作者被禁止或删除 内容自动屏蔽

论坛徽章:
0
3 [报告]
发表于 2013-01-25 10:11 |只看该作者
提示: 作者被禁止或删除 内容自动屏蔽

论坛徽章:
4
酉鸡
日期:2014-03-21 23:19:50狮子座
日期:2014-08-01 22:11:40酉鸡
日期:2015-01-10 21:31:442015年辞旧岁徽章
日期:2015-03-03 16:54:15
4 [报告]
发表于 2013-01-25 10:26 |只看该作者
感谢回复!
就是这个"unpack_to_rootfs就是将initramfs或者initrd的内容释放到"/"那里", 我搞不明白其中的奥秘...
是说释放之后, "/"就是实际根文件系统了, 是吧? 只是这个系统是特殊的, 是在ram中的?

回复 2# stephen_du


   

论坛徽章:
4
酉鸡
日期:2014-03-21 23:19:50狮子座
日期:2014-08-01 22:11:40酉鸡
日期:2015-01-10 21:31:442015年辞旧岁徽章
日期:2015-03-03 16:54:15
5 [报告]
发表于 2013-01-25 13:03 |只看该作者
哦...有点明白了.我的理解, 按顺序的3个阶段:
1. 首先建立虚拟根文件系统, 就是"/"
2. initrd/initramfs释放得到rootfs, 就是"/root"
3. mount真正的根文件系统, 自然也会有新的"/root"

如有不正, 请指点, 谢谢!

回复 4# stephen_du


   

论坛徽章:
0
6 [报告]
发表于 2013-01-25 13:08 |只看该作者
提示: 作者被禁止或删除 内容自动屏蔽

论坛徽章:
4
酉鸡
日期:2014-03-21 23:19:50狮子座
日期:2014-08-01 22:11:40酉鸡
日期:2015-01-10 21:31:442015年辞旧岁徽章
日期:2015-03-03 16:54:15
7 [报告]
发表于 2013-01-25 15:08 |只看该作者
最后一点:
header_buf symlink_buf name_buf : 这几个全局变量的作用是?

论坛徽章:
0
8 [报告]
发表于 2014-05-22 14:29 |只看该作者
要知道 header_buf symlink_buf name_buf,这三个buf的作用需要对cpio的格式有所了解.
CPIO 的结构是这样的:
                   110字节的Head(6 + 8*13)
                   不定长的文件名(文件名的长度是olen)
                   结束字符 \0
                   文件的内容
                   .... //重复上面4个
                   最后的文件名是一个 TRAILER!!!
了解了cpio的格式之后就很容易知道:  
1. header_buf就是一个文件在cpio中的head,共110个字节
      header_buf = kmalloc(110, GFP_KERNEL);
2.  symlink_buf就是符号链接所指的路径
     假设有这样的符号连接:  ln -s /home/cong/Desktop/record.txt link
     symlink_buf="/home/cong/Desktop/record.txt"
3. name_buf 就是文件名(除符号链接之外的文件名),
    可以是普通文件名,目录名,FIFO名等反正就是存名字

这些都很容易理解, 就是有一点需要注意: 什么时候会用到这些buffer?
以header_buf为例说明一下:
    内核两次调用了unpack_to_rootfs,
    第一次解压usr/initramfs_data.cpio,这时候head_buff压根就没有用到.

    第二次是解压initramfs,这个rootfs是gzip压缩的,内核会一边解压缩initramfs一边把解压出来的文件填充到文件系统中.
    解压后并不是每一次都把110个字节拷贝到header_buf中,这样没有必要
    而是在gunzip中每次解压出的32K的buffer, 只有当这32k剩下的数据是cpio的头且不足110个字节时,才会用到header_buf.
    先将不足的字节临时放在header_buf中,然后再调用gunzip,从解出32K的buffer中拿走剩下的字节填充到header_buf中凑満110个字节.
symlink_buf, name_buf同样也是这种情况下才使用.

论坛徽章:
4
酉鸡
日期:2014-03-21 23:19:50狮子座
日期:2014-08-01 22:11:40酉鸡
日期:2015-01-10 21:31:442015年辞旧岁徽章
日期:2015-03-03 16:54:15
9 [报告]
发表于 2014-05-24 13:15 |只看该作者
本帖最后由 chishanmingshen 于 2014-05-24 13:42 编辑

回复 8# wangcong02345

thanks!

>第一次解压usr/initramfs_data.cpio,这时候head_buff压根就没有用到.

  第一次为啥没用到?  请指教,谢谢!  

论坛徽章:
0
10 [报告]
发表于 2014-05-26 11:33 |只看该作者
head_buff什么时候才会用到呢? 只有在解压过程中才有可能用到.
像initramfs或者旧的initrd文件的生成过程都经过了gzip压缩,所以内核在用这些文件时需要先解压缩,gunzip每次会解压出32Kbuffer, 只有当这32k剩下的数据是cpio的头且不足110个字节时,才会用到header_buf.
而第一次解压的/usr/initramfs_dat.cpio,这是个cpio文件没有经过压缩,也就没有解压的过程,所以不会用到header_buf.
您需要登录后才可以回帖 登录 | 注册

本版积分规则 发表回复

  

北京盛拓优讯信息技术有限公司. 版权所有 京ICP备16024965号-6 北京市公安局海淀分局网监中心备案编号:11010802020122 niuxiaotong@pcpop.com 17352615567
未成年举报专区
中国互联网协会会员  联系我们:huangweiwei@itpub.net
感谢所有关心和支持过ChinaUnix的朋友们 转载本站内容请注明原作者名及出处

清除 Cookies - ChinaUnix - Archiver - WAP - TOP