mirror of
git://sourceware.org/git/lvm2.git
synced 2025-09-26 01:44:19 +03:00
Compare commits
160 Commits
old-v1_00_
...
v1_00_20
Author | SHA1 | Date | |
---|---|---|---|
|
9812657777 | ||
|
0b09312fc6 | ||
|
d0a7ac6b74 | ||
|
ff9a238fbd | ||
|
359fffa5f1 | ||
|
5bf92ced1a | ||
|
340bcc7b45 | ||
|
ef03742bd4 | ||
|
20431ec16d | ||
|
becba8157b | ||
|
51fd3bb0eb | ||
|
4bbd3acb4e | ||
|
3bc930ea7b | ||
|
d1b26f8e86 | ||
|
fdf15caaff | ||
|
c7b4a53c0b | ||
|
af78dc0308 | ||
|
5ad39493c4 | ||
|
61f597b408 | ||
|
2162825240 | ||
|
2b780e70d1 | ||
|
a3823f818e | ||
|
1f7c47bcaf | ||
|
ec53c365a2 | ||
|
793ad1f2d4 | ||
|
9bc733b76c | ||
|
21b28f0217 | ||
|
d3e23caa52 | ||
|
9e7518de67 | ||
|
679f0047aa | ||
|
d77d5ce14b | ||
|
33ec22a2af | ||
|
353053225f | ||
|
b7f3d6f7f7 | ||
|
e34577499d | ||
|
4cf8960c0c | ||
|
1f93ea0675 | ||
|
25b705c3a8 | ||
|
0725588731 | ||
|
fc5c61cc8b | ||
|
ac282e63c6 | ||
|
c3941941ce | ||
|
46cdd53323 | ||
|
3ff3e302c3 | ||
|
f2ceecf95c | ||
|
9314c7c881 | ||
|
54abb2c572 | ||
|
8fa3bdd025 | ||
|
5e7a308528 | ||
|
7952177786 | ||
|
9afbe49c84 | ||
|
9f06ba2db3 | ||
|
fe55bfddcf | ||
|
c0842e6444 | ||
|
3fed20d06a | ||
|
5e8f2e2c04 | ||
|
e4df99ea84 | ||
|
b3276f5f11 | ||
|
32667ca256 | ||
|
bed122a170 | ||
|
14adc9b875 | ||
|
a8778bbc5a | ||
|
a54e641f44 | ||
|
5c99efe87a | ||
|
7da1d731ff | ||
|
af9828e819 | ||
|
7a27136142 | ||
|
012ad2d423 | ||
|
ef3bdbf4da | ||
|
b3bb698f7b | ||
|
1ed5d1e4c1 | ||
|
bdee01a03d | ||
|
458f7376d7 | ||
|
cb3a00e027 | ||
|
482eb1f3fb | ||
|
6e0f638f5e | ||
|
bab349047d | ||
|
28ea6b8de8 | ||
|
9d51bbdae8 | ||
|
d622f79533 | ||
|
04c8515ad1 | ||
|
53bc4251d1 | ||
|
a5a751f02f | ||
|
66ed5f82c4 | ||
|
c802a9e6aa | ||
|
880f210946 | ||
|
4f9f7eb6a6 | ||
|
f910c4a8e7 | ||
|
529686d965 | ||
|
84dfd1536f | ||
|
85dedc324c | ||
|
d639237411 | ||
|
449aaf75f1 | ||
|
b1fda66caa | ||
|
66a8e90fd9 | ||
|
37b487d191 | ||
|
6c59fe3577 | ||
|
1cbb70c992 | ||
|
e06b39f882 | ||
|
2602b1493e | ||
|
989d14502d | ||
|
f78a550282 | ||
|
54a1abb284 | ||
|
97b492a8e2 | ||
|
0873bd14a9 | ||
|
eff6ba429a | ||
|
8c18064be4 | ||
|
44a1ac0cf3 | ||
|
28dc8d88dd | ||
|
2c0c2b64ba | ||
|
bd3e0f5248 | ||
|
cd52d98938 | ||
|
894c70e7f8 | ||
|
51d70c2edd | ||
|
7d4b355240 | ||
|
3b56193b98 | ||
|
b16045b57d | ||
|
9e8b0fca5b | ||
|
35cf1b3b5b | ||
|
83f788af57 | ||
|
2ffe378d3f | ||
|
38b33a4a5e | ||
|
60bf9ed0a0 | ||
|
16adf4de1b | ||
|
80de983023 | ||
|
8703ca623f | ||
|
286253a73f | ||
|
bd806a41df | ||
|
b89c4e9002 | ||
|
6dbf31c0c3 | ||
|
060c45d8a1 | ||
|
33d3e82e4d | ||
|
4bb074514d | ||
|
e3f8892003 | ||
|
9d00ad5f18 | ||
|
dae4344850 | ||
|
aa7f3fabe2 | ||
|
f93434a8ce | ||
|
25dee56be9 | ||
|
ce9a3f3797 | ||
|
11e384920a | ||
|
a0a1f1e536 | ||
|
3b3d0ea9eb | ||
|
2f4d78286d | ||
|
677dc6f985 | ||
|
d52057e732 | ||
|
fa2a1cb1fb | ||
|
19a0fb04ad | ||
|
947352f2fe | ||
|
adcbedb686 | ||
|
7732f92acd | ||
|
ad8a001688 | ||
|
9121eada08 | ||
|
49bd4d25a2 | ||
|
d80b4129c6 | ||
|
7edb4172d5 | ||
|
c3a4677990 | ||
|
5cbb893a3b | ||
|
f28a2a432b | ||
|
03b75a2d27 |
43
Makefile.in
43
Makefile.in
@@ -1,35 +1,48 @@
|
||||
#
|
||||
# Copyright (C) 2001 Sistina Software
|
||||
# Copyright (C) 2001-2004 Sistina Software, Inc. All rights reserved.
|
||||
# Copyright (C) 2004 Red Hat, Inc. All rights reserved.
|
||||
#
|
||||
# This LVM library is free software; you can redistribute it and/or
|
||||
# modify it under the terms of the GNU Library General Public
|
||||
# License as published by the Free Software Foundation; either
|
||||
# version 2 of the License, or (at your option) any later version.
|
||||
# This file is part of the LVM2.
|
||||
#
|
||||
# This LVM library is distributed in the hope that it will be useful,
|
||||
# but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
# Library General Public License for more details.
|
||||
# This copyrighted material is made available to anyone wishing to use,
|
||||
# modify, copy, or redistribute it subject to the terms and conditions
|
||||
# of the GNU General Public License v.2.
|
||||
#
|
||||
# You should have received a copy of the GNU Library General Public
|
||||
# License along with this LVM library; if not, write to the Free
|
||||
# Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
|
||||
# MA 02111-1307, USA
|
||||
# You should have received a copy of the GNU General Public License
|
||||
# along with this program; if not, write to the Free Software Foundation,
|
||||
# Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
|
||||
srcdir = @srcdir@
|
||||
top_srcdir = @top_srcdir@
|
||||
VPATH = @srcdir@
|
||||
|
||||
SUBDIRS = include man lib tools
|
||||
SUBDIRS = doc include man
|
||||
|
||||
ifeq ("@INTL@", "yes")
|
||||
SUBDIRS += po
|
||||
endif
|
||||
|
||||
SUBDIRS += lib tools
|
||||
|
||||
ifeq ($(MAKECMDGOALS),distclean)
|
||||
SUBDIRS += lib/format1 \
|
||||
lib/format_pool \
|
||||
lib/mirror \
|
||||
lib/snapshot \
|
||||
po \
|
||||
test/mm test/device test/format1 test/regex test/filters
|
||||
endif
|
||||
|
||||
include make.tmpl
|
||||
|
||||
lib: include
|
||||
tools: include lib
|
||||
tools: lib
|
||||
po: lib tools
|
||||
|
||||
ifeq ("@INTL@", "yes")
|
||||
lib.pofile: include.pofile
|
||||
tools.pofile: lib.pofile
|
||||
po.pofile: lib.pofile tools.pofile
|
||||
pofile: po.pofile
|
||||
endif
|
||||
|
||||
|
10
README
10
README
@@ -13,11 +13,11 @@ Tarballs are available from:
|
||||
ftp://ftp.sistina.com/pub/LVM2/device-mapper/
|
||||
|
||||
To access the CVS tree use:
|
||||
cvs -d :pserver:cvs@tech.sistina.com:/data/cvs login
|
||||
CVS password: cvs1
|
||||
cvs -d :pserver:cvs@tech.sistina.com:/data/cvs checkout LVM2
|
||||
cvs -d :pserver:cvs@sources.redhat.com:/cvs/lvm2 login
|
||||
CVS password: cvs
|
||||
cvs -d :pserver:cvs@sources.redhat.com:/cvs/lvm2 co LVM2
|
||||
|
||||
Mailing list for discussion/bug reports etc.
|
||||
linux-lvm@sistina.com
|
||||
Subscribe from http://lists.sistina.com/mailman/listinfo/linux-lvm
|
||||
linux-lvm@redhat.com
|
||||
Subscribe from https://www.redhat.com/mailman/listinfo/linux-lvm
|
||||
|
||||
|
110
WHATS_NEW
110
WHATS_NEW
@@ -1,3 +1,112 @@
|
||||
Version 2.00.17 -
|
||||
=============================
|
||||
Add read-only GFS pool support.
|
||||
Add lvm2create_initrd script from http://poochiereds.net/svn/lvm2/
|
||||
Fix rounding of large diplayed sizes.
|
||||
Suppress decimal point when using units of sectors/bytes.
|
||||
Additional kernel target checks before pvmove & snapshot creation.
|
||||
Add i2o_block.
|
||||
|
||||
Version 2.00.16 - 24 May 2004
|
||||
=============================
|
||||
Set area_count within alloc_lv_segment.
|
||||
Remove error labels from lvresize.
|
||||
Fix a pvs error path.
|
||||
xxchange -ae for exclusive activation.
|
||||
Don't return non-zero status if there aren't any volume groups.
|
||||
Add --alloc argument to tools.
|
||||
Rename allocation policies to contiguous, normal, anywhere, inherit.
|
||||
nextfree becomes normal; anywhere isn't implemented yet.
|
||||
LV inherits allocation policy from VG. Defaults: LV - inherit; VG - normal
|
||||
Additional status character added to vgs to indicate allocation policy.
|
||||
Add reset_fn to external_locking.
|
||||
Ensure presence of virtual targets before attempting activating.
|
||||
Attempt to fix resizing of snapshot origins.
|
||||
Restructure lvresize, bringing it closer to lvcreate.
|
||||
A quick sanity check on vg_disk struct when read in. More checks needed.
|
||||
Only include visible LVs in active/open counts.
|
||||
Add virtual segment types, zero and error. A large sparse device can be
|
||||
constructed as a writeable snapshot of a large zero segment.
|
||||
Add --type to lvcreate/resize.
|
||||
Push lv_create & alloc policy up to tool level.
|
||||
Fix pvdisplay return code.
|
||||
Detect invalid LV names in arg lists.
|
||||
Reporting uses line-at-a-time output.
|
||||
lvm2 format sets unlimited_vols format flag.
|
||||
Internal-only metadata flag support.
|
||||
Basic checking for presence of device-mapper targets.
|
||||
Separate out polldaemon.
|
||||
Revise internal locking semantics.
|
||||
Move find_pv_by_name to library.
|
||||
Rename move->copy.
|
||||
Add devices to segments report.
|
||||
Begin separating out segment code. There's a lot of change here.
|
||||
Compress any (obsolete) long LVM1 pvids encountered.
|
||||
Support for tagged config files.
|
||||
Don't abort operations if selinux present but disabled.
|
||||
Fix typo in configure which left HAVE_LIBDL unset.
|
||||
|
||||
Version 2.00.15 - 19 Apr 2004
|
||||
=============================
|
||||
configure --with-owner= --with-group= to avoid -o and -g args to 'install'
|
||||
|
||||
Version 2.00.14 - 16 Apr 2004
|
||||
=============================
|
||||
Use 64-bit file functions by default.
|
||||
|
||||
Version 2.00.13 - 16 Apr 2004
|
||||
=============================
|
||||
Set devices/md_component_detection = 1 to ignore devices containing md
|
||||
superblocks. [Luca Berra]
|
||||
Ignore error setting selinux file context if fs doesn't support it.
|
||||
|
||||
Version 2.00.12 - 14 Apr 2004
|
||||
=============================
|
||||
Install a default lvm.conf into /etc/lvm if there isn't one already.
|
||||
Allow different installation dir for lvm.static (configure --staticdir=)
|
||||
Fix inverted selinux error check.
|
||||
Recognise power2 in /proc/devices.
|
||||
Fix counting in lvs_in_vg_opened. [It ignored devices open more than once.]
|
||||
|
||||
Version 2.00.11 - 8 Apr 2004
|
||||
============================
|
||||
Set fallback_to_lvm1 in lvm.conf (or configure --enable-lvm1_fallback)
|
||||
to run lvm1 binaries if running a 2.4 kernel without device-mapper.
|
||||
|
||||
Version 2.00.10 - 7 Apr 2004
|
||||
============================
|
||||
More fixes for static build.
|
||||
Add basic selinux support.
|
||||
Fix sysfs detection.
|
||||
|
||||
Version 2.00.09 - 31 Mar 2004
|
||||
=============================
|
||||
Update copyright notices for Red Hat.
|
||||
Fix vgmknodes to remove dud /dev/mapper entries. (libdevmapper update reqd).
|
||||
Add LVM1-style colon output to vgdisplay.
|
||||
lvchange --refresh to reload active LVs.
|
||||
Add string display to memory leak dump.
|
||||
Add locking flags & memlock option.
|
||||
Add list_versions to library.
|
||||
Ignore open hidden LVs when checking if deactivation is OK.
|
||||
Suppress move percentage when device inactive.
|
||||
Add lv_info_by_lvid.
|
||||
Various tidy-ups to the build process.
|
||||
Rebaseline internal verbose level.
|
||||
Add --nolocking option for read operations if locking is failing.
|
||||
Add option to compile into a library.
|
||||
When compiled without libdevmapper, only print warning message once.
|
||||
Fix lvreduce PV extent calculations.
|
||||
Fix DESTDIR to work with configure path overrides.
|
||||
Always use / as config file separator & rename internal config file variables.
|
||||
Add support for tagging PV/VG/LVs and hosts.
|
||||
Fix rare bug in recognition of long cmdline argument forms.
|
||||
Add basic internationalisation infrastructure.
|
||||
Don't recurse symlinked dirs such as /dev/fd on 2.6 kernels.
|
||||
Update autoconf files.
|
||||
Add sysfs block device filtering for 2.6 kernels.
|
||||
Update refs for move to sources.redhat.com.
|
||||
|
||||
Friday 14th November 2003
|
||||
=========================
|
||||
Some bug fixes & minor enhancements, including:
|
||||
@@ -6,6 +115,7 @@ Some bug fixes & minor enhancements, including:
|
||||
Tool error codes made more consistent.
|
||||
vgmknodes written.
|
||||
O_DIRECT can be turned off if it doesn't work in your kernel.
|
||||
dumpconfig to display the active configuration file
|
||||
|
||||
You need to update libdevmapper before using 'vgmknodes' or 'vgscan --mknodes'.
|
||||
If your root filesystem is on an LV, you should run one of those two
|
||||
|
63
WHATS_NEW_DM
Normal file
63
WHATS_NEW_DM
Normal file
@@ -0,0 +1,63 @@
|
||||
Version 1.00.18
|
||||
=============================
|
||||
Add target message-passing ioctl.
|
||||
|
||||
Version 1.00.17 - 17 Apr 2004
|
||||
=============================
|
||||
configure --with-owner= --with-group= to avoid -o and -g args to 'install'
|
||||
Fix library selinux linking.
|
||||
|
||||
Version 1.00.16 - 16 Apr 2004
|
||||
=============================
|
||||
Ignore error setting selinux file context if fs doesn't support it.
|
||||
|
||||
Version 1.00.15 - 7 Apr 2004
|
||||
============================
|
||||
Fix status overflow check in kernel patches.
|
||||
|
||||
Version 1.00.14 - 6 Apr 2004
|
||||
============================
|
||||
Fix static selinux build.
|
||||
|
||||
Version 1.00.13 - 6 Apr 2004
|
||||
============================
|
||||
Add some basic selinux support.
|
||||
|
||||
Version 1.00.12 - 6 Apr 2004
|
||||
============================
|
||||
Fix dmsetup.static install.
|
||||
|
||||
Version 1.00.11 - 5 Apr 2004
|
||||
============================
|
||||
configure --enable-static_link does static build in addition to dynamic.
|
||||
Moved Makefile library targets definition into template.
|
||||
|
||||
Version 1.00.10 - 2 Apr 2004
|
||||
============================
|
||||
Fix DESTDIR handling.
|
||||
Static build installs to dmsetup.static.
|
||||
Basic support for internationalisation.
|
||||
Minor Makefile tidy-ups/fixes.
|
||||
|
||||
Version 1.00.09 - 31 Mar 2004
|
||||
=============================
|
||||
Update copyright notices to Red Hat.
|
||||
Move full mknodes functionality from dmsetup into libdevmapper.
|
||||
Avoid sscanf %as for uClibc compatibility.
|
||||
Cope if DM_LIST_VERSIONS is not defined.
|
||||
Add DM_LIST_VERSIONS functionality to kernel patches.
|
||||
Generate new kernel patches for 2.4.26-rc1.
|
||||
|
||||
Version 1.00.08 - 27 Feb 2004
|
||||
=============================
|
||||
Added 'dmsetup targets'.
|
||||
Added event_nr support to 'dmsetup wait'.
|
||||
Updated dmsetup man page.
|
||||
Allow logging function to be reset to use internal one.
|
||||
Bring log macros in line with LVM2 ones.
|
||||
Added 'make install_static_lib' which installs libdevmapper.a.
|
||||
Made configure/makefiles closer to LVM2 versions.
|
||||
Fixed DESTDIR for make install/install_static_lib.
|
||||
Updated README/INSTALL to reflect move to sources.redhat.com.
|
||||
Updated autoconf files to 2003-06-17.
|
||||
|
537
autoconf/config.guess
vendored
537
autoconf/config.guess
vendored
@@ -1,9 +1,9 @@
|
||||
#! /bin/sh
|
||||
# Attempt to guess a canonical system name.
|
||||
# Copyright (C) 1992, 1993, 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001
|
||||
# Free Software Foundation, Inc.
|
||||
# Copyright (C) 1992, 1993, 1994, 1995, 1996, 1997, 1998, 1999,
|
||||
# 2000, 2001, 2002, 2003 Free Software Foundation, Inc.
|
||||
|
||||
timestamp='2001-09-04'
|
||||
timestamp='2003-06-17'
|
||||
|
||||
# This file is free software; you can redistribute it and/or modify it
|
||||
# under the terms of the GNU General Public License as published by
|
||||
@@ -24,8 +24,9 @@ timestamp='2001-09-04'
|
||||
# configuration script generated by Autoconf, you may include it under
|
||||
# the same distribution terms that you use for the rest of that program.
|
||||
|
||||
# Written by Per Bothner <bothner@cygnus.com>.
|
||||
# Please send patches to <config-patches@gnu.org>.
|
||||
# Originally written by Per Bothner <per@bothner.com>.
|
||||
# Please send patches to <config-patches@gnu.org>. Submit a context
|
||||
# diff and a properly formatted ChangeLog entry.
|
||||
#
|
||||
# This script attempts to guess a canonical system name similar to
|
||||
# config.sub. If it succeeds, it prints the system name on stdout, and
|
||||
@@ -87,30 +88,42 @@ if test $# != 0; then
|
||||
exit 1
|
||||
fi
|
||||
|
||||
trap 'exit 1' 1 2 15
|
||||
|
||||
dummy=dummy-$$
|
||||
trap 'rm -f $dummy.c $dummy.o $dummy.rel $dummy; exit 1' 1 2 15
|
||||
# CC_FOR_BUILD -- compiler used by this script. Note that the use of a
|
||||
# compiler to aid in system detection is discouraged as it requires
|
||||
# temporary files to be created and, as you can see below, it is a
|
||||
# headache to deal with in a portable fashion.
|
||||
|
||||
# CC_FOR_BUILD -- compiler used by this script.
|
||||
# Historically, `CC_FOR_BUILD' used to be named `HOST_CC'. We still
|
||||
# use `HOST_CC' if defined, but it is deprecated.
|
||||
|
||||
set_cc_for_build='case $CC_FOR_BUILD,$HOST_CC,$CC in
|
||||
,,) echo "int dummy(){}" > $dummy.c ;
|
||||
for c in cc gcc c89 ; do
|
||||
($c $dummy.c -c -o $dummy.o) >/dev/null 2>&1 ;
|
||||
if test $? = 0 ; then
|
||||
# Portable tmp directory creation inspired by the Autoconf team.
|
||||
|
||||
set_cc_for_build='
|
||||
trap "exitcode=\$?; (rm -f \$tmpfiles 2>/dev/null; rmdir \$tmp 2>/dev/null) && exit \$exitcode" 0 ;
|
||||
trap "rm -f \$tmpfiles 2>/dev/null; rmdir \$tmp 2>/dev/null; exit 1" 1 2 13 15 ;
|
||||
: ${TMPDIR=/tmp} ;
|
||||
{ tmp=`(umask 077 && mktemp -d -q "$TMPDIR/cgXXXXXX") 2>/dev/null` && test -n "$tmp" && test -d "$tmp" ; } ||
|
||||
{ test -n "$RANDOM" && tmp=$TMPDIR/cg$$-$RANDOM && (umask 077 && mkdir $tmp) ; } ||
|
||||
{ tmp=$TMPDIR/cg-$$ && (umask 077 && mkdir $tmp) && echo "Warning: creating insecure temp directory" >&2 ; } ||
|
||||
{ echo "$me: cannot create a temporary directory in $TMPDIR" >&2 ; exit 1 ; } ;
|
||||
dummy=$tmp/dummy ;
|
||||
tmpfiles="$dummy.c $dummy.o $dummy.rel $dummy" ;
|
||||
case $CC_FOR_BUILD,$HOST_CC,$CC in
|
||||
,,) echo "int x;" > $dummy.c ;
|
||||
for c in cc gcc c89 c99 ; do
|
||||
if ($c -c -o $dummy.o $dummy.c) >/dev/null 2>&1 ; then
|
||||
CC_FOR_BUILD="$c"; break ;
|
||||
fi ;
|
||||
done ;
|
||||
rm -f $dummy.c $dummy.o $dummy.rel ;
|
||||
if test x"$CC_FOR_BUILD" = x ; then
|
||||
CC_FOR_BUILD=no_compiler_found ;
|
||||
fi
|
||||
;;
|
||||
,,*) CC_FOR_BUILD=$CC ;;
|
||||
,*,*) CC_FOR_BUILD=$HOST_CC ;;
|
||||
esac'
|
||||
esac ;'
|
||||
|
||||
# This is needed to find uname on a Pyramid OSx when run in the BSD universe.
|
||||
# (ghazi@noc.rutgers.edu 1994-08-24)
|
||||
@@ -127,29 +140,30 @@ UNAME_VERSION=`(uname -v) 2>/dev/null` || UNAME_VERSION=unknown
|
||||
|
||||
case "${UNAME_MACHINE}:${UNAME_SYSTEM}:${UNAME_RELEASE}:${UNAME_VERSION}" in
|
||||
*:NetBSD:*:*)
|
||||
# Netbsd (nbsd) targets should (where applicable) match one or
|
||||
# NetBSD (nbsd) targets should (where applicable) match one or
|
||||
# more of the tupples: *-*-netbsdelf*, *-*-netbsdaout*,
|
||||
# *-*-netbsdecoff* and *-*-netbsd*. For targets that recently
|
||||
# switched to ELF, *-*-netbsd* would select the old
|
||||
# object file format. This provides both forward
|
||||
# compatibility and a consistent mechanism for selecting the
|
||||
# object file format.
|
||||
# Determine the machine/vendor (is the vendor relevant).
|
||||
case "${UNAME_MACHINE}" in
|
||||
amiga) machine=m68k-unknown ;;
|
||||
arm32) machine=arm-unknown ;;
|
||||
atari*) machine=m68k-atari ;;
|
||||
sun3*) machine=m68k-sun ;;
|
||||
mac68k) machine=m68k-apple ;;
|
||||
macppc) machine=powerpc-apple ;;
|
||||
hp3[0-9][05]) machine=m68k-hp ;;
|
||||
ibmrt|romp-ibm) machine=romp-ibm ;;
|
||||
*) machine=${UNAME_MACHINE}-unknown ;;
|
||||
#
|
||||
# Note: NetBSD doesn't particularly care about the vendor
|
||||
# portion of the name. We always set it to "unknown".
|
||||
sysctl="sysctl -n hw.machine_arch"
|
||||
UNAME_MACHINE_ARCH=`(/sbin/$sysctl 2>/dev/null || \
|
||||
/usr/sbin/$sysctl 2>/dev/null || echo unknown)`
|
||||
case "${UNAME_MACHINE_ARCH}" in
|
||||
armeb) machine=armeb-unknown ;;
|
||||
arm*) machine=arm-unknown ;;
|
||||
sh3el) machine=shl-unknown ;;
|
||||
sh3eb) machine=sh-unknown ;;
|
||||
*) machine=${UNAME_MACHINE_ARCH}-unknown ;;
|
||||
esac
|
||||
# The Operating System including object format, if it has switched
|
||||
# to ELF recently, or will in the future.
|
||||
case "${UNAME_MACHINE}" in
|
||||
i386|sparc|amiga|arm*|hp300|mvme68k|vax|atari|luna68k|mac68k|news68k|next68k|pc532|sun3*|x68k)
|
||||
case "${UNAME_MACHINE_ARCH}" in
|
||||
arm*|i386|m68k|ns32k|sh3*|sparc|vax)
|
||||
eval $set_cc_for_build
|
||||
if echo __ELF__ | $CC_FOR_BUILD -E - 2>/dev/null \
|
||||
| grep __ELF__ >/dev/null
|
||||
@@ -166,75 +180,112 @@ case "${UNAME_MACHINE}:${UNAME_SYSTEM}:${UNAME_RELEASE}:${UNAME_VERSION}" in
|
||||
;;
|
||||
esac
|
||||
# The OS release
|
||||
release=`echo ${UNAME_RELEASE}|sed -e 's/[-_].*/\./'`
|
||||
# Debian GNU/NetBSD machines have a different userland, and
|
||||
# thus, need a distinct triplet. However, they do not need
|
||||
# kernel version information, so it can be replaced with a
|
||||
# suitable tag, in the style of linux-gnu.
|
||||
case "${UNAME_VERSION}" in
|
||||
Debian*)
|
||||
release='-gnu'
|
||||
;;
|
||||
*)
|
||||
release=`echo ${UNAME_RELEASE}|sed -e 's/[-_].*/\./'`
|
||||
;;
|
||||
esac
|
||||
# Since CPU_TYPE-MANUFACTURER-KERNEL-OPERATING_SYSTEM:
|
||||
# contains redundant information, the shorter form:
|
||||
# CPU_TYPE-MANUFACTURER-OPERATING_SYSTEM is used.
|
||||
echo "${machine}-${os}${release}"
|
||||
exit 0 ;;
|
||||
amiga:OpenBSD:*:*)
|
||||
echo m68k-unknown-openbsd${UNAME_RELEASE}
|
||||
exit 0 ;;
|
||||
arc:OpenBSD:*:*)
|
||||
echo mipsel-unknown-openbsd${UNAME_RELEASE}
|
||||
exit 0 ;;
|
||||
hp300:OpenBSD:*:*)
|
||||
echo m68k-unknown-openbsd${UNAME_RELEASE}
|
||||
exit 0 ;;
|
||||
mac68k:OpenBSD:*:*)
|
||||
echo m68k-unknown-openbsd${UNAME_RELEASE}
|
||||
exit 0 ;;
|
||||
macppc:OpenBSD:*:*)
|
||||
echo powerpc-unknown-openbsd${UNAME_RELEASE}
|
||||
exit 0 ;;
|
||||
mvme68k:OpenBSD:*:*)
|
||||
echo m68k-unknown-openbsd${UNAME_RELEASE}
|
||||
exit 0 ;;
|
||||
mvme88k:OpenBSD:*:*)
|
||||
echo m88k-unknown-openbsd${UNAME_RELEASE}
|
||||
exit 0 ;;
|
||||
mvmeppc:OpenBSD:*:*)
|
||||
echo powerpc-unknown-openbsd${UNAME_RELEASE}
|
||||
exit 0 ;;
|
||||
pmax:OpenBSD:*:*)
|
||||
echo mipsel-unknown-openbsd${UNAME_RELEASE}
|
||||
exit 0 ;;
|
||||
sgi:OpenBSD:*:*)
|
||||
echo mipseb-unknown-openbsd${UNAME_RELEASE}
|
||||
exit 0 ;;
|
||||
sun3:OpenBSD:*:*)
|
||||
echo m68k-unknown-openbsd${UNAME_RELEASE}
|
||||
exit 0 ;;
|
||||
wgrisc:OpenBSD:*:*)
|
||||
echo mipsel-unknown-openbsd${UNAME_RELEASE}
|
||||
exit 0 ;;
|
||||
*:OpenBSD:*:*)
|
||||
echo ${UNAME_MACHINE}-unknown-openbsd${UNAME_RELEASE}
|
||||
exit 0 ;;
|
||||
alpha:OSF1:*:*)
|
||||
if test $UNAME_RELEASE = "V4.0"; then
|
||||
UNAME_RELEASE=`/usr/sbin/sizer -v | awk '{print $3}'`
|
||||
fi
|
||||
# According to Compaq, /usr/sbin/psrinfo has been available on
|
||||
# OSF/1 and Tru64 systems produced since 1995. I hope that
|
||||
# covers most systems running today. This code pipes the CPU
|
||||
# types through head -n 1, so we only detect the type of CPU 0.
|
||||
ALPHA_CPU_TYPE=`/usr/sbin/psrinfo -v | sed -n -e 's/^ The alpha \(.*\) processor.*$/\1/p' | head -n 1`
|
||||
case "$ALPHA_CPU_TYPE" in
|
||||
"EV4 (21064)")
|
||||
UNAME_MACHINE="alpha" ;;
|
||||
"EV4.5 (21064)")
|
||||
UNAME_MACHINE="alpha" ;;
|
||||
"LCA4 (21066/21068)")
|
||||
UNAME_MACHINE="alpha" ;;
|
||||
"EV5 (21164)")
|
||||
UNAME_MACHINE="alphaev5" ;;
|
||||
"EV5.6 (21164A)")
|
||||
UNAME_MACHINE="alphaev56" ;;
|
||||
"EV5.6 (21164PC)")
|
||||
UNAME_MACHINE="alphapca56" ;;
|
||||
"EV5.7 (21164PC)")
|
||||
UNAME_MACHINE="alphapca57" ;;
|
||||
"EV6 (21264)")
|
||||
UNAME_MACHINE="alphaev6" ;;
|
||||
"EV6.7 (21264A)")
|
||||
UNAME_MACHINE="alphaev67" ;;
|
||||
"EV6.8CB (21264C)")
|
||||
UNAME_MACHINE="alphaev68" ;;
|
||||
"EV6.8AL (21264B)")
|
||||
UNAME_MACHINE="alphaev68" ;;
|
||||
"EV6.8CX (21264D)")
|
||||
UNAME_MACHINE="alphaev68" ;;
|
||||
"EV6.9A (21264/EV69A)")
|
||||
UNAME_MACHINE="alphaev69" ;;
|
||||
"EV7 (21364)")
|
||||
UNAME_MACHINE="alphaev7" ;;
|
||||
"EV7.9 (21364A)")
|
||||
UNAME_MACHINE="alphaev79" ;;
|
||||
esac
|
||||
# A Vn.n version is a released version.
|
||||
# A Tn.n version is a released field test version.
|
||||
# A Xn.n version is an unreleased experimental baselevel.
|
||||
# 1.2 uses "1.2" for uname -r.
|
||||
cat <<EOF >$dummy.s
|
||||
.data
|
||||
\$Lformat:
|
||||
.byte 37,100,45,37,120,10,0 # "%d-%x\n"
|
||||
|
||||
.text
|
||||
.globl main
|
||||
.align 4
|
||||
.ent main
|
||||
main:
|
||||
.frame \$30,16,\$26,0
|
||||
ldgp \$29,0(\$27)
|
||||
.prologue 1
|
||||
.long 0x47e03d80 # implver \$0
|
||||
lda \$2,-1
|
||||
.long 0x47e20c21 # amask \$2,\$1
|
||||
lda \$16,\$Lformat
|
||||
mov \$0,\$17
|
||||
not \$1,\$18
|
||||
jsr \$26,printf
|
||||
ldgp \$29,0(\$26)
|
||||
mov 0,\$16
|
||||
jsr \$26,exit
|
||||
.end main
|
||||
EOF
|
||||
eval $set_cc_for_build
|
||||
$CC_FOR_BUILD $dummy.s -o $dummy 2>/dev/null
|
||||
if test "$?" = 0 ; then
|
||||
case `./$dummy` in
|
||||
0-0)
|
||||
UNAME_MACHINE="alpha"
|
||||
;;
|
||||
1-0)
|
||||
UNAME_MACHINE="alphaev5"
|
||||
;;
|
||||
1-1)
|
||||
UNAME_MACHINE="alphaev56"
|
||||
;;
|
||||
1-101)
|
||||
UNAME_MACHINE="alphapca56"
|
||||
;;
|
||||
2-303)
|
||||
UNAME_MACHINE="alphaev6"
|
||||
;;
|
||||
2-307)
|
||||
UNAME_MACHINE="alphaev67"
|
||||
;;
|
||||
2-1307)
|
||||
UNAME_MACHINE="alphaev68"
|
||||
;;
|
||||
esac
|
||||
fi
|
||||
rm -f $dummy.s $dummy
|
||||
echo ${UNAME_MACHINE}-dec-osf`echo ${UNAME_RELEASE} | sed -e 's/^[VTX]//' | tr 'ABCDEFGHIJKLMNOPQRSTUVWXYZ' 'abcdefghijklmnopqrstuvwxyz'`
|
||||
exit 0 ;;
|
||||
Alpha*:OpenVMS:*:*)
|
||||
echo alpha-hp-vms
|
||||
exit 0 ;;
|
||||
Alpha\ *:Windows_NT*:*)
|
||||
# How do we know it's Interix rather than the generic POSIX subsystem?
|
||||
# Should we change UNAME_MACHINE based on the output of uname instead
|
||||
@@ -247,29 +298,11 @@ EOF
|
||||
Amiga*:UNIX_System_V:4.0:*)
|
||||
echo m68k-unknown-sysv4
|
||||
exit 0;;
|
||||
amiga:OpenBSD:*:*)
|
||||
echo m68k-unknown-openbsd${UNAME_RELEASE}
|
||||
exit 0 ;;
|
||||
*:[Aa]miga[Oo][Ss]:*:*)
|
||||
echo ${UNAME_MACHINE}-unknown-amigaos
|
||||
exit 0 ;;
|
||||
arc64:OpenBSD:*:*)
|
||||
echo mips64el-unknown-openbsd${UNAME_RELEASE}
|
||||
exit 0 ;;
|
||||
arc:OpenBSD:*:*)
|
||||
echo mipsel-unknown-openbsd${UNAME_RELEASE}
|
||||
exit 0 ;;
|
||||
hkmips:OpenBSD:*:*)
|
||||
echo mips-unknown-openbsd${UNAME_RELEASE}
|
||||
exit 0 ;;
|
||||
pmax:OpenBSD:*:*)
|
||||
echo mipsel-unknown-openbsd${UNAME_RELEASE}
|
||||
exit 0 ;;
|
||||
sgi:OpenBSD:*:*)
|
||||
echo mips-unknown-openbsd${UNAME_RELEASE}
|
||||
exit 0 ;;
|
||||
wgrisc:OpenBSD:*:*)
|
||||
echo mipsel-unknown-openbsd${UNAME_RELEASE}
|
||||
*:[Mm]orph[Oo][Ss]:*:*)
|
||||
echo ${UNAME_MACHINE}-unknown-morphos
|
||||
exit 0 ;;
|
||||
*:OS/390:*:*)
|
||||
echo i370-ibm-openedition
|
||||
@@ -291,6 +324,13 @@ EOF
|
||||
NILE*:*:*:dcosx)
|
||||
echo pyramid-pyramid-svr4
|
||||
exit 0 ;;
|
||||
DRS?6000:unix:4.0:6*)
|
||||
echo sparc-icl-nx6
|
||||
exit 0 ;;
|
||||
DRS?6000:UNIX_SV:4.2*:7*)
|
||||
case `/usr/bin/uname -p` in
|
||||
sparc) echo sparc-icl-nx7 && exit 0 ;;
|
||||
esac ;;
|
||||
sun4H:SunOS:5.*:*)
|
||||
echo sparc-hal-solaris2`echo ${UNAME_RELEASE}|sed -e 's/[^.]*//'`
|
||||
exit 0 ;;
|
||||
@@ -319,7 +359,7 @@ EOF
|
||||
echo m68k-sun-sunos${UNAME_RELEASE}
|
||||
exit 0 ;;
|
||||
sun*:*:4.2BSD:*)
|
||||
UNAME_RELEASE=`(head -1 /etc/motd | awk '{print substr($5,1,3)}') 2>/dev/null`
|
||||
UNAME_RELEASE=`(sed 1q /etc/motd | awk '{print substr($5,1,3)}') 2>/dev/null`
|
||||
test "x${UNAME_RELEASE}" = "x" && UNAME_RELEASE=3
|
||||
case "`/bin/arch`" in
|
||||
sun3)
|
||||
@@ -333,12 +373,6 @@ EOF
|
||||
aushp:SunOS:*:*)
|
||||
echo sparc-auspex-sunos${UNAME_RELEASE}
|
||||
exit 0 ;;
|
||||
sparc*:NetBSD:*)
|
||||
echo `uname -p`-unknown-netbsd${UNAME_RELEASE}
|
||||
exit 0 ;;
|
||||
atari*:OpenBSD:*:*)
|
||||
echo m68k-unknown-openbsd${UNAME_RELEASE}
|
||||
exit 0 ;;
|
||||
# The situation for MiNT is a little confusing. The machine name
|
||||
# can be virtually everything (everything which is not
|
||||
# "atarist" or "atariste" at least should have a processor
|
||||
@@ -365,18 +399,6 @@ EOF
|
||||
*:*MiNT:*:* | *:*mint:*:* | *:*TOS:*:*)
|
||||
echo m68k-unknown-mint${UNAME_RELEASE}
|
||||
exit 0 ;;
|
||||
sun3*:OpenBSD:*:*)
|
||||
echo m68k-unknown-openbsd${UNAME_RELEASE}
|
||||
exit 0 ;;
|
||||
mac68k:OpenBSD:*:*)
|
||||
echo m68k-unknown-openbsd${UNAME_RELEASE}
|
||||
exit 0 ;;
|
||||
mvme68k:OpenBSD:*:*)
|
||||
echo m68k-unknown-openbsd${UNAME_RELEASE}
|
||||
exit 0 ;;
|
||||
mvme88k:OpenBSD:*:*)
|
||||
echo m88k-unknown-openbsd${UNAME_RELEASE}
|
||||
exit 0 ;;
|
||||
powerpc:machten:*:*)
|
||||
echo powerpc-apple-machten${UNAME_RELEASE}
|
||||
exit 0 ;;
|
||||
@@ -415,15 +437,20 @@ EOF
|
||||
exit (-1);
|
||||
}
|
||||
EOF
|
||||
$CC_FOR_BUILD $dummy.c -o $dummy \
|
||||
&& ./$dummy `echo "${UNAME_RELEASE}" | sed -n 's/\([0-9]*\).*/\1/p'` \
|
||||
&& rm -f $dummy.c $dummy && exit 0
|
||||
rm -f $dummy.c $dummy
|
||||
$CC_FOR_BUILD -o $dummy $dummy.c \
|
||||
&& $dummy `echo "${UNAME_RELEASE}" | sed -n 's/\([0-9]*\).*/\1/p'` \
|
||||
&& exit 0
|
||||
echo mips-mips-riscos${UNAME_RELEASE}
|
||||
exit 0 ;;
|
||||
Motorola:PowerMAX_OS:*:*)
|
||||
echo powerpc-motorola-powermax
|
||||
exit 0 ;;
|
||||
Motorola:*:4.3:PL8-*)
|
||||
echo powerpc-harris-powermax
|
||||
exit 0 ;;
|
||||
Night_Hawk:*:*:PowerMAX_OS | Synergy:PowerMAX_OS:*:*)
|
||||
echo powerpc-harris-powermax
|
||||
exit 0 ;;
|
||||
Night_Hawk:Power_UNIX:*:*)
|
||||
echo powerpc-harris-powerunix
|
||||
exit 0 ;;
|
||||
@@ -496,8 +523,7 @@ EOF
|
||||
exit(0);
|
||||
}
|
||||
EOF
|
||||
$CC_FOR_BUILD $dummy.c -o $dummy && ./$dummy && rm -f $dummy.c $dummy && exit 0
|
||||
rm -f $dummy.c $dummy
|
||||
$CC_FOR_BUILD -o $dummy $dummy.c && $dummy && exit 0
|
||||
echo rs6000-ibm-aix3.2.5
|
||||
elif grep bos324 /usr/include/stdio.h >/dev/null 2>&1; then
|
||||
echo rs6000-ibm-aix3.2.4
|
||||
@@ -506,7 +532,7 @@ EOF
|
||||
fi
|
||||
exit 0 ;;
|
||||
*:AIX:*:[45])
|
||||
IBM_CPU_ID=`/usr/sbin/lsdev -C -c processor -S available | head -1 | awk '{ print $1 }'`
|
||||
IBM_CPU_ID=`/usr/sbin/lsdev -C -c processor -S available | sed 1q | awk '{ print $1 }'`
|
||||
if /usr/sbin/lsattr -El ${IBM_CPU_ID} | grep ' POWER' >/dev/null 2>&1; then
|
||||
IBM_ARCH=rs6000
|
||||
else
|
||||
@@ -546,10 +572,8 @@ EOF
|
||||
9000/31? ) HP_ARCH=m68000 ;;
|
||||
9000/[34]?? ) HP_ARCH=m68k ;;
|
||||
9000/[678][0-9][0-9])
|
||||
case "${HPUX_REV}" in
|
||||
11.[0-9][0-9])
|
||||
if [ -x /usr/bin/getconf ]; then
|
||||
sc_cpu_version=`/usr/bin/getconf SC_CPU_VERSION 2>/dev/null`
|
||||
if [ -x /usr/bin/getconf ]; then
|
||||
sc_cpu_version=`/usr/bin/getconf SC_CPU_VERSION 2>/dev/null`
|
||||
sc_kernel_bits=`/usr/bin/getconf SC_KERNEL_BITS 2>/dev/null`
|
||||
case "${sc_cpu_version}" in
|
||||
523) HP_ARCH="hppa1.0" ;; # CPU_PA_RISC1_0
|
||||
@@ -558,13 +582,13 @@ EOF
|
||||
case "${sc_kernel_bits}" in
|
||||
32) HP_ARCH="hppa2.0n" ;;
|
||||
64) HP_ARCH="hppa2.0w" ;;
|
||||
'') HP_ARCH="hppa2.0" ;; # HP-UX 10.20
|
||||
esac ;;
|
||||
esac
|
||||
fi ;;
|
||||
esac
|
||||
if [ "${HP_ARCH}" = "" ]; then
|
||||
eval $set_cc_for_build
|
||||
sed 's/^ //' << EOF >$dummy.c
|
||||
fi
|
||||
if [ "${HP_ARCH}" = "" ]; then
|
||||
eval $set_cc_for_build
|
||||
sed 's/^ //' << EOF >$dummy.c
|
||||
|
||||
#define _HPUX_SOURCE
|
||||
#include <stdlib.h>
|
||||
@@ -597,11 +621,21 @@ EOF
|
||||
exit (0);
|
||||
}
|
||||
EOF
|
||||
(CCOPTS= $CC_FOR_BUILD $dummy.c -o $dummy 2>/dev/null ) && HP_ARCH=`./$dummy`
|
||||
if test -z "$HP_ARCH"; then HP_ARCH=hppa; fi
|
||||
rm -f $dummy.c $dummy
|
||||
fi ;;
|
||||
(CCOPTS= $CC_FOR_BUILD -o $dummy $dummy.c 2>/dev/null) && HP_ARCH=`$dummy`
|
||||
test -z "$HP_ARCH" && HP_ARCH=hppa
|
||||
fi ;;
|
||||
esac
|
||||
if [ ${HP_ARCH} = "hppa2.0w" ]
|
||||
then
|
||||
# avoid double evaluation of $set_cc_for_build
|
||||
test -n "$CC_FOR_BUILD" || eval $set_cc_for_build
|
||||
if echo __LP64__ | (CCOPTS= $CC_FOR_BUILD -E -) | grep __LP64__ >/dev/null
|
||||
then
|
||||
HP_ARCH="hppa2.0w"
|
||||
else
|
||||
HP_ARCH="hppa64"
|
||||
fi
|
||||
fi
|
||||
echo ${HP_ARCH}-hp-hpux${HPUX_REV}
|
||||
exit 0 ;;
|
||||
ia64:HP-UX:*:*)
|
||||
@@ -635,8 +669,7 @@ EOF
|
||||
exit (0);
|
||||
}
|
||||
EOF
|
||||
$CC_FOR_BUILD $dummy.c -o $dummy && ./$dummy && rm -f $dummy.c $dummy && exit 0
|
||||
rm -f $dummy.c $dummy
|
||||
$CC_FOR_BUILD -o $dummy $dummy.c && $dummy && exit 0
|
||||
echo unknown-hitachi-hiuxwe2
|
||||
exit 0 ;;
|
||||
9000/7??:4.3bsd:*:* | 9000/8?[79]:4.3bsd:*:* )
|
||||
@@ -664,9 +697,6 @@ EOF
|
||||
parisc*:Lites*:*:*)
|
||||
echo hppa1.1-hp-lites
|
||||
exit 0 ;;
|
||||
hppa*:OpenBSD:*:*)
|
||||
echo hppa-unknown-openbsd
|
||||
exit 0 ;;
|
||||
C1*:ConvexOS:*:* | convex:ConvexOS:C1*:*)
|
||||
echo c1-convex-bsd
|
||||
exit 0 ;;
|
||||
@@ -685,9 +715,6 @@ EOF
|
||||
C4*:ConvexOS:*:* | convex:ConvexOS:C4*:*)
|
||||
echo c4-convex-bsd
|
||||
exit 0 ;;
|
||||
CRAY*X-MP:*:*:*)
|
||||
echo xmp-cray-unicos
|
||||
exit 0 ;;
|
||||
CRAY*Y-MP:*:*:*)
|
||||
echo ymp-cray-unicos${UNAME_RELEASE} | sed -e 's/\.[^.]*$/.X/'
|
||||
exit 0 ;;
|
||||
@@ -700,27 +727,21 @@ EOF
|
||||
CRAY*TS:*:*:*)
|
||||
echo t90-cray-unicos${UNAME_RELEASE} | sed -e 's/\.[^.]*$/.X/'
|
||||
exit 0 ;;
|
||||
CRAY*T3D:*:*:*)
|
||||
echo alpha-cray-unicosmk${UNAME_RELEASE} | sed -e 's/\.[^.]*$/.X/'
|
||||
exit 0 ;;
|
||||
CRAY*T3E:*:*:*)
|
||||
echo alphaev5-cray-unicosmk${UNAME_RELEASE} | sed -e 's/\.[^.]*$/.X/'
|
||||
exit 0 ;;
|
||||
CRAY*SV1:*:*:*)
|
||||
echo sv1-cray-unicos${UNAME_RELEASE} | sed -e 's/\.[^.]*$/.X/'
|
||||
exit 0 ;;
|
||||
CRAY-2:*:*:*)
|
||||
echo cray2-cray-unicos
|
||||
exit 0 ;;
|
||||
*:UNICOS/mp:*:*)
|
||||
echo nv1-cray-unicosmp${UNAME_RELEASE} | sed -e 's/\.[^.]*$/.X/'
|
||||
exit 0 ;;
|
||||
F30[01]:UNIX_System_V:*:* | F700:UNIX_System_V:*:*)
|
||||
FUJITSU_PROC=`uname -m | tr 'ABCDEFGHIJKLMNOPQRSTUVWXYZ' 'abcdefghijklmnopqrstuvwxyz'`
|
||||
FUJITSU_SYS=`uname -p | tr 'ABCDEFGHIJKLMNOPQRSTUVWXYZ' 'abcdefghijklmnopqrstuvwxyz' | sed -e 's/\///'`
|
||||
FUJITSU_REL=`echo ${UNAME_RELEASE} | sed -e 's/ /_/'`
|
||||
echo "${FUJITSU_PROC}-fujitsu-${FUJITSU_SYS}${FUJITSU_REL}"
|
||||
exit 0 ;;
|
||||
hp300:OpenBSD:*:*)
|
||||
echo m68k-unknown-openbsd${UNAME_RELEASE}
|
||||
exit 0 ;;
|
||||
i*86:BSD/386:*:* | i*86:BSD/OS:*:* | *:Ascend\ Embedded/OS:*:*)
|
||||
echo ${UNAME_MACHINE}-pc-bsdi${UNAME_RELEASE}
|
||||
exit 0 ;;
|
||||
@@ -730,11 +751,19 @@ EOF
|
||||
*:BSD/OS:*:*)
|
||||
echo ${UNAME_MACHINE}-unknown-bsdi${UNAME_RELEASE}
|
||||
exit 0 ;;
|
||||
*:FreeBSD:*:*)
|
||||
echo ${UNAME_MACHINE}-unknown-freebsd`echo ${UNAME_RELEASE}|sed -e 's/[-(].*//'`
|
||||
exit 0 ;;
|
||||
*:OpenBSD:*:*)
|
||||
echo ${UNAME_MACHINE}-unknown-openbsd`echo ${UNAME_RELEASE}|sed -e 's/[-_].*/\./'`
|
||||
*:FreeBSD:*:*|*:GNU/FreeBSD:*:*)
|
||||
# Determine whether the default compiler uses glibc.
|
||||
eval $set_cc_for_build
|
||||
sed 's/^ //' << EOF >$dummy.c
|
||||
#include <features.h>
|
||||
#if __GLIBC__ >= 2
|
||||
LIBC=gnu
|
||||
#else
|
||||
LIBC=
|
||||
#endif
|
||||
EOF
|
||||
eval `$CC_FOR_BUILD -E $dummy.c 2>/dev/null | grep ^LIBC=`
|
||||
echo ${UNAME_MACHINE}-unknown-freebsd`echo ${UNAME_RELEASE}|sed -e 's/[-(].*//'`${LIBC:+-$LIBC}
|
||||
exit 0 ;;
|
||||
i*:CYGWIN*:*)
|
||||
echo ${UNAME_MACHINE}-pc-cygwin
|
||||
@@ -745,11 +774,17 @@ EOF
|
||||
i*:PW*:*)
|
||||
echo ${UNAME_MACHINE}-pc-pw32
|
||||
exit 0 ;;
|
||||
x86:Interix*:[34]*)
|
||||
echo i586-pc-interix${UNAME_RELEASE}|sed -e 's/\..*//'
|
||||
exit 0 ;;
|
||||
[345]86:Windows_95:* | [345]86:Windows_98:* | [345]86:Windows_NT:*)
|
||||
echo i${UNAME_MACHINE}-pc-mks
|
||||
exit 0 ;;
|
||||
i*:Windows_NT*:* | Pentium*:Windows_NT*:*)
|
||||
# How do we know it's Interix rather than the generic POSIX subsystem?
|
||||
# It also conflicts with pre-2.0 versions of AT&T UWIN. Should we
|
||||
# UNAME_MACHINE based on the output of uname instead of i386?
|
||||
echo i386-pc-interix
|
||||
echo i586-pc-interix
|
||||
exit 0 ;;
|
||||
i*:UWIN*:*)
|
||||
echo ${UNAME_MACHINE}-pc-uwin
|
||||
@@ -769,17 +804,52 @@ EOF
|
||||
arm*:Linux:*:*)
|
||||
echo ${UNAME_MACHINE}-unknown-linux-gnu
|
||||
exit 0 ;;
|
||||
cris:Linux:*:*)
|
||||
echo cris-axis-linux-gnu
|
||||
exit 0 ;;
|
||||
ia64:Linux:*:*)
|
||||
echo ${UNAME_MACHINE}-unknown-linux
|
||||
echo ${UNAME_MACHINE}-unknown-linux-gnu
|
||||
exit 0 ;;
|
||||
m68*:Linux:*:*)
|
||||
echo ${UNAME_MACHINE}-unknown-linux-gnu
|
||||
exit 0 ;;
|
||||
mips:Linux:*:*)
|
||||
case `sed -n '/^byte/s/^.*: \(.*\) endian/\1/p' < /proc/cpuinfo` in
|
||||
big) echo mips-unknown-linux-gnu && exit 0 ;;
|
||||
little) echo mipsel-unknown-linux-gnu && exit 0 ;;
|
||||
esac
|
||||
eval $set_cc_for_build
|
||||
sed 's/^ //' << EOF >$dummy.c
|
||||
#undef CPU
|
||||
#undef mips
|
||||
#undef mipsel
|
||||
#if defined(__MIPSEL__) || defined(__MIPSEL) || defined(_MIPSEL) || defined(MIPSEL)
|
||||
CPU=mipsel
|
||||
#else
|
||||
#if defined(__MIPSEB__) || defined(__MIPSEB) || defined(_MIPSEB) || defined(MIPSEB)
|
||||
CPU=mips
|
||||
#else
|
||||
CPU=
|
||||
#endif
|
||||
#endif
|
||||
EOF
|
||||
eval `$CC_FOR_BUILD -E $dummy.c 2>/dev/null | grep ^CPU=`
|
||||
test x"${CPU}" != x && echo "${CPU}-unknown-linux-gnu" && exit 0
|
||||
;;
|
||||
mips64:Linux:*:*)
|
||||
eval $set_cc_for_build
|
||||
sed 's/^ //' << EOF >$dummy.c
|
||||
#undef CPU
|
||||
#undef mips64
|
||||
#undef mips64el
|
||||
#if defined(__MIPSEL__) || defined(__MIPSEL) || defined(_MIPSEL) || defined(MIPSEL)
|
||||
CPU=mips64el
|
||||
#else
|
||||
#if defined(__MIPSEB__) || defined(__MIPSEB) || defined(_MIPSEB) || defined(MIPSEB)
|
||||
CPU=mips64
|
||||
#else
|
||||
CPU=
|
||||
#endif
|
||||
#endif
|
||||
EOF
|
||||
eval `$CC_FOR_BUILD -E $dummy.c 2>/dev/null | grep ^CPU=`
|
||||
test x"${CPU}" != x && echo "${CPU}-unknown-linux-gnu" && exit 0
|
||||
;;
|
||||
ppc:Linux:*:*)
|
||||
echo powerpc-unknown-linux-gnu
|
||||
@@ -815,6 +885,9 @@ EOF
|
||||
s390:Linux:*:* | s390x:Linux:*:*)
|
||||
echo ${UNAME_MACHINE}-ibm-linux
|
||||
exit 0 ;;
|
||||
sh64*:Linux:*:*)
|
||||
echo ${UNAME_MACHINE}-unknown-linux-gnu
|
||||
exit 0 ;;
|
||||
sh*:Linux:*:*)
|
||||
echo ${UNAME_MACHINE}-unknown-linux-gnu
|
||||
exit 0 ;;
|
||||
@@ -828,7 +901,8 @@ EOF
|
||||
# The BFD linker knows what the default object file format is, so
|
||||
# first see if it will tell us. cd to the root directory to prevent
|
||||
# problems with other programs or directories called `ld' in the path.
|
||||
ld_supported_targets=`cd /; ld --help 2>&1 \
|
||||
# Set LC_ALL=C to ensure ld outputs messages in English.
|
||||
ld_supported_targets=`cd /; LC_ALL=C ld --help 2>&1 \
|
||||
| sed -ne '/supported targets:/!d
|
||||
s/[ ][ ]*/ /g
|
||||
s/.*supported targets: *//
|
||||
@@ -840,7 +914,7 @@ EOF
|
||||
;;
|
||||
a.out-i386-linux)
|
||||
echo "${UNAME_MACHINE}-pc-linux-gnuaout"
|
||||
exit 0 ;;
|
||||
exit 0 ;;
|
||||
coff-i386)
|
||||
echo "${UNAME_MACHINE}-pc-linux-gnucoff"
|
||||
exit 0 ;;
|
||||
@@ -852,32 +926,28 @@ EOF
|
||||
esac
|
||||
# Determine whether the default compiler is a.out or elf
|
||||
eval $set_cc_for_build
|
||||
cat >$dummy.c <<EOF
|
||||
#include <features.h>
|
||||
#ifdef __cplusplus
|
||||
#include <stdio.h> /* for printf() prototype */
|
||||
int main (int argc, char *argv[]) {
|
||||
#else
|
||||
int main (argc, argv) int argc; char *argv[]; {
|
||||
#endif
|
||||
#ifdef __ELF__
|
||||
# ifdef __GLIBC__
|
||||
# if __GLIBC__ >= 2
|
||||
printf ("%s-pc-linux-gnu\n", argv[1]);
|
||||
# else
|
||||
printf ("%s-pc-linux-gnulibc1\n", argv[1]);
|
||||
# endif
|
||||
# else
|
||||
printf ("%s-pc-linux-gnulibc1\n", argv[1]);
|
||||
# endif
|
||||
#else
|
||||
printf ("%s-pc-linux-gnuaout\n", argv[1]);
|
||||
#endif
|
||||
return 0;
|
||||
}
|
||||
sed 's/^ //' << EOF >$dummy.c
|
||||
#include <features.h>
|
||||
#ifdef __ELF__
|
||||
# ifdef __GLIBC__
|
||||
# if __GLIBC__ >= 2
|
||||
LIBC=gnu
|
||||
# else
|
||||
LIBC=gnulibc1
|
||||
# endif
|
||||
# else
|
||||
LIBC=gnulibc1
|
||||
# endif
|
||||
#else
|
||||
#ifdef __INTEL_COMPILER
|
||||
LIBC=gnu
|
||||
#else
|
||||
LIBC=gnuaout
|
||||
#endif
|
||||
#endif
|
||||
EOF
|
||||
$CC_FOR_BUILD $dummy.c -o $dummy 2>/dev/null && ./$dummy "${UNAME_MACHINE}" && rm -f $dummy.c $dummy && exit 0
|
||||
rm -f $dummy.c $dummy
|
||||
eval `$CC_FOR_BUILD -E $dummy.c 2>/dev/null | grep ^LIBC=`
|
||||
test x"${LIBC}" != x && echo "${UNAME_MACHINE}-pc-linux-${LIBC}" && exit 0
|
||||
test x"${TENTATIVE}" != x && echo "${TENTATIVE}" && exit 0
|
||||
;;
|
||||
i*86:DYNIX/ptx:4*:*)
|
||||
@@ -894,6 +964,23 @@ EOF
|
||||
# Use sysv4.2uw... so that sysv4* matches it.
|
||||
echo ${UNAME_MACHINE}-pc-sysv4.2uw${UNAME_VERSION}
|
||||
exit 0 ;;
|
||||
i*86:OS/2:*:*)
|
||||
# If we were able to find `uname', then EMX Unix compatibility
|
||||
# is probably installed.
|
||||
echo ${UNAME_MACHINE}-pc-os2-emx
|
||||
exit 0 ;;
|
||||
i*86:XTS-300:*:STOP)
|
||||
echo ${UNAME_MACHINE}-unknown-stop
|
||||
exit 0 ;;
|
||||
i*86:atheos:*:*)
|
||||
echo ${UNAME_MACHINE}-unknown-atheos
|
||||
exit 0 ;;
|
||||
i*86:LynxOS:2.*:* | i*86:LynxOS:3.[01]*:* | i*86:LynxOS:4.0*:*)
|
||||
echo i386-unknown-lynxos${UNAME_RELEASE}
|
||||
exit 0 ;;
|
||||
i*86:*DOS:*:*)
|
||||
echo ${UNAME_MACHINE}-pc-msdosdjgpp
|
||||
exit 0 ;;
|
||||
i*86:*:4.*:* | i*86:SYSTEM_V:4.*:*)
|
||||
UNAME_REL=`echo ${UNAME_RELEASE} | sed 's/\/MP$//'`
|
||||
if grep Novell /usr/include/link.h >/dev/null 2>/dev/null; then
|
||||
@@ -915,22 +1002,19 @@ EOF
|
||||
UNAME_REL=`sed -n 's/.*Version //p' </usr/options/cb.name`
|
||||
echo ${UNAME_MACHINE}-pc-isc$UNAME_REL
|
||||
elif /bin/uname -X 2>/dev/null >/dev/null ; then
|
||||
UNAME_REL=`(/bin/uname -X|egrep Release|sed -e 's/.*= //')`
|
||||
(/bin/uname -X|egrep i80486 >/dev/null) && UNAME_MACHINE=i486
|
||||
(/bin/uname -X|egrep '^Machine.*Pentium' >/dev/null) \
|
||||
UNAME_REL=`(/bin/uname -X|grep Release|sed -e 's/.*= //')`
|
||||
(/bin/uname -X|grep i80486 >/dev/null) && UNAME_MACHINE=i486
|
||||
(/bin/uname -X|grep '^Machine.*Pentium' >/dev/null) \
|
||||
&& UNAME_MACHINE=i586
|
||||
(/bin/uname -X|egrep '^Machine.*Pent ?II' >/dev/null) \
|
||||
(/bin/uname -X|grep '^Machine.*Pent *II' >/dev/null) \
|
||||
&& UNAME_MACHINE=i686
|
||||
(/bin/uname -X|egrep '^Machine.*Pentium Pro' >/dev/null) \
|
||||
(/bin/uname -X|grep '^Machine.*Pentium Pro' >/dev/null) \
|
||||
&& UNAME_MACHINE=i686
|
||||
echo ${UNAME_MACHINE}-pc-sco$UNAME_REL
|
||||
else
|
||||
echo ${UNAME_MACHINE}-pc-sysv32
|
||||
fi
|
||||
exit 0 ;;
|
||||
i*86:*DOS:*:*)
|
||||
echo ${UNAME_MACHINE}-pc-msdosdjgpp
|
||||
exit 0 ;;
|
||||
pc:*:*:*)
|
||||
# Left here for compatibility:
|
||||
# uname -m prints for DJGPP always 'pc', but it prints nothing about
|
||||
@@ -954,9 +1038,15 @@ EOF
|
||||
# "miniframe"
|
||||
echo m68010-convergent-sysv
|
||||
exit 0 ;;
|
||||
mc68k:UNIX:SYSTEM5:3.51m)
|
||||
echo m68k-convergent-sysv
|
||||
exit 0 ;;
|
||||
M680?0:D-NIX:5.3:*)
|
||||
echo m68k-diab-dnix
|
||||
exit 0 ;;
|
||||
M68*:*:R3V[567]*:*)
|
||||
test -r /sysV68 && echo 'm68k-motorola-sysv' && exit 0 ;;
|
||||
3[34]??:*:4.0:3.0 | 3[34]??A:*:4.0:3.0 | 3[34]??,*:*:4.0:3.0 | 4850:*:4.0:3.0)
|
||||
3[34]??:*:4.0:3.0 | 3[34]??A:*:4.0:3.0 | 3[34]??,*:*:4.0:3.0 | 3[34]??/*:*:4.0:3.0 | 4400:*:4.0:3.0 | 4850:*:4.0:3.0 | SKA40:*:4.0:3.0 | SDS2:*:4.0:3.0 | SHG2:*:4.0:3.0)
|
||||
OS_REL=''
|
||||
test -r /etc/.relid \
|
||||
&& OS_REL=.`sed -n 's/[^ ]* [^ ]* \([0-9][0-9]\).*/\1/p' < /etc/.relid`
|
||||
@@ -973,9 +1063,6 @@ EOF
|
||||
mc68030:UNIX_System_V:4.*:*)
|
||||
echo m68k-atari-sysv4
|
||||
exit 0 ;;
|
||||
i*86:LynxOS:2.*:* | i*86:LynxOS:3.[01]*:* | i*86:LynxOS:4.0*:*)
|
||||
echo i386-unknown-lynxos${UNAME_RELEASE}
|
||||
exit 0 ;;
|
||||
TSUNAMI:LynxOS:2.*:*)
|
||||
echo sparc-unknown-lynxos${UNAME_RELEASE}
|
||||
exit 0 ;;
|
||||
@@ -1047,6 +1134,9 @@ EOF
|
||||
SX-5:SUPER-UX:*:*)
|
||||
echo sx5-nec-superux${UNAME_RELEASE}
|
||||
exit 0 ;;
|
||||
SX-6:SUPER-UX:*:*)
|
||||
echo sx6-nec-superux${UNAME_RELEASE}
|
||||
exit 0 ;;
|
||||
Power*:Rhapsody:*:*)
|
||||
echo powerpc-apple-rhapsody${UNAME_RELEASE}
|
||||
exit 0 ;;
|
||||
@@ -1054,18 +1144,24 @@ EOF
|
||||
echo ${UNAME_MACHINE}-apple-rhapsody${UNAME_RELEASE}
|
||||
exit 0 ;;
|
||||
*:Darwin:*:*)
|
||||
echo `uname -p`-apple-darwin${UNAME_RELEASE}
|
||||
case `uname -p` in
|
||||
*86) UNAME_PROCESSOR=i686 ;;
|
||||
powerpc) UNAME_PROCESSOR=powerpc ;;
|
||||
esac
|
||||
echo ${UNAME_PROCESSOR}-apple-darwin${UNAME_RELEASE}
|
||||
exit 0 ;;
|
||||
*:procnto*:*:* | *:QNX:[0123456789]*:*)
|
||||
if test "${UNAME_MACHINE}" = "x86pc"; then
|
||||
UNAME_PROCESSOR=`uname -p`
|
||||
if test "$UNAME_PROCESSOR" = "x86"; then
|
||||
UNAME_PROCESSOR=i386
|
||||
UNAME_MACHINE=pc
|
||||
fi
|
||||
echo `uname -p`-${UNAME_MACHINE}-nto-qnx
|
||||
echo ${UNAME_PROCESSOR}-${UNAME_MACHINE}-nto-qnx${UNAME_RELEASE}
|
||||
exit 0 ;;
|
||||
*:QNX:*:4*)
|
||||
echo i386-pc-qnx
|
||||
exit 0 ;;
|
||||
NSR-[KW]:NONSTOP_KERNEL:*:*)
|
||||
NSR-[DGKLNPTVW]:NONSTOP_KERNEL:*:*)
|
||||
echo nsr-tandem-nsk${UNAME_RELEASE}
|
||||
exit 0 ;;
|
||||
*:NonStop-UX:*:*)
|
||||
@@ -1088,11 +1184,6 @@ EOF
|
||||
fi
|
||||
echo ${UNAME_MACHINE}-unknown-plan9
|
||||
exit 0 ;;
|
||||
i*86:OS/2:*:*)
|
||||
# If we were able to find `uname', then EMX Unix compatibility
|
||||
# is probably installed.
|
||||
echo ${UNAME_MACHINE}-pc-os2-emx
|
||||
exit 0 ;;
|
||||
*:TOPS-10:*:*)
|
||||
echo pdp10-unknown-tops10
|
||||
exit 0 ;;
|
||||
@@ -1111,11 +1202,8 @@ EOF
|
||||
*:ITS:*:*)
|
||||
echo pdp10-unknown-its
|
||||
exit 0 ;;
|
||||
i*86:XTS-300:*:STOP)
|
||||
echo ${UNAME_MACHINE}-unknown-stop
|
||||
exit 0 ;;
|
||||
i*86:atheos:*:*)
|
||||
echo ${UNAME_MACHINE}-unknown-atheos
|
||||
SEI:*:*:SEIUX)
|
||||
echo mips-sei-seiux${UNAME_RELEASE}
|
||||
exit 0 ;;
|
||||
esac
|
||||
|
||||
@@ -1237,8 +1325,7 @@ main ()
|
||||
}
|
||||
EOF
|
||||
|
||||
$CC_FOR_BUILD $dummy.c -o $dummy 2>/dev/null && ./$dummy && rm -f $dummy.c $dummy && exit 0
|
||||
rm -f $dummy.c $dummy
|
||||
$CC_FOR_BUILD -o $dummy $dummy.c 2>/dev/null && $dummy && exit 0
|
||||
|
||||
# Apollos put the system type in the environment.
|
||||
|
||||
|
303
autoconf/config.sub
vendored
303
autoconf/config.sub
vendored
@@ -1,9 +1,9 @@
|
||||
#! /bin/sh
|
||||
# Configuration validation subroutine script.
|
||||
# Copyright (C) 1992, 1993, 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001
|
||||
# Free Software Foundation, Inc.
|
||||
# Copyright (C) 1992, 1993, 1994, 1995, 1996, 1997, 1998, 1999,
|
||||
# 2000, 2001, 2002, 2003 Free Software Foundation, Inc.
|
||||
|
||||
timestamp='2001-09-07'
|
||||
timestamp='2003-06-17'
|
||||
|
||||
# This file is (in principle) common to ALL GNU software.
|
||||
# The presence of a machine in this file suggests that SOME GNU software
|
||||
@@ -29,7 +29,8 @@ timestamp='2001-09-07'
|
||||
# configuration script generated by Autoconf, you may include it under
|
||||
# the same distribution terms that you use for the rest of that program.
|
||||
|
||||
# Please send patches to <config-patches@gnu.org>.
|
||||
# Please send patches to <config-patches@gnu.org>. Submit a context
|
||||
# diff and a properly formatted ChangeLog entry.
|
||||
#
|
||||
# Configuration subroutine to validate and canonicalize a configuration type.
|
||||
# Supply the specified configuration type as an argument.
|
||||
@@ -117,7 +118,7 @@ esac
|
||||
# Here we must recognize all the valid KERNEL-OS combinations.
|
||||
maybe_os=`echo $1 | sed 's/^\(.*\)-\([^-]*-[^-]*\)$/\2/'`
|
||||
case $maybe_os in
|
||||
nto-qnx* | linux-gnu* | storm-chaos* | os2-emx* | windows32-*)
|
||||
nto-qnx* | linux-gnu* | freebsd*-gnu* | netbsd*-gnu* | storm-chaos* | os2-emx* | rtmk-nova*)
|
||||
os=-$maybe_os
|
||||
basic_machine=`echo $1 | sed 's/^\(.*\)-\([^-]*-[^-]*\)$/\1/'`
|
||||
;;
|
||||
@@ -226,32 +227,44 @@ case $basic_machine in
|
||||
1750a | 580 \
|
||||
| a29k \
|
||||
| alpha | alphaev[4-8] | alphaev56 | alphaev6[78] | alphapca5[67] \
|
||||
| alpha64 | alpha64ev[4-8] | alpha64ev56 | alpha64ev6[78] | alpha64pca5[67] \
|
||||
| arc | arm | arm[bl]e | arme[lb] | armv[2345] | armv[345][lb] | avr \
|
||||
| c4x | clipper \
|
||||
| d10v | d30v | dsp16xx \
|
||||
| fr30 \
|
||||
| d10v | d30v | dlx | dsp16xx \
|
||||
| fr30 | frv \
|
||||
| h8300 | h8500 | hppa | hppa1.[01] | hppa2.0 | hppa2.0[nw] | hppa64 \
|
||||
| i370 | i860 | i960 | ia64 \
|
||||
| ip2k \
|
||||
| m32r | m68000 | m68k | m88k | mcore \
|
||||
| mips16 | mips64 | mips64el | mips64orion | mips64orionel \
|
||||
| mips64vr4100 | mips64vr4100el | mips64vr4300 \
|
||||
| mips64vr4300el | mips64vr5000 | mips64vr5000el \
|
||||
| mipsbe | mipseb | mipsel | mipsle | mipstx39 | mipstx39el \
|
||||
| mipsisa32 \
|
||||
| mips | mipsbe | mipseb | mipsel | mipsle \
|
||||
| mips16 \
|
||||
| mips64 | mips64el \
|
||||
| mips64vr | mips64vrel \
|
||||
| mips64orion | mips64orionel \
|
||||
| mips64vr4100 | mips64vr4100el \
|
||||
| mips64vr4300 | mips64vr4300el \
|
||||
| mips64vr5000 | mips64vr5000el \
|
||||
| mipsisa32 | mipsisa32el \
|
||||
| mipsisa32r2 | mipsisa32r2el \
|
||||
| mipsisa64 | mipsisa64el \
|
||||
| mipsisa64sb1 | mipsisa64sb1el \
|
||||
| mipsisa64sr71k | mipsisa64sr71kel \
|
||||
| mipstx39 | mipstx39el \
|
||||
| mn10200 | mn10300 \
|
||||
| msp430 \
|
||||
| ns16k | ns32k \
|
||||
| openrisc \
|
||||
| openrisc | or32 \
|
||||
| pdp10 | pdp11 | pj | pjl \
|
||||
| powerpc | powerpc64 | powerpc64le | powerpcle | ppcbe \
|
||||
| pyramid \
|
||||
| s390 | s390x \
|
||||
| sh | sh[34] | sh[34]eb | shbe | shle \
|
||||
| sparc | sparc64 | sparclet | sparclite | sparcv9 | sparcv9b \
|
||||
| stormy16 | strongarm \
|
||||
| tahoe | thumb | tic80 | tron \
|
||||
| v850 \
|
||||
| sh | sh[1234] | sh[23]e | sh[34]eb | shbe | shle | sh[1234]le | sh3ele \
|
||||
| sh64 | sh64le \
|
||||
| sparc | sparc64 | sparc86x | sparclet | sparclite | sparcv9 | sparcv9b \
|
||||
| strongarm \
|
||||
| tahoe | thumb | tic4x | tic80 | tron \
|
||||
| v850 | v850e \
|
||||
| we32k \
|
||||
| x86 | xscale \
|
||||
| x86 | xscale | xstormy16 | xtensa \
|
||||
| z8k)
|
||||
basic_machine=$basic_machine-unknown
|
||||
;;
|
||||
@@ -278,38 +291,55 @@ case $basic_machine in
|
||||
580-* \
|
||||
| a29k-* \
|
||||
| alpha-* | alphaev[4-8]-* | alphaev56-* | alphaev6[78]-* \
|
||||
| alphapca5[67]-* | arc-* \
|
||||
| arm-* | armbe-* | armle-* | armv*-* \
|
||||
| alpha64-* | alpha64ev[4-8]-* | alpha64ev56-* | alpha64ev6[78]-* \
|
||||
| alphapca5[67]-* | alpha64pca5[67]-* | arc-* \
|
||||
| arm-* | armbe-* | armle-* | armeb-* | armv*-* \
|
||||
| avr-* \
|
||||
| bs2000-* \
|
||||
| c[123]* | c30-* | [cjt]90-* | c54x-* \
|
||||
| clipper-* | cray2-* | cydra-* \
|
||||
| d10v-* | d30v-* \
|
||||
| c[123]* | c30-* | [cjt]90-* | c4x-* | c54x-* | c55x-* | c6x-* \
|
||||
| clipper-* | cydra-* \
|
||||
| d10v-* | d30v-* | dlx-* \
|
||||
| elxsi-* \
|
||||
| f30[01]-* | f700-* | fr30-* | fx80-* \
|
||||
| f30[01]-* | f700-* | fr30-* | frv-* | fx80-* \
|
||||
| h8300-* | h8500-* \
|
||||
| hppa-* | hppa1.[01]-* | hppa2.0-* | hppa2.0[nw]-* | hppa64-* \
|
||||
| i*86-* | i860-* | i960-* | ia64-* \
|
||||
| ip2k-* \
|
||||
| m32r-* \
|
||||
| m68000-* | m680[01234]0-* | m68360-* | m683?2-* | m68k-* \
|
||||
| m68000-* | m680[012346]0-* | m68360-* | m683?2-* | m68k-* \
|
||||
| m88110-* | m88k-* | mcore-* \
|
||||
| mips-* | mips16-* | mips64-* | mips64el-* | mips64orion-* \
|
||||
| mips64orionel-* | mips64vr4100-* | mips64vr4100el-* \
|
||||
| mips64vr4300-* | mips64vr4300el-* | mipsbe-* | mipseb-* \
|
||||
| mipsle-* | mipsel-* | mipstx39-* | mipstx39el-* \
|
||||
| none-* | np1-* | ns16k-* | ns32k-* \
|
||||
| mips-* | mipsbe-* | mipseb-* | mipsel-* | mipsle-* \
|
||||
| mips16-* \
|
||||
| mips64-* | mips64el-* \
|
||||
| mips64vr-* | mips64vrel-* \
|
||||
| mips64orion-* | mips64orionel-* \
|
||||
| mips64vr4100-* | mips64vr4100el-* \
|
||||
| mips64vr4300-* | mips64vr4300el-* \
|
||||
| mips64vr5000-* | mips64vr5000el-* \
|
||||
| mipsisa32-* | mipsisa32el-* \
|
||||
| mipsisa32r2-* | mipsisa32r2el-* \
|
||||
| mipsisa64-* | mipsisa64el-* \
|
||||
| mipsisa64sb1-* | mipsisa64sb1el-* \
|
||||
| mipsisa64sr71k-* | mipsisa64sr71kel-* \
|
||||
| mipstx39-* | mipstx39el-* \
|
||||
| msp430-* \
|
||||
| none-* | np1-* | nv1-* | ns16k-* | ns32k-* \
|
||||
| orion-* \
|
||||
| pdp10-* | pdp11-* | pj-* | pjl-* | pn-* | power-* \
|
||||
| powerpc-* | powerpc64-* | powerpc64le-* | powerpcle-* | ppcbe-* \
|
||||
| pyramid-* \
|
||||
| romp-* | rs6000-* \
|
||||
| s390-* | s390x-* \
|
||||
| sh-* | sh[34]-* | sh[34]eb-* | shbe-* | shle-* \
|
||||
| sparc-* | sparc64-* | sparc86x-* | sparclite-* \
|
||||
| sparcv9-* | sparcv9b-* | stormy16-* | strongarm-* | sv1-* \
|
||||
| t3e-* | tahoe-* | thumb-* | tic30-* | tic54x-* | tic80-* | tron-* \
|
||||
| v850-* | vax-* \
|
||||
| sh-* | sh[1234]-* | sh[23]e-* | sh[34]eb-* | shbe-* \
|
||||
| shle-* | sh[1234]le-* | sh3ele-* | sh64-* | sh64le-* \
|
||||
| sparc-* | sparc64-* | sparc86x-* | sparclet-* | sparclite-* \
|
||||
| sparcv9-* | sparcv9b-* | strongarm-* | sv1-* | sx?-* \
|
||||
| tahoe-* | thumb-* \
|
||||
| tic30-* | tic4x-* | tic54x-* | tic55x-* | tic6x-* | tic80-* \
|
||||
| tron-* \
|
||||
| v850-* | v850e-* | vax-* \
|
||||
| we32k-* \
|
||||
| x86-* | x86_64-* | xmp-* | xps100-* | xscale-* \
|
||||
| x86-* | x86_64-* | xps100-* | xscale-* | xstormy16-* \
|
||||
| xtensa-* \
|
||||
| ymp-* \
|
||||
| z8k-*)
|
||||
;;
|
||||
@@ -343,6 +373,9 @@ case $basic_machine in
|
||||
basic_machine=a29k-none
|
||||
os=-bsd
|
||||
;;
|
||||
amd64)
|
||||
basic_machine=x86_64-pc
|
||||
;;
|
||||
amdahl)
|
||||
basic_machine=580-amdahl
|
||||
os=-sysv
|
||||
@@ -374,6 +407,10 @@ case $basic_machine in
|
||||
basic_machine=ns32k-sequent
|
||||
os=-dynix
|
||||
;;
|
||||
c90)
|
||||
basic_machine=c90-cray
|
||||
os=-unicos
|
||||
;;
|
||||
convex-c1)
|
||||
basic_machine=c1-convex
|
||||
os=-bsd
|
||||
@@ -394,16 +431,8 @@ case $basic_machine in
|
||||
basic_machine=c38-convex
|
||||
os=-bsd
|
||||
;;
|
||||
cray | ymp)
|
||||
basic_machine=ymp-cray
|
||||
os=-unicos
|
||||
;;
|
||||
cray2)
|
||||
basic_machine=cray2-cray
|
||||
os=-unicos
|
||||
;;
|
||||
[cjt]90)
|
||||
basic_machine=${basic_machine}-cray
|
||||
cray | j90)
|
||||
basic_machine=j90-cray
|
||||
os=-unicos
|
||||
;;
|
||||
crds | unos)
|
||||
@@ -418,6 +447,14 @@ case $basic_machine in
|
||||
decstation | decstation-3100 | pmax | pmax-* | pmin | dec3100 | decstatn)
|
||||
basic_machine=mips-dec
|
||||
;;
|
||||
decsystem10* | dec10*)
|
||||
basic_machine=pdp10-dec
|
||||
os=-tops10
|
||||
;;
|
||||
decsystem20* | dec20*)
|
||||
basic_machine=pdp10-dec
|
||||
os=-tops20
|
||||
;;
|
||||
delta | 3300 | motorola-3300 | motorola-delta \
|
||||
| 3300-motorola | delta-motorola)
|
||||
basic_machine=m68k-motorola
|
||||
@@ -598,14 +635,6 @@ case $basic_machine in
|
||||
basic_machine=m68k-atari
|
||||
os=-mint
|
||||
;;
|
||||
mipsel*-linux*)
|
||||
basic_machine=mipsel-unknown
|
||||
os=-linux-gnu
|
||||
;;
|
||||
mips*-linux*)
|
||||
basic_machine=mips-unknown
|
||||
os=-linux-gnu
|
||||
;;
|
||||
mips3*-*)
|
||||
basic_machine=`echo $basic_machine | sed -e 's/mips3/mips64/'`
|
||||
;;
|
||||
@@ -620,6 +649,10 @@ case $basic_machine in
|
||||
basic_machine=m68k-rom68k
|
||||
os=-coff
|
||||
;;
|
||||
morphos)
|
||||
basic_machine=powerpc-unknown
|
||||
os=-morphos
|
||||
;;
|
||||
msdos)
|
||||
basic_machine=i386-pc
|
||||
os=-msdos
|
||||
@@ -692,6 +725,10 @@ case $basic_machine in
|
||||
np1)
|
||||
basic_machine=np1-gould
|
||||
;;
|
||||
nv1)
|
||||
basic_machine=nv1-cray
|
||||
os=-unicosmp
|
||||
;;
|
||||
nsr-tandem)
|
||||
basic_machine=nsr-tandem
|
||||
;;
|
||||
@@ -699,6 +736,10 @@ case $basic_machine in
|
||||
basic_machine=hppa1.1-oki
|
||||
os=-proelf
|
||||
;;
|
||||
or32 | or32-*)
|
||||
basic_machine=or32-unknown
|
||||
os=-coff
|
||||
;;
|
||||
OSE68000 | ose68000)
|
||||
basic_machine=m68000-ericsson
|
||||
os=-ose
|
||||
@@ -721,49 +762,55 @@ case $basic_machine in
|
||||
pbb)
|
||||
basic_machine=m68k-tti
|
||||
;;
|
||||
pc532 | pc532-*)
|
||||
pc532 | pc532-*)
|
||||
basic_machine=ns32k-pc532
|
||||
;;
|
||||
pentium | p5 | k5 | k6 | nexgen)
|
||||
pentium | p5 | k5 | k6 | nexgen | viac3)
|
||||
basic_machine=i586-pc
|
||||
;;
|
||||
pentiumpro | p6 | 6x86 | athlon)
|
||||
pentiumpro | p6 | 6x86 | athlon | athlon_*)
|
||||
basic_machine=i686-pc
|
||||
;;
|
||||
pentiumii | pentium2)
|
||||
pentiumii | pentium2 | pentiumiii | pentium3)
|
||||
basic_machine=i686-pc
|
||||
;;
|
||||
pentium-* | p5-* | k5-* | k6-* | nexgen-*)
|
||||
pentium4)
|
||||
basic_machine=i786-pc
|
||||
;;
|
||||
pentium-* | p5-* | k5-* | k6-* | nexgen-* | viac3-*)
|
||||
basic_machine=i586-`echo $basic_machine | sed 's/^[^-]*-//'`
|
||||
;;
|
||||
pentiumpro-* | p6-* | 6x86-* | athlon-*)
|
||||
basic_machine=i686-`echo $basic_machine | sed 's/^[^-]*-//'`
|
||||
;;
|
||||
pentiumii-* | pentium2-*)
|
||||
pentiumii-* | pentium2-* | pentiumiii-* | pentium3-*)
|
||||
basic_machine=i686-`echo $basic_machine | sed 's/^[^-]*-//'`
|
||||
;;
|
||||
pentium4-*)
|
||||
basic_machine=i786-`echo $basic_machine | sed 's/^[^-]*-//'`
|
||||
;;
|
||||
pn)
|
||||
basic_machine=pn-gould
|
||||
;;
|
||||
power) basic_machine=power-ibm
|
||||
;;
|
||||
ppc) basic_machine=powerpc-unknown
|
||||
;;
|
||||
;;
|
||||
ppc-*) basic_machine=powerpc-`echo $basic_machine | sed 's/^[^-]*-//'`
|
||||
;;
|
||||
ppcle | powerpclittle | ppc-le | powerpc-little)
|
||||
basic_machine=powerpcle-unknown
|
||||
;;
|
||||
;;
|
||||
ppcle-* | powerpclittle-*)
|
||||
basic_machine=powerpcle-`echo $basic_machine | sed 's/^[^-]*-//'`
|
||||
;;
|
||||
ppc64) basic_machine=powerpc64-unknown
|
||||
;;
|
||||
;;
|
||||
ppc64-*) basic_machine=powerpc64-`echo $basic_machine | sed 's/^[^-]*-//'`
|
||||
;;
|
||||
ppc64le | powerpc64little | ppc64-le | powerpc64-little)
|
||||
basic_machine=powerpc64le-unknown
|
||||
;;
|
||||
;;
|
||||
ppc64le-* | powerpc64little-*)
|
||||
basic_machine=powerpc64le-`echo $basic_machine | sed 's/^[^-]*-//'`
|
||||
;;
|
||||
@@ -784,10 +831,26 @@ case $basic_machine in
|
||||
rtpc | rtpc-*)
|
||||
basic_machine=romp-ibm
|
||||
;;
|
||||
s390 | s390-*)
|
||||
basic_machine=s390-ibm
|
||||
;;
|
||||
s390x | s390x-*)
|
||||
basic_machine=s390x-ibm
|
||||
;;
|
||||
sa29200)
|
||||
basic_machine=a29k-amd
|
||||
os=-udi
|
||||
;;
|
||||
sb1)
|
||||
basic_machine=mipsisa64sb1-unknown
|
||||
;;
|
||||
sb1el)
|
||||
basic_machine=mipsisa64sb1el-unknown
|
||||
;;
|
||||
sei)
|
||||
basic_machine=mips-sei
|
||||
os=-seiux
|
||||
;;
|
||||
sequent)
|
||||
basic_machine=i386-sequent
|
||||
;;
|
||||
@@ -795,7 +858,10 @@ case $basic_machine in
|
||||
basic_machine=sh-hitachi
|
||||
os=-hms
|
||||
;;
|
||||
sparclite-wrs)
|
||||
sh64)
|
||||
basic_machine=sh64-unknown
|
||||
;;
|
||||
sparclite-wrs | simso-wrs)
|
||||
basic_machine=sparclite-wrs
|
||||
os=-vxworks
|
||||
;;
|
||||
@@ -862,19 +928,35 @@ case $basic_machine in
|
||||
os=-dynix
|
||||
;;
|
||||
t3e)
|
||||
basic_machine=t3e-cray
|
||||
basic_machine=alphaev5-cray
|
||||
os=-unicos
|
||||
;;
|
||||
t90)
|
||||
basic_machine=t90-cray
|
||||
os=-unicos
|
||||
;;
|
||||
tic54x | c54x*)
|
||||
basic_machine=tic54x-unknown
|
||||
os=-coff
|
||||
;;
|
||||
tic55x | c55x*)
|
||||
basic_machine=tic55x-unknown
|
||||
os=-coff
|
||||
;;
|
||||
tic6x | c6x*)
|
||||
basic_machine=tic6x-unknown
|
||||
os=-coff
|
||||
;;
|
||||
tx39)
|
||||
basic_machine=mipstx39-unknown
|
||||
;;
|
||||
tx39el)
|
||||
basic_machine=mipstx39el-unknown
|
||||
;;
|
||||
toad1)
|
||||
basic_machine=pdp10-xkl
|
||||
os=-tops20
|
||||
;;
|
||||
tower | tower-32)
|
||||
basic_machine=m68k-ncr
|
||||
;;
|
||||
@@ -899,8 +981,8 @@ case $basic_machine in
|
||||
os=-vms
|
||||
;;
|
||||
vpp*|vx|vx-*)
|
||||
basic_machine=f301-fujitsu
|
||||
;;
|
||||
basic_machine=f301-fujitsu
|
||||
;;
|
||||
vxworks960)
|
||||
basic_machine=i960-wrs
|
||||
os=-vxworks
|
||||
@@ -921,17 +1003,13 @@ case $basic_machine in
|
||||
basic_machine=hppa1.1-winbond
|
||||
os=-proelf
|
||||
;;
|
||||
windows32)
|
||||
basic_machine=i386-pc
|
||||
os=-windows32-msvcrt
|
||||
;;
|
||||
xmp)
|
||||
basic_machine=xmp-cray
|
||||
os=-unicos
|
||||
;;
|
||||
xps | xps100)
|
||||
xps | xps100)
|
||||
basic_machine=xps100-honeywell
|
||||
;;
|
||||
ymp)
|
||||
basic_machine=ymp-cray
|
||||
os=-unicos
|
||||
;;
|
||||
z8k-*-coff)
|
||||
basic_machine=z8k-unknown
|
||||
os=-sim
|
||||
@@ -952,13 +1030,6 @@ case $basic_machine in
|
||||
op60c)
|
||||
basic_machine=hppa1.1-oki
|
||||
;;
|
||||
mips)
|
||||
if [ x$os = x-linux-gnu ]; then
|
||||
basic_machine=mips-unknown
|
||||
else
|
||||
basic_machine=mips-mips
|
||||
fi
|
||||
;;
|
||||
romp)
|
||||
basic_machine=romp-ibm
|
||||
;;
|
||||
@@ -978,13 +1049,16 @@ case $basic_machine in
|
||||
we32k)
|
||||
basic_machine=we32k-att
|
||||
;;
|
||||
sh3 | sh4 | sh3eb | sh4eb)
|
||||
sh3 | sh4 | sh[34]eb | sh[1234]le | sh[23]ele)
|
||||
basic_machine=sh-unknown
|
||||
;;
|
||||
sh64)
|
||||
basic_machine=sh64-unknown
|
||||
;;
|
||||
sparc | sparcv9 | sparcv9b)
|
||||
basic_machine=sparc-sun
|
||||
;;
|
||||
cydra)
|
||||
cydra)
|
||||
basic_machine=cydra-cydrome
|
||||
;;
|
||||
orion)
|
||||
@@ -999,10 +1073,6 @@ case $basic_machine in
|
||||
pmac | pmac-mpw)
|
||||
basic_machine=powerpc-apple
|
||||
;;
|
||||
c4x*)
|
||||
basic_machine=c4x-none
|
||||
os=-coff
|
||||
;;
|
||||
*-unknown)
|
||||
# Make sure to match an already-canonicalized machine name.
|
||||
;;
|
||||
@@ -1065,10 +1135,12 @@ case $os in
|
||||
| -chorusos* | -chorusrdb* \
|
||||
| -cygwin* | -pe* | -psos* | -moss* | -proelf* | -rtems* \
|
||||
| -mingw32* | -linux-gnu* | -uxpv* | -beos* | -mpeix* | -udk* \
|
||||
| -interix* | -uwin* | -rhapsody* | -darwin* | -opened* \
|
||||
| -interix* | -uwin* | -mks* | -rhapsody* | -darwin* | -opened* \
|
||||
| -openstep* | -oskit* | -conix* | -pw32* | -nonstopux* \
|
||||
| -storm-chaos* | -tops10* | -tenex* | -tops20* | -its* \
|
||||
| -os2* | -vos*)
|
||||
| -os2* | -vos* | -palmos* | -uclinux* | -nucleus* \
|
||||
| -morphos* | -superux* | -rtmk* | -rtmk-nova* | -windiss* \
|
||||
| -powermax* | -dnix* | -nx6 | -nx7 | -sei*)
|
||||
# Remember, each alternative MUST END IN *, to match a version number.
|
||||
;;
|
||||
-qnx*)
|
||||
@@ -1080,8 +1152,10 @@ case $os in
|
||||
;;
|
||||
esac
|
||||
;;
|
||||
-nto-qnx*)
|
||||
;;
|
||||
-nto*)
|
||||
os=-nto-qnx
|
||||
os=`echo $os | sed -e 's|nto|nto-qnx|'`
|
||||
;;
|
||||
-sim | -es1800* | -hms* | -xray | -os68k* | -none* | -v88r* \
|
||||
| -windows* | -osx | -abug | -netware* | -os9* | -beos* \
|
||||
@@ -1120,14 +1194,20 @@ case $os in
|
||||
-acis*)
|
||||
os=-aos
|
||||
;;
|
||||
-atheos*)
|
||||
os=-atheos
|
||||
;;
|
||||
-386bsd)
|
||||
os=-bsd
|
||||
;;
|
||||
-ctix* | -uts*)
|
||||
os=-sysv
|
||||
;;
|
||||
-nova*)
|
||||
os=-rtmk-nova
|
||||
;;
|
||||
-ns2 )
|
||||
os=-nextstep2
|
||||
os=-nextstep2
|
||||
;;
|
||||
-nsk*)
|
||||
os=-nsk
|
||||
@@ -1166,8 +1246,14 @@ case $os in
|
||||
-xenix)
|
||||
os=-xenix
|
||||
;;
|
||||
-*mint | -mint[0-9]* | -*MiNT | -MiNT[0-9]*)
|
||||
os=-mint
|
||||
-*mint | -mint[0-9]* | -*MiNT | -MiNT[0-9]*)
|
||||
os=-mint
|
||||
;;
|
||||
-aros*)
|
||||
os=-aros
|
||||
;;
|
||||
-kaos*)
|
||||
os=-kaos
|
||||
;;
|
||||
-none)
|
||||
;;
|
||||
@@ -1200,10 +1286,14 @@ case $basic_machine in
|
||||
arm*-semi)
|
||||
os=-aout
|
||||
;;
|
||||
c4x-* | tic4x-*)
|
||||
os=-coff
|
||||
;;
|
||||
# This must come before the *-dec entry.
|
||||
pdp10-*)
|
||||
os=-tops20
|
||||
;;
|
||||
pdp11-*)
|
||||
pdp11-*)
|
||||
os=-none
|
||||
;;
|
||||
*-dec | vax-*)
|
||||
@@ -1230,6 +1320,9 @@ case $basic_machine in
|
||||
mips*-*)
|
||||
os=-elf
|
||||
;;
|
||||
or32-*)
|
||||
os=-coff
|
||||
;;
|
||||
*-tti) # must be before sparc entry or we get the wrong os.
|
||||
os=-sysv3
|
||||
;;
|
||||
@@ -1293,19 +1386,19 @@ case $basic_machine in
|
||||
*-next)
|
||||
os=-nextstep3
|
||||
;;
|
||||
*-gould)
|
||||
*-gould)
|
||||
os=-sysv
|
||||
;;
|
||||
*-highlevel)
|
||||
*-highlevel)
|
||||
os=-bsd
|
||||
;;
|
||||
*-encore)
|
||||
os=-bsd
|
||||
;;
|
||||
*-sgi)
|
||||
*-sgi)
|
||||
os=-irix
|
||||
;;
|
||||
*-siemens)
|
||||
*-siemens)
|
||||
os=-sysv4
|
||||
;;
|
||||
*-masscomp)
|
||||
@@ -1377,7 +1470,7 @@ case $basic_machine in
|
||||
-ptx*)
|
||||
vendor=sequent
|
||||
;;
|
||||
-vxsim* | -vxworks*)
|
||||
-vxsim* | -vxworks* | -windiss*)
|
||||
vendor=wrs
|
||||
;;
|
||||
-aux*)
|
||||
|
@@ -1,19 +1,38 @@
|
||||
#!/bin/sh
|
||||
#
|
||||
# install - install a program, script, or datafile
|
||||
# This comes from X11R5 (mit/util/scripts/install.sh).
|
||||
|
||||
scriptversion=2003-06-13.21
|
||||
|
||||
# This originates from X11R5 (mit/util/scripts/install.sh), which was
|
||||
# later released in X11R6 (xc/config/util/install.sh) with the
|
||||
# following copyright and license.
|
||||
#
|
||||
# Copyright 1991 by the Massachusetts Institute of Technology
|
||||
# Copyright (C) 1994 X Consortium
|
||||
#
|
||||
# Permission to use, copy, modify, distribute, and sell this software and its
|
||||
# documentation for any purpose is hereby granted without fee, provided that
|
||||
# the above copyright notice appear in all copies and that both that
|
||||
# copyright notice and this permission notice appear in supporting
|
||||
# documentation, and that the name of M.I.T. not be used in advertising or
|
||||
# publicity pertaining to distribution of the software without specific,
|
||||
# written prior permission. M.I.T. makes no representations about the
|
||||
# suitability of this software for any purpose. It is provided "as is"
|
||||
# without express or implied warranty.
|
||||
# Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
# of this software and associated documentation files (the "Software"), to
|
||||
# deal in the Software without restriction, including without limitation the
|
||||
# rights to use, copy, modify, merge, publish, distribute, sublicense, and/or
|
||||
# sell copies of the Software, and to permit persons to whom the Software is
|
||||
# furnished to do so, subject to the following conditions:
|
||||
#
|
||||
# The above copyright notice and this permission notice shall be included in
|
||||
# all copies or substantial portions of the Software.
|
||||
#
|
||||
# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
# IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
# FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
# X CONSORTIUM BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
|
||||
# AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNEC-
|
||||
# TION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
|
||||
#
|
||||
# Except as contained in this notice, the name of the X Consortium shall not
|
||||
# be used in advertising or otherwise to promote the sale, use or other deal-
|
||||
# ings in this Software without prior written authorization from the X Consor-
|
||||
# tium.
|
||||
#
|
||||
#
|
||||
# FSF changes to this file are in the public domain.
|
||||
#
|
||||
# Calling this script install-sh is preferred over install.sh, to prevent
|
||||
# `make' implicit rules from creating a file called install from it
|
||||
@@ -23,13 +42,11 @@
|
||||
# from scratch. It can only install one file at a time, a restriction
|
||||
# shared with many OS's install programs.
|
||||
|
||||
|
||||
# set DOITPROG to echo to test this script
|
||||
|
||||
# Don't use :- since 4.3BSD and earlier shells don't like it.
|
||||
doit="${DOITPROG-}"
|
||||
|
||||
|
||||
# put in absolute paths if you don't have them in your path; or use env. vars.
|
||||
|
||||
mvprog="${MVPROG-mv}"
|
||||
@@ -41,211 +58,229 @@ stripprog="${STRIPPROG-strip}"
|
||||
rmprog="${RMPROG-rm}"
|
||||
mkdirprog="${MKDIRPROG-mkdir}"
|
||||
|
||||
transformbasename=""
|
||||
transform_arg=""
|
||||
transformbasename=
|
||||
transform_arg=
|
||||
instcmd="$mvprog"
|
||||
chmodcmd="$chmodprog 0755"
|
||||
chowncmd=""
|
||||
chgrpcmd=""
|
||||
stripcmd=""
|
||||
chowncmd=
|
||||
chgrpcmd=
|
||||
stripcmd=
|
||||
rmcmd="$rmprog -f"
|
||||
mvcmd="$mvprog"
|
||||
src=""
|
||||
dst=""
|
||||
dir_arg=""
|
||||
src=
|
||||
dst=
|
||||
dir_arg=
|
||||
|
||||
while [ x"$1" != x ]; do
|
||||
case $1 in
|
||||
-c) instcmd="$cpprog"
|
||||
shift
|
||||
continue;;
|
||||
usage="Usage: $0 [OPTION]... SRCFILE DSTFILE
|
||||
or: $0 -d DIR1 DIR2...
|
||||
|
||||
-d) dir_arg=true
|
||||
shift
|
||||
continue;;
|
||||
In the first form, install SRCFILE to DSTFILE, removing SRCFILE by default.
|
||||
In the second, create the directory path DIR.
|
||||
|
||||
-m) chmodcmd="$chmodprog $2"
|
||||
shift
|
||||
shift
|
||||
continue;;
|
||||
Options:
|
||||
-b=TRANSFORMBASENAME
|
||||
-c copy source (using $cpprog) instead of moving (using $mvprog).
|
||||
-d create directories instead of installing files.
|
||||
-g GROUP $chgrp installed files to GROUP.
|
||||
-m MODE $chmod installed files to MODE.
|
||||
-o USER $chown installed files to USER.
|
||||
-s strip installed files (using $stripprog).
|
||||
-t=TRANSFORM
|
||||
--help display this help and exit.
|
||||
--version display version info and exit.
|
||||
|
||||
-o) chowncmd="$chownprog $2"
|
||||
shift
|
||||
shift
|
||||
continue;;
|
||||
Environment variables override the default commands:
|
||||
CHGRPPROG CHMODPROG CHOWNPROG CPPROG MKDIRPROG MVPROG RMPROG STRIPPROG
|
||||
"
|
||||
|
||||
-g) chgrpcmd="$chgrpprog $2"
|
||||
shift
|
||||
shift
|
||||
continue;;
|
||||
while test -n "$1"; do
|
||||
case $1 in
|
||||
-b=*) transformbasename=`echo $1 | sed 's/-b=//'`
|
||||
shift
|
||||
continue;;
|
||||
|
||||
-s) stripcmd="$stripprog"
|
||||
shift
|
||||
continue;;
|
||||
-c) instcmd=$cpprog
|
||||
shift
|
||||
continue;;
|
||||
|
||||
-t=*) transformarg=`echo $1 | sed 's/-t=//'`
|
||||
shift
|
||||
continue;;
|
||||
-d) dir_arg=true
|
||||
shift
|
||||
continue;;
|
||||
|
||||
-b=*) transformbasename=`echo $1 | sed 's/-b=//'`
|
||||
shift
|
||||
continue;;
|
||||
-g) chgrpcmd="$chgrpprog $2"
|
||||
shift
|
||||
shift
|
||||
continue;;
|
||||
|
||||
*) if [ x"$src" = x ]
|
||||
then
|
||||
src=$1
|
||||
else
|
||||
# this colon is to work around a 386BSD /bin/sh bug
|
||||
:
|
||||
dst=$1
|
||||
fi
|
||||
shift
|
||||
continue;;
|
||||
esac
|
||||
--help) echo "$usage"; exit 0;;
|
||||
|
||||
-m) chmodcmd="$chmodprog $2"
|
||||
shift
|
||||
shift
|
||||
continue;;
|
||||
|
||||
-o) chowncmd="$chownprog $2"
|
||||
shift
|
||||
shift
|
||||
continue;;
|
||||
|
||||
-s) stripcmd=$stripprog
|
||||
shift
|
||||
continue;;
|
||||
|
||||
-t=*) transformarg=`echo $1 | sed 's/-t=//'`
|
||||
shift
|
||||
continue;;
|
||||
|
||||
--version) echo "$0 $scriptversion"; exit 0;;
|
||||
|
||||
*) if test -z "$src"; then
|
||||
src=$1
|
||||
else
|
||||
# this colon is to work around a 386BSD /bin/sh bug
|
||||
:
|
||||
dst=$1
|
||||
fi
|
||||
shift
|
||||
continue;;
|
||||
esac
|
||||
done
|
||||
|
||||
if [ x"$src" = x ]
|
||||
then
|
||||
echo "install: no input file specified"
|
||||
exit 1
|
||||
else
|
||||
true
|
||||
if test -z "$src"; then
|
||||
echo "$0: no input file specified." >&2
|
||||
exit 1
|
||||
fi
|
||||
|
||||
if [ x"$dir_arg" != x ]; then
|
||||
dst=$src
|
||||
src=""
|
||||
|
||||
if [ -d $dst ]; then
|
||||
instcmd=:
|
||||
chmodcmd=""
|
||||
else
|
||||
instcmd=mkdir
|
||||
fi
|
||||
if test -n "$dir_arg"; then
|
||||
dst=$src
|
||||
src=
|
||||
|
||||
if test -d "$dst"; then
|
||||
instcmd=:
|
||||
chmodcmd=
|
||||
else
|
||||
instcmd=$mkdirprog
|
||||
fi
|
||||
else
|
||||
# Waiting for this to be detected by the "$instcmd $src $dsttmp" command
|
||||
# might cause directories to be created, which would be especially bad
|
||||
# if $src (and thus $dsttmp) contains '*'.
|
||||
if test ! -f "$src" && test ! -d "$src"; then
|
||||
echo "$0: $src does not exist." >&2
|
||||
exit 1
|
||||
fi
|
||||
|
||||
# Waiting for this to be detected by the "$instcmd $src $dsttmp" command
|
||||
# might cause directories to be created, which would be especially bad
|
||||
# if $src (and thus $dsttmp) contains '*'.
|
||||
if test -z "$dst"; then
|
||||
echo "$0: no destination specified." >&2
|
||||
exit 1
|
||||
fi
|
||||
|
||||
if [ -f $src -o -d $src ]
|
||||
then
|
||||
true
|
||||
else
|
||||
echo "install: $src does not exist"
|
||||
exit 1
|
||||
fi
|
||||
|
||||
if [ x"$dst" = x ]
|
||||
then
|
||||
echo "install: no destination specified"
|
||||
exit 1
|
||||
else
|
||||
true
|
||||
fi
|
||||
|
||||
# If destination is a directory, append the input filename; if your system
|
||||
# does not like double slashes in filenames, you may need to add some logic
|
||||
|
||||
if [ -d $dst ]
|
||||
then
|
||||
dst="$dst"/`basename $src`
|
||||
else
|
||||
true
|
||||
fi
|
||||
# If destination is a directory, append the input filename; won't work
|
||||
# if double slashes aren't ignored.
|
||||
if test -d "$dst"; then
|
||||
dst=$dst/`basename "$src"`
|
||||
fi
|
||||
fi
|
||||
|
||||
## this sed command emulates the dirname command
|
||||
dstdir=`echo $dst | sed -e 's,[^/]*$,,;s,/$,,;s,^$,.,'`
|
||||
dstdir=`echo "$dst" | sed -e 's,[^/]*$,,;s,/$,,;s,^$,.,'`
|
||||
|
||||
# Make sure that the destination directory exists.
|
||||
# this part is taken from Noah Friedman's mkinstalldirs script
|
||||
# (this part is taken from Noah Friedman's mkinstalldirs script.)
|
||||
|
||||
# Skip lots of stat calls in the usual case.
|
||||
if [ ! -d "$dstdir" ]; then
|
||||
defaultIFS='
|
||||
'
|
||||
IFS="${IFS-${defaultIFS}}"
|
||||
if test ! -d "$dstdir"; then
|
||||
defaultIFS='
|
||||
'
|
||||
IFS="${IFS-$defaultIFS}"
|
||||
|
||||
oIFS="${IFS}"
|
||||
# Some sh's can't handle IFS=/ for some reason.
|
||||
IFS='%'
|
||||
set - `echo ${dstdir} | sed -e 's@/@%@g' -e 's@^%@/@'`
|
||||
IFS="${oIFS}"
|
||||
oIFS=$IFS
|
||||
# Some sh's can't handle IFS=/ for some reason.
|
||||
IFS='%'
|
||||
set - `echo "$dstdir" | sed -e 's@/@%@g' -e 's@^%@/@'`
|
||||
IFS=$oIFS
|
||||
|
||||
pathcomp=''
|
||||
pathcomp=
|
||||
|
||||
while [ $# -ne 0 ] ; do
|
||||
pathcomp="${pathcomp}${1}"
|
||||
shift
|
||||
|
||||
if [ ! -d "${pathcomp}" ] ;
|
||||
then
|
||||
$mkdirprog "${pathcomp}"
|
||||
else
|
||||
true
|
||||
fi
|
||||
|
||||
pathcomp="${pathcomp}/"
|
||||
done
|
||||
while test $# -ne 0 ; do
|
||||
pathcomp=$pathcomp$1
|
||||
shift
|
||||
test -d "$pathcomp" || $mkdirprog "$pathcomp"
|
||||
pathcomp=$pathcomp/
|
||||
done
|
||||
fi
|
||||
|
||||
if [ x"$dir_arg" != x ]
|
||||
then
|
||||
$doit $instcmd $dst &&
|
||||
if test -n "$dir_arg"; then
|
||||
$doit $instcmd "$dst" \
|
||||
&& { test -z "$chowncmd" || $doit $chowncmd "$dst"; } \
|
||||
&& { test -z "$chgrpcmd" || $doit $chgrpcmd "$dst"; } \
|
||||
&& { test -z "$stripcmd" || $doit $stripcmd "$dst"; } \
|
||||
&& { test -z "$chmodcmd" || $doit $chmodcmd "$dst"; }
|
||||
|
||||
if [ x"$chowncmd" != x ]; then $doit $chowncmd $dst; else true ; fi &&
|
||||
if [ x"$chgrpcmd" != x ]; then $doit $chgrpcmd $dst; else true ; fi &&
|
||||
if [ x"$stripcmd" != x ]; then $doit $stripcmd $dst; else true ; fi &&
|
||||
if [ x"$chmodcmd" != x ]; then $doit $chmodcmd $dst; else true ; fi
|
||||
else
|
||||
# If we're going to rename the final executable, determine the name now.
|
||||
if test -z "$transformarg"; then
|
||||
dstfile=`basename "$dst"`
|
||||
else
|
||||
dstfile=`basename "$dst" $transformbasename \
|
||||
| sed $transformarg`$transformbasename
|
||||
fi
|
||||
|
||||
# If we're going to rename the final executable, determine the name now.
|
||||
# don't allow the sed command to completely eliminate the filename.
|
||||
test -z "$dstfile" && dstfile=`basename "$dst"`
|
||||
|
||||
if [ x"$transformarg" = x ]
|
||||
then
|
||||
dstfile=`basename $dst`
|
||||
else
|
||||
dstfile=`basename $dst $transformbasename |
|
||||
sed $transformarg`$transformbasename
|
||||
fi
|
||||
# Make a couple of temp file names in the proper directory.
|
||||
dsttmp=$dstdir/_inst.$$_
|
||||
rmtmp=$dstdir/_rm.$$_
|
||||
|
||||
# don't allow the sed command to completely eliminate the filename
|
||||
# Trap to clean up those temp files at exit.
|
||||
trap 'status=$?; rm -f "$dsttmp" "$rmtmp" && exit $status' 0
|
||||
trap '(exit $?); exit' 1 2 13 15
|
||||
|
||||
if [ x"$dstfile" = x ]
|
||||
then
|
||||
dstfile=`basename $dst`
|
||||
else
|
||||
true
|
||||
fi
|
||||
# Move or copy the file name to the temp name
|
||||
$doit $instcmd "$src" "$dsttmp" &&
|
||||
|
||||
# Make a temp file name in the proper directory.
|
||||
# and set any options; do chmod last to preserve setuid bits.
|
||||
#
|
||||
# If any of these fail, we abort the whole thing. If we want to
|
||||
# ignore errors from any of these, just make sure not to ignore
|
||||
# errors from the above "$doit $instcmd $src $dsttmp" command.
|
||||
#
|
||||
{ test -z "$chowncmd" || $doit $chowncmd "$dsttmp"; } \
|
||||
&& { test -z "$chgrpcmd" || $doit $chgrpcmd "$dsttmp"; } \
|
||||
&& { test -z "$stripcmd" || $doit $stripcmd "$dsttmp"; } \
|
||||
&& { test -z "$chmodcmd" || $doit $chmodcmd "$dsttmp"; } &&
|
||||
|
||||
dsttmp=$dstdir/#inst.$$#
|
||||
|
||||
# Move or copy the file name to the temp name
|
||||
|
||||
$doit $instcmd $src $dsttmp &&
|
||||
|
||||
trap "rm -f ${dsttmp}" 0 &&
|
||||
|
||||
# and set any options; do chmod last to preserve setuid bits
|
||||
|
||||
# If any of these fail, we abort the whole thing. If we want to
|
||||
# ignore errors from any of these, just make sure not to ignore
|
||||
# errors from the above "$doit $instcmd $src $dsttmp" command.
|
||||
|
||||
if [ x"$chowncmd" != x ]; then $doit $chowncmd $dsttmp; else true;fi &&
|
||||
if [ x"$chgrpcmd" != x ]; then $doit $chgrpcmd $dsttmp; else true;fi &&
|
||||
if [ x"$stripcmd" != x ]; then $doit $stripcmd $dsttmp; else true;fi &&
|
||||
if [ x"$chmodcmd" != x ]; then $doit $chmodcmd $dsttmp; else true;fi &&
|
||||
|
||||
# Now rename the file to the real destination.
|
||||
|
||||
$doit $rmcmd -f $dstdir/$dstfile &&
|
||||
$doit $mvcmd $dsttmp $dstdir/$dstfile
|
||||
# Now remove or move aside any old file at destination location. We
|
||||
# try this two ways since rm can't unlink itself on some systems and
|
||||
# the destination file might be busy for other reasons. In this case,
|
||||
# the final cleanup might fail but the new file should still install
|
||||
# successfully.
|
||||
{
|
||||
if test -f "$dstdir/$dstfile"; then
|
||||
$doit $rmcmd -f "$dstdir/$dstfile" 2>/dev/null \
|
||||
|| $doit $mvcmd -f "$dstdir/$dstfile" "$rmtmp" 2>/dev/null \
|
||||
|| {
|
||||
echo "$0: cannot unlink or rename $dstdir/$dstfile" >&2
|
||||
(exit 1); exit
|
||||
}
|
||||
else
|
||||
:
|
||||
fi
|
||||
} &&
|
||||
|
||||
# Now rename the file to the real destination.
|
||||
$doit $mvcmd "$dsttmp" "$dstdir/$dstfile"
|
||||
fi &&
|
||||
|
||||
# The final little trick to "correctly" pass the exit status to the exit trap.
|
||||
{
|
||||
(exit 0); exit
|
||||
}
|
||||
|
||||
exit 0
|
||||
# Local variables:
|
||||
# eval: (add-hook 'write-file-hooks 'time-stamp)
|
||||
# time-stamp-start: "scriptversion="
|
||||
# time-stamp-format: "%:y-%02m-%02d.%02H"
|
||||
# time-stamp-end: "$"
|
||||
# End:
|
||||
|
204
configure.in
204
configure.in
@@ -1,4 +1,3 @@
|
||||
################################################################################
|
||||
##
|
||||
## Copyright 1999-2000 Sistina Software, Inc.
|
||||
##
|
||||
@@ -51,23 +50,58 @@ AC_CANONICAL_SYSTEM
|
||||
|
||||
case "$host_os" in
|
||||
linux*)
|
||||
CFLAGS= ;;
|
||||
CFLAGS=
|
||||
CLDFLAGS="-Wl,--version-script,.export.sym"
|
||||
CLDWHOLEARCHIVE="-Wl,-whole-archive"
|
||||
CLDNOWHOLEARCHIVE="-Wl,-no-whole-archive"
|
||||
LD_DEPS=".export.sym"
|
||||
LD_FLAGS="-Wl,--export-dynamic"
|
||||
SOFLAG="-shared"
|
||||
DEVMAPPER=yes
|
||||
ODIRECT=yes ;;
|
||||
darwin*)
|
||||
CFLAGS="-no-cpp-precomp -fno-common"
|
||||
CLDFLAGS=
|
||||
CLDWHOLEARCHIVE="-all_load"
|
||||
CLDNOWHOLEARCHIVE=
|
||||
LD_DEPS=
|
||||
LD_FLAGS=
|
||||
SOFLAG="-dynamiclib"
|
||||
DEVMAPPER=no
|
||||
ODIRECT=no ;;
|
||||
esac
|
||||
|
||||
dnl -- prefix is /usr by default, the exec_prefix default is setup later
|
||||
AC_PREFIX_DEFAULT(/usr)
|
||||
|
||||
OWNER="root"
|
||||
GROUP="root"
|
||||
|
||||
dnl -- setup the ownership of the files
|
||||
AC_ARG_WITH(user,
|
||||
[ --with-user=USER Set the owner of installed files ],
|
||||
[ OWNER="$withval" ],
|
||||
[ OWNER="root" ])
|
||||
[ OWNER="$withval" ])
|
||||
|
||||
if test x$OWNER != x; then
|
||||
OWNER="-o $OWNER"
|
||||
fi
|
||||
|
||||
dnl -- setup the group ownership of the files
|
||||
AC_ARG_WITH(group,
|
||||
[ --with-group=GROUP Set the group owner of installed files ],
|
||||
[ GROUP="$withval" ],
|
||||
[ GROUP="root" ])
|
||||
[ GROUP="$withval" ])
|
||||
|
||||
if test x$GROUP != x; then
|
||||
GROUP="-g $GROUP"
|
||||
fi
|
||||
|
||||
dnl -- LVM1 tool fallback option
|
||||
AC_ARG_ENABLE(lvm1_fallback, [ --enable-lvm1_fallback Use this to fall back and use LVM1 binaries if
|
||||
device-mapper is missing from the kernel], LVM1_FALLBACK=$enableval, LVM1_FALLBACK=no)
|
||||
|
||||
if test x$LVM1_FALLBACK = xyes; then
|
||||
CFLAGS="$CFLAGS -DLVM1_FALLBACK"
|
||||
fi
|
||||
|
||||
dnl -- format1 inclusion type
|
||||
AC_ARG_WITH(lvm1,
|
||||
@@ -87,10 +121,65 @@ if test x$LVM1 = xinternal; then
|
||||
CFLAGS="$CFLAGS -DLVM1_INTERNAL"
|
||||
fi
|
||||
|
||||
dnl -- format_pool inclusion type
|
||||
AC_ARG_WITH(pool,
|
||||
[ --with-pool=TYPE GFS pool read-only support: internal/shared/none
|
||||
[TYPE=internal] ],
|
||||
[ POOL="$withval" ],
|
||||
[ POOL="internal" ])
|
||||
|
||||
if [[ "x$POOL" != xnone -a "x$POOL" != xinternal -a "x$POOL" != xshared ]];
|
||||
then AC_MSG_ERROR(
|
||||
--with-pool parameter invalid
|
||||
)
|
||||
exit
|
||||
fi;
|
||||
|
||||
if test x$POOL = xinternal; then
|
||||
CFLAGS="$CFLAGS -DPOOL_INTERNAL"
|
||||
fi
|
||||
|
||||
|
||||
AC_ARG_ENABLE(jobs, [ --enable-jobs=NUM Number of jobs to run simultaneously], JOBS=-j$enableval, JOBS=-j2)
|
||||
|
||||
dnl Enables staticly linked tools
|
||||
AC_ARG_ENABLE(static_link, [ --enable-static_link Use this to link the tools to the liblvm library
|
||||
dnl -- snapshots inclusion type
|
||||
AC_ARG_WITH(snapshots,
|
||||
[ --with-snapshots=TYPE Snapshot support: internal/shared/none
|
||||
[TYPE=internal] ],
|
||||
[ SNAPSHOTS="$withval" ],
|
||||
[ SNAPSHOTS="internal" ])
|
||||
|
||||
if [[ "x$SNAPSHOTS" != xnone -a "x$SNAPSHOTS" != xinternal -a "x$SNAPSHOTS" != xshared ]];
|
||||
then AC_MSG_ERROR(
|
||||
--with-snapshots parameter invalid
|
||||
)
|
||||
exit
|
||||
fi;
|
||||
|
||||
if test x$SNAPSHOTS = xinternal; then
|
||||
CFLAGS="$CFLAGS -DSNAPSHOT_INTERNAL"
|
||||
fi
|
||||
|
||||
dnl -- mirrors inclusion type
|
||||
AC_ARG_WITH(mirrors,
|
||||
[ --with-mirrors=TYPE Mirror support: internal/shared/none
|
||||
[TYPE=internal] ],
|
||||
[ MIRRORS="$withval" ],
|
||||
[ MIRRORS="internal" ])
|
||||
|
||||
if [[ "x$MIRRORS" != xnone -a "x$MIRRORS" != xinternal -a "x$MIRRORS" != xshared ]];
|
||||
then AC_MSG_ERROR(
|
||||
--with-mirrors parameter invalid
|
||||
)
|
||||
exit
|
||||
fi;
|
||||
|
||||
if test x$MIRRORS = xinternal; then
|
||||
CFLAGS="$CFLAGS -DMIRRORED_INTERNAL"
|
||||
fi
|
||||
|
||||
dnl Enables staticly-linked tools
|
||||
AC_ARG_ENABLE(static_link, [ --enable-static_link Use this to link the tools to their libraries
|
||||
statically. Default is dynamic linking], STATIC_LINK=$enableval, STATIC_LINK=no)
|
||||
|
||||
dnl Enable readline
|
||||
@@ -101,26 +190,42 @@ if test x$READLINE = xyes; then
|
||||
CFLAGS="$CFLAGS -DREADLINE_SUPPORT"
|
||||
fi
|
||||
|
||||
echo $ac_n "checking whether to enable debugging""... $ac_c" 1>&6
|
||||
dnl Enable Debugging
|
||||
AC_ARG_ENABLE(debug, [ --enable-debug Enable debugging], \
|
||||
DEBUG=yes, DEBUG=no)
|
||||
echo "$ac_t""$DEBUG" 1>&6
|
||||
|
||||
echo $ac_n "checking whether to enable device-mapper""... $ac_c" 1>&6
|
||||
dnl Disable devmapper
|
||||
AC_ARG_ENABLE(devmapper, [ --disable-devmapper Disable device-mapper interaction], \
|
||||
DEVMAPPER=no, DEVMAPPER=yes)
|
||||
DEVMAPPER=no)
|
||||
echo "$ac_t""$DEVMAPPER" 1>&6
|
||||
|
||||
if test x$DEVMAPPER = xyes; then
|
||||
CFLAGS="$CFLAGS -DDEVMAPPER_SUPPORT"
|
||||
fi
|
||||
|
||||
echo $ac_n "checking whether to enable O_DIRECT""... $ac_c" 1>&6
|
||||
dnl Disable O_DIRECT
|
||||
AC_ARG_ENABLE(o_direct, [ --disable-o_direct Disable O_DIRECT], \
|
||||
ODIRECT=no, ODIRECT=yes)
|
||||
ODIRECT=no)
|
||||
echo "$ac_t""$ODIRECT" 1>&6
|
||||
|
||||
if test x$ODIRECT = xyes; then
|
||||
CFLAGS="$CFLAGS -DO_DIRECT_SUPPORT"
|
||||
fi
|
||||
|
||||
echo $ac_n "checking whether to compile liblvm2cmd.so""... $ac_c" 1>&6
|
||||
dnl Enable cmdlib
|
||||
AC_ARG_ENABLE(cmdlib, [ --enable-cmdlib Build shared command library], \
|
||||
CMDLIB=yes, CMDLIB=no)
|
||||
echo "$ac_t""$CMDLIB" 1>&6
|
||||
|
||||
if test x$CMDLIB = xyes; then
|
||||
CFLAGS="$CFLAGS -DCMDLIB"
|
||||
fi
|
||||
|
||||
dnl Mess with default exec_prefix
|
||||
if [[ "x$exec_prefix" = xNONE -a "x$prefix" = xNONE ]];
|
||||
then exec_prefix="";
|
||||
@@ -152,9 +257,29 @@ fi
|
||||
dnl Check for dlopen
|
||||
AC_CHECK_LIB(dl, dlopen, HAVE_LIBDL=yes, HAVE_LIBDL=no)
|
||||
|
||||
if test x$HAVE_LIBDL = xyes; then
|
||||
if [[ "x$HAVE_LIBDL" = xyes -a "x$STATIC_LINK" = xno ]]; then
|
||||
CFLAGS="$CFLAGS -DHAVE_LIBDL"
|
||||
LIBS="-ldl $LIBS"
|
||||
else
|
||||
HAVE_LIBDL=no
|
||||
fi
|
||||
|
||||
dnl Check for shared/static conflicts
|
||||
if [[ \( "x$LVM1" = xshared -o "x$POOL" = xshared -o \
|
||||
"x$SNAPSHOTS" = xshared -o "x$MIRRORS" = xshared \
|
||||
\) -a "x$STATIC_LINK" = xyes ]];
|
||||
then AC_MSG_ERROR(
|
||||
Features cannot be 'shared' when building statically
|
||||
)
|
||||
exit
|
||||
fi
|
||||
|
||||
dnl Check for is_selinux_enabled
|
||||
AC_CHECK_LIB(selinux, is_selinux_enabled, HAVE_SELINUX=yes, HAVE_SELINUX=no)
|
||||
|
||||
if test x$HAVE_SELINUX = xyes; then
|
||||
CFLAGS="$CFLAGS -DHAVE_SELINUX"
|
||||
LIBS="-lselinux $LIBS"
|
||||
fi
|
||||
|
||||
dnl Check for getopt
|
||||
@@ -177,6 +302,39 @@ package as well (which may be called readline-devel or something similar).
|
||||
|
||||
fi
|
||||
|
||||
echo $ac_n "checking whether to enable internationalisation""... $ac_c" 1>&6
|
||||
dnl Internationalisation stuff
|
||||
AC_ARG_ENABLE(nls, [ --enable-nls Enable Native Language Support],\
|
||||
INTL=yes, INTL=no)
|
||||
echo "$ac_t""$INTL" 1>&6
|
||||
|
||||
if test x$INTL = xyes; then
|
||||
INTL_PACKAGE="lvm2"
|
||||
AC_PATH_PROG(MSGFMT, msgfmt)
|
||||
if [[ "x$MSGFMT" == x ]];
|
||||
then AC_MSG_ERROR(
|
||||
msgfmt not found in path $PATH
|
||||
)
|
||||
exit
|
||||
fi;
|
||||
|
||||
AC_ARG_WITH(localedir,
|
||||
[ --with-localedir=DIR Translation files in DIR [PREFIX/share/locale]],
|
||||
[ LOCALEDIR="$withval" ],
|
||||
[ LOCALEDIR='${prefix}/share/locale' ])
|
||||
fi
|
||||
|
||||
AC_ARG_WITH(confdir,
|
||||
[ --with-confdir=DIR Configuration files in DIR [/etc]],
|
||||
[ CONFDIR="$withval" ],
|
||||
[ CONFDIR='/etc' ])
|
||||
|
||||
AC_ARG_WITH(staticdir,
|
||||
[ --with-staticdir=DIR Static binary in DIR [EXEC_PREFIX/sbin]],
|
||||
[ STATICDIR="$withval" ],
|
||||
[ STATICDIR='${exec_prefix}/sbin' ])
|
||||
|
||||
|
||||
if test "-f VERSION"; then
|
||||
LVM_VERSION="\"`cat VERSION`\""
|
||||
else
|
||||
@@ -186,23 +344,47 @@ fi
|
||||
AC_SUBST(JOBS)
|
||||
AC_SUBST(STATIC_LINK)
|
||||
AC_SUBST(LVM1)
|
||||
AC_SUBST(POOL)
|
||||
AC_SUBST(SNAPSHOTS)
|
||||
AC_SUBST(MIRRORS)
|
||||
AC_SUBST(OWNER)
|
||||
AC_SUBST(GROUP)
|
||||
AC_SUBST(CFLAGS)
|
||||
AC_SUBST(CLDFLAGS)
|
||||
AC_SUBST(CLDWHOLEARCHIVE)
|
||||
AC_SUBST(CLDNOWHOLEARCHIVE)
|
||||
AC_SUBST(LD_DEPS)
|
||||
AC_SUBST(LD_FLAGS)
|
||||
AC_SUBST(SOFLAG)
|
||||
AC_SUBST(LIBS)
|
||||
AC_SUBST(LVM_VERSION)
|
||||
AC_SUBST(LVM1_FALLBACK)
|
||||
AC_SUBST(DEBUG)
|
||||
AC_SUBST(DEVMAPPER)
|
||||
AC_SUBST(HAVE_LIBDL)
|
||||
AC_SUBST(HAVE_SELINUX)
|
||||
AC_SUBST(CMDLIB)
|
||||
AC_SUBST(MSGFMT)
|
||||
AC_SUBST(LOCALEDIR)
|
||||
AC_SUBST(CONFDIR)
|
||||
AC_SUBST(STATICDIR)
|
||||
AC_SUBST(INTL_PACKAGE)
|
||||
AC_SUBST(INTL)
|
||||
|
||||
dnl First and last lines should not contain files to generate in order to
|
||||
dnl keep utility scripts running properly
|
||||
AC_OUTPUT( \
|
||||
Makefile \
|
||||
make.tmpl \
|
||||
doc/Makefile \
|
||||
include/Makefile \
|
||||
lib/Makefile \
|
||||
lib/format1/Makefile \
|
||||
lib/format_pool/Makefile \
|
||||
lib/mirror/Makefile \
|
||||
lib/snapshot/Makefile \
|
||||
man/Makefile \
|
||||
po/Makefile \
|
||||
tools/Makefile \
|
||||
tools/version.h \
|
||||
test/mm/Makefile \
|
||||
|
29
doc/Makefile.in
Normal file
29
doc/Makefile.in
Normal file
@@ -0,0 +1,29 @@
|
||||
#
|
||||
# Copyright (C) 2004 Red Hat, Inc. All rights reserved.
|
||||
#
|
||||
# This file is part of the LVM2.
|
||||
#
|
||||
# This copyrighted material is made available to anyone wishing to use,
|
||||
# modify, copy, or redistribute it subject to the terms and conditions
|
||||
# of the GNU General Public License v.2.
|
||||
#
|
||||
# You should have received a copy of the GNU General Public License
|
||||
# along with this program; if not, write to the Free Software Foundation,
|
||||
# Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
|
||||
srcdir = @srcdir@
|
||||
top_srcdir = @top_srcdir@
|
||||
VPATH = @srcdir@
|
||||
|
||||
CONFSRC=example.conf
|
||||
CONFDEST=lvm.conf
|
||||
|
||||
include ../make.tmpl
|
||||
|
||||
install:
|
||||
@if [ ! -e $(confdir)/$(CONFDEST) ]; then \
|
||||
echo "Installing $(CONFSRC) as $(confdir)/$(CONFDEST)"; \
|
||||
@INSTALL@ -D $(OWNER) $(GROUP) -m 644 $(CONFSRC) \
|
||||
$(confdir)/$(CONFDEST); \
|
||||
fi
|
||||
|
@@ -27,9 +27,6 @@ devices {
|
||||
# the device will be accepted or rejected (ignored). Devices that
|
||||
# don't match any patterns are accepted.
|
||||
|
||||
# If using RAID md devices as physical volumes, you should
|
||||
# set up a filter here to reject the constituent devices.
|
||||
|
||||
# Remember to run vgscan after you change this parameter to ensure
|
||||
# that the cache file gets regenerated (see below).
|
||||
|
||||
@@ -57,10 +54,21 @@ devices {
|
||||
# You can turn off writing this cache file by setting this to 0.
|
||||
write_cache_state = 1
|
||||
|
||||
# An advanced setting.
|
||||
# Advanced settings.
|
||||
|
||||
# List of pairs of additional acceptable block device types found
|
||||
# in /proc/devices with maximum (non-zero) number of partitions.
|
||||
# types = [ "fd", 16 ]
|
||||
|
||||
# If sysfs is mounted (2.6 kernels) restrict device scanning to
|
||||
# the block devices it believes are valid.
|
||||
# 1 enables; 0 disables.
|
||||
sysfs_scan = 1
|
||||
|
||||
# By default, LVM2 will ignore devices used as components of
|
||||
# software RAID (md) devices by looking for md superblocks.
|
||||
# 1 enables; 0 disables.
|
||||
md_component_detection = 1
|
||||
}
|
||||
|
||||
# This section that allows you to configure the nature of the
|
||||
@@ -171,6 +179,16 @@ global {
|
||||
# setting this to 0 should suppress the error messages.
|
||||
activation = 1
|
||||
|
||||
# If we can't communicate with device-mapper, should we try running
|
||||
# the LVM1 tools?
|
||||
# This option only applies to 2.4 kernels and is provided to help you
|
||||
# switch between device-mapper kernels and LVM1 kernels.
|
||||
# The LVM1 tools need to be installed with .lvm1 suffices
|
||||
# e.g. vgscan.lvm1 and they will stop working after you start using
|
||||
# the new lvm2 on-disk metadata format.
|
||||
# The default value is set when the tools are built.
|
||||
# fallback_to_lvm1 = 0
|
||||
|
||||
# The default metadata format that commands should use - "lvm1" or "lvm2".
|
||||
# The command line override is -M1 or -M2.
|
||||
# Defaults to "lvm1" if compiled in, else "lvm2".
|
||||
@@ -215,6 +233,14 @@ activation {
|
||||
|
||||
# Nice value used while devices suspended
|
||||
process_priority = -18
|
||||
|
||||
# If volume_list is defined, each LV is only activated if there is a
|
||||
# match against the list.
|
||||
# "vgname" and "vgname/lvname" are matched exactly.
|
||||
# "@tag" matches any tag set in the LV or VG.
|
||||
# "@*" matches if any tag defined on the host is also set in the LV or VG
|
||||
#
|
||||
# volume_list = [ "vg1", "vg2/lvol1", "@tag1", "@*" ]
|
||||
}
|
||||
|
||||
|
||||
|
47
doc/example_cmdlib.c
Normal file
47
doc/example_cmdlib.c
Normal file
@@ -0,0 +1,47 @@
|
||||
/*
|
||||
* Copyright (C) 2004 Red Hat, Inc. All rights reserved.
|
||||
*
|
||||
* This file is part of LVM2.
|
||||
*
|
||||
* This copyrighted material is made available to anyone wishing to use,
|
||||
* modify, copy, or redistribute it subject to the terms and conditions
|
||||
* of the GNU General Public License v.2.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software Foundation,
|
||||
* Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
*/
|
||||
|
||||
#include "lvm2cmd.h"
|
||||
|
||||
/* All output gets passed to this function line-by-line */
|
||||
void test_log_fn(int level, const char *file, int line, const char *format)
|
||||
{
|
||||
/* Extract and process output here rather than printing it */
|
||||
|
||||
if (level != 4)
|
||||
return;
|
||||
|
||||
printf("%s\n", format);
|
||||
return;
|
||||
}
|
||||
|
||||
int main(int argc, char **argv)
|
||||
{
|
||||
void *handle;
|
||||
int r;
|
||||
|
||||
lvm2_log_fn(test_log_fn);
|
||||
|
||||
handle = lvm2_init();
|
||||
|
||||
lvm2_log_level(handle, 1);
|
||||
r = lvm2_run(handle, "vgs --noheadings vg1");
|
||||
|
||||
/* More commands here */
|
||||
|
||||
lvm2_exit(handle);
|
||||
|
||||
return r;
|
||||
}
|
||||
|
@@ -1,4 +1,5 @@
|
||||
../lib/activate/activate.h
|
||||
../lib/activate/targets.h
|
||||
../lib/cache/lvmcache.h
|
||||
../lib/commands/errors.h
|
||||
../lib/commands/toolcontext.h
|
||||
@@ -14,25 +15,34 @@
|
||||
../lib/device/device.h
|
||||
../lib/display/display.h
|
||||
../lib/filters/filter-composite.h
|
||||
../lib/filters/filter-md.h
|
||||
../lib/filters/filter-persistent.h
|
||||
../lib/filters/filter-regex.h
|
||||
../lib/filters/filter-sysfs.h
|
||||
../lib/filters/filter.h
|
||||
../lib/format1/format1.h
|
||||
../lib/format_pool/format_pool.h
|
||||
../lib/format_text/format-text.h
|
||||
../lib/format_text/text_export.h
|
||||
../lib/format_text/text_import.h
|
||||
../lib/label/label.h
|
||||
../lib/locking/locking.h
|
||||
../lib/log/log.h
|
||||
../lib/metadata/lv_alloc.h
|
||||
../lib/metadata/metadata.h
|
||||
../lib/metadata/segtypes.h
|
||||
../lib/mm/dbg_malloc.h
|
||||
../lib/mm/memlock.h
|
||||
../lib/mm/pool.h
|
||||
../lib/mm/xlate.h
|
||||
../lib/misc/crc.h
|
||||
../lib/misc/intl.h
|
||||
../lib/misc/lib.h
|
||||
../lib/misc/lvm-file.h
|
||||
../lib/misc/lvm-string.h
|
||||
../lib/misc/selinux.h
|
||||
../lib/misc/sharedlib.h
|
||||
../lib/regex/matcher.h
|
||||
../lib/report/report.h
|
||||
../lib/uuid/uuid.h
|
||||
../po/pogen.h
|
||||
|
@@ -1,20 +1,16 @@
|
||||
#
|
||||
# Copyright (C) 2001 Sistina Software
|
||||
# Copyright (C) 2001-2004 Sistina Software, Inc. All rights reserved.
|
||||
# Copyright (C) 2004 Red Hat, Inc. All rights reserved.
|
||||
#
|
||||
# This LVM library is free software; you can redistribute it and/or
|
||||
# modify it under the terms of the GNU Library General Public
|
||||
# License as published by the Free Software Foundation; either
|
||||
# version 2 of the License, or (at your option) any later version.
|
||||
# This file is part of the LVM2.
|
||||
#
|
||||
# This LVM library is distributed in the hope that it will be useful,
|
||||
# but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
# Library General Public License for more details.
|
||||
# This copyrighted material is made available to anyone wishing to use,
|
||||
# modify, copy, or redistribute it subject to the terms and conditions
|
||||
# of the GNU General Public License v.2.
|
||||
#
|
||||
# You should have received a copy of the GNU Library General Public
|
||||
# License along with this LVM library; if not, write to the Free
|
||||
# Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
|
||||
# MA 02111-1307, USA
|
||||
# You should have received a copy of the GNU General Public License
|
||||
# along with this program; if not, write to the Free Software Foundation,
|
||||
# Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
|
||||
SHELL = /bin/sh
|
||||
|
||||
@@ -35,9 +31,11 @@ distclean:
|
||||
find . -maxdepth 1 -type l -exec $(RM) \{\} \;
|
||||
$(RM) Makefile .include_symlinks .symlinks_created
|
||||
|
||||
pofile: all
|
||||
|
||||
clean:
|
||||
|
||||
install:
|
||||
|
||||
.PHONY: clean distclean all install
|
||||
.PHONY: clean distclean all install pofile
|
||||
|
||||
|
@@ -1,8 +1,16 @@
|
||||
#
|
||||
# Copyright (C) 2001 Sistina Software (UK) Limited
|
||||
# Copyright (C) 2001-2004 Sistina Software, Inc. All rights reserved.
|
||||
# Copyright (C) 2004 Red Hat, Inc. All rights reserved.
|
||||
#
|
||||
# This file is released under the GPL.
|
||||
# This file is part of the LVM2.
|
||||
#
|
||||
# This copyrighted material is made available to anyone wishing to use,
|
||||
# modify, copy, or redistribute it subject to the terms and conditions
|
||||
# of the GNU General Public License v.2.
|
||||
#
|
||||
# You should have received a copy of the GNU General Public License
|
||||
# along with this program; if not, write to the Free Software Foundation,
|
||||
# Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
|
||||
srcdir = @srcdir@
|
||||
top_srcdir = @top_srcdir@
|
||||
@@ -12,7 +20,19 @@ ifeq ("@LVM1@", "shared")
|
||||
SUBDIRS = format1
|
||||
endif
|
||||
|
||||
SOURCES=\
|
||||
ifeq ("@POOL@", "shared")
|
||||
SUBDIRS += format_pool
|
||||
endif
|
||||
|
||||
ifeq ("@SNAPSHOTS@", "shared")
|
||||
SUBDIRS += snapshot
|
||||
endif
|
||||
|
||||
ifeq ("@MIRRORS@", "shared")
|
||||
SUBDIRS += mirror
|
||||
endif
|
||||
|
||||
SOURCES =\
|
||||
activate/activate.c \
|
||||
cache/lvmcache.c \
|
||||
commands/toolcontext.c \
|
||||
@@ -25,9 +45,12 @@ SOURCES=\
|
||||
device/dev-io.c \
|
||||
device/device.c \
|
||||
display/display.c \
|
||||
error/errseg.c \
|
||||
filters/filter-composite.c \
|
||||
filters/filter-persistent.c \
|
||||
filters/filter-regex.c \
|
||||
filters/filter-sysfs.c \
|
||||
filters/filter-md.c \
|
||||
filters/filter.c \
|
||||
format_text/archive.c \
|
||||
format_text/export.c \
|
||||
@@ -35,6 +58,7 @@ SOURCES=\
|
||||
format_text/format-text.c \
|
||||
format_text/import.c \
|
||||
format_text/import_vsn1.c \
|
||||
format_text/tags.c \
|
||||
format_text/text_label.c \
|
||||
label/label.c \
|
||||
locking/file_locking.c \
|
||||
@@ -46,6 +70,7 @@ SOURCES=\
|
||||
metadata/metadata.c \
|
||||
metadata/mirror.c \
|
||||
metadata/pv_map.c \
|
||||
metadata/segtypes.c \
|
||||
metadata/snapshot_manip.c \
|
||||
misc/crc.c \
|
||||
misc/lvm-file.c \
|
||||
@@ -56,10 +81,12 @@ SOURCES=\
|
||||
regex/parse_rx.c \
|
||||
regex/ttree.c \
|
||||
report/report.c \
|
||||
uuid/uuid.c
|
||||
striped/striped.c \
|
||||
uuid/uuid.c \
|
||||
zero/zero.c
|
||||
|
||||
ifeq ("@LVM1@", "internal")
|
||||
SOURCES+=\
|
||||
SOURCES +=\
|
||||
format1/disk-rep.c \
|
||||
format1/format1.c \
|
||||
format1/import-export.c \
|
||||
@@ -69,29 +96,45 @@ ifeq ("@LVM1@", "internal")
|
||||
format1/vg_number.c
|
||||
endif
|
||||
|
||||
ifeq ("@POOL@", "internal")
|
||||
SOURCES +=\
|
||||
format_pool/disk_rep.c \
|
||||
format_pool/format_pool.c \
|
||||
format_pool/import_export.c \
|
||||
format_pool/pool_label.c
|
||||
endif
|
||||
|
||||
ifeq ("@SNAPSHOTS@", "internal")
|
||||
SOURCES += snapshot/snapshot.c
|
||||
endif
|
||||
|
||||
ifeq ("@MIRRORS@", "internal")
|
||||
SOURCES += mirror/mirrored.c
|
||||
endif
|
||||
|
||||
ifeq ("@DEBUG@", "yes")
|
||||
SOURCES+=\
|
||||
mm/dbg_malloc.c
|
||||
SOURCES += mm/dbg_malloc.c
|
||||
endif
|
||||
|
||||
ifeq ("@DEVMAPPER@", "yes")
|
||||
SOURCES+=\
|
||||
SOURCES +=\
|
||||
activate/dev_manager.c \
|
||||
activate/fs.c
|
||||
endif
|
||||
|
||||
ifeq ("@HAVE_LIBDL@", "yes")
|
||||
SOURCES+=\
|
||||
SOURCES +=\
|
||||
locking/external_locking.c \
|
||||
misc/sharedlib.c
|
||||
endif
|
||||
|
||||
TARGETS=liblvm.a
|
||||
ifeq ("@HAVE_SELINUX@", "yes")
|
||||
SOURCES += misc/selinux.c
|
||||
endif
|
||||
|
||||
LIB_STATIC = liblvm.a
|
||||
|
||||
$(SUBDIRS): $(LIB_STATIC)
|
||||
|
||||
include ../make.tmpl
|
||||
|
||||
liblvm.a: $(OBJECTS)
|
||||
$(RM) $@
|
||||
$(AR) r $@ $(OBJECTS)
|
||||
$(RANLIB) $@
|
||||
|
||||
|
@@ -1,7 +1,16 @@
|
||||
/*
|
||||
* Copyright (C) 2001 Sistina Software (UK) Limited.
|
||||
* Copyright (C) 2001-2004 Sistina Software, Inc. All rights reserved.
|
||||
* Copyright (C) 2004 Red Hat, Inc. All rights reserved.
|
||||
*
|
||||
* This file is released under the LGPL.
|
||||
* This file is part of LVM2.
|
||||
*
|
||||
* This copyrighted material is made available to anyone wishing to use,
|
||||
* modify, copy, or redistribute it subject to the terms and conditions
|
||||
* of the GNU General Public License v.2.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software Foundation,
|
||||
* Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
*/
|
||||
|
||||
#include "lib.h"
|
||||
@@ -10,10 +19,13 @@
|
||||
#include "memlock.h"
|
||||
#include "display.h"
|
||||
#include "fs.h"
|
||||
#include "lvm-file.h"
|
||||
#include "lvm-string.h"
|
||||
#include "pool.h"
|
||||
#include "toolcontext.h"
|
||||
#include "dev_manager.h"
|
||||
#include "str_list.h"
|
||||
#include "config.h"
|
||||
|
||||
#include <limits.h>
|
||||
#include <fcntl.h>
|
||||
@@ -21,12 +33,34 @@
|
||||
|
||||
#define _skip(fmt, args...) log_very_verbose("Skipping: " fmt , ## args)
|
||||
|
||||
int lvm1_present(struct cmd_context *cmd)
|
||||
{
|
||||
char path[PATH_MAX];
|
||||
|
||||
if (lvm_snprintf(path, sizeof(path), "%s/lvm/global", cmd->proc_dir)
|
||||
< 0) {
|
||||
log_error("LVM1 proc global snprintf failed");
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (path_exists(path))
|
||||
return 1;
|
||||
else
|
||||
return 0;
|
||||
}
|
||||
|
||||
#ifndef DEVMAPPER_SUPPORT
|
||||
void set_activation(int act)
|
||||
{
|
||||
if (act)
|
||||
log_error("Compiled without libdevmapper support. "
|
||||
"Can't enable activation.");
|
||||
static int warned = 0;
|
||||
|
||||
if (warned || !act)
|
||||
return;
|
||||
|
||||
log_error("Compiled without libdevmapper support. "
|
||||
"Can't enable activation.");
|
||||
|
||||
warned = 1;
|
||||
}
|
||||
int activation(void)
|
||||
{
|
||||
@@ -40,10 +74,19 @@ int driver_version(char *version, size_t size)
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
int target_present(const char *target_name)
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
int lv_info(const struct logical_volume *lv, struct lvinfo *info)
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
int lv_info_by_lvid(struct cmd_context *cmd, const char *lvid_s,
|
||||
struct lvinfo *info)
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
int lv_snapshot_percent(struct logical_volume *lv, float *percent)
|
||||
{
|
||||
return 0;
|
||||
@@ -61,10 +104,18 @@ int lvs_in_vg_opened(struct volume_group *vg)
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
int lv_suspend(struct cmd_context *cmd, const char *lvid_s)
|
||||
{
|
||||
return 1;
|
||||
}
|
||||
int lv_suspend_if_active(struct cmd_context *cmd, const char *lvid_s)
|
||||
{
|
||||
return 1;
|
||||
}
|
||||
int lv_resume(struct cmd_context *cmd, const char *lvid_s)
|
||||
{
|
||||
return 1;
|
||||
}
|
||||
int lv_resume_if_active(struct cmd_context *cmd, const char *lvid_s)
|
||||
{
|
||||
return 1;
|
||||
@@ -73,10 +124,19 @@ int lv_deactivate(struct cmd_context *cmd, const char *lvid_s)
|
||||
{
|
||||
return 1;
|
||||
}
|
||||
int lv_activation_filter(struct cmd_context *cmd, const char *lvid_s,
|
||||
int *activate_lv)
|
||||
{
|
||||
return 1;
|
||||
}
|
||||
int lv_activate(struct cmd_context *cmd, const char *lvid_s)
|
||||
{
|
||||
return 1;
|
||||
}
|
||||
int lv_activate_with_filter(struct cmd_context *cmd, const char *lvid_s)
|
||||
{
|
||||
return 1;
|
||||
}
|
||||
|
||||
int lv_mknodes(struct cmd_context *cmd, const struct logical_volume *lv)
|
||||
{
|
||||
@@ -111,6 +171,86 @@ int activation(void)
|
||||
return _activation;
|
||||
}
|
||||
|
||||
static int _passes_activation_filter(struct cmd_context *cmd,
|
||||
struct logical_volume *lv)
|
||||
{
|
||||
const struct config_node *cn;
|
||||
struct config_value *cv;
|
||||
char *str;
|
||||
char path[PATH_MAX];
|
||||
|
||||
if (!(cn = find_config_node(cmd->cft->root, "activation/volume_list"))) {
|
||||
/* If no host tags defined, activate */
|
||||
if (list_empty(&cmd->tags))
|
||||
return 1;
|
||||
|
||||
/* If any host tag matches any LV or VG tag, activate */
|
||||
if (str_list_match_list(&cmd->tags, &lv->tags) ||
|
||||
str_list_match_list(&cmd->tags, &lv->vg->tags))
|
||||
return 1;
|
||||
|
||||
/* Don't activate */
|
||||
return 0;
|
||||
}
|
||||
|
||||
for (cv = cn->v; cv; cv = cv->next) {
|
||||
if (cv->type != CFG_STRING) {
|
||||
log_error("Ignoring invalid string in config file "
|
||||
"activation/volume_list");
|
||||
continue;
|
||||
}
|
||||
str = cv->v.str;
|
||||
if (!*str) {
|
||||
log_error("Ignoring empty string in config file "
|
||||
"activation/volume_list");
|
||||
continue;
|
||||
}
|
||||
|
||||
/* Tag? */
|
||||
if (*str == '@') {
|
||||
str++;
|
||||
if (!*str) {
|
||||
log_error("Ignoring empty tag in config file "
|
||||
"activation/volume_list");
|
||||
continue;
|
||||
}
|
||||
/* If any host tag matches any LV or VG tag, activate */
|
||||
if (!strcmp(str, "*")) {
|
||||
if (str_list_match_list(&cmd->tags, &lv->tags)
|
||||
|| str_list_match_list(&cmd->tags,
|
||||
&lv->vg->tags))
|
||||
return 1;
|
||||
else
|
||||
continue;
|
||||
}
|
||||
/* If supplied tag matches LV or VG tag, activate */
|
||||
if (str_list_match_item(&lv->tags, str) ||
|
||||
str_list_match_item(&lv->vg->tags, str))
|
||||
return 1;
|
||||
else
|
||||
continue;
|
||||
}
|
||||
if (!index(str, '/')) {
|
||||
/* vgname supplied */
|
||||
if (!strcmp(str, lv->vg->name))
|
||||
return 1;
|
||||
else
|
||||
continue;
|
||||
}
|
||||
/* vgname/lvname */
|
||||
if (lvm_snprintf(path, sizeof(path), "%s/%s", lv->vg->name,
|
||||
lv->name) < 0) {
|
||||
log_error("lvm_snprintf error from %s/%s", lv->vg->name,
|
||||
lv->name);
|
||||
continue;
|
||||
}
|
||||
if (!strcmp(path, str))
|
||||
return 1;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
int library_version(char *version, size_t size)
|
||||
{
|
||||
if (!activation())
|
||||
@@ -149,6 +289,46 @@ int driver_version(char *version, size_t size)
|
||||
return r;
|
||||
}
|
||||
|
||||
int target_present(const char *target_name)
|
||||
{
|
||||
int r = 0;
|
||||
struct dm_task *dmt;
|
||||
struct dm_versions *target, *last_target;
|
||||
|
||||
if (!activation())
|
||||
return 0;
|
||||
|
||||
log_very_verbose("Getting target version for %s", target_name);
|
||||
if (!(dmt = dm_task_create(DM_DEVICE_LIST_VERSIONS))) {
|
||||
stack;
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (!dm_task_run(dmt)) {
|
||||
log_debug("Failed to get %s target version", target_name);
|
||||
/* Assume this was because LIST_VERSIONS isn't supported */
|
||||
return 1;
|
||||
}
|
||||
|
||||
target = dm_task_get_versions(dmt);
|
||||
|
||||
do {
|
||||
last_target = target;
|
||||
|
||||
if (!strcmp(target_name, target->name)) {
|
||||
r = 1;
|
||||
goto out;
|
||||
}
|
||||
|
||||
target = (void *) target + target->next;
|
||||
} while (last_target != target);
|
||||
|
||||
out:
|
||||
dm_task_destroy(dmt);
|
||||
|
||||
return r;
|
||||
}
|
||||
|
||||
/*
|
||||
* Returns 1 if info structure populated, else 0 on failure.
|
||||
*/
|
||||
@@ -162,7 +342,7 @@ static int _lv_info(const struct logical_volume *lv, int mknodes,
|
||||
if (!activation())
|
||||
return 0;
|
||||
|
||||
if (!(dm = dev_manager_create(lv->vg->name, lv->vg->cmd->cf))) {
|
||||
if (!(dm = dev_manager_create(lv->vg->cmd, lv->vg->name))) {
|
||||
stack;
|
||||
return 0;
|
||||
}
|
||||
@@ -186,6 +366,17 @@ int lv_info(const struct logical_volume *lv, struct lvinfo *info)
|
||||
return _lv_info(lv, 0, info);
|
||||
}
|
||||
|
||||
int lv_info_by_lvid(struct cmd_context *cmd, const char *lvid_s,
|
||||
struct lvinfo *info)
|
||||
{
|
||||
struct logical_volume *lv;
|
||||
|
||||
if (!(lv = lv_from_lvid(cmd, lvid_s)))
|
||||
return 0;
|
||||
|
||||
return _lv_info(lv, 0, info);
|
||||
}
|
||||
|
||||
/*
|
||||
* Returns 1 if percent set, else 0 on failure.
|
||||
*/
|
||||
@@ -197,7 +388,7 @@ int lv_snapshot_percent(struct logical_volume *lv, float *percent)
|
||||
if (!activation())
|
||||
return 0;
|
||||
|
||||
if (!(dm = dev_manager_create(lv->vg->name, lv->vg->cmd->cf))) {
|
||||
if (!(dm = dev_manager_create(lv->vg->cmd, lv->vg->name))) {
|
||||
stack;
|
||||
return 0;
|
||||
}
|
||||
@@ -216,11 +407,20 @@ int lv_mirror_percent(struct logical_volume *lv, int wait, float *percent,
|
||||
{
|
||||
int r;
|
||||
struct dev_manager *dm;
|
||||
struct lvinfo info;
|
||||
|
||||
if (!activation())
|
||||
return 0;
|
||||
|
||||
if (!(dm = dev_manager_create(lv->vg->name, lv->vg->cmd->cf))) {
|
||||
if (!lv_info(lv, &info)) {
|
||||
stack;
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (!info.exists)
|
||||
return 0;
|
||||
|
||||
if (!(dm = dev_manager_create(lv->vg->cmd, lv->vg->name))) {
|
||||
stack;
|
||||
return 0;
|
||||
}
|
||||
@@ -258,12 +458,12 @@ static int _lv_open_count(struct logical_volume *lv)
|
||||
}
|
||||
|
||||
/* FIXME Need to detect and handle an lv rename */
|
||||
static int _lv_activate(struct logical_volume *lv)
|
||||
static int _lv_activate_lv(struct logical_volume *lv)
|
||||
{
|
||||
int r;
|
||||
struct dev_manager *dm;
|
||||
|
||||
if (!(dm = dev_manager_create(lv->vg->name, lv->vg->cmd->cf))) {
|
||||
if (!(dm = dev_manager_create(lv->vg->cmd, lv->vg->name))) {
|
||||
stack;
|
||||
return 0;
|
||||
}
|
||||
@@ -280,7 +480,7 @@ static int _lv_deactivate(struct logical_volume *lv)
|
||||
int r;
|
||||
struct dev_manager *dm;
|
||||
|
||||
if (!(dm = dev_manager_create(lv->vg->name, lv->vg->cmd->cf))) {
|
||||
if (!(dm = dev_manager_create(lv->vg->cmd, lv->vg->name))) {
|
||||
stack;
|
||||
return 0;
|
||||
}
|
||||
@@ -292,12 +492,12 @@ static int _lv_deactivate(struct logical_volume *lv)
|
||||
return r;
|
||||
}
|
||||
|
||||
static int _lv_suspend(struct logical_volume *lv)
|
||||
static int _lv_suspend_lv(struct logical_volume *lv)
|
||||
{
|
||||
int r;
|
||||
struct dev_manager *dm;
|
||||
|
||||
if (!(dm = dev_manager_create(lv->vg->name, lv->vg->cmd->cf))) {
|
||||
if (!(dm = dev_manager_create(lv->vg->cmd, lv->vg->name))) {
|
||||
stack;
|
||||
return 0;
|
||||
}
|
||||
@@ -310,7 +510,7 @@ static int _lv_suspend(struct logical_volume *lv)
|
||||
}
|
||||
|
||||
/*
|
||||
* These two functions return the number of LVs in the state,
|
||||
* These two functions return the number of visible LVs in the state,
|
||||
* or -1 on error.
|
||||
*/
|
||||
int lvs_in_vg_activated(struct volume_group *vg)
|
||||
@@ -324,7 +524,8 @@ int lvs_in_vg_activated(struct volume_group *vg)
|
||||
|
||||
list_iterate(lvh, &vg->lvs) {
|
||||
lv = list_item(lvh, struct lv_list)->lv;
|
||||
count += (_lv_active(lv) == 1);
|
||||
if (lv->status & VISIBLE_LV)
|
||||
count += (_lv_active(lv) == 1);
|
||||
}
|
||||
|
||||
return count;
|
||||
@@ -341,14 +542,15 @@ int lvs_in_vg_opened(struct volume_group *vg)
|
||||
|
||||
list_iterate(lvh, &vg->lvs) {
|
||||
lv = list_item(lvh, struct lv_list)->lv;
|
||||
count += (_lv_open_count(lv) == 1);
|
||||
if (lv->status & VISIBLE_LV)
|
||||
count += (_lv_open_count(lv) > 0);
|
||||
}
|
||||
|
||||
return count;
|
||||
}
|
||||
|
||||
/* These return success if the device is not active */
|
||||
int lv_suspend_if_active(struct cmd_context *cmd, const char *lvid_s)
|
||||
static int _lv_suspend(struct cmd_context *cmd, const char *lvid_s,
|
||||
int error_if_not_suspended)
|
||||
{
|
||||
struct logical_volume *lv;
|
||||
struct lvinfo info;
|
||||
@@ -370,10 +572,10 @@ int lv_suspend_if_active(struct cmd_context *cmd, const char *lvid_s)
|
||||
}
|
||||
|
||||
if (!info.exists || info.suspended)
|
||||
return 1;
|
||||
return error_if_not_suspended ? 0 : 1;
|
||||
|
||||
memlock_inc();
|
||||
if (!_lv_suspend(lv)) {
|
||||
if (!_lv_suspend_lv(lv)) {
|
||||
memlock_dec();
|
||||
fs_unlock();
|
||||
return 0;
|
||||
@@ -382,7 +584,19 @@ int lv_suspend_if_active(struct cmd_context *cmd, const char *lvid_s)
|
||||
return 1;
|
||||
}
|
||||
|
||||
int lv_resume_if_active(struct cmd_context *cmd, const char *lvid_s)
|
||||
/* Returns success if the device is not active */
|
||||
int lv_suspend_if_active(struct cmd_context *cmd, const char *lvid_s)
|
||||
{
|
||||
return _lv_suspend(cmd, lvid_s, 0);
|
||||
}
|
||||
|
||||
int lv_suspend(struct cmd_context *cmd, const char *lvid_s)
|
||||
{
|
||||
return _lv_suspend(cmd, lvid_s, 1);
|
||||
}
|
||||
|
||||
static int _lv_resume(struct cmd_context *cmd, const char *lvid_s,
|
||||
int error_if_not_active)
|
||||
{
|
||||
struct logical_volume *lv;
|
||||
struct lvinfo info;
|
||||
@@ -404,9 +618,9 @@ int lv_resume_if_active(struct cmd_context *cmd, const char *lvid_s)
|
||||
}
|
||||
|
||||
if (!info.exists || !info.suspended)
|
||||
return 1;
|
||||
return error_if_not_active ? 0 : 1;
|
||||
|
||||
if (!_lv_activate(lv))
|
||||
if (!_lv_activate_lv(lv))
|
||||
return 0;
|
||||
|
||||
memlock_dec();
|
||||
@@ -415,6 +629,17 @@ int lv_resume_if_active(struct cmd_context *cmd, const char *lvid_s)
|
||||
return 1;
|
||||
}
|
||||
|
||||
/* Returns success if the device is not active */
|
||||
int lv_resume_if_active(struct cmd_context *cmd, const char *lvid_s)
|
||||
{
|
||||
return _lv_resume(cmd, lvid_s, 0);
|
||||
}
|
||||
|
||||
int lv_resume(struct cmd_context *cmd, const char *lvid_s)
|
||||
{
|
||||
return _lv_resume(cmd, lvid_s, 1);
|
||||
}
|
||||
|
||||
int lv_deactivate(struct cmd_context *cmd, const char *lvid_s)
|
||||
{
|
||||
struct logical_volume *lv;
|
||||
@@ -440,7 +665,7 @@ int lv_deactivate(struct cmd_context *cmd, const char *lvid_s)
|
||||
if (!info.exists)
|
||||
return 1;
|
||||
|
||||
if (info.open_count) {
|
||||
if (info.open_count && (lv->status & VISIBLE_LV)) {
|
||||
log_error("LV %s/%s in use: not removing", lv->vg->name,
|
||||
lv->name);
|
||||
return 0;
|
||||
@@ -454,7 +679,31 @@ int lv_deactivate(struct cmd_context *cmd, const char *lvid_s)
|
||||
return r;
|
||||
}
|
||||
|
||||
int lv_activate(struct cmd_context *cmd, const char *lvid_s)
|
||||
/* Test if LV passes filter */
|
||||
int lv_activation_filter(struct cmd_context *cmd, const char *lvid_s,
|
||||
int *activate_lv)
|
||||
{
|
||||
struct logical_volume *lv;
|
||||
|
||||
if (!activation())
|
||||
goto activate;
|
||||
|
||||
if (!(lv = lv_from_lvid(cmd, lvid_s)))
|
||||
return 0;
|
||||
|
||||
if (!_passes_activation_filter(cmd, lv)) {
|
||||
log_verbose("Not activating %s/%s due to config file settings",
|
||||
lv->vg->name, lv->name);
|
||||
*activate_lv = 0;
|
||||
return 1;
|
||||
}
|
||||
|
||||
activate:
|
||||
*activate_lv = 1;
|
||||
return 1;
|
||||
}
|
||||
|
||||
static int _lv_activate(struct cmd_context *cmd, const char *lvid_s, int filter)
|
||||
{
|
||||
struct logical_volume *lv;
|
||||
struct lvinfo info;
|
||||
@@ -466,6 +715,12 @@ int lv_activate(struct cmd_context *cmd, const char *lvid_s)
|
||||
if (!(lv = lv_from_lvid(cmd, lvid_s)))
|
||||
return 0;
|
||||
|
||||
if (filter && !_passes_activation_filter(cmd, lv)) {
|
||||
log_verbose("Not activating %s/%s due to config file settings",
|
||||
lv->vg->name, lv->name);
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (test_mode()) {
|
||||
_skip("Activating '%s'.", lv->name);
|
||||
return 1;
|
||||
@@ -480,27 +735,45 @@ int lv_activate(struct cmd_context *cmd, const char *lvid_s)
|
||||
return 1;
|
||||
|
||||
memlock_inc();
|
||||
r = _lv_activate(lv);
|
||||
r = _lv_activate_lv(lv);
|
||||
memlock_dec();
|
||||
fs_unlock();
|
||||
|
||||
return r;
|
||||
}
|
||||
|
||||
/* Activate LV */
|
||||
int lv_activate(struct cmd_context *cmd, const char *lvid_s)
|
||||
{
|
||||
return _lv_activate(cmd, lvid_s, 0);
|
||||
}
|
||||
|
||||
/* Activate LV only if it passes filter */
|
||||
int lv_activate_with_filter(struct cmd_context *cmd, const char *lvid_s)
|
||||
{
|
||||
return _lv_activate(cmd, lvid_s, 1);
|
||||
}
|
||||
|
||||
int lv_mknodes(struct cmd_context *cmd, const struct logical_volume *lv)
|
||||
{
|
||||
struct lvinfo info;
|
||||
int r = 1;
|
||||
|
||||
if (!lv) {
|
||||
r = dev_manager_mknodes();
|
||||
fs_unlock();
|
||||
return r;
|
||||
}
|
||||
|
||||
if (!_lv_info(lv, 1, &info)) {
|
||||
stack;
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (info.exists)
|
||||
r = dev_manager_mknodes(lv);
|
||||
r = dev_manager_lv_mknodes(lv);
|
||||
else
|
||||
r = dev_manager_rmnodes(lv);
|
||||
r = dev_manager_lv_rmnodes(lv);
|
||||
|
||||
fs_unlock();
|
||||
|
||||
|
@@ -1,7 +1,16 @@
|
||||
/*
|
||||
* Copyright (C) 2001 Sistina Software (UK) Limited.
|
||||
* Copyright (C) 2001-2004 Sistina Software, Inc. All rights reserved.
|
||||
* Copyright (C) 2004 Red Hat, Inc. All rights reserved.
|
||||
*
|
||||
* This file is released under the LGPL.
|
||||
* This file is part of LVM2.
|
||||
*
|
||||
* This copyrighted material is made available to anyone wishing to use,
|
||||
* modify, copy, or redistribute it subject to the terms and conditions
|
||||
* of the GNU General Public License v.2.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software Foundation,
|
||||
* Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
*/
|
||||
|
||||
#ifndef LVM_ACTIVATE_H
|
||||
@@ -27,12 +36,18 @@ int activation(void);
|
||||
|
||||
int driver_version(char *version, size_t size);
|
||||
int library_version(char *version, size_t size);
|
||||
int lvm1_present(struct cmd_context *cmd);
|
||||
|
||||
int target_present(const char *target_name);
|
||||
|
||||
void activation_exit(void);
|
||||
|
||||
int lv_suspend(struct cmd_context *cmd, const char *lvid_s);
|
||||
int lv_suspend_if_active(struct cmd_context *cmd, const char *lvid_s);
|
||||
int lv_resume(struct cmd_context *cmd, const char *lvid_s);
|
||||
int lv_resume_if_active(struct cmd_context *cmd, const char *lvid_s);
|
||||
int lv_activate(struct cmd_context *cmd, const char *lvid_s);
|
||||
int lv_activate_with_filter(struct cmd_context *cmd, const char *lvid_s);
|
||||
int lv_deactivate(struct cmd_context *cmd, const char *lvid_s);
|
||||
|
||||
int lv_mknodes(struct cmd_context *cmd, const struct logical_volume *lv);
|
||||
@@ -41,6 +56,15 @@ int lv_mknodes(struct cmd_context *cmd, const struct logical_volume *lv);
|
||||
* Returns 1 if info structure has been populated, else 0.
|
||||
*/
|
||||
int lv_info(const struct logical_volume *lv, struct lvinfo *info);
|
||||
int lv_info_by_lvid(struct cmd_context *cmd, const char *lvid_s,
|
||||
struct lvinfo *info);
|
||||
|
||||
/*
|
||||
* Returns 1 if activate_lv has been set: 1 = activate; 0 = don't.
|
||||
*/
|
||||
int lv_activation_filter(struct cmd_context *cmd, const char *lvid_s,
|
||||
int *activate_lv);
|
||||
|
||||
/*
|
||||
* Returns 1 if percent has been set, else 0.
|
||||
*/
|
||||
|
@@ -1,7 +1,16 @@
|
||||
/*
|
||||
* Copyright (C) 2002 Sistina Software (UK) Limited.
|
||||
* Copyright (C) 2002-2004 Sistina Software, Inc. All rights reserved.
|
||||
* Copyright (C) 2004 Red Hat, Inc. All rights reserved.
|
||||
*
|
||||
* This file is released under the LGPL.
|
||||
* This file is part of LVM2.
|
||||
*
|
||||
* This copyrighted material is made available to anyone wishing to use,
|
||||
* modify, copy, or redistribute it subject to the terms and conditions
|
||||
* of the GNU General Public License v.2.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software Foundation,
|
||||
* Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
*/
|
||||
|
||||
#include "lib.h"
|
||||
@@ -12,7 +21,11 @@
|
||||
#include "lvm-string.h"
|
||||
#include "fs.h"
|
||||
#include "defaults.h"
|
||||
#include "segtypes.h"
|
||||
#include "display.h"
|
||||
#include "toolcontext.h"
|
||||
#include "targets.h"
|
||||
#include "config.h"
|
||||
|
||||
#include <libdevmapper.h>
|
||||
#include <limits.h>
|
||||
@@ -53,13 +66,8 @@ enum {
|
||||
SUSPENDED = 4,
|
||||
NOPROPAGATE = 5,
|
||||
TOPLEVEL = 6,
|
||||
REMOVE = 7
|
||||
};
|
||||
|
||||
enum {
|
||||
MIRR_DISABLED,
|
||||
MIRR_RUNNING,
|
||||
MIRR_COMPLETED
|
||||
REMOVE = 7,
|
||||
RESUME_IMMEDIATE = 8
|
||||
};
|
||||
|
||||
typedef enum {
|
||||
@@ -103,14 +111,14 @@ struct dl_list {
|
||||
};
|
||||
|
||||
static const char *stripe_filler = NULL;
|
||||
static uint32_t mirror_region_size = 0;
|
||||
|
||||
struct dev_manager {
|
||||
struct pool *mem;
|
||||
|
||||
struct config_tree *cf;
|
||||
struct cmd_context *cmd;
|
||||
|
||||
const char *stripe_filler;
|
||||
uint32_t mirror_region_size;
|
||||
void *target_state;
|
||||
uint32_t pvmove_mirror_count;
|
||||
|
||||
char *vg_name;
|
||||
@@ -327,7 +335,7 @@ static int _info_run(const char *name, const char *uuid, struct dm_info *info,
|
||||
static int _info(const char *name, const char *uuid, int mknodes,
|
||||
struct dm_info *info, struct pool *mem, char **uuid_out)
|
||||
{
|
||||
if (!mknodes && uuid && *uuid &&
|
||||
if (!mknodes && uuid && *uuid &&
|
||||
_info_run(NULL, uuid, info, 0, mem, uuid_out) && info->exists)
|
||||
return 1;
|
||||
|
||||
@@ -418,18 +426,16 @@ static int _percent_run(struct dev_manager *dm, const char *name,
|
||||
uint64_t start, length;
|
||||
char *type = NULL;
|
||||
char *params = NULL;
|
||||
float percent2;
|
||||
struct list *segh = &lv->segments;
|
||||
struct lv_segment *seg = NULL;
|
||||
struct segment_type *segtype;
|
||||
|
||||
uint64_t numerator, denominator;
|
||||
uint64_t total_numerator = 0, total_denominator = 0;
|
||||
|
||||
*percent = -1;
|
||||
|
||||
if (!(dmt = _setup_task(name, uuid, event_nr,
|
||||
wait ? DM_DEVICE_WAITEVENT : DM_DEVICE_STATUS)))
|
||||
{
|
||||
wait ? DM_DEVICE_WAITEVENT : DM_DEVICE_STATUS))) {
|
||||
stack;
|
||||
return 0;
|
||||
}
|
||||
@@ -462,40 +468,19 @@ static int _percent_run(struct dev_manager *dm, const char *name,
|
||||
if (!type || !params || strcmp(type, target_type))
|
||||
continue;
|
||||
|
||||
/* Mirror? */
|
||||
if (!strcmp(type, "mirror")) {
|
||||
log_debug("Mirror status: %s", params);
|
||||
if (sscanf(params, "%*d %*x:%*x %*x:%*x %" PRIu64
|
||||
"/%" PRIu64, &numerator,
|
||||
&denominator) != 2) {
|
||||
log_error("Failure parsing mirror status: %s",
|
||||
params);
|
||||
goto out;
|
||||
}
|
||||
total_numerator += numerator;
|
||||
total_denominator += denominator;
|
||||
|
||||
if (seg && (seg->status & PVMOVE))
|
||||
seg->extents_moved = dm->mirror_region_size *
|
||||
numerator / lv->vg->extent_size;
|
||||
if (!(segtype = get_segtype_from_string(dm->cmd, type)))
|
||||
continue;
|
||||
|
||||
if (segtype->ops->target_percent &&
|
||||
!segtype->ops->target_percent(&dm->target_state, dm->mem,
|
||||
dm->cmd->cft, seg, params,
|
||||
&total_numerator,
|
||||
&total_denominator,
|
||||
percent)) {
|
||||
stack;
|
||||
goto out;
|
||||
}
|
||||
|
||||
if (strcmp(type, "snapshot"))
|
||||
continue;
|
||||
|
||||
/* Snapshot */
|
||||
if (index(params, '/')) {
|
||||
if (sscanf(params, "%" PRIu64 "/%" PRIu64,
|
||||
&numerator, &denominator) == 2) {
|
||||
total_numerator += numerator;
|
||||
total_denominator += denominator;
|
||||
}
|
||||
continue;
|
||||
} else if (sscanf(params, "%f", &percent2) == 1) {
|
||||
*percent += percent2;
|
||||
*percent /= 2;
|
||||
}
|
||||
} while (next);
|
||||
|
||||
if (lv && (segh = list_next(&lv->segments, segh))) {
|
||||
@@ -506,7 +491,7 @@ static int _percent_run(struct dev_manager *dm, const char *name,
|
||||
|
||||
if (total_denominator)
|
||||
*percent = (float) total_numerator *100 / total_denominator;
|
||||
else
|
||||
else if (*percent < 0)
|
||||
*percent = 100;
|
||||
|
||||
log_debug("LV percent: %f", *percent);
|
||||
@@ -565,6 +550,55 @@ static int _rename(struct dev_layer *dl, char *newname)
|
||||
return r;
|
||||
}
|
||||
|
||||
static int _suspend_or_resume(const char *name, action_t suspend)
|
||||
{
|
||||
int r;
|
||||
struct dm_task *dmt;
|
||||
int sus = (suspend == SUSPEND) ? 1 : 0;
|
||||
int task = sus ? DM_DEVICE_SUSPEND : DM_DEVICE_RESUME;
|
||||
|
||||
log_very_verbose("%s %s", sus ? "Suspending" : "Resuming", name);
|
||||
if (!(dmt = _setup_task(name, NULL, 0, task))) {
|
||||
stack;
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (!(r = dm_task_run(dmt)))
|
||||
log_error("Couldn't %s device '%s'", sus ? "suspend" : "resume",
|
||||
name);
|
||||
|
||||
dm_task_destroy(dmt);
|
||||
return r;
|
||||
}
|
||||
|
||||
static int _suspend(struct dev_layer *dl)
|
||||
{
|
||||
if (!dl->info.exists || dl->info.suspended)
|
||||
return 1;
|
||||
|
||||
if (!_suspend_or_resume(dl->name, SUSPEND)) {
|
||||
stack;
|
||||
return 0;
|
||||
}
|
||||
|
||||
dl->info.suspended = 1;
|
||||
return 1;
|
||||
}
|
||||
|
||||
static int _resume(struct dev_layer *dl)
|
||||
{
|
||||
if (!dl->info.exists || !dl->info.suspended)
|
||||
return 1;
|
||||
|
||||
if (!_suspend_or_resume(dl->name, RESUME)) {
|
||||
stack;
|
||||
return 0;
|
||||
}
|
||||
|
||||
dl->info.suspended = 0;
|
||||
return 1;
|
||||
}
|
||||
|
||||
static int _load(struct dev_manager *dm, struct dev_layer *dl, int task)
|
||||
{
|
||||
int r = 1;
|
||||
@@ -624,9 +658,9 @@ static int _load(struct dev_manager *dm, struct dev_layer *dl, int task)
|
||||
log_error("Couldn't load device '%s'.", dl->name);
|
||||
if ((dl->lv->minor >= 0 || dl->lv->major >= 0) &&
|
||||
_get_flag(dl, VISIBLE))
|
||||
log_error("Perhaps the persistent device number "
|
||||
"%d:%d is already in use?",
|
||||
dl->lv->major, dl->lv->minor);
|
||||
log_error("Perhaps the persistent device number "
|
||||
"%d:%d is already in use?",
|
||||
dl->lv->major, dl->lv->minor);
|
||||
}
|
||||
|
||||
if (!dm_task_get_info(dmt, &dl->info)) {
|
||||
@@ -641,6 +675,13 @@ static int _load(struct dev_manager *dm, struct dev_layer *dl, int task)
|
||||
goto out;
|
||||
}
|
||||
|
||||
if (_get_flag(dl, RESUME_IMMEDIATE) && dl->info.suspended &&
|
||||
!_resume(dl)) {
|
||||
stack;
|
||||
r = 0;
|
||||
goto out;
|
||||
}
|
||||
|
||||
log_very_verbose("Activated %s %s %03u:%03u", dl->name,
|
||||
dl->dlid, dl->info.major, dl->info.minor);
|
||||
|
||||
@@ -687,55 +728,6 @@ static int _remove(struct dev_layer *dl)
|
||||
return r;
|
||||
}
|
||||
|
||||
static int _suspend_or_resume(const char *name, action_t suspend)
|
||||
{
|
||||
int r;
|
||||
struct dm_task *dmt;
|
||||
int sus = (suspend == SUSPEND) ? 1 : 0;
|
||||
int task = sus ? DM_DEVICE_SUSPEND : DM_DEVICE_RESUME;
|
||||
|
||||
log_very_verbose("%s %s", sus ? "Suspending" : "Resuming", name);
|
||||
if (!(dmt = _setup_task(name, NULL, 0, task))) {
|
||||
stack;
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (!(r = dm_task_run(dmt)))
|
||||
log_error("Couldn't %s device '%s'", sus ? "suspend" : "resume",
|
||||
name);
|
||||
|
||||
dm_task_destroy(dmt);
|
||||
return r;
|
||||
}
|
||||
|
||||
static int _suspend(struct dev_layer *dl)
|
||||
{
|
||||
if (!dl->info.exists || dl->info.suspended)
|
||||
return 1;
|
||||
|
||||
if (!_suspend_or_resume(dl->name, SUSPEND)) {
|
||||
stack;
|
||||
return 0;
|
||||
}
|
||||
|
||||
dl->info.suspended = 1;
|
||||
return 1;
|
||||
}
|
||||
|
||||
static int _resume(struct dev_layer *dl)
|
||||
{
|
||||
if (!dl->info.exists || !dl->info.suspended)
|
||||
return 1;
|
||||
|
||||
if (!_suspend_or_resume(dl->name, RESUME)) {
|
||||
stack;
|
||||
return 0;
|
||||
}
|
||||
|
||||
dl->info.suspended = 0;
|
||||
return 1;
|
||||
}
|
||||
|
||||
/*
|
||||
* The functions that populate the table in a dm_task as part of
|
||||
* a create/reload.
|
||||
@@ -750,98 +742,26 @@ static int _emit_target_line(struct dev_manager *dm, struct dm_task *dmt,
|
||||
size_t paramsize)
|
||||
{
|
||||
uint64_t esize = seg->lv->vg->extent_size;
|
||||
uint32_t s, start_area = 0u, areas = seg->area_count;
|
||||
int w = 0, tw = 0;
|
||||
int w = 0;
|
||||
const char *target = NULL;
|
||||
const char *trailing_space;
|
||||
int mirror_status;
|
||||
struct dev_layer *dl;
|
||||
char devbuf[10];
|
||||
int r;
|
||||
|
||||
switch (seg->type) {
|
||||
case SEG_SNAPSHOT:
|
||||
if (!seg->segtype->ops->compose_target_line) {
|
||||
log_error("_emit_target: Internal error: Can't handle "
|
||||
"SEG_SNAPSHOT");
|
||||
"segment type %s", seg->segtype->name);
|
||||
return 0;
|
||||
/* Target formats:
|
||||
* linear [device offset]+
|
||||
* striped #stripes stripe_size [device offset]+
|
||||
* mirror log_type #log_params [log_params]*
|
||||
* #mirrors [device offset]+
|
||||
*/
|
||||
case SEG_STRIPED:
|
||||
if (areas == 1)
|
||||
target = "linear";
|
||||
else if (areas > 1) {
|
||||
target = "striped";
|
||||
if ((tw = lvm_snprintf(params, paramsize, "%u %u ",
|
||||
areas, seg->stripe_size)) < 0)
|
||||
goto error;
|
||||
w = tw;
|
||||
} else {
|
||||
log_error("_emit_target: Internal error: SEG_STRIPED "
|
||||
"with no stripes");
|
||||
return 0;
|
||||
}
|
||||
break;
|
||||
case SEG_MIRRORED:
|
||||
mirror_status = MIRR_RUNNING;
|
||||
if (seg->status & PVMOVE) {
|
||||
if (seg->extents_moved == seg->area_len) {
|
||||
mirror_status = MIRR_COMPLETED;
|
||||
start_area = 1;
|
||||
} else if (dm->pvmove_mirror_count++) {
|
||||
mirror_status = MIRR_DISABLED;
|
||||
areas = 1;
|
||||
}
|
||||
}
|
||||
if (mirror_status != MIRR_RUNNING) {
|
||||
target = "linear";
|
||||
break;
|
||||
}
|
||||
target = "mirror";
|
||||
if ((tw = lvm_snprintf(params, paramsize, "core 1 %u %u ",
|
||||
dm->mirror_region_size, areas)) < 0)
|
||||
goto error;
|
||||
w = tw;
|
||||
break;
|
||||
}
|
||||
|
||||
for (s = start_area; s < areas; s++, w += tw) {
|
||||
trailing_space = (areas - s - 1) ? " " : "";
|
||||
if ((seg->area[s].type == AREA_PV &&
|
||||
(!seg->area[s].u.pv.pv || !seg->area[s].u.pv.pv->dev)) ||
|
||||
(seg->area[s].type == AREA_LV && !seg->area[s].u.lv.lv))
|
||||
tw = lvm_snprintf(params + w, paramsize - w,
|
||||
"%s 0%s", dm->stripe_filler,
|
||||
trailing_space);
|
||||
else if (seg->area[s].type == AREA_PV)
|
||||
tw = lvm_snprintf(params + w, paramsize - w,
|
||||
"%s %" PRIu64 "%s",
|
||||
dev_name(seg->area[s].u.pv.pv->dev),
|
||||
(seg->area[s].u.pv.pv->pe_start +
|
||||
(esize * seg->area[s].u.pv.pe)),
|
||||
trailing_space);
|
||||
else {
|
||||
if (!(dl = hash_lookup(dm->layers,
|
||||
seg->area[s].u.lv.lv->lvid.s))) {
|
||||
log_error("device layer %s missing from hash",
|
||||
seg->area[s].u.lv.lv->lvid.s);
|
||||
return 0;
|
||||
}
|
||||
if (!dm_format_dev(devbuf, sizeof(devbuf), dl->info.major, dl->info.minor)) {
|
||||
log_error("Failed to format device number as dm target (%u,%u)",
|
||||
dl->info.major, dl->info.minor);
|
||||
return 0;
|
||||
}
|
||||
tw = lvm_snprintf(params + w, paramsize - w,
|
||||
"%s %" PRIu64 "%s", devbuf,
|
||||
esize * seg->area[s].u.lv.le,
|
||||
trailing_space);
|
||||
}
|
||||
|
||||
if (tw < 0)
|
||||
goto error;
|
||||
if ((r = seg->segtype->ops->compose_target_line(dm, dm->mem,
|
||||
dm->cmd->cft,
|
||||
&dm->target_state, seg,
|
||||
params, paramsize,
|
||||
&target, &w,
|
||||
&dm->
|
||||
pvmove_mirror_count)) <=
|
||||
0) {
|
||||
stack;
|
||||
return r;
|
||||
}
|
||||
|
||||
log_debug("Adding target: %" PRIu64 " %" PRIu64 " %s %s",
|
||||
@@ -854,11 +774,62 @@ static int _emit_target_line(struct dev_manager *dm, struct dm_task *dmt,
|
||||
}
|
||||
|
||||
return 1;
|
||||
}
|
||||
|
||||
error:
|
||||
log_debug("Insufficient space in params[%" PRIsize_t "] for target "
|
||||
"parameters.", paramsize);
|
||||
return -1;
|
||||
int compose_areas_line(struct dev_manager *dm, struct lv_segment *seg,
|
||||
char *params, size_t paramsize, int *pos, int start_area,
|
||||
int areas)
|
||||
{
|
||||
uint32_t s;
|
||||
int tw = 0;
|
||||
const char *trailing_space;
|
||||
uint64_t esize = seg->lv->vg->extent_size;
|
||||
struct dev_layer *dl;
|
||||
char devbuf[10];
|
||||
|
||||
for (s = start_area; s < areas; s++, *pos += tw) {
|
||||
trailing_space = (areas - s - 1) ? " " : "";
|
||||
if ((seg->area[s].type == AREA_PV &&
|
||||
(!seg->area[s].u.pv.pv || !seg->area[s].u.pv.pv->dev)) ||
|
||||
(seg->area[s].type == AREA_LV && !seg->area[s].u.lv.lv))
|
||||
tw = lvm_snprintf(params + *pos, paramsize - *pos,
|
||||
"%s 0%s", dm->stripe_filler,
|
||||
trailing_space);
|
||||
else if (seg->area[s].type == AREA_PV)
|
||||
tw = lvm_snprintf(params + *pos, paramsize - *pos,
|
||||
"%s %" PRIu64 "%s",
|
||||
dev_name(seg->area[s].u.pv.pv->dev),
|
||||
(seg->area[s].u.pv.pv->pe_start +
|
||||
(esize * seg->area[s].u.pv.pe)),
|
||||
trailing_space);
|
||||
else {
|
||||
if (!(dl = hash_lookup(dm->layers,
|
||||
seg->area[s].u.lv.lv->lvid.s))) {
|
||||
log_error("device layer %s missing from hash",
|
||||
seg->area[s].u.lv.lv->lvid.s);
|
||||
return 0;
|
||||
}
|
||||
if (!dm_format_dev
|
||||
(devbuf, sizeof(devbuf), dl->info.major,
|
||||
dl->info.minor)) {
|
||||
log_error
|
||||
("Failed to format device number as dm target (%u,%u)",
|
||||
dl->info.major, dl->info.minor);
|
||||
return 0;
|
||||
}
|
||||
tw = lvm_snprintf(params + *pos, paramsize - *pos,
|
||||
"%s %" PRIu64 "%s", devbuf,
|
||||
esize * seg->area[s].u.lv.le,
|
||||
trailing_space);
|
||||
}
|
||||
|
||||
if (tw < 0) {
|
||||
stack;
|
||||
return -1;
|
||||
}
|
||||
}
|
||||
|
||||
return 1;
|
||||
}
|
||||
|
||||
static int _emit_target(struct dev_manager *dm, struct dm_task *dmt,
|
||||
@@ -883,6 +854,9 @@ static int _emit_target(struct dev_manager *dm, struct dm_task *dmt,
|
||||
if (ret >= 0)
|
||||
return ret;
|
||||
|
||||
log_debug("Insufficient space in params[%" PRIsize_t
|
||||
"] for target parameters.", paramsize);
|
||||
|
||||
paramsize *= 2;
|
||||
} while (paramsize < MAX_TARGET_PARAMSIZE);
|
||||
|
||||
@@ -1014,8 +988,8 @@ static int _populate_snapshot(struct dev_manager *dm,
|
||||
/*
|
||||
* dev_manager implementation.
|
||||
*/
|
||||
struct dev_manager *dev_manager_create(const char *vg_name,
|
||||
struct config_tree *cf)
|
||||
struct dev_manager *dev_manager_create(struct cmd_context *cmd,
|
||||
const char *vg_name)
|
||||
{
|
||||
struct pool *mem;
|
||||
struct dev_manager *dm;
|
||||
@@ -1030,23 +1004,16 @@ struct dev_manager *dev_manager_create(const char *vg_name,
|
||||
goto bad;
|
||||
}
|
||||
|
||||
dm->cmd = cmd;
|
||||
dm->mem = mem;
|
||||
dm->cf = cf;
|
||||
|
||||
if (!stripe_filler) {
|
||||
stripe_filler = find_config_str(cf->root,
|
||||
stripe_filler = find_config_str(cmd->cft->root,
|
||||
"activation/missing_stripe_filler",
|
||||
'/', DEFAULT_STRIPE_FILLER);
|
||||
DEFAULT_STRIPE_FILLER);
|
||||
}
|
||||
dm->stripe_filler = stripe_filler;
|
||||
|
||||
if (!mirror_region_size) {
|
||||
mirror_region_size = 2 * find_config_int(cf->root,
|
||||
"activation/mirror_region_size",
|
||||
'/',
|
||||
DEFAULT_MIRROR_REGION_SIZE);
|
||||
}
|
||||
dm->mirror_region_size = mirror_region_size;
|
||||
|
||||
if (!(dm->vg_name = pool_strdup(dm->mem, vg_name))) {
|
||||
stack;
|
||||
goto bad;
|
||||
@@ -1062,6 +1029,8 @@ struct dev_manager *dev_manager_create(const char *vg_name,
|
||||
list_init(&dm->remove_list);
|
||||
list_init(&dm->suspend_list);
|
||||
|
||||
dm->target_state = NULL;
|
||||
|
||||
return dm;
|
||||
|
||||
bad:
|
||||
@@ -1274,15 +1243,13 @@ static int _expand_vanilla(struct dev_manager *dm, struct logical_volume *lv,
|
||||
/* Add dependencies for any LVs that segments refer to */
|
||||
list_iterate(segh, &lv->segments) {
|
||||
seg = list_item(segh, struct lv_segment);
|
||||
if (seg->type != SEG_STRIPED && seg->type != SEG_MIRRORED)
|
||||
continue;
|
||||
for (s = 0; s < seg->area_count; s++) {
|
||||
if (seg->area[s].type != AREA_LV)
|
||||
continue;
|
||||
if (!str_list_add(dm->mem, &dl->pre_create,
|
||||
_build_dlid(dm->mem,
|
||||
seg->area[s].u.lv.
|
||||
lv->lvid.s, NULL))) {
|
||||
seg->area[s].u.lv.lv->
|
||||
lvid.s, NULL))) {
|
||||
stack;
|
||||
return 0;
|
||||
}
|
||||
@@ -1303,7 +1270,7 @@ static int _expand_vanilla(struct dev_manager *dm, struct logical_volume *lv,
|
||||
_clear_flag(dlr, VISIBLE);
|
||||
_clear_flag(dlr, TOPLEVEL);
|
||||
_set_flag(dlr, REMOVE);
|
||||
|
||||
|
||||
/* add the dependency on the real device */
|
||||
if (!str_list_add(dm->mem, &dl->pre_create,
|
||||
pool_strdup(dm->mem, dlr->dlid))) {
|
||||
@@ -1328,6 +1295,9 @@ static int _expand_origin_real(struct dev_manager *dm,
|
||||
_clear_flag(dl, VISIBLE);
|
||||
_clear_flag(dl, TOPLEVEL);
|
||||
|
||||
/* Size changes must take effect before tables using it are reloaded */
|
||||
_set_flag(dl, RESUME_IMMEDIATE);
|
||||
|
||||
real_dlid = dl->dlid;
|
||||
|
||||
if (!(dl = _create_layer(dm, NULL, lv))) {
|
||||
@@ -1680,7 +1650,6 @@ static int _create_rec(struct dev_manager *dm, struct dev_layer *dl)
|
||||
return 1;
|
||||
}
|
||||
|
||||
|
||||
static int _build_all_layers(struct dev_manager *dm, struct volume_group *vg)
|
||||
{
|
||||
struct list *lvh;
|
||||
@@ -1748,8 +1717,7 @@ static int _populate_pre_suspend_lists(struct dev_manager *dm)
|
||||
continue;
|
||||
}
|
||||
|
||||
if (!str_list_add(dm->mem, &dep->pre_create,
|
||||
dl->dlid)) {
|
||||
if (!str_list_add(dm->mem, &dep->pre_create, dl->dlid)) {
|
||||
stack;
|
||||
return 0;
|
||||
}
|
||||
@@ -1765,8 +1733,7 @@ static int _populate_pre_suspend_lists(struct dev_manager *dm)
|
||||
continue;
|
||||
}
|
||||
|
||||
if (!str_list_add(dm->mem, &dep->pre_suspend,
|
||||
dl->dlid)) {
|
||||
if (!str_list_add(dm->mem, &dep->pre_suspend, dl->dlid)) {
|
||||
stack;
|
||||
return 0;
|
||||
}
|
||||
@@ -1940,7 +1907,6 @@ static int _add_existing_layer(struct dev_manager *dm, const char *name)
|
||||
|
||||
static int _scan_existing_devices(struct dev_manager *dm)
|
||||
{
|
||||
|
||||
int r = 0;
|
||||
struct dm_names *names;
|
||||
unsigned next = 0;
|
||||
@@ -2079,6 +2045,73 @@ static int _remove_suspended_lvs(struct dev_manager *dm,
|
||||
return 1;
|
||||
}
|
||||
|
||||
static int _targets_present(struct dev_manager *dm, struct list *lvs)
|
||||
{
|
||||
struct logical_volume *lv;
|
||||
struct list *lvh, *segh;
|
||||
struct segment_type *segtype;
|
||||
struct lv_segment *seg;
|
||||
int snapshots = 0, mirrors = 0;
|
||||
|
||||
list_iterate(lvh, lvs) {
|
||||
lv = list_item(lvh, struct lv_list)->lv;
|
||||
|
||||
if (!snapshots)
|
||||
if (lv_is_cow(lv) || lv_is_origin(lv))
|
||||
snapshots = 1;
|
||||
|
||||
if (!mirrors)
|
||||
if (lv->status & PVMOVE)
|
||||
mirrors = 1;
|
||||
|
||||
if (lv->status & VIRTUAL) {
|
||||
list_iterate(segh, &lv->segments) {
|
||||
seg = list_item(segh, struct lv_segment);
|
||||
if (seg->segtype->ops->target_present &&
|
||||
!seg->segtype->ops->target_present()) {
|
||||
log_error("Can't expand LV: %s target "
|
||||
"support missing "
|
||||
"from kernel?",
|
||||
seg->segtype->name);
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (mirrors) {
|
||||
if (!(segtype = get_segtype_from_string(dm->cmd, "mirror"))) {
|
||||
log_error("Can't expand LV: Mirror support "
|
||||
"missing from tools?");
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (!segtype->ops->target_present ||
|
||||
!segtype->ops->target_present()) {
|
||||
log_error("Can't expand LV: Mirror support missing "
|
||||
"from kernel?");
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
|
||||
if (snapshots) {
|
||||
if (!(segtype = get_segtype_from_string(dm->cmd, "snapshot"))) {
|
||||
log_error("Can't expand LV: Snapshot support "
|
||||
"missing from tools?");
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (!segtype->ops->target_present ||
|
||||
!segtype->ops->target_present()) {
|
||||
log_error("Can't expand LV: Snapshot support missing "
|
||||
"from kernel?");
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
|
||||
return 1;
|
||||
}
|
||||
|
||||
static int _fill_in_active_list(struct dev_manager *dm, struct volume_group *vg)
|
||||
{
|
||||
char *dlid;
|
||||
@@ -2161,6 +2194,12 @@ static int _action(struct dev_manager *dm, struct logical_volume *lv,
|
||||
}
|
||||
}
|
||||
|
||||
if (!_targets_present(dm, &dm->active_list) ||
|
||||
!_targets_present(dm, &dm->reload_list)) {
|
||||
stack;
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (!_execute(dm, lv->vg)) {
|
||||
stack;
|
||||
return 0;
|
||||
@@ -2184,7 +2223,7 @@ int dev_manager_suspend(struct dev_manager *dm, struct logical_volume *lv)
|
||||
return _action(dm, lv, SUSPEND);
|
||||
}
|
||||
|
||||
int dev_manager_mknodes(const struct logical_volume *lv)
|
||||
int dev_manager_lv_mknodes(const struct logical_volume *lv)
|
||||
{
|
||||
char *name;
|
||||
|
||||
@@ -2197,11 +2236,25 @@ int dev_manager_mknodes(const struct logical_volume *lv)
|
||||
return fs_add_lv(lv, name);
|
||||
}
|
||||
|
||||
int dev_manager_rmnodes(const struct logical_volume *lv)
|
||||
int dev_manager_lv_rmnodes(const struct logical_volume *lv)
|
||||
{
|
||||
return fs_del_lv(lv);
|
||||
}
|
||||
|
||||
int dev_manager_mknodes(void)
|
||||
{
|
||||
struct dm_task *dmt;
|
||||
int r;
|
||||
|
||||
if (!(dmt = dm_task_create(DM_DEVICE_MKNODES)))
|
||||
return 0;
|
||||
|
||||
r = dm_task_run(dmt);
|
||||
|
||||
dm_task_destroy(dmt);
|
||||
return r;
|
||||
}
|
||||
|
||||
void dev_manager_exit(void)
|
||||
{
|
||||
dm_lib_exit();
|
||||
|
@@ -1,23 +1,31 @@
|
||||
/*
|
||||
* Copyright (C) 2002 Sistina Software (UK) Limited.
|
||||
* Copyright (C) 2002-2004 Sistina Software, Inc. All rights reserved.
|
||||
* Copyright (C) 2004 Red Hat, Inc. All rights reserved.
|
||||
*
|
||||
* This file is released under the LGPL.
|
||||
* This file is part of LVM2.
|
||||
*
|
||||
* This copyrighted material is made available to anyone wishing to use,
|
||||
* modify, copy, or redistribute it subject to the terms and conditions
|
||||
* of the GNU General Public License v.2.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software Foundation,
|
||||
* Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
*/
|
||||
|
||||
#ifndef _LVM_DEV_MANAGER_H
|
||||
#define _LVM_DEV_MANAGER_H
|
||||
|
||||
#include "metadata.h"
|
||||
#include "config.h"
|
||||
|
||||
struct logical_volume;
|
||||
struct cmd_context;
|
||||
struct dev_manager;
|
||||
struct dm_info;
|
||||
|
||||
/*
|
||||
* Constructor and destructor.
|
||||
*/
|
||||
struct dev_manager *dev_manager_create(const char *vg_name,
|
||||
struct config_tree *cf);
|
||||
struct dev_manager *dev_manager_create(struct cmd_context *cmd,
|
||||
const char *vg_name);
|
||||
void dev_manager_destroy(struct dev_manager *dm);
|
||||
void dev_manager_exit(void);
|
||||
|
||||
@@ -38,8 +46,9 @@ int dev_manager_suspend(struct dev_manager *dm, struct logical_volume *lv);
|
||||
int dev_manager_activate(struct dev_manager *dm, struct logical_volume *lv);
|
||||
int dev_manager_deactivate(struct dev_manager *dm, struct logical_volume *lv);
|
||||
|
||||
int dev_manager_mknodes(const struct logical_volume *lv);
|
||||
int dev_manager_rmnodes(const struct logical_volume *lv);
|
||||
int dev_manager_lv_mknodes(const struct logical_volume *lv);
|
||||
int dev_manager_lv_rmnodes(const struct logical_volume *lv);
|
||||
int dev_manager_mknodes(void);
|
||||
|
||||
/*
|
||||
* Put the desired changes into effect.
|
||||
|
@@ -1,7 +1,16 @@
|
||||
/*
|
||||
* Copyright (C) 2001 Sistina Software (UK) Limited.
|
||||
* Copyright (C) 2001-2004 Sistina Software, Inc. All rights reserved.
|
||||
* Copyright (C) 2004 Red Hat, Inc. All rights reserved.
|
||||
*
|
||||
* This file is released under the LGPL.
|
||||
* This file is part of LVM2.
|
||||
*
|
||||
* This copyrighted material is made available to anyone wishing to use,
|
||||
* modify, copy, or redistribute it subject to the terms and conditions
|
||||
* of the GNU General Public License v.2.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software Foundation,
|
||||
* Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
*/
|
||||
|
||||
#include "lib.h"
|
||||
@@ -11,6 +20,10 @@
|
||||
#include "lvm-file.h"
|
||||
#include "memlock.h"
|
||||
|
||||
#ifdef HAVE_SELINUX
|
||||
# include "selinux.h"
|
||||
#endif
|
||||
|
||||
#include <sys/stat.h>
|
||||
#include <fcntl.h>
|
||||
#include <unistd.h>
|
||||
@@ -166,6 +179,13 @@ static int _mk_link(const char *dev_dir, const char *vg_name,
|
||||
return 0;
|
||||
}
|
||||
|
||||
#ifdef HAVE_SELINUX
|
||||
if (!set_selinux_context(lv_path)) {
|
||||
stack;
|
||||
return 0;
|
||||
}
|
||||
#endif
|
||||
|
||||
return 1;
|
||||
}
|
||||
|
||||
|
@@ -1,7 +1,16 @@
|
||||
/*
|
||||
* Copyright (C) 2001 Sistina Software (UK) Limited.
|
||||
* Copyright (C) 2001-2004 Sistina Software, Inc. All rights reserved.
|
||||
* Copyright (C) 2004 Red Hat, Inc. All rights reserved.
|
||||
*
|
||||
* This file is released under the LGPL.
|
||||
* This file is part of LVM2.
|
||||
*
|
||||
* This copyrighted material is made available to anyone wishing to use,
|
||||
* modify, copy, or redistribute it subject to the terms and conditions
|
||||
* of the GNU General Public License v.2.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software Foundation,
|
||||
* Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
*/
|
||||
|
||||
#ifndef _LVM_FS_H
|
||||
|
25
lib/activate/targets.h
Normal file
25
lib/activate/targets.h
Normal file
@@ -0,0 +1,25 @@
|
||||
/*
|
||||
* Copyright (C) 2003-2004 Sistina Software, Inc. All rights reserved.
|
||||
* Copyright (C) 2004 Red Hat, Inc. All rights reserved.
|
||||
*
|
||||
* This file is part of LVM2.
|
||||
*
|
||||
* This copyrighted material is made available to anyone wishing to use,
|
||||
* modify, copy, or redistribute it subject to the terms and conditions
|
||||
* of the GNU General Public License v.2.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software Foundation,
|
||||
* Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
*/
|
||||
|
||||
#ifndef _LVM_TARGETS_H
|
||||
#define _LVM_TARGETS_H
|
||||
|
||||
struct dev_manager;
|
||||
struct lv_segment;
|
||||
|
||||
int compose_areas_line(struct dev_manager *dm, struct lv_segment *seg, char *params, size_t paramsize, int *pos,
|
||||
int start_area, int areas);
|
||||
|
||||
#endif
|
13
lib/cache/lvmcache.c
vendored
13
lib/cache/lvmcache.c
vendored
@@ -1,7 +1,16 @@
|
||||
/*
|
||||
* Copyright (C) 2001 Sistina Software (UK) Limited.
|
||||
* Copyright (C) 2001-2004 Sistina Software, Inc. All rights reserved.
|
||||
* Copyright (C) 2004 Red Hat, Inc. All rights reserved.
|
||||
*
|
||||
* This file is released under the LGPL.
|
||||
* This file is part of LVM2.
|
||||
*
|
||||
* This copyrighted material is made available to anyone wishing to use,
|
||||
* modify, copy, or redistribute it subject to the terms and conditions
|
||||
* of the GNU General Public License v.2.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software Foundation,
|
||||
* Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
*
|
||||
*/
|
||||
|
||||
|
18
lib/cache/lvmcache.h
vendored
18
lib/cache/lvmcache.h
vendored
@@ -1,7 +1,16 @@
|
||||
/*
|
||||
* Copyright (C) 2001 Sistina Software (UK) Limited.
|
||||
* Copyright (C) 2001-2004 Sistina Software, Inc. All rights reserved.
|
||||
* Copyright (C) 2004 Red Hat, Inc. All rights reserved.
|
||||
*
|
||||
* This file is released under the LGPL.
|
||||
* This file is part of LVM2.
|
||||
*
|
||||
* This copyrighted material is made available to anyone wishing to use,
|
||||
* modify, copy, or redistribute it subject to the terms and conditions
|
||||
* of the GNU General Public License v.2.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software Foundation,
|
||||
* Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
*
|
||||
*/
|
||||
|
||||
@@ -11,7 +20,6 @@
|
||||
#include "dev-cache.h"
|
||||
#include "uuid.h"
|
||||
#include "label.h"
|
||||
#include "metadata.h"
|
||||
|
||||
#define ORPHAN ""
|
||||
|
||||
@@ -21,6 +29,10 @@
|
||||
/* LVM specific per-volume info */
|
||||
/* Eventual replacement for struct physical_volume perhaps? */
|
||||
|
||||
struct cmd_context;
|
||||
struct format_type;
|
||||
struct volume_group;
|
||||
|
||||
struct lvmcache_vginfo {
|
||||
struct list list; /* Join these vginfos together */
|
||||
struct list infos; /* List head for lvmcache_infos */
|
||||
|
@@ -1,7 +1,16 @@
|
||||
/*
|
||||
* Copyright (C) 2001 Sistina Software (UK) Limited.
|
||||
* Copyright (C) 2001-2004 Sistina Software, Inc. All rights reserved.
|
||||
* Copyright (C) 2004 Red Hat, Inc. All rights reserved.
|
||||
*
|
||||
* This file is released under the LGPL.
|
||||
* This file is part of LVM2.
|
||||
*
|
||||
* This copyrighted material is made available to anyone wishing to use,
|
||||
* modify, copy, or redistribute it subject to the terms and conditions
|
||||
* of the GNU General Public License v.2.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software Foundation,
|
||||
* Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
*/
|
||||
|
||||
#ifndef _LVM_ERRORS_H
|
||||
|
@@ -1,7 +1,16 @@
|
||||
/*
|
||||
* Copyright (C) 2001 Sistina Software (UK) Limited.
|
||||
* Copyright (C) 2001-2004 Sistina Software, Inc. All rights reserved.
|
||||
* Copyright (C) 2004 Red Hat, Inc. All rights reserved.
|
||||
*
|
||||
* This file is released under the LGPL.
|
||||
* This file is part of LVM2.
|
||||
*
|
||||
* This copyrighted material is made available to anyone wishing to use,
|
||||
* modify, copy, or redistribute it subject to the terms and conditions
|
||||
* of the GNU General Public License v.2.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software Foundation,
|
||||
* Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
*
|
||||
*/
|
||||
|
||||
@@ -14,13 +23,18 @@
|
||||
#include "activate.h"
|
||||
#include "filter.h"
|
||||
#include "filter-composite.h"
|
||||
#include "filter-md.h"
|
||||
#include "filter-persistent.h"
|
||||
#include "filter-regex.h"
|
||||
#include "filter-sysfs.h"
|
||||
#include "label.h"
|
||||
#include "lvm-file.h"
|
||||
#include "format-text.h"
|
||||
#include "display.h"
|
||||
#include "memlock.h"
|
||||
#include "str_list.h"
|
||||
#include "segtypes.h"
|
||||
#include "lvmcache.h"
|
||||
|
||||
#ifdef HAVE_LIBDL
|
||||
#include "sharedlib.h"
|
||||
@@ -30,8 +44,13 @@
|
||||
#include "format1.h"
|
||||
#endif
|
||||
|
||||
#ifdef POOL_INTERNAL
|
||||
#include "format_pool.h"
|
||||
#endif
|
||||
|
||||
#include <locale.h>
|
||||
#include <sys/stat.h>
|
||||
#include <sys/utsname.h>
|
||||
#include <syslog.h>
|
||||
#include <time.h>
|
||||
|
||||
@@ -67,7 +86,7 @@ static void _init_logging(struct cmd_context *cmd)
|
||||
|
||||
/* Syslog */
|
||||
cmd->default_settings.syslog =
|
||||
find_config_int(cmd->cf->root, "log/syslog", '/', DEFAULT_SYSLOG);
|
||||
find_config_int(cmd->cft->root, "log/syslog", DEFAULT_SYSLOG);
|
||||
if (cmd->default_settings.syslog != 1)
|
||||
fin_syslog();
|
||||
|
||||
@@ -76,47 +95,50 @@ static void _init_logging(struct cmd_context *cmd)
|
||||
|
||||
/* Debug level for log file output */
|
||||
cmd->default_settings.debug =
|
||||
find_config_int(cmd->cf->root, "log/level", '/', DEFAULT_LOGLEVEL);
|
||||
find_config_int(cmd->cft->root, "log/level", DEFAULT_LOGLEVEL);
|
||||
init_debug(cmd->default_settings.debug);
|
||||
|
||||
/* Verbose level for tty output */
|
||||
cmd->default_settings.verbose =
|
||||
find_config_int(cmd->cf->root, "log/verbose", '/', DEFAULT_VERBOSE);
|
||||
init_verbose(cmd->default_settings.verbose);
|
||||
find_config_int(cmd->cft->root, "log/verbose", DEFAULT_VERBOSE);
|
||||
init_verbose(cmd->default_settings.verbose + VERBOSE_BASE_LEVEL);
|
||||
|
||||
/* Log message formatting */
|
||||
init_indent(find_config_int(cmd->cf->root, "log/indent", '/',
|
||||
init_indent(find_config_int(cmd->cft->root, "log/indent",
|
||||
DEFAULT_INDENT));
|
||||
|
||||
cmd->default_settings.msg_prefix = find_config_str(cmd->cf->root,
|
||||
"log/prefix", '/',
|
||||
cmd->default_settings.msg_prefix = find_config_str(cmd->cft->root,
|
||||
"log/prefix",
|
||||
DEFAULT_MSG_PREFIX);
|
||||
init_msg_prefix(cmd->default_settings.msg_prefix);
|
||||
|
||||
cmd->default_settings.cmd_name = find_config_int(cmd->cf->root,
|
||||
cmd->default_settings.cmd_name = find_config_int(cmd->cft->root,
|
||||
"log/command_names",
|
||||
'/', DEFAULT_CMD_NAME);
|
||||
DEFAULT_CMD_NAME);
|
||||
init_cmd_name(cmd->default_settings.cmd_name);
|
||||
|
||||
/* Test mode */
|
||||
cmd->default_settings.test =
|
||||
find_config_int(cmd->cf->root, "global/test", '/', 0);
|
||||
find_config_int(cmd->cft->root, "global/test", 0);
|
||||
|
||||
/* Settings for logging to file */
|
||||
if (find_config_int(cmd->cf->root, "log/overwrite", '/',
|
||||
DEFAULT_OVERWRITE))
|
||||
if (find_config_int(cmd->cft->root, "log/overwrite", DEFAULT_OVERWRITE))
|
||||
append = 0;
|
||||
|
||||
log_file = find_config_str(cmd->cf->root, "log/file", '/', 0);
|
||||
if (log_file)
|
||||
init_log_file(log_file, append);
|
||||
log_file = find_config_str(cmd->cft->root, "log/file", 0);
|
||||
|
||||
log_file = find_config_str(cmd->cf->root, "log/activate_file", '/', 0);
|
||||
if (log_file) {
|
||||
release_log_memory();
|
||||
fin_log();
|
||||
init_log_file(log_file, append);
|
||||
}
|
||||
|
||||
log_file = find_config_str(cmd->cft->root, "log/activate_file", 0);
|
||||
if (log_file)
|
||||
init_log_direct(log_file, append);
|
||||
|
||||
init_log_while_suspended(find_config_int(cmd->cf->root,
|
||||
"log/activation", '/', 0));
|
||||
init_log_while_suspended(find_config_int(cmd->cft->root,
|
||||
"log/activation", 0));
|
||||
|
||||
t = time(NULL);
|
||||
log_verbose("Logging initialised at %s", ctime(&t));
|
||||
@@ -132,8 +154,8 @@ static int _process_config(struct cmd_context *cmd)
|
||||
mode_t old_umask;
|
||||
|
||||
/* umask */
|
||||
cmd->default_settings.umask = find_config_int(cmd->cf->root,
|
||||
"global/umask", '/',
|
||||
cmd->default_settings.umask = find_config_int(cmd->cft->root,
|
||||
"global/umask",
|
||||
DEFAULT_UMASK);
|
||||
|
||||
if ((old_umask = umask((mode_t) cmd->default_settings.umask)) !=
|
||||
@@ -142,8 +164,8 @@ static int _process_config(struct cmd_context *cmd)
|
||||
|
||||
/* dev dir */
|
||||
if (lvm_snprintf(cmd->dev_dir, sizeof(cmd->dev_dir), "%s/",
|
||||
find_config_str(cmd->cf->root, "devices/dir",
|
||||
'/', DEFAULT_DEV_DIR)) < 0) {
|
||||
find_config_str(cmd->cft->root, "devices/dir",
|
||||
DEFAULT_DEV_DIR)) < 0) {
|
||||
log_error("Device directory given in config file too long");
|
||||
return 0;
|
||||
}
|
||||
@@ -153,27 +175,25 @@ static int _process_config(struct cmd_context *cmd)
|
||||
|
||||
/* proc dir */
|
||||
if (lvm_snprintf(cmd->proc_dir, sizeof(cmd->proc_dir), "%s",
|
||||
find_config_str(cmd->cf->root, "global/proc",
|
||||
'/', DEFAULT_PROC_DIR)) < 0) {
|
||||
find_config_str(cmd->cft->root, "global/proc",
|
||||
DEFAULT_PROC_DIR)) < 0) {
|
||||
log_error("Device directory given in config file too long");
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* activation? */
|
||||
cmd->default_settings.activation = find_config_int(cmd->cf->root,
|
||||
cmd->default_settings.activation = find_config_int(cmd->cft->root,
|
||||
"global/activation",
|
||||
'/',
|
||||
DEFAULT_ACTIVATION);
|
||||
set_activation(cmd->default_settings.activation);
|
||||
|
||||
cmd->default_settings.suffix = find_config_int(cmd->cf->root,
|
||||
cmd->default_settings.suffix = find_config_int(cmd->cft->root,
|
||||
"global/suffix",
|
||||
'/', DEFAULT_SUFFIX);
|
||||
DEFAULT_SUFFIX);
|
||||
|
||||
if (!(cmd->default_settings.unit_factor =
|
||||
units_to_bytes(find_config_str(cmd->cf->root,
|
||||
units_to_bytes(find_config_str(cmd->cft->root,
|
||||
"global/units",
|
||||
'/',
|
||||
DEFAULT_UNITS),
|
||||
&cmd->default_settings.unit_type))) {
|
||||
log_error("Invalid units specification");
|
||||
@@ -183,57 +203,266 @@ static int _process_config(struct cmd_context *cmd)
|
||||
return 1;
|
||||
}
|
||||
|
||||
/* Find and read config file */
|
||||
static int _init_config(struct cmd_context *cmd)
|
||||
static int _set_tag(struct cmd_context *cmd, const char *tag)
|
||||
{
|
||||
struct stat info;
|
||||
char config_file[PATH_MAX] = "";
|
||||
log_very_verbose("Setting host tag: %s", pool_strdup(cmd->libmem, tag));
|
||||
|
||||
if (!(cmd->cf = create_config_tree())) {
|
||||
stack;
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* No config file if LVM_SYSTEM_DIR is empty */
|
||||
if (!*cmd->sys_dir)
|
||||
return 1;
|
||||
|
||||
if (lvm_snprintf(config_file, sizeof(config_file),
|
||||
"%s/lvm.conf", cmd->sys_dir) < 0) {
|
||||
log_error("LVM_SYSTEM_DIR was too long");
|
||||
destroy_config_tree(cmd->cf);
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* Is there a config file? */
|
||||
if (stat(config_file, &info) == -1) {
|
||||
if (errno == ENOENT)
|
||||
return 1;
|
||||
log_sys_error("stat", config_file);
|
||||
destroy_config_tree(cmd->cf);
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (!read_config_file(cmd->cf, config_file)) {
|
||||
log_error("Failed to load config file %s", config_file);
|
||||
destroy_config_tree(cmd->cf);
|
||||
if (!str_list_add(cmd->libmem, &cmd->tags, tag)) {
|
||||
log_error("_set_tag: str_list_add %s failed", tag);
|
||||
return 0;
|
||||
}
|
||||
|
||||
return 1;
|
||||
}
|
||||
|
||||
static int _init_dev_cache(struct cmd_context *cmd)
|
||||
static int _check_host_filters(struct cmd_context *cmd, struct config_node *hn,
|
||||
int *passes)
|
||||
{
|
||||
struct config_node *cn;
|
||||
struct config_value *cv;
|
||||
|
||||
*passes = 1;
|
||||
|
||||
for (cn = hn; cn; cn = cn->sib) {
|
||||
if (!cn->v)
|
||||
continue;
|
||||
if (!strcmp(cn->key, "host_list")) {
|
||||
*passes = 0;
|
||||
if (cn->v->type == CFG_EMPTY_ARRAY)
|
||||
continue;
|
||||
for (cv = cn->v; cv; cv = cv->next) {
|
||||
if (cv->type != CFG_STRING) {
|
||||
log_error("Invalid hostname string "
|
||||
"for tag %s", cn->key);
|
||||
return 0;
|
||||
}
|
||||
if (!strcmp(cv->v.str, cmd->hostname)) {
|
||||
*passes = 1;
|
||||
return 1;
|
||||
}
|
||||
}
|
||||
}
|
||||
if (!strcmp(cn->key, "host_filter")) {
|
||||
log_error("host_filter not supported yet");
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
|
||||
return 1;
|
||||
}
|
||||
|
||||
static int _init_tags(struct cmd_context *cmd, struct config_tree *cft)
|
||||
{
|
||||
const struct config_node *tn, *cn;
|
||||
const char *tag;
|
||||
int passes;
|
||||
|
||||
if (!(tn = find_config_node(cft->root, "tags")) || !tn->child)
|
||||
return 1;
|
||||
|
||||
/* NB hosttags 0 when already 1 intentionally does not delete the tag */
|
||||
if (!cmd->hosttags && find_config_int(cft->root, "tags/hosttags",
|
||||
DEFAULT_HOSTTAGS)) {
|
||||
/* FIXME Strip out invalid chars: only A-Za-z0-9_+.- */
|
||||
if (!_set_tag(cmd, cmd->hostname)) {
|
||||
stack;
|
||||
return 0;
|
||||
}
|
||||
cmd->hosttags = 1;
|
||||
}
|
||||
|
||||
for (cn = tn->child; cn; cn = cn->sib) {
|
||||
if (cn->v)
|
||||
continue;
|
||||
tag = cn->key;
|
||||
if (*tag == '@')
|
||||
tag++;
|
||||
if (!validate_name(tag)) {
|
||||
log_error("Invalid tag in config file: %s", cn->key);
|
||||
return 0;
|
||||
}
|
||||
if (cn->child) {
|
||||
passes = 0;
|
||||
if (!_check_host_filters(cmd, cn->child, &passes)) {
|
||||
stack;
|
||||
return 0;
|
||||
}
|
||||
if (!passes)
|
||||
continue;
|
||||
}
|
||||
if (!_set_tag(cmd, tag)) {
|
||||
stack;
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
|
||||
return 1;
|
||||
}
|
||||
|
||||
static int _load_config_file(struct cmd_context *cmd, const char *tag)
|
||||
{
|
||||
char config_file[PATH_MAX] = "";
|
||||
const char *filler = "";
|
||||
struct stat info;
|
||||
struct config_tree_list *cfl;
|
||||
|
||||
if (*tag)
|
||||
filler = "_";
|
||||
|
||||
if (lvm_snprintf(config_file, sizeof(config_file), "%s/lvm%s%s.conf",
|
||||
cmd->sys_dir, filler, tag) < 0) {
|
||||
log_error("LVM_SYSTEM_DIR or tag was too long");
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (!(cfl = pool_alloc(cmd->libmem, sizeof(*cfl)))) {
|
||||
log_error("config_tree_list allocation failed");
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (!(cfl->cft = create_config_tree(config_file))) {
|
||||
log_error("config_tree allocation failed");
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* Is there a config file? */
|
||||
if (stat(config_file, &info) == -1) {
|
||||
if (errno == ENOENT) {
|
||||
list_add(&cmd->config_files, &cfl->list);
|
||||
goto out;
|
||||
}
|
||||
log_sys_error("stat", config_file);
|
||||
destroy_config_tree(cfl->cft);
|
||||
return 0;
|
||||
}
|
||||
|
||||
log_very_verbose("Loading config file: %s", config_file);
|
||||
if (!read_config_file(cfl->cft)) {
|
||||
log_error("Failed to load config file %s", config_file);
|
||||
destroy_config_tree(cfl->cft);
|
||||
return 0;
|
||||
}
|
||||
|
||||
list_add(&cmd->config_files, &cfl->list);
|
||||
|
||||
out:
|
||||
if (*tag)
|
||||
_init_tags(cmd, cfl->cft);
|
||||
else
|
||||
/* Use temporary copy of lvm.conf while loading other files */
|
||||
cmd->cft = cfl->cft;
|
||||
|
||||
return 1;
|
||||
}
|
||||
|
||||
/* Find and read first config file */
|
||||
static int _init_lvm_conf(struct cmd_context *cmd)
|
||||
{
|
||||
/* No config file if LVM_SYSTEM_DIR is empty */
|
||||
if (!*cmd->sys_dir) {
|
||||
if (!(cmd->cft = create_config_tree(NULL))) {
|
||||
log_error("Failed to create config tree");
|
||||
return 0;
|
||||
}
|
||||
return 1;
|
||||
}
|
||||
|
||||
if (!_load_config_file(cmd, "")) {
|
||||
stack;
|
||||
return 0;
|
||||
}
|
||||
|
||||
return 1;
|
||||
}
|
||||
|
||||
/* Read any additional config files */
|
||||
static int _init_tag_configs(struct cmd_context *cmd)
|
||||
{
|
||||
struct str_list *sl;
|
||||
|
||||
/* Tag list may grow while inside this loop */
|
||||
list_iterate_items(sl, &cmd->tags) {
|
||||
if (!_load_config_file(cmd, sl->str)) {
|
||||
stack;
|
||||
return 0;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
return 1;
|
||||
}
|
||||
|
||||
static int _merge_config_files(struct cmd_context *cmd)
|
||||
{
|
||||
struct config_tree_list *cfl;
|
||||
|
||||
/* Replace temporary duplicate copy of lvm.conf */
|
||||
if (cmd->cft->root) {
|
||||
if (!(cmd->cft = create_config_tree(NULL))) {
|
||||
log_error("Failed to create config tree");
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
|
||||
list_iterate_items(cfl, &cmd->config_files) {
|
||||
/* Merge all config trees into cmd->cft using merge/tag rules */
|
||||
if (!merge_config_tree(cmd, cmd->cft, cfl->cft)) {
|
||||
stack;
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
|
||||
return 1;
|
||||
}
|
||||
|
||||
static void _destroy_tags(struct cmd_context *cmd)
|
||||
{
|
||||
struct list *slh, *slht;
|
||||
|
||||
list_iterate_safe(slh, slht, &cmd->tags) {
|
||||
list_del(slh);
|
||||
}
|
||||
}
|
||||
|
||||
int config_files_changed(struct cmd_context *cmd)
|
||||
{
|
||||
struct config_tree_list *cfl;
|
||||
|
||||
list_iterate_items(cfl, &cmd->config_files) {
|
||||
if (config_file_changed(cfl->cft))
|
||||
return 1;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static void _destroy_tag_configs(struct cmd_context *cmd)
|
||||
{
|
||||
struct config_tree_list *cfl;
|
||||
|
||||
if (cmd->cft && cmd->cft->root) {
|
||||
destroy_config_tree(cmd->cft);
|
||||
cmd->cft = NULL;
|
||||
}
|
||||
|
||||
list_iterate_items(cfl, &cmd->config_files) {
|
||||
destroy_config_tree(cfl->cft);
|
||||
}
|
||||
|
||||
list_init(&cmd->config_files);
|
||||
}
|
||||
|
||||
static int _init_dev_cache(struct cmd_context *cmd)
|
||||
{
|
||||
const struct config_node *cn;
|
||||
struct config_value *cv;
|
||||
|
||||
if (!dev_cache_init()) {
|
||||
stack;
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (!(cn = find_config_node(cmd->cf->root, "devices/scan", '/'))) {
|
||||
if (!(cn = find_config_node(cmd->cft->root, "devices/scan"))) {
|
||||
if (!dev_cache_add_dir("/dev")) {
|
||||
log_error("Failed to add /dev to internal "
|
||||
"device cache");
|
||||
@@ -261,33 +490,60 @@ static int _init_dev_cache(struct cmd_context *cmd)
|
||||
return 1;
|
||||
}
|
||||
|
||||
#define MAX_FILTERS 4
|
||||
|
||||
static struct dev_filter *_init_filter_components(struct cmd_context *cmd)
|
||||
{
|
||||
struct config_node *cn;
|
||||
struct dev_filter *f1, *f2, *f3;
|
||||
unsigned nr_filt = 0;
|
||||
const struct config_node *cn;
|
||||
struct dev_filter *filters[MAX_FILTERS];
|
||||
|
||||
cn = find_config_node(cmd->cf->root, "devices/types", '/');
|
||||
memset(filters, 0, sizeof(filters));
|
||||
|
||||
if (!(f2 = lvm_type_filter_create(cmd->proc_dir, cn)))
|
||||
return NULL;
|
||||
/*
|
||||
* Filters listed in order: top one gets applied first.
|
||||
* Failure to initialise some filters is not fatal.
|
||||
* Update MAX_FILTERS definition above when adding new filters.
|
||||
*/
|
||||
|
||||
if (!(cn = find_config_node(cmd->cf->root, "devices/filter", '/'))) {
|
||||
log_debug("devices/filter not found in config file: no regex "
|
||||
"filter installed");
|
||||
return f2;
|
||||
/*
|
||||
* sysfs filter. Only available on 2.6 kernels. Non-critical.
|
||||
* Listed first because it's very efficient at eliminating
|
||||
* unavailable devices.
|
||||
*/
|
||||
if (find_config_bool(cmd->cft->root, "devices/sysfs_scan",
|
||||
DEFAULT_SYSFS_SCAN)) {
|
||||
if ((filters[nr_filt] = sysfs_filter_create(cmd->proc_dir)))
|
||||
nr_filt++;
|
||||
}
|
||||
|
||||
if (!(f1 = regex_filter_create(cn->v))) {
|
||||
/* regex filter. Optional. */
|
||||
if (!(cn = find_config_node(cmd->cft->root, "devices/filter")))
|
||||
log_debug("devices/filter not found in config file: no regex "
|
||||
"filter installed");
|
||||
|
||||
else if (!(filters[nr_filt++] = regex_filter_create(cn->v))) {
|
||||
log_error("Failed to create regex device filter");
|
||||
return NULL;
|
||||
}
|
||||
|
||||
if (!(f3 = composite_filter_create(2, f1, f2))) {
|
||||
log_error("Failed to create composite device filter");
|
||||
/* device type filter. Required. */
|
||||
cn = find_config_node(cmd->cft->root, "devices/types");
|
||||
if (!(filters[nr_filt++] = lvm_type_filter_create(cmd->proc_dir, cn))) {
|
||||
log_error("Failed to create lvm type filter");
|
||||
return NULL;
|
||||
}
|
||||
|
||||
return f3;
|
||||
/* md component filter. Optional, non-critical. */
|
||||
if (find_config_bool(cmd->cft->root, "devices/md_component_detection",
|
||||
DEFAULT_MD_COMPONENT_DETECTION)) {
|
||||
if ((filters[nr_filt] = md_filter_create()))
|
||||
nr_filt++;
|
||||
}
|
||||
|
||||
/* Only build a composite filter if we really need it. */
|
||||
return (nr_filt == 1) ?
|
||||
filters[0] : composite_filter_create(nr_filt, filters);
|
||||
}
|
||||
|
||||
static int _init_filters(struct cmd_context *cmd)
|
||||
@@ -309,22 +565,22 @@ static int _init_filters(struct cmd_context *cmd)
|
||||
return 0;
|
||||
}
|
||||
|
||||
dev_cache =
|
||||
find_config_str(cmd->cf->root, "devices/cache", '/', cache_file);
|
||||
dev_cache = find_config_str(cmd->cft->root, "devices/cache",
|
||||
cache_file);
|
||||
if (!(f4 = persistent_filter_create(f3, dev_cache))) {
|
||||
log_error("Failed to create persistent device filter");
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* Should we ever dump persistent filter state? */
|
||||
if (find_config_int(cmd->cf->root, "devices/write_cache_state", '/', 1))
|
||||
if (find_config_int(cmd->cft->root, "devices/write_cache_state", 1))
|
||||
cmd->dump_filter = 1;
|
||||
|
||||
if (!*cmd->sys_dir)
|
||||
cmd->dump_filter = 0;
|
||||
|
||||
if (!stat(dev_cache, &st) &&
|
||||
(st.st_mtime > config_file_timestamp(cmd->cf)) &&
|
||||
(st.st_mtime > config_file_timestamp(cmd->cft)) &&
|
||||
!persistent_filter_load(f4))
|
||||
log_verbose("Failed to load existing device cache from %s",
|
||||
dev_cache);
|
||||
@@ -342,7 +598,7 @@ static int _init_formats(struct cmd_context *cmd)
|
||||
struct list *fmth;
|
||||
|
||||
#ifdef HAVE_LIBDL
|
||||
struct config_node *cn;
|
||||
const struct config_node *cn;
|
||||
#endif
|
||||
|
||||
label_init();
|
||||
@@ -354,10 +610,16 @@ static int _init_formats(struct cmd_context *cmd)
|
||||
list_add(&cmd->formats, &fmt->list);
|
||||
#endif
|
||||
|
||||
#ifdef POOL_INTERNAL
|
||||
if (!(fmt = init_pool_format(cmd)))
|
||||
return 0;
|
||||
fmt->library = NULL;
|
||||
list_add(&cmd->formats, &fmt->list);
|
||||
#endif
|
||||
|
||||
#ifdef HAVE_LIBDL
|
||||
/* Load any formats in shared libs */
|
||||
if ((cn = find_config_node(cmd->cf->root, "global/format_libraries",
|
||||
'/'))) {
|
||||
if ((cn = find_config_node(cmd->cft->root, "global/format_libraries"))) {
|
||||
|
||||
struct config_value *cv;
|
||||
struct format_type *(*init_format_fn) (struct cmd_context *);
|
||||
@@ -369,7 +631,7 @@ static int _init_formats(struct cmd_context *cmd)
|
||||
"global/format_libraries");
|
||||
return 0;
|
||||
}
|
||||
if (!(lib = load_shared_library(cmd->cf, cv->v.str,
|
||||
if (!(lib = load_shared_library(cmd->cft, cv->v.str,
|
||||
"format"))) {
|
||||
stack;
|
||||
return 0;
|
||||
@@ -397,7 +659,7 @@ static int _init_formats(struct cmd_context *cmd)
|
||||
|
||||
cmd->fmt_backup = fmt;
|
||||
|
||||
format = find_config_str(cmd->cf->root, "global/format", '/',
|
||||
format = find_config_str(cmd->cft->root, "global/format",
|
||||
DEFAULT_FORMAT);
|
||||
|
||||
list_iterate(fmth, &cmd->formats) {
|
||||
@@ -413,6 +675,119 @@ static int _init_formats(struct cmd_context *cmd)
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int _init_segtypes(struct cmd_context *cmd)
|
||||
{
|
||||
struct segment_type *segtype;
|
||||
|
||||
#ifdef HAVE_LIBDL
|
||||
const struct config_node *cn;
|
||||
#endif
|
||||
|
||||
if (!(segtype = init_striped_segtype(cmd)))
|
||||
return 0;
|
||||
segtype->library = NULL;
|
||||
list_add(&cmd->segtypes, &segtype->list);
|
||||
|
||||
if (!(segtype = init_zero_segtype(cmd)))
|
||||
return 0;
|
||||
segtype->library = NULL;
|
||||
list_add(&cmd->segtypes, &segtype->list);
|
||||
|
||||
if (!(segtype = init_error_segtype(cmd)))
|
||||
return 0;
|
||||
segtype->library = NULL;
|
||||
list_add(&cmd->segtypes, &segtype->list);
|
||||
|
||||
#ifdef SNAPSHOT_INTERNAL
|
||||
if (!(segtype = init_snapshot_segtype(cmd)))
|
||||
return 0;
|
||||
segtype->library = NULL;
|
||||
list_add(&cmd->segtypes, &segtype->list);
|
||||
#endif
|
||||
|
||||
#ifdef MIRRORED_INTERNAL
|
||||
if (!(segtype = init_mirrored_segtype(cmd)))
|
||||
return 0;
|
||||
segtype->library = NULL;
|
||||
list_add(&cmd->segtypes, &segtype->list);
|
||||
#endif
|
||||
|
||||
#ifdef HAVE_LIBDL
|
||||
/* Load any formats in shared libs */
|
||||
if ((cn = find_config_node(cmd->cft->root, "global/segment_libraries"))) {
|
||||
|
||||
struct config_value *cv;
|
||||
struct segment_type *(*init_segtype_fn) (struct cmd_context *);
|
||||
void *lib;
|
||||
struct list *sgtl, *tmp;
|
||||
struct segment_type *segtype2;
|
||||
|
||||
for (cv = cn->v; cv; cv = cv->next) {
|
||||
if (cv->type != CFG_STRING) {
|
||||
log_error("Invalid string in config file: "
|
||||
"global/segment_libraries");
|
||||
return 0;
|
||||
}
|
||||
if (!(lib = load_shared_library(cmd->cft, cv->v.str,
|
||||
"segment type"))) {
|
||||
stack;
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (!(init_segtype_fn = dlsym(lib, "init_segtype"))) {
|
||||
log_error("Shared library %s does not contain "
|
||||
"segment type functions", cv->v.str);
|
||||
dlclose(lib);
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (!(segtype = init_segtype_fn(cmd)))
|
||||
return 0;
|
||||
segtype->library = lib;
|
||||
list_add(&cmd->segtypes, &segtype->list);
|
||||
|
||||
list_iterate_safe(sgtl, tmp, &cmd->segtypes) {
|
||||
segtype2 = list_item(sgtl, struct segment_type);
|
||||
if (!strcmp(segtype2->name, segtype->name)) {
|
||||
log_error("Duplicate segment type %s: "
|
||||
"unloading shared library %s",
|
||||
segtype->name, cv->v.str);
|
||||
list_del(&segtype->list);
|
||||
segtype->ops->destroy(segtype);
|
||||
dlclose(lib);
|
||||
break;
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
||||
return 1;
|
||||
}
|
||||
|
||||
static int _init_hostname(struct cmd_context *cmd)
|
||||
{
|
||||
struct utsname uts;
|
||||
|
||||
if (uname(&uts)) {
|
||||
log_sys_error("uname", "_init_hostname");
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (!(cmd->hostname = pool_strdup(cmd->libmem, uts.nodename))) {
|
||||
log_error("_init_hostname: pool_strdup failed");
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (!(cmd->kernel_vsn = pool_strdup(cmd->libmem, uts.release))) {
|
||||
log_error("_init_hostname: pool_strdup kernel_vsn failed");
|
||||
return 0;
|
||||
}
|
||||
|
||||
return 1;
|
||||
}
|
||||
|
||||
/* Entry point */
|
||||
struct cmd_context *create_toolcontext(struct arg *the_args)
|
||||
{
|
||||
@@ -425,6 +800,10 @@ struct cmd_context *create_toolcontext(struct arg *the_args)
|
||||
if (!setlocale(LC_ALL, ""))
|
||||
log_error("setlocale failed");
|
||||
|
||||
#ifdef INTL_PACKAGE
|
||||
bindtextdomain(INTL_PACKAGE, LOCALEDIR);
|
||||
#endif
|
||||
|
||||
init_syslog(DEFAULT_LOG_FACILITY);
|
||||
|
||||
if (!(cmd = dbg_malloc(sizeof(*cmd)))) {
|
||||
@@ -433,7 +812,11 @@ struct cmd_context *create_toolcontext(struct arg *the_args)
|
||||
}
|
||||
memset(cmd, 0, sizeof(*cmd));
|
||||
cmd->args = the_args;
|
||||
cmd->hosttags = 0;
|
||||
list_init(&cmd->formats);
|
||||
list_init(&cmd->segtypes);
|
||||
list_init(&cmd->tags);
|
||||
list_init(&cmd->config_files);
|
||||
|
||||
strcpy(cmd->sys_dir, DEFAULT_SYS_DIR);
|
||||
|
||||
@@ -444,11 +827,28 @@ struct cmd_context *create_toolcontext(struct arg *the_args)
|
||||
if (*cmd->sys_dir && !create_dir(cmd->sys_dir))
|
||||
goto error;
|
||||
|
||||
if (!_init_config(cmd))
|
||||
if (!(cmd->libmem = pool_create(4 * 1024))) {
|
||||
log_error("Library memory pool creation failed");
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (!_init_lvm_conf(cmd))
|
||||
goto error;
|
||||
|
||||
_init_logging(cmd);
|
||||
|
||||
if (!_init_hostname(cmd))
|
||||
goto error;
|
||||
|
||||
if (!_init_tags(cmd, cmd->cft))
|
||||
goto error;
|
||||
|
||||
if (!_init_tag_configs(cmd))
|
||||
goto error;
|
||||
|
||||
if (!_merge_config_files(cmd))
|
||||
goto error;
|
||||
|
||||
if (!_process_config(cmd))
|
||||
goto error;
|
||||
|
||||
@@ -468,8 +868,12 @@ struct cmd_context *create_toolcontext(struct arg *the_args)
|
||||
if (!_init_formats(cmd))
|
||||
goto error;
|
||||
|
||||
if (!_init_segtypes(cmd))
|
||||
goto error;
|
||||
|
||||
cmd->current_settings = cmd->default_settings;
|
||||
|
||||
cmd->config_valid = 1;
|
||||
return cmd;
|
||||
|
||||
error:
|
||||
@@ -495,6 +899,83 @@ static void _destroy_formats(struct list *formats)
|
||||
}
|
||||
}
|
||||
|
||||
static void _destroy_segtypes(struct list *segtypes)
|
||||
{
|
||||
struct list *sgtl, *tmp;
|
||||
struct segment_type *segtype;
|
||||
void *lib;
|
||||
|
||||
list_iterate_safe(sgtl, tmp, segtypes) {
|
||||
segtype = list_item(sgtl, struct segment_type);
|
||||
list_del(&segtype->list);
|
||||
lib = segtype->library;
|
||||
segtype->ops->destroy(segtype);
|
||||
#ifdef HAVE_LIBDL
|
||||
if (lib)
|
||||
dlclose(lib);
|
||||
#endif
|
||||
}
|
||||
}
|
||||
|
||||
int refresh_toolcontext(struct cmd_context *cmd)
|
||||
{
|
||||
log_verbose("Reloading config files");
|
||||
|
||||
if (cmd->config_valid) {
|
||||
if (cmd->dump_filter)
|
||||
persistent_filter_dump(cmd->filter);
|
||||
}
|
||||
|
||||
activation_exit();
|
||||
lvmcache_destroy();
|
||||
label_exit();
|
||||
_destroy_segtypes(&cmd->segtypes);
|
||||
_destroy_formats(&cmd->formats);
|
||||
if (cmd->filter) {
|
||||
cmd->filter->destroy(cmd->filter);
|
||||
cmd->filter = NULL;
|
||||
}
|
||||
dev_cache_exit();
|
||||
_destroy_tags(cmd);
|
||||
_destroy_tag_configs(cmd);
|
||||
|
||||
cmd->config_valid = 0;
|
||||
|
||||
cmd->hosttags = 0;
|
||||
|
||||
if (!_init_lvm_conf(cmd))
|
||||
return 0;
|
||||
|
||||
_init_logging(cmd);
|
||||
|
||||
if (!_init_tags(cmd, cmd->cft))
|
||||
return 0;
|
||||
|
||||
if (!_init_tag_configs(cmd))
|
||||
return 0;
|
||||
|
||||
if (!_merge_config_files(cmd))
|
||||
return 0;
|
||||
|
||||
if (!_process_config(cmd))
|
||||
return 0;
|
||||
|
||||
if (!_init_dev_cache(cmd))
|
||||
return 0;
|
||||
|
||||
if (!_init_filters(cmd))
|
||||
return 0;
|
||||
|
||||
if (!_init_formats(cmd))
|
||||
return 0;
|
||||
|
||||
if (!_init_segtypes(cmd))
|
||||
return 0;
|
||||
|
||||
cmd->config_valid = 1;
|
||||
return 1;
|
||||
}
|
||||
|
||||
void destroy_toolcontext(struct cmd_context *cmd)
|
||||
{
|
||||
if (cmd->dump_filter)
|
||||
@@ -503,11 +984,14 @@ void destroy_toolcontext(struct cmd_context *cmd)
|
||||
activation_exit();
|
||||
lvmcache_destroy();
|
||||
label_exit();
|
||||
_destroy_segtypes(&cmd->segtypes);
|
||||
_destroy_formats(&cmd->formats);
|
||||
cmd->filter->destroy(cmd->filter);
|
||||
pool_destroy(cmd->mem);
|
||||
dev_cache_exit();
|
||||
destroy_config_tree(cmd->cf);
|
||||
_destroy_tags(cmd);
|
||||
_destroy_tag_configs(cmd);
|
||||
pool_destroy(cmd->libmem);
|
||||
dbg_free(cmd);
|
||||
|
||||
release_log_memory();
|
||||
|
@@ -1,17 +1,23 @@
|
||||
/*
|
||||
* Copyright (C) 2001 Sistina Software (UK) Limited.
|
||||
* Copyright (C) 2001-2004 Sistina Software, Inc. All rights reserved.
|
||||
* Copyright (C) 2004 Red Hat, Inc. All rights reserved.
|
||||
*
|
||||
* This file is released under the LGPL.
|
||||
* This file is part of LVM2.
|
||||
*
|
||||
* This copyrighted material is made available to anyone wishing to use,
|
||||
* modify, copy, or redistribute it subject to the terms and conditions
|
||||
* of the GNU General Public License v.2.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software Foundation,
|
||||
* Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
*/
|
||||
|
||||
#ifndef _LVM_TOOLCONTEXT_H
|
||||
#define _LVM_TOOLCONTEXT_H
|
||||
|
||||
#include "dev-cache.h"
|
||||
#include "config.h"
|
||||
#include "pool.h"
|
||||
#include "metadata.h"
|
||||
|
||||
#include <stdio.h>
|
||||
#include <limits.h>
|
||||
@@ -39,16 +45,21 @@ struct config_info {
|
||||
mode_t umask;
|
||||
};
|
||||
|
||||
struct config_tree;
|
||||
|
||||
/* FIXME Split into tool & library contexts */
|
||||
/* command-instance-related variables needed by library */
|
||||
struct cmd_context {
|
||||
/* format handler allocates all objects from here */
|
||||
struct pool *mem;
|
||||
struct pool *libmem; /* For permanent config data */
|
||||
struct pool *mem; /* Transient: Cleared between each command */
|
||||
|
||||
const struct format_type *fmt; /* Current format to use by default */
|
||||
struct format_type *fmt_backup; /* Format to use for backups */
|
||||
|
||||
struct list formats; /* Available formats */
|
||||
struct list segtypes; /* Available segment types */
|
||||
const char *hostname;
|
||||
const char *kernel_vsn;
|
||||
|
||||
char *cmd_line;
|
||||
struct command *command;
|
||||
@@ -58,10 +69,16 @@ struct cmd_context {
|
||||
struct dev_filter *filter;
|
||||
int dump_filter; /* Dump filter when exiting? */
|
||||
|
||||
struct config_tree *cf;
|
||||
struct list config_files;
|
||||
int config_valid;
|
||||
struct config_tree *cft;
|
||||
struct config_info default_settings;
|
||||
struct config_info current_settings;
|
||||
|
||||
/* List of defined tags */
|
||||
struct list tags;
|
||||
int hosttags;
|
||||
|
||||
char sys_dir[PATH_MAX];
|
||||
char dev_dir[PATH_MAX];
|
||||
char proc_dir[PATH_MAX];
|
||||
@@ -69,5 +86,7 @@ struct cmd_context {
|
||||
|
||||
struct cmd_context *create_toolcontext(struct arg *the_args);
|
||||
void destroy_toolcontext(struct cmd_context *cmd);
|
||||
int refresh_toolcontext(struct cmd_context *cmd);
|
||||
int config_files_changed(struct cmd_context *cmd);
|
||||
|
||||
#endif
|
||||
|
@@ -1,7 +1,16 @@
|
||||
/*
|
||||
* Copyright (C) 2001 Sistina Software (UK) Limited.
|
||||
* Copyright (C) 2001-2004 Sistina Software, Inc. All rights reserved.
|
||||
* Copyright (C) 2004 Red Hat, Inc. All rights reserved.
|
||||
*
|
||||
* This file is released under the LGPL.
|
||||
* This file is part of LVM2.
|
||||
*
|
||||
* This copyrighted material is made available to anyone wishing to use,
|
||||
* modify, copy, or redistribute it subject to the terms and conditions
|
||||
* of the GNU General Public License v.2.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software Foundation,
|
||||
* Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
*/
|
||||
|
||||
#include "lib.h"
|
||||
@@ -9,6 +18,8 @@
|
||||
#include "crc.h"
|
||||
#include "pool.h"
|
||||
#include "device.h"
|
||||
#include "str_list.h"
|
||||
#include "toolcontext.h"
|
||||
|
||||
#include <sys/stat.h>
|
||||
#include <sys/mman.h>
|
||||
@@ -43,10 +54,11 @@ struct parser {
|
||||
};
|
||||
|
||||
struct cs {
|
||||
struct config_tree cf;
|
||||
struct config_tree cft;
|
||||
struct pool *mem;
|
||||
time_t timestamp;
|
||||
char *filename;
|
||||
int exists;
|
||||
};
|
||||
|
||||
static void _get_token(struct parser *p, int tok_prev);
|
||||
@@ -60,6 +72,8 @@ static struct config_value *_create_value(struct parser *p);
|
||||
static struct config_node *_create_node(struct parser *p);
|
||||
static char *_dup_tok(struct parser *p);
|
||||
|
||||
static const int sep = '/';
|
||||
|
||||
#define MAX_INDENT 32
|
||||
|
||||
#define match(t) do {\
|
||||
@@ -82,7 +96,7 @@ static int _tok_match(const char *str, const char *b, const char *e)
|
||||
/*
|
||||
* public interface
|
||||
*/
|
||||
struct config_tree *create_config_tree(void)
|
||||
struct config_tree *create_config_tree(const char *filename)
|
||||
{
|
||||
struct cs *c;
|
||||
struct pool *mem = pool_create(10 * 1024);
|
||||
@@ -92,29 +106,31 @@ struct config_tree *create_config_tree(void)
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (!(c = pool_alloc(mem, sizeof(*c)))) {
|
||||
if (!(c = pool_zalloc(mem, sizeof(*c)))) {
|
||||
stack;
|
||||
pool_destroy(mem);
|
||||
return 0;
|
||||
}
|
||||
|
||||
c->mem = mem;
|
||||
c->cf.root = (struct config_node *) NULL;
|
||||
c->cft.root = (struct config_node *) NULL;
|
||||
c->timestamp = 0;
|
||||
c->filename = NULL;
|
||||
return &c->cf;
|
||||
c->exists = 0;
|
||||
if (filename)
|
||||
c->filename = pool_strdup(c->mem, filename);
|
||||
return &c->cft;
|
||||
}
|
||||
|
||||
void destroy_config_tree(struct config_tree *cf)
|
||||
void destroy_config_tree(struct config_tree *cft)
|
||||
{
|
||||
pool_destroy(((struct cs *) cf)->mem);
|
||||
pool_destroy(((struct cs *) cft)->mem);
|
||||
}
|
||||
|
||||
int read_config_fd(struct config_tree *cf, struct device *dev,
|
||||
int read_config_fd(struct config_tree *cft, struct device *dev,
|
||||
off_t offset, size_t size, off_t offset2, size_t size2,
|
||||
checksum_fn_t checksum_fn, uint32_t checksum)
|
||||
{
|
||||
struct cs *c = (struct cs *) cf;
|
||||
struct cs *c = (struct cs *) cft;
|
||||
struct parser *p;
|
||||
int r = 0;
|
||||
int use_mmap = 1;
|
||||
@@ -172,7 +188,7 @@ int read_config_fd(struct config_tree *cf, struct device *dev,
|
||||
p->tb = p->te = p->fb;
|
||||
p->line = 1;
|
||||
_get_token(p, TOK_SECTION_E);
|
||||
if (!(cf->root = _file(p))) {
|
||||
if (!(cft->root = _file(p))) {
|
||||
stack;
|
||||
goto out;
|
||||
}
|
||||
@@ -193,99 +209,30 @@ int read_config_fd(struct config_tree *cf, struct device *dev,
|
||||
return r;
|
||||
}
|
||||
|
||||
int read_config_file(struct config_tree *cf, const char *file)
|
||||
int read_config_file(struct config_tree *cft)
|
||||
{
|
||||
struct cs *c = (struct cs *) cf;
|
||||
struct cs *c = (struct cs *) cft;
|
||||
struct stat info;
|
||||
struct device *dev;
|
||||
int r = 1;
|
||||
|
||||
if (stat(file, &info)) {
|
||||
log_sys_error("stat", file);
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (!S_ISREG(info.st_mode)) {
|
||||
log_error("%s is not a regular file", file);
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (info.st_size == 0) {
|
||||
log_verbose("%s is empty", file);
|
||||
return 1;
|
||||
}
|
||||
|
||||
if (!(dev = dev_create_file(file, NULL, NULL))) {
|
||||
stack;
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (!dev_open_flags(dev, O_RDONLY, 0, 0)) {
|
||||
stack;
|
||||
return 0;
|
||||
}
|
||||
|
||||
r = read_config_fd(cf, dev, 0, (size_t) info.st_size, 0, 0,
|
||||
(checksum_fn_t) NULL, 0);
|
||||
|
||||
dev_close(dev);
|
||||
|
||||
c->timestamp = info.st_mtime;
|
||||
c->filename = pool_strdup(c->mem, file);
|
||||
|
||||
return r;
|
||||
}
|
||||
|
||||
time_t config_file_timestamp(struct config_tree *cf)
|
||||
{
|
||||
struct cs *c = (struct cs *) cf;
|
||||
|
||||
return c->timestamp;
|
||||
}
|
||||
|
||||
/*
|
||||
* Returns 1 if config file reloaded
|
||||
*/
|
||||
int reload_config_file(struct config_tree **cf)
|
||||
{
|
||||
struct config_tree *new_cf;
|
||||
struct cs *c = (struct cs *) *cf;
|
||||
struct cs *new_cs;
|
||||
struct stat info;
|
||||
struct device *dev;
|
||||
int r;
|
||||
|
||||
if (!c->filename)
|
||||
return 0;
|
||||
|
||||
if (stat(c->filename, &info) == -1) {
|
||||
if (errno == ENOENT)
|
||||
return 1;
|
||||
if (stat(c->filename, &info)) {
|
||||
log_sys_error("stat", c->filename);
|
||||
log_error("Failed to reload configuration file");
|
||||
c->exists = 0;
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (!S_ISREG(info.st_mode)) {
|
||||
log_error("Configuration file %s is not a regular file",
|
||||
c->filename);
|
||||
log_error("%s is not a regular file", c->filename);
|
||||
c->exists = 0;
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* Unchanged? */
|
||||
if (c->timestamp == info.st_mtime)
|
||||
return 0;
|
||||
|
||||
log_verbose("Detected config file change: Reloading %s", c->filename);
|
||||
c->exists = 1;
|
||||
|
||||
if (info.st_size == 0) {
|
||||
log_verbose("Config file reload: %s is empty", c->filename);
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (!(new_cf = create_config_tree())) {
|
||||
log_error("Allocation of new config_tree failed");
|
||||
return 0;
|
||||
log_verbose("%s is empty", c->filename);
|
||||
return 1;
|
||||
}
|
||||
|
||||
if (!(dev = dev_create_file(c->filename, NULL, NULL))) {
|
||||
@@ -298,22 +245,63 @@ int reload_config_file(struct config_tree **cf)
|
||||
return 0;
|
||||
}
|
||||
|
||||
r = read_config_fd(new_cf, dev, 0, (size_t) info.st_size,
|
||||
0, 0, (checksum_fn_t) NULL, 0);
|
||||
r = read_config_fd(cft, dev, 0, (size_t) info.st_size, 0, 0,
|
||||
(checksum_fn_t) NULL, 0);
|
||||
|
||||
dev_close(dev);
|
||||
|
||||
if (r) {
|
||||
new_cs = (struct cs *) new_cf;
|
||||
new_cs->filename = pool_strdup(new_cs->mem, c->filename);
|
||||
new_cs->timestamp = info.st_mtime;
|
||||
destroy_config_tree(*cf);
|
||||
*cf = new_cf;
|
||||
}
|
||||
c->timestamp = info.st_mtime;
|
||||
|
||||
return r;
|
||||
}
|
||||
|
||||
time_t config_file_timestamp(struct config_tree *cft)
|
||||
{
|
||||
struct cs *c = (struct cs *) cft;
|
||||
|
||||
return c->timestamp;
|
||||
}
|
||||
|
||||
/*
|
||||
* Return 1 if config files ought to be reloaded
|
||||
*/
|
||||
int config_file_changed(struct config_tree *cft)
|
||||
{
|
||||
struct cs *c = (struct cs *) cft;
|
||||
struct stat info;
|
||||
|
||||
if (!c->filename)
|
||||
return 0;
|
||||
|
||||
if (stat(c->filename, &info) == -1) {
|
||||
/* Ignore a deleted config file: still use original data */
|
||||
if (errno == ENOENT) {
|
||||
if (!c->exists)
|
||||
return 0;
|
||||
log_very_verbose("Config file %s has disappeared!",
|
||||
c->filename);
|
||||
goto reload;
|
||||
}
|
||||
log_sys_error("stat", c->filename);
|
||||
log_error("Failed to reload configuration files");
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (!S_ISREG(info.st_mode)) {
|
||||
log_error("Configuration file %s is not a regular file",
|
||||
c->filename);
|
||||
goto reload;
|
||||
}
|
||||
|
||||
/* Unchanged? */
|
||||
if (c->timestamp == info.st_mtime)
|
||||
return 0;
|
||||
|
||||
reload:
|
||||
log_verbose("Detected config file change to %s", c->filename);
|
||||
return 1;
|
||||
}
|
||||
|
||||
static void _write_value(FILE *fp, struct config_value *v)
|
||||
{
|
||||
switch (v->type) {
|
||||
@@ -382,7 +370,7 @@ static int _write_config(struct config_node *n, FILE *fp, int level)
|
||||
return 1;
|
||||
}
|
||||
|
||||
int write_config_file(struct config_tree *cf, const char *file)
|
||||
int write_config_file(struct config_tree *cft, const char *file)
|
||||
{
|
||||
int r = 1;
|
||||
FILE *fp;
|
||||
@@ -396,7 +384,7 @@ int write_config_file(struct config_tree *cf, const char *file)
|
||||
}
|
||||
|
||||
log_verbose("Dumping configuration to %s", file);
|
||||
if (!_write_config(cf->root, fp, 0)) {
|
||||
if (!_write_config(cft->root, fp, 0)) {
|
||||
log_error("Failure while writing configuration");
|
||||
r = 0;
|
||||
}
|
||||
@@ -728,8 +716,8 @@ static char *_dup_tok(struct parser *p)
|
||||
/*
|
||||
* utility functions
|
||||
*/
|
||||
struct config_node *find_config_node(struct config_node *cn,
|
||||
const char *path, const int sep)
|
||||
struct config_node *find_config_node(const struct config_node *cn,
|
||||
const char *path)
|
||||
{
|
||||
const char *e;
|
||||
|
||||
@@ -757,13 +745,13 @@ struct config_node *find_config_node(struct config_node *cn,
|
||||
path = e;
|
||||
}
|
||||
|
||||
return cn;
|
||||
return (struct config_node *) cn;
|
||||
}
|
||||
|
||||
const char *find_config_str(struct config_node *cn,
|
||||
const char *path, const int sep, const char *fail)
|
||||
const char *find_config_str(const struct config_node *cn,
|
||||
const char *path, const char *fail)
|
||||
{
|
||||
struct config_node *n = find_config_node(cn, path, sep);
|
||||
const struct config_node *n = find_config_node(cn, path);
|
||||
|
||||
if (n && n->v->type == CFG_STRING) {
|
||||
if (*n->v->v.str)
|
||||
@@ -777,10 +765,9 @@ const char *find_config_str(struct config_node *cn,
|
||||
return fail;
|
||||
}
|
||||
|
||||
int find_config_int(struct config_node *cn, const char *path,
|
||||
const int sep, int fail)
|
||||
int find_config_int(const struct config_node *cn, const char *path, int fail)
|
||||
{
|
||||
struct config_node *n = find_config_node(cn, path, sep);
|
||||
const struct config_node *n = find_config_node(cn, path);
|
||||
|
||||
if (n && n->v->type == CFG_INT) {
|
||||
log_very_verbose("Setting %s to %d", path, n->v->v.i);
|
||||
@@ -792,10 +779,10 @@ int find_config_int(struct config_node *cn, const char *path,
|
||||
return fail;
|
||||
}
|
||||
|
||||
float find_config_float(struct config_node *cn, const char *path,
|
||||
const int sep, float fail)
|
||||
float find_config_float(const struct config_node *cn, const char *path,
|
||||
float fail)
|
||||
{
|
||||
struct config_node *n = find_config_node(cn, path, sep);
|
||||
const struct config_node *n = find_config_node(cn, path);
|
||||
|
||||
if (n && n->v->type == CFG_FLOAT) {
|
||||
log_very_verbose("Setting %s to %f", path, n->v->v.r);
|
||||
@@ -835,10 +822,9 @@ static int _str_to_bool(const char *str, int fail)
|
||||
return fail;
|
||||
}
|
||||
|
||||
int find_config_bool(struct config_node *cn, const char *path,
|
||||
const int sep, int fail)
|
||||
int find_config_bool(const struct config_node *cn, const char *path, int fail)
|
||||
{
|
||||
struct config_node *n = find_config_node(cn, path, sep);
|
||||
const struct config_node *n = find_config_node(cn, path);
|
||||
struct config_value *v;
|
||||
|
||||
if (!n)
|
||||
@@ -857,12 +843,12 @@ int find_config_bool(struct config_node *cn, const char *path,
|
||||
return fail;
|
||||
}
|
||||
|
||||
int get_config_uint32(struct config_node *cn, const char *path,
|
||||
const int sep, uint32_t *result)
|
||||
int get_config_uint32(const struct config_node *cn, const char *path,
|
||||
uint32_t *result)
|
||||
{
|
||||
struct config_node *n;
|
||||
const struct config_node *n;
|
||||
|
||||
n = find_config_node(cn, path, sep);
|
||||
n = find_config_node(cn, path);
|
||||
|
||||
if (!n || !n->v || n->v->type != CFG_INT)
|
||||
return 0;
|
||||
@@ -871,12 +857,12 @@ int get_config_uint32(struct config_node *cn, const char *path,
|
||||
return 1;
|
||||
}
|
||||
|
||||
int get_config_uint64(struct config_node *cn, const char *path,
|
||||
const int sep, uint64_t *result)
|
||||
int get_config_uint64(const struct config_node *cn, const char *path,
|
||||
uint64_t *result)
|
||||
{
|
||||
struct config_node *n;
|
||||
const struct config_node *n;
|
||||
|
||||
n = find_config_node(cn, path, sep);
|
||||
n = find_config_node(cn, path);
|
||||
|
||||
if (!n || !n->v || n->v->type != CFG_INT)
|
||||
return 0;
|
||||
@@ -886,12 +872,12 @@ int get_config_uint64(struct config_node *cn, const char *path,
|
||||
return 1;
|
||||
}
|
||||
|
||||
int get_config_str(struct config_node *cn, const char *path,
|
||||
const int sep, char **result)
|
||||
int get_config_str(const struct config_node *cn, const char *path,
|
||||
char **result)
|
||||
{
|
||||
struct config_node *n;
|
||||
const struct config_node *n;
|
||||
|
||||
n = find_config_node(cn, path, sep);
|
||||
n = find_config_node(cn, path);
|
||||
|
||||
if (!n || !n->v || n->v->type != CFG_STRING)
|
||||
return 0;
|
||||
@@ -899,3 +885,115 @@ int get_config_str(struct config_node *cn, const char *path,
|
||||
*result = n->v->v.str;
|
||||
return 1;
|
||||
}
|
||||
|
||||
/* Insert cn2 after cn1 */
|
||||
static void _insert_config_node(struct config_node **cn1,
|
||||
struct config_node *cn2)
|
||||
{
|
||||
if (!*cn1) {
|
||||
*cn1 = cn2;
|
||||
cn2->sib = NULL;
|
||||
} else {
|
||||
cn2->sib = (*cn1)->sib;
|
||||
(*cn1)->sib = cn2;
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
* Merge section cn2 into section cn1 (which has the same name)
|
||||
* overwriting any existing cn1 nodes with matching names.
|
||||
*/
|
||||
static void _merge_section(struct config_node *cn1, struct config_node *cn2)
|
||||
{
|
||||
struct config_node *cn, *nextn, *oldn;
|
||||
struct config_value *cv;
|
||||
|
||||
for (cn = cn2->child; cn; cn = nextn) {
|
||||
nextn = cn->sib;
|
||||
|
||||
/* Skip "tags" */
|
||||
if (!strcmp(cn->key, "tags"))
|
||||
continue;
|
||||
|
||||
/* Subsection? */
|
||||
if (!cn->v)
|
||||
/* Ignore - we don't have any of these yet */
|
||||
continue;
|
||||
/* Not already present? */
|
||||
if (!(oldn = find_config_node(cn1->child, cn->key))) {
|
||||
_insert_config_node(&cn1->child, cn);
|
||||
continue;
|
||||
}
|
||||
/* Merge certain value lists */
|
||||
if ((!strcmp(cn1->key, "activation") &&
|
||||
!strcmp(cn->key, "volume_list")) ||
|
||||
(!strcmp(cn1->key, "devices") &&
|
||||
(!strcmp(cn->key, "filter") || !strcmp(cn->key, "types")))) {
|
||||
cv = cn->v;
|
||||
while (cv->next)
|
||||
cv = cv->next;
|
||||
cv->next = oldn->v;
|
||||
}
|
||||
|
||||
/* Replace values */
|
||||
oldn->v = cn->v;
|
||||
}
|
||||
}
|
||||
|
||||
static int _match_host_tags(struct list *tags, struct config_node *tn)
|
||||
{
|
||||
struct config_value *tv;
|
||||
const char *str;
|
||||
|
||||
for (tv = tn->v; tv; tv = tv->next) {
|
||||
if (tv->type != CFG_STRING)
|
||||
continue;
|
||||
str = tv->v.str;
|
||||
if (*str == '@')
|
||||
str++;
|
||||
if (!*str)
|
||||
continue;
|
||||
if (str_list_match_item(tags, str))
|
||||
return 1;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* Destructively merge a new config tree into an existing one */
|
||||
int merge_config_tree(struct cmd_context *cmd, struct config_tree *cft,
|
||||
struct config_tree *newdata)
|
||||
{
|
||||
struct config_node *root = cft->root;
|
||||
struct config_node *cn, *nextn, *oldn, *tn, *cn2;
|
||||
|
||||
for (cn = newdata->root; cn; cn = nextn) {
|
||||
nextn = cn->sib;
|
||||
/* Ignore tags section */
|
||||
if (!strcmp(cn->key, "tags"))
|
||||
continue;
|
||||
/* If there's a tags node, skip if host tags don't match */
|
||||
if ((tn = find_config_node(cn->child, "tags"))) {
|
||||
if (!_match_host_tags(&cmd->tags, tn))
|
||||
continue;
|
||||
}
|
||||
if (!(oldn = find_config_node(root, cn->key))) {
|
||||
_insert_config_node(&cft->root, cn);
|
||||
/* Remove any "tags" nodes */
|
||||
for (cn2 = cn->child; cn2; cn2 = cn2->sib) {
|
||||
if (!strcmp(cn2->key, "tags")) {
|
||||
cn->child = cn2->sib;
|
||||
continue;
|
||||
}
|
||||
if (cn2->sib && !strcmp(cn2->sib->key, "tags")) {
|
||||
cn2->sib = cn2->sib->sib;
|
||||
continue;
|
||||
}
|
||||
}
|
||||
continue;
|
||||
}
|
||||
_merge_section(oldn, cn);
|
||||
}
|
||||
|
||||
return 1;
|
||||
}
|
||||
|
@@ -1,13 +1,23 @@
|
||||
/*
|
||||
* Copyright (C) 2001 Sistina Software (UK) Limited.
|
||||
* Copyright (C) 2001-2004 Sistina Software, Inc. All rights reserved.
|
||||
* Copyright (C) 2004 Red Hat, Inc. All rights reserved.
|
||||
*
|
||||
* This file is released under the LGPL.
|
||||
* This file is part of LVM2.
|
||||
*
|
||||
* This copyrighted material is made available to anyone wishing to use,
|
||||
* modify, copy, or redistribute it subject to the terms and conditions
|
||||
* of the GNU General Public License v.2.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software Foundation,
|
||||
* Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
*/
|
||||
|
||||
#ifndef _LVM_CONFIG_H
|
||||
#define _LVM_CONFIG_H
|
||||
|
||||
#include "device.h"
|
||||
struct device;
|
||||
struct cmd_context;
|
||||
|
||||
enum {
|
||||
CFG_STRING,
|
||||
@@ -36,46 +46,51 @@ struct config_tree {
|
||||
struct config_node *root;
|
||||
};
|
||||
|
||||
struct config_tree *create_config_tree(void);
|
||||
void destroy_config_tree(struct config_tree *cf);
|
||||
struct config_tree_list {
|
||||
struct list list;
|
||||
struct config_tree *cft;
|
||||
};
|
||||
|
||||
struct config_tree *create_config_tree(const char *filename);
|
||||
void destroy_config_tree(struct config_tree *cft);
|
||||
|
||||
typedef uint32_t (*checksum_fn_t) (uint32_t initial, void *buf, uint32_t size);
|
||||
|
||||
int read_config_fd(struct config_tree *cf, struct device *dev,
|
||||
int read_config_fd(struct config_tree *cft, struct device *dev,
|
||||
off_t offset, size_t size, off_t offset2, size_t size2,
|
||||
checksum_fn_t checksum_fn, uint32_t checksum);
|
||||
|
||||
int read_config_file(struct config_tree *cf, const char *file);
|
||||
int write_config_file(struct config_tree *cf, const char *file);
|
||||
int reload_config_file(struct config_tree **cf);
|
||||
time_t config_file_timestamp(struct config_tree *cf);
|
||||
int read_config_file(struct config_tree *cft);
|
||||
int write_config_file(struct config_tree *cft, const char *file);
|
||||
time_t config_file_timestamp(struct config_tree *cft);
|
||||
int config_file_changed(struct config_tree *cft);
|
||||
int merge_config_tree(struct cmd_context *cmd, struct config_tree *cft,
|
||||
struct config_tree *newdata);
|
||||
|
||||
struct config_node *find_config_node(struct config_node *cn,
|
||||
const char *path, const int separator);
|
||||
struct config_node *find_config_node(const struct config_node *cn,
|
||||
const char *path);
|
||||
|
||||
const char *find_config_str(struct config_node *cn,
|
||||
const char *path, const int sep, const char *fail);
|
||||
const char *find_config_str(const struct config_node *cn, const char *path,
|
||||
const char *fail);
|
||||
|
||||
int find_config_int(struct config_node *cn, const char *path,
|
||||
const int sep, int fail);
|
||||
int find_config_int(const struct config_node *cn, const char *path, int fail);
|
||||
|
||||
float find_config_float(struct config_node *cn, const char *path,
|
||||
const int sep, float fail);
|
||||
float find_config_float(const struct config_node *cn, const char *path,
|
||||
float fail);
|
||||
|
||||
/*
|
||||
* Understands (0, ~0), (y, n), (yes, no), (on,
|
||||
* off), (true, false).
|
||||
*/
|
||||
int find_config_bool(struct config_node *cn, const char *path,
|
||||
const int sep, int fail);
|
||||
int find_config_bool(const struct config_node *cn, const char *path, int fail);
|
||||
|
||||
int get_config_uint32(struct config_node *cn, const char *path,
|
||||
const int sep, uint32_t *result);
|
||||
int get_config_uint32(const struct config_node *cn, const char *path,
|
||||
uint32_t *result);
|
||||
|
||||
int get_config_uint64(struct config_node *cn, const char *path,
|
||||
const int sep, uint64_t *result);
|
||||
int get_config_uint64(const struct config_node *cn, const char *path,
|
||||
uint64_t *result);
|
||||
|
||||
int get_config_str(struct config_node *cn, const char *path,
|
||||
const int sep, char **result);
|
||||
int get_config_str(const struct config_node *cn, const char *path,
|
||||
char **result);
|
||||
|
||||
#endif
|
||||
|
@@ -1,7 +1,16 @@
|
||||
/*
|
||||
* Copyright (C) 2001 Sistina Software (UK) Limited.
|
||||
* Copyright (C) 2001-2004 Sistina Software, Inc. All rights reserved.
|
||||
* Copyright (C) 2004 Red Hat, Inc. All rights reserved.
|
||||
*
|
||||
* This file is released under the GPL.
|
||||
* This file is part of LVM2.
|
||||
*
|
||||
* This copyrighted material is made available to anyone wishing to use,
|
||||
* modify, copy, or redistribute it subject to the terms and conditions
|
||||
* of the GNU General Public License v.2.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software Foundation,
|
||||
* Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
*/
|
||||
|
||||
#ifndef _LVM_DEFAULTS_H
|
||||
@@ -19,12 +28,20 @@
|
||||
#define DEFAULT_SYS_DIR "/etc/lvm"
|
||||
#define DEFAULT_DEV_DIR "/dev"
|
||||
#define DEFAULT_PROC_DIR "/proc"
|
||||
#define DEFAULT_SYSFS_SCAN 1
|
||||
#define DEFAULT_MD_COMPONENT_DETECTION 1
|
||||
|
||||
#define DEFAULT_LOCK_DIR "/var/lock/lvm"
|
||||
#define DEFAULT_LOCKING_LIB "lvm2_locking.so"
|
||||
|
||||
#define DEFAULT_UMASK 0077
|
||||
|
||||
#ifdef LVM1_FALLBACK
|
||||
# define DEFAULT_FALLBACK_TO_LVM1 1
|
||||
#else
|
||||
# define DEFAULT_FALLBACK_TO_LVM1 0
|
||||
#endif
|
||||
|
||||
#ifdef LVM1_SUPPORT
|
||||
# define DEFAULT_FORMAT "lvm1"
|
||||
#else
|
||||
@@ -50,6 +67,7 @@
|
||||
#define DEFAULT_INDENT 1
|
||||
#define DEFAULT_UNITS "h"
|
||||
#define DEFAULT_SUFFIX 1
|
||||
#define DEFAULT_HOSTTAGS 0
|
||||
|
||||
#ifdef DEVMAPPER_SUPPORT
|
||||
# define DEFAULT_ACTIVATION 1
|
||||
@@ -73,12 +91,12 @@
|
||||
#define DEFAULT_REP_HEADINGS 1
|
||||
#define DEFAULT_REP_SEPARATOR " "
|
||||
|
||||
#define DEFAULT_LVS_COLS "lv_name,vg_name,lv_attr,lv_size,origin,snap_percent,move_pv,move_percent"
|
||||
#define DEFAULT_LVS_COLS "lv_name,vg_name,lv_attr,lv_size,origin,snap_percent,move_pv,copy_percent"
|
||||
#define DEFAULT_VGS_COLS "vg_name,pv_count,lv_count,snap_count,vg_attr,vg_size,vg_free"
|
||||
#define DEFAULT_PVS_COLS "pv_name,vg_name,pv_fmt,pv_attr,pv_size,pv_free"
|
||||
#define DEFAULT_SEGS_COLS "lv_name,vg_name,lv_attr,stripes,segtype,seg_size"
|
||||
|
||||
#define DEFAULT_LVS_COLS_VERB "lv_name,vg_name,seg_count,lv_attr,lv_size,lv_major,lv_minor,origin,snap_percent,move_pv,move_percent,lv_uuid"
|
||||
#define DEFAULT_LVS_COLS_VERB "lv_name,vg_name,seg_count,lv_attr,lv_size,lv_major,lv_minor,origin,snap_percent,move_pv,copy_percent,lv_uuid"
|
||||
#define DEFAULT_VGS_COLS_VERB "vg_name,vg_attr,vg_extent_size,pv_count,lv_count,snap_count,vg_size,vg_free,vg_uuid"
|
||||
#define DEFAULT_PVS_COLS_VERB "pv_name,vg_name,pv_fmt,pv_attr,pv_size,pv_free,pv_uuid"
|
||||
#define DEFAULT_SEGS_COLS_VERB "lv_name,vg_name,lv_attr,seg_start,seg_size,stripes,segtype,stripesize,chunksize"
|
||||
|
@@ -1,7 +1,16 @@
|
||||
/*
|
||||
* Copyright (C) 2001 Sistina Software (UK) Limited.
|
||||
* Copyright (C) 2001-2004 Sistina Software, Inc. All rights reserved.
|
||||
* Copyright (C) 2004 Red Hat, Inc. All rights reserved.
|
||||
*
|
||||
* This file is released under the LGPL.
|
||||
* This file is part of LVM2.
|
||||
*
|
||||
* This copyrighted material is made available to anyone wishing to use,
|
||||
* modify, copy, or redistribute it subject to the terms and conditions
|
||||
* of the GNU General Public License v.2.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software Foundation,
|
||||
* Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
*/
|
||||
|
||||
#include "lib.h"
|
||||
|
@@ -1,7 +1,16 @@
|
||||
/*
|
||||
* Copyright (C) 2001 Sistina Software (UK) Limited.
|
||||
* Copyright (C) 2001-2004 Sistina Software, Inc. All rights reserved.
|
||||
* Copyright (C) 2004 Red Hat, Inc. All rights reserved.
|
||||
*
|
||||
* This file is released under the GPL.
|
||||
* This file is part of LVM2.
|
||||
*
|
||||
* This copyrighted material is made available to anyone wishing to use,
|
||||
* modify, copy, or redistribute it subject to the terms and conditions
|
||||
* of the GNU General Public License v.2.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software Foundation,
|
||||
* Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
*/
|
||||
|
||||
#ifndef _LVM_BITSET_H
|
||||
|
@@ -1,7 +1,16 @@
|
||||
/*
|
||||
* Copyright (C) 2001 Sistina Software (UK) Limited.
|
||||
* Copyright (C) 2001-2004 Sistina Software, Inc. All rights reserved.
|
||||
* Copyright (C) 2004 Red Hat, Inc. All rights reserved.
|
||||
*
|
||||
* This file is released under the LGPL.
|
||||
* This file is part of LVM2.
|
||||
*
|
||||
* This copyrighted material is made available to anyone wishing to use,
|
||||
* modify, copy, or redistribute it subject to the terms and conditions
|
||||
* of the GNU General Public License v.2.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software Foundation,
|
||||
* Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
*/
|
||||
|
||||
#include "lib.h"
|
||||
|
@@ -1,7 +1,16 @@
|
||||
/*
|
||||
* Copyright (C) 2001 Sistina Software (UK) Limited.
|
||||
* Copyright (C) 2001-2004 Sistina Software, Inc. All rights reserved.
|
||||
* Copyright (C) 2004 Red Hat, Inc. All rights reserved.
|
||||
*
|
||||
* This file is released under the GPL.
|
||||
* This file is part of LVM2.
|
||||
*
|
||||
* This copyrighted material is made available to anyone wishing to use,
|
||||
* modify, copy, or redistribute it subject to the terms and conditions
|
||||
* of the GNU General Public License v.2.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software Foundation,
|
||||
* Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
*/
|
||||
|
||||
#ifndef _LVM_BTREE_H
|
||||
|
@@ -1,7 +1,16 @@
|
||||
/*
|
||||
* Copyright (C) 2001 Sistina Software
|
||||
* Copyright (C) 2001-2004 Sistina Software, Inc. All rights reserved.
|
||||
* Copyright (C) 2004 Red Hat, Inc. All rights reserved.
|
||||
*
|
||||
* This file is released under the LGPL.
|
||||
* This file is part of LVM2.
|
||||
*
|
||||
* This copyrighted material is made available to anyone wishing to use,
|
||||
* modify, copy, or redistribute it subject to the terms and conditions
|
||||
* of the GNU General Public License v.2.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software Foundation,
|
||||
* Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
*/
|
||||
|
||||
#include "lib.h"
|
||||
@@ -125,7 +134,7 @@ void hash_destroy(struct hash_table *t)
|
||||
dbg_free(t);
|
||||
}
|
||||
|
||||
static inline struct hash_node **_find(struct hash_table *t, const char *key)
|
||||
static struct hash_node **_find(struct hash_table *t, const char *key)
|
||||
{
|
||||
unsigned h = _hash(key) & (t->num_slots - 1);
|
||||
struct hash_node **c;
|
||||
|
@@ -1,7 +1,16 @@
|
||||
/*
|
||||
* Copyright (C) 2001 Sistina Software
|
||||
* Copyright (C) 2001-2004 Sistina Software, Inc. All rights reserved.
|
||||
* Copyright (C) 2004 Red Hat, Inc. All rights reserved.
|
||||
*
|
||||
* This file is released under the GPL.
|
||||
* This file is part of LVM2.
|
||||
*
|
||||
* This copyrighted material is made available to anyone wishing to use,
|
||||
* modify, copy, or redistribute it subject to the terms and conditions
|
||||
* of the GNU General Public License v.2.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software Foundation,
|
||||
* Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
*/
|
||||
|
||||
#ifndef _LVM_HASH_H
|
||||
|
@@ -1,7 +1,16 @@
|
||||
/*
|
||||
* Copyright (C) 2001 Sistina Software
|
||||
* Copyright (C) 2001-2004 Sistina Software, Inc. All rights reserved.
|
||||
* Copyright (C) 2004 Red Hat, Inc. All rights reserved.
|
||||
*
|
||||
* This file is released under the LGPL.
|
||||
* This file is part of LVM2.
|
||||
*
|
||||
* This copyrighted material is made available to anyone wishing to use,
|
||||
* modify, copy, or redistribute it subject to the terms and conditions
|
||||
* of the GNU General Public License v.2.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software Foundation,
|
||||
* Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
*/
|
||||
|
||||
#ifndef _LVM_LIST_H
|
||||
|
@@ -1,7 +1,16 @@
|
||||
/*
|
||||
* Copyright (C) 2001 Sistina Software (UK) Limited.
|
||||
* Copyright (C) 2001-2004 Sistina Software, Inc. All rights reserved.
|
||||
* Copyright (C) 2004 Red Hat, Inc. All rights reserved.
|
||||
*
|
||||
* This file is released under the GPL.
|
||||
* This file is part of LVM2.
|
||||
*
|
||||
* This copyrighted material is made available to anyone wishing to use,
|
||||
* modify, copy, or redistribute it subject to the terms and conditions
|
||||
* of the GNU General Public License v.2.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software Foundation,
|
||||
* Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
*/
|
||||
|
||||
#ifndef _LVM_TYPES_H
|
||||
|
@@ -1,7 +1,16 @@
|
||||
/*
|
||||
* Copyright (C) 2003 Sistina Software
|
||||
* Copyright (C) 2003-2004 Sistina Software, Inc. All rights reserved.
|
||||
* Copyright (C) 2004 Red Hat, Inc. All rights reserved.
|
||||
*
|
||||
* This file is released under the LGPL.
|
||||
* This file is part of LVM2.
|
||||
*
|
||||
* This copyrighted material is made available to anyone wishing to use,
|
||||
* modify, copy, or redistribute it subject to the terms and conditions
|
||||
* of the GNU General Public License v.2.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software Foundation,
|
||||
* Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
*/
|
||||
|
||||
#include "lib.h"
|
||||
@@ -57,6 +66,25 @@ int str_list_del(struct list *sll, const char *str)
|
||||
return 1;
|
||||
}
|
||||
|
||||
int str_list_dup(struct pool *mem, struct list *sllnew, struct list *sllold)
|
||||
{
|
||||
struct str_list *sl;
|
||||
|
||||
list_init(sllnew);
|
||||
|
||||
list_iterate_items(sl, sllold) {
|
||||
if (!str_list_add(mem, sllnew, strdup(sl->str))) {
|
||||
stack;
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
|
||||
return 1;
|
||||
}
|
||||
|
||||
/*
|
||||
* Is item on list?
|
||||
*/
|
||||
int str_list_match_item(struct list *sll, const char *str)
|
||||
{
|
||||
struct str_list *sl;
|
||||
@@ -68,6 +96,9 @@ int str_list_match_item(struct list *sll, const char *str)
|
||||
return 0;
|
||||
}
|
||||
|
||||
/*
|
||||
* Is at least one item on both lists?
|
||||
*/
|
||||
int str_list_match_list(struct list *sll, struct list *sll2)
|
||||
{
|
||||
struct str_list *sl;
|
||||
@@ -78,3 +109,20 @@ int str_list_match_list(struct list *sll, struct list *sll2)
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/*
|
||||
* Do both lists contain the same set of items?
|
||||
*/
|
||||
int str_list_lists_equal(struct list *sll, struct list *sll2)
|
||||
{
|
||||
struct str_list *sl;
|
||||
|
||||
if (list_size(sll) != list_size(sll2))
|
||||
return 0;
|
||||
|
||||
list_iterate_items(sl, sll)
|
||||
if (!str_list_match_item(sll2, sl->str))
|
||||
return 0;
|
||||
|
||||
return 1;
|
||||
}
|
||||
|
@@ -1,7 +1,16 @@
|
||||
/*
|
||||
* Copyright (C) 2003 Sistina Software (UK) Limited.
|
||||
* Copyright (C) 2003-2004 Sistina Software, Inc. All rights reserved.
|
||||
* Copyright (C) 2004 Red Hat, Inc. All rights reserved.
|
||||
*
|
||||
* This file is released under the GPL.
|
||||
* This file is part of LVM2.
|
||||
*
|
||||
* This copyrighted material is made available to anyone wishing to use,
|
||||
* modify, copy, or redistribute it subject to the terms and conditions
|
||||
* of the GNU General Public License v.2.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software Foundation,
|
||||
* Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
*/
|
||||
|
||||
#ifndef _LVM_STR_LIST_H
|
||||
@@ -14,5 +23,7 @@ int str_list_add(struct pool *mem, struct list *sll, const char *str);
|
||||
int str_list_del(struct list *sll, const char *str);
|
||||
int str_list_match_item(struct list *sll, const char *str);
|
||||
int str_list_match_list(struct list *sll, struct list *sll2);
|
||||
int str_list_lists_equal(struct list *sll, struct list *sll2);
|
||||
int str_list_dup(struct pool *mem, struct list *sllnew, struct list *sllold);
|
||||
|
||||
#endif
|
||||
|
@@ -1,7 +1,16 @@
|
||||
/*
|
||||
* Copyright (C) 2001 Sistina Software (UK) Limited.
|
||||
* Copyright (C) 2001-2004 Sistina Software, Inc. All rights reserved.
|
||||
* Copyright (C) 2004 Red Hat, Inc. All rights reserved.
|
||||
*
|
||||
* This file is released under the LGPL.
|
||||
* This file is part of LVM2.
|
||||
*
|
||||
* This copyrighted material is made available to anyone wishing to use,
|
||||
* modify, copy, or redistribute it subject to the terms and conditions
|
||||
* of the GNU General Public License v.2.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software Foundation,
|
||||
* Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
*/
|
||||
|
||||
#include "lib.h"
|
||||
@@ -313,6 +322,17 @@ static int _insert(const char *path, int rec)
|
||||
}
|
||||
|
||||
if (S_ISDIR(info.st_mode)) { /* add a directory */
|
||||
/* check it's not a symbolic link */
|
||||
if (lstat(path, &info) < 0) {
|
||||
log_sys_very_verbose("lstat", path);
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (S_ISLNK(info.st_mode)) {
|
||||
log_debug("%s: Symbolic link to directory", path);
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (rec)
|
||||
r = _insert_dir(path);
|
||||
|
||||
@@ -471,7 +491,7 @@ const char *dev_name_confirmed(struct device *dev, int quiet)
|
||||
}
|
||||
if (quiet)
|
||||
log_debug("Path %s no longer valid for device(%d,%d)",
|
||||
name, (int) MAJOR(dev->dev),
|
||||
name, (int) MAJOR(dev->dev),
|
||||
(int) MINOR(dev->dev));
|
||||
else
|
||||
log_error("Path %s no longer valid for device(%d,%d)",
|
||||
|
@@ -1,7 +1,16 @@
|
||||
/*
|
||||
* Copyright (C) 2001 Sistina Software (UK) Limited.
|
||||
* Copyright (C) 2001-2004 Sistina Software, Inc. All rights reserved.
|
||||
* Copyright (C) 2004 Red Hat, Inc. All rights reserved.
|
||||
*
|
||||
* This file is released under the GPL.
|
||||
* This file is part of LVM2.
|
||||
*
|
||||
* This copyrighted material is made available to anyone wishing to use,
|
||||
* modify, copy, or redistribute it subject to the terms and conditions
|
||||
* of the GNU General Public License v.2.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software Foundation,
|
||||
* Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
*/
|
||||
|
||||
#ifndef _LVM_DEV_CACHE_H
|
||||
|
@@ -1,7 +1,16 @@
|
||||
/*
|
||||
* Copyright (C) 2001 Sistina Software
|
||||
* Copyright (C) 2001-2004 Sistina Software, Inc. All rights reserved.
|
||||
* Copyright (C) 2004 Red Hat, Inc. All rights reserved.
|
||||
*
|
||||
* This file is released under the LGPL.
|
||||
* This file is part of LVM2.
|
||||
*
|
||||
* This copyrighted material is made available to anyone wishing to use,
|
||||
* modify, copy, or redistribute it subject to the terms and conditions
|
||||
* of the GNU General Public License v.2.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software Foundation,
|
||||
* Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
*/
|
||||
|
||||
#include "lib.h"
|
||||
@@ -10,6 +19,7 @@
|
||||
#include "metadata.h"
|
||||
#include "lvmcache.h"
|
||||
#include "memlock.h"
|
||||
#include "locking.h"
|
||||
|
||||
#include <limits.h>
|
||||
#include <sys/stat.h>
|
||||
@@ -23,6 +33,9 @@
|
||||
# undef WUNTRACED /* Avoid redefinition */
|
||||
# include <linux/fs.h> /* For block ioctl definitions */
|
||||
# define BLKSIZE_SHIFT SECTOR_SHIFT
|
||||
# ifndef BLKGETSIZE64 /* fs.h out-of-date */
|
||||
# define BLKGETSIZE64 _IOR(0x12, 114, size_t)
|
||||
# endif /* BLKGETSIZE64 */
|
||||
#else
|
||||
# include <sys/disk.h>
|
||||
# define BLKBSZGET DKIOCGETBLOCKSIZE
|
||||
@@ -38,12 +51,6 @@
|
||||
# endif
|
||||
#endif
|
||||
|
||||
|
||||
/* FIXME Use _llseek for 64-bit
|
||||
_syscall5(int, _llseek, uint, fd, ulong, hi, ulong, lo, loff_t *, res, uint, wh);
|
||||
if (_llseek((unsigned) fd, (ulong) (offset >> 32), (ulong) (offset & 0xFFFFFFFF), &pos, SEEK_SET) < 0) {
|
||||
*/
|
||||
|
||||
static LIST_INIT(_open_devices);
|
||||
|
||||
/*-----------------------------------------------------------------
|
||||
@@ -326,14 +333,20 @@ int dev_open_flags(struct device *dev, int flags, int direct, int quiet)
|
||||
|
||||
int dev_open_quiet(struct device *dev)
|
||||
{
|
||||
/* FIXME Open O_RDONLY if vg read lock? */
|
||||
return dev_open_flags(dev, O_RDWR, 1, 1);
|
||||
int flags;
|
||||
|
||||
flags = vg_write_lock_held() ? O_RDWR : O_RDONLY;
|
||||
|
||||
return dev_open_flags(dev, flags, 1, 1);
|
||||
}
|
||||
|
||||
int dev_open(struct device *dev)
|
||||
{
|
||||
/* FIXME Open O_RDONLY if vg read lock? */
|
||||
return dev_open_flags(dev, O_RDWR, 1, 0);
|
||||
int flags;
|
||||
|
||||
flags = vg_write_lock_held() ? O_RDWR : O_RDONLY;
|
||||
|
||||
return dev_open_flags(dev, flags, 1, 0);
|
||||
}
|
||||
|
||||
static void _close(struct device *dev)
|
||||
|
@@ -1,20 +1,16 @@
|
||||
/*
|
||||
* Copyright (C) 2001 Sistina Software
|
||||
* Copyright (C) 2001-2004 Sistina Software, Inc. All rights reserved.
|
||||
* Copyright (C) 2004 Red Hat, Inc. All rights reserved.
|
||||
*
|
||||
* This LVM library is free software; you can redistribute it and/or
|
||||
* modify it under the terms of the GNU Library General Public
|
||||
* License as published by the Free Software Foundation; either
|
||||
* version 2 of the License, or (at your option) any later version.
|
||||
* This file is part of LVM2.
|
||||
*
|
||||
* This LVM library is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
* Library General Public License for more details.
|
||||
* This copyrighted material is made available to anyone wishing to use,
|
||||
* modify, copy, or redistribute it subject to the terms and conditions
|
||||
* of the GNU General Public License v.2.
|
||||
*
|
||||
* You should have received a copy of the GNU Library General Public
|
||||
* License along with this LVM library; if not, write to the Free
|
||||
* Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
|
||||
* MA 02111-1307, USA
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software Foundation,
|
||||
* Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
*/
|
||||
|
||||
#if 0
|
||||
|
@@ -1,7 +1,16 @@
|
||||
/*
|
||||
* Copyright (C) 2001 Sistina Software (UK) Limited.
|
||||
* Copyright (C) 2001-2004 Sistina Software, Inc. All rights reserved.
|
||||
* Copyright (C) 2004 Red Hat, Inc. All rights reserved.
|
||||
*
|
||||
* This file is released under the GPL.
|
||||
* This file is part of LVM2.
|
||||
*
|
||||
* This copyrighted material is made available to anyone wishing to use,
|
||||
* modify, copy, or redistribute it subject to the terms and conditions
|
||||
* of the GNU General Public License v.2.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software Foundation,
|
||||
* Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
*/
|
||||
|
||||
#ifndef _LVM_DEVICE_H
|
||||
|
@@ -1,21 +1,16 @@
|
||||
/*
|
||||
* Copyright (C) 2001 Sistina Software
|
||||
* Copyright (C) 2001-2004 Sistina Software, Inc. All rights reserved.
|
||||
* Copyright (C) 2004 Red Hat, Inc. All rights reserved.
|
||||
*
|
||||
* This LVM library is free software; you can redistribute it and/or
|
||||
* modify it under the terms of the GNU Library General Public
|
||||
* License as published by the Free Software Foundation; either
|
||||
* version 2 of the License, or (at your option) any later version.
|
||||
* This file is part of LVM2.
|
||||
*
|
||||
* This LVM library is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
* Library General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Library General Public
|
||||
* License along with this LVM library; if not, write to the Free
|
||||
* Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
|
||||
* MA 02111-1307, USA
|
||||
* This copyrighted material is made available to anyone wishing to use,
|
||||
* modify, copy, or redistribute it subject to the terms and conditions
|
||||
* of the GNU General Public License v.2.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software Foundation,
|
||||
* Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
*/
|
||||
|
||||
#include "lib.h"
|
||||
@@ -23,6 +18,7 @@
|
||||
#include "display.h"
|
||||
#include "activate.h"
|
||||
#include "toolcontext.h"
|
||||
#include "segtypes.h"
|
||||
|
||||
#define SIZE_BUF 128
|
||||
|
||||
@@ -31,23 +27,13 @@ static struct {
|
||||
const char *str;
|
||||
} _policies[] = {
|
||||
{
|
||||
ALLOC_NEXT_FREE, "next free"}, {
|
||||
ALLOC_CONTIGUOUS, "contiguous"}, {
|
||||
ALLOC_DEFAULT, "next free (default)"}
|
||||
};
|
||||
|
||||
static struct {
|
||||
segment_type_t segtype;
|
||||
const char *str;
|
||||
} _segtypes[] = {
|
||||
{
|
||||
SEG_STRIPED, "striped"}, {
|
||||
SEG_MIRRORED, "mirror"}, {
|
||||
SEG_SNAPSHOT, "snapshot"}
|
||||
ALLOC_NORMAL, "normal"}, {
|
||||
ALLOC_ANYWHERE, "anywhere"}, {
|
||||
ALLOC_INHERIT, "inherit"}
|
||||
};
|
||||
|
||||
static int _num_policies = sizeof(_policies) / sizeof(*_policies);
|
||||
static int _num_segtypes = sizeof(_segtypes) / sizeof(*_segtypes);
|
||||
|
||||
uint64_t units_to_bytes(const char *units, char *unit_type)
|
||||
{
|
||||
@@ -129,17 +115,6 @@ const char *get_alloc_string(alloc_policy_t alloc)
|
||||
return NULL;
|
||||
}
|
||||
|
||||
const char *get_segtype_string(segment_type_t segtype)
|
||||
{
|
||||
int i;
|
||||
|
||||
for (i = 0; i < _num_segtypes; i++)
|
||||
if (_segtypes[i].segtype == segtype)
|
||||
return _segtypes[i].str;
|
||||
|
||||
return "unknown";
|
||||
}
|
||||
|
||||
alloc_policy_t get_alloc_from_string(const char *str)
|
||||
{
|
||||
int i;
|
||||
@@ -148,26 +123,19 @@ alloc_policy_t get_alloc_from_string(const char *str)
|
||||
if (!strcmp(_policies[i].str, str))
|
||||
return _policies[i].alloc;
|
||||
|
||||
log_error("Unrecognised allocation policy - using default");
|
||||
return ALLOC_DEFAULT;
|
||||
}
|
||||
|
||||
segment_type_t get_segtype_from_string(const char *str)
|
||||
{
|
||||
int i;
|
||||
|
||||
for (i = 0; i < _num_segtypes; i++)
|
||||
if (!strcmp(_segtypes[i].str, str))
|
||||
return _segtypes[i].segtype;
|
||||
|
||||
log_error("Unrecognised segment type - using default (striped)");
|
||||
return SEG_STRIPED;
|
||||
/* Special case for old metadata */
|
||||
if(!strcmp("next free", str))
|
||||
return ALLOC_NORMAL;
|
||||
|
||||
log_error("Unrecognised allocation policy %s", str);
|
||||
return ALLOC_INVALID;
|
||||
}
|
||||
|
||||
/* Size supplied in sectors */
|
||||
const char *display_size(struct cmd_context *cmd, uint64_t size, size_len_t sl)
|
||||
{
|
||||
int s;
|
||||
int suffix = 1;
|
||||
int suffix = 1, precision;
|
||||
uint64_t byte = UINT64_C(0);
|
||||
uint64_t units = UINT64_C(1024);
|
||||
char *size_buf = NULL;
|
||||
@@ -202,8 +170,9 @@ const char *display_size(struct cmd_context *cmd, uint64_t size, size_len_t sl)
|
||||
|
||||
if (s < 8) {
|
||||
byte = cmd->current_settings.unit_factor;
|
||||
size *= UINT64_C(1024);
|
||||
size *= UINT64_C(512);
|
||||
} else {
|
||||
size /= 2;
|
||||
suffix = 1;
|
||||
if (cmd->current_settings.unit_type == 'H')
|
||||
units = UINT64_C(1000);
|
||||
@@ -215,8 +184,18 @@ const char *display_size(struct cmd_context *cmd, uint64_t size, size_len_t sl)
|
||||
s++, byte /= units;
|
||||
}
|
||||
|
||||
snprintf(size_buf, SIZE_BUF - 1, "%.2f%s", (float) size / byte,
|
||||
suffix ? size_str[s][sl] : "");
|
||||
/* FIXME Make precision configurable */
|
||||
switch(toupper((int) cmd->current_settings.unit_type)) {
|
||||
case 'B':
|
||||
case 'S':
|
||||
precision = 0;
|
||||
break;
|
||||
default:
|
||||
precision = 2;
|
||||
}
|
||||
|
||||
snprintf(size_buf, SIZE_BUF - 1, "%.*f%s", precision,
|
||||
(double) size / byte, suffix ? size_str[s][sl] : "");
|
||||
|
||||
return size_buf;
|
||||
}
|
||||
@@ -269,18 +248,18 @@ void pvdisplay_full(struct cmd_context *cmd, struct physical_volume *pv,
|
||||
log_print("VG Name %s%s", pv->vg_name,
|
||||
pv->status & EXPORTED_VG ? " (exported)" : "");
|
||||
|
||||
size = display_size(cmd, (uint64_t) pv->size / 2, SIZE_SHORT);
|
||||
size = display_size(cmd, (uint64_t) pv->size, SIZE_SHORT);
|
||||
if (pv->pe_size && pv->pe_count) {
|
||||
|
||||
/******** FIXME display LVM on-disk data size
|
||||
size2 = display_size(pv->size / 2, SIZE_SHORT);
|
||||
size2 = display_size(pv->size, SIZE_SHORT);
|
||||
********/
|
||||
|
||||
log_print("PV Size %s" " / not usable %s", /* [LVM: %s]", */
|
||||
size, display_size(cmd,
|
||||
(pv->size -
|
||||
pv->pe_count * pv->pe_size) / 2,
|
||||
SIZE_SHORT));
|
||||
size,
|
||||
display_size(cmd, (pv->size -
|
||||
pv->pe_count * pv->pe_size),
|
||||
SIZE_SHORT));
|
||||
|
||||
} else
|
||||
log_print("PV Size %s", size);
|
||||
@@ -391,8 +370,7 @@ int lvdisplay_full(struct cmd_context *cmd, struct logical_volume *lv,
|
||||
snap_active = lv_snapshot_percent(snap->cow,
|
||||
&snap_percent);
|
||||
if (!snap_active || snap_percent < 0 ||
|
||||
snap_percent >= 100)
|
||||
snap_active = 0;
|
||||
snap_percent >= 100) snap_active = 0;
|
||||
log_print(" %s%s/%s [%s]",
|
||||
lv->vg->cmd->dev_dir, lv->vg->name,
|
||||
snap->cow->name,
|
||||
@@ -424,7 +402,7 @@ int lvdisplay_full(struct cmd_context *cmd, struct logical_volume *lv,
|
||||
|
||||
log_print("LV Size %s",
|
||||
display_size(cmd,
|
||||
snap ? snap->origin->size / 2 : lv->size / 2,
|
||||
snap ? snap->origin->size : lv->size,
|
||||
SIZE_SHORT));
|
||||
|
||||
log_print("Current LE %u",
|
||||
@@ -445,11 +423,11 @@ int lvdisplay_full(struct cmd_context *cmd, struct logical_volume *lv,
|
||||
snap_percent = 100;
|
||||
|
||||
log_print("Snapshot chunk size %s",
|
||||
display_size(cmd, (uint64_t) snap->chunk_size / 2,
|
||||
display_size(cmd, (uint64_t) snap->chunk_size,
|
||||
SIZE_SHORT));
|
||||
|
||||
/*
|
||||
size = display_size(lv->size / 2, SIZE_SHORT);
|
||||
size = display_size(lv->size, SIZE_SHORT);
|
||||
sscanf(size, "%f", &fsize);
|
||||
fused = fsize * snap_percent / 100;
|
||||
*/
|
||||
@@ -483,7 +461,7 @@ int lvdisplay_full(struct cmd_context *cmd, struct logical_volume *lv,
|
||||
return 0;
|
||||
}
|
||||
|
||||
static void _display_stripe(struct lv_segment *seg, uint32_t s, const char *pre)
|
||||
void display_stripe(const struct lv_segment *seg, uint32_t s, const char *pre)
|
||||
{
|
||||
switch (seg->area[s].type) {
|
||||
case AREA_PV:
|
||||
@@ -511,52 +489,18 @@ static void _display_stripe(struct lv_segment *seg, uint32_t s, const char *pre)
|
||||
|
||||
int lvdisplay_segments(struct logical_volume *lv)
|
||||
{
|
||||
uint32_t s;
|
||||
struct list *segh;
|
||||
struct lv_segment *seg;
|
||||
|
||||
log_print("--- Segments ---");
|
||||
|
||||
list_iterate(segh, &lv->segments) {
|
||||
seg = list_item(segh, struct lv_segment);
|
||||
|
||||
list_iterate_items(seg, &lv->segments) {
|
||||
log_print("Logical extent %u to %u:",
|
||||
seg->le, seg->le + seg->len - 1);
|
||||
|
||||
if (seg->type == SEG_STRIPED && seg->area_count == 1)
|
||||
log_print(" Type\t\tlinear");
|
||||
else
|
||||
log_print(" Type\t\t%s",
|
||||
get_segtype_string(seg->type));
|
||||
log_print(" Type\t\t%s", seg->segtype->ops->name(seg));
|
||||
|
||||
switch (seg->type) {
|
||||
case SEG_STRIPED:
|
||||
if (seg->area_count == 1)
|
||||
_display_stripe(seg, 0, " ");
|
||||
else {
|
||||
log_print(" Stripes\t\t%u", seg->area_count);
|
||||
log_print(" Stripe size\t\t%u KB",
|
||||
seg->stripe_size / 2);
|
||||
|
||||
for (s = 0; s < seg->area_count; s++) {
|
||||
log_print(" Stripe %d:", s);
|
||||
_display_stripe(seg, s, " ");
|
||||
}
|
||||
}
|
||||
log_print(" ");
|
||||
break;
|
||||
case SEG_SNAPSHOT:
|
||||
break;
|
||||
case SEG_MIRRORED:
|
||||
log_print(" Mirrors\t\t%u", seg->area_count);
|
||||
log_print(" Mirror size\t\t%u", seg->area_len);
|
||||
log_print(" Mirror original:");
|
||||
_display_stripe(seg, 0, " ");
|
||||
log_print(" Mirror destination:");
|
||||
_display_stripe(seg, 1, " ");
|
||||
log_print(" ");
|
||||
break;
|
||||
}
|
||||
if (seg->segtype->ops->display)
|
||||
seg->segtype->ops->display(seg);
|
||||
}
|
||||
|
||||
log_print(" ");
|
||||
@@ -610,7 +554,7 @@ void vgdisplay_full(struct volume_group *vg)
|
||||
log_print("Open LV %u", lvs_in_vg_opened(vg));
|
||||
/****** FIXME Max LV Size
|
||||
log_print ( "MAX LV Size %s",
|
||||
( s1 = display_size ( LVM_LV_SIZE_MAX(vg) / 2, SIZE_SHORT)));
|
||||
( s1 = display_size ( LVM_LV_SIZE_MAX(vg), SIZE_SHORT)));
|
||||
free ( s1);
|
||||
*********/
|
||||
log_print("Max PV %u", vg->max_pv);
|
||||
@@ -619,32 +563,25 @@ void vgdisplay_full(struct volume_group *vg)
|
||||
|
||||
log_print("VG Size %s",
|
||||
display_size(vg->cmd,
|
||||
(uint64_t) vg->extent_count * (vg->extent_size /
|
||||
2), SIZE_SHORT));
|
||||
(uint64_t) vg->extent_count * vg->extent_size,
|
||||
SIZE_SHORT));
|
||||
|
||||
log_print("PE Size %s",
|
||||
display_size(vg->cmd, (uint64_t) vg->extent_size / 2,
|
||||
display_size(vg->cmd, (uint64_t) vg->extent_size,
|
||||
SIZE_SHORT));
|
||||
|
||||
log_print("Total PE %u", vg->extent_count);
|
||||
|
||||
log_print("Alloc PE / Size %u / %s",
|
||||
vg->extent_count - vg->free_count, display_size(vg->cmd,
|
||||
((uint64_t)
|
||||
vg->
|
||||
extent_count
|
||||
-
|
||||
vg->
|
||||
free_count) *
|
||||
(vg->
|
||||
extent_size /
|
||||
2),
|
||||
SIZE_SHORT));
|
||||
vg->extent_count - vg->free_count,
|
||||
display_size(vg->cmd,
|
||||
((uint64_t) vg->extent_count - vg->free_count) *
|
||||
vg->extent_size, SIZE_SHORT));
|
||||
|
||||
log_print("Free PE / Size %u / %s", vg->free_count,
|
||||
display_size(vg->cmd,
|
||||
(uint64_t) vg->free_count * (vg->extent_size /
|
||||
2), SIZE_SHORT));
|
||||
(uint64_t) vg->free_count * vg->extent_size,
|
||||
SIZE_SHORT));
|
||||
|
||||
if (!id_write_format(&vg->id, uuid, sizeof(uuid))) {
|
||||
stack;
|
||||
@@ -659,6 +596,53 @@ void vgdisplay_full(struct volume_group *vg)
|
||||
|
||||
void vgdisplay_colons(struct volume_group *vg)
|
||||
{
|
||||
uint32_t active_pvs;
|
||||
const char *access;
|
||||
char uuid[64];
|
||||
|
||||
if (vg->status & PARTIAL_VG)
|
||||
active_pvs = list_size(&vg->pvs);
|
||||
else
|
||||
active_pvs = vg->pv_count;
|
||||
|
||||
switch (vg->status & (LVM_READ | LVM_WRITE)) {
|
||||
case LVM_READ | LVM_WRITE:
|
||||
access = "r/w";
|
||||
break;
|
||||
case LVM_READ:
|
||||
access = "r";
|
||||
break;
|
||||
case LVM_WRITE:
|
||||
access = "w";
|
||||
break;
|
||||
default:
|
||||
access = "";
|
||||
}
|
||||
|
||||
if (!id_write_format(&vg->id, uuid, sizeof(uuid))) {
|
||||
stack;
|
||||
return;
|
||||
}
|
||||
|
||||
log_print("%s:%s:%d:-1:%u:%u:%u:-1:%u:%u:%u:%" PRIu64 ":%" PRIu32
|
||||
":%u:%u:%u:%s",
|
||||
vg->name,
|
||||
access,
|
||||
vg->status,
|
||||
/* internal volume group number; obsolete */
|
||||
vg->max_lv,
|
||||
vg->lv_count,
|
||||
lvs_in_vg_opened(vg),
|
||||
/* FIXME: maximum logical volume size */
|
||||
vg->max_pv,
|
||||
vg->pv_count,
|
||||
active_pvs,
|
||||
(uint64_t) vg->extent_count * (vg->extent_size / 2),
|
||||
vg->extent_size / 2,
|
||||
vg->extent_count,
|
||||
vg->extent_count - vg->free_count,
|
||||
vg->free_count,
|
||||
uuid[0] ? uuid : "none");
|
||||
return;
|
||||
}
|
||||
|
||||
@@ -666,15 +650,15 @@ void vgdisplay_short(struct volume_group *vg)
|
||||
{
|
||||
log_print("\"%s\" %-9s [%-9s used / %s free]", vg->name,
|
||||
/********* FIXME if "open" print "/used" else print "/idle"??? ******/
|
||||
display_size(vg->cmd, (uint64_t) vg->extent_count *
|
||||
vg->extent_size / 2, SIZE_SHORT),
|
||||
display_size(vg->cmd,
|
||||
(uint64_t) vg->extent_count * vg->extent_size,
|
||||
SIZE_SHORT),
|
||||
display_size(vg->cmd,
|
||||
((uint64_t) vg->extent_count -
|
||||
vg->free_count) * vg->extent_size / 2,
|
||||
SIZE_SHORT), display_size(vg->cmd,
|
||||
(uint64_t) vg->
|
||||
free_count *
|
||||
vg->extent_size / 2,
|
||||
SIZE_SHORT));
|
||||
vg->free_count) * vg->extent_size,
|
||||
SIZE_SHORT),
|
||||
display_size(vg->cmd,
|
||||
(uint64_t) vg->free_count * vg->extent_size,
|
||||
SIZE_SHORT));
|
||||
return;
|
||||
}
|
||||
|
@@ -1,21 +1,16 @@
|
||||
/*
|
||||
* Copyright (C) 2001 Sistina Software
|
||||
* Copyright (C) 2001-2004 Sistina Software, Inc. All rights reserved.
|
||||
* Copyright (C) 2004 Red Hat, Inc. All rights reserved.
|
||||
*
|
||||
* This LVM library is free software; you can redistribute it and/or
|
||||
* modify it under the terms of the GNU Library General Public
|
||||
* License as published by the Free Software Foundation; either
|
||||
* version 2 of the License, or (at your option) any later version.
|
||||
* This file is part of LVM2.
|
||||
*
|
||||
* This LVM library is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
* Library General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Library General Public
|
||||
* License along with this LVM library; if not, write to the Free
|
||||
* Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
|
||||
* MA 02111-1307, USA
|
||||
* This copyrighted material is made available to anyone wishing to use,
|
||||
* modify, copy, or redistribute it subject to the terms and conditions
|
||||
* of the GNU General Public License v.2.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software Foundation,
|
||||
* Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
*/
|
||||
|
||||
#ifndef _LVM_DISPLAY_H
|
||||
@@ -32,6 +27,7 @@ uint64_t units_to_bytes(const char *units, char *unit_type);
|
||||
/* Specify size in KB */
|
||||
const char *display_size(struct cmd_context *cmd, uint64_t size, size_len_t sl);
|
||||
char *display_uuid(char *uuidstr);
|
||||
void display_stripe(const struct lv_segment *seg, uint32_t s, const char *pre);
|
||||
|
||||
void pvdisplay_colons(struct physical_volume *pv);
|
||||
void pvdisplay_full(struct cmd_context *cmd, struct physical_volume *pv,
|
||||
@@ -55,10 +51,4 @@ void vgdisplay_short(struct volume_group *vg);
|
||||
const char *get_alloc_string(alloc_policy_t alloc);
|
||||
alloc_policy_t get_alloc_from_string(const char *str);
|
||||
|
||||
/*
|
||||
* Segment type display conversion routines.
|
||||
*/
|
||||
segment_type_t get_segtype_from_string(const char *str);
|
||||
const char *get_segtype_string(segment_type_t segtype);
|
||||
|
||||
#endif
|
||||
|
101
lib/error/errseg.c
Normal file
101
lib/error/errseg.c
Normal file
@@ -0,0 +1,101 @@
|
||||
/*
|
||||
* Copyright (C) 2004 Red Hat, Inc. All rights reserved.
|
||||
*
|
||||
* This file is part of LVM2.
|
||||
*
|
||||
* This copyrighted material is made available to anyone wishing to use,
|
||||
* modify, copy, or redistribute it subject to the terms and conditions
|
||||
* of the GNU General Public License v.2.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software Foundation,
|
||||
* Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
*/
|
||||
|
||||
#include "lib.h"
|
||||
#include "pool.h"
|
||||
#include "list.h"
|
||||
#include "toolcontext.h"
|
||||
#include "segtypes.h"
|
||||
#include "display.h"
|
||||
#include "text_export.h"
|
||||
#include "text_import.h"
|
||||
#include "config.h"
|
||||
#include "str_list.h"
|
||||
#include "targets.h"
|
||||
#include "lvm-string.h"
|
||||
#include "activate.h"
|
||||
|
||||
static const char *_name(const struct lv_segment *seg)
|
||||
{
|
||||
return seg->segtype->name;
|
||||
}
|
||||
|
||||
static int _merge_segments(struct lv_segment *seg1, struct lv_segment *seg2)
|
||||
{
|
||||
seg1->len += seg2->len;
|
||||
seg1->area_len += seg2->area_len;
|
||||
|
||||
return 1;
|
||||
}
|
||||
|
||||
#ifdef DEVMAPPER_SUPPORT
|
||||
static int _compose_target_line(struct dev_manager *dm, struct pool *mem,
|
||||
struct config_tree *cft, void **target_state,
|
||||
struct lv_segment *seg, char *params,
|
||||
size_t paramsize, const char **target, int *pos,
|
||||
uint32_t *pvmove_mirror_count)
|
||||
{
|
||||
/* error */
|
||||
|
||||
*target = "error";
|
||||
*params = '\0';
|
||||
|
||||
return 1;
|
||||
}
|
||||
|
||||
static int _target_present(void)
|
||||
{
|
||||
static int checked = 0;
|
||||
static int present = 0;
|
||||
|
||||
if (!checked)
|
||||
present = target_present("error");
|
||||
|
||||
checked = 1;
|
||||
return present;
|
||||
}
|
||||
#endif
|
||||
|
||||
static void _destroy(const struct segment_type *segtype)
|
||||
{
|
||||
dbg_free((void *) segtype);
|
||||
}
|
||||
|
||||
static struct segtype_handler _error_ops = {
|
||||
name:_name,
|
||||
merge_segments:_merge_segments,
|
||||
#ifdef DEVMAPPER_SUPPORT
|
||||
compose_target_line:_compose_target_line,
|
||||
target_present:_target_present,
|
||||
#endif
|
||||
destroy:_destroy,
|
||||
};
|
||||
|
||||
struct segment_type *init_error_segtype(struct cmd_context *cmd)
|
||||
{
|
||||
struct segment_type *segtype = dbg_malloc(sizeof(*segtype));
|
||||
|
||||
if (!segtype) {
|
||||
stack;
|
||||
return NULL;
|
||||
}
|
||||
|
||||
segtype->cmd = cmd;
|
||||
segtype->ops = &_error_ops;
|
||||
segtype->name = "error";
|
||||
segtype->private = NULL;
|
||||
segtype->flags = SEG_CAN_SPLIT | SEG_VIRTUAL;
|
||||
|
||||
return segtype;
|
||||
}
|
@@ -1,7 +1,16 @@
|
||||
/*
|
||||
* Copyright (C) 2001 Sistina Software (UK) Limited.
|
||||
* Copyright (C) 2001-2004 Sistina Software, Inc. All rights reserved.
|
||||
* Copyright (C) 2004 Red Hat, Inc. All rights reserved.
|
||||
*
|
||||
* This file is released under the LGPL.
|
||||
* This file is part of LVM2.
|
||||
*
|
||||
* This copyrighted material is made available to anyone wishing to use,
|
||||
* modify, copy, or redistribute it subject to the terms and conditions
|
||||
* of the GNU General Public License v.2.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software Foundation,
|
||||
* Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
*/
|
||||
|
||||
#include "lib.h"
|
||||
@@ -37,35 +46,32 @@ static void _destroy(struct dev_filter *f)
|
||||
dbg_free(f);
|
||||
}
|
||||
|
||||
struct dev_filter *composite_filter_create(int n, ...)
|
||||
struct dev_filter *composite_filter_create(int n, struct dev_filter **filters)
|
||||
{
|
||||
struct dev_filter **filters = dbg_malloc(sizeof(*filters) * (n + 1));
|
||||
struct dev_filter *cf;
|
||||
va_list ap;
|
||||
int i;
|
||||
struct dev_filter **filters_copy, *cft;
|
||||
|
||||
if (!filters) {
|
||||
stack;
|
||||
return NULL;
|
||||
}
|
||||
|
||||
if (!(cf = dbg_malloc(sizeof(*cf)))) {
|
||||
stack;
|
||||
dbg_free(filters);
|
||||
if (!(filters_copy = dbg_malloc(sizeof(*filters) * (n + 1)))) {
|
||||
log_error("composite filters allocation failed");
|
||||
return NULL;
|
||||
}
|
||||
|
||||
va_start(ap, n);
|
||||
for (i = 0; i < n; i++) {
|
||||
struct dev_filter *f = va_arg(ap, struct dev_filter *);
|
||||
filters[i] = f;
|
||||
memcpy(filters_copy, filters, sizeof(*filters) * n);
|
||||
filters_copy[n] = NULL;
|
||||
|
||||
if (!(cft = dbg_malloc(sizeof(*cft)))) {
|
||||
log_error("compsoite filters allocation failed");
|
||||
dbg_free(filters_copy);
|
||||
return NULL;
|
||||
}
|
||||
filters[i] = NULL;
|
||||
va_end(ap);
|
||||
|
||||
cf->passes_filter = _and_p;
|
||||
cf->destroy = _destroy;
|
||||
cf->private = filters;
|
||||
cft->passes_filter = _and_p;
|
||||
cft->destroy = _destroy;
|
||||
cft->private = filters_copy;
|
||||
|
||||
return cf;
|
||||
return cft;
|
||||
}
|
||||
|
@@ -1,7 +1,16 @@
|
||||
/*
|
||||
* Copyright (C) 2001 Sistina Software (UK) Limited.
|
||||
* Copyright (C) 2001-2004 Sistina Software, Inc. All rights reserved.
|
||||
* Copyright (C) 2004 Red Hat, Inc. All rights reserved.
|
||||
*
|
||||
* This file is released under the GPL.
|
||||
* This file is part of LVM2.
|
||||
*
|
||||
* This copyrighted material is made available to anyone wishing to use,
|
||||
* modify, copy, or redistribute it subject to the terms and conditions
|
||||
* of the GNU General Public License v.2.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software Foundation,
|
||||
* Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
*/
|
||||
|
||||
#ifndef _LVM_FILTER_COMPOSITE_H
|
||||
@@ -9,6 +18,6 @@
|
||||
|
||||
#include "dev-cache.h"
|
||||
|
||||
struct dev_filter *composite_filter_create(int n, ...);
|
||||
struct dev_filter *composite_filter_create(int n, struct dev_filter **filters);
|
||||
|
||||
#endif
|
||||
|
98
lib/filters/filter-md.c
Normal file
98
lib/filters/filter-md.c
Normal file
@@ -0,0 +1,98 @@
|
||||
/*
|
||||
* Copyright (C) 2004 Luca Berra
|
||||
*
|
||||
* This file is part of LVM2.
|
||||
*
|
||||
* This copyrighted material is made available to anyone wishing to use,
|
||||
* modify, copy, or redistribute it subject to the terms and conditions
|
||||
* of the GNU Lesser General Public License v.2.1.
|
||||
*
|
||||
* You should have received a copy of the GNU Lesser General Public License
|
||||
* along with this program; if not, write to the Free Software Foundation,
|
||||
* Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
*/
|
||||
|
||||
#include "lib.h"
|
||||
#include "filter-md.h"
|
||||
#include "metadata.h"
|
||||
|
||||
#ifdef linux
|
||||
|
||||
/* Lifted from <linux/raid/md_p.h> because of difficulty including it */
|
||||
|
||||
#define MD_SB_MAGIC 0xa92b4efc
|
||||
#define MD_RESERVED_BYTES (64 * 1024)
|
||||
#define MD_RESERVED_SECTORS (MD_RESERVED_BYTES / 512)
|
||||
#define MD_NEW_SIZE_SECTORS(x) ((x & ~(MD_RESERVED_SECTORS - 1)) \
|
||||
- MD_RESERVED_SECTORS)
|
||||
|
||||
static int _ignore_md(struct dev_filter *f, struct device *dev)
|
||||
{
|
||||
uint64_t size, sector;
|
||||
uint32_t md_magic;
|
||||
|
||||
if (!dev_get_size(dev, &size)) {
|
||||
stack;
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (size < MD_RESERVED_SECTORS * 2)
|
||||
/*
|
||||
* We could ignore it since it is obviously too
|
||||
* small, but that's not our job.
|
||||
*/
|
||||
return 1;
|
||||
|
||||
if (!dev_open(dev)) {
|
||||
stack;
|
||||
return 0;
|
||||
}
|
||||
|
||||
sector = MD_NEW_SIZE_SECTORS(size);
|
||||
|
||||
/* Check if it is an md component device. */
|
||||
if (dev_read(dev, sector << SECTOR_SHIFT, sizeof(uint32_t), &md_magic)) {
|
||||
if (md_magic == MD_SB_MAGIC) {
|
||||
log_debug("%s: Skipping md component device",
|
||||
dev_name(dev));
|
||||
if (!dev_close(dev))
|
||||
stack;
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
|
||||
if (!dev_close(dev))
|
||||
stack;
|
||||
|
||||
return 1;
|
||||
}
|
||||
|
||||
static void _destroy(struct dev_filter *f)
|
||||
{
|
||||
dbg_free(f);
|
||||
}
|
||||
|
||||
struct dev_filter *md_filter_create(void)
|
||||
{
|
||||
struct dev_filter *f;
|
||||
|
||||
if (!(f = dbg_malloc(sizeof(*f)))) {
|
||||
log_error("md filter allocation failed");
|
||||
return NULL;
|
||||
}
|
||||
|
||||
f->passes_filter = _ignore_md;
|
||||
f->destroy = _destroy;
|
||||
f->private = NULL;
|
||||
|
||||
return f;
|
||||
}
|
||||
|
||||
#else
|
||||
|
||||
struct dev_filter *md_filter_create(void)
|
||||
{
|
||||
return NULL;
|
||||
}
|
||||
|
||||
#endif
|
23
lib/filters/filter-md.h
Normal file
23
lib/filters/filter-md.h
Normal file
@@ -0,0 +1,23 @@
|
||||
/*
|
||||
* Copyright (C) 2004 Luca Berra
|
||||
*
|
||||
* This file is part of LVM2.
|
||||
*
|
||||
* This copyrighted material is made available to anyone wishing to use,
|
||||
* modify, copy, or redistribute it subject to the terms and conditions
|
||||
* of the GNU Lesser General Public License v.2.1.
|
||||
*
|
||||
* You should have received a copy of the GNU Lesser General Public License
|
||||
* along with this program; if not, write to the Free Software Foundation,
|
||||
* Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
*/
|
||||
|
||||
#ifndef _LVM_FILTER_MD_H
|
||||
#define _LVM_FILTER_MD_H
|
||||
|
||||
#include "dev-cache.h"
|
||||
|
||||
struct dev_filter *md_filter_create(void);
|
||||
|
||||
#endif
|
||||
|
@@ -1,7 +1,16 @@
|
||||
/*
|
||||
* Copyright (C) 2001 Sistina Software (UK) Limited.
|
||||
* Copyright (C) 2001-2004 Sistina Software, Inc. All rights reserved.
|
||||
* Copyright (C) 2004 Red Hat, Inc. All rights reserved.
|
||||
*
|
||||
* This file is released under the LGPL.
|
||||
* This file is part of LVM2.
|
||||
*
|
||||
* This copyrighted material is made available to anyone wishing to use,
|
||||
* modify, copy, or redistribute it subject to the terms and conditions
|
||||
* of the GNU General Public License v.2.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software Foundation,
|
||||
* Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
*/
|
||||
|
||||
#include "lib.h"
|
||||
@@ -51,13 +60,13 @@ int persistent_filter_wipe(struct dev_filter *f)
|
||||
return 1;
|
||||
}
|
||||
|
||||
static int _read_array(struct pfilter *pf, struct config_tree *cf,
|
||||
static int _read_array(struct pfilter *pf, struct config_tree *cft,
|
||||
const char *path, void *data)
|
||||
{
|
||||
struct config_node *cn;
|
||||
const struct config_node *cn;
|
||||
struct config_value *cv;
|
||||
|
||||
if (!(cn = find_config_node(cf->root, path, '/'))) {
|
||||
if (!(cn = find_config_node(cft->root, path))) {
|
||||
log_very_verbose("Couldn't find %s array in '%s'",
|
||||
path, pf->file);
|
||||
return 0;
|
||||
@@ -88,22 +97,22 @@ int persistent_filter_load(struct dev_filter *f)
|
||||
struct pfilter *pf = (struct pfilter *) f->private;
|
||||
|
||||
int r = 0;
|
||||
struct config_tree *cf;
|
||||
struct config_tree *cft;
|
||||
|
||||
if (!(cf = create_config_tree())) {
|
||||
if (!(cft = create_config_tree(pf->file))) {
|
||||
stack;
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (!read_config_file(cf, pf->file)) {
|
||||
if (!read_config_file(cft)) {
|
||||
stack;
|
||||
goto out;
|
||||
}
|
||||
|
||||
_read_array(pf, cf, "persistent_filter_cache/valid_devices",
|
||||
_read_array(pf, cft, "persistent_filter_cache/valid_devices",
|
||||
PF_GOOD_DEVICE);
|
||||
/* We don't gain anything by holding invalid devices */
|
||||
/* _read_array(pf, cf, "persistent_filter_cache/invalid_devices",
|
||||
/* _read_array(pf, cft, "persistent_filter_cache/invalid_devices",
|
||||
PF_BAD_DEVICE); */
|
||||
|
||||
/* Did we find anything? */
|
||||
@@ -116,7 +125,7 @@ int persistent_filter_load(struct dev_filter *f)
|
||||
log_very_verbose("Loaded persistent filter cache from %s", pf->file);
|
||||
|
||||
out:
|
||||
destroy_config_tree(cf);
|
||||
destroy_config_tree(cft);
|
||||
return r;
|
||||
}
|
||||
|
||||
|
@@ -1,7 +1,16 @@
|
||||
/*
|
||||
* Copyright (C) 2001 Sistina Software (UK) Limited.
|
||||
* Copyright (C) 2001-2004 Sistina Software, Inc. All rights reserved.
|
||||
* Copyright (C) 2004 Red Hat, Inc. All rights reserved.
|
||||
*
|
||||
* This file is released under the GPL.
|
||||
* This file is part of LVM2.
|
||||
*
|
||||
* This copyrighted material is made available to anyone wishing to use,
|
||||
* modify, copy, or redistribute it subject to the terms and conditions
|
||||
* of the GNU General Public License v.2.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software Foundation,
|
||||
* Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
*/
|
||||
|
||||
#ifndef _LVM_FILTER_PERSISTENT_H
|
||||
|
@@ -1,7 +1,16 @@
|
||||
/*
|
||||
* Copyright (C) 2001 Sistina Software (UK) Limited.
|
||||
* Copyright (C) 2001-2004 Sistina Software, Inc. All rights reserved.
|
||||
* Copyright (C) 2004 Red Hat, Inc. All rights reserved.
|
||||
*
|
||||
* This file is released under the LGPL.
|
||||
* This file is part of LVM2.
|
||||
*
|
||||
* This copyrighted material is made available to anyone wishing to use,
|
||||
* modify, copy, or redistribute it subject to the terms and conditions
|
||||
* of the GNU General Public License v.2.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software Foundation,
|
||||
* Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
*/
|
||||
|
||||
#include "lib.h"
|
||||
@@ -42,7 +51,7 @@ static int _extract_pattern(struct pool *mem, const char *pat,
|
||||
pat++;
|
||||
|
||||
/*
|
||||
* get the seperator
|
||||
* get the separator
|
||||
*/
|
||||
switch (*pat) {
|
||||
case '(':
|
||||
@@ -75,7 +84,7 @@ static int _extract_pattern(struct pool *mem, const char *pat,
|
||||
*/
|
||||
ptr = r + strlen(r) - 1;
|
||||
if (*ptr != sep) {
|
||||
log_info("invalid seperator at end of regex");
|
||||
log_info("invalid separator at end of regex");
|
||||
return 0;
|
||||
}
|
||||
*ptr = '\0';
|
||||
|
@@ -1,7 +1,16 @@
|
||||
/*
|
||||
* Copyright (C) 2001 Sistina Software (UK) Limited.
|
||||
* Copyright (C) 2001-2004 Sistina Software, Inc. All rights reserved.
|
||||
* Copyright (C) 2004 Red Hat, Inc. All rights reserved.
|
||||
*
|
||||
* This file is released under the GPL.
|
||||
* This file is part of LVM2.
|
||||
*
|
||||
* This copyrighted material is made available to anyone wishing to use,
|
||||
* modify, copy, or redistribute it subject to the terms and conditions
|
||||
* of the GNU General Public License v.2.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software Foundation,
|
||||
* Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
*/
|
||||
|
||||
#ifndef _LVM_FILTER_REGEX_H
|
||||
|
288
lib/filters/filter-sysfs.c
Normal file
288
lib/filters/filter-sysfs.c
Normal file
@@ -0,0 +1,288 @@
|
||||
/*
|
||||
* Copyright (C) 2004 Red Hat, Inc. All rights reserved.
|
||||
*
|
||||
* This file is part of LVM2.
|
||||
*
|
||||
* This copyrighted material is made available to anyone wishing to use,
|
||||
* modify, copy, or redistribute it subject to the terms and conditions
|
||||
* of the GNU General Public License v.2.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software Foundation,
|
||||
* Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
*/
|
||||
|
||||
#include "lib.h"
|
||||
#include "filter-sysfs.h"
|
||||
#include "lvm-string.h"
|
||||
#include "pool.h"
|
||||
|
||||
#ifdef linux
|
||||
|
||||
#include <dirent.h>
|
||||
|
||||
static int _locate_sysfs_blocks(const char *proc, char *path, size_t len)
|
||||
{
|
||||
char proc_mounts[PATH_MAX];
|
||||
int r = 0;
|
||||
FILE *fp;
|
||||
char *split[4], buffer[PATH_MAX + 16];
|
||||
|
||||
if (!*proc) {
|
||||
log_verbose("No proc filesystem found: skipping sysfs filter");
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (lvm_snprintf(proc_mounts, sizeof(proc_mounts),
|
||||
"%s/mounts", proc) < 0) {
|
||||
log_error("Failed to create /proc/mounts string");
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (!(fp = fopen(proc_mounts, "r"))) {
|
||||
log_sys_error("fopen %s", proc_mounts);
|
||||
return 0;
|
||||
}
|
||||
|
||||
while (fgets(buffer, sizeof(buffer), fp)) {
|
||||
if (split_words(buffer, 4, split) == 4 &&
|
||||
!strcmp(split[2], "sysfs")) {
|
||||
if (lvm_snprintf(path, len, "%s/%s", split[1],
|
||||
"block") >= 0) {
|
||||
r = 1;
|
||||
}
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
fclose(fp);
|
||||
return r;
|
||||
}
|
||||
|
||||
/*----------------------------------------------------------------
|
||||
* We need to store a set of dev_t.
|
||||
*--------------------------------------------------------------*/
|
||||
struct entry {
|
||||
struct entry *next;
|
||||
dev_t dev;
|
||||
};
|
||||
|
||||
#define SET_BUCKETS 64
|
||||
struct dev_set {
|
||||
struct pool *mem;
|
||||
const char *sys_block;
|
||||
int initialised;
|
||||
struct entry *slots[SET_BUCKETS];
|
||||
};
|
||||
|
||||
static struct dev_set *_dev_set_create(struct pool *mem, const char *sys_block)
|
||||
{
|
||||
struct dev_set *ds;
|
||||
|
||||
if (!(ds = pool_zalloc(mem, sizeof(*ds))))
|
||||
return NULL;
|
||||
|
||||
ds->mem = mem;
|
||||
ds->sys_block = pool_strdup(mem, sys_block);
|
||||
ds->initialised = 0;
|
||||
|
||||
return ds;
|
||||
}
|
||||
|
||||
static inline unsigned _hash_dev(dev_t dev)
|
||||
{
|
||||
return (major(dev) ^ minor(dev)) & (SET_BUCKETS - 1);
|
||||
}
|
||||
|
||||
/*
|
||||
* Doesn't check that the set already contains dev.
|
||||
*/
|
||||
static int _set_insert(struct dev_set *ds, dev_t dev)
|
||||
{
|
||||
struct entry *e;
|
||||
unsigned h = _hash_dev(dev);
|
||||
|
||||
if (!(e = pool_alloc(ds->mem, sizeof(*e))))
|
||||
return 0;
|
||||
|
||||
e->next = ds->slots[h];
|
||||
e->dev = dev;
|
||||
ds->slots[h] = e;
|
||||
|
||||
return 1;
|
||||
}
|
||||
|
||||
static int _set_lookup(struct dev_set *ds, dev_t dev)
|
||||
{
|
||||
unsigned h = _hash_dev(dev);
|
||||
struct entry *e;
|
||||
|
||||
for (e = ds->slots[h]; e; e = e->next)
|
||||
if (e->dev == dev)
|
||||
return 1;
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/*----------------------------------------------------------------
|
||||
* filter methods
|
||||
*--------------------------------------------------------------*/
|
||||
static int _parse_dev(const char *file, FILE *fp, dev_t *result)
|
||||
{
|
||||
unsigned major, minor;
|
||||
char buffer[64];
|
||||
|
||||
if (!fgets(buffer, sizeof(buffer), fp)) {
|
||||
log_error("Empty sysfs device file: %s", file);
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (sscanf(buffer, "%u:%u", &major, &minor) != 2) {
|
||||
log_info("sysfs device file not correct format");
|
||||
return 0;
|
||||
}
|
||||
|
||||
*result = makedev(major, minor);
|
||||
return 1;
|
||||
}
|
||||
|
||||
static int _read_dev(const char *file, dev_t *result)
|
||||
{
|
||||
int r;
|
||||
FILE *fp;
|
||||
|
||||
if (!(fp = fopen(file, "r"))) {
|
||||
log_sys_error("fopen", file);
|
||||
return 0;
|
||||
}
|
||||
|
||||
r = _parse_dev(file, fp, result);
|
||||
fclose(fp);
|
||||
|
||||
return r;
|
||||
}
|
||||
|
||||
/*
|
||||
* Recurse through sysfs directories, inserting any devs found.
|
||||
*/
|
||||
static int _read_devs(struct dev_set *ds, const char *dir)
|
||||
{
|
||||
struct dirent *d;
|
||||
DIR *dr;
|
||||
char path[PATH_MAX];
|
||||
dev_t dev;
|
||||
int r = 1;
|
||||
|
||||
if (!(dr = opendir(dir))) {
|
||||
log_sys_error("opendir", dir);
|
||||
return 0;
|
||||
}
|
||||
|
||||
while ((d = readdir(dr))) {
|
||||
if (!strcmp(d->d_name, ".") || !strcmp(d->d_name, ".."))
|
||||
continue;
|
||||
|
||||
if (lvm_snprintf(path, sizeof(path), "%s/%s", dir,
|
||||
d->d_name) < 0) {
|
||||
log_error("sysfs path name too long: %s in %s",
|
||||
d->d_name, dir);
|
||||
continue;
|
||||
}
|
||||
|
||||
if (d->d_type == DT_DIR) {
|
||||
if (!_read_devs(ds, path)) {
|
||||
r = 0;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
if ((d->d_type == DT_REG && !strcmp(d->d_name, "dev")))
|
||||
if (!_read_dev(path, &dev) || !_set_insert(ds, dev)) {
|
||||
r = 0;
|
||||
break;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
if (closedir(dr))
|
||||
log_sys_error("closedir", dir);
|
||||
|
||||
return r;
|
||||
}
|
||||
|
||||
static int _init_devs(struct dev_set *ds)
|
||||
{
|
||||
if (!_read_devs(ds, ds->sys_block)) {
|
||||
ds->initialised = -1;
|
||||
return 0;
|
||||
}
|
||||
|
||||
ds->initialised = 1;
|
||||
|
||||
return 1;
|
||||
}
|
||||
|
||||
|
||||
static int _accept_p(struct dev_filter *f, struct device *dev)
|
||||
{
|
||||
struct dev_set *ds = (struct dev_set *) f->private;
|
||||
|
||||
if (!ds->initialised)
|
||||
_init_devs(ds);
|
||||
|
||||
/* Pass through if initialisation failed */
|
||||
if (ds->initialised != 1)
|
||||
return 1;
|
||||
|
||||
return _set_lookup(ds, dev->dev);
|
||||
}
|
||||
|
||||
static void _destroy(struct dev_filter *f)
|
||||
{
|
||||
struct dev_set *ds = (struct dev_set *) f->private;
|
||||
pool_destroy(ds->mem);
|
||||
}
|
||||
|
||||
struct dev_filter *sysfs_filter_create(const char *proc)
|
||||
{
|
||||
char sys_block[PATH_MAX];
|
||||
struct pool *mem;
|
||||
struct dev_set *ds;
|
||||
struct dev_filter *f;
|
||||
|
||||
if (!_locate_sysfs_blocks(proc, sys_block, sizeof(sys_block)))
|
||||
return NULL;
|
||||
|
||||
if (!(mem = pool_create(256))) {
|
||||
log_error("sysfs pool creation failed");
|
||||
return NULL;
|
||||
}
|
||||
|
||||
if (!(ds = _dev_set_create(mem, sys_block))) {
|
||||
log_error("sysfs dev_set creation failed");
|
||||
goto bad;
|
||||
}
|
||||
|
||||
if (!(f = pool_zalloc(mem, sizeof(*f)))) {
|
||||
stack;
|
||||
goto bad;
|
||||
}
|
||||
|
||||
f->passes_filter = _accept_p;
|
||||
f->destroy = _destroy;
|
||||
f->private = ds;
|
||||
return f;
|
||||
|
||||
bad:
|
||||
pool_destroy(mem);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
#else
|
||||
|
||||
struct dev_filter *sysfs_filter_create(const char *proc)
|
||||
{
|
||||
return NULL;
|
||||
}
|
||||
|
||||
#endif
|
23
lib/filters/filter-sysfs.h
Normal file
23
lib/filters/filter-sysfs.h
Normal file
@@ -0,0 +1,23 @@
|
||||
/*
|
||||
* Copyright (C) 2004 Red Hat, Inc. All rights reserved.
|
||||
*
|
||||
* This file is part of LVM2.
|
||||
*
|
||||
* This copyrighted material is made available to anyone wishing to use,
|
||||
* modify, copy, or redistribute it subject to the terms and conditions
|
||||
* of the GNU General Public License v.2.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software Foundation,
|
||||
* Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
*/
|
||||
|
||||
#ifndef _LVM_FILTER_SYSFS_H
|
||||
#define _LVM_FILTER_SYSFS_H
|
||||
|
||||
#include "config.h"
|
||||
#include "dev-cache.h"
|
||||
|
||||
struct dev_filter *sysfs_filter_create(const char *proc);
|
||||
|
||||
#endif
|
@@ -1,21 +1,16 @@
|
||||
/*
|
||||
* Copyright (C) 2001 Sistina Software
|
||||
* Copyright (C) 2001-2004 Sistina Software, Inc. All rights reserved.
|
||||
* Copyright (C) 2004 Red Hat, Inc. All rights reserved.
|
||||
*
|
||||
* lvm is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation; either version 2, or (at your option)
|
||||
* any later version.
|
||||
* This file is part of LVM2.
|
||||
*
|
||||
* lvm is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
* This copyrighted material is made available to anyone wishing to use,
|
||||
* modify, copy, or redistribute it subject to the terms and conditions
|
||||
* of the GNU General Public License v.2.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with GNU CC; see the file COPYING. If not, write to
|
||||
* the Free Software Foundation, 59 Temple Place - Suite 330,
|
||||
* Boston, MA 02111-1307, USA.
|
||||
*
|
||||
* along with this program; if not, write to the Free Software Foundation,
|
||||
* Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
*/
|
||||
|
||||
#include "lib.h"
|
||||
@@ -58,6 +53,8 @@ static const device_info_t device_info[] = {
|
||||
{"ubd", 16}, /* User-mode virtual block device */
|
||||
{"ataraid", 16}, /* ATA Raid */
|
||||
{"drbd", 16}, /* Distributed Replicated Block Device */
|
||||
{"power2", 16}, /* EMC Powerpath */
|
||||
{"i2o_block", 16}, /* i2o Block Disk */
|
||||
{NULL, 0}
|
||||
};
|
||||
|
||||
@@ -86,7 +83,7 @@ static int _passes_lvm_type_device_filter(struct dev_filter *f,
|
||||
return 1;
|
||||
}
|
||||
|
||||
static int *_scan_proc_dev(const char *proc, struct config_node *cn)
|
||||
static int *_scan_proc_dev(const char *proc, const struct config_node *cn)
|
||||
{
|
||||
char line[80];
|
||||
char proc_devices[PATH_MAX];
|
||||
@@ -203,7 +200,7 @@ static int *_scan_proc_dev(const char *proc, struct config_node *cn)
|
||||
}
|
||||
|
||||
struct dev_filter *lvm_type_filter_create(const char *proc,
|
||||
struct config_node *cn)
|
||||
const struct config_node *cn)
|
||||
{
|
||||
struct dev_filter *f;
|
||||
|
||||
|
@@ -1,21 +1,16 @@
|
||||
/*
|
||||
* Copyright (C) 2001 Sistina Software
|
||||
* Copyright (C) 2001-2004 Sistina Software, Inc. All rights reserved.
|
||||
* Copyright (C) 2004 Red Hat, Inc. All rights reserved.
|
||||
*
|
||||
* lvm is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation; either version 2, or (at your option)
|
||||
* any later version.
|
||||
* This file is part of LVM2.
|
||||
*
|
||||
* lvm is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
* This copyrighted material is made available to anyone wishing to use,
|
||||
* modify, copy, or redistribute it subject to the terms and conditions
|
||||
* of the GNU General Public License v.2.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with GNU CC; see the file COPYING. If not, write to
|
||||
* the Free Software Foundation, 59 Temple Place - Suite 330,
|
||||
* Boston, MA 02111-1307, USA.
|
||||
*
|
||||
* along with this program; if not, write to the Free Software Foundation,
|
||||
* Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
*/
|
||||
|
||||
#ifndef _LVM_FILTER_H
|
||||
@@ -34,7 +29,7 @@
|
||||
#endif
|
||||
|
||||
struct dev_filter *lvm_type_filter_create(const char *proc,
|
||||
struct config_node *cn);
|
||||
const struct config_node *cn);
|
||||
|
||||
void lvm_type_filter_destroy(struct dev_filter *f);
|
||||
|
||||
|
@@ -1,7 +0,0 @@
|
||||
Base {
|
||||
global:
|
||||
init_format;
|
||||
local:
|
||||
*;
|
||||
};
|
||||
|
1
lib/format1/.exported_symbols
Normal file
1
lib/format1/.exported_symbols
Normal file
@@ -0,0 +1 @@
|
||||
init_format
|
@@ -1,14 +1,22 @@
|
||||
#
|
||||
# Copyright (C) 2002 Sistina Software (UK) Limited.
|
||||
# Copyright (C) 2002-2004 Sistina Software, Inc. All rights reserved.
|
||||
# Copyright (C) 2004 Red Hat, Inc. All rights reserved.
|
||||
#
|
||||
# This file is released under the LGPL.
|
||||
# This file is part of the LVM2.
|
||||
#
|
||||
# This copyrighted material is made available to anyone wishing to use,
|
||||
# modify, copy, or redistribute it subject to the terms and conditions
|
||||
# of the GNU General Public License v.2.
|
||||
#
|
||||
# You should have received a copy of the GNU General Public License
|
||||
# along with this program; if not, write to the Free Software Foundation,
|
||||
# Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
|
||||
srcdir = @srcdir@
|
||||
top_srcdir = @top_srcdir@
|
||||
VPATH = @srcdir@
|
||||
|
||||
SOURCES=\
|
||||
SOURCES =\
|
||||
disk-rep.c \
|
||||
format1.c \
|
||||
import-export.c \
|
||||
@@ -17,15 +25,14 @@ SOURCES=\
|
||||
lvm1-label.c \
|
||||
vg_number.c
|
||||
|
||||
TARGETS=liblvm2format1.so
|
||||
LIB_SHARED = liblvm2format1.so
|
||||
|
||||
include ../../make.tmpl
|
||||
|
||||
.PHONY: install
|
||||
|
||||
install: liblvm2format1.so
|
||||
$(INSTALL) -D -o $(OWNER) -g $(GROUP) -m 555 $(STRIP) $< \
|
||||
$(INSTALL) -D $(OWNER) $(GROUP) -m 555 $(STRIP) $< \
|
||||
$(libdir)/liblvm2format1.so.$(LIB_VERSION)
|
||||
$(LN_S) -f liblvm2format1.so.$(LIB_VERSION) $(libdir)/liblvm2format1.so
|
||||
|
||||
.PHONY: install
|
||||
|
||||
|
@@ -1,7 +1,16 @@
|
||||
/*
|
||||
* Copyright (C) 2001 Sistina Software (UK) Limited.
|
||||
* Copyright (C) 2001-2004 Sistina Software, Inc. All rights reserved.
|
||||
* Copyright (C) 2004 Red Hat, Inc. All rights reserved.
|
||||
*
|
||||
* This file is released under the LGPL.
|
||||
* This file is part of LVM2.
|
||||
*
|
||||
* This copyrighted material is made available to anyone wishing to use,
|
||||
* modify, copy, or redistribute it subject to the terms and conditions
|
||||
* of the GNU General Public License v.2.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software Foundation,
|
||||
* Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
*/
|
||||
|
||||
#include "lib.h"
|
||||
@@ -108,6 +117,7 @@ static void _xlate_extents(struct pe_disk *extents, uint32_t count)
|
||||
static int _munge_formats(struct pv_disk *pvd)
|
||||
{
|
||||
uint32_t pe_start;
|
||||
int b, e;
|
||||
|
||||
switch (pvd->version) {
|
||||
case 1:
|
||||
@@ -125,17 +135,54 @@ static int _munge_formats(struct pv_disk *pvd)
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* UUID too long? */
|
||||
if (pvd->pv_uuid[ID_LEN]) {
|
||||
/* Retain ID_LEN chars from end */
|
||||
for (e = ID_LEN; e < sizeof(pvd->pv_uuid); e++) {
|
||||
if (!pvd->pv_uuid[e]) {
|
||||
e--;
|
||||
break;
|
||||
}
|
||||
}
|
||||
for (b = 0; b < ID_LEN; b++) {
|
||||
pvd->pv_uuid[b] = pvd->pv_uuid[++e - ID_LEN];
|
||||
/* FIXME Remove all invalid chars */
|
||||
if (pvd->pv_uuid[b] == '/')
|
||||
pvd->pv_uuid[b] = '#';
|
||||
}
|
||||
memset(&pvd->pv_uuid[ID_LEN], 0, sizeof(pvd->pv_uuid) - ID_LEN);
|
||||
}
|
||||
|
||||
/* If UUID is missing, create one */
|
||||
if (pvd->pv_uuid[0] == '\0')
|
||||
uuid_from_num(pvd->pv_uuid, pvd->pv_number);
|
||||
|
||||
return 1;
|
||||
}
|
||||
|
||||
static int _read_pvd(struct device *dev, struct pv_disk *pvd)
|
||||
/*
|
||||
* If exported, remove "PV_EXP" from end of VG name
|
||||
*/
|
||||
static void _munge_exported_vg(struct pv_disk *pvd)
|
||||
{
|
||||
if (!dev_read(dev, UINT64_C(0), sizeof(*pvd), pvd)) {
|
||||
log_very_verbose("Failed to read PV data from %s",
|
||||
dev_name(dev));
|
||||
return 0;
|
||||
}
|
||||
int l;
|
||||
size_t s;
|
||||
|
||||
/* Return if PV not in a VG */
|
||||
if ((!*pvd->vg_name))
|
||||
return;
|
||||
/* FIXME also check vgd->status & VG_EXPORTED? */
|
||||
|
||||
l = strlen(pvd->vg_name);
|
||||
s = sizeof(EXPORTED_TAG);
|
||||
if (!strncmp(pvd->vg_name + l - s + 1, EXPORTED_TAG, s)) {
|
||||
pvd->vg_name[l - s + 1] = '\0';
|
||||
pvd->pv_status |= VG_EXPORTED;
|
||||
}
|
||||
}
|
||||
|
||||
int munge_pvd(struct device *dev, struct pv_disk *pvd)
|
||||
{
|
||||
_xlate_pvd(pvd);
|
||||
|
||||
if (pvd->id[0] != 'H' || pvd->id[1] != 'M') {
|
||||
@@ -150,9 +197,23 @@ static int _read_pvd(struct device *dev, struct pv_disk *pvd)
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* If VG is exported, set VG name back to the real name */
|
||||
_munge_exported_vg(pvd);
|
||||
|
||||
return 1;
|
||||
}
|
||||
|
||||
static int _read_pvd(struct device *dev, struct pv_disk *pvd)
|
||||
{
|
||||
if (!dev_read(dev, UINT64_C(0), sizeof(*pvd), pvd)) {
|
||||
log_very_verbose("Failed to read PV data from %s",
|
||||
dev_name(dev));
|
||||
return 0;
|
||||
}
|
||||
|
||||
return munge_pvd(dev, pvd);
|
||||
}
|
||||
|
||||
static int _read_lvd(struct device *dev, uint64_t pos, struct lv_disk *disk)
|
||||
{
|
||||
if (!dev_read(dev, pos, sizeof(*disk), disk))
|
||||
@@ -172,6 +233,13 @@ static int _read_vgd(struct disk_list *data)
|
||||
|
||||
_xlate_vgd(vgd);
|
||||
|
||||
if ((vgd->lv_max > MAX_LV) || (vgd->pv_max > MAX_PV))
|
||||
fail;
|
||||
|
||||
/* If UUID is missing, create one */
|
||||
if (vgd->vg_uuid[0] == '\0')
|
||||
uuid_from_num(vgd->vg_uuid, vgd->vg_number);
|
||||
|
||||
return 1;
|
||||
}
|
||||
|
||||
@@ -252,26 +320,6 @@ static int _read_extents(struct disk_list *data)
|
||||
return 1;
|
||||
}
|
||||
|
||||
/*
|
||||
* If exported, remove "PV_EXP" from end of VG name
|
||||
*/
|
||||
void munge_exported_vg(struct pv_disk *pvd)
|
||||
{
|
||||
int l;
|
||||
size_t s;
|
||||
|
||||
/* Return if PV not in a VG */
|
||||
if ((!*pvd->vg_name))
|
||||
return;
|
||||
|
||||
l = strlen(pvd->vg_name);
|
||||
s = sizeof(EXPORTED_TAG);
|
||||
if (!strncmp(pvd->vg_name + l - s + 1, EXPORTED_TAG, s)) {
|
||||
pvd->vg_name[l - s + 1] = '\0';
|
||||
pvd->pv_status |= VG_EXPORTED;
|
||||
}
|
||||
}
|
||||
|
||||
static struct disk_list *__read_disk(const struct format_type *fmt,
|
||||
struct device *dev, struct pool *mem,
|
||||
const char *vg_name)
|
||||
@@ -295,9 +343,6 @@ static struct disk_list *__read_disk(const struct format_type *fmt,
|
||||
goto bad;
|
||||
}
|
||||
|
||||
/* If VG is exported, set VG name back to the real name */
|
||||
munge_exported_vg(&dl->pvd);
|
||||
|
||||
if (!(info = lvmcache_add(fmt->labeller, dl->pvd.pv_uuid, dev,
|
||||
dl->pvd.vg_name, NULL)))
|
||||
stack;
|
||||
|
@@ -1,7 +1,16 @@
|
||||
/*
|
||||
* Copyright (C) 2001 Sistina Software (UK) Limited.
|
||||
* Copyright (C) 2001-2004 Sistina Software, Inc. All rights reserved.
|
||||
* Copyright (C) 2004 Red Hat, Inc. All rights reserved.
|
||||
*
|
||||
* This file is released under the GPL.
|
||||
* This file is part of LVM2.
|
||||
*
|
||||
* This copyrighted material is made available to anyone wishing to use,
|
||||
* modify, copy, or redistribute it subject to the terms and conditions
|
||||
* of the GNU General Public License v.2.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software Foundation,
|
||||
* Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
*/
|
||||
|
||||
#ifndef DISK_REP_FORMAT1_H
|
||||
@@ -10,6 +19,7 @@
|
||||
#include "lvm-types.h"
|
||||
#include "metadata.h"
|
||||
#include "pool.h"
|
||||
#include "toolcontext.h"
|
||||
|
||||
#define MAX_PV 256
|
||||
#define MAX_LV 256
|
||||
@@ -173,7 +183,7 @@ struct disk_list {
|
||||
*/
|
||||
int calculate_layout(struct disk_list *dl);
|
||||
int calculate_extent_count(struct physical_volume *pv, uint32_t extent_size,
|
||||
uint32_t max_extent_count);
|
||||
uint32_t max_extent_count, uint64_t pe_start);
|
||||
|
||||
/*
|
||||
* Low level io routines which read/write
|
||||
@@ -196,7 +206,8 @@ int write_disks(const struct format_type *fmt, struct list *pvds);
|
||||
int import_pv(struct pool *mem, struct device *dev,
|
||||
struct volume_group *vg,
|
||||
struct physical_volume *pv, struct pv_disk *pvd);
|
||||
int export_pv(struct pool *mem, struct volume_group *vg,
|
||||
int export_pv(struct cmd_context *cmd, struct pool *mem,
|
||||
struct volume_group *vg,
|
||||
struct pv_disk *pvd, struct physical_volume *pv);
|
||||
|
||||
int import_vg(struct pool *mem,
|
||||
@@ -205,7 +216,7 @@ int export_vg(struct vg_disk *vgd, struct volume_group *vg);
|
||||
|
||||
int import_lv(struct pool *mem, struct logical_volume *lv, struct lv_disk *lvd);
|
||||
|
||||
int import_extents(struct pool *mem, struct volume_group *vg,
|
||||
int import_extents(struct cmd_context *cmd, struct volume_group *vg,
|
||||
struct list *pvds);
|
||||
int export_extents(struct disk_list *dl, uint32_t lv_num,
|
||||
struct logical_volume *lv, struct physical_volume *pv);
|
||||
@@ -226,7 +237,7 @@ int export_uuids(struct disk_list *dl, struct volume_group *vg);
|
||||
void export_numbers(struct list *pvds, struct volume_group *vg);
|
||||
|
||||
void export_pv_act(struct list *pvds);
|
||||
void munge_exported_vg(struct pv_disk *pvd);
|
||||
int munge_pvd(struct device *dev, struct pv_disk *pvd);
|
||||
|
||||
/* blech */
|
||||
int get_free_vg_number(struct format_instance *fid, struct dev_filter *filter,
|
||||
|
@@ -1,7 +1,16 @@
|
||||
/*
|
||||
* Copyright (C) 2001 Sistina Software (UK) Limited.
|
||||
* Copyright (C) 2001-2004 Sistina Software, Inc. All rights reserved.
|
||||
* Copyright (C) 2004 Red Hat, Inc. All rights reserved.
|
||||
*
|
||||
* This file is released under the LGPL.
|
||||
* This file is part of LVM2.
|
||||
*
|
||||
* This copyrighted material is made available to anyone wishing to use,
|
||||
* modify, copy, or redistribute it subject to the terms and conditions
|
||||
* of the GNU General Public License v.2.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software Foundation,
|
||||
* Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
*/
|
||||
|
||||
#include "lib.h"
|
||||
@@ -66,6 +75,35 @@ static int _check_vgs(struct list *pvs, int *partial)
|
||||
else if (memcmp(&first->vgd, &dl->vgd, sizeof(first->vgd))) {
|
||||
log_error("VG data differs between PVs %s and %s",
|
||||
dev_name(first->dev), dev_name(dl->dev));
|
||||
log_debug("VG data on %s: %s %s %" PRIu32 " %" PRIu32
|
||||
" %" PRIu32 " %" PRIu32 " %" PRIu32 " %"
|
||||
PRIu32 " %" PRIu32 " %" PRIu32 " %" PRIu32
|
||||
" %" PRIu32 " %" PRIu32 " %" PRIu32 " %"
|
||||
PRIu32 " %" PRIu32 " %" PRIu32,
|
||||
dev_name(first->dev), first->vgd.vg_uuid,
|
||||
first->vgd.vg_name_dummy,
|
||||
first->vgd.vg_number, first->vgd.vg_access,
|
||||
first->vgd.vg_status, first->vgd.lv_max,
|
||||
first->vgd.lv_cur, first->vgd.lv_open,
|
||||
first->vgd.pv_max, first->vgd.pv_cur,
|
||||
first->vgd.pv_act, first->vgd.dummy,
|
||||
first->vgd.vgda, first->vgd.pe_size,
|
||||
first->vgd.pe_total, first->vgd.pe_allocated,
|
||||
first->vgd.pvg_total);
|
||||
log_debug("VG data on %s: %s %s %" PRIu32 " %" PRIu32
|
||||
" %" PRIu32 " %" PRIu32 " %" PRIu32 " %"
|
||||
PRIu32 " %" PRIu32 " %" PRIu32 " %" PRIu32
|
||||
" %" PRIu32 " %" PRIu32 " %" PRIu32 " %"
|
||||
PRIu32 " %" PRIu32 " %" PRIu32,
|
||||
dev_name(dl->dev), dl->vgd.vg_uuid,
|
||||
dl->vgd.vg_name_dummy, dl->vgd.vg_number,
|
||||
dl->vgd.vg_access, dl->vgd.vg_status,
|
||||
dl->vgd.lv_max, dl->vgd.lv_cur,
|
||||
dl->vgd.lv_open, dl->vgd.pv_max,
|
||||
dl->vgd.pv_cur, dl->vgd.pv_act, dl->vgd.dummy,
|
||||
dl->vgd.vgda, dl->vgd.pe_size,
|
||||
dl->vgd.pe_total, dl->vgd.pe_allocated,
|
||||
dl->vgd.pvg_total);
|
||||
list_del(pvh);
|
||||
if (partial_mode()) {
|
||||
*partial = 1;
|
||||
@@ -110,6 +148,7 @@ static struct volume_group *_build_vg(struct format_instance *fid,
|
||||
list_init(&vg->pvs);
|
||||
list_init(&vg->lvs);
|
||||
list_init(&vg->snapshots);
|
||||
list_init(&vg->tags);
|
||||
|
||||
if (!_check_vgs(pvs, &partial))
|
||||
goto bad;
|
||||
@@ -125,7 +164,7 @@ static struct volume_group *_build_vg(struct format_instance *fid,
|
||||
if (!import_lvs(mem, vg, pvs))
|
||||
goto bad;
|
||||
|
||||
if (!import_extents(mem, vg, pvs))
|
||||
if (!import_extents(fid->fmt->cmd, vg, pvs))
|
||||
goto bad;
|
||||
|
||||
if (!import_snapshots(mem, vg, pvs))
|
||||
@@ -172,7 +211,8 @@ static struct volume_group *_vg_read(struct format_instance *fid,
|
||||
return vg;
|
||||
}
|
||||
|
||||
static struct disk_list *_flatten_pv(struct pool *mem, struct volume_group *vg,
|
||||
static struct disk_list *_flatten_pv(struct format_instance *fid,
|
||||
struct pool *mem, struct volume_group *vg,
|
||||
struct physical_volume *pv,
|
||||
const char *dev_dir)
|
||||
{
|
||||
@@ -189,7 +229,7 @@ static struct disk_list *_flatten_pv(struct pool *mem, struct volume_group *vg,
|
||||
list_init(&dl->uuids);
|
||||
list_init(&dl->lvds);
|
||||
|
||||
if (!export_pv(mem, vg, &dl->pvd, pv) ||
|
||||
if (!export_pv(fid->fmt->cmd, mem, vg, &dl->pvd, pv) ||
|
||||
!export_vg(&dl->vgd, vg) ||
|
||||
!export_uuids(dl, vg) ||
|
||||
!export_lvs(dl, vg, pv, dev_dir) || !calculate_layout(dl)) {
|
||||
@@ -213,7 +253,7 @@ static int _flatten_vg(struct format_instance *fid, struct pool *mem,
|
||||
list_iterate(pvh, &vg->pvs) {
|
||||
pvl = list_item(pvh, struct pv_list);
|
||||
|
||||
if (!(data = _flatten_pv(mem, vg, pvl->pv, dev_dir))) {
|
||||
if (!(data = _flatten_pv(fid, mem, vg, pvl->pv, dev_dir))) {
|
||||
stack;
|
||||
return 0;
|
||||
}
|
||||
@@ -305,7 +345,7 @@ static int _pv_setup(const struct format_type *fmt,
|
||||
pv->size--;
|
||||
if (pv->size > MAX_PV_SIZE) {
|
||||
log_error("Physical volumes cannot be bigger than %s",
|
||||
display_size(fmt->cmd, (uint64_t) MAX_PV_SIZE / 2,
|
||||
display_size(fmt->cmd, (uint64_t) MAX_PV_SIZE,
|
||||
SIZE_SHORT));
|
||||
return 0;
|
||||
}
|
||||
@@ -317,14 +357,12 @@ static int _pv_setup(const struct format_type *fmt,
|
||||
/*
|
||||
* This works out pe_start and pe_count.
|
||||
*/
|
||||
if (!calculate_extent_count(pv, extent_size, extent_count)) {
|
||||
if (!calculate_extent_count(pv, extent_size, extent_count, pe_start)) {
|
||||
stack;
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* Retain existing extent locations exactly */
|
||||
/* FIXME Relax this so a non-overlapping existing pe_start can also
|
||||
* be used in place of the calculated one */
|
||||
if (((pe_start || extent_count) && (pe_start != pv->pe_start)) ||
|
||||
(extent_count && (extent_count != pv->pe_count))) {
|
||||
log_error("Metadata would overwrite physical extents");
|
||||
@@ -348,7 +386,7 @@ static int _lv_setup(struct format_instance *fid, struct logical_volume *lv)
|
||||
}
|
||||
if (lv->size > max_size) {
|
||||
log_error("logical volumes cannot be larger than %s",
|
||||
display_size(fid->fmt->cmd, max_size / 2,
|
||||
display_size(fid->fmt->cmd, max_size,
|
||||
SIZE_SHORT));
|
||||
return 0;
|
||||
}
|
||||
@@ -394,7 +432,7 @@ static int _pv_write(const struct format_type *fmt, struct physical_volume *pv,
|
||||
dl->mem = mem;
|
||||
dl->dev = pv->dev;
|
||||
|
||||
if (!export_pv(mem, NULL, &dl->pvd, pv)) {
|
||||
if (!export_pv(fmt->cmd, mem, NULL, &dl->pvd, pv)) {
|
||||
stack;
|
||||
goto bad;
|
||||
}
|
||||
@@ -430,21 +468,18 @@ static int _vg_setup(struct format_instance *fid, struct volume_group *vg)
|
||||
|
||||
if (vg->extent_size > MAX_PE_SIZE || vg->extent_size < MIN_PE_SIZE) {
|
||||
log_error("Extent size must be between %s and %s",
|
||||
display_size(fid->fmt->cmd, (uint64_t) MIN_PE_SIZE
|
||||
/ 2,
|
||||
SIZE_SHORT), display_size(fid->fmt->cmd,
|
||||
(uint64_t)
|
||||
MAX_PE_SIZE
|
||||
/ 2,
|
||||
SIZE_SHORT));
|
||||
display_size(fid->fmt->cmd, (uint64_t) MIN_PE_SIZE,
|
||||
SIZE_SHORT),
|
||||
display_size(fid->fmt->cmd, (uint64_t) MAX_PE_SIZE,
|
||||
SIZE_SHORT));
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (vg->extent_size % MIN_PE_SIZE) {
|
||||
log_error("Extent size must be multiple of %s",
|
||||
display_size(fid->fmt->cmd,
|
||||
(uint64_t) MIN_PE_SIZE / 2, SIZE_SHORT));
|
||||
display_size(fid->fmt->cmd, (uint64_t) MIN_PE_SIZE,
|
||||
SIZE_SHORT));
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
@@ -1,7 +1,16 @@
|
||||
/*
|
||||
* Copyright (C) 2001 Sistina Software (UK) Limited.
|
||||
* Copyright (C) 2001-2004 Sistina Software, Inc. All rights reserved.
|
||||
* Copyright (C) 2004 Red Hat, Inc. All rights reserved.
|
||||
*
|
||||
* This file is released under the GPL.
|
||||
* This file is part of LVM2.
|
||||
*
|
||||
* This copyrighted material is made available to anyone wishing to use,
|
||||
* modify, copy, or redistribute it subject to the terms and conditions
|
||||
* of the GNU General Public License v.2.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software Foundation,
|
||||
* Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
*/
|
||||
|
||||
#ifndef _LVM_FORMAT1_H
|
||||
|
@@ -1,9 +1,20 @@
|
||||
/*
|
||||
* Copyright (C) 2001 Sistina Software (UK) Limited.
|
||||
* Copyright (C) 2001-2004 Sistina Software, Inc. All rights reserved.
|
||||
* Copyright (C) 2004 Red Hat, Inc. All rights reserved.
|
||||
*
|
||||
* This file is part of LVM2.
|
||||
*
|
||||
* This copyrighted material is made available to anyone wishing to use,
|
||||
* modify, copy, or redistribute it subject to the terms and conditions
|
||||
* of the GNU General Public License v.2.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software Foundation,
|
||||
* Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
*/
|
||||
|
||||
/*
|
||||
* Translates between disk and in-core formats.
|
||||
*
|
||||
* This file is released under the LGPL.
|
||||
*/
|
||||
|
||||
#include "lib.h"
|
||||
@@ -13,9 +24,10 @@
|
||||
#include "list.h"
|
||||
#include "lvm-string.h"
|
||||
#include "filter.h"
|
||||
#include "toolcontext.h"
|
||||
#include "segtypes.h"
|
||||
|
||||
#include <time.h>
|
||||
#include <sys/utsname.h>
|
||||
|
||||
static int _check_vg_name(const char *name)
|
||||
{
|
||||
@@ -56,9 +68,9 @@ int import_pv(struct pool *mem, struct device *dev,
|
||||
|
||||
if (vg &&
|
||||
strncmp(vg->system_id, pvd->system_id, sizeof(pvd->system_id)))
|
||||
log_very_verbose("System ID %s on %s differs from %s for "
|
||||
"volume group", pvd->system_id,
|
||||
dev_name(pv->dev), vg->system_id);
|
||||
log_very_verbose("System ID %s on %s differs from %s for "
|
||||
"volume group", pvd->system_id,
|
||||
dev_name(pv->dev), vg->system_id);
|
||||
|
||||
/*
|
||||
* If exported, we still need to flag in pv->status too because
|
||||
@@ -76,20 +88,16 @@ int import_pv(struct pool *mem, struct device *dev,
|
||||
pv->pe_count = pvd->pe_total;
|
||||
pv->pe_alloc_count = pvd->pe_allocated;
|
||||
|
||||
list_init(&pv->tags);
|
||||
|
||||
return 1;
|
||||
}
|
||||
|
||||
static int _system_id(char *s, const char *prefix)
|
||||
static int _system_id(struct cmd_context *cmd, char *s, const char *prefix)
|
||||
{
|
||||
struct utsname uts;
|
||||
|
||||
if (uname(&uts) != 0) {
|
||||
log_sys_error("uname", "_system_id");
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (lvm_snprintf(s, NAME_LEN, "%s%s%lu",
|
||||
prefix, uts.nodename, time(NULL)) < 0) {
|
||||
prefix, cmd->hostname, time(NULL)) < 0) {
|
||||
log_error("Generated system_id too long");
|
||||
return 0;
|
||||
}
|
||||
@@ -97,7 +105,8 @@ static int _system_id(char *s, const char *prefix)
|
||||
return 1;
|
||||
}
|
||||
|
||||
int export_pv(struct pool *mem, struct volume_group *vg,
|
||||
int export_pv(struct cmd_context *cmd, struct pool *mem,
|
||||
struct volume_group *vg,
|
||||
struct pv_disk *pvd, struct physical_volume *pv)
|
||||
{
|
||||
memset(pvd, 0, sizeof(*pvd));
|
||||
@@ -128,7 +137,7 @@ int export_pv(struct pool *mem, struct volume_group *vg,
|
||||
if (!*vg->system_id ||
|
||||
strncmp(vg->system_id, EXPORTED_TAG,
|
||||
sizeof(EXPORTED_TAG) - 1)) {
|
||||
if (!_system_id(pvd->system_id, EXPORTED_TAG)) {
|
||||
if (!_system_id(cmd, pvd->system_id, EXPORTED_TAG)) {
|
||||
stack;
|
||||
return 0;
|
||||
}
|
||||
@@ -145,7 +154,7 @@ int export_pv(struct pool *mem, struct volume_group *vg,
|
||||
/* Is VG being imported? */
|
||||
if (vg && !(vg->status & EXPORTED_VG) && *vg->system_id &&
|
||||
!strncmp(vg->system_id, EXPORTED_TAG, sizeof(EXPORTED_TAG) - 1)) {
|
||||
if (!_system_id(pvd->system_id, IMPORTED_TAG)) {
|
||||
if (!_system_id(cmd, pvd->system_id, IMPORTED_TAG)) {
|
||||
stack;
|
||||
return 0;
|
||||
}
|
||||
@@ -153,7 +162,7 @@ int export_pv(struct pool *mem, struct volume_group *vg,
|
||||
|
||||
/* Generate system_id if PV is in VG */
|
||||
if (!pvd->system_id || !*pvd->system_id)
|
||||
if (!_system_id(pvd->system_id, "")) {
|
||||
if (!_system_id(cmd, pvd->system_id, "")) {
|
||||
stack;
|
||||
return 0;
|
||||
}
|
||||
@@ -162,7 +171,7 @@ int export_pv(struct pool *mem, struct volume_group *vg,
|
||||
if (vg &&
|
||||
(!*vg->system_id ||
|
||||
strncmp(vg->system_id, pvd->system_id, sizeof(pvd->system_id))))
|
||||
strncpy(vg->system_id, pvd->system_id, NAME_LEN);
|
||||
strncpy(vg->system_id, pvd->system_id, NAME_LEN);
|
||||
|
||||
//pvd->pv_major = MAJOR(pv->dev);
|
||||
|
||||
@@ -228,6 +237,7 @@ int import_vg(struct pool *mem,
|
||||
vg->free_count = vgd->pe_total - vgd->pe_allocated;
|
||||
vg->max_lv = vgd->lv_max;
|
||||
vg->max_pv = vgd->pv_max;
|
||||
vg->alloc = ALLOC_NORMAL;
|
||||
|
||||
if (partial)
|
||||
vg->status |= PARTIAL_VG;
|
||||
@@ -307,13 +317,14 @@ int import_lv(struct pool *mem, struct logical_volume *lv, struct lv_disk *lvd)
|
||||
if (lvd->lv_allocation & LV_CONTIGUOUS)
|
||||
lv->alloc = ALLOC_CONTIGUOUS;
|
||||
else
|
||||
lv->alloc = ALLOC_NEXT_FREE;
|
||||
lv->alloc = ALLOC_NORMAL;
|
||||
|
||||
lv->read_ahead = lvd->lv_read_ahead;
|
||||
lv->size = lvd->lv_size;
|
||||
lv->le_count = lvd->lv_allocated_le;
|
||||
|
||||
list_init(&lv->segments);
|
||||
list_init(&lv->tags);
|
||||
|
||||
return 1;
|
||||
}
|
||||
@@ -371,9 +382,10 @@ int export_extents(struct disk_list *dl, uint32_t lv_num,
|
||||
seg = list_item(segh, struct lv_segment);
|
||||
|
||||
for (s = 0; s < seg->area_count; s++) {
|
||||
if (seg->type != SEG_STRIPED) {
|
||||
log_error("Non-striped segment type in LV %s: "
|
||||
"unsupported by format1", lv->name);
|
||||
if (!(seg->segtype->flags & SEG_FORMAT1_SUPPORT)) {
|
||||
log_error("Segment type %s in LV %s: "
|
||||
"unsupported by format1",
|
||||
seg->segtype->name, lv->name);
|
||||
return 0;
|
||||
}
|
||||
if (seg->area[s].type != AREA_PV) {
|
||||
|
@@ -1,7 +1,16 @@
|
||||
/*
|
||||
* Copyright (C) 2001 Sistina Software (UK) Limited.
|
||||
* Copyright (C) 2001-2004 Sistina Software, Inc. All rights reserved.
|
||||
* Copyright (C) 2004 Red Hat, Inc. All rights reserved.
|
||||
*
|
||||
* This file is released under the LGPL.
|
||||
* This file is part of LVM2.
|
||||
*
|
||||
* This copyrighted material is made available to anyone wishing to use,
|
||||
* modify, copy, or redistribute it subject to the terms and conditions
|
||||
* of the GNU General Public License v.2.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software Foundation,
|
||||
* Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
*/
|
||||
|
||||
#include "lib.h"
|
||||
@@ -10,6 +19,8 @@
|
||||
#include "pool.h"
|
||||
#include "disk-rep.h"
|
||||
#include "lv_alloc.h"
|
||||
#include "display.h"
|
||||
#include "segtypes.h"
|
||||
|
||||
/*
|
||||
* After much thought I have decided it is easier,
|
||||
@@ -192,21 +203,24 @@ static int _check_maps_are_complete(struct hash_table *maps)
|
||||
return 1;
|
||||
}
|
||||
|
||||
static int _read_linear(struct pool *mem, struct lv_map *lvm)
|
||||
static int _read_linear(struct cmd_context *cmd, struct lv_map *lvm)
|
||||
{
|
||||
uint32_t le = 0;
|
||||
struct lv_segment *seg;
|
||||
|
||||
while (le < lvm->lv->le_count) {
|
||||
seg = alloc_lv_segment(mem, 1);
|
||||
seg = alloc_lv_segment(cmd->mem, 1);
|
||||
|
||||
seg->lv = lvm->lv;
|
||||
seg->type = SEG_STRIPED;
|
||||
if (!(seg->segtype = get_segtype_from_string(cmd, "striped"))) {
|
||||
stack;
|
||||
return 0;
|
||||
}
|
||||
|
||||
seg->le = le;
|
||||
seg->len = 0;
|
||||
seg->area_len = 0;
|
||||
seg->stripe_size = 0;
|
||||
seg->area_count = 1;
|
||||
|
||||
seg->area[0].type = AREA_PV;
|
||||
seg->area[0].u.pv.pv = lvm->map[le].pv;
|
||||
@@ -242,13 +256,12 @@ static int _check_stripe(struct lv_map *lvm, struct lv_segment *seg,
|
||||
if ((lvm->map[le + st * len].pv != seg->area[st].u.pv.pv) ||
|
||||
(seg->area[st].u.pv.pv &&
|
||||
lvm->map[le + st * len].pe !=
|
||||
seg->area[st].u.pv.pe + seg->len))
|
||||
return 0;
|
||||
seg->area[st].u.pv.pe + seg->len)) return 0;
|
||||
|
||||
return 1;
|
||||
}
|
||||
|
||||
static int _read_stripes(struct pool *mem, struct lv_map *lvm)
|
||||
static int _read_stripes(struct cmd_context *cmd, struct lv_map *lvm)
|
||||
{
|
||||
uint32_t st, le = 0, len;
|
||||
struct lv_segment *seg;
|
||||
@@ -264,15 +277,17 @@ static int _read_stripes(struct pool *mem, struct lv_map *lvm)
|
||||
len = lvm->lv->le_count / lvm->stripes;
|
||||
|
||||
while (le < len) {
|
||||
if (!(seg = alloc_lv_segment(mem, lvm->stripes))) {
|
||||
if (!(seg = alloc_lv_segment(cmd->mem, lvm->stripes))) {
|
||||
stack;
|
||||
return 0;
|
||||
}
|
||||
|
||||
seg->lv = lvm->lv;
|
||||
seg->type = SEG_STRIPED;
|
||||
if (!(seg->segtype = get_segtype_from_string(cmd, "striped"))) {
|
||||
stack;
|
||||
return 0;
|
||||
}
|
||||
seg->stripe_size = lvm->stripe_size;
|
||||
seg->area_count = lvm->stripes;
|
||||
seg->le = seg->area_count * le;
|
||||
seg->len = 1;
|
||||
seg->area_len = 1;
|
||||
@@ -303,20 +318,20 @@ static int _read_stripes(struct pool *mem, struct lv_map *lvm)
|
||||
return 1;
|
||||
}
|
||||
|
||||
static int _build_segments(struct pool *mem, struct lv_map *lvm)
|
||||
static int _build_segments(struct cmd_context *cmd, struct lv_map *lvm)
|
||||
{
|
||||
return (lvm->stripes > 1 ? _read_stripes(mem, lvm) :
|
||||
_read_linear(mem, lvm));
|
||||
return (lvm->stripes > 1 ? _read_stripes(cmd, lvm) :
|
||||
_read_linear(cmd, lvm));
|
||||
}
|
||||
|
||||
static int _build_all_segments(struct pool *mem, struct hash_table *maps)
|
||||
static int _build_all_segments(struct cmd_context *cmd, struct hash_table *maps)
|
||||
{
|
||||
struct hash_node *n;
|
||||
struct lv_map *lvm;
|
||||
|
||||
for (n = hash_get_first(maps); n; n = hash_get_next(maps, n)) {
|
||||
lvm = (struct lv_map *) hash_get_data(maps, n);
|
||||
if (!_build_segments(mem, lvm)) {
|
||||
if (!_build_segments(cmd, lvm)) {
|
||||
stack;
|
||||
return 0;
|
||||
}
|
||||
@@ -325,7 +340,8 @@ static int _build_all_segments(struct pool *mem, struct hash_table *maps)
|
||||
return 1;
|
||||
}
|
||||
|
||||
int import_extents(struct pool *mem, struct volume_group *vg, struct list *pvds)
|
||||
int import_extents(struct cmd_context *cmd, struct volume_group *vg,
|
||||
struct list *pvds)
|
||||
{
|
||||
int r = 0;
|
||||
struct pool *scratch = pool_create(10 * 1024);
|
||||
@@ -351,7 +367,7 @@ int import_extents(struct pool *mem, struct volume_group *vg, struct list *pvds)
|
||||
goto out;
|
||||
}
|
||||
|
||||
if (!_build_all_segments(mem, maps)) {
|
||||
if (!_build_all_segments(cmd, maps)) {
|
||||
log_err("Couldn't build extent segments.");
|
||||
goto out;
|
||||
}
|
||||
|
@@ -1,7 +1,16 @@
|
||||
/*
|
||||
* Copyright (C) 2001 Sistina Software (UK) Limited.
|
||||
* Copyright (C) 2001-2004 Sistina Software, Inc. All rights reserved.
|
||||
* Copyright (C) 2004 Red Hat, Inc. All rights reserved.
|
||||
*
|
||||
* This file is released under the LGPL.
|
||||
* This file is part of LVM2.
|
||||
*
|
||||
* This copyrighted material is made available to anyone wishing to use,
|
||||
* modify, copy, or redistribute it subject to the terms and conditions
|
||||
* of the GNU General Public License v.2.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software Foundation,
|
||||
* Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
*/
|
||||
|
||||
#include "lib.h"
|
||||
@@ -103,9 +112,10 @@ int calculate_layout(struct disk_list *dl)
|
||||
|
||||
/*
|
||||
* The number of extents that can fit on a disk is metadata format dependant.
|
||||
* pe_start is any existing value for pe_start
|
||||
*/
|
||||
int calculate_extent_count(struct physical_volume *pv, uint32_t extent_size,
|
||||
uint32_t max_extent_count)
|
||||
uint32_t max_extent_count, uint64_t pe_start)
|
||||
{
|
||||
struct pv_disk *pvd = dbg_malloc(sizeof(*pvd));
|
||||
uint32_t end;
|
||||
@@ -138,6 +148,9 @@ int calculate_extent_count(struct physical_volume *pv, uint32_t extent_size,
|
||||
end = ((pvd->pe_on_disk.base + pvd->pe_on_disk.size +
|
||||
SECTOR_SIZE - 1) >> SECTOR_SHIFT);
|
||||
|
||||
if (pe_start && end < pe_start)
|
||||
end = pe_start;
|
||||
|
||||
pvd->pe_start = _round_up(end, PE_ALIGN);
|
||||
|
||||
} while ((pvd->pe_start + (pvd->pe_total * extent_size))
|
||||
|
@@ -1,7 +1,16 @@
|
||||
/*
|
||||
* Copyright (C) 2002 Sistina Software (UK) Limited.
|
||||
* Copyright (C) 2002-2004 Sistina Software, Inc. All rights reserved.
|
||||
* Copyright (C) 2004 Red Hat, Inc. All rights reserved.
|
||||
*
|
||||
* This file is released under the LGPL.
|
||||
* This file is part of LVM2.
|
||||
*
|
||||
* This copyrighted material is made available to anyone wishing to use,
|
||||
* modify, copy, or redistribute it subject to the terms and conditions
|
||||
* of the GNU General Public License v.2.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software Foundation,
|
||||
* Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
*/
|
||||
|
||||
#include "lib.h"
|
||||
@@ -51,7 +60,8 @@ static int _read(struct labeller *l, struct device *dev, char *buf,
|
||||
struct pv_disk *pvd = (struct pv_disk *) buf;
|
||||
struct lvmcache_info *info;
|
||||
|
||||
munge_exported_vg(pvd);
|
||||
munge_pvd(dev, pvd);
|
||||
|
||||
if (!(info = lvmcache_add(l, pvd->pv_uuid, dev, pvd->vg_name, NULL))) {
|
||||
stack;
|
||||
return 0;
|
||||
|
@@ -1,7 +1,16 @@
|
||||
/*
|
||||
* Copyright (C) 2002 Sistina Software (UK) Limited.
|
||||
* Copyright (C) 2002-2004 Sistina Software, Inc. All rights reserved.
|
||||
* Copyright (C) 2004 Red Hat, Inc. All rights reserved.
|
||||
*
|
||||
* This file is released under the LGPL.
|
||||
* This file is part of LVM2.
|
||||
*
|
||||
* This copyrighted material is made available to anyone wishing to use,
|
||||
* modify, copy, or redistribute it subject to the terms and conditions
|
||||
* of the GNU General Public License v.2.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software Foundation,
|
||||
* Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
*/
|
||||
|
||||
#ifndef _LVM_LVM1_LABEL_H
|
||||
|
@@ -1,7 +1,16 @@
|
||||
/*
|
||||
* Copyright (C) 2001 Sistina Software (UK) Limited.
|
||||
* Copyright (C) 2001-2004 Sistina Software, Inc. All rights reserved.
|
||||
* Copyright (C) 2004 Red Hat, Inc. All rights reserved.
|
||||
*
|
||||
* This file is released under the LGPL.
|
||||
* This file is part of LVM2.
|
||||
*
|
||||
* This copyrighted material is made available to anyone wishing to use,
|
||||
* modify, copy, or redistribute it subject to the terms and conditions
|
||||
* of the GNU General Public License v.2.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software Foundation,
|
||||
* Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
*/
|
||||
|
||||
#include "lib.h"
|
||||
|
1
lib/format_pool/.exported_symbols
Normal file
1
lib/format_pool/.exported_symbols
Normal file
@@ -0,0 +1 @@
|
||||
init_format
|
37
lib/format_pool/Makefile.in
Normal file
37
lib/format_pool/Makefile.in
Normal file
@@ -0,0 +1,37 @@
|
||||
#
|
||||
# Copyright (C) 2003-2004 Sistina Software, Inc. All rights reserved.
|
||||
# Copyright (C) 2004 Red Hat, Inc. All rights reserved.
|
||||
#
|
||||
# This file is part of the LVM2.
|
||||
#
|
||||
# This copyrighted material is made available to anyone wishing to use,
|
||||
# modify, copy, or redistribute it subject to the terms and conditions
|
||||
# of the GNU General Public License v.2.
|
||||
#
|
||||
# You should have received a copy of the GNU General Public License
|
||||
# along with this program; if not, write to the Free Software Foundation,
|
||||
# Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
|
||||
srcdir = @srcdir@
|
||||
top_srcdir = @top_srcdir@
|
||||
VPATH = @srcdir@
|
||||
|
||||
SOURCES =\
|
||||
disk_rep.c \
|
||||
format_pool.c \
|
||||
import_export.c \
|
||||
pool_label.c
|
||||
|
||||
LIB_SHARED = liblvm2formatpool.so
|
||||
|
||||
include ../../make.tmpl
|
||||
|
||||
.PHONY: install
|
||||
|
||||
install: liblvm2formatpool.so
|
||||
$(INSTALL) -D $(OWNER) $(GROUP) -m 555 $(STRIP) $< \
|
||||
$(libdir)/liblvm2formatpool.so.$(LIB_VERSION)
|
||||
$(LN_S) -f liblvm2formatpool.so.$(LIB_VERSION) \
|
||||
$(libdir)/liblvm2formatpool.so
|
||||
|
||||
|
385
lib/format_pool/disk_rep.c
Normal file
385
lib/format_pool/disk_rep.c
Normal file
@@ -0,0 +1,385 @@
|
||||
/*
|
||||
* Copyright (C) 1997-2004 Sistina Software, Inc. All rights reserved.
|
||||
* Copyright (C) 2004 Red Hat, Inc. All rights reserved.
|
||||
*
|
||||
* This file is part of LVM2.
|
||||
*
|
||||
* This copyrighted material is made available to anyone wishing to use,
|
||||
* modify, copy, or redistribute it subject to the terms and conditions
|
||||
* of the GNU General Public License v.2.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software Foundation,
|
||||
* Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
*/
|
||||
|
||||
#include "lib.h"
|
||||
#include "pool.h"
|
||||
#include "label.h"
|
||||
#include "metadata.h"
|
||||
#include "lvmcache.h"
|
||||
#include "filter.h"
|
||||
#include "list.h"
|
||||
#include "xlate.h"
|
||||
|
||||
#include "disk_rep.h"
|
||||
|
||||
/* FIXME: memcpy might not be portable */
|
||||
#define CPIN_8(x, y, z) {memcpy((x), (y), (z));}
|
||||
#define CPOUT_8(x, y, z) {memcpy((y), (x), (z));}
|
||||
#define CPIN_16(x, y) {(x) = xlate16_be((y));}
|
||||
#define CPOUT_16(x, y) {(y) = xlate16_be((x));}
|
||||
#define CPIN_32(x, y) {(x) = xlate32_be((y));}
|
||||
#define CPOUT_32(x, y) {(y) = xlate32_be((x));}
|
||||
#define CPIN_64(x, y) {(x) = xlate64_be((y));}
|
||||
#define CPOUT_64(x, y) {(y) = xlate64_be((x));}
|
||||
|
||||
static int __read_pool_disk(const struct format_type *fmt, struct device *dev,
|
||||
struct pool *mem, struct pool_list *pl,
|
||||
const char *vg_name)
|
||||
{
|
||||
char buf[512];
|
||||
|
||||
/* FIXME: Need to check the cache here first */
|
||||
if (!dev_read(dev, UINT64_C(0), 512, buf)) {
|
||||
log_very_verbose("Failed to read PV data from %s",
|
||||
dev_name(dev));
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (!read_pool_label(pl, fmt->labeller, dev, buf, NULL)) {
|
||||
stack;
|
||||
return 0;
|
||||
}
|
||||
|
||||
return 1;
|
||||
}
|
||||
|
||||
static void _add_pl_to_list(struct list *head, struct pool_list *data)
|
||||
{
|
||||
struct list *pvdh;
|
||||
struct pool_list *pl;
|
||||
|
||||
list_iterate(pvdh, head) {
|
||||
pl = list_item(pvdh, struct pool_list);
|
||||
|
||||
if (id_equal(&data->pv_uuid, &pl->pv_uuid)) {
|
||||
char uuid[ID_LEN + 7];
|
||||
|
||||
id_write_format(&pl->pv_uuid, uuid, ID_LEN + 7);
|
||||
|
||||
if (MAJOR(data->dev->dev) != md_major()) {
|
||||
log_very_verbose("Ignoring duplicate PV %s on "
|
||||
"%s", uuid,
|
||||
dev_name(data->dev));
|
||||
return;
|
||||
}
|
||||
log_very_verbose("Duplicate PV %s - using md %s",
|
||||
uuid, dev_name(data->dev));
|
||||
list_del(pvdh);
|
||||
break;
|
||||
}
|
||||
}
|
||||
list_add(head, &data->list);
|
||||
}
|
||||
|
||||
int read_pool_label(struct pool_list *pl, struct labeller *l,
|
||||
struct device *dev, char *buf, struct label **label)
|
||||
{
|
||||
struct lvmcache_info *info;
|
||||
struct id pvid;
|
||||
struct id vgid;
|
||||
char uuid[ID_LEN + 7];
|
||||
struct pool_disk *pd = &pl->pd;
|
||||
|
||||
pool_label_in(pd, buf);
|
||||
|
||||
get_pool_pv_uuid(&pvid, pd);
|
||||
id_write_format(&pvid, uuid, ID_LEN + 7);
|
||||
log_debug("Calculated uuid %s for %s", uuid, dev_name(dev));
|
||||
|
||||
get_pool_vg_uuid(&vgid, pd);
|
||||
id_write_format(&vgid, uuid, ID_LEN + 7);
|
||||
log_debug("Calculated uuid %s for %s", uuid, pd->pl_pool_name);
|
||||
|
||||
if (!(info = lvmcache_add(l, (char *) &pvid, dev, pd->pl_pool_name,
|
||||
(char *) &vgid))) {
|
||||
stack;
|
||||
return 0;
|
||||
}
|
||||
if (label)
|
||||
*label = info->label;
|
||||
|
||||
info->device_size = xlate32_be(pd->pl_blocks) << SECTOR_SHIFT;
|
||||
list_init(&info->mdas);
|
||||
|
||||
info->status &= ~CACHE_INVALID;
|
||||
|
||||
pl->dev = dev;
|
||||
pl->pv = NULL;
|
||||
memcpy(&pl->pv_uuid, &pvid, sizeof(pvid));
|
||||
|
||||
return 1;
|
||||
}
|
||||
|
||||
/**
|
||||
* pool_label_out - copies a pool_label_t into a char buffer
|
||||
* @pl: ptr to a pool_label_t struct
|
||||
* @buf: ptr to raw space where label info will be copied
|
||||
*
|
||||
* This function is important because it takes care of all of
|
||||
* the endian issues when copying to disk. This way, when
|
||||
* machines of different architectures are used, they will
|
||||
* be able to interpret ondisk labels correctly. Always use
|
||||
* this function before writing to disk.
|
||||
*/
|
||||
void pool_label_out(struct pool_disk *pl, char *buf)
|
||||
{
|
||||
struct pool_disk *bufpl = (struct pool_disk *) buf;
|
||||
|
||||
CPOUT_64(pl->pl_magic, bufpl->pl_magic);
|
||||
CPOUT_64(pl->pl_pool_id, bufpl->pl_pool_id);
|
||||
CPOUT_8(pl->pl_pool_name, bufpl->pl_pool_name, POOL_NAME_SIZE);
|
||||
CPOUT_32(pl->pl_version, bufpl->pl_version);
|
||||
CPOUT_32(pl->pl_subpools, bufpl->pl_subpools);
|
||||
CPOUT_32(pl->pl_sp_id, bufpl->pl_sp_id);
|
||||
CPOUT_32(pl->pl_sp_devs, bufpl->pl_sp_devs);
|
||||
CPOUT_32(pl->pl_sp_devid, bufpl->pl_sp_devid);
|
||||
CPOUT_32(pl->pl_sp_type, bufpl->pl_sp_type);
|
||||
CPOUT_64(pl->pl_blocks, bufpl->pl_blocks);
|
||||
CPOUT_32(pl->pl_striping, bufpl->pl_striping);
|
||||
CPOUT_32(pl->pl_sp_dmepdevs, bufpl->pl_sp_dmepdevs);
|
||||
CPOUT_32(pl->pl_sp_dmepid, bufpl->pl_sp_dmepid);
|
||||
CPOUT_32(pl->pl_sp_weight, bufpl->pl_sp_weight);
|
||||
CPOUT_32(pl->pl_minor, bufpl->pl_minor);
|
||||
CPOUT_32(pl->pl_padding, bufpl->pl_padding);
|
||||
CPOUT_8(pl->pl_reserve, bufpl->pl_reserve, 184);
|
||||
}
|
||||
|
||||
/**
|
||||
* pool_label_in - copies a char buffer into a pool_label_t
|
||||
* @pl: ptr to a pool_label_t struct
|
||||
* @buf: ptr to raw space where label info is copied from
|
||||
*
|
||||
* This function is important because it takes care of all of
|
||||
* the endian issues when information from disk is about to be
|
||||
* used. This way, when machines of different architectures
|
||||
* are used, they will be able to interpret ondisk labels
|
||||
* correctly. Always use this function before using labels that
|
||||
* were read from disk.
|
||||
*/
|
||||
void pool_label_in(struct pool_disk *pl, char *buf)
|
||||
{
|
||||
struct pool_disk *bufpl = (struct pool_disk *) buf;
|
||||
|
||||
CPIN_64(pl->pl_magic, bufpl->pl_magic);
|
||||
CPIN_64(pl->pl_pool_id, bufpl->pl_pool_id);
|
||||
CPIN_8(pl->pl_pool_name, bufpl->pl_pool_name, POOL_NAME_SIZE);
|
||||
CPIN_32(pl->pl_version, bufpl->pl_version);
|
||||
CPIN_32(pl->pl_subpools, bufpl->pl_subpools);
|
||||
CPIN_32(pl->pl_sp_id, bufpl->pl_sp_id);
|
||||
CPIN_32(pl->pl_sp_devs, bufpl->pl_sp_devs);
|
||||
CPIN_32(pl->pl_sp_devid, bufpl->pl_sp_devid);
|
||||
CPIN_32(pl->pl_sp_type, bufpl->pl_sp_type);
|
||||
CPIN_64(pl->pl_blocks, bufpl->pl_blocks);
|
||||
CPIN_32(pl->pl_striping, bufpl->pl_striping);
|
||||
CPIN_32(pl->pl_sp_dmepdevs, bufpl->pl_sp_dmepdevs);
|
||||
CPIN_32(pl->pl_sp_dmepid, bufpl->pl_sp_dmepid);
|
||||
CPIN_32(pl->pl_sp_weight, bufpl->pl_sp_weight);
|
||||
CPIN_32(pl->pl_minor, bufpl->pl_minor);
|
||||
CPIN_32(pl->pl_padding, bufpl->pl_padding);
|
||||
CPIN_8(pl->pl_reserve, bufpl->pl_reserve, 184);
|
||||
}
|
||||
|
||||
static char _calc_char(unsigned int id)
|
||||
{
|
||||
/*
|
||||
* [0-9A-Za-z!#] - 64 printable chars (6-bits)
|
||||
*/
|
||||
|
||||
if (id < 10)
|
||||
return id + 48;
|
||||
if (id < 36)
|
||||
return (id - 10) + 65;
|
||||
if (id < 62)
|
||||
return (id - 36) + 97;
|
||||
if (id == 62)
|
||||
return '!';
|
||||
if (id == 63)
|
||||
return '#';
|
||||
|
||||
return '%';
|
||||
}
|
||||
|
||||
void get_pool_uuid(char *uuid, uint64_t poolid, uint32_t spid, uint32_t devid)
|
||||
{
|
||||
int i;
|
||||
unsigned shifter = 0x003F;
|
||||
|
||||
assert(ID_LEN == 32);
|
||||
memset(uuid, 0, ID_LEN);
|
||||
strcat(uuid, "POOL0000000000");
|
||||
|
||||
/* We grab the entire 64 bits (+2 that get shifted in) */
|
||||
for (i = 13; i < 24; i++) {
|
||||
uuid[i] = _calc_char(((unsigned) poolid) & shifter);
|
||||
poolid = poolid >> 6;
|
||||
}
|
||||
|
||||
/* We grab the entire 32 bits (+4 that get shifted in) */
|
||||
for (i = 24; i < 30; i++) {
|
||||
uuid[i] = _calc_char((unsigned) (spid & shifter));
|
||||
spid = spid >> 6;
|
||||
}
|
||||
|
||||
/*
|
||||
* Since we can only have 128 devices, we only worry about the
|
||||
* last 12 bits
|
||||
*/
|
||||
for (i = 30; i < 32; i++) {
|
||||
uuid[i] = _calc_char((unsigned) (devid & shifter));
|
||||
devid = devid >> 6;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
static int _read_vg_pds(const struct format_type *fmt, struct pool *mem,
|
||||
struct lvmcache_vginfo *vginfo, struct list *head,
|
||||
uint32_t *devcount)
|
||||
{
|
||||
|
||||
struct list *vgih = NULL;
|
||||
struct device *dev;
|
||||
struct pool_list *pl = NULL;
|
||||
struct pool *tmpmem = NULL;
|
||||
|
||||
uint32_t sp_count = 0;
|
||||
uint32_t *sp_devs = NULL;
|
||||
int i;
|
||||
|
||||
/* FIXME: maybe should return a different error in memory
|
||||
* allocation failure */
|
||||
if (!(tmpmem = pool_create(512))) {
|
||||
stack;
|
||||
return 0;
|
||||
}
|
||||
|
||||
list_iterate(vgih, &vginfo->infos) {
|
||||
dev = list_item(vgih, struct lvmcache_info)->dev;
|
||||
if (dev &&
|
||||
!(pl = read_pool_disk(fmt, dev, mem, vginfo->vgname)))
|
||||
break;
|
||||
/*
|
||||
* We need to keep track of the total expected number
|
||||
* of devices per subpool
|
||||
*/
|
||||
if (!sp_count) {
|
||||
sp_count = pl->pd.pl_subpools;
|
||||
if (!(sp_devs =
|
||||
pool_zalloc(tmpmem,
|
||||
sizeof(uint32_t) * sp_count))) {
|
||||
log_error("Unable to allocate %d 32-bit uints",
|
||||
sp_count);
|
||||
pool_destroy(tmpmem);
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
/*
|
||||
* watch out for a pool label with a different subpool
|
||||
* count than the original - give up if it does
|
||||
*/
|
||||
if (sp_count != pl->pd.pl_subpools)
|
||||
break;
|
||||
|
||||
_add_pl_to_list(head, pl);
|
||||
|
||||
if (sp_count > pl->pd.pl_sp_id && sp_devs[pl->pd.pl_sp_id] == 0)
|
||||
sp_devs[pl->pd.pl_sp_id] = pl->pd.pl_sp_devs;
|
||||
}
|
||||
|
||||
*devcount = 0;
|
||||
for (i = 0; i < sp_count; i++) {
|
||||
*devcount += sp_devs[i];
|
||||
}
|
||||
|
||||
pool_destroy(tmpmem);
|
||||
|
||||
if (pl && *pl->pd.pl_pool_name)
|
||||
return 1;
|
||||
|
||||
return 0;
|
||||
|
||||
}
|
||||
|
||||
int read_pool_pds(const struct format_type *fmt, const char *vg_name,
|
||||
struct pool *mem, struct list *pdhead)
|
||||
{
|
||||
struct lvmcache_vginfo *vginfo;
|
||||
uint32_t totaldevs;
|
||||
int full_scan = -1;
|
||||
|
||||
do {
|
||||
/*
|
||||
* If the cache scanning doesn't work, this will never work
|
||||
*/
|
||||
if (vg_name && (vginfo = vginfo_from_vgname(vg_name)) &&
|
||||
vginfo->infos.n) {
|
||||
|
||||
if (_read_vg_pds(fmt, mem, vginfo, pdhead, &totaldevs)) {
|
||||
/*
|
||||
* If we found all the devices we were
|
||||
* expecting, return success
|
||||
*/
|
||||
if (list_size(pdhead) == totaldevs)
|
||||
return 1;
|
||||
|
||||
/*
|
||||
* accept partial pool if we've done a full
|
||||
* rescan of the cache
|
||||
*/
|
||||
if (full_scan > 0)
|
||||
return 1;
|
||||
}
|
||||
}
|
||||
/* Failed */
|
||||
list_init(pdhead);
|
||||
|
||||
full_scan++;
|
||||
if (full_scan > 1) {
|
||||
log_debug("No devices for vg %s found in cache",
|
||||
vg_name);
|
||||
return 0;
|
||||
}
|
||||
lvmcache_label_scan(fmt->cmd, full_scan);
|
||||
|
||||
} while (1);
|
||||
|
||||
}
|
||||
|
||||
struct pool_list *read_pool_disk(const struct format_type *fmt,
|
||||
struct device *dev, struct pool *mem,
|
||||
const char *vg_name)
|
||||
{
|
||||
struct pool_list *pl;
|
||||
|
||||
if (!dev_open(dev)) {
|
||||
stack;
|
||||
return NULL;
|
||||
}
|
||||
|
||||
if (!(pl = pool_zalloc(mem, sizeof(*pl)))) {
|
||||
log_error("Unable to allocate pool list structure");
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (!__read_pool_disk(fmt, dev, mem, pl, vg_name)) {
|
||||
stack;
|
||||
return NULL;
|
||||
}
|
||||
|
||||
if (!dev_close(dev))
|
||||
stack;
|
||||
|
||||
return pl;
|
||||
|
||||
}
|
178
lib/format_pool/disk_rep.h
Normal file
178
lib/format_pool/disk_rep.h
Normal file
@@ -0,0 +1,178 @@
|
||||
/*
|
||||
* Copyright (C) 1997-2004 Sistina Software, Inc. All rights reserved.
|
||||
* Copyright (C) 2004 Red Hat, Inc. All rights reserved.
|
||||
*
|
||||
* This file is part of LVM2.
|
||||
*
|
||||
* This copyrighted material is made available to anyone wishing to use,
|
||||
* modify, copy, or redistribute it subject to the terms and conditions
|
||||
* of the GNU General Public License v.2.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software Foundation,
|
||||
* Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
*/
|
||||
|
||||
#ifndef DISK_REP_FORMAT_POOL_H
|
||||
#define DISK_REP_FORMAT_POOL_H
|
||||
|
||||
#include "label.h"
|
||||
#include "metadata.h"
|
||||
#include "pool.h"
|
||||
|
||||
/* From NSP.cf */
|
||||
#define NSPMajorVersion 4
|
||||
#define NSPMinorVersion 1
|
||||
#define NSPUpdateLevel 3
|
||||
|
||||
/* From pool_std.h */
|
||||
#define POOL_NAME_SIZE (256)
|
||||
#define POOL_MAGIC 0x011670
|
||||
#define POOL_MAJOR (121)
|
||||
#define POOL_MAX_DEVICES 128
|
||||
|
||||
/* When checking for version matching, the first two numbers **
|
||||
** are important for metadata formats, a.k.a pool labels. **
|
||||
** All the numbers are important when checking if the user **
|
||||
** space tools match up with the kernel module............. */
|
||||
#define POOL_VERSION (NSPMajorVersion << 16 | \
|
||||
NSPMinorVersion << 8 | \
|
||||
NSPUpdateLevel)
|
||||
|
||||
/* Pool label is at the head of every pool disk partition */
|
||||
#define SIZEOF_POOL_LABEL (8192)
|
||||
|
||||
/* in sectors */
|
||||
#define POOL_PE_SIZE (SIZEOF_POOL_LABEL >> SECTOR_SHIFT)
|
||||
#define POOL_PE_START (SIZEOF_POOL_LABEL >> SECTOR_SHIFT)
|
||||
|
||||
/* Helper fxns */
|
||||
#define get_pool_vg_uuid(id, pd) do { get_pool_uuid((char *)(id), \
|
||||
(pd)->pl_pool_id, 0, 0); \
|
||||
} while(0)
|
||||
#define get_pool_pv_uuid(id, pd) do { get_pool_uuid((char *)(id), \
|
||||
(pd)->pl_pool_id, \
|
||||
(pd)->pl_sp_id, \
|
||||
(pd)->pl_sp_devid); \
|
||||
} while(0)
|
||||
#define get_pool_lv_uuid(id, pd) do { get_pool_uuid((char *)&(id)[0], \
|
||||
(pd)->pl_pool_id, 0, 0); \
|
||||
get_pool_uuid((char*)&(id)[1], \
|
||||
(pd)->pl_pool_id, 0, 0); \
|
||||
} while(0)
|
||||
|
||||
struct pool_disk;
|
||||
struct pool_list;
|
||||
struct user_subpool;
|
||||
struct user_device;
|
||||
|
||||
/* This must be kept up to date with sistina/pool/module/pool_sptypes.h */
|
||||
|
||||
/* Generic Labels */
|
||||
#define SPTYPE_DATA (0x00000000)
|
||||
|
||||
/* GFS specific labels */
|
||||
#define SPTYPE_GFS_DATA (0x68011670)
|
||||
#define SPTYPE_GFS_JOURNAL (0x69011670)
|
||||
|
||||
struct sptype_name {
|
||||
const char *name;
|
||||
uint32_t label;
|
||||
};
|
||||
|
||||
static const struct sptype_name sptype_names[] = {
|
||||
{"data", SPTYPE_DATA},
|
||||
|
||||
{"gfs_data", SPTYPE_GFS_DATA},
|
||||
{"gfs_journal", SPTYPE_GFS_JOURNAL},
|
||||
|
||||
{"", 0x0} /* This must be the last flag. */
|
||||
};
|
||||
|
||||
struct pool_disk {
|
||||
uint64_t pl_magic; /* Pool magic number */
|
||||
uint64_t pl_pool_id; /* Unique pool identifier */
|
||||
char pl_pool_name[POOL_NAME_SIZE]; /* Name of pool */
|
||||
uint32_t pl_version; /* Pool version */
|
||||
uint32_t pl_subpools; /* Number of subpools in this pool */
|
||||
uint32_t pl_sp_id; /* Subpool number within pool */
|
||||
uint32_t pl_sp_devs; /* Number of data partitions in this subpool */
|
||||
uint32_t pl_sp_devid; /* Partition number within subpool */
|
||||
uint32_t pl_sp_type; /* Partition type */
|
||||
uint64_t pl_blocks; /* Number of blocks in this partition */
|
||||
uint32_t pl_striping; /* Striping size within subpool */
|
||||
/*
|
||||
* If the number of DMEP devices is zero, then the next field **
|
||||
* ** (pl_sp_dmepid) becomes the subpool ID for redirection. In **
|
||||
* ** other words, if this subpool does not have the capability **
|
||||
* ** to do DMEP, then it must specify which subpool will do it **
|
||||
* ** in it's place
|
||||
*/
|
||||
|
||||
/*
|
||||
* While the next 3 field are no longer used, they must stay to keep **
|
||||
* ** backward compatibility...........................................
|
||||
*/
|
||||
uint32_t pl_sp_dmepdevs;/* Number of dmep devices in this subpool */
|
||||
uint32_t pl_sp_dmepid; /* Dmep device number within subpool */
|
||||
uint32_t pl_sp_weight; /* if dmep dev, pref to using it */
|
||||
|
||||
uint32_t pl_minor; /* the pool minor number */
|
||||
uint32_t pl_padding; /* reminder - think about alignment */
|
||||
|
||||
/*
|
||||
* Even though we're zeroing out 8k at the front of the disk before
|
||||
* writing the label, putting this in
|
||||
*/
|
||||
char pl_reserve[184]; /* bump the structure size out to 512 bytes */
|
||||
};
|
||||
|
||||
struct pool_list {
|
||||
struct list list;
|
||||
struct pool_disk pd;
|
||||
struct physical_volume *pv;
|
||||
struct id pv_uuid;
|
||||
struct device *dev;
|
||||
};
|
||||
|
||||
struct user_subpool {
|
||||
uint32_t initialized;
|
||||
uint32_t id;
|
||||
uint32_t striping;
|
||||
uint32_t num_devs;
|
||||
uint32_t type;
|
||||
uint32_t dummy;
|
||||
struct user_device *devs;
|
||||
};
|
||||
|
||||
struct user_device {
|
||||
uint32_t initialized;
|
||||
uint32_t sp_id;
|
||||
uint32_t devid;
|
||||
uint32_t dummy;
|
||||
uint64_t blocks;
|
||||
struct physical_volume *pv;
|
||||
};
|
||||
|
||||
int read_pool_label(struct pool_list *pl, struct labeller *l,
|
||||
struct device *dev, char *buf, struct label **label);
|
||||
void pool_label_out(struct pool_disk *pl, char *buf);
|
||||
void pool_label_in(struct pool_disk *pl, char *buf);
|
||||
void get_pool_uuid(char *uuid, uint64_t poolid, uint32_t spid, uint32_t devid);
|
||||
int import_pool_vg(struct volume_group *vg, struct pool *mem, struct list *pls);
|
||||
int import_pool_lvs(struct volume_group *vg, struct pool *mem,
|
||||
struct list *pls);
|
||||
int import_pool_pvs(const struct format_type *fmt, struct volume_group *vg,
|
||||
struct list *pvs, struct pool *mem, struct list *pls);
|
||||
int import_pool_pv(const struct format_type *fmt, struct pool *mem,
|
||||
struct volume_group *vg, struct physical_volume *pv,
|
||||
struct pool_list *pl);
|
||||
int import_pool_segments(struct list *lvs, struct pool *mem,
|
||||
struct user_subpool *usp, int sp_count);
|
||||
int read_pool_pds(const struct format_type *fmt, const char *vgname,
|
||||
struct pool *mem, struct list *head);
|
||||
struct pool_list *read_pool_disk(const struct format_type *fmt,
|
||||
struct device *dev, struct pool *mem,
|
||||
const char *vg_name);
|
||||
|
||||
#endif /* DISK_REP_POOL_FORMAT_H */
|
361
lib/format_pool/format_pool.c
Normal file
361
lib/format_pool/format_pool.c
Normal file
@@ -0,0 +1,361 @@
|
||||
/*
|
||||
* Copyright (C) 1997-2004 Sistina Software, Inc. All rights reserved.
|
||||
* Copyright (C) 2004 Red Hat, Inc. All rights reserved.
|
||||
*
|
||||
* This file is part of LVM2.
|
||||
*
|
||||
* This copyrighted material is made available to anyone wishing to use,
|
||||
* modify, copy, or redistribute it subject to the terms and conditions
|
||||
* of the GNU General Public License v.2.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software Foundation,
|
||||
* Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
*/
|
||||
|
||||
#include "lib.h"
|
||||
#include "pool.h"
|
||||
#include "label.h"
|
||||
#include "metadata.h"
|
||||
#include "hash.h"
|
||||
#include "limits.h"
|
||||
#include "list.h"
|
||||
#include "display.h"
|
||||
#include "toolcontext.h"
|
||||
#include "lvmcache.h"
|
||||
#include "disk_rep.h"
|
||||
#include "format_pool.h"
|
||||
#include "pool_label.h"
|
||||
|
||||
#define FMT_POOL_NAME "pool"
|
||||
|
||||
/* Must be called after pvs are imported */
|
||||
static struct user_subpool *_build_usp(struct list *pls, struct pool *mem,
|
||||
int *sps)
|
||||
{
|
||||
|
||||
struct list *plhs;
|
||||
struct pool_list *pl;
|
||||
struct user_subpool *usp = NULL, *cur_sp = NULL;
|
||||
struct user_device *cur_dev = NULL;
|
||||
|
||||
/*
|
||||
* FIXME: Need to do some checks here - I'm tempted to add a
|
||||
* user_pool structure and build the entire thing to check against.
|
||||
*/
|
||||
list_iterate(plhs, pls) {
|
||||
pl = list_item(plhs, struct pool_list);
|
||||
|
||||
*sps = pl->pd.pl_subpools;
|
||||
if (!usp && (!(usp = pool_zalloc(mem, sizeof(*usp) * (*sps))))) {
|
||||
log_error("Unable to allocate %d subpool structures",
|
||||
*sps);
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (cur_sp != &usp[pl->pd.pl_sp_id]) {
|
||||
cur_sp = &usp[pl->pd.pl_sp_id];
|
||||
|
||||
cur_sp->id = pl->pd.pl_sp_id;
|
||||
cur_sp->striping = pl->pd.pl_striping;
|
||||
cur_sp->num_devs = pl->pd.pl_sp_devs;
|
||||
cur_sp->type = pl->pd.pl_sp_type;
|
||||
cur_sp->initialized = 1;
|
||||
}
|
||||
|
||||
if (!cur_sp->devs &&
|
||||
(!(cur_sp->devs =
|
||||
pool_zalloc(mem,
|
||||
sizeof(*usp->devs) * pl->pd.pl_sp_devs)))) {
|
||||
|
||||
log_error("Unable to allocate %d pool_device "
|
||||
"structures", pl->pd.pl_sp_devs);
|
||||
return 0;
|
||||
}
|
||||
cur_dev = &cur_sp->devs[pl->pd.pl_sp_devid];
|
||||
cur_dev->sp_id = cur_sp->id;
|
||||
cur_dev->devid = pl->pd.pl_sp_id;
|
||||
cur_dev->blocks = pl->pd.pl_blocks;
|
||||
cur_dev->pv = pl->pv;
|
||||
cur_dev->initialized = 1;
|
||||
|
||||
}
|
||||
|
||||
return usp;
|
||||
}
|
||||
|
||||
static int _check_usp(char *vgname, struct user_subpool *usp, int sp_count)
|
||||
{
|
||||
int i, j;
|
||||
|
||||
for (i = 0; i < sp_count; i++) {
|
||||
if (!usp[i].initialized) {
|
||||
log_error("Missing subpool %d in pool %s", i, vgname);
|
||||
return 0;
|
||||
}
|
||||
for (j = 0; j < usp[i].num_devs; j++) {
|
||||
if (!usp[i].devs[j].initialized) {
|
||||
log_error("Missing device %d for subpool %d"
|
||||
" in pool %s", j, i, vgname);
|
||||
return 0;
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
return 1;
|
||||
}
|
||||
|
||||
static struct volume_group *_build_vg_from_pds(struct format_instance
|
||||
*fid, struct pool *mem,
|
||||
struct list *pds)
|
||||
{
|
||||
struct pool *smem = fid->fmt->cmd->mem;
|
||||
struct volume_group *vg = NULL;
|
||||
struct user_subpool *usp = NULL;
|
||||
int sp_count;
|
||||
|
||||
if (!(vg = pool_zalloc(smem, sizeof(*vg)))) {
|
||||
log_error("Unable to allocate volume group structure");
|
||||
return NULL;
|
||||
}
|
||||
|
||||
vg->cmd = fid->fmt->cmd;
|
||||
vg->fid = fid;
|
||||
vg->name = NULL;
|
||||
vg->status = 0;
|
||||
vg->extent_count = 0;
|
||||
vg->pv_count = 0;
|
||||
vg->lv_count = 0;
|
||||
vg->snapshot_count = 0;
|
||||
vg->seqno = 1;
|
||||
vg->system_id = NULL;
|
||||
list_init(&vg->pvs);
|
||||
list_init(&vg->lvs);
|
||||
list_init(&vg->snapshots);
|
||||
list_init(&vg->tags);
|
||||
|
||||
if (!import_pool_vg(vg, smem, pds)) {
|
||||
stack;
|
||||
return NULL;
|
||||
}
|
||||
|
||||
if (!import_pool_pvs(fid->fmt, vg, &vg->pvs, smem, pds)) {
|
||||
stack;
|
||||
return NULL;
|
||||
}
|
||||
|
||||
if (!import_pool_lvs(vg, smem, pds)) {
|
||||
stack;
|
||||
return NULL;
|
||||
}
|
||||
|
||||
/*
|
||||
* I need an intermediate subpool structure that contains all the
|
||||
* relevant info for this. Then i can iterate through the subpool
|
||||
* structures for checking, and create the segments
|
||||
*/
|
||||
if (!(usp = _build_usp(pds, mem, &sp_count))) {
|
||||
stack;
|
||||
return NULL;
|
||||
}
|
||||
|
||||
/*
|
||||
* check the subpool structures - we can't handle partial VGs in
|
||||
* the pool format, so this will error out if we're missing PVs
|
||||
*/
|
||||
if (!_check_usp(vg->name, usp, sp_count)) {
|
||||
stack;
|
||||
return NULL;
|
||||
}
|
||||
|
||||
if (!import_pool_segments(&vg->lvs, smem, usp, sp_count)) {
|
||||
stack;
|
||||
return NULL;
|
||||
}
|
||||
|
||||
return vg;
|
||||
}
|
||||
|
||||
static struct volume_group *_vg_read(struct format_instance *fid,
|
||||
const char *vg_name,
|
||||
struct metadata_area *mda)
|
||||
{
|
||||
struct pool *mem = pool_create(1024);
|
||||
struct list pds;
|
||||
struct volume_group *vg = NULL;
|
||||
|
||||
list_init(&pds);
|
||||
|
||||
/* We can safely ignore the mda passed in */
|
||||
|
||||
if (!mem) {
|
||||
stack;
|
||||
return NULL;
|
||||
}
|
||||
|
||||
/* Strip dev_dir if present */
|
||||
vg_name = strip_dir(vg_name, fid->fmt->cmd->dev_dir);
|
||||
|
||||
/* Read all the pvs in the vg */
|
||||
if (!read_pool_pds(fid->fmt, vg_name, mem, &pds)) {
|
||||
stack;
|
||||
goto out;
|
||||
}
|
||||
|
||||
/* Do the rest of the vg stuff */
|
||||
if (!(vg = _build_vg_from_pds(fid, mem, &pds))) {
|
||||
stack;
|
||||
goto out;
|
||||
}
|
||||
|
||||
out:
|
||||
pool_destroy(mem);
|
||||
return vg;
|
||||
}
|
||||
|
||||
static int _pv_setup(const struct format_type *fmt,
|
||||
uint64_t pe_start, uint32_t extent_count,
|
||||
uint32_t extent_size,
|
||||
int pvmetadatacopies,
|
||||
uint64_t pvmetadatasize, struct list *mdas,
|
||||
struct physical_volume *pv, struct volume_group *vg)
|
||||
{
|
||||
return 1;
|
||||
}
|
||||
|
||||
static int _pv_read(const struct format_type *fmt, const char *pv_name,
|
||||
struct physical_volume *pv, struct list *mdas)
|
||||
{
|
||||
struct pool *mem = pool_create(1024);
|
||||
struct pool_list *pl;
|
||||
struct device *dev;
|
||||
int r = 0;
|
||||
|
||||
log_very_verbose("Reading physical volume data %s from disk", pv_name);
|
||||
|
||||
if (!mem) {
|
||||
stack;
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (!(dev = dev_cache_get(pv_name, fmt->cmd->filter))) {
|
||||
stack;
|
||||
goto out;
|
||||
}
|
||||
|
||||
/*
|
||||
* I need to read the disk and populate a pv structure here
|
||||
* I'll probably need to abstract some of this later for the
|
||||
* vg_read code
|
||||
*/
|
||||
if (!(pl = read_pool_disk(fmt, dev, mem, NULL))) {
|
||||
stack;
|
||||
goto out;
|
||||
}
|
||||
|
||||
if (!import_pool_pv(fmt, fmt->cmd->mem, NULL, pv, pl)) {
|
||||
stack;
|
||||
goto out;
|
||||
}
|
||||
|
||||
pv->fmt = fmt;
|
||||
|
||||
r = 1;
|
||||
|
||||
out:
|
||||
pool_destroy(mem);
|
||||
return r;
|
||||
}
|
||||
|
||||
/* *INDENT-OFF* */
|
||||
static struct metadata_area_ops _metadata_format_pool_ops = {
|
||||
vg_read:_vg_read,
|
||||
};
|
||||
/* *INDENT-ON* */
|
||||
|
||||
static struct format_instance *_create_instance(const struct format_type *fmt,
|
||||
const char *vgname,
|
||||
void *private)
|
||||
{
|
||||
struct format_instance *fid;
|
||||
struct metadata_area *mda;
|
||||
|
||||
if (!(fid = pool_zalloc(fmt->cmd->mem, sizeof(*fid)))) {
|
||||
log_error("Unable to allocate format instance structure for "
|
||||
"pool format");
|
||||
return NULL;
|
||||
}
|
||||
|
||||
fid->fmt = fmt;
|
||||
list_init(&fid->metadata_areas);
|
||||
|
||||
/* Define a NULL metadata area */
|
||||
if (!(mda = pool_zalloc(fmt->cmd->mem, sizeof(*mda)))) {
|
||||
log_error("Unable to allocate metadata area structure "
|
||||
"for pool format");
|
||||
pool_free(fmt->cmd->mem, fid);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
mda->ops = &_metadata_format_pool_ops;
|
||||
mda->metadata_locn = NULL;
|
||||
list_add(&fid->metadata_areas, &mda->list);
|
||||
|
||||
return fid;
|
||||
}
|
||||
|
||||
static void _destroy_instance(struct format_instance *fid)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
static void _destroy(const struct format_type *fmt)
|
||||
{
|
||||
dbg_free((void *) fmt);
|
||||
}
|
||||
|
||||
/* *INDENT-OFF* */
|
||||
static struct format_handler _format_pool_ops = {
|
||||
pv_read:_pv_read,
|
||||
pv_setup:_pv_setup,
|
||||
create_instance:_create_instance,
|
||||
destroy_instance:_destroy_instance,
|
||||
destroy:_destroy,
|
||||
};
|
||||
/* *INDENT-ON */
|
||||
|
||||
#ifdef POOL_INTERNAL
|
||||
struct format_type *init_pool_format(struct cmd_context *cmd)
|
||||
#else /* Shared */
|
||||
struct format_type *init_format(struct cmd_context *cmd);
|
||||
struct format_type *init_format(struct cmd_context *cmd)
|
||||
#endif
|
||||
{
|
||||
struct format_type *fmt = dbg_malloc(sizeof(*fmt));
|
||||
|
||||
if (!fmt) {
|
||||
log_error("Unable to allocate format type structure for pool "
|
||||
"format");
|
||||
return NULL;
|
||||
}
|
||||
|
||||
fmt->cmd = cmd;
|
||||
fmt->ops = &_format_pool_ops;
|
||||
fmt->name = FMT_POOL_NAME;
|
||||
fmt->alias = NULL;
|
||||
fmt->features = 0;
|
||||
fmt->private = NULL;
|
||||
|
||||
if (!(fmt->labeller = pool_labeller_create(fmt))) {
|
||||
log_error("Couldn't create pool label handler.");
|
||||
return NULL;
|
||||
}
|
||||
|
||||
if (!(label_register_handler(FMT_POOL_NAME, fmt->labeller))) {
|
||||
log_error("Couldn't register pool label handler.");
|
||||
return NULL;
|
||||
}
|
||||
|
||||
return fmt;
|
||||
}
|
25
lib/format_pool/format_pool.h
Normal file
25
lib/format_pool/format_pool.h
Normal file
@@ -0,0 +1,25 @@
|
||||
/*
|
||||
* Copyright (C) 2003-2004 Sistina Software, Inc. All rights reserved.
|
||||
* Copyright (C) 2004 Red Hat, Inc. All rights reserved.
|
||||
*
|
||||
* This file is part of LVM2.
|
||||
*
|
||||
* This copyrighted material is made available to anyone wishing to use,
|
||||
* modify, copy, or redistribute it subject to the terms and conditions
|
||||
* of the GNU General Public License v.2.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software Foundation,
|
||||
* Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
*/
|
||||
|
||||
#ifndef _LVM_FORMAT_POOL_H
|
||||
#define _LVM_FORMAT_POOL_H
|
||||
|
||||
#include "metadata.h"
|
||||
|
||||
#ifdef POOL_INTERNAL
|
||||
struct format_type *init_pool_format(struct cmd_context *cmd);
|
||||
#endif
|
||||
|
||||
#endif
|
309
lib/format_pool/import_export.c
Normal file
309
lib/format_pool/import_export.c
Normal file
@@ -0,0 +1,309 @@
|
||||
/*
|
||||
* Copyright (C) 1997-2004 Sistina Software, Inc. All rights reserved.
|
||||
* Copyright (C) 2004 Red Hat, Inc. All rights reserved.
|
||||
*
|
||||
* This file is part of LVM2.
|
||||
*
|
||||
* This copyrighted material is made available to anyone wishing to use,
|
||||
* modify, copy, or redistribute it subject to the terms and conditions
|
||||
* of the GNU General Public License v.2.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software Foundation,
|
||||
* Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
*/
|
||||
|
||||
#include "lib.h"
|
||||
#include "pool.h"
|
||||
#include "label.h"
|
||||
#include "metadata.h"
|
||||
#include "lvmcache.h"
|
||||
#include "disk_rep.h"
|
||||
#include "lv_alloc.h"
|
||||
#include "str_list.h"
|
||||
#include "display.h"
|
||||
#include "segtypes.h"
|
||||
|
||||
/* This file contains only imports at the moment... */
|
||||
|
||||
int import_pool_vg(struct volume_group *vg, struct pool *mem, struct list *pls)
|
||||
{
|
||||
struct list *plhs;
|
||||
struct pool_list *pl;
|
||||
|
||||
list_iterate(plhs, pls) {
|
||||
pl = list_item(plhs, struct pool_list);
|
||||
|
||||
vg->extent_count +=
|
||||
((pl->pd.pl_blocks) / POOL_PE_SIZE);
|
||||
|
||||
vg->pv_count++;
|
||||
|
||||
if (vg->name)
|
||||
continue;
|
||||
|
||||
vg->name = pool_strdup(mem, pl->pd.pl_pool_name);
|
||||
get_pool_vg_uuid(&vg->id, &pl->pd);
|
||||
vg->extent_size = POOL_PE_SIZE;
|
||||
vg->status |= LVM_READ | LVM_WRITE | CLUSTERED | SHARED;
|
||||
vg->free_count = 0;
|
||||
vg->max_lv = 1;
|
||||
vg->max_pv = POOL_MAX_DEVICES;
|
||||
vg->alloc = ALLOC_NORMAL;
|
||||
vg->lv_count = 0;
|
||||
}
|
||||
|
||||
return 1;
|
||||
}
|
||||
|
||||
int import_pool_lvs(struct volume_group *vg, struct pool *mem, struct list *pls)
|
||||
{
|
||||
struct pool_list *pl;
|
||||
struct list *plhs;
|
||||
struct lv_list *lvl = pool_zalloc(mem, sizeof(*lvl));
|
||||
struct logical_volume *lv;
|
||||
|
||||
if (!lvl) {
|
||||
log_error("Unable to allocate lv list structure");
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (!(lvl->lv = pool_zalloc(mem, sizeof(*lvl->lv)))) {
|
||||
log_error("Unable to allocate logical volume structure");
|
||||
return 0;
|
||||
}
|
||||
|
||||
lv = lvl->lv;
|
||||
lv->status = 0;
|
||||
lv->vg = vg;
|
||||
lv->alloc = ALLOC_NORMAL;
|
||||
lv->size = 0;
|
||||
lv->name = NULL;
|
||||
lv->le_count = 0;
|
||||
lv->read_ahead = 0;
|
||||
list_init(&lv->segments);
|
||||
list_init(&lv->tags);
|
||||
|
||||
list_iterate(plhs, pls) {
|
||||
pl = list_item(plhs, struct pool_list);
|
||||
|
||||
lv->size += pl->pd.pl_blocks;
|
||||
|
||||
if (lv->name)
|
||||
continue;
|
||||
|
||||
if (!(lv->name = pool_strdup(mem, pl->pd.pl_pool_name))) {
|
||||
stack;
|
||||
return 0;
|
||||
}
|
||||
|
||||
get_pool_lv_uuid(lv->lvid.id, &pl->pd);
|
||||
log_debug("Calculated lv uuid for lv %s: %s", lv->name,
|
||||
lv->lvid.s);
|
||||
|
||||
lv->status |= VISIBLE_LV | LVM_READ | LVM_WRITE;
|
||||
lv->major = POOL_MAJOR;
|
||||
|
||||
/* for pool a minor of 0 is dynamic */
|
||||
if (pl->pd.pl_minor) {
|
||||
lv->status |= FIXED_MINOR;
|
||||
lv->minor = pl->pd.pl_minor;
|
||||
} else {
|
||||
lv->minor = -1;
|
||||
}
|
||||
list_init(&lv->segments);
|
||||
list_init(&lv->tags);
|
||||
}
|
||||
|
||||
lv->le_count = lv->size / POOL_PE_SIZE;
|
||||
lvl->lv = lv;
|
||||
list_add(&vg->lvs, &lvl->list);
|
||||
vg->lv_count++;
|
||||
|
||||
return 1;
|
||||
}
|
||||
|
||||
int import_pool_pvs(const struct format_type *fmt, struct volume_group *vg,
|
||||
struct list *pvs, struct pool *mem, struct list *pls)
|
||||
{
|
||||
struct pv_list *pvl;
|
||||
struct pool_list *pl;
|
||||
struct list *plhs;
|
||||
|
||||
list_iterate(plhs, pls) {
|
||||
pl = list_item(plhs, struct pool_list);
|
||||
|
||||
if (!(pvl = pool_zalloc(mem, sizeof(*pvl)))) {
|
||||
log_error("Unable to allocate pv list structure");
|
||||
return 0;
|
||||
}
|
||||
if (!(pvl->pv = pool_zalloc(mem, sizeof(*pvl->pv)))) {
|
||||
log_error("Unable to allocate pv structure");
|
||||
return 0;
|
||||
}
|
||||
if (!import_pool_pv(fmt, mem, vg, pvl->pv, pl)) {
|
||||
return 0;
|
||||
}
|
||||
pl->pv = pvl->pv;
|
||||
pvl->mdas = NULL;
|
||||
pvl->alloc_areas = NULL;
|
||||
list_add(pvs, &pvl->list);
|
||||
}
|
||||
|
||||
return 1;
|
||||
}
|
||||
|
||||
int import_pool_pv(const struct format_type *fmt, struct pool *mem,
|
||||
struct volume_group *vg, struct physical_volume *pv,
|
||||
struct pool_list *pl)
|
||||
{
|
||||
struct pool_disk *pd = &pl->pd;
|
||||
|
||||
memset(pv, 0, sizeof(*pv));
|
||||
|
||||
get_pool_pv_uuid(&pv->id, pd);
|
||||
pv->fmt = fmt;
|
||||
|
||||
pv->dev = pl->dev;
|
||||
if (!(pv->vg_name = pool_strdup(mem, pd->pl_pool_name))) {
|
||||
log_error("Unable to duplicate vg_name string");
|
||||
return 0;
|
||||
}
|
||||
pv->status = 0;
|
||||
pv->size = pd->pl_blocks;
|
||||
pv->pe_size = POOL_PE_SIZE;
|
||||
pv->pe_start = POOL_PE_START;
|
||||
pv->pe_count = pv->size / POOL_PE_SIZE;
|
||||
pv->pe_alloc_count = pv->pe_count;
|
||||
|
||||
list_init(&pv->tags);
|
||||
|
||||
return 1;
|
||||
}
|
||||
|
||||
static const char *_cvt_sptype(uint32_t sptype)
|
||||
{
|
||||
int i;
|
||||
for (i = 0; sptype_names[i].name[0]; i++) {
|
||||
if (sptype == sptype_names[i].label) {
|
||||
break;
|
||||
}
|
||||
}
|
||||
log_debug("Found sptype %X and converted it to %s",
|
||||
sptype, sptype_names[i].name);
|
||||
return sptype_names[i].name;
|
||||
}
|
||||
|
||||
static int _add_stripe_seg(struct pool *mem,
|
||||
struct user_subpool *usp, struct logical_volume *lv,
|
||||
uint32_t *le_cur)
|
||||
{
|
||||
struct lv_segment *seg;
|
||||
int j;
|
||||
|
||||
if (!(seg = alloc_lv_segment(mem, usp->num_devs))) {
|
||||
log_error("Unable to allocate striped lv_segment structure");
|
||||
return 0;
|
||||
}
|
||||
if(usp->striping & (usp->striping - 1)) {
|
||||
log_error("Stripe size must be a power of 2");
|
||||
return 0;
|
||||
}
|
||||
seg->stripe_size = usp->striping;
|
||||
seg->status |= 0;
|
||||
seg->le += *le_cur;
|
||||
|
||||
/* add the subpool type to the segment tag list */
|
||||
str_list_add(mem, &seg->tags, _cvt_sptype(usp->type));
|
||||
|
||||
for (j = 0; j < usp->num_devs; j++) {
|
||||
if (!(seg->segtype = get_segtype_from_string(lv->vg->cmd,
|
||||
"striped"))) {
|
||||
stack;
|
||||
return 0;
|
||||
}
|
||||
|
||||
seg->area_len = (usp->devs[j].blocks) / POOL_PE_SIZE;
|
||||
seg->len += seg->area_len;
|
||||
*le_cur += seg->area_len;
|
||||
seg->lv = lv;
|
||||
|
||||
seg->area[j].type = AREA_PV;
|
||||
seg->area[j].u.pv.pv = usp->devs[j].pv;
|
||||
seg->area[j].u.pv.pe = 0;
|
||||
}
|
||||
list_add(&lv->segments, &seg->list);
|
||||
return 1;
|
||||
}
|
||||
|
||||
static int _add_linear_seg(struct pool *mem,
|
||||
struct user_subpool *usp, struct logical_volume *lv,
|
||||
uint32_t *le_cur)
|
||||
{
|
||||
struct lv_segment *seg;
|
||||
int j;
|
||||
|
||||
for (j = 0; j < usp->num_devs; j++) {
|
||||
/* linear segments only have 1 data area */
|
||||
if (!(seg = alloc_lv_segment(mem, 1))) {
|
||||
log_error("Unable to allocate linear lv_segment "
|
||||
"structure");
|
||||
return 0;
|
||||
}
|
||||
seg->stripe_size = usp->striping;
|
||||
seg->le += *le_cur;
|
||||
seg->chunk_size = POOL_PE_SIZE;
|
||||
seg->status |= 0;
|
||||
if (!(seg->segtype = get_segtype_from_string(lv->vg->cmd,
|
||||
"striped"))) {
|
||||
stack;
|
||||
return 0;
|
||||
}
|
||||
/* add the subpool type to the segment tag list */
|
||||
str_list_add(mem, &seg->tags, _cvt_sptype(usp->type));
|
||||
|
||||
seg->lv = lv;
|
||||
|
||||
seg->area_len = (usp->devs[j].blocks) / POOL_PE_SIZE;
|
||||
seg->len = seg->area_len;
|
||||
*le_cur += seg->len;
|
||||
seg->area[0].type = AREA_PV;
|
||||
seg->area[0].u.pv.pv = usp->devs[j].pv;
|
||||
seg->area[0].u.pv.pe = 0;
|
||||
list_add(&lv->segments, &seg->list);
|
||||
}
|
||||
return 1;
|
||||
}
|
||||
|
||||
int import_pool_segments(struct list *lvs, struct pool *mem,
|
||||
struct user_subpool *usp, int subpools)
|
||||
{
|
||||
|
||||
struct list *lvhs;
|
||||
struct lv_list *lvl;
|
||||
struct logical_volume *lv;
|
||||
uint32_t le_cur = 0;
|
||||
int i;
|
||||
|
||||
list_iterate(lvhs, lvs) {
|
||||
lvl = list_item(lvhs, struct lv_list);
|
||||
|
||||
lv = lvl->lv;
|
||||
for (i = 0; i < subpools; i++) {
|
||||
if (usp[i].striping) {
|
||||
if (!_add_stripe_seg(mem, &usp[i], lv, &le_cur)) {
|
||||
stack;
|
||||
return 0;
|
||||
}
|
||||
} else {
|
||||
if (!_add_linear_seg(mem, &usp[i], lv, &le_cur)) {
|
||||
stack;
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return 1;
|
||||
|
||||
}
|
108
lib/format_pool/pool_label.c
Normal file
108
lib/format_pool/pool_label.c
Normal file
@@ -0,0 +1,108 @@
|
||||
/*
|
||||
* Copyright (C) 1997-2004 Sistina Software, Inc. All rights reserved.
|
||||
* Copyright (C) 2004 Red Hat, Inc. All rights reserved.
|
||||
*
|
||||
* This file is part of LVM2.
|
||||
*
|
||||
* This copyrighted material is made available to anyone wishing to use,
|
||||
* modify, copy, or redistribute it subject to the terms and conditions
|
||||
* of the GNU General Public License v.2.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software Foundation,
|
||||
* Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
*/
|
||||
|
||||
#include "lib.h"
|
||||
#include "pool.h"
|
||||
#include "label.h"
|
||||
#include "metadata.h"
|
||||
#include "xlate.h"
|
||||
#include "disk_rep.h"
|
||||
#include "pool_label.h"
|
||||
|
||||
#include <sys/stat.h>
|
||||
#include <fcntl.h>
|
||||
|
||||
static void _not_supported(const char *op)
|
||||
{
|
||||
log_error("The '%s' operation is not supported for the pool labeller.",
|
||||
op);
|
||||
}
|
||||
|
||||
static int _can_handle(struct labeller *l, char *buf, uint64_t sector)
|
||||
{
|
||||
|
||||
struct pool_disk pd;
|
||||
|
||||
/*
|
||||
* POOL label must always be in first sector
|
||||
*/
|
||||
if (sector)
|
||||
return 0;
|
||||
|
||||
pool_label_in(&pd, buf);
|
||||
|
||||
/* can ignore 8 rightmost bits for ondisk format check */
|
||||
if ((pd.pl_magic == POOL_MAGIC) &&
|
||||
(pd.pl_version >> 8 == POOL_VERSION >> 8))
|
||||
return 1;
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int _write(struct label *label, char *buf)
|
||||
{
|
||||
_not_supported("write");
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int _read(struct labeller *l, struct device *dev, char *buf,
|
||||
struct label **label)
|
||||
{
|
||||
struct pool_list pl;
|
||||
|
||||
return read_pool_label(&pl, l, dev, buf, label);
|
||||
}
|
||||
|
||||
static int _initialise_label(struct labeller *l, struct label *label)
|
||||
{
|
||||
strcpy(label->type, "POOL");
|
||||
|
||||
return 1;
|
||||
}
|
||||
|
||||
static void _destroy_label(struct labeller *l, struct label *label)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
static void _destroy(struct labeller *l)
|
||||
{
|
||||
dbg_free(l);
|
||||
}
|
||||
|
||||
struct label_ops _pool_ops = {
|
||||
can_handle:_can_handle,
|
||||
write:_write,
|
||||
read:_read,
|
||||
verify:_can_handle,
|
||||
initialise_label:_initialise_label,
|
||||
destroy_label:_destroy_label,
|
||||
destroy:_destroy
|
||||
};
|
||||
|
||||
struct labeller *pool_labeller_create(struct format_type *fmt)
|
||||
{
|
||||
struct labeller *l;
|
||||
|
||||
if (!(l = dbg_malloc(sizeof(*l)))) {
|
||||
log_error("Couldn't allocate labeller object.");
|
||||
return NULL;
|
||||
}
|
||||
|
||||
l->ops = &_pool_ops;
|
||||
l->private = (const void *) fmt;
|
||||
|
||||
return l;
|
||||
}
|
23
lib/format_pool/pool_label.h
Normal file
23
lib/format_pool/pool_label.h
Normal file
@@ -0,0 +1,23 @@
|
||||
/*
|
||||
* Copyright (C) 1997-2004 Sistina Software, Inc. All rights reserved.
|
||||
* Copyright (C) 2004 Red Hat, Inc. All rights reserved.
|
||||
*
|
||||
* This file is part of LVM2.
|
||||
*
|
||||
* This copyrighted material is made available to anyone wishing to use,
|
||||
* modify, copy, or redistribute it subject to the terms and conditions
|
||||
* of the GNU General Public License v.2.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software Foundation,
|
||||
* Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
*/
|
||||
|
||||
#ifndef _LVM_POOL_LABEL_H
|
||||
#define _LVM_POOL_LABEL_H
|
||||
|
||||
#include "metadata.h"
|
||||
|
||||
struct labeller *pool_labeller_create(struct format_type *fmt);
|
||||
|
||||
#endif
|
@@ -1,7 +1,16 @@
|
||||
/*
|
||||
* Copyright (C) 2001 Sistina Software (UK) Limited.
|
||||
* Copyright (C) 2001-2004 Sistina Software, Inc. All rights reserved.
|
||||
* Copyright (C) 2004 Red Hat, Inc. All rights reserved.
|
||||
*
|
||||
* This file is released under the LGPL.
|
||||
* This file is part of LVM2.
|
||||
*
|
||||
* This copyrighted material is made available to anyone wishing to use,
|
||||
* modify, copy, or redistribute it subject to the terms and conditions
|
||||
* of the GNU General Public License v.2.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software Foundation,
|
||||
* Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
*/
|
||||
|
||||
#include "lib.h"
|
||||
@@ -371,4 +380,3 @@ int backup_list(struct cmd_context *cmd, const char *dir, const char *vgname)
|
||||
|
||||
return 1;
|
||||
}
|
||||
|
||||
|
@@ -1,7 +1,16 @@
|
||||
/*
|
||||
* Copyright (C) 2001 Sistina Software (UK) Limited.
|
||||
* Copyright (C) 2001-2004 Sistina Software, Inc. All rights reserved.
|
||||
* Copyright (C) 2004 Red Hat, Inc. All rights reserved.
|
||||
*
|
||||
* This file is released under the LGPL.
|
||||
* This file is part of LVM2.
|
||||
*
|
||||
* This copyrighted material is made available to anyone wishing to use,
|
||||
* modify, copy, or redistribute it subject to the terms and conditions
|
||||
* of the GNU General Public License v.2.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software Foundation,
|
||||
* Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
*/
|
||||
|
||||
#include "lib.h"
|
||||
@@ -11,6 +20,8 @@
|
||||
#include "pool.h"
|
||||
#include "display.h"
|
||||
#include "lvm-string.h"
|
||||
#include "segtypes.h"
|
||||
#include "text_export.h"
|
||||
|
||||
#include <stdarg.h>
|
||||
#include <time.h>
|
||||
@@ -65,14 +76,6 @@ static void _init(void)
|
||||
/*
|
||||
* Formatting functions.
|
||||
*/
|
||||
static int _out_size(struct formatter *f, uint64_t size, const char *fmt, ...)
|
||||
__attribute__ ((format(printf, 3, 4)));
|
||||
|
||||
static int _out_hint(struct formatter *f, const char *fmt, ...)
|
||||
__attribute__ ((format(printf, 2, 3)));
|
||||
|
||||
static int _out(struct formatter *f, const char *fmt, ...)
|
||||
__attribute__ ((format(printf, 2, 3)));
|
||||
|
||||
#define MAX_INDENT 5
|
||||
static void _inc_indent(struct formatter *f)
|
||||
@@ -197,7 +200,7 @@ static int _sectors_to_units(uint64_t sectors, char *buffer, size_t s)
|
||||
* Appends a comment giving a size in more easily
|
||||
* readable form (eg, 4M instead of 8096).
|
||||
*/
|
||||
static int _out_size(struct formatter *f, uint64_t size, const char *fmt, ...)
|
||||
int out_size(struct formatter *f, uint64_t size, const char *fmt, ...)
|
||||
{
|
||||
char buffer[64];
|
||||
va_list ap;
|
||||
@@ -217,7 +220,7 @@ static int _out_size(struct formatter *f, uint64_t size, const char *fmt, ...)
|
||||
* Appends a comment indicating that the line is
|
||||
* only a hint.
|
||||
*/
|
||||
static int _out_hint(struct formatter *f, const char *fmt, ...)
|
||||
int out_hint(struct formatter *f, const char *fmt, ...)
|
||||
{
|
||||
va_list ap;
|
||||
int r;
|
||||
@@ -232,7 +235,7 @@ static int _out_hint(struct formatter *f, const char *fmt, ...)
|
||||
/*
|
||||
* The normal output function.
|
||||
*/
|
||||
static int _out(struct formatter *f, const char *fmt, ...)
|
||||
int out_text(struct formatter *f, const char *fmt, ...)
|
||||
{
|
||||
va_list ap;
|
||||
int r;
|
||||
@@ -244,8 +247,6 @@ static int _out(struct formatter *f, const char *fmt, ...)
|
||||
return r;
|
||||
}
|
||||
|
||||
#define _outf(args...) do {if (!_out(args)) {stack; return 0;}} while (0)
|
||||
|
||||
static int _print_header(struct formatter *f,
|
||||
struct volume_group *vg, const char *desc)
|
||||
{
|
||||
@@ -253,48 +254,65 @@ static int _print_header(struct formatter *f,
|
||||
|
||||
t = time(NULL);
|
||||
|
||||
_outf(f, "# Generated by LVM2: %s", ctime(&t));
|
||||
_outf(f, CONTENTS_FIELD " = \"" CONTENTS_VALUE "\"");
|
||||
_outf(f, FORMAT_VERSION_FIELD " = %d", FORMAT_VERSION_VALUE);
|
||||
outf(f, "# Generated by LVM2: %s", ctime(&t));
|
||||
outf(f, CONTENTS_FIELD " = \"" CONTENTS_VALUE "\"");
|
||||
outf(f, FORMAT_VERSION_FIELD " = %d", FORMAT_VERSION_VALUE);
|
||||
f->nl(f);
|
||||
|
||||
_outf(f, "description = \"%s\"", desc);
|
||||
outf(f, "description = \"%s\"", desc);
|
||||
f->nl(f);
|
||||
_outf(f, "creation_host = \"%s\"\t# %s %s %s %s %s", _utsname.nodename,
|
||||
_utsname.sysname, _utsname.nodename, _utsname.release,
|
||||
_utsname.version, _utsname.machine);
|
||||
_outf(f, "creation_time = %lu\t# %s", t, ctime(&t));
|
||||
outf(f, "creation_host = \"%s\"\t# %s %s %s %s %s", _utsname.nodename,
|
||||
_utsname.sysname, _utsname.nodename, _utsname.release,
|
||||
_utsname.version, _utsname.machine);
|
||||
outf(f, "creation_time = %lu\t# %s", t, ctime(&t));
|
||||
|
||||
return 1;
|
||||
}
|
||||
|
||||
static int _print_vg(struct formatter *f, struct volume_group *vg)
|
||||
{
|
||||
char buffer[256];
|
||||
char buffer[4096];
|
||||
|
||||
if (!id_write_format(&vg->id, buffer, sizeof(buffer))) {
|
||||
stack;
|
||||
return 0;
|
||||
}
|
||||
|
||||
_outf(f, "id = \"%s\"", buffer);
|
||||
outf(f, "id = \"%s\"", buffer);
|
||||
|
||||
outf(f, "seqno = %u", vg->seqno);
|
||||
|
||||
_outf(f, "seqno = %u", vg->seqno);
|
||||
if (!print_flags(vg->status, VG_FLAGS, buffer, sizeof(buffer))) {
|
||||
stack;
|
||||
return 0;
|
||||
}
|
||||
outf(f, "status = %s", buffer);
|
||||
|
||||
if (!list_empty(&vg->tags)) {
|
||||
if (!print_tags(&vg->tags, buffer, sizeof(buffer))) {
|
||||
stack;
|
||||
return 0;
|
||||
}
|
||||
outf(f, "tags = %s", buffer);
|
||||
}
|
||||
|
||||
_outf(f, "status = %s", buffer);
|
||||
if (vg->system_id && *vg->system_id)
|
||||
_outf(f, "system_id = \"%s\"", vg->system_id);
|
||||
if (!_out_size(f, (uint64_t) vg->extent_size, "extent_size = %u",
|
||||
vg->extent_size)) {
|
||||
outf(f, "system_id = \"%s\"", vg->system_id);
|
||||
|
||||
if (!out_size(f, (uint64_t) vg->extent_size, "extent_size = %u",
|
||||
vg->extent_size)) {
|
||||
stack;
|
||||
return 0;
|
||||
}
|
||||
_outf(f, "max_lv = %u", vg->max_lv);
|
||||
_outf(f, "max_pv = %u", vg->max_pv);
|
||||
outf(f, "max_lv = %u", vg->max_lv);
|
||||
outf(f, "max_pv = %u", vg->max_pv);
|
||||
|
||||
/* Default policy is NORMAL; INHERIT is meaningless */
|
||||
if (vg->alloc != ALLOC_NORMAL && vg->alloc != ALLOC_INHERIT) {
|
||||
f->nl(f);
|
||||
outf(f, "allocation_policy = \"%s\"",
|
||||
get_alloc_string(vg->alloc));
|
||||
}
|
||||
|
||||
return 1;
|
||||
}
|
||||
@@ -314,10 +332,10 @@ static int _print_pvs(struct formatter *f, struct volume_group *vg)
|
||||
{
|
||||
struct list *pvh;
|
||||
struct physical_volume *pv;
|
||||
char buffer[256];
|
||||
char buffer[4096];
|
||||
const char *name;
|
||||
|
||||
_outf(f, "physical_volumes {");
|
||||
outf(f, "physical_volumes {");
|
||||
_inc_indent(f);
|
||||
|
||||
list_iterate(pvh, &vg->pvs) {
|
||||
@@ -329,7 +347,7 @@ static int _print_pvs(struct formatter *f, struct volume_group *vg)
|
||||
}
|
||||
|
||||
f->nl(f);
|
||||
_outf(f, "%s {", name);
|
||||
outf(f, "%s {", name);
|
||||
_inc_indent(f);
|
||||
|
||||
if (!id_write_format(&pv->id, buffer, sizeof(buffer))) {
|
||||
@@ -337,8 +355,8 @@ static int _print_pvs(struct formatter *f, struct volume_group *vg)
|
||||
return 0;
|
||||
}
|
||||
|
||||
_outf(f, "id = \"%s\"", buffer);
|
||||
if (!_out_hint(f, "device = \"%s\"", dev_name(pv->dev))) {
|
||||
outf(f, "id = \"%s\"", buffer);
|
||||
if (!out_hint(f, "device = \"%s\"", dev_name(pv->dev))) {
|
||||
stack;
|
||||
return 0;
|
||||
}
|
||||
@@ -348,102 +366,106 @@ static int _print_pvs(struct formatter *f, struct volume_group *vg)
|
||||
stack;
|
||||
return 0;
|
||||
}
|
||||
outf(f, "status = %s", buffer);
|
||||
|
||||
_outf(f, "status = %s", buffer);
|
||||
_outf(f, "pe_start = %" PRIu64, pv->pe_start);
|
||||
if (!_out_size(f, vg->extent_size * (uint64_t) pv->pe_count,
|
||||
"pe_count = %u", pv->pe_count)) {
|
||||
if (!list_empty(&pv->tags)) {
|
||||
if (!print_tags(&pv->tags, buffer, sizeof(buffer))) {
|
||||
stack;
|
||||
return 0;
|
||||
}
|
||||
outf(f, "tags = %s", buffer);
|
||||
}
|
||||
|
||||
outf(f, "pe_start = %" PRIu64, pv->pe_start);
|
||||
if (!out_size(f, vg->extent_size * (uint64_t) pv->pe_count,
|
||||
"pe_count = %u", pv->pe_count)) {
|
||||
stack;
|
||||
return 0;
|
||||
}
|
||||
|
||||
_dec_indent(f);
|
||||
_outf(f, "}");
|
||||
outf(f, "}");
|
||||
}
|
||||
|
||||
_dec_indent(f);
|
||||
_outf(f, "}");
|
||||
outf(f, "}");
|
||||
return 1;
|
||||
}
|
||||
|
||||
static int _print_segment(struct formatter *f, struct volume_group *vg,
|
||||
int count, struct lv_segment *seg)
|
||||
{
|
||||
unsigned int s;
|
||||
const char *name;
|
||||
const char *type;
|
||||
char buffer[4096];
|
||||
|
||||
_outf(f, "segment%u {", count);
|
||||
outf(f, "segment%u {", count);
|
||||
_inc_indent(f);
|
||||
|
||||
_outf(f, "start_extent = %u", seg->le);
|
||||
if (!_out_size(f, (uint64_t) seg->len * vg->extent_size,
|
||||
"extent_count = %u", seg->len)) {
|
||||
outf(f, "start_extent = %u", seg->le);
|
||||
if (!out_size(f, (uint64_t) seg->len * vg->extent_size,
|
||||
"extent_count = %u", seg->len)) {
|
||||
stack;
|
||||
return 0;
|
||||
}
|
||||
|
||||
f->nl(f);
|
||||
_outf(f, "type = \"%s\"", get_segtype_string(seg->type));
|
||||
outf(f, "type = \"%s\"", seg->segtype->name);
|
||||
|
||||
switch (seg->type) {
|
||||
case SEG_SNAPSHOT:
|
||||
_outf(f, "chunk_size = %u", seg->chunk_size);
|
||||
_outf(f, "origin = \"%s\"", seg->origin->name);
|
||||
_outf(f, "cow_store = \"%s\"", seg->cow->name);
|
||||
break;
|
||||
|
||||
case SEG_MIRRORED:
|
||||
case SEG_STRIPED:
|
||||
type = (seg->type == SEG_MIRRORED) ? "mirror" : "stripe";
|
||||
_outf(f, "%s_count = %u%s", type, seg->area_count,
|
||||
(seg->area_count == 1) ? "\t# linear" : "");
|
||||
|
||||
if ((seg->type == SEG_MIRRORED) && (seg->status & PVMOVE))
|
||||
_out_size(f, (uint64_t) seg->extents_moved,
|
||||
"extents_moved = %u", seg->extents_moved);
|
||||
|
||||
if ((seg->type == SEG_STRIPED) && (seg->area_count > 1))
|
||||
_out_size(f, (uint64_t) seg->stripe_size,
|
||||
"stripe_size = %u", seg->stripe_size);
|
||||
|
||||
f->nl(f);
|
||||
|
||||
_outf(f, "%ss = [", type);
|
||||
_inc_indent(f);
|
||||
|
||||
for (s = 0; s < seg->area_count; s++) {
|
||||
switch (seg->area[s].type) {
|
||||
case AREA_PV:
|
||||
if (!(name = _get_pv_name(f, seg->
|
||||
area[s].u.pv.pv))) {
|
||||
stack;
|
||||
return 0;
|
||||
}
|
||||
|
||||
_outf(f, "\"%s\", %u%s", name,
|
||||
seg->area[s].u.pv.pe,
|
||||
(s == seg->area_count - 1) ? "" : ",");
|
||||
break;
|
||||
case AREA_LV:
|
||||
_outf(f, "\"%s\", %u%s",
|
||||
seg->area[s].u.lv.lv->name,
|
||||
seg->area[s].u.lv.le,
|
||||
(s == seg->area_count - 1) ? "" : ",");
|
||||
}
|
||||
if (!list_empty(&seg->tags)) {
|
||||
if (!print_tags(&seg->tags, buffer, sizeof(buffer))) {
|
||||
stack;
|
||||
return 0;
|
||||
}
|
||||
outf(f, "tags = %s", buffer);
|
||||
}
|
||||
|
||||
_dec_indent(f);
|
||||
_outf(f, "]");
|
||||
break;
|
||||
if (seg->segtype->ops->text_export &&
|
||||
!seg->segtype->ops->text_export(seg, f)) {
|
||||
stack;
|
||||
return 0;
|
||||
}
|
||||
|
||||
_dec_indent(f);
|
||||
_outf(f, "}");
|
||||
outf(f, "}");
|
||||
|
||||
return 1;
|
||||
}
|
||||
|
||||
int out_areas(struct formatter *f, const struct lv_segment *seg,
|
||||
const char *type)
|
||||
{
|
||||
const char *name;
|
||||
unsigned int s;
|
||||
|
||||
f->nl(f);
|
||||
|
||||
outf(f, "%ss = [", type);
|
||||
_inc_indent(f);
|
||||
|
||||
for (s = 0; s < seg->area_count; s++) {
|
||||
switch (seg->area[s].type) {
|
||||
case AREA_PV:
|
||||
if (!(name = _get_pv_name(f, seg->area[s].u.pv.pv))) {
|
||||
stack;
|
||||
return 0;
|
||||
}
|
||||
|
||||
outf(f, "\"%s\", %u%s", name,
|
||||
seg->area[s].u.pv.pe,
|
||||
(s == seg->area_count - 1) ? "" : ",");
|
||||
break;
|
||||
case AREA_LV:
|
||||
outf(f, "\"%s\", %u%s",
|
||||
seg->area[s].u.lv.lv->name,
|
||||
seg->area[s].u.lv.le,
|
||||
(s == seg->area_count - 1) ? "" : ",");
|
||||
}
|
||||
}
|
||||
|
||||
_dec_indent(f);
|
||||
outf(f, "]");
|
||||
return 1;
|
||||
}
|
||||
|
||||
static int _count_segments(struct logical_volume *lv)
|
||||
{
|
||||
int r = 0;
|
||||
@@ -463,7 +485,7 @@ static int _print_snapshot(struct formatter *f, struct snapshot *snap,
|
||||
|
||||
f->nl(f);
|
||||
|
||||
_outf(f, "snapshot%u {", count);
|
||||
outf(f, "snapshot%u {", count);
|
||||
_inc_indent(f);
|
||||
|
||||
if (!id_write_format(&snap->id, buffer, sizeof(buffer))) {
|
||||
@@ -471,32 +493,49 @@ static int _print_snapshot(struct formatter *f, struct snapshot *snap,
|
||||
return 0;
|
||||
}
|
||||
|
||||
_outf(f, "id = \"%s\"", buffer);
|
||||
if (!print_flags(LVM_READ | LVM_WRITE | VISIBLE_LV, LV_FLAGS,
|
||||
buffer, sizeof(buffer))) {
|
||||
outf(f, "id = \"%s\"", buffer);
|
||||
|
||||
seg.status = LVM_READ | LVM_WRITE | VISIBLE_LV;
|
||||
if (!print_flags(seg.status, LV_FLAGS, buffer, sizeof(buffer))) {
|
||||
stack;
|
||||
return 0;
|
||||
}
|
||||
|
||||
_outf(f, "status = %s", buffer);
|
||||
_outf(f, "segment_count = 1");
|
||||
outf(f, "status = %s", buffer);
|
||||
outf(f, "segment_count = 1");
|
||||
|
||||
f->nl(f);
|
||||
|
||||
seg.type = SEG_SNAPSHOT;
|
||||
if (!(seg.segtype = get_segtype_from_string(snap->origin->vg->cmd,
|
||||
"snapshot"))) {
|
||||
stack;
|
||||
return 0;
|
||||
}
|
||||
|
||||
seg.le = 0;
|
||||
seg.len = snap->origin->le_count;
|
||||
seg.origin = snap->origin;
|
||||
seg.cow = snap->cow;
|
||||
seg.chunk_size = snap->chunk_size;
|
||||
|
||||
/* FIXME Dummy values */
|
||||
list_init(&seg.list);
|
||||
seg.lv = snap->cow;
|
||||
seg.stripe_size = 0;
|
||||
seg.area_count = 0;
|
||||
seg.area_len = 0;
|
||||
seg.extents_copied = 0;
|
||||
|
||||
/* Can't tag a snapshot independently of its origin */
|
||||
list_init(&seg.tags);
|
||||
|
||||
if (!_print_segment(f, snap->origin->vg, 1, &seg)) {
|
||||
stack;
|
||||
return 0;
|
||||
}
|
||||
|
||||
_dec_indent(f);
|
||||
_outf(f, "}");
|
||||
outf(f, "}");
|
||||
|
||||
return 1;
|
||||
}
|
||||
@@ -524,7 +563,7 @@ static int _print_lvs(struct formatter *f, struct volume_group *vg)
|
||||
struct list *lvh;
|
||||
struct logical_volume *lv;
|
||||
struct lv_segment *seg;
|
||||
char buffer[256];
|
||||
char buffer[4096];
|
||||
int seg_count;
|
||||
|
||||
/*
|
||||
@@ -533,14 +572,14 @@ static int _print_lvs(struct formatter *f, struct volume_group *vg)
|
||||
if (list_empty(&vg->lvs))
|
||||
return 1;
|
||||
|
||||
_outf(f, "logical_volumes {");
|
||||
outf(f, "logical_volumes {");
|
||||
_inc_indent(f);
|
||||
|
||||
list_iterate(lvh, &vg->lvs) {
|
||||
lv = list_item(lvh, struct lv_list)->lv;
|
||||
|
||||
f->nl(f);
|
||||
_outf(f, "%s {", lv->name);
|
||||
outf(f, "%s {", lv->name);
|
||||
_inc_indent(f);
|
||||
|
||||
/* FIXME: Write full lvid */
|
||||
@@ -549,24 +588,33 @@ static int _print_lvs(struct formatter *f, struct volume_group *vg)
|
||||
return 0;
|
||||
}
|
||||
|
||||
_outf(f, "id = \"%s\"", buffer);
|
||||
outf(f, "id = \"%s\"", buffer);
|
||||
|
||||
if (!print_flags(lv->status, LV_FLAGS, buffer, sizeof(buffer))) {
|
||||
stack;
|
||||
return 0;
|
||||
}
|
||||
outf(f, "status = %s", buffer);
|
||||
|
||||
if (!list_empty(&lv->tags)) {
|
||||
if (!print_tags(&lv->tags, buffer, sizeof(buffer))) {
|
||||
stack;
|
||||
return 0;
|
||||
}
|
||||
outf(f, "tags = %s", buffer);
|
||||
}
|
||||
|
||||
if (lv->alloc != ALLOC_INHERIT)
|
||||
outf(f, "allocation_policy = \"%s\"",
|
||||
get_alloc_string(lv->alloc));
|
||||
|
||||
_outf(f, "status = %s", buffer);
|
||||
if (lv->alloc != ALLOC_DEFAULT)
|
||||
_outf(f, "allocation_policy = \"%s\"",
|
||||
get_alloc_string(lv->alloc));
|
||||
if (lv->read_ahead)
|
||||
_outf(f, "read_ahead = %u", lv->read_ahead);
|
||||
outf(f, "read_ahead = %u", lv->read_ahead);
|
||||
if (lv->major >= 0)
|
||||
_outf(f, "major = %d", lv->major);
|
||||
outf(f, "major = %d", lv->major);
|
||||
if (lv->minor >= 0)
|
||||
_outf(f, "minor = %d", lv->minor);
|
||||
_outf(f, "segment_count = %u", _count_segments(lv));
|
||||
outf(f, "minor = %d", lv->minor);
|
||||
outf(f, "segment_count = %u", _count_segments(lv));
|
||||
f->nl(f);
|
||||
|
||||
seg_count = 1;
|
||||
@@ -578,7 +626,7 @@ static int _print_lvs(struct formatter *f, struct volume_group *vg)
|
||||
}
|
||||
|
||||
_dec_indent(f);
|
||||
_outf(f, "}");
|
||||
outf(f, "}");
|
||||
}
|
||||
|
||||
if (!_print_snapshots(f, vg)) {
|
||||
@@ -587,7 +635,7 @@ static int _print_lvs(struct formatter *f, struct volume_group *vg)
|
||||
}
|
||||
|
||||
_dec_indent(f);
|
||||
_outf(f, "}");
|
||||
outf(f, "}");
|
||||
|
||||
return 1;
|
||||
}
|
||||
@@ -660,7 +708,7 @@ static int _text_vg_export(struct formatter *f,
|
||||
if (f->header && !_print_header(f, vg, desc))
|
||||
fail;
|
||||
|
||||
if (!_out(f, "%s {", vg->name))
|
||||
if (!out_text(f, "%s {", vg->name))
|
||||
fail;
|
||||
|
||||
_inc_indent(f);
|
||||
@@ -677,7 +725,7 @@ static int _text_vg_export(struct formatter *f,
|
||||
fail;
|
||||
|
||||
_dec_indent(f);
|
||||
if (!_out(f, "}"))
|
||||
if (!out_text(f, "}"))
|
||||
fail;
|
||||
|
||||
if (!f->header && !_print_header(f, vg, desc))
|
||||
@@ -757,4 +805,4 @@ int text_vg_export_raw(struct volume_group *vg, const char *desc, char *buf,
|
||||
return r;
|
||||
}
|
||||
|
||||
#undef _outf
|
||||
#undef outf
|
||||
|
@@ -1,7 +1,16 @@
|
||||
/*
|
||||
* Copyright (C) 2001 Sistina Software (UK) Limited.
|
||||
* Copyright (C) 2001-2004 Sistina Software, Inc. All rights reserved.
|
||||
* Copyright (C) 2004 Red Hat, Inc. All rights reserved.
|
||||
*
|
||||
* This file is released under the LGPL.
|
||||
* This file is part of LVM2.
|
||||
*
|
||||
* This copyrighted material is made available to anyone wishing to use,
|
||||
* modify, copy, or redistribute it subject to the terms and conditions
|
||||
* of the GNU General Public License v.2.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software Foundation,
|
||||
* Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
*/
|
||||
|
||||
#include "lib.h"
|
||||
@@ -43,6 +52,8 @@ static struct flag _lv_flags[] = {
|
||||
{VISIBLE_LV, "VISIBLE"},
|
||||
{PVMOVE, "PVMOVE"},
|
||||
{LOCKED, "LOCKED"},
|
||||
{MIRRORED, NULL},
|
||||
{VIRTUAL, NULL},
|
||||
{0, NULL}
|
||||
};
|
||||
|
||||
@@ -83,18 +94,21 @@ int print_flags(uint32_t status, int type, char *buffer, size_t size)
|
||||
|
||||
for (f = 0; flags[f].mask; f++) {
|
||||
if (status & flags[f].mask) {
|
||||
status &= ~flags[f].mask;
|
||||
|
||||
/* Internal-only flag? */
|
||||
if (!flags[f].description)
|
||||
continue;
|
||||
|
||||
if (!first) {
|
||||
if (!emit_to_buffer(&buffer, &size, ", "))
|
||||
return 0;
|
||||
|
||||
} else
|
||||
first = 0;
|
||||
|
||||
|
||||
if (!emit_to_buffer(&buffer, &size, "\"%s\"",
|
||||
flags[f].description))
|
||||
flags[f].description))
|
||||
return 0;
|
||||
|
||||
status &= ~flags[f].mask;
|
||||
}
|
||||
}
|
||||
|
||||
|
@@ -1,7 +1,16 @@
|
||||
/*
|
||||
* Copyright (C) 2001-2002 Sistina Software (UK) Limited.
|
||||
* Copyright (C) 2001-2004 Sistina Software, Inc. All rights reserved.
|
||||
* Copyright (C) 2004 Red Hat, Inc. All rights reserved.
|
||||
*
|
||||
* This file is released under the LGPL.
|
||||
* This file is part of LVM2.
|
||||
*
|
||||
* This copyrighted material is made available to anyone wishing to use,
|
||||
* modify, copy, or redistribute it subject to the terms and conditions
|
||||
* of the GNU General Public License v.2.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software Foundation,
|
||||
* Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
*/
|
||||
|
||||
#include "lib.h"
|
||||
@@ -21,6 +30,7 @@
|
||||
#include "xlate.h"
|
||||
#include "label.h"
|
||||
#include "memlock.h"
|
||||
#include "lvmcache.h"
|
||||
|
||||
#include <unistd.h>
|
||||
#include <sys/file.h>
|
||||
@@ -71,7 +81,7 @@ static int _lv_setup(struct format_instance *fid, struct logical_volume *lv)
|
||||
uint64_t max_size = UINT_MAX;
|
||||
|
||||
if (lv->size > max_size) {
|
||||
char *dummy = display_size(max_size / 2, SIZE_SHORT);
|
||||
char *dummy = display_size(max_size, SIZE_SHORT);
|
||||
log_error("logical volumes cannot be larger than %s", dummy);
|
||||
dbg_free(dummy);
|
||||
return 0;
|
||||
@@ -919,8 +929,7 @@ static int _mda_setup(const struct format_type *fmt,
|
||||
/* FIXME If creating new mdas, wipe them! */
|
||||
if (mda_size1) {
|
||||
if (!add_mda(fmt, fmt->cmd->mem, mdas, pv->dev, start1,
|
||||
mda_size1))
|
||||
return 0;
|
||||
mda_size1)) return 0;
|
||||
|
||||
if (!dev_zero((struct device *) pv->dev, start1,
|
||||
(size_t) (mda_size1 >
|
||||
@@ -967,8 +976,7 @@ static int _mda_setup(const struct format_type *fmt,
|
||||
|
||||
if (mda_size2) {
|
||||
if (!add_mda(fmt, fmt->cmd->mem, mdas, pv->dev, start2,
|
||||
mda_size2))
|
||||
return 0;
|
||||
mda_size2)) return 0;
|
||||
if (!dev_zero(pv->dev, start2,
|
||||
(size_t) (mda_size1 >
|
||||
wipe_size ? wipe_size : mda_size1))) {
|
||||
@@ -1057,8 +1065,7 @@ static int _pv_write(const struct format_type *fmt, struct physical_volume *pv,
|
||||
}
|
||||
}
|
||||
if (!add_da
|
||||
(fmt, NULL, &info->das, pv->pe_start << SECTOR_SHIFT,
|
||||
UINT64_C(0))) {
|
||||
(fmt, NULL, &info->das, pv->pe_start << SECTOR_SHIFT, UINT64_C(0))) {
|
||||
stack;
|
||||
return 0;
|
||||
}
|
||||
@@ -1130,8 +1137,7 @@ static int _add_raw(struct list *raw_list, struct device_area *dev_area)
|
||||
rl = list_item(rlh, struct raw_list);
|
||||
/* FIXME Check size/overlap consistency too */
|
||||
if (rl->dev_area.dev == dev_area->dev &&
|
||||
rl->dev_area.start == dev_area->start)
|
||||
return 1;
|
||||
rl->dev_area.start == dev_area->start) return 1;
|
||||
}
|
||||
|
||||
if (!(rl = dbg_malloc(sizeof(struct raw_list)))) {
|
||||
@@ -1325,11 +1331,10 @@ static int _pv_setup(const struct format_type *fmt,
|
||||
list_item(mdash,
|
||||
struct metadata_area);
|
||||
if (mda2->ops !=
|
||||
&_metadata_text_raw_ops)
|
||||
continue;
|
||||
&_metadata_text_raw_ops) continue;
|
||||
mdac2 =
|
||||
(struct mda_context *) mda2->
|
||||
metadata_locn;
|
||||
(struct mda_context *)
|
||||
mda2->metadata_locn;
|
||||
if (!memcmp
|
||||
(&mdac2->area, &mdac->area,
|
||||
sizeof(mdac->area))) {
|
||||
@@ -1347,8 +1352,7 @@ static int _pv_setup(const struct format_type *fmt,
|
||||
}
|
||||
|
||||
if (!(mdac_new = pool_alloc(fmt->cmd->mem,
|
||||
sizeof(*mdac_new))))
|
||||
{
|
||||
sizeof(*mdac_new)))) {
|
||||
stack;
|
||||
return 0;
|
||||
}
|
||||
@@ -1477,8 +1481,7 @@ static struct format_instance *_create_text_instance(const struct format_type
|
||||
}
|
||||
|
||||
if (!(mdac_new = pool_alloc(fmt->cmd->mem,
|
||||
sizeof(*mdac_new))))
|
||||
{
|
||||
sizeof(*mdac_new)))) {
|
||||
stack;
|
||||
return NULL;
|
||||
}
|
||||
@@ -1584,21 +1587,21 @@ static int _get_config_disk_area(struct cmd_context *cmd,
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (!get_config_uint64(cn, "start_sector", '/', &dev_area.start)) {
|
||||
if (!get_config_uint64(cn, "start_sector", &dev_area.start)) {
|
||||
log_error("Missing start_sector in metadata disk_area section "
|
||||
"of config file");
|
||||
return 0;
|
||||
}
|
||||
dev_area.start <<= SECTOR_SHIFT;
|
||||
|
||||
if (!get_config_uint64(cn, "size", '/', &dev_area.size)) {
|
||||
if (!get_config_uint64(cn, "size", &dev_area.size)) {
|
||||
log_error("Missing size in metadata disk_area section "
|
||||
"of config file");
|
||||
return 0;
|
||||
}
|
||||
dev_area.size <<= SECTOR_SHIFT;
|
||||
|
||||
if (!get_config_str(cn, "id", '/', &id_str)) {
|
||||
if (!get_config_str(cn, "id", &id_str)) {
|
||||
log_error("Missing uuid in metadata disk_area section "
|
||||
"of config file");
|
||||
return 0;
|
||||
@@ -1640,7 +1643,7 @@ struct format_type *create_text_format(struct cmd_context *cmd)
|
||||
fmt->ops = &_text_handler;
|
||||
fmt->name = FMT_TEXT_NAME;
|
||||
fmt->alias = FMT_TEXT_ALIAS;
|
||||
fmt->features = FMT_SEGMENTS | FMT_MDAS;
|
||||
fmt->features = FMT_SEGMENTS | FMT_MDAS | FMT_TAGS | FMT_UNLIMITED_VOLS;
|
||||
|
||||
if (!(mda_lists = dbg_malloc(sizeof(struct mda_lists)))) {
|
||||
log_error("Failed to allocate dir_list");
|
||||
@@ -1663,7 +1666,7 @@ struct format_type *create_text_format(struct cmd_context *cmd)
|
||||
return NULL;
|
||||
}
|
||||
|
||||
if ((cn = find_config_node(cmd->cf->root, "metadata/dirs", '/'))) {
|
||||
if ((cn = find_config_node(cmd->cft->root, "metadata/dirs"))) {
|
||||
for (cv = cn->v; cv; cv = cv->next) {
|
||||
if (cv->type != CFG_STRING) {
|
||||
log_error("Invalid string in config file: "
|
||||
@@ -1679,7 +1682,7 @@ struct format_type *create_text_format(struct cmd_context *cmd)
|
||||
}
|
||||
}
|
||||
|
||||
if (!(cn = find_config_node(cmd->cf->root, "metadata/disk_areas", '/')))
|
||||
if (!(cn = find_config_node(cmd->cft->root, "metadata/disk_areas")))
|
||||
return fmt;
|
||||
|
||||
for (cn = cn->child; cn; cn = cn->sib) {
|
||||
|
@@ -1,7 +1,16 @@
|
||||
/*
|
||||
* Copyright (C) 2001 Sistina Software (UK) Limited.
|
||||
* Copyright (C) 2001-2004 Sistina Software, Inc. All rights reserved.
|
||||
* Copyright (C) 2004 Red Hat, Inc. All rights reserved.
|
||||
*
|
||||
* This file is released under the LGPL.
|
||||
* This file is part of LVM2.
|
||||
*
|
||||
* This copyrighted material is made available to anyone wishing to use,
|
||||
* modify, copy, or redistribute it subject to the terms and conditions
|
||||
* of the GNU General Public License v.2.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software Foundation,
|
||||
* Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
*/
|
||||
|
||||
#ifndef _LVM_FORMAT_TEXT_H
|
||||
|
@@ -1,7 +1,16 @@
|
||||
/*
|
||||
* Copyright (C) 2001 Sistina Software (UK) Limited.
|
||||
* Copyright (C) 2001-2004 Sistina Software, Inc. All rights reserved.
|
||||
* Copyright (C) 2004 Red Hat, Inc. All rights reserved.
|
||||
*
|
||||
* This file is released under the LGPL.
|
||||
* This file is part of LVM2.
|
||||
*
|
||||
* This copyrighted material is made available to anyone wishing to use,
|
||||
* modify, copy, or redistribute it subject to the terms and conditions
|
||||
* of the GNU General Public License v.2.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software Foundation,
|
||||
* Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
*/
|
||||
|
||||
#ifndef _LVM_TEXT_IMPORT_EXPORT_H
|
||||
@@ -46,6 +55,9 @@ struct text_vg_version_ops *text_vg_vsn1_init(void);
|
||||
int print_flags(uint32_t status, int type, char *buffer, size_t size);
|
||||
int read_flags(uint32_t *status, int type, struct config_value *cv);
|
||||
|
||||
int print_tags(struct list *tags, char *buffer, size_t size);
|
||||
int read_tags(struct pool *mem, struct list *tags, struct config_value *cv);
|
||||
|
||||
int text_vg_export_file(struct volume_group *vg, const char *desc, FILE *fp);
|
||||
int text_vg_export_raw(struct volume_group *vg, const char *desc, char *buf,
|
||||
uint32_t size);
|
||||
|
@@ -1,7 +1,16 @@
|
||||
/*
|
||||
* Copyright (C) 2001 Sistina Software (UK) Limited.
|
||||
* Copyright (C) 2001-2004 Sistina Software, Inc. All rights reserved.
|
||||
* Copyright (C) 2004 Red Hat, Inc. All rights reserved.
|
||||
*
|
||||
* This file is released under the LGPL.
|
||||
* This file is part of LVM2.
|
||||
*
|
||||
* This copyrighted material is made available to anyone wishing to use,
|
||||
* modify, copy, or redistribute it subject to the terms and conditions
|
||||
* of the GNU General Public License v.2.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software Foundation,
|
||||
* Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
*/
|
||||
|
||||
#include "lib.h"
|
||||
@@ -26,7 +35,7 @@ struct volume_group *text_vg_import_fd(struct format_instance *fid,
|
||||
time_t *when, char **desc)
|
||||
{
|
||||
struct volume_group *vg = NULL;
|
||||
struct config_tree *cf;
|
||||
struct config_tree *cft;
|
||||
struct text_vg_version_ops **vsn;
|
||||
|
||||
static int _initialised = 0;
|
||||
@@ -40,13 +49,13 @@ struct volume_group *text_vg_import_fd(struct format_instance *fid,
|
||||
*desc = NULL;
|
||||
*when = 0;
|
||||
|
||||
if (!(cf = create_config_tree())) {
|
||||
if (!(cft = create_config_tree(file))) {
|
||||
stack;
|
||||
goto out;
|
||||
}
|
||||
|
||||
if ((!dev && !read_config_file(cf, file)) ||
|
||||
(dev && !read_config_fd(cf, dev, offset, size,
|
||||
if ((!dev && !read_config_file(cft)) ||
|
||||
(dev && !read_config_fd(cft, dev, offset, size,
|
||||
offset2, size2, checksum_fn, checksum))) {
|
||||
log_error("Couldn't read volume group metadata.");
|
||||
goto out;
|
||||
@@ -56,20 +65,20 @@ struct volume_group *text_vg_import_fd(struct format_instance *fid,
|
||||
* Find a set of version functions that can read this file
|
||||
*/
|
||||
for (vsn = &_text_vsn_list[0]; *vsn; vsn++) {
|
||||
if (!(*vsn)->check_version(cf))
|
||||
if (!(*vsn)->check_version(cft))
|
||||
continue;
|
||||
|
||||
if (!(vg = (*vsn)->read_vg(fid, cf))) {
|
||||
if (!(vg = (*vsn)->read_vg(fid, cft))) {
|
||||
stack;
|
||||
goto out;
|
||||
}
|
||||
|
||||
(*vsn)->read_desc(fid->fmt->cmd->mem, cf, when, desc);
|
||||
(*vsn)->read_desc(fid->fmt->cmd->mem, cft, when, desc);
|
||||
break;
|
||||
}
|
||||
|
||||
out:
|
||||
destroy_config_tree(cf);
|
||||
destroy_config_tree(cft);
|
||||
return vg;
|
||||
}
|
||||
|
||||
|
@@ -1,7 +1,16 @@
|
||||
/*
|
||||
* Copyright (C) 2001 Sistina Software (UK) Limited.
|
||||
* Copyright (C) 2001-2004 Sistina Software, Inc. All rights reserved.
|
||||
* Copyright (C) 2004 Red Hat, Inc. All rights reserved.
|
||||
*
|
||||
* This file is released under the LGPL.
|
||||
* This file is part of LVM2.
|
||||
*
|
||||
* This copyrighted material is made available to anyone wishing to use,
|
||||
* modify, copy, or redistribute it subject to the terms and conditions
|
||||
* of the GNU General Public License v.2.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software Foundation,
|
||||
* Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
*/
|
||||
|
||||
#include "lib.h"
|
||||
@@ -13,6 +22,8 @@
|
||||
#include "toolcontext.h"
|
||||
#include "lvmcache.h"
|
||||
#include "lv_alloc.h"
|
||||
#include "segtypes.h"
|
||||
#include "text_import.h"
|
||||
|
||||
typedef int (*section_fn) (struct format_instance * fid, struct pool * mem,
|
||||
struct volume_group * vg, struct config_node * pvn,
|
||||
@@ -20,13 +31,13 @@ typedef int (*section_fn) (struct format_instance * fid, struct pool * mem,
|
||||
struct hash_table * pv_hash);
|
||||
|
||||
#define _read_int32(root, path, result) \
|
||||
get_config_uint32(root, path, '/', result)
|
||||
get_config_uint32(root, path, result)
|
||||
|
||||
#define _read_uint32(root, path, result) \
|
||||
get_config_uint32(root, path, '/', result)
|
||||
get_config_uint32(root, path, result)
|
||||
|
||||
#define _read_int64(root, path, result) \
|
||||
get_config_uint64(root, path, '/', result)
|
||||
get_config_uint64(root, path, result)
|
||||
|
||||
/*
|
||||
* Logs an attempt to read an invalid format file.
|
||||
@@ -40,7 +51,7 @@ static void _invalid_format(const char *str)
|
||||
* Checks that the config file contains vg metadata, and that it
|
||||
* we recognise the version number,
|
||||
*/
|
||||
static int _check_version(struct config_tree *cf)
|
||||
static int _check_version(struct config_tree *cft)
|
||||
{
|
||||
struct config_node *cn;
|
||||
struct config_value *cv;
|
||||
@@ -48,7 +59,7 @@ static int _check_version(struct config_tree *cf)
|
||||
/*
|
||||
* Check the contents field.
|
||||
*/
|
||||
if (!(cn = find_config_node(cf->root, CONTENTS_FIELD, '/'))) {
|
||||
if (!(cn = find_config_node(cft->root, CONTENTS_FIELD))) {
|
||||
_invalid_format("missing contents field");
|
||||
return 0;
|
||||
}
|
||||
@@ -62,7 +73,7 @@ static int _check_version(struct config_tree *cf)
|
||||
/*
|
||||
* Check the version number.
|
||||
*/
|
||||
if (!(cn = find_config_node(cf->root, FORMAT_VERSION_FIELD, '/'))) {
|
||||
if (!(cn = find_config_node(cft->root, FORMAT_VERSION_FIELD))) {
|
||||
_invalid_format("missing version number");
|
||||
return 0;
|
||||
}
|
||||
@@ -80,7 +91,7 @@ static int _read_id(struct id *id, struct config_node *cn, const char *path)
|
||||
{
|
||||
struct config_value *cv;
|
||||
|
||||
if (!(cn = find_config_node(cn, path, '/'))) {
|
||||
if (!(cn = find_config_node(cn, path))) {
|
||||
log_error("Couldn't find uuid.");
|
||||
return 0;
|
||||
}
|
||||
@@ -157,7 +168,7 @@ static int _read_pv(struct format_instance *fid, struct pool *mem,
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (!(cn = find_config_node(pvn, "status", '/'))) {
|
||||
if (!(cn = find_config_node(pvn, "status"))) {
|
||||
log_error("Couldn't find status flags for physical volume.");
|
||||
return 0;
|
||||
}
|
||||
@@ -178,6 +189,16 @@ static int _read_pv(struct format_instance *fid, struct pool *mem,
|
||||
return 0;
|
||||
}
|
||||
|
||||
list_init(&pv->tags);
|
||||
|
||||
/* Optional tags */
|
||||
if ((cn = find_config_node(pvn, "tags")) &&
|
||||
!(read_tags(mem, &pv->tags, cn->v))) {
|
||||
log_error("Couldn't read tags for physical volume %s in %s.",
|
||||
dev_name(pv->dev), vg->name);
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* adjust the volume group. */
|
||||
vg->extent_count += pv->pe_count;
|
||||
vg->free_count += pv->pe_count;
|
||||
@@ -215,17 +236,13 @@ static int _read_segment(struct pool *mem, struct volume_group *vg,
|
||||
struct logical_volume *lv, struct config_node *sn,
|
||||
struct hash_table *pv_hash)
|
||||
{
|
||||
unsigned int s;
|
||||
uint32_t area_count = 0;
|
||||
uint32_t area_count = 0u;
|
||||
struct lv_segment *seg;
|
||||
struct config_node *cn;
|
||||
struct config_value *cv;
|
||||
const char *seg_name = sn->key;
|
||||
uint32_t start_extent, extent_count;
|
||||
uint32_t chunk_size, extents_moved = 0u, seg_status = 0u;
|
||||
const char *org_name, *cow_name;
|
||||
struct logical_volume *org, *cow, *lv1;
|
||||
segment_type_t segtype;
|
||||
struct segment_type *segtype;
|
||||
const char *segtype_str;
|
||||
|
||||
if (!(sn = sn->child)) {
|
||||
log_error("Empty segment section.");
|
||||
@@ -244,40 +261,26 @@ static int _read_segment(struct pool *mem, struct volume_group *vg,
|
||||
return 0;
|
||||
}
|
||||
|
||||
segtype = SEG_STRIPED; /* Default */
|
||||
if ((cn = find_config_node(sn, "type", '/'))) {
|
||||
segtype_str = "striped";
|
||||
|
||||
if ((cn = find_config_node(sn, "type"))) {
|
||||
cv = cn->v;
|
||||
if (!cv || !cv->v.str) {
|
||||
log_error("Segment type must be a string.");
|
||||
return 0;
|
||||
}
|
||||
segtype = get_segtype_from_string(cv->v.str);
|
||||
segtype_str = cv->v.str;
|
||||
}
|
||||
|
||||
if (segtype == SEG_STRIPED) {
|
||||
if (!_read_int32(sn, "stripe_count", &area_count)) {
|
||||
log_error("Couldn't read 'stripe_count' for "
|
||||
"segment '%s'.", sn->key);
|
||||
return 0;
|
||||
}
|
||||
if (!(segtype = get_segtype_from_string(vg->cmd, segtype_str))) {
|
||||
stack;
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (segtype == SEG_MIRRORED) {
|
||||
if (!_read_int32(sn, "mirror_count", &area_count)) {
|
||||
log_error("Couldn't read 'mirror_count' for "
|
||||
"segment '%s'.", sn->key);
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (find_config_node(sn, "extents_moved", '/')) {
|
||||
if (_read_uint32(sn, "extents_moved", &extents_moved))
|
||||
seg_status |= PVMOVE;
|
||||
else {
|
||||
log_error("Couldn't read 'extents_moved' for "
|
||||
"segment '%s'.", sn->key);
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
if (segtype->ops->text_import_area_count &&
|
||||
!segtype->ops->text_import_area_count(sn, &area_count)) {
|
||||
stack;
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (!(seg = alloc_lv_segment(mem, area_count))) {
|
||||
@@ -289,149 +292,107 @@ static int _read_segment(struct pool *mem, struct volume_group *vg,
|
||||
seg->le = start_extent;
|
||||
seg->len = extent_count;
|
||||
seg->area_len = extent_count;
|
||||
seg->type = segtype;
|
||||
seg->status = seg_status;
|
||||
seg->extents_moved = extents_moved;
|
||||
seg->status = 0u;
|
||||
seg->segtype = segtype;
|
||||
seg->extents_copied = 0u;
|
||||
|
||||
switch (segtype) {
|
||||
case SEG_SNAPSHOT:
|
||||
lv->status |= SNAPSHOT;
|
||||
|
||||
if (!_read_uint32(sn, "chunk_size", &chunk_size)) {
|
||||
log_error("Couldn't read chunk size for snapshot.");
|
||||
return 0;
|
||||
}
|
||||
|
||||
log_suppress(1);
|
||||
|
||||
if (!(cow_name = find_config_str(sn, "cow_store", '/', NULL))) {
|
||||
log_suppress(0);
|
||||
log_error("Snapshot cow storage not specified.");
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (!(org_name = find_config_str(sn, "origin", '/', NULL))) {
|
||||
log_suppress(0);
|
||||
log_error("Snapshot origin not specified.");
|
||||
return 0;
|
||||
}
|
||||
|
||||
log_suppress(0);
|
||||
|
||||
if (!(cow = find_lv(vg, cow_name))) {
|
||||
log_error("Unknown logical volume specified for "
|
||||
"snapshot cow store.");
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (!(org = find_lv(vg, org_name))) {
|
||||
log_error("Unknown logical volume specified for "
|
||||
"snapshot origin.");
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (!vg_add_snapshot(org, cow, 1, &lv->lvid.id[1], chunk_size)) {
|
||||
stack;
|
||||
return 0;
|
||||
}
|
||||
break;
|
||||
|
||||
case SEG_STRIPED:
|
||||
if ((area_count != 1) &&
|
||||
!_read_int32(sn, "stripe_size", &seg->stripe_size)) {
|
||||
log_error("Couldn't read stripe_size for segment '%s'.",
|
||||
sn->key);
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (!(cn = find_config_node(sn, "stripes", '/'))) {
|
||||
log_error("Couldn't find stripes array for segment "
|
||||
"'%s'.", sn->key);
|
||||
return 0;
|
||||
}
|
||||
|
||||
seg->area_len /= area_count;
|
||||
|
||||
case SEG_MIRRORED:
|
||||
seg->area_count = area_count;
|
||||
|
||||
if (!seg->area_count) {
|
||||
log_error("Zero areas not allowed for segment '%s'",
|
||||
sn->key);
|
||||
return 0;
|
||||
}
|
||||
|
||||
if ((seg->type == SEG_MIRRORED) &&
|
||||
!(cn = find_config_node(sn, "mirrors", '/'))) {
|
||||
log_error("Couldn't find mirrors array for segment "
|
||||
"'%s'.", sn->key);
|
||||
return 0;
|
||||
}
|
||||
|
||||
for (cv = cn->v, s = 0; cv && s < seg->area_count;
|
||||
s++, cv = cv->next) {
|
||||
|
||||
/* first we read the pv */
|
||||
const char *bad = "Badly formed areas array for "
|
||||
"segment '%s'.";
|
||||
struct physical_volume *pv;
|
||||
|
||||
if (cv->type != CFG_STRING) {
|
||||
log_error(bad, sn->key);
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (!cv->next) {
|
||||
log_error(bad, sn->key);
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (cv->next->type != CFG_INT) {
|
||||
log_error(bad, sn->key);
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* FIXME Cope if LV not yet read in */
|
||||
if ((pv = hash_lookup(pv_hash, cv->v.str))) {
|
||||
seg->area[s].type = AREA_PV;
|
||||
seg->area[s].u.pv.pv = pv;
|
||||
seg->area[s].u.pv.pe = cv->next->v.i;
|
||||
/*
|
||||
* Adjust extent counts in the pv and vg.
|
||||
*/
|
||||
pv->pe_alloc_count += seg->area_len;
|
||||
vg->free_count -= seg->area_len;
|
||||
|
||||
} else if ((lv1 = find_lv(vg, cv->v.str))) {
|
||||
seg->area[s].type = AREA_LV;
|
||||
seg->area[s].u.lv.lv = lv1;
|
||||
seg->area[s].u.lv.le = cv->next->v.i;
|
||||
} else {
|
||||
log_error("Couldn't find volume '%s' "
|
||||
"for segment '%s'.",
|
||||
cv->v.str ? cv->v.str : "NULL",
|
||||
seg_name);
|
||||
return 0;
|
||||
}
|
||||
|
||||
cv = cv->next;
|
||||
}
|
||||
|
||||
/*
|
||||
* Check we read the correct number of stripes.
|
||||
*/
|
||||
if (cv || (s < seg->area_count)) {
|
||||
log_error("Incorrect number of areas in area array "
|
||||
"for segment '%s'.", seg_name);
|
||||
return 0;
|
||||
}
|
||||
if (seg->segtype->ops->text_import &&
|
||||
!seg->segtype->ops->text_import(seg, sn, pv_hash)) {
|
||||
stack;
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* Optional tags */
|
||||
if ((cn = find_config_node(sn, "tags")) &&
|
||||
!(read_tags(mem, &seg->tags, cn->v))) {
|
||||
log_error("Couldn't read tags for a segment of %s/%s.",
|
||||
vg->name, lv->name);
|
||||
return 0;
|
||||
}
|
||||
|
||||
/*
|
||||
* Insert into correct part of segment list.
|
||||
*/
|
||||
_insert_segment(lv, seg);
|
||||
|
||||
if (seg->segtype->flags & SEG_AREAS_MIRRORED)
|
||||
lv->status |= MIRRORED;
|
||||
|
||||
if (seg->segtype->flags & SEG_VIRTUAL)
|
||||
lv->status |= VIRTUAL;
|
||||
|
||||
return 1;
|
||||
}
|
||||
|
||||
int text_import_areas(struct lv_segment *seg, const struct config_node *sn,
|
||||
const struct config_node *cn, struct hash_table *pv_hash)
|
||||
{
|
||||
unsigned int s;
|
||||
struct config_value *cv;
|
||||
struct logical_volume *lv1;
|
||||
const char *seg_name = sn->key;
|
||||
|
||||
if (!seg->area_count) {
|
||||
log_error("Zero areas not allowed for segment '%s'", sn->key);
|
||||
return 0;
|
||||
}
|
||||
|
||||
for (cv = cn->v, s = 0; cv && s < seg->area_count; s++, cv = cv->next) {
|
||||
|
||||
/* first we read the pv */
|
||||
const char *bad = "Badly formed areas array for "
|
||||
"segment '%s'.";
|
||||
struct physical_volume *pv;
|
||||
|
||||
if (cv->type != CFG_STRING) {
|
||||
log_error(bad, sn->key);
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (!cv->next) {
|
||||
log_error(bad, sn->key);
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (cv->next->type != CFG_INT) {
|
||||
log_error(bad, sn->key);
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* FIXME Cope if LV not yet read in */
|
||||
if ((pv = hash_lookup(pv_hash, cv->v.str))) {
|
||||
seg->area[s].type = AREA_PV;
|
||||
seg->area[s].u.pv.pv = pv;
|
||||
seg->area[s].u.pv.pe = cv->next->v.i;
|
||||
/*
|
||||
* Adjust extent counts in the pv and vg.
|
||||
*/
|
||||
pv->pe_alloc_count += seg->area_len;
|
||||
seg->lv->vg->free_count -= seg->area_len;
|
||||
|
||||
} else if ((lv1 = find_lv(seg->lv->vg, cv->v.str))) {
|
||||
seg->area[s].type = AREA_LV;
|
||||
seg->area[s].u.lv.lv = lv1;
|
||||
seg->area[s].u.lv.le = cv->next->v.i;
|
||||
} else {
|
||||
log_error("Couldn't find volume '%s' "
|
||||
"for segment '%s'.",
|
||||
cv->v.str ? cv->v.str : "NULL", seg_name);
|
||||
return 0;
|
||||
}
|
||||
|
||||
cv = cv->next;
|
||||
}
|
||||
|
||||
/*
|
||||
* Check we read the correct number of stripes.
|
||||
*/
|
||||
if (cv || (s < seg->area_count)) {
|
||||
log_error("Incorrect number of areas in area array "
|
||||
"for segment '%s'.", seg_name);
|
||||
return 0;
|
||||
}
|
||||
|
||||
return 1;
|
||||
}
|
||||
|
||||
@@ -518,7 +479,7 @@ static int _read_lvnames(struct format_instance *fid, struct pool *mem,
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (!(cn = find_config_node(lvn, "status", '/'))) {
|
||||
if (!(cn = find_config_node(lvn, "status"))) {
|
||||
log_error("Couldn't find status flags for logical volume.");
|
||||
return 0;
|
||||
}
|
||||
@@ -528,8 +489,8 @@ static int _read_lvnames(struct format_instance *fid, struct pool *mem,
|
||||
return 0;
|
||||
}
|
||||
|
||||
lv->alloc = ALLOC_DEFAULT;
|
||||
if ((cn = find_config_node(lvn, "allocation_policy", '/'))) {
|
||||
lv->alloc = ALLOC_INHERIT;
|
||||
if ((cn = find_config_node(lvn, "allocation_policy"))) {
|
||||
struct config_value *cv = cn->v;
|
||||
if (!cv || !cv->v.str) {
|
||||
log_error("allocation_policy must be a string.");
|
||||
@@ -537,6 +498,10 @@ static int _read_lvnames(struct format_instance *fid, struct pool *mem,
|
||||
}
|
||||
|
||||
lv->alloc = get_alloc_from_string(cv->v.str);
|
||||
if (lv->alloc == ALLOC_INVALID) {
|
||||
stack;
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
|
||||
/* read_ahead defaults to 0 */
|
||||
@@ -544,6 +509,15 @@ static int _read_lvnames(struct format_instance *fid, struct pool *mem,
|
||||
lv->read_ahead = 0;
|
||||
|
||||
list_init(&lv->segments);
|
||||
list_init(&lv->tags);
|
||||
|
||||
/* Optional tags */
|
||||
if ((cn = find_config_node(lvn, "tags")) &&
|
||||
!(read_tags(mem, &lv->tags, cn->v))) {
|
||||
log_error("Couldn't read tags for logical volume %s/%s.",
|
||||
vg->name, lv->name);
|
||||
return 0;
|
||||
}
|
||||
|
||||
lv->vg = vg;
|
||||
vg->lv_count++;
|
||||
@@ -618,7 +592,7 @@ static int _read_sections(struct format_instance *fid,
|
||||
{
|
||||
struct config_node *n;
|
||||
|
||||
if (!(n = find_config_node(vgn, section, '/'))) {
|
||||
if (!(n = find_config_node(vgn, section))) {
|
||||
if (!optional) {
|
||||
log_error("Couldn't find section '%s'.", section);
|
||||
return 0;
|
||||
@@ -638,7 +612,7 @@ static int _read_sections(struct format_instance *fid,
|
||||
}
|
||||
|
||||
static struct volume_group *_read_vg(struct format_instance *fid,
|
||||
struct config_tree *cf)
|
||||
struct config_tree *cft)
|
||||
{
|
||||
struct config_node *vgn, *cn;
|
||||
struct volume_group *vg;
|
||||
@@ -646,7 +620,7 @@ static struct volume_group *_read_vg(struct format_instance *fid,
|
||||
struct pool *mem = fid->fmt->cmd->mem;
|
||||
|
||||
/* skip any top-level values */
|
||||
for (vgn = cf->root; (vgn && vgn->v); vgn = vgn->sib) ;
|
||||
for (vgn = cft->root; (vgn && vgn->v); vgn = vgn->sib) ;
|
||||
|
||||
if (!vgn) {
|
||||
log_error("Couldn't find volume group in file.");
|
||||
@@ -675,7 +649,7 @@ static struct volume_group *_read_vg(struct format_instance *fid,
|
||||
|
||||
vgn = vgn->child;
|
||||
|
||||
if ((cn = find_config_node(vgn, "system_id", '/')) && cn->v) {
|
||||
if ((cn = find_config_node(vgn, "system_id")) && cn->v) {
|
||||
if (!cn->v->v.str) {
|
||||
log_error("system_id must be a string");
|
||||
goto bad;
|
||||
@@ -694,7 +668,7 @@ static struct volume_group *_read_vg(struct format_instance *fid,
|
||||
goto bad;
|
||||
}
|
||||
|
||||
if (!(cn = find_config_node(vgn, "status", '/'))) {
|
||||
if (!(cn = find_config_node(vgn, "status"))) {
|
||||
log_error("Couldn't find status flags for volume group %s.",
|
||||
vg->name);
|
||||
goto bad;
|
||||
@@ -729,6 +703,21 @@ static struct volume_group *_read_vg(struct format_instance *fid,
|
||||
goto bad;
|
||||
}
|
||||
|
||||
vg->alloc = ALLOC_NORMAL;
|
||||
if ((cn = find_config_node(vgn, "allocation_policy"))) {
|
||||
struct config_value *cv = cn->v;
|
||||
if (!cv || !cv->v.str) {
|
||||
log_error("allocation_policy must be a string.");
|
||||
return 0;
|
||||
}
|
||||
|
||||
vg->alloc = get_alloc_from_string(cv->v.str);
|
||||
if (vg->alloc == ALLOC_INVALID) {
|
||||
stack;
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
* The pv hash memoises the pv section names -> pv
|
||||
* structures.
|
||||
@@ -748,6 +737,14 @@ static struct volume_group *_read_vg(struct format_instance *fid,
|
||||
|
||||
list_init(&vg->lvs);
|
||||
list_init(&vg->snapshots);
|
||||
list_init(&vg->tags);
|
||||
|
||||
/* Optional tags */
|
||||
if ((cn = find_config_node(vgn, "tags")) &&
|
||||
!(read_tags(mem, &vg->tags, cn->v))) {
|
||||
log_error("Couldn't read tags for volume group %s.", vg->name);
|
||||
goto bad;
|
||||
}
|
||||
|
||||
if (!_read_sections(fid, "logical_volumes", _read_lvnames, mem, vg,
|
||||
vgn, pv_hash, 1)) {
|
||||
@@ -784,17 +781,17 @@ static struct volume_group *_read_vg(struct format_instance *fid,
|
||||
}
|
||||
|
||||
static void _read_desc(struct pool *mem,
|
||||
struct config_tree *cf, time_t *when, char **desc)
|
||||
struct config_tree *cft, time_t *when, char **desc)
|
||||
{
|
||||
const char *d;
|
||||
unsigned int u = 0u;
|
||||
|
||||
log_suppress(1);
|
||||
d = find_config_str(cf->root, "description", '/', "");
|
||||
d = find_config_str(cft->root, "description", "");
|
||||
log_suppress(0);
|
||||
*desc = pool_strdup(mem, d);
|
||||
|
||||
get_config_uint32(cf->root, "creation_time", '/', &u);
|
||||
get_config_uint32(cft->root, "creation_time", &u);
|
||||
*when = u;
|
||||
}
|
||||
|
||||
|
@@ -1,7 +1,16 @@
|
||||
/*
|
||||
* Copyright (C) 2001 Sistina Software (UK) Limited.
|
||||
* Copyright (C) 2001-2004 Sistina Software, Inc. All rights reserved.
|
||||
* Copyright (C) 2004 Red Hat, Inc. All rights reserved.
|
||||
*
|
||||
* This file is released under the LGPL.
|
||||
* This file is part of LVM2.
|
||||
*
|
||||
* This copyrighted material is made available to anyone wishing to use,
|
||||
* modify, copy, or redistribute it subject to the terms and conditions
|
||||
* of the GNU General Public License v.2.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software Foundation,
|
||||
* Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
*/
|
||||
|
||||
#ifndef _LVM_TEXT_LAYOUT_H
|
||||
|
76
lib/format_text/tags.c
Normal file
76
lib/format_text/tags.c
Normal file
@@ -0,0 +1,76 @@
|
||||
/*
|
||||
* Copyright (C) 2003-2004 Sistina Software, Inc. All rights reserved.
|
||||
* Copyright (C) 2004 Red Hat, Inc. All rights reserved.
|
||||
*
|
||||
* This file is part of LVM2.
|
||||
*
|
||||
* This copyrighted material is made available to anyone wishing to use,
|
||||
* modify, copy, or redistribute it subject to the terms and conditions
|
||||
* of the GNU General Public License v.2.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software Foundation,
|
||||
* Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
*/
|
||||
|
||||
#include "lib.h"
|
||||
#include "metadata.h"
|
||||
#include "import-export.h"
|
||||
#include "pool.h"
|
||||
#include "str_list.h"
|
||||
#include "lvm-string.h"
|
||||
|
||||
int print_tags(struct list *tags, char *buffer, size_t size)
|
||||
{
|
||||
struct str_list *sl;
|
||||
int first = 1;
|
||||
|
||||
if (!emit_to_buffer(&buffer, &size, "[")) {
|
||||
stack;
|
||||
return 0;
|
||||
}
|
||||
|
||||
list_iterate_items(sl, tags) {
|
||||
if (!first) {
|
||||
if (!emit_to_buffer(&buffer, &size, ", ")) {
|
||||
stack;
|
||||
return 0;
|
||||
}
|
||||
} else
|
||||
first = 0;
|
||||
|
||||
if (!emit_to_buffer(&buffer, &size, "\"%s\"", sl->str)) {
|
||||
stack;
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
|
||||
if (!emit_to_buffer(&buffer, &size, "]")) {
|
||||
stack;
|
||||
return 0;
|
||||
}
|
||||
|
||||
return 1;
|
||||
}
|
||||
|
||||
int read_tags(struct pool *mem, struct list *tags, struct config_value *cv)
|
||||
{
|
||||
if (cv->type == CFG_EMPTY_ARRAY)
|
||||
return 1;
|
||||
|
||||
while (cv) {
|
||||
if (cv->type != CFG_STRING) {
|
||||
log_error("Found a tag that is not a string");
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (!str_list_add(mem, tags, pool_strdup(mem, cv->v.str))) {
|
||||
stack;
|
||||
return 0;
|
||||
}
|
||||
|
||||
cv = cv->next;
|
||||
}
|
||||
|
||||
return 1;
|
||||
}
|
36
lib/format_text/text_export.h
Normal file
36
lib/format_text/text_export.h
Normal file
@@ -0,0 +1,36 @@
|
||||
/*
|
||||
* Copyright (C) 2003-2004 Sistina Software, Inc. All rights reserved.
|
||||
* Copyright (C) 2004 Red Hat, Inc. All rights reserved.
|
||||
*
|
||||
* This file is part of LVM2.
|
||||
*
|
||||
* This copyrighted material is made available to anyone wishing to use,
|
||||
* modify, copy, or redistribute it subject to the terms and conditions
|
||||
* of the GNU General Public License v.2.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software Foundation,
|
||||
* Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
*/
|
||||
|
||||
#ifndef _LVM_TEXT_EXPORT_H
|
||||
#define _LVM_TEXT_EXPORT_H
|
||||
|
||||
#define outf(args...) do {if (!out_text(args)) {stack; return 0;}} while (0)
|
||||
|
||||
struct formatter;
|
||||
struct lv_segment;
|
||||
|
||||
int out_size(struct formatter *f, uint64_t size, const char *fmt, ...)
|
||||
__attribute__ ((format(printf, 3, 4)));
|
||||
|
||||
int out_hint(struct formatter *f, const char *fmt, ...)
|
||||
__attribute__ ((format(printf, 2, 3)));
|
||||
|
||||
int out_text(struct formatter *f, const char *fmt, ...)
|
||||
__attribute__ ((format(printf, 2, 3)));
|
||||
|
||||
int out_areas(struct formatter *f, const struct lv_segment *seg,
|
||||
const char *type);
|
||||
|
||||
#endif
|
25
lib/format_text/text_import.h
Normal file
25
lib/format_text/text_import.h
Normal file
@@ -0,0 +1,25 @@
|
||||
/*
|
||||
* Copyright (C) 2003-2004 Sistina Software, Inc. All rights reserved.
|
||||
* Copyright (C) 2004 Red Hat, Inc. All rights reserved.
|
||||
*
|
||||
* This file is part of LVM2.
|
||||
*
|
||||
* This copyrighted material is made available to anyone wishing to use,
|
||||
* modify, copy, or redistribute it subject to the terms and conditions
|
||||
* of the GNU General Public License v.2.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software Foundation,
|
||||
* Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
*/
|
||||
|
||||
#ifndef _LVM_TEXT_IMPORT_H
|
||||
#define _LVM_TEXT_IMPORT_H
|
||||
|
||||
struct lv_segment;
|
||||
struct config_node;
|
||||
|
||||
int text_import_areas(struct lv_segment *seg, const struct config_node *sn,
|
||||
const struct config_node *cn, struct hash_table *pv_hash);
|
||||
|
||||
#endif
|
@@ -1,7 +1,16 @@
|
||||
/*
|
||||
* Copyright (C) 2002 Sistina Software (UK) Limited.
|
||||
* Copyright (C) 2002-2004 Sistina Software, Inc. All rights reserved.
|
||||
* Copyright (C) 2004 Red Hat, Inc. All rights reserved.
|
||||
*
|
||||
* This file is released under the LGPL.
|
||||
* This file is part of LVM2.
|
||||
*
|
||||
* This copyrighted material is made available to anyone wishing to use,
|
||||
* modify, copy, or redistribute it subject to the terms and conditions
|
||||
* of the GNU General Public License v.2.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software Foundation,
|
||||
* Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
*/
|
||||
|
||||
#include "lib.h"
|
||||
@@ -9,6 +18,7 @@
|
||||
#include "layout.h"
|
||||
#include "label.h"
|
||||
#include "xlate.h"
|
||||
#include "lvmcache.h"
|
||||
|
||||
#include <sys/stat.h>
|
||||
#include <fcntl.h>
|
||||
|
@@ -1,7 +1,16 @@
|
||||
/*
|
||||
* Copyright (C) 2002 Sistina Software
|
||||
* Copyright (C) 2002-2004 Sistina Software, Inc. All rights reserved.
|
||||
* Copyright (C) 2004 Red Hat, Inc. All rights reserved.
|
||||
*
|
||||
* This file is released under the LGPL.
|
||||
* This file is part of LVM2.
|
||||
*
|
||||
* This copyrighted material is made available to anyone wishing to use,
|
||||
* modify, copy, or redistribute it subject to the terms and conditions
|
||||
* of the GNU General Public License v.2.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software Foundation,
|
||||
* Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
*/
|
||||
|
||||
#include "lib.h"
|
||||
@@ -10,6 +19,7 @@
|
||||
#include "crc.h"
|
||||
#include "xlate.h"
|
||||
#include "lvmcache.h"
|
||||
#include "metadata.h"
|
||||
|
||||
#include <sys/stat.h>
|
||||
#include <fcntl.h>
|
||||
@@ -69,6 +79,8 @@ void label_exit(void)
|
||||
li->l->ops->destroy(li->l);
|
||||
_free_li(li);
|
||||
}
|
||||
|
||||
list_init(&_labellers);
|
||||
}
|
||||
|
||||
int label_register_handler(const char *name, struct labeller *handler)
|
||||
|
@@ -1,13 +1,21 @@
|
||||
/*
|
||||
* Copyright (C) 2002 Sistina Software (UK) Limited.
|
||||
* Copyright (C) 2002-2004 Sistina Software, Inc. All rights reserved.
|
||||
* Copyright (C) 2004 Red Hat, Inc. All rights reserved.
|
||||
*
|
||||
* This file is released under the LGPL.
|
||||
* This file is part of LVM2.
|
||||
*
|
||||
* This copyrighted material is made available to anyone wishing to use,
|
||||
* modify, copy, or redistribute it subject to the terms and conditions
|
||||
* of the GNU General Public License v.2.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software Foundation,
|
||||
* Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
*/
|
||||
|
||||
#ifndef _LVM_LABEL_H
|
||||
#define _LVM_LABEL_H
|
||||
|
||||
#include "lvmcache.h"
|
||||
#include "uuid.h"
|
||||
#include "device.h"
|
||||
|
||||
@@ -16,6 +24,8 @@
|
||||
#define LABEL_SCAN_SECTORS 4L
|
||||
#define LABEL_SCAN_SIZE (LABEL_SCAN_SECTORS << SECTOR_SHIFT)
|
||||
|
||||
struct labeller;
|
||||
|
||||
/* On disk - 32 bytes */
|
||||
struct label_header {
|
||||
uint8_t id[8]; /* LABELONE */
|
||||
|
@@ -1,8 +1,16 @@
|
||||
/*
|
||||
* Copyright (C) 2002 Sistina Software (UK) Limited.
|
||||
* Copyright (C) 2002-2004 Sistina Software, Inc. All rights reserved.
|
||||
* Copyright (C) 2004 Red Hat, Inc. All rights reserved.
|
||||
*
|
||||
* This file is released under the LGPL.
|
||||
* This file is part of LVM2.
|
||||
*
|
||||
* This copyrighted material is made available to anyone wishing to use,
|
||||
* modify, copy, or redistribute it subject to the terms and conditions
|
||||
* of the GNU General Public License v.2.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software Foundation,
|
||||
* Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
*/
|
||||
|
||||
#include "lib.h"
|
||||
@@ -11,10 +19,12 @@
|
||||
#include "sharedlib.h"
|
||||
|
||||
static void *_locking_lib = NULL;
|
||||
static void (*_reset_fn) (void) = NULL;
|
||||
static void (*_end_fn) (void) = NULL;
|
||||
static int (*_lock_fn) (struct cmd_context * cmd, const char *resource,
|
||||
int flags) = NULL;
|
||||
static int (*_init_fn) (int type, struct config_tree * cf) = NULL;
|
||||
static int (*_init_fn) (int type, struct config_tree * cft,
|
||||
uint32_t *flags) = NULL;
|
||||
|
||||
static int _lock_resource(struct cmd_context *cmd, const char *resource,
|
||||
int flags)
|
||||
@@ -36,9 +46,16 @@ static void _fin_external_locking(void)
|
||||
_init_fn = NULL;
|
||||
_end_fn = NULL;
|
||||
_lock_fn = NULL;
|
||||
_reset_fn = NULL;
|
||||
}
|
||||
|
||||
int init_external_locking(struct locking_type *locking, struct config_tree *cf)
|
||||
static void _reset_external_locking(void)
|
||||
{
|
||||
if (_reset_fn)
|
||||
_reset_fn();
|
||||
}
|
||||
|
||||
int init_external_locking(struct locking_type *locking, struct config_tree *cft)
|
||||
{
|
||||
const char *libname;
|
||||
|
||||
@@ -49,19 +66,22 @@ int init_external_locking(struct locking_type *locking, struct config_tree *cf)
|
||||
|
||||
locking->lock_resource = _lock_resource;
|
||||
locking->fin_locking = _fin_external_locking;
|
||||
locking->reset_locking = _reset_external_locking;
|
||||
locking->flags = 0;
|
||||
|
||||
libname = find_config_str(cf->root, "global/locking_library", '/',
|
||||
libname = find_config_str(cft->root, "global/locking_library",
|
||||
DEFAULT_LOCKING_LIB);
|
||||
|
||||
if (!(_locking_lib = load_shared_library(cf, libname, "locking"))) {
|
||||
if (!(_locking_lib = load_shared_library(cft, libname, "locking"))) {
|
||||
stack;
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* Get the functions we need */
|
||||
if (!(_init_fn = dlsym(_locking_lib, "init_locking")) ||
|
||||
if (!(_init_fn = dlsym(_locking_lib, "locking_init")) ||
|
||||
!(_lock_fn = dlsym(_locking_lib, "lock_resource")) ||
|
||||
!(_end_fn = dlsym(_locking_lib, "end_locking"))) {
|
||||
!(_reset_fn = dlsym(_locking_lib, "reset_locking")) ||
|
||||
!(_end_fn = dlsym(_locking_lib, "locking_end"))) {
|
||||
log_error("Shared library %s does not contain locking "
|
||||
"functions", libname);
|
||||
dlclose(_locking_lib);
|
||||
@@ -70,5 +90,5 @@ int init_external_locking(struct locking_type *locking, struct config_tree *cf)
|
||||
}
|
||||
|
||||
log_verbose("Loaded external locking library %s", libname);
|
||||
return _init_fn(2, cf);
|
||||
return _init_fn(2, cft, &locking->flags);
|
||||
}
|
||||
|
@@ -1,8 +1,16 @@
|
||||
/*
|
||||
* Copyright (C) 2001 Sistina Software (UK) Limited.
|
||||
* Copyright (C) 2001-2004 Sistina Software, Inc. All rights reserved.
|
||||
* Copyright (C) 2004 Red Hat, Inc. All rights reserved.
|
||||
*
|
||||
* This file is released under the LGPL.
|
||||
* This file is part of LVM2.
|
||||
*
|
||||
* This copyrighted material is made available to anyone wishing to use,
|
||||
* modify, copy, or redistribute it subject to the terms and conditions
|
||||
* of the GNU General Public License v.2.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software Foundation,
|
||||
* Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
*/
|
||||
|
||||
#include "lib.h"
|
||||
@@ -224,9 +232,14 @@ static int _file_lock_resource(struct cmd_context *cmd, const char *resource,
|
||||
if (!lv_resume_if_active(cmd, resource))
|
||||
return 0;
|
||||
break;
|
||||
case LCK_NULL:
|
||||
log_debug("Locking LV %s (NL)", resource);
|
||||
if (!lv_deactivate(cmd, resource))
|
||||
return 0;
|
||||
break;
|
||||
case LCK_READ:
|
||||
log_debug("Locking LV %s (R)", resource);
|
||||
if (!lv_activate(cmd, resource))
|
||||
if (!lv_activate_with_filter(cmd, resource))
|
||||
return 0;
|
||||
break;
|
||||
case LCK_WRITE:
|
||||
@@ -236,7 +249,7 @@ static int _file_lock_resource(struct cmd_context *cmd, const char *resource,
|
||||
break;
|
||||
case LCK_EXCL:
|
||||
log_debug("Locking LV %s (EX)", resource);
|
||||
if (!lv_deactivate(cmd, resource))
|
||||
if (!lv_activate_with_filter(cmd, resource))
|
||||
return 0;
|
||||
break;
|
||||
default:
|
||||
@@ -252,15 +265,16 @@ static int _file_lock_resource(struct cmd_context *cmd, const char *resource,
|
||||
return 1;
|
||||
}
|
||||
|
||||
int init_file_locking(struct locking_type *locking, struct config_tree *cf)
|
||||
int init_file_locking(struct locking_type *locking, struct config_tree *cft)
|
||||
{
|
||||
locking->lock_resource = _file_lock_resource;
|
||||
locking->reset_locking = _reset_file_locking;
|
||||
locking->fin_locking = _fin_file_locking;
|
||||
locking->flags = 0;
|
||||
|
||||
/* Get lockfile directory from config file */
|
||||
strncpy(_lock_dir, find_config_str(cf->root, "global/locking_dir",
|
||||
'/', DEFAULT_LOCK_DIR),
|
||||
strncpy(_lock_dir, find_config_str(cft->root, "global/locking_dir",
|
||||
DEFAULT_LOCK_DIR),
|
||||
sizeof(_lock_dir));
|
||||
|
||||
if (!create_dir(_lock_dir))
|
||||
|
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user