1.\" Copyright (c) 2003-2011 Tim Kientzle
2.\" All rights reserved.
3.\"
4.\" Redistribution and use in source and binary forms, with or without
5.\" modification, are permitted provided that the following conditions
6.\" are met:
7.\" 1. Redistributions of source code must retain the above copyright
8.\"    notice, this list of conditions and the following disclaimer.
9.\" 2. Redistributions in binary form must reproduce the above copyright
10.\"    notice, this list of conditions and the following disclaimer in the
11.\"    documentation and/or other materials provided with the distribution.
12.\"
13.\" THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
14.\" ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
15.\" IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
16.\" ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
17.\" FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
18.\" DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
19.\" OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
20.\" HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
21.\" LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
22.\" OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
23.\" SUCH DAMAGE.
24.\"
25.\" $FreeBSD$
26.\"
27.Dd February 2, 2012
28.Dt ARCHIVE_WRITE 3
29.Os
30.Sh NAME
31.Nm archive_write
32.Nd functions for creating archives
33.Sh LIBRARY
34Streaming Archive Library (libarchive, -larchive)
35.Sh SYNOPSIS
36.In archive.h
37.Sh DESCRIPTION
38These functions provide a complete API for creating streaming
39archive files.
40The general process is to first create the
41.Tn struct archive
42object, set any desired options, initialize the archive, append entries, then
43close the archive and release all resources.
44.\"
45.Ss Create archive object
46See
47.Xr archive_write_new 3 .
48.Pp
49To write an archive, you must first obtain an initialized
50.Tn struct archive
51object from
52.Fn archive_write_new .
53.\"
54.Ss Enable filters and formats, configure block size and padding
55See
56.Xr archive_write_filter 3 ,
57.Xr archive_write_format 3
58and
59.Xr archive_write_blocksize 3 .
60.Pp
61You can then modify this object for the desired operations with the
62various
63.Fn archive_write_set_XXX
64functions.
65In particular, you will need to invoke appropriate
66.Fn archive_write_add_XXX
67and
68.Fn archive_write_set_XXX
69functions to enable the corresponding compression and format
70support.
71.\"
72.Ss Set options
73See
74.Xr archive_read_set_options 3 .
75.\"
76.Ss Open archive
77See
78.Xr archive_write_open 3 .
79.Pp
80Once you have prepared the
81.Tn struct archive
82object, you call
83.Fn archive_write_open
84to actually open the archive and prepare it for writing.
85There are several variants of this function;
86the most basic expects you to provide pointers to several
87functions that can provide blocks of bytes from the archive.
88There are convenience forms that allow you to
89specify a filename, file descriptor,
90.Ft "FILE *"
91object, or a block of memory from which to write the archive data.
92.\"
93.Ss Produce archive
94See
95.Xr archive_write_header 3
96and
97.Xr archive_write_data 3 .
98.Pp
99Individual archive entries are written in a three-step
100process:
101You first initialize a
102.Tn struct archive_entry
103structure with information about the new entry.
104At a minimum, you should set the pathname of the
105entry and provide a
106.Va struct stat
107with a valid
108.Va st_mode
109field, which specifies the type of object and
110.Va st_size
111field, which specifies the size of the data portion of the object.
112.\"
113.Ss Release resources
114See
115.Xr archive_write_free 3 .
116.Pp
117After all entries have been written, use the
118.Fn archive_write_free
119function to release all resources.
120.\"
121.Sh EXAMPLE
122The following sketch illustrates basic usage of the library.
123In this example,
124the callback functions are simply wrappers around the standard
125.Xr open 2 ,
126.Xr write 2 ,
127and
128.Xr close 2
129system calls.
130.Bd -literal -offset indent
131#ifdef __linux__
132#define	_FILE_OFFSET_BITS 64
133#endif
134#include <sys/stat.h>
135#include <archive.h>
136#include <archive_entry.h>
137#include <fcntl.h>
138#include <stdlib.h>
139#include <unistd.h>
140
141struct mydata {
142  const char *name;
143  int fd;
144};
145
146int
147myopen(struct archive *a, void *client_data)
148{
149  struct mydata *mydata = client_data;
150
151  mydata->fd = open(mydata->name, O_WRONLY | O_CREAT, 0644);
152  if (mydata->fd >= 0)
153    return (ARCHIVE_OK);
154  else
155    return (ARCHIVE_FATAL);
156}
157
158ssize_t
159mywrite(struct archive *a, void *client_data, const void *buff, size_t n)
160{
161  struct mydata *mydata = client_data;
162
163  return (write(mydata->fd, buff, n));
164}
165
166int
167myclose(struct archive *a, void *client_data)
168{
169  struct mydata *mydata = client_data;
170
171  if (mydata->fd > 0)
172    close(mydata->fd);
173  return (0);
174}
175
176void
177write_archive(const char *outname, const char **filename)
178{
179  struct mydata *mydata = malloc(sizeof(struct mydata));
180  struct archive *a;
181  struct archive_entry *entry;
182  struct stat st;
183  char buff[8192];
184  int len;
185  int fd;
186
187  a = archive_write_new();
188  mydata->name = outname;
189  archive_write_add_filter_gzip(a);
190  archive_write_set_format_ustar(a);
191  archive_write_open(a, mydata, myopen, mywrite, myclose);
192  while (*filename) {
193    stat(*filename, &st);
194    entry = archive_entry_new();
195    archive_entry_copy_stat(entry, &st);
196    archive_entry_set_pathname(entry, *filename);
197    archive_write_header(a, entry);
198    if ((fd = open(*filename, O_RDONLY)) != -1) {
199      len = read(fd, buff, sizeof(buff));
200      while ( len > 0 ) {
201        archive_write_data(a, buff, len);
202        len = read(fd, buff, sizeof(buff));
203      }
204      close(fd);
205    }
206    archive_entry_free(entry);
207    filename++;
208  }
209  archive_write_free(a);
210}
211
212int main(int argc, const char **argv)
213{
214  const char *outname;
215  argv++;
216  outname = argv++;
217  write_archive(outname, argv);
218  return 0;
219}
220.Ed
221.Sh SEE ALSO
222.Xr tar 1 ,
223.Xr libarchive 3 ,
224.Xr archive_write_set_options 3 ,
225.Xr cpio 5 ,
226.Xr mtree 5 ,
227.Xr tar 5
228.Sh HISTORY
229The
230.Nm libarchive
231library first appeared in
232.Fx 5.3 .
233.Sh AUTHORS
234.An -nosplit
235The
236.Nm libarchive
237library was written by
238.An Tim Kientzle Aq kientzle@acm.org .
239.Sh BUGS
240There are many peculiar bugs in historic tar implementations that may cause
241certain programs to reject archives written by this library.
242For example, several historic implementations calculated header checksums
243incorrectly and will thus reject valid archives; GNU tar does not fully support
244pax interchange format; some old tar implementations required specific
245field terminations.
246.Pp
247The default pax interchange format eliminates most of the historic
248tar limitations and provides a generic key/value attribute facility
249for vendor-defined extensions.
250One oversight in POSIX is the failure to provide a standard attribute
251for large device numbers.
252This library uses
253.Dq SCHILY.devminor
254and
255.Dq SCHILY.devmajor
256for device numbers that exceed the range supported by the backwards-compatible
257ustar header.
258These keys are compatible with Joerg Schilling's
259.Nm star
260archiver.
261Other implementations may not recognize these keys and will thus be unable
262to correctly restore device nodes with large device numbers from archives
263created by this library.
264