[pkg-d-commits] [ldc] 05/211: Add the ldc-prune-cache stand-alone tool.

Matthias Klumpp mak at moszumanska.debian.org
Sun Apr 23 22:36:04 UTC 2017


This is an automated email from the git hooks/post-receive script.

mak pushed a commit to annotated tag v1.1.0
in repository ldc.

commit fa42d6e1c527267153111cb7f362ed043b6bc79b
Author: Johan Engelen <jbc.engelen at gmail.com>
Date:   Mon Sep 12 15:11:13 2016 +0200

    Add the ldc-prune-cache stand-alone tool.
---
 CMakeLists.txt                  |  7 ++-
 tests/CMakeLists.txt            | 11 ++---
 tests/lit.site.cfg.in           | 18 ++++----
 tests/tools/ldc_prune_cache_1.d | 46 +++++++++++++++++++
 tools/CMakeLists.txt            | 46 +++++++++++++++++++
 tools/ldc-prune-cache.d         | 99 +++++++++++++++++++++++++++++++++++++++++
 6 files changed, 213 insertions(+), 14 deletions(-)

diff --git a/CMakeLists.txt b/CMakeLists.txt
index daeab2e..a9c0100 100644
--- a/CMakeLists.txt
+++ b/CMakeLists.txt
@@ -665,11 +665,16 @@ build_d_executable(
 
 
 #
-# Auxiliary tools.
+# Auxiliary build and test utils.
 #
 add_subdirectory(utils)
 
 #
+# Auxiliary tools.
+#
+add_subdirectory(tools)
+
+#
 # Test and runtime targets. Note that enable_testing() is order-sensitive!
 #
 enable_testing()
diff --git a/tests/CMakeLists.txt b/tests/CMakeLists.txt
index 8948e2c..6b6fa56 100644
--- a/tests/CMakeLists.txt
+++ b/tests/CMakeLists.txt
@@ -1,8 +1,9 @@
-set( LDC2_BIN        ${PROJECT_BINARY_DIR}/bin/${LDC_EXE}  )
-set( LDCPROFDATA_BIN ${PROJECT_BINARY_DIR}/bin/${LDCPROFDATA_EXE} )
-set( LLVM_TOOLS_DIR  ${LLVM_ROOT_DIR}/bin                  )
-set( LDC2_BIN_DIR    ${PROJECT_BINARY_DIR}/bin             )
-set( TESTS_IR_DIR    ${CMAKE_CURRENT_SOURCE_DIR}           )
+set( LDC2_BIN          ${PROJECT_BINARY_DIR}/bin/${LDC_EXE} )
+set( LDCPROFDATA_BIN   ${PROJECT_BINARY_DIR}/bin/${LDCPROFDATA_EXE} )
+set( LDCPRUNECACHE_BIN ${PROJECT_BINARY_DIR}/bin/${LDCPRUNECACHE_EXE} )
+set( LLVM_TOOLS_DIR    ${LLVM_ROOT_DIR}/bin )
+set( LDC2_BIN_DIR      ${PROJECT_BINARY_DIR}/bin )
+set( TESTS_IR_DIR      ${CMAKE_CURRENT_SOURCE_DIR} )
 
 if(CMAKE_SIZEOF_VOID_P EQUAL 8)
     set( DEFAULT_TARGET_BITS 64 )
diff --git a/tests/lit.site.cfg.in b/tests/lit.site.cfg.in
index 7815fba..a47558e 100644
--- a/tests/lit.site.cfg.in
+++ b/tests/lit.site.cfg.in
@@ -5,15 +5,16 @@ import platform
 import string
 
 ## Auto-initialized variables by cmake:
-config.ldc2_bin         = "@LDC2_BIN@"
-config.ldcprofdata_bin  = "@LDCPROFDATA_BIN@"
-config.ldc2_bin_dir     = "@LDC2_BIN_DIR@"
-config.test_source_root = "@TESTS_IR_DIR@"
-config.llvm_tools_dir   = "@LLVM_TOOLS_DIR@"
-config.llvm_version     = @LDC_LLVM_VER@
-config.llvm_targetsstr  = "@LLVM_TARGETS_TO_BUILD@"
+config.ldc2_bin            = "@LDC2_BIN@"
+config.ldcprofdata_bin     = "@LDCPROFDATA_BIN@"
+config.ldcprunecache_bin   = "@LDCPRUNECACHE_BIN@"
+config.ldc2_bin_dir        = "@LDC2_BIN_DIR@"
+config.test_source_root    = "@TESTS_IR_DIR@"
+config.llvm_tools_dir      = "@LLVM_TOOLS_DIR@"
+config.llvm_version        = @LDC_LLVM_VER@
+config.llvm_targetsstr     = "@LLVM_TARGETS_TO_BUILD@"
 config.default_target_bits = @DEFAULT_TARGET_BITS@
-config.with_PGO         = @LDC_WITH_PGO@
+config.with_PGO            = @LDC_WITH_PGO@
 
 config.name = 'LDC'
 
@@ -86,6 +87,7 @@ config.environment['PATH'] = path
 # Add substitutions
 config.substitutions.append( ('%ldc', config.ldc2_bin) )
 config.substitutions.append( ('%profdata', config.ldcprofdata_bin) )
+config.substitutions.append( ('%prunecache', config.ldcprunecache_bin) )
 
 # Add platform-dependent file extension substitutions
 if (platform.system() == 'Windows'):
diff --git a/tests/tools/ldc_prune_cache_1.d b/tests/tools/ldc_prune_cache_1.d
new file mode 100644
index 0000000..f3a9ebc
--- /dev/null
+++ b/tests/tools/ldc_prune_cache_1.d
@@ -0,0 +1,46 @@
+// Test ldc-cache-prune tool
+
+// This test assumes that the `void main(){}` object file size is below 200_000 bytes and above 200_000/2,
+// such that rebuilding with version(NEW_OBJ_FILE) will clear the cache of all but the latest object file.
+
+// RUN: %ldc %s -ir2obj-cache=%T/tempcache1 \
+// RUN: && %ldc %s -ir2obj-cache=%T/tempcache1 -d-version=SLEEP \
+// RUN: && %prunecache -f %T/tempcache1 \
+// RUN: && %ldc %s -ir2obj-cache=%T/tempcache1 -vv | FileCheck --check-prefix=MUST_HIT %s \
+// RUN: && %ldc %s -ir2obj-cache=%T/tempcache1 -vv -d-version=NEW_OBJ_FILE | FileCheck --check-prefix=NO_HIT %s \
+// RUN: && %prunecache %T/tempcache1 -f \
+// RUN: && %ldc %s -ir2obj-cache=%T/tempcache1 -vv | FileCheck --check-prefix=MUST_HIT %s \
+// RUN: && %ldc -d-version=SLEEP -run %s \
+// RUN: && %ldc %s -c -of=%t%obj -ir2obj-cache=%T/tempcache1 -vv | FileCheck --check-prefix=MUST_HIT %s \
+// RUN: && %prunecache --force --max-bytes=200000 %T/tempcache1 \
+// RUN: && %ldc %t%obj \
+// RUN: && %ldc %s -ir2obj-cache=%T/tempcache1 -d-version=SLEEP -vv | FileCheck --check-prefix=NO_HIT %s \
+// RUN: && %ldc -d-version=SLEEP -run %s \
+// RUN: && %ldc %s -ir2obj-cache=%T/tempcache1 -d-version=NEW_OBJ_FILE \
+// RUN: && %prunecache --interval=0 %T/tempcache1 --max-bytes=200000 \
+// RUN: && %ldc %s -ir2obj-cache=%T/tempcache1 -vv | FileCheck --check-prefix=NO_HIT %s \
+// RUN: && %ldc -d-version=SLEEP -run %s \
+// RUN: && %ldc -d-version=SLEEP -run %s \
+// RUN: && %prunecache %T/tempcache1 -f --expiry=2  \
+// RUN: && %ldc %s -ir2obj-cache=%T/tempcache1 -vv | FileCheck --check-prefix=NO_HIT %s
+
+// MUST_HIT: Cache object found!
+// NO_HIT-NOT: Cache object found!
+
+void main()
+{
+    // Add non-zero static data to guarantee a binary size larger than 200_000/2.
+    static byte[120_000] dummy = 1;
+
+    version (NEW_OBJ_FILE)
+    {
+        auto a = __TIME__;
+    }
+
+    version (SLEEP)
+    {
+        // Sleep for 2 seconds, so we are sure that the cache object file timestamps are "aging".
+        import core.thread;
+        Thread.sleep( dur!"seconds"(2) );
+    }
+}
diff --git a/tools/CMakeLists.txt b/tools/CMakeLists.txt
new file mode 100644
index 0000000..a78132a
--- /dev/null
+++ b/tools/CMakeLists.txt
@@ -0,0 +1,46 @@
+# "tools" are supposed to be packaged with LDC.
+# (in contrast to "utils" which are only used for building / testing)
+
+# Set tool names
+set(LDCPRUNECACHE_EXE ldc-prune-cache)
+set(LDCPRUNECACHE_EXE ${LDCPRUNECACHE_EXE} PARENT_SCOPE) # needed for correctly populating lit.site.cfg.in
+set(LDCPRUNECACHE_EXE_NAME ${PROGRAM_PREFIX}${LDCPRUNECACHE_EXE}${PROGRAM_SUFFIX})
+set(LDCPRUNECACHE_EXE_FULL ${PROJECT_BINARY_DIR}/bin/${LDCPRUNECACHE_EXE_NAME}${CMAKE_EXECUTABLE_SUFFIX})
+
+function(build_d_tool output_exe compiler_args linker_args compile_deps link_deps)
+    set(dflags "${D_COMPILER_FLAGS} ${DDMD_DFLAGS}")
+    set(lflags "")
+    if(UNIX)
+      separate_arguments(dflags UNIX_COMMAND "${dflags}")
+      separate_arguments(lflags UNIX_COMMAND "${lflags}")
+    else()
+      separate_arguments(dflags WINDOWS_COMMAND "${dflags}")
+      separate_arguments(lflags WINDOWS_COMMAND "${lflags}")
+    endif()
+    foreach(f ${linker_args})
+        append("-L\"${f}\"" lflags)
+    endforeach()
+    add_custom_command(
+        OUTPUT ${output_exe}
+        COMMAND ${D_COMPILER} ${dflags} ${lflags} -I${PROJECT_SOURCE_DIR}/${DDMDFE_PATH} -of${output_exe} ${compiler_args} ${linker_args}
+        WORKING_DIRECTORY ${PROJECT_SOURCE_DIR}
+        DEPENDS ${compile_deps} ${link_deps}
+    )
+endfunction()
+
+# Build ldc-prune-cache
+add_custom_target(${LDCPRUNECACHE_EXE} ALL DEPENDS ${LDCPRUNECACHE_EXE_FULL})
+set(LDCPRUNECACHE_D_SRC
+    ${PROJECT_SOURCE_DIR}/tools/ldc-prune-cache.d
+    ${PROJECT_SOURCE_DIR}/driver/ir2obj_cache_pruning.d
+)
+build_d_tool(
+    "${LDCPRUNECACHE_EXE_FULL}"
+    "${LDCPRUNECACHE_D_SRC}"
+    ""
+    "${LDCPRUNECACHE_D_SRC}"
+    ""
+)
+
+# Install the tools
+install(PROGRAMS ${LDCPRUNECACHE_EXE_FULL} DESTINATION ${CMAKE_INSTALL_PREFIX}/bin)
diff --git a/tools/ldc-prune-cache.d b/tools/ldc-prune-cache.d
new file mode 100644
index 0000000..9963972
--- /dev/null
+++ b/tools/ldc-prune-cache.d
@@ -0,0 +1,99 @@
+//===-- tools/ldc-prune-cache.d -----------------------------------*- D -*-===//
+//
+//                         LDC – the LLVM D compiler
+//
+// This file is distributed under the BSD-style LDC license. See the LICENSE
+// file for details.
+//
+//===----------------------------------------------------------------------===//
+//
+// Prunes the ir2obj cache.
+//
+// TODO: Let the commandline parameters accept units, e.g.
+//       `--interval=30m`, or `--max-bytes=5GB`.
+//
+//===----------------------------------------------------------------------===//
+
+module ldc_prune_cache;
+
+import std.stdio;
+import std.getopt;
+import std.file: isDir;
+
+import driver.ir2obj_cache_pruning;
+
+// System exit codes:
+enum EX_OK = 0;
+enum EX_USAGE = 64;
+
+int main(string[] args)
+{
+    bool force, showHelp, error;
+    uint pruneIntervalSeconds = 20 * 60;
+    uint expireIntervalSeconds = 7 * 24 * 3600;
+    ulong sizeLimitBytes = 0;
+    uint sizeLimitPercentage = 75;
+
+    try
+    {
+        getopt(args,
+            "f|force", &force,
+            "h|help", &showHelp,
+            "interval", &pruneIntervalSeconds,
+            "expiry", &expireIntervalSeconds,
+            "max-bytes", &sizeLimitBytes,
+            "max-percentage-of-avail", &sizeLimitPercentage
+        );
+    }
+    catch(Exception e)
+    {
+        stderr.writeln(e.msg);
+        stderr.writeln();
+        args.length = 1; // Force display of help message.
+    }
+
+    if (showHelp || args.length != 2)
+    {
+        stderr.writef(q"EOS
+OVERVIEW: LDC-PRUNE-CACHE
+  Prunes the LDC's object file cache to prevent the cache growing infinitely.
+  When a minimum pruning interval has passed (--interval), the following
+  pruning scheme is executed:
+  1. remove cached files that have passed the expiry duration (--expiry);
+  2. remove cached files (oldest first) until the total cache size is below a
+     set limit (--max-bytes, --max-percentage-of-avail).
+
+USAGE: ldc-prune-cache [OPTION]... PATH
+  PATH should be a directory where LDC has placed its object files cache (see
+  LDC's --ir2obj-cache option).
+
+OPTIONS:
+  --expiration=<dur>     Sets the pruning expiration time of cache files to
+                         <duration> seconds (default: 1 week).
+  -f, --force            Force pruning, ignoring the prune interval.
+  -h, --help             Show this message.
+  --interval=<dur>       Sets the cache pruning interval to <duration> seconds
+                         (default: 20 min). Set to 0 to force pruning, see -f.
+  --max-bytes=<size>     Sets the cache size absolute limit to <size> bytes
+                         (default: no absolute limit).
+  --max-percentage-of-avail=<perc>
+                         Sets the cache size limit to <perc> percent of the
+                         available disk space (default 75%%).
+EOS");
+        return showHelp ? EX_OK : EX_USAGE;
+    }
+
+    string cacheDirectory = args[1];
+    if (!isDir(cacheDirectory))
+    {
+        stderr.write("PATH must be a directory.");
+        return EX_USAGE;
+    }
+
+    auto pruner = CachePruner(cacheDirectory,
+        force ? 0 : pruneIntervalSeconds, expireIntervalSeconds, sizeLimitBytes, sizeLimitPercentage);
+
+    pruner.doPrune();
+
+    return EX_OK;
+}

-- 
Alioth's /usr/local/bin/git-commit-notice on /srv/git.debian.org/git/pkg-d/ldc.git



More information about the pkg-d-commits mailing list