From e682b5d1d4d4e3ed8ef022839493d1c18b470503 Mon Sep 17 00:00:00 2001 From: Apple Date: Thu, 18 Nov 2010 02:27:37 +0000 Subject: [PATCH] libutil-25.tar.gz --- Makefile | 42 ++++++++++++++++++--------- humanize_number.c | 36 ++++++++++++++++-------- libutil.exports | 1 + libutil.h | 3 ++ reexec_to_match_kernel.3 | 22 ++++++++++++++- reexec_to_match_kernel.c | 61 +++++++++++++++++++++++++++++++++------- wipefs.cpp | 13 ++++++--- 7 files changed, 138 insertions(+), 40 deletions(-) diff --git a/Makefile b/Makefile index 67173c8..99b4304 100644 --- a/Makefile +++ b/Makefile @@ -1,13 +1,18 @@ SHELL := /bin/sh -SDKROOT ?= / VERSION = 1.0 CC = xcrun cc CPP = xcrun c++ CPPFLAGS = -I$(SRCROOT) -CFLAGS = -Os -g3 -no-cpp-precomp -Wall $(RC_CFLAGS) -isysroot $(SDKROOT) + +ifneq ($(SDKROOT),) +CFLAGS_SDK = -isysroot $(SDKROOT) +LDFLAGS_SDK = -Wl,-syslibroot,$(SDKROOT) +endif + +CFLAGS = -Os -g3 -no-cpp-precomp -Wall $(RC_CFLAGS) $(CFLAGS_SDK) LDFLAGS = $(RC_CFLAGS) -install_name /usr/lib/libutil.dylib -compatibility_version $(VERSION) \ - -current_version $(VERSION) -lstdc++ -exported_symbols_list libutil.exports -isysroot $(SDKROOT) + -current_version $(VERSION) -lstdc++ -exported_symbols_list libutil.exports $(LDFLAGS_SDK) INSTALL = install -c LN = ln MKDIR = mkdir -p @@ -30,6 +35,13 @@ MAN3 := _secure_path.3 getmntopts.3 humanize_number.3 pidfile.3 \ property.3 realhostname.3 realhostname_sa.3 trimdomain.3 \ uucplock.3 wipefs.3 reexec_to_match_kernel.3 +ifeq ($(RC_ProjectName),libutil_Sim) + INSTALL_PREFIX = $(SDKROOT) +else + INSTALL_PREFIX = +endif + + .SUFFIXES : .SUFFIXES : .c .cpp .h .o @@ -55,11 +67,15 @@ installsrc : done installhdrs : - $(INSTALL) -d $(DSTROOT)/usr/local/include - $(INSTALL) -m 0644 $(HDRS) $(DSTROOT)/usr/local/include + $(INSTALL) -d $(DSTROOT)$(INSTALL_PREFIX)/usr/local/include + $(INSTALL) -m 0644 $(HDRS) $(DSTROOT)$(INSTALL_PREFIX)/usr/local/include +ifeq ($(RC_ProjectName),libutil_Sim) +install : installhdrs installlib strip install-plist +else install : installhdrs installlib strip installman install-plist +endif clean : rm -f $(patsubst %.cpp,$(OBJROOT)/%.o,$(patsubst %.c,$(OBJROOT)/%.o,$(SRCS))) @@ -68,16 +84,16 @@ clean : rm -f $(SYMROOT)/$(LIB) strip: - $(STRIP) -x -S $(DSTROOT)/usr/lib/$(LIB) + $(STRIP) -x -S $(DSTROOT)$(INSTALL_PREFIX)/usr/lib/$(LIB) # # Internal targets and rules. # installlib : $(SYMROOT)/$(LIB) $(DSYMUTIL) $(SYMROOT)/$(LIB) -o $(SYMROOT)/$(LIB).dSYM - $(INSTALL) -d $(DSTROOT)/usr/lib - $(INSTALL) -m 0755 $< $(DSTROOT)/usr/lib - $(LN) -fs libutil1.0.dylib $(DSTROOT)/usr/lib/libutil.dylib + $(INSTALL) -d $(DSTROOT)$(INSTALL_PREFIX)/usr/lib + $(INSTALL) -m 0755 $< $(DSTROOT)$(INSTALL_PREFIX)/usr/lib + $(LN) -fs libutil1.0.dylib $(DSTROOT)$(INSTALL_PREFIX)/usr/lib/libutil.dylib installman : $(INSTALL) -d $(DSTROOT)/usr/local/share/man/man3 @@ -97,11 +113,11 @@ $(OBJROOT)/%.o : $(SRCROOT)/%.cpp \ $(SYMROOT)/$(LIB) : $(patsubst %.cpp,$(OBJROOT)/%.o,$(patsubst %.c,$(OBJROOT)/%.o,$(SRCS))) $(CC) -dynamiclib $(LDFLAGS) -o $@ $(patsubst %.cpp,$(OBJROOT)/%.o,$(patsubst %.c,$(OBJROOT)/%.o,$(SRCS))) -OSV = $(DSTROOT)/usr/local/OpenSourceVersions -OSL = $(DSTROOT)/usr/local/OpenSourceLicenses +OSV = $(DSTROOT)$(INSTALL_PREFIX)/usr/local/OpenSourceVersions +OSL = $(DSTROOT)$(INSTALL_PREFIX)/usr/local/OpenSourceLicenses install-plist: $(MKDIR) $(OSV) - $(INSTALL) $(SRCROOT)/libutil.plist $(OSV)/ + $(INSTALL) -m 644 $(SRCROOT)/libutil.plist $(OSV)/ $(MKDIR) $(OSL) - $(INSTALL) $(SRCROOT)/libutil.txt $(OSL)/ + $(INSTALL) -m 644 $(SRCROOT)/libutil.txt $(OSL)/ diff --git a/humanize_number.c b/humanize_number.c index 8ab419b..5f801cf 100644 --- a/humanize_number.c +++ b/humanize_number.c @@ -46,6 +46,8 @@ #include #include #include +#include +#include int humanize_number(char *buf, size_t len, int64_t bytes, @@ -53,7 +55,15 @@ humanize_number(char *buf, size_t len, int64_t bytes, { const char *prefixes, *sep; int b, i, r, maxscale, s1, s2, sign; - int64_t divisor, max; + int64_t divisor, max; + // We multiply bytes by 100 to deal with rounding, so we need something + // big enough to hold LLONG_MAX * 100. On 64-bit we can use 128-bit wide + // integers with __int128_t, but on 32-bit we have to use long double. +#ifdef __LP64__ + __int128_t scalable = (__int128_t)bytes; +#else + long double scalable = (long double)bytes; +#endif size_t baselen; assert(buf != NULL); @@ -93,11 +103,11 @@ humanize_number(char *buf, size_t len, int64_t bytes, buf[0] = '\0'; if (bytes < 0) { sign = -1; - bytes *= -100; + scalable *= -100; baselen = 3; /* sign, digit, prefix */ } else { sign = 1; - bytes *= 100; + scalable *= 100; baselen = 2; /* digit, prefix */ } if (flags & HN_NOSPACE) @@ -117,30 +127,32 @@ humanize_number(char *buf, size_t len, int64_t bytes, for (max = 100, i = len - baselen; i-- > 0;) max *= 10; - for (i = 0; bytes >= max && i < maxscale; i++) - bytes /= divisor; + for (i = 0; scalable >= max && i < maxscale; i++) + scalable /= divisor; if (scale & HN_GETSCALE) return (i); } else for (i = 0; i < scale && i < maxscale; i++) - bytes /= divisor; + scalable /= divisor; /* If a value <= 9.9 after rounding and ... */ - if (bytes < 995 && i > 0 && flags & HN_DECIMAL) { + if (scalable < 995 && i > 0 && flags & HN_DECIMAL) { /* baselen + \0 + .N */ if (len < baselen + 1 + 2) return (-1); - b = ((int)bytes + 5) / 10; + b = ((int)scalable + 5) / 10; s1 = b / 10; s2 = b % 10; - r = snprintf(buf, len, "%d%s%d%s%s%s", - sign * s1, localeconv()->decimal_point, s2, + r = snprintf(buf, len, "%s%d%s%d%s%s%s", + ((sign == -1) ? "-" : ""), + s1, localeconv()->decimal_point, s2, sep, SCALE2PREFIX(i), suffix); } else - r = snprintf(buf, len, "%lld%s%s%s", + r = snprintf(buf, len, "%s%lld%s%s%s", /* LONGLONG */ - (long long)(sign * ((bytes + 50) / 100)), + ((sign == -1) ? "-" : ""), + (long long)((scalable + 50) / 100), sep, SCALE2PREFIX(i), suffix); return (r); diff --git a/libutil.exports b/libutil.exports index 5da5c6f..36dc4a4 100644 --- a/libutil.exports +++ b/libutil.exports @@ -15,6 +15,7 @@ _property_find _realhostname _realhostname_sa _reexec_to_match_kernel +_reexec_to_match_lp64ness _trimdomain _uu_lock _uu_lock_txfr diff --git a/libutil.h b/libutil.h index c1a1bcd..0a5949a 100644 --- a/libutil.h +++ b/libutil.h @@ -40,6 +40,8 @@ #define _LIBUTIL_H_ #include +#include + #define PROPERTY_MAX_NAME 64 #define PROPERTY_MAX_VALUE 512 @@ -123,6 +125,7 @@ int pidfile_remove(struct pidfh *pfh); #endif int reexec_to_match_kernel(void); +int reexec_to_match_lp64ness(bool isLP64); __END_DECLS diff --git a/reexec_to_match_kernel.3 b/reexec_to_match_kernel.3 index df1c77d..fb20c50 100644 --- a/reexec_to_match_kernel.3 +++ b/reexec_to_match_kernel.3 @@ -12,6 +12,10 @@ .Fo reexec_to_match_kernel .Fa "void" .Fc +.Ft int +.Fo reexec_to_match_lp64ness +.Fa "bool isLP64" +.Fc .Sh DESCRIPTION The .Fn reexec_to_match_kernel @@ -20,10 +24,26 @@ That is, if the current kernel is a 64-bit Intel kernel, it will attempt to execute the 64-bit x86_64 userspace slice of the universal binary. The API intentionally does not take arguments because its use should be transparent to the program and to the user. +.Pp +The +.Fn reexec_to_match_lp64ness +is coarser-grained, and only attempts to match the word width that is requested. +For example, if the current system defaults to executing the 64-bit x86_64 +userspace slice, but the program should instead run in 32-bit i386 mode, +this routine can be used. +.Pp +Both +.Fn reexec_to_match_kernel +and +.Fn reexec_to_match_lp64ness +can each be used exactly once in a program's lifetime. In certain circumstances, +it may even be desirable to use one, and then the other. .Sh RETURN VALUES The .Fn reexec_to_match_kernel -function returns 0 if re-execution was not required. It returns -1 and +and +.Fn reexec_to_match_lp64ness +functions return 0 if re-execution was not required. It returns -1 and sets errno if there was an error performing the re-execution, for example if the binary is not universal, or does not contain a slice to match the running kernel's ABI. If the function succeeds, control never returns to the caller diff --git a/reexec_to_match_kernel.c b/reexec_to_match_kernel.c index a617c64..d510fbc 100644 --- a/reexec_to_match_kernel.c +++ b/reexec_to_match_kernel.c @@ -1,5 +1,5 @@ /* - * Copyright (c) 2008 Apple Inc. All rights reserved. + * Copyright (c) 2008-2010 Apple Inc. All rights reserved. * * @APPLE_LICENSE_HEADER_START@ * @@ -37,16 +37,17 @@ static cpu_type_t current_program_arch(void); static cpu_type_t current_kernel_arch(void); -static int reexec(cpu_type_t cputype); +static int reexec(cpu_type_t cputype, const char *guardenv); -#define kReExec "REEXEC_TO_MATCH_KERNEL" +#define kReExecToMatchKernel "REEXEC_TO_MATCH_KERNEL" +#define kReExecToMatchLP64 "REEXEC_TO_MATCH_LP64NESS" int reexec_to_match_kernel(void) { cpu_type_t kernarch, progarch; char *alreadyenv; - alreadyenv = getenv(kReExec); + alreadyenv = getenv(kReExecToMatchKernel); if (alreadyenv) { /* we've done this at least once, assume another try won't help */ @@ -68,7 +69,43 @@ int reexec_to_match_kernel(void) } /* Now we need to re-exec */ - return reexec(kernarch); + return reexec(kernarch, kReExecToMatchKernel); +} + +int reexec_to_match_lp64ness(bool isLP64) +{ + cpu_type_t kernarch, progarch, targetarch; + char *alreadyenv; + + alreadyenv = getenv(kReExecToMatchLP64); + if (alreadyenv) { + /* we've done this at least once, assume + another try won't help */ + return 0; + } + + kernarch = current_kernel_arch(); + progarch = current_program_arch(); + + if (kernarch == 0) { + /* could not determine kernel arch */ + errno = EINVAL; + return -1; + } + + if (isLP64) { + targetarch = kernarch | CPU_ARCH_ABI64; + } else { + targetarch = kernarch & ~CPU_ARCH_ABI64; + } + + if (targetarch == progarch) { + /* nothing to do here */ + return 0; + } + + /* Now we need to re-exec */ + return reexec(targetarch, kReExecToMatchLP64); } static cpu_type_t current_program_arch(void) @@ -114,7 +151,7 @@ static cpu_type_t current_kernel_arch(void) return current_arch; } -static int reexec(cpu_type_t cputype) +static int reexec(cpu_type_t cputype, const char *guardenv) { posix_spawnattr_t attr; int ret, envcount; @@ -122,6 +159,7 @@ static int reexec(cpu_type_t cputype) char **argv, **oldenvp, **newenvp; char execpath[MAXPATHLEN+1]; uint32_t execsize; + char guardstr[32]; argv = *_NSGetArgv(); oldenvp = *_NSGetEnviron(); @@ -132,7 +170,9 @@ static int reexec(cpu_type_t cputype) for (envcount = 0; oldenvp[envcount]; envcount++) { newenvp[envcount] = oldenvp[envcount]; } - newenvp[envcount++] = kReExec"=1"; + + snprintf(guardstr, sizeof(guardstr), "%s=1", guardenv); + newenvp[envcount++] = guardstr; newenvp[envcount] = NULL; execsize = (uint32_t)sizeof(execpath); @@ -154,15 +194,16 @@ static int reexec(cpu_type_t cputype) return -1; } - /* - fprintf(stderr, "reexec: %s\n", execpath); +#if 0 + fprintf(stderr, "reexec: %s (arch=%d)\n", execpath, cputype); for (envcount=0; newenvp[envcount]; envcount++) { fprintf(stderr, "env[%d] = %s\n", envcount, newenvp[envcount]); } for (envcount=0; argv[envcount]; envcount++) { fprintf(stderr, "argv[%d] = %s\n", envcount, argv[envcount]); } - */ +#endif + ret = posix_spawn(NULL, execpath, NULL, &attr, argv, newenvp); if (ret != 0) { errno = ret; diff --git a/wipefs.cpp b/wipefs.cpp index d5efc05..7b0857a 100644 --- a/wipefs.cpp +++ b/wipefs.cpp @@ -225,16 +225,21 @@ wipefs_wipe(wipefs_ctx handle) uint8_t *bufZero = NULL; ListExtIt curExt; size_t bufSize; - dk_discard_t discard; + dk_extent_t extent; + dk_unmap_t unmap; - memset(&discard, 0, sizeof(dk_discard_t)); - discard.length = handle->extMan.totalBytes; + memset(&extent, 0, sizeof(dk_extent_t)); + extent.length = handle->extMan.totalBytes; + + memset(&unmap, 0, sizeof(dk_unmap_t)); + unmap.extents = &extent; + unmap.extentsCount = 1; // // Don't bother to check the return value since this is mostly // informational for the lower-level drivers. // - ioctl(handle->fd, DKIOCDISCARD, (caddr_t)&discard); + ioctl(handle->fd, DKIOCUNMAP, (caddr_t)&unmap); bufSize = 256 * 1024; // issue large I/O to get better performance -- 2.45.2