iPXE
cpio.c
Go to the documentation of this file.
1/*
2 * Copyright (C) 2007 Michael Brown <mbrown@fensystems.co.uk>.
3 *
4 * This program is free software; you can redistribute it and/or
5 * modify it under the terms of the GNU General Public License as
6 * published by the Free Software Foundation; either version 2 of the
7 * License, or any later version.
8 *
9 * This program is distributed in the hope that it will be useful, but
10 * WITHOUT ANY WARRANTY; without even the implied warranty of
11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
12 * General Public License for more details.
13 *
14 * You should have received a copy of the GNU General Public License
15 * along with this program; if not, write to the Free Software
16 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
17 * 02110-1301, USA.
18 *
19 * You can also choose to distribute this program under the terms of
20 * the Unmodified Binary Distribution Licence (as given in the file
21 * COPYING.UBDL), provided that you have satisfied its requirements.
22 */
23
24FILE_LICENCE ( GPL2_OR_LATER_OR_UBDL );
25FILE_SECBOOT ( PERMITTED );
26
27/** @file
28 *
29 * CPIO archives
30 *
31 */
32
33#include <stdio.h>
34#include <stdlib.h>
35#include <string.h>
36#include <ipxe/cpio.h>
37
38/** CPIO default file mode */
39#define CPIO_DEFAULT_MODE 0644
40
41/** CPIO directory mode */
42#define CPIO_DEFAULT_DIR_MODE 0755
43
44/**
45 * Set field within a CPIO header
46 *
47 * @v field Field within CPIO header
48 * @v value Value to set
49 */
50static void cpio_set_field ( char *field, unsigned long value ) {
51 char buf[9];
52
53 snprintf ( buf, sizeof ( buf ), "%08lx", value );
54 memcpy ( field, buf, 8 );
55}
56
57/**
58 * Get maximum number of CPIO headers (i.e. number of path components)
59 *
60 * @v image Image
61 * @ret max Maximum number of CPIO headers
62 */
63static unsigned int cpio_max ( struct image *image ) {
64 const char *name = cpio_name ( image );
65 unsigned int max = 0;
66 char c;
67 char p;
68
69 /* Check for existence of CPIO filename */
70 if ( ! name )
71 return 0;
72
73 /* Count number of path components */
74 for ( p = '/' ; ( ( ( c = *(name++) ) ) && ( c != ' ' ) ) ; p = c ) {
75 if ( ( p == '/' ) && ( c != '/' ) )
76 max++;
77 }
78
79 return max;
80}
81
82/**
83 * Get CPIO image filename
84 *
85 * @v image Image
86 * @v depth Path depth
87 * @ret len Filename length
88 */
89static size_t cpio_name_len ( struct image *image, unsigned int depth ) {
90 const char *name = cpio_name ( image );
91 size_t len;
92 char c;
93 char p;
94
95 /* Sanity checks */
96 assert ( name != NULL );
97 assert ( depth > 0 );
98
99 /* Calculate length up to specified path depth */
100 for ( len = 0, p = '/' ; ( ( ( c = name[len] ) ) && ( c != ' ' ) ) ;
101 len++, p = c ) {
102 if ( ( c == '/' ) && ( p != '/' ) && ( --depth == 0 ) )
103 break;
104 }
105
106 return len;
107}
108
109/**
110 * Parse CPIO image parameters
111 *
112 * @v image Image
113 * @v mode Mode to fill in
114 * @v count Number of CPIO headers to fill in
115 */
116static void cpio_parse_cmdline ( struct image *image, unsigned int *mode,
117 unsigned int *count ) {
118 const char *arg;
119 char *end;
120
121 /* Set default values */
123 *count = 1;
124
125 /* Parse "mode=...", if present */
126 if ( ( arg = image_argument ( image, "mode=" ) ) ) {
127 *mode = strtoul ( arg, &end, 8 /* Octal for file mode */ );
128 if ( *end && ( *end != ' ' ) ) {
129 DBGC ( image, "CPIO %s strange \"mode=\" "
130 "terminator '%c'\n", image->name, *end );
131 }
132 }
133
134 /* Parse "mkdir=...", if present */
135 if ( ( arg = image_argument ( image, "mkdir=" ) ) ) {
136 *count += strtoul ( arg, &end, 10 );
137 if ( *end && ( *end != ' ' ) ) {
138 DBGC ( image, "CPIO %s strange \"mkdir=\" "
139 "terminator '%c'\n", image->name, *end );
140 }
141 }
142
143 /* Allow "mkdir=-1" to request creation of full directory tree */
144 if ( ! *count )
145 *count = -1U;
146}
147
148/**
149 * Construct CPIO header for image, if applicable
150 *
151 * @v image Image
152 * @v index CPIO header index
153 * @v cpio CPIO header to fill in
154 * @ret len Length of CPIO header (including name, excluding NUL)
155 */
156size_t cpio_header ( struct image *image, unsigned int index,
157 struct cpio_header *cpio ) {
158 const char *name = cpio_name ( image );
159 unsigned int mode;
160 unsigned int count;
161 unsigned int max;
162 unsigned int depth;
163 unsigned int i;
164 size_t name_len;
165 size_t len;
166
167 /* Parse command line arguments */
169
170 /* Determine number of CPIO headers to be constructed */
171 max = cpio_max ( image );
172 if ( count > max )
173 count = max;
174
175 /* Determine path depth of this CPIO header */
176 if ( index >= count )
177 return 0;
178 depth = ( max - count + index + 1 );
179
180 /* Get filename length */
181 name_len = cpio_name_len ( image, depth );
182
183 /* Set directory mode or file mode as appropriate */
184 if ( name[name_len] == '/' ) {
186 } else {
188 }
189
190 /* Set length on final header */
191 len = ( ( depth < max ) ? 0 : image->len );
192
193 /* Construct CPIO header */
194 memset ( cpio, '0', sizeof ( *cpio ) );
195 memcpy ( cpio->c_magic, CPIO_MAGIC, sizeof ( cpio->c_magic ) );
196 cpio_set_field ( cpio->c_mode, mode );
197 cpio_set_field ( cpio->c_nlink, 1 );
198 cpio_set_field ( cpio->c_filesize, len );
199 cpio_set_field ( cpio->c_namesize, ( name_len + 1 /* NUL */ ) );
200 DBGC ( image, "CPIO %s %d/%d \"", image->name, depth, max );
201 for ( i = 0 ; i < name_len ; i++ )
202 DBGC ( image, "%c", name[i] );
203 DBGC ( image, "\"\n" );
204 DBGC2_HDA ( image, 0, cpio, sizeof ( *cpio ) );
205
206 /* Calculate total length */
207 return ( sizeof ( *cpio ) + name_len );
208}
#define NULL
NULL pointer (VOID *)
Definition Base.h:322
pseudo_bit_t value[0x00020]
Definition arbel.h:2
long index
Definition bigint.h:65
#define assert(condition)
Assert a condition at run-time.
Definition assert.h:50
const char * name
Definition ath9k_hw.c:1986
#define max(x, y)
Definition ath.h:41
static void cpio_parse_cmdline(struct image *image, unsigned int *mode, unsigned int *count)
Parse CPIO image parameters.
Definition cpio.c:116
static size_t cpio_name_len(struct image *image, unsigned int depth)
Get CPIO image filename.
Definition cpio.c:89
#define CPIO_DEFAULT_MODE
CPIO default file mode.
Definition cpio.c:39
size_t cpio_header(struct image *image, unsigned int index, struct cpio_header *cpio)
Construct CPIO header for image, if applicable.
Definition cpio.c:156
static void cpio_set_field(char *field, unsigned long value)
Set field within a CPIO header.
Definition cpio.c:50
static unsigned int cpio_max(struct image *image)
Get maximum number of CPIO headers (i.e.
Definition cpio.c:63
#define CPIO_DEFAULT_DIR_MODE
CPIO directory mode.
Definition cpio.c:42
CPIO archives.
#define CPIO_MODE_DIR
CPIO type for directories.
Definition cpio.h:59
#define CPIO_MAGIC
CPIO magic.
Definition cpio.h:53
#define CPIO_MODE_FILE
CPIO type for regular files.
Definition cpio.h:56
static const char * cpio_name(struct image *image)
Get CPIO image name.
Definition cpio.h:71
ring len
Length.
Definition dwmac.h:226
uint16_t mode
Acceleration mode.
Definition ena.h:15
#define DBGC2_HDA(...)
Definition compiler.h:523
#define DBGC(...)
Definition compiler.h:505
static unsigned int count
Number of entries.
Definition dwmac.h:220
#define FILE_LICENCE(_licence)
Declare a particular licence as applying to a file.
Definition compiler.h:896
#define FILE_SECBOOT(_status)
Declare a file's UEFI Secure Boot permission status.
Definition compiler.h:926
const char * image_argument(struct image *image, const char *key)
Find argument within image command line.
Definition image.c:653
String functions.
void * memcpy(void *dest, const void *src, size_t len) __nonnull
void * memset(void *dest, int character, size_t len) __nonnull
uint32_t end
Ending offset.
Definition netvsc.h:7
unsigned long strtoul(const char *string, char **endp, int base)
Convert string to numeric value.
Definition string.c:485
A CPIO archive header.
Definition cpio.h:21
char c_filesize[8]
Size of data field.
Definition cpio.h:37
char c_mode[8]
File mode and permissions.
Definition cpio.h:27
char c_nlink[8]
Number of links.
Definition cpio.h:33
char c_namesize[8]
Length of filename, including final NUL.
Definition cpio.h:47
char c_magic[6]
The string "070701" or "070702".
Definition cpio.h:23
An executable image.
Definition image.h:24
char * name
Name.
Definition image.h:38
size_t len
Length of raw file image.
Definition image.h:56
int snprintf(char *buf, size_t size, const char *fmt,...)
Write a formatted string to a buffer.
Definition vsprintf.c:383