PERFORCE change 54131 for review
Marcel Moolenaar
marcel at FreeBSD.org
Fri Jun 4 04:16:12 GMT 2004
http://perforce.freebsd.org/chv.cgi?CH=54131
Change 54131 by marcel at marcel_nfs on 2004/06/03 21:15:36
IFC @54128
Affected files ...
.. //depot/projects/gdb/bin/ls/ls.c#3 integrate
.. //depot/projects/gdb/etc/defaults/rc.conf#10 integrate
.. //depot/projects/gdb/etc/rc.d/ip6addrctl#3 integrate
.. //depot/projects/gdb/gnu/usr.bin/tar/Makefile#4 integrate
.. //depot/projects/gdb/lib/libarchive/Makefile#9 integrate
.. //depot/projects/gdb/lib/libarchive/archive.h#10 integrate
.. //depot/projects/gdb/lib/libarchive/archive_private.h#11 integrate
.. //depot/projects/gdb/lib/libarchive/archive_read.3#6 integrate
.. //depot/projects/gdb/lib/libarchive/archive_read.c#7 integrate
.. //depot/projects/gdb/lib/libarchive/archive_read_data_into_fd.c#6 integrate
.. //depot/projects/gdb/lib/libarchive/archive_read_extract.c#12 integrate
.. //depot/projects/gdb/lib/libarchive/archive_read_support_format_cpio.c#9 integrate
.. //depot/projects/gdb/lib/libarchive/archive_read_support_format_tar.c#12 integrate
.. //depot/projects/gdb/lib/libarchive/archive_write.c#7 integrate
.. //depot/projects/gdb/lib/libc/gen/dlopen.3#2 integrate
.. //depot/projects/gdb/lib/libc/net/name6.c#6 integrate
.. //depot/projects/gdb/lib/libusbhid/usbhid.h#3 integrate
.. //depot/projects/gdb/lib/msun/src/e_atan2f.c#2 integrate
.. //depot/projects/gdb/lib/msun/src/k_tan.c#2 integrate
.. //depot/projects/gdb/lib/msun/src/k_tanf.c#2 integrate
.. //depot/projects/gdb/release/alpha/mkisoimages.sh#2 integrate
.. //depot/projects/gdb/release/amd64/mkisoimages.sh#2 integrate
.. //depot/projects/gdb/release/i386/mkisoimages.sh#2 integrate
.. //depot/projects/gdb/release/ia64/mkisoimages.sh#2 integrate
.. //depot/projects/gdb/release/sparc64/mkisoimages.sh#2 integrate
.. //depot/projects/gdb/sbin/devfs/extern.h#2 integrate
.. //depot/projects/gdb/sbin/ggate/ggated/ggated.c#4 integrate
.. //depot/projects/gdb/sbin/ipfw/ipfw2.c#7 integrate
.. //depot/projects/gdb/sbin/sunlabel/sunlabel.8#4 integrate
.. //depot/projects/gdb/share/man/man7/ports.7#2 integrate
.. //depot/projects/gdb/sys/alpha/alpha/mem.c#4 integrate
.. //depot/projects/gdb/sys/alpha/alpha/uio_machdep.c#3 integrate
.. //depot/projects/gdb/sys/amd64/acpica/madt.c#4 integrate
.. //depot/projects/gdb/sys/amd64/amd64/identcpu.c#5 integrate
.. //depot/projects/gdb/sys/amd64/amd64/io_apic.c#3 integrate
.. //depot/projects/gdb/sys/amd64/amd64/legacy.c#3 integrate
.. //depot/projects/gdb/sys/amd64/amd64/mem.c#4 integrate
.. //depot/projects/gdb/sys/amd64/amd64/mptable.c#3 integrate
.. //depot/projects/gdb/sys/amd64/amd64/nexus.c#3 integrate
.. //depot/projects/gdb/sys/amd64/amd64/trap.c#9 integrate
.. //depot/projects/gdb/sys/amd64/amd64/uio_machdep.c#3 integrate
.. //depot/projects/gdb/sys/amd64/conf/GENERIC#7 integrate
.. //depot/projects/gdb/sys/amd64/include/cputypes.h#2 integrate
.. //depot/projects/gdb/sys/amd64/isa/atpic.c#5 integrate
.. //depot/projects/gdb/sys/amd64/isa/clock.c#5 integrate
.. //depot/projects/gdb/sys/amd64/pci/pci_bus.c#4 integrate
.. //depot/projects/gdb/sys/arm/arm/uio_machdep.c#2 integrate
.. //depot/projects/gdb/sys/boot/i386/boot2/boot1.S#4 integrate
.. //depot/projects/gdb/sys/dev/aac/aac.c#6 integrate
.. //depot/projects/gdb/sys/dev/aac/aac_cam.c#3 integrate
.. //depot/projects/gdb/sys/dev/aac/aac_disk.c#4 integrate
.. //depot/projects/gdb/sys/dev/aac/aacvar.h#4 integrate
.. //depot/projects/gdb/sys/dev/adlink/adlink.c#4 integrate
.. //depot/projects/gdb/sys/dev/arl/if_arl.c#5 integrate
.. //depot/projects/gdb/sys/dev/ata/ata-cbus.c#4 integrate
.. //depot/projects/gdb/sys/dev/fb/tga.c#2 integrate
.. //depot/projects/gdb/sys/dev/fxp/if_fxp.c#8 integrate
.. //depot/projects/gdb/sys/dev/fxp/if_fxpvar.h#3 integrate
.. //depot/projects/gdb/sys/dev/gem/if_gem.c#5 integrate
.. //depot/projects/gdb/sys/dev/gem/if_gem_pci.c#4 integrate
.. //depot/projects/gdb/sys/dev/hme/if_hme.c#7 integrate
.. //depot/projects/gdb/sys/dev/hme/if_hme_pci.c#3 integrate
.. //depot/projects/gdb/sys/dev/hme/if_hme_sbus.c#4 integrate
.. //depot/projects/gdb/sys/dev/isp/isp_sbus.c#4 integrate
.. //depot/projects/gdb/sys/dev/ixgb/if_ixgb.h#2 integrate
.. //depot/projects/gdb/sys/dev/lnc/if_lnc_cbus.c#3 integrate
.. //depot/projects/gdb/sys/dev/puc/puc_ebus.c#2 integrate
.. //depot/projects/gdb/sys/dev/puc/puc_sbus.c#3 integrate
.. //depot/projects/gdb/sys/dev/sab/sab.c#6 integrate
.. //depot/projects/gdb/sys/dev/tga/tga_pci.c#3 integrate
.. //depot/projects/gdb/sys/dev/uart/uart_bus_ebus.c#3 integrate
.. //depot/projects/gdb/sys/dev/zs/zs_sbus.c#3 integrate
.. //depot/projects/gdb/sys/i386/i386/bios.c#3 integrate
.. //depot/projects/gdb/sys/i386/i386/geode.c#3 integrate
.. //depot/projects/gdb/sys/i386/i386/identcpu.c#7 integrate
.. //depot/projects/gdb/sys/i386/i386/trap.c#11 integrate
.. //depot/projects/gdb/sys/i386/i386/uio_machdep.c#4 integrate
.. //depot/projects/gdb/sys/i386/i386/vm_machdep.c#12 integrate
.. //depot/projects/gdb/sys/i386/include/cputypes.h#3 integrate
.. //depot/projects/gdb/sys/i386/include/pc/bios.h#2 integrate
.. //depot/projects/gdb/sys/ia64/ia64/mem.c#4 integrate
.. //depot/projects/gdb/sys/ia64/ia64/uio_machdep.c#3 integrate
.. //depot/projects/gdb/sys/kern/kern_clock.c#8 integrate
.. //depot/projects/gdb/sys/kern/kern_exec.c#9 integrate
.. //depot/projects/gdb/sys/kern/kern_exit.c#9 integrate
.. //depot/projects/gdb/sys/kern/kern_lock.c#2 integrate
.. //depot/projects/gdb/sys/kern/kern_sig.c#8 integrate
.. //depot/projects/gdb/sys/kern/kern_subr.c#4 integrate
.. //depot/projects/gdb/sys/kern/kern_thread.c#11 integrate
.. //depot/projects/gdb/sys/kern/sched_ule.c#11 integrate
.. //depot/projects/gdb/sys/kern/subr_blist.c#2 integrate
.. //depot/projects/gdb/sys/kern/subr_bus.c#7 integrate
.. //depot/projects/gdb/sys/kern/subr_witness.c#9 integrate
.. //depot/projects/gdb/sys/net/ethernet.h#2 integrate
.. //depot/projects/gdb/sys/net/if_ethersubr.c#12 integrate
.. //depot/projects/gdb/sys/netinet/raw_ip.c#7 integrate
.. //depot/projects/gdb/sys/netinet6/ip6_input.c#5 integrate
.. //depot/projects/gdb/sys/pc98/pc98/pmc.c#2 integrate
.. //depot/projects/gdb/sys/powerpc/powerpc/uio_machdep.c#3 integrate
.. //depot/projects/gdb/sys/sparc64/central/central.c#2 integrate
.. //depot/projects/gdb/sys/sparc64/ebus/ebus.c#6 integrate
.. //depot/projects/gdb/sys/sparc64/fhc/fhc_central.c#2 integrate
.. //depot/projects/gdb/sys/sparc64/fhc/fhc_nexus.c#2 integrate
.. //depot/projects/gdb/sys/sparc64/pci/apb.c#3 integrate
.. //depot/projects/gdb/sys/sparc64/sparc64/mem.c#4 integrate
.. //depot/projects/gdb/sys/sparc64/sparc64/uio_machdep.c#4 integrate
.. //depot/projects/gdb/sys/sys/blist.h#2 integrate
.. //depot/projects/gdb/sys/sys/proc.h#14 integrate
.. //depot/projects/gdb/sys/ufs/ffs/ffs_rawread.c#2 integrate
.. //depot/projects/gdb/sys/vm/vm_page.h#6 integrate
.. //depot/projects/gdb/usr.bin/calendar/calendars/calendar.freebsd#8 integrate
.. //depot/projects/gdb/usr.bin/du/du.1#2 integrate
.. //depot/projects/gdb/usr.bin/du/du.c#5 integrate
.. //depot/projects/gdb/usr.bin/netstat/inet.c#5 integrate
.. //depot/projects/gdb/usr.bin/sed/main.c#2 integrate
.. //depot/projects/gdb/usr.bin/tar/Makefile#5 integrate
.. //depot/projects/gdb/usr.bin/tar/bsdtar.c#15 integrate
.. //depot/projects/gdb/usr.bin/tar/matching.c#4 integrate
.. //depot/projects/gdb/usr.bin/tar/util.c#5 integrate
.. //depot/projects/gdb/usr.sbin/daemon/daemon.8#2 integrate
.. //depot/projects/gdb/usr.sbin/daemon/daemon.c#2 integrate
.. //depot/projects/gdb/usr.sbin/newsyslog/newsyslog.c#4 integrate
.. //depot/projects/gdb/usr.sbin/newsyslog/newsyslog.conf.5#2 integrate
Differences ...
==== //depot/projects/gdb/bin/ls/ls.c#3 (text+ko) ====
@@ -42,7 +42,7 @@
#endif /* not lint */
#endif
#include <sys/cdefs.h>
-__FBSDID("$FreeBSD: src/bin/ls/ls.c,v 1.76 2004/04/06 20:06:47 markm Exp $");
+__FBSDID("$FreeBSD: src/bin/ls/ls.c,v 1.77 2004/06/03 15:04:00 le Exp $");
#include <sys/types.h>
#include <sys/stat.h>
@@ -621,6 +621,7 @@
MAKENINES(maxblock);
MAKENINES(maxnlink);
MAKENINES(maxsize);
+ free(jinitmax);
}
bcfile = 0;
flags = NULL;
==== //depot/projects/gdb/etc/defaults/rc.conf#10 (text+ko) ====
@@ -13,7 +13,7 @@
#
# All arguments must be in double or single quotes.
#
-# $FreeBSD: src/etc/defaults/rc.conf,v 1.206 2004/05/29 04:52:37 njl Exp $
+# $FreeBSD: src/etc/defaults/rc.conf,v 1.208 2004/06/02 09:58:18 ume Exp $
##############################################################
### Important initial Boot-time options ####################
@@ -340,6 +340,8 @@
ipv6_ipfilter_rules="/etc/ipf6.rules" # rules definition file for ipfilter,
# see /usr/src/contrib/ipfilter/rules
# for examples
+ip6addrctl_enable="NO" # Set to YES to enable default address selection
+ip6addrctl_verbose="NO" # Set to YES to enable verbose configuration messages
##############################################################
### System console options #################################
==== //depot/projects/gdb/etc/rc.d/ip6addrctl#3 (text+ko) ====
@@ -1,6 +1,6 @@
#!/bin/sh
#
-# $FreeBSD: src/etc/rc.d/ip6addrctl,v 1.2 2004/03/08 12:25:05 pjd Exp $
+# $FreeBSD: src/etc/rc.d/ip6addrctl,v 1.3 2004/06/02 09:39:49 ume Exp $
#
# PROVIDE: ip6addrctl
@@ -9,11 +9,37 @@
# KEYWORD: FreeBSD nojail
. /etc/rc.subr
-. /etc/network.subr
name="ip6addrctl"
+rcvar=`set_rcvar`
start_cmd="ip6addrctl_start"
-stop_cmd=':'
+stop_cmd="ip6addrctl_stop"
+extra_commands="status prefer_ipv6 prefer_ipv4"
+status_cmd="ip6addrctl"
+prefer_ipv6_cmd="ip6addrctl_prefer_ipv6"
+prefer_ipv4_cmd="ip6addrctl_prefer_ipv4"
+
+ip6addrctl_prefer_ipv6()
+{
+ ip6addrctl flush >/dev/null 2>&1
+ ip6addrctl add ::1/128 50 0
+ ip6addrctl add ::/0 40 1
+ ip6addrctl add 2002::/16 30 2
+ ip6addrctl add ::/96 20 3
+ ip6addrctl add ::ffff:0:0/96 10 4
+ checkyesno ip6addrctl_verbose && ip6addrctl
+}
+
+ip6addrctl_prefer_ipv4()
+{
+ ip6addrctl flush >/dev/null 2>&1
+ ip6addrctl add ::ffff:0:0/96 50 0
+ ip6addrctl add ::1/128 40 1
+ ip6addrctl add ::/0 30 2
+ ip6addrctl add 2002::/16 20 3
+ ip6addrctl add ::/96 10 4
+ checkyesno ip6addrctl_verbose && ip6addrctl
+}
ip6addrctl_start()
{
@@ -24,10 +50,24 @@
if [ -f /etc/ip6addrctl.conf ]; then
ip6addrctl flush >/dev/null 2>&1
ip6addrctl install /etc/ip6addrctl.conf
- ip6addrctl
+ checkyesno ip6addrctl_verbose && ip6addrctl
+ else
+ if checkyesno ipv6_enable; then
+ ip6addrctl_prefer_ipv6
+ else
+ ip6addrctl_prefer_ipv4
+ fi
fi
fi
}
+ip6addrctl_stop()
+{
+ if ifconfig lo0 inet6 >/dev/null 2>&1; then
+ # We have IPv6 support in kernel.
+ ip6addrctl flush >/dev/null 2>&1
+ fi
+}
+
load_rc_config $name
run_rc_command "$1"
==== //depot/projects/gdb/gnu/usr.bin/tar/Makefile#4 (text+ko) ====
@@ -1,4 +1,4 @@
-# $FreeBSD: src/gnu/usr.bin/tar/Makefile,v 1.22 2004/03/03 17:04:49 ru Exp $
+# $FreeBSD: src/gnu/usr.bin/tar/Makefile,v 1.23 2004/06/04 00:39:46 kientzle Exp $
TARDIR= ${.CURDIR}/../../../contrib/tar
.PATH: ${TARDIR}/lib ${TARDIR}/src
@@ -6,7 +6,7 @@
PROG= gtar
.if !defined(WITH_BSDTAR)
-LINKS= ${BINDIR}/gtar ${BINDIR}/tar
+SYMLINKS= ${BINDIR}/gtar ${BINDIR}/tar
MLINKS= gtar.1 tar.1
.endif
==== //depot/projects/gdb/lib/libarchive/Makefile#9 (text+ko) ====
@@ -1,10 +1,10 @@
-# $FreeBSD: src/lib/libarchive/Makefile,v 1.11 2004/05/27 23:57:45 kientzle Exp $
+# $FreeBSD: src/lib/libarchive/Makefile,v 1.12 2004/06/02 08:16:21 kientzle Exp $
LIB= archive
SHLIB_MAJOR= 1
.if ${MACHINE_ARCH} == "arm"
-WARNS?= 3
+WARNS?= 3
.else
WARNS?= 6
.endif
@@ -92,8 +92,9 @@
MLINKS+= archive_entry.3 archive_entry_uname.3
MLINKS+= archive_entry.3 archive_entry_uname_w.3
MLINKS+= archive_read.3 archive_read_data.3
+MLINKS+= archive_read.3 archive_read_data_block.3
MLINKS+= archive_read.3 archive_read_data_into_buffer.3
-MLINKS+= archive_read.3 archive_read_data_into_file.3
+MLINKS+= archive_read.3 archive_read_data_into_fd.3
MLINKS+= archive_read.3 archive_read_data_skip.3
MLINKS+= archive_read.3 archive_read_extract.3
MLINKS+= archive_read.3 archive_read_extract_set_progress_callback.3
==== //depot/projects/gdb/lib/libarchive/archive.h#10 (text+ko) ====
@@ -23,7 +23,7 @@
* (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
* THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*
- * $FreeBSD: src/lib/libarchive/archive.h,v 1.10 2004/05/27 04:00:25 kientzle Exp $
+ * $FreeBSD: src/lib/libarchive/archive.h,v 1.11 2004/06/02 08:14:43 kientzle Exp $
*/
#ifndef ARCHIVE_H_INCLUDED
@@ -166,6 +166,14 @@
/* Read data from the body of an entry. Similar to read(2). */
ssize_t archive_read_data(struct archive *, void *, size_t);
+/*
+ * A zero-copy version of archive_read_data that also exposes the file offset
+ * of each returned block. Note that the client has no way to specify
+ * the desired size of the block. The API does gaurantee that offsets will
+ * be strictly increasing and that returned blocks will not overlap.
+ */
+int archive_read_data_block(struct archive *a,
+ const void **buff, size_t *size, off_t *offset);
/*-
* Some convenience functions that are built on archive_read_data:
==== //depot/projects/gdb/lib/libarchive/archive_private.h#11 (text+ko) ====
@@ -23,7 +23,7 @@
* (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
* THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*
- * $FreeBSD: src/lib/libarchive/archive_private.h,v 1.10 2004/05/27 05:02:35 kientzle Exp $
+ * $FreeBSD: src/lib/libarchive/archive_private.h,v 1.12 2004/06/03 23:29:47 kientzle Exp $
*/
#ifndef ARCHIVE_PRIVATE_H_INCLUDED
@@ -54,12 +54,13 @@
size_t null_length;
/*
- * Used to limit reads of entry data. Eventually, each reader
- * will be able to register it's own read_data routine and these
- * will move into the per-format data for the formats that use them.
+ * Used by archive_read_data() to track blocks and copy
+ * data to client buffers, filling gaps with zero bytes.
*/
- off_t entry_bytes_remaining;
- off_t entry_padding; /* Skip this much after entry data. */
+ const char *read_data_block;
+ off_t read_data_offset;
+ off_t read_data_output_offset;
+ size_t read_data_remaining;
uid_t user_uid; /* UID of current user. */
@@ -151,6 +152,7 @@
struct archive_format_descriptor {
int (*bid)(struct archive *);
int (*read_header)(struct archive *, struct archive_entry *);
+ int (*read_data)(struct archive *, const void **, size_t *, off_t *);
int (*cleanup)(struct archive *);
void *format_data; /* Format-specific data for readers. */
} formats[4];
@@ -168,9 +170,8 @@
void *format_data; /* Used by writers. */
/*
- * Pointers to format-specific functions. On read, these are
- * initialized in the bid process. On write, they're initialized by
- * archive_write_set_format_XXX() calls.
+ * Pointers to format-specific functions for writing. They're
+ * initialized by archive_write_set_format_XXX() calls.
*/
int (*format_init)(struct archive *); /* Only used on write. */
int (*format_finish)(struct archive *);
@@ -183,8 +184,7 @@
/*
* Various information needed by archive_extract.
*/
- struct archive_string extract_mkdirpath;
- struct archive_extract_fixup *archive_extract_fixup;
+ struct extract *extract;
void (*extract_progress)(void *);
void *extract_progress_user_data;
void (*cleanup_archive_extract)(struct archive *);
@@ -220,6 +220,7 @@
void *format_data,
int (*bid)(struct archive *),
int (*read_header)(struct archive *, struct archive_entry *),
+ int (*read_data)(struct archive *, const void **, size_t *, off_t *),
int (*cleanup)(struct archive *));
int __archive_read_register_compression(struct archive *a,
==== //depot/projects/gdb/lib/libarchive/archive_read.3#6 (text+ko) ====
@@ -22,7 +22,7 @@
.\" OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
.\" SUCH DAMAGE.
.\"
-.\" $FreeBSD: src/lib/libarchive/archive_read.3,v 1.5 2004/05/27 04:21:52 kientzle Exp $
+.\" $FreeBSD: src/lib/libarchive/archive_read.3,v 1.6 2004/06/02 08:14:43 kientzle Exp $
.\"
.Dd October 1, 2003
.Dt archive_read 3
@@ -43,9 +43,10 @@
.Nm archive_read_open_file ,
.Nm archive_read_next_header ,
.Nm archive_read_data ,
+.Nm archive_read_data_block ,
.Nm archive_read_data_skip ,
.Nm archive_read_data_into_buffer ,
-.Nm archive_read_data_into_file ,
+.Nm archive_read_data_into_fd ,
.Nm archive_read_extract ,
.Nm archive_read_extract_set_progress_callback ,
.Nm archive_read_finish
@@ -83,11 +84,13 @@
.Ft ssize_t
.Fn archive_read_data "struct archive *" "void *buff" "size_t len"
.Ft int
+.Fn archive_read_data_block "struct archive *" "const void **buff" "size_t *len" "off_t *offset"
+.Ft int
.Fn archive_read_data_skip "struct archive *"
.Ft int
.Fn archive_read_data_into_buffer "struct archive *" "void *"
.Ft int
-.Fn archive_read_data_into_file "struct archive *" "int fd"
+.Fn archive_read_data_into_fd "struct archive *" "int fd"
.Ft int
.Fn archive_read_extract "struct archive *" "int flags"
.Ft void
@@ -165,18 +168,30 @@
.Tn struct archive_entry .
.It Fn archive_read_data
Read data associated with the header just read.
+Internally, this is a convenience function that uses
+.Fn archive_read_data_block .
+.It Fn archive_read_data_block
+Return the next available block of data for this entry.
+Unlike
+.Fn archive_read_data ,
+the
+.Fn archive_read_data_block
+function avoids copying data and allows you to correctly handle
+sparse files, as supported by some archive formats.
+The library gaurantees that offsets will increase and that blocks
+will not overlap.
.It Fn archive_read_data_skip
A convenience function that repeatedly calls
-.Fn archive_read_data
+.Fn archive_read_data_block
to skip all of the data for this archive entry.
.It Fn archive_read_data_into_buffer
A convenience function that repeatedly calls
-.Fn archive_read_data
+.Fn archive_read_data_block
to copy the entire entry into the client-supplied buffer.
Note that the client is responsible for sizing the buffer appropriately.
-.It Fn archive_read_data_into_file
+.It Fn archive_read_data_into_fd
A convenience function that repeatedly calls
-.Fn archive_read_data
+.Fn archive_read_data_block
to copy the entire entry to the provided file descriptor.
.It Fn archive_read_extract
A convenience function that recreates the specified object on
==== //depot/projects/gdb/lib/libarchive/archive_read.c#7 (text+ko) ====
@@ -33,7 +33,7 @@
*/
#include "archive_platform.h"
-__FBSDID("$FreeBSD: src/lib/libarchive/archive_read.c,v 1.6 2004/04/13 23:45:37 kientzle Exp $");
+__FBSDID("$FreeBSD: src/lib/libarchive/archive_read.c,v 1.9 2004/06/04 01:36:10 kientzle Exp $");
#include <err.h>
#include <errno.h>
@@ -103,7 +103,7 @@
archive_close_callback *closer)
{
const void *buffer;
- size_t bytes_read;
+ ssize_t bytes_read;
int high_bidder;
int e;
@@ -130,6 +130,17 @@
/* Read first block now for format detection. */
bytes_read = (a->client_reader)(a, a->client_data, &buffer);
+ /* client_reader should have already set error information. */
+ if (bytes_read < 0)
+ return (ARCHIVE_FATAL);
+
+ /* An empty archive is a serious error. */
+ if (bytes_read == 0) {
+ archive_set_error(a, ARCHIVE_ERRNO_FILE_FORMAT,
+ "Empty input file");
+ return (ARCHIVE_FATAL);
+ }
+
/* Select a decompression routine. */
high_bidder = choose_decompressor(a, buffer, bytes_read);
if (high_bidder < 0)
@@ -319,42 +330,61 @@
}
/*
- * Read data from an archive entry.
+ * Read data from an archive entry, using a read(2)-style interface.
+ * This is a convenience routine that just calls
+ * archive_read_data_block and copies the results into the client
+ * buffer, filling any gaps with zero bytes. Clients using this
+ * API can be completely ignorant of sparse-file issues; sparse files
+ * will simply be padded with nulls.
*/
ssize_t
archive_read_data(struct archive *a, void *buff, size_t s)
{
- const void *data;
- ssize_t bytes_read;
+ off_t remaining;
+ char *dest;
+ size_t bytes_read;
+ size_t len;
+ int r;
+
+ bytes_read = 0;
+ dest = buff;
- archive_check_magic(a, ARCHIVE_READ_MAGIC, ARCHIVE_STATE_DATA);
- /*
- * off_t is generally at least as wide as size_t, so widen for
- * comparison and narrow for the assignment. Otherwise, on
- * platforms with 32-bit size_t and 64-bit off_t, we won't be
- * able to correctly read archives with entries larger than
- * 4gig.
- */
- if ((off_t)s > a->entry_bytes_remaining)
- s = (size_t)a->entry_bytes_remaining;
- if (s > 0) {
- bytes_read = (a->compression_read_ahead)(a, &data, 1);
- if (bytes_read < 0) {
- a->state = ARCHIVE_STATE_FATAL;
- return (bytes_read);
+ while (s > 0) {
+ if (a->read_data_remaining <= 0) {
+ r = archive_read_data_block(a,
+ (const void **)&a->read_data_block,
+ &a->read_data_remaining,
+ &a->read_data_offset);
+ if (r == ARCHIVE_EOF)
+ return (bytes_read);
+ if (r != ARCHIVE_OK)
+ return (r);
}
- if ((size_t)bytes_read > s)
- bytes_read = s;
- } else
- bytes_read = 0;
- if (bytes_read > 0) {
- memcpy(buff, data, bytes_read);
- (a->compression_read_consume)(a, bytes_read);
+ if (a->read_data_offset < a->read_data_output_offset) {
+ remaining =
+ a->read_data_output_offset - a->read_data_offset;
+ if (remaining > (off_t)s)
+ remaining = (off_t)s;
+ len = (size_t)remaining;
+ memset(dest, 0, len);
+ a->read_data_output_offset += len;
+ s -= len;
+ bytes_read += len;
+ } else {
+ len = a->read_data_remaining;
+ if (len > s)
+ len = s;
+ memcpy(dest, a->read_data_block, len);
+ s -= len;
+ a->read_data_remaining -= len;
+ a->read_data_output_offset += len;
+ a->read_data_offset += len;
+ dest += len;
+ bytes_read += len;
+ }
}
-
- a->entry_bytes_remaining -= bytes_read;
- return (bytes_read);
+ return (ARCHIVE_OK);
}
/*
@@ -363,33 +393,46 @@
int
archive_read_data_skip(struct archive *a)
{
+ int r;
const void *buff;
- ssize_t bytes_read, to_skip;
+ ssize_t size;
+ off_t offset;
archive_check_magic(a, ARCHIVE_READ_MAGIC, ARCHIVE_STATE_DATA);
- to_skip = a->entry_bytes_remaining + a->entry_padding;
- a->entry_bytes_remaining = 0;
+ while ((r = archive_read_data_block(a, &buff, &size, &offset)) ==
+ ARCHIVE_OK)
+ ;
+
+ if (r == ARCHIVE_EOF)
+ r = ARCHIVE_OK;
+
+ a->state = ARCHIVE_STATE_HEADER;
+ return (r);
+}
+
+/*
+ * Read the next block of entry data from the archive.
+ * This is a zero-copy interface; the client receives a pointer,
+ * size, and file offset of the next available block of data.
+ *
+ * Returns ARCHIVE_OK if the operation is successful, ARCHIVE_EOF if
+ * the end of entry is encountered.
+ */
+int
+archive_read_data_block(struct archive *a,
+ const void **buff, size_t *size, off_t *offset)
+{
+ archive_check_magic(a, ARCHIVE_READ_MAGIC, ARCHIVE_STATE_DATA);
- for (; to_skip > 0; to_skip -= bytes_read) {
- /* TODO: Optimize skip in compression layer. */
- bytes_read = (a->compression_read_ahead)(a, &buff, to_skip);
- if (bytes_read < 0) {
- a->entry_padding = to_skip;
- return (ARCHIVE_FATAL);
- }
- if (bytes_read == 0) {
- archive_set_error(a, EIO,
- "Premature end of archive entry");
- return (ARCHIVE_FATAL);
- }
- if (bytes_read > to_skip)
- bytes_read = to_skip;
- (a->compression_read_consume)(a, bytes_read);
+ if (a->format->read_data == NULL) {
+ archive_set_error(a, ARCHIVE_ERRNO_PROGRAMMER,
+ "Internal error: "
+ "No format_read_data_block function registered");
+ return (ARCHIVE_FATAL);
}
- a->entry_padding = 0;
- a->state = ARCHIVE_STATE_HEADER;
- return (ARCHIVE_OK);
+
+ return (a->format->read_data)(a, buff, size, offset);
}
/*
@@ -428,7 +471,6 @@
/* Casting a pointer to int allows us to remove 'const.' */
free((void *)(uintptr_t)(const void *)a->nulls);
- archive_string_free(&a->extract_mkdirpath);
archive_string_free(&a->error_string);
if (a->entry)
archive_entry_free(a->entry);
@@ -445,6 +487,7 @@
void *format_data,
int (*bid)(struct archive *),
int (*read_header)(struct archive *, struct archive_entry *),
+ int (*read_data)(struct archive *, const void **, size_t *, off_t *),
int (*cleanup)(struct archive *))
{
int i, number_slots;
@@ -459,6 +502,7 @@
if (a->formats[i].bid == NULL) {
a->formats[i].bid = bid;
a->formats[i].read_header = read_header;
+ a->formats[i].read_data = read_data;
a->formats[i].cleanup = cleanup;
a->formats[i].format_data = format_data;
return (ARCHIVE_OK);
==== //depot/projects/gdb/lib/libarchive/archive_read_data_into_fd.c#6 (text+ko) ====
@@ -25,7 +25,7 @@
*/
#include "archive_platform.h"
-__FBSDID("$FreeBSD: src/lib/libarchive/archive_read_data_into_fd.c,v 1.5 2004/05/13 06:01:14 kientzle Exp $");
+__FBSDID("$FreeBSD: src/lib/libarchive/archive_read_data_into_fd.c,v 1.6 2004/06/02 08:14:43 kientzle Exp $");
#include <sys/types.h>
#include <unistd.h>
@@ -33,36 +33,49 @@
#include "archive.h"
#include "archive_private.h"
+/* Maximum amount of data to write at one time. */
+#define MAX_WRITE (1024 * 1024)
+
/*
- * This implementation minimizes copying of data.
+ * This implementation minimizes copying of data and is sparse-file aware.
*/
ssize_t
archive_read_data_into_fd(struct archive *a, int fd)
{
- ssize_t bytes_read, bytes_written, total_written;
+ int r;
const void *buff;
+ ssize_t size, bytes_to_write;
+ ssize_t bytes_written, total_written;
+ off_t offset;
+ off_t output_offset;
+
+ archive_check_magic(a, ARCHIVE_READ_MAGIC, ARCHIVE_STATE_DATA);
total_written = 0;
- while (a->entry_bytes_remaining > 0) {
- /* Remember: '1' here is minimum, not maximum. */
- /* Read-ahead function will return as much as is convenient. */
- bytes_read = (a->compression_read_ahead)(a, &buff, 1);
- if (bytes_read < 0)
- return (-1);
- if (bytes_read > a->entry_bytes_remaining)
- bytes_read = (ssize_t)a->entry_bytes_remaining;
- /* Don't copy more than 1 megabyte at a time. */
- if (bytes_read > (1024*1024))
- bytes_read = 1024*1024;
+ output_offset = 0;
- bytes_written = write(fd, buff, bytes_read);
- if (bytes_written < 0)
- return (-1);
- (a->compression_read_consume)(a, bytes_written);
- total_written += bytes_written;
- a->entry_bytes_remaining -= bytes_written;
- if (a->extract_progress != NULL)
- (*a->extract_progress)(a->extract_progress_user_data);
+ while ((r = archive_read_data_block(a, &buff, &size, &offset)) ==
+ ARCHIVE_OK) {
+ if (offset > output_offset) {
+ lseek(fd, offset - output_offset, SEEK_CUR);
+ output_offset = offset;
+ }
+ while (size > 0) {
+ bytes_to_write = size;
+ if (bytes_to_write > MAX_WRITE)
+ bytes_to_write = MAX_WRITE;
+ bytes_written = write(fd, buff, bytes_to_write);
+ if (bytes_written < 0)
+ return (-1);
+ output_offset += bytes_written;
+ total_written += bytes_written;
+ size -= bytes_written;
+ if (a->extract_progress != NULL)
+ (*a->extract_progress)(a->extract_progress_user_data);
+ }
}
+
+ if (r != ARCHIVE_EOF)
+ return (-1);
return (total_written);
}
==== //depot/projects/gdb/lib/libarchive/archive_read_extract.c#12 (text+ko) ====
@@ -25,7 +25,7 @@
*/
#include "archive_platform.h"
-__FBSDID("$FreeBSD: src/lib/libarchive/archive_read_extract.c,v 1.13 2004/05/27 05:02:35 kientzle Exp $");
+__FBSDID("$FreeBSD: src/lib/libarchive/archive_read_extract.c,v 1.14 2004/06/03 23:29:47 kientzle Exp $");
#include <sys/stat.h>
#include <sys/types.h>
@@ -42,7 +42,6 @@
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
-#include <tar.h>
#include <unistd.h>
#ifdef LINUX
#include <ext2fs/ext2_fs.h>
@@ -54,6 +53,27 @@
#include "archive_entry.h"
#include "archive_private.h"
+struct fixup_entry {
+ struct fixup_entry *next;
+ mode_t mode;
+ int64_t mtime;
+ int64_t atime;
+ unsigned long mtime_nanos;
+ unsigned long atime_nanos;
+ unsigned long fflags_set;
+ int fixup; /* bitmask of what needs fixing */
+ char *name;
+};
+
+#define FIXUP_MODE 1
+#define FIXUP_TIMES 2
+#define FIXUP_FFLAGS 4
+
+struct extract {
+ struct archive_string mkdirpath;
+ struct fixup_entry *fixup_list;
+};
+
static void archive_extract_cleanup(struct archive *);
static int archive_read_extract_block_device(struct archive *,
struct archive_entry *, int);
@@ -93,82 +113,41 @@
static int set_perm(struct archive *, struct archive_entry *, int mode,
int flags);
static int set_time(struct archive *, struct archive_entry *, int);
-static struct archive_extract_fixup *
- sort_dir_list(struct archive_extract_fixup *p);
-
+static struct fixup_entry *sort_dir_list(struct fixup_entry *p);
-struct archive_extract_fixup {
- struct archive_extract_fixup *next;
- mode_t mode;
- int64_t mtime;
- int64_t atime;
- unsigned long mtime_nanos;
- unsigned long atime_nanos;
- unsigned long fflags_set;
- int fixup; /* bitmask of what needs fixing */
- char *name;
-};
-
-#define FIXUP_MODE 1
-#define FIXUP_TIMES 2
-#define FIXUP_FFLAGS 4
/*
* Extract this entry to disk.
*
- * TODO: Validate hardlinks. Is there any way to validate hardlinks
- * without keeping a complete list of filenames from the entire archive?? Ugh.
+ * TODO: Validate hardlinks. According to the standards, we're
+ * supposed to check each extracted hardlink and squawk if it refers
+ * to a file that we didn't restore. I'm not entirely convinced this
+ * is a good idea, but more importantly: Is there any way to validate
+ * hardlinks without keeping a complete list of filenames from the
+ * entire archive?? Ugh.
*
*/
int
archive_read_extract(struct archive *a, struct archive_entry *entry, int flags)
{
- mode_t writable_mode;
- struct archive_extract_fixup *le;
- const struct stat *st;
+ mode_t mode;
+ struct extract *extract;
int ret;
int restore_pwd;
- restore_pwd = -1;
- st = archive_entry_stat(entry);
- if (S_ISDIR(st->st_mode)) {
- /*
- * TODO: Does this really work under all conditions?
- *
- * E.g., root restores a dir owned by someone else?
- */
- writable_mode = st->st_mode | 0700;
-
- /*
- * In order to correctly restore non-writable dirs or
- * dir timestamps, we need to maintain a fix-up list.
- */
- if (st->st_mode != writable_mode ||
- flags & ARCHIVE_EXTRACT_TIME) {
- le = malloc(sizeof(struct archive_extract_fixup));
- le->fixup = 0;
- le->next = a->archive_extract_fixup;
- a->archive_extract_fixup = le;
- le->name = strdup(archive_entry_pathname(entry));
- a->cleanup_archive_extract = archive_extract_cleanup;
-
- if (st->st_mode != writable_mode) {
- le->mode = st->st_mode;
- le->fixup |= FIXUP_MODE;
- /* Make sure I can write to this directory. */
- archive_entry_set_mode(entry, writable_mode);
- }
- if (flags & ARCHIVE_EXTRACT_TIME) {
- le->mtime = st->st_mtime;
- le->mtime_nanos = ARCHIVE_STAT_MTIME_NANOS(st);
- le->atime = st->st_atime;
- le->atime_nanos = ARCHIVE_STAT_ATIME_NANOS(st);
- le->fixup |= FIXUP_TIMES;
- }
-
+ if (a->extract == NULL) {
+ a->extract = malloc(sizeof(*a->extract));
+ if (a->extract == NULL) {
+ archive_set_error(a, ENOMEM, "Can't extract");
+ return (ARCHIVE_FATAL);
}
+ a->cleanup_archive_extract = archive_extract_cleanup;
+ memset(a->extract, 0, sizeof(*a->extract));
}
+ extract = a->extract;
+ restore_pwd = -1;
+
if (archive_entry_hardlink(entry) != NULL)
return (archive_read_extract_hard_link(a, entry, flags));
@@ -183,7 +162,8 @@
/* XXX Update pathname in 'entry' XXX */
}
- switch (st->st_mode & S_IFMT) {
+ mode = archive_entry_mode(entry);
+ switch (mode & S_IFMT) {
default:
/* Fall through, as required by POSIX. */
case S_IFREG:
@@ -235,10 +215,13 @@
static
void archive_extract_cleanup(struct archive *a)
{
- struct archive_extract_fixup *next, *p;
+ struct fixup_entry *next, *p;
+ struct extract *extract;
+
/* Sort dir list so directories are fixed up in depth-first order. */
- p = sort_dir_list(a->archive_extract_fixup);
+ extract = a->extract;
+ p = sort_dir_list(extract->fixup_list);
while (p != NULL) {
if (p->fixup & FIXUP_TIMES) {
@@ -260,17 +243,20 @@
free(p);
p = next;
}
- a->archive_extract_fixup = NULL;
+ extract->fixup_list = NULL;
+ archive_string_free(&extract->mkdirpath);
+ free(a->extract);
+ a->extract = NULL;
}
/*
* Simple O(n log n) merge sort to order the fixup list. In
* particular, we want to restore dir timestamps depth-first.
*/
-static struct archive_extract_fixup *
-sort_dir_list(struct archive_extract_fixup *p)
+static struct fixup_entry *
+sort_dir_list(struct fixup_entry *p)
{
- struct archive_extract_fixup *a, *b, *t;
+ struct fixup_entry *a, *b, *t;
if (p == NULL)
return (NULL);
@@ -397,9 +383,44 @@
archive_read_extract_dir(struct archive *a, struct archive_entry *entry,
int flags)
{
- int mode, ret, ret2;
+ struct extract *extract;
+ struct fixup_entry *le;
+ const struct stat *st;
+ mode_t mode, writable_mode;
+ int ret, ret2;
+
+ extract = a->extract;
+ st = archive_entry_stat(entry);
+ mode = st->st_mode;
+
+ /*
+ * XXX TODO: Does this really work under all conditions?
+ * E.g., root restores a dir owned by someone else? XXX
+ */
+ /* Ensure we can write to this directory. */
+ writable_mode = mode | 0700;
+
+ if (mode != writable_mode || flags & ARCHIVE_EXTRACT_TIME) {
+ /* Add this dir to the fixup list. */
+ le = malloc(sizeof(struct fixup_entry));
+ le->fixup = 0;
+ le->next = extract->fixup_list;
+ extract->fixup_list = le;
+ le->name = strdup(archive_entry_pathname(entry));
- mode = archive_entry_stat(entry)->st_mode;
>>> TRUNCATED FOR MAIL (1000 lines) <<<
More information about the p4-projects
mailing list