前回cpioアーカイブの構造体はcpio.hではなく、cpiohdr.hにあることが分かりました。
今回は、cpiohdr.h内の構造体を特定して、アーカイブの構造を確認していこうと思います。
まず、構造体のキーワードはstructなので、cpiohdr.hで定義されているstructを検索します。
takk@deb9:~/src/cpio-2.11+dfsg/src$ grep struct cpiohdr.h struct old_cpio_header struct old_ascii_header struct new_ascii_header struct cpio_file_stat /* Internal representation of a CPIO header */ takk@deb9:~/src/cpio-2.11+dfsg/src$
たくさん出てきました。どの構造体がcopyout.c時に使用されているか調べるため、grepパターンリストとして/tmp/greplistに抽出します。
/tmpディレクトリはこのようなときに便利ですね。/tmpの中のファイルは一度使ったら気にしない、とルールを決めておけば困ることはありません。
takk@deb9:~/src/cpio-2.11+dfsg/src$ grep struct cpiohdr.h | cut -d' ' -f2 old_cpio_header old_ascii_header new_ascii_header cpio_file_stat takk@deb9:~/src/cpio-2.11+dfsg/src$ grep struct cpiohdr.h | cut -d' ' -f2 > /tmp/greplist takk@deb9:~/src/cpio-2.11+dfsg/src$
さらにgrepする時単語区切りになるように/tmp/greplistをは各検索キーワードを\<~\>で囲んでおきます。
takk@deb9:~/src/cpio-2.11+dfsg/src$ cat /tmp/greplist \<old_cpio_header\> \<old_ascii_header\> \<new_ascii_header\> \<cpio_file_stat\> takk@deb9:~/src/cpio-2.11+dfsg/src$
grep -fオプションで、/tmp/greplistを与えて、copyout.cの中に各キーワードがあるか探します。
takk@deb9:~/src/cpio-2.11+dfsg/src$ grep -f /tmp/greplist copyout.c
count_defered_links_to_dev_ino (struct cpio_file_stat *file_hdr)
last_link (struct cpio_file_stat *file_hdr)
add_link_defer (struct cpio_file_stat *file_hdr)
writeout_other_defers (struct cpio_file_stat *file_hdr, int out_des)
writeout_defered_file (struct cpio_file_stat *header, int out_file_des)
struct cpio_file_stat file_hdr;
struct cpio_file_stat file_hdr;
struct cpio_file_stat *file_hdr, int out_des)
struct cpio_file_stat *file_hdr, int out_des)
hp_compute_dev (struct cpio_file_stat *file_hdr, dev_t *pdev, dev_t *prdev)
struct cpio_file_stat *file_hdr, int out_des)
struct old_cpio_header short_hdr;
write_out_header (struct cpio_file_stat *file_hdr, int out_des)
struct cpio_file_stat file_hdr; /* Output header information. */
takk@deb9:~/src/cpio-2.11+dfsg/src$
たくさん出てきて見づらいです。このような時はカラーオプション等をつければ、色がついて一目で確認できるようになります。

一か所out~というところもありますが、write_out_header関数で使用していることを考えると、cpio_file_statが目的の構造体のようですので、cpio_file_statをcpiohdr.hから抽出しましょう。
20Byteもあれば足りるでしょう。grepに-A20を指定します。
takk@deb9:~/src/cpio-2.11+dfsg/src$ grep -A20 cpio_file_stat cpiohdr.h
struct cpio_file_stat /* Internal representation of a CPIO header */
{
unsigned short c_magic;
ino_t c_ino;
mode_t c_mode;
uid_t c_uid;
gid_t c_gid;
size_t c_nlink;
time_t c_mtime;
off_t c_filesize;
long c_dev_maj;
long c_dev_min;
long c_rdev_maj;
long c_rdev_min;
size_t c_namesize;
unsigned long c_chksum;
char *c_name;
char *c_tar_linkname;
};
takk@deb9:~/src/cpio-2.11+dfsg/src$
前回作成したa.binをアーカイブ化したファイルa.bin.cpioのダンプをもう一度見てみましょう。
takk@deb9:~/tmp$ hd !$ hd a.bin.cpio 00000000 c7 71 01 08 56 58 a4 81 e8 03 e8 03 01 00 00 00 |.q..VX..........| 00000010 f0 5a 44 3a 06 00 00 00 03 00 61 2e 62 69 6e 00 |.ZD:......a.bin.| 00000020 01 03 03 00 c7 71 00 00 00 00 00 00 00 00 00 00 |.....q..........| 00000030 01 00 00 00 00 00 00 00 0b 00 00 00 00 00 54 52 |..............TR| 00000040 41 49 4c 45 52 21 21 21 00 00 00 00 00 00 00 00 |AILER!!!........| 00000050 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 |................| * 00000200 takk@deb9:~/tmp$
ファイル名であるa.binの文字列を追っていくと該当メンバが探しやすいです。
char *c_nameを中心に3つに分離してみます。
c_magicからchar *c_nameの前まで
00000000 c7 71 01 08 56 58 a4 81 e8 03 e8 03 01 00 00 00 |.q..VX..........| 00000010 f0 5a 44 3a 06 00 00 00 03 00
char *c_name
61 2e 62 69 6e 00 |a.bin.|
char *c_tar_linkname
00000020 01 03 03 00 c7 71 00 00 00 00 00 00 00 00 00 00 |.....q..........| 00000030 01 00 00 00 00 00 00 00 0b 00 00 00 00 00 54 52 |..............TR| 00000040 41 49 4c 45 52 21 21 21 00 00 00 00 00 00 00 00 |AILER!!!........| 00000050 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 |................| * 00000200 takk@deb9:~/tmp$
ものすごく単純な構成であることが分かりました。
別のファイルでも試してみます。b.binを作成しアーカイブ化。
takk@deb9:~/tmp$ echo -ne "\x11\x22\x33" > b.bin takk@deb9:~/tmp$ echo b.bin | cpio -o > b.bin.cpio 1 block takk@deb9:~/tmp$ hd b.bin.cpio 00000000 c7 71 01 08 82 58 a4 81 e8 03 e8 03 01 00 00 00 |.q...X..........| 00000010 f6 5a f4 b9 06 00 00 00 03 00 62 2e 62 69 6e 00 |.Z........b.bin.| 00000020 11 22 33 00 c7 71 00 00 00 00 00 00 00 00 00 00 |."3..q..........| 00000030 01 00 00 00 00 00 00 00 0b 00 00 00 00 00 54 52 |..............TR| 00000040 41 49 4c 45 52 21 21 21 00 00 00 00 00 00 00 00 |AILER!!!........| 00000050 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 |................| * 00000200 takk@deb9:~/tmp$
今回、1ファイルをアーカイブ化した場合のバイナリしか見ていませんが、
ポイントとして、cpiohdr.hの struct cpio_file_statを押さえておけばよいことが分かりました。
最後に今回確認したcpiohdr.hの全文を載せておきます。
takk@deb9:~/src/cpio-2.11+dfsg/src$ cat -n cpiohdr.h
1 /* Extended cpio header from POSIX.1.
2 Copyright (C) 1992, 2006, 2007, 2010 Free Software Foundation, Inc.
3
4 This program is free software; you can redistribute it and/or modify
5 it under the terms of the GNU General Public License as published by
6 the Free Software Foundation; either version 3, or (at your option)
7 any later version.
8
9 This program is distributed in the hope that it will be useful,
10 but WITHOUT ANY WARRANTY; without even the implied warranty of
11 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12 GNU General Public License for more details.
13
14 You should have received a copy of the GNU General Public
15 License along with this program; if not, write to the Free
16 Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
17 Boston, MA 02110-1301 USA. */
18
19 #ifndef _CPIOHDR_H
20
21 #define _CPIOHDR_H 1
22
23 #include <cpio.h>
24
25 #ifdef HAVE_ATTRIB_PACKED
26 #define ATTRIB_PACKED __attribute__((packed))
27 #endif
28
29 #ifdef HAVE_PRAGMA_PACK
30 #pragma pack(1)
31 #endif
32
33 #ifdef HAVE_PRAGMA_PACK_HPPA
34 #pragma pack 1
35 #endif
36
37 struct old_cpio_header
38 {
39 unsigned short c_magic;
40 unsigned short c_dev;
41 unsigned short c_ino;
42 unsigned short c_mode;
43 unsigned short c_uid;
44 unsigned short c_gid;
45 unsigned short c_nlink;
46 unsigned short c_rdev;
47 unsigned short c_mtimes[2];
48 unsigned short c_namesize;
49 unsigned short c_filesizes[2];
50 } ATTRIB_PACKED;
51
52 #ifdef HAVE_PRAGMA_PACK
53 #pragma pack(1)
54 #endif
55
56 #ifdef HAVE_PRAGMA_PACK_HPPA
57 #pragma pack 1
58 #endif
59 struct old_ascii_header
60 {
61 char c_magic[6];
62 char c_dev[6];
63 char c_ino[6];
64 char c_mode[6];
65 char c_uid[6];
66 char c_gid[6];
67 char c_nlink[6];
68 char c_rdev[6];
69 char c_mtime[11];
70 char c_namesize[6];
71 char c_filesize[11];
72 } ATTRIB_PACKED;
73
74 /* "New" portable format and CRC format:
75
76 Each file has a 110 byte header,
77 a variable length, NUL terminated filename,
78 and variable length file data.
79 A header for a filename "TRAILER!!!" indicates the end of the archive. */
80
81 /* All the fields in the header are ISO 646 (approximately ASCII) strings
82 of hexadecimal numbers, left padded, not NUL terminated: */
83
84 #ifdef HAVE_PRAGMA_PACK
85 #pragma pack(1)
86 #endif
87
88 #ifdef HAVE_PRAGMA_PACK_HPPA
89 #pragma pack 1
90 #endif
91 struct new_ascii_header
92 {
93 char c_magic[6]; /* "070701" for "new" portable format
94 "070702" for CRC format */
95 char c_ino[8];
96 char c_mode[8];
97 char c_uid[8];
98 char c_gid[8];
99 char c_nlink[8];
100 char c_mtime[8];
101 char c_filesize[8]; /* must be 0 for FIFOs and directories */
102 char c_dev_maj[8];
103 char c_dev_min[8];
104 char c_rdev_maj[8]; /* only valid for chr and blk special files */
105 char c_rdev_min[8]; /* only valid for chr and blk special files */
106 char c_namesize[8]; /* count includes terminating NUL in pathname */
107 char c_chksum[8]; /* 0 for "new" portable format; for CRC format
108 the sum of all the bytes in the file */
109 } ATTRIB_PACKED;
110
111 struct cpio_file_stat /* Internal representation of a CPIO header */
112 {
113 unsigned short c_magic;
114 ino_t c_ino;
115 mode_t c_mode;
116 uid_t c_uid;
117 gid_t c_gid;
118 size_t c_nlink;
119 time_t c_mtime;
120 off_t c_filesize;
121 long c_dev_maj;
122 long c_dev_min;
123 long c_rdev_maj;
124 long c_rdev_min;
125 size_t c_namesize;
126 unsigned long c_chksum;
127 char *c_name;
128 char *c_tar_linkname;
129 };
130
131
132 #endif /* cpiohdr.h */
takk@deb9:~/src/cpio-2.11+dfsg/src$



コメント